diff --git a/notebooks/train-yolov5-object-detection-on-custom-data.ipynb b/notebooks/train-yolov5-object-detection-on-custom-data.ipynb
index 7681142..9ba952d 100644
--- a/notebooks/train-yolov5-object-detection-on-custom-data.ipynb
+++ b/notebooks/train-yolov5-object-detection-on-custom-data.ipynb
@@ -6,8 +6,12 @@
"id": "GD9gUQpaBxNa"
},
"source": [
+ "[![Roboflow Notebooks](https://media.roboflow.com/notebooks/template/bannertest2-2.png?ik-sdk-version=javascript-1.4.3&updatedAt=1672932710194)](https://github.com/roboflow/notebooks)\n",
+ "\n",
"# How to Train YOLOv5 on Custom Objects\n",
"\n",
+ "**⚠️ This notebook was updated on October 24th, 2023. Since then, the way to load data into the notebook has changed. Thus, this notebook is not the same as the original version used in the accompanying YouTube video or blog post.**\n",
+ "\n",
"This tutorial is based on the [YOLOv5 repository](https://github.com/ultralytics/yolov5) by [Ultralytics](https://www.ultralytics.com/). This notebook shows training on **your own custom objects**. Many thanks to Ultralytics for putting this repository together - we hope that in combination with clean data management tools at Roboflow, this technologoy will become easily accessible to any developer wishing to use computer vision in their projects.\n",
"\n",
"### Accompanying Blog Post\n",
@@ -29,16 +33,7 @@
"* Run YOLOv5 inference on test images\n",
"* Export saved YOLOv5 weights for future inference\n",
"\n",
- "\n",
- "\n",
- "### **About**\n",
- "\n",
- "[Roboflow](https://roboflow.com) enables teams to deploy custom computer vision models quickly and accurately. Convert data from to annotation format, assess dataset health, preprocess, augment, and more. It's free for your first 1000 source images.\n",
- "\n",
- "**Looking for a vision model available via API without hassle? Try Roboflow Train.**\n",
- "\n",
- "![Roboflow Wordmark](https://i.imgur.com/dcLNMhV.png)\n",
- "\n"
+ "Let's get started!"
]
},
{
@@ -54,31 +49,31 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 1,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "Ie5uLDH4uzAp",
- "outputId": "d2e38392-e09e-4caf-e309-72b5354a5c9b",
+ "outputId": "5aaf0b1c-4892-46ea-9273-9a22994dfb20",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
"output_type": "stream",
+ "name": "stdout",
"text": [
"Cloning into 'yolov5'...\n",
- "remote: Enumerating objects: 12811, done.\u001b[K\n",
- "remote: Counting objects: 100% (92/92), done.\u001b[K\n",
- "remote: Compressing objects: 100% (48/48), done.\u001b[K\n",
- "remote: Total 12811 (delta 52), reused 75 (delta 44), pack-reused 12719\u001b[K\n",
- "Receiving objects: 100% (12811/12811), 12.40 MiB | 21.02 MiB/s, done.\n",
- "Resolving deltas: 100% (8807/8807), done.\n",
+ "remote: Enumerating objects: 16013, done.\u001b[K\n",
+ "remote: Counting objects: 100% (46/46), done.\u001b[K\n",
+ "remote: Compressing objects: 100% (33/33), done.\u001b[K\n",
+ "remote: Total 16013 (delta 25), reused 23 (delta 13), pack-reused 15967\u001b[K\n",
+ "Receiving objects: 100% (16013/16013), 14.68 MiB | 17.18 MiB/s, done.\n",
+ "Resolving deltas: 100% (10991/10991), done.\n",
"/content/yolov5\n",
- "HEAD is now at fbe67e4 Fix `OMP_NUM_THREADS=1` for macOS (#8624)\n"
+ "HEAD is now at 064365d Update parse_opt() in export.py to work as in train.py (#10789)\n"
]
}
],
@@ -91,24 +86,26 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 2,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "wbvMlHd_QwMG",
- "outputId": "484dd5f5-a33e-4e56-ac20-10dc71b36009",
+ "outputId": "04bf61dc-0730-422e-cf30-481ece54b934",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
"output_type": "stream",
+ "name": "stdout",
"text": [
- "\u001b[?25l\r\u001b[K |▌ | 10 kB 20.4 MB/s eta 0:00:01\r\u001b[K |█ | 20 kB 9.2 MB/s eta 0:00:01\r\u001b[K |█▋ | 30 kB 7.9 MB/s eta 0:00:01\r\u001b[K |██▏ | 40 kB 7.4 MB/s eta 0:00:01\r\u001b[K |██▊ | 51 kB 4.5 MB/s eta 0:00:01\r\u001b[K |███▎ | 61 kB 5.4 MB/s eta 0:00:01\r\u001b[K |███▉ | 71 kB 4.5 MB/s eta 0:00:01\r\u001b[K |████▍ | 81 kB 5.1 MB/s eta 0:00:01\r\u001b[K |█████ | 92 kB 5.7 MB/s eta 0:00:01\r\u001b[K |█████▌ | 102 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████ | 112 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████▋ | 122 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████▏ | 133 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████▊ | 143 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████▎ | 153 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████▉ | 163 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████▍ | 174 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████ | 184 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████▍ | 194 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████ | 204 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████▌ | 215 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████ | 225 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████▋ | 235 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████▏ | 245 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████▊ | 256 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████▎ | 266 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████▉ | 276 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████▍ | 286 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████ | 296 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████▌ | 307 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████ | 317 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████▋ | 327 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████▏ | 337 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████▊ | 348 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████▎ | 358 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████▉ | 368 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████▍ | 378 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████▉ | 389 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████████▍ | 399 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████████ | 409 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████████▌ | 419 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████ | 430 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████▋ | 440 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████████▏ | 450 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████████▊ | 460 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████████████▎ | 471 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████████████▉ | 481 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████████████▍ | 491 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████████ | 501 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████████▌ | 512 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████████████ | 522 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████████████▋ | 532 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████████████████▏ | 542 kB 5.0 MB/s eta 0:00:01\r\u001b[K |█████████████████████████████▊ | 552 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████████████████▎ | 563 kB 5.0 MB/s eta 0:00:01\r\u001b[K |██████████████████████████████▊ | 573 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████████████▎| 583 kB 5.0 MB/s eta 0:00:01\r\u001b[K |███████████████████████████████▉| 593 kB 5.0 MB/s eta 0:00:01\r\u001b[K |████████████████████████████████| 596 kB 5.0 MB/s \n",
- "\u001b[?25hSetup complete. Using torch 1.12.0+cu113 _CudaDeviceProperties(name='Tesla P100-PCIE-16GB', major=6, minor=0, total_memory=16280MB, multi_processor_count=56)\n"
+ "\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m190.6/190.6 kB\u001b[0m \u001b[31m5.0 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
+ "\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m62.7/62.7 kB\u001b[0m \u001b[31m7.4 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
+ "\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m1.6/1.6 MB\u001b[0m \u001b[31m13.9 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
+ "\u001b[?25hSetup complete. Using torch 2.1.0+cu118 _CudaDeviceProperties(name='Tesla T4', major=7, minor=5, total_memory=15101MB, multi_processor_count=40)\n"
]
}
],
@@ -130,11 +127,73 @@
"id": "SDIhrBF0sPaM"
},
"source": [
- "# Download Correctly Formatted Custom Dataset \n",
+ "## Roboflow Universe\n",
+ "\n",
+ "Need data for your project? Before spending time on annotating, check out Roboflow Universe, a repository of more than 200,000 open-source datasets that you can use in your projects. You'll find datasets containing everything from annotated cracks in concrete to plant images with disease annotations.\n",
+ "\n",
+ "\n",
+ "[![Roboflow Universe](https://media.roboflow.com/notebooks/template/uni-banner-frame.png?ik-sdk-version=javascript-1.4.3&updatedAt=1672878480290)](https://universe.roboflow.com/)\n",
+ "\n",
+ "## Preparing a custom dataset\n",
+ "\n",
+ "Building a custom dataset can be a painful process. It might take dozens or even hundreds of hours to collect images, label them, and export them in the proper format. Fortunately, Roboflow makes this process as straightforward and fast as possible. Let me show you how!\n",
+ "\n",
+ "### Step 1: Creating project\n",
+ "\n",
+ "Before you start, you need to create a Roboflow [account](https://app.roboflow.com/login). Once you do that, you can create a new project in the Roboflow [dashboard](https://app.roboflow.com/). Keep in mind to choose the right project type. In our case, Object Detection.\n",
+ "\n",
+ "
\n",
+ "
\n",
+ "
\n",
+ "\n",
+ "### Step 2: Uploading images\n",
+ "\n",
+ "Next, add the data to your newly created project. You can do it via API or through our [web interface](https://docs.roboflow.com/adding-data/object-detection).\n",
+ "\n",
+ "If you drag and drop a directory with a dataset in a supported format, the Roboflow dashboard will automatically read the images and annotations together.\n",
"\n",
- "We'll download our dataset from Roboflow. Use the \"**YOLOv5 PyTorch**\" export format. Note that the Ultralytics implementation calls for a YAML file defining where your training and test data is. The Roboflow export also writes this format for us.\n",
+ "\n",
+ "
\n",
+ "
\n",
"\n",
- "To get your data into Roboflow, follow the [Getting Started Guide](https://blog.roboflow.ai/getting-started-with-roboflow/)."
+ "### Step 3: Labeling\n",
+ "\n",
+ "If you only have images, you can label them in [Roboflow Annotate](https://docs.roboflow.com/annotate).\n",
+ "\n",
+ "\n",
+ "
\n",
+ "
\n",
+ "\n",
+ "### Step 4: Generate new dataset version\n",
+ "\n",
+ "Now that we have our images and annotations added, we can Generate a Dataset Version. When Generating a Version, you may elect to add preprocessing and augmentations. This step is completely optional, however, it can allow you to significantly improve the robustness of your model.\n",
+ "\n",
+ "\n",
+ "
\n",
+ "
\n",
+ "\n",
+ "### Step 5: Exporting dataset\n",
+ "\n",
+ "Once the dataset version is generated, we have a hosted dataset we can load directly into our notebook for easy training. Click `Export` and select the `YOLO v5 PyTorch` dataset format.\n",
+ "\n",
+ "\n",
+ "
\n",
+ "
\n"
]
},
{
@@ -143,119 +202,131 @@
"id": "vDeebwqS9JbZ"
},
"source": [
+ "## Step 6: Download a Dataset\n",
"\n",
- "\n",
- "![YOLOv5 PyTorch export](https://i.imgur.com/5vr9G2u.png)\n"
+ "Add your Roboflow API key below to download the default money counting dataset. Alternatively, use the code provided by the Roboflow dashboard in the above step to load a custom dataset."
]
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 5,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "Knxi2ncxWffW",
- "outputId": "d4d0155d-63c9-4c2c-a63e-a553ecbef611",
+ "outputId": "067d051c-9ae6-4cf0-db2e-fac32b2df01a",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
+ "output_type": "stream",
"name": "stdout",
+ "text": [
+ "loading Roboflow workspace...\n",
+ "loading Roboflow project...\n"
+ ]
+ },
+ {
"output_type": "stream",
+ "name": "stderr",
+ "text": [
+ "Downloading Dataset Version Zip in Cash-Counter-10 to yolov5pytorch:: 100%|██████████| 121603/121603 [00:02<00:00, 59447.22it/s]"
+ ]
+ },
+ {
+ "output_type": "stream",
+ "name": "stdout",
"text": [
- "\u001b[K |████████████████████████████████| 178 kB 7.6 MB/s \n",
- "\u001b[K |████████████████████████████████| 21.6 MB 1.2 MB/s \n",
- "\u001b[K |████████████████████████████████| 54 kB 2.8 MB/s \n",
- "\u001b[K |████████████████████████████████| 67 kB 6.4 MB/s \n",
- "\u001b[K |████████████████████████████████| 1.1 MB 68.0 MB/s \n",
- "\u001b[K |████████████████████████████████| 145 kB 72.2 MB/s \n",
- "\u001b[K |████████████████████████████████| 4.3 MB 55.6 MB/s \n",
- "\u001b[K |████████████████████████████████| 138 kB 68.1 MB/s \n",
- "\u001b[K |████████████████████████████████| 62 kB 1.7 MB/s \n",
- "\u001b[?25h Building wheel for wget (setup.py) ... \u001b[?25l\u001b[?25hdone\n",
- "\u001b[31mERROR: pip's dependency resolver does not currently take into account all the packages that are installed. This behaviour is the source of the following dependency conflicts.\n",
- "google-colab 1.0.0 requires requests~=2.23.0, but you have requests 2.28.1 which is incompatible.\n",
- "datascience 0.10.6 requires folium==0.2.1, but you have folium 0.8.3 which is incompatible.\n",
- "albumentations 0.1.12 requires imgaug<0.2.7,>=0.2.5, but you have imgaug 0.2.9 which is incompatible.\u001b[0m\n",
- "upload and label your dataset, and get an API KEY here: https://app.roboflow.com/?model=yolov5&ref=roboflow-yolov5\n"
+ "\n"
+ ]
+ },
+ {
+ "output_type": "stream",
+ "name": "stderr",
+ "text": [
+ "\n",
+ "Extracting Dataset Version Zip to Cash-Counter-10 in yolov5pytorch:: 100%|██████████| 6112/6112 [00:00<00:00, 7450.91it/s]\n"
]
}
],
"source": [
- "#follow the link below to get your download code from from Roboflow\n",
"!pip install -q roboflow\n",
+ "\n",
"from roboflow import Roboflow\n",
- "rf = Roboflow(model_format=\"yolov5\", notebook=\"roboflow-yolov5\")"
+ "\n",
+ "rf = Roboflow(api_key=\"YOUR_API_KEY\")\n",
+ "project = rf.workspace(\"alex-hyams-cosqx\").project(\"cash-counter\")\n",
+ "dataset = project.version(10).download(\"yolov5\")"
]
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 6,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "Ug_PhK1oqwQA",
- "outputId": "b417162b-c116-416c-88e8-96b2563d1ee1",
+ "outputId": "3807a1b7-0e6b-4c1b-c1bc-f2d32d626811",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
- "output_type": "stream",
- "text": [
- "/content/yolov5\n",
- "loading Roboflow workspace...\n",
- "loading Roboflow project...\n",
- "Downloading Dataset Version Zip in American-Mushrooms-1 to yolov5pytorch: 100% [3866359 / 3866359] bytes\n"
- ]
- },
- {
- "name": "stderr",
"output_type": "stream",
+ "name": "stdout",
"text": [
- "Extracting Dataset Version Zip to American-Mushrooms-1 in yolov5pytorch:: 100%|██████████| 278/278 [00:00<00:00, 1111.85it/s]\n"
+ "/content/yolov5\n"
]
}
],
"source": [
- "%cd /content/yolov5\n",
- "#after following the link above, recieve python code with these fields filled in\n",
- "#from roboflow import Roboflow\n",
- "#rf = Roboflow(api_key=\"YOUR API KEY HERE\")\n",
- "#project = rf.workspace().project(\"YOUR PROJECT\")\n",
- "#dataset = project.version(\"YOUR VERSION\").download(\"yolov5\")"
+ "%cd /content/yolov5"
]
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 7,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "ZZ3DmmGQztJj",
- "outputId": "895f8313-8441-4c2d-9c87-01cc89f22acb",
+ "outputId": "b710c5de-9fd6-4ca7-8053-de3b5bdae0c6",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
"output_type": "stream",
+ "name": "stdout",
"text": [
"names:\n",
- "- CoW\n",
- "- chanterelle\n",
- "nc: 2\n",
- "train: American-Mushrooms-1/train/images\n",
- "val: American-Mushrooms-1/valid/images\n"
+ "- Dime\n",
+ "- Nickel\n",
+ "- Penny\n",
+ "- Quarter\n",
+ "- fifty\n",
+ "- five\n",
+ "- hundred\n",
+ "- one\n",
+ "- ten\n",
+ "- twenty\n",
+ "nc: 10\n",
+ "roboflow:\n",
+ " license: CC BY 4.0\n",
+ " project: cash-counter\n",
+ " url: https://universe.roboflow.com/alex-hyams-cosqx/cash-counter/dataset/10\n",
+ " version: 10\n",
+ " workspace: alex-hyams-cosqx\n",
+ "test: ../test/images\n",
+ "train: Cash-Counter-10/train/images\n",
+ "val: Cash-Counter-10/valid/images\n"
]
}
],
@@ -279,7 +350,7 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 8,
"metadata": {
"id": "dOPn9wjOAwwK",
"vscode": {
@@ -296,49 +367,49 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 9,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "1Rvt5wilnDyX",
- "outputId": "8b8386bc-0e05-49a8-c1e0-48a836a0b399",
+ "outputId": "717ac830-0313-4132-cd38-7bbebec1d695",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
"output_type": "stream",
+ "name": "stdout",
"text": [
- "# parameters\n",
+ "# YOLOv5 🚀 by Ultralytics, GPL-3.0 license\n",
+ "\n",
+ "# Parameters\n",
"nc: 80 # number of classes\n",
"depth_multiple: 0.33 # model depth multiple\n",
"width_multiple: 0.50 # layer channel multiple\n",
- "\n",
- "# anchors\n",
"anchors:\n",
" - [10,13, 16,30, 33,23] # P3/8\n",
" - [30,61, 62,45, 59,119] # P4/16\n",
" - [116,90, 156,198, 373,326] # P5/32\n",
"\n",
- "# YOLOv5 backbone\n",
+ "# YOLOv5 v6.0 backbone\n",
"backbone:\n",
" # [from, number, module, args]\n",
- " [[-1, 1, Focus, [64, 3]], # 0-P1/2\n",
+ " [[-1, 1, Conv, [64, 6, 2, 2]], # 0-P1/2\n",
" [-1, 1, Conv, [128, 3, 2]], # 1-P2/4\n",
" [-1, 3, C3, [128]],\n",
" [-1, 1, Conv, [256, 3, 2]], # 3-P3/8\n",
- " [-1, 9, C3, [256]],\n",
+ " [-1, 6, C3, [256]],\n",
" [-1, 1, Conv, [512, 3, 2]], # 5-P4/16\n",
" [-1, 9, C3, [512]],\n",
" [-1, 1, Conv, [1024, 3, 2]], # 7-P5/32\n",
- " [-1, 1, SPP, [1024, [5, 9, 13]]],\n",
- " [-1, 3, C3, [1024, False]], # 9\n",
+ " [-1, 3, C3, [1024]],\n",
+ " [-1, 1, SPPF, [1024, 5]], # 9\n",
" ]\n",
"\n",
- "# YOLOv5 head\n",
+ "# YOLOv5 v6.0 head\n",
"head:\n",
" [[-1, 1, Conv, [512, 1, 1]],\n",
" [-1, 1, nn.Upsample, [None, 2, 'nearest']],\n",
@@ -364,13 +435,13 @@
}
],
"source": [
- "#this is the model configuration we will use for our tutorial \n",
+ "#this is the model configuration we will use for our tutorial\n",
"%cat /content/yolov5/models/yolov5s.yaml"
]
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 10,
"metadata": {
"id": "t14hhyqdmw6O",
"vscode": {
@@ -390,7 +461,7 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 11,
"metadata": {
"id": "uDxebz13RdRA",
"vscode": {
@@ -476,39 +547,48 @@
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 12,
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "1NcFxRcFdJ_O",
- "outputId": "84614320-0d9c-40c2-dbef-a2c121ab667b",
+ "outputId": "5d81137a-2d31-42a7-e0a4-b0675337ef96",
"vscode": {
"languageId": "python"
}
},
"outputs": [
{
- "name": "stdout",
"output_type": "stream",
+ "name": "stdout",
"text": [
"/content/yolov5\n",
- "\u001b[34m\u001b[1mgithub: \u001b[0m⚠️ WARNING: code is out of date by 577 commits. Use 'git pull' to update or 'git clone https://github.com/ultralytics/yolov5' to download latest.\n",
- "YOLOv5 v4.0-126-g886f1c0 torch 1.9.0+cu111 CUDA:0 (Tesla P100-PCIE-16GB, 16280.875MB)\n",
+ "2023-10-24 10:18:27.283913: E tensorflow/compiler/xla/stream_executor/cuda/cuda_dnn.cc:9342] Unable to register cuDNN factory: Attempting to register factory for plugin cuDNN when one has already been registered\n",
+ "2023-10-24 10:18:27.283968: E tensorflow/compiler/xla/stream_executor/cuda/cuda_fft.cc:609] Unable to register cuFFT factory: Attempting to register factory for plugin cuFFT when one has already been registered\n",
+ "2023-10-24 10:18:27.284008: E tensorflow/compiler/xla/stream_executor/cuda/cuda_blas.cc:1518] Unable to register cuBLAS factory: Attempting to register factory for plugin cuBLAS when one has already been registered\n",
+ "2023-10-24 10:18:27.291751: I tensorflow/core/platform/cpu_feature_guard.cc:182] This TensorFlow binary is optimized to use available CPU instructions in performance-critical operations.\n",
+ "To enable the following instructions: AVX2 AVX512F FMA, in other operations, rebuild TensorFlow with the appropriate compiler flags.\n",
+ "2023-10-24 10:18:28.448223: W tensorflow/compiler/tf2tensorrt/utils/py_utils.cc:38] TF-TRT Warning: Could not find TensorRT\n",
+ "\u001b[34m\u001b[1mtrain: \u001b[0mweights=, cfg=./models/custom_yolov5s.yaml, data=/content/yolov5/Cash-Counter-10/data.yaml, hyp=data/hyps/hyp.scratch-low.yaml, epochs=100, batch_size=16, imgsz=416, rect=False, resume=False, nosave=False, noval=False, noautoanchor=False, noplots=False, evolve=None, bucket=, cache=ram, image_weights=False, device=, multi_scale=False, single_cls=False, optimizer=SGD, sync_bn=False, workers=8, project=runs/train, name=yolov5s_results, exist_ok=False, quad=False, cos_lr=False, label_smoothing=0.0, patience=100, freeze=[0], save_period=-1, seed=0, local_rank=-1, entity=None, upload_dataset=False, bbox_interval=-1, artifact_alias=latest\n",
+ "\u001b[34m\u001b[1mgithub: \u001b[0m⚠️ YOLOv5 is out of date by 156 commits. Use `git pull` or `git clone https://github.com/ultralytics/yolov5` to update.\n",
+ "YOLOv5 🚀 v7.0-72-g064365d Python-3.10.12 torch-2.1.0+cu118 CUDA:0 (Tesla T4, 15102MiB)\n",
"\n",
- "Namespace(adam=False, batch_size=16, bucket='', cache_images=True, cfg='./models/custom_yolov5s.yaml', data='/content/yolov5/American-Mushrooms-1/data.yaml', device='', entity=None, epochs=100, evolve=False, exist_ok=False, global_rank=-1, hyp='data/hyp.scratch.yaml', image_weights=False, img_size=[416, 416], linear_lr=False, local_rank=-1, log_artifacts=False, log_imgs=16, multi_scale=False, name='yolov5s_results', noautoanchor=False, nosave=False, notest=False, project='runs/train', quad=False, rect=False, resume=False, save_dir='runs/train/yolov5s_results', single_cls=False, sync_bn=False, total_batch_size=16, weights='', workers=8, world_size=1)\n",
- "\u001b[34m\u001b[1mwandb: \u001b[0mInstall Weights & Biases for YOLOv5 logging with 'pip install wandb' (recommended)\n",
- "Start Tensorboard with \"tensorboard --logdir runs/train\", view at http://localhost:6006/\n",
- "\u001b[34m\u001b[1mhyperparameters: \u001b[0mlr0=0.01, lrf=0.2, momentum=0.937, weight_decay=0.0005, warmup_epochs=3.0, warmup_momentum=0.8, warmup_bias_lr=0.1, box=0.05, cls=0.5, cls_pw=1.0, obj=1.0, obj_pw=1.0, iou_t=0.2, anchor_t=4.0, fl_gamma=0.0, hsv_h=0.015, hsv_s=0.7, hsv_v=0.4, degrees=0.0, translate=0.1, scale=0.5, shear=0.0, perspective=0.0, flipud=0.0, fliplr=0.5, mosaic=1.0, mixup=0.0\n",
+ "\u001b[34m\u001b[1mhyperparameters: \u001b[0mlr0=0.01, lrf=0.01, momentum=0.937, weight_decay=0.0005, warmup_epochs=3.0, warmup_momentum=0.8, warmup_bias_lr=0.1, box=0.05, cls=0.5, cls_pw=1.0, obj=1.0, obj_pw=1.0, iou_t=0.2, anchor_t=4.0, fl_gamma=0.0, hsv_h=0.015, hsv_s=0.7, hsv_v=0.4, degrees=0.0, translate=0.1, scale=0.5, shear=0.0, perspective=0.0, flipud=0.0, fliplr=0.5, mosaic=1.0, mixup=0.0, copy_paste=0.0\n",
+ "\u001b[34m\u001b[1mClearML: \u001b[0mrun 'pip install clearml' to automatically track, visualize and remotely train YOLOv5 🚀 in ClearML\n",
+ "\u001b[34m\u001b[1mComet: \u001b[0mrun 'pip install comet_ml' to automatically track and visualize YOLOv5 🚀 runs in Comet\n",
+ "\u001b[34m\u001b[1mTensorBoard: \u001b[0mStart with 'tensorboard --logdir runs/train', view at http://localhost:6006/\n",
+ "Downloading https://ultralytics.com/assets/Arial.ttf to /root/.config/Ultralytics/Arial.ttf...\n",
+ "100% 755k/755k [00:00<00:00, 19.6MB/s]\n",
"\n",
" from n params module arguments \n",
" 0 -1 1 3520 models.common.Focus [3, 32, 3] \n",
" 1 -1 1 18560 models.common.Conv [32, 64, 3, 2] \n",
" 2 -1 1 19904 models.common.BottleneckCSP [64, 64, 1] \n",
" 3 -1 1 73984 models.common.Conv [64, 128, 3, 2] \n",
- " 4 -1 1 161152 models.common.BottleneckCSP [128, 128, 3] \n",
+ " 4 -1 3 161152 models.common.BottleneckCSP [128, 128, 3] \n",
" 5 -1 1 295424 models.common.Conv [128, 256, 3, 2] \n",
- " 6 -1 1 641792 models.common.BottleneckCSP [256, 256, 3] \n",
+ " 6 -1 3 641792 models.common.BottleneckCSP [256, 256, 3] \n",
" 7 -1 1 1180672 models.common.Conv [256, 512, 3, 2] \n",
" 8 -1 1 656896 models.common.SPP [512, 512, [5, 9, 13]] \n",
" 9 -1 1 1248768 models.common.BottleneckCSP [512, 512, 1, False] \n",
@@ -526,48 +606,548 @@
" 21 -1 1 590336 models.common.Conv [256, 256, 3, 2] \n",
" 22 [-1, 10] 1 0 models.common.Concat [1] \n",
" 23 -1 1 1248768 models.common.BottleneckCSP [512, 512, 1, False] \n",
- " 24 [17, 20, 23] 1 18879 models.yolo.Detect [2, [[10, 13, 16, 30, 33, 23], [30, 61, 62, 45, 59, 119], [116, 90, 156, 198, 373, 326]], [128, 256, 512]]\n",
- "/usr/local/lib/python3.7/dist-packages/torch/nn/functional.py:718: UserWarning: Named tensors and all their associated APIs are an experimental feature and subject to change. Please do not use them for anything important until they are released as stable. (Triggered internally at /pytorch/c10/core/TensorImpl.h:1156.)\n",
- " return torch.max_pool2d(input, kernel_size, stride, padding, dilation, ceil_mode)\n",
- "Model Summary: 283 layers, 7257791 parameters, 7257791 gradients, 16.8 GFLOPS\n",
- "\n",
- "Scaled weight_decay = 0.0005\n",
- "Optimizer groups: 62 .bias, 70 conv.weight, 59 other\n",
- "\u001b[34m\u001b[1mtrain: \u001b[0mScanning 'American-Mushrooms-1/train/labels' for images and labels... 123 found, 0 missing, 0 empty, 0 corrupted: 100% 123/123 [00:00<00:00, 2407.13it/s]\n",
- "\u001b[34m\u001b[1mtrain: \u001b[0mNew cache created: American-Mushrooms-1/train/labels.cache\n",
- "\u001b[34m\u001b[1mtrain: \u001b[0mCaching images (0.1GB): 100% 123/123 [00:00<00:00, 511.60it/s]\n",
- "\u001b[34m\u001b[1mval: \u001b[0mScanning 'American-Mushrooms-1/valid/labels' for images and labels... 5 found, 0 missing, 0 empty, 0 corrupted: 100% 5/5 [00:00<00:00, 1242.98it/s]\n",
- "\u001b[34m\u001b[1mval: \u001b[0mNew cache created: American-Mushrooms-1/valid/labels.cache\n",
- "\u001b[34m\u001b[1mval: \u001b[0mCaching images (0.0GB): 100% 5/5 [00:00<00:00, 321.12it/s]\n",
- "[W pthreadpool-cpp.cc:90] Warning: Leaking Caffe2 thread-pool after fork. (function pthreadpool)\n",
- "[W pthreadpool-cpp.cc:90] Warning: Leaking Caffe2 thread-pool after fork. (function pthreadpool)\n",
- "Plotting labels... \n",
- "\n",
- "\u001b[34m\u001b[1mautoanchor: \u001b[0mAnalyzing anchors... anchors/target = 3.48, Best Possible Recall (BPR) = 1.0000\n",
- "Image sizes 416 train, 416 test\n",
+ " 24 [17, 20, 23] 1 40455 models.yolo.Detect [10, [[10, 13, 16, 30, 33, 23], [30, 61, 62, 45, 59, 119], [116, 90, 156, 198, 373, 326]], [128, 256, 512]]\n",
+ "custom_YOLOv5s summary: 233 layers, 7279367 parameters, 7279367 gradients\n",
+ "\n",
+ "\u001b[34m\u001b[1mAMP: \u001b[0mchecks passed ✅\n",
+ "\u001b[34m\u001b[1moptimizer:\u001b[0m SGD(lr=0.01) with parameter groups 59 weight(decay=0.0), 70 weight(decay=0.0005), 62 bias\n",
+ "\u001b[34m\u001b[1malbumentations: \u001b[0mBlur(p=0.01, blur_limit=(3, 7)), MedianBlur(p=0.01, blur_limit=(3, 7)), ToGray(p=0.01), CLAHE(p=0.01, clip_limit=(1, 4.0), tile_grid_size=(8, 8))\n",
+ "\u001b[34m\u001b[1mtrain: \u001b[0mScanning /content/yolov5/Cash-Counter-10/train/labels... 2670 images, 914 backgrounds, 0 corrupt: 100% 2670/2670 [00:01<00:00, 1924.04it/s]\n",
+ "\u001b[34m\u001b[1mtrain: \u001b[0mNew cache created: /content/yolov5/Cash-Counter-10/train/labels.cache\n",
+ "\u001b[34m\u001b[1mtrain: \u001b[0mCaching images (1.3GB ram): 100% 2670/2670 [00:14<00:00, 188.00it/s]\n",
+ "\u001b[34m\u001b[1mval: \u001b[0mScanning /content/yolov5/Cash-Counter-10/valid/labels... 249 images, 83 backgrounds, 0 corrupt: 100% 249/249 [00:00<00:00, 634.84it/s]\n",
+ "\u001b[34m\u001b[1mval: \u001b[0mNew cache created: /content/yolov5/Cash-Counter-10/valid/labels.cache\n",
+ "\u001b[34m\u001b[1mval: \u001b[0mCaching images (0.1GB ram): 100% 249/249 [00:02<00:00, 92.86it/s]\n",
+ "\n",
+ "\u001b[34m\u001b[1mAutoAnchor: \u001b[0m5.98 anchors/target, 1.000 Best Possible Recall (BPR). Current anchors are a good fit to dataset ✅\n",
+ "Plotting labels to runs/train/yolov5s_results/labels.jpg... \n",
+ "Image sizes 416 train, 416 val\n",
"Using 2 dataloader workers\n",
- "Logging results to runs/train/yolov5s_results\n",
+ "Logging results to \u001b[1mruns/train/yolov5s_results\u001b[0m\n",
"Starting training for 100 epochs...\n",
"\n",
- " Epoch gpu_mem box obj cls total targets img_size\n",
- " 0/99 1.41G 0.1144 0.02597 0.02773 0.1681 49 416: 100% 8/8 [00:03<00:00, 2.55it/s]\n",
- " Class Images Targets P R mAP@.5 mAP@.5:.95: 100% 1/1 [00:00<00:00, 4.55it/s]\n",
- " all 5 14 0.00492 0.478 0.00691 0.00154\n",
- "\n",
- " Epoch gpu_mem box obj cls total targets img_size\n",
- " 0% 0/8 [00:00, ?it/s]\n",
- "Traceback (most recent call last):\n",
- " File \"train.py\", line 531, in \n",
- " train(hyp, opt, device, tb_writer, wandb)\n",
- " File \"train.py\", line 304, in train\n",
- " scaler.scale(loss).backward()\n",
- " File \"/usr/local/lib/python3.7/dist-packages/torch/_tensor.py\", line 255, in backward\n",
- " torch.autograd.backward(self, gradient, retain_graph, create_graph, inputs=inputs)\n",
- " File \"/usr/local/lib/python3.7/dist-packages/torch/autograd/__init__.py\", line 149, in backward\n",
- " allow_unreachable=True, accumulate_grad=True) # allow_unreachable flag\n",
- "KeyboardInterrupt\n",
- "CPU times: user 173 ms, sys: 37.6 ms, total: 211 ms\n",
- "Wall time: 25.7 s\n"
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 0/99 1.68G 0.09775 0.04436 0.0621 42 416: 100% 167/167 [00:35<00:00, 4.72it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:03<00:00, 2.17it/s]\n",
+ " all 249 1379 0.000415 0.0169 0.000222 3.82e-05\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 1/99 1.84G 0.09002 0.04745 0.05694 77 416: 100% 167/167 [00:28<00:00, 5.89it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.94it/s]\n",
+ " all 249 1379 0.00403 0.0824 0.00376 0.000841\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 2/99 1.84G 0.08354 0.04398 0.05172 69 416: 100% 167/167 [00:27<00:00, 6.07it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 5.14it/s]\n",
+ " all 249 1379 0.419 0.0175 0.00635 0.00225\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 3/99 1.84G 0.07113 0.04331 0.04881 21 416: 100% 167/167 [00:27<00:00, 6.11it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:06<00:00, 1.29it/s]\n",
+ " all 249 1379 0.673 0.189 0.0875 0.0319\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 4/99 1.84G 0.05779 0.03983 0.04666 87 416: 100% 167/167 [00:27<00:00, 6.02it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.08it/s]\n",
+ " all 249 1379 0.706 0.311 0.146 0.0664\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 5/99 1.84G 0.05051 0.03817 0.04587 43 416: 100% 167/167 [00:27<00:00, 6.11it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.99it/s]\n",
+ " all 249 1379 0.721 0.324 0.195 0.0886\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 6/99 1.84G 0.0459 0.03622 0.04517 107 416: 100% 167/167 [00:27<00:00, 6.11it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.13it/s]\n",
+ " all 249 1379 0.725 0.342 0.231 0.14\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 7/99 1.84G 0.0433 0.03545 0.0443 45 416: 100% 167/167 [00:27<00:00, 6.14it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.36it/s]\n",
+ " all 249 1379 0.504 0.392 0.312 0.147\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 8/99 1.84G 0.04119 0.03564 0.04325 115 416: 100% 167/167 [00:28<00:00, 5.80it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.46it/s]\n",
+ " all 249 1379 0.281 0.435 0.287 0.151\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 9/99 1.84G 0.03922 0.03452 0.04243 68 416: 100% 167/167 [00:27<00:00, 6.04it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.16it/s]\n",
+ " all 249 1379 0.799 0.272 0.328 0.205\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 10/99 1.84G 0.03885 0.0336 0.04172 31 416: 100% 167/167 [00:27<00:00, 6.07it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.43it/s]\n",
+ " all 249 1379 0.386 0.393 0.343 0.22\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 11/99 1.84G 0.03671 0.03205 0.03982 98 416: 100% 167/167 [00:27<00:00, 6.13it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.52it/s]\n",
+ " all 249 1379 0.428 0.444 0.383 0.245\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 12/99 1.84G 0.03713 0.03193 0.03942 88 416: 100% 167/167 [00:27<00:00, 6.10it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.45it/s]\n",
+ " all 249 1379 0.343 0.508 0.389 0.251\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 13/99 1.84G 0.03644 0.03261 0.0386 72 416: 100% 167/167 [00:27<00:00, 6.12it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.37 0.49 0.404 0.194\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 14/99 1.84G 0.03624 0.03257 0.03792 82 416: 100% 167/167 [00:27<00:00, 6.08it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.52it/s]\n",
+ " all 249 1379 0.301 0.643 0.42 0.272\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 15/99 1.84G 0.03456 0.03264 0.03665 144 416: 100% 167/167 [00:27<00:00, 6.13it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.07it/s]\n",
+ " all 249 1379 0.251 0.549 0.416 0.257\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 16/99 1.84G 0.03397 0.03066 0.03658 81 416: 100% 167/167 [00:27<00:00, 6.14it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.12it/s]\n",
+ " all 249 1379 0.251 0.633 0.422 0.245\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 17/99 1.84G 0.03464 0.03155 0.03478 71 416: 100% 167/167 [00:27<00:00, 6.07it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.274 0.528 0.415 0.253\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 18/99 1.84G 0.03406 0.03187 0.03437 8 416: 100% 167/167 [00:27<00:00, 6.18it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.63it/s]\n",
+ " all 249 1379 0.3 0.555 0.427 0.239\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 19/99 1.84G 0.03348 0.03082 0.03527 102 416: 100% 167/167 [00:27<00:00, 6.17it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.42it/s]\n",
+ " all 249 1379 0.292 0.667 0.413 0.278\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 20/99 1.84G 0.03336 0.03093 0.03424 33 416: 100% 167/167 [00:27<00:00, 6.10it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.61it/s]\n",
+ " all 249 1379 0.362 0.583 0.437 0.282\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 21/99 1.84G 0.03338 0.03025 0.03368 80 416: 100% 167/167 [00:26<00:00, 6.33it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.44it/s]\n",
+ " all 249 1379 0.278 0.657 0.435 0.268\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 22/99 1.84G 0.03199 0.03174 0.03265 25 416: 100% 167/167 [00:27<00:00, 6.13it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.66it/s]\n",
+ " all 249 1379 0.276 0.577 0.46 0.306\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 23/99 1.84G 0.03277 0.02992 0.03366 36 416: 100% 167/167 [00:27<00:00, 6.16it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.73it/s]\n",
+ " all 249 1379 0.288 0.618 0.476 0.32\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 24/99 1.84G 0.03226 0.029 0.03289 57 416: 100% 167/167 [00:26<00:00, 6.23it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.64it/s]\n",
+ " all 249 1379 0.282 0.539 0.443 0.287\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 25/99 1.84G 0.03243 0.03037 0.03249 48 416: 100% 167/167 [00:28<00:00, 5.79it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.77it/s]\n",
+ " all 249 1379 0.333 0.543 0.47 0.303\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 26/99 1.84G 0.03206 0.0289 0.03225 27 416: 100% 167/167 [00:26<00:00, 6.22it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.91it/s]\n",
+ " all 249 1379 0.385 0.685 0.455 0.308\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 27/99 1.84G 0.03216 0.02981 0.03224 105 416: 100% 167/167 [00:26<00:00, 6.22it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.14it/s]\n",
+ " all 249 1379 0.327 0.635 0.458 0.285\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 28/99 1.84G 0.03141 0.03002 0.03074 80 416: 100% 167/167 [00:27<00:00, 6.15it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.37it/s]\n",
+ " all 249 1379 0.386 0.695 0.477 0.308\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 29/99 1.84G 0.03103 0.03057 0.03039 39 416: 100% 167/167 [00:26<00:00, 6.23it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.51it/s]\n",
+ " all 249 1379 0.331 0.68 0.483 0.33\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 30/99 1.84G 0.03102 0.02814 0.03114 53 416: 100% 167/167 [00:27<00:00, 6.17it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.77it/s]\n",
+ " all 249 1379 0.319 0.639 0.452 0.305\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 31/99 1.84G 0.0314 0.02844 0.03106 98 416: 100% 167/167 [00:27<00:00, 6.18it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.68it/s]\n",
+ " all 249 1379 0.342 0.728 0.489 0.293\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 32/99 1.84G 0.03055 0.02902 0.02847 59 416: 100% 167/167 [00:26<00:00, 6.20it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.84it/s]\n",
+ " all 249 1379 0.354 0.758 0.514 0.334\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 33/99 1.84G 0.03032 0.02914 0.0285 121 416: 100% 167/167 [00:28<00:00, 5.79it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.90it/s]\n",
+ " all 249 1379 0.338 0.795 0.518 0.354\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 34/99 1.84G 0.02985 0.02742 0.03082 102 416: 100% 167/167 [00:27<00:00, 6.17it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.51it/s]\n",
+ " all 249 1379 0.354 0.753 0.52 0.353\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 35/99 1.84G 0.03064 0.02948 0.02885 85 416: 100% 167/167 [00:27<00:00, 6.03it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.17it/s]\n",
+ " all 249 1379 0.362 0.688 0.517 0.336\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 36/99 1.84G 0.03074 0.02933 0.02895 108 416: 100% 167/167 [00:27<00:00, 6.02it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.83it/s]\n",
+ " all 249 1379 0.389 0.714 0.53 0.351\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 37/99 1.84G 0.02974 0.02851 0.0272 78 416: 100% 167/167 [00:26<00:00, 6.20it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.83it/s]\n",
+ " all 249 1379 0.351 0.709 0.495 0.336\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 38/99 1.84G 0.0293 0.02952 0.02935 235 416: 100% 167/167 [00:26<00:00, 6.23it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.91it/s]\n",
+ " all 249 1379 0.358 0.767 0.538 0.353\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 39/99 1.84G 0.02917 0.0272 0.02802 88 416: 100% 167/167 [00:26<00:00, 6.26it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.99it/s]\n",
+ " all 249 1379 0.359 0.797 0.525 0.349\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 40/99 1.84G 0.02958 0.02936 0.02784 60 416: 100% 167/167 [00:27<00:00, 6.16it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 5.01it/s]\n",
+ " all 249 1379 0.374 0.799 0.529 0.335\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 41/99 1.84G 0.02882 0.0281 0.02712 149 416: 100% 167/167 [00:26<00:00, 6.30it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.86it/s]\n",
+ " all 249 1379 0.412 0.678 0.562 0.373\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 42/99 1.84G 0.03004 0.02807 0.02852 76 416: 100% 167/167 [00:27<00:00, 5.97it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.99it/s]\n",
+ " all 249 1379 0.41 0.721 0.556 0.378\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 43/99 1.84G 0.0294 0.02797 0.02815 61 416: 100% 167/167 [00:26<00:00, 6.27it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.50it/s]\n",
+ " all 249 1379 0.425 0.751 0.553 0.382\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 44/99 1.84G 0.02861 0.0278 0.02785 22 416: 100% 167/167 [00:26<00:00, 6.24it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.37it/s]\n",
+ " all 249 1379 0.402 0.763 0.525 0.346\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 45/99 1.84G 0.02854 0.02819 0.02707 45 416: 100% 167/167 [00:26<00:00, 6.31it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.39it/s]\n",
+ " all 249 1379 0.381 0.728 0.573 0.397\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 46/99 1.84G 0.0286 0.02739 0.02689 124 416: 100% 167/167 [00:26<00:00, 6.27it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.80it/s]\n",
+ " all 249 1379 0.354 0.674 0.53 0.358\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 47/99 1.84G 0.02892 0.0284 0.02604 77 416: 100% 167/167 [00:26<00:00, 6.22it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.90it/s]\n",
+ " all 249 1379 0.405 0.676 0.552 0.373\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 48/99 1.84G 0.02906 0.02854 0.02638 60 416: 100% 167/167 [00:26<00:00, 6.28it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.55it/s]\n",
+ " all 249 1379 0.388 0.7 0.568 0.399\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 49/99 1.84G 0.02873 0.02854 0.02655 53 416: 100% 167/167 [00:26<00:00, 6.28it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.87it/s]\n",
+ " all 249 1379 0.41 0.682 0.582 0.4\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 50/99 1.84G 0.02836 0.02612 0.0271 65 416: 100% 167/167 [00:28<00:00, 5.88it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.77it/s]\n",
+ " all 249 1379 0.411 0.791 0.583 0.399\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 51/99 1.84G 0.02817 0.02724 0.0258 87 416: 100% 167/167 [00:26<00:00, 6.31it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.89it/s]\n",
+ " all 249 1379 0.384 0.677 0.576 0.394\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 52/99 1.84G 0.02736 0.02737 0.02469 46 416: 100% 167/167 [00:26<00:00, 6.28it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.49it/s]\n",
+ " all 249 1379 0.39 0.723 0.561 0.383\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 53/99 1.84G 0.02792 0.02821 0.02469 58 416: 100% 167/167 [00:26<00:00, 6.28it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.52it/s]\n",
+ " all 249 1379 0.41 0.793 0.575 0.398\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 54/99 1.84G 0.02776 0.02762 0.02611 85 416: 100% 167/167 [00:26<00:00, 6.34it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.18it/s]\n",
+ " all 249 1379 0.453 0.682 0.566 0.394\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 55/99 1.84G 0.02811 0.02673 0.02686 63 416: 100% 167/167 [00:26<00:00, 6.29it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.73it/s]\n",
+ " all 249 1379 0.407 0.744 0.567 0.384\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 56/99 1.84G 0.0278 0.02727 0.02552 51 416: 100% 167/167 [00:26<00:00, 6.25it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.63it/s]\n",
+ " all 249 1379 0.399 0.707 0.578 0.406\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 57/99 1.84G 0.02775 0.02714 0.02418 103 416: 100% 167/167 [00:27<00:00, 6.10it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.92it/s]\n",
+ " all 249 1379 0.407 0.848 0.593 0.399\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 58/99 1.84G 0.02815 0.02696 0.0247 82 416: 100% 167/167 [00:27<00:00, 6.14it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.41it/s]\n",
+ " all 249 1379 0.42 0.819 0.591 0.398\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 59/99 1.84G 0.02718 0.02709 0.02424 91 416: 100% 167/167 [00:26<00:00, 6.27it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.99it/s]\n",
+ " all 249 1379 0.441 0.761 0.601 0.422\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 60/99 1.84G 0.02701 0.02622 0.02344 38 416: 100% 167/167 [00:26<00:00, 6.28it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.16it/s]\n",
+ " all 249 1379 0.436 0.857 0.607 0.414\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 61/99 1.84G 0.02717 0.02683 0.02334 66 416: 100% 167/167 [00:26<00:00, 6.31it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.53it/s]\n",
+ " all 249 1379 0.423 0.756 0.586 0.399\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 62/99 1.84G 0.02721 0.02661 0.02401 57 416: 100% 167/167 [00:26<00:00, 6.31it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.15it/s]\n",
+ " all 249 1379 0.439 0.737 0.589 0.394\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 63/99 1.84G 0.02742 0.02583 0.02359 98 416: 100% 167/167 [00:27<00:00, 6.02it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.61it/s]\n",
+ " all 249 1379 0.404 0.732 0.578 0.39\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 64/99 1.84G 0.02714 0.02731 0.02258 45 416: 100% 167/167 [00:28<00:00, 5.82it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.65it/s]\n",
+ " all 249 1379 0.456 0.731 0.594 0.407\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 65/99 1.84G 0.0266 0.02584 0.02354 39 416: 100% 167/167 [00:27<00:00, 5.99it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.79it/s]\n",
+ " all 249 1379 0.45 0.853 0.591 0.41\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 66/99 1.84G 0.02738 0.02611 0.0235 53 416: 100% 167/167 [00:27<00:00, 6.00it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.36it/s]\n",
+ " all 249 1379 0.451 0.797 0.582 0.414\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 67/99 1.84G 0.02695 0.02622 0.02324 48 416: 100% 167/167 [00:30<00:00, 5.50it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.30it/s]\n",
+ " all 249 1379 0.452 0.837 0.589 0.417\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 68/99 1.84G 0.02664 0.02507 0.0239 150 416: 100% 167/167 [00:27<00:00, 6.08it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.76it/s]\n",
+ " all 249 1379 0.455 0.852 0.565 0.398\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 69/99 1.84G 0.02612 0.02559 0.02371 86 416: 100% 167/167 [00:28<00:00, 5.95it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.84it/s]\n",
+ " all 249 1379 0.464 0.841 0.589 0.408\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 70/99 1.84G 0.02637 0.02583 0.02237 52 416: 100% 167/167 [00:27<00:00, 6.15it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.80it/s]\n",
+ " all 249 1379 0.485 0.871 0.594 0.422\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 71/99 1.84G 0.02709 0.0262 0.02201 70 416: 100% 167/167 [00:27<00:00, 6.05it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.84it/s]\n",
+ " all 249 1379 0.445 0.807 0.6 0.403\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 72/99 1.84G 0.02666 0.02575 0.02218 74 416: 100% 167/167 [00:27<00:00, 6.00it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.78it/s]\n",
+ " all 249 1379 0.477 0.782 0.599 0.41\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 73/99 1.84G 0.02612 0.02553 0.02283 60 416: 100% 167/167 [00:27<00:00, 6.03it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.70it/s]\n",
+ " all 249 1379 0.479 0.85 0.604 0.432\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 74/99 1.84G 0.02639 0.02537 0.02128 80 416: 100% 167/167 [00:27<00:00, 6.00it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.81it/s]\n",
+ " all 249 1379 0.491 0.839 0.603 0.42\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 75/99 1.84G 0.0256 0.02432 0.02368 42 416: 100% 167/167 [00:29<00:00, 5.66it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.72it/s]\n",
+ " all 249 1379 0.472 0.813 0.603 0.415\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 76/99 1.84G 0.02628 0.02604 0.02191 38 416: 100% 167/167 [00:28<00:00, 5.85it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.467 0.751 0.601 0.418\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 77/99 1.84G 0.0254 0.02536 0.021 38 416: 100% 167/167 [00:28<00:00, 5.79it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.63it/s]\n",
+ " all 249 1379 0.487 0.78 0.602 0.409\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 78/99 1.84G 0.02553 0.02492 0.02133 150 416: 100% 167/167 [00:28<00:00, 5.88it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.94it/s]\n",
+ " all 249 1379 0.47 0.848 0.598 0.409\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 79/99 1.84G 0.02563 0.02494 0.02103 80 416: 100% 167/167 [00:28<00:00, 5.93it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.52it/s]\n",
+ " all 249 1379 0.495 0.81 0.605 0.43\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 80/99 1.84G 0.0256 0.0248 0.02165 47 416: 100% 167/167 [00:28<00:00, 5.91it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.69it/s]\n",
+ " all 249 1379 0.485 0.86 0.612 0.422\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 81/99 1.84G 0.02557 0.0256 0.02054 35 416: 100% 167/167 [00:28<00:00, 5.78it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.58it/s]\n",
+ " all 249 1379 0.469 0.822 0.612 0.418\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 82/99 1.84G 0.02549 0.02499 0.01994 60 416: 100% 167/167 [00:29<00:00, 5.65it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.62it/s]\n",
+ " all 249 1379 0.467 0.857 0.602 0.421\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 83/99 1.84G 0.02638 0.02606 0.01999 40 416: 100% 167/167 [00:31<00:00, 5.38it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.10it/s]\n",
+ " all 249 1379 0.5 0.781 0.61 0.424\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 84/99 1.84G 0.02574 0.02447 0.02159 78 416: 100% 167/167 [00:28<00:00, 5.81it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.71it/s]\n",
+ " all 249 1379 0.458 0.853 0.61 0.419\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 85/99 1.84G 0.02529 0.02549 0.02106 41 416: 100% 167/167 [00:28<00:00, 5.85it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.70it/s]\n",
+ " all 249 1379 0.482 0.868 0.603 0.413\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 86/99 1.84G 0.02462 0.02453 0.02045 56 416: 100% 167/167 [00:28<00:00, 5.81it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.491 0.859 0.608 0.417\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 87/99 1.84G 0.02509 0.02538 0.01955 123 416: 100% 167/167 [00:29<00:00, 5.70it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.71it/s]\n",
+ " all 249 1379 0.473 0.882 0.613 0.429\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 88/99 1.84G 0.02532 0.02468 0.02032 114 416: 100% 167/167 [00:29<00:00, 5.75it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.33it/s]\n",
+ " all 249 1379 0.474 0.769 0.613 0.426\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 89/99 1.84G 0.02434 0.02459 0.02016 36 416: 100% 167/167 [00:28<00:00, 5.82it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.69it/s]\n",
+ " all 249 1379 0.484 0.849 0.606 0.428\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 90/99 1.84G 0.02485 0.02456 0.01918 63 416: 100% 167/167 [00:30<00:00, 5.46it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.62it/s]\n",
+ " all 249 1379 0.512 0.809 0.631 0.445\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 91/99 1.84G 0.02523 0.02394 0.01908 80 416: 100% 167/167 [00:28<00:00, 5.80it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.62it/s]\n",
+ " all 249 1379 0.488 0.819 0.612 0.435\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 92/99 1.84G 0.02522 0.02471 0.01873 27 416: 100% 167/167 [00:29<00:00, 5.74it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.53it/s]\n",
+ " all 249 1379 0.473 0.811 0.615 0.436\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 93/99 1.84G 0.02505 0.02417 0.01981 65 416: 100% 167/167 [00:28<00:00, 5.83it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.16it/s]\n",
+ " all 249 1379 0.468 0.822 0.616 0.426\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 94/99 1.84G 0.02454 0.02377 0.01962 50 416: 100% 167/167 [00:29<00:00, 5.71it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.63it/s]\n",
+ " all 249 1379 0.488 0.815 0.617 0.433\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 95/99 1.84G 0.02484 0.02411 0.01905 89 416: 100% 167/167 [00:29<00:00, 5.74it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.488 0.866 0.62 0.432\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 96/99 1.84G 0.02429 0.0254 0.01824 69 416: 100% 167/167 [00:28<00:00, 5.81it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.59it/s]\n",
+ " all 249 1379 0.495 0.859 0.62 0.441\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 97/99 1.84G 0.02508 0.02506 0.01825 64 416: 100% 167/167 [00:29<00:00, 5.68it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:02<00:00, 3.52it/s]\n",
+ " all 249 1379 0.505 0.876 0.622 0.442\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 98/99 1.84G 0.02512 0.0246 0.01919 59 416: 100% 167/167 [00:30<00:00, 5.47it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.70it/s]\n",
+ " all 249 1379 0.49 0.885 0.621 0.435\n",
+ "\n",
+ " Epoch GPU_mem box_loss obj_loss cls_loss Instances Size\n",
+ " 99/99 1.84G 0.02408 0.02346 0.01833 42 416: 100% 167/167 [00:29<00:00, 5.75it/s]\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:01<00:00, 4.55it/s]\n",
+ " all 249 1379 0.482 0.896 0.609 0.425\n",
+ "\n",
+ "100 epochs completed in 0.840 hours.\n",
+ "Optimizer stripped from runs/train/yolov5s_results/weights/last.pt, 14.8MB\n",
+ "Optimizer stripped from runs/train/yolov5s_results/weights/best.pt, 14.8MB\n",
+ "\n",
+ "Validating runs/train/yolov5s_results/weights/best.pt...\n",
+ "Fusing layers... \n",
+ "custom_YOLOv5s summary: 182 layers, 7270791 parameters, 0 gradients\n",
+ " Class Images Instances P R mAP50 mAP50-95: 100% 8/8 [00:10<00:00, 1.30s/it]\n",
+ " all 249 1379 0.512 0.809 0.631 0.445\n",
+ " Dime 249 202 0.617 0.965 0.949 0.596\n",
+ " Nickel 249 357 0.738 0.933 0.939 0.645\n",
+ " Penny 249 502 0.82 0.998 0.988 0.688\n",
+ " Quarter 249 214 0.79 0.977 0.963 0.697\n",
+ " fifty 249 15 0.168 0.733 0.231 0.168\n",
+ " five 249 15 0.299 0.4 0.274 0.229\n",
+ " hundred 249 20 0.932 0.65 0.743 0.507\n",
+ " one 249 20 0.322 0.808 0.526 0.404\n",
+ " ten 249 16 0.214 0.938 0.393 0.319\n",
+ " twenty 249 18 0.224 0.689 0.304 0.203\n",
+ "Results saved to \u001b[1mruns/train/yolov5s_results\u001b[0m\n",
+ "CPU times: user 36.6 s, sys: 3.78 s, total: 40.4 s\n",
+ "Wall time: 51min 21s\n"
]
}
],
@@ -594,299 +1174,45 @@
"id": "7KN5ghjE6ZWh"
},
"source": [
- "Training losses and performance metrics are saved to Tensorboard and also to a logfile defined above with the **--name** flag when we train. In our case, we named this `yolov5s_results`. (If given no name, it defaults to `results.txt`.) The results file is plotted as a png after training completes.\n",
+ "You can view the training graphs associated with a training job in the `/content/yolov5/runs/train/yolov5s_results/results.png` folder.\n",
+ "\n",
+ "Training losses and performance metrics are also saved to Tensorboard and also to a logfile defined above with the **--name** flag when we train. In our case, we named this `yolov5s_results`.\n",
"\n",
"Note from Glenn: Partially completed `results.txt` files can be plotted with `from utils.utils import plot_results; plot_results()`."
]
},
{
"cell_type": "code",
- "execution_count": null,
- "metadata": {
- "colab": {
- "base_uri": "https://localhost:8080/",
- "height": 821,
- "resources": {
- "https://localhost:6006/?tensorboardColab=true": {
- "data": "PCFkb2N0eXBlIGh0bWw+PG1ldGEgbmFtZT0idGItcmVsYXRpdmUtcm9vdCIgY29udGVudD0iLi8iPjwhZG9jdHlwZSBodG1sPjwhLS0KQGxpY2Vuc2UKQ29weXJpZ2h0IDIwMTkgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCkxpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwp5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCllvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQpkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLApXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZApsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KLS0+PGh0bWw+PGhlYWQ+PG1ldGEgY2hhcnNldD0idXRmLTgiPgo8dGl0bGU+VGVuc29yQm9hcmQ8L3RpdGxlPgo8bGluayByZWw9InNob3J0Y3V0IGljb24iIGhyZWY9ImRhdGE6aW1hZ2UvcG5nO2Jhc2U2NCxpVkJPUncwS0dnb0FBQUFOU1VoRVVnQUFBTVFBQUFERUNBWUFBQURBcG81ckFBQUFCSE5DU1ZRSUNBZ0lmQWhraUFBQUFBbHdTRmx6QUFCYWJnQUFXbTRCeFdzak9BQUFBQmwwUlZoMFUyOW1kSGRoY21VQWQzZDNMbWx1YTNOallYQmxMbTl5WjV2dVBCb0FBQmwwU1VSQlZIaWM3WjE1ZUZUVjNjYy92NXNGQ1ZSeHFWdHB0VlcyVmx4ZjYxcXRpcTBMOUdsOU5YVUJGRXBGUlRJaGhCQURDVGRBTUFFa0NZc0s3cUI5K2tENzJxZkJXaXZxVzdWYTY3NGlyZTlyYXhYMWJaVldaVEhML040LzVnNEdTR0R1ekwxejc1MDVuMzg0ek13NTU4dk0vWEsyM3prSERJR2ppemhQRjNGZTBEb01JRUVMeUdkMFBvT3dhQUF1Y1Y1YWgwVzVWUEI2a0xyeUdXT0lBRkNiL3ZTakVxZ0crdXp3S3dnZHdDMTBVQ2ZWL0RzWWhmbUxNVVFXVVJ1TEVrWUQ4eEVPMnY3R2pvWndQc3hIV014aElFdWxsSzVzNnN4bmpDR3loQzdnSkpSVzRDU2daeFAwbkg0Smk1aVU4N2pmR2czR0VMNmpUUXdFNWdHamtXN2ZkK3FHU0xLV0lzcGtNbS83SU5QZ1lBemhFMnBUUWgrcXNLZ0MrZ0x1VGJCcmVpdXdtSFlhWkRxZmVpcllBQmhEZUk0cVFpTVhBd3NRRHZQQUJEMmxOeUxVczRuYnhTYWV1V3BERW1NSUQ5RWJPUUZvUlRodCs0ditHQ0w1NTdOQXVjUjRLaTNCaGwwd2h2QUFiZUFRTEd4Z0FtRDVhb0x1NmNTZml2QUxsRXFKOFk1TDZZYWRNSWJJQUxVcHBvaHJFV1lqN0wzOWpld2FJcG5lakxLUXZXbVVjV3hMNlI5ZzJBVmppRFRSdVl6Q29nWDRCcEE5RTNSUDkveiszNEdaVXNiS1hxUWJkb014aEV1MGdhTVJtbEhPOXZBQi82T1RPdGtEUXlUU3lpTW81UkxqdFo3K0hZYWVzWUlXRUJYVVpqK2RTeXZ3UE1yWkhoVzdFV0VpbjNFYVV6a1ZvUlQ0bXljbEMrZGc4Ykl1WmFYZXdvR2VsSmtIbUJaaUQ2aE5JVVdNUjJrQUR2Q29WZGlLc0pqNHJ1c0p1cHdTUHFNS3FFS2M5WXZleWttOXprMUFFd2ZTTEtXMFkrZ1ZZNGpkb1BXY2cwVUx3bEhiWDh6Y0VHc1J5bVRhN2xlY3RZbUJGRGtyM095d3hwMk9JWkxwRFFoVDVUb2UyRjNkK1l3eFJBL29IQVpCdDdCc2IxcUZGeW1nWENyZHhTVHBJczRFV2hDTzNhWE05TFdzbzRDWVhNTWJiclRrQThZUTNWQ2IvZ2lWeUU1aDJaa1o0aU9FT1J5ZWZ0U3EybGdNWURUS2ZPQWdqM1Ixb054Q0lYVXkwWVNaSnpHR3dIbmdMT2VCNnlrc083MEhML0hBaVhmN0duUVovV252d2JEcGF3U2NNUFA5VEpnNUdFT2dzMU1JeTNiL3NLMGpUa3hxL09tU2FDdURVQnFRN1R2dHZPald2WWhRTHRma2Q1aDUzaHBDYlJkaDJhay9WQnRRS3FTRzMzZ3F0aGUwbFhPQUZ1QW9EOWRFMWxKQW1mdzBQOFBNODg0UWFsTUN6clJtcW1IWmUzNlFOaUUwOFRuTlltZDNXbE50Q3RtWDhZZ3pMZHk3UmpmcFJKaDVFUTN5ay93S004OGJReWdJZFZ5TXhRTFVaVmgyNys5M290eUpNRk5xK0lmWG10MmdpOWlQUW1ZQjF5RVVibjhqTTNPOGgxTERSRmFKb0o0S0RpbDVZUWl0NVFRa2c3RHNubDk3Rkl0eXFlWlZUOFZtaUM1aEtFb3o0aHhyNDAxWDZsbVVtRnpEMHg1S0RTVTViUWl0NFJDS3NORU13N0ozZk8wdGxCcVp5UnFQNVhxS0xtWVVRZ3ZpQkI5Q3B1WlE0RjQ2cUpKSmZPQ3AyQkNSazRaUW0ySTZQUXpMVHZ5WkNLL2VoeHVsak04OWx1d0xhbFBNL3M3M0FIdDcxRnBzUmxoSVlXNkdtZWVjSVhTRzUySFpjWVQ3RUtiSkRENzBWbTEyME9VY1FnYzI0clNVNE1YMzhoWkNqVXdJZDB2cGxwd3hoTjdBVUFwb0JzN3pjQXJ5R1pTWTFQR01oMUlEUTI5MnRyZ3FwM24ySFZrOFNwd3A4bE5lOFZCcVlFVGVFR3F6SHgzTVFyZ09uTm1Wekgvc2Q0RVoxT2JlN0lvcXdpM09JUWh3R09ERjk5V0pPTE50NDRPZGJjdVV5QnBDYlFycFlEeDRHcGE5QlZqQWwyaVNDclo2S0RkMDZISks2S1FLU1NITVBOVzB4U2JpTkxGM2RNUE1JMmtJclhGV2FMMEx5MWJnRnhRd1RXWjZ0RUVuSXVqaUZNTE0zYVlUWWVZVk1pNDdLL1plRWlsRDZFd0dFZmM4TFBzNUxNcWxqajk0cHpSNjZNMmM2VXhHN0JwbTdqYjl4V3ZyS0tSTXhyTGVPNlgrRWdsRHFPMUVlU3JWQ0gyMnY1R1pJVFlDOVdBTyswcWlOaFlITzRjeGR3OHpoMHpXYlJKUnZ4M1JDRE1QdFNIVXhtSXJvN0djSHdpOGFCWGFnVnNwWWFZNURySm5kQm45c2FqRWNzTE1JUk5ESkVtRW1mY05kNWg1YUEyaE4zUUx5L1p1R25VdFFreHMvdGREcVRtTDNzb2d4T21pWm02SVpQb0ZsSElaeHhOZWF2V0swQmxDcXhpSTFXMlFCMTYwQ2kraGxNc2NmdStwMkR4QlZ6RENpWTlLVEdKa1pvaGtlaTF4SnNzNC91cWwxa3dKalNIVXBvUXR6alFnOVBXb1ZVaHMzMXpQVWxrVDNtWTZDcWhOSVY5eFRoOFJKOHdjTWpFRUpLYTVsOUNYdVZMS1o5NHFUby9BRGFFZ1RPTml4RmtvY3YrbDlwUk9YRXZWVHAwMGhYOGdGeVgwZHZaRG1RVk1BZ295TkVReS9SNUNEYU9EWHdnTjFCQTZsUk93ZWduTFR0OFE2eERLWlk2NXVOQlA5RGFHQVl1UWJyZW5adjdiL1FtTG1JemVmcEpoMWduRUVGcnVoR1h2N3JSczkxL3FCdUpNbFhubXpLRnNvcmN6Q3B4Z1NtOWFkMFdjTVBOeDJROHp6Nm9obk83Uk5KUmFoUDQ5cW5EL3BYNE0xRlBFeldMVDZhMWlReXJvWGV4Rm5BcmdCcUMvUitPL1Q3Q1lReEdMc3hrR2t2VVdRaXM0emprTjc0d2VWYVJ1aUVSWWRoR1ZZdk4vZm1nMXVFT1hjd2lGUG9XWlg1R2RNUFBBeGhCYXlTaUVWdURycmcyaFBJb3dSZWJsUnNoeHJxRjNjd0pkenRqUXV6V2tSMUhLWmJTL1czYURIVlRiRkxPWmF4SG1BRi9hUVZIUFg4eGJXTlJJUTI1dFNzbEZWQkh1OWlITUhPNmtpSmxTNmsrWWVlRFRyZ0JheGFIQUxHQUMwbU5UbTlpMldFeWoyTG0zYlRHWDBlV1VVSnppYWVhcHB6ZWgxSE1veStRc2I4ZU5vVEJFRXEzaVA1eHUxS21Pc3NURzlpNnFaRUh1Ym16UEIvUTJCbExNUE5URE1ITjRFNHNLdVpRSHZkSVpLa09BTXhNMW5URUlGMk5oeXp4ZUNGcVR3VHYwTHI3cmhKa2ZzLzNGek0xeFAzRXE1WXJNWTlSQ1p3aEQ3cU0yRm9jN1llYVNRWmo1anVrT0xHNmhnMW9aelNmcGFqT0dNQVNHcnFZL1c3dWRaZzZadHhiQyt5ZzJGbmVrRTJadURHRUlITDJQUVhTbEVXYSt1elE4ajBXNWxQS2tHeTNHRUliUW9QZHdQc0lpaEtGQXBvYUF4S1gyRStUSDNKbXFCdGUza0dvNUU3U2NIN3JOWnpEc0NibVNCOW5LMGNCRTRKOWVGQWtjNmlhRCsydDVsU05SN3RjWTYvUjZ4OGtHZzBmSVJEcGtEQ3Zvd3hCZ01XUjNIMHM2aGloeVV1ZFF3Q3NhbzFXdjZ4YW9aekI0Z0pUeXNZd21ScHpod0crelZhOTdRMWpiRFFGUUJKUlJ4SHFOTWRZelZRYURnNHhsdll6bWZJUWZnUDk3NFROcElib3pFTGhIeTNqWWRLTU1maUNYMDBZUnc0QnlTSCtkWVUrNE53UTlHaUtCTUlJQ1h0WXBOS3JOWHVuTE1oaDJSVXBwbHl0b1JSZ0cvcHlsNWEwaEVoU2pUT2Rmdks0eFJxWWp5bURZSFhJWkc4R2Z2ZGQrR0NMSk54RGFkQXB0V3NuWDA2akhZTWc2WG8waGRzZEl1bmhkSzdCTk44b1FkaktkWlVxVnZpaXorSVRYdEpJTDA4aHZNR1NGYkxRUTNUbUNPR3UxZ2pZdDUvQU15akVZZk1IUE1jVHVHRWtCYjJpbDZVWVp3a1ZRaG9Ca04rcFRYdFZwWE9CUm1RWkRSZ1JwaUNSSG9qeWdVMm5UYXRPTk1nUkx0c2NRdlNPTXBKUFh0UXBiSjNlN0ZNVmd5Q0x1RFNFK0dTSkJDY29zK3ZDYVR1dDJacWpCa0NYQzBHWGFGZUZJNEVHdG9rMm5PbWY2R0F4WklKeUcrSUxFYkpUcFJobXlSTmdOQVZBQ3pLS0VWM1U2Mzg5eTNZWThJd3FHU0RJSStLMVcwNmJUK1ZwQUdndzVUcFFNa1VBWmliQmVxN0hWcGpoUUxZYWNJM3FHU0pEb1JtM2pWYTNtZTBHTE1lUU9VVFZFa3NFSUQra050T2tNdmhxMEdFUDBpYm9oa293a3pucXRNZDBvUTJia2lpRUErZ0d6YU9jVnJlSGNvTVVZb29rclEyamk0S2RDbjdSNHhSRGdkenJEZEtNTTduSFhRbHdkZWpOMFp5U3dYbWVhYmxSZUUzZDNHSUhiTGxOWXUwdTkwUTlsRmwyOHJETVpFYlFZUTFiWmpGTFBOaGE1eWVUT0VQdEd6aEFKbEtIQTczUW1LN1dHZzRLV1kvQVZCVmJSd1NDNURGdkd1YnVDelowaE9pTnFpQVFDaktHQURUcVRtTnFSNnY0WlVrSDVFeGFueWFXTWxURzhuMDRSN2d6UkZXbERKTmtIb1lVdW50TmFUZ3Rhak1FVDNrVzRra3M1V1VwNU9wT0MzQm5DcjgxQndYQU13aE5hWjdwUmtVWFpBdFJUd0dDNWxKVWltUjllNXM0UThad3lCQ1M3VVlXOHFYWEU5QklLZ2haa1NCRmhGVVVNbHN1d3BaU3QzaFhyQXIyZW9SU3czbFdwMFVxL2hEQkpiSjdDa0plNGF5R0tjcTZGMkpsamdTZlZacVhhSEJpMEdFUDJ5ZWN4Uk0rbzA0MkNEVnBQVEZlYmJsUStZUXpST3dOUVdsalBzenFiVTRJV1k4Z091YjVTN1FYSG9meEI2MW1wOC9oeTBHSU0vbUphaU5SSWRLTTYyYUJ6VERjcWwzRm5DTW43SUxsOVVWcll3SjkwTGljSExjYmdQYWJMbEE3SzhTaFA2UnpUamNvMVRKY3BmUkxkcUM3VGpjb2xUQXVST2ZzaXRQQVhudEhabkJTMEdFTm11RE5FZXJjSDVRZktDVmc4cFhOWnFUWUhCQzNIa0I2bWhmQVdDMkVNUld6UUJtSnFwN1ZuUFZSb013T0MxcEFKdXBxRDNYemU3USsyNXowRXJxS2pjcGI5Z0JhS2VWSWJPU1pvTWVtZ1N6aFVsN0tjWXVZRXJTVWRkQlZEOUdjOFFBZFQzZVJ6TzZoMk4rMXF6SEVLU2xuUUl0eWdOc1c2aEJnV2J5SmNUWG9uc3dTRzNzZStlaCtOV0x3QzdtK21jcmRyVENsSyt5SGZNZDltNERHZ2pTNmVvSWpIMEJ6ZGt4Q25QV2dKcWFMTEdJWFNDdEc3VjF4dExJNWdOTEFBMGcvTWRMdU5NcE14eE5zb0R3TnIyWWVIeFA3aVFkRktLb0Q3TWlnN3ZBZ2RRVXZZRTdxTVk0blRnbkptMEZyU1FlL2pMT0swSUJ5ZGFWbnVER0ZSNUdKUFVoZUovUVZyRWRya0pwN3Y3WU95a0o5cEpaZEREdDVoTGVGdElYUXArd04xeEprRTBWdEgwWlY4RFl1NUtHTzg2cDY3N3pMdG5zMkkweFVxNU5leWdBOWNLTG1lTHI1TDRnUyszRUhEMTBMb2NvcG81enJpMUNQc0U3UWV0K2hLK2lGTUE2YWo3T1hsV05XTEx0UGJDQThqdTNhRjNDQ04vRldyYUVDWmwzZ2huVkpDU01nTW9Zc1p3ZWUwQU44S1dvdGJWQkh1WlF4S0U3aWJUazJWZEF6eFJWY29UcHNzN3IwcjVKb1NGckNaVWhJNzEzSURLeHlHMEtVTXBvdEZLQmRHOFQ4YnZZc1RXVVVyK0xzM3haMGh1cmliSXVaTE14LzdJVVpzT3JXUzZ4Q2VwUHQwWDIvN29LTkJvR01JYldZQVFqVmRUSUhvUlN2clBYd0Z1QkVZVFJaK2ZWZUdrS1c4NlplUTdYVXM1R21keG5MZ1dyL3J5Z29CZFpuVXhtSkE1dE9RUWFHcjZjdFd5b0Fad0pleVZXODRGMTIyVVkzdzNoNC9GNFhXSW9CWkpyMkpzOWlIRjRCN2lLSVo3bUlVVzNnRHBaRXNtZ0ZDYWdoWndpZEFoYnRNL21qSm1DeTJFSG9UWDlWbVZtTHhLRVF2WkVUdjVIaTlpOGNSZmcwY0hvU0cwSjV2S2syczFtbU1SaGpsUHJNUGd0SWxDNGJRQmZURFlockNkR0F2dit2ekdyMkgvZW1pRGdsK1BTUzBoZ0RBNG5xVXM0RCthWmNSdkRsODZ6S3BJaXppWW9TRkVMMnJpblU1UlJSekhWM2hXUThKWlpjcGlUVHhEa0s5ZHdWNlZsTHErRFR0cWdzNWtVVThDYXdtaW1hNGt4RVU4UkpLQzRURERKQmxRNmhOb2JwOUxQdlNBcnpvdVpqc21HTVR5cXRlRnFoTkhLb0xXWTd3UitCVUw4dk9Cbm9IUS9SMkhuRGkycjRadEo2ZDhkMFFPcGsrT29VUldrRXJuL0F1VTdqS1RYNng2VVM1bXNTQ29ELzRZUTdsQXl6T2tocmU4S3pJaFZ4RUFYK0c2SVZsQStqdGpBZGVROXlIWldjTFg3NVVuVUpmbmNJb25jSktDdmtRZUJnb0F3NUNhTllxQnJvcFQrYnpISEN6SDFwM3JjeVRVdDZtZ085SU5TOTdVdG9YSEVPMFk3MkdFZkp4cTJmaXRKd0JLT2NpakVMNUVkQy9sNGRySDdxNEJWek9IaWt6RUg0RTdzeVVFZW1aNHpVSytiNU1aNlBIYWd4WklLTVdRaWV4djhZWXF6SGFVRDRrTWNBYnc1NW5oVVpxQlQ5MlU1Zk01MU1rOUx2UEhxZUEwNDBab290clEraGtCbW9aVjJ1TU5ncDVuOFJxNkVqY3hza0lTN1hTM1NxcU5ISS95cTljMWVNVmUyNHQxbExDZVZMTnY3T2d4dUFUN2k1dUwrY2lMTjVCV0U3Q0JKbnNvRHVBT00ydWN5bVRJT0NIYm1kektQZnlaUzZTQ3U5dXNqRUVnOXNydGZyaDVaeU1jTGxPNVlldXNzeG5JOG9zenpSa2lzVVN1cmhTSm9ZanpOdVFHY0ZQM1FrM2F6WDd1c3JUbHlYQUgvMFJsRElLMU1zTXlzUW1IckFXZzBjRWJ3ZzRoRTZhM0dRUW16Z1dFeUd3LzVXN1VLNlJXdXlBNmpmNFJCZ01BVEJCcC9FOU54bGtIcThBUzN6U3N6dmFFUzZUT2xZRVVMZkJaOEppQ0NIT2NyVmRCdkgxb1JaNDJ4OUpQYklaWVpUTVpFMFc2elJra2JBWUFvVEQyY3hjVjFsc3RqZ2h3OW5nWXl4R1NDMi95MUo5aGdBSWp5RVNUTmJwbk80bWc4empRZUFYUHVsSjhnN0NxVEl6OElHOHdXZkNaZ2lMT0xlcjdYS1RTeWVUZ1gvNUk0bjFGSEM2MUxMQnAvSU5JU0pzaGdBWXdtWnEzV1J3RGtTYjZZT1c1eWppVEpuSjM5TXRRQnM0eWt0QkJuOEpveUVBcXJTYUUxemxLT1lXNENrUE5UekdYcHd0TmZ3ajNRTDBScVlqVkhxb3llQXpZVFZFSVhIdTBLdFREdzBSbXpnRlhJTTNheE8vQWk2UTZYeWFiZ0hhd0d6bjFBaERoQWlySVFDT1lRQlZiakxJSEY1RjBvaVAycEc3Z1V2RVpsczZtVlVSYmFBRmNkZnRNNFNETUJzQ29GYW51enlEZEFzMjhEOXAxU1kwaWMwNHNlbE1KN3V1cG9CNTNBN0UwcXJmRURoaE4wUWY0QTY5SlBXalNhU1pyVTVFYk9vSWlsSXBOdFZ1QlNiUjFSVHdaKzRDeHFkYmhpRjR3bTRJVUU3aTYweDJrMFhtOFJEQ3oxUDhlQmN3UVdaemszdHhDZFNtbUQrekJtRk11bVVZd2tINERRRWdOR2cxUjdyS0U2Y2MyTFNIVDMxT1lyeHdaN3JTMUthRVF0cUFINlZiaGlFOFJNTVFVSUp5bTVzamJHUWVIOEp1dTBEL3dtS0V6T2IrZEVYcEF2bzVabkFWbUdnSUwxRXhCTUIzcWVhbnJuSTBjQnZ3WkEvdkpJNklzWHQ4THlYVVpnRGJXQWVjblc0Wmh2QVJKVU9Bc2tCbjhOVlVQeTZKVFR3VFNIU05raVNPaUxGNUtXMFpOZ2RTd0g4REo2ZGJoaUdjUk1zUXNEZGQzT29tZzh4bEE3RFErZXZyeFBtTzJMeVZyZ0MxT1pnQ0hpR0NwMnNiOWt6VURBRndnVlp6aGFzY2hjeEZ1WnNDVHBlR0ZPNmQ2QVdkeTJGWVBBRW1QaWxYQ2ZVcGFydWhWV3RZNXd5Yzk0aXo2and1a3dyVlpqQngxa0hxWFRaRDlJaGlDd0d3UDhyaWJGV21jeGlHeFdNWU0rUThVVFVFS0tWNkF4ZjVYbzNOOGNSNUhEalU3N29Nd1JOZFF5UllwamI3K1ZXNHp1WkVoSWVCQS95cXd4QXVvbTZJZzltV2ZzakY3dERabklueUNQaG5PRVA0aUxvaFFMaEtxem5QeXlLMW52T0o4eUJadmdIVEVEelJOd1NBc0Z5cnZIbDQxZVlIS1BjRGZiMG96eEF0Y3NNUThEVUt1VEhUUXJTT3k0QmZrZ2c3TitRaHVXSUlnR3QxQm1la20xbHRya2E0bCtpdXpSZzhJSmNNWWFIY3BsUGNkM1cwamtuQXJlVFc5MkZJZzF4N0FBWlQ0dTRBWXExak9zSlNOQVEzV2hzQ0o5Y01BY3BVcmVYRWxENDZpM293SjJQa01HK2cvTkpOQm5lRzZPSnhKUFJubXhZUTV3NjFlNy9pUzBGMEZxMG9kZGtVWnNnYW00QnFDamxPUnJzN2Z0VFZBRktXOFRmZyt6cUZFY1JwQVpjblltU1A0YlJ6QTFDLzh4dHFZOUhKQ3BTZkJLREw0Qzl4NEQ2S21DcWw2UjB3bDFhWFNacFp4MWFPUXlrbjZQdmVla09vMFZxR2QzOUpMNkdBVHU1RWpCbHlEdUZSTEk2VEt4aWJyaGtnZ3pHRXJLQkRGdE5LSjBjQWkwbWNYaEVtaW9semo5cUpWbEJ0aWhuS2FvUXJneFptOEpTM0VFcmxDczZSeTNrbDA4SXlIbFRMTWo2U1ZtSUl3NEdITWkzUFk0NmpnM0tkVEI4NldRUCtSOGNhc3NabW9KNU9oc3NWM2wxZzQ5a2lsTFN3SGpoUFkxeUNNQjg0M0t1eU0wS1l6VDVjQkp3U3RCU0RKeWh3TDUxVXlUZys4THB3ejZkZHBaVTFER0FJUWpud2lkZmxwMEZmakJseWhXZFJUcE94alBYRERPRFRPb1RZdEVzenJSUXhERmdCNXRwYVEwYThoM0lsWXpoSnJ1UnBQeXZ5ZFdGTzVyTlJtcGtJbkFUOHdjKzZERG5KVnFDSnZneVZxMWdwZ3ZwZFlWWUMyYVNaNXhTK1F3VVhBd3VBdzdKUnJ5SFNyRVdaTEZmeDEyeFdtclhRRFFHVlJhemhNNzZKVUUvQy9RYkR6cnlBY29aY3hTZ1psMTB6UUFDeFRMS0NMYklRbXdJR0E2dkEvMmJRRUFrK0FzcnB4N2RsSEU4RUpTS3c0RDZaejd0eUUyT0JVeEJ6M1cwZTB3RXNwcDBqWkJ5dFVocnNBbS9nMGE2eWtHZm94Mm5PQ25KS0I0OFpjb1oxd0xFeW5waE1ERWNJVU9DR2dNU0ZpYktBbFNoSE9PT0x6L2VZeVJCbE5tQnhvWXpuWEJuUEcwR0w2VTRvREpGRUZySlo1bU5Ud0ZHSWQ4dnhodER3TWNway9zNVJNbzdmQkMybUowSzVmMWdhZVFzbzFXck9kc0xNaCs4cGp5SDh5SVRNRDRMd20xQzFFRHNqalR4S0NjY2pUSVQwUTNvTmhsUUp0U0VBeEtaVEdsbUJNQVNsQ1dnUFdwTWhkd205SVpKSUk1dGtQdFhFT1JyQzJmODBSSi9JR0NLSnpHZUROSEloY0M2RWE0YkNFSDBpWjRnazBzZzZQdUpZSjh3OEZIUFlodWdUV1VPQXM0MTFIcTNBRWM0RkttSGJ4bXFJR0pFMlJCSzVrWS9rUm1MRU9SRjRQR2c5aHVpU0U0WklJbzI4S1BNNEUvZ0I4SGJRZWd6Ukk2Y01rVVFhYUdNTDMwS3BCajROV284aE91U2tJUUNrbWEweWp5WUtHWXFhYmF5RzFNaFpReVFSbTQzU3dFU1VreENlQ2xwUHhQZ3Y0dHN2dmM4TGN0NFFTYVNCNTVqTjZRaWx3RHRCNndrNWJ3TG55eVQrVXlibjExZ3Nid3dCempiVzJheWhnR0Vrem4zZEZyU21rUEV4U2puL1pMaE00cmRCaXdtQ3ZESkVFckhaSXJPeHNSZ0VyQ0lMcHptRW5FNWdCVVVNa2NtMGlrMW4wSUtDSWk4TmtVUnMzcFhaaktXTHM0Q1hndFlUQ01vanhEbE9Kak5SSnZMUG9PVUVUVjRiSW9uTTRmY0lKK1RaTnRhL0lKUktHU01reG10Qml3a0x4aEFPWWhNWG01WEFrWkRUMjFnL1E2a0hoc3Rrc3l0eFo0d2hka0pzUGhNYm13S0dRMDQ5TUhGZ0ZjcVJFc09Xc3B3MWZFYUVjZ3RwR0pCYS9nS1VhajNuQU0xRWV4dnJNeWd4S2VlWm9JV0VIZE5DN0FHWnhTTW94ME1rdDdHK0MxeEpqRk9NR1ZMREdDSUZ4S1pUNmxoQm5LRWtia3NLKzdUa0ZxQ2VPSU9sUER1SEJPY0t4aEF1RUp1UHBZNFlCUXhIZVRCb1BUMmd3QnE2K0taTXdaWUtjMzZ1Vzh3WUlnMmtoamVCQzNRT0kwaTBHTU1DbGdUQzgwQk1wcGhyQnpMQnRCQVpJTFdzNDhzY0UvQnRyTzhqVE9UZmZOdVlJWE9NSVRKRUp0SWh0YlJpY1FTUzFXMnM3Y0JpaWhncVUxZ2h0Z2x2OXdKakNJK1FHajZTR21MQXQ4SDM0OXpYWWpGTXBoS1RzbERjNDVjem1ER0V4OGdNWGdETzBMbU13cUxWNCtMZlJEaGJwdktZeCtVYURQNmpOaVhheUJsQjZ6Q2t6djhEUWQ3UXJNYkxSMUFBQUFBQVNVVk9SSzVDWUlJPSI+CjxsaW5rIHJlbD0iYXBwbGUtdG91Y2gtaWNvbiIgaHJlZj0iZGF0YTppbWFnZS9wbmc7YmFzZTY0LGlWQk9SdzBLR2dvQUFBQU5TVWhFVWdBQUFNUUFBQURFQ0FZQUFBREFwbzVyQUFBQUJITkNTVlFJQ0FnSWZBaGtpQUFBQUFsd1NGbHpBQUJhYmdBQVdtNEJ4V3NqT0FBQUFCbDBSVmgwVTI5bWRIZGhjbVVBZDNkM0xtbHVhM05qWVhCbExtOXlaNXZ1UEJvQUFCbDBTVVJCVkhpYzdaMTVlRlRWM2NjL3Y1c0ZDVlJ4cVZ0cHRWVzJWbHhmNjFxdGlxMEw5R2w5TlhVQkZFcEZSVEloaEJBRENUZEFNQUVrQ1lzSzdxQjkra0Q3MnFmQldpdnFXN1ZhNjc0aXJlOXJheFgxYlpWV1pUSEwvTjQvNWc0R1NHRHV6TDF6NzUwNW4zODR6TXc1NTh2TS9YSzIzemtIRElHaml6aFBGM0ZlMERvTUlFRUx5R2QwUG9Pd2FBQXVjVjVhaDBXNVZQQjZrTHJ5R1dPSUFGQ2IvdlNqRXFnRyt1endLd2dkd0MxMFVDZlYvRHNZaGZtTE1VUVdVUnVMRWtZRDh4RU8ydjdHam9ad1BzeEhXTXhoSUV1bGxLNXM2c3huakNHeWhDN2dKSlJXNENTZ1p4UDBuSDRKaTVpVTg3amZHZzNHRUw2alRRd0U1Z0dqa1c3ZmQrcUdTTEtXSXNwa01tLzdJTlBnWUF6aEUycFRRaCtxc0tnQytnTHVUYkJyZWl1d21IWWFaRHFmZWlyWUFCaERlSTRxUWlNWEF3c1FEdlBBQkQybE55TFVzNG5ieFNhZXVXcERFbU1JRDlFYk9RRm9SVGh0KzR2K0dDTDU1N05BdWNSNEtpM0JobDB3aHZBQWJlQVFMR3hnQW1ENWFvTHU2Y1NmaXZBTGxFcUo4WTVMNllhZE1JYklBTFVwcG9ockVXWWo3TDM5amV3YUlwbmVqTEtRdldtVWNXeEw2UjlnMkFWamlEVFJ1WXpDb2dYNEJwQTlFM1JQOS96KzM0R1pVc2JLWHFRYmRvTXhoRXUwZ2FNUm1sSE85dkFCLzZPVE90a0RReVRTeWlNbzVSTGp0WjcrSFlhZXNZSVdFQlhVWmorZFN5dndQTXJaSGhXN0VXRWluM0VhVXprVm9SVDRteWNsQytkZzhiSXVaYVhld29HZWxKa0htQlppRDZoTklVV01SMmtBRHZDb1ZkaUtzSmo0cnVzSnVwd1NQcU1LcUVLYzlZdmV5a205emsxQUV3ZlNMS1cwWStnVlk0amRvUFdjZzBVTHdsSGJYOHpjRUdzUnltVGE3bGVjdFltQkZEa3IzT3l3eHAyT0laTHBEUWhUNVRvZTJGM2QrWXd4UkEvb0hBWkJ0N0JzYjFxRkZ5bWdYQ3JkeFNUcElzNEVXaENPM2FYTTlMV3NvNENZWE1NYmJyVGtBOFlRM1ZDYi9naVZ5RTVoMlprWjRpT0VPUnllZnRTcTJsZ01ZRFRLZk9BZ2ozUjFvTnhDSVhVeTBZU1pKekdHd0huZ0xPZUI2eWtzTzcwSEwvSEFpWGY3R25RWi9XbnZ3YkRwYXdTY01QUDlUSmc1R0VPZ3MxTUl5M2Ivc0swalRreHEvT21TYUN1RFVCcVE3VHZ0dk9qV3ZZaFFMdGZrZDVoNTNocENiUmRoMmFrL1ZCdFFLcVNHMzNncXRoZTBsWE9BRnVBb0Q5ZEUxbEpBbWZ3MFA4UE04ODRRYWxNQ3pyUm1xbUhaZTM2UU5pRTA4VG5OWW1kM1dsTnRDdG1YOFlnekxkeTdSamZwUkpoNUVRM3lrL3dLTTg4YlF5Z0lkVnlNeFFMVVpWaDI3Kzkzb3R5Sk1GTnErSWZYbXQyZ2k5aVBRbVlCMXlFVWJuOGpNM084aDFMRFJGYUpvSjRLRGlsNVlRaXQ1UVFrZzdEc25sOTdGSXR5cWVaVlQ4Vm1pQzVoS0VvejRoeHI0MDFYNmxtVW1GekQweDVLRFNVNWJRaXQ0UkNLc05FTXc3SjNmTzB0bEJxWnlScVA1WHFLTG1ZVVFndmlCQjlDcHVaUTRGNDZxSkpKZk9DcDJCQ1JrNFpRbTJJNlBRekxUdnlaQ0svZWh4dWxqTTg5bHV3TGFsUE0vczczQUh0NzFGcHNSbGhJWVc2R21lZWNJWFNHNTJIWmNZVDdFS2JKREQ3MFZtMTIwT1VjUWdjMjRyU1U0TVgzOGhaQ2pVd0lkMHZwbHB3eGhON0FVQXBvQnM3emNBcnlHWlNZMVBHTWgxSURRMjkydHJncXAzbjJIVms4U3B3cDhsTmU4VkJxWUVUZUVHcXpIeDNNUXJnT25ObVZ6SC9zZDRFWjFPYmU3SW9xd2kzT0lRaHdHT0RGOTlXSk9MTnQ0NE9kYmN1VXlCcENiUXJwWUR4NEdwYTlCVmpBbDJpU0NyWjZLRGQwNkhKSzZLUUtTU0hNUE5XMHhTYmlOTEYzZE1QTUkya0lyWEZXYUwwTHkxYmdGeFF3VFdaNnRFRW5JdWppRk1MTTNhWVRZZVlWTWk0N0svWmVFaWxENkV3R0VmYzhMUHM1TE1xbGpqOTRwelI2Nk0yYzZVeEc3QnBtN2piOXhXdnJLS1JNeHJMZU82WCtFZ2xEcU8xRWVTclZDSDIydjVHWklUWUM5V0FPKzBxaU5oWUhPNGN4ZHc4emgweldiUkpSdngzUkNETVB0U0hVeG1Jcm83R2NId2k4YUJYYWdWc3BZYVk1RHJKbmRCbjlzYWpFY3NMTUlSTkRKRW1FbWZjTmQ1aDVhQTJoTjNRTHkvWnVHblV0UWt4cy90ZERxVG1MM3NvZ3hPbWlabTZJWlBvRmxISVp4eE5lYXZXSzBCbENxeGlJMVcyUUIxNjBDaStobE1zY2Z1K3AyRHhCVnpEQ2lZOUtUR0prWm9oa2VpMXhKc3M0L3VxbDFrd0pqU0hVcG9RdHpqUWc5UFdvVlVoczMxelBVbGtUM21ZNkNxaE5JVjl4VGg4Uko4d2NNakVFSkthNWw5Q1h1VkxLWjk0cVRvL0FEYUVnVE9OaXhGa29jditsOXBST1hFdlZUcDAwaFg4Z0Z5WDBkdlpEbVFWTUFnb3lORVF5L1I1Q0RhT0RYd2dOMUJBNmxST3dlZ25MVHQ4UTZ4REtaWTY1dU5CUDlEYUdBWXVRYnJlblp2N2IvUW1MbUl6ZWZwSmgxZ25FRUZydWhHWHY3clJzOTEvcUJ1Sk1sWG5tektGc29yY3pDcHhnU205YWQwV2NNUE54MlE4eno2b2huTzdSTkpSYWhQNDlxbkQvcFg0TTFGUEV6V0xUNmExaVF5cm9YZXhGbkFyZ0JxQy9SK08vVDdDWVF4R0xzeGtHa3ZVV1FpczR6amtONzR3ZVZhUnVpRVJZZGhHVll2Ti9mbWcxdUVPWGN3aUZQb1daWDVHZE1QUEF4aEJheVNpRVZ1RHJyZzJoUElvd1JlYmxSc2h4cnFGM2N3SmR6dGpRdXpXa1IxSEtaYlMvVzNhREhWVGJGTE9aYXhIbUFGL2FRVkhQWDh4YldOUklRMjV0U3NsRlZCSHU5aUhNSE82a2lKbFM2aytZZWVEVHJnQmF4YUhBTEdBQzBtTlRtOWkyV0V5ajJMbTNiVEdYMGVXVVVKemlhZWFwcHplaDFITW95K1FzYjhlTm9UQkVFcTNpUDV4dTFLbU9zc1RHOWk2cVpFSHVibXpQQi9RMkJsTE1QTlRETUhONEU0c0t1WlFIdmRJWktrT0FNeE0xblRFSUYyTmh5enhlQ0ZxVHdUdjBMcjdyaEprZnMvM0Z6TTF4UDNFcTVZck1ZOVJDWndoRDdxTTJGb2M3WWVhU1FaajVqdWtPTEc2aGcxb1p6U2ZwYWpPR01BU0dycVkvVzd1ZFpnNlp0eGJDK3lnMkZuZWtFMlp1REdFSUhMMlBRWFNsRVdhK3V6UThqMFc1bFBLa0d5M0dFSWJRb1Bkd1BzSWloS0ZBcG9hQXhLWDJFK1RIM0ptcUJ0ZTNrR281RTdTY0g3ck5aekRzQ2JtU0I5bkswY0JFNEo5ZUZBa2M2aWFEKzJ0NWxTTlI3dGNZNi9SNng4a0dnMGZJUkRwa0RDdm93eEJnTVdSM0gwczZoaWh5VXVkUXdDc2FvMVd2Nnhhb1p6QjRnSlR5c1l3bVJwemh3Ryt6VmE5N1ExamJEUUZRQkpSUnhIcU5NZFl6VlFhRGc0eGx2WXptZklRZmdQOTc0VE5wSWJvekVMaEh5M2pZZEtNTWZpQ1gwMFlSdzRCeVNIK2RZVSs0TndROUdpS0JNSUlDWHRZcE5Lck5YdW5MTWhoMlJVcHBseXRvUlJnRy9weWw1YTBoRWhTalRPZGZ2SzR4UnFZanltRFlIWElaRzhHZnZkZCtHQ0xKTnhEYWRBcHRXc25YMDZqSFlNZzZYbzBoZHNkSXVuaGRLN0JOTjhvUWRqS2RaVXFWdmlpeitJVFh0SklMMDhodk1HU0ZiTFFRM1RtQ09HdTFnall0NS9BTXlqRVlmTUhQTWNUdUdFa0JiMmlsNlVZWndrVlFob0JrTitwVFh0VnBYT0JSbVFaRFJnUnBpQ1JIb2p5Z1UyblRhdE9OTWdSTHRzY1F2U09NcEpQWHRRcGJKM2U3Rk1WZ3lDTHVEU0UrR1NKQkNjb3MrdkNhVHV0MlpxakJrQ1hDMEdYYUZlRkk0RUd0b2sybk9tZjZHQXhaSUp5RytJTEViSlRwUmhteVJOZ05BVkFDektLRVYzVTYzODl5M1lZOEl3cUdTRElJK0sxVzA2YlQrVnBBR2d3NVRwUU1rVUFaaWJCZXE3SFZwamhRTFlhY0kzcUdTSkRvUm0zalZhM21lMEdMTWVRT1VUVkVrc0VJRCtrTnRPa012aHEwR0VQMGlib2hrb3drem5xdE1kMG9RMmJraWlFQStnR3phT2NWcmVIY29NVVlvb2tyUTJqaTRLZENuN1I0eFJEZ2R6ckRkS01NN25IWFFsd2Rlak4wWnlTd1htZWFibFJlRTNkM0dJSGJMbE5ZdTB1OTBROWxGbDI4ckRNWkViUVlRMWJaakZMUE5oYTV5ZVRPRVB0R3poQUpsS0hBNzNRbUs3V0dnNEtXWS9BVkJWYlJ3U0M1REZ2R3VidUN6WjBoT2lOcWlBUUNqS0dBRFRxVG1OcVI2djRaVWtINUV4YW55YVdNbFRHOG4wNFI3Z3pSRldsREpOa0hvWVV1bnROYVRndGFqTUVUM2tXNGtrczVXVXA1T3BPQzNCbkNyODFCd1hBTXdoTmFaN3BSa1VYWkF0UlR3R0M1bEpVaW1SOWU1czRROFp3eUJDUzdVWVc4cVhYRTlCSUtnaFprU0JGaEZVVU1sc3V3cFpTdDNoWHJBcjJlb1JTdzNsV3AwVXEvaERCSmJKN0NrSmU0YXlHS2NxNkYySmxqZ1NmVlpxWGFIQmkwR0VQMnllY3hSTStvMDQyQ0RWcFBURmViYmxRK1lRelJPd05RV2xqUHN6cWJVNElXWThnT3ViNVM3UVhIb2Z4QjYxbXA4L2h5MEdJTS9tSmFpTlJJZEtNNjJhQnpURGNxbDNGbkNNbjdJTGw5VVZyWXdKOTBMaWNITGNiZ1BhYkxsQTdLOFNoUDZSelRqY28xVEpjcGZSTGRxQzdUamNvbFRBdVJPZnNpdFBBWG50SFpuQlMwR0VObXVETkVlcmNINVFmS0NWZzhwWE5acVRZSEJDM0hrQjZtaGZBV0MyRU1SV3pRQm1KcXA3Vm5QVlJvTXdPQzFwQUp1cHFEM1h6ZTdRKzI1ejBFcnFLamNwYjlnQmFLZVZJYk9TWm9NZW1nU3poVWw3S2NZdVlFclNVZGRCVkQ5R2M4UUFkVDNlUnpPNmgyTisxcXpIRUtTbG5RSXR5Z05zVzZoQmdXYnlKY1RYb25zd1NHM3NlK2VoK05XTHdDN20rbWNyZHJUQ2xLK3lIZk1kOW00REdnalM2ZW9JakgwQnpka3hDblBXZ0pxYUxMR0lYU0N0RzdWMXh0TEk1Z05MQUEwZy9NZEx1Tk1wTXh4TnNvRHdOcjJZZUh4UDdpUWRGS0tvRDdNaWc3dkFnZFFVdllFN3FNWTRuVGduSm0wRnJTUWUvakxPSzBJQnlkYVZudURHRlI1R0pQVWhlSi9RVnJFZHJrSnA3djdZT3lrSjlwSlpkRER0NWhMZUZ0SVhRcCt3TjF4SmtFMFZ0SDBaVjhEWXU1S0dPODZwNjc3ekx0bnMySTB4VXE1TmV5Z0E5Y0tMbWVMcjVMNGdTKzNFSEQxMExvY29wbzV6cmkxQ1BzRTdRZXQraEsraUZNQTZhajdPWGxXTldMTHRQYkNBOGp1M2FGM0NDTi9GV3JhRUNabDNnaG5WSkNTTWdNb1lzWndlZTBBTjhLV290YlZCSHVaUXhLRTdpYlRrMlZkQXp4UlZjb1Rwc3M3cjByNUpvU0ZyQ1pVaEk3MTNJREt4eUcwS1VNcG90RktCZEc4VDhidllzVFdVVXIrTHMzeFowaHVyaWJJdVpMTXgvN0lVWnNPcldTNnhDZXBQdDBYMi83b0tOQm9HTUliV1lBUWpWZFRJSG9SU3ZyUFh3RnVCRVlUUlorZlZlR2tLVzg2WmVRN1hVczVHbWR4bkxnV3Ivcnlnb0JkWm5VeG1KQTV0T1FRYUdyNmN0V3lvQVp3SmV5Vlc4NEYxMjJVWTN3M2g0L0Y0WFdJb0JaSnIySnM5aUhGNEI3aUtJWjdtSVVXM2dEcFpFc21nRkNhZ2had2lkQWhidE0vbWpKbUN5MkVIb1RYOVZtVm1MeEtFUXZaRVR2NUhpOWk4Y1JmZzBjSG9TRzBKNXZLazJzMW1tTVJoamxQck1QZ3RJbEM0YlFCZlREWWhyQ2RHQXZ2K3Z6R3IySC9lbWlEZ2wrUFNTMGhnREE0bnFVczREK2FaY1J2RGw4NnpLcElpemlZb1NGRUwycmluVTVSUlJ6SFYzaFdROEpaWmNwaVRUeERrSzlkd1Y2VmxMcStEVHRxZ3M1a1VVOENhd21pbWE0a3hFVThSSktDNFREREpCbFE2aE5vYnA5TFB2U0Fyem91WmpzbUdNVHlxdGVGcWhOSEtvTFdZN3dSK0JVTDh2T0Jub0hRL1IySG5EaTJyNFp0SjZkOGQwUU9waytPb1VSV2tFcm4vQXVVN2pLVFg2eDZVUzVtc1NDb0QvNFlRN2xBeXpPa2hyZThLekloVnhFQVgrRzZJVmxBK2p0akFkZVE5eUhaV2NMWDc1VW5VSmZuY0lvbmNKS0N2a1FlQmdvQXc1Q2FOWXFCcm9wVCtiekhIQ3pIMXAzcmN5VFV0Nm1nTzlJTlM5N1V0b1hIRU8wWTcyR0VmSnhxMmZpdEp3QktPY2lqRUw1RWRDL2w0ZHJIN3E0QlZ6T0hpa3pFSDRFN3N5VUVlbVo0elVLK2I1TVo2UEhhZ3haSUtNV1FpZXh2OFlZcXpIYVVENGtNY0FidzU1bmhVWnFCVDkyVTVmTTUxTWs5THZQSHFlQTA0MFpvb3RyUStoa0Jtb1pWMnVNTmdwNW44UnE2RWpjeHNrSVM3WFMzU3FxTkhJL3lxOWMxZU1WZTI0dDFsTENlVkxOdjdPZ3h1QVQ3aTV1TCtjaUxONUJXRTdDQkpuc29EdUFPTTJ1Y3ltVElPQ0hibWR6S1BmeVpTNlNDdTl1c2pFRWc5c3J0ZnJoNVp5TWNMbE81WWV1c3N4bkk4b3N6elJraXNVU3VyaFNKb1lqek51UUdjRlAzUWszYXpYN3VzclRseVhBSC8wUmxESUsxTXNNeXNRbUhyQVdnMGNFYndnNGhFNmEzR1FRbXpnV0V5R3cvNVc3VUs2Uld1eUE2amY0UkJnTUFUQkJwL0U5Tnhsa0hxOEFTM3pTc3p2YUVTNlRPbFlFVUxmQlo4SmlDQ0hPY3JWZEJ2SDFvUlo0Mng5SlBiSVpZWlRNWkUwVzZ6UmtrYkFZQW9URDJjeGNWMWxzdGpnaHc5bmdZeXhHU0MyL3kxSjloZ0FJanlFU1ROYnBuTzRtZzh6alFlQVhQdWxKOGc3Q3FUSXo4SUc4d1dmQ1pnaUxPTGVyN1hLVFN5ZVRnWC81STRuMUZIQzYxTExCcC9JTklTSnNoZ0FZd21acTNXUndEa1NiNllPVzV5amlUSm5KMzlNdFFCczR5a3RCQm44Sm95RUFxclNhRTF6bEtPWVc0Q2tQTlR6R1hwd3ROZndqM1FMMFJxWWpWSHFveWVBellUVkVJWEh1MEt0VER3MFJtemdGWElNM2F4Ty9BaTZRNlh5YWJnSGF3R3puMUFoRGhBaXJJUUNPWVFCVmJqTElIRjVGMG9pUDJwRzdnVXZFWmxzNm1WVVJiYUFGY2RmdE00U0RNQnNDb0ZhbnV6eURkQXMyOEQ5cDFTWTBpYzA0c2VsTUo3dXVwb0I1M0E3RTBxcmZFRGhoTjBRZjRBNjlKUFdqU2FTWnJVNUViT29JaWxJcE50VnVCU2JSMVJUd1orNEN4cWRiaGlGNHdtNElVRTdpNjB4MmswWG04UkRDejFQOGVCY3dRV1p6azN0eENkU21tRCt6Qm1GTXVtVVl3a0g0RFFFZ05HZzFSN3JLRTZjYzJMU0hUMzFPWXJ4d1o3clMxS2FFUXRxQUg2VmJoaUU4Uk1NUVVJSnltNXNqYkdRZUg4SnV1MEQvd21LRXpPYitkRVhwQXZvNVpuQVZtR2dJTDFFeEJNQjNxZWFucm5JMGNCdndaQS92Skk2SXNYdDhMeVhVWmdEYldBZWNuVzRaaHZBUkpVT0Fza0JuOE5WVVB5NkpUVHdUU0hTTmtpU09pTEY1S1cwWk5nZFN3SDhESjZkYmhpR2NSTXNRc0RkZDNPb21nOHhsQTdEUStldnJ4UG1PMkx5VnJnQzFPWmdDSGlHQ3Ayc2I5a3pVREFGd2dWWnpoYXNjaGN4RnVac0NUcGVHRk82ZDZBV2R5MkZZUEFFbVBpbFhDZlVwYXJ1aFZXdFk1d3ljOTRpejZqd3Vrd3JWWmpCeDFrSHFYVFpEOUloaUN3R3dQOHJpYkZXbWN4aUd4V01ZTStROFVUVUVLS1Y2QXhmNVhvM044Y1I1SERqVTc3b013Uk5kUXlSWXBqYjcrVlc0enVaRWhJZUJBL3lxd3hBdW9tNklnOW1XZnNqRjd0RFpuSW55Q1Bobk9FUDRpTG9oUUxoS3F6blB5eUsxbnZPSjh5Qlp2Z0hURUR6Uk53U0FzRnlydkhsNDFlWUhLUGNEZmIwb3p4QXRjc01ROERVS3VUSFRRclNPeTRCZmtnZzdOK1FodVdJSWdHdDFCbWVrbTFsdHJrYTRsK2l1elJnOElKY01ZYUhjcGxQY2QzVzBqa25BcmVUVzkyRklnMXg3QUFaVDR1NEFZcTFqT3NKU05BUTNXaHNDSjljTUFjcFVyZVhFbEQ0Nmkzb3dKMlBrTUcrZy9OSk5CbmVHNk9KeEpQUm5teFlRNXc2MWU3L2lTMEYwRnEwb2Rka1Vac2dhbTRCcUNqbE9ScnM3ZnRUVkFGS1c4VGZnK3pxRkVjUnBBWmNuWW1TUDRiUnpBMUMvOHh0cVk5SEpDcFNmQktETDRDOXg0RDZLbUNxbDZSMHdsMWFYU1pwWngxYU9ReWtuNlB2ZWVrT28wVnFHZDM5Skw2R0FUdTVFakJseUR1RlJMSTZUS3hpYnJoa2dnekdFcktCREZ0TktKMGNBaTBtY1hoRW1pb2x6ajlxSlZsQnRpaG5LYW9Rcmd4Wm04SlMzRUVybENzNlJ5M2tsMDhJeUhsVExNajZTVm1JSXc0R0hNaTNQWTQ2amczS2RUQjg2V1FQK1I4Y2Fzc1ptb0o1T2hzc1YzbDFnNDlraWxMU3dIamhQWTF5Q01CODQzS3V5TTBLWXpUNWNCSndTdEJTREp5aHdMNTFVeVRnKzhMcHd6NmRkcFpVMURHQUlRam53aWRmbHAwRmZqQmx5aFdkUlRwT3hqUFhERE9EVE9vVFl0RXN6clJReERGZ0I1dHBhUTBhOGgzSWxZemhKcnVScFB5dnlkV0ZPNXJOUm1wa0luQVQ4d2MrNkREbkpWcUNKdmd5VnExZ3BndnBkWVZZQzJhU1o1eFMrUXdVWEF3dUF3N0pScnlIU3JFV1pMRmZ4MTJ4V21yWFFEUUdWUmF6aE03NkpVRS9DL1FiRHpyeUFjb1pjeFNnWmwxMHpRQUN4VExLQ0xiSVFtd0lHQTZ2QS8yYlFFQWsrQXNycHg3ZGxIRThFSlNLdzRENlp6N3R5RTJPQlV4QnozVzBlMHdFc3BwMGpaQnl0VWhyc0FtL2cwYTZ5a0dmb3gybk9DbkpLQjQ4WmNvWjF3TEV5bnBoTURFY0lVT0NHZ01TRmliS0FsU2hIT09PTHovZVl5UkJsTm1CeG9Zem5YQm5QRzBHTDZVNG9ESkZFRnJKWjVtTlR3RkdJZDh2eGh0RHdNY3BrL3M1Uk1vN2ZCQzJtSjBLNWYxZ2FlUXNvMVdyT2RzTE1oKzhwanlIOHlJVE1ENEx3bTFDMUVEc2pqVHhLQ2NjalRJVDBRM29OaGxRSnRTRUF4S1pUR2xtQk1BU2xDV2dQV3BNaGR3bTlJWkpJSTV0a1B0WEVPUnJDMmY4MFJKL0lHQ0tKekdlRE5ISWhjQzZFYTRiQ0VIMGlaNGdrMHNnNlB1SllKOHc4RkhQWWh1Z1RXVU9BczQxMUhxM0FFYzRGS21IYnhtcUlHSkUyUkJLNWtZL2tSbUxFT1JGNFBHZzlodWlTRTRaSUlvMjhLUE00RS9nQjhIYlFlZ3pSSTZjTWtVUWFhR01MMzBLcEJqNE5XbzhoT3VTa0lRQ2ttYTB5anlZS0dZcWFiYXlHMU1oWlF5UVJtNDNTd0VTVWt4Q2VDbHBQeFBndjR0c3Z2YzhMY3Q0UVNhU0I1NWpONlFpbHdEdEI2d2s1YndMbnl5VCtVeWJuMTFnc2J3d0J6amJXMmF5aGdHRWt6bjNkRnJTbWtQRXhTam4vWkxoTTRyZEJpd21DdkRKRUVySFpJck94c1JnRXJDSUxwem1FbkU1Z0JVVU1rY20waWsxbjBJS0NJaThOa1VSczNwWFpqS1dMczRDWGd0WVRDTW9qeERsT0pqTlJKdkxQb09VRVRWNGJJb25NNGZjSUorVFpOdGEvSUpSS0dTTWt4bXRCaXdrTHhoQU9ZaE1YbTVYQWtaRFQyMWcvUTZrSGhzdGtzeXR4WjR3aGRrSnNQaE1ibXdLR1EwNDlNSEZnRmNxUkVzT1dzcHcxZkVhRWNndHBHSkJhL2dLVWFqM25BTTFFZXh2ck15Z3hLZWVab0lXRUhkTkM3QUdaeFNNb3gwTWt0N0crQzF4SmpGT01HVkxER0NJRnhLWlQ2bGhCbktFa2Jrc0srN1RrRnFDZU9JT2xQRHVIQk9jS3hoQXVFSnVQcFk0WUJReEhlVEJvUFQyZ3dCcTYrS1pNd1pZS2MzNnVXOHdZSWcya2hqZUJDM1FPSTBpMEdNTUNsZ1RDODBCTXBwaHJCekxCdEJBWklMV3M0OHNjRS9CdHJPOGpUT1RmZk51WUlYT01JVEpFSnRJaHRiUmljUVNTMVcyczdjQmlpaGdxVTFnaHRnbHY5d0pqQ0krUUdqNlNHbUxBdDhIMzQ5elhZakZNcGhLVHNsRGM0NWN6bURHRXg4Z01YZ0RPMExtTXdxTFY0K0xmUkRoYnB2S1l4K1VhRFA2ak5pWGF5QmxCNnpDa3p2OERRZDdRck1iTFIxQUFBQUFBU1VWT1JLNUNZSUk9Ij4KCjxzdHlsZT4KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNDAwOwogIHNyYzogbG9jYWwoJ1JvYm90bycpLCBsb2NhbCgnUm9ib3RvLVJlZ3VsYXInKSwgdXJsKC9mb250LXJvYm90by91WUVDTUtvSGNPOXgxd2RtYnlISW0zLV9rZjZCeVlPNkNMWWRCNEhRRS1ZLndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDAwLTA0NUYsIFUrMDQ5MC0wNDkxLCBVKzA0QjAtMDRCMSwgVSsyMTE2Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8nKSwgbG9jYWwoJ1JvYm90by1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vc1RkYUE2ajBQc2I5MjBWanYtbXJ6SC1fa2Y2QnlZTzZDTFlkQjRIUUUtWS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQ2MC0wNTJGLCBVKzIwQjQsIFUrMkRFMC0yREZGLCBVK0E2NDAtQTY5RjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvJyksIGxvY2FsKCdSb2JvdG8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL19WWUZ4LXM4MjRrWHFfVWwyQkhxWUgtX2tmNkJ5WU82Q0xZZEI0SFFFLVkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAzNzAtMDNGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvJyksIGxvY2FsKCdSb2JvdG8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL3RuajRTQjZETmJkYVFuc004Q0ZxQlgtX2tmNkJ5WU82Q0xZZEI0SFFFLVkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzFGMDAtMUZGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvJyksIGxvY2FsKCdSb2JvdG8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL29NTWdmWk1RdGhPcnlRbzluMjJkY3V2dkRpbjFwSzhhS3RlTHBlWjVjMEEud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAwMDAtMDBGRiwgVSswMTMxLCBVKzAxNTItMDE1MywgVSswMkM2LCBVKzAyREEsIFUrMDJEQywgVSsyMDAwLTIwNkYsIFUrMjA3NCwgVSsyMEFDLCBVKzIyMTIsIFUrMjIxNTsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvJyksIGxvY2FsKCdSb2JvdG8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL0tzX2NWeGlDaXdVV1ZzRldGQTNCam4tX2tmNkJ5WU82Q0xZZEI0SFFFLVkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDAtMDI0RiwgVSsxRTAwLTFFRkYsIFUrMjBBMC0yMEFCLCBVKzIwQUQtMjBDRiwgVSsyQzYwLTJDN0YsIFUrQTcyMC1BN0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8nKSwgbG9jYWwoJ1JvYm90by1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vTko0dnhsZ1d3V2JFc3YxOGRBaHFubi1fa2Y2QnlZTzZDTFlkQjRIUUUtWS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMi0wMTAzLCBVKzFFQTAtMUVGOSwgVSsyMEFCOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by9pc1otd2JDWE5LQWJuam82X1R3SFRvWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDAwLTA0NUYsIFUrMDQ5MC0wNDkxLCBVKzA0QjAtMDRCMSwgVSsyMTE2Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by83N0ZYRmpSYkd6TjRhQ3JTRmhsaDNvWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDYwLTA1MkYsIFUrMjBCNCwgVSsyREUwLTJERkYsIFUrQTY0MC1BNjlGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by9qU04yQ0dWRGJjVnlDbmZKZmpTZGZJWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMzcwLTAzRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBCb2xkJyksIGxvY2FsKCdSb2JvdG8tQm9sZCcpLCB1cmwoL2ZvbnQtcm9ib3RvL1VYNmk0SnhRRG0zZlZUYzFDUHV3cW9YMGhWZ3paUVVmUkR1WnJQdkgzRDgud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzFGMDAtMUZGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIEJvbGQnKSwgbG9jYWwoJ1JvYm90by1Cb2xkJyksIHVybCgvZm9udC1yb2JvdG8vZC02SVlwbE9Gb2NDYWNLenh3WFNPSkJ3MXhVMXJLcHRKal8wamFuczkyMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDAwMC0wMEZGLCBVKzAxMzEsIFUrMDE1Mi0wMTUzLCBVKzAyQzYsIFUrMDJEQSwgVSswMkRDLCBVKzIwMDAtMjA2RiwgVSsyMDc0LCBVKzIwQUMsIFUrMjIxMiwgVSsyMjE1Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by85N3VhaHhpcVpSb25jQmFDRUkzYVc0WDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMTAwLTAyNEYsIFUrMUUwMC0xRUZGLCBVKzIwQTAtMjBBQiwgVSsyMEFELTIwQ0YsIFUrMkM2MC0yQzdGLCBVK0E3MjAtQTdGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIEJvbGQnKSwgbG9jYWwoJ1JvYm90by1Cb2xkJyksIHVybCgvZm9udC1yb2JvdG8vUHdaYy1ZYklMNDE0d0I5ckIxSUFQWVgwaFZnelpRVWZSRHVaclB2SDNEOC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMi0wMTAzLCBVKzFFQTAtMUVGOSwgVSsyMEFCOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gQm9sZCBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1Cb2xkSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vdDZOZDRjZlBSaFpQNDRRNVFBamNDMTRzWVlkSmc1ZFUycXpKRVZTdXRhMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQwMC0wNDVGLCBVKzA0OTAtMDQ5MSwgVSswNEIwLTA0QjEsIFUrMjExNjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIEJvbGQgSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tQm9sZEl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL3Q2TmQ0Y2ZQUmhaUDQ0UTVRQWpjQ19acmFSMlRnOHcybHptN2tMTkwwLXcud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzA0NjAtMDUyRiwgVSsyMEI0LCBVKzJERTAtMkRGRiwgVStBNjQwLUE2OUY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBCb2xkIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUJvbGRJdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by90Nk5kNGNmUFJoWlA0NFE1UUFqY0N3dF9SbTY5MUxUZWJLZlkyWmtLU21JLndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMzcwLTAzRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBCb2xkIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUJvbGRJdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by90Nk5kNGNmUFJoWlA0NFE1UUFqY0MxQlcyNlF4cFNqLV9aS21feFQ0aFd3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSsxRjAwLTFGRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBCb2xkIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUJvbGRJdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by90Nk5kNGNmUFJoWlA0NFE1UUFqY0M0Z3A5UThnYllyaHFHbFJhdl9JWGZrLndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMDAwLTAwRkYsIFUrMDEzMSwgVSswMTUyLTAxNTMsIFUrMDJDNiwgVSswMkRBLCBVKzAyREMsIFUrMjAwMC0yMDZGLCBVKzIwNzQsIFUrMjBBQywgVSsyMjEyLCBVKzIyMTU7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBCb2xkIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUJvbGRJdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by90Nk5kNGNmUFJoWlA0NFE1UUFqY0M2RThrTTR4V1IxXzFiWVVSUm9qUkdjLndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMTAwLTAyNEYsIFUrMUUwMC0xRUZGLCBVKzIwQTAtMjBBQiwgVSsyMEFELTIwQ0YsIFUrMkM2MC0yQzdGLCBVK0E3MjAtQTdGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIEJvbGQgSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tQm9sZEl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL3Q2TmQ0Y2ZQUmhaUDQ0UTVRQWpjQzlEaU5zUjVhLTlPZV9JdnB1OFhXbFkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDItMDEwMywgVSsxRUEwLTFFRjksIFUrMjBBQjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL09wWFVxVG8wVWdRUWhHal9TRmRMV0JrQXo0clluNDdaeTJydmlnV1FmNncud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzA0MDAtMDQ1RiwgVSswNDkwLTA0OTEsIFUrMDRCMC0wNEIxLCBVKzIxMTY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNDAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1JdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by9XeHJYSmEwQzNLZHRDN2xNYWZHNGRSa0F6NHJZbjQ3WnkycnZpZ1dRZjZ3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDYwLTA1MkYsIFUrMjBCNCwgVSsyREUwLTJERkYsIFUrQTY0MC1BNjlGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vY0RLaFJhWG5RVE9WYmFveHdkT3I5eGtBejRyWW40N1p5MnJ2aWdXUWY2dy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDM3MC0wM0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vMWhaZjAyUE9BTmgzMmsyVmtnRW9VQmtBejRyWW40N1p5MnJ2aWdXUWY2dy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMUYwMC0xRkZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vdlBjeW5TTDBxSHFfNmRYN2xLVkJ5WFloamJTcHZjNDdlZTZ4Ul84MEhudy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDAwMC0wMEZGLCBVKzAxMzEsIFUrMDE1Mi0wMTUzLCBVKzAyQzYsIFUrMDJEQSwgVSswMkRDLCBVKzIwMDAtMjA2RiwgVSsyMDc0LCBVKzIwQUMsIFUrMjIxMiwgVSsyMjE1Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vdlN6dWxmS1NLMExMampmZWF4Y1JFaGtBejRyWW40N1p5MnJ2aWdXUWY2dy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMC0wMjRGLCBVKzFFMDAtMUVGRiwgVSsyMEEwLTIwQUIsIFUrMjBBRC0yMENGLCBVKzJDNjAtMkM3RiwgVStBNzIwLUE3RkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNDAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1JdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by9LMjNjeFdWVHJJRkQ2REpzRVZpMDdSa0F6NHJZbjQ3WnkycnZpZ1dRZjZ3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMTAyLTAxMDMsIFUrMUVBMC0xRUY5LCBVKzIwQUI7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogMzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBMaWdodCcpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0JyksIHVybCgvZm9udC1yb2JvdG8vRmw0eTBRZE94eXlUSEVHTVhYOGtjWVgwaFZnelpRVWZSRHVaclB2SDNEOC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQwMC0wNDVGLCBVKzA0OTAtMDQ5MSwgVSswNEIwLTA0QjEsIFUrMjExNjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0JyksIGxvY2FsKCdSb2JvdG8tTGlnaHQnKSwgdXJsKC9mb250LXJvYm90by8wZUM2ZmwwNmx1WEVZV3BCU0p2WENJWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDYwLTA1MkYsIFUrMjBCNCwgVSsyREUwLTJERkYsIFUrQTY0MC1BNjlGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDMwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTGlnaHQnKSwgbG9jYWwoJ1JvYm90by1MaWdodCcpLCB1cmwoL2ZvbnQtcm9ib3RvL0kzUzF3c2dTZzlZQ3VyVjZQVWtUT1lYMGhWZ3paUVVmUkR1WnJQdkgzRDgud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAzNzAtMDNGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0JyksIGxvY2FsKCdSb2JvdG8tTGlnaHQnKSwgdXJsKC9mb250LXJvYm90by8tTDE0SmswNm02cFVIQi01bVhRUW5ZWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSsxRjAwLTFGRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogMzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBMaWdodCcpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0JyksIHVybCgvZm9udC1yb2JvdG8vSGdvMTNrLXRmU3BuMHFpMVNGZFVmWkJ3MXhVMXJLcHRKal8wamFuczkyMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDAwMC0wMEZGLCBVKzAxMzEsIFUrMDE1Mi0wMTUzLCBVKzAyQzYsIFUrMDJEQSwgVSswMkRDLCBVKzIwMDAtMjA2RiwgVSsyMDc0LCBVKzIwQUMsIFUrMjIxMiwgVSsyMjE1Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDMwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTGlnaHQnKSwgbG9jYWwoJ1JvYm90by1MaWdodCcpLCB1cmwoL2ZvbnQtcm9ib3RvL1BydTMzcWpTaHBaU21HM3o2Vll3bllYMGhWZ3paUVVmUkR1WnJQdkgzRDgud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDAtMDI0RiwgVSsxRTAwLTFFRkYsIFUrMjBBMC0yMEFCLCBVKzIwQUQtMjBDRiwgVSsyQzYwLTJDN0YsIFUrQTcyMC1BN0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDMwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTGlnaHQnKSwgbG9jYWwoJ1JvYm90by1MaWdodCcpLCB1cmwoL2ZvbnQtcm9ib3RvL05ZRFdCZEQ0Z0lxMjZHNVhZYkhzRklYMGhWZ3paUVVmUkR1WnJQdkgzRDgud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDItMDEwMywgVSsxRUEwLTFFRjksIFUrMjBBQjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0IEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0SXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vN204bDdUbEZPLVMzVmtoSHVSMGF0MTRzWVlkSmc1ZFUycXpKRVZTdXRhMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQwMC0wNDVGLCBVKzA0OTAtMDQ5MSwgVSswNEIwLTA0QjEsIFUrMjExNjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0IEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0SXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vN204bDdUbEZPLVMzVmtoSHVSMGF0X1pyYVIyVGc4dzJsem03a0xOTDAtdy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQ2MC0wNTJGLCBVKzIwQjQsIFUrMkRFMC0yREZGLCBVK0E2NDAtQTY5RjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0IEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0SXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vN204bDdUbEZPLVMzVmtoSHVSMGF0d3RfUm02OTFMVGViS2ZZMlprS1NtSS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDM3MC0wM0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDMwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTGlnaHQgSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tTGlnaHRJdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by83bThsN1RsRk8tUzNWa2hIdVIwYXQxQlcyNlF4cFNqLV9aS21feFQ0aFd3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSsxRjAwLTFGRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogMzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBMaWdodCBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1MaWdodEl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvLzdtOGw3VGxGTy1TM1ZraEh1UjBhdDRncDlROGdiWXJocUdsUmF2X0lYZmsud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAwMDAtMDBGRiwgVSswMTMxLCBVKzAxNTItMDE1MywgVSswMkM2LCBVKzAyREEsIFUrMDJEQywgVSsyMDAwLTIwNkYsIFUrMjA3NCwgVSsyMEFDLCBVKzIyMTIsIFUrMjIxNTsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiAzMDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIExpZ2h0IEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLUxpZ2h0SXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vN204bDdUbEZPLVMzVmtoSHVSMGF0NkU4a000eFdSMV8xYllVUlJvalJHYy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMC0wMjRGLCBVKzFFMDAtMUVGRiwgVSsyMEEwLTIwQUIsIFUrMjBBRC0yMENGLCBVKzJDNjAtMkM3RiwgVStBNzIwLUE3RkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogMzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBMaWdodCBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1MaWdodEl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvLzdtOGw3VGxGTy1TM1ZraEh1UjBhdDlEaU5zUjVhLTlPZV9JdnB1OFhXbFkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDItMDEwMywgVSsxRUEwLTFFRjksIFUrMjBBQjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA1MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1lZGl1bScpLCBsb2NhbCgnUm9ib3RvLU1lZGl1bScpLCB1cmwoL2ZvbnQtcm9ib3RvL29IaTMwa3dRV3ZwQ1dxQWh6SGNDU0lYMGhWZ3paUVVmUkR1WnJQdkgzRDgud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzA0MDAtMDQ1RiwgVSswNDkwLTA0OTEsIFUrMDRCMC0wNEIxLCBVKzIxMTY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNTAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNZWRpdW0nKSwgbG9jYWwoJ1JvYm90by1NZWRpdW0nKSwgdXJsKC9mb250LXJvYm90by9aTHFLZWVsWWJBVEc2MEVwWkJTRHk0WDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDYwLTA1MkYsIFUrMjBCNCwgVSsyREUwLTJERkYsIFUrQTY0MC1BNjlGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtJyksIHVybCgvZm9udC1yb2JvdG8vbXg5VWNrNnVCNjNWSUtGWW5FTVhyWVgwaFZnelpRVWZSRHVaclB2SDNEOC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDM3MC0wM0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtJyksIHVybCgvZm9udC1yb2JvdG8vckd2SGRKbnIybDc1cWIwWU5EOU55SVgwaFZnelpRVWZSRHVaclB2SDNEOC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMUYwMC0xRkZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtJyksIHVybCgvZm9udC1yb2JvdG8vUnhaSmRuemVvM1I1elNleGdlOFVVWkJ3MXhVMXJLcHRKal8wamFuczkyMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDAwMC0wMEZGLCBVKzAxMzEsIFUrMDE1Mi0wMTUzLCBVKzAyQzYsIFUrMDJEQSwgVSswMkRDLCBVKzIwMDAtMjA2RiwgVSsyMDc0LCBVKzIwQUMsIFUrMjIxMiwgVSsyMjE1Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtJyksIHVybCgvZm9udC1yb2JvdG8vb09lRndaTmxyVGVmekxZbWxWVjFVSVgwaFZnelpRVWZSRHVaclB2SDNEOC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMC0wMjRGLCBVKzFFMDAtMUVGRiwgVSsyMEEwLTIwQUIsIFUrMjBBRC0yMENGLCBVKzJDNjAtMkM3RiwgVStBNzIwLUE3RkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNTAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNZWRpdW0nKSwgbG9jYWwoJ1JvYm90by1NZWRpdW0nKSwgdXJsKC9mb250LXJvYm90by9tYm1ocHJNSDY5Wmk2ZUVQQllWRmhZWDBoVmd6WlFVZlJEdVpyUHZIM0Q4LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMTAyLTAxMDMsIFUrMUVBMC0xRUY5LCBVKzIwQUI7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNTAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNZWRpdW0gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vT0xmZkdCVGFGMFhGT1cxZ251SEYwVjRzWVlkSmc1ZFUycXpKRVZTdXRhMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQwMC0wNDVGLCBVKzA0OTAtMDQ5MSwgVSswNEIwLTA0QjEsIFUrMjExNjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiA1MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1lZGl1bSBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1NZWRpdW1JdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by9PTGZmR0JUYUYwWEZPVzFnbnVIRjBmWnJhUjJUZzh3Mmx6bTdrTE5MMC13LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDYwLTA1MkYsIFUrMjBCNCwgVSsyREUwLTJERkYsIFUrQTY0MC1BNjlGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLU1lZGl1bUl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL09MZmZHQlRhRjBYRk9XMWdudUhGMFF0X1JtNjkxTFRlYktmWTJaa0tTbUkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAzNzAtMDNGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byc7CiAgZm9udC1zdHlsZTogaXRhbGljOwogIGZvbnQtd2VpZ2h0OiA1MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1lZGl1bSBJdGFsaWMnKSwgbG9jYWwoJ1JvYm90by1NZWRpdW1JdGFsaWMnKSwgdXJsKC9mb250LXJvYm90by9PTGZmR0JUYUYwWEZPVzFnbnVIRjBWQlcyNlF4cFNqLV9aS21feFQ0aFd3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSsxRjAwLTFGRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8nOwogIGZvbnQtc3R5bGU6IGl0YWxpYzsKICBmb250LXdlaWdodDogNTAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNZWRpdW0gSXRhbGljJyksIGxvY2FsKCdSb2JvdG8tTWVkaXVtSXRhbGljJyksIHVybCgvZm9udC1yb2JvdG8vT0xmZkdCVGFGMFhGT1cxZ251SEYwWWdwOVE4Z2JZcmhxR2xSYXZfSVhmay53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDAwMC0wMEZGLCBVKzAxMzEsIFUrMDE1Mi0wMTUzLCBVKzAyQzYsIFUrMDJEQSwgVSswMkRDLCBVKzIwMDAtMjA2RiwgVSsyMDc0LCBVKzIwQUMsIFUrMjIxMiwgVSsyMjE1Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLU1lZGl1bUl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL09MZmZHQlRhRjBYRk9XMWdudUhGMGFFOGtNNHhXUjFfMWJZVVJSb2pSR2Mud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDAtMDI0RiwgVSsxRTAwLTFFRkYsIFUrMjBBMC0yMEFCLCBVKzIwQUQtMjBDRiwgVSsyQzYwLTJDN0YsIFUrQTcyMC1BN0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvJzsKICBmb250LXN0eWxlOiBpdGFsaWM7CiAgZm9udC13ZWlnaHQ6IDUwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTWVkaXVtIEl0YWxpYycpLCBsb2NhbCgnUm9ib3RvLU1lZGl1bUl0YWxpYycpLCB1cmwoL2ZvbnQtcm9ib3RvL09MZmZHQlRhRjBYRk9XMWdudUhGMGREaU5zUjVhLTlPZV9JdnB1OFhXbFkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDItMDEwMywgVSsxRUEwLTFFRjksIFUrMjBBQjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubycpLCBsb2NhbCgnUm9ib3RvTW9uby1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vaE1xUE5Mc3VfZHl3TWE0Q19ERXBZMTRzWVlkSmc1ZFUycXpKRVZTdXRhMC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQwMC0wNDVGLCBVKzA0OTAtMDQ5MSwgVSswNEIwLTA0QjEsIFUrMjExNjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubycpLCBsb2NhbCgnUm9ib3RvTW9uby1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vaE1xUE5Mc3VfZHl3TWE0Q19ERXBZX1pyYVIyVGc4dzJsem03a0xOTDAtdy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDQ2MC0wNTJGLCBVKzIwQjQsIFUrMkRFMC0yREZGLCBVK0E2NDAtQTY5RjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubycpLCBsb2NhbCgnUm9ib3RvTW9uby1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vaE1xUE5Mc3VfZHl3TWE0Q19ERXBZd3RfUm02OTFMVGViS2ZZMlprS1NtSS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDM3MC0wM0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvIE1vbm8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNDAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNb25vJyksIGxvY2FsKCdSb2JvdG9Nb25vLVJlZ3VsYXInKSwgdXJsKC9mb250LXJvYm90by9oTXFQTkxzdV9keXdNYTRDX0RFcFkxQlcyNlF4cFNqLV9aS21feFQ0aFd3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSsxRjAwLTFGRkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8gTW9ubyc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1vbm8nKSwgbG9jYWwoJ1JvYm90b01vbm8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL2hNcVBOTHN1X2R5d01hNENfREVwWTRncDlROGdiWXJocUdsUmF2X0lYZmsud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAwMDAtMDBGRiwgVSswMTMxLCBVKzAxNTItMDE1MywgVSswMkM2LCBVKzAyREEsIFUrMDJEQywgVSsyMDAwLTIwNkYsIFUrMjA3NCwgVSsyMEFDLCBVKzIyMTIsIFUrMjIxNTsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDQwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubycpLCBsb2NhbCgnUm9ib3RvTW9uby1SZWd1bGFyJyksIHVybCgvZm9udC1yb2JvdG8vaE1xUE5Mc3VfZHl3TWE0Q19ERXBZNkU4a000eFdSMV8xYllVUlJvalJHYy53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMC0wMjRGLCBVKzFFMDAtMUVGRiwgVSsyMEEwLTIwQUIsIFUrMjBBRC0yMENGLCBVKzJDNjAtMkM3RiwgVStBNzIwLUE3RkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8gTW9ubyc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA0MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1vbm8nKSwgbG9jYWwoJ1JvYm90b01vbm8tUmVndWxhcicpLCB1cmwoL2ZvbnQtcm9ib3RvL2hNcVBOTHN1X2R5d01hNENfREVwWTlEaU5zUjVhLTlPZV9JdnB1OFhXbFkud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzAxMDItMDEwMywgVSsxRUEwLTFFRjksIFUrMjBBQjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubyBCb2xkJyksIGxvY2FsKCdSb2JvdG9Nb25vLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by9ONGR1VmM5QzU4dXdQaVk4XzU5RnoxeC1NMUkxdzVPTWlxblZGOHhCTGhVLndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswNDAwLTA0NUYsIFUrMDQ5MC0wNDkxLCBVKzA0QjAtMDRCMSwgVSsyMTE2Owp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvIE1vbm8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNb25vIEJvbGQnKSwgbG9jYWwoJ1JvYm90b01vbm8tQm9sZCcpLCB1cmwoL2ZvbnQtcm9ib3RvL040ZHVWYzlDNTh1d1BpWThfNTlGendYYUFYdXA1bVpsZks2eFJMcmhzY28ud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzA0NjAtMDUyRiwgVSsyMEI0LCBVKzJERTAtMkRGRiwgVStBNjQwLUE2OUY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8gTW9ubyc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1vbm8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvTW9uby1Cb2xkJyksIHVybCgvZm9udC1yb2JvdG8vTjRkdVZjOUM1OHV3UGlZOF81OUZ6d242V3F4by14d3hpbERYUFU4Y2hWVS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDM3MC0wM0ZGOwp9CkBmb250LWZhY2UgewogIGZvbnQtZmFtaWx5OiAnUm9ib3RvIE1vbm8nOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKICBmb250LXdlaWdodDogNzAwOwogIHNyYzogbG9jYWwoJ1JvYm90byBNb25vIEJvbGQnKSwgbG9jYWwoJ1JvYm90b01vbm8tQm9sZCcpLCB1cmwoL2ZvbnQtcm9ib3RvL040ZHVWYzlDNTh1d1BpWThfNTlGejFUN2FKTEs2bktwbjM2SU13VGNNTWMud29mZjIpIGZvcm1hdCgnd29mZjInKTsKICB1bmljb2RlLXJhbmdlOiBVKzFGMDAtMUZGRjsKfQpAZm9udC1mYWNlIHsKICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJzsKICBmb250LXN0eWxlOiBub3JtYWw7CiAgZm9udC13ZWlnaHQ6IDcwMDsKICBzcmM6IGxvY2FsKCdSb2JvdG8gTW9ubyBCb2xkJyksIGxvY2FsKCdSb2JvdG9Nb25vLUJvbGQnKSwgdXJsKC9mb250LXJvYm90by9ONGR1VmM5QzU4dXdQaVk4XzU5RnpfNzlfWnVVeENpZ00yRGVzcFRuRmF3LndvZmYyKSBmb3JtYXQoJ3dvZmYyJyk7CiAgdW5pY29kZS1yYW5nZTogVSswMDAwLTAwRkYsIFUrMDEzMSwgVSswMTUyLTAxNTMsIFUrMDJDNiwgVSswMkRBLCBVKzAyREMsIFUrMjAwMC0yMDZGLCBVKzIwNzQsIFUrMjBBQywgVSsyMjEyLCBVKzIyMTU7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8gTW9ubyc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1vbm8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvTW9uby1Cb2xkJyksIHVybCgvZm9udC1yb2JvdG8vTjRkdVZjOUM1OHV3UGlZOF81OUZ6NGdkOU9FUFVDTjNBZFlXMGU4dGF0NC53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMC0wMjRGLCBVKzFFMDAtMUVGRiwgVSsyMEEwLTIwQUIsIFUrMjBBRC0yMENGLCBVKzJDNjAtMkM3RiwgVStBNzIwLUE3RkY7Cn0KQGZvbnQtZmFjZSB7CiAgZm9udC1mYW1pbHk6ICdSb2JvdG8gTW9ubyc7CiAgZm9udC1zdHlsZTogbm9ybWFsOwogIGZvbnQtd2VpZ2h0OiA3MDA7CiAgc3JjOiBsb2NhbCgnUm9ib3RvIE1vbm8gQm9sZCcpLCBsb2NhbCgnUm9ib3RvTW9uby1Cb2xkJyksIHVybCgvZm9udC1yb2JvdG8vTjRkdVZjOUM1OHV3UGlZOF81OUZ6OGJJUVNZWm5XTGFXQzlRTkNwVEtfVS53b2ZmMikgZm9ybWF0KCd3b2ZmMicpOwogIHVuaWNvZGUtcmFuZ2U6IFUrMDEwMi0wMTAzLCBVKzFFQTAtMUVGOSwgVSsyMEFCOwp9Cjwvc3R5bGU+CgoKCjxzdHlsZT4ubWF0LWJhZGdlLWNvbnRlbnR7Zm9udC13ZWlnaHQ6NjAwO2ZvbnQtc2l6ZToxMnB4O2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LWJhZGdlLXNtYWxsIC5tYXQtYmFkZ2UtY29udGVudHtmb250LXNpemU6OXB4fS5tYXQtYmFkZ2UtbGFyZ2UgLm1hdC1iYWRnZS1jb250ZW50e2ZvbnQtc2l6ZToyNHB4fS5tYXQtaDEsLm1hdC1oZWFkbGluZSwubWF0LXR5cG9ncmFwaHkgaDF7Zm9udDo0MDAgMjRweC8zMnB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWw7bWFyZ2luOjAgMCAxNnB4fS5tYXQtaDIsLm1hdC10aXRsZSwubWF0LXR5cG9ncmFwaHkgaDJ7Zm9udDo1MDAgMjBweC8zMnB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWw7bWFyZ2luOjAgMCAxNnB4fS5tYXQtaDMsLm1hdC1zdWJoZWFkaW5nLTIsLm1hdC10eXBvZ3JhcGh5IGgze2ZvbnQ6NDAwIDE2cHgvMjhweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bGV0dGVyLXNwYWNpbmc6bm9ybWFsO21hcmdpbjowIDAgMTZweH0ubWF0LWg0LC5tYXQtc3ViaGVhZGluZy0xLC5tYXQtdHlwb2dyYXBoeSBoNHtmb250OjQwMCAxNXB4LzI0cHggUm9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmO2xldHRlci1zcGFjaW5nOm5vcm1hbDttYXJnaW46MCAwIDE2cHh9Lm1hdC1oNSwubWF0LXR5cG9ncmFwaHkgaDV7Zm9udDo0MDAgY2FsYygxNHB4ICogMC44MykvMjBweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bWFyZ2luOjAgMCAxMnB4fS5tYXQtaDYsLm1hdC10eXBvZ3JhcGh5IGg2e2ZvbnQ6NDAwIGNhbGMoMTRweCAqIDAuNjcpLzIwcHggUm9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmO21hcmdpbjowIDAgMTJweH0ubWF0LWJvZHktc3Ryb25nLC5tYXQtYm9keS0ye2ZvbnQ6NTAwIDE0cHgvMjRweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bGV0dGVyLXNwYWNpbmc6bm9ybWFsfS5tYXQtYm9keSwubWF0LWJvZHktMSwubWF0LXR5cG9ncmFwaHl7Zm9udDo0MDAgMTRweC8yMHB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWx9Lm1hdC1ib2R5IHAsLm1hdC1ib2R5LTEgcCwubWF0LXR5cG9ncmFwaHkgcHttYXJnaW46MCAwIDEycHh9Lm1hdC1zbWFsbCwubWF0LWNhcHRpb257Zm9udDo0MDAgMTJweC8yMHB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWx9Lm1hdC1kaXNwbGF5LTQsLm1hdC10eXBvZ3JhcGh5IC5tYXQtZGlzcGxheS00e2ZvbnQ6MzAwIDExMnB4LzExMnB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzotMC4wNWVtO21hcmdpbjowIDAgNTZweH0ubWF0LWRpc3BsYXktMywubWF0LXR5cG9ncmFwaHkgLm1hdC1kaXNwbGF5LTN7Zm9udDo0MDAgNTZweC81NnB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzotMC4wMmVtO21hcmdpbjowIDAgNjRweH0ubWF0LWRpc3BsYXktMiwubWF0LXR5cG9ncmFwaHkgLm1hdC1kaXNwbGF5LTJ7Zm9udDo0MDAgNDVweC80OHB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzotMC4wMDVlbTttYXJnaW46MCAwIDY0cHh9Lm1hdC1kaXNwbGF5LTEsLm1hdC10eXBvZ3JhcGh5IC5tYXQtZGlzcGxheS0xe2ZvbnQ6NDAwIDM0cHgvNDBweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bGV0dGVyLXNwYWNpbmc6bm9ybWFsO21hcmdpbjowIDAgNjRweH0ubWF0LWJvdHRvbS1zaGVldC1jb250YWluZXJ7Zm9udDo0MDAgMTRweC8yMHB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWx9Lm1hdC1idXR0b24sLm1hdC1yYWlzZWQtYnV0dG9uLC5tYXQtaWNvbi1idXR0b24sLm1hdC1zdHJva2VkLWJ1dHRvbiwubWF0LWZsYXQtYnV0dG9uLC5tYXQtZmFiLC5tYXQtbWluaS1mYWJ7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmO2ZvbnQtc2l6ZToxNHB4O2ZvbnQtd2VpZ2h0OjUwMH0ubWF0LWJ1dHRvbi10b2dnbGV7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmfS5tYXQtY2FyZHtmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWZ9Lm1hdC1jYXJkLXRpdGxle2ZvbnQtc2l6ZToyNHB4O2ZvbnQtd2VpZ2h0OjUwMH0ubWF0LWNhcmQtaGVhZGVyIC5tYXQtY2FyZC10aXRsZXtmb250LXNpemU6MjBweH0ubWF0LWNhcmQtc3VidGl0bGUsLm1hdC1jYXJkLWNvbnRlbnR7Zm9udC1zaXplOjE0cHh9Lm1hdC1jaGVja2JveHtmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWZ9Lm1hdC1jaGVja2JveC1sYXlvdXQgLm1hdC1jaGVja2JveC1sYWJlbHtsaW5lLWhlaWdodDoyNHB4fS5tYXQtY2hpcHtmb250LXNpemU6MTRweDtmb250LXdlaWdodDo1MDB9Lm1hdC1jaGlwIC5tYXQtY2hpcC10cmFpbGluZy1pY29uLm1hdC1pY29uLC5tYXQtY2hpcCAubWF0LWNoaXAtcmVtb3ZlLm1hdC1pY29ue2ZvbnQtc2l6ZToxOHB4fS5tYXQtdGFibGV7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmfS5tYXQtaGVhZGVyLWNlbGx7Zm9udC1zaXplOjEycHg7Zm9udC13ZWlnaHQ6NTAwfS5tYXQtY2VsbCwubWF0LWZvb3Rlci1jZWxse2ZvbnQtc2l6ZToxNHB4fS5tYXQtY2FsZW5kYXJ7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmfS5tYXQtY2FsZW5kYXItYm9keXtmb250LXNpemU6MTNweH0ubWF0LWNhbGVuZGFyLWJvZHktbGFiZWwsLm1hdC1jYWxlbmRhci1wZXJpb2QtYnV0dG9ue2ZvbnQtc2l6ZToxNHB4O2ZvbnQtd2VpZ2h0OjUwMH0ubWF0LWNhbGVuZGFyLXRhYmxlLWhlYWRlciB0aHtmb250LXNpemU6MTFweDtmb250LXdlaWdodDo0MDB9Lm1hdC1kaWFsb2ctdGl0bGV7Zm9udDo1MDAgMjBweC8zMnB4IFJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWx9Lm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVye2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTVweDtmb250LXdlaWdodDo0MDB9Lm1hdC1leHBhbnNpb24tcGFuZWwtY29udGVudHtmb250OjQwMCAxNHB4LzIwcHggUm9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmO2xldHRlci1zcGFjaW5nOm5vcm1hbH0ubWF0LWZvcm0tZmllbGR7Zm9udC1zaXplOmluaGVyaXQ7Zm9udC13ZWlnaHQ6NDAwO2xpbmUtaGVpZ2h0OjEuMTI1O2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtsZXR0ZXItc3BhY2luZzpub3JtYWx9Lm1hdC1mb3JtLWZpZWxkLXdyYXBwZXJ7cGFkZGluZy1ib3R0b206MS4zNDM3NWVtfS5tYXQtZm9ybS1maWVsZC1wcmVmaXggLm1hdC1pY29uLC5tYXQtZm9ybS1maWVsZC1zdWZmaXggLm1hdC1pY29ue2ZvbnQtc2l6ZToxNTAlO2xpbmUtaGVpZ2h0OjEuMTI1fS5tYXQtZm9ybS1maWVsZC1wcmVmaXggLm1hdC1pY29uLWJ1dHRvbiwubWF0LWZvcm0tZmllbGQtc3VmZml4IC5tYXQtaWNvbi1idXR0b257aGVpZ2h0OjEuNWVtO3dpZHRoOjEuNWVtfS5tYXQtZm9ybS1maWVsZC1wcmVmaXggLm1hdC1pY29uLWJ1dHRvbiAubWF0LWljb24sLm1hdC1mb3JtLWZpZWxkLXN1ZmZpeCAubWF0LWljb24tYnV0dG9uIC5tYXQtaWNvbntoZWlnaHQ6MS4xMjVlbTtsaW5lLWhlaWdodDoxLjEyNX0ubWF0LWZvcm0tZmllbGQtaW5maXh7cGFkZGluZzouNWVtIDA7Ym9yZGVyLXRvcDouODQzNzVlbSBzb2xpZCB0cmFuc3BhcmVudH0ubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0Lm1hdC1mb3JtLWZpZWxkLXNob3VsZC1mbG9hdCAubWF0LWZvcm0tZmllbGQtbGFiZWwsLm1hdC1mb3JtLWZpZWxkLWNhbi1mbG9hdCAubWF0LWlucHV0LXNlcnZlcjpmb2N1cysubWF0LWZvcm0tZmllbGQtbGFiZWwtd3JhcHBlciAubWF0LWZvcm0tZmllbGQtbGFiZWx7dHJhbnNmb3JtOnRyYW5zbGF0ZVkoLTEuMzQzNzVlbSkgc2NhbGUoMC43NSk7d2lkdGg6MTMzLjMzMzMzMzMzMzMlfS5tYXQtZm9ybS1maWVsZC1jYW4tZmxvYXQgLm1hdC1pbnB1dC1zZXJ2ZXJbbGFiZWxdOm5vdCg6bGFiZWwtc2hvd24pKy5tYXQtZm9ybS1maWVsZC1sYWJlbC13cmFwcGVyIC5tYXQtZm9ybS1maWVsZC1sYWJlbHt0cmFuc2Zvcm06dHJhbnNsYXRlWSgtMS4zNDM3NGVtKSBzY2FsZSgwLjc1KTt3aWR0aDoxMzMuMzMzMzQzMzMzMyV9Lm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXJ7dG9wOi0wLjg0Mzc1ZW07cGFkZGluZy10b3A6Ljg0Mzc1ZW19Lm1hdC1mb3JtLWZpZWxkLWxhYmVse3RvcDoxLjM0Mzc1ZW19Lm1hdC1mb3JtLWZpZWxkLXVuZGVybGluZXtib3R0b206MS4zNDM3NWVtfS5tYXQtZm9ybS1maWVsZC1zdWJzY3JpcHQtd3JhcHBlcntmb250LXNpemU6NzUlO21hcmdpbi10b3A6LjY2NjY2NjY2NjdlbTt0b3A6Y2FsYygxMDAlIC0gMS43OTE2NjY2NjY3ZW0pfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeSAubWF0LWZvcm0tZmllbGQtd3JhcHBlcntwYWRkaW5nLWJvdHRvbToxLjI1ZW19Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2UtbGVnYWN5IC5tYXQtZm9ybS1maWVsZC1pbmZpeHtwYWRkaW5nOi40Mzc1ZW0gMH0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0Lm1hdC1mb3JtLWZpZWxkLXNob3VsZC1mbG9hdCAubWF0LWZvcm0tZmllbGQtbGFiZWwsLm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2UtbGVnYWN5Lm1hdC1mb3JtLWZpZWxkLWNhbi1mbG9hdCAubWF0LWlucHV0LXNlcnZlcjpmb2N1cysubWF0LWZvcm0tZmllbGQtbGFiZWwtd3JhcHBlciAubWF0LWZvcm0tZmllbGQtbGFiZWx7dHJhbnNmb3JtOnRyYW5zbGF0ZVkoLTEuMjgxMjVlbSkgc2NhbGUoMC43NSkgcGVyc3BlY3RpdmUoMTAwcHgpIHRyYW5zbGF0ZVooMC4wMDFweCk7LW1zLXRyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjI4MTI1ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzMzMzMzMzJX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0IC5tYXQtZm9ybS1maWVsZC1hdXRvZmlsbC1jb250cm9sOi13ZWJraXQtYXV0b2ZpbGwrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjI4MTI1ZW0pIHNjYWxlKDAuNzUpIHBlcnNwZWN0aXZlKDEwMHB4KSB0cmFuc2xhdGVaKDAuMDAxMDFweCk7LW1zLXRyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjI4MTI0ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzNDMzMzMzJX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0IC5tYXQtaW5wdXQtc2VydmVyW2xhYmVsXTpub3QoOmxhYmVsLXNob3duKSsubWF0LWZvcm0tZmllbGQtbGFiZWwtd3JhcHBlciAubWF0LWZvcm0tZmllbGQtbGFiZWx7dHJhbnNmb3JtOnRyYW5zbGF0ZVkoLTEuMjgxMjVlbSkgc2NhbGUoMC43NSkgcGVyc3BlY3RpdmUoMTAwcHgpIHRyYW5zbGF0ZVooMC4wMDEwMnB4KTstbXMtdHJhbnNmb3JtOnRyYW5zbGF0ZVkoLTEuMjgxMjNlbSkgc2NhbGUoMC43NSk7d2lkdGg6MTMzLjMzMzM1MzMzMzMlfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeSAubWF0LWZvcm0tZmllbGQtbGFiZWx7dG9wOjEuMjgxMjVlbX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kgLm1hdC1mb3JtLWZpZWxkLXVuZGVybGluZXtib3R0b206MS4yNWVtfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeSAubWF0LWZvcm0tZmllbGQtc3Vic2NyaXB0LXdyYXBwZXJ7bWFyZ2luLXRvcDouNTQxNjY2NjY2N2VtO3RvcDpjYWxjKDEwMCUgLSAxLjY2NjY2NjY2NjdlbSl9QG1lZGlhIHByaW50ey5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeS5tYXQtZm9ybS1maWVsZC1jYW4tZmxvYXQubWF0LWZvcm0tZmllbGQtc2hvdWxkLWZsb2F0IC5tYXQtZm9ybS1maWVsZC1sYWJlbCwubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0IC5tYXQtaW5wdXQtc2VydmVyOmZvY3VzKy5tYXQtZm9ybS1maWVsZC1sYWJlbC13cmFwcGVyIC5tYXQtZm9ybS1maWVsZC1sYWJlbHt0cmFuc2Zvcm06dHJhbnNsYXRlWSgtMS4yODEyMmVtKSBzY2FsZSgwLjc1KX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0IC5tYXQtZm9ybS1maWVsZC1hdXRvZmlsbC1jb250cm9sOi13ZWJraXQtYXV0b2ZpbGwrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjI4MTIxZW0pIHNjYWxlKDAuNzUpfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeS5tYXQtZm9ybS1maWVsZC1jYW4tZmxvYXQgLm1hdC1pbnB1dC1zZXJ2ZXJbbGFiZWxdOm5vdCg6bGFiZWwtc2hvd24pKy5tYXQtZm9ybS1maWVsZC1sYWJlbC13cmFwcGVyIC5tYXQtZm9ybS1maWVsZC1sYWJlbHt0cmFuc2Zvcm06dHJhbnNsYXRlWSgtMS4yODEyZW0pIHNjYWxlKDAuNzUpfX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1maWxsIC5tYXQtZm9ybS1maWVsZC1pbmZpeHtwYWRkaW5nOi4yNWVtIDAgLjc1ZW0gMH0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1maWxsIC5tYXQtZm9ybS1maWVsZC1sYWJlbHt0b3A6MS4wOTM3NWVtO21hcmdpbi10b3A6LTAuNWVtfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWZpbGwubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0Lm1hdC1mb3JtLWZpZWxkLXNob3VsZC1mbG9hdCAubWF0LWZvcm0tZmllbGQtbGFiZWwsLm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2UtZmlsbC5tYXQtZm9ybS1maWVsZC1jYW4tZmxvYXQgLm1hdC1pbnB1dC1zZXJ2ZXI6Zm9jdXMrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0wLjU5Mzc1ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzMzMzMzMzJX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1maWxsLm1hdC1mb3JtLWZpZWxkLWNhbi1mbG9hdCAubWF0LWlucHV0LXNlcnZlcltsYWJlbF06bm90KDpsYWJlbC1zaG93bikrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0wLjU5Mzc0ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzNDMzMzMzJX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1vdXRsaW5lIC5tYXQtZm9ybS1maWVsZC1pbmZpeHtwYWRkaW5nOjFlbSAwIDFlbSAwfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLW91dGxpbmUgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RvcDoxLjg0Mzc1ZW07bWFyZ2luLXRvcDotMC4yNWVtfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLW91dGxpbmUubWF0LWZvcm0tZmllbGQtY2FuLWZsb2F0Lm1hdC1mb3JtLWZpZWxkLXNob3VsZC1mbG9hdCAubWF0LWZvcm0tZmllbGQtbGFiZWwsLm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2Utb3V0bGluZS5tYXQtZm9ybS1maWVsZC1jYW4tZmxvYXQgLm1hdC1pbnB1dC1zZXJ2ZXI6Zm9jdXMrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjU5Mzc1ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzMzMzMzMzJX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1vdXRsaW5lLm1hdC1mb3JtLWZpZWxkLWNhbi1mbG9hdCAubWF0LWlucHV0LXNlcnZlcltsYWJlbF06bm90KDpsYWJlbC1zaG93bikrLm1hdC1mb3JtLWZpZWxkLWxhYmVsLXdyYXBwZXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVse3RyYW5zZm9ybTp0cmFuc2xhdGVZKC0xLjU5Mzc0ZW0pIHNjYWxlKDAuNzUpO3dpZHRoOjEzMy4zMzMzNDMzMzMzJX0ubWF0LWdyaWQtdGlsZS1oZWFkZXIsLm1hdC1ncmlkLXRpbGUtZm9vdGVye2ZvbnQtc2l6ZToxNHB4fS5tYXQtZ3JpZC10aWxlLWhlYWRlciAubWF0LWxpbmUsLm1hdC1ncmlkLXRpbGUtZm9vdGVyIC5tYXQtbGluZXt3aGl0ZS1zcGFjZTpub3dyYXA7b3ZlcmZsb3c6aGlkZGVuO3RleHQtb3ZlcmZsb3c6ZWxsaXBzaXM7ZGlzcGxheTpibG9jaztib3gtc2l6aW5nOmJvcmRlci1ib3h9Lm1hdC1ncmlkLXRpbGUtaGVhZGVyIC5tYXQtbGluZTpudGgtY2hpbGQobisyKSwubWF0LWdyaWQtdGlsZS1mb290ZXIgLm1hdC1saW5lOm50aC1jaGlsZChuKzIpe2ZvbnQtc2l6ZToxMnB4fWlucHV0Lm1hdC1pbnB1dC1lbGVtZW50e21hcmdpbi10b3A6LTAuMDYyNWVtfS5tYXQtbWVudS1pdGVte2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTRweDtmb250LXdlaWdodDo0MDB9Lm1hdC1wYWdpbmF0b3IsLm1hdC1wYWdpbmF0b3ItcGFnZS1zaXplIC5tYXQtc2VsZWN0LXRyaWdnZXJ7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmO2ZvbnQtc2l6ZToxMnB4fS5tYXQtcmFkaW8tYnV0dG9ue2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LXNlbGVjdHtmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWZ9Lm1hdC1zZWxlY3QtdHJpZ2dlcntoZWlnaHQ6MS4xMjVlbX0ubWF0LXNsaWRlLXRvZ2dsZS1jb250ZW50e2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LXNsaWRlci10aHVtYi1sYWJlbC10ZXh0e2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTJweDtmb250LXdlaWdodDo1MDB9Lm1hdC1zdGVwcGVyLXZlcnRpY2FsLC5tYXQtc3RlcHBlci1ob3Jpem9udGFse2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LXN0ZXAtbGFiZWx7Zm9udC1zaXplOjE0cHg7Zm9udC13ZWlnaHQ6NDAwfS5tYXQtc3RlcC1zdWItbGFiZWwtZXJyb3J7Zm9udC13ZWlnaHQ6bm9ybWFsfS5tYXQtc3RlcC1sYWJlbC1lcnJvcntmb250LXNpemU6MTRweH0ubWF0LXN0ZXAtbGFiZWwtc2VsZWN0ZWR7Zm9udC1zaXplOjE0cHg7Zm9udC13ZWlnaHQ6NTAwfS5tYXQtdGFiLWdyb3Vwe2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LXRhYi1sYWJlbCwubWF0LXRhYi1saW5re2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTRweDtmb250LXdlaWdodDo1MDB9Lm1hdC10b29sYmFyLC5tYXQtdG9vbGJhciBoMSwubWF0LXRvb2xiYXIgaDIsLm1hdC10b29sYmFyIGgzLC5tYXQtdG9vbGJhciBoNCwubWF0LXRvb2xiYXIgaDUsLm1hdC10b29sYmFyIGg2e2ZvbnQ6NTAwIDIwcHgvMzJweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bGV0dGVyLXNwYWNpbmc6bm9ybWFsO21hcmdpbjowfS5tYXQtdG9vbHRpcHtmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7Zm9udC1zaXplOjEwcHg7cGFkZGluZy10b3A6NnB4O3BhZGRpbmctYm90dG9tOjZweH0ubWF0LXRvb2x0aXAtaGFuZHNldHtmb250LXNpemU6MTRweDtwYWRkaW5nLXRvcDo4cHg7cGFkZGluZy1ib3R0b206OHB4fS5tYXQtbGlzdC1pdGVte2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LWxpc3Qtb3B0aW9ue2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZn0ubWF0LWxpc3QtYmFzZSAubWF0LWxpc3QtaXRlbXtmb250LXNpemU6MTZweH0ubWF0LWxpc3QtYmFzZSAubWF0LWxpc3QtaXRlbSAubWF0LWxpbmV7d2hpdGUtc3BhY2U6bm93cmFwO292ZXJmbG93OmhpZGRlbjt0ZXh0LW92ZXJmbG93OmVsbGlwc2lzO2Rpc3BsYXk6YmxvY2s7Ym94LXNpemluZzpib3JkZXItYm94fS5tYXQtbGlzdC1iYXNlIC5tYXQtbGlzdC1pdGVtIC5tYXQtbGluZTpudGgtY2hpbGQobisyKXtmb250LXNpemU6MTRweH0ubWF0LWxpc3QtYmFzZSAubWF0LWxpc3Qtb3B0aW9ue2ZvbnQtc2l6ZToxNnB4fS5tYXQtbGlzdC1iYXNlIC5tYXQtbGlzdC1vcHRpb24gLm1hdC1saW5le3doaXRlLXNwYWNlOm5vd3JhcDtvdmVyZmxvdzpoaWRkZW47dGV4dC1vdmVyZmxvdzplbGxpcHNpcztkaXNwbGF5OmJsb2NrO2JveC1zaXppbmc6Ym9yZGVyLWJveH0ubWF0LWxpc3QtYmFzZSAubWF0LWxpc3Qtb3B0aW9uIC5tYXQtbGluZTpudGgtY2hpbGQobisyKXtmb250LXNpemU6MTRweH0ubWF0LWxpc3QtYmFzZSAubWF0LXN1YmhlYWRlcntmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7Zm9udC1zaXplOjE0cHg7Zm9udC13ZWlnaHQ6NTAwfS5tYXQtbGlzdC1iYXNlW2RlbnNlXSAubWF0LWxpc3QtaXRlbXtmb250LXNpemU6MTJweH0ubWF0LWxpc3QtYmFzZVtkZW5zZV0gLm1hdC1saXN0LWl0ZW0gLm1hdC1saW5le3doaXRlLXNwYWNlOm5vd3JhcDtvdmVyZmxvdzpoaWRkZW47dGV4dC1vdmVyZmxvdzplbGxpcHNpcztkaXNwbGF5OmJsb2NrO2JveC1zaXppbmc6Ym9yZGVyLWJveH0ubWF0LWxpc3QtYmFzZVtkZW5zZV0gLm1hdC1saXN0LWl0ZW0gLm1hdC1saW5lOm50aC1jaGlsZChuKzIpe2ZvbnQtc2l6ZToxMnB4fS5tYXQtbGlzdC1iYXNlW2RlbnNlXSAubWF0LWxpc3Qtb3B0aW9ue2ZvbnQtc2l6ZToxMnB4fS5tYXQtbGlzdC1iYXNlW2RlbnNlXSAubWF0LWxpc3Qtb3B0aW9uIC5tYXQtbGluZXt3aGl0ZS1zcGFjZTpub3dyYXA7b3ZlcmZsb3c6aGlkZGVuO3RleHQtb3ZlcmZsb3c6ZWxsaXBzaXM7ZGlzcGxheTpibG9jaztib3gtc2l6aW5nOmJvcmRlci1ib3h9Lm1hdC1saXN0LWJhc2VbZGVuc2VdIC5tYXQtbGlzdC1vcHRpb24gLm1hdC1saW5lOm50aC1jaGlsZChuKzIpe2ZvbnQtc2l6ZToxMnB4fS5tYXQtbGlzdC1iYXNlW2RlbnNlXSAubWF0LXN1YmhlYWRlcntmb250LWZhbWlseTpSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7Zm9udC1zaXplOjEycHg7Zm9udC13ZWlnaHQ6NTAwfS5tYXQtb3B0aW9ue2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTZweH0ubWF0LW9wdGdyb3VwLWxhYmVse2ZvbnQ6NTAwIDE0cHgvMjRweCBSb2JvdG8sICJIZWx2ZXRpY2EgTmV1ZSIsIHNhbnMtc2VyaWY7bGV0dGVyLXNwYWNpbmc6bm9ybWFsfS5tYXQtc2ltcGxlLXNuYWNrYmFye2ZvbnQtZmFtaWx5OlJvYm90bywgIkhlbHZldGljYSBOZXVlIiwgc2Fucy1zZXJpZjtmb250LXNpemU6MTRweH0ubWF0LXNpbXBsZS1zbmFja2Jhci1hY3Rpb257bGluZS1oZWlnaHQ6MTtmb250LWZhbWlseTppbmhlcml0O2ZvbnQtc2l6ZTppbmhlcml0O2ZvbnQtd2VpZ2h0OjUwMH0ubWF0LXRyZWV7Zm9udC1mYW1pbHk6Um9ib3RvLCAiSGVsdmV0aWNhIE5ldWUiLCBzYW5zLXNlcmlmfS5tYXQtdHJlZS1ub2RlLC5tYXQtbmVzdGVkLXRyZWUtbm9kZXtmb250LXdlaWdodDo0MDA7Zm9udC1zaXplOjE0cHh9Lm1hdC1yaXBwbGV7b3ZlcmZsb3c6aGlkZGVuO3Bvc2l0aW9uOnJlbGF0aXZlfS5tYXQtcmlwcGxlOm5vdCg6ZW1wdHkpe3RyYW5zZm9ybTp0cmFuc2xhdGVaKDApfS5tYXQtcmlwcGxlLm1hdC1yaXBwbGUtdW5ib3VuZGVke292ZXJmbG93OnZpc2libGV9Lm1hdC1yaXBwbGUtZWxlbWVudHtwb3NpdGlvbjphYnNvbHV0ZTtib3JkZXItcmFkaXVzOjUwJTtwb2ludGVyLWV2ZW50czpub25lO3RyYW5zaXRpb246b3BhY2l0eSx0cmFuc2Zvcm0gMG1zIGN1YmljLWJlemllcigwLCAwLCAwLjIsIDEpO3RyYW5zZm9ybTpzY2FsZSgwKX0uY2RrLWhpZ2gtY29udHJhc3QtYWN0aXZlIC5tYXQtcmlwcGxlLWVsZW1lbnR7ZGlzcGxheTpub25lfS5jZGstdmlzdWFsbHktaGlkZGVue2JvcmRlcjowO2NsaXA6cmVjdCgwIDAgMCAwKTtoZWlnaHQ6MXB4O21hcmdpbjotMXB4O292ZXJmbG93OmhpZGRlbjtwYWRkaW5nOjA7cG9zaXRpb246YWJzb2x1dGU7d2lkdGg6MXB4O291dGxpbmU6MDstd2Via2l0LWFwcGVhcmFuY2U6bm9uZTstbW96LWFwcGVhcmFuY2U6bm9uZX0uY2RrLW92ZXJsYXktY29udGFpbmVyLC5jZGstZ2xvYmFsLW92ZXJsYXktd3JhcHBlcntwb2ludGVyLWV2ZW50czpub25lO3RvcDowO2xlZnQ6MDtoZWlnaHQ6MTAwJTt3aWR0aDoxMDAlfS5jZGstb3ZlcmxheS1jb250YWluZXJ7cG9zaXRpb246Zml4ZWQ7ei1pbmRleDoxMDAwfS5jZGstb3ZlcmxheS1jb250YWluZXI6ZW1wdHl7ZGlzcGxheTpub25lfS5jZGstZ2xvYmFsLW92ZXJsYXktd3JhcHBlcntkaXNwbGF5OmZsZXg7cG9zaXRpb246YWJzb2x1dGU7ei1pbmRleDoxMDAwfS5jZGstb3ZlcmxheS1wYW5le3Bvc2l0aW9uOmFic29sdXRlO3BvaW50ZXItZXZlbnRzOmF1dG87Ym94LXNpemluZzpib3JkZXItYm94O3otaW5kZXg6MTAwMDtkaXNwbGF5OmZsZXg7bWF4LXdpZHRoOjEwMCU7bWF4LWhlaWdodDoxMDAlfS5jZGstb3ZlcmxheS1iYWNrZHJvcHtwb3NpdGlvbjphYnNvbHV0ZTt0b3A6MDtib3R0b206MDtsZWZ0OjA7cmlnaHQ6MDt6LWluZGV4OjEwMDA7cG9pbnRlci1ldmVudHM6YXV0bzstd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3I6dHJhbnNwYXJlbnQ7dHJhbnNpdGlvbjpvcGFjaXR5IDQwMG1zIGN1YmljLWJlemllcigwLjI1LCAwLjgsIDAuMjUsIDEpO29wYWNpdHk6MH0uY2RrLW92ZXJsYXktYmFja2Ryb3AuY2RrLW92ZXJsYXktYmFja2Ryb3Atc2hvd2luZ3tvcGFjaXR5OjF9QG1lZGlhIHNjcmVlbiBhbmQgKC1tcy1oaWdoLWNvbnRyYXN0OiBhY3RpdmUpey5jZGstb3ZlcmxheS1iYWNrZHJvcC5jZGstb3ZlcmxheS1iYWNrZHJvcC1zaG93aW5ne29wYWNpdHk6LjZ9fS5jZGstb3ZlcmxheS1kYXJrLWJhY2tkcm9we2JhY2tncm91bmQ6cmdiYSgwLDAsMCwuMzIpfS5jZGstb3ZlcmxheS10cmFuc3BhcmVudC1iYWNrZHJvcCwuY2RrLW92ZXJsYXktdHJhbnNwYXJlbnQtYmFja2Ryb3AuY2RrLW92ZXJsYXktYmFja2Ryb3Atc2hvd2luZ3tvcGFjaXR5OjB9LmNkay1vdmVybGF5LWNvbm5lY3RlZC1wb3NpdGlvbi1ib3VuZGluZy1ib3h7cG9zaXRpb246YWJzb2x1dGU7ei1pbmRleDoxMDAwO2Rpc3BsYXk6ZmxleDtmbGV4LWRpcmVjdGlvbjpjb2x1bW47bWluLXdpZHRoOjFweDttaW4taGVpZ2h0OjFweH0uY2RrLWdsb2JhbC1zY3JvbGxibG9ja3twb3NpdGlvbjpmaXhlZDt3aWR0aDoxMDAlO292ZXJmbG93LXk6c2Nyb2xsfUBrZXlmcmFtZXMgY2RrLXRleHQtZmllbGQtYXV0b2ZpbGwtc3RhcnR7LyohKi99QGtleWZyYW1lcyBjZGstdGV4dC1maWVsZC1hdXRvZmlsbC1lbmR7LyohKi99LmNkay10ZXh0LWZpZWxkLWF1dG9maWxsLW1vbml0b3JlZDotd2Via2l0LWF1dG9maWxse2FuaW1hdGlvbjpjZGstdGV4dC1maWVsZC1hdXRvZmlsbC1zdGFydCAwcyAxbXN9LmNkay10ZXh0LWZpZWxkLWF1dG9maWxsLW1vbml0b3JlZDpub3QoOi13ZWJraXQtYXV0b2ZpbGwpe2FuaW1hdGlvbjpjZGstdGV4dC1maWVsZC1hdXRvZmlsbC1lbmQgMHMgMW1zfXRleHRhcmVhLmNkay10ZXh0YXJlYS1hdXRvc2l6ZXtyZXNpemU6bm9uZX10ZXh0YXJlYS5jZGstdGV4dGFyZWEtYXV0b3NpemUtbWVhc3VyaW5ne3BhZGRpbmc6MnB4IDAgIWltcG9ydGFudDtib3gtc2l6aW5nOmNvbnRlbnQtYm94ICFpbXBvcnRhbnQ7aGVpZ2h0OmF1dG8gIWltcG9ydGFudDtvdmVyZmxvdzpoaWRkZW4gIWltcG9ydGFudH10ZXh0YXJlYS5jZGstdGV4dGFyZWEtYXV0b3NpemUtbWVhc3VyaW5nLWZpcmVmb3h7cGFkZGluZzoycHggMCAhaW1wb3J0YW50O2JveC1zaXppbmc6Y29udGVudC1ib3ggIWltcG9ydGFudDtoZWlnaHQ6MCAhaW1wb3J0YW50fS5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC4xKX0ubWF0LW9wdGlvbntjb2xvcjojMjEyMTIxfS5tYXQtb3B0aW9uOmhvdmVyOm5vdCgubWF0LW9wdGlvbi1kaXNhYmxlZCksLm1hdC1vcHRpb246Zm9jdXM6bm90KC5tYXQtb3B0aW9uLWRpc2FibGVkKXtiYWNrZ3JvdW5kOnJnYmEoMCwwLDAsLjA0KX0ubWF0LW9wdGlvbi5tYXQtc2VsZWN0ZWQ6bm90KC5tYXQtb3B0aW9uLW11bHRpcGxlKTpub3QoLm1hdC1vcHRpb24tZGlzYWJsZWQpe2JhY2tncm91bmQ6cmdiYSgwLDAsMCwuMDQpfS5tYXQtb3B0aW9uLm1hdC1hY3RpdmV7YmFja2dyb3VuZDpyZ2JhKDAsMCwwLC4wNCk7Y29sb3I6IzIxMjEyMX0ubWF0LW9wdGlvbi5tYXQtb3B0aW9uLWRpc2FibGVke2NvbG9yOnJnYmEoMCwwLDAsLjM4KX0ubWF0LXByaW1hcnkgLm1hdC1vcHRpb24ubWF0LXNlbGVjdGVkOm5vdCgubWF0LW9wdGlvbi1kaXNhYmxlZCl7Y29sb3I6I2Y1N2MwMH0ubWF0LWFjY2VudCAubWF0LW9wdGlvbi5tYXQtc2VsZWN0ZWQ6bm90KC5tYXQtb3B0aW9uLWRpc2FibGVkKXtjb2xvcjojZmY5ODAwfS5tYXQtd2FybiAubWF0LW9wdGlvbi5tYXQtc2VsZWN0ZWQ6bm90KC5tYXQtb3B0aW9uLWRpc2FibGVkKXtjb2xvcjojZjQ0MzM2fS5tYXQtb3B0Z3JvdXAtbGFiZWx7Y29sb3I6IzYxNjE2MX0ubWF0LW9wdGdyb3VwLWRpc2FibGVkIC5tYXQtb3B0Z3JvdXAtbGFiZWx7Y29sb3I6cmdiYSgwLDAsMCwuMzgpfS5tYXQtcHNldWRvLWNoZWNrYm94e2NvbG9yOiM2MTYxNjF9Lm1hdC1wc2V1ZG8tY2hlY2tib3g6OmFmdGVye2NvbG9yOiNmYWZhZmF9Lm1hdC1wc2V1ZG8tY2hlY2tib3gtZGlzYWJsZWR7Y29sb3I6I2IwYjBiMH0ubWF0LXByaW1hcnkgLm1hdC1wc2V1ZG8tY2hlY2tib3gtY2hlY2tlZCwubWF0LXByaW1hcnkgLm1hdC1wc2V1ZG8tY2hlY2tib3gtaW5kZXRlcm1pbmF0ZXtiYWNrZ3JvdW5kOiNmNTdjMDB9Lm1hdC1wc2V1ZG8tY2hlY2tib3gtY2hlY2tlZCwubWF0LXBzZXVkby1jaGVja2JveC1pbmRldGVybWluYXRlLC5tYXQtYWNjZW50IC5tYXQtcHNldWRvLWNoZWNrYm94LWNoZWNrZWQsLm1hdC1hY2NlbnQgLm1hdC1wc2V1ZG8tY2hlY2tib3gtaW5kZXRlcm1pbmF0ZXtiYWNrZ3JvdW5kOiNmZjk4MDB9Lm1hdC13YXJuIC5tYXQtcHNldWRvLWNoZWNrYm94LWNoZWNrZWQsLm1hdC13YXJuIC5tYXQtcHNldWRvLWNoZWNrYm94LWluZGV0ZXJtaW5hdGV7YmFja2dyb3VuZDojZjQ0MzM2fS5tYXQtcHNldWRvLWNoZWNrYm94LWNoZWNrZWQubWF0LXBzZXVkby1jaGVja2JveC1kaXNhYmxlZCwubWF0LXBzZXVkby1jaGVja2JveC1pbmRldGVybWluYXRlLm1hdC1wc2V1ZG8tY2hlY2tib3gtZGlzYWJsZWR7YmFja2dyb3VuZDojYjBiMGIwfS5tYXQtZWxldmF0aW9uLXowe2JveC1zaGFkb3c6MHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16MXtib3gtc2hhZG93OjBweCAycHggMXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAxcHggMXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggM3B4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtZWxldmF0aW9uLXoye2JveC1zaGFkb3c6MHB4IDNweCAxcHggLTJweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDJweCAycHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDFweCA1cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejN7Ym94LXNoYWRvdzowcHggM3B4IDNweCAtMnB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggM3B4IDRweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDhweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16NHtib3gtc2hhZG93OjBweCAycHggNHB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA0cHggNXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16NXtib3gtc2hhZG93OjBweCAzcHggNXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA1cHggOHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggMTRweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16Nntib3gtc2hhZG93OjBweCAzcHggNXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA2cHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDE4cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejd7Ym94LXNoYWRvdzowcHggNHB4IDVweCAtMnB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggN3B4IDEwcHggMXB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDJweCAxNnB4IDFweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtZWxldmF0aW9uLXo4e2JveC1zaGFkb3c6MHB4IDVweCA1cHggLTNweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDhweCAxMHB4IDFweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAzcHggMTRweCAycHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16OXtib3gtc2hhZG93OjBweCA1cHggNnB4IC0zcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA5cHggMTJweCAxcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggM3B4IDE2cHggMnB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejEwe2JveC1zaGFkb3c6MHB4IDZweCA2cHggLTNweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDEwcHggMTRweCAxcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNHB4IDE4cHggM3B4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejExe2JveC1zaGFkb3c6MHB4IDZweCA3cHggLTRweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDExcHggMTVweCAxcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNHB4IDIwcHggM3B4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejEye2JveC1zaGFkb3c6MHB4IDdweCA4cHggLTRweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDEycHggMTdweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNXB4IDIycHggNHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejEze2JveC1zaGFkb3c6MHB4IDdweCA4cHggLTRweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDEzcHggMTlweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNXB4IDI0cHggNHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejE0e2JveC1zaGFkb3c6MHB4IDdweCA5cHggLTRweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDE0cHggMjFweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNXB4IDI2cHggNHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejE1e2JveC1zaGFkb3c6MHB4IDhweCA5cHggLTVweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDE1cHggMjJweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNnB4IDI4cHggNXB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejE2e2JveC1zaGFkb3c6MHB4IDhweCAxMHB4IC01cHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAxNnB4IDI0cHggMnB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDZweCAzMHB4IDVweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtZWxldmF0aW9uLXoxN3tib3gtc2hhZG93OjBweCA4cHggMTFweCAtNXB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMTdweCAyNnB4IDJweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCA2cHggMzJweCA1cHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16MTh7Ym94LXNoYWRvdzowcHggOXB4IDExcHggLTVweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDE4cHggMjhweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggN3B4IDM0cHggNnB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejE5e2JveC1zaGFkb3c6MHB4IDlweCAxMnB4IC02cHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAxOXB4IDI5cHggMnB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDdweCAzNnB4IDZweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtZWxldmF0aW9uLXoyMHtib3gtc2hhZG93OjBweCAxMHB4IDEzcHggLTZweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDIwcHggMzFweCAzcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggOHB4IDM4cHggN3B4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejIxe2JveC1zaGFkb3c6MHB4IDEwcHggMTNweCAtNnB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMjFweCAzM3B4IDNweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCA4cHggNDBweCA3cHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWVsZXZhdGlvbi16MjJ7Ym94LXNoYWRvdzowcHggMTBweCAxNHB4IC02cHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAyMnB4IDM1cHggM3B4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDhweCA0MnB4IDdweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtZWxldmF0aW9uLXoyM3tib3gtc2hhZG93OjBweCAxMXB4IDE0cHggLTdweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDIzcHggMzZweCAzcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggOXB4IDQ0cHggOHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1lbGV2YXRpb24tejI0e2JveC1zaGFkb3c6MHB4IDExcHggMTVweCAtN3B4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMjRweCAzOHB4IDNweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCA5cHggNDZweCA4cHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWFwcC1iYWNrZ3JvdW5ke2JhY2tncm91bmQtY29sb3I6I2ZhZmFmYTtjb2xvcjojMjEyMTIxfS5tYXQtdGhlbWUtbG9hZGVkLW1hcmtlcntkaXNwbGF5Om5vbmV9Lm1hdC1hdXRvY29tcGxldGUtcGFuZWx7YmFja2dyb3VuZDojZmZmO2NvbG9yOiMyMTIxMjF9Lm1hdC1hdXRvY29tcGxldGUtcGFuZWw6bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSl7Ym94LXNoYWRvdzowcHggMnB4IDRweCAtMXB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggNHB4IDVweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDEwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1hdXRvY29tcGxldGUtcGFuZWwgLm1hdC1vcHRpb24ubWF0LXNlbGVjdGVkOm5vdCgubWF0LWFjdGl2ZSk6bm90KDpob3Zlcil7YmFja2dyb3VuZDojZmZmfS5tYXQtYXV0b2NvbXBsZXRlLXBhbmVsIC5tYXQtb3B0aW9uLm1hdC1zZWxlY3RlZDpub3QoLm1hdC1hY3RpdmUpOm5vdCg6aG92ZXIpOm5vdCgubWF0LW9wdGlvbi1kaXNhYmxlZCl7Y29sb3I6IzIxMjEyMX0ubWF0LWJhZGdlLWNvbnRlbnR7Y29sb3I6I2ZmZjtiYWNrZ3JvdW5kOiNmNTdjMDB9LmNkay1oaWdoLWNvbnRyYXN0LWFjdGl2ZSAubWF0LWJhZGdlLWNvbnRlbnR7b3V0bGluZTpzb2xpZCAxcHg7Ym9yZGVyLXJhZGl1czowfS5tYXQtYmFkZ2UtYWNjZW50IC5tYXQtYmFkZ2UtY29udGVudHtiYWNrZ3JvdW5kOiNmZjk4MDA7Y29sb3I6I2ZmZn0ubWF0LWJhZGdlLXdhcm4gLm1hdC1iYWRnZS1jb250ZW50e2NvbG9yOiNmZmY7YmFja2dyb3VuZDojZjQ0MzM2fS5tYXQtYmFkZ2V7cG9zaXRpb246cmVsYXRpdmV9Lm1hdC1iYWRnZS1oaWRkZW4gLm1hdC1iYWRnZS1jb250ZW50e2Rpc3BsYXk6bm9uZX0ubWF0LWJhZGdlLWRpc2FibGVkIC5tYXQtYmFkZ2UtY29udGVudHtiYWNrZ3JvdW5kOiNiOWI5Yjk7Y29sb3I6Izc1NzU3NX0ubWF0LWJhZGdlLWNvbnRlbnR7cG9zaXRpb246YWJzb2x1dGU7dGV4dC1hbGlnbjpjZW50ZXI7ZGlzcGxheTppbmxpbmUtYmxvY2s7Ym9yZGVyLXJhZGl1czo1MCU7dHJhbnNpdGlvbjp0cmFuc2Zvcm0gMjAwbXMgZWFzZS1pbi1vdXQ7dHJhbnNmb3JtOnNjYWxlKDAuNik7b3ZlcmZsb3c6aGlkZGVuO3doaXRlLXNwYWNlOm5vd3JhcDt0ZXh0LW92ZXJmbG93OmVsbGlwc2lzO3BvaW50ZXItZXZlbnRzOm5vbmV9Lm5nLWFuaW1hdGUtZGlzYWJsZWQgLm1hdC1iYWRnZS1jb250ZW50LC5tYXQtYmFkZ2UtY29udGVudC5fbWF0LWFuaW1hdGlvbi1ub29wYWJsZXt0cmFuc2l0aW9uOm5vbmV9Lm1hdC1iYWRnZS1jb250ZW50Lm1hdC1iYWRnZS1hY3RpdmV7dHJhbnNmb3JtOm5vbmV9Lm1hdC1iYWRnZS1zbWFsbCAubWF0LWJhZGdlLWNvbnRlbnR7d2lkdGg6MTZweDtoZWlnaHQ6MTZweDtsaW5lLWhlaWdodDoxNnB4fS5tYXQtYmFkZ2Utc21hbGwubWF0LWJhZGdlLWFib3ZlIC5tYXQtYmFkZ2UtY29udGVudHt0b3A6LThweH0ubWF0LWJhZGdlLXNtYWxsLm1hdC1iYWRnZS1iZWxvdyAubWF0LWJhZGdlLWNvbnRlbnR7Ym90dG9tOi04cHh9Lm1hdC1iYWRnZS1zbWFsbC5tYXQtYmFkZ2UtYmVmb3JlIC5tYXQtYmFkZ2UtY29udGVudHtsZWZ0Oi0xNnB4fVtkaXI9cnRsXSAubWF0LWJhZGdlLXNtYWxsLm1hdC1iYWRnZS1iZWZvcmUgLm1hdC1iYWRnZS1jb250ZW50e2xlZnQ6YXV0bztyaWdodDotMTZweH0ubWF0LWJhZGdlLXNtYWxsLm1hdC1iYWRnZS1hZnRlciAubWF0LWJhZGdlLWNvbnRlbnR7cmlnaHQ6LTE2cHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2Utc21hbGwubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDphdXRvO2xlZnQ6LTE2cHh9Lm1hdC1iYWRnZS1zbWFsbC5tYXQtYmFkZ2Utb3ZlcmxhcC5tYXQtYmFkZ2UtYmVmb3JlIC5tYXQtYmFkZ2UtY29udGVudHtsZWZ0Oi04cHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2Utc21hbGwubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWJlZm9yZSAubWF0LWJhZGdlLWNvbnRlbnR7bGVmdDphdXRvO3JpZ2h0Oi04cHh9Lm1hdC1iYWRnZS1zbWFsbC5tYXQtYmFkZ2Utb3ZlcmxhcC5tYXQtYmFkZ2UtYWZ0ZXIgLm1hdC1iYWRnZS1jb250ZW50e3JpZ2h0Oi04cHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2Utc21hbGwubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDphdXRvO2xlZnQ6LThweH0ubWF0LWJhZGdlLW1lZGl1bSAubWF0LWJhZGdlLWNvbnRlbnR7d2lkdGg6MjJweDtoZWlnaHQ6MjJweDtsaW5lLWhlaWdodDoyMnB4fS5tYXQtYmFkZ2UtbWVkaXVtLm1hdC1iYWRnZS1hYm92ZSAubWF0LWJhZGdlLWNvbnRlbnR7dG9wOi0xMXB4fS5tYXQtYmFkZ2UtbWVkaXVtLm1hdC1iYWRnZS1iZWxvdyAubWF0LWJhZGdlLWNvbnRlbnR7Ym90dG9tOi0xMXB4fS5tYXQtYmFkZ2UtbWVkaXVtLm1hdC1iYWRnZS1iZWZvcmUgLm1hdC1iYWRnZS1jb250ZW50e2xlZnQ6LTIycHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2UtbWVkaXVtLm1hdC1iYWRnZS1iZWZvcmUgLm1hdC1iYWRnZS1jb250ZW50e2xlZnQ6YXV0bztyaWdodDotMjJweH0ubWF0LWJhZGdlLW1lZGl1bS5tYXQtYmFkZ2UtYWZ0ZXIgLm1hdC1iYWRnZS1jb250ZW50e3JpZ2h0Oi0yMnB4fVtkaXI9cnRsXSAubWF0LWJhZGdlLW1lZGl1bS5tYXQtYmFkZ2UtYWZ0ZXIgLm1hdC1iYWRnZS1jb250ZW50e3JpZ2h0OmF1dG87bGVmdDotMjJweH0ubWF0LWJhZGdlLW1lZGl1bS5tYXQtYmFkZ2Utb3ZlcmxhcC5tYXQtYmFkZ2UtYmVmb3JlIC5tYXQtYmFkZ2UtY29udGVudHtsZWZ0Oi0xMXB4fVtkaXI9cnRsXSAubWF0LWJhZGdlLW1lZGl1bS5tYXQtYmFkZ2Utb3ZlcmxhcC5tYXQtYmFkZ2UtYmVmb3JlIC5tYXQtYmFkZ2UtY29udGVudHtsZWZ0OmF1dG87cmlnaHQ6LTExcHh9Lm1hdC1iYWRnZS1tZWRpdW0ubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDotMTFweH1bZGlyPXJ0bF0gLm1hdC1iYWRnZS1tZWRpdW0ubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDphdXRvO2xlZnQ6LTExcHh9Lm1hdC1iYWRnZS1sYXJnZSAubWF0LWJhZGdlLWNvbnRlbnR7d2lkdGg6MjhweDtoZWlnaHQ6MjhweDtsaW5lLWhlaWdodDoyOHB4fS5tYXQtYmFkZ2UtbGFyZ2UubWF0LWJhZGdlLWFib3ZlIC5tYXQtYmFkZ2UtY29udGVudHt0b3A6LTE0cHh9Lm1hdC1iYWRnZS1sYXJnZS5tYXQtYmFkZ2UtYmVsb3cgLm1hdC1iYWRnZS1jb250ZW50e2JvdHRvbTotMTRweH0ubWF0LWJhZGdlLWxhcmdlLm1hdC1iYWRnZS1iZWZvcmUgLm1hdC1iYWRnZS1jb250ZW50e2xlZnQ6LTI4cHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2UtbGFyZ2UubWF0LWJhZGdlLWJlZm9yZSAubWF0LWJhZGdlLWNvbnRlbnR7bGVmdDphdXRvO3JpZ2h0Oi0yOHB4fS5tYXQtYmFkZ2UtbGFyZ2UubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDotMjhweH1bZGlyPXJ0bF0gLm1hdC1iYWRnZS1sYXJnZS5tYXQtYmFkZ2UtYWZ0ZXIgLm1hdC1iYWRnZS1jb250ZW50e3JpZ2h0OmF1dG87bGVmdDotMjhweH0ubWF0LWJhZGdlLWxhcmdlLm1hdC1iYWRnZS1vdmVybGFwLm1hdC1iYWRnZS1iZWZvcmUgLm1hdC1iYWRnZS1jb250ZW50e2xlZnQ6LTE0cHh9W2Rpcj1ydGxdIC5tYXQtYmFkZ2UtbGFyZ2UubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWJlZm9yZSAubWF0LWJhZGdlLWNvbnRlbnR7bGVmdDphdXRvO3JpZ2h0Oi0xNHB4fS5tYXQtYmFkZ2UtbGFyZ2UubWF0LWJhZGdlLW92ZXJsYXAubWF0LWJhZGdlLWFmdGVyIC5tYXQtYmFkZ2UtY29udGVudHtyaWdodDotMTRweH1bZGlyPXJ0bF0gLm1hdC1iYWRnZS1sYXJnZS5tYXQtYmFkZ2Utb3ZlcmxhcC5tYXQtYmFkZ2UtYWZ0ZXIgLm1hdC1iYWRnZS1jb250ZW50e3JpZ2h0OmF1dG87bGVmdDotMTRweH0ubWF0LWJvdHRvbS1zaGVldC1jb250YWluZXJ7Ym94LXNoYWRvdzowcHggOHB4IDEwcHggLTVweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDE2cHggMjRweCAycHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggNnB4IDMwcHggNXB4IHJnYmEoMCwgMCwgMCwgMC4xMik7YmFja2dyb3VuZDojZmZmO2NvbG9yOiMyMTIxMjF9Lm1hdC1idXR0b24sLm1hdC1pY29uLWJ1dHRvbiwubWF0LXN0cm9rZWQtYnV0dG9ue2NvbG9yOmluaGVyaXQ7YmFja2dyb3VuZDp0cmFuc3BhcmVudH0ubWF0LWJ1dHRvbi5tYXQtcHJpbWFyeSwubWF0LWljb24tYnV0dG9uLm1hdC1wcmltYXJ5LC5tYXQtc3Ryb2tlZC1idXR0b24ubWF0LXByaW1hcnl7Y29sb3I6I2Y1N2MwMH0ubWF0LWJ1dHRvbi5tYXQtYWNjZW50LC5tYXQtaWNvbi1idXR0b24ubWF0LWFjY2VudCwubWF0LXN0cm9rZWQtYnV0dG9uLm1hdC1hY2NlbnR7Y29sb3I6I2ZmOTgwMH0ubWF0LWJ1dHRvbi5tYXQtd2FybiwubWF0LWljb24tYnV0dG9uLm1hdC13YXJuLC5tYXQtc3Ryb2tlZC1idXR0b24ubWF0LXdhcm57Y29sb3I6I2Y0NDMzNn0ubWF0LWJ1dHRvbi5tYXQtcHJpbWFyeVtkaXNhYmxlZF0sLm1hdC1idXR0b24ubWF0LWFjY2VudFtkaXNhYmxlZF0sLm1hdC1idXR0b24ubWF0LXdhcm5bZGlzYWJsZWRdLC5tYXQtYnV0dG9uW2Rpc2FibGVkXVtkaXNhYmxlZF0sLm1hdC1pY29uLWJ1dHRvbi5tYXQtcHJpbWFyeVtkaXNhYmxlZF0sLm1hdC1pY29uLWJ1dHRvbi5tYXQtYWNjZW50W2Rpc2FibGVkXSwubWF0LWljb24tYnV0dG9uLm1hdC13YXJuW2Rpc2FibGVkXSwubWF0LWljb24tYnV0dG9uW2Rpc2FibGVkXVtkaXNhYmxlZF0sLm1hdC1zdHJva2VkLWJ1dHRvbi5tYXQtcHJpbWFyeVtkaXNhYmxlZF0sLm1hdC1zdHJva2VkLWJ1dHRvbi5tYXQtYWNjZW50W2Rpc2FibGVkXSwubWF0LXN0cm9rZWQtYnV0dG9uLm1hdC13YXJuW2Rpc2FibGVkXSwubWF0LXN0cm9rZWQtYnV0dG9uW2Rpc2FibGVkXVtkaXNhYmxlZF17Y29sb3I6cmdiYSgwLDAsMCwuMjYpfS5tYXQtYnV0dG9uLm1hdC1wcmltYXJ5IC5tYXQtYnV0dG9uLWZvY3VzLW92ZXJsYXksLm1hdC1pY29uLWJ1dHRvbi5tYXQtcHJpbWFyeSAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5LC5tYXQtc3Ryb2tlZC1idXR0b24ubWF0LXByaW1hcnkgLm1hdC1idXR0b24tZm9jdXMtb3ZlcmxheXtiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDB9Lm1hdC1idXR0b24ubWF0LWFjY2VudCAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5LC5tYXQtaWNvbi1idXR0b24ubWF0LWFjY2VudCAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5LC5tYXQtc3Ryb2tlZC1idXR0b24ubWF0LWFjY2VudCAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5e2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMH0ubWF0LWJ1dHRvbi5tYXQtd2FybiAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5LC5tYXQtaWNvbi1idXR0b24ubWF0LXdhcm4gLm1hdC1idXR0b24tZm9jdXMtb3ZlcmxheSwubWF0LXN0cm9rZWQtYnV0dG9uLm1hdC13YXJuIC5tYXQtYnV0dG9uLWZvY3VzLW92ZXJsYXl7YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtYnV0dG9uW2Rpc2FibGVkXSAubWF0LWJ1dHRvbi1mb2N1cy1vdmVybGF5LC5tYXQtaWNvbi1idXR0b25bZGlzYWJsZWRdIC5tYXQtYnV0dG9uLWZvY3VzLW92ZXJsYXksLm1hdC1zdHJva2VkLWJ1dHRvbltkaXNhYmxlZF0gLm1hdC1idXR0b24tZm9jdXMtb3ZlcmxheXtiYWNrZ3JvdW5kLWNvbG9yOnRyYW5zcGFyZW50fS5tYXQtYnV0dG9uIC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC1pY29uLWJ1dHRvbiAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtc3Ryb2tlZC1idXR0b24gLm1hdC1yaXBwbGUtZWxlbWVudHtvcGFjaXR5Oi4xO2JhY2tncm91bmQtY29sb3I6Y3VycmVudENvbG9yfS5tYXQtYnV0dG9uLWZvY3VzLW92ZXJsYXl7YmFja2dyb3VuZDojMDAwfS5tYXQtc3Ryb2tlZC1idXR0b246bm90KFtkaXNhYmxlZF0pe2JvcmRlci1jb2xvcjpyZ2JhKDAsMCwwLC4xMil9Lm1hdC1mbGF0LWJ1dHRvbiwubWF0LXJhaXNlZC1idXR0b24sLm1hdC1mYWIsLm1hdC1taW5pLWZhYntjb2xvcjojMjEyMTIxO2JhY2tncm91bmQtY29sb3I6I2ZmZn0ubWF0LWZsYXQtYnV0dG9uLm1hdC1wcmltYXJ5LC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtcHJpbWFyeSwubWF0LWZhYi5tYXQtcHJpbWFyeSwubWF0LW1pbmktZmFiLm1hdC1wcmltYXJ5e2NvbG9yOiNmZmZ9Lm1hdC1mbGF0LWJ1dHRvbi5tYXQtYWNjZW50LC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtYWNjZW50LC5tYXQtZmFiLm1hdC1hY2NlbnQsLm1hdC1taW5pLWZhYi5tYXQtYWNjZW50e2NvbG9yOiNmZmZ9Lm1hdC1mbGF0LWJ1dHRvbi5tYXQtd2FybiwubWF0LXJhaXNlZC1idXR0b24ubWF0LXdhcm4sLm1hdC1mYWIubWF0LXdhcm4sLm1hdC1taW5pLWZhYi5tYXQtd2Fybntjb2xvcjojZmZmfS5tYXQtZmxhdC1idXR0b24ubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtZmxhdC1idXR0b24ubWF0LWFjY2VudFtkaXNhYmxlZF0sLm1hdC1mbGF0LWJ1dHRvbi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1mbGF0LWJ1dHRvbltkaXNhYmxlZF1bZGlzYWJsZWRdLC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtcHJpbWFyeVtkaXNhYmxlZF0sLm1hdC1yYWlzZWQtYnV0dG9uLm1hdC1hY2NlbnRbZGlzYWJsZWRdLC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1yYWlzZWQtYnV0dG9uW2Rpc2FibGVkXVtkaXNhYmxlZF0sLm1hdC1mYWIubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtZmFiLm1hdC1hY2NlbnRbZGlzYWJsZWRdLC5tYXQtZmFiLm1hdC13YXJuW2Rpc2FibGVkXSwubWF0LWZhYltkaXNhYmxlZF1bZGlzYWJsZWRdLC5tYXQtbWluaS1mYWIubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtbWluaS1mYWIubWF0LWFjY2VudFtkaXNhYmxlZF0sLm1hdC1taW5pLWZhYi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1taW5pLWZhYltkaXNhYmxlZF1bZGlzYWJsZWRde2NvbG9yOnJnYmEoMCwwLDAsLjI2KX0ubWF0LWZsYXQtYnV0dG9uLm1hdC1wcmltYXJ5LC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtcHJpbWFyeSwubWF0LWZhYi5tYXQtcHJpbWFyeSwubWF0LW1pbmktZmFiLm1hdC1wcmltYXJ5e2JhY2tncm91bmQtY29sb3I6I2Y1N2MwMH0ubWF0LWZsYXQtYnV0dG9uLm1hdC1hY2NlbnQsLm1hdC1yYWlzZWQtYnV0dG9uLm1hdC1hY2NlbnQsLm1hdC1mYWIubWF0LWFjY2VudCwubWF0LW1pbmktZmFiLm1hdC1hY2NlbnR7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwfS5tYXQtZmxhdC1idXR0b24ubWF0LXdhcm4sLm1hdC1yYWlzZWQtYnV0dG9uLm1hdC13YXJuLC5tYXQtZmFiLm1hdC13YXJuLC5tYXQtbWluaS1mYWIubWF0LXdhcm57YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtZmxhdC1idXR0b24ubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtZmxhdC1idXR0b24ubWF0LWFjY2VudFtkaXNhYmxlZF0sLm1hdC1mbGF0LWJ1dHRvbi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1mbGF0LWJ1dHRvbltkaXNhYmxlZF1bZGlzYWJsZWRdLC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtcHJpbWFyeVtkaXNhYmxlZF0sLm1hdC1yYWlzZWQtYnV0dG9uLm1hdC1hY2NlbnRbZGlzYWJsZWRdLC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1yYWlzZWQtYnV0dG9uW2Rpc2FibGVkXVtkaXNhYmxlZF0sLm1hdC1mYWIubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtZmFiLm1hdC1hY2NlbnRbZGlzYWJsZWRdLC5tYXQtZmFiLm1hdC13YXJuW2Rpc2FibGVkXSwubWF0LWZhYltkaXNhYmxlZF1bZGlzYWJsZWRdLC5tYXQtbWluaS1mYWIubWF0LXByaW1hcnlbZGlzYWJsZWRdLC5tYXQtbWluaS1mYWIubWF0LWFjY2VudFtkaXNhYmxlZF0sLm1hdC1taW5pLWZhYi5tYXQtd2FybltkaXNhYmxlZF0sLm1hdC1taW5pLWZhYltkaXNhYmxlZF1bZGlzYWJsZWRde2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtZmxhdC1idXR0b24ubWF0LXByaW1hcnkgLm1hdC1yaXBwbGUtZWxlbWVudCwubWF0LXJhaXNlZC1idXR0b24ubWF0LXByaW1hcnkgLm1hdC1yaXBwbGUtZWxlbWVudCwubWF0LWZhYi5tYXQtcHJpbWFyeSAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtbWluaS1mYWIubWF0LXByaW1hcnkgLm1hdC1yaXBwbGUtZWxlbWVudHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDI1NSwyNTUsLjEpfS5tYXQtZmxhdC1idXR0b24ubWF0LWFjY2VudCAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtYWNjZW50IC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC1mYWIubWF0LWFjY2VudCAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtbWluaS1mYWIubWF0LWFjY2VudCAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuMSl9Lm1hdC1mbGF0LWJ1dHRvbi5tYXQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtcmFpc2VkLWJ1dHRvbi5tYXQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtZmFiLm1hdC13YXJuIC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC1taW5pLWZhYi5tYXQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuMSl9Lm1hdC1zdHJva2VkLWJ1dHRvbjpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKSwubWF0LWZsYXQtYnV0dG9uOm5vdChbY2xhc3MqPW1hdC1lbGV2YXRpb24tel0pe2JveC1zaGFkb3c6MHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LXJhaXNlZC1idXR0b246bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSl7Ym94LXNoYWRvdzowcHggM3B4IDFweCAtMnB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMnB4IDJweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDVweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LXJhaXNlZC1idXR0b246bm90KFtkaXNhYmxlZF0pOmFjdGl2ZTpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCA1cHggNXB4IC0zcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA4cHggMTBweCAxcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggM3B4IDE0cHggMnB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1yYWlzZWQtYnV0dG9uW2Rpc2FibGVkXTpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCAwcHggMHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1mYWI6bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSksLm1hdC1taW5pLWZhYjpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCAzcHggNXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA2cHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDE4cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1mYWI6bm90KFtkaXNhYmxlZF0pOmFjdGl2ZTpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKSwubWF0LW1pbmktZmFiOm5vdChbZGlzYWJsZWRdKTphY3RpdmU6bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSl7Ym94LXNoYWRvdzowcHggN3B4IDhweCAtNHB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMTJweCAxN3B4IDJweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCA1cHggMjJweCA0cHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWZhYltkaXNhYmxlZF06bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSksLm1hdC1taW5pLWZhYltkaXNhYmxlZF06bm90KFtjbGFzcyo9bWF0LWVsZXZhdGlvbi16XSl7Ym94LXNoYWRvdzowcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAwcHggMHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAwcHggMHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtYnV0dG9uLXRvZ2dsZS1zdGFuZGFsb25lLC5tYXQtYnV0dG9uLXRvZ2dsZS1ncm91cHtib3gtc2hhZG93OjBweCAzcHggMXB4IC0ycHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAycHggMnB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggNXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtYnV0dG9uLXRvZ2dsZS1zdGFuZGFsb25lLm1hdC1idXR0b24tdG9nZ2xlLWFwcGVhcmFuY2Utc3RhbmRhcmQsLm1hdC1idXR0b24tdG9nZ2xlLWdyb3VwLWFwcGVhcmFuY2Utc3RhbmRhcmR7Ym94LXNoYWRvdzpub25lfS5tYXQtYnV0dG9uLXRvZ2dsZXtjb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1idXR0b24tdG9nZ2xlIC5tYXQtYnV0dG9uLXRvZ2dsZS1mb2N1cy1vdmVybGF5e2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtYnV0dG9uLXRvZ2dsZS1hcHBlYXJhbmNlLXN0YW5kYXJke2NvbG9yOiMyMTIxMjE7YmFja2dyb3VuZDojZmZmfS5tYXQtYnV0dG9uLXRvZ2dsZS1hcHBlYXJhbmNlLXN0YW5kYXJkIC5tYXQtYnV0dG9uLXRvZ2dsZS1mb2N1cy1vdmVybGF5e2JhY2tncm91bmQtY29sb3I6IzAwMH0ubWF0LWJ1dHRvbi10b2dnbGUtZ3JvdXAtYXBwZWFyYW5jZS1zdGFuZGFyZCAubWF0LWJ1dHRvbi10b2dnbGUrLm1hdC1idXR0b24tdG9nZ2xle2JvcmRlci1sZWZ0OnNvbGlkIDFweCByZ2JhKDAsMCwwLC4xMil9W2Rpcj1ydGxdIC5tYXQtYnV0dG9uLXRvZ2dsZS1ncm91cC1hcHBlYXJhbmNlLXN0YW5kYXJkIC5tYXQtYnV0dG9uLXRvZ2dsZSsubWF0LWJ1dHRvbi10b2dnbGV7Ym9yZGVyLWxlZnQ6bm9uZTtib3JkZXItcmlnaHQ6c29saWQgMXB4IHJnYmEoMCwwLDAsLjEyKX0ubWF0LWJ1dHRvbi10b2dnbGUtZ3JvdXAtYXBwZWFyYW5jZS1zdGFuZGFyZC5tYXQtYnV0dG9uLXRvZ2dsZS12ZXJ0aWNhbCAubWF0LWJ1dHRvbi10b2dnbGUrLm1hdC1idXR0b24tdG9nZ2xle2JvcmRlci1sZWZ0Om5vbmU7Ym9yZGVyLXJpZ2h0Om5vbmU7Ym9yZGVyLXRvcDpzb2xpZCAxcHggcmdiYSgwLDAsMCwuMTIpfS5tYXQtYnV0dG9uLXRvZ2dsZS1jaGVja2Vke2JhY2tncm91bmQtY29sb3I6I2UwZTBlMDtjb2xvcjojNjE2MTYxfS5tYXQtYnV0dG9uLXRvZ2dsZS1jaGVja2VkLm1hdC1idXR0b24tdG9nZ2xlLWFwcGVhcmFuY2Utc3RhbmRhcmR7Y29sb3I6IzIxMjEyMX0ubWF0LWJ1dHRvbi10b2dnbGUtZGlzYWJsZWR7Y29sb3I6cmdiYSgwLDAsMCwuMjYpO2JhY2tncm91bmQtY29sb3I6I2VlZX0ubWF0LWJ1dHRvbi10b2dnbGUtZGlzYWJsZWQubWF0LWJ1dHRvbi10b2dnbGUtYXBwZWFyYW5jZS1zdGFuZGFyZHtiYWNrZ3JvdW5kOiNmZmZ9Lm1hdC1idXR0b24tdG9nZ2xlLWRpc2FibGVkLm1hdC1idXR0b24tdG9nZ2xlLWNoZWNrZWR7YmFja2dyb3VuZC1jb2xvcjojYmRiZGJkfS5tYXQtYnV0dG9uLXRvZ2dsZS1zdGFuZGFsb25lLm1hdC1idXR0b24tdG9nZ2xlLWFwcGVhcmFuY2Utc3RhbmRhcmQsLm1hdC1idXR0b24tdG9nZ2xlLWdyb3VwLWFwcGVhcmFuY2Utc3RhbmRhcmR7Ym9yZGVyOnNvbGlkIDFweCByZ2JhKDAsMCwwLC4xMil9Lm1hdC1jYXJke2JhY2tncm91bmQ6I2ZmZjtjb2xvcjojMjEyMTIxfS5tYXQtY2FyZDpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCAycHggMXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAxcHggMXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggM3B4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtY2FyZC5tYXQtY2FyZC1mbGF0Om5vdChbY2xhc3MqPW1hdC1lbGV2YXRpb24tel0pe2JveC1zaGFkb3c6MHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWNhcmQtc3VidGl0bGV7Y29sb3I6IzYxNjE2MX0ubWF0LWNoZWNrYm94LWZyYW1le2JvcmRlci1jb2xvcjojNjE2MTYxfS5tYXQtY2hlY2tib3gtY2hlY2ttYXJre2ZpbGw6I2ZhZmFmYX0ubWF0LWNoZWNrYm94LWNoZWNrbWFyay1wYXRoe3N0cm9rZTojZmFmYWZhICFpbXBvcnRhbnR9Lm1hdC1jaGVja2JveC1taXhlZG1hcmt7YmFja2dyb3VuZC1jb2xvcjojZmFmYWZhfS5tYXQtY2hlY2tib3gtaW5kZXRlcm1pbmF0ZS5tYXQtcHJpbWFyeSAubWF0LWNoZWNrYm94LWJhY2tncm91bmQsLm1hdC1jaGVja2JveC1jaGVja2VkLm1hdC1wcmltYXJ5IC5tYXQtY2hlY2tib3gtYmFja2dyb3VuZHtiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDB9Lm1hdC1jaGVja2JveC1pbmRldGVybWluYXRlLm1hdC1hY2NlbnQgLm1hdC1jaGVja2JveC1iYWNrZ3JvdW5kLC5tYXQtY2hlY2tib3gtY2hlY2tlZC5tYXQtYWNjZW50IC5tYXQtY2hlY2tib3gtYmFja2dyb3VuZHtiYWNrZ3JvdW5kLWNvbG9yOiNmZjk4MDB9Lm1hdC1jaGVja2JveC1pbmRldGVybWluYXRlLm1hdC13YXJuIC5tYXQtY2hlY2tib3gtYmFja2dyb3VuZCwubWF0LWNoZWNrYm94LWNoZWNrZWQubWF0LXdhcm4gLm1hdC1jaGVja2JveC1iYWNrZ3JvdW5ke2JhY2tncm91bmQtY29sb3I6I2Y0NDMzNn0ubWF0LWNoZWNrYm94LWRpc2FibGVkLm1hdC1jaGVja2JveC1jaGVja2VkIC5tYXQtY2hlY2tib3gtYmFja2dyb3VuZCwubWF0LWNoZWNrYm94LWRpc2FibGVkLm1hdC1jaGVja2JveC1pbmRldGVybWluYXRlIC5tYXQtY2hlY2tib3gtYmFja2dyb3VuZHtiYWNrZ3JvdW5kLWNvbG9yOiNiMGIwYjB9Lm1hdC1jaGVja2JveC1kaXNhYmxlZDpub3QoLm1hdC1jaGVja2JveC1jaGVja2VkKSAubWF0LWNoZWNrYm94LWZyYW1le2JvcmRlci1jb2xvcjojYjBiMGIwfS5tYXQtY2hlY2tib3gtZGlzYWJsZWQgLm1hdC1jaGVja2JveC1sYWJlbHtjb2xvcjojNjE2MTYxfS5tYXQtY2hlY2tib3ggLm1hdC1yaXBwbGUtZWxlbWVudHtiYWNrZ3JvdW5kLWNvbG9yOiMwMDB9Lm1hdC1jaGVja2JveC1jaGVja2VkOm5vdCgubWF0LWNoZWNrYm94LWRpc2FibGVkKS5tYXQtcHJpbWFyeSAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtY2hlY2tib3g6YWN0aXZlOm5vdCgubWF0LWNoZWNrYm94LWRpc2FibGVkKS5tYXQtcHJpbWFyeSAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQ6I2Y1N2MwMH0ubWF0LWNoZWNrYm94LWNoZWNrZWQ6bm90KC5tYXQtY2hlY2tib3gtZGlzYWJsZWQpLm1hdC1hY2NlbnQgLm1hdC1yaXBwbGUtZWxlbWVudCwubWF0LWNoZWNrYm94OmFjdGl2ZTpub3QoLm1hdC1jaGVja2JveC1kaXNhYmxlZCkubWF0LWFjY2VudCAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQ6I2ZmOTgwMH0ubWF0LWNoZWNrYm94LWNoZWNrZWQ6bm90KC5tYXQtY2hlY2tib3gtZGlzYWJsZWQpLm1hdC13YXJuIC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC1jaGVja2JveDphY3RpdmU6bm90KC5tYXQtY2hlY2tib3gtZGlzYWJsZWQpLm1hdC13YXJuIC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZDojZjQ0MzM2fS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcHtiYWNrZ3JvdW5kLWNvbG9yOiNlMGUwZTA7Y29sb3I6IzIxMjEyMX0ubWF0LWNoaXAubWF0LXN0YW5kYXJkLWNoaXAgLm1hdC1jaGlwLXJlbW92ZXtjb2xvcjojMjEyMTIxO29wYWNpdHk6LjR9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwOm5vdCgubWF0LWNoaXAtZGlzYWJsZWQpOmFjdGl2ZXtib3gtc2hhZG93OjBweCAzcHggM3B4IC0ycHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCAzcHggNHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggOHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpfS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcDpub3QoLm1hdC1jaGlwLWRpc2FibGVkKSAubWF0LWNoaXAtcmVtb3ZlOmhvdmVye29wYWNpdHk6LjU0fS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcC5tYXQtY2hpcC1kaXNhYmxlZHtvcGFjaXR5Oi40fS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcDo6YWZ0ZXJ7YmFja2dyb3VuZDojMDAwfS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcC5tYXQtY2hpcC1zZWxlY3RlZC5tYXQtcHJpbWFyeXtiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDA7Y29sb3I6I2ZmZn0ubWF0LWNoaXAubWF0LXN0YW5kYXJkLWNoaXAubWF0LWNoaXAtc2VsZWN0ZWQubWF0LXByaW1hcnkgLm1hdC1jaGlwLXJlbW92ZXtjb2xvcjojZmZmO29wYWNpdHk6LjR9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwLm1hdC1jaGlwLXNlbGVjdGVkLm1hdC1wcmltYXJ5IC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI1NSwyNTUsMjU1LC4xKX0ubWF0LWNoaXAubWF0LXN0YW5kYXJkLWNoaXAubWF0LWNoaXAtc2VsZWN0ZWQubWF0LXdhcm57YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2O2NvbG9yOiNmZmZ9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwLm1hdC1jaGlwLXNlbGVjdGVkLm1hdC13YXJuIC5tYXQtY2hpcC1yZW1vdmV7Y29sb3I6I2ZmZjtvcGFjaXR5Oi40fS5tYXQtY2hpcC5tYXQtc3RhbmRhcmQtY2hpcC5tYXQtY2hpcC1zZWxlY3RlZC5tYXQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuMSl9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwLm1hdC1jaGlwLXNlbGVjdGVkLm1hdC1hY2NlbnR7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwO2NvbG9yOiNmZmZ9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwLm1hdC1jaGlwLXNlbGVjdGVkLm1hdC1hY2NlbnQgLm1hdC1jaGlwLXJlbW92ZXtjb2xvcjojZmZmO29wYWNpdHk6LjR9Lm1hdC1jaGlwLm1hdC1zdGFuZGFyZC1jaGlwLm1hdC1jaGlwLXNlbGVjdGVkLm1hdC1hY2NlbnQgLm1hdC1yaXBwbGUtZWxlbWVudHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDI1NSwyNTUsLjEpfS5tYXQtdGFibGV7YmFja2dyb3VuZDojZmZmfS5tYXQtdGFibGUgdGhlYWQsLm1hdC10YWJsZSB0Ym9keSwubWF0LXRhYmxlIHRmb290LG1hdC1oZWFkZXItcm93LG1hdC1yb3csbWF0LWZvb3Rlci1yb3csW21hdC1oZWFkZXItcm93XSxbbWF0LXJvd10sW21hdC1mb290ZXItcm93XSwubWF0LXRhYmxlLXN0aWNreXtiYWNrZ3JvdW5kOmluaGVyaXR9bWF0LXJvdyxtYXQtaGVhZGVyLXJvdyxtYXQtZm9vdGVyLXJvdyx0aC5tYXQtaGVhZGVyLWNlbGwsdGQubWF0LWNlbGwsdGQubWF0LWZvb3Rlci1jZWxse2JvcmRlci1ib3R0b20tY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtaGVhZGVyLWNlbGx7Y29sb3I6IzYxNjE2MX0ubWF0LWNlbGwsLm1hdC1mb290ZXItY2VsbHtjb2xvcjojMjEyMTIxfS5tYXQtY2FsZW5kYXItYXJyb3d7Ym9yZGVyLXRvcC1jb2xvcjpyZ2JhKDAsMCwwLC41NCl9Lm1hdC1kYXRlcGlja2VyLXRvZ2dsZSwubWF0LWRhdGVwaWNrZXItY29udGVudCAubWF0LWNhbGVuZGFyLW5leHQtYnV0dG9uLC5tYXQtZGF0ZXBpY2tlci1jb250ZW50IC5tYXQtY2FsZW5kYXItcHJldmlvdXMtYnV0dG9ue2NvbG9yOnJnYmEoMCwwLDAsLjU0KX0ubWF0LWNhbGVuZGFyLXRhYmxlLWhlYWRlcntjb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1jYWxlbmRhci10YWJsZS1oZWFkZXItZGl2aWRlcjo6YWZ0ZXJ7YmFja2dyb3VuZDpyZ2JhKDAsMCwwLC4xMil9Lm1hdC1jYWxlbmRhci1ib2R5LWxhYmVse2NvbG9yOiM2MTYxNjF9Lm1hdC1jYWxlbmRhci1ib2R5LWNlbGwtY29udGVudHtjb2xvcjojMjEyMTIxO2JvcmRlci1jb2xvcjp0cmFuc3BhcmVudH0ubWF0LWNhbGVuZGFyLWJvZHktZGlzYWJsZWQ+Lm1hdC1jYWxlbmRhci1ib2R5LWNlbGwtY29udGVudDpub3QoLm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVkKXtjb2xvcjojNzU3NTc1fS5tYXQtY2FsZW5kYXItYm9keS1jZWxsOm5vdCgubWF0LWNhbGVuZGFyLWJvZHktZGlzYWJsZWQpOmhvdmVyPi5tYXQtY2FsZW5kYXItYm9keS1jZWxsLWNvbnRlbnQ6bm90KC5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZCksLmNkay1rZXlib2FyZC1mb2N1c2VkIC5tYXQtY2FsZW5kYXItYm9keS1hY3RpdmU+Lm1hdC1jYWxlbmRhci1ib2R5LWNlbGwtY29udGVudDpub3QoLm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVkKSwuY2RrLXByb2dyYW0tZm9jdXNlZCAubWF0LWNhbGVuZGFyLWJvZHktYWN0aXZlPi5tYXQtY2FsZW5kYXItYm9keS1jZWxsLWNvbnRlbnQ6bm90KC5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZCl7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC4wNCl9Lm1hdC1jYWxlbmRhci1ib2R5LXRvZGF5Om5vdCgubWF0LWNhbGVuZGFyLWJvZHktc2VsZWN0ZWQpe2JvcmRlci1jb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1jYWxlbmRhci1ib2R5LWRpc2FibGVkPi5tYXQtY2FsZW5kYXItYm9keS10b2RheTpub3QoLm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVkKXtib3JkZXItY29sb3I6cmdiYSgwLDAsMCwuMTgpfS5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDA7Y29sb3I6I2ZmZn0ubWF0LWNhbGVuZGFyLWJvZHktZGlzYWJsZWQ+Lm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVke2JhY2tncm91bmQtY29sb3I6cmdiYSgyNDUsMTI0LDAsLjQpfS5tYXQtY2FsZW5kYXItYm9keS10b2RheS5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtib3gtc2hhZG93Omluc2V0IDAgMCAwIDFweCAjZmZmfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50e2JveC1zaGFkb3c6MHB4IDJweCA0cHggLTFweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDRweCA1cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDFweCAxMHB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTIpO2JhY2tncm91bmQtY29sb3I6I2ZmZjtjb2xvcjojMjEyMTIxfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50Lm1hdC1hY2NlbnQgLm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVke2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMDtjb2xvcjojZmZmfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50Lm1hdC1hY2NlbnQgLm1hdC1jYWxlbmRhci1ib2R5LWRpc2FibGVkPi5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDE1MiwwLC40KX0ubWF0LWRhdGVwaWNrZXItY29udGVudC5tYXQtYWNjZW50IC5tYXQtY2FsZW5kYXItYm9keS10b2RheS5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtib3gtc2hhZG93Omluc2V0IDAgMCAwIDFweCAjZmZmfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50Lm1hdC13YXJuIC5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtiYWNrZ3JvdW5kLWNvbG9yOiNmNDQzMzY7Y29sb3I6I2ZmZn0ubWF0LWRhdGVwaWNrZXItY29udGVudC5tYXQtd2FybiAubWF0LWNhbGVuZGFyLWJvZHktZGlzYWJsZWQ+Lm1hdC1jYWxlbmRhci1ib2R5LXNlbGVjdGVke2JhY2tncm91bmQtY29sb3I6cmdiYSgyNDQsNjcsNTQsLjQpfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50Lm1hdC13YXJuIC5tYXQtY2FsZW5kYXItYm9keS10b2RheS5tYXQtY2FsZW5kYXItYm9keS1zZWxlY3RlZHtib3gtc2hhZG93Omluc2V0IDAgMCAwIDFweCAjZmZmfS5tYXQtZGF0ZXBpY2tlci1jb250ZW50LXRvdWNoe2JveC1zaGFkb3c6MHB4IDBweCAwcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMHB4IDBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWRhdGVwaWNrZXItdG9nZ2xlLWFjdGl2ZXtjb2xvcjojZjU3YzAwfS5tYXQtZGF0ZXBpY2tlci10b2dnbGUtYWN0aXZlLm1hdC1hY2NlbnR7Y29sb3I6I2ZmOTgwMH0ubWF0LWRhdGVwaWNrZXItdG9nZ2xlLWFjdGl2ZS5tYXQtd2Fybntjb2xvcjojZjQ0MzM2fS5tYXQtZGlhbG9nLWNvbnRhaW5lcntib3gtc2hhZG93OjBweCAxMXB4IDE1cHggLTdweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDI0cHggMzhweCAzcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggOXB4IDQ2cHggOHB4IHJnYmEoMCwgMCwgMCwgMC4xMik7YmFja2dyb3VuZDojZmZmO2NvbG9yOiMyMTIxMjF9Lm1hdC1kaXZpZGVye2JvcmRlci10b3AtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtZGl2aWRlci12ZXJ0aWNhbHtib3JkZXItcmlnaHQtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtZXhwYW5zaW9uLXBhbmVse2JhY2tncm91bmQ6I2ZmZjtjb2xvcjojMjEyMTIxfS5tYXQtZXhwYW5zaW9uLXBhbmVsOm5vdChbY2xhc3MqPW1hdC1lbGV2YXRpb24tel0pe2JveC1zaGFkb3c6MHB4IDNweCAxcHggLTJweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDJweCAycHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDFweCA1cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1hY3Rpb24tcm93e2JvcmRlci10b3AtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtZXhwYW5zaW9uLXBhbmVsIC5tYXQtZXhwYW5zaW9uLXBhbmVsLWhlYWRlci5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoW2FyaWEtZGlzYWJsZWQ9dHJ1ZV0pLC5tYXQtZXhwYW5zaW9uLXBhbmVsIC5tYXQtZXhwYW5zaW9uLXBhbmVsLWhlYWRlci5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdChbYXJpYS1kaXNhYmxlZD10cnVlXSksLm1hdC1leHBhbnNpb24tcGFuZWw6bm90KC5tYXQtZXhwYW5kZWQpIC5tYXQtZXhwYW5zaW9uLXBhbmVsLWhlYWRlcjpob3Zlcjpub3QoW2FyaWEtZGlzYWJsZWQ9dHJ1ZV0pe2JhY2tncm91bmQ6cmdiYSgwLDAsMCwuMDQpfUBtZWRpYShob3Zlcjogbm9uZSl7Lm1hdC1leHBhbnNpb24tcGFuZWw6bm90KC5tYXQtZXhwYW5kZWQpOm5vdChbYXJpYS1kaXNhYmxlZD10cnVlXSkgLm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVyOmhvdmVye2JhY2tncm91bmQ6I2ZmZn19Lm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVyLXRpdGxle2NvbG9yOiMyMTIxMjF9Lm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVyLWRlc2NyaXB0aW9uLC5tYXQtZXhwYW5zaW9uLWluZGljYXRvcjo6YWZ0ZXJ7Y29sb3I6IzYxNjE2MX0ubWF0LWV4cGFuc2lvbi1wYW5lbC1oZWFkZXJbYXJpYS1kaXNhYmxlZD10cnVlXXtjb2xvcjpyZ2JhKDAsMCwwLC4yNil9Lm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVyW2FyaWEtZGlzYWJsZWQ9dHJ1ZV0gLm1hdC1leHBhbnNpb24tcGFuZWwtaGVhZGVyLXRpdGxlLC5tYXQtZXhwYW5zaW9uLXBhbmVsLWhlYWRlclthcmlhLWRpc2FibGVkPXRydWVdIC5tYXQtZXhwYW5zaW9uLXBhbmVsLWhlYWRlci1kZXNjcmlwdGlvbntjb2xvcjppbmhlcml0fS5tYXQtZm9ybS1maWVsZC1sYWJlbHtjb2xvcjpyZ2JhKDk3LDk3LDk3LC42KX0ubWF0LWhpbnR7Y29sb3I6cmdiYSg5Nyw5Nyw5NywuNil9Lm1hdC1mb3JtLWZpZWxkLm1hdC1mb2N1c2VkIC5tYXQtZm9ybS1maWVsZC1sYWJlbHtjb2xvcjojZjU3YzAwfS5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZCAubWF0LWZvcm0tZmllbGQtbGFiZWwubWF0LWFjY2VudHtjb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZCAubWF0LWZvcm0tZmllbGQtbGFiZWwubWF0LXdhcm57Y29sb3I6I2Y0NDMzNn0ubWF0LWZvY3VzZWQgLm1hdC1mb3JtLWZpZWxkLXJlcXVpcmVkLW1hcmtlcntjb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC1yaXBwbGV7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC44Nyl9Lm1hdC1mb3JtLWZpZWxkLm1hdC1mb2N1c2VkIC5tYXQtZm9ybS1maWVsZC1yaXBwbGV7YmFja2dyb3VuZC1jb2xvcjojZjU3YzAwfS5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZCAubWF0LWZvcm0tZmllbGQtcmlwcGxlLm1hdC1hY2NlbnR7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZCAubWF0LWZvcm0tZmllbGQtcmlwcGxlLm1hdC13YXJue2JhY2tncm91bmQtY29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQtdHlwZS1tYXQtbmF0aXZlLXNlbGVjdC5tYXQtZm9jdXNlZDpub3QoLm1hdC1mb3JtLWZpZWxkLWludmFsaWQpIC5tYXQtZm9ybS1maWVsZC1pbmZpeDo6YWZ0ZXJ7Y29sb3I6I2Y1N2MwMH0ubWF0LWZvcm0tZmllbGQtdHlwZS1tYXQtbmF0aXZlLXNlbGVjdC5tYXQtZm9jdXNlZDpub3QoLm1hdC1mb3JtLWZpZWxkLWludmFsaWQpLm1hdC1hY2NlbnQgLm1hdC1mb3JtLWZpZWxkLWluZml4OjphZnRlcntjb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC10eXBlLW1hdC1uYXRpdmUtc2VsZWN0Lm1hdC1mb2N1c2VkOm5vdCgubWF0LWZvcm0tZmllbGQtaW52YWxpZCkubWF0LXdhcm4gLm1hdC1mb3JtLWZpZWxkLWluZml4OjphZnRlcntjb2xvcjojZjQ0MzM2fS5tYXQtZm9ybS1maWVsZC5tYXQtZm9ybS1maWVsZC1pbnZhbGlkIC5tYXQtZm9ybS1maWVsZC1sYWJlbHtjb2xvcjojZjQ0MzM2fS5tYXQtZm9ybS1maWVsZC5tYXQtZm9ybS1maWVsZC1pbnZhbGlkIC5tYXQtZm9ybS1maWVsZC1sYWJlbC5tYXQtYWNjZW50LC5tYXQtZm9ybS1maWVsZC5tYXQtZm9ybS1maWVsZC1pbnZhbGlkIC5tYXQtZm9ybS1maWVsZC1sYWJlbCAubWF0LWZvcm0tZmllbGQtcmVxdWlyZWQtbWFya2Vye2NvbG9yOiNmNDQzMzZ9Lm1hdC1mb3JtLWZpZWxkLm1hdC1mb3JtLWZpZWxkLWludmFsaWQgLm1hdC1mb3JtLWZpZWxkLXJpcHBsZSwubWF0LWZvcm0tZmllbGQubWF0LWZvcm0tZmllbGQtaW52YWxpZCAubWF0LWZvcm0tZmllbGQtcmlwcGxlLm1hdC1hY2NlbnR7YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtZXJyb3J7Y29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1sZWdhY3kgLm1hdC1mb3JtLWZpZWxkLWxhYmVse2NvbG9yOiM2MTYxNjF9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2UtbGVnYWN5IC5tYXQtaGludHtjb2xvcjojNjE2MTYxfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeSAubWF0LWZvcm0tZmllbGQtdW5kZXJsaW5le2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuNDIpfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWxlZ2FjeS5tYXQtZm9ybS1maWVsZC1kaXNhYmxlZCAubWF0LWZvcm0tZmllbGQtdW5kZXJsaW5le2JhY2tncm91bmQtaW1hZ2U6bGluZWFyLWdyYWRpZW50KHRvIHJpZ2h0LCByZ2JhKDAsIDAsIDAsIDAuNDIpIDAlLCByZ2JhKDAsIDAsIDAsIDAuNDIpIDMzJSwgdHJhbnNwYXJlbnQgMCUpO2JhY2tncm91bmQtc2l6ZTo0cHggMTAwJTtiYWNrZ3JvdW5kLXJlcGVhdDpyZXBlYXQteH0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1zdGFuZGFyZCAubWF0LWZvcm0tZmllbGQtdW5kZXJsaW5le2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuNDIpfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLXN0YW5kYXJkLm1hdC1mb3JtLWZpZWxkLWRpc2FibGVkIC5tYXQtZm9ybS1maWVsZC11bmRlcmxpbmV7YmFja2dyb3VuZC1pbWFnZTpsaW5lYXItZ3JhZGllbnQodG8gcmlnaHQsIHJnYmEoMCwgMCwgMCwgMC40MikgMCUsIHJnYmEoMCwgMCwgMCwgMC40MikgMzMlLCB0cmFuc3BhcmVudCAwJSk7YmFja2dyb3VuZC1zaXplOjRweCAxMDAlO2JhY2tncm91bmQtcmVwZWF0OnJlcGVhdC14fS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWZpbGwgLm1hdC1mb3JtLWZpZWxkLWZsZXh7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC4wNCl9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2UtZmlsbC5tYXQtZm9ybS1maWVsZC1kaXNhYmxlZCAubWF0LWZvcm0tZmllbGQtZmxleHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjAyKX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1maWxsIC5tYXQtZm9ybS1maWVsZC11bmRlcmxpbmU6OmJlZm9yZXtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjQyKX0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1maWxsLm1hdC1mb3JtLWZpZWxkLWRpc2FibGVkIC5tYXQtZm9ybS1maWVsZC1sYWJlbHtjb2xvcjojNzU3NTc1fS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLWZpbGwubWF0LWZvcm0tZmllbGQtZGlzYWJsZWQgLm1hdC1mb3JtLWZpZWxkLXVuZGVybGluZTo6YmVmb3Jle2JhY2tncm91bmQtY29sb3I6dHJhbnNwYXJlbnR9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2Utb3V0bGluZSAubWF0LWZvcm0tZmllbGQtb3V0bGluZXtjb2xvcjpyZ2JhKDAsMCwwLC4xMil9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2Utb3V0bGluZSAubWF0LWZvcm0tZmllbGQtb3V0bGluZS10aGlja3tjb2xvcjpyZ2JhKDAsMCwwLC44Nyl9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2Utb3V0bGluZS5tYXQtZm9jdXNlZCAubWF0LWZvcm0tZmllbGQtb3V0bGluZS10aGlja3tjb2xvcjojZjU3YzAwfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLW91dGxpbmUubWF0LWZvY3VzZWQubWF0LWFjY2VudCAubWF0LWZvcm0tZmllbGQtb3V0bGluZS10aGlja3tjb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLW91dGxpbmUubWF0LWZvY3VzZWQubWF0LXdhcm4gLm1hdC1mb3JtLWZpZWxkLW91dGxpbmUtdGhpY2t7Y29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQtYXBwZWFyYW5jZS1vdXRsaW5lLm1hdC1mb3JtLWZpZWxkLWludmFsaWQubWF0LWZvcm0tZmllbGQtaW52YWxpZCAubWF0LWZvcm0tZmllbGQtb3V0bGluZS10aGlja3tjb2xvcjojZjQ0MzM2fS5tYXQtZm9ybS1maWVsZC1hcHBlYXJhbmNlLW91dGxpbmUubWF0LWZvcm0tZmllbGQtZGlzYWJsZWQgLm1hdC1mb3JtLWZpZWxkLWxhYmVse2NvbG9yOiM3NTc1NzV9Lm1hdC1mb3JtLWZpZWxkLWFwcGVhcmFuY2Utb3V0bGluZS5tYXQtZm9ybS1maWVsZC1kaXNhYmxlZCAubWF0LWZvcm0tZmllbGQtb3V0bGluZXtjb2xvcjpyZ2JhKDAsMCwwLC4wNil9Lm1hdC1pY29uLm1hdC1wcmltYXJ5e2NvbG9yOiNmNTdjMDB9Lm1hdC1pY29uLm1hdC1hY2NlbnR7Y29sb3I6I2ZmOTgwMH0ubWF0LWljb24ubWF0LXdhcm57Y29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQtdHlwZS1tYXQtbmF0aXZlLXNlbGVjdCAubWF0LWZvcm0tZmllbGQtaW5maXg6OmFmdGVye2NvbG9yOiM2MTYxNjF9Lm1hdC1pbnB1dC1lbGVtZW50OmRpc2FibGVkLC5tYXQtZm9ybS1maWVsZC10eXBlLW1hdC1uYXRpdmUtc2VsZWN0Lm1hdC1mb3JtLWZpZWxkLWRpc2FibGVkIC5tYXQtZm9ybS1maWVsZC1pbmZpeDo6YWZ0ZXJ7Y29sb3I6Izc1NzU3NX0ubWF0LWlucHV0LWVsZW1lbnR7Y2FyZXQtY29sb3I6I2Y1N2MwMH0ubWF0LWlucHV0LWVsZW1lbnQ6OnBsYWNlaG9sZGVye2NvbG9yOnJnYmEoOTcsOTcsOTcsLjQyKX0ubWF0LWlucHV0LWVsZW1lbnQ6Oi1tb3otcGxhY2Vob2xkZXJ7Y29sb3I6cmdiYSg5Nyw5Nyw5NywuNDIpfS5tYXQtaW5wdXQtZWxlbWVudDo6LXdlYmtpdC1pbnB1dC1wbGFjZWhvbGRlcntjb2xvcjpyZ2JhKDk3LDk3LDk3LC40Mil9Lm1hdC1pbnB1dC1lbGVtZW50Oi1tcy1pbnB1dC1wbGFjZWhvbGRlcntjb2xvcjpyZ2JhKDk3LDk3LDk3LC40Mil9Lm1hdC1hY2NlbnQgLm1hdC1pbnB1dC1lbGVtZW50e2NhcmV0LWNvbG9yOiNmZjk4MDB9Lm1hdC13YXJuIC5tYXQtaW5wdXQtZWxlbWVudCwubWF0LWZvcm0tZmllbGQtaW52YWxpZCAubWF0LWlucHV0LWVsZW1lbnR7Y2FyZXQtY29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQtdHlwZS1tYXQtbmF0aXZlLXNlbGVjdC5tYXQtZm9ybS1maWVsZC1pbnZhbGlkIC5tYXQtZm9ybS1maWVsZC1pbmZpeDo6YWZ0ZXJ7Y29sb3I6I2Y0NDMzNn0ubWF0LWxpc3QtYmFzZSAubWF0LWxpc3QtaXRlbXtjb2xvcjojMjEyMTIxfS5tYXQtbGlzdC1iYXNlIC5tYXQtbGlzdC1vcHRpb257Y29sb3I6IzIxMjEyMX0ubWF0LWxpc3QtYmFzZSAubWF0LXN1YmhlYWRlcntjb2xvcjojNjE2MTYxfS5tYXQtbGlzdC1pdGVtLWRpc2FibGVke2JhY2tncm91bmQtY29sb3I6I2VlZX0ubWF0LWxpc3Qtb3B0aW9uOmhvdmVyLC5tYXQtbGlzdC1vcHRpb246Zm9jdXMsLm1hdC1uYXYtbGlzdCAubWF0LWxpc3QtaXRlbTpob3ZlciwubWF0LW5hdi1saXN0IC5tYXQtbGlzdC1pdGVtOmZvY3VzLC5tYXQtYWN0aW9uLWxpc3QgLm1hdC1saXN0LWl0ZW06aG92ZXIsLm1hdC1hY3Rpb24tbGlzdCAubWF0LWxpc3QtaXRlbTpmb2N1c3tiYWNrZ3JvdW5kOnJnYmEoMCwwLDAsLjA0KX0ubWF0LWxpc3Qtc2luZ2xlLXNlbGVjdGVkLW9wdGlvbiwubWF0LWxpc3Qtc2luZ2xlLXNlbGVjdGVkLW9wdGlvbjpob3ZlciwubWF0LWxpc3Qtc2luZ2xlLXNlbGVjdGVkLW9wdGlvbjpmb2N1c3tiYWNrZ3JvdW5kOnJnYmEoMCwwLDAsLjEyKX0ubWF0LW1lbnUtcGFuZWx7YmFja2dyb3VuZDojZmZmfS5tYXQtbWVudS1wYW5lbDpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCAycHggNHB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA0cHggNXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LW1lbnUtaXRlbXtiYWNrZ3JvdW5kOnRyYW5zcGFyZW50O2NvbG9yOiMyMTIxMjF9Lm1hdC1tZW51LWl0ZW1bZGlzYWJsZWRdLC5tYXQtbWVudS1pdGVtW2Rpc2FibGVkXTo6YWZ0ZXJ7Y29sb3I6cmdiYSgwLDAsMCwuMzgpfS5tYXQtbWVudS1pdGVtIC5tYXQtaWNvbi1uby1jb2xvciwubWF0LW1lbnUtaXRlbS1zdWJtZW51LXRyaWdnZXI6OmFmdGVye2NvbG9yOnJnYmEoMCwwLDAsLjU0KX0ubWF0LW1lbnUtaXRlbTpob3Zlcjpub3QoW2Rpc2FibGVkXSksLm1hdC1tZW51LWl0ZW0uY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoW2Rpc2FibGVkXSksLm1hdC1tZW51LWl0ZW0uY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KFtkaXNhYmxlZF0pLC5tYXQtbWVudS1pdGVtLWhpZ2hsaWdodGVkOm5vdChbZGlzYWJsZWRdKXtiYWNrZ3JvdW5kOnJnYmEoMCwwLDAsLjA0KX0ubWF0LXBhZ2luYXRvcntiYWNrZ3JvdW5kOiNmZmZ9Lm1hdC1wYWdpbmF0b3IsLm1hdC1wYWdpbmF0b3ItcGFnZS1zaXplIC5tYXQtc2VsZWN0LXRyaWdnZXJ7Y29sb3I6IzYxNjE2MX0ubWF0LXBhZ2luYXRvci1kZWNyZW1lbnQsLm1hdC1wYWdpbmF0b3ItaW5jcmVtZW50e2JvcmRlci10b3A6MnB4IHNvbGlkIHJnYmEoMCwwLDAsLjU0KTtib3JkZXItcmlnaHQ6MnB4IHNvbGlkIHJnYmEoMCwwLDAsLjU0KX0ubWF0LXBhZ2luYXRvci1maXJzdCwubWF0LXBhZ2luYXRvci1sYXN0e2JvcmRlci10b3A6MnB4IHNvbGlkIHJnYmEoMCwwLDAsLjU0KX0ubWF0LWljb24tYnV0dG9uW2Rpc2FibGVkXSAubWF0LXBhZ2luYXRvci1kZWNyZW1lbnQsLm1hdC1pY29uLWJ1dHRvbltkaXNhYmxlZF0gLm1hdC1wYWdpbmF0b3ItaW5jcmVtZW50LC5tYXQtaWNvbi1idXR0b25bZGlzYWJsZWRdIC5tYXQtcGFnaW5hdG9yLWZpcnN0LC5tYXQtaWNvbi1idXR0b25bZGlzYWJsZWRdIC5tYXQtcGFnaW5hdG9yLWxhc3R7Ym9yZGVyLWNvbG9yOnJnYmEoMCwwLDAsLjM4KX0ubWF0LXByb2dyZXNzLWJhci1iYWNrZ3JvdW5ke2ZpbGw6I2ZmOTgwMH0ubWF0LXByb2dyZXNzLWJhci1idWZmZXJ7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwfS5tYXQtcHJvZ3Jlc3MtYmFyLWZpbGw6OmFmdGVye2JhY2tncm91bmQtY29sb3I6I2Y1N2MwMH0ubWF0LXByb2dyZXNzLWJhci5tYXQtYWNjZW50IC5tYXQtcHJvZ3Jlc3MtYmFyLWJhY2tncm91bmR7ZmlsbDojZmY5ODAwfS5tYXQtcHJvZ3Jlc3MtYmFyLm1hdC1hY2NlbnQgLm1hdC1wcm9ncmVzcy1iYXItYnVmZmVye2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMH0ubWF0LXByb2dyZXNzLWJhci5tYXQtYWNjZW50IC5tYXQtcHJvZ3Jlc3MtYmFyLWZpbGw6OmFmdGVye2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMH0ubWF0LXByb2dyZXNzLWJhci5tYXQtd2FybiAubWF0LXByb2dyZXNzLWJhci1iYWNrZ3JvdW5ke2ZpbGw6I2ZmY2RkMn0ubWF0LXByb2dyZXNzLWJhci5tYXQtd2FybiAubWF0LXByb2dyZXNzLWJhci1idWZmZXJ7YmFja2dyb3VuZC1jb2xvcjojZmZjZGQyfS5tYXQtcHJvZ3Jlc3MtYmFyLm1hdC13YXJuIC5tYXQtcHJvZ3Jlc3MtYmFyLWZpbGw6OmFmdGVye2JhY2tncm91bmQtY29sb3I6I2Y0NDMzNn0ubWF0LXByb2dyZXNzLXNwaW5uZXIgY2lyY2xlLC5tYXQtc3Bpbm5lciBjaXJjbGV7c3Ryb2tlOiNmNTdjMDB9Lm1hdC1wcm9ncmVzcy1zcGlubmVyLm1hdC1hY2NlbnQgY2lyY2xlLC5tYXQtc3Bpbm5lci5tYXQtYWNjZW50IGNpcmNsZXtzdHJva2U6I2ZmOTgwMH0ubWF0LXByb2dyZXNzLXNwaW5uZXIubWF0LXdhcm4gY2lyY2xlLC5tYXQtc3Bpbm5lci5tYXQtd2FybiBjaXJjbGV7c3Ryb2tlOiNmNDQzMzZ9Lm1hdC1yYWRpby1vdXRlci1jaXJjbGV7Ym9yZGVyLWNvbG9yOiM2MTYxNjF9Lm1hdC1yYWRpby1idXR0b24ubWF0LXByaW1hcnkubWF0LXJhZGlvLWNoZWNrZWQgLm1hdC1yYWRpby1vdXRlci1jaXJjbGV7Ym9yZGVyLWNvbG9yOiNmNTdjMDB9Lm1hdC1yYWRpby1idXR0b24ubWF0LXByaW1hcnkgLm1hdC1yYWRpby1pbm5lci1jaXJjbGUsLm1hdC1yYWRpby1idXR0b24ubWF0LXByaW1hcnkgLm1hdC1yYWRpby1yaXBwbGUgLm1hdC1yaXBwbGUtZWxlbWVudDpub3QoLm1hdC1yYWRpby1wZXJzaXN0ZW50LXJpcHBsZSksLm1hdC1yYWRpby1idXR0b24ubWF0LXByaW1hcnkubWF0LXJhZGlvLWNoZWNrZWQgLm1hdC1yYWRpby1wZXJzaXN0ZW50LXJpcHBsZSwubWF0LXJhZGlvLWJ1dHRvbi5tYXQtcHJpbWFyeTphY3RpdmUgLm1hdC1yYWRpby1wZXJzaXN0ZW50LXJpcHBsZXtiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDB9Lm1hdC1yYWRpby1idXR0b24ubWF0LWFjY2VudC5tYXQtcmFkaW8tY2hlY2tlZCAubWF0LXJhZGlvLW91dGVyLWNpcmNsZXtib3JkZXItY29sb3I6I2ZmOTgwMH0ubWF0LXJhZGlvLWJ1dHRvbi5tYXQtYWNjZW50IC5tYXQtcmFkaW8taW5uZXItY2lyY2xlLC5tYXQtcmFkaW8tYnV0dG9uLm1hdC1hY2NlbnQgLm1hdC1yYWRpby1yaXBwbGUgLm1hdC1yaXBwbGUtZWxlbWVudDpub3QoLm1hdC1yYWRpby1wZXJzaXN0ZW50LXJpcHBsZSksLm1hdC1yYWRpby1idXR0b24ubWF0LWFjY2VudC5tYXQtcmFkaW8tY2hlY2tlZCAubWF0LXJhZGlvLXBlcnNpc3RlbnQtcmlwcGxlLC5tYXQtcmFkaW8tYnV0dG9uLm1hdC1hY2NlbnQ6YWN0aXZlIC5tYXQtcmFkaW8tcGVyc2lzdGVudC1yaXBwbGV7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwfS5tYXQtcmFkaW8tYnV0dG9uLm1hdC13YXJuLm1hdC1yYWRpby1jaGVja2VkIC5tYXQtcmFkaW8tb3V0ZXItY2lyY2xle2JvcmRlci1jb2xvcjojZjQ0MzM2fS5tYXQtcmFkaW8tYnV0dG9uLm1hdC13YXJuIC5tYXQtcmFkaW8taW5uZXItY2lyY2xlLC5tYXQtcmFkaW8tYnV0dG9uLm1hdC13YXJuIC5tYXQtcmFkaW8tcmlwcGxlIC5tYXQtcmlwcGxlLWVsZW1lbnQ6bm90KC5tYXQtcmFkaW8tcGVyc2lzdGVudC1yaXBwbGUpLC5tYXQtcmFkaW8tYnV0dG9uLm1hdC13YXJuLm1hdC1yYWRpby1jaGVja2VkIC5tYXQtcmFkaW8tcGVyc2lzdGVudC1yaXBwbGUsLm1hdC1yYWRpby1idXR0b24ubWF0LXdhcm46YWN0aXZlIC5tYXQtcmFkaW8tcGVyc2lzdGVudC1yaXBwbGV7YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtcmFkaW8tYnV0dG9uLm1hdC1yYWRpby1kaXNhYmxlZC5tYXQtcmFkaW8tY2hlY2tlZCAubWF0LXJhZGlvLW91dGVyLWNpcmNsZSwubWF0LXJhZGlvLWJ1dHRvbi5tYXQtcmFkaW8tZGlzYWJsZWQgLm1hdC1yYWRpby1vdXRlci1jaXJjbGV7Ym9yZGVyLWNvbG9yOnJnYmEoMCwwLDAsLjM4KX0ubWF0LXJhZGlvLWJ1dHRvbi5tYXQtcmFkaW8tZGlzYWJsZWQgLm1hdC1yYWRpby1yaXBwbGUgLm1hdC1yaXBwbGUtZWxlbWVudCwubWF0LXJhZGlvLWJ1dHRvbi5tYXQtcmFkaW8tZGlzYWJsZWQgLm1hdC1yYWRpby1pbm5lci1jaXJjbGV7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1yYWRpby1idXR0b24ubWF0LXJhZGlvLWRpc2FibGVkIC5tYXQtcmFkaW8tbGFiZWwtY29udGVudHtjb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1yYWRpby1idXR0b24gLm1hdC1yaXBwbGUtZWxlbWVudHtiYWNrZ3JvdW5kLWNvbG9yOiMwMDB9Lm1hdC1zZWxlY3QtdmFsdWV7Y29sb3I6IzIxMjEyMX0ubWF0LXNlbGVjdC1wbGFjZWhvbGRlcntjb2xvcjpyZ2JhKDk3LDk3LDk3LC40Mil9Lm1hdC1zZWxlY3QtZGlzYWJsZWQgLm1hdC1zZWxlY3QtdmFsdWV7Y29sb3I6Izc1NzU3NX0ubWF0LXNlbGVjdC1hcnJvd3tjb2xvcjojNjE2MTYxfS5tYXQtc2VsZWN0LXBhbmVse2JhY2tncm91bmQ6I2ZmZn0ubWF0LXNlbGVjdC1wYW5lbDpub3QoW2NsYXNzKj1tYXQtZWxldmF0aW9uLXpdKXtib3gtc2hhZG93OjBweCAycHggNHB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA0cHggNXB4IDBweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCAxcHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LXNlbGVjdC1wYW5lbCAubWF0LW9wdGlvbi5tYXQtc2VsZWN0ZWQ6bm90KC5tYXQtb3B0aW9uLW11bHRpcGxlKXtiYWNrZ3JvdW5kOnJnYmEoMCwwLDAsLjEyKX0ubWF0LWZvcm0tZmllbGQubWF0LWZvY3VzZWQubWF0LXByaW1hcnkgLm1hdC1zZWxlY3QtYXJyb3d7Y29sb3I6I2Y1N2MwMH0ubWF0LWZvcm0tZmllbGQubWF0LWZvY3VzZWQubWF0LWFjY2VudCAubWF0LXNlbGVjdC1hcnJvd3tjb2xvcjojZmY5ODAwfS5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZC5tYXQtd2FybiAubWF0LXNlbGVjdC1hcnJvd3tjb2xvcjojZjQ0MzM2fS5tYXQtZm9ybS1maWVsZCAubWF0LXNlbGVjdC5tYXQtc2VsZWN0LWludmFsaWQgLm1hdC1zZWxlY3QtYXJyb3d7Y29sb3I6I2Y0NDMzNn0ubWF0LWZvcm0tZmllbGQgLm1hdC1zZWxlY3QubWF0LXNlbGVjdC1kaXNhYmxlZCAubWF0LXNlbGVjdC1hcnJvd3tjb2xvcjojNzU3NTc1fS5tYXQtZHJhd2VyLWNvbnRhaW5lcntiYWNrZ3JvdW5kLWNvbG9yOiNmYWZhZmE7Y29sb3I6IzIxMjEyMX0ubWF0LWRyYXdlcntiYWNrZ3JvdW5kLWNvbG9yOiNmZmY7Y29sb3I6IzIxMjEyMX0ubWF0LWRyYXdlci5tYXQtZHJhd2VyLXB1c2h7YmFja2dyb3VuZC1jb2xvcjojZmZmfS5tYXQtZHJhd2VyOm5vdCgubWF0LWRyYXdlci1zaWRlKXtib3gtc2hhZG93OjBweCA4cHggMTBweCAtNXB4IHJnYmEoMCwgMCwgMCwgMC4yKSwwcHggMTZweCAyNHB4IDJweCByZ2JhKDAsIDAsIDAsIDAuMTQpLDBweCA2cHggMzBweCA1cHggcmdiYSgwLCAwLCAwLCAwLjEyKX0ubWF0LWRyYXdlci1zaWRle2JvcmRlci1yaWdodDpzb2xpZCAxcHggcmdiYSgwLDAsMCwuMTIpfS5tYXQtZHJhd2VyLXNpZGUubWF0LWRyYXdlci1lbmR7Ym9yZGVyLWxlZnQ6c29saWQgMXB4IHJnYmEoMCwwLDAsLjEyKTtib3JkZXItcmlnaHQ6bm9uZX1bZGlyPXJ0bF0gLm1hdC1kcmF3ZXItc2lkZXtib3JkZXItbGVmdDpzb2xpZCAxcHggcmdiYSgwLDAsMCwuMTIpO2JvcmRlci1yaWdodDpub25lfVtkaXI9cnRsXSAubWF0LWRyYXdlci1zaWRlLm1hdC1kcmF3ZXItZW5ke2JvcmRlci1sZWZ0Om5vbmU7Ym9yZGVyLXJpZ2h0OnNvbGlkIDFweCByZ2JhKDAsMCwwLC4xMil9Lm1hdC1kcmF3ZXItYmFja2Ryb3AubWF0LWRyYXdlci1zaG93bntiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjYpfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC1jaGVja2VkIC5tYXQtc2xpZGUtdG9nZ2xlLXRodW1ie2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMH0ubWF0LXNsaWRlLXRvZ2dsZS5tYXQtY2hlY2tlZCAubWF0LXNsaWRlLXRvZ2dsZS1iYXJ7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI1NSwxNTIsMCwuNTQpfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC1jaGVja2VkIC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjojZmY5ODAwfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC1wcmltYXJ5Lm1hdC1jaGVja2VkIC5tYXQtc2xpZGUtdG9nZ2xlLXRodW1ie2JhY2tncm91bmQtY29sb3I6I2Y1N2MwMH0ubWF0LXNsaWRlLXRvZ2dsZS5tYXQtcHJpbWFyeS5tYXQtY2hlY2tlZCAubWF0LXNsaWRlLXRvZ2dsZS1iYXJ7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI0NSwxMjQsMCwuNTQpfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC1wcmltYXJ5Lm1hdC1jaGVja2VkIC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjojZjU3YzAwfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC13YXJuLm1hdC1jaGVja2VkIC5tYXQtc2xpZGUtdG9nZ2xlLXRodW1ie2JhY2tncm91bmQtY29sb3I6I2Y0NDMzNn0ubWF0LXNsaWRlLXRvZ2dsZS5tYXQtd2Fybi5tYXQtY2hlY2tlZCAubWF0LXNsaWRlLXRvZ2dsZS1iYXJ7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI0NCw2Nyw1NCwuNTQpfS5tYXQtc2xpZGUtdG9nZ2xlLm1hdC13YXJuLm1hdC1jaGVja2VkIC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtc2xpZGUtdG9nZ2xlOm5vdCgubWF0LWNoZWNrZWQpIC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjojMDAwfS5tYXQtc2xpZGUtdG9nZ2xlLXRodW1ie2JveC1zaGFkb3c6MHB4IDJweCAxcHggLTFweCByZ2JhKDAsIDAsIDAsIDAuMiksMHB4IDFweCAxcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xNCksMHB4IDFweCAzcHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMik7YmFja2dyb3VuZC1jb2xvcjojZmFmYWZhfS5tYXQtc2xpZGUtdG9nZ2xlLWJhcntiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjM4KX0ubWF0LXNsaWRlci10cmFjay1iYWNrZ3JvdW5ke2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMjYpfS5tYXQtcHJpbWFyeSAubWF0LXNsaWRlci10cmFjay1maWxsLC5tYXQtcHJpbWFyeSAubWF0LXNsaWRlci10aHVtYiwubWF0LXByaW1hcnkgLm1hdC1zbGlkZXItdGh1bWItbGFiZWx7YmFja2dyb3VuZC1jb2xvcjojZjU3YzAwfS5tYXQtcHJpbWFyeSAubWF0LXNsaWRlci10aHVtYi1sYWJlbC10ZXh0e2NvbG9yOiNmZmZ9Lm1hdC1hY2NlbnQgLm1hdC1zbGlkZXItdHJhY2stZmlsbCwubWF0LWFjY2VudCAubWF0LXNsaWRlci10aHVtYiwubWF0LWFjY2VudCAubWF0LXNsaWRlci10aHVtYi1sYWJlbHtiYWNrZ3JvdW5kLWNvbG9yOiNmZjk4MDB9Lm1hdC1hY2NlbnQgLm1hdC1zbGlkZXItdGh1bWItbGFiZWwtdGV4dHtjb2xvcjojZmZmfS5tYXQtd2FybiAubWF0LXNsaWRlci10cmFjay1maWxsLC5tYXQtd2FybiAubWF0LXNsaWRlci10aHVtYiwubWF0LXdhcm4gLm1hdC1zbGlkZXItdGh1bWItbGFiZWx7YmFja2dyb3VuZC1jb2xvcjojZjQ0MzM2fS5tYXQtd2FybiAubWF0LXNsaWRlci10aHVtYi1sYWJlbC10ZXh0e2NvbG9yOiNmZmZ9Lm1hdC1zbGlkZXItZm9jdXMtcmluZ3tiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDE1MiwwLC4yKX0ubWF0LXNsaWRlcjpob3ZlciAubWF0LXNsaWRlci10cmFjay1iYWNrZ3JvdW5kLC5jZGstZm9jdXNlZCAubWF0LXNsaWRlci10cmFjay1iYWNrZ3JvdW5ke2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMzgpfS5tYXQtc2xpZGVyLWRpc2FibGVkIC5tYXQtc2xpZGVyLXRyYWNrLWJhY2tncm91bmQsLm1hdC1zbGlkZXItZGlzYWJsZWQgLm1hdC1zbGlkZXItdHJhY2stZmlsbCwubWF0LXNsaWRlci1kaXNhYmxlZCAubWF0LXNsaWRlci10aHVtYntiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjI2KX0ubWF0LXNsaWRlci1kaXNhYmxlZDpob3ZlciAubWF0LXNsaWRlci10cmFjay1iYWNrZ3JvdW5ke2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMjYpfS5tYXQtc2xpZGVyLW1pbi12YWx1ZSAubWF0LXNsaWRlci1mb2N1cy1yaW5ne2JhY2tncm91bmQtY29sb3I6cmdiYSgwLDAsMCwuMTIpfS5tYXQtc2xpZGVyLW1pbi12YWx1ZS5tYXQtc2xpZGVyLXRodW1iLWxhYmVsLXNob3dpbmcgLm1hdC1zbGlkZXItdGh1bWIsLm1hdC1zbGlkZXItbWluLXZhbHVlLm1hdC1zbGlkZXItdGh1bWItbGFiZWwtc2hvd2luZyAubWF0LXNsaWRlci10aHVtYi1sYWJlbHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjg3KX0ubWF0LXNsaWRlci1taW4tdmFsdWUubWF0LXNsaWRlci10aHVtYi1sYWJlbC1zaG93aW5nLmNkay1mb2N1c2VkIC5tYXQtc2xpZGVyLXRodW1iLC5tYXQtc2xpZGVyLW1pbi12YWx1ZS5tYXQtc2xpZGVyLXRodW1iLWxhYmVsLXNob3dpbmcuY2RrLWZvY3VzZWQgLm1hdC1zbGlkZXItdGh1bWItbGFiZWx7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDAsMCwwLC4yNil9Lm1hdC1zbGlkZXItbWluLXZhbHVlOm5vdCgubWF0LXNsaWRlci10aHVtYi1sYWJlbC1zaG93aW5nKSAubWF0LXNsaWRlci10aHVtYntib3JkZXItY29sb3I6cmdiYSgwLDAsMCwuMjYpO2JhY2tncm91bmQtY29sb3I6dHJhbnNwYXJlbnR9Lm1hdC1zbGlkZXItbWluLXZhbHVlOm5vdCgubWF0LXNsaWRlci10aHVtYi1sYWJlbC1zaG93aW5nKTpob3ZlciAubWF0LXNsaWRlci10aHVtYiwubWF0LXNsaWRlci1taW4tdmFsdWU6bm90KC5tYXQtc2xpZGVyLXRodW1iLWxhYmVsLXNob3dpbmcpLmNkay1mb2N1c2VkIC5tYXQtc2xpZGVyLXRodW1ie2JvcmRlci1jb2xvcjpyZ2JhKDAsMCwwLC4zOCl9Lm1hdC1zbGlkZXItbWluLXZhbHVlOm5vdCgubWF0LXNsaWRlci10aHVtYi1sYWJlbC1zaG93aW5nKTpob3Zlci5tYXQtc2xpZGVyLWRpc2FibGVkIC5tYXQtc2xpZGVyLXRodW1iLC5tYXQtc2xpZGVyLW1pbi12YWx1ZTpub3QoLm1hdC1zbGlkZXItdGh1bWItbGFiZWwtc2hvd2luZykuY2RrLWZvY3VzZWQubWF0LXNsaWRlci1kaXNhYmxlZCAubWF0LXNsaWRlci10aHVtYntib3JkZXItY29sb3I6cmdiYSgwLDAsMCwuMjYpfS5tYXQtc2xpZGVyLWhhcy10aWNrcyAubWF0LXNsaWRlci13cmFwcGVyOjphZnRlcntib3JkZXItY29sb3I6cmdiYSgwLDAsMCwuNyl9Lm1hdC1zbGlkZXItaG9yaXpvbnRhbCAubWF0LXNsaWRlci10aWNrc3tiYWNrZ3JvdW5kLWltYWdlOnJlcGVhdGluZy1saW5lYXItZ3JhZGllbnQodG8gcmlnaHQsIHJnYmEoMCwgMCwgMCwgMC43KSwgcmdiYSgwLCAwLCAwLCAwLjcpIDJweCwgdHJhbnNwYXJlbnQgMCwgdHJhbnNwYXJlbnQpO2JhY2tncm91bmQtaW1hZ2U6LW1vei1yZXBlYXRpbmctbGluZWFyLWdyYWRpZW50KDAuMDAwMWRlZywgcmdiYSgwLCAwLCAwLCAwLjcpLCByZ2JhKDAsIDAsIDAsIDAuNykgMnB4LCB0cmFuc3BhcmVudCAwLCB0cmFuc3BhcmVudCl9Lm1hdC1zbGlkZXItdmVydGljYWwgLm1hdC1zbGlkZXItdGlja3N7YmFja2dyb3VuZC1pbWFnZTpyZXBlYXRpbmctbGluZWFyLWdyYWRpZW50KHRvIGJvdHRvbSwgcmdiYSgwLCAwLCAwLCAwLjcpLCByZ2JhKDAsIDAsIDAsIDAuNykgMnB4LCB0cmFuc3BhcmVudCAwLCB0cmFuc3BhcmVudCl9Lm1hdC1zdGVwLWhlYWRlci5jZGsta2V5Ym9hcmQtZm9jdXNlZCwubWF0LXN0ZXAtaGVhZGVyLmNkay1wcm9ncmFtLWZvY3VzZWQsLm1hdC1zdGVwLWhlYWRlcjpob3ZlcntiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMCwwLDAsLjA0KX1AbWVkaWEoaG92ZXI6IG5vbmUpey5tYXQtc3RlcC1oZWFkZXI6aG92ZXJ7YmFja2dyb3VuZDpub25lfX0ubWF0LXN0ZXAtaGVhZGVyIC5tYXQtc3RlcC1sYWJlbCwubWF0LXN0ZXAtaGVhZGVyIC5tYXQtc3RlcC1vcHRpb25hbHtjb2xvcjojNjE2MTYxfS5tYXQtc3RlcC1oZWFkZXIgLm1hdC1zdGVwLWljb257YmFja2dyb3VuZC1jb2xvcjojNjE2MTYxO2NvbG9yOiNmZmZ9Lm1hdC1zdGVwLWhlYWRlciAubWF0LXN0ZXAtaWNvbi1zZWxlY3RlZCwubWF0LXN0ZXAtaGVhZGVyIC5tYXQtc3RlcC1pY29uLXN0YXRlLWRvbmUsLm1hdC1zdGVwLWhlYWRlciAubWF0LXN0ZXAtaWNvbi1zdGF0ZS1lZGl0e2JhY2tncm91bmQtY29sb3I6I2Y1N2MwMDtjb2xvcjojZmZmfS5tYXQtc3RlcC1oZWFkZXIgLm1hdC1zdGVwLWljb24tc3RhdGUtZXJyb3J7YmFja2dyb3VuZC1jb2xvcjp0cmFuc3BhcmVudDtjb2xvcjojZjQ0MzM2fS5tYXQtc3RlcC1oZWFkZXIgLm1hdC1zdGVwLWxhYmVsLm1hdC1zdGVwLWxhYmVsLWFjdGl2ZXtjb2xvcjojMjEyMTIxfS5tYXQtc3RlcC1oZWFkZXIgLm1hdC1zdGVwLWxhYmVsLm1hdC1zdGVwLWxhYmVsLWVycm9ye2NvbG9yOiNmNDQzMzZ9Lm1hdC1zdGVwcGVyLWhvcml6b250YWwsLm1hdC1zdGVwcGVyLXZlcnRpY2Fse2JhY2tncm91bmQtY29sb3I6I2ZmZn0ubWF0LXN0ZXBwZXItdmVydGljYWwtbGluZTo6YmVmb3Jle2JvcmRlci1sZWZ0LWNvbG9yOnJnYmEoMCwwLDAsLjEyKX0ubWF0LWhvcml6b250YWwtc3RlcHBlci1oZWFkZXI6OmJlZm9yZSwubWF0LWhvcml6b250YWwtc3RlcHBlci1oZWFkZXI6OmFmdGVyLC5tYXQtc3RlcHBlci1ob3Jpem9udGFsLWxpbmV7Ym9yZGVyLXRvcC1jb2xvcjpyZ2JhKDAsMCwwLC4xMil9Lm1hdC1zb3J0LWhlYWRlci1hcnJvd3tjb2xvcjojNjE2MTYxfS5tYXQtdGFiLW5hdi1iYXIsLm1hdC10YWItaGVhZGVye2JvcmRlci1ib3R0b206MXB4IHNvbGlkIHJnYmEoMCwwLDAsLjEyKX0ubWF0LXRhYi1ncm91cC1pbnZlcnRlZC1oZWFkZXIgLm1hdC10YWItbmF2LWJhciwubWF0LXRhYi1ncm91cC1pbnZlcnRlZC1oZWFkZXIgLm1hdC10YWItaGVhZGVye2JvcmRlci10b3A6MXB4IHNvbGlkIHJnYmEoMCwwLDAsLjEyKTtib3JkZXItYm90dG9tOm5vbmV9Lm1hdC10YWItbGFiZWwsLm1hdC10YWItbGlua3tjb2xvcjojMjEyMTIxfS5tYXQtdGFiLWxhYmVsLm1hdC10YWItZGlzYWJsZWQsLm1hdC10YWItbGluay5tYXQtdGFiLWRpc2FibGVke2NvbG9yOiM3NTc1NzV9Lm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tY2hldnJvbntib3JkZXItY29sb3I6IzIxMjEyMX0ubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1kaXNhYmxlZCAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9ue2JvcmRlci1jb2xvcjojNzU3NTc1fS5tYXQtdGFiLWdyb3VwW2NsYXNzKj1tYXQtYmFja2dyb3VuZC1dIC5tYXQtdGFiLWhlYWRlciwubWF0LXRhYi1uYXYtYmFyW2NsYXNzKj1tYXQtYmFja2dyb3VuZC1de2JvcmRlci1ib3R0b206bm9uZTtib3JkZXItdG9wOm5vbmV9Lm1hdC10YWItZ3JvdXAubWF0LXByaW1hcnkgLm1hdC10YWItbGFiZWwuY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1ncm91cC5tYXQtcHJpbWFyeSAubWF0LXRhYi1sYWJlbC5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LXByaW1hcnkgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1wcmltYXJ5IC5tYXQtdGFiLWxpbmsuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLW5hdi1iYXIubWF0LXByaW1hcnkgLm1hdC10YWItbGFiZWwuY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1wcmltYXJ5IC5tYXQtdGFiLWxpbmsuY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1wcmltYXJ5IC5tYXQtdGFiLWxpbmsuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpe2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMTUyLDAsLjMpfS5tYXQtdGFiLWdyb3VwLm1hdC1wcmltYXJ5IC5tYXQtaW5rLWJhciwubWF0LXRhYi1uYXYtYmFyLm1hdC1wcmltYXJ5IC5tYXQtaW5rLWJhcntiYWNrZ3JvdW5kLWNvbG9yOiNmNTdjMDB9Lm1hdC10YWItZ3JvdXAubWF0LXByaW1hcnkubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LWluay1iYXIsLm1hdC10YWItbmF2LWJhci5tYXQtcHJpbWFyeS5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtaW5rLWJhcntiYWNrZ3JvdW5kLWNvbG9yOiNmZmZ9Lm1hdC10YWItZ3JvdXAubWF0LWFjY2VudCAubWF0LXRhYi1sYWJlbC5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1hY2NlbnQgLm1hdC10YWItbGFiZWwuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1hY2NlbnQgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1hY2NlbnQgLm1hdC10YWItbGluay5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1hY2NlbnQgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLW5hdi1iYXIubWF0LWFjY2VudCAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKXtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDE1MiwwLC4zKX0ubWF0LXRhYi1ncm91cC5tYXQtYWNjZW50IC5tYXQtaW5rLWJhciwubWF0LXRhYi1uYXYtYmFyLm1hdC1hY2NlbnQgLm1hdC1pbmstYmFye2JhY2tncm91bmQtY29sb3I6I2ZmOTgwMH0ubWF0LXRhYi1ncm91cC5tYXQtYWNjZW50Lm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LWluay1iYXIsLm1hdC10YWItbmF2LWJhci5tYXQtYWNjZW50Lm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LWluay1iYXJ7YmFja2dyb3VuZC1jb2xvcjojZmZmfS5tYXQtdGFiLWdyb3VwLm1hdC13YXJuIC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LXdhcm4gLm1hdC10YWItbGFiZWwuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC13YXJuIC5tYXQtdGFiLWxpbmsuY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1ncm91cC5tYXQtd2FybiAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC13YXJuIC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtd2FybiAubWF0LXRhYi1sYWJlbC5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtd2FybiAubWF0LXRhYi1saW5rLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtd2FybiAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKXtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDIwNSwyMTAsLjMpfS5tYXQtdGFiLWdyb3VwLm1hdC13YXJuIC5tYXQtaW5rLWJhciwubWF0LXRhYi1uYXYtYmFyLm1hdC13YXJuIC5tYXQtaW5rLWJhcntiYWNrZ3JvdW5kLWNvbG9yOiNmNDQzMzZ9Lm1hdC10YWItZ3JvdXAubWF0LXdhcm4ubWF0LWJhY2tncm91bmQtd2FybiAubWF0LWluay1iYXIsLm1hdC10YWItbmF2LWJhci5tYXQtd2Fybi5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtaW5rLWJhcntiYWNrZ3JvdW5kLWNvbG9yOiNmZmZ9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LXRhYi1sYWJlbC5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGFiZWwuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGluay5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKXtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDE1MiwwLC4zKX0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWhlYWRlciwubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxpbmtzLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24sLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWhlYWRlciwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGlua3MsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9ue2JhY2tncm91bmQtY29sb3I6I2Y1N2MwMH0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGluaywubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXByaW1hcnkgLm1hdC10YWItbGFiZWwsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxpbmt7Y29sb3I6I2ZmZn0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLm1hdC10YWItZGlzYWJsZWQsLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LXRhYi1saW5rLm1hdC10YWItZGlzYWJsZWQsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxhYmVsLm1hdC10YWItZGlzYWJsZWQsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWxpbmsubWF0LXRhYi1kaXNhYmxlZHtjb2xvcjpyZ2JhKDI1NSwyNTUsMjU1LC40KX0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLWNoZXZyb24sLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLWNoZXZyb257Ym9yZGVyLWNvbG9yOiNmZmZ9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1kaXNhYmxlZCAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9uLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtcHJpbWFyeSAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1kaXNhYmxlZCAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9ue2JvcmRlci1jb2xvcjpyZ2JhKDI1NSwyNTUsMjU1LC40KX0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1wcmltYXJ5IC5tYXQtcmlwcGxlLWVsZW1lbnR7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI1NSwyNTUsMjU1LC4xMil9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGluay5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1sYWJlbC5jZGsta2V5Ym9hcmQtZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1saW5rLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGluay5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCl7YmFja2dyb3VuZC1jb2xvcjpyZ2JhKDI1NSwxNTIsMCwuMyl9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWhlYWRlciwubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGlua3MsLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWhlYWRlciwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1saW5rcywubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbntiYWNrZ3JvdW5kLWNvbG9yOiNmZjk4MDB9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1saW5rLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxpbmt7Y29sb3I6I2ZmZn0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGFiZWwubWF0LXRhYi1kaXNhYmxlZCwubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGluay5tYXQtdGFiLWRpc2FibGVkLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWxhYmVsLm1hdC10YWItZGlzYWJsZWQsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItbGluay5tYXQtdGFiLWRpc2FibGVke2NvbG9yOnJnYmEoMjU1LDI1NSwyNTUsLjQpfS5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLWFjY2VudCAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9uLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLWNoZXZyb257Ym9yZGVyLWNvbG9yOiNmZmZ9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLWRpc2FibGVkIC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLWNoZXZyb24sLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tZGlzYWJsZWQgLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tY2hldnJvbntib3JkZXItY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuNCl9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtYWNjZW50IC5tYXQtcmlwcGxlLWVsZW1lbnQsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC1hY2NlbnQgLm1hdC1yaXBwbGUtZWxlbWVudHtiYWNrZ3JvdW5kLWNvbG9yOnJnYmEoMjU1LDI1NSwyNTUsLjEyKX0ubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWxhYmVsLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1sYWJlbC5jZGstcHJvZ3JhbS1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5rLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5rLmNkay1wcm9ncmFtLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXdhcm4gLm1hdC10YWItbGFiZWwuY2RrLWtleWJvYXJkLWZvY3VzZWQ6bm90KC5tYXQtdGFiLWRpc2FibGVkKSwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXdhcm4gLm1hdC10YWItbGFiZWwuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5rLmNkay1rZXlib2FyZC1mb2N1c2VkOm5vdCgubWF0LXRhYi1kaXNhYmxlZCksLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWxpbmsuY2RrLXByb2dyYW0tZm9jdXNlZDpub3QoLm1hdC10YWItZGlzYWJsZWQpe2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMjA1LDIxMCwuMyl9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1oZWFkZXIsLm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5rcywubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWhlYWRlci1wYWdpbmF0aW9uLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1oZWFkZXIsLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWxpbmtzLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbntiYWNrZ3JvdW5kLWNvbG9yOiNmNDQzMzZ9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1sYWJlbCwubWF0LXRhYi1ncm91cC5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWxpbmssLm1hdC10YWItbmF2LWJhci5tYXQtYmFja2dyb3VuZC13YXJuIC5tYXQtdGFiLWxhYmVsLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5re2NvbG9yOiNmZmZ9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1sYWJlbC5tYXQtdGFiLWRpc2FibGVkLC5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXdhcm4gLm1hdC10YWItbGluay5tYXQtdGFiLWRpc2FibGVkLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1sYWJlbC5tYXQtdGFiLWRpc2FibGVkLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1saW5rLm1hdC10YWItZGlzYWJsZWR7Y29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuNCl9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9uLC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXRhYi1oZWFkZXItcGFnaW5hdGlvbi1jaGV2cm9ue2JvcmRlci1jb2xvcjojZmZmfS5tYXQtdGFiLWdyb3VwLm1hdC1iYWNrZ3JvdW5kLXdhcm4gLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tZGlzYWJsZWQgLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tY2hldnJvbiwubWF0LXRhYi1uYXYtYmFyLm1hdC1iYWNrZ3JvdW5kLXdhcm4gLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tZGlzYWJsZWQgLm1hdC10YWItaGVhZGVyLXBhZ2luYXRpb24tY2hldnJvbntib3JkZXItY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuNCl9Lm1hdC10YWItZ3JvdXAubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50LC5tYXQtdGFiLW5hdi1iYXIubWF0LWJhY2tncm91bmQtd2FybiAubWF0LXJpcHBsZS1lbGVtZW50e2JhY2tncm91bmQtY29sb3I6cmdiYSgyNTUsMjU1LDI1NSwuMTIpfS5tYXQtdG9vbGJhcntiYWNrZ3JvdW5kOiNmNWY1ZjU7Y29sb3I6IzIxMjEyMX0ubWF0LXRvb2xiYXIubWF0LXByaW1hcnl7YmFja2dyb3VuZDojZjU3YzAwO2NvbG9yOiNmZmZ9Lm1hdC10b29sYmFyLm1hdC1hY2NlbnR7YmFja2dyb3VuZDojZmY5ODAwO2NvbG9yOiNmZmZ9Lm1hdC10b29sYmFyLm1hdC13YXJue2JhY2tncm91bmQ6I2Y0NDMzNjtjb2xvcjojZmZmfS5tYXQtdG9vbGJhciAubWF0LWZvcm0tZmllbGQtdW5kZXJsaW5lLC5tYXQtdG9vbGJhciAubWF0LWZvcm0tZmllbGQtcmlwcGxlLC5tYXQtdG9vbGJhciAubWF0LWZvY3VzZWQgLm1hdC1mb3JtLWZpZWxkLXJpcHBsZXtiYWNrZ3JvdW5kLWNvbG9yOmN1cnJlbnRDb2xvcn0ubWF0LXRvb2xiYXIgLm1hdC1mb3JtLWZpZWxkLWxhYmVsLC5tYXQtdG9vbGJhciAubWF0LWZvY3VzZWQgLm1hdC1mb3JtLWZpZWxkLWxhYmVsLC5tYXQtdG9vbGJhciAubWF0LXNlbGVjdC12YWx1ZSwubWF0LXRvb2xiYXIgLm1hdC1zZWxlY3QtYXJyb3csLm1hdC10b29sYmFyIC5tYXQtZm9ybS1maWVsZC5tYXQtZm9jdXNlZCAubWF0LXNlbGVjdC1hcnJvd3tjb2xvcjppbmhlcml0fS5tYXQtdG9vbGJhciAubWF0LWlucHV0LWVsZW1lbnR7Y2FyZXQtY29sb3I6Y3VycmVudENvbG9yfS5tYXQtdG9vbHRpcHtiYWNrZ3JvdW5kOnJnYmEoOTcsOTcsOTcsLjkpfS5tYXQtdHJlZXtiYWNrZ3JvdW5kOiNmZmZ9Lm1hdC10cmVlLW5vZGUsLm1hdC1uZXN0ZWQtdHJlZS1ub2Rle2NvbG9yOiMyMTIxMjF9Lm1hdC1zbmFjay1iYXItY29udGFpbmVye2NvbG9yOnJnYmEoMjU1LDI1NSwyNTUsLjcpO2JhY2tncm91bmQ6IzMyMzIzMjtib3gtc2hhZG93OjBweCAzcHggNXB4IC0xcHggcmdiYSgwLCAwLCAwLCAwLjIpLDBweCA2cHggMTBweCAwcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwwcHggMXB4IDE4cHggMHB4IHJnYmEoMCwgMCwgMCwgMC4xMil9Lm1hdC1zaW1wbGUtc25hY2tiYXItYWN0aW9ue2NvbG9yOiNmZjk4MDB9Cjwvc3R5bGU+Cgo8c3R5bGU+CiAgaHRtbCwKICBib2R5IHsKICAgIG1hcmdpbjogMDsKICAgIHBhZGRpbmc6IDA7CiAgICBoZWlnaHQ6IDEwMCU7CiAgICBmb250LWZhbWlseTogUm9ib3RvLCBzYW5zLXNlcmlmOwogICAgY29sb3I6IHZhcigtLXByaW1hcnktdGV4dC1jb2xvcik7CgogICAgLyogTGVnYWN5IG1lY2hhbmlzbSB0byBhdm9pZCBpc3N1ZXMgd2l0aCBzdWJwaXhlbCBhbnRpLWFsaWFzaW5nIG9uIG1hY09TLgogICAgICoKICAgICAqIEluIHRoZSBwYXN0IFsxXSwgbWFjT1Mgc3VicGl4ZWwgQUEgY2F1c2VkIGV4Y2Vzc2l2ZSBib2xkaW5nIGZvciBsaWdodC1vbi1kYXJrIHRleHQ7IHRoaXMgcnVsZQogICAgICogYXZvaWRzIHRoYXQgYnkgcmVxdWVzdGluZyBub24tc3VicGl4ZWwgQUEgYWx3YXlzLCByYXRoZXIgdGhhbiB0aGUgZGVmYXVsdCBiZWhhdmlvciwgd2hpY2ggaXMKICAgICAqIHRvIHVzZSBzdWJwaXhlbCBBQSB3aGVuIGF2YWlsYWJsZS4gVGhlIG9yaWdpbmFsIGlzc3VlIHdhcyAiZml4ZWQiIGJ5IHJlbW92aW5nIHN1YnBpeGVsIEFBIGluCiAgICAgKiBtYWNPUyAxNCAoTW9qYXZlKSwgYnV0IGZvciBsZWdhY3kgcmVhc29ucyB0aGV5IHByZXNlcnZlZCB0aGUgYm9sZGluZyBlZmZlY3QgYXMgYW4gb3B0aW9uLgogICAgICogQ2hyb21lIHRoZW4gaW4gdHVybiB1cGRhdGVkIGl0cyBmb250IHJlbmRlcmluZyB0byBhcHBseSB0aGF0IGJvbGRpbmcgZWZmZWN0IFsyXSwgd2hpY2ggbWVhbnMKICAgICAqIHRoYXQgZXZlbiB0aG91Z2ggdGhlIGAtd2Via2l0LWZvbnQtc21vb3RoaW5nYCBkb2NzIFszXSBzdWdnZXN0IHRoYXQgc2V0dGluZyBgYW50aWFsaWFzZWRgCiAgICAgKiB3b3VsZCBoYXZlIG5vIGVmZmVjdCBmb3IgcmVjZW50IHZlcnNpb25zIG9mIG1hY09TLCBpdCBzdGlsbCBpcyBuZWVkZWQgdG8gYXZvaWQgdGhlIGJvbGRpbmcuCiAgICAgKgogICAgICogWzFdOiBodHRwOi8vd3d3LmxpZ2h0ZXJyYS5jb20vYXJ0aWNsZXMvbWFjb3N4dGV4dGFhYnVnLwogICAgICogWzJdOiBodHRwczovL2J1Z3MuY2hyb21pdW0ub3JnL3AvY2hyb21pdW0vaXNzdWVzL2RldGFpbD9pZD04NTg4NjEKICAgICAqIFszXTogaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQ1NTL2ZvbnQtc21vb3RoCiAgICAgKgogICAgICovCgogICAgLXdlYmtpdC1mb250LXNtb290aGluZzogYW50aWFsaWFzZWQ7CiAgfQo8L3N0eWxlPgoKPC9oZWFkPjxib2R5Pjx0Yi13ZWJhcHA+PC90Yi13ZWJhcHA+PHNjcmlwdCBzcmM9ImluZGV4LmpzIj48L3NjcmlwdD48L2JvZHk+PC9odG1sPg==",
- "headers": [
- [
- "content-type",
- "text/html; charset=utf-8"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/environment": {
- "data": "eyJkYXRhX2xvY2F0aW9uIjogInJ1bnMiLCAid2luZG93X3RpdGxlIjogIiJ9",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=metrics%2FmAP_0.5": {
- "data": "W1sxNjE0ODg1NTQwLjc3NzA2NzcsIDAsIDAuMDMxOTExMjY4ODMwMjk5MzhdXQ==",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=metrics%2FmAP_0.5%3A0.95": {
- "data": "W1sxNjE0ODg1NTQwLjc3NzA4ODksIDAsIDAuMDA4ODMwMTQ0MDcwMDg4ODYzXV0=",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=metrics%2Fprecision": {
- "data": "W1sxNjE0ODg1NTQwLjc3NzAxOTcsIDAsIDAuMF1d",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=metrics%2Frecall": {
- "data": "W1sxNjE0ODg1NTQwLjc3NzA0NTIsIDAsIDAuMF1d",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=train%2Fbox_loss": {
- "data": "W1sxNjE0ODg1NTQwLjc3NjQ3NTQsIDAsIDAuMDk0ODM1NzA2MDU1MTY0MzRdXQ==",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=train%2Fcls_loss": {
- "data": "W1sxNjE0ODg1NTQwLjc3Njk3MjgsIDAsIDAuMDM0NTA3MjMzNjQ5NDkyMjY0XV0=",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/scalars?run=train%2Fyolov5s_results2&tag=train%2Fobj_loss": {
- "data": "W1sxNjE0ODg1NTQwLjc3Njg3MTIsIDAsIDAuMzU2MTI2MTU5NDI5NTUwMTddXQ==",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugin/scalars/tags": {
- "data": "eyJ0cmFpbi95b2xvdjVzX3Jlc3VsdHMyIjogeyJ0cmFpbi9ib3hfbG9zcyI6IHsiZGlzcGxheU5hbWUiOiAidHJhaW4vYm94X2xvc3MiLCAiZGVzY3JpcHRpb24iOiAiIn0sICJ0cmFpbi9vYmpfbG9zcyI6IHsiZGlzcGxheU5hbWUiOiAidHJhaW4vb2JqX2xvc3MiLCAiZGVzY3JpcHRpb24iOiAiIn0sICJ0cmFpbi9jbHNfbG9zcyI6IHsiZGlzcGxheU5hbWUiOiAidHJhaW4vY2xzX2xvc3MiLCAiZGVzY3JpcHRpb24iOiAiIn0sICJtZXRyaWNzL3ByZWNpc2lvbiI6IHsiZGlzcGxheU5hbWUiOiAibWV0cmljcy9wcmVjaXNpb24iLCAiZGVzY3JpcHRpb24iOiAiIn0sICJtZXRyaWNzL3JlY2FsbCI6IHsiZGlzcGxheU5hbWUiOiAibWV0cmljcy9yZWNhbGwiLCAiZGVzY3JpcHRpb24iOiAiIn0sICJtZXRyaWNzL21BUF8wLjUiOiB7ImRpc3BsYXlOYW1lIjogIm1ldHJpY3MvbUFQXzAuNSIsICJkZXNjcmlwdGlvbiI6ICIifSwgIm1ldHJpY3MvbUFQXzAuNTowLjk1IjogeyJkaXNwbGF5TmFtZSI6ICJtZXRyaWNzL21BUF8wLjU6MC45NSIsICJkZXNjcmlwdGlvbiI6ICIifSwgInZhbC9ib3hfbG9zcyI6IHsiZGlzcGxheU5hbWUiOiAidmFsL2JveF9sb3NzIiwgImRlc2NyaXB0aW9uIjogIiJ9LCAidmFsL29ial9sb3NzIjogeyJkaXNwbGF5TmFtZSI6ICJ2YWwvb2JqX2xvc3MiLCAiZGVzY3JpcHRpb24iOiAiIn0sICJ2YWwvY2xzX2xvc3MiOiB7ImRpc3BsYXlOYW1lIjogInZhbC9jbHNfbG9zcyIsICJkZXNjcmlwdGlvbiI6ICIifSwgIngvbHIwIjogeyJkaXNwbGF5TmFtZSI6ICJ4L2xyMCIsICJkZXNjcmlwdGlvbiI6ICIifSwgIngvbHIxIjogeyJkaXNwbGF5TmFtZSI6ICJ4L2xyMSIsICJkZXNjcmlwdGlvbiI6ICIifSwgIngvbHIyIjogeyJkaXNwbGF5TmFtZSI6ICJ4L2xyMiIsICJkZXNjcmlwdGlvbiI6ICIifX19",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/plugins_listing": {
- "data": "eyJzY2FsYXJzIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IHRydWUsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJzY2FsYXJzIiwgImxvYWRpbmdfbWVjaGFuaXNtIjogeyJ0eXBlIjogIkNVU1RPTV9FTEVNRU5UIiwgImVsZW1lbnRfbmFtZSI6ICJ0Zi1zY2FsYXItZGFzaGJvYXJkIn19LCAiY3VzdG9tX3NjYWxhcnMiOiB7ImRpc2FibGVfcmVsb2FkIjogZmFsc2UsICJlbmFibGVkIjogZmFsc2UsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJDdXN0b20gU2NhbGFycyIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJDVVNUT01fRUxFTUVOVCIsICJlbGVtZW50X25hbWUiOiAidGYtY3VzdG9tLXNjYWxhci1kYXNoYm9hcmQifX0sICJpbWFnZXMiOiB7ImRpc2FibGVfcmVsb2FkIjogZmFsc2UsICJlbmFibGVkIjogZmFsc2UsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJpbWFnZXMiLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiQ1VTVE9NX0VMRU1FTlQiLCAiZWxlbWVudF9uYW1lIjogInRmLWltYWdlLWRhc2hib2FyZCJ9fSwgImF1ZGlvIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAiYXVkaW8iLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiQ1VTVE9NX0VMRU1FTlQiLCAiZWxlbWVudF9uYW1lIjogInRmLWF1ZGlvLWRhc2hib2FyZCJ9fSwgImRlYnVnZ2VyLXYyIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAiRGVidWdnZXIgVjIiLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiTkdfQ09NUE9ORU5UIn19LCAiZ3JhcGhzIjogeyJkaXNhYmxlX3JlbG9hZCI6IHRydWUsICJlbmFibGVkIjogZmFsc2UsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJncmFwaHMiLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiQ1VTVE9NX0VMRU1FTlQiLCAiZWxlbWVudF9uYW1lIjogInRmLWdyYXBoLWRhc2hib2FyZCJ9fSwgImRpc3RyaWJ1dGlvbnMiOiB7ImRpc2FibGVfcmVsb2FkIjogZmFsc2UsICJlbmFibGVkIjogdHJ1ZSwgInJlbW92ZV9kb20iOiBmYWxzZSwgInRhYl9uYW1lIjogImRpc3RyaWJ1dGlvbnMiLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiQ1VTVE9NX0VMRU1FTlQiLCAiZWxlbWVudF9uYW1lIjogInRmLWRpc3RyaWJ1dGlvbi1kYXNoYm9hcmQifX0sICJoaXN0b2dyYW1zIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IHRydWUsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJoaXN0b2dyYW1zIiwgImxvYWRpbmdfbWVjaGFuaXNtIjogeyJ0eXBlIjogIkNVU1RPTV9FTEVNRU5UIiwgImVsZW1lbnRfbmFtZSI6ICJ0Zi1oaXN0b2dyYW0tZGFzaGJvYXJkIn19LCAidGV4dCI6IHsiZGlzYWJsZV9yZWxvYWQiOiBmYWxzZSwgImVuYWJsZWQiOiBmYWxzZSwgInJlbW92ZV9kb20iOiBmYWxzZSwgInRhYl9uYW1lIjogInRleHQiLCAibG9hZGluZ19tZWNoYW5pc20iOiB7InR5cGUiOiAiQ1VTVE9NX0VMRU1FTlQiLCAiZWxlbWVudF9uYW1lIjogInRmLXRleHQtZGFzaGJvYXJkIn19LCAicHJfY3VydmVzIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAiUFIgQ3VydmVzIiwgImxvYWRpbmdfbWVjaGFuaXNtIjogeyJ0eXBlIjogIkNVU1RPTV9FTEVNRU5UIiwgImVsZW1lbnRfbmFtZSI6ICJ0Zi1wci1jdXJ2ZS1kYXNoYm9hcmQifX0sICJwcm9maWxlX3JlZGlyZWN0IjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAiUHJvZmlsZSIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJDVVNUT01fRUxFTUVOVCIsICJlbGVtZW50X25hbWUiOiAidGYtcHJvZmlsZS1yZWRpcmVjdC1kYXNoYm9hcmQifX0sICJocGFyYW1zIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAiaHBhcmFtcyIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJDVVNUT01fRUxFTUVOVCIsICJlbGVtZW50X25hbWUiOiAidGYtaHBhcmFtcy1kYXNoYm9hcmQifX0sICJtZXNoIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IGZhbHNlLCAicmVtb3ZlX2RvbSI6IGZhbHNlLCAidGFiX25hbWUiOiAibWVzaCIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJDVVNUT01fRUxFTUVOVCIsICJlbGVtZW50X25hbWUiOiAibWVzaC1kYXNoYm9hcmQifX0sICJ0aW1lc2VyaWVzIjogeyJkaXNhYmxlX3JlbG9hZCI6IGZhbHNlLCAiZW5hYmxlZCI6IHRydWUsICJyZW1vdmVfZG9tIjogZmFsc2UsICJ0YWJfbmFtZSI6ICJUaW1lIFNlcmllcyIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJOR19DT01QT05FTlQifX0sICJwcm9qZWN0b3IiOiB7ImRpc2FibGVfcmVsb2FkIjogdHJ1ZSwgImVuYWJsZWQiOiBmYWxzZSwgInJlbW92ZV9kb20iOiBmYWxzZSwgInRhYl9uYW1lIjogInByb2plY3RvciIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJJRlJBTUUiLCAibW9kdWxlX3BhdGgiOiAiL2RhdGEvcGx1Z2luL3Byb2plY3Rvci9pbmRleC5qcyJ9fSwgIndoYXRpZiI6IHsiZGlzYWJsZV9yZWxvYWQiOiBmYWxzZSwgImVuYWJsZWQiOiBmYWxzZSwgInJlbW92ZV9kb20iOiBmYWxzZSwgInRhYl9uYW1lIjogIldoYXQtSWYgVG9vbCIsICJsb2FkaW5nX21lY2hhbmlzbSI6IHsidHlwZSI6ICJJRlJBTUUiLCAibW9kdWxlX3BhdGgiOiAiL2RhdGEvcGx1Z2luL3doYXRpZi9pbmRleC5qcyJ9fX0=",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/data/runs": {
- "data": "WyJ0cmFpbi95b2xvdjVzX3Jlc3VsdHMiLCAidHJhaW4veW9sb3Y1c19yZXN1bHRzMiJd",
- "headers": [
- [
- "content-type",
- "application/json"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/font-roboto/Hgo13k-tfSpn0qi1SFdUfZBw1xU1rKptJj_0jans920.woff2": {
- "data": "d09GMgABAAAAACp8AA4AAAAAUwAAACokAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGmQbmUAcg0oGYACGTBEMCu882RYLg14AATYCJAOHNgQgBYJ8ByAbB0Wzon60XsEcRckcrcr+ywTtCAu7vIkKUSLAEkX79qHYsVrOIXiSMp377A39RgODYjP02tCGSQRohCSzPDz5F++ZOzNvvxxoA3ZwF1dQBbkTWP2kVEVi7w/83Hp/Y6PDGnqCKCJlUaKURMVGDUdvMDJHVIg4QBAkokTKpsw6k0LdbmmVFEuwwOtQpqUCDdCJ2b0GBxDpf/9u9j+XQGQGIl+tEq1VOr0S2T2sZ9/yxZFpIOkgKdrXFN+0M4foFz9c20sDSrJUtd8OCK1oKHa27U18eptmu8+6n1sZZrwh1iFPj21mdFClKFNUq/93o939u+KbE5lkB2SZJB2R5cAGsWTqrUM7zIdYBXl6atOlKtOWiEXbpgo81PXj7dWfHuECB1Jm2+HuZL8f70TNAaYHlnBAUZgNm3JkGG03jk1xP/499lO/h8a025fRsa1BIErglKnQ8fHzfnMpUDgA2BYKi5NUIDQ4QIQIgYgWDRErFiJBAkSyZIhU6RBVaqF0ewuBQAEzgDkQoECEQIBppKlg2GIrPTMQ2TfEnwgiB/rjvUHkMOfAGyCCAZD/FKAcur//DWACClAwQAGBpUlB5GIAtizHa0ttKaeKQm2vQ3WjLhTVQKGY0BvBgRIKqVANlwisjyMh0ppQ1Deh+NGEqrmqWJVvR6sBXG61pUbIcN+o7fsN1YWeG1N63ISEowypb1sGWKzY8DpJ3CkSTjtHmhx5511wiQJFylRcoU2HHkPGTJiyYMWGLXuOcuTKV6Bbj3t69ek3YNCQYSNGTZsxa868FVu2PfTIczt27dl34I23EJdyAwMFfBTxUCZghQAEb+JI40oBPPzwTqYFqckPl/DRyMe08rXrBG3owhTmxS1yn3W+YpMv2NPI6flaXgooRLGrJy3cQy/60I8B12qP3ccaHmAdG67NXtvCNh7iEXawiz3s48D1olde4hVeu970wtsMwjaH99Tmno4VDtFZAeNSrlHIXYr5hnI+ssI6gwG6/lZhafUuYcKQGyyyk21O8pl0F5anRKe+hKRJzioM2PG5intH5jlnvABOsOE15+h57j1YUvnOZcECFrGE5QH5YHFhVcVk89DKF64D2tCFORWrpzfpHFxyGfkocG32wha28RCPBmallW9chzZ0YY50bGIL23iIR92j6eBkRZYtblimWt8BdrGHfRwMjMGVcXiQh0IUU5XwBm/wBm/wRsbArPTgGMKouGlGscxMtljtDPousId9HHCk8eGjnchRVvmebT6Bxp77ruYXziqNopPv7ulXENErGQ4s+RyvBEcuYqbr2GmL3GDVUKy+Fj7ZKiznRWelhByWnEOKchUiN+kQOtihuhEG0J8bccBhQuqyeXrnTrum1lzT8jWp2mttvd+rXmrFWQVIfwX5paKwooXeF1k1MKMFSTfeC7JJvONjX+SHa4rSa/WkWSiSb/fh3hfYv4gLkMKyVHDm+2ltX5m8yJ7Zj+T0P384/U+tXkEdC+GzK+QVhIv8inJt93vWy/aEFWd2g4oPFenBdtqonu5m1d3tTZW48eREz/uAHZAvcedZrc/Z2ZBl7ZbD+VW1lVH3UtjKlWmNTW66A2eK6YxQXGCt7o8ih+Tr9u/et9hB7qnKD2j5a5i4Z9KsXOmQ+czviLa92Z982e1vGSa/gQdzLk/G24L+OfYP7itOpkh5++FJX0EunXxrrYAP7qX7eG+L2sz/9h83iBO6mH7laRzKccmdjdbuSS2w9+gvrXKTz/at3rbWE5gza5LxXcakfbfXdMP6xUO5j0tdabfOe5ev7B89BnJbvZQWauCDDYLpIrhE4fmNdpIEBpLkMbtERT9r0CJMGx6mFx9hzMxRFh5nE59gx8F/UmJxOQqdUvxdSrdHznnugHke87CFcr5fBBHkUDiUWBQxhYnL7ZQICTGkZHFOVtIKkBMhL59LsrssCwVFKCpESS7KslGRk4ZYmjLSyvxqzTAFhmqCgSlEM5ORhbxsZGYnD3uZOcghpTDmeEdBeciHcr3VYKHCBoFwKLkY0WMAyuB/3IaMwpg2D7FgGYsVitms2oC1GfPb8giT520GOw6g0Rsxww33kQ83sgCGM3wFS44oZ1gUKQXJiXJelIuZA7EZFpjhhxdOWOFqsKraELpcEJRAw3BEM4cIS9lYZwxiC5jAdGQXC1HSRElvI7JkE8AQbvjghu/I5y6KAIAtKPRAwQxrYDw/guAGOsE7e7/wGsZi+ukydWme9zxdUpnlFWHcdBcNHJ3NTcyqyq1Mrh6ktI2hnrTtVQtpR0P9yp1NdLkOk6PJsGPejIsG6rax+x1B8gGx/3dnPpA8zNPdGS6AQ2nG60cE+fiDkZAZgArFfpACYdfq1hcvVOAKcZBlx1exPgowcdUHjmrjNRnlbeurgqLfPvZhR61kpJob9SfpQOg1EJ7ycT9eWB0N8FQRgGw66oOyZnCnVokV0Y9MCYsG9eo0atLspha32r0VRNb1baECBKJr067DHZ1QEHyOALWRiiQM6Nd1OVBWeGiuLyOEPpR6zFPA6sDmVoettzPUAlWw0jws/AU4YFQcgIPcDGibdDpcqEGDNV9WLeXh2bCAchCGogdsBIeBEDBThEr5t9agCYv2vfcPkSmmMRFb8XDMhxPBHcUdx4nhFHDquONwi8fz7x+YCadSleJzD5m05MCHU8SkNy9OCHd47Mvdl/yWuwRyBEsOg/wh+PTl26TwTf3p/B0RqEKRBXJh7fST5zENEFDpawHrYY+J1v7H63WjdZv64frlx4i1YNGSZSvixFt135oH1m1IkPiD9gknSfbCS6+89kaKt9gAJXsfe3UUa+YWFWOchEZuwb24FYuxL7kb9+EePIgj8RAexwPkCZyKJ/EiHiQv4X68jDfwFN7EWzgNb+N9vIAP8CHOwEf4HK+SL3AWvsSPeJv8hLPxM/7AJ/gTf+Ec/I3/8RWZ4DySwvflZW3R+c6yo7CT6ILyeEJ0UXm8I7q4PN4TXeIczxcWiC51jpcUlhZd7hwvKywvuqp8vJLo2vLxaqLrnOONhU1E15ePtxDdWD4+TnRT+XhxyM2+pcAIboFAYarPf2YX+CGpvIeFOPMLceFeq6w/gTgKoAOPf8ccgYGG2FEPQNWhofLt/UALE/2mIyCoiUWA8u69T4ycPEbW3F4KAyVXBYbCtFbWDIAcu3egbYgijIKBSmtD3rZHg70UQqd9HYL1m5HgXPSvCAYWDOYwKN7mdOwa82gYrBC4l+W7YTuzMlPOrQBlwS/rf4hsqNQT0ZlDuzeZesi9DmVE0YpagF3r3PY2r9MVxxBTw2Hco1tnXKeDMuJAF1gsIMfjOmbAN1QXPTaSPaYCbcTshjElittS+z/nIl4/b9ZtQGSp2g1zHq1K41Qq7QFeCq6YYH7Dc1act4bNyMpcOWb3gdM0dyI+PWsGO50zEbTHmFCU3YtPIP04/5T7OCK1C77qhjQKb+TGUupLBOix9GHsmjPRi4XI1AiCigGn2ZgTpNVfKSstJaBY0ohrqVDeESsYjADmyaEiQtD64s8Ll5k9zYqF67Ram0p57DSqUwp1KYL2qu0iZU4uuafHGZIUzA/Lbp1zH7cp+VncGlW+u15Bul4rudhswtRWUi+ttiILG20q/+z4wOwPqX+o9gZy2NehB66FNVd4NRro0wqm4aTRZO/iiU0XCpl4YpiHYW0aOeEH8nhtpJV6KtIKO8h74pAu7IpgKUkDYKbDl3dUHnW4w08ZXtMxr2jrw0QmQAtrbcEUdRrS9zvQ7u9W6ZKaqpIdPYcBZ0OfG7xnLXsSYjof7vz2Ab8AR+H4rujx0VQdMg3PM+cokxlNDuMJMWHaGNJ0Rfk+kAWTf1009M98UKgRNLn+y5AIhhvD5j7PKyKGSIyXtSqbH9XMK6Gf3cnYdAy85G7oXdgsD4irnbLXImb7v5s3q9X6r1HsSfXtaptuM9pu/wkHteuoCqHP95OsuN1HphiTTkLsaTN5ZnvaiRx4g3gGLpd/Yi4bLbK4pKJVuFnlZkG6Phpl7KRdA6SrPzFppuJzTWST5rbdgy5L0O4MJlaMC7r4dPbKxEIQmEzFlvfnruhciE7XzhrtnkOe0USojrcyvQeZQNpa/Zv9WoyHHeiuGrEKWY4fYbJraxfWRlMprZXocIL5lOaP/8zbtZLTcCxjYnGpWmCj1FRZ86AMand3Su7LE40xRdnVeUGzTA/dVbM8B5hoivq182/t2V/4mirsvY66MUq9uJDrI/g0Ot2gespzFY0XL7+SKcKExsowxTf6JqTl++Ic0Ok5PDvF4IxCK2qjkxpNDy4QtjMvMMYELnsoDMhe7AriwA4ekL0R21UGh9R70/+ZdCbZ1t6gs4yyUwCzDGFZ5XJqmDs5Asx0Le2pVHLjxclmg04GIdxQGUMnwdL8LFIBDsWoW3ktMIWwVhnP+4K6agDowkRGVZn8jsqOCBlqoKCYlTjJz3k1eODW10lDTcflpoMhxO4l6MrkQSRsdNbMPBo9bNEwPrOSdY6ezTs+lrZGmnpQY/ZZIC1DyjNjOjqHlpZRyyXNd+ZVEMoleF5+i9Vxwi1foWkjhI8lwzFbKbqEPY7idhBST44a75IK9XCsd7mzTsbOuNSwXvCSXSlRLY8tArQFhNT7n+U5KKjGuluuQ/ZkOccGNfHQysY5LL3hutJgXHpyhEP9zmOPaK8fLdSYhEwHuoLbogcvj2XudCGKXCynsEsLUlkBrOEYmQbLUW7gl0tzpqoAJgS55SycCwUTUxqeEosN32jpJNHJUg2MzYX0hse5st1NKhhUchjvkL7ApR6ioKFOEgMPwm+dk9rkGla1ajkHb8jlUGaeBBsW2Fa5mFEZBnTqgQtLmC7kHZzRoEH1BjoU9TWd+cyswCZCXQRO208HPaFk9UL5zFUf0zWnCrbDpCGR0swhjHlHWprAOZSksdvo51vt71uyWcnolYB0FTuT4fm1F49PRbA8XrgjlScpL4Dn6vndtJm/jkn9X3OR9fsWNuK+x+ekfHmC589NrdoMGrktOpNFk43qvZRnTTvP9zS2aOEm+3h2ZsKu+5T0mOZsb6mU3pKWWl+4/ZrZZUSXvhLoOI2i2WqKfS8O03WdTT28eU2AjhSHxLw7ypQ8PhCW7+SNpPBTCiTHkBmJMgTXOHeHc2FjD9q7na2WxKWa8Yk5HqujY3lyNItQQxKQzSTMW/NlNYgmwItXI2cuqmaGAFtJSeOyXAt5YPMsU9Eetk5dMQhV/eq78AM7ohXTU/AS/9O9Ep7WG1s17oShrQgNnEst9OGam5O8LGUOojRXOb4aQJp7GJGWL1zgQG0qFYlu8B/F+tnM4XtFrz77kQUzRT2Gp1WeOBsxdrozEryYyTMRuze2TcCmETjB3TJ1cNQ4ZAHzQNvuRQW2dEdzQHo8r3I9gflbwYhaMyM40VkBtURhRp+mw9yUSsks19NaH/TC330nLVdxRVYWp6q6aogZW5i+zlWTuif/GE/EmPgYjnB8YtJsmytjbBqKvxfd5k1nKkAixEIK1bB3blMaczMgwHpHM/7FTMexvWR5QTEuhYW6evbeSbd+IbboMFVAe8GynImOj5qeA5mvhjd1cSnRSK4BKtKxE8/7KgECClcH07ranaNROF2Zd7NSPN5om6XkLAC2mn5Ot6bcI4SnGLiiE47zBL6mXXjfr2k0cgwVFv7qId4RM2TCrd18jzs8y3QmtDm5arXv2itPt0lvtIeMAYY+hsbbAYaRO0Yj+D0reacKjdgnIfZoOJRLArdDYUx1XscH9BaOi87p9QHn+UDeS0aoMefXqVE0RreFD0UKekWu387+2XdNugWdJAwqXElQFNyie07f59F/9r2FWrftb4ohoAjbX4fupIy0TpVnmp0jJTWTMzfZZwgztzmHDibJZdXd6bTy3DBKVoJDcDnRINejdm6qnX0A3z/Ftv18nFLaSa+htRcA9n5hTGXzj8rmJK2o8uYwak1DihPWnkC2NHejOGnbu1PMTD3IbuKjZ2Mqm75VN6ZoPdQlOTI4bBAsunbRdiIEWpi5B7l+P9A5JxnoX76sQVhNxMLDoNa4qLOtKPVmZVhmXUoFNWPZJvse6Udk88RBZniWgf6CZcDS5/vtXmF9pUFNA7bNemqa+euPV0Yr8mM7ytF8kqEJdTGuf4x9dAy8PWxcAsKB42QAl7QNg3g+AVJ1t0jF62ZU7cNGV6WiO/DfVeTHlh2i68RcVWd6EbrrJsR8QJQe3mrXjKP00YWzRv1Jx4S9RceoRilH9RgI17P+jSaVgEDOC13vY266oWg/D8ZAtQicm57/45NmKmvSs1JmShC00+vb+zzkebtv+0oIxHBqytmEoGJKgsKXgNPwCf4JZGqdGDJa0nxoNAcpYT5i2LNEuOLvKP9M5eHG3iXUaYzcjuL2xo40+hQZ87P6X111zf/I56P/NzJWVdYi8AO6KIDBpWb7vr/LB8KZdp/OU2mOPVYpVZW0nDu9+WTqjek5/9ipp8udhIiPFXfyZv6AsJxwmHvRdaMI07Systy09tpEip/fvWk8dWJnvc8zjh5wJvFkandU7+eduZgN9+B7YZTU4dbCkpbygux7RV0UuBC9toPf8aX43lI/feJ3rMSJbRFVeVvYfKk5vkHyk30daFg2/vJftb/zZ3Hg9SrXQABXbkNhRmn5+N3Ktuli8/DTGsog39nryYE5I8vJpWjSYxMw9JzpAc1zZzwichkj9YGS6Nqiid7C+48l4NwJAyPvS9NaHjW1tCyCap232J53uFidjhKhH1TkL/vFtntLhJ8uGIzo/bO1vPp7sy8sazjitLdEZLtf54u1qFfrmBPeScOtUoM3BXpqK0p6a1CuGuEt9QlJjZWxUY0lyYnNpXDxWvUV+34CKaw/0v1ZQuaN1xMxMdufZUWIKYap1gLgfpoBzXnMYoQyQBP303jc/aWM1rnb2tD6GBZpd89EyLVRneXaQiNAOUD5mtc1jHQG8rI5E1JU+eVQZ1rz1DAg5yBBihnjI5eMjjqphMfRyJTsJCSQjNRsjjW2TEy1EJ37ksJ9HToT9I+3iot59LeAmHgL+FQjDNnOP1sS/J1D8Ly23sMDackfuec4qoP/DtB89ANO66nKXmYOMIi0pBZ+YJrnybUudFw1WRmNFvxeGqE0v23Xdqb9qGH8rKzHT/en7fWsIqz8D1siX33951w2Fakb/8NDa6JOj+VfSfQ1aVtSNV33AihVFeblFUQfD6IH4bUSJe2CXOdRE4ZuwNBbX30c6vMLrfc6EXGoeDhy+MfGY+9eM7/y7sqMRHppaSjBqAjVmBKf1hrXJge6HyeE9gQ+v6j+UZV4Cgb6RxLP/K2uf8Xxm/9x2Fl//MQrcUz7790zo8Oj3QLdvF+1BR2HqsvPjSSMlp09WnOP+7zWE759fmmGqF/cZ58AKI/cazLh9EgBDD3ek+VkEyhXNzY0UgFDT/BkvdAA+tK3rthw4ZtuMtdknYHh7nMyDqhn3LvCU1SRioXahrm3okwt9b5/V1KTK/xktHGKlEQPFLwPu6d6jz2fSlOlhYHB87MEuU562L8f3n2dvr/zaJJaXldekNp6FymDfytz08xfP2NuqRruEudECd5T+SDnvuihCxh6GPB30kXzMKKdmNrV0kOZk0X3GBxFx/610giGeeALVd7s8eMwui0l7/bkSSgYjCRPp5xDapr+XSZeyJ9Mk0VqjaAqVRw1EsrJ+FZicfbDabZC9HupheWXp1lB1siYx1r/sIM9mJ3//fiDn3tQR29TYcG99ptIOBjEJC9lyycaMO2b6Z4CYwHzelRNuiSM1fAcuaEZqUmTmQqFsqUZ4V3l0muJ1Lp9g4M8u//mS8yz2bSateRT3l7ssdL+kyElvbfTikeb2mzhCkIIaUobjXDXyfFsaeBZepC1SwqfpIblzd5paRjPpZDaUhO9pv3xFT4tPIvPisEnbjyKWrzXNtg8nwfaGlqfAaNFldX6ydMJdM7Tn0N25OaLwIJ9vp8Mj16HbnYvz3gszXZtwY2OCNrh2t+Jonv0YHpFJ8BYkuSzC+u8YzIk3jiZ85vndrgCxSMEzenBfLUB/2WcyOD/LyBYUIMeAeJy14vcc57Nf3iW20BtomZ/fPZ8Pgdc8g6titBwO2n/Uf/DraZlwzv3WA8h+wsMrzQ9H1vB0QciK4B9s0LQAcZuHUBj6EFi2LNBANgoXRXTJayuyNy1iDnPzqXA0w9sJB4EwkUc3i/+3odDbi98nglmghYPg6uK8YiVT+nQrfhy7N3Xm9RAWlxyeE2kDRmi3/fd7ly6g6qCMpw+23dzSl/Aaad3D9qR6QiSbQIZVGV5/jw51f88oIEhxxewQHb1oz8devwfhox6UPeiIKDC9xTxhfXsbm79SzhjFN6YhiUFMLj4VffZEtd+iP/8r5L0dSk+rX1/lbElgDGiviSyuv3l6onF9gPwFvv99PTwtn+LIxmw4MuQ4V/zpHdXEijYxbp3BY/sRn7brWwXNLwBFd6Ux4nUTwVnSin/r9MixvfZXqoxCHavfKl0ytZQ1NO5FDvAzfs7sXuctz6ZnaGkYRQ+bXS4dMTWN7YVqFcyuR5SdPUJ9UtAuaA2wFvs79NTw4/8b2NKfP9bfvl5ym/OTcH0mlZEye38BjqqNMm/4mHfzpl/kT2AeWzHv0u4lxFJ62fELRer4HTX06e1aRRGJ8iTkElJjyc1p5wK2iNrJReOUxQoaZeSna2nPq/XD9z3FXrzM8rSLhxHXPqk2ud7FJPFB9T7xcVuqbdCKS4ptowCWKCs+4aU5RfMTH7yy4DjHzYJcOUqoG8rOnc43wD15ctuw8QgOyx1hTINmaGpqVFIWzVz4BxlBVKikhL8qqLEIvYpCvuF3TvZreTa6XFDtoeqANaSpZT/H6akbbBK/RQuo/zcTkxfZ+vbkplGpn7UVMs9zQmG2c7X+XpXTv+cBdXjI76u+h4HlZwiA2aLhCkMbHk88vAkhoxebHpfeKPMU8KN8bRdhbNPQeMHPLNHt/3qMdm+O/MoYkFF6wP4/WJZaXyXv+54j0fSqdzDs6DpHUig71uc8S0OwwUfkBWCkJsOgyuycyB7ldea5n1MqdxAz884aq2+oXOrPZPiWB4eEkzzMDMOtlLQLjXVDTJLfljT3v+qK42C9agOTAgv8gF+vCH/U5enyzaqlnpHrzEzOD81ppJoqSuTLpP8cF412bv07a2OKWRsiNx2/ieD+gNOikIgvKnly8mjCqsrOAu7KVCh/Ae3naAzl5oSgYv3/CE/AQ/2HZUw3jsKBG5Xm5lZbl5rAm+tAhXex5zoot3giRBLl5v+RNPDxYZdPB0+3eQdpUUf3v1Ethq7d4YdXNasiBYnPeWzhONkYuGV2yDe1EoCTQ1z57WGsJwGmaZnvY8YDzwOMHvQ1fCsUVbY4LP+5bVvd6/f1fu4iz7xyQgE2PGAHcADk1pogz7x9M+QGnfza03ps66wQbNs/e69J5ijW5nxUW/TswYZMHD5nVc/GH097EJnpeUpWWuXIF9vyKvqS9CJU7Y1vqbiKHvRyj3cB261kSBQOIwpD3+8X2/eMr+a1I2ojSlMfgGMKXOjOZy7lL1ugdUjL/97vHK8R+AhZbuYc3IZU+Ktf1hz4pj4kFtXrV967Hm4SArb82ojxkz8fR7dTKJTD9/0dK2stFET83Kiw3PoJUyiVh6gSY/X15o08nteW1BcZmZeXklt2N6Ja25oNrOob6pNbalNb2oxt2xujW56uh7SWF1jbqEaQ02Jev8sJSr6SWrku5TUmHePEuFJYsw74Ngi3k+hvbtsTZgjWBHUqeouVi5zLtaX09+lQjk7moKeonyjgMbH226hKUSczTmn1Bu1vwY3fYYuql2K95sjI6ULrW2VvSl++ur2FfrOjrcIVjS8W2CaJ85cyjaVWIWMrD398Wyekj3YVVXXkxRgqGxfoFsuOSrbR7BML3znzRYUYG2q6VipO3PR9hCJLdbfwiU+qOUiMOUF/rxpndfr7zz2/IMEmjyOhTVVkl2rnTatd++frqssdH264RVZlW6bEF5N9CJ6Bss9DaVXy53saGwQbauX7Wivkz5Ob7h5srPinNmtmXvWOhNR2hP3rGfGOyx1libGdRY6LSFp6JWJhXdiUGyg2436kOpUZXNDe2MbguZ1LwyhLiYhLIuWoGgnbKFvdN5f8XVj9H52BChEx1AO3/GSBPwGxxIdcbIztJBS/v/EbKKjXu443eAEvVa+nV517njHzcbj9DrphQ/WLlqonLLQ8Pi0K1rCF4mFjGoJXITVbGsdbZtem05jD1MNc4vrnkgrnNO44u3sDeJuMx7p6W74DNpCVvYELTuNoGZlGWduqaZhbn3tqrU1iPEqJxISu0hd5YTyLpLAf5/V8GpQXKioe+Wyp4/2FSM9Q0t7K21PYln673QqAR8UQni21AVcd0wtjBAHLSUVc21jPUdtBU+nUio5KotMuKRrryFYJZFDKKPGRFdHuHupeBiZWdrpXqMtaANvF2TtC3oCd65C2J3w7uS4Iv/DASiKgg+2yPnWWrdFGDMZMFvQxETMfxQQdD91jfnv7lPA0KF67sSg0RPNx0YD8G2wli/frsw7Catv7at6UcHijBXj4QhYLPQqONCwUfPiAKZAYhF9IDuHPlDuUHS7Pzunra/Cm8HfN97D1T+W4hgQEDflnxgEYq1IqExQb6+PkUdsdHxqFDk9FQmkIHXLYzfbZyZvkTynaQlmmlgiop5oYD5r0O8DyHDFme3FZV/kpzsRugRw+gRtYfsBc5ksdpScMti144kW9gaG5vZ7OcqT2zAwwHu7eSdsy7wX5+RW4ZG00XnXLCfBeuSNT3NSvRrdc9/Ed4DQFdVyTEiheOyr4JjBHG6ZFzOxq4bpYp8feZkWpXJ/aXm+0qU1Mlbxvn3Uns9PV9Am6hTA0Mm5/uplg81CXc35aOCkuE8NbDQXDTSmKIg4akYJGUtfMnEfSLdKMsxe7ag16zwXKeqmVySnFpoT6aJs6dsVb5ug7xT+xMw+PNj2O1oGDLn4UieIik6KzjveqU09jZllD9vnUBxWcRE5ETF10Z7BbJkvOrrC6V7inoqufb6BY08/IBteX49MDz5v6UkJkrLIjFXNdLO9Z7soCck3Q5g80M4xpEsnCuM6RnkaqMeKK9tBtlPw7f+YghsVpL/TaRExq6HU50l779gn3Vr0FK5J/GxoeJoie30+Mslz/poY4aNWfeowRfY62pVfSMzkliOpqn25x926vdwNn976YxWuPY/bD9xX0TIQ/vOx+ZFRP1jNr3uEv+s5/QoH11l7LfeXOaKlIb+2E9OItqcMKh1cZlw1fd4Wkm9o9qsrCZmK6Jy2rZr+OfuAxf1q5zshOQE1UYuqqR9zoOq/9Dr7Hy1IAcZKil1g08N8y3s5CLOEdZmL7zPEURQo4JsJen18oaWfcxLZkCaFlnjur3ml8R28Wj9B9hyPJhPO69JC8QHsn4LY4wefMMLT8zvP2MBesozyaysxhbadohynGL6WFTG+92Pb6feRnvFPxSv+wXLGcclfkh5lXKYqRW8lp68z5QqbaXz8a3Xl2NdFwdGJ76rj3xe0n03E3J3mKY86mt3QDZJ3vrCQGrrqu3zY3/7VA0bzACNfHyNDP4n6eNf7XU/PQPbqVVkZNVW58xpXz8lcUwPpznkn30ATvUyfy+feXrJG2RHJFtJqoj3DElKqVy8Bxz6Plqx1ECoxiuxrp9METGa6mnLWFFRcbDB+GUj7ozlNbjAGQxEZvxSE951YhaKSa8gxm/ZRcQDLEFRKDWV1QdZ7Q7yrqQneCdE7ZYx3NDXDOxvDwWneWE+xUF6xUE9g66CLRUbNa57DmwyJFO1fdgTtPVOOR66G+9HGx4kgvCizV8AR//8Pn0RhDg1ZD9UO2QxxHDnzv2vcUWYi6bjPxIM3uzU2NbU1oBLTqkZQg92NOy53SLd6B24mpCvwEkLkI74jPn9c/myoT9VCckG0nCMu7qSc1KAkq++PFKi52VIc9kMJMBvk/NU2z627MPmw72jvvy5/N8gb8xvJF56Uw+VH7+qbt4rCayiA6TOBdkF3uyhQEnz9S5Gu62SNxpzGuNi8BqQyszr7dkKifBav9WANtAq1on/LDbAOt7r9P7D0ROr/XlzgibSK7PXszUBfTRMkJSOiUc8gMk06ccGWfGTn6kmHsKykoNBMWmJAUSjW1QOr7nhN43aHvqO9jemxdhD9fMRaWZBfxyY2MIVGDswrCouvqElRXXm4O4GK97rsoSAl7UDwMdV1JBga2ztA9vqNdZJP7561OYRpKGvZTmoIm7mou5eRY+PLyO7qpq6aQlNaNspumUGh1Kxg08Ur7gbVeH1VdcL1WjddviYFW93ruuY6ikrWmto6ltrAb6lpFR2Unh1MKa8ITcyuQ7I0V1bWZoAfzHnFkTpE1UHJUM7L2dNY3+lGpYMbPGjrJHQW/YkwHI4ur835+mEdld4u8gCr4fkBjPDkh1pCvMFeCotLs1Qy+226pKjn24lUOg+KlxZjYHX1+TUKeellRQATRk0xDG5Er1gb9mVr37qKlJV6V1OVB8+g0bkooqnybdB7XjXYWmUGgwMOUO1VyingyvEbQModoD7XT5BWWCisnii3SR2uFx9cTSCuRQOuIU2kmdwkLeRWSetBgQXuxGpOimlVLwJF8Y17UBl0p1non2nuqJ/Wq9mVUfSLqkPcFVKe53eHRKu6f8hVcA8qje40d4mX46y7eta7BzFwp6UD8TJlZSwrOEtONUmraBE5+wfiTvOvf6Y/iJHl1WxdFpBUKYqEgf0A3Gm+ES9LmUqqKudNDXKQdUA07FHEnSajf6Z0zDavZoazxAEYouWwJNrSDCDa9gDiThNDvKxUSFL7As0GQStXDOVzyUWIl2kCB0nG1MO0wSIABnYKuNEkemCPZ7G8mi1rAY5lYm0PBXeaZMvrjWVP5VeBlQy8tgGgqpfacIJ9V4L8f3KeiS+5K/ajSLaLlCYfjmjsjiq3qtYyAaqrWqXTwNBP7K3ccAOCO/+m96iI1pZc+USQs3etLtfmHLIDD/WmG6xYgLvyRwtQSjGKoqu3soz0SOndUxRKtxD1QsApXdA7qVjIgaGMgbvpRlZEfVoyYRRc0ekoaB+PFM+IDBEkUMxP7ES9DfYx3bi8zUZXgVzMxgI7KLuBWou2NDvzr7bmmpgHCEbzbv02EhSeb/bNSIsQZXJCYoPqydWMFIlMZwBLgnbP6Dw3XMFMDgAV/Rt5aI1DsQscJup1rhmwoctZGwAq+rdi4/kclLX7FxUk/OjM1Ucy6a+yD8QSvUcpqM/1bdorWNwAQEUwINuV4wqPZmYGqOjfxhyHm+hW+gAet+kRIFaeV/y1GD+UfmcSngKAxy63FACvH5NPf+L+rDGLTAkApkIBFDA6bMIGMHXDFfGvBiva1UN9P2ncTCu/bDfnC4pCT0ZrYN5IAvpLPu0NYrFDjnRpUUK04h1pcXRLEqXQIVNeyqpnHd2rU4B2eMIFamhEDPThVQxfWkWWDEpNUD99H3ntpLBazWxkwK/9g+Xbge4uK7Yr627p0KOmR1Jk9aYiIWp13Wl1Nku4GBjesLO3ZryEt7cPqzek8+ls/azaJPl+TXV779hIknLbc7HNEGrTbMprNVWcNK0uqDvTr4GQ0ObetLk1kpJ2jEPzR2zH2US9K813WLab0jIrr6xm4bw+G7B5JCi/4esblQ1LOhgx2qbZ7ICPbIJ294V1k9jABFfqLuk6D9eMbBm11MuY9jRzD5U1rO60Zovcstn3aT4NR6j0qWjrCNVP8oDnXVOU1TrUZi9s8LIEr6IVCxlNmVns0pOHpxWqwlqg6jrPtHxXUz5xwbOPqMUSa6WAPidgYAO34YLg2sJqpI27SbPHbnMPuNvoCoYx5q1BXktzvQWybhEqypTGUQjiyI1D9VUZVEGVyqtfUDFICi9ELtydSnEmEW5cw5N6GA/F8mV3UfXhjIjn4lzzqcQuxUZi2jLVNT3SzdaVoeLsoNihhwhYQguKIMIJKjB06cYuSyiCCCeowNDQtWFqk6luS9SWOiyobTG78hIGOjuEGWf+9R3YVGGY5Jpqak/MZjoi1Iao/bQjB5apfE7xDOYqfH22UxgmwSukdrNd4CDADzIIsIaBAMwCAXUMLASYggANacwA9gAvfRFCHPqicAi2o5vsDNAXQ0ycjgVpfroczIxQQ+IrhD9P7jwEwpElTebjwtFCkiER4QfWdoMrKf2qAtFvwsAD3rxQvAB4/oLhuZFigsQFSSASHD1KRpXtLgiRM2Dh8hfAk9/oG1Ktci5SlOS0F8WMdZZtswP5UnAuOshpKc58obuujIwnhcSf+7xEnlzh3ZDRw/d+jh5tajQYMKXhbL8+6azgxtKLmxoAAA==",
- "headers": [
- [
- "content-type",
- "font/woff2"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/font-roboto/RxZJdnzeo3R5zSexge8UUZBw1xU1rKptJj_0jans920.woff2": {
- "data": "d09GMgABAAAAACokAA4AAAAAUkQAACnNAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGmQbmXocg0oGYACGTBEMCu1A1wwLg14AATYCJAOHNgQgBYMAByAbO0QF3Bhn2DiAgX12b1EEGwcBhTGLomxQFmT/lwnmGE77wayn0NBAJAPXITeLlQAVKYYKjM1mpr7CgS0HNgpkY1bqRLvLsXy3dA8XPXqvM/yN+w2v2FOlAb85QmOf5P7Az633/wJaSkUwMImTqgk4GDAic6S4MSrGqFakDCocigoYRBqEHnCIYBIGGExRT1Qeqv3690x3z90AwCasSP6ngswqFUVYHrB8VBQAKcYder52r1wzByMHJRZ//0+nNV9g+H/GsveOK0AqSpwZGZI47CReYMFvJOfQ2hTNUVES1lvdXXeyFKh29/XX4ACRY/9vTgMuqbMdO2B5UFAD4VG4vRkzpRE/HAS4Jss5uTZKgIn5b///mp923r+ZD/x22f0pcYRbsj0ne84XpsZN7mQyee9lwgszWcwvZJLFD4WkECjkFyHriuAA87NMWVUCV9VTC6S6tsdX+ApZK4nU+gqn6ipcefja71ffCTv/vpktBbH4Q8OmUzIhiS6SSKLxDYn4I3iKlCraxSKRmLCxMhnQLaUZLPeL70z9PLvdGe4aJpgghNJhdNDfIYfbP4Zrr4IRvQYW1AHHsRm/MoBA8QMAALCA4nacDoQBD4hYsRCpUiHSpUMwMSGyZUPkyoe4rB6qxyYEAgXAC0AAAgCBiIUA4KZAB3a3PfY7jNipySXnETvz4unnEjtv7bILiMECgG+hS5x7+iUX4AR8gRVUUNx1liijpQ3akVwcN9akGiFf5sfC53+NGKbR5WqKVWK9kAti+AS1eOOOyCvDaIwf8afMcFGbPJk65ZRuuRKVi5n34MXC5+eY8DF3ego/YaXaA/kGJCdNqR9aLDwevIQdJ0mKNBnyFChToUqNBoJTtOk4zZgJM5as2bDlwIkLV+48lSpzznk9evW57Y677uk3YNCQYfc98NAjk55Y9MySZa+9sWLVmnUbNiE0xggsAhGnnKBtjyf2QAgPTgoEFh8Jtbt2fBCTGwppEGEglZ5H9iEjajJmypb9zQ7WcvY+F29zpybfh8pFRalEVy+iPrfdcde9rn89b9acef9Z6HrqQ4ueWbLsjRWr1qx3vfW+d9770LXhbZuHCFeD868+CuUUv9RhOBpeRLDSKRtpW+4JClYxVTYdM1P8F5yw4yEH/bl6XJhQCcKlImFqL9vlsPiIpJtgDl7nnTDswuvDCv+DO1fDk/MxTTZl2ozHg0XCE4hnXuaoUGRvMwJjpuxnZEv+3pQmUBk753x56pZFeGbJ8s2IMhXxINvIiBgzZS/fU4ueWbJ8N5ZJIjmllGuC4g0HW6/PDdHeZGVFrFqzPhRHACMh5SpUzmRow4YNGzamMFQ4soqMGDNtbEWyl05HornGI/8uT9miZ5Ysd70RacWqNeumCoS86xhHXc3Jp1y9CINvDOn62prjoEx81Jz3IVIDWX7co1E3yT++FWYmuuNgIacdlV09TGcJJhPrX4ppsGwDXfCvkmLgAFmk6LCYxAftHyxYL1O0P9FCx9PR3lipv92N96FztJm7THzvXYCZF1CGmPHV7zjxlE+yUMyjYlkzeXrN1+XDXy7mZ4SaH3nFQ7Ww4uDmIe7T/PFaC3qFyJcS82v/iTr6GwvR3ze+XD27dfVbnYZQeRFxzohzSVz399nlr3kVWPXOwUJ5dHBrvN8bC/o9RRmDNlxKMCFjXvucAiWWoH0uC9Id0GRlZgrJ2SxOo/NX1BHQbaQBUf96uxZTd36ybZDQD2eu0GhiDfZmfDlc0VzFOlV8wKy9uuc9zoT+etNtsqFheWuKpVn11wnNyFUttlZgbJzVYnwrmDBpqX3O62J0xc3aVeaABaXbnkaGt5Tna0TncyyvCyiVfDTfNg2Tskx1qffMM0NtN69smvOiem3QnIGRMuk1rbqfMN9WYlYX54kVN9Zr843PpJvb6ivMNl+RmEB/BdWcgMMDITBSlFAjGMdJwzpJBRcNOoQYINvHmOh+Zu4HWLNzkAM9wsX9KDcejslxl1SqgpTK+nJ6LJP32jr7AVDWFUr1sbAX9oI4EVeZok7QfSSpICmKkKY4cpSbPOWhQPdQpggVKkKD8tGk3AhUzCkqSosK0Ka8dOguBhTPkHIg8915deAkWMcGli0ohh3l4ECFuVAublSIO+XiQfnlCI7BobVXOYT4INHaqwJUXCUV1+OO6HUPqn/XBA0YhnPfJMSUx7g9IXde/1qA99R9t0XLOL0eivXGOox6LVwgCIKWCEHQPYSoiOMCDwv1DyhKju6lTFGqFKXO+RXrwA1csBuEYRfwgABq5RhDmLJAVAIMYC0Me1CEI+XlzHGKeeAEnBafdFBUHkXlD0UUK7FHQxAEERAEEUvELYg9ALxA1QMUuICHcCSXIboBRsXRb32AMzlHPf3L87pFpik149XgSKLrYiABJiQbu7XX0EZ3qpa5pRm10HWgNpbmvXY2psKEBVBRiYumxxD0yfF+4RFhcOKf8uTBydDgQG9QA2iNNAqnhUWBFCuRLAAGylcAEIhW6rsQekPBdeKnxE2kSncIhFMQTwLtqlUHw4S5y9CmoHva/VBPrVxRoSAQJgJKgoic9kRheIYBERIBcwcACx1JTRqgQScM5u6itHBr0qhBsxat2rTrgDEjYrt2VZyzqFi6XHNdtxtQ2CIOaKHU/e2ri+Ee7MoA2fSUxbwhIBp/6EsBkrpI3jbygQfuiQiOrDHBHxAwqwyQgDwGALBLnUWCBAxYjpb9+Roy/wk3QM6CbfsB0CABSxQAnySXXv93+42ZtuaTv23HZhtjsRhL87XmG8w3mW8+33q+NN/tvsvue+KI0PgLi4TLN3UaMG7Gus+UbHrWnK8332j4spfb2B4r9owh3GMQ/P1r9sv3jkH4J/6/8X/35zeIF4eOyoczmc/Yz+9yx8tGBoAK8xg3HB/3Xk/VY2LM+/9p0k2ZNuOxJxgy/GvWnHn/WcCUORZ+dZZsb73z3gcbcmziBQDI4H0igCRkjW8HQ0ISbLrkpsva+aYOt3TqF2HAqN40JtW4af1pRo/H5k34z4I0Ty2b8twLDC+t+jetYVr3ydP0WaYvtr323Q9ZfvrtbfojJ/2tNjOyY0BujRxSHRqQl9GXAgoy+mFAYUY/DiiqJdZsXwtAMZBYr30DAKVAYqNqk4BzWWLzgAtZYuuAylpiWbUUUJUldguoyRKXBdRmiScCLuYjazwIlyBQnNDxd6jn4zYgH2sRfLeGyBuBeX8dvQgt3Aq6mTwCBwO5ip6gBxjoGBZbM34NE52ChI4XgbqSgsMohHqFmIhSL8HR1+qELePMETQQxH8ATAWSCRJ80KkVSFyshn4rVqc4xO4K9/sBbZUfGmjTrPCOlAJr8aYOsysMEbR4GDZjo5nqxAmguf2d+5ll4+q6dZTUZq1hMoksN66UXJTBBGyt+DrbhMcLq9Bk+7CpxVTXjuuYlC46w3z6kfH9bpWmwC9ElhFLbSMmAlXH7IyhWaYUCy19n4kkfj+MNwH1CXMxzHzrLGoTEVEJIpwww/SO24xCz4blyGgkPPISNVwJHMS8s9eaLgV7MO1MMFVxzgWKDObEffRpbR65hHZghKBm46hPHQIbxBUaIedU2SrMOQQSCxSYE85BZDigzEa1QKgIKEMqmHOWKIr7/orgvAATAUj2mnDy/ahrDOXUW7VsRjmHFUELlLgbeqsOaSaMtOVts1bo7cfGG5ZmMnzyvz7a9D8A49yfhKY0fT2zRlfuOMrMoba1d2Hf2SfChT0yvB6uDam/YVYHeti3rIR00JWgXBrYWqccXULUgWBDLc56ozkbZOKZwbkbwr43STuwCuPa2d9GGGB7Fc7RbV2Y1ryEAPZ+fo+bAVMVWitQuWZzibW7iEwCHXQ7lilW/mPjcU90+t1SKzITRy0tdDnD32eBJegGqTt8gwv7C7U0By0yLHifOEbuQI/HKbSqiN2A7cIrLxEuI4jzhl62d8SsW0WgmoflnBB4zekZkQIL7kLPmy8SnYVExDCJn/vsvX46iwidi74aH8QGlQbnqrSnHdb+O9sslbarcTLIeXWoS3vjlXrP/Atapqv5ib+Vp+qjuFwuDUd/fyHu9CVTIq+qFWJV1Ca09xxlk3lq/Sq37HDeHFvIRQz0Bit3uYQ2MH0kRGaKWNr6gj0uyh0nEF3uif0c7nh4lCgrKdH9hQwYPB6dSzZHuxICRr/dIPICn1SQxKhh5hC5lEbayfHCibqcyA3ZtYkTVgm64xjTZc9SxrTlX5q0if+LMeMTHtRHRueOGGKjMO15oLHaiPWlWmRl/IO10evXz7Uh09LcSPILgN4V8uqJuvCbsexNLzoP3QgU4zJftrAt4TZuhNhSaFJDq30QNy+xijFVzLR5y1ZKXp6namdX7u3I6Z6K8vco9tBP1UZPnALuwG2CMSEhWTElyCqRQIzcxyntYtKFHuO26n2pAIJzuhqKmVWMk0lxlhMvhrOMcQYnpoV7MSCclFSNxvg5F/MSasrgQr4o9P/8ce7LjPQpQTUxFy4xpt29wJlYCQSLskVnUbXUlJD+kq+gImoiUOysTerfknkgSGBDUDKkls/jNmRXBzLzuE4Pph76s3u6BjIpbNN2/uUtpLEO4NfUee3hd2ICHNJIbu7KwOJmXM0OKEjTZcEy+gJZO1A8QqI9juOkuT8zAuZZP3b47Ea8GRr/Yqom6GrAfgurEO3uc8eXUoGKktCRgBAsVnVIoJf9NmMuK5NrsY9ALjf2gU9eNkQ3qYUTAKnCxlt0ZamUlmPRKIzah/3WyZgfmmfwywWHYariaOMQdaAnLtycQZ5AEUKtcuPbwWIRiIXc0guTOqWrEHyCxSaVinmQAkGenh5YyHy4OjCmRFbrOukQ0opaxEEb9LTnu4pMNA5oajIR6FNAvzNYBLI5H1jCNkosMq20DStOahu6Tl25xsb5RqciLQK1kSpeRs15JKSgo+2DBNpTgyY1mugTZwLBQyFZ2LYikcEqfUfXzD5bqRfbmJc7cYYTstDGs2DiLeG4oBCqhtfubuK8OpzZGwftSZqHgjNcMqO0bGJkQTvYWwXWjfQkKZ/6Gt0O9Ma9RrPA7FkHm4ogchaY4T0BfhuQpl0SlqxIwD6dfNlAQepRTVGp5sm+1YGJbv55UKec+VpxVrICAWlg8rr/IVfIahPZWyD4cFFDlIMc+CTZ15JKxmYxJL5x33PQTi4/jNDXsEHs6OL1DQlR6YioBK1LayaotNggHdb6wZHpOYgdxN2h7EuKiQ2Cu82lamU02Q63JmZzS29vUgECR0IeX+G5RNlpnEnO7QNnchXLXsAOlQQHHeTBg7EsUtguvOiQEKbkgjf0n6GjHfqwIC4SWja8GiY+QtaysAIH+Xtc/S34rotjyJiIgZU5ikRm+iLHHqKCu1qwRWEv3fudKN0MuGkIb7vVjGeHHxCp9OWJ6ErT2plncvoXMmdytfNnJjFy1gw9xNMkd0saBFfI4o1358aFbq/Y7HG+0KmQY85AZYiQxA0RN7R7GoFWI0woIEO6jdfg5/lv1W9L8MdgGrzibDAjUzPbmi3IYPDcUi4SpawuXitn7HSA2yOtc0ts4mgYWjYsiSiVXBuGBQjXZXxxpS2Jq6yBdvXRk6hLpa/aV6B4YBjv08cEdkBW/TjBgnZNauhzxqZs3IZtaqmJYIwCdm2CuAwGScMv6WjknojNJSYEDVznSdIe4CUSKBCkndAmwd2jkRJS/wOiqKUozXfWEQvrk2GMFeh/k3cHmd+e5nwHpxKCSAEShab0a9gp/nOaf2S/o/xG9ll8TwiBm+JxaYSCbbEJObCxpFX4W0prjI5tAu+5849d5//w4G4tCb/Zm21f/T+Nbt3FsPz5tFFX9NlIbH+MUDEgQNPWNDZJoT5NdbIxox4IqtKPpOXydp7MulwVpi68NL3QjJdbr8VparAvCppfbCLx6mT+zMWP3/nLtb88S5po6i/tPz5fgrJign1I+C8ng+NvE7413p9rF168tNQhevfryFZSZJG3V0igtyMl6O9ysaVvgGqGS8vU4x6h4YtDo7tnP42xk5KyqVHRYYBXqWC0NOfkNTdnG6U3N+VkdtbnteAMzOxO65jaGRsbmNknmTiQDx9VYHY0ZGa1N+ST0xqbRVsbs1uw+hYOOkQjG1NTQ3NbbR0zW5Pf7ATySWpUAhnss/zDmi+ftaPolRu2TY+xLj7oy3F1rQgy9SGLmmrRS//lS2yb2xGz9qqistCVV0fiKdba0at0F5p/aiJS2moXkBRu+nbeQdPeSo9s6wkCN9L3MS9ieyHZcj2+9pNhhq58fh6l8yaHGNjLty5eiJdnZuh+NoqrBqvTz2Orv9swifLM8rOdS0p795yfyM/+IJ+ZrP3pVDKTYxpEhh8pOKo1y1L5Ha/zu0tFqbapOo5zFQVfP9S1p9gfZN4cTnie0LXRlfQ8qXwDaslp5pouMkwwuPsMOiE4aBZsOflG+ED4727GZgRNYxN9XVNjqrEZDCT0H52X7Qe9I/6E9zqfNz6qoQo7hPeaXz69V0QVtoQnI+7F0SO60X6TR2fG42gRPegI/N26X+yk+swhIP7btCIQRHWqtgyiJvtGpxYmsjNiZl/SSme/zt4Ji/uYe943oR5EfcllEZB2JjQoNCrSJzHSlR0ZfWs2gLH4Y3HYJ6Hd5x+6VMLVuBHe9WdPeF70sb1S6GFnUulRZzPjmYVAUOK4MXxDn61Pw5dKkhZ+SWJaEr0OQcdji2X+J/qSrn6ayTNrXK+e/51eTOBfc/d+4AuOj/SLTLiYk5FdGavnesQG1Hbfun/wIcp+umecGndz8Pmu/55jhWYX+XVxtsnULo8PN60YzgdNTK5k3ltIvMyZ3AAkf+lj/tJ/txSbX4a/APGYQkhYo4f8GZW4W9QBzMuFp9hX/bT43ghFd/nQxpC+T08fTX56yqdsHZrCmE1KDwtJSF6Kiz+44xkW1xdC9fcLpfWF0kDxtXdsSt3AG95nRWffzaXmLyFkYf0c3xov9MD9o/Po6sQzfuNk2yPGnpfTh58ktDOyE5tANdr8BVvFmjaoYk1lgw6b1+OBR5THfQ94Fx/8+pMaQh1UQ6ifwL0tQ7dm6M75BLKHm4+LQ5CXLRthbUwO33/58Fbd+Zq4GF0TpJCtdsrY6DQxgiXDv0ihT/A8P5cl7t3QuqBkyjQ1KTn3SXBi15Uk3FBBuF2KtIOuspLQaEZA2iKuQyBSJ5M4IjfcFcW5wfM5x+3gjWm7m5JfjmeNTykE/wmZd3no/oT7OI/gcnfKl+2fAYtdlacfU3kzjfOs1Tw9Dtic3BCSj8idAS1FWxWaDccRf9abIzQWp+/BxieuUAY4Fvs7MjriF3Ix8B/aoRRWwiT+2bfdReP76Bm04DfrWNneH9EMik9onGfaNlh0Le5++w/2ZydnfaE8OpE1Vawp0HL9y3Hc3o87gtUlOQUNrM/I29SN5u915eUZwlWyP5KdgzJtdaceGU/Xayq0jHL7rYg1jM/+QN5ab07+HAGdqByHgdsPegDH6nrUXeIA2teCTYJ/A45V8+hSlwlYwl2LgL3B127ta6hQQSejTE5FibMPfNr/6oc0nqOV9RXdiNwYw3YNWTseODkgBdYpsPNZbubQi/z2yPXYgYs7lzpH5DLsHv9+jP02v/J9dXKHGkUNC4hh0kGVWt851nI32nLbW34r7WccHf7nJBTdL39QUjEWHBhliem7iam4kUWM/VI0VWzF54bYrLdoykuh+WAdCb8fK+PiuvyukOrm4/sF1q+vzZfqCbVf7xJpP3caZmzmzhkItfsJtZYTYXYHu3UTaa7vAeS93ec+XGNz99/tivYf+A04luzXg78fz4tu/j75QCEzPykmujAvEVEH65Jr02lyNKefQ3Wlql8fGbLOE13d/MS/sdu3fjfXnfSd/UYPV1NLqlVBTPHgBw12eq/mS/JGElUMPfh2af/CphSmRNIYyekID2g8pnsxAz2DA4ljCfdZB9+sVmxGZE4l7UQVpGQkZAV7WpVSbP0mUzwbI2/umf9Uy0ktmcz+nVCXeYHBoIApdmVs5dfK0KN0MJ1jTb6V4v/+/3HuzUc7UyWlF4qOqYxBmdbeY2f3SIyyvkk0sHaD1eUgfqzRr9041pagnaRgtyT7OrL5i/+YoaCf4SxIlV5R5Dt26/HgsqTGbs3dJ4aWex4fg/DfFl2iB9MrRP+IHiyt2Aep97kfaNXLixA3Hh26BIdHZxoA79hwtwI4nlQAYsD6fAIv+xngqaASOJ5U3m0CvGMTiNs1dj2akplvk56fBM2U/vL+cpAoe/yAT243YP7wGJyNaa6b7M3ugJ5P5WQ7dz8v22AbItuZVvnAMfHeq3to+9sSKQdBtNMoyeD/R+mZme4Ohm42QDoitPNSevRecBYPdQnwwH4mKP7a2KvjnFt4VvzV6NrT2feIeRej4luQNtDocKUHY8xXMX60zvv+tDdcxzH7vnNIrQxuvcTdXMW4RdPdopNboUOSldQOFsf+X5cbbg+my7ABD0s8EaHpN++9V9z60pDUQyvXZ0zppZZHJ/eBk/D6wSNbB68k/HmVn7v8eR/qM8ydUV1FbwpipiUQvRYo3KSLfnG5AgnTQhyxZxLgCbOhu8G3e3y4m0gWxN2lq3Ze91rqXmKC9bGdjZMjvcEp3KHP9s1xfntFf+1DsIwqjmDUx+amJRsHUa/e+yz75Vsdoy+61DBxST+uNIZxF/YMj0Rn33TB5gyz+yK93DxKyKk4NuCBLZLZBDYiqmG4XvkGaaiTjRiGRrC3nlDZWN95kTQz4KQQi6bXidRmn02HhHsPXftVUw8Zq2PFQ3ei90GytP9z2iNCwEeeYYw9tWygNcxf7xxFBsbZA4HOnkG2QU4iZFhlT2Dv3SvRihZgE2D3CgGfQC8atsGlPWTfDXTy8S8lM1A2ASxOXEz88yar7JnAPu63nJfifq1kn1sVUvizxdmUfWc7q7+3Pq8/lp57B0io0K83MgPXKFSEDbjFl1xhlNSesZcn8F9wV1LuxpQT417qJp6jpvWBxfE/69JjN4KT+CgLgFtk7wRHtA69k9v61ph2h1pkELdhQCugMnrhH2W378pNmskrbMJbXIxjXrXKAVg8rkshfVe2kbzh2JT34fbNoY/9F9iGgW4OVn7GOhru2gd0rjhYxDqWfOkeyZj2PNvkvYG1p7v5evkagdicLkd/d7+bDv60TMsdmz3moqr+17qvcYDCAIWSOMrqnhy+y+6bauvSTuJiE1bh54v8tvhfe6mEf/fWE3aApGjZ9n5TiEqYWF97szYhxCBsdr5efn0LACd9+U1E7I/x/ndm/gy//TFjEV7YHj1bxoitPPcR2FT9cueJm5uemMURt70jqnhIHiQOhV88Ni8+YlkJXoFePnjPuVeD1wZfz6LXu5evKsrntqvjfi68andpd30zh/vZrg52fE2Av9cEYotXNTB/ZtZv2N+wfz+N+XNVQz73hlLXSu/Eq6FrQ69Gb19b6VYC82Eh1t3nBSYJ6hey9CROkMwC7QbbbiyWmTAIRel6hyVJthF20FL+GGGgiABNXYNsoqtHNtFQJ5vo6ZJNwKLDmR6Is1zBZI48KhZ/P/H+5uGHB5f2zz08dPPwq4mXNeI9/2GqVvCeNKrr2i51ILOS2mHH4K9mnrbrgfv7HtgEyYS74nsuj1dxfHnw89259ac93zyDgjycA1KDOL+ojwNpJqQ26eGDmsSU9LxCZpZv1ehEaH1hSV5hflFl1MBQJbWoNL+o9Byl9sGgd1VOXn6RRlp8TNjkXerSXVro5MfQh3eoz+9SQx/CEWFLnBef3f33FfI58uflZXdkVc6r5KhU/HC4LwiZfOKr4hOr26tgNDje0+rE9O3t4Bt9v31oYfoLhFfRs2LzPCzNM1z61G4r3Q1zuxDW0+xMVCRl+rUKPVz7zPPyEZtSlBwTn+NhY0d3SAscjHSuUAqzEjEVD5FMsPaxL5O7pvIiSo5mnekFuDkHJT1SNInkRyJF65EmFD78Ow0Gr+0qOi8T78x2n+m8N1tb115fXu3lauPkFpAZTYsOzHB1drbyaWA0lu8XbK27KFBXdciu8pBAI1Go5fwha4GmB33OJmMpxmN9zmV9zuSJoUGj8dvO4DkgQDKzTohOiwsOb4rpCFBOpuoaKSm08wV1pmRlXyhiaHnvs/JMlbI92pxNMQX7U4pOoHU4egIb30YCh4WrNVsLPJzAEY9FF+vzNvsutDETaXQd4n7l8Do86ZxA1eAlM10985qMQgM3bTVDQ4Ib5INKA+/V2qsgShuhXKhZOl8ZGlZZuVRdQ8lU1TdUVdE3pZBNg4zIID2c7jjuyFhg+I/7xy4IH/tlPWINXZV+ifuxkQEkGTsVgq6uWh+1uSKzsCr5bEiwv7dDbuRZEBgJs2Z4H7XTUSCeONrnWx+fVnglJpjOVCqTKqCwEgszW5PO9J3QV9E6PSbjnwFuIKwGu0XkhkFUn5CA5DmlUpoJMUJswgu8vSulNNZMbWgLcIvA4LRa4/w9P8f1Z+0w4FiQf59gbM40MSecMjcm6poagzbaUC5WEtxGq8Jn6RnKycgaHrHEHsoBpLKXMCFfEh4tDBxU70v3htT6BxuNLt4eqqm9O1zXifVxC7OycAkBLytvtzBLC7fQAKCVIfEqRUYWAcHOXhQPbzdnp2Df1e/efpwemno10dNQecXVzZzMFSWyraZhaMKISRWvjAnQIiGN33b7lu0RFVXWy1GmwPljo/uF75+3VgyMFcsEs5BTumOytJzw4Do1jEgggs2RjdXr2V2fbuJS3lK0OTQUSJorJwl3Xhst8HMoaCrZqh4ArVMDptOGyYd8CQ52mRutevc4Gv85c7D0mLlq8Lbo96oojSX65avg5sS44Ef21kk24Fhbi2vbiUWpz3PTYxGI27KeX9mcuj3f16Ij5q0fuZsoeZJo21VqlWXattAzZtV6wklh6GHSMTVvZ3uSooFLR6ZVppVT4oS5tauXVQ9mGyy8RH7nXiKazdkyWeNXq2s32971k109Apxco5z0vgiV7PSMvghnpDHHkdlN9EP2Lc6c8zXMbIrmoFGDgfrMabWUHkIm4cHjkUCE7mGo62ahdG3dNyl7V9LIwTOhsaByfO9vzmKbxkT8SnFezqvExFdZ5ZFrkwmMkkgXhebE2IdM89C2M4nWl6VNhjYVWczrdPPQgjXkb6pukZTTVJ6U1xQekTXeAaQow6+zX7e79I1No4xN9EmzWqZNsXU3CYaR3KUETWNjGzamzLVRHA8bFhT7Tw9XEMtm2t35ALnkU3NqsnxLtfq0t4zXqma7V5yNZZpukk6XlOOz+oEUJfT9tdxQEf3iHJfY0sHRrNHXx/Fb2Ma03mh2iGlsAhuiZsC3UTi2ibOklBdpIbQXCXKXN8c3Crv9Mvg7PeEwcNtIYb9vIK/GGT7Xy51TcFttsGsGXE784Jd7+TODRbS96R4K85voRlYrd05RDc25QNpQ0aLGUOcRMeZ7bkdGx/YbvpPoF87WjN5YekbPQCPzbgwts1dHoM+eniUcc2NfRGQsqKh84BkuryqrGuTjFy6E3QEy7slxrQl0L+8EemtSnMC0vC5RTp54WkFOR89HRw9Uae/Ck4q9JFOCTrWJnTCSK+MITyr31LzkrHLCSR4EG8XizVwYaGHFXA54BswA91eIN3NOQ4tr53ICg2agXTrO3C4JLS1dzAA3/2lgaSeZ22Wh1fcX+yBE7YyC73dikrljPqb84eJNX/8l4EzHeMbE+AXSY3yOe0RHB/rGRCFucEp0u6DpUIbwoYwm2HW95UX9rtguhJbQ/1cOQu3KLj9cx5W2inAPCfGH9P0pcPwQB9Ke354yH1IH759/xH5TGAfFH/kf9j9/uY2zzjffL8UPdLbCchm/u208JBNICr4x6JplVXLYYt+xiWz5qAhfL2/9ue45ZqDncpXLT/vzmYz0uG4oObvzx+8NN+eHRuJI8oBbZa8+R1MFHn98IlP+bIbNpDKnhJbvVeKqEqcWh9wmuIa+YTTXfRvYon2xpqWopLaltqKmpqO46GJ7bR9PCy0Kre1poUdgLgDPY5z+j4KHpud5z7rbdQGcMaE/7lIX+7bmwDtJuXzjnJ1w6SI5PTcjLuZKRV5qezri04u1jqIlauiR9EhkOHr0yIXiLA9eb0P9EBozP47eVMEsbW2sUnzyaf15ebOs7tG1Y8XJqiQDNSp0tNm0jdgkdZ+LgXNEaqRaulYK5VJsQV5dTEhKulakGjW4kpaaVkkTP6S65UKUp/wdbp1rdRhxkJT32gVrqroaLknM7MSYljpG7uUG5Nyp/54tvADh0sIYa582i6MGRrpEFWWiuab6KRJcy7vdejvud/wYOrmrQ3UPZzdAdj4bsl16trMHJwj9C8BBaPxKa5K4nayl8ATWSLdXfZuqajai9urlaXVLWl1S43gaFezUNHGc2viWGFVqfMapNI6ZqJrQkGIdrVlpSR2gMlMI5Rq69DmzV4hdMrcHAWfs9BAoTZU2Z769bOXxZc3VFkp4xWibBOFYwgTorrQA9CHSRO6XW+RWuU1ulzugk+IJJrd2XG6lfjva1JwnrQ15Fhg+vshoU78zxce0UticGgUkldh2f/wL0iv1vW3a8KS1TM8CWeMproOsp/4470mj6lkw1MdTho+p9Irw0VTODQiyMjyVlWFRVoYll3JHw5maAiAoawJL1qzs8owCRFg7UwQYHKuvA6APmyGAR8X+5eSiA+FGlKvISqHXVEyywqAtG9PLQDYOESOUrdi5bKecB7mT9W/92UnbzKds/CivQ1ggaPNaTYebto+Dm7It2LtszSNuSJ/mqPEUqaYzG67KzmDhcq440LVTrjHdCbAH3C3KLoZujDGxdgHfzSH/3ziKTf8HIG18azVlTW7R07J2d0c5mZEt3MkFd2eAu7W3sVJe7p0CX/6/fltthFVFKkqjtj7zaoWWRHyaxBAL0BcngJzxrUs1ANWoinudxTTyo7X3vEkF7WDJOkHMB/f2PmpRAYPiGEZh1PFXRQ6uOCwmCQHcLjO1QlaXT8roV1cmYLFRH/qIMoDdb6ZdyDqrc40JgDyupesAej3axsPANaHW0d+K3v6VKQO4dWcnBYyNfnCmBlndj15UYmvdLQVZXYXCAbDvSi53l78mgAvp6tvmI7ycB8vFRn4rC7Z0d8UzgaupqRsZLwDkzv5TIUDPRtu4pZzR/x9ttS/uo2IB5q++zRLVtCeAC/F3TemP0Fvzeym4EC8U3sW+Oa/B+37nEQDoFmu8ZrzdTlxV63fOfcsBAMDIT4LbAYC5ZvPd/8f+n1vebbmzALigAAAQwHHeYgTAdW6gdaFbBSKcajPz+Ekgi2VtdCuFUcG/XvOq0KvaX/LtBzg0FzbxQEo8IZXZxItGvw3ZH5eQQ0tmykBTWTCTZmJNLIkKSSU0YkCCXm33OCStrZMrQacrTnHJSMkVWjMprt2WUOdV1jUFdIKyYhLzf/dFofSrNUJPXZ0h23k0yS4yQ7itdzJmqjhwsrzqj+7MMqlnKY2qS+yyhGbcFLoA6XqJo95gFYoY6USEG+HNc6lmNUzcTbHsuFSqhFJgWYx5103ZxjzZymZTZ8QGj8RAxo2ShcMjb9pOU86KrQLkSLnRmOFGDjONFpx1CXp+s6dvOVx4h3IVL7nbxFUagep8f8S7NVocxKxEfnWDR6/hXkQ87T9Z9YNLZnCf9Dlmsfx8zbHCJMebeqYquSWXCc/YpjXvmnpUiazbSnKTQegpCAFh2s9hSjah52vufYbz9A+ryVFgrtCbZYzt0mfeGYLrgbJalzUNMqomgVWMVFks67y0EFM46+Y3I3DNNWVxTUwuiOvSaiYFqW2Ab7tDuU1RShGhKY6YnJTioazeKCeihEYwu6wmG9tUK49HpautZqJ1h+zsKPQcWAqIKVEnqsSSmJtqnhheK9M0WhgtmepO47uVyu7QWpqtDIeIjQmvctt4GOq3VGnMpi5Rs9OaD+OCoIJ9ijAlxEZ3q8K2cSvUZp3SmC0KHW3jbeojAD4qtIcFXFQPgB+g0B3g59viFAADqeUBeIDyWIQYj2NR/GIqMalKLI7FOYHJ8JDbG+VnZwxJhEixogQLFIRKghIFiqMigSxCBQ3lf2Jj4XzJMV2HhIZtGOJsxPx3x1+U6Iz5JTk2Ivg0hJqUYJ7IBqMJo7HA0wrlnUoclChnBYvwhxO5lcrUnXqV0epC08uiW50qEoH8CHRHjrfInPkG3P3JiRAlkIUK83VE+Guys6hlxhiJAQu2q5B9cEhhYPBIf8/JTwAA",
- "headers": [
- [
- "content-type",
- "font/woff2"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/font-roboto/d-6IYplOFocCacKzxwXSOJBw1xU1rKptJj_0jans920.woff2": {
- "data": "d09GMgABAAAAACoMAA4AAAAAUsQAACm2AAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGmQbmXocg0oGYACGTBEMCu5A1nULg14AATYCJAOHNgQgBYJ+ByAbIkSzoqzwsjiKkj2aj6JicZf9lwnmGDrzUL5ooaWgICnvqxcvLU1UUm052dq0PPEbkDL7t7A4c3dKponrEu8IjX2Sy0PoX9DLJNk9AHsAO6uC0MkqVZH48wM/t95fEVEDtBGpESMixmDAqNgYMLpGpmSIhFWEFSiIoIiFRIli3p2nHuksZyTDeXbXshPuAKlMlW53Zbg7HZue7/8N06wSlnxFE+rSAhYVkmR44D5FCo4yXQlcOX/hZsHaQuZYMcQ8fkufGldr+uACwqKNzkSGPbR7G1BVUZ3KOl0lGRYOQuDT2zTbfVpvBF5fojuuchvk6YE73cxV6dJS//W/1qu/X2vQGiTZDshHKx3JCpgmIwjIGl8FXKUCLIGkY12AuaMOqUzRXNWnLQmqS1HWqdIFnu/vG79/2raDcUAPMPAMtn38TkB/ouZjIAEmGGgThZmsWZkYwdIwtsYh6+N7ZqYra0NPaN1poDFKzhjB6Ep9/G4ZTnWidqQaNBB6+Y1RoPACsDkUTvsZQJjzgUiWDJEtGyJXLgQLC6JIEUSJMohOPVAu+QiBQAHTADNAgAKRDAGmosIAZt317VxBcvfkGAZI7h0THA6SB/jHRYIkDOBDaNj+e8ZEAjtwbBhGLXC2MFFLe6nWKwp1sS6WQ4VY39XdhkP/X4wChWLH4FC8KPFQDqMIiLjGjWJFabOIvvgn/jQ7N9ClKlWDRqlUq8XUxVp68cWGQ7/D+N36//YNN54bY0H9DUgUJtSPLQYOF25C9jvokMOOOE6FOg0EmrQR6dJnwJA1G3YcOXNB4obCkxdvvmrUqtfgksuuuOqa68ZNmDTlhpvue+ChRx6bteiVJa8t+2DFqjXrdnyE0M5bMIiE6TpAn6hZohBCyQ4q+IddgvVd259GlFOFNmHm+YZlbrMiWMMWJJCru+Uaj9zimRu8ySnLbXUJGnkTtMtp5Aqu4hquY1x71htzeI55LOCF9rJti3iFJbzGB6xgFWtY1zbasoktbGs7bfiYRnjlVP+hPoJCwSt7WIClnW8Rc4Vu7tDP12bBMR5M8483PCX8SrDD5C1uOcErZ0QkQ1pGyk5TrDylKDth8BBmTIBbLvMnBPCBG9uCt+WBq3CUc5cOYxpP8BQzexSGw49L58kUZJkbrABr2IJMeXnZ7NTgV8uoR4P2sg2LeIUlvK6OqM1GXCxzhxXBGrYgowwvsYhXWMLrdWPYEEahxosAu8OGlMtrXNyHhK8kWMUa1veMxZ95BFGHRjTRCLGDHexgBzsEexZimY2sYA1bh5RM5GSge4rzwqVs5y8Zi3iFJbzWPsS0glWsYV0g5P5oijmKkp9O3nw7kCfXGOc3/jcHxSZ3fc4WRHYgzYszl8Xt4s0nAnMbv+OWL1BmKuw9jcgRaflYdnZg5ZSinHQinwkpJtdyISq/Exs8UN0JBvTnxrwgTdysfiY754dWTK8Zted21jPU8/6ErTbDLJtDyepp3/I79jzdpwqjW9NkvFDxcrFn8ct7uyI/Nw20ef7NquSYG/mY2X3qX1lrwCxM5fcKo/9ELfnuZQg72j1T/muh/JezBlNxFtf0x58eYNG3oste6z3I1ae4pvIFyU8FzkQfejHes5fRm2qnDgIE807LfcaTOpsEUuLOw/wOZH8rylWi04VRGvkSdfjzXLcqGTZ0Ft8w4B8+d+iZ6+vzC6o0sWYSH/HEcH5jFetUsY0j935Npssg79F/4F6kHQmLa1Ms9Va9TLCHGVYlSVrgX3FCh77jG/+4Jd/AaEir86/WBqxJDUpC15D5baQ+bKJ1eAepuz3VUvN2vN56JxY2PSZ7AvMVJjZbZ/Wx571F+emsX0bLt4pUr261+xXWRibmZHFmW+n8uPjvZqdsHgYZaJrhAxFfgsQCHC4IflcVRfA32n6HYSjRwEGbwf3enCUJ1lCaXS7DmStZbirwzBVR+dinOD+oRqNDmr4ru+S145atI/8AunlBIbSLGGJIJak5i3JACQcVcEjEYbGU5XRcLiqKUhehoTBteejIiagkXcXpyU9fbgbyMRfHQjaWR5G4utgTpnSBQYJorrJxU4inHKgK8paDj7yKT2w/DkNMHU5SPxJDTCOU0qSUSznisnEoE/8JmHQT1n2PIabN4DRLObdnXsB5mYtY9Bq75SrGB+vQ4jU5EEAghAngKCphl/AJZwLlKIuirBh1UQiiaB15BevihAMRhOCDC/6lVKU1hC2fEJFAgwk0MkS4y81DLM9ndsFgDx65EKVUlLIqoko1UQkRQBgBhEPYRZxEAe6EEg8UHHAltutriGyg55hs2Ia9sP/pma3UcvNIgV4p7wPbWtuZ49ms4+I6jtZ3MR7rbeZo5+bGbm7taB/butgGVl5gXjGwzjQ6od7j9jgoKgIO/FOeB1A6gBbqD5oWvarVQfERMeBEXNJTXfov3YSsODZL10PI5bawcHipoWJqco0AdmG0Fahzlbqh2bDXCVXlnj+0tNzjd9JFoCEQNgJSIKK4OEEIjqMBwZ4QEBpHObSmwc1GiBZw3z09nPr16TVg0ElDThk+b/Qg+WyPShErzpjTzjjrnPNQEMJkgNr64xos6Fd0dVDm386rLwuJ+xGaHfI4sBiwjhfOBls4WgIeLDgTDv4A7DVuCsBDrgW0NfsYPDw0GIp54gptJc57XPaBKXbA6vAwxIFpZegI/5mdcMcTaz75i6gWUtyJxViaCOMl8bJ4BfwBPBFvhj8Cf9eCM/39C7yAR2e1EZPuemrdZ1JcdhbCi+OlD61TG8kfuUI0b+DMKZD/KL48Ms+I/9/7//zvc+8ypk6ZOG5Aj0fefn1zjikFLImVsdORlv+39+LZLrn3l/f7z5Fr2hNPzZiVJ98zc56bt+AFloK/wve6UJENm7Zs21HsI25A+fEeyGIo1rRLVExwDJpyHe7F9bgLuyt34z7cgwdxMB7C43hAeQLH40m8iAeVl3A/XsYbeApv4i2cgLfxPl7AB/gQJ+EjfI5XlS9wCr7Ej3hb+Qmn4mf8gU/wJ/7Cafgb/+MrZcAZSkrfq2UFjzO9ZWtpG4+z1HjC4xw13vE4V433PM7zTmY+8CwAzgeTOQ48F4ALwWQeaT6PS9TJgh6Xq5NFPa7wTtaQ1vS4Up2s63G1OjnC4xp1cpfHteqCM9mu+6jLZofKv/gMfuhW3pPiAU17HJjlQVDfAHEIQIeI+YlHYKEhpagtUCaan7BRoLDQThEoqCOLAJWzHoFQz5cnRaEgTFRYKkwRY+WMAUjjWkaXIJEwAoNOLUHcfDGMY644+bMo8P1hJLwSUN+asKZZ45uRjo1YMxyWKxyRtHwY9rOgmds0CKCF/jl3i3nj6npwDKJXOkiXSZbceUDhogx++TB31vdN6ZQnaxvAQgPbYXpfy/I6Gby5BrrAfAo57tf9GfB1tVXWWnuVU4GpY37ByDQpciH9rs9Fkp9P443DfcLcV8x96yyufmrJu5efcMIUsxvuc0q7GNZjpZHyRPs5yF+Nft3+yuA/6LcH2dFJjHAgZXAZJRIrN6goNldD9qlBbULVGSsaoh5oEK2LNnEsNozxNUMUkOcgY6GEwOWgXGdoIAytWzkWqXKsImVogtwlQ6QN8eIy43KaUgRlyCHLph1r2AI9X9Vp3ZzH4o1zI21kn+12int3NZc1cRD+pVws+BcrisPZ0GTWgzeWRs/8GTt0dqHtPLTxTW/D3C0Nb4WbLdHYNhtN3WpYVp50ki+pRNOGEQ3TGe1XMQgbZqEtbIgFv2GLob7lvxkOXHOrQVt7Ed5GWJeVDTwqrq9hZ66xSVL3jemdwJRJq1wbKtXMS5RsB3cd4wyxAPKkX7WsRqr4UBTVodqIhaMvIjaz6kPjla6hfx8DZaTPbfjoYxyuhqsJPQaOci4eSa7i9dxYeCq5d1aMAgpd2LR+JNLCmbR5fPmVlgbeuLah8bWrk7zjSbyg6uCwN0H2uIb1gvYbHvHHMPI78fT26Z1plmlY57237cR6slAinFkaTXsr8XAewr3w+momYZWzR5msF3pxUIdK5nei6fZM+2y4iu7NclQfbX/3oD9FtSFZjeVptS5YHdzJpO576objZkvUXNJktpdTQegVeg9Gzh5ZHQS/LZxulgBukUUnpQKlD+SqF0CN6zCTvb0ge2b2lOwzluW4B5tBiBIDlsULM1QhKCo1EytKj8N4somh9ur6hh11ciy3r59QPI4gw49GNFn7I8lyUorpYmXFzjZFpH0JWquDrEFBcpBGa8utTlysjL+82uit732iQ1pvhaCa2QM5MSLq0N1X7EzVecMmY510zPNyN+SKrEi8nktuL5OjLasS13VMy/usRnKieE17mxmz4I7q9uTejhz0H6VBrCCLktoO4Do0xSxgGguASIz1eDdRMHGDBqJH4xrWmfZU8FnFQKiplhMeNcfLAY7wkEeRkvNbHPtl1GhoqSMIr8zRc08vrfOrukNlnsFPH3XFAWJRHPJeKKpxULH9tiq5HwhfRkoogqAEVPNr/U1Gk4S0wo9pUSYUzhMD/Z2cKSKASmK6Q7XiprYN2yaK7MTN1lDiefZgXJDF/FFdp5SsqD0xumuYK3gTM/jD5bS40vIY0TEdlLp2etK4TCObfadRkLW26S3ICt+EabwQUb0NORjj9tOjnxs9HEXZAQfv8IxenpliLP26MSoQ+VEge76lti+2vQJFXjSImMBJx3JeyRNABXcr0jrwoOmkSCj8ow+n2qIquDBOM1bkfmRHQZxO66uEndYiMWz7Wg36SDwGTvrpVJ8M7WmLNRxIrMPxKynGGUzRXKIms/m16TyC3OwSC+PaSZzFqBVyXQfkAhKw2ODi0Q8bbOFZraQiMZYMOa193XxYXDO9SYRoLxcBkkPjzs36WsU8toTC1kPSKODcxrQN0RLjyLRGYOq4RmBPnDyqCNoi6dBIdQVIUEBK9wQVShR91SyrUlkWFbtzj5w13eK2As0rWE45U5zMAT982YojPiwMPrBKstKUGlMj0jMV1NsIworbxO3YX6FkvXjDXT7YnZ3giY5LPcMPCo4JoQPHhjEHWyI9+H5kBI7Jr2I9+t5IFpk+4lFZEfygX9jxrUCfWGTElirbElcxYKGs4GLzWiohxwyNi6K+CBbpYRU7/8WdHX+A4hbFFXkIf6XuFwodK7Yp3qX/QYZY7RAXjpn9tdnMGVqD4r83BTShxhFk7Dv29m2sUZsWbUA4pKLGbZGPPGjI6EQSrONDR103OGFBrMZiGP51aOrYVpprLdmIMnevqUA2g4lab3f2wt2O2dnVeztEQE1HIkZidCiJdDJyMNBV7+HYdDObwZ7Io2AGeZJ3vZI0s6ySFSg6wXlk+wuh4bCgL9DfL3KcmAxvo1uxtLlzSB2goNAWmSKvqtfOGRGdWHg5LkLOzkKGmFn7ZBPmULKaYlwt8nV4/YmGVWnhwAKUXjXS6hV2Zg4G3yG1GZvVT1HEQKvDK9Aw2sW1jP4ifj2x2E0Xs0YplhtsVEaRClGNl8uQ0ajYNQNZTdgRXNBE6H5tp+sv+fGrxNvsO8tz2cRj/q1d2Wwww4mV7VyCv4jm9lg6286I6NMyFpQcNGkvq4V2YYfaLZ7JhmUUSmamR0s+GYRiflL54FlmOlIgQaViIWKS5x0zaZlBvRgnzfLxqi/GMpaVV4zXW5ZliWVFPcc4jOTBaAJPjASuIvbLZ1nM4fZNaLjU2PHUB7gvgIBQ2o7YEXhLu61A6t80krAiF4C/rBsYkkz3cjJLN5ImOOVew3WXBhKDoQQaQKkbtzRiE4uO+8PY360dkcjskaGdYYSpzm3aQL6oE0RWUkwm4xF5qQuD65N63/eKXzz4u6tQLNff6J3+Pzu8epPi2nvxmg/2jtrxzyjFPQ2OngprCtnURD3WVrXyKG7A35twsKlr/wOzogN5v/vQdGLK8sTFvtKHU4iq1MYIm1X7BZJuSBdjr0b+u8bfnfoTinmaT5k/1TdA1T/TxdPvpXOrEzPMoCxgcGHhjMB8x8sx8bvfbsonBSSQXDyoLnbuXru+J1xpdK1Cr5PPnl0WvNt+55HIux+P5ROZGXRKMBWw3xpZw31lFcM9ZVYFw91l5SM9pRNYPTMrprG1gY2esTVRy9TKWC73eMFoT2n5SFeFFWuop6JyuLdoAq1laa+ZUmCnZ2rFNLUyRL6V2irFxZTagkVBMHOoPszIzbqRdHJ+7kL306mqkdG8KKf/FImxpT+kc0Zf/m9lQ+6gzbxAL29iwqg6srYOFNtQ90gGIhRv6x5tp9arZBlkbU00sHEEAUKEdM3Fg3OQ6ria3PrRoFhfq7kqvPumstzxzts1UVqNBXpbGqk16Ffgp72c3fnVsFhXq7GM3n0dJU842nW3Krre5kz8TMhrRi2BCOmGDoV4TjNNiHpLKFA5hXjBkDLD0cY8r3hWoi0cjgYep2FpjUKNdCy9QAguM+odFI1MkpGkd9/gLkRGvIeO/9Q31SG9zJxKtrCkks3NvFytLL1c4X7agjzr2AKYxngq/2u4t/tLB7WPW/V/3aVf2qh9eInzAT20EL8WVF/AGb9T4XTvXuQkyMt7UujbngtyYL12Z/67H43aaunvH+kVwGRFKuRnvFpPq3n/z8JtRtTbglobagyI11CaImkRXpQwfyopytNaPibl3FJw/jp26UZQcn+AUsrRpNGkG5Kbm4vCq9flXVJCPUPjGJ6Ln0+Abte+3s1eXXldMvf5/V8n9h1QLzVB4aHsIemDyp6ponaIZtzTbWSjLOHN65SGvPf0nCl0qiy7JyOIEkArzU5LzmWGfr8MWoSJXembqN3bYqOx8afH3/K9KU9ZfZdZviZpyBX28Qzd4c4SbL6wiLYaolRFd4V6x1THJ8ZWgZkIryKBV1XR7M7cFgaM847Rad1UFZpa6pnkG2zv7nC8n0pOPRumSlUJ66Zf+bn0fO6fRX51c9+IaG9qBNPPOzzaz4ceIfOK7BHi4uwRSHH3oPVQaKASY8GMbJhaZ39fkbb7Nq+08m1FKg8MhzNo7bY8FrD3ecTfOW4RZFmdWBPV6eMe1ZaUyGgECk3nnjhhJmJHDywORgFbGTsZrRXgGsPsgahmdMQ2vQyRYuA5Xmrae65DN0h7sMWG4ok4KiDjXxZm5zYfXSXb1vt4OdnZWnH660mrmXq6lXu6uXO4Wv4GQYSLOOffo9JNtzRrObPAks7q9u9C9wV6cuBuUVxFkPGWmjGHgyZJj5o6jx3mpxITCFPHbg6HcW7w+evm6JLO7zOW3X/i7rQKjT127kIblxyX0Ifzhbs/f/Xmz1YYZsdy5poW2qm6k6WdDr9gHI7NuAm62Uq8gUcN5VfHRBVExgzlZRkX8JAD2LE/HAIPboVHdPnvj5LKGkyd5Vr4iXAkFyH0hCCPe9MowWdvltGnA2Pc0mbBsWqVf0ubB8SNkqw9ZmsMBU9e+F+dR+yrEmcpK6O4vnYeeR+5U/6yqaQwgyOP81M9Oal8atDgoenDPt3jw+PAEXf9UdXY5VXkuf2biyunwWA50YjVs/cUsGPTX7u8jC5nkIxISmbyua+FSS+jE/6Sk99B+rnr0j1NOsizwMVqA+GBK2jFH5Lb+4TSCmOTTrSvwrL36vDmwKCl5S+B1/rgogJKTGsme7aSg7WDEkztY6D0fHgEn0tS5t7Glq0jWwvK4R7B/m7B8RFgbdnc3/H4HtTmnot5E41hyZseDobhz+l7g0xV8L1jYkF4MTN8cbmFY+UyI+K1+tPieXoyw+XjoeCCB6V9uePj7A9uX83k5FFwWb640GAqOXrxvNRwswnMWC00WUiOMHoyPYz547Da/bGxoXsLli3fdn9vaujcgWUYBoR16412zz+J+Utl8/t+oHFfuBPTosLC03MjESFwuXHxUa5SnOfe9fEBwj9WOlyTLcKfRFo/YjIosdXZuqw7OUSiC68JHs3+JTo1Jjg0Lj55D7ScM8iJnlpBnio/8z8k5F36J7S55SuT9ThXKSg9MiYymWpnWe5bfPiv3eaHk9dl5r8MCKVUPi87tocPT3QDu57r49eVrl/62gX22LGJT0dE0H+rCrX9QGmqojAn+Tea4z40hwn3WDrInR/TkasbswdHpIfbjPuoMGFMmffZdM+Vtzt5lNuVkw/D+QcOnb3C/92jf+bMa2+x3y7sPZO9hgcczMUrV1jJfOjgV+WvnklrmPj8Zo88dgzD8+Sr2SlQyJ8oB5x6+dsxYNsbA+hjBw/gjh0CeKPtovVtRYBof2lM1/C9tSPzs7LQKujAcoX8MwSKrg8+ChF0YVmzKCxuoP3pxdJTfy5+hnwDWzsPkrWLub68T2z7M8+8e1v3LjyHE4cdBATvGYVrt19hvOSpA01bczBdFsK8Vrg7FsbijsEADuQPBsZ133mnwI7H9ITWhxarM4c0oktKjxYJG4PKnFOgO2LFBxHxFx4FpW1wHcAI/cdxeOPhtzVkgg8hBYa5BIdU98r2B1eB8b7fy0dvt4XEH1IAHGB5YsJZJyfWlPA/GmmdwSxN5hCBmT8DfkK7RxS/Snenw1px7Zs/YkjCaR5aaSaj3zuprM3I63UIZ26SGz2WN7xaDPENDIPxkM65TuqFp/eu6bkJod5qa3SfcF+YWwgBs33/7hy/fyYgmSsYJ1qeNbMZ0Zr43kfHJnM0PKkpNjMlmhjI7L75WeV/PHtNfF9onnbAXZ2A7LCEQRCvuRVTNOKHaTwvP+ztSPHO1PZH5AEH8tChQFRQEzN2I9nauJOMTSikagoJJIWJ8Wev3zlra8q/qn0wtyRR9GFnvdtX+ufp0FCbb2+zIGlZCpt5sW4MJNhBhwLgQAHEVojsSTGlt2bse6J7no0NPZo+q3CGaunqlaOaCmvyp32sSR6pmsG/5YkgVktkT4utvHmq/z5y76r8Oaqji3eKXugveSIYH+hM/bVR1PRKmItvFbH+V0RpTvQoCs/WFNvFoMV3nG6I7w2nx/aA6azQf8tKUz1B0X/kAbvIzUELSx+89/ogBo9toHeHFKqFXtWgFz4B4wN/lw/eGQnJE2T+Aeyiwu9AZtfU6lH8v82MzsB8TdoEITgvKKITlL4e7T/WoxZ5S54owJblVtuk0gKXjhDC9GLFsp1+Vu5OTk3/mGqWN3B0Ils7GqureBIXjlhLrpCe1P6+cL9w1i9xIEAQbUdz9iC5GoB0nRnn5bnL0nrPjFUsXrlKeKpg1Szb5to44UcEPfv6yIW7yORt+auDTTWawX8UiPyA9rv3Qll0jiism1EG46misjExATPil0cDhu8td1KsdPT26Axw/jhvQlAXMDqoOUmaIGnJL7SagCagGu92aEppLCf5PXtraCT4aszFSZUmTxE7p68FVzYENnPG/m/f3QocAuvQ0CDG3Wdnnoyg78xdPvvhrJpWh62UfTGSMrt8xvOM14c5zGa9OnjxjAJufBTkbzcQ0NtzyxfcL7ivz6A3GrS1Os6onl2GiwvoOyNPzsy8ZPP2DQA7ksSVy+s1NhnavW0WRMtAh3nkyrn39Q6Zul1Npro2NDsYzNhDCX1WFzq/39SLXOpFZpFsxNnb3n78SOXkbJP01r3NKzLP5JZFF2fkr8m9u/e+S/rSa6SLHyEHhjiHBNdCu/xASCWoG2KLU/WtyvYU96iWAp2Y5q6dJtzygx+bT+b23k3Kkd08nE3c/P3Ylwk7YMof3pbx4GFrelZuaQWrMLD59iNGR0X1XqGssilm6kZTXEWNqVBTT297MOXfXFyKCtoxqQnhD8bjoiKVzP0SEsPvXY+NYoLg5w0UAtPequsY318cxcfiR/CiSqJqI2qxaqPfTO7rQiaPFEbqHuYHBqyn3l/opLCCr4wK3vmCyD5/iAePTJ9MZqyNoXGWMyPoUoRnHf1cJ7Ug5PKQ+Mynn3zv78u7p9DDIxPtzawjraP9b0R4N87E2BwONHexST342sRZ2dvA0yH+IIgRyAR7K30DW+swW5s0O5sZdU0nK6KugzVB4/TfCmA+69o40ml0be5c9Mj4XFv3qZ66Fj8vFwo1iAXM1PhgFtXDwymgN6+vTlrgZHc7f3eznGuTHH+fkeBgg5wzf/+DKx42d7Js7lzxePDouqfV7Ykpq7tXPcBrsinMzjktISeFFtmfNByinhlnbKWmcoonbCSrsKC5Il/PX8LJN/sQad9AId0WyLqqFNATSLiHSR0yBfILgat35n+Yh/9bLno6N7hINAwXZjCZ+tMqkT0403r+5qkOO2MT+9b8QhsfQw0LCyIVyoDQy3am/wywrYzFdHZGRrR1rLW1RDC6W/jYCWYWBA0zW7qlbZiVJRwhjVjtWTF+Mxz3HN1/C97G+G37wbkmRrEsMFVIYq6+asPHp+NOthbUdmQlWljGhrvVxPiCgHC0SyJFsUj1yIjM45CBlNyqkwnhiSzVukMVtAsZteVDeTHTCqYqGnpmitRkoIJgH+gKE7ZB8hYxKsMpIbBOK+yXPJEHa0qhFIZYKl2SB+wiFLM7rbH/nn/O8WftCGDHoOSSuRe5nEou9na1sPJ0AwpusE6yOvJCZh+uj+l8xETWBiNbDnxNj/ZdO9QWnyQEbEH+HeM3NCem+qzar95obbt+s3sEE0CNcHLwDAc/J39qhKMDlRECJ3Ly9bvbarQtpa2VWpvsPT0QJ3lkYm9+9vn2g2vtjY1+VOkD/ghFUdUVn4y4SsjmsRvvsyOp7h/7Z8eNN+DHzg5fEd0e8dAS0wGjODVtt9Bg/3FNFc0xdDirCuE4AUguzal19uSYu1ZeK9+7dSNMJ/W5pxdGi52tU6/mL5+5TSJm6Z5SYY5/s9ILbwT9ty4J07A/7OK6ubJ3Q9cOLINk8BjXWifsRmY+Yj0Q/voJ80VOHrBj+K/n3sZnx9/KSIxCYEDefunnx+WJtTtDDPqw/X49B3f7+vza06u3Fpxb5RIJK/7qyY4kK0NlMzdn47rEer+Ic44WFBezdswc2L8T/llcbWj2yD79yvPTna0/h77AgI6dE9nexcdCAy9Yh7n29FlsRHrUXWRuD7fR2sIZW5wcb58j56Zkd81Ka95QgzmnGqsUcL3HByJJ+tpOJqpqPZ6MGG5GhrSPWzAQRCT+YKHA5lSewMf6msrVjKx3hevfOacLw21VGuKY48n20Q1+sZY1Bzzffjx+Ovckwy56aNHUpSY6pjabmVgeEJp8rg3M1HQxa5huOTNPkpUl1cXc1MPFxtadtHVq0OOrEuwqbV7eGTJ7t9biXxGlLV8nCcuazpBn01V4nZxD9mgh/aP02J7xhph9zn/t5SFafAeYfiHM/oHM3wrA1qGguPTtuvN2Pxse199jHiF4ghDG+tPUL0+Uh3gjSOgTSh4Rqm7kRA3oD9fzC9eNpfYJxX3t9DLcNmR1W/vJ+IRy70TxUOq7L8EpwljfVXA50Jn833px03pJbX79PDL/HdlpK+dj5qSFkvPxzkoOV6x0XholbpbUFtXOCh9B49mamV0MenTHmROx3XRadDdxrMfeP5qPHiXpT/UHrbgN7rUTlScql/kPCg0AW/wxt+wEb2pOHIWcGevrnx4f46LUFtSmpDwSMAKawd+icxt9D3SEai1JKSLK/RxROc2+sg6JOq8kFPHKILCmUOBALkCV9K/W+4TNAbfi3rkiC1UxuNbsGTgD91Vks/bpqJrzu9ALlIDH8NSs3E7OR7W9WPgO+Hkv/rXiqeQaVNXCk/EA8Q16CazfYbnpYYysVCToaGhOGp2WlxoO9lyfyq+I5Qv16SvAf7Z5F756nf+pAk4y/ld5ObWWMY6Y6uqaZpqrrOJeqnQem5ok26/BxsG0wcYh/l96ojhajqziF285LylJvH2jY5ojGCq4+u74wvkE8elRQx7+WHpfMEk8vOsvHc5v8OCs0vO55yEFCkQF0DDHkzlsbvVbp42mwosfvCtydf3BXIOLHGC/KzQwI0Hc6lk33AzyayooxOkp8Cz+nWHOML714Fmlx2QeFk/msJVKmZYGzgfYZv6gtpXuNKGpo6+mrr0XqR5u7h6squ4eOvGQvZ4eiGbddtU0UgtGFQH/czz+71GoOaWf0v643ZOLFbQ7HTndNfcc3NIIDT+7nIRZW+Z5RbkpqYONJdln85CgabR5cFi0+il9tSP3QbF7/0B1FpnXw8woPCGvPDnuVEvhiaEuVK3+069bG82XHVUOpMYdM9ZXDYTTnTadL2wjB/oyod0wJlIrSzeL0ZVUVdmXxMjOITJ1mGGtiZxt8ZevOtNDnQ+VqhwvFQy3didb27uTYUnZRN0ptSQnN+l0X25lTx806r5YerEp0E33liEYkVoMsfbxNCWiuVY4dOScu3gu8ef6WkyzX1VVnbm8tWj21b827xXAoiD4lz9i7Pyt6nDQYjeJA37Ral/z+2QzEgCOrwXrb0HKMxeDvr9vUI3stCJywO4bN4ga0VrhO7BrfX8fo9rG96L565FJbRBtB7ClAVBGNYMFdGyA3WMjyFI5EBJi1Iqvhj1Zg/iC46vlHVeL0BKCbBBiF/IOQrbRY1ttECCa0Y9GZVA5qQwp6XBKGXaNTAkcCHQtaj/PArPCh2g6gfHlVmC567tXujMaK9K9qNYqim+pkw9qyeVW/pUPLzAzPzoIjC8lgeXyxtG1y8cCzZIVGI8YWJ4a4+jpaKmFKG9Y6rHJMoq6PKuoyw8VdXlOUZfXLJ3wrX9tCKUjCCzXP47uhqVPkksscwZ/DlDMm7VMeISS5dNJlWvkePomQAWebJZvA0vZGNbSyD4SEEptFVmItWQJ66Ova5VI2xPXng2PYC1uWWopVIYg9J2IS1iurSxSLHKzQpKd6kjYSEXC1iqSaw/Lw1duUDxkuzqPkvWOPvouljdBFpe94/SldWOqtTZ8YPcFIf8fW1L7P+Do/F5uNSqdoQY5O7809tJrR21BllZP12bBoB/UT3IF/fE+xgeMpsFe1RiuracaiQjXPktPJbOJVyxOgVXdi+URwMn5vceXwwjRHJN9jGWUxZl+CSEaz/5h5vw0YOHc7Nep+3CmkeKYRmmM8JclsvyKzljBBvoOY81EUVc4vzwV3AbV9qvfkgPa1mOdJJPn7xVQHmapzhPXtuYocCeGE7ePeeyHpi84VueWO095rAlFfQdOiGu9pyiOYEhDgfYjzNYAhwM0YP9Yc6jmwWRQrT+aAytaA9kRYLN9LgdAub3vYYE4m7zZisvRXP3SfhsNtOmxf5jEroHpCEAtg39O2HTw4SAIDT1scgjDmwI7BwFioZlex7GL+PR+Z5eYAgCPfYFlAXh9XN74T+X/51MWTBELwQEFUMD4gIEbYMozKs9AWAXEbF/fb6kgbWUYVollpEUVo3aLajeg9g2+3YhlsWUYT/wPZdah2kGq+dAp3yhWSZFBkhG/82ss92X0wwJG0AINQdCH71PtFibSQ4JOE6TZahU2BUn1l2Pjw2x7ALYuJafrcevqcloW8YDz1Fg+vb9KkNW1JIe6cCKRvWMU72POihWHt6arb0bbZt6+xryXzMR1XWyjv6DYRYi2L1DtJevQkVT9QKyBp2ZSqtWQ6KXRbJi1bFFNiUnLYdJIrOINmVbFvKUICzkRIZydZyEq5GSMPopqqWiNxcRHym+Nbe4rQzvO4aTXbFzA09+TboJEGgbQ84FtoodK4GD45VHoKuhhIqs1CWxTAnsx52aDMzCQ1dmAWq/xGVlwq2WK6l+wbzQZbs2GgoEqJaPZ8YhftPSXXCX6BbePSuo226ApjX0C4peCOiCh/gVyHxc8EuM6SuRTfzEf50M1I8Y9l3d7I79zQ8Foiklr4toqGbY8Jq1YdKhijSf4jbWQ6k+pcVJifSm+80LjSEpEeSuszCOW/5lUQ8xqzqrqMIl3Cvq2/MjACDqnWkU2fiG0Bh4tRk17Q7itkxlHJFPiP1oogCVUQIA5LKAOS800frEEAeawsNSLpqmGqSaT3Tl3tFR0SbXFdGUYimhesYS9Odo0rKnCmMZMHNUT1UxxE1HSTx4mh2oOeLC82drUrJ3CmDZF2GuFATQ0BPhBBVEOsBCA6UBArQgHAaYQAg1pHAB2AsddEdx8dkVhR98VTVTMoTG7Yh1QyHE+ZeSh8nJ1i6koTMli0IQKEwdPjQpVp+FZiiLwMwTv2VqkQMrc+AZGs4uHiHXiwWI1HiPBxoMo3+JRAhhxMFmZIShrxveFm088Fg0isn0oL1CnRTeYkVp+7mO07cw4TETHnZxYTZk/Jn+BwhKuzE6MUMdtNk2gYJFB3pNYx9mxZsqcAxJzx1ptUvlZcFlJF2QG",
- "headers": [
- [
- "content-type",
- "font/woff2"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/font-roboto/oMMgfZMQthOryQo9n22dcuvvDin1pK8aKteLpeZ5c0A.woff2": {
- "data": "d09GMgABAAAAACn8AA4AAAAAUjgAACmjAAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGmQbmUAcg0oGYACGTBEMCu1810YLg14AATYCJAOHNgQgBYJ0ByAbL0RFB2LYOGCA7DduwB2DjQOQz3hJ9n+ZwI0hWB/YxYSYMBRSFENBsWqrAkWbJBHpUKamYBECLd7YUy2OVYvlKX1dMf05+T/7LtU4wMKUW3v6cz1MLF0FGyHJLEG01r/VMHufgpZJIoGKBHQMKsYkFpgU4tsDmtv9xsaIGoiNiIJRtJKSElLSIdGjQuiRIypl0JtBlKISJSqZZnH/Oq0ZWaYZyYoPCFpukb7+N+xuwk6iBRZMI8WdlLQH1F3R7l157zoCyXjA9AD36nWBrP07PZhwgBLSeMnLEQ4VqJsqlv8siGuabsED3LeKFnxrugO3hMah9NJJ/ipRkvNo0bWSH6xvN8TX2qedvrqte1s1/yDEW6dCUB4tkIxQEeoDTSYMiiaAuBEGJLK/dSEgoaIi0Ua4CGXj/7vX2aa3YewLW7L1Fw6EC+fgxB/7NWWpMKZaUyFMhaxEyArLmA7J/62Zdje5MjlgYyvcOTf7ZycwswkX9oD2CklKoSNIzN4VWFXVET5/gKgKaO9USZgKCaxcreurQxDS1KS6SqUxAJqz+B+OtbQOoul9mcsgjITAKKN32318dn4Bhdn5t38EFHq8pCEUmUMECIAIFw4RKRIiRgxEnDiIBEkQpSqgdDmAQKCAVcCaECAgAiDACvyk0ex3gJounDg3gOACJy4k2DnDicusvN3gBBrAILTCpecT3AAH9C0NYpDo+7rNUJuyf/BUQ/cM42KIV0v11FyNhkyiUDj0XDKjjuX1lEnr9K7FjMnEPpZVifqZhCWKr4SbqzTQwLYaKjSBrueqpWpPjRbN9WixjymuFFH/CwqFBhYDRux4XXDRJZfdwE+IMBGibhEnQYq021SoUqPpHm069BkyZsKMhXQZsmTrQkH1yGNPPNWtR68+/Z4b8cJLr0x66515C1atWbdh05Z9BxC3mkNDHAcJeFI4TeKEYI8bP9Y44ePEm77r41+ewEGxRUrtUWZUuIsOetH6bTJql3HbzKjlpPZkximHvICSPiqPeMwTngZTLZpmhlleMxe8ac9b3jHPAmuss8EmW8F2u3bYZS/Yb9vBNIRJvask5+7FELPwimHcaoZ46yTaJ9WCSTY0DsjmwGD82Y7DoWmOfu1MGuY6fi64i8JTF1OyuErRYMJBFtuDaaussAMsMLJnmS0vuQHreu+JDYwyxjgTDXPAYsWQxpkTT6ltykCFu+glcU3S4tKxymCyyA7etO0t75hnoWEGSu1TRoW76JHEG97yjnkWzo2mioUhQSbYYOmYZg2ss8EmWw1jsBYFTyY55CV9Yp999tlnP46GGajhpolWtE5hDEphgsHaYdbBBptsWWTntaOdq59hH5i0BI2pTbJ9tW44FNXel24XIjwwjRl9q3SNYW6MMqPqdvrNMVySVP2Trj0U3CvhlYipV1w9cpuCyIgMoYoJ6uAoNADzvug45Zj7yoBXfrjWup4FNpUP90w83Gjmo+puO/m8JAbcN3D4dUpCw6N96EFl/RgLIB76ETisxR/w6aPfR7D+NjfOfbeHOYYeHrwM6cPqaG0C4EDa+qeN8E9UN/umlSM27Cex9S8bW/9cmENaN4plychcK2z/rnfLbrbSThvtiLBzSrZHuO7Wmpvu9U1ldbZfCTb4hlrtIxcAHO5g65ppXrrnhMPC1kvnK5fWHKkuAKxYS2ygcV0rlvjEtGOxglUm6USA2od7bZ7ZA0zgcMNXu6Vq96DjVnaFuUnt8GvYm+2/bLjrmx9odH8OHtYJcBgN/b8kxzn07RsPkp7oNsv+PxY7vLXhbI0B2O6kbBr78YIaGQ9mNpD/ZDn01If3Bh8OOu7XP4HYqD7kLYGVOfcyTk47aKYl0X7mMjiMDjPg7M42er6j3/abnabFTbZeexnmm/4ZPQMO37lXsuKw1GmniQNWEawkgpUo+P+g8bqExlXC6NwiDU+RkuNUiKeoeU+7RxcXffIw9p5jytx58d4L0uW4KO/t67osuGHVFr1lzLkJFBG7OIqjOKlO+kwUPh53gWwuEnGJGNdJ7wYZ8JOTEBHC5HCLTMRIT5wnSPAYSbKSIiNpslAk1h3SUiqP+NULp2hOtdHQAdF0S1ofe7ErOh/EMyMdczKLF9olnjsqE3JyqeeOygFPyuNJXV4ExVMo3X9j06MfxnOvIEZNoDdJXkZT5mC98R7x1gKc1fs01mxBk9dJBzawOQ5sKDkp7MUhWOFQrjBRrvMoIaKIEOVmyUxYL3rQ4QjYwQIGsIZUnapA3GVBSAIaNA5ND0QYkJFRiSHMgAOcYxIJoiQSJek+IlUaTgrBBg6wgcNx6IRwArCCIg8o0IFB0e4sQGgD2sfstj0Yi/vtsrpEq52XqxUx7wXavU9R5AbVfbV1p6EDtGWnJA/XVOMRsvo8RlPdHad9NxBpoVtpYHLL0QrVHnveFe6uwPf/7jyBq5c52luBaALJx8pX+LgSQAvlHBSU/jQISHSdPDXyK0T8EDNBpjzkeaygcCLzJqgiKV9QtldXCkW9eOkpVFBLmWjZoyokvMYGYuM3q7LDGjTAj7sPXGsYBaVQYdkTHmY1/zyKJHrVqlSqUatOvQaNHgpOvOwmgbx4I2vWolWbdigIDqeB6phIgQHjoSEEYoO3GfWG+xmO9H2b14EtgH09CwceqakEMmDjtbHwH1ywyEvghjwO6F0GGbeagAYru65f6TdFf8NxEZpQA3bCjcYxgDMmoUrc/1DdhozZ9MEhMsFlbnKRv254PFwOt8PD8DLMhvlhdVifRh0CAEy4lSj1fMkew8Zt+fiWtyg/Gs6H67an546+N+CsD3294PDnwOcHM058+/z/7Vt/15TJ8MUb+x/6/XXxtmRzAC4jjHlHw5q/XvcP1+XZL9e/HyHSqDHjJkyKEm3KtBmzXpsTI/YX7U0Txdm2Y9eeffEOMAIAZPHeNcAFkH5MT6DhJhQar4QOSmnAxmukk4d0404Pg1C8IcIZ7jem0m8c6GKCWZ7xmjkieMMCoyyyRBTLbDDlbRLDFh94430klk98Z5Uf/ITIL/6x7f0n3jtUBxqZCCT4yEItBRI1aiOQrFEfAiSN+hJI8bmP1LFAqs99ri4F0n3ua3UrkKW5HwRyNfeLQJ7PPVUzgXzNPRco1NwrgSLNvRYo1jyHQ6BkqJuBg+pwqVfwfijyRYUwvQnHv6TWp0PyKigaNh96H4GBhmyOegPVB40f59xGEvqhc+sAD9WxCKjVXrZAVDdIs68AhHKCotyajCaMMM33GHhE96JFqxBPQEEEoqpC8iJOGGL05OS/t6P7dswwoetDgYYOgzlyg98MT+zFf0ajcoEikxZ3w24atFBdBAG0lP/g72LZuroeHO2D0lGazKLkzmMauyiDCdhr2a5txrOVjSChgd2ova0t77MhhbcusVxATqdNzYG/FtlUbXRQPRO4OeZ3jE2LIpfa374QSXm/jXcJ1RlLGxZ+dBY1t4Brn0S4YIb5A885pd4Nm4nTxHTsncPU/uJFsrvfCo55+xh0RpRwlNVFmRZ5JT0a8vqz7YKjXITu0NETuTeLgWx0wlG1ZKwnE8zEIEPVAl29KW8grf5KvdJSAaHPwFwMFyKZcNGCzUM5o39uRYwWpCG2syOpPpQYJcOaFn+YiakAyoJBWW1PdQ3gky5Lyrv1Qu08YS8gSdFMp6Xw8V//1cwtjV/OeuogqHw10Ysw1TOlp8shZnahTTWfy4ZZH3Bv01/rq0FPiwuORTUH3Rr39SnJaRmeqQkMhbRqn4TlQFNuBzh2XJgnuDqHspyu0HjUXsMzfPUKBo4oQFl/59ra8oQdbCz13uBAOQ+7IIF6czUJA1lU66Bw5NYfWV31oNN7ypngGeWsuTqsEsrhFQEqG1WQZkIcz5vH8rsZjFklUsoKdqUiEv68IaVRHWA1ltQdWoR4IBbvBaMNWXDw7xohT2WjEINN7BucggQF7qiNneY8xhDhaJpbjN+TprJdqRJ68eUpZ5QTOoqiy71R/rGSuGKW/zv5f6bK+V+XqNf9bxu3tMVwufyHCz+PSnKjrh9+fWXoqLsUjumye4LFDWIi7dtumjw+brjklOBI+ScdTjXMTJQ4+jRhyjVAOkeCkt30cx/S2Z8qaXHhEDOrpWN7sCJd6FjeIVEmfARcWahxPLsI1sVRRvQyvF1z0BOqq/mw7dXZ5YiDWzSTRl1gQmV52yFfjGnz20KQxu571VcjSo6/lSSUtDza2mZJtR3ssJefgx5bpVWyM8HDYK/wkP5JPnL6UqVarauNUmfRkTOho3FTlGoP6PIFDRtZeBq6BcMRkGuIiNY4MYmDV0ujHNQz+aSb3NheHTbPCEeU8Mg3wvEIObtW60VLwLt7tL9LwT6HZUmRTfWEN7twFXImIwjFDI64QVhZ3NhBFt8eBbxHMZ8CaIe7H1C8xvXMdyxLPb6VIsSjjQ5Tu6SCqgAr05exOiWSIOmZeqYl2yAKsJ4IfFNStZo5LrDOMVUi2QHIrmqZ8dR/Sd8CWKfN1Wr8Mskb5eGEuUnILSj6pq4YSmagxspkGt6pTX8GqCojM8mUjwKb6kdQiWqQsEttHrQP39bBMb/jp+WMbYfEKRvFj3/DjHhrj/gV5E+5wKkhbQbvSCZBg9oF+S042qt+KCNAGgjS24pSDB1vg0HdlcYmpwORmpccTd0pV+zgEtazSNPfQ0pIHnElz5rKRywGsg04LtCsfnVCrglVCXW2UwSoJrdok1FMXuGCi+3BkEsTB73xIylxRo9pfLYQYxLuUC1A6WAXzk0miNkeiw1OG6sUC1JVAcxx+9QSh5gpb4ljMlXlQ8qQQ3dgkoicYMp93+rZewvB1cgE6qFuCI/w2OaxiJkb+/Jx6REGfgqeugr5MzGoCXlAhbvvgpRRatUGSqa0aT40UTVEIniStK2KkQNSWnadTS44MC0ZcShqn/tNbjSpzhJPWqmVtdIahqMy4JIurfISwFqdDknlN/ZkJWaJOfPmu0hCIViLEiCXeDo1fx31S8zs39RXB2funyM/h/4qJvzk1FE1AlLSBoRckNzDUC2Vie0A3dVydpP2+nlQlXWLmsM6kpxf2qNAnzxXE9I8zbaSdNBbUmBp9qN4v7SdxKEPSQw7OPKYqmGDHU1G25UrXOzQT8UESQ8gg7ZI7KplJNU1l8Ei8eqUd9TGu/Hq7MDh3qFLtVYpmTYB1RVu8jGGn+HIKixbp7pl08klbTB60qEpikY9sjLo9EaglvU96Bz3EvfEcLRjtkf+1rba2RopIJY4orU7uObY3Y9SlGnOR8UZRdWYYRWrEpkS6FgkfdvN4lxqew4RQe5mP6W+wnEkhvXYbXxIZd2qOGV+DxkBE9TT6D3p7Zq2VzJUAseOmluQLiocOOkAKDVWaXR015dYYhhgYrCcD6ml8QGDF/GOWXf4pN3DFIOvh2olo92vyup7stXa0MvaZcUB90LXMpfiqT0HdGwvKlR7KYetkJMa2zJ/eArTc+pPLwuQVoRD7jxII8nWDhElbFkfTa6MUhEyZ1g5yvyhBBlM5pzxUDZLT/37WD/EMrpTwTbt4IhlG7ZotGO0+OI4aZ8Go5MwWJcz21FJpnoSIFY/ccFOPVCPGOEsSkbF/PQIj5jGOrVbVnfwRTqNq6nNasQEQSYH7oLXLiW31UgXpk8J44vqKc0GKe+BUadt3wUGAkJHB7zFtQeGQxccdSieReslSPWf21E+PxPTi3gAyczhLgUOemFaBT28Nb0szb2eFfH0QV74/FTUWTUSxGVUnmvtGSxEF+eUJztVfeYpr5KlNEbYbqQ/w8UBwJAH0HamgKFli1D0/cDgt1aKRsyIiBkajPOqYfpIH2OmzjUXl2DjQBcnYNPzP23nDgeJTLHZjvA3F6eZS+qL+hBHp2CFSjh9r5hEHI5LWf8yYeu+fiXuj2dEpxTy4BSscCAS7mcaFpIjOC3TN15a8XSiiv1d5nw1J3XvVVdSdCXBLyTQ7X6UP791na9WoVPtyKsOfHdGN4V1cnOIkpCaGROZGQLYjJzIqtrI6Io6olJUVVV4RG1VQhxWw8BWVUnfSk9FQ88uQ89O+1zrjciqGmx1dYKSoDTFEzCaH0DKetZ6qpr6NipKhta6Pz/vyl71JjjIgm2Mo3dThbeljyxJqar/UU1W/8NoQ8MMt3tOGvIR8uHF1YdJ9djPRUuCiuyQgv0MsjKrmh7gbl1DWxUY4ZuThDq3YelD8tGWvyGgLy1vY6imbeEGLDOpHO7hsJgJURqr/sUfdMIUeQNS3akvcKdANyLxpG6ttwWvR5SKf+OeDogqLHnnfDSKVObzyPWhfkSuc08aOBScttLk84hUfq/nmw8c5a+vGV3LuuaOM8ilM73oei1b0HiQOciMcqb1WLAxXFpjymrKekl9Wf4AqqVC9FkHJbMIdHx1e6qd9XNg5NrO3gaSJT+J0MR/vZGQBOTgYj7stSKQKXNVXJDY31kSRgv+kF24ebC3cBUl1sW4FzlLSg6fQRYu7hOXE+KiplBr8IY64U2sYRs6DULU6B833EN1i/QIcale8TkFiZTnqB9vXuxNN79muxhd9Q6O2QgmRCCZ0QQ4jJKJnpTGv+v9oztv+iwCmx2v+PFGND0YOBw/gIUOqldmXGhMUkLkg/zYNCQBblntjGSPaFO1s10v9n8avPBleHDEAF69UZnZrVe/kugkTRzewS6vfEa97f0yw/q4iTWYFOobntaUn1ZEjgpQEKYF4W/NhTyv0Yd/jpcJkcNPVxmmV74yjU6gZf4ppenXaNNMkCyKPbn0FNpK3wWEJHdmZqV0gZyeMm+7ch9v5jGOnDmQHhB2JdRa3fDkj3rk9+T/0vjk3+XHvmFPPPktb7jXunTtve7t2X9N52URmJf7Oyv7Z1pSZER6MpvtCdeYGG/3KOJiemfEJYDQapiYQomOZSg1yG6ZmOa28yKIOPdT7qhorWaMNs35ggvr6G+bbL/MCjzP6ah2FK4FBKZTczOTe4A20vPvgNDZoDTV5MABkCq/LlcqJyNXIgcCLfEZqKciVoFpdFmDesA2F/EViFPTiYjRMXd1dPV1vB/kbEJBSleHOp5MjjQ3lda6OCtr5fRIdt1PHpfS7wyfXh9tfyRcLaIbr62anLqFf8lc4Y96mu5478FlTWmhS/jNdM+EJUwrPupOtsbzm0OtfvTfGH6QXPh6JozbrrScJ8y+FHD8bb/cUsVwggG/0BH0/sMvm6XGSpkVD6YkrWxDSTe7c+a4a9+DZXxyDkByItiaGDTEM0iu4ZkhD7Yc//CjBmoBQ54/eN/fc9+rwOayDzexK2zg39L2rRpGqZi8+EBartu5PKFZIS7+CS6kU6AePnpik+v3e5Sop2jiixQhuoqm7aMozvXeY41V+Vld4yx/kg4Gj7aU1KWcbDU7WvOfnqsuEoFnZqNFInyV/QiTCN5nZPE7+yH+3MbPICCNKvWjWSgsBAw5vWhq2g8k+yJtInsAQ44pGvpsA+o93SqOOAdyC3tVlhAy8kBF0JFz/cg210yPCDdP7xAzQPhtibvbpfSGstK9AlbQCoPe0sXS0v49hEVCL/h99hL428m9tBO/9ybefFp41hNCTIjwS8uEGDhR0dy1v7/a8ZixbckIvvJrm+BY0FLoZabrhRNHyKcHKnr6S5R8k83m9Hp++unpHLzlzRK4Kve1aWvrXsVreu2rvX03aKXVzpKkaavJDXQ1abeQV46TqbL0dQ1N9DUkmZmnCHqM41HHOAfqm/OfSS4K9QUz6i84iIkjPTGOf2D+8nwat/5Dv8AorzwlLqI8PxllC1r42qlofn899IsIf8EvSmxaRteT6WtFppluQF5yPm0H5ff4GW+Z9FRNX92p9/Tqd9zSLDHteYSAniPjaOrOBVJNenBsCSkb+ECP+P3O8mhOA355PmvXK+xFQG9UdVZuclGwu1FWoJPdy0Drcvdm9umtLDQhcfhBb1RfTnlOadBspjeo+OCnAYPvBgx+qug+qFaSF+EVYN6xnP1wEkFWlp++LWp8WFre0Fj0DuL/n6Bpnjw7SK47206egNWRk90XG/Don2Vs6T8vNHH1M59b7+U8Qm7CD/ByunG6sXvzNnHWWfcvykeYXlt9MTG7sG530/7m2uuFlxMrYDsd9PbtGZvUMz1npmGdh1sFsoXnUwTWI9iKfiQBd/t2N2CJ3TkBQNsVAKhoMpkPe40M8E5YoCEH5vQGfmL1womKR09WGi7PPrg0Ww9iYdkZ2RlwuuJtMcK7BBcPd0eHRbeWvGxLqAXqTpuelRfB0ybaRol6j5A1YOD7aIqKLv+cyWvA+jXRIN+IR2kxVXfYwMsK5FBsP9eu9rxyT8EF1wEWKFLu8fHLl9BdNE9SX8V1atZO69a2Rae/AqkIm3Q/WqMmGlOf6gEbtwUaPjhT5PVtLjaj4+Mb2sYmWofkGMekvJGec49yn4M576+9691P3cKFKYCFOpyXW+zQ432hn13YruyxGLJW4SftnAZi9gSosc+zc3/mKQ38O58cPrVzBK2+gC5uGYi3jtUUlPUwiB3He414ZJexpXEx0ybG5sFWfT2p3v0h5UmdzDJd5raIsZWDNWGLtFUPFrz/di73Drkl4PxquSd/fvrZZ8lGXN/CzTetITYrO97M7UHP010ByufOzPHYpntF73Xz6mKzJ4BDpzMwa9AAFfGC8hK8HdzdjWMteNXRFMACBfQo4pRhrmuuLiHGQS7OwNEm3nnrpJRAxg9haRk5nUd4rqtuIqKZvwlQvnr5B2uUXmrtq2WzUtE/4/MG9JI3MrBXiNP4+SaMrN1rFFFvsPC1xfjPUEa8HQkh9rGB9Paj1MH9rQ65PE6KOLC3iWNig/KfOSOIf67GfMXB/xbjSAusAv+Zivx/LyekzbMK/KXg2qreJCZVzg+31MwnxlW/AdlVth8r13oHPYLpKIB5W4vz80h43r/Ki+1Cd+ZPEWt0MjDa6fXRBZNgznu4PjDY4xZG61IHmLcUGnc/6sA2/98uWmrBVHSlfireILkspnAaLnllZAl0yOQBRbwNFWycUi36BPjPnrnroX1MokJHw0srermzqWv9SQZVLczV2s7TQEneUZ5Dql5P298gdeshJWLYxKPCkkJjGu9CcAzVhWM+MtgR0kixrIiMLHdQljK7YnBIZnzxIGkQC4Jhzs6hE41tz2Cgh/Lo+7NpxUJ2ijgZPv5e6b/95JiCeNKxKPEnoFBy6JYEhb1NPIvVS5gVLZzFXiHexaRzmaX/ciZ8f/ghfs6K04Vn9lfGr4zXLjxWnLNwwMzSf2XopPCKLdM8jwJjFru5w92zthddj52/PgJiWQHZJkReneNqucKR4OdKFmhZfzz8ZTp1+vM40vFwuUWQlzAud2JkrcqwymhjFIV/JQvyTJmAfZoJ+N8jMli6+a02nbZ7Oy9OjMvxEsgCzcvQNflhOnX6y8jjtpWHAqDxha6IOhen/EC4Jl3l3GUNHSfzEqSk81WCWsLtppJfvWrmXhZQW18D0xx9jJlqUfd4qETYpvvTGjZhQgafkY7vUHZbzg6fnD83/fwUmXuVspTJ2T2FyWx/XN5I63GlfZcnZbwABbhCdX+BCMQCRztfWViCQw9/PXj2dGGquds5NMjdMTw3BIe+XQgKHz2KIifGisKjY8Nj4hPt80dG3cvSssJj0zIL/foHivwzsiOJWbmuZS8G7IqSSZGx4qigIMJUf8Bqf6DHZNCww4C/h2e/370LcLb1uFDWjNsYJkShUiFYQa5XTjpYulI6hJZG+RykMR2lHn1G/U4FpdSmJxRdBX6lWNsa9NC6x7ObirfiPV5RkIjWrAJipbelUZLDuFT7jW430zx3aruBLP+dWNsq+uHFbfTKK0pIdV5CcgnBWvGmZowMl2aNkoelWBhXndFR1ROaeFVbxTsimlGyJ++R1dl1bBUN410Aq2cyj4Fgrmu8HNb/FBQ/6+U2lBQVPp7scCM/ncwvqS/PTLMx1zUxd44L8vR3jjM3NdWx+x/ZUHweXynDVll8vqGu8Cy+qrSEvaLoHKF2hGqkOhSmMkQ1GhlsNVAdHxpUHW03AMeeZr27emF+4UH27lV+DS7CscGKGiJCJQz29eFx0bnJMZJWx7VMAq8YXKAme2iDobSQOUis+FFx0aW3wWgO0UEYcqC8klL2moKzDfUF3Ozpp1v3V+2kexy5NREhQQ9kAgQgV0ofw5o6ReFmsSCgmx4UKCEGsqIq6pK28SC4wVlCKgHc+R6HjHwnh7Q8R6e0TAfHzMz/R0RV7oiJq6iK3lTVcFFVgYvp+i7ZLkXVReHZ4YXVHBxf5HPkoS7PwOXKcRc7RYG/knfv3BUrJFSl43JD3RycnHQ0mlJIwJpxX1dVSZL/2s4dMVXBS4XWZYHBcfn+DjcVjWWPZVwkOdUGE6MqQ5yLrmlIyN9RlhDyzEcMgX0Ilhl4M+GIsHgAlN3P9x6WyuamilfjCKYxdelayjMUwLyFGJzuJu7f7Azd/00mwJAhbe73yGi98ZCQDKdbc06kWRV7kLBOmvpCN67+ssKdiYb3eYVGr2+FWXvjgbbCpuhRX17+o54q1WJqr/CT3soyjK2lp66OOcFOw8bSU+eehStiCXerwfFiqIVPZw+9NYerF8HVNtjDhIKULL/oHJh51tpY/NDFQ1Y9rUcyfuzXrqbD6OMBXsyWwi8tV29iyJ05reyzGtnKR/C9emz+z7jmwVBZRVNJwzdQWUN5mq+koaJpVdXq8iy6yqyPuGeZl0zafNLtoDNDavVsevD9iqSi/0QqwislY/PVKvGcPNHOrWoRVqaAFlPHzQgeHU/j2wGzsc9NTgyZ92j6Owff3tA+2s01vBgVMGTKY54jycVZ/kHFWbEAz1AMxkd3qW0DLcUhD0YUhVTNH5H0YtWKR5o77rVdMbmcxxJzRcTZw0xbWMXicZp+3D2j+FFdc3snw7e8oLHMgYltldFbMUuqftSQXbjauLCk5+wa6OCY4HqvE0/61PbIq0lbQFtao1HfcXILdrzmsE2NTzMz/O++vx1b6H/bI0u5UOXIwbo3kuCqo+5oKoIW9sqoY40/cSYqOg2EFI/8pM01K/L++5oUE/suzH8pJt19ezQ8vNzf80ZfYuKbdGXr7ohI4w7+W0XvRR7GPw5TtsFGMh1ljFc2TS19Wp1Y1R8WkrPSBXKThptdmxZiMZHcSEhC/WAVfhwwcr7SgX+X40luZpeU04PtXvblyhQF/Vsipjjo8ahkBNuMvMzoEu2zdNNvX1KOr35j19ah76bT5CCXUPWWAnKE0fTiaUsooh6RfbKHelRxKnikgFYzB6HsX2YCM9SJNMSz/ssqC65lv/Nj4Uuu0I9mQUnmpKcdU7ILs0tj7zoyKjbVtwuWfCX+/94Sk+OeeUvayNj1EzzGdv7teY9ia8sHYh77OauEECO/xb50l7aRsh7yiJmnvfG/C9dZ/Dohrnh2tKNkLj62dEZufNYms+xIHPOJEGIm8Nu+p8/NrM2ozWX8xuIBPD5hBkHeJqaBPg2BAV2BAap6N+TkBfjlZa3lFAQEZRVBaGPeJTDa9FKrpVTDqUtFAkFYZ/8Es3NeFmJnz1y5JX8NWDfZHZVMQ1FpxC7v+5bDQJfB6aBkGo4ipXRGgI3lECSecFA2DkWl+lJs7ayfQ+JVByVjIiqHQqlwsZ6cv50bQmqFs+U44MppDNzcTU08Xcx4DVxdzc3c3AzhNC+SmMQXyc4XlQTMXu2zkGVMRpKQZChztf9XC2d/bUXwp8PQfa0Tld52Z9mL/U77/zx1HsPQEtwS1xLSQoc5xfXFKYaLvdSFx62CPIJ59CAkLC4MpFsS5LPlYWTu2FLT9tHnTzzqJLnygwU8/RycnM0XSAv1Ko2WUQhjE8Su9mzSeT5JKQc+HL7Q0N3ZbHdZEjBzlLlngRRjHMHL0cV8kbT46iml1KdRxEuEMJrPJpQ6HKgfYi0ferUX0wUKZdmNSQn59VCcXJ7XmJCUXY8UFGB74qPRra19CVHoNsCNDMfvAs3LzhHOtYW1fhg7f0xp0M7SWQZwjxBIXYwyO7JVVStzSjUsmRgQXJwSE1AVgrF9mM76elklVQVpdTVVlTrguZFrzMYI54dKhxF8Y1L8vItyoxKqKrOFflz46uUOuVPolSssPMdp696WUtcIvnMXKp40pVaZpg1GBBC/j6+vaLz42KnYn7Uv2klOxfL31Tv42mf5hISqKoiDwupi0rdVxYRF7oqF4k2b8OHmOv/1LY/vTvvDtz33k7HzTYwLDSgrDo/Lr0Cl7/5RIvvag6xIq8BC80t3JHU0NCUl7urIy6qow/BDX2R/8eCH/sKLD/7dvqB0/Tw9bdbyF/8BbA7/B8ACfv5RXi4s/FISFuuq3TPy/xld+aEw/7/MKFgNXAXhBB65quZ3mSNchXEMzjWjNmffEVy77YdFatbn0cri6o3s6doSBL/VEMh8d5R8AGqv7OXj7Ca4f4GMTaYvg+n0kAfMWAUnGXGbq5WubLETFC6/WIYgF1AL8uFFVasHdK2u0/W6QTfiIbHA5gvygmuF4A/RnOkT3Way54spBkO81cmv3dOk0ApZXJgOiMn5By5dK/gTcmD6RLyZLGPEyQCumQpztelDxEyeZUacZg8r6CL+WCHfqB23tFDzijCT7c2n2ArJAFtxcrcVQzi4EqKJ6RNUM9nAiJOvVkoJxLqiODYDRAJrtvBsknxFNpJyCU2M1VykPk3yDYNVohi3tQoHgVZp6OZCZDnjOkFDskq4nijcegh9PuvE5JKvQ50g+jd1bdeqZ1sdixjTOjCv6diLvkJ1nJdYR4410sawNoJ+zUjOShINpFgzFZyEmXM6HtqB8mpjAeduDMj/r/PZkuf+D7hl/haureDS0u+otzR8X3bZVuu5csq/2umBcedopEW8gHvF349HyjOhk4pHKvnj+bNyaIF8NLGTbM6MmQDumb/1qAmimZ+PBplWJmXh6LqSU9bIxFQDfVc/Ooi7qETTFD9xKpmamfyj8OaZZEJ1OAXGegvRs0KesdMf8OOk8lvar+fGgFrQByzkYE7awz8Q118VeWAeDX/e4QBmRp+xoE2+m7GMlofvvD/oaG9B4fka2H8Se6HrFqJLTH+wgH5KKNfdqN0JIDb2+w0mUSZMl/ar/dZgRnxZN8SfnmUeAnHhOHQfyB3h9xrb8lTF+40BiaA+G/tMsBstPAFki2qMQUS/5tcNCQScSy8XOQVfxRiEALnJ2ldCUowtWCR/bx1fBoCnf+puD8A7of3bP+v8X7X5l3kBy6EAAiwuW1oFsPzgUpZe2gHEfVPfVyJbQ+Pfi3eaa0BJkhD7gF+HchvzHPsXu7Bjn49F5zN8RXCq42hEmtMpgjdPSik1+KfGC9Rhhjki5BGFOh7P2jY+iolml5qNctvK6etiatjdxQ1O45ZT/UftEOE3bqvtRDIu1wZeAkdbRF7T2U5EBo1LadSY/qpN8LQwvoPx7dm69oGa7qbVQwQGv8Rx1KnFcVKDBsR6FEuP0M8z0krZRXo2dGVIpgrQZACxNubaIRKbn2lHsmgpZjlM0jyXZTtIjE+SYmfuBjMu9EnBAg0J7SSxU5jouEQW2Q64r7UQXTsi1rKzExqu1A+X6jlOatkw28nEF02OfXiKPKIS2pJjVzEZbbh3ISyxJ723GZchu0mFSaVLr173282DSdX1rOok5z8RfYdVfiCXH0hnhKAmyqsd8skpPf7wplGBVT7cT4/7Y57eJEJrEuNezyksAufPrcCIunfeVFXdJ2HqpdFkoZ1KqYlMukBm/Ja/KOWwUGBVA2qzUUANCRoyyqbbUiKXJc7FH9nO5zSHfEcye4+oFvHDWEbe54KHMapyEvmBaIey6DQ17eZMJ5Ccps8yPphAoIU0opigjziaqITS2h0IHAZOJg0ztFwK+wTcwrzSCwDrvIzxyBPmHfMMp0JDJH6JwCfgTFgBHAL+5BPz43dD42VNaMz8iDuhIZIjIvBGKEtHgB+QcNKFyZXG6iChNoVd1bfMfWhI0wE4A1wvQzAyX4bCzEmN3qWmgWUYfPyXYZ1S1F1muqjkufMQgMCRPQfeuAniJ9At5KbEXeAZLuxWVeHGxnWjrMG7WLQ1mFfOaLe47BD4atnWdUN2Z13y3lDgbc+HC6sgr7+IwIsjc7PHX98u5CYJ6wVv6hZ2bQUWvb15EHej0/q5rrPikXjbcGDnOhsJmr8hO7LRvBu4V/sNalTIU6RBh6Jrts38i4GTzfts3QMAAAA=",
- "headers": [
- [
- "content-type",
- "font/woff2"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/icon_bundle.svg": {
- "data": "PHN2Zz48ZGVmcz4KPHN2ZyBpZD0iYXJyb3dfZG93bndhcmRfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZmlsbD0iIzAxMDEwMSIgZD0iTTIwIDEybC0xLjQxLTEuNDFMMTMgMTYuMTdWNGgtMnYxMi4xN2wtNS41OC01LjU5TDQgMTJsOCA4IDgtOHoiLz48L3N2Zz48c3ZnIGlkPSJhcnJvd191cHdhcmRfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTQgMTJsMS40MSAxLjQxTDExIDcuODNWMjBoMlY3LjgzbDUuNTggNS41OUwyMCAxMmwtOC04LTggOHoiLz48L3N2Zz48c3ZnIGlkPSJidWdfcmVwb3J0XzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiB3aWR0aD0iMjQiPjxwYXRoIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNMjAgOGgtMi44MWMtLjQ1LS43OC0xLjA3LTEuNDUtMS44Mi0xLjk2TDE3IDQuNDEgMTUuNTkgM2wtMi4xNyAyLjE3QzEyLjk2IDUuMDYgMTIuNDkgNSAxMiA1Yy0uNDkgMC0uOTYuMDYtMS40MS4xN0w4LjQxIDMgNyA0LjQxbDEuNjIgMS42M0M3Ljg4IDYuNTUgNy4yNiA3LjIyIDYuODEgOEg0djJoMi4wOWMtLjA1LjMzLS4wOS42Ni0uMDkgMXYxSDR2MmgydjFjMCAuMzQuMDQuNjcuMDkgMUg0djJoMi44MWMxLjA0IDEuNzkgMi45NyAzIDUuMTkgM3M0LjE1LTEuMjEgNS4xOS0zSDIwdi0yaC0yLjA5Yy4wNS0uMzMuMDktLjY2LjA5LTF2LTFoMnYtMmgtMnYtMWMwLS4zNC0uMDQtLjY3LS4wOS0xSDIwVjh6bS02IDhoLTR2LTJoNHYyem0wLTRoLTR2LTJoNHYyeiIvPjwvc3ZnPjxzdmcgaWQ9ImNhbmNlbF8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTIgMkM2LjQ3IDIgMiA2LjQ3IDIgMTJzNC40NyAxMCAxMCAxMCAxMC00LjQ3IDEwLTEwUzE3LjUzIDIgMTIgMnptNSAxMy41OUwxNS41OSAxNyAxMiAxMy40MSA4LjQxIDE3IDcgMTUuNTkgMTAuNTkgMTIgNyA4LjQxIDguNDEgNyAxMiAxMC41OSAxNS41OSA3IDE3IDguNDEgMTMuNDEgMTIgMTcgMTUuNTl6Ii8+PC9zdmc+PHN2ZyBpZD0iY2hldnJvbl9sZWZ0XzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgd2lkdGg9IjI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGQ9Ik0xNS40MSA3LjQxTDE0IDZsLTYgNiA2IDYgMS40MS0xLjQxTDEwLjgzIDEyeiIvPjwvc3ZnPjxzdmcgaWQ9ImNoZXZyb25fcmlnaHRfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTEwIDZMOC41OSA3LjQxIDEzLjE3IDEybC00LjU4IDQuNTlMMTAgMThsNi02eiIvPjwvc3ZnPjxzdmcgaWQ9ImNsZWFyXzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgd2lkdGg9IjI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGQ9Ik0xOSA2LjQxTDE3LjU5IDUgMTIgMTAuNTkgNi40MSA1IDUgNi40MSAxMC41OSAxMiA1IDE3LjU5IDYuNDEgMTkgMTIgMTMuNDEgMTcuNTkgMTkgMTkgMTcuNTkgMTMuNDEgMTJ6Ii8+PC9zdmc+PHN2ZyBpZD0iY2xvc2VfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xOSA2LjQxTDE3LjU5IDUgMTIgMTAuNTkgNi40MSA1IDUgNi40MSAxMC41OSAxMiA1IDE3LjU5IDYuNDEgMTkgMTIgMTMuNDEgMTcuNTkgMTkgMTkgMTcuNTkgMTMuNDEgMTJ6Ii8+PC9zdmc+PHN2ZyBpZD0iY29udGVudF9jb3B5XzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgd2lkdGg9IjI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGQ9Ik0xNiAxSDRjLTEuMSAwLTIgLjktMiAydjE0aDJWM2gxMlYxem0zIDRIOGMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxMWMxLjEgMCAyLS45IDItMlY3YzAtMS4xLS45LTItMi0yem0wIDE2SDhWN2gxMXYxNHoiLz48L3N2Zz48c3ZnIGlkPSJlcnJvcl8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMSAxNWgtMnYtMmgydjJ6bTAtNGgtMlY3aDJ2NnoiLz48L3N2Zz48c3ZnIGlkPSJleHBhbmRfbGVzc18yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTIgOGwtNiA2IDEuNDEgMS40MUwxMiAxMC44M2w0LjU5IDQuNThMMTggMTR6Ii8+PC9zdmc+PHN2ZyBpZD0iZXhwYW5kX21vcmVfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTE2LjU5IDguNTlMMTIgMTMuMTcgNy40MSA4LjU5IDYgMTBsNiA2IDYtNnoiLz48L3N2Zz48c3ZnIGlkPSJmaWx0ZXJfYWx0XzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgZW5hYmxlLWJhY2tncm91bmQ9Im5ldyAwIDAgMjQgMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCIgd2lkdGg9IjI0Ij48Zz48cGF0aCBkPSJNMCwwaDI0IE0yNCwyNEgwIiBmaWxsPSJub25lIi8+PHBhdGggZD0iTTQuMjUsNS42MUM2LjI3LDguMiwxMCwxMywxMCwxM3Y2YzAsMC41NSwwLjQ1LDEsMSwxaDJjMC41NSwwLDEtMC40NSwxLTF2LTZjMCwwLDMuNzItNC44LDUuNzQtNy4zOSBDMjAuMjUsNC45NSwxOS43OCw0LDE4Ljk1LDRINS4wNEM0LjIxLDQsMy43NCw0Ljk1LDQuMjUsNS42MXoiLz48cGF0aCBkPSJNMCwwaDI0djI0SDBWMHoiIGZpbGw9Im5vbmUiLz48L2c+PC9zdmc+PHN2ZyBpZD0iZmxhZ18yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTQuNCA2TDE0IDRINXYxN2gydi03aDUuNmwuNCAyaDdWNnoiLz48L3N2Zz48c3ZnIGlkPSJmdWxsc2NyZWVuXzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiB3aWR0aD0iMjQiPjxwYXRoIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNNyAxNEg1djVoNXYtMkg3di0zem0tMi00aDJWN2gzVjVINXY1em0xMiA3aC0zdjJoNXYtNWgtMnYzek0xNCA1djJoM3YzaDJWNWgtNXoiLz48L3N2Zz48c3ZnIGlkPSJmdWxsc2NyZWVuX2V4aXRfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik01IDE2aDN2M2gydi01SDV2MnptMy04SDV2Mmg1VjVIOHYzem02IDExaDJ2LTNoM3YtMmgtNXY1em0yLTExVjVoLTJ2NWg1VjhoLTN6Ii8+PC9zdmc+PHN2ZyBpZD0iZ2V0X2FwcF8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTkgOWgtNFYzSDl2Nkg1bDcgNyA3LTd6TTUgMTh2MmgxNHYtMkg1eiIvPjwvc3ZnPjxzdmcgaWQ9ImhlbHBfb3V0bGluZV8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0Ij48cGF0aCBkPSJNMTEgMThoMnYtMmgtMnYyem0xLTE2QzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOHMzLjU5LTggOC04IDggMy41OSA4IDgtMy41OSA4LTggOHptMC0xNGMtMi4yMSAwLTQgMS43OS00IDRoMmMwLTEuMS45LTIgMi0yczIgLjkgMiAyYzAgMi0zIDEuNzUtMyA1aDJjMC0yLjI1IDMtMi41IDMtNSAwLTIuMjEtMS43OS00LTQtNHoiLz48L3N2Zz48c3ZnIGlkPSJpbWFnZV9zZWFyY2hfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0wIDBoMjR2MjRIMFYweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xOCAxM3Y3SDRWNmg1LjAyYy4wNS0uNzEuMjItMS4zOC40OC0ySDRjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJ2LTVsLTItMnptLTEuNSA1aC0xMWwyLjc1LTMuNTMgMS45NiAyLjM2IDIuNzUtMy41NHptMi44LTkuMTFjLjQ0LS43LjctMS41MS43LTIuMzlDMjAgNC4wMSAxNy45OSAyIDE1LjUgMlMxMSA0LjAxIDExIDYuNXMyLjAxIDQuNSA0LjQ5IDQuNWMuODggMCAxLjctLjI2IDIuMzktLjdMMjEgMTMuNDIgMjIuNDIgMTIgMTkuMyA4Ljg5ek0xNS41IDlDMTQuMTIgOSAxMyA3Ljg4IDEzIDYuNVMxNC4xMiA0IDE1LjUgNCAxOCA1LjEyIDE4IDYuNSAxNi44OCA5IDE1LjUgOXoiLz48L3N2Zz48c3ZnIGlkPSJpbmZvX291dGxpbmVfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTExIDE3aDJ2LTZoLTJ2NnptMS0xNUM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6TTExIDloMlY3aC0ydjJ6Ii8+PC9zdmc+PHN2ZyBpZD0ia2VlcF8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIGVuYWJsZS1iYWNrZ3JvdW5kPSJuZXcgMCAwIDI0IDI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PGc+PHJlY3QgZmlsbD0ibm9uZSIgaGVpZ2h0PSIyNCIgd2lkdGg9IjI0Ii8+PC9nPjxnPjxwYXRoIGQ9Ik0xNiw5VjRsMSwwYzAuNTUsMCwxLTAuNDUsMS0xdjBjMC0wLjU1LTAuNDUtMS0xLTFIN0M2LjQ1LDIsNiwyLjQ1LDYsM3YwIGMwLDAuNTUsMC40NSwxLDEsMWwxLDB2NWMwLDEuNjYtMS4zNCwzLTMsM2gwdjJoNS45N3Y3bDEsMWwxLTF2LTdIMTl2LTJoMEMxNy4zNCwxMiwxNiwxMC42NiwxNiw5eiIgZmlsbC1ydWxlPSJldmVub2RkIi8+PC9nPjwvc3ZnPjxzdmcgaWQ9ImtlZXBfb3V0bGluZV8yNHB4IiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIGVuYWJsZS1iYWNrZ3JvdW5kPSJuZXcgMCAwIDI0IDI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PGc+PHJlY3QgZmlsbD0ibm9uZSIgaGVpZ2h0PSIyNCIgd2lkdGg9IjI0Ii8+PC9nPjxnPjxwYXRoIGQ9Ik0xNCw0djVjMCwxLjEyLDAuMzcsMi4xNiwxLDNIOWMwLjY1LTAuODYsMS0xLjksMS0zVjRIMTQgTTE3LDJIN0M2LjQ1LDIsNiwyLjQ1LDYsM2MwLDAuNTUsMC40NSwxLDEsMWMwLDAsMCwwLDAsMGwxLDB2NSBjMCwxLjY2LTEuMzQsMy0zLDN2Mmg1Ljk3djdsMSwxbDEtMXYtN0gxOXYtMmMwLDAsMCwwLDAsMGMtMS42NiwwLTMtMS4zNC0zLTNWNGwxLDBjMCwwLDAsMCwwLDBjMC41NSwwLDEtMC40NSwxLTEgQzE4LDIuNDUsMTcuNTUsMiwxNywyTDE3LDJ6Ii8+PC9nPjwvc3ZnPjxzdmcgaWQ9ImxpbmVfd2VpZ2h0XzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgZW5hYmxlLWJhY2tncm91bmQ9Im5ldyAwIDAgMjQgMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCIgd2lkdGg9IjI0Ij48Zz48cmVjdCBmaWxsPSJub25lIiBoZWlnaHQ9IjI0IiB3aWR0aD0iMjQiIHg9IjAiLz48L2c+PGc+PGc+PGc+PHBhdGggZD0iTTMsMTdoMTh2LTJIM1YxN3ogTTMsMjBoMTh2LTFIM1YyMHogTTMsMTNoMTh2LTNIM1YxM3ogTTMsNHY0aDE4VjRIM3oiLz48L2c+PC9nPjwvZz48L3N2Zz48c3ZnIGlkPSJtb3JlX3ZlcnRfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xMiA4YzEuMSAwIDItLjkgMi0ycy0uOS0yLTItMi0yIC45LTIgMiAuOSAyIDIgMnptMCAyYy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnptMCA2Yy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnoiLz48L3N2Zz48c3ZnIGlkPSJyZWZyZXNoXzI0cHgiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgd2lkdGg9IjI0IiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiPjxwYXRoIGQ9Ik0xNy42NSA2LjM1QzE2LjIgNC45IDE0LjIxIDQgMTIgNGMtNC40MiAwLTcuOTkgMy41OC03Ljk5IDhzMy41NyA4IDcuOTkgOGMzLjczIDAgNi44NC0yLjU1IDcuNzMtNmgtMi4wOGMtLjgyIDIuMzMtMy4wNCA0LTUuNjUgNC0zLjMxIDAtNi0yLjY5LTYtNnMyLjY5LTYgNi02YzEuNjYgMCAzLjE0LjY5IDQuMjIgMS43OEwxMyAxMWg3VjRsLTIuMzUgMi4zNXoiLz48L3N2Zz48c3ZnIGlkPSJzZWFyY2hfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTE1LjUgMTRoLS43OWwtLjI4LS4yN0MxNS40MSAxMi41OSAxNiAxMS4xMSAxNiA5LjUgMTYgNS45MSAxMy4wOSAzIDkuNSAzUzMgNS45MSAzIDkuNSA1LjkxIDE2IDkuNSAxNmMxLjYxIDAgMy4wOS0uNTkgNC4yMy0xLjU3bC4yNy4yOHYuNzlsNSA0Ljk5TDIwLjQ5IDE5bC00Ljk5LTV6bS02IDBDNy4wMSAxNCA1IDExLjk5IDUgOS41UzcuMDEgNSA5LjUgNSAxNCA3LjAxIDE0IDkuNSAxMS45OSAxNCA5LjUgMTR6Ii8+PC9zdmc+PHN2ZyBpZD0ic2V0dGluZ3NfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTE5LjQzIDEyLjk4Yy4wNC0uMzIuMDctLjY0LjA3LS45OHMtLjAzLS42Ni0uMDctLjk4bDIuMTEtMS42NWMuMTktLjE1LjI0LS40Mi4xMi0uNjRsLTItMy40NmMtLjEyLS4yMi0uMzktLjMtLjYxLS4yMmwtMi40OSAxYy0uNTItLjQtMS4wOC0uNzMtMS42OS0uOThsLS4zOC0yLjY1QzE0LjQ2IDIuMTggMTQuMjUgMiAxNCAyaC00Yy0uMjUgMC0uNDYuMTgtLjQ5LjQybC0uMzggMi42NWMtLjYxLjI1LTEuMTcuNTktMS42OS45OGwtMi40OS0xYy0uMjMtLjA5LS40OSAwLS42MS4yMmwtMiAzLjQ2Yy0uMTMuMjItLjA3LjQ5LjEyLjY0bDIuMTEgMS42NWMtLjA0LjMyLS4wNy42NS0uMDcuOThzLjAzLjY2LjA3Ljk4bC0yLjExIDEuNjVjLS4xOS4xNS0uMjQuNDItLjEyLjY0bDIgMy40NmMuMTIuMjIuMzkuMy42MS4yMmwyLjQ5LTFjLjUyLjQgMS4wOC43MyAxLjY5Ljk4bC4zOCAyLjY1Yy4wMy4yNC4yNC40Mi40OS40Mmg0Yy4yNSAwIC40Ni0uMTguNDktLjQybC4zOC0yLjY1Yy42MS0uMjUgMS4xNy0uNTkgMS42OS0uOThsMi40OSAxYy4yMy4wOS40OSAwIC42MS0uMjJsMi0zLjQ2Yy4xMi0uMjIuMDctLjQ5LS4xMi0uNjRsLTIuMTEtMS42NXpNMTIgMTUuNWMtMS45MyAwLTMuNS0xLjU3LTMuNS0zLjVzMS41Ny0zLjUgMy41LTMuNSAzLjUgMS41NyAzLjUgMy41LTEuNTcgMy41LTMuNSAzLjV6Ii8+PC9zdmc+PHN2ZyBpZD0ic2V0dGluZ3NfYmFja3VwX3Jlc3RvcmVfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xNCAxMmMwLTEuMS0uOS0yLTItMnMtMiAuOS0yIDIgLjkgMiAyIDIgMi0uOSAyLTJ6bS0yLTljLTQuOTcgMC05IDQuMDMtOSA5SDBsNCA0IDQtNEg1YzAtMy44NyAzLjEzLTcgNy03czcgMy4xMyA3IDctMy4xMyA3LTcgN2MtMS41MSAwLTIuOTEtLjQ5LTQuMDYtMS4zbC0xLjQyIDEuNDRDOC4wNCAyMC4zIDkuOTQgMjEgMTIgMjFjNC45NyAwIDktNC4wMyA5LTlzLTQuMDMtOS05LTl6Ii8+PC9zdmc+PHN2ZyBpZD0ic2V0dGluZ3Nfb3ZlcnNjYW5fMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xMi4wMSA1LjVMMTAgOGg0bC0xLjk5LTIuNXpNMTggMTB2NGwyLjUtMS45OUwxOCAxMHpNNiAxMGwtMi41IDIuMDFMNiAxNHYtNHptOCA2aC00bDIuMDEgMi41TDE0IDE2em03LTEzSDNjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMThjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxNi4wMUgzVjQuOTloMTh2MTQuMDJ6Ii8+PC9zdmc+PHN2ZyBpZD0idmlzaWJpbGl0eV9vZmZfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZD0iTTEyIDdjMi43NiAwIDUgMi4yNCA1IDUgMCAuNjUtLjEzIDEuMjYtLjM2IDEuODNsMi45MiAyLjkyYzEuNTEtMS4yNiAyLjctMi44OSAzLjQzLTQuNzUtMS43My00LjM5LTYtNy41LTExLTcuNS0xLjQgMC0yLjc0LjI1LTMuOTguN2wyLjE2IDIuMTZDMTAuNzQgNy4xMyAxMS4zNSA3IDEyIDd6TTIgNC4yN2wyLjI4IDIuMjguNDYuNDZDMy4wOCA4LjMgMS43OCAxMC4wMiAxIDEyYzEuNzMgNC4zOSA2IDcuNSAxMSA3LjUgMS41NSAwIDMuMDMtLjMgNC4zOC0uODRsLjQyLjQyTDE5LjczIDIyIDIxIDIwLjczIDMuMjcgMyAyIDQuMjd6TTcuNTMgOS44bDEuNTUgMS41NWMtLjA1LjIxLS4wOC40My0uMDguNjUgMCAxLjY2IDEuMzQgMyAzIDMgLjIyIDAgLjQ0LS4wMy42NS0uMDhsMS41NSAxLjU1Yy0uNjcuMzMtMS40MS41My0yLjIuNTMtMi43NiAwLTUtMi4yNC01LTUgMC0uNzkuMi0xLjUzLjUzLTIuMnptNC4zMS0uNzhsMy4xNSAzLjE1LjAyLS4xNmMwLTEuNjYtMS4zNC0zLTMtM2wtLjE3LjAxeiIvPjwvc3ZnPjxzdmcgaWQ9Indhcm5pbmdfMjRweCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiBoZWlnaHQ9IjI0IiB2aWV3Qm94PSIwIDAgMjQgMjQiIHdpZHRoPSIyNCI+PHBhdGggZD0iTTAgMGgyNHYyNEgweiIgZmlsbD0ibm9uZSIvPjxwYXRoIGQ9Ik0xIDIxaDIyTDEyIDIgMSAyMXptMTItM2gtMnYtMmgydjJ6bTAtNGgtMnYtNGgydjR6Ii8+PC9zdmc+PC9kZWZzPjwvc3ZnPgo=",
- "headers": [
- [
- "content-type",
- "image/svg+xml; charset=utf-8"
- ]
- ],
- "ok": true,
- "status": 200,
- "status_text": "OK"
- },
- "https://localhost:6006/index.js": {
- "data": "dmFyIENMT1NVUkVfTk9fREVQUyA9IHRydWU7Ci8vIENvcHlyaWdodCAyMDA2IFRoZSBDbG9zdXJlIExpYnJhcnkgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KLy8KLy8gTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7Ci8vIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KLy8gWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0Ci8vCi8vICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCi8vCi8vIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKLy8gZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTLUlTIiBCQVNJUywKLy8gV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCi8vIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKLy8gbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCgovKioKICogQGZpbGVvdmVydmlldyBCb290c3RyYXAgZm9yIHRoZSBHb29nbGUgSlMgTGlicmFyeSAoQ2xvc3VyZSkuCiAqCiAqIEluIHVuY29tcGlsZWQgbW9kZSBiYXNlLmpzIHdpbGwgYXR0ZW1wdCB0byBsb2FkIENsb3N1cmUncyBkZXBzIGZpbGUsIHVubGVzcwogKiB0aGUgZ2xvYmFsIDxjb2RlPkNMT1NVUkVfTk9fREVQUzwvY29kZT4gaXMgc2V0IHRvIHRydWUuICBUaGlzIGFsbG93cyBwcm9qZWN0cwogKiB0byBpbmNsdWRlIHRoZWlyIG93biBkZXBzIGZpbGUocykgZnJvbSBkaWZmZXJlbnQgbG9jYXRpb25zLgogKgogKiBBdm9pZCBpbmNsdWRpbmcgYmFzZS5qcyBtb3JlIHRoYW4gb25jZS4gVGhpcyBpcyBzdHJpY3RseSBkaXNjb3VyYWdlZCBhbmQgbm90CiAqIHN1cHBvcnRlZC4gZ29vZy5yZXF1aXJlKC4uLikgd29uJ3Qgd29yayBwcm9wZXJseSBpbiB0aGF0IGNhc2UuCiAqCiAqIEBwcm92aWRlR29vZwogKi8KCgovKioKICogQGRlZmluZSB7Ym9vbGVhbn0gT3ZlcnJpZGRlbiB0byB0cnVlIGJ5IHRoZSBjb21waWxlci4KICovCnZhciBDT01QSUxFRCA9IGZhbHNlOwoKCi8qKgogKiBCYXNlIG5hbWVzcGFjZSBmb3IgdGhlIENsb3N1cmUgbGlicmFyeS4gIENoZWNrcyB0byBzZWUgZ29vZyBpcyBhbHJlYWR5CiAqIGRlZmluZWQgaW4gdGhlIGN1cnJlbnQgc2NvcGUgYmVmb3JlIGFzc2lnbmluZyB0byBwcmV2ZW50IGNsb2JiZXJpbmcgaWYKICogYmFzZS5qcyBpcyBsb2FkZWQgbW9yZSB0aGFuIG9uY2UuCiAqCiAqIEBjb25zdAogKi8KdmFyIGdvb2cgPSBnb29nIHx8IHt9OwoKLyoqCiAqIFJlZmVyZW5jZSB0byB0aGUgZ2xvYmFsIG9iamVjdC4KICogaHR0cHM6Ly93d3cuZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi85LjAvaW5kZXguaHRtbCNzZWMtZ2xvYmFsLW9iamVjdAogKgogKiBNb3JlIGluZm8gb24gdGhpcyBpbXBsZW1lbnRhdGlvbiBoZXJlOgogKiBodHRwczovL2RvY3MuZ29vZ2xlLmNvbS9kb2N1bWVudC9kLzFOQWVXNFdrN0k3RlYwWTJ0Y1VGdlFkR01jODlrMnZkZ1NYSW53OF9udkNJL2VkaXQKICoKICogQGNvbnN0CiAqIEBzdXBwcmVzcyB7dW5kZWZpbmVkVmFyc30gc2VsZiB3b24ndCBiZSByZWZlcmVuY2VkIHVubGVzcyBgdGhpc2AgaXMgZmFsc3kuCiAqIEB0eXBlIHshR2xvYmFsfQogKi8KZ29vZy5nbG9iYWwgPQogICAgLy8gQ2hlY2sgYHRoaXNgIGZpcnN0IGZvciBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eS4KICAgIC8vIFZhbGlkIHVubGVzcyBydW5uaW5nIGFzIGFuIEVTIG1vZHVsZSBvciBpbiBhIGZ1bmN0aW9uIHdyYXBwZXIgY2FsbGVkCiAgICAvLyAgIHdpdGhvdXQgc2V0dGluZyBgdGhpc2AgcHJvcGVybHkuCiAgICAvLyBOb3RlIHRoYXQgYmFzZS5qcyBjYW4ndCB1c2VmdWxseSBiZSBpbXBvcnRlZCBhcyBhbiBFUyBtb2R1bGUsIGJ1dCBpdCBtYXkKICAgIC8vIGJlIGNvbXBpbGVkIGludG8gYnVuZGxlcyB0aGF0IGFyZSBsb2FkYWJsZSBhcyBFUyBtb2R1bGVzLgogICAgdGhpcyB8fAogICAgLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQVBJL1dpbmRvdy9zZWxmCiAgICAvLyBGb3IgaW4tcGFnZSBicm93c2VyIGVudmlyb25tZW50cyBhbmQgd29ya2Vycy4KICAgIHNlbGY7CgoKLyoqCiAqIEEgaG9vayBmb3Igb3ZlcnJpZGluZyB0aGUgZGVmaW5lIHZhbHVlcyBpbiB1bmNvbXBpbGVkIG1vZGUuCiAqCiAqIEluIHVuY29tcGlsZWQgbW9kZSwgYENMT1NVUkVfVU5DT01QSUxFRF9ERUZJTkVTYCBtYXkgYmUgZGVmaW5lZCBiZWZvcmUKICogbG9hZGluZyBiYXNlLmpzLiAgSWYgYSBrZXkgaXMgZGVmaW5lZCBpbiBgQ0xPU1VSRV9VTkNPTVBJTEVEX0RFRklORVNgLAogKiBgZ29vZy5kZWZpbmVgIHdpbGwgdXNlIHRoZSB2YWx1ZSBpbnN0ZWFkIG9mIHRoZSBkZWZhdWx0IHZhbHVlLiAgVGhpcwogKiBhbGxvd3MgZmxhZ3MgdG8gYmUgb3ZlcndyaXR0ZW4gd2l0aG91dCBjb21waWxhdGlvbiAodGhpcyBpcyBub3JtYWxseQogKiBhY2NvbXBsaXNoZWQgd2l0aCB0aGUgY29tcGlsZXIncyAiZGVmaW5lIiBmbGFnKS4KICoKICogRXhhbXBsZToKICogPHByZT4KICogICB2YXIgQ0xPU1VSRV9VTkNPTVBJTEVEX0RFRklORVMgPSB7J2dvb2cuREVCVUcnOiBmYWxzZX07CiAqIDwvcHJlPgogKgogKiBAdHlwZSB7T2JqZWN0PHN0cmluZywgKHN0cmluZ3xudW1iZXJ8Ym9vbGVhbik+fHVuZGVmaW5lZH0KICovCmdvb2cuZ2xvYmFsLkNMT1NVUkVfVU5DT01QSUxFRF9ERUZJTkVTOwoKCi8qKgogKiBBIGhvb2sgZm9yIG92ZXJyaWRpbmcgdGhlIGRlZmluZSB2YWx1ZXMgaW4gdW5jb21waWxlZCBvciBjb21waWxlZCBtb2RlLAogKiBsaWtlIENMT1NVUkVfVU5DT01QSUxFRF9ERUZJTkVTIGJ1dCBlZmZlY3RpdmUgaW4gY29tcGlsZWQgY29kZS4gIEluCiAqIHVuY29tcGlsZWQgY29kZSBDTE9TVVJFX1VOQ09NUElMRURfREVGSU5FUyB0YWtlcyBwcmVjZWRlbmNlLgogKgogKiBBbHNvIHVubGlrZSBDTE9TVVJFX1VOQ09NUElMRURfREVGSU5FUyB0aGUgdmFsdWVzIG11c3QgYmUgbnVtYmVyLCBib29sZWFuIG9yCiAqIHN0cmluZyBsaXRlcmFscyBvciB0aGUgY29tcGlsZXIgd2lsbCBlbWl0IGFuIGVycm9yLgogKgogKiBXaGlsZSBhbnkgQGRlZmluZSB2YWx1ZSBtYXkgYmUgc2V0LCBvbmx5IHRob3NlIHNldCB3aXRoIGdvb2cuZGVmaW5lIHdpbGwgYmUKICogZWZmZWN0aXZlIGZvciB1bmNvbXBpbGVkIGNvZGUuCiAqCiAqIEV4YW1wbGU6CiAqIDxwcmU+CiAqICAgdmFyIENMT1NVUkVfREVGSU5FUyA9IHsnZ29vZy5ERUJVRyc6IGZhbHNlfSA7CiAqIDwvcHJlPgogKgogKiBAdHlwZSB7T2JqZWN0PHN0cmluZywgKHN0cmluZ3xudW1iZXJ8Ym9vbGVhbik+fHVuZGVmaW5lZH0KICovCmdvb2cuZ2xvYmFsLkNMT1NVUkVfREVGSU5FUzsKCgovKioKICogUmV0dXJucyB0cnVlIGlmIHRoZSBzcGVjaWZpZWQgdmFsdWUgaXMgbm90IHVuZGVmaW5lZC4KICoKICogQHBhcmFtIHs/fSB2YWwgVmFyaWFibGUgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB2YXJpYWJsZSBpcyBkZWZpbmVkLgogKiBAZGVwcmVjYXRlZCBVc2UgYHZhbCAhPT0gdW5kZWZpbmVkYCBpbnN0ZWFkLgogKi8KZ29vZy5pc0RlZiA9IGZ1bmN0aW9uKHZhbCkgewogIC8vIHZvaWQgMCBhbHdheXMgZXZhbHVhdGVzIHRvIHVuZGVmaW5lZCBhbmQgaGVuY2Ugd2UgZG8gbm90IG5lZWQgdG8gZGVwZW5kIG9uCiAgLy8gdGhlIGRlZmluaXRpb24gb2YgdGhlIGdsb2JhbCB2YXJpYWJsZSBuYW1lZCAndW5kZWZpbmVkJy4KICByZXR1cm4gdmFsICE9PSB2b2lkIDA7Cn07CgovKioKICogUmV0dXJucyB0cnVlIGlmIHRoZSBzcGVjaWZpZWQgdmFsdWUgaXMgYSBzdHJpbmcuCiAqIEBwYXJhbSB7P30gdmFsIFZhcmlhYmxlIHRvIHRlc3QuCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdmFyaWFibGUgaXMgYSBzdHJpbmcuCiAqIEBkZXByZWNhdGVkIFVzZSBgdHlwZW9mIHZhbCA9PT0gJ3N0cmluZydgIGluc3RlYWQuCiAqLwpnb29nLmlzU3RyaW5nID0gZnVuY3Rpb24odmFsKSB7CiAgcmV0dXJuIHR5cGVvZiB2YWwgPT0gJ3N0cmluZyc7Cn07CgoKLyoqCiAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgc3BlY2lmaWVkIHZhbHVlIGlzIGEgYm9vbGVhbi4KICogQHBhcmFtIHs/fSB2YWwgVmFyaWFibGUgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB2YXJpYWJsZSBpcyBib29sZWFuLgogKiBAZGVwcmVjYXRlZCBVc2UgYHR5cGVvZiB2YWwgPT09ICdib29sZWFuJ2AgaW5zdGVhZC4KICovCmdvb2cuaXNCb29sZWFuID0gZnVuY3Rpb24odmFsKSB7CiAgcmV0dXJuIHR5cGVvZiB2YWwgPT0gJ2Jvb2xlYW4nOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCB2YWx1ZSBpcyBhIG51bWJlci4KICogQHBhcmFtIHs/fSB2YWwgVmFyaWFibGUgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB2YXJpYWJsZSBpcyBhIG51bWJlci4KICogQGRlcHJlY2F0ZWQgVXNlIGB0eXBlb2YgdmFsID09PSAnbnVtYmVyJ2AgaW5zdGVhZC4KICovCmdvb2cuaXNOdW1iZXIgPSBmdW5jdGlvbih2YWwpIHsKICByZXR1cm4gdHlwZW9mIHZhbCA9PSAnbnVtYmVyJzsKfTsKCgovKioKICogQnVpbGRzIGFuIG9iamVjdCBzdHJ1Y3R1cmUgZm9yIHRoZSBwcm92aWRlZCBuYW1lc3BhY2UgcGF0aCwgZW5zdXJpbmcgdGhhdAogKiBuYW1lcyB0aGF0IGFscmVhZHkgZXhpc3QgYXJlIG5vdCBvdmVyd3JpdHRlbi4gRm9yIGV4YW1wbGU6CiAqICJhLmIuYyIgLT4gYSA9IHt9O2EuYj17fTthLmIuYz17fTsKICogVXNlZCBieSBnb29nLnByb3ZpZGUgYW5kIGdvb2cuZXhwb3J0U3ltYm9sLgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBuYW1lIG9mIHRoZSBvYmplY3QgdGhhdCB0aGlzIGZpbGUgZGVmaW5lcy4KICogQHBhcmFtIHsqPX0gb3B0X29iamVjdCB0aGUgb2JqZWN0IHRvIGV4cG9zZSBhdCB0aGUgZW5kIG9mIHRoZSBwYXRoLgogKiBAcGFyYW0ge09iamVjdD19IG9wdF9vYmplY3RUb0V4cG9ydFRvIFRoZSBvYmplY3QgdG8gYWRkIHRoZSBwYXRoIHRvOyBkZWZhdWx0CiAqICAgICBpcyBgZ29vZy5nbG9iYWxgLgogKiBAcHJpdmF0ZQogKi8KZ29vZy5leHBvcnRQYXRoXyA9IGZ1bmN0aW9uKG5hbWUsIG9wdF9vYmplY3QsIG9wdF9vYmplY3RUb0V4cG9ydFRvKSB7CiAgdmFyIHBhcnRzID0gbmFtZS5zcGxpdCgnLicpOwogIHZhciBjdXIgPSBvcHRfb2JqZWN0VG9FeHBvcnRUbyB8fCBnb29nLmdsb2JhbDsKCiAgLy8gSW50ZXJuZXQgRXhwbG9yZXIgZXhoaWJpdHMgc3RyYW5nZSBiZWhhdmlvciB3aGVuIHRocm93aW5nIGVycm9ycyBmcm9tCiAgLy8gbWV0aG9kcyBleHRlcm5lZCBpbiB0aGlzIG1hbm5lci4gIFNlZSB0aGUgdGVzdEV4cG9ydFN5bWJvbEV4Y2VwdGlvbnMgaW4KICAvLyBiYXNlX3Rlc3QuaHRtbCBmb3IgYW4gZXhhbXBsZS4KICBpZiAoIShwYXJ0c1swXSBpbiBjdXIpICYmIHR5cGVvZiBjdXIuZXhlY1NjcmlwdCAhPSAndW5kZWZpbmVkJykgewogICAgY3VyLmV4ZWNTY3JpcHQoJ3ZhciAnICsgcGFydHNbMF0pOwogIH0KCiAgZm9yICh2YXIgcGFydDsgcGFydHMubGVuZ3RoICYmIChwYXJ0ID0gcGFydHMuc2hpZnQoKSk7KSB7CiAgICBpZiAoIXBhcnRzLmxlbmd0aCAmJiBvcHRfb2JqZWN0ICE9PSB1bmRlZmluZWQpIHsKICAgICAgLy8gbGFzdCBwYXJ0IGFuZCB3ZSBoYXZlIGFuIG9iamVjdDsgdXNlIGl0CiAgICAgIGN1cltwYXJ0XSA9IG9wdF9vYmplY3Q7CiAgICB9IGVsc2UgaWYgKGN1cltwYXJ0XSAmJiBjdXJbcGFydF0gIT09IE9iamVjdC5wcm90b3R5cGVbcGFydF0pIHsKICAgICAgY3VyID0gY3VyW3BhcnRdOwogICAgfSBlbHNlIHsKICAgICAgY3VyID0gY3VyW3BhcnRdID0ge307CiAgICB9CiAgfQp9OwoKCi8qKgogKiBEZWZpbmVzIGEgbmFtZWQgdmFsdWUuIEluIHVuY29tcGlsZWQgbW9kZSwgdGhlIHZhbHVlIGlzIHJldHJpZXZlZCBmcm9tCiAqIENMT1NVUkVfREVGSU5FUyBvciBDTE9TVVJFX1VOQ09NUElMRURfREVGSU5FUyBpZiB0aGUgb2JqZWN0IGlzIGRlZmluZWQgYW5kCiAqIGhhcyB0aGUgcHJvcGVydHkgc3BlY2lmaWVkLCBhbmQgb3RoZXJ3aXNlIHVzZWQgdGhlIGRlZmluZWQgZGVmYXVsdFZhbHVlLgogKiBXaGVuIGNvbXBpbGVkIHRoZSBkZWZhdWx0IGNhbiBiZSBvdmVycmlkZGVuIHVzaW5nIHRoZSBjb21waWxlciBvcHRpb25zIG9yIHRoZQogKiB2YWx1ZSBzZXQgaW4gdGhlIENMT1NVUkVfREVGSU5FUyBvYmplY3QuIFJldHVybnMgdGhlIGRlZmluZWQgdmFsdWUgc28gdGhhdCBpdAogKiBjYW4gYmUgdXNlZCBzYWZlbHkgaW4gbW9kdWxlcy4gTm90ZSB0aGF0IHRoZSB2YWx1ZSB0eXBlIE1VU1QgYmUgZWl0aGVyCiAqIGJvb2xlYW4sIG51bWJlciwgb3Igc3RyaW5nLgogKgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBUaGUgZGlzdGluZ3Vpc2hlZCBuYW1lIHRvIHByb3ZpZGUuCiAqIEBwYXJhbSB7VH0gZGVmYXVsdFZhbHVlCiAqIEByZXR1cm4ge1R9IFRoZSBkZWZpbmVkIHZhbHVlLgogKiBAdGVtcGxhdGUgVAogKi8KZ29vZy5kZWZpbmUgPSBmdW5jdGlvbihuYW1lLCBkZWZhdWx0VmFsdWUpIHsKICB2YXIgdmFsdWUgPSBkZWZhdWx0VmFsdWU7CiAgaWYgKCFDT01QSUxFRCkgewogICAgdmFyIHVuY29tcGlsZWREZWZpbmVzID0gZ29vZy5nbG9iYWwuQ0xPU1VSRV9VTkNPTVBJTEVEX0RFRklORVM7CiAgICB2YXIgZGVmaW5lcyA9IGdvb2cuZ2xvYmFsLkNMT1NVUkVfREVGSU5FUzsKICAgIGlmICh1bmNvbXBpbGVkRGVmaW5lcyAmJgogICAgICAgIC8vIEFudGkgRE9NLWNsb2JiZXJpbmcgcnVudGltZSBjaGVjayAoYi8zNzczNjU3NikuCiAgICAgICAgLyoqIEB0eXBlIHs/fSAqLyAodW5jb21waWxlZERlZmluZXMpLm5vZGVUeXBlID09PSB1bmRlZmluZWQgJiYKICAgICAgICBPYmplY3QucHJvdG90eXBlLmhhc093blByb3BlcnR5LmNhbGwodW5jb21waWxlZERlZmluZXMsIG5hbWUpKSB7CiAgICAgIHZhbHVlID0gdW5jb21waWxlZERlZmluZXNbbmFtZV07CiAgICB9IGVsc2UgaWYgKAogICAgICAgIGRlZmluZXMgJiYKICAgICAgICAvLyBBbnRpIERPTS1jbG9iYmVyaW5nIHJ1bnRpbWUgY2hlY2sgKGIvMzc3MzY1NzYpLgogICAgICAgIC8qKiBAdHlwZSB7P30gKi8gKGRlZmluZXMpLm5vZGVUeXBlID09PSB1bmRlZmluZWQgJiYKICAgICAgICBPYmplY3QucHJvdG90eXBlLmhhc093blByb3BlcnR5LmNhbGwoZGVmaW5lcywgbmFtZSkpIHsKICAgICAgdmFsdWUgPSBkZWZpbmVzW25hbWVdOwogICAgfQogIH0KICByZXR1cm4gdmFsdWU7Cn07CgoKLyoqCiAqIEBkZWZpbmUge251bWJlcn0gSW50ZWdlciB5ZWFyIGluZGljYXRpbmcgdGhlIHNldCBvZiBicm93c2VyIGZlYXR1cmVzIHRoYXQgYXJlCiAqIGd1YXJhbnRlZWQgdG8gYmUgcHJlc2VudC4gIFRoaXMgaXMgZGVmaW5lZCB0byBpbmNsdWRlIGV4YWN0bHkgZmVhdHVyZXMgdGhhdAogKiB3b3JrIGNvcnJlY3RseSBvbiBhbGwgIm1vZGVybiIgYnJvd3NlcnMgdGhhdCBhcmUgc3RhYmxlIG9uIEphbnVhcnkgMSBvZiB0aGUKICogc3BlY2lmaWVkIHllYXIuICBGb3IgZXhhbXBsZSwKICogYGBganMKICogaWYgKGdvb2cuRkVBVFVSRVNFVF9ZRUFSID49IDIwMTkpIHsKICogICAvLyB1c2UgQVBJcyBrbm93biB0byBiZSBhdmFpbGFibGUgb24gYWxsIG1ham9yIHN0YWJsZSBicm93c2VycyBKYW4gMSwgMjAxOQogKiB9IGVsc2UgewogKiAgIC8vIHBvbHlmaWxsIGZvciBvbGRlciBicm93c2VycwogKiB9CiAqIGBgYAogKiBUaGlzIGlzIGludGVuZGVkIHRvIGJlIHRoZSBwcmltYXJ5IGRlZmluZSBmb3IgcmVtb3ZpbmcKICogdW5uZWNlc3NhcnkgYnJvd3NlciBjb21wYXRpYmlsaXR5IGNvZGUgKHN1Y2ggYXMgcG9ueWZpbGxzIGFuZCB3b3JrYXJvdW5kcyksCiAqIGFuZCBzaG91bGQgaW5mb3JtIHRoZSBkZWZhdWx0IHZhbHVlIGZvciBtb3N0IG90aGVyIGRlZmluZXM6CiAqIGBgYGpzCiAqIGNvbnN0IEFTU1VNRV9OQVRJVkVfUFJPTUlTRSA9CiAqICAgICBnb29nLmRlZmluZSgnQVNTVU1FX05BVElWRV9QUk9NSVNFJywgZ29vZy5GRUFUVVJFU0VUX1lFQVIgPj0gMjAxNik7CiAqIGBgYAogKgogKiBUaGUgZGVmYXVsdCBhc3N1bXB0aW9uIGlzIHRoYXQgSUU5IGlzIHRoZSBsb3dlc3Qgc3VwcG9ydGVkIGJyb3dzZXIsIHdoaWNoIHdhcwogKiBmaXJzdCBhdmFpbGFibGUgSmFuIDEsIDIwMTIuCiAqCiAqIFRPRE8odXNlcik6IFJlZmVyZW5jZSBtb3JlIHRob3JvdWdoIGRvY3VtZW50YXRpb24gd2hlbiBpdCdzIGF2YWlsYWJsZS4KICovCmdvb2cuRkVBVFVSRVNFVF9ZRUFSID0gZ29vZy5kZWZpbmUoJ2dvb2cuRkVBVFVSRVNFVF9ZRUFSJywgMjAxMik7CgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IERFQlVHIGlzIHByb3ZpZGVkIGFzIGEgY29udmVuaWVuY2Ugc28gdGhhdCBkZWJ1Z2dpbmcgY29kZQogKiB0aGF0IHNob3VsZCBub3QgYmUgaW5jbHVkZWQgaW4gYSBwcm9kdWN0aW9uLiBJdCBjYW4gYmUgZWFzaWx5IHN0cmlwcGVkCiAqIGJ5IHNwZWNpZnlpbmcgLS1kZWZpbmUgZ29vZy5ERUJVRz1mYWxzZSB0byB0aGUgQ2xvc3VyZSBDb21waWxlciBha2EKICogSlNDb21waWxlci4gRm9yIGV4YW1wbGUsIG1vc3QgdG9TdHJpbmcoKSBtZXRob2RzIHNob3VsZCBiZSBkZWNsYXJlZCBpbnNpZGUgYW4KICogImlmIChnb29nLkRFQlVHKSIgY29uZGl0aW9uYWwgYmVjYXVzZSB0aGV5IGFyZSBnZW5lcmFsbHkgdXNlZCBmb3IgZGVidWdnaW5nCiAqIHB1cnBvc2VzIGFuZCBpdCBpcyBkaWZmaWN1bHQgZm9yIHRoZSBKU0NvbXBpbGVyIHRvIHN0YXRpY2FsbHkgZGV0ZXJtaW5lCiAqIHdoZXRoZXIgdGhleSBhcmUgdXNlZC4KICovCmdvb2cuREVCVUcgPSBnb29nLmRlZmluZSgnZ29vZy5ERUJVRycsIHRydWUpOwoKCi8qKgogKiBAZGVmaW5lIHtzdHJpbmd9IExPQ0FMRSBkZWZpbmVzIHRoZSBsb2NhbGUgYmVpbmcgdXNlZCBmb3IgY29tcGlsYXRpb24uIEl0IGlzCiAqIHVzZWQgdG8gc2VsZWN0IGxvY2FsZSBzcGVjaWZpYyBkYXRhIHRvIGJlIGNvbXBpbGVkIGluIGpzIGJpbmFyeS4gQlVJTEQgcnVsZQogKiBjYW4gc3BlY2lmeSB0aGlzIHZhbHVlIGJ5ICItLWRlZmluZSBnb29nLkxPQ0FMRT08bG9jYWxlX25hbWU+IiBhcyBhIGNvbXBpbGVyCiAqIG9wdGlvbi4KICoKICogVGFrZSBpbnRvIGFjY291bnQgdGhhdCB0aGUgbG9jYWxlIGNvZGUgZm9ybWF0IGlzIGltcG9ydGFudC4gWW91IHNob3VsZCB1c2UKICogdGhlIGNhbm9uaWNhbCBVbmljb2RlIGZvcm1hdCB3aXRoIGh5cGhlbiBhcyBhIGRlbGltaXRlci4gTGFuZ3VhZ2UgbXVzdCBiZQogKiBsb3dlcmNhc2UsIExhbmd1YWdlIFNjcmlwdCAtIENhcGl0YWxpemVkLCBSZWdpb24gLSBVUFBFUkNBU0UuCiAqIFRoZXJlIGFyZSBmZXcgZXhhbXBsZXM6IHB0LUJSLCBlbiwgZW4tVVMsIHNyLUxhdGluLUJPLCB6aC1IYW5zLUNOLgogKgogKiBTZWUgbW9yZSBpbmZvIGFib3V0IGxvY2FsZSBjb2RlcyBoZXJlOgogKiBodHRwOi8vd3d3LnVuaWNvZGUub3JnL3JlcG9ydHMvdHIzNS8jVW5pY29kZV9MYW5ndWFnZV9hbmRfTG9jYWxlX0lkZW50aWZpZXJzCiAqCiAqIEZvciBsYW5ndWFnZSBjb2RlcyB5b3Ugc2hvdWxkIHVzZSB2YWx1ZXMgZGVmaW5lZCBieSBJU08gNjkzLTEuIFNlZSBpdCBoZXJlCiAqIGh0dHA6Ly93d3cudzMub3JnL1dBSS9FUi9JRy9lcnQvaXNvNjM5Lmh0bS4gVGhlcmUgaXMgb25seSBvbmUgZXhjZXB0aW9uIGZyb20KICogdGhpcyBydWxlOiB0aGUgSGVicmV3IGxhbmd1YWdlLiBGb3IgbGVnYWN5IHJlYXNvbnMgdGhlIG9sZCBjb2RlIChpdykgc2hvdWxkCiAqIGJlIHVzZWQgaW5zdGVhZCBvZiB0aGUgbmV3IGNvZGUgKGhlKS4KICoKICovCmdvb2cuTE9DQUxFID0gZ29vZy5kZWZpbmUoJ2dvb2cuTE9DQUxFJywgJ2VuJyk7ICAvLyBkZWZhdWx0IHRvIGVuCgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IFdoZXRoZXIgdGhpcyBjb2RlIGlzIHJ1bm5pbmcgb24gdHJ1c3RlZCBzaXRlcy4KICoKICogT24gdW50cnVzdGVkIHNpdGVzLCBzZXZlcmFsIG5hdGl2ZSBmdW5jdGlvbnMgY2FuIGJlIGRlZmluZWQgb3Igb3ZlcnJpZGRlbiBieQogKiBleHRlcm5hbCBsaWJyYXJpZXMgbGlrZSBQcm90b3R5cGUsIERhdGVqcywgYW5kIEpRdWVyeSBhbmQgc2V0dGluZyB0aGlzIGZsYWcKICogdG8gZmFsc2UgZm9yY2VzIGNsb3N1cmUgdG8gdXNlIGl0cyBvd24gaW1wbGVtZW50YXRpb25zIHdoZW4gcG9zc2libGUuCiAqCiAqIElmIHlvdXIgSmF2YVNjcmlwdCBjYW4gYmUgbG9hZGVkIGJ5IGEgdGhpcmQgcGFydHkgc2l0ZSBhbmQgeW91IGFyZSB3YXJ5IGFib3V0CiAqIHJlbHlpbmcgb24gbm9uLXN0YW5kYXJkIGltcGxlbWVudGF0aW9ucywgc3BlY2lmeQogKiAiLS1kZWZpbmUgZ29vZy5UUlVTVEVEX1NJVEU9ZmFsc2UiIHRvIHRoZSBjb21waWxlci4KICovCmdvb2cuVFJVU1RFRF9TSVRFID0gZ29vZy5kZWZpbmUoJ2dvb2cuVFJVU1RFRF9TSVRFJywgdHJ1ZSk7CgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IFdoZXRoZXIgYSBwcm9qZWN0IGlzIGV4cGVjdGVkIHRvIGJlIHJ1bm5pbmcgaW4gc3RyaWN0IG1vZGUuCiAqCiAqIFRoaXMgZGVmaW5lIGNhbiBiZSB1c2VkIHRvIHRyaWdnZXIgYWx0ZXJuYXRlIGltcGxlbWVudGF0aW9ucyBjb21wYXRpYmxlIHdpdGgKICogcnVubmluZyBpbiBFY21hU2NyaXB0IFN0cmljdCBtb2RlIG9yIHdhcm4gYWJvdXQgdW5hdmFpbGFibGUgZnVuY3Rpb25hbGl0eS4KICogQHNlZSBodHRwczovL2dvby5nbC9QdWRRNHkKICoKICovCmdvb2cuU1RSSUNUX01PREVfQ09NUEFUSUJMRSA9IGdvb2cuZGVmaW5lKCdnb29nLlNUUklDVF9NT0RFX0NPTVBBVElCTEUnLCBmYWxzZSk7CgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IFdoZXRoZXIgY29kZSB0aGF0IGNhbGxzIHtAbGluayBnb29nLnNldFRlc3RPbmx5fSBzaG91bGQKICogICAgIGJlIGRpc2FsbG93ZWQgaW4gdGhlIGNvbXBpbGF0aW9uIHVuaXQuCiAqLwpnb29nLkRJU0FMTE9XX1RFU1RfT05MWV9DT0RFID0KICAgIGdvb2cuZGVmaW5lKCdnb29nLkRJU0FMTE9XX1RFU1RfT05MWV9DT0RFJywgQ09NUElMRUQgJiYgIWdvb2cuREVCVUcpOwoKCi8qKgogKiBAZGVmaW5lIHtib29sZWFufSBXaGV0aGVyIHRvIHVzZSBhIENocm9tZSBhcHAgQ1NQLWNvbXBsaWFudCBtZXRob2QgZm9yCiAqICAgICBsb2FkaW5nIHNjcmlwdHMgdmlhIGdvb2cucmVxdWlyZS4gQHNlZSBhcHBlbmRTY3JpcHRTcmNOb2RlXy4KICovCmdvb2cuRU5BQkxFX0NIUk9NRV9BUFBfU0FGRV9TQ1JJUFRfTE9BRElORyA9CiAgICBnb29nLmRlZmluZSgnZ29vZy5FTkFCTEVfQ0hST01FX0FQUF9TQUZFX1NDUklQVF9MT0FESU5HJywgZmFsc2UpOwoKCi8qKgogKiBEZWZpbmVzIGEgbmFtZXNwYWNlIGluIENsb3N1cmUuCiAqCiAqIEEgbmFtZXNwYWNlIG1heSBvbmx5IGJlIGRlZmluZWQgb25jZSBpbiBhIGNvZGViYXNlLiBJdCBtYXkgYmUgZGVmaW5lZCB1c2luZwogKiBnb29nLnByb3ZpZGUoKSBvciBnb29nLm1vZHVsZSgpLgogKgogKiBUaGUgcHJlc2VuY2Ugb2Ygb25lIG9yIG1vcmUgZ29vZy5wcm92aWRlKCkgY2FsbHMgaW4gYSBmaWxlIGluZGljYXRlcwogKiB0aGF0IHRoZSBmaWxlIGRlZmluZXMgdGhlIGdpdmVuIG9iamVjdHMvbmFtZXNwYWNlcy4KICogUHJvdmlkZWQgc3ltYm9scyBtdXN0IG5vdCBiZSBudWxsIG9yIHVuZGVmaW5lZC4KICoKICogSW4gYWRkaXRpb24sIGdvb2cucHJvdmlkZSgpIGNyZWF0ZXMgdGhlIG9iamVjdCBzdHVicyBmb3IgYSBuYW1lc3BhY2UKICogKGZvciBleGFtcGxlLCBnb29nLnByb3ZpZGUoImdvb2cuZm9vLmJhciIpIHdpbGwgY3JlYXRlIHRoZSBvYmplY3QKICogZ29vZy5mb28uYmFyIGlmIGl0IGRvZXMgbm90IGFscmVhZHkgZXhpc3QpLgogKgogKiBCdWlsZCB0b29scyBhbHNvIHNjYW4gZm9yIHByb3ZpZGUvcmVxdWlyZS9tb2R1bGUgc3RhdGVtZW50cwogKiB0byBkaXNjZXJuIGRlcGVuZGVuY2llcywgYnVpbGQgZGVwZW5kZW5jeSBmaWxlcyAoc2VlIGRlcHMuanMpLCBldGMuCiAqCiAqIEBzZWUgZ29vZy5yZXF1aXJlCiAqIEBzZWUgZ29vZy5tb2R1bGUKICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgTmFtZXNwYWNlIHByb3ZpZGVkIGJ5IHRoaXMgZmlsZSBpbiB0aGUgZm9ybQogKiAgICAgImdvb2cucGFja2FnZS5wYXJ0Ii4KICovCmdvb2cucHJvdmlkZSA9IGZ1bmN0aW9uKG5hbWUpIHsKICBpZiAoZ29vZy5pc0luTW9kdWxlTG9hZGVyXygpKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoJ2dvb2cucHJvdmlkZSBjYW5ub3QgYmUgdXNlZCB3aXRoaW4gYSBtb2R1bGUuJyk7CiAgfQogIGlmICghQ09NUElMRUQpIHsKICAgIC8vIEVuc3VyZSB0aGF0IHRoZSBzYW1lIG5hbWVzcGFjZSBpc24ndCBwcm92aWRlZCB0d2ljZS4KICAgIC8vIEEgZ29vZy5tb2R1bGUvZ29vZy5wcm92aWRlIG1hcHMgYSBnb29nLnJlcXVpcmUgdG8gYSBzcGVjaWZpYyBmaWxlCiAgICBpZiAoZ29vZy5pc1Byb3ZpZGVkXyhuYW1lKSkgewogICAgICB0aHJvdyBuZXcgRXJyb3IoJ05hbWVzcGFjZSAiJyArIG5hbWUgKyAnIiBhbHJlYWR5IGRlY2xhcmVkLicpOwogICAgfQogIH0KCiAgZ29vZy5jb25zdHJ1Y3ROYW1lc3BhY2VfKG5hbWUpOwp9OwoKCi8qKgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBOYW1lc3BhY2UgcHJvdmlkZWQgYnkgdGhpcyBmaWxlIGluIHRoZSBmb3JtCiAqICAgICAiZ29vZy5wYWNrYWdlLnBhcnQiLgogKiBAcGFyYW0ge09iamVjdD19IG9wdF9vYmogVGhlIG9iamVjdCB0byBlbWJlZCBpbiB0aGUgbmFtZXNwYWNlLgogKiBAcHJpdmF0ZQogKi8KZ29vZy5jb25zdHJ1Y3ROYW1lc3BhY2VfID0gZnVuY3Rpb24obmFtZSwgb3B0X29iaikgewogIGlmICghQ09NUElMRUQpIHsKICAgIGRlbGV0ZSBnb29nLmltcGxpY2l0TmFtZXNwYWNlc19bbmFtZV07CgogICAgdmFyIG5hbWVzcGFjZSA9IG5hbWU7CiAgICB3aGlsZSAoKG5hbWVzcGFjZSA9IG5hbWVzcGFjZS5zdWJzdHJpbmcoMCwgbmFtZXNwYWNlLmxhc3RJbmRleE9mKCcuJykpKSkgewogICAgICBpZiAoZ29vZy5nZXRPYmplY3RCeU5hbWUobmFtZXNwYWNlKSkgewogICAgICAgIGJyZWFrOwogICAgICB9CiAgICAgIGdvb2cuaW1wbGljaXROYW1lc3BhY2VzX1tuYW1lc3BhY2VdID0gdHJ1ZTsKICAgIH0KICB9CgogIGdvb2cuZXhwb3J0UGF0aF8obmFtZSwgb3B0X29iaik7Cn07CgoKLyoqCiAqIFJldHVybnMgQ1NQIG5vbmNlLCBpZiBzZXQgZm9yIGFueSBzY3JpcHQgdGFnLgogKiBAcGFyYW0gez9XaW5kb3c9fSBvcHRfd2luZG93IFRoZSB3aW5kb3cgY29udGV4dCB1c2VkIHRvIHJldHJpZXZlIHRoZSBub25jZS4KICogICAgIERlZmF1bHRzIHRvIGdsb2JhbCBjb250ZXh0LgogKiBAcmV0dXJuIHtzdHJpbmd9IENTUCBub25jZSBvciBlbXB0eSBzdHJpbmcgaWYgbm8gbm9uY2UgaXMgcHJlc2VudC4KICovCmdvb2cuZ2V0U2NyaXB0Tm9uY2UgPSBmdW5jdGlvbihvcHRfd2luZG93KSB7CiAgaWYgKG9wdF93aW5kb3cgJiYgb3B0X3dpbmRvdyAhPSBnb29nLmdsb2JhbCkgewogICAgcmV0dXJuIGdvb2cuZ2V0U2NyaXB0Tm9uY2VfKG9wdF93aW5kb3cuZG9jdW1lbnQpOwogIH0KICBpZiAoZ29vZy5jc3BOb25jZV8gPT09IG51bGwpIHsKICAgIGdvb2cuY3NwTm9uY2VfID0gZ29vZy5nZXRTY3JpcHROb25jZV8oZ29vZy5nbG9iYWwuZG9jdW1lbnQpOwogIH0KICByZXR1cm4gZ29vZy5jc3BOb25jZV87Cn07CgoKLyoqCiAqIEFjY29yZGluZyB0byB0aGUgQ1NQMyBzcGVjIGEgbm9uY2UgbXVzdCBiZSBhIHZhbGlkIGJhc2U2NCBzdHJpbmcuCiAqIEBzZWUgaHR0cHM6Ly93d3cudzMub3JnL1RSL0NTUDMvI2dyYW1tYXJkZWYtYmFzZTY0LXZhbHVlCiAqIEBwcml2YXRlIEBjb25zdAogKi8KZ29vZy5OT05DRV9QQVRURVJOXyA9IC9eW1x3Ky9fLV0rWz1dezAsMn0kLzsKCgovKioKICogQHByaXZhdGUgez9zdHJpbmd9CiAqLwpnb29nLmNzcE5vbmNlXyA9IG51bGw7CgoKLyoqCiAqIFJldHVybnMgQ1NQIG5vbmNlLCBpZiBzZXQgZm9yIGFueSBzY3JpcHQgdGFnLgogKiBAcGFyYW0geyFEb2N1bWVudH0gZG9jCiAqIEByZXR1cm4ge3N0cmluZ30gQ1NQIG5vbmNlIG9yIGVtcHR5IHN0cmluZyBpZiBubyBub25jZSBpcyBwcmVzZW50LgogKiBAcHJpdmF0ZQogKi8KZ29vZy5nZXRTY3JpcHROb25jZV8gPSBmdW5jdGlvbihkb2MpIHsKICB2YXIgc2NyaXB0ID0gZG9jLnF1ZXJ5U2VsZWN0b3IgJiYgZG9jLnF1ZXJ5U2VsZWN0b3IoJ3NjcmlwdFtub25jZV0nKTsKICBpZiAoc2NyaXB0KSB7CiAgICAvLyBUcnkgdG8gZ2V0IHRoZSBub25jZSBmcm9tIHRoZSBJREwgcHJvcGVydHkgZmlyc3QsIGJlY2F1c2UgYnJvd3NlcnMgdGhhdAogICAgLy8gaW1wbGVtZW50IGFkZGl0aW9uYWwgbm9uY2UgcHJvdGVjdGlvbiBmZWF0dXJlcyAoY3VycmVudGx5IG9ubHkgQ2hyb21lKSB0bwogICAgLy8gcHJldmVudCBub25jZSBzdGVhbGluZyB2aWEgQ1NTIGRvIG5vdCBleHBvc2UgdGhlIG5vbmNlIHZpYSBhdHRyaWJ1dGVzLgogICAgLy8gU2VlIGh0dHBzOi8vZ2l0aHViLmNvbS93aGF0d2cvaHRtbC9pc3N1ZXMvMjM2OQogICAgdmFyIG5vbmNlID0gc2NyaXB0Wydub25jZSddIHx8IHNjcmlwdC5nZXRBdHRyaWJ1dGUoJ25vbmNlJyk7CiAgICBpZiAobm9uY2UgJiYgZ29vZy5OT05DRV9QQVRURVJOXy50ZXN0KG5vbmNlKSkgewogICAgICByZXR1cm4gbm9uY2U7CiAgICB9CiAgfQogIHJldHVybiAnJzsKfTsKCgovKioKICogTW9kdWxlIGlkZW50aWZpZXIgdmFsaWRhdGlvbiByZWdleHAuCiAqIE5vdGU6IFRoaXMgaXMgYSBjb25zZXJ2YXRpdmUgY2hlY2ssIGl0IGlzIHZlcnkgcG9zc2libGUgdG8gYmUgbW9yZSBsZW5pZW50LAogKiAgIHRoZSBwcmltYXJ5IGV4Y2x1c2lvbiBoZXJlIGlzICIvIiBhbmQgIlwiIGFuZCBhIGxlYWRpbmcgIi4iLCB0aGVzZQogKiAgIHJlc3RyaWN0aW9ucyBhcmUgaW50ZW5kZWQgdG8gbGVhdmUgdGhlIGRvb3Igb3BlbiBmb3IgdXNpbmcgZ29vZy5yZXF1aXJlCiAqICAgd2l0aCByZWxhdGl2ZSBmaWxlIHBhdGhzIHJhdGhlciB0aGFuIG1vZHVsZSBpZGVudGlmaWVycy4KICogQHByaXZhdGUKICovCmdvb2cuVkFMSURfTU9EVUxFX1JFXyA9IC9eW2EtekEtWl8kXVthLXpBLVowLTkuXyRdKiQvOwoKCi8qKgogKiBEZWZpbmVzIGEgbW9kdWxlIGluIENsb3N1cmUuCiAqCiAqIE1hcmtzIHRoYXQgdGhpcyBmaWxlIG11c3QgYmUgbG9hZGVkIGFzIGEgbW9kdWxlIGFuZCBjbGFpbXMgdGhlIG5hbWVzcGFjZS4KICoKICogQSBuYW1lc3BhY2UgbWF5IG9ubHkgYmUgZGVmaW5lZCBvbmNlIGluIGEgY29kZWJhc2UuIEl0IG1heSBiZSBkZWZpbmVkIHVzaW5nCiAqIGdvb2cucHJvdmlkZSgpIG9yIGdvb2cubW9kdWxlKCkuCiAqCiAqIGdvb2cubW9kdWxlKCkgaGFzIHRocmVlIHJlcXVpcmVtZW50czoKICogLSBnb29nLm1vZHVsZSBtYXkgbm90IGJlIHVzZWQgaW4gdGhlIHNhbWUgZmlsZSBhcyBnb29nLnByb3ZpZGUuCiAqIC0gZ29vZy5tb2R1bGUgbXVzdCBiZSB0aGUgZmlyc3Qgc3RhdGVtZW50IGluIHRoZSBmaWxlLgogKiAtIG9ubHkgb25lIGdvb2cubW9kdWxlIGlzIGFsbG93ZWQgcGVyIGZpbGUuCiAqCiAqIFdoZW4gYSBnb29nLm1vZHVsZSBhbm5vdGF0ZWQgZmlsZSBpcyBsb2FkZWQsIGl0IGlzIGVuY2xvc2VkIGluCiAqIGEgc3RyaWN0IGZ1bmN0aW9uIGNsb3N1cmUuIFRoaXMgbWVhbnMgdGhhdDoKICogLSBhbnkgdmFyaWFibGVzIGRlY2xhcmVkIGluIGEgZ29vZy5tb2R1bGUgZmlsZSBhcmUgcHJpdmF0ZSB0byB0aGUgZmlsZQogKiAobm90IGdsb2JhbCksIHRob3VnaCB0aGUgY29tcGlsZXIgaXMgZXhwZWN0ZWQgdG8gaW5saW5lIHRoZSBtb2R1bGUuCiAqIC0gVGhlIGNvZGUgbXVzdCBvYmV5IGFsbCB0aGUgcnVsZXMgb2YgInN0cmljdCIgSmF2YVNjcmlwdC4KICogLSB0aGUgZmlsZSB3aWxsIGJlIG1hcmtlZCBhcyAidXNlIHN0cmljdCIKICoKICogTk9URTogdW5saWtlIGdvb2cucHJvdmlkZSwgZ29vZy5tb2R1bGUgZG9lcyBub3QgZGVjbGFyZSBhbnkgc3ltYm9scyBieQogKiBpdHNlbGYuIElmIGRlY2xhcmVkIHN5bWJvbHMgYXJlIGRlc2lyZWQsIHVzZQogKiBnb29nLm1vZHVsZS5kZWNsYXJlTGVnYWN5TmFtZXNwYWNlKCkuCiAqCiAqCiAqIFNlZSB0aGUgcHVibGljIGdvb2cubW9kdWxlIHByb3Bvc2FsOiBodHRwOi8vZ29vLmdsL1ZhMWhpbgogKgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBOYW1lc3BhY2UgcHJvdmlkZWQgYnkgdGhpcyBmaWxlIGluIHRoZSBmb3JtCiAqICAgICAiZ29vZy5wYWNrYWdlLnBhcnQiLCBpcyBleHBlY3RlZCBidXQgbm90IHJlcXVpcmVkLgogKiBAcmV0dXJuIHt2b2lkfQogKi8KZ29vZy5tb2R1bGUgPSBmdW5jdGlvbihuYW1lKSB7CiAgaWYgKHR5cGVvZiBuYW1lICE9PSAnc3RyaW5nJyB8fCAhbmFtZSB8fAogICAgICBuYW1lLnNlYXJjaChnb29nLlZBTElEX01PRFVMRV9SRV8pID09IC0xKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgbW9kdWxlIGlkZW50aWZpZXInKTsKICB9CiAgaWYgKCFnb29nLmlzSW5Hb29nTW9kdWxlTG9hZGVyXygpKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgJ01vZHVsZSAnICsgbmFtZSArICcgaGFzIGJlZW4gbG9hZGVkIGluY29ycmVjdGx5LiBOb3RlLCAnICsKICAgICAgICAnbW9kdWxlcyBjYW5ub3QgYmUgbG9hZGVkIGFzIG5vcm1hbCBzY3JpcHRzLiBUaGV5IHJlcXVpcmUgc29tZSBraW5kIG9mICcgKwogICAgICAgICdwcmUtcHJvY2Vzc2luZyBzdGVwLiBZb3VcJ3JlIGxpa2VseSB0cnlpbmcgdG8gbG9hZCBhIG1vZHVsZSB2aWEgYSAnICsKICAgICAgICAnc2NyaXB0IHRhZyBvciBhcyBhIHBhcnQgb2YgYSBjb25jYXRlbmF0ZWQgYnVuZGxlIHdpdGhvdXQgcmV3cml0aW5nIHRoZSAnICsKICAgICAgICAnbW9kdWxlLiBGb3IgbW9yZSBpbmZvIHNlZTogJyArCiAgICAgICAgJ2h0dHBzOi8vZ2l0aHViLmNvbS9nb29nbGUvY2xvc3VyZS1saWJyYXJ5L3dpa2kvZ29vZy5tb2R1bGU6LWFuLUVTNi1tb2R1bGUtbGlrZS1hbHRlcm5hdGl2ZS10by1nb29nLnByb3ZpZGUuJyk7CiAgfQogIGlmIChnb29nLm1vZHVsZUxvYWRlclN0YXRlXy5tb2R1bGVOYW1lKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoJ2dvb2cubW9kdWxlIG1heSBvbmx5IGJlIGNhbGxlZCBvbmNlIHBlciBtb2R1bGUuJyk7CiAgfQoKICAvLyBTdG9yZSB0aGUgbW9kdWxlIG5hbWUgZm9yIHRoZSBsb2FkZXIuCiAgZ29vZy5tb2R1bGVMb2FkZXJTdGF0ZV8ubW9kdWxlTmFtZSA9IG5hbWU7CiAgaWYgKCFDT01QSUxFRCkgewogICAgLy8gRW5zdXJlIHRoYXQgdGhlIHNhbWUgbmFtZXNwYWNlIGlzbid0IHByb3ZpZGVkIHR3aWNlLgogICAgLy8gQSBnb29nLm1vZHVsZS9nb29nLnByb3ZpZGUgbWFwcyBhIGdvb2cucmVxdWlyZSB0byBhIHNwZWNpZmljIGZpbGUKICAgIGlmIChnb29nLmlzUHJvdmlkZWRfKG5hbWUpKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcignTmFtZXNwYWNlICInICsgbmFtZSArICciIGFscmVhZHkgZGVjbGFyZWQuJyk7CiAgICB9CiAgICBkZWxldGUgZ29vZy5pbXBsaWNpdE5hbWVzcGFjZXNfW25hbWVdOwogIH0KfTsKCgovKioKICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgVGhlIG1vZHVsZSBpZGVudGlmaWVyLgogKiBAcmV0dXJuIHs/fSBUaGUgbW9kdWxlIGV4cG9ydHMgZm9yIGFuIGFscmVhZHkgbG9hZGVkIG1vZHVsZSBvciBudWxsLgogKgogKiBOb3RlOiBUaGlzIGlzIG5vdCBhbiBhbHRlcm5hdGl2ZSB0byBnb29nLnJlcXVpcmUsIGl0IGRvZXMgbm90CiAqIGluZGljYXRlIGEgaGFyZCBkZXBlbmRlbmN5LCBpbnN0ZWFkIGl0IGlzIHVzZWQgdG8gaW5kaWNhdGUKICogYW4gb3B0aW9uYWwgZGVwZW5kZW5jeSBvciB0byBhY2Nlc3MgdGhlIGV4cG9ydHMgb2YgYSBtb2R1bGUKICogdGhhdCBoYXMgYWxyZWFkeSBiZWVuIGxvYWRlZC4KICogQHN1cHByZXNzIHttaXNzaW5nUHJvdmlkZX0KICovCmdvb2cubW9kdWxlLmdldCA9IGZ1bmN0aW9uKG5hbWUpIHsKICByZXR1cm4gZ29vZy5tb2R1bGUuZ2V0SW50ZXJuYWxfKG5hbWUpOwp9OwoKCi8qKgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBUaGUgbW9kdWxlIGlkZW50aWZpZXIuCiAqIEByZXR1cm4gez99IFRoZSBtb2R1bGUgZXhwb3J0cyBmb3IgYW4gYWxyZWFkeSBsb2FkZWQgbW9kdWxlIG9yIG51bGwuCiAqIEBwcml2YXRlCiAqLwpnb29nLm1vZHVsZS5nZXRJbnRlcm5hbF8gPSBmdW5jdGlvbihuYW1lKSB7CiAgaWYgKCFDT01QSUxFRCkgewogICAgaWYgKG5hbWUgaW4gZ29vZy5sb2FkZWRNb2R1bGVzXykgewogICAgICByZXR1cm4gZ29vZy5sb2FkZWRNb2R1bGVzX1tuYW1lXS5leHBvcnRzOwogICAgfSBlbHNlIGlmICghZ29vZy5pbXBsaWNpdE5hbWVzcGFjZXNfW25hbWVdKSB7CiAgICAgIHZhciBucyA9IGdvb2cuZ2V0T2JqZWN0QnlOYW1lKG5hbWUpOwogICAgICByZXR1cm4gbnMgIT0gbnVsbCA/IG5zIDogbnVsbDsKICAgIH0KICB9CiAgcmV0dXJuIG51bGw7Cn07CgoKLyoqCiAqIFR5cGVzIG9mIG1vZHVsZXMgdGhlIGRlYnVnIGxvYWRlciBjYW4gbG9hZC4KICogQGVudW0ge3N0cmluZ30KICovCmdvb2cuTW9kdWxlVHlwZSA9IHsKICBFUzY6ICdlczYnLAogIEdPT0c6ICdnb29nJwp9OwoKCi8qKgogKiBAcHJpdmF0ZSB7P3sKICogICBtb2R1bGVOYW1lOiAoc3RyaW5nfHVuZGVmaW5lZCksCiAqICAgZGVjbGFyZUxlZ2FjeU5hbWVzcGFjZTpib29sZWFuLAogKiAgIHR5cGU6ID9nb29nLk1vZHVsZVR5cGUKICogfX0KICovCmdvb2cubW9kdWxlTG9hZGVyU3RhdGVfID0gbnVsbDsKCgovKioKICogQHByaXZhdGUKICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciBhIGdvb2cubW9kdWxlIG9yIGFuIGVzNiBtb2R1bGUgaXMgY3VycmVudGx5IGJlaW5nCiAqICAgICBpbml0aWFsaXplZC4KICovCmdvb2cuaXNJbk1vZHVsZUxvYWRlcl8gPSBmdW5jdGlvbigpIHsKICByZXR1cm4gZ29vZy5pc0luR29vZ01vZHVsZUxvYWRlcl8oKSB8fCBnb29nLmlzSW5FczZNb2R1bGVMb2FkZXJfKCk7Cn07CgoKLyoqCiAqIEBwcml2YXRlCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgYSBnb29nLm1vZHVsZSBpcyBjdXJyZW50bHkgYmVpbmcgaW5pdGlhbGl6ZWQuCiAqLwpnb29nLmlzSW5Hb29nTW9kdWxlTG9hZGVyXyA9IGZ1bmN0aW9uKCkgewogIHJldHVybiAhIWdvb2cubW9kdWxlTG9hZGVyU3RhdGVfICYmCiAgICAgIGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfLnR5cGUgPT0gZ29vZy5Nb2R1bGVUeXBlLkdPT0c7Cn07CgoKLyoqCiAqIEBwcml2YXRlCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgYW4gZXM2IG1vZHVsZSBpcyBjdXJyZW50bHkgYmVpbmcgaW5pdGlhbGl6ZWQuCiAqLwpnb29nLmlzSW5FczZNb2R1bGVMb2FkZXJfID0gZnVuY3Rpb24oKSB7CiAgdmFyIGluTG9hZGVyID0gISFnb29nLm1vZHVsZUxvYWRlclN0YXRlXyAmJgogICAgICBnb29nLm1vZHVsZUxvYWRlclN0YXRlXy50eXBlID09IGdvb2cuTW9kdWxlVHlwZS5FUzY7CgogIGlmIChpbkxvYWRlcikgewogICAgcmV0dXJuIHRydWU7CiAgfQoKICB2YXIganNjb21wID0gZ29vZy5nbG9iYWxbJyRqc2NvbXAnXTsKCiAgaWYgKGpzY29tcCkgewogICAgLy8ganNjb21wIG1heSBub3QgaGF2ZSBnZXRDdXJyZW50TW9kdWxlUGF0aCBpZiB0aGlzIGlzIGEgY29tcGlsZWQgYnVuZGxlCiAgICAvLyB0aGF0IGhhcyBzb21lIG9mIHRoZSBydW50aW1lLCBidXQgbm90IGFsbCBvZiBpdC4gVGhpcyBjYW4gaGFwcGVuIGlmCiAgICAvLyBvcHRpbWl6YXRpb25zIGFyZSB0dXJuZWQgb24gc28gdGhlIHVudXNlZCBydW50aW1lIGlzIHJlbW92ZWQgYnV0IHJlbmFtaW5nCiAgICAvLyBhbmQgQ2xvc3VyZSBwYXNzIGFyZSBvZmYgKHNvICRqc2NvbXAgaXMgc3RpbGwgbmFtZWQgJGpzY29tcCBhbmQgdGhlCiAgICAvLyBnb29nLnByb3ZpZGUvcmVxdWlyZSBjYWxscyBzdGlsbCBleGlzdCkuCiAgICBpZiAodHlwZW9mIGpzY29tcC5nZXRDdXJyZW50TW9kdWxlUGF0aCAhPSAnZnVuY3Rpb24nKSB7CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KCiAgICAvLyBCdW5kbGVkIEVTNiBtb2R1bGUuCiAgICByZXR1cm4gISFqc2NvbXAuZ2V0Q3VycmVudE1vZHVsZVBhdGgoKTsKICB9CgogIHJldHVybiBmYWxzZTsKfTsKCgovKioKICogUHJvdmlkZSB0aGUgbW9kdWxlJ3MgZXhwb3J0cyBhcyBhIGdsb2JhbGx5IGFjY2Vzc2libGUgb2JqZWN0IHVuZGVyIHRoZQogKiBtb2R1bGUncyBkZWNsYXJlZCBuYW1lLiAgVGhpcyBpcyBpbnRlbmRlZCB0byBlYXNlIG1pZ3JhdGlvbiB0byBnb29nLm1vZHVsZQogKiBmb3IgZmlsZXMgdGhhdCBoYXZlIGV4aXN0aW5nIHVzYWdlcy4KICogQHN1cHByZXNzIHttaXNzaW5nUHJvdmlkZX0KICovCmdvb2cubW9kdWxlLmRlY2xhcmVMZWdhY3lOYW1lc3BhY2UgPSBmdW5jdGlvbigpIHsKICBpZiAoIUNPTVBJTEVEICYmICFnb29nLmlzSW5Hb29nTW9kdWxlTG9hZGVyXygpKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgJ2dvb2cubW9kdWxlLmRlY2xhcmVMZWdhY3lOYW1lc3BhY2UgbXVzdCBiZSBjYWxsZWQgZnJvbSAnICsKICAgICAgICAnd2l0aGluIGEgZ29vZy5tb2R1bGUnKTsKICB9CiAgaWYgKCFDT01QSUxFRCAmJiAhZ29vZy5tb2R1bGVMb2FkZXJTdGF0ZV8ubW9kdWxlTmFtZSkgewogICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICdnb29nLm1vZHVsZSBtdXN0IGJlIGNhbGxlZCBwcmlvciB0byAnICsKICAgICAgICAnZ29vZy5tb2R1bGUuZGVjbGFyZUxlZ2FjeU5hbWVzcGFjZS4nKTsKICB9CiAgZ29vZy5tb2R1bGVMb2FkZXJTdGF0ZV8uZGVjbGFyZUxlZ2FjeU5hbWVzcGFjZSA9IHRydWU7Cn07CgoKLyoqCiAqIEFzc29jaWF0ZXMgYW4gRVM2IG1vZHVsZSB3aXRoIGEgQ2xvc3VyZSBtb2R1bGUgSUQgc28gdGhhdCBpcyBhdmFpbGFibGUgdmlhCiAqIGdvb2cucmVxdWlyZS4gVGhlIGFzc29jaWF0ZWQgSUQgIGFjdHMgbGlrZSBhIGdvb2cubW9kdWxlIElEIC0gaXQgZG9lcyBub3QKICogY3JlYXRlIGFueSBnbG9iYWwgbmFtZXMsIGl0IGlzIG1lcmVseSBhdmFpbGFibGUgdmlhIGdvb2cucmVxdWlyZSAvCiAqIGdvb2cubW9kdWxlLmdldCAvIGdvb2cuZm9yd2FyZERlY2xhcmUgLyBnb29nLnJlcXVpcmVUeXBlLiBnb29nLnJlcXVpcmUgYW5kCiAqIGdvb2cubW9kdWxlLmdldCB3aWxsIHJldHVybiB0aGUgZW50aXJlIG1vZHVsZSBhcyBpZiBpdCB3YXMgaW1wb3J0IConZC4gVGhpcwogKiBhbGxvd3MgQ2xvc3VyZSBmaWxlcyB0byByZWZlcmVuY2UgRVM2IG1vZHVsZXMgZm9yIHRoZSBzYWtlIG9mIG1pZ3JhdGlvbi4KICoKICogQHBhcmFtIHtzdHJpbmd9IG5hbWVzcGFjZQogKiBAc3VwcHJlc3Mge21pc3NpbmdQcm92aWRlfQogKi8KZ29vZy5kZWNsYXJlTW9kdWxlSWQgPSBmdW5jdGlvbihuYW1lc3BhY2UpIHsKICBpZiAoIUNPTVBJTEVEKSB7CiAgICBpZiAoIWdvb2cuaXNJbkVzNk1vZHVsZUxvYWRlcl8oKSkgewogICAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgICAnZ29vZy5kZWNsYXJlTW9kdWxlSWQgbWF5IG9ubHkgYmUgY2FsbGVkIGZyb20gJyArCiAgICAgICAgICAnd2l0aGluIGFuIEVTNiBtb2R1bGUnKTsKICAgIH0KICAgIGlmIChnb29nLm1vZHVsZUxvYWRlclN0YXRlXyAmJiBnb29nLm1vZHVsZUxvYWRlclN0YXRlXy5tb2R1bGVOYW1lKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICdnb29nLmRlY2xhcmVNb2R1bGVJZCBtYXkgb25seSBiZSBjYWxsZWQgb25jZSBwZXIgbW9kdWxlLicpOwogICAgfQogICAgaWYgKG5hbWVzcGFjZSBpbiBnb29nLmxvYWRlZE1vZHVsZXNfKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICdNb2R1bGUgd2l0aCBuYW1lc3BhY2UgIicgKyBuYW1lc3BhY2UgKyAnIiBhbHJlYWR5IGV4aXN0cy4nKTsKICAgIH0KICB9CiAgaWYgKGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfKSB7CiAgICAvLyBOb3QgYnVuZGxlZCAtIGRlYnVnIGxvYWRpbmcuCiAgICBnb29nLm1vZHVsZUxvYWRlclN0YXRlXy5tb2R1bGVOYW1lID0gbmFtZXNwYWNlOwogIH0gZWxzZSB7CiAgICAvLyBCdW5kbGVkIC0gbm90IGRlYnVnIGxvYWRpbmcsIG5vIG1vZHVsZSBsb2FkZXIgc3RhdGUuCiAgICB2YXIganNjb21wID0gZ29vZy5nbG9iYWxbJyRqc2NvbXAnXTsKICAgIGlmICghanNjb21wIHx8IHR5cGVvZiBqc2NvbXAuZ2V0Q3VycmVudE1vZHVsZVBhdGggIT0gJ2Z1bmN0aW9uJykgewogICAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgICAnTW9kdWxlIHdpdGggbmFtZXNwYWNlICInICsgbmFtZXNwYWNlICsKICAgICAgICAgICciIGhhcyBiZWVuIGxvYWRlZCBpbmNvcnJlY3RseS4nKTsKICAgIH0KICAgIHZhciBleHBvcnRzID0ganNjb21wLnJlcXVpcmUoanNjb21wLmdldEN1cnJlbnRNb2R1bGVQYXRoKCkpOwogICAgZ29vZy5sb2FkZWRNb2R1bGVzX1tuYW1lc3BhY2VdID0gewogICAgICBleHBvcnRzOiBleHBvcnRzLAogICAgICB0eXBlOiBnb29nLk1vZHVsZVR5cGUuRVM2LAogICAgICBtb2R1bGVJZDogbmFtZXNwYWNlCiAgICB9OwogIH0KfTsKCgovKioKICogTWFya3MgdGhhdCB0aGUgY3VycmVudCBmaWxlIHNob3VsZCBvbmx5IGJlIHVzZWQgZm9yIHRlc3RpbmcsIGFuZCBuZXZlciBmb3IKICogbGl2ZSBjb2RlIGluIHByb2R1Y3Rpb24uCiAqCiAqIEluIHRoZSBjYXNlIG9mIHVuaXQgdGVzdHMsIHRoZSBtZXNzYWdlIG1heSBvcHRpb25hbGx5IGJlIGFuIGV4YWN0IG5hbWVzcGFjZQogKiBmb3IgdGhlIHRlc3QgKGUuZy4gJ2dvb2cuc3RyaW5nVGVzdCcpLiBUaGUgbGludGVyIHdpbGwgdGhlbiBpZ25vcmUgdGhlIGV4dHJhCiAqIHByb3ZpZGUgKGlmIG5vdCBleHBsaWNpdGx5IGRlZmluZWQgaW4gdGhlIGNvZGUpLgogKgogKiBAcGFyYW0ge3N0cmluZz19IG9wdF9tZXNzYWdlIE9wdGlvbmFsIG1lc3NhZ2UgdG8gYWRkIHRvIHRoZSBlcnJvciB0aGF0J3MKICogICAgIHJhaXNlZCB3aGVuIHVzZWQgaW4gcHJvZHVjdGlvbiBjb2RlLgogKi8KZ29vZy5zZXRUZXN0T25seSA9IGZ1bmN0aW9uKG9wdF9tZXNzYWdlKSB7CiAgaWYgKGdvb2cuRElTQUxMT1dfVEVTVF9PTkxZX0NPREUpIHsKICAgIG9wdF9tZXNzYWdlID0gb3B0X21lc3NhZ2UgfHwgJyc7CiAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgJ0ltcG9ydGluZyB0ZXN0LW9ubHkgY29kZSBpbnRvIG5vbi1kZWJ1ZyBlbnZpcm9ubWVudCcgKwogICAgICAgIChvcHRfbWVzc2FnZSA/ICc6ICcgKyBvcHRfbWVzc2FnZSA6ICcuJykpOwogIH0KfTsKCgovKioKICogRm9yd2FyZCBkZWNsYXJlcyBhIHN5bWJvbC4gVGhpcyBpcyBhbiBpbmRpY2F0aW9uIHRvIHRoZSBjb21waWxlciB0aGF0IHRoZQogKiBzeW1ib2wgbWF5IGJlIHVzZWQgaW4gdGhlIHNvdXJjZSB5ZXQgaXMgbm90IHJlcXVpcmVkIGFuZCBtYXkgbm90IGJlIHByb3ZpZGVkCiAqIGluIGNvbXBpbGF0aW9uLgogKgogKiBUaGUgbW9zdCBjb21tb24gdXNhZ2Ugb2YgZm9yd2FyZCBkZWNsYXJhdGlvbiBpcyBjb2RlIHRoYXQgdGFrZXMgYSB0eXBlIGFzIGEKICogZnVuY3Rpb24gcGFyYW1ldGVyIGJ1dCBkb2VzIG5vdCBuZWVkIHRvIHJlcXVpcmUgaXQuIEJ5IGZvcndhcmQgZGVjbGFyaW5nCiAqIGluc3RlYWQgb2YgcmVxdWlyaW5nLCBubyBoYXJkIGRlcGVuZGVuY3kgaXMgbWFkZSwgYW5kIChpZiBub3QgcmVxdWlyZWQKICogZWxzZXdoZXJlKSB0aGUgbmFtZXNwYWNlIG1heSBuZXZlciBiZSByZXF1aXJlZCBhbmQgdGh1cywgbm90IGJlIHB1bGxlZAogKiBpbnRvIHRoZSBKYXZhU2NyaXB0IGJpbmFyeS4gSWYgaXQgaXMgcmVxdWlyZWQgZWxzZXdoZXJlLCBpdCB3aWxsIGJlIHR5cGUKICogY2hlY2tlZCBhcyBub3JtYWwuCiAqCiAqIEJlZm9yZSB1c2luZyBnb29nLmZvcndhcmREZWNsYXJlLCBwbGVhc2UgcmVhZCB0aGUgZG9jdW1lbnRhdGlvbiBhdAogKiBodHRwczovL2dpdGh1Yi5jb20vZ29vZ2xlL2Nsb3N1cmUtY29tcGlsZXIvd2lraS9CYWQtVHlwZS1Bbm5vdGF0aW9uIHRvCiAqIHVuZGVyc3RhbmQgdGhlIG9wdGlvbnMgYW5kIHRyYWRlb2ZmcyB3aGVuIHdvcmtpbmcgd2l0aCBmb3J3YXJkIGRlY2xhcmF0aW9ucy4KICoKICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgVGhlIG5hbWVzcGFjZSB0byBmb3J3YXJkIGRlY2xhcmUgaW4gdGhlIGZvcm0gb2YKICogICAgICJnb29nLnBhY2thZ2UucGFydCIuCiAqLwpnb29nLmZvcndhcmREZWNsYXJlID0gZnVuY3Rpb24obmFtZSkge307CgoKLyoqCiAqIEZvcndhcmQgZGVjbGFyZSB0eXBlIGluZm9ybWF0aW9uLiBVc2VkIHRvIGFzc2lnbiB0eXBlcyB0byBnb29nLmdsb2JhbAogKiByZWZlcmVuY2VkIG9iamVjdCB0aGF0IHdvdWxkIG90aGVyd2lzZSByZXN1bHQgaW4gdW5rbm93biB0eXBlIHJlZmVyZW5jZXMKICogYW5kIHRodXMgYmxvY2sgcHJvcGVydHkgZGlzYW1iaWd1YXRpb24uCiAqLwpnb29nLmZvcndhcmREZWNsYXJlKCdEb2N1bWVudCcpOwpnb29nLmZvcndhcmREZWNsYXJlKCdIVE1MU2NyaXB0RWxlbWVudCcpOwpnb29nLmZvcndhcmREZWNsYXJlKCdYTUxIdHRwUmVxdWVzdCcpOwoKCmlmICghQ09NUElMRUQpIHsKICAvKioKICAgKiBDaGVjayBpZiB0aGUgZ2l2ZW4gbmFtZSBoYXMgYmVlbiBnb29nLnByb3ZpZGVkLiBUaGlzIHdpbGwgcmV0dXJuIGZhbHNlIGZvcgogICAqIG5hbWVzIHRoYXQgYXJlIGF2YWlsYWJsZSBvbmx5IGFzIGltcGxpY2l0IG5hbWVzcGFjZXMuCiAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgbmFtZSBvZiB0aGUgb2JqZWN0IHRvIGxvb2sgZm9yLgogICAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdGhlIG5hbWUgaGFzIGJlZW4gcHJvdmlkZWQuCiAgICogQHByaXZhdGUKICAgKi8KICBnb29nLmlzUHJvdmlkZWRfID0gZnVuY3Rpb24obmFtZSkgewogICAgcmV0dXJuIChuYW1lIGluIGdvb2cubG9hZGVkTW9kdWxlc18pIHx8CiAgICAgICAgKCFnb29nLmltcGxpY2l0TmFtZXNwYWNlc19bbmFtZV0gJiYgZ29vZy5nZXRPYmplY3RCeU5hbWUobmFtZSkgIT0gbnVsbCk7CiAgfTsKCiAgLyoqCiAgICogTmFtZXNwYWNlcyBpbXBsaWNpdGx5IGRlZmluZWQgYnkgZ29vZy5wcm92aWRlLiBGb3IgZXhhbXBsZSwKICAgKiBnb29nLnByb3ZpZGUoJ2dvb2cuZXZlbnRzLkV2ZW50JykgaW1wbGljaXRseSBkZWNsYXJlcyB0aGF0ICdnb29nJyBhbmQKICAgKiAnZ29vZy5ldmVudHMnIG11c3QgYmUgbmFtZXNwYWNlcy4KICAgKgogICAqIEB0eXBlIHshT2JqZWN0PHN0cmluZywgKGJvb2xlYW58dW5kZWZpbmVkKT59CiAgICogQHByaXZhdGUKICAgKi8KICBnb29nLmltcGxpY2l0TmFtZXNwYWNlc18gPSB7J2dvb2cubW9kdWxlJzogdHJ1ZX07CgogIC8vIE5PVEU6IFdlIGFkZCBnb29nLm1vZHVsZSBhcyBhbiBpbXBsaWNpdCBuYW1lc3BhY2UgYXMgZ29vZy5tb2R1bGUgaXMgZGVmaW5lZAogIC8vIGhlcmUgYW5kIGJlY2F1c2UgdGhlIGV4aXN0aW5nIG1vZHVsZSBwYWNrYWdlIGhhcyBub3QgYmVlbiBtb3ZlZCB5ZXQgb3V0IG9mCiAgLy8gdGhlIGdvb2cubW9kdWxlIG5hbWVzcGFjZS4gVGhpcyBzYXRpc2lmaWVzIGJvdGggdGhlIGRlYnVnIGxvYWRlciBhbmQKICAvLyBhaGVhZC1vZi10aW1lIGRlcGVuZGVuY3kgbWFuYWdlbWVudC4KfQoKCi8qKgogKiBSZXR1cm5zIGFuIG9iamVjdCBiYXNlZCBvbiBpdHMgZnVsbHkgcXVhbGlmaWVkIGV4dGVybmFsIG5hbWUuICBUaGUgb2JqZWN0CiAqIGlzIG5vdCBmb3VuZCBpZiBudWxsIG9yIHVuZGVmaW5lZC4gIElmIHlvdSBhcmUgdXNpbmcgYSBjb21waWxhdGlvbiBwYXNzIHRoYXQKICogcmVuYW1lcyBwcm9wZXJ0eSBuYW1lcyBiZXdhcmUgdGhhdCB1c2luZyB0aGlzIGZ1bmN0aW9uIHdpbGwgbm90IGZpbmQgcmVuYW1lZAogKiBwcm9wZXJ0aWVzLgogKgogKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBUaGUgZnVsbHkgcXVhbGlmaWVkIG5hbWUuCiAqIEBwYXJhbSB7T2JqZWN0PX0gb3B0X29iaiBUaGUgb2JqZWN0IHdpdGhpbiB3aGljaCB0byBsb29rOyBkZWZhdWx0IGlzCiAqICAgICB8Z29vZy5nbG9iYWx8LgogKiBAcmV0dXJuIHs/fSBUaGUgdmFsdWUgKG9iamVjdCBvciBwcmltaXRpdmUpIG9yLCBpZiBub3QgZm91bmQsIG51bGwuCiAqLwpnb29nLmdldE9iamVjdEJ5TmFtZSA9IGZ1bmN0aW9uKG5hbWUsIG9wdF9vYmopIHsKICB2YXIgcGFydHMgPSBuYW1lLnNwbGl0KCcuJyk7CiAgdmFyIGN1ciA9IG9wdF9vYmogfHwgZ29vZy5nbG9iYWw7CiAgZm9yICh2YXIgaSA9IDA7IGkgPCBwYXJ0cy5sZW5ndGg7IGkrKykgewogICAgY3VyID0gY3VyW3BhcnRzW2ldXTsKICAgIGlmIChjdXIgPT0gbnVsbCkgewogICAgICByZXR1cm4gbnVsbDsKICAgIH0KICB9CiAgcmV0dXJuIGN1cjsKfTsKCgovKioKICogR2xvYmFsaXplcyBhIHdob2xlIG5hbWVzcGFjZSwgc3VjaCBhcyBnb29nIG9yIGdvb2cubGFuZy4KICoKICogQHBhcmFtIHshT2JqZWN0fSBvYmogVGhlIG5hbWVzcGFjZSB0byBnbG9iYWxpemUuCiAqIEBwYXJhbSB7T2JqZWN0PX0gb3B0X2dsb2JhbCBUaGUgb2JqZWN0IHRvIGFkZCB0aGUgcHJvcGVydGllcyB0by4KICogQGRlcHJlY2F0ZWQgUHJvcGVydGllcyBtYXkgYmUgZXhwbGljaXRseSBleHBvcnRlZCB0byB0aGUgZ2xvYmFsIHNjb3BlLCBidXQKICogICAgIHRoaXMgc2hvdWxkIG5vIGxvbmdlciBiZSBkb25lIGluIGJ1bGsuCiAqLwpnb29nLmdsb2JhbGl6ZSA9IGZ1bmN0aW9uKG9iaiwgb3B0X2dsb2JhbCkgewogIHZhciBnbG9iYWwgPSBvcHRfZ2xvYmFsIHx8IGdvb2cuZ2xvYmFsOwogIGZvciAodmFyIHggaW4gb2JqKSB7CiAgICBnbG9iYWxbeF0gPSBvYmpbeF07CiAgfQp9OwoKCi8qKgogKiBBZGRzIGEgZGVwZW5kZW5jeSBmcm9tIGEgZmlsZSB0byB0aGUgZmlsZXMgaXQgcmVxdWlyZXMuCiAqIEBwYXJhbSB7c3RyaW5nfSByZWxQYXRoIFRoZSBwYXRoIHRvIHRoZSBqcyBmaWxlLgogKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBwcm92aWRlcyBBbiBhcnJheSBvZiBzdHJpbmdzIHdpdGgKICogICAgIHRoZSBuYW1lcyBvZiB0aGUgb2JqZWN0cyB0aGlzIGZpbGUgcHJvdmlkZXMuCiAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHJlcXVpcmVzIEFuIGFycmF5IG9mIHN0cmluZ3Mgd2l0aAogKiAgICAgdGhlIG5hbWVzIG9mIHRoZSBvYmplY3RzIHRoaXMgZmlsZSByZXF1aXJlcy4KICogQHBhcmFtIHtib29sZWFufCFPYmplY3Q8c3RyaW5nPj19IG9wdF9sb2FkRmxhZ3MgUGFyYW1ldGVycyBpbmRpY2F0aW5nCiAqICAgICBob3cgdGhlIGZpbGUgbXVzdCBiZSBsb2FkZWQuICBUaGUgYm9vbGVhbiAndHJ1ZScgaXMgZXF1aXZhbGVudAogKiAgICAgdG8geydtb2R1bGUnOiAnZ29vZyd9IGZvciBiYWNrd2FyZHMtY29tcGF0aWJpbGl0eS4gIFZhbGlkIHByb3BlcnRpZXMKICogICAgIGFuZCB2YWx1ZXMgaW5jbHVkZSB7J21vZHVsZSc6ICdnb29nJ30gYW5kIHsnbGFuZyc6ICdlczYnfS4KICovCmdvb2cuYWRkRGVwZW5kZW5jeSA9IGZ1bmN0aW9uKHJlbFBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgb3B0X2xvYWRGbGFncykgewogIGlmICghQ09NUElMRUQgJiYgZ29vZy5ERVBFTkRFTkNJRVNfRU5BQkxFRCkgewogICAgZ29vZy5kZWJ1Z0xvYWRlcl8uYWRkRGVwZW5kZW5jeShyZWxQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIG9wdF9sb2FkRmxhZ3MpOwogIH0KfTsKCgoKCi8vIE5PVEUobm5hemUpOiBUaGUgZGVidWcgRE9NIGxvYWRlciB3YXMgaW5jbHVkZWQgaW4gYmFzZS5qcyBhcyBhbiBvcmlnaW5hbCB3YXkKLy8gdG8gZG8gImRlYnVnLW1vZGUiIGRldmVsb3BtZW50LiAgVGhlIGRlcGVuZGVuY3kgc3lzdGVtIGNhbiBzb21ldGltZXMgYmUKLy8gY29uZnVzaW5nLCBhcyBjYW4gdGhlIGRlYnVnIERPTSBsb2FkZXIncyBhc3luY2hyb25vdXMgbmF0dXJlLgovLwovLyBXaXRoIHRoZSBET00gbG9hZGVyLCBhIGNhbGwgdG8gZ29vZy5yZXF1aXJlKCkgaXMgbm90IGJsb2NraW5nIC0tIHRoZSBzY3JpcHQKLy8gd2lsbCBub3QgbG9hZCB1bnRpbCBzb21lIHBvaW50IGFmdGVyIHRoZSBjdXJyZW50IHNjcmlwdC4gIElmIGEgbmFtZXNwYWNlIGlzCi8vIG5lZWRlZCBhdCBydW50aW1lLCBpdCBuZWVkcyB0byBiZSBkZWZpbmVkIGluIGEgcHJldmlvdXMgc2NyaXB0LCBvciBsb2FkZWQgdmlhCi8vIHJlcXVpcmUoKSB3aXRoIGl0cyByZWdpc3RlcmVkIGRlcGVuZGVuY2llcy4KLy8KLy8gVXNlci1kZWZpbmVkIG5hbWVzcGFjZXMgbWF5IG5lZWQgdGhlaXIgb3duIGRlcHMgZmlsZS4gRm9yIGEgcmVmZXJlbmNlIG9uCi8vIGNyZWF0aW5nIGEgZGVwcyBmaWxlLCBzZWU6Ci8vIEV4dGVybmFsbHk6IGh0dHBzOi8vZGV2ZWxvcGVycy5nb29nbGUuY29tL2Nsb3N1cmUvbGlicmFyeS9kb2NzL2RlcHN3cml0ZXIKLy8KLy8gQmVjYXVzZSBvZiBsZWdhY3kgY2xpZW50cywgdGhlIERPTSBsb2FkZXIgY2FuJ3QgYmUgZWFzaWx5IHJlbW92ZWQgZnJvbQovLyBiYXNlLmpzLiAgV29yayB3YXMgZG9uZSB0byBtYWtlIGl0IGRpc2FibGVhYmxlIG9yIHJlcGxhY2VhYmxlIGZvcgovLyBkaWZmZXJlbnQgZW52aXJvbm1lbnRzIChET00tbGVzcyBKYXZhU2NyaXB0IGludGVycHJldGVycyBsaWtlIFJoaW5vIG9yIFY4LAovLyBmb3IgZXhhbXBsZSkuIFNlZSBib290c3RyYXAvIGZvciBtb3JlIGluZm9ybWF0aW9uLgoKCi8qKgogKiBAZGVmaW5lIHtib29sZWFufSBXaGV0aGVyIHRvIGVuYWJsZSB0aGUgZGVidWcgbG9hZGVyLgogKgogKiBJZiBlbmFibGVkLCBhIGNhbGwgdG8gZ29vZy5yZXF1aXJlKCkgd2lsbCBhdHRlbXB0IHRvIGxvYWQgdGhlIG5hbWVzcGFjZSBieQogKiBhcHBlbmRpbmcgYSBzY3JpcHQgdGFnIHRvIHRoZSBET00gKGlmIHRoZSBuYW1lc3BhY2UgaGFzIGJlZW4gcmVnaXN0ZXJlZCkuCiAqCiAqIElmIGRpc2FibGVkLCBnb29nLnJlcXVpcmUoKSB3aWxsIHNpbXBseSBhc3NlcnQgdGhhdCB0aGUgbmFtZXNwYWNlIGhhcyBiZWVuCiAqIHByb3ZpZGVkIChhbmQgZGVwZW5kIG9uIHRoZSBmYWN0IHRoYXQgc29tZSBvdXRzaWRlIHRvb2wgY29ycmVjdGx5IG9yZGVyZWQKICogdGhlIHNjcmlwdCkuCiAqLwpnb29nLkVOQUJMRV9ERUJVR19MT0FERVIgPSBnb29nLmRlZmluZSgnZ29vZy5FTkFCTEVfREVCVUdfTE9BREVSJywgdHJ1ZSk7CgoKLyoqCiAqIEBwYXJhbSB7c3RyaW5nfSBtc2cKICogQHByaXZhdGUKICovCmdvb2cubG9nVG9Db25zb2xlXyA9IGZ1bmN0aW9uKG1zZykgewogIGlmIChnb29nLmdsb2JhbC5jb25zb2xlKSB7CiAgICBnb29nLmdsb2JhbC5jb25zb2xlWydlcnJvciddKG1zZyk7CiAgfQp9OwoKCi8qKgogKiBJbXBsZW1lbnRzIGEgc3lzdGVtIGZvciB0aGUgZHluYW1pYyByZXNvbHV0aW9uIG9mIGRlcGVuZGVuY2llcyB0aGF0IHdvcmtzIGluCiAqIHBhcmFsbGVsIHdpdGggdGhlIEJVSUxEIHN5c3RlbS4KICoKICogTm90ZSB0aGF0IGFsbCBjYWxscyB0byBnb29nLnJlcXVpcmUgd2lsbCBiZSBzdHJpcHBlZCBieSB0aGUgY29tcGlsZXIuCiAqCiAqIEBzZWUgZ29vZy5wcm92aWRlCiAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lc3BhY2UgTmFtZXNwYWNlIChhcyB3YXMgZ2l2ZW4gaW4gZ29vZy5wcm92aWRlLAogKiAgICAgZ29vZy5tb2R1bGUsIG9yIGdvb2cuZGVjbGFyZU1vZHVsZUlkKSBpbiB0aGUgZm9ybQogKiAgICAgImdvb2cucGFja2FnZS5wYXJ0Ii4KICogQHJldHVybiB7P30gSWYgY2FsbGVkIHdpdGhpbiBhIGdvb2cubW9kdWxlIG9yIEVTNiBtb2R1bGUgZmlsZSwgdGhlIGFzc29jaWF0ZWQKICogICAgIG5hbWVzcGFjZSBvciBtb2R1bGUgb3RoZXJ3aXNlIG51bGwuCiAqLwpnb29nLnJlcXVpcmUgPSBmdW5jdGlvbihuYW1lc3BhY2UpIHsKICBpZiAoIUNPTVBJTEVEKSB7CiAgICAvLyBNaWdodCBuZWVkIHRvIGxhenkgbG9hZCBvbiBvbGQgSUUuCiAgICBpZiAoZ29vZy5FTkFCTEVfREVCVUdfTE9BREVSKSB7CiAgICAgIGdvb2cuZGVidWdMb2FkZXJfLnJlcXVlc3RlZChuYW1lc3BhY2UpOwogICAgfQoKICAgIC8vIElmIHRoZSBvYmplY3QgYWxyZWFkeSBleGlzdHMgd2UgZG8gbm90IG5lZWQgdG8gZG8gYW55dGhpbmcuCiAgICBpZiAoZ29vZy5pc1Byb3ZpZGVkXyhuYW1lc3BhY2UpKSB7CiAgICAgIGlmIChnb29nLmlzSW5Nb2R1bGVMb2FkZXJfKCkpIHsKICAgICAgICByZXR1cm4gZ29vZy5tb2R1bGUuZ2V0SW50ZXJuYWxfKG5hbWVzcGFjZSk7CiAgICAgIH0KICAgIH0gZWxzZSBpZiAoZ29vZy5FTkFCTEVfREVCVUdfTE9BREVSKSB7CiAgICAgIHZhciBtb2R1bGVMb2FkZXJTdGF0ZSA9IGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfOwogICAgICBnb29nLm1vZHVsZUxvYWRlclN0YXRlXyA9IG51bGw7CiAgICAgIHRyeSB7CiAgICAgICAgZ29vZy5kZWJ1Z0xvYWRlcl8ubG9hZF8obmFtZXNwYWNlKTsKICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBnb29nLm1vZHVsZUxvYWRlclN0YXRlXyA9IG1vZHVsZUxvYWRlclN0YXRlOwogICAgICB9CiAgICB9CgogICAgcmV0dXJuIG51bGw7CiAgfQp9OwoKCi8qKgogKiBSZXF1aXJlcyBhIHN5bWJvbCBmb3IgaXRzIHR5cGUgaW5mb3JtYXRpb24uIFRoaXMgaXMgYW4gaW5kaWNhdGlvbiB0byB0aGUKICogY29tcGlsZXIgdGhhdCB0aGUgc3ltYm9sIG1heSBhcHBlYXIgaW4gdHlwZSBhbm5vdGF0aW9ucywgeWV0IGl0IGlzIG5vdAogKiByZWZlcmVuY2VkIGF0IHJ1bnRpbWUuCiAqCiAqIFdoZW4gY2FsbGVkIHdpdGhpbiBhIGdvb2cubW9kdWxlIG9yIEVTNiBtb2R1bGUgZmlsZSwgdGhlIHJldHVybiB2YWx1ZSBtYXkgYmUKICogYXNzaWduZWQgdG8gb3IgZGVzdHJ1Y3R1cmVkIGludG8gYSB2YXJpYWJsZSwgYnV0IGl0IG1heSBub3QgYmUgb3RoZXJ3aXNlIHVzZWQKICogaW4gY29kZSBvdXRzaWRlIG9mIGEgdHlwZSBhbm5vdGF0aW9uLgogKgogKiBOb3RlIHRoYXQgYWxsIGNhbGxzIHRvIGdvb2cucmVxdWlyZVR5cGUgd2lsbCBiZSBzdHJpcHBlZCBieSB0aGUgY29tcGlsZXIuCiAqCiAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lc3BhY2UgTmFtZXNwYWNlIChhcyB3YXMgZ2l2ZW4gaW4gZ29vZy5wcm92aWRlLAogKiAgICAgZ29vZy5tb2R1bGUsIG9yIGdvb2cuZGVjbGFyZU1vZHVsZUlkKSBpbiB0aGUgZm9ybQogKiAgICAgImdvb2cucGFja2FnZS5wYXJ0Ii4KICogQHJldHVybiB7P30KICovCmdvb2cucmVxdWlyZVR5cGUgPSBmdW5jdGlvbihuYW1lc3BhY2UpIHsKICAvLyBSZXR1cm4gYW4gZW1wdHkgb2JqZWN0IHNvIHRoYXQgc2luZ2xlLWxldmVsIGRlc3RydWN0dXJpbmcgb2YgdGhlIHJldHVybgogIC8vIHZhbHVlIGRvZXNuJ3QgY3Jhc2ggYXQgcnVudGltZSB3aGVuIHVzaW5nIHRoZSBkZWJ1ZyBsb2FkZXIuIE11bHRpLWxldmVsCiAgLy8gZGVzdHJ1Y3R1cmluZyBpc24ndCBzdXBwb3J0ZWQuCiAgcmV0dXJuIHt9Owp9OwoKCi8qKgogKiBQYXRoIGZvciBpbmNsdWRlZCBzY3JpcHRzLgogKiBAdHlwZSB7c3RyaW5nfQogKi8KZ29vZy5iYXNlUGF0aCA9ICcnOwoKCi8qKgogKiBBIGhvb2sgZm9yIG92ZXJyaWRpbmcgdGhlIGJhc2UgcGF0aC4KICogQHR5cGUge3N0cmluZ3x1bmRlZmluZWR9CiAqLwpnb29nLmdsb2JhbC5DTE9TVVJFX0JBU0VfUEFUSDsKCgovKioKICogV2hldGhlciB0byBhdHRlbXB0IHRvIGxvYWQgQ2xvc3VyZSdzIGRlcHMgZmlsZS4gQnkgZGVmYXVsdCwgd2hlbiB1bmNvbXBpbGVkLAogKiBkZXBzIGZpbGVzIHdpbGwgYXR0ZW1wdCB0byBiZSBsb2FkZWQuCiAqIEB0eXBlIHtib29sZWFufHVuZGVmaW5lZH0KICovCmdvb2cuZ2xvYmFsLkNMT1NVUkVfTk9fREVQUzsKCgovKioKICogQSBmdW5jdGlvbiB0byBpbXBvcnQgYSBzaW5nbGUgc2NyaXB0LiBUaGlzIGlzIG1lYW50IHRvIGJlIG92ZXJyaWRkZW4gd2hlbgogKiBDbG9zdXJlIGlzIGJlaW5nIHJ1biBpbiBub24tSFRNTCBjb250ZXh0cywgc3VjaCBhcyB3ZWIgd29ya2Vycy4gSXQncyBkZWZpbmVkCiAqIGluIHRoZSBnbG9iYWwgc2NvcGUgc28gdGhhdCBpdCBjYW4gYmUgc2V0IGJlZm9yZSBiYXNlLmpzIGlzIGxvYWRlZCwgd2hpY2gKICogYWxsb3dzIGRlcHMuanMgdG8gYmUgaW1wb3J0ZWQgcHJvcGVybHkuCiAqCiAqIFRoZSBmaXJzdCBwYXJhbWV0ZXIgdGhlIHNjcmlwdCBzb3VyY2UsIHdoaWNoIGlzIGEgcmVsYXRpdmUgVVJJLiBUaGUgc2Vjb25kLAogKiBvcHRpb25hbCBwYXJhbWV0ZXIgaXMgdGhlIHNjcmlwdCBjb250ZW50cywgaW4gdGhlIGV2ZW50IHRoZSBzY3JpcHQgbmVlZGVkCiAqIHRyYW5zZm9ybWF0aW9uLiBJdCBzaG91bGQgcmV0dXJuIHRydWUgaWYgdGhlIHNjcmlwdCB3YXMgaW1wb3J0ZWQsIGZhbHNlCiAqIG90aGVyd2lzZS4KICogQHR5cGUgeyhmdW5jdGlvbihzdHJpbmcsIHN0cmluZz0pOiBib29sZWFuKXx1bmRlZmluZWR9CiAqLwpnb29nLmdsb2JhbC5DTE9TVVJFX0lNUE9SVF9TQ1JJUFQ7CgoKLyoqCiAqIE51bGwgZnVuY3Rpb24gdXNlZCBmb3IgZGVmYXVsdCB2YWx1ZXMgb2YgY2FsbGJhY2tzLCBldGMuCiAqIEByZXR1cm4ge3ZvaWR9IE5vdGhpbmcuCiAqLwpnb29nLm51bGxGdW5jdGlvbiA9IGZ1bmN0aW9uKCkge307CgoKLyoqCiAqIFdoZW4gZGVmaW5pbmcgYSBjbGFzcyBGb28gd2l0aCBhbiBhYnN0cmFjdCBtZXRob2QgYmFyKCksIHlvdSBjYW4gZG86CiAqIEZvby5wcm90b3R5cGUuYmFyID0gZ29vZy5hYnN0cmFjdE1ldGhvZAogKgogKiBOb3cgaWYgYSBzdWJjbGFzcyBvZiBGb28gZmFpbHMgdG8gb3ZlcnJpZGUgYmFyKCksIGFuIGVycm9yIHdpbGwgYmUgdGhyb3duCiAqIHdoZW4gYmFyKCkgaXMgaW52b2tlZC4KICoKICogQHR5cGUgeyFGdW5jdGlvbn0KICogQHRocm93cyB7RXJyb3J9IHdoZW4gaW52b2tlZCB0byBpbmRpY2F0ZSB0aGUgbWV0aG9kIHNob3VsZCBiZSBvdmVycmlkZGVuLgogKiBAZGVwcmVjYXRlZCBVc2UgIkBhYnN0cmFjdCIgYW5ub3RhdGlvbiBpbnN0ZWFkIG9mIGdvb2cuYWJzdHJhY3RNZXRob2QgaW4gbmV3CiAqICAgICBjb2RlLiBTZWUKICogICAgIGh0dHBzOi8vZ2l0aHViLmNvbS9nb29nbGUvY2xvc3VyZS1jb21waWxlci93aWtpL0BhYnN0cmFjdC1jbGFzc2VzLWFuZC1tZXRob2RzCiAqLwpnb29nLmFic3RyYWN0TWV0aG9kID0gZnVuY3Rpb24oKSB7CiAgdGhyb3cgbmV3IEVycm9yKCd1bmltcGxlbWVudGVkIGFic3RyYWN0IG1ldGhvZCcpOwp9OwoKCi8qKgogKiBBZGRzIGEgYGdldEluc3RhbmNlYCBzdGF0aWMgbWV0aG9kIHRoYXQgYWx3YXlzIHJldHVybnMgdGhlIHNhbWUKICogaW5zdGFuY2Ugb2JqZWN0LgogKiBAcGFyYW0geyFGdW5jdGlvbn0gY3RvciBUaGUgY29uc3RydWN0b3IgZm9yIHRoZSBjbGFzcyB0byBhZGQgdGhlIHN0YXRpYwogKiAgICAgbWV0aG9kIHRvLgogKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSAnaW5zdGFuY2VfJyBpc24ndCBhIHByb3BlcnR5IG9uICdGdW5jdGlvbicKICogICAgIGJ1dCB3ZSBkb24ndCBoYXZlIGEgYmV0dGVyIHR5cGUgdG8gdXNlIGhlcmUuCiAqLwpnb29nLmFkZFNpbmdsZXRvbkdldHRlciA9IGZ1bmN0aW9uKGN0b3IpIHsKICAvLyBpbnN0YW5jZV8gaXMgaW1tZWRpYXRlbHkgc2V0IHRvIHByZXZlbnQgaXNzdWVzIHdpdGggc2VhbGVkIGNvbnN0cnVjdG9ycwogIC8vIHN1Y2ggYXMgYXJlIGVuY291bnRlcmVkIHdoZW4gYSBjb25zdHJ1Y3RvciBpcyByZXR1cm5lZCBhcyB0aGUgZXhwb3J0IG9iamVjdAogIC8vIG9mIGEgZ29vZy5tb2R1bGUgaW4gdW5vcHRpbWl6ZWQgY29kZS4KICAvLyBEZWxjYXJlIHR5cGUgdG8gYXZvaWQgY29uZm9ybWFuY2UgdmlvbGF0aW9ucyB0aGF0IGN0b3IuaW5zdGFuY2VfIGlzIHVua25vd24KICAvKiogQHR5cGUge3VuZGVmaW5lZHwhT2JqZWN0fSBAc3VwcHJlc3Mge3VuZGVyc2NvcmV9ICovCiAgY3Rvci5pbnN0YW5jZV8gPSB1bmRlZmluZWQ7CiAgY3Rvci5nZXRJbnN0YW5jZSA9IGZ1bmN0aW9uKCkgewogICAgaWYgKGN0b3IuaW5zdGFuY2VfKSB7CiAgICAgIHJldHVybiBjdG9yLmluc3RhbmNlXzsKICAgIH0KICAgIGlmIChnb29nLkRFQlVHKSB7CiAgICAgIC8vIE5PVEU6IEpTQ29tcGlsZXIgY2FuJ3Qgb3B0aW1pemUgYXdheSBBcnJheSNwdXNoLgogICAgICBnb29nLmluc3RhbnRpYXRlZFNpbmdsZXRvbnNfW2dvb2cuaW5zdGFudGlhdGVkU2luZ2xldG9uc18ubGVuZ3RoXSA9IGN0b3I7CiAgICB9CiAgICAvLyBDYXN0IHRvIGF2b2lkIGNvbmZvcm1hbmNlIHZpb2xhdGlvbnMgdGhhdCBjdG9yLmluc3RhbmNlXyBpcyB1bmtub3duCiAgICByZXR1cm4gLyoqIEB0eXBlIHshT2JqZWN0fHVuZGVmaW5lZH0gKi8gKGN0b3IuaW5zdGFuY2VfKSA9IG5ldyBjdG9yOwogIH07Cn07CgoKLyoqCiAqIEFsbCBzaW5nbGV0b24gY2xhc3NlcyB0aGF0IGhhdmUgYmVlbiBpbnN0YW50aWF0ZWQsIGZvciB0ZXN0aW5nLiBEb24ndCByZWFkCiAqIGl0IGRpcmVjdGx5LCB1c2UgdGhlIGBnb29nLnRlc3Rpbmcuc2luZ2xldG9uYCBtb2R1bGUuIFRoZSBjb21waWxlcgogKiByZW1vdmVzIHRoaXMgdmFyaWFibGUgaWYgdW51c2VkLgogKiBAdHlwZSB7IUFycmF5PCFGdW5jdGlvbj59CiAqIEBwcml2YXRlCiAqLwpnb29nLmluc3RhbnRpYXRlZFNpbmdsZXRvbnNfID0gW107CgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IFdoZXRoZXIgdG8gbG9hZCBnb29nLm1vZHVsZXMgdXNpbmcgYGV2YWxgIHdoZW4gdXNpbmcKICogdGhlIGRlYnVnIGxvYWRlci4gIFRoaXMgcHJvdmlkZXMgYSBiZXR0ZXIgZGVidWdnaW5nIGV4cGVyaWVuY2UgYXMgdGhlCiAqIHNvdXJjZSBpcyB1bm1vZGlmaWVkIGFuZCBjYW4gYmUgZWRpdGVkIHVzaW5nIENocm9tZSBXb3Jrc3BhY2VzIG9yIHNpbWlsYXIuCiAqIEhvd2V2ZXIgaW4gc29tZSBlbnZpcm9ubWVudHMgdGhlIHVzZSBvZiBgZXZhbGAgaXMgYmFubmVkCiAqIHNvIHdlIHByb3ZpZGUgYW4gYWx0ZXJuYXRpdmUuCiAqLwpnb29nLkxPQURfTU9EVUxFX1VTSU5HX0VWQUwgPSBnb29nLmRlZmluZSgnZ29vZy5MT0FEX01PRFVMRV9VU0lOR19FVkFMJywgdHJ1ZSk7CgoKLyoqCiAqIEBkZWZpbmUge2Jvb2xlYW59IFdoZXRoZXIgdGhlIGV4cG9ydHMgb2YgZ29vZy5tb2R1bGVzIHNob3VsZCBiZSBzZWFsZWQgd2hlbgogKiBwb3NzaWJsZS4KICovCmdvb2cuU0VBTF9NT0RVTEVfRVhQT1JUUyA9IGdvb2cuZGVmaW5lKCdnb29nLlNFQUxfTU9EVUxFX0VYUE9SVFMnLCBnb29nLkRFQlVHKTsKCgovKioKICogVGhlIHJlZ2lzdHJ5IG9mIGluaXRpYWxpemVkIG1vZHVsZXM6CiAqIFRoZSBtb2R1bGUgaWRlbnRpZmllciBvciBwYXRoIHRvIG1vZHVsZSBleHBvcnRzIG1hcC4KICogQHByaXZhdGUgQGNvbnN0IHshT2JqZWN0PHN0cmluZywge2V4cG9ydHM6Pyx0eXBlOnN0cmluZyxtb2R1bGVJZDpzdHJpbmd9Pn0KICovCmdvb2cubG9hZGVkTW9kdWxlc18gPSB7fTsKCgovKioKICogVHJ1ZSBpZiB0aGUgZGVidWcgbG9hZGVyIGVuYWJsZWQgYW5kIHVzZWQuCiAqIEBjb25zdCB7Ym9vbGVhbn0KICovCmdvb2cuREVQRU5ERU5DSUVTX0VOQUJMRUQgPSAhQ09NUElMRUQgJiYgZ29vZy5FTkFCTEVfREVCVUdfTE9BREVSOwoKCi8qKgogKiBAZGVmaW5lIHtzdHJpbmd9IEhvdyB0byBkZWNpZGUgd2hldGhlciB0byB0cmFuc3BpbGUuICBWYWxpZCB2YWx1ZXMKICogYXJlICdhbHdheXMnLCAnbmV2ZXInLCBhbmQgJ2RldGVjdCcuICBUaGUgZGVmYXVsdCAoJ2RldGVjdCcpIGlzIHRvCiAqIHVzZSBmZWF0dXJlIGRldGVjdGlvbiB0byBkZXRlcm1pbmUgd2hpY2ggbGFuZ3VhZ2UgbGV2ZWxzIG5lZWQKICogdHJhbnNwaWxhdGlvbi4KICovCi8vIE5PVEUoc2RoKTogd2UgY291bGQgZXhwYW5kIHRoaXMgdG8gYWNjZXB0IGEgbGFuZ3VhZ2UgbGV2ZWwgdG8gYnlwYXNzCi8vIGRldGVjdGlvbjogZS5nLiBnb29nLlRSQU5TUElMRSA9PSAnZXM1JyB3b3VsZCB0cmFuc3BpbGUgRVM2IGZpbGVzIGJ1dAovLyB3b3VsZCBsZWF2ZSBFUzMgYW5kIEVTNSBmaWxlcyBhbG9uZS4KZ29vZy5UUkFOU1BJTEUgPSBnb29nLmRlZmluZSgnZ29vZy5UUkFOU1BJTEUnLCAnZGV0ZWN0Jyk7CgovKioKICogQGRlZmluZSB7Ym9vbGVhbn0gSWYgdHJ1ZSBhc3N1bWUgdGhhdCBFUyBtb2R1bGVzIGhhdmUgYWxyZWFkeSBiZWVuCiAqIHRyYW5zcGlsZWQgYnkgdGhlIGpzY29tcGlsZXIgKGluIHRoZSBzYW1lIHdheSB0aGF0IHRyYW5zcGlsZS5qcyB3b3VsZAogKiB0cmFuc3BpbGUgdGhlbSAtIHRvIGpzY29tcCBtb2R1bGVzKS4gVXNlZnVsIG9ubHkgZm9yIHNlcnZlcnMgdGhhdCB3aXNoIHRvIHVzZQogKiB0aGUgZGVidWcgbG9hZGVyIGFuZCB0cmFuc3BpbGUgc2VydmVyIHNpZGUuIFRodXMgdGhpcyBpcyBvbmx5IHJlc3BlY3RlZCBpZgogKiBnb29nLlRSQU5TUElMRSBpcyAibmV2ZXIiLgogKi8KZ29vZy5BU1NVTUVfRVNfTU9EVUxFU19UUkFOU1BJTEVEID0KICAgIGdvb2cuZGVmaW5lKCdnb29nLkFTU1VNRV9FU19NT0RVTEVTX1RSQU5TUElMRUQnLCBmYWxzZSk7CgoKLyoqCiAqIEBkZWZpbmUge3N0cmluZ30gSWYgYSBmaWxlIG5lZWRzIHRvIGJlIHRyYW5zcGlsZWQgd2hhdCB0aGUgb3V0cHV0IGxhbmd1YWdlCiAqIHNob3VsZCBiZS4gQnkgZGVmYXVsdCB0aGlzIGlzIHRoZSBoaWdoZXN0IGxhbmd1YWdlIGxldmVsIHRoaXMgZmlsZSBkZXRlY3RzCiAqIHRoZSBjdXJyZW50IGVudmlyb25tZW50IHN1cHBvcnRzLiBHZW5lcmFsbHkgdGhpcyBmbGFnIHNob3VsZCBub3QgYmUgc2V0LCBidXQKICogaXQgY291bGQgYmUgdXNlZnVsIHRvIG92ZXJyaWRlLiBFeGFtcGxlOiBJZiB0aGUgY3VycmVudCBlbnZpcm9ubWVudCBzdXBwb3J0cwogKiBFUzYgdGhlbiBieSBkZWZhdWx0IEVTNysgZmlsZXMgd2lsbCBiZSB0cmFuc3BpbGVkIHRvIEVTNiwgdW5sZXNzIHRoaXMgaXMKICogb3ZlcnJpZGRlbi4KICoKICogVmFsaWQgdmFsdWVzIGluY2x1ZGU6IGVzMywgZXM1LCBlczYsIGVzNywgYW5kIGVzOC4gQW55dGhpbmcgbm90IHJlY29nbml6ZWQKICogaXMgdHJlYXRlZCBhcyBlczMuCiAqCiAqIE5vdGUgdGhhdCBzZXR0aW5nIHRoaXMgdmFsdWUgZG9lcyBub3QgZm9yY2UgdHJhbnNwaWxhdGlvbi4gSnVzdCBpZgogKiB0cmFuc3BpbGF0aW9uIG9jY3VycyB0aGlzIHdpbGwgYmUgdGhlIG91dHB1dC4gU28gdGhpcyBpcyBtb3N0IHVzZWZ1bCB3aGVuCiAqIGdvb2cuVFJBTlNQSUxFIGlzIHNldCB0byAnYWx3YXlzJyBhbmQgdGhlbiBmb3JjaW5nIHRoZSBsYW5ndWFnZSBsZXZlbCB0byBiZQogKiBzb21ldGhpbmcgbG93ZXIgdGhhbiB3aGF0IHRoZSBlbnZpcm9ubWVudCBkZXRlY3RzLgogKi8KZ29vZy5UUkFOU1BJTEVfVE9fTEFOR1VBR0UgPSBnb29nLmRlZmluZSgnZ29vZy5UUkFOU1BJTEVfVE9fTEFOR1VBR0UnLCAnJyk7CgoKLyoqCiAqIEBkZWZpbmUge3N0cmluZ30gUGF0aCB0byB0aGUgdHJhbnNwaWxlci4gIEV4ZWN1dGluZyB0aGUgc2NyaXB0IGF0IHRoaXMKICogcGF0aCAocmVsYXRpdmUgdG8gYmFzZS5qcykgc2hvdWxkIGRlZmluZSBhIGZ1bmN0aW9uICRqc2NvbXAudHJhbnNwaWxlLgogKi8KZ29vZy5UUkFOU1BJTEVSID0gZ29vZy5kZWZpbmUoJ2dvb2cuVFJBTlNQSUxFUicsICd0cmFuc3BpbGUuanMnKTsKCgovKioKICogQHBhY2thZ2Ugez9ib29sZWFufQogKiBWaXNpYmxlIGZvciB0ZXN0aW5nLgogKi8KZ29vZy5oYXNCYWRMZXRTY29waW5nID0gbnVsbDsKCgovKioKICogQHJldHVybiB7Ym9vbGVhbn0KICogQHBhY2thZ2UgVmlzaWJsZSBmb3IgdGVzdGluZy4KICovCmdvb2cudXNlU2FmYXJpMTBXb3JrYXJvdW5kID0gZnVuY3Rpb24oKSB7CiAgaWYgKGdvb2cuaGFzQmFkTGV0U2NvcGluZyA9PSBudWxsKSB7CiAgICB2YXIgaGFzQmFkTGV0U2NvcGluZzsKICAgIHRyeSB7CiAgICAgIGhhc0JhZExldFNjb3BpbmcgPSAhZXZhbCgKICAgICAgICAgICcidXNlIHN0cmljdCI7JyArCiAgICAgICAgICAnbGV0IHggPSAxOyBmdW5jdGlvbiBmKCkgeyByZXR1cm4gdHlwZW9mIHg7IH07JyArCiAgICAgICAgICAnZigpID09ICJudW1iZXIiOycpOwogICAgfSBjYXRjaCAoZSkgewogICAgICAvLyBBc3N1bWUgdGhhdCBFUzYgc3ludGF4IGlzbid0IHN1cHBvcnRlZC4KICAgICAgaGFzQmFkTGV0U2NvcGluZyA9IGZhbHNlOwogICAgfQogICAgZ29vZy5oYXNCYWRMZXRTY29waW5nID0gaGFzQmFkTGV0U2NvcGluZzsKICB9CiAgcmV0dXJuIGdvb2cuaGFzQmFkTGV0U2NvcGluZzsKfTsKCgovKioKICogQHBhcmFtIHtzdHJpbmd9IG1vZHVsZURlZgogKiBAcmV0dXJuIHtzdHJpbmd9CiAqIEBwYWNrYWdlIFZpc2libGUgZm9yIHRlc3RpbmcuCiAqLwpnb29nLndvcmthcm91bmRTYWZhcmkxMEV2YWxCdWcgPSBmdW5jdGlvbihtb2R1bGVEZWYpIHsKICByZXR1cm4gJyhmdW5jdGlvbigpeycgKyBtb2R1bGVEZWYgKwogICAgICAnXG4nICsgIC8vIFRlcm1pbmF0ZSBhbnkgdHJhaWxpbmcgc2luZ2xlIGxpbmUgY29tbWVudC4KICAgICAgJzsnICsgICAvLyBUZXJtaW5hdGUgYW55IHRyYWlsaW5nIGV4cHJlc3Npb24uCiAgICAgICd9KSgpO1xuJzsKfTsKCgovKioKICogQHBhcmFtIHtmdW5jdGlvbig/KTo/fHN0cmluZ30gbW9kdWxlRGVmIFRoZSBtb2R1bGUgZGVmaW5pdGlvbi4KICovCmdvb2cubG9hZE1vZHVsZSA9IGZ1bmN0aW9uKG1vZHVsZURlZikgewogIC8vIE5PVEU6IHdlIGFsbG93IGZ1bmN0aW9uIGRlZmluaXRpb25zIHRvIGJlIGVpdGhlciBpbiB0aGUgZnJvbQogIC8vIG9mIGEgc3RyaW5nIHRvIGV2YWwgKHdoaWNoIGtlZXBzIHRoZSBvcmlnaW5hbCBzb3VyY2UgaW50YWN0KSBvcgogIC8vIGluIGEgZXZhbCBmb3JiaWRkZW4gZW52aXJvbm1lbnQgKENTUCkgd2UgYWxsb3cgYSBmdW5jdGlvbiBkZWZpbml0aW9uCiAgLy8gd2hpY2ggaW4gaXRzIGJvZHkgbXVzdCBjYWxsIGBnb29nLm1vZHVsZWAsIGFuZCByZXR1cm4gdGhlIGV4cG9ydHMKICAvLyBvZiB0aGUgbW9kdWxlLgogIHZhciBwcmV2aW91c1N0YXRlID0gZ29vZy5tb2R1bGVMb2FkZXJTdGF0ZV87CiAgdHJ5IHsKICAgIGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfID0gewogICAgICBtb2R1bGVOYW1lOiAnJywKICAgICAgZGVjbGFyZUxlZ2FjeU5hbWVzcGFjZTogZmFsc2UsCiAgICAgIHR5cGU6IGdvb2cuTW9kdWxlVHlwZS5HT09HCiAgICB9OwogICAgdmFyIGV4cG9ydHM7CiAgICBpZiAoZ29vZy5pc0Z1bmN0aW9uKG1vZHVsZURlZikpIHsKICAgICAgZXhwb3J0cyA9IG1vZHVsZURlZi5jYWxsKHVuZGVmaW5lZCwge30pOwogICAgfSBlbHNlIGlmICh0eXBlb2YgbW9kdWxlRGVmID09PSAnc3RyaW5nJykgewogICAgICBpZiAoZ29vZy51c2VTYWZhcmkxMFdvcmthcm91bmQoKSkgewogICAgICAgIG1vZHVsZURlZiA9IGdvb2cud29ya2Fyb3VuZFNhZmFyaTEwRXZhbEJ1Zyhtb2R1bGVEZWYpOwogICAgICB9CgogICAgICBleHBvcnRzID0gZ29vZy5sb2FkTW9kdWxlRnJvbVNvdXJjZV8uY2FsbCh1bmRlZmluZWQsIG1vZHVsZURlZik7CiAgICB9IGVsc2UgewogICAgICB0aHJvdyBuZXcgRXJyb3IoJ0ludmFsaWQgbW9kdWxlIGRlZmluaXRpb24nKTsKICAgIH0KCiAgICB2YXIgbW9kdWxlTmFtZSA9IGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfLm1vZHVsZU5hbWU7CiAgICBpZiAodHlwZW9mIG1vZHVsZU5hbWUgPT09ICdzdHJpbmcnICYmIG1vZHVsZU5hbWUpIHsKICAgICAgLy8gRG9uJ3Qgc2VhbCBsZWdhY3kgbmFtZXNwYWNlcyBhcyB0aGV5IG1heSBiZSB1c2VkIGFzIGEgcGFyZW50IG9mCiAgICAgIC8vIGFub3RoZXIgbmFtZXNwYWNlCiAgICAgIGlmIChnb29nLm1vZHVsZUxvYWRlclN0YXRlXy5kZWNsYXJlTGVnYWN5TmFtZXNwYWNlKSB7CiAgICAgICAgZ29vZy5jb25zdHJ1Y3ROYW1lc3BhY2VfKG1vZHVsZU5hbWUsIGV4cG9ydHMpOwogICAgICB9IGVsc2UgaWYgKAogICAgICAgICAgZ29vZy5TRUFMX01PRFVMRV9FWFBPUlRTICYmIE9iamVjdC5zZWFsICYmCiAgICAgICAgICB0eXBlb2YgZXhwb3J0cyA9PSAnb2JqZWN0JyAmJiBleHBvcnRzICE9IG51bGwpIHsKICAgICAgICBPYmplY3Quc2VhbChleHBvcnRzKTsKICAgICAgfQoKICAgICAgdmFyIGRhdGEgPSB7CiAgICAgICAgZXhwb3J0czogZXhwb3J0cywKICAgICAgICB0eXBlOiBnb29nLk1vZHVsZVR5cGUuR09PRywKICAgICAgICBtb2R1bGVJZDogZ29vZy5tb2R1bGVMb2FkZXJTdGF0ZV8ubW9kdWxlTmFtZQogICAgICB9OwogICAgICBnb29nLmxvYWRlZE1vZHVsZXNfW21vZHVsZU5hbWVdID0gZGF0YTsKICAgIH0gZWxzZSB7CiAgICAgIHRocm93IG5ldyBFcnJvcignSW52YWxpZCBtb2R1bGUgbmFtZSBcIicgKyBtb2R1bGVOYW1lICsgJ1wiJyk7CiAgICB9CiAgfSBmaW5hbGx5IHsKICAgIGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfID0gcHJldmlvdXNTdGF0ZTsKICB9Cn07CgoKLyoqCiAqIEBwcml2YXRlIEBjb25zdAogKi8KZ29vZy5sb2FkTW9kdWxlRnJvbVNvdXJjZV8gPSAvKiogQHR5cGUge2Z1bmN0aW9uKHN0cmluZyk6P30gKi8gKGZ1bmN0aW9uKCkgewogIC8vIE5PVEU6IHdlIGF2b2lkIGRlY2xhcmluZyBwYXJhbWV0ZXJzIG9yIGxvY2FsIHZhcmlhYmxlcyBoZXJlIHRvIGF2b2lkCiAgLy8gbWFza2luZyBnbG9iYWxzIG9yIGxlYWtpbmcgdmFsdWVzIGludG8gdGhlIG1vZHVsZSBkZWZpbml0aW9uLgogICd1c2Ugc3RyaWN0JzsKICB2YXIgZXhwb3J0cyA9IHt9OwogIGV2YWwoYXJndW1lbnRzWzBdKTsKICByZXR1cm4gZXhwb3J0czsKfSk7CgoKLyoqCiAqIE5vcm1hbGl6ZSBhIGZpbGUgcGF0aCBieSByZW1vdmluZyByZWR1bmRhbnQgIi4uIiBhbmQgZXh0cmFuZW91cyAiLiIgZmlsZQogKiBwYXRoIGNvbXBvbmVudHMuCiAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoCiAqIEByZXR1cm4ge3N0cmluZ30KICogQHByaXZhdGUKICovCmdvb2cubm9ybWFsaXplUGF0aF8gPSBmdW5jdGlvbihwYXRoKSB7CiAgdmFyIGNvbXBvbmVudHMgPSBwYXRoLnNwbGl0KCcvJyk7CiAgdmFyIGkgPSAwOwogIHdoaWxlIChpIDwgY29tcG9uZW50cy5sZW5ndGgpIHsKICAgIGlmIChjb21wb25lbnRzW2ldID09ICcuJykgewogICAgICBjb21wb25lbnRzLnNwbGljZShpLCAxKTsKICAgIH0gZWxzZSBpZiAoCiAgICAgICAgaSAmJiBjb21wb25lbnRzW2ldID09ICcuLicgJiYgY29tcG9uZW50c1tpIC0gMV0gJiYKICAgICAgICBjb21wb25lbnRzW2kgLSAxXSAhPSAnLi4nKSB7CiAgICAgIGNvbXBvbmVudHMuc3BsaWNlKC0taSwgMik7CiAgICB9IGVsc2UgewogICAgICBpKys7CiAgICB9CiAgfQogIHJldHVybiBjb21wb25lbnRzLmpvaW4oJy8nKTsKfTsKCgovKioKICogUHJvdmlkZXMgYSBob29rIGZvciBsb2FkaW5nIGEgZmlsZSB3aGVuIHVzaW5nIENsb3N1cmUncyBnb29nLnJlcXVpcmUoKSBBUEkKICogd2l0aCBnb29nLm1vZHVsZXMuICBJbiBwYXJ0aWN1bGFyIHRoaXMgaG9vayBpcyBwcm92aWRlZCB0byBzdXBwb3J0IE5vZGUuanMuCiAqCiAqIEB0eXBlIHsoZnVuY3Rpb24oc3RyaW5nKTpzdHJpbmcpfHVuZGVmaW5lZH0KICovCmdvb2cuZ2xvYmFsLkNMT1NVUkVfTE9BRF9GSUxFX1NZTkM7CgoKLyoqCiAqIExvYWRzIGZpbGUgYnkgc3luY2hyb25vdXMgWEhSLiBTaG91bGQgbm90IGJlIHVzZWQgaW4gcHJvZHVjdGlvbiBlbnZpcm9ubWVudHMuCiAqIEBwYXJhbSB7c3RyaW5nfSBzcmMgU291cmNlIFVSTC4KICogQHJldHVybiB7P3N0cmluZ30gRmlsZSBjb250ZW50cywgb3IgbnVsbCBpZiBsb2FkIGZhaWxlZC4KICogQHByaXZhdGUKICovCmdvb2cubG9hZEZpbGVTeW5jXyA9IGZ1bmN0aW9uKHNyYykgewogIGlmIChnb29nLmdsb2JhbC5DTE9TVVJFX0xPQURfRklMRV9TWU5DKSB7CiAgICByZXR1cm4gZ29vZy5nbG9iYWwuQ0xPU1VSRV9MT0FEX0ZJTEVfU1lOQyhzcmMpOwogIH0gZWxzZSB7CiAgICB0cnkgewogICAgICAvKiogQHR5cGUge1hNTEh0dHBSZXF1ZXN0fSAqLwogICAgICB2YXIgeGhyID0gbmV3IGdvb2cuZ2xvYmFsWydYTUxIdHRwUmVxdWVzdCddKCk7CiAgICAgIHhoci5vcGVuKCdnZXQnLCBzcmMsIGZhbHNlKTsKICAgICAgeGhyLnNlbmQoKTsKICAgICAgLy8gTk9URTogU3VjY2Vzc2Z1bCBodHRwOiByZXF1ZXN0cyBoYXZlIGEgc3RhdHVzIG9mIDIwMCwgYnV0IHN1Y2Nlc3NmdWwKICAgICAgLy8gZmlsZTogcmVxdWVzdHMgbWF5IGhhdmUgYSBzdGF0dXMgb2YgemVyby4gIEFueSBvdGhlciBzdGF0dXMsIG9yIGEKICAgICAgLy8gdGhyb3duIGV4Y2VwdGlvbiAocGFydGljdWxhcmx5IGluIGNhc2Ugb2YgZmlsZTogcmVxdWVzdHMpIGluZGljYXRlcwogICAgICAvLyBzb21lIHNvcnQgb2YgZXJyb3IsIHdoaWNoIHdlIHRyZWF0IGFzIGEgbWlzc2luZyBvciB1bmF2YWlsYWJsZSBmaWxlLgogICAgICByZXR1cm4geGhyLnN0YXR1cyA9PSAwIHx8IHhoci5zdGF0dXMgPT0gMjAwID8geGhyLnJlc3BvbnNlVGV4dCA6IG51bGw7CiAgICB9IGNhdGNoIChlcnIpIHsKICAgICAgLy8gTm8gbmVlZCB0byByZXRocm93IG9yIGxvZywgc2luY2UgZXJyb3JzIHNob3VsZCBzaG93IHVwIG9uIHRoZWlyIG93bi4KICAgICAgcmV0dXJuIG51bGw7CiAgICB9CiAgfQp9OwoKCi8qKgogKiBMYXppbHkgcmV0cmlldmVzIHRoZSB0cmFuc3BpbGVyIGFuZCBhcHBsaWVzIGl0IHRvIHRoZSBzb3VyY2UuCiAqIEBwYXJhbSB7c3RyaW5nfSBjb2RlIEpTIGNvZGUuCiAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFBhdGggdG8gdGhlIGNvZGUuCiAqIEBwYXJhbSB7c3RyaW5nfSB0YXJnZXQgTGFuZ3VhZ2UgbGV2ZWwgb3V0cHV0LgogKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSB0cmFuc3BpbGVkIGNvZGUuCiAqIEBwcml2YXRlCiAqLwpnb29nLnRyYW5zcGlsZV8gPSBmdW5jdGlvbihjb2RlLCBwYXRoLCB0YXJnZXQpIHsKICB2YXIganNjb21wID0gZ29vZy5nbG9iYWxbJyRqc2NvbXAnXTsKICBpZiAoIWpzY29tcCkgewogICAgZ29vZy5nbG9iYWxbJyRqc2NvbXAnXSA9IGpzY29tcCA9IHt9OwogIH0KICB2YXIgdHJhbnNwaWxlID0ganNjb21wLnRyYW5zcGlsZTsKICBpZiAoIXRyYW5zcGlsZSkgewogICAgdmFyIHRyYW5zcGlsZXJQYXRoID0gZ29vZy5iYXNlUGF0aCArIGdvb2cuVFJBTlNQSUxFUjsKICAgIHZhciB0cmFuc3BpbGVyQ29kZSA9IGdvb2cubG9hZEZpbGVTeW5jXyh0cmFuc3BpbGVyUGF0aCk7CiAgICBpZiAodHJhbnNwaWxlckNvZGUpIHsKICAgICAgLy8gVGhpcyBtdXN0IGJlIGV4ZWN1dGVkIHN5bmNocm9ub3VzbHksIHNpbmNlIGJ5IHRoZSB0aW1lIHdlIGtub3cgd2UKICAgICAgLy8gbmVlZCBpdCwgd2UncmUgYWJvdXQgdG8gbG9hZCBhbmQgd3JpdGUgdGhlIEVTNiBjb2RlIHN5bmNocm9ub3VzbHksCiAgICAgIC8vIHNvIGEgbm9ybWFsIHNjcmlwdC10YWcgbG9hZCB3aWxsIGJlIHRvbyBzbG93LiBXcmFwcGVkIGluIGEgZnVuY3Rpb24KICAgICAgLy8gc28gdGhhdCBjb2RlIGlzIGV2YWwnZCBpbiB0aGUgZ2xvYmFsIHNjb3BlLgogICAgICAoZnVuY3Rpb24oKSB7CiAgICAgICAgKDAsIGV2YWwpKHRyYW5zcGlsZXJDb2RlICsgJ1xuLy8jIHNvdXJjZVVSTD0nICsgdHJhbnNwaWxlclBhdGgpOwogICAgICB9KS5jYWxsKGdvb2cuZ2xvYmFsKTsKICAgICAgLy8gRXZlbiB0aG91Z2ggdGhlIHRyYW5zcGlsZXIgaXMgb3B0aW9uYWwsIGlmICRnd3RFeHBvcnQgaXMgZm91bmQsIGl0J3MKICAgICAgLy8gYSBzaWduIHRoZSB0cmFuc3BpbGVyIHdhcyBsb2FkZWQgYW5kIHRoZSAkanNjb21wLnRyYW5zcGlsZSAqc2hvdWxkKgogICAgICAvLyBiZSB0aGVyZS4KICAgICAgaWYgKGdvb2cuZ2xvYmFsWyckZ3d0RXhwb3J0J10gJiYgZ29vZy5nbG9iYWxbJyRnd3RFeHBvcnQnXVsnJGpzY29tcCddICYmCiAgICAgICAgICAhZ29vZy5nbG9iYWxbJyRnd3RFeHBvcnQnXVsnJGpzY29tcCddWyd0cmFuc3BpbGUnXSkgewogICAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICAgJ1RoZSB0cmFuc3BpbGVyIGRpZCBub3QgcHJvcGVybHkgZXhwb3J0IHRoZSAidHJhbnNwaWxlIiAnICsKICAgICAgICAgICAgJ21ldGhvZC4gJGd3dEV4cG9ydDogJyArIEpTT04uc3RyaW5naWZ5KGdvb2cuZ2xvYmFsWyckZ3d0RXhwb3J0J10pKTsKICAgICAgfQogICAgICAvLyB0cmFuc3BpbGUuanMgb25seSBleHBvcnRzIGEgc2luZ2xlICRqc2NvbXAgZnVuY3Rpb24sIHRyYW5zcGlsZS4gV2UKICAgICAgLy8gZ3JhYiBqdXN0IHRoYXQgYW5kIGFkZCBpdCB0byB0aGUgZXhpc3RpbmcgZGVmaW5pdGlvbiBvZiAkanNjb21wIHdoaWNoCiAgICAgIC8vIGNvbnRhaW5zIHRoZSBwb2x5ZmlsbHMuCiAgICAgIGdvb2cuZ2xvYmFsWyckanNjb21wJ10udHJhbnNwaWxlID0KICAgICAgICAgIGdvb2cuZ2xvYmFsWyckZ3d0RXhwb3J0J11bJyRqc2NvbXAnXVsndHJhbnNwaWxlJ107CiAgICAgIGpzY29tcCA9IGdvb2cuZ2xvYmFsWyckanNjb21wJ107CiAgICAgIHRyYW5zcGlsZSA9IGpzY29tcC50cmFuc3BpbGU7CiAgICB9CiAgfQogIGlmICghdHJhbnNwaWxlKSB7CiAgICAvLyBUaGUgdHJhbnNwaWxlciBpcyBhbiBvcHRpb25hbCBjb21wb25lbnQuICBJZiBpdCdzIG5vdCBhdmFpbGFibGUgdGhlbgogICAgLy8gcmVwbGFjZSBpdCB3aXRoIGEgcGFzcy10aHJvdWdoIGZ1bmN0aW9uIHRoYXQgc2ltcGx5IGxvZ3MuCiAgICB2YXIgc3VmZml4ID0gJyByZXF1aXJlcyB0cmFuc3BpbGF0aW9uIGJ1dCBubyB0cmFuc3BpbGVyIHdhcyBmb3VuZC4nOwogICAgdHJhbnNwaWxlID0ganNjb21wLnRyYW5zcGlsZSA9IGZ1bmN0aW9uKGNvZGUsIHBhdGgpIHsKICAgICAgLy8gVE9ETyhzZGgpOiBmaWd1cmUgb3V0IHNvbWUgd2F5IHRvIGdldCB0aGlzIGVycm9yIHRvIHNob3cgdXAKICAgICAgLy8gaW4gdGVzdCByZXN1bHRzLCBub3RpbmcgdGhhdCB0aGUgZmFpbHVyZSBtYXkgb2NjdXIgaW4gbWFueQogICAgICAvLyBkaWZmZXJlbnQgd2F5cywgaW5jbHVkaW5nIGluIGxvYWRNb2R1bGUoKSBiZWZvcmUgdGhlIHRlc3QKICAgICAgLy8gcnVubmVyIGV2ZW4gY29tZXMgdXAuCiAgICAgIGdvb2cubG9nVG9Db25zb2xlXyhwYXRoICsgc3VmZml4KTsKICAgICAgcmV0dXJuIGNvZGU7CiAgICB9OwogIH0KICAvLyBOb3RlOiBhbnkgdHJhbnNwaWxhdGlvbiBlcnJvcnMvd2FybmluZ3Mgd2lsbCBiZSBsb2dnZWQgdG8gdGhlIGNvbnNvbGUuCiAgcmV0dXJuIHRyYW5zcGlsZShjb2RlLCBwYXRoLCB0YXJnZXQpOwp9OwoKLy89PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLy8gTGFuZ3VhZ2UgRW5oYW5jZW1lbnRzCi8vPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09CgoKLyoqCiAqIFRoaXMgaXMgYSAiZml4ZWQiIHZlcnNpb24gb2YgdGhlIHR5cGVvZiBvcGVyYXRvci4gIEl0IGRpZmZlcnMgZnJvbSB0aGUgdHlwZW9mCiAqIG9wZXJhdG9yIGluIHN1Y2ggYSB3YXkgdGhhdCBudWxsIHJldHVybnMgJ251bGwnIGFuZCBhcnJheXMgcmV0dXJuICdhcnJheScuCiAqIEBwYXJhbSB7P30gdmFsdWUgVGhlIHZhbHVlIHRvIGdldCB0aGUgdHlwZSBvZi4KICogQHJldHVybiB7c3RyaW5nfSBUaGUgbmFtZSBvZiB0aGUgdHlwZS4KICovCmdvb2cudHlwZU9mID0gZnVuY3Rpb24odmFsdWUpIHsKICB2YXIgcyA9IHR5cGVvZiB2YWx1ZTsKICBpZiAocyA9PSAnb2JqZWN0JykgewogICAgaWYgKHZhbHVlKSB7CiAgICAgIC8vIENoZWNrIHRoZXNlIGZpcnN0LCBzbyB3ZSBjYW4gYXZvaWQgY2FsbGluZyBPYmplY3QucHJvdG90eXBlLnRvU3RyaW5nIGlmCiAgICAgIC8vIHBvc3NpYmxlLgogICAgICAvLwogICAgICAvLyBJRSBpbXByb3Blcmx5IG1hcnNoYWxzIHR5cGVvZiBhY3Jvc3MgZXhlY3V0aW9uIGNvbnRleHRzLCBidXQgYQogICAgICAvLyBjcm9zcy1jb250ZXh0IG9iamVjdCB3aWxsIHN0aWxsIHJldHVybiBmYWxzZSBmb3IgImluc3RhbmNlb2YgT2JqZWN0Ii4KICAgICAgaWYgKHZhbHVlIGluc3RhbmNlb2YgQXJyYXkpIHsKICAgICAgICByZXR1cm4gJ2FycmF5JzsKICAgICAgfSBlbHNlIGlmICh2YWx1ZSBpbnN0YW5jZW9mIE9iamVjdCkgewogICAgICAgIHJldHVybiBzOwogICAgICB9CgogICAgICAvLyBIQUNLOiBJbiBvcmRlciB0byB1c2UgYW4gT2JqZWN0IHByb3RvdHlwZSBtZXRob2Qgb24gdGhlIGFyYml0cmFyeQogICAgICAvLyAgIHZhbHVlLCB0aGUgY29tcGlsZXIgcmVxdWlyZXMgdGhlIHZhbHVlIGJlIGNhc3QgdG8gdHlwZSBPYmplY3QsCiAgICAgIC8vICAgZXZlbiB0aG91Z2ggdGhlIEVDTUEgc3BlYyBleHBsaWNpdGx5IGFsbG93cyBpdC4KICAgICAgdmFyIGNsYXNzTmFtZSA9IE9iamVjdC5wcm90b3R5cGUudG9TdHJpbmcuY2FsbCgKICAgICAgICAgIC8qKiBAdHlwZSB7IU9iamVjdH0gKi8gKHZhbHVlKSk7CiAgICAgIC8vIEluIEZpcmVmb3ggMy42LCBhdHRlbXB0aW5nIHRvIGFjY2VzcyBpZnJhbWUgd2luZG93IG9iamVjdHMnIGxlbmd0aAogICAgICAvLyBwcm9wZXJ0eSB0aHJvd3MgYW4gTlNfRVJST1JfRkFJTFVSRSwgc28gd2UgbmVlZCB0byBzcGVjaWFsLWNhc2UgaXQKICAgICAgLy8gaGVyZS4KICAgICAgaWYgKGNsYXNzTmFtZSA9PSAnW29iamVjdCBXaW5kb3ddJykgewogICAgICAgIHJldHVybiAnb2JqZWN0JzsKICAgICAgfQoKICAgICAgLy8gV2UgY2Fubm90IGFsd2F5cyB1c2UgY29uc3RydWN0b3IgPT0gQXJyYXkgb3IgaW5zdGFuY2VvZiBBcnJheSBiZWNhdXNlCiAgICAgIC8vIGRpZmZlcmVudCBmcmFtZXMgaGF2ZSBkaWZmZXJlbnQgQXJyYXkgb2JqZWN0cy4gSW4gSUU2LCBpZiB0aGUgaWZyYW1lCiAgICAgIC8vIHdoZXJlIHRoZSBhcnJheSB3YXMgY3JlYXRlZCBpcyBkZXN0cm95ZWQsIHRoZSBhcnJheSBsb3NlcyBpdHMKICAgICAgLy8gcHJvdG90eXBlLiBUaGVuIGRlcmVmZXJlbmNpbmcgdmFsLnNwbGljZSBoZXJlIHRocm93cyBhbiBleGNlcHRpb24sIHNvCiAgICAgIC8vIHdlIGNhbid0IHVzZSBnb29nLmlzRnVuY3Rpb24uIENhbGxpbmcgdHlwZW9mIGRpcmVjdGx5IHJldHVybnMgJ3Vua25vd24nCiAgICAgIC8vIHNvIHRoYXQgd2lsbCB3b3JrLiBJbiB0aGlzIGNhc2UsIHRoaXMgZnVuY3Rpb24gd2lsbCByZXR1cm4gZmFsc2UgYW5kCiAgICAgIC8vIG1vc3QgYXJyYXkgZnVuY3Rpb25zIHdpbGwgc3RpbGwgd29yayBiZWNhdXNlIHRoZSBhcnJheSBpcyBzdGlsbAogICAgICAvLyBhcnJheS1saWtlIChzdXBwb3J0cyBsZW5ndGggYW5kIFtdKSBldmVuIHRob3VnaCBpdCBoYXMgbG9zdCBpdHMKICAgICAgLy8gcHJvdG90eXBlLgogICAgICAvLyBNYXJrIE1pbGxlciBub3RpY2VkIHRoYXQgT2JqZWN0LnByb3RvdHlwZS50b1N0cmluZwogICAgICAvLyBhbGxvd3MgYWNjZXNzIHRvIHRoZSB1bmZvcmdlYWJsZSBbW0NsYXNzXV0gcHJvcGVydHkuCiAgICAgIC8vICAxNS4yLjQuMiBPYmplY3QucHJvdG90eXBlLnRvU3RyaW5nICggKQogICAgICAvLyAgV2hlbiB0aGUgdG9TdHJpbmcgbWV0aG9kIGlzIGNhbGxlZCwgdGhlIGZvbGxvd2luZyBzdGVwcyBhcmUgdGFrZW46CiAgICAgIC8vICAgICAgMS4gR2V0IHRoZSBbW0NsYXNzXV0gcHJvcGVydHkgb2YgdGhpcyBvYmplY3QuCiAgICAgIC8vICAgICAgMi4gQ29tcHV0ZSBhIHN0cmluZyB2YWx1ZSBieSBjb25jYXRlbmF0aW5nIHRoZSB0aHJlZSBzdHJpbmdzCiAgICAgIC8vICAgICAgICAgIltvYmplY3QgIiwgUmVzdWx0KDEpLCBhbmQgIl0iLgogICAgICAvLyAgICAgIDMuIFJldHVybiBSZXN1bHQoMikuCiAgICAgIC8vIGFuZCB0aGlzIGJlaGF2aW9yIHN1cnZpdmVzIHRoZSBkZXN0cnVjdGlvbiBvZiB0aGUgZXhlY3V0aW9uIGNvbnRleHQuCiAgICAgIGlmICgoY2xhc3NOYW1lID09ICdbb2JqZWN0IEFycmF5XScgfHwKICAgICAgICAgICAvLyBJbiBJRSBhbGwgbm9uIHZhbHVlIHR5cGVzIGFyZSB3cmFwcGVkIGFzIG9iamVjdHMgYWNyb3NzIHdpbmRvdwogICAgICAgICAgIC8vIGJvdW5kYXJpZXMgKG5vdCBpZnJhbWUgdGhvdWdoKSBzbyB3ZSBoYXZlIHRvIGRvIG9iamVjdCBkZXRlY3Rpb24KICAgICAgICAgICAvLyBmb3IgdGhpcyBlZGdlIGNhc2UuCiAgICAgICAgICAgdHlwZW9mIHZhbHVlLmxlbmd0aCA9PSAnbnVtYmVyJyAmJgogICAgICAgICAgICAgICB0eXBlb2YgdmFsdWUuc3BsaWNlICE9ICd1bmRlZmluZWQnICYmCiAgICAgICAgICAgICAgIHR5cGVvZiB2YWx1ZS5wcm9wZXJ0eUlzRW51bWVyYWJsZSAhPSAndW5kZWZpbmVkJyAmJgogICAgICAgICAgICAgICAhdmFsdWUucHJvcGVydHlJc0VudW1lcmFibGUoJ3NwbGljZScpCgogICAgICAgICAgICAgICApKSB7CiAgICAgICAgcmV0dXJuICdhcnJheSc7CiAgICAgIH0KICAgICAgLy8gSEFDSzogVGhlcmUgaXMgc3RpbGwgYW4gYXJyYXkgY2FzZSB0aGF0IGZhaWxzLgogICAgICAvLyAgICAgZnVuY3Rpb24gQXJyYXlJbXBvc3RvcigpIHt9CiAgICAgIC8vICAgICBBcnJheUltcG9zdG9yLnByb3RvdHlwZSA9IFtdOwogICAgICAvLyAgICAgdmFyIGltcG9zdG9yID0gbmV3IEFycmF5SW1wb3N0b3I7CiAgICAgIC8vIHRoaXMgY2FuIGJlIGZpeGVkIGJ5IGdldHRpbmcgcmlkIG9mIHRoZSBmYXN0IHBhdGgKICAgICAgLy8gKHZhbHVlIGluc3RhbmNlb2YgQXJyYXkpIGFuZCBzb2xlbHkgcmVseWluZyBvbgogICAgICAvLyAodmFsdWUgJiYgT2JqZWN0LnByb3RvdHlwZS50b1N0cmluZy52YWxsKHZhbHVlKSA9PT0gJ1tvYmplY3QgQXJyYXldJykKICAgICAgLy8gYnV0IHRoYXQgd291bGQgcmVxdWlyZSBtYW55IG1vcmUgZnVuY3Rpb24gY2FsbHMgYW5kIGlzIG5vdCB3YXJyYW50ZWQKICAgICAgLy8gdW5sZXNzIGNsb3N1cmUgY29kZSBpcyByZWNlaXZpbmcgb2JqZWN0cyBmcm9tIHVudHJ1c3RlZCBzb3VyY2VzLgoKICAgICAgLy8gSUUgaW4gY3Jvc3Mtd2luZG93IGNhbGxzIGRvZXMgbm90IGNvcnJlY3RseSBtYXJzaGFsIHRoZSBmdW5jdGlvbiB0eXBlCiAgICAgIC8vIChpdCBhcHBlYXJzIGp1c3QgYXMgYW4gb2JqZWN0KSBzbyB3ZSBjYW5ub3QgdXNlIGp1c3QgdHlwZW9mIHZhbCA9PQogICAgICAvLyAnZnVuY3Rpb24nLiBIb3dldmVyLCBpZiB0aGUgb2JqZWN0IGhhcyBhIGNhbGwgcHJvcGVydHksIGl0IGlzIGEKICAgICAgLy8gZnVuY3Rpb24uCiAgICAgIGlmICgoY2xhc3NOYW1lID09ICdbb2JqZWN0IEZ1bmN0aW9uXScgfHwKICAgICAgICAgICB0eXBlb2YgdmFsdWUuY2FsbCAhPSAndW5kZWZpbmVkJyAmJgogICAgICAgICAgICAgICB0eXBlb2YgdmFsdWUucHJvcGVydHlJc0VudW1lcmFibGUgIT0gJ3VuZGVmaW5lZCcgJiYKICAgICAgICAgICAgICAgIXZhbHVlLnByb3BlcnR5SXNFbnVtZXJhYmxlKCdjYWxsJykpKSB7CiAgICAgICAgcmV0dXJuICdmdW5jdGlvbic7CiAgICAgIH0KCiAgICB9IGVsc2UgewogICAgICByZXR1cm4gJ251bGwnOwogICAgfQoKICB9IGVsc2UgaWYgKHMgPT0gJ2Z1bmN0aW9uJyAmJiB0eXBlb2YgdmFsdWUuY2FsbCA9PSAndW5kZWZpbmVkJykgewogICAgLy8gSW4gU2FmYXJpIHR5cGVvZiBub2RlTGlzdCByZXR1cm5zICdmdW5jdGlvbicsIGFuZCBvbiBGaXJlZm94IHR5cGVvZgogICAgLy8gYmVoYXZlcyBzaW1pbGFybHkgZm9yIEhUTUx7QXBwbGV0LEVtYmVkLE9iamVjdH0sIEVsZW1lbnRzIGFuZCBSZWdFeHBzLiBXZQogICAgLy8gd291bGQgbGlrZSB0byByZXR1cm4gb2JqZWN0IGZvciB0aG9zZSBhbmQgd2UgY2FuIGRldGVjdCBhbiBpbnZhbGlkCiAgICAvLyBmdW5jdGlvbiBieSBtYWtpbmcgc3VyZSB0aGF0IHRoZSBmdW5jdGlvbiBvYmplY3QgaGFzIGEgY2FsbCBtZXRob2QuCiAgICByZXR1cm4gJ29iamVjdCc7CiAgfQogIHJldHVybiBzOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCB2YWx1ZSBpcyBudWxsLgogKiBAcGFyYW0gez99IHZhbCBWYXJpYWJsZSB0byB0ZXN0LgogKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHZhcmlhYmxlIGlzIG51bGwuCiAqIEBkZXByZWNhdGVkIFVzZSBgdmFsID09PSBudWxsYCBpbnN0ZWFkLgogKi8KZ29vZy5pc051bGwgPSBmdW5jdGlvbih2YWwpIHsKICByZXR1cm4gdmFsID09PSBudWxsOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCB2YWx1ZSBpcyBkZWZpbmVkIGFuZCBub3QgbnVsbC4KICogQHBhcmFtIHs/fSB2YWwgVmFyaWFibGUgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB2YXJpYWJsZSBpcyBkZWZpbmVkIGFuZCBub3QgbnVsbC4KICogQGRlcHJlY2F0ZWQgVXNlIGB2YWwgIT0gbnVsbGAgaW5zdGVhZC4KICovCmdvb2cuaXNEZWZBbmROb3ROdWxsID0gZnVuY3Rpb24odmFsKSB7CiAgLy8gTm90ZSB0aGF0IHVuZGVmaW5lZCA9PSBudWxsLgogIHJldHVybiB2YWwgIT0gbnVsbDsKfTsKCgovKioKICogUmV0dXJucyB0cnVlIGlmIHRoZSBzcGVjaWZpZWQgdmFsdWUgaXMgYW4gYXJyYXkuCiAqIEBwYXJhbSB7P30gdmFsIFZhcmlhYmxlIHRvIHRlc3QuCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdmFyaWFibGUgaXMgYW4gYXJyYXkuCiAqLwpnb29nLmlzQXJyYXkgPSBmdW5jdGlvbih2YWwpIHsKICByZXR1cm4gZ29vZy50eXBlT2YodmFsKSA9PSAnYXJyYXknOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIG9iamVjdCBsb29rcyBsaWtlIGFuIGFycmF5LiBUbyBxdWFsaWZ5IGFzIGFycmF5IGxpa2UKICogdGhlIHZhbHVlIG5lZWRzIHRvIGJlIGVpdGhlciBhIE5vZGVMaXN0IG9yIGFuIG9iamVjdCB3aXRoIGEgTnVtYmVyIGxlbmd0aAogKiBwcm9wZXJ0eS4gTm90ZSB0aGF0IGZvciB0aGlzIGZ1bmN0aW9uIG5laXRoZXIgc3RyaW5ncyBub3IgZnVuY3Rpb25zIGFyZQogKiBjb25zaWRlcmVkICJhcnJheS1saWtlIi4KICoKICogQHBhcmFtIHs/fSB2YWwgVmFyaWFibGUgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB2YXJpYWJsZSBpcyBhbiBhcnJheS4KICovCmdvb2cuaXNBcnJheUxpa2UgPSBmdW5jdGlvbih2YWwpIHsKICB2YXIgdHlwZSA9IGdvb2cudHlwZU9mKHZhbCk7CiAgLy8gV2UgZG8gbm90IHVzZSBnb29nLmlzT2JqZWN0IGhlcmUgaW4gb3JkZXIgdG8gZXhjbHVkZSBmdW5jdGlvbiB2YWx1ZXMuCiAgcmV0dXJuIHR5cGUgPT0gJ2FycmF5JyB8fCB0eXBlID09ICdvYmplY3QnICYmIHR5cGVvZiB2YWwubGVuZ3RoID09ICdudW1iZXInOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIG9iamVjdCBsb29rcyBsaWtlIGEgRGF0ZS4gVG8gcXVhbGlmeSBhcyBEYXRlLWxpa2UgdGhlCiAqIHZhbHVlIG5lZWRzIHRvIGJlIGFuIG9iamVjdCBhbmQgaGF2ZSBhIGdldEZ1bGxZZWFyKCkgZnVuY3Rpb24uCiAqIEBwYXJhbSB7P30gdmFsIFZhcmlhYmxlIHRvIHRlc3QuCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdmFyaWFibGUgaXMgYSBsaWtlIGEgRGF0ZS4KICovCmdvb2cuaXNEYXRlTGlrZSA9IGZ1bmN0aW9uKHZhbCkgewogIHJldHVybiBnb29nLmlzT2JqZWN0KHZhbCkgJiYgdHlwZW9mIHZhbC5nZXRGdWxsWWVhciA9PSAnZnVuY3Rpb24nOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCB2YWx1ZSBpcyBhIGZ1bmN0aW9uLgogKiBAcGFyYW0gez99IHZhbCBWYXJpYWJsZSB0byB0ZXN0LgogKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHZhcmlhYmxlIGlzIGEgZnVuY3Rpb24uCiAqLwpnb29nLmlzRnVuY3Rpb24gPSBmdW5jdGlvbih2YWwpIHsKICByZXR1cm4gZ29vZy50eXBlT2YodmFsKSA9PSAnZnVuY3Rpb24nOwp9OwoKCi8qKgogKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCB2YWx1ZSBpcyBhbiBvYmplY3QuICBUaGlzIGluY2x1ZGVzIGFycmF5cyBhbmQKICogZnVuY3Rpb25zLgogKiBAcGFyYW0gez99IHZhbCBWYXJpYWJsZSB0byB0ZXN0LgogKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHZhcmlhYmxlIGlzIGFuIG9iamVjdC4KICovCmdvb2cuaXNPYmplY3QgPSBmdW5jdGlvbih2YWwpIHsKICB2YXIgdHlwZSA9IHR5cGVvZiB2YWw7CiAgcmV0dXJuIHR5cGUgPT0gJ29iamVjdCcgJiYgdmFsICE9IG51bGwgfHwgdHlwZSA9PSAnZnVuY3Rpb24nOwogIC8vIHJldHVybiBPYmplY3QodmFsKSA9PT0gdmFsIGFsc28gd29ya3MsIGJ1dCBpcyBzbG93ZXIsIGVzcGVjaWFsbHkgaWYgdmFsIGlzCiAgLy8gbm90IGFuIG9iamVjdC4KfTsKCgovKioKICogR2V0cyBhIHVuaXF1ZSBJRCBmb3IgYW4gb2JqZWN0LiBUaGlzIG11dGF0ZXMgdGhlIG9iamVjdCBzbyB0aGF0IGZ1cnRoZXIgY2FsbHMKICogd2l0aCB0aGUgc2FtZSBvYmplY3QgYXMgYSBwYXJhbWV0ZXIgcmV0dXJucyB0aGUgc2FtZSB2YWx1ZS4gVGhlIHVuaXF1ZSBJRCBpcwogKiBndWFyYW50ZWVkIHRvIGJlIHVuaXF1ZSBhY3Jvc3MgdGhlIGN1cnJlbnQgc2Vzc2lvbiBhbW9uZ3N0IG9iamVjdHMgdGhhdCBhcmUKICogcGFzc2VkIGludG8gYGdldFVpZGAuIFRoZXJlIGlzIG5vIGd1YXJhbnRlZSB0aGF0IHRoZSBJRCBpcyB1bmlxdWUgb3IKICogY29uc2lzdGVudCBhY3Jvc3Mgc2Vzc2lvbnMuIEl0IGlzIHVuc2FmZSB0byBnZW5lcmF0ZSB1bmlxdWUgSUQgZm9yIGZ1bmN0aW9uCiAqIHByb3RvdHlwZXMuCiAqCiAqIEBwYXJhbSB7T2JqZWN0fSBvYmogVGhlIG9iamVjdCB0byBnZXQgdGhlIHVuaXF1ZSBJRCBmb3IuCiAqIEByZXR1cm4ge251bWJlcn0gVGhlIHVuaXF1ZSBJRCBmb3IgdGhlIG9iamVjdC4KICovCmdvb2cuZ2V0VWlkID0gZnVuY3Rpb24ob2JqKSB7CiAgLy8gVE9ETyhhcnYpOiBNYWtlIHRoZSB0eXBlIHN0cmljdGVyLCBkbyBub3QgYWNjZXB0IG51bGwuCgogIC8vIEluIE9wZXJhIHdpbmRvdy5oYXNPd25Qcm9wZXJ0eSBleGlzdHMgYnV0IGFsd2F5cyByZXR1cm5zIGZhbHNlIHNvIHdlIGF2b2lkCiAgLy8gdXNpbmcgaXQuIEFzIGEgY29uc2VxdWVuY2UgdGhlIHVuaXF1ZSBJRCBnZW5lcmF0ZWQgZm9yIEJhc2VDbGFzcy5wcm90b3R5cGUKICAvLyBhbmQgU3ViQ2xhc3MucHJvdG90eXBlIHdpbGwgYmUgdGhlIHNhbWUuCiAgLy8gVE9ETyhiLzE0MTUxMjMyMyk6IFVVSURzIGFyZSBicm9rZW4gZm9yIGN0b3JzIHdpdGggY2xhc3Mtc2lkZSBpbmhlcml0YW5jZS4KICByZXR1cm4gb2JqW2dvb2cuVUlEX1BST1BFUlRZX10gfHwKICAgICAgKG9ialtnb29nLlVJRF9QUk9QRVJUWV9dID0gKytnb29nLnVpZENvdW50ZXJfKTsKfTsKCgovKioKICogV2hldGhlciB0aGUgZ2l2ZW4gb2JqZWN0IGlzIGFscmVhZHkgYXNzaWduZWQgYSB1bmlxdWUgSUQuCiAqCiAqIFRoaXMgZG9lcyBub3QgbW9kaWZ5IHRoZSBvYmplY3QuCiAqCiAqIEBwYXJhbSB7IU9iamVjdH0gb2JqIFRoZSBvYmplY3QgdG8gY2hlY2suCiAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdGhlcmUgaXMgYW4gYXNzaWduZWQgdW5pcXVlIGlkIGZvciB0aGUgb2JqZWN0LgogKi8KZ29vZy5oYXNVaWQgPSBmdW5jdGlvbihvYmopIHsKICByZXR1cm4gISFvYmpbZ29vZy5VSURfUFJPUEVSVFlfXTsKfTsKCgovKioKICogUmVtb3ZlcyB0aGUgdW5pcXVlIElEIGZyb20gYW4gb2JqZWN0LiBUaGlzIGlzIHVzZWZ1bCBpZiB0aGUgb2JqZWN0IHdhcwogKiBwcmV2aW91c2x5IG11dGF0ZWQgdXNpbmcgYGdvb2cuZ2V0VWlkYCBpbiB3aGljaCBjYXNlIHRoZSBtdXRhdGlvbiBpcwogKiB1bmRvbmUuCiAqIEBwYXJhbSB7T2JqZWN0fSBvYmogVGhlIG9iamVjdCB0byByZW1vdmUgdGhlIHVuaXF1ZSBJRCBmaWVsZCBmcm9tLgogKi8KZ29vZy5yZW1vdmVVaWQgPSBmdW5jdGlvbihvYmopIHsKICAvLyBUT0RPKGFydik6IE1ha2UgdGhlIHR5cGUgc3RyaWN0ZXIsIGRvIG5vdCBhY2NlcHQgbnVsbC4KCiAgLy8gSW4gSUUsIERPTSBub2RlcyBhcmUgbm90IGluc3RhbmNlcyBvZiBPYmplY3QgYW5kIHRocm93IGFuIGV4Y2VwdGlvbiBpZiB3ZQogIC8vIHRyeSB0byBkZWxldGUuICBJbnN0ZWFkIHdlIHRyeSB0byB1c2UgcmVtb3ZlQXR0cmlidXRlLgogIGlmIChvYmogIT09IG51bGwgJiYgJ3JlbW92ZUF0dHJpYnV0ZScgaW4gb2JqKSB7CiAgICBvYmoucmVtb3ZlQXR0cmlidXRlKGdvb2cuVUlEX1BST1BFUlRZXyk7CiAgfQoKICB0cnkgewogICAgZGVsZXRlIG9ialtnb29nLlVJRF9QUk9QRVJUWV9dOwogIH0gY2F0Y2ggKGV4KSB7CiAgfQp9OwoKCi8qKgogKiBOYW1lIGZvciB1bmlxdWUgSUQgcHJvcGVydHkuIEluaXRpYWxpemVkIGluIGEgd2F5IHRvIGhlbHAgYXZvaWQgY29sbGlzaW9ucwogKiB3aXRoIG90aGVyIGNsb3N1cmUgSmF2YVNjcmlwdCBvbiB0aGUgc2FtZSBwYWdlLgogKiBAdHlwZSB7c3RyaW5nfQogKiBAcHJpdmF0ZQogKi8KZ29vZy5VSURfUFJPUEVSVFlfID0gJ2Nsb3N1cmVfdWlkXycgKyAoKE1hdGgucmFuZG9tKCkgKiAxZTkpID4+PiAwKTsKCgovKioKICogQ291bnRlciBmb3IgVUlELgogKiBAdHlwZSB7bnVtYmVyfQogKiBAcHJpdmF0ZQogKi8KZ29vZy51aWRDb3VudGVyXyA9IDA7CgoKLyoqCiAqIEFkZHMgYSBoYXNoIGNvZGUgZmllbGQgdG8gYW4gb2JqZWN0LiBUaGUgaGFzaCBjb2RlIGlzIHVuaXF1ZSBmb3IgdGhlCiAqIGdpdmVuIG9iamVjdC4KICogQHBhcmFtIHtPYmplY3R9IG9iaiBUaGUgb2JqZWN0IHRvIGdldCB0aGUgaGFzaCBjb2RlIGZvci4KICogQHJldHVybiB7bnVtYmVyfSBUaGUgaGFzaCBjb2RlIGZvciB0aGUgb2JqZWN0LgogKiBAZGVwcmVjYXRlZCBVc2UgZ29vZy5nZXRVaWQgaW5zdGVhZC4KICovCmdvb2cuZ2V0SGFzaENvZGUgPSBnb29nLmdldFVpZDsKCgovKioKICogUmVtb3ZlcyB0aGUgaGFzaCBjb2RlIGZpZWxkIGZyb20gYW4gb2JqZWN0LgogKiBAcGFyYW0ge09iamVjdH0gb2JqIFRoZSBvYmplY3QgdG8gcmVtb3ZlIHRoZSBmaWVsZCBmcm9tLgogKiBAZGVwcmVjYXRlZCBVc2UgZ29vZy5yZW1vdmVVaWQgaW5zdGVhZC4KICovCmdvb2cucmVtb3ZlSGFzaENvZGUgPSBnb29nLnJlbW92ZVVpZDsKCgovKioKICogQ2xvbmVzIGEgdmFsdWUuIFRoZSBpbnB1dCBtYXkgYmUgYW4gT2JqZWN0LCBBcnJheSwgb3IgYmFzaWMgdHlwZS4gT2JqZWN0cyBhbmQKICogYXJyYXlzIHdpbGwgYmUgY2xvbmVkIHJlY3Vyc2l2ZWx5LgogKgogKiBXQVJOSU5HUzoKICogPGNvZGU+Z29vZy5jbG9uZU9iamVjdDwvY29kZT4gZG9lcyBub3QgZGV0ZWN0IHJlZmVyZW5jZSBsb29wcy4gT2JqZWN0cyB0aGF0CiAqIHJlZmVyIHRvIHRoZW1zZWx2ZXMgd2lsbCBjYXVzZSBpbmZpbml0ZSByZWN1cnNpb24uCiAqCiAqIDxjb2RlPmdvb2cuY2xvbmVPYmplY3Q8L2NvZGU+IGlzIHVuYXdhcmUgb2YgdW5pcXVlIGlkZW50aWZpZXJzLCBhbmQgY29waWVzCiAqIFVJRHMgY3JlYXRlZCBieSA8Y29kZT5nZXRVaWQ8L2NvZGU+IGludG8gY2xvbmVkIHJlc3VsdHMuCiAqCiAqIEBwYXJhbSB7Kn0gb2JqIFRoZSB2YWx1ZSB0byBjbG9uZS4KICogQHJldHVybiB7Kn0gQSBjbG9uZSBvZiB0aGUgaW5wdXQgdmFsdWUuCiAqIEBkZXByZWNhdGVkIGdvb2cuY2xvbmVPYmplY3QgaXMgdW5zYWZlLiBQcmVmZXIgdGhlIGdvb2cub2JqZWN0IG1ldGhvZHMuCiAqLwpnb29nLmNsb25lT2JqZWN0ID0gZnVuY3Rpb24ob2JqKSB7CiAgdmFyIHR5cGUgPSBnb29nLnR5cGVPZihvYmopOwogIGlmICh0eXBlID09ICdvYmplY3QnIHx8IHR5cGUgPT0gJ2FycmF5JykgewogICAgaWYgKHR5cGVvZiBvYmouY2xvbmUgPT09ICdmdW5jdGlvbicpIHsKICAgICAgcmV0dXJuIG9iai5jbG9uZSgpOwogICAgfQogICAgdmFyIGNsb25lID0gdHlwZSA9PSAnYXJyYXknID8gW10gOiB7fTsKICAgIGZvciAodmFyIGtleSBpbiBvYmopIHsKICAgICAgY2xvbmVba2V5XSA9IGdvb2cuY2xvbmVPYmplY3Qob2JqW2tleV0pOwogICAgfQogICAgcmV0dXJuIGNsb25lOwogIH0KCiAgcmV0dXJuIG9iajsKfTsKCgovKioKICogQSBuYXRpdmUgaW1wbGVtZW50YXRpb24gb2YgZ29vZy5iaW5kLgogKiBAcGFyYW0gez9mdW5jdGlvbih0aGlzOlQsIC4uLil9IGZuIEEgZnVuY3Rpb24gdG8gcGFydGlhbGx5IGFwcGx5LgogKiBAcGFyYW0ge1R9IHNlbGZPYmogU3BlY2lmaWVzIHRoZSBvYmplY3Qgd2hpY2ggdGhpcyBzaG91bGQgcG9pbnQgdG8gd2hlbiB0aGUKICogICAgIGZ1bmN0aW9uIGlzIHJ1bi4KICogQHBhcmFtIHsuLi4qfSB2YXJfYXJncyBBZGRpdGlvbmFsIGFyZ3VtZW50cyB0aGF0IGFyZSBwYXJ0aWFsbHkgYXBwbGllZCB0byB0aGUKICogICAgIGZ1bmN0aW9uLgogKiBAcmV0dXJuIHshRnVuY3Rpb259IEEgcGFydGlhbGx5LWFwcGxpZWQgZm9ybSBvZiB0aGUgZnVuY3Rpb24gZ29vZy5iaW5kKCkgd2FzCiAqICAgICBpbnZva2VkIGFzIGEgbWV0aG9kIG9mLgogKiBAdGVtcGxhdGUgVAogKiBAcHJpdmF0ZQogKi8KZ29vZy5iaW5kTmF0aXZlXyA9IGZ1bmN0aW9uKGZuLCBzZWxmT2JqLCB2YXJfYXJncykgewogIHJldHVybiAvKiogQHR5cGUgeyFGdW5jdGlvbn0gKi8gKGZuLmNhbGwuYXBwbHkoZm4uYmluZCwgYXJndW1lbnRzKSk7Cn07CgoKLyoqCiAqIEEgcHVyZS1KUyBpbXBsZW1lbnRhdGlvbiBvZiBnb29nLmJpbmQuCiAqIEBwYXJhbSB7P2Z1bmN0aW9uKHRoaXM6VCwgLi4uKX0gZm4gQSBmdW5jdGlvbiB0byBwYXJ0aWFsbHkgYXBwbHkuCiAqIEBwYXJhbSB7VH0gc2VsZk9iaiBTcGVjaWZpZXMgdGhlIG9iamVjdCB3aGljaCB0aGlzIHNob3VsZCBwb2ludCB0byB3aGVuIHRoZQogKiAgICAgZnVuY3Rpb24gaXMgcnVuLgogKiBAcGFyYW0gey4uLip9IHZhcl9hcmdzIEFkZGl0aW9uYWwgYXJndW1lbnRzIHRoYXQgYXJlIHBhcnRpYWxseSBhcHBsaWVkIHRvIHRoZQogKiAgICAgZnVuY3Rpb24uCiAqIEByZXR1cm4geyFGdW5jdGlvbn0gQSBwYXJ0aWFsbHktYXBwbGllZCBmb3JtIG9mIHRoZSBmdW5jdGlvbiBnb29nLmJpbmQoKSB3YXMKICogICAgIGludm9rZWQgYXMgYSBtZXRob2Qgb2YuCiAqIEB0ZW1wbGF0ZSBUCiAqIEBwcml2YXRlCiAqLwpnb29nLmJpbmRKc18gPSBmdW5jdGlvbihmbiwgc2VsZk9iaiwgdmFyX2FyZ3MpIHsKICBpZiAoIWZuKSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoKTsKICB9CgogIGlmIChhcmd1bWVudHMubGVuZ3RoID4gMikgewogICAgdmFyIGJvdW5kQXJncyA9IEFycmF5LnByb3RvdHlwZS5zbGljZS5jYWxsKGFyZ3VtZW50cywgMik7CiAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgIC8vIFByZXBlbmQgdGhlIGJvdW5kIGFyZ3VtZW50cyB0byB0aGUgY3VycmVudCBhcmd1bWVudHMuCiAgICAgIHZhciBuZXdBcmdzID0gQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwoYXJndW1lbnRzKTsKICAgICAgQXJyYXkucHJvdG90eXBlLnVuc2hpZnQuYXBwbHkobmV3QXJncywgYm91bmRBcmdzKTsKICAgICAgcmV0dXJuIGZuLmFwcGx5KHNlbGZPYmosIG5ld0FyZ3MpOwogICAgfTsKCiAgfSBlbHNlIHsKICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIGZuLmFwcGx5KHNlbGZPYmosIGFyZ3VtZW50cyk7CiAgICB9OwogIH0KfTsKCgovKioKICogUGFydGlhbGx5IGFwcGxpZXMgdGhpcyBmdW5jdGlvbiB0byBhIHBhcnRpY3VsYXIgJ3RoaXMgb2JqZWN0JyBhbmQgemVybyBvcgogKiBtb3JlIGFyZ3VtZW50cy4gVGhlIHJlc3VsdCBpcyBhIG5ldyBmdW5jdGlvbiB3aXRoIHNvbWUgYXJndW1lbnRzIG9mIHRoZSBmaXJzdAogKiBmdW5jdGlvbiBwcmUtZmlsbGVkIGFuZCB0aGUgdmFsdWUgb2YgdGhpcyAncHJlLXNwZWNpZmllZCcuCiAqCiAqIFJlbWFpbmluZyBhcmd1bWVudHMgc3BlY2lmaWVkIGF0IGNhbGwtdGltZSBhcmUgYXBwZW5kZWQgdG8gdGhlIHByZS1zcGVjaWZpZWQKICogb25lcy4KICoKICogQWxzbyBzZWU6IHtAbGluayAjcGFydGlhbH0uCiAqCiAqIFVzYWdlOgogKiA8cHJlPnZhciBiYXJNZXRoQm91bmQgPSBnb29nLmJpbmQobXlGdW5jdGlvbiwgbXlPYmosICdhcmcxJywgJ2FyZzInKTsKICogYmFyTWV0aEJvdW5kKCdhcmczJywgJ2FyZzQnKTs8L3ByZT4KICoKICogQHBhcmFtIHs/ZnVuY3Rpb24odGhpczpULCAuLi4pfSBmbiBBIGZ1bmN0aW9uIHRvIHBhcnRpYWxseSBhcHBseS4KICogQHBhcmFtIHtUfSBzZWxmT2JqIFNwZWNpZmllcyB0aGUgb2JqZWN0IHdoaWNoIHRoaXMgc2hvdWxkIHBvaW50IHRvIHdoZW4gdGhlCiAqICAgICBmdW5jdGlvbiBpcyBydW4uCiAqIEBwYXJhbSB7Li4uKn0gdmFyX2FyZ3MgQWRkaXRpb25hbCBhcmd1bWVudHMgdGhhdCBhcmUgcGFydGlhbGx5IGFwcGxpZWQgdG8gdGhlCiAqICAgICBmdW5jdGlvbi4KICogQHJldHVybiB7IUZ1bmN0aW9ufSBBIHBhcnRpYWxseS1hcHBsaWVkIGZvcm0gb2YgdGhlIGZ1bmN0aW9uIGdvb2cuYmluZCgpIHdhcwogKiAgICAgaW52b2tlZCBhcyBhIG1ldGhvZCBvZi4KICogQHRlbXBsYXRlIFQKICogQHN1cHByZXNzIHtkZXByZWNhdGVkfSBTZWUgYWJvdmUuCiAqLwpnb29nLmJpbmQgPSBmdW5jdGlvbihmbiwgc2VsZk9iaiwgdmFyX2FyZ3MpIHsKICAvLyBUT0RPKG5pY2tzYW50b3MpOiBuYXJyb3cgdGhlIHR5cGUgc2lnbmF0dXJlLgogIGlmIChGdW5jdGlvbi5wcm90b3R5cGUuYmluZCAmJgogICAgICAvLyBOT1RFKG5pY2tzYW50b3MpOiBTb21lYm9keSBwdWxsZWQgYmFzZS5qcyBpbnRvIHRoZSBkZWZhdWx0IENocm9tZQogICAgICAvLyBleHRlbnNpb24gZW52aXJvbm1lbnQuIFRoaXMgbWVhbnMgdGhhdCBmb3IgQ2hyb21lIGV4dGVuc2lvbnMsIHRoZXkgZ2V0CiAgICAgIC8vIHRoZSBpbXBsZW1lbnRhdGlvbiBvZiBGdW5jdGlvbi5wcm90b3R5cGUuYmluZCB0aGF0IGNhbGxzIGdvb2cuYmluZAogICAgICAvLyBpbnN0ZWFkIG9mIHRoZSBuYXRpdmUgb25lLiBFdmVuIHdvcnNlLCB3ZSBkb24ndCB3YW50IHRvIGludHJvZHVjZSBhCiAgICAgIC8vIGNpcmN1bGFyIGRlcGVuZGVuY3kgYmV0d2VlbiBnb29nLmJpbmQgYW5kIEZ1bmN0aW9uLnByb3RvdHlwZS5iaW5kLCBzbwogICAgICAvLyB3ZSBoYXZlIHRvIGhhY2sgdGhpcyB0byBtYWtlIHN1cmUgaXQgd29ya3MgY29ycmVjdGx5LgogICAgICBGdW5jdGlvbi5wcm90b3R5cGUuYmluZC50b1N0cmluZygpLmluZGV4T2YoJ25hdGl2ZSBjb2RlJykgIT0gLTEpIHsKICAgIGdvb2cuYmluZCA9IGdvb2cuYmluZE5hdGl2ZV87CiAgfSBlbHNlIHsKICAgIGdvb2cuYmluZCA9IGdvb2cuYmluZEpzXzsKICB9CiAgcmV0dXJuIGdvb2cuYmluZC5hcHBseShudWxsLCBhcmd1bWVudHMpOwp9OwoKCi8qKgogKiBMaWtlIGdvb2cuYmluZCgpLCBleGNlcHQgdGhhdCBhICd0aGlzIG9iamVjdCcgaXMgbm90IHJlcXVpcmVkLiBVc2VmdWwgd2hlbgogKiB0aGUgdGFyZ2V0IGZ1bmN0aW9uIGlzIGFscmVhZHkgYm91bmQuCiAqCiAqIFVzYWdlOgogKiB2YXIgZyA9IGdvb2cucGFydGlhbChmLCBhcmcxLCBhcmcyKTsKICogZyhhcmczLCBhcmc0KTsKICoKICogQHBhcmFtIHtGdW5jdGlvbn0gZm4gQSBmdW5jdGlvbiB0byBwYXJ0aWFsbHkgYXBwbHkuCiAqIEBwYXJhbSB7Li4uKn0gdmFyX2FyZ3MgQWRkaXRpb25hbCBhcmd1bWVudHMgdGhhdCBhcmUgcGFydGlhbGx5IGFwcGxpZWQgdG8gZm4uCiAqIEByZXR1cm4geyFGdW5jdGlvbn0gQSBwYXJ0aWFsbHktYXBwbGllZCBmb3JtIG9mIHRoZSBmdW5jdGlvbiBnb29nLnBhcnRpYWwoKQogKiAgICAgd2FzIGludm9rZWQgYXMgYSBtZXRob2Qgb2YuCiAqLwpnb29nLnBhcnRpYWwgPSBmdW5jdGlvbihmbiwgdmFyX2FyZ3MpIHsKICB2YXIgYXJncyA9IEFycmF5LnByb3RvdHlwZS5zbGljZS5jYWxsKGFyZ3VtZW50cywgMSk7CiAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgLy8gQ2xvbmUgdGhlIGFycmF5ICh3aXRoIHNsaWNlKCkpIGFuZCBhcHBlbmQgYWRkaXRpb25hbCBhcmd1bWVudHMKICAgIC8vIHRvIHRoZSBleGlzdGluZyBhcmd1bWVudHMuCiAgICB2YXIgbmV3QXJncyA9IGFyZ3Muc2xpY2UoKTsKICAgIG5ld0FyZ3MucHVzaC5hcHBseShuZXdBcmdzLCBhcmd1bWVudHMpOwogICAgcmV0dXJuIGZuLmFwcGx5KC8qKiBAdHlwZSB7P30gKi8gKHRoaXMpLCBuZXdBcmdzKTsKICB9Owp9OwoKCi8qKgogKiBDb3BpZXMgYWxsIHRoZSBtZW1iZXJzIG9mIGEgc291cmNlIG9iamVjdCB0byBhIHRhcmdldCBvYmplY3QuIFRoaXMgbWV0aG9kCiAqIGRvZXMgbm90IHdvcmsgb24gYWxsIGJyb3dzZXJzIGZvciBhbGwgb2JqZWN0cyB0aGF0IGNvbnRhaW4ga2V5cyBzdWNoIGFzCiAqIHRvU3RyaW5nIG9yIGhhc093blByb3BlcnR5LiBVc2UgZ29vZy5vYmplY3QuZXh0ZW5kIGZvciB0aGlzIHB1cnBvc2UuCiAqCiAqIE5PVEU6IFNvbWUgaGF2ZSBhZHZvY2F0ZWQgZm9yIHRoZSB1c2Ugb2YgZ29vZy5taXhpbiB0byBzZXR1cCBjbGFzc2VzCiAqIHdpdGggbXVsdGlwbGUgaW5oZXJpdGVuY2UgKHRyYWl0cywgbWl4aW5zLCBldGMpLiAgSG93ZXZlciwgYXMgaXQgc2ltcGx5CiAqIHVzZXMgImZvciBpbiIsIHRoaXMgaXMgbm90IGNvbXBhdGlibGUgd2l0aCBFUzYgY2xhc3NlcyB3aG9zZSBtZXRob2RzIGFyZQogKiBub24tZW51bWVyYWJsZS4gIENoYW5naW5nIHRoaXMsIHdvdWxkIGJyZWFrIGNhc2VzIHdoZXJlIG5vbi1lbnVtZXJhYmxlCiAqIHByb3BlcnRpZXMgYXJlIG5vdCBleHBlY3RlZC4KICoKICogQHBhcmFtIHtPYmplY3R9IHRhcmdldCBUYXJnZXQuCiAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgU291cmNlLgogKiBAZGVwcmVjYXRlZCBQcmVmZXIgT2JqZWN0LmFzc2lnbgogKi8KZ29vZy5taXhpbiA9IGZ1bmN0aW9uKHRhcmdldCwgc291cmNlKSB7CiAgZm9yICh2YXIgeCBpbiBzb3VyY2UpIHsKICAgIHRhcmdldFt4XSA9IHNvdXJjZVt4XTsKICB9CgogIC8vIEZvciBJRTcgb3IgbG93ZXIsIHRoZSBmb3ItaW4tbG9vcCBkb2VzIG5vdCBjb250YWluIGFueSBwcm9wZXJ0aWVzIHRoYXQgYXJlCiAgLy8gbm90IGVudW1lcmFibGUgb24gdGhlIHByb3RvdHlwZSBvYmplY3QgKGZvciBleGFtcGxlLCBpc1Byb3RvdHlwZU9mIGZyb20KICAvLyBPYmplY3QucHJvdG90eXBlKSBidXQgYWxzbyBpdCB3aWxsIG5vdCBpbmNsdWRlICdyZXBsYWNlJyBvbiBvYmplY3RzIHRoYXQKICAvLyBleHRlbmQgU3RyaW5nIGFuZCBjaGFuZ2UgJ3JlcGxhY2UnIChub3QgdGhhdCBpdCBpcyBjb21tb24gZm9yIGFueW9uZSB0bwogIC8vIGV4dGVuZCBhbnl0aGluZyBleGNlcHQgT2JqZWN0KS4KfTsKCgovKioKICogQHJldHVybiB7bnVtYmVyfSBBbiBpbnRlZ2VyIHZhbHVlIHJlcHJlc2VudGluZyB0aGUgbnVtYmVyIG9mIG1pbGxpc2Vjb25kcwogKiAgICAgYmV0d2VlbiBtaWRuaWdodCwgSmFudWFyeSAxLCAxOTcwIGFuZCB0aGUgY3VycmVudCB0aW1lLgogKiBAZGVwcmVjYXRlZCBVc2UgRGF0ZS5ub3cKICovCmdvb2cubm93ID0gKGdvb2cuVFJVU1RFRF9TSVRFICYmIERhdGUubm93KSB8fCAoZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAvLyBVbmFyeSBwbHVzIG9wZXJhdG9yIGNvbnZlcnRzIGl0cyBvcGVyYW5kIHRvIGEgbnVtYmVyIHdoaWNoIGluCiAgICAgICAgICAgICAvLyB0aGUgY2FzZSBvZgogICAgICAgICAgICAgLy8gYSBkYXRlIGlzIGRvbmUgYnkgY2FsbGluZyBnZXRUaW1lKCkuCiAgICAgICAgICAgICByZXR1cm4gK25ldyBEYXRlKCk7CiAgICAgICAgICAgfSk7CgoKLyoqCiAqIEV2YWxzIEphdmFTY3JpcHQgaW4gdGhlIGdsb2JhbCBzY29wZS4gIEluIElFIHRoaXMgdXNlcyBleGVjU2NyaXB0LCBvdGhlcgogKiBicm93c2VycyB1c2UgZ29vZy5nbG9iYWwuZXZhbC4gSWYgZ29vZy5nbG9iYWwuZXZhbCBkb2VzIG5vdCBldmFsdWF0ZSBpbiB0aGUKICogZ2xvYmFsIHNjb3BlIChmb3IgZXhhbXBsZSwgaW4gU2FmYXJpKSwgYXBwZW5kcyBhIHNjcmlwdCB0YWcgaW5zdGVhZC4KICogVGhyb3dzIGFuIGV4Y2VwdGlvbiBpZiBuZWl0aGVyIGV4ZWNTY3JpcHQgb3IgZXZhbCBpcyBkZWZpbmVkLgogKiBAcGFyYW0ge3N0cmluZ30gc2NyaXB0IEphdmFTY3JpcHQgc3RyaW5nLgogKi8KZ29vZy5nbG9iYWxFdmFsID0gZnVuY3Rpb24oc2NyaXB0KSB7CiAgaWYgKGdvb2cuZ2xvYmFsLmV4ZWNTY3JpcHQpIHsKICAgIGdvb2cuZ2xvYmFsLmV4ZWNTY3JpcHQoc2NyaXB0LCAnSmF2YVNjcmlwdCcpOwogIH0gZWxzZSBpZiAoZ29vZy5nbG9iYWwuZXZhbCkgewogICAgLy8gVGVzdCB0byBzZWUgaWYgZXZhbCB3b3JrcwogICAgaWYgKGdvb2cuZXZhbFdvcmtzRm9yR2xvYmFsc18gPT0gbnVsbCkgewogICAgICB0cnkgewogICAgICAgIGdvb2cuZ2xvYmFsLmV2YWwoJ3ZhciBfZXZhbFRlc3RfID0gMTsnKTsKICAgICAgfSBjYXRjaCAoaWdub3JlKSB7CiAgICAgIH0KICAgICAgaWYgKHR5cGVvZiBnb29nLmdsb2JhbFsnX2V2YWxUZXN0XyddICE9ICd1bmRlZmluZWQnKSB7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIGRlbGV0ZSBnb29nLmdsb2JhbFsnX2V2YWxUZXN0XyddOwogICAgICAgIH0gY2F0Y2ggKGlnbm9yZSkgewogICAgICAgICAgLy8gTWljcm9zb2Z0IGVkZ2UgZmFpbHMgdGhlIGRlbGV0aW9uIGFib3ZlIGluIHN0cmljdCBtb2RlLgogICAgICAgIH0KICAgICAgICBnb29nLmV2YWxXb3Jrc0Zvckdsb2JhbHNfID0gdHJ1ZTsKICAgICAgfSBlbHNlIHsKICAgICAgICBnb29nLmV2YWxXb3Jrc0Zvckdsb2JhbHNfID0gZmFsc2U7CiAgICAgIH0KICAgIH0KCiAgICBpZiAoZ29vZy5ldmFsV29ya3NGb3JHbG9iYWxzXykgewogICAgICBnb29nLmdsb2JhbC5ldmFsKHNjcmlwdCk7CiAgICB9IGVsc2UgewogICAgICAvKiogQHR5cGUgeyFEb2N1bWVudH0gKi8KICAgICAgdmFyIGRvYyA9IGdvb2cuZ2xvYmFsLmRvY3VtZW50OwogICAgICB2YXIgc2NyaXB0RWx0ID0KICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxTY3JpcHRFbGVtZW50fSAqLyAoZG9jLmNyZWF0ZUVsZW1lbnQoJ3NjcmlwdCcpKTsKICAgICAgc2NyaXB0RWx0LnR5cGUgPSAndGV4dC9qYXZhc2NyaXB0JzsKICAgICAgc2NyaXB0RWx0LmRlZmVyID0gZmFsc2U7CiAgICAgIC8vIE5vdGUodXNlcik6IGNhbid0IHVzZSAuaW5uZXJIVE1MIHNpbmNlICJ0KCc8dGVzdD4nKSIgd2lsbCBmYWlsIGFuZAogICAgICAvLyAudGV4dCBkb2Vzbid0IHdvcmsgaW4gU2FmYXJpIDIuICBUaGVyZWZvcmUgd2UgYXBwZW5kIGEgdGV4dCBub2RlLgogICAgICBzY3JpcHRFbHQuYXBwZW5kQ2hpbGQoZG9jLmNyZWF0ZVRleHROb2RlKHNjcmlwdCkpOwogICAgICBkb2MuaGVhZC5hcHBlbmRDaGlsZChzY3JpcHRFbHQpOwogICAgICBkb2MuaGVhZC5yZW1vdmVDaGlsZChzY3JpcHRFbHQpOwogICAgfQogIH0gZWxzZSB7CiAgICB0aHJvdyBuZXcgRXJyb3IoJ2dvb2cuZ2xvYmFsRXZhbCBub3QgYXZhaWxhYmxlJyk7CiAgfQp9OwoKCi8qKgogKiBJbmRpY2F0ZXMgd2hldGhlciBvciBub3Qgd2UgY2FuIGNhbGwgJ2V2YWwnIGRpcmVjdGx5IHRvIGV2YWwgY29kZSBpbiB0aGUKICogZ2xvYmFsIHNjb3BlLiBTZXQgdG8gYSBCb29sZWFuIGJ5IHRoZSBmaXJzdCBjYWxsIHRvIGdvb2cuZ2xvYmFsRXZhbCAod2hpY2gKICogZW1waXJpY2FsbHkgdGVzdHMgd2hldGhlciBldmFsIHdvcmtzIGZvciBnbG9iYWxzKS4gQHNlZSBnb29nLmdsb2JhbEV2YWwKICogQHR5cGUgez9ib29sZWFufQogKiBAcHJpdmF0ZQogKi8KZ29vZy5ldmFsV29ya3NGb3JHbG9iYWxzXyA9IG51bGw7CgoKLyoqCiAqIE9wdGlvbmFsIG1hcCBvZiBDU1MgY2xhc3MgbmFtZXMgdG8gb2JmdXNjYXRlZCBuYW1lcyB1c2VkIHdpdGgKICogZ29vZy5nZXRDc3NOYW1lKCkuCiAqIEBwcml2YXRlIHshT2JqZWN0PHN0cmluZywgc3RyaW5nPnx1bmRlZmluZWR9CiAqIEBzZWUgZ29vZy5zZXRDc3NOYW1lTWFwcGluZwogKi8KZ29vZy5jc3NOYW1lTWFwcGluZ187CgoKLyoqCiAqIE9wdGlvbmFsIG9iZnVzY2F0aW9uIHN0eWxlIGZvciBDU1MgY2xhc3MgbmFtZXMuIFNob3VsZCBiZSBzZXQgdG8gZWl0aGVyCiAqICdCWV9XSE9MRScgb3IgJ0JZX1BBUlQnIGlmIGRlZmluZWQuCiAqIEB0eXBlIHtzdHJpbmd8dW5kZWZpbmVkfQogKiBAcHJpdmF0ZQogKiBAc2VlIGdvb2cuc2V0Q3NzTmFtZU1hcHBpbmcKICovCmdvb2cuY3NzTmFtZU1hcHBpbmdTdHlsZV87CgoKCi8qKgogKiBBIGhvb2sgZm9yIG1vZGlmeWluZyB0aGUgZGVmYXVsdCBiZWhhdmlvciBnb29nLmdldENzc05hbWUuIFRoZSBmdW5jdGlvbgogKiBpZiBwcmVzZW50LCB3aWxsIHJlY2VpdmUgdGhlIHN0YW5kYXJkIG91dHB1dCBvZiB0aGUgZ29vZy5nZXRDc3NOYW1lIGFzCiAqIGl0cyBpbnB1dC4KICoKICogQHR5cGUgeyhmdW5jdGlvbihzdHJpbmcpOnN0cmluZyl8dW5kZWZpbmVkfQogKi8KZ29vZy5nbG9iYWwuQ0xPU1VSRV9DU1NfTkFNRV9NQVBfRk47CgoKLyoqCiAqIEhhbmRsZXMgc3RyaW5ncyB0aGF0IGFyZSBpbnRlbmRlZCB0byBiZSB1c2VkIGFzIENTUyBjbGFzcyBuYW1lcy4KICoKICogVGhpcyBmdW5jdGlvbiB3b3JrcyBpbiB0YW5kZW0gd2l0aCBAc2VlIGdvb2cuc2V0Q3NzTmFtZU1hcHBpbmcuCiAqCiAqIFdpdGhvdXQgYW55IG1hcHBpbmcgc2V0LCB0aGUgYXJndW1lbnRzIGFyZSBzaW1wbGUgam9pbmVkIHdpdGggYSBoeXBoZW4gYW5kCiAqIHBhc3NlZCB0aHJvdWdoIHVuYWx0ZXJlZC4KICoKICogV2hlbiB0aGVyZSBpcyBhIG1hcHBpbmcsIHRoZXJlIGFyZSB0d28gcG9zc2libGUgc3R5bGVzIGluIHdoaWNoIHRoZXNlCiAqIG1hcHBpbmdzIGFyZSB1c2VkLiBJbiB0aGUgQllfUEFSVCBzdHlsZSwgZWFjaCBwYXJ0IChpLmUuIGluIGJldHdlZW4gaHlwaGVucykKICogb2YgdGhlIHBhc3NlZCBpbiBjc3MgbmFtZSBpcyByZXdyaXR0ZW4gYWNjb3JkaW5nIHRvIHRoZSBtYXAuIEluIHRoZSBCWV9XSE9MRQogKiBzdHlsZSwgdGhlIGZ1bGwgY3NzIG5hbWUgaXMgbG9va2VkIHVwIGluIHRoZSBtYXAgZGlyZWN0bHkuIElmIGEgcmV3cml0ZSBpcwogKiBub3Qgc3BlY2lmaWVkIGJ5IHRoZSBtYXAsIHRoZSBjb21waWxlciB3aWxsIG91dHB1dCBhIHdhcm5pbmcuCiAqCiAqIFdoZW4gdGhlIG1hcHBpbmcgaXMgcGFzc2VkIHRvIHRoZSBjb21waWxlciwgaXQgd2lsbCByZXBsYWNlIGNhbGxzIHRvCiAqIGdvb2cuZ2V0Q3NzTmFtZSB3aXRoIHRoZSBzdHJpbmdzIGZyb20gdGhlIG1hcHBpbmcsIGUuZy4KICogICAgIHZhciB4ID0gZ29vZy5nZXRDc3NOYW1lKCdmb28nKTsKICogICAgIHZhciB5ID0gZ29vZy5nZXRDc3NOYW1lKHRoaXMuYmFzZUNsYXNzLCAnYWN0aXZlJyk7CiAqICBiZWNvbWVzOgogKiAgICAgdmFyIHggPSAnZm9vJzsKICogICAgIHZhciB5ID0gdGhpcy5iYXNlQ2xhc3MgKyAnLWFjdGl2ZSc7CiAqCiAqIElmIG9uZSBhcmd1bWVudCBpcyBwYXNzZWQgaXQgd2lsbCBiZSBwcm9jZXNzZWQsIGlmIHR3byBhcmUgcGFzc2VkIG9ubHkgdGhlCiAqIG1vZGlmaWVyIHdpbGwgYmUgcHJvY2Vzc2VkLCBhcyBpdCBpcyBhc3N1bWVkIHRoZSBmaXJzdCBhcmd1bWVudCB3YXMgZ2VuZXJhdGVkCiAqIGFzIGEgcmVzdWx0IG9mIGNhbGxpbmcgZ29vZy5nZXRDc3NOYW1lLgogKgogKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIFRoZSBjbGFzcyBuYW1lLgogKiBAcGFyYW0ge3N0cmluZz19IG9wdF9tb2RpZmllciBBIG1vZGlmaWVyIHRvIGJlIGFwcGVuZGVkIHRvIHRoZSBjbGFzcyBuYW1lLgogKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSBjbGFzcyBuYW1lIG9yIHRoZSBjb25jYXRlbmF0aW9uIG9mIHRoZSBjbGFzcyBuYW1lIGFuZAogKiAgICAgdGhlIG1vZGlmaWVyLgogKi8KZ29vZy5nZXRDc3NOYW1lID0gZnVuY3Rpb24oY2xhc3NOYW1lLCBvcHRfbW9kaWZpZXIpIHsKICAvLyBTdHJpbmcoKSBpcyB1c2VkIGZvciBjb21wYXRpYmlsaXR5IHdpdGggY29tcGlsZWQgc295IHdoZXJlIHRoZSBwYXNzZWQKICAvLyBjbGFzc05hbWUgY2FuIGJlIG5vbi1zdHJpbmcgb2JqZWN0cy4KICBpZiAoU3RyaW5nKGNsYXNzTmFtZSkuY2hhckF0KDApID09ICcuJykgewogICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICdjbGFzc05hbWUgcGFzc2VkIGluIGdvb2cuZ2V0Q3NzTmFtZSBtdXN0IG5vdCBzdGFydCB3aXRoICIuIi4nICsKICAgICAgICAnIFlvdSBwYXNzZWQ6ICcgKyBjbGFzc05hbWUpOwogIH0KCiAgdmFyIGdldE1hcHBpbmcgPSBmdW5jdGlvbihjc3NOYW1lKSB7CiAgICByZXR1cm4gZ29vZy5jc3NOYW1lTWFwcGluZ19bY3NzTmFtZV0gfHwgY3NzTmFtZTsKICB9OwoKICB2YXIgcmVuYW1lQnlQYXJ0cyA9IGZ1bmN0aW9uKGNzc05hbWUpIHsKICAgIC8vIFJlbWFwIGFsbCB0aGUgcGFydHMgaW5kaXZpZHVhbGx5LgogICAgdmFyIHBhcnRzID0gY3NzTmFtZS5zcGxpdCgnLScpOwogICAgdmFyIG1hcHBlZCA9IFtdOwogICAgZm9yICh2YXIgaSA9IDA7IGkgPCBwYXJ0cy5sZW5ndGg7IGkrKykgewogICAgICBtYXBwZWQucHVzaChnZXRNYXBwaW5nKHBhcnRzW2ldKSk7CiAgICB9CiAgICByZXR1cm4gbWFwcGVkLmpvaW4oJy0nKTsKICB9OwoKICB2YXIgcmVuYW1lOwogIGlmIChnb29nLmNzc05hbWVNYXBwaW5nXykgewogICAgcmVuYW1lID0KICAgICAgICBnb29nLmNzc05hbWVNYXBwaW5nU3R5bGVfID09ICdCWV9XSE9MRScgPyBnZXRNYXBwaW5nIDogcmVuYW1lQnlQYXJ0czsKICB9IGVsc2UgewogICAgcmVuYW1lID0gZnVuY3Rpb24oYSkgewogICAgICByZXR1cm4gYTsKICAgIH07CiAgfQoKICB2YXIgcmVzdWx0ID0KICAgICAgb3B0X21vZGlmaWVyID8gY2xhc3NOYW1lICsgJy0nICsgcmVuYW1lKG9wdF9tb2RpZmllcikgOiByZW5hbWUoY2xhc3NOYW1lKTsKCiAgLy8gVGhlIHNwZWNpYWwgQ0xPU1VSRV9DU1NfTkFNRV9NQVBfRk4gYWxsb3dzIHVzZXJzIHRvIHNwZWNpZnkgZnVydGhlcgogIC8vIHByb2Nlc3Npbmcgb2YgdGhlIGNsYXNzIG5hbWUuCiAgaWYgKGdvb2cuZ2xvYmFsLkNMT1NVUkVfQ1NTX05BTUVfTUFQX0ZOKSB7CiAgICByZXR1cm4gZ29vZy5nbG9iYWwuQ0xPU1VSRV9DU1NfTkFNRV9NQVBfRk4ocmVzdWx0KTsKICB9CgogIHJldHVybiByZXN1bHQ7Cn07CgoKLyoqCiAqIFNldHMgdGhlIG1hcCB0byBjaGVjayB3aGVuIHJldHVybmluZyBhIHZhbHVlIGZyb20gZ29vZy5nZXRDc3NOYW1lKCkuIEV4YW1wbGU6CiAqIDxwcmU+CiAqIGdvb2cuc2V0Q3NzTmFtZU1hcHBpbmcoewogKiAgICJnb29nIjogImEiLAogKiAgICJkaXNhYmxlZCI6ICJiIiwKICogfSk7CiAqCiAqIHZhciB4ID0gZ29vZy5nZXRDc3NOYW1lKCdnb29nJyk7CiAqIC8vIFRoZSBmb2xsb3dpbmcgZXZhbHVhdGVzIHRvOiAiYSBhLWIiLgogKiBnb29nLmdldENzc05hbWUoJ2dvb2cnKSArICcgJyArIGdvb2cuZ2V0Q3NzTmFtZSh4LCAnZGlzYWJsZWQnKQogKiA8L3ByZT4KICogV2hlbiBkZWNsYXJlZCBhcyBhIG1hcCBvZiBzdHJpbmcgbGl0ZXJhbHMgdG8gc3RyaW5nIGxpdGVyYWxzLCB0aGUgSlNDb21waWxlcgogKiB3aWxsIHJlcGxhY2UgYWxsIGNhbGxzIHRvIGdvb2cuZ2V0Q3NzTmFtZSgpIHVzaW5nIHRoZSBzdXBwbGllZCBtYXAgaWYgdGhlCiAqIC0tcHJvY2Vzc19jbG9zdXJlX3ByaW1pdGl2ZXMgZmxhZyBpcyBzZXQuCiAqCiAqIEBwYXJhbSB7IU9iamVjdH0gbWFwcGluZyBBIG1hcCBvZiBzdHJpbmdzIHRvIHN0cmluZ3Mgd2hlcmUga2V5cyBhcmUgcG9zc2libGUKICogICAgIGFyZ3VtZW50cyB0byBnb29nLmdldENzc05hbWUoKSBhbmQgdmFsdWVzIGFyZSB0aGUgY29ycmVzcG9uZGluZyB2YWx1ZXMKICogICAgIHRoYXQgc2hvdWxkIGJlIHJldHVybmVkLgogKiBAcGFyYW0ge3N0cmluZz19IG9wdF9zdHlsZSBUaGUgc3R5bGUgb2YgY3NzIG5hbWUgbWFwcGluZy4gVGhlcmUgYXJlIHR3byB2YWxpZAogKiAgICAgb3B0aW9uczogJ0JZX1BBUlQnLCBhbmQgJ0JZX1dIT0xFJy4KICogQHNlZSBnb29nLmdldENzc05hbWUgZm9yIGEgZGVzY3JpcHRpb24uCiAqLwpnb29nLnNldENzc05hbWVNYXBwaW5nID0gZnVuY3Rpb24obWFwcGluZywgb3B0X3N0eWxlKSB7CiAgZ29vZy5jc3NOYW1lTWFwcGluZ18gPSBtYXBwaW5nOwogIGdvb2cuY3NzTmFtZU1hcHBpbmdTdHlsZV8gPSBvcHRfc3R5bGU7Cn07CgoKLyoqCiAqIFRvIHVzZSBDU1MgcmVuYW1pbmcgaW4gY29tcGlsZWQgbW9kZSwgb25lIG9mIHRoZSBpbnB1dCBmaWxlcyBzaG91bGQgaGF2ZSBhCiAqIGNhbGwgdG8gZ29vZy5zZXRDc3NOYW1lTWFwcGluZygpIHdpdGggYW4gb2JqZWN0IGxpdGVyYWwgdGhhdCB0aGUgSlNDb21waWxlcgogKiBjYW4gZXh0cmFjdCBhbmQgdXNlIHRvIHJlcGxhY2UgYWxsIGNhbGxzIHRvIGdvb2cuZ2V0Q3NzTmFtZSgpLiBJbiB1bmNvbXBpbGVkCiAqIG1vZGUsIEphdmFTY3JpcHQgY29kZSBzaG91bGQgYmUgbG9hZGVkIGJlZm9yZSB0aGlzIGJhc2UuanMgZmlsZSB0aGF0IGRlY2xhcmVzCiAqIGEgZ2xvYmFsIHZhcmlhYmxlLCBDTE9TVVJFX0NTU19OQU1FX01BUFBJTkcsIHdoaWNoIGlzIHVzZWQgYmVsb3cuIFRoaXMgaXMKICogdG8gZW5zdXJlIHRoYXQgdGhlIG1hcHBpbmcgaXMgbG9hZGVkIGJlZm9yZSBhbnkgY2FsbHMgdG8gZ29vZy5nZXRDc3NOYW1lKCkKICogYXJlIG1hZGUgaW4gdW5jb21waWxlZCBtb2RlLgogKgogKiBBIGhvb2sgZm9yIG92ZXJyaWRpbmcgdGhlIENTUyBuYW1lIG1hcHBpbmcuCiAqIEB0eXBlIHshT2JqZWN0PHN0cmluZywgc3RyaW5nPnx1bmRlZmluZWR9CiAqLwpnb29nLmdsb2JhbC5DTE9TVVJFX0NTU19OQU1FX01BUFBJTkc7CgoKaWYgKCFDT01QSUxFRCAmJiBnb29nLmdsb2JhbC5DTE9TVVJFX0NTU19OQU1FX01BUFBJTkcpIHsKICAvLyBUaGlzIGRvZXMgbm90IGNhbGwgZ29vZy5zZXRDc3NOYW1lTWFwcGluZygpIGJlY2F1c2UgdGhlIEpTQ29tcGlsZXIKICAvLyByZXF1aXJlcyB0aGF0IGdvb2cuc2V0Q3NzTmFtZU1hcHBpbmcoKSBiZSBjYWxsZWQgd2l0aCBhbiBvYmplY3QgbGl0ZXJhbC4KICBnb29nLmNzc05hbWVNYXBwaW5nXyA9IGdvb2cuZ2xvYmFsLkNMT1NVUkVfQ1NTX05BTUVfTUFQUElORzsKfQoKCi8qKgogKiBHZXRzIGEgbG9jYWxpemVkIG1lc3NhZ2UuCiAqCiAqIFRoaXMgZnVuY3Rpb24gaXMgYSBjb21waWxlciBwcmltaXRpdmUuIElmIHlvdSBnaXZlIHRoZSBjb21waWxlciBhIGxvY2FsaXplZAogKiBtZXNzYWdlIGJ1bmRsZSwgaXQgd2lsbCByZXBsYWNlIHRoZSBzdHJpbmcgYXQgY29tcGlsZS10aW1lIHdpdGggYSBsb2NhbGl6ZWQKICogdmVyc2lvbiwgYW5kIGV4cGFuZCBnb29nLmdldE1zZyBjYWxsIHRvIGEgY29uY2F0ZW5hdGVkIHN0cmluZy4KICoKICogTWVzc2FnZXMgbXVzdCBiZSBpbml0aWFsaXplZCBpbiB0aGUgZm9ybToKICogPGNvZGU+CiAqIHZhciBNU0dfTkFNRSA9IGdvb2cuZ2V0TXNnKCdIZWxsbyB7JHBsYWNlaG9sZGVyfScsIHsncGxhY2Vob2xkZXInOiAnd29ybGQnfSk7CiAqIDwvY29kZT4KICoKICogVGhpcyBmdW5jdGlvbiBwcm9kdWNlcyBhIHN0cmluZyB3aGljaCBzaG91bGQgYmUgdHJlYXRlZCBhcyBwbGFpbiB0ZXh0LiBVc2UKICoge0BsaW5rIGdvb2cuaHRtbC5TYWZlSHRtbEZvcm1hdHRlcn0gaW4gY29uanVuY3Rpb24gd2l0aCBnb29nLmdldE1zZyB0bwogKiBwcm9kdWNlIFNhZmVIdG1sLgogKgogKiBAcGFyYW0ge3N0cmluZ30gc3RyIFRyYW5zbGF0YWJsZSBzdHJpbmcsIHBsYWNlcyBob2xkZXJzIGluIHRoZSBmb3JtIHskZm9vfS4KICogQHBhcmFtIHtPYmplY3Q8c3RyaW5nLCBzdHJpbmc+PX0gb3B0X3ZhbHVlcyBNYXBzIHBsYWNlIGhvbGRlciBuYW1lIHRvIHZhbHVlLgogKiBAcGFyYW0ge3todG1sOiBib29sZWFufT19IG9wdF9vcHRpb25zIE9wdGlvbnM6CiAqICAgICBodG1sOiBFc2NhcGUgJzwnIGluIHN0ciB0byAnJmx0OycuIFVzZWQgYnkgQ2xvc3VyZSBUZW1wbGF0ZXMgd2hlcmUgdGhlCiAqICAgICBnZW5lcmF0ZWQgY29kZSBzaXplIGFuZCBwZXJmb3JtYW5jZSBpcyBjcml0aWNhbCB3aGljaCBpcyB3aHkge0BsaW5rCiAqICAgICBnb29nLmh0bWwuU2FmZUh0bWxGb3JtYXR0ZXJ9IGlzIG5vdCB1c2VkLiBUaGUgdmFsdWUgbXVzdCBiZSBsaXRlcmFsIHRydWUKICogICAgIG9yIGZhbHNlLgogKiBAcmV0dXJuIHtzdHJpbmd9IG1lc3NhZ2Ugd2l0aCBwbGFjZWhvbGRlcnMgZmlsbGVkLgogKi8KZ29vZy5nZXRNc2cgPSBmdW5jdGlvbihzdHIsIG9wdF92YWx1ZXMsIG9wdF9vcHRpb25zKSB7CiAgaWYgKG9wdF9vcHRpb25zICYmIG9wdF9vcHRpb25zLmh0bWwpIHsKICAgIC8vIE5vdGUgdGhhdCAnJicgaXMgbm90IHJlcGxhY2VkIGJlY2F1c2UgdGhlIHRyYW5zbGF0aW9uIGNhbiBjb250YWluIEhUTUwKICAgIC8vIGVudGl0aWVzLgogICAgc3RyID0gc3RyLnJlcGxhY2UoLzwvZywgJyZsdDsnKTsKICB9CiAgaWYgKG9wdF92YWx1ZXMpIHsKICAgIHN0ciA9IHN0ci5yZXBsYWNlKC9ce1wkKFtefV0rKX0vZywgZnVuY3Rpb24obWF0Y2gsIGtleSkgewogICAgICByZXR1cm4gKG9wdF92YWx1ZXMgIT0gbnVsbCAmJiBrZXkgaW4gb3B0X3ZhbHVlcykgPyBvcHRfdmFsdWVzW2tleV0gOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBtYXRjaDsKICAgIH0pOwogIH0KICByZXR1cm4gc3RyOwp9OwoKCi8qKgogKiBHZXRzIGEgbG9jYWxpemVkIG1lc3NhZ2UuIElmIHRoZSBtZXNzYWdlIGRvZXMgbm90IGhhdmUgYSB0cmFuc2xhdGlvbiwgZ2l2ZXMgYQogKiBmYWxsYmFjayBtZXNzYWdlLgogKgogKiBUaGlzIGlzIHVzZWZ1bCB3aGVuIGludHJvZHVjaW5nIGEgbmV3IG1lc3NhZ2UgdGhhdCBoYXMgbm90IHlldCBiZWVuCiAqIHRyYW5zbGF0ZWQgaW50byBhbGwgbGFuZ3VhZ2VzLgogKgogKiBUaGlzIGZ1bmN0aW9uIGlzIGEgY29tcGlsZXIgcHJpbWl0aXZlLiBNdXN0IGJlIHVzZWQgaW4gdGhlIGZvcm06CiAqIDxjb2RlPnZhciB4ID0gZ29vZy5nZXRNc2dXaXRoRmFsbGJhY2soTVNHX0EsIE1TR19CKTs8L2NvZGU+CiAqIHdoZXJlIE1TR19BIGFuZCBNU0dfQiB3ZXJlIGluaXRpYWxpemVkIHdpdGggZ29vZy5nZXRNc2cuCiAqCiAqIEBwYXJhbSB7c3RyaW5nfSBhIFRoZSBwcmVmZXJyZWQgbWVzc2FnZS4KICogQHBhcmFtIHtzdHJpbmd9IGIgVGhlIGZhbGxiYWNrIG1lc3NhZ2UuCiAqIEByZXR1cm4ge3N0cmluZ30gVGhlIGJlc3QgdHJhbnNsYXRlZCBtZXNzYWdlLgogKi8KZ29vZy5nZXRNc2dXaXRoRmFsbGJhY2sgPSBmdW5jdGlvbihhLCBiKSB7CiAgcmV0dXJuIGE7Cn07CgoKLyoqCiAqIEV4cG9zZXMgYW4gdW5vYmZ1c2NhdGVkIGdsb2JhbCBuYW1lc3BhY2UgcGF0aCBmb3IgdGhlIGdpdmVuIG9iamVjdC4KICogTm90ZSB0aGF0IGZpZWxkcyBvZiB0aGUgZXhwb3J0ZWQgb2JqZWN0ICp3aWxsKiBiZSBvYmZ1c2NhdGVkLCB1bmxlc3MgdGhleSBhcmUKICogZXhwb3J0ZWQgaW4gdHVybiB2aWEgdGhpcyBmdW5jdGlvbiBvciBnb29nLmV4cG9ydFByb3BlcnR5LgogKgogKiBBbHNvIGhhbmR5IGZvciBtYWtpbmcgcHVibGljIGl0ZW1zIHRoYXQgYXJlIGRlZmluZWQgaW4gYW5vbnltb3VzIGNsb3N1cmVzLgogKgogKiBleC4gZ29vZy5leHBvcnRTeW1ib2woJ3B1YmxpYy5wYXRoLkZvbycsIEZvbyk7CiAqCiAqIGV4LiBnb29nLmV4cG9ydFN5bWJvbCgncHVibGljLnBhdGguRm9vLnN0YXRpY0Z1bmN0aW9uJywgRm9vLnN0YXRpY0Z1bmN0aW9uKTsKICogICAgIHB1YmxpYy5wYXRoLkZvby5zdGF0aWNGdW5jdGlvbigpOwogKgogKiBleC4gZ29vZy5leHBvcnRTeW1ib2woJ3B1YmxpYy5wYXRoLkZvby5wcm90b3R5cGUubXlNZXRob2QnLAogKiAgICAgICAgICAgICAgICAgICAgICAgRm9vLnByb3RvdHlwZS5teU1ldGhvZCk7CiAqICAgICBuZXcgcHVibGljLnBhdGguRm9vKCkubXlNZXRob2QoKTsKICoKICogQHBhcmFtIHtzdHJpbmd9IHB1YmxpY1BhdGggVW5vYmZ1c2NhdGVkIG5hbWUgdG8gZXhwb3J0LgogKiBAcGFyYW0geyp9IG9iamVjdCBPYmplY3QgdGhlIG5hbWUgc2hvdWxkIHBvaW50IHRvLgogKiBAcGFyYW0ge09iamVjdD19IG9wdF9vYmplY3RUb0V4cG9ydFRvIFRoZSBvYmplY3QgdG8gYWRkIHRoZSBwYXRoIHRvOyBkZWZhdWx0CiAqICAgICBpcyBnb29nLmdsb2JhbC4KICovCmdvb2cuZXhwb3J0U3ltYm9sID0gZnVuY3Rpb24ocHVibGljUGF0aCwgb2JqZWN0LCBvcHRfb2JqZWN0VG9FeHBvcnRUbykgewogIGdvb2cuZXhwb3J0UGF0aF8ocHVibGljUGF0aCwgb2JqZWN0LCBvcHRfb2JqZWN0VG9FeHBvcnRUbyk7Cn07CgoKLyoqCiAqIEV4cG9ydHMgYSBwcm9wZXJ0eSB1bm9iZnVzY2F0ZWQgaW50byB0aGUgb2JqZWN0J3MgbmFtZXNwYWNlLgogKiBleC4gZ29vZy5leHBvcnRQcm9wZXJ0eShGb28sICdzdGF0aWNGdW5jdGlvbicsIEZvby5zdGF0aWNGdW5jdGlvbik7CiAqIGV4LiBnb29nLmV4cG9ydFByb3BlcnR5KEZvby5wcm90b3R5cGUsICdteU1ldGhvZCcsIEZvby5wcm90b3R5cGUubXlNZXRob2QpOwogKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IE9iamVjdCB3aG9zZSBzdGF0aWMgcHJvcGVydHkgaXMgYmVpbmcgZXhwb3J0ZWQuCiAqIEBwYXJhbSB7c3RyaW5nfSBwdWJsaWNOYW1lIFVub2JmdXNjYXRlZCBuYW1lIHRvIGV4cG9ydC4KICogQHBhcmFtIHsqfSBzeW1ib2wgT2JqZWN0IHRoZSBuYW1lIHNob3VsZCBwb2ludCB0by4KICovCmdvb2cuZXhwb3J0UHJvcGVydHkgPSBmdW5jdGlvbihvYmplY3QsIHB1YmxpY05hbWUsIHN5bWJvbCkgewogIG9iamVjdFtwdWJsaWNOYW1lXSA9IHN5bWJvbDsKfTsKCgovKioKICogSW5oZXJpdCB0aGUgcHJvdG90eXBlIG1ldGhvZHMgZnJvbSBvbmUgY29uc3RydWN0b3IgaW50byBhbm90aGVyLgogKgogKiBVc2FnZToKICogPHByZT4KICogZnVuY3Rpb24gUGFyZW50Q2xhc3MoYSwgYikgeyB9CiAqIFBhcmVudENsYXNzLnByb3RvdHlwZS5mb28gPSBmdW5jdGlvbihhKSB7IH07CiAqCiAqIGZ1bmN0aW9uIENoaWxkQ2xhc3MoYSwgYiwgYykgewogKiAgIENoaWxkQ2xhc3MuYmFzZSh0aGlzLCAnY29uc3RydWN0b3InLCBhLCBiKTsKICogfQogKiBnb29nLmluaGVyaXRzKENoaWxkQ2xhc3MsIFBhcmVudENsYXNzKTsKICoKICogdmFyIGNoaWxkID0gbmV3IENoaWxkQ2xhc3MoJ2EnLCAnYicsICdzZWUnKTsKICogY2hpbGQuZm9vKCk7IC8vIFRoaXMgd29ya3MuCiAqIDwvcHJlPgogKgogKiBAcGFyYW0geyFGdW5jdGlvbn0gY2hpbGRDdG9yIENoaWxkIGNsYXNzLgogKiBAcGFyYW0geyFGdW5jdGlvbn0gcGFyZW50Q3RvciBQYXJlbnQgY2xhc3MuCiAqIEBzdXBwcmVzcyB7c3RyaWN0TWlzc2luZ1Byb3BlcnRpZXN9IHN1cGVyQ2xhc3NfIGFuZCBiYXNlIGlzIG5vdCBkZWZpbmVkIG9uCiAqICAgIEZ1bmN0aW9uLgogKi8KZ29vZy5pbmhlcml0cyA9IGZ1bmN0aW9uKGNoaWxkQ3RvciwgcGFyZW50Q3RvcikgewogIC8qKiBAY29uc3RydWN0b3IgKi8KICBmdW5jdGlvbiB0ZW1wQ3RvcigpIHt9CiAgdGVtcEN0b3IucHJvdG90eXBlID0gcGFyZW50Q3Rvci5wcm90b3R5cGU7CiAgY2hpbGRDdG9yLnN1cGVyQ2xhc3NfID0gcGFyZW50Q3Rvci5wcm90b3R5cGU7CiAgY2hpbGRDdG9yLnByb3RvdHlwZSA9IG5ldyB0ZW1wQ3RvcigpOwogIC8qKiBAb3ZlcnJpZGUgKi8KICBjaGlsZEN0b3IucHJvdG90eXBlLmNvbnN0cnVjdG9yID0gY2hpbGRDdG9yOwoKICAvKioKICAgKiBDYWxscyBzdXBlcmNsYXNzIGNvbnN0cnVjdG9yL21ldGhvZC4KICAgKgogICAqIFRoaXMgZnVuY3Rpb24gaXMgb25seSBhdmFpbGFibGUgaWYgeW91IHVzZSBnb29nLmluaGVyaXRzIHRvCiAgICogZXhwcmVzcyBpbmhlcml0YW5jZSByZWxhdGlvbnNoaXBzIGJldHdlZW4gY2xhc3Nlcy4KICAgKgogICAqIE5PVEU6IFRoaXMgaXMgYSByZXBsYWNlbWVudCBmb3IgZ29vZy5iYXNlIGFuZCBmb3Igc3VwZXJDbGFzc18KICAgKiBwcm9wZXJ0eSBkZWZpbmVkIGluIGNoaWxkQ3Rvci4KICAgKgogICAqIEBwYXJhbSB7IU9iamVjdH0gbWUgU2hvdWxkIGFsd2F5cyBiZSAidGhpcyIuCiAgICogQHBhcmFtIHtzdHJpbmd9IG1ldGhvZE5hbWUgVGhlIG1ldGhvZCBuYW1lIHRvIGNhbGwuIENhbGxpbmcKICAgKiAgICAgc3VwZXJjbGFzcyBjb25zdHJ1Y3RvciBjYW4gYmUgZG9uZSB3aXRoIHRoZSBzcGVjaWFsIHN0cmluZwogICAqICAgICAnY29uc3RydWN0b3InLgogICAqIEBwYXJhbSB7Li4uKn0gdmFyX2FyZ3MgVGhlIGFyZ3VtZW50cyB0byBwYXNzIHRvIHN1cGVyY2xhc3MKICAgKiAgICAgbWV0aG9kL2NvbnN0cnVjdG9yLgogICAqIEByZXR1cm4geyp9IFRoZSByZXR1cm4gdmFsdWUgb2YgdGhlIHN1cGVyY2xhc3MgbWV0aG9kL2NvbnN0cnVjdG9yLgogICAqLwogIGNoaWxkQ3Rvci5iYXNlID0gZnVuY3Rpb24obWUsIG1ldGhvZE5hbWUsIHZhcl9hcmdzKSB7CiAgICAvLyBDb3B5aW5nIHVzaW5nIGxvb3AgdG8gYXZvaWQgZGVvcCBkdWUgdG8gcGFzc2luZyBhcmd1bWVudHMgb2JqZWN0IHRvCiAgICAvLyBmdW5jdGlvbi4gVGhpcyBpcyBmYXN0ZXIgaW4gbWFueSBKUyBlbmdpbmVzIGFzIG9mIGxhdGUgMjAxNC4KICAgIHZhciBhcmdzID0gbmV3IEFycmF5KGFyZ3VtZW50cy5sZW5ndGggLSAyKTsKICAgIGZvciAodmFyIGkgPSAyOyBpIDwgYXJndW1lbnRzLmxlbmd0aDsgaSsrKSB7CiAgICAgIGFyZ3NbaSAtIDJdID0gYXJndW1lbnRzW2ldOwogICAgfQogICAgcmV0dXJuIHBhcmVudEN0b3IucHJvdG90eXBlW21ldGhvZE5hbWVdLmFwcGx5KG1lLCBhcmdzKTsKICB9Owp9OwoKCi8qKgogKiBDYWxsIHVwIHRvIHRoZSBzdXBlcmNsYXNzLgogKgogKiBJZiB0aGlzIGlzIGNhbGxlZCBmcm9tIGEgY29uc3RydWN0b3IsIHRoZW4gdGhpcyBjYWxscyB0aGUgc3VwZXJjbGFzcwogKiBjb25zdHJ1Y3RvciB3aXRoIGFyZ3VtZW50cyAxLU4uCiAqCiAqIElmIHRoaXMgaXMgY2FsbGVkIGZyb20gYSBwcm90b3R5cGUgbWV0aG9kLCB0aGVuIHlvdSBtdXN0IHBhc3MgdGhlIG5hbWUgb2YgdGhlCiAqIG1ldGhvZCBhcyB0aGUgc2Vjb25kIGFyZ3VtZW50IHRvIHRoaXMgZnVuY3Rpb24uIElmIHlvdSBkbyBub3QsIHlvdSB3aWxsIGdldCBhCiAqIHJ1bnRpbWUgZXJyb3IuIFRoaXMgY2FsbHMgdGhlIHN1cGVyY2xhc3MnIG1ldGhvZCB3aXRoIGFyZ3VtZW50cyAyLU4uCiAqCiAqIFRoaXMgZnVuY3Rpb24gb25seSB3b3JrcyBpZiB5b3UgdXNlIGdvb2cuaW5oZXJpdHMgdG8gZXhwcmVzcyBpbmhlcml0YW5jZQogKiByZWxhdGlvbnNoaXBzIGJldHdlZW4geW91ciBjbGFzc2VzLgogKgogKiBUaGlzIGZ1bmN0aW9uIGlzIGEgY29tcGlsZXIgcHJpbWl0aXZlLiBBdCBjb21waWxlLXRpbWUsIHRoZSBjb21waWxlciB3aWxsIGRvCiAqIG1hY3JvIGV4cGFuc2lvbiB0byByZW1vdmUgYSBsb3Qgb2YgdGhlIGV4dHJhIG92ZXJoZWFkIHRoYXQgdGhpcyBmdW5jdGlvbgogKiBpbnRyb2R1Y2VzLiBUaGUgY29tcGlsZXIgd2lsbCBhbHNvIGVuZm9yY2UgYSBsb3Qgb2YgdGhlIGFzc3VtcHRpb25zIHRoYXQgdGhpcwogKiBmdW5jdGlvbiBtYWtlcywgYW5kIHRyZWF0IGl0IGFzIGEgY29tcGlsZXIgZXJyb3IgaWYgeW91IGJyZWFrIHRoZW0uCiAqCiAqIEBwYXJhbSB7IU9iamVjdH0gbWUgU2hvdWxkIGFsd2F5cyBiZSAidGhpcyIuCiAqIEBwYXJhbSB7Kj19IG9wdF9tZXRob2ROYW1lIFRoZSBtZXRob2QgbmFtZSBpZiBjYWxsaW5nIGEgc3VwZXIgbWV0aG9kLgogKiBAcGFyYW0gey4uLip9IHZhcl9hcmdzIFRoZSByZXN0IG9mIHRoZSBhcmd1bWVudHMuCiAqIEByZXR1cm4geyp9IFRoZSByZXR1cm4gdmFsdWUgb2YgdGhlIHN1cGVyY2xhc3MgbWV0aG9kLgogKiBAc3VwcHJlc3Mge2VzNVN0cmljdH0gVGhpcyBtZXRob2QgY2FuIG5vdCBiZSB1c2VkIGluIHN0cmljdCBtb2RlLCBidXQKICogICAgIGFsbCBDbG9zdXJlIExpYnJhcnkgY29uc3VtZXJzIG11c3QgZGVwZW5kIG9uIHRoaXMgZmlsZS4KICogQGRlcHJlY2F0ZWQgZ29vZy5iYXNlIGlzIG5vdCBzdHJpY3QgbW9kZSBjb21wYXRpYmxlLiAgUHJlZmVyIHRoZSBzdGF0aWMKICogICAgICJiYXNlIiBtZXRob2QgYWRkZWQgdG8gdGhlIGNvbnN0cnVjdG9yIGJ5IGdvb2cuaW5oZXJpdHMKICogICAgIG9yIEVTNiBjbGFzc2VzIGFuZCB0aGUgInN1cGVyIiBrZXl3b3JkLgogKi8KZ29vZy5iYXNlID0gZnVuY3Rpb24obWUsIG9wdF9tZXRob2ROYW1lLCB2YXJfYXJncykgewogIHZhciBjYWxsZXIgPSBhcmd1bWVudHMuY2FsbGVlLmNhbGxlcjsKCiAgaWYgKGdvb2cuU1RSSUNUX01PREVfQ09NUEFUSUJMRSB8fCAoZ29vZy5ERUJVRyAmJiAhY2FsbGVyKSkgewogICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICdhcmd1bWVudHMuY2FsbGVyIG5vdCBkZWZpbmVkLiAgZ29vZy5iYXNlKCkgY2Fubm90IGJlIHVzZWQgJyArCiAgICAgICAgJ3dpdGggc3RyaWN0IG1vZGUgY29kZS4gU2VlICcgKwogICAgICAgICdodHRwOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNS4xLyNzZWMtQycpOwogIH0KCiAgaWYgKHR5cGVvZiBjYWxsZXIuc3VwZXJDbGFzc18gIT09ICd1bmRlZmluZWQnKSB7CiAgICAvLyBDb3B5aW5nIHVzaW5nIGxvb3AgdG8gYXZvaWQgZGVvcCBkdWUgdG8gcGFzc2luZyBhcmd1bWVudHMgb2JqZWN0IHRvCiAgICAvLyBmdW5jdGlvbi4gVGhpcyBpcyBmYXN0ZXIgaW4gbWFueSBKUyBlbmdpbmVzIGFzIG9mIGxhdGUgMjAxNC4KICAgIHZhciBjdG9yQXJncyA9IG5ldyBBcnJheShhcmd1bWVudHMubGVuZ3RoIC0gMSk7CiAgICBmb3IgKHZhciBpID0gMTsgaSA8IGFyZ3VtZW50cy5sZW5ndGg7IGkrKykgewogICAgICBjdG9yQXJnc1tpIC0gMV0gPSBhcmd1bWVudHNbaV07CiAgICB9CiAgICAvLyBUaGlzIGlzIGEgY29uc3RydWN0b3IuIENhbGwgdGhlIHN1cGVyY2xhc3MgY29uc3RydWN0b3IuCiAgICByZXR1cm4gLyoqIEB0eXBlIHshRnVuY3Rpb259ICovIChjYWxsZXIuc3VwZXJDbGFzc18pCiAgICAgICAgLmNvbnN0cnVjdG9yLmFwcGx5KG1lLCBjdG9yQXJncyk7CiAgfQoKICBpZiAodHlwZW9mIG9wdF9tZXRob2ROYW1lICE9ICdzdHJpbmcnICYmIHR5cGVvZiBvcHRfbWV0aG9kTmFtZSAhPSAnc3ltYm9sJykgewogICAgdGhyb3cgbmV3IEVycm9yKAogICAgICAgICdtZXRob2QgbmFtZXMgcHJvdmlkZWQgdG8gZ29vZy5iYXNlIG11c3QgYmUgYSBzdHJpbmcgb3IgYSBzeW1ib2wnKTsKICB9CgogIC8vIENvcHlpbmcgdXNpbmcgbG9vcCB0byBhdm9pZCBkZW9wIGR1ZSB0byBwYXNzaW5nIGFyZ3VtZW50cyBvYmplY3QgdG8KICAvLyBmdW5jdGlvbi4gVGhpcyBpcyBmYXN0ZXIgaW4gbWFueSBKUyBlbmdpbmVzIGFzIG9mIGxhdGUgMjAxNC4KICB2YXIgYXJncyA9IG5ldyBBcnJheShhcmd1bWVudHMubGVuZ3RoIC0gMik7CiAgZm9yICh2YXIgaSA9IDI7IGkgPCBhcmd1bWVudHMubGVuZ3RoOyBpKyspIHsKICAgIGFyZ3NbaSAtIDJdID0gYXJndW1lbnRzW2ldOwogIH0KICB2YXIgZm91bmRDYWxsZXIgPSBmYWxzZTsKICBmb3IgKHZhciBwcm90byA9IG1lLmNvbnN0cnVjdG9yLnByb3RvdHlwZTsgcHJvdG87CiAgICAgICBwcm90byA9IE9iamVjdC5nZXRQcm90b3R5cGVPZihwcm90bykpIHsKICAgIGlmIChwcm90b1tvcHRfbWV0aG9kTmFtZV0gPT09IGNhbGxlcikgewogICAgICBmb3VuZENhbGxlciA9IHRydWU7CiAgICB9IGVsc2UgaWYgKGZvdW5kQ2FsbGVyKSB7CiAgICAgIHJldHVybiBwcm90b1tvcHRfbWV0aG9kTmFtZV0uYXBwbHkobWUsIGFyZ3MpOwogICAgfQogIH0KCiAgLy8gSWYgd2UgZGlkIG5vdCBmaW5kIHRoZSBjYWxsZXIgaW4gdGhlIHByb3RvdHlwZSBjaGFpbiwgdGhlbiBvbmUgb2YgdHdvCiAgLy8gdGhpbmdzIGhhcHBlbmVkOgogIC8vIDEpIFRoZSBjYWxsZXIgaXMgYW4gaW5zdGFuY2UgbWV0aG9kLgogIC8vIDIpIFRoaXMgbWV0aG9kIHdhcyBub3QgY2FsbGVkIGJ5IHRoZSByaWdodCBjYWxsZXIuCiAgaWYgKG1lW29wdF9tZXRob2ROYW1lXSA9PT0gY2FsbGVyKSB7CiAgICByZXR1cm4gbWUuY29uc3RydWN0b3IucHJvdG90eXBlW29wdF9tZXRob2ROYW1lXS5hcHBseShtZSwgYXJncyk7CiAgfSBlbHNlIHsKICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAnZ29vZy5iYXNlIGNhbGxlZCBmcm9tIGEgbWV0aG9kIG9mIG9uZSBuYW1lICcgKwogICAgICAgICd0byBhIG1ldGhvZCBvZiBhIGRpZmZlcmVudCBuYW1lJyk7CiAgfQp9OwoKCi8qKgogKiBBbGxvdyBmb3IgYWxpYXNpbmcgd2l0aGluIHNjb3BlIGZ1bmN0aW9ucy4gIFRoaXMgZnVuY3Rpb24gZXhpc3RzIGZvcgogKiB1bmNvbXBpbGVkIGNvZGUgLSBpbiBjb21waWxlZCBjb2RlIHRoZSBjYWxscyB3aWxsIGJlIGlubGluZWQgYW5kIHRoZSBhbGlhc2VzCiAqIGFwcGxpZWQuICBJbiB1bmNvbXBpbGVkIGNvZGUgdGhlIGZ1bmN0aW9uIGlzIHNpbXBseSBydW4gc2luY2UgdGhlIGFsaWFzZXMgYXMKICogd3JpdHRlbiBhcmUgdmFsaWQgSmF2YVNjcmlwdC4KICoKICoKICogQHBhcmFtIHtmdW5jdGlvbigpfSBmbiBGdW5jdGlvbiB0byBjYWxsLiAgVGhpcyBmdW5jdGlvbiBjYW4gY29udGFpbiBhbGlhc2VzCiAqICAgICB0byBuYW1lc3BhY2VzIChlLmcuICJ2YXIgZG9tID0gZ29vZy5kb20iKSBvciBjbGFzc2VzCiAqICAgICAoZS5nLiAidmFyIFRpbWVyID0gZ29vZy5UaW1lciIpLgogKi8KZ29vZy5zY29wZSA9IGZ1bmN0aW9uKGZuKSB7CiAgaWYgKGdvb2cuaXNJbk1vZHVsZUxvYWRlcl8oKSkgewogICAgdGhyb3cgbmV3IEVycm9yKCdnb29nLnNjb3BlIGlzIG5vdCBzdXBwb3J0ZWQgd2l0aGluIGEgbW9kdWxlLicpOwogIH0KICBmbi5jYWxsKGdvb2cuZ2xvYmFsKTsKfTsKCgovKgogKiBUbyBzdXBwb3J0IHVuY29tcGlsZWQsIHN0cmljdCBtb2RlIGJ1bmRsZXMgdGhhdCB1c2UgZXZhbCB0byBkaXZpZGUgc291cmNlCiAqIGxpa2Ugc286CiAqICAgIGV2YWwoJ3NvbWVTb3VyY2U7Ly8jIHNvdXJjZVVybCBzb3VyY2VmaWxlLmpzJyk7CiAqIFdlIG5lZWQgdG8gZXhwb3J0IHRoZSBnbG9iYWxseSBkZWZpbmVkIHN5bWJvbHMgImdvb2ciIGFuZCAiQ09NUElMRUQiLgogKiBFeHBvcnRpbmcgImdvb2ciIGJyZWFrcyB0aGUgY29tcGlsZXIgb3B0aW1pemF0aW9ucywgc28gd2UgcmVxdWlyZWQgdGhhdAogKiBiZSBkZWZpbmVkIGV4dGVybmFsbHkuCiAqIE5PVEU6IFdlIGRvbid0IHVzZSBnb29nLmV4cG9ydFN5bWJvbCBoZXJlIGJlY2F1c2Ugd2UgZG9uJ3Qgd2FudCB0byB0cmlnZ2VyCiAqIGV4dGVybiBnZW5lcmF0aW9uIHdoZW4gdGhhdCBjb21waWxlciBvcHRpb24gaXMgZW5hYmxlZC4KICovCmlmICghQ09NUElMRUQpIHsKICBnb29nLmdsb2JhbFsnQ09NUElMRUQnXSA9IENPTVBJTEVEOwp9CgoKLy89PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLy8gZ29vZy5kZWZpbmVDbGFzcyBpbXBsZW1lbnRhdGlvbgovLz09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PQoKCi8qKgogKiBDcmVhdGVzIGEgcmVzdHJpY3RlZCBmb3JtIG9mIGEgQ2xvc3VyZSAiY2xhc3MiOgogKiAgIC0gZnJvbSB0aGUgY29tcGlsZXIncyBwZXJzcGVjdGl2ZSwgdGhlIGluc3RhbmNlIHJldHVybmVkIGZyb20gdGhlCiAqICAgICBjb25zdHJ1Y3RvciBpcyBzZWFsZWQgKG5vIG5ldyBwcm9wZXJ0aWVzIG1heSBiZSBhZGRlZCkuICBUaGlzIGVuYWJsZXMKICogICAgIGJldHRlciBjaGVja3MuCiAqICAgLSB0aGUgY29tcGlsZXIgd2lsbCByZXdyaXRlIHRoaXMgZGVmaW5pdGlvbiB0byBhIGZvcm0gdGhhdCBpcyBvcHRpbWFsCiAqICAgICBmb3IgdHlwZSBjaGVja2luZyBhbmQgb3B0aW1pemF0aW9uIChpbml0aWFsbHkgdGhpcyB3aWxsIGJlIGEgbW9yZQogKiAgICAgdHJhZGl0aW9uYWwgZm9ybSkuCiAqCiAqIEBwYXJhbSB7RnVuY3Rpb259IHN1cGVyQ2xhc3MgVGhlIHN1cGVyY2xhc3MsIE9iamVjdCBvciBudWxsLgogKiBAcGFyYW0ge2dvb2cuZGVmaW5lQ2xhc3MuQ2xhc3NEZXNjcmlwdG9yfSBkZWYKICogICAgIEFuIG9iamVjdCBsaXRlcmFsIGRlc2NyaWJpbmcKICogICAgIHRoZSBjbGFzcy4gIEl0IG1heSBoYXZlIHRoZSBmb2xsb3dpbmcgcHJvcGVydGllczoKICogICAgICJjb25zdHJ1Y3RvciI6IHRoZSBjb25zdHJ1Y3RvciBmdW5jdGlvbgogKiAgICAgInN0YXRpY3MiOiBhbiBvYmplY3QgbGl0ZXJhbCBjb250YWluaW5nIG1ldGhvZHMgdG8gYWRkIHRvIHRoZSBjb25zdHJ1Y3RvcgogKiAgICAgICAgYXMgInN0YXRpYyIgbWV0aG9kcyBvciBhIGZ1bmN0aW9uIHRoYXQgd2lsbCByZWNlaXZlIHRoZSBjb25zdHJ1Y3RvcgogKiAgICAgICAgZnVuY3Rpb24gYXMgaXRzIG9ubHkgcGFyYW1ldGVyIHRvIHdoaWNoIHN0YXRpYyBwcm9wZXJ0aWVzIGNhbgogKiAgICAgICAgYmUgYWRkZWQuCiAqICAgICBhbGwgb3RoZXIgcHJvcGVydGllcyBhcmUgYWRkZWQgdG8gdGhlIHByb3RvdHlwZS4KICogQHJldHVybiB7IUZ1bmN0aW9ufSBUaGUgY2xhc3MgY29uc3RydWN0b3IuCiAqIEBkZXByZWNhdGVkIFVzZSBFUzYgY2xhc3Mgc3ludGF4IGluc3RlYWQuCiAqLwpnb29nLmRlZmluZUNsYXNzID0gZnVuY3Rpb24oc3VwZXJDbGFzcywgZGVmKSB7CiAgLy8gVE9ETyhqb2hubGVueik6IGNvbnNpZGVyIG1ha2luZyB0aGUgc3VwZXJDbGFzcyBhbiBvcHRpb25hbCBwYXJhbWV0ZXIuCiAgdmFyIGNvbnN0cnVjdG9yID0gZGVmLmNvbnN0cnVjdG9yOwogIHZhciBzdGF0aWNzID0gZGVmLnN0YXRpY3M7CiAgLy8gV3JhcCB0aGUgY29uc3RydWN0b3IgcHJpb3IgdG8gc2V0dGluZyB1cCB0aGUgcHJvdG90eXBlIGFuZCBzdGF0aWMgbWV0aG9kcy4KICBpZiAoIWNvbnN0cnVjdG9yIHx8IGNvbnN0cnVjdG9yID09IE9iamVjdC5wcm90b3R5cGUuY29uc3RydWN0b3IpIHsKICAgIGNvbnN0cnVjdG9yID0gZnVuY3Rpb24oKSB7CiAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICdjYW5ub3QgaW5zdGFudGlhdGUgYW4gaW50ZXJmYWNlIChubyBjb25zdHJ1Y3RvciBkZWZpbmVkKS4nKTsKICAgIH07CiAgfQoKICB2YXIgY2xzID0gZ29vZy5kZWZpbmVDbGFzcy5jcmVhdGVTZWFsaW5nQ29uc3RydWN0b3JfKGNvbnN0cnVjdG9yLCBzdXBlckNsYXNzKTsKICBpZiAoc3VwZXJDbGFzcykgewogICAgZ29vZy5pbmhlcml0cyhjbHMsIHN1cGVyQ2xhc3MpOwogIH0KCiAgLy8gUmVtb3ZlIGFsbCB0aGUgcHJvcGVydGllcyB0aGF0IHNob3VsZCBub3QgYmUgY29waWVkIHRvIHRoZSBwcm90b3R5cGUuCiAgZGVsZXRlIGRlZi5jb25zdHJ1Y3RvcjsKICBkZWxldGUgZGVmLnN0YXRpY3M7CgogIGdvb2cuZGVmaW5lQ2xhc3MuYXBwbHlQcm9wZXJ0aWVzXyhjbHMucHJvdG90eXBlLCBkZWYpOwogIGlmIChzdGF0aWNzICE9IG51bGwpIHsKICAgIGlmIChzdGF0aWNzIGluc3RhbmNlb2YgRnVuY3Rpb24pIHsKICAgICAgc3RhdGljcyhjbHMpOwogICAgfSBlbHNlIHsKICAgICAgZ29vZy5kZWZpbmVDbGFzcy5hcHBseVByb3BlcnRpZXNfKGNscywgc3RhdGljcyk7CiAgICB9CiAgfQoKICByZXR1cm4gY2xzOwp9OwoKCi8qKgogKiBAdHlwZWRlZiB7ewogKiAgIGNvbnN0cnVjdG9yOiAoIUZ1bmN0aW9ufHVuZGVmaW5lZCksCiAqICAgc3RhdGljczogKE9iamVjdHx1bmRlZmluZWR8ZnVuY3Rpb24oRnVuY3Rpb24pOnZvaWQpCiAqIH19CiAqLwpnb29nLmRlZmluZUNsYXNzLkNsYXNzRGVzY3JpcHRvcjsKCgovKioKICogQGRlZmluZSB7Ym9vbGVhbn0gV2hldGhlciB0aGUgaW5zdGFuY2VzIHJldHVybmVkIGJ5IGdvb2cuZGVmaW5lQ2xhc3Mgc2hvdWxkCiAqICAgICBiZSBzZWFsZWQgd2hlbiBwb3NzaWJsZS4KICoKICogV2hlbiBzZWFsaW5nIGlzIGRpc2FibGVkIHRoZSBjb25zdHJ1Y3RvciBmdW5jdGlvbiB3aWxsIG5vdCBiZSB3cmFwcGVkIGJ5CiAqIGdvb2cuZGVmaW5lQ2xhc3MsIG1ha2luZyBpdCBpbmNvbXBhdGlibGUgd2l0aCBFUzYgY2xhc3MgbWV0aG9kcy4KICovCmdvb2cuZGVmaW5lQ2xhc3MuU0VBTF9DTEFTU19JTlNUQU5DRVMgPQogICAgZ29vZy5kZWZpbmUoJ2dvb2cuZGVmaW5lQ2xhc3MuU0VBTF9DTEFTU19JTlNUQU5DRVMnLCBnb29nLkRFQlVHKTsKCgovKioKICogSWYgZ29vZy5kZWZpbmVDbGFzcy5TRUFMX0NMQVNTX0lOU1RBTkNFUyBpcyBlbmFibGVkIGFuZCBPYmplY3Quc2VhbCBpcwogKiBkZWZpbmVkLCB0aGlzIGZ1bmN0aW9uIHdpbGwgd3JhcCB0aGUgY29uc3RydWN0b3IgaW4gYSBmdW5jdGlvbiB0aGF0IHNlYWxzIHRoZQogKiByZXN1bHRzIG9mIHRoZSBwcm92aWRlZCBjb25zdHJ1Y3RvciBmdW5jdGlvbi4KICoKICogQHBhcmFtIHshRnVuY3Rpb259IGN0ciBUaGUgY29uc3RydWN0b3Igd2hvc2UgcmVzdWx0cyBtYXliZSBiZSBzZWFsZWQuCiAqIEBwYXJhbSB7RnVuY3Rpb259IHN1cGVyQ2xhc3MgVGhlIHN1cGVyY2xhc3MgY29uc3RydWN0b3IuCiAqIEByZXR1cm4geyFGdW5jdGlvbn0gVGhlIHJlcGxhY2VtZW50IGNvbnN0cnVjdG9yLgogKiBAcHJpdmF0ZQogKi8KZ29vZy5kZWZpbmVDbGFzcy5jcmVhdGVTZWFsaW5nQ29uc3RydWN0b3JfID0gZnVuY3Rpb24oY3RyLCBzdXBlckNsYXNzKSB7CiAgaWYgKCFnb29nLmRlZmluZUNsYXNzLlNFQUxfQ0xBU1NfSU5TVEFOQ0VTKSB7CiAgICAvLyBEbyBub3cgd3JhcCB0aGUgY29uc3RydWN0b3Igd2hlbiBzZWFsaW5nIGlzIGRpc2FibGVkLiBBbmd1bGFyIGNvZGUKICAgIC8vIGRlcGVuZHMgb24gdGhpcyBmb3IgaW5qZWN0aW9uIHRvIHdvcmsgcHJvcGVybHkuCiAgICByZXR1cm4gY3RyOwogIH0KCiAgLy8gQ29tcHV0ZSB3aGV0aGVyIHRoZSBjb25zdHJ1Y3RvciBpcyBzZWFsYWJsZSBhdCBkZWZpbml0aW9uIHRpbWUsIHJhdGhlcgogIC8vIHRoYW4gd2hlbiB0aGUgaW5zdGFuY2UgaXMgYmVpbmcgY29uc3RydWN0ZWQuCiAgdmFyIHN1cGVyY2xhc3NTZWFsYWJsZSA9ICFnb29nLmRlZmluZUNsYXNzLmlzVW5zZWFsYWJsZV8oc3VwZXJDbGFzcyk7CgogIC8qKgogICAqIEB0aGlzIHtPYmplY3R9CiAgICogQHJldHVybiB7P30KICAgKi8KICB2YXIgd3JhcHBlZEN0ciA9IGZ1bmN0aW9uKCkgewogICAgLy8gRG9uJ3Qgc2VhbCBhbiBpbnN0YW5jZSBvZiBhIHN1YmNsYXNzIHdoZW4gaXQgY2FsbHMgdGhlIGNvbnN0cnVjdG9yIG9mCiAgICAvLyBpdHMgc3VwZXIgY2xhc3MgYXMgdGhlcmUgaXMgbW9zdCBsaWtlbHkgc3RpbGwgc2V0dXAgdG8gZG8uCiAgICB2YXIgaW5zdGFuY2UgPSBjdHIuYXBwbHkodGhpcywgYXJndW1lbnRzKSB8fCB0aGlzOwogICAgaW5zdGFuY2VbZ29vZy5VSURfUFJPUEVSVFlfXSA9IGluc3RhbmNlW2dvb2cuVUlEX1BST1BFUlRZX107CgogICAgaWYgKHRoaXMuY29uc3RydWN0b3IgPT09IHdyYXBwZWRDdHIgJiYgc3VwZXJjbGFzc1NlYWxhYmxlICYmCiAgICAgICAgT2JqZWN0LnNlYWwgaW5zdGFuY2VvZiBGdW5jdGlvbikgewogICAgICBPYmplY3Quc2VhbChpbnN0YW5jZSk7CiAgICB9CiAgICByZXR1cm4gaW5zdGFuY2U7CiAgfTsKCiAgcmV0dXJuIHdyYXBwZWRDdHI7Cn07CgoKLyoqCiAqIEBwYXJhbSB7RnVuY3Rpb259IGN0ciBUaGUgY29uc3RydWN0b3IgdG8gdGVzdC4KICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB0aGUgY29uc3RydWN0b3IgaGFzIGJlZW4gdGFnZ2VkIGFzIHVuc2VhbGFibGUKICogICAgIHVzaW5nIGdvb2cudGFnVW5zZWFsYWJsZUNsYXNzLgogKiBAcHJpdmF0ZQogKi8KZ29vZy5kZWZpbmVDbGFzcy5pc1Vuc2VhbGFibGVfID0gZnVuY3Rpb24oY3RyKSB7CiAgcmV0dXJuIGN0ciAmJiBjdHIucHJvdG90eXBlICYmCiAgICAgIGN0ci5wcm90b3R5cGVbZ29vZy5VTlNFQUxBQkxFX0NPTlNUUlVDVE9SX1BST1BFUlRZX107Cn07CgoKLy8gVE9ETyhqb2hubGVueik6IHNoYXJlIHRoZXNlIHZhbHVlcyB3aXRoIHRoZSBnb29nLm9iamVjdAovKioKICogVGhlIG5hbWVzIG9mIHRoZSBmaWVsZHMgdGhhdCBhcmUgZGVmaW5lZCBvbiBPYmplY3QucHJvdG90eXBlLgogKiBAdHlwZSB7IUFycmF5PHN0cmluZz59CiAqIEBwcml2YXRlCiAqIEBjb25zdAogKi8KZ29vZy5kZWZpbmVDbGFzcy5PQkpFQ1RfUFJPVE9UWVBFX0ZJRUxEU18gPSBbCiAgJ2NvbnN0cnVjdG9yJywgJ2hhc093blByb3BlcnR5JywgJ2lzUHJvdG90eXBlT2YnLCAncHJvcGVydHlJc0VudW1lcmFibGUnLAogICd0b0xvY2FsZVN0cmluZycsICd0b1N0cmluZycsICd2YWx1ZU9mJwpdOwoKCi8vIFRPRE8oam9obmxlbnopOiBzaGFyZSB0aGlzIGZ1bmN0aW9uIHdpdGggdGhlIGdvb2cub2JqZWN0Ci8qKgogKiBAcGFyYW0geyFPYmplY3R9IHRhcmdldCBUaGUgb2JqZWN0IHRvIGFkZCBwcm9wZXJ0aWVzIHRvLgogKiBAcGFyYW0geyFPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IHRvIGNvcHkgcHJvcGVydGllcyBmcm9tLgogKiBAcHJpdmF0ZQogKi8KZ29vZy5kZWZpbmVDbGFzcy5hcHBseVByb3BlcnRpZXNfID0gZnVuY3Rpb24odGFyZ2V0LCBzb3VyY2UpIHsKICAvLyBUT0RPKGpvaG5sZW56KTogdXBkYXRlIHRoaXMgdG8gc3VwcG9ydCBFUzUgZ2V0dGVycy9zZXR0ZXJzCgogIHZhciBrZXk7CiAgZm9yIChrZXkgaW4gc291cmNlKSB7CiAgICBpZiAoT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKHNvdXJjZSwga2V5KSkgewogICAgICB0YXJnZXRba2V5XSA9IHNvdXJjZVtrZXldOwogICAgfQogIH0KCiAgLy8gRm9yIElFIHRoZSBmb3ItaW4tbG9vcCBkb2VzIG5vdCBjb250YWluIGFueSBwcm9wZXJ0aWVzIHRoYXQgYXJlIG5vdAogIC8vIGVudW1lcmFibGUgb24gdGhlIHByb3RvdHlwZSBvYmplY3QgKGZvciBleGFtcGxlIGlzUHJvdG90eXBlT2YgZnJvbQogIC8vIE9iamVjdC5wcm90b3R5cGUpIGFuZCBpdCB3aWxsIGFsc28gbm90IGluY2x1ZGUgJ3JlcGxhY2UnIG9uIG9iamVjdHMgdGhhdAogIC8vIGV4dGVuZCBTdHJpbmcgYW5kIGNoYW5nZSAncmVwbGFjZScgKG5vdCB0aGF0IGl0IGlzIGNvbW1vbiBmb3IgYW55b25lIHRvCiAgLy8gZXh0ZW5kIGFueXRoaW5nIGV4Y2VwdCBPYmplY3QpLgogIGZvciAodmFyIGkgPSAwOyBpIDwgZ29vZy5kZWZpbmVDbGFzcy5PQkpFQ1RfUFJPVE9UWVBFX0ZJRUxEU18ubGVuZ3RoOyBpKyspIHsKICAgIGtleSA9IGdvb2cuZGVmaW5lQ2xhc3MuT0JKRUNUX1BST1RPVFlQRV9GSUVMRFNfW2ldOwogICAgaWYgKE9iamVjdC5wcm90b3R5cGUuaGFzT3duUHJvcGVydHkuY2FsbChzb3VyY2UsIGtleSkpIHsKICAgICAgdGFyZ2V0W2tleV0gPSBzb3VyY2Vba2V5XTsKICAgIH0KICB9Cn07CgoKLyoqCiAqIFNlYWxpbmcgY2xhc3NlcyBicmVha3MgdGhlIG9sZGVyIGlkaW9tIG9mIGFzc2lnbmluZyBwcm9wZXJ0aWVzIG9uIHRoZQogKiBwcm90b3R5cGUgcmF0aGVyIHRoYW4gaW4gdGhlIGNvbnN0cnVjdG9yLiBBcyBzdWNoLCBnb29nLmRlZmluZUNsYXNzCiAqIG11c3Qgbm90IHNlYWwgc3ViY2xhc3NlcyBvZiB0aGVzZSBvbGQtc3R5bGUgY2xhc3NlcyB1bnRpbCB0aGV5IGFyZSBmaXhlZC4KICogVW50aWwgdGhlbiwgdGhpcyBtYXJrcyBhIGNsYXNzIGFzICJicm9rZW4iLCBpbnN0cnVjdGluZyBkZWZpbmVDbGFzcwogKiBub3QgdG8gc2VhbCBzdWJjbGFzc2VzLgogKiBAcGFyYW0geyFGdW5jdGlvbn0gY3RyIFRoZSBsZWdhY3kgY29uc3RydWN0b3IgdG8gdGFnIGFzIHVuc2VhbGFibGUuCiAqLwpnb29nLnRhZ1Vuc2VhbGFibGVDbGFzcyA9IGZ1bmN0aW9uKGN0cikgewogIGlmICghQ09NUElMRUQgJiYgZ29vZy5kZWZpbmVDbGFzcy5TRUFMX0NMQVNTX0lOU1RBTkNFUykgewogICAgY3RyLnByb3RvdHlwZVtnb29nLlVOU0VBTEFCTEVfQ09OU1RSVUNUT1JfUFJPUEVSVFlfXSA9IHRydWU7CiAgfQp9OwoKCi8qKgogKiBOYW1lIGZvciB1bnNlYWxhYmxlIHRhZyBwcm9wZXJ0eS4KICogQGNvbnN0IEBwcml2YXRlIHtzdHJpbmd9CiAqLwpnb29nLlVOU0VBTEFCTEVfQ09OU1RSVUNUT1JfUFJPUEVSVFlfID0gJ2dvb2dfZGVmaW5lQ2xhc3NfbGVnYWN5X3Vuc2VhbGFibGUnOwoKCi8vIFRoZXJlJ3MgYSBidWcgaW4gdGhlIGNvbXBpbGVyIHdoZXJlIHdpdGhvdXQgY29sbGFwc2UgcHJvcGVydGllcyB0aGUKLy8gQ2xvc3VyZSBuYW1lc3BhY2UgZGVmaW5lcyBkbyBub3QgZ3VhcmQgY29kZSBjb3JyZWN0bHkuIFRvIGhlbHAgcmVkdWNlIGNvZGUKLy8gc2l6ZSBhbHNvIGNoZWNrIGZvciAhQ09NUElMRUQgZXZlbiB0aG91Z2ggaXQgcmVkdW5kYW50IHVudGlsIHRoaXMgaXMgZml4ZWQuCmlmICghQ09NUElMRUQgJiYgZ29vZy5ERVBFTkRFTkNJRVNfRU5BQkxFRCkgewoKICAvKioKICAgKiBUcmllcyB0byBkZXRlY3Qgd2hldGhlciBpcyBpbiB0aGUgY29udGV4dCBvZiBhbiBIVE1MIGRvY3VtZW50LgogICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgaXQgbG9va3MgbGlrZSBIVE1MIGRvY3VtZW50LgogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5pbkh0bWxEb2N1bWVudF8gPSBmdW5jdGlvbigpIHsKICAgIC8qKiBAdHlwZSB7IURvY3VtZW50fSAqLwogICAgdmFyIGRvYyA9IGdvb2cuZ2xvYmFsLmRvY3VtZW50OwogICAgcmV0dXJuIGRvYyAhPSBudWxsICYmICd3cml0ZScgaW4gZG9jOyAgLy8gWFVMRG9jdW1lbnQgbWlzc2VzIHdyaXRlLgogIH07CgoKICAvKioKICAgKiBXZSdkIGxpa2UgdG8gY2hlY2sgZm9yIGlmIHRoZSBkb2N1bWVudCByZWFkeVN0YXRlIGlzICdsb2FkaW5nJzsgaG93ZXZlcgogICAqIHRoZXJlIGFyZSBidWdzIG9uIElFIDEwIGFuZCBiZWxvdyB3aGVyZSB0aGUgcmVhZHlTdGF0ZSBiZWluZyBhbnl0aGluZyBvdGhlcgogICAqIHRoYW4gJ2NvbXBsZXRlJyBpcyBub3QgcmVsaWFibGUuCiAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgKiBAcHJpdmF0ZQogICAqLwogIGdvb2cuaXNEb2N1bWVudExvYWRpbmdfID0gZnVuY3Rpb24oKSB7CiAgICAvLyBhdHRhY2hFdmVudCBpcyBhdmFpbGFibGUgb24gSUUgNiB0aHJ1IDEwIG9ubHksIGFuZCB0aHVzIGNhbiBiZSB1c2VkIHRvCiAgICAvLyBkZXRlY3QgdGhvc2UgYnJvd3NlcnMuCiAgICAvKiogQHR5cGUgeyFIVE1MRG9jdW1lbnR9ICovCiAgICB2YXIgZG9jID0gZ29vZy5nbG9iYWwuZG9jdW1lbnQ7CiAgICByZXR1cm4gZG9jLmF0dGFjaEV2ZW50ID8gZG9jLnJlYWR5U3RhdGUgIT0gJ2NvbXBsZXRlJyA6CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZG9jLnJlYWR5U3RhdGUgPT0gJ2xvYWRpbmcnOwogIH07CgoKICAvKioKICAgKiBUcmllcyB0byBkZXRlY3QgdGhlIGJhc2UgcGF0aCBvZiBiYXNlLmpzIHNjcmlwdCB0aGF0IGJvb3RzdHJhcHMgQ2xvc3VyZS4KICAgKiBAcHJpdmF0ZQogICAqLwogIGdvb2cuZmluZEJhc2VQYXRoXyA9IGZ1bmN0aW9uKCkgewogICAgaWYgKGdvb2cuZ2xvYmFsLkNMT1NVUkVfQkFTRV9QQVRIICE9IHVuZGVmaW5lZCAmJgogICAgICAgIC8vIEFudGkgRE9NLWNsb2JiZXJpbmcgcnVudGltZSBjaGVjayAoYi8zNzczNjU3NikuCiAgICAgICAgdHlwZW9mIGdvb2cuZ2xvYmFsLkNMT1NVUkVfQkFTRV9QQVRIID09PSAnc3RyaW5nJykgewogICAgICBnb29nLmJhc2VQYXRoID0gZ29vZy5nbG9iYWwuQ0xPU1VSRV9CQVNFX1BBVEg7CiAgICAgIHJldHVybjsKICAgIH0gZWxzZSBpZiAoIWdvb2cuaW5IdG1sRG9jdW1lbnRfKCkpIHsKICAgICAgcmV0dXJuOwogICAgfQogICAgLyoqIEB0eXBlIHshRG9jdW1lbnR9ICovCiAgICB2YXIgZG9jID0gZ29vZy5nbG9iYWwuZG9jdW1lbnQ7CiAgICAvLyBJZiB3ZSBoYXZlIGEgY3VycmVudFNjcmlwdCBhdmFpbGFibGUsIHVzZSBpdCBleGNsdXNpdmVseS4KICAgIHZhciBjdXJyZW50U2NyaXB0ID0gZG9jLmN1cnJlbnRTY3JpcHQ7CiAgICBpZiAoY3VycmVudFNjcmlwdCkgewogICAgICB2YXIgc2NyaXB0cyA9IFtjdXJyZW50U2NyaXB0XTsKICAgIH0gZWxzZSB7CiAgICAgIHZhciBzY3JpcHRzID0gZG9jLmdldEVsZW1lbnRzQnlUYWdOYW1lKCdTQ1JJUFQnKTsKICAgIH0KICAgIC8vIFNlYXJjaCBiYWNrd2FyZHMgc2luY2UgdGhlIGN1cnJlbnQgc2NyaXB0IGlzIGluIGFsbW9zdCBhbGwgY2FzZXMgdGhlIG9uZQogICAgLy8gdGhhdCBoYXMgYmFzZS5qcy4KICAgIGZvciAodmFyIGkgPSBzY3JpcHRzLmxlbmd0aCAtIDE7IGkgPj0gMDsgLS1pKSB7CiAgICAgIHZhciBzY3JpcHQgPSAvKiogQHR5cGUgeyFIVE1MU2NyaXB0RWxlbWVudH0gKi8gKHNjcmlwdHNbaV0pOwogICAgICB2YXIgc3JjID0gc2NyaXB0LnNyYzsKICAgICAgdmFyIHFtYXJrID0gc3JjLmxhc3RJbmRleE9mKCc/Jyk7CiAgICAgIHZhciBsID0gcW1hcmsgPT0gLTEgPyBzcmMubGVuZ3RoIDogcW1hcms7CiAgICAgIGlmIChzcmMuc3Vic3RyKGwgLSA3LCA3KSA9PSAnYmFzZS5qcycpIHsKICAgICAgICBnb29nLmJhc2VQYXRoID0gc3JjLnN1YnN0cigwLCBsIC0gNyk7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICB9CiAgfTsKCiAgZ29vZy5maW5kQmFzZVBhdGhfKCk7CgogIC8qKiBAc3RydWN0IEBjb25zdHJ1Y3RvciBAZmluYWwgKi8KICBnb29nLlRyYW5zcGlsZXIgPSBmdW5jdGlvbigpIHsKICAgIC8qKiBAcHJpdmF0ZSB7P09iamVjdDxzdHJpbmcsIGJvb2xlYW4+fSAqLwogICAgdGhpcy5yZXF1aXJlc1RyYW5zcGlsYXRpb25fID0gbnVsbDsKICAgIC8qKiBAcHJpdmF0ZSB7c3RyaW5nfSAqLwogICAgdGhpcy50cmFuc3BpbGF0aW9uVGFyZ2V0XyA9IGdvb2cuVFJBTlNQSUxFX1RPX0xBTkdVQUdFOwogIH07CgoKICAvKioKICAgKiBSZXR1cm5zIGEgbmV3bHkgY3JlYXRlZCBtYXAgZnJvbSBsYW5ndWFnZSBtb2RlIHN0cmluZyB0byBhIGJvb2xlYW4KICAgKiBpbmRpY2F0aW5nIHdoZXRoZXIgdHJhbnNwaWxhdGlvbiBzaG91bGQgYmUgZG9uZSBmb3IgdGhhdCBtb2RlIGFzIHdlbGwgYXMKICAgKiB0aGUgaGlnaGVzdCBsZXZlbCBsYW5ndWFnZSB0aGF0IHRoaXMgZW52aXJvbm1lbnQgc3VwcG9ydHMuCiAgICoKICAgKiBHdWFyYW50ZWVkIGludmFyaWFudDoKICAgKiBGb3IgYW55IHR3byBtb2RlcywgbDEgYW5kIGwyIHdoZXJlIGwyIGlzIGEgbmV3ZXIgbW9kZSB0aGFuIGwxLAogICAqIGBtYXBbbDFdID09IHRydWVgIGltcGxpZXMgdGhhdCBgbWFwW2wyXSA9PSB0cnVlYC4KICAgKgogICAqIE5vdGUgdGhpcyBtZXRob2QgaXMgZXh0cmFjdGVkIGFuZCB1c2VkIGVsc2V3aGVyZSwgc28gaXQgY2Fubm90IHJlbHkgb24KICAgKiBhbnl0aGluZyBleHRlcm5hbCAoaXQgc2hvdWxkIGVhc2lseSBiZSBhYmxlIHRvIGJlIHRyYW5zZm9ybWVkIGludG8gYQogICAqIHN0YW5kYWxvbmUsIHRvcCBsZXZlbCBmdW5jdGlvbikuCiAgICoKICAgKiBAcHJpdmF0ZQogICAqIEByZXR1cm4ge3sKICAgKiAgIHRhcmdldDogc3RyaW5nLAogICAqICAgbWFwOiAhT2JqZWN0PHN0cmluZywgYm9vbGVhbj4KICAgKiB9fQogICAqLwogIGdvb2cuVHJhbnNwaWxlci5wcm90b3R5cGUuY3JlYXRlUmVxdWlyZXNUcmFuc3BpbGF0aW9uXyA9IGZ1bmN0aW9uKCkgewogICAgdmFyIHRyYW5zcGlsYXRpb25UYXJnZXQgPSAnZXMzJzsKICAgIHZhciAvKiogIU9iamVjdDxzdHJpbmcsIGJvb2xlYW4+ICovIHJlcXVpcmVzVHJhbnNwaWxhdGlvbiA9IHsnZXMzJzogZmFsc2V9OwogICAgdmFyIHRyYW5zcGlsYXRpb25SZXF1aXJlZEZvckFsbExhdGVyTW9kZXMgPSBmYWxzZTsKCiAgICAvKioKICAgICAqIEFkZHMgYW4gZW50cnkgdG8gcmVxdWlyZXNUcmFuc3BsaWF0aW9uIGZvciB0aGUgZ2l2ZW4gbGFuZ3VhZ2UgbW9kZS4KICAgICAqCiAgICAgKiBJTVBPUlRBTlQ6IENhbGxzIG11c3QgYmUgbWFkZSBpbiBvcmRlciBmcm9tIG9sZGVzdCB0byBuZXdlc3QgbGFuZ3VhZ2UKICAgICAqIG1vZGUuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gbW9kZU5hbWUKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oKTogYm9vbGVhbn0gaXNTdXBwb3J0ZWQgUmV0dXJucyB0cnVlIGlmIHRoZSBKUyBlbmdpbmUKICAgICAqICAgICBzdXBwb3J0cyB0aGUgZ2l2ZW4gbW9kZS4KICAgICAqLwogICAgZnVuY3Rpb24gYWRkTmV3ZXJMYW5ndWFnZVRyYW5zcGlsYXRpb25DaGVjayhtb2RlTmFtZSwgaXNTdXBwb3J0ZWQpIHsKICAgICAgaWYgKHRyYW5zcGlsYXRpb25SZXF1aXJlZEZvckFsbExhdGVyTW9kZXMpIHsKICAgICAgICByZXF1aXJlc1RyYW5zcGlsYXRpb25bbW9kZU5hbWVdID0gdHJ1ZTsKICAgICAgfSBlbHNlIGlmIChpc1N1cHBvcnRlZCgpKSB7CiAgICAgICAgdHJhbnNwaWxhdGlvblRhcmdldCA9IG1vZGVOYW1lOwogICAgICAgIHJlcXVpcmVzVHJhbnNwaWxhdGlvblttb2RlTmFtZV0gPSBmYWxzZTsKICAgICAgfSBlbHNlIHsKICAgICAgICByZXF1aXJlc1RyYW5zcGlsYXRpb25bbW9kZU5hbWVdID0gdHJ1ZTsKICAgICAgICB0cmFuc3BpbGF0aW9uUmVxdWlyZWRGb3JBbGxMYXRlck1vZGVzID0gdHJ1ZTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogRG9lcyB0aGUgZ2l2ZW4gY29kZSBldmFsdWF0ZSB3aXRob3V0IHN5bnRheCBlcnJvcnMgYW5kIHJldHVybiBhIHRydXRoeQogICAgICogcmVzdWx0PwogICAgICovCiAgICBmdW5jdGlvbiAvKiogYm9vbGVhbiAqLyBldmFsQ2hlY2soLyoqIHN0cmluZyAqLyBjb2RlKSB7CiAgICAgIHRyeSB7CiAgICAgICAgcmV0dXJuICEhZXZhbChjb2RlKTsKICAgICAgfSBjYXRjaCAoaWdub3JlZCkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfQoKICAgIHZhciB1c2VyQWdlbnQgPSBnb29nLmdsb2JhbC5uYXZpZ2F0b3IgJiYgZ29vZy5nbG9iYWwubmF2aWdhdG9yLnVzZXJBZ2VudCA/CiAgICAgICAgZ29vZy5nbG9iYWwubmF2aWdhdG9yLnVzZXJBZ2VudCA6CiAgICAgICAgJyc7CgogICAgLy8gSWRlbnRpZnkgRVMzLW9ubHkgYnJvd3NlcnMgYnkgdGhlaXIgaW5jb3JyZWN0IHRyZWF0bWVudCBvZiBjb21tYXMuCiAgICBhZGROZXdlckxhbmd1YWdlVHJhbnNwaWxhdGlvbkNoZWNrKCdlczUnLCBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIGV2YWxDaGVjaygnWzEsXS5sZW5ndGg9PTEnKTsKICAgIH0pOwogICAgYWRkTmV3ZXJMYW5ndWFnZVRyYW5zcGlsYXRpb25DaGVjaygnZXM2JywgZnVuY3Rpb24oKSB7CiAgICAgIC8vIEVkZ2UgaGFzIGEgbm9uLWRldGVybWluaXN0aWMgKGkuZS4sIG5vdCByZXByb2R1Y2libGUpIGJ1ZyB3aXRoIEVTNjoKICAgICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL01pY3Jvc29mdC9DaGFrcmFDb3JlL2lzc3Vlcy8xNDk2LgogICAgICB2YXIgcmUgPSAvRWRnZVwvKFxkKykoXC5cZCkqL2k7CiAgICAgIHZhciBlZGdlVXNlckFnZW50ID0gdXNlckFnZW50Lm1hdGNoKHJlKTsKICAgICAgaWYgKGVkZ2VVc2VyQWdlbnQpIHsKICAgICAgICAvLyBUaGUgUmVmbGVjdC5jb25zdHJ1Y3QgdGVzdCBiZWxvdyBpcyBmbGFreSBvbiBFZGdlLiBJdCBjYW4gc29tZXRpbWVzCiAgICAgICAgLy8gcGFzcyBvciBmYWlsIG9uIDQwIDE1LjE1MDYzLCBzbyBqdXN0IGV4aXQgZWFybHkgZm9yIEVkZ2UgYW5kIHRyZWF0CiAgICAgICAgLy8gaXQgYXMgRVM1LiBVbnRpbCB3ZSdyZSBvbiBhIG1vcmUgdXAgdG8gZGF0ZSB2ZXJzaW9uIGp1c3QgYWx3YXlzIHVzZQogICAgICAgIC8vIEVTNS4gU2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9NaWNyb3NvZnQvQ2hha3JhQ29yZS9pc3N1ZXMvMzIxNy4KICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgLy8gVGVzdCBlczY6IFtGRjUwICg/KSwgRWRnZSAxNCAoPyksIENocm9tZSA1MF0KICAgICAgLy8gICAoYSkgZGVmYXVsdCBwYXJhbXMgKHNwZWNpZmljYWxseSBzaGFkb3dpbmcgbG9jYWxzKSwKICAgICAgLy8gICAoYikgZGVzdHJ1Y3R1cmluZywgKGMpIGJsb2NrLXNjb3BlZCBmdW5jdGlvbnMsCiAgICAgIC8vICAgKGQpIGZvci1vZiAoY29uc3QpLCAoZSkgbmV3LnRhcmdldC9SZWZsZWN0LmNvbnN0cnVjdAogICAgICB2YXIgZXM2ZnVsbFRlc3QgPQogICAgICAgICAgJ2NsYXNzIFh7Y29uc3RydWN0b3IoKXtpZihuZXcudGFyZ2V0IT1TdHJpbmcpdGhyb3cgMTt0aGlzLng9NDJ9fScgKwogICAgICAgICAgJ2xldCBxPVJlZmxlY3QuY29uc3RydWN0KFgsW10sU3RyaW5nKTtpZihxLnghPTQyfHwhKHEgaW5zdGFuY2VvZiAnICsKICAgICAgICAgICdTdHJpbmcpKXRocm93IDE7Zm9yKGNvbnN0IGEgb2ZbMiwzXSl7aWYoYT09Miljb250aW51ZTtmdW5jdGlvbiAnICsKICAgICAgICAgICdmKHo9e2F9KXtsZXQgYT0wO3JldHVybiB6LmF9e2Z1bmN0aW9uIGYoKXtyZXR1cm4gMDt9fXJldHVybiBmKCknICsKICAgICAgICAgICc9PTN9JzsKCiAgICAgIHJldHVybiBldmFsQ2hlY2soJygoKT0+eyJ1c2Ugc3RyaWN0IjsnICsgZXM2ZnVsbFRlc3QgKyAnfSkoKScpOwogICAgfSk7CiAgICAvLyAqKiBhbmQgKio9IGFyZSB0aGUgb25seSBuZXcgZmVhdHVyZXMgaW4gJ2VzNycKICAgIGFkZE5ld2VyTGFuZ3VhZ2VUcmFuc3BpbGF0aW9uQ2hlY2soJ2VzNycsIGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gZXZhbENoZWNrKCcyICoqIDIgPT0gNCcpOwogICAgfSk7CiAgICAvLyBhc3luYyBmdW5jdGlvbnMgYXJlIHRoZSBvbmx5IG5ldyBmZWF0dXJlcyBpbiAnZXM4JwogICAgYWRkTmV3ZXJMYW5ndWFnZVRyYW5zcGlsYXRpb25DaGVjaygnZXM4JywgZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBldmFsQ2hlY2soJ2FzeW5jICgpID0+IDEsIHRydWUnKTsKICAgIH0pOwogICAgYWRkTmV3ZXJMYW5ndWFnZVRyYW5zcGlsYXRpb25DaGVjaygnZXM5JywgZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBldmFsQ2hlY2soJyh7Li4ucmVzdH0gPSB7fSksIHRydWUnKTsKICAgIH0pOwogICAgYWRkTmV3ZXJMYW5ndWFnZVRyYW5zcGlsYXRpb25DaGVjaygnZXNfbmV4dCcsIGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gZmFsc2U7ICAvLyBhc3N1bWUgaXQgYWx3YXlzIG5lZWQgdG8gdHJhbnNwaWxlCiAgICB9KTsKICAgIHJldHVybiB7dGFyZ2V0OiB0cmFuc3BpbGF0aW9uVGFyZ2V0LCBtYXA6IHJlcXVpcmVzVHJhbnNwaWxhdGlvbn07CiAgfTsKCgogIC8qKgogICAqIERldGVybWluZXMgd2hldGhlciB0aGUgZ2l2ZW4gbGFuZ3VhZ2UgbmVlZHMgdG8gYmUgdHJhbnNwaWxlZC4KICAgKiBAcGFyYW0ge3N0cmluZ30gbGFuZwogICAqIEBwYXJhbSB7c3RyaW5nfHVuZGVmaW5lZH0gbW9kdWxlCiAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgKi8KICBnb29nLlRyYW5zcGlsZXIucHJvdG90eXBlLm5lZWRzVHJhbnNwaWxlID0gZnVuY3Rpb24obGFuZywgbW9kdWxlKSB7CiAgICBpZiAoZ29vZy5UUkFOU1BJTEUgPT0gJ2Fsd2F5cycpIHsKICAgICAgcmV0dXJuIHRydWU7CiAgICB9IGVsc2UgaWYgKGdvb2cuVFJBTlNQSUxFID09ICduZXZlcicpIHsKICAgICAgcmV0dXJuIGZhbHNlOwogICAgfSBlbHNlIGlmICghdGhpcy5yZXF1aXJlc1RyYW5zcGlsYXRpb25fKSB7CiAgICAgIHZhciBvYmogPSB0aGlzLmNyZWF0ZVJlcXVpcmVzVHJhbnNwaWxhdGlvbl8oKTsKICAgICAgdGhpcy5yZXF1aXJlc1RyYW5zcGlsYXRpb25fID0gb2JqLm1hcDsKICAgICAgdGhpcy50cmFuc3BpbGF0aW9uVGFyZ2V0XyA9IHRoaXMudHJhbnNwaWxhdGlvblRhcmdldF8gfHwgb2JqLnRhcmdldDsKICAgIH0KICAgIGlmIChsYW5nIGluIHRoaXMucmVxdWlyZXNUcmFuc3BpbGF0aW9uXykgewogICAgICBpZiAodGhpcy5yZXF1aXJlc1RyYW5zcGlsYXRpb25fW2xhbmddKSB7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0gZWxzZSBpZiAoCiAgICAgICAgICBnb29nLmluSHRtbERvY3VtZW50XygpICYmIG1vZHVsZSA9PSAnZXM2JyAmJgogICAgICAgICAgISgnbm9Nb2R1bGUnIGluIGdvb2cuZ2xvYmFsLmRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3NjcmlwdCcpKSkgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfSBlbHNlIHsKICAgICAgdGhyb3cgbmV3IEVycm9yKCdVbmtub3duIGxhbmd1YWdlIG1vZGU6ICcgKyBsYW5nKTsKICAgIH0KICB9OwoKCiAgLyoqCiAgICogTGF6aWx5IHJldHJpZXZlcyB0aGUgdHJhbnNwaWxlciBhbmQgYXBwbGllcyBpdCB0byB0aGUgc291cmNlLgogICAqIEBwYXJhbSB7c3RyaW5nfSBjb2RlIEpTIGNvZGUuCiAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggUGF0aCB0byB0aGUgY29kZS4KICAgKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSB0cmFuc3BpbGVkIGNvZGUuCiAgICovCiAgZ29vZy5UcmFuc3BpbGVyLnByb3RvdHlwZS50cmFuc3BpbGUgPSBmdW5jdGlvbihjb2RlLCBwYXRoKSB7CiAgICAvLyBUT0RPKGpvaG5wbGFpc3RlZCk6IFdlIHNob3VsZCBkZWxldGUgZ29vZy50cmFuc3BpbGVfIGFuZCBqdXN0IGhhdmUgdGhpcwogICAgLy8gZnVuY3Rpb24uIEJ1dCB0aGVyZSdzIHNvbWUgY29tcGlsZSBlcnJvciBhdG0gd2hlcmUgZ29vZy5nbG9iYWwgaXMgYmVpbmcKICAgIC8vIHN0cmlwcGVkIGluY29ycmVjdGx5IHdpdGhvdXQgdGhpcy4KICAgIHJldHVybiBnb29nLnRyYW5zcGlsZV8oY29kZSwgcGF0aCwgdGhpcy50cmFuc3BpbGF0aW9uVGFyZ2V0Xyk7CiAgfTsKCgogIC8qKiBAcHJpdmF0ZSBAZmluYWwgeyFnb29nLlRyYW5zcGlsZXJ9ICovCiAgZ29vZy50cmFuc3BpbGVyXyA9IG5ldyBnb29nLlRyYW5zcGlsZXIoKTsKCiAgLyoqCiAgICogUmV3cml0ZXMgY2xvc2luZyBzY3JpcHQgdGFncyBpbiBpbnB1dCB0byBhdm9pZCBlbmRpbmcgYW4gZW5jbG9zaW5nIHNjcmlwdAogICAqIHRhZy4KICAgKgogICAqIEBwYXJhbSB7c3RyaW5nfSBzdHIKICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICogQHByaXZhdGUKICAgKi8KICBnb29nLnByb3RlY3RTY3JpcHRUYWdfID0gZnVuY3Rpb24oc3RyKSB7CiAgICByZXR1cm4gc3RyLnJlcGxhY2UoLzxcLyhTQ1JJUFQpL2lnLCAnXFx4M2MvJDEnKTsKICB9OwoKCiAgLyoqCiAgICogQSBkZWJ1ZyBsb2FkZXIgaXMgcmVzcG9uc2libGUgZm9yIGRvd25sb2FkaW5nIGFuZCBleGVjdXRpbmcgamF2YXNjcmlwdAogICAqIGZpbGVzIGluIGFuIHVuYnVuZGxlZCwgdW5jb21waWxlZCBlbnZpcm9ubWVudC4KICAgKgogICAqIFRoaXMgY2FuIGJlIGN1c3RpbWl6ZWQgdmlhIHRoZSBzZXREZXBlbmRlbmN5RmFjdG9yeSBtZXRob2QsIG9yIGJ5CiAgICogQ0xPU1VSRV9JTVBPUlRfU0NSSVBUL0NMT1NVUkVfTE9BRF9GSUxFX1NZTkMuCiAgICoKICAgKiBAc3RydWN0IEBjb25zdHJ1Y3RvciBAZmluYWwgQHByaXZhdGUKICAgKi8KICBnb29nLkRlYnVnTG9hZGVyXyA9IGZ1bmN0aW9uKCkgewogICAgLyoqIEBwcml2YXRlIEBjb25zdCB7IU9iamVjdDxzdHJpbmcsICFnb29nLkRlcGVuZGVuY3k+fSAqLwogICAgdGhpcy5kZXBlbmRlbmNpZXNfID0ge307CiAgICAvKiogQHByaXZhdGUgQGNvbnN0IHshT2JqZWN0PHN0cmluZywgc3RyaW5nPn0gKi8KICAgIHRoaXMuaWRUb1BhdGhfID0ge307CiAgICAvKiogQHByaXZhdGUgQGNvbnN0IHshT2JqZWN0PHN0cmluZywgYm9vbGVhbj59ICovCiAgICB0aGlzLndyaXR0ZW5fID0ge307CiAgICAvKiogQHByaXZhdGUgQGNvbnN0IHshQXJyYXk8IWdvb2cuRGVwZW5kZW5jeT59ICovCiAgICB0aGlzLmxvYWRpbmdEZXBzXyA9IFtdOwogICAgLyoqIEBwcml2YXRlIHshQXJyYXk8IWdvb2cuRGVwZW5kZW5jeT59ICovCiAgICB0aGlzLmRlcHNUb0xvYWRfID0gW107CiAgICAvKiogQHByaXZhdGUge2Jvb2xlYW59ICovCiAgICB0aGlzLnBhdXNlZF8gPSBmYWxzZTsKICAgIC8qKiBAcHJpdmF0ZSB7IWdvb2cuRGVwZW5kZW5jeUZhY3Rvcnl9ICovCiAgICB0aGlzLmZhY3RvcnlfID0gbmV3IGdvb2cuRGVwZW5kZW5jeUZhY3RvcnkoZ29vZy50cmFuc3BpbGVyXyk7CiAgICAvKiogQHByaXZhdGUgQGNvbnN0IHshT2JqZWN0PHN0cmluZywgIUZ1bmN0aW9uPn0gKi8KICAgIHRoaXMuZGVmZXJyZWRDYWxsYmFja3NfID0ge307CiAgICAvKiogQHByaXZhdGUgQGNvbnN0IHshQXJyYXk8c3RyaW5nPn0gKi8KICAgIHRoaXMuZGVmZXJyZWRRdWV1ZV8gPSBbXTsKICB9OwoKICAvKioKICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBuYW1lc3BhY2VzCiAgICogQHBhcmFtIHtmdW5jdGlvbigpOiB1bmRlZmluZWR9IGNhbGxiYWNrIEZ1bmN0aW9uIHRvIGNhbGwgb25jZSBhbGwgdGhlCiAgICogICAgIG5hbWVzcGFjZXMgaGF2ZSBsb2FkZWQuCiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmJvb3RzdHJhcCA9IGZ1bmN0aW9uKG5hbWVzcGFjZXMsIGNhbGxiYWNrKSB7CiAgICB2YXIgY2IgPSBjYWxsYmFjazsKICAgIGZ1bmN0aW9uIHJlc29sdmUoKSB7CiAgICAgIGlmIChjYikgewogICAgICAgIGdvb2cuZ2xvYmFsLnNldFRpbWVvdXQoY2IsIDApOwogICAgICAgIGNiID0gbnVsbDsKICAgICAgfQogICAgfQoKICAgIGlmICghbmFtZXNwYWNlcy5sZW5ndGgpIHsKICAgICAgcmVzb2x2ZSgpOwogICAgICByZXR1cm47CiAgICB9CgogICAgdmFyIGRlcHMgPSBbXTsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbmFtZXNwYWNlcy5sZW5ndGg7IGkrKykgewogICAgICB2YXIgcGF0aCA9IHRoaXMuZ2V0UGF0aEZyb21EZXBzXyhuYW1lc3BhY2VzW2ldKTsKICAgICAgaWYgKCFwYXRoKSB7CiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdVbnJlZ29uaXplZCBuYW1lc3BhY2U6ICcgKyBuYW1lc3BhY2VzW2ldKTsKICAgICAgfQogICAgICBkZXBzLnB1c2godGhpcy5kZXBlbmRlbmNpZXNfW3BhdGhdKTsKICAgIH0KCiAgICB2YXIgcmVxdWlyZSA9IGdvb2cucmVxdWlyZTsKICAgIHZhciBsb2FkZWQgPSAwOwogICAgZm9yICh2YXIgaSA9IDA7IGkgPCBuYW1lc3BhY2VzLmxlbmd0aDsgaSsrKSB7CiAgICAgIHJlcXVpcmUobmFtZXNwYWNlc1tpXSk7CiAgICAgIGRlcHNbaV0ub25Mb2FkKGZ1bmN0aW9uKCkgewogICAgICAgIGlmICgrK2xvYWRlZCA9PSBuYW1lc3BhY2VzLmxlbmd0aCkgewogICAgICAgICAgcmVzb2x2ZSgpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CiAgfTsKCgogIC8qKgogICAqIExvYWRzIHRoZSBDbG9zdXJlIERlcGVuZGVuY3kgZmlsZS4KICAgKgogICAqIEV4cG9zZWQgYSBwdWJsaWMgZnVuY3Rpb24gc28gQ0xPU1VSRV9OT19ERVBTIGNhbiBiZSBzZXQgdG8gZmFsc2UsIGJhc2UKICAgKiBsb2FkZWQsIHNldERlcGVuZGVuY3lGYWN0b3J5IGNhbGxlZCwgYW5kIHRoZW4gdGhpcyBjYWxsZWQuIGkuZS4gYWxsb3dzCiAgICogY3VzdG9tIGxvYWRpbmcgb2YgdGhlIGRlcHMgZmlsZS4KICAgKi8KICBnb29nLkRlYnVnTG9hZGVyXy5wcm90b3R5cGUubG9hZENsb3N1cmVEZXBzID0gZnVuY3Rpb24oKSB7CiAgICAvLyBDaXJjdW12ZW50IGFkZERlcGVuZGVuY3ksIHdoaWNoIHdvdWxkIHRyeSB0byB0cmFuc3BpbGUgZGVwcy5qcyBpZgogICAgLy8gdHJhbnNwaWxlIGlzIHNldCB0byBhbHdheXMuCiAgICB2YXIgcmVsUGF0aCA9ICdkZXBzLmpzJzsKICAgIHRoaXMuZGVwc1RvTG9hZF8ucHVzaCh0aGlzLmZhY3RvcnlfLmNyZWF0ZURlcGVuZGVuY3koCiAgICAgICAgZ29vZy5ub3JtYWxpemVQYXRoXyhnb29nLmJhc2VQYXRoICsgcmVsUGF0aCksIHJlbFBhdGgsIFtdLCBbXSwge30sCiAgICAgICAgZmFsc2UpKTsKICAgIHRoaXMubG9hZERlcHNfKCk7CiAgfTsKCgogIC8qKgogICAqIE5vdGlmaWVzIHRoZSBkZWJ1ZyBsb2FkZXIgd2hlbiBhIGRlcGVuZGVuY3kgaGFzIGJlZW4gcmVxdWVzdGVkLgogICAqCiAgICogQHBhcmFtIHtzdHJpbmd9IGFic1BhdGhPcklkIFBhdGggb2YgdGhlIGRlcGVuZGVuY3kgb3IgZ29vZyBpZC4KICAgKiBAcGFyYW0ge2Jvb2xlYW49fSBvcHRfZm9yY2UKICAgKi8KICBnb29nLkRlYnVnTG9hZGVyXy5wcm90b3R5cGUucmVxdWVzdGVkID0gZnVuY3Rpb24oYWJzUGF0aE9ySWQsIG9wdF9mb3JjZSkgewogICAgdmFyIHBhdGggPSB0aGlzLmdldFBhdGhGcm9tRGVwc18oYWJzUGF0aE9ySWQpOwogICAgaWYgKHBhdGggJiYKICAgICAgICAob3B0X2ZvcmNlIHx8IHRoaXMuYXJlRGVwc0xvYWRlZF8odGhpcy5kZXBlbmRlbmNpZXNfW3BhdGhdLnJlcXVpcmVzKSkpIHsKICAgICAgdmFyIGNhbGxiYWNrID0gdGhpcy5kZWZlcnJlZENhbGxiYWNrc19bcGF0aF07CiAgICAgIGlmIChjYWxsYmFjaykgewogICAgICAgIGRlbGV0ZSB0aGlzLmRlZmVycmVkQ2FsbGJhY2tzX1twYXRoXTsKICAgICAgICBjYWxsYmFjaygpOwogICAgICB9CiAgICB9CiAgfTsKCgogIC8qKgogICAqIFNldHMgdGhlIGRlcGVuZGVuY3kgZmFjdG9yeSwgd2hpY2ggY2FuIGJlIHVzZWQgdG8gY3JlYXRlIGN1c3RvbQogICAqIGdvb2cuRGVwZW5kZW5jeSBpbXBsZW1lbnRhdGlvbnMgdG8gY29udHJvbCBob3cgZGVwZW5kZW5jaWVzIGFyZSBsb2FkZWQuCiAgICoKICAgKiBAcGFyYW0geyFnb29nLkRlcGVuZGVuY3lGYWN0b3J5fSBmYWN0b3J5CiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLnNldERlcGVuZGVuY3lGYWN0b3J5ID0gZnVuY3Rpb24oZmFjdG9yeSkgewogICAgdGhpcy5mYWN0b3J5XyA9IGZhY3Rvcnk7CiAgfTsKCgogIC8qKgogICAqIFRyYXZzZXJzZXMgdGhlIGRlcGVuZGVuY3kgZ3JhcGggYW5kIHF1ZXVlcyB0aGUgZ2l2ZW4gZGVwZW5kZW5jeSwgYW5kIGFsbCBvZgogICAqIGl0cyB0cmFuc2l0aXZlIGRlcGVuZGVuY2llcywgZm9yIGxvYWRpbmcgYW5kIHRoZW4gc3RhcnRzIGxvYWRpbmcgaWYgbm90CiAgICogcGF1c2VkLgogICAqCiAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWVzcGFjZQogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmxvYWRfID0gZnVuY3Rpb24obmFtZXNwYWNlKSB7CiAgICBpZiAoIXRoaXMuZ2V0UGF0aEZyb21EZXBzXyhuYW1lc3BhY2UpKSB7CiAgICAgIHZhciBlcnJvck1lc3NhZ2UgPSAnZ29vZy5yZXF1aXJlIGNvdWxkIG5vdCBmaW5kOiAnICsgbmFtZXNwYWNlOwoKICAgICAgZ29vZy5sb2dUb0NvbnNvbGVfKGVycm9yTWVzc2FnZSk7CiAgICAgIHRocm93IEVycm9yKGVycm9yTWVzc2FnZSk7CiAgICB9IGVsc2UgewogICAgICB2YXIgbG9hZGVyID0gdGhpczsKCiAgICAgIHZhciBkZXBzID0gW107CgogICAgICAvKiogQHBhcmFtIHtzdHJpbmd9IG5hbWVzcGFjZSAqLwogICAgICB2YXIgdmlzaXQgPSBmdW5jdGlvbihuYW1lc3BhY2UpIHsKICAgICAgICB2YXIgcGF0aCA9IGxvYWRlci5nZXRQYXRoRnJvbURlcHNfKG5hbWVzcGFjZSk7CgogICAgICAgIGlmICghcGF0aCkgewogICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdCYWQgZGVwZW5kZW5jeSBwYXRoIG9yIHN5bWJvbDogJyArIG5hbWVzcGFjZSk7CiAgICAgICAgfQoKICAgICAgICBpZiAobG9hZGVyLndyaXR0ZW5fW3BhdGhdKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBsb2FkZXIud3JpdHRlbl9bcGF0aF0gPSB0cnVlOwoKICAgICAgICB2YXIgZGVwID0gbG9hZGVyLmRlcGVuZGVuY2llc19bcGF0aF07CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBkZXAucmVxdWlyZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGlmICghZ29vZy5pc1Byb3ZpZGVkXyhkZXAucmVxdWlyZXNbaV0pKSB7CiAgICAgICAgICAgIHZpc2l0KGRlcC5yZXF1aXJlc1tpXSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBkZXBzLnB1c2goZGVwKTsKICAgICAgfTsKCiAgICAgIHZpc2l0KG5hbWVzcGFjZSk7CgogICAgICB2YXIgd2FzTG9hZGluZyA9ICEhdGhpcy5kZXBzVG9Mb2FkXy5sZW5ndGg7CiAgICAgIHRoaXMuZGVwc1RvTG9hZF8gPSB0aGlzLmRlcHNUb0xvYWRfLmNvbmNhdChkZXBzKTsKCiAgICAgIGlmICghdGhpcy5wYXVzZWRfICYmICF3YXNMb2FkaW5nKSB7CiAgICAgICAgdGhpcy5sb2FkRGVwc18oKTsKICAgICAgfQogICAgfQogIH07CgoKICAvKioKICAgKiBMb2FkcyBhbnkgcXVldWVkIGRlcGVuZGVuY2llcyB1bnRpbCB0aGV5IGFyZSBhbGwgbG9hZGVkIG9yIHBhdXNlZC4KICAgKgogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmxvYWREZXBzXyA9IGZ1bmN0aW9uKCkgewogICAgdmFyIGxvYWRlciA9IHRoaXM7CiAgICB2YXIgcGF1c2VkID0gdGhpcy5wYXVzZWRfOwoKICAgIHdoaWxlICh0aGlzLmRlcHNUb0xvYWRfLmxlbmd0aCAmJiAhcGF1c2VkKSB7CiAgICAgIChmdW5jdGlvbigpIHsKICAgICAgICB2YXIgbG9hZENhbGxEb25lID0gZmFsc2U7CiAgICAgICAgdmFyIGRlcCA9IGxvYWRlci5kZXBzVG9Mb2FkXy5zaGlmdCgpOwoKICAgICAgICB2YXIgbG9hZGVkID0gZmFsc2U7CiAgICAgICAgbG9hZGVyLmxvYWRpbmdfKGRlcCk7CgogICAgICAgIHZhciBjb250cm9sbGVyID0gewogICAgICAgICAgcGF1c2U6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBpZiAobG9hZENhbGxEb25lKSB7CiAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdDYW5ub3QgY2FsbCBwYXVzZSBhZnRlciB0aGUgY2FsbCB0byBsb2FkLicpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHBhdXNlZCA9IHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0sCiAgICAgICAgICByZXN1bWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBpZiAobG9hZENhbGxEb25lKSB7CiAgICAgICAgICAgICAgbG9hZGVyLnJlc3VtZV8oKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAvLyBTb21lIGRlcCBjYWxsZWQgcGF1c2UgYW5kIHRoZW4gcmVzdW1lIGluIHRoZSBzYW1lIGxvYWQgY2FsbC4KICAgICAgICAgICAgICAvLyBKdXN0IGtlZXAgcnVubmluZyB0aGlzIHNhbWUgbG9vcC4KICAgICAgICAgICAgICBwYXVzZWQgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgfSwKICAgICAgICAgIGxvYWRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIGlmIChsb2FkZWQpIHsKICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0RvdWJsZSBjYWxsIHRvIGxvYWRlZC4nKTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgbG9hZGVkID0gdHJ1ZTsKICAgICAgICAgICAgbG9hZGVyLmxvYWRlZF8oZGVwKTsKICAgICAgICAgIH0sCiAgICAgICAgICBwZW5kaW5nOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgLy8gRGVmZW5zaXZlIGNvcHkuCiAgICAgICAgICAgIHZhciBwZW5kaW5nID0gW107CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbG9hZGVyLmxvYWRpbmdEZXBzXy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgIHBlbmRpbmcucHVzaChsb2FkZXIubG9hZGluZ0RlcHNfW2ldKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gcGVuZGluZzsKICAgICAgICAgIH0sCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEBwYXJhbSB7Z29vZy5Nb2R1bGVUeXBlfSB0eXBlCiAgICAgICAgICAgKi8KICAgICAgICAgIHNldE1vZHVsZVN0YXRlOiBmdW5jdGlvbih0eXBlKSB7CiAgICAgICAgICAgIGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfID0gewogICAgICAgICAgICAgIHR5cGU6IHR5cGUsCiAgICAgICAgICAgICAgbW9kdWxlTmFtZTogJycsCiAgICAgICAgICAgICAgZGVjbGFyZUxlZ2FjeU5hbWVzcGFjZTogZmFsc2UKICAgICAgICAgICAgfTsKICAgICAgICAgIH0sCiAgICAgICAgICAvKiogQHR5cGUge2Z1bmN0aW9uKHN0cmluZywgc3RyaW5nLCBzdHJpbmc9KX0gKi8KICAgICAgICAgIHJlZ2lzdGVyRXM2TW9kdWxlRXhwb3J0czogZnVuY3Rpb24oCiAgICAgICAgICAgICAgcGF0aCwgZXhwb3J0cywgb3B0X2Nsb3N1cmVOYW1lc3BhY2UpIHsKICAgICAgICAgICAgaWYgKG9wdF9jbG9zdXJlTmFtZXNwYWNlKSB7CiAgICAgICAgICAgICAgZ29vZy5sb2FkZWRNb2R1bGVzX1tvcHRfY2xvc3VyZU5hbWVzcGFjZV0gPSB7CiAgICAgICAgICAgICAgICBleHBvcnRzOiBleHBvcnRzLAogICAgICAgICAgICAgICAgdHlwZTogZ29vZy5Nb2R1bGVUeXBlLkVTNiwKICAgICAgICAgICAgICAgIG1vZHVsZUlkOiBvcHRfY2xvc3VyZU5hbWVzcGFjZSB8fCAnJwogICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgIH0sCiAgICAgICAgICAvKiogQHR5cGUge2Z1bmN0aW9uKHN0cmluZywgPyl9ICovCiAgICAgICAgICByZWdpc3Rlckdvb2dNb2R1bGVFeHBvcnRzOiBmdW5jdGlvbihtb2R1bGVJZCwgZXhwb3J0cykgewogICAgICAgICAgICBnb29nLmxvYWRlZE1vZHVsZXNfW21vZHVsZUlkXSA9IHsKICAgICAgICAgICAgICBleHBvcnRzOiBleHBvcnRzLAogICAgICAgICAgICAgIHR5cGU6IGdvb2cuTW9kdWxlVHlwZS5HT09HLAogICAgICAgICAgICAgIG1vZHVsZUlkOiBtb2R1bGVJZAogICAgICAgICAgICB9OwogICAgICAgICAgfSwKICAgICAgICAgIGNsZWFyTW9kdWxlU3RhdGU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBnb29nLm1vZHVsZUxvYWRlclN0YXRlXyA9IG51bGw7CiAgICAgICAgICB9LAogICAgICAgICAgZGVmZXI6IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIGlmIChsb2FkQ2FsbERvbmUpIHsKICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoCiAgICAgICAgICAgICAgICAgICdDYW5ub3QgcmVnaXN0ZXIgd2l0aCBkZWZlciBhZnRlciB0aGUgY2FsbCB0byBsb2FkLicpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxvYWRlci5kZWZlcl8oZGVwLCBjYWxsYmFjayk7CiAgICAgICAgICB9LAogICAgICAgICAgYXJlRGVwc0xvYWRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBsb2FkZXIuYXJlRGVwc0xvYWRlZF8oZGVwLnJlcXVpcmVzKTsKICAgICAgICAgIH0KICAgICAgICB9OwoKICAgICAgICB0cnkgewogICAgICAgICAgZGVwLmxvYWQoY29udHJvbGxlcik7CiAgICAgICAgfSBmaW5hbGx5IHsKICAgICAgICAgIGxvYWRDYWxsRG9uZSA9IHRydWU7CiAgICAgICAgfQogICAgICB9KSgpOwogICAgfQoKICAgIGlmIChwYXVzZWQpIHsKICAgICAgdGhpcy5wYXVzZV8oKTsKICAgIH0KICB9OwoKCiAgLyoqIEBwcml2YXRlICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLnBhdXNlXyA9IGZ1bmN0aW9uKCkgewogICAgdGhpcy5wYXVzZWRfID0gdHJ1ZTsKICB9OwoKCiAgLyoqIEBwcml2YXRlICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLnJlc3VtZV8gPSBmdW5jdGlvbigpIHsKICAgIGlmICh0aGlzLnBhdXNlZF8pIHsKICAgICAgdGhpcy5wYXVzZWRfID0gZmFsc2U7CiAgICAgIHRoaXMubG9hZERlcHNfKCk7CiAgICB9CiAgfTsKCgogIC8qKgogICAqIE1hcmtzIHRoZSBnaXZlbiBkZXBlbmRlbmN5IGFzIGxvYWRpbmcgKGxvYWQgaGFzIGJlZW4gY2FsbGVkIGJ1dCBpdCBoYXMgbm90CiAgICogeWV0IG1hcmtlZCBpdHNlbGYgYXMgZmluaXNoZWQpLiBVc2VmdWwgZm9yIGRlcGVuZGVuY2llcyB0aGF0IHdhbnQgdG8ga25vdwogICAqIHdoYXQgZWxzZSBpcyBsb2FkaW5nLiBFeGFtcGxlOiBnb29nLm1vZHVsZXMgY2Fubm90IGV2YWwgaWYgdGhlcmUgYXJlCiAgICogbG9hZGluZyBkZXBlbmRlbmNpZXMuCiAgICoKICAgKiBAcGFyYW0geyFnb29nLkRlcGVuZGVuY3l9IGRlcAogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmxvYWRpbmdfID0gZnVuY3Rpb24oZGVwKSB7CiAgICB0aGlzLmxvYWRpbmdEZXBzXy5wdXNoKGRlcCk7CiAgfTsKCgogIC8qKgogICAqIE1hcmtzIHRoZSBnaXZlbiBkZXBlbmRlbmN5IGFzIGhhdmluZyBmaW5pc2hlZCBsb2FkaW5nIGFuZCBiZWluZyBhdmFpbGFibGUKICAgKiBmb3IgcmVxdWlyZS4KICAgKgogICAqIEBwYXJhbSB7IWdvb2cuRGVwZW5kZW5jeX0gZGVwCiAgICogQHByaXZhdGUKICAgKi8KICBnb29nLkRlYnVnTG9hZGVyXy5wcm90b3R5cGUubG9hZGVkXyA9IGZ1bmN0aW9uKGRlcCkgewogICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLmxvYWRpbmdEZXBzXy5sZW5ndGg7IGkrKykgewogICAgICBpZiAodGhpcy5sb2FkaW5nRGVwc19baV0gPT0gZGVwKSB7CiAgICAgICAgdGhpcy5sb2FkaW5nRGVwc18uc3BsaWNlKGksIDEpOwogICAgICAgIGJyZWFrOwogICAgICB9CiAgICB9CgogICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLmRlZmVycmVkUXVldWVfLmxlbmd0aDsgaSsrKSB7CiAgICAgIGlmICh0aGlzLmRlZmVycmVkUXVldWVfW2ldID09IGRlcC5wYXRoKSB7CiAgICAgICAgdGhpcy5kZWZlcnJlZFF1ZXVlXy5zcGxpY2UoaSwgMSk7CiAgICAgICAgYnJlYWs7CiAgICAgIH0KICAgIH0KCiAgICBpZiAodGhpcy5sb2FkaW5nRGVwc18ubGVuZ3RoID09IHRoaXMuZGVmZXJyZWRRdWV1ZV8ubGVuZ3RoICYmCiAgICAgICAgIXRoaXMuZGVwc1RvTG9hZF8ubGVuZ3RoKSB7CiAgICAgIC8vIFNvbWV0aGluZyBoYXMgYXNrZWQgdG8gbG9hZCB0aGVzZSwgYnV0IHRoZXkgbWF5IG5vdCBiZSBkaXJlY3RseQogICAgICAvLyByZXF1aXJlZCBhZ2FpbiBsYXRlciwgc28gbG9hZCB0aGVtIG5vdyB0aGF0IHdlIGtub3cgd2UncmUgZG9uZSBsb2FkaW5nCiAgICAgIC8vIGV2ZXJ5dGhpbmcgZWxzZS4gZS5nLiBhIGdvb2cgbW9kdWxlIGVudHJ5IHBvaW50LgogICAgICB3aGlsZSAodGhpcy5kZWZlcnJlZFF1ZXVlXy5sZW5ndGgpIHsKICAgICAgICB0aGlzLnJlcXVlc3RlZCh0aGlzLmRlZmVycmVkUXVldWVfLnNoaWZ0KCksIHRydWUpOwogICAgICB9CiAgICB9CgogICAgZGVwLmxvYWRlZCgpOwogIH07CgoKICAvKioKICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBwYXRoc09ySWRzCiAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgKiBAcHJpdmF0ZQogICAqLwogIGdvb2cuRGVidWdMb2FkZXJfLnByb3RvdHlwZS5hcmVEZXBzTG9hZGVkXyA9IGZ1bmN0aW9uKHBhdGhzT3JJZHMpIHsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcGF0aHNPcklkcy5sZW5ndGg7IGkrKykgewogICAgICB2YXIgcGF0aCA9IHRoaXMuZ2V0UGF0aEZyb21EZXBzXyhwYXRoc09ySWRzW2ldKTsKICAgICAgaWYgKCFwYXRoIHx8CiAgICAgICAgICAoIShwYXRoIGluIHRoaXMuZGVmZXJyZWRDYWxsYmFja3NfKSAmJgogICAgICAgICAgICFnb29nLmlzUHJvdmlkZWRfKHBhdGhzT3JJZHNbaV0pKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfQoKICAgIHJldHVybiB0cnVlOwogIH07CgoKICAvKioKICAgKiBAcGFyYW0ge3N0cmluZ30gYWJzUGF0aE9ySWQKICAgKiBAcmV0dXJuIHs/c3RyaW5nfQogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmdldFBhdGhGcm9tRGVwc18gPSBmdW5jdGlvbihhYnNQYXRoT3JJZCkgewogICAgaWYgKGFic1BhdGhPcklkIGluIHRoaXMuaWRUb1BhdGhfKSB7CiAgICAgIHJldHVybiB0aGlzLmlkVG9QYXRoX1thYnNQYXRoT3JJZF07CiAgICB9IGVsc2UgaWYgKGFic1BhdGhPcklkIGluIHRoaXMuZGVwZW5kZW5jaWVzXykgewogICAgICByZXR1cm4gYWJzUGF0aE9ySWQ7CiAgICB9IGVsc2UgewogICAgICByZXR1cm4gbnVsbDsKICAgIH0KICB9OwoKCiAgLyoqCiAgICogQHBhcmFtIHshZ29vZy5EZXBlbmRlbmN5fSBkZXBlbmRlbmN5CiAgICogQHBhcmFtIHshRnVuY3Rpb259IGNhbGxiYWNrCiAgICogQHByaXZhdGUKICAgKi8KICBnb29nLkRlYnVnTG9hZGVyXy5wcm90b3R5cGUuZGVmZXJfID0gZnVuY3Rpb24oZGVwZW5kZW5jeSwgY2FsbGJhY2spIHsKICAgIHRoaXMuZGVmZXJyZWRDYWxsYmFja3NfW2RlcGVuZGVuY3kucGF0aF0gPSBjYWxsYmFjazsKICAgIHRoaXMuZGVmZXJyZWRRdWV1ZV8ucHVzaChkZXBlbmRlbmN5LnBhdGgpOwogIH07CgoKICAvKioKICAgKiBJbnRlcmZhY2UgZm9yIGdvb2cuRGVwZW5kZW5jeSBpbXBsZW1lbnRhdGlvbnMgdG8gaGF2ZSBzb21lIGNvbnRyb2wgb3ZlcgogICAqIGxvYWRpbmcgb2YgZGVwZW5kZW5jaWVzLgogICAqCiAgICogQHJlY29yZAogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIgPSBmdW5jdGlvbigpIHt9OwoKCiAgLyoqCiAgICogVGVsbHMgdGhlIGNvbnRyb2xsZXIgdG8gaGFsdCBsb2FkaW5nIG9mIG1vcmUgZGVwZW5kZW5jaWVzLgogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLnBhdXNlID0gZnVuY3Rpb24oKSB7fTsKCgogIC8qKgogICAqIFRlbGxzIHRoZSBjb250cm9sbGVyIHRvIHJlc3VtZSBsb2FkaW5nIG9mIG1vcmUgZGVwZW5kZW5jaWVzIGlmIHBhdXNlZC4KICAgKi8KICBnb29nLkxvYWRDb250cm9sbGVyLnByb3RvdHlwZS5yZXN1bWUgPSBmdW5jdGlvbigpIHt9OwoKCiAgLyoqCiAgICogVGVsbHMgdGhlIGNvbnRyb2xsZXIgdGhhdCB0aGlzIGRlcGVuZGVuY3kgaGFzIGZpbmlzaGVkIGxvYWRpbmcuCiAgICoKICAgKiBUaGlzIGNhdXNlcyB0aGlzIHRvIGJlIHJlbW92ZWQgZnJvbSBwZW5kaW5nKCkgYW5kIGFueSBsb2FkIGNhbGxiYWNrcyB0bwogICAqIGZpcmUuCiAgICovCiAgZ29vZy5Mb2FkQ29udHJvbGxlci5wcm90b3R5cGUubG9hZGVkID0gZnVuY3Rpb24oKSB7fTsKCgogIC8qKgogICAqIExpc3Qgb2YgZGVwZW5kZW5jaWVzIG9uIHdoaWNoIGxvYWQgaGFzIGJlZW4gY2FsbGVkIGJ1dCB3aGljaCBoYXZlIG5vdAogICAqIGNhbGxlZCBsb2FkZWQgb24gdGhlaXIgY29udHJvbGxlci4gVGhpcyBpbmNsdWRlcyB0aGUgY3VycmVudCBkZXBlbmRlbmN5LgogICAqCiAgICogQHJldHVybiB7IUFycmF5PCFnb29nLkRlcGVuZGVuY3k+fQogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLnBlbmRpbmcgPSBmdW5jdGlvbigpIHt9OwoKCiAgLyoqCiAgICogUmVnaXN0ZXJzIGFuIG9iamVjdCBhcyBhbiBFUzYgbW9kdWxlJ3MgZXhwb3J0cyBzbyB0aGF0IGdvb2cubW9kdWxlcyBtYXkKICAgKiByZXF1aXJlIGl0IGJ5IHBhdGguCiAgICoKICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBGdWxsIHBhdGggb2YgdGhlIG1vZHVsZS4KICAgKiBAcGFyYW0gez99IGV4cG9ydHMKICAgKiBAcGFyYW0ge3N0cmluZz19IG9wdF9jbG9zdXJlTmFtZXNwYWNlIENsb3N1cmUgbmFtZXNwYWNlIHRvIGFzc29jaWF0ZSB3aXRoCiAgICogICAgIHRoaXMgbW9kdWxlLgogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLnJlZ2lzdGVyRXM2TW9kdWxlRXhwb3J0cyA9IGZ1bmN0aW9uKAogICAgICBwYXRoLCBleHBvcnRzLCBvcHRfY2xvc3VyZU5hbWVzcGFjZSkge307CgoKICAvKioKICAgKiBTZXRzIHRoZSBjdXJyZW50IG1vZHVsZSBzdGF0ZS4KICAgKgogICAqIEBwYXJhbSB7Z29vZy5Nb2R1bGVUeXBlfSB0eXBlIFR5cGUgb2YgbW9kdWxlLgogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLnNldE1vZHVsZVN0YXRlID0gZnVuY3Rpb24odHlwZSkge307CgoKICAvKioKICAgKiBDbGVhcnMgdGhlIGN1cnJlbnQgbW9kdWxlIHN0YXRlLgogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLmNsZWFyTW9kdWxlU3RhdGUgPSBmdW5jdGlvbigpIHt9OwoKCiAgLyoqCiAgICogUmVnaXN0ZXJzIGEgY2FsbGJhY2sgdG8gY2FsbCBvbmNlIHRoZSBkZXBlbmRlbmN5IGlzIGFjdHVhbGx5IHJlcXVlc3RlZAogICAqIHZpYSBnb29nLnJlcXVpcmUgKyBhbGwgb2YgdGhlIGltbWVkaWF0ZSBkZXBlbmRlbmNpZXMgaGF2ZSBiZWVuIGxvYWRlZCBvcgogICAqIGFsbCBvdGhlciBmaWxlcyBoYXZlIGJlZW4gbG9hZGVkLiBBbGxvd3MgZm9yIGxhenkgbG9hZGluZyB1bnRpbAogICAqIHJlcXVpcmUnZCB3aXRob3V0IHBhdXNpbmcgZGVwZW5kZW5jeSBsb2FkaW5nLCB3aGljaCBpcyBuZWVkZWQgb24gb2xkIElFLgogICAqCiAgICogQHBhcmFtIHshRnVuY3Rpb259IGNhbGxiYWNrCiAgICovCiAgZ29vZy5Mb2FkQ29udHJvbGxlci5wcm90b3R5cGUuZGVmZXIgPSBmdW5jdGlvbihjYWxsYmFjaykge307CgoKICAvKioKICAgKiBAcmV0dXJuIHtib29sZWFufQogICAqLwogIGdvb2cuTG9hZENvbnRyb2xsZXIucHJvdG90eXBlLmFyZURlcHNMb2FkZWQgPSBmdW5jdGlvbigpIHt9OwoKCiAgLyoqCiAgICogQmFzaWMgc3VwZXIgY2xhc3MgZm9yIGFsbCBkZXBlbmRlbmNpZXMgQ2xvc3VyZSBMaWJyYXJ5IGNhbiBsb2FkLgogICAqCiAgICogVGhpcyBkZWZhdWx0IGltcGxlbWVudGF0aW9uIGlzIGRlc2lnbmVkIHRvIGxvYWQgdW50cmFuc3BpbGVkLCBub24tbW9kdWxlCiAgICogc2NyaXB0cyBpbiBhIHdlYiBicm9zd2VyLgogICAqCiAgICogRm9yIHRyYW5zcGlsZWQgbm9uLWdvb2cubW9kdWxlIGZpbGVzIHtAc2VlIGdvb2cuVHJhbnNwaWxlZERlcGVuZGVuY3l9LgogICAqIEZvciBnb29nLm1vZHVsZXMgc2VlIHtAc2VlIGdvb2cuR29vZ01vZHVsZURlcGVuZGVuY3l9LgogICAqIEZvciB1bnRyYW5zcGlsZWQgRVM2IG1vZHVsZXMge0BzZWUgZ29vZy5FczZNb2R1bGVEZXBlbmRlbmN5fS4KICAgKgogICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIEFic29sdXRlIHBhdGggb2YgdGhpcyBzY3JpcHQuCiAgICogQHBhcmFtIHtzdHJpbmd9IHJlbGF0aXZlUGF0aCBQYXRoIG9mIHRoaXMgc2NyaXB0IHJlbGF0aXZlIHRvIGdvb2cuYmFzZVBhdGguCiAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPn0gcHJvdmlkZXMgZ29vZy5wcm92aWRlZCBvciBnb29nLm1vZHVsZSBzeW1ib2xzCiAgICogICAgIGluIHRoaXMgZmlsZS4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSByZXF1aXJlcyBnb29nIHN5bWJvbHMgb3IgcmVsYXRpdmUgcGF0aHMgdG8gQ2xvc3VyZQogICAqICAgICB0aGlzIGRlcGVuZHMgb24uCiAgICogQHBhcmFtIHshT2JqZWN0PHN0cmluZywgc3RyaW5nPn0gbG9hZEZsYWdzCiAgICogQHN0cnVjdCBAY29uc3RydWN0b3IKICAgKi8KICBnb29nLkRlcGVuZGVuY3kgPSBmdW5jdGlvbigKICAgICAgcGF0aCwgcmVsYXRpdmVQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIGxvYWRGbGFncykgewogICAgLyoqIEBjb25zdCAqLwogICAgdGhpcy5wYXRoID0gcGF0aDsKICAgIC8qKiBAY29uc3QgKi8KICAgIHRoaXMucmVsYXRpdmVQYXRoID0gcmVsYXRpdmVQYXRoOwogICAgLyoqIEBjb25zdCAqLwogICAgdGhpcy5wcm92aWRlcyA9IHByb3ZpZGVzOwogICAgLyoqIEBjb25zdCAqLwogICAgdGhpcy5yZXF1aXJlcyA9IHJlcXVpcmVzOwogICAgLyoqIEBjb25zdCAqLwogICAgdGhpcy5sb2FkRmxhZ3MgPSBsb2FkRmxhZ3M7CiAgICAvKiogQHByaXZhdGUge2Jvb2xlYW59ICovCiAgICB0aGlzLmxvYWRlZF8gPSBmYWxzZTsKICAgIC8qKiBAcHJpdmF0ZSB7IUFycmF5PGZ1bmN0aW9uKCk+fSAqLwogICAgdGhpcy5sb2FkQ2FsbGJhY2tzXyA9IFtdOwogIH07CgoKICAvKioKICAgKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSBwYXRobmFtZSBwYXJ0IG9mIHRoaXMgZGVwZW5kZW5jeSdzIHBhdGggaWYgaXQgaXMgYQogICAqICAgICBVUkkuCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LnByb3RvdHlwZS5nZXRQYXRoTmFtZSA9IGZ1bmN0aW9uKCkgewogICAgdmFyIHBhdGhOYW1lID0gdGhpcy5wYXRoOwogICAgdmFyIHByb3RvY29sSW5kZXggPSBwYXRoTmFtZS5pbmRleE9mKCc6Ly8nKTsKICAgIGlmIChwcm90b2NvbEluZGV4ID49IDApIHsKICAgICAgcGF0aE5hbWUgPSBwYXRoTmFtZS5zdWJzdHJpbmcocHJvdG9jb2xJbmRleCArIDMpOwogICAgICB2YXIgc2xhc2hJbmRleCA9IHBhdGhOYW1lLmluZGV4T2YoJy8nKTsKICAgICAgaWYgKHNsYXNoSW5kZXggPj0gMCkgewogICAgICAgIHBhdGhOYW1lID0gcGF0aE5hbWUuc3Vic3RyaW5nKHNsYXNoSW5kZXggKyAxKTsKICAgICAgfQogICAgfQogICAgcmV0dXJuIHBhdGhOYW1lOwogIH07CgoKICAvKioKICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCl9IGNhbGxiYWNrIENhbGxiYWNrIHRvIGZpcmUgYXMgc29vbiBhcyB0aGlzIGhhcyBsb2FkZWQuCiAgICogQGZpbmFsCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LnByb3RvdHlwZS5vbkxvYWQgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgaWYgKHRoaXMubG9hZGVkXykgewogICAgICBjYWxsYmFjaygpOwogICAgfSBlbHNlIHsKICAgICAgdGhpcy5sb2FkQ2FsbGJhY2tzXy5wdXNoKGNhbGxiYWNrKTsKICAgIH0KICB9OwoKCiAgLyoqCiAgICogTWFya3MgdGhpcyBkZXBlbmRlbmN5IGFzIGxvYWRlZCBhbmQgZmlyZXMgYW55IGNhbGxiYWNrcyByZWdpc3RlcmVkIHdpdGgKICAgKiBvbkxvYWQuCiAgICogQGZpbmFsCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LnByb3RvdHlwZS5sb2FkZWQgPSBmdW5jdGlvbigpIHsKICAgIHRoaXMubG9hZGVkXyA9IHRydWU7CiAgICB2YXIgY2FsbGJhY2tzID0gdGhpcy5sb2FkQ2FsbGJhY2tzXzsKICAgIHRoaXMubG9hZENhbGxiYWNrc18gPSBbXTsKICAgIGZvciAodmFyIGkgPSAwOyBpIDwgY2FsbGJhY2tzLmxlbmd0aDsgaSsrKSB7CiAgICAgIGNhbGxiYWNrc1tpXSgpOwogICAgfQogIH07CgoKICAvKioKICAgKiBXaGV0aGVyIG9yIG5vdCBkb2N1bWVudC53cml0dGVuIC8gYXBwZW5kZWQgc2NyaXB0IHRhZ3Mgc2hvdWxkIGJlIGRlZmVycmVkLgogICAqCiAgICogQHByaXZhdGUge2Jvb2xlYW59CiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LmRlZmVyXyA9IGZhbHNlOwoKCiAgLyoqCiAgICogTWFwIG9mIHNjcmlwdCByZWFkeSAvIHN0YXRlIGNoYW5nZSBjYWxsYmFja3MuIE9sZCBJRSBjYW5ub3QgaGFuZGxlIHB1dHRpbmcKICAgKiB0aGVzZSBwcm9wZXJ0aWVzIG9uIGdvb2cuZ2xvYmFsLgogICAqCiAgICogQHByaXZhdGUgQGNvbnN0IHshT2JqZWN0PHN0cmluZywgZnVuY3Rpb24oPyk6dW5kZWZpbmVkPn0KICAgKi8KICBnb29nLkRlcGVuZGVuY3kuY2FsbGJhY2tNYXBfID0ge307CgoKICAvKioKICAgKiBAcGFyYW0ge2Z1bmN0aW9uKC4uLj8pOj99IGNhbGxiYWNrCiAgICogQHJldHVybiB7c3RyaW5nfQogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LnJlZ2lzdGVyQ2FsbGJhY2tfID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgIHZhciBrZXkgPSBNYXRoLnJhbmRvbSgpLnRvU3RyaW5nKDMyKTsKICAgIGdvb2cuRGVwZW5kZW5jeS5jYWxsYmFja01hcF9ba2V5XSA9IGNhbGxiYWNrOwogICAgcmV0dXJuIGtleTsKICB9OwoKCiAgLyoqCiAgICogQHBhcmFtIHtzdHJpbmd9IGtleQogICAqIEBwcml2YXRlCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5LnVucmVnaXN0ZXJDYWxsYmFja18gPSBmdW5jdGlvbihrZXkpIHsKICAgIGRlbGV0ZSBnb29nLkRlcGVuZGVuY3kuY2FsbGJhY2tNYXBfW2tleV07CiAgfTsKCgogIC8qKgogICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkKICAgKiBAcGFyYW0gey4uLj99IHZhcl9hcmdzCiAgICogQHByaXZhdGUKICAgKiBAc3VwcHJlc3Mge3VudXNlZFByaXZhdGVNZW1iZXJzfQogICAqLwogIGdvb2cuRGVwZW5kZW5jeS5jYWxsYmFja18gPSBmdW5jdGlvbihrZXksIHZhcl9hcmdzKSB7CiAgICBpZiAoa2V5IGluIGdvb2cuRGVwZW5kZW5jeS5jYWxsYmFja01hcF8pIHsKICAgICAgdmFyIGNhbGxiYWNrID0gZ29vZy5EZXBlbmRlbmN5LmNhbGxiYWNrTWFwX1trZXldOwogICAgICB2YXIgYXJncyA9IFtdOwogICAgICBmb3IgKHZhciBpID0gMTsgaSA8IGFyZ3VtZW50cy5sZW5ndGg7IGkrKykgewogICAgICAgIGFyZ3MucHVzaChhcmd1bWVudHNbaV0pOwogICAgICB9CiAgICAgIGNhbGxiYWNrLmFwcGx5KHVuZGVmaW5lZCwgYXJncyk7CiAgICB9IGVsc2UgewogICAgICB2YXIgZXJyb3JNZXNzYWdlID0gJ0NhbGxiYWNrIGtleSAnICsga2V5ICsKICAgICAgICAgICcgZG9lcyBub3QgZXhpc3QgKHdhcyBiYXNlLmpzIGxvYWRlZCBtb3JlIHRoYW4gb25jZT8pLic7CiAgICAgIHRocm93IEVycm9yKGVycm9yTWVzc2FnZSk7CiAgICB9CiAgfTsKCgogIC8qKgogICAqIFN0YXJ0cyBsb2FkaW5nIHRoaXMgZGVwZW5kZW5jeS4gVGhpcyBkZXBlbmRlbmN5IGNhbiBwYXVzZSBsb2FkaW5nIGlmIGl0CiAgICogbmVlZHMgdG8gYW5kIHJlc3VtZSBpdCBsYXRlciB2aWEgdGhlIGNvbnRyb2xsZXIgaW50ZXJmYWNlLgogICAqCiAgICogV2hlbiB0aGlzIGlzIGxvYWRlZCBpdCBzaG91bGQgY2FsbCBjb250cm9sbGVyLmxvYWRlZCgpLiBOb3RlIHRoYXQgdGhpcyB3aWxsCiAgICogZW5kIHVwIGNhbGxpbmcgdGhlIGxvYWRlZCBtZXRob2Qgb2YgdGhpcyBkZXBlbmRlbmN5OyB0aGVyZSBpcyBubyBuZWVkIHRvCiAgICogY2FsbCBpdCBleHBsaWNpdGx5LgogICAqCiAgICogQHBhcmFtIHshZ29vZy5Mb2FkQ29udHJvbGxlcn0gY29udHJvbGxlcgogICAqLwogIGdvb2cuRGVwZW5kZW5jeS5wcm90b3R5cGUubG9hZCA9IGZ1bmN0aW9uKGNvbnRyb2xsZXIpIHsKICAgIGlmIChnb29nLmdsb2JhbC5DTE9TVVJFX0lNUE9SVF9TQ1JJUFQpIHsKICAgICAgaWYgKGdvb2cuZ2xvYmFsLkNMT1NVUkVfSU1QT1JUX1NDUklQVCh0aGlzLnBhdGgpKSB7CiAgICAgICAgY29udHJvbGxlci5sb2FkZWQoKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBjb250cm9sbGVyLnBhdXNlKCk7CiAgICAgIH0KICAgICAgcmV0dXJuOwogICAgfQoKICAgIGlmICghZ29vZy5pbkh0bWxEb2N1bWVudF8oKSkgewogICAgICBnb29nLmxvZ1RvQ29uc29sZV8oCiAgICAgICAgICAnQ2Fubm90IHVzZSBkZWZhdWx0IGRlYnVnIGxvYWRlciBvdXRzaWRlIG9mIEhUTUwgZG9jdW1lbnRzLicpOwogICAgICBpZiAodGhpcy5yZWxhdGl2ZVBhdGggPT0gJ2RlcHMuanMnKSB7CiAgICAgICAgLy8gU29tZSBvbGQgY29kZSBpcyByZWx5aW5nIG9uIGJhc2UuanMgYXV0byBsb2FkaW5nIGRlcHMuanMgZmFpbGluZyB3aXRoCiAgICAgICAgLy8gbm8gZXJyb3IgYmVmb3JlIGxhdGVyIHNldHRpbmcgQ0xPU1VSRV9JTVBPUlRfU0NSSVBULgogICAgICAgIC8vIENMT1NVUkVfSU1QT1JUX1NDUklQVCBzaG91bGQgYmUgc2V0ICpiZWZvcmUqIGJhc2UuanMgaXMgbG9hZGVkLCBvcgogICAgICAgIC8vIENMT1NVUkVfTk9fREVQUyBzZXQgdG8gdHJ1ZS4KICAgICAgICBnb29nLmxvZ1RvQ29uc29sZV8oCiAgICAgICAgICAgICdDb25zaWRlciBzZXR0aW5nIENMT1NVUkVfSU1QT1JUX1NDUklQVCBiZWZvcmUgbG9hZGluZyBiYXNlLmpzLCAnICsKICAgICAgICAgICAgJ29yIHNldHRpbmcgQ0xPU1VSRV9OT19ERVBTIHRvIHRydWUuJyk7CiAgICAgICAgY29udHJvbGxlci5sb2FkZWQoKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBjb250cm9sbGVyLnBhdXNlKCk7CiAgICAgIH0KICAgICAgcmV0dXJuOwogICAgfQoKICAgIC8qKiBAdHlwZSB7IUhUTUxEb2N1bWVudH0gKi8KICAgIHZhciBkb2MgPSBnb29nLmdsb2JhbC5kb2N1bWVudDsKCiAgICAvLyBJZiB0aGUgdXNlciB0cmllcyB0byByZXF1aXJlIGEgbmV3IHN5bWJvbCBhZnRlciBkb2N1bWVudCBsb2FkLAogICAgLy8gc29tZXRoaW5nIGhhcyBnb25lIHRlcnJpYmx5IHdyb25nLiBEb2luZyBhIGRvY3VtZW50LndyaXRlIHdvdWxkCiAgICAvLyB3aXBlIG91dCB0aGUgcGFnZS4gVGhpcyBkb2VzIG5vdCBhcHBseSB0byB0aGUgQ1NQLWNvbXBsaWFudCBtZXRob2QKICAgIC8vIG9mIHdyaXRpbmcgc2NyaXB0IHRhZ3MuCiAgICBpZiAoZG9jLnJlYWR5U3RhdGUgPT0gJ2NvbXBsZXRlJyAmJgogICAgICAgICFnb29nLkVOQUJMRV9DSFJPTUVfQVBQX1NBRkVfU0NSSVBUX0xPQURJTkcpIHsKICAgICAgLy8gQ2VydGFpbiB0ZXN0IGZyYW1ld29ya3MgbG9hZCBiYXNlLmpzIG11bHRpcGxlIHRpbWVzLCB3aGljaCB0cmllcwogICAgICAvLyB0byB3cml0ZSBkZXBzLmpzIGVhY2ggdGltZS4gSWYgdGhhdCBoYXBwZW5zLCBqdXN0IGZhaWwgc2lsZW50bHkuCiAgICAgIC8vIFRoZXNlIGZyYW1ld29ya3Mgd2lwZSB0aGUgcGFnZSBiZXR3ZWVuIGVhY2ggbG9hZCBvZiBiYXNlLmpzLCBzbyB0aGlzCiAgICAgIC8vIGlzIE9LLgogICAgICB2YXIgaXNEZXBzID0gL1xiZGVwcy5qcyQvLnRlc3QodGhpcy5wYXRoKTsKICAgICAgaWYgKGlzRGVwcykgewogICAgICAgIGNvbnRyb2xsZXIubG9hZGVkKCk7CiAgICAgICAgcmV0dXJuOwogICAgICB9IGVsc2UgewogICAgICAgIHRocm93IEVycm9yKCdDYW5ub3Qgd3JpdGUgIicgKyB0aGlzLnBhdGggKyAnIiBhZnRlciBkb2N1bWVudCBsb2FkJyk7CiAgICAgIH0KICAgIH0KCiAgICBpZiAoIWdvb2cuRU5BQkxFX0NIUk9NRV9BUFBfU0FGRV9TQ1JJUFRfTE9BRElORyAmJgogICAgICAgIGdvb2cuaXNEb2N1bWVudExvYWRpbmdfKCkpIHsKICAgICAgdmFyIGtleSA9IGdvb2cuRGVwZW5kZW5jeS5yZWdpc3RlckNhbGxiYWNrXyhmdW5jdGlvbihzY3JpcHQpIHsKICAgICAgICBpZiAoIWdvb2cuRGVidWdMb2FkZXJfLklTX09MRF9JRV8gfHwgc2NyaXB0LnJlYWR5U3RhdGUgPT0gJ2NvbXBsZXRlJykgewogICAgICAgICAgZ29vZy5EZXBlbmRlbmN5LnVucmVnaXN0ZXJDYWxsYmFja18oa2V5KTsKICAgICAgICAgIGNvbnRyb2xsZXIubG9hZGVkKCk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgdmFyIG5vbmNlQXR0ciA9ICFnb29nLkRlYnVnTG9hZGVyXy5JU19PTERfSUVfICYmIGdvb2cuZ2V0U2NyaXB0Tm9uY2UoKSA/CiAgICAgICAgICAnIG5vbmNlPSInICsgZ29vZy5nZXRTY3JpcHROb25jZSgpICsgJyInIDoKICAgICAgICAgICcnOwogICAgICB2YXIgZXZlbnQgPQogICAgICAgICAgZ29vZy5EZWJ1Z0xvYWRlcl8uSVNfT0xEX0lFXyA/ICdvbnJlYWR5c3RhdGVjaGFuZ2UnIDogJ29ubG9hZCc7CiAgICAgIHZhciBkZWZlciA9IGdvb2cuRGVwZW5kZW5jeS5kZWZlcl8gPyAnZGVmZXInIDogJyc7CiAgICAgIHZhciBzY3JpcHQgPSAnPHNjcmlwdCBzcmM9IicgKyB0aGlzLnBhdGggKyAnIiAnICsgZXZlbnQgKwogICAgICAgICAgJz0iZ29vZy5EZXBlbmRlbmN5LmNhbGxiYWNrXyhcJycgKyBrZXkgKwogICAgICAgICAgJ1wnLCB0aGlzKSIgdHlwZT0idGV4dC9qYXZhc2NyaXB0IiAnICsgZGVmZXIgKyBub25jZUF0dHIgKyAnPjwnICsKICAgICAgICAgICcvc2NyaXB0Pic7CiAgICAgIGRvYy53cml0ZSgKICAgICAgICAgIGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfID8KICAgICAgICAgICAgICBnb29nLlRSVVNURURfVFlQRVNfUE9MSUNZXy5jcmVhdGVIVE1MKHNjcmlwdCkgOgogICAgICAgICAgICAgIHNjcmlwdCk7CiAgICB9IGVsc2UgewogICAgICB2YXIgc2NyaXB0RWwgPQogICAgICAgICAgLyoqIEB0eXBlIHshSFRNTFNjcmlwdEVsZW1lbnR9ICovIChkb2MuY3JlYXRlRWxlbWVudCgnc2NyaXB0JykpOwogICAgICBzY3JpcHRFbC5kZWZlciA9IGdvb2cuRGVwZW5kZW5jeS5kZWZlcl87CiAgICAgIHNjcmlwdEVsLmFzeW5jID0gZmFsc2U7CiAgICAgIHNjcmlwdEVsLnR5cGUgPSAndGV4dC9qYXZhc2NyaXB0JzsKCiAgICAgIC8vIElmIENTUCBub25jZXMgYXJlIHVzZWQsIHByb3BhZ2F0ZSB0aGVtIHRvIGR5bmFtaWNhbGx5IGNyZWF0ZWQgc2NyaXB0cy4KICAgICAgLy8gVGhpcyBpcyBuZWNlc3NhcnkgdG8gYWxsb3cgbm9uY2UtYmFzZWQgQ1NQcyB3aXRob3V0ICdzdHJpY3QtZHluYW1pYycuCiAgICAgIHZhciBub25jZSA9IGdvb2cuZ2V0U2NyaXB0Tm9uY2UoKTsKICAgICAgaWYgKG5vbmNlKSB7CiAgICAgICAgc2NyaXB0RWwuc2V0QXR0cmlidXRlKCdub25jZScsIG5vbmNlKTsKICAgICAgfQoKICAgICAgaWYgKGdvb2cuRGVidWdMb2FkZXJfLklTX09MRF9JRV8pIHsKICAgICAgICAvLyBFeGVjdXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQgb24gb2xkIElFLCBoYWx0IGxvYWRpbmcgYW5kIHdyaXRlCiAgICAgICAgLy8gdGhlc2Ugc2NyaXB0cyBvbmUgYXQgYSB0aW1lLCBhZnRlciBlYWNoIGxvYWRzLgogICAgICAgIGNvbnRyb2xsZXIucGF1c2UoKTsKICAgICAgICBzY3JpcHRFbC5vbnJlYWR5c3RhdGVjaGFuZ2UgPSBmdW5jdGlvbigpIHsKICAgICAgICAgIGlmIChzY3JpcHRFbC5yZWFkeVN0YXRlID09ICdsb2FkZWQnIHx8CiAgICAgICAgICAgICAgc2NyaXB0RWwucmVhZHlTdGF0ZSA9PSAnY29tcGxldGUnKSB7CiAgICAgICAgICAgIGNvbnRyb2xsZXIubG9hZGVkKCk7CiAgICAgICAgICAgIGNvbnRyb2xsZXIucmVzdW1lKCk7CiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfSBlbHNlIHsKICAgICAgICBzY3JpcHRFbC5vbmxvYWQgPSBmdW5jdGlvbigpIHsKICAgICAgICAgIHNjcmlwdEVsLm9ubG9hZCA9IG51bGw7CiAgICAgICAgICBjb250cm9sbGVyLmxvYWRlZCgpOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHNjcmlwdEVsLnNyYyA9IGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfID8KICAgICAgICAgIGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfLmNyZWF0ZVNjcmlwdFVSTCh0aGlzLnBhdGgpIDoKICAgICAgICAgIHRoaXMucGF0aDsKICAgICAgZG9jLmhlYWQuYXBwZW5kQ2hpbGQoc2NyaXB0RWwpOwogICAgfQogIH07CgoKICAvKioKICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBBYnNvbHV0ZSBwYXRoIG9mIHRoaXMgc2NyaXB0LgogICAqIEBwYXJhbSB7c3RyaW5nfSByZWxhdGl2ZVBhdGggUGF0aCBvZiB0aGlzIHNjcmlwdCByZWxhdGl2ZSB0byBnb29nLmJhc2VQYXRoLgogICAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHByb3ZpZGVzIFNob3VsZCBiZSBhbiBlbXB0eSBhcnJheS4KICAgKiAgICAgVE9ETyhqb2hucGxhaXN0ZWQpIGFkZCBzdXBwb3J0IGZvciBhZGRpbmcgY2xvc3VyZSBuYW1lc3BhY2VzIHRvIEVTNgogICAqICAgICBtb2R1bGVzIGZvciBpbnRlcm9wIHB1cnBvc2VzLgogICAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHJlcXVpcmVzIGdvb2cgc3ltYm9scyBvciByZWxhdGl2ZSBwYXRocyB0byBDbG9zdXJlCiAgICogICAgIHRoaXMgZGVwZW5kcyBvbi4KICAgKiBAcGFyYW0geyFPYmplY3Q8c3RyaW5nLCBzdHJpbmc+fSBsb2FkRmxhZ3MKICAgKiBAc3RydWN0IEBjb25zdHJ1Y3RvcgogICAqIEBleHRlbmRzIHtnb29nLkRlcGVuZGVuY3l9CiAgICovCiAgZ29vZy5FczZNb2R1bGVEZXBlbmRlbmN5ID0gZnVuY3Rpb24oCiAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MpIHsKICAgIGdvb2cuRXM2TW9kdWxlRGVwZW5kZW5jeS5iYXNlKAogICAgICAgIHRoaXMsICdjb25zdHJ1Y3RvcicsIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MpOwogIH07CiAgZ29vZy5pbmhlcml0cyhnb29nLkVzNk1vZHVsZURlcGVuZGVuY3ksIGdvb2cuRGVwZW5kZW5jeSk7CgoKICAvKiogQG92ZXJyaWRlICovCiAgZ29vZy5FczZNb2R1bGVEZXBlbmRlbmN5LnByb3RvdHlwZS5sb2FkID0gZnVuY3Rpb24oY29udHJvbGxlcikgewogICAgaWYgKGdvb2cuZ2xvYmFsLkNMT1NVUkVfSU1QT1JUX1NDUklQVCkgewogICAgICBpZiAoZ29vZy5nbG9iYWwuQ0xPU1VSRV9JTVBPUlRfU0NSSVBUKHRoaXMucGF0aCkpIHsKICAgICAgICBjb250cm9sbGVyLmxvYWRlZCgpOwogICAgICB9IGVsc2UgewogICAgICAgIGNvbnRyb2xsZXIucGF1c2UoKTsKICAgICAgfQogICAgICByZXR1cm47CiAgICB9CgogICAgaWYgKCFnb29nLmluSHRtbERvY3VtZW50XygpKSB7CiAgICAgIGdvb2cubG9nVG9Db25zb2xlXygKICAgICAgICAgICdDYW5ub3QgdXNlIGRlZmF1bHQgZGVidWcgbG9hZGVyIG91dHNpZGUgb2YgSFRNTCBkb2N1bWVudHMuJyk7CiAgICAgIGNvbnRyb2xsZXIucGF1c2UoKTsKICAgICAgcmV0dXJuOwogICAgfQoKICAgIC8qKiBAdHlwZSB7IUhUTUxEb2N1bWVudH0gKi8KICAgIHZhciBkb2MgPSBnb29nLmdsb2JhbC5kb2N1bWVudDsKCiAgICB2YXIgZGVwID0gdGhpczsKCiAgICAvLyBUT0RPKGpvaG5wbGFpc3RlZCk6IERvZXMgZG9jdW1lbnQud3JpdGluZyByZWFsbHkgc3BlZWQgdXAgYW55dGhpbmc/IEFueQogICAgLy8gZGlmZmVyZW5jZSBiZXR3ZWVuIHRoaXMgYW5kIGp1c3Qgd2FpdGluZyBmb3IgaW50ZXJhY3RpdmUgbW9kZSBhbmQgdGhlbgogICAgLy8gYXBwZW5kaW5nPwogICAgZnVuY3Rpb24gd3JpdGUoc3JjLCBjb250ZW50cykgewogICAgICBpZiAoY29udGVudHMpIHsKICAgICAgICB2YXIgc2NyaXB0ID0gJzxzY3JpcHQgdHlwZT0ibW9kdWxlIiBjcm9zc29yaWdpbj4nICsgY29udGVudHMgKyAnPC8nICsKICAgICAgICAgICAgJ3NjcmlwdD4nOwogICAgICAgIGRvYy53cml0ZSgKICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8gPwogICAgICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8uY3JlYXRlSFRNTChzY3JpcHQpIDoKICAgICAgICAgICAgICAgIHNjcmlwdCk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgdmFyIHNjcmlwdCA9ICc8c2NyaXB0IHR5cGU9Im1vZHVsZSIgY3Jvc3NvcmlnaW4gc3JjPSInICsgc3JjICsgJyI+PC8nICsKICAgICAgICAgICAgJ3NjcmlwdD4nOwogICAgICAgIGRvYy53cml0ZSgKICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8gPwogICAgICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8uY3JlYXRlSFRNTChzY3JpcHQpIDoKICAgICAgICAgICAgICAgIHNjcmlwdCk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBhcHBlbmQoc3JjLCBjb250ZW50cykgewogICAgICB2YXIgc2NyaXB0RWwgPQogICAgICAgICAgLyoqIEB0eXBlIHshSFRNTFNjcmlwdEVsZW1lbnR9ICovIChkb2MuY3JlYXRlRWxlbWVudCgnc2NyaXB0JykpOwogICAgICBzY3JpcHRFbC5kZWZlciA9IHRydWU7CiAgICAgIHNjcmlwdEVsLmFzeW5jID0gZmFsc2U7CiAgICAgIHNjcmlwdEVsLnR5cGUgPSAnbW9kdWxlJzsKICAgICAgc2NyaXB0RWwuc2V0QXR0cmlidXRlKCdjcm9zc29yaWdpbicsIHRydWUpOwoKICAgICAgLy8gSWYgQ1NQIG5vbmNlcyBhcmUgdXNlZCwgcHJvcGFnYXRlIHRoZW0gdG8gZHluYW1pY2FsbHkgY3JlYXRlZCBzY3JpcHRzLgogICAgICAvLyBUaGlzIGlzIG5lY2Vzc2FyeSB0byBhbGxvdyBub25jZS1iYXNlZCBDU1BzIHdpdGhvdXQgJ3N0cmljdC1keW5hbWljJy4KICAgICAgdmFyIG5vbmNlID0gZ29vZy5nZXRTY3JpcHROb25jZSgpOwogICAgICBpZiAobm9uY2UpIHsKICAgICAgICBzY3JpcHRFbC5zZXRBdHRyaWJ1dGUoJ25vbmNlJywgbm9uY2UpOwogICAgICB9CgogICAgICBpZiAoY29udGVudHMpIHsKICAgICAgICBzY3JpcHRFbC50ZXh0Q29udGVudCA9IGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfID8KICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8uY3JlYXRlU2NyaXB0KGNvbnRlbnRzKSA6CiAgICAgICAgICAgIGNvbnRlbnRzOwogICAgICB9IGVsc2UgewogICAgICAgIHNjcmlwdEVsLnNyYyA9IGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfID8KICAgICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8uY3JlYXRlU2NyaXB0VVJMKHNyYykgOgogICAgICAgICAgICBzcmM7CiAgICAgIH0KCiAgICAgIGRvYy5oZWFkLmFwcGVuZENoaWxkKHNjcmlwdEVsKTsKICAgIH0KCiAgICB2YXIgY3JlYXRlOwoKICAgIGlmIChnb29nLmlzRG9jdW1lbnRMb2FkaW5nXygpKSB7CiAgICAgIGNyZWF0ZSA9IHdyaXRlOwogICAgICAvLyBXZSBjYW4gT05MWSBjYWxsIGRvY3VtZW50LndyaXRlIGlmIHdlIGFyZSBndWFyYW50ZWVkIHRoYXQgYW55CiAgICAgIC8vIG5vbi1tb2R1bGUgc2NyaXB0IHRhZ3MgZG9jdW1lbnQud3JpdHRlbiBhZnRlciB0aGlzIGFyZSBkZWZlcnJlZC4KICAgICAgLy8gU21hbGwgb3B0aW1pemF0aW9uLCBpbiB0aGVvcnkgZG9jdW1lbnQud3JpdGluZyBpcyBmYXN0ZXIuCiAgICAgIGdvb2cuRGVwZW5kZW5jeS5kZWZlcl8gPSB0cnVlOwogICAgfSBlbHNlIHsKICAgICAgY3JlYXRlID0gYXBwZW5kOwogICAgfQoKICAgIC8vIFdyaXRlIDQgc2VwYXJhdGUgdGFncyBoZXJlOgogICAgLy8gMSkgU2V0cyB0aGUgbW9kdWxlIHN0YXRlIGF0IHRoZSBjb3JyZWN0IHRpbWUgKGp1c3QgYmVmb3JlIGV4ZWN1dGlvbikuCiAgICAvLyAyKSBBIHNyYyBub2RlIGZvciB0aGlzLCB3aGljaCBqdXN0IGhvcGVmdWxseSBsZXRzIHRoZSBicm93c2VyIGxvYWQgaXQgYQogICAgLy8gICAgbGl0dGxlIGVhcmx5IChubyBuZWVkIHRvIHBhcnNlICMzKS4KICAgIC8vIDMpIEltcG9ydCB0aGUgbW9kdWxlIGFuZCByZWdpc3RlciBpdC4KICAgIC8vIDQpIENsZWFyIHRoZSBtb2R1bGUgc3RhdGUgYXQgdGhlIGNvcnJlY3QgdGltZS4gR3VhcmFudGVlZCB0byBydW4gZXZlbgogICAgLy8gICAgaWYgdGhlcmUgaXMgYW4gZXJyb3IgaW4gdGhlIG1vZHVsZSAoIzMgd2lsbCBub3QgcnVuIGlmIHRoZXJlIGlzIGFuCiAgICAvLyAgICBlcnJvciBpbiB0aGUgbW9kdWxlKS4KICAgIHZhciBiZWZvcmVLZXkgPSBnb29nLkRlcGVuZGVuY3kucmVnaXN0ZXJDYWxsYmFja18oZnVuY3Rpb24oKSB7CiAgICAgIGdvb2cuRGVwZW5kZW5jeS51bnJlZ2lzdGVyQ2FsbGJhY2tfKGJlZm9yZUtleSk7CiAgICAgIGNvbnRyb2xsZXIuc2V0TW9kdWxlU3RhdGUoZ29vZy5Nb2R1bGVUeXBlLkVTNik7CiAgICB9KTsKICAgIGNyZWF0ZSh1bmRlZmluZWQsICdnb29nLkRlcGVuZGVuY3kuY2FsbGJhY2tfKCInICsgYmVmb3JlS2V5ICsgJyIpJyk7CgogICAgLy8gVE9ETyhqb2hucGxhaXN0ZWQpOiBEb2VzIHRoaXMgcmVhbGx5IHNwZWVkIHVwIGFueXRoaW5nPwogICAgY3JlYXRlKHRoaXMucGF0aCwgdW5kZWZpbmVkKTsKCiAgICB2YXIgcmVnaXN0ZXJLZXkgPSBnb29nLkRlcGVuZGVuY3kucmVnaXN0ZXJDYWxsYmFja18oZnVuY3Rpb24oZXhwb3J0cykgewogICAgICBnb29nLkRlcGVuZGVuY3kudW5yZWdpc3RlckNhbGxiYWNrXyhyZWdpc3RlcktleSk7CiAgICAgIGNvbnRyb2xsZXIucmVnaXN0ZXJFczZNb2R1bGVFeHBvcnRzKAogICAgICAgICAgZGVwLnBhdGgsIGV4cG9ydHMsIGdvb2cubW9kdWxlTG9hZGVyU3RhdGVfLm1vZHVsZU5hbWUpOwogICAgfSk7CiAgICBjcmVhdGUoCiAgICAgICAgdW5kZWZpbmVkLAogICAgICAgICdpbXBvcnQgKiBhcyBtIGZyb20gIicgKyB0aGlzLnBhdGggKyAnIjsgZ29vZy5EZXBlbmRlbmN5LmNhbGxiYWNrXygiJyArCiAgICAgICAgICAgIHJlZ2lzdGVyS2V5ICsgJyIsIG0pJyk7CgogICAgdmFyIGFmdGVyS2V5ID0gZ29vZy5EZXBlbmRlbmN5LnJlZ2lzdGVyQ2FsbGJhY2tfKGZ1bmN0aW9uKCkgewogICAgICBnb29nLkRlcGVuZGVuY3kudW5yZWdpc3RlckNhbGxiYWNrXyhhZnRlcktleSk7CiAgICAgIGNvbnRyb2xsZXIuY2xlYXJNb2R1bGVTdGF0ZSgpOwogICAgICBjb250cm9sbGVyLmxvYWRlZCgpOwogICAgfSk7CiAgICBjcmVhdGUodW5kZWZpbmVkLCAnZ29vZy5EZXBlbmRlbmN5LmNhbGxiYWNrXygiJyArIGFmdGVyS2V5ICsgJyIpJyk7CiAgfTsKCgogIC8qKgogICAqIFN1cGVyY2xhc3Mgb2YgYW55IGRlcGVuZGVuY3kgdGhhdCBuZWVkcyB0byBiZSBsb2FkZWQgaW50byBtZW1vcnksCiAgICogdHJhbnNmb3JtZWQsIGFuZCB0aGVuIGV2YWwnZCAoZ29vZy5tb2R1bGVzIGFuZCB0cmFuc3BpbGVkIGZpbGVzKS4KICAgKgogICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIEFic29sdXRlIHBhdGggb2YgdGhpcyBzY3JpcHQuCiAgICogQHBhcmFtIHtzdHJpbmd9IHJlbGF0aXZlUGF0aCBQYXRoIG9mIHRoaXMgc2NyaXB0IHJlbGF0aXZlIHRvIGdvb2cuYmFzZVBhdGguCiAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPn0gcHJvdmlkZXMgZ29vZy5wcm92aWRlZCBvciBnb29nLm1vZHVsZSBzeW1ib2xzCiAgICogICAgIGluIHRoaXMgZmlsZS4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSByZXF1aXJlcyBnb29nIHN5bWJvbHMgb3IgcmVsYXRpdmUgcGF0aHMgdG8gQ2xvc3VyZQogICAqICAgICB0aGlzIGRlcGVuZHMgb24uCiAgICogQHBhcmFtIHshT2JqZWN0PHN0cmluZywgc3RyaW5nPn0gbG9hZEZsYWdzCiAgICogQHN0cnVjdCBAY29uc3RydWN0b3IgQGFic3RyYWN0CiAgICogQGV4dGVuZHMge2dvb2cuRGVwZW5kZW5jeX0KICAgKi8KICBnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeSA9IGZ1bmN0aW9uKAogICAgICBwYXRoLCByZWxhdGl2ZVBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgbG9hZEZsYWdzKSB7CiAgICBnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeS5iYXNlKAogICAgICAgIHRoaXMsICdjb25zdHJ1Y3RvcicsIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MpOwogICAgLyoqIEBwcml2YXRlIHs/c3RyaW5nfSAqLwogICAgdGhpcy5jb250ZW50c18gPSBudWxsOwoKICAgIC8qKgogICAgICogV2hldGhlciB0byBsYXppbHkgbWFrZSB0aGUgc3luY2hyb25vdXMgWEhSICh3aGVuIGdvb2cucmVxdWlyZSdkKSBvciBtYWtlCiAgICAgKiB0aGUgc3luY2hyb25vdXMgWEhSIHdoZW4gaW5pdGlhbGx5IGxvYWRpbmcuIE9uIEZpcmVGb3ggNjEgdGhlcmUgaXMgYSBidWcKICAgICAqIHdoZXJlIGFuIEVTNiBtb2R1bGUgY2Fubm90IG1ha2UgYSBzeW5jaHJvbm91cyBYSFIgKHJhdGhlciwgaXQgY2FuLCBidXQgaWYKICAgICAqIGl0IGRvZXMgdGhlbiBubyBvdGhlciBFUzYgbW9kdWxlcyB3aWxsIGxvYWQgYWZ0ZXIpLgogICAgICoKICAgICAqIHRsO2RyIHdlIGxhenkgbG9hZCBkdWUgdG8gYnVncyBvbiBvbGRlciBicm93c2VycyBhbmQgZWFnZXIgbG9hZCBkdWUgdG8KICAgICAqIGJ1Z3Mgb24gbmV3ZXIgb25lcy4KICAgICAqCiAgICAgKiBodHRwczovL2J1Z3ppbGxhLm1vemlsbGEub3JnL3Nob3dfYnVnLmNnaT9pZD0xNDc3MDkwCiAgICAgKgogICAgICogQHByaXZhdGUgQGNvbnN0IHtib29sZWFufQogICAgICovCiAgICB0aGlzLmxhenlGZXRjaF8gPSAhZ29vZy5pbkh0bWxEb2N1bWVudF8oKSB8fAogICAgICAgICEoJ25vTW9kdWxlJyBpbiBnb29nLmdsb2JhbC5kb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzY3JpcHQnKSk7CiAgfTsKICBnb29nLmluaGVyaXRzKGdvb2cuVHJhbnNmb3JtZWREZXBlbmRlbmN5LCBnb29nLkRlcGVuZGVuY3kpOwoKCiAgLyoqIEBvdmVycmlkZSAqLwogIGdvb2cuVHJhbnNmb3JtZWREZXBlbmRlbmN5LnByb3RvdHlwZS5sb2FkID0gZnVuY3Rpb24oY29udHJvbGxlcikgewogICAgdmFyIGRlcCA9IHRoaXM7CgogICAgZnVuY3Rpb24gZmV0Y2goKSB7CiAgICAgIGRlcC5jb250ZW50c18gPSBnb29nLmxvYWRGaWxlU3luY18oZGVwLnBhdGgpOwoKICAgICAgaWYgKGRlcC5jb250ZW50c18pIHsKICAgICAgICBkZXAuY29udGVudHNfID0gZGVwLnRyYW5zZm9ybShkZXAuY29udGVudHNfKTsKICAgICAgICBpZiAoZGVwLmNvbnRlbnRzXykgewogICAgICAgICAgZGVwLmNvbnRlbnRzXyArPSAnXG4vLyMgc291cmNlVVJMPScgKyBkZXAucGF0aDsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBpZiAoZ29vZy5nbG9iYWwuQ0xPU1VSRV9JTVBPUlRfU0NSSVBUKSB7CiAgICAgIGZldGNoKCk7CiAgICAgIGlmICh0aGlzLmNvbnRlbnRzXyAmJgogICAgICAgICAgZ29vZy5nbG9iYWwuQ0xPU1VSRV9JTVBPUlRfU0NSSVBUKCcnLCB0aGlzLmNvbnRlbnRzXykpIHsKICAgICAgICB0aGlzLmNvbnRlbnRzXyA9IG51bGw7CiAgICAgICAgY29udHJvbGxlci5sb2FkZWQoKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBjb250cm9sbGVyLnBhdXNlKCk7CiAgICAgIH0KICAgICAgcmV0dXJuOwogICAgfQoKCiAgICB2YXIgaXNFczYgPSB0aGlzLmxvYWRGbGFnc1snbW9kdWxlJ10gPT0gZ29vZy5Nb2R1bGVUeXBlLkVTNjsKCiAgICBpZiAoIXRoaXMubGF6eUZldGNoXykgewogICAgICBmZXRjaCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxvYWQoKSB7CiAgICAgIGlmIChkZXAubGF6eUZldGNoXykgewogICAgICAgIGZldGNoKCk7CiAgICAgIH0KCiAgICAgIGlmICghZGVwLmNvbnRlbnRzXykgewogICAgICAgIC8vIGxvYWRGaWxlU3luY18gb3IgdHJhbnNmb3JtIGFyZSByZXNwb25zaWJsZS4gQXNzdW1lIHRoZXkgbG9nZ2VkIGFuCiAgICAgICAgLy8gZXJyb3IuCiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBpZiAoaXNFczYpIHsKICAgICAgICBjb250cm9sbGVyLnNldE1vZHVsZVN0YXRlKGdvb2cuTW9kdWxlVHlwZS5FUzYpOwogICAgICB9CgogICAgICB2YXIgbmFtZXNwYWNlOwoKICAgICAgdHJ5IHsKICAgICAgICB2YXIgY29udGVudHMgPSBkZXAuY29udGVudHNfOwogICAgICAgIGRlcC5jb250ZW50c18gPSBudWxsOwogICAgICAgIGdvb2cuZ2xvYmFsRXZhbChjb250ZW50cyk7CiAgICAgICAgaWYgKGlzRXM2KSB7CiAgICAgICAgICBuYW1lc3BhY2UgPSBnb29nLm1vZHVsZUxvYWRlclN0YXRlXy5tb2R1bGVOYW1lOwogICAgICAgIH0KICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBpZiAoaXNFczYpIHsKICAgICAgICAgIGNvbnRyb2xsZXIuY2xlYXJNb2R1bGVTdGF0ZSgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgaWYgKGlzRXM2KSB7CiAgICAgICAgLy8gRHVlIHRvIGNpcmN1bGFyIGRlcGVuZGVuY2llcyB0aGlzIG1heSBub3QgYmUgYXZhaWxhYmxlIGZvciByZXF1aXJlCiAgICAgICAgLy8gcmlnaHQgbm93LgogICAgICAgIGdvb2cuZ2xvYmFsWyckanNjb21wJ11bJ3JlcXVpcmUnXVsnZW5zdXJlJ10oCiAgICAgICAgICAgIFtkZXAuZ2V0UGF0aE5hbWUoKV0sIGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIGNvbnRyb2xsZXIucmVnaXN0ZXJFczZNb2R1bGVFeHBvcnRzKAogICAgICAgICAgICAgICAgICBkZXAucGF0aCwKICAgICAgICAgICAgICAgICAgZ29vZy5nbG9iYWxbJyRqc2NvbXAnXVsncmVxdWlyZSddKGRlcC5nZXRQYXRoTmFtZSgpKSwKICAgICAgICAgICAgICAgICAgbmFtZXNwYWNlKTsKICAgICAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIGNvbnRyb2xsZXIubG9hZGVkKCk7CiAgICB9CgogICAgLy8gRG8gbm90IGZldGNoIG5vdzsgaW4gRmlyZUZveCA0NyB0aGUgc3luY2hyb25vdXMgWEhSIGRvZXNuJ3QgYmxvY2sgYWxsCiAgICAvLyBldmVudHMuIElmIHdlIGZldGNoZWQgbm93IGFuZCB0aGVuIGRvY3VtZW50LndyaXRlJ2QgdGhlIGNvbnRlbnRzIHRoZQogICAgLy8gZG9jdW1lbnQud3JpdGUgd291bGQgYmUgYW4gZXZhbCBhbmQgd291bGQgZXhlY3V0ZSB0b28gc29vbiEgSW5zdGVhZCB3cml0ZQogICAgLy8gYSBzY3JpcHQgdGFnIHRvIGZldGNoIGFuZCBldmFsIHN5bmNocm9ub3VzbHkgYXQgdGhlIGNvcnJlY3QgdGltZS4KICAgIGZ1bmN0aW9uIGZldGNoSW5Pd25TY3JpcHRUaGVuTG9hZCgpIHsKICAgICAgLyoqIEB0eXBlIHshSFRNTERvY3VtZW50fSAqLwogICAgICB2YXIgZG9jID0gZ29vZy5nbG9iYWwuZG9jdW1lbnQ7CgogICAgICB2YXIga2V5ID0gZ29vZy5EZXBlbmRlbmN5LnJlZ2lzdGVyQ2FsbGJhY2tfKGZ1bmN0aW9uKCkgewogICAgICAgIGdvb2cuRGVwZW5kZW5jeS51bnJlZ2lzdGVyQ2FsbGJhY2tfKGtleSk7CiAgICAgICAgbG9hZCgpOwogICAgICB9KTsKCiAgICAgIHZhciBzY3JpcHQgPSAnPHNjcmlwdCB0eXBlPSJ0ZXh0L2phdmFzY3JpcHQiPicgKwogICAgICAgICAgZ29vZy5wcm90ZWN0U2NyaXB0VGFnXygnZ29vZy5EZXBlbmRlbmN5LmNhbGxiYWNrXygiJyArIGtleSArICciKTsnKSArCiAgICAgICAgICAnPC8nICsKICAgICAgICAgICdzY3JpcHQ+JzsKICAgICAgZG9jLndyaXRlKAogICAgICAgICAgZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV8gPwogICAgICAgICAgICAgIGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfLmNyZWF0ZUhUTUwoc2NyaXB0KSA6CiAgICAgICAgICAgICAgc2NyaXB0KTsKICAgIH0KCiAgICAvLyBJZiBvbmUgdGhpbmcgaXMgcGVuZGluZyBpdCBpcyB0aGlzLgogICAgdmFyIGFueXRoaW5nRWxzZVBlbmRpbmcgPSBjb250cm9sbGVyLnBlbmRpbmcoKS5sZW5ndGggPiAxOwoKICAgIC8vIElmIGFueXRoaW5nIGVsc2UgaXMgbG9hZGluZyB3ZSBuZWVkIHRvIGxhenkgbG9hZCBkdWUgdG8gYnVncyBpbiBvbGQgSUUuCiAgICAvLyBTcGVjaWZpY2FsbHkgc2NyaXB0IHRhZ3Mgd2l0aCBzcmMgYW5kIHNjcmlwdCB0YWdzIHdpdGggY29udGVudHMgY291bGQKICAgIC8vIGV4ZWN1dGUgb3V0IG9mIG9yZGVyIGlmIGRvY3VtZW50LndyaXRlIGlzIHVzZWQsIHNvIHdlIGNhbm5vdCB1c2UKICAgIC8vIGRvY3VtZW50LndyaXRlLiBEbyBub3QgcGF1c2UgaGVyZTsgaXQgYnJlYWtzIG9sZCBJRSBhcyB3ZWxsLgogICAgdmFyIHVzZU9sZEllV29ya0Fyb3VuZCA9CiAgICAgICAgYW55dGhpbmdFbHNlUGVuZGluZyAmJiBnb29nLkRlYnVnTG9hZGVyXy5JU19PTERfSUVfOwoKICAgIC8vIEFkZGl0aW9uYWxseSBpZiB3ZSBhcmUgbWVhbnQgdG8gZGVmZXIgc2NyaXB0cyBidXQgdGhlIHBhZ2UgaXMgc3RpbGwKICAgIC8vIGxvYWRpbmcgKGUuZy4gYW4gRVM2IG1vZHVsZSBpcyBsb2FkaW5nKSB0aGVuIGFsc28gZGVmZXIuIE9yIGlmIHdlIGFyZQogICAgLy8gbWVhbnQgdG8gZGVmZXIgYW5kIGFueXRoaW5nIGVsc2UgaXMgcGVuZGluZyB0aGVuIGRlZmVyICh0aG9zZSBtYXkgYmUKICAgIC8vIHNjcmlwdHMgdGhhdCBkaWQgbm90IG5lZWQgdHJhbnNmb3JtYXRpb24gYW5kIGFyZSBqdXN0IHNjcmlwdCB0YWdzIHdpdGgKICAgIC8vIGRlZmVyIHNldCB0byB0cnVlLCBhbmQgd2UgbmVlZCB0byBldmFsdWF0ZSBhZnRlciB0aGF0IGRlZmVycmVkIHNjcmlwdCkuCiAgICB2YXIgbmVlZHNBc3luY0xvYWRpbmcgPSBnb29nLkRlcGVuZGVuY3kuZGVmZXJfICYmCiAgICAgICAgKGFueXRoaW5nRWxzZVBlbmRpbmcgfHwgZ29vZy5pc0RvY3VtZW50TG9hZGluZ18oKSk7CgogICAgaWYgKHVzZU9sZEllV29ya0Fyb3VuZCB8fCBuZWVkc0FzeW5jTG9hZGluZykgewogICAgICAvLyBOb3RlIHRoYXQgd2Ugb25seSBkZWZlciB3aGVuIHdlIGhhdmUgdG8gcmF0aGVyIHRoYW4gMTAwJSBvZiB0aGUgdGltZS4KICAgICAgLy8gQWx3YXlzIGRlZmVyaW5nIHdvdWxkIHdvcmssIGJ1dCB0aGVuIGluIHRoZW9yeSB0aGUgb3JkZXIgb2YKICAgICAgLy8gZ29vZy5yZXF1aXJlIGNhbGxzIHdvdWxkIHRoZW4gbWF0dGVyLiBXZSB3YW50IHRvIGVuZm9yY2UgdGhhdCBtb3N0IG9mCiAgICAgIC8vIHRoZSB0aW1lIHRoZSBvcmRlciBvZiB0aGUgcmVxdWlyZSBjYWxscyBkb2VzIG5vdCBtYXR0ZXIuCiAgICAgIGNvbnRyb2xsZXIuZGVmZXIoZnVuY3Rpb24oKSB7CiAgICAgICAgbG9hZCgpOwogICAgICB9KTsKICAgICAgcmV0dXJuOwogICAgfQogICAgLy8gVE9ETyhqb2hucGxhaXN0ZWQpOiBFeHRlcm5zIGFyZSBtaXNzaW5nIG9ucmVhZHlzdGF0ZWNoYW5nZSBmb3IKICAgIC8vIEhUTUxEb2N1bWVudC4KICAgIC8qKiBAdHlwZSB7P30gKi8KICAgIHZhciBkb2MgPSBnb29nLmdsb2JhbC5kb2N1bWVudDsKCiAgICB2YXIgaXNJbnRlcm5ldEV4cGxvcmVyID0KICAgICAgICBnb29nLmluSHRtbERvY3VtZW50XygpICYmICdBY3RpdmVYT2JqZWN0JyBpbiBnb29nLmdsb2JhbDsKCiAgICAvLyBEb24ndCBkZWxheSBpbiBhbnkgdmVyc2lvbiBvZiBJRS4gVGhlcmUncyBidWcgYXJvdW5kIHRoaXMgdGhhdCB3aWxsCiAgICAvLyBjYXVzZSBvdXQgb2Ygb3JkZXIgc2NyaXB0IGV4ZWN1dGlvbi4gVGhpcyBtZWFucyB0aGF0IG9uIG9sZGVyIElFIEVTNgogICAgLy8gbW9kdWxlcyB3aWxsIGxvYWQgdG9vIGVhcmx5ICh3aGlsZSB0aGUgZG9jdW1lbnQgaXMgc3RpbGwgbG9hZGluZyArIHRoZQogICAgLy8gZG9tIGlzIG5vdCBhdmFpbGFibGUpLiBUaGUgb3RoZXIgb3B0aW9uIGlzIHRvIGxvYWQgdG9vIGxhdGUgKHdoZW4gdGhlCiAgICAvLyBkb2N1bWVudCBpcyBjb21wbGV0ZSBhbmQgdGhlIG9ubG9hZCBldmVuIHdpbGwgbmV2ZXIgZmlyZSkuIFRoaXMgc2VlbXMKICAgIC8vIHRvIGJlIHRoZSBsZXNzZXIgb2YgdHdvIGV2aWxzIGFzIHNjcmlwdHMgYWxyZWFkeSBhY3QgbGlrZSB0aGUgZm9ybWVyLgogICAgaWYgKGlzRXM2ICYmIGdvb2cuaW5IdG1sRG9jdW1lbnRfKCkgJiYgZ29vZy5pc0RvY3VtZW50TG9hZGluZ18oKSAmJgogICAgICAgICFpc0ludGVybmV0RXhwbG9yZXIpIHsKICAgICAgZ29vZy5EZXBlbmRlbmN5LmRlZmVyXyA9IHRydWU7CiAgICAgIC8vIFRyYW5zcGlsZWQgRVM2IG1vZHVsZXMgc3RpbGwgbmVlZCB0byBsb2FkIGxpa2UgcmVndWxhciBFUzYgbW9kdWxlcywKICAgICAgLy8gYWthIG9ubHkgYWZ0ZXIgdGhlIGRvY3VtZW50IGlzIGludGVyYWN0aXZlLgogICAgICBjb250cm9sbGVyLnBhdXNlKCk7CiAgICAgIHZhciBvbGRDYWxsYmFjayA9IGRvYy5vbnJlYWR5c3RhdGVjaGFuZ2U7CiAgICAgIGRvYy5vbnJlYWR5c3RhdGVjaGFuZ2UgPSBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoZG9jLnJlYWR5U3RhdGUgPT0gJ2ludGVyYWN0aXZlJykgewogICAgICAgICAgZG9jLm9ucmVhZHlzdGF0ZWNoYW5nZSA9IG9sZENhbGxiYWNrOwogICAgICAgICAgbG9hZCgpOwogICAgICAgICAgY29udHJvbGxlci5yZXN1bWUoKTsKICAgICAgICB9CiAgICAgICAgaWYgKGdvb2cuaXNGdW5jdGlvbihvbGRDYWxsYmFjaykpIHsKICAgICAgICAgIG9sZENhbGxiYWNrLmFwcGx5KHVuZGVmaW5lZCwgYXJndW1lbnRzKTsKICAgICAgICB9CiAgICAgIH07CiAgICB9IGVsc2UgewogICAgICAvLyBBbHdheXMgZXZhbCBvbiBvbGQgSUUuCiAgICAgIGlmIChnb29nLkRlYnVnTG9hZGVyXy5JU19PTERfSUVfIHx8ICFnb29nLmluSHRtbERvY3VtZW50XygpIHx8CiAgICAgICAgICAhZ29vZy5pc0RvY3VtZW50TG9hZGluZ18oKSkgewogICAgICAgIGxvYWQoKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBmZXRjaEluT3duU2NyaXB0VGhlbkxvYWQoKTsKICAgICAgfQogICAgfQogIH07CgoKICAvKioKICAgKiBAcGFyYW0ge3N0cmluZ30gY29udGVudHMKICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICogQGFic3RyYWN0CiAgICovCiAgZ29vZy5UcmFuc2Zvcm1lZERlcGVuZGVuY3kucHJvdG90eXBlLnRyYW5zZm9ybSA9IGZ1bmN0aW9uKGNvbnRlbnRzKSB7fTsKCgogIC8qKgogICAqIEFueSBub24tZ29vZy5tb2R1bGUgZGVwZW5kZW5jeSB3aGljaCBuZWVkcyB0byBiZSB0cmFuc3BpbGVkIGJlZm9yZSBldmFsLgogICAqCiAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggQWJzb2x1dGUgcGF0aCBvZiB0aGlzIHNjcmlwdC4KICAgKiBAcGFyYW0ge3N0cmluZ30gcmVsYXRpdmVQYXRoIFBhdGggb2YgdGhpcyBzY3JpcHQgcmVsYXRpdmUgdG8gZ29vZy5iYXNlUGF0aC4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBwcm92aWRlcyBnb29nLnByb3ZpZGVkIG9yIGdvb2cubW9kdWxlIHN5bWJvbHMKICAgKiAgICAgaW4gdGhpcyBmaWxlLgogICAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHJlcXVpcmVzIGdvb2cgc3ltYm9scyBvciByZWxhdGl2ZSBwYXRocyB0byBDbG9zdXJlCiAgICogICAgIHRoaXMgZGVwZW5kcyBvbi4KICAgKiBAcGFyYW0geyFPYmplY3Q8c3RyaW5nLCBzdHJpbmc+fSBsb2FkRmxhZ3MKICAgKiBAcGFyYW0geyFnb29nLlRyYW5zcGlsZXJ9IHRyYW5zcGlsZXIKICAgKiBAc3RydWN0IEBjb25zdHJ1Y3RvcgogICAqIEBleHRlbmRzIHtnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeX0KICAgKi8KICBnb29nLlRyYW5zcGlsZWREZXBlbmRlbmN5ID0gZnVuY3Rpb24oCiAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MsIHRyYW5zcGlsZXIpIHsKICAgIGdvb2cuVHJhbnNwaWxlZERlcGVuZGVuY3kuYmFzZSgKICAgICAgICB0aGlzLCAnY29uc3RydWN0b3InLCBwYXRoLCByZWxhdGl2ZVBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgbG9hZEZsYWdzKTsKICAgIC8qKiBAcHJvdGVjdGVkIEBjb25zdCovCiAgICB0aGlzLnRyYW5zcGlsZXIgPSB0cmFuc3BpbGVyOwogIH07CiAgZ29vZy5pbmhlcml0cyhnb29nLlRyYW5zcGlsZWREZXBlbmRlbmN5LCBnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeSk7CgoKICAvKiogQG92ZXJyaWRlICovCiAgZ29vZy5UcmFuc3BpbGVkRGVwZW5kZW5jeS5wcm90b3R5cGUudHJhbnNmb3JtID0gZnVuY3Rpb24oY29udGVudHMpIHsKICAgIC8vIFRyYW5zcGlsZSB3aXRoIHRoZSBwYXRobmFtZSBzbyB0aGF0IEVTNiBtb2R1bGVzIGFyZSBkb21haW4gYWdub3N0aWMuCiAgICByZXR1cm4gdGhpcy50cmFuc3BpbGVyLnRyYW5zcGlsZShjb250ZW50cywgdGhpcy5nZXRQYXRoTmFtZSgpKTsKICB9OwoKCiAgLyoqCiAgICogQW4gRVM2IG1vZHVsZSBkZXBlbmRlbmN5IHRoYXQgd2FzIHRyYW5zcGlsZWQgdG8gYSBqc2NvbXAgbW9kdWxlIG91dHNpZGUKICAgKiBvZiB0aGUgZGVidWcgbG9hZGVyLCBlLmcuIHNlcnZlciBzaWRlLgogICAqCiAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggQWJzb2x1dGUgcGF0aCBvZiB0aGlzIHNjcmlwdC4KICAgKiBAcGFyYW0ge3N0cmluZ30gcmVsYXRpdmVQYXRoIFBhdGggb2YgdGhpcyBzY3JpcHQgcmVsYXRpdmUgdG8gZ29vZy5iYXNlUGF0aC4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBwcm92aWRlcyBnb29nLnByb3ZpZGVkIG9yIGdvb2cubW9kdWxlIHN5bWJvbHMKICAgKiAgICAgaW4gdGhpcyBmaWxlLgogICAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHJlcXVpcmVzIGdvb2cgc3ltYm9scyBvciByZWxhdGl2ZSBwYXRocyB0byBDbG9zdXJlCiAgICogICAgIHRoaXMgZGVwZW5kcyBvbi4KICAgKiBAcGFyYW0geyFPYmplY3Q8c3RyaW5nLCBzdHJpbmc+fSBsb2FkRmxhZ3MKICAgKiBAc3RydWN0IEBjb25zdHJ1Y3RvcgogICAqIEBleHRlbmRzIHtnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeX0KICAgKi8KICBnb29nLlByZVRyYW5zcGlsZWRFczZNb2R1bGVEZXBlbmRlbmN5ID0gZnVuY3Rpb24oCiAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MpIHsKICAgIGdvb2cuUHJlVHJhbnNwaWxlZEVzNk1vZHVsZURlcGVuZGVuY3kuYmFzZSgKICAgICAgICB0aGlzLCAnY29uc3RydWN0b3InLCBwYXRoLCByZWxhdGl2ZVBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgbG9hZEZsYWdzKTsKICB9OwogIGdvb2cuaW5oZXJpdHMoCiAgICAgIGdvb2cuUHJlVHJhbnNwaWxlZEVzNk1vZHVsZURlcGVuZGVuY3ksIGdvb2cuVHJhbnNmb3JtZWREZXBlbmRlbmN5KTsKCgogIC8qKiBAb3ZlcnJpZGUgKi8KICBnb29nLlByZVRyYW5zcGlsZWRFczZNb2R1bGVEZXBlbmRlbmN5LnByb3RvdHlwZS50cmFuc2Zvcm0gPSBmdW5jdGlvbigKICAgICAgY29udGVudHMpIHsKICAgIHJldHVybiBjb250ZW50czsKICB9OwoKCiAgLyoqCiAgICogQSBnb29nLm1vZHVsZSwgdHJhbnNwaWxlZCBvciBub3QuIFdpbGwgYWx3YXlzIHBlcmZvcm0gc29tZSBtaW5pbWFsCiAgICogdHJhbnNmb3JtYXRpb24gZXZlbiB3aGVuIG5vdCB0cmFuc3BpbGVkIHRvIHdyYXAgaW4gYSBnb29nLmxvYWRNb2R1bGUKICAgKiBzdGF0ZW1lbnQuCiAgICoKICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBBYnNvbHV0ZSBwYXRoIG9mIHRoaXMgc2NyaXB0LgogICAqIEBwYXJhbSB7c3RyaW5nfSByZWxhdGl2ZVBhdGggUGF0aCBvZiB0aGlzIHNjcmlwdCByZWxhdGl2ZSB0byBnb29nLmJhc2VQYXRoLgogICAqIEBwYXJhbSB7IUFycmF5PHN0cmluZz59IHByb3ZpZGVzIGdvb2cucHJvdmlkZWQgb3IgZ29vZy5tb2R1bGUgc3ltYm9scwogICAqICAgICBpbiB0aGlzIGZpbGUuCiAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPn0gcmVxdWlyZXMgZ29vZyBzeW1ib2xzIG9yIHJlbGF0aXZlIHBhdGhzIHRvIENsb3N1cmUKICAgKiAgICAgdGhpcyBkZXBlbmRzIG9uLgogICAqIEBwYXJhbSB7IU9iamVjdDxzdHJpbmcsIHN0cmluZz59IGxvYWRGbGFncwogICAqIEBwYXJhbSB7Ym9vbGVhbn0gbmVlZHNUcmFuc3BpbGUKICAgKiBAcGFyYW0geyFnb29nLlRyYW5zcGlsZXJ9IHRyYW5zcGlsZXIKICAgKiBAc3RydWN0IEBjb25zdHJ1Y3RvcgogICAqIEBleHRlbmRzIHtnb29nLlRyYW5zZm9ybWVkRGVwZW5kZW5jeX0KICAgKi8KICBnb29nLkdvb2dNb2R1bGVEZXBlbmRlbmN5ID0gZnVuY3Rpb24oCiAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MsIG5lZWRzVHJhbnNwaWxlLAogICAgICB0cmFuc3BpbGVyKSB7CiAgICBnb29nLkdvb2dNb2R1bGVEZXBlbmRlbmN5LmJhc2UoCiAgICAgICAgdGhpcywgJ2NvbnN0cnVjdG9yJywgcGF0aCwgcmVsYXRpdmVQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIGxvYWRGbGFncyk7CiAgICAvKiogQHByaXZhdGUgQGNvbnN0ICovCiAgICB0aGlzLm5lZWRzVHJhbnNwaWxlXyA9IG5lZWRzVHJhbnNwaWxlOwogICAgLyoqIEBwcml2YXRlIEBjb25zdCAqLwogICAgdGhpcy50cmFuc3BpbGVyXyA9IHRyYW5zcGlsZXI7CiAgfTsKICBnb29nLmluaGVyaXRzKGdvb2cuR29vZ01vZHVsZURlcGVuZGVuY3ksIGdvb2cuVHJhbnNmb3JtZWREZXBlbmRlbmN5KTsKCgogIC8qKiBAb3ZlcnJpZGUgKi8KICBnb29nLkdvb2dNb2R1bGVEZXBlbmRlbmN5LnByb3RvdHlwZS50cmFuc2Zvcm0gPSBmdW5jdGlvbihjb250ZW50cykgewogICAgaWYgKHRoaXMubmVlZHNUcmFuc3BpbGVfKSB7CiAgICAgIGNvbnRlbnRzID0gdGhpcy50cmFuc3BpbGVyXy50cmFuc3BpbGUoY29udGVudHMsIHRoaXMuZ2V0UGF0aE5hbWUoKSk7CiAgICB9CgogICAgaWYgKCFnb29nLkxPQURfTU9EVUxFX1VTSU5HX0VWQUwgfHwgZ29vZy5nbG9iYWwuSlNPTiA9PT0gdW5kZWZpbmVkKSB7CiAgICAgIHJldHVybiAnJyArCiAgICAgICAgICAnZ29vZy5sb2FkTW9kdWxlKGZ1bmN0aW9uKGV4cG9ydHMpIHsnICsKICAgICAgICAgICcidXNlIHN0cmljdCI7JyArIGNvbnRlbnRzICsKICAgICAgICAgICdcbicgKyAgLy8gdGVybWluYXRlIGFueSB0cmFpbGluZyBzaW5nbGUgbGluZSBjb21tZW50LgogICAgICAgICAgJztyZXR1cm4gZXhwb3J0cycgKwogICAgICAgICAgJ30pOycgKwogICAgICAgICAgJ1xuLy8jIHNvdXJjZVVSTD0nICsgdGhpcy5wYXRoICsgJ1xuJzsKICAgIH0gZWxzZSB7CiAgICAgIHJldHVybiAnJyArCiAgICAgICAgICAnZ29vZy5sb2FkTW9kdWxlKCcgKwogICAgICAgICAgZ29vZy5nbG9iYWwuSlNPTi5zdHJpbmdpZnkoCiAgICAgICAgICAgICAgY29udGVudHMgKyAnXG4vLyMgc291cmNlVVJMPScgKyB0aGlzLnBhdGggKyAnXG4nKSArCiAgICAgICAgICAnKTsnOwogICAgfQogIH07CgoKICAvKioKICAgKiBXaGV0aGVyIHRoZSBicm93c2VyIGlzIElFOSBvciBlYXJsaWVyLCB3aGljaCBuZWVkcyBzcGVjaWFsIGhhbmRsaW5nCiAgICogZm9yIGRlZmVycmVkIG1vZHVsZXMuCiAgICogQGNvbnN0IEBwcml2YXRlIHtib29sZWFufQogICAqLwogIGdvb2cuRGVidWdMb2FkZXJfLklTX09MRF9JRV8gPSAhISgKICAgICAgIWdvb2cuZ2xvYmFsLmF0b2IgJiYgZ29vZy5nbG9iYWwuZG9jdW1lbnQgJiYgZ29vZy5nbG9iYWwuZG9jdW1lbnRbJ2FsbCddKTsKCgogIC8qKgogICAqIEBwYXJhbSB7c3RyaW5nfSByZWxQYXRoCiAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPnx1bmRlZmluZWR9IHByb3ZpZGVzCiAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPn0gcmVxdWlyZXMKICAgKiBAcGFyYW0ge2Jvb2xlYW58IU9iamVjdDxzdHJpbmc+PX0gb3B0X2xvYWRGbGFncwogICAqIEBzZWUgZ29vZy5hZGREZXBlbmRlbmN5CiAgICovCiAgZ29vZy5EZWJ1Z0xvYWRlcl8ucHJvdG90eXBlLmFkZERlcGVuZGVuY3kgPSBmdW5jdGlvbigKICAgICAgcmVsUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBvcHRfbG9hZEZsYWdzKSB7CiAgICBwcm92aWRlcyA9IHByb3ZpZGVzIHx8IFtdOwogICAgcmVsUGF0aCA9IHJlbFBhdGgucmVwbGFjZSgvXFwvZywgJy8nKTsKICAgIHZhciBwYXRoID0gZ29vZy5ub3JtYWxpemVQYXRoXyhnb29nLmJhc2VQYXRoICsgcmVsUGF0aCk7CiAgICBpZiAoIW9wdF9sb2FkRmxhZ3MgfHwgdHlwZW9mIG9wdF9sb2FkRmxhZ3MgPT09ICdib29sZWFuJykgewogICAgICBvcHRfbG9hZEZsYWdzID0gb3B0X2xvYWRGbGFncyA/IHsnbW9kdWxlJzogZ29vZy5Nb2R1bGVUeXBlLkdPT0d9IDoge307CiAgICB9CiAgICB2YXIgZGVwID0gdGhpcy5mYWN0b3J5Xy5jcmVhdGVEZXBlbmRlbmN5KAogICAgICAgIHBhdGgsIHJlbFBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgb3B0X2xvYWRGbGFncywKICAgICAgICBnb29nLnRyYW5zcGlsZXJfLm5lZWRzVHJhbnNwaWxlKAogICAgICAgICAgICBvcHRfbG9hZEZsYWdzWydsYW5nJ10gfHwgJ2VzMycsIG9wdF9sb2FkRmxhZ3NbJ21vZHVsZSddKSk7CiAgICB0aGlzLmRlcGVuZGVuY2llc19bcGF0aF0gPSBkZXA7CiAgICBmb3IgKHZhciBpID0gMDsgaSA8IHByb3ZpZGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgIHRoaXMuaWRUb1BhdGhfW3Byb3ZpZGVzW2ldXSA9IHBhdGg7CiAgICB9CiAgICB0aGlzLmlkVG9QYXRoX1tyZWxQYXRoXSA9IHBhdGg7CiAgfTsKCgogIC8qKgogICAqIENyZWF0ZXMgZ29vZy5EZXBlbmRlbmN5IGluc3RhbmNlcyBmb3IgdGhlIGRlYnVnIGxvYWRlciB0byBsb2FkLgogICAqCiAgICogU2hvdWxkIGJlIG92ZXJyaWRkZW4gdG8gaGF2ZSB0aGUgZGVidWcgbG9hZGVyIHVzZSBjdXN0b20gc3ViY2xhc3NlcyBvZgogICAqIGdvb2cuRGVwZW5kZW5jeS4KICAgKgogICAqIEBwYXJhbSB7IWdvb2cuVHJhbnNwaWxlcn0gdHJhbnNwaWxlcgogICAqIEBzdHJ1Y3QgQGNvbnN0cnVjdG9yCiAgICovCiAgZ29vZy5EZXBlbmRlbmN5RmFjdG9yeSA9IGZ1bmN0aW9uKHRyYW5zcGlsZXIpIHsKICAgIC8qKiBAcHJvdGVjdGVkIEBjb25zdCAqLwogICAgdGhpcy50cmFuc3BpbGVyID0gdHJhbnNwaWxlcjsKICB9OwoKCiAgLyoqCiAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggQWJzb2x1dGUgcGF0aCBvZiB0aGUgZmlsZS4KICAgKiBAcGFyYW0ge3N0cmluZ30gcmVsYXRpdmVQYXRoIFBhdGggcmVsYXRpdmUgdG8gY2xvc3VyZeKAmXMgYmFzZS5qcy4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBwcm92aWRlcyBBcnJheSBvZiBwcm92aWRlZCBnb29nLnByb3ZpZGUvbW9kdWxlIGlkcy4KICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSByZXF1aXJlcyBBcnJheSBvZiByZXF1aXJlZCBnb29nLnByb3ZpZGUvbW9kdWxlIC8KICAgKiAgICAgcmVsYXRpdmUgRVM2IG1vZHVsZSBwYXRocy4KICAgKiBAcGFyYW0geyFPYmplY3Q8c3RyaW5nLCBzdHJpbmc+fSBsb2FkRmxhZ3MKICAgKiBAcGFyYW0ge2Jvb2xlYW59IG5lZWRzVHJhbnNwaWxlIFRydWUgaWYgdGhlIGZpbGUgbmVlZHMgdG8gYmUgdHJhbnNwaWxlZAogICAqICAgICBwZXIgdGhlIGdvb2cuVHJhbnNwaWxlci4KICAgKiBAcmV0dXJuIHshZ29vZy5EZXBlbmRlbmN5fQogICAqLwogIGdvb2cuRGVwZW5kZW5jeUZhY3RvcnkucHJvdG90eXBlLmNyZWF0ZURlcGVuZGVuY3kgPSBmdW5jdGlvbigKICAgICAgcGF0aCwgcmVsYXRpdmVQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIGxvYWRGbGFncywgbmVlZHNUcmFuc3BpbGUpIHsKCiAgICBpZiAobG9hZEZsYWdzWydtb2R1bGUnXSA9PSBnb29nLk1vZHVsZVR5cGUuR09PRykgewogICAgICByZXR1cm4gbmV3IGdvb2cuR29vZ01vZHVsZURlcGVuZGVuY3koCiAgICAgICAgICBwYXRoLCByZWxhdGl2ZVBhdGgsIHByb3ZpZGVzLCByZXF1aXJlcywgbG9hZEZsYWdzLCBuZWVkc1RyYW5zcGlsZSwKICAgICAgICAgIHRoaXMudHJhbnNwaWxlcik7CiAgICB9IGVsc2UgaWYgKG5lZWRzVHJhbnNwaWxlKSB7CiAgICAgIHJldHVybiBuZXcgZ29vZy5UcmFuc3BpbGVkRGVwZW5kZW5jeSgKICAgICAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MsIHRoaXMudHJhbnNwaWxlcik7CiAgICB9IGVsc2UgewogICAgICBpZiAobG9hZEZsYWdzWydtb2R1bGUnXSA9PSBnb29nLk1vZHVsZVR5cGUuRVM2KSB7CiAgICAgICAgaWYgKGdvb2cuVFJBTlNQSUxFID09ICduZXZlcicgJiYgZ29vZy5BU1NVTUVfRVNfTU9EVUxFU19UUkFOU1BJTEVEKSB7CiAgICAgICAgICByZXR1cm4gbmV3IGdvb2cuUHJlVHJhbnNwaWxlZEVzNk1vZHVsZURlcGVuZGVuY3koCiAgICAgICAgICAgICAgcGF0aCwgcmVsYXRpdmVQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIGxvYWRGbGFncyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJldHVybiBuZXcgZ29vZy5FczZNb2R1bGVEZXBlbmRlbmN5KAogICAgICAgICAgICAgIHBhdGgsIHJlbGF0aXZlUGF0aCwgcHJvdmlkZXMsIHJlcXVpcmVzLCBsb2FkRmxhZ3MpOwogICAgICAgIH0KICAgICAgfSBlbHNlIHsKICAgICAgICByZXR1cm4gbmV3IGdvb2cuRGVwZW5kZW5jeSgKICAgICAgICAgICAgcGF0aCwgcmVsYXRpdmVQYXRoLCBwcm92aWRlcywgcmVxdWlyZXMsIGxvYWRGbGFncyk7CiAgICAgIH0KICAgIH0KICB9OwoKCiAgLyoqIEBwcml2YXRlIEBjb25zdCAqLwogIGdvb2cuZGVidWdMb2FkZXJfID0gbmV3IGdvb2cuRGVidWdMb2FkZXJfKCk7CgoKICAvKioKICAgKiBMb2FkcyB0aGUgQ2xvc3VyZSBEZXBlbmRlbmN5IGZpbGUuCiAgICoKICAgKiBFeHBvc2VkIGEgcHVibGljIGZ1bmN0aW9uIHNvIENMT1NVUkVfTk9fREVQUyBjYW4gYmUgc2V0IHRvIGZhbHNlLCBiYXNlCiAgICogbG9hZGVkLCBzZXREZXBlbmRlbmN5RmFjdG9yeSBjYWxsZWQsIGFuZCB0aGVuIHRoaXMgY2FsbGVkLiBpLmUuIGFsbG93cwogICAqIGN1c3RvbSBsb2FkaW5nIG9mIHRoZSBkZXBzIGZpbGUuCiAgICovCiAgZ29vZy5sb2FkQ2xvc3VyZURlcHMgPSBmdW5jdGlvbigpIHsKICAgIGdvb2cuZGVidWdMb2FkZXJfLmxvYWRDbG9zdXJlRGVwcygpOwogIH07CgoKICAvKioKICAgKiBTZXRzIHRoZSBkZXBlbmRlbmN5IGZhY3RvcnksIHdoaWNoIGNhbiBiZSB1c2VkIHRvIGNyZWF0ZSBjdXN0b20KICAgKiBnb29nLkRlcGVuZGVuY3kgaW1wbGVtZW50YXRpb25zIHRvIGNvbnRyb2wgaG93IGRlcGVuZGVuY2llcyBhcmUgbG9hZGVkLgogICAqCiAgICogTm90ZTogaWYgeW91IHdpc2ggdG8gY2FsbCB0aGlzIGZ1bmN0aW9uIGFuZCBwcm92aWRlIHlvdXIgb3duIGltcGxlbW5ldGF0aW9uCiAgICogaXQgaXMgYSB3aXNlIGlkZWEgdG8gc2V0IENMT1NVUkVfTk9fREVQUyB0byB0cnVlLCBvdGhlcndpc2UgdGhlIGRlcGVuZGVuY3kKICAgKiBmaWxlIGFuZCBhbGwgb2YgaXRzIGdvb2cuYWRkRGVwZW5kZW5jeSBjYWxscyB3aWxsIHVzZSB0aGUgZGVmYXVsdCBmYWN0b3J5LgogICAqIFlvdSBjYW4gY2FsbCBnb29nLmxvYWRDbG9zdXJlRGVwcyB0byBsb2FkIHRoZSBDbG9zdXJlIGRlcGVuZGVuY3kgZmlsZQogICAqIGxhdGVyLCBhZnRlciB5b3VyIGZhY3RvcnkgaXMgaW5qZWN0ZWQuCiAgICoKICAgKiBAcGFyYW0geyFnb29nLkRlcGVuZGVuY3lGYWN0b3J5fSBmYWN0b3J5CiAgICovCiAgZ29vZy5zZXREZXBlbmRlbmN5RmFjdG9yeSA9IGZ1bmN0aW9uKGZhY3RvcnkpIHsKICAgIGdvb2cuZGVidWdMb2FkZXJfLnNldERlcGVuZGVuY3lGYWN0b3J5KGZhY3RvcnkpOwogIH07CgoKICBpZiAoIWdvb2cuZ2xvYmFsLkNMT1NVUkVfTk9fREVQUykgewogICAgZ29vZy5kZWJ1Z0xvYWRlcl8ubG9hZENsb3N1cmVEZXBzKCk7CiAgfQoKCiAgLyoqCiAgICogQm9vdHN0cmFwcyB0aGUgZ2l2ZW4gbmFtZXNwYWNlcyBhbmQgY2FsbHMgdGhlIGNhbGxiYWNrIG9uY2UgdGhleSBhcmUKICAgKiBhdmFpbGFibGUgZWl0aGVyIHZpYSBnb29nLnJlcXVpcmUuIFRoaXMgaXMgYSByZXBsYWNlbWVudCBmb3IgdXNpbmcKICAgKiBgZ29vZy5yZXF1aXJlYCB0byBib290c3RyYXAgQ2xvc3VyZSBKYXZhU2NyaXB0LiBQcmV2aW91c2x5IGEgYGdvb2cucmVxdWlyZWAKICAgKiBpbiBhbiBIVE1MIGZpbGUgd291bGQgZ3VhcmFudGVlIHRoYXQgdGhlIHJlcXVpcmUnZCBuYW1lc3BhY2Ugd2FzIGF2YWlsYWJsZQogICAqIGluIHRoZSBuZXh0IGltbWVkaWF0ZSBzY3JpcHQgdGFnLiBXaXRoIEVTNiBtb2R1bGVzIHRoaXMgbm8gbG9uZ2VyIGEKICAgKiBndWFyYW50ZWUuCiAgICoKICAgKiBAcGFyYW0geyFBcnJheTxzdHJpbmc+fSBuYW1lc3BhY2VzCiAgICogQHBhcmFtIHtmdW5jdGlvbigpOiA/fSBjYWxsYmFjayBGdW5jdGlvbiB0byBjYWxsIG9uY2UgYWxsIHRoZSBuYW1lc3BhY2VzCiAgICogICAgIGhhdmUgbG9hZGVkLiBBbHdheXMgY2FsbGVkIGFzeW5jaHJvbm91c2x5LgogICAqLwogIGdvb2cuYm9vdHN0cmFwID0gZnVuY3Rpb24obmFtZXNwYWNlcywgY2FsbGJhY2spIHsKICAgIGdvb2cuZGVidWdMb2FkZXJfLmJvb3RzdHJhcChuYW1lc3BhY2VzLCBjYWxsYmFjayk7CiAgfTsKfQoKCi8qKgogKiBAZGVmaW5lIHtzdHJpbmd9IFRydXN0ZWQgVHlwZXMgcG9saWN5IG5hbWUuIElmIG5vbi1lbXB0eSB0aGVuIENsb3N1cmUgd2lsbAogKiB1c2UgVHJ1c3RlZCBUeXBlcy4KICovCmdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfTkFNRSA9CiAgICBnb29nLmRlZmluZSgnZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV9OQU1FJywgJycpOwoKCi8qKgogKiBSZXR1cm5zIHRoZSBwYXJhbWV0ZXIuCiAqIEBwYXJhbSB7c3RyaW5nfSBzCiAqIEByZXR1cm4ge3N0cmluZ30KICogQHByaXZhdGUKICovCmdvb2cuaWRlbnRpdHlfID0gZnVuY3Rpb24ocykgewogIHJldHVybiBzOwp9OwoKCi8qKgogKiBDcmVhdGVzIFRydXN0ZWQgVHlwZXMgcG9saWN5IGlmIFRydXN0ZWQgVHlwZXMgYXJlIHN1cHBvcnRlZCBieSB0aGUgYnJvd3Nlci4KICogVGhlIHBvbGljeSBqdXN0IGJsZXNzZXMgYW55IHN0cmluZyBhcyBhIFRydXN0ZWQgVHlwZS4gSXQgaXMgbm90IHZpc2liaWxpdHkKICogcmVzdHJpY3RlZCBiZWNhdXNlIGFueW9uZSBjYW4gYWxzbyBjYWxsIFRydXN0ZWRUeXBlcy5jcmVhdGVQb2xpY3kgZGlyZWN0bHkuCiAqIEhvd2V2ZXIsIHRoZSBhbGxvd2VkIG5hbWVzIHNob3VsZCBiZSByZXN0cmljdGVkIGJ5IGEgSFRUUCBoZWFkZXIgYW5kIHRoZQogKiByZWZlcmVuY2UgdG8gdGhlIGNyZWF0ZWQgcG9saWN5IHNob3VsZCBiZSB2aXNpYmlsaXR5IHJlc3RyaWN0ZWQuCiAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lCiAqIEByZXR1cm4gez9UcnVzdGVkVHlwZVBvbGljeX0KICovCmdvb2cuY3JlYXRlVHJ1c3RlZFR5cGVzUG9saWN5ID0gZnVuY3Rpb24obmFtZSkgewogIHZhciBwb2xpY3kgPSBudWxsOwogIC8vIFRPRE8oa290byk6IFJlbW92ZSB3aW5kb3cuVHJ1c3RlZFR5cGVzIHZhcmlhbnQgd2hlbiB0aGUgbmV3ZXIgQVBJIHNoaXBzLgogIHZhciBwb2xpY3lGYWN0b3J5ID0gZ29vZy5nbG9iYWwudHJ1c3RlZFR5cGVzIHx8IGdvb2cuZ2xvYmFsLlRydXN0ZWRUeXBlczsKICBpZiAoIXBvbGljeUZhY3RvcnkgfHwgIXBvbGljeUZhY3RvcnkuY3JlYXRlUG9saWN5KSB7CiAgICByZXR1cm4gcG9saWN5OwogIH0KICAvLyBUcnVzdGVkVHlwZXMuY3JlYXRlUG9saWN5IHRocm93cyBpZiBjYWxsZWQgd2l0aCBhIG5hbWUgdGhhdCBpcyBhbHJlYWR5CiAgLy8gcmVnaXN0ZXJlZCwgZXZlbiBpbiByZXBvcnQtb25seSBtb2RlLiBVbnRpbCB0aGUgQVBJIGNoYW5nZXMsIGNhdGNoIHRoZQogIC8vIGVycm9yIG5vdCB0byBicmVhayB0aGUgYXBwbGljYXRpb25zIGZ1bmN0aW9uYWxseS4gSW4gc3VjaCBjYXNlLCB0aGUgY29kZQogIC8vIHdpbGwgZmFsbCBiYWNrIHRvIHVzaW5nIHJlZ3VsYXIgU2FmZSBUeXBlcy4KICAvLyBUT0RPKGtvdG8pOiBSZW1vdmUgY2F0Y2hpbmcgb25jZSBjcmVhdGVQb2xpY3kgQVBJIHN0b3BzIHRocm93aW5nLgogIHRyeSB7CiAgICBwb2xpY3kgPSBwb2xpY3lGYWN0b3J5LmNyZWF0ZVBvbGljeShuYW1lLCB7CiAgICAgIGNyZWF0ZUhUTUw6IGdvb2cuaWRlbnRpdHlfLAogICAgICBjcmVhdGVTY3JpcHQ6IGdvb2cuaWRlbnRpdHlfLAogICAgICBjcmVhdGVTY3JpcHRVUkw6IGdvb2cuaWRlbnRpdHlfLAogICAgICBjcmVhdGVVUkw6IGdvb2cuaWRlbnRpdHlfCiAgICB9KTsKICB9IGNhdGNoIChlKSB7CiAgICBnb29nLmxvZ1RvQ29uc29sZV8oZS5tZXNzYWdlKTsKICB9CiAgcmV0dXJuIHBvbGljeTsKfTsKCgovKiogQHByaXZhdGUgQGNvbnN0IHs/VHJ1c3RlZFR5cGVQb2xpY3l9ICovCmdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfID0gZ29vZy5UUlVTVEVEX1RZUEVTX1BPTElDWV9OQU1FID8KICAgIGdvb2cuY3JlYXRlVHJ1c3RlZFR5cGVzUG9saWN5KGdvb2cuVFJVU1RFRF9UWVBFU19QT0xJQ1lfTkFNRSArICcjYmFzZScpIDoKICAgIG51bGw7CgovLyBDb3B5cmlnaHQgMjAxOSBUaGUgQ2xvc3VyZSBMaWJyYXJ5IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCi8vCi8vIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwovLyB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCi8vIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAovLwovLyAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAovLwovLyBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCi8vIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUy1JUyIgQkFTSVMsCi8vIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgovLyBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCi8vIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgovLwovLyBUaGlzIGZpbGUgaGFzIGJlZW4gYXV0by1nZW5lcmF0ZWQgYnkgR2VuSnNEZXBzLCBwbGVhc2UgZG8gbm90IGVkaXQuCgovLyBEaXNhYmxlIENsYW5nIGZvcm1hdHRlciBmb3IgdGhpcyBmaWxlLgovLyBTZWUgaHR0cDovL2dvby5nbC9TZGl3WkgKLy8gY2xhbmctZm9ybWF0IG9mZgoKZ29vZy5hZGREZXBlbmRlbmN5KCdjb2xsZWN0aW9ucy9zZXRzLmpzJywgWydnb29nLmNvbGxlY3Rpb25zLnNldHMnXSwgWydnb29nLmxhYnMuY29sbGVjdGlvbnMuaXRlcmFibGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY29sbGVjdGlvbnMvc2V0c190ZXN0LmpzJywgWydnb29nLmNvbGxlY3Rpb25zLnNldHNUZXN0J10sIFsnZ29vZy5jb2xsZWN0aW9ucy5zZXRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCcuLi8uLi90aGlyZF9wYXJ0eS9jbG9zdXJlL2dvb2cvbW9jaGlraXQvYXN5bmMvZGVmZXJyZWQuanMnLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5hc3luYy5EZWZlcnJlZC5BbHJlYWR5Q2FsbGVkRXJyb3InLCAnZ29vZy5hc3luYy5EZWZlcnJlZC5DYW5jZWxlZEVycm9yJ10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuVGhlbmFibGUnLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5FcnJvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnLi4vLi4vdGhpcmRfcGFydHkvY2xvc3VyZS9nb29nL21vY2hpa2l0L2FzeW5jL2RlZmVycmVkX2FzeW5jX3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMuZGVmZXJyZWRBc3luY1Rlc3QnXSwgWydnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCcuLi8uLi90aGlyZF9wYXJ0eS9jbG9zdXJlL2dvb2cvbW9jaGlraXQvYXN5bmMvZGVmZXJyZWRfdGVzdC5qcycsIFsnZ29vZy5hc3luYy5kZWZlcnJlZFRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaGVuYWJsZScsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCcuLi8uLi90aGlyZF9wYXJ0eS9jbG9zdXJlL2dvb2cvbW9jaGlraXQvYXN5bmMvZGVmZXJyZWRsaXN0LmpzJywgWydnb29nLmFzeW5jLkRlZmVycmVkTGlzdCddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJy4uLy4uL3RoaXJkX3BhcnR5L2Nsb3N1cmUvZ29vZy9tb2NoaWtpdC9hc3luYy9kZWZlcnJlZGxpc3RfdGVzdC5qcycsIFsnZ29vZy5hc3luYy5kZWZlcnJlZExpc3RUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuYXN5bmMuRGVmZXJyZWRMaXN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90by9wcm90by5qcycsIFsnZ29vZy5wcm90byddLCBbJ2dvb2cucHJvdG8uU2VyaWFsaXplciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8vc2VyaWFsaXplci5qcycsIFsnZ29vZy5wcm90by5TZXJpYWxpemVyJ10sIFsnZ29vZy5qc29uLlNlcmlhbGl6ZXInLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvL3NlcmlhbGl6ZXJfdGVzdC5qcycsIFsnZ29vZy5wcm90b1Rlc3QnXSwgWydnb29nLnByb3RvJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhMTF5L2FyaWEvYW5ub3VuY2VyLmpzJywgWydnb29nLmExMXkuYXJpYS5Bbm5vdW5jZXInXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5UaW1lcicsICdnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5MaXZlUHJpb3JpdHknLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYTExeS9hcmlhL2Fubm91bmNlcl90ZXN0LmpzJywgWydnb29nLmExMXkuYXJpYS5Bbm5vdW5jZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuQW5ub3VuY2VyJywgJ2dvb2cuYTExeS5hcmlhLkxpdmVQcmlvcml0eScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uaWZyYW1lJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2ExMXkvYXJpYS9hcmlhLmpzJywgWydnb29nLmExMXkuYXJpYSddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hMTF5LmFyaWEuZGF0YXRhYmxlcycsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhMTF5L2FyaWEvYXJpYV90ZXN0LmpzJywgWydnb29nLmExMXkuYXJpYVRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2ExMXkvYXJpYS9hdHRyaWJ1dGVzLmpzJywgWydnb29nLmExMXkuYXJpYS5BdXRvQ29tcGxldGVWYWx1ZXMnLCAnZ29vZy5hMTF5LmFyaWEuQ2hlY2tlZFZhbHVlcycsICdnb29nLmExMXkuYXJpYS5Ecm9wRWZmZWN0VmFsdWVzJywgJ2dvb2cuYTExeS5hcmlhLkV4cGFuZGVkVmFsdWVzJywgJ2dvb2cuYTExeS5hcmlhLkdyYWJiZWRWYWx1ZXMnLCAnZ29vZy5hMTF5LmFyaWEuSW52YWxpZFZhbHVlcycsICdnb29nLmExMXkuYXJpYS5MaXZlUHJpb3JpdHknLCAnZ29vZy5hMTF5LmFyaWEuT3JpZW50YXRpb25WYWx1ZXMnLCAnZ29vZy5hMTF5LmFyaWEuUHJlc3NlZFZhbHVlcycsICdnb29nLmExMXkuYXJpYS5SZWxldmFudFZhbHVlcycsICdnb29nLmExMXkuYXJpYS5TZWxlY3RlZFZhbHVlcycsICdnb29nLmExMXkuYXJpYS5Tb3J0VmFsdWVzJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYTExeS9hcmlhL2RhdGF0YWJsZXMuanMnLCBbJ2dvb2cuYTExeS5hcmlhLmRhdGF0YWJsZXMnXSwgWydnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYTExeS9hcmlhL3JvbGVzLmpzJywgWydnb29nLmExMXkuYXJpYS5Sb2xlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXJyYXkvYXJyYXkuanMnLCBbJ2dvb2cuYXJyYXknXSwgWydnb29nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FycmF5L2FycmF5X3Rlc3QuanMnLCBbJ2dvb2cuYXJyYXlUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczcnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXNzZXJ0cy9hc3NlcnRzLmpzJywgWydnb29nLmFzc2VydHMnLCAnZ29vZy5hc3NlcnRzLkFzc2VydGlvbkVycm9yJ10sIFsnZ29vZy5kZWJ1Zy5FcnJvcicsICdnb29nLmRvbS5Ob2RlVHlwZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXNzZXJ0cy9hc3NlcnRzX3Rlc3QuanMnLCBbJ2dvb2cuYXNzZXJ0c1Rlc3QnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5hc3NlcnRzLkFzc2VydGlvbkVycm9yJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5yZWZsZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhc3luYy9hbmltYXRpb25kZWxheS5qcycsIFsnZ29vZy5hc3luYy5BbmltYXRpb25EZWxheSddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmV2ZW50cycsICdnb29nLmZ1bmN0aW9ucyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvYW5pbWF0aW9uZGVsYXlfdGVzdC5qcycsIFsnZ29vZy5hc3luYy5BbmltYXRpb25EZWxheVRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaW1lcicsICdnb29nLmFzeW5jLkFuaW1hdGlvbkRlbGF5JywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhc3luYy9jb25kaXRpb25hbGRlbGF5LmpzJywgWydnb29nLmFzeW5jLkNvbmRpdGlvbmFsRGVsYXknXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5hc3luYy5EZWxheSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvY29uZGl0aW9uYWxkZWxheV90ZXN0LmpzJywgWydnb29nLmFzeW5jLkNvbmRpdGlvbmFsRGVsYXlUZXN0J10sIFsnZ29vZy5hc3luYy5Db25kaXRpb25hbERlbGF5JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL2RlYm91bmNlci5qcycsIFsnZ29vZy5hc3luYy5EZWJvdW5jZXInXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5UaW1lciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvZGVib3VuY2VyX3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMuRGVib3VuY2VyVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3luYy5EZWJvdW5jZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL2RlbGF5LmpzJywgWydnb29nLkRlbGF5JywgJ2dvb2cuYXN5bmMuRGVsYXknXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5UaW1lciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvZGVsYXlfdGVzdC5qcycsIFsnZ29vZy5hc3luYy5EZWxheVRlc3QnXSwgWydnb29nLmFzeW5jLkRlbGF5JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL2ZyZWVsaXN0LmpzJywgWydnb29nLmFzeW5jLkZyZWVMaXN0J10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL2ZyZWVsaXN0X3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMuRnJlZUxpc3RUZXN0J10sIFsnZ29vZy5hc3luYy5GcmVlTGlzdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvbmV4dHRpY2suanMnLCBbJ2dvb2cuYXN5bmMubmV4dFRpY2snLCAnZ29vZy5hc3luYy50aHJvd0V4Y2VwdGlvbiddLCBbJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC5lbmdpbmUnLCAnZ29vZy5zdHJpbmcuQ29uc3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL25leHR0aWNrX3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMubmV4dFRpY2tUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuYXN5bmMubmV4dFRpY2snLCAnZ29vZy5kZWJ1Zy5FcnJvckhhbmRsZXInLCAnZ29vZy5kZWJ1Zy5lbnRyeVBvaW50UmVnaXN0cnknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvcnVuLmpzJywgWydnb29nLmFzeW5jLnJ1biddLCBbJ2dvb2cuYXN5bmMuV29ya1F1ZXVlJywgJ2dvb2cuYXN5bmMubmV4dFRpY2snLCAnZ29vZy5hc3luYy50aHJvd0V4Y2VwdGlvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvcnVuX25leHRfdGlja190ZXN0LmpzJywgWydnb29nLmFzeW5jLnJ1bk5leHRUaWNrVGVzdCddLCBbJ2dvb2cuYXN5bmMucnVuJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhc3luYy9ydW5fdGVzdC5qcycsIFsnZ29vZy5hc3luYy5ydW5UZXN0J10sIFsnZ29vZy5hc3luYy5ydW4nLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhc3luYy90aHJvdHRsZS5qcycsIFsnZ29vZy5UaHJvdHRsZScsICdnb29nLmFzeW5jLlRocm90dGxlJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuVGltZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2FzeW5jL3Rocm90dGxlX3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMuVGhyb3R0bGVUZXN0J10sIFsnZ29vZy5hc3luYy5UaHJvdHRsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdhc3luYy93b3JrcXVldWUuanMnLCBbJ2dvb2cuYXN5bmMuV29ya0l0ZW0nLCAnZ29vZy5hc3luYy5Xb3JrUXVldWUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5GcmVlTGlzdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYXN5bmMvd29ya3F1ZXVlX3Rlc3QuanMnLCBbJ2dvb2cuYXN5bmMuV29ya1F1ZXVlVGVzdCddLCBbJ2dvb2cuYXN5bmMuV29ya1F1ZXVlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdiYXNlLmpzJywgWydnb29nJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnYmFzZV9tb2R1bGVfdGVzdC5qcycsIFsnZ29vZy5iYXNlTW9kdWxlVGVzdCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy50ZXN0X21vZHVsZScsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuanN1bml0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdiYXNlX3Rlc3QuanMnLCBbJ2dvb2cuYmFzZVRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaW1lcicsICdnb29nLlVyaScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdF9tb2R1bGUnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjb2xvci9hbHBoYS5qcycsIFsnZ29vZy5jb2xvci5hbHBoYSddLCBbJ2dvb2cuY29sb3InXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NvbG9yL2FscGhhX3Rlc3QuanMnLCBbJ2dvb2cuY29sb3IuYWxwaGFUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmNvbG9yLmFscGhhJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjb2xvci9jb2xvci5qcycsIFsnZ29vZy5jb2xvcicsICdnb29nLmNvbG9yLkhzbCcsICdnb29nLmNvbG9yLkhzdicsICdnb29nLmNvbG9yLlJnYiddLCBbJ2dvb2cuY29sb3IubmFtZXMnLCAnZ29vZy5tYXRoJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjb2xvci9jb2xvcl90ZXN0LmpzJywgWydnb29nLmNvbG9yVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5jb2xvcicsICdnb29nLmNvbG9yLm5hbWVzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjb2xvci9uYW1lcy5qcycsIFsnZ29vZy5jb2xvci5uYW1lcyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2Flcy5qcycsIFsnZ29vZy5jcnlwdC5BZXMnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5jcnlwdC5CbG9ja0NpcGhlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYWVzX3Rlc3QuanMnLCBbJ2dvb2cuY3J5cHQuQWVzVGVzdCddLCBbJ2dvb2cuY3J5cHQnLCAnZ29vZy5jcnlwdC5BZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2FyYzQuanMnLCBbJ2dvb2cuY3J5cHQuQXJjNCddLCBbJ2dvb2cuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYXJjNF90ZXN0LmpzJywgWydnb29nLmNyeXB0LkFyYzRUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmNyeXB0LkFyYzQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2Jhc2U2NC5qcycsIFsnZ29vZy5jcnlwdC5iYXNlNjQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5jcnlwdCcsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczUnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYmFzZTY0X3Rlc3QuanMnLCBbJ2dvb2cuY3J5cHQuYmFzZTY0VGVzdCddLCBbJ2dvb2cuY3J5cHQnLCAnZ29vZy5jcnlwdC5iYXNlNjQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2Jhc2VuLmpzJywgWydnb29nLmNyeXB0LmJhc2VOJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2Jhc2VuX3Rlc3QuanMnLCBbJ2dvb2cuY3J5cHQuYmFzZU5UZXN0J10sIFsnZ29vZy5jcnlwdC5iYXNlTicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYmxvYmhhc2hlci5qcycsIFsnZ29vZy5jcnlwdC5CbG9iSGFzaGVyJywgJ2dvb2cuY3J5cHQuQmxvYkhhc2hlci5FdmVudFR5cGUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5mcycsICdnb29nLmxvZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYmxvYmhhc2hlcl90ZXN0LmpzJywgWydnb29nLmNyeXB0LkJsb2JIYXNoZXJUZXN0J10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0LkJsb2JIYXNoZXInLCAnZ29vZy5jcnlwdC5NZDUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2Jsb2NrY2lwaGVyLmpzJywgWydnb29nLmNyeXB0LkJsb2NrQ2lwaGVyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvYnl0ZXN0cmluZ19wZXJmLmpzJywgWydnb29nLmNyeXB0LmJ5dGVBcnJheVRvU3RyaW5nUGVyZiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLlBlcmZvcm1hbmNlVGFibGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2NiYy5qcycsIFsnZ29vZy5jcnlwdC5DYmMnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQuQmxvY2tDaXBoZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2NiY190ZXN0LmpzJywgWydnb29nLmNyeXB0LkNiY1Rlc3QnXSwgWydnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQuQWVzJywgJ2dvb2cuY3J5cHQuQ2JjJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9jcnlwdC5qcycsIFsnZ29vZy5jcnlwdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9jcnlwdF90ZXN0LmpzJywgWydnb29nLmNyeXB0VGVzdCddLCBbJ2dvb2cuY3J5cHQnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2N0ci5qcycsIFsnZ29vZy5jcnlwdC5DdHInXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmNyeXB0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9jdHJfdGVzdC5qcycsIFsnZ29vZy5jcnlwdC5DdHJUZXN0J10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0LkFlcycsICdnb29nLmNyeXB0LkN0cicsICdnb29nLnRlc3RpbmcuanN1bml0J10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvaGFzaC5qcycsIFsnZ29vZy5jcnlwdC5IYXNoJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvaGFzaDMyLmpzJywgWydnb29nLmNyeXB0Lmhhc2gzMiddLCBbJ2dvb2cuY3J5cHQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2hhc2gzMl90ZXN0LmpzJywgWydnb29nLmNyeXB0Lmhhc2gzMlRlc3QnXSwgWydnb29nLmNyeXB0Lmhhc2gzMicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2hhc2h0ZXN0ZXIuanMnLCBbJ2dvb2cuY3J5cHQuaGFzaFRlc3RlciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5jcnlwdCcsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cucmVmbGVjdCcsICdnb29nLnRlc3RpbmcuUGVyZm9ybWFuY2VUYWJsZScsICdnb29nLnRlc3RpbmcuUHNldWRvUmFuZG9tJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9obWFjLmpzJywgWydnb29nLmNyeXB0LkhtYWMnXSwgWydnb29nLmNyeXB0Lkhhc2gnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L2htYWNfdGVzdC5qcycsIFsnZ29vZy5jcnlwdC5IbWFjVGVzdCddLCBbJ2dvb2cuY3J5cHQuSG1hYycsICdnb29nLmNyeXB0LlNoYTEnLCAnZ29vZy5jcnlwdC5oYXNoVGVzdGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9tZDUuanMnLCBbJ2dvb2cuY3J5cHQuTWQ1J10sIFsnZ29vZy5jcnlwdC5IYXNoJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9tZDVfdGVzdC5qcycsIFsnZ29vZy5jcnlwdC5NZDVUZXN0J10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0Lk1kNScsICdnb29nLmNyeXB0Lmhhc2hUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3Bia2RmMi5qcycsIFsnZ29vZy5jcnlwdC5wYmtkZjInXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQuSG1hYycsICdnb29nLmNyeXB0LlNoYTEnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3Bia2RmMl90ZXN0LmpzJywgWydnb29nLmNyeXB0LnBia2RmMlRlc3QnXSwgWydnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQucGJrZGYyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9zaGExLmpzJywgWydnb29nLmNyeXB0LlNoYTEnXSwgWydnb29nLmNyeXB0Lkhhc2gnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTFfdGVzdC5qcycsIFsnZ29vZy5jcnlwdC5TaGExVGVzdCddLCBbJ2dvb2cuY3J5cHQnLCAnZ29vZy5jcnlwdC5TaGExJywgJ2dvb2cuY3J5cHQuaGFzaFRlc3RlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvc2hhMi5qcycsIFsnZ29vZy5jcnlwdC5TaGEyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5jcnlwdC5IYXNoJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9zaGEyMjQuanMnLCBbJ2dvb2cuY3J5cHQuU2hhMjI0J10sIFsnZ29vZy5jcnlwdC5TaGEyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9zaGEyMjRfdGVzdC5qcycsIFsnZ29vZy5jcnlwdC5TaGEyMjRUZXN0J10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0LlNoYTIyNCcsICdnb29nLmNyeXB0Lmhhc2hUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTI1Ni5qcycsIFsnZ29vZy5jcnlwdC5TaGEyNTYnXSwgWydnb29nLmNyeXB0LlNoYTInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTI1Nl90ZXN0LmpzJywgWydnb29nLmNyeXB0LlNoYTI1NlRlc3QnXSwgWydnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQuU2hhMjU2JywgJ2dvb2cuY3J5cHQuaGFzaFRlc3RlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3J5cHQvc2hhMl82NGJpdC5qcycsIFsnZ29vZy5jcnlwdC5TaGEyXzY0Yml0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5jcnlwdC5IYXNoJywgJ2dvb2cubWF0aC5Mb25nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdjcnlwdC9zaGEyXzY0Yml0X3Rlc3QuanMnLCBbJ2dvb2cuY3J5cHQuU2hhMl82NGJpdF90ZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmNyeXB0JywgJ2dvb2cuY3J5cHQuU2hhMzg0JywgJ2dvb2cuY3J5cHQuU2hhNTEyJywgJ2dvb2cuY3J5cHQuU2hhNTEyXzI1NicsICdnb29nLmNyeXB0Lmhhc2hUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTM4NC5qcycsIFsnZ29vZy5jcnlwdC5TaGEzODQnXSwgWydnb29nLmNyeXB0LlNoYTJfNjRiaXQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTUxMi5qcycsIFsnZ29vZy5jcnlwdC5TaGE1MTInXSwgWydnb29nLmNyeXB0LlNoYTJfNjRiaXQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2NyeXB0L3NoYTUxMl8yNTYuanMnLCBbJ2dvb2cuY3J5cHQuU2hhNTEyXzI1NiddLCBbJ2dvb2cuY3J5cHQuU2hhMl82NGJpdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3Nzb20vY3Nzb20uanMnLCBbJ2dvb2cuY3Nzb20nLCAnZ29vZy5jc3NvbS5Dc3NSdWxlVHlwZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3Nzb20vY3Nzb21fdGVzdC5qcycsIFsnZ29vZy5jc3NvbVRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuY3Nzb20nLCAnZ29vZy5jc3NvbS5Dc3NSdWxlVHlwZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnY3Nzb20vaWZyYW1lL3N0eWxlLmpzJywgWydnb29nLmNzc29tLmlmcmFtZS5zdHlsZSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmNzc29tJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Nzc29tL2lmcmFtZS9zdHlsZV90ZXN0LmpzJywgWydnb29nLmNzc29tLmlmcmFtZS5zdHlsZVRlc3QnXSwgWydnb29nLmNzc29tJywgJ2dvb2cuY3Nzb20uaWZyYW1lLnN0eWxlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2RhdGFtYW5hZ2VyLmpzJywgWydnb29nLmRzLkRhdGFNYW5hZ2VyJ10sIFsnZ29vZy5kcy5CYXNpY05vZGVMaXN0JywgJ2dvb2cuZHMuRGF0YU5vZGUnLCAnZ29vZy5kcy5FeHByJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RydWN0cycsICdnb29nLnN0cnVjdHMuTWFwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2RhdGFzb3VyY2UuanMnLCBbJ2dvb2cuZHMuQmFzZURhdGFOb2RlJywgJ2dvb2cuZHMuQmFzaWNOb2RlTGlzdCcsICdnb29nLmRzLkRhdGFOb2RlJywgJ2dvb2cuZHMuRGF0YU5vZGVMaXN0JywgJ2dvb2cuZHMuRW1wdHlOb2RlTGlzdCcsICdnb29nLmRzLkxvYWRTdGF0ZScsICdnb29nLmRzLlNvcnRlZE5vZGVMaXN0JywgJ2dvb2cuZHMuVXRpbCcsICdnb29nLmRzLmxvZ2dlciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5sb2cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGFzb3VyY2UvZGF0YXNvdXJjZV90ZXN0LmpzJywgWydnb29nLmRzLkpzRGF0YVNvdXJjZVRlc3QnXSwgWydnb29nLmRvbS54bWwnLCAnZ29vZy5kcy5EYXRhTWFuYWdlcicsICdnb29nLmRzLkpzRGF0YVNvdXJjZScsICdnb29nLmRzLlNvcnRlZE5vZGVMaXN0JywgJ2dvb2cuZHMuWG1sRGF0YVNvdXJjZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0YXNvdXJjZS9leHByLmpzJywgWydnb29nLmRzLkV4cHInXSwgWydnb29nLmRzLkJhc2ljTm9kZUxpc3QnLCAnZ29vZy5kcy5FbXB0eU5vZGVMaXN0JywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2V4cHJfdGVzdC5qcycsIFsnZ29vZy5kcy5FeHByVGVzdCddLCBbJ2dvb2cuZHMuRGF0YU1hbmFnZXInLCAnZ29vZy5kcy5FeHByJywgJ2dvb2cuZHMuSnNEYXRhU291cmNlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2Zhc3RkYXRhbm9kZS5qcycsIFsnZ29vZy5kcy5BYnN0cmFjdEZhc3REYXRhTm9kZScsICdnb29nLmRzLkZhc3REYXRhTm9kZScsICdnb29nLmRzLkZhc3RMaXN0Tm9kZScsICdnb29nLmRzLlByaW1pdGl2ZUZhc3REYXRhTm9kZSddLCBbJ2dvb2cuZHMuRGF0YU1hbmFnZXInLCAnZ29vZy5kcy5EYXRhTm9kZUxpc3QnLCAnZ29vZy5kcy5FbXB0eU5vZGVMaXN0JywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2Zhc3RkYXRhbm9kZV90ZXN0LmpzJywgWydnb29nLmRzLkZhc3REYXRhTm9kZVRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZHMuRGF0YU1hbmFnZXInLCAnZ29vZy5kcy5FeHByJywgJ2dvb2cuZHMuRmFzdERhdGFOb2RlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2pzZGF0YXNvdXJjZS5qcycsIFsnZ29vZy5kcy5Kc0RhdGFTb3VyY2UnLCAnZ29vZy5kcy5Kc1Byb3BlcnR5RGF0YVNvdXJjZSddLCBbJ2dvb2cuZHMuQmFzZURhdGFOb2RlJywgJ2dvb2cuZHMuQmFzaWNOb2RlTGlzdCcsICdnb29nLmRzLkRhdGFNYW5hZ2VyJywgJ2dvb2cuZHMuRGF0YU5vZGUnLCAnZ29vZy5kcy5FbXB0eU5vZGVMaXN0JywgJ2dvb2cuZHMuTG9hZFN0YXRlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRhc291cmNlL2pzb25kYXRhc291cmNlLmpzJywgWydnb29nLmRzLkpzb25EYXRhU291cmNlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuZHMuRGF0YU1hbmFnZXInLCAnZ29vZy5kcy5Kc0RhdGFTb3VyY2UnLCAnZ29vZy5kcy5Mb2FkU3RhdGUnLCAnZ29vZy5kcy5sb2dnZXInLCAnZ29vZy5sb2cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGFzb3VyY2UvanN4bWxodHRwZGF0YXNvdXJjZS5qcycsIFsnZ29vZy5kcy5Kc1htbEh0dHBEYXRhU291cmNlJ10sIFsnZ29vZy5VcmknLCAnZ29vZy5kcy5EYXRhTWFuYWdlcicsICdnb29nLmRzLkZhc3REYXRhTm9kZScsICdnb29nLmRzLkxvYWRTdGF0ZScsICdnb29nLmRzLmxvZ2dlcicsICdnb29nLmV2ZW50cycsICdnb29nLmxvZycsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuWGhySW8nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGFzb3VyY2UvanN4bWxodHRwZGF0YXNvdXJjZV90ZXN0LmpzJywgWydnb29nLmRzLkpzWG1sSHR0cERhdGFTb3VyY2VUZXN0J10sIFsnZ29vZy5kcy5Kc1htbEh0dHBEYXRhU291cmNlJywgJ2dvb2cudGVzdGluZy5UZXN0UXVldWUnLCAnZ29vZy50ZXN0aW5nLm5ldC5YaHJJbycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0YXNvdXJjZS94bWxkYXRhc291cmNlLmpzJywgWydnb29nLmRzLlhtbERhdGFTb3VyY2UnLCAnZ29vZy5kcy5YbWxIdHRwRGF0YVNvdXJjZSddLCBbJ2dvb2cuVXJpJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLnhtbCcsICdnb29nLmRzLkJhc2ljTm9kZUxpc3QnLCAnZ29vZy5kcy5EYXRhTWFuYWdlcicsICdnb29nLmRzLkRhdGFOb2RlJywgJ2dvb2cuZHMuTG9hZFN0YXRlJywgJ2dvb2cuZHMubG9nZ2VyJywgJ2dvb2cubG9nJywgJ2dvb2cubmV0LlhocklvJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRlL2RhdGUuanMnLCBbJ2dvb2cuZGF0ZScsICdnb29nLmRhdGUuRGF0ZScsICdnb29nLmRhdGUuRGF0ZVRpbWUnLCAnZ29vZy5kYXRlLkludGVydmFsJywgJ2dvb2cuZGF0ZS5tb250aCcsICdnb29nLmRhdGUud2Vla0RheSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRhdGUuRGF0ZUxpa2UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scycsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0ZS9kYXRlX3Rlc3QuanMnLCBbJ2dvb2cuZGF0ZVRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZGF0ZScsICdnb29nLmRhdGUuRGF0ZScsICdnb29nLmRhdGUuRGF0ZVRpbWUnLCAnZ29vZy5kYXRlLkludGVydmFsJywgJ2dvb2cuZGF0ZS5tb250aCcsICdnb29nLmRhdGUud2Vla0RheScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzJywgJ2dvb2cudGVzdGluZy5FeHBlY3RlZEZhaWx1cmVzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucGxhdGZvcm0nLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGUvZGF0ZWxpa2UuanMnLCBbJ2dvb2cuZGF0ZS5EYXRlTGlrZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGUvZGF0ZXJhbmdlLmpzJywgWydnb29nLmRhdGUuRGF0ZVJhbmdlJywgJ2dvb2cuZGF0ZS5EYXRlUmFuZ2UuSXRlcmF0b3InLCAnZ29vZy5kYXRlLkRhdGVSYW5nZS5TdGFuZGFyZERhdGVSYW5nZUtleXMnXSwgWydnb29nLmRhdGUuRGF0ZScsICdnb29nLmRhdGUuSW50ZXJ2YWwnLCAnZ29vZy5pdGVyLkl0ZXJhdG9yJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRlL2RhdGVyYW5nZV90ZXN0LmpzJywgWydnb29nLmRhdGUuRGF0ZVJhbmdlVGVzdCddLCBbJ2dvb2cuZGF0ZS5EYXRlJywgJ2dvb2cuZGF0ZS5EYXRlUmFuZ2UnLCAnZ29vZy5kYXRlLkludGVydmFsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RhdGUvZHVyYXRpb24uanMnLCBbJ2dvb2cuZGF0ZS5kdXJhdGlvbiddLCBbJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uTWVzc2FnZUZvcm1hdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0ZS9kdXJhdGlvbl90ZXN0LmpzJywgWydnb29nLmRhdGUuZHVyYXRpb25UZXN0J10sIFsnZ29vZy5kYXRlLmR1cmF0aW9uJywgJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYm4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZhJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRlL3JlbGF0aXZlLmpzJywgWydnb29nLmRhdGUucmVsYXRpdmUnLCAnZ29vZy5kYXRlLnJlbGF0aXZlLlRpbWVEZWx0YUZvcm1hdHRlcicsICdnb29nLmRhdGUucmVsYXRpdmUuVW5pdCddLCBbJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJucycsICdnb29nLmkxOG4uUmVsYXRpdmVEYXRlVGltZUZvcm1hdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0ZS9yZWxhdGl2ZV90ZXN0LmpzJywgWydnb29nLmRhdGUucmVsYXRpdmVUZXN0J10sIFsnZ29vZy5kYXRlLnJlbGF0aXZlQ29tbW9uVGVzdHMnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRlL3JlbGF0aXZlY29tbW9udGVzdHMuanMnLCBbJ2dvb2cuZGF0ZS5yZWxhdGl2ZUNvbW1vblRlc3RzJ10sIFsnZ29vZy5kYXRlLkRhdGVUaW1lJywgJ2dvb2cuZGF0ZS5yZWxhdGl2ZScsICdnb29nLmkxOG4uRGF0ZVRpbWVGb3JtYXQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYXInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYm4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbm8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbm8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYm4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbm8nLCAnZ29vZy5pMThuLnJlbGF0aXZlRGF0ZVRpbWVTeW1ib2xzJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYXRlL3V0Y2RhdGV0aW1lLmpzJywgWydnb29nLmRhdGUuVXRjRGF0ZVRpbWUnXSwgWydnb29nLmRhdGUnLCAnZ29vZy5kYXRlLkRhdGUnLCAnZ29vZy5kYXRlLkRhdGVUaW1lJywgJ2dvb2cuZGF0ZS5JbnRlcnZhbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGF0ZS91dGNkYXRldGltZV90ZXN0LmpzJywgWydnb29nLmRhdGUuVXRjRGF0ZVRpbWVUZXN0J10sIFsnZ29vZy5kYXRlLkludGVydmFsJywgJ2dvb2cuZGF0ZS5VdGNEYXRlVGltZScsICdnb29nLmRhdGUubW9udGgnLCAnZ29vZy5kYXRlLndlZWtEYXknLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RiL2N1cnNvci5qcycsIFsnZ29vZy5kYi5DdXJzb3InXSwgWydnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZGIuRXJyb3InLCAnZ29vZy5kYi5LZXlSYW5nZScsICdnb29nLmRlYnVnJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYi9kYi5qcycsIFsnZ29vZy5kYicsICdnb29nLmRiLkJsb2NrZWRDYWxsYmFjaycsICdnb29nLmRiLlVwZ3JhZGVOZWVkZWRDYWxsYmFjayddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZGIuRXJyb3InLCAnZ29vZy5kYi5JbmRleGVkRGInLCAnZ29vZy5kYi5UcmFuc2FjdGlvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGIvZGJfdGVzdC5qcycsIFsnZ29vZy5kYlRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5hcnJheScsICdnb29nLmRiJywgJ2dvb2cuZGIuQ3Vyc29yJywgJ2dvb2cuZGIuRXJyb3InLCAnZ29vZy5kYi5JbmRleGVkRGInLCAnZ29vZy5kYi5LZXlSYW5nZScsICdnb29nLmRiLlRyYW5zYWN0aW9uJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYi9lcnJvci5qcycsIFsnZ29vZy5kYi5Eb21FcnJvckxpa2UnLCAnZ29vZy5kYi5FcnJvcicsICdnb29nLmRiLkVycm9yLkVycm9yQ29kZScsICdnb29nLmRiLkVycm9yLkVycm9yTmFtZScsICdnb29nLmRiLkVycm9yLlZlcnNpb25DaGFuZ2VCbG9ja2VkRXJyb3InXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5FcnJvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGIvaW5kZXguanMnLCBbJ2dvb2cuZGIuSW5kZXgnXSwgWydnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZGIuQ3Vyc29yJywgJ2dvb2cuZGIuRXJyb3InLCAnZ29vZy5kYi5LZXlSYW5nZScsICdnb29nLmRlYnVnJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYi9pbmRleGVkZGIuanMnLCBbJ2dvb2cuZGIuSW5kZXhlZERiJ10sIFsnZ29vZy5kYi5FcnJvcicsICdnb29nLmRiLk9iamVjdFN0b3JlJywgJ2dvb2cuZGIuVHJhbnNhY3Rpb24nLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0J10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGIva2V5cmFuZ2UuanMnLCBbJ2dvb2cuZGIuS2V5UmFuZ2UnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkYi9vYmplY3RzdG9yZS5qcycsIFsnZ29vZy5kYi5PYmplY3RTdG9yZSddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5kYi5DdXJzb3InLCAnZ29vZy5kYi5FcnJvcicsICdnb29nLmRiLkluZGV4JywgJ2dvb2cuZGIuS2V5UmFuZ2UnLCAnZ29vZy5kZWJ1ZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGIvdHJhbnNhY3Rpb24uanMnLCBbJ2dvb2cuZGIuVHJhbnNhY3Rpb24nLCAnZ29vZy5kYi5UcmFuc2FjdGlvbi5UcmFuc2FjdGlvbk1vZGUnXSwgWydnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZGIuRXJyb3InLCAnZ29vZy5kYi5PYmplY3RTdG9yZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2NvbnNvbGUuanMnLCBbJ2dvb2cuZGVidWcuQ29uc29sZSddLCBbJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLmRlYnVnLlRleHRGb3JtYXR0ZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2NvbnNvbGVfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5Db25zb2xlVGVzdCddLCBbJ2dvb2cuZGVidWcuQ29uc29sZScsICdnb29nLmRlYnVnLkxvZ1JlY29yZCcsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2RlYnVnLmpzJywgWydnb29nLmRlYnVnJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRlYnVnLmVycm9yY29udGV4dCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZGVidWdfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Z1Rlc3QnXSwgWydnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuZXJyb3Jjb250ZXh0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9kZWJ1Z3dpbmRvdy5qcycsIFsnZ29vZy5kZWJ1Zy5EZWJ1Z1dpbmRvdyddLCBbJ2dvb2cuZGVidWcuSHRtbEZvcm1hdHRlcicsICdnb29nLmRlYnVnLkxvZ01hbmFnZXInLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3RydWN0cy5DaXJjdWxhckJ1ZmZlcicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZGVidWd3aW5kb3dfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5EZWJ1Z1dpbmRvd1Rlc3QnXSwgWydnb29nLmRlYnVnLkRlYnVnV2luZG93JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9kZXZjc3MvZGV2Y3NzLmpzJywgWydnb29nLmRlYnVnLkRldkNzcycsICdnb29nLmRlYnVnLkRldkNzcy5Vc2VyQWdlbnQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5jc3NvbScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9kZXZjc3MvZGV2Y3NzX3Rlc3QuanMnLCBbJ2dvb2cuZGVidWcuRGV2Q3NzVGVzdCddLCBbJ2dvb2cuZGVidWcuRGV2Q3NzJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2RldmNzcy9kZXZjc3NydW5uZXIuanMnLCBbJ2dvb2cuZGVidWcuZGV2Q3NzUnVubmVyJ10sIFsnZ29vZy5kZWJ1Zy5EZXZDc3MnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2RpdmNvbnNvbGUuanMnLCBbJ2dvb2cuZGVidWcuRGl2Q29uc29sZSddLCBbJ2dvb2cuZGVidWcuSHRtbEZvcm1hdHRlcicsICdnb29nLmRlYnVnLkxvZ01hbmFnZXInLCAnZ29vZy5kb20uRG9tSGVscGVyJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2VuaGFuY2VlcnJvcl90ZXN0LmpzJywgWydnb29nLmRlYnVnRW5oYW5jZUVycm9yVGVzdCddLCBbJ2dvb2cuZGVidWcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2VudHJ5cG9pbnRyZWdpc3RyeS5qcycsIFsnZ29vZy5kZWJ1Zy5FbnRyeVBvaW50TW9uaXRvcicsICdnb29nLmRlYnVnLmVudHJ5UG9pbnRSZWdpc3RyeSddLCBbJ2dvb2cuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZW50cnlwb2ludHJlZ2lzdHJ5X3Rlc3QuanMnLCBbJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5VGVzdCddLCBbJ2dvb2cuZGVidWcuRXJyb3JIYW5kbGVyJywgJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9lcnJvci5qcycsIFsnZ29vZy5kZWJ1Zy5FcnJvciddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9lcnJvcl90ZXN0LmpzJywgWydnb29nLmRlYnVnLkVycm9yVGVzdCddLCBbJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZXJyb3Jjb250ZXh0LmpzJywgWydnb29nLmRlYnVnLmVycm9yY29udGV4dCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2Vycm9yY29udGV4dF90ZXN0LmpzJywgWydnb29nLmRlYnVnLmVycm9yY29udGV4dFRlc3QnXSwgWydnb29nLmRlYnVnLmVycm9yY29udGV4dCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZXJyb3JoYW5kbGVyLmpzJywgWydnb29nLmRlYnVnLkVycm9ySGFuZGxlcicsICdnb29nLmRlYnVnLkVycm9ySGFuZGxlci5Qcm90ZWN0ZWRGdW5jdGlvbkVycm9yJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuRW50cnlQb2ludE1vbml0b3InLCAnZ29vZy5kZWJ1Zy5FcnJvcicsICdnb29nLmRlYnVnLlRyYWNlJ10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZXJyb3JoYW5kbGVyX2FzeW5jX3Rlc3QuanMnLCBbJ2dvb2cuZGVidWcuRXJyb3JIYW5kbGVyQXN5bmNUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuZGVidWcuRXJyb3JIYW5kbGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzOCcsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9lcnJvcmhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5FcnJvckhhbmRsZXJUZXN0J10sIFsnZ29vZy5kZWJ1Zy5FcnJvckhhbmRsZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9lcnJvcmhhbmRsZXJ3ZWFrZGVwLmpzJywgWydnb29nLmRlYnVnLmVycm9ySGFuZGxlcldlYWtEZXAnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9lcnJvcnJlcG9ydGVyLmpzJywgWydnb29nLmRlYnVnLkVycm9yUmVwb3J0ZXInLCAnZ29vZy5kZWJ1Zy5FcnJvclJlcG9ydGVyLkV4Y2VwdGlvbkV2ZW50J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcnLCAnZ29vZy5kZWJ1Zy5FcnJvcicsICdnb29nLmRlYnVnLkVycm9ySGFuZGxlcicsICdnb29nLmRlYnVnLmVudHJ5UG9pbnRSZWdpc3RyeScsICdnb29nLmRlYnVnLmVycm9yY29udGV4dCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmxvZycsICdnb29nLm5ldC5YaHJJbycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnVyaS51dGlscycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZXJyb3JyZXBvcnRlcl90ZXN0LmpzJywgWydnb29nLmRlYnVnLkVycm9yUmVwb3J0ZXJUZXN0J10sIFsnZ29vZy5kZWJ1Zy5FcnJvcicsICdnb29nLmRlYnVnLkVycm9yUmVwb3J0ZXInLCAnZ29vZy5kZWJ1Zy5lcnJvcmNvbnRleHQnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZmFuY3l3aW5kb3cuanMnLCBbJ2dvb2cuZGVidWcuRmFuY3lXaW5kb3cnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRlYnVnLkRlYnVnV2luZG93JywgJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLmRvbS5Eb21IZWxwZXInLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVN0eWxlU2hlZXQnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2Zvcm1hdHRlci5qcycsIFsnZ29vZy5kZWJ1Zy5Gb3JtYXR0ZXInLCAnZ29vZy5kZWJ1Zy5IdG1sRm9ybWF0dGVyJywgJ2dvb2cuZGVidWcuVGV4dEZvcm1hdHRlciddLCBbJ2dvb2cuZGVidWcnLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5kZWJ1Zy5SZWxhdGl2ZVRpbWVQcm92aWRlcicsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cuc3RyaW5nLkNvbnN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9mb3JtYXR0ZXJfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5Gb3JtYXR0ZXJUZXN0J10sIFsnZ29vZy5kZWJ1Zy5IdG1sRm9ybWF0dGVyJywgJ2dvb2cuZGVidWcuTG9nUmVjb3JkJywgJ2dvb2cuZGVidWcuTG9nZ2VyJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZnBzZGlzcGxheS5qcycsIFsnZ29vZy5kZWJ1Zy5GcHNEaXNwbGF5J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuYXN5bmMuQW5pbWF0aW9uRGVsYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvZnBzZGlzcGxheV90ZXN0LmpzJywgWydnb29nLmRlYnVnLkZwc0Rpc3BsYXlUZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmRlYnVnLkZwc0Rpc3BsYXknLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9sb2didWZmZXIuanMnLCBbJ2dvb2cuZGVidWcuTG9nQnVmZmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuTG9nUmVjb3JkJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9sb2didWZmZXJfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5Mb2dCdWZmZXJUZXN0J10sIFsnZ29vZy5kZWJ1Zy5Mb2dCdWZmZXInLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL2xvZ2dlci5qcycsIFsnZ29vZy5kZWJ1Zy5Mb2dNYW5hZ2VyJywgJ2dvb2cuZGVidWcuTG9nZ2FibGUnLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5kZWJ1Zy5Mb2dnZXIuTGV2ZWwnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuTG9nQnVmZmVyJywgJ2dvb2cuZGVidWcuTG9nUmVjb3JkJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9sb2dnZXJfdGVzdC5qcycsIFsnZ29vZy5kZWJ1Zy5Mb2dnZXJUZXN0J10sIFsnZ29vZy5kZWJ1Zy5Mb2dNYW5hZ2VyJywgJ2dvb2cuZGVidWcuTG9nZ2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9sb2dyZWNvcmQuanMnLCBbJ2dvb2cuZGVidWcuTG9nUmVjb3JkJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvbG9ncmVjb3Jkc2VyaWFsaXplci5qcycsIFsnZ29vZy5kZWJ1Zy5sb2dSZWNvcmRTZXJpYWxpemVyJ10sIFsnZ29vZy5kZWJ1Zy5Mb2dSZWNvcmQnLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5qc29uJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWJ1Zy9sb2dyZWNvcmRzZXJpYWxpemVyX3Rlc3QuanMnLCBbJ2dvb2cuZGVidWcubG9nUmVjb3JkU2VyaWFsaXplclRlc3QnXSwgWydnb29nLmRlYnVnLkxvZ1JlY29yZCcsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLmRlYnVnLmxvZ1JlY29yZFNlcmlhbGl6ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL3JlbGF0aXZldGltZXByb3ZpZGVyLmpzJywgWydnb29nLmRlYnVnLlJlbGF0aXZlVGltZVByb3ZpZGVyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVidWcvdHJhY2VyLmpzJywgWydnb29nLmRlYnVnLlN0b3BUcmFjZURldGFpbCcsICdnb29nLmRlYnVnLlRyYWNlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5pdGVyJywgJ2dvb2cubG9nJywgJ2dvb2cuc3RydWN0cy5NYXAnLCAnZ29vZy5zdHJ1Y3RzLlNpbXBsZVBvb2wnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlYnVnL3RyYWNlcl90ZXN0LmpzJywgWydnb29nLmRlYnVnLlRyYWNlVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kZWJ1Zy5UcmFjZScsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlZmluZWNsYXNzX3Rlc3QuanMnLCBbJ2dvb2cuZGVmaW5lQ2xhc3NUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RlbGVnYXRlL2RlbGVnYXRlcmVnaXN0cnkuanMnLCBbJ2dvb2cuZGVsZWdhdGUuRGVsZWdhdGVSZWdpc3RyeSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWxlZ2F0ZS9kZWxlZ2F0ZXJlZ2lzdHJ5X3Rlc3QuanMnLCBbJ2dvb2cuZGVsZWdhdGUuRGVsZWdhdGVSZWdpc3RyeVRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZGVsZWdhdGUuRGVsZWdhdGVSZWdpc3RyeScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZGVsZWdhdGUvZGVsZWdhdGVzLmpzJywgWydnb29nLmRlbGVnYXRlLmRlbGVnYXRlcyddLCBbXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkZWxlZ2F0ZS9kZWxlZ2F0ZXNfdGVzdC5qcycsIFsnZ29vZy5kZWxlZ2F0ZS5kZWxlZ2F0ZXNUZXN0J10sIFsnZ29vZy5kZWxlZ2F0ZS5kZWxlZ2F0ZXMnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkaXNwb3NhYmxlL2Rpc3Bvc2FibGUuanMnLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmRpc3Bvc2UnLCAnZ29vZy5kaXNwb3NlQWxsJ10sIFsnZ29vZy5kaXNwb3NhYmxlLklEaXNwb3NhYmxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkaXNwb3NhYmxlL2Rpc3Bvc2FibGVfdGVzdC5qcycsIFsnZ29vZy5EaXNwb3NhYmxlVGVzdCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Rpc3Bvc2FibGUvaWRpc3Bvc2FibGUuanMnLCBbJ2dvb2cuZGlzcG9zYWJsZS5JRGlzcG9zYWJsZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hYnN0cmFjdG11bHRpcmFuZ2UuanMnLCBbJ2dvb2cuZG9tLkFic3RyYWN0TXVsdGlSYW5nZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uQWJzdHJhY3RSYW5nZScsICdnb29nLmRvbS5UZXh0UmFuZ2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hYnN0cmFjdHJhbmdlLmpzJywgWydnb29nLmRvbS5BYnN0cmFjdFJhbmdlJywgJ2dvb2cuZG9tLlJhbmdlSXRlcmF0b3InLCAnZ29vZy5kb20uUmFuZ2VUeXBlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uU2F2ZWRDYXJldFJhbmdlJywgJ2dvb2cuZG9tLlRhZ0l0ZXJhdG9yJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vYWJzdHJhY3RyYW5nZV90ZXN0LmpzJywgWydnb29nLmRvbS5BYnN0cmFjdFJhbmdlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkFic3RyYWN0UmFuZ2UnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2FuaW1hdGlvbmZyYW1lL2FuaW1hdGlvbmZyYW1lLmpzJywgWydnb29nLmRvbS5hbmltYXRpb25GcmFtZScsICdnb29nLmRvbS5hbmltYXRpb25GcmFtZS5TcGVjJywgJ2dvb2cuZG9tLmFuaW1hdGlvbkZyYW1lLlN0YXRlJ10sIFsnZ29vZy5kb20uYW5pbWF0aW9uRnJhbWUucG9seWZpbGwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hbmltYXRpb25mcmFtZS9hbmltYXRpb25mcmFtZV90ZXN0LmpzJywgWydnb29nLmRvbS5BbmltYXRpb25GcmFtZVRlc3QnXSwgWydnb29nLmRvbS5hbmltYXRpb25GcmFtZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vYW5pbWF0aW9uZnJhbWUvcG9seWZpbGwuanMnLCBbJ2dvb2cuZG9tLmFuaW1hdGlvbkZyYW1lLnBvbHlmaWxsJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hbm5vdGF0ZS5qcycsIFsnZ29vZy5kb20uYW5ub3RhdGUnLCAnZ29vZy5kb20uYW5ub3RhdGUuQW5ub3RhdGVGbiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hbm5vdGF0ZV90ZXN0LmpzJywgWydnb29nLmRvbS5hbm5vdGF0ZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmFubm90YXRlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2Fzc2VydHMuanMnLCBbJ2dvb2cuZG9tLmFzc2VydHMnXSwgWydnb29nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9hc3NlcnRzX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLmFzc2VydHNUZXN0J10sIFsnZ29vZy5kb20uYXNzZXJ0cycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2F0dHIuanMnLCBbJ2dvb2cuZG9tLkF0dHInXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vYnJvd3NlcmZlYXR1cmUuanMnLCBbJ2dvb2cuZG9tLkJyb3dzZXJGZWF0dXJlJ10sIFsnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9icm93c2VyZmVhdHVyZV90ZXN0LmpzJywgWydnb29nLmRvbS5Ccm93c2VyRmVhdHVyZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ccm93c2VyRmVhdHVyZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2Jyb3dzZXJyYW5nZS9hYnN0cmFjdHJhbmdlLmpzJywgWydnb29nLmRvbS5icm93c2VycmFuZ2UuQWJzdHJhY3RSYW5nZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlRW5kcG9pbnQnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5UZXh0UmFuZ2VJdGVyYXRvcicsICdnb29nLml0ZXInLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuU3RyaW5nQnVmZmVyJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vYnJvd3NlcnJhbmdlL2Jyb3dzZXJyYW5nZS5qcycsIFsnZ29vZy5kb20uYnJvd3NlcnJhbmdlJywgJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5FcnJvciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5HZWNrb1JhbmdlJywgJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5JZVJhbmdlJywgJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5PcGVyYVJhbmdlJywgJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5XM2NSYW5nZScsICdnb29nLmRvbS5icm93c2VycmFuZ2UuV2ViS2l0UmFuZ2UnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9icm93c2VycmFuZ2UvYnJvd3NlcnJhbmdlX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5SYW5nZUVuZHBvaW50JywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uYnJvd3NlcnJhbmdlJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9icm93c2VycmFuZ2UvZ2Vja29yYW5nZS5qcycsIFsnZ29vZy5kb20uYnJvd3NlcnJhbmdlLkdlY2tvUmFuZ2UnXSwgWydnb29nLmRvbS5icm93c2VycmFuZ2UuVzNjUmFuZ2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9icm93c2VycmFuZ2UvaWVyYW5nZS5qcycsIFsnZ29vZy5kb20uYnJvd3NlcnJhbmdlLkllUmFuZ2UnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlRW5kcG9pbnQnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5icm93c2VycmFuZ2UuQWJzdHJhY3RSYW5nZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLmxvZycsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2Jyb3dzZXJyYW5nZS9vcGVyYXJhbmdlLmpzJywgWydnb29nLmRvbS5icm93c2VycmFuZ2UuT3BlcmFSYW5nZSddLCBbJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5XM2NSYW5nZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2Jyb3dzZXJyYW5nZS93M2NyYW5nZS5qcycsIFsnZ29vZy5kb20uYnJvd3NlcnJhbmdlLlczY1JhbmdlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZUVuZHBvaW50JywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uYnJvd3NlcnJhbmdlLkFic3RyYWN0UmFuZ2UnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9icm93c2VycmFuZ2Uvd2Via2l0cmFuZ2UuanMnLCBbJ2dvb2cuZG9tLmJyb3dzZXJyYW5nZS5XZWJLaXRSYW5nZSddLCBbJ2dvb2cuZG9tLlJhbmdlRW5kcG9pbnQnLCAnZ29vZy5kb20uYnJvd3NlcnJhbmdlLlczY1JhbmdlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vYnVmZmVyZWR2aWV3cG9ydHNpemVtb25pdG9yLmpzJywgWydnb29nLmRvbS5CdWZmZXJlZFZpZXdwb3J0U2l6ZU1vbml0b3InXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5EZWxheScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9idWZmZXJlZHZpZXdwb3J0c2l6ZW1vbml0b3JfdGVzdC5qcycsIFsnZ29vZy5kb20uQnVmZmVyZWRWaWV3cG9ydFNpemVNb25pdG9yVGVzdCddLCBbJ2dvb2cuZG9tLkJ1ZmZlcmVkVmlld3BvcnRTaXplTW9uaXRvcicsICdnb29nLmRvbS5WaWV3cG9ydFNpemVNb25pdG9yJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm1hdGguU2l6ZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2NsYXNzZXMuanMnLCBbJ2dvb2cuZG9tLmNsYXNzZXMnXSwgWydnb29nLmFycmF5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vY2xhc3Nlc190ZXN0LmpzJywgWydnb29nLmRvbS5jbGFzc2VzX3Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9jbGFzc2xpc3QuanMnLCBbJ2dvb2cuZG9tLmNsYXNzbGlzdCddLCBbJ2dvb2cuYXJyYXknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9jbGFzc2xpc3RfdGVzdC5qcycsIFsnZ29vZy5kb20uY2xhc3NsaXN0X3Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2NvbnRyb2xyYW5nZS5qcycsIFsnZ29vZy5kb20uQ29udHJvbFJhbmdlJywgJ2dvb2cuZG9tLkNvbnRyb2xSYW5nZUl0ZXJhdG9yJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5BYnN0cmFjdE11bHRpUmFuZ2UnLCAnZ29vZy5kb20uQWJzdHJhY3RSYW5nZScsICdnb29nLmRvbS5SYW5nZUl0ZXJhdG9yJywgJ2dvb2cuZG9tLlJhbmdlVHlwZScsICdnb29nLmRvbS5TYXZlZFJhbmdlJywgJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuZG9tLlRleHRSYW5nZScsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2NvbnRyb2xyYW5nZV90ZXN0LmpzJywgWydnb29nLmRvbS5Db250cm9sUmFuZ2VUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uQ29udHJvbFJhbmdlJywgJ2dvb2cuZG9tLlJhbmdlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLlRleHRSYW5nZScsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZGF0YXNldC5qcycsIFsnZ29vZy5kb20uZGF0YXNldCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZGF0YXNldF90ZXN0LmpzJywgWydnb29nLmRvbS5kYXRhc2V0VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmRhdGFzZXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9kb20uanMnLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkFwcGVuZGFibGUnLCAnZ29vZy5kb20uRG9tSGVscGVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20uQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwudW5jaGVja2VkY29udmVyc2lvbnMnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2RvbV9jb21waWxlX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLkRvbUNvbXBpbGVUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2RvbV90ZXN0LmpzJywgWydnb29nLmRvbS5kb21fdGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwudGVzdGluZycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnN0cmluZy5Vbmljb2RlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZm9udHNpemVtb25pdG9yLmpzJywgWydnb29nLmRvbS5Gb250U2l6ZU1vbml0b3InLCAnZ29vZy5kb20uRm9udFNpemVNb25pdG9yLkV2ZW50VHlwZSddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZm9udHNpemVtb25pdG9yX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLkZvbnRTaXplTW9uaXRvclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Gb250U2l6ZU1vbml0b3InLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZm9ybXMuanMnLCBbJ2dvb2cuZG9tLmZvcm1zJ10sIFsnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cud2luZG93J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vZm9ybXNfdGVzdC5qcycsIFsnZ29vZy5kb20uZm9ybXNUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uZm9ybXMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9mdWxsc2NyZWVuLmpzJywgWydnb29nLmRvbS5mdWxsc2NyZWVuJywgJ2dvb2cuZG9tLmZ1bGxzY3JlZW4uRXZlbnRUeXBlJ10sIFsnZ29vZy5kb20nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9mdWxsc2NyZWVuX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLmZ1bGxzY3JlZW5fdGVzdCddLCBbJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5mdWxsc2NyZWVuJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vaHRtbGVsZW1lbnQuanMnLCBbJ2dvb2cuZG9tLkh0bWxFbGVtZW50J10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2lmcmFtZS5qcycsIFsnZ29vZy5kb20uaWZyYW1lJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVN0eWxlJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9pZnJhbWVfdGVzdC5qcycsIFsnZ29vZy5kb20uaWZyYW1lVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmlmcmFtZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2lucHV0dHlwZS5qcycsIFsnZ29vZy5kb20uSW5wdXRUeXBlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2lucHV0dHlwZV90ZXN0LmpzJywgWydnb29nLmRvbS5JbnB1dFR5cGVUZXN0J10sIFsnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vaXRlci5qcycsIFsnZ29vZy5kb20uaXRlci5BbmNlc3Rvckl0ZXJhdG9yJywgJ2dvb2cuZG9tLml0ZXIuQ2hpbGRJdGVyYXRvcicsICdnb29nLmRvbS5pdGVyLlNpYmxpbmdJdGVyYXRvciddLCBbJ2dvb2cuaXRlci5JdGVyYXRvcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL2l0ZXJfdGVzdC5qcycsIFsnZ29vZy5kb20uaXRlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5pdGVyLkFuY2VzdG9ySXRlcmF0b3InLCAnZ29vZy5kb20uaXRlci5DaGlsZEl0ZXJhdG9yJywgJ2dvb2cuZG9tLml0ZXIuU2libGluZ0l0ZXJhdG9yJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9tdWx0aXJhbmdlLmpzJywgWydnb29nLmRvbS5NdWx0aVJhbmdlJywgJ2dvb2cuZG9tLk11bHRpUmFuZ2VJdGVyYXRvciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uQWJzdHJhY3RNdWx0aVJhbmdlJywgJ2dvb2cuZG9tLkFic3RyYWN0UmFuZ2UnLCAnZ29vZy5kb20uUmFuZ2VJdGVyYXRvcicsICdnb29nLmRvbS5SYW5nZVR5cGUnLCAnZ29vZy5kb20uU2F2ZWRSYW5nZScsICdnb29nLmRvbS5UZXh0UmFuZ2UnLCAnZ29vZy5pdGVyJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJywgJ2dvb2cubG9nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vbXVsdGlyYW5nZV90ZXN0LmpzJywgWydnb29nLmRvbS5NdWx0aVJhbmdlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk11bHRpUmFuZ2UnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5pdGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vbm9kZWl0ZXJhdG9yLmpzJywgWydnb29nLmRvbS5Ob2RlSXRlcmF0b3InXSwgWydnb29nLmRvbS5UYWdJdGVyYXRvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL25vZGVpdGVyYXRvcl90ZXN0LmpzJywgWydnb29nLmRvbS5Ob2RlSXRlcmF0b3JUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZUl0ZXJhdG9yJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9ub2Rlb2Zmc2V0LmpzJywgWydnb29nLmRvbS5Ob2RlT2Zmc2V0J10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuZG9tLlRhZ05hbWUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9ub2Rlb2Zmc2V0X3Rlc3QuanMnLCBbJ2dvb2cuZG9tLk5vZGVPZmZzZXRUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZU9mZnNldCcsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vbm9kZXR5cGUuanMnLCBbJ2dvb2cuZG9tLk5vZGVUeXBlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vYWJzdHJhY3RwYXR0ZXJuLmpzJywgWydnb29nLmRvbS5wYXR0ZXJuLkFic3RyYWN0UGF0dGVybiddLCBbJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9hbGxjaGlsZHJlbi5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5BbGxDaGlsZHJlbiddLCBbJ2dvb2cuZG9tLnBhdHRlcm4uQWJzdHJhY3RQYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9jYWxsYmFjay9jYWxsYmFjay5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5jYWxsYmFjayddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuaXRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vY2FsbGJhY2svY291bnRlci5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5jYWxsYmFjay5Db3VudGVyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vY2FsbGJhY2svdGVzdC5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5jYWxsYmFjay5UZXN0J10sIFsnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9wYXR0ZXJuL2NoaWxkbWF0Y2hlcy5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5DaGlsZE1hdGNoZXMnXSwgWydnb29nLmRvbS5wYXR0ZXJuLkFsbENoaWxkcmVuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9lbmR0YWcuanMnLCBbJ2dvb2cuZG9tLnBhdHRlcm4uRW5kVGFnJ10sIFsnZ29vZy5kb20uVGFnV2Fsa1R5cGUnLCAnZ29vZy5kb20ucGF0dGVybi5UYWcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9wYXR0ZXJuL2Z1bGx0YWcuanMnLCBbJ2dvb2cuZG9tLnBhdHRlcm4uRnVsbFRhZyddLCBbJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4uU3RhcnRUYWcnLCAnZ29vZy5kb20ucGF0dGVybi5UYWcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9wYXR0ZXJuL21hdGNoZXIuanMnLCBbJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hlciddLCBbJ2dvb2cuZG9tLlRhZ0l0ZXJhdG9yJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJywgJ2dvb2cuaXRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vbWF0Y2hlcl90ZXN0LmpzJywgWydnb29nLmRvbS5wYXR0ZXJuLm1hdGNoZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5wYXR0ZXJuLkVuZFRhZycsICdnb29nLmRvbS5wYXR0ZXJuLkZ1bGxUYWcnLCAnZ29vZy5kb20ucGF0dGVybi5NYXRjaGVyJywgJ2dvb2cuZG9tLnBhdHRlcm4uUmVwZWF0JywgJ2dvb2cuZG9tLnBhdHRlcm4uU2VxdWVuY2UnLCAnZ29vZy5kb20ucGF0dGVybi5TdGFydFRhZycsICdnb29nLmRvbS5wYXR0ZXJuLmNhbGxiYWNrLkNvdW50ZXInLCAnZ29vZy5kb20ucGF0dGVybi5jYWxsYmFjay5UZXN0JywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9ub2RldHlwZS5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5Ob2RlVHlwZSddLCBbJ2dvb2cuZG9tLnBhdHRlcm4uQWJzdHJhY3RQYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9wYXR0ZXJuLmpzJywgWydnb29nLmRvbS5wYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vcGF0dGVybl90ZXN0LmpzJywgWydnb29nLmRvbS5wYXR0ZXJuVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4uQWxsQ2hpbGRyZW4nLCAnZ29vZy5kb20ucGF0dGVybi5DaGlsZE1hdGNoZXMnLCAnZ29vZy5kb20ucGF0dGVybi5FbmRUYWcnLCAnZ29vZy5kb20ucGF0dGVybi5GdWxsVGFnJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4uTm9kZVR5cGUnLCAnZ29vZy5kb20ucGF0dGVybi5SZXBlYXQnLCAnZ29vZy5kb20ucGF0dGVybi5TZXF1ZW5jZScsICdnb29nLmRvbS5wYXR0ZXJuLlN0YXJ0VGFnJywgJ2dvb2cuZG9tLnBhdHRlcm4uVGV4dCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3BhdHRlcm4vcmVwZWF0LmpzJywgWydnb29nLmRvbS5wYXR0ZXJuLlJlcGVhdCddLCBbJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4uQWJzdHJhY3RQYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi9zZXF1ZW5jZS5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5TZXF1ZW5jZSddLCBbJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLnBhdHRlcm4nLCAnZ29vZy5kb20ucGF0dGVybi5BYnN0cmFjdFBhdHRlcm4nLCAnZ29vZy5kb20ucGF0dGVybi5NYXRjaFR5cGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9wYXR0ZXJuL3N0YXJ0dGFnLmpzJywgWydnb29nLmRvbS5wYXR0ZXJuLlN0YXJ0VGFnJ10sIFsnZ29vZy5kb20uVGFnV2Fsa1R5cGUnLCAnZ29vZy5kb20ucGF0dGVybi5UYWcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9wYXR0ZXJuL3RhZy5qcycsIFsnZ29vZy5kb20ucGF0dGVybi5UYWcnXSwgWydnb29nLmRvbS5wYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uQWJzdHJhY3RQYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcGF0dGVybi90ZXh0LmpzJywgWydnb29nLmRvbS5wYXR0ZXJuLlRleHQnXSwgWydnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5wYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uQWJzdHJhY3RQYXR0ZXJuJywgJ2dvb2cuZG9tLnBhdHRlcm4uTWF0Y2hUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vcmFuZ2UuanMnLCBbJ2dvb2cuZG9tLlJhbmdlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uQWJzdHJhY3RSYW5nZScsICdnb29nLmRvbS5Ccm93c2VyRmVhdHVyZScsICdnb29nLmRvbS5Db250cm9sUmFuZ2UnLCAnZ29vZy5kb20uTXVsdGlSYW5nZScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UZXh0UmFuZ2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9yYW5nZV90ZXN0LmpzJywgWydnb29nLmRvbS5SYW5nZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5SYW5nZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5UZXh0UmFuZ2UnLCAnZ29vZy5kb20uYnJvd3NlcnJhbmdlJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9yYW5nZWVuZHBvaW50LmpzJywgWydnb29nLmRvbS5SYW5nZUVuZHBvaW50J10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3NhZmUuanMnLCBbJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5kb20uc2FmZS5JbnNlcnRBZGphY2VudEh0bWxQb3NpdGlvbiddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5hc3NlcnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVNjcmlwdCcsICdnb29nLmh0bWwuU2FmZVN0eWxlJywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3RyaW5nLmludGVybmFsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vc2FmZV90ZXN0LmpzJywgWydnb29nLmRvbS5zYWZlVGVzdCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5kb20uc2FmZS5JbnNlcnRBZGphY2VudEh0bWxQb3NpdGlvbicsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTY3JpcHQnLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudGVzdGluZycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3NhdmVkY2FyZXRyYW5nZS5qcycsIFsnZ29vZy5kb20uU2F2ZWRDYXJldFJhbmdlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5TYXZlZFJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS9zYXZlZGNhcmV0cmFuZ2VfdGVzdC5qcycsIFsnZ29vZy5kb20uU2F2ZWRDYXJldFJhbmdlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlNhdmVkQ2FyZXRSYW5nZScsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vc2F2ZWRyYW5nZS5qcycsIFsnZ29vZy5kb20uU2F2ZWRSYW5nZSddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmxvZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3NhdmVkcmFuZ2VfdGVzdC5qcycsIFsnZ29vZy5kb20uU2F2ZWRSYW5nZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3NlbGVjdGlvbi5qcycsIFsnZ29vZy5kb20uc2VsZWN0aW9uJ10sIFsnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vc2VsZWN0aW9uX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLnNlbGVjdGlvblRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zZWxlY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS90YWdpdGVyYXRvci5qcycsIFsnZ29vZy5kb20uVGFnSXRlcmF0b3InLCAnZ29vZy5kb20uVGFnV2Fsa1R5cGUnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLml0ZXIuSXRlcmF0b3InLCAnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS90YWdpdGVyYXRvcl90ZXN0LmpzJywgWydnb29nLmRvbS5UYWdJdGVyYXRvclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdJdGVyYXRvcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuaXRlcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdGFnbmFtZS5qcycsIFsnZ29vZy5kb20uVGFnTmFtZSddLCBbJ2dvb2cuZG9tLkh0bWxFbGVtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdGFnbmFtZV90ZXN0LmpzJywgWydnb29nLmRvbS5UYWdOYW1lVGVzdCddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS90YWdzLmpzJywgWydnb29nLmRvbS50YWdzJ10sIFsnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS90YWdzX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLnRhZ3NUZXN0J10sIFsnZ29vZy5kb20udGFncycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3RleHRhc3NlcnQuanMnLCBbJ2dvb2cuZG9tLnRleHRBc3NlcnQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3RleHRhc3NlcnRfdGVzdC5qcycsIFsnZ29vZy5kb20udGV4dGFzc2VydF90ZXN0J10sIFsnZ29vZy5kb20udGV4dEFzc2VydCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3RleHRyYW5nZS5qcycsIFsnZ29vZy5kb20uVGV4dFJhbmdlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5BYnN0cmFjdFJhbmdlJywgJ2dvb2cuZG9tLlJhbmdlVHlwZScsICdnb29nLmRvbS5TYXZlZFJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uVGV4dFJhbmdlSXRlcmF0b3InLCAnZ29vZy5kb20uYnJvd3NlcnJhbmdlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdGV4dHJhbmdlX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLlRleHRSYW5nZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Db250cm9sUmFuZ2UnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGV4dFJhbmdlJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3RleHRyYW5nZWl0ZXJhdG9yLmpzJywgWydnb29nLmRvbS5UZXh0UmFuZ2VJdGVyYXRvciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uUmFuZ2VJdGVyYXRvcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdGV4dHJhbmdlaXRlcmF0b3JfdGVzdC5qcycsIFsnZ29vZy5kb20uVGV4dFJhbmdlSXRlcmF0b3JUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5UZXh0UmFuZ2VJdGVyYXRvcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdXJpLmpzJywgWydnb29nLmRvbS51cmknXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cuc3RyaW5nLkNvbnN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3VyaV90ZXN0LmpzJywgWydnb29nLmRvbS51cmlUZXN0J10sIFsnZ29vZy5kb20udXJpJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS92ZW5kb3IuanMnLCBbJ2dvb2cuZG9tLnZlbmRvciddLCBbJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdkb20vdmVuZG9yX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLnZlbmRvclRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tLnZlbmRvcicsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLk1vY2tVc2VyQWdlbnQnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudFRlc3RVdGlsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3ZpZXdwb3J0c2l6ZW1vbml0b3IuanMnLCBbJ2dvb2cuZG9tLlZpZXdwb3J0U2l6ZU1vbml0b3InXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5tYXRoLlNpemUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS92aWV3cG9ydHNpemVtb25pdG9yX3Rlc3QuanMnLCBbJ2dvb2cuZG9tLlZpZXdwb3J0U2l6ZU1vbml0b3JUZXN0J10sIFsnZ29vZy5kb20uVmlld3BvcnRTaXplTW9uaXRvcicsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZG9tL3htbC5qcycsIFsnZ29vZy5kb20ueG1sJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwubGVnYWN5Y29udmVyc2lvbnMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2RvbS94bWxfdGVzdC5qcycsIFsnZ29vZy5kb20ueG1sVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20ueG1sJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvYnJvd3NlcmZlYXR1cmUuanMnLCBbJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJ10sIFsnZ29vZy5lZGl0b3IuZGVmaW5lcycsICdnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL2Jyb3dzZXJmZWF0dXJlX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9jbGlja3RvZWRpdHdyYXBwZXIuanMnLCBbJ2dvb2cuZWRpdG9yLkNsaWNrVG9FZGl0V3JhcHBlciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9jbGlja3RvZWRpdHdyYXBwZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IuQ2xpY2tUb0VkaXRXcmFwcGVyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQ2xpY2tUb0VkaXRXcmFwcGVyJywgJ2dvb2cuZWRpdG9yLlNlYW1sZXNzRmllbGQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvY29tbWFuZC5qcycsIFsnZ29vZy5lZGl0b3IuQ29tbWFuZCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9jb250ZW50ZWRpdGFibGVmaWVsZC5qcycsIFsnZ29vZy5lZGl0b3IuQ29udGVudEVkaXRhYmxlRmllbGQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5sb2cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9jb250ZW50ZWRpdGFibGVmaWVsZF90ZXN0LmpzJywgWydnb29nLmVkaXRvci5Db250ZW50RWRpdGFibGVGaWVsZFRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmVkaXRvci5Db250ZW50RWRpdGFibGVGaWVsZCcsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9kZWZpbmVzLmpzJywgWydnb29nLmVkaXRvci5kZWZpbmVzJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL2ZpZWxkLmpzJywgWydnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5GaWVsZC5FdmVudFR5cGUnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuYXN5bmMuRGVsYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLlBsdWdpbkltcGwnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQuRmllbGRGb3JtYXRJbmZvJywgJ2dvb2cuZWRpdG9yLmljb250ZW50LkZpZWxkU3R5bGVJbmZvJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cubG9nJywgJ2dvb2cubG9nLkxldmVsJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvZmllbGRfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IuZmllbGRfdGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cudGVzdGluZy5Mb29zZU1vY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9mb2N1cy5qcycsIFsnZ29vZy5lZGl0b3IuZm9jdXMnXSwgWydnb29nLmRvbS5zZWxlY3Rpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9mb2N1c190ZXN0LmpzJywgWydnb29nLmVkaXRvci5mb2N1c1Rlc3QnXSwgWydnb29nLmRvbS5zZWxlY3Rpb24nLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuZm9jdXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9pY29udGVudC5qcycsIFsnZ29vZy5lZGl0b3IuaWNvbnRlbnQnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQuRmllbGRGb3JtYXRJbmZvJywgJ2dvb2cuZWRpdG9yLmljb250ZW50LkZpZWxkU3R5bGVJbmZvJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL2ljb250ZW50X3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLmljb250ZW50VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQuRmllbGRGb3JtYXRJbmZvJywgJ2dvb2cuZWRpdG9yLmljb250ZW50LkZpZWxkU3R5bGVJbmZvJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvbGluay5qcycsIFsnZ29vZy5lZGl0b3IuTGluayddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnVyaS51dGlscycsICdnb29nLnVyaS51dGlscy5Db21wb25lbnRJbmRleCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL2xpbmtfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IuTGlua1Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkxpbmsnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9ub2RlLmpzJywgWydnb29nLmVkaXRvci5ub2RlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5pdGVyLkNoaWxkSXRlcmF0b3InLCAnZ29vZy5kb20uaXRlci5TaWJsaW5nSXRlcmF0b3InLCAnZ29vZy5pdGVyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9ub2RlX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLm5vZGVUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2luLmpzJywgWydnb29nLmVkaXRvci5QbHVnaW4nXSwgWydnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5QbHVnaW5JbXBsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2luX2ltcGwuanMnLCBbJ2dvb2cuZWRpdG9yLlBsdWdpbkltcGwnXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmxvZycsICdnb29nLm9iamVjdCcsICdnb29nLnJlZmxlY3QnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5fdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IuUGx1Z2luVGVzdCddLCBbJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvYWJzdHJhY3RidWJibGVwbHVnaW4uanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3RCdWJibGVQbHVnaW4nXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5zdHlsZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLmFjdGlvbkV2ZW50V3JhcHBlcicsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnN0cmluZy5Vbmljb2RlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuZWRpdG9yLkJ1YmJsZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvYWJzdHJhY3RidWJibGVwbHVnaW5fdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdEJ1YmJsZVBsdWdpblRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3RCdWJibGVQbHVnaW4nLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuRmllbGRNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVkaXRvci5CdWJibGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9hYnN0cmFjdGRpYWxvZ3BsdWdpbi5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdERpYWxvZ1BsdWdpbicsICdnb29nLmVkaXRvci5wbHVnaW5zLkFic3RyYWN0RGlhbG9nUGx1Z2luLkV2ZW50VHlwZSddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5yYW5nZScsICdnb29nLmV2ZW50cycsICdnb29nLnVpLmVkaXRvci5BYnN0cmFjdERpYWxvZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvYWJzdHJhY3RkaWFsb2dwbHVnaW5fdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdERpYWxvZ1BsdWdpblRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5TYXZlZFJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdERpYWxvZ1BsdWdpbicsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuRmllbGRNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMuQXJndW1lbnRNYXRjaGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5lZGl0b3IuQWJzdHJhY3REaWFsb2cnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9hYnN0cmFjdHRhYmhhbmRsZXIuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3RUYWJIYW5kbGVyJ10sIFsnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9hYnN0cmFjdHRhYmhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdFRhYkhhbmRsZXJUZXN0J10sIFsnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5BYnN0cmFjdFRhYkhhbmRsZXInLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cudGVzdGluZy5TdHJpY3RNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuRmllbGRNb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9iYXNpY3RleHRmb3JtYXR0ZXIuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQmFzaWNUZXh0Rm9ybWF0dGVyJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQmFzaWNUZXh0Rm9ybWF0dGVyLkNPTU1BTkQnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuQ29tbWFuZCcsICdnb29nLmVkaXRvci5MaW5rJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZWRpdG9yLnN0eWxlJywgJ2dvb2cuaXRlcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLmxvZycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cmluZy5Vbmljb2RlJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5lZGl0b3IubWVzc2FnZXMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2Jhc2ljdGV4dGZvcm1hdHRlcl90ZXN0LmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLkJhc2ljVGV4dEZvcm1hdHRlclRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuQ29tbWFuZCcsICdnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5QbHVnaW4nLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5CYXNpY1RleHRGb3JtYXR0ZXInLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLkxvb3NlTW9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9ibG9ja3F1b3RlLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLkJsb2NrcXVvdGUnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubG9nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9ibG9ja3F1b3RlX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQmxvY2txdW90ZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQmxvY2txdW90ZScsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2Vtb3RpY29ucy5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5FbW90aWNvbnMnXSwgWydnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5yYW5nZScsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnVpLmVtb2ppLkVtb2ppJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9lbW90aWNvbnNfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5FbW90aWNvbnNUZXN0J10sIFsnZ29vZy5VcmknLCAnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuRW1vdGljb25zJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5lbW9qaS5FbW9qaScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2VudGVyaGFuZGxlci5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5FbnRlckhhbmRsZXInXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlT2Zmc2V0JywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5CbG9ja3F1b3RlJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZWRpdG9yLnN0eWxlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9lbnRlcmhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5FbnRlckhhbmRsZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5QbHVnaW4nLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5CbG9ja3F1b3RlJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuRW50ZXJIYW5kbGVyJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy5FeHBlY3RlZEZhaWx1cmVzJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvZmlyc3RzdHJvbmcuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuRmlyc3RTdHJvbmcnXSwgWydnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdJdGVyYXRvcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5pMThuLmJpZGknLCAnZ29vZy5pMThuLnVDaGFyJywgJ2dvb2cuaXRlcicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvZmlyc3RzdHJvbmdfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5GaXJzdFN0cm9uZ1Rlc3QnXSwgWydnb29nLmRvbS5SYW5nZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuRmlyc3RTdHJvbmcnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvaGVhZGVyZm9ybWF0dGVyLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLkhlYWRlckZvcm1hdHRlciddLCBbJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9oZWFkZXJmb3JtYXR0ZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5IZWFkZXJGb3JtYXR0ZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5lZGl0b3IuQ29tbWFuZCcsICdnb29nLmVkaXRvci5wbHVnaW5zLkJhc2ljVGV4dEZvcm1hdHRlcicsICdnb29nLmVkaXRvci5wbHVnaW5zLkhlYWRlckZvcm1hdHRlcicsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy50ZXN0aW5nLkxvb3NlTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2xpbmtidWJibGUuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuTGlua0J1YmJsZScsICdnb29nLmVkaXRvci5wbHVnaW5zLkxpbmtCdWJibGUuQWN0aW9uJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuTGluaycsICdnb29nLmVkaXRvci5wbHVnaW5zLkFic3RyYWN0QnViYmxlUGx1Z2luJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5lZGl0b3IubWVzc2FnZXMnLCAnZ29vZy51cmkudXRpbHMnLCAnZ29vZy53aW5kb3cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2xpbmtidWJibGVfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5MaW5rQnViYmxlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQ29tbWFuZCcsICdnb29nLmVkaXRvci5MaW5rJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuTGlua0J1YmJsZScsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkZ1bmN0aW9uTW9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvbGlua2RpYWxvZ3BsdWdpbi5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5MaW5rRGlhbG9nUGx1Z2luJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3REaWFsb2dQbHVnaW4nLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cudWkuZWRpdG9yLkFic3RyYWN0RGlhbG9nJywgJ2dvb2cudWkuZWRpdG9yLkxpbmtEaWFsb2cnLCAnZ29vZy51cmkudXRpbHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2xpbmtkaWFsb2dwbHVnaW5fdGVzdC5qcycsIFsnZ29vZy51aS5lZGl0b3IucGx1Z2lucy5MaW5rRGlhbG9nVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IuTGluaycsICdnb29nLmVkaXRvci5wbHVnaW5zLkxpbmtEaWFsb2dQbHVnaW4nLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuRmllbGRNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcuZWRpdG9yLmRvbScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVkaXRvci5BYnN0cmFjdERpYWxvZycsICdnb29nLnVpLmVkaXRvci5MaW5rRGlhbG9nJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvbGlua3Nob3J0Y3V0cGx1Z2luLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLkxpbmtTaG9ydGN1dFBsdWdpbiddLCBbJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9saW5rc2hvcnRjdXRwbHVnaW5fdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5MaW5rU2hvcnRjdXRQbHVnaW5UZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5wbHVnaW5zLkJhc2ljVGV4dEZvcm1hdHRlcicsICdnb29nLmVkaXRvci5wbHVnaW5zLkxpbmtCdWJibGUnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5MaW5rU2hvcnRjdXRQbHVnaW4nLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL2xpc3R0YWJoYW5kbGVyLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLkxpc3RUYWJIYW5kbGVyJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3RUYWJIYW5kbGVyJywgJ2dvb2cuaXRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvbGlzdHRhYmhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5MaXN0VGFiSGFuZGxlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuTGlzdFRhYkhhbmRsZXInLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cudGVzdGluZy5TdHJpY3RNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuRmllbGRNb2NrJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvbG9yZW1pcHN1bS5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5Mb3JlbUlwc3VtJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZWRpdG9yLkNvbW1hbmQnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IuUGx1Z2luJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy9sb3JlbWlwc3VtX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuTG9yZW1JcHN1bVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuTG9yZW1JcHN1bScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvcmVtb3ZlZm9ybWF0dGluZy5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5SZW1vdmVGb3JtYXR0aW5nJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5QbHVnaW4nLCAnZ29vZy5lZGl0b3Iubm9kZScsICdnb29nLmVkaXRvci5yYW5nZScsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvcmVtb3ZlZm9ybWF0dGluZ190ZXN0LmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlJlbW92ZUZvcm1hdHRpbmdUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5wbHVnaW5zLlJlbW92ZUZvcm1hdHRpbmcnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvc3BhY2VzdGFiaGFuZGxlci5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5TcGFjZXNUYWJIYW5kbGVyJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5wbHVnaW5zLkFic3RyYWN0VGFiSGFuZGxlcicsICdnb29nLmVkaXRvci5yYW5nZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvc3BhY2VzdGFiaGFuZGxlcl90ZXN0LmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlNwYWNlc1RhYkhhbmRsZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5TcGFjZXNUYWJIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLkZpZWxkTW9jaycsICdnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL3RhYmxlZWRpdG9yLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlRhYmxlRWRpdG9yJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5UYWJsZScsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy90YWJsZWVkaXRvcl90ZXN0LmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlRhYmxlRWRpdG9yVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5UYWJsZUVkaXRvcicsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5GaWVsZE1vY2snLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5UZXN0SGVscGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy90YWdvbmVudGVyaGFuZGxlci5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5UYWdPbkVudGVySGFuZGxlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQ29tbWFuZCcsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuRW50ZXJIYW5kbGVyJywgJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZWRpdG9yLnN0eWxlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvdGFnb25lbnRlcmhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5UYWdPbkVudGVySGFuZGxlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5wbHVnaW5zLlRhZ09uRW50ZXJIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLnN0cmluZy5Vbmljb2RlJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5UZXN0SGVscGVyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL3VuZG9yZWRvLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlVuZG9SZWRvJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZU9mZnNldCcsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuZWRpdG9yLkZpZWxkJywgJ2dvb2cuZWRpdG9yLlBsdWdpbicsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuVW5kb1JlZG9NYW5hZ2VyJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuVW5kb1JlZG9TdGF0ZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL3VuZG9yZWRvX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLnBsdWdpbnMuVW5kb1JlZG9UZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5icm93c2VycmFuZ2UnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5Mb3JlbUlwc3VtJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuVW5kb1JlZG8nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci9wbHVnaW5zL3VuZG9yZWRvbWFuYWdlci5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb01hbmFnZXInLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb01hbmFnZXIuRXZlbnRUeXBlJ10sIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb1N0YXRlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy91bmRvcmVkb21hbmFnZXJfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb01hbmFnZXJUZXN0J10sIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb01hbmFnZXInLCAnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb1N0YXRlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5TdHJpY3RNb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcGx1Z2lucy91bmRvcmVkb3N0YXRlLmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlVuZG9SZWRvU3RhdGUnXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3BsdWdpbnMvdW5kb3JlZG9zdGF0ZV90ZXN0LmpzJywgWydnb29nLmVkaXRvci5wbHVnaW5zLlVuZG9SZWRvU3RhdGVUZXN0J10sIFsnZ29vZy5lZGl0b3IucGx1Z2lucy5VbmRvUmVkb1N0YXRlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvcmFuZ2UuanMnLCBbJ2dvb2cuZWRpdG9yLnJhbmdlJywgJ2dvb2cuZWRpdG9yLnJhbmdlLlBvaW50J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5SYW5nZUVuZHBvaW50JywgJ2dvb2cuZG9tLlNhdmVkQ2FyZXRSYW5nZScsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnN0eWxlJywgJ2dvb2cuaXRlcicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3JhbmdlX3Rlc3QuanMnLCBbJ2dvb2cuZWRpdG9yLnJhbmdlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IucmFuZ2UnLCAnZ29vZy5lZGl0b3IucmFuZ2UuUG9pbnQnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3NlYW1sZXNzZmllbGQuanMnLCBbJ2dvb2cuZWRpdG9yLlNlYW1sZXNzRmllbGQnXSwgWydnb29nLmNzc29tLmlmcmFtZS5zdHlsZScsICdnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuRmllbGQnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQnLCAnZ29vZy5lZGl0b3IuaWNvbnRlbnQuRmllbGRGb3JtYXRJbmZvJywgJ2dvb2cuZWRpdG9yLmljb250ZW50LkZpZWxkU3R5bGVJbmZvJywgJ2dvb2cuZWRpdG9yLm5vZGUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmxvZycsICdnb29nLnN0eWxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3Ivc2VhbWxlc3NmaWVsZF90ZXN0LmpzJywgWydnb29nLmVkaXRvci5zZWFtbGVzc2ZpZWxkX3Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Eb21IZWxwZXInLCAnZ29vZy5kb20uUmFuZ2UnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmVkaXRvci5TZWFtbGVzc0ZpZWxkJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tSYW5nZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZWRpdG9yL3N0eWxlLmpzJywgWydnb29nLmVkaXRvci5zdHlsZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm9iamVjdCcsICdnb29nLnN0eWxlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3Ivc3R5bGVfdGVzdC5qcycsIFsnZ29vZy5lZGl0b3Iuc3R5bGVUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5zdHlsZScsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkxvb3NlTW9jaycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdlZGl0b3IvdGFibGUuanMnLCBbJ2dvb2cuZWRpdG9yLlRhYmxlJywgJ2dvb2cuZWRpdG9yLlRhYmxlQ2VsbCcsICdnb29nLmVkaXRvci5UYWJsZVJvdyddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5Eb21IZWxwZXInLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmxvZycsICdnb29nLnN0cmluZy5Vbmljb2RlJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2VkaXRvci90YWJsZV90ZXN0LmpzJywgWydnb29nLmVkaXRvci5UYWJsZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZWRpdG9yLlRhYmxlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvYWN0aW9uZXZlbnR3cmFwcGVyLmpzJywgWydnb29nLmV2ZW50cy5hY3Rpb25FdmVudFdyYXBwZXInXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuRXZlbnRXcmFwcGVyJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvYWN0aW9uZXZlbnR3cmFwcGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLmFjdGlvbkV2ZW50V3JhcHBlclRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5hY3Rpb25FdmVudFdyYXBwZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2FjdGlvbmhhbmRsZXIuanMnLCBbJ2dvb2cuZXZlbnRzLkFjdGlvbkV2ZW50JywgJ2dvb2cuZXZlbnRzLkFjdGlvbkhhbmRsZXInLCAnZ29vZy5ldmVudHMuQWN0aW9uSGFuZGxlci5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuQmVmb3JlQWN0aW9uRXZlbnQnXSwgWydnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvYWN0aW9uaGFuZGxlcl90ZXN0LmpzJywgWydnb29nLmV2ZW50cy5BY3Rpb25IYW5kbGVyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkFjdGlvbkhhbmRsZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2Jyb3dzZXJldmVudC5qcycsIFsnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudC5Nb3VzZUJ1dHRvbicsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQuUG9pbnRlclR5cGUnXSwgWydnb29nLmRlYnVnJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnJlZmxlY3QnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9icm93c2VyZXZlbnRfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50VGVzdCddLCBbJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5Ccm93c2VyRmVhdHVyZScsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2Jyb3dzZXJmZWF0dXJlLmpzJywgWydnb29nLmV2ZW50cy5Ccm93c2VyRmVhdHVyZSddLCBbJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnQuanMnLCBbJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50TGlrZSddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmV2ZW50cy5FdmVudElkJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnRfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuRXZlbnRUZXN0J10sIFsnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRJZCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2V2ZW50aGFuZGxlci5qcycsIFsnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnRoYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlclRlc3QnXSwgWydnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnRpZC5qcycsIFsnZ29vZy5ldmVudHMuRXZlbnRJZCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9ldmVudHMuanMnLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkNhcHR1cmVTaW11bGF0aW9uTW9kZScsICdnb29nLmV2ZW50cy5LZXknLCAnZ29vZy5ldmVudHMuTGlzdGVuYWJsZVR5cGUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5lbnRyeVBvaW50UmVnaXN0cnknLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZXZlbnRzLkxpc3RlbmFibGUnLCAnZ29vZy5ldmVudHMuTGlzdGVuZXJNYXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9ldmVudHNfdGVzdC5qcycsIFsnZ29vZy5ldmVudHNUZXN0J10sIFsnZ29vZy5hc3NlcnRzLkFzc2VydGlvbkVycm9yJywgJ2dvb2cuZGVidWcuRW50cnlQb2ludE1vbml0b3InLCAnZ29vZy5kZWJ1Zy5FcnJvckhhbmRsZXInLCAnZ29vZy5kZWJ1Zy5lbnRyeVBvaW50UmVnaXN0cnknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRmVhdHVyZScsICdnb29nLmV2ZW50cy5DYXB0dXJlU2ltdWxhdGlvbk1vZGUnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLkxpc3RlbmVyJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2V2ZW50dGFyZ2V0LmpzJywgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuTGlzdGVuYWJsZScsICdnb29nLmV2ZW50cy5MaXN0ZW5lck1hcCcsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2V2ZW50dGFyZ2V0X3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0VGVzdCddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkxpc3RlbmFibGUnLCAnZ29vZy5ldmVudHMuZXZlbnRUYXJnZXRUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9ldmVudHRhcmdldF92aWFfZ29vZ2V2ZW50c190ZXN0LmpzJywgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldEdvb2dFdmVudHNUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuZXZlbnRUYXJnZXRUZXN0ZXInLCAnZ29vZy50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnR0YXJnZXRfdmlhX3czY2ludGVyZmFjZV90ZXN0LmpzJywgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldFczQ1Rlc3QnXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5ldmVudFRhcmdldFRlc3RlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2V2ZW50dGFyZ2V0dGVzdGVyLmpzJywgWydnb29nLmV2ZW50cy5ldmVudFRhcmdldFRlc3RlciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuTGlzdGVuYWJsZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnR0eXBlLmpzJywgWydnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuTW91c2VBc01vdXNlRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLk1vdXNlRXZlbnRzJywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJBc01vdXNlRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJBc1RvdWNoRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJGYWxsYmFja0V2ZW50VHlwZScsICdnb29nLmV2ZW50cy5Qb2ludGVyVG91Y2hGYWxsYmFja0V2ZW50VHlwZSddLCBbJ2dvb2cuZXZlbnRzLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnR0eXBlX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZVRlc3QnXSwgWydnb29nLmV2ZW50cy5Ccm93c2VyRmVhdHVyZScsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuUG9pbnRlckZhbGxiYWNrRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJUb3VjaEZhbGxiYWNrRXZlbnRUeXBlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZXZlbnR3cmFwcGVyLmpzJywgWydnb29nLmV2ZW50cy5FdmVudFdyYXBwZXInXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZmlsZWRyb3BoYW5kbGVyLmpzJywgWydnb29nLmV2ZW50cy5GaWxlRHJvcEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRmlsZURyb3BIYW5kbGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5sb2cnLCAnZ29vZy5sb2cuTGV2ZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9maWxlZHJvcGhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuRmlsZURyb3BIYW5kbGVyVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuRmlsZURyb3BIYW5kbGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvZm9jdXNoYW5kbGVyLmpzJywgWydnb29nLmV2ZW50cy5Gb2N1c0hhbmRsZXInLCAnZ29vZy5ldmVudHMuRm9jdXNIYW5kbGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2ltZWhhbmRsZXIuanMnLCBbJ2dvb2cuZXZlbnRzLkltZUhhbmRsZXInLCAnZ29vZy5ldmVudHMuSW1lSGFuZGxlci5FdmVudCcsICdnb29nLmV2ZW50cy5JbWVIYW5kbGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9pbWVoYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLkltZUhhbmRsZXJUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5JbWVIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2lucHV0aGFuZGxlci5qcycsIFsnZ29vZy5ldmVudHMuSW5wdXRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLklucHV0SGFuZGxlci5FdmVudFR5cGUnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2lucHV0aGFuZGxlcl90ZXN0LmpzJywgWydnb29nLmV2ZW50cy5JbnB1dEhhbmRsZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5JbnB1dEhhbmRsZXInLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50JywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2tleWNvZGVzLmpzJywgWydnb29nLmV2ZW50cy5LZXlDb2RlcyddLCBbJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMva2V5Y29kZXNfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuS2V5Q29kZXNUZXN0J10sIFsnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMva2V5aGFuZGxlci5qcycsIFsnZ29vZy5ldmVudHMuS2V5RXZlbnQnLCAnZ29vZy5ldmVudHMuS2V5SGFuZGxlcicsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9rZXloYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLktleUV2ZW50VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9rZXluYW1lcy5qcycsIFsnZ29vZy5ldmVudHMuS2V5TmFtZXMnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMva2V5cy5qcycsIFsnZ29vZy5ldmVudHMuS2V5cyddLCBbXSwgeydsYW5nJzogJ2VzNSd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvbGlzdGVuYWJsZS5qcycsIFsnZ29vZy5ldmVudHMuTGlzdGVuYWJsZScsICdnb29nLmV2ZW50cy5MaXN0ZW5hYmxlS2V5J10sIFsnZ29vZy5ldmVudHMuRXZlbnRJZCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2xpc3RlbmFibGVfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuTGlzdGVuYWJsZVRlc3QnXSwgWydnb29nLmV2ZW50cy5MaXN0ZW5hYmxlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvbGlzdGVuZXIuanMnLCBbJ2dvb2cuZXZlbnRzLkxpc3RlbmVyJ10sIFsnZ29vZy5ldmVudHMuTGlzdGVuYWJsZUtleSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL2xpc3RlbmVybWFwLmpzJywgWydnb29nLmV2ZW50cy5MaXN0ZW5lck1hcCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5ldmVudHMuTGlzdGVuZXInLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9saXN0ZW5lcm1hcF90ZXN0LmpzJywgWydnb29nLmV2ZW50cy5MaXN0ZW5lck1hcFRlc3QnXSwgWydnb29nLmRpc3Bvc2UnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRJZCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5MaXN0ZW5lck1hcCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL21vdXNld2hlZWxoYW5kbGVyLmpzJywgWydnb29nLmV2ZW50cy5Nb3VzZVdoZWVsRXZlbnQnLCAnZ29vZy5ldmVudHMuTW91c2VXaGVlbEhhbmRsZXInLCAnZ29vZy5ldmVudHMuTW91c2VXaGVlbEhhbmRsZXIuRXZlbnRUeXBlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cubWF0aCcsICdnb29nLnN0eWxlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvbW91c2V3aGVlbGhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy5ldmVudHMuTW91c2VXaGVlbEhhbmRsZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLk1vdXNlV2hlZWxFdmVudCcsICdnb29nLmV2ZW50cy5Nb3VzZVdoZWVsSGFuZGxlcicsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvb25saW5laGFuZGxlci5qcycsIFsnZ29vZy5ldmVudHMuT25saW5lSGFuZGxlcicsICdnb29nLmV2ZW50cy5PbmxpbmVIYW5kbGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5ldmVudHMuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm5ldC5OZXR3b3JrU3RhdHVzTW9uaXRvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZXZlbnRzL29ubGluZWxpc3RlbmVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLk9ubGluZUhhbmRsZXJUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLk9ubGluZUhhbmRsZXInLCAnZ29vZy5uZXQuTmV0d29ya1N0YXR1c01vbml0b3InLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy9wYXN0ZWhhbmRsZXIuanMnLCBbJ2dvb2cuZXZlbnRzLlBhc3RlSGFuZGxlcicsICdnb29nLmV2ZW50cy5QYXN0ZUhhbmRsZXIuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLlBhc3RlSGFuZGxlci5TdGF0ZSddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hc3luYy5Db25kaXRpb25hbERlbGF5JywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubG9nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvcGFzdGVoYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLlBhc3RlSGFuZGxlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLlBhc3RlSGFuZGxlcicsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvd2hlZWxldmVudC5qcycsIFsnZ29vZy5ldmVudHMuV2hlZWxFdmVudCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2V2ZW50cy93aGVlbGhhbmRsZXIuanMnLCBbJ2dvb2cuZXZlbnRzLldoZWVsSGFuZGxlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLldoZWVsRXZlbnQnLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QuaXNWZXJzaW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdldmVudHMvd2hlZWxoYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cuZXZlbnRzLldoZWVsSGFuZGxlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuV2hlZWxFdmVudCcsICdnb29nLmV2ZW50cy5XaGVlbEhhbmRsZXInLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZm9ybWF0L2VtYWlsYWRkcmVzcy5qcycsIFsnZ29vZy5mb3JtYXQuRW1haWxBZGRyZXNzJ10sIFsnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Zvcm1hdC9lbWFpbGFkZHJlc3NfdGVzdC5qcycsIFsnZ29vZy5mb3JtYXQuRW1haWxBZGRyZXNzVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5mb3JtYXQuRW1haWxBZGRyZXNzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmb3JtYXQvZm9ybWF0LmpzJywgWydnb29nLmZvcm1hdCddLCBbJ2dvb2cuaTE4bi5HcmFwaGVtZUJyZWFrJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmb3JtYXQvZm9ybWF0X3Rlc3QuanMnLCBbJ2dvb2cuZm9ybWF0VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5mb3JtYXQnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Zvcm1hdC9odG1scHJldHR5cHJpbnRlci5qcycsIFsnZ29vZy5mb3JtYXQuSHRtbFByZXR0eVByaW50ZXInLCAnZ29vZy5mb3JtYXQuSHRtbFByZXR0eVByaW50ZXIuQnVmZmVyJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5TdHJpbmdCdWZmZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Zvcm1hdC9odG1scHJldHR5cHJpbnRlcl90ZXN0LmpzJywgWydnb29nLmZvcm1hdC5IdG1sUHJldHR5UHJpbnRlclRlc3QnXSwgWydnb29nLmZvcm1hdC5IdG1sUHJldHR5UHJpbnRlcicsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmb3JtYXQvaW50ZXJuYXRpb25hbGl6ZWRlbWFpbGFkZHJlc3MuanMnLCBbJ2dvb2cuZm9ybWF0LkludGVybmF0aW9uYWxpemVkRW1haWxBZGRyZXNzJ10sIFsnZ29vZy5mb3JtYXQuRW1haWxBZGRyZXNzJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmb3JtYXQvaW50ZXJuYXRpb25hbGl6ZWRlbWFpbGFkZHJlc3NfdGVzdC5qcycsIFsnZ29vZy5mb3JtYXQuSW50ZXJuYXRpb25hbGl6ZWRFbWFpbEFkZHJlc3NUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmZvcm1hdC5JbnRlcm5hdGlvbmFsaXplZEVtYWlsQWRkcmVzcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZm9ybWF0L2pzb25wcmV0dHlwcmludGVyLmpzJywgWydnb29nLmZvcm1hdC5Kc29uUHJldHR5UHJpbnRlcicsICdnb29nLmZvcm1hdC5Kc29uUHJldHR5UHJpbnRlci5TYWZlSHRtbERlbGltaXRlcnMnLCAnZ29vZy5mb3JtYXQuSnNvblByZXR0eVByaW50ZXIuVGV4dERlbGltaXRlcnMnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5qc29uJywgJ2dvb2cuanNvbi5TZXJpYWxpemVyJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLmZvcm1hdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZm9ybWF0L2pzb25wcmV0dHlwcmludGVyX3Rlc3QuanMnLCBbJ2dvb2cuZm9ybWF0Lkpzb25QcmV0dHlQcmludGVyVGVzdCddLCBbJ2dvb2cuZm9ybWF0Lkpzb25QcmV0dHlQcmludGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmcy9lbnRyeS5qcycsIFsnZ29vZy5mcy5EaXJlY3RvcnlFbnRyeScsICdnb29nLmZzLkRpcmVjdG9yeUVudHJ5LkJlaGF2aW9yJywgJ2dvb2cuZnMuRW50cnknLCAnZ29vZy5mcy5GaWxlRW50cnknXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmcy9lbnRyeWltcGwuanMnLCBbJ2dvb2cuZnMuRGlyZWN0b3J5RW50cnlJbXBsJywgJ2dvb2cuZnMuRW50cnlJbXBsJywgJ2dvb2cuZnMuRmlsZUVudHJ5SW1wbCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmZzLkRpcmVjdG9yeUVudHJ5JywgJ2dvb2cuZnMuRW50cnknLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVFbnRyeScsICdnb29nLmZzLkZpbGVXcml0ZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2ZzL2Vycm9yLmpzJywgWydnb29nLmZzLkRPTUVycm9yTGlrZScsICdnb29nLmZzLkVycm9yJywgJ2dvb2cuZnMuRXJyb3IuRXJyb3JDb2RlJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2ZzL2ZpbGVyZWFkZXIuanMnLCBbJ2dvb2cuZnMuRmlsZVJlYWRlcicsICdnb29nLmZzLkZpbGVSZWFkZXIuRXZlbnRUeXBlJywgJ2dvb2cuZnMuRmlsZVJlYWRlci5SZWFkeVN0YXRlJ10sIFsnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmZzLkVycm9yJywgJ2dvb2cuZnMuUHJvZ3Jlc3NFdmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvZmlsZXNhdmVyLmpzJywgWydnb29nLmZzLkZpbGVTYXZlcicsICdnb29nLmZzLkZpbGVTYXZlci5FdmVudFR5cGUnLCAnZ29vZy5mcy5GaWxlU2F2ZXIuUmVhZHlTdGF0ZSddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZnMuRXJyb3InLCAnZ29vZy5mcy5Qcm9ncmVzc0V2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmcy9maWxlc3lzdGVtLmpzJywgWydnb29nLmZzLkZpbGVTeXN0ZW0nXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmcy9maWxlc3lzdGVtaW1wbC5qcycsIFsnZ29vZy5mcy5GaWxlU3lzdGVtSW1wbCddLCBbJ2dvb2cuZnMuRGlyZWN0b3J5RW50cnlJbXBsJywgJ2dvb2cuZnMuRmlsZVN5c3RlbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvZmlsZXdyaXRlci5qcycsIFsnZ29vZy5mcy5GaWxlV3JpdGVyJ10sIFsnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVTYXZlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvZnMuanMnLCBbJ2dvb2cuZnMnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVSZWFkZXInLCAnZ29vZy5mcy5GaWxlU3lzdGVtSW1wbCcsICdnb29nLmZzLnVybCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvZnNfdGVzdC5qcycsIFsnZ29vZy5mc1Rlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnMnLCAnZ29vZy5mcy5EaXJlY3RvcnlFbnRyeScsICdnb29nLmZzLkVycm9yJywgJ2dvb2cuZnMuRmlsZVJlYWRlcicsICdnb29nLmZzLkZpbGVTYXZlcicsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvcHJvZ3Jlc3NldmVudC5qcycsIFsnZ29vZy5mcy5Qcm9ncmVzc0V2ZW50J10sIFsnZ29vZy5ldmVudHMuRXZlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2ZzL3VybC5qcycsIFsnZ29vZy5mcy51cmwnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZnMvdXJsX3Rlc3QuanMnLCBbJ2dvb2cudXJsVGVzdCddLCBbJ2dvb2cuZnMudXJsJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmdW5jdGlvbnMvZnVuY3Rpb25zLmpzJywgWydnb29nLmZ1bmN0aW9ucyddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmdW5jdGlvbnMvZnVuY3Rpb25zX3Rlc3QuanMnLCBbJ2dvb2cuZnVuY3Rpb25zVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2Fic3RyYWN0ZHJhZ2Ryb3AuanMnLCBbJ2dvb2cuZnguQWJzdHJhY3REcmFnRHJvcCcsICdnb29nLmZ4LkFic3RyYWN0RHJhZ0Ryb3AuRXZlbnRUeXBlJywgJ2dvb2cuZnguRHJhZ0Ryb3BFdmVudCcsICdnb29nLmZ4LkRyYWdEcm9wSXRlbSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZnguRHJhZ2dlcicsICdnb29nLm1hdGguQm94JywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2Fic3RyYWN0ZHJhZ2Ryb3BfdGVzdC5qcycsIFsnZ29vZy5meC5BYnN0cmFjdERyYWdEcm9wVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5meC5BYnN0cmFjdERyYWdEcm9wJywgJ2dvb2cuZnguRHJhZ0Ryb3BJdGVtJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2FuaW0vYW5pbS5qcycsIFsnZ29vZy5meC5hbmltJywgJ2dvb2cuZnguYW5pbS5BbmltYXRlZCddLCBbJ2dvb2cuYXN5bmMuQW5pbWF0aW9uRGVsYXknLCAnZ29vZy5hc3luYy5EZWxheScsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvYW5pbS9hbmltX3Rlc3QuanMnLCBbJ2dvb2cuZnguYW5pbVRlc3QnXSwgWydnb29nLmFzeW5jLkFuaW1hdGlvbkRlbGF5JywgJ2dvb2cuYXN5bmMuRGVsYXknLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5meC5hbmltJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC9hbmltYXRpb24uanMnLCBbJ2dvb2cuZnguQW5pbWF0aW9uJywgJ2dvb2cuZnguQW5pbWF0aW9uLkV2ZW50VHlwZScsICdnb29nLmZ4LkFuaW1hdGlvbi5TdGF0ZScsICdnb29nLmZ4LkFuaW1hdGlvbkV2ZW50J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5meC5UcmFuc2l0aW9uJywgJ2dvb2cuZnguVHJhbnNpdGlvbkJhc2UnLCAnZ29vZy5meC5hbmltJywgJ2dvb2cuZnguYW5pbS5BbmltYXRlZCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvYW5pbWF0aW9uX3Rlc3QuanMnLCBbJ2dvb2cuZnguQW5pbWF0aW9uVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnguQW5pbWF0aW9uJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2FuaW1hdGlvbnF1ZXVlLmpzJywgWydnb29nLmZ4LkFuaW1hdGlvblBhcmFsbGVsUXVldWUnLCAnZ29vZy5meC5BbmltYXRpb25RdWV1ZScsICdnb29nLmZ4LkFuaW1hdGlvblNlcmlhbFF1ZXVlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5meC5UcmFuc2l0aW9uJywgJ2dvb2cuZnguVHJhbnNpdGlvbkJhc2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2FuaW1hdGlvbnF1ZXVlX3Rlc3QuanMnLCBbJ2dvb2cuZnguQW5pbWF0aW9uUXVldWVUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5meC5BbmltYXRpb25QYXJhbGxlbFF1ZXVlJywgJ2dvb2cuZnguQW5pbWF0aW9uU2VyaWFsUXVldWUnLCAnZ29vZy5meC5UcmFuc2l0aW9uJywgJ2dvb2cuZnguYW5pbScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC9jc3MzL2Z4LmpzJywgWydnb29nLmZ4LmNzczMnXSwgWydnb29nLmZ4LmNzczMuVHJhbnNpdGlvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvY3NzMy90cmFuc2l0aW9uLmpzJywgWydnb29nLmZ4LmNzczMuVHJhbnNpdGlvbiddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZnguVHJhbnNpdGlvbkJhc2UnLCAnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLnRyYW5zaXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2NzczMvdHJhbnNpdGlvbl90ZXN0LmpzJywgWydnb29nLmZ4LmNzczMuVHJhbnNpdGlvblRlc3QnXSwgWydnb29nLmRpc3Bvc2UnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmZ4LlRyYW5zaXRpb24nLCAnZ29vZy5meC5jc3MzLlRyYW5zaXRpb24nLCAnZ29vZy5zdHlsZS50cmFuc2l0aW9uJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC9jc3NzcHJpdGVhbmltYXRpb24uanMnLCBbJ2dvb2cuZnguQ3NzU3ByaXRlQW5pbWF0aW9uJ10sIFsnZ29vZy5meC5BbmltYXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2Nzc3Nwcml0ZWFuaW1hdGlvbl90ZXN0LmpzJywgWydnb29nLmZ4LkNzc1Nwcml0ZUFuaW1hdGlvblRlc3QnXSwgWydnb29nLmZ4LkNzc1Nwcml0ZUFuaW1hdGlvbicsICdnb29nLm1hdGguQm94JywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2RvbS5qcycsIFsnZ29vZy5meC5kb20nLCAnZ29vZy5meC5kb20uQmdDb2xvclRyYW5zZm9ybScsICdnb29nLmZ4LmRvbS5Db2xvclRyYW5zZm9ybScsICdnb29nLmZ4LmRvbS5GYWRlJywgJ2dvb2cuZnguZG9tLkZhZGVJbicsICdnb29nLmZ4LmRvbS5GYWRlSW5BbmRTaG93JywgJ2dvb2cuZnguZG9tLkZhZGVPdXQnLCAnZ29vZy5meC5kb20uRmFkZU91dEFuZEhpZGUnLCAnZ29vZy5meC5kb20uUHJlZGVmaW5lZEVmZmVjdCcsICdnb29nLmZ4LmRvbS5SZXNpemUnLCAnZ29vZy5meC5kb20uUmVzaXplSGVpZ2h0JywgJ2dvb2cuZnguZG9tLlJlc2l6ZVdpZHRoJywgJ2dvb2cuZnguZG9tLlNjcm9sbCcsICdnb29nLmZ4LmRvbS5TbGlkZScsICdnb29nLmZ4LmRvbS5TbGlkZUZyb20nLCAnZ29vZy5meC5kb20uU3dpcGUnXSwgWydnb29nLmNvbG9yJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnguQW5pbWF0aW9uJywgJ2dvb2cuZnguVHJhbnNpdGlvbicsICdnb29nLnN0eWxlJywgJ2dvb2cuc3R5bGUuYmlkaSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZHJhZ2Ryb3AuanMnLCBbJ2dvb2cuZnguRHJhZ0Ryb3AnXSwgWydnb29nLmZ4LkFic3RyYWN0RHJhZ0Ryb3AnLCAnZ29vZy5meC5EcmFnRHJvcEl0ZW0nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2RyYWdkcm9wZ3JvdXAuanMnLCBbJ2dvb2cuZnguRHJhZ0Ryb3BHcm91cCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZnguQWJzdHJhY3REcmFnRHJvcCcsICdnb29nLmZ4LkRyYWdEcm9wSXRlbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZHJhZ2Ryb3Bncm91cF90ZXN0LmpzJywgWydnb29nLmZ4LkRyYWdEcm9wR3JvdXBUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5meC5EcmFnRHJvcEdyb3VwJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC9kcmFnZ2VyLmpzJywgWydnb29nLmZ4LkRyYWdFdmVudCcsICdnb29nLmZ4LkRyYWdnZXInLCAnZ29vZy5meC5EcmFnZ2VyLkV2ZW50VHlwZSddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLm1hdGguUmVjdCcsICdnb29nLnN0eWxlJywgJ2dvb2cuc3R5bGUuYmlkaScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZHJhZ2dlcl90ZXN0LmpzJywgWydnb29nLmZ4LkRyYWdnZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZnguRHJhZ2dlcicsICdnb29nLm1hdGguUmVjdCcsICdnb29nLnN0eWxlLmJpZGknLCAnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZHJhZ2xpc3Rncm91cC5qcycsIFsnZ29vZy5meC5EcmFnTGlzdERpcmVjdGlvbicsICdnb29nLmZ4LkRyYWdMaXN0R3JvdXAnLCAnZ29vZy5meC5EcmFnTGlzdEdyb3VwLkV2ZW50VHlwZScsICdnb29nLmZ4LkRyYWdMaXN0R3JvdXBFdmVudCcsICdnb29nLmZ4LkRyYWdMaXN0UGVybWlzc2lvbiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRJZCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5meC5EcmFnZ2VyJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2RyYWdsaXN0Z3JvdXBfdGVzdC5qcycsIFsnZ29vZy5meC5EcmFnTGlzdEdyb3VwVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmZ4LkRyYWdFdmVudCcsICdnb29nLmZ4LkRyYWdMaXN0RGlyZWN0aW9uJywgJ2dvb2cuZnguRHJhZ0xpc3RHcm91cCcsICdnb29nLmZ4LkRyYWdMaXN0UGVybWlzc2lvbicsICdnb29nLmZ4LkRyYWdnZXInLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC9kcmFnc2Nyb2xsc3VwcG9ydC5qcycsIFsnZ29vZy5meC5EcmFnU2Nyb2xsU3VwcG9ydCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZHJhZ3Njcm9sbHN1cHBvcnRfdGVzdC5qcycsIFsnZ29vZy5meC5EcmFnU2Nyb2xsU3VwcG9ydFRlc3QnXSwgWydnb29nLmZ4LkRyYWdTY3JvbGxTdXBwb3J0JywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cubWF0aC5SZWN0JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZWFzaW5nLmpzJywgWydnb29nLmZ4LmVhc2luZyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L2Vhc2luZ190ZXN0LmpzJywgWydnb29nLmZ4LmVhc2luZ1Rlc3QnXSwgWydnb29nLmZ4LmVhc2luZycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZnguanMnLCBbJ2dvb2cuZngnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5meC5BbmltYXRpb24uRXZlbnRUeXBlJywgJ2dvb2cuZnguQW5pbWF0aW9uLlN0YXRlJywgJ2dvb2cuZnguQW5pbWF0aW9uRXZlbnQnLCAnZ29vZy5meC5UcmFuc2l0aW9uLkV2ZW50VHlwZScsICdnb29nLmZ4LmVhc2luZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZngvZnhfdGVzdC5qcycsIFsnZ29vZy5meFRlc3QnXSwgWydnb29nLmZ4LkFuaW1hdGlvbicsICdnb29nLm9iamVjdCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdmeC90cmFuc2l0aW9uLmpzJywgWydnb29nLmZ4LlRyYW5zaXRpb24nLCAnZ29vZy5meC5UcmFuc2l0aW9uLkV2ZW50VHlwZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2Z4L3RyYW5zaXRpb25iYXNlLmpzJywgWydnb29nLmZ4LlRyYW5zaXRpb25CYXNlJywgJ2dvb2cuZnguVHJhbnNpdGlvbkJhc2UuU3RhdGUnXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmZ4LlRyYW5zaXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dvb2cuanMnLCBbXSwgW10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9hYnN0cmFjdGdyYXBoaWNzLmpzJywgWydnb29nLmdyYXBoaWNzLkFic3RyYWN0R3JhcGhpY3MnXSwgWydnb29nLmRvbScsICdnb29nLmdyYXBoaWNzLkFmZmluZVRyYW5zZm9ybScsICdnb29nLmdyYXBoaWNzLkVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5FbGxpcHNlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkZpbGwnLCAnZ29vZy5ncmFwaGljcy5Gb250JywgJ2dvb2cuZ3JhcGhpY3MuR3JvdXBFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuUGF0aCcsICdnb29nLmdyYXBoaWNzLlBhdGhFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuUmVjdEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdHJva2UnLCAnZ29vZy5ncmFwaGljcy5TdHJva2VBbmRGaWxsRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlRleHRFbGVtZW50JywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2FmZmluZXRyYW5zZm9ybS5qcycsIFsnZ29vZy5ncmFwaGljcy5BZmZpbmVUcmFuc2Zvcm0nXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvYWZmaW5ldHJhbnNmb3JtX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuQWZmaW5lVHJhbnNmb3JtVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5ncmFwaGljcycsICdnb29nLmdyYXBoaWNzLkFmZmluZVRyYW5zZm9ybScsICdnb29nLm1hdGgnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2NhbnZhc2VsZW1lbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuQ2FudmFzRWxsaXBzZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNHcm91cEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNJbWFnZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNQYXRoRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkNhbnZhc1JlY3RFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuQ2FudmFzVGV4dEVsZW1lbnQnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmdyYXBoaWNzLkVsbGlwc2VFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuRm9udCcsICdnb29nLmdyYXBoaWNzLkdyb3VwRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkltYWdlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlBhdGgnLCAnZ29vZy5ncmFwaGljcy5QYXRoRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlJlY3RFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuVGV4dEVsZW1lbnQnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLm1hdGgnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2NhbnZhc2dyYXBoaWNzLmpzJywgWydnb29nLmdyYXBoaWNzLkNhbnZhc0dyYXBoaWNzJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ncmFwaGljcy5BYnN0cmFjdEdyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MuQ2FudmFzRWxsaXBzZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNHcm91cEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNJbWFnZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5DYW52YXNQYXRoRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkNhbnZhc1JlY3RFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuQ2FudmFzVGV4dEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5Gb250JywgJ2dvb2cuZ3JhcGhpY3MuU29saWRGaWxsJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2NhbnZhc2dyYXBoaWNzX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuQ2FudmFzR3JhcGhpY3NUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ncmFwaGljcy5DYW52YXNHcmFwaGljcycsICdnb29nLmdyYXBoaWNzLlNvbGlkRmlsbCcsICdnb29nLmdyYXBoaWNzLlN0cm9rZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZWxlbWVudC5qcycsIFsnZ29vZy5ncmFwaGljcy5FbGVtZW50J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkxpc3RlbmFibGUnLCAnZ29vZy5ncmFwaGljcy5BZmZpbmVUcmFuc2Zvcm0nLCAnZ29vZy5tYXRoJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9lbGxpcHNlZWxlbWVudC5qcycsIFsnZ29vZy5ncmFwaGljcy5FbGxpcHNlRWxlbWVudCddLCBbJ2dvb2cuZ3JhcGhpY3MuU3Ryb2tlQW5kRmlsbEVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2V4dC9jb29yZGluYXRlcy5qcycsIFsnZ29vZy5ncmFwaGljcy5leHQuY29vcmRpbmF0ZXMnXSwgWydnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L2Nvb3JkaW5hdGVzX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LmNvb3JkaW5hdGVzVGVzdCddLCBbJ2dvb2cuZ3JhcGhpY3MnLCAnZ29vZy5ncmFwaGljcy5leHQuY29vcmRpbmF0ZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2V4dC9lbGVtZW50LmpzJywgWydnb29nLmdyYXBoaWNzLmV4dC5FbGVtZW50J10sIFsnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5ncmFwaGljcy5leHQuY29vcmRpbmF0ZXMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2V4dC9lbGVtZW50X3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LkVsZW1lbnRUZXN0J10sIFsnZ29vZy5ncmFwaGljcycsICdnb29nLmdyYXBoaWNzLmV4dCcsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L2VsbGlwc2UuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LkVsbGlwc2UnXSwgWydnb29nLmdyYXBoaWNzLmV4dC5TdHJva2VBbmRGaWxsRWxlbWVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L2V4dC5qcycsIFsnZ29vZy5ncmFwaGljcy5leHQnXSwgWydnb29nLmdyYXBoaWNzLmV4dC5FbGxpcHNlJywgJ2dvb2cuZ3JhcGhpY3MuZXh0LkdyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MuZXh0Lkdyb3VwJywgJ2dvb2cuZ3JhcGhpY3MuZXh0LkltYWdlJywgJ2dvb2cuZ3JhcGhpY3MuZXh0LlJlY3RhbmdsZScsICdnb29nLmdyYXBoaWNzLmV4dC5TaGFwZScsICdnb29nLmdyYXBoaWNzLmV4dC5jb29yZGluYXRlcyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L2dyYXBoaWNzLmpzJywgWydnb29nLmdyYXBoaWNzLmV4dC5HcmFwaGljcyddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmdyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MuZXh0Lkdyb3VwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9leHQvZ3JvdXAuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0Lkdyb3VwJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmdyYXBoaWNzLmV4dC5FbGVtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9leHQvaW1hZ2UuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LkltYWdlJ10sIFsnZ29vZy5ncmFwaGljcy5leHQuRWxlbWVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L3BhdGguanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LlBhdGgnXSwgWydnb29nLmdyYXBoaWNzLkFmZmluZVRyYW5zZm9ybScsICdnb29nLmdyYXBoaWNzLlBhdGgnLCAnZ29vZy5tYXRoLlJlY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2V4dC9wYXRoX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LlBhdGhUZXN0J10sIFsnZ29vZy5ncmFwaGljcycsICdnb29nLmdyYXBoaWNzLmV4dC5QYXRoJywgJ2dvb2cubWF0aC5SZWN0JywgJ2dvb2cudGVzdGluZy5ncmFwaGljcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L3JlY3RhbmdsZS5qcycsIFsnZ29vZy5ncmFwaGljcy5leHQuUmVjdGFuZ2xlJ10sIFsnZ29vZy5ncmFwaGljcy5leHQuU3Ryb2tlQW5kRmlsbEVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2V4dC9zaGFwZS5qcycsIFsnZ29vZy5ncmFwaGljcy5leHQuU2hhcGUnXSwgWydnb29nLmdyYXBoaWNzLmV4dC5TdHJva2VBbmRGaWxsRWxlbWVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvZXh0L3N0cm9rZWFuZGZpbGxlbGVtZW50LmpzJywgWydnb29nLmdyYXBoaWNzLmV4dC5TdHJva2VBbmRGaWxsRWxlbWVudCddLCBbJ2dvb2cuZ3JhcGhpY3MuZXh0LkVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2ZpbGwuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuRmlsbCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2ZvbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuRm9udCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2dyYXBoaWNzLmpzJywgWydnb29nLmdyYXBoaWNzJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5ncmFwaGljcy5DYW52YXNHcmFwaGljcycsICdnb29nLmdyYXBoaWNzLlN2Z0dyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MuVm1sR3JhcGhpY3MnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2dyb3VwZWxlbWVudC5qcycsIFsnZ29vZy5ncmFwaGljcy5Hcm91cEVsZW1lbnQnXSwgWydnb29nLmdyYXBoaWNzLkVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2ltYWdlZWxlbWVudC5qcycsIFsnZ29vZy5ncmFwaGljcy5JbWFnZUVsZW1lbnQnXSwgWydnb29nLmdyYXBoaWNzLkVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL2xpbmVhcmdyYWRpZW50LmpzJywgWydnb29nLmdyYXBoaWNzLkxpbmVhckdyYWRpZW50J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZ3JhcGhpY3MuRmlsbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvcGF0aC5qcycsIFsnZ29vZy5ncmFwaGljcy5QYXRoJywgJ2dvb2cuZ3JhcGhpY3MuUGF0aC5TZWdtZW50J10sIFsnZ29vZy5hcnJheScsICdnb29nLmdyYXBoaWNzLkFmZmluZVRyYW5zZm9ybScsICdnb29nLm1hdGgnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL3BhdGhfdGVzdC5qcycsIFsnZ29vZy5ncmFwaGljcy5QYXRoVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5ncmFwaGljcy5BZmZpbmVUcmFuc2Zvcm0nLCAnZ29vZy5ncmFwaGljcy5QYXRoJywgJ2dvb2cudGVzdGluZy5ncmFwaGljcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvcGF0aGVsZW1lbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuUGF0aEVsZW1lbnQnXSwgWydnb29nLmdyYXBoaWNzLlN0cm9rZUFuZEZpbGxFbGVtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9wYXRocy5qcycsIFsnZ29vZy5ncmFwaGljcy5wYXRocyddLCBbJ2dvb2cuZ3JhcGhpY3MuUGF0aCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvcGF0aHNfdGVzdC5qcycsIFsnZ29vZy5ncmFwaGljcy5wYXRoc1Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmdyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MucGF0aHMnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL3JlY3RlbGVtZW50LmpzJywgWydnb29nLmdyYXBoaWNzLlJlY3RFbGVtZW50J10sIFsnZ29vZy5ncmFwaGljcy5TdHJva2VBbmRGaWxsRWxlbWVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3Mvc29saWRmaWxsLmpzJywgWydnb29nLmdyYXBoaWNzLlNvbGlkRmlsbCddLCBbJ2dvb2cuZ3JhcGhpY3MuRmlsbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3Mvc29saWRmaWxsX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuU29saWRGaWxsVGVzdCddLCBbJ2dvb2cuZ3JhcGhpY3MuU29saWRGaWxsJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9zdHJva2UuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuU3Ryb2tlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3Mvc3Ryb2tlYW5kZmlsbGVsZW1lbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuU3Ryb2tlQW5kRmlsbEVsZW1lbnQnXSwgWydnb29nLmdyYXBoaWNzLkVsZW1lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL3N2Z2VsZW1lbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuU3ZnRWxsaXBzZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdHcm91cEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdJbWFnZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdQYXRoRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlN2Z1JlY3RFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuU3ZnVGV4dEVsZW1lbnQnXSwgWydnb29nLmRvbScsICdnb29nLmdyYXBoaWNzLkVsbGlwc2VFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuR3JvdXBFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuSW1hZ2VFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuUGF0aEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5SZWN0RWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlRleHRFbGVtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy9zdmdncmFwaGljcy5qcycsIFsnZ29vZy5ncmFwaGljcy5TdmdHcmFwaGljcyddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmdyYXBoaWNzLkFic3RyYWN0R3JhcGhpY3MnLCAnZ29vZy5ncmFwaGljcy5Gb250JywgJ2dvb2cuZ3JhcGhpY3MuTGluZWFyR3JhZGllbnQnLCAnZ29vZy5ncmFwaGljcy5QYXRoJywgJ2dvb2cuZ3JhcGhpY3MuU29saWRGaWxsJywgJ2dvb2cuZ3JhcGhpY3MuU3Ryb2tlJywgJ2dvb2cuZ3JhcGhpY3MuU3ZnRWxsaXBzZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdHcm91cEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdJbWFnZUVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5TdmdQYXRoRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlN2Z1JlY3RFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuU3ZnVGV4dEVsZW1lbnQnLCAnZ29vZy5tYXRoJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2dyYXBoaWNzL3N2Z2dyYXBoaWNzX3Rlc3QuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuU3ZnR3JhcGhpY3NUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ncmFwaGljcy5BZmZpbmVUcmFuc2Zvcm0nLCAnZ29vZy5ncmFwaGljcy5Tb2xpZEZpbGwnLCAnZ29vZy5ncmFwaGljcy5TdmdHcmFwaGljcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3MvdGV4dGVsZW1lbnQuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuVGV4dEVsZW1lbnQnXSwgWydnb29nLmdyYXBoaWNzLlN0cm9rZUFuZEZpbGxFbGVtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdncmFwaGljcy92bWxlbGVtZW50LmpzJywgWydnb29nLmdyYXBoaWNzLlZtbEVsbGlwc2VFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuVm1sR3JvdXBFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuVm1sSW1hZ2VFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuVm1sUGF0aEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5WbWxSZWN0RWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlZtbFRleHRFbGVtZW50J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ncmFwaGljcy5FbGxpcHNlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkdyb3VwRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLkltYWdlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlBhdGhFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuUmVjdEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5UZXh0RWxlbWVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnZ3JhcGhpY3Mvdm1sZ3JhcGhpY3MuanMnLCBbJ2dvb2cuZ3JhcGhpY3MuVm1sR3JhcGhpY3MnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZ3JhcGhpY3MuQWJzdHJhY3RHcmFwaGljcycsICdnb29nLmdyYXBoaWNzLkZvbnQnLCAnZ29vZy5ncmFwaGljcy5MaW5lYXJHcmFkaWVudCcsICdnb29nLmdyYXBoaWNzLlBhdGgnLCAnZ29vZy5ncmFwaGljcy5Tb2xpZEZpbGwnLCAnZ29vZy5ncmFwaGljcy5WbWxFbGxpcHNlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlZtbEdyb3VwRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlZtbEltYWdlRWxlbWVudCcsICdnb29nLmdyYXBoaWNzLlZtbFBhdGhFbGVtZW50JywgJ2dvb2cuZ3JhcGhpY3MuVm1sUmVjdEVsZW1lbnQnLCAnZ29vZy5ncmFwaGljcy5WbWxUZXh0RWxlbWVudCcsICdnb29nLmh0bWwudW5jaGVja2VkY29udmVyc2lvbnMnLCAnZ29vZy5tYXRoJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cucmVmbGVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnN0eWxlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdoaXN0b3J5L2V2ZW50LmpzJywgWydnb29nLmhpc3RvcnkuRXZlbnQnXSwgWydnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmhpc3RvcnkuRXZlbnRUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdoaXN0b3J5L2V2ZW50dHlwZS5qcycsIFsnZ29vZy5oaXN0b3J5LkV2ZW50VHlwZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2hpc3RvcnkvaGlzdG9yeS5qcycsIFsnZ29vZy5IaXN0b3J5JywgJ2dvb2cuSGlzdG9yeS5FdmVudCcsICdnb29nLkhpc3RvcnkuRXZlbnRUeXBlJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmhpc3RvcnkuRXZlbnQnLCAnZ29vZy5oaXN0b3J5LkV2ZW50VHlwZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwudW5jaGVja2VkY29udmVyc2lvbnMnLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC5kZXZpY2UnLCAnZ29vZy5tZW1vaXplJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdoaXN0b3J5L2hpc3RvcnlfdGVzdC5qcycsIFsnZ29vZy5IaXN0b3J5VGVzdCddLCBbJ2dvb2cuSGlzdG9yeScsICdnb29nLmRpc3Bvc2UnLCAnZ29vZy5kb20nLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaGlzdG9yeS9odG1sNWhpc3RvcnkuanMnLCBbJ2dvb2cuaGlzdG9yeS5IdG1sNUhpc3RvcnknLCAnZ29vZy5oaXN0b3J5Lkh0bWw1SGlzdG9yeS5Ub2tlblRyYW5zZm9ybWVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmhpc3RvcnkuRXZlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2hpc3RvcnkvaHRtbDVoaXN0b3J5X3Rlc3QuanMnLCBbJ2dvb2cuaGlzdG9yeS5IdG1sNUhpc3RvcnlUZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5oaXN0b3J5LkV2ZW50VHlwZScsICdnb29nLmhpc3RvcnkuSHRtbDVIaXN0b3J5JywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9jc3NzcGVjaWZpY2l0eS5qcycsIFsnZ29vZy5odG1sLkNzc1NwZWNpZmljaXR5J10sIFsnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvY3Nzc3BlY2lmaWNpdHlfdGVzdC5qcycsIFsnZ29vZy5odG1sLkNzc1NwZWNpZmljaXR5VGVzdCddLCBbJ2dvb2cuaHRtbC5Dc3NTcGVjaWZpY2l0eScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL2ZsYXNoLmpzJywgWydnb29nLmh0bWwuZmxhc2gnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL2ZsYXNoX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5mbGFzaFRlc3QnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwuZmxhc2gnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvbGVnYWN5Y29udmVyc2lvbnMuanMnLCBbJ2dvb2cuaHRtbC5sZWdhY3ljb252ZXJzaW9ucyddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVNjcmlwdCcsICdnb29nLmh0bWwuU2FmZVN0eWxlJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGVTaGVldCcsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL2xlZ2FjeWNvbnZlcnNpb25zX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5sZWdhY3ljb252ZXJzaW9uc1Rlc3QnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTY3JpcHQnLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLmh0bWwuU2FmZVN0eWxlU2hlZXQnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwubGVnYWN5Y29udmVyc2lvbnMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZWh0bWwuanMnLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20udGFncycsICdnb29nLmh0bWwuU2FmZVNjcmlwdCcsICdnb29nLmh0bWwuU2FmZVN0eWxlJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGVTaGVldCcsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJywgJ2dvb2cuaHRtbC50cnVzdGVkdHlwZXMnLCAnZ29vZy5pMThuLmJpZGkuRGlyJywgJ2dvb2cuaTE4bi5iaWRpLkRpcmVjdGlvbmFsU3RyaW5nJywgJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnN0cmluZy5UeXBlZFN0cmluZycsICdnb29nLnN0cmluZy5pbnRlcm5hbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYWZlaHRtbF90ZXN0LmpzJywgWydnb29nLmh0bWwuc2FmZUh0bWxUZXN0J10sIFsnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC5TYWZlU2NyaXB0JywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy5odG1sLnRydXN0ZWR0eXBlcycsICdnb29nLmkxOG4uYmlkaS5EaXInLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC5icm93c2VyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3NhZmVodG1sZm9ybWF0dGVyLmpzJywgWydnb29nLmh0bWwuU2FmZUh0bWxGb3JtYXR0ZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20udGFncycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZWh0bWxmb3JtYXR0ZXJfdGVzdC5qcycsIFsnZ29vZy5odG1sLnNhZmVIdG1sRm9ybWF0dGVyVGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZUh0bWxGb3JtYXR0ZXInLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZXNjcmlwdC5qcycsIFsnZ29vZy5odG1sLlNhZmVTY3JpcHQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLnRydXN0ZWR0eXBlcycsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnN0cmluZy5UeXBlZFN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYWZlc2NyaXB0X3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5zYWZlU2NyaXB0VGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlU2NyaXB0JywgJ2dvb2cuaHRtbC50cnVzdGVkdHlwZXMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZXN0eWxlLmpzJywgWydnb29nLmh0bWwuU2FmZVN0eWxlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy5zdHJpbmcuVHlwZWRTdHJpbmcnLCAnZ29vZy5zdHJpbmcuaW50ZXJuYWwnXSwgeydsYW5nJzogJ2VzNSd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3NhZmVzdHlsZV90ZXN0LmpzJywgWydnb29nLmh0bWwuc2FmZVN0eWxlVGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZXN0eWxlc2hlZXQuanMnLCBbJ2dvb2cuaHRtbC5TYWZlU3R5bGVTaGVldCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy5zdHJpbmcuVHlwZWRTdHJpbmcnLCAnZ29vZy5zdHJpbmcuaW50ZXJuYWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FmZXN0eWxlc2hlZXRfdGVzdC5qcycsIFsnZ29vZy5odG1sLnNhZmVTdHlsZVNoZWV0VGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3NhZmV1cmwuanMnLCBbJ2dvb2cuaHRtbC5TYWZlVXJsJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZnMudXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5pMThuLmJpZGkuRGlyJywgJ2dvb2cuaTE4bi5iaWRpLkRpcmVjdGlvbmFsU3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3RyaW5nLlR5cGVkU3RyaW5nJywgJ2dvb2cuc3RyaW5nLmludGVybmFsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3NhZmV1cmxfdGVzdC5qcycsIFsnZ29vZy5odG1sLnNhZmVVcmxUZXN0J10sIFsnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwuc2FmZVVybFRlc3RWZWN0b3JzJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYWZldXJsX3Rlc3RfdmVjdG9ycy5qcycsIFsnZ29vZy5odG1sLnNhZmVVcmxUZXN0VmVjdG9ycyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL2F0dHJpYnV0ZXdoaXRlbGlzdC5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5BdHRyaWJ1dGVTYW5pdGl6ZWRXaGl0ZWxpc3QnLCAnZ29vZy5odG1sLnNhbml0aXplci5BdHRyaWJ1dGVXaGl0ZWxpc3QnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9jc3Nwcm9wZXJ0eXNhbml0aXplci5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5Dc3NQcm9wZXJ0eVNhbml0aXplciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZyddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL2Nzc3Byb3BlcnR5c2FuaXRpemVyX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQ3NzUHJvcGVydHlTYW5pdGl6ZXJUZXN0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLnNhbml0aXplci5Dc3NQcm9wZXJ0eVNhbml0aXplcicsICdnb29nLmh0bWwuc2FuaXRpemVyLm5vY2xvYmJlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9jc3NzYW5pdGl6ZXIuanMnLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQ3NzU2FuaXRpemVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5odG1sLkNzc1NwZWNpZmljaXR5JywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQ3NzUHJvcGVydHlTYW5pdGl6ZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5ub2Nsb2JiZXInLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL2Nzc3Nhbml0aXplcl90ZXN0LmpzJywgWydnb29nLmh0bWwuQ3NzU2FuaXRpemVyVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLmh0bWwuU2FmZVN0eWxlU2hlZXQnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLnNhbml0aXplci5Dc3NTYW5pdGl6ZXInLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9lbGVtZW50d2Vha21hcC5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5FbGVtZW50V2Vha01hcCddLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIubm9jbG9iYmVyJ10sIHsnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYW5pdGl6ZXIvZWxlbWVudHdlYWttYXBfdGVzdC5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5FbGVtZW50V2Vha01hcFRlc3QnXSwgWydnb29nLmh0bWwuc2FuaXRpemVyLkVsZW1lbnRXZWFrTWFwJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9odG1sX3Rlc3RfdmVjdG9ycy5qcycsIFsnZ29vZy5odG1sLmh0bWxUZXN0VmVjdG9ycyddLCBbXSwgeydsYW5nJzogJ2VzNSd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9odG1sc2FuaXRpemVyLmpzJywgWydnb29nLmh0bWwuc2FuaXRpemVyLkh0bWxTYW5pdGl6ZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5IdG1sU2FuaXRpemVyLkJ1aWxkZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5IdG1sU2FuaXRpemVyQXR0cmlidXRlUG9saWN5JywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuSHRtbFNhbml0aXplclBvbGljeScsICdnb29nLmh0bWwuc2FuaXRpemVyLkh0bWxTYW5pdGl6ZXJQb2xpY3lDb250ZXh0JywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuSHRtbFNhbml0aXplclBvbGljeUhpbnRzJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuSHRtbFNhbml0aXplclVybFBvbGljeSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQXR0cmlidXRlU2FuaXRpemVkV2hpdGVsaXN0JywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQXR0cmlidXRlV2hpdGVsaXN0JywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuQ3NzU2FuaXRpemVyJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuU2FmZURvbVRyZWVQcm9jZXNzb3InLCAnZ29vZy5odG1sLnNhbml0aXplci5UYWdCbGFja2xpc3QnLCAnZ29vZy5odG1sLnNhbml0aXplci5UYWdXaGl0ZWxpc3QnLCAnZ29vZy5odG1sLnNhbml0aXplci5ub2Nsb2JiZXInLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0J10sIHsnbGFuZyc6ICdlczUnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYW5pdGl6ZXIvaHRtbHNhbml0aXplcl90ZXN0LmpzJywgWydnb29nLmh0bWwuSHRtbFNhbml0aXplclRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwuc2FuaXRpemVyLkh0bWxTYW5pdGl6ZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5IdG1sU2FuaXRpemVyLkJ1aWxkZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5UYWdXaGl0ZWxpc3QnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9odG1sc2FuaXRpemVyX3VuaWZpZWRfdGVzdC5qcycsIFsnZ29vZy5odG1sLkh0bWxTYW5pdGl6ZXJVbmlmaWVkVGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuaHRtbFRlc3RWZWN0b3JzJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuSHRtbFNhbml0aXplci5CdWlsZGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9ub2Nsb2JiZXIuanMnLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIubm9jbG9iYmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNScsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9ub2Nsb2JiZXJfdGVzdC5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5ub2Nsb2JiZXJUZXN0J10sIFsnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5odG1sLnNhbml0aXplci5ub2Nsb2JiZXInLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci9zYWZlZG9tdHJlZXByb2Nlc3Nvci5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci5TYWZlRG9tVHJlZVByb2Nlc3NvciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuc2FuaXRpemVyLkVsZW1lbnRXZWFrTWFwJywgJ2dvb2cuaHRtbC5zYW5pdGl6ZXIubm9jbG9iYmVyJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLmxvZycsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnVzZXJBZ2VudCddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL3NhZmVkb210cmVlcHJvY2Vzc29yX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuU2FmZURvbVRyZWVQcm9jZXNzb3JUZXN0J10sIFsnZ29vZy5odG1sLnNhbml0aXplci5TYWZlRG9tVHJlZVByb2Nlc3NvcicsICdnb29nLmh0bWwuc2FuaXRpemVyLm5vY2xvYmJlcicsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3Nhbml0aXplci90YWdibGFja2xpc3QuanMnLCBbJ2dvb2cuaHRtbC5zYW5pdGl6ZXIuVGFnQmxhY2tsaXN0J10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zYW5pdGl6ZXIvdGFnd2hpdGVsaXN0LmpzJywgWydnb29nLmh0bWwuc2FuaXRpemVyLlRhZ1doaXRlbGlzdCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL3Vuc2FmZS5qcycsIFsnZ29vZy5odG1sLnNhbml0aXplci51bnNhZmUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLnNhbml0aXplci5IdG1sU2FuaXRpemVyLkJ1aWxkZXInLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvc2FuaXRpemVyL3Vuc2FmZV90ZXN0LmpzJywgWydnb29nLmh0bWwuVW5zYWZlVGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuc2FuaXRpemVyLkF0dHJpYnV0ZVdoaXRlbGlzdCcsICdnb29nLmh0bWwuc2FuaXRpemVyLkh0bWxTYW5pdGl6ZXInLCAnZ29vZy5odG1sLnNhbml0aXplci5UYWdXaGl0ZWxpc3QnLCAnZ29vZy5odG1sLnNhbml0aXplci51bnNhZmUnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC9zaWx2ZXJsaWdodC5qcycsIFsnZ29vZy5odG1sLnNpbHZlcmxpZ2h0J10sIFsnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5odG1sLmZsYXNoJywgJ2dvb2cuc3RyaW5nLkNvbnN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3NpbHZlcmxpZ2h0X3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5zaWx2ZXJsaWdodFRlc3QnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwuc2lsdmVybGlnaHQnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvdGVzdGluZy5qcycsIFsnZ29vZy5odG1sLnRlc3RpbmcnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTY3JpcHQnLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLmh0bWwuU2FmZVN0eWxlU2hlZXQnLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLkFyZ3VtZW50TWF0Y2hlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC90ZXh0ZXh0cmFjdG9yLmpzJywgWydnb29nLmh0bWwudGV4dEV4dHJhY3RvciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmh0bWwuc2FuaXRpemVyLkh0bWxTYW5pdGl6ZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvdGV4dGV4dHJhY3Rvcl90ZXN0LmpzJywgWydnb29nLmh0bWwudGV4dEV4dHJhY3RvclRlc3QnXSwgWydnb29nLmh0bWwudGV4dEV4dHJhY3RvcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC90cnVzdGVkcmVzb3VyY2V1cmwuanMnLCBbJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLnRydXN0ZWR0eXBlcycsICdnb29nLmkxOG4uYmlkaS5EaXInLCAnZ29vZy5pMThuLmJpZGkuRGlyZWN0aW9uYWxTdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy5zdHJpbmcuVHlwZWRTdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvdHJ1c3RlZHJlc291cmNldXJsX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC50cnVzdGVkUmVzb3VyY2VVcmxUZXN0J10sIFsnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmh0bWwudHJ1c3RlZHR5cGVzJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaHRtbC90cnVzdGVkdHlwZXMuanMnLCBbJ2dvb2cuaHRtbC50cnVzdGVkdHlwZXMnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3VuY2hlY2tlZGNvbnZlcnNpb25zLmpzJywgWydnb29nLmh0bWwudW5jaGVja2VkY29udmVyc2lvbnMnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC5TYWZlU2NyaXB0JywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy5zdHJpbmcuaW50ZXJuYWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvdW5jaGVja2VkY29udmVyc2lvbnNfdGVzdC5qcycsIFsnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zVGVzdCddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZVNjcmlwdCcsICdnb29nLmh0bWwuU2FmZVN0eWxlJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGVTaGVldCcsICdnb29nLmh0bWwuU2FmZVVybCcsICdnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLmkxOG4uYmlkaS5EaXInLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2h0bWwvdXRpbHMuanMnLCBbJ2dvb2cuaHRtbC51dGlscyddLCBbJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdodG1sL3V0aWxzX3Rlc3QuanMnLCBbJ2dvb2cuaHRtbC5VdGlsc1Rlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5odG1sLnV0aWxzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2JpZGkuanMnLCBbJ2dvb2cuaTE4bi5iaWRpJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLmkxOG4uYmlkaS5EaXJlY3Rpb25hbFN0cmluZycsICdnb29nLmkxOG4uYmlkaS5Gb3JtYXQnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9iaWRpX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5iaWRpVGVzdCddLCBbJ2dvb2cuaTE4bi5iaWRpJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9iaWRpZm9ybWF0dGVyLmpzJywgWydnb29nLmkxOG4uQmlkaUZvcm1hdHRlciddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmkxOG4uYmlkaScsICdnb29nLmkxOG4uYmlkaS5EaXInLCAnZ29vZy5pMThuLmJpZGkuRm9ybWF0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2JpZGlmb3JtYXR0ZXJfdGVzdC5qcycsIFsnZ29vZy5pMThuLkJpZGlGb3JtYXR0ZXJUZXN0J10sIFsnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cuaTE4bi5CaWRpRm9ybWF0dGVyJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLmkxOG4uYmlkaS5Gb3JtYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY2hhcmxpc3RkZWNvbXByZXNzb3IuanMnLCBbJ2dvb2cuaTE4bi5DaGFyTGlzdERlY29tcHJlc3NvciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5pMThuLnVDaGFyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2NoYXJsaXN0ZGVjb21wcmVzc29yX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5DaGFyTGlzdERlY29tcHJlc3NvclRlc3QnXSwgWydnb29nLmkxOG4uQ2hhckxpc3REZWNvbXByZXNzb3InLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY2hhcnBpY2tlcmRhdGEuanMnLCBbJ2dvb2cuaTE4bi5DaGFyUGlja2VyRGF0YSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY29sbGF0aW9uLmpzJywgWydnb29nLmkxOG4uY29sbGF0aW9uJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY29sbGF0aW9uX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5jb2xsYXRpb25UZXN0J10sIFsnZ29vZy5pMThuLmNvbGxhdGlvbicsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9jb21wYWN0bnVtYmVyZm9ybWF0c3ltYm9scy5qcycsIFsnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hZicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYW0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9EWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfRUcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2F6JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19iZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYmcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19icicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYnMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jaHInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jeScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZGEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2RlJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kZV9BVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZGVfQ0gnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VsJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQVUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0NBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9HQicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fSUUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9TRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVVMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1pBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lcycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfNDE5JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19FUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfTVgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1VTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ldCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19maScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZmlsJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfQ0EnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2dhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19nbCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ3N3JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ndScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaGF3JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19oZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaGknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hyJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19odScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaHknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2lkJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pbicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaXMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2l0JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pdycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfamEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2thJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19raycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa20nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa3knLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbHQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2x2JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19taycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21uJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbXInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21zJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tdCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbXknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25iJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19uZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25vJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ub19OTycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfb3InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3BhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wbCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcHQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3B0X0JSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wdF9QVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcm8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3J1JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zaCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2knLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NrJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zbCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc3EnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zcl9MYXRuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zdicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc3cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190ZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RsJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190cicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdWsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3VyJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc191eicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdmknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3poJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9DTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfemhfSEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3poX1RXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196dSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY29tcGFjdG51bWJlcmZvcm1hdHN5bWJvbHNleHQuanMnLCBbJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc0V4dCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYWZfTkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FmX1pBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hZ3EnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FncV9DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYWsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FrX0dIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hbV9FVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfMDAxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9BRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfQkgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0RKJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9FSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfRVInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0lMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9JUScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfSk8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0tNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9LVycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfTEInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0xZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9NQScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfTVInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX09NJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9QUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfUUEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9TRCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfU08nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9TWScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfVEQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1ROJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hcl9YQicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXJfWUUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hc19JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXNhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hc2FfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2FzdCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYXN0X0VTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hel9DeXJsJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hel9DeXJsX0FaJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hel9MYXRuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19hel9MYXRuX0FaJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19iYXMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2Jhc19DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYmVfQlknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JlbScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYmVtX1pNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19iZXonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2Jlel9UWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYmdfQkcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JtJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ibV9NTCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYm5fQkQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JuX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ibycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYm9fQ04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JvX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19icl9GUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfYnJ4JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19icnhfSU4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0N5cmwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0N5cmxfQkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0xhdG4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0xhdG5fQkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NhX0FEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jYV9FUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2FfRlInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NhX0lUJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jY3AnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NjcF9CRCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2NwX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2VfUlUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NlYicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2ViX1BIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jZ2cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NnZ19VRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2hyX1VTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ja2InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2NrYl9JUScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY2tiX0lSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19jc19DWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfY3lfR0InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2RhX0RLJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kYV9HTCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZGF2JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kYXZfS0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0JFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kZV9ERScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZGVfSVQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0xJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kZV9MVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZGplJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kamVfTkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2RzYicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZHNiX0RFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kdWEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2R1YV9DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZHlvJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19keW9fU04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2R6JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kel9CVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZWJ1JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lYnVfS0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VlJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lZV9HSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZWVfVEcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VsX0NZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbF9HUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fMDAxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl8xNTAnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0FFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9BRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQUknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0FTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9BVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQkInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0JFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9CSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQk0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0JTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9CVycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQlonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0NDJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9DSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ0snLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9DWCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ1knLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0RFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9ERycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fREsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0RNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9FUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fRkknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0ZKJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9GSycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fRk0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0dEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9HRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fR0gnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0dJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9HTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fR1UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0dZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9ISycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fSUwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0lNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9JTycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fSkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0pNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fS0knLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0tOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9LWScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTEMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0xSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9MUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTUcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX01IJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9NTycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVAnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX01TJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9NVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX01XJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9NWScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX05GJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9ORycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX05SJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9OVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fTlonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1BHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9QSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fUEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1BOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9QUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fUFcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1JXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9TQicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0MnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1NEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9TRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0gnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1NJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9TTCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fU1MnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1NYJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9TWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVEMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1RLJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9UTycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVFQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1RWJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9UWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVUcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1VNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9VU19QT1NJWCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVkMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1ZHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9WSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fVlUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1dTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbl9YQScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW5fWk0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1pXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW9fMDAxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19BUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfQk8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0JSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19CWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfQ0wnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0NPJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19DUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfQ1UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0RPJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19FQScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfRUMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0dRJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19HVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfSE4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0lDJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19OSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfUEEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19QSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfUFInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19lc19TVicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXNfVVknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1ZFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ldF9FRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXVfRVMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2V3bycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZXdvX0NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mYV9BRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZmFfSVInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZmJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0JGJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0xSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX01SJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX05FJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX05HJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX1NMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX1NOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19maV9GSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZmlsX1BIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZm9fREsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZvX0ZPJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfQkYnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0JJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CSicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfQkwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0NEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfQ0cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0NIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfQ00nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0RKJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9EWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfRlInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0dBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfR04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0dQJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HUScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfSFQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0tNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9MVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfTUEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX01DJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfTUcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX01MJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NUScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfTVInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX01VJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9OQycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfTkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX1BGJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9QTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfUkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX1JXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9TQycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfU04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX1NZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9URCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfVEcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX1ROJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mcl9WVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnJfV0YnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX1lUJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19mdXInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2Z1cl9JVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZnknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2Z5X05MJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19nYV9JRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ2QnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2dkX0dCJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19nbF9FUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ3N3X0NIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19nc3dfRlInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2dzd19MSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ3VfSU4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2d1eicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ3V6X0tFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ndicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZ3ZfSU0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19oYV9HSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaGFfTkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hhX05HJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19oYXdfVVMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hlX0lMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19oaV9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaHJfQkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hyX0hSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19oc2InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2hzYl9ERScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaHVfSFUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2h5X0FNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pYScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaWFfMDAxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pZF9JRCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaWcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2lnX05HJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19paScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaWlfQ04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2lzX0lTJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pdF9DSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfaXRfSVQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2l0X1NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19pdF9WQScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfamFfSlAnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2pnbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfamdvX0NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19qbWMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ptY19UWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfanYnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2p2X0lEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rYV9HRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2FiJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rYWJfRFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2thbScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2FtX0tFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rZGUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tkZV9UWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2VhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rZWFfQ1YnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tocScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2hxX01MJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19raScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2lfS0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2trX0taJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ra2onLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tral9DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa2wnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tsX0dMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rbG4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tsbl9LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa21fS0gnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tuX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rb19LUCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa29fS1InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tvaycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa29rX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rcycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa3NfSU4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tzYicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa3NiX1RaJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rc2YnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2tzZl9DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa3NoJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rc2hfREUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2t1JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19rdV9UUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfa3cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2t3X0dCJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19reV9LRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbGFnJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sYWdfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xiJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sYl9MVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbGcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xnX1VHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sa3QnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xrdF9VUycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbG5fQU8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xuX0NEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sbl9DRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbG5fQ0cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xvX0xBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19scmMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2xyY19JUScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbHJjX0lSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sdF9MVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbHUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2x1X0NEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sdW8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2x1b19LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbHV5JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19sdXlfS0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2x2X0xWJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tYXMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21hc19LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWFzX1RaJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tZXInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21lcl9LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWZlJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tZmVfTVUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21nJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tZ19NRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWdoJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tZ2hfTVonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21nbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWdvX0NNJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19taScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbWlfTlonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21rX01LJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tbF9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbW5fTU4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21yX0lOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tc19CTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbXNfTVknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX21zX1NHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tdF9NVCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbXVhJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tdWFfQ00nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX215X01NJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19tem4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX216bl9JUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmFxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19uYXFfTkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25iX05PJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19uYl9TSicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25kX1pXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19uZHMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25kc19ERScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmRzX05MJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19uZV9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmVfTlAnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25sX0FXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ubF9CRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmxfQlEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25sX0NXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ubF9OTCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbmxfU1InLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25sX1NYJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ubWcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25tZ19DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbm4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25uX05PJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ubmgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX25uaF9DTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbnVzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19udXNfU1MnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX255bicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfbnluX1VHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19vbScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfb21fRVQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX29tX0tFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19vcl9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfb3MnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX29zX0dFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19vc19SVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcGFfQXJhYicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcGFfQXJhYl9QSycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcGFfR3VydScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcGFfR3VydV9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcGxfUEwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3BzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wc19BRicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcHNfUEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3B0X0FPJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wdF9DSCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcHRfQ1YnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3B0X0dRJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wdF9HVycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcHRfTFUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3B0X01PJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19wdF9NWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcHRfU1QnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3B0X1RMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19xdScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcXVfQk8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3F1X0VDJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19xdV9QRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcm0nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3JtX0NIJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ybicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcm5fQkknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3JvX01EJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19yb19STycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcm9mJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19yb2ZfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3J1X0JZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ydV9LRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcnVfS1onLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3J1X01EJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19ydV9SVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcnVfVUEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3J3JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19yd19SVycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfcndrJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19yd2tfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NhaCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2FoX1JVJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zYXEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NhcV9LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2JwJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zYnBfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NkJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zZF9QSycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NlX0ZJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zZV9OTycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2VfU0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NlaCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2VoX01aJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zZXMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3Nlc19NTCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NnX0NGJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zaGknLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NoaV9MYXRuJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zaGlfTGF0bl9NQScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2hpX1RmbmcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NoaV9UZm5nX01BJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zaV9MSycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc2tfU0snLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NsX1NJJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zbW4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3Ntbl9GSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc24nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NuX1pXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc29fREonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NvX0VUJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zb19LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc29fU08nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NxX0FMJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zcV9NSycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc3FfWEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmxfQkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmxfTUUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmxfUlMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmxfWEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0xhdG5fQkEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0xhdG5fTUUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0xhdG5fUlMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0xhdG5fWEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3N2X0FYJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zdl9GSScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc3ZfU0UnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3N3X0NEJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19zd19LRScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfc3dfVFonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3N3X1VHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190YV9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGFfTEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RhX01ZJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190YV9TRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGVfSU4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RlbycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGVvX0tFJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190ZW9fVUcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RnJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190Z19USicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGhfVEgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RpJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190aV9FUicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdGlfRVQnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RrJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190a19UTScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdG8nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3RvX1RPJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190cl9DWScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdHJfVFInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3R0JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190dF9SVScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdHdxJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc190d3FfTkUnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3R6bScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdHptX01BJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc191ZycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdWdfQ04nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3VrX1VBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc191cl9JTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdXJfUEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0FyYWInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0FyYWJfQUYnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0N5cmwnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0N5cmxfVVonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0xhdG4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0xhdG5fVVonLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdmFpX0xhdG4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaV9MYXRuX0xSJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc192YWlfVmFpaScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfdmFpX1ZhaWlfTFInLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3ZpX1ZOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc192dW4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3Z1bl9UWicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfd2FlJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc193YWVfQ0gnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3dvJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc193b19TTicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfeGgnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3hoX1pBJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc194b2cnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3hvZ19VRycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfeWF2JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc195YXZfQ00nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3lpJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc195aV8wMDEnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3lvJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc195b19CSicsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfeW9fTkcnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3l1ZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfeXVlX0hhbnMnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3l1ZV9IYW5zX0NOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc195dWVfSGFudCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfeXVlX0hhbnRfSEsnLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX3pnaCcsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfemdoX01BJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zX0NOJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zX0hLJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zX01PJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zX1NHJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50JywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50X0hLJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50X01PJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50X1RXJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc196dV9aQSddLCBbJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9scyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9jdXJyZW5jeS5qcycsIFsnZ29vZy5pMThuLmN1cnJlbmN5JywgJ2dvb2cuaTE4bi5jdXJyZW5jeS5DdXJyZW5jeUluZm8nLCAnZ29vZy5pMThuLmN1cnJlbmN5LkN1cnJlbmN5SW5mb1RpZXIyJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY3VycmVuY3lfdGVzdC5qcycsIFsnZ29vZy5pMThuLmN1cnJlbmN5VGVzdCddLCBbJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXQnLCAnZ29vZy5pMThuLmN1cnJlbmN5JywgJ2dvb2cuaTE4bi5jdXJyZW5jeS5DdXJyZW5jeUluZm8nLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vY3VycmVuY3ljb2RlbWFwLmpzJywgWydnb29nLmkxOG4uY3VycmVuY3lDb2RlTWFwJywgJ2dvb2cuaTE4bi5jdXJyZW5jeUNvZGVNYXBUaWVyMiddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vZGF0ZWludGVydmFsZm9ybWF0LmpzJywgWydnb29nLmkxOG4uRGF0ZUludGVydmFsRm9ybWF0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kYXRlLkRhdGVMaWtlJywgJ2dvb2cuZGF0ZS5EYXRlUmFuZ2UnLCAnZ29vZy5kYXRlLkRhdGVUaW1lJywgJ2dvb2cuZGF0ZS5JbnRlcnZhbCcsICdnb29nLmkxOG4uRGF0ZVRpbWVGb3JtYXQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzVHlwZScsICdnb29nLmkxOG4uVGltZVpvbmUnLCAnZ29vZy5pMThuLmRhdGVJbnRlcnZhbFN5bWJvbHMnLCAnZ29vZy5vYmplY3QnXSwgeydsYW5nJzogJ2VzNScsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2RhdGVpbnRlcnZhbGZvcm1hdF90ZXN0LmpzJywgWydnb29nLmkxOG4uRGF0ZUludGVydmFsRm9ybWF0VGVzdCddLCBbJ2dvb2cuZGF0ZS5EYXRlJywgJ2dvb2cuZGF0ZS5EYXRlUmFuZ2UnLCAnZ29vZy5kYXRlLkRhdGVUaW1lJywgJ2dvb2cuZGF0ZS5JbnRlcnZhbCcsICdnb29nLmkxOG4uRGF0ZUludGVydmFsRm9ybWF0JywgJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9DQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2dsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaGknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aCcsICdnb29nLmkxOG4uVGltZVpvbmUnLCAnZ29vZy5pMThuLmRhdGVJbnRlcnZhbFBhdHRlcm5zJywgJ2dvb2cuaTE4bi5kYXRlSW50ZXJ2YWxTeW1ib2xzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2RhdGVpbnRlcnZhbHBhdHRlcm5zLmpzJywgWydnb29nLmkxOG4uZGF0ZUludGVydmFsUGF0dGVybnMnXSwgWydnb29nLmkxOG4uZGF0ZUludGVydmFsU3ltYm9scyddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vZGF0ZWludGVydmFscGF0dGVybnNleHQuanMnLCBbJ2dvb2cuaTE4bi5kYXRlSW50ZXJ2YWxQYXR0ZXJuc0V4dCddLCBbJ2dvb2cuaTE4bi5kYXRlSW50ZXJ2YWxQYXR0ZXJucyddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vZGF0ZWludGVydmFsc3ltYm9scy5qcycsIFsnZ29vZy5pMThuLmRhdGVJbnRlcnZhbFN5bWJvbHMnXSwgW10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9kYXRlaW50ZXJ2YWxzeW1ib2xzZXh0LmpzJywgWydnb29nLmkxOG4uZGF0ZUludGVydmFsU3ltYm9sc0V4dCddLCBbJ2dvb2cuaTE4bi5kYXRlSW50ZXJ2YWxTeW1ib2xzJ10sIHsnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9kYXRldGltZWZvcm1hdC5qcycsIFsnZ29vZy5pMThuLkRhdGVUaW1lRm9ybWF0JywgJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdC5Gb3JtYXQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kYXRlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHMnLCAnZ29vZy5pMThuLlRpbWVab25lJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2RhdGV0aW1lZm9ybWF0X3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdFRlc3QnXSwgWydnb29nLmRhdGUuRGF0ZScsICdnb29nLmRhdGUuRGF0ZVRpbWUnLCAnZ29vZy5pMThuLkRhdGVUaW1lRm9ybWF0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JnJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2RlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VuX1hBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2phJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3N2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3poX0hLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3poX0hhbnRfVFcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0FFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfRUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9TQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JuX0JEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0dCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fSUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0RKJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaGVfSUwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19qYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3JvX1JPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3YnLCAnZ29vZy5pMThuLlRpbWVab25lJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2RhdGV0aW1lcGFyc2UuanMnLCBbJ2dvb2cuaTE4bi5EYXRlVGltZVBhcnNlJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGF0ZScsICdnb29nLmkxOG4uRGF0ZVRpbWVGb3JtYXQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9kYXRldGltZXBhcnNlX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5EYXRlVGltZVBhcnNlVGVzdCddLCBbJ2dvb2cuZGF0ZS5EYXRlJywgJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXJzZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcGwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aCcsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9kYXRldGltZXBhdHRlcm5zLmpzJywgWydnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJucycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hZicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hbScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hcicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hcl9EWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hcl9FRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19heicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19iZScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19iZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ibicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19icicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19icycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jYScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jaHInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY3MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY3knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfQVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZWwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQVUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ0EnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR0InLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fWkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZXNfNDE5JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX01YJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2V0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2V1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZpbCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mcicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mcl9DQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nYScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nbCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nc3cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZ3UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfaGF3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2h1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2h5JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2lkJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2luJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2lzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2l0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2l3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2phJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2thJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2trJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ttJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t5JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2xuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2xvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2x0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2x2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21rJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21sJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21uJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21vJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21yJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21zJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX210JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX215JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25iJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25lJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25sJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25vJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25vX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29yJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3BhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3BsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3B0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3B0X0JSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3B0X1BUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3JvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3J1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NoJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NrJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NyX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc3YnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc3cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdGEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdGUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdGgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdGwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdHInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdWsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdmknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfQ04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfSEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfVFcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfenUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2RhdGV0aW1lcGF0dGVybnNleHQuanMnLCBbJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zRXh0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FmX05BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FmX1pBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FncScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hZ3FfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYWsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYWtfR0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYW1fRVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYXJfMDAxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0FFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0JIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0RKJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0VIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0VSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0lMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0lRJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0pPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0tNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0tXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0xCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX0xZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX01BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX01SJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX09NJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1BTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1FBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1NBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1NEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1NPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1NTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1NZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1REJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1ROJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1hCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FyX1lFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FzX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FzYScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hc2FfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYXN0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2FzdF9FUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hel9DeXJsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2F6X0N5cmxfQVonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYXpfTGF0bicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19hel9MYXRuX0FaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JhcycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19iYXNfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYmVfQlknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYmVtJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JlbV9aTScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19iZXonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYmV6X1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JnX0JHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JtJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JtX01MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JuX0JEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JuX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JvX0NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JvX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JyX0ZSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JyeCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19icnhfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYnNfQ3lybCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ic19DeXJsX0JBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2JzX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfYnNfTGF0bl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jYV9BRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jYV9FUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jYV9GUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jYV9JVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jY3AnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY2NwX0JEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2NjcF9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jZScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jZV9SVScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jZWInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY2ViX1BIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2NnZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19jZ2dfVUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY2hyX1VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2NrYicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ja2JfSVEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfY2tiX0lSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2NzX0NaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2N5X0dCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2RhX0RLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2RhX0dMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2RhdicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19kYXZfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfREUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfSVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfTEknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGVfTFUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZGplJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2RqZV9ORScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19kc2InLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZHNiX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2R1YScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19kdWFfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZHlvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2R5b19TTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19keicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19kel9CVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19lYnUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZWJ1X0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VlX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VlX1RHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VsX0NZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VsX0dSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VuXzAwMScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19lbl8xNTAnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQUknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQkInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQkknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQk0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQlMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQlonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ0MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ0snLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ1gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fQ1knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fREUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fREcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fREsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRE0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRVInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRkknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRkonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRksnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fRk0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR0cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR0knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR1UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fR1knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSUwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSU0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fSk0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fS0knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fS04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fS1knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTEMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTFInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTFMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTUgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVAnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTVknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTkYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTkcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTkwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTlInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fTlonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUEcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUEgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUE4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUFInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUFcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fUlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0InLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU1MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU1gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fU1onLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVEMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVE8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVFQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVFYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVU0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVVNfUE9TSVgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVkMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVkcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVkknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fVlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fV1MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fWEEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fWk0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW5fWlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZW9fMDAxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0FSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0JPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0JSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0JaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0NMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0NPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0NSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0NVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0RPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0VBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0VDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0dRJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0dUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0hOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX0lDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX05JJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1BBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1BFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1BIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1BSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1BZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1NWJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1VZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2VzX1ZFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2V0X0VFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2V1X0VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2V3bycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ld29fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmFfQUYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmFfSVInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmZfTGF0bicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mZl9MYXRuX0JGJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZmX0xhdG5fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmZfTGF0bl9HSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mZl9MYXRuX0dNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZmX0xhdG5fR04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmZfTGF0bl9HVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mZl9MYXRuX0xSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZmX0xhdG5fTVInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmZfTGF0bl9ORScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19mZl9MYXRuX05HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ZmX0xhdG5fU0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZmZfTGF0bl9TTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19maV9GSScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19maWxfUEgnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZm8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZm9fREsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZm9fRk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQkYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQkknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQkonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQkwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ0YnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ0cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ0knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfREonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfRFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfRlInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfR0EnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfR0YnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfR04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfR1AnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfR1EnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfSFQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfS00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTFUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTUMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTUYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTUwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTVEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTVInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTVUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTkMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfTkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfUEYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfUE0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfUkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfUlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfU0MnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfU04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfU1knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfVEQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfVEcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfVE4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfVlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfV0YnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnJfWVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZnVyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2Z1cl9JVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19meScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19meV9OTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nYV9JRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nZF9HQicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nbF9FUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19nc3dfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZ3N3X0ZSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2dzd19MSScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ndV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ndXonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfZ3V6X0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2d2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2d2X0lNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hhX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hhX05FJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hhX05HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2hhd19VUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19oZV9JTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19oaV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ocl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ocl9IUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19oc2InLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfaHNiX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2h1X0hVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2h5X0FNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2lhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2lhXzAwMScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pZF9JRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pZ19ORycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19paScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19paV9DTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pc19JUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pdF9DSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pdF9JVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pdF9TTScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19pdF9WQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19qYV9KUCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19qZ28nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfamdvX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2ptYycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19qbWNfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfanYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfanZfSUQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2FfR0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2FiJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2thYl9EWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rYW0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2FtX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tkZScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rZGVfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2VhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tlYV9DVicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19raHEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2hxX01MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tpX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2trX0taJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2traicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ra2pfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2wnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2xfR0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa2xuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tsbl9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rbV9LSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rbl9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rb19LUCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rb19LUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rb2snLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa29rX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tzX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tzYicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rc2JfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa3NmJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2tzZl9DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19rc2gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfa3NoX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t1X1RSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t3X0dCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2t5X0tHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2xhZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sYWdfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbGInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbGJfTFUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbGcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbGdfVUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbGt0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2xrdF9VUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sbl9BTycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sbl9DRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sbl9DRicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sbl9DRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sb19MQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19scmMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbHJjX0lRJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2xyY19JUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sdF9MVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sdScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sdV9DRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sdW8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbHVvX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX2x1eScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19sdXlfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbHZfTFYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbWFzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21hc19LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tYXNfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbWVyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21lcl9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tZmUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbWZlX01VJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21nJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21nX01HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21naCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tZ2hfTVonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbWdvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX21nb19DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19taScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19taV9OWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ta19NSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tbF9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tbl9NTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tcl9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tc19CTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tc19NWScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tc19TRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tdF9NVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tdWEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbXVhX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX215X01NJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX216bicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19tem5fSVInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbmFxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25hcV9OQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uYl9OTycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uYl9TSicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uZF9aVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uZHMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbmRzX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25kc19OTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uZV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19uZV9OUCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9BVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9CRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9CUScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9DVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9OTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9TUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubF9TWCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubWcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbm1nX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25uJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25uX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX25uaCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ubmhfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbnVzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX251c19TUycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ueW4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfbnluX1VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29tJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29tX0VUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29tX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29yX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29zJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29zX0dFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX29zX1JVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3BhX0FyYWInLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcGFfQXJhYl9QSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19wYV9HdXJ1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3BhX0d1cnVfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcGxfUEwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHNfQUYnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHNfUEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfQU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfQ1YnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfR1EnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfR1cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfTFUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfTU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfTVonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfU1QnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcHRfVEwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcXUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcXVfQk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcXVfRUMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcXVfUEUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm0nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm1fQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm5fQkknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm9fTUQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm9fUk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcm9mJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3JvZl9UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9CWScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9LRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9LWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9NRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9SVScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydV9VQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19ydycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19yd19SVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19yd2snLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfcndrX1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NhaCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zYWhfUlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2FxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NhcV9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zYnAnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2JwX1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NkJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NkX1BLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NlX0ZJJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NlX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NlX1NFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NlaCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zZWhfTVonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2VzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3Nlc19NTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zZ19DRicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zaGknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2hpX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2hpX0xhdG5fTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2hpX1RmbmcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2hpX1RmbmdfTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2lfTEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2tfU0snLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc2xfU0knLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc21uJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3Ntbl9GSScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zbicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zbl9aVycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zbycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zb19ESicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zb19FVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zb19LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zb19TTycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcV9BTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcV9NSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcV9YSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcl9DeXJsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NyX0N5cmxfQkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc3JfQ3lybF9NRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcl9DeXJsX1JTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NyX0N5cmxfWEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc3JfTGF0bl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zcl9MYXRuX01FJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3NyX0xhdG5fUlMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfc3JfTGF0bl9YSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zdl9BWCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zdl9GSScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zdl9TRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zd19DRCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zd19LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zd19UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc19zd19VRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190YV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190YV9MSycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190YV9NWScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190YV9TRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190ZV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190ZW8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdGVvX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3Rlb19VRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190ZycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190Z19USicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190aF9USCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190aScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190aV9FUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190aV9FVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190aycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190a19UTScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190bycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190b19UTycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190cl9DWScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190cl9UUicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190dCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190dF9SVScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190d3EnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdHdxX05FJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3R6bScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc190em1fTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdWcnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdWdfQ04nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdWtfVUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXJfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXJfUEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXpfQXJhYicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc191el9BcmFiX0FGJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3V6X0N5cmwnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdXpfQ3lybF9VWicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc191el9MYXRuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3V6X0xhdG5fVVonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfdmFpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3ZhaV9MYXRuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3ZhaV9MYXRuX0xSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3ZhaV9WYWlpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3ZhaV9WYWlpX0xSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3ZpX1ZOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3Z1bicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc192dW5fVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfd2FlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3dhZV9DSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc193bycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc193b19TTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc194aCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc194aF9aQScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc194b2cnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfeG9nX1VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3lhdicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc195YXZfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfeWknLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfeWlfMDAxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3lvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3lvX0JKJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3lvX05HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3l1ZScsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc195dWVfSGFucycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc195dWVfSGFuc19DTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc195dWVfSGFudCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc195dWVfSGFudF9ISycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc196Z2gnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemdoX01BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3poX0hhbnMnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfSGFuc19DTicsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc196aF9IYW5zX0hLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3poX0hhbnNfTU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfSGFuc19TRycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc196aF9IYW50JywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3poX0hhbnRfSEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnNfemhfSGFudF9NTycsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXR0ZXJuc196aF9IYW50X1RXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVBhdHRlcm5zX3p1X1pBJ10sIFsnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vZGF0ZXRpbWVzeW1ib2xzLmpzJywgWydnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNUeXBlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYWYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hbScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfRFonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9FRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2F6JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19iZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYnInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19icycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2hyJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY3MnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19jeScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19kZV9BVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RlX0NIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZWwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0FVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQ0EnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9HQicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0lFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9JU08nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9TRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fWkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lcycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzXzQxOScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfTVgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19VUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2V0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmlsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9DQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2dhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZ2wnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19nc3cnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ndScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hhdycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hlJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaGknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ocicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2h1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaHknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19pZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2luJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19pdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2l3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfamEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2trJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa20nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa3knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2xvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sdicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21rJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21vJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbXInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tcycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX210JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbXknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19uYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25lJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ubycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25vX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfb3InLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3BsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wdF9CUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3B0X1BUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcm8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ydScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NoJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zaycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3EnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zcicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NyX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zdicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3N3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190ZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RoJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190cicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3VrJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdXInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc191eicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3ZpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aF9DTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3poX0hLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemhfVFcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196dSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vZGF0ZXRpbWVzeW1ib2xzZXh0LmpzJywgWydnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzRXh0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYWZfTkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hZl9aQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FncScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FncV9DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FrJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYWtfR0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hbV9FVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyXzAwMScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0FFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfQkgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9ESicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0VIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfRVInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9JTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0lRJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfSk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9LTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX0tXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfTEInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9MWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX01BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfTVInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9PTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX1BTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfUUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9TQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX1NEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfU08nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9TUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX1NZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfVEQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcl9UTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FyX1hCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXJfWUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hcycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2FzX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXNhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXNhX1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXN0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXN0X0VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXpfQ3lybCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2F6X0N5cmxfQVonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19hel9MYXRuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYXpfTGF0bl9BWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JhcycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2Jhc19DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JlX0JZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmVtJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmVtX1pNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmV6JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmV6X1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYmdfQkcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ibScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JtX01MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYm5fQkQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ibl9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYm9fQ04nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ib19JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JyX0ZSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYnJ4JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYnJ4X0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYnNfQ3lybCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2JzX0N5cmxfQkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ic19MYXRuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfYnNfTGF0bl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NhX0FEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2FfRVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19jYV9GUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NhX0lUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2NwJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2NwX0JEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2NwX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY2UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19jZV9SVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NlYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NlYl9QSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NnZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NnZ19VRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2Nocl9VUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NrYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NrYl9JUScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NrYl9JUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2NzX0NaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfY3lfR0InLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19kYV9ESycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RhX0dMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGF2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGF2X0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGVfQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19kZV9ERScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RlX0lUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZGVfTEknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19kZV9MVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RqZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RqZV9ORScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RzYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2RzYl9ERScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2R1YScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2R1YV9DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2R5bycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2R5b19TTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2R6JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZHpfQlQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lYnUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lYnVfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VlX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZWVfVEcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbF9DWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VsX0dSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fMDAxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fMTUwJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9BRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0FJJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9BVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0JCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9CSScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0JNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQlMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9CVycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0JaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQ0MnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9DSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0NLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9DWCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0NZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fREUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9ERycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0RLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fRE0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9FUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0ZJJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fRkonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9GSycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0ZNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fR0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9HRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fR0knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9HTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0dVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fR1knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9ISycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0lMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fSU0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9JTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0pFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fSk0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0tJJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fS04nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9LWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX0xDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTFInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9MUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX01HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTUgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9NTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX01QJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9NVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX01VJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTVcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9NWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX05BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTkYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9ORycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX05MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fTlInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9OVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX05aJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fUEcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9QSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1BLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fUE4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9QUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1BXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fUlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9TQicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1NDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fU0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9TRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1NIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fU0knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9TTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1NTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fU1gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9TWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1RDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fVEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9UTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1RUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fVFYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fVU0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9VU19QT1NJWCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1ZDJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fVkcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9WSScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1ZVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fV1MnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbl9YQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1pNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZW5fWlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lbycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VvXzAwMScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0FSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfQk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19CUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0JaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfQ0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19DTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0NSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfQ1UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19ETycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0VBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfRUMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19HUScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX0dUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfSE4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19JQycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX05JJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfUEEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19QRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX1BIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfUFInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19QWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VzX1NWJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXNfVVknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19lc19WRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2V0X0VFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZXVfRVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ld28nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ld29fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mYV9BRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZhX0lSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mZl9MYXRuJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmZfTGF0bl9CRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZmX0xhdG5fQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mZl9MYXRuX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmZfTGF0bl9HTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZmX0xhdG5fR04nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mZl9MYXRuX0dXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmZfTGF0bl9MUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZmX0xhdG5fTVInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mZl9MYXRuX05FJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmZfTGF0bl9ORycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZmX0xhdG5fU0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mZl9MYXRuX1NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZmlfRkknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19maWxfUEgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mbycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZvX0RLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZm9fRk8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9CRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0JGJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfQkknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9CSicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0JMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfQ0QnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9DRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0NHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9DSScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfREonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9EWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0ZSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfR0EnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9HRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0dOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfR1AnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9HUScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX0hUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfS00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9MVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX01BJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfTUMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9NRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX01HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfTUwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9NUScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX01SJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfTVUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9OQycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX05FJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfUEYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9QTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX1JFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfUlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9TQycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX1NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfU1knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9URCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX1RHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfVE4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mcl9WVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ZyX1dGJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZnJfWVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mdXInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19mdXJfSVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19meScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2Z5X05MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZ2FfSUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19nZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2dkX0dCJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZ2xfRVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19nc3dfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19nc3dfRlInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19nc3dfTEknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ndV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2d1eicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2d1el9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2d2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfZ3ZfSU0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19oYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hhX0dIJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaGFfTkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19oYV9ORycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hhd19VUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hlX0lMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaGlfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ocl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2hyX0hSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaHNiJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaHNiX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaHVfSFUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19oeV9BTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2lhJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaWFfMDAxJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaWRfSUQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19pZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2lnX05HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaWknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19paV9DTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2lzX0lTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaXRfQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19pdF9JVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2l0X1NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfaXRfVkEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19qYV9KUCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2pnbycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2pnb19DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ptYycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2ptY19UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2p2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfanZfSUQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rYV9HRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2thYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2thYl9EWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2thbScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2thbV9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tkZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tkZV9UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tlYScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tlYV9DVicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tocScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tocV9NTCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa2lfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ra19LWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2traicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tral9DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa2xfR0wnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rbG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rbG5fS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rbV9LSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tuX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa29fS1AnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rb19LUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tvaycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tva19JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2tzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa3NfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2InLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2JfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2YnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2ZfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rc2hfREUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rdScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2t1X1RSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfa3cnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19rd19HQicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2t5X0tHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbGFnJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbGFnX1RaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbGInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sYl9MVScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2xnJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbGdfVUcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sa3QnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sa3RfVVMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sbl9BTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2xuX0NEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbG5fQ0YnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sbl9DRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2xvX0xBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHJjJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHJjX0lRJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHJjX0lSJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHRfTFQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19sdScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2x1X0NEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHVvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHVvX0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHV5JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHV5X0tFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbHZfTFYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tYXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tYXNfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tYXNfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tZXInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tZXJfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tZmUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tZmVfTVUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21nX01HJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWdoJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWdoX01aJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWdvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWdvX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19taV9OWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21rX01LJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbWxfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tbl9NTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21yX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbXNfQk4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tc19NWScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX21zX1NHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbXRfTVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tdWEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19tdWFfQ00nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19teV9NTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX216bicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX216bl9JUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25hcScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25hcV9OQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25iX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmJfU0onLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19uZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25kX1pXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmRzJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmRzX0RFJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmRzX05MJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmVfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19uZV9OUCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25sX0FXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmxfQkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ubF9CUScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25sX0NXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbmxfTkwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ubF9TUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25sX1NYJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbm1nJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbm1nX0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfbm4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ubl9OTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25uaCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX25uaF9DTScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX251cycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX251c19TUycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX255bicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX255bl9VRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX29tJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfb21fRVQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19vbV9LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX29yX0lOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfb3MnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19vc19HRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX29zX1JVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcGFfQXJhYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3BhX0FyYWJfUEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wYV9HdXJ1JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcGFfR3VydV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3BsX1BMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wc19BRicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3BzX1BLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHRfQU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wdF9DSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3B0X0NWJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHRfR1EnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wdF9HVycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3B0X0xVJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHRfTU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19wdF9NWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3B0X1NUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcHRfVEwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19xdScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3F1X0JPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcXVfRUMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19xdV9QRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3JtJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcm1fQ0gnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ybicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3JuX0JJJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcm9fTUQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19yb19STycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3JvZicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3JvZl9UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3J1X0JZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcnVfS0cnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ydV9LWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3J1X01EJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcnVfUlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19ydV9VQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3J3JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfcndfUlcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19yd2snLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19yd2tfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYWgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYWhfUlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYXEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYXFfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYnAnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zYnBfVFonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NkX1BLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZV9GSScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NlX05PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2VfU0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZWgnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZWhfTVonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZXNfTUwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NnX0NGJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2hpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2hpX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zaGlfTGF0bl9NQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NoaV9UZm5nJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2hpX1RmbmdfTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zaV9MSycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NrX1NLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc2xfU0knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zbW4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zbW5fRkknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zbicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NuX1pXJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc28nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zb19ESicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NvX0VUJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc29fS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zb19TTycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NxX0FMJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3FfTUsnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zcV9YSycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NyX0N5cmwnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zcl9DeXJsX0JBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3JfQ3lybF9NRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NyX0N5cmxfUlMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zcl9DeXJsX1hLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3JfTGF0bl9CQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3NyX0xhdG5fTUUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zcl9MYXRuX1JTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3JfTGF0bl9YSycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3N2X0FYJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3ZfRkknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zdl9TRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3N3X0NEJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfc3dfS0UnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc19zd19UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3N3X1VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGFfSU4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190YV9MSycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RhX01ZJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGFfU0cnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190ZV9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RlbycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3Rlb19LRScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3Rlb19VRycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RnJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGdfVEonLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190aF9USCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGlfRVInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190aV9FVCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RrJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdGtfVE0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190bycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3RvX1RPJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdHJfQ1knLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190cl9UUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3R0JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdHRfUlUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190d3EnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190d3FfTkUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190em0nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc190em1fTUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc191ZycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3VnX0NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdWtfVUEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc191cl9JTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3VyX1BLJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdXpfQXJhYicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3V6X0FyYWJfQUYnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc191el9DeXJsJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdXpfQ3lybF9VWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3V6X0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc191el9MYXRuX1VaJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdmFpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdmFpX0xhdG4nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc192YWlfTGF0bl9MUicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3ZhaV9WYWlpJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfdmFpX1ZhaWlfTFInLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc192aV9WTicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3Z1bicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3Z1bl9UWicsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3dhZScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3dhZV9DSCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3dvJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfd29fU04nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc194aCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3hoX1pBJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeG9nJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeG9nX1VHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeWF2JywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeWF2X0NNJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeWknLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc195aV8wMDEnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc195bycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3lvX0JKJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeW9fTkcnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc195dWUnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc195dWVfSGFucycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3l1ZV9IYW5zX0NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfeXVlX0hhbnQnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc195dWVfSGFudF9ISycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3pnaCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3pnaF9NQScsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3poX0hhbnMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aF9IYW5zX0NOJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemhfSGFuc19ISycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3poX0hhbnNfTU8nLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aF9IYW5zX1NHJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemhfSGFudCcsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3poX0hhbnRfSEsnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9sc196aF9IYW50X01PJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemhfSGFudF9UVycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX3p1X1pBJ10sIFsnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9ncmFwaGVtZWJyZWFrLmpzJywgWydnb29nLmkxOG4uR3JhcGhlbWVCcmVhayddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmkxOG4udUNoYXInLCAnZ29vZy5zdHJ1Y3RzLkludmVyc2lvbk1hcCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9ncmFwaGVtZWJyZWFrX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5HcmFwaGVtZUJyZWFrVGVzdCddLCBbJ2dvb2cuaTE4bi5HcmFwaGVtZUJyZWFrJywgJ2dvb2cuaTE4bi51Q2hhcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9sb2NhbGVmZWF0dXJlLmpzJywgWydnb29nLmkxOG4uTG9jYWxlRmVhdHVyZSddLCBbXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL2xvY2FsZWZlYXR1cmVfdGVzdC5qcycsIFsnZ29vZy5pMThuLkxvY2FsZUZlYXR1cmVUZXN0J10sIFsnZ29vZy5pMThuLkxvY2FsZUZlYXR1cmUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vbWVzc2FnZWZvcm1hdC5qcycsIFsnZ29vZy5pMThuLk1lc3NhZ2VGb3JtYXQnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9scycsICdnb29nLmkxOG4ub3JkaW5hbFJ1bGVzJywgJ2dvb2cuaTE4bi5wbHVyYWxSdWxlcyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9tZXNzYWdlZm9ybWF0X3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5NZXNzYWdlRm9ybWF0VGVzdCddLCBbJ2dvb2cuaTE4bi5NZXNzYWdlRm9ybWF0JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hyJywgJ2dvb2cuaTE4bi5wbHVyYWxSdWxlcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9taW1lLmpzJywgWydnb29nLmkxOG4ubWltZScsICdnb29nLmkxOG4ubWltZS5lbmNvZGUnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuaTE4bi51Q2hhciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9taW1lX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5taW1lLmVuY29kZVRlc3QnXSwgWydnb29nLmkxOG4ubWltZS5lbmNvZGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vbnVtYmVyZm9ybWF0LmpzJywgWydnb29nLmkxOG4uTnVtYmVyRm9ybWF0JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXQuQ3VycmVuY3lTdHlsZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0LkZvcm1hdCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5jdXJyZW5jeScsICdnb29nLm1hdGgnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vbnVtYmVyZm9ybWF0X3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRUZXN0J10sIFsnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzJywgJ2dvb2cuaTE4bi5Db21wYWN0TnVtYmVyRm9ybWF0U3ltYm9sc19kZScsICdnb29nLmkxOG4uQ29tcGFjdE51bWJlckZvcm1hdFN5bWJvbHNfZW4nLCAnZ29vZy5pMThuLkNvbXBhY3ROdW1iZXJGb3JtYXRTeW1ib2xzX2ZyJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfRUcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfRUdfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0FVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZpJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZyJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3BsJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3JvJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3VfbnVfbGF0bicsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL251bWJlcmZvcm1hdHN5bWJvbHMuanMnLCBbJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FmJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FtJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0VHX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19heicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19iZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19iZycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ibicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ibl91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYnInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYnMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2EnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2hyJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2N5JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RhJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0FUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0NIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VsJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0FVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0NBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0dCJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0lFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1NHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuX1pBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzXzQxOScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lc19FUycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lc19NWCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lc19VUycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ldCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ldScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mYScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mYV91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmlsJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZyJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZyX0NBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dhJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dsJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dzdycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ndScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19oYXcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaHInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaHUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaHknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaWQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaW4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaXMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaXQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaXcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfamEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2EnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2snLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa20nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa24nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa28nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbW4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbW8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXJfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21zJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX210JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX215JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX215X3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19uYicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19uZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19uZV91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbm8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbm9fTk8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfb3InLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcGEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcGwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfQlInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfUFQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcnUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2snLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2wnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3EnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3InLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3JfTGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zdicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zdycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190YScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190ZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190aCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190bCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190cicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdWsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdXInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdXonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdmknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemgnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfQ04nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfSEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfVFcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfenUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL251bWJlcmZvcm1hdHN5bWJvbHNleHQuanMnLCBbJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzRXh0JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FmX05BJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FmX1pBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FncScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hZ3FfQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYWsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYWtfR0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYW1fRVQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfMDAxJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0FFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0FFX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9CSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9CSF91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfREonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfREpfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0VIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0VSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0VSX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9JTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9JTF91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfSVEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfSVFfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0pPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0pPX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9LTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9LTV91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfS1cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfS1dfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0xCJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX0xCX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9MWScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9NQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9NUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9NUl91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfT00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfT01fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1BTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1BTX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9RQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9RQV91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfU0EnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfU0FfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NEJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NEX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9TTycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9TT191X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfU1MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfU1NfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FyX1NZX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9URCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9URF91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfVE4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfWEInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfWUUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXJfWUVfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FzX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FzX0lOX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hc191X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXNhJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2FzYV9UWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hc3QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXN0X0VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2F6X0N5cmwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYXpfQ3lybF9BWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hel9MYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2F6X0xhdG5fQVonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYmFzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2Jhc19DTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19iZV9CWScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19iZW0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYmVtX1pNJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2JleicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19iZXpfVFonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYmdfQkcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYm0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYm1fTUwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYm5fQkQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYm5fQkRfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2JuX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2JuX0lOX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ibycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ib19DTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ib19JTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19icl9GUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19icngnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYnJ4X0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0N5cmwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfYnNfQ3lybF9CQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ic19MYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2JzX0xhdG5fQkEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2FfQUQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2FfRVMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2FfRlInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2FfSVQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2NwJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NjcF9CRCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19jY3BfQkRfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NjcF9JTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19jY3BfSU5fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NjcF91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2VfUlUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2ViJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NlYl9QSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19jZ2cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2dnX1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2Nocl9VUycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ja2InLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2tiX0lRJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NrYl9JUV91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2tiX0lSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2NrYl9JUl91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfY2tiX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19jc19DWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19jeV9HQicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19kYV9ESycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19kYV9HTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19kYXYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZGF2X0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0JFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0RFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0lUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0xJJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RlX0xVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RqZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19kamVfTkUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZHNiJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2RzYl9ERScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19kdWEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZHVhX0NNJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2R5bycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19keW9fU04nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZHonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZHpfQlQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZHpfQlRfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2R6X3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lYnUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZWJ1X0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VlX0dIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VlX1RHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VsX0NZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VsX0dSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VuXzAwMScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lbl8xNTAnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQUUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQUcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQUknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQVMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQVQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQkInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQkUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQkknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQk0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQlMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQlcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQlonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ0MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ0snLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ1gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fQ1knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fREUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fREcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fREsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRE0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRVInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRkknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRkonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRksnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fRk0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR0QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR0cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR0knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR1UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fR1knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSUwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSU0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSkUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fSk0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fS0knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fS04nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fS1knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTEMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTFInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTFMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTUcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTUgnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVAnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTVknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTkwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTlInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTlUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fTlonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUEcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUEgnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUE4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUFInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUFcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fUlcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0InLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU0wnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU1MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU1gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fU1onLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVEMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVE8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVFQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVFYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVFonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVUcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVU0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVVNfUE9TSVgnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVkMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVkcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVkknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fVlUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fV1MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fWEEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fWk0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW5fWlcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZW9fMDAxJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0FSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0JPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0JSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0JaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0NMJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0NPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0NSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0NVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0RPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0VBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0VDJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0dRJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0dUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0hOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX0lDJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX05JJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1BZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1NWJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1VZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2VzX1ZFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2V0X0VFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2V1X0VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2V3bycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ld29fQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmFfQUYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmFfQUZfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZhX0lSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZhX0lSX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fQkYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmZfTGF0bl9DTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fR00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmZfTGF0bl9HTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX0dXJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fTFInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmZfTGF0bl9NUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX05FJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fTkcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZmZfTGF0bl9TTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mZl9MYXRuX1NOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZpX0ZJJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ZpbF9QSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mbycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mb19ESycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mb19GTycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CSScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CSicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9CTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DRCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DSScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9DTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9ESicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9EWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9GUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HUCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9HUScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9IVCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9LTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9MVScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NQycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NUScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9NVScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9OQycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9ORScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9QRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9QTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9SRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9SVycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9TQycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9TTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9TWScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9URCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9URycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9UTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9WVScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9XRicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mcl9ZVCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mdXInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZnVyX0lUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2Z5JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2Z5X05MJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dhX0lFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dkJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dkX0dCJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dsX0VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2dzd19DSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19nc3dfRlInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZ3N3X0xJJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2d1X0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2d1eicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ndXpfS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZ3YnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfZ3ZfSU0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGFfR0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGFfTkUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGFfTkcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaGF3X1VTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hlX0lMJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hpX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hyX0JBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hyX0hSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2hzYicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19oc2JfREUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaHVfSFUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaHlfQU0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaWEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfaWFfMDAxJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lkX0lEJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lnJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lnX05HJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lpJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lpX0NOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2lzX0lTJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2l0X0NIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2l0X0lUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2l0X1NNJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2l0X1ZBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2phX0pQJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2pnbycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19qZ29fQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfam1jJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ptY19UWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19qdicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19qdl9JRCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rYV9HRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rYWInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2FiX0RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2thbScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rYW1fS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2RlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tkZV9UWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rZWEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2VhX0NWJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tocScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19raHFfTUwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2knLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2lfS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2tfS1onLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2tqJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tral9DTScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rbCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rbF9HTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rbG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa2xuX0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2ttX0tIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tuX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tvX0tQJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tvX0tSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tvaycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rb2tfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3MnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3NfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3NfSU5fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tzX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rc2InLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3NiX1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tzZicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rc2ZfQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfa3NoJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2tzaF9ERScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rdScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rdV9UUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rdycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19rd19HQicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19reV9LRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19sYWcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbGFnX1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xiJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xiX0xVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xnJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xnX1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xrdCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19sa3RfVVMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG5fQU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG5fQ0QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG5fQ0YnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG5fQ0cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbG9fTEEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHJjJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xyY19JUScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19scmNfSVFfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xyY19JUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19scmNfSVJfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2xyY191X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHRfTFQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHVfQ0QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHVvJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2x1b19LRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19sdXknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbHV5X0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX2x2X0xWJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21hcycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tYXNfS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWFzX1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21lcicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tZXJfS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWZlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21mZV9NVScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tZycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tZ19NRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tZ2gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWdoX01aJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21nbycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tZ29fQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWlfTlonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWtfTUsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbWxfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbW5fTU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXJfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXJfSU5fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21zX0JOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21zX01ZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX21zX1NHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX210X01UJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX211YScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tdWFfQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXlfTU0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXlfTU1fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX216bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tem5fSVInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbXpuX0lSX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19tem5fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25hcScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19uYXFfTkEnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmJfTk8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmJfU0onLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmRfWlcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmRzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25kc19ERScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19uZHNfTkwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmVfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbmVfSU5fdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25lX05QJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25lX05QX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9BVycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9CRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9CUScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9DVycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9OTCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9TUicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubF9TWCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubWcnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbm1nX0NNJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25uJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25uX05PJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX25uaCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ubmhfQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbnVzJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX251c19TUycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ueW4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfbnluX1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29tJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29tX0VUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29tX0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29yX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29zJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29zX0dFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX29zX1JVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3BhX0FyYWInLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcGFfQXJhYl9QSycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19wYV9BcmFiX1BLX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19wYV9BcmFiX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19wYV9HdXJ1JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3BhX0d1cnVfSU4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcGxfUEwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHNfQUYnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHNfQUZfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3BzX1BLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3BzX1BLX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19wc191X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfQU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfQ0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfQ1YnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfR1EnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfR1cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfTFUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfTU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfTVonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfU1QnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcHRfVEwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcXUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcXVfQk8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcXVfRUMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcXVfUEUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm0nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm1fQ0gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm5fQkknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm9fTUQnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm9fUk8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcm9mJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3JvZl9UWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9CWScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9LRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9LWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9NRCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9SVScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydV9VQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19ydycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19yd19SVycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19yd2snLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfcndrX1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NhaCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zYWhfUlUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2FxJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NhcV9LRScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zYnAnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2JwX1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NkJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NkX1BLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NkX1BLX3VfbnVfbGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zZF91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2VfRkknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2VfTk8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2VfU0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2VoJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NlaF9NWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zZXMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc2VzX01MJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NnJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NnX0NGJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NoaScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zaGlfTGF0bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zaGlfTGF0bl9NQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zaGlfVGZuZycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zaGlfVGZuZ19NQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zaV9MSycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19za19TSycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zbF9TSScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zbW4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc21uX0ZJJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NuX1pXJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NvJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NvX0RKJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NvX0VUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NvX0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NvX1NPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NxX0FMJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NxX01LJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NxX1hLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3JfQ3lybF9CQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zcl9DeXJsX01FJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0N5cmxfUlMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3JfQ3lybF9YSycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zcl9MYXRuX0JBJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3NyX0xhdG5fTUUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfc3JfTGF0bl9SUycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19zcl9MYXRuX1hLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N2X0FYJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N2X0ZJJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N2X1NFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N3X0NEJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N3X0tFJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N3X1RaJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3N3X1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RhX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RhX0xLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RhX01ZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RhX1NHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RlX0lOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RlbycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190ZW9fS0UnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdGVvX1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RnJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RnX1RKJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RoX1RIJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RpJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RpX0VSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RpX0VUJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RrJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RrX1RNJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RvJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RvX1RPJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RyX0NZJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3RyX1RSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3R0JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3R0X1JVJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3R3cScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc190d3FfTkUnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdHptJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3R6bV9NQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191ZycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191Z19DTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191a19VQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191cl9JTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191cl9JTl91X251X2xhdG4nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdXJfUEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdXpfQXJhYicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191el9BcmFiX0FGJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0FyYWJfQUZfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0FyYWJfdV9udV9sYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0N5cmwnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdXpfQ3lybF9VWicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc191el9MYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3V6X0xhdG5fVVonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdmFpJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaV9MYXRuJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaV9MYXRuX0xSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaV9WYWlpJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3ZhaV9WYWlpX0xSJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3ZpX1ZOJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3Z1bicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc192dW5fVFonLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfd2FlJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3dhZV9DSCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc193bycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc193b19TTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc194aCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc194aF9aQScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc194b2cnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfeG9nX1VHJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3lhdicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc195YXZfQ00nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfeWknLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfeWlfMDAxJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3lvJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3lvX0JKJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3lvX05HJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3l1ZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc195dWVfSGFucycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc195dWVfSGFuc19DTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc195dWVfSGFudCcsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc195dWVfSGFudF9ISycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc196Z2gnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemdoX01BJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3poX0hhbnMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfSGFuc19DTicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW5zX0hLJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3poX0hhbnNfTU8nLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfSGFuc19TRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50JywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3poX0hhbnRfSEsnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfemhfSGFudF9NTycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc196aF9IYW50X1RXJywgJ2dvb2cuaTE4bi5OdW1iZXJGb3JtYXRTeW1ib2xzX3p1X1pBJ10sIFsnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHMnLCAnZ29vZy5pMThuLk51bWJlckZvcm1hdFN5bWJvbHNfdV9udV9sYXRuJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL29yZGluYWxydWxlcy5qcycsIFsnZ29vZy5pMThuLm9yZGluYWxSdWxlcyddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL3BsdXJhbHJ1bGVzLmpzJywgWydnb29nLmkxOG4ucGx1cmFsUnVsZXMnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9wbHVyYWxydWxlc190ZXN0LmpzJywgWydnb29nLmkxOG4ucGx1cmFsUnVsZXNUZXN0J10sIFsnZ29vZy5pMThuLnBsdXJhbFJ1bGVzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL3JlbGF0aXZlZGF0ZXRpbWVmb3JtYXQuanMnLCBbJ2dvb2cuaTE4bi5SZWxhdGl2ZURhdGVUaW1lRm9ybWF0J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaTE4bi5Mb2NhbGVGZWF0dXJlJywgJ2dvb2cuaTE4bi5NZXNzYWdlRm9ybWF0JywgJ2dvb2cuaTE4bi5yZWxhdGl2ZURhdGVUaW1lU3ltYm9scyddLCB7J2xhbmcnOiAnZXM1JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vcmVsYXRpdmVkYXRldGltZWZvcm1hdF90ZXN0LmpzJywgWydnb29nLmkxOG4uUmVsYXRpdmVEYXRlVGltZUZvcm1hdFRlc3QnXSwgWydnb29nLmkxOG4uTG9jYWxlRmVhdHVyZScsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19hcl9FRycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lbicsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19lcycsICdnb29nLmkxOG4uTnVtYmVyRm9ybWF0U3ltYm9sc19mYScsICdnb29nLmkxOG4uUmVsYXRpdmVEYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4ucmVsYXRpdmVEYXRlVGltZVN5bWJvbHMnLCAnZ29vZy5pMThuLnJlbGF0aXZlRGF0ZVRpbWVTeW1ib2xzRXh0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL3JlbGF0aXZlZGF0ZXRpbWVzeW1ib2xzLmpzJywgWydnb29nLmkxOG4ucmVsYXRpdmVEYXRlVGltZVN5bWJvbHMnXSwgW10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi9yZWxhdGl2ZWRhdGV0aW1lc3ltYm9sc2V4dC5qcycsIFsnZ29vZy5pMThuLnJlbGF0aXZlRGF0ZVRpbWVTeW1ib2xzRXh0J10sIFsnZ29vZy5pMThuLnJlbGF0aXZlRGF0ZVRpbWVTeW1ib2xzJ10sIHsnbGFuZyc6ICdlczUnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi90aW1lem9uZS5qcycsIFsnZ29vZy5pMThuLlRpbWVab25lJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRhdGUuRGF0ZUxpa2UnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdGltZXpvbmVfdGVzdC5qcycsIFsnZ29vZy5pMThuLlRpbWVab25lVGVzdCddLCBbJ2dvb2cuaTE4bi5UaW1lWm9uZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi91Y2hhci5qcycsIFsnZ29vZy5pMThuLnVDaGFyJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXIvbG9jYWxuYW1lZmV0Y2hlci5qcycsIFsnZ29vZy5pMThuLnVDaGFyLkxvY2FsTmFtZUZldGNoZXInXSwgWydnb29nLmkxOG4udUNoYXIuTmFtZUZldGNoZXInLCAnZ29vZy5pMThuLnVDaGFyTmFtZXMnLCAnZ29vZy5sb2cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXIvbG9jYWxuYW1lZmV0Y2hlcl90ZXN0LmpzJywgWydnb29nLmkxOG4udUNoYXIuTG9jYWxOYW1lRmV0Y2hlclRlc3QnXSwgWydnb29nLmkxOG4udUNoYXIuTG9jYWxOYW1lRmV0Y2hlcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXIvbmFtZWZldGNoZXIuanMnLCBbJ2dvb2cuaTE4bi51Q2hhci5OYW1lRmV0Y2hlciddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXIvcmVtb3RlbmFtZWZldGNoZXIuanMnLCBbJ2dvb2cuaTE4bi51Q2hhci5SZW1vdGVOYW1lRmV0Y2hlciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLlVyaScsICdnb29nLmV2ZW50cycsICdnb29nLmkxOG4udUNoYXInLCAnZ29vZy5pMThuLnVDaGFyLk5hbWVGZXRjaGVyJywgJ2dvb2cubG9nJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5YaHJJbyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaTE4bi91Y2hhci9yZW1vdGVuYW1lZmV0Y2hlcl90ZXN0LmpzJywgWydnb29nLmkxOG4udUNoYXIuUmVtb3RlTmFtZUZldGNoZXJUZXN0J10sIFsnZ29vZy5pMThuLnVDaGFyLlJlbW90ZU5hbWVGZXRjaGVyJywgJ2dvb2cubmV0LlhocklvJywgJ2dvb2cudGVzdGluZy5uZXQuWGhySW8nLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdpMThuL3VjaGFyX3Rlc3QuanMnLCBbJ2dvb2cuaTE4bi51Q2hhclRlc3QnXSwgWydnb29nLmkxOG4udUNoYXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXJuYW1lcy5qcycsIFsnZ29vZy5pMThuLnVDaGFyTmFtZXMnXSwgWydnb29nLmkxOG4udUNoYXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2kxOG4vdWNoYXJuYW1lc190ZXN0LmpzJywgWydnb29nLmkxOG4udUNoYXJOYW1lc1Rlc3QnXSwgWydnb29nLmkxOG4udUNoYXJOYW1lcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaXRlci9lczYuanMnLCBbJ2dvb2cuaXRlci5lczYnXSwgWydnb29nLml0ZXIuSXRlcmFibGUnLCAnZ29vZy5pdGVyLkl0ZXJhdG9yJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaXRlci9lczZfdGVzdC5qcycsIFsnZ29vZy5pdGVyLmVzNlRlc3QnXSwgWydnb29nLml0ZXInLCAnZ29vZy5pdGVyLmVzNicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaXRlci9pdGVyLmpzJywgWydnb29nLml0ZXInLCAnZ29vZy5pdGVyLkl0ZXJhYmxlJywgJ2dvb2cuaXRlci5JdGVyYXRvcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubWF0aCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnaXRlci9pdGVyX3Rlc3QuanMnLCBbJ2dvb2cuaXRlclRlc3QnXSwgWydnb29nLml0ZXInLCAnZ29vZy5pdGVyLkl0ZXJhdG9yJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdqc29uL2h5YnJpZC5qcycsIFsnZ29vZy5qc29uLmh5YnJpZCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmpzb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2pzb24vaHlicmlkX3Rlc3QuanMnLCBbJ2dvb2cuanNvbi5oeWJyaWRUZXN0J10sIFsnZ29vZy5qc29uJywgJ2dvb2cuanNvbi5oeWJyaWQnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdqc29uL2pzb24uanMnLCBbJ2dvb2cuanNvbicsICdnb29nLmpzb24uUmVwbGFjZXInLCAnZ29vZy5qc29uLlJldml2ZXInLCAnZ29vZy5qc29uLlNlcmlhbGl6ZXInXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnanNvbi9qc29uX3BlcmYuanMnLCBbJ2dvb2cuanNvblBlcmYnXSwgWydnb29nLmRvbScsICdnb29nLmpzb24nLCAnZ29vZy5tYXRoJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5QZXJmb3JtYW5jZVRhYmxlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2pzb24vanNvbl90ZXN0LmpzJywgWydnb29nLmpzb25UZXN0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5qc29uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdqc29uL2pzb25hYmxlLmpzJywgWydnb29nLmpzb24uSnNvbmFibGUnXSwgW10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnanNvbi9uYXRpdmVqc29ucHJvY2Vzc29yLmpzJywgWydnb29nLmpzb24uTmF0aXZlSnNvblByb2Nlc3NvciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmpzb24uUHJvY2Vzc29yJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdqc29uL3Byb2Nlc3Nvci5qcycsIFsnZ29vZy5qc29uLlByb2Nlc3NvciddLCBbJ2dvb2cuc3RyaW5nLlBhcnNlcicsICdnb29nLnN0cmluZy5TdHJpbmdpZmllciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnanNvbi9wcm9jZXNzb3JfdGVzdC5qcycsIFsnZ29vZy5qc29uLnByb2Nlc3NvclRlc3QnXSwgWydnb29nLmpzb24uTmF0aXZlSnNvblByb2Nlc3NvcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9jb2xsZWN0aW9ucy9pdGVyYWJsZXMuanMnLCBbJ2dvb2cubGFicy5jb2xsZWN0aW9ucy5pdGVyYWJsZXMnXSwgW10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9jb2xsZWN0aW9ucy9pdGVyYWJsZXNfdGVzdC5qcycsIFsnZ29vZy5sYWJzLml0ZXJhYmxlVGVzdCddLCBbJ2dvb2cubGFicy5jb2xsZWN0aW9ucy5pdGVyYWJsZXMnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2RvbS9wYWdldmlzaWJpbGl0eW1vbml0b3IuanMnLCBbJ2dvb2cubGFicy5kb20uUGFnZVZpc2liaWxpdHlFdmVudCcsICdnb29nLmxhYnMuZG9tLlBhZ2VWaXNpYmlsaXR5TW9uaXRvcicsICdnb29nLmxhYnMuZG9tLlBhZ2VWaXNpYmlsaXR5U3RhdGUnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS52ZW5kb3InLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubWVtb2l6ZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9kb20vcGFnZXZpc2liaWxpdHltb25pdG9yX3Rlc3QuanMnLCBbJ2dvb2cubGFicy5kb20uUGFnZVZpc2liaWxpdHlNb25pdG9yVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubGFicy5kb20uUGFnZVZpc2liaWxpdHlNb25pdG9yJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvZXZlbnRzL25vbmRpc3Bvc2FibGVldmVudHRhcmdldC5qcycsIFsnZ29vZy5sYWJzLmV2ZW50cy5Ob25EaXNwb3NhYmxlRXZlbnRUYXJnZXQnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5MaXN0ZW5hYmxlJywgJ2dvb2cuZXZlbnRzLkxpc3RlbmVyTWFwJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2V2ZW50cy9ub25kaXNwb3NhYmxlZXZlbnR0YXJnZXRfdGVzdC5qcycsIFsnZ29vZy5sYWJzLmV2ZW50cy5Ob25EaXNwb3NhYmxlRXZlbnRUYXJnZXRUZXN0J10sIFsnZ29vZy5ldmVudHMuTGlzdGVuYWJsZScsICdnb29nLmV2ZW50cy5ldmVudFRhcmdldFRlc3RlcicsICdnb29nLmxhYnMuZXZlbnRzLk5vbkRpc3Bvc2FibGVFdmVudFRhcmdldCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9ldmVudHMvbm9uZGlzcG9zYWJsZWV2ZW50dGFyZ2V0X3ZpYV9nb29nZXZlbnRzX3Rlc3QuanMnLCBbJ2dvb2cubGFicy5ldmVudHMuTm9uRGlzcG9zYWJsZUV2ZW50VGFyZ2V0R29vZ0V2ZW50c1Rlc3QnXSwgWydnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5ldmVudFRhcmdldFRlc3RlcicsICdnb29nLmxhYnMuZXZlbnRzLk5vbkRpc3Bvc2FibGVFdmVudFRhcmdldCcsICdnb29nLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvZXZlbnRzL3RvdWNoLmpzJywgWydnb29nLmxhYnMuZXZlbnRzLnRvdWNoJywgJ2dvb2cubGFicy5ldmVudHMudG91Y2guVG91Y2hEYXRhJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2V2ZW50cy90b3VjaF90ZXN0LmpzJywgWydnb29nLmxhYnMuZXZlbnRzLnRvdWNoVGVzdCddLCBbJ2dvb2cubGFicy5ldmVudHMudG91Y2gnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvZm9ybWF0L2Nzdi5qcycsIFsnZ29vZy5sYWJzLmZvcm1hdC5jc3YnLCAnZ29vZy5sYWJzLmZvcm1hdC5jc3YuUGFyc2VFcnJvcicsICdnb29nLmxhYnMuZm9ybWF0LmNzdi5Ub2tlbiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcubmV3bGluZXMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvZm9ybWF0L2Nzdl90ZXN0LmpzJywgWydnb29nLmxhYnMuZm9ybWF0LmNzdlRlc3QnXSwgWydnb29nLmxhYnMuZm9ybWF0LmNzdicsICdnb29nLmxhYnMuZm9ybWF0LmNzdi5QYXJzZUVycm9yJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2kxOG4vbGlzdGZvcm1hdC5qcycsIFsnZ29vZy5sYWJzLmkxOG4uR2VuZGVySW5mbycsICdnb29nLmxhYnMuaTE4bi5HZW5kZXJJbmZvLkdlbmRlcicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2kxOG4vbGlzdGZvcm1hdF90ZXN0LmpzJywgWydnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0VGVzdCddLCBbJ2dvb2cubGFicy5pMThuLkdlbmRlckluZm8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9scycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19lbCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19lbicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mcicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tbCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc196dScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9pMThuL2xpc3RzeW1ib2xzLmpzJywgWydnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9scycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hZicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hbScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hcicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hcl9EWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hcl9FRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19heicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19iZScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19iZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ibicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19icicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19icycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jYScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jaHInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY3MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY3knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfQVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZWwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQVUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ0EnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR0InLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSUUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSU4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVVMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fWkEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZXMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZXNfNDE5JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0VTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX01YJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1VTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2V0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2V1JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZhJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZpbCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mcicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mcl9DQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nYScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nbCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nc3cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZ3UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfaGF3JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hlJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hyJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2h1JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2h5JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2lkJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2luJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2lzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2l0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2l3JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2phJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2thJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2trJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ttJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tuJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t5JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2xuJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2xvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2x0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2x2JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21rJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21sJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21uJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21vJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21yJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21zJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX210JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX215JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25iJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25lJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25sJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25vJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25vX05PJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29yJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3BhJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3BsJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3B0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3B0X0JSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3B0X1BUJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3JvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3J1JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NoJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NrJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NsJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NyJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NyX0xhdG4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc3YnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc3cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdGEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdGUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdGgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdGwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdHInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdWsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdmknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfQ04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfSEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfVFcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfenUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL2kxOG4vbGlzdHN5bWJvbHNleHQuanMnLCBbJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzRXh0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FmX05BJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FmX1pBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FncScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hZ3FfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYWsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYWtfR0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYW1fRVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYXJfMDAxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0FFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0JIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0RKJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0VIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0VSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0lMJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0lRJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0pPJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0tNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0tXJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0xCJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX0xZJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX01BJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX01SJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX09NJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1BTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1FBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1NBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1NEJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1NPJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1NTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1NZJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1REJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1ROJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1hCJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FyX1lFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FzX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FzYScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hc2FfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYXN0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2FzdF9FUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hel9DeXJsJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2F6X0N5cmxfQVonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYXpfTGF0bicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19hel9MYXRuX0FaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JhcycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19iYXNfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYmVfQlknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYmVtJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JlbV9aTScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19iZXonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYmV6X1RaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JnX0JHJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JtJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JtX01MJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JuX0JEJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JuX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JvX0NOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JvX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JyX0ZSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JyeCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19icnhfSU4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYnNfQ3lybCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ic19DeXJsX0JBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2JzX0xhdG4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfYnNfTGF0bl9CQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jYV9BRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jYV9FUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jYV9GUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jYV9JVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jY3AnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY2NwX0JEJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2NjcF9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jZScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jZV9SVScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jZWInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY2ViX1BIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2NnZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19jZ2dfVUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY2hyX1VTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2NrYicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ja2JfSVEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfY2tiX0lSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2NzX0NaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2N5X0dCJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2RhX0RLJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2RhX0dMJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2RhdicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19kYXZfS0UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfQkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfREUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfSVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfTEknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGVfTFUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZGplJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2RqZV9ORScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19kc2InLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZHNiX0RFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2R1YScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19kdWFfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZHlvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2R5b19TTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19keicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19kel9CVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19lYnUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZWJ1X0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VlJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VlX0dIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VlX1RHJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VsX0NZJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VsX0dSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VuXzAwMScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19lbl8xNTAnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQUUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQUknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQVMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQkInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQkknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQk0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQlMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQlcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQlonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ0MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ0snLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ1gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fQ1knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fREUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fREcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fREsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRE0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRVInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRkknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRkonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRksnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fRk0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR0QnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR0cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR0knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR1UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fR1knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSUwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSU0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSU8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fSk0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fS0UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fS0knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fS04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fS1knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTEMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTFInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTFMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTUgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTU8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVAnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTVknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTkEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTkYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTkcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTkwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTlInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTlUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fTlonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUEcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUEgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUE4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUFInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUFcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fUlcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0InLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0QnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU0wnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU1MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU1gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fU1onLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVEMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVE8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVFQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVFYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVU0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVVNfUE9TSVgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVkMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVkcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVkknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fVlUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fV1MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fWEEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fWk0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW5fWlcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZW9fMDAxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0FSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0JPJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0JSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0JaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0NMJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0NPJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0NSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0NVJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0RPJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0VBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0VDJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0dRJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0dUJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0hOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX0lDJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX05JJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1BBJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1BFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1BIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1BSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1BZJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1NWJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1VZJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2VzX1ZFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2V0X0VFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2V1X0VTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2V3bycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ld29fQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmFfQUYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmFfSVInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmZfTGF0bicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mZl9MYXRuX0JGJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmZfTGF0bl9HSCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mZl9MYXRuX0dNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fR04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmZfTGF0bl9HVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mZl9MYXRuX0xSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fTVInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmZfTGF0bl9ORScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19mZl9MYXRuX05HJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ZmX0xhdG5fU0wnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZmZfTGF0bl9TTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19maV9GSScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19maWxfUEgnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZm8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZm9fREsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZm9fRk8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQkYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQkknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQkonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQkwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ0QnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ0YnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ0cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ0knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfREonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfRFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfRlInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfR0EnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfR0YnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfR04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfR1AnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfR1EnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfSFQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfS00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTFUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTUEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTUMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTUYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTUwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTVEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTVInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTVUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTkMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfTkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfUEYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfUE0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfUkUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfUlcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfU0MnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfU04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfU1knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfVEQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfVEcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfVE4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfVlUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfV0YnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnJfWVQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZnVyJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2Z1cl9JVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19meScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19meV9OTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nYV9JRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nZCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nZF9HQicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nbF9FUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19nc3dfQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZ3N3X0ZSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2dzd19MSScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ndV9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ndXonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfZ3V6X0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2d2JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2d2X0lNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hhJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hhX0dIJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hhX05FJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hhX05HJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2hhd19VUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19oZV9JTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19oaV9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ocl9CQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ocl9IUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19oc2InLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfaHNiX0RFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2h1X0hVJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2h5X0FNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2lhJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2lhXzAwMScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pZF9JRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pZ19ORycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19paScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19paV9DTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pc19JUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pdF9DSCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pdF9JVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pdF9TTScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19pdF9WQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19qYV9KUCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19qZ28nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfamdvX0NNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2ptYycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19qbWNfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfanYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfanZfSUQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2FfR0UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2FiJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2thYl9EWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rYW0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2FtX0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tkZScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rZGVfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2VhJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tlYV9DVicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19raHEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2hxX01MJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tpX0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2trX0taJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2traicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ra2pfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2wnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2xfR0wnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa2xuJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tsbl9LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rbV9LSCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rbl9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rb19LUCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rb19LUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rb2snLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa29rX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tzX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tzYicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rc2JfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa3NmJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2tzZl9DTScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19rc2gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfa3NoX0RFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t1JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t1X1RSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t3JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t3X0dCJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2t5X0tHJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2xhZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sYWdfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbGInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbGJfTFUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbGcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbGdfVUcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbGt0JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2xrdF9VUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sbl9BTycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sbl9DRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sbl9DRicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sbl9DRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sb19MQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19scmMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbHJjX0lRJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2xyY19JUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sdF9MVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sdScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sdV9DRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sdW8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbHVvX0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX2x1eScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19sdXlfS0UnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbHZfTFYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbWFzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21hc19LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tYXNfVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbWVyJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21lcl9LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tZmUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbWZlX01VJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21nJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21nX01HJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21naCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tZ2hfTVonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbWdvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX21nb19DTScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19taScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19taV9OWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ta19NSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tbF9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tbl9NTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tcl9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tc19CTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tc19NWScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tc19TRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tdF9NVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tdWEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbXVhX0NNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX215X01NJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX216bicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19tem5fSVInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbmFxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25hcV9OQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uYl9OTycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uYl9TSicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uZCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uZF9aVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uZHMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbmRzX0RFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25kc19OTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uZV9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19uZV9OUCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9BVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9CRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9CUScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9DVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9OTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9TUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubF9TWCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubWcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbm1nX0NNJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25uJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25uX05PJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX25uaCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ubmhfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbnVzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX251c19TUycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ueW4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfbnluX1VHJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29tJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29tX0VUJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29tX0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29yX0lOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29zJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29zX0dFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX29zX1JVJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3BhX0FyYWInLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcGFfQXJhYl9QSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19wYV9HdXJ1JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3BhX0d1cnVfSU4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcGxfUEwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHNfQUYnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHNfUEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfQU8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfQ1YnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfR1EnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfR1cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfTFUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfTU8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfTVonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfU1QnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcHRfVEwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcXUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcXVfQk8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcXVfRUMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcXVfUEUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm0nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm1fQ0gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm5fQkknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm9fTUQnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm9fUk8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcm9mJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3JvZl9UWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9CWScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9LRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9LWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9NRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9SVScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydV9VQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19ydycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19yd19SVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19yd2snLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfcndrX1RaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NhaCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zYWhfUlUnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2FxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NhcV9LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zYnAnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2JwX1RaJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NkJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NkX1BLJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NlJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NlX0ZJJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NlX05PJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NlX1NFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NlaCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zZWhfTVonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2VzJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3Nlc19NTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zZ19DRicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zaGknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2hpX0xhdG4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2hpX0xhdG5fTUEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2hpX1RmbmcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2hpX1RmbmdfTUEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2lfTEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2tfU0snLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc2xfU0knLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc21uJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3Ntbl9GSScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zbicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zbl9aVycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zbycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zb19ESicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zb19FVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zb19LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zb19TTycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcV9BTCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcV9NSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcV9YSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcl9DeXJsJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NyX0N5cmxfQkEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc3JfQ3lybF9NRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcl9DeXJsX1JTJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NyX0N5cmxfWEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc3JfTGF0bl9CQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zcl9MYXRuX01FJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3NyX0xhdG5fUlMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfc3JfTGF0bl9YSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zdl9BWCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zdl9GSScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zdl9TRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zd19DRCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zd19LRScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zd19UWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc19zd19VRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190YV9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190YV9MSycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190YV9NWScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190YV9TRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190ZV9JTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190ZW8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdGVvX0tFJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3Rlb19VRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190ZycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190Z19USicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190aF9USCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190aScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190aV9FUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190aV9FVCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190aycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190a19UTScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190bycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190b19UTycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190cl9DWScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190cl9UUicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190dCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190dF9SVScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190d3EnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdHdxX05FJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3R6bScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc190em1fTUEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdWcnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdWdfQ04nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdWtfVUEnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXJfSU4nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXJfUEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXpfQXJhYicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc191el9BcmFiX0FGJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3V6X0N5cmwnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdXpfQ3lybF9VWicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc191el9MYXRuJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3V6X0xhdG5fVVonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfdmFpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3ZhaV9MYXRuJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3ZhaV9MYXRuX0xSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3ZhaV9WYWlpJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3ZhaV9WYWlpX0xSJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3ZpX1ZOJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3Z1bicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc192dW5fVFonLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfd2FlJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3dhZV9DSCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc193bycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc193b19TTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc194aCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc194aF9aQScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc194b2cnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfeG9nX1VHJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3lhdicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc195YXZfQ00nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfeWknLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfeWlfMDAxJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3lvJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3lvX0JKJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3lvX05HJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3l1ZScsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc195dWVfSGFucycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc195dWVfSGFuc19DTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc195dWVfSGFudCcsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc195dWVfSGFudF9ISycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc196Z2gnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemdoX01BJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3poX0hhbnMnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfSGFuc19DTicsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc196aF9IYW5zX0hLJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3poX0hhbnNfTU8nLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfSGFuc19TRycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc196aF9IYW50JywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3poX0hhbnRfSEsnLCAnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHNfemhfSGFudF9NTycsICdnb29nLmxhYnMuaTE4bi5MaXN0Rm9ybWF0U3ltYm9sc196aF9IYW50X1RXJywgJ2dvb2cubGFicy5pMThuLkxpc3RGb3JtYXRTeW1ib2xzX3p1X1pBJ10sIFsnZ29vZy5sYWJzLmkxOG4uTGlzdEZvcm1hdFN5bWJvbHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbW9jay9tb2NrLmpzJywgWydnb29nLmxhYnMubW9jaycsICdnb29nLmxhYnMubW9jay5UaW1lb3V0RXJyb3InLCAnZ29vZy5sYWJzLm1vY2suVmVyaWZpY2F0aW9uRXJyb3InXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5sYWJzLm1vY2sudGltZW91dCcsICdnb29nLmxhYnMubW9jay50aW1lb3V0LlRpbWVvdXRNb2RlJywgJ2dvb2cubGFicy5tb2NrLnZlcmlmaWNhdGlvbicsICdnb29nLmxhYnMubW9jay52ZXJpZmljYXRpb24uQmFzZVZlcmlmaWNhdGlvbk1vZGUnLCAnZ29vZy5sYWJzLm1vY2sudmVyaWZpY2F0aW9uLlZlcmlmaWNhdGlvbk1vZGUnLCAnZ29vZy5vYmplY3QnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL21vY2svbW9ja190ZXN0LmpzJywgWydnb29nLmxhYnMubW9ja1Rlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubGFicy5tb2NrJywgJ2dvb2cubGFicy5tb2NrLlRpbWVvdXRFcnJvcicsICdnb29nLmxhYnMubW9jay5WZXJpZmljYXRpb25FcnJvcicsICdnb29nLmxhYnMubW9jay50aW1lb3V0JywgJ2dvb2cubGFicy5tb2NrLnZlcmlmaWNhdGlvbicsICdnb29nLmxhYnMudGVzdGluZy5Bbnl0aGluZ01hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuR3JlYXRlclRoYW5NYXRjaGVyJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnXSwgeydsYW5nJzogJ2VzOCd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL21vY2svdGltZW91dG1vZGUuanMnLCBbJ2dvb2cubGFicy5tb2NrLnRpbWVvdXQnLCAnZ29vZy5sYWJzLm1vY2sudGltZW91dC5UaW1lb3V0TW9kZSddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL21vY2svdmVyaWZpY2F0aW9ubW9kZS5qcycsIFsnZ29vZy5sYWJzLm1vY2sudmVyaWZpY2F0aW9uJywgJ2dvb2cubGFicy5tb2NrLnZlcmlmaWNhdGlvbi5CYXNlVmVyaWZpY2F0aW9uTW9kZScsICdnb29nLmxhYnMubW9jay52ZXJpZmljYXRpb24uVmVyaWZpY2F0aW9uTW9kZSddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL21vY2svdmVyaWZpY2F0aW9ubW9kZV90ZXN0LmpzJywgWydnb29nLmxhYnMubW9jay5WZXJpZmljYXRpb25Nb2RlVGVzdCddLCBbJ2dvb2cubGFicy5tb2NrLnZlcmlmaWNhdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvaW1hZ2UuanMnLCBbJ2dvb2cubGFicy5uZXQuaW1hZ2UnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvaW1hZ2VfdGVzdC5qcycsIFsnZ29vZy5sYWJzLm5ldC5pbWFnZVRlc3QnXSwgWydnb29nLmxhYnMubmV0LmltYWdlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwuanMnLCBbJ2dvb2cubmV0LldlYkNoYW5uZWwnXSwgWydnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5MaXN0ZW5hYmxlJywgJ2dvb2cubmV0LlhtbEh0dHBGYWN0b3J5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL2Jhc2V0ZXN0Y2hhbm5lbC5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkJhc2VUZXN0Q2hhbm5lbCddLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5DaGFubmVsJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5DaGFubmVsUmVxdWVzdCcsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbERlYnVnJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMnLCAnZ29vZy5uZXQuV2ViQ2hhbm5lbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC9jaGFubmVsLmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuQ2hhbm5lbCddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL2NoYW5uZWxyZXF1ZXN0LmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuQ2hhbm5lbFJlcXVlc3QnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYXN5bmMuVGhyb3R0bGUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5DaGFubmVsJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XZWJDaGFubmVsRGVidWcnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLmVudmlyb25tZW50JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMnLCAnZ29vZy5uZXQuRXJyb3JDb2RlJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5XZWJDaGFubmVsJywgJ2dvb2cubmV0LlhtbEh0dHAnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvY2hhbm5lbHJlcXVlc3RfdGVzdC5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLmNoYW5uZWxSZXF1ZXN0VGVzdCddLCBbJ2dvb2cuVXJpJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5DaGFubmVsUmVxdWVzdCcsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbERlYnVnJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLnJlcXVlc3RTdGF0cy5TZXJ2ZXJSZWFjaGFiaWxpdHknLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcubmV0LlhocklvJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC9jb25uZWN0aW9uc3RhdGUuanMnLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5Db25uZWN0aW9uU3RhdGUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL2Vudmlyb25tZW50LmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuZW52aXJvbm1lbnQnXSwgWydnb29nLnVzZXJBZ2VudCddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvZW52aXJvbm1lbnRfdGVzdC5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkVudmlyb25tZW50VGVzdCddLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5lbnZpcm9ubWVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC9mb3J3YXJkY2hhbm5lbHJlcXVlc3Rwb29sLmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuRm9yd2FyZENoYW5uZWxSZXF1ZXN0UG9vbCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkNoYW5uZWxSZXF1ZXN0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XaXJlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RydWN0cy5TZXQnXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL2ZvcndhcmRjaGFubmVscmVxdWVzdHBvb2xfdGVzdC5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkZvcndhcmRDaGFubmVsUmVxdWVzdFBvb2xUZXN0J10sIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkNoYW5uZWxSZXF1ZXN0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5Gb3J3YXJkQ2hhbm5lbFJlcXVlc3RQb29sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL25ldHV0aWxzLmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwubmV0VXRpbHMnXSwgWydnb29nLlVyaScsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbERlYnVnJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL3JlcXVlc3RzdGF0cy5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLnJlcXVlc3RTdGF0cycsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwucmVxdWVzdFN0YXRzLkV2ZW50JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMuU2VydmVyUmVhY2hhYmlsaXR5JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMuU2VydmVyUmVhY2hhYmlsaXR5RXZlbnQnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLnJlcXVlc3RTdGF0cy5TdGF0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMuU3RhdEV2ZW50JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMuVGltaW5nRXZlbnQnXSwgWydnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC93ZWJjaGFubmVsYmFzZS5qcycsIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldlYkNoYW5uZWxCYXNlJ10sIFsnZ29vZy5VcmknLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5ydW4nLCAnZ29vZy5qc29uJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5CYXNlVGVzdENoYW5uZWwnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkNoYW5uZWwnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkNoYW5uZWxSZXF1ZXN0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5Db25uZWN0aW9uU3RhdGUnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkZvcndhcmRDaGFubmVsUmVxdWVzdFBvb2wnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldlYkNoYW5uZWxEZWJ1ZycsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2lyZScsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2lyZVY4JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5uZXRVdGlscycsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwucmVxdWVzdFN0YXRzJywgJ2dvb2cubmV0LldlYkNoYW5uZWwnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWG1sSHR0cEZhY3RvcnknLCAnZ29vZy5uZXQucnBjLkh0dHBDb3JzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RydWN0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC93ZWJjaGFubmVsYmFzZV90ZXN0LmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwud2ViQ2hhbm5lbEJhc2VUZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuanNvbicsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuQ2hhbm5lbFJlcXVlc3QnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkZvcndhcmRDaGFubmVsUmVxdWVzdFBvb2wnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldlYkNoYW5uZWxCYXNlJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XZWJDaGFubmVsQmFzZVRyYW5zcG9ydCcsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbERlYnVnJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XaXJlJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5uZXRVdGlscycsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwucmVxdWVzdFN0YXRzJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5yZXF1ZXN0U3RhdHMuU3RhdCcsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvd2ViY2hhbm5lbGJhc2V0cmFuc3BvcnQuanMnLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XZWJDaGFubmVsQmFzZVRyYW5zcG9ydCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmpzb24nLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLkNoYW5uZWxSZXF1ZXN0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XZWJDaGFubmVsQmFzZScsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2lyZScsICdnb29nLmxvZycsICdnb29nLm5ldC5XZWJDaGFubmVsJywgJ2dvb2cubmV0LldlYkNoYW5uZWxUcmFuc3BvcnQnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcucGF0aCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbC93ZWJjaGFubmVsYmFzZXRyYW5zcG9ydF90ZXN0LmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwud2ViQ2hhbm5lbEJhc2VUcmFuc3BvcnRUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5qc29uJywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5DaGFubmVsUmVxdWVzdCcsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbEJhc2UnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldlYkNoYW5uZWxCYXNlVHJhbnNwb3J0JywgJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XaXJlJywgJ2dvb2cubmV0LldlYkNoYW5uZWwnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvd2ViY2hhbm5lbGRlYnVnLmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2ViQ2hhbm5lbERlYnVnJ10sIFsnZ29vZy5qc29uJywgJ2dvb2cubG9nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC93ZWJjaGFubmVsL3dpcmUuanMnLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XaXJlJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvd2lyZXY4LmpzJywgWydnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2lyZVY4J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuanNvbicsICdnb29nLmpzb24uTmF0aXZlSnNvblByb2Nlc3NvcicsICdnb29nLmxhYnMubmV0LndlYkNoYW5uZWwuV2lyZScsICdnb29nLnN0cnVjdHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWwvd2lyZXY4X3Rlc3QuanMnLCBbJ2dvb2cubGFicy5uZXQud2ViQ2hhbm5lbC5XaXJlVjhUZXN0J10sIFsnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldpcmVWOCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9uZXQvd2ViY2hhbm5lbHRyYW5zcG9ydC5qcycsIFsnZ29vZy5uZXQuV2ViQ2hhbm5lbFRyYW5zcG9ydCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvbmV0L3dlYmNoYW5uZWx0cmFuc3BvcnRmYWN0b3J5LmpzJywgWydnb29nLm5ldC5jcmVhdGVXZWJDaGFubmVsVHJhbnNwb3J0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5sYWJzLm5ldC53ZWJDaGFubmVsLldlYkNoYW5uZWxCYXNlVHJhbnNwb3J0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC94aHIuanMnLCBbJ2dvb2cubGFicy5uZXQueGhyJywgJ2dvb2cubGFicy5uZXQueGhyLkVycm9yJywgJ2dvb2cubGFicy5uZXQueGhyLkh0dHBFcnJvcicsICdnb29nLmxhYnMubmV0Lnhoci5PcHRpb25zJywgJ2dvb2cubGFicy5uZXQueGhyLlBvc3REYXRhJywgJ2dvb2cubGFicy5uZXQueGhyLlJlc3BvbnNlVHlwZScsICdnb29nLmxhYnMubmV0Lnhoci5UaW1lb3V0RXJyb3InXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy5uZXQuSHR0cFN0YXR1cycsICdnb29nLm5ldC5YbWxIdHRwJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXJpLnV0aWxzJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL25ldC94aHJfdGVzdC5qcycsIFsnZ29vZy5sYWJzLm5ldC54aHJUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmxhYnMubmV0LnhocicsICdnb29nLm5ldC5XcmFwcGVyWG1sSHR0cEZhY3RvcnknLCAnZ29vZy5uZXQuWGhyTGlrZScsICdnb29nLm5ldC5YbWxIdHRwJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3B1YnN1Yi9icm9hZGNhc3RwdWJzdWIuanMnLCBbJ2dvb2cubGFicy5wdWJzdWIuQnJvYWRjYXN0UHViU3ViJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLnJ1bicsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubG9nJywgJ2dvb2cubWF0aCcsICdnb29nLnB1YnN1Yi5QdWJTdWInLCAnZ29vZy5zdG9yYWdlLlN0b3JhZ2UnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5IVE1MNUxvY2FsU3RvcmFnZScsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9wdWJzdWIvYnJvYWRjYXN0cHVic3ViX3Rlc3QuanMnLCBbJ2dvb2cubGFicy5wdWJzdWIuQnJvYWRjYXN0UHViU3ViVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kZWJ1Zy5Mb2dnZXInLCAnZ29vZy5qc29uJywgJ2dvb2cubGFicy5wdWJzdWIuQnJvYWRjYXN0UHViU3ViJywgJ2dvb2cuc3RvcmFnZS5TdG9yYWdlJywgJ2dvb2cuc3RydWN0cy5NYXAnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50JywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3N0b3JhZ2UvYm91bmRlZGNvbGxlY3RhYmxlc3RvcmFnZS5qcycsIFsnZ29vZy5sYWJzLnN0b3JhZ2UuQm91bmRlZENvbGxlY3RhYmxlU3RvcmFnZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaXRlcicsICdnb29nLnN0b3JhZ2UuQ29sbGVjdGFibGVTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5FcnJvckNvZGUnLCAnZ29vZy5zdG9yYWdlLkV4cGlyaW5nU3RvcmFnZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9zdG9yYWdlL2JvdW5kZWRjb2xsZWN0YWJsZXN0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy5sYWJzLnN0b3JhZ2UuQm91bmRlZENvbGxlY3RhYmxlU3RvcmFnZVRlc3QnXSwgWydnb29nLmxhYnMuc3RvcmFnZS5Cb3VuZGVkQ29sbGVjdGFibGVTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5jb2xsZWN0YWJsZVN0b3JhZ2VUZXN0ZXInLCAnZ29vZy5zdG9yYWdlLnN0b3JhZ2VUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3Rpbmcuc3RvcmFnZS5GYWtlTWVjaGFuaXNtJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3N0cnVjdHMvbXVsdGltYXAuanMnLCBbJ2dvb2cubGFicy5zdHJ1Y3RzLk11bHRpbWFwJ10sIFsnZ29vZy5hcnJheScsICdnb29nLm9iamVjdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvc3RydWN0cy9tdWx0aW1hcF90ZXN0LmpzJywgWydnb29nLmxhYnMuc3RydWN0cy5NdWx0aW1hcFRlc3QnXSwgWydnb29nLmxhYnMuc3RydWN0cy5NdWx0aW1hcCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy9zdHlsZS9waXhlbGRlbnNpdHltb25pdG9yLmpzJywgWydnb29nLmxhYnMuc3R5bGUuUGl4ZWxEZW5zaXR5TW9uaXRvcicsICdnb29nLmxhYnMuc3R5bGUuUGl4ZWxEZW5zaXR5TW9uaXRvci5EZW5zaXR5JywgJ2dvb2cubGFicy5zdHlsZS5QaXhlbERlbnNpdHlNb25pdG9yLkV2ZW50VHlwZSddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3N0eWxlL3BpeGVsZGVuc2l0eW1vbml0b3JfdGVzdC5qcycsIFsnZ29vZy5sYWJzLnN0eWxlLlBpeGVsRGVuc2l0eU1vbml0b3JUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbS5Eb21IZWxwZXInLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5sYWJzLnN0eWxlLlBpeGVsRGVuc2l0eU1vbml0b3InLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy90ZXN0aW5nL2Fzc2VydHRoYXQuanMnLCBbJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXJFcnJvcicsICdnb29nLmxhYnMudGVzdGluZy5hc3NlcnRUaGF0J10sIFsnZ29vZy5kZWJ1Zy5FcnJvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy90ZXN0aW5nL2Fzc2VydHRoYXRfdGVzdC5qcycsIFsnZ29vZy5sYWJzLnRlc3RpbmcuYXNzZXJ0VGhhdFRlc3QnXSwgWydnb29nLmxhYnMudGVzdGluZy5NYXRjaGVyRXJyb3InLCAnZ29vZy5sYWJzLnRlc3RpbmcuYXNzZXJ0VGhhdCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9kZWNvcmF0b3JtYXRjaGVyLmpzJywgWydnb29nLmxhYnMudGVzdGluZy5Bbnl0aGluZ01hdGNoZXInXSwgWydnb29nLmxhYnMudGVzdGluZy5NYXRjaGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3Rlc3RpbmcvZGVjb3JhdG9ybWF0Y2hlcl90ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5kZWNvcmF0b3JNYXRjaGVyVGVzdCddLCBbJ2dvb2cubGFicy50ZXN0aW5nLkFueXRoaW5nTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5HcmVhdGVyVGhhbk1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuTWF0Y2hlckVycm9yJywgJ2dvb2cubGFicy50ZXN0aW5nLmFzc2VydFRoYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9kaWN0aW9uYXJ5bWF0Y2hlci5qcycsIFsnZ29vZy5sYWJzLnRlc3RpbmcuSGFzRW50cmllc01hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSGFzRW50cnlNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkhhc0tleU1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSGFzVmFsdWVNYXRjaGVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXInLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9kaWN0aW9uYXJ5bWF0Y2hlcl90ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5kaWN0aW9uYXJ5TWF0Y2hlclRlc3QnXSwgWydnb29nLmxhYnMudGVzdGluZy5IYXNFbnRyeU1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuTWF0Y2hlckVycm9yJywgJ2dvb2cubGFicy50ZXN0aW5nLmFzc2VydFRoYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9lbnZpcm9ubWVudC5qcycsIFsnZ29vZy5sYWJzLnRlc3RpbmcuRW52aXJvbm1lbnQnXSwgWydnb29nLlRoZW5hYmxlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuQ29uc29sZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9lbnZpcm9ubWVudF90ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5lbnZpcm9ubWVudFRlc3QnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5sYWJzLnRlc3RpbmcuRW52aXJvbm1lbnQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczgnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy90ZXN0aW5nL2Vudmlyb25tZW50X3VzYWdlX3Rlc3QuanMnLCBbJ2dvb2cubGFicy50ZXN0aW5nLmVudmlyb25tZW50VXNhZ2VUZXN0J10sIFsnZ29vZy5sYWJzLnRlc3RpbmcuRW52aXJvbm1lbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9qc29uX2Z1enppbmcuanMnLCBbJ2dvb2cubGFicy50ZXN0aW5nLkpzb25GdXp6aW5nJ10sIFsnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLlBzZXVkb1JhbmRvbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy90ZXN0aW5nL2pzb25fZnV6emluZ190ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5Kc29uRnV6emluZ1Rlc3QnXSwgWydnb29nLmpzb24nLCAnZ29vZy5sYWJzLnRlc3RpbmcuSnNvbkZ1enppbmcnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9sb2dpY21hdGNoZXIuanMnLCBbJ2dvb2cubGFicy50ZXN0aW5nLkFsbE9mTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5BbnlPZk1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSXNOb3RNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLmxvZ2ljTWF0Y2hlcnMnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9sb2dpY21hdGNoZXJfdGVzdC5qcycsIFsnZ29vZy5sYWJzLnRlc3RpbmcubG9naWNNYXRjaGVyVGVzdCddLCBbJ2dvb2cubGFicy50ZXN0aW5nLkFsbE9mTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5HcmVhdGVyVGhhbk1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuTWF0Y2hlckVycm9yJywgJ2dvb2cubGFicy50ZXN0aW5nLmFzc2VydFRoYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9tYXRjaGVyLmpzJywgWydnb29nLmxhYnMudGVzdGluZy5NYXRjaGVyJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9udW1iZXJtYXRjaGVyLmpzJywgWydnb29nLmxhYnMudGVzdGluZy5BbnlOdW1iZXJNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkNsb3NlVG9NYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkVxdWFsVG9NYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkdyZWF0ZXJUaGFuRXF1YWxUb01hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuR3JlYXRlclRoYW5NYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkxlc3NUaGFuRXF1YWxUb01hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuTGVzc1RoYW5NYXRjaGVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9udW1iZXJtYXRjaGVyX3Rlc3QuanMnLCBbJ2dvb2cubGFicy50ZXN0aW5nLm51bWJlck1hdGNoZXJUZXN0J10sIFsnZ29vZy5sYWJzLnRlc3RpbmcuTGVzc1RoYW5NYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXJFcnJvcicsICdnb29nLmxhYnMudGVzdGluZy5hc3NlcnRUaGF0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3Rlc3Rpbmcvb2JqZWN0bWF0Y2hlci5qcycsIFsnZ29vZy5sYWJzLnRlc3RpbmcuQW55T2JqZWN0TWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5IYXNQcm9wZXJ0eU1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSW5zdGFuY2VPZk1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSXNOdWxsTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5Jc051bGxPclVuZGVmaW5lZE1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuSXNVbmRlZmluZWRNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLk9iamVjdEVxdWFsc01hdGNoZXInXSwgWydnb29nLmxhYnMudGVzdGluZy5NYXRjaGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3Rlc3Rpbmcvb2JqZWN0bWF0Y2hlcl90ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5vYmplY3RNYXRjaGVyVGVzdCddLCBbJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXJFcnJvcicsICdnb29nLmxhYnMudGVzdGluZy5PYmplY3RFcXVhbHNNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLmFzc2VydFRoYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdGVzdGluZy9zdHJpbmdtYXRjaGVyLmpzJywgWydnb29nLmxhYnMudGVzdGluZy5BbnlTdHJpbmdNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLkNvbnRhaW5zU3RyaW5nTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5FbmRzV2l0aE1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuRXF1YWxUb0lnbm9yaW5nV2hpdGVzcGFjZU1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuRXF1YWxzTWF0Y2hlcicsICdnb29nLmxhYnMudGVzdGluZy5SZWdleE1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuU3RhcnRzV2l0aE1hdGNoZXInLCAnZ29vZy5sYWJzLnRlc3RpbmcuU3RyaW5nQ29udGFpbnNJbk9yZGVyTWF0Y2hlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmxhYnMudGVzdGluZy5NYXRjaGVyJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3Rlc3Rpbmcvc3RyaW5nbWF0Y2hlcl90ZXN0LmpzJywgWydnb29nLmxhYnMudGVzdGluZy5zdHJpbmdNYXRjaGVyVGVzdCddLCBbJ2dvb2cubGFicy50ZXN0aW5nLk1hdGNoZXJFcnJvcicsICdnb29nLmxhYnMudGVzdGluZy5TdHJpbmdDb250YWluc0luT3JkZXJNYXRjaGVyJywgJ2dvb2cubGFicy50ZXN0aW5nLmFzc2VydFRoYXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdXNlcmFnZW50L2Jyb3dzZXIuanMnLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlciddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC51dGlsJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nLmludGVybmFsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3VzZXJhZ2VudC9icm93c2VyX3Rlc3QuanMnLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlclRlc3QnXSwgWydnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC50ZXN0QWdlbnRzJywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLm9iamVjdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvZGV2aWNlLmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LmRldmljZSddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvZGV2aWNlX3Rlc3QuanMnLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuZGV2aWNlVGVzdCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuZGV2aWNlJywgJ2dvb2cubGFicy51c2VyQWdlbnQudGVzdEFnZW50cycsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdXNlcmFnZW50L2VuZ2luZS5qcycsIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC5lbmdpbmUnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvZW5naW5lX3Rlc3QuanMnLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuZW5naW5lVGVzdCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuZW5naW5lJywgJ2dvb2cubGFicy51c2VyQWdlbnQudGVzdEFnZW50cycsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdXNlcmFnZW50L2V4dHJhLmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LmV4dHJhJ10sIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC5icm93c2VyJywgJ2dvb2cubGFicy51c2VyQWdlbnQucGxhdGZvcm0nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3VzZXJhZ2VudC9leHRyYV90ZXN0LmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LmV4dHJhVGVzdCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLmxhYnMudXNlckFnZW50LmV4dHJhJywgJ2dvb2cubGFicy51c2VyQWdlbnQudGVzdEFnZW50cycsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xhYnMvdXNlcmFnZW50L3BsYXRmb3JtLmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJ10sIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC51dGlsJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3VzZXJhZ2VudC9wbGF0Zm9ybV90ZXN0LmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtVGVzdCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQucGxhdGZvcm0nLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC50ZXN0QWdlbnRzJywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvdGVzdF9hZ2VudHMuanMnLCBbJ2dvb2cubGFicy51c2VyQWdlbnQudGVzdEFnZW50cyddLCBbXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsYWJzL3VzZXJhZ2VudC91dGlsLmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LnV0aWwnXSwgWydnb29nLnN0cmluZy5pbnRlcm5hbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvdXRpbF90ZXN0LmpzJywgWydnb29nLmxhYnMudXNlckFnZW50LnV0aWxUZXN0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC50ZXN0QWdlbnRzJywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvdmVyaWZpZXIuanMnLCBbJ2dvb2cubGFicy51c2VyYWdlbnQudmVyaWZpZXInXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbGFicy91c2VyYWdlbnQvdmVyaWZpZXJfdGVzdC5qcycsIFsnZ29vZy5sYWJzLnVzZXJhZ2VudC52ZXJpZmllclRlc3QnXSwgWydnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy5sYWJzLnVzZXJhZ2VudC52ZXJpZmllcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9hZGVyL2Fic3RyYWN0bW9kdWxlbWFuYWdlci5qcycsIFsnZ29vZy5sb2FkZXIuQWJzdHJhY3RNb2R1bGVNYW5hZ2VyJywgJ2dvb2cubG9hZGVyLkFic3RyYWN0TW9kdWxlTWFuYWdlci5DYWxsYmFja1R5cGUnLCAnZ29vZy5sb2FkZXIuQWJzdHJhY3RNb2R1bGVNYW5hZ2VyLkZhaWx1cmVUeXBlJ10sIFsnZ29vZy5tb2R1bGUuQWJzdHJhY3RNb2R1bGVMb2FkZXInLCAnZ29vZy5tb2R1bGUuTW9kdWxlSW5mbycsICdnb29nLm1vZHVsZS5Nb2R1bGVMb2FkQ2FsbGJhY2snXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvYWRlci9hY3RpdmVtb2R1bGVtYW5hZ2VyLmpzJywgWydnb29nLmxvYWRlci5hY3RpdmVNb2R1bGVNYW5hZ2VyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubG9hZGVyLkFic3RyYWN0TW9kdWxlTWFuYWdlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvY2FsZS9jb3VudHJpZXMuanMnLCBbJ2dvb2cubG9jYWxlLmNvdW50cmllcyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvY2FsZS9jb3VudHJ5bGFuZ3VhZ2VuYW1lc190ZXN0LmpzJywgWydnb29nLmxvY2FsZS5jb3VudHJ5TGFuZ3VhZ2VOYW1lc1Rlc3QnXSwgWydnb29nLmxvY2FsZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9jYWxlL2RlZmF1bHRsb2NhbGVuYW1lY29uc3RhbnRzLmpzJywgWydnb29nLmxvY2FsZS5kZWZhdWx0TG9jYWxlTmFtZUNvbnN0YW50cyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvY2FsZS9nZW5lcmljZm9udG5hbWVzLmpzJywgWydnb29nLmxvY2FsZS5nZW5lcmljRm9udE5hbWVzJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9jYWxlL2dlbmVyaWNmb250bmFtZXNfdGVzdC5qcycsIFsnZ29vZy5sb2NhbGUuZ2VuZXJpY0ZvbnROYW1lc1Rlc3QnXSwgWydnb29nLmxvY2FsZS5nZW5lcmljRm9udE5hbWVzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsb2NhbGUvZ2VuZXJpY2ZvbnRuYW1lc2RhdGEuanMnLCBbJ2dvb2cubG9jYWxlLmdlbmVyaWNGb250TmFtZXNEYXRhJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9jYWxlL2xvY2FsZS5qcycsIFsnZ29vZy5sb2NhbGUnXSwgWydnb29nLmxvY2FsZS5uYXRpdmVOYW1lQ29uc3RhbnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsb2NhbGUvbmF0aXZlbmFtZWNvbnN0YW50cy5qcycsIFsnZ29vZy5sb2NhbGUubmF0aXZlTmFtZUNvbnN0YW50cyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvY2FsZS9zY3JpcHRUb0xhbmd1YWdlcy5qcycsIFsnZ29vZy5sb2NhbGUuc2NyaXB0VG9MYW5ndWFnZXMnXSwgWydnb29nLmxvY2FsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9jYWxlL3RpbWV6b25lZGV0ZWN0aW9uLmpzJywgWydnb29nLmxvY2FsZS50aW1lWm9uZURldGVjdGlvbiddLCBbJ2dvb2cubG9jYWxlLlRpbWVab25lRmluZ2VycHJpbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvY2FsZS90aW1lem9uZWRldGVjdGlvbl90ZXN0LmpzJywgWydnb29nLmxvY2FsZS50aW1lWm9uZURldGVjdGlvblRlc3QnXSwgWydnb29nLmxvY2FsZS50aW1lWm9uZURldGVjdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9jYWxlL3RpbWV6b25lZmluZ2VycHJpbnQuanMnLCBbJ2dvb2cubG9jYWxlLlRpbWVab25lRmluZ2VycHJpbnQnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsb2NhbGUvdGltZXpvbmVsaXN0LmpzJywgWydnb29nLmxvY2FsZS5UaW1lWm9uZUxpc3QnLCAnZ29vZy5sb2NhbGUuZ2V0VGltZVpvbmVBbGxMb25nTmFtZXMnLCAnZ29vZy5sb2NhbGUuZ2V0VGltZVpvbmVTZWxlY3RlZExvbmdOYW1lcycsICdnb29nLmxvY2FsZS5nZXRUaW1lWm9uZVNlbGVjdGVkU2hvcnROYW1lcyddLCBbJ2dvb2cubG9jYWxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdsb2NhbGUvdGltZXpvbmVsaXN0X3Rlc3QuanMnLCBbJ2dvb2cubG9jYWxlLlRpbWVab25lTGlzdFRlc3QnXSwgWydnb29nLmxvY2FsZScsICdnb29nLmxvY2FsZS5UaW1lWm9uZUxpc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ2xvZy9sb2cuanMnLCBbJ2dvb2cubG9nJywgJ2dvb2cubG9nLkxldmVsJywgJ2dvb2cubG9nLkxvZ1JlY29yZCcsICdnb29nLmxvZy5Mb2dnZXInXSwgWydnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRlYnVnLkxvZ1JlY29yZCcsICdnb29nLmRlYnVnLkxvZ2dlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbG9nL2xvZ190ZXN0LmpzJywgWydnb29nLmxvZ1Rlc3QnXSwgWydnb29nLmRlYnVnLkxvZ01hbmFnZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5sb2cuTGV2ZWwnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvYWZmaW5ldHJhbnNmb3JtLmpzJywgWydnb29nLm1hdGguQWZmaW5lVHJhbnNmb3JtJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvYWZmaW5ldHJhbnNmb3JtX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5BZmZpbmVUcmFuc2Zvcm1UZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLm1hdGgnLCAnZ29vZy5tYXRoLkFmZmluZVRyYW5zZm9ybScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9iZXppZXIuanMnLCBbJ2dvb2cubWF0aC5CZXppZXInXSwgWydnb29nLm1hdGgnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvYmV6aWVyX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5CZXppZXJUZXN0J10sIFsnZ29vZy5tYXRoJywgJ2dvb2cubWF0aC5CZXppZXInLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvYm94LmpzJywgWydnb29nLm1hdGguQm94J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2JveF90ZXN0LmpzJywgWydnb29nLm1hdGguQm94VGVzdCddLCBbJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvY29vcmRpbmF0ZS5qcycsIFsnZ29vZy5tYXRoLkNvb3JkaW5hdGUnXSwgWydnb29nLm1hdGgnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvY29vcmRpbmF0ZTMuanMnLCBbJ2dvb2cubWF0aC5Db29yZGluYXRlMyddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2Nvb3JkaW5hdGUzX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5Db29yZGluYXRlM1Rlc3QnXSwgWydnb29nLm1hdGguQ29vcmRpbmF0ZTMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvY29vcmRpbmF0ZV90ZXN0LmpzJywgWydnb29nLm1hdGguQ29vcmRpbmF0ZVRlc3QnXSwgWydnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9leHBvbmVudGlhbGJhY2tvZmYuanMnLCBbJ2dvb2cubWF0aC5FeHBvbmVudGlhbEJhY2tvZmYnXSwgWydnb29nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvZXhwb25lbnRpYWxiYWNrb2ZmX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5FeHBvbmVudGlhbEJhY2tvZmZUZXN0J10sIFsnZ29vZy5tYXRoLkV4cG9uZW50aWFsQmFja29mZicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9pbnRlZ2VyLmpzJywgWydnb29nLm1hdGguSW50ZWdlciddLCBbJ2dvb2cucmVmbGVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9pbnRlZ2VyX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5JbnRlZ2VyVGVzdCddLCBbJ2dvb2cubWF0aC5JbnRlZ2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2ludGVycG9sYXRvci9pbnRlcnBvbGF0b3IxLmpzJywgWydnb29nLm1hdGguaW50ZXJwb2xhdG9yLkludGVycG9sYXRvcjEnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2ludGVycG9sYXRvci9saW5lYXIxLmpzJywgWydnb29nLm1hdGguaW50ZXJwb2xhdG9yLkxpbmVhcjEnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLm1hdGgnLCAnZ29vZy5tYXRoLmludGVycG9sYXRvci5JbnRlcnBvbGF0b3IxJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2ludGVycG9sYXRvci9saW5lYXIxX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5pbnRlcnBvbGF0b3IuTGluZWFyMVRlc3QnXSwgWydnb29nLm1hdGguaW50ZXJwb2xhdG9yLkxpbmVhcjEnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvaW50ZXJwb2xhdG9yL3BjaGlwMS5qcycsIFsnZ29vZy5tYXRoLmludGVycG9sYXRvci5QY2hpcDEnXSwgWydnb29nLm1hdGgnLCAnZ29vZy5tYXRoLmludGVycG9sYXRvci5TcGxpbmUxJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2ludGVycG9sYXRvci9wY2hpcDFfdGVzdC5qcycsIFsnZ29vZy5tYXRoLmludGVycG9sYXRvci5QY2hpcDFUZXN0J10sIFsnZ29vZy5tYXRoLmludGVycG9sYXRvci5QY2hpcDEnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvaW50ZXJwb2xhdG9yL3NwbGluZTEuanMnLCBbJ2dvb2cubWF0aC5pbnRlcnBvbGF0b3IuU3BsaW5lMSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cubWF0aCcsICdnb29nLm1hdGguaW50ZXJwb2xhdG9yLkludGVycG9sYXRvcjEnLCAnZ29vZy5tYXRoLnRkbWEnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvaW50ZXJwb2xhdG9yL3NwbGluZTFfdGVzdC5qcycsIFsnZ29vZy5tYXRoLmludGVycG9sYXRvci5TcGxpbmUxVGVzdCddLCBbJ2dvb2cubWF0aC5pbnRlcnBvbGF0b3IuU3BsaW5lMScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9pcmVjdC5qcycsIFsnZ29vZy5tYXRoLklSZWN0J10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9saW5lLmpzJywgWydnb29nLm1hdGguTGluZSddLCBbJ2dvb2cubWF0aCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9saW5lX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5MaW5lVGVzdCddLCBbJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cubWF0aC5MaW5lJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL2xvbmcuanMnLCBbJ2dvb2cubWF0aC5Mb25nJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cucmVmbGVjdCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvbG9uZ190ZXN0LmpzJywgWydnb29nLm1hdGguTG9uZ1Rlc3QnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5tYXRoLkxvbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvbWF0aC5qcycsIFsnZ29vZy5tYXRoJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvbWF0aF90ZXN0LmpzJywgWydnb29nLm1hdGhUZXN0J10sIFsnZ29vZy5tYXRoJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL21hdHJpeC5qcycsIFsnZ29vZy5tYXRoLk1hdHJpeCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cubWF0aCcsICdnb29nLm1hdGguU2l6ZScsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9tYXRyaXhfdGVzdC5qcycsIFsnZ29vZy5tYXRoLk1hdHJpeFRlc3QnXSwgWydnb29nLm1hdGguTWF0cml4JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3BhdGguanMnLCBbJ2dvb2cubWF0aC5QYXRoJywgJ2dvb2cubWF0aC5QYXRoLlNlZ21lbnQnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubWF0aCcsICdnb29nLm1hdGguQWZmaW5lVHJhbnNmb3JtJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3BhdGhfdGVzdC5qcycsIFsnZ29vZy5tYXRoLlBhdGhUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLm1hdGguQWZmaW5lVHJhbnNmb3JtJywgJ2dvb2cubWF0aC5QYXRoJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3BhdGhzLmpzJywgWydnb29nLm1hdGgucGF0aHMnXSwgWydnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLm1hdGguUGF0aCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9wYXRoc190ZXN0LmpzJywgWydnb29nLm1hdGgucGF0aHNUZXN0J10sIFsnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLnBhdGhzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3JhbmdlLmpzJywgWydnb29nLm1hdGguUmFuZ2UnXSwgWydnb29nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvcmFuZ2VfdGVzdC5qcycsIFsnZ29vZy5tYXRoLlJhbmdlVGVzdCddLCBbJ2dvb2cubWF0aC5SYW5nZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9yYW5nZXNldC5qcycsIFsnZ29vZy5tYXRoLlJhbmdlU2V0J10sIFsnZ29vZy5hcnJheScsICdnb29nLml0ZXIuSXRlcmF0b3InLCAnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nLCAnZ29vZy5tYXRoLlJhbmdlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3Jhbmdlc2V0X3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5SYW5nZVNldFRlc3QnXSwgWydnb29nLml0ZXInLCAnZ29vZy5tYXRoLlJhbmdlJywgJ2dvb2cubWF0aC5SYW5nZVNldCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9yZWN0LmpzJywgWydnb29nLm1hdGguUmVjdCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLm1hdGguQm94JywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cubWF0aC5JUmVjdCcsICdnb29nLm1hdGguU2l6ZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9yZWN0X3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5SZWN0VGVzdCddLCBbJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlJlY3QnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvc2l6ZS5qcycsIFsnZ29vZy5tYXRoLlNpemUnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC9zaXplX3Rlc3QuanMnLCBbJ2dvb2cubWF0aC5TaXplVGVzdCddLCBbJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtYXRoL3RkbWEuanMnLCBbJ2dvb2cubWF0aC50ZG1hJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvdGRtYV90ZXN0LmpzJywgWydnb29nLm1hdGgudGRtYVRlc3QnXSwgWydnb29nLm1hdGgudGRtYScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC92ZWMyLmpzJywgWydnb29nLm1hdGguVmVjMiddLCBbJ2dvb2cubWF0aCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZSddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvdmVjMl90ZXN0LmpzJywgWydnb29nLm1hdGguVmVjMlRlc3QnXSwgWydnb29nLm1hdGguVmVjMicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWF0aC92ZWMzLmpzJywgWydnb29nLm1hdGguVmVjMyddLCBbJ2dvb2cubWF0aCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZTMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21hdGgvdmVjM190ZXN0LmpzJywgWydnb29nLm1hdGguVmVjM1Rlc3QnXSwgWydnb29nLm1hdGguQ29vcmRpbmF0ZTMnLCAnZ29vZy5tYXRoLlZlYzMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lbW9pemUvbWVtb2l6ZS5qcycsIFsnZ29vZy5tZW1vaXplJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lbW9pemUvbWVtb2l6ZV90ZXN0LmpzJywgWydnb29nLm1lbW9pemVUZXN0J10sIFsnZ29vZy5tZW1vaXplJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvYWJzdHJhY3RjaGFubmVsLmpzJywgWydnb29nLm1lc3NhZ2luZy5BYnN0cmFjdENoYW5uZWwnXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5qc29uJywgJ2dvb2cubG9nJywgJ2dvb2cubWVzc2FnaW5nLk1lc3NhZ2VDaGFubmVsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvYWJzdHJhY3RjaGFubmVsX3Rlc3QuanMnLCBbJ2dvb2cubWVzc2FnaW5nLkFic3RyYWN0Q2hhbm5lbFRlc3QnXSwgWydnb29nLm1lc3NhZ2luZy5BYnN0cmFjdENoYW5uZWwnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5hc3luYy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL2J1ZmZlcmVkY2hhbm5lbC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuQnVmZmVyZWRDaGFubmVsJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5sb2cnLCAnZ29vZy5tZXNzYWdpbmcuTWVzc2FnZUNoYW5uZWwnLCAnZ29vZy5tZXNzYWdpbmcuTXVsdGlDaGFubmVsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvYnVmZmVyZWRjaGFubmVsX3Rlc3QuanMnLCBbJ2dvb2cubWVzc2FnaW5nLkJ1ZmZlcmVkQ2hhbm5lbFRlc3QnXSwgWydnb29nLmRlYnVnLkNvbnNvbGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmxvZycsICdnb29nLmxvZy5MZXZlbCcsICdnb29nLm1lc3NhZ2luZy5CdWZmZXJlZENoYW5uZWwnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLmFzeW5jLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvZGVmZXJyZWRjaGFubmVsLmpzJywgWydnb29nLm1lc3NhZ2luZy5EZWZlcnJlZENoYW5uZWwnXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5tZXNzYWdpbmcuTWVzc2FnZUNoYW5uZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lc3NhZ2luZy9kZWZlcnJlZGNoYW5uZWxfdGVzdC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuRGVmZXJyZWRDaGFubmVsVGVzdCddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5tZXNzYWdpbmcuRGVmZXJyZWRDaGFubmVsJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuYXN5bmMuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLm1lc3NhZ2luZy5Nb2NrTWVzc2FnZUNoYW5uZWwnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lc3NhZ2luZy9sb2dnZXJjbGllbnQuanMnLCBbJ2dvb2cubWVzc2FnaW5nLkxvZ2dlckNsaWVudCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmRlYnVnJywgJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRlYnVnLkxvZ2dlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL2xvZ2dlcmNsaWVudF90ZXN0LmpzJywgWydnb29nLm1lc3NhZ2luZy5Mb2dnZXJDbGllbnRUZXN0J10sIFsnZ29vZy5kZWJ1ZycsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLm1lc3NhZ2luZy5Mb2dnZXJDbGllbnQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvbG9nZ2Vyc2VydmVyLmpzJywgWydnb29nLm1lc3NhZ2luZy5Mb2dnZXJTZXJ2ZXInXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5sb2cnLCAnZ29vZy5sb2cuTGV2ZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lc3NhZ2luZy9sb2dnZXJzZXJ2ZXJfdGVzdC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuTG9nZ2VyU2VydmVyVGVzdCddLCBbJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLmxvZycsICdnb29nLmxvZy5MZXZlbCcsICdnb29nLm1lc3NhZ2luZy5Mb2dnZXJTZXJ2ZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvbWVzc2FnZWNoYW5uZWwuanMnLCBbJ2dvb2cubWVzc2FnaW5nLk1lc3NhZ2VDaGFubmVsJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL21lc3NhZ2luZy5qcycsIFsnZ29vZy5tZXNzYWdpbmcnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvbWVzc2FnaW5nX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsVGVzdCddLCBbJ2dvb2cubWVzc2FnaW5nJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcubWVzc2FnaW5nLk1vY2tNZXNzYWdlQ2hhbm5lbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL211bHRpY2hhbm5lbC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuTXVsdGlDaGFubmVsJywgJ2dvb2cubWVzc2FnaW5nLk11bHRpQ2hhbm5lbC5WaXJ0dWFsQ2hhbm5lbCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmxvZycsICdnb29nLm1lc3NhZ2luZy5NZXNzYWdlQ2hhbm5lbCcsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL211bHRpY2hhbm5lbF90ZXN0LmpzJywgWydnb29nLm1lc3NhZ2luZy5NdWx0aUNoYW5uZWxUZXN0J10sIFsnZ29vZy5tZXNzYWdpbmcuTXVsdGlDaGFubmVsJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcubWVzc2FnaW5nLk1vY2tNZXNzYWdlQ2hhbm5lbCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLklnbm9yZUFyZ3VtZW50JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcG9ydGNhbGxlci5qcycsIFsnZ29vZy5tZXNzYWdpbmcuUG9ydENhbGxlciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cubWVzc2FnaW5nLkRlZmVycmVkQ2hhbm5lbCcsICdnb29nLm1lc3NhZ2luZy5Qb3J0Q2hhbm5lbCcsICdnb29nLm1lc3NhZ2luZy5Qb3J0TmV0d29yaycsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL3BvcnRjYWxsZXJfdGVzdC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuUG9ydENhbGxlclRlc3QnXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLm1lc3NhZ2luZy5Qb3J0Q2FsbGVyJywgJ2dvb2cubWVzc2FnaW5nLlBvcnROZXR3b3JrJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcubWVzc2FnaW5nLk1vY2tNZXNzYWdlQ2hhbm5lbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL3BvcnRjaGFubmVsLmpzJywgWydnb29nLm1lc3NhZ2luZy5Qb3J0Q2hhbm5lbCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZGVidWcnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuanNvbicsICdnb29nLmxvZycsICdnb29nLm1lc3NhZ2luZy5BYnN0cmFjdENoYW5uZWwnLCAnZ29vZy5tZXNzYWdpbmcuRGVmZXJyZWRDaGFubmVsJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcG9ydGNoYW5uZWxfdGVzdC5qcycsIFsnZ29vZy5tZXNzYWdpbmcuUG9ydENoYW5uZWxUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5qc29uJywgJ2dvb2cubWVzc2FnaW5nLlBvcnRDaGFubmVsJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLm1lc3NhZ2luZy5Nb2NrTWVzc2FnZUV2ZW50JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcG9ydG5ldHdvcmsuanMnLCBbJ2dvb2cubWVzc2FnaW5nLlBvcnROZXR3b3JrJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL3BvcnRuZXR3b3JrX3Rlc3QuanMnLCBbJ2dvb2cubWVzc2FnaW5nLlBvcnROZXR3b3JrVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLlRpbWVyJywgJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLm1lc3NhZ2luZy5Qb3J0Q2hhbm5lbCcsICdnb29nLm1lc3NhZ2luZy5Qb3J0T3BlcmF0b3InLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcG9ydG9wZXJhdG9yLmpzJywgWydnb29nLm1lc3NhZ2luZy5Qb3J0T3BlcmF0b3InXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cubG9nJywgJ2dvb2cubWVzc2FnaW5nLlBvcnRDaGFubmVsJywgJ2dvb2cubWVzc2FnaW5nLlBvcnROZXR3b3JrJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcG9ydG9wZXJhdG9yX3Rlc3QuanMnLCBbJ2dvb2cubWVzc2FnaW5nLlBvcnRPcGVyYXRvclRlc3QnXSwgWydnb29nLm1lc3NhZ2luZy5Qb3J0TmV0d29yaycsICdnb29nLm1lc3NhZ2luZy5Qb3J0T3BlcmF0b3InLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VQb3J0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtZXNzYWdpbmcvcmVzcG9uZGluZ2NoYW5uZWwuanMnLCBbJ2dvb2cubWVzc2FnaW5nLlJlc3BvbmRpbmdDaGFubmVsJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuUHJvbWlzZScsICdnb29nLmxvZycsICdnb29nLm1lc3NhZ2luZy5NdWx0aUNoYW5uZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lc3NhZ2luZy9yZXNwb25kaW5nY2hhbm5lbF90ZXN0LmpzJywgWydnb29nLm1lc3NhZ2luZy5SZXNwb25kaW5nQ2hhbm5lbFRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5tZXNzYWdpbmcuUmVzcG9uZGluZ0NoYW5uZWwnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL3Rlc3RkYXRhL3BvcnRjaGFubmVsX3dvcmtlci5qcycsIFsnZ29vZy5tZXNzYWdpbmcudGVzdGRhdGEucG9ydGNoYW5uZWxfd29ya2VyJ10sIFsnZ29vZy5tZXNzYWdpbmcuUG9ydENoYW5uZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21lc3NhZ2luZy90ZXN0ZGF0YS9wb3J0bmV0d29ya193b3JrZXIxLmpzJywgWydnb29nLm1lc3NhZ2luZy50ZXN0ZGF0YS5wb3J0bmV0d29ya193b3JrZXIxJ10sIFsnZ29vZy5tZXNzYWdpbmcuUG9ydENhbGxlcicsICdnb29nLm1lc3NhZ2luZy5Qb3J0Q2hhbm5lbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbWVzc2FnaW5nL3Rlc3RkYXRhL3BvcnRuZXR3b3JrX3dvcmtlcjIuanMnLCBbJ2dvb2cubWVzc2FnaW5nLnRlc3RkYXRhLnBvcnRuZXR3b3JrX3dvcmtlcjInXSwgWydnb29nLm1lc3NhZ2luZy5Qb3J0Q2FsbGVyJywgJ2dvb2cubWVzc2FnaW5nLlBvcnRDaGFubmVsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvYWJzdHJhY3Rtb2R1bGVsb2FkZXIuanMnLCBbJ2dvb2cubW9kdWxlLkFic3RyYWN0TW9kdWxlTG9hZGVyJ10sIFsnZ29vZy5tb2R1bGUnLCAnZ29vZy5tb2R1bGUuTW9kdWxlSW5mbyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbW9kdWxlL2Jhc2Vtb2R1bGUuanMnLCBbJ2dvb2cubW9kdWxlLkJhc2VNb2R1bGUnXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5tb2R1bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21vZHVsZS9sb2FkZXIuanMnLCBbJ2dvb2cubW9kdWxlLkxvYWRlciddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5sZWdhY3ljb252ZXJzaW9ucycsICdnb29nLm1vZHVsZScsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbW9kdWxlL21vZHVsZS5qcycsIFsnZ29vZy5tb2R1bGUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvbW9kdWxlaW5mby5qcycsIFsnZ29vZy5tb2R1bGUuTW9kdWxlSW5mbyddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmFzeW5jLnRocm93RXhjZXB0aW9uJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5tb2R1bGUnLCAnZ29vZy5tb2R1bGUuQmFzZU1vZHVsZScsICdnb29nLm1vZHVsZS5Nb2R1bGVMb2FkQ2FsbGJhY2snXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21vZHVsZS9tb2R1bGVpbmZvX3Rlc3QuanMnLCBbJ2dvb2cubW9kdWxlLk1vZHVsZUluZm9UZXN0J10sIFsnZ29vZy5tb2R1bGUuQmFzZU1vZHVsZScsICdnb29nLm1vZHVsZS5Nb2R1bGVJbmZvJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21vZHVsZS9tb2R1bGVsb2FkY2FsbGJhY2suanMnLCBbJ2dvb2cubW9kdWxlLk1vZHVsZUxvYWRDYWxsYmFjayddLCBbJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cubW9kdWxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvbW9kdWxlbG9hZGNhbGxiYWNrX3Rlc3QuanMnLCBbJ2dvb2cubW9kdWxlLk1vZHVsZUxvYWRDYWxsYmFja1Rlc3QnXSwgWydnb29nLmRlYnVnLkVycm9ySGFuZGxlcicsICdnb29nLmRlYnVnLmVudHJ5UG9pbnRSZWdpc3RyeScsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLm1vZHVsZS5Nb2R1bGVMb2FkQ2FsbGJhY2snLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvbW9kdWxlbG9hZGVyLmpzJywgWydnb29nLm1vZHVsZS5Nb2R1bGVMb2FkZXInXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50SWQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmxhYnMudXNlckFnZW50LmJyb3dzZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5tb2R1bGUuQWJzdHJhY3RNb2R1bGVMb2FkZXInLCAnZ29vZy5uZXQuQnVsa0xvYWRlcicsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuanNsb2FkZXInLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ21vZHVsZS9tb2R1bGVsb2FkZXJfdGVzdC5qcycsIFsnZ29vZy5tb2R1bGUuTW9kdWxlTG9hZGVyVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLmxvYWRlci5hY3RpdmVNb2R1bGVNYW5hZ2VyJywgJ2dvb2cubW9kdWxlLk1vZHVsZUxvYWRlcicsICdnb29nLm1vZHVsZS5Nb2R1bGVNYW5hZ2VyJywgJ2dvb2cubmV0LkJ1bGtMb2FkZXInLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudE9ic2VydmVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvbW9kdWxlbWFuYWdlci5qcycsIFsnZ29vZy5tb2R1bGUuTW9kdWxlTWFuYWdlcicsICdnb29nLm1vZHVsZS5Nb2R1bGVNYW5hZ2VyLkNhbGxiYWNrVHlwZScsICdnb29nLm1vZHVsZS5Nb2R1bGVNYW5hZ2VyLkZhaWx1cmVUeXBlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmRlYnVnLlRyYWNlJywgJ2dvb2cuZGlzcG9zYWJsZS5JRGlzcG9zYWJsZScsICdnb29nLmRpc3Bvc2VBbGwnLCAnZ29vZy5sb2FkZXIuQWJzdHJhY3RNb2R1bGVNYW5hZ2VyJywgJ2dvb2cubG9hZGVyLmFjdGl2ZU1vZHVsZU1hbmFnZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5tb2R1bGUnLCAnZ29vZy5tb2R1bGUuTW9kdWxlSW5mbycsICdnb29nLm1vZHVsZS5Nb2R1bGVMb2FkQ2FsbGJhY2snLCAnZ29vZy5vYmplY3QnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdtb2R1bGUvbW9kdWxlbWFuYWdlcl90ZXN0LmpzJywgWydnb29nLm1vZHVsZS5Nb2R1bGVNYW5hZ2VyVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5tb2R1bGUuQmFzZU1vZHVsZScsICdnb29nLm1vZHVsZS5Nb2R1bGVNYW5hZ2VyJywgJ2dvb2cudGVzdGluZycsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbW9kdWxlL3Rlc3RkYXRhL21vZEFfMS5qcycsIFsnZ29vZy5tb2R1bGUudGVzdGRhdGEubW9kQV8xJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbW9kdWxlL3Rlc3RkYXRhL21vZEFfMi5qcycsIFsnZ29vZy5tb2R1bGUudGVzdGRhdGEubW9kQV8yJ10sIFsnZ29vZy5tb2R1bGUuTW9kdWxlTWFuYWdlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbW9kdWxlL3Rlc3RkYXRhL21vZEJfMS5qcycsIFsnZ29vZy5tb2R1bGUudGVzdGRhdGEubW9kQl8xJ10sIFsnZ29vZy5tb2R1bGUuTW9kdWxlTWFuYWdlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2Jyb3dzZXJjaGFubmVsLmpzJywgWydnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbCcsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbC5FcnJvcicsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbC5FdmVudCcsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbC5IYW5kbGVyJywgJ2dvb2cubmV0LkJyb3dzZXJDaGFubmVsLkxvZ1NhdmVyJywgJ2dvb2cubmV0LkJyb3dzZXJDaGFubmVsLlF1ZXVlZE1hcCcsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbC5TZXJ2ZXJSZWFjaGFiaWxpdHknLCAnZ29vZy5uZXQuQnJvd3NlckNoYW5uZWwuU2VydmVyUmVhY2hhYmlsaXR5RXZlbnQnLCAnZ29vZy5uZXQuQnJvd3NlckNoYW5uZWwuU3RhdCcsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbC5TdGF0RXZlbnQnLCAnZ29vZy5uZXQuQnJvd3NlckNoYW5uZWwuU3RhdGUnLCAnZ29vZy5uZXQuQnJvd3NlckNoYW5uZWwuVGltaW5nRXZlbnQnXSwgWydnb29nLlVyaScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRlYnVnLlRleHRGb3JtYXR0ZXInLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5qc29uJywgJ2dvb2cuanNvbi5OYXRpdmVKc29uUHJvY2Vzc29yJywgJ2dvb2cubG9nJywgJ2dvb2cubmV0LkJyb3dzZXJUZXN0Q2hhbm5lbCcsICdnb29nLm5ldC5DaGFubmVsRGVidWcnLCAnZ29vZy5uZXQuQ2hhbm5lbFJlcXVlc3QnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQudG1wbmV0d29yaycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLkNpcmN1bGFyQnVmZmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvYnJvd3NlcmNoYW5uZWxfdGVzdC5qcycsIFsnZ29vZy5uZXQuQnJvd3NlckNoYW5uZWxUZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuanNvbicsICdnb29nLm5ldC5Ccm93c2VyQ2hhbm5lbCcsICdnb29nLm5ldC5DaGFubmVsRGVidWcnLCAnZ29vZy5uZXQuQ2hhbm5lbFJlcXVlc3QnLCAnZ29vZy5uZXQudG1wbmV0d29yaycsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvYnJvd3NlcnRlc3RjaGFubmVsLmpzJywgWydnb29nLm5ldC5Ccm93c2VyVGVzdENoYW5uZWwnXSwgWydnb29nLmpzb24uTmF0aXZlSnNvblByb2Nlc3NvcicsICdnb29nLm5ldC5DaGFubmVsUmVxdWVzdCcsICdnb29nLm5ldC5DaGFubmVsUmVxdWVzdC5FcnJvcicsICdnb29nLm5ldC50bXBuZXR3b3JrJywgJ2dvb2cuc3RyaW5nLlBhcnNlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2J1bGtsb2FkZXIuanMnLCBbJ2dvb2cubmV0LkJ1bGtMb2FkZXInXSwgWydnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5sb2cnLCAnZ29vZy5uZXQuQnVsa0xvYWRlckhlbHBlcicsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuWGhySW8nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9idWxrbG9hZGVyX3Rlc3QuanMnLCBbJ2dvb2cubmV0LkJ1bGtMb2FkZXJUZXN0J10sIFsnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cubmV0LkJ1bGtMb2FkZXInLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9idWxrbG9hZGVyaGVscGVyLmpzJywgWydnb29nLm5ldC5CdWxrTG9hZGVySGVscGVyJ10sIFsnZ29vZy5EaXNwb3NhYmxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvY2hhbm5lbGRlYnVnLmpzJywgWydnb29nLm5ldC5DaGFubmVsRGVidWcnXSwgWydnb29nLmpzb24nLCAnZ29vZy5sb2cnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvY2hhbm5lbHJlcXVlc3QuanMnLCBbJ2dvb2cubmV0LkNoYW5uZWxSZXF1ZXN0JywgJ2dvb2cubmV0LkNoYW5uZWxSZXF1ZXN0LkVycm9yJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFzeW5jLlRocm90dGxlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5odG1sLlNhZmVVcmwnLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cubmV0LkVycm9yQ29kZScsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2NoYW5uZWxyZXF1ZXN0X3Rlc3QuanMnLCBbJ2dvb2cubmV0LkNoYW5uZWxSZXF1ZXN0VGVzdCddLCBbJ2dvb2cuVXJpJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubmV0LkJyb3dzZXJDaGFubmVsJywgJ2dvb2cubmV0LkNoYW5uZWxEZWJ1ZycsICdnb29nLm5ldC5DaGFubmVsUmVxdWVzdCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5uZXQuWGhySW8nLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvY29va2llcy5qcycsIFsnZ29vZy5uZXQuQ29va2llcycsICdnb29nLm5ldC5jb29raWVzJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuc3RyaW5nJ10sIHsnbGFuZyc6ICdlczUnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2Nvb2tpZXNfdGVzdC5qcycsIFsnZ29vZy5uZXQuY29va2llc1Rlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubmV0LkNvb2tpZXMnLCAnZ29vZy5uZXQuY29va2llcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2NvcnN4bWxodHRwZmFjdG9yeS5qcycsIFsnZ29vZy5uZXQuQ29yc1htbEh0dHBGYWN0b3J5JywgJ2dvb2cubmV0LkllQ29yc1hockFkYXB0ZXInXSwgWydnb29nLm5ldC5IdHRwU3RhdHVzJywgJ2dvb2cubmV0Llhockxpa2UnLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm5ldC5YbWxIdHRwRmFjdG9yeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2NvcnN4bWxodHRwZmFjdG9yeV90ZXN0LmpzJywgWydnb29nLm5ldC5Db3JzWG1sSHR0cEZhY3RvcnlUZXN0J10sIFsnZ29vZy5uZXQuQ29yc1htbEh0dHBGYWN0b3J5JywgJ2dvb2cubmV0LkllQ29yc1hockFkYXB0ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9jcm9zc2RvbWFpbnJwYy5qcycsIFsnZ29vZy5uZXQuQ3Jvc3NEb21haW5ScGMnXSwgWydnb29nLlVyaScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmxvZycsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuSHR0cFN0YXR1cycsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2Nyb3NzZG9tYWlucnBjX3Rlc3QuanMnLCBbJ2dvb2cubmV0LkNyb3NzRG9tYWluUnBjVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmxvZycsICdnb29nLm5ldC5Dcm9zc0RvbWFpblJwYycsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2Vycm9yY29kZS5qcycsIFsnZ29vZy5uZXQuRXJyb3JDb2RlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2V2ZW50dHlwZS5qcycsIFsnZ29vZy5uZXQuRXZlbnRUeXBlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2ZldGNoeG1saHR0cGZhY3RvcnkuanMnLCBbJ2dvb2cubmV0LkZldGNoWG1sSHR0cCcsICdnb29nLm5ldC5GZXRjaFhtbEh0dHBGYWN0b3J5J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubG9nJywgJ2dvb2cubmV0Llhockxpa2UnLCAnZ29vZy5uZXQuWG1sSHR0cEZhY3RvcnknXSwgeydsYW5nJzogJ2VzNSd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvZmV0Y2h4bWxodHRwZmFjdG9yeV90ZXN0LmpzJywgWydnb29nLm5ldC5GZXRjaFhtbEh0dHBGYWN0b3J5VGVzdCddLCBbJ2dvb2cubmV0LkZldGNoWG1sSHR0cCcsICdnb29nLm5ldC5GZXRjaFhtbEh0dHBGYWN0b3J5JywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QuaXNWZXJzaW9uJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2ZpbGVkb3dubG9hZGVyLmpzJywgWydnb29nLm5ldC5GaWxlRG93bmxvYWRlcicsICdnb29nLm5ldC5GaWxlRG93bmxvYWRlci5FcnJvciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmNyeXB0Lmhhc2gzMicsICdnb29nLmRlYnVnLkVycm9yJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmZzJywgJ2dvb2cuZnMuRGlyZWN0b3J5RW50cnknLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVTYXZlcicsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWGhySW9Qb29sJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvZmlsZWRvd25sb2FkZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuRmlsZURvd25sb2FkZXJUZXN0J10sIFsnZ29vZy5mcy5FcnJvcicsICdnb29nLm5ldC5FcnJvckNvZGUnLCAnZ29vZy5uZXQuRmlsZURvd25sb2FkZXInLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5mcycsICdnb29nLnRlc3RpbmcuZnMuRmlsZVN5c3RlbScsICdnb29nLnRlc3RpbmcubmV0LlhocklvUG9vbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2h0dHBzdGF0dXMuanMnLCBbJ2dvb2cubmV0Lkh0dHBTdGF0dXMnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvaHR0cHN0YXR1c25hbWUuanMnLCBbJ2dvb2cubmV0Lkh0dHBTdGF0dXNOYW1lJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2lmcmFtZWlvLmpzJywgWydnb29nLm5ldC5JZnJhbWVJbycsICdnb29nLm5ldC5JZnJhbWVJby5JbmNyZW1lbnRhbERhdGFFdmVudCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5VcmknLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5IdG1sRm9ybWF0dGVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLklucHV0VHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5sZWdhY3ljb252ZXJzaW9ucycsICdnb29nLmh0bWwudW5jaGVja2VkY29udmVyc2lvbnMnLCAnZ29vZy5qc29uJywgJ2dvb2cubG9nJywgJ2dvb2cubG9nLkxldmVsJywgJ2dvb2cubmV0LkVycm9yQ29kZScsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5yZWZsZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3RydWN0cycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2lmcmFtZWlvX3Rlc3QuanMnLCBbJ2dvb2cubmV0LklmcmFtZUlvVGVzdCddLCBbJ2dvb2cuZGVidWcnLCAnZ29vZy5kZWJ1Zy5EaXZDb25zb2xlJywgJ2dvb2cuZGVidWcuTG9nTWFuYWdlcicsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmxvZycsICdnb29nLmxvZy5MZXZlbCcsICdnb29nLm5ldC5JZnJhbWVJbycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCcsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9pZnJhbWVsb2FkbW9uaXRvci5qcycsIFsnZ29vZy5uZXQuSWZyYW1lTG9hZE1vbml0b3InXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9pZnJhbWVsb2FkbW9uaXRvcl90ZXN0LmpzJywgWydnb29nLm5ldC5JZnJhbWVMb2FkTW9uaXRvclRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaW1lcicsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cubmV0LklmcmFtZUxvYWRNb25pdG9yJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvaW1hZ2Vsb2FkZXIuanMnLCBbJ2dvb2cubmV0LkltYWdlTG9hZGVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvaW1hZ2Vsb2FkZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuSW1hZ2VMb2FkZXJUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLmRpc3Bvc2UnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5JbWFnZUxvYWRlcicsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvaXBhZGRyZXNzLmpzJywgWydnb29nLm5ldC5JcEFkZHJlc3MnLCAnZ29vZy5uZXQuSXB2NEFkZHJlc3MnLCAnZ29vZy5uZXQuSXB2NkFkZHJlc3MnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubWF0aC5JbnRlZ2VyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvaXBhZGRyZXNzX3Rlc3QuanMnLCBbJ2dvb2cubmV0LklwQWRkcmVzc1Rlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cubWF0aC5JbnRlZ2VyJywgJ2dvb2cubmV0LklwQWRkcmVzcycsICdnb29nLm5ldC5JcHY0QWRkcmVzcycsICdnb29nLm5ldC5JcHY2QWRkcmVzcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2pzbG9hZGVyLmpzJywgWydnb29nLm5ldC5qc2xvYWRlcicsICdnb29nLm5ldC5qc2xvYWRlci5FcnJvcicsICdnb29nLm5ldC5qc2xvYWRlci5FcnJvckNvZGUnLCAnZ29vZy5uZXQuanNsb2FkZXIuT3B0aW9ucyddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmRlYnVnLkVycm9yJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvanNsb2FkZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuanNsb2FkZXJUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5uZXQuanNsb2FkZXInLCAnZ29vZy5uZXQuanNsb2FkZXIuRXJyb3JDb2RlJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvanNvbnAuanMnLCBbJ2dvb2cubmV0Lkpzb25wJ10sIFsnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLm5ldC5qc2xvYWRlcicsICdnb29nLm9iamVjdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L2pzb25wX3Rlc3QuanMnLCBbJ2dvb2cubmV0Lkpzb25wVGVzdCddLCBbJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5uZXQuSnNvbnAnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvbW9ja2lmcmFtZWlvLmpzJywgWydnb29nLm5ldC5Nb2NrSUZyYW1lSW8nXSwgWydnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLm5ldC5FcnJvckNvZGUnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cubmV0LklmcmFtZUlvJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvbXVsdGlpZnJhbWVsb2FkbW9uaXRvci5qcycsIFsnZ29vZy5uZXQuTXVsdGlJZnJhbWVMb2FkTW9uaXRvciddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cubmV0LklmcmFtZUxvYWRNb25pdG9yJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvbXVsdGlpZnJhbWVsb2FkbW9uaXRvcl90ZXN0LmpzJywgWydnb29nLm5ldC5NdWx0aUlmcmFtZUxvYWRNb25pdG9yVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5uZXQuTXVsdGlJZnJhbWVMb2FkTW9uaXRvcicsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L25ldHdvcmtzdGF0dXNtb25pdG9yLmpzJywgWydnb29nLm5ldC5OZXR3b3JrU3RhdHVzTW9uaXRvciddLCBbJ2dvb2cuZXZlbnRzLkxpc3RlbmFibGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9uZXR3b3JrdGVzdGVyLmpzJywgWydnb29nLm5ldC5OZXR3b3JrVGVzdGVyJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLlVyaScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cubG9nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvbmV0d29ya3Rlc3Rlcl90ZXN0LmpzJywgWydnb29nLm5ldC5OZXR3b3JrVGVzdGVyVGVzdCddLCBbJ2dvb2cuVXJpJywgJ2dvb2cubmV0Lk5ldHdvcmtUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3JwYy9odHRwY29ycy5qcycsIFsnZ29vZy5uZXQucnBjLkh0dHBDb3JzJ10sIFsnZ29vZy5VcmknLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy51cmkudXRpbHMnXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvcnBjL2h0dHBjb3JzX3Rlc3QuanMnLCBbJ2dvb2cubmV0LnJwYy5IdHRwQ29yc1Rlc3QnXSwgWydnb29nLlVyaScsICdnb29nLm5ldC5ycGMuSHR0cENvcnMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL2Jhc2U2NHBic3RyZWFtcGFyc2VyLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLkJhc2U2NFBiU3RyZWFtUGFyc2VyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubmV0LnN0cmVhbXMuQmFzZTY0U3RyZWFtRGVjb2RlcicsICdnb29nLm5ldC5zdHJlYW1zLlBiU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuU3RyZWFtUGFyc2VyJ10sIHsnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMvYmFzZTY0cGJzdHJlYW1wYXJzZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5CYXNlNjRQYlN0cmVhbVBhcnNlclRlc3QnXSwgWydnb29nLmNyeXB0LmJhc2U2NCcsICdnb29nLm5ldC5zdHJlYW1zLkJhc2U2NFBiU3RyZWFtUGFyc2VyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvc3RyZWFtcy9iYXNlNjRzdHJlYW1kZWNvZGVyLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLkJhc2U2NFN0cmVhbURlY29kZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5jcnlwdC5iYXNlNjQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL2Jhc2U2NHN0cmVhbWRlY29kZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5CYXNlNjRTdHJlYW1EZWNvZGVyVGVzdCddLCBbJ2dvb2cubmV0LnN0cmVhbXMuQmFzZTY0U3RyZWFtRGVjb2RlcicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMvanNvbnN0cmVhbXBhcnNlci5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5Kc29uU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuSnNvblN0cmVhbVBhcnNlci5PcHRpb25zJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubmV0LnN0cmVhbXMuU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMudXRpbHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL2pzb25zdHJlYW1wYXJzZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5Kc29uU3RyZWFtUGFyc2VyVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5qc29uJywgJ2dvb2cubGFicy50ZXN0aW5nLkpzb25GdXp6aW5nJywgJ2dvb2cubmV0LnN0cmVhbXMuSnNvblN0cmVhbVBhcnNlcicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXJpLnV0aWxzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMvbm9kZXJlYWRhYmxlc3RyZWFtLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLk5vZGVSZWFkYWJsZVN0cmVhbSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL3BianNvbnN0cmVhbXBhcnNlci5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5QYkpzb25TdHJlYW1QYXJzZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5uZXQuc3RyZWFtcy5Kc29uU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMudXRpbHMnXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvc3RyZWFtcy9wYmpzb25zdHJlYW1wYXJzZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5QYkpzb25TdHJlYW1QYXJzZXJUZXN0J10sIFsnZ29vZy5uZXQuc3RyZWFtcy5QYkpzb25TdHJlYW1QYXJzZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL3Bic3RyZWFtcGFyc2VyLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLlBiU3RyZWFtUGFyc2VyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubmV0LnN0cmVhbXMuU3RyZWFtUGFyc2VyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvc3RyZWFtcy9wYnN0cmVhbXBhcnNlcl90ZXN0LmpzJywgWydnb29nLm5ldC5zdHJlYW1zLlBiU3RyZWFtUGFyc2VyVGVzdCddLCBbJ2dvb2cubmV0LnN0cmVhbXMuUGJTdHJlYW1QYXJzZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL3N0cmVhbWZhY3RvcnkuanMnLCBbJ2dvb2cubmV0LnN0cmVhbXMuY3JlYXRlWGhyTm9kZVJlYWRhYmxlU3RyZWFtJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cubmV0LnN0cmVhbXMuWGhyTm9kZVJlYWRhYmxlU3RyZWFtJywgJ2dvb2cubmV0LnN0cmVhbXMuWGhyU3RyZWFtUmVhZGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvc3RyZWFtcy9zdHJlYW1wYXJzZXIuanMnLCBbJ2dvb2cubmV0LnN0cmVhbXMuU3RyZWFtUGFyc2VyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMvdXRpbHMuanMnLCBbJ2dvb2cubmV0LnN0cmVhbXMudXRpbHMnXSwgW10sIHsnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMveGhybm9kZXJlYWRhYmxlc3RyZWFtLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLlhock5vZGVSZWFkYWJsZVN0cmVhbSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5sb2cnLCAnZ29vZy5uZXQuc3RyZWFtcy5Ob2RlUmVhZGFibGVTdHJlYW0nLCAnZ29vZy5uZXQuc3RyZWFtcy5YaHJTdHJlYW1SZWFkZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC9zdHJlYW1zL3hocm5vZGVyZWFkYWJsZXN0cmVhbV90ZXN0LmpzJywgWydnb29nLm5ldC5zdHJlYW1zLlhock5vZGVSZWFkYWJsZVN0cmVhbVRlc3QnXSwgWydnb29nLm5ldC5zdHJlYW1zLk5vZGVSZWFkYWJsZVN0cmVhbScsICdnb29nLm5ldC5zdHJlYW1zLlhock5vZGVSZWFkYWJsZVN0cmVhbScsICdnb29nLm5ldC5zdHJlYW1zLlhoclN0cmVhbVJlYWRlcicsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3N0cmVhbXMveGhyc3RyZWFtcmVhZGVyLmpzJywgWydnb29nLm5ldC5zdHJlYW1zLlhoclN0cmVhbVJlYWRlciddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmxvZycsICdnb29nLm5ldC5FcnJvckNvZGUnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cubmV0Lkh0dHBTdGF0dXMnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm5ldC5zdHJlYW1zLkJhc2U2NFBiU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuSnNvblN0cmVhbVBhcnNlcicsICdnb29nLm5ldC5zdHJlYW1zLlBiSnNvblN0cmVhbVBhcnNlcicsICdnb29nLm5ldC5zdHJlYW1zLlBiU3RyZWFtUGFyc2VyJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvc3RyZWFtcy94aHJzdHJlYW1yZWFkZXJfdGVzdC5qcycsIFsnZ29vZy5uZXQuc3RyZWFtcy5YaHJTdHJlYW1SZWFkZXJUZXN0J10sIFsnZ29vZy5uZXQuRXJyb3JDb2RlJywgJ2dvb2cubmV0Lkh0dHBTdGF0dXMnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm5ldC5zdHJlYW1zLkJhc2U2NFBiU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuSnNvblN0cmVhbVBhcnNlcicsICdnb29nLm5ldC5zdHJlYW1zLlBiSnNvblN0cmVhbVBhcnNlcicsICdnb29nLm5ldC5zdHJlYW1zLlBiU3RyZWFtUGFyc2VyJywgJ2dvb2cubmV0LnN0cmVhbXMuWGhyU3RyZWFtUmVhZGVyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5uZXQuWGhySW8nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC90ZXN0ZGF0YS9qc2xvYWRlcl90ZXN0MS5qcycsIFsnZ29vZy5uZXQudGVzdGRhdGEuanNsb2FkZXJfdGVzdDEnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvdGVzdGRhdGEvanNsb2FkZXJfdGVzdDIuanMnLCBbJ2dvb2cubmV0LnRlc3RkYXRhLmpzbG9hZGVyX3Rlc3QyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3Rlc3RkYXRhL2pzbG9hZGVyX3Rlc3QzLmpzJywgWydnb29nLm5ldC50ZXN0ZGF0YS5qc2xvYWRlcl90ZXN0MyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC90ZXN0ZGF0YS9qc2xvYWRlcl90ZXN0NC5qcycsIFsnZ29vZy5uZXQudGVzdGRhdGEuanNsb2FkZXJfdGVzdDQnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvdG1wbmV0d29yay5qcycsIFsnZ29vZy5uZXQudG1wbmV0d29yayddLCBbJ2dvb2cuVXJpJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5uZXQuQ2hhbm5lbERlYnVnJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvd2Vic29ja2V0LmpzJywgWydnb29nLm5ldC5XZWJTb2NrZXQnLCAnZ29vZy5uZXQuV2ViU29ja2V0LkVycm9yRXZlbnQnLCAnZ29vZy5uZXQuV2ViU29ja2V0LkV2ZW50VHlwZScsICdnb29nLm5ldC5XZWJTb2NrZXQuTWVzc2FnZUV2ZW50J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5lbnRyeVBvaW50UmVnaXN0cnknLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5sb2cnXSwgeydsYW5nJzogJ2VzNSd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQvd2Vic29ja2V0X3Rlc3QuanMnLCBbJ2dvb2cubmV0LldlYlNvY2tldFRlc3QnXSwgWydnb29nLmRlYnVnLkVudHJ5UG9pbnRNb25pdG9yJywgJ2dvb2cuZGVidWcuRXJyb3JIYW5kbGVyJywgJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubmV0LldlYlNvY2tldCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3dyYXBwZXJ4bWxodHRwZmFjdG9yeS5qcycsIFsnZ29vZy5uZXQuV3JhcHBlclhtbEh0dHBGYWN0b3J5J10sIFsnZ29vZy5uZXQuWGhyTGlrZScsICdnb29nLm5ldC5YbWxIdHRwRmFjdG9yeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3hocmlvLmpzJywgWydnb29nLm5ldC5YaHJJbycsICdnb29nLm5ldC5YaHJJby5SZXNwb25zZVR5cGUnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuanNvbi5oeWJyaWQnLCAnZ29vZy5sb2cnLCAnZ29vZy5uZXQuRXJyb3JDb2RlJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5IdHRwU3RhdHVzJywgJ2dvb2cubmV0LlhtbEh0dHAnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJ1Y3RzJywgJ2dvb2cuc3RydWN0cy5NYXAnLCAnZ29vZy51cmkudXRpbHMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94aHJpb190ZXN0LmpzJywgWydnb29nLm5ldC5YaHJJb1Rlc3QnXSwgWydnb29nLlVyaScsICdnb29nLmRlYnVnLkVudHJ5UG9pbnRNb25pdG9yJywgJ2dvb2cuZGVidWcuRXJyb3JIYW5kbGVyJywgJ2dvb2cuZGVidWcuZW50cnlQb2ludFJlZ2lzdHJ5JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5XcmFwcGVyWG1sSHR0cEZhY3RvcnknLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnLCAnZ29vZy50ZXN0aW5nLm5ldC5YaHJJbycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94aHJpb3Bvb2wuanMnLCBbJ2dvb2cubmV0LlhocklvUG9vbCddLCBbJ2dvb2cubmV0LlhocklvJywgJ2dvb2cuc3RydWN0cy5Qcmlvcml0eVBvb2wnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94aHJpb3Bvb2xfdGVzdC5qcycsIFsnZ29vZy5uZXQuWGhySW9Qb29sVGVzdCddLCBbJ2dvb2cubmV0LlhocklvUG9vbCcsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveGhybGlrZS5qcycsIFsnZ29vZy5uZXQuWGhyTGlrZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94aHJtYW5hZ2VyLmpzJywgWydnb29nLm5ldC5YaHJNYW5hZ2VyJywgJ2dvb2cubmV0Llhock1hbmFnZXIuRXZlbnQnLCAnZ29vZy5uZXQuWGhyTWFuYWdlci5SZXF1ZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cubmV0LkVycm9yQ29kZScsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWGhySW9Qb29sJywgJ2dvb2cuc3RydWN0cy5NYXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94aHJtYW5hZ2VyX3Rlc3QuanMnLCBbJ2dvb2cubmV0Llhock1hbmFnZXJUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cubmV0LlhocklvJywgJ2dvb2cubmV0Llhock1hbmFnZXInLCAnZ29vZy50ZXN0aW5nLm5ldC5YaHJJb1Bvb2wnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveG1saHR0cC5qcycsIFsnZ29vZy5uZXQuRGVmYXVsdFhtbEh0dHBGYWN0b3J5JywgJ2dvb2cubmV0LlhtbEh0dHAnLCAnZ29vZy5uZXQuWG1sSHR0cC5PcHRpb25UeXBlJywgJ2dvb2cubmV0LlhtbEh0dHAuUmVhZHlTdGF0ZScsICdnb29nLm5ldC5YbWxIdHRwRGVmaW5lcyddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLm5ldC5XcmFwcGVyWG1sSHR0cEZhY3RvcnknLCAnZ29vZy5uZXQuWG1sSHR0cEZhY3RvcnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94bWxodHRwZmFjdG9yeS5qcycsIFsnZ29vZy5uZXQuWG1sSHR0cEZhY3RvcnknXSwgWydnb29nLm5ldC5YaHJMaWtlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveHBjL2Nyb3NzcGFnZWNoYW5uZWwuanMnLCBbJ2dvb2cubmV0LnhwYy5Dcm9zc1BhZ2VDaGFubmVsJ10sIFsnZ29vZy5VcmknLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmFzeW5jLkRlbGF5JywgJ2dvb2cuZGlzcG9zZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmh0bWwubGVnYWN5Y29udmVyc2lvbnMnLCAnZ29vZy5qc29uJywgJ2dvb2cubG9nJywgJ2dvb2cubWVzc2FnaW5nLkFic3RyYWN0Q2hhbm5lbCcsICdnb29nLm5ldC54cGMnLCAnZ29vZy5uZXQueHBjLkNmZ0ZpZWxkcycsICdnb29nLm5ldC54cGMuQ2hhbm5lbFN0YXRlcycsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnLCAnZ29vZy5uZXQueHBjLkRpcmVjdFRyYW5zcG9ydCcsICdnb29nLm5ldC54cGMuTmF0aXZlTWVzc2FnaW5nVHJhbnNwb3J0JywgJ2dvb2cubmV0LnhwYy5UcmFuc3BvcnRUeXBlcycsICdnb29nLm5ldC54cGMuVXJpQ2ZnRmllbGRzJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXJpLnV0aWxzJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveHBjL2Nyb3NzcGFnZWNoYW5uZWxfdGVzdC5qcycsIFsnZ29vZy5uZXQueHBjLkNyb3NzUGFnZUNoYW5uZWxUZXN0J10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuUHJvbWlzZScsICdnb29nLlRpbWVyJywgJ2dvb2cuVXJpJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC5icm93c2VyJywgJ2dvb2cubG9nJywgJ2dvb2cubG9nLkxldmVsJywgJ2dvb2cubmV0LnhwYycsICdnb29nLm5ldC54cGMuQ2ZnRmllbGRzJywgJ2dvb2cubmV0LnhwYy5Dcm9zc1BhZ2VDaGFubmVsJywgJ2dvb2cubmV0LnhwYy5Dcm9zc1BhZ2VDaGFubmVsUm9sZScsICdnb29nLm5ldC54cGMuVHJhbnNwb3J0VHlwZXMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnXSwgeydsYW5nJzogJ2VzOCd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveHBjL2Nyb3NzcGFnZWNoYW5uZWxyb2xlLmpzJywgWydnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveHBjL2RpcmVjdHRyYW5zcG9ydC5qcycsIFsnZ29vZy5uZXQueHBjLkRpcmVjdFRyYW5zcG9ydCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5uZXQueHBjJywgJ2dvb2cubmV0LnhwYy5DZmdGaWVsZHMnLCAnZ29vZy5uZXQueHBjLkNyb3NzUGFnZUNoYW5uZWxSb2xlJywgJ2dvb2cubmV0LnhwYy5UcmFuc3BvcnQnLCAnZ29vZy5uZXQueHBjLlRyYW5zcG9ydFR5cGVzJywgJ2dvb2cub2JqZWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCduZXQveHBjL2RpcmVjdHRyYW5zcG9ydF90ZXN0LmpzJywgWydnb29nLm5ldC54cGMuRGlyZWN0VHJhbnNwb3J0VGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLmxvZycsICdnb29nLmxvZy5MZXZlbCcsICdnb29nLm5ldC54cGMnLCAnZ29vZy5uZXQueHBjLkNmZ0ZpZWxkcycsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbCcsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnLCAnZ29vZy5uZXQueHBjLlRyYW5zcG9ydFR5cGVzJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3hwYy9pZnJhbWVwb2xsaW5ndHJhbnNwb3J0LmpzJywgWydnb29nLm5ldC54cGMuSWZyYW1lUG9sbGluZ1RyYW5zcG9ydCcsICdnb29nLm5ldC54cGMuSWZyYW1lUG9sbGluZ1RyYW5zcG9ydC5SZWNlaXZlcicsICdnb29nLm5ldC54cGMuSWZyYW1lUG9sbGluZ1RyYW5zcG9ydC5TZW5kZXInXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmxvZycsICdnb29nLmxvZy5MZXZlbCcsICdnb29nLm5ldC54cGMnLCAnZ29vZy5uZXQueHBjLkNmZ0ZpZWxkcycsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnLCAnZ29vZy5uZXQueHBjLlRyYW5zcG9ydCcsICdnb29nLm5ldC54cGMuVHJhbnNwb3J0VHlwZXMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94cGMvaWZyYW1lcG9sbGluZ3RyYW5zcG9ydF90ZXN0LmpzJywgWydnb29nLm5ldC54cGMuSWZyYW1lUG9sbGluZ1RyYW5zcG9ydFRlc3QnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5uZXQueHBjLkNmZ0ZpZWxkcycsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbCcsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnLCAnZ29vZy5uZXQueHBjLklmcmFtZVBvbGxpbmdUcmFuc3BvcnQnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94cGMvbmF0aXZlbWVzc2FnaW5ndHJhbnNwb3J0LmpzJywgWydnb29nLm5ldC54cGMuTmF0aXZlTWVzc2FnaW5nVHJhbnNwb3J0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5sb2cnLCAnZ29vZy5uZXQueHBjJywgJ2dvb2cubmV0LnhwYy5Dcm9zc1BhZ2VDaGFubmVsUm9sZScsICdnb29nLm5ldC54cGMuVHJhbnNwb3J0JywgJ2dvb2cubmV0LnhwYy5UcmFuc3BvcnRUeXBlcyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3hwYy9uYXRpdmVtZXNzYWdpbmd0cmFuc3BvcnRfdGVzdC5qcycsIFsnZ29vZy5uZXQueHBjLk5hdGl2ZU1lc3NhZ2luZ1RyYW5zcG9ydFRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLm5ldC54cGMnLCAnZ29vZy5uZXQueHBjLkNmZ0ZpZWxkcycsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbCcsICdnb29nLm5ldC54cGMuQ3Jvc3NQYWdlQ2hhbm5lbFJvbGUnLCAnZ29vZy5uZXQueHBjLk5hdGl2ZU1lc3NhZ2luZ1RyYW5zcG9ydCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3hwYy9yZWxheS5qcycsIFsnZ29vZy5uZXQueHBjLnJlbGF5J10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ25ldC94cGMvdHJhbnNwb3J0LmpzJywgWydnb29nLm5ldC54cGMuVHJhbnNwb3J0J10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuZG9tJywgJ2dvb2cubmV0LnhwYy5UcmFuc3BvcnROYW1lcyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnbmV0L3hwYy94cGMuanMnLCBbJ2dvb2cubmV0LnhwYycsICdnb29nLm5ldC54cGMuQ2ZnRmllbGRzJywgJ2dvb2cubmV0LnhwYy5DaGFubmVsU3RhdGVzJywgJ2dvb2cubmV0LnhwYy5UcmFuc3BvcnROYW1lcycsICdnb29nLm5ldC54cGMuVHJhbnNwb3J0VHlwZXMnLCAnZ29vZy5uZXQueHBjLlVyaUNmZ0ZpZWxkcyddLCBbJ2dvb2cubG9nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdvYmplY3Qvb2JqZWN0LmpzJywgWydnb29nLm9iamVjdCddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdvYmplY3Qvb2JqZWN0X3Rlc3QuanMnLCBbJ2dvb2cub2JqZWN0VGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwb3NpdGlvbmluZy9hYnNvbHV0ZXBvc2l0aW9uLmpzJywgWydnb29nLnBvc2l0aW9uaW5nLkFic29sdXRlUG9zaXRpb24nXSwgWydnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnBvc2l0aW9uaW5nJywgJ2dvb2cucG9zaXRpb25pbmcuQWJzdHJhY3RQb3NpdGlvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvYWJzdHJhY3Rwb3NpdGlvbi5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5BYnN0cmFjdFBvc2l0aW9uJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvYW5jaG9yZWRwb3NpdGlvbi5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5BbmNob3JlZFBvc2l0aW9uJ10sIFsnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkFic3RyYWN0UG9zaXRpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL2FuY2hvcmVkcG9zaXRpb25fdGVzdC5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5BbmNob3JlZFBvc2l0aW9uVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRQb3NpdGlvbicsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL2FuY2hvcmVkdmlld3BvcnRwb3NpdGlvbi5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5BbmNob3JlZFZpZXdwb3J0UG9zaXRpb24nXSwgWydnb29nLnBvc2l0aW9uaW5nJywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRQb3NpdGlvbicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93JywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3dTdGF0dXMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL2FuY2hvcmVkdmlld3BvcnRwb3NpdGlvbl90ZXN0LmpzJywgWydnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkVmlld3BvcnRQb3NpdGlvblRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLm1hdGguQm94JywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRWaWV3cG9ydFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3dTdGF0dXMnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvY2xpZW50cG9zaXRpb24uanMnLCBbJ2dvb2cucG9zaXRpb25pbmcuQ2xpZW50UG9zaXRpb24nXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkFic3RyYWN0UG9zaXRpb24nLCAnZ29vZy5zdHlsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvY2xpZW50cG9zaXRpb25fdGVzdC5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5jbGllbnRQb3NpdGlvblRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cucG9zaXRpb25pbmcuQ2xpZW50UG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvbWVudWFuY2hvcmVkcG9zaXRpb24uanMnLCBbJ2dvb2cucG9zaXRpb25pbmcuTWVudUFuY2hvcmVkUG9zaXRpb24nXSwgWydnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkVmlld3BvcnRQb3NpdGlvbicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwb3NpdGlvbmluZy9tZW51YW5jaG9yZWRwb3NpdGlvbl90ZXN0LmpzJywgWydnb29nLnBvc2l0aW9uaW5nLk1lbnVBbmNob3JlZFBvc2l0aW9uVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5wb3NpdGlvbmluZy5NZW51QW5jaG9yZWRQb3NpdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncG9zaXRpb25pbmcvcG9zaXRpb25pbmcuanMnLCBbJ2dvb2cucG9zaXRpb25pbmcnLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXJCaXQnLCAnZ29vZy5wb3NpdGlvbmluZy5PdmVyZmxvdycsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93U3RhdHVzJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlJlY3QnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLmJpZGknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL3Bvc2l0aW9uaW5nX3Rlc3QuanMnLCBbJ2dvb2cucG9zaXRpb25pbmdUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uRG9tSGVscGVyJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC5icm93c2VyJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93JywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3dTdGF0dXMnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwb3NpdGlvbmluZy92aWV3cG9ydGNsaWVudHBvc2l0aW9uLmpzJywgWydnb29nLnBvc2l0aW9uaW5nLlZpZXdwb3J0Q2xpZW50UG9zaXRpb24nXSwgWydnb29nLmRvbScsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnBvc2l0aW9uaW5nJywgJ2dvb2cucG9zaXRpb25pbmcuQ2xpZW50UG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5PdmVyZmxvdycsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93U3RhdHVzJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL3ZpZXdwb3J0Y2xpZW50cG9zaXRpb25fdGVzdC5qcycsIFsnZ29vZy5wb3NpdGlvbmluZy5WaWV3cG9ydENsaWVudFBvc2l0aW9uVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3cnLCAnZ29vZy5wb3NpdGlvbmluZy5WaWV3cG9ydENsaWVudFBvc2l0aW9uJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Bvc2l0aW9uaW5nL3ZpZXdwb3J0cG9zaXRpb24uanMnLCBbJ2dvb2cucG9zaXRpb25pbmcuVmlld3BvcnRQb3NpdGlvbiddLCBbJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cucG9zaXRpb25pbmcnLCAnZ29vZy5wb3NpdGlvbmluZy5BYnN0cmFjdFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb21pc2UvbmF0aXZlcmVzb2x2ZXIuanMnLCBbJ2dvb2cucHJvbWlzZS5OYXRpdmVSZXNvbHZlciddLCBbXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm9taXNlL25hdGl2ZXJlc29sdmVyX3Rlc3QuanMnLCBbJ2dvb2cucHJvbWlzZS5uYXRpdmVSZXNvbHZlclRlc3QnXSwgWydnb29nLnByb21pc2UuTmF0aXZlUmVzb2x2ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb21pc2UvcHJvbWlzZS5qcycsIFsnZ29vZy5Qcm9taXNlJ10sIFsnZ29vZy5UaGVuYWJsZScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5GcmVlTGlzdCcsICdnb29nLmFzeW5jLnJ1bicsICdnb29nLmFzeW5jLnRocm93RXhjZXB0aW9uJywgJ2dvb2cuZGVidWcuRXJyb3InLCAnZ29vZy5wcm9taXNlLlJlc29sdmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm9taXNlL3Byb21pc2VfdGVzdC5qcycsIFsnZ29vZy5Qcm9taXNlVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLlRoZW5hYmxlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzOCcsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm9taXNlL3Jlc29sdmVyLmpzJywgWydnb29nLnByb21pc2UuUmVzb2x2ZXInXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm9taXNlL3Rlc3RzdWl0ZWFkYXB0ZXIuanMnLCBbJ2dvb2cucHJvbWlzZS50ZXN0U3VpdGVBZGFwdGVyJ10sIFsnZ29vZy5Qcm9taXNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm9taXNlL3RoZW5hYmxlLmpzJywgWydnb29nLlRoZW5hYmxlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL2Rlc2NyaXB0b3IuanMnLCBbJ2dvb2cucHJvdG8yLkRlc2NyaXB0b3InLCAnZ29vZy5wcm90bzIuTWV0YWRhdGEnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL2Rlc2NyaXB0b3JfdGVzdC5qcycsIFsnZ29vZy5wcm90bzIuRGVzY3JpcHRvclRlc3QnXSwgWydnb29nLnByb3RvMi5EZXNjcmlwdG9yJywgJ2dvb2cucHJvdG8yLk1lc3NhZ2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi9maWVsZGRlc2NyaXB0b3IuanMnLCBbJ2dvb2cucHJvdG8yLkZpZWxkRGVzY3JpcHRvciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL2ZpZWxkZGVzY3JpcHRvcl90ZXN0LmpzJywgWydnb29nLnByb3RvMi5GaWVsZERlc2NyaXB0b3JUZXN0J10sIFsnZ29vZy5wcm90bzIuRmllbGREZXNjcmlwdG9yJywgJ2dvb2cucHJvdG8yLk1lc3NhZ2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi9sYXp5ZGVzZXJpYWxpemVyLmpzJywgWydnb29nLnByb3RvMi5MYXp5RGVzZXJpYWxpemVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cucHJvdG8yLk1lc3NhZ2UnLCAnZ29vZy5wcm90bzIuU2VyaWFsaXplciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL21lc3NhZ2UuanMnLCBbJ2dvb2cucHJvdG8yLk1lc3NhZ2UnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5wcm90bzIuRGVzY3JpcHRvcicsICdnb29nLnByb3RvMi5GaWVsZERlc2NyaXB0b3InXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi9tZXNzYWdlX3Rlc3QuanMnLCBbJ2dvb2cucHJvdG8yLk1lc3NhZ2VUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdwcm90bzIuVGVzdEFsbFR5cGVzJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMuTmVzdGVkRW51bScsICdwcm90bzIuVGVzdEFsbFR5cGVzLk5lc3RlZE1lc3NhZ2UnLCAncHJvdG8yLlRlc3RBbGxUeXBlcy5PcHRpb25hbEdyb3VwJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMuUmVwZWF0ZWRHcm91cCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi9vYmplY3RzZXJpYWxpemVyLmpzJywgWydnb29nLnByb3RvMi5PYmplY3RTZXJpYWxpemVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cucHJvdG8yLkZpZWxkRGVzY3JpcHRvcicsICdnb29nLnByb3RvMi5TZXJpYWxpemVyJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90bzIvb2JqZWN0c2VyaWFsaXplcl90ZXN0LmpzJywgWydnb29nLnByb3RvMi5PYmplY3RTZXJpYWxpemVyVGVzdCddLCBbJ2dvb2cucHJvdG8yLk9iamVjdFNlcmlhbGl6ZXInLCAnZ29vZy5wcm90bzIuU2VyaWFsaXplcicsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90bzIvcGFja2FnZV90ZXN0LnBiLmpzJywgWydzb21lcHJvdG9wYWNrYWdlLlRlc3RQYWNrYWdlVHlwZXMnXSwgWydnb29nLnByb3RvMi5NZXNzYWdlJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90bzIvcGJsaXRlc2VyaWFsaXplci5qcycsIFsnZ29vZy5wcm90bzIuUGJMaXRlU2VyaWFsaXplciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLnByb3RvMi5GaWVsZERlc2NyaXB0b3InLCAnZ29vZy5wcm90bzIuTGF6eURlc2VyaWFsaXplcicsICdnb29nLnByb3RvMi5TZXJpYWxpemVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90bzIvcGJsaXRlc2VyaWFsaXplcl90ZXN0LmpzJywgWydnb29nLnByb3RvMi5QYkxpdGVTZXJpYWxpemVyVGVzdCddLCBbJ2dvb2cucHJvdG8yLlBiTGl0ZVNlcmlhbGl6ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdwcm90bzIuVGVzdEFsbFR5cGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL3Byb3RvX3Rlc3QuanMnLCBbJ2dvb2cucHJvdG8yLm1lc3NhZ2VUZXN0J10sIFsnZ29vZy5wcm90bzIuRmllbGREZXNjcmlwdG9yJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAncHJvdG8yLlRlc3RBbGxUeXBlcycsICdwcm90bzIuVGVzdERlZmF1bHRQYXJlbnQnLCAnc29tZXByb3RvcGFja2FnZS5UZXN0UGFja2FnZVR5cGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHJvdG8yL3NlcmlhbGl6ZXIuanMnLCBbJ2dvb2cucHJvdG8yLlNlcmlhbGl6ZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5wcm90bzIuRmllbGREZXNjcmlwdG9yJywgJ2dvb2cucHJvdG8yLk1lc3NhZ2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi90ZXN0LnBiLmpzJywgWydwcm90bzIuVGVzdEFsbFR5cGVzJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMuTmVzdGVkRW51bScsICdwcm90bzIuVGVzdEFsbFR5cGVzLk5lc3RlZE1lc3NhZ2UnLCAncHJvdG8yLlRlc3RBbGxUeXBlcy5PcHRpb25hbEdyb3VwJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMuUmVwZWF0ZWRHcm91cCcsICdwcm90bzIuVGVzdERlZmF1bHRDaGlsZCcsICdwcm90bzIuVGVzdERlZmF1bHRQYXJlbnQnXSwgWydnb29nLnByb3RvMi5NZXNzYWdlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwcm90bzIvdGV4dGZvcm1hdHNlcmlhbGl6ZXIuanMnLCBbJ2dvb2cucHJvdG8yLlRleHRGb3JtYXRTZXJpYWxpemVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5tYXRoJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cucHJvdG8yLkZpZWxkRGVzY3JpcHRvcicsICdnb29nLnByb3RvMi5NZXNzYWdlJywgJ2dvb2cucHJvdG8yLlNlcmlhbGl6ZXInLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi90ZXh0Zm9ybWF0c2VyaWFsaXplcl90ZXN0LmpzJywgWydnb29nLnByb3RvMi5UZXh0Rm9ybWF0U2VyaWFsaXplclRlc3QnXSwgWydnb29nLnByb3RvMi5PYmplY3RTZXJpYWxpemVyJywgJ2dvb2cucHJvdG8yLlRleHRGb3JtYXRTZXJpYWxpemVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAncHJvdG8yLlRlc3RBbGxUeXBlcyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Byb3RvMi91dGlsLmpzJywgWydnb29nLnByb3RvMi5VdGlsJ10sIFsnZ29vZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwdWJzdWIvcHVic3ViLmpzJywgWydnb29nLnB1YnN1Yi5QdWJTdWInXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLnJ1biddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHVic3ViL3B1YnN1Yl90ZXN0LmpzJywgWydnb29nLnB1YnN1Yi5QdWJTdWJUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLnB1YnN1Yi5QdWJTdWInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHVic3ViL3RvcGljaWQuanMnLCBbJ2dvb2cucHVic3ViLlRvcGljSWQnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdwdWJzdWIvdHlwZWRwdWJzdWIuanMnLCBbJ2dvb2cucHVic3ViLlR5cGVkUHViU3ViJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cucHVic3ViLlB1YlN1YiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncHVic3ViL3R5cGVkcHVic3ViX3Rlc3QuanMnLCBbJ2dvb2cucHVic3ViLlR5cGVkUHViU3ViVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5wdWJzdWIuVG9waWNJZCcsICdnb29nLnB1YnN1Yi5UeXBlZFB1YlN1YicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVmbGVjdC9yZWZsZWN0LmpzJywgWydnb29nLnJlZmxlY3QnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVmbGVjdC9yZWZsZWN0X3Rlc3QuanMnLCBbJ2dvb2cucmVmbGVjdFRlc3QnXSwgWydnb29nLm9iamVjdCcsICdnb29nLnJlZmxlY3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC9jaGFpbl90ZXN0LmpzJywgWydnb29nLnJlc3VsdC5jaGFpblRlc3QnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cucmVzdWx0JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdyZXN1bHQvY29tYmluZV90ZXN0LmpzJywgWydnb29nLnJlc3VsdC5jb21iaW5lVGVzdCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLnJlc3VsdCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVzdWx0L2RlZmVycmVkYWRhcHRvci5qcycsIFsnZ29vZy5yZXN1bHQuRGVmZXJyZWRBZGFwdG9yJ10sIFsnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLnJlc3VsdCcsICdnb29nLnJlc3VsdC5SZXN1bHQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC9kZWZlcnJlZGFkYXB0b3JfdGVzdC5qcycsIFsnZ29vZy5yZXN1bHQuRGVmZXJyZWRBZGFwdG9yVGVzdCddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5yZXN1bHQnLCAnZ29vZy5yZXN1bHQuRGVmZXJyZWRBZGFwdG9yJywgJ2dvb2cucmVzdWx0LlNpbXBsZVJlc3VsdCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC9kZXBlbmRlbnRyZXN1bHQuanMnLCBbJ2dvb2cucmVzdWx0LkRlcGVuZGVudFJlc3VsdCddLCBbJ2dvb2cucmVzdWx0LlJlc3VsdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVzdWx0L3Jlc3VsdF9pbnRlcmZhY2UuanMnLCBbJ2dvb2cucmVzdWx0LlJlc3VsdCddLCBbJ2dvb2cuVGhlbmFibGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC9yZXN1bHR1dGlsLmpzJywgWydnb29nLnJlc3VsdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5yZXN1bHQuRGVwZW5kZW50UmVzdWx0JywgJ2dvb2cucmVzdWx0LlJlc3VsdCcsICdnb29nLnJlc3VsdC5TaW1wbGVSZXN1bHQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC9yZXN1bHR1dGlsX3Rlc3QuanMnLCBbJ2dvb2cucmVzdWx0VGVzdCddLCBbJ2dvb2cucmVzdWx0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdyZXN1bHQvc2ltcGxlcmVzdWx0LmpzJywgWydnb29nLnJlc3VsdC5TaW1wbGVSZXN1bHQnLCAnZ29vZy5yZXN1bHQuU2ltcGxlUmVzdWx0LlN0YXRlRXJyb3InXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaGVuYWJsZScsICdnb29nLmRlYnVnLkVycm9yJywgJ2dvb2cucmVzdWx0LlJlc3VsdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVzdWx0L3NpbXBsZXJlc3VsdF90ZXN0LmpzJywgWydnb29nLnJlc3VsdC5TaW1wbGVSZXN1bHRUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuVGhlbmFibGUnLCAnZ29vZy5UaW1lcicsICdnb29nLnJlc3VsdCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgncmVzdWx0L3RyYW5zZm9ybV90ZXN0LmpzJywgWydnb29nLnJlc3VsdC50cmFuc2Zvcm1UZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLnJlc3VsdCcsICdnb29nLnJlc3VsdC5TaW1wbGVSZXN1bHQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Jlc3VsdC93YWl0X3Rlc3QuanMnLCBbJ2dvb2cucmVzdWx0LndhaXRUZXN0J10sIFsnZ29vZy5UaW1lcicsICdnb29nLnJlc3VsdCcsICdnb29nLnJlc3VsdC5TaW1wbGVSZXN1bHQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3NveS9kYXRhLmpzJywgWydnb29nLnNveS5kYXRhLlNhbml0aXplZENvbnRlbnQnLCAnZ29vZy5zb3kuZGF0YS5TYW5pdGl6ZWRDb250ZW50S2luZCcsICdnb29nLnNveS5kYXRhLlNhbml0aXplZENzcycsICdnb29nLnNveS5kYXRhLlNhbml0aXplZEh0bWwnLCAnZ29vZy5zb3kuZGF0YS5TYW5pdGl6ZWRIdG1sQXR0cmlidXRlJywgJ2dvb2cuc295LmRhdGEuU2FuaXRpemVkSnMnLCAnZ29vZy5zb3kuZGF0YS5TYW5pdGl6ZWRUcnVzdGVkUmVzb3VyY2VVcmknLCAnZ29vZy5zb3kuZGF0YS5TYW5pdGl6ZWRVcmknXSwgWydnb29nLlVyaScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaHRtbC5TYWZlU2NyaXB0JywgJ2dvb2cuaHRtbC5TYWZlU3R5bGUnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5odG1sLnVuY2hlY2tlZGNvbnZlcnNpb25zJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLnN0cmluZy5Db25zdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc295L2RhdGFfdGVzdC5qcycsIFsnZ29vZy5zb3kuZGF0YVRlc3QnXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5zb3kudGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc295L3JlbmRlcmVyLmpzJywgWydnb29nLnNveS5JbmplY3RlZERhdGFTdXBwbGllcicsICdnb29nLnNveS5SZW5kZXJlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLnNveScsICdnb29nLnNveS5kYXRhLlNhbml0aXplZENvbnRlbnQnLCAnZ29vZy5zb3kuZGF0YS5TYW5pdGl6ZWRDb250ZW50S2luZCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc295L3JlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cuc295LlJlbmRlcmVyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuaTE4bi5iaWRpLkRpcicsICdnb29nLnNveS5SZW5kZXJlcicsICdnb29nLnNveS5kYXRhLlNhbml0aXplZENvbnRlbnRLaW5kJywgJ2dvb2cuc295LnRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzb3kvc295LmpzJywgWydnb29nLnNveSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cuc295LmRhdGEuU2FuaXRpemVkQ29udGVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc295L3NveV90ZXN0LmpzJywgWydnb29nLnNveVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuc295JywgJ2dvb2cuc295LnRlc3RIZWxwZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3NveS9zb3lfdGVzdGhlbHBlci5qcycsIFsnZ29vZy5zb3kudGVzdEhlbHBlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5pMThuLmJpZGkuRGlyJywgJ2dvb2cuc295LmRhdGEuU2FuaXRpemVkQ29udGVudCcsICdnb29nLnNveS5kYXRhLlNhbml0aXplZENvbnRlbnRLaW5kJywgJ2dvb2cuc295LmRhdGEuU2FuaXRpemVkQ3NzJywgJ2dvb2cuc295LmRhdGEuU2FuaXRpemVkVHJ1c3RlZFJlc291cmNlVXJpJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3BlbGwvc3BlbGxjaGVjay5qcycsIFsnZ29vZy5zcGVsbC5TcGVsbENoZWNrJywgJ2dvb2cuc3BlbGwuU3BlbGxDaGVjay5Xb3JkQ2hhbmdlZEV2ZW50J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnN0cnVjdHMuU2V0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzcGVsbC9zcGVsbGNoZWNrX3Rlc3QuanMnLCBbJ2dvb2cuc3BlbGwuU3BlbGxDaGVja1Rlc3QnXSwgWydnb29nLnNwZWxsLlNwZWxsQ2hlY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0YXRzL2Jhc2ljc3RhdC5qcycsIFsnZ29vZy5zdGF0cy5CYXNpY1N0YXQnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5sb2cnLCAnZ29vZy5zdHJpbmcuZm9ybWF0JywgJ2dvb2cuc3RydWN0cy5DaXJjdWxhckJ1ZmZlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RhdHMvYmFzaWNzdGF0X3Rlc3QuanMnLCBbJ2dvb2cuc3RhdHMuQmFzaWNTdGF0VGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5zdGF0cy5CYXNpY1N0YXQnLCAnZ29vZy5zdHJpbmcuZm9ybWF0JywgJ2dvb2cudGVzdGluZy5Qc2V1ZG9SYW5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvY29sbGVjdGFibGVzdG9yYWdlLmpzJywgWydnb29nLnN0b3JhZ2UuQ29sbGVjdGFibGVTdG9yYWdlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLml0ZXInLCAnZ29vZy5zdG9yYWdlLkVycm9yQ29kZScsICdnb29nLnN0b3JhZ2UuRXhwaXJpbmdTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5SaWNoU3RvcmFnZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9jb2xsZWN0YWJsZXN0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy5zdG9yYWdlLkNvbGxlY3RhYmxlU3RvcmFnZVRlc3QnXSwgWydnb29nLnN0b3JhZ2UuQ29sbGVjdGFibGVTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5jb2xsZWN0YWJsZVN0b3JhZ2VUZXN0ZXInLCAnZ29vZy5zdG9yYWdlLnN0b3JhZ2VUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3Rpbmcuc3RvcmFnZS5GYWtlTWVjaGFuaXNtJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL2NvbGxlY3RhYmxlc3RvcmFnZXRlc3Rlci5qcycsIFsnZ29vZy5zdG9yYWdlLmNvbGxlY3RhYmxlU3RvcmFnZVRlc3RlciddLCBbJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL2VuY3J5cHRlZHN0b3JhZ2UuanMnLCBbJ2dvb2cuc3RvcmFnZS5FbmNyeXB0ZWRTdG9yYWdlJ10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0LkFyYzQnLCAnZ29vZy5jcnlwdC5TaGExJywgJ2dvb2cuY3J5cHQuYmFzZTY0JywgJ2dvb2cuanNvbicsICdnb29nLmpzb24uU2VyaWFsaXplcicsICdnb29nLnN0b3JhZ2UuQ29sbGVjdGFibGVTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5FcnJvckNvZGUnLCAnZ29vZy5zdG9yYWdlLlJpY2hTdG9yYWdlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL2VuY3J5cHRlZHN0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy5zdG9yYWdlLkVuY3J5cHRlZFN0b3JhZ2VUZXN0J10sIFsnZ29vZy5qc29uJywgJ2dvb2cuc3RvcmFnZS5FbmNyeXB0ZWRTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5FcnJvckNvZGUnLCAnZ29vZy5zdG9yYWdlLlJpY2hTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5jb2xsZWN0YWJsZVN0b3JhZ2VUZXN0ZXInLCAnZ29vZy5zdG9yYWdlLnN0b3JhZ2VUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuUHNldWRvUmFuZG9tJywgJ2dvb2cudGVzdGluZy5zdG9yYWdlLkZha2VNZWNoYW5pc20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvZXJyb3Jjb2RlLmpzJywgWydnb29nLnN0b3JhZ2UuRXJyb3JDb2RlJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9leHBpcmluZ3N0b3JhZ2UuanMnLCBbJ2dvb2cuc3RvcmFnZS5FeHBpcmluZ1N0b3JhZ2UnXSwgWydnb29nLnN0b3JhZ2UuUmljaFN0b3JhZ2UnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvZXhwaXJpbmdzdG9yYWdlX3Rlc3QuanMnLCBbJ2dvb2cuc3RvcmFnZS5FeHBpcmluZ1N0b3JhZ2VUZXN0J10sIFsnZ29vZy5zdG9yYWdlLkV4cGlyaW5nU3RvcmFnZScsICdnb29nLnN0b3JhZ2Uuc3RvcmFnZVRlc3RlcicsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5zdG9yYWdlLkZha2VNZWNoYW5pc20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvbWVjaGFuaXNtL2Vycm9yY29kZS5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5FcnJvckNvZGUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9lcnJvcmhhbmRsaW5nbWVjaGFuaXNtLmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkVycm9ySGFuZGxpbmdNZWNoYW5pc20nXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLk1lY2hhbmlzbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vZXJyb3JoYW5kbGluZ21lY2hhbmlzbV90ZXN0LmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkVycm9ySGFuZGxpbmdNZWNoYW5pc21UZXN0J10sIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5FcnJvckhhbmRsaW5nTWVjaGFuaXNtJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vaHRtbDVsb2NhbHN0b3JhZ2UuanMnLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSFRNTDVMb2NhbFN0b3JhZ2UnXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1V2ViU3RvcmFnZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vaHRtbDVsb2NhbHN0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5IVE1MNUxvY2FsU3RvcmFnZVRlc3QnXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1TG9jYWxTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20ubWVjaGFuaXNtU2VwYXJhdGlvblRlc3RlcicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVNoYXJpbmdUZXN0ZXInLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21UZXN0RGVmaW5pdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9odG1sNXNlc3Npb25zdG9yYWdlLmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1U2Vzc2lvblN0b3JhZ2UnXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1V2ViU3RvcmFnZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vaHRtbDVzZXNzaW9uc3RvcmFnZV90ZXN0LmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1U2Vzc2lvblN0b3JhZ2VUZXN0J10sIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5IVE1MNVNlc3Npb25TdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20ubWVjaGFuaXNtU2VwYXJhdGlvblRlc3RlcicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVNoYXJpbmdUZXN0ZXInLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21UZXN0RGVmaW5pdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9odG1sNXdlYnN0b3JhZ2UuanMnLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSFRNTDVXZWJTdG9yYWdlJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaXRlci5JdGVyYXRvcicsICdnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkVycm9yQ29kZScsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkl0ZXJhYmxlTWVjaGFuaXNtJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9odG1sNXdlYnN0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5IVE1MNVdlYlN0b3JhZ2VUZXN0J10sIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5FcnJvckNvZGUnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5IVE1MNVdlYlN0b3JhZ2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvbWVjaGFuaXNtL2lldXNlcmRhdGEuanMnLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSUVVc2VyRGF0YSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLml0ZXIuSXRlcmF0b3InLCAnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5FcnJvckNvZGUnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5JdGVyYWJsZU1lY2hhbmlzbScsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9pZXVzZXJkYXRhX3Rlc3QuanMnLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSUVVc2VyRGF0YVRlc3QnXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLklFVXNlckRhdGEnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21TZXBhcmF0aW9uVGVzdGVyJywgJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20ubWVjaGFuaXNtU2hhcmluZ1Rlc3RlcicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVRlc3REZWZpbml0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9pdGVyYWJsZW1lY2hhbmlzbS5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5JdGVyYWJsZU1lY2hhbmlzbSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaXRlcicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLk1lY2hhbmlzbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vaXRlcmFibGVtZWNoYW5pc210ZXN0ZXIuanMnLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uaXRlcmFibGVNZWNoYW5pc21UZXN0ZXInXSwgWydnb29nLml0ZXInLCAnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvbWVjaGFuaXNtL21lY2hhbmlzbS5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5NZWNoYW5pc20nXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9tZWNoYW5pc21mYWN0b3J5LmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbWZhY3RvcnknXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkhUTUw1TG9jYWxTdG9yYWdlJywgJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSFRNTDVTZXNzaW9uU3RvcmFnZScsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLklFVXNlckRhdGEnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5QcmVmaXhlZE1lY2hhbmlzbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RvcmFnZS9tZWNoYW5pc20vbWVjaGFuaXNtZmFjdG9yeV90ZXN0LmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbWZhY3RvcnlUZXN0J10sIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21mYWN0b3J5JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9tZWNoYW5pc21zZXBhcmF0aW9udGVzdGVyLmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVNlcGFyYXRpb25UZXN0ZXInXSwgWydnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVRlc3REZWZpbml0aW9uJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9tZWNoYW5pc21zaGFyaW5ndGVzdGVyLmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVNoYXJpbmdUZXN0ZXInXSwgWydnb29nLml0ZXIuU3RvcEl0ZXJhdGlvbicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVRlc3REZWZpbml0aW9uJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9tZWNoYW5pc210ZXN0ZGVmaW5pdGlvbi5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21UZXN0RGVmaW5pdGlvbiddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2UvbWVjaGFuaXNtL21lY2hhbmlzbXRlc3Rlci5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21UZXN0ZXInXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkVycm9yQ29kZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QuaXNWZXJzaW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9wcmVmaXhlZG1lY2hhbmlzbS5qcycsIFsnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5QcmVmaXhlZE1lY2hhbmlzbSddLCBbJ2dvb2cuaXRlci5JdGVyYXRvcicsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkl0ZXJhYmxlTWVjaGFuaXNtJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL21lY2hhbmlzbS9wcmVmaXhlZG1lY2hhbmlzbV90ZXN0LmpzJywgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLlByZWZpeGVkTWVjaGFuaXNtVGVzdCddLCBbJ2dvb2cuc3RvcmFnZS5tZWNoYW5pc20uSFRNTDVMb2NhbFN0b3JhZ2UnLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5QcmVmaXhlZE1lY2hhbmlzbScsICdnb29nLnN0b3JhZ2UubWVjaGFuaXNtLm1lY2hhbmlzbVNlcGFyYXRpb25UZXN0ZXInLCAnZ29vZy5zdG9yYWdlLm1lY2hhbmlzbS5tZWNoYW5pc21TaGFyaW5nVGVzdGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL3JpY2hzdG9yYWdlLmpzJywgWydnb29nLnN0b3JhZ2UuUmljaFN0b3JhZ2UnLCAnZ29vZy5zdG9yYWdlLlJpY2hTdG9yYWdlLldyYXBwZXInXSwgWydnb29nLnN0b3JhZ2UuRXJyb3JDb2RlJywgJ2dvb2cuc3RvcmFnZS5TdG9yYWdlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL3JpY2hzdG9yYWdlX3Rlc3QuanMnLCBbJ2dvb2cuc3RvcmFnZS5SaWNoU3RvcmFnZVRlc3QnXSwgWydnb29nLnN0b3JhZ2UuRXJyb3JDb2RlJywgJ2dvb2cuc3RvcmFnZS5SaWNoU3RvcmFnZScsICdnb29nLnN0b3JhZ2Uuc3RvcmFnZVRlc3RlcicsICdnb29nLnRlc3Rpbmcuc3RvcmFnZS5GYWtlTWVjaGFuaXNtJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL3N0b3JhZ2UuanMnLCBbJ2dvb2cuc3RvcmFnZS5TdG9yYWdlJ10sIFsnZ29vZy5qc29uJywgJ2dvb2cuc3RvcmFnZS5FcnJvckNvZGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0b3JhZ2Uvc3RvcmFnZV90ZXN0LmpzJywgWydnb29nLnN0b3JhZ2Uuc3RvcmFnZV90ZXN0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5zdG9yYWdlLkVycm9yQ29kZScsICdnb29nLnN0b3JhZ2UuU3RvcmFnZScsICdnb29nLnN0b3JhZ2Uuc3RvcmFnZVRlc3RlcicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3Rpbmcuc3RvcmFnZS5GYWtlTWVjaGFuaXNtJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdG9yYWdlL3N0b3JhZ2V0ZXN0ZXIuanMnLCBbJ2dvb2cuc3RvcmFnZS5zdG9yYWdlVGVzdGVyJ10sIFsnZ29vZy5zdG9yYWdlLlN0b3JhZ2UnLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9kZWZpbmVzLmpzJywgWydnb29nLnN0cmVhbXMuZGVmaW5lcyddLCBbXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJlYW1zL2Z1bGwuanMnLCBbJ2dvb2cuc3RyZWFtcy5mdWxsJ10sIFsnZ29vZy5zdHJlYW1zLmRlZmluZXMnLCAnZ29vZy5zdHJlYW1zLmZ1bGxJbXBsJywgJ2dvb2cuc3RyZWFtcy5mdWxsTmF0aXZlSW1wbCcsICdnb29nLnN0cmVhbXMuZnVsbFR5cGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9mdWxsX2ltcGwuanMnLCBbJ2dvb2cuc3RyZWFtcy5mdWxsSW1wbCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLnByb21pc2UuTmF0aXZlUmVzb2x2ZXInLCAnZ29vZy5zdHJlYW1zLmZ1bGxUeXBlcycsICdnb29nLnN0cmVhbXMubGl0ZUltcGwnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJlYW1zL2Z1bGxfaW1wbF90ZXN0LmpzJywgWydnb29nLnN0cmVhbXMuZnVsbEltcGxUZXN0J10sIFsnZ29vZy5zdHJlYW1zLmZ1bGxJbXBsJywgJ2dvb2cuc3RyZWFtcy5mdWxsVGVzdENhc2VzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJlYW1zL2Z1bGxfbmF0aXZlX2ltcGwuanMnLCBbJ2dvb2cuc3RyZWFtcy5mdWxsTmF0aXZlSW1wbCddLCBbJ2dvb2cuc3RyZWFtcy5mdWxsVHlwZXMnLCAnZ29vZy5zdHJlYW1zLmxpdGVOYXRpdmVJbXBsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9mdWxsX25hdGl2ZV9pbXBsX3Rlc3QuanMnLCBbJ2dvb2cuc3RyZWFtcy5mdWxsTmF0aXZlSW1wbFRlc3QnXSwgWydnb29nLnN0cmVhbXMuZnVsbE5hdGl2ZUltcGwnLCAnZ29vZy5zdHJlYW1zLmZ1bGxUZXN0Q2FzZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmVhbXMvZnVsbF90ZXN0X2Nhc2VzLmpzJywgWydnb29nLnN0cmVhbXMuZnVsbFRlc3RDYXNlcyddLCBbJ2dvb2cuc3RyZWFtcy5mdWxsVHlwZXMnLCAnZ29vZy5zdHJlYW1zLmxpdGVUZXN0Q2FzZXMnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJ10sIHsnbGFuZyc6ICdlczknLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9mdWxsX3R5cGVzLmpzJywgWydnb29nLnN0cmVhbXMuZnVsbFR5cGVzJ10sIFsnZ29vZy5zdHJlYW1zLmxpdGVUeXBlcyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmVhbXMvbGl0ZS5qcycsIFsnZ29vZy5zdHJlYW1zLmxpdGUnXSwgWydnb29nLnN0cmVhbXMuZGVmaW5lcycsICdnb29nLnN0cmVhbXMubGl0ZUltcGwnLCAnZ29vZy5zdHJlYW1zLmxpdGVOYXRpdmVJbXBsJywgJ2dvb2cuc3RyZWFtcy5saXRlVHlwZXMnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJlYW1zL2xpdGVfaW1wbC5qcycsIFsnZ29vZy5zdHJlYW1zLmxpdGVJbXBsJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cucHJvbWlzZS5OYXRpdmVSZXNvbHZlcicsICdnb29nLnN0cmVhbXMubGl0ZVR5cGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9saXRlX2ltcGxfdGVzdC5qcycsIFsnZ29vZy5zdHJlYW1zLmxpdGVJbXBsVGVzdCddLCBbJ2dvb2cuc3RyZWFtcy5saXRlSW1wbCcsICdnb29nLnN0cmVhbXMubGl0ZVRlc3RDYXNlcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9saXRlX25hdGl2ZV9pbXBsLmpzJywgWydnb29nLnN0cmVhbXMubGl0ZU5hdGl2ZUltcGwnXSwgWydnb29nLnN0cmVhbXMubGl0ZVR5cGVzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyZWFtcy9saXRlX25hdGl2ZV9pbXBsX3Rlc3QuanMnLCBbJ2dvb2cuc3RyZWFtcy5saXRlTmF0aXZlSW1wbFRlc3QnXSwgWydnb29nLnN0cmVhbXMubGl0ZU5hdGl2ZUltcGwnLCAnZ29vZy5zdHJlYW1zLmxpdGVUZXN0Q2FzZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmVhbXMvbGl0ZV90ZXN0X2Nhc2VzLmpzJywgWydnb29nLnN0cmVhbXMubGl0ZVRlc3RDYXNlcyddLCBbJ2dvb2cuc3RyZWFtcy5saXRlVHlwZXMnLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCB7J2xhbmcnOiAnZXM4JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmVhbXMvbGl0ZV90eXBlcy5qcycsIFsnZ29vZy5zdHJlYW1zLmxpdGVUeXBlcyddLCBbXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvY29uc3QuanMnLCBbJ2dvb2cuc3RyaW5nLkNvbnN0J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuc3RyaW5nLlR5cGVkU3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvY29uc3RfdGVzdC5qcycsIFsnZ29vZy5zdHJpbmcuY29uc3RUZXN0J10sIFsnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmluZy9pbnRlcm5hbC5qcycsIFsnZ29vZy5zdHJpbmcuaW50ZXJuYWwnXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL2xpbmtpZnkuanMnLCBbJ2dvb2cuc3RyaW5nLmxpbmtpZnknXSwgWydnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5zdHJpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmluZy9saW5raWZ5X3Rlc3QuanMnLCBbJ2dvb2cuc3RyaW5nLmxpbmtpZnlUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cmluZy5saW5raWZ5JywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmluZy9uZXdsaW5lcy5qcycsIFsnZ29vZy5zdHJpbmcubmV3bGluZXMnLCAnZ29vZy5zdHJpbmcubmV3bGluZXMuTGluZSddLCBbJ2dvb2cuYXJyYXknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmluZy9uZXdsaW5lc190ZXN0LmpzJywgWydnb29nLnN0cmluZy5uZXdsaW5lc1Rlc3QnXSwgWydnb29nLnN0cmluZy5uZXdsaW5lcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3BhcnNlci5qcycsIFsnZ29vZy5zdHJpbmcuUGFyc2VyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3BhdGguanMnLCBbJ2dvb2cuc3RyaW5nLnBhdGgnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvcGF0aF90ZXN0LmpzJywgWydnb29nLnN0cmluZy5wYXRoVGVzdCddLCBbJ2dvb2cuc3RyaW5nLnBhdGgnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cmluZy9zdHJpbmcuanMnLCBbJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnXSwgWydnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnN0cmluZy5pbnRlcm5hbCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3N0cmluZ190ZXN0LmpzJywgWydnb29nLnN0cmluZ1Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLlVuaWNvZGUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvc3RyaW5nYnVmZmVyLmpzJywgWydnb29nLnN0cmluZy5TdHJpbmdCdWZmZXInXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3N0cmluZ2J1ZmZlcl90ZXN0LmpzJywgWydnb29nLnN0cmluZy5TdHJpbmdCdWZmZXJUZXN0J10sIFsnZ29vZy5zdHJpbmcuU3RyaW5nQnVmZmVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvc3RyaW5nZm9ybWF0LmpzJywgWydnb29nLnN0cmluZy5mb3JtYXQnXSwgWydnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3N0cmluZ2Zvcm1hdF90ZXN0LmpzJywgWydnb29nLnN0cmluZy5mb3JtYXRUZXN0J10sIFsnZ29vZy5zdHJpbmcuZm9ybWF0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJpbmcvc3RyaW5naWZpZXIuanMnLCBbJ2dvb2cuc3RyaW5nLlN0cmluZ2lmaWVyJ10sIFtdLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RyaW5nL3R5cGVkc3RyaW5nLmpzJywgWydnb29nLnN0cmluZy5UeXBlZFN0cmluZyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvYXZsdHJlZS5qcycsIFsnZ29vZy5zdHJ1Y3RzLkF2bFRyZWUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5zdHJ1Y3RzLkNvbGxlY3Rpb24nXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL2F2bHRyZWVfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLkF2bFRyZWVUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLnN0cnVjdHMuQXZsVHJlZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9jaXJjdWxhcmJ1ZmZlci5qcycsIFsnZ29vZy5zdHJ1Y3RzLkNpcmN1bGFyQnVmZmVyJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvY2lyY3VsYXJidWZmZXJfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLkNpcmN1bGFyQnVmZmVyVGVzdCddLCBbJ2dvb2cuc3RydWN0cy5DaXJjdWxhckJ1ZmZlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9jb2xsZWN0aW9uLmpzJywgWydnb29nLnN0cnVjdHMuQ29sbGVjdGlvbiddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvY29sbGVjdGlvbl90ZXN0LmpzJywgWydnb29nLnN0cnVjdHMuQ29sbGVjdGlvblRlc3QnXSwgWydnb29nLnN0cnVjdHMuQXZsVHJlZScsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL2hlYXAuanMnLCBbJ2dvb2cuc3RydWN0cy5IZWFwJ10sIFsnZ29vZy5hcnJheScsICdnb29nLm9iamVjdCcsICdnb29nLnN0cnVjdHMuTm9kZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9oZWFwX3Rlc3QuanMnLCBbJ2dvb2cuc3RydWN0cy5IZWFwVGVzdCddLCBbJ2dvb2cuc3RydWN0cycsICdnb29nLnN0cnVjdHMuSGVhcCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9pbnZlcnNpb25tYXAuanMnLCBbJ2dvb2cuc3RydWN0cy5JbnZlcnNpb25NYXAnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9pbnZlcnNpb25tYXBfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLkludmVyc2lvbk1hcFRlc3QnXSwgWydnb29nLnN0cnVjdHMuSW52ZXJzaW9uTWFwJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL2xpbmtlZG1hcC5qcycsIFsnZ29vZy5zdHJ1Y3RzLkxpbmtlZE1hcCddLCBbJ2dvb2cuc3RydWN0cy5NYXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvbGlua2VkbWFwX3Rlc3QuanMnLCBbJ2dvb2cuc3RydWN0cy5MaW5rZWRNYXBUZXN0J10sIFsnZ29vZy5zdHJ1Y3RzLkxpbmtlZE1hcCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvbWFwLmpzJywgWydnb29nLnN0cnVjdHMuTWFwJ10sIFsnZ29vZy5pdGVyLkl0ZXJhdG9yJywgJ2dvb2cuaXRlci5TdG9wSXRlcmF0aW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL21hcF90ZXN0LmpzJywgWydnb29nLnN0cnVjdHMuTWFwVGVzdCddLCBbJ2dvb2cuaXRlcicsICdnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9ub2RlLmpzJywgWydnb29nLnN0cnVjdHMuTm9kZSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvcG9vbC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlBvb2wnXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5zdHJ1Y3RzLlF1ZXVlJywgJ2dvb2cuc3RydWN0cy5TZXQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvcG9vbF90ZXN0LmpzJywgWydnb29nLnN0cnVjdHMuUG9vbFRlc3QnXSwgWydnb29nLnN0cnVjdHMuUG9vbCcsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3ByaW9yaXR5cG9vbC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlByaW9yaXR5UG9vbCddLCBbJ2dvb2cuc3RydWN0cy5Qb29sJywgJ2dvb2cuc3RydWN0cy5Qcmlvcml0eVF1ZXVlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3ByaW9yaXR5cG9vbF90ZXN0LmpzJywgWydnb29nLnN0cnVjdHMuUHJpb3JpdHlQb29sVGVzdCddLCBbJ2dvb2cuc3RydWN0cy5Qcmlvcml0eVBvb2wnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9wcmlvcml0eXF1ZXVlLmpzJywgWydnb29nLnN0cnVjdHMuUHJpb3JpdHlRdWV1ZSddLCBbJ2dvb2cuc3RydWN0cy5IZWFwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3ByaW9yaXR5cXVldWVfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlByaW9yaXR5UXVldWVUZXN0J10sIFsnZ29vZy5zdHJ1Y3RzJywgJ2dvb2cuc3RydWN0cy5Qcmlvcml0eVF1ZXVlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3F1YWR0cmVlLmpzJywgWydnb29nLnN0cnVjdHMuUXVhZFRyZWUnLCAnZ29vZy5zdHJ1Y3RzLlF1YWRUcmVlLk5vZGUnLCAnZ29vZy5zdHJ1Y3RzLlF1YWRUcmVlLlBvaW50J10sIFsnZ29vZy5tYXRoLkNvb3JkaW5hdGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvcXVhZHRyZWVfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlF1YWRUcmVlVGVzdCddLCBbJ2dvb2cuc3RydWN0cycsICdnb29nLnN0cnVjdHMuUXVhZFRyZWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvcXVldWUuanMnLCBbJ2dvb2cuc3RydWN0cy5RdWV1ZSddLCBbJ2dvb2cuYXJyYXknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvcXVldWVfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlF1ZXVlVGVzdCddLCBbJ2dvb2cuc3RydWN0cy5RdWV1ZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9zZXQuanMnLCBbJ2dvb2cuc3RydWN0cy5TZXQnXSwgWydnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLkNvbGxlY3Rpb24nLCAnZ29vZy5zdHJ1Y3RzLk1hcCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9zZXRfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlNldFRlc3QnXSwgWydnb29nLml0ZXInLCAnZ29vZy5zdHJ1Y3RzJywgJ2dvb2cuc3RydWN0cy5TZXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvc2ltcGxlcG9vbC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlNpbXBsZVBvb2wnXSwgWydnb29nLkRpc3Bvc2FibGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvc3RyaW5nc2V0LmpzJywgWydnb29nLnN0cnVjdHMuU3RyaW5nU2V0J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuaXRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3RydWN0cy9zdHJpbmdzZXRfdGVzdC5qcycsIFsnZ29vZy5zdHJ1Y3RzLlN0cmluZ1NldFRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuaXRlcicsICdnb29nLnN0cnVjdHMuU3RyaW5nU2V0JywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3N0cnVjdHMuanMnLCBbJ2dvb2cuc3RydWN0cyddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvc3RydWN0c190ZXN0LmpzJywgWydnb29nLnN0cnVjdHNUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3RydWN0cycsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cuc3RydWN0cy5TZXQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvdHJlZW5vZGUuanMnLCBbJ2dvb2cuc3RydWN0cy5UcmVlTm9kZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuc3RydWN0cy5Ob2RlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHJ1Y3RzL3RyZWVub2RlX3Rlc3QuanMnLCBbJ2dvb2cuc3RydWN0cy5UcmVlTm9kZVRlc3QnXSwgWydnb29nLnN0cnVjdHMuVHJlZU5vZGUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvdHJpZS5qcycsIFsnZ29vZy5zdHJ1Y3RzLlRyaWUnXSwgWydnb29nLm9iamVjdCcsICdnb29nLnN0cnVjdHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0cnVjdHMvdHJpZV90ZXN0LmpzJywgWydnb29nLnN0cnVjdHMuVHJpZVRlc3QnXSwgWydnb29nLm9iamVjdCcsICdnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLlRyaWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0eWxlL2JpZGkuanMnLCBbJ2dvb2cuc3R5bGUuYmlkaSddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucGxhdGZvcm0nLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3R5bGUvYmlkaV90ZXN0LmpzJywgWydnb29nLnN0eWxlLmJpZGlUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLmJpZGknLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0eWxlL2N1cnNvci5qcycsIFsnZ29vZy5zdHlsZS5jdXJzb3InXSwgWydnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3R5bGUvY3Vyc29yX3Rlc3QuanMnLCBbJ2dvb2cuc3R5bGUuY3Vyc29yVGVzdCddLCBbJ2dvb2cuc3R5bGUuY3Vyc29yJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHlsZS9zdHlsZS5qcycsIFsnZ29vZy5zdHlsZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20udmVuZG9yJywgJ2dvb2cuaHRtbC5TYWZlU3R5bGVTaGVldCcsICdnb29nLm1hdGguQm94JywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cubWF0aC5SZWN0JywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cucmVmbGVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3R5bGUvc3R5bGVfZG9jdW1lbnRfc2Nyb2xsX3Rlc3QuanMnLCBbJ2dvb2cuc3R5bGUuc3R5bGVfZG9jdW1lbnRfc2Nyb2xsX3Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHlsZS9zdHlsZV90ZXN0LmpzJywgWydnb29nLnN0eWxlX3Rlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuY29sb3InLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC51dGlsJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlJlY3QnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudCcsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50VGVzdFV0aWwnLCAnZ29vZy51c2VyQWdlbnRUZXN0VXRpbC5Vc2VyQWdlbnRzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3R5bGUvc3R5bGVfd2Via2l0X3Njcm9sbGJhcnNfdGVzdC5qcycsIFsnZ29vZy5zdHlsZS53ZWJraXRTY3JvbGxiYXJzVGVzdCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLnN0eWxlJywgJ2dvb2cuc3R5bGVTY3JvbGxiYXJUZXN0ZXInLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0eWxlL3N0eWxlc2Nyb2xsYmFydGVzdGVyLmpzJywgWydnb29nLnN0eWxlU2Nyb2xsYmFyVGVzdGVyJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCdzdHlsZS90cmFuc2Zvcm0uanMnLCBbJ2dvb2cuc3R5bGUudHJhbnNmb3JtJ10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUzJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0eWxlL3RyYW5zZm9ybV90ZXN0LmpzJywgWydnb29nLnN0eWxlLnRyYW5zZm9ybVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy5zdHlsZS50cmFuc2Zvcm0nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3N0eWxlL3RyYW5zaXRpb24uanMnLCBbJ2dvb2cuc3R5bGUudHJhbnNpdGlvbicsICdnb29nLnN0eWxlLnRyYW5zaXRpb24uQ3NzM1Byb3BlcnR5J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuZG9tLnZlbmRvcicsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgnc3R5bGUvdHJhbnNpdGlvbl90ZXN0LmpzJywgWydnb29nLnN0eWxlLnRyYW5zaXRpb25UZXN0J10sIFsnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLnRyYW5zaXRpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RfbW9kdWxlLmpzJywgWydnb29nLnRlc3RfbW9kdWxlJ10sIFsnZ29vZy50ZXN0X21vZHVsZV9kZXAnXSwgeydtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0X21vZHVsZV9kZXAuanMnLCBbJ2dvb2cudGVzdF9tb2R1bGVfZGVwJ10sIFtdLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvYXNzZXJ0aW9uZmFpbHVyZS5qcycsIFsnZ29vZy50ZXN0aW5nLnNhZmUuYXNzZXJ0aW9uRmFpbHVyZSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvYXNzZXJ0cy5qcycsIFsnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwgWydnb29nLnRlc3RpbmcuSnNVbml0RXhjZXB0aW9uJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2Fzc2VydHNfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmFzc2VydHNUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmRvbScsICdnb29nLml0ZXIuSXRlcmF0b3InLCAnZ29vZy5pdGVyLlN0b3BJdGVyYXRpb24nLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzOCcsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2FzeW5jL21vY2tjb250cm9sLmpzJywgWydnb29nLnRlc3RpbmcuYXN5bmMuTW9ja0NvbnRyb2wnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLmRlYnVnJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLklnbm9yZUFyZ3VtZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2FzeW5jL21vY2tjb250cm9sX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5hc3luYy5Nb2NrQ29udHJvbFRlc3QnXSwgWydnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcuYXN5bmMuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvYXN5bmN0ZXN0Y2FzZS5qcycsIFsnZ29vZy50ZXN0aW5nLkFzeW5jVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLkFzeW5jVGVzdENhc2UuQ29udHJvbEJyZWFraW5nRXhjZXB0aW9uJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9hc3luY3Rlc3RjYXNlX2FzeW5jX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5Bc3luY1Rlc3RDYXNlQXN5bmNUZXN0J10sIFsnZ29vZy50ZXN0aW5nLkFzeW5jVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5qc3VuaXQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2FzeW5jdGVzdGNhc2Vfbm9hc3luY190ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuQXN5bmNUZXN0Q2FzZVN5bmNUZXN0J10sIFsnZ29vZy50ZXN0aW5nLkFzeW5jVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvYXN5bmN0ZXN0Y2FzZV90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuQXN5bmNUZXN0Q2FzZVRlc3QnXSwgWydnb29nLmRlYnVnLkVycm9yJywgJ2dvb2cudGVzdGluZy5Bc3luY1Rlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2JlbmNobWFyay5qcycsIFsnZ29vZy50ZXN0aW5nLmJlbmNobWFyayddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLlBlcmZvcm1hbmNlVGFibGUnLCAnZ29vZy50ZXN0aW5nLlBlcmZvcm1hbmNlVGltZXInLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2NvbnRpbnVhdGlvbnRlc3RjYXNlLmpzJywgWydnb29nLnRlc3RpbmcuQ29udGludWF0aW9uVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLkNvbnRpbnVhdGlvblRlc3RDYXNlLkNvbnRpbnVhdGlvblRlc3QnLCAnZ29vZy50ZXN0aW5nLkNvbnRpbnVhdGlvblRlc3RDYXNlLlN0ZXAnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvY29udGludWF0aW9udGVzdGNhc2VfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLkNvbnRpbnVhdGlvblRlc3RDYXNlVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cudGVzdGluZy5Db250aW51YXRpb25UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuanN1bml0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9kZWZlcnJlZHRlc3RjYXNlLmpzJywgWydnb29nLnRlc3RpbmcuRGVmZXJyZWRUZXN0Q2FzZSddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy50ZXN0aW5nLkFzeW5jVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2RlZmVycmVkdGVzdGNhc2VfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLkRlZmVycmVkVGVzdENhc2VUZXN0J10sIFsnZ29vZy5hc3luYy5EZWZlcnJlZCcsICdnb29nLnRlc3RpbmcuRGVmZXJyZWRUZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLlRlc3RSdW5uZXInLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2RvbS5qcycsIFsnZ29vZy50ZXN0aW5nLmRvbSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkFic3RyYWN0UmFuZ2UnLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLk5vZGVJdGVyYXRvcicsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdJdGVyYXRvcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLml0ZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9kb21fdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmRvbVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZWRpdG9yL2RvbS5qcycsIFsnZ29vZy50ZXN0aW5nLmVkaXRvci5kb20nXSwgWydnb29nLmRvbS5BYnN0cmFjdFJhbmdlJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ0l0ZXJhdG9yJywgJ2dvb2cuZG9tLlRhZ1dhbGtUeXBlJywgJ2dvb2cuaXRlcicsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9lZGl0b3IvZG9tX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5lZGl0b3IuZG9tVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZWRpdG9yL2ZpZWxkbW9jay5qcycsIFsnZ29vZy50ZXN0aW5nLmVkaXRvci5GaWVsZE1vY2snXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLnRlc3RpbmcuTG9vc2VNb2NrJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZWRpdG9yL3Rlc3RoZWxwZXIuanMnLCBbJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmRvbScsICdnb29nLmRvbS5SYW5nZScsICdnb29nLmVkaXRvci5Ccm93c2VyRmVhdHVyZScsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cuZWRpdG9yLnBsdWdpbnMuQWJzdHJhY3RCdWJibGVQbHVnaW4nLCAnZ29vZy50ZXN0aW5nLmRvbSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9lZGl0b3IvdGVzdGhlbHBlcl90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuZWRpdG9yLlRlc3RIZWxwZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmVkaXRvci5ub2RlJywgJ2dvb2cudGVzdGluZy5lZGl0b3IuVGVzdEhlbHBlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9ldmVudHMvZXZlbnRvYnNlcnZlci5qcycsIFsnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudE9ic2VydmVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmV2ZW50cy5FdmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9ldmVudHMvZXZlbnRvYnNlcnZlcl90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50T2JzZXJ2ZXJUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50T2JzZXJ2ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXZlbnRzL2V2ZW50cy5qcycsIFsnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50J10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXZlbnRzL2V2ZW50c190ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuZXZlbnRzVGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXZlbnRzL21hdGNoZXJzLmpzJywgWydnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50TWF0Y2hlciddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMuQXJndW1lbnRNYXRjaGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2V2ZW50cy9tYXRjaGVyc190ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50TWF0Y2hlclRlc3QnXSwgWydnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50TWF0Y2hlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9ldmVudHMvb25saW5laGFuZGxlci5qcycsIFsnZ29vZy50ZXN0aW5nLmV2ZW50cy5PbmxpbmVIYW5kbGVyJ10sIFsnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5uZXQuTmV0d29ya1N0YXR1c01vbml0b3InXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXZlbnRzL29ubGluZWhhbmRsZXJfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmV2ZW50cy5PbmxpbmVIYW5kbGVyVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cubmV0Lk5ldHdvcmtTdGF0dXNNb25pdG9yJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnRPYnNlcnZlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzLk9ubGluZUhhbmRsZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXhwZWN0ZWRmYWlsdXJlcy5qcycsIFsnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kZWJ1Zy5EaXZDb25zb2xlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubG9nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkpzVW5pdEV4Y2VwdGlvbicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZXhwZWN0ZWRmYWlsdXJlc190ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlc1Rlc3QnXSwgWydnb29nLmRlYnVnLkxvZ2dlcicsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuSnNVbml0RXhjZXB0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2ZzL2Jsb2IuanMnLCBbJ2dvb2cudGVzdGluZy5mcy5CbG9iJ10sIFsnZ29vZy5jcnlwdCcsICdnb29nLmNyeXB0LmJhc2U2NCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9ibG9iX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5mcy5CbG9iVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy5mcy5CbG9iJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2ZzL2RpcmVjdG9yeWVudHJ5X3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5mcy5EaXJlY3RvcnlFbnRyeVRlc3QnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZnMuRGlyZWN0b3J5RW50cnknLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuZnMuRmlsZVN5c3RlbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9lbnRyeS5qcycsIFsnZ29vZy50ZXN0aW5nLmZzLkRpcmVjdG9yeUVudHJ5JywgJ2dvb2cudGVzdGluZy5mcy5FbnRyeScsICdnb29nLnRlc3RpbmcuZnMuRmlsZUVudHJ5J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZnMuRGlyZWN0b3J5RW50cnknLCAnZ29vZy5mcy5EaXJlY3RvcnlFbnRyeUltcGwnLCAnZ29vZy5mcy5FbnRyeScsICdnb29nLmZzLkVycm9yJywgJ2dvb2cuZnMuRmlsZUVudHJ5JywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5mcy5GaWxlJywgJ2dvb2cudGVzdGluZy5mcy5GaWxlV3JpdGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2ZzL2VudHJ5X3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5mcy5FbnRyeVRlc3QnXSwgWydnb29nLmZzLkRpcmVjdG9yeUVudHJ5JywgJ2dvb2cuZnMuRXJyb3InLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmZzLkZpbGVTeXN0ZW0nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZnMvZmlsZS5qcycsIFsnZ29vZy50ZXN0aW5nLmZzLkZpbGUnXSwgWydnb29nLnRlc3RpbmcuZnMuQmxvYiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9maWxlZW50cnlfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmZzLkZpbGVFbnRyeVRlc3QnXSwgWydnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5mcy5GaWxlRW50cnknLCAnZ29vZy50ZXN0aW5nLmZzLkZpbGVTeXN0ZW0nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZnMvZmlsZXJlYWRlci5qcycsIFsnZ29vZy50ZXN0aW5nLmZzLkZpbGVSZWFkZXInXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZnMuRXJyb3InLCAnZ29vZy5mcy5GaWxlUmVhZGVyJywgJ2dvb2cudGVzdGluZy5mcy5CbG9iJywgJ2dvb2cudGVzdGluZy5mcy5Qcm9ncmVzc0V2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2ZzL2ZpbGVyZWFkZXJfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmZzLkZpbGVSZWFkZXJUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVSZWFkZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudE9ic2VydmVyJywgJ2dvb2cudGVzdGluZy5mcy5GaWxlUmVhZGVyJywgJ2dvb2cudGVzdGluZy5mcy5GaWxlU3lzdGVtJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2ZzL2ZpbGVzeXN0ZW0uanMnLCBbJ2dvb2cudGVzdGluZy5mcy5GaWxlU3lzdGVtJ10sIFsnZ29vZy5mcy5GaWxlU3lzdGVtJywgJ2dvb2cudGVzdGluZy5mcy5EaXJlY3RvcnlFbnRyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9maWxld3JpdGVyLmpzJywgWydnb29nLnRlc3RpbmcuZnMuRmlsZVdyaXRlciddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5mcy5FcnJvcicsICdnb29nLmZzLkZpbGVTYXZlcicsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuZnMuQmxvYicsICdnb29nLnRlc3RpbmcuZnMuRmlsZScsICdnb29nLnRlc3RpbmcuZnMuUHJvZ3Jlc3NFdmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9maWxld3JpdGVyX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5mcy5GaWxlV3JpdGVyVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmFycmF5JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnMuRXJyb3InLCAnZ29vZy5mcy5GaWxlU2F2ZXInLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50T2JzZXJ2ZXInLCAnZ29vZy50ZXN0aW5nLmZzLkJsb2InLCAnZ29vZy50ZXN0aW5nLmZzLkZpbGVTeXN0ZW0nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZnMvZnMuanMnLCBbJ2dvb2cudGVzdGluZy5mcyddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLkRlZmVycmVkJywgJ2dvb2cuZnMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmZzLkJsb2InLCAnZ29vZy50ZXN0aW5nLmZzLkZpbGVTeXN0ZW0nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZnMvZnNfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLmZzVGVzdCddLCBbJ2dvb2cudGVzdGluZy5mcycsICdnb29nLnRlc3RpbmcuZnMuQmxvYicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9pbnRlZ3JhdGlvbl90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuZnMuaW50ZWdyYXRpb25UZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnMnLCAnZ29vZy5mcy5EaXJlY3RvcnlFbnRyeScsICdnb29nLmZzLkVycm9yJywgJ2dvb2cuZnMuRmlsZVNhdmVyJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5mcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9mcy9wcm9ncmVzc2V2ZW50LmpzJywgWydnb29nLnRlc3RpbmcuZnMuUHJvZ3Jlc3NFdmVudCddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2Z1bmN0aW9ubW9jay5qcycsIFsnZ29vZy50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy5GdW5jdGlvbk1vY2snLCAnZ29vZy50ZXN0aW5nLkdsb2JhbEZ1bmN0aW9uTW9jaycsICdnb29nLnRlc3RpbmcuTWV0aG9kTW9jayddLCBbJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5Mb29zZU1vY2snLCAnZ29vZy50ZXN0aW5nLk1vY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvZnVuY3Rpb25tb2NrX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5GdW5jdGlvbk1vY2tUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLkZ1bmN0aW9uTW9jaycsICdnb29nLnRlc3RpbmcuTW9jaycsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2dyYXBoaWNzLmpzJywgWydnb29nLnRlc3RpbmcuZ3JhcGhpY3MnXSwgWydnb29nLmdyYXBoaWNzLlBhdGgnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvaTE4bi9hc3NlcnRzLmpzJywgWydnb29nLnRlc3RpbmcuaTE4bi5hc3NlcnRzJ10sIFsnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvaTE4bi9hc3NlcnRzX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5pMThuLmFzc2VydHNUZXN0J10sIFsnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLmkxOG4uYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9qc3RkYXN5bmN3cmFwcGVyLmpzJywgWydnb29nLnRlc3RpbmcuSnNUZEFzeW5jV3JhcHBlciddLCBbJ2dvb2cuUHJvbWlzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9qc3RkdGVzdGNhc2VhZGFwdGVyLmpzJywgWydnb29nLnRlc3RpbmcuSnNUZFRlc3RDYXNlQWRhcHRlciddLCBbJ2dvb2cuYXN5bmMucnVuJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cudGVzdGluZy5Kc1RkQXN5bmNXcmFwcGVyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuanN1bml0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2pzdW5pdC5qcycsIFsnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5UZXN0UnVubmVyJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2pzdW5pdGV4Y2VwdGlvbi5qcycsIFsnZ29vZy50ZXN0aW5nLkpzVW5pdEV4Y2VwdGlvbiddLCBbJ2dvb2cudGVzdGluZy5zdGFja3RyYWNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL2xvb3NlbW9jay5qcycsIFsnZ29vZy50ZXN0aW5nLkxvb3NlRXhwZWN0YXRpb25Db2xsZWN0aW9uJywgJ2dvb2cudGVzdGluZy5Mb29zZU1vY2snXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cuc3RydWN0cy5TZXQnLCAnZ29vZy50ZXN0aW5nLk1vY2snXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbG9vc2Vtb2NrX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5Mb29zZU1vY2tUZXN0J10sIFsnZ29vZy50ZXN0aW5nLkxvb3NlTW9jaycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzOCcsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21lc3NhZ2luZy9tb2NrbWVzc2FnZWNoYW5uZWwuanMnLCBbJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VDaGFubmVsJ10sIFsnZ29vZy5tZXNzYWdpbmcuQWJzdHJhY3RDaGFubmVsJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tZXNzYWdpbmcvbW9ja21lc3NhZ2VldmVudC5qcycsIFsnZ29vZy50ZXN0aW5nLm1lc3NhZ2luZy5Nb2NrTWVzc2FnZUV2ZW50J10sIFsnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21lc3NhZ2luZy9tb2NrbWVzc2FnZXBvcnQuanMnLCBbJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja01lc3NhZ2VQb3J0J10sIFsnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21lc3NhZ2luZy9tb2NrcG9ydG5ldHdvcmsuanMnLCBbJ2dvb2cudGVzdGluZy5tZXNzYWdpbmcuTW9ja1BvcnROZXR3b3JrJ10sIFsnZ29vZy5tZXNzYWdpbmcuUG9ydE5ldHdvcmsnLCAnZ29vZy50ZXN0aW5nLm1lc3NhZ2luZy5Nb2NrTWVzc2FnZUNoYW5uZWwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9jay5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tFeHBlY3RhdGlvbiddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLm9iamVjdCcsICdnb29nLnByb21pc2UuUmVzb2x2ZXInLCAnZ29vZy50ZXN0aW5nLkpzVW5pdEV4Y2VwdGlvbicsICdnb29nLnRlc3RpbmcuTW9ja0ludGVyZmFjZScsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21vY2tfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLk1vY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Nb2NrRXhwZWN0YXRpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM4JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja2NsYXNzZmFjdG9yeS5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tDbGFzc0ZhY3RvcnknLCAnZ29vZy50ZXN0aW5nLk1vY2tDbGFzc1JlY29yZCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLkxvb3NlTW9jaycsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NrY2xhc3NmYWN0b3J5X3Rlc3QuanMnLCBbJ2Zha2UuQmFzZUNsYXNzJywgJ2Zha2UuQ2hpbGRDbGFzcycsICdnb29nLnRlc3RpbmcuTW9ja0NsYXNzRmFjdG9yeVRlc3QnXSwgWydnb29nLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbGFzc0ZhY3RvcnknLCAnZ29vZy50ZXN0aW5nLmpzdW5pdCddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja2Nsb2NrLmpzJywgWydnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuUHJvbWlzZScsICdnb29nLlRoZW5hYmxlJywgJ2dvb2cuYXN5bmMucnVuJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NrY2xvY2tfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tDbG9ja1Rlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5UaW1lcicsICdnb29nLmV2ZW50cycsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NrY29udHJvbC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJ10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy5Mb29zZU1vY2snLCAnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja2NvbnRyb2xfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sVGVzdCddLCBbJ2dvb2cudGVzdGluZy5Nb2NrJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NraW50ZXJmYWNlLmpzJywgWydnb29nLnRlc3RpbmcuTW9ja0ludGVyZmFjZSddLCBbJ2dvb2cuUHJvbWlzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NrbWF0Y2hlcnMuanMnLCBbJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5JZ25vcmVBcmd1bWVudCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLkluc3RhbmNlT2YnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5PYmplY3RFcXVhbHMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5SZWdleHBNYXRjaCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLlNhdmVBcmd1bWVudCcsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzLlR5cGVPZiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja21hdGNoZXJzX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnNUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnRlc3RpbmcuanN1bml0JywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21vY2tyYW5kb20uanMnLCBbJ2dvb2cudGVzdGluZy5Nb2NrUmFuZG9tJ10sIFsnZ29vZy5EaXNwb3NhYmxlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21vY2tyYW5kb21fdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tSYW5kb21UZXN0J10sIFsnZ29vZy50ZXN0aW5nLk1vY2tSYW5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja3JhbmdlLmpzJywgWydnb29nLnRlc3RpbmcuTW9ja1JhbmdlJ10sIFsnZ29vZy5kb20uQWJzdHJhY3RSYW5nZScsICdnb29nLnRlc3RpbmcuTG9vc2VNb2NrJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL21vY2tyYW5nZV90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuTW9ja1JhbmdlVGVzdCddLCBbJ2dvb2cudGVzdGluZy5Nb2NrUmFuZ2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja3N0b3JhZ2UuanMnLCBbJ2dvb2cudGVzdGluZy5Nb2NrU3RvcmFnZSddLCBbJ2dvb2cuc3RydWN0cy5NYXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja3N0b3JhZ2VfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk1vY2tTdG9yYWdlVGVzdCddLCBbJ2dvb2cudGVzdGluZy5Nb2NrU3RvcmFnZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tb2NrdXNlcmFnZW50LmpzJywgWydnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudCddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbW9ja3VzZXJhZ2VudF90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudFRlc3QnXSwgWydnb29nLmRpc3Bvc2UnLCAnZ29vZy50ZXN0aW5nLk1vY2tVc2VyQWdlbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvbXVsdGl0ZXN0cnVubmVyLmpzJywgWydnb29nLnRlc3RpbmcuTXVsdGlUZXN0UnVubmVyJywgJ2dvb2cudGVzdGluZy5NdWx0aVRlc3RSdW5uZXIuVGVzdEZyYW1lJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuU2VydmVyQ2hhcnQnLCAnZ29vZy51aS5UYWJsZVNvcnRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9tdWx0aXRlc3RydW5uZXJfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLk11bHRpVGVzdFJ1bm5lclRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5hcnJheScsICdnb29nLmV2ZW50cycsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLk11bHRpVGVzdFJ1bm5lcicsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9uZXQvbW9ja2lmcmFtZWlvLmpzJywgWydnb29nLnRlc3RpbmcubmV0Lk1vY2tJRnJhbWVJbyddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cubmV0LkVycm9yQ29kZScsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5uZXQuSWZyYW1lSW8nLCAnZ29vZy50ZXN0aW5nLlRlc3RRdWV1ZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9uZXQveGhyaW8uanMnLCBbJ2dvb2cudGVzdGluZy5uZXQuWGhySW8nXSwgWydnb29nLlVyaScsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tLnhtbCcsICdnb29nLmV2ZW50cycsICdnb29nLm5ldC5FcnJvckNvZGUnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cubmV0Lkh0dHBTdGF0dXMnLCAnZ29vZy5uZXQuWGhySW8nLCAnZ29vZy5uZXQuWG1sSHR0cCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnRlc3RpbmcuVGVzdFF1ZXVlJywgJ2dvb2cudXJpLnV0aWxzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL25ldC94aHJpb190ZXN0LmpzJywgWydnb29nLnRlc3RpbmcubmV0LlhocklvVGVzdCddLCBbJ2dvb2cuZG9tLnhtbCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLm5ldC5FcnJvckNvZGUnLCAnZ29vZy5uZXQuRXZlbnRUeXBlJywgJ2dvb2cubmV0LlhtbEh0dHAnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMuSW5zdGFuY2VPZicsICdnb29nLnRlc3RpbmcubmV0LlhocklvJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL25ldC94aHJpb3Bvb2wuanMnLCBbJ2dvb2cudGVzdGluZy5uZXQuWGhySW9Qb29sJ10sIFsnZ29vZy5uZXQuWGhySW9Qb29sJywgJ2dvb2cudGVzdGluZy5uZXQuWGhySW8nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3Rpbmcvb2JqZWN0cHJvcGVydHlzdHJpbmcuanMnLCBbJ2dvb2cudGVzdGluZy5PYmplY3RQcm9wZXJ0eVN0cmluZyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvcGFyYWxsZWxfY2xvc3VyZV90ZXN0X3N1aXRlLmpzJywgWydnb29nLnRlc3RpbmcucGFyYWxsZWxDbG9zdXJlVGVzdFN1aXRlJ10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmV2ZW50cycsICdnb29nLmpzb24nLCAnZ29vZy50ZXN0aW5nLk11bHRpVGVzdFJ1bm5lcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvcGFyYWxsZWxfY2xvc3VyZV90ZXN0X3N1aXRlX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5wYXJhbGxlbENsb3N1cmVUZXN0U3VpdGVUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5NdWx0aVRlc3RSdW5uZXInLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInLCAnZ29vZy50ZXN0aW5nLnBhcmFsbGVsQ2xvc3VyZVRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9wZXJmb3JtYW5jZXRhYmxlLmpzJywgWydnb29nLnRlc3RpbmcuUGVyZm9ybWFuY2VUYWJsZSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy5QZXJmb3JtYW5jZVRpbWVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3BlcmZvcm1hbmNldGltZXIuanMnLCBbJ2dvb2cudGVzdGluZy5QZXJmb3JtYW5jZVRpbWVyJywgJ2dvb2cudGVzdGluZy5QZXJmb3JtYW5jZVRpbWVyLlRhc2snXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5tYXRoJ10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9wZXJmb3JtYW5jZXRpbWVyX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5QZXJmb3JtYW5jZVRpbWVyVGVzdCddLCBbJ2dvb2cuYXN5bmMuRGVmZXJyZWQnLCAnZ29vZy5kb20nLCAnZ29vZy5tYXRoJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlBlcmZvcm1hbmNlVGltZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvcHJvcGVydHlyZXBsYWNlci5qcycsIFsnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvcHJvcGVydHlyZXBsYWNlcl90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvcHJvdG8yL3Byb3RvMi5qcycsIFsnZ29vZy50ZXN0aW5nLnByb3RvMiddLCBbJ2dvb2cucHJvdG8yLk1lc3NhZ2UnLCAnZ29vZy5wcm90bzIuT2JqZWN0U2VyaWFsaXplcicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9wcm90bzIvcHJvdG8yX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5wcm90bzJUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnByb3RvMicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ3Byb3RvMi5UZXN0QWxsVHlwZXMnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3BzZXVkb3JhbmRvbS5qcycsIFsnZ29vZy50ZXN0aW5nLlBzZXVkb1JhbmRvbSddLCBbJ2dvb2cuRGlzcG9zYWJsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9wc2V1ZG9yYW5kb21fdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLlBzZXVkb1JhbmRvbVRlc3QnXSwgWydnb29nLnRlc3RpbmcuUHNldWRvUmFuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3JlY29yZGZ1bmN0aW9uLmpzJywgWydnb29nLnRlc3RpbmcuRnVuY3Rpb25DYWxsJywgJ2dvb2cudGVzdGluZy5yZWNvcmRDb25zdHJ1Y3RvcicsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5wcm9taXNlLlJlc29sdmVyJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3JlY29yZGZ1bmN0aW9uX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvblRlc3QnXSwgWydnb29nLmZ1bmN0aW9ucycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcucmVjb3JkQ29uc3RydWN0b3InLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzOCcsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3NoYXJkaW5ndGVzdGNhc2UuanMnLCBbJ2dvb2cudGVzdGluZy5TaGFyZGluZ1Rlc3RDYXNlJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zaGFyZGluZ3Rlc3RjYXNlX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5TaGFyZGluZ1Rlc3RDYXNlVGVzdCddLCBbJ2dvb2cudGVzdGluZy5TaGFyZGluZ1Rlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcuanN1bml0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zaW5nbGV0b24uanMnLCBbJ2dvb2cudGVzdGluZy5zaW5nbGV0b24nXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zaW5nbGV0b25fdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLnNpbmdsZXRvblRlc3QnXSwgWydnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3Rpbmcuc2luZ2xldG9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3N0YWNrdHJhY2UuanMnLCBbJ2dvb2cudGVzdGluZy5zdGFja3RyYWNlJywgJ2dvb2cudGVzdGluZy5zdGFja3RyYWNlLkZyYW1lJ10sIFtdLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3Rpbmcvc3RhY2t0cmFjZV90ZXN0LmpzJywgWydnb29nLnRlc3Rpbmcuc3RhY2t0cmFjZVRlc3QnXSwgWydnb29nLmZ1bmN0aW9ucycsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuU3RyaWN0TW9jaycsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3Rpbmcuc3RhY2t0cmFjZScsICdnb29nLnRlc3Rpbmcuc3RhY2t0cmFjZS5GcmFtZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zdG9yYWdlL2Zha2VtZWNoYW5pc20uanMnLCBbJ2dvb2cudGVzdGluZy5zdG9yYWdlLkZha2VNZWNoYW5pc20nXSwgWydnb29nLnN0b3JhZ2UubWVjaGFuaXNtLkl0ZXJhYmxlTWVjaGFuaXNtJywgJ2dvb2cuc3RydWN0cy5NYXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3Rpbmcvc3RyaWN0bW9jay5qcycsIFsnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cudGVzdGluZy5Nb2NrJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3N0cmljdG1vY2tfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2tUZXN0J10sIFsnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM4JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3Rpbmcvc3R5bGUvbGF5b3V0YXNzZXJ0cy5qcycsIFsnZ29vZy50ZXN0aW5nLnN0eWxlLmxheW91dGFzc2VydHMnXSwgWydnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJywgJ2dvb2cudGVzdGluZy5zdHlsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zdHlsZS9sYXlvdXRhc3NlcnRzX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy5zdHlsZS5sYXlvdXRhc3NlcnRzVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3Rpbmcuc3R5bGUubGF5b3V0YXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zdHlsZS9zdHlsZS5qcycsIFsnZ29vZy50ZXN0aW5nLnN0eWxlJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5tYXRoLlJlY3QnLCAnZ29vZy5zdHlsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy9zdHlsZS9zdHlsZV90ZXN0LmpzJywgWydnb29nLnRlc3Rpbmcuc3R5bGVUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5zdHlsZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy90ZXN0Y2FzZS5qcycsIFsnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZS5FcnJvcicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UuT3JkZXInLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlLlJlc3VsdCcsICdnb29nLnRlc3RpbmcuVGVzdENhc2UuVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLlRoZW5hYmxlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLkpzVW5pdEV4Y2VwdGlvbicsICdnb29nLnRlc3RpbmcuYXNzZXJ0cyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy90ZXN0Y2FzZV90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuVGVzdENhc2VUZXN0J10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLkZ1bmN0aW9uTW9jaycsICdnb29nLnRlc3RpbmcuSnNVbml0RXhjZXB0aW9uJywgJ2dvb2cudGVzdGluZy5NZXRob2RNb2NrJywgJ2dvb2cudGVzdGluZy5Nb2NrUmFuZG9tJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczgnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy90ZXN0cXVldWUuanMnLCBbJ2dvb2cudGVzdGluZy5UZXN0UXVldWUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3Rlc3RydW5uZXIuanMnLCBbJ2dvb2cudGVzdGluZy5UZXN0UnVubmVyJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuanNvbicsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvdGVzdHJ1bm5lcl90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcuVGVzdFJ1bm5lclRlc3QnXSwgWydnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLlRlc3RSdW5uZXInLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3Rlc3RpbmcvdGVzdHN1aXRlLmpzJywgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIFsnZ29vZy5sYWJzLnRlc3RpbmcuRW52aXJvbm1lbnQnLCAnZ29vZy50ZXN0aW5nLlRlc3RDYXNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3Rlc3RzdWl0ZV90ZXN0LmpzJywgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlVGVzdCddLCBbJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy91aS9yZW5kZXJlcmFzc2VydHMuanMnLCBbJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnXSwgWydnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy91aS9yZW5kZXJlcmFzc2VydHNfdGVzdC5qcycsIFsnZ29vZy50ZXN0aW5nLnVpLnJlbmRlcmVyYXNzZXJ0c1Rlc3QnXSwgWydnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnLCAnZ29vZy51aS5Db250cm9sUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3VpL3JlbmRlcmVyaGFybmVzcy5qcycsIFsnZ29vZy50ZXN0aW5nLnVpLlJlbmRlcmVySGFybmVzcyddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLnRlc3RpbmcuYXNzZXJ0cycsICdnb29nLnRlc3RpbmcuZG9tJywgJ2dvb2cudWkuQ29udHJvbCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndGVzdGluZy91aS9zdHlsZS5qcycsIFsnZ29vZy50ZXN0aW5nLnVpLnN0eWxlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudGVzdGluZy5hc3NlcnRzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0ZXN0aW5nL3VpL3N0eWxlX3Rlc3QuanMnLCBbJ2dvb2cudGVzdGluZy51aS5zdHlsZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5zdHlsZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3RpbWVyL3RpbWVyLmpzJywgWydnb29nLlRpbWVyJ10sIFsnZ29vZy5Qcm9taXNlJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd0aW1lci90aW1lcl90ZXN0LmpzJywgWydnb29nLlRpbWVyVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLlRpbWVyJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL2VudHJpZXMuanMnLCBbJ2dvb2cudHdlYWsuQmFzZUVudHJ5JywgJ2dvb2cudHdlYWsuQmFzZVByaW1pdGl2ZVNldHRpbmcnLCAnZ29vZy50d2Vhay5CYXNlU2V0dGluZycsICdnb29nLnR3ZWFrLkJvb2xlYW5Hcm91cCcsICdnb29nLnR3ZWFrLkJvb2xlYW5Jbkdyb3VwU2V0dGluZycsICdnb29nLnR3ZWFrLkJvb2xlYW5TZXR0aW5nJywgJ2dvb2cudHdlYWsuQnV0dG9uQWN0aW9uJywgJ2dvb2cudHdlYWsuTnVtZXJpY1NldHRpbmcnLCAnZ29vZy50d2Vhay5TdHJpbmdTZXR0aW5nJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5sb2cnLCAnZ29vZy5vYmplY3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL2VudHJpZXNfdGVzdC5qcycsIFsnZ29vZy50d2Vhay5CYXNlRW50cnlUZXN0J10sIFsnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy50d2Vhay50ZXN0aGVscGVycyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL3JlZ2lzdHJ5LmpzJywgWydnb29nLnR3ZWFrLlJlZ2lzdHJ5J10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5sb2cnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50d2Vhay5CYXNlUHJpbWl0aXZlU2V0dGluZycsICdnb29nLnR3ZWFrLkJhc2VTZXR0aW5nJywgJ2dvb2cudHdlYWsuQm9vbGVhblNldHRpbmcnLCAnZ29vZy50d2Vhay5OdW1lcmljU2V0dGluZycsICdnb29nLnR3ZWFrLlN0cmluZ1NldHRpbmcnLCAnZ29vZy51cmkudXRpbHMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL3JlZ2lzdHJ5X3Rlc3QuanMnLCBbJ2dvb2cudHdlYWsuUmVnaXN0cnlUZXN0J10sIFsnZ29vZy5hc3NlcnRzLkFzc2VydGlvbkVycm9yJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy50d2VhaycsICdnb29nLnR3ZWFrLnRlc3RoZWxwZXJzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndHdlYWsvdGVzdGhlbHBlcnMuanMnLCBbJ2dvb2cudHdlYWsudGVzdGhlbHBlcnMnXSwgWydnb29nLnR3ZWFrJywgJ2dvb2cudHdlYWsuQm9vbGVhbkdyb3VwJywgJ2dvb2cudHdlYWsuQm9vbGVhbkluR3JvdXBTZXR0aW5nJywgJ2dvb2cudHdlYWsuQm9vbGVhblNldHRpbmcnLCAnZ29vZy50d2Vhay5CdXR0b25BY3Rpb24nLCAnZ29vZy50d2Vhay5OdW1lcmljU2V0dGluZycsICdnb29nLnR3ZWFrLlJlZ2lzdHJ5JywgJ2dvb2cudHdlYWsuU3RyaW5nU2V0dGluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndHdlYWsvdHdlYWsuanMnLCBbJ2dvb2cudHdlYWsnLCAnZ29vZy50d2Vhay5Db25maWdQYXJhbXMnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy50d2Vhay5CYXNlU2V0dGluZycsICdnb29nLnR3ZWFrLkJvb2xlYW5Hcm91cCcsICdnb29nLnR3ZWFrLkJvb2xlYW5Jbkdyb3VwU2V0dGluZycsICdnb29nLnR3ZWFrLkJvb2xlYW5TZXR0aW5nJywgJ2dvb2cudHdlYWsuQnV0dG9uQWN0aW9uJywgJ2dvb2cudHdlYWsuTnVtZXJpY1NldHRpbmcnLCAnZ29vZy50d2Vhay5SZWdpc3RyeScsICdnb29nLnR3ZWFrLlN0cmluZ1NldHRpbmcnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL3R3ZWFrdWkuanMnLCBbJ2dvb2cudHdlYWsuRW50cmllc1BhbmVsJywgJ2dvb2cudHdlYWsuVHdlYWtVaSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50d2VhaycsICdnb29nLnR3ZWFrLkJhc2VFbnRyeScsICdnb29nLnR3ZWFrLkJvb2xlYW5Hcm91cCcsICdnb29nLnR3ZWFrLkJvb2xlYW5Jbkdyb3VwU2V0dGluZycsICdnb29nLnR3ZWFrLkJvb2xlYW5TZXR0aW5nJywgJ2dvb2cudHdlYWsuQnV0dG9uQWN0aW9uJywgJ2dvb2cudHdlYWsuTnVtZXJpY1NldHRpbmcnLCAnZ29vZy50d2Vhay5TdHJpbmdTZXR0aW5nJywgJ2dvb2cudWkuWmlwcHknLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3R3ZWFrL3R3ZWFrdWlfdGVzdC5qcycsIFsnZ29vZy50d2Vhay5Ud2Vha1VpVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnR3ZWFrJywgJ2dvb2cudHdlYWsuVHdlYWtVaScsICdnb29nLnR3ZWFrLnRlc3RoZWxwZXJzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWJzdHJhY3RzcGVsbGNoZWNrZXIuanMnLCBbJ2dvb2cudWkuQWJzdHJhY3RTcGVsbENoZWNrZXInLCAnZ29vZy51aS5BYnN0cmFjdFNwZWxsQ2hlY2tlci5Bc3luY1Jlc3VsdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLklucHV0VHlwZScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmRvbS5zZWxlY3Rpb24nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3BlbGwuU3BlbGxDaGVjaycsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLk1lbnVTZXBhcmF0b3InLCAnZ29vZy51aS5Qb3B1cE1lbnUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL2FjLmpzJywgWydnb29nLnVpLmFjJ10sIFsnZ29vZy51aS5hYy5BcnJheU1hdGNoZXInLCAnZ29vZy51aS5hYy5BdXRvQ29tcGxldGUnLCAnZ29vZy51aS5hYy5JbnB1dEhhbmRsZXInLCAnZ29vZy51aS5hYy5SZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWMvYWNfdGVzdC5qcycsIFsnZ29vZy51aS5hY1Rlc3QnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZG9tLnNlbGVjdGlvbicsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5hYycsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL2FycmF5bWF0Y2hlci5qcycsIFsnZ29vZy51aS5hYy5BcnJheU1hdGNoZXInXSwgWydnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWMvYXJyYXltYXRjaGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuYWMuQXJyYXlNYXRjaGVyVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5hYy5BcnJheU1hdGNoZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9hdXRvY29tcGxldGUuanMnLCBbJ2dvb2cudWkuYWMuQXV0b0NvbXBsZXRlJywgJ2dvb2cudWkuYWMuQXV0b0NvbXBsZXRlLkV2ZW50VHlwZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudWkuYWMuUmVuZGVyT3B0aW9ucyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWMvYXV0b2NvbXBsZXRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuYWMuQXV0b0NvbXBsZXRlVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmFjLkF1dG9Db21wbGV0ZScsICdnb29nLnVpLmFjLklucHV0SGFuZGxlcicsICdnb29nLnVpLmFjLlJlbmRlck9wdGlvbnMnLCAnZ29vZy51aS5hYy5SZW5kZXJlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL2NhY2hpbmdtYXRjaGVyLmpzJywgWydnb29nLnVpLmFjLkNhY2hpbmdNYXRjaGVyJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmFzeW5jLlRocm90dGxlJywgJ2dvb2cudWkuYWMuQXJyYXlNYXRjaGVyJywgJ2dvb2cudWkuYWMuUmVuZGVyT3B0aW9ucyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWMvY2FjaGluZ21hdGNoZXJfdGVzdC5qcycsIFsnZ29vZy51aS5hYy5DYWNoaW5nTWF0Y2hlclRlc3QnXSwgWydnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuYWMuQ2FjaGluZ01hdGNoZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9pbnB1dGhhbmRsZXIuanMnLCBbJ2dvb2cudWkuYWMuSW5wdXRIYW5kbGVyJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuVGltZXInLCAnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5zZWxlY3Rpb24nLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL2lucHV0aGFuZGxlcl90ZXN0LmpzJywgWydnb29nLnVpLmFjLklucHV0SGFuZGxlclRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2VsZWN0aW9uJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmFjLklucHV0SGFuZGxlcicsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL3JlbW90ZS5qcycsIFsnZ29vZy51aS5hYy5SZW1vdGUnXSwgWydnb29nLnVpLmFjLkF1dG9Db21wbGV0ZScsICdnb29nLnVpLmFjLklucHV0SGFuZGxlcicsICdnb29nLnVpLmFjLlJlbW90ZUFycmF5TWF0Y2hlcicsICdnb29nLnVpLmFjLlJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9yZW1vdGVhcnJheW1hdGNoZXIuanMnLCBbJ2dvb2cudWkuYWMuUmVtb3RlQXJyYXlNYXRjaGVyJ10sIFsnZ29vZy5EaXNwb3NhYmxlJywgJ2dvb2cuVXJpJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLm5ldC5YaHJJbyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWMvcmVtb3RlYXJyYXltYXRjaGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuYWMuUmVtb3RlQXJyYXlNYXRjaGVyVGVzdCddLCBbJ2dvb2cubmV0LlhocklvJywgJ2dvb2cudGVzdGluZy5Nb2NrQ29udHJvbCcsICdnb29nLnRlc3RpbmcubmV0LlhocklvJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5hYy5SZW1vdGVBcnJheU1hdGNoZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9yZW5kZXJlci5qcycsIFsnZ29vZy51aS5hYy5SZW5kZXJlcicsICdnb29nLnVpLmFjLlJlbmRlcmVyLkN1c3RvbVJlbmRlcmVyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRpc3Bvc2UnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZnguZG9tLkZhZGVJbkFuZFNob3cnLCAnZ29vZy5meC5kb20uRmFkZU91dEFuZEhpZGUnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5JZEdlbmVyYXRvcicsICdnb29nLnVpLmFjLkF1dG9Db21wbGV0ZSddLCB7J2xhbmcnOiAnZXM2J30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL3JlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuYWMuUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5meC5kb20uRmFkZUluQW5kU2hvdycsICdnb29nLmZ4LmRvbS5GYWRlT3V0QW5kSGlkZScsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5hYy5BdXRvQ29tcGxldGUnLCAnZ29vZy51aS5hYy5SZW5kZXJlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL3JlbmRlcm9wdGlvbnMuanMnLCBbJ2dvb2cudWkuYWMuUmVuZGVyT3B0aW9ucyddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL3JpY2hpbnB1dGhhbmRsZXIuanMnLCBbJ2dvb2cudWkuYWMuUmljaElucHV0SGFuZGxlciddLCBbJ2dvb2cudWkuYWMuSW5wdXRIYW5kbGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9yaWNocmVtb3RlLmpzJywgWydnb29nLnVpLmFjLlJpY2hSZW1vdGUnXSwgWydnb29nLnVpLmFjLkF1dG9Db21wbGV0ZScsICdnb29nLnVpLmFjLlJlbW90ZScsICdnb29nLnVpLmFjLlJlbmRlcmVyJywgJ2dvb2cudWkuYWMuUmljaElucHV0SGFuZGxlcicsICdnb29nLnVpLmFjLlJpY2hSZW1vdGVBcnJheU1hdGNoZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjL3JpY2hyZW1vdGVhcnJheW1hdGNoZXIuanMnLCBbJ2dvb2cudWkuYWMuUmljaFJlbW90ZUFycmF5TWF0Y2hlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudWkuYWMuUmVtb3RlQXJyYXlNYXRjaGVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hYy9yaWNocmVtb3RlYXJyYXltYXRjaGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuYWMuUmljaFJlbW90ZUFycmF5TWF0Y2hlclRlc3QnXSwgWydnb29nLm5ldC5YaHJJbycsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLm5ldC5YaHJJbycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuYWMuUmljaFJlbW90ZUFycmF5TWF0Y2hlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FjdGl2aXR5bW9uaXRvci5qcycsIFsnZ29vZy51aS5BY3Rpdml0eU1vbml0b3InXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hY3Rpdml0eW1vbml0b3JfdGVzdC5qcycsIFsnZ29vZy51aS5BY3Rpdml0eU1vbml0b3JUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkFjdGl2aXR5TW9uaXRvciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2FkdmFuY2VkdG9vbHRpcC5qcycsIFsnZ29vZy51aS5BZHZhbmNlZFRvb2x0aXAnXSwgWydnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5tYXRoLkJveCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuVG9vbHRpcCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYWR2YW5jZWR0b29sdGlwX3Rlc3QuanMnLCBbJ2dvb2cudWkuQWR2YW5jZWRUb29sdGlwVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkFkdmFuY2VkVG9vbHRpcCcsICdnb29nLnVpLlRvb2x0aXAnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hbmltYXRlZHppcHB5LmpzJywgWydnb29nLnVpLkFuaW1hdGVkWmlwcHknXSwgWydnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5meC5UcmFuc2l0aW9uJywgJ2dvb2cuZnguZWFzaW5nJywgJ2dvb2cudWkuWmlwcHknLCAnZ29vZy51aS5aaXBweUV2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9hbmltYXRlZHppcHB5X3Rlc3QuanMnLCBbJ2dvb2cudWkuQW5pbWF0ZWRaaXBweVRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmZ4LkFuaW1hdGlvbicsICdnb29nLmZ4LlRyYW5zaXRpb24nLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkFuaW1hdGVkWmlwcHknLCAnZ29vZy51aS5aaXBweSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2F0dGFjaGFibGVtZW51LmpzJywgWydnb29nLnVpLkF0dGFjaGFibGVNZW51J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5JdGVtRXZlbnQnLCAnZ29vZy51aS5NZW51QmFzZScsICdnb29nLnVpLlBvcHVwQmFzZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYmlkaWlucHV0LmpzJywgWydnb29nLnVpLkJpZGlJbnB1dCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLklucHV0VHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLklucHV0SGFuZGxlcicsICdnb29nLmkxOG4uYmlkaScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYmlkaWlucHV0X3Rlc3QuanMnLCBbJ2dvb2cudWkuQmlkaUlucHV0VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5CaWRpSW5wdXQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9idWJibGUuanMnLCBbJ2dvb2cudWkuQnViYmxlJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5tYXRoLkJveCcsICdnb29nLnBvc2l0aW9uaW5nJywgJ2dvb2cucG9zaXRpb25pbmcuQWJzb2x1dGVQb3NpdGlvbicsICdnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXJCaXQnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLlBvcHVwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9idXR0b24uanMnLCBbJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQnV0dG9uLlNpZGUnXSwgWydnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5ldmVudHMuS2V5SGFuZGxlcicsICdnb29nLnVpLkJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkuQnV0dG9uU2lkZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5OYXRpdmVCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9idXR0b25fdGVzdC5qcycsIFsnZ29vZy51aS5CdXR0b25UZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkJ1dHRvbicsICdnb29nLnVpLkJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkuQnV0dG9uU2lkZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLk5hdGl2ZUJ1dHRvblJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvYnV0dG9ucmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuQnV0dG9uUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLnVpLkJ1dHRvblNpZGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db250cm9sUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2J1dHRvbnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuQnV0dG9uUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnLCAnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5CdXR0b25SZW5kZXJlcicsICdnb29nLnVpLkJ1dHRvblNpZGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db250cm9sUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9idXR0b25zaWRlLmpzJywgWydnb29nLnVpLkJ1dHRvblNpZGUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jaGFyY291bnRlci5qcycsIFsnZ29vZy51aS5DaGFyQ291bnRlcicsICdnb29nLnVpLkNoYXJDb3VudGVyLkRpc3BsYXknXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5JbnB1dEhhbmRsZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NoYXJjb3VudGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuQ2hhckNvdW50ZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLmFzc2VydHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNoYXJDb3VudGVyJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY2hhcnBpY2tlci5qcycsIFsnZ29vZy51aS5DaGFyUGlja2VyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5JbnB1dEhhbmRsZXInLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5ldmVudHMuS2V5SGFuZGxlcicsICdnb29nLmkxOG4uQ2hhckxpc3REZWNvbXByZXNzb3InLCAnZ29vZy5pMThuLkNoYXJQaWNrZXJEYXRhJywgJ2dvb2cuaTE4bi51Q2hhcicsICdnb29nLmkxOG4udUNoYXIuTmFtZUZldGNoZXInLCAnZ29vZy5zdHJ1Y3RzLlNldCcsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udGFpbmVyU2Nyb2xsZXInLCAnZ29vZy51aS5GbGF0QnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5Ib3ZlckNhcmQnLCAnZ29vZy51aS5MYWJlbElucHV0JywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnVCdXR0b24nLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLlRvb2x0aXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NoYXJwaWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5DaGFyUGlja2VyVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZGlzcG9zZScsICdnb29nLmRvbScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5pMThuLkNoYXJQaWNrZXJEYXRhJywgJ2dvb2cuaTE4bi51Q2hhci5OYW1lRmV0Y2hlcicsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5DaGFyUGlja2VyJywgJ2dvb2cudWkuRmxhdEJ1dHRvblJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY2hlY2tib3guanMnLCBbJ2dvb2cudWkuQ2hlY2tib3gnLCAnZ29vZy51aS5DaGVja2JveC5TdGF0ZSddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLnN0cmluZycsICdnb29nLnVpLkNoZWNrYm94UmVuZGVyZXInLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db250cm9sJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NoZWNrYm94X3Rlc3QuanMnLCBbJ2dvb2cudWkuQ2hlY2tib3hUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5DaGVja2JveCcsICdnb29nLnVpLkNoZWNrYm94UmVuZGVyZXInLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db250cm9sUmVuZGVyZXInLCAnZ29vZy51aS5kZWNvcmF0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NoZWNrYm94bWVudWl0ZW0uanMnLCBbJ2dvb2cudWkuQ2hlY2tCb3hNZW51SXRlbSddLCBbJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY2hlY2tib3hyZW5kZXJlci5qcycsIFsnZ29vZy51aS5DaGVja2JveFJlbmRlcmVyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLm9iamVjdCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29sb3JtZW51YnV0dG9uLmpzJywgWydnb29nLnVpLkNvbG9yTWVudUJ1dHRvbiddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5vYmplY3QnLCAnZ29vZy51aS5Db2xvck1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLkNvbG9yUGFsZXR0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLk1lbnUnLCAnZ29vZy51aS5NZW51QnV0dG9uJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbG9ybWVudWJ1dHRvbnJlbmRlcmVyLmpzJywgWydnb29nLnVpLkNvbG9yTWVudUJ1dHRvblJlbmRlcmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuY29sb3InLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy51aS5NZW51QnV0dG9uUmVuZGVyZXInLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbG9ybWVudWJ1dHRvbnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuQ29sb3JNZW51QnV0dG9uVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkuUmVuZGVyZXJIYXJuZXNzJywgJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnLCAnZ29vZy51aS5Db2xvck1lbnVCdXR0b24nLCAnZ29vZy51aS5Db2xvck1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbG9ycGFsZXR0ZS5qcycsIFsnZ29vZy51aS5Db2xvclBhbGV0dGUnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuY29sb3InLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuUGFsZXR0ZScsICdnb29nLnVpLlBhbGV0dGVSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29sb3JwYWxldHRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuQ29sb3JQYWxldHRlVGVzdCddLCBbJ2dvb2cuY29sb3InLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29sb3JQYWxldHRlJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29sb3JwaWNrZXIuanMnLCBbJ2dvb2cudWkuQ29sb3JQaWNrZXInLCAnZ29vZy51aS5Db2xvclBpY2tlci5FdmVudFR5cGUnXSwgWydnb29nLnVpLkNvbG9yUGFsZXR0ZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29tYm9ib3guanMnLCBbJ2dvb2cudWkuQ29tYm9Cb3gnLCAnZ29vZy51aS5Db21ib0JveEl0ZW0nXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLklucHV0SGFuZGxlcicsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cubG9nJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cucG9zaXRpb25pbmcuTWVudUFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkl0ZW1FdmVudCcsICdnb29nLnVpLkxhYmVsSW5wdXQnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5NZW51U2VwYXJhdG9yJywgJ2dvb2cudWkucmVnaXN0cnknLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbWJvYm94X3Rlc3QuanMnLCBbJ2dvb2cudWkuQ29tYm9Cb3hUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21ib0JveCcsICdnb29nLnVpLkNvbWJvQm94SXRlbScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlcicsICdnb29nLnVpLkxhYmVsSW5wdXQnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb21wb25lbnQuanMnLCBbJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29tcG9uZW50LkVycm9yJywgJ2dvb2cudWkuQ29tcG9uZW50LkV2ZW50VHlwZScsICdnb29nLnVpLkNvbXBvbmVudC5TdGF0ZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5JZEdlbmVyYXRvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29tcG9uZW50X3Rlc3QuanMnLCBbJ2dvb2cudWkuQ29tcG9uZW50VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21wb25lbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb21wb25lbnR1dGlsLmpzJywgWydnb29nLnVpLkNvbXBvbmVudFV0aWwnXSwgWydnb29nLmV2ZW50cy5Nb3VzZUFzTW91c2VFdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuTW91c2VFdmVudHMnLCAnZ29vZy5ldmVudHMuUG9pbnRlckFzTW91c2VFdmVudFR5cGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbXBvbmVudHV0aWxfdGVzdC5qcycsIFsnZ29vZy51aS5Db21wb25lbnRVdGlsVGVzdCddLCBbJ2dvb2cuZXZlbnRzLk1vdXNlQXNNb3VzZUV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5Qb2ludGVyQXNNb3VzZUV2ZW50VHlwZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29tcG9uZW50VXRpbCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbnRhaW5lci5qcycsIFsnZ29vZy51aS5Db250YWluZXInLCAnZ29vZy51aS5Db250YWluZXIuRXZlbnRUeXBlJywgJ2dvb2cudWkuQ29udGFpbmVyLk9yaWVudGF0aW9uJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db21wb25lbnRVdGlsJywgJ2dvb2cudWkuQ29udGFpbmVyUmVuZGVyZXInLCAnZ29vZy51aS5Db250cm9sJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250YWluZXJfdGVzdC5qcycsIFsnZ29vZy51aS5Db250YWluZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLktleUV2ZW50JywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJGYWxsYmFja0V2ZW50VHlwZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLkNvbnRyb2wnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250YWluZXJyZW5kZXJlci5qcycsIFsnZ29vZy51aS5Db250YWluZXJSZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5yZWdpc3RyeScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29udGFpbmVycmVuZGVyZXJfdGVzdC5qcycsIFsnZ29vZy51aS5Db250YWluZXJSZW5kZXJlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuQ29udGFpbmVyJywgJ2dvb2cudWkuQ29udGFpbmVyUmVuZGVyZXInLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250YWluZXJzY3JvbGxlci5qcycsIFsnZ29vZy51aS5Db250YWluZXJTY3JvbGxlciddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLlRpbWVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udGFpbmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250YWluZXJzY3JvbGxlcl90ZXN0LmpzJywgWydnb29nLnVpLkNvbnRhaW5lclNjcm9sbGVyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29udGFpbmVyJywgJ2dvb2cudWkuQ29udGFpbmVyU2Nyb2xsZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250cm9sLmpzJywgWydnb29nLnVpLkNvbnRyb2wnXSwgWydnb29nLkRpc3Bvc2FibGUnLCAnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29tcG9uZW50VXRpbCcsICdnb29nLnVpLkNvbnRyb2xDb250ZW50JywgJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbnRyb2xfdGVzdC5qcycsIFsnZ29vZy51aS5Db250cm9sVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLlBvaW50ZXJGYWxsYmFja0V2ZW50VHlwZScsICdnb29nLmh0bWwudGVzdGluZycsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5FeHBlY3RlZEZhaWx1cmVzJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udHJvbCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5JywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29udHJvbGNvbnRlbnQuanMnLCBbJ2dvb2cudWkuQ29udHJvbENvbnRlbnQnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb250cm9scmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLm9iamVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udHJvbENvbnRlbnQnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NvbnRyb2xyZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLkNvbnRyb2xSZW5kZXJlclRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5Db250cm9sUmVuZGVyZXInLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jb29raWVlZGl0b3IuanMnLCBbJ2dvb2cudWkuQ29va2llRWRpdG9yJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubmV0LmNvb2tpZXMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY29va2llZWRpdG9yX3Rlc3QuanMnLCBbJ2dvb2cudWkuQ29va2llRWRpdG9yVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm5ldC5jb29raWVzJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvb2tpZUVkaXRvciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2NzczNidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5Dc3MzQnV0dG9uUmVuZGVyZXInXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5CdXR0b25SZW5kZXJlcicsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY3NzM21lbnVidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5Dc3MzTWVudUJ1dHRvblJlbmRlcmVyJ10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5NZW51QnV0dG9uJywgJ2dvb2cudWkuTWVudUJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Nzc25hbWVzLmpzJywgWydnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jdXN0b21idXR0b24uanMnLCBbJ2dvb2cudWkuQ3VzdG9tQnV0dG9uJ10sIFsnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5DdXN0b21CdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jdXN0b21idXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5DdXN0b21CdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudWkuQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5JTkxJTkVfQkxPQ0tfQ0xBU1NOQU1FJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9jdXN0b21jb2xvcnBhbGV0dGUuanMnLCBbJ2dvb2cudWkuQ3VzdG9tQ29sb3JQYWxldHRlJ10sIFsnZ29vZy5jb2xvcicsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLkNvbG9yUGFsZXR0ZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvY3VzdG9tY29sb3JwYWxldHRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuQ3VzdG9tQ29sb3JQYWxldHRlVGVzdCddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5DdXN0b21Db2xvclBhbGV0dGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kYXRlcGlja2VyLmpzJywgWydnb29nLnVpLkRhdGVQaWNrZXInLCAnZ29vZy51aS5EYXRlUGlja2VyLkV2ZW50cycsICdnb29nLnVpLkRhdGVQaWNrZXJFdmVudCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRhdGUuRGF0ZScsICdnb29nLmRhdGUuRGF0ZVJhbmdlJywgJ2dvb2cuZGF0ZS5JbnRlcnZhbCcsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlVHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5SGFuZGxlcicsICdnb29nLmkxOG4uRGF0ZVRpbWVGb3JtYXQnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGF0dGVybnMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuRGVmYXVsdERhdGVQaWNrZXJSZW5kZXJlcicsICdnb29nLnVpLklkR2VuZXJhdG9yJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kYXRlcGlja2VyX3Rlc3QuanMnLCBbJ2dvb2cudWkuRGF0ZVBpY2tlclRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuZGF0ZS5EYXRlJywgJ2dvb2cuZGF0ZS5EYXRlUmFuZ2UnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5pMThuLkRhdGVUaW1lU3ltYm9scycsICdnb29nLmkxOG4uRGF0ZVRpbWVTeW1ib2xzX2VuX1VTJywgJ2dvb2cuaTE4bi5EYXRlVGltZVN5bWJvbHNfemhfSEsnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuRGF0ZVBpY2tlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2RhdGVwaWNrZXJyZW5kZXJlci5qcycsIFsnZ29vZy51aS5EYXRlUGlja2VyUmVuZGVyZXInXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kZWNvcmF0ZS5qcycsIFsnZ29vZy51aS5kZWNvcmF0ZSddLCBbJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2RlY29yYXRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuZGVjb3JhdGVUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmRlY29yYXRlJywgJ2dvb2cudWkucmVnaXN0cnknXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kZWZhdWx0ZGF0ZXBpY2tlcnJlbmRlcmVyLmpzJywgWydnb29nLnVpLkRlZmF1bHREYXRlUGlja2VyUmVuZGVyZXInXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudWkuRGF0ZVBpY2tlclJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kaWFsb2cuanMnLCBbJ2dvb2cudWkuRGlhbG9nJywgJ2dvb2cudWkuRGlhbG9nLkJ1dHRvblNldCcsICdnb29nLnVpLkRpYWxvZy5CdXR0b25TZXQuRGVmYXVsdEJ1dHRvbnMnLCAnZ29vZy51aS5EaWFsb2cuRGVmYXVsdEJ1dHRvbkNhcHRpb25zJywgJ2dvb2cudWkuRGlhbG9nLkRlZmF1bHRCdXR0b25LZXlzJywgJ2dvb2cudWkuRGlhbG9nLkV2ZW50JywgJ2dvb2cudWkuRGlhbG9nLkV2ZW50VHlwZSddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZG9tLnNhZmUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLktleXMnLCAnZ29vZy5meC5EcmFnZ2VyJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLm1hdGguUmVjdCcsICdnb29nLnN0cmluZycsICdnb29nLnN0cnVjdHMuTWFwJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Nb2RhbFBvcHVwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kaWFsb2dfdGVzdC5qcycsIFsnZ29vZy51aS5EaWFsb2dUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5meC5jc3MzJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwudGVzdGluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkRpYWxvZycsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2RpbWVuc2lvbnBpY2tlci5qcycsIFsnZ29vZy51aS5EaW1lbnNpb25QaWNrZXInXSwgWydnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQuUG9pbnRlclR5cGUnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29tcG9uZW50VXRpbCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5EaW1lbnNpb25QaWNrZXJSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kaW1lbnNpb25waWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5EaW1lbnNpb25QaWNrZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuRGltZW5zaW9uUGlja2VyJywgJ2dvb2cudWkuRGltZW5zaW9uUGlja2VyUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kaW1lbnNpb25waWNrZXJyZW5kZXJlci5qcycsIFsnZ29vZy51aS5EaW1lbnNpb25QaWNrZXJSZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhLkFubm91bmNlcicsICdnb29nLmExMXkuYXJpYS5MaXZlUHJpb3JpdHknLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmkxOG4uYmlkaScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kaW1lbnNpb25waWNrZXJyZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLkRpbWVuc2lvblBpY2tlclJlbmRlcmVyVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhLkxpdmVQcmlvcml0eScsICdnb29nLmFycmF5JywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuRGltZW5zaW9uUGlja2VyJywgJ2dvb2cudWkuRGltZW5zaW9uUGlja2VyUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9kcmFnZHJvcGRldGVjdG9yLmpzJywgWydnb29nLnVpLkRyYWdEcm9wRGV0ZWN0b3InLCAnZ29vZy51aS5EcmFnRHJvcERldGVjdG9yLkV2ZW50VHlwZScsICdnb29nLnVpLkRyYWdEcm9wRGV0ZWN0b3IuSW1hZ2VEcm9wRXZlbnQnLCAnZ29vZy51aS5EcmFnRHJvcERldGVjdG9yLkxpbmtEcm9wRXZlbnQnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2RyaWxsZG93bnJvdy5qcycsIFsnZ29vZy51aS5EcmlsbGRvd25Sb3cnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZHJpbGxkb3ducm93X3Rlc3QuanMnLCBbJ2dvb2cudWkuRHJpbGxkb3duUm93VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5odG1sLlNhZmVIdG1sJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5EcmlsbGRvd25Sb3cnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lZGl0b3IvYWJzdHJhY3RkaWFsb2cuanMnLCBbJ2dvb2cudWkuZWRpdG9yLkFic3RyYWN0RGlhbG9nJywgJ2dvb2cudWkuZWRpdG9yLkFic3RyYWN0RGlhbG9nLkJ1aWxkZXInLCAnZ29vZy51aS5lZGl0b3IuQWJzdHJhY3REaWFsb2cuRXZlbnRUeXBlJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnN0cmluZycsICdnb29nLnVpLkRpYWxvZycsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZWRpdG9yL2Fic3RyYWN0ZGlhbG9nX3Rlc3QuanMnLCBbJ2dvb2cudWkuZWRpdG9yLkFic3RyYWN0RGlhbG9nVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLkRvbUhlbHBlcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVkaXRvci5BYnN0cmFjdERpYWxvZycsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci9idWJibGUuanMnLCBbJ2dvb2cudWkuZWRpdG9yLkJ1YmJsZSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLlZpZXdwb3J0U2l6ZU1vbml0b3InLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZWRpdG9yLnN0eWxlJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5sb2cnLCAnZ29vZy5tYXRoLkJveCcsICdnb29nLm9iamVjdCcsICdnb29nLnBvc2l0aW9uaW5nJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3cnLCAnZ29vZy5wb3NpdGlvbmluZy5PdmVyZmxvd1N0YXR1cycsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuUG9wdXBCYXNlJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lZGl0b3IvYnViYmxlX3Rlc3QuanMnLCBbJ2dvb2cudWkuZWRpdG9yLkJ1YmJsZVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93U3RhdHVzJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5UZXN0SGVscGVyJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLmVkaXRvci5CdWJibGUnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci9kZWZhdWx0dG9vbGJhci5qcycsIFsnZ29vZy51aS5lZGl0b3IuQnV0dG9uRGVzY3JpcHRvcicsICdnb29nLnVpLmVkaXRvci5EZWZhdWx0VG9vbGJhciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmVkaXRvci5Db21tYW5kJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5lZGl0b3IuVG9vbGJhckZhY3RvcnknLCAnZ29vZy51aS5lZGl0b3IubWVzc2FnZXMnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci9saW5rZGlhbG9nLmpzJywgWydnb29nLnVpLmVkaXRvci5MaW5rRGlhbG9nJywgJ2dvb2cudWkuZWRpdG9yLkxpbmtEaWFsb2cuQmVmb3JlVGVzdExpbmtFdmVudCcsICdnb29nLnVpLmVkaXRvci5MaW5rRGlhbG9nLkV2ZW50VHlwZScsICdnb29nLnVpLmVkaXRvci5MaW5rRGlhbG9nLk9rRXZlbnQnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuZWRpdG9yLkJyb3dzZXJGZWF0dXJlJywgJ2dvb2cuZWRpdG9yLkxpbmsnLCAnZ29vZy5lZGl0b3IuZm9jdXMnLCAnZ29vZy5lZGl0b3Iubm9kZScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuSW5wdXRIYW5kbGVyJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmh0bWwuU2FmZUh0bWxGb3JtYXR0ZXInLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuTGlua0J1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkuZWRpdG9yLkFic3RyYWN0RGlhbG9nJywgJ2dvb2cudWkuZWRpdG9yLlRhYlBhbmUnLCAnZ29vZy51aS5lZGl0b3IubWVzc2FnZXMnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy53aW5kb3cnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci9saW5rZGlhbG9nX3Rlc3QuanMnLCBbJ2dvb2cudWkuZWRpdG9yLkxpbmtEaWFsb2dUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uRG9tSGVscGVyJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5lZGl0b3IuQnJvd3NlckZlYXR1cmUnLCAnZ29vZy5lZGl0b3IuTGluaycsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50JywgJ2dvb2cudGVzdGluZy5tb2NrbWF0Y2hlcnMnLCAnZ29vZy50ZXN0aW5nLm1vY2ttYXRjaGVycy5Bcmd1bWVudE1hdGNoZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVkaXRvci5BYnN0cmFjdERpYWxvZycsICdnb29nLnVpLmVkaXRvci5MaW5rRGlhbG9nJywgJ2dvb2cudWkuZWRpdG9yLm1lc3NhZ2VzJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZWRpdG9yL21lc3NhZ2VzLmpzJywgWydnb29nLnVpLmVkaXRvci5tZXNzYWdlcyddLCBbJ2dvb2cuaHRtbC5TYWZlSHRtbEZvcm1hdHRlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZWRpdG9yL3RhYnBhbmUuanMnLCBbJ2dvb2cudWkuZWRpdG9yLlRhYlBhbmUnXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5UYWInLCAnZ29vZy51aS5UYWJCYXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci90b29sYmFyY29udHJvbGxlci5qcycsIFsnZ29vZy51aS5lZGl0b3IuVG9vbGJhckNvbnRyb2xsZXInXSwgWydnb29nLmVkaXRvci5GaWVsZCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2VkaXRvci90b29sYmFyZmFjdG9yeS5qcycsIFsnZ29vZy51aS5lZGl0b3IuVG9vbGJhckZhY3RvcnknXSwgWydnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuVW5pY29kZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udGFpbmVyJywgJ2dvb2cudWkuT3B0aW9uJywgJ2dvb2cudWkuVG9vbGJhcicsICdnb29nLnVpLlRvb2xiYXJCdXR0b24nLCAnZ29vZy51aS5Ub29sYmFyQ29sb3JNZW51QnV0dG9uJywgJ2dvb2cudWkuVG9vbGJhck1lbnVCdXR0b24nLCAnZ29vZy51aS5Ub29sYmFyUmVuZGVyZXInLCAnZ29vZy51aS5Ub29sYmFyU2VsZWN0JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lZGl0b3IvdG9vbGJhcmZhY3RvcnlfdGVzdC5qcycsIFsnZ29vZy51aS5lZGl0b3IuVG9vbGJhckZhY3RvcnlUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLmVkaXRvci5UZXN0SGVscGVyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5lZGl0b3IuVG9vbGJhckZhY3RvcnknLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lbW9qaS9lbW9qaS5qcycsIFsnZ29vZy51aS5lbW9qaS5FbW9qaSddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Vtb2ppL2Vtb2ppcGFsZXR0ZS5qcycsIFsnZ29vZy51aS5lbW9qaS5FbW9qaVBhbGV0dGUnXSwgWydnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5uZXQuSW1hZ2VMb2FkZXInLCAnZ29vZy51aS5QYWxldHRlJywgJ2dvb2cudWkuZW1vamkuRW1vamknLCAnZ29vZy51aS5lbW9qaS5FbW9qaVBhbGV0dGVSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZW1vamkvZW1vamlwYWxldHRlcmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuZW1vamkuRW1vamlQYWxldHRlUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLlBhbGV0dGVSZW5kZXJlcicsICdnb29nLnVpLmVtb2ppLkVtb2ppJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lbW9qaS9lbW9qaXBpY2tlci5qcycsIFsnZ29vZy51aS5lbW9qaS5FbW9qaVBpY2tlciddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLlRhYlBhbmUnLCAnZ29vZy51aS5lbW9qaS5FbW9qaScsICdnb29nLnVpLmVtb2ppLkVtb2ppUGFsZXR0ZScsICdnb29nLnVpLmVtb2ppLkVtb2ppUGFsZXR0ZVJlbmRlcmVyJywgJ2dvb2cudWkuZW1vamkuUHJvZ3Jlc3NpdmVFbW9qaVBhbGV0dGVSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZW1vamkvZW1vamlwaWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5lbW9qaS5FbW9qaVBpY2tlclRlc3QnXSwgWydnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5lbW9qaS5FbW9qaScsICdnb29nLnVpLmVtb2ppLkVtb2ppUGlja2VyJywgJ2dvb2cudWkuZW1vamkuU3ByaXRlSW5mbyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Vtb2ppL2Zhc3Rfbm9ucHJvZ3Jlc3NpdmVfZW1vamlwaWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5lbW9qaS5GYXN0Tm9uUHJvZ3Jlc3NpdmVFbW9qaVBpY2tlclRlc3QnXSwgWydnb29nLlByb21pc2UnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLm5ldC5FdmVudFR5cGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuVGVzdENhc2UnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVtb2ppLkVtb2ppJywgJ2dvb2cudWkuZW1vamkuRW1vamlQaWNrZXInLCAnZ29vZy51aS5lbW9qaS5TcHJpdGVJbmZvJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZW1vamkvZmFzdF9wcm9ncmVzc2l2ZV9lbW9qaXBpY2tlcl90ZXN0LmpzJywgWydnb29nLnVpLmVtb2ppLkZhc3RQcm9ncmVzc2l2ZUVtb2ppUGlja2VyVGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cubmV0LkV2ZW50VHlwZScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5lbW9qaS5FbW9qaScsICdnb29nLnVpLmVtb2ppLkVtb2ppUGlja2VyJywgJ2dvb2cudWkuZW1vamkuU3ByaXRlSW5mbyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Vtb2ppL3BvcHVwZW1vamlwaWNrZXIuanMnLCBbJ2dvb2cudWkuZW1vamkuUG9wdXBFbW9qaVBpY2tlciddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Qb3B1cCcsICdnb29nLnVpLmVtb2ppLkVtb2ppUGlja2VyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lbW9qaS9wb3B1cGVtb2ppcGlja2VyX3Rlc3QuanMnLCBbJ2dvb2cudWkuZW1vamkuUG9wdXBFbW9qaVBpY2tlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuZW1vamkuUG9wdXBFbW9qaVBpY2tlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Vtb2ppL3Byb2dyZXNzaXZlZW1vamlwYWxldHRlcmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuZW1vamkuUHJvZ3Jlc3NpdmVFbW9qaVBhbGV0dGVSZW5kZXJlciddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLmVtb2ppLkVtb2ppUGFsZXR0ZVJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9lbW9qaS9zcHJpdGVpbmZvLmpzJywgWydnb29nLnVpLmVtb2ppLlNwcml0ZUluZm8nXSwgW10sIHsnbGFuZyc6ICdlczYnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZW1vamkvc3ByaXRlaW5mb190ZXN0LmpzJywgWydnb29nLnVpLmVtb2ppLlNwcml0ZUluZm9UZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLmVtb2ppLlNwcml0ZUluZm8nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9maWx0ZXJlZG1lbnUuanMnLCBbJ2dvb2cudWkuRmlsdGVyZWRNZW51J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuQXV0b0NvbXBsZXRlVmFsdWVzJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLklucHV0VHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5JbnB1dEhhbmRsZXInLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkZpbHRlck9ic2VydmluZ01lbnVJdGVtJywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnVJdGVtJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9maWx0ZXJlZG1lbnVfdGVzdC5qcycsIFsnZ29vZy51aS5GaWx0ZXJlZE1lbnVUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuQXV0b0NvbXBsZXRlVmFsdWVzJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubWF0aC5SZWN0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuRmlsdGVyZWRNZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9maWx0ZXJvYnNlcnZpbmdtZW51aXRlbS5qcycsIFsnZ29vZy51aS5GaWx0ZXJPYnNlcnZpbmdNZW51SXRlbSddLCBbJ2dvb2cudWkuRmlsdGVyT2JzZXJ2aW5nTWVudUl0ZW1SZW5kZXJlcicsICdnb29nLnVpLk1lbnVJdGVtJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2ZpbHRlcm9ic2VydmluZ21lbnVpdGVtcmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuRmlsdGVyT2JzZXJ2aW5nTWVudUl0ZW1SZW5kZXJlciddLCBbJ2dvb2cudWkuTWVudUl0ZW1SZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZmxhdGJ1dHRvbnJlbmRlcmVyLmpzJywgWydnb29nLnVpLkZsYXRCdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5JTkxJTkVfQkxPQ0tfQ0xBU1NOQU1FJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2ZsYXRtZW51YnV0dG9ucmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuRmxhdE1lbnVCdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkZsYXRCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUJ1dHRvbicsICdnb29nLnVpLk1lbnVSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9mb3JtcG9zdC5qcycsIFsnZ29vZy51aS5Gb3JtUG9zdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2Zvcm1wb3N0X3Rlc3QuanMnLCBbJ2dvb2cudWkuRm9ybVBvc3RUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Gb3JtUG9zdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QuaXNWZXJzaW9uJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZ2F1Z2UuanMnLCBbJ2dvb2cudWkuR2F1Z2UnLCAnZ29vZy51aS5HYXVnZUNvbG9yZWRSYW5nZSddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnguQW5pbWF0aW9uJywgJ2dvb2cuZnguVHJhbnNpdGlvbicsICdnb29nLmZ4LmVhc2luZycsICdnb29nLmdyYXBoaWNzJywgJ2dvb2cuZ3JhcGhpY3MuRm9udCcsICdnb29nLmdyYXBoaWNzLlBhdGgnLCAnZ29vZy5ncmFwaGljcy5Tb2xpZEZpbGwnLCAnZ29vZy5tYXRoJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuR2F1Z2VUaGVtZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvZ2F1Z2V0aGVtZS5qcycsIFsnZ29vZy51aS5HYXVnZVRoZW1lJ10sIFsnZ29vZy5ncmFwaGljcy5MaW5lYXJHcmFkaWVudCcsICdnb29nLmdyYXBoaWNzLlNvbGlkRmlsbCcsICdnb29nLmdyYXBoaWNzLlN0cm9rZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaG92ZXJjYXJkLmpzJywgWydnb29nLnVpLkhvdmVyQ2FyZCcsICdnb29nLnVpLkhvdmVyQ2FyZC5FdmVudFR5cGUnLCAnZ29vZy51aS5Ib3ZlckNhcmQuVHJpZ2dlckV2ZW50J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy51aS5BZHZhbmNlZFRvb2x0aXAnLCAnZ29vZy51aS5Qb3B1cEJhc2UnLCAnZ29vZy51aS5Ub29sdGlwJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9ob3ZlcmNhcmRfdGVzdC5qcycsIFsnZ29vZy51aS5Ib3ZlckNhcmRUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuSG92ZXJDYXJkJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaHN2YXBhbGV0dGUuanMnLCBbJ2dvb2cudWkuSHN2YVBhbGV0dGUnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuY29sb3IuYWxwaGEnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkhzdlBhbGV0dGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2hzdmFwYWxldHRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuSHN2YVBhbGV0dGVUZXN0J10sIFsnZ29vZy5jb2xvci5hbHBoYScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Ic3ZhUGFsZXR0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2hzdnBhbGV0dGUuanMnLCBbJ2dvb2cudWkuSHN2UGFsZXR0ZSddLCBbJ2dvb2cuY29sb3InLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLklucHV0SGFuZGxlcicsICdnb29nLnN0eWxlJywgJ2dvb2cuc3R5bGUuYmlkaScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaHN2cGFsZXR0ZV90ZXN0LmpzJywgWydnb29nLnVpLkhzdlBhbGV0dGVUZXN0J10sIFsnZ29vZy5jb2xvcicsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Ic3ZQYWxldHRlJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaWRnZW5lcmF0b3IuanMnLCBbJ2dvb2cudWkuSWRHZW5lcmF0b3InXSwgW10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9pZGxldGltZXIuanMnLCBbJ2dvb2cudWkuSWRsZVRpbWVyJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cudWkuQWN0aXZpdHlNb25pdG9yJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9pZGxldGltZXJfdGVzdC5qcycsIFsnZ29vZy51aS5JZGxlVGltZXJUZXN0J10sIFsnZ29vZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuSWRsZVRpbWVyJywgJ2dvb2cudWkuTW9ja0FjdGl2aXR5TW9uaXRvciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2lmcmFtZW1hc2suanMnLCBbJ2dvb2cudWkuSWZyYW1lTWFzayddLCBbJ2dvb2cuRGlzcG9zYWJsZScsICdnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmlmcmFtZScsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5zdHJ1Y3RzLlBvb2wnLCAnZ29vZy5zdHlsZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaWZyYW1lbWFza190ZXN0LmpzJywgWydnb29nLnVpLklmcmFtZU1hc2tUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5pZnJhbWUnLCAnZ29vZy5zdHJ1Y3RzLlBvb2wnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5TdHJpY3RNb2NrJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5JZnJhbWVNYXNrJywgJ2dvb2cudWkuUG9wdXAnLCAnZ29vZy51aS5Qb3B1cEJhc2UnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9pbWFnZWxlc3NidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5JbWFnZWxlc3NCdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ3VzdG9tQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5JTkxJTkVfQkxPQ0tfQ0xBU1NOQU1FJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2ltYWdlbGVzc21lbnVidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5JbWFnZWxlc3NNZW51QnV0dG9uUmVuZGVyZXInXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5NZW51QnV0dG9uJywgJ2dvb2cudWkuTWVudUJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2lucHV0ZGF0ZXBpY2tlci5qcycsIFsnZ29vZy51aS5JbnB1dERhdGVQaWNrZXInXSwgWydnb29nLmRhdGUuRGF0ZVRpbWUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5pMThuLkRhdGVUaW1lUGFyc2UnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5EYXRlUGlja2VyJywgJ2dvb2cudWkuTGFiZWxJbnB1dCcsICdnb29nLnVpLlBvcHVwQmFzZScsICdnb29nLnVpLlBvcHVwRGF0ZVBpY2tlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaW5wdXRkYXRlcGlja2VyX3Rlc3QuanMnLCBbJ2dvb2cudWkuSW5wdXREYXRlUGlja2VyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuaTE4bi5EYXRlVGltZUZvcm1hdCcsICdnb29nLmkxOG4uRGF0ZVRpbWVQYXJzZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuSW5wdXREYXRlUGlja2VyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvaXRlbWV2ZW50LmpzJywgWydnb29nLnVpLkl0ZW1FdmVudCddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9rZXlib2FyZGV2ZW50ZGF0YS5qcycsIFsnZ29vZy51aS5LZXlib2FyZEV2ZW50RGF0YSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9rZXlib2FyZHNob3J0Y3V0aGFuZGxlci5qcycsIFsnZ29vZy51aS5LZXlib2FyZFNob3J0Y3V0RXZlbnQnLCAnZ29vZy51aS5LZXlib2FyZFNob3J0Y3V0SGFuZGxlcicsICdnb29nLnVpLktleWJvYXJkU2hvcnRjdXRIYW5kbGVyLkV2ZW50VHlwZScsICdnb29nLnVpLktleWJvYXJkU2hvcnRjdXRIYW5kbGVyLk1vZGlmaWVycyddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLktleU5hbWVzJywgJ2dvb2cuZXZlbnRzLktleXMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy51aS5LZXlib2FyZEV2ZW50RGF0YScsICdnb29nLnVpLlN5bnRoZXRpY0tleWJvYXJkRXZlbnQnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2tleWJvYXJkc2hvcnRjdXRoYW5kbGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuS2V5Ym9hcmRTaG9ydGN1dEhhbmRsZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuQnJvd3NlckV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cudGVzdGluZy5Nb2NrQ2xvY2snLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLlN0cmljdE1vY2snLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuS2V5Ym9hcmRTaG9ydGN1dEhhbmRsZXInLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9sYWJlbGlucHV0LmpzJywgWydnb29nLnVpLkxhYmVsSW5wdXQnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbGFiZWxpbnB1dF90ZXN0LmpzJywgWydnb29nLnVpLkxhYmVsSW5wdXRUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuTGFiZWxJbnB1dCcsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL2xpbmtidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5MaW5rQnV0dG9uUmVuZGVyZXInXSwgWydnb29nLnVpLkJ1dHRvbicsICdnb29nLnVpLkZsYXRCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS9mbGFzaG9iamVjdC5qcycsIFsnZ29vZy51aS5tZWRpYS5GbGFzaE9iamVjdCcsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0LlNjcmlwdEFjY2Vzc0xldmVsJywgJ2dvb2cudWkubWVkaWEuRmxhc2hPYmplY3QuV21vZGVzJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5odG1sLmZsYXNoJywgJ2dvb2cubG9nJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RydWN0cy5NYXAnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5mbGFzaCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvZmxhc2hvYmplY3RfdGVzdC5qcycsIFsnZ29vZy51aS5tZWRpYS5GbGFzaE9iamVjdFRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5Eb21IZWxwZXInLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLk1vY2tDb250cm9sJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvZmxpY2tyLmpzJywgWydnb29nLnVpLm1lZGlhLkZsaWNrclNldCcsICdnb29nLnVpLm1lZGlhLkZsaWNrclNldE1vZGVsJ10sIFsnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuTWVkaWEnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsJywgJ2dvb2cudWkubWVkaWEuTWVkaWFSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvZmxpY2tyX3Rlc3QuanMnLCBbJ2dvb2cudWkubWVkaWEuRmxpY2tyU2V0VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuRmxpY2tyU2V0JywgJ2dvb2cudWkubWVkaWEuRmxpY2tyU2V0TW9kZWwnLCAnZ29vZy51aS5tZWRpYS5NZWRpYSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL2dvb2dsZXZpZGVvLmpzJywgWydnb29nLnVpLm1lZGlhLkdvb2dsZVZpZGVvJywgJ2dvb2cudWkubWVkaWEuR29vZ2xlVmlkZW9Nb2RlbCddLCBbJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy51aS5tZWRpYS5GbGFzaE9iamVjdCcsICdnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbCcsICdnb29nLnVpLm1lZGlhLk1lZGlhUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL2dvb2dsZXZpZGVvX3Rlc3QuanMnLCBbJ2dvb2cudWkubWVkaWEuR29vZ2xlVmlkZW9UZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkubWVkaWEuRmxhc2hPYmplY3QnLCAnZ29vZy51aS5tZWRpYS5Hb29nbGVWaWRlbycsICdnb29nLnVpLm1lZGlhLkdvb2dsZVZpZGVvTW9kZWwnLCAnZ29vZy51aS5tZWRpYS5NZWRpYSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL21lZGlhLmpzJywgWydnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFSZW5kZXJlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5Db250cm9sJywgJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS9tZWRpYV90ZXN0LmpzJywgWydnb29nLnVpLm1lZGlhLk1lZGlhVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlcicsICdnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbCcsICdnb29nLnVpLm1lZGlhLk1lZGlhUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS9tZWRpYW1vZGVsLmpzJywgWydnb29nLnVpLm1lZGlhLk1lZGlhTW9kZWwnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsLkNhdGVnb3J5JywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbC5DcmVkaXQnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsLkNyZWRpdC5Sb2xlJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbC5DcmVkaXQuU2NoZW1lJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbC5NZWRpdW0nLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsLk1pbWVUeXBlJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbC5QbGF5ZXInLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsLlN1YlRpdGxlJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbC5UaHVtYm5haWwnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL21lZGlhbW9kZWxfdGVzdC5qcycsIFsnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvbXAzLmpzJywgWydnb29nLnVpLm1lZGlhLk1wMyddLCBbJ2dvb2cuc3RyaW5nJywgJ2dvb2cudWkubWVkaWEuRmxhc2hPYmplY3QnLCAnZ29vZy51aS5tZWRpYS5NZWRpYScsICdnb29nLnVpLm1lZGlhLk1lZGlhUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL21wM190ZXN0LmpzJywgWydnb29nLnVpLm1lZGlhLk1wM1Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5tZWRpYS5GbGFzaE9iamVjdCcsICdnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbCcsICdnb29nLnVpLm1lZGlhLk1wMyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL3Bob3RvLmpzJywgWydnb29nLnVpLm1lZGlhLlBob3RvJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvcGhvdG9fdGVzdC5qcycsIFsnZ29vZy51aS5tZWRpYS5QaG90b1Rlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsJywgJ2dvb2cudWkubWVkaWEuUGhvdG8nXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS9waWNhc2EuanMnLCBbJ2dvb2cudWkubWVkaWEuUGljYXNhQWxidW0nLCAnZ29vZy51aS5tZWRpYS5QaWNhc2FBbGJ1bU1vZGVsJ10sIFsnZ29vZy5odG1sLlRydXN0ZWRSZXNvdXJjZVVybCcsICdnb29nLnN0cmluZy5Db25zdCcsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuTWVkaWEnLCAnZ29vZy51aS5tZWRpYS5NZWRpYU1vZGVsJywgJ2dvb2cudWkubWVkaWEuTWVkaWFSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVkaWEvcGljYXNhX3Rlc3QuanMnLCBbJ2dvb2cudWkubWVkaWEuUGljYXNhVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuTWVkaWEnLCAnZ29vZy51aS5tZWRpYS5QaWNhc2FBbGJ1bScsICdnb29nLnVpLm1lZGlhLlBpY2FzYUFsYnVtTW9kZWwnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS92aW1lby5qcycsIFsnZ29vZy51aS5tZWRpYS5WaW1lbycsICdnb29nLnVpLm1lZGlhLlZpbWVvTW9kZWwnXSwgWydnb29nLmh0bWwuVHJ1c3RlZFJlc291cmNlVXJsJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudWkubWVkaWEuRmxhc2hPYmplY3QnLCAnZ29vZy51aS5tZWRpYS5NZWRpYScsICdnb29nLnVpLm1lZGlhLk1lZGlhTW9kZWwnLCAnZ29vZy51aS5tZWRpYS5NZWRpYVJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS92aW1lb190ZXN0LmpzJywgWydnb29nLnVpLm1lZGlhLlZpbWVvVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuTWVkaWEnLCAnZ29vZy51aS5tZWRpYS5WaW1lbycsICdnb29nLnVpLm1lZGlhLlZpbWVvTW9kZWwnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZWRpYS95b3V0dWJlLmpzJywgWydnb29nLnVpLm1lZGlhLllvdXR1YmUnLCAnZ29vZy51aS5tZWRpYS5Zb3V0dWJlTW9kZWwnXSwgWydnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaHRtbC5UcnVzdGVkUmVzb3VyY2VVcmwnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJpbmcuQ29uc3QnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5tZWRpYS5GbGFzaE9iamVjdCcsICdnb29nLnVpLm1lZGlhLk1lZGlhJywgJ2dvb2cudWkubWVkaWEuTWVkaWFNb2RlbCcsICdnb29nLnVpLm1lZGlhLk1lZGlhUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lZGlhL3lvdXR1YmVfdGVzdC5qcycsIFsnZ29vZy51aS5tZWRpYS5Zb3V0dWJlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLm1lZGlhLkZsYXNoT2JqZWN0JywgJ2dvb2cudWkubWVkaWEuWW91dHViZScsICdnb29nLnVpLm1lZGlhLllvdXR1YmVNb2RlbCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnUuanMnLCBbJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnUuRXZlbnRUeXBlJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50LkV2ZW50VHlwZScsICdnb29nLnVpLkNvbXBvbmVudC5TdGF0ZScsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLkNvbnRhaW5lci5PcmllbnRhdGlvbicsICdnb29nLnVpLk1lbnVIZWFkZXInLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLk1lbnVSZW5kZXJlcicsICdnb29nLnVpLk1lbnVTZXBhcmF0b3InXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVfdGVzdC5qcycsIFsnZ29vZy51aS5NZW51VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLk1lbnUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51YmFyLmpzJywgWydnb29nLnVpLm1lbnVCYXInXSwgWydnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLk1lbnVCYXJSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVudWJhcmRlY29yYXRvci5qcycsIFsnZ29vZy51aS5tZW51QmFyRGVjb3JhdG9yJ10sIFsnZ29vZy51aS5NZW51QmFyUmVuZGVyZXInLCAnZ29vZy51aS5tZW51QmFyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnViYXJyZW5kZXJlci5qcycsIFsnZ29vZy51aS5NZW51QmFyUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cudWkuQ29udGFpbmVyJywgJ2dvb2cudWkuQ29udGFpbmVyUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnViYXNlLmpzJywgWydnb29nLnVpLk1lbnVCYXNlJ10sIFsnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cudWkuUG9wdXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVidXR0b24uanMnLCBbJ2dvb2cudWkuTWVudUJ1dHRvbiddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5tYXRoLlJlY3QnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk1lbnVBbmNob3JlZFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3cnLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkJ1dHRvbicsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLklkR2VuZXJhdG9yJywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLk1lbnVJdGVtJywgJ2dvb2cudWkuTWVudVJlbmRlcmVyJywgJ2dvb2cudWkuU3ViTWVudScsICdnb29nLnVpLnJlZ2lzdHJ5JywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51YnV0dG9uX3Rlc3QuanMnLCBbJ2dvb2cudWkuTWVudUJ1dHRvblRlc3QnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLktleUhhbmRsZXInLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnBvc2l0aW9uaW5nLk1lbnVBbmNob3JlZFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuT3ZlcmZsb3cnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnVCdXR0b24nLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLlN1Yk1lbnUnLCAnZ29vZy51c2VyQWdlbnQnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0LmlzVmVyc2lvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5NZW51QnV0dG9uUmVuZGVyZXInXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5DdXN0b21CdXR0b25SZW5kZXJlcicsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudVJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51YnV0dG9ucmVuZGVyZXJfdGVzdC5qcycsIFsnZ29vZy51aS5NZW51QnV0dG9uUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuTWVudUJ1dHRvbicsICdnb29nLnVpLk1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVoZWFkZXIuanMnLCBbJ2dvb2cudWkuTWVudUhlYWRlciddLCBbJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udHJvbCcsICdnb29nLnVpLk1lbnVIZWFkZXJSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51aGVhZGVycmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuTWVudUhlYWRlclJlbmRlcmVyJ10sIFsnZ29vZy51aS5Db250cm9sUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVpdGVtLmpzJywgWydnb29nLnVpLk1lbnVJdGVtJ10sIFsnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0cmluZycsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5NZW51SXRlbVJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21lbnVpdGVtX3Rlc3QuanMnLCBbJ2dvb2cudWkuTWVudUl0ZW1UZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cubWF0aC5Db29yZGluYXRlJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLk1lbnVJdGVtUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51aXRlbXJlbmRlcmVyLmpzJywgWydnb29nLnVpLk1lbnVJdGVtUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVudWl0ZW1yZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLk1lbnVJdGVtUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5NZW51SXRlbVJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVudXJlbmRlcmVyLmpzJywgWydnb29nLnVpLk1lbnVSZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy51aS5Db250YWluZXJSZW5kZXJlcicsICdnb29nLnVpLlNlcGFyYXRvciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVudXNlcGFyYXRvci5qcycsIFsnZ29vZy51aS5NZW51U2VwYXJhdG9yJ10sIFsnZ29vZy51aS5NZW51U2VwYXJhdG9yUmVuZGVyZXInLCAnZ29vZy51aS5TZXBhcmF0b3InLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbWVudXNlcGFyYXRvcnJlbmRlcmVyLmpzJywgWydnb29nLnVpLk1lbnVTZXBhcmF0b3JSZW5kZXJlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tZW51c2VwYXJhdG9ycmVuZGVyZXJfdGVzdC5qcycsIFsnZ29vZy51aS5NZW51U2VwYXJhdG9yUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLk1lbnVTZXBhcmF0b3InLCAnZ29vZy51aS5NZW51U2VwYXJhdG9yUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tb2NrYWN0aXZpdHltb25pdG9yLmpzJywgWydnb29nLnVpLk1vY2tBY3Rpdml0eU1vbml0b3InXSwgWydnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy51aS5BY3Rpdml0eU1vbml0b3InXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21vY2thY3Rpdml0eW1vbml0b3JfdGVzdC5qcycsIFsnZ29vZy51aS5Nb2NrQWN0aXZpdHlNb25pdG9yVGVzdCddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQWN0aXZpdHlNb25pdG9yJywgJ2dvb2cudWkuTW9ja0FjdGl2aXR5TW9uaXRvciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21vZGFsYXJpYXZpc2liaWxpdHloZWxwZXIuanMnLCBbJ2dvb2cudWkuTW9kYWxBcmlhVmlzaWJpbGl0eUhlbHBlciddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9tb2RhbGFyaWF2aXNpYmlsaXR5aGVscGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuTW9kYWxBcmlhVmlzaWJpbGl0eUhlbHBlclRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLnN0cmluZycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuTW9kYWxBcmlhVmlzaWJpbGl0eUhlbHBlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL21vZGFscG9wdXAuanMnLCBbJ2dvb2cudWkuTW9kYWxQb3B1cCddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uYW5pbWF0aW9uRnJhbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZG9tLmlmcmFtZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuRm9jdXNIYW5kbGVyJywgJ2dvb2cuZnguVHJhbnNpdGlvbicsICdnb29nLnN0cmluZycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuTW9kYWxBcmlhVmlzaWJpbGl0eUhlbHBlcicsICdnb29nLnVpLlBvcHVwQmFzZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvbW9kYWxwb3B1cF90ZXN0LmpzJywgWydnb29nLnVpLk1vZGFsUG9wdXBUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kaXNwb3NlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZnguVHJhbnNpdGlvbicsICdnb29nLmZ4LmNzczMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLk1vZGFsUG9wdXAnLCAnZ29vZy51aS5Qb3B1cEJhc2UnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9uYXRpdmVidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5OYXRpdmVCdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5JbnB1dFR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cudWkuQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL25hdGl2ZWJ1dHRvbnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuTmF0aXZlQnV0dG9uUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLkV4cGVjdGVkRmFpbHVyZXMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnLCAnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5OYXRpdmVCdXR0b25SZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL29wdGlvbi5qcycsIFsnZ29vZy51aS5PcHRpb24nXSwgWydnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLk1lbnVJdGVtJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BhbGV0dGUuanMnLCBbJ2dvb2cudWkuUGFsZXR0ZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubWF0aC5TaXplJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udHJvbCcsICdnb29nLnVpLlBhbGV0dGVSZW5kZXJlcicsICdnb29nLnVpLlNlbGVjdGlvbk1vZGVsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9wYWxldHRlX3Rlc3QuanMnLCBbJ2dvb2cudWkuUGFsZXR0ZVRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5ldmVudHMuS2V5RXZlbnQnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cy5FdmVudCcsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLlBhbGV0dGUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9wYWxldHRlcmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuUGFsZXR0ZVJlbmRlcmVyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5Ob2RlSXRlcmF0b3InLCAnZ29vZy5kb20uTm9kZVR5cGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5kb20uZGF0YXNldCcsICdnb29nLml0ZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcGFsZXR0ZXJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuUGFsZXR0ZVJlbmRlcmVyVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuaHRtbC50ZXN0aW5nJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5QYWxldHRlJywgJ2dvb2cudWkuUGFsZXR0ZVJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcGxhaW50ZXh0c3BlbGxjaGVja2VyLmpzJywgWydnb29nLnVpLlBsYWluVGV4dFNwZWxsQ2hlY2tlciddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuc3BlbGwuU3BlbGxDaGVjaycsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQWJzdHJhY3RTcGVsbENoZWNrZXInLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BsYWludGV4dHNwZWxsY2hlY2tlcl90ZXN0LmpzJywgWydnb29nLnVpLlBsYWluVGV4dFNwZWxsQ2hlY2tlclRlc3QnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuc3BlbGwuU3BlbGxDaGVjaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5BYnN0cmFjdFNwZWxsQ2hlY2tlcicsICdnb29nLnVpLlBsYWluVGV4dFNwZWxsQ2hlY2tlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BvcHVwLmpzJywgWydnb29nLnVpLlBvcHVwJ10sIFsnZ29vZy5tYXRoLkJveCcsICdnb29nLnBvc2l0aW9uaW5nLkFic3RyYWN0UG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcG9wdXBfdGVzdC5qcycsIFsnZ29vZy51aS5Qb3B1cFRlc3QnXSwgWydnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuUG9wdXAnLCAnZ29vZy51c2VyQWdlbnQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9wb3B1cGJhc2UuanMnLCBbJ2dvb2cudWkuUG9wdXBCYXNlJywgJ2dvb2cudWkuUG9wdXBCYXNlLkV2ZW50VHlwZScsICdnb29nLnVpLlBvcHVwQmFzZS5UeXBlJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFycmF5JywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmZ4LlRyYW5zaXRpb24nLCAnZ29vZy5zdHlsZScsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcG9wdXBiYXNlX3Rlc3QuanMnLCBbJ2dvb2cudWkuUG9wdXBCYXNlVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZnguVHJhbnNpdGlvbicsICdnb29nLmZ4LmNzczMnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BvcHVwY29sb3JwaWNrZXIuanMnLCBbJ2dvb2cudWkuUG9wdXBDb2xvclBpY2tlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRQb3NpdGlvbicsICdnb29nLnBvc2l0aW9uaW5nLkNvcm5lcicsICdnb29nLnVpLkNvbG9yUGlja2VyJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuUG9wdXAnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BvcHVwY29sb3JwaWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5Qb3B1cENvbG9yUGlja2VyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbG9yUGlja2VyJywgJ2dvb2cudWkuUG9wdXBDb2xvclBpY2tlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3BvcHVwZGF0ZXBpY2tlci5qcycsIFsnZ29vZy51aS5Qb3B1cERhdGVQaWNrZXInXSwgWydnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5wb3NpdGlvbmluZy5BbmNob3JlZFZpZXdwb3J0UG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkRhdGVQaWNrZXInLCAnZ29vZy51aS5Qb3B1cCcsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcG9wdXBkYXRlcGlja2VyX3Rlc3QuanMnLCBbJ2dvb2cudWkuUG9wdXBEYXRlUGlja2VyVGVzdCddLCBbJ2dvb2cuZGF0ZS5EYXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLnJlY29yZEZ1bmN0aW9uJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5EYXRlUGlja2VyJywgJ2dvb2cudWkuUG9wdXBCYXNlJywgJ2dvb2cudWkuUG9wdXBEYXRlUGlja2VyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcG9wdXBtZW51LmpzJywgWydnb29nLnVpLlBvcHVwTWVudSddLCBbJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5Ccm93c2VyRXZlbnQuTW91c2VCdXR0b24nLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRWaWV3cG9ydFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cucG9zaXRpb25pbmcuTWVudUFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5PdmVyZmxvdycsICdnb29nLnBvc2l0aW9uaW5nLlZpZXdwb3J0Q2xpZW50UG9zaXRpb24nLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcG9wdXBtZW51X3Rlc3QuanMnLCBbJ2dvb2cudWkuUG9wdXBNZW51VGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkJyb3dzZXJFdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5Qb3B1cE1lbnUnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9wcm9ncmVzc2Jhci5qcycsIFsnZ29vZy51aS5Qcm9ncmVzc0JhcicsICdnb29nLnVpLlByb2dyZXNzQmFyLk9yaWVudGF0aW9uJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLlJhbmdlTW9kZWwnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Byb21wdC5qcycsIFsnZ29vZy51aS5Qcm9tcHQnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLklucHV0VHlwZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmZ1bmN0aW9ucycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5EaWFsb2cnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Byb21wdF90ZXN0LmpzJywgWydnb29nLnVpLlByb21wdFRlc3QnXSwgWydnb29nLmRvbS5zZWxlY3Rpb24nLCAnZ29vZy5ldmVudHMuSW5wdXRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkJpZGlJbnB1dCcsICdnb29nLnVpLkRpYWxvZycsICdnb29nLnVpLlByb21wdCcsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcmFuZ2Vtb2RlbC5qcycsIFsnZ29vZy51aS5SYW5nZU1vZGVsJ10sIFsnZ29vZy5ldmVudHMuRXZlbnRUYXJnZXQnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3JhbmdlbW9kZWxfdGVzdC5qcycsIFsnZ29vZy51aS5SYW5nZU1vZGVsVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5SYW5nZU1vZGVsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcmF0aW5ncy5qcycsIFsnZ29vZy51aS5SYXRpbmdzJywgJ2dvb2cudWkuUmF0aW5ncy5FdmVudFR5cGUnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3JlZ2lzdHJ5LmpzJywgWydnb29nLnVpLnJlZ2lzdHJ5J10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcmVnaXN0cnlfdGVzdC5qcycsIFsnZ29vZy51aS5yZWdpc3RyeVRlc3QnXSwgWydnb29nLm9iamVjdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkucmVnaXN0cnknXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9yaWNodGV4dHNwZWxsY2hlY2tlci5qcycsIFsnZ29vZy51aS5SaWNoVGV4dFNwZWxsQ2hlY2tlciddLCBbJ2dvb2cuVGltZXInLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLk5vZGVUeXBlJywgJ2dvb2cuZG9tLlJhbmdlJywgJ2dvb2cuZXZlbnRzLkV2ZW50SGFuZGxlcicsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5ldmVudHMuS2V5SGFuZGxlcicsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnNwZWxsLlNwZWxsQ2hlY2snLCAnZ29vZy5zdHJpbmcuU3RyaW5nQnVmZmVyJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5BYnN0cmFjdFNwZWxsQ2hlY2tlcicsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLlBvcHVwTWVudSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcmljaHRleHRzcGVsbGNoZWNrZXJfdGVzdC5qcycsIFsnZ29vZy51aS5SaWNoVGV4dFNwZWxsQ2hlY2tlclRlc3QnXSwgWydnb29nLmRvbS5SYW5nZScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLm9iamVjdCcsICdnb29nLnNwZWxsLlNwZWxsQ2hlY2snLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5SaWNoVGV4dFNwZWxsQ2hlY2tlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3JvdW5kZWRwYW5lbC5qcycsIFsnZ29vZy51aS5CYXNlUm91bmRlZFBhbmVsJywgJ2dvb2cudWkuQ3NzUm91bmRlZFBhbmVsJywgJ2dvb2cudWkuR3JhcGhpY3NSb3VuZGVkUGFuZWwnLCAnZ29vZy51aS5Sb3VuZGVkUGFuZWwnLCAnZ29vZy51aS5Sb3VuZGVkUGFuZWwuQ29ybmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZ3JhcGhpY3MnLCAnZ29vZy5ncmFwaGljcy5QYXRoJywgJ2dvb2cuZ3JhcGhpY3MuU29saWRGaWxsJywgJ2dvb2cuZ3JhcGhpY3MuU3Ryb2tlJywgJ2dvb2cubWF0aCcsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9yb3VuZGVkcGFuZWxfdGVzdC5qcycsIFsnZ29vZy51aS5Sb3VuZGVkUGFuZWxUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNzc1JvdW5kZWRQYW5lbCcsICdnb29nLnVpLkdyYXBoaWNzUm91bmRlZFBhbmVsJywgJ2dvb2cudWkuUm91bmRlZFBhbmVsJywgJ2dvb2cudXNlckFnZW50J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvcm91bmRlZHRhYnJlbmRlcmVyLmpzJywgWydnb29nLnVpLlJvdW5kZWRUYWJSZW5kZXJlciddLCBbJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy51aS5UYWInLCAnZ29vZy51aS5UYWJCYXInLCAnZ29vZy51aS5UYWJSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zY3JvbGxmbG9hdGVyLmpzJywgWydnb29nLnVpLlNjcm9sbEZsb2F0ZXInLCAnZ29vZy51aS5TY3JvbGxGbG9hdGVyLkV2ZW50VHlwZSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zY3JvbGxmbG9hdGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuU2Nyb2xsRmxvYXRlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLnN0eWxlJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5TY3JvbGxGbG9hdGVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc2VsZWN0LmpzJywgWydnb29nLnVpLlNlbGVjdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5hcnJheScsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5JZEdlbmVyYXRvcicsICdnb29nLnVpLk1lbnVCdXR0b24nLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLk1lbnVSZW5kZXJlcicsICdnb29nLnVpLlNlbGVjdGlvbk1vZGVsJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3NlbGVjdF90ZXN0LmpzJywgWydnb29nLnVpLlNlbGVjdFRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ3VzdG9tQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5TZWxlY3QnLCAnZ29vZy51aS5TZXBhcmF0b3InXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zZWxlY3Rpb25tZW51YnV0dG9uLmpzJywgWydnb29nLnVpLlNlbGVjdGlvbk1lbnVCdXR0b24nLCAnZ29vZy51aS5TZWxlY3Rpb25NZW51QnV0dG9uLlNlbGVjdGlvblN0YXRlJ10sIFsnZ29vZy5kb20uSW5wdXRUeXBlJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51QnV0dG9uJywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc2VsZWN0aW9ubWVudWJ1dHRvbl90ZXN0LmpzJywgWydnb29nLnVpLlNlbGVjdGlvbk1lbnVCdXR0b25UZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuU2VsZWN0aW9uTWVudUJ1dHRvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3NlbGVjdGlvbm1vZGVsLmpzJywgWydnb29nLnVpLlNlbGVjdGlvbk1vZGVsJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3NlbGVjdGlvbm1vZGVsX3Rlc3QuanMnLCBbJ2dvb2cudWkuU2VsZWN0aW9uTW9kZWxUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLnRlc3RpbmcucmVjb3JkRnVuY3Rpb24nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLlNlbGVjdGlvbk1vZGVsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc2VwYXJhdG9yLmpzJywgWydnb29nLnVpLlNlcGFyYXRvciddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5NZW51U2VwYXJhdG9yUmVuZGVyZXInLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc2VydmVyY2hhcnQuanMnLCBbJ2dvb2cudWkuU2VydmVyQ2hhcnQnLCAnZ29vZy51aS5TZXJ2ZXJDaGFydC5BeGlzRGlzcGxheVR5cGUnLCAnZ29vZy51aS5TZXJ2ZXJDaGFydC5DaGFydFR5cGUnLCAnZ29vZy51aS5TZXJ2ZXJDaGFydC5FbmNvZGluZ1R5cGUnLCAnZ29vZy51aS5TZXJ2ZXJDaGFydC5FdmVudCcsICdnb29nLnVpLlNlcnZlckNoYXJ0LkxlZ2VuZFBvc2l0aW9uJywgJ2dvb2cudWkuU2VydmVyQ2hhcnQuTWF4aW11bVZhbHVlJywgJ2dvb2cudWkuU2VydmVyQ2hhcnQuTXVsdGlBeGlzQWxpZ25tZW50JywgJ2dvb2cudWkuU2VydmVyQ2hhcnQuTXVsdGlBeGlzVHlwZScsICdnb29nLnVpLlNlcnZlckNoYXJ0LlVyaVBhcmFtJywgJ2dvb2cudWkuU2VydmVyQ2hhcnQuVXJpVG9vTG9uZ0V2ZW50J10sIFsnZ29vZy5VcmknLCAnZ29vZy5hcnJheScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudWkuQ29tcG9uZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zZXJ2ZXJjaGFydF90ZXN0LmpzJywgWydnb29nLnVpLlNlcnZlckNoYXJ0VGVzdCddLCBbJ2dvb2cuVXJpJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5TZXJ2ZXJDaGFydCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3NsaWRlci5qcycsIFsnZ29vZy51aS5TbGlkZXInLCAnZ29vZy51aS5TbGlkZXIuT3JpZW50YXRpb24nXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy51aS5TbGlkZXJCYXNlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zbGlkZXJiYXNlLmpzJywgWydnb29nLnVpLlNsaWRlckJhc2UnLCAnZ29vZy51aS5TbGlkZXJCYXNlLkFuaW1hdGlvbkZhY3RvcnknLCAnZ29vZy51aS5TbGlkZXJCYXNlLk9yaWVudGF0aW9uJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLk1vdXNlV2hlZWxIYW5kbGVyJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuZnguQW5pbWF0aW9uUGFyYWxsZWxRdWV1ZScsICdnb29nLmZ4LkRyYWdnZXInLCAnZ29vZy5meC5UcmFuc2l0aW9uJywgJ2dvb2cuZnguZG9tLlJlc2l6ZUhlaWdodCcsICdnb29nLmZ4LmRvbS5SZXNpemVXaWR0aCcsICdnb29nLmZ4LmRvbS5TbGlkZScsICdnb29nLm1hdGgnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLmJpZGknLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5SYW5nZU1vZGVsJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zbGlkZXJiYXNlX3Rlc3QuanMnLCBbJ2dvb2cudWkuU2xpZGVyQmFzZVRlc3QnXSwgWydnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5meC5BbmltYXRpb24nLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5zdHlsZScsICdnb29nLnN0eWxlLmJpZGknLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuTW9ja0NvbnRyb2wnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcubW9ja21hdGNoZXJzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuU2xpZGVyQmFzZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3NwbGl0cGFuZS5qcycsIFsnZ29vZy51aS5TcGxpdFBhbmUnLCAnZ29vZy51aS5TcGxpdFBhbmUuT3JpZW50YXRpb24nXSwgWydnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZnguRHJhZ2dlcicsICdnb29nLm1hdGguUmVjdCcsICdnb29nLm1hdGguU2l6ZScsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zcGxpdHBhbmVfdGVzdC5qcycsIFsnZ29vZy51aS5TcGxpdFBhbmVUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5tYXRoLlNpemUnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5yZWNvcmRGdW5jdGlvbicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuU3BsaXRQYW5lJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3R5bGUvYXBwL2J1dHRvbnJlbmRlcmVyLmpzJywgWydnb29nLnVpLnN0eWxlLmFwcC5CdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQ3VzdG9tQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5JTkxJTkVfQkxPQ0tfQ0xBU1NOQU1FJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3N0eWxlL2FwcC9idXR0b25yZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLnN0eWxlLmFwcC5CdXR0b25SZW5kZXJlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5zdHlsZScsICdnb29nLnVpLkJ1dHRvbicsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLnN0eWxlLmFwcC5CdXR0b25SZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3N0eWxlL2FwcC9tZW51YnV0dG9ucmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuc3R5bGUuYXBwLk1lbnVCdXR0b25SZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudVJlbmRlcmVyJywgJ2dvb2cudWkuc3R5bGUuYXBwLkJ1dHRvblJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS9zdHlsZS9hcHAvbWVudWJ1dHRvbnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuc3R5bGUuYXBwLk1lbnVCdXR0b25SZW5kZXJlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLk1lbnVCdXR0b24nLCAnZ29vZy51aS5zdHlsZS5hcHAuTWVudUJ1dHRvblJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3R5bGUvYXBwL3ByaW1hcnlhY3Rpb25idXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5zdHlsZS5hcHAuUHJpbWFyeUFjdGlvbkJ1dHRvblJlbmRlcmVyJ10sIFsnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5yZWdpc3RyeScsICdnb29nLnVpLnN0eWxlLmFwcC5CdXR0b25SZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3R5bGUvYXBwL3ByaW1hcnlhY3Rpb25idXR0b25yZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLnN0eWxlLmFwcC5QcmltYXJ5QWN0aW9uQnV0dG9uUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkuc3R5bGUnLCAnZ29vZy51aS5CdXR0b24nLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5zdHlsZS5hcHAuUHJpbWFyeUFjdGlvbkJ1dHRvblJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3VibWVudS5qcycsIFsnZ29vZy51aS5TdWJNZW51J10sIFsnZ29vZy5UaW1lcicsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cucG9zaXRpb25pbmcuQW5jaG9yZWRWaWV3cG9ydFBvc2l0aW9uJywgJ2dvb2cucG9zaXRpb25pbmcuQ29ybmVyJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5TdWJNZW51UmVuZGVyZXInLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3VibWVudV90ZXN0LmpzJywgWydnb29nLnVpLlN1Yk1lbnVUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuU3RhdGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cuZXZlbnRzLktleUNvZGVzJywgJ2dvb2cuZXZlbnRzLktleUhhbmRsZXInLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy50ZXN0aW5nLk1vY2tDbG9jaycsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51JywgJ2dvb2cudWkuTWVudUl0ZW0nLCAnZ29vZy51aS5TdWJNZW51JywgJ2dvb2cudWkuU3ViTWVudVJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvc3VibWVudXJlbmRlcmVyLmpzJywgWydnb29nLnVpLlN1Yk1lbnVSZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYTExeS5hcmlhLlN0YXRlJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnN0eWxlJywgJ2dvb2cudWkuTWVudScsICdnb29nLnVpLk1lbnVJdGVtUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3N5bnRoZXRpY2tleWJvYXJkZXZlbnQuanMnLCBbJ2dvb2cudWkuU3ludGhldGljS2V5Ym9hcmRFdmVudCddLCBbJ2dvb2cuZXZlbnRzLkV2ZW50JywgJ2dvb2cudWkuS2V5Ym9hcmRFdmVudERhdGEnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYi5qcycsIFsnZ29vZy51aS5UYWInXSwgWydnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2wnLCAnZ29vZy51aS5UYWJSZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90YWJfdGVzdC5qcycsIFsnZ29vZy51aS5UYWJUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLlRhYicsICdnb29nLnVpLlRhYlJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdGFiYmFyLmpzJywgWydnb29nLnVpLlRhYkJhcicsICdnb29nLnVpLlRhYkJhci5Mb2NhdGlvbiddLCBbJ2dvb2cudWkuQ29tcG9uZW50LkV2ZW50VHlwZScsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLkNvbnRhaW5lci5PcmllbnRhdGlvbicsICdnb29nLnVpLlRhYicsICdnb29nLnVpLlRhYkJhclJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYmJhcl90ZXN0LmpzJywgWydnb29nLnVpLlRhYkJhclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLlRhYicsICdnb29nLnVpLlRhYkJhcicsICdnb29nLnVpLlRhYkJhclJlbmRlcmVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdGFiYmFycmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuVGFiQmFyUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudWkuQ29udGFpbmVyUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYmJhcnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuVGFiQmFyUmVuZGVyZXJUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudGVzdGluZy51aS5yZW5kZXJlcmFzc2VydHMnLCAnZ29vZy51aS5Db250YWluZXInLCAnZ29vZy51aS5UYWJCYXInLCAnZ29vZy51aS5UYWJCYXJSZW5kZXJlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYmxlc29ydGVyLmpzJywgWydnb29nLnVpLlRhYmxlU29ydGVyJywgJ2dvb2cudWkuVGFibGVTb3J0ZXIuRXZlbnRUeXBlJ10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy51aS5Db21wb25lbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYmxlc29ydGVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuVGFibGVTb3J0ZXJUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5UYWJsZVNvcnRlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYnBhbmUuanMnLCBbJ2dvb2cudWkuVGFiUGFuZScsICdnb29nLnVpLlRhYlBhbmUuRXZlbnRzJywgJ2dvb2cudWkuVGFiUGFuZS5UYWJMb2NhdGlvbicsICdnb29nLnVpLlRhYlBhbmUuVGFiUGFnZScsICdnb29nLnVpLlRhYlBhbmVFdmVudCddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudFRhcmdldCcsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5odG1sLlNhZmVTdHlsZVNoZWV0JywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RhYnBhbmVfdGVzdC5qcycsIFsnZ29vZy51aS5UYWJQYW5lVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS5UYWJQYW5lJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdGFicmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuVGFiUmVuZGVyZXInXSwgWydnb29nLmExMXkuYXJpYS5Sb2xlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ29udHJvbFJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90YWJyZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLlRhYlJlbmRlcmVyVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uY2xhc3NsaXN0JywgJ2dvb2cudGVzdGluZy5kb20nLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuVGFiJywgJ2dvb2cudWkuVGFiUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90ZXh0YXJlYS5qcycsIFsnZ29vZy51aS5UZXh0YXJlYScsICdnb29nLnVpLlRleHRhcmVhLkV2ZW50VHlwZSddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Db250cm9sJywgJ2dvb2cudWkuVGV4dGFyZWFSZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdGV4dGFyZWFfdGVzdC5qcycsIFsnZ29vZy51aS5UZXh0YXJlYVRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuRXhwZWN0ZWRGYWlsdXJlcycsICdnb29nLnRlc3RpbmcuZXZlbnRzLkV2ZW50T2JzZXJ2ZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLlRleHRhcmVhJywgJ2dvb2cudWkuVGV4dGFyZWFSZW5kZXJlcicsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdGV4dGFyZWFyZW5kZXJlci5qcycsIFsnZ29vZy51aS5UZXh0YXJlYVJlbmRlcmVyJ10sIFsnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLkNvbnRyb2xSZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9nZ2xlYnV0dG9uLmpzJywgWydnb29nLnVpLlRvZ2dsZUJ1dHRvbiddLCBbJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuQ3VzdG9tQnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbGJhci5qcycsIFsnZ29vZy51aS5Ub29sYmFyJ10sIFsnZ29vZy51aS5Db250YWluZXInLCAnZ29vZy51aS5Ub29sYmFyUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Rvb2xiYXJfdGVzdC5qcycsIFsnZ29vZy51aS5Ub29sYmFyVGVzdCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuZG9tJywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLnRlc3RpbmcuZXZlbnRzJywgJ2dvb2cudGVzdGluZy5ldmVudHMuRXZlbnQnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLlRvb2xiYXInLCAnZ29vZy51aS5Ub29sYmFyTWVudUJ1dHRvbiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Rvb2xiYXJidXR0b24uanMnLCBbJ2dvb2cudWkuVG9vbGJhckJ1dHRvbiddLCBbJ2dvb2cudWkuQnV0dG9uJywgJ2dvb2cudWkuVG9vbGJhckJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkucmVnaXN0cnknXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Rvb2xiYXJidXR0b25yZW5kZXJlci5qcycsIFsnZ29vZy51aS5Ub29sYmFyQnV0dG9uUmVuZGVyZXInXSwgWydnb29nLnVpLkN1c3RvbUJ1dHRvblJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sYmFyY29sb3JtZW51YnV0dG9uLmpzJywgWydnb29nLnVpLlRvb2xiYXJDb2xvck1lbnVCdXR0b24nXSwgWydnb29nLnVpLkNvbG9yTWVudUJ1dHRvbicsICdnb29nLnVpLlRvb2xiYXJDb2xvck1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sYmFyY29sb3JtZW51YnV0dG9ucmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuVG9vbGJhckNvbG9yTWVudUJ1dHRvblJlbmRlcmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLkNvbG9yTWVudUJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkuTWVudUJ1dHRvblJlbmRlcmVyJywgJ2dvb2cudWkuVG9vbGJhck1lbnVCdXR0b25SZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbGJhcmNvbG9ybWVudWJ1dHRvbnJlbmRlcmVyX3Rlc3QuanMnLCBbJ2dvb2cudWkuVG9vbGJhckNvbG9yTWVudUJ1dHRvblJlbmRlcmVyVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy50ZXN0aW5nLnVpLlJlbmRlcmVySGFybmVzcycsICdnb29nLnRlc3RpbmcudWkucmVuZGVyZXJhc3NlcnRzJywgJ2dvb2cudWkuVG9vbGJhckNvbG9yTWVudUJ1dHRvbicsICdnb29nLnVpLlRvb2xiYXJDb2xvck1lbnVCdXR0b25SZW5kZXJlciddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Rvb2xiYXJtZW51YnV0dG9uLmpzJywgWydnb29nLnVpLlRvb2xiYXJNZW51QnV0dG9uJ10sIFsnZ29vZy51aS5NZW51QnV0dG9uJywgJ2dvb2cudWkuVG9vbGJhck1lbnVCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sYmFybWVudWJ1dHRvbnJlbmRlcmVyLmpzJywgWydnb29nLnVpLlRvb2xiYXJNZW51QnV0dG9uUmVuZGVyZXInXSwgWydnb29nLnVpLk1lbnVCdXR0b25SZW5kZXJlciddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbGJhcnJlbmRlcmVyLmpzJywgWydnb29nLnVpLlRvb2xiYXJSZW5kZXJlciddLCBbJ2dvb2cuYTExeS5hcmlhLlJvbGUnLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLnVpLkNvbnRhaW5lcicsICdnb29nLnVpLkNvbnRhaW5lclJlbmRlcmVyJywgJ2dvb2cudWkuU2VwYXJhdG9yJywgJ2dvb2cudWkuVG9vbGJhclNlcGFyYXRvclJlbmRlcmVyJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sYmFyc2VsZWN0LmpzJywgWydnb29nLnVpLlRvb2xiYXJTZWxlY3QnXSwgWydnb29nLnVpLlNlbGVjdCcsICdnb29nLnVpLlRvb2xiYXJNZW51QnV0dG9uUmVuZGVyZXInLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbGJhcnNlcGFyYXRvci5qcycsIFsnZ29vZy51aS5Ub29sYmFyU2VwYXJhdG9yJ10sIFsnZ29vZy51aS5TZXBhcmF0b3InLCAnZ29vZy51aS5Ub29sYmFyU2VwYXJhdG9yUmVuZGVyZXInLCAnZ29vZy51aS5yZWdpc3RyeSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbGJhcnNlcGFyYXRvcnJlbmRlcmVyLmpzJywgWydnb29nLnVpLlRvb2xiYXJTZXBhcmF0b3JSZW5kZXJlciddLCBbJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLklOTElORV9CTE9DS19DTEFTU05BTUUnLCAnZ29vZy51aS5NZW51U2VwYXJhdG9yUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3Rvb2xiYXJzZXBhcmF0b3JyZW5kZXJlcl90ZXN0LmpzJywgWydnb29nLnVpLlRvb2xiYXJTZXBhcmF0b3JSZW5kZXJlclRlc3QnXSwgWydnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuQ29tcG9uZW50JywgJ2dvb2cudWkuSU5MSU5FX0JMT0NLX0NMQVNTTkFNRScsICdnb29nLnVpLlRvb2xiYXJTZXBhcmF0b3InLCAnZ29vZy51aS5Ub29sYmFyU2VwYXJhdG9yUmVuZGVyZXInXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sYmFydG9nZ2xlYnV0dG9uLmpzJywgWydnb29nLnVpLlRvb2xiYXJUb2dnbGVCdXR0b24nXSwgWydnb29nLnVpLlRvZ2dsZUJ1dHRvbicsICdnb29nLnVpLlRvb2xiYXJCdXR0b25SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90b29sdGlwLmpzJywgWydnb29nLnVpLlRvb2x0aXAnLCAnZ29vZy51aS5Ub29sdGlwLkN1cnNvclRvb2x0aXBQb3NpdGlvbicsICdnb29nLnVpLlRvb2x0aXAuRWxlbWVudFRvb2x0aXBQb3NpdGlvbicsICdnb29nLnVpLlRvb2x0aXAuU3RhdGUnXSwgWydnb29nLlRpbWVyJywgJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tJywgJ2dvb2cuZG9tLlRhZ05hbWUnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cycsICdnb29nLmV2ZW50cy5FdmVudFR5cGUnLCAnZ29vZy5ldmVudHMuRm9jdXNIYW5kbGVyJywgJ2dvb2cubWF0aC5Cb3gnLCAnZ29vZy5tYXRoLkNvb3JkaW5hdGUnLCAnZ29vZy5wb3NpdGlvbmluZycsICdnb29nLnBvc2l0aW9uaW5nLkFuY2hvcmVkUG9zaXRpb24nLCAnZ29vZy5wb3NpdGlvbmluZy5Db3JuZXInLCAnZ29vZy5wb3NpdGlvbmluZy5PdmVyZmxvdycsICdnb29nLnBvc2l0aW9uaW5nLk92ZXJmbG93U3RhdHVzJywgJ2dvb2cucG9zaXRpb25pbmcuVmlld3BvcnRQb3NpdGlvbicsICdnb29nLnN0cnVjdHMuU2V0JywgJ2dvb2cuc3R5bGUnLCAnZ29vZy51aS5Qb3B1cCcsICdnb29nLnVpLlBvcHVwQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdG9vbHRpcF90ZXN0LmpzJywgWydnb29nLnVpLlRvb2x0aXBUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5FdmVudEhhbmRsZXInLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLkZvY3VzSGFuZGxlcicsICdnb29nLmh0bWwudGVzdGluZycsICdnb29nLm1hdGguQ29vcmRpbmF0ZScsICdnb29nLnBvc2l0aW9uaW5nLkFic29sdXRlUG9zaXRpb24nLCAnZ29vZy5zdHlsZScsICdnb29nLnRlc3RpbmcuTW9ja0Nsb2NrJywgJ2dvb2cudGVzdGluZy5UZXN0UXVldWUnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuUG9wdXBCYXNlJywgJ2dvb2cudWkuVG9vbHRpcCcsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RyZWUvYmFzZW5vZGUuanMnLCBbJ2dvb2cudWkudHJlZS5CYXNlTm9kZScsICdnb29nLnVpLnRyZWUuQmFzZU5vZGUuRXZlbnRUeXBlJ10sIFsnZ29vZy5UaW1lcicsICdnb29nLmExMXkuYXJpYScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmFzc2VydHMnLCAnZ29vZy5kb20uc2FmZScsICdnb29nLmV2ZW50cy5FdmVudCcsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmh0bWwuU2FmZUh0bWwnLCAnZ29vZy5odG1sLlNhZmVTdHlsZScsICdnb29nLnN0cmluZycsICdnb29nLnN0cmluZy5TdHJpbmdCdWZmZXInLCAnZ29vZy5zdHlsZScsICdnb29nLnVpLkNvbXBvbmVudCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdHJlZS9iYXNlbm9kZV90ZXN0LmpzJywgWydnb29nLnVpLnRyZWUuQmFzZU5vZGVUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5odG1sLnRlc3RpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLkNvbXBvbmVudCcsICdnb29nLnVpLnRyZWUuQmFzZU5vZGUnLCAnZ29vZy51aS50cmVlLlRyZWVDb250cm9sJywgJ2dvb2cudWkudHJlZS5UcmVlTm9kZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RyZWUvdHJlZWNvbnRyb2wuanMnLCBbJ2dvb2cudWkudHJlZS5UcmVlQ29udHJvbCddLCBbJ2dvb2cuYTExeS5hcmlhJywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnRUeXBlJywgJ2dvb2cuZXZlbnRzLkZvY3VzSGFuZGxlcicsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuaHRtbC5TYWZlSHRtbCcsICdnb29nLmxvZycsICdnb29nLnVpLnRyZWUuQmFzZU5vZGUnLCAnZ29vZy51aS50cmVlLlRyZWVOb2RlJywgJ2dvb2cudWkudHJlZS5UeXBlQWhlYWQnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RyZWUvdHJlZWNvbnRyb2xfdGVzdC5qcycsIFsnZ29vZy51aS50cmVlLlRyZWVDb250cm9sVGVzdCddLCBbJ2dvb2cuZG9tJywgJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51aS50cmVlLlRyZWVDb250cm9sJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdHJlZS90cmVlbm9kZS5qcycsIFsnZ29vZy51aS50cmVlLlRyZWVOb2RlJ10sIFsnZ29vZy51aS50cmVlLkJhc2VOb2RlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90cmVlL3R5cGVhaGVhZC5qcycsIFsnZ29vZy51aS50cmVlLlR5cGVBaGVhZCcsICdnb29nLnVpLnRyZWUuVHlwZUFoZWFkLk9mZnNldCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy5zdHJ1Y3RzLlRyaWUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RyZWUvdHlwZWFoZWFkX3Rlc3QuanMnLCBbJ2dvb2cudWkudHJlZS5UeXBlQWhlYWRUZXN0J10sIFsnZ29vZy5kb20nLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVpLnRyZWUuVHJlZUNvbnRyb2wnLCAnZ29vZy51aS50cmVlLlR5cGVBaGVhZCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3RyaXN0YXRlbWVudWl0ZW0uanMnLCBbJ2dvb2cudWkuVHJpU3RhdGVNZW51SXRlbScsICdnb29nLnVpLlRyaVN0YXRlTWVudUl0ZW0uU3RhdGUnXSwgWydnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy51aS5Db21wb25lbnQnLCAnZ29vZy51aS5NZW51SXRlbScsICdnb29nLnVpLlRyaVN0YXRlTWVudUl0ZW1SZW5kZXJlcicsICdnb29nLnVpLnJlZ2lzdHJ5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1aS90cmlzdGF0ZW1lbnVpdGVtcmVuZGVyZXIuanMnLCBbJ2dvb2cudWkuVHJpU3RhdGVNZW51SXRlbVJlbmRlcmVyJ10sIFsnZ29vZy5hc3NlcnRzJywgJ2dvb2cuZG9tLmNsYXNzbGlzdCcsICdnb29nLnVpLk1lbnVJdGVtUmVuZGVyZXInXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3R3b3RodW1ic2xpZGVyLmpzJywgWydnb29nLnVpLlR3b1RodW1iU2xpZGVyJ10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cudWkuU2xpZGVyQmFzZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvdHdvdGh1bWJzbGlkZXJfdGVzdC5qcycsIFsnZ29vZy51aS5Ud29UaHVtYlNsaWRlclRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuU2xpZGVyQmFzZScsICdnb29nLnVpLlR3b1RodW1iU2xpZGVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndWkvemlwcHkuanMnLCBbJ2dvb2cudWkuWmlwcHknLCAnZ29vZy51aS5aaXBweS5FdmVudHMnLCAnZ29vZy51aS5aaXBweUV2ZW50J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5hMTF5LmFyaWEuUm9sZScsICdnb29nLmExMXkuYXJpYS5TdGF0ZScsICdnb29nLmRvbScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMuRXZlbnQnLCAnZ29vZy5ldmVudHMuRXZlbnRIYW5kbGVyJywgJ2dvb2cuZXZlbnRzLkV2ZW50VGFyZ2V0JywgJ2dvb2cuZXZlbnRzLkV2ZW50VHlwZScsICdnb29nLmV2ZW50cy5LZXlDb2RlcycsICdnb29nLmV2ZW50cy5LZXlIYW5kbGVyJywgJ2dvb2cuc3R5bGUnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VpL3ppcHB5X3Rlc3QuanMnLCBbJ2dvb2cudWkuWmlwcHlUZXN0J10sIFsnZ29vZy5hMTF5LmFyaWEnLCAnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5jbGFzc2xpc3QnLCAnZ29vZy5ldmVudHMnLCAnZ29vZy5ldmVudHMuS2V5Q29kZXMnLCAnZ29vZy5vYmplY3QnLCAnZ29vZy50ZXN0aW5nLmV2ZW50cycsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudWkuWmlwcHknXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1cmkvdXJpLmpzJywgWydnb29nLlVyaScsICdnb29nLlVyaS5RdWVyeURhdGEnXSwgWydnb29nLmFycmF5JywgJ2dvb2cuYXNzZXJ0cycsICdnb29nLnN0cmluZycsICdnb29nLnN0cnVjdHMnLCAnZ29vZy5zdHJ1Y3RzLk1hcCcsICdnb29nLnVyaS51dGlscycsICdnb29nLnVyaS51dGlscy5Db21wb25lbnRJbmRleCcsICdnb29nLnVyaS51dGlscy5TdGFuZGFyZFF1ZXJ5UGFyYW0nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VyaS91cmlfdGVzdC5qcycsIFsnZ29vZy5VcmlUZXN0J10sIFsnZ29vZy5VcmknLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VyaS91dGlscy5qcycsIFsnZ29vZy51cmkudXRpbHMnLCAnZ29vZy51cmkudXRpbHMuQ29tcG9uZW50SW5kZXgnLCAnZ29vZy51cmkudXRpbHMuUXVlcnlBcnJheScsICdnb29nLnVyaS51dGlscy5RdWVyeVZhbHVlJywgJ2dvb2cudXJpLnV0aWxzLlN0YW5kYXJkUXVlcnlQYXJhbSddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5hc3NlcnRzJywgJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1cmkvdXRpbHNfdGVzdC5qcycsIFsnZ29vZy51cmkudXRpbHNUZXN0J10sIFsnZ29vZy5mdW5jdGlvbnMnLCAnZ29vZy5zdHJpbmcnLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVyaS51dGlscyddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC9hZG9iZXJlYWRlci5qcycsIFsnZ29vZy51c2VyQWdlbnQuYWRvYmVSZWFkZXInXSwgWydnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCddLCB7J21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC9hZG9iZXJlYWRlcl90ZXN0LmpzJywgWydnb29nLnVzZXJBZ2VudC5hZG9iZVJlYWRlclRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50LmFkb2JlUmVhZGVyJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndXNlcmFnZW50L2ZsYXNoLmpzJywgWydnb29nLnVzZXJBZ2VudC5mbGFzaCddLCBbJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvZmxhc2hfdGVzdC5qcycsIFsnZ29vZy51c2VyQWdlbnQuZmxhc2hUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudC5mbGFzaCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC9pcGhvdG8uanMnLCBbJ2dvb2cudXNlckFnZW50LmlwaG90byddLCBbJ2dvb2cuc3RyaW5nJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvanNjcmlwdC5qcycsIFsnZ29vZy51c2VyQWdlbnQuanNjcmlwdCddLCBbJ2dvb2cuc3RyaW5nJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvanNjcmlwdF90ZXN0LmpzJywgWydnb29nLnVzZXJBZ2VudC5qc2NyaXB0VGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy51c2VyQWdlbnQuanNjcmlwdCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC9rZXlib2FyZC5qcycsIFsnZ29vZy51c2VyQWdlbnQua2V5Ym9hcmQnXSwgWydnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQva2V5Ym9hcmRfdGVzdC5qcycsIFsnZ29vZy51c2VyQWdlbnQua2V5Ym9hcmRUZXN0J10sIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC50ZXN0QWdlbnRzJywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50LmtleWJvYXJkJywgJ2dvb2cudXNlckFnZW50VGVzdFV0aWwnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvcGxhdGZvcm0uanMnLCBbJ2dvb2cudXNlckFnZW50LnBsYXRmb3JtJ10sIFsnZ29vZy5zdHJpbmcnLCAnZ29vZy51c2VyQWdlbnQnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC9wbGF0Zm9ybV90ZXN0LmpzJywgWydnb29nLnVzZXJBZ2VudC5wbGF0Zm9ybVRlc3QnXSwgWydnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudCcsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cudXNlckFnZW50VGVzdFV0aWwnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvcHJvZHVjdC5qcycsIFsnZ29vZy51c2VyQWdlbnQucHJvZHVjdCddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvcHJvZHVjdF9pc3ZlcnNpb24uanMnLCBbJ2dvb2cudXNlckFnZW50LnByb2R1Y3QuaXNWZXJzaW9uJ10sIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC5wbGF0Zm9ybScsICdnb29nLnN0cmluZycsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudC5wcm9kdWN0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd1c2VyYWdlbnQvcHJvZHVjdF90ZXN0LmpzJywgWydnb29nLnVzZXJBZ2VudC5wcm9kdWN0VGVzdCddLCBbJ2dvb2cuYXJyYXknLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC50ZXN0QWdlbnRzJywgJ2dvb2cubGFicy51c2VyQWdlbnQudXRpbCcsICdnb29nLnRlc3RpbmcuTW9ja1VzZXJBZ2VudCcsICdnb29nLnRlc3RpbmcuUHJvcGVydHlSZXBsYWNlcicsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nLCAnZ29vZy51c2VyQWdlbnRUZXN0VXRpbCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC91c2VyYWdlbnQuanMnLCBbJ2dvb2cudXNlckFnZW50J10sIFsnZ29vZy5sYWJzLnVzZXJBZ2VudC5icm93c2VyJywgJ2dvb2cubGFicy51c2VyQWdlbnQuZW5naW5lJywgJ2dvb2cubGFicy51c2VyQWdlbnQucGxhdGZvcm0nLCAnZ29vZy5sYWJzLnVzZXJBZ2VudC51dGlsJywgJ2dvb2cucmVmbGVjdCcsICdnb29nLnN0cmluZyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndXNlcmFnZW50L3VzZXJhZ2VudF9xdWlya3NfdGVzdC5qcycsIFsnZ29vZy51c2VyQWdlbnRRdWlya3NUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3VzZXJhZ2VudC91c2VyYWdlbnRfdGVzdC5qcycsIFsnZ29vZy51c2VyQWdlbnRUZXN0J10sIFsnZ29vZy5hcnJheScsICdnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cubGFicy51c2VyQWdlbnQudGVzdEFnZW50cycsICdnb29nLmxhYnMudXNlckFnZW50LnV0aWwnLCAnZ29vZy50ZXN0aW5nLlByb3BlcnR5UmVwbGFjZXInLCAnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnVzZXJBZ2VudCcsICdnb29nLnVzZXJBZ2VudFRlc3RVdGlsJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndXNlcmFnZW50L3VzZXJhZ2VudHRlc3R1dGlsLmpzJywgWydnb29nLnVzZXJBZ2VudFRlc3RVdGlsJywgJ2dvb2cudXNlckFnZW50VGVzdFV0aWwuVXNlckFnZW50cyddLCBbJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLmxhYnMudXNlckFnZW50LmVuZ2luZScsICdnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cub2JqZWN0JywgJ2dvb2cudXNlckFnZW50JywgJ2dvb2cudXNlckFnZW50LmtleWJvYXJkJywgJ2dvb2cudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cudXNlckFnZW50LnByb2R1Y3QnLCAnZ29vZy51c2VyQWdlbnQucHJvZHVjdC5pc1ZlcnNpb24nXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9mbG9hdDMyYXJyYXkuanMnLCBbJ2dvb2cudmVjLkZsb2F0MzJBcnJheSddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvZmxvYXQzMmFycmF5X3Rlc3QuanMnLCBbJ2dvb2cudmVjLkZsb2F0MzJBcnJheVRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLkZsb2F0MzJBcnJheSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9mbG9hdDY0YXJyYXkuanMnLCBbJ2dvb2cudmVjLkZsb2F0NjRBcnJheSddLCBbXSwgeydsYW5nJzogJ2VzNid9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvZmxvYXQ2NGFycmF5X3Rlc3QuanMnLCBbJ2dvb2cudmVjLkZsb2F0NjRBcnJheVRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLkZsb2F0NjRBcnJheSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9tYXQzLmpzJywgWydnb29nLnZlYy5NYXQzJ10sIFsnZ29vZy52ZWMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9tYXQzX3Rlc3QuanMnLCBbJ2dvb2cudmVjLk1hdDNUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy5NYXQzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL21hdDNkLmpzJywgWydnb29nLnZlYy5tYXQzZCcsICdnb29nLnZlYy5tYXQzZC5UeXBlJ10sIFsnZ29vZy52ZWMnLCAnZ29vZy52ZWMudmVjM2QuVHlwZSddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL21hdDNkX3Rlc3QuanMnLCBbJ2dvb2cudmVjLm1hdDNkVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMubWF0M2QnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvbWF0M2YuanMnLCBbJ2dvb2cudmVjLm1hdDNmJywgJ2dvb2cudmVjLm1hdDNmLlR5cGUnXSwgWydnb29nLnZlYycsICdnb29nLnZlYy52ZWMzZi5UeXBlJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvbWF0M2ZfdGVzdC5qcycsIFsnZ29vZy52ZWMubWF0M2ZUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy5tYXQzZiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9tYXQ0LmpzJywgWydnb29nLnZlYy5NYXQ0J10sIFsnZ29vZy52ZWMnLCAnZ29vZy52ZWMuVmVjMycsICdnb29nLnZlYy5WZWM0J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvbWF0NF90ZXN0LmpzJywgWydnb29nLnZlYy5NYXQ0VGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMuTWF0NCcsICdnb29nLnZlYy5WZWMzJywgJ2dvb2cudmVjLlZlYzQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvbWF0NGQuanMnLCBbJ2dvb2cudmVjLm1hdDRkJywgJ2dvb2cudmVjLm1hdDRkLlR5cGUnXSwgWydnb29nLnZlYycsICdnb29nLnZlYy5RdWF0ZXJuaW9uJywgJ2dvb2cudmVjLnZlYzNkJywgJ2dvb2cudmVjLnZlYzRkJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvbWF0NGRfdGVzdC5qcycsIFsnZ29vZy52ZWMubWF0NGRUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy5RdWF0ZXJuaW9uJywgJ2dvb2cudmVjLm1hdDRkJywgJ2dvb2cudmVjLnZlYzNkJywgJ2dvb2cudmVjLnZlYzRkJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL21hdDRmLmpzJywgWydnb29nLnZlYy5tYXQ0ZicsICdnb29nLnZlYy5tYXQ0Zi5UeXBlJ10sIFsnZ29vZy52ZWMnLCAnZ29vZy52ZWMuUXVhdGVybmlvbicsICdnb29nLnZlYy52ZWMzZicsICdnb29nLnZlYy52ZWM0ZiddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL21hdDRmX3Rlc3QuanMnLCBbJ2dvb2cudmVjLm1hdDRmVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMuUXVhdGVybmlvbicsICdnb29nLnZlYy5tYXQ0ZicsICdnb29nLnZlYy52ZWMzZicsICdnb29nLnZlYy52ZWM0ZiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy9xdWF0ZXJuaW9uLmpzJywgWydnb29nLnZlYy5RdWF0ZXJuaW9uJywgJ2dvb2cudmVjLlF1YXRlcm5pb24uQW55VHlwZSddLCBbJ2dvb2cudmVjJywgJ2dvb2cudmVjLlZlYzMnLCAnZ29vZy52ZWMuVmVjNCddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3F1YXRlcm5pb25fdGVzdC5qcycsIFsnZ29vZy52ZWMuUXVhdGVybmlvblRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLk1hdDMnLCAnZ29vZy52ZWMuTWF0NCcsICdnb29nLnZlYy5RdWF0ZXJuaW9uJywgJ2dvb2cudmVjLlZlYzMnLCAnZ29vZy52ZWMudmVjM2YnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvcmF5LmpzJywgWydnb29nLnZlYy5SYXknXSwgWydnb29nLnZlYy5WZWMzJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvcmF5X3Rlc3QuanMnLCBbJ2dvb2cudmVjLlJheVRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLlJheSddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMuanMnLCBbJ2dvb2cudmVjJywgJ2dvb2cudmVjLkFueVR5cGUnLCAnZ29vZy52ZWMuQXJyYXlUeXBlJywgJ2dvb2cudmVjLkZsb2F0MzInLCAnZ29vZy52ZWMuRmxvYXQ2NCcsICdnb29nLnZlYy5OdW1iZXInXSwgWydnb29nLnZlYy5GbG9hdDMyQXJyYXknLCAnZ29vZy52ZWMuRmxvYXQ2NEFycmF5J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjMi5qcycsIFsnZ29vZy52ZWMuVmVjMiddLCBbJ2dvb2cudmVjJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjMl90ZXN0LmpzJywgWydnb29nLnZlYy5WZWMyVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMuVmVjMiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMyZC5qcycsIFsnZ29vZy52ZWMudmVjMmQnLCAnZ29vZy52ZWMudmVjMmQuVHlwZSddLCBbJ2dvb2cudmVjJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjMmRfdGVzdC5qcycsIFsnZ29vZy52ZWMudmVjMmRUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy52ZWMyZCddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMyZi5qcycsIFsnZ29vZy52ZWMudmVjMmYnLCAnZ29vZy52ZWMudmVjMmYuVHlwZSddLCBbJ2dvb2cudmVjJ10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjMmZfdGVzdC5qcycsIFsnZ29vZy52ZWMudmVjMmZUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy52ZWMyZiddLCB7J2xhbmcnOiAnZXM2JywgJ21vZHVsZSc6ICdnb29nJ30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMzLmpzJywgWydnb29nLnZlYy5WZWMzJ10sIFsnZ29vZy52ZWMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMzX3Rlc3QuanMnLCBbJ2dvb2cudmVjLlZlYzNUZXN0J10sIFsnZ29vZy50ZXN0aW5nLnRlc3RTdWl0ZScsICdnb29nLnZlYy5WZWMzJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzNkLmpzJywgWydnb29nLnZlYy52ZWMzZCcsICdnb29nLnZlYy52ZWMzZC5UeXBlJ10sIFsnZ29vZy52ZWMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMzZF90ZXN0LmpzJywgWydnb29nLnZlYy52ZWMzZFRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLnZlYzNkJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzNmLmpzJywgWydnb29nLnZlYy52ZWMzZicsICdnb29nLnZlYy52ZWMzZi5UeXBlJ10sIFsnZ29vZy52ZWMnXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3ZlYy92ZWMzZl90ZXN0LmpzJywgWydnb29nLnZlYy52ZWMzZlRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLnZlYzNmJ10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzQuanMnLCBbJ2dvb2cudmVjLlZlYzQnXSwgWydnb29nLnZlYyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzRfdGVzdC5qcycsIFsnZ29vZy52ZWMuVmVjNFRlc3QnXSwgWydnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cudmVjLlZlYzQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjNGQuanMnLCBbJ2dvb2cudmVjLnZlYzRkJywgJ2dvb2cudmVjLnZlYzRkLlR5cGUnXSwgWydnb29nLnZlYyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzRkX3Rlc3QuanMnLCBbJ2dvb2cudmVjLnZlYzRkVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMudmVjNGQnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd2ZWMvdmVjNGYuanMnLCBbJ2dvb2cudmVjLnZlYzRmJywgJ2dvb2cudmVjLnZlYzRmLlR5cGUnXSwgWydnb29nLnZlYyddLCB7fSk7Cmdvb2cuYWRkRGVwZW5kZW5jeSgndmVjL3ZlYzRmX3Rlc3QuanMnLCBbJ2dvb2cudmVjLnZlYzRmVGVzdCddLCBbJ2dvb2cudGVzdGluZy50ZXN0U3VpdGUnLCAnZ29vZy52ZWMudmVjNGYnXSwgeydsYW5nJzogJ2VzNicsICdtb2R1bGUnOiAnZ29vZyd9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd3ZWJnbC93ZWJnbC5qcycsIFsnZ29vZy53ZWJnbCddLCBbXSwge30pOwpnb29nLmFkZERlcGVuZGVuY3koJ3dpbmRvdy93aW5kb3cuanMnLCBbJ2dvb2cud2luZG93J10sIFsnZ29vZy5kb20nLCAnZ29vZy5kb20uVGFnTmFtZScsICdnb29nLmRvbS5zYWZlJywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cuaHRtbC51bmNoZWNrZWRjb252ZXJzaW9ucycsICdnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cuc3RyaW5nLkNvbnN0JywgJ2dvb2cudXNlckFnZW50J10sIHt9KTsKZ29vZy5hZGREZXBlbmRlbmN5KCd3aW5kb3cvd2luZG93X3Rlc3QuanMnLCBbJ2dvb2cud2luZG93VGVzdCddLCBbJ2dvb2cuUHJvbWlzZScsICdnb29nLmRvbScsICdnb29nLmRvbS5UYWdOYW1lJywgJ2dvb2cuZXZlbnRzJywgJ2dvb2cuZnVuY3Rpb25zJywgJ2dvb2cuaHRtbC5TYWZlVXJsJywgJ2dvb2cubGFicy51c2VyQWdlbnQuYnJvd3NlcicsICdnb29nLmxhYnMudXNlckFnZW50LmVuZ2luZScsICdnb29nLmxhYnMudXNlckFnZW50LnBsYXRmb3JtJywgJ2dvb2cuc3RyaW5nJywgJ2dvb2cudGVzdGluZy5Qcm9wZXJ0eVJlcGxhY2VyJywgJ2dvb2cudGVzdGluZy5UZXN0Q2FzZScsICdnb29nLnRlc3RpbmcudGVzdFN1aXRlJywgJ2dvb2cud2luZG93J10sIHsnbGFuZyc6ICdlczYnLCAnbW9kdWxlJzogJ2dvb2cnfSk7Cgp3aW5kb3cucG9seW1lclNraXBMb2FkaW5nRm9udFJvYm90byA9IHRydWU7Ci8qKiB2aW06IGV0OnRzPTQ6c3c9NDpzdHM9NAogKiBAbGljZW5zZSBSZXF1aXJlSlMgMi4zLjYgQ29weXJpZ2h0IGpRdWVyeSBGb3VuZGF0aW9uIGFuZCBvdGhlciBjb250cmlidXRvcnMuCiAqIFJlbGVhc2VkIHVuZGVyIE1JVCBsaWNlbnNlLCBodHRwczovL2dpdGh1Yi5jb20vcmVxdWlyZWpzL3JlcXVpcmVqcy9ibG9iL21hc3Rlci9MSUNFTlNFCiAqLwovL05vdCB1c2luZyBzdHJpY3Q6IHVuZXZlbiBzdHJpY3Qgc3VwcG9ydCBpbiBicm93c2VycywgIzM5MiwgYW5kIGNhdXNlcwovL3Byb2JsZW1zIHdpdGggcmVxdWlyZWpzLmV4ZWMoKS90cmFuc3BpbGVyIHBsdWdpbnMgdGhhdCBtYXkgbm90IGJlIHN0cmljdC4KLypqc2xpbnQgcmVnZXhwOiB0cnVlLCBub21lbjogdHJ1ZSwgc2xvcHB5OiB0cnVlICovCi8qZ2xvYmFsIHdpbmRvdywgbmF2aWdhdG9yLCBkb2N1bWVudCwgaW1wb3J0U2NyaXB0cywgc2V0VGltZW91dCwgb3BlcmEgKi8KCnZhciByZXF1aXJlanMsIHJlcXVpcmUsIGRlZmluZTsKKGZ1bmN0aW9uIChnbG9iYWwsIHNldFRpbWVvdXQpIHsKICAgIHZhciByZXEsIHMsIGhlYWQsIGJhc2VFbGVtZW50LCBkYXRhTWFpbiwgc3JjLAogICAgICAgIGludGVyYWN0aXZlU2NyaXB0LCBjdXJyZW50bHlBZGRpbmdTY3JpcHQsIG1haW5TY3JpcHQsIHN1YlBhdGgsCiAgICAgICAgdmVyc2lvbiA9ICcyLjMuNicsCiAgICAgICAgY29tbWVudFJlZ0V4cCA9IC9cL1wqW1xzXFNdKj9cKlwvfChbXjoiJz1dfF4pXC9cLy4qJC9tZywKICAgICAgICBjanNSZXF1aXJlUmVnRXhwID0gL1teLl1ccypyZXF1aXJlXHMqXChccypbIiddKFteJyJcc10rKVsiJ11ccypcKS9nLAogICAgICAgIGpzU3VmZml4UmVnRXhwID0gL1wuanMkLywKICAgICAgICBjdXJyRGlyUmVnRXhwID0gL15cLlwvLywKICAgICAgICBvcCA9IE9iamVjdC5wcm90b3R5cGUsCiAgICAgICAgb3N0cmluZyA9IG9wLnRvU3RyaW5nLAogICAgICAgIGhhc093biA9IG9wLmhhc093blByb3BlcnR5LAogICAgICAgIGlzQnJvd3NlciA9ICEhKHR5cGVvZiB3aW5kb3cgIT09ICd1bmRlZmluZWQnICYmIHR5cGVvZiBuYXZpZ2F0b3IgIT09ICd1bmRlZmluZWQnICYmIHdpbmRvdy5kb2N1bWVudCksCiAgICAgICAgaXNXZWJXb3JrZXIgPSAhaXNCcm93c2VyICYmIHR5cGVvZiBpbXBvcnRTY3JpcHRzICE9PSAndW5kZWZpbmVkJywKICAgICAgICAvL1BTMyBpbmRpY2F0ZXMgbG9hZGVkIGFuZCBjb21wbGV0ZSwgYnV0IG5lZWQgdG8gd2FpdCBmb3IgY29tcGxldGUKICAgICAgICAvL3NwZWNpZmljYWxseS4gU2VxdWVuY2UgaXMgJ2xvYWRpbmcnLCAnbG9hZGVkJywgZXhlY3V0aW9uLAogICAgICAgIC8vIHRoZW4gJ2NvbXBsZXRlJy4gVGhlIFVBIGNoZWNrIGlzIHVuZm9ydHVuYXRlLCBidXQgbm90IHN1cmUgaG93CiAgICAgICAgLy90byBmZWF0dXJlIHRlc3Qgdy9vIGNhdXNpbmcgcGVyZiBpc3N1ZXMuCiAgICAgICAgcmVhZHlSZWdFeHAgPSBpc0Jyb3dzZXIgJiYgbmF2aWdhdG9yLnBsYXRmb3JtID09PSAnUExBWVNUQVRJT04gMycgPwogICAgICAgICAgICAgICAgICAgICAgL15jb21wbGV0ZSQvIDogL14oY29tcGxldGV8bG9hZGVkKSQvLAogICAgICAgIGRlZkNvbnRleHROYW1lID0gJ18nLAogICAgICAgIC8vT2ggdGhlIHRyYWdlZHksIGRldGVjdGluZyBvcGVyYS4gU2VlIHRoZSB1c2FnZSBvZiBpc09wZXJhIGZvciByZWFzb24uCiAgICAgICAgaXNPcGVyYSA9IHR5cGVvZiBvcGVyYSAhPT0gJ3VuZGVmaW5lZCcgJiYgb3BlcmEudG9TdHJpbmcoKSA9PT0gJ1tvYmplY3QgT3BlcmFdJywKICAgICAgICBjb250ZXh0cyA9IHt9LAogICAgICAgIGNmZyA9IHt9LAogICAgICAgIGdsb2JhbERlZlF1ZXVlID0gW10sCiAgICAgICAgdXNlSW50ZXJhY3RpdmUgPSBmYWxzZTsKCiAgICAvL0NvdWxkIG1hdGNoIHNvbWV0aGluZyBsaWtlICcpLy9jb21tZW50JywgZG8gbm90IGxvc2UgdGhlIHByZWZpeCB0byBjb21tZW50LgogICAgZnVuY3Rpb24gY29tbWVudFJlcGxhY2UobWF0Y2gsIHNpbmdsZVByZWZpeCkgewogICAgICAgIHJldHVybiBzaW5nbGVQcmVmaXggfHwgJyc7CiAgICB9CgogICAgZnVuY3Rpb24gaXNGdW5jdGlvbihpdCkgewogICAgICAgIHJldHVybiBvc3RyaW5nLmNhbGwoaXQpID09PSAnW29iamVjdCBGdW5jdGlvbl0nOwogICAgfQoKICAgIGZ1bmN0aW9uIGlzQXJyYXkoaXQpIHsKICAgICAgICByZXR1cm4gb3N0cmluZy5jYWxsKGl0KSA9PT0gJ1tvYmplY3QgQXJyYXldJzsKICAgIH0KCiAgICAvKioKICAgICAqIEhlbHBlciBmdW5jdGlvbiBmb3IgaXRlcmF0aW5nIG92ZXIgYW4gYXJyYXkuIElmIHRoZSBmdW5jIHJldHVybnMKICAgICAqIGEgdHJ1ZSB2YWx1ZSwgaXQgd2lsbCBicmVhayBvdXQgb2YgdGhlIGxvb3AuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVhY2goYXJ5LCBmdW5jKSB7CiAgICAgICAgaWYgKGFyeSkgewogICAgICAgICAgICB2YXIgaTsKICAgICAgICAgICAgZm9yIChpID0gMDsgaSA8IGFyeS5sZW5ndGg7IGkgKz0gMSkgewogICAgICAgICAgICAgICAgaWYgKGFyeVtpXSAmJiBmdW5jKGFyeVtpXSwgaSwgYXJ5KSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogSGVscGVyIGZ1bmN0aW9uIGZvciBpdGVyYXRpbmcgb3ZlciBhbiBhcnJheSBiYWNrd2FyZHMuIElmIHRoZSBmdW5jCiAgICAgKiByZXR1cm5zIGEgdHJ1ZSB2YWx1ZSwgaXQgd2lsbCBicmVhayBvdXQgb2YgdGhlIGxvb3AuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVhY2hSZXZlcnNlKGFyeSwgZnVuYykgewogICAgICAgIGlmIChhcnkpIHsKICAgICAgICAgICAgdmFyIGk7CiAgICAgICAgICAgIGZvciAoaSA9IGFyeS5sZW5ndGggLSAxOyBpID4gLTE7IGkgLT0gMSkgewogICAgICAgICAgICAgICAgaWYgKGFyeVtpXSAmJiBmdW5jKGFyeVtpXSwgaSwgYXJ5KSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGhhc1Byb3Aob2JqLCBwcm9wKSB7CiAgICAgICAgcmV0dXJuIGhhc093bi5jYWxsKG9iaiwgcHJvcCk7CiAgICB9CgogICAgZnVuY3Rpb24gZ2V0T3duKG9iaiwgcHJvcCkgewogICAgICAgIHJldHVybiBoYXNQcm9wKG9iaiwgcHJvcCkgJiYgb2JqW3Byb3BdOwogICAgfQoKICAgIC8qKgogICAgICogQ3ljbGVzIG92ZXIgcHJvcGVydGllcyBpbiBhbiBvYmplY3QgYW5kIGNhbGxzIGEgZnVuY3Rpb24gZm9yIGVhY2gKICAgICAqIHByb3BlcnR5IHZhbHVlLiBJZiB0aGUgZnVuY3Rpb24gcmV0dXJucyBhIHRydXRoeSB2YWx1ZSwgdGhlbiB0aGUKICAgICAqIGl0ZXJhdGlvbiBpcyBzdG9wcGVkLgogICAgICovCiAgICBmdW5jdGlvbiBlYWNoUHJvcChvYmosIGZ1bmMpIHsKICAgICAgICB2YXIgcHJvcDsKICAgICAgICBmb3IgKHByb3AgaW4gb2JqKSB7CiAgICAgICAgICAgIGlmIChoYXNQcm9wKG9iaiwgcHJvcCkpIHsKICAgICAgICAgICAgICAgIGlmIChmdW5jKG9ialtwcm9wXSwgcHJvcCkpIHsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFNpbXBsZSBmdW5jdGlvbiB0byBtaXggaW4gcHJvcGVydGllcyBmcm9tIHNvdXJjZSBpbnRvIHRhcmdldCwKICAgICAqIGJ1dCBvbmx5IGlmIHRhcmdldCBkb2VzIG5vdCBhbHJlYWR5IGhhdmUgYSBwcm9wZXJ0eSBvZiB0aGUgc2FtZSBuYW1lLgogICAgICovCiAgICBmdW5jdGlvbiBtaXhpbih0YXJnZXQsIHNvdXJjZSwgZm9yY2UsIGRlZXBTdHJpbmdNaXhpbikgewogICAgICAgIGlmIChzb3VyY2UpIHsKICAgICAgICAgICAgZWFjaFByb3Aoc291cmNlLCBmdW5jdGlvbiAodmFsdWUsIHByb3ApIHsKICAgICAgICAgICAgICAgIGlmIChmb3JjZSB8fCAhaGFzUHJvcCh0YXJnZXQsIHByb3ApKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKGRlZXBTdHJpbmdNaXhpbiAmJiB0eXBlb2YgdmFsdWUgPT09ICdvYmplY3QnICYmIHZhbHVlICYmCiAgICAgICAgICAgICAgICAgICAgICAgICFpc0FycmF5KHZhbHVlKSAmJiAhaXNGdW5jdGlvbih2YWx1ZSkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgISh2YWx1ZSBpbnN0YW5jZW9mIFJlZ0V4cCkpIHsKCiAgICAgICAgICAgICAgICAgICAgICAgIGlmICghdGFyZ2V0W3Byb3BdKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0YXJnZXRbcHJvcF0gPSB7fTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBtaXhpbih0YXJnZXRbcHJvcF0sIHZhbHVlLCBmb3JjZSwgZGVlcFN0cmluZ01peGluKTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICB0YXJnZXRbcHJvcF0gPSB2YWx1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGFyZ2V0OwogICAgfQoKICAgIC8vU2ltaWxhciB0byBGdW5jdGlvbi5wcm90b3R5cGUuYmluZCwgYnV0IHRoZSAndGhpcycgb2JqZWN0IGlzIHNwZWNpZmllZAogICAgLy9maXJzdCwgc2luY2UgaXQgaXMgZWFzaWVyIHRvIHJlYWQvZmlndXJlIG91dCB3aGF0ICd0aGlzJyB3aWxsIGJlLgogICAgZnVuY3Rpb24gYmluZChvYmosIGZuKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIGZuLmFwcGx5KG9iaiwgYXJndW1lbnRzKTsKICAgICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNjcmlwdHMoKSB7CiAgICAgICAgcmV0dXJuIGRvY3VtZW50LmdldEVsZW1lbnRzQnlUYWdOYW1lKCdzY3JpcHQnKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0T25FcnJvcihlcnIpIHsKICAgICAgICB0aHJvdyBlcnI7CiAgICB9CgogICAgLy9BbGxvdyBnZXR0aW5nIGEgZ2xvYmFsIHRoYXQgaXMgZXhwcmVzc2VkIGluCiAgICAvL2RvdCBub3RhdGlvbiwgbGlrZSAnYS5iLmMnLgogICAgZnVuY3Rpb24gZ2V0R2xvYmFsKHZhbHVlKSB7CiAgICAgICAgaWYgKCF2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgfQogICAgICAgIHZhciBnID0gZ2xvYmFsOwogICAgICAgIGVhY2godmFsdWUuc3BsaXQoJy4nKSwgZnVuY3Rpb24gKHBhcnQpIHsKICAgICAgICAgICAgZyA9IGdbcGFydF07CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGc7CiAgICB9CgogICAgLyoqCiAgICAgKiBDb25zdHJ1Y3RzIGFuIGVycm9yIHdpdGggYSBwb2ludGVyIHRvIGFuIFVSTCB3aXRoIG1vcmUgaW5mb3JtYXRpb24uCiAgICAgKiBAcGFyYW0ge1N0cmluZ30gaWQgdGhlIGVycm9yIElEIHRoYXQgbWFwcyB0byBhbiBJRCBvbiBhIHdlYiBwYWdlLgogICAgICogQHBhcmFtIHtTdHJpbmd9IG1lc3NhZ2UgaHVtYW4gcmVhZGFibGUgZXJyb3IuCiAgICAgKiBAcGFyYW0ge0Vycm9yfSBbZXJyXSB0aGUgb3JpZ2luYWwgZXJyb3IsIGlmIHRoZXJlIGlzIG9uZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7RXJyb3J9CiAgICAgKi8KICAgIGZ1bmN0aW9uIG1ha2VFcnJvcihpZCwgbXNnLCBlcnIsIHJlcXVpcmVNb2R1bGVzKSB7CiAgICAgICAgdmFyIGUgPSBuZXcgRXJyb3IobXNnICsgJ1xuaHR0cHM6Ly9yZXF1aXJlanMub3JnL2RvY3MvZXJyb3JzLmh0bWwjJyArIGlkKTsKICAgICAgICBlLnJlcXVpcmVUeXBlID0gaWQ7CiAgICAgICAgZS5yZXF1aXJlTW9kdWxlcyA9IHJlcXVpcmVNb2R1bGVzOwogICAgICAgIGlmIChlcnIpIHsKICAgICAgICAgICAgZS5vcmlnaW5hbEVycm9yID0gZXJyOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZTsKICAgIH0KCiAgICBpZiAodHlwZW9mIGRlZmluZSAhPT0gJ3VuZGVmaW5lZCcpIHsKICAgICAgICAvL0lmIGEgZGVmaW5lIGlzIGFscmVhZHkgaW4gcGxheSB2aWEgYW5vdGhlciBBTUQgbG9hZGVyLAogICAgICAgIC8vZG8gbm90IG92ZXJ3cml0ZS4KICAgICAgICByZXR1cm47CiAgICB9CgogICAgaWYgKHR5cGVvZiByZXF1aXJlanMgIT09ICd1bmRlZmluZWQnKSB7CiAgICAgICAgaWYgKGlzRnVuY3Rpb24ocmVxdWlyZWpzKSkgewogICAgICAgICAgICAvL0RvIG5vdCBvdmVyd3JpdGUgYW4gZXhpc3RpbmcgcmVxdWlyZWpzIGluc3RhbmNlLgogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGNmZyA9IHJlcXVpcmVqczsKICAgICAgICByZXF1aXJlanMgPSB1bmRlZmluZWQ7CiAgICB9CgogICAgLy9BbGxvdyBmb3IgYSByZXF1aXJlIGNvbmZpZyBvYmplY3QKICAgIGlmICh0eXBlb2YgcmVxdWlyZSAhPT0gJ3VuZGVmaW5lZCcgJiYgIWlzRnVuY3Rpb24ocmVxdWlyZSkpIHsKICAgICAgICAvL2Fzc3VtZSBpdCBpcyBhIGNvbmZpZyBvYmplY3QuCiAgICAgICAgY2ZnID0gcmVxdWlyZTsKICAgICAgICByZXF1aXJlID0gdW5kZWZpbmVkOwogICAgfQoKICAgIGZ1bmN0aW9uIG5ld0NvbnRleHQoY29udGV4dE5hbWUpIHsKICAgICAgICB2YXIgaW5DaGVja0xvYWRlZCwgTW9kdWxlLCBjb250ZXh0LCBoYW5kbGVycywKICAgICAgICAgICAgY2hlY2tMb2FkZWRUaW1lb3V0SWQsCiAgICAgICAgICAgIGNvbmZpZyA9IHsKICAgICAgICAgICAgICAgIC8vRGVmYXVsdHMuIERvIG5vdCBzZXQgYSBkZWZhdWx0IGZvciBtYXAKICAgICAgICAgICAgICAgIC8vY29uZmlnIHRvIHNwZWVkIHVwIG5vcm1hbGl6ZSgpLCB3aGljaAogICAgICAgICAgICAgICAgLy93aWxsIHJ1biBmYXN0ZXIgaWYgdGhlcmUgaXMgbm8gZGVmYXVsdC4KICAgICAgICAgICAgICAgIHdhaXRTZWNvbmRzOiA3LAogICAgICAgICAgICAgICAgYmFzZVVybDogJy4vJywKICAgICAgICAgICAgICAgIHBhdGhzOiB7fSwKICAgICAgICAgICAgICAgIGJ1bmRsZXM6IHt9LAogICAgICAgICAgICAgICAgcGtnczoge30sCiAgICAgICAgICAgICAgICBzaGltOiB7fSwKICAgICAgICAgICAgICAgIGNvbmZpZzoge30KICAgICAgICAgICAgfSwKICAgICAgICAgICAgcmVnaXN0cnkgPSB7fSwKICAgICAgICAgICAgLy9yZWdpc3RyeSBvZiBqdXN0IGVuYWJsZWQgbW9kdWxlcywgdG8gc3BlZWQKICAgICAgICAgICAgLy9jeWNsZSBicmVha2luZyBjb2RlIHdoZW4gbG90cyBvZiBtb2R1bGVzCiAgICAgICAgICAgIC8vYXJlIHJlZ2lzdGVyZWQsIGJ1dCBub3QgYWN0aXZhdGVkLgogICAgICAgICAgICBlbmFibGVkUmVnaXN0cnkgPSB7fSwKICAgICAgICAgICAgdW5kZWZFdmVudHMgPSB7fSwKICAgICAgICAgICAgZGVmUXVldWUgPSBbXSwKICAgICAgICAgICAgZGVmaW5lZCA9IHt9LAogICAgICAgICAgICB1cmxGZXRjaGVkID0ge30sCiAgICAgICAgICAgIGJ1bmRsZXNNYXAgPSB7fSwKICAgICAgICAgICAgcmVxdWlyZUNvdW50ZXIgPSAxLAogICAgICAgICAgICB1bm5vcm1hbGl6ZWRDb3VudGVyID0gMTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVHJpbXMgdGhlIC4gYW5kIC4uIGZyb20gYW4gYXJyYXkgb2YgcGF0aCBzZWdtZW50cy4KICAgICAgICAgKiBJdCB3aWxsIGtlZXAgYSBsZWFkaW5nIHBhdGggc2VnbWVudCBpZiBhIC4uIHdpbGwgYmVjb21lCiAgICAgICAgICogdGhlIGZpcnN0IHBhdGggc2VnbWVudCwgdG8gaGVscCB3aXRoIG1vZHVsZSBuYW1lIGxvb2t1cHMsCiAgICAgICAgICogd2hpY2ggYWN0IGxpa2UgcGF0aHMsIGJ1dCBjYW4gYmUgcmVtYXBwZWQuIEJ1dCB0aGUgZW5kIHJlc3VsdCwKICAgICAgICAgKiBhbGwgcGF0aHMgdGhhdCB1c2UgdGhpcyBmdW5jdGlvbiBzaG91bGQgbG9vayBub3JtYWxpemVkLgogICAgICAgICAqIE5PVEU6IHRoaXMgbWV0aG9kIE1PRElGSUVTIHRoZSBpbnB1dCBhcnJheS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnkgdGhlIGFycmF5IG9mIHBhdGggc2VnbWVudHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdHJpbURvdHMoYXJ5KSB7CiAgICAgICAgICAgIHZhciBpLCBwYXJ0OwogICAgICAgICAgICBmb3IgKGkgPSAwOyBpIDwgYXJ5Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBwYXJ0ID0gYXJ5W2ldOwogICAgICAgICAgICAgICAgaWYgKHBhcnQgPT09ICcuJykgewogICAgICAgICAgICAgICAgICAgIGFyeS5zcGxpY2UoaSwgMSk7CiAgICAgICAgICAgICAgICAgICAgaSAtPSAxOwogICAgICAgICAgICAgICAgfSBlbHNlIGlmIChwYXJ0ID09PSAnLi4nKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gSWYgYXQgdGhlIHN0YXJ0LCBvciBwcmV2aW91cyB2YWx1ZSBpcyBzdGlsbCAuLiwKICAgICAgICAgICAgICAgICAgICAvLyBrZWVwIHRoZW0gc28gdGhhdCB3aGVuIGNvbnZlcnRlZCB0byBhIHBhdGggaXQgbWF5CiAgICAgICAgICAgICAgICAgICAgLy8gc3RpbGwgd29yayB3aGVuIGNvbnZlcnRlZCB0byBhIHBhdGgsIGV2ZW4gdGhvdWdoCiAgICAgICAgICAgICAgICAgICAgLy8gYXMgYW4gSUQgaXQgaXMgbGVzcyB0aGFuIGlkZWFsLiBJbiBsYXJnZXIgcG9pbnQKICAgICAgICAgICAgICAgICAgICAvLyByZWxlYXNlcywgbWF5IGJlIGJldHRlciB0byBqdXN0IGtpY2sgb3V0IGFuIGVycm9yLgogICAgICAgICAgICAgICAgICAgIGlmIChpID09PSAwIHx8IChpID09PSAxICYmIGFyeVsyXSA9PT0gJy4uJykgfHwgYXJ5W2kgLSAxXSA9PT0gJy4uJykgewogICAgICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgaWYgKGkgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGFyeS5zcGxpY2UoaSAtIDEsIDIpOwogICAgICAgICAgICAgICAgICAgICAgICBpIC09IDI7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHaXZlbiBhIHJlbGF0aXZlIG1vZHVsZSBuYW1lLCBsaWtlIC4vc29tZXRoaW5nLCBub3JtYWxpemUgaXQgdG8KICAgICAgICAgKiBhIHJlYWwgbmFtZSB0aGF0IGNhbiBiZSBtYXBwZWQgdG8gYSBwYXRoLgogICAgICAgICAqIEBwYXJhbSB7U3RyaW5nfSBuYW1lIHRoZSByZWxhdGl2ZSBuYW1lCiAgICAgICAgICogQHBhcmFtIHtTdHJpbmd9IGJhc2VOYW1lIGEgcmVhbCBuYW1lIHRoYXQgdGhlIG5hbWUgYXJnIGlzIHJlbGF0aXZlCiAgICAgICAgICogdG8uCiAgICAgICAgICogQHBhcmFtIHtCb29sZWFufSBhcHBseU1hcCBhcHBseSB0aGUgbWFwIGNvbmZpZyB0byB0aGUgdmFsdWUuIFNob3VsZAogICAgICAgICAqIG9ubHkgYmUgZG9uZSBpZiB0aGlzIG5vcm1hbGl6YXRpb24gaXMgZm9yIGEgZGVwZW5kZW5jeSBJRC4KICAgICAgICAgKiBAcmV0dXJucyB7U3RyaW5nfSBub3JtYWxpemVkIG5hbWUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBub3JtYWxpemUobmFtZSwgYmFzZU5hbWUsIGFwcGx5TWFwKSB7CiAgICAgICAgICAgIHZhciBwa2dNYWluLCBtYXBWYWx1ZSwgbmFtZVBhcnRzLCBpLCBqLCBuYW1lU2VnbWVudCwgbGFzdEluZGV4LAogICAgICAgICAgICAgICAgZm91bmRNYXAsIGZvdW5kSSwgZm91bmRTdGFyTWFwLCBzdGFySSwgbm9ybWFsaXplZEJhc2VQYXJ0cywKICAgICAgICAgICAgICAgIGJhc2VQYXJ0cyA9IChiYXNlTmFtZSAmJiBiYXNlTmFtZS5zcGxpdCgnLycpKSwKICAgICAgICAgICAgICAgIG1hcCA9IGNvbmZpZy5tYXAsCiAgICAgICAgICAgICAgICBzdGFyTWFwID0gbWFwICYmIG1hcFsnKiddOwoKICAgICAgICAgICAgLy9BZGp1c3QgYW55IHJlbGF0aXZlIHBhdGhzLgogICAgICAgICAgICBpZiAobmFtZSkgewogICAgICAgICAgICAgICAgbmFtZSA9IG5hbWUuc3BsaXQoJy8nKTsKICAgICAgICAgICAgICAgIGxhc3RJbmRleCA9IG5hbWUubGVuZ3RoIC0gMTsKCiAgICAgICAgICAgICAgICAvLyBJZiB3YW50aW5nIG5vZGUgSUQgY29tcGF0aWJpbGl0eSwgc3RyaXAgLmpzIGZyb20gZW5kCiAgICAgICAgICAgICAgICAvLyBvZiBJRHMuIEhhdmUgdG8gZG8gdGhpcyBoZXJlLCBhbmQgbm90IGluIG5hbWVUb1VybAogICAgICAgICAgICAgICAgLy8gYmVjYXVzZSBub2RlIGFsbG93cyBlaXRoZXIgLmpzIG9yIG5vbiAuanMgdG8gbWFwCiAgICAgICAgICAgICAgICAvLyB0byBzYW1lIGZpbGUuCiAgICAgICAgICAgICAgICBpZiAoY29uZmlnLm5vZGVJZENvbXBhdCAmJiBqc1N1ZmZpeFJlZ0V4cC50ZXN0KG5hbWVbbGFzdEluZGV4XSkpIHsKICAgICAgICAgICAgICAgICAgICBuYW1lW2xhc3RJbmRleF0gPSBuYW1lW2xhc3RJbmRleF0ucmVwbGFjZShqc1N1ZmZpeFJlZ0V4cCwgJycpOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIC8vIFN0YXJ0cyB3aXRoIGEgJy4nIHNvIG5lZWQgdGhlIGJhc2VOYW1lCiAgICAgICAgICAgICAgICBpZiAobmFtZVswXS5jaGFyQXQoMCkgPT09ICcuJyAmJiBiYXNlUGFydHMpIHsKICAgICAgICAgICAgICAgICAgICAvL0NvbnZlcnQgYmFzZU5hbWUgdG8gYXJyYXksIGFuZCBsb3Agb2ZmIHRoZSBsYXN0IHBhcnQsCiAgICAgICAgICAgICAgICAgICAgLy9zbyB0aGF0IC4gbWF0Y2hlcyB0aGF0ICdkaXJlY3RvcnknIGFuZCBub3QgbmFtZSBvZiB0aGUgYmFzZU5hbWUncwogICAgICAgICAgICAgICAgICAgIC8vbW9kdWxlLiBGb3IgaW5zdGFuY2UsIGJhc2VOYW1lIG9mICdvbmUvdHdvL3RocmVlJywgbWFwcyB0bwogICAgICAgICAgICAgICAgICAgIC8vJ29uZS90d28vdGhyZWUuanMnLCBidXQgd2Ugd2FudCB0aGUgZGlyZWN0b3J5LCAnb25lL3R3bycgZm9yCiAgICAgICAgICAgICAgICAgICAgLy90aGlzIG5vcm1hbGl6YXRpb24uCiAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZEJhc2VQYXJ0cyA9IGJhc2VQYXJ0cy5zbGljZSgwLCBiYXNlUGFydHMubGVuZ3RoIC0gMSk7CiAgICAgICAgICAgICAgICAgICAgbmFtZSA9IG5vcm1hbGl6ZWRCYXNlUGFydHMuY29uY2F0KG5hbWUpOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIHRyaW1Eb3RzKG5hbWUpOwogICAgICAgICAgICAgICAgbmFtZSA9IG5hbWUuam9pbignLycpOwogICAgICAgICAgICB9CgogICAgICAgICAgICAvL0FwcGx5IG1hcCBjb25maWcgaWYgYXZhaWxhYmxlLgogICAgICAgICAgICBpZiAoYXBwbHlNYXAgJiYgbWFwICYmIChiYXNlUGFydHMgfHwgc3Rhck1hcCkpIHsKICAgICAgICAgICAgICAgIG5hbWVQYXJ0cyA9IG5hbWUuc3BsaXQoJy8nKTsKCiAgICAgICAgICAgICAgICBvdXRlckxvb3A6IGZvciAoaSA9IG5hbWVQYXJ0cy5sZW5ndGg7IGkgPiAwOyBpIC09IDEpIHsKICAgICAgICAgICAgICAgICAgICBuYW1lU2VnbWVudCA9IG5hbWVQYXJ0cy5zbGljZSgwLCBpKS5qb2luKCcvJyk7CgogICAgICAgICAgICAgICAgICAgIGlmIChiYXNlUGFydHMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy9GaW5kIHRoZSBsb25nZXN0IGJhc2VOYW1lIHNlZ21lbnQgbWF0Y2ggaW4gdGhlIGNvbmZpZy4KICAgICAgICAgICAgICAgICAgICAgICAgLy9TbywgZG8gam9pbnMgb24gdGhlIGJpZ2dlc3QgdG8gc21hbGxlc3QgbGVuZ3RocyBvZiBiYXNlUGFydHMuCiAgICAgICAgICAgICAgICAgICAgICAgIGZvciAoaiA9IGJhc2VQYXJ0cy5sZW5ndGg7IGogPiAwOyBqIC09IDEpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1hcFZhbHVlID0gZ2V0T3duKG1hcCwgYmFzZVBhcnRzLnNsaWNlKDAsIGopLmpvaW4oJy8nKSk7CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9iYXNlTmFtZSBzZWdtZW50IGhhcyBjb25maWcsIGZpbmQgaWYgaXQgaGFzIG9uZSBmb3IKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vdGhpcyBuYW1lLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG1hcFZhbHVlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbWFwVmFsdWUgPSBnZXRPd24obWFwVmFsdWUsIG5hbWVTZWdtZW50KTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAobWFwVmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9NYXRjaCwgdXBkYXRlIG5hbWUgdG8gdGhlIG5ldyB2YWx1ZS4KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZm91bmRNYXAgPSBtYXBWYWx1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZm91bmRJID0gaTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWsgb3V0ZXJMb29wOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgLy9DaGVjayBmb3IgYSBzdGFyIG1hcCBtYXRjaCwgYnV0IGp1c3QgaG9sZCBvbiB0byBpdCwKICAgICAgICAgICAgICAgICAgICAvL2lmIHRoZXJlIGlzIGEgc2hvcnRlciBzZWdtZW50IG1hdGNoIGxhdGVyIGluIGEgbWF0Y2hpbmcKICAgICAgICAgICAgICAgICAgICAvL2NvbmZpZywgdGhlbiBmYXZvciBvdmVyIHRoaXMgc3RhciBtYXAuCiAgICAgICAgICAgICAgICAgICAgaWYgKCFmb3VuZFN0YXJNYXAgJiYgc3Rhck1hcCAmJiBnZXRPd24oc3Rhck1hcCwgbmFtZVNlZ21lbnQpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGZvdW5kU3Rhck1hcCA9IGdldE93bihzdGFyTWFwLCBuYW1lU2VnbWVudCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHN0YXJJID0gaTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgaWYgKCFmb3VuZE1hcCAmJiBmb3VuZFN0YXJNYXApIHsKICAgICAgICAgICAgICAgICAgICBmb3VuZE1hcCA9IGZvdW5kU3Rhck1hcDsKICAgICAgICAgICAgICAgICAgICBmb3VuZEkgPSBzdGFySTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBpZiAoZm91bmRNYXApIHsKICAgICAgICAgICAgICAgICAgICBuYW1lUGFydHMuc3BsaWNlKDAsIGZvdW5kSSwgZm91bmRNYXApOwogICAgICAgICAgICAgICAgICAgIG5hbWUgPSBuYW1lUGFydHMuam9pbignLycpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CgogICAgICAgICAgICAvLyBJZiB0aGUgbmFtZSBwb2ludHMgdG8gYSBwYWNrYWdlJ3MgbmFtZSwgdXNlCiAgICAgICAgICAgIC8vIHRoZSBwYWNrYWdlIG1haW4gaW5zdGVhZC4KICAgICAgICAgICAgcGtnTWFpbiA9IGdldE93bihjb25maWcucGtncywgbmFtZSk7CgogICAgICAgICAgICByZXR1cm4gcGtnTWFpbiA/IHBrZ01haW4gOiBuYW1lOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcmVtb3ZlU2NyaXB0KG5hbWUpIHsKICAgICAgICAgICAgaWYgKGlzQnJvd3NlcikgewogICAgICAgICAgICAgICAgZWFjaChzY3JpcHRzKCksIGZ1bmN0aW9uIChzY3JpcHROb2RlKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHNjcmlwdE5vZGUuZ2V0QXR0cmlidXRlKCdkYXRhLXJlcXVpcmVtb2R1bGUnKSA9PT0gbmFtZSAmJgogICAgICAgICAgICAgICAgICAgICAgICAgICAgc2NyaXB0Tm9kZS5nZXRBdHRyaWJ1dGUoJ2RhdGEtcmVxdWlyZWNvbnRleHQnKSA9PT0gY29udGV4dC5jb250ZXh0TmFtZSkgewogICAgICAgICAgICAgICAgICAgICAgICBzY3JpcHROb2RlLnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQoc2NyaXB0Tm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBoYXNQYXRoRmFsbGJhY2soaWQpIHsKICAgICAgICAgICAgdmFyIHBhdGhDb25maWcgPSBnZXRPd24oY29uZmlnLnBhdGhzLCBpZCk7CiAgICAgICAgICAgIGlmIChwYXRoQ29uZmlnICYmIGlzQXJyYXkocGF0aENvbmZpZykgJiYgcGF0aENvbmZpZy5sZW5ndGggPiAxKSB7CiAgICAgICAgICAgICAgICAvL1BvcCBvZmYgdGhlIGZpcnN0IGFycmF5IHZhbHVlLCBzaW5jZSBpdCBmYWlsZWQsIGFuZAogICAgICAgICAgICAgICAgLy9yZXRyeQogICAgICAgICAgICAgICAgcGF0aENvbmZpZy5zaGlmdCgpOwogICAgICAgICAgICAgICAgY29udGV4dC5yZXF1aXJlLnVuZGVmKGlkKTsKCiAgICAgICAgICAgICAgICAvL0N1c3RvbSByZXF1aXJlIHRoYXQgZG9lcyBub3QgZG8gbWFwIHRyYW5zbGF0aW9uLCBzaW5jZQogICAgICAgICAgICAgICAgLy9JRCBpcyAiYWJzb2x1dGUiLCBhbHJlYWR5IG1hcHBlZC9yZXNvbHZlZC4KICAgICAgICAgICAgICAgIGNvbnRleHQubWFrZVJlcXVpcmUobnVsbCwgewogICAgICAgICAgICAgICAgICAgIHNraXBNYXA6IHRydWUKICAgICAgICAgICAgICAgIH0pKFtpZF0pOwoKICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvL1R1cm5zIGEgcGx1Z2luIXJlc291cmNlIHRvIFtwbHVnaW4sIHJlc291cmNlXQogICAgICAgIC8vd2l0aCB0aGUgcGx1Z2luIGJlaW5nIHVuZGVmaW5lZCBpZiB0aGUgbmFtZQogICAgICAgIC8vZGlkIG5vdCBoYXZlIGEgcGx1Z2luIHByZWZpeC4KICAgICAgICBmdW5jdGlvbiBzcGxpdFByZWZpeChuYW1lKSB7CiAgICAgICAgICAgIHZhciBwcmVmaXgsCiAgICAgICAgICAgICAgICBpbmRleCA9IG5hbWUgPyBuYW1lLmluZGV4T2YoJyEnKSA6IC0xOwogICAgICAgICAgICBpZiAoaW5kZXggPiAtMSkgewogICAgICAgICAgICAgICAgcHJlZml4ID0gbmFtZS5zdWJzdHJpbmcoMCwgaW5kZXgpOwogICAgICAgICAgICAgICAgbmFtZSA9IG5hbWUuc3Vic3RyaW5nKGluZGV4ICsgMSwgbmFtZS5sZW5ndGgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBbcHJlZml4LCBuYW1lXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBtb2R1bGUgbWFwcGluZyB0aGF0IGluY2x1ZGVzIHBsdWdpbiBwcmVmaXgsIG1vZHVsZQogICAgICAgICAqIG5hbWUsIGFuZCBwYXRoLiBJZiBwYXJlbnRNb2R1bGVNYXAgaXMgcHJvdmlkZWQgaXQgd2lsbAogICAgICAgICAqIGFsc28gbm9ybWFsaXplIHRoZSBuYW1lIHZpYSByZXF1aXJlLm5vcm1hbGl6ZSgpCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1N0cmluZ30gbmFtZSB0aGUgbW9kdWxlIG5hbWUKICAgICAgICAgKiBAcGFyYW0ge1N0cmluZ30gW3BhcmVudE1vZHVsZU1hcF0gcGFyZW50IG1vZHVsZSBtYXAKICAgICAgICAgKiBmb3IgdGhlIG1vZHVsZSBuYW1lLCB1c2VkIHRvIHJlc29sdmUgcmVsYXRpdmUgbmFtZXMuCiAgICAgICAgICogQHBhcmFtIHtCb29sZWFufSBpc05vcm1hbGl6ZWQ6IGlzIHRoZSBJRCBhbHJlYWR5IG5vcm1hbGl6ZWQuCiAgICAgICAgICogVGhpcyBpcyB0cnVlIGlmIHRoaXMgY2FsbCBpcyBkb25lIGZvciBhIGRlZmluZSgpIG1vZHVsZSBJRC4KICAgICAgICAgKiBAcGFyYW0ge0Jvb2xlYW59IGFwcGx5TWFwOiBhcHBseSB0aGUgbWFwIGNvbmZpZyB0byB0aGUgSUQuCiAgICAgICAgICogU2hvdWxkIG9ubHkgYmUgdHJ1ZSBpZiB0aGlzIG1hcCBpcyBmb3IgYSBkZXBlbmRlbmN5LgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYWtlTW9kdWxlTWFwKG5hbWUsIHBhcmVudE1vZHVsZU1hcCwgaXNOb3JtYWxpemVkLCBhcHBseU1hcCkgewogICAgICAgICAgICB2YXIgdXJsLCBwbHVnaW5Nb2R1bGUsIHN1ZmZpeCwgbmFtZVBhcnRzLAogICAgICAgICAgICAgICAgcHJlZml4ID0gbnVsbCwKICAgICAgICAgICAgICAgIHBhcmVudE5hbWUgPSBwYXJlbnRNb2R1bGVNYXAgPyBwYXJlbnRNb2R1bGVNYXAubmFtZSA6IG51bGwsCiAgICAgICAgICAgICAgICBvcmlnaW5hbE5hbWUgPSBuYW1lLAogICAgICAgICAgICAgICAgaXNEZWZpbmUgPSB0cnVlLAogICAgICAgICAgICAgICAgbm9ybWFsaXplZE5hbWUgPSAnJzsKCiAgICAgICAgICAgIC8vSWYgbm8gbmFtZSwgdGhlbiBpdCBtZWFucyBpdCBpcyBhIHJlcXVpcmUgY2FsbCwgZ2VuZXJhdGUgYW4KICAgICAgICAgICAgLy9pbnRlcm5hbCBuYW1lLgogICAgICAgICAgICBpZiAoIW5hbWUpIHsKICAgICAgICAgICAgICAgIGlzRGVmaW5lID0gZmFsc2U7CiAgICAgICAgICAgICAgICBuYW1lID0gJ19AcicgKyAocmVxdWlyZUNvdW50ZXIgKz0gMSk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIG5hbWVQYXJ0cyA9IHNwbGl0UHJlZml4KG5hbWUpOwogICAgICAgICAgICBwcmVmaXggPSBuYW1lUGFydHNbMF07CiAgICAgICAgICAgIG5hbWUgPSBuYW1lUGFydHNbMV07CgogICAgICAgICAgICBpZiAocHJlZml4KSB7CiAgICAgICAgICAgICAgICBwcmVmaXggPSBub3JtYWxpemUocHJlZml4LCBwYXJlbnROYW1lLCBhcHBseU1hcCk7CiAgICAgICAgICAgICAgICBwbHVnaW5Nb2R1bGUgPSBnZXRPd24oZGVmaW5lZCwgcHJlZml4KTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgLy9BY2NvdW50IGZvciByZWxhdGl2ZSBwYXRocyBpZiB0aGVyZSBpcyBhIGJhc2UgbmFtZS4KICAgICAgICAgICAgaWYgKG5hbWUpIHsKICAgICAgICAgICAgICAgIGlmIChwcmVmaXgpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoaXNOb3JtYWxpemVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIG5vcm1hbGl6ZWROYW1lID0gbmFtZTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgaWYgKHBsdWdpbk1vZHVsZSAmJiBwbHVnaW5Nb2R1bGUubm9ybWFsaXplKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vUGx1Z2luIGlzIGxvYWRlZCwgdXNlIGl0cyBub3JtYWxpemUgbWV0aG9kLgogICAgICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkTmFtZSA9IHBsdWdpbk1vZHVsZS5ub3JtYWxpemUobmFtZSwgZnVuY3Rpb24gKG5hbWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBub3JtYWxpemUobmFtZSwgcGFyZW50TmFtZSwgYXBwbHlNYXApOwogICAgICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBJZiBuZXN0ZWQgcGx1Z2luIHJlZmVyZW5jZXMsIHRoZW4gZG8gbm90IHRyeSB0bwogICAgICAgICAgICAgICAgICAgICAgICAvLyBub3JtYWxpemUsIGFzIGl0IHdpbGwgbm90IG5vcm1hbGl6ZSBjb3JyZWN0bHkuIFRoaXMKICAgICAgICAgICAgICAgICAgICAgICAgLy8gcGxhY2VzIGEgcmVzdHJpY3Rpb24gb24gcmVzb3VyY2VJZHMsIGFuZCB0aGUgbG9uZ2VyCiAgICAgICAgICAgICAgICAgICAgICAgIC8vIHRlcm0gc29sdXRpb24gaXMgbm90IHRvIG5vcm1hbGl6ZSB1bnRpbCBwbHVnaW5zIGFyZQogICAgICAgICAgICAgICAgICAgICAgICAvLyBsb2FkZWQgYW5kIGFsbCBub3JtYWxpemF0aW9ucyB0byBhbGxvdyBmb3IgYXN5bmMKICAgICAgICAgICAgICAgICAgICAgICAgLy8gbG9hZGluZyBvZiBhIGxvYWRlciBwbHVnaW4uIEJ1dCBmb3Igbm93LCBmaXhlcyB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgLy8gY29tbW9uIHVzZXMuIERldGFpbHMgaW4gIzExMzEKICAgICAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZE5hbWUgPSBuYW1lLmluZGV4T2YoJyEnKSA9PT0gLTEgPwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5vcm1hbGl6ZShuYW1lLCBwYXJlbnROYW1lLCBhcHBseU1hcCkgOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5hbWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAvL0EgcmVndWxhciBtb2R1bGUuCiAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZE5hbWUgPSBub3JtYWxpemUobmFtZSwgcGFyZW50TmFtZSwgYXBwbHlNYXApOwoKICAgICAgICAgICAgICAgICAgICAvL05vcm1hbGl6ZWQgbmFtZSBtYXkgYmUgYSBwbHVnaW4gSUQgZHVlIHRvIG1hcCBjb25maWcKICAgICAgICAgICAgICAgICAgICAvL2FwcGxpY2F0aW9uIGluIG5vcm1hbGl6ZS4gVGhlIG1hcCBjb25maWcgdmFsdWVzIG11c3QKICAgICAgICAgICAgICAgICAgICAvL2FscmVhZHkgYmUgbm9ybWFsaXplZCwgc28gZG8gbm90IG5lZWQgdG8gcmVkbyB0aGF0IHBhcnQuCiAgICAgICAgICAgICAgICAgICAgbmFtZVBhcnRzID0gc3BsaXRQcmVmaXgobm9ybWFsaXplZE5hbWUpOwogICAgICAgICAgICAgICAgICAgIHByZWZpeCA9IG5hbWVQYXJ0c1swXTsKICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkTmFtZSA9IG5hbWVQYXJ0c1sxXTsKICAgICAgICAgICAgICAgICAgICBpc05vcm1hbGl6ZWQgPSB0cnVlOwoKICAgICAgICAgICAgICAgICAgICB1cmwgPSBjb250ZXh0Lm5hbWVUb1VybChub3JtYWxpemVkTmFtZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIC8vSWYgdGhlIGlkIGlzIGEgcGx1Z2luIGlkIHRoYXQgY2Fubm90IGJlIGRldGVybWluZWQgaWYgaXQgbmVlZHMKICAgICAgICAgICAgLy9ub3JtYWxpemF0aW9uLCBzdGFtcCBpdCB3aXRoIGEgdW5pcXVlIElEIHNvIHR3byBtYXRjaGluZyByZWxhdGl2ZQogICAgICAgICAgICAvL2lkcyB0aGF0IG1heSBjb25mbGljdCBjYW4gYmUgc2VwYXJhdGUuCiAgICAgICAgICAgIHN1ZmZpeCA9IHByZWZpeCAmJiAhcGx1Z2luTW9kdWxlICYmICFpc05vcm1hbGl6ZWQgPwogICAgICAgICAgICAgICAgICAgICAnX3Vubm9ybWFsaXplZCcgKyAodW5ub3JtYWxpemVkQ291bnRlciArPSAxKSA6CiAgICAgICAgICAgICAgICAgICAgICcnOwoKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHByZWZpeDogcHJlZml4LAogICAgICAgICAgICAgICAgbmFtZTogbm9ybWFsaXplZE5hbWUsCiAgICAgICAgICAgICAgICBwYXJlbnRNYXA6IHBhcmVudE1vZHVsZU1hcCwKICAgICAgICAgICAgICAgIHVubm9ybWFsaXplZDogISFzdWZmaXgsCiAgICAgICAgICAgICAgICB1cmw6IHVybCwKICAgICAgICAgICAgICAgIG9yaWdpbmFsTmFtZTogb3JpZ2luYWxOYW1lLAogICAgICAgICAgICAgICAgaXNEZWZpbmU6IGlzRGVmaW5lLAogICAgICAgICAgICAgICAgaWQ6IChwcmVmaXggPwogICAgICAgICAgICAgICAgICAgICAgICBwcmVmaXggKyAnIScgKyBub3JtYWxpemVkTmFtZSA6CiAgICAgICAgICAgICAgICAgICAgICAgIG5vcm1hbGl6ZWROYW1lKSArIHN1ZmZpeAogICAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gZ2V0TW9kdWxlKGRlcE1hcCkgewogICAgICAgICAgICB2YXIgaWQgPSBkZXBNYXAuaWQsCiAgICAgICAgICAgICAgICBtb2QgPSBnZXRPd24ocmVnaXN0cnksIGlkKTsKCiAgICAgICAgICAgIGlmICghbW9kKSB7CiAgICAgICAgICAgICAgICBtb2QgPSByZWdpc3RyeVtpZF0gPSBuZXcgY29udGV4dC5Nb2R1bGUoZGVwTWFwKTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgcmV0dXJuIG1vZDsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIG9uKGRlcE1hcCwgbmFtZSwgZm4pIHsKICAgICAgICAgICAgdmFyIGlkID0gZGVwTWFwLmlkLAogICAgICAgICAgICAgICAgbW9kID0gZ2V0T3duKHJlZ2lzdHJ5LCBpZCk7CgogICAgICAgICAgICBpZiAoaGFzUHJvcChkZWZpbmVkLCBpZCkgJiYKICAgICAgICAgICAgICAgICAgICAoIW1vZCB8fCBtb2QuZGVmaW5lRW1pdENvbXBsZXRlKSkgewogICAgICAgICAgICAgICAgaWYgKG5hbWUgPT09ICdkZWZpbmVkJykgewogICAgICAgICAgICAgICAgICAgIGZuKGRlZmluZWRbaWRdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIG1vZCA9IGdldE1vZHVsZShkZXBNYXApOwogICAgICAgICAgICAgICAgaWYgKG1vZC5lcnJvciAmJiBuYW1lID09PSAnZXJyb3InKSB7CiAgICAgICAgICAgICAgICAgICAgZm4obW9kLmVycm9yKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgbW9kLm9uKG5hbWUsIGZuKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gb25FcnJvcihlcnIsIGVycmJhY2spIHsKICAgICAgICAgICAgdmFyIGlkcyA9IGVyci5yZXF1aXJlTW9kdWxlcywKICAgICAgICAgICAgICAgIG5vdGlmaWVkID0gZmFsc2U7CgogICAgICAgICAgICBpZiAoZXJyYmFjaykgewogICAgICAgICAgICAgICAgZXJyYmFjayhlcnIpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgZWFjaChpZHMsIGZ1bmN0aW9uIChpZCkgewogICAgICAgICAgICAgICAgICAgIHZhciBtb2QgPSBnZXRPd24ocmVnaXN0cnksIGlkKTsKICAgICAgICAgICAgICAgICAgICBpZiAobW9kKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vU2V0IGVycm9yIG9uIG1vZHVsZSwgc28gaXQgc2tpcHMgdGltZW91dCBjaGVja3MuCiAgICAgICAgICAgICAgICAgICAgICAgIG1vZC5lcnJvciA9IGVycjsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG1vZC5ldmVudHMuZXJyb3IpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5vdGlmaWVkID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1vZC5lbWl0KCdlcnJvcicsIGVycik7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICBpZiAoIW5vdGlmaWVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmVxLm9uRXJyb3IoZXJyKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogSW50ZXJuYWwgbWV0aG9kIHRvIHRyYW5zZmVyIGdsb2JhbFF1ZXVlIGl0ZW1zIHRvIHRoaXMgY29udGV4dCdzCiAgICAgICAgICogZGVmUXVldWUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdGFrZUdsb2JhbFF1ZXVlKCkgewogICAgICAgICAgICAvL1B1c2ggYWxsIHRoZSBnbG9iYWxEZWZRdWV1ZSBpdGVtcyBpbnRvIHRoZSBjb250ZXh0J3MgZGVmUXVldWUKICAgICAgICAgICAgaWYgKGdsb2JhbERlZlF1ZXVlLmxlbmd0aCkgewogICAgICAgICAgICAgICAgZWFjaChnbG9iYWxEZWZRdWV1ZSwgZnVuY3Rpb24ocXVldWVJdGVtKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGlkID0gcXVldWVJdGVtWzBdOwogICAgICAgICAgICAgICAgICAgIGlmICh0eXBlb2YgaWQgPT09ICdzdHJpbmcnKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRleHQuZGVmUXVldWVNYXBbaWRdID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZGVmUXVldWUucHVzaChxdWV1ZUl0ZW0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBnbG9iYWxEZWZRdWV1ZSA9IFtdOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBoYW5kbGVycyA9IHsKICAgICAgICAgICAgJ3JlcXVpcmUnOiBmdW5jdGlvbiAobW9kKSB7CiAgICAgICAgICAgICAgICBpZiAobW9kLnJlcXVpcmUpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbW9kLnJlcXVpcmU7CiAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgIHJldHVybiAobW9kLnJlcXVpcmUgPSBjb250ZXh0Lm1ha2VSZXF1aXJlKG1vZC5tYXApKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgJ2V4cG9ydHMnOiBmdW5jdGlvbiAobW9kKSB7CiAgICAgICAgICAgICAgICBtb2QudXNpbmdFeHBvcnRzID0gdHJ1ZTsKICAgICAgICAgICAgICAgIGlmIChtb2QubWFwLmlzRGVmaW5lKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKG1vZC5leHBvcnRzKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAoZGVmaW5lZFttb2QubWFwLmlkXSA9IG1vZC5leHBvcnRzKTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gKG1vZC5leHBvcnRzID0gZGVmaW5lZFttb2QubWFwLmlkXSA9IHt9KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgICdtb2R1bGUnOiBmdW5jdGlvbiAobW9kKSB7CiAgICAgICAgICAgICAgICBpZiAobW9kLm1vZHVsZSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBtb2QubW9kdWxlOwogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gKG1vZC5tb2R1bGUgPSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlkOiBtb2QubWFwLmlkLAogICAgICAgICAgICAgICAgICAgICAgICB1cmk6IG1vZC5tYXAudXJsLAogICAgICAgICAgICAgICAgICAgICAgICBjb25maWc6IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBnZXRPd24oY29uZmlnLmNvbmZpZywgbW9kLm1hcC5pZCkgfHwge307CiAgICAgICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgICAgIGV4cG9ydHM6IG1vZC5leHBvcnRzIHx8IChtb2QuZXhwb3J0cyA9IHt9KQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfTsKCiAgICAgICAgZnVuY3Rpb24gY2xlYW5SZWdpc3RyeShpZCkgewogICAgICAgICAgICAvL0NsZWFuIHVwIG1hY2hpbmVyeSB1c2VkIGZvciB3YWl0aW5nIG1vZHVsZXMuCiAgICAgICAgICAgIGRlbGV0ZSByZWdpc3RyeVtpZF07CiAgICAgICAgICAgIGRlbGV0ZSBlbmFibGVkUmVnaXN0cnlbaWRdOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gYnJlYWtDeWNsZShtb2QsIHRyYWNlZCwgcHJvY2Vzc2VkKSB7CiAgICAgICAgICAgIHZhciBpZCA9IG1vZC5tYXAuaWQ7CgogICAgICAgICAgICBpZiAobW9kLmVycm9yKSB7CiAgICAgICAgICAgICAgICBtb2QuZW1pdCgnZXJyb3InLCBtb2QuZXJyb3IpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgdHJhY2VkW2lkXSA9IHRydWU7CiAgICAgICAgICAgICAgICBlYWNoKG1vZC5kZXBNYXBzLCBmdW5jdGlvbiAoZGVwTWFwLCBpKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGRlcElkID0gZGVwTWFwLmlkLAogICAgICAgICAgICAgICAgICAgICAgICBkZXAgPSBnZXRPd24ocmVnaXN0cnksIGRlcElkKTsKCiAgICAgICAgICAgICAgICAgICAgLy9Pbmx5IGZvcmNlIHRoaW5ncyB0aGF0IGhhdmUgbm90IGNvbXBsZXRlZAogICAgICAgICAgICAgICAgICAgIC8vYmVpbmcgZGVmaW5lZCwgc28gc3RpbGwgaW4gdGhlIHJlZ2lzdHJ5LAogICAgICAgICAgICAgICAgICAgIC8vYW5kIG9ubHkgaWYgaXQgaGFzIG5vdCBiZWVuIG1hdGNoZWQgdXAKICAgICAgICAgICAgICAgICAgICAvL2luIHRoZSBtb2R1bGUgYWxyZWFkeS4KICAgICAgICAgICAgICAgICAgICBpZiAoZGVwICYmICFtb2QuZGVwTWF0Y2hlZFtpXSAmJiAhcHJvY2Vzc2VkW2RlcElkXSkgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoZ2V0T3duKHRyYWNlZCwgZGVwSWQpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtb2QuZGVmaW5lRGVwKGksIGRlZmluZWRbZGVwSWRdKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1vZC5jaGVjaygpOyAvL3Bhc3MgZmFsc2U/CiAgICAgICAgICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBicmVha0N5Y2xlKGRlcCwgdHJhY2VkLCBwcm9jZXNzZWQpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBwcm9jZXNzZWRbaWRdID0gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gY2hlY2tMb2FkZWQoKSB7CiAgICAgICAgICAgIHZhciBlcnIsIHVzaW5nUGF0aEZhbGxiYWNrLAogICAgICAgICAgICAgICAgd2FpdEludGVydmFsID0gY29uZmlnLndhaXRTZWNvbmRzICogMTAwMCwKICAgICAgICAgICAgICAgIC8vSXQgaXMgcG9zc2libGUgdG8gZGlzYWJsZSB0aGUgd2FpdCBpbnRlcnZhbCBieSB1c2luZyB3YWl0U2Vjb25kcyBvZiAwLgogICAgICAgICAgICAgICAgZXhwaXJlZCA9IHdhaXRJbnRlcnZhbCAmJiAoY29udGV4dC5zdGFydFRpbWUgKyB3YWl0SW50ZXJ2YWwpIDwgbmV3IERhdGUoKS5nZXRUaW1lKCksCiAgICAgICAgICAgICAgICBub0xvYWRzID0gW10sCiAgICAgICAgICAgICAgICByZXFDYWxscyA9IFtdLAogICAgICAgICAgICAgICAgc3RpbGxMb2FkaW5nID0gZmFsc2UsCiAgICAgICAgICAgICAgICBuZWVkQ3ljbGVDaGVjayA9IHRydWU7CgogICAgICAgICAgICAvL0RvIG5vdCBib3RoZXIgaWYgdGhpcyBjYWxsIHdhcyBhIHJlc3VsdCBvZiBhIGN5Y2xlIGJyZWFrLgogICAgICAgICAgICBpZiAoaW5DaGVja0xvYWRlZCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpbkNoZWNrTG9hZGVkID0gdHJ1ZTsKCiAgICAgICAgICAgIC8vRmlndXJlIG91dCB0aGUgc3RhdGUgb2YgYWxsIHRoZSBtb2R1bGVzLgogICAgICAgICAgICBlYWNoUHJvcChlbmFibGVkUmVnaXN0cnksIGZ1bmN0aW9uIChtb2QpIHsKICAgICAgICAgICAgICAgIHZhciBtYXAgPSBtb2QubWFwLAogICAgICAgICAgICAgICAgICAgIG1vZElkID0gbWFwLmlkOwoKICAgICAgICAgICAgICAgIC8vU2tpcCB0aGluZ3MgdGhhdCBhcmUgbm90IGVuYWJsZWQgb3IgaW4gZXJyb3Igc3RhdGUuCiAgICAgICAgICAgICAgICBpZiAoIW1vZC5lbmFibGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIGlmICghbWFwLmlzRGVmaW5lKSB7CiAgICAgICAgICAgICAgICAgICAgcmVxQ2FsbHMucHVzaChtb2QpOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIGlmICghbW9kLmVycm9yKSB7CiAgICAgICAgICAgICAgICAgICAgLy9JZiB0aGUgbW9kdWxlIHNob3VsZCBiZSBleGVjdXRlZCwgYW5kIGl0IGhhcyBub3QKICAgICAgICAgICAgICAgICAgICAvL2JlZW4gaW5pdGVkIGFuZCB0aW1lIGlzIHVwLCByZW1lbWJlciBpdC4KICAgICAgICAgICAgICAgICAgICBpZiAoIW1vZC5pbml0ZWQgJiYgZXhwaXJlZCkgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaGFzUGF0aEZhbGxiYWNrKG1vZElkKSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgdXNpbmdQYXRoRmFsbGJhY2sgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RpbGxMb2FkaW5nID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5vTG9hZHMucHVzaChtb2RJZCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZW1vdmVTY3JpcHQobW9kSWQpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIGlmICghbW9kLmluaXRlZCAmJiBtb2QuZmV0Y2hlZCAmJiBtYXAuaXNEZWZpbmUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgc3RpbGxMb2FkaW5nID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFtYXAucHJlZml4KSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL05vIHJlYXNvbiB0byBrZWVwIGxvb2tpbmcgZm9yIHVuZmluaXNoZWQKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vbG9hZGluZy4gSWYgdGhlIG9ubHkgc3RpbGxMb2FkaW5nIGlzIGEKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vcGx1Z2luIHJlc291cmNlIHRob3VnaCwga2VlcCBnb2luZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vYmVjYXVzZSBpdCBtYXkgYmUgdGhhdCBhIHBsdWdpbiByZXNvdXJjZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9pcyB3YWl0aW5nIG9uIGEgbm9uLXBsdWdpbiBjeWNsZS4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAobmVlZEN5Y2xlQ2hlY2sgPSBmYWxzZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwoKICAgICAgICAgICAgaWYgKGV4cGlyZWQgJiYgbm9Mb2Fkcy5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIC8vSWYgd2FpdCB0aW1lIGV4cGlyZWQsIHRocm93IGVycm9yIG9mIHVubG9hZGVkIG1vZHVsZXMuCiAgICAgICAgICAgICAgICBlcnIgPSBtYWtlRXJyb3IoJ3RpbWVvdXQnLCAnTG9hZCB0aW1lb3V0IGZvciBtb2R1bGVzOiAnICsgbm9Mb2FkcywgbnVsbCwgbm9Mb2Fkcyk7CiAgICAgICAgICAgICAgICBlcnIuY29udGV4dE5hbWUgPSBjb250ZXh0LmNvbnRleHROYW1lOwogICAgICAgICAgICAgICAgcmV0dXJuIG9uRXJyb3IoZXJyKTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgLy9Ob3QgZXhwaXJlZCwgY2hlY2sgZm9yIGEgY3ljbGUuCiAgICAgICAgICAgIGlmIChuZWVkQ3ljbGVDaGVjaykgewogICAgICAgICAgICAgICAgZWFjaChyZXFDYWxscywgZnVuY3Rpb24gKG1vZCkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrQ3ljbGUobW9kLCB7fSwge30pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIC8vSWYgc3RpbGwgd2FpdGluZyBvbiBsb2FkcywgYW5kIHRoZSB3YWl0aW5nIGxvYWQgaXMgc29tZXRoaW5nCiAgICAgICAgICAgIC8vb3RoZXIgdGhhbiBhIHBsdWdpbiByZXNvdXJjZSwgb3IgdGhlcmUgYXJlIHN0aWxsIG91dHN0YW5kaW5nCiAgICAgICAgICAgIC8vc2NyaXB0cywgdGhlbiBqdXN0IHRyeSBiYWNrIGxhdGVyLgogICAgICAgICAgICBpZiAoKCFleHBpcmVkIHx8IHVzaW5nUGF0aEZhbGxiYWNrKSAmJiBzdGlsbExvYWRpbmcpIHsKICAgICAgICAgICAgICAgIC8vU29tZXRoaW5nIGlzIHN0aWxsIHdhaXRpbmcgdG8gbG9hZC4gV2FpdCBmb3IgaXQsIGJ1dCBvbmx5CiAgICAgICAgICAgICAgICAvL2lmIGEgdGltZW91dCBpcyBub3QgYWxyZWFkeSBpbiBlZmZlY3QuCiAgICAgICAgICAgICAgICBpZiAoKGlzQnJvd3NlciB8fCBpc1dlYldvcmtlcikgJiYgIWNoZWNrTG9hZGVkVGltZW91dElkKSB7CiAgICAgICAgICAgICAgICAgICAgY2hlY2tMb2FkZWRUaW1lb3V0SWQgPSBzZXRUaW1lb3V0KGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY2hlY2tMb2FkZWRUaW1lb3V0SWQgPSAwOwogICAgICAgICAgICAgICAgICAgICAgICBjaGVja0xvYWRlZCgpOwogICAgICAgICAgICAgICAgICAgIH0sIDUwKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQoKICAgICAgICAgICAgaW5DaGVja0xvYWRlZCA9IGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgTW9kdWxlID0gZnVuY3Rpb24gKG1hcCkgewogICAgICAgICAgICB0aGlzLmV2ZW50cyA9IGdldE93bih1bmRlZkV2ZW50cywgbWFwLmlkKSB8fCB7fTsKICAgICAgICAgICAgdGhpcy5tYXAgPSBtYXA7CiAgICAgICAgICAgIHRoaXMuc2hpbSA9IGdldE93bihjb25maWcuc2hpbSwgbWFwLmlkKTsKICAgICAgICAgICAgdGhpcy5kZXBFeHBvcnRzID0gW107CiAgICAgICAgICAgIHRoaXMuZGVwTWFwcyA9IFtdOwogICAgICAgICAgICB0aGlzLmRlcE1hdGNoZWQgPSBbXTsKICAgICAgICAgICAgdGhpcy5wbHVnaW5NYXBzID0ge307CiAgICAgICAgICAgIHRoaXMuZGVwQ291bnQgPSAwOwoKICAgICAgICAgICAgLyogdGhpcy5leHBvcnRzIHRoaXMuZmFjdG9yeQogICAgICAgICAgICAgICB0aGlzLmRlcE1hcHMgPSBbXSwKICAgICAgICAgICAgICAgdGhpcy5lbmFibGVkLCB0aGlzLmZldGNoZWQKICAgICAgICAgICAgKi8KICAgICAgICB9OwoKICAgICAgICBNb2R1bGUucHJvdG90eXBlID0gewogICAgICAgICAgICBpbml0OiBmdW5jdGlvbiAoZGVwTWFwcywgZmFjdG9yeSwgZXJyYmFjaywgb3B0aW9ucykgewogICAgICAgICAgICAgICAgb3B0aW9ucyA9IG9wdGlvbnMgfHwge307CgogICAgICAgICAgICAgICAgLy9EbyBub3QgZG8gbW9yZSBpbml0cyBpZiBhbHJlYWR5IGRvbmUuIENhbiBoYXBwZW4gaWYgdGhlcmUKICAgICAgICAgICAgICAgIC8vYXJlIG11bHRpcGxlIGRlZmluZSBjYWxscyBmb3IgdGhlIHNhbWUgbW9kdWxlLiBUaGF0IGlzIG5vdAogICAgICAgICAgICAgICAgLy9hIG5vcm1hbCwgY29tbW9uIGNhc2UsIGJ1dCBpdCBpcyBhbHNvIG5vdCB1bmV4cGVjdGVkLgogICAgICAgICAgICAgICAgaWYgKHRoaXMuaW5pdGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIHRoaXMuZmFjdG9yeSA9IGZhY3Rvcnk7CgogICAgICAgICAgICAgICAgaWYgKGVycmJhY2spIHsKICAgICAgICAgICAgICAgICAgICAvL1JlZ2lzdGVyIGZvciBlcnJvcnMgb24gdGhpcyBtb2R1bGUuCiAgICAgICAgICAgICAgICAgICAgdGhpcy5vbignZXJyb3InLCBlcnJiYWNrKTsKICAgICAgICAgICAgICAgIH0gZWxzZSBpZiAodGhpcy5ldmVudHMuZXJyb3IpIHsKICAgICAgICAgICAgICAgICAgICAvL0lmIG5vIGVycmJhY2sgYWxyZWFkeSwgYnV0IHRoZXJlIGFyZSBlcnJvciBsaXN0ZW5lcnMKICAgICAgICAgICAgICAgICAgICAvL29uIHRoaXMgbW9kdWxlLCBzZXQgdXAgYW4gZXJyYmFjayB0byBwYXNzIHRvIHRoZSBkZXBzLgogICAgICAgICAgICAgICAgICAgIGVycmJhY2sgPSBiaW5kKHRoaXMsIGZ1bmN0aW9uIChlcnIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5lbWl0KCdlcnJvcicsIGVycik7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgLy9EbyBhIGNvcHkgb2YgdGhlIGRlcGVuZGVuY3kgYXJyYXksIHNvIHRoYXQKICAgICAgICAgICAgICAgIC8vc291cmNlIGlucHV0cyBhcmUgbm90IG1vZGlmaWVkLiBGb3IgZXhhbXBsZQogICAgICAgICAgICAgICAgLy8ic2hpbSIgZGVwcyBhcmUgcGFzc2VkIGluIGhlcmUgZGlyZWN0bHksIGFuZAogICAgICAgICAgICAgICAgLy9kb2luZyBhIGRpcmVjdCBtb2RpZmljYXRpb24gb2YgdGhlIGRlcE1hcHMgYXJyYXkKICAgICAgICAgICAgICAgIC8vd291bGQgYWZmZWN0IHRoYXQgY29uZmlnLgogICAgICAgICAgICAgICAgdGhpcy5kZXBNYXBzID0gZGVwTWFwcyAmJiBkZXBNYXBzLnNsaWNlKDApOwoKICAgICAgICAgICAgICAgIHRoaXMuZXJyYmFjayA9IGVycmJhY2s7CgogICAgICAgICAgICAgICAgLy9JbmRpY2F0ZSB0aGlzIG1vZHVsZSBoYXMgYmUgaW5pdGlhbGl6ZWQKICAgICAgICAgICAgICAgIHRoaXMuaW5pdGVkID0gdHJ1ZTsKCiAgICAgICAgICAgICAgICB0aGlzLmlnbm9yZSA9IG9wdGlvbnMuaWdub3JlOwoKICAgICAgICAgICAgICAgIC8vQ291bGQgaGF2ZSBvcHRpb24gdG8gaW5pdCB0aGlzIG1vZHVsZSBpbiBlbmFibGVkIG1vZGUsCiAgICAgICAgICAgICAgICAvL29yIGNvdWxkIGhhdmUgYmVlbiBwcmV2aW91c2x5IG1hcmtlZCBhcyBlbmFibGVkLiBIb3dldmVyLAogICAgICAgICAgICAgICAgLy90aGUgZGVwZW5kZW5jaWVzIGFyZSBub3Qga25vd24gdW50aWwgaW5pdCBpcyBjYWxsZWQuIFNvCiAgICAgICAgICAgICAgICAvL2lmIGVuYWJsZWQgcHJldmlvdXNseSwgbm93IHRyaWdnZXIgZGVwZW5kZW5jaWVzIGFzIGVuYWJsZWQuCiAgICAgICAgICAgICAgICBpZiAob3B0aW9ucy5lbmFibGVkIHx8IHRoaXMuZW5hYmxlZCkgewogICAgICAgICAgICAgICAgICAgIC8vRW5hYmxlIHRoaXMgbW9kdWxlIGFuZCBkZXBlbmRlbmNpZXMuCiAgICAgICAgICAgICAgICAgICAgLy9XaWxsIGNhbGwgdGhpcy5jaGVjaygpCiAgICAgICAgICAgICAgICAgICAgdGhpcy5lbmFibGUoKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5jaGVjaygpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAoKICAgICAgICAgICAgZGVmaW5lRGVwOiBmdW5jdGlvbiAoaSwgZGVwRXhwb3J0cykgewogICAgICAgICAgICAgICAgLy9CZWNhdXNlIG9mIGN5Y2xlcywgZGVmaW5lZCBjYWxsYmFjayBmb3IgYSBnaXZlbgogICAgICAgICAgICAgICAgLy9leHBvcnQgY2FuIGJlIGNhbGxlZCBtb3JlIHRoYW4gb25jZS4KICAgICAgICAgICAgICAgIGlmICghdGhpcy5kZXBNYXRjaGVkW2ldKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5kZXBNYXRjaGVkW2ldID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB0aGlzLmRlcENvdW50IC09IDE7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5kZXBFeHBvcnRzW2ldID0gZGVwRXhwb3J0czsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIGZldGNoOiBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5mZXRjaGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5mZXRjaGVkID0gdHJ1ZTsKCiAgICAgICAgICAgICAgICBjb250ZXh0LnN0YXJ0VGltZSA9IChuZXcgRGF0ZSgpKS5nZXRUaW1lKCk7CgogICAgICAgICAgICAgICAgdmFyIG1hcCA9IHRoaXMubWFwOwoKICAgICAgICAgICAgICAgIC8vSWYgdGhlIG1hbmFnZXIgaXMgZm9yIGEgcGx1Z2luIG1hbmFnZWQgcmVzb3VyY2UsCiAgICAgICAgICAgICAgICAvL2FzayB0aGUgcGx1Z2luIHRvIGxvYWQgaXQgbm93LgogICAgICAgICAgICAgICAgaWYgKHRoaXMuc2hpbSkgewogICAgICAgICAgICAgICAgICAgIGNvbnRleHQubWFrZVJlcXVpcmUodGhpcy5tYXAsIHsKICAgICAgICAgICAgICAgICAgICAgICAgZW5hYmxlQnVpbGRDYWxsYmFjazogdHJ1ZQogICAgICAgICAgICAgICAgICAgIH0pKHRoaXMuc2hpbS5kZXBzIHx8IFtdLCBiaW5kKHRoaXMsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG1hcC5wcmVmaXggPyB0aGlzLmNhbGxQbHVnaW4oKSA6IHRoaXMubG9hZCgpOwogICAgICAgICAgICAgICAgICAgIH0pKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgLy9SZWd1bGFyIGRlcGVuZGVuY3kuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG1hcC5wcmVmaXggPyB0aGlzLmNhbGxQbHVnaW4oKSA6IHRoaXMubG9hZCgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAoKICAgICAgICAgICAgbG9hZDogZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdmFyIHVybCA9IHRoaXMubWFwLnVybDsKCiAgICAgICAgICAgICAgICAvL1JlZ3VsYXIgZGVwZW5kZW5jeS4KICAgICAgICAgICAgICAgIGlmICghdXJsRmV0Y2hlZFt1cmxdKSB7CiAgICAgICAgICAgICAgICAgICAgdXJsRmV0Y2hlZFt1cmxdID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICBjb250ZXh0LmxvYWQodGhpcy5tYXAuaWQsIHVybCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sCgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQ2hlY2tzIGlmIHRoZSBtb2R1bGUgaXMgcmVhZHkgdG8gZGVmaW5lIGl0c2VsZiwgYW5kIGlmIHNvLAogICAgICAgICAgICAgKiBkZWZpbmUgaXQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBjaGVjazogZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgaWYgKCF0aGlzLmVuYWJsZWQgfHwgdGhpcy5lbmFibGluZykgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICB2YXIgZXJyLCBjanNNb2R1bGUsCiAgICAgICAgICAgICAgICAgICAgaWQgPSB0aGlzLm1hcC5pZCwKICAgICAgICAgICAgICAgICAgICBkZXBFeHBvcnRzID0gdGhpcy5kZXBFeHBvcnRzLAogICAgICAgICAgICAgICAgICAgIGV4cG9ydHMgPSB0aGlzLmV4cG9ydHMsCiAgICAgICAgICAgICAgICAgICAgZmFjdG9yeSA9IHRoaXMuZmFjdG9yeTsKCiAgICAgICAgICAgICAgICBpZiAoIXRoaXMuaW5pdGVkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gT25seSBmZXRjaCBpZiBub3QgYWxyZWFkeSBpbiB0aGUgZGVmUXVldWUuCiAgICAgICAgICAgICAgICAgICAgaWYgKCFoYXNQcm9wKGNvbnRleHQuZGVmUXVldWVNYXAsIGlkKSkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmZldGNoKCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSBlbHNlIGlmICh0aGlzLmVycm9yKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5lbWl0KCdlcnJvcicsIHRoaXMuZXJyb3IpOwogICAgICAgICAgICAgICAgfSBlbHNlIGlmICghdGhpcy5kZWZpbmluZykgewogICAgICAgICAgICAgICAgICAgIC8vVGhlIGZhY3RvcnkgY291bGQgdHJpZ2dlciBhbm90aGVyIHJlcXVpcmUgY2FsbAogICAgICAgICAgICAgICAgICAgIC8vdGhhdCB3b3VsZCByZXN1bHQgaW4gY2hlY2tpbmcgdGhpcyBtb2R1bGUgdG8KICAgICAgICAgICAgICAgICAgICAvL2RlZmluZSBpdHNlbGYgYWdhaW4uIElmIGFscmVhZHkgaW4gdGhlIHByb2Nlc3MKICAgICAgICAgICAgICAgICAgICAvL29mIGRvaW5nIHRoYXQsIHNraXAgdGhpcyB3b3JrLgogICAgICAgICAgICAgICAgICAgIHRoaXMuZGVmaW5pbmcgPSB0cnVlOwoKICAgICAgICAgICAgICAgICAgICBpZiAodGhpcy5kZXBDb3VudCA8IDEgJiYgIXRoaXMuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaXNGdW5jdGlvbihmYWN0b3J5KSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9JZiB0aGVyZSBpcyBhbiBlcnJvciBsaXN0ZW5lciwgZmF2b3IgcGFzc2luZwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy90byB0aGF0IGluc3RlYWQgb2YgdGhyb3dpbmcgYW4gZXJyb3IuIEhvd2V2ZXIsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL29ubHkgZG8gaXQgZm9yIGRlZmluZSgpJ2QgIG1vZHVsZXMuIHJlcXVpcmUKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vZXJyYmFja3Mgc2hvdWxkIG5vdCBiZSBjYWxsZWQgZm9yIGZhaWx1cmVzIGluCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL3RoZWlyIGNhbGxiYWNrcyAoIzY5OSkuIEhvd2V2ZXIgaWYgYSBnbG9iYWwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vb25FcnJvciBpcyBzZXQsIHVzZSB0aGF0LgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCh0aGlzLmV2ZW50cy5lcnJvciAmJiB0aGlzLm1hcC5pc0RlZmluZSkgfHwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXEub25FcnJvciAhPT0gZGVmYXVsdE9uRXJyb3IpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBleHBvcnRzID0gY29udGV4dC5leGVjQ2IoaWQsIGZhY3RvcnksIGRlcEV4cG9ydHMsIGV4cG9ydHMpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZXJyID0gZTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGV4cG9ydHMgPSBjb250ZXh0LmV4ZWNDYihpZCwgZmFjdG9yeSwgZGVwRXhwb3J0cywgZXhwb3J0cyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gRmF2b3IgcmV0dXJuIHZhbHVlIG92ZXIgZXhwb3J0cy4gSWYgbm9kZS9janMgaW4gcGxheSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIHRoZW4gd2lsbCBub3QgaGF2ZSBhIHJldHVybiB2YWx1ZSBhbnl3YXkuIEZhdm9yCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBtb2R1bGUuZXhwb3J0cyBhc3NpZ25tZW50IG92ZXIgZXhwb3J0cyBvYmplY3QuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAodGhpcy5tYXAuaXNEZWZpbmUgJiYgZXhwb3J0cyA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY2pzTW9kdWxlID0gdGhpcy5tb2R1bGU7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGNqc01vZHVsZSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBleHBvcnRzID0gY2pzTW9kdWxlLmV4cG9ydHM7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSBlbHNlIGlmICh0aGlzLnVzaW5nRXhwb3J0cykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL2V4cG9ydHMgYWxyZWFkeSBzZXQgdGhlIGRlZmluZWQgdmFsdWUuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGV4cG9ydHMgPSB0aGlzLmV4cG9ydHM7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChlcnIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlcnIucmVxdWlyZU1hcCA9IHRoaXMubWFwOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVyci5yZXF1aXJlTW9kdWxlcyA9IHRoaXMubWFwLmlzRGVmaW5lID8gW3RoaXMubWFwLmlkXSA6IG51bGw7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZXJyLnJlcXVpcmVUeXBlID0gdGhpcy5tYXAuaXNEZWZpbmUgPyAnZGVmaW5lJyA6ICdyZXF1aXJlJzsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gb25FcnJvcigodGhpcy5lcnJvciA9IGVycikpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vSnVzdCBhIGxpdGVyYWwgdmFsdWUKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGV4cG9ydHMgPSBmYWN0b3J5OwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmV4cG9ydHMgPSBleHBvcnRzOwoKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMubWFwLmlzRGVmaW5lICYmICF0aGlzLmlnbm9yZSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgZGVmaW5lZFtpZF0gPSBleHBvcnRzOwoKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChyZXEub25SZXNvdXJjZUxvYWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YXIgcmVzTG9hZE1hcHMgPSBbXTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlYWNoKHRoaXMuZGVwTWFwcywgZnVuY3Rpb24gKGRlcE1hcCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXNMb2FkTWFwcy5wdXNoKGRlcE1hcC5ub3JtYWxpemVkTWFwIHx8IGRlcE1hcCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVxLm9uUmVzb3VyY2VMb2FkKGNvbnRleHQsIHRoaXMubWFwLCByZXNMb2FkTWFwcyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgICAgIC8vQ2xlYW4gdXAKICAgICAgICAgICAgICAgICAgICAgICAgY2xlYW5SZWdpc3RyeShpZCk7CgogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmRlZmluZWQgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgLy9GaW5pc2hlZCB0aGUgZGVmaW5lIHN0YWdlLiBBbGxvdyBjYWxsaW5nIGNoZWNrIGFnYWluCiAgICAgICAgICAgICAgICAgICAgLy90byBhbGxvdyBkZWZpbmUgbm90aWZpY2F0aW9ucyBiZWxvdyBpbiB0aGUgY2FzZSBvZiBhCiAgICAgICAgICAgICAgICAgICAgLy9jeWNsZS4KICAgICAgICAgICAgICAgICAgICB0aGlzLmRlZmluaW5nID0gZmFsc2U7CgogICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLmRlZmluZWQgJiYgIXRoaXMuZGVmaW5lRW1pdHRlZCkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmRlZmluZUVtaXR0ZWQgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmVtaXQoJ2RlZmluZWQnLCB0aGlzLmV4cG9ydHMpOwogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmRlZmluZUVtaXRDb21wbGV0ZSA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIGNhbGxQbHVnaW46IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHZhciBtYXAgPSB0aGlzLm1hcCwKICAgICAgICAgICAgICAgICAgICBpZCA9IG1hcC5pZCwKICAgICAgICAgICAgICAgICAgICAvL01hcCBhbHJlYWR5IG5vcm1hbGl6ZWQgdGhlIHByZWZpeC4KICAgICAgICAgICAgICAgICAgICBwbHVnaW5NYXAgPSBtYWtlTW9kdWxlTWFwKG1hcC5wcmVmaXgpOwoKICAgICAgICAgICAgICAgIC8vTWFyayB0aGlzIGFzIGEgZGVwZW5kZW5jeSBmb3IgdGhpcyBwbHVnaW4sIHNvIGl0CiAgICAgICAgICAgICAgICAvL2NhbiBiZSB0cmFjZWQgZm9yIGN5Y2xlcy4KICAgICAgICAgICAgICAgIHRoaXMuZGVwTWFwcy5wdXNoKHBsdWdpbk1hcCk7CgogICAgICAgICAgICAgICAgb24ocGx1Z2luTWFwLCAnZGVmaW5lZCcsIGJpbmQodGhpcywgZnVuY3Rpb24gKHBsdWdpbikgewogICAgICAgICAgICAgICAgICAgIHZhciBsb2FkLCBub3JtYWxpemVkTWFwLCBub3JtYWxpemVkTW9kLAogICAgICAgICAgICAgICAgICAgICAgICBidW5kbGVJZCA9IGdldE93bihidW5kbGVzTWFwLCB0aGlzLm1hcC5pZCksCiAgICAgICAgICAgICAgICAgICAgICAgIG5hbWUgPSB0aGlzLm1hcC5uYW1lLAogICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnROYW1lID0gdGhpcy5tYXAucGFyZW50TWFwID8gdGhpcy5tYXAucGFyZW50TWFwLm5hbWUgOiBudWxsLAogICAgICAgICAgICAgICAgICAgICAgICBsb2NhbFJlcXVpcmUgPSBjb250ZXh0Lm1ha2VSZXF1aXJlKG1hcC5wYXJlbnRNYXAsIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVuYWJsZUJ1aWxkQ2FsbGJhY2s6IHRydWUKICAgICAgICAgICAgICAgICAgICAgICAgfSk7CgogICAgICAgICAgICAgICAgICAgIC8vSWYgY3VycmVudCBtYXAgaXMgbm90IG5vcm1hbGl6ZWQsIHdhaXQgZm9yIHRoYXQKICAgICAgICAgICAgICAgICAgICAvL25vcm1hbGl6ZWQgbmFtZSB0byBsb2FkIGluc3RlYWQgb2YgY29udGludWluZy4KICAgICAgICAgICAgICAgICAgICBpZiAodGhpcy5tYXAudW5ub3JtYWxpemVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vTm9ybWFsaXplIHRoZSBJRCBpZiB0aGUgcGx1Z2luIGFsbG93cyBpdC4KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHBsdWdpbi5ub3JtYWxpemUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5hbWUgPSBwbHVnaW4ubm9ybWFsaXplKG5hbWUsIGZ1bmN0aW9uIChuYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG5vcm1hbGl6ZShuYW1lLCBwYXJlbnROYW1lLCB0cnVlKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pIHx8ICcnOwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAvL3ByZWZpeCBhbmQgbmFtZSBzaG91bGQgYWxyZWFkeSBiZSBub3JtYWxpemVkLCBubyBuZWVkCiAgICAgICAgICAgICAgICAgICAgICAgIC8vZm9yIGFwcGx5aW5nIG1hcCBjb25maWcgYWdhaW4gZWl0aGVyLgogICAgICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkTWFwID0gbWFrZU1vZHVsZU1hcChtYXAucHJlZml4ICsgJyEnICsgbmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5tYXAucGFyZW50TWFwLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0cnVlKTsKICAgICAgICAgICAgICAgICAgICAgICAgb24obm9ybWFsaXplZE1hcCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICdkZWZpbmVkJywgYmluZCh0aGlzLCBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLm1hcC5ub3JtYWxpemVkTWFwID0gbm9ybWFsaXplZE1hcDsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmluaXQoW10sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIHZhbHVlOyB9LCBudWxsLCB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVuYWJsZWQ6IHRydWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlnbm9yZTogdHJ1ZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfSkpOwoKICAgICAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZE1vZCA9IGdldE93bihyZWdpc3RyeSwgbm9ybWFsaXplZE1hcC5pZCk7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChub3JtYWxpemVkTW9kKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL01hcmsgdGhpcyBhcyBhIGRlcGVuZGVuY3kgZm9yIHRoaXMgcGx1Z2luLCBzbyBpdAogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9jYW4gYmUgdHJhY2VkIGZvciBjeWNsZXMuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmRlcE1hcHMucHVzaChub3JtYWxpemVkTWFwKTsKCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAodGhpcy5ldmVudHMuZXJyb3IpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkTW9kLm9uKCdlcnJvcicsIGJpbmQodGhpcywgZnVuY3Rpb24gKGVycikgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmVtaXQoJ2Vycm9yJywgZXJyKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkTW9kLmVuYWJsZSgpOwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAvL0lmIGEgcGF0aHMgY29uZmlnLCB0aGVuIGp1c3QgbG9hZCB0aGF0IGZpbGUgaW5zdGVhZCB0bwogICAgICAgICAgICAgICAgICAgIC8vcmVzb2x2ZSB0aGUgcGx1Z2luLCBhcyBpdCBpcyBidWlsdCBpbnRvIHRoYXQgcGF0aHMgbGF5ZXIuCiAgICAgICAgICAgICAgICAgICAgaWYgKGJ1bmRsZUlkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMubWFwLnVybCA9IGNvbnRleHQubmFtZVRvVXJsKGJ1bmRsZUlkKTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5sb2FkKCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgIGxvYWQgPSBiaW5kKHRoaXMsIGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmluaXQoW10sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIHZhbHVlOyB9LCBudWxsLCB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlbmFibGVkOiB0cnVlCiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH0pOwoKICAgICAgICAgICAgICAgICAgICBsb2FkLmVycm9yID0gYmluZCh0aGlzLCBmdW5jdGlvbiAoZXJyKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuaW5pdGVkID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5lcnJvciA9IGVycjsKICAgICAgICAgICAgICAgICAgICAgICAgZXJyLnJlcXVpcmVNb2R1bGVzID0gW2lkXTsKCiAgICAgICAgICAgICAgICAgICAgICAgIC8vUmVtb3ZlIHRlbXAgdW5ub3JtYWxpemVkIG1vZHVsZXMgZm9yIHRoaXMgbW9kdWxlLAogICAgICAgICAgICAgICAgICAgICAgICAvL3NpbmNlIHRoZXkgd2lsbCBuZXZlciBiZSByZXNvbHZlZCBvdGhlcndpc2Ugbm93LgogICAgICAgICAgICAgICAgICAgICAgICBlYWNoUHJvcChyZWdpc3RyeSwgZnVuY3Rpb24gKG1vZCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG1vZC5tYXAuaWQuaW5kZXhPZihpZCArICdfdW5ub3JtYWxpemVkJykgPT09IDApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjbGVhblJlZ2lzdHJ5KG1vZC5tYXAuaWQpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICAgICAgICAgIG9uRXJyb3IoZXJyKTsKICAgICAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICAgICAgLy9BbGxvdyBwbHVnaW5zIHRvIGxvYWQgb3RoZXIgY29kZSB3aXRob3V0IGhhdmluZyB0byBrbm93IHRoZQogICAgICAgICAgICAgICAgICAgIC8vY29udGV4dCBvciBob3cgdG8gJ2NvbXBsZXRlJyB0aGUgbG9hZC4KICAgICAgICAgICAgICAgICAgICBsb2FkLmZyb21UZXh0ID0gYmluZCh0aGlzLCBmdW5jdGlvbiAodGV4dCwgdGV4dEFsdCkgewogICAgICAgICAgICAgICAgICAgICAgICAvKmpzbGludCBldmlsOiB0cnVlICovCiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBtb2R1bGVOYW1lID0gbWFwLm5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtb2R1bGVNYXAgPSBtYWtlTW9kdWxlTWFwKG1vZHVsZU5hbWUpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFzSW50ZXJhY3RpdmUgPSB1c2VJbnRlcmFjdGl2ZTsKCiAgICAgICAgICAgICAgICAgICAgICAgIC8vQXMgb2YgMi4xLjAsIHN1cHBvcnQganVzdCBwYXNzaW5nIHRoZSB0ZXh0LCB0byByZWluZm9yY2UKICAgICAgICAgICAgICAgICAgICAgICAgLy9mcm9tVGV4dCBvbmx5IGJlaW5nIGNhbGxlZCBvbmNlIHBlciByZXNvdXJjZS4gU3RpbGwKICAgICAgICAgICAgICAgICAgICAgICAgLy9zdXBwb3J0IG9sZCBzdHlsZSBvZiBwYXNzaW5nIG1vZHVsZU5hbWUgYnV0IGRpc2NhcmQKICAgICAgICAgICAgICAgICAgICAgICAgLy90aGF0IG1vZHVsZU5hbWUgaW4gZmF2b3Igb2YgdGhlIGludGVybmFsIHJlZi4KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHRleHRBbHQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRleHQgPSB0ZXh0QWx0OwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAvL1R1cm4gb2ZmIGludGVyYWN0aXZlIHNjcmlwdCBtYXRjaGluZyBmb3IgSUUgZm9yIGFueSBkZWZpbmUKICAgICAgICAgICAgICAgICAgICAgICAgLy9jYWxscyBpbiB0aGUgdGV4dCwgdGhlbiB0dXJuIGl0IGJhY2sgb24gYXQgdGhlIGVuZC4KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGhhc0ludGVyYWN0aXZlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB1c2VJbnRlcmFjdGl2ZSA9IGZhbHNlOwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAvL1ByaW1lIHRoZSBzeXN0ZW0gYnkgY3JlYXRpbmcgYSBtb2R1bGUgaW5zdGFuY2UgZm9yCiAgICAgICAgICAgICAgICAgICAgICAgIC8vaXQuCiAgICAgICAgICAgICAgICAgICAgICAgIGdldE1vZHVsZShtb2R1bGVNYXApOwoKICAgICAgICAgICAgICAgICAgICAgICAgLy9UcmFuc2ZlciBhbnkgY29uZmlnIHRvIHRoaXMgb3RoZXIgbW9kdWxlLgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaGFzUHJvcChjb25maWcuY29uZmlnLCBpZCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbmZpZy5jb25maWdbbW9kdWxlTmFtZV0gPSBjb25maWcuY29uZmlnW2lkXTsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcS5leGVjKHRleHQpOwogICAgICAgICAgICAgICAgICAgICAgICB9IGNhdGNoIChlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gb25FcnJvcihtYWtlRXJyb3IoJ2Zyb210ZXh0ZXZhbCcsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICdmcm9tVGV4dCBldmFsIGZvciAnICsgaWQgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICcgZmFpbGVkOiAnICsgZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgW2lkXSkpOwogICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaGFzSW50ZXJhY3RpdmUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVzZUludGVyYWN0aXZlID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgLy9NYXJrIHRoaXMgYXMgYSBkZXBlbmRlbmN5IGZvciB0aGUgcGx1Z2luCiAgICAgICAgICAgICAgICAgICAgICAgIC8vcmVzb3VyY2UKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5kZXBNYXBzLnB1c2gobW9kdWxlTWFwKTsKCiAgICAgICAgICAgICAgICAgICAgICAgIC8vU3VwcG9ydCBhbm9ueW1vdXMgbW9kdWxlcy4KICAgICAgICAgICAgICAgICAgICAgICAgY29udGV4dC5jb21wbGV0ZUxvYWQobW9kdWxlTmFtZSk7CgogICAgICAgICAgICAgICAgICAgICAgICAvL0JpbmQgdGhlIHZhbHVlIG9mIHRoYXQgbW9kdWxlIHRvIHRoZSB2YWx1ZSBmb3IgdGhpcwogICAgICAgICAgICAgICAgICAgICAgICAvL3Jlc291cmNlIElELgogICAgICAgICAgICAgICAgICAgICAgICBsb2NhbFJlcXVpcmUoW21vZHVsZU5hbWVdLCBsb2FkKTsKICAgICAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICAgICAgLy9Vc2UgcGFyZW50TmFtZSBoZXJlIHNpbmNlIHRoZSBwbHVnaW4ncyBuYW1lIGlzIG5vdCByZWxpYWJsZSwKICAgICAgICAgICAgICAgICAgICAvL2NvdWxkIGJlIHNvbWUgd2VpcmQgc3RyaW5nIHdpdGggbm8gcGF0aCB0aGF0IGFjdHVhbGx5IHdhbnRzIHRvCiAgICAgICAgICAgICAgICAgICAgLy9yZWZlcmVuY2UgdGhlIHBhcmVudE5hbWUncyBwYXRoLgogICAgICAgICAgICAgICAgICAgIHBsdWdpbi5sb2FkKG1hcC5uYW1lLCBsb2NhbFJlcXVpcmUsIGxvYWQsIGNvbmZpZyk7CiAgICAgICAgICAgICAgICB9KSk7CgogICAgICAgICAgICAgICAgY29udGV4dC5lbmFibGUocGx1Z2luTWFwLCB0aGlzKTsKICAgICAgICAgICAgICAgIHRoaXMucGx1Z2luTWFwc1twbHVnaW5NYXAuaWRdID0gcGx1Z2luTWFwOwogICAgICAgICAgICB9LAoKICAgICAgICAgICAgZW5hYmxlOiBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBlbmFibGVkUmVnaXN0cnlbdGhpcy5tYXAuaWRdID0gdGhpczsKICAgICAgICAgICAgICAgIHRoaXMuZW5hYmxlZCA9IHRydWU7CgogICAgICAgICAgICAgICAgLy9TZXQgZmxhZyBtZW50aW9uaW5nIHRoYXQgdGhlIG1vZHVsZSBpcyBlbmFibGluZywKICAgICAgICAgICAgICAgIC8vc28gdGhhdCBpbW1lZGlhdGUgY2FsbHMgdG8gdGhlIGRlZmluZWQgY2FsbGJhY2tzCiAgICAgICAgICAgICAgICAvL2ZvciBkZXBlbmRlbmNpZXMgZG8gbm90IHRyaWdnZXIgaW5hZHZlcnRlbnQgbG9hZAogICAgICAgICAgICAgICAgLy93aXRoIHRoZSBkZXBDb3VudCBzdGlsbCBiZWluZyB6ZXJvLgogICAgICAgICAgICAgICAgdGhpcy5lbmFibGluZyA9IHRydWU7CgogICAgICAgICAgICAgICAgLy9FbmFibGUgZWFjaCBkZXBlbmRlbmN5CiAgICAgICAgICAgICAgICBlYWNoKHRoaXMuZGVwTWFwcywgYmluZCh0aGlzLCBmdW5jdGlvbiAoZGVwTWFwLCBpKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGlkLCBtb2QsIGhhbmRsZXI7CgogICAgICAgICAgICAgICAgICAgIGlmICh0eXBlb2YgZGVwTWFwID09PSAnc3RyaW5nJykgewogICAgICAgICAgICAgICAgICAgICAgICAvL0RlcGVuZGVuY3kgbmVlZHMgdG8gYmUgY29udmVydGVkIHRvIGEgZGVwTWFwCiAgICAgICAgICAgICAgICAgICAgICAgIC8vYW5kIHdpcmVkIHVwIHRvIHRoaXMgbW9kdWxlLgogICAgICAgICAgICAgICAgICAgICAgICBkZXBNYXAgPSBtYWtlTW9kdWxlTWFwKGRlcE1hcCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodGhpcy5tYXAuaXNEZWZpbmUgPyB0aGlzLm1hcCA6IHRoaXMubWFwLnBhcmVudE1hcCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIXRoaXMuc2tpcE1hcCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuZGVwTWFwc1tpXSA9IGRlcE1hcDsKCiAgICAgICAgICAgICAgICAgICAgICAgIGhhbmRsZXIgPSBnZXRPd24oaGFuZGxlcnMsIGRlcE1hcC5pZCk7CgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaGFuZGxlcikgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5kZXBFeHBvcnRzW2ldID0gaGFuZGxlcih0aGlzKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5kZXBDb3VudCArPSAxOwoKICAgICAgICAgICAgICAgICAgICAgICAgb24oZGVwTWFwLCAnZGVmaW5lZCcsIGJpbmQodGhpcywgZnVuY3Rpb24gKGRlcEV4cG9ydHMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLnVuZGVmZWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmRlZmluZURlcChpLCBkZXBFeHBvcnRzKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuY2hlY2soKTsKICAgICAgICAgICAgICAgICAgICAgICAgfSkpOwoKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuZXJyYmFjaykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgb24oZGVwTWFwLCAnZXJyb3InLCBiaW5kKHRoaXMsIHRoaXMuZXJyYmFjaykpOwogICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuZXZlbnRzLmVycm9yKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBObyBkaXJlY3QgZXJyYmFjayBvbiB0aGlzIG1vZHVsZSwgYnV0IHNvbWV0aGluZwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gZWxzZSBpcyBsaXN0ZW5pbmcgZm9yIGVycm9ycywgc28gYmUgc3VyZSB0bwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gcHJvcGFnYXRlIHRoZSBlcnJvciBjb3JyZWN0bHkuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbihkZXBNYXAsICdlcnJvcicsIGJpbmQodGhpcywgZnVuY3Rpb24oZXJyKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5lbWl0KCdlcnJvcicsIGVycik7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgIGlkID0gZGVwTWFwLmlkOwogICAgICAgICAgICAgICAgICAgIG1vZCA9IHJlZ2lzdHJ5W2lkXTsKCiAgICAgICAgICAgICAgICAgICAgLy9Ta2lwIHNwZWNpYWwgbW9kdWxlcyBsaWtlICdyZXF1aXJlJywgJ2V4cG9ydHMnLCAnbW9kdWxlJwogICAgICAgICAgICAgICAgICAgIC8vQWxzbywgZG9uJ3QgY2FsbCBlbmFibGUgaWYgaXQgaXMgYWxyZWFkeSBlbmFibGVkLAogICAgICAgICAgICAgICAgICAgIC8vaW1wb3J0YW50IGluIGNpcmN1bGFyIGRlcGVuZGVuY3kgY2FzZXMuCiAgICAgICAgICAgICAgICAgICAgaWYgKCFoYXNQcm9wKGhhbmRsZXJzLCBpZCkgJiYgbW9kICYmICFtb2QuZW5hYmxlZCkgewogICAgICAgICAgICAgICAgICAgICAgICBjb250ZXh0LmVuYWJsZShkZXBNYXAsIHRoaXMpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pKTsKCiAgICAgICAgICAgICAgICAvL0VuYWJsZSBlYWNoIHBsdWdpbiB0aGF0IGlzIHVzZWQgaW4KICAgICAgICAgICAgICAgIC8vYSBkZXBlbmRlbmN5CiAgICAgICAgICAgICAgICBlYWNoUHJvcCh0aGlzLnBsdWdpbk1hcHMsIGJpbmQodGhpcywgZnVuY3Rpb24gKHBsdWdpbk1hcCkgewogICAgICAgICAgICAgICAgICAgIHZhciBtb2QgPSBnZXRPd24ocmVnaXN0cnksIHBsdWdpbk1hcC5pZCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKG1vZCAmJiAhbW9kLmVuYWJsZWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29udGV4dC5lbmFibGUocGx1Z2luTWFwLCB0aGlzKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KSk7CgogICAgICAgICAgICAgICAgdGhpcy5lbmFibGluZyA9IGZhbHNlOwoKICAgICAgICAgICAgICAgIHRoaXMuY2hlY2soKTsKICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIG9uOiBmdW5jdGlvbiAobmFtZSwgY2IpIHsKICAgICAgICAgICAgICAgIHZhciBjYnMgPSB0aGlzLmV2ZW50c1tuYW1lXTsKICAgICAgICAgICAgICAgIGlmICghY2JzKSB7CiAgICAgICAgICAgICAgICAgICAgY2JzID0gdGhpcy5ldmVudHNbbmFtZV0gPSBbXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNicy5wdXNoKGNiKTsKICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIGVtaXQ6IGZ1bmN0aW9uIChuYW1lLCBldnQpIHsKICAgICAgICAgICAgICAgIGVhY2godGhpcy5ldmVudHNbbmFtZV0sIGZ1bmN0aW9uIChjYikgewogICAgICAgICAgICAgICAgICAgIGNiKGV2dCk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGlmIChuYW1lID09PSAnZXJyb3InKSB7CiAgICAgICAgICAgICAgICAgICAgLy9Ob3cgdGhhdCB0aGUgZXJyb3IgaGFuZGxlciB3YXMgdHJpZ2dlcmVkLCByZW1vdmUKICAgICAgICAgICAgICAgICAgICAvL3RoZSBsaXN0ZW5lcnMsIHNpbmNlIHRoaXMgYnJva2VuIE1vZHVsZSBpbnN0YW5jZQogICAgICAgICAgICAgICAgICAgIC8vY2FuIHN0YXkgYXJvdW5kIGZvciBhIHdoaWxlIGluIHRoZSByZWdpc3RyeS4KICAgICAgICAgICAgICAgICAgICBkZWxldGUgdGhpcy5ldmVudHNbbmFtZV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9OwoKICAgICAgICBmdW5jdGlvbiBjYWxsR2V0TW9kdWxlKGFyZ3MpIHsKICAgICAgICAgICAgLy9Ta2lwIG1vZHVsZXMgYWxyZWFkeSBkZWZpbmVkLgogICAgICAgICAgICBpZiAoIWhhc1Byb3AoZGVmaW5lZCwgYXJnc1swXSkpIHsKICAgICAgICAgICAgICAgIGdldE1vZHVsZShtYWtlTW9kdWxlTWFwKGFyZ3NbMF0sIG51bGwsIHRydWUpKS5pbml0KGFyZ3NbMV0sIGFyZ3NbMl0pOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiByZW1vdmVMaXN0ZW5lcihub2RlLCBmdW5jLCBuYW1lLCBpZU5hbWUpIHsKICAgICAgICAgICAgLy9GYXZvciBkZXRhY2hFdmVudCBiZWNhdXNlIG9mIElFOQogICAgICAgICAgICAvL2lzc3VlLCBzZWUgYXR0YWNoRXZlbnQvYWRkRXZlbnRMaXN0ZW5lciBjb21tZW50IGVsc2V3aGVyZQogICAgICAgICAgICAvL2luIHRoaXMgZmlsZS4KICAgICAgICAgICAgaWYgKG5vZGUuZGV0YWNoRXZlbnQgJiYgIWlzT3BlcmEpIHsKICAgICAgICAgICAgICAgIC8vUHJvYmFibHkgSUUuIElmIG5vdCBpdCB3aWxsIHRocm93IGFuIGVycm9yLCB3aGljaCB3aWxsIGJlCiAgICAgICAgICAgICAgICAvL3VzZWZ1bCB0byBrbm93LgogICAgICAgICAgICAgICAgaWYgKGllTmFtZSkgewogICAgICAgICAgICAgICAgICAgIG5vZGUuZGV0YWNoRXZlbnQoaWVOYW1lLCBmdW5jKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIG5vZGUucmVtb3ZlRXZlbnRMaXN0ZW5lcihuYW1lLCBmdW5jLCBmYWxzZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEdpdmVuIGFuIGV2ZW50IGZyb20gYSBzY3JpcHQgbm9kZSwgZ2V0IHRoZSByZXF1aXJlanMgaW5mbyBmcm9tIGl0LAogICAgICAgICAqIGFuZCB0aGVuIHJlbW92ZXMgdGhlIGV2ZW50IGxpc3RlbmVycyBvbiB0aGUgbm9kZS4KICAgICAgICAgKiBAcGFyYW0ge0V2ZW50fSBldnQKICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldFNjcmlwdERhdGEoZXZ0KSB7CiAgICAgICAgICAgIC8vVXNpbmcgY3VycmVudFRhcmdldCBpbnN0ZWFkIG9mIHRhcmdldCBmb3IgRmlyZWZveCAyLjAncyBzYWtlLiBOb3QKICAgICAgICAgICAgLy9hbGwgb2xkIGJyb3dzZXJzIHdpbGwgYmUgc3VwcG9ydGVkLCBidXQgdGhpcyBvbmUgd2FzIGVhc3kgZW5vdWdoCiAgICAgICAgICAgIC8vdG8gc3VwcG9ydCBhbmQgc3RpbGwgbWFrZXMgc2Vuc2UuCiAgICAgICAgICAgIHZhciBub2RlID0gZXZ0LmN1cnJlbnRUYXJnZXQgfHwgZXZ0LnNyY0VsZW1lbnQ7CgogICAgICAgICAgICAvL1JlbW92ZSB0aGUgbGlzdGVuZXJzIG9uY2UgaGVyZS4KICAgICAgICAgICAgcmVtb3ZlTGlzdGVuZXIobm9kZSwgY29udGV4dC5vblNjcmlwdExvYWQsICdsb2FkJywgJ29ucmVhZHlzdGF0ZWNoYW5nZScpOwogICAgICAgICAgICByZW1vdmVMaXN0ZW5lcihub2RlLCBjb250ZXh0Lm9uU2NyaXB0RXJyb3IsICdlcnJvcicpOwoKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIG5vZGU6IG5vZGUsCiAgICAgICAgICAgICAgICBpZDogbm9kZSAmJiBub2RlLmdldEF0dHJpYnV0ZSgnZGF0YS1yZXF1aXJlbW9kdWxlJykKICAgICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGludGFrZURlZmluZXMoKSB7CiAgICAgICAgICAgIHZhciBhcmdzOwoKICAgICAgICAgICAgLy9BbnkgZGVmaW5lZCBtb2R1bGVzIGluIHRoZSBnbG9iYWwgcXVldWUsIGludGFrZSB0aGVtIG5vdy4KICAgICAgICAgICAgdGFrZUdsb2JhbFF1ZXVlKCk7CgogICAgICAgICAgICAvL01ha2Ugc3VyZSBhbnkgcmVtYWluaW5nIGRlZlF1ZXVlIGl0ZW1zIGdldCBwcm9wZXJseSBwcm9jZXNzZWQuCiAgICAgICAgICAgIHdoaWxlIChkZWZRdWV1ZS5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIGFyZ3MgPSBkZWZRdWV1ZS5zaGlmdCgpOwogICAgICAgICAgICAgICAgaWYgKGFyZ3NbMF0gPT09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gb25FcnJvcihtYWtlRXJyb3IoJ21pc21hdGNoJywgJ01pc21hdGNoZWQgYW5vbnltb3VzIGRlZmluZSgpIG1vZHVsZTogJyArCiAgICAgICAgICAgICAgICAgICAgICAgIGFyZ3NbYXJncy5sZW5ndGggLSAxXSkpOwogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAvL2FyZ3MgYXJlIGlkLCBkZXBzLCBmYWN0b3J5LiBTaG91bGQgYmUgbm9ybWFsaXplZCBieSB0aGUKICAgICAgICAgICAgICAgICAgICAvL2RlZmluZSgpIGZ1bmN0aW9uLgogICAgICAgICAgICAgICAgICAgIGNhbGxHZXRNb2R1bGUoYXJncyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29udGV4dC5kZWZRdWV1ZU1hcCA9IHt9OwogICAgICAgIH0KCiAgICAgICAgY29udGV4dCA9IHsKICAgICAgICAgICAgY29uZmlnOiBjb25maWcsCiAgICAgICAgICAgIGNvbnRleHROYW1lOiBjb250ZXh0TmFtZSwKICAgICAgICAgICAgcmVnaXN0cnk6IHJlZ2lzdHJ5LAogICAgICAgICAgICBkZWZpbmVkOiBkZWZpbmVkLAogICAgICAgICAgICB1cmxGZXRjaGVkOiB1cmxGZXRjaGVkLAogICAgICAgICAgICBkZWZRdWV1ZTogZGVmUXVldWUsCiAgICAgICAgICAgIGRlZlF1ZXVlTWFwOiB7fSwKICAgICAgICAgICAgTW9kdWxlOiBNb2R1bGUsCiAgICAgICAgICAgIG1ha2VNb2R1bGVNYXA6IG1ha2VNb2R1bGVNYXAsCiAgICAgICAgICAgIG5leHRUaWNrOiByZXEubmV4dFRpY2ssCiAgICAgICAgICAgIG9uRXJyb3I6IG9uRXJyb3IsCgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogU2V0IGEgY29uZmlndXJhdGlvbiBmb3IgdGhlIGNvbnRleHQuCiAgICAgICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBjZmcgY29uZmlnIG9iamVjdCB0byBpbnRlZ3JhdGUuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBjb25maWd1cmU6IGZ1bmN0aW9uIChjZmcpIHsKICAgICAgICAgICAgICAgIC8vTWFrZSBzdXJlIHRoZSBiYXNlVXJsIGVuZHMgaW4gYSBzbGFzaC4KICAgICAgICAgICAgICAgIGlmIChjZmcuYmFzZVVybCkgewogICAgICAgICAgICAgICAgICAgIGlmIChjZmcuYmFzZVVybC5jaGFyQXQoY2ZnLmJhc2VVcmwubGVuZ3RoIC0gMSkgIT09ICcvJykgewogICAgICAgICAgICAgICAgICAgICAgICBjZmcuYmFzZVVybCArPSAnLyc7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIC8vIENvbnZlcnQgb2xkIHN0eWxlIHVybEFyZ3Mgc3RyaW5nIHRvIGEgZnVuY3Rpb24uCiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIGNmZy51cmxBcmdzID09PSAnc3RyaW5nJykgewogICAgICAgICAgICAgICAgICAgIHZhciB1cmxBcmdzID0gY2ZnLnVybEFyZ3M7CiAgICAgICAgICAgICAgICAgICAgY2ZnLnVybEFyZ3MgPSBmdW5jdGlvbihpZCwgdXJsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAodXJsLmluZGV4T2YoJz8nKSA9PT0gLTEgPyAnPycgOiAnJicpICsgdXJsQXJnczsKICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIC8vU2F2ZSBvZmYgdGhlIHBhdGhzIHNpbmNlIHRoZXkgcmVxdWlyZSBzcGVjaWFsIHByb2Nlc3NpbmcsCiAgICAgICAgICAgICAgICAvL3RoZXkgYXJlIGFkZGl0aXZlLgogICAgICAgICAgICAgICAgdmFyIHNoaW0gPSBjb25maWcuc2hpbSwKICAgICAgICAgICAgICAgICAgICBvYmpzID0gewogICAgICAgICAgICAgICAgICAgICAgICBwYXRoczogdHJ1ZSwKICAgICAgICAgICAgICAgICAgICAgICAgYnVuZGxlczogdHJ1ZSwKICAgICAgICAgICAgICAgICAgICAgICAgY29uZmlnOiB0cnVlLAogICAgICAgICAgICAgICAgICAgICAgICBtYXA6IHRydWUKICAgICAgICAgICAgICAgICAgICB9OwoKICAgICAgICAgICAgICAgIGVhY2hQcm9wKGNmZywgZnVuY3Rpb24gKHZhbHVlLCBwcm9wKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKG9ianNbcHJvcF0pIHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFjb25maWdbcHJvcF0pIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbmZpZ1twcm9wXSA9IHt9OwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIG1peGluKGNvbmZpZ1twcm9wXSwgdmFsdWUsIHRydWUsIHRydWUpOwogICAgICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbmZpZ1twcm9wXSA9IHZhbHVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwoKICAgICAgICAgICAgICAgIC8vUmV2ZXJzZSBtYXAgdGhlIGJ1bmRsZXMKICAgICAgICAgICAgICAgIGlmIChjZmcuYnVuZGxlcykgewogICAgICAgICAgICAgICAgICAgIGVhY2hQcm9wKGNmZy5idW5kbGVzLCBmdW5jdGlvbiAodmFsdWUsIHByb3ApIHsKICAgICAgICAgICAgICAgICAgICAgICAgZWFjaCh2YWx1ZSwgZnVuY3Rpb24gKHYpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmICh2ICE9PSBwcm9wKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYnVuZGxlc01hcFt2XSA9IHByb3A7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIC8vTWVyZ2Ugc2hpbQogICAgICAgICAgICAgICAgaWYgKGNmZy5zaGltKSB7CiAgICAgICAgICAgICAgICAgICAgZWFjaFByb3AoY2ZnLnNoaW0sIGZ1bmN0aW9uICh2YWx1ZSwgaWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy9Ob3JtYWxpemUgdGhlIHN0cnVjdHVyZQogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaXNBcnJheSh2YWx1ZSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZhbHVlID0gewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGRlcHM6IHZhbHVlCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGlmICgodmFsdWUuZXhwb3J0cyB8fCB2YWx1ZS5pbml0KSAmJiAhdmFsdWUuZXhwb3J0c0ZuKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZS5leHBvcnRzRm4gPSBjb250ZXh0Lm1ha2VTaGltRXhwb3J0cyh2YWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgc2hpbVtpZF0gPSB2YWx1ZTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICBjb25maWcuc2hpbSA9IHNoaW07CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgLy9BZGp1c3QgcGFja2FnZXMgaWYgbmVjZXNzYXJ5LgogICAgICAgICAgICAgICAgaWYgKGNmZy5wYWNrYWdlcykgewogICAgICAgICAgICAgICAgICAgIGVhY2goY2ZnLnBhY2thZ2VzLCBmdW5jdGlvbiAocGtnT2JqKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBsb2NhdGlvbiwgbmFtZTsKCiAgICAgICAgICAgICAgICAgICAgICAgIHBrZ09iaiA9IHR5cGVvZiBwa2dPYmogPT09ICdzdHJpbmcnID8ge25hbWU6IHBrZ09ian0gOiBwa2dPYmo7CgogICAgICAgICAgICAgICAgICAgICAgICBuYW1lID0gcGtnT2JqLm5hbWU7CiAgICAgICAgICAgICAgICAgICAgICAgIGxvY2F0aW9uID0gcGtnT2JqLmxvY2F0aW9uOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAobG9jYXRpb24pIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbmZpZy5wYXRoc1tuYW1lXSA9IHBrZ09iai5sb2NhdGlvbjsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgLy9TYXZlIHBvaW50ZXIgdG8gbWFpbiBtb2R1bGUgSUQgZm9yIHBrZyBuYW1lLgogICAgICAgICAgICAgICAgICAgICAgICAvL1JlbW92ZSBsZWFkaW5nIGRvdCBpbiBtYWluLCBzbyBtYWluIHBhdGhzIGFyZSBub3JtYWxpemVkLAogICAgICAgICAgICAgICAgICAgICAgICAvL2FuZCByZW1vdmUgYW55IHRyYWlsaW5nIC5qcywgc2luY2UgZGlmZmVyZW50IHBhY2thZ2UKICAgICAgICAgICAgICAgICAgICAgICAgLy9lbnZzIGhhdmUgZGlmZmVyZW50IGNvbnZlbnRpb25zOiBzb21lIHVzZSBhIG1vZHVsZSBuYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAvL3NvbWUgdXNlIGEgZmlsZSBuYW1lLgogICAgICAgICAgICAgICAgICAgICAgICBjb25maWcucGtnc1tuYW1lXSA9IHBrZ09iai5uYW1lICsgJy8nICsgKHBrZ09iai5tYWluIHx8ICdtYWluJykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC5yZXBsYWNlKGN1cnJEaXJSZWdFeHAsICcnKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoanNTdWZmaXhSZWdFeHAsICcnKTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAvL0lmIHRoZXJlIGFyZSBhbnkgIndhaXRpbmcgdG8gZXhlY3V0ZSIgbW9kdWxlcyBpbiB0aGUgcmVnaXN0cnksCiAgICAgICAgICAgICAgICAvL3VwZGF0ZSB0aGUgbWFwcyBmb3IgdGhlbSwgc2luY2UgdGhlaXIgaW5mbywgbGlrZSBVUkxzIHRvIGxvYWQsCiAgICAgICAgICAgICAgICAvL21heSBoYXZlIGNoYW5nZWQuCiAgICAgICAgICAgICAgICBlYWNoUHJvcChyZWdpc3RyeSwgZnVuY3Rpb24gKG1vZCwgaWQpIHsKICAgICAgICAgICAgICAgICAgICAvL0lmIG1vZHVsZSBhbHJlYWR5IGhhcyBpbml0IGNhbGxlZCwgc2luY2UgaXQgaXMgdG9vCiAgICAgICAgICAgICAgICAgICAgLy9sYXRlIHRvIG1vZGlmeSB0aGVtLCBhbmQgaWdub3JlIHVubm9ybWFsaXplZCBvbmVzCiAgICAgICAgICAgICAgICAgICAgLy9zaW5jZSB0aGV5IGFyZSB0cmFuc2llbnQuCiAgICAgICAgICAgICAgICAgICAgaWYgKCFtb2QuaW5pdGVkICYmICFtb2QubWFwLnVubm9ybWFsaXplZCkgewogICAgICAgICAgICAgICAgICAgICAgICBtb2QubWFwID0gbWFrZU1vZHVsZU1hcChpZCwgbnVsbCwgdHJ1ZSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CgogICAgICAgICAgICAgICAgLy9JZiBhIGRlcHMgYXJyYXkgb3IgYSBjb25maWcgY2FsbGJhY2sgaXMgc3BlY2lmaWVkLCB0aGVuIGNhbGwKICAgICAgICAgICAgICAgIC8vcmVxdWlyZSB3aXRoIHRob3NlIGFyZ3MuIFRoaXMgaXMgdXNlZnVsIHdoZW4gcmVxdWlyZSBpcyBkZWZpbmVkIGFzIGEKICAgICAgICAgICAgICAgIC8vY29uZmlnIG9iamVjdCBiZWZvcmUgcmVxdWlyZS5qcyBpcyBsb2FkZWQuCiAgICAgICAgICAgICAgICBpZiAoY2ZnLmRlcHMgfHwgY2ZnLmNhbGxiYWNrKSB7CiAgICAgICAgICAgICAgICAgICAgY29udGV4dC5yZXF1aXJlKGNmZy5kZXBzIHx8IFtdLCBjZmcuY2FsbGJhY2spOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAoKICAgICAgICAgICAgbWFrZVNoaW1FeHBvcnRzOiBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgICAgIGZ1bmN0aW9uIGZuKCkgewogICAgICAgICAgICAgICAgICAgIHZhciByZXQ7CiAgICAgICAgICAgICAgICAgICAgaWYgKHZhbHVlLmluaXQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0ID0gdmFsdWUuaW5pdC5hcHBseShnbG9iYWwsIGFyZ3VtZW50cyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIHJldHVybiByZXQgfHwgKHZhbHVlLmV4cG9ydHMgJiYgZ2V0R2xvYmFsKHZhbHVlLmV4cG9ydHMpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiBmbjsKICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIG1ha2VSZXF1aXJlOiBmdW5jdGlvbiAocmVsTWFwLCBvcHRpb25zKSB7CiAgICAgICAgICAgICAgICBvcHRpb25zID0gb3B0aW9ucyB8fCB7fTsKCiAgICAgICAgICAgICAgICBmdW5jdGlvbiBsb2NhbFJlcXVpcmUoZGVwcywgY2FsbGJhY2ssIGVycmJhY2spIHsKICAgICAgICAgICAgICAgICAgICB2YXIgaWQsIG1hcCwgcmVxdWlyZU1vZDsKCiAgICAgICAgICAgICAgICAgICAgaWYgKG9wdGlvbnMuZW5hYmxlQnVpbGRDYWxsYmFjayAmJiBjYWxsYmFjayAmJiBpc0Z1bmN0aW9uKGNhbGxiYWNrKSkgewogICAgICAgICAgICAgICAgICAgICAgICBjYWxsYmFjay5fX3JlcXVpcmVKc0J1aWxkID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgIGlmICh0eXBlb2YgZGVwcyA9PT0gJ3N0cmluZycpIHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlzRnVuY3Rpb24oY2FsbGJhY2spKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL0ludmFsaWQgY2FsbAogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9uRXJyb3IobWFrZUVycm9yKCdyZXF1aXJlYXJncycsICdJbnZhbGlkIHJlcXVpcmUgY2FsbCcpLCBlcnJiYWNrKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAgICAgLy9JZiByZXF1aXJlfGV4cG9ydHN8bW9kdWxlIGFyZSByZXF1ZXN0ZWQsIGdldCB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgLy92YWx1ZSBmb3IgdGhlbSBmcm9tIHRoZSBzcGVjaWFsIGhhbmRsZXJzLiBDYXZlYXQ6CiAgICAgICAgICAgICAgICAgICAgICAgIC8vdGhpcyBvbmx5IHdvcmtzIHdoaWxlIG1vZHVsZSBpcyBiZWluZyBkZWZpbmVkLgogICAgICAgICAgICAgICAgICAgICAgICBpZiAocmVsTWFwICYmIGhhc1Byb3AoaGFuZGxlcnMsIGRlcHMpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gaGFuZGxlcnNbZGVwc10ocmVnaXN0cnlbcmVsTWFwLmlkXSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgICAgIC8vU3luY2hyb25vdXMgYWNjZXNzIHRvIG9uZSBtb2R1bGUuIElmIHJlcXVpcmUuZ2V0IGlzCiAgICAgICAgICAgICAgICAgICAgICAgIC8vYXZhaWxhYmxlIChhcyBpbiB0aGUgTm9kZSBhZGFwdGVyKSwgcHJlZmVyIHRoYXQuCiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChyZXEuZ2V0KSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gcmVxLmdldChjb250ZXh0LCBkZXBzLCByZWxNYXAsIGxvY2FsUmVxdWlyZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgICAgIC8vTm9ybWFsaXplIG1vZHVsZSBuYW1lLCBpZiBpdCBjb250YWlucyAuIG9yIC4uCiAgICAgICAgICAgICAgICAgICAgICAgIG1hcCA9IG1ha2VNb2R1bGVNYXAoZGVwcywgcmVsTWFwLCBmYWxzZSwgdHJ1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGlkID0gbWFwLmlkOwoKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFoYXNQcm9wKGRlZmluZWQsIGlkKSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9uRXJyb3IobWFrZUVycm9yKCdub3Rsb2FkZWQnLCAnTW9kdWxlIG5hbWUgIicgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWQgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJyIgaGFzIG5vdCBiZWVuIGxvYWRlZCB5ZXQgZm9yIGNvbnRleHQ6ICcgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29udGV4dE5hbWUgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKHJlbE1hcCA/ICcnIDogJy4gVXNlIHJlcXVpcmUoW10pJykpKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gZGVmaW5lZFtpZF07CiAgICAgICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgICAgICAvL0dyYWIgZGVmaW5lcyB3YWl0aW5nIGluIHRoZSBnbG9iYWwgcXVldWUuCiAgICAgICAgICAgICAgICAgICAgaW50YWtlRGVmaW5lcygpOwoKICAgICAgICAgICAgICAgICAgICAvL01hcmsgYWxsIHRoZSBkZXBlbmRlbmNpZXMgYXMgbmVlZGluZyB0byBiZSBsb2FkZWQuCiAgICAgICAgICAgICAgICAgICAgY29udGV4dC5uZXh0VGljayhmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vU29tZSBkZWZpbmVzIGNvdWxkIGhhdmUgYmVlbiBhZGRlZCBzaW5jZSB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgLy9yZXF1aXJlIGNhbGwsIGNvbGxlY3QgdGhlbS4KICAgICAgICAgICAgICAgICAgICAgICAgaW50YWtlRGVmaW5lcygpOwoKICAgICAgICAgICAgICAgICAgICAgICAgcmVxdWlyZU1vZCA9IGdldE1vZHVsZShtYWtlTW9kdWxlTWFwKG51bGwsIHJlbE1hcCkpOwoKICAgICAgICAgICAgICAgICAgICAgICAgLy9TdG9yZSBpZiBtYXAgY29uZmlnIHNob3VsZCBiZSBhcHBsaWVkIHRvIHRoaXMgcmVxdWlyZQogICAgICAgICAgICAgICAgICAgICAgICAvL2NhbGwgZm9yIGRlcGVuZGVuY2llcy4KICAgICAgICAgICAgICAgICAgICAgICAgcmVxdWlyZU1vZC5za2lwTWFwID0gb3B0aW9ucy5za2lwTWFwOwoKICAgICAgICAgICAgICAgICAgICAgICAgcmVxdWlyZU1vZC5pbml0KGRlcHMsIGNhbGxiYWNrLCBlcnJiYWNrLCB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlbmFibGVkOiB0cnVlCiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwoKICAgICAgICAgICAgICAgICAgICAgICAgY2hlY2tMb2FkZWQoKTsKICAgICAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGxvY2FsUmVxdWlyZTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBtaXhpbihsb2NhbFJlcXVpcmUsIHsKICAgICAgICAgICAgICAgICAgICBpc0Jyb3dzZXI6IGlzQnJvd3NlciwKCiAgICAgICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgICAgICogQ29udmVydHMgYSBtb2R1bGUgbmFtZSArIC5leHRlbnNpb24gaW50byBhbiBVUkwgcGF0aC4KICAgICAgICAgICAgICAgICAgICAgKiAqUmVxdWlyZXMqIHRoZSB1c2Ugb2YgYSBtb2R1bGUgbmFtZS4gSXQgZG9lcyBub3Qgc3VwcG9ydCB1c2luZwogICAgICAgICAgICAgICAgICAgICAqIHBsYWluIFVSTHMgbGlrZSBuYW1lVG9VcmwuCiAgICAgICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICAgICAgdG9Vcmw6IGZ1bmN0aW9uIChtb2R1bGVOYW1lUGx1c0V4dCkgewogICAgICAgICAgICAgICAgICAgICAgICB2YXIgZXh0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5kZXggPSBtb2R1bGVOYW1lUGx1c0V4dC5sYXN0SW5kZXhPZignLicpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc2VnbWVudCA9IG1vZHVsZU5hbWVQbHVzRXh0LnNwbGl0KCcvJylbMF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpc1JlbGF0aXZlID0gc2VnbWVudCA9PT0gJy4nIHx8IHNlZ21lbnQgPT09ICcuLic7CgogICAgICAgICAgICAgICAgICAgICAgICAvL0hhdmUgYSBmaWxlIGV4dGVuc2lvbiBhbGlhcywgYW5kIGl0IGlzIG5vdCB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgLy9kb3RzIGZyb20gYSByZWxhdGl2ZSBwYXRoLgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaW5kZXggIT09IC0xICYmICghaXNSZWxhdGl2ZSB8fCBpbmRleCA+IDEpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBleHQgPSBtb2R1bGVOYW1lUGx1c0V4dC5zdWJzdHJpbmcoaW5kZXgsIG1vZHVsZU5hbWVQbHVzRXh0Lmxlbmd0aCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtb2R1bGVOYW1lUGx1c0V4dCA9IG1vZHVsZU5hbWVQbHVzRXh0LnN1YnN0cmluZygwLCBpbmRleCk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBjb250ZXh0Lm5hbWVUb1VybChub3JtYWxpemUobW9kdWxlTmFtZVBsdXNFeHQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlbE1hcCAmJiByZWxNYXAuaWQsIHRydWUpLCBleHQsICB0cnVlKTsKICAgICAgICAgICAgICAgICAgICB9LAoKICAgICAgICAgICAgICAgICAgICBkZWZpbmVkOiBmdW5jdGlvbiAoaWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGhhc1Byb3AoZGVmaW5lZCwgbWFrZU1vZHVsZU1hcChpZCwgcmVsTWFwLCBmYWxzZSwgdHJ1ZSkuaWQpOwogICAgICAgICAgICAgICAgICAgIH0sCgogICAgICAgICAgICAgICAgICAgIHNwZWNpZmllZDogZnVuY3Rpb24gKGlkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlkID0gbWFrZU1vZHVsZU1hcChpZCwgcmVsTWFwLCBmYWxzZSwgdHJ1ZSkuaWQ7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBoYXNQcm9wKGRlZmluZWQsIGlkKSB8fCBoYXNQcm9wKHJlZ2lzdHJ5LCBpZCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CgogICAgICAgICAgICAgICAgLy9Pbmx5IGFsbG93IHVuZGVmIG9uIHRvcCBsZXZlbCByZXF1aXJlIGNhbGxzCiAgICAgICAgICAgICAgICBpZiAoIXJlbE1hcCkgewogICAgICAgICAgICAgICAgICAgIGxvY2FsUmVxdWlyZS51bmRlZiA9IGZ1bmN0aW9uIChpZCkgewogICAgICAgICAgICAgICAgICAgICAgICAvL0JpbmQgYW55IHdhaXRpbmcgZGVmaW5lKCkgY2FsbHMgdG8gdGhpcyBjb250ZXh0LAogICAgICAgICAgICAgICAgICAgICAgICAvL2ZpeCBmb3IgIzQwOAogICAgICAgICAgICAgICAgICAgICAgICB0YWtlR2xvYmFsUXVldWUoKTsKCiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBtYXAgPSBtYWtlTW9kdWxlTWFwKGlkLCByZWxNYXAsIHRydWUpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgbW9kID0gZ2V0T3duKHJlZ2lzdHJ5LCBpZCk7CgogICAgICAgICAgICAgICAgICAgICAgICBtb2QudW5kZWZlZCA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgICAgIHJlbW92ZVNjcmlwdChpZCk7CgogICAgICAgICAgICAgICAgICAgICAgICBkZWxldGUgZGVmaW5lZFtpZF07CiAgICAgICAgICAgICAgICAgICAgICAgIGRlbGV0ZSB1cmxGZXRjaGVkW21hcC51cmxdOwogICAgICAgICAgICAgICAgICAgICAgICBkZWxldGUgdW5kZWZFdmVudHNbaWRdOwoKICAgICAgICAgICAgICAgICAgICAgICAgLy9DbGVhbiBxdWV1ZWQgZGVmaW5lcyB0b28uIEdvIGJhY2t3YXJkcwogICAgICAgICAgICAgICAgICAgICAgICAvL2luIGFycmF5IHNvIHRoYXQgdGhlIHNwbGljZXMgZG8gbm90CiAgICAgICAgICAgICAgICAgICAgICAgIC8vbWVzcyB1cCB0aGUgaXRlcmF0aW9uLgogICAgICAgICAgICAgICAgICAgICAgICBlYWNoUmV2ZXJzZShkZWZRdWV1ZSwgZnVuY3Rpb24oYXJncywgaSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGFyZ3NbMF0gPT09IGlkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZGVmUXVldWUuc3BsaWNlKGksIDEpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICAgICAgZGVsZXRlIGNvbnRleHQuZGVmUXVldWVNYXBbaWRdOwoKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG1vZCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9Ib2xkIG9uIHRvIGxpc3RlbmVycyBpbiBjYXNlIHRoZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9tb2R1bGUgd2lsbCBiZSBhdHRlbXB0ZWQgdG8gYmUgcmVsb2FkZWQKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vdXNpbmcgYSBkaWZmZXJlbnQgY29uZmlnLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG1vZC5ldmVudHMuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVuZGVmRXZlbnRzW2lkXSA9IG1vZC5ldmVudHM7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgICAgICAgICAgY2xlYW5SZWdpc3RyeShpZCk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIHJldHVybiBsb2NhbFJlcXVpcmU7CiAgICAgICAgICAgIH0sCgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQ2FsbGVkIHRvIGVuYWJsZSBhIG1vZHVsZSBpZiBpdCBpcyBzdGlsbCBpbiB0aGUgcmVnaXN0cnkKICAgICAgICAgICAgICogYXdhaXRpbmcgZW5hYmxlbWVudC4gQSBzZWNvbmQgYXJnLCBwYXJlbnQsIHRoZSBwYXJlbnQgbW9kdWxlLAogICAgICAgICAgICAgKiBpcyBwYXNzZWQgaW4gZm9yIGNvbnRleHQsIHdoZW4gdGhpcyBtZXRob2QgaXMgb3ZlcnJpZGRlbiBieQogICAgICAgICAgICAgKiB0aGUgb3B0aW1pemVyLiBOb3Qgc2hvd24gaGVyZSB0byBrZWVwIGNvZGUgY29tcGFjdC4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIGVuYWJsZTogZnVuY3Rpb24gKGRlcE1hcCkgewogICAgICAgICAgICAgICAgdmFyIG1vZCA9IGdldE93bihyZWdpc3RyeSwgZGVwTWFwLmlkKTsKICAgICAgICAgICAgICAgIGlmIChtb2QpIHsKICAgICAgICAgICAgICAgICAgICBnZXRNb2R1bGUoZGVwTWFwKS5lbmFibGUoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBJbnRlcm5hbCBtZXRob2QgdXNlZCBieSBlbnZpcm9ubWVudCBhZGFwdGVycyB0byBjb21wbGV0ZSBhIGxvYWQgZXZlbnQuCiAgICAgICAgICAgICAqIEEgbG9hZCBldmVudCBjb3VsZCBiZSBhIHNjcmlwdCBsb2FkIG9yIGp1c3QgYSBsb2FkIHBhc3MgZnJvbSBhIHN5bmNocm9ub3VzCiAgICAgICAgICAgICAqIGxvYWQgY2FsbC4KICAgICAgICAgICAgICogQHBhcmFtIHtTdHJpbmd9IG1vZHVsZU5hbWUgdGhlIG5hbWUgb2YgdGhlIG1vZHVsZSB0byBwb3RlbnRpYWxseSBjb21wbGV0ZS4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIGNvbXBsZXRlTG9hZDogZnVuY3Rpb24gKG1vZHVsZU5hbWUpIHsKICAgICAgICAgICAgICAgIHZhciBmb3VuZCwgYXJncywgbW9kLAogICAgICAgICAgICAgICAgICAgIHNoaW0gPSBnZXRPd24oY29uZmlnLnNoaW0sIG1vZHVsZU5hbWUpIHx8IHt9LAogICAgICAgICAgICAgICAgICAgIHNoRXhwb3J0cyA9IHNoaW0uZXhwb3J0czsKCiAgICAgICAgICAgICAgICB0YWtlR2xvYmFsUXVldWUoKTsKCiAgICAgICAgICAgICAgICB3aGlsZSAoZGVmUXVldWUubGVuZ3RoKSB7CiAgICAgICAgICAgICAgICAgICAgYXJncyA9IGRlZlF1ZXVlLnNoaWZ0KCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKGFyZ3NbMF0gPT09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgYXJnc1swXSA9IG1vZHVsZU5hbWU7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vSWYgYWxyZWFkeSBmb3VuZCBhbiBhbm9ueW1vdXMgbW9kdWxlIGFuZCBib3VuZCBpdAogICAgICAgICAgICAgICAgICAgICAgICAvL3RvIHRoaXMgbmFtZSwgdGhlbiB0aGlzIGlzIHNvbWUgb3RoZXIgYW5vbiBtb2R1bGUKICAgICAgICAgICAgICAgICAgICAgICAgLy93YWl0aW5nIGZvciBpdHMgY29tcGxldGVMb2FkIHRvIGZpcmUuCiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChmb3VuZCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZm91bmQgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0gZWxzZSBpZiAoYXJnc1swXSA9PT0gbW9kdWxlTmFtZSkgewogICAgICAgICAgICAgICAgICAgICAgICAvL0ZvdW5kIG1hdGNoaW5nIGRlZmluZSBjYWxsIGZvciB0aGlzIHNjcmlwdCEKICAgICAgICAgICAgICAgICAgICAgICAgZm91bmQgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAgICAgY2FsbEdldE1vZHVsZShhcmdzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNvbnRleHQuZGVmUXVldWVNYXAgPSB7fTsKCiAgICAgICAgICAgICAgICAvL0RvIHRoaXMgYWZ0ZXIgdGhlIGN5Y2xlIG9mIGNhbGxHZXRNb2R1bGUgaW4gY2FzZSB0aGUgcmVzdWx0CiAgICAgICAgICAgICAgICAvL29mIHRob3NlIGNhbGxzL2luaXQgY2FsbHMgY2hhbmdlcyB0aGUgcmVnaXN0cnkuCiAgICAgICAgICAgICAgICBtb2QgPSBnZXRPd24ocmVnaXN0cnksIG1vZHVsZU5hbWUpOwoKICAgICAgICAgICAgICAgIGlmICghZm91bmQgJiYgIWhhc1Byb3AoZGVmaW5lZCwgbW9kdWxlTmFtZSkgJiYgbW9kICYmICFtb2QuaW5pdGVkKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKGNvbmZpZy5lbmZvcmNlRGVmaW5lICYmICghc2hFeHBvcnRzIHx8ICFnZXRHbG9iYWwoc2hFeHBvcnRzKSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGhhc1BhdGhGYWxsYmFjayhtb2R1bGVOYW1lKSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9uRXJyb3IobWFrZUVycm9yKCdub2RlZmluZScsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICdObyBkZWZpbmUgY2FsbCBmb3IgJyArIG1vZHVsZU5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG51bGwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFttb2R1bGVOYW1lXSkpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy9BIHNjcmlwdCB0aGF0IGRvZXMgbm90IGNhbGwgZGVmaW5lKCksIHNvIGp1c3Qgc2ltdWxhdGUKICAgICAgICAgICAgICAgICAgICAgICAgLy90aGUgY2FsbCBmb3IgaXQuCiAgICAgICAgICAgICAgICAgICAgICAgIGNhbGxHZXRNb2R1bGUoW21vZHVsZU5hbWUsIChzaGltLmRlcHMgfHwgW10pLCBzaGltLmV4cG9ydHNGbl0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICBjaGVja0xvYWRlZCgpOwogICAgICAgICAgICB9LAoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIENvbnZlcnRzIGEgbW9kdWxlIG5hbWUgdG8gYSBmaWxlIHBhdGguIFN1cHBvcnRzIGNhc2VzIHdoZXJlCiAgICAgICAgICAgICAqIG1vZHVsZU5hbWUgbWF5IGFjdHVhbGx5IGJlIGp1c3QgYW4gVVJMLgogICAgICAgICAgICAgKiBOb3RlIHRoYXQgaXQgKipkb2VzIG5vdCoqIGNhbGwgbm9ybWFsaXplIG9uIHRoZSBtb2R1bGVOYW1lLAogICAgICAgICAgICAgKiBpdCBpcyBhc3N1bWVkIHRvIGhhdmUgYWxyZWFkeSBiZWVuIG5vcm1hbGl6ZWQuIFRoaXMgaXMgYW4KICAgICAgICAgICAgICogaW50ZXJuYWwgQVBJLCBub3QgYSBwdWJsaWMgb25lLiBVc2UgdG9VcmwgZm9yIHRoZSBwdWJsaWMgQVBJLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgbmFtZVRvVXJsOiBmdW5jdGlvbiAobW9kdWxlTmFtZSwgZXh0LCBza2lwRXh0KSB7CiAgICAgICAgICAgICAgICB2YXIgcGF0aHMsIHN5bXMsIGksIHBhcmVudE1vZHVsZSwgdXJsLAogICAgICAgICAgICAgICAgICAgIHBhcmVudFBhdGgsIGJ1bmRsZUlkLAogICAgICAgICAgICAgICAgICAgIHBrZ01haW4gPSBnZXRPd24oY29uZmlnLnBrZ3MsIG1vZHVsZU5hbWUpOwoKICAgICAgICAgICAgICAgIGlmIChwa2dNYWluKSB7CiAgICAgICAgICAgICAgICAgICAgbW9kdWxlTmFtZSA9IHBrZ01haW47CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgYnVuZGxlSWQgPSBnZXRPd24oYnVuZGxlc01hcCwgbW9kdWxlTmFtZSk7CgogICAgICAgICAgICAgICAgaWYgKGJ1bmRsZUlkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGNvbnRleHQubmFtZVRvVXJsKGJ1bmRsZUlkLCBleHQsIHNraXBFeHQpOwogICAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICAgIC8vSWYgYSBjb2xvbiBpcyBpbiB0aGUgVVJMLCBpdCBpbmRpY2F0ZXMgYSBwcm90b2NvbCBpcyB1c2VkIGFuZCBpdCBpcyBqdXN0CiAgICAgICAgICAgICAgICAvL2FuIFVSTCB0byBhIGZpbGUsIG9yIGlmIGl0IHN0YXJ0cyB3aXRoIGEgc2xhc2gsIGNvbnRhaW5zIGEgcXVlcnkgYXJnIChpLmUuID8pCiAgICAgICAgICAgICAgICAvL29yIGVuZHMgd2l0aCAuanMsIHRoZW4gYXNzdW1lIHRoZSB1c2VyIG1lYW50IHRvIHVzZSBhbiB1cmwgYW5kIG5vdCBhIG1vZHVsZSBpZC4KICAgICAgICAgICAgICAgIC8vVGhlIHNsYXNoIGlzIGltcG9ydGFudCBmb3IgcHJvdG9jb2wtbGVzcyBVUkxzIGFzIHdlbGwgYXMgZnVsbCBwYXRocy4KICAgICAgICAgICAgICAgIGlmIChyZXEuanNFeHRSZWdFeHAudGVzdChtb2R1bGVOYW1lKSkgewogICAgICAgICAgICAgICAgICAgIC8vSnVzdCBhIHBsYWluIHBhdGgsIG5vdCBtb2R1bGUgbmFtZSBsb29rdXAsIHNvIGp1c3QgcmV0dXJuIGl0LgogICAgICAgICAgICAgICAgICAgIC8vQWRkIGV4dGVuc2lvbiBpZiBpdCBpcyBpbmNsdWRlZC4gVGhpcyBpcyBhIGJpdCB3b25reSwgb25seSBub24tLmpzIHRoaW5ncyBwYXNzCiAgICAgICAgICAgICAgICAgICAgLy9hbiBleHRlbnNpb24sIHRoaXMgbWV0aG9kIHByb2JhYmx5IG5lZWRzIHRvIGJlIHJld29ya2VkLgogICAgICAgICAgICAgICAgICAgIHVybCA9IG1vZHVsZU5hbWUgKyAoZXh0IHx8ICcnKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgLy9BIG1vZHVsZSB0aGF0IG5lZWRzIHRvIGJlIGNvbnZlcnRlZCB0byBhIHBhdGguCiAgICAgICAgICAgICAgICAgICAgcGF0aHMgPSBjb25maWcucGF0aHM7CgogICAgICAgICAgICAgICAgICAgIHN5bXMgPSBtb2R1bGVOYW1lLnNwbGl0KCcvJyk7CiAgICAgICAgICAgICAgICAgICAgLy9Gb3IgZWFjaCBtb2R1bGUgbmFtZSBzZWdtZW50LCBzZWUgaWYgdGhlcmUgaXMgYSBwYXRoCiAgICAgICAgICAgICAgICAgICAgLy9yZWdpc3RlcmVkIGZvciBpdC4gU3RhcnQgd2l0aCBtb3N0IHNwZWNpZmljIG5hbWUKICAgICAgICAgICAgICAgICAgICAvL2FuZCB3b3JrIHVwIGZyb20gaXQuCiAgICAgICAgICAgICAgICAgICAgZm9yIChpID0gc3ltcy5sZW5ndGg7IGkgPiAwOyBpIC09IDEpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcGFyZW50TW9kdWxlID0gc3ltcy5zbGljZSgwLCBpKS5qb2luKCcvJyk7CgogICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnRQYXRoID0gZ2V0T3duKHBhdGhzLCBwYXJlbnRNb2R1bGUpOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAocGFyZW50UGF0aCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy9JZiBhbiBhcnJheSwgaXQgbWVhbnMgdGhlcmUgYXJlIGEgZmV3IGNob2ljZXMsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvL0Nob29zZSB0aGUgb25lIHRoYXQgaXMgZGVzaXJlZAogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlzQXJyYXkocGFyZW50UGF0aCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnRQYXRoID0gcGFyZW50UGF0aFswXTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN5bXMuc3BsaWNlKDAsIGksIHBhcmVudFBhdGgpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgICAgIC8vSm9pbiB0aGUgcGF0aCBwYXJ0cyB0b2dldGhlciwgdGhlbiBmaWd1cmUgb3V0IGlmIGJhc2VVcmwgaXMgbmVlZGVkLgogICAgICAgICAgICAgICAgICAgIHVybCA9IHN5bXMuam9pbignLycpOwogICAgICAgICAgICAgICAgICAgIHVybCArPSAoZXh0IHx8ICgvXmRhdGFcOnxeYmxvYlw6fFw/Ly50ZXN0KHVybCkgfHwgc2tpcEV4dCA/ICcnIDogJy5qcycpKTsKICAgICAgICAgICAgICAgICAgICB1cmwgPSAodXJsLmNoYXJBdCgwKSA9PT0gJy8nIHx8IHVybC5tYXRjaCgvXltcd1wrXC5cLV0rOi8pID8gJycgOiBjb25maWcuYmFzZVVybCkgKyB1cmw7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgcmV0dXJuIGNvbmZpZy51cmxBcmdzICYmICEvXmJsb2JcOi8udGVzdCh1cmwpID8KICAgICAgICAgICAgICAgICAgICAgICB1cmwgKyBjb25maWcudXJsQXJncyhtb2R1bGVOYW1lLCB1cmwpIDogdXJsOwogICAgICAgICAgICB9LAoKICAgICAgICAgICAgLy9EZWxlZ2F0ZXMgdG8gcmVxLmxvYWQuIEJyb2tlbiBvdXQgYXMgYSBzZXBhcmF0ZSBmdW5jdGlvbiB0bwogICAgICAgICAgICAvL2FsbG93IG92ZXJyaWRpbmcgaW4gdGhlIG9wdGltaXplci4KICAgICAgICAgICAgbG9hZDogZnVuY3Rpb24gKGlkLCB1cmwpIHsKICAgICAgICAgICAgICAgIHJlcS5sb2FkKGNvbnRleHQsIGlkLCB1cmwpOwogICAgICAgICAgICB9LAoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEV4ZWN1dGVzIGEgbW9kdWxlIGNhbGxiYWNrIGZ1bmN0aW9uLiBCcm9rZW4gb3V0IGFzIGEgc2VwYXJhdGUgZnVuY3Rpb24KICAgICAgICAgICAgICogc29sZWx5IHRvIGFsbG93IHRoZSBidWlsZCBzeXN0ZW0gdG8gc2VxdWVuY2UgdGhlIGZpbGVzIGluIHRoZSBidWlsdAogICAgICAgICAgICAgKiBsYXllciBpbiB0aGUgcmlnaHQgc2VxdWVuY2UuCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBleGVjQ2I6IGZ1bmN0aW9uIChuYW1lLCBjYWxsYmFjaywgYXJncywgZXhwb3J0cykgewogICAgICAgICAgICAgICAgcmV0dXJuIGNhbGxiYWNrLmFwcGx5KGV4cG9ydHMsIGFyZ3MpOwogICAgICAgICAgICB9LAoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIGNhbGxiYWNrIGZvciBzY3JpcHQgbG9hZHMsIHVzZWQgdG8gY2hlY2sgc3RhdHVzIG9mIGxvYWRpbmcuCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIEBwYXJhbSB7RXZlbnR9IGV2dCB0aGUgZXZlbnQgZnJvbSB0aGUgYnJvd3NlciBmb3IgdGhlIHNjcmlwdAogICAgICAgICAgICAgKiB0aGF0IHdhcyBsb2FkZWQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBvblNjcmlwdExvYWQ6IGZ1bmN0aW9uIChldnQpIHsKICAgICAgICAgICAgICAgIC8vVXNpbmcgY3VycmVudFRhcmdldCBpbnN0ZWFkIG9mIHRhcmdldCBmb3IgRmlyZWZveCAyLjAncyBzYWtlLiBOb3QKICAgICAgICAgICAgICAgIC8vYWxsIG9sZCBicm93c2VycyB3aWxsIGJlIHN1cHBvcnRlZCwgYnV0IHRoaXMgb25lIHdhcyBlYXN5IGVub3VnaAogICAgICAgICAgICAgICAgLy90byBzdXBwb3J0IGFuZCBzdGlsbCBtYWtlcyBzZW5zZS4KICAgICAgICAgICAgICAgIGlmIChldnQudHlwZSA9PT0gJ2xvYWQnIHx8CiAgICAgICAgICAgICAgICAgICAgICAgIChyZWFkeVJlZ0V4cC50ZXN0KChldnQuY3VycmVudFRhcmdldCB8fCBldnQuc3JjRWxlbWVudCkucmVhZHlTdGF0ZSkpKSB7CiAgICAgICAgICAgICAgICAgICAgLy9SZXNldCBpbnRlcmFjdGl2ZSBzY3JpcHQgc28gYSBzY3JpcHQgbm9kZSBpcyBub3QgaGVsZCBvbnRvIGZvcgogICAgICAgICAgICAgICAgICAgIC8vdG8gbG9uZy4KICAgICAgICAgICAgICAgICAgICBpbnRlcmFjdGl2ZVNjcmlwdCA9IG51bGw7CgogICAgICAgICAgICAgICAgICAgIC8vUHVsbCBvdXQgdGhlIG5hbWUgb2YgdGhlIG1vZHVsZSBhbmQgdGhlIGNvbnRleHQuCiAgICAgICAgICAgICAgICAgICAgdmFyIGRhdGEgPSBnZXRTY3JpcHREYXRhKGV2dCk7CiAgICAgICAgICAgICAgICAgICAgY29udGV4dC5jb21wbGV0ZUxvYWQoZGF0YS5pZCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sCgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQ2FsbGJhY2sgZm9yIHNjcmlwdCBlcnJvcnMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBvblNjcmlwdEVycm9yOiBmdW5jdGlvbiAoZXZ0KSB7CiAgICAgICAgICAgICAgICB2YXIgZGF0YSA9IGdldFNjcmlwdERhdGEoZXZ0KTsKICAgICAgICAgICAgICAgIGlmICghaGFzUGF0aEZhbGxiYWNrKGRhdGEuaWQpKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHBhcmVudHMgPSBbXTsKICAgICAgICAgICAgICAgICAgICBlYWNoUHJvcChyZWdpc3RyeSwgZnVuY3Rpb24odmFsdWUsIGtleSkgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoa2V5LmluZGV4T2YoJ19AcicpICE9PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlYWNoKHZhbHVlLmRlcE1hcHMsIGZ1bmN0aW9uKGRlcE1hcCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChkZXBNYXAuaWQgPT09IGRhdGEuaWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyZW50cy5wdXNoKGtleSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9uRXJyb3IobWFrZUVycm9yKCdzY3JpcHRlcnJvcicsICdTY3JpcHQgZXJyb3IgZm9yICInICsgZGF0YS5pZCArCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIChwYXJlbnRzLmxlbmd0aCA/CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICciLCBuZWVkZWQgYnk6ICcgKyBwYXJlbnRzLmpvaW4oJywgJykgOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAnIicpLCBldnQsIFtkYXRhLmlkXSkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfTsKCiAgICAgICAgY29udGV4dC5yZXF1aXJlID0gY29udGV4dC5tYWtlUmVxdWlyZSgpOwogICAgICAgIHJldHVybiBjb250ZXh0OwogICAgfQoKICAgIC8qKgogICAgICogTWFpbiBlbnRyeSBwb2ludC4KICAgICAqCiAgICAgKiBJZiB0aGUgb25seSBhcmd1bWVudCB0byByZXF1aXJlIGlzIGEgc3RyaW5nLCB0aGVuIHRoZSBtb2R1bGUgdGhhdAogICAgICogaXMgcmVwcmVzZW50ZWQgYnkgdGhhdCBzdHJpbmcgaXMgZmV0Y2hlZCBmb3IgdGhlIGFwcHJvcHJpYXRlIGNvbnRleHQuCiAgICAgKgogICAgICogSWYgdGhlIGZpcnN0IGFyZ3VtZW50IGlzIGFuIGFycmF5LCB0aGVuIGl0IHdpbGwgYmUgdHJlYXRlZCBhcyBhbiBhcnJheQogICAgICogb2YgZGVwZW5kZW5jeSBzdHJpbmcgbmFtZXMgdG8gZmV0Y2guIEFuIG9wdGlvbmFsIGZ1bmN0aW9uIGNhbGxiYWNrIGNhbgogICAgICogYmUgc3BlY2lmaWVkIHRvIGV4ZWN1dGUgd2hlbiBhbGwgb2YgdGhvc2UgZGVwZW5kZW5jaWVzIGFyZSBhdmFpbGFibGUuCiAgICAgKgogICAgICogTWFrZSBhIGxvY2FsIHJlcSB2YXJpYWJsZSB0byBoZWxwIENhamEgY29tcGxpYW5jZSAoaXQgYXNzdW1lcyB0aGluZ3MKICAgICAqIG9uIGEgcmVxdWlyZSB0aGF0IGFyZSBub3Qgc3RhbmRhcmRpemVkKSwgYW5kIHRvIGdpdmUgYSBzaG9ydAogICAgICogbmFtZSBmb3IgbWluaWZpY2F0aW9uL2xvY2FsIHNjb3BlIHVzZS4KICAgICAqLwogICAgcmVxID0gcmVxdWlyZWpzID0gZnVuY3Rpb24gKGRlcHMsIGNhbGxiYWNrLCBlcnJiYWNrLCBvcHRpb25hbCkgewoKICAgICAgICAvL0ZpbmQgdGhlIHJpZ2h0IGNvbnRleHQsIHVzZSBkZWZhdWx0CiAgICAgICAgdmFyIGNvbnRleHQsIGNvbmZpZywKICAgICAgICAgICAgY29udGV4dE5hbWUgPSBkZWZDb250ZXh0TmFtZTsKCiAgICAgICAgLy8gRGV0ZXJtaW5lIGlmIGhhdmUgY29uZmlnIG9iamVjdCBpbiB0aGUgY2FsbC4KICAgICAgICBpZiAoIWlzQXJyYXkoZGVwcykgJiYgdHlwZW9mIGRlcHMgIT09ICdzdHJpbmcnKSB7CiAgICAgICAgICAgIC8vIGRlcHMgaXMgYSBjb25maWcgb2JqZWN0CiAgICAgICAgICAgIGNvbmZpZyA9IGRlcHM7CiAgICAgICAgICAgIGlmIChpc0FycmF5KGNhbGxiYWNrKSkgewogICAgICAgICAgICAgICAgLy8gQWRqdXN0IGFyZ3MgaWYgdGhlcmUgYXJlIGRlcGVuZGVuY2llcwogICAgICAgICAgICAgICAgZGVwcyA9IGNhbGxiYWNrOwogICAgICAgICAgICAgICAgY2FsbGJhY2sgPSBlcnJiYWNrOwogICAgICAgICAgICAgICAgZXJyYmFjayA9IG9wdGlvbmFsOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgZGVwcyA9IFtdOwogICAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAoY29uZmlnICYmIGNvbmZpZy5jb250ZXh0KSB7CiAgICAgICAgICAgIGNvbnRleHROYW1lID0gY29uZmlnLmNvbnRleHQ7CiAgICAgICAgfQoKICAgICAgICBjb250ZXh0ID0gZ2V0T3duKGNvbnRleHRzLCBjb250ZXh0TmFtZSk7CiAgICAgICAgaWYgKCFjb250ZXh0KSB7CiAgICAgICAgICAgIGNvbnRleHQgPSBjb250ZXh0c1tjb250ZXh0TmFtZV0gPSByZXEucy5uZXdDb250ZXh0KGNvbnRleHROYW1lKTsKICAgICAgICB9CgogICAgICAgIGlmIChjb25maWcpIHsKICAgICAgICAgICAgY29udGV4dC5jb25maWd1cmUoY29uZmlnKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBjb250ZXh0LnJlcXVpcmUoZGVwcywgY2FsbGJhY2ssIGVycmJhY2spOwogICAgfTsKCiAgICAvKioKICAgICAqIFN1cHBvcnQgcmVxdWlyZS5jb25maWcoKSB0byBtYWtlIGl0IGVhc2llciB0byBjb29wZXJhdGUgd2l0aCBvdGhlcgogICAgICogQU1EIGxvYWRlcnMgb24gZ2xvYmFsbHkgYWdyZWVkIG5hbWVzLgogICAgICovCiAgICByZXEuY29uZmlnID0gZnVuY3Rpb24gKGNvbmZpZykgewogICAgICAgIHJldHVybiByZXEoY29uZmlnKTsKICAgIH07CgogICAgLyoqCiAgICAgKiBFeGVjdXRlIHNvbWV0aGluZyBhZnRlciB0aGUgY3VycmVudCB0aWNrCiAgICAgKiBvZiB0aGUgZXZlbnQgbG9vcC4gT3ZlcnJpZGUgZm9yIG90aGVyIGVudnMKICAgICAqIHRoYXQgaGF2ZSBhIGJldHRlciBzb2x1dGlvbiB0aGFuIHNldFRpbWVvdXQuCiAgICAgKiBAcGFyYW0gIHtGdW5jdGlvbn0gZm4gZnVuY3Rpb24gdG8gZXhlY3V0ZSBsYXRlci4KICAgICAqLwogICAgcmVxLm5leHRUaWNrID0gdHlwZW9mIHNldFRpbWVvdXQgIT09ICd1bmRlZmluZWQnID8gZnVuY3Rpb24gKGZuKSB7CiAgICAgICAgc2V0VGltZW91dChmbiwgNCk7CiAgICB9IDogZnVuY3Rpb24gKGZuKSB7IGZuKCk7IH07CgogICAgLyoqCiAgICAgKiBFeHBvcnQgcmVxdWlyZSBhcyBhIGdsb2JhbCwgYnV0IG9ubHkgaWYgaXQgZG9lcyBub3QgYWxyZWFkeSBleGlzdC4KICAgICAqLwogICAgaWYgKCFyZXF1aXJlKSB7CiAgICAgICAgcmVxdWlyZSA9IHJlcTsKICAgIH0KCiAgICByZXEudmVyc2lvbiA9IHZlcnNpb247CgogICAgLy9Vc2VkIHRvIGZpbHRlciBvdXQgZGVwZW5kZW5jaWVzIHRoYXQgYXJlIGFscmVhZHkgcGF0aHMuCiAgICByZXEuanNFeHRSZWdFeHAgPSAvXlwvfDp8XD98XC5qcyQvOwogICAgcmVxLmlzQnJvd3NlciA9IGlzQnJvd3NlcjsKICAgIHMgPSByZXEucyA9IHsKICAgICAgICBjb250ZXh0czogY29udGV4dHMsCiAgICAgICAgbmV3Q29udGV4dDogbmV3Q29udGV4dAogICAgfTsKCiAgICAvL0NyZWF0ZSBkZWZhdWx0IGNvbnRleHQuCiAgICByZXEoe30pOwoKICAgIC8vRXhwb3J0cyBzb21lIGNvbnRleHQtc2Vuc2l0aXZlIG1ldGhvZHMgb24gZ2xvYmFsIHJlcXVpcmUuCiAgICBlYWNoKFsKICAgICAgICAndG9VcmwnLAogICAgICAgICd1bmRlZicsCiAgICAgICAgJ2RlZmluZWQnLAogICAgICAgICdzcGVjaWZpZWQnCiAgICBdLCBmdW5jdGlvbiAocHJvcCkgewogICAgICAgIC8vUmVmZXJlbmNlIGZyb20gY29udGV4dHMgaW5zdGVhZCBvZiBlYXJseSBiaW5kaW5nIHRvIGRlZmF1bHQgY29udGV4dCwKICAgICAgICAvL3NvIHRoYXQgZHVyaW5nIGJ1aWxkcywgdGhlIGxhdGVzdCBpbnN0YW5jZSBvZiB0aGUgZGVmYXVsdCBjb250ZXh0CiAgICAgICAgLy93aXRoIGl0cyBjb25maWcgZ2V0cyB1c2VkLgogICAgICAgIHJlcVtwcm9wXSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGN0eCA9IGNvbnRleHRzW2RlZkNvbnRleHROYW1lXTsKICAgICAgICAgICAgcmV0dXJuIGN0eC5yZXF1aXJlW3Byb3BdLmFwcGx5KGN0eCwgYXJndW1lbnRzKTsKICAgICAgICB9OwogICAgfSk7CgogICAgaWYgKGlzQnJvd3NlcikgewogICAgICAgIGhlYWQgPSBzLmhlYWQgPSBkb2N1bWVudC5nZXRFbGVtZW50c0J5VGFnTmFtZSgnaGVhZCcpWzBdOwogICAgICAgIC8vSWYgQkFTRSB0YWcgaXMgaW4gcGxheSwgdXNpbmcgYXBwZW5kQ2hpbGQgaXMgYSBwcm9ibGVtIGZvciBJRTYuCiAgICAgICAgLy9XaGVuIHRoYXQgYnJvd3NlciBkaWVzLCB0aGlzIGNhbiBiZSByZW1vdmVkLiBEZXRhaWxzIGluIHRoaXMgalF1ZXJ5IGJ1ZzoKICAgICAgICAvL2h0dHA6Ly9kZXYuanF1ZXJ5LmNvbS90aWNrZXQvMjcwOQogICAgICAgIGJhc2VFbGVtZW50ID0gZG9jdW1lbnQuZ2V0RWxlbWVudHNCeVRhZ05hbWUoJ2Jhc2UnKVswXTsKICAgICAgICBpZiAoYmFzZUVsZW1lbnQpIHsKICAgICAgICAgICAgaGVhZCA9IHMuaGVhZCA9IGJhc2VFbGVtZW50LnBhcmVudE5vZGU7CiAgICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQW55IGVycm9ycyB0aGF0IHJlcXVpcmUgZXhwbGljaXRseSBnZW5lcmF0ZXMgd2lsbCBiZSBwYXNzZWQgdG8gdGhpcwogICAgICogZnVuY3Rpb24uIEludGVyY2VwdC9vdmVycmlkZSBpdCBpZiB5b3Ugd2FudCBjdXN0b20gZXJyb3IgaGFuZGxpbmcuCiAgICAgKiBAcGFyYW0ge0Vycm9yfSBlcnIgdGhlIGVycm9yIG9iamVjdC4KICAgICAqLwogICAgcmVxLm9uRXJyb3IgPSBkZWZhdWx0T25FcnJvcjsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgdGhlIG5vZGUgZm9yIHRoZSBsb2FkIGNvbW1hbmQuIE9ubHkgdXNlZCBpbiBicm93c2VyIGVudnMuCiAgICAgKi8KICAgIHJlcS5jcmVhdGVOb2RlID0gZnVuY3Rpb24gKGNvbmZpZywgbW9kdWxlTmFtZSwgdXJsKSB7CiAgICAgICAgdmFyIG5vZGUgPSBjb25maWcueGh0bWwgPwogICAgICAgICAgICAgICAgZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCdodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sJywgJ2h0bWw6c2NyaXB0JykgOgogICAgICAgICAgICAgICAgZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc2NyaXB0Jyk7CiAgICAgICAgbm9kZS50eXBlID0gY29uZmlnLnNjcmlwdFR5cGUgfHwgJ3RleHQvamF2YXNjcmlwdCc7CiAgICAgICAgbm9kZS5jaGFyc2V0ID0gJ3V0Zi04JzsKICAgICAgICBub2RlLmFzeW5jID0gdHJ1ZTsKICAgICAgICByZXR1cm4gbm9kZTsKICAgIH07CgogICAgLyoqCiAgICAgKiBEb2VzIHRoZSByZXF1ZXN0IHRvIGxvYWQgYSBtb2R1bGUgZm9yIHRoZSBicm93c2VyIGNhc2UuCiAgICAgKiBNYWtlIHRoaXMgYSBzZXBhcmF0ZSBmdW5jdGlvbiB0byBhbGxvdyBvdGhlciBlbnZpcm9ubWVudHMKICAgICAqIHRvIG92ZXJyaWRlIGl0LgogICAgICoKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBjb250ZXh0IHRoZSByZXF1aXJlIGNvbnRleHQgdG8gZmluZCBzdGF0ZS4KICAgICAqIEBwYXJhbSB7U3RyaW5nfSBtb2R1bGVOYW1lIHRoZSBuYW1lIG9mIHRoZSBtb2R1bGUuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gdXJsIHRoZSBVUkwgdG8gdGhlIG1vZHVsZS4KICAgICAqLwogICAgcmVxLmxvYWQgPSBmdW5jdGlvbiAoY29udGV4dCwgbW9kdWxlTmFtZSwgdXJsKSB7CiAgICAgICAgdmFyIGNvbmZpZyA9IChjb250ZXh0ICYmIGNvbnRleHQuY29uZmlnKSB8fCB7fSwKICAgICAgICAgICAgbm9kZTsKICAgICAgICBpZiAoaXNCcm93c2VyKSB7CiAgICAgICAgICAgIC8vSW4gdGhlIGJyb3dzZXIgc28gdXNlIGEgc2NyaXB0IHRhZwogICAgICAgICAgICBub2RlID0gcmVxLmNyZWF0ZU5vZGUoY29uZmlnLCBtb2R1bGVOYW1lLCB1cmwpOwoKICAgICAgICAgICAgbm9kZS5zZXRBdHRyaWJ1dGUoJ2RhdGEtcmVxdWlyZWNvbnRleHQnLCBjb250ZXh0LmNvbnRleHROYW1lKTsKICAgICAgICAgICAgbm9kZS5zZXRBdHRyaWJ1dGUoJ2RhdGEtcmVxdWlyZW1vZHVsZScsIG1vZHVsZU5hbWUpOwoKICAgICAgICAgICAgLy9TZXQgdXAgbG9hZCBsaXN0ZW5lci4gVGVzdCBhdHRhY2hFdmVudCBmaXJzdCBiZWNhdXNlIElFOSBoYXMKICAgICAgICAgICAgLy9hIHN1YnRsZSBpc3N1ZSBpbiBpdHMgYWRkRXZlbnRMaXN0ZW5lciBhbmQgc2NyaXB0IG9ubG9hZCBmaXJpbmdzCiAgICAgICAgICAgIC8vdGhhdCBkbyBub3QgbWF0Y2ggdGhlIGJlaGF2aW9yIG9mIGFsbCBvdGhlciBicm93c2VycyB3aXRoCiAgICAgICAgICAgIC8vYWRkRXZlbnRMaXN0ZW5lciBzdXBwb3J0LCB3aGljaCBmaXJlIHRoZSBvbmxvYWQgZXZlbnQgZm9yIGEKICAgICAgICAgICAgLy9zY3JpcHQgcmlnaHQgYWZ0ZXIgdGhlIHNjcmlwdCBleGVjdXRpb24uIFNlZToKICAgICAgICAgICAgLy9odHRwczovL2Nvbm5lY3QubWljcm9zb2Z0LmNvbS9JRS9mZWVkYmFjay9kZXRhaWxzLzY0ODA1Ny9zY3JpcHQtb25sb2FkLWV2ZW50LWlzLW5vdC1maXJlZC1pbW1lZGlhdGVseS1hZnRlci1zY3JpcHQtZXhlY3V0aW9uCiAgICAgICAgICAgIC8vVU5GT1JUVU5BVEVMWSBPcGVyYSBpbXBsZW1lbnRzIGF0dGFjaEV2ZW50IGJ1dCBkb2VzIG5vdCBmb2xsb3cgdGhlIHNjcmlwdAogICAgICAgICAgICAvL3NjcmlwdCBleGVjdXRpb24gbW9kZS4KICAgICAgICAgICAgaWYgKG5vZGUuYXR0YWNoRXZlbnQgJiYKICAgICAgICAgICAgICAgICAgICAvL0NoZWNrIGlmIG5vZGUuYXR0YWNoRXZlbnQgaXMgYXJ0aWZpY2lhbGx5IGFkZGVkIGJ5IGN1c3RvbSBzY3JpcHQgb3IKICAgICAgICAgICAgICAgICAgICAvL25hdGl2ZWx5IHN1cHBvcnRlZCBieSBicm93c2VyCiAgICAgICAgICAgICAgICAgICAgLy9yZWFkIGh0dHBzOi8vZ2l0aHViLmNvbS9yZXF1aXJlanMvcmVxdWlyZWpzL2lzc3Vlcy8xODcKICAgICAgICAgICAgICAgICAgICAvL2lmIHdlIGNhbiBOT1QgZmluZCBbbmF0aXZlIGNvZGVdIHRoZW4gaXQgbXVzdCBOT1QgbmF0aXZlbHkgc3VwcG9ydGVkLgogICAgICAgICAgICAgICAgICAgIC8vaW4gSUU4LCBub2RlLmF0dGFjaEV2ZW50IGRvZXMgbm90IGhhdmUgdG9TdHJpbmcoKQogICAgICAgICAgICAgICAgICAgIC8vTm90ZSB0aGUgdGVzdCBmb3IgIltuYXRpdmUgY29kZSIgd2l0aCBubyBjbG9zaW5nIGJyYWNlLCBzZWU6CiAgICAgICAgICAgICAgICAgICAgLy9odHRwczovL2dpdGh1Yi5jb20vcmVxdWlyZWpzL3JlcXVpcmVqcy9pc3N1ZXMvMjczCiAgICAgICAgICAgICAgICAgICAgIShub2RlLmF0dGFjaEV2ZW50LnRvU3RyaW5nICYmIG5vZGUuYXR0YWNoRXZlbnQudG9TdHJpbmcoKS5pbmRleE9mKCdbbmF0aXZlIGNvZGUnKSA8IDApICYmCiAgICAgICAgICAgICAgICAgICAgIWlzT3BlcmEpIHsKICAgICAgICAgICAgICAgIC8vUHJvYmFibHkgSUUuIElFIChhdCBsZWFzdCA2LTgpIGRvIG5vdCBmaXJlCiAgICAgICAgICAgICAgICAvL3NjcmlwdCBvbmxvYWQgcmlnaHQgYWZ0ZXIgZXhlY3V0aW5nIHRoZSBzY3JpcHQsIHNvCiAgICAgICAgICAgICAgICAvL3dlIGNhbm5vdCB0aWUgdGhlIGFub255bW91cyBkZWZpbmUgY2FsbCB0byBhIG5hbWUuCiAgICAgICAgICAgICAgICAvL0hvd2V2ZXIsIElFIHJlcG9ydHMgdGhlIHNjcmlwdCBhcyBiZWluZyBpbiAnaW50ZXJhY3RpdmUnCiAgICAgICAgICAgICAgICAvL3JlYWR5U3RhdGUgYXQgdGhlIHRpbWUgb2YgdGhlIGRlZmluZSBjYWxsLgogICAgICAgICAgICAgICAgdXNlSW50ZXJhY3RpdmUgPSB0cnVlOwoKICAgICAgICAgICAgICAgIG5vZGUuYXR0YWNoRXZlbnQoJ29ucmVhZHlzdGF0ZWNoYW5nZScsIGNvbnRleHQub25TY3JpcHRMb2FkKTsKICAgICAgICAgICAgICAgIC8vSXQgd291bGQgYmUgZ3JlYXQgdG8gYWRkIGFuIGVycm9yIGhhbmRsZXIgaGVyZSB0byBjYXRjaAogICAgICAgICAgICAgICAgLy80MDRzIGluIElFOSsuIEhvd2V2ZXIsIG9ucmVhZHlzdGF0ZWNoYW5nZSB3aWxsIGZpcmUgYmVmb3JlCiAgICAgICAgICAgICAgICAvL3RoZSBlcnJvciBoYW5kbGVyLCBzbyB0aGF0IGRvZXMgbm90IGhlbHAuIElmIGFkZEV2ZW50TGlzdGVuZXIKICAgICAgICAgICAgICAgIC8vaXMgdXNlZCwgdGhlbiBJRSB3aWxsIGZpcmUgZXJyb3IgYmVmb3JlIGxvYWQsIGJ1dCB3ZSBjYW5ub3QKICAgICAgICAgICAgICAgIC8vdXNlIHRoYXQgcGF0aHdheSBnaXZlbiB0aGUgY29ubmVjdC5taWNyb3NvZnQuY29tIGlzc3VlCiAgICAgICAgICAgICAgICAvL21lbnRpb25lZCBhYm92ZSBhYm91dCBub3QgZG9pbmcgdGhlICdzY3JpcHQgZXhlY3V0ZSwKICAgICAgICAgICAgICAgIC8vdGhlbiBmaXJlIHRoZSBzY3JpcHQgbG9hZCBldmVudCBsaXN0ZW5lciBiZWZvcmUgZXhlY3V0ZQogICAgICAgICAgICAgICAgLy9uZXh0IHNjcmlwdCcgdGhhdCBvdGhlciBicm93c2VycyBkby4KICAgICAgICAgICAgICAgIC8vQmVzdCBob3BlOiBJRTEwIGZpeGVzIHRoZSBpc3N1ZXMsCiAgICAgICAgICAgICAgICAvL2FuZCB0aGVuIGRlc3Ryb3lzIGFsbCBpbnN0YWxscyBvZiBJRSA2LTkuCiAgICAgICAgICAgICAgICAvL25vZGUuYXR0YWNoRXZlbnQoJ29uZXJyb3InLCBjb250ZXh0Lm9uU2NyaXB0RXJyb3IpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgbm9kZS5hZGRFdmVudExpc3RlbmVyKCdsb2FkJywgY29udGV4dC5vblNjcmlwdExvYWQsIGZhbHNlKTsKICAgICAgICAgICAgICAgIG5vZGUuYWRkRXZlbnRMaXN0ZW5lcignZXJyb3InLCBjb250ZXh0Lm9uU2NyaXB0RXJyb3IsIGZhbHNlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBub2RlLnNyYyA9IHVybDsKCiAgICAgICAgICAgIC8vQ2FsbGluZyBvbk5vZGVDcmVhdGVkIGFmdGVyIGFsbCBwcm9wZXJ0aWVzIG9uIHRoZSBub2RlIGhhdmUgYmVlbgogICAgICAgICAgICAvL3NldCwgYnV0IGJlZm9yZSBpdCBpcyBwbGFjZWQgaW4gdGhlIERPTS4KICAgICAgICAgICAgaWYgKGNvbmZpZy5vbk5vZGVDcmVhdGVkKSB7CiAgICAgICAgICAgICAgICBjb25maWcub25Ob2RlQ3JlYXRlZChub2RlLCBjb25maWcsIG1vZHVsZU5hbWUsIHVybCk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIC8vRm9yIHNvbWUgY2FjaGUgY2FzZXMgaW4gSUUgNi04LCB0aGUgc2NyaXB0IGV4ZWN1dGVzIGJlZm9yZSB0aGUgZW5kCiAgICAgICAgICAgIC8vb2YgdGhlIGFwcGVuZENoaWxkIGV4ZWN1dGlvbiwgc28gdG8gdGllIGFuIGFub255bW91cyBkZWZpbmUKICAgICAgICAgICAgLy9jYWxsIHRvIHRoZSBtb2R1bGUgbmFtZSAod2hpY2ggaXMgc3RvcmVkIG9uIHRoZSBub2RlKSwgaG9sZCBvbgogICAgICAgICAgICAvL3RvIGEgcmVmZXJlbmNlIHRvIHRoaXMgbm9kZSwgYnV0IGNsZWFyIGFmdGVyIHRoZSBET00gaW5zZXJ0aW9uLgogICAgICAgICAgICBjdXJyZW50bHlBZGRpbmdTY3JpcHQgPSBub2RlOwogICAgICAgICAgICBpZiAoYmFzZUVsZW1lbnQpIHsKICAgICAgICAgICAgICAgIGhlYWQuaW5zZXJ0QmVmb3JlKG5vZGUsIGJhc2VFbGVtZW50KTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIGhlYWQuYXBwZW5kQ2hpbGQobm9kZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY3VycmVudGx5QWRkaW5nU2NyaXB0ID0gbnVsbDsKCiAgICAgICAgICAgIHJldHVybiBub2RlOwogICAgICAgIH0gZWxzZSBpZiAoaXNXZWJXb3JrZXIpIHsKICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgIC8vSW4gYSB3ZWIgd29ya2VyLCB1c2UgaW1wb3J0U2NyaXB0cy4gVGhpcyBpcyBub3QgYSB2ZXJ5CiAgICAgICAgICAgICAgICAvL2VmZmljaWVudCB1c2Ugb2YgaW1wb3J0U2NyaXB0cywgaW1wb3J0U2NyaXB0cyB3aWxsIGJsb2NrIHVudGlsCiAgICAgICAgICAgICAgICAvL2l0cyBzY3JpcHQgaXMgZG93bmxvYWRlZCBhbmQgZXZhbHVhdGVkLiBIb3dldmVyLCBpZiB3ZWIgd29ya2VycwogICAgICAgICAgICAgICAgLy9hcmUgaW4gcGxheSwgdGhlIGV4cGVjdGF0aW9uIGlzIHRoYXQgYSBidWlsZCBoYXMgYmVlbiBkb25lIHNvCiAgICAgICAgICAgICAgICAvL3RoYXQgb25seSBvbmUgc2NyaXB0IG5lZWRzIHRvIGJlIGxvYWRlZCBhbnl3YXkuIFRoaXMgbWF5IG5lZWQKICAgICAgICAgICAgICAgIC8vdG8gYmUgcmVldmFsdWF0ZWQgaWYgb3RoZXIgdXNlIGNhc2VzIGJlY29tZSBjb21tb24uCgogICAgICAgICAgICAgICAgLy8gUG9zdCBhIHRhc2sgdG8gdGhlIGV2ZW50IGxvb3AgdG8gd29yayBhcm91bmQgYSBidWcgaW4gV2ViS2l0CiAgICAgICAgICAgICAgICAvLyB3aGVyZSB0aGUgd29ya2VyIGdldHMgZ2FyYmFnZS1jb2xsZWN0ZWQgYWZ0ZXIgY2FsbGluZwogICAgICAgICAgICAgICAgLy8gaW1wb3J0U2NyaXB0cygpOiBodHRwczovL3dlYmtpdC5vcmcvYi8xNTMzMTcKICAgICAgICAgICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7fSwgMCk7CiAgICAgICAgICAgICAgICBpbXBvcnRTY3JpcHRzKHVybCk7CgogICAgICAgICAgICAgICAgLy9BY2NvdW50IGZvciBhbm9ueW1vdXMgbW9kdWxlcwogICAgICAgICAgICAgICAgY29udGV4dC5jb21wbGV0ZUxvYWQobW9kdWxlTmFtZSk7CiAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgIGNvbnRleHQub25FcnJvcihtYWtlRXJyb3IoJ2ltcG9ydHNjcmlwdHMnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICdpbXBvcnRTY3JpcHRzIGZhaWxlZCBmb3IgJyArCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG1vZHVsZU5hbWUgKyAnIGF0ICcgKyB1cmwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbbW9kdWxlTmFtZV0pKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gZ2V0SW50ZXJhY3RpdmVTY3JpcHQoKSB7CiAgICAgICAgaWYgKGludGVyYWN0aXZlU2NyaXB0ICYmIGludGVyYWN0aXZlU2NyaXB0LnJlYWR5U3RhdGUgPT09ICdpbnRlcmFjdGl2ZScpIHsKICAgICAgICAgICAgcmV0dXJuIGludGVyYWN0aXZlU2NyaXB0OwogICAgICAgIH0KCiAgICAgICAgZWFjaFJldmVyc2Uoc2NyaXB0cygpLCBmdW5jdGlvbiAoc2NyaXB0KSB7CiAgICAgICAgICAgIGlmIChzY3JpcHQucmVhZHlTdGF0ZSA9PT0gJ2ludGVyYWN0aXZlJykgewogICAgICAgICAgICAgICAgcmV0dXJuIChpbnRlcmFjdGl2ZVNjcmlwdCA9IHNjcmlwdCk7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICByZXR1cm4gaW50ZXJhY3RpdmVTY3JpcHQ7CiAgICB9CgogICAgLy9Mb29rIGZvciBhIGRhdGEtbWFpbiBzY3JpcHQgYXR0cmlidXRlLCB3aGljaCBjb3VsZCBhbHNvIGFkanVzdCB0aGUgYmFzZVVybC4KICAgIGlmIChpc0Jyb3dzZXIgJiYgIWNmZy5za2lwRGF0YU1haW4pIHsKICAgICAgICAvL0ZpZ3VyZSBvdXQgYmFzZVVybC4gR2V0IGl0IGZyb20gdGhlIHNjcmlwdCB0YWcgd2l0aCByZXF1aXJlLmpzIGluIGl0LgogICAgICAgIGVhY2hSZXZlcnNlKHNjcmlwdHMoKSwgZnVuY3Rpb24gKHNjcmlwdCkgewogICAgICAgICAgICAvL1NldCB0aGUgJ2hlYWQnIHdoZXJlIHdlIGNhbiBhcHBlbmQgY2hpbGRyZW4gYnkKICAgICAgICAgICAgLy91c2luZyB0aGUgc2NyaXB0J3MgcGFyZW50LgogICAgICAgICAgICBpZiAoIWhlYWQpIHsKICAgICAgICAgICAgICAgIGhlYWQgPSBzY3JpcHQucGFyZW50Tm9kZTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgLy9Mb29rIGZvciBhIGRhdGEtbWFpbiBhdHRyaWJ1dGUgdG8gc2V0IG1haW4gc2NyaXB0IGZvciB0aGUgcGFnZQogICAgICAgICAgICAvL3RvIGxvYWQuIElmIGl0IGlzIHRoZXJlLCB0aGUgcGF0aCB0byBkYXRhIG1haW4gYmVjb21lcyB0aGUKICAgICAgICAgICAgLy9iYXNlVXJsLCBpZiBpdCBpcyBub3QgYWxyZWFkeSBzZXQuCiAgICAgICAgICAgIGRhdGFNYWluID0gc2NyaXB0LmdldEF0dHJpYnV0ZSgnZGF0YS1tYWluJyk7CiAgICAgICAgICAgIGlmIChkYXRhTWFpbikgewogICAgICAgICAgICAgICAgLy9QcmVzZXJ2ZSBkYXRhTWFpbiBpbiBjYXNlIGl0IGlzIGEgcGF0aCAoaS5lLiBjb250YWlucyAnPycpCiAgICAgICAgICAgICAgICBtYWluU2NyaXB0ID0gZGF0YU1haW47CgogICAgICAgICAgICAgICAgLy9TZXQgZmluYWwgYmFzZVVybCBpZiB0aGVyZSBpcyBub3QgYWxyZWFkeSBhbiBleHBsaWNpdCBvbmUsCiAgICAgICAgICAgICAgICAvL2J1dCBvbmx5IGRvIHNvIGlmIHRoZSBkYXRhLW1haW4gdmFsdWUgaXMgbm90IGEgbG9hZGVyIHBsdWdpbgogICAgICAgICAgICAgICAgLy9tb2R1bGUgSUQuCiAgICAgICAgICAgICAgICBpZiAoIWNmZy5iYXNlVXJsICYmIG1haW5TY3JpcHQuaW5kZXhPZignIScpID09PSAtMSkgewogICAgICAgICAgICAgICAgICAgIC8vUHVsbCBvZmYgdGhlIGRpcmVjdG9yeSBvZiBkYXRhLW1haW4gZm9yIHVzZSBhcyB0aGUKICAgICAgICAgICAgICAgICAgICAvL2Jhc2VVcmwuCiAgICAgICAgICAgICAgICAgICAgc3JjID0gbWFpblNjcmlwdC5zcGxpdCgnLycpOwogICAgICAgICAgICAgICAgICAgIG1haW5TY3JpcHQgPSBzcmMucG9wKCk7CiAgICAgICAgICAgICAgICAgICAgc3ViUGF0aCA9IHNyYy5sZW5ndGggPyBzcmMuam9pbignLycpICArICcvJyA6ICcuLyc7CgogICAgICAgICAgICAgICAgICAgIGNmZy5iYXNlVXJsID0gc3ViUGF0aDsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAvL1N0cmlwIG9mZiBhbnkgdHJhaWxpbmcgLmpzIHNpbmNlIG1haW5TY3JpcHQgaXMgbm93CiAgICAgICAgICAgICAgICAvL2xpa2UgYSBtb2R1bGUgbmFtZS4KICAgICAgICAgICAgICAgIG1haW5TY3JpcHQgPSBtYWluU2NyaXB0LnJlcGxhY2UoanNTdWZmaXhSZWdFeHAsICcnKTsKCiAgICAgICAgICAgICAgICAvL0lmIG1haW5TY3JpcHQgaXMgc3RpbGwgYSBwYXRoLCBmYWxsIGJhY2sgdG8gZGF0YU1haW4KICAgICAgICAgICAgICAgIGlmIChyZXEuanNFeHRSZWdFeHAudGVzdChtYWluU2NyaXB0KSkgewogICAgICAgICAgICAgICAgICAgIG1haW5TY3JpcHQgPSBkYXRhTWFpbjsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICAvL1B1dCB0aGUgZGF0YS1tYWluIHNjcmlwdCBpbiB0aGUgZmlsZXMgdG8gbG9hZC4KICAgICAgICAgICAgICAgIGNmZy5kZXBzID0gY2ZnLmRlcHMgPyBjZmcuZGVwcy5jb25jYXQobWFpblNjcmlwdCkgOiBbbWFpblNjcmlwdF07CgogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgIH0KCiAgICAvKioKICAgICAqIFRoZSBmdW5jdGlvbiB0aGF0IGhhbmRsZXMgZGVmaW5pdGlvbnMgb2YgbW9kdWxlcy4gRGlmZmVycyBmcm9tCiAgICAgKiByZXF1aXJlKCkgaW4gdGhhdCBhIHN0cmluZyBmb3IgdGhlIG1vZHVsZSBzaG91bGQgYmUgdGhlIGZpcnN0IGFyZ3VtZW50LAogICAgICogYW5kIHRoZSBmdW5jdGlvbiB0byBleGVjdXRlIGFmdGVyIGRlcGVuZGVuY2llcyBhcmUgbG9hZGVkIHNob3VsZAogICAgICogcmV0dXJuIGEgdmFsdWUgdG8gZGVmaW5lIHRoZSBtb2R1bGUgY29ycmVzcG9uZGluZyB0byB0aGUgZmlyc3QgYXJndW1lbnQncwogICAgICogbmFtZS4KICAgICAqLwogICAgZGVmaW5lID0gZnVuY3Rpb24gKG5hbWUsIGRlcHMsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIG5vZGUsIGNvbnRleHQ7CgogICAgICAgIC8vQWxsb3cgZm9yIGFub255bW91cyBtb2R1bGVzCiAgICAgICAgaWYgKHR5cGVvZiBuYW1lICE9PSAnc3RyaW5nJykgewogICAgICAgICAgICAvL0FkanVzdCBhcmdzIGFwcHJvcHJpYXRlbHkKICAgICAgICAgICAgY2FsbGJhY2sgPSBkZXBzOwogICAgICAgICAgICBkZXBzID0gbmFtZTsKICAgICAgICAgICAgbmFtZSA9IG51bGw7CiAgICAgICAgfQoKICAgICAgICAvL1RoaXMgbW9kdWxlIG1heSBub3QgaGF2ZSBkZXBlbmRlbmNpZXMKICAgICAgICBpZiAoIWlzQXJyYXkoZGVwcykpIHsKICAgICAgICAgICAgY2FsbGJhY2sgPSBkZXBzOwogICAgICAgICAgICBkZXBzID0gbnVsbDsKICAgICAgICB9CgogICAgICAgIC8vSWYgbm8gbmFtZSwgYW5kIGNhbGxiYWNrIGlzIGEgZnVuY3Rpb24sIHRoZW4gZmlndXJlIG91dCBpZiBpdCBhCiAgICAgICAgLy9Db21tb25KUyB0aGluZyB3aXRoIGRlcGVuZGVuY2llcy4KICAgICAgICBpZiAoIWRlcHMgJiYgaXNGdW5jdGlvbihjYWxsYmFjaykpIHsKICAgICAgICAgICAgZGVwcyA9IFtdOwogICAgICAgICAgICAvL1JlbW92ZSBjb21tZW50cyBmcm9tIHRoZSBjYWxsYmFjayBzdHJpbmcsCiAgICAgICAgICAgIC8vbG9vayBmb3IgcmVxdWlyZSBjYWxscywgYW5kIHB1bGwgdGhlbSBpbnRvIHRoZSBkZXBlbmRlbmNpZXMsCiAgICAgICAgICAgIC8vYnV0IG9ubHkgaWYgdGhlcmUgYXJlIGZ1bmN0aW9uIGFyZ3MuCiAgICAgICAgICAgIGlmIChjYWxsYmFjay5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIGNhbGxiYWNrCiAgICAgICAgICAgICAgICAgICAgLnRvU3RyaW5nKCkKICAgICAgICAgICAgICAgICAgICAucmVwbGFjZShjb21tZW50UmVnRXhwLCBjb21tZW50UmVwbGFjZSkKICAgICAgICAgICAgICAgICAgICAucmVwbGFjZShjanNSZXF1aXJlUmVnRXhwLCBmdW5jdGlvbiAobWF0Y2gsIGRlcCkgewogICAgICAgICAgICAgICAgICAgICAgICBkZXBzLnB1c2goZGVwKTsKICAgICAgICAgICAgICAgICAgICB9KTsKCiAgICAgICAgICAgICAgICAvL01heSBiZSBhIENvbW1vbkpTIHRoaW5nIGV2ZW4gd2l0aG91dCByZXF1aXJlIGNhbGxzLCBidXQgc3RpbGwKICAgICAgICAgICAgICAgIC8vY291bGQgdXNlIGV4cG9ydHMsIGFuZCBtb2R1bGUuIEF2b2lkIGRvaW5nIGV4cG9ydHMgYW5kIG1vZHVsZQogICAgICAgICAgICAgICAgLy93b3JrIHRob3VnaCBpZiBpdCBqdXN0IG5lZWRzIHJlcXVpcmUuCiAgICAgICAgICAgICAgICAvL1JFUVVJUkVTIHRoZSBmdW5jdGlvbiB0byBleHBlY3QgdGhlIENvbW1vbkpTIHZhcmlhYmxlcyBpbiB0aGUKICAgICAgICAgICAgICAgIC8vb3JkZXIgbGlzdGVkIGJlbG93LgogICAgICAgICAgICAgICAgZGVwcyA9IChjYWxsYmFjay5sZW5ndGggPT09IDEgPyBbJ3JlcXVpcmUnXSA6IFsncmVxdWlyZScsICdleHBvcnRzJywgJ21vZHVsZSddKS5jb25jYXQoZGVwcyk7CiAgICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vSWYgaW4gSUUgNi04IGFuZCBoaXQgYW4gYW5vbnltb3VzIGRlZmluZSgpIGNhbGwsIGRvIHRoZSBpbnRlcmFjdGl2ZQogICAgICAgIC8vd29yay4KICAgICAgICBpZiAodXNlSW50ZXJhY3RpdmUpIHsKICAgICAgICAgICAgbm9kZSA9IGN1cnJlbnRseUFkZGluZ1NjcmlwdCB8fCBnZXRJbnRlcmFjdGl2ZVNjcmlwdCgpOwogICAgICAgICAgICBpZiAobm9kZSkgewogICAgICAgICAgICAgICAgaWYgKCFuYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgbmFtZSA9IG5vZGUuZ2V0QXR0cmlidXRlKCdkYXRhLXJlcXVpcmVtb2R1bGUnKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNvbnRleHQgPSBjb250ZXh0c1tub2RlLmdldEF0dHJpYnV0ZSgnZGF0YS1yZXF1aXJlY29udGV4dCcpXTsKICAgICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy9BbHdheXMgc2F2ZSBvZmYgZXZhbHVhdGluZyB0aGUgZGVmIGNhbGwgdW50aWwgdGhlIHNjcmlwdCBvbmxvYWQgaGFuZGxlci4KICAgICAgICAvL1RoaXMgYWxsb3dzIG11bHRpcGxlIG1vZHVsZXMgdG8gYmUgaW4gYSBmaWxlIHdpdGhvdXQgcHJlbWF0dXJlbHkKICAgICAgICAvL3RyYWNpbmcgZGVwZW5kZW5jaWVzLCBhbmQgYWxsb3dzIGZvciBhbm9ueW1vdXMgbW9kdWxlIHN1cHBvcnQsCiAgICAgICAgLy93aGVyZSB0aGUgbW9kdWxlIG5hbWUgaXMgbm90IGtub3duIHVudGlsIHRoZSBzY3JpcHQgb25sb2FkIGV2ZW50CiAgICAgICAgLy9vY2N1cnMuIElmIG5vIGNvbnRleHQsIHVzZSB0aGUgZ2xvYmFsIHF1ZXVlLCBhbmQgZ2V0IGl0IHByb2Nlc3NlZAogICAgICAgIC8vaW4gdGhlIG9uc2NyaXB0IGxvYWQgY2FsbGJhY2suCiAgICAgICAgaWYgKGNvbnRleHQpIHsKICAgICAgICAgICAgY29udGV4dC5kZWZRdWV1ZS5wdXNoKFtuYW1lLCBkZXBzLCBjYWxsYmFja10pOwogICAgICAgICAgICBjb250ZXh0LmRlZlF1ZXVlTWFwW25hbWVdID0gdHJ1ZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBnbG9iYWxEZWZRdWV1ZS5wdXNoKFtuYW1lLCBkZXBzLCBjYWxsYmFja10pOwogICAgICAgIH0KICAgIH07CgogICAgZGVmaW5lLmFtZCA9IHsKICAgICAgICBqUXVlcnk6IHRydWUKICAgIH07CgogICAgLyoqCiAgICAgKiBFeGVjdXRlcyB0aGUgdGV4dC4gTm9ybWFsbHkganVzdCB1c2VzIGV2YWwsIGJ1dCBjYW4gYmUgbW9kaWZpZWQKICAgICAqIHRvIHVzZSBhIGJldHRlciwgZW52aXJvbm1lbnQtc3BlY2lmaWMgY2FsbC4gT25seSB1c2VkIGZvciB0cmFuc3BpbGluZwogICAgICogbG9hZGVyIHBsdWdpbnMsIG5vdCBmb3IgcGxhaW4gSlMgbW9kdWxlcy4KICAgICAqIEBwYXJhbSB7U3RyaW5nfSB0ZXh0IHRoZSB0ZXh0IHRvIGV4ZWN1dGUvZXZhbHVhdGUuCiAgICAgKi8KICAgIHJlcS5leGVjID0gZnVuY3Rpb24gKHRleHQpIHsKICAgICAgICAvKmpzbGludCBldmlsOiB0cnVlICovCiAgICAgICAgcmV0dXJuIGV2YWwodGV4dCk7CiAgICB9OwoKICAgIC8vU2V0IHVwIHdpdGggY29uZmlnIGluZm8uCiAgICByZXEoY2ZnKTsKfSh0aGlzLCAodHlwZW9mIHNldFRpbWVvdXQgPT09ICd1bmRlZmluZWQnID8gdW5kZWZpbmVkIDogc2V0VGltZW91dCkpKTsKCi8vIENvcHlyaWdodCAyMDE0IEdvb2dsZSBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCi8vCi8vIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwovLyB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCi8vICAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKLy8KLy8gaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCi8vCi8vIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKLy8gZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKLy8gV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCi8vICAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCi8vIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgoKIWZ1bmN0aW9uKCl7dmFyIGE9e30sYj17fSxjPXt9OyFmdW5jdGlvbihhLGIpe2Z1bmN0aW9uIGMoYSl7aWYoIm51bWJlciI9PXR5cGVvZiBhKXJldHVybiBhO3ZhciBiPXt9O2Zvcih2YXIgYyBpbiBhKWJbY109YVtjXTtyZXR1cm4gYn1mdW5jdGlvbiBkKCl7dGhpcy5fZGVsYXk9MCx0aGlzLl9lbmREZWxheT0wLHRoaXMuX2ZpbGw9Im5vbmUiLHRoaXMuX2l0ZXJhdGlvblN0YXJ0PTAsdGhpcy5faXRlcmF0aW9ucz0xLHRoaXMuX2R1cmF0aW9uPTAsdGhpcy5fcGxheWJhY2tSYXRlPTEsdGhpcy5fZGlyZWN0aW9uPSJub3JtYWwiLHRoaXMuX2Vhc2luZz0ibGluZWFyIix0aGlzLl9lYXNpbmdGdW5jdGlvbj14fWZ1bmN0aW9uIGUoKXtyZXR1cm4gYS5pc0RlcHJlY2F0ZWQoIkludmFsaWQgdGltaW5nIGlucHV0cyIsIjIwMTYtMDMtMDIiLCJUeXBlRXJyb3IgZXhjZXB0aW9ucyB3aWxsIGJlIHRocm93biBpbnN0ZWFkLiIsITApfWZ1bmN0aW9uIGYoYixjLGUpe3ZhciBmPW5ldyBkO3JldHVybiBjJiYoZi5maWxsPSJib3RoIixmLmR1cmF0aW9uPSJhdXRvIiksIm51bWJlciIhPXR5cGVvZiBifHxpc05hTihiKT92b2lkIDAhPT1iJiZPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhiKS5mb3JFYWNoKGZ1bmN0aW9uKGMpe2lmKCJhdXRvIiE9YltjXSl7aWYoKCJudW1iZXIiPT10eXBlb2YgZltjXXx8ImR1cmF0aW9uIj09YykmJigibnVtYmVyIiE9dHlwZW9mIGJbY118fGlzTmFOKGJbY10pKSlyZXR1cm47aWYoImZpbGwiPT1jJiYtMT09di5pbmRleE9mKGJbY10pKXJldHVybjtpZigiZGlyZWN0aW9uIj09YyYmLTE9PXcuaW5kZXhPZihiW2NdKSlyZXR1cm47aWYoInBsYXliYWNrUmF0ZSI9PWMmJjEhPT1iW2NdJiZhLmlzRGVwcmVjYXRlZCgiQW5pbWF0aW9uRWZmZWN0VGltaW5nLnBsYXliYWNrUmF0ZSIsIjIwMTQtMTEtMjgiLCJVc2UgQW5pbWF0aW9uLnBsYXliYWNrUmF0ZSBpbnN0ZWFkLiIpKXJldHVybjtmW2NdPWJbY119fSk6Zi5kdXJhdGlvbj1iLGZ9ZnVuY3Rpb24gZyhhKXtyZXR1cm4ibnVtYmVyIj09dHlwZW9mIGEmJihhPWlzTmFOKGEpP3tkdXJhdGlvbjowfTp7ZHVyYXRpb246YX0pLGF9ZnVuY3Rpb24gaChiLGMpe3JldHVybiBiPWEubnVtZXJpY1RpbWluZ1RvT2JqZWN0KGIpLGYoYixjKX1mdW5jdGlvbiBpKGEsYixjLGQpe3JldHVybiBhPDB8fGE+MXx8YzwwfHxjPjE/eDpmdW5jdGlvbihlKXtmdW5jdGlvbiBmKGEsYixjKXtyZXR1cm4gMyphKigxLWMpKigxLWMpKmMrMypiKigxLWMpKmMqYytjKmMqY31pZihlPD0wKXt2YXIgZz0wO3JldHVybiBhPjA/Zz1iL2E6IWImJmM+MCYmKGc9ZC9jKSxnKmV9aWYoZT49MSl7dmFyIGg9MDtyZXR1cm4gYzwxP2g9KGQtMSkvKGMtMSk6MT09YyYmYTwxJiYoaD0oYi0xKS8oYS0xKSksMStoKihlLTEpfWZvcih2YXIgaT0wLGo9MTtpPGo7KXt2YXIgaz0oaStqKS8yLGw9ZihhLGMsayk7aWYoTWF0aC5hYnMoZS1sKTwxZS01KXJldHVybiBmKGIsZCxrKTtsPGU/aT1rOmo9a31yZXR1cm4gZihiLGQsayl9fWZ1bmN0aW9uIGooYSxiKXtyZXR1cm4gZnVuY3Rpb24oYyl7aWYoYz49MSlyZXR1cm4gMTt2YXIgZD0xL2E7cmV0dXJuKGMrPWIqZCktYyVkfX1mdW5jdGlvbiBrKGEpe0N8fChDPWRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoImRpdiIpLnN0eWxlKSxDLmFuaW1hdGlvblRpbWluZ0Z1bmN0aW9uPSIiLEMuYW5pbWF0aW9uVGltaW5nRnVuY3Rpb249YTt2YXIgYj1DLmFuaW1hdGlvblRpbWluZ0Z1bmN0aW9uO2lmKCIiPT1iJiZlKCkpdGhyb3cgbmV3IFR5cGVFcnJvcihhKyIgaXMgbm90IGEgdmFsaWQgdmFsdWUgZm9yIGVhc2luZyIpO3JldHVybiBifWZ1bmN0aW9uIGwoYSl7aWYoImxpbmVhciI9PWEpcmV0dXJuIHg7dmFyIGI9RS5leGVjKGEpO2lmKGIpcmV0dXJuIGkuYXBwbHkodGhpcyxiLnNsaWNlKDEpLm1hcChOdW1iZXIpKTt2YXIgYz1GLmV4ZWMoYSk7aWYoYylyZXR1cm4gaihOdW1iZXIoY1sxXSksQSk7dmFyIGQ9Ry5leGVjKGEpO3JldHVybiBkP2ooTnVtYmVyKGRbMV0pLHtzdGFydDp5LG1pZGRsZTp6LGVuZDpBfVtkWzJdXSk6QlthXXx8eH1mdW5jdGlvbiBtKGEpe3JldHVybiBNYXRoLmFicyhuKGEpL2EucGxheWJhY2tSYXRlKX1mdW5jdGlvbiBuKGEpe3JldHVybiAwPT09YS5kdXJhdGlvbnx8MD09PWEuaXRlcmF0aW9ucz8wOmEuZHVyYXRpb24qYS5pdGVyYXRpb25zfWZ1bmN0aW9uIG8oYSxiLGMpe2lmKG51bGw9PWIpcmV0dXJuIEg7dmFyIGQ9Yy5kZWxheSthK2MuZW5kRGVsYXk7cmV0dXJuIGI8TWF0aC5taW4oYy5kZWxheSxkKT9JOmI+PU1hdGgubWluKGMuZGVsYXkrYSxkKT9KOkt9ZnVuY3Rpb24gcChhLGIsYyxkLGUpe3N3aXRjaChkKXtjYXNlIEk6cmV0dXJuImJhY2t3YXJkcyI9PWJ8fCJib3RoIj09Yj8wOm51bGw7Y2FzZSBLOnJldHVybiBjLWU7Y2FzZSBKOnJldHVybiJmb3J3YXJkcyI9PWJ8fCJib3RoIj09Yj9hOm51bGw7Y2FzZSBIOnJldHVybiBudWxsfX1mdW5jdGlvbiBxKGEsYixjLGQsZSl7dmFyIGY9ZTtyZXR1cm4gMD09PWE/YiE9PUkmJihmKz1jKTpmKz1kL2EsZn1mdW5jdGlvbiByKGEsYixjLGQsZSxmKXt2YXIgZz1hPT09MS8wP2IlMTphJTE7cmV0dXJuIDAhPT1nfHxjIT09Snx8MD09PWR8fDA9PT1lJiYwIT09Znx8KGc9MSksZ31mdW5jdGlvbiBzKGEsYixjLGQpe3JldHVybiBhPT09SiYmYj09PTEvMD8xLzA6MT09PWM/TWF0aC5mbG9vcihkKS0xOk1hdGguZmxvb3IoZCl9ZnVuY3Rpb24gdChhLGIsYyl7dmFyIGQ9YTtpZigibm9ybWFsIiE9PWEmJiJyZXZlcnNlIiE9PWEpe3ZhciBlPWI7ImFsdGVybmF0ZS1yZXZlcnNlIj09PWEmJihlKz0xKSxkPSJub3JtYWwiLGUhPT0xLzAmJmUlMiE9MCYmKGQ9InJldmVyc2UiKX1yZXR1cm4ibm9ybWFsIj09PWQ/YzoxLWN9ZnVuY3Rpb24gdShhLGIsYyl7dmFyIGQ9byhhLGIsYyksZT1wKGEsYy5maWxsLGIsZCxjLmRlbGF5KTtpZihudWxsPT09ZSlyZXR1cm4gbnVsbDt2YXIgZj1xKGMuZHVyYXRpb24sZCxjLml0ZXJhdGlvbnMsZSxjLml0ZXJhdGlvblN0YXJ0KSxnPXIoZixjLml0ZXJhdGlvblN0YXJ0LGQsYy5pdGVyYXRpb25zLGUsYy5kdXJhdGlvbiksaD1zKGQsYy5pdGVyYXRpb25zLGcsZiksaT10KGMuZGlyZWN0aW9uLGgsZyk7cmV0dXJuIGMuX2Vhc2luZ0Z1bmN0aW9uKGkpfXZhciB2PSJiYWNrd2FyZHN8Zm9yd2FyZHN8Ym90aHxub25lIi5zcGxpdCgifCIpLHc9InJldmVyc2V8YWx0ZXJuYXRlfGFsdGVybmF0ZS1yZXZlcnNlIi5zcGxpdCgifCIpLHg9ZnVuY3Rpb24oYSl7cmV0dXJuIGF9O2QucHJvdG90eXBlPXtfc2V0TWVtYmVyOmZ1bmN0aW9uKGIsYyl7dGhpc1siXyIrYl09Yyx0aGlzLl9lZmZlY3QmJih0aGlzLl9lZmZlY3QuX3RpbWluZ0lucHV0W2JdPWMsdGhpcy5fZWZmZWN0Ll90aW1pbmc9YS5ub3JtYWxpemVUaW1pbmdJbnB1dCh0aGlzLl9lZmZlY3QuX3RpbWluZ0lucHV0KSx0aGlzLl9lZmZlY3QuYWN0aXZlRHVyYXRpb249YS5jYWxjdWxhdGVBY3RpdmVEdXJhdGlvbih0aGlzLl9lZmZlY3QuX3RpbWluZyksdGhpcy5fZWZmZWN0Ll9hbmltYXRpb24mJnRoaXMuX2VmZmVjdC5fYW5pbWF0aW9uLl9yZWJ1aWxkVW5kZXJseWluZ0FuaW1hdGlvbigpKX0sZ2V0IHBsYXliYWNrUmF0ZSgpe3JldHVybiB0aGlzLl9wbGF5YmFja1JhdGV9LHNldCBkZWxheShhKXt0aGlzLl9zZXRNZW1iZXIoImRlbGF5IixhKX0sZ2V0IGRlbGF5KCl7cmV0dXJuIHRoaXMuX2RlbGF5fSxzZXQgZW5kRGVsYXkoYSl7dGhpcy5fc2V0TWVtYmVyKCJlbmREZWxheSIsYSl9LGdldCBlbmREZWxheSgpe3JldHVybiB0aGlzLl9lbmREZWxheX0sc2V0IGZpbGwoYSl7dGhpcy5fc2V0TWVtYmVyKCJmaWxsIixhKX0sZ2V0IGZpbGwoKXtyZXR1cm4gdGhpcy5fZmlsbH0sc2V0IGl0ZXJhdGlvblN0YXJ0KGEpe2lmKChpc05hTihhKXx8YTwwKSYmZSgpKXRocm93IG5ldyBUeXBlRXJyb3IoIml0ZXJhdGlvblN0YXJ0IG11c3QgYmUgYSBub24tbmVnYXRpdmUgbnVtYmVyLCByZWNlaXZlZDogIithKTt0aGlzLl9zZXRNZW1iZXIoIml0ZXJhdGlvblN0YXJ0IixhKX0sZ2V0IGl0ZXJhdGlvblN0YXJ0KCl7cmV0dXJuIHRoaXMuX2l0ZXJhdGlvblN0YXJ0fSxzZXQgZHVyYXRpb24oYSl7aWYoImF1dG8iIT1hJiYoaXNOYU4oYSl8fGE8MCkmJmUoKSl0aHJvdyBuZXcgVHlwZUVycm9yKCJkdXJhdGlvbiBtdXN0IGJlIG5vbi1uZWdhdGl2ZSBvciBhdXRvLCByZWNlaXZlZDogIithKTt0aGlzLl9zZXRNZW1iZXIoImR1cmF0aW9uIixhKX0sZ2V0IGR1cmF0aW9uKCl7cmV0dXJuIHRoaXMuX2R1cmF0aW9ufSxzZXQgZGlyZWN0aW9uKGEpe3RoaXMuX3NldE1lbWJlcigiZGlyZWN0aW9uIixhKX0sZ2V0IGRpcmVjdGlvbigpe3JldHVybiB0aGlzLl9kaXJlY3Rpb259LHNldCBlYXNpbmcoYSl7dGhpcy5fZWFzaW5nRnVuY3Rpb249bChrKGEpKSx0aGlzLl9zZXRNZW1iZXIoImVhc2luZyIsYSl9LGdldCBlYXNpbmcoKXtyZXR1cm4gdGhpcy5fZWFzaW5nfSxzZXQgaXRlcmF0aW9ucyhhKXtpZigoaXNOYU4oYSl8fGE8MCkmJmUoKSl0aHJvdyBuZXcgVHlwZUVycm9yKCJpdGVyYXRpb25zIG11c3QgYmUgbm9uLW5lZ2F0aXZlLCByZWNlaXZlZDogIithKTt0aGlzLl9zZXRNZW1iZXIoIml0ZXJhdGlvbnMiLGEpfSxnZXQgaXRlcmF0aW9ucygpe3JldHVybiB0aGlzLl9pdGVyYXRpb25zfX07dmFyIHk9MSx6PS41LEE9MCxCPXtlYXNlOmkoLjI1LC4xLC4yNSwxKSwiZWFzZS1pbiI6aSguNDIsMCwxLDEpLCJlYXNlLW91dCI6aSgwLDAsLjU4LDEpLCJlYXNlLWluLW91dCI6aSguNDIsMCwuNTgsMSksInN0ZXAtc3RhcnQiOmooMSx5KSwic3RlcC1taWRkbGUiOmooMSx6KSwic3RlcC1lbmQiOmooMSxBKX0sQz1udWxsLEQ9IlxccyooLT9cXGQrXFwuP1xcZCp8LT9cXC5cXGQrKVxccyoiLEU9bmV3IFJlZ0V4cCgiY3ViaWMtYmV6aWVyXFwoIitEKyIsIitEKyIsIitEKyIsIitEKyJcXCkiKSxGPS9zdGVwc1woXHMqKFxkKylccypcKS8sRz0vc3RlcHNcKFxzKihcZCspXHMqLFxzKihzdGFydHxtaWRkbGV8ZW5kKVxzKlwpLyxIPTAsST0xLEo9MixLPTM7YS5jbG9uZVRpbWluZ0lucHV0PWMsYS5tYWtlVGltaW5nPWYsYS5udW1lcmljVGltaW5nVG9PYmplY3Q9ZyxhLm5vcm1hbGl6ZVRpbWluZ0lucHV0PWgsYS5jYWxjdWxhdGVBY3RpdmVEdXJhdGlvbj1tLGEuY2FsY3VsYXRlSXRlcmF0aW9uUHJvZ3Jlc3M9dSxhLmNhbGN1bGF0ZVBoYXNlPW8sYS5ub3JtYWxpemVFYXNpbmc9ayxhLnBhcnNlRWFzaW5nRnVuY3Rpb249bH0oYSksZnVuY3Rpb24oYSxiKXtmdW5jdGlvbiBjKGEsYil7cmV0dXJuIGEgaW4gaz9rW2FdW2JdfHxiOmJ9ZnVuY3Rpb24gZChhKXtyZXR1cm4iZGlzcGxheSI9PT1hfHwwPT09YS5sYXN0SW5kZXhPZigiYW5pbWF0aW9uIiwwKXx8MD09PWEubGFzdEluZGV4T2YoInRyYW5zaXRpb24iLDApfWZ1bmN0aW9uIGUoYSxiLGUpe2lmKCFkKGEpKXt2YXIgZj1oW2FdO2lmKGYpe2kuc3R5bGVbYV09Yjtmb3IodmFyIGcgaW4gZil7dmFyIGo9ZltnXSxrPWkuc3R5bGVbal07ZVtqXT1jKGosayl9fWVsc2UgZVthXT1jKGEsYil9fWZ1bmN0aW9uIGYoYSl7dmFyIGI9W107Zm9yKHZhciBjIGluIGEpaWYoIShjIGluWyJlYXNpbmciLCJvZmZzZXQiLCJjb21wb3NpdGUiXSkpe3ZhciBkPWFbY107QXJyYXkuaXNBcnJheShkKXx8KGQ9W2RdKTtmb3IodmFyIGUsZj1kLmxlbmd0aCxnPTA7ZzxmO2crKyllPXt9LGUub2Zmc2V0PSJvZmZzZXQiaW4gYT9hLm9mZnNldDoxPT1mPzE6Zy8oZi0xKSwiZWFzaW5nImluIGEmJihlLmVhc2luZz1hLmVhc2luZyksImNvbXBvc2l0ZSJpbiBhJiYoZS5jb21wb3NpdGU9YS5jb21wb3NpdGUpLGVbY109ZFtnXSxiLnB1c2goZSl9cmV0dXJuIGIuc29ydChmdW5jdGlvbihhLGIpe3JldHVybiBhLm9mZnNldC1iLm9mZnNldH0pLGJ9ZnVuY3Rpb24gZyhiKXtmdW5jdGlvbiBjKCl7dmFyIGE9ZC5sZW5ndGg7bnVsbD09ZFthLTFdLm9mZnNldCYmKGRbYS0xXS5vZmZzZXQ9MSksYT4xJiZudWxsPT1kWzBdLm9mZnNldCYmKGRbMF0ub2Zmc2V0PTApO2Zvcih2YXIgYj0wLGM9ZFswXS5vZmZzZXQsZT0xO2U8YTtlKyspe3ZhciBmPWRbZV0ub2Zmc2V0O2lmKG51bGwhPWYpe2Zvcih2YXIgZz0xO2c8ZS1iO2crKylkW2IrZ10ub2Zmc2V0PWMrKGYtYykqZy8oZS1iKTtiPWUsYz1mfX19aWYobnVsbD09YilyZXR1cm5bXTt3aW5kb3cuU3ltYm9sJiZTeW1ib2wuaXRlcmF0b3ImJkFycmF5LnByb3RvdHlwZS5mcm9tJiZiW1N5bWJvbC5pdGVyYXRvcl0mJihiPUFycmF5LmZyb20oYikpLEFycmF5LmlzQXJyYXkoYil8fChiPWYoYikpO2Zvcih2YXIgZD1iLm1hcChmdW5jdGlvbihiKXt2YXIgYz17fTtmb3IodmFyIGQgaW4gYil7dmFyIGY9YltkXTtpZigib2Zmc2V0Ij09ZCl7aWYobnVsbCE9Zil7aWYoZj1OdW1iZXIoZiksIWlzRmluaXRlKGYpKXRocm93IG5ldyBUeXBlRXJyb3IoIktleWZyYW1lIG9mZnNldHMgbXVzdCBiZSBudW1iZXJzLiIpO2lmKGY8MHx8Zj4xKXRocm93IG5ldyBUeXBlRXJyb3IoIktleWZyYW1lIG9mZnNldHMgbXVzdCBiZSBiZXR3ZWVuIDAgYW5kIDEuIil9fWVsc2UgaWYoImNvbXBvc2l0ZSI9PWQpe2lmKCJhZGQiPT1mfHwiYWNjdW11bGF0ZSI9PWYpdGhyb3d7dHlwZTpET01FeGNlcHRpb24uTk9UX1NVUFBPUlRFRF9FUlIsbmFtZToiTm90U3VwcG9ydGVkRXJyb3IiLG1lc3NhZ2U6ImFkZCBjb21wb3NpdGluZyBpcyBub3Qgc3VwcG9ydGVkIn07aWYoInJlcGxhY2UiIT1mKXRocm93IG5ldyBUeXBlRXJyb3IoIkludmFsaWQgY29tcG9zaXRlIG1vZGUgIitmKyIuIil9ZWxzZSBmPSJlYXNpbmciPT1kP2Eubm9ybWFsaXplRWFzaW5nKGYpOiIiK2Y7ZShkLGYsYyl9cmV0dXJuIHZvaWQgMD09Yy5vZmZzZXQmJihjLm9mZnNldD1udWxsKSx2b2lkIDA9PWMuZWFzaW5nJiYoYy5lYXNpbmc9ImxpbmVhciIpLGN9KSxnPSEwLGg9LTEvMCxpPTA7aTxkLmxlbmd0aDtpKyspe3ZhciBqPWRbaV0ub2Zmc2V0O2lmKG51bGwhPWope2lmKGo8aCl0aHJvdyBuZXcgVHlwZUVycm9yKCJLZXlmcmFtZXMgYXJlIG5vdCBsb29zZWx5IHNvcnRlZCBieSBvZmZzZXQuIFNvcnQgb3Igc3BlY2lmeSBvZmZzZXRzLiIpO2g9an1lbHNlIGc9ITF9cmV0dXJuIGQ9ZC5maWx0ZXIoZnVuY3Rpb24oYSl7cmV0dXJuIGEub2Zmc2V0Pj0wJiZhLm9mZnNldDw9MX0pLGd8fGMoKSxkfXZhciBoPXtiYWNrZ3JvdW5kOlsiYmFja2dyb3VuZEltYWdlIiwiYmFja2dyb3VuZFBvc2l0aW9uIiwiYmFja2dyb3VuZFNpemUiLCJiYWNrZ3JvdW5kUmVwZWF0IiwiYmFja2dyb3VuZEF0dGFjaG1lbnQiLCJiYWNrZ3JvdW5kT3JpZ2luIiwiYmFja2dyb3VuZENsaXAiLCJiYWNrZ3JvdW5kQ29sb3IiXSxib3JkZXI6WyJib3JkZXJUb3BDb2xvciIsImJvcmRlclRvcFN0eWxlIiwiYm9yZGVyVG9wV2lkdGgiLCJib3JkZXJSaWdodENvbG9yIiwiYm9yZGVyUmlnaHRTdHlsZSIsImJvcmRlclJpZ2h0V2lkdGgiLCJib3JkZXJCb3R0b21Db2xvciIsImJvcmRlckJvdHRvbVN0eWxlIiwiYm9yZGVyQm90dG9tV2lkdGgiLCJib3JkZXJMZWZ0Q29sb3IiLCJib3JkZXJMZWZ0U3R5bGUiLCJib3JkZXJMZWZ0V2lkdGgiXSxib3JkZXJCb3R0b206WyJib3JkZXJCb3R0b21XaWR0aCIsImJvcmRlckJvdHRvbVN0eWxlIiwiYm9yZGVyQm90dG9tQ29sb3IiXSxib3JkZXJDb2xvcjpbImJvcmRlclRvcENvbG9yIiwiYm9yZGVyUmlnaHRDb2xvciIsImJvcmRlckJvdHRvbUNvbG9yIiwiYm9yZGVyTGVmdENvbG9yIl0sYm9yZGVyTGVmdDpbImJvcmRlckxlZnRXaWR0aCIsImJvcmRlckxlZnRTdHlsZSIsImJvcmRlckxlZnRDb2xvciJdLGJvcmRlclJhZGl1czpbImJvcmRlclRvcExlZnRSYWRpdXMiLCJib3JkZXJUb3BSaWdodFJhZGl1cyIsImJvcmRlckJvdHRvbVJpZ2h0UmFkaXVzIiwiYm9yZGVyQm90dG9tTGVmdFJhZGl1cyJdLGJvcmRlclJpZ2h0OlsiYm9yZGVyUmlnaHRXaWR0aCIsImJvcmRlclJpZ2h0U3R5bGUiLCJib3JkZXJSaWdodENvbG9yIl0sYm9yZGVyVG9wOlsiYm9yZGVyVG9wV2lkdGgiLCJib3JkZXJUb3BTdHlsZSIsImJvcmRlclRvcENvbG9yIl0sYm9yZGVyV2lkdGg6WyJib3JkZXJUb3BXaWR0aCIsImJvcmRlclJpZ2h0V2lkdGgiLCJib3JkZXJCb3R0b21XaWR0aCIsImJvcmRlckxlZnRXaWR0aCJdLGZsZXg6WyJmbGV4R3JvdyIsImZsZXhTaHJpbmsiLCJmbGV4QmFzaXMiXSxmb250OlsiZm9udEZhbWlseSIsImZvbnRTaXplIiwiZm9udFN0eWxlIiwiZm9udFZhcmlhbnQiLCJmb250V2VpZ2h0IiwibGluZUhlaWdodCJdLG1hcmdpbjpbIm1hcmdpblRvcCIsIm1hcmdpblJpZ2h0IiwibWFyZ2luQm90dG9tIiwibWFyZ2luTGVmdCJdLG91dGxpbmU6WyJvdXRsaW5lQ29sb3IiLCJvdXRsaW5lU3R5bGUiLCJvdXRsaW5lV2lkdGgiXSxwYWRkaW5nOlsicGFkZGluZ1RvcCIsInBhZGRpbmdSaWdodCIsInBhZGRpbmdCb3R0b20iLCJwYWRkaW5nTGVmdCJdfSxpPWRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygiaHR0cDovL3d3dy53My5vcmcvMTk5OS94aHRtbCIsImRpdiIpLGo9e3RoaW46IjFweCIsbWVkaXVtOiIzcHgiLHRoaWNrOiI1cHgifSxrPXtib3JkZXJCb3R0b21XaWR0aDpqLGJvcmRlckxlZnRXaWR0aDpqLGJvcmRlclJpZ2h0V2lkdGg6aixib3JkZXJUb3BXaWR0aDpqLGZvbnRTaXplOnsieHgtc21hbGwiOiI2MCUiLCJ4LXNtYWxsIjoiNzUlIixzbWFsbDoiODklIixtZWRpdW06IjEwMCUiLGxhcmdlOiIxMjAlIiwieC1sYXJnZSI6IjE1MCUiLCJ4eC1sYXJnZSI6IjIwMCUifSxmb250V2VpZ2h0Ontub3JtYWw6IjQwMCIsYm9sZDoiNzAwIn0sb3V0bGluZVdpZHRoOmosdGV4dFNoYWRvdzp7bm9uZToiMHB4IDBweCAwcHggdHJhbnNwYXJlbnQifSxib3hTaGFkb3c6e25vbmU6IjBweCAwcHggMHB4IDBweCB0cmFuc3BhcmVudCJ9fTthLmNvbnZlcnRUb0FycmF5Rm9ybT1mLGEubm9ybWFsaXplS2V5ZnJhbWVzPWd9KGEpLGZ1bmN0aW9uKGEpe3ZhciBiPXt9O2EuaXNEZXByZWNhdGVkPWZ1bmN0aW9uKGEsYyxkLGUpe3ZhciBmPWU/ImFyZSI6ImlzIixnPW5ldyBEYXRlLGg9bmV3IERhdGUoYyk7cmV0dXJuIGguc2V0TW9udGgoaC5nZXRNb250aCgpKzMpLCEoZzxoJiYoYSBpbiBifHxjb25zb2xlLndhcm4oIldlYiBBbmltYXRpb25zOiAiK2ErIiAiK2YrIiBkZXByZWNhdGVkIGFuZCB3aWxsIHN0b3Agd29ya2luZyBvbiAiK2gudG9EYXRlU3RyaW5nKCkrIi4gIitkKSxiW2FdPSEwLDEpKX0sYS5kZXByZWNhdGVkPWZ1bmN0aW9uKGIsYyxkLGUpe3ZhciBmPWU/ImFyZSI6ImlzIjtpZihhLmlzRGVwcmVjYXRlZChiLGMsZCxlKSl0aHJvdyBuZXcgRXJyb3IoYisiICIrZisiIG5vIGxvbmdlciBzdXBwb3J0ZWQuICIrZCl9fShhKSxmdW5jdGlvbigpe2lmKGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5hbmltYXRlKXt2YXIgYz1kb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuYW5pbWF0ZShbXSwwKSxkPSEwO2lmKGMmJihkPSExLCJwbGF5fGN1cnJlbnRUaW1lfHBhdXNlfHJldmVyc2V8cGxheWJhY2tSYXRlfGNhbmNlbHxmaW5pc2h8c3RhcnRUaW1lfHBsYXlTdGF0ZSIuc3BsaXQoInwiKS5mb3JFYWNoKGZ1bmN0aW9uKGEpe3ZvaWQgMD09PWNbYV0mJihkPSEwKX0pKSwhZClyZXR1cm59IWZ1bmN0aW9uKGEsYixjKXtmdW5jdGlvbiBkKGEpe2Zvcih2YXIgYj17fSxjPTA7YzxhLmxlbmd0aDtjKyspZm9yKHZhciBkIGluIGFbY10paWYoIm9mZnNldCIhPWQmJiJlYXNpbmciIT1kJiYiY29tcG9zaXRlIiE9ZCl7dmFyIGU9e29mZnNldDphW2NdLm9mZnNldCxlYXNpbmc6YVtjXS5lYXNpbmcsdmFsdWU6YVtjXVtkXX07YltkXT1iW2RdfHxbXSxiW2RdLnB1c2goZSl9Zm9yKHZhciBmIGluIGIpe3ZhciBnPWJbZl07aWYoMCE9Z1swXS5vZmZzZXR8fDEhPWdbZy5sZW5ndGgtMV0ub2Zmc2V0KXRocm93e3R5cGU6RE9NRXhjZXB0aW9uLk5PVF9TVVBQT1JURURfRVJSLG5hbWU6Ik5vdFN1cHBvcnRlZEVycm9yIixtZXNzYWdlOiJQYXJ0aWFsIGtleWZyYW1lcyBhcmUgbm90IHN1cHBvcnRlZCJ9fXJldHVybiBifWZ1bmN0aW9uIGUoYyl7dmFyIGQ9W107Zm9yKHZhciBlIGluIGMpZm9yKHZhciBmPWNbZV0sZz0wO2c8Zi5sZW5ndGgtMTtnKyspe3ZhciBoPWcsaT1nKzEsaj1mW2hdLm9mZnNldCxrPWZbaV0ub2Zmc2V0LGw9aixtPWs7MD09ZyYmKGw9LTEvMCwwPT1rJiYoaT1oKSksZz09Zi5sZW5ndGgtMiYmKG09MS8wLDE9PWomJihoPWkpKSxkLnB1c2goe2FwcGx5RnJvbTpsLGFwcGx5VG86bSxzdGFydE9mZnNldDpmW2hdLm9mZnNldCxlbmRPZmZzZXQ6ZltpXS5vZmZzZXQsZWFzaW5nRnVuY3Rpb246YS5wYXJzZUVhc2luZ0Z1bmN0aW9uKGZbaF0uZWFzaW5nKSxwcm9wZXJ0eTplLGludGVycG9sYXRpb246Yi5wcm9wZXJ0eUludGVycG9sYXRpb24oZSxmW2hdLnZhbHVlLGZbaV0udmFsdWUpfSl9cmV0dXJuIGQuc29ydChmdW5jdGlvbihhLGIpe3JldHVybiBhLnN0YXJ0T2Zmc2V0LWIuc3RhcnRPZmZzZXR9KSxkfWIuY29udmVydEVmZmVjdElucHV0PWZ1bmN0aW9uKGMpe3ZhciBmPWEubm9ybWFsaXplS2V5ZnJhbWVzKGMpLGc9ZChmKSxoPWUoZyk7cmV0dXJuIGZ1bmN0aW9uKGEsYyl7aWYobnVsbCE9YyloLmZpbHRlcihmdW5jdGlvbihhKXtyZXR1cm4gYz49YS5hcHBseUZyb20mJmM8YS5hcHBseVRvfSkuZm9yRWFjaChmdW5jdGlvbihkKXt2YXIgZT1jLWQuc3RhcnRPZmZzZXQsZj1kLmVuZE9mZnNldC1kLnN0YXJ0T2Zmc2V0LGc9MD09Zj8wOmQuZWFzaW5nRnVuY3Rpb24oZS9mKTtiLmFwcGx5KGEsZC5wcm9wZXJ0eSxkLmludGVycG9sYXRpb24oZykpfSk7ZWxzZSBmb3IodmFyIGQgaW4gZykib2Zmc2V0IiE9ZCYmImVhc2luZyIhPWQmJiJjb21wb3NpdGUiIT1kJiZiLmNsZWFyKGEsZCl9fX0oYSxiKSxmdW5jdGlvbihhLGIsYyl7ZnVuY3Rpb24gZChhKXtyZXR1cm4gYS5yZXBsYWNlKC8tKC4pL2csZnVuY3Rpb24oYSxiKXtyZXR1cm4gYi50b1VwcGVyQ2FzZSgpfSl9ZnVuY3Rpb24gZShhLGIsYyl7aFtjXT1oW2NdfHxbXSxoW2NdLnB1c2goW2EsYl0pfWZ1bmN0aW9uIGYoYSxiLGMpe2Zvcih2YXIgZj0wO2Y8Yy5sZW5ndGg7ZisrKXtlKGEsYixkKGNbZl0pKX19ZnVuY3Rpb24gZyhjLGUsZil7dmFyIGc9YzsvLS8udGVzdChjKSYmIWEuaXNEZXByZWNhdGVkKCJIeXBoZW5hdGVkIHByb3BlcnR5IG5hbWVzIiwiMjAxNi0wMy0yMiIsIlVzZSBjYW1lbENhc2UgaW5zdGVhZC4iLCEwKSYmKGc9ZChjKSksImluaXRpYWwiIT1lJiYiaW5pdGlhbCIhPWZ8fCgiaW5pdGlhbCI9PWUmJihlPWlbZ10pLCJpbml0aWFsIj09ZiYmKGY9aVtnXSkpO2Zvcih2YXIgaj1lPT1mP1tdOmhbZ10saz0wO2omJms8ai5sZW5ndGg7aysrKXt2YXIgbD1qW2tdWzBdKGUpLG09altrXVswXShmKTtpZih2b2lkIDAhPT1sJiZ2b2lkIDAhPT1tKXt2YXIgbj1qW2tdWzFdKGwsbSk7aWYobil7dmFyIG89Yi5JbnRlcnBvbGF0aW9uLmFwcGx5KG51bGwsbik7cmV0dXJuIGZ1bmN0aW9uKGEpe3JldHVybiAwPT1hP2U6MT09YT9mOm8oYSl9fX19cmV0dXJuIGIuSW50ZXJwb2xhdGlvbighMSwhMCxmdW5jdGlvbihhKXtyZXR1cm4gYT9mOmV9KX12YXIgaD17fTtiLmFkZFByb3BlcnRpZXNIYW5kbGVyPWY7dmFyIGk9e2JhY2tncm91bmRDb2xvcjoidHJhbnNwYXJlbnQiLGJhY2tncm91bmRQb3NpdGlvbjoiMCUgMCUiLGJvcmRlckJvdHRvbUNvbG9yOiJjdXJyZW50Q29sb3IiLGJvcmRlckJvdHRvbUxlZnRSYWRpdXM6IjBweCIsYm9yZGVyQm90dG9tUmlnaHRSYWRpdXM6IjBweCIsYm9yZGVyQm90dG9tV2lkdGg6IjNweCIsYm9yZGVyTGVmdENvbG9yOiJjdXJyZW50Q29sb3IiLGJvcmRlckxlZnRXaWR0aDoiM3B4Iixib3JkZXJSaWdodENvbG9yOiJjdXJyZW50Q29sb3IiLGJvcmRlclJpZ2h0V2lkdGg6IjNweCIsYm9yZGVyU3BhY2luZzoiMnB4Iixib3JkZXJUb3BDb2xvcjoiY3VycmVudENvbG9yIixib3JkZXJUb3BMZWZ0UmFkaXVzOiIwcHgiLGJvcmRlclRvcFJpZ2h0UmFkaXVzOiIwcHgiLGJvcmRlclRvcFdpZHRoOiIzcHgiLGJvdHRvbToiYXV0byIsY2xpcDoicmVjdCgwcHgsIDBweCwgMHB4LCAwcHgpIixjb2xvcjoiYmxhY2siLGZvbnRTaXplOiIxMDAlIixmb250V2VpZ2h0OiI0MDAiLGhlaWdodDoiYXV0byIsbGVmdDoiYXV0byIsbGV0dGVyU3BhY2luZzoibm9ybWFsIixsaW5lSGVpZ2h0OiIxMjAlIixtYXJnaW5Cb3R0b206IjBweCIsbWFyZ2luTGVmdDoiMHB4IixtYXJnaW5SaWdodDoiMHB4IixtYXJnaW5Ub3A6IjBweCIsbWF4SGVpZ2h0OiJub25lIixtYXhXaWR0aDoibm9uZSIsbWluSGVpZ2h0OiIwcHgiLG1pbldpZHRoOiIwcHgiLG9wYWNpdHk6IjEuMCIsb3V0bGluZUNvbG9yOiJpbnZlcnQiLG91dGxpbmVPZmZzZXQ6IjBweCIsb3V0bGluZVdpZHRoOiIzcHgiLHBhZGRpbmdCb3R0b206IjBweCIscGFkZGluZ0xlZnQ6IjBweCIscGFkZGluZ1JpZ2h0OiIwcHgiLHBhZGRpbmdUb3A6IjBweCIscmlnaHQ6ImF1dG8iLHN0cm9rZURhc2hhcnJheToibm9uZSIsc3Ryb2tlRGFzaG9mZnNldDoiMHB4Iix0ZXh0SW5kZW50OiIwcHgiLHRleHRTaGFkb3c6IjBweCAwcHggMHB4IHRyYW5zcGFyZW50Iix0b3A6ImF1dG8iLHRyYW5zZm9ybToiIix2ZXJ0aWNhbEFsaWduOiIwcHgiLHZpc2liaWxpdHk6InZpc2libGUiLHdpZHRoOiJhdXRvIix3b3JkU3BhY2luZzoibm9ybWFsIix6SW5kZXg6ImF1dG8ifTtiLnByb3BlcnR5SW50ZXJwb2xhdGlvbj1nfShhLGIpLGZ1bmN0aW9uKGEsYixjKXtmdW5jdGlvbiBkKGIpe3ZhciBjPWEuY2FsY3VsYXRlQWN0aXZlRHVyYXRpb24oYiksZD1mdW5jdGlvbihkKXtyZXR1cm4gYS5jYWxjdWxhdGVJdGVyYXRpb25Qcm9ncmVzcyhjLGQsYil9O3JldHVybiBkLl90b3RhbER1cmF0aW9uPWIuZGVsYXkrYytiLmVuZERlbGF5LGR9Yi5LZXlmcmFtZUVmZmVjdD1mdW5jdGlvbihjLGUsZixnKXt2YXIgaCxpPWQoYS5ub3JtYWxpemVUaW1pbmdJbnB1dChmKSksaj1iLmNvbnZlcnRFZmZlY3RJbnB1dChlKSxrPWZ1bmN0aW9uKCl7aihjLGgpfTtyZXR1cm4gay5fdXBkYXRlPWZ1bmN0aW9uKGEpe3JldHVybiBudWxsIT09KGg9aShhKSl9LGsuX2NsZWFyPWZ1bmN0aW9uKCl7aihjLG51bGwpfSxrLl9oYXNTYW1lVGFyZ2V0PWZ1bmN0aW9uKGEpe3JldHVybiBjPT09YX0say5fdGFyZ2V0PWMsay5fdG90YWxEdXJhdGlvbj1pLl90b3RhbER1cmF0aW9uLGsuX2lkPWcsa319KGEsYiksZnVuY3Rpb24oYSxiKXthLmFwcGx5PWZ1bmN0aW9uKGIsYyxkKXtiLnN0eWxlW2EucHJvcGVydHlOYW1lKGMpXT1kfSxhLmNsZWFyPWZ1bmN0aW9uKGIsYyl7Yi5zdHlsZVthLnByb3BlcnR5TmFtZShjKV09IiJ9fShiKSxmdW5jdGlvbihhKXt3aW5kb3cuRWxlbWVudC5wcm90b3R5cGUuYW5pbWF0ZT1mdW5jdGlvbihiLGMpe3ZhciBkPSIiO3JldHVybiBjJiZjLmlkJiYoZD1jLmlkKSxhLnRpbWVsaW5lLl9wbGF5KGEuS2V5ZnJhbWVFZmZlY3QodGhpcyxiLGMsZCkpfX0oYiksZnVuY3Rpb24oYSxiKXtmdW5jdGlvbiBjKGEsYixkKXtpZigibnVtYmVyIj09dHlwZW9mIGEmJiJudW1iZXIiPT10eXBlb2YgYilyZXR1cm4gYSooMS1kKStiKmQ7aWYoImJvb2xlYW4iPT10eXBlb2YgYSYmImJvb2xlYW4iPT10eXBlb2YgYilyZXR1cm4gZDwuNT9hOmI7aWYoYS5sZW5ndGg9PWIubGVuZ3RoKXtmb3IodmFyIGU9W10sZj0wO2Y8YS5sZW5ndGg7ZisrKWUucHVzaChjKGFbZl0sYltmXSxkKSk7cmV0dXJuIGV9dGhyb3ciTWlzbWF0Y2hlZCBpbnRlcnBvbGF0aW9uIGFyZ3VtZW50cyAiK2ErIjoiK2J9YS5JbnRlcnBvbGF0aW9uPWZ1bmN0aW9uKGEsYixkKXtyZXR1cm4gZnVuY3Rpb24oZSl7cmV0dXJuIGQoYyhhLGIsZSkpfX19KGIpLGZ1bmN0aW9uKGEsYixjKXthLnNlcXVlbmNlTnVtYmVyPTA7dmFyIGQ9ZnVuY3Rpb24oYSxiLGMpe3RoaXMudGFyZ2V0PWEsdGhpcy5jdXJyZW50VGltZT1iLHRoaXMudGltZWxpbmVUaW1lPWMsdGhpcy50eXBlPSJmaW5pc2giLHRoaXMuYnViYmxlcz0hMSx0aGlzLmNhbmNlbGFibGU9ITEsdGhpcy5jdXJyZW50VGFyZ2V0PWEsdGhpcy5kZWZhdWx0UHJldmVudGVkPSExLHRoaXMuZXZlbnRQaGFzZT1FdmVudC5BVF9UQVJHRVQsdGhpcy50aW1lU3RhbXA9RGF0ZS5ub3coKX07Yi5BbmltYXRpb249ZnVuY3Rpb24oYil7dGhpcy5pZD0iIixiJiZiLl9pZCYmKHRoaXMuaWQ9Yi5faWQpLHRoaXMuX3NlcXVlbmNlTnVtYmVyPWEuc2VxdWVuY2VOdW1iZXIrKyx0aGlzLl9jdXJyZW50VGltZT0wLHRoaXMuX3N0YXJ0VGltZT1udWxsLHRoaXMuX3BhdXNlZD0hMSx0aGlzLl9wbGF5YmFja1JhdGU9MSx0aGlzLl9pblRpbWVsaW5lPSEwLHRoaXMuX2ZpbmlzaGVkRmxhZz0hMCx0aGlzLm9uZmluaXNoPW51bGwsdGhpcy5fZmluaXNoSGFuZGxlcnM9W10sdGhpcy5fZWZmZWN0PWIsdGhpcy5faW5FZmZlY3Q9dGhpcy5fZWZmZWN0Ll91cGRhdGUoMCksdGhpcy5faWRsZT0hMCx0aGlzLl9jdXJyZW50VGltZVBlbmRpbmc9ITF9LGIuQW5pbWF0aW9uLnByb3RvdHlwZT17X2Vuc3VyZUFsaXZlOmZ1bmN0aW9uKCl7dGhpcy5wbGF5YmFja1JhdGU8MCYmMD09PXRoaXMuY3VycmVudFRpbWU/dGhpcy5faW5FZmZlY3Q9dGhpcy5fZWZmZWN0Ll91cGRhdGUoLTEpOnRoaXMuX2luRWZmZWN0PXRoaXMuX2VmZmVjdC5fdXBkYXRlKHRoaXMuY3VycmVudFRpbWUpLHRoaXMuX2luVGltZWxpbmV8fCF0aGlzLl9pbkVmZmVjdCYmdGhpcy5fZmluaXNoZWRGbGFnfHwodGhpcy5faW5UaW1lbGluZT0hMCxiLnRpbWVsaW5lLl9hbmltYXRpb25zLnB1c2godGhpcykpfSxfdGlja0N1cnJlbnRUaW1lOmZ1bmN0aW9uKGEsYil7YSE9dGhpcy5fY3VycmVudFRpbWUmJih0aGlzLl9jdXJyZW50VGltZT1hLHRoaXMuX2lzRmluaXNoZWQmJiFiJiYodGhpcy5fY3VycmVudFRpbWU9dGhpcy5fcGxheWJhY2tSYXRlPjA/dGhpcy5fdG90YWxEdXJhdGlvbjowKSx0aGlzLl9lbnN1cmVBbGl2ZSgpKX0sZ2V0IGN1cnJlbnRUaW1lKCl7cmV0dXJuIHRoaXMuX2lkbGV8fHRoaXMuX2N1cnJlbnRUaW1lUGVuZGluZz9udWxsOnRoaXMuX2N1cnJlbnRUaW1lfSxzZXQgY3VycmVudFRpbWUoYSl7YT0rYSxpc05hTihhKXx8KGIucmVzdGFydCgpLHRoaXMuX3BhdXNlZHx8bnVsbD09dGhpcy5fc3RhcnRUaW1lfHwodGhpcy5fc3RhcnRUaW1lPXRoaXMuX3RpbWVsaW5lLmN1cnJlbnRUaW1lLWEvdGhpcy5fcGxheWJhY2tSYXRlKSx0aGlzLl9jdXJyZW50VGltZVBlbmRpbmc9ITEsdGhpcy5fY3VycmVudFRpbWUhPWEmJih0aGlzLl9pZGxlJiYodGhpcy5faWRsZT0hMSx0aGlzLl9wYXVzZWQ9ITApLHRoaXMuX3RpY2tDdXJyZW50VGltZShhLCEwKSxiLmFwcGx5RGlydGllZEFuaW1hdGlvbih0aGlzKSkpfSxnZXQgc3RhcnRUaW1lKCl7cmV0dXJuIHRoaXMuX3N0YXJ0VGltZX0sc2V0IHN0YXJ0VGltZShhKXthPSthLGlzTmFOKGEpfHx0aGlzLl9wYXVzZWR8fHRoaXMuX2lkbGV8fCh0aGlzLl9zdGFydFRpbWU9YSx0aGlzLl90aWNrQ3VycmVudFRpbWUoKHRoaXMuX3RpbWVsaW5lLmN1cnJlbnRUaW1lLXRoaXMuX3N0YXJ0VGltZSkqdGhpcy5wbGF5YmFja1JhdGUpLGIuYXBwbHlEaXJ0aWVkQW5pbWF0aW9uKHRoaXMpKX0sZ2V0IHBsYXliYWNrUmF0ZSgpe3JldHVybiB0aGlzLl9wbGF5YmFja1JhdGV9LHNldCBwbGF5YmFja1JhdGUoYSl7aWYoYSE9dGhpcy5fcGxheWJhY2tSYXRlKXt2YXIgYz10aGlzLmN1cnJlbnRUaW1lO3RoaXMuX3BsYXliYWNrUmF0ZT1hLHRoaXMuX3N0YXJ0VGltZT1udWxsLCJwYXVzZWQiIT10aGlzLnBsYXlTdGF0ZSYmImlkbGUiIT10aGlzLnBsYXlTdGF0ZSYmKHRoaXMuX2ZpbmlzaGVkRmxhZz0hMSx0aGlzLl9pZGxlPSExLHRoaXMuX2Vuc3VyZUFsaXZlKCksYi5hcHBseURpcnRpZWRBbmltYXRpb24odGhpcykpLG51bGwhPWMmJih0aGlzLmN1cnJlbnRUaW1lPWMpfX0sZ2V0IF9pc0ZpbmlzaGVkKCl7cmV0dXJuIXRoaXMuX2lkbGUmJih0aGlzLl9wbGF5YmFja1JhdGU+MCYmdGhpcy5fY3VycmVudFRpbWU+PXRoaXMuX3RvdGFsRHVyYXRpb258fHRoaXMuX3BsYXliYWNrUmF0ZTwwJiZ0aGlzLl9jdXJyZW50VGltZTw9MCl9LGdldCBfdG90YWxEdXJhdGlvbigpe3JldHVybiB0aGlzLl9lZmZlY3QuX3RvdGFsRHVyYXRpb259LGdldCBwbGF5U3RhdGUoKXtyZXR1cm4gdGhpcy5faWRsZT8iaWRsZSI6bnVsbD09dGhpcy5fc3RhcnRUaW1lJiYhdGhpcy5fcGF1c2VkJiYwIT10aGlzLnBsYXliYWNrUmF0ZXx8dGhpcy5fY3VycmVudFRpbWVQZW5kaW5nPyJwZW5kaW5nIjp0aGlzLl9wYXVzZWQ/InBhdXNlZCI6dGhpcy5faXNGaW5pc2hlZD8iZmluaXNoZWQiOiJydW5uaW5nIn0sX3Jld2luZDpmdW5jdGlvbigpe2lmKHRoaXMuX3BsYXliYWNrUmF0ZT49MCl0aGlzLl9jdXJyZW50VGltZT0wO2Vsc2V7aWYoISh0aGlzLl90b3RhbER1cmF0aW9uPDEvMCkpdGhyb3cgbmV3IERPTUV4Y2VwdGlvbigiVW5hYmxlIHRvIHJld2luZCBuZWdhdGl2ZSBwbGF5YmFjayByYXRlIGFuaW1hdGlvbiB3aXRoIGluZmluaXRlIGR1cmF0aW9uIiwiSW52YWxpZFN0YXRlRXJyb3IiKTt0aGlzLl9jdXJyZW50VGltZT10aGlzLl90b3RhbER1cmF0aW9ufX0scGxheTpmdW5jdGlvbigpe3RoaXMuX3BhdXNlZD0hMSwodGhpcy5faXNGaW5pc2hlZHx8dGhpcy5faWRsZSkmJih0aGlzLl9yZXdpbmQoKSx0aGlzLl9zdGFydFRpbWU9bnVsbCksdGhpcy5fZmluaXNoZWRGbGFnPSExLHRoaXMuX2lkbGU9ITEsdGhpcy5fZW5zdXJlQWxpdmUoKSxiLmFwcGx5RGlydGllZEFuaW1hdGlvbih0aGlzKX0scGF1c2U6ZnVuY3Rpb24oKXt0aGlzLl9pc0ZpbmlzaGVkfHx0aGlzLl9wYXVzZWR8fHRoaXMuX2lkbGU/dGhpcy5faWRsZSYmKHRoaXMuX3Jld2luZCgpLHRoaXMuX2lkbGU9ITEpOnRoaXMuX2N1cnJlbnRUaW1lUGVuZGluZz0hMCx0aGlzLl9zdGFydFRpbWU9bnVsbCx0aGlzLl9wYXVzZWQ9ITB9LGZpbmlzaDpmdW5jdGlvbigpe3RoaXMuX2lkbGV8fCh0aGlzLmN1cnJlbnRUaW1lPXRoaXMuX3BsYXliYWNrUmF0ZT4wP3RoaXMuX3RvdGFsRHVyYXRpb246MCx0aGlzLl9zdGFydFRpbWU9dGhpcy5fdG90YWxEdXJhdGlvbi10aGlzLmN1cnJlbnRUaW1lLHRoaXMuX2N1cnJlbnRUaW1lUGVuZGluZz0hMSxiLmFwcGx5RGlydGllZEFuaW1hdGlvbih0aGlzKSl9LGNhbmNlbDpmdW5jdGlvbigpe3RoaXMuX2luRWZmZWN0JiYodGhpcy5faW5FZmZlY3Q9ITEsdGhpcy5faWRsZT0hMCx0aGlzLl9wYXVzZWQ9ITEsdGhpcy5fZmluaXNoZWRGbGFnPSEwLHRoaXMuX2N1cnJlbnRUaW1lPTAsdGhpcy5fc3RhcnRUaW1lPW51bGwsdGhpcy5fZWZmZWN0Ll91cGRhdGUobnVsbCksYi5hcHBseURpcnRpZWRBbmltYXRpb24odGhpcykpfSxyZXZlcnNlOmZ1bmN0aW9uKCl7dGhpcy5wbGF5YmFja1JhdGUqPS0xLHRoaXMucGxheSgpfSxhZGRFdmVudExpc3RlbmVyOmZ1bmN0aW9uKGEsYil7ImZ1bmN0aW9uIj09dHlwZW9mIGImJiJmaW5pc2giPT1hJiZ0aGlzLl9maW5pc2hIYW5kbGVycy5wdXNoKGIpfSxyZW1vdmVFdmVudExpc3RlbmVyOmZ1bmN0aW9uKGEsYil7aWYoImZpbmlzaCI9PWEpe3ZhciBjPXRoaXMuX2ZpbmlzaEhhbmRsZXJzLmluZGV4T2YoYik7Yz49MCYmdGhpcy5fZmluaXNoSGFuZGxlcnMuc3BsaWNlKGMsMSl9fSxfZmlyZUV2ZW50czpmdW5jdGlvbihhKXtpZih0aGlzLl9pc0ZpbmlzaGVkKXtpZighdGhpcy5fZmluaXNoZWRGbGFnKXt2YXIgYj1uZXcgZCh0aGlzLHRoaXMuX2N1cnJlbnRUaW1lLGEpLGM9dGhpcy5fZmluaXNoSGFuZGxlcnMuY29uY2F0KHRoaXMub25maW5pc2g/W3RoaXMub25maW5pc2hdOltdKTtzZXRUaW1lb3V0KGZ1bmN0aW9uKCl7Yy5mb3JFYWNoKGZ1bmN0aW9uKGEpe2EuY2FsbChiLnRhcmdldCxiKX0pfSwwKSx0aGlzLl9maW5pc2hlZEZsYWc9ITB9fWVsc2UgdGhpcy5fZmluaXNoZWRGbGFnPSExfSxfdGljazpmdW5jdGlvbihhLGIpe3RoaXMuX2lkbGV8fHRoaXMuX3BhdXNlZHx8KG51bGw9PXRoaXMuX3N0YXJ0VGltZT9iJiYodGhpcy5zdGFydFRpbWU9YS10aGlzLl9jdXJyZW50VGltZS90aGlzLnBsYXliYWNrUmF0ZSk6dGhpcy5faXNGaW5pc2hlZHx8dGhpcy5fdGlja0N1cnJlbnRUaW1lKChhLXRoaXMuX3N0YXJ0VGltZSkqdGhpcy5wbGF5YmFja1JhdGUpKSxiJiYodGhpcy5fY3VycmVudFRpbWVQZW5kaW5nPSExLHRoaXMuX2ZpcmVFdmVudHMoYSkpfSxnZXQgX25lZWRzVGljaygpe3JldHVybiB0aGlzLnBsYXlTdGF0ZSBpbntwZW5kaW5nOjEscnVubmluZzoxfXx8IXRoaXMuX2ZpbmlzaGVkRmxhZ30sX3RhcmdldEFuaW1hdGlvbnM6ZnVuY3Rpb24oKXt2YXIgYT10aGlzLl9lZmZlY3QuX3RhcmdldDtyZXR1cm4gYS5fYWN0aXZlQW5pbWF0aW9uc3x8KGEuX2FjdGl2ZUFuaW1hdGlvbnM9W10pLGEuX2FjdGl2ZUFuaW1hdGlvbnN9LF9tYXJrVGFyZ2V0OmZ1bmN0aW9uKCl7dmFyIGE9dGhpcy5fdGFyZ2V0QW5pbWF0aW9ucygpOy0xPT09YS5pbmRleE9mKHRoaXMpJiZhLnB1c2godGhpcyl9LF91bm1hcmtUYXJnZXQ6ZnVuY3Rpb24oKXt2YXIgYT10aGlzLl90YXJnZXRBbmltYXRpb25zKCksYj1hLmluZGV4T2YodGhpcyk7LTEhPT1iJiZhLnNwbGljZShiLDEpfX19KGEsYiksZnVuY3Rpb24oYSxiLGMpe2Z1bmN0aW9uIGQoYSl7dmFyIGI9ajtqPVtdLGE8cS5jdXJyZW50VGltZSYmKGE9cS5jdXJyZW50VGltZSkscS5fYW5pbWF0aW9ucy5zb3J0KGUpLHEuX2FuaW1hdGlvbnM9aChhLCEwLHEuX2FuaW1hdGlvbnMpWzBdLGIuZm9yRWFjaChmdW5jdGlvbihiKXtiWzFdKGEpfSksZygpLGw9dm9pZCAwfWZ1bmN0aW9uIGUoYSxiKXtyZXR1cm4gYS5fc2VxdWVuY2VOdW1iZXItYi5fc2VxdWVuY2VOdW1iZXJ9ZnVuY3Rpb24gZigpe3RoaXMuX2FuaW1hdGlvbnM9W10sdGhpcy5jdXJyZW50VGltZT13aW5kb3cucGVyZm9ybWFuY2UmJnBlcmZvcm1hbmNlLm5vdz9wZXJmb3JtYW5jZS5ub3coKTowfWZ1bmN0aW9uIGcoKXtvLmZvckVhY2goZnVuY3Rpb24oYSl7YSgpfSksby5sZW5ndGg9MH1mdW5jdGlvbiBoKGEsYyxkKXtwPSEwLG49ITEsYi50aW1lbGluZS5jdXJyZW50VGltZT1hLG09ITE7dmFyIGU9W10sZj1bXSxnPVtdLGg9W107cmV0dXJuIGQuZm9yRWFjaChmdW5jdGlvbihiKXtiLl90aWNrKGEsYyksYi5faW5FZmZlY3Q/KGYucHVzaChiLl9lZmZlY3QpLGIuX21hcmtUYXJnZXQoKSk6KGUucHVzaChiLl9lZmZlY3QpLGIuX3VubWFya1RhcmdldCgpKSxiLl9uZWVkc1RpY2smJihtPSEwKTt2YXIgZD1iLl9pbkVmZmVjdHx8Yi5fbmVlZHNUaWNrO2IuX2luVGltZWxpbmU9ZCxkP2cucHVzaChiKTpoLnB1c2goYil9KSxvLnB1c2guYXBwbHkobyxlKSxvLnB1c2guYXBwbHkobyxmKSxtJiZyZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZnVuY3Rpb24oKXt9KSxwPSExLFtnLGhdfXZhciBpPXdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUsaj1bXSxrPTA7d2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZT1mdW5jdGlvbihhKXt2YXIgYj1rKys7cmV0dXJuIDA9PWoubGVuZ3RoJiZpKGQpLGoucHVzaChbYixhXSksYn0sd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lPWZ1bmN0aW9uKGEpe2ouZm9yRWFjaChmdW5jdGlvbihiKXtiWzBdPT1hJiYoYlsxXT1mdW5jdGlvbigpe30pfSl9LGYucHJvdG90eXBlPXtfcGxheTpmdW5jdGlvbihjKXtjLl90aW1pbmc9YS5ub3JtYWxpemVUaW1pbmdJbnB1dChjLnRpbWluZyk7dmFyIGQ9bmV3IGIuQW5pbWF0aW9uKGMpO3JldHVybiBkLl9pZGxlPSExLGQuX3RpbWVsaW5lPXRoaXMsdGhpcy5fYW5pbWF0aW9ucy5wdXNoKGQpLGIucmVzdGFydCgpLGIuYXBwbHlEaXJ0aWVkQW5pbWF0aW9uKGQpLGR9fTt2YXIgbD12b2lkIDAsbT0hMSxuPSExO2IucmVzdGFydD1mdW5jdGlvbigpe3JldHVybiBtfHwobT0hMCxyZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZnVuY3Rpb24oKXt9KSxuPSEwKSxufSxiLmFwcGx5RGlydGllZEFuaW1hdGlvbj1mdW5jdGlvbihhKXtpZighcCl7YS5fbWFya1RhcmdldCgpO3ZhciBjPWEuX3RhcmdldEFuaW1hdGlvbnMoKTtjLnNvcnQoZSksaChiLnRpbWVsaW5lLmN1cnJlbnRUaW1lLCExLGMuc2xpY2UoKSlbMV0uZm9yRWFjaChmdW5jdGlvbihhKXt2YXIgYj1xLl9hbmltYXRpb25zLmluZGV4T2YoYSk7LTEhPT1iJiZxLl9hbmltYXRpb25zLnNwbGljZShiLDEpfSksZygpfX07dmFyIG89W10scD0hMSxxPW5ldyBmO2IudGltZWxpbmU9cX0oYSxiKSxmdW5jdGlvbihhKXtmdW5jdGlvbiBiKGEsYil7dmFyIGM9YS5leGVjKGIpO2lmKGMpcmV0dXJuIGM9YS5pZ25vcmVDYXNlP2NbMF0udG9Mb3dlckNhc2UoKTpjWzBdLFtjLGIuc3Vic3RyKGMubGVuZ3RoKV19ZnVuY3Rpb24gYyhhLGIpe2I9Yi5yZXBsYWNlKC9eXHMqLywiIik7dmFyIGM9YShiKTtpZihjKXJldHVybltjWzBdLGNbMV0ucmVwbGFjZSgvXlxzKi8sIiIpXX1mdW5jdGlvbiBkKGEsZCxlKXthPWMuYmluZChudWxsLGEpO2Zvcih2YXIgZj1bXTs7KXt2YXIgZz1hKGUpO2lmKCFnKXJldHVybltmLGVdO2lmKGYucHVzaChnWzBdKSxlPWdbMV0sIShnPWIoZCxlKSl8fCIiPT1nWzFdKXJldHVybltmLGVdO2U9Z1sxXX19ZnVuY3Rpb24gZShhLGIpe2Zvcih2YXIgYz0wLGQ9MDtkPGIubGVuZ3RoJiYoIS9cc3wsLy50ZXN0KGJbZF0pfHwwIT1jKTtkKyspaWYoIigiPT1iW2RdKWMrKztlbHNlIGlmKCIpIj09YltkXSYmKGMtLSwwPT1jJiZkKyssYzw9MCkpYnJlYWs7dmFyIGU9YShiLnN1YnN0cigwLGQpKTtyZXR1cm4gdm9pZCAwPT1lP3ZvaWQgMDpbZSxiLnN1YnN0cihkKV19ZnVuY3Rpb24gZihhLGIpe2Zvcih2YXIgYz1hLGQ9YjtjJiZkOyljPmQ/YyU9ZDpkJT1jO3JldHVybiBjPWEqYi8oYytkKX1mdW5jdGlvbiBnKGEpe3JldHVybiBmdW5jdGlvbihiKXt2YXIgYz1hKGIpO3JldHVybiBjJiYoY1swXT12b2lkIDApLGN9fWZ1bmN0aW9uIGgoYSxiKXtyZXR1cm4gZnVuY3Rpb24oYyl7cmV0dXJuIGEoYyl8fFtiLGNdfX1mdW5jdGlvbiBpKGIsYyl7Zm9yKHZhciBkPVtdLGU9MDtlPGIubGVuZ3RoO2UrKyl7dmFyIGY9YS5jb25zdW1lVHJpbW1lZChiW2VdLGMpO2lmKCFmfHwiIj09ZlswXSlyZXR1cm47dm9pZCAwIT09ZlswXSYmZC5wdXNoKGZbMF0pLGM9ZlsxXX1pZigiIj09YylyZXR1cm4gZH1mdW5jdGlvbiBqKGEsYixjLGQsZSl7Zm9yKHZhciBnPVtdLGg9W10saT1bXSxqPWYoZC5sZW5ndGgsZS5sZW5ndGgpLGs9MDtrPGo7aysrKXt2YXIgbD1iKGRbayVkLmxlbmd0aF0sZVtrJWUubGVuZ3RoXSk7aWYoIWwpcmV0dXJuO2cucHVzaChsWzBdKSxoLnB1c2gobFsxXSksaS5wdXNoKGxbMl0pfXJldHVybltnLGgsZnVuY3Rpb24oYil7dmFyIGQ9Yi5tYXAoZnVuY3Rpb24oYSxiKXtyZXR1cm4gaVtiXShhKX0pLmpvaW4oYyk7cmV0dXJuIGE/YShkKTpkfV19ZnVuY3Rpb24gayhhLGIsYyl7Zm9yKHZhciBkPVtdLGU9W10sZj1bXSxnPTAsaD0wO2g8Yy5sZW5ndGg7aCsrKWlmKCJmdW5jdGlvbiI9PXR5cGVvZiBjW2hdKXt2YXIgaT1jW2hdKGFbZ10sYltnKytdKTtkLnB1c2goaVswXSksZS5wdXNoKGlbMV0pLGYucHVzaChpWzJdKX1lbHNlIWZ1bmN0aW9uKGEpe2QucHVzaCghMSksZS5wdXNoKCExKSxmLnB1c2goZnVuY3Rpb24oKXtyZXR1cm4gY1thXX0pfShoKTtyZXR1cm5bZCxlLGZ1bmN0aW9uKGEpe2Zvcih2YXIgYj0iIixjPTA7YzxhLmxlbmd0aDtjKyspYis9ZltjXShhW2NdKTtyZXR1cm4gYn1dfWEuY29uc3VtZVRva2VuPWIsYS5jb25zdW1lVHJpbW1lZD1jLGEuY29uc3VtZVJlcGVhdGVkPWQsYS5jb25zdW1lUGFyZW50aGVzaXNlZD1lLGEuaWdub3JlPWcsYS5vcHRpb25hbD1oLGEuY29uc3VtZUxpc3Q9aSxhLm1lcmdlTmVzdGVkUmVwZWF0ZWQ9ai5iaW5kKG51bGwsbnVsbCksYS5tZXJnZVdyYXBwZWROZXN0ZWRSZXBlYXRlZD1qLGEubWVyZ2VMaXN0PWt9KGIpLGZ1bmN0aW9uKGEpe2Z1bmN0aW9uIGIoYil7ZnVuY3Rpb24gYyhiKXt2YXIgYz1hLmNvbnN1bWVUb2tlbigvXmluc2V0L2ksYik7cmV0dXJuIGM/KGQuaW5zZXQ9ITAsYyk6KGM9YS5jb25zdW1lTGVuZ3RoT3JQZXJjZW50KGIpKT8oZC5sZW5ndGhzLnB1c2goY1swXSksYyk6KGM9YS5jb25zdW1lQ29sb3IoYiksYz8oZC5jb2xvcj1jWzBdLGMpOnZvaWQgMCl9dmFyIGQ9e2luc2V0OiExLGxlbmd0aHM6W10sY29sb3I6bnVsbH0sZT1hLmNvbnN1bWVSZXBlYXRlZChjLC9eLyxiKTtpZihlJiZlWzBdLmxlbmd0aClyZXR1cm5bZCxlWzFdXX1mdW5jdGlvbiBjKGMpe3ZhciBkPWEuY29uc3VtZVJlcGVhdGVkKGIsL14sLyxjKTtpZihkJiYiIj09ZFsxXSlyZXR1cm4gZFswXX1mdW5jdGlvbiBkKGIsYyl7Zm9yKDtiLmxlbmd0aHMubGVuZ3RoPE1hdGgubWF4KGIubGVuZ3Rocy5sZW5ndGgsYy5sZW5ndGhzLmxlbmd0aCk7KWIubGVuZ3Rocy5wdXNoKHtweDowfSk7Zm9yKDtjLmxlbmd0aHMubGVuZ3RoPE1hdGgubWF4KGIubGVuZ3Rocy5sZW5ndGgsYy5sZW5ndGhzLmxlbmd0aCk7KWMubGVuZ3Rocy5wdXNoKHtweDowfSk7aWYoYi5pbnNldD09Yy5pbnNldCYmISFiLmNvbG9yPT0hIWMuY29sb3Ipe2Zvcih2YXIgZCxlPVtdLGY9W1tdLDBdLGc9W1tdLDBdLGg9MDtoPGIubGVuZ3Rocy5sZW5ndGg7aCsrKXt2YXIgaT1hLm1lcmdlRGltZW5zaW9ucyhiLmxlbmd0aHNbaF0sYy5sZW5ndGhzW2hdLDI9PWgpO2ZbMF0ucHVzaChpWzBdKSxnWzBdLnB1c2goaVsxXSksZS5wdXNoKGlbMl0pfWlmKGIuY29sb3ImJmMuY29sb3Ipe3ZhciBqPWEubWVyZ2VDb2xvcnMoYi5jb2xvcixjLmNvbG9yKTtmWzFdPWpbMF0sZ1sxXT1qWzFdLGQ9alsyXX1yZXR1cm5bZixnLGZ1bmN0aW9uKGEpe2Zvcih2YXIgYz1iLmluc2V0PyJpbnNldCAiOiIgIixmPTA7ZjxlLmxlbmd0aDtmKyspYys9ZVtmXShhWzBdW2ZdKSsiICI7cmV0dXJuIGQmJihjKz1kKGFbMV0pKSxjfV19fWZ1bmN0aW9uIGUoYixjLGQsZSl7ZnVuY3Rpb24gZihhKXtyZXR1cm57aW5zZXQ6YSxjb2xvcjpbMCwwLDAsMF0sbGVuZ3Roczpbe3B4OjB9LHtweDowfSx7cHg6MH0se3B4OjB9XX19Zm9yKHZhciBnPVtdLGg9W10saT0wO2k8ZC5sZW5ndGh8fGk8ZS5sZW5ndGg7aSsrKXt2YXIgaj1kW2ldfHxmKGVbaV0uaW5zZXQpLGs9ZVtpXXx8ZihkW2ldLmluc2V0KTtnLnB1c2goaiksaC5wdXNoKGspfXJldHVybiBhLm1lcmdlTmVzdGVkUmVwZWF0ZWQoYixjLGcsaCl9dmFyIGY9ZS5iaW5kKG51bGwsZCwiLCAiKTthLmFkZFByb3BlcnRpZXNIYW5kbGVyKGMsZixbImJveC1zaGFkb3ciLCJ0ZXh0LXNoYWRvdyJdKX0oYiksZnVuY3Rpb24oYSxiKXtmdW5jdGlvbiBjKGEpe3JldHVybiBhLnRvRml4ZWQoMykucmVwbGFjZSgvMCskLywiIikucmVwbGFjZSgvXC4kLywiIil9ZnVuY3Rpb24gZChhLGIsYyl7cmV0dXJuIE1hdGgubWluKGIsTWF0aC5tYXgoYSxjKSl9ZnVuY3Rpb24gZShhKXtpZigvXlxzKlstK10/KFxkKlwuKT9cZCtccyokLy50ZXN0KGEpKXJldHVybiBOdW1iZXIoYSl9ZnVuY3Rpb24gZihhLGIpe3JldHVyblthLGIsY119ZnVuY3Rpb24gZyhhLGIpe2lmKDAhPWEpcmV0dXJuIGkoMCwxLzApKGEsYil9ZnVuY3Rpb24gaChhLGIpe3JldHVyblthLGIsZnVuY3Rpb24oYSl7cmV0dXJuIE1hdGgucm91bmQoZCgxLDEvMCxhKSl9XX1mdW5jdGlvbiBpKGEsYil7cmV0dXJuIGZ1bmN0aW9uKGUsZil7cmV0dXJuW2UsZixmdW5jdGlvbihlKXtyZXR1cm4gYyhkKGEsYixlKSl9XX19ZnVuY3Rpb24gaihhKXt2YXIgYj1hLnRyaW0oKS5zcGxpdCgvXHMqW1xzLF1ccyovKTtpZigwIT09Yi5sZW5ndGgpe2Zvcih2YXIgYz1bXSxkPTA7ZDxiLmxlbmd0aDtkKyspe3ZhciBmPWUoYltkXSk7aWYodm9pZCAwPT09ZilyZXR1cm47Yy5wdXNoKGYpfXJldHVybiBjfX1mdW5jdGlvbiBrKGEsYil7aWYoYS5sZW5ndGg9PWIubGVuZ3RoKXJldHVyblthLGIsZnVuY3Rpb24oYSl7cmV0dXJuIGEubWFwKGMpLmpvaW4oIiAiKX1dfWZ1bmN0aW9uIGwoYSxiKXtyZXR1cm5bYSxiLE1hdGgucm91bmRdfWEuY2xhbXA9ZCxhLmFkZFByb3BlcnRpZXNIYW5kbGVyKGosayxbInN0cm9rZS1kYXNoYXJyYXkiXSksYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihlLGkoMCwxLzApLFsiYm9yZGVyLWltYWdlLXdpZHRoIiwibGluZS1oZWlnaHQiXSksYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihlLGkoMCwxKSxbIm9wYWNpdHkiLCJzaGFwZS1pbWFnZS10aHJlc2hvbGQiXSksYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihlLGcsWyJmbGV4LWdyb3ciLCJmbGV4LXNocmluayJdKSxhLmFkZFByb3BlcnRpZXNIYW5kbGVyKGUsaCxbIm9ycGhhbnMiLCJ3aWRvd3MiXSksYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihlLGwsWyJ6LWluZGV4Il0pLGEucGFyc2VOdW1iZXI9ZSxhLnBhcnNlTnVtYmVyTGlzdD1qLGEubWVyZ2VOdW1iZXJzPWYsYS5udW1iZXJUb1N0cmluZz1jfShiKSxmdW5jdGlvbihhLGIpe2Z1bmN0aW9uIGMoYSxiKXtpZigidmlzaWJsZSI9PWF8fCJ2aXNpYmxlIj09YilyZXR1cm5bMCwxLGZ1bmN0aW9uKGMpe3JldHVybiBjPD0wP2E6Yz49MT9iOiJ2aXNpYmxlIn1dfWEuYWRkUHJvcGVydGllc0hhbmRsZXIoU3RyaW5nLGMsWyJ2aXNpYmlsaXR5Il0pfShiKSxmdW5jdGlvbihhLGIpe2Z1bmN0aW9uIGMoYSl7YT1hLnRyaW0oKSxmLmZpbGxTdHlsZT0iIzAwMCIsZi5maWxsU3R5bGU9YTt2YXIgYj1mLmZpbGxTdHlsZTtpZihmLmZpbGxTdHlsZT0iI2ZmZiIsZi5maWxsU3R5bGU9YSxiPT1mLmZpbGxTdHlsZSl7Zi5maWxsUmVjdCgwLDAsMSwxKTt2YXIgYz1mLmdldEltYWdlRGF0YSgwLDAsMSwxKS5kYXRhO2YuY2xlYXJSZWN0KDAsMCwxLDEpO3ZhciBkPWNbM10vMjU1O3JldHVybltjWzBdKmQsY1sxXSpkLGNbMl0qZCxkXX19ZnVuY3Rpb24gZChiLGMpe3JldHVybltiLGMsZnVuY3Rpb24oYil7ZnVuY3Rpb24gYyhhKXtyZXR1cm4gTWF0aC5tYXgoMCxNYXRoLm1pbigyNTUsYSkpfWlmKGJbM10pZm9yKHZhciBkPTA7ZDwzO2QrKyliW2RdPU1hdGgucm91bmQoYyhiW2RdL2JbM10pKTtyZXR1cm4gYlszXT1hLm51bWJlclRvU3RyaW5nKGEuY2xhbXAoMCwxLGJbM10pKSwicmdiYSgiK2Iuam9pbigiLCIpKyIpIn1dfXZhciBlPWRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygiaHR0cDovL3d3dy53My5vcmcvMTk5OS94aHRtbCIsImNhbnZhcyIpO2Uud2lkdGg9ZS5oZWlnaHQ9MTt2YXIgZj1lLmdldENvbnRleHQoIjJkIik7YS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihjLGQsWyJiYWNrZ3JvdW5kLWNvbG9yIiwiYm9yZGVyLWJvdHRvbS1jb2xvciIsImJvcmRlci1sZWZ0LWNvbG9yIiwiYm9yZGVyLXJpZ2h0LWNvbG9yIiwiYm9yZGVyLXRvcC1jb2xvciIsImNvbG9yIiwiZmlsbCIsImZsb29kLWNvbG9yIiwibGlnaHRpbmctY29sb3IiLCJvdXRsaW5lLWNvbG9yIiwic3RvcC1jb2xvciIsInN0cm9rZSIsInRleHQtZGVjb3JhdGlvbi1jb2xvciJdKSxhLmNvbnN1bWVDb2xvcj1hLmNvbnN1bWVQYXJlbnRoZXNpc2VkLmJpbmQobnVsbCxjKSxhLm1lcmdlQ29sb3JzPWR9KGIpLGZ1bmN0aW9uKGEsYil7ZnVuY3Rpb24gYyhhKXtmdW5jdGlvbiBiKCl7dmFyIGI9aC5leGVjKGEpO2c9Yj9iWzBdOnZvaWQgMH1mdW5jdGlvbiBjKCl7dmFyIGE9TnVtYmVyKGcpO3JldHVybiBiKCksYX1mdW5jdGlvbiBkKCl7aWYoIigiIT09ZylyZXR1cm4gYygpO2IoKTt2YXIgYT1mKCk7cmV0dXJuIikiIT09Zz9OYU46KGIoKSxhKX1mdW5jdGlvbiBlKCl7Zm9yKHZhciBhPWQoKTsiKiI9PT1nfHwiLyI9PT1nOyl7dmFyIGM9ZztiKCk7dmFyIGU9ZCgpOyIqIj09PWM/YSo9ZTphLz1lfXJldHVybiBhfWZ1bmN0aW9uIGYoKXtmb3IodmFyIGE9ZSgpOyIrIj09PWd8fCItIj09PWc7KXt2YXIgYz1nO2IoKTt2YXIgZD1lKCk7IisiPT09Yz9hKz1kOmEtPWR9cmV0dXJuIGF9dmFyIGcsaD0vKFtcK1wtXHdcLl0rfFtcKFwpXCpcL10pL2c7cmV0dXJuIGIoKSxmKCl9ZnVuY3Rpb24gZChhLGIpe2lmKCIwIj09KGI9Yi50cmltKCkudG9Mb3dlckNhc2UoKSkmJiJweCIuc2VhcmNoKGEpPj0wKXJldHVybntweDowfTtpZigvXlteKF0qJHxeY2FsYy8udGVzdChiKSl7Yj1iLnJlcGxhY2UoL2NhbGNcKC9nLCIoIik7dmFyIGQ9e307Yj1iLnJlcGxhY2UoYSxmdW5jdGlvbihhKXtyZXR1cm4gZFthXT1udWxsLCJVIithfSk7Zm9yKHZhciBlPSJVKCIrYS5zb3VyY2UrIikiLGY9Yi5yZXBsYWNlKC9bLStdPyhcZCpcLik/XGQrKFtFZV1bLStdP1xkKyk/L2csIk4iKS5yZXBsYWNlKG5ldyBSZWdFeHAoIk4iK2UsImciKSwiRCIpLnJlcGxhY2UoL1xzWystXVxzL2csIk8iKS5yZXBsYWNlKC9ccy9nLCIiKSxnPVsvTlwqKEQpL2csLyhOfEQpWypcL11OL2csLyhOfEQpT1wxL2csL1woKE58RClcKS9nXSxoPTA7aDxnLmxlbmd0aDspZ1toXS50ZXN0KGYpPyhmPWYucmVwbGFjZShnW2hdLCIkMSIpLGg9MCk6aCsrO2lmKCJEIj09Zil7Zm9yKHZhciBpIGluIGQpe3ZhciBqPWMoYi5yZXBsYWNlKG5ldyBSZWdFeHAoIlUiK2ksImciKSwiIikucmVwbGFjZShuZXcgUmVnRXhwKGUsImciKSwiKjAiKSk7aWYoIWlzRmluaXRlKGopKXJldHVybjtkW2ldPWp9cmV0dXJuIGR9fX1mdW5jdGlvbiBlKGEsYil7cmV0dXJuIGYoYSxiLCEwKX1mdW5jdGlvbiBmKGIsYyxkKXt2YXIgZSxmPVtdO2ZvcihlIGluIGIpZi5wdXNoKGUpO2ZvcihlIGluIGMpZi5pbmRleE9mKGUpPDAmJmYucHVzaChlKTtyZXR1cm4gYj1mLm1hcChmdW5jdGlvbihhKXtyZXR1cm4gYlthXXx8MH0pLGM9Zi5tYXAoZnVuY3Rpb24oYSl7cmV0dXJuIGNbYV18fDB9KSxbYixjLGZ1bmN0aW9uKGIpe3ZhciBjPWIubWFwKGZ1bmN0aW9uKGMsZSl7cmV0dXJuIDE9PWIubGVuZ3RoJiZkJiYoYz1NYXRoLm1heChjLDApKSxhLm51bWJlclRvU3RyaW5nKGMpK2ZbZV19KS5qb2luKCIgKyAiKTtyZXR1cm4gYi5sZW5ndGg+MT8iY2FsYygiK2MrIikiOmN9XX12YXIgZz0icHh8ZW18ZXh8Y2h8cmVtfHZ3fHZofHZtaW58dm1heHxjbXxtbXxpbnxwdHxwYyIsaD1kLmJpbmQobnVsbCxuZXcgUmVnRXhwKGcsImciKSksaT1kLmJpbmQobnVsbCxuZXcgUmVnRXhwKGcrInwlIiwiZyIpKSxqPWQuYmluZChudWxsLC9kZWd8cmFkfGdyYWR8dHVybi9nKTthLnBhcnNlTGVuZ3RoPWgsYS5wYXJzZUxlbmd0aE9yUGVyY2VudD1pLGEuY29uc3VtZUxlbmd0aE9yUGVyY2VudD1hLmNvbnN1bWVQYXJlbnRoZXNpc2VkLmJpbmQobnVsbCxpKSxhLnBhcnNlQW5nbGU9aixhLm1lcmdlRGltZW5zaW9ucz1mO3ZhciBrPWEuY29uc3VtZVBhcmVudGhlc2lzZWQuYmluZChudWxsLGgpLGw9YS5jb25zdW1lUmVwZWF0ZWQuYmluZCh2b2lkIDAsaywvXi8pLG09YS5jb25zdW1lUmVwZWF0ZWQuYmluZCh2b2lkIDAsbCwvXiwvKTthLmNvbnN1bWVTaXplUGFpckxpc3Q9bTt2YXIgbj1mdW5jdGlvbihhKXt2YXIgYj1tKGEpO2lmKGImJiIiPT1iWzFdKXJldHVybiBiWzBdfSxvPWEubWVyZ2VOZXN0ZWRSZXBlYXRlZC5iaW5kKHZvaWQgMCxlLCIgIikscD1hLm1lcmdlTmVzdGVkUmVwZWF0ZWQuYmluZCh2b2lkIDAsbywiLCIpO2EubWVyZ2VOb25OZWdhdGl2ZVNpemVQYWlyPW8sYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihuLHAsWyJiYWNrZ3JvdW5kLXNpemUiXSksYS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihpLGUsWyJib3JkZXItYm90dG9tLXdpZHRoIiwiYm9yZGVyLWltYWdlLXdpZHRoIiwiYm9yZGVyLWxlZnQtd2lkdGgiLCJib3JkZXItcmlnaHQtd2lkdGgiLCJib3JkZXItdG9wLXdpZHRoIiwiZmxleC1iYXNpcyIsImZvbnQtc2l6ZSIsImhlaWdodCIsImxpbmUtaGVpZ2h0IiwibWF4LWhlaWdodCIsIm1heC13aWR0aCIsIm91dGxpbmUtd2lkdGgiLCJ3aWR0aCJdKSxhLmFkZFByb3BlcnRpZXNIYW5kbGVyKGksZixbImJvcmRlci1ib3R0b20tbGVmdC1yYWRpdXMiLCJib3JkZXItYm90dG9tLXJpZ2h0LXJhZGl1cyIsImJvcmRlci10b3AtbGVmdC1yYWRpdXMiLCJib3JkZXItdG9wLXJpZ2h0LXJhZGl1cyIsImJvdHRvbSIsImxlZnQiLCJsZXR0ZXItc3BhY2luZyIsIm1hcmdpbi1ib3R0b20iLCJtYXJnaW4tbGVmdCIsIm1hcmdpbi1yaWdodCIsIm1hcmdpbi10b3AiLCJtaW4taGVpZ2h0IiwibWluLXdpZHRoIiwib3V0bGluZS1vZmZzZXQiLCJwYWRkaW5nLWJvdHRvbSIsInBhZGRpbmctbGVmdCIsInBhZGRpbmctcmlnaHQiLCJwYWRkaW5nLXRvcCIsInBlcnNwZWN0aXZlIiwicmlnaHQiLCJzaGFwZS1tYXJnaW4iLCJzdHJva2UtZGFzaG9mZnNldCIsInRleHQtaW5kZW50IiwidG9wIiwidmVydGljYWwtYWxpZ24iLCJ3b3JkLXNwYWNpbmciXSl9KGIpLGZ1bmN0aW9uKGEsYil7ZnVuY3Rpb24gYyhiKXtyZXR1cm4gYS5jb25zdW1lTGVuZ3RoT3JQZXJjZW50KGIpfHxhLmNvbnN1bWVUb2tlbigvXmF1dG8vLGIpfWZ1bmN0aW9uIGQoYil7dmFyIGQ9YS5jb25zdW1lTGlzdChbYS5pZ25vcmUoYS5jb25zdW1lVG9rZW4uYmluZChudWxsLC9ecmVjdC8pKSxhLmlnbm9yZShhLmNvbnN1bWVUb2tlbi5iaW5kKG51bGwsL15cKC8pKSxhLmNvbnN1bWVSZXBlYXRlZC5iaW5kKG51bGwsYywvXiwvKSxhLmlnbm9yZShhLmNvbnN1bWVUb2tlbi5iaW5kKG51bGwsL15cKS8pKV0sYik7aWYoZCYmND09ZFswXS5sZW5ndGgpcmV0dXJuIGRbMF19ZnVuY3Rpb24gZShiLGMpe3JldHVybiJhdXRvIj09Ynx8ImF1dG8iPT1jP1shMCwhMSxmdW5jdGlvbihkKXt2YXIgZT1kP2I6YztpZigiYXV0byI9PWUpcmV0dXJuImF1dG8iO3ZhciBmPWEubWVyZ2VEaW1lbnNpb25zKGUsZSk7cmV0dXJuIGZbMl0oZlswXSl9XTphLm1lcmdlRGltZW5zaW9ucyhiLGMpfWZ1bmN0aW9uIGYoYSl7cmV0dXJuInJlY3QoIithKyIpIn12YXIgZz1hLm1lcmdlV3JhcHBlZE5lc3RlZFJlcGVhdGVkLmJpbmQobnVsbCxmLGUsIiwgIik7YS5wYXJzZUJveD1kLGEubWVyZ2VCb3hlcz1nLGEuYWRkUHJvcGVydGllc0hhbmRsZXIoZCxnLFsiY2xpcCJdKX0oYiksZnVuY3Rpb24oYSxiKXtmdW5jdGlvbiBjKGEpe3JldHVybiBmdW5jdGlvbihiKXt2YXIgYz0wO3JldHVybiBhLm1hcChmdW5jdGlvbihhKXtyZXR1cm4gYT09PWs/YltjKytdOmF9KX19ZnVuY3Rpb24gZChhKXtyZXR1cm4gYX1mdW5jdGlvbiBlKGIpe2lmKCJub25lIj09KGI9Yi50b0xvd2VyQ2FzZSgpLnRyaW0oKSkpcmV0dXJuW107Zm9yKHZhciBjLGQ9L1xzKihcdyspXCgoW14pXSopXCkvZyxlPVtdLGY9MDtjPWQuZXhlYyhiKTspe2lmKGMuaW5kZXghPWYpcmV0dXJuO2Y9Yy5pbmRleCtjWzBdLmxlbmd0aDt2YXIgZz1jWzFdLGg9bltnXTtpZighaClyZXR1cm47dmFyIGk9Y1syXS5zcGxpdCgiLCIpLGo9aFswXTtpZihqLmxlbmd0aDxpLmxlbmd0aClyZXR1cm47Zm9yKHZhciBrPVtdLG89MDtvPGoubGVuZ3RoO28rKyl7dmFyIHAscT1pW29dLHI9altvXTtpZih2b2lkIDA9PT0ocD1xP3tBOmZ1bmN0aW9uKGIpe3JldHVybiIwIj09Yi50cmltKCk/bTphLnBhcnNlQW5nbGUoYil9LE46YS5wYXJzZU51bWJlcixUOmEucGFyc2VMZW5ndGhPclBlcmNlbnQsTDphLnBhcnNlTGVuZ3RofVtyLnRvVXBwZXJDYXNlKCldKHEpOnthOm0sbjprWzBdLHQ6bH1bcl0pKXJldHVybjtrLnB1c2gocCl9aWYoZS5wdXNoKHt0OmcsZDprfSksZC5sYXN0SW5kZXg9PWIubGVuZ3RoKXJldHVybiBlfX1mdW5jdGlvbiBmKGEpe3JldHVybiBhLnRvRml4ZWQoNikucmVwbGFjZSgiLjAwMDAwMCIsIiIpfWZ1bmN0aW9uIGcoYixjKXtpZihiLmRlY29tcG9zaXRpb25QYWlyIT09Yyl7Yi5kZWNvbXBvc2l0aW9uUGFpcj1jO3ZhciBkPWEubWFrZU1hdHJpeERlY29tcG9zaXRpb24oYil9aWYoYy5kZWNvbXBvc2l0aW9uUGFpciE9PWIpe2MuZGVjb21wb3NpdGlvblBhaXI9Yjt2YXIgZT1hLm1ha2VNYXRyaXhEZWNvbXBvc2l0aW9uKGMpfXJldHVybiBudWxsPT1kWzBdfHxudWxsPT1lWzBdP1tbITFdLFshMF0sZnVuY3Rpb24oYSl7cmV0dXJuIGE/Y1swXS5kOmJbMF0uZH1dOihkWzBdLnB1c2goMCksZVswXS5wdXNoKDEpLFtkLGUsZnVuY3Rpb24oYil7dmFyIGM9YS5xdWF0KGRbMF1bM10sZVswXVszXSxiWzVdKTtyZXR1cm4gYS5jb21wb3NlTWF0cml4KGJbMF0sYlsxXSxiWzJdLGMsYls0XSkubWFwKGYpLmpvaW4oIiwiKX1dKX1mdW5jdGlvbiBoKGEpe3JldHVybiBhLnJlcGxhY2UoL1t4eV0vLCIiKX1mdW5jdGlvbiBpKGEpe3JldHVybiBhLnJlcGxhY2UoLyh4fHl8enwzZCk/JC8sIjNkIil9ZnVuY3Rpb24gaihiLGMpe3ZhciBkPWEubWFrZU1hdHJpeERlY29tcG9zaXRpb24mJiEwLGU9ITE7aWYoIWIubGVuZ3RofHwhYy5sZW5ndGgpe2IubGVuZ3RofHwoZT0hMCxiPWMsYz1bXSk7Zm9yKHZhciBmPTA7ZjxiLmxlbmd0aDtmKyspe3ZhciBqPWJbZl0udCxrPWJbZl0uZCxsPSJzY2FsZSI9PWouc3Vic3RyKDAsNSk/MTowO2MucHVzaCh7dDpqLGQ6ay5tYXAoZnVuY3Rpb24oYSl7aWYoIm51bWJlciI9PXR5cGVvZiBhKXJldHVybiBsO3ZhciBiPXt9O2Zvcih2YXIgYyBpbiBhKWJbY109bDtyZXR1cm4gYn0pfSl9fXZhciBtPWZ1bmN0aW9uKGEsYil7cmV0dXJuInBlcnNwZWN0aXZlIj09YSYmInBlcnNwZWN0aXZlIj09Ynx8KCJtYXRyaXgiPT1hfHwibWF0cml4M2QiPT1hKSYmKCJtYXRyaXgiPT1ifHwibWF0cml4M2QiPT1iKX0sbz1bXSxwPVtdLHE9W107aWYoYi5sZW5ndGghPWMubGVuZ3RoKXtpZighZClyZXR1cm47dmFyIHI9ZyhiLGMpO289W3JbMF1dLHA9W3JbMV1dLHE9W1sibWF0cml4IixbclsyXV1dXX1lbHNlIGZvcih2YXIgZj0wO2Y8Yi5sZW5ndGg7ZisrKXt2YXIgaixzPWJbZl0udCx0PWNbZl0udCx1PWJbZl0uZCx2PWNbZl0uZCx3PW5bc10seD1uW3RdO2lmKG0ocyx0KSl7aWYoIWQpcmV0dXJuO3ZhciByPWcoW2JbZl1dLFtjW2ZdXSk7by5wdXNoKHJbMF0pLHAucHVzaChyWzFdKSxxLnB1c2goWyJtYXRyaXgiLFtyWzJdXV0pfWVsc2V7aWYocz09dClqPXM7ZWxzZSBpZih3WzJdJiZ4WzJdJiZoKHMpPT1oKHQpKWo9aChzKSx1PXdbMl0odSksdj14WzJdKHYpO2Vsc2V7aWYoIXdbMV18fCF4WzFdfHxpKHMpIT1pKHQpKXtpZighZClyZXR1cm47dmFyIHI9ZyhiLGMpO289W3JbMF1dLHA9W3JbMV1dLHE9W1sibWF0cml4IixbclsyXV1dXTticmVha31qPWkocyksdT13WzFdKHUpLHY9eFsxXSh2KX1mb3IodmFyIHk9W10sej1bXSxBPVtdLEI9MDtCPHUubGVuZ3RoO0IrKyl7dmFyIEM9Im51bWJlciI9PXR5cGVvZiB1W0JdP2EubWVyZ2VOdW1iZXJzOmEubWVyZ2VEaW1lbnNpb25zLHI9Qyh1W0JdLHZbQl0pO3lbQl09clswXSx6W0JdPXJbMV0sQS5wdXNoKHJbMl0pfW8ucHVzaCh5KSxwLnB1c2goeikscS5wdXNoKFtqLEFdKX19aWYoZSl7dmFyIEQ9bztvPXAscD1EfXJldHVybltvLHAsZnVuY3Rpb24oYSl7cmV0dXJuIGEubWFwKGZ1bmN0aW9uKGEsYil7dmFyIGM9YS5tYXAoZnVuY3Rpb24oYSxjKXtyZXR1cm4gcVtiXVsxXVtjXShhKX0pLmpvaW4oIiwiKTtyZXR1cm4ibWF0cml4Ij09cVtiXVswXSYmMTY9PWMuc3BsaXQoIiwiKS5sZW5ndGgmJihxW2JdWzBdPSJtYXRyaXgzZCIpLHFbYl1bMF0rIigiK2MrIikifSkuam9pbigiICIpfV19dmFyIGs9bnVsbCxsPXtweDowfSxtPXtkZWc6MH0sbj17bWF0cml4OlsiTk5OTk5OIixbayxrLDAsMCxrLGssMCwwLDAsMCwxLDAsayxrLDAsMV0sZF0sbWF0cml4M2Q6WyJOTk5OTk5OTk5OTk5OTk5OIixkXSxyb3RhdGU6WyJBIl0scm90YXRleDpbIkEiXSxyb3RhdGV5OlsiQSJdLHJvdGF0ZXo6WyJBIl0scm90YXRlM2Q6WyJOTk5BIl0scGVyc3BlY3RpdmU6WyJMIl0sc2NhbGU6WyJObiIsYyhbayxrLDFdKSxkXSxzY2FsZXg6WyJOIixjKFtrLDEsMV0pLGMoW2ssMV0pXSxzY2FsZXk6WyJOIixjKFsxLGssMV0pLGMoWzEsa10pXSxzY2FsZXo6WyJOIixjKFsxLDEsa10pXSxzY2FsZTNkOlsiTk5OIixkXSxza2V3OlsiQWEiLG51bGwsZF0sc2tld3g6WyJBIixudWxsLGMoW2ssbV0pXSxza2V3eTpbIkEiLG51bGwsYyhbbSxrXSldLHRyYW5zbGF0ZTpbIlR0IixjKFtrLGssbF0pLGRdLHRyYW5zbGF0ZXg6WyJUIixjKFtrLGwsbF0pLGMoW2ssbF0pXSx0cmFuc2xhdGV5OlsiVCIsYyhbbCxrLGxdKSxjKFtsLGtdKV0sdHJhbnNsYXRlejpbIkwiLGMoW2wsbCxrXSldLHRyYW5zbGF0ZTNkOlsiVFRMIixkXX07YS5hZGRQcm9wZXJ0aWVzSGFuZGxlcihlLGosWyJ0cmFuc2Zvcm0iXSksYS50cmFuc2Zvcm1Ub1N2Z01hdHJpeD1mdW5jdGlvbihiKXt2YXIgYz1hLnRyYW5zZm9ybUxpc3RUb01hdHJpeChlKGIpKTtyZXR1cm4ibWF0cml4KCIrZihjWzBdKSsiICIrZihjWzFdKSsiICIrZihjWzRdKSsiICIrZihjWzVdKSsiICIrZihjWzEyXSkrIiAiK2YoY1sxM10pKyIpIn19KGIpLGZ1bmN0aW9uKGEsYil7ZnVuY3Rpb24gYyhhLGIpe2IuY29uY2F0KFthXSkuZm9yRWFjaChmdW5jdGlvbihiKXtiIGluIGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5zdHlsZSYmKGRbYV09YiksZVtiXT1hfSl9dmFyIGQ9e30sZT17fTtjKCJ0cmFuc2Zvcm0iLFsid2Via2l0VHJhbnNmb3JtIiwibXNUcmFuc2Zvcm0iXSksYygidHJhbnNmb3JtT3JpZ2luIixbIndlYmtpdFRyYW5zZm9ybU9yaWdpbiJdKSxjKCJwZXJzcGVjdGl2ZSIsWyJ3ZWJraXRQZXJzcGVjdGl2ZSJdKSxjKCJwZXJzcGVjdGl2ZU9yaWdpbiIsWyJ3ZWJraXRQZXJzcGVjdGl2ZU9yaWdpbiJdKSxhLnByb3BlcnR5TmFtZT1mdW5jdGlvbihhKXtyZXR1cm4gZFthXXx8YX0sYS51bnByZWZpeGVkUHJvcGVydHlOYW1lPWZ1bmN0aW9uKGEpe3JldHVybiBlW2FdfHxhfX0oYil9KCksZnVuY3Rpb24oKXtpZih2b2lkIDA9PT1kb2N1bWVudC5jcmVhdGVFbGVtZW50KCJkaXYiKS5hbmltYXRlKFtdKS5vbmNhbmNlbCl7dmFyIGE7aWYod2luZG93LnBlcmZvcm1hbmNlJiZwZXJmb3JtYW5jZS5ub3cpdmFyIGE9ZnVuY3Rpb24oKXtyZXR1cm4gcGVyZm9ybWFuY2Uubm93KCl9O2Vsc2UgdmFyIGE9ZnVuY3Rpb24oKXtyZXR1cm4gRGF0ZS5ub3coKX07dmFyIGI9ZnVuY3Rpb24oYSxiLGMpe3RoaXMudGFyZ2V0PWEsdGhpcy5jdXJyZW50VGltZT1iLHRoaXMudGltZWxpbmVUaW1lPWMsdGhpcy50eXBlPSJjYW5jZWwiLHRoaXMuYnViYmxlcz0hMSx0aGlzLmNhbmNlbGFibGU9ITEsdGhpcy5jdXJyZW50VGFyZ2V0PWEsdGhpcy5kZWZhdWx0UHJldmVudGVkPSExLHRoaXMuZXZlbnRQaGFzZT1FdmVudC5BVF9UQVJHRVQsdGhpcy50aW1lU3RhbXA9RGF0ZS5ub3coKX0sYz13aW5kb3cuRWxlbWVudC5wcm90b3R5cGUuYW5pbWF0ZTt3aW5kb3cuRWxlbWVudC5wcm90b3R5cGUuYW5pbWF0ZT1mdW5jdGlvbihkLGUpe3ZhciBmPWMuY2FsbCh0aGlzLGQsZSk7Zi5fY2FuY2VsSGFuZGxlcnM9W10sZi5vbmNhbmNlbD1udWxsO3ZhciBnPWYuY2FuY2VsO2YuY2FuY2VsPWZ1bmN0aW9uKCl7Zy5jYWxsKHRoaXMpO3ZhciBjPW5ldyBiKHRoaXMsbnVsbCxhKCkpLGQ9dGhpcy5fY2FuY2VsSGFuZGxlcnMuY29uY2F0KHRoaXMub25jYW5jZWw/W3RoaXMub25jYW5jZWxdOltdKTtzZXRUaW1lb3V0KGZ1bmN0aW9uKCl7ZC5mb3JFYWNoKGZ1bmN0aW9uKGEpe2EuY2FsbChjLnRhcmdldCxjKX0pfSwwKX07dmFyIGg9Zi5hZGRFdmVudExpc3RlbmVyO2YuYWRkRXZlbnRMaXN0ZW5lcj1mdW5jdGlvbihhLGIpeyJmdW5jdGlvbiI9PXR5cGVvZiBiJiYiY2FuY2VsIj09YT90aGlzLl9jYW5jZWxIYW5kbGVycy5wdXNoKGIpOmguY2FsbCh0aGlzLGEsYil9O3ZhciBpPWYucmVtb3ZlRXZlbnRMaXN0ZW5lcjtyZXR1cm4gZi5yZW1vdmVFdmVudExpc3RlbmVyPWZ1bmN0aW9uKGEsYil7aWYoImNhbmNlbCI9PWEpe3ZhciBjPXRoaXMuX2NhbmNlbEhhbmRsZXJzLmluZGV4T2YoYik7Yz49MCYmdGhpcy5fY2FuY2VsSGFuZGxlcnMuc3BsaWNlKGMsMSl9ZWxzZSBpLmNhbGwodGhpcyxhLGIpfSxmfX19KCksZnVuY3Rpb24oYSl7dmFyIGI9ZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LGM9bnVsbCxkPSExO3RyeXt2YXIgZT1nZXRDb21wdXRlZFN0eWxlKGIpLmdldFByb3BlcnR5VmFsdWUoIm9wYWNpdHkiKSxmPSIwIj09ZT8iMSI6IjAiO2M9Yi5hbmltYXRlKHtvcGFjaXR5OltmLGZdfSx7ZHVyYXRpb246MX0pLGMuY3VycmVudFRpbWU9MCxkPWdldENvbXB1dGVkU3R5bGUoYikuZ2V0UHJvcGVydHlWYWx1ZSgib3BhY2l0eSIpPT1mfWNhdGNoKGEpe31maW5hbGx5e2MmJmMuY2FuY2VsKCl9aWYoIWQpe3ZhciBnPXdpbmRvdy5FbGVtZW50LnByb3RvdHlwZS5hbmltYXRlO3dpbmRvdy5FbGVtZW50LnByb3RvdHlwZS5hbmltYXRlPWZ1bmN0aW9uKGIsYyl7cmV0dXJuIHdpbmRvdy5TeW1ib2wmJlN5bWJvbC5pdGVyYXRvciYmQXJyYXkucHJvdG90eXBlLmZyb20mJmJbU3ltYm9sLml0ZXJhdG9yXSYmKGI9QXJyYXkuZnJvbShiKSksQXJyYXkuaXNBcnJheShiKXx8bnVsbD09PWJ8fChiPWEuY29udmVydFRvQXJyYXlGb3JtKGIpKSxnLmNhbGwodGhpcyxiLGMpfX19KGEpLGZ1bmN0aW9uKGEsYixjKXtmdW5jdGlvbiBkKGEpe3ZhciBjPWIudGltZWxpbmU7Yy5jdXJyZW50VGltZT1hLGMuX2Rpc2NhcmRBbmltYXRpb25zKCksMD09Yy5fYW5pbWF0aW9ucy5sZW5ndGg/Zj0hMTpyZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZCl9dmFyIGU9d2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZTt3aW5kb3cucmVxdWVzdEFuaW1hdGlvbkZyYW1lPWZ1bmN0aW9uKGEpe3JldHVybiBlKGZ1bmN0aW9uKGMpe2IudGltZWxpbmUuX3VwZGF0ZUFuaW1hdGlvbnNQcm9taXNlcygpLGEoYyksYi50aW1lbGluZS5fdXBkYXRlQW5pbWF0aW9uc1Byb21pc2VzKCl9KX0sYi5BbmltYXRpb25UaW1lbGluZT1mdW5jdGlvbigpe3RoaXMuX2FuaW1hdGlvbnM9W10sdGhpcy5jdXJyZW50VGltZT12b2lkIDB9LGIuQW5pbWF0aW9uVGltZWxpbmUucHJvdG90eXBlPXtnZXRBbmltYXRpb25zOmZ1bmN0aW9uKCl7cmV0dXJuIHRoaXMuX2Rpc2NhcmRBbmltYXRpb25zKCksdGhpcy5fYW5pbWF0aW9ucy5zbGljZSgpfSxfdXBkYXRlQW5pbWF0aW9uc1Byb21pc2VzOmZ1bmN0aW9uKCl7Yi5hbmltYXRpb25zV2l0aFByb21pc2VzPWIuYW5pbWF0aW9uc1dpdGhQcm9taXNlcy5maWx0ZXIoZnVuY3Rpb24oYSl7cmV0dXJuIGEuX3VwZGF0ZVByb21pc2VzKCl9KX0sX2Rpc2NhcmRBbmltYXRpb25zOmZ1bmN0aW9uKCl7dGhpcy5fdXBkYXRlQW5pbWF0aW9uc1Byb21pc2VzKCksdGhpcy5fYW5pbWF0aW9ucz10aGlzLl9hbmltYXRpb25zLmZpbHRlcihmdW5jdGlvbihhKXtyZXR1cm4iZmluaXNoZWQiIT1hLnBsYXlTdGF0ZSYmImlkbGUiIT1hLnBsYXlTdGF0ZX0pfSxfcGxheTpmdW5jdGlvbihhKXt2YXIgYz1uZXcgYi5BbmltYXRpb24oYSx0aGlzKTtyZXR1cm4gdGhpcy5fYW5pbWF0aW9ucy5wdXNoKGMpLGIucmVzdGFydFdlYkFuaW1hdGlvbnNOZXh0VGljaygpLGMuX3VwZGF0ZVByb21pc2VzKCksYy5fYW5pbWF0aW9uLnBsYXkoKSxjLl91cGRhdGVQcm9taXNlcygpLGN9LHBsYXk6ZnVuY3Rpb24oYSl7cmV0dXJuIGEmJmEucmVtb3ZlKCksdGhpcy5fcGxheShhKX19O3ZhciBmPSExO2IucmVzdGFydFdlYkFuaW1hdGlvbnNOZXh0VGljaz1mdW5jdGlvbigpe2Z8fChmPSEwLHJlcXVlc3RBbmltYXRpb25GcmFtZShkKSl9O3ZhciBnPW5ldyBiLkFuaW1hdGlvblRpbWVsaW5lO2IudGltZWxpbmU9Zzt0cnl7T2JqZWN0LmRlZmluZVByb3BlcnR5KHdpbmRvdy5kb2N1bWVudCwidGltZWxpbmUiLHtjb25maWd1cmFibGU6ITAsZ2V0OmZ1bmN0aW9uKCl7cmV0dXJuIGd9fSl9Y2F0Y2goYSl7fXRyeXt3aW5kb3cuZG9jdW1lbnQudGltZWxpbmU9Z31jYXRjaChhKXt9fSgwLGMpLGZ1bmN0aW9uKGEsYixjKXtiLmFuaW1hdGlvbnNXaXRoUHJvbWlzZXM9W10sYi5BbmltYXRpb249ZnVuY3Rpb24oYixjKXtpZih0aGlzLmlkPSIiLGImJmIuX2lkJiYodGhpcy5pZD1iLl9pZCksdGhpcy5lZmZlY3Q9YixiJiYoYi5fYW5pbWF0aW9uPXRoaXMpLCFjKXRocm93IG5ldyBFcnJvcigiQW5pbWF0aW9uIHdpdGggbnVsbCB0aW1lbGluZSBpcyBub3Qgc3VwcG9ydGVkIik7dGhpcy5fdGltZWxpbmU9Yyx0aGlzLl9zZXF1ZW5jZU51bWJlcj1hLnNlcXVlbmNlTnVtYmVyKyssdGhpcy5faG9sZFRpbWU9MCx0aGlzLl9wYXVzZWQ9ITEsdGhpcy5faXNHcm91cD0hMSx0aGlzLl9hbmltYXRpb249bnVsbCx0aGlzLl9jaGlsZEFuaW1hdGlvbnM9W10sdGhpcy5fY2FsbGJhY2s9bnVsbCx0aGlzLl9vbGRQbGF5U3RhdGU9ImlkbGUiLHRoaXMuX3JlYnVpbGRVbmRlcmx5aW5nQW5pbWF0aW9uKCksdGhpcy5fYW5pbWF0aW9uLmNhbmNlbCgpLHRoaXMuX3VwZGF0ZVByb21pc2VzKCl9LGIuQW5pbWF0aW9uLnByb3RvdHlwZT17X3VwZGF0ZVByb21pc2VzOmZ1bmN0aW9uKCl7dmFyIGE9dGhpcy5fb2xkUGxheVN0YXRlLGI9dGhpcy5wbGF5U3RhdGU7cmV0dXJuIHRoaXMuX3JlYWR5UHJvbWlzZSYmYiE9PWEmJigiaWRsZSI9PWI/KHRoaXMuX3JlamVjdFJlYWR5UHJvbWlzZSgpLHRoaXMuX3JlYWR5UHJvbWlzZT12b2lkIDApOiJwZW5kaW5nIj09YT90aGlzLl9yZXNvbHZlUmVhZHlQcm9taXNlKCk6InBlbmRpbmciPT1iJiYodGhpcy5fcmVhZHlQcm9taXNlPXZvaWQgMCkpLHRoaXMuX2ZpbmlzaGVkUHJvbWlzZSYmYiE9PWEmJigiaWRsZSI9PWI/KHRoaXMuX3JlamVjdEZpbmlzaGVkUHJvbWlzZSgpLHRoaXMuX2ZpbmlzaGVkUHJvbWlzZT12b2lkIDApOiJmaW5pc2hlZCI9PWI/dGhpcy5fcmVzb2x2ZUZpbmlzaGVkUHJvbWlzZSgpOiJmaW5pc2hlZCI9PWEmJih0aGlzLl9maW5pc2hlZFByb21pc2U9dm9pZCAwKSksdGhpcy5fb2xkUGxheVN0YXRlPXRoaXMucGxheVN0YXRlLHRoaXMuX3JlYWR5UHJvbWlzZXx8dGhpcy5fZmluaXNoZWRQcm9taXNlfSxfcmVidWlsZFVuZGVybHlpbmdBbmltYXRpb246ZnVuY3Rpb24oKXt0aGlzLl91cGRhdGVQcm9taXNlcygpO3ZhciBhLGMsZCxlLGY9ISF0aGlzLl9hbmltYXRpb247ZiYmKGE9dGhpcy5wbGF5YmFja1JhdGUsYz10aGlzLl9wYXVzZWQsZD10aGlzLnN0YXJ0VGltZSxlPXRoaXMuY3VycmVudFRpbWUsdGhpcy5fYW5pbWF0aW9uLmNhbmNlbCgpLHRoaXMuX2FuaW1hdGlvbi5fd3JhcHBlcj1udWxsLHRoaXMuX2FuaW1hdGlvbj1udWxsKSwoIXRoaXMuZWZmZWN0fHx0aGlzLmVmZmVjdCBpbnN0YW5jZW9mIHdpbmRvdy5LZXlmcmFtZUVmZmVjdCkmJih0aGlzLl9hbmltYXRpb249Yi5uZXdVbmRlcmx5aW5nQW5pbWF0aW9uRm9yS2V5ZnJhbWVFZmZlY3QodGhpcy5lZmZlY3QpLGIuYmluZEFuaW1hdGlvbkZvcktleWZyYW1lRWZmZWN0KHRoaXMpKSwodGhpcy5lZmZlY3QgaW5zdGFuY2VvZiB3aW5kb3cuU2VxdWVuY2VFZmZlY3R8fHRoaXMuZWZmZWN0IGluc3RhbmNlb2Ygd2luZG93Lkdyb3VwRWZmZWN0KSYmKHRoaXMuX2FuaW1hdGlvbj1iLm5ld1VuZGVybHlpbmdBbmltYXRpb25Gb3JHcm91cCh0aGlzLmVmZmVjdCksYi5iaW5kQW5pbWF0aW9uRm9yR3JvdXAodGhpcykpLHRoaXMuZWZmZWN0JiZ0aGlzLmVmZmVjdC5fb25zYW1wbGUmJmIuYmluZEFuaW1hdGlvbkZvckN1c3RvbUVmZmVjdCh0aGlzKSxmJiYoMSE9YSYmKHRoaXMucGxheWJhY2tSYXRlPWEpLG51bGwhPT1kP3RoaXMuc3RhcnRUaW1lPWQ6bnVsbCE9PWU/dGhpcy5jdXJyZW50VGltZT1lOm51bGwhPT10aGlzLl9ob2xkVGltZSYmKHRoaXMuY3VycmVudFRpbWU9dGhpcy5faG9sZFRpbWUpLGMmJnRoaXMucGF1c2UoKSksdGhpcy5fdXBkYXRlUHJvbWlzZXMoKX0sX3VwZGF0ZUNoaWxkcmVuOmZ1bmN0aW9uKCl7aWYodGhpcy5lZmZlY3QmJiJpZGxlIiE9dGhpcy5wbGF5U3RhdGUpe3ZhciBhPXRoaXMuZWZmZWN0Ll90aW1pbmcuZGVsYXk7dGhpcy5fY2hpbGRBbmltYXRpb25zLmZvckVhY2goZnVuY3Rpb24oYyl7dGhpcy5fYXJyYW5nZUNoaWxkcmVuKGMsYSksdGhpcy5lZmZlY3QgaW5zdGFuY2VvZiB3aW5kb3cuU2VxdWVuY2VFZmZlY3QmJihhKz1iLmdyb3VwQ2hpbGREdXJhdGlvbihjLmVmZmVjdCkpfS5iaW5kKHRoaXMpKX19LF9zZXRFeHRlcm5hbEFuaW1hdGlvbjpmdW5jdGlvbihhKXtpZih0aGlzLmVmZmVjdCYmdGhpcy5faXNHcm91cClmb3IodmFyIGI9MDtiPHRoaXMuZWZmZWN0LmNoaWxkcmVuLmxlbmd0aDtiKyspdGhpcy5lZmZlY3QuY2hpbGRyZW5bYl0uX2FuaW1hdGlvbj1hLHRoaXMuX2NoaWxkQW5pbWF0aW9uc1tiXS5fc2V0RXh0ZXJuYWxBbmltYXRpb24oYSl9LF9jb25zdHJ1Y3RDaGlsZEFuaW1hdGlvbnM6ZnVuY3Rpb24oKXtpZih0aGlzLmVmZmVjdCYmdGhpcy5faXNHcm91cCl7dmFyIGE9dGhpcy5lZmZlY3QuX3RpbWluZy5kZWxheTt0aGlzLl9yZW1vdmVDaGlsZEFuaW1hdGlvbnMoKSx0aGlzLmVmZmVjdC5jaGlsZHJlbi5mb3JFYWNoKGZ1bmN0aW9uKGMpe3ZhciBkPWIudGltZWxpbmUuX3BsYXkoYyk7dGhpcy5fY2hpbGRBbmltYXRpb25zLnB1c2goZCksZC5wbGF5YmFja1JhdGU9dGhpcy5wbGF5YmFja1JhdGUsdGhpcy5fcGF1c2VkJiZkLnBhdXNlKCksYy5fYW5pbWF0aW9uPXRoaXMuZWZmZWN0Ll9hbmltYXRpb24sdGhpcy5fYXJyYW5nZUNoaWxkcmVuKGQsYSksdGhpcy5lZmZlY3QgaW5zdGFuY2VvZiB3aW5kb3cuU2VxdWVuY2VFZmZlY3QmJihhKz1iLmdyb3VwQ2hpbGREdXJhdGlvbihjKSl9LmJpbmQodGhpcykpfX0sX2FycmFuZ2VDaGlsZHJlbjpmdW5jdGlvbihhLGIpe251bGw9PT10aGlzLnN0YXJ0VGltZT9hLmN1cnJlbnRUaW1lPXRoaXMuY3VycmVudFRpbWUtYi90aGlzLnBsYXliYWNrUmF0ZTphLnN0YXJ0VGltZSE9PXRoaXMuc3RhcnRUaW1lK2IvdGhpcy5wbGF5YmFja1JhdGUmJihhLnN0YXJ0VGltZT10aGlzLnN0YXJ0VGltZStiL3RoaXMucGxheWJhY2tSYXRlKX0sZ2V0IHRpbWVsaW5lKCl7cmV0dXJuIHRoaXMuX3RpbWVsaW5lfSxnZXQgcGxheVN0YXRlKCl7cmV0dXJuIHRoaXMuX2FuaW1hdGlvbj90aGlzLl9hbmltYXRpb24ucGxheVN0YXRlOiJpZGxlIn0sZ2V0IGZpbmlzaGVkKCl7cmV0dXJuIHdpbmRvdy5Qcm9taXNlPyh0aGlzLl9maW5pc2hlZFByb21pc2V8fCgtMT09Yi5hbmltYXRpb25zV2l0aFByb21pc2VzLmluZGV4T2YodGhpcykmJmIuYW5pbWF0aW9uc1dpdGhQcm9taXNlcy5wdXNoKHRoaXMpLHRoaXMuX2ZpbmlzaGVkUHJvbWlzZT1uZXcgUHJvbWlzZShmdW5jdGlvbihhLGIpe3RoaXMuX3Jlc29sdmVGaW5pc2hlZFByb21pc2U9ZnVuY3Rpb24oKXthKHRoaXMpfSx0aGlzLl9yZWplY3RGaW5pc2hlZFByb21pc2U9ZnVuY3Rpb24oKXtiKHt0eXBlOkRPTUV4Y2VwdGlvbi5BQk9SVF9FUlIsbmFtZToiQWJvcnRFcnJvciJ9KX19LmJpbmQodGhpcykpLCJmaW5pc2hlZCI9PXRoaXMucGxheVN0YXRlJiZ0aGlzLl9yZXNvbHZlRmluaXNoZWRQcm9taXNlKCkpLHRoaXMuX2ZpbmlzaGVkUHJvbWlzZSk6KGNvbnNvbGUud2FybigiQW5pbWF0aW9uIFByb21pc2VzIHJlcXVpcmUgSmF2YVNjcmlwdCBQcm9taXNlIGNvbnN0cnVjdG9yIiksbnVsbCl9LGdldCByZWFkeSgpe3JldHVybiB3aW5kb3cuUHJvbWlzZT8odGhpcy5fcmVhZHlQcm9taXNlfHwoLTE9PWIuYW5pbWF0aW9uc1dpdGhQcm9taXNlcy5pbmRleE9mKHRoaXMpJiZiLmFuaW1hdGlvbnNXaXRoUHJvbWlzZXMucHVzaCh0aGlzKSx0aGlzLl9yZWFkeVByb21pc2U9bmV3IFByb21pc2UoZnVuY3Rpb24oYSxiKXt0aGlzLl9yZXNvbHZlUmVhZHlQcm9taXNlPWZ1bmN0aW9uKCl7YSh0aGlzKX0sdGhpcy5fcmVqZWN0UmVhZHlQcm9taXNlPWZ1bmN0aW9uKCl7Yih7dHlwZTpET01FeGNlcHRpb24uQUJPUlRfRVJSLG5hbWU6IkFib3J0RXJyb3IifSl9fS5iaW5kKHRoaXMpKSwicGVuZGluZyIhPT10aGlzLnBsYXlTdGF0ZSYmdGhpcy5fcmVzb2x2ZVJlYWR5UHJvbWlzZSgpKSx0aGlzLl9yZWFkeVByb21pc2UpOihjb25zb2xlLndhcm4oIkFuaW1hdGlvbiBQcm9taXNlcyByZXF1aXJlIEphdmFTY3JpcHQgUHJvbWlzZSBjb25zdHJ1Y3RvciIpLG51bGwpfSxnZXQgb25maW5pc2goKXtyZXR1cm4gdGhpcy5fYW5pbWF0aW9uLm9uZmluaXNofSxzZXQgb25maW5pc2goYSl7dGhpcy5fYW5pbWF0aW9uLm9uZmluaXNoPSJmdW5jdGlvbiI9PXR5cGVvZiBhP2Z1bmN0aW9uKGIpe2IudGFyZ2V0PXRoaXMsYS5jYWxsKHRoaXMsYil9LmJpbmQodGhpcyk6YX0sZ2V0IG9uY2FuY2VsKCl7cmV0dXJuIHRoaXMuX2FuaW1hdGlvbi5vbmNhbmNlbH0sc2V0IG9uY2FuY2VsKGEpe3RoaXMuX2FuaW1hdGlvbi5vbmNhbmNlbD0iZnVuY3Rpb24iPT10eXBlb2YgYT9mdW5jdGlvbihiKXtiLnRhcmdldD10aGlzLGEuY2FsbCh0aGlzLGIpfS5iaW5kKHRoaXMpOmF9LGdldCBjdXJyZW50VGltZSgpe3RoaXMuX3VwZGF0ZVByb21pc2VzKCk7dmFyIGE9dGhpcy5fYW5pbWF0aW9uLmN1cnJlbnRUaW1lO3JldHVybiB0aGlzLl91cGRhdGVQcm9taXNlcygpLGF9LHNldCBjdXJyZW50VGltZShhKXt0aGlzLl91cGRhdGVQcm9taXNlcygpLHRoaXMuX2FuaW1hdGlvbi5jdXJyZW50VGltZT1pc0Zpbml0ZShhKT9hOk1hdGguc2lnbihhKSpOdW1iZXIuTUFYX1ZBTFVFLHRoaXMuX3JlZ2lzdGVyKCksdGhpcy5fZm9yRWFjaENoaWxkKGZ1bmN0aW9uKGIsYyl7Yi5jdXJyZW50VGltZT1hLWN9KSx0aGlzLl91cGRhdGVQcm9taXNlcygpfSxnZXQgc3RhcnRUaW1lKCl7cmV0dXJuIHRoaXMuX2FuaW1hdGlvbi5zdGFydFRpbWV9LHNldCBzdGFydFRpbWUoYSl7dGhpcy5fdXBkYXRlUHJvbWlzZXMoKSx0aGlzLl9hbmltYXRpb24uc3RhcnRUaW1lPWlzRmluaXRlKGEpP2E6TWF0aC5zaWduKGEpKk51bWJlci5NQVhfVkFMVUUsdGhpcy5fcmVnaXN0ZXIoKSx0aGlzLl9mb3JFYWNoQ2hpbGQoZnVuY3Rpb24oYixjKXtiLnN0YXJ0VGltZT1hK2N9KSx0aGlzLl91cGRhdGVQcm9taXNlcygpfSxnZXQgcGxheWJhY2tSYXRlKCl7cmV0dXJuIHRoaXMuX2FuaW1hdGlvbi5wbGF5YmFja1JhdGV9LHNldCBwbGF5YmFja1JhdGUoYSl7dGhpcy5fdXBkYXRlUHJvbWlzZXMoKTt2YXIgYj10aGlzLmN1cnJlbnRUaW1lO3RoaXMuX2FuaW1hdGlvbi5wbGF5YmFja1JhdGU9YSx0aGlzLl9mb3JFYWNoQ2hpbGQoZnVuY3Rpb24oYil7Yi5wbGF5YmFja1JhdGU9YX0pLG51bGwhPT1iJiYodGhpcy5jdXJyZW50VGltZT1iKSx0aGlzLl91cGRhdGVQcm9taXNlcygpfSxwbGF5OmZ1bmN0aW9uKCl7dGhpcy5fdXBkYXRlUHJvbWlzZXMoKSx0aGlzLl9wYXVzZWQ9ITEsdGhpcy5fYW5pbWF0aW9uLnBsYXkoKSwtMT09dGhpcy5fdGltZWxpbmUuX2FuaW1hdGlvbnMuaW5kZXhPZih0aGlzKSYmdGhpcy5fdGltZWxpbmUuX2FuaW1hdGlvbnMucHVzaCh0aGlzKSx0aGlzLl9yZWdpc3RlcigpLGIuYXdhaXRTdGFydFRpbWUodGhpcyksdGhpcy5fZm9yRWFjaENoaWxkKGZ1bmN0aW9uKGEpe3ZhciBiPWEuY3VycmVudFRpbWU7YS5wbGF5KCksYS5jdXJyZW50VGltZT1ifSksdGhpcy5fdXBkYXRlUHJvbWlzZXMoKX0scGF1c2U6ZnVuY3Rpb24oKXt0aGlzLl91cGRhdGVQcm9taXNlcygpLHRoaXMuY3VycmVudFRpbWUmJih0aGlzLl9ob2xkVGltZT10aGlzLmN1cnJlbnRUaW1lKSx0aGlzLl9hbmltYXRpb24ucGF1c2UoKSx0aGlzLl9yZWdpc3RlcigpLHRoaXMuX2ZvckVhY2hDaGlsZChmdW5jdGlvbihhKXthLnBhdXNlKCl9KSx0aGlzLl9wYXVzZWQ9ITAsdGhpcy5fdXBkYXRlUHJvbWlzZXMoKX0sZmluaXNoOmZ1bmN0aW9uKCl7dGhpcy5fdXBkYXRlUHJvbWlzZXMoKSx0aGlzLl9hbmltYXRpb24uZmluaXNoKCksdGhpcy5fcmVnaXN0ZXIoKSx0aGlzLl91cGRhdGVQcm9taXNlcygpfSxjYW5jZWw6ZnVuY3Rpb24oKXt0aGlzLl91cGRhdGVQcm9taXNlcygpLHRoaXMuX2FuaW1hdGlvbi5jYW5jZWwoKSx0aGlzLl9yZWdpc3RlcigpLHRoaXMuX3JlbW92ZUNoaWxkQW5pbWF0aW9ucygpLHRoaXMuX3VwZGF0ZVByb21pc2VzKCl9LHJldmVyc2U6ZnVuY3Rpb24oKXt0aGlzLl91cGRhdGVQcm9taXNlcygpO3ZhciBhPXRoaXMuY3VycmVudFRpbWU7dGhpcy5fYW5pbWF0aW9uLnJldmVyc2UoKSx0aGlzLl9mb3JFYWNoQ2hpbGQoZnVuY3Rpb24oYSl7YS5yZXZlcnNlKCl9KSxudWxsIT09YSYmKHRoaXMuY3VycmVudFRpbWU9YSksdGhpcy5fdXBkYXRlUHJvbWlzZXMoKX0sYWRkRXZlbnRMaXN0ZW5lcjpmdW5jdGlvbihhLGIpe3ZhciBjPWI7ImZ1bmN0aW9uIj09dHlwZW9mIGImJihjPWZ1bmN0aW9uKGEpe2EudGFyZ2V0PXRoaXMsYi5jYWxsKHRoaXMsYSl9LmJpbmQodGhpcyksYi5fd3JhcHBlcj1jKSx0aGlzLl9hbmltYXRpb24uYWRkRXZlbnRMaXN0ZW5lcihhLGMpfSxyZW1vdmVFdmVudExpc3RlbmVyOmZ1bmN0aW9uKGEsYil7dGhpcy5fYW5pbWF0aW9uLnJlbW92ZUV2ZW50TGlzdGVuZXIoYSxiJiZiLl93cmFwcGVyfHxiKX0sX3JlbW92ZUNoaWxkQW5pbWF0aW9uczpmdW5jdGlvbigpe2Zvcig7dGhpcy5fY2hpbGRBbmltYXRpb25zLmxlbmd0aDspdGhpcy5fY2hpbGRBbmltYXRpb25zLnBvcCgpLmNhbmNlbCgpfSxfZm9yRWFjaENoaWxkOmZ1bmN0aW9uKGIpe3ZhciBjPTA7aWYodGhpcy5lZmZlY3QuY2hpbGRyZW4mJnRoaXMuX2NoaWxkQW5pbWF0aW9ucy5sZW5ndGg8dGhpcy5lZmZlY3QuY2hpbGRyZW4ubGVuZ3RoJiZ0aGlzLl9jb25zdHJ1Y3RDaGlsZEFuaW1hdGlvbnMoKSx0aGlzLl9jaGlsZEFuaW1hdGlvbnMuZm9yRWFjaChmdW5jdGlvbihhKXtiLmNhbGwodGhpcyxhLGMpLHRoaXMuZWZmZWN0IGluc3RhbmNlb2Ygd2luZG93LlNlcXVlbmNlRWZmZWN0JiYoYys9YS5lZmZlY3QuYWN0aXZlRHVyYXRpb24pfS5iaW5kKHRoaXMpKSwicGVuZGluZyIhPXRoaXMucGxheVN0YXRlKXt2YXIgZD10aGlzLmVmZmVjdC5fdGltaW5nLGU9dGhpcy5jdXJyZW50VGltZTtudWxsIT09ZSYmKGU9YS5jYWxjdWxhdGVJdGVyYXRpb25Qcm9ncmVzcyhhLmNhbGN1bGF0ZUFjdGl2ZUR1cmF0aW9uKGQpLGUsZCkpLChudWxsPT1lfHxpc05hTihlKSkmJnRoaXMuX3JlbW92ZUNoaWxkQW5pbWF0aW9ucygpfX19LHdpbmRvdy5BbmltYXRpb249Yi5BbmltYXRpb259KGEsYyksZnVuY3Rpb24oYSxiLGMpe2Z1bmN0aW9uIGQoYil7dGhpcy5fZnJhbWVzPWEubm9ybWFsaXplS2V5ZnJhbWVzKGIpfWZ1bmN0aW9uIGUoKXtmb3IodmFyIGE9ITE7aS5sZW5ndGg7KWkuc2hpZnQoKS5fdXBkYXRlQ2hpbGRyZW4oKSxhPSEwO3JldHVybiBhfXZhciBmPWZ1bmN0aW9uKGEpe2lmKGEuX2FuaW1hdGlvbj12b2lkIDAsYSBpbnN0YW5jZW9mIHdpbmRvdy5TZXF1ZW5jZUVmZmVjdHx8YSBpbnN0YW5jZW9mIHdpbmRvdy5Hcm91cEVmZmVjdClmb3IodmFyIGI9MDtiPGEuY2hpbGRyZW4ubGVuZ3RoO2IrKylmKGEuY2hpbGRyZW5bYl0pfTtiLnJlbW92ZU11bHRpPWZ1bmN0aW9uKGEpe2Zvcih2YXIgYj1bXSxjPTA7YzxhLmxlbmd0aDtjKyspe3ZhciBkPWFbY107ZC5fcGFyZW50PygtMT09Yi5pbmRleE9mKGQuX3BhcmVudCkmJmIucHVzaChkLl9wYXJlbnQpLGQuX3BhcmVudC5jaGlsZHJlbi5zcGxpY2UoZC5fcGFyZW50LmNoaWxkcmVuLmluZGV4T2YoZCksMSksZC5fcGFyZW50PW51bGwsZihkKSk6ZC5fYW5pbWF0aW9uJiZkLl9hbmltYXRpb24uZWZmZWN0PT1kJiYoZC5fYW5pbWF0aW9uLmNhbmNlbCgpLGQuX2FuaW1hdGlvbi5lZmZlY3Q9bmV3IEtleWZyYW1lRWZmZWN0KG51bGwsW10pLGQuX2FuaW1hdGlvbi5fY2FsbGJhY2smJihkLl9hbmltYXRpb24uX2NhbGxiYWNrLl9hbmltYXRpb249bnVsbCksZC5fYW5pbWF0aW9uLl9yZWJ1aWxkVW5kZXJseWluZ0FuaW1hdGlvbigpLGYoZCkpfWZvcihjPTA7YzxiLmxlbmd0aDtjKyspYltjXS5fcmVidWlsZCgpfSxiLktleWZyYW1lRWZmZWN0PWZ1bmN0aW9uKGIsYyxlLGYpe3JldHVybiB0aGlzLnRhcmdldD1iLHRoaXMuX3BhcmVudD1udWxsLGU9YS5udW1lcmljVGltaW5nVG9PYmplY3QoZSksdGhpcy5fdGltaW5nSW5wdXQ9YS5jbG9uZVRpbWluZ0lucHV0KGUpLHRoaXMuX3RpbWluZz1hLm5vcm1hbGl6ZVRpbWluZ0lucHV0KGUpLHRoaXMudGltaW5nPWEubWFrZVRpbWluZyhlLCExLHRoaXMpLHRoaXMudGltaW5nLl9lZmZlY3Q9dGhpcywiZnVuY3Rpb24iPT10eXBlb2YgYz8oYS5kZXByZWNhdGVkKCJDdXN0b20gS2V5ZnJhbWVFZmZlY3QiLCIyMDE1LTA2LTIyIiwiVXNlIEtleWZyYW1lRWZmZWN0Lm9uc2FtcGxlIGluc3RlYWQuIiksdGhpcy5fbm9ybWFsaXplZEtleWZyYW1lcz1jKTp0aGlzLl9ub3JtYWxpemVkS2V5ZnJhbWVzPW5ldyBkKGMpLHRoaXMuX2tleWZyYW1lcz1jLHRoaXMuYWN0aXZlRHVyYXRpb249YS5jYWxjdWxhdGVBY3RpdmVEdXJhdGlvbih0aGlzLl90aW1pbmcpLHRoaXMuX2lkPWYsdGhpc30sYi5LZXlmcmFtZUVmZmVjdC5wcm90b3R5cGU9e2dldEZyYW1lczpmdW5jdGlvbigpe3JldHVybiJmdW5jdGlvbiI9PXR5cGVvZiB0aGlzLl9ub3JtYWxpemVkS2V5ZnJhbWVzP3RoaXMuX25vcm1hbGl6ZWRLZXlmcmFtZXM6dGhpcy5fbm9ybWFsaXplZEtleWZyYW1lcy5fZnJhbWVzfSxzZXQgb25zYW1wbGUoYSl7aWYoImZ1bmN0aW9uIj09dHlwZW9mIHRoaXMuZ2V0RnJhbWVzKCkpdGhyb3cgbmV3IEVycm9yKCJTZXR0aW5nIG9uc2FtcGxlIG9uIGN1c3RvbSBlZmZlY3QgS2V5ZnJhbWVFZmZlY3QgaXMgbm90IHN1cHBvcnRlZC4iKTt0aGlzLl9vbnNhbXBsZT1hLHRoaXMuX2FuaW1hdGlvbiYmdGhpcy5fYW5pbWF0aW9uLl9yZWJ1aWxkVW5kZXJseWluZ0FuaW1hdGlvbigpfSxnZXQgcGFyZW50KCl7cmV0dXJuIHRoaXMuX3BhcmVudH0sY2xvbmU6ZnVuY3Rpb24oKXtpZigiZnVuY3Rpb24iPT10eXBlb2YgdGhpcy5nZXRGcmFtZXMoKSl0aHJvdyBuZXcgRXJyb3IoIkNsb25pbmcgY3VzdG9tIGVmZmVjdHMgaXMgbm90IHN1cHBvcnRlZC4iKTt2YXIgYj1uZXcgS2V5ZnJhbWVFZmZlY3QodGhpcy50YXJnZXQsW10sYS5jbG9uZVRpbWluZ0lucHV0KHRoaXMuX3RpbWluZ0lucHV0KSx0aGlzLl9pZCk7cmV0dXJuIGIuX25vcm1hbGl6ZWRLZXlmcmFtZXM9dGhpcy5fbm9ybWFsaXplZEtleWZyYW1lcyxiLl9rZXlmcmFtZXM9dGhpcy5fa2V5ZnJhbWVzLGJ9LHJlbW92ZTpmdW5jdGlvbigpe2IucmVtb3ZlTXVsdGkoW3RoaXNdKX19O3ZhciBnPUVsZW1lbnQucHJvdG90eXBlLmFuaW1hdGU7RWxlbWVudC5wcm90b3R5cGUuYW5pbWF0ZT1mdW5jdGlvbihhLGMpe3ZhciBkPSIiO3JldHVybiBjJiZjLmlkJiYoZD1jLmlkKSxiLnRpbWVsaW5lLl9wbGF5KG5ldyBiLktleWZyYW1lRWZmZWN0KHRoaXMsYSxjLGQpKX07dmFyIGg9ZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sIiwiZGl2Iik7Yi5uZXdVbmRlcmx5aW5nQW5pbWF0aW9uRm9yS2V5ZnJhbWVFZmZlY3Q9ZnVuY3Rpb24oYSl7aWYoYSl7dmFyIGI9YS50YXJnZXR8fGgsYz1hLl9rZXlmcmFtZXM7ImZ1bmN0aW9uIj09dHlwZW9mIGMmJihjPVtdKTt2YXIgZD1hLl90aW1pbmdJbnB1dDtkLmlkPWEuX2lkfWVsc2UgdmFyIGI9aCxjPVtdLGQ9MDtyZXR1cm4gZy5hcHBseShiLFtjLGRdKX0sYi5iaW5kQW5pbWF0aW9uRm9yS2V5ZnJhbWVFZmZlY3Q9ZnVuY3Rpb24oYSl7YS5lZmZlY3QmJiJmdW5jdGlvbiI9PXR5cGVvZiBhLmVmZmVjdC5fbm9ybWFsaXplZEtleWZyYW1lcyYmYi5iaW5kQW5pbWF0aW9uRm9yQ3VzdG9tRWZmZWN0KGEpfTt2YXIgaT1bXTtiLmF3YWl0U3RhcnRUaW1lPWZ1bmN0aW9uKGEpe251bGw9PT1hLnN0YXJ0VGltZSYmYS5faXNHcm91cCYmKDA9PWkubGVuZ3RoJiZyZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZSksaS5wdXNoKGEpKX07dmFyIGo9d2luZG93LmdldENvbXB1dGVkU3R5bGU7T2JqZWN0LmRlZmluZVByb3BlcnR5KHdpbmRvdywiZ2V0Q29tcHV0ZWRTdHlsZSIse2NvbmZpZ3VyYWJsZTohMCxlbnVtZXJhYmxlOiEwLHZhbHVlOmZ1bmN0aW9uKCl7Yi50aW1lbGluZS5fdXBkYXRlQW5pbWF0aW9uc1Byb21pc2VzKCk7dmFyIGE9ai5hcHBseSh0aGlzLGFyZ3VtZW50cyk7cmV0dXJuIGUoKSYmKGE9ai5hcHBseSh0aGlzLGFyZ3VtZW50cykpLGIudGltZWxpbmUuX3VwZGF0ZUFuaW1hdGlvbnNQcm9taXNlcygpLGF9fSksd2luZG93LktleWZyYW1lRWZmZWN0PWIuS2V5ZnJhbWVFZmZlY3Qsd2luZG93LkVsZW1lbnQucHJvdG90eXBlLmdldEFuaW1hdGlvbnM9ZnVuY3Rpb24oKXtyZXR1cm4gZG9jdW1lbnQudGltZWxpbmUuZ2V0QW5pbWF0aW9ucygpLmZpbHRlcihmdW5jdGlvbihhKXtyZXR1cm4gbnVsbCE9PWEuZWZmZWN0JiZhLmVmZmVjdC50YXJnZXQ9PXRoaXN9LmJpbmQodGhpcykpfX0oYSxjKSxmdW5jdGlvbihhLGIsYyl7ZnVuY3Rpb24gZChhKXthLl9yZWdpc3RlcmVkfHwoYS5fcmVnaXN0ZXJlZD0hMCxnLnB1c2goYSksaHx8KGg9ITAscmVxdWVzdEFuaW1hdGlvbkZyYW1lKGUpKSl9ZnVuY3Rpb24gZShhKXt2YXIgYj1nO2c9W10sYi5zb3J0KGZ1bmN0aW9uKGEsYil7cmV0dXJuIGEuX3NlcXVlbmNlTnVtYmVyLWIuX3NlcXVlbmNlTnVtYmVyfSksYj1iLmZpbHRlcihmdW5jdGlvbihhKXthKCk7dmFyIGI9YS5fYW5pbWF0aW9uP2EuX2FuaW1hdGlvbi5wbGF5U3RhdGU6ImlkbGUiO3JldHVybiJydW5uaW5nIiE9YiYmInBlbmRpbmciIT1iJiYoYS5fcmVnaXN0ZXJlZD0hMSksYS5fcmVnaXN0ZXJlZH0pLGcucHVzaC5hcHBseShnLGIpLGcubGVuZ3RoPyhoPSEwLHJlcXVlc3RBbmltYXRpb25GcmFtZShlKSk6aD0hMX12YXIgZj0oZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sIiwiZGl2IiksMCk7Yi5iaW5kQW5pbWF0aW9uRm9yQ3VzdG9tRWZmZWN0PWZ1bmN0aW9uKGIpe3ZhciBjLGU9Yi5lZmZlY3QudGFyZ2V0LGc9ImZ1bmN0aW9uIj09dHlwZW9mIGIuZWZmZWN0LmdldEZyYW1lcygpO2M9Zz9iLmVmZmVjdC5nZXRGcmFtZXMoKTpiLmVmZmVjdC5fb25zYW1wbGU7dmFyIGg9Yi5lZmZlY3QudGltaW5nLGk9bnVsbDtoPWEubm9ybWFsaXplVGltaW5nSW5wdXQoaCk7dmFyIGo9ZnVuY3Rpb24oKXt2YXIgZD1qLl9hbmltYXRpb24/ai5fYW5pbWF0aW9uLmN1cnJlbnRUaW1lOm51bGw7bnVsbCE9PWQmJihkPWEuY2FsY3VsYXRlSXRlcmF0aW9uUHJvZ3Jlc3MoYS5jYWxjdWxhdGVBY3RpdmVEdXJhdGlvbihoKSxkLGgpLGlzTmFOKGQpJiYoZD1udWxsKSksZCE9PWkmJihnP2MoZCxlLGIuZWZmZWN0KTpjKGQsYi5lZmZlY3QsYi5lZmZlY3QuX2FuaW1hdGlvbikpLGk9ZH07ai5fYW5pbWF0aW9uPWIsai5fcmVnaXN0ZXJlZD0hMSxqLl9zZXF1ZW5jZU51bWJlcj1mKyssYi5fY2FsbGJhY2s9aixkKGopfTt2YXIgZz1bXSxoPSExO2IuQW5pbWF0aW9uLnByb3RvdHlwZS5fcmVnaXN0ZXI9ZnVuY3Rpb24oKXt0aGlzLl9jYWxsYmFjayYmZCh0aGlzLl9jYWxsYmFjayl9fShhLGMpLGZ1bmN0aW9uKGEsYixjKXtmdW5jdGlvbiBkKGEpe3JldHVybiBhLl90aW1pbmcuZGVsYXkrYS5hY3RpdmVEdXJhdGlvbithLl90aW1pbmcuZW5kRGVsYXl9ZnVuY3Rpb24gZShiLGMsZCl7dGhpcy5faWQ9ZCx0aGlzLl9wYXJlbnQ9bnVsbCx0aGlzLmNoaWxkcmVuPWJ8fFtdLHRoaXMuX3JlcGFyZW50KHRoaXMuY2hpbGRyZW4pLGM9YS5udW1lcmljVGltaW5nVG9PYmplY3QoYyksdGhpcy5fdGltaW5nSW5wdXQ9YS5jbG9uZVRpbWluZ0lucHV0KGMpLHRoaXMuX3RpbWluZz1hLm5vcm1hbGl6ZVRpbWluZ0lucHV0KGMsITApLHRoaXMudGltaW5nPWEubWFrZVRpbWluZyhjLCEwLHRoaXMpLHRoaXMudGltaW5nLl9lZmZlY3Q9dGhpcywiYXV0byI9PT10aGlzLl90aW1pbmcuZHVyYXRpb24mJih0aGlzLl90aW1pbmcuZHVyYXRpb249dGhpcy5hY3RpdmVEdXJhdGlvbil9d2luZG93LlNlcXVlbmNlRWZmZWN0PWZ1bmN0aW9uKCl7ZS5hcHBseSh0aGlzLGFyZ3VtZW50cyl9LHdpbmRvdy5Hcm91cEVmZmVjdD1mdW5jdGlvbigpe2UuYXBwbHkodGhpcyxhcmd1bWVudHMpfSxlLnByb3RvdHlwZT17X2lzQW5jZXN0b3I6ZnVuY3Rpb24oYSl7Zm9yKHZhciBiPXRoaXM7bnVsbCE9PWI7KXtpZihiPT1hKXJldHVybiEwO2I9Yi5fcGFyZW50fXJldHVybiExfSxfcmVidWlsZDpmdW5jdGlvbigpe2Zvcih2YXIgYT10aGlzO2E7KSJhdXRvIj09PWEudGltaW5nLmR1cmF0aW9uJiYoYS5fdGltaW5nLmR1cmF0aW9uPWEuYWN0aXZlRHVyYXRpb24pLGE9YS5fcGFyZW50O3RoaXMuX2FuaW1hdGlvbiYmdGhpcy5fYW5pbWF0aW9uLl9yZWJ1aWxkVW5kZXJseWluZ0FuaW1hdGlvbigpfSxfcmVwYXJlbnQ6ZnVuY3Rpb24oYSl7Yi5yZW1vdmVNdWx0aShhKTtmb3IodmFyIGM9MDtjPGEubGVuZ3RoO2MrKylhW2NdLl9wYXJlbnQ9dGhpc30sX3B1dENoaWxkOmZ1bmN0aW9uKGEsYil7Zm9yKHZhciBjPWI/IkNhbm5vdCBhcHBlbmQgYW4gYW5jZXN0b3Igb3Igc2VsZiI6IkNhbm5vdCBwcmVwZW5kIGFuIGFuY2VzdG9yIG9yIHNlbGYiLGQ9MDtkPGEubGVuZ3RoO2QrKylpZih0aGlzLl9pc0FuY2VzdG9yKGFbZF0pKXRocm93e3R5cGU6RE9NRXhjZXB0aW9uLkhJRVJBUkNIWV9SRVFVRVNUX0VSUixuYW1lOiJIaWVyYXJjaHlSZXF1ZXN0RXJyb3IiLG1lc3NhZ2U6Y307Zm9yKHZhciBkPTA7ZDxhLmxlbmd0aDtkKyspYj90aGlzLmNoaWxkcmVuLnB1c2goYVtkXSk6dGhpcy5jaGlsZHJlbi51bnNoaWZ0KGFbZF0pO3RoaXMuX3JlcGFyZW50KGEpLHRoaXMuX3JlYnVpbGQoKX0sYXBwZW5kOmZ1bmN0aW9uKCl7dGhpcy5fcHV0Q2hpbGQoYXJndW1lbnRzLCEwKX0scHJlcGVuZDpmdW5jdGlvbigpe3RoaXMuX3B1dENoaWxkKGFyZ3VtZW50cywhMSl9LGdldCBwYXJlbnQoKXtyZXR1cm4gdGhpcy5fcGFyZW50fSxnZXQgZmlyc3RDaGlsZCgpe3JldHVybiB0aGlzLmNoaWxkcmVuLmxlbmd0aD90aGlzLmNoaWxkcmVuWzBdOm51bGx9LGdldCBsYXN0Q2hpbGQoKXtyZXR1cm4gdGhpcy5jaGlsZHJlbi5sZW5ndGg/dGhpcy5jaGlsZHJlblt0aGlzLmNoaWxkcmVuLmxlbmd0aC0xXTpudWxsfSxjbG9uZTpmdW5jdGlvbigpe2Zvcih2YXIgYj1hLmNsb25lVGltaW5nSW5wdXQodGhpcy5fdGltaW5nSW5wdXQpLGM9W10sZD0wO2Q8dGhpcy5jaGlsZHJlbi5sZW5ndGg7ZCsrKWMucHVzaCh0aGlzLmNoaWxkcmVuW2RdLmNsb25lKCkpO3JldHVybiB0aGlzIGluc3RhbmNlb2YgR3JvdXBFZmZlY3Q/bmV3IEdyb3VwRWZmZWN0KGMsYik6bmV3IFNlcXVlbmNlRWZmZWN0KGMsYil9LHJlbW92ZTpmdW5jdGlvbigpe2IucmVtb3ZlTXVsdGkoW3RoaXNdKX19LHdpbmRvdy5TZXF1ZW5jZUVmZmVjdC5wcm90b3R5cGU9T2JqZWN0LmNyZWF0ZShlLnByb3RvdHlwZSksT2JqZWN0LmRlZmluZVByb3BlcnR5KHdpbmRvdy5TZXF1ZW5jZUVmZmVjdC5wcm90b3R5cGUsImFjdGl2ZUR1cmF0aW9uIix7Z2V0OmZ1bmN0aW9uKCl7dmFyIGE9MDtyZXR1cm4gdGhpcy5jaGlsZHJlbi5mb3JFYWNoKGZ1bmN0aW9uKGIpe2ErPWQoYil9KSxNYXRoLm1heChhLDApfX0pLHdpbmRvdy5Hcm91cEVmZmVjdC5wcm90b3R5cGU9T2JqZWN0LmNyZWF0ZShlLnByb3RvdHlwZSksT2JqZWN0LmRlZmluZVByb3BlcnR5KHdpbmRvdy5Hcm91cEVmZmVjdC5wcm90b3R5cGUsImFjdGl2ZUR1cmF0aW9uIix7Z2V0OmZ1bmN0aW9uKCl7dmFyIGE9MDtyZXR1cm4gdGhpcy5jaGlsZHJlbi5mb3JFYWNoKGZ1bmN0aW9uKGIpe2E9TWF0aC5tYXgoYSxkKGIpKX0pLGF9fSksYi5uZXdVbmRlcmx5aW5nQW5pbWF0aW9uRm9yR3JvdXA9ZnVuY3Rpb24oYyl7dmFyIGQsZT1udWxsLGY9ZnVuY3Rpb24oYil7dmFyIGM9ZC5fd3JhcHBlcjtpZihjJiYicGVuZGluZyIhPWMucGxheVN0YXRlJiZjLmVmZmVjdClyZXR1cm4gbnVsbD09Yj92b2lkIGMuX3JlbW92ZUNoaWxkQW5pbWF0aW9ucygpOjA9PWImJmMucGxheWJhY2tSYXRlPDAmJihlfHwoZT1hLm5vcm1hbGl6ZVRpbWluZ0lucHV0KGMuZWZmZWN0LnRpbWluZykpLGI9YS5jYWxjdWxhdGVJdGVyYXRpb25Qcm9ncmVzcyhhLmNhbGN1bGF0ZUFjdGl2ZUR1cmF0aW9uKGUpLC0xLGUpLGlzTmFOKGIpfHxudWxsPT1iKT8oYy5fZm9yRWFjaENoaWxkKGZ1bmN0aW9uKGEpe2EuY3VycmVudFRpbWU9LTF9KSx2b2lkIGMuX3JlbW92ZUNoaWxkQW5pbWF0aW9ucygpKTp2b2lkIDB9LGc9bmV3IEtleWZyYW1lRWZmZWN0KG51bGwsW10sYy5fdGltaW5nLGMuX2lkKTtyZXR1cm4gZy5vbnNhbXBsZT1mLGQ9Yi50aW1lbGluZS5fcGxheShnKX0sYi5iaW5kQW5pbWF0aW9uRm9yR3JvdXA9ZnVuY3Rpb24oYSl7YS5fYW5pbWF0aW9uLl93cmFwcGVyPWEsYS5faXNHcm91cD0hMCxiLmF3YWl0U3RhcnRUaW1lKGEpLGEuX2NvbnN0cnVjdENoaWxkQW5pbWF0aW9ucygpLGEuX3NldEV4dGVybmFsQW5pbWF0aW9uKGEpfSxiLmdyb3VwQ2hpbGREdXJhdGlvbj1kfShhLGMpfSgpOwoKKGZ1bmN0aW9uICgpIHsKCiAgICAvKiEgKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioNCiAgICBDb3B5cmlnaHQgKGMpIE1pY3Jvc29mdCBDb3Jwb3JhdGlvbi4NCg0KICAgIFBlcm1pc3Npb24gdG8gdXNlLCBjb3B5LCBtb2RpZnksIGFuZC9vciBkaXN0cmlidXRlIHRoaXMgc29mdHdhcmUgZm9yIGFueQ0KICAgIHB1cnBvc2Ugd2l0aCBvciB3aXRob3V0IGZlZSBpcyBoZXJlYnkgZ3JhbnRlZC4NCg0KICAgIFRIRSBTT0ZUV0FSRSBJUyBQUk9WSURFRCAiQVMgSVMiIEFORCBUSEUgQVVUSE9SIERJU0NMQUlNUyBBTEwgV0FSUkFOVElFUyBXSVRIDQogICAgUkVHQVJEIFRPIFRISVMgU09GVFdBUkUgSU5DTFVESU5HIEFMTCBJTVBMSUVEIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZDQogICAgQU5EIEZJVE5FU1MuIElOIE5PIEVWRU5UIFNIQUxMIFRIRSBBVVRIT1IgQkUgTElBQkxFIEZPUiBBTlkgU1BFQ0lBTCwgRElSRUNULA0KICAgIElORElSRUNULCBPUiBDT05TRVFVRU5USUFMIERBTUFHRVMgT1IgQU5ZIERBTUFHRVMgV0hBVFNPRVZFUiBSRVNVTFRJTkcgRlJPTQ0KICAgIExPU1MgT0YgVVNFLCBEQVRBIE9SIFBST0ZJVFMsIFdIRVRIRVIgSU4gQU4gQUNUSU9OIE9GIENPTlRSQUNULCBORUdMSUdFTkNFIE9SDQogICAgT1RIRVIgVE9SVElPVVMgQUNUSU9OLCBBUklTSU5HIE9VVCBPRiBPUiBJTiBDT05ORUNUSU9OIFdJVEggVEhFIFVTRSBPUg0KICAgIFBFUkZPUk1BTkNFIE9GIFRISVMgU09GVFdBUkUuDQogICAgKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiogKi8NCg0KICAgIGZ1bmN0aW9uIF9fZGVjb3JhdGUoZGVjb3JhdG9ycywgdGFyZ2V0LCBrZXksIGRlc2MpIHsNCiAgICAgICAgdmFyIGMgPSBhcmd1bWVudHMubGVuZ3RoLCByID0gYyA8IDMgPyB0YXJnZXQgOiBkZXNjID09PSBudWxsID8gZGVzYyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3IodGFyZ2V0LCBrZXkpIDogZGVzYywgZDsNCiAgICAgICAgaWYgKHR5cGVvZiBSZWZsZWN0ID09PSAib2JqZWN0IiAmJiB0eXBlb2YgUmVmbGVjdC5kZWNvcmF0ZSA9PT0gImZ1bmN0aW9uIikgciA9IFJlZmxlY3QuZGVjb3JhdGUoZGVjb3JhdG9ycywgdGFyZ2V0LCBrZXksIGRlc2MpOw0KICAgICAgICBlbHNlIGZvciAodmFyIGkgPSBkZWNvcmF0b3JzLmxlbmd0aCAtIDE7IGkgPj0gMDsgaS0tKSBpZiAoZCA9IGRlY29yYXRvcnNbaV0pIHIgPSAoYyA8IDMgPyBkKHIpIDogYyA+IDMgPyBkKHRhcmdldCwga2V5LCByKSA6IGQodGFyZ2V0LCBrZXkpKSB8fCByOw0KICAgICAgICByZXR1cm4gYyA+IDMgJiYgciAmJiBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBrZXksIHIpLCByOw0KICAgIH0NCg0KICAgIGZ1bmN0aW9uIF9fbWV0YWRhdGEobWV0YWRhdGFLZXksIG1ldGFkYXRhVmFsdWUpIHsNCiAgICAgICAgaWYgKHR5cGVvZiBSZWZsZWN0ID09PSAib2JqZWN0IiAmJiB0eXBlb2YgUmVmbGVjdC5tZXRhZGF0YSA9PT0gImZ1bmN0aW9uIikgcmV0dXJuIFJlZmxlY3QubWV0YWRhdGEobWV0YWRhdGFLZXksIG1ldGFkYXRhVmFsdWUpOw0KICAgIH0NCg0KICAgIGZ1bmN0aW9uIF9fYXdhaXRlcih0aGlzQXJnLCBfYXJndW1lbnRzLCBQLCBnZW5lcmF0b3IpIHsNCiAgICAgICAgZnVuY3Rpb24gYWRvcHQodmFsdWUpIHsgcmV0dXJuIHZhbHVlIGluc3RhbmNlb2YgUCA/IHZhbHVlIDogbmV3IFAoZnVuY3Rpb24gKHJlc29sdmUpIHsgcmVzb2x2ZSh2YWx1ZSk7IH0pOyB9DQogICAgICAgIHJldHVybiBuZXcgKFAgfHwgKFAgPSBQcm9taXNlKSkoZnVuY3Rpb24gKHJlc29sdmUsIHJlamVjdCkgew0KICAgICAgICAgICAgZnVuY3Rpb24gZnVsZmlsbGVkKHZhbHVlKSB7IHRyeSB7IHN0ZXAoZ2VuZXJhdG9yLm5leHQodmFsdWUpKTsgfSBjYXRjaCAoZSkgeyByZWplY3QoZSk7IH0gfQ0KICAgICAgICAgICAgZnVuY3Rpb24gcmVqZWN0ZWQodmFsdWUpIHsgdHJ5IHsgc3RlcChnZW5lcmF0b3JbInRocm93Il0odmFsdWUpKTsgfSBjYXRjaCAoZSkgeyByZWplY3QoZSk7IH0gfQ0KICAgICAgICAgICAgZnVuY3Rpb24gc3RlcChyZXN1bHQpIHsgcmVzdWx0LmRvbmUgPyByZXNvbHZlKHJlc3VsdC52YWx1ZSkgOiBhZG9wdChyZXN1bHQudmFsdWUpLnRoZW4oZnVsZmlsbGVkLCByZWplY3RlZCk7IH0NCiAgICAgICAgICAgIHN0ZXAoKGdlbmVyYXRvciA9IGdlbmVyYXRvci5hcHBseSh0aGlzQXJnLCBfYXJndW1lbnRzIHx8IFtdKSkubmV4dCgpKTsNCiAgICAgICAgfSk7DQogICAgfQoKICAgIC8qKgogICAgICogQGxpY2Vuc2UKICAgICAqIENvcHlyaWdodCAoYykgMjAxNiBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgICAqIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kCiAgICAgKiBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5CiAgICAgKiBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5CiAgICAgKiBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQCiAgICAgKiByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAgKi8KICAgIC8qKgogICAgICogQSBUeXBlU2NyaXB0IGNsYXNzIGRlY29yYXRvciBmYWN0b3J5IHRoYXQgcmVnaXN0ZXJzIHRoZSBjbGFzcyBhcyBhIGN1c3RvbQogICAgICogZWxlbWVudC4KICAgICAqCiAgICAgKiBJZiBgdGFnbmFtZWAgaXMgcHJvdmlkZWQsIGl0IHdpbGwgYmUgdXNlZCBhcyB0aGUgY3VzdG9tIGVsZW1lbnQgbmFtZSwgYW5kCiAgICAgKiB3aWxsIGJlIGFzc2lnbmVkIHRvIHRoZSBjbGFzcyBzdGF0aWMgYGlzYCBwcm9wZXJ0eS4gSWYgYHRhZ25hbWVgIGlzIG9taXR0ZWQsCiAgICAgKiB0aGUgc3RhdGljIGBpc2AgcHJvcGVydHkgb2YgdGhlIGNsYXNzIHdpbGwgYmUgdXNlZCBpbnN0ZWFkLiBJZiBuZWl0aGVyIGV4aXN0LAogICAgICogb3IgaWYgYm90aCBleGlzdCBidXQgaGF2ZSBkaWZmZXJlbnQgdmFsdWVzIChleGNlcHQgaW4gdGhlIGNhc2UgdGhhdCB0aGUgYGlzYAogICAgICogcHJvcGVydHkgaXMgbm90IGFuIG93bi1wcm9wZXJ0eSBvZiB0aGUgY2xhc3MpLCBhbiBleGNlcHRpb24gaXMgdGhyb3duLgogICAgICovCiAgICBmdW5jdGlvbiBjdXN0b21FbGVtZW50KHRhZ25hbWUpIHsKICAgICAgICByZXR1cm4gKGNsYXNzXykgPT4gewogICAgICAgICAgICBpZiAodGFnbmFtZSkgewogICAgICAgICAgICAgICAgLy8gT25seSBjaGVjayB0aGF0IHRhZyBuYW1lcyBtYXRjaCB3aGVuIGBpc2AgaXMgb3VyIG93biBwcm9wZXJ0eS4gSXQgbWlnaHQKICAgICAgICAgICAgICAgIC8vIGJlIGluaGVyaXRlZCBmcm9tIGEgc3VwZXJjbGFzcywgaW4gd2hpY2ggY2FzZSBpdCdzIG9rIGlmIHRoZXkncmUKICAgICAgICAgICAgICAgIC8vIGRpZmZlcmVudCwgYW5kIHdlJ2xsIG92ZXJyaWRlIGl0IHdpdGggb3VyIG93biBwcm9wZXJ0eSBiZWxvdy4KICAgICAgICAgICAgICAgIGlmIChjbGFzc18uaGFzT3duUHJvcGVydHkoJ2lzJykpIHsKICAgICAgICAgICAgICAgICAgICBpZiAodGFnbmFtZSAhPT0gY2xhc3NfLmlzKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgY3VzdG9tIGVsZW1lbnQgdGFnIG5hbWVzIGRvIG5vdCBtYXRjaDogYCArCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBgKCR7dGFnbmFtZX0gIT09ICR7Y2xhc3NfLmlzfSlgKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoY2xhc3NfLCAnaXMnLCB7IHZhbHVlOiB0YWduYW1lIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFRocm93cyBpZiB0YWcgbmFtZSBpcyBtaXNzaW5nIG9yIGludmFsaWQuCiAgICAgICAgICAgIHdpbmRvdy5jdXN0b21FbGVtZW50cy5kZWZpbmUoY2xhc3NfLmlzLCBjbGFzc18pOwogICAgICAgIH07CiAgICB9CiAgICBmdW5jdGlvbiBjcmVhdGVQcm9wZXJ0eShwcm90bywgbmFtZSwgb3B0aW9ucykgewogICAgICAgIGlmICghcHJvdG8uY29uc3RydWN0b3IuaGFzT3duUHJvcGVydHkoJ3Byb3BlcnRpZXMnKSkgewogICAgICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkocHJvdG8uY29uc3RydWN0b3IsICdwcm9wZXJ0aWVzJywgeyB2YWx1ZToge30gfSk7CiAgICAgICAgfQogICAgICAgIHByb3RvLmNvbnN0cnVjdG9yLnByb3BlcnRpZXNbbmFtZV0gPSBPYmplY3QuYXNzaWduKHt9LCBwcm90by5jb25zdHJ1Y3Rvci5wcm9wZXJ0aWVzW25hbWVdLCBvcHRpb25zKTsKICAgIH0KICAgIC8qKgogICAgICogQSBUeXBlU2NyaXB0IHByb3BlcnR5IGRlY29yYXRvciBmYWN0b3J5IHRoYXQgZGVmaW5lcyB0aGlzIGFzIGEgUG9seW1lcgogICAgICogcHJvcGVydHkuCiAgICAgKgogICAgICogVGhpcyBmdW5jdGlvbiBtdXN0IGJlIGludm9rZWQgdG8gcmV0dXJuIGEgZGVjb3JhdG9yLgogICAgICoKICAgICAqIEBFeHBvcnREZWNvcmF0ZWRJdGVtcwogICAgICovCiAgICBmdW5jdGlvbiBwcm9wZXJ0eShvcHRpb25zKSB7CiAgICAgICAgcmV0dXJuIChwcm90bywgcHJvcE5hbWUpID0+IHsKICAgICAgICAgICAgY3JlYXRlUHJvcGVydHkocHJvdG8sIHByb3BOYW1lLCBvcHRpb25zKTsKICAgICAgICB9OwogICAgfQogICAgLyoqCiAgICAgKiBBIFR5cGVTY3JpcHQgcHJvcGVydHkgZGVjb3JhdG9yIGZhY3RvcnkgdGhhdCBjYXVzZXMgdGhlIGRlY29yYXRlZCBtZXRob2QgdG8KICAgICAqIGJlIGNhbGxlZCB3aGVuIGEgcHJvcGVydHkgY2hhbmdlcy4KICAgICAqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIG11c3QgYmUgaW52b2tlZCB0byByZXR1cm4gYSBkZWNvcmF0b3IuCiAgICAgKgogICAgICogQEV4cG9ydERlY29yYXRlZEl0ZW1zCiAgICAgKi8KICAgIGZ1bmN0aW9uIG9ic2VydmUoLi4udGFyZ2V0cykgewogICAgICAgIHJldHVybiAocHJvdG8sIHByb3BOYW1lKSA9PiB7CiAgICAgICAgICAgIGlmICghcHJvdG8uY29uc3RydWN0b3IuaGFzT3duUHJvcGVydHkoJ29ic2VydmVycycpKSB7CiAgICAgICAgICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkocHJvdG8uY29uc3RydWN0b3IsICdvYnNlcnZlcnMnLCB7IHZhbHVlOiBbXSB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBwcm90by5jb25zdHJ1Y3Rvci5vYnNlcnZlcnMucHVzaChgJHtwcm9wTmFtZX0oJHt0YXJnZXRzLmpvaW4oJywnKX0pYCk7CiAgICAgICAgfTsKICAgIH0KICAgIC8qKgogICAgICogQSBUeXBlU2NyaXB0IGFjY2Vzc29yIGRlY29yYXRvciBmYWN0b3J5IHRoYXQgY2F1c2VzIHRoZSBkZWNvcmF0ZWQgZ2V0dGVyIHRvCiAgICAgKiBiZSBjYWxsZWQgd2hlbiBhIHNldCBvZiBkZXBlbmRlbmNpZXMgY2hhbmdlLiBUaGUgYXJndW1lbnRzIG9mIHRoaXMgZGVjb3JhdG9yCiAgICAgKiBzaG91bGQgYmUgcGF0aHMgb2YgdGhlIGRhdGEgZGVwZW5kZW5jaWVzIGFzIGRlc2NyaWJlZAogICAgICogW2hlcmVdKGh0dHBzOi8vd3d3LnBvbHltZXItcHJvamVjdC5vcmcvMi4wL2RvY3MvZGV2Z3VpZGUvb2JzZXJ2ZXJzI2RlZmluZS1hLWNvbXB1dGVkLXByb3BlcnR5KQogICAgICogVGhlIGRlY29yYXRlZCBnZXR0ZXIgc2hvdWxkIG5vdCBoYXZlIGFuIGFzc29jaWF0ZWQgc2V0dGVyLgogICAgICoKICAgICAqIFRoaXMgZnVuY3Rpb24gbXVzdCBiZSBpbnZva2VkIHRvIHJldHVybiBhIGRlY29yYXRvci4KICAgICAqCiAgICAgKiBARXhwb3J0RGVjb3JhdGVkSXRlbXMKICAgICAqLwogICAgZnVuY3Rpb24gY29tcHV0ZWQoZmlyc3RUYXJnZXQsIC4uLm1vcmVUYXJnZXRzKSB7CiAgICAgICAgcmV0dXJuIChwcm90bywgcHJvcE5hbWUsIGRlc2NyaXB0b3IpID0+IHsKICAgICAgICAgICAgY29uc3QgZm5OYW1lID0gYF9fY29tcHV0ZSR7cHJvcE5hbWV9YDsKICAgICAgICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHByb3RvLCBmbk5hbWUsIHsgdmFsdWU6IGRlc2NyaXB0b3IuZ2V0IH0pOwogICAgICAgICAgICBkZXNjcmlwdG9yLmdldCA9IHVuZGVmaW5lZDsKICAgICAgICAgICAgY29uc3QgdGFyZ2V0cyA9IFtmaXJzdFRhcmdldCwgLi4ubW9yZVRhcmdldHNdLmpvaW4oJywnKTsKICAgICAgICAgICAgY3JlYXRlUHJvcGVydHkocHJvdG8sIHByb3BOYW1lLCB7IGNvbXB1dGVkOiBgJHtmbk5hbWV9KCR7dGFyZ2V0c30pYCB9KTsKICAgICAgICB9OwogICAgfQoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyogZXNsaW50LWRpc2FibGUgbm8tdW51c2VkLXZhcnMgKi8KICAgIC8qKgogICAgICogV2hlbiB1c2luZyBDbG9zdXJlIENvbXBpbGVyLCBKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KHByb3BlcnR5LCBvYmplY3QpIGlzIHJlcGxhY2VkIGJ5IHRoZSBtdW5nZWQgbmFtZSBmb3Igb2JqZWN0W3Byb3BlcnR5XQogICAgICogV2UgY2Fubm90IGFsaWFzIHRoaXMgZnVuY3Rpb24sIHNvIHdlIGhhdmUgdG8gdXNlIGEgc21hbGwgc2hpbSB0aGF0IGhhcyB0aGUgc2FtZSBiZWhhdmlvciB3aGVuIG5vdCBjb21waWxpbmcuCiAgICAgKgogICAgICogQHBhcmFtIHs/fSBwcm9wIFByb3BlcnR5IG5hbWUKICAgICAqIEBwYXJhbSB7Kn0gb2JqIFJlZmVyZW5jZSBvYmplY3QKICAgICAqIEByZXR1cm4ge3N0cmluZ30gUG90ZW50aWFsbHkgcmVuYW1lZCBwcm9wZXJ0eSBuYW1lCiAgICAgKi8KICAgIHdpbmRvdy5KU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5ID0gZnVuY3Rpb24ocHJvcCwgb2JqKSB7CiAgICAgIHJldHVybiBwcm9wOwogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGxldCBDU1NfVVJMX1JYID0gLyh1cmxcKCkoW14pXSopKFwpKS9nOwogICAgbGV0IEFCU19VUkwgPSAvKF5cL1teXC9dKXwoXiMpfCheW1x3LVxkXSo6KS87CiAgICBsZXQgd29ya2luZ1VSTDsKICAgIGxldCByZXNvbHZlRG9jOwogICAgLyoqCiAgICAgKiBSZXNvbHZlcyB0aGUgZ2l2ZW4gVVJMIGFnYWluc3QgdGhlIHByb3ZpZGVkIGBiYXNlVXJpJy4KICAgICAqCiAgICAgKiBOb3RlIHRoYXQgdGhpcyBmdW5jdGlvbiBwZXJmb3JtcyBubyByZXNvbHV0aW9uIGZvciBVUkxzIHRoYXQgc3RhcnQKICAgICAqIHdpdGggYC9gIChhYnNvbHV0ZSBVUkxzKSBvciBgI2AgKGhhc2ggaWRlbnRpZmllcnMpLiAgRm9yIGdlbmVyYWwgcHVycG9zZQogICAgICogVVJMIHJlc29sdXRpb24sIHVzZSBgd2luZG93LlVSTGAuCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmd9IHVybCBJbnB1dCBVUkwgdG8gcmVzb2x2ZQogICAgICogQHBhcmFtIHs/c3RyaW5nPX0gYmFzZVVSSSBCYXNlIFVSSSB0byByZXNvbHZlIHRoZSBVUkwgYWdhaW5zdAogICAgICogQHJldHVybiB7c3RyaW5nfSByZXNvbHZlZCBVUkwKICAgICAqLwogICAgZnVuY3Rpb24gcmVzb2x2ZVVybCh1cmwsIGJhc2VVUkkpIHsKICAgICAgaWYgKHVybCAmJiBBQlNfVVJMLnRlc3QodXJsKSkgewogICAgICAgIHJldHVybiB1cmw7CiAgICAgIH0KICAgICAgaWYgKHVybCA9PT0gJy8vJykgewogICAgICAgIHJldHVybiB1cmw7CiAgICAgIH0KICAgICAgLy8gTGF6eSBmZWF0dXJlIGRldGVjdGlvbi4KICAgICAgaWYgKHdvcmtpbmdVUkwgPT09IHVuZGVmaW5lZCkgewogICAgICAgIHdvcmtpbmdVUkwgPSBmYWxzZTsKICAgICAgICB0cnkgewogICAgICAgICAgY29uc3QgdSA9IG5ldyBVUkwoJ2InLCAnaHR0cDovL2EnKTsKICAgICAgICAgIHUucGF0aG5hbWUgPSAnYyUyMGQnOwogICAgICAgICAgd29ya2luZ1VSTCA9ICh1LmhyZWYgPT09ICdodHRwOi8vYS9jJTIwZCcpOwogICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgIC8vIHNpbGVudGx5IGZhaWwKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKCFiYXNlVVJJKSB7CiAgICAgICAgYmFzZVVSSSA9IGRvY3VtZW50LmJhc2VVUkkgfHwgd2luZG93LmxvY2F0aW9uLmhyZWY7CiAgICAgIH0KICAgICAgaWYgKHdvcmtpbmdVUkwpIHsKICAgICAgICB0cnkgewogICAgICAgICAgcmV0dXJuIChuZXcgVVJMKHVybCwgYmFzZVVSSSkpLmhyZWY7CiAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgLy8gQmFkIHVybCBvciBiYXNlVVJJIHN0cnVjdHVyZS4gRG8gbm90IGF0dGVtcHQgdG8gcmVzb2x2ZS4KICAgICAgICAgIHJldHVybiB1cmw7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8vIEZhbGxiYWNrIHRvIGNyZWF0aW5nIGFuIGFuY2hvciBpbnRvIGEgZGlzY29ubmVjdGVkIGRvY3VtZW50LgogICAgICBpZiAoIXJlc29sdmVEb2MpIHsKICAgICAgICByZXNvbHZlRG9jID0gZG9jdW1lbnQuaW1wbGVtZW50YXRpb24uY3JlYXRlSFRNTERvY3VtZW50KCd0ZW1wJyk7CiAgICAgICAgcmVzb2x2ZURvYy5iYXNlID0gcmVzb2x2ZURvYy5jcmVhdGVFbGVtZW50KCdiYXNlJyk7CiAgICAgICAgcmVzb2x2ZURvYy5oZWFkLmFwcGVuZENoaWxkKHJlc29sdmVEb2MuYmFzZSk7CiAgICAgICAgcmVzb2x2ZURvYy5hbmNob3IgPSByZXNvbHZlRG9jLmNyZWF0ZUVsZW1lbnQoJ2EnKTsKICAgICAgICByZXNvbHZlRG9jLmJvZHkuYXBwZW5kQ2hpbGQocmVzb2x2ZURvYy5hbmNob3IpOwogICAgICB9CiAgICAgIHJlc29sdmVEb2MuYmFzZS5ocmVmID0gYmFzZVVSSTsKICAgICAgcmVzb2x2ZURvYy5hbmNob3IuaHJlZiA9IHVybDsKICAgICAgcmV0dXJuIHJlc29sdmVEb2MuYW5jaG9yLmhyZWYgfHwgdXJsOwoKICAgIH0KCiAgICAvKioKICAgICAqIFJlc29sdmVzIGFueSByZWxhdGl2ZSBVUkwncyBpbiB0aGUgZ2l2ZW4gQ1NTIHRleHQgYWdhaW5zdCB0aGUgcHJvdmlkZWQKICAgICAqIGBvd25lckRvY3VtZW50YCdzIGBiYXNlVVJJYC4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY3NzVGV4dCBDU1MgdGV4dCB0byBwcm9jZXNzCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gYmFzZVVSSSBCYXNlIFVSSSB0byByZXNvbHZlIHRoZSBVUkwgYWdhaW5zdAogICAgICogQHJldHVybiB7c3RyaW5nfSBQcm9jZXNzZWQgQ1NTIHRleHQgd2l0aCByZXNvbHZlZCBVUkwncwogICAgICovCiAgICBmdW5jdGlvbiByZXNvbHZlQ3NzKGNzc1RleHQsIGJhc2VVUkkpIHsKICAgICAgcmV0dXJuIGNzc1RleHQucmVwbGFjZShDU1NfVVJMX1JYLCBmdW5jdGlvbihtLCBwcmUsIHVybCwgcG9zdCkgewogICAgICAgIHJldHVybiBwcmUgKyAnXCcnICsKICAgICAgICAgIHJlc29sdmVVcmwodXJsLnJlcGxhY2UoL1siJ10vZywgJycpLCBiYXNlVVJJKSArCiAgICAgICAgICAnXCcnICsgcG9zdDsKICAgICAgfSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZXR1cm5zIGEgcGF0aCBmcm9tIGEgZ2l2ZW4gYHVybGAuIFRoZSBwYXRoIGluY2x1ZGVzIHRoZSB0cmFpbGluZwogICAgICogYC9gIGZyb20gdGhlIHVybC4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gdXJsIElucHV0IFVSTCB0byB0cmFuc2Zvcm0KICAgICAqIEByZXR1cm4ge3N0cmluZ30gcmVzb2x2ZWQgcGF0aAogICAgICovCiAgICBmdW5jdGlvbiBwYXRoRnJvbVVybCh1cmwpIHsKICAgICAgcmV0dXJuIHVybC5zdWJzdHJpbmcoMCwgdXJsLmxhc3RJbmRleE9mKCcvJykgKyAxKTsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgY29uc3QgdXNlU2hhZG93ID0gISh3aW5kb3cuU2hhZHlET00pIHx8ICEod2luZG93LlNoYWR5RE9NLmluVXNlKTsKICAgIGNvbnN0IHVzZU5hdGl2ZUNTU1Byb3BlcnRpZXMgPSBCb29sZWFuKCF3aW5kb3cuU2hhZHlDU1MgfHwgd2luZG93LlNoYWR5Q1NTLm5hdGl2ZUNzcyk7CiAgICBjb25zdCBzdXBwb3J0c0Fkb3B0aW5nU3R5bGVTaGVldHMgPSB1c2VTaGFkb3cgJiYKICAgICAgICAoJ2Fkb3B0ZWRTdHlsZVNoZWV0cycgaW4gRG9jdW1lbnQucHJvdG90eXBlKSAmJgogICAgICAgICgncmVwbGFjZVN5bmMnIGluIENTU1N0eWxlU2hlZXQucHJvdG90eXBlKSAmJgogICAgICAgIC8vIFNpbmNlIHNwZWMgbWF5IGNoYW5nZSwgZmVhdHVyZSBkZXRlY3QgZXhhY3QgQVBJIHdlIG5lZWQKICAgICAgICAoKCkgPT4gewogICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgY29uc3Qgc2hlZXQgPSBuZXcgQ1NTU3R5bGVTaGVldCgpOwogICAgICAgICAgICBzaGVldC5yZXBsYWNlU3luYygnJyk7CiAgICAgICAgICAgIGNvbnN0IGhvc3QgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgICAgICAgICAgaG9zdC5hdHRhY2hTaGFkb3coe21vZGU6ICdvcGVuJ30pOwogICAgICAgICAgICBob3N0LnNoYWRvd1Jvb3QuYWRvcHRlZFN0eWxlU2hlZXRzID0gW3NoZWV0XTsKICAgICAgICAgICAgcmV0dXJuIChob3N0LnNoYWRvd1Jvb3QuYWRvcHRlZFN0eWxlU2hlZXRzWzBdID09PSBzaGVldCk7CiAgICAgICAgICB9IGNhdGNoKGUpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0pKCk7CgogICAgLyoqCiAgICAgKiBHbG9iYWxseSBzZXR0YWJsZSBwcm9wZXJ0eSB0aGF0IGlzIGF1dG9tYXRpY2FsbHkgYXNzaWduZWQgdG8KICAgICAqIGBFbGVtZW50TWl4aW5gIGluc3RhbmNlcywgdXNlZnVsIGZvciBiaW5kaW5nIGluIHRlbXBsYXRlcyB0bwogICAgICogbWFrZSBVUkwncyByZWxhdGl2ZSB0byBhbiBhcHBsaWNhdGlvbidzIHJvb3QuICBEZWZhdWx0cyB0byB0aGUgbWFpbgogICAgICogZG9jdW1lbnQgVVJMLCBidXQgY2FuIGJlIG92ZXJyaWRkZW4gYnkgdXNlcnMuICBJdCBtYXkgYmUgdXNlZnVsIHRvIHNldAogICAgICogYHJvb3RQYXRoYCB0byBwcm92aWRlIGEgc3RhYmxlIGFwcGxpY2F0aW9uIG1vdW50IHBhdGggd2hlbgogICAgICogdXNpbmcgY2xpZW50IHNpZGUgcm91dGluZy4KICAgICAqLwogICAgbGV0IHJvb3RQYXRoID0gd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIucm9vdFBhdGggfHwKICAgICAgcGF0aEZyb21VcmwoZG9jdW1lbnQuYmFzZVVSSSB8fCB3aW5kb3cubG9jYXRpb24uaHJlZik7CgogICAgLyoqCiAgICAgKiBBIGdsb2JhbCBjYWxsYmFjayB1c2VkIHRvIHNhbml0aXplIGFueSB2YWx1ZSBiZWZvcmUgaW5zZXJ0aW5nIGl0IGludG8gdGhlIERPTS4KICAgICAqIFRoZSBjYWxsYmFjayBzaWduYXR1cmUgaXM6CiAgICAgKgogICAgICogIGZ1bmN0aW9uIHNhbml0aXplRE9NVmFsdWUodmFsdWUsIG5hbWUsIHR5cGUsIG5vZGUpIHsgLi4uIH0KICAgICAqCiAgICAgKiBXaGVyZToKICAgICAqCiAgICAgKiBgdmFsdWVgIGlzIHRoZSB2YWx1ZSB0byBzYW5pdGl6ZS4KICAgICAqIGBuYW1lYCBpcyB0aGUgbmFtZSBvZiBhbiBhdHRyaWJ1dGUgb3IgcHJvcGVydHkgKGZvciBleGFtcGxlLCBocmVmKS4KICAgICAqIGB0eXBlYCBpbmRpY2F0ZXMgd2hlcmUgdGhlIHZhbHVlIGlzIGJlaW5nIGluc2VydGVkOiBvbmUgb2YgcHJvcGVydHksIGF0dHJpYnV0ZSwgb3IgdGV4dC4KICAgICAqIGBub2RlYCBpcyB0aGUgbm9kZSB3aGVyZSB0aGUgdmFsdWUgaXMgYmVpbmcgaW5zZXJ0ZWQuCiAgICAgKgogICAgICogQHR5cGUgeyhmdW5jdGlvbigqLHN0cmluZyxzdHJpbmcsP05vZGUpOiopfHVuZGVmaW5lZH0KICAgICAqLwogICAgbGV0IHNhbml0aXplRE9NVmFsdWUgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5zYW5pdGl6ZURPTVZhbHVlIHx8IHVuZGVmaW5lZDsKCiAgICAvKioKICAgICAqIEdsb2JhbGx5IHNldHRhYmxlIHByb3BlcnR5IHRvIG1ha2UgUG9seW1lciBHZXN0dXJlcyB1c2UgcGFzc2l2ZSBUb3VjaEV2ZW50IGxpc3RlbmVycyB3aGVuIHJlY29nbml6aW5nIGdlc3R1cmVzLgogICAgICogV2hlbiBzZXQgdG8gYHRydWVgLCBnZXN0dXJlcyBtYWRlIGZyb20gdG91Y2ggd2lsbCBub3QgYmUgYWJsZSB0byBwcmV2ZW50IHNjcm9sbGluZywgYWxsb3dpbmcgZm9yIHNtb290aGVyCiAgICAgKiBzY3JvbGxpbmcgcGVyZm9ybWFuY2UuCiAgICAgKiBEZWZhdWx0cyB0byBgZmFsc2VgIGZvciBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eS4KICAgICAqLwogICAgbGV0IHBhc3NpdmVUb3VjaEdlc3R1cmVzID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIuc2V0UGFzc2l2ZVRvdWNoR2VzdHVyZXMgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIGVuc3VyZSBQb2x5bWVyIHRlbXBsYXRlIGV2YWx1YXRpb24gb25seSBvY2N1cnMgYmFzZWQgb24gdGVtcGF0ZXMKICAgICAqIGRlZmluZWQgaW4gdHJ1c3RlZCBzY3JpcHQuICBXaGVuIHRydWUsIGA8ZG9tLW1vZHVsZT5gIHJlLXJlZ2lzdHJhdGlvbiBpcwogICAgICogZGlzYWxsb3dlZCwgYDxkb20tYmluZD5gIGlzIGRpc2FibGVkLCBhbmQgYDxkb20taWY+YC9gPGRvbS1yZXBlYXQ+YAogICAgICogdGVtcGxhdGVzIHdpbGwgb25seSBldmFsdWF0ZSBpbiB0aGUgY29udGV4dCBvZiBhIHRydXN0ZWQgZWxlbWVudCB0ZW1wbGF0ZS4KICAgICAqLwogICAgbGV0IHN0cmljdFRlbXBsYXRlUG9saWN5ID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIuc3RyaWN0VGVtcGxhdGVQb2xpY3kgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIGVuYWJsZSBkb20tbW9kdWxlIGxvb2t1cCBmcm9tIFBvbHltZXIuRWxlbWVudC4gIEJ5IGRlZmF1bHQsCiAgICAgKiB0ZW1wbGF0ZXMgbXVzdCBiZSBkZWZpbmVkIGluIHNjcmlwdCB1c2luZyB0aGUgYHN0YXRpYyBnZXQgdGVtcGxhdGUoKWAKICAgICAqIGdldHRlciBhbmQgdGhlIGBodG1sYCB0YWcgZnVuY3Rpb24uICBUbyBlbmFibGUgbGVnYWN5IGxvYWRpbmcgb2YgdGVtcGxhdGVzCiAgICAgKiB2aWEgZG9tLW1vZHVsZSwgc2V0IHRoaXMgZmxhZyB0byB0cnVlLgogICAgICovCiAgICBsZXQgYWxsb3dUZW1wbGF0ZUZyb21Eb21Nb2R1bGUgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5hbGxvd1RlbXBsYXRlRnJvbURvbU1vZHVsZSB8fCBmYWxzZTsKCiAgICAvKioKICAgICAqIFNldHRpbmcgdG8gc2tpcCBwcm9jZXNzaW5nIHN0eWxlIGluY2x1ZGVzIGFuZCByZS13cml0aW5nIHVybHMgaW4gY3NzIHN0eWxlcy4KICAgICAqIE5vcm1hbGx5ICJpbmNsdWRlZCIgc3R5bGVzIGFyZSBwdWxsZWQgaW50byB0aGUgZWxlbWVudCBhbmQgYWxsIHVybHMgaW4gc3R5bGVzCiAgICAgKiBhcmUgcmUtd3JpdHRlbiB0byBiZSByZWxhdGl2ZSB0byB0aGUgY29udGFpbmluZyBzY3JpcHQgdXJsLgogICAgICogSWYgbm8gaW5jbHVkZXMgb3IgcmVsYXRpdmUgdXJscyBhcmUgdXNlZCBpbiBzdHlsZXMsIHRoZXNlIHN0ZXBzIGNhbiBiZQogICAgICogc2tpcHBlZCBhcyBhbiBvcHRpbWl6YXRpb24uCiAgICAgKi8KICAgIGxldCBsZWdhY3lPcHRpbWl6YXRpb25zID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIubGVnYWN5T3B0aW1pemF0aW9ucyB8fCBmYWxzZTsKCiAgICAvKioKICAgICAqIFNldHRpbmcgdG8gYWRkIHdhcm5pbmdzIHVzZWZ1bCB3aGVuIG1pZ3JhdGluZyBmcm9tIFBvbHltZXIgMS54IHRvIDIueC4KICAgICAqLwogICAgbGV0IGxlZ2FjeVdhcm5pbmdzID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIubGVnYWN5V2FybmluZ3MgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIHBlcmZvcm0gaW5pdGlhbCByZW5kZXJpbmcgc3luY2hyb25vdXNseSB3aGVuIHJ1bm5pbmcgdW5kZXIgU2hhZHlET00uCiAgICAgKiBUaGlzIG1hdGNoZXMgdGhlIGJlaGF2aW9yIG9mIFBvbHltZXIgMS4KICAgICAqLwogICAgbGV0IHN5bmNJbml0aWFsUmVuZGVyID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIuc3luY0luaXRpYWxSZW5kZXIgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIHJldGFpbiB0aGUgbGVnYWN5IFBvbHltZXIgMSBiZWhhdmlvciBmb3IgbXVsdGktcHJvcGVydHkKICAgICAqIG9ic2VydmVycyBhcm91bmQgdW5kZWZpbmVkIHZhbHVlcy4gT2JzZXJ2ZXJzIGFuZCBjb21wdXRlZCBwcm9wZXJ0eSBtZXRob2RzCiAgICAgKiBhcmUgbm90IGNhbGxlZCB1bnRpbCBubyBhcmd1bWVudCBpcyB1bmRlZmluZWQuCiAgICAgKi8KICAgIGxldCBsZWdhY3lVbmRlZmluZWQgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5sZWdhY3lVbmRlZmluZWQgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIGVuc3VyZSBjb21wdXRlZCBwcm9wZXJ0aWVzIGFyZSBjb21wdXRlZCBpbiBvcmRlciB0byBlbnN1cmUKICAgICAqIHJlLWNvbXB1dGF0aW9uIG5ldmVyIG9jY3VycyBpbiBhIGdpdmVuIHR1cm4uCiAgICAgKi8KICAgIGxldCBvcmRlcmVkQ29tcHV0ZWQgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5vcmRlcmVkQ29tcHV0ZWQgfHwgZmFsc2U7CgogICAgLyoqCiAgICAgKiBTZXR0aW5nIHRvIHJlbW92ZSBuZXN0ZWQgdGVtcGxhdGVzIGluc2lkZSBgZG9tLWlmYCBhbmQgYGRvbS1yZXBlYXRgIGFzCiAgICAgKiBwYXJ0IG9mIGVsZW1lbnQgdGVtcGxhdGUgcGFyc2luZy4gIFRoaXMgaXMgYSBwZXJmb3JtYW5jZSBvcHRpbWl6YXRpb24gdGhhdAogICAgICogZWxpbWluYXRlcyBtb3N0IG9mIHRoZSB0YXggb2YgbmVlZGluZyB0d28gZWxlbWVudHMgZHVlIHRvIHRoZSBsb3NzIG9mCiAgICAgKiB0eXBlLWV4dGVuZGVkIHRlbXBsYXRlcyBhcyBhIHJlc3VsdCBvZiB0aGUgVjEgc3BlY2lmaWNhdGlvbiBjaGFuZ2VzLgogICAgICovCiAgICBsZXQgcmVtb3ZlTmVzdGVkVGVtcGxhdGVzID0KICAgICAgd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIucmVtb3ZlTmVzdGVkVGVtcGxhdGVzIHx8IGZhbHNlOwoKICAgIC8qKgogICAgICogU2V0dGluZyB0byBwbGFjZSBgZG9tLWlmYCBlbGVtZW50cyBpbiBhIHBlcmZvcm1hbmNlLW9wdGltaXplZCBtb2RlIHRoYXQgdGFrZXMKICAgICAqIGFkdmFudGFnZSBvZiBsaWdodGVyLXdlaWdodCBob3N0IHJ1bnRpbWUgdGVtcGxhdGUgc3RhbXBpbmcgdG8gZWxpbWluYXRlIHRoZQogICAgICogbmVlZCBmb3IgYW4gaW50ZXJtZWRpYXRlIFRlbXBsYXRpemVyIGBUZW1wbGF0ZUluc3RhbmNlYCB0byBtYW5nZSB0aGUgbm9kZXMKICAgICAqIHN0YW1wZWQgYnkgYGRvbS1pZmAuICBVbmRlciB0aGlzIHNldHRpbmcsIGFueSBUZW1wbGF0aXplci1wcm92aWRlZCBBUEkncwogICAgICogc3VjaCBhcyBgbW9kZWxGb3JFbGVtZW50YCB3aWxsIG5vdCBiZSBhdmFpbGFibGUgZm9yIG5vZGVzIHN0YW1wZWQgYnkKICAgICAqIGBkb20taWZgLgogICAgICovCiAgICBsZXQgZmFzdERvbUlmID0gd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIuZmFzdERvbUlmIHx8IGZhbHNlOwoKICAgIC8qKgogICAgICogU2V0dGluZyB0byBkaXNhYmxlIGBkb20tY2hhbmdlYCBhbmQgYHJlbmRlcmVkLWl0ZW0tY291bnRgIGV2ZW50cyBmcm9tCiAgICAgKiBgZG9tLWlmYCBhbmQgYGRvbS1yZXBlYXRgLiBVc2VycyBjYW4gb3B0IGJhY2sgaW50byBgZG9tLWNoYW5nZWAgZXZlbnRzIGJ5CiAgICAgKiBzZXR0aW5nIHRoZSBgbm90aWZ5LWRvbS1jaGFuZ2VgIGF0dHJpYnV0ZSAoYG5vdGlmeURvbUNoYW5nZTogdHJ1ZWAgcHJvcGVydHkpCiAgICAgKiB0byBgZG9tLWlmYC9gZG9uLXJlcGVhdGAgaW5zdGFuY2VzLgogICAgICovCiAgICBsZXQgc3VwcHJlc3NUZW1wbGF0ZU5vdGlmaWNhdGlvbnMgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5zdXBwcmVzc1RlbXBsYXRlTm90aWZpY2F0aW9ucyB8fCBmYWxzZTsKCiAgICAvKioKICAgICAqIFNldHRpbmcgdG8gZGlzYWJsZSB1c2Ugb2YgZHluYW1pYyBhdHRyaWJ1dGVzLiBUaGlzIGlzIGFuIG9wdGltaXphdGlvbgogICAgICogdG8gYXZvaWQgc2V0dGluZyBgb2JzZXJ2ZWRBdHRyaWJ1dGVzYC4gSW5zdGVhZCBhdHRyaWJ1dGVzIGFyZSByZWFkCiAgICAgKiBvbmNlIGF0IGNyZWF0ZSB0aW1lIGFuZCBzZXQvcmVtb3ZlQXR0cmlidXRlIGFyZSBwYXRjaGVkLgogICAgICovCiAgICBsZXQgbGVnYWN5Tm9PYnNlcnZlZEF0dHJpYnV0ZXMgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci5sZWdhY3lOb09ic2VydmVkQXR0cmlidXRlcyB8fCBmYWxzZTsKCiAgICAvKioKICAgICAqIFNldHRpbmcgdG8gZW5hYmxlIHVzZSBvZiBgYWRvcHRlZFN0eWxlU2hlZXRzYCBmb3Igc2hhcmluZyBzdHlsZSBzaGVldHMKICAgICAqIGJldHdlZW4gY29tcG9uZW50IGluc3RhbmNlcycgc2hhZG93IHJvb3RzLCBpZiB0aGUgYXBwIHVzZXMgYnVpbHQgU2hhZHkgQ1NTCiAgICAgKiBzdHlsZXMuCiAgICAgKi8KICAgIGxldCB1c2VBZG9wdGVkU3R5bGVTaGVldHNXaXRoQnVpbHRDU1MgPQogICAgICB3aW5kb3cuUG9seW1lciAmJiB3aW5kb3cuUG9seW1lci51c2VBZG9wdGVkU3R5bGVTaGVldHNXaXRoQnVpbHRDU1MgfHwgZmFsc2U7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyB1bmlxdWUgZ2xvYmFsIGlkIGZvciBkZWR1cGluZyBtaXhpbnMuCiAgICBsZXQgZGVkdXBlSWQgPSAwOwoKICAgIC8qIGVzbGludC1kaXNhYmxlIHZhbGlkLWpzZG9jICovCiAgICAvKioKICAgICAqIFdyYXBzIGFuIEVTNiBjbGFzcyBleHByZXNzaW9uIG1peGluIHN1Y2ggdGhhdCB0aGUgbWl4aW4gaXMgb25seSBhcHBsaWVkCiAgICAgKiBpZiBpdCBoYXMgbm90IGFscmVhZHkgYmVlbiBhcHBsaWVkIGl0cyBiYXNlIGFyZ3VtZW50LiBBbHNvIG1lbW9pemVzIG1peGluCiAgICAgKiBhcHBsaWNhdGlvbnMuCiAgICAgKgogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7VH0gbWl4aW4gRVM2IGNsYXNzIGV4cHJlc3Npb24gbWl4aW4gdG8gd3JhcAogICAgICogQHJldHVybiB7VH0KICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfQogICAgICovCiAgICBjb25zdCBkZWR1cGluZ01peGluID0gZnVuY3Rpb24obWl4aW4pIHsKICAgICAgbGV0IG1peGluQXBwbGljYXRpb25zID0gLyoqIEB0eXBlIHshTWl4aW5GdW5jdGlvbn0gKi8obWl4aW4pLl9fbWl4aW5BcHBsaWNhdGlvbnM7CiAgICAgIGlmICghbWl4aW5BcHBsaWNhdGlvbnMpIHsKICAgICAgICBtaXhpbkFwcGxpY2F0aW9ucyA9IG5ldyBXZWFrTWFwKCk7CiAgICAgICAgLyoqIEB0eXBlIHshTWl4aW5GdW5jdGlvbn0gKi8obWl4aW4pLl9fbWl4aW5BcHBsaWNhdGlvbnMgPSBtaXhpbkFwcGxpY2F0aW9uczsKICAgICAgfQogICAgICAvLyBtYWludGFpbiBhIHVuaXF1ZSBpZCBmb3IgZWFjaCBtaXhpbgogICAgICBsZXQgbWl4aW5EZWR1cGVJZCA9IGRlZHVwZUlkKys7CiAgICAgIGZ1bmN0aW9uIGRlZHVwaW5nTWl4aW4oYmFzZSkgewogICAgICAgIGxldCBiYXNlU2V0ID0gLyoqIEB0eXBlIHshTWl4aW5GdW5jdGlvbn0gKi8oYmFzZSkuX19taXhpblNldDsKICAgICAgICBpZiAoYmFzZVNldCAmJiBiYXNlU2V0W21peGluRGVkdXBlSWRdKSB7CiAgICAgICAgICByZXR1cm4gYmFzZTsKICAgICAgICB9CiAgICAgICAgbGV0IG1hcCA9IG1peGluQXBwbGljYXRpb25zOwogICAgICAgIGxldCBleHRlbmRlZCA9IG1hcC5nZXQoYmFzZSk7CiAgICAgICAgaWYgKCFleHRlbmRlZCkgewogICAgICAgICAgZXh0ZW5kZWQgPSAvKiogQHR5cGUgeyFGdW5jdGlvbn0gKi8obWl4aW4pKGJhc2UpOwogICAgICAgICAgbWFwLnNldChiYXNlLCBleHRlbmRlZCk7CiAgICAgICAgICAvLyBjb3B5IGluaGVyaXRlZCBtaXhpbiBzZXQgZnJvbSB0aGUgZXh0ZW5kZWQgY2xhc3MsIG9yIHRoZSBiYXNlIGNsYXNzCiAgICAgICAgICAvLyBOT1RFOiB3ZSBhdm9pZCB1c2Ugb2YgU2V0IGhlcmUgYmVjYXVzZSBzb21lIGJyb3dzZXIgKElFMTEpCiAgICAgICAgICAvLyBjYW5ub3QgZXh0ZW5kIGEgYmFzZSBTZXQgdmlhIHRoZSBjb25zdHJ1Y3Rvci4KICAgICAgICAgIGxldCBtaXhpblNldCA9IE9iamVjdC5jcmVhdGUoLyoqIEB0eXBlIHshTWl4aW5GdW5jdGlvbn0gKi8oZXh0ZW5kZWQpLl9fbWl4aW5TZXQgfHwgYmFzZVNldCB8fCBudWxsKTsKICAgICAgICAgIG1peGluU2V0W21peGluRGVkdXBlSWRdID0gdHJ1ZTsKICAgICAgICAgIC8qKiBAdHlwZSB7IU1peGluRnVuY3Rpb259ICovKGV4dGVuZGVkKS5fX21peGluU2V0ID0gbWl4aW5TZXQ7CiAgICAgICAgfQogICAgICAgIHJldHVybiBleHRlbmRlZDsKICAgICAgfQoKICAgICAgcmV0dXJuIGRlZHVwaW5nTWl4aW47CiAgICB9OwogICAgLyogZXNsaW50LWVuYWJsZSB2YWxpZC1qc2RvYyAqLwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgbGV0IG1vZHVsZXMgPSB7fTsKICAgIGxldCBsY01vZHVsZXMgPSB7fTsKICAgIC8qKgogICAgICogU2V0cyBhIGRvbS1tb2R1bGUgaW50byB0aGUgZ2xvYmFsIHJlZ2lzdHJ5IGJ5IGlkLgogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBpZCBkb20tbW9kdWxlIGlkCiAgICAgKiBAcGFyYW0ge0RvbU1vZHVsZX0gbW9kdWxlIGRvbS1tb2R1bGUgaW5zdGFuY2UKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHNldE1vZHVsZShpZCwgbW9kdWxlKSB7CiAgICAgIC8vIHN0b3JlIGlkIHNlcGFyYXRlIGZyb20gbG93ZXJjYXNlZCBpZCBzbyB0aGF0CiAgICAgIC8vIGluIGFsbCBjYXNlcyBtaXhlZENhc2UgaWQgd2lsbCBzdG9yZWQgZGlzdGluY3RseQogICAgICAvLyBhbmQgbG93ZXJjYXNlIHZlcnNpb24gaXMgYSBmYWxsYmFjawogICAgICBtb2R1bGVzW2lkXSA9IGxjTW9kdWxlc1tpZC50b0xvd2VyQ2FzZSgpXSA9IG1vZHVsZTsKICAgIH0KICAgIC8qKgogICAgICogUmV0cmlldmVzIGEgZG9tLW1vZHVsZSBmcm9tIHRoZSBnbG9iYWwgcmVnaXN0cnkgYnkgaWQuCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmd9IGlkIGRvbS1tb2R1bGUgaWQKICAgICAqIEByZXR1cm4ge0RvbU1vZHVsZSF9IGRvbS1tb2R1bGUgaW5zdGFuY2UKICAgICAqLwogICAgZnVuY3Rpb24gZmluZE1vZHVsZShpZCkgewogICAgICByZXR1cm4gbW9kdWxlc1tpZF0gfHwgbGNNb2R1bGVzW2lkLnRvTG93ZXJDYXNlKCldOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlT3V0c2lkZVRlbXBsYXRlQ2hlY2soaW5zdCkgewogICAgICBpZiAoaW5zdC5xdWVyeVNlbGVjdG9yKCdzdHlsZScpKSB7CiAgICAgICAgY29uc29sZS53YXJuKCdkb20tbW9kdWxlICVzIGhhcyBzdHlsZSBvdXRzaWRlIHRlbXBsYXRlJywgaW5zdC5pZCk7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFRoZSBgZG9tLW1vZHVsZWAgZWxlbWVudCByZWdpc3RlcnMgdGhlIGRvbSBpdCBjb250YWlucyB0byB0aGUgbmFtZSBnaXZlbgogICAgICogYnkgdGhlIG1vZHVsZSdzIGlkIGF0dHJpYnV0ZS4gSXQgcHJvdmlkZXMgYSB1bmlmaWVkIGRhdGFiYXNlIG9mIGRvbQogICAgICogYWNjZXNzaWJsZSB2aWEgaXRzIHN0YXRpYyBgaW1wb3J0YCBBUEkuCiAgICAgKgogICAgICogQSBrZXkgdXNlIGNhc2Ugb2YgYGRvbS1tb2R1bGVgIGlzIGZvciBwcm92aWRpbmcgY3VzdG9tIGVsZW1lbnQgYDx0ZW1wbGF0ZT5gcwogICAgICogdmlhIEhUTUwgaW1wb3J0cyB0aGF0IGFyZSBwYXJzZWQgYnkgdGhlIG5hdGl2ZSBIVE1MIHBhcnNlciwgdGhhdCBjYW4gYmUKICAgICAqIHJlbG9jYXRlZCBkdXJpbmcgYSBidW5kbGluZyBwYXNzIGFuZCBzdGlsbCBsb29rZWQgdXAgYnkgYGlkYC4KICAgICAqCiAgICAgKiBFeGFtcGxlOgogICAgICoKICAgICAqICAgICA8ZG9tLW1vZHVsZSBpZD0iZm9vIj4KICAgICAqICAgICAgIDxpbWcgc3JjPSJzdHVmZi5wbmciPgogICAgICogICAgIDwvZG9tLW1vZHVsZT4KICAgICAqCiAgICAgKiBUaGVuIGluIGNvZGUgaW4gc29tZSBvdGhlciBsb2NhdGlvbiB0aGF0IGNhbm5vdCBhY2Nlc3MgdGhlIGRvbS1tb2R1bGUgYWJvdmUKICAgICAqCiAgICAgKiAgICAgbGV0IGltZyA9IGN1c3RvbUVsZW1lbnRzLmdldCgnZG9tLW1vZHVsZScpLmltcG9ydCgnZm9vJywgJ2ltZycpOwogICAgICoKICAgICAqIEBjdXN0b21FbGVtZW50CiAgICAgKiBAZXh0ZW5kcyBIVE1MRWxlbWVudAogICAgICogQHN1bW1hcnkgQ3VzdG9tIGVsZW1lbnQgdGhhdCBwcm92aWRlcyBhIHJlZ2lzdHJ5IG9mIHJlbG9jYXRhYmxlIERPTSBjb250ZW50CiAgICAgKiAgIGJ5IGBpZGAgdGhhdCBpcyBhZ25vc3RpYyB0byBidW5kbGluZy4KICAgICAqIEB1bnJlc3RyaWN0ZWQKICAgICAqLwogICAgY2xhc3MgRG9tTW9kdWxlIGV4dGVuZHMgSFRNTEVsZW1lbnQgewoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHsgcmV0dXJuIFsnaWQnXTsgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHJpZXZlcyB0aGUgZWxlbWVudCBzcGVjaWZpZWQgYnkgdGhlIGNzcyBgc2VsZWN0b3JgIGluIHRoZSBtb2R1bGUKICAgICAgICogcmVnaXN0ZXJlZCBieSBgaWRgLiBGb3IgZXhhbXBsZSwgdGhpcy5pbXBvcnQoJ2ZvbycsICdpbWcnKTsKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGlkIFRoZSBpZCBvZiB0aGUgZG9tLW1vZHVsZSBpbiB3aGljaCB0byBzZWFyY2guCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gc2VsZWN0b3IgVGhlIGNzcyBzZWxlY3RvciBieSB3aGljaCB0byBmaW5kIHRoZSBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHtFbGVtZW50fSBSZXR1cm5zIHRoZSBlbGVtZW50IHdoaWNoIG1hdGNoZXMgYHNlbGVjdG9yYCBpbiB0aGUKICAgICAgICogbW9kdWxlIHJlZ2lzdGVyZWQgYXQgdGhlIHNwZWNpZmllZCBgaWRgLgogICAgICAgKgogICAgICAgKiBAZXhwb3J0CiAgICAgICAqIEBub2NvbGxhcHNlIFJlZmVycmVkIHRvIGluZGlyZWN0bHkgaW4gc3R5bGUtZ2F0aGVyLmpzCiAgICAgICAqLwogICAgICBzdGF0aWMgaW1wb3J0KGlkLCBzZWxlY3RvcikgewogICAgICAgIGlmIChpZCkgewogICAgICAgICAgbGV0IG0gPSBmaW5kTW9kdWxlKGlkKTsKICAgICAgICAgIGlmIChtICYmIHNlbGVjdG9yKSB7CiAgICAgICAgICAgIHJldHVybiBtLnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG07CiAgICAgICAgfQogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CgogICAgICAvKiBlc2xpbnQtZGlzYWJsZSBuby11bnVzZWQtdmFycyAqLwogICAgICAvKioKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgTmFtZSBvZiBhdHRyaWJ1dGUuCiAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gb2xkIE9sZCB2YWx1ZSBvZiBhdHRyaWJ1dGUuCiAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gdmFsdWUgQ3VycmVudCB2YWx1ZSBvZiBhdHRyaWJ1dGUuCiAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gbmFtZXNwYWNlIEF0dHJpYnV0ZSBuYW1lc3BhY2UuCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZCwgdmFsdWUsIG5hbWVzcGFjZSkgewogICAgICAgIGlmIChvbGQgIT09IHZhbHVlKSB7CiAgICAgICAgICB0aGlzLnJlZ2lzdGVyKCk7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qIGVzbGludC1lbmFibGUgbm8tdW51c2VkLWFyZ3MgKi8KCiAgICAgIC8qKgogICAgICAgKiBUaGUgYWJzb2x1dGUgVVJMIG9mIHRoZSBvcmlnaW5hbCBsb2NhdGlvbiBvZiB0aGlzIGBkb20tbW9kdWxlYC4KICAgICAgICoKICAgICAgICogVGhpcyB2YWx1ZSB3aWxsIGRpZmZlciBmcm9tIHRoaXMgZWxlbWVudCdzIGBvd25lckRvY3VtZW50YCBpbiB0aGUKICAgICAgICogZm9sbG93aW5nIHdheXM6CiAgICAgICAqIC0gVGFrZXMgaW50byBhY2NvdW50IGFueSBgYXNzZXRwYXRoYCBhdHRyaWJ1dGUgYWRkZWQgZHVyaW5nIGJ1bmRsaW5nCiAgICAgICAqICAgdG8gaW5kaWNhdGUgdGhlIG9yaWdpbmFsIGxvY2F0aW9uIHJlbGF0aXZlIHRvIHRoZSBidW5kbGVkIGxvY2F0aW9uCiAgICAgICAqIC0gVXNlcyB0aGUgSFRNTEltcG9ydHMgcG9seWZpbGwncyBgaW1wb3J0Rm9yRWxlbWVudGAgQVBJIHRvIGVuc3VyZQogICAgICAgKiAgIHRoZSBwYXRoIGlzIHJlbGF0aXZlIHRvIHRoZSBpbXBvcnQgZG9jdW1lbnQncyBsb2NhdGlvbiBzaW5jZQogICAgICAgKiAgIGBvd25lckRvY3VtZW50YCBpcyBub3QgY3VycmVudGx5IHBvbHlmaWxsZWQKICAgICAgICovCiAgICAgIGdldCBhc3NldHBhdGgoKSB7CiAgICAgICAgLy8gRG9uJ3Qgb3ZlcnJpZGUgZXhpc3RpbmcgYXNzZXRwYXRoLgogICAgICAgIGlmICghdGhpcy5fX2Fzc2V0cGF0aCkgewogICAgICAgICAgLy8gbm90ZTogYXNzZXRwYXRoIHNldCB2aWEgYW4gYXR0cmlidXRlIG11c3QgYmUgcmVsYXRpdmUgdG8gdGhpcwogICAgICAgICAgLy8gZWxlbWVudCdzIGxvY2F0aW9uOyBhY2NvbW9kYXRlIHBvbHlmaWxsZWQgSFRNTEltcG9ydHMKICAgICAgICAgIGNvbnN0IG93bmVyID0gd2luZG93LkhUTUxJbXBvcnRzICYmIEhUTUxJbXBvcnRzLmltcG9ydEZvckVsZW1lbnQgPwogICAgICAgICAgICBIVE1MSW1wb3J0cy5pbXBvcnRGb3JFbGVtZW50KHRoaXMpIHx8IGRvY3VtZW50IDogdGhpcy5vd25lckRvY3VtZW50OwogICAgICAgICAgY29uc3QgdXJsID0gcmVzb2x2ZVVybCgKICAgICAgICAgICAgdGhpcy5nZXRBdHRyaWJ1dGUoJ2Fzc2V0cGF0aCcpIHx8ICcnLCBvd25lci5iYXNlVVJJKTsKICAgICAgICAgIHRoaXMuX19hc3NldHBhdGggPSBwYXRoRnJvbVVybCh1cmwpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy5fX2Fzc2V0cGF0aDsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJlZ2lzdGVycyB0aGUgZG9tLW1vZHVsZSBhdCBhIGdpdmVuIGlkLiBUaGlzIG1ldGhvZCBzaG91bGQgb25seSBiZSBjYWxsZWQKICAgICAgICogd2hlbiBhIGRvbS1tb2R1bGUgaXMgaW1wZXJhdGl2ZWx5IGNyZWF0ZWQuIEZvcgogICAgICAgKiBleGFtcGxlLCBgZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZG9tLW1vZHVsZScpLnJlZ2lzdGVyKCdmb28nKWAuCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gaWQgVGhlIGlkIGF0IHdoaWNoIHRvIHJlZ2lzdGVyIHRoZSBkb20tbW9kdWxlLgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgcmVnaXN0ZXIoaWQpIHsKICAgICAgICBpZCA9IGlkIHx8IHRoaXMuaWQ7CiAgICAgICAgaWYgKGlkKSB7CiAgICAgICAgICAvLyBVbmRlciBzdHJpY3RUZW1wbGF0ZVBvbGljeSwgcmVqZWN0IGFuZCBudWxsIG91dCBhbnkgcmUtcmVnaXN0ZXJlZAogICAgICAgICAgLy8gZG9tLW1vZHVsZSBzaW5jZSBpdCBpcyBhbWJpZ3VvdXMgd2hldGhlciBmaXJzdC1pbiBvciBsYXN0LWluIGlzIHRydXN0ZWQKICAgICAgICAgIGlmIChzdHJpY3RUZW1wbGF0ZVBvbGljeSAmJiBmaW5kTW9kdWxlKGlkKSAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgIHNldE1vZHVsZShpZCwgbnVsbCk7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgc3RyaWN0VGVtcGxhdGVQb2xpY3k6IGRvbS1tb2R1bGUgJHtpZH0gcmUtcmVnaXN0ZXJlZGApOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5pZCA9IGlkOwogICAgICAgICAgc2V0TW9kdWxlKGlkLCB0aGlzKTsKICAgICAgICAgIHN0eWxlT3V0c2lkZVRlbXBsYXRlQ2hlY2sodGhpcyk7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgRG9tTW9kdWxlLnByb3RvdHlwZVsnbW9kdWxlcyddID0gbW9kdWxlczsKCiAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ2RvbS1tb2R1bGUnLCBEb21Nb2R1bGUpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgTU9EVUxFX1NUWUxFX0xJTktfU0VMRUNUT1IgPSAnbGlua1tyZWw9aW1wb3J0XVt0eXBlfj1jc3NdJzsKICAgIGNvbnN0IElOQ0xVREVfQVRUUiA9ICdpbmNsdWRlJzsKICAgIGNvbnN0IFNIQURZX1VOU0NPUEVEX0FUVFIgPSAnc2hhZHktdW5zY29wZWQnOwoKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IG1vZHVsZUlkIC4KICAgICAqIEByZXR1cm4gez9Eb21Nb2R1bGV9IC4KICAgICAqLwogICAgZnVuY3Rpb24gaW1wb3J0TW9kdWxlKG1vZHVsZUlkKSB7CiAgICAgIHJldHVybiAvKiogQHR5cGUgez9Eb21Nb2R1bGV9ICovKERvbU1vZHVsZS5pbXBvcnQobW9kdWxlSWQpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUZvckltcG9ydChpbXBvcnREb2MpIHsKICAgICAgLy8gTk9URTogcG9seWZpbGwgYWZmb3JkYW5jZS4KICAgICAgLy8gdW5kZXIgdGhlIEhUTUxJbXBvcnRzIHBvbHlmaWxsLCB0aGVyZSB3aWxsIGJlIG5vICdib2R5JywKICAgICAgLy8gYnV0IHRoZSBpbXBvcnQgcHNldWRvLWRvYyBjYW4gYmUgdXNlZCBkaXJlY3RseS4KICAgICAgbGV0IGNvbnRhaW5lciA9IGltcG9ydERvYy5ib2R5ID8gaW1wb3J0RG9jLmJvZHkgOiBpbXBvcnREb2M7CiAgICAgIGNvbnN0IGltcG9ydENzcyA9IHJlc29sdmVDc3MoY29udGFpbmVyLnRleHRDb250ZW50LAogICAgICAgIGltcG9ydERvYy5iYXNlVVJJKTsKICAgICAgY29uc3Qgc3R5bGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzdHlsZScpOwogICAgICBzdHlsZS50ZXh0Q29udGVudCA9IGltcG9ydENzczsKICAgICAgcmV0dXJuIHN0eWxlOwogICAgfQoKCiAgICAvKioKICAgICAqIFJldHVybnMgYSBsaXN0IG9mIDxzdHlsZT4gZWxlbWVudHMgaW4gYSBzcGFjZS1zZXBhcmF0ZWQgbGlzdCBvZiBgZG9tLW1vZHVsZWBzLgogICAgICoKICAgICAqIEBmdW5jdGlvbgogICAgICogQHBhcmFtIHtzdHJpbmd9IG1vZHVsZUlkcyBMaXN0IG9mIGRvbS1tb2R1bGUgaWQncyB3aXRoaW4gd2hpY2ggdG8KICAgICAqIHNlYXJjaCBmb3IgY3NzLgogICAgICogQHJldHVybiB7IUFycmF5PCFIVE1MU3R5bGVFbGVtZW50Pn0gQXJyYXkgb2YgY29udGFpbmVkIDxzdHlsZT4gZWxlbWVudHMKICAgICAqLwogICAgZnVuY3Rpb24gc3R5bGVzRnJvbU1vZHVsZXMobW9kdWxlSWRzKSB7CiAgICAgY29uc3QgbW9kdWxlcyA9IG1vZHVsZUlkcy50cmltKCkuc3BsaXQoL1xzKy8pOwogICAgIGNvbnN0IHN0eWxlcyA9IFtdOwogICAgIGZvciAobGV0IGk9MDsgaSA8IG1vZHVsZXMubGVuZ3RoOyBpKyspIHsKICAgICAgIHN0eWxlcy5wdXNoKC4uLnN0eWxlc0Zyb21Nb2R1bGUobW9kdWxlc1tpXSkpOwogICAgIH0KICAgICByZXR1cm4gc3R5bGVzOwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyBhIGxpc3Qgb2YgPHN0eWxlPiBlbGVtZW50cyBpbiBhIGdpdmVuIGBkb20tbW9kdWxlYC4KICAgICAqIFN0eWxlcyBpbiBhIGBkb20tbW9kdWxlYCBjYW4gY29tZSBlaXRoZXIgZnJvbSBgPHN0eWxlPmBzIHdpdGhpbiB0aGUKICAgICAqIGZpcnN0IGA8dGVtcGxhdGU+YCwgb3IgZWxzZSBmcm9tIG9uZSBvciBtb3JlCiAgICAgKiBgPGxpbmsgcmVsPSJpbXBvcnQiIHR5cGU9ImNzcyI+YCBsaW5rcyBvdXRzaWRlIHRoZSB0ZW1wbGF0ZS4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gbW9kdWxlSWQgZG9tLW1vZHVsZSBpZCB0byBnYXRoZXIgc3R5bGVzIGZyb20KICAgICAqIEByZXR1cm4geyFBcnJheTwhSFRNTFN0eWxlRWxlbWVudD59IEFycmF5IG9mIGNvbnRhaW5lZCBzdHlsZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0eWxlc0Zyb21Nb2R1bGUobW9kdWxlSWQpIHsKICAgICAgY29uc3QgbSA9IGltcG9ydE1vZHVsZShtb2R1bGVJZCk7CgogICAgICBpZiAoIW0pIHsKICAgICAgICBjb25zb2xlLndhcm4oJ0NvdWxkIG5vdCBmaW5kIHN0eWxlIGRhdGEgaW4gbW9kdWxlIG5hbWVkJywgbW9kdWxlSWQpOwogICAgICAgIHJldHVybiBbXTsKICAgICAgfQoKICAgICAgaWYgKG0uX3N0eWxlcyA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgY29uc3Qgc3R5bGVzID0gW107CiAgICAgICAgLy8gbW9kdWxlIGltcG9ydHM6IDxsaW5rIHJlbD0iaW1wb3J0IiB0eXBlPSJjc3MiPgogICAgICAgIHN0eWxlcy5wdXNoKC4uLl9zdHlsZXNGcm9tTW9kdWxlSW1wb3J0cyhtKSk7CiAgICAgICAgLy8gaW5jbHVkZSBjc3MgZnJvbSB0aGUgZmlyc3QgdGVtcGxhdGUgaW4gdGhlIG1vZHVsZQogICAgICAgIGNvbnN0IHRlbXBsYXRlID0gLyoqIEB0eXBlIHs/SFRNTFRlbXBsYXRlRWxlbWVudH0gKi8oCiAgICAgICAgICAgIG0ucXVlcnlTZWxlY3RvcigndGVtcGxhdGUnKSk7CiAgICAgICAgaWYgKHRlbXBsYXRlKSB7CiAgICAgICAgICBzdHlsZXMucHVzaCguLi5zdHlsZXNGcm9tVGVtcGxhdGUodGVtcGxhdGUsCiAgICAgICAgICAgIC8qKiBAdHlwZSB7dGVtcGxhdGVXaXRoQXNzZXRQYXRofSAqLyhtKS5hc3NldHBhdGgpKTsKICAgICAgICB9CgogICAgICAgIG0uX3N0eWxlcyA9IHN0eWxlczsKICAgICAgfQoKICAgICAgcmV0dXJuIG0uX3N0eWxlczsKICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGA8c3R5bGU+YCBlbGVtZW50cyB3aXRoaW4gYSBnaXZlbiB0ZW1wbGF0ZS4KICAgICAqCiAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZSBUZW1wbGF0ZSB0byBnYXRoZXIgc3R5bGVzIGZyb20KICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gYmFzZVVSSSBiYXNlVVJJIGZvciBzdHlsZSBjb250ZW50CiAgICAgKiBAcmV0dXJuIHshQXJyYXk8IUhUTUxTdHlsZUVsZW1lbnQ+fSBBcnJheSBvZiBzdHlsZXMKICAgICAqLwogICAgZnVuY3Rpb24gc3R5bGVzRnJvbVRlbXBsYXRlKHRlbXBsYXRlLCBiYXNlVVJJKSB7CiAgICAgIGlmICghdGVtcGxhdGUuX3N0eWxlcykgewogICAgICAgIGNvbnN0IHN0eWxlcyA9IFtdOwogICAgICAgIC8vIGlmIGVsZW1lbnQgaXMgYSB0ZW1wbGF0ZSwgZ2V0IGNvbnRlbnQgZnJvbSBpdHMgLmNvbnRlbnQKICAgICAgICBjb25zdCBlJCA9IHRlbXBsYXRlLmNvbnRlbnQucXVlcnlTZWxlY3RvckFsbCgnc3R5bGUnKTsKICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBlJC5sZW5ndGg7IGkrKykgewogICAgICAgICAgbGV0IGUgPSBlJFtpXTsKICAgICAgICAgIC8vIHN1cHBvcnQgc3R5bGUgc2hhcmluZyBieSBhbGxvd2luZyBzdHlsZXMgdG8gImluY2x1ZGUiCiAgICAgICAgICAvLyBvdGhlciBkb20tbW9kdWxlcyB0aGF0IGNvbnRhaW4gc3R5bGluZwogICAgICAgICAgbGV0IGluY2x1ZGUgPSBlLmdldEF0dHJpYnV0ZShJTkNMVURFX0FUVFIpOwogICAgICAgICAgaWYgKGluY2x1ZGUpIHsKICAgICAgICAgICAgc3R5bGVzLnB1c2goLi4uc3R5bGVzRnJvbU1vZHVsZXMoaW5jbHVkZSkuZmlsdGVyKGZ1bmN0aW9uKGl0ZW0sIGluZGV4LCBzZWxmKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHNlbGYuaW5kZXhPZihpdGVtKSA9PT0gaW5kZXg7CiAgICAgICAgICAgIH0pKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChiYXNlVVJJKSB7CiAgICAgICAgICAgIGUudGV4dENvbnRlbnQgPQogICAgICAgICAgICAgICAgcmVzb2x2ZUNzcyhlLnRleHRDb250ZW50LCAvKiogQHR5cGUge3N0cmluZ30gKi8gKGJhc2VVUkkpKTsKICAgICAgICAgIH0KICAgICAgICAgIHN0eWxlcy5wdXNoKGUpOwogICAgICAgIH0KICAgICAgICB0ZW1wbGF0ZS5fc3R5bGVzID0gc3R5bGVzOwogICAgICB9CiAgICAgIHJldHVybiB0ZW1wbGF0ZS5fc3R5bGVzOwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyBhIGxpc3Qgb2YgPHN0eWxlPiBlbGVtZW50cyAgZnJvbSBzdHlsZXNoZWV0cyBsb2FkZWQgdmlhIGA8bGluayByZWw9ImltcG9ydCIgdHlwZT0iY3NzIj5gIGxpbmtzIHdpdGhpbiB0aGUgc3BlY2lmaWVkIGBkb20tbW9kdWxlYC4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gbW9kdWxlSWQgSWQgb2YgYGRvbS1tb2R1bGVgIHRvIGdhdGhlciBDU1MgZnJvbQogICAgICogQHJldHVybiB7IUFycmF5PCFIVE1MU3R5bGVFbGVtZW50Pn0gQXJyYXkgb2YgY29udGFpbmVkIHN0eWxlcy4KICAgICAqLwogICAgZnVuY3Rpb24gc3R5bGVzRnJvbU1vZHVsZUltcG9ydHMobW9kdWxlSWQpIHsKICAgICBsZXQgbSA9IGltcG9ydE1vZHVsZShtb2R1bGVJZCk7CiAgICAgcmV0dXJuIG0gPyBfc3R5bGVzRnJvbU1vZHVsZUltcG9ydHMobSkgOiBbXTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSBtb2R1bGUgZG9tLW1vZHVsZSBlbGVtZW50IHRoYXQgY291bGQgY29udGFpbiBgPGxpbmsgcmVsPSJpbXBvcnQiIHR5cGU9ImNzcyI+YCBzdHlsZXMKICAgICAqIEByZXR1cm4geyFBcnJheTwhSFRNTFN0eWxlRWxlbWVudD59IEFycmF5IG9mIGNvbnRhaW5lZCBzdHlsZXMKICAgICAqLwogICAgZnVuY3Rpb24gX3N0eWxlc0Zyb21Nb2R1bGVJbXBvcnRzKG1vZHVsZSkgewogICAgICBjb25zdCBzdHlsZXMgPSBbXTsKICAgICAgY29uc3QgcCQgPSBtb2R1bGUucXVlcnlTZWxlY3RvckFsbChNT0RVTEVfU1RZTEVfTElOS19TRUxFQ1RPUik7CiAgICAgIGZvciAobGV0IGk9MDsgaSA8IHAkLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgbGV0IHAgPSBwJFtpXTsKICAgICAgICBpZiAocC5pbXBvcnQpIHsKICAgICAgICAgIGNvbnN0IGltcG9ydERvYyA9IHAuaW1wb3J0OwogICAgICAgICAgY29uc3QgdW5zY29wZWQgPSBwLmhhc0F0dHJpYnV0ZShTSEFEWV9VTlNDT1BFRF9BVFRSKTsKICAgICAgICAgIGlmICh1bnNjb3BlZCAmJiAhaW1wb3J0RG9jLl91bnNjb3BlZFN0eWxlKSB7CiAgICAgICAgICAgIGNvbnN0IHN0eWxlID0gc3R5bGVGb3JJbXBvcnQoaW1wb3J0RG9jKTsKICAgICAgICAgICAgc3R5bGUuc2V0QXR0cmlidXRlKFNIQURZX1VOU0NPUEVEX0FUVFIsICcnKTsKICAgICAgICAgICAgaW1wb3J0RG9jLl91bnNjb3BlZFN0eWxlID0gc3R5bGU7CiAgICAgICAgICB9IGVsc2UgaWYgKCFpbXBvcnREb2MuX3N0eWxlKSB7CiAgICAgICAgICAgIGltcG9ydERvYy5fc3R5bGUgPSBzdHlsZUZvckltcG9ydChpbXBvcnREb2MpOwogICAgICAgICAgfQogICAgICAgICAgc3R5bGVzLnB1c2godW5zY29wZWQgPyBpbXBvcnREb2MuX3Vuc2NvcGVkU3R5bGUgOiBpbXBvcnREb2MuX3N0eWxlKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHN0eWxlczsKICAgIH0KCiAgICAvKioKICAgICAqCiAgICAgKiBSZXR1cm5zIENTUyB0ZXh0IG9mIHN0eWxlcyBpbiBhIHNwYWNlLXNlcGFyYXRlZCBsaXN0IG9mIGBkb20tbW9kdWxlYHMuCiAgICAgKiBOb3RlOiBUaGlzIG1ldGhvZCBpcyBkZXByZWNhdGVkLCB1c2UgYHN0eWxlc0Zyb21Nb2R1bGVzYCBpbnN0ZWFkLgogICAgICoKICAgICAqIEBkZXByZWNhdGVkCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gbW9kdWxlSWRzIExpc3Qgb2YgZG9tLW1vZHVsZSBpZCdzIHdpdGhpbiB3aGljaCB0bwogICAgICogc2VhcmNoIGZvciBjc3MuCiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IENvbmNhdGVuYXRlZCBDU1MgY29udGVudCBmcm9tIHNwZWNpZmllZCBgZG9tLW1vZHVsZWBzCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNzc0Zyb21Nb2R1bGVzKG1vZHVsZUlkcykgewogICAgIGxldCBtb2R1bGVzID0gbW9kdWxlSWRzLnRyaW0oKS5zcGxpdCgvXHMrLyk7CiAgICAgbGV0IGNzc1RleHQgPSAnJzsKICAgICBmb3IgKGxldCBpPTA7IGkgPCBtb2R1bGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICBjc3NUZXh0ICs9IGNzc0Zyb21Nb2R1bGUobW9kdWxlc1tpXSk7CiAgICAgfQogICAgIHJldHVybiBjc3NUZXh0OwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyBDU1MgdGV4dCBvZiBzdHlsZXMgaW4gYSBnaXZlbiBgZG9tLW1vZHVsZWAuICBDU1MgaW4gYSBgZG9tLW1vZHVsZWAKICAgICAqIGNhbiBjb21lIGVpdGhlciBmcm9tIGA8c3R5bGU+YHMgd2l0aGluIHRoZSBmaXJzdCBgPHRlbXBsYXRlPmAsIG9yIGVsc2UKICAgICAqIGZyb20gb25lIG9yIG1vcmUgYDxsaW5rIHJlbD0iaW1wb3J0IiB0eXBlPSJjc3MiPmAgbGlua3Mgb3V0c2lkZSB0aGUKICAgICAqIHRlbXBsYXRlLgogICAgICoKICAgICAqIEFueSBgPHN0eWxlcz5gIHByb2Nlc3NlZCBhcmUgcmVtb3ZlZCBmcm9tIHRoZWlyIG9yaWdpbmFsIGxvY2F0aW9uLgogICAgICogTm90ZTogVGhpcyBtZXRob2QgaXMgZGVwcmVjYXRlZCwgdXNlIGBzdHlsZUZyb21Nb2R1bGVgIGluc3RlYWQuCiAgICAgKgogICAgICogQGRlcHJlY2F0ZWQKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBtb2R1bGVJZCBkb20tbW9kdWxlIGlkIHRvIGdhdGhlciBzdHlsZXMgZnJvbQogICAgICogQHJldHVybiB7c3RyaW5nfSBDb25jYXRlbmF0ZWQgQ1NTIGNvbnRlbnQgZnJvbSBzcGVjaWZpZWQgYGRvbS1tb2R1bGVgCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNzc0Zyb21Nb2R1bGUobW9kdWxlSWQpIHsKICAgICAgbGV0IG0gPSBpbXBvcnRNb2R1bGUobW9kdWxlSWQpOwogICAgICBpZiAobSAmJiBtLl9jc3NUZXh0ID09PSB1bmRlZmluZWQpIHsKICAgICAgICAvLyBtb2R1bGUgaW1wb3J0czogPGxpbmsgcmVsPSJpbXBvcnQiIHR5cGU9ImNzcyI+CiAgICAgICAgbGV0IGNzc1RleHQgPSBfY3NzRnJvbU1vZHVsZUltcG9ydHMobSk7CiAgICAgICAgLy8gaW5jbHVkZSBjc3MgZnJvbSB0aGUgZmlyc3QgdGVtcGxhdGUgaW4gdGhlIG1vZHVsZQogICAgICAgIGxldCB0ID0gLyoqIEB0eXBlIHs/SFRNTFRlbXBsYXRlRWxlbWVudH0gKi8obS5xdWVyeVNlbGVjdG9yKCd0ZW1wbGF0ZScpKTsKICAgICAgICBpZiAodCkgewogICAgICAgICAgY3NzVGV4dCArPSBjc3NGcm9tVGVtcGxhdGUodCwKICAgICAgICAgICAgLyoqIEB0eXBlIHt0ZW1wbGF0ZVdpdGhBc3NldFBhdGh9ICovKG0pLmFzc2V0cGF0aCk7CiAgICAgICAgfQogICAgICAgIG0uX2Nzc1RleHQgPSBjc3NUZXh0IHx8IG51bGw7CiAgICAgIH0KICAgICAgaWYgKCFtKSB7CiAgICAgICAgY29uc29sZS53YXJuKCdDb3VsZCBub3QgZmluZCBzdHlsZSBkYXRhIGluIG1vZHVsZSBuYW1lZCcsIG1vZHVsZUlkKTsKICAgICAgfQogICAgICByZXR1cm4gbSAmJiBtLl9jc3NUZXh0IHx8ICcnOwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyBDU1MgdGV4dCBvZiBgPHN0eWxlcz5gIHdpdGhpbiBhIGdpdmVuIHRlbXBsYXRlLgogICAgICoKICAgICAqIEFueSBgPHN0eWxlcz5gIHByb2Nlc3NlZCBhcmUgcmVtb3ZlZCBmcm9tIHRoZWlyIG9yaWdpbmFsIGxvY2F0aW9uLgogICAgICogTm90ZTogVGhpcyBtZXRob2QgaXMgZGVwcmVjYXRlZCwgdXNlIGBzdHlsZUZyb21UZW1wbGF0ZWAgaW5zdGVhZC4KICAgICAqCiAgICAgKiBAZGVwcmVjYXRlZAogICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUgVGVtcGxhdGUgdG8gZ2F0aGVyIHN0eWxlcyBmcm9tCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gYmFzZVVSSSBCYXNlIFVSSSB0byByZXNvbHZlIHRoZSBVUkwgYWdhaW5zdAogICAgICogQHJldHVybiB7c3RyaW5nfSBDb25jYXRlbmF0ZWQgQ1NTIGNvbnRlbnQgZnJvbSBzcGVjaWZpZWQgdGVtcGxhdGUKICAgICAqLwogICAgZnVuY3Rpb24gY3NzRnJvbVRlbXBsYXRlKHRlbXBsYXRlLCBiYXNlVVJJKSB7CiAgICAgIGxldCBjc3NUZXh0ID0gJyc7CiAgICAgIGNvbnN0IGUkID0gc3R5bGVzRnJvbVRlbXBsYXRlKHRlbXBsYXRlLCBiYXNlVVJJKTsKICAgICAgLy8gaWYgZWxlbWVudCBpcyBhIHRlbXBsYXRlLCBnZXQgY29udGVudCBmcm9tIGl0cyAuY29udGVudAogICAgICBmb3IgKGxldCBpPTA7IGkgPCBlJC5sZW5ndGg7IGkrKykgewogICAgICAgIGxldCBlID0gZSRbaV07CiAgICAgICAgaWYgKGUucGFyZW50Tm9kZSkgewogICAgICAgICAgZS5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKGUpOwogICAgICAgIH0KICAgICAgICBjc3NUZXh0ICs9IGUudGV4dENvbnRlbnQ7CiAgICAgIH0KICAgICAgcmV0dXJuIGNzc1RleHQ7CiAgICB9CgogICAgLyoqCiAgICAgKiBAZGVwcmVjYXRlZAogICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IG1vZHVsZSBkb20tbW9kdWxlIGVsZW1lbnQgdGhhdCBjb3VsZCBjb250YWluIGA8bGluayByZWw9ImltcG9ydCIgdHlwZT0iY3NzIj5gIHN0eWxlcwogICAgICogQHJldHVybiB7c3RyaW5nfSBDb25jYXRlbmF0ZWQgQ1NTIGNvbnRlbnQgZnJvbSBsaW5rcyBpbiB0aGUgZG9tLW1vZHVsZQogICAgICovCiAgICBmdW5jdGlvbiBfY3NzRnJvbU1vZHVsZUltcG9ydHMobW9kdWxlKSB7CiAgICAgIGxldCBjc3NUZXh0ID0gJyc7CiAgICAgIGxldCBzdHlsZXMgPSBfc3R5bGVzRnJvbU1vZHVsZUltcG9ydHMobW9kdWxlKTsKICAgICAgZm9yIChsZXQgaT0wOyBpIDwgc3R5bGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgY3NzVGV4dCArPSBzdHlsZXNbaV0udGV4dENvbnRlbnQ7CiAgICAgIH0KICAgICAgcmV0dXJuIGNzc1RleHQ7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKiBlc2xpbnQtZGlzYWJsZSB2YWxpZC1qc2RvYyAqLwogICAgLyoqCiAgICAgKiBOb2RlIHdyYXBwZXIgdG8gZW5zdXJlIFNoYWRvd0RPTSBzYWZlIG9wZXJhdGlvbiByZWdhcmRsZXNzIG9mIHBvbHlmaWxsCiAgICAgKiBwcmVzZW5jZSBvciBtb2RlLiBOb3RlIHRoYXQgd2l0aCB0aGUgaW50cm9kdWN0aW9uIG9mIGBTaGFkeURPTS5ub1BhdGNoYCwKICAgICAqIGEgbm9kZSB3cmFwcGVyIG11c3QgYmUgdXNlZCB0byBhY2Nlc3MgU2hhZG93RE9NIEFQSS4KICAgICAqIFRoaXMgaXMgc2ltaWxhciB0byB1c2luZyBgUG9seW1lci5kb21gIGJ1dCByZWxpZXMgZXhjbHVzaXZlbHkKICAgICAqIG9uIHRoZSBwcmVzZW5jZSBvZiB0aGUgU2hhZHlET00gcG9seWZpbGwgcmF0aGVyIHRoYW4gcmVxdWlyaW5nIHRoZSBsb2FkaW5nCiAgICAgKiBvZiBsZWdhY3kgKFBvbHltZXIuZG9tKSBBUEkuCiAgICAgKiBAdHlwZSB7ZnVuY3Rpb24oTm9kZSk6Tm9kZX0KICAgICAqLwogICAgY29uc3Qgd3JhcCA9ICh3aW5kb3dbJ1NoYWR5RE9NJ10gJiYgd2luZG93WydTaGFkeURPTSddWydub1BhdGNoJ10gJiYgd2luZG93WydTaGFkeURPTSddWyd3cmFwJ10pID8KICAgICAgd2luZG93WydTaGFkeURPTSddWyd3cmFwJ10gOgogICAgICAod2luZG93WydTaGFkeURPTSddID8gKG4pID0+IFNoYWR5RE9NWydwYXRjaCddKG4pIDogKG4pID0+IG4pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBNb2R1bGUgd2l0aCB1dGlsaXRpZXMgZm9yIG1hbmlwdWxhdGluZyBzdHJ1Y3R1cmVkIGRhdGEgcGF0aCBzdHJpbmdzLgogICAgICoKICAgICAqIEBzdW1tYXJ5IE1vZHVsZSB3aXRoIHV0aWxpdGllcyBmb3IgbWFuaXB1bGF0aW5nIHN0cnVjdHVyZWQgZGF0YSBwYXRoIHN0cmluZ3MuCiAgICAgKi8KCiAgICAvKioKICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgZ2l2ZW4gc3RyaW5nIGlzIGEgc3RydWN0dXJlZCBkYXRhIHBhdGggKGhhcyBkb3RzKS4KICAgICAqCiAgICAgKiBFeGFtcGxlOgogICAgICoKICAgICAqIGBgYAogICAgICogaXNQYXRoKCdmb28uYmFyLmJheicpIC8vIHRydWUKICAgICAqIGlzUGF0aCgnZm9vJykgICAgICAgICAvLyBmYWxzZQogICAgICogYGBgCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggUGF0aCBzdHJpbmcKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgdGhlIHN0cmluZyBjb250YWluZWQgb25lIG9yIG1vcmUgZG90cwogICAgICovCiAgICBmdW5jdGlvbiBpc1BhdGgocGF0aCkgewogICAgICByZXR1cm4gcGF0aC5pbmRleE9mKCcuJykgPj0gMDsKICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIHJvb3QgcHJvcGVydHkgbmFtZSBmb3IgdGhlIGdpdmVuIHBhdGguCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGAKICAgICAqIHJvb3QoJ2Zvby5iYXIuYmF6JykgLy8gJ2ZvbycKICAgICAqIHJvb3QoJ2ZvbycpICAgICAgICAgLy8gJ2ZvbycKICAgICAqIGBgYAogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFBhdGggc3RyaW5nCiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IFJvb3QgcHJvcGVydHkgbmFtZQogICAgICovCiAgICBmdW5jdGlvbiByb290KHBhdGgpIHsKICAgICAgbGV0IGRvdEluZGV4ID0gcGF0aC5pbmRleE9mKCcuJyk7CiAgICAgIGlmIChkb3RJbmRleCA9PT0gLTEpIHsKICAgICAgICByZXR1cm4gcGF0aDsKICAgICAgfQogICAgICByZXR1cm4gcGF0aC5zbGljZSgwLCBkb3RJbmRleCk7CiAgICB9CgogICAgLyoqCiAgICAgKiBHaXZlbiBgYmFzZWAgaXMgYGZvby5iYXJgLCBgZm9vYCBpcyBhbiBhbmNlc3RvciwgYGZvby5iYXJgIGlzIG5vdAogICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBnaXZlbiBwYXRoIGlzIGFuIGFuY2VzdG9yIG9mIHRoZSBiYXNlIHBhdGguCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGAKICAgICAqIGlzQW5jZXN0b3IoJ2Zvby5iYXInLCAnZm9vJykgICAgICAgICAvLyB0cnVlCiAgICAgKiBpc0FuY2VzdG9yKCdmb28uYmFyJywgJ2Zvby5iYXInKSAgICAgLy8gZmFsc2UKICAgICAqIGlzQW5jZXN0b3IoJ2Zvby5iYXInLCAnZm9vLmJhci5iYXonKSAvLyBmYWxzZQogICAgICogYGBgCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmd9IGJhc2UgUGF0aCBzdHJpbmcgdG8gdGVzdCBhZ2FpbnN0LgogICAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggUGF0aCBzdHJpbmcgdG8gdGVzdC4KICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgYHBhdGhgIGlzIGFuIGFuY2VzdG9yIG9mIGBiYXNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gaXNBbmNlc3RvcihiYXNlLCBwYXRoKSB7CiAgICAgIC8vICAgICBiYXNlLnN0YXJ0c1dpdGgocGF0aCArICcuJyk7CiAgICAgIHJldHVybiBiYXNlLmluZGV4T2YocGF0aCArICcuJykgPT09IDA7CiAgICB9CgogICAgLyoqCiAgICAgKiBHaXZlbiBgYmFzZWAgaXMgYGZvby5iYXJgLCBgZm9vLmJhci5iYXpgIGlzIGFuIGRlc2NlbmRhbnQKICAgICAqCiAgICAgKiBFeGFtcGxlOgogICAgICoKICAgICAqIGBgYAogICAgICogaXNEZXNjZW5kYW50KCdmb28uYmFyJywgJ2Zvby5iYXIuYmF6JykgLy8gdHJ1ZQogICAgICogaXNEZXNjZW5kYW50KCdmb28uYmFyJywgJ2Zvby5iYXInKSAgICAgLy8gZmFsc2UKICAgICAqIGlzRGVzY2VuZGFudCgnZm9vLmJhcicsICdmb28nKSAgICAgICAgIC8vIGZhbHNlCiAgICAgKiBgYGAKICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gYmFzZSBQYXRoIHN0cmluZyB0byB0ZXN0IGFnYWluc3QuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBQYXRoIHN0cmluZyB0byB0ZXN0LgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBgcGF0aGAgaXMgYSBkZXNjZW5kYW50IG9mIGBiYXNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gaXNEZXNjZW5kYW50KGJhc2UsIHBhdGgpIHsKICAgICAgLy8gICAgIHBhdGguc3RhcnRzV2l0aChiYXNlICsgJy4nKTsKICAgICAgcmV0dXJuIHBhdGguaW5kZXhPZihiYXNlICsgJy4nKSA9PT0gMDsKICAgIH0KCiAgICAvKioKICAgICAqIFJlcGxhY2VzIGEgcHJldmlvdXMgYmFzZSBwYXRoIHdpdGggYSBuZXcgYmFzZSBwYXRoLCBwcmVzZXJ2aW5nIHRoZQogICAgICogcmVtYWluZGVyIG9mIHRoZSBwYXRoLgogICAgICoKICAgICAqIFVzZXIgbXVzdCBlbnN1cmUgYHBhdGhgIGhhcyBhIHByZWZpeCBvZiBgYmFzZWAuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGAKICAgICAqIHRyYW5zbGF0ZSgnZm9vLmJhcicsICd6b3QnLCAnZm9vLmJhci5iYXonKSAvLyAnem90LmJheicKICAgICAqIGBgYAogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBiYXNlIEN1cnJlbnQgYmFzZSBzdHJpbmcgdG8gcmVtb3ZlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gbmV3QmFzZSBOZXcgYmFzZSBzdHJpbmcgdG8gcmVwbGFjZSB3aXRoCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBQYXRoIHRvIHRyYW5zbGF0ZQogICAgICogQHJldHVybiB7c3RyaW5nfSBUcmFuc2xhdGVkIHN0cmluZwogICAgICovCiAgICBmdW5jdGlvbiB0cmFuc2xhdGUoYmFzZSwgbmV3QmFzZSwgcGF0aCkgewogICAgICByZXR1cm4gbmV3QmFzZSArIHBhdGguc2xpY2UoYmFzZS5sZW5ndGgpOwogICAgfQoKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IGJhc2UgUGF0aCBzdHJpbmcgdG8gdGVzdCBhZ2FpbnN0CiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBQYXRoIHN0cmluZyB0byB0ZXN0CiAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIGBwYXRoYCBpcyBlcXVhbCB0byBgYmFzZWAKICAgICAqLwogICAgZnVuY3Rpb24gbWF0Y2hlcyhiYXNlLCBwYXRoKSB7CiAgICAgIHJldHVybiAoYmFzZSA9PT0gcGF0aCkgfHwKICAgICAgICAgICAgIGlzQW5jZXN0b3IoYmFzZSwgcGF0aCkgfHwKICAgICAgICAgICAgIGlzRGVzY2VuZGFudChiYXNlLCBwYXRoKTsKICAgIH0KCiAgICAvKioKICAgICAqIENvbnZlcnRzIGFycmF5LWJhc2VkIHBhdGhzIHRvIGZsYXR0ZW5lZCBwYXRoLiAgU3RyaW5nLWJhc2VkIHBhdGhzCiAgICAgKiBhcmUgcmV0dXJuZWQgYXMtaXMuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGAKICAgICAqIG5vcm1hbGl6ZShbJ2Zvby5iYXInLCAwLCAnYmF6J10pICAvLyAnZm9vLmJhci4wLmJheicKICAgICAqIG5vcm1hbGl6ZSgnZm9vLmJhci4wLmJheicpICAgICAgICAvLyAnZm9vLmJhci4wLmJheicKICAgICAqIGBgYAogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nIHwgIUFycmF5PHN0cmluZ3xudW1iZXI+fSBwYXRoIElucHV0IHBhdGgKICAgICAqIEByZXR1cm4ge3N0cmluZ30gRmxhdHRlbmVkIHBhdGgKICAgICAqLwogICAgZnVuY3Rpb24gbm9ybWFsaXplKHBhdGgpIHsKICAgICAgaWYgKEFycmF5LmlzQXJyYXkocGF0aCkpIHsKICAgICAgICBsZXQgcGFydHMgPSBbXTsKICAgICAgICBmb3IgKGxldCBpPTA7IGk8cGF0aC5sZW5ndGg7IGkrKykgewogICAgICAgICAgbGV0IGFyZ3MgPSBwYXRoW2ldLnRvU3RyaW5nKCkuc3BsaXQoJy4nKTsKICAgICAgICAgIGZvciAobGV0IGo9MDsgajxhcmdzLmxlbmd0aDsgaisrKSB7CiAgICAgICAgICAgIHBhcnRzLnB1c2goYXJnc1tqXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBwYXJ0cy5qb2luKCcuJyk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHBhdGg7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFNwbGl0cyBhIHBhdGggaW50byBhbiBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcy4gQWNjZXB0cyBlaXRoZXIgYXJyYXlzCiAgICAgKiBvZiBwYXRoIHBhcnRzIG9yIHN0cmluZ3MuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGAKICAgICAqIHNwbGl0KFsnZm9vLmJhcicsIDAsICdiYXonXSkgIC8vIFsnZm9vJywgJ2JhcicsICcwJywgJ2JheiddCiAgICAgKiBzcGxpdCgnZm9vLmJhci4wLmJheicpICAgICAgICAvLyBbJ2ZvbycsICdiYXInLCAnMCcsICdiYXonXQogICAgICogYGBgCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmcgfCAhQXJyYXk8c3RyaW5nfG51bWJlcj59IHBhdGggSW5wdXQgcGF0aAogICAgICogQHJldHVybiB7IUFycmF5PHN0cmluZz59IEFycmF5IG9mIHBhdGggcGFydHMKICAgICAqIEBzdXBwcmVzcyB7Y2hlY2tUeXBlc30KICAgICAqLwogICAgZnVuY3Rpb24gc3BsaXQocGF0aCkgewogICAgICBpZiAoQXJyYXkuaXNBcnJheShwYXRoKSkgewogICAgICAgIHJldHVybiBub3JtYWxpemUocGF0aCkuc3BsaXQoJy4nKTsKICAgICAgfQogICAgICByZXR1cm4gcGF0aC50b1N0cmluZygpLnNwbGl0KCcuJyk7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZWFkcyBhIHZhbHVlIGZyb20gYSBwYXRoLiAgSWYgYW55IHN1Yi1wcm9wZXJ0eSBpbiB0aGUgcGF0aCBpcyBgdW5kZWZpbmVkYCwKICAgICAqIHRoaXMgbWV0aG9kIHJldHVybnMgYHVuZGVmaW5lZGAgKHdpbGwgbmV2ZXIgdGhyb3cuCiAgICAgKgogICAgICogQHBhcmFtIHtPYmplY3R9IHJvb3QgT2JqZWN0IGZyb20gd2hpY2ggdG8gZGVyZWZlcmVuY2UgcGF0aCBmcm9tCiAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxzdHJpbmd8bnVtYmVyPn0gcGF0aCBQYXRoIHRvIHJlYWQKICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gaW5mbyBJZiBhbiBvYmplY3QgaXMgcHJvdmlkZWQgdG8gYGluZm9gLCB0aGUgbm9ybWFsaXplZAogICAgICogIChmbGF0dGVuZWQpIHBhdGggd2lsbCBiZSBzZXQgdG8gYGluZm8ucGF0aGAuCiAgICAgKiBAcmV0dXJuIHsqfSBWYWx1ZSBhdCBwYXRoLCBvciBgdW5kZWZpbmVkYCBpZiB0aGUgcGF0aCBjb3VsZCBub3QgYmUKICAgICAqICBmdWxseSBkZXJlZmVyZW5jZWQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldChyb290LCBwYXRoLCBpbmZvKSB7CiAgICAgIGxldCBwcm9wID0gcm9vdDsKICAgICAgbGV0IHBhcnRzID0gc3BsaXQocGF0aCk7CiAgICAgIC8vIExvb3Agb3ZlciBwYXRoIHBhcnRzWzAuLm4tMV0gYW5kIGRlcmVmZXJlbmNlCiAgICAgIGZvciAobGV0IGk9MDsgaTxwYXJ0cy5sZW5ndGg7IGkrKykgewogICAgICAgIGlmICghcHJvcCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBsZXQgcGFydCA9IHBhcnRzW2ldOwogICAgICAgIHByb3AgPSBwcm9wW3BhcnRdOwogICAgICB9CiAgICAgIGlmIChpbmZvKSB7CiAgICAgICAgaW5mby5wYXRoID0gcGFydHMuam9pbignLicpOwogICAgICB9CiAgICAgIHJldHVybiBwcm9wOwogICAgfQoKICAgIC8qKgogICAgICogU2V0cyBhIHZhbHVlIHRvIGEgcGF0aC4gIElmIGFueSBzdWItcHJvcGVydHkgaW4gdGhlIHBhdGggaXMgYHVuZGVmaW5lZGAsCiAgICAgKiB0aGlzIG1ldGhvZCB3aWxsIG5vLW9wLgogICAgICoKICAgICAqIEBwYXJhbSB7T2JqZWN0fSByb290IE9iamVjdCBmcm9tIHdoaWNoIHRvIGRlcmVmZXJlbmNlIHBhdGggZnJvbQogICAgICogQHBhcmFtIHtzdHJpbmcgfCAhQXJyYXk8c3RyaW5nfG51bWJlcj59IHBhdGggUGF0aCB0byBzZXQKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVmFsdWUgdG8gc2V0IHRvIHBhdGgKICAgICAqIEByZXR1cm4ge3N0cmluZyB8IHVuZGVmaW5lZH0gVGhlIG5vcm1hbGl6ZWQgdmVyc2lvbiBvZiB0aGUgaW5wdXQgcGF0aAogICAgICovCiAgICBmdW5jdGlvbiBzZXQocm9vdCwgcGF0aCwgdmFsdWUpIHsKICAgICAgbGV0IHByb3AgPSByb290OwogICAgICBsZXQgcGFydHMgPSBzcGxpdChwYXRoKTsKICAgICAgbGV0IGxhc3QgPSBwYXJ0c1twYXJ0cy5sZW5ndGgtMV07CiAgICAgIGlmIChwYXJ0cy5sZW5ndGggPiAxKSB7CiAgICAgICAgLy8gTG9vcCBvdmVyIHBhdGggcGFydHNbMC4ubi0yXSBhbmQgZGVyZWZlcmVuY2UKICAgICAgICBmb3IgKGxldCBpPTA7IGk8cGFydHMubGVuZ3RoLTE7IGkrKykgewogICAgICAgICAgbGV0IHBhcnQgPSBwYXJ0c1tpXTsKICAgICAgICAgIHByb3AgPSBwcm9wW3BhcnRdOwogICAgICAgICAgaWYgKCFwcm9wKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gU2V0IHZhbHVlIHRvIG9iamVjdCBhdCBlbmQgb2YgcGF0aAogICAgICAgIHByb3BbbGFzdF0gPSB2YWx1ZTsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBTaW1wbGUgcHJvcGVydHkgc2V0CiAgICAgICAgcHJvcFtwYXRoXSA9IHZhbHVlOwogICAgICB9CiAgICAgIHJldHVybiBwYXJ0cy5qb2luKCcuJyk7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCBjYXNlTWFwID0ge307CiAgICBjb25zdCBEQVNIX1RPX0NBTUVMID0gLy1bYS16XS9nOwogICAgY29uc3QgQ0FNRUxfVE9fREFTSCA9IC8oW0EtWl0pL2c7CgogICAgLyoqCiAgICAgKiBAZmlsZW92ZXJ2aWV3IE1vZHVsZSB3aXRoIHV0aWxpdGllcyBmb3IgY29udmVydGluZyBiZXR3ZWVuICJkYXNoLWNhc2UiIGFuZAogICAgICogImNhbWVsQ2FzZSIgaWRlbnRpZmllcnMuCiAgICAgKi8KCiAgICAvKioKICAgICAqIENvbnZlcnRzICJkYXNoLWNhc2UiIGlkZW50aWZpZXIgKGUuZy4gYGZvby1iYXItYmF6YCkgdG8gImNhbWVsQ2FzZSIKICAgICAqIChlLmcuIGBmb29CYXJCYXpgKS4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZGFzaCBEYXNoLWNhc2UgaWRlbnRpZmllcgogICAgICogQHJldHVybiB7c3RyaW5nfSBDYW1lbC1jYXNlIHJlcHJlc2VudGF0aW9uIG9mIHRoZSBpZGVudGlmaWVyCiAgICAgKi8KICAgIGZ1bmN0aW9uIGRhc2hUb0NhbWVsQ2FzZShkYXNoKSB7CiAgICAgIHJldHVybiBjYXNlTWFwW2Rhc2hdIHx8ICgKICAgICAgICBjYXNlTWFwW2Rhc2hdID0gZGFzaC5pbmRleE9mKCctJykgPCAwID8gZGFzaCA6IGRhc2gucmVwbGFjZShEQVNIX1RPX0NBTUVMLAogICAgICAgICAgKG0pID0+IG1bMV0udG9VcHBlckNhc2UoKQogICAgICAgICkKICAgICAgKTsKICAgIH0KCiAgICAvKioKICAgICAqIENvbnZlcnRzICJjYW1lbENhc2UiIGlkZW50aWZpZXIgKGUuZy4gYGZvb0JhckJhemApIHRvICJkYXNoLWNhc2UiCiAgICAgKiAoZS5nLiBgZm9vLWJhci1iYXpgKS4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2FtZWwgQ2FtZWwtY2FzZSBpZGVudGlmaWVyCiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IERhc2gtY2FzZSByZXByZXNlbnRhdGlvbiBvZiB0aGUgaWRlbnRpZmllcgogICAgICovCiAgICBmdW5jdGlvbiBjYW1lbFRvRGFzaENhc2UoY2FtZWwpIHsKICAgICAgcmV0dXJuIGNhc2VNYXBbY2FtZWxdIHx8ICgKICAgICAgICBjYXNlTWFwW2NhbWVsXSA9IGNhbWVsLnJlcGxhY2UoQ0FNRUxfVE9fREFTSCwgJy0kMScpLnRvTG93ZXJDYXNlKCkKICAgICAgKTsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8vIE1pY3JvdGFzayBpbXBsZW1lbnRlZCB1c2luZyBNdXRhdGlvbiBPYnNlcnZlcgogICAgbGV0IG1pY3JvdGFza0N1cnJIYW5kbGUgPSAwOwogICAgbGV0IG1pY3JvdGFza0xhc3RIYW5kbGUgPSAwOwogICAgbGV0IG1pY3JvdGFza0NhbGxiYWNrcyA9IFtdOwogICAgbGV0IG1pY3JvdGFza05vZGVDb250ZW50ID0gMDsKICAgIGxldCBtaWNyb3Rhc2tTY2hlZHVsZWQgPSBmYWxzZTsKICAgIGxldCBtaWNyb3Rhc2tOb2RlID0gZG9jdW1lbnQuY3JlYXRlVGV4dE5vZGUoJycpOwogICAgbmV3IHdpbmRvdy5NdXRhdGlvbk9ic2VydmVyKG1pY3JvdGFza0ZsdXNoKS5vYnNlcnZlKG1pY3JvdGFza05vZGUsIHtjaGFyYWN0ZXJEYXRhOiB0cnVlfSk7CgogICAgZnVuY3Rpb24gbWljcm90YXNrRmx1c2goKSB7CiAgICAgIG1pY3JvdGFza1NjaGVkdWxlZCA9IGZhbHNlOwogICAgICBjb25zdCBsZW4gPSBtaWNyb3Rhc2tDYWxsYmFja3MubGVuZ3RoOwogICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGxlbjsgaSsrKSB7CiAgICAgICAgbGV0IGNiID0gbWljcm90YXNrQ2FsbGJhY2tzW2ldOwogICAgICAgIGlmIChjYikgewogICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgY2IoKTsKICAgICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7IHRocm93IGU7IH0pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICBtaWNyb3Rhc2tDYWxsYmFja3Muc3BsaWNlKDAsIGxlbik7CiAgICAgIG1pY3JvdGFza0xhc3RIYW5kbGUgKz0gbGVuOwogICAgfQoKICAgIC8qKgogICAgICogQXN5bmMgaW50ZXJmYWNlIHdyYXBwZXIgYXJvdW5kIGBzZXRUaW1lb3V0YC4KICAgICAqCiAgICAgKiBAbmFtZXNwYWNlCiAgICAgKiBAc3VtbWFyeSBBc3luYyBpbnRlcmZhY2Ugd3JhcHBlciBhcm91bmQgYHNldFRpbWVvdXRgLgogICAgICovCiAgICBjb25zdCB0aW1lT3V0ID0gewogICAgICAvKioKICAgICAgICogUmV0dXJucyBhIHN1Yi1tb2R1bGUgd2l0aCB0aGUgYXN5bmMgaW50ZXJmYWNlIHByb3ZpZGluZyB0aGUgcHJvdmlkZWQKICAgICAgICogZGVsYXkuCiAgICAgICAqCiAgICAgICAqIEBtZW1iZXJvZiB0aW1lT3V0CiAgICAgICAqIEBwYXJhbSB7bnVtYmVyPX0gZGVsYXkgVGltZSB0byB3YWl0IGJlZm9yZSBjYWxsaW5nIGNhbGxiYWNrcyBpbiBtcwogICAgICAgKiBAcmV0dXJuIHshQXN5bmNJbnRlcmZhY2V9IEFuIGFzeW5jIHRpbWVvdXQgaW50ZXJmYWNlCiAgICAgICAqLwogICAgICBhZnRlcihkZWxheSkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICBydW4oZm4pIHsgcmV0dXJuIHdpbmRvdy5zZXRUaW1lb3V0KGZuLCBkZWxheSk7IH0sCiAgICAgICAgICBjYW5jZWwoaGFuZGxlKSB7CiAgICAgICAgICAgIHdpbmRvdy5jbGVhclRpbWVvdXQoaGFuZGxlKTsKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICB9LAogICAgICAvKioKICAgICAgICogRW5xdWV1ZXMgYSBmdW5jdGlvbiBjYWxsZWQgaW4gdGhlIG5leHQgdGFzay4KICAgICAgICoKICAgICAgICogQG1lbWJlcm9mIHRpbWVPdXQKICAgICAgICogQHBhcmFtIHshRnVuY3Rpb259IGZuIENhbGxiYWNrIHRvIHJ1bgogICAgICAgKiBAcGFyYW0ge251bWJlcj19IGRlbGF5IERlbGF5IGluIG1pbGxpc2Vjb25kcwogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9IEhhbmRsZSB1c2VkIGZvciBjYW5jZWxpbmcgdGFzawogICAgICAgKi8KICAgICAgcnVuKGZuLCBkZWxheSkgewogICAgICAgIHJldHVybiB3aW5kb3cuc2V0VGltZW91dChmbiwgZGVsYXkpOwogICAgICB9LAogICAgICAvKioKICAgICAgICogQ2FuY2VscyBhIHByZXZpb3VzbHkgZW5xdWV1ZWQgYHRpbWVPdXRgIGNhbGxiYWNrLgogICAgICAgKgogICAgICAgKiBAbWVtYmVyb2YgdGltZU91dAogICAgICAgKiBAcGFyYW0ge251bWJlcn0gaGFuZGxlIEhhbmRsZSByZXR1cm5lZCBmcm9tIGBydW5gIG9mIGNhbGxiYWNrIHRvIGNhbmNlbAogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgY2FuY2VsKGhhbmRsZSkgewogICAgICAgIHdpbmRvdy5jbGVhclRpbWVvdXQoaGFuZGxlKTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgICAqIEFzeW5jIGludGVyZmFjZSB3cmFwcGVyIGFyb3VuZCBgcmVxdWVzdEFuaW1hdGlvbkZyYW1lYC4KICAgICAqCiAgICAgKiBAbmFtZXNwYWNlCiAgICAgKiBAc3VtbWFyeSBBc3luYyBpbnRlcmZhY2Ugd3JhcHBlciBhcm91bmQgYHJlcXVlc3RBbmltYXRpb25GcmFtZWAuCiAgICAgKi8KICAgIGNvbnN0IGFuaW1hdGlvbkZyYW1lID0gewogICAgICAvKioKICAgICAgICogRW5xdWV1ZXMgYSBmdW5jdGlvbiBjYWxsZWQgYXQgYHJlcXVlc3RBbmltYXRpb25GcmFtZWAgdGltaW5nLgogICAgICAgKgogICAgICAgKiBAbWVtYmVyb2YgYW5pbWF0aW9uRnJhbWUKICAgICAgICogQHBhcmFtIHtmdW5jdGlvbihudW1iZXIpOnZvaWR9IGZuIENhbGxiYWNrIHRvIHJ1bgogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9IEhhbmRsZSB1c2VkIGZvciBjYW5jZWxpbmcgdGFzawogICAgICAgKi8KICAgICAgcnVuKGZuKSB7CiAgICAgICAgcmV0dXJuIHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUoZm4pOwogICAgICB9LAogICAgICAvKioKICAgICAgICogQ2FuY2VscyBhIHByZXZpb3VzbHkgZW5xdWV1ZWQgYGFuaW1hdGlvbkZyYW1lYCBjYWxsYmFjay4KICAgICAgICoKICAgICAgICogQG1lbWJlcm9mIGFuaW1hdGlvbkZyYW1lCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBoYW5kbGUgSGFuZGxlIHJldHVybmVkIGZyb20gYHJ1bmAgb2YgY2FsbGJhY2sgdG8gY2FuY2VsCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBjYW5jZWwoaGFuZGxlKSB7CiAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKGhhbmRsZSk7CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICAgKiBBc3luYyBpbnRlcmZhY2Ugd3JhcHBlciBhcm91bmQgYHJlcXVlc3RJZGxlQ2FsbGJhY2tgLiAgRmFsbHMgYmFjayB0bwogICAgICogYHNldFRpbWVvdXRgIG9uIGJyb3dzZXJzIHRoYXQgZG8gbm90IHN1cHBvcnQgYHJlcXVlc3RJZGxlQ2FsbGJhY2tgLgogICAgICoKICAgICAqIEBuYW1lc3BhY2UKICAgICAqIEBzdW1tYXJ5IEFzeW5jIGludGVyZmFjZSB3cmFwcGVyIGFyb3VuZCBgcmVxdWVzdElkbGVDYWxsYmFja2AuCiAgICAgKi8KICAgIGNvbnN0IGlkbGVQZXJpb2QgPSB7CiAgICAgIC8qKgogICAgICAgKiBFbnF1ZXVlcyBhIGZ1bmN0aW9uIGNhbGxlZCBhdCBgcmVxdWVzdElkbGVDYWxsYmFja2AgdGltaW5nLgogICAgICAgKgogICAgICAgKiBAbWVtYmVyb2YgaWRsZVBlcmlvZAogICAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCFJZGxlRGVhZGxpbmUpOnZvaWR9IGZuIENhbGxiYWNrIHRvIHJ1bgogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9IEhhbmRsZSB1c2VkIGZvciBjYW5jZWxpbmcgdGFzawogICAgICAgKi8KICAgICAgcnVuKGZuKSB7CiAgICAgICAgcmV0dXJuIHdpbmRvdy5yZXF1ZXN0SWRsZUNhbGxiYWNrID8KICAgICAgICAgIHdpbmRvdy5yZXF1ZXN0SWRsZUNhbGxiYWNrKGZuKSA6CiAgICAgICAgICB3aW5kb3cuc2V0VGltZW91dChmbiwgMTYpOwogICAgICB9LAogICAgICAvKioKICAgICAgICogQ2FuY2VscyBhIHByZXZpb3VzbHkgZW5xdWV1ZWQgYGlkbGVQZXJpb2RgIGNhbGxiYWNrLgogICAgICAgKgogICAgICAgKiBAbWVtYmVyb2YgaWRsZVBlcmlvZAogICAgICAgKiBAcGFyYW0ge251bWJlcn0gaGFuZGxlIEhhbmRsZSByZXR1cm5lZCBmcm9tIGBydW5gIG9mIGNhbGxiYWNrIHRvIGNhbmNlbAogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgY2FuY2VsKGhhbmRsZSkgewogICAgICAgIHdpbmRvdy5jYW5jZWxJZGxlQ2FsbGJhY2sgPwogICAgICAgICAgd2luZG93LmNhbmNlbElkbGVDYWxsYmFjayhoYW5kbGUpIDoKICAgICAgICAgIHdpbmRvdy5jbGVhclRpbWVvdXQoaGFuZGxlKTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgICAqIEFzeW5jIGludGVyZmFjZSBmb3IgZW5xdWV1aW5nIGNhbGxiYWNrcyB0aGF0IHJ1biBhdCBtaWNyb3Rhc2sgdGltaW5nLgogICAgICoKICAgICAqIE5vdGUgdGhhdCBtaWNyb3Rhc2sgdGltaW5nIGlzIGFjaGlldmVkIHZpYSBhIHNpbmdsZSBgTXV0YXRpb25PYnNlcnZlcmAsCiAgICAgKiBhbmQgdGh1cyBjYWxsYmFja3MgZW5xdWV1ZWQgd2l0aCB0aGlzIEFQSSB3aWxsIGFsbCBydW4gaW4gYSBzaW5nbGUKICAgICAqIGJhdGNoLCBhbmQgbm90IGludGVybGVhdmVkIHdpdGggb3RoZXIgbWljcm90YXNrcyBzdWNoIGFzIHByb21pc2VzLgogICAgICogUHJvbWlzZXMgYXJlIGF2b2lkZWQgYXMgYW4gaW1wbGVtZW50YXRpb24gY2hvaWNlIGZvciB0aGUgdGltZSBiZWluZwogICAgICogZHVlIHRvIFNhZmFyaSBidWdzIHRoYXQgY2F1c2UgUHJvbWlzZXMgdG8gbGFjayBtaWNyb3Rhc2sgZ3VhcmFudGVlcy4KICAgICAqCiAgICAgKiBAbmFtZXNwYWNlCiAgICAgKiBAc3VtbWFyeSBBc3luYyBpbnRlcmZhY2UgZm9yIGVucXVldWluZyBjYWxsYmFja3MgdGhhdCBydW4gYXQgbWljcm90YXNrCiAgICAgKiAgIHRpbWluZy4KICAgICAqLwogICAgY29uc3QgbWljcm9UYXNrID0gewoKICAgICAgLyoqCiAgICAgICAqIEVucXVldWVzIGEgZnVuY3Rpb24gY2FsbGVkIGF0IG1pY3JvdGFzayB0aW1pbmcuCiAgICAgICAqCiAgICAgICAqIEBtZW1iZXJvZiBtaWNyb1Rhc2sKICAgICAgICogQHBhcmFtIHshRnVuY3Rpb249fSBjYWxsYmFjayBDYWxsYmFjayB0byBydW4KICAgICAgICogQHJldHVybiB7bnVtYmVyfSBIYW5kbGUgdXNlZCBmb3IgY2FuY2VsaW5nIHRhc2sKICAgICAgICovCiAgICAgIHJ1bihjYWxsYmFjaykgewogICAgICAgIGlmICghbWljcm90YXNrU2NoZWR1bGVkKSB7CiAgICAgICAgICBtaWNyb3Rhc2tTY2hlZHVsZWQgPSB0cnVlOwogICAgICAgICAgbWljcm90YXNrTm9kZS50ZXh0Q29udGVudCA9IG1pY3JvdGFza05vZGVDb250ZW50Kys7CiAgICAgICAgfQogICAgICAgIG1pY3JvdGFza0NhbGxiYWNrcy5wdXNoKGNhbGxiYWNrKTsKICAgICAgICByZXR1cm4gbWljcm90YXNrQ3VyckhhbmRsZSsrOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbmNlbHMgYSBwcmV2aW91c2x5IGVucXVldWVkIGBtaWNyb1Rhc2tgIGNhbGxiYWNrLgogICAgICAgKgogICAgICAgKiBAbWVtYmVyb2YgbWljcm9UYXNrCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBoYW5kbGUgSGFuZGxlIHJldHVybmVkIGZyb20gYHJ1bmAgb2YgY2FsbGJhY2sgdG8gY2FuY2VsCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBjYW5jZWwoaGFuZGxlKSB7CiAgICAgICAgY29uc3QgaWR4ID0gaGFuZGxlIC0gbWljcm90YXNrTGFzdEhhbmRsZTsKICAgICAgICBpZiAoaWR4ID49IDApIHsKICAgICAgICAgIGlmICghbWljcm90YXNrQ2FsbGJhY2tzW2lkeF0pIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdpbnZhbGlkIGFzeW5jIGhhbmRsZTogJyArIGhhbmRsZSk7CiAgICAgICAgICB9CiAgICAgICAgICBtaWNyb3Rhc2tDYWxsYmFja3NbaWR4XSA9IG51bGw7CiAgICAgICAgfQogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKiBAY29uc3QgeyFBc3luY0ludGVyZmFjZX0gKi8KICAgIGNvbnN0IG1pY3JvdGFzayA9IG1pY3JvVGFzazsKCiAgICAvKioKICAgICAqIEVsZW1lbnQgY2xhc3MgbWl4aW4gdGhhdCBwcm92aWRlcyBiYXNpYyBtZXRhLXByb2dyYW1taW5nIGZvciBjcmVhdGluZyBvbmUKICAgICAqIG9yIG1vcmUgcHJvcGVydHkgYWNjZXNzb3JzIChnZXR0ZXIvc2V0dGVyIHBhaXIpIHRoYXQgZW5xdWV1ZSBhbiBhc3luYwogICAgICogKGJhdGNoZWQpIGBfcHJvcGVydGllc0NoYW5nZWRgIGNhbGxiYWNrLgogICAgICoKICAgICAqIEZvciBiYXNpYyB1c2FnZSBvZiB0aGlzIG1peGluLCBjYWxsIGBNeUNsYXNzLmNyZWF0ZVByb3BlcnRpZXMocHJvcHMpYAogICAgICogb25jZSBhdCBjbGFzcyBkZWZpbml0aW9uIHRpbWUgdG8gY3JlYXRlIHByb3BlcnR5IGFjY2Vzc29ycyBmb3IgcHJvcGVydGllcwogICAgICogbmFtZWQgaW4gcHJvcHMsIGltcGxlbWVudCBgX3Byb3BlcnRpZXNDaGFuZ2VkYCB0byByZWFjdCBhcyBkZXNpcmVkIHRvCiAgICAgKiBwcm9wZXJ0eSBjaGFuZ2VzLCBhbmQgaW1wbGVtZW50IGBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpYCBhbmQKICAgICAqIGluY2x1ZGUgbG93ZXJjYXNlIHZlcnNpb25zIG9mIGFueSBwcm9wZXJ0eSBuYW1lcyB0aGF0IHNob3VsZCBiZSBzZXQgZnJvbQogICAgICogYXR0cmlidXRlcy4gTGFzdCwgY2FsbCBgdGhpcy5fZW5hYmxlUHJvcGVydGllcygpYCBpbiB0aGUgZWxlbWVudCdzCiAgICAgKiBgY29ubmVjdGVkQ2FsbGJhY2tgIHRvIGVuYWJsZSB0aGUgYWNjZXNzb3JzLgogICAgICoKICAgICAqIEBtaXhpbkZ1bmN0aW9uCiAgICAgKiBAcG9seW1lcgogICAgICogQHN1bW1hcnkgRWxlbWVudCBjbGFzcyBtaXhpbiBmb3IgcmVhY3RpbmcgdG8gcHJvcGVydHkgY2hhbmdlcyBmcm9tCiAgICAgKiAgIGdlbmVyYXRlZCBwcm9wZXJ0eSBhY2Nlc3NvcnMuCiAgICAgKiBAdGVtcGxhdGUgVAogICAgICogQHBhcmFtIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3MgQ2xhc3MgdG8gYXBwbHkgbWl4aW4gdG8uCiAgICAgKiBAcmV0dXJuIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3Mgd2l0aCBtaXhpbiBhcHBsaWVkLgogICAgICovCiAgICBjb25zdCBQcm9wZXJ0aWVzQ2hhbmdlZCA9IGRlZHVwaW5nTWl4aW4oCiAgICAgICAgLyoqCiAgICAgICAgICogQHRlbXBsYXRlIFQKICAgICAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyBDbGFzcyB0byBhcHBseSBtaXhpbiB0by4KICAgICAgICAgKiBAcmV0dXJuIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3Mgd2l0aCBtaXhpbiBhcHBsaWVkLgogICAgICAgICAqLwogICAgICAgIChzdXBlckNsYXNzKSA9PiB7CgogICAgICAvKioKICAgICAgICogQHBvbHltZXIKICAgICAgICogQG1peGluQ2xhc3MKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfUHJvcGVydGllc0NoYW5nZWR9CiAgICAgICAqIEB1bnJlc3RyaWN0ZWQKICAgICAgICovCiAgICAgIGNsYXNzIFByb3BlcnRpZXNDaGFuZ2VkIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgcHJvcGVydHkgYWNjZXNzb3JzIGZvciB0aGUgZ2l2ZW4gcHJvcGVydHkgbmFtZXMuCiAgICAgICAgICogQHBhcmFtIHshT2JqZWN0fSBwcm9wcyBPYmplY3Qgd2hvc2Uga2V5cyBhcmUgbmFtZXMgb2YgYWNjZXNzb3JzLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIGNyZWF0ZVByb3BlcnRpZXMocHJvcHMpIHsKICAgICAgICAgIGNvbnN0IHByb3RvID0gdGhpcy5wcm90b3R5cGU7CiAgICAgICAgICBmb3IgKGxldCBwcm9wIGluIHByb3BzKSB7CiAgICAgICAgICAgIC8vIGRvbid0IHN0b21wIGFuIGV4aXN0aW5nIGFjY2Vzc29yCiAgICAgICAgICAgIGlmICghKHByb3AgaW4gcHJvdG8pKSB7CiAgICAgICAgICAgICAgcHJvdG8uX2NyZWF0ZVByb3BlcnR5QWNjZXNzb3IocHJvcCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYW4gYXR0cmlidXRlIG5hbWUgdGhhdCBjb3JyZXNwb25kcyB0byB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICogVGhlIGF0dHJpYnV0ZSBuYW1lIGlzIHRoZSBsb3dlcmNhc2VkIHByb3BlcnR5IG5hbWUuIE92ZXJyaWRlIHRvCiAgICAgICAgICogY3VzdG9taXplIHRoaXMgbWFwcGluZy4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgdG8gY29udmVydAogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gQXR0cmlidXRlIG5hbWUgY29ycmVzcG9uZGluZyB0byB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgYXR0cmlidXRlTmFtZUZvclByb3BlcnR5KHByb3BlcnR5KSB7CiAgICAgICAgICByZXR1cm4gcHJvcGVydHkudG9Mb3dlckNhc2UoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlIHBvaW50IHRvIHByb3ZpZGUgYSB0eXBlIHRvIHdoaWNoIHRvIGRlc2VyaWFsaXplIGEgdmFsdWUgdG8KICAgICAgICAgKiBhIGdpdmVuIHByb3BlcnR5LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgcHJvcGVydHkKICAgICAgICAgKgogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyB0eXBlRm9yUHJvcGVydHkobmFtZSkgeyB9IC8vZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtdmFycwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2V0dGVyL2dldHRlciBwYWlyIGZvciB0aGUgbmFtZWQgcHJvcGVydHkgd2l0aCBpdHMgb3duCiAgICAgICAgICogbG9jYWwgc3RvcmFnZS4gIFRoZSBnZXR0ZXIgcmV0dXJucyB0aGUgdmFsdWUgaW4gdGhlIGxvY2FsIHN0b3JhZ2UsCiAgICAgICAgICogYW5kIHRoZSBzZXR0ZXIgY2FsbHMgYF9zZXRQcm9wZXJ0eWAsIHdoaWNoIHVwZGF0ZXMgdGhlIGxvY2FsIHN0b3JhZ2UKICAgICAgICAgKiBmb3IgdGhlIHByb3BlcnR5IGFuZCBlbnF1ZXVlcyBhIGBfcHJvcGVydGllc0NoYW5nZWRgIGNhbGxiYWNrLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBtZXRob2QgbWF5IGJlIGNhbGxlZCBvbiBhIHByb3RvdHlwZSBvciBhbiBpbnN0YW5jZS4gIENhbGxpbmcKICAgICAgICAgKiB0aGlzIG1ldGhvZCBtYXkgb3ZlcndyaXRlIGEgcHJvcGVydHkgdmFsdWUgdGhhdCBhbHJlYWR5IGV4aXN0cyBvbgogICAgICAgICAqIHRoZSBwcm90b3R5cGUvaW5zdGFuY2UgYnkgY3JlYXRpbmcgdGhlIGFjY2Vzc29yLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IE5hbWUgb2YgdGhlIHByb3BlcnR5CiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gcmVhZE9ubHkgV2hlbiB0cnVlLCBubyBzZXR0ZXIgaXMgY3JlYXRlZDsgdGhlCiAgICAgICAgICogICBwcm90ZWN0ZWQgYF9zZXRQcm9wZXJ0eWAgZnVuY3Rpb24gbXVzdCBiZSB1c2VkIHRvIHNldCB0aGUgcHJvcGVydHkKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfY3JlYXRlUHJvcGVydHlBY2Nlc3Nvcihwcm9wZXJ0eSwgcmVhZE9ubHkpIHsKICAgICAgICAgIHRoaXMuX2FkZFByb3BlcnR5VG9BdHRyaWJ1dGVNYXAocHJvcGVydHkpOwogICAgICAgICAgaWYgKCF0aGlzLmhhc093blByb3BlcnR5KEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ19fZGF0YUhhc0FjY2Vzc29yJywgdGhpcykpKSB7CiAgICAgICAgICAgIHRoaXMuX19kYXRhSGFzQWNjZXNzb3IgPSBPYmplY3QuYXNzaWduKHt9LCB0aGlzLl9fZGF0YUhhc0FjY2Vzc29yKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICghdGhpcy5fX2RhdGFIYXNBY2Nlc3Nvcltwcm9wZXJ0eV0pIHsKICAgICAgICAgICAgdGhpcy5fX2RhdGFIYXNBY2Nlc3Nvcltwcm9wZXJ0eV0gPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9kZWZpbmVQcm9wZXJ0eUFjY2Vzc29yKHByb3BlcnR5LCByZWFkT25seSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIHRoZSBnaXZlbiBgcHJvcGVydHlgIHRvIGEgbWFwIG1hdGNoaW5nIGF0dHJpYnV0ZSBuYW1lcwogICAgICAgICAqIHRvIHByb3BlcnR5IG5hbWVzLCB1c2luZyBgYXR0cmlidXRlTmFtZUZvclByb3BlcnR5YC4gVGhpcyBtYXAgaXMKICAgICAgICAgKiB1c2VkIHdoZW4gZGVzZXJpYWxpemluZyBhdHRyaWJ1dGUgdmFsdWVzIHRvIHByb3BlcnRpZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiB0aGUgcHJvcGVydHkKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfYWRkUHJvcGVydHlUb0F0dHJpYnV0ZU1hcChwcm9wZXJ0eSkgewogICAgICAgICAgaWYgKCF0aGlzLmhhc093blByb3BlcnR5KEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ19fZGF0YUF0dHJpYnV0ZXMnLCB0aGlzKSkpIHsKICAgICAgICAgICAgdGhpcy5fX2RhdGFBdHRyaWJ1dGVzID0gT2JqZWN0LmFzc2lnbih7fSwgdGhpcy5fX2RhdGFBdHRyaWJ1dGVzKTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIFRoaXMgY2hlY2sgaXMgdGVjaG5pY2FsbHkgbm90IGNvcnJlY3Q7IGl0J3MgYW4gb3B0aW1pemF0aW9uIHRoYXQKICAgICAgICAgIC8vIGFzc3VtZXMgdGhhdCBpZiBhIF9wcm9wZXJ0eV8gbmFtZSBpcyBhbHJlYWR5IGluIHRoZSBtYXAgKG5vdGUgdGhpcyBpcwogICAgICAgICAgLy8gYW4gYXR0ci0+cHJvcGVydHkgbWFwKSwgdGhlIHByb3BlcnR5IG1hcHBlZCBkaXJlY3RseSB0byB0aGUgYXR0cmlidXRlCiAgICAgICAgICAvLyBhbmQgaXQgaGFzIGFscmVhZHkgYmVlbiBtYXBwZWQuICBUaGlzIHdvdWxkIGZhaWwgaWYKICAgICAgICAgIC8vIGBhdHRyaWJ1dGVOYW1lRm9yUHJvcGVydHlgIHdlcmUgb3ZlcnJpZGRlbiBzdWNoIHRoYXQgdGhpcyB3YXMgbm90IHRoZQogICAgICAgICAgLy8gY2FzZS4KICAgICAgICAgIGxldCBhdHRyID0gdGhpcy5fX2RhdGFBdHRyaWJ1dGVzW3Byb3BlcnR5XTsKICAgICAgICAgIGlmICghYXR0cikgewogICAgICAgICAgICBhdHRyID0gdGhpcy5jb25zdHJ1Y3Rvci5hdHRyaWJ1dGVOYW1lRm9yUHJvcGVydHkocHJvcGVydHkpOwogICAgICAgICAgICB0aGlzLl9fZGF0YUF0dHJpYnV0ZXNbYXR0cl0gPSBwcm9wZXJ0eTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBhdHRyOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRGVmaW5lcyBhIHByb3BlcnR5IGFjY2Vzc29yIGZvciB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IE5hbWUgb2YgdGhlIHByb3BlcnR5CiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gcmVhZE9ubHkgV2hlbiB0cnVlLCBubyBzZXR0ZXIgaXMgY3JlYXRlZAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgIF9kZWZpbmVQcm9wZXJ0eUFjY2Vzc29yKHByb3BlcnR5LCByZWFkT25seSkgewogICAgICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHRoaXMsIHByb3BlcnR5LCB7CiAgICAgICAgICAgIC8qIGVzbGludC1kaXNhYmxlIHZhbGlkLWpzZG9jICovCiAgICAgICAgICAgIC8qKiBAdGhpcyB7UHJvcGVydGllc0NoYW5nZWR9ICovCiAgICAgICAgICAgIGdldCgpIHsKICAgICAgICAgICAgICAvLyBJbmxpbmUgZm9yIHBlcmYgaW5zdGVhZCBvZiB1c2luZyBgX2dldFByb3BlcnR5YAogICAgICAgICAgICAgIHJldHVybiB0aGlzLl9fZGF0YVtwcm9wZXJ0eV07CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIC8qKiBAdGhpcyB7UHJvcGVydGllc0NoYW5nZWR9ICovCiAgICAgICAgICAgIHNldDogcmVhZE9ubHkgPyBmdW5jdGlvbiAoKSB7fSA6IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICAgIC8vIElubGluZSBmb3IgcGVyZiBpbnN0ZWFkIG9mIHVzaW5nIGBfc2V0UHJvcGVydHlgCiAgICAgICAgICAgICAgaWYgKHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eShwcm9wZXJ0eSwgdmFsdWUsIHRydWUpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9pbnZhbGlkYXRlUHJvcGVydGllcygpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICAvKiBlc2xpbnQtZW5hYmxlICovCiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgc3VwZXIoKTsKICAgICAgICAgIC8qKiBAdHlwZSB7Ym9vbGVhbn0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhRW5hYmxlZCA9IGZhbHNlOwogICAgICAgICAgdGhpcy5fX2RhdGFSZWFkeSA9IGZhbHNlOwogICAgICAgICAgdGhpcy5fX2RhdGFJbnZhbGlkID0gZmFsc2U7CiAgICAgICAgICB0aGlzLl9fZGF0YSA9IHt9OwogICAgICAgICAgdGhpcy5fX2RhdGFQZW5kaW5nID0gbnVsbDsKICAgICAgICAgIHRoaXMuX19kYXRhT2xkID0gbnVsbDsKICAgICAgICAgIHRoaXMuX19kYXRhSW5zdGFuY2VQcm9wcyA9IG51bGw7CiAgICAgICAgICAvKiogQHR5cGUge251bWJlcn0gKi8KICAgICAgICAgIC8vIE5PVEU6IHVzZWQgdG8gdHJhY2sgcmUtZW50cmFudCBjYWxscyB0byBgX2ZsdXNoUHJvcGVydGllc2AKICAgICAgICAgIHRoaXMuX19kYXRhQ291bnRlciA9IDA7CiAgICAgICAgICB0aGlzLl9fc2VyaWFsaXppbmcgPSBmYWxzZTsKICAgICAgICAgIHRoaXMuX2luaXRpYWxpemVQcm9wZXJ0aWVzKCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBMaWZlY3ljbGUgY2FsbGJhY2sgY2FsbGVkIHdoZW4gcHJvcGVydGllcyBhcmUgZW5hYmxlZCB2aWEKICAgICAgICAgKiBgX2VuYWJsZVByb3BlcnRpZXNgLgogICAgICAgICAqCiAgICAgICAgICogVXNlcnMgbWF5IG92ZXJyaWRlIHRoaXMgZnVuY3Rpb24gdG8gaW1wbGVtZW50IGJlaGF2aW9yIHRoYXQgaXMKICAgICAgICAgKiBkZXBlbmRlbnQgb24gdGhlIGVsZW1lbnQgaGF2aW5nIGl0cyBwcm9wZXJ0eSBkYXRhIGluaXRpYWxpemVkLCBlLmcuCiAgICAgICAgICogZnJvbSBkZWZhdWx0cyAoaW5pdGlhbGl6ZWQgZnJvbSBgY29uc3RydWN0b3JgLCBgX2luaXRpYWxpemVQcm9wZXJ0aWVzYCksCiAgICAgICAgICogYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AsIG9yIHZhbHVlcyBwcm9wYWdhdGVkIGZyb20gaG9zdCBlLmcuIHZpYQogICAgICAgICAqIGJpbmRpbmdzLiAgYHN1cGVyLnJlYWR5KClgIG11c3QgYmUgY2FsbGVkIHRvIGVuc3VyZSB0aGUgZGF0YSBzeXN0ZW0KICAgICAgICAgKiBiZWNvbWVzIGVuYWJsZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgIHRoaXMuX19kYXRhUmVhZHkgPSB0cnVlOwogICAgICAgICAgdGhpcy5fZmx1c2hQcm9wZXJ0aWVzKCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJbml0aWFsaXplcyB0aGUgbG9jYWwgc3RvcmFnZSBmb3IgcHJvcGVydHkgYWNjZXNzb3JzLgogICAgICAgICAqCiAgICAgICAgICogUHJvdmlkZWQgYXMgYW4gb3ZlcnJpZGUgcG9pbnQgZm9yIHBlcmZvcm1pbmcgYW55IHNldHVwIHdvcmsgcHJpb3IKICAgICAgICAgKiB0byBpbml0aWFsaXppbmcgdGhlIHByb3BlcnR5IGFjY2Vzc29yIHN5c3RlbS4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9pbml0aWFsaXplUHJvcGVydGllcygpIHsKICAgICAgICAgIC8vIENhcHR1cmUgaW5zdGFuY2UgcHJvcGVydGllczsgdGhlc2Ugd2lsbCBiZSBzZXQgaW50byBhY2Nlc3NvcnMKICAgICAgICAgIC8vIGR1cmluZyBmaXJzdCBmbHVzaC4gRG9uJ3Qgc2V0IHRoZW0gaGVyZSwgc2luY2Ugd2Ugd2FudAogICAgICAgICAgLy8gdGhlc2UgdG8gb3ZlcndyaXRlIGRlZmF1bHRzL2NvbnN0cnVjdG9yIGFzc2lnbm1lbnRzCiAgICAgICAgICBmb3IgKGxldCBwIGluIHRoaXMuX19kYXRhSGFzQWNjZXNzb3IpIHsKICAgICAgICAgICAgaWYgKHRoaXMuaGFzT3duUHJvcGVydHkocCkpIHsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YUluc3RhbmNlUHJvcHMgPSB0aGlzLl9fZGF0YUluc3RhbmNlUHJvcHMgfHwge307CiAgICAgICAgICAgICAgdGhpcy5fX2RhdGFJbnN0YW5jZVByb3BzW3BdID0gdGhpc1twXTsKICAgICAgICAgICAgICBkZWxldGUgdGhpc1twXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2FsbGVkIGF0IHJlYWR5IHRpbWUgd2l0aCBiYWcgb2YgaW5zdGFuY2UgcHJvcGVydGllcyB0aGF0IG92ZXJ3cm90ZQogICAgICAgICAqIGFjY2Vzc29ycyB3aGVuIHRoZSBlbGVtZW50IHVwZ3JhZGVkLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gc2V0cyB0aGVzZSBwcm9wZXJ0aWVzIGJhY2sgaW50byB0aGUKICAgICAgICAgKiBzZXR0ZXIgYXQgcmVhZHkgdGltZS4gIFRoaXMgbWV0aG9kIGlzIHByb3ZpZGVkIGFzIGFuIG92ZXJyaWRlCiAgICAgICAgICogcG9pbnQgZm9yIGN1c3RvbWl6aW5nIG9yIHByb3ZpZGluZyBtb3JlIGVmZmljaWVudCBpbml0aWFsaXphdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgcHJvcGVydHkgdmFsdWVzIHRoYXQgd2VyZSBvdmVyd3JpdHRlbgogICAgICAgICAqICAgd2hlbiBjcmVhdGluZyBwcm9wZXJ0eSBhY2Nlc3NvcnMuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2luaXRpYWxpemVJbnN0YW5jZVByb3BlcnRpZXMocHJvcHMpIHsKICAgICAgICAgIE9iamVjdC5hc3NpZ24odGhpcywgcHJvcHMpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVXBkYXRlcyB0aGUgbG9jYWwgc3RvcmFnZSBmb3IgYSBwcm9wZXJ0eSAodmlhIGBfc2V0UGVuZGluZ1Byb3BlcnR5YCkKICAgICAgICAgKiBhbmQgZW5xdWV1ZXMgYSBgX3Byb2VwcnRpZXNDaGFuZ2VkYCBjYWxsYmFjay4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIHRoZSBwcm9wZXJ0eQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVmFsdWUgdG8gc2V0CiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3NldFByb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSkgewogICAgICAgICAgaWYgKHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eShwcm9wZXJ0eSwgdmFsdWUpKSB7CiAgICAgICAgICAgIHRoaXMuX2ludmFsaWRhdGVQcm9wZXJ0aWVzKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSB2YWx1ZSBmb3IgdGhlIGdpdmVuIHByb3BlcnR5LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIHByb3BlcnR5CiAgICAgICAgICogQHJldHVybiB7Kn0gVmFsdWUgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfZ2V0UHJvcGVydHkocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9fZGF0YVtwcm9wZXJ0eV07CiAgICAgICAgfQoKICAgICAgICAvKiBlc2xpbnQtZGlzYWJsZSBuby11bnVzZWQtdmFycyAqLwogICAgICAgIC8qKgogICAgICAgICAqIFVwZGF0ZXMgdGhlIGxvY2FsIHN0b3JhZ2UgZm9yIGEgcHJvcGVydHksIHJlY29yZHMgdGhlIHByZXZpb3VzIHZhbHVlLAogICAgICAgICAqIGFuZCBhZGRzIGl0IHRvIHRoZSBzZXQgb2YgInBlbmRpbmcgY2hhbmdlcyIgdGhhdCB3aWxsIGJlIHBhc3NlZCB0byB0aGUKICAgICAgICAgKiBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBjYWxsYmFjay4gIFRoaXMgbWV0aG9kIGRvZXMgbm90IGVucXVldWUgdGhlCiAgICAgICAgICogYF9wcm9wZXJ0aWVzQ2hhbmdlZGAgY2FsbGJhY2suCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiB0aGUgcHJvcGVydHkKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIHNldAogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IGV4dCBOb3QgdXNlZCBoZXJlOyBhZmZvcmRhbmNlIGZvciBjbG9zdXJlCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIHRoZSBwcm9wZXJ0eSBjaGFuZ2VkCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9zZXRQZW5kaW5nUHJvcGVydHkocHJvcGVydHksIHZhbHVlLCBleHQpIHsKICAgICAgICAgIGxldCBvbGQgPSB0aGlzLl9fZGF0YVtwcm9wZXJ0eV07CiAgICAgICAgICBsZXQgY2hhbmdlZCA9IHRoaXMuX3Nob3VsZFByb3BlcnR5Q2hhbmdlKHByb3BlcnR5LCB2YWx1ZSwgb2xkKTsKICAgICAgICAgIGlmIChjaGFuZ2VkKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fX2RhdGFQZW5kaW5nKSB7CiAgICAgICAgICAgICAgdGhpcy5fX2RhdGFQZW5kaW5nID0ge307CiAgICAgICAgICAgICAgdGhpcy5fX2RhdGFPbGQgPSB7fTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBFbnN1cmUgb2xkIGlzIGNhcHR1cmVkIGZyb20gdGhlIGxhc3QgdHVybgogICAgICAgICAgICBpZiAodGhpcy5fX2RhdGFPbGQgJiYgIShwcm9wZXJ0eSBpbiB0aGlzLl9fZGF0YU9sZCkpIHsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YU9sZFtwcm9wZXJ0eV0gPSBvbGQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fX2RhdGFbcHJvcGVydHldID0gdmFsdWU7CiAgICAgICAgICAgIHRoaXMuX19kYXRhUGVuZGluZ1twcm9wZXJ0eV0gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBjaGFuZ2VkOwogICAgICAgIH0KICAgICAgICAvKiBlc2xpbnQtZW5hYmxlICovCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIHRoZSBwcm9wZXJ0eQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFJldHVybnMgdHJ1ZSBpZiB0aGUgcHJvcGVydHkgaXMgcGVuZGluZy4KICAgICAgICAgKi8KICAgICAgICBfaXNQcm9wZXJ0eVBlbmRpbmcocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiAhISh0aGlzLl9fZGF0YVBlbmRpbmcgJiYgdGhpcy5fX2RhdGFQZW5kaW5nLmhhc093blByb3BlcnR5KHByb3BlcnR5KSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBNYXJrcyB0aGUgcHJvcGVydGllcyBhcyBpbnZhbGlkLCBhbmQgZW5xdWV1ZXMgYW4gYXN5bmMKICAgICAgICAgKiBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBjYWxsYmFjay4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9pbnZhbGlkYXRlUHJvcGVydGllcygpIHsKICAgICAgICAgIGlmICghdGhpcy5fX2RhdGFJbnZhbGlkICYmIHRoaXMuX19kYXRhUmVhZHkpIHsKICAgICAgICAgICAgdGhpcy5fX2RhdGFJbnZhbGlkID0gdHJ1ZTsKICAgICAgICAgICAgbWljcm90YXNrLnJ1bigoKSA9PiB7CiAgICAgICAgICAgICAgaWYgKHRoaXMuX19kYXRhSW52YWxpZCkgewogICAgICAgICAgICAgICAgdGhpcy5fX2RhdGFJbnZhbGlkID0gZmFsc2U7CiAgICAgICAgICAgICAgICB0aGlzLl9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2FsbCB0byBlbmFibGUgcHJvcGVydHkgYWNjZXNzb3IgcHJvY2Vzc2luZy4gQmVmb3JlIHRoaXMgbWV0aG9kIGlzCiAgICAgICAgICogY2FsbGVkIGFjY2Vzc29yIHZhbHVlcyB3aWxsIGJlIHNldCBidXQgc2lkZSBlZmZlY3RzIGFyZQogICAgICAgICAqIHF1ZXVlZC4gV2hlbiBjYWxsZWQsIGFueSBwZW5kaW5nIHNpZGUgZWZmZWN0cyBvY2N1ciBpbW1lZGlhdGVseS4KICAgICAgICAgKiBGb3IgZWxlbWVudHMsIGdlbmVyYWxseSBgY29ubmVjdGVkQ2FsbGJhY2tgIGlzIGEgbm9ybWFsIHNwb3QgdG8gZG8gc28uCiAgICAgICAgICogSXQgaXMgc2FmZSB0byBjYWxsIHRoaXMgbWV0aG9kIG11bHRpcGxlIHRpbWVzIGFzIGl0IG9ubHkgdHVybnMgb24KICAgICAgICAgKiBwcm9wZXJ0eSBhY2Nlc3NvcnMgb25jZS4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9lbmFibGVQcm9wZXJ0aWVzKCkgewogICAgICAgICAgaWYgKCF0aGlzLl9fZGF0YUVuYWJsZWQpIHsKICAgICAgICAgICAgdGhpcy5fX2RhdGFFbmFibGVkID0gdHJ1ZTsKICAgICAgICAgICAgaWYgKHRoaXMuX19kYXRhSW5zdGFuY2VQcm9wcykgewogICAgICAgICAgICAgIHRoaXMuX2luaXRpYWxpemVJbnN0YW5jZVByb3BlcnRpZXModGhpcy5fX2RhdGFJbnN0YW5jZVByb3BzKTsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YUluc3RhbmNlUHJvcHMgPSBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMucmVhZHkoKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxzIHRoZSBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBjYWxsYmFjayB3aXRoIHRoZSBjdXJyZW50IHNldCBvZgogICAgICAgICAqIHBlbmRpbmcgY2hhbmdlcyAoYW5kIG9sZCB2YWx1ZXMgcmVjb3JkZWQgd2hlbiBwZW5kaW5nIGNoYW5nZXMgd2VyZQogICAgICAgICAqIHNldCksIGFuZCByZXNldHMgdGhlIHBlbmRpbmcgc2V0IG9mIGNoYW5nZXMuIEdlbmVyYWxseSwgdGhpcyBtZXRob2QKICAgICAgICAgKiBzaG91bGQgbm90IGJlIGNhbGxlZCBpbiB1c2VyIGNvZGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfZmx1c2hQcm9wZXJ0aWVzKCkgewogICAgICAgICAgdGhpcy5fX2RhdGFDb3VudGVyKys7CiAgICAgICAgICBjb25zdCBwcm9wcyA9IHRoaXMuX19kYXRhOwogICAgICAgICAgY29uc3QgY2hhbmdlZFByb3BzID0gdGhpcy5fX2RhdGFQZW5kaW5nOwogICAgICAgICAgY29uc3Qgb2xkID0gdGhpcy5fX2RhdGFPbGQ7CiAgICAgICAgICBpZiAodGhpcy5fc2hvdWxkUHJvcGVydGllc0NoYW5nZShwcm9wcywgY2hhbmdlZFByb3BzLCBvbGQpKSB7CiAgICAgICAgICAgIHRoaXMuX19kYXRhUGVuZGluZyA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX19kYXRhT2xkID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5fcHJvcGVydGllc0NoYW5nZWQocHJvcHMsIGNoYW5nZWRQcm9wcywgb2xkKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX19kYXRhQ291bnRlci0tOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2FsbGVkIGluIGBfZmx1c2hQcm9wZXJ0aWVzYCB0byBkZXRlcm1pbmUgaWYgYF9wcm9wZXJ0aWVzQ2hhbmdlZGAKICAgICAgICAgKiBzaG91bGQgYmUgY2FsbGVkLiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiByZXR1cm5zIHRydWUgaWYKICAgICAgICAgKiBwcm9wZXJ0aWVzIGFyZSBwZW5kaW5nLiBPdmVycmlkZSB0byBjdXN0b21pemUgd2hlbgogICAgICAgICAqIGBfcHJvcGVydGllc0NoYW5nZWRgIGlzIGNhbGxlZC4KICAgICAgICAgKiBAcGFyYW0geyFPYmplY3R9IGN1cnJlbnRQcm9wcyBCYWcgb2YgYWxsIGN1cnJlbnQgYWNjZXNzb3IgdmFsdWVzCiAgICAgICAgICogQHBhcmFtIHs/T2JqZWN0fSBjaGFuZ2VkUHJvcHMgQmFnIG9mIHByb3BlcnRpZXMgY2hhbmdlZCBzaW5jZSB0aGUgbGFzdAogICAgICAgICAqICAgY2FsbCB0byBgX3Byb3BlcnRpZXNDaGFuZ2VkYAogICAgICAgICAqIEBwYXJhbSB7P09iamVjdH0gb2xkUHJvcHMgQmFnIG9mIHByZXZpb3VzIHZhbHVlcyBmb3IgZWFjaCBwcm9wZXJ0eQogICAgICAgICAqICAgaW4gYGNoYW5nZWRQcm9wc2AKICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSB0cnVlIGlmIGNoYW5nZWRQcm9wcyBpcyB0cnV0aHkKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfc2hvdWxkUHJvcGVydGllc0NoYW5nZShjdXJyZW50UHJvcHMsIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMpIHsgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtdmFycwogICAgICAgICAgcmV0dXJuIEJvb2xlYW4oY2hhbmdlZFByb3BzKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxiYWNrIGNhbGxlZCB3aGVuIGFueSBwcm9wZXJ0aWVzIHdpdGggYWNjZXNzb3JzIGNyZWF0ZWQgdmlhCiAgICAgICAgICogYF9jcmVhdGVQcm9wZXJ0eUFjY2Vzc29yYCBoYXZlIGJlZW4gc2V0LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshT2JqZWN0fSBjdXJyZW50UHJvcHMgQmFnIG9mIGFsbCBjdXJyZW50IGFjY2Vzc29yIHZhbHVlcwogICAgICAgICAqIEBwYXJhbSB7P09iamVjdH0gY2hhbmdlZFByb3BzIEJhZyBvZiBwcm9wZXJ0aWVzIGNoYW5nZWQgc2luY2UgdGhlIGxhc3QKICAgICAgICAgKiAgIGNhbGwgdG8gYF9wcm9wZXJ0aWVzQ2hhbmdlZGAKICAgICAgICAgKiBAcGFyYW0gez9PYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGVhY2ggcHJvcGVydHkKICAgICAgICAgKiAgIGluIGBjaGFuZ2VkUHJvcHNgCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3Byb3BlcnRpZXNDaGFuZ2VkKGN1cnJlbnRQcm9wcywgY2hhbmdlZFByb3BzLCBvbGRQcm9wcykgeyAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXVudXNlZC12YXJzCiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBNZXRob2QgY2FsbGVkIHRvIGRldGVybWluZSB3aGV0aGVyIGEgcHJvcGVydHkgdmFsdWUgc2hvdWxkIGJlCiAgICAgICAgICogY29uc2lkZXJlZCBhcyBhIGNoYW5nZSBhbmQgY2F1c2UgdGhlIGBfcHJvcGVydGllc0NoYW5nZWRgIGNhbGxiYWNrCiAgICAgICAgICogdG8gYmUgZW5xdWV1ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiByZXR1cm5zIGB0cnVlYCBpZiBhIHN0cmljdCBlcXVhbGl0eQogICAgICAgICAqIGNoZWNrIGZhaWxzLiBUaGUgbWV0aG9kIGFsd2F5cyByZXR1cm5zIGZhbHNlIGZvciBgTmFOYC4KICAgICAgICAgKgogICAgICAgICAqIE92ZXJyaWRlIHRoaXMgbWV0aG9kIHRvIGUuZy4gcHJvdmlkZSBzdHJpY3RlciBjaGVja2luZyBmb3IKICAgICAgICAgKiBPYmplY3RzL0FycmF5cyB3aGVuIHVzaW5nIGltbXV0YWJsZSBwYXR0ZXJucy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBOZXcgcHJvcGVydHkgdmFsdWUKICAgICAgICAgKiBAcGFyYW0geyp9IG9sZCBQcmV2aW91cyBwcm9wZXJ0eSB2YWx1ZQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdGhlIHByb3BlcnR5IHNob3VsZCBiZSBjb25zaWRlcmVkIGEgY2hhbmdlCiAgICAgICAgICogICBhbmQgZW5xdWV1ZSBhIGBfcHJvZXBydGllc0NoYW5nZWRgIGNhbGxiYWNrCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9zaG91bGRQcm9wZXJ0eUNoYW5nZShwcm9wZXJ0eSwgdmFsdWUsIG9sZCkgewogICAgICAgICAgcmV0dXJuICgKICAgICAgICAgICAgLy8gU3RyaWN0IGVxdWFsaXR5IGNoZWNrCiAgICAgICAgICAgIChvbGQgIT09IHZhbHVlICYmCiAgICAgICAgICAgICAgLy8gVGhpcyBlbnN1cmVzIChvbGQ9PU5hTiwgdmFsdWU9PU5hTikgYWx3YXlzIHJldHVybnMgZmFsc2UKICAgICAgICAgICAgICAob2xkID09PSBvbGQgfHwgdmFsdWUgPT09IHZhbHVlKSkKICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJbXBsZW1lbnRzIG5hdGl2ZSBDdXN0b20gRWxlbWVudHMgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgdG8KICAgICAgICAgKiBzZXQgYW4gYXR0cmlidXRlIHZhbHVlIHRvIGEgcHJvcGVydHkgdmlhIGBfYXR0cmlidXRlVG9Qcm9wZXJ0eWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBOYW1lIG9mIGF0dHJpYnV0ZSB0aGF0IGNoYW5nZWQKICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IG9sZCBPbGQgYXR0cmlidXRlIHZhbHVlCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSB2YWx1ZSBOZXcgYXR0cmlidXRlIHZhbHVlCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSBuYW1lc3BhY2UgQXR0cmlidXRlIG5hbWVzcGFjZS4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBzdXBwcmVzcyB7bWlzc2luZ1Byb3BlcnRpZXN9IFN1cGVyIG1heSBvciBtYXkgbm90IGltcGxlbWVudCB0aGUgY2FsbGJhY2sKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sobmFtZSwgb2xkLCB2YWx1ZSwgbmFtZXNwYWNlKSB7CiAgICAgICAgICBpZiAob2xkICE9PSB2YWx1ZSkgewogICAgICAgICAgICB0aGlzLl9hdHRyaWJ1dGVUb1Byb3BlcnR5KG5hbWUsIHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsKICAgICAgICAgICAgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZCwgdmFsdWUsIG5hbWVzcGFjZSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBEZXNlcmlhbGl6ZXMgYW4gYXR0cmlidXRlIHRvIGl0cyBhc3NvY2lhdGVkIHByb3BlcnR5LgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBtZXRob2QgY2FsbHMgdGhlIGBfZGVzZXJpYWxpemVWYWx1ZWAgbWV0aG9kIHRvIGNvbnZlcnQgdGhlIHN0cmluZyB0bwogICAgICAgICAqIGEgdHlwZWQgdmFsdWUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIE5hbWUgb2YgYXR0cmlidXRlIHRvIGRlc2VyaWFsaXplLgogICAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gdmFsdWUgb2YgdGhlIGF0dHJpYnV0ZS4KICAgICAgICAgKiBAcGFyYW0geyo9fSB0eXBlIHR5cGUgdG8gZGVzZXJpYWxpemUgdG8sIGRlZmF1bHRzIHRvIHRoZSB2YWx1ZQogICAgICAgICAqIHJldHVybmVkIGZyb20gYHR5cGVGb3JQcm9wZXJ0eWAKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9hdHRyaWJ1dGVUb1Byb3BlcnR5KGF0dHJpYnV0ZSwgdmFsdWUsIHR5cGUpIHsKICAgICAgICAgIGlmICghdGhpcy5fX3NlcmlhbGl6aW5nKSB7CiAgICAgICAgICAgIGNvbnN0IG1hcCA9IHRoaXMuX19kYXRhQXR0cmlidXRlczsKICAgICAgICAgICAgY29uc3QgcHJvcGVydHkgPSBtYXAgJiYgbWFwW2F0dHJpYnV0ZV0gfHwgYXR0cmlidXRlOwogICAgICAgICAgICB0aGlzW3Byb3BlcnR5XSA9IHRoaXMuX2Rlc2VyaWFsaXplVmFsdWUodmFsdWUsIHR5cGUgfHwKICAgICAgICAgICAgICB0aGlzLmNvbnN0cnVjdG9yLnR5cGVGb3JQcm9wZXJ0eShwcm9wZXJ0eSkpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogU2VyaWFsaXplcyBhIHByb3BlcnR5IHRvIGl0cyBhc3NvY2lhdGVkIGF0dHJpYnV0ZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfSBDbG9zdXJlIGNhbid0IGZpZ3VyZSBvdXQgYHRoaXNgIGlzIGFuIGVsZW1lbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZSB0byByZWZsZWN0LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gYXR0cmlidXRlIEF0dHJpYnV0ZSBuYW1lIHRvIHJlZmxlY3QgdG8uCiAgICAgICAgICogQHBhcmFtIHsqPX0gdmFsdWUgUHJvcGVydHkgdmFsdWUgdG8gcmVmZWN0LgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3Byb3BlcnR5VG9BdHRyaWJ1dGUocHJvcGVydHksIGF0dHJpYnV0ZSwgdmFsdWUpIHsKICAgICAgICAgIHRoaXMuX19zZXJpYWxpemluZyA9IHRydWU7CiAgICAgICAgICB2YWx1ZSA9IChhcmd1bWVudHMubGVuZ3RoIDwgMykgPyB0aGlzW3Byb3BlcnR5XSA6IHZhbHVlOwogICAgICAgICAgdGhpcy5fdmFsdWVUb05vZGVBdHRyaWJ1dGUoLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovKHRoaXMpLCB2YWx1ZSwKICAgICAgICAgICAgYXR0cmlidXRlIHx8IHRoaXMuY29uc3RydWN0b3IuYXR0cmlidXRlTmFtZUZvclByb3BlcnR5KHByb3BlcnR5KSk7CiAgICAgICAgICB0aGlzLl9fc2VyaWFsaXppbmcgPSBmYWxzZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgYSB0eXBlZCB2YWx1ZSB0byBhbiBIVE1MIGF0dHJpYnV0ZSBvbiBhIG5vZGUuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBjYWxscyB0aGUgYF9zZXJpYWxpemVWYWx1ZWAgbWV0aG9kIHRvIGNvbnZlcnQgdGhlIHR5cGVkCiAgICAgICAgICogdmFsdWUgdG8gYSBzdHJpbmcuICBJZiB0aGUgYF9zZXJpYWxpemVWYWx1ZWAgbWV0aG9kIHJldHVybnMgYHVuZGVmaW5lZGAsCiAgICAgICAgICogdGhlIGF0dHJpYnV0ZSB3aWxsIGJlIHJlbW92ZWQgKHRoaXMgaXMgdGhlIGRlZmF1bHQgZm9yIGJvb2xlYW4KICAgICAgICAgKiB0eXBlIGBmYWxzZWApLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBub2RlIEVsZW1lbnQgdG8gc2V0IGF0dHJpYnV0ZSB0by4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIHNlcmlhbGl6ZS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIEF0dHJpYnV0ZSBuYW1lIHRvIHNlcmlhbGl6ZSB0by4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF92YWx1ZVRvTm9kZUF0dHJpYnV0ZShub2RlLCB2YWx1ZSwgYXR0cmlidXRlKSB7CiAgICAgICAgICBjb25zdCBzdHIgPSB0aGlzLl9zZXJpYWxpemVWYWx1ZSh2YWx1ZSk7CiAgICAgICAgICBpZiAoYXR0cmlidXRlID09PSAnY2xhc3MnIHx8IGF0dHJpYnV0ZSA9PT0gJ25hbWUnIHx8IGF0dHJpYnV0ZSA9PT0gJ3Nsb3QnKSB7CiAgICAgICAgICAgIG5vZGUgPSAvKiogQHR5cGUgez9FbGVtZW50fSAqLyh3cmFwKG5vZGUpKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChzdHIgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICBub2RlLnJlbW92ZUF0dHJpYnV0ZShhdHRyaWJ1dGUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZS5zZXRBdHRyaWJ1dGUoYXR0cmlidXRlLCBzdHIpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYSB0eXBlZCBKYXZhU2NyaXB0IHZhbHVlIHRvIGEgc3RyaW5nLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgY2FsbGVkIHdoZW4gc2V0dGluZyBKUyBwcm9wZXJ0eSB2YWx1ZXMgdG8KICAgICAgICAgKiBIVE1MIGF0dHJpYnV0ZXMuICBVc2VycyBtYXkgb3ZlcnJpZGUgdGhpcyBtZXRob2QgdG8gcHJvdmlkZQogICAgICAgICAqIHNlcmlhbGl6YXRpb24gZm9yIGN1c3RvbSB0eXBlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgUHJvcGVydHkgdmFsdWUgdG8gc2VyaWFsaXplLgogICAgICAgICAqIEByZXR1cm4ge3N0cmluZyB8IHVuZGVmaW5lZH0gU3RyaW5nIHNlcmlhbGl6ZWQgZnJvbSB0aGUgcHJvdmlkZWQKICAgICAgICAgKiBwcm9wZXJ0eSAgdmFsdWUuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3NlcmlhbGl6ZVZhbHVlKHZhbHVlKSB7CiAgICAgICAgICBzd2l0Y2ggKHR5cGVvZiB2YWx1ZSkgewogICAgICAgICAgICBjYXNlICdib29sZWFuJzoKICAgICAgICAgICAgICByZXR1cm4gdmFsdWUgPyAnJyA6IHVuZGVmaW5lZDsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICByZXR1cm4gdmFsdWUgIT0gbnVsbCA/IHZhbHVlLnRvU3RyaW5nKCkgOiB1bmRlZmluZWQ7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBhIHN0cmluZyB0byBhIHR5cGVkIEphdmFTY3JpcHQgdmFsdWUuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBjYWxsZWQgd2hlbiByZWFkaW5nIEhUTUwgYXR0cmlidXRlIHZhbHVlcyB0bwogICAgICAgICAqIEpTIHByb3BlcnRpZXMuICBVc2VycyBtYXkgb3ZlcnJpZGUgdGhpcyBtZXRob2QgdG8gcHJvdmlkZQogICAgICAgICAqIGRlc2VyaWFsaXphdGlvbiBmb3IgY3VzdG9tIGB0eXBlYHMuIFR5cGVzIGZvciBgQm9vbGVhbmAsIGBTdHJpbmdgLAogICAgICAgICAqIGFuZCBgTnVtYmVyYCBjb252ZXJ0IGF0dHJpYnV0ZXMgdG8gdGhlIGV4cGVjdGVkIHR5cGVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSB2YWx1ZSBWYWx1ZSB0byBkZXNlcmlhbGl6ZS4KICAgICAgICAgKiBAcGFyYW0geyo9fSB0eXBlIFR5cGUgdG8gZGVzZXJpYWxpemUgdGhlIHN0cmluZyB0by4KICAgICAgICAgKiBAcmV0dXJuIHsqfSBUeXBlZCB2YWx1ZSBkZXNlcmlhbGl6ZWQgZnJvbSB0aGUgcHJvdmlkZWQgc3RyaW5nLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9kZXNlcmlhbGl6ZVZhbHVlKHZhbHVlLCB0eXBlKSB7CiAgICAgICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICAgICAgY2FzZSBCb29sZWFuOgogICAgICAgICAgICAgIHJldHVybiAodmFsdWUgIT09IG51bGwpOwogICAgICAgICAgICBjYXNlIE51bWJlcjoKICAgICAgICAgICAgICByZXR1cm4gTnVtYmVyKHZhbHVlKTsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgfQoKICAgICAgcmV0dXJuIFByb3BlcnRpZXNDaGFuZ2VkOwogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyBTYXZlIG1hcCBvZiBuYXRpdmUgcHJvcGVydGllczsgdGhpcyBmb3JtcyBhIGJsYWNrbGlzdCBvciBwcm9wZXJ0aWVzCiAgICAvLyB0aGF0IHdvbid0IGhhdmUgdGhlaXIgdmFsdWVzICJzYXZlZCIgYnkgYHNhdmVBY2Nlc3NvclZhbHVlYCwgc2luY2UKICAgIC8vIHJlYWRpbmcgZnJvbSBhbiBIVE1MRWxlbWVudCBhY2Nlc3NvciBmcm9tIHRoZSBjb250ZXh0IG9mIGEgcHJvdG90eXBlIHRocm93cwogICAgY29uc3QgbmF0aXZlUHJvcGVydGllcyA9IHt9OwogICAgbGV0IHByb3RvID0gSFRNTEVsZW1lbnQucHJvdG90eXBlOwogICAgd2hpbGUgKHByb3RvKSB7CiAgICAgIGxldCBwcm9wcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKHByb3RvKTsKICAgICAgZm9yIChsZXQgaT0wOyBpPHByb3BzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgbmF0aXZlUHJvcGVydGllc1twcm9wc1tpXV0gPSB0cnVlOwogICAgICB9CiAgICAgIHByb3RvID0gT2JqZWN0LmdldFByb3RvdHlwZU9mKHByb3RvKTsKICAgIH0KCiAgICAvKioKICAgICAqIFVzZWQgdG8gc2F2ZSB0aGUgdmFsdWUgb2YgYSBwcm9wZXJ0eSB0aGF0IHdpbGwgYmUgb3ZlcnJpZGRlbiB3aXRoCiAgICAgKiBhbiBhY2Nlc3Nvci4gSWYgdGhlIGBtb2RlbGAgaXMgYSBwcm90b3R5cGUsIHRoZSB2YWx1ZXMgd2lsbCBiZSBzYXZlZAogICAgICogaW4gYF9fZGF0YVByb3RvYCwgYW5kIGl0J3MgdXAgdG8gdGhlIHVzZXIgKG9yIGRvd25zdHJlYW0gbWl4aW4pIHRvCiAgICAgKiBkZWNpZGUgaG93L3doZW4gdG8gc2V0IHRoZXNlIHZhbHVlcyBiYWNrIGludG8gdGhlIGFjY2Vzc29ycy4KICAgICAqIElmIGBtb2RlbGAgaXMgYWxyZWFkeSBhbiBpbnN0YW5jZSAoaXQgaGFzIGEgYF9fZGF0YWAgcHJvcGVydHkpLCB0aGVuCiAgICAgKiB0aGUgdmFsdWUgd2lsbCBiZSBzZXQgYXMgYSBwZW5kaW5nIHByb3BlcnR5LCBtZWFuaW5nIHRoZSB1c2VyIHNob3VsZAogICAgICogY2FsbCBgX2ludmFsaWRhdGVQcm9wZXJ0aWVzYCBvciBgX2ZsdXNoUHJvcGVydGllc2AgdG8gdGFrZSBlZmZlY3QKICAgICAqCiAgICAgKiBAcGFyYW0ge09iamVjdH0gbW9kZWwgUHJvdG90eXBlIG9yIGluc3RhbmNlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiBwcm9wZXJ0eQogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHNhdmVBY2Nlc3NvclZhbHVlKG1vZGVsLCBwcm9wZXJ0eSkgewogICAgICAvLyBEb24ndCByZWFkL3N0b3JlIHZhbHVlIGZvciBhbnkgbmF0aXZlIHByb3BlcnRpZXMgc2luY2UgdGhleSBjb3VsZCB0aHJvdwogICAgICBpZiAoIW5hdGl2ZVByb3BlcnRpZXNbcHJvcGVydHldKSB7CiAgICAgICAgbGV0IHZhbHVlID0gbW9kZWxbcHJvcGVydHldOwogICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICBpZiAobW9kZWwuX19kYXRhKSB7CiAgICAgICAgICAgIC8vIEFkZGluZyBhY2Nlc3NvciB0byBpbnN0YW5jZTsgdXBkYXRlIHRoZSBwcm9wZXJ0eQogICAgICAgICAgICAvLyBJdCBpcyB0aGUgdXNlcidzIHJlc3BvbnNpYmlsaXR5IHRvIGNhbGwgX2ZsdXNoUHJvcGVydGllcwogICAgICAgICAgICBtb2RlbC5fc2V0UGVuZGluZ1Byb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvLyBBZGRpbmcgYWNjZXNzb3IgdG8gcHJvdG87IHNhdmUgcHJvdG8ncyB2YWx1ZSBmb3IgaW5zdGFuY2UtdGltZSB1c2UKICAgICAgICAgICAgaWYgKCFtb2RlbC5fX2RhdGFQcm90bykgewogICAgICAgICAgICAgIG1vZGVsLl9fZGF0YVByb3RvID0ge307CiAgICAgICAgICAgIH0gZWxzZSBpZiAoIW1vZGVsLmhhc093blByb3BlcnR5KEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ19fZGF0YVByb3RvJywgbW9kZWwpKSkgewogICAgICAgICAgICAgIG1vZGVsLl9fZGF0YVByb3RvID0gT2JqZWN0LmNyZWF0ZShtb2RlbC5fX2RhdGFQcm90byk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbW9kZWwuX19kYXRhUHJvdG9bcHJvcGVydHldID0gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBFbGVtZW50IGNsYXNzIG1peGluIHRoYXQgcHJvdmlkZXMgYmFzaWMgbWV0YS1wcm9ncmFtbWluZyBmb3IgY3JlYXRpbmcgb25lCiAgICAgKiBvciBtb3JlIHByb3BlcnR5IGFjY2Vzc29ycyAoZ2V0dGVyL3NldHRlciBwYWlyKSB0aGF0IGVucXVldWUgYW4gYXN5bmMKICAgICAqIChiYXRjaGVkKSBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBjYWxsYmFjay4KICAgICAqCiAgICAgKiBGb3IgYmFzaWMgdXNhZ2Ugb2YgdGhpcyBtaXhpbjoKICAgICAqCiAgICAgKiAtICAgRGVjbGFyZSBhdHRyaWJ1dGVzIHRvIG9ic2VydmUgdmlhIHRoZSBzdGFuZGFyZCBgc3RhdGljIGdldAogICAgICogICAgIG9ic2VydmVkQXR0cmlidXRlcygpYC4gVXNlIGBkYXNoLWNhc2VgIGF0dHJpYnV0ZSBuYW1lcyB0byByZXByZXNlbnQKICAgICAqICAgICBgY2FtZWxDYXNlYCBwcm9wZXJ0eSBuYW1lcy4KICAgICAqIC0gICBJbXBsZW1lbnQgdGhlIGBfcHJvcGVydGllc0NoYW5nZWRgIGNhbGxiYWNrIG9uIHRoZSBjbGFzcy4KICAgICAqIC0gICBDYWxsIGBNeUNsYXNzLmNyZWF0ZVByb3BlcnRpZXNGb3JBdHRyaWJ1dGVzKClgICoqb25jZSoqIG9uIHRoZSBjbGFzcyB0bwogICAgICogICAgIGdlbmVyYXRlIHByb3BlcnR5IGFjY2Vzc29ycyBmb3IgZWFjaCBvYnNlcnZlZCBhdHRyaWJ1dGUuIFRoaXMgbXVzdCBiZQogICAgICogICAgIGNhbGxlZCBiZWZvcmUgdGhlIGZpcnN0IGluc3RhbmNlIGlzIGNyZWF0ZWQsIGZvciBleGFtcGxlLCBieSBjYWxsaW5nIGl0CiAgICAgKiAgICAgYmVmb3JlIGNhbGxpbmcgYGN1c3RvbUVsZW1lbnRzLmRlZmluZWAuIEl0IGNhbiBhbHNvIGJlIGNhbGxlZCBsYXppbHkgZnJvbQogICAgICogICAgIHRoZSBlbGVtZW50J3MgYGNvbnN0cnVjdG9yYCwgYXMgbG9uZyBhcyBpdCdzIGd1YXJkZWQgc28gdGhhdCB0aGUgY2FsbCBpcwogICAgICogICAgIG9ubHkgbWFkZSBvbmNlLCB3aGVuIHRoZSBmaXJzdCBpbnN0YW5jZSBpcyBjcmVhdGVkLgogICAgICogLSAgIENhbGwgYHRoaXMuX2VuYWJsZVByb3BlcnRpZXMoKWAgaW4gdGhlIGVsZW1lbnQncyBgY29ubmVjdGVkQ2FsbGJhY2tgIHRvCiAgICAgKiAgICAgZW5hYmxlIHRoZSBhY2Nlc3NvcnMuCiAgICAgKgogICAgICogQW55IGBvYnNlcnZlZEF0dHJpYnV0ZXNgIHdpbGwgYXV0b21hdGljYWxseSBiZQogICAgICogZGVzZXJpYWxpemVkIHZpYSBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCBhbmQgc2V0IHRvIHRoZSBhc3NvY2lhdGVkCiAgICAgKiBwcm9wZXJ0eSB1c2luZyBgZGFzaC1jYXNlYC10by1gY2FtZWxDYXNlYCBjb252ZW50aW9uLgogICAgICoKICAgICAqIEBtaXhpbkZ1bmN0aW9uCiAgICAgKiBAcG9seW1lcgogICAgICogQGFwcGxpZXNNaXhpbiBQcm9wZXJ0aWVzQ2hhbmdlZAogICAgICogQHN1bW1hcnkgRWxlbWVudCBjbGFzcyBtaXhpbiBmb3IgcmVhY3RpbmcgdG8gcHJvcGVydHkgY2hhbmdlcyBmcm9tCiAgICAgKiAgIGdlbmVyYXRlZCBwcm9wZXJ0eSBhY2Nlc3NvcnMuCiAgICAgKiBAdGVtcGxhdGUgVAogICAgICogQHBhcmFtIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3MgQ2xhc3MgdG8gYXBwbHkgbWl4aW4gdG8uCiAgICAgKiBAcmV0dXJuIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3Mgd2l0aCBtaXhpbiBhcHBsaWVkLgogICAgICovCiAgICBjb25zdCBQcm9wZXJ0eUFjY2Vzc29ycyA9IGRlZHVwaW5nTWl4aW4oc3VwZXJDbGFzcyA9PiB7CgogICAgICAvKioKICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1Byb3BlcnRpZXNDaGFuZ2VkfQogICAgICAgKiBAdW5yZXN0cmljdGVkCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICAgY29uc3QgYmFzZSA9IFByb3BlcnRpZXNDaGFuZ2VkKHN1cGVyQ2xhc3MpOwoKICAgICAgLyoqCiAgICAgICAqIEBwb2x5bWVyCiAgICAgICAqIEBtaXhpbkNsYXNzCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1Byb3BlcnR5QWNjZXNzb3JzfQogICAgICAgKiBAZXh0ZW5kcyB7YmFzZX0KICAgICAgICogQHVucmVzdHJpY3RlZAogICAgICAgKi8KICAgICAgY2xhc3MgUHJvcGVydHlBY2Nlc3NvcnMgZXh0ZW5kcyBiYXNlIHsKCiAgICAgICAgLyoqCiAgICAgICAgICogR2VuZXJhdGVzIHByb3BlcnR5IGFjY2Vzc29ycyBmb3IgYWxsIGF0dHJpYnV0ZXMgaW4gdGhlIHN0YW5kYXJkCiAgICAgICAgICogc3RhdGljIGBvYnNlcnZlZEF0dHJpYnV0ZXNgIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQXR0cmlidXRlIG5hbWVzIGFyZSBtYXBwZWQgdG8gcHJvcGVydHkgbmFtZXMgdXNpbmcgdGhlIGBkYXNoLWNhc2VgIHRvCiAgICAgICAgICogYGNhbWVsQ2FzZWAgY29udmVudGlvbgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBjcmVhdGVQcm9wZXJ0aWVzRm9yQXR0cmlidXRlcygpIHsKICAgICAgICAgIGxldCBhJCA9ICAvKiogQHR5cGUgez99ICovICh0aGlzKS5vYnNlcnZlZEF0dHJpYnV0ZXM7CiAgICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBhJC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fY3JlYXRlUHJvcGVydHlBY2Nlc3NvcihkYXNoVG9DYW1lbENhc2UoYSRbaV0pKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYW4gYXR0cmlidXRlIG5hbWUgdGhhdCBjb3JyZXNwb25kcyB0byB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICogQnkgZGVmYXVsdCwgY29udmVydHMgY2FtZWwgdG8gZGFzaCBjYXNlLCBlLmcuIGBmb29CYXJgIHRvIGBmb28tYmFyYC4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgdG8gY29udmVydAogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gQXR0cmlidXRlIG5hbWUgY29ycmVzcG9uZGluZyB0byB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgYXR0cmlidXRlTmFtZUZvclByb3BlcnR5KHByb3BlcnR5KSB7CiAgICAgICAgICByZXR1cm4gY2FtZWxUb0Rhc2hDYXNlKHByb3BlcnR5KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyBQcm9wZXJ0aWVzQ2hhbmdlZCBpbXBsZW1lbnRhdGlvbiB0byBpbml0aWFsaXplIHZhbHVlcyBmb3IKICAgICAgICAgKiBhY2Nlc3NvcnMgY3JlYXRlZCBmb3IgdmFsdWVzIHRoYXQgYWxyZWFkeSBleGlzdGVkIG9uIHRoZSBlbGVtZW50CiAgICAgICAgICogcHJvdG90eXBlLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2luaXRpYWxpemVQcm9wZXJ0aWVzKCkgewogICAgICAgICAgaWYgKHRoaXMuX19kYXRhUHJvdG8pIHsKICAgICAgICAgICAgdGhpcy5faW5pdGlhbGl6ZVByb3RvUHJvcGVydGllcyh0aGlzLl9fZGF0YVByb3RvKTsKICAgICAgICAgICAgdGhpcy5fX2RhdGFQcm90byA9IG51bGw7CiAgICAgICAgICB9CiAgICAgICAgICBzdXBlci5faW5pdGlhbGl6ZVByb3BlcnRpZXMoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxlZCBhdCBpbnN0YW5jZSB0aW1lIHdpdGggYmFnIG9mIHByb3BlcnRpZXMgdGhhdCB3ZXJlIG92ZXJ3cml0dGVuCiAgICAgICAgICogYnkgYWNjZXNzb3JzIG9uIHRoZSBwcm90b3R5cGUgd2hlbiBhY2Nlc3NvcnMgd2VyZSBjcmVhdGVkLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gc2V0cyB0aGVzZSBwcm9wZXJ0aWVzIGJhY2sgaW50byB0aGUKICAgICAgICAgKiBzZXR0ZXIgYXQgaW5zdGFuY2UgdGltZS4gIFRoaXMgbWV0aG9kIGlzIHByb3ZpZGVkIGFzIGFuIG92ZXJyaWRlCiAgICAgICAgICogcG9pbnQgZm9yIGN1c3RvbWl6aW5nIG9yIHByb3ZpZGluZyBtb3JlIGVmZmljaWVudCBpbml0aWFsaXphdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgcHJvcGVydHkgdmFsdWVzIHRoYXQgd2VyZSBvdmVyd3JpdHRlbgogICAgICAgICAqICAgd2hlbiBjcmVhdGluZyBwcm9wZXJ0eSBhY2Nlc3NvcnMuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2luaXRpYWxpemVQcm90b1Byb3BlcnRpZXMocHJvcHMpIHsKICAgICAgICAgIGZvciAobGV0IHAgaW4gcHJvcHMpIHsKICAgICAgICAgICAgdGhpcy5fc2V0UHJvcGVydHkocCwgcHJvcHNbcF0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRW5zdXJlcyB0aGUgZWxlbWVudCBoYXMgdGhlIGdpdmVuIGF0dHJpYnV0ZS4gSWYgaXQgZG9lcyBub3QsCiAgICAgICAgICogYXNzaWducyB0aGUgZ2l2ZW4gdmFsdWUgdG8gdGhlIGF0dHJpYnV0ZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfSBDbG9zdXJlIGNhbid0IGZpZ3VyZSBvdXQgYHRoaXNgIGlzIGluZmFjdCBhbgogICAgICAgICAqICAgICBlbGVtZW50CiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIE5hbWUgb2YgYXR0cmlidXRlIHRvIGVuc3VyZSBpcyBzZXQuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHZhbHVlIG9mIHRoZSBhdHRyaWJ1dGUuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfZW5zdXJlQXR0cmlidXRlKGF0dHJpYnV0ZSwgdmFsdWUpIHsKICAgICAgICAgIGNvbnN0IGVsID0gLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovKHRoaXMpOwogICAgICAgICAgaWYgKCFlbC5oYXNBdHRyaWJ1dGUoYXR0cmlidXRlKSkgewogICAgICAgICAgICB0aGlzLl92YWx1ZVRvTm9kZUF0dHJpYnV0ZShlbCwgdmFsdWUsIGF0dHJpYnV0ZSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgUHJvcGVydGllc0NoYW5nZWQgaW1wbGVtZW50aW9uIHRvIHNlcmlhbGl6ZSBvYmplY3RzIGFzIEpTT04uCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFByb3BlcnR5IHZhbHVlIHRvIHNlcmlhbGl6ZS4KICAgICAgICAgKiBAcmV0dXJuIHtzdHJpbmcgfCB1bmRlZmluZWR9IFN0cmluZyBzZXJpYWxpemVkIGZyb20gdGhlIHByb3ZpZGVkIHByb3BlcnR5CiAgICAgICAgICogICAgIHZhbHVlLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9zZXJpYWxpemVWYWx1ZSh2YWx1ZSkgewogICAgICAgICAgLyogZXNsaW50LWRpc2FibGUgbm8tZmFsbHRocm91Z2ggKi8KICAgICAgICAgIHN3aXRjaCAodHlwZW9mIHZhbHVlKSB7CiAgICAgICAgICAgIGNhc2UgJ29iamVjdCc6CiAgICAgICAgICAgICAgaWYgKHZhbHVlIGluc3RhbmNlb2YgRGF0ZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHZhbHVlLnRvU3RyaW5nKCk7CiAgICAgICAgICAgICAgfSBlbHNlIGlmICh2YWx1ZSkgewogICAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIEpTT04uc3RyaW5naWZ5KHZhbHVlKTsKICAgICAgICAgICAgICAgIH0gY2F0Y2goeCkgewogICAgICAgICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICByZXR1cm4gc3VwZXIuX3NlcmlhbGl6ZVZhbHVlKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGEgc3RyaW5nIHRvIGEgdHlwZWQgSmF2YVNjcmlwdCB2YWx1ZS4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGNhbGxlZCBieSBQb2x5bWVyIHdoZW4gcmVhZGluZyBIVE1MIGF0dHJpYnV0ZSB2YWx1ZXMgdG8KICAgICAgICAgKiBKUyBwcm9wZXJ0aWVzLiAgVXNlcnMgbWF5IG92ZXJyaWRlIHRoaXMgbWV0aG9kIG9uIFBvbHltZXIgZWxlbWVudAogICAgICAgICAqIHByb3RvdHlwZXMgdG8gcHJvdmlkZSBkZXNlcmlhbGl6YXRpb24gZm9yIGN1c3RvbSBgdHlwZWBzLiAgTm90ZSwKICAgICAgICAgKiB0aGUgYHR5cGVgIGFyZ3VtZW50IGlzIHRoZSB2YWx1ZSBvZiB0aGUgYHR5cGVgIGZpZWxkIHByb3ZpZGVkIGluIHRoZQogICAgICAgICAqIGBwcm9wZXJ0aWVzYCBjb25maWd1cmF0aW9uIG9iamVjdCBmb3IgYSBnaXZlbiBwcm9wZXJ0eSwgYW5kIGlzCiAgICAgICAgICogYnkgY29udmVudGlvbiB0aGUgY29uc3RydWN0b3IgZm9yIHRoZSB0eXBlIHRvIGRlc2VyaWFsaXplLgogICAgICAgICAqCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlIEF0dHJpYnV0ZSB2YWx1ZSB0byBkZXNlcmlhbGl6ZS4KICAgICAgICAgKiBAcGFyYW0geyo9fSB0eXBlIFR5cGUgdG8gZGVzZXJpYWxpemUgdGhlIHN0cmluZyB0by4KICAgICAgICAgKiBAcmV0dXJuIHsqfSBUeXBlZCB2YWx1ZSBkZXNlcmlhbGl6ZWQgZnJvbSB0aGUgcHJvdmlkZWQgc3RyaW5nLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9kZXNlcmlhbGl6ZVZhbHVlKHZhbHVlLCB0eXBlKSB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEB0eXBlIHsqfQogICAgICAgICAgICovCiAgICAgICAgICBsZXQgb3V0VmFsdWU7CiAgICAgICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICAgICAgY2FzZSBPYmplY3Q6CiAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgIG91dFZhbHVlID0gSlNPTi5wYXJzZSgvKiogQHR5cGUge3N0cmluZ30gKi8odmFsdWUpKTsKICAgICAgICAgICAgICB9IGNhdGNoKHgpIHsKICAgICAgICAgICAgICAgIC8vIGFsbG93IG5vbi1KU09OIGxpdGVyYWxzIGxpa2UgU3RyaW5ncyBhbmQgTnVtYmVycwogICAgICAgICAgICAgICAgb3V0VmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgQXJyYXk6CiAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgIG91dFZhbHVlID0gSlNPTi5wYXJzZSgvKiogQHR5cGUge3N0cmluZ30gKi8odmFsdWUpKTsKICAgICAgICAgICAgICB9IGNhdGNoKHgpIHsKICAgICAgICAgICAgICAgIG91dFZhbHVlID0gbnVsbDsKICAgICAgICAgICAgICAgIGNvbnNvbGUud2FybihgUG9seW1lcjo6QXR0cmlidXRlczogY291bGRuJ3QgZGVjb2RlIEFycmF5IGFzIEpTT046ICR7dmFsdWV9YCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIERhdGU6CiAgICAgICAgICAgICAgb3V0VmFsdWUgPSBpc05hTih2YWx1ZSkgPyBTdHJpbmcodmFsdWUpIDogTnVtYmVyKHZhbHVlKTsKICAgICAgICAgICAgICBvdXRWYWx1ZSA9IG5ldyBEYXRlKG91dFZhbHVlKTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICBvdXRWYWx1ZSA9IHN1cGVyLl9kZXNlcmlhbGl6ZVZhbHVlKHZhbHVlLCB0eXBlKTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBvdXRWYWx1ZTsKICAgICAgICB9CiAgICAgICAgLyogZXNsaW50LWVuYWJsZSBuby1mYWxsdGhyb3VnaCAqLwoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgUHJvcGVydGllc0NoYW5nZWQgaW1wbGVtZW50YXRpb24gdG8gc2F2ZSBleGlzdGluZyBwcm90b3R5cGUKICAgICAgICAgKiBwcm9wZXJ0eSB2YWx1ZSBzbyB0aGF0IGl0IGNhbiBiZSByZXNldC4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiB0aGUgcHJvcGVydHkKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW49fSByZWFkT25seSBXaGVuIHRydWUsIG5vIHNldHRlciBpcyBjcmVhdGVkCiAgICAgICAgICoKICAgICAgICAgKiBXaGVuIGNhbGxpbmcgb24gYSBwcm90b3R5cGUsIGFueSBvdmVyd3JpdHRlbiB2YWx1ZXMgYXJlIHNhdmVkIGluCiAgICAgICAgICogYF9fZGF0YVByb3RvYCwgYW5kIGl0IGlzIHVwIHRvIHRoZSBzdWJjbGFzc2VyIHRvIGRlY2lkZSBob3cvd2hlbgogICAgICAgICAqIHRvIHNldCB0aG9zZSBwcm9wZXJ0aWVzIGJhY2sgaW50byB0aGUgYWNjZXNzb3IuICBXaGVuIGNhbGxpbmcgb24gYW4KICAgICAgICAgKiBpbnN0YW5jZSwgdGhlIG92ZXJ3cml0dGVuIHZhbHVlIGlzIHNldCB2aWEgYF9zZXRQZW5kaW5nUHJvcGVydHlgLAogICAgICAgICAqIGFuZCB0aGUgdXNlciBzaG91bGQgY2FsbCBgX2ludmFsaWRhdGVQcm9wZXJ0aWVzYCBvciBgX2ZsdXNoUHJvcGVydGllc2AKICAgICAgICAgKiBmb3IgdGhlIHZhbHVlcyB0byB0YWtlIGVmZmVjdC4KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfZGVmaW5lUHJvcGVydHlBY2Nlc3Nvcihwcm9wZXJ0eSwgcmVhZE9ubHkpIHsKICAgICAgICAgIHNhdmVBY2Nlc3NvclZhbHVlKHRoaXMsIHByb3BlcnR5KTsKICAgICAgICAgIHN1cGVyLl9kZWZpbmVQcm9wZXJ0eUFjY2Vzc29yKHByb3BlcnR5LCByZWFkT25seSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhpcyBsaWJyYXJ5IGNyZWF0ZWQgYW4gYWNjZXNzb3IgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBhbiBhY2Nlc3NvciB3YXMgY3JlYXRlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9oYXNBY2Nlc3Nvcihwcm9wZXJ0eSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX19kYXRhSGFzQWNjZXNzb3IgJiYgdGhpcy5fX2RhdGFIYXNBY2Nlc3Nvcltwcm9wZXJ0eV07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCBwcm9wZXJ0eSBoYXMgYSBwZW5kaW5nIGNoYW5nZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wIFByb3BlcnR5IG5hbWUKICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHByb3BlcnR5IGhhcyBhIHBlbmRpbmcgY2hhbmdlCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9pc1Byb3BlcnR5UGVuZGluZyhwcm9wKSB7CiAgICAgICAgICByZXR1cm4gQm9vbGVhbih0aGlzLl9fZGF0YVBlbmRpbmcgJiYgKHByb3AgaW4gdGhpcy5fX2RhdGFQZW5kaW5nKSk7CiAgICAgICAgfQoKICAgICAgfQoKICAgICAgcmV0dXJuIFByb3BlcnR5QWNjZXNzb3JzOwoKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLy8gMS54IGJhY2t3YXJkcy1jb21wYXRpYmxlIGF1dG8td3JhcHBlciBmb3IgdGVtcGxhdGUgdHlwZSBleHRlbnNpb25zCiAgICAvLyBUaGlzIGlzIGEgY2xlYXIgbGF5ZXJpbmcgdmlvbGF0aW9uIGFuZCBnaXZlcyBmYXZvcmVkLW5hdGlvbiBzdGF0dXMgdG8KICAgIC8vIGRvbS1pZiBhbmQgZG9tLXJlcGVhdCB0ZW1wbGF0ZXMuICBUaGlzIGlzIGEgY29uY2VpdCB3ZSdyZSBjaG9vc2luZyB0byBrZWVwCiAgICAvLyBhLikgdG8gZWFzZSAxLnggYmFja3dhcmRzLWNvbXBhdGliaWxpdHkgZHVlIHRvIGxvc3Mgb2YgYGlzYCwgYW5kCiAgICAvLyBiLikgdG8gbWFpbnRhaW4gaWYvcmVwZWF0IGNhcGFiaWxpdHkgaW4gcGFyc2VyLWNvbnN0cmFpbmVkIGVsZW1lbnRzCiAgICAvLyAgICAgKGUuZy4gdGFibGUsIHNlbGVjdCkgaW4gbGlldSBvZiBuYXRpdmUgQ0UgdHlwZSBleHRlbnNpb25zIHdpdGhvdXQKICAgIC8vICAgICBtYXNzaXZlIG5ldyBpbnZlbnRpb24gaW4gdGhpcyBzcGFjZSAoZS5nLiBkaXJlY3RpdmUgc3lzdGVtKQogICAgY29uc3QgdGVtcGxhdGVFeHRlbnNpb25zID0gewogICAgICAnZG9tLWlmJzogdHJ1ZSwKICAgICAgJ2RvbS1yZXBlYXQnOiB0cnVlCiAgICB9OwoKICAgIGxldCBwbGFjZWhvbGRlckJ1Z0RldGVjdCA9IGZhbHNlOwogICAgbGV0IHBsYWNlaG9sZGVyQnVnID0gZmFsc2U7CgogICAgZnVuY3Rpb24gaGFzUGxhY2Vob2xkZXJCdWcoKSB7CiAgICAgIGlmICghcGxhY2Vob2xkZXJCdWdEZXRlY3QpIHsKICAgICAgICBwbGFjZWhvbGRlckJ1Z0RldGVjdCA9IHRydWU7CiAgICAgICAgY29uc3QgdCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RleHRhcmVhJyk7CiAgICAgICAgdC5wbGFjZWhvbGRlciA9ICdhJzsKICAgICAgICBwbGFjZWhvbGRlckJ1ZyA9IHQucGxhY2Vob2xkZXIgPT09IHQudGV4dENvbnRlbnQ7CiAgICAgIH0KICAgICAgcmV0dXJuIHBsYWNlaG9sZGVyQnVnOwogICAgfQoKICAgIC8qKgogICAgICogU29tZSBicm93c2VycyBoYXZlIGEgYnVnIHdpdGggdGV4dGFyZWEsIHdoZXJlIHBsYWNlaG9sZGVyIHRleHQgaXMgY29waWVkIGFzCiAgICAgKiBhIHRleHRub2RlIGNoaWxkIG9mIHRoZSB0ZXh0YXJlYS4KICAgICAqCiAgICAgKiBJZiB0aGUgcGxhY2Vob2xkZXIgaXMgYSBiaW5kaW5nLCB0aGlzIGNhbiBicmVhayB0ZW1wbGF0ZSBzdGFtcGluZyBpbiB0d28KICAgICAqIHdheXMuCiAgICAgKgogICAgICogT25lIGlzc3VlIGlzIHRoYXQgd2hlbiB0aGUgYHBsYWNlaG9sZGVyYCBhdHRyaWJ1dGUgaXMgcmVtb3ZlZCB3aGVuIHRoZQogICAgICogYmluZGluZyBpcyBwcm9jZXNzZWQsIHRoZSB0ZXh0bm9kZSBjaGlsZCBvZiB0aGUgdGV4dGFyZWEgaXMgZGVsZXRlZCwgYW5kIHRoZQogICAgICogdGVtcGxhdGUgaW5mbyB0cmllcyB0byBiaW5kIGludG8gdGhhdCBub2RlLgogICAgICoKICAgICAqIFdpdGggYGxlZ2FjeU9wdGltaXphdGlvbnNgIGluIHVzZSwgd2hlbiB0aGUgdGVtcGxhdGUgaXMgc3RhbXBlZCBhbmQgdGhlCiAgICAgKiBgdGV4dGFyZWEudGV4dENvbnRlbnRgIGJpbmRpbmcgaXMgcHJvY2Vzc2VkLCBubyBjb3JyZXNwb25kaW5nIG5vZGUgaXMgZm91bmQKICAgICAqIGJlY2F1c2UgaXQgd2FzIHJlbW92ZWQgZHVyaW5nIHBhcnNpbmcuIEFuIGV4Y2VwdGlvbiBpcyBnZW5lcmF0ZWQgd2hlbiB0aGlzCiAgICAgKiBiaW5kaW5nIGlzIHVwZGF0ZWQuCiAgICAgKgogICAgICogV2l0aCBgbGVnYWN5T3B0aW1pemF0aW9uc2Agbm90IGluIHVzZSwgdGhlIHRlbXBsYXRlIGlzIGNsb25lZCBiZWZvcmUKICAgICAqIHByb2Nlc3NpbmcgYW5kIHRoaXMgY2hhbmdlcyB0aGUgYWJvdmUgYmVoYXZpb3IuIFRoZSBjbG9uZWQgdGVtcGxhdGUgYWxzbyBoYXMKICAgICAqIGEgdmFsdWUgcHJvcGVydHkgc2V0IHRvIHRoZSBwbGFjZWhvbGRlciBhbmQgdGV4dENvbnRlbnQuIFRoaXMgcHJldmVudHMgdGhlCiAgICAgKiByZW1vdmFsIG9mIHRoZSB0ZXh0Q29udGVudCB3aGVuIHRoZSBwbGFjZWhvbGRlciBhdHRyaWJ1dGUgaXMgcmVtb3ZlZC4KICAgICAqIFRoZXJlZm9yZSB0aGUgZXhjZXB0aW9uIGRvZXMgbm90IG9jY3VyLiBIb3dldmVyLCB0aGVyZSBpcyBhbiBleHRyYQogICAgICogdW5uZWNlc3NhcnkgYmluZGluZy4KICAgICAqCiAgICAgKiBAcGFyYW0geyFOb2RlfSBub2RlIENoZWNrIG5vZGUgZm9yIHBsYWNlaG9sZGVyIGJ1ZwogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gZml4UGxhY2Vob2xkZXIobm9kZSkgewogICAgICBpZiAoaGFzUGxhY2Vob2xkZXJCdWcoKSAmJiBub2RlLmxvY2FsTmFtZSA9PT0gJ3RleHRhcmVhJyAmJiBub2RlLnBsYWNlaG9sZGVyCiAgICAgICAgICAgICYmIG5vZGUucGxhY2Vob2xkZXIgPT09IG5vZGUudGV4dENvbnRlbnQpIHsKICAgICAgICBub2RlLnRleHRDb250ZW50ID0gbnVsbDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHdyYXBUZW1wbGF0ZUV4dGVuc2lvbihub2RlKSB7CiAgICAgIGxldCBpcyA9IG5vZGUuZ2V0QXR0cmlidXRlKCdpcycpOwogICAgICBpZiAoaXMgJiYgdGVtcGxhdGVFeHRlbnNpb25zW2lzXSkgewogICAgICAgIGxldCB0ID0gbm9kZTsKICAgICAgICB0LnJlbW92ZUF0dHJpYnV0ZSgnaXMnKTsKICAgICAgICBub2RlID0gdC5vd25lckRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoaXMpOwogICAgICAgIHQucGFyZW50Tm9kZS5yZXBsYWNlQ2hpbGQobm9kZSwgdCk7CiAgICAgICAgbm9kZS5hcHBlbmRDaGlsZCh0KTsKICAgICAgICB3aGlsZSh0LmF0dHJpYnV0ZXMubGVuZ3RoKSB7CiAgICAgICAgICBub2RlLnNldEF0dHJpYnV0ZSh0LmF0dHJpYnV0ZXNbMF0ubmFtZSwgdC5hdHRyaWJ1dGVzWzBdLnZhbHVlKTsKICAgICAgICAgIHQucmVtb3ZlQXR0cmlidXRlKHQuYXR0cmlidXRlc1swXS5uYW1lKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgZnVuY3Rpb24gZmluZFRlbXBsYXRlTm9kZShyb290LCBub2RlSW5mbykgewogICAgICAvLyByZWN1cnNpdmVseSBhc2NlbmQgdHJlZSB1bnRpbCB3ZSBoaXQgcm9vdAogICAgICBsZXQgcGFyZW50ID0gbm9kZUluZm8ucGFyZW50SW5mbyAmJiBmaW5kVGVtcGxhdGVOb2RlKHJvb3QsIG5vZGVJbmZvLnBhcmVudEluZm8pOwogICAgICAvLyB1bndpbmQgdGhlIHN0YWNrLCByZXR1cm5pbmcgdGhlIGluZGV4ZWQgbm9kZSBhdCBlYWNoIGxldmVsCiAgICAgIGlmIChwYXJlbnQpIHsKICAgICAgICAvLyBub3RlOiBtYXJnaW5hbGx5IGZhc3RlciB0aGFuIGluZGV4aW5nIHZpYSBjaGlsZE5vZGVzCiAgICAgICAgLy8gKGh0dHA6Ly9qc3BlcmYuY29tL2NoaWxkbm9kZXMtbG9va3VwKQogICAgICAgIGZvciAobGV0IG49cGFyZW50LmZpcnN0Q2hpbGQsIGk9MDsgbjsgbj1uLm5leHRTaWJsaW5nKSB7CiAgICAgICAgICBpZiAobm9kZUluZm8ucGFyZW50SW5kZXggPT09IGkrKykgewogICAgICAgICAgICByZXR1cm4gbjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHJvb3Q7CiAgICAgIH0KICAgIH0KCiAgICAvLyBjb25zdHJ1Y3QgYCRgIG1hcCAoZnJvbSBpZCBhbm5vdGF0aW9ucykKICAgIGZ1bmN0aW9uIGFwcGx5SWRUb01hcChpbnN0LCBtYXAsIG5vZGUsIG5vZGVJbmZvKSB7CiAgICAgIGlmIChub2RlSW5mby5pZCkgewogICAgICAgIG1hcFtub2RlSW5mby5pZF0gPSBub2RlOwogICAgICB9CiAgICB9CgogICAgLy8gaW5zdGFsbCBldmVudCBsaXN0ZW5lcnMgKGZyb20gZXZlbnQgYW5ub3RhdGlvbnMpCiAgICBmdW5jdGlvbiBhcHBseUV2ZW50TGlzdGVuZXIoaW5zdCwgbm9kZSwgbm9kZUluZm8pIHsKICAgICAgaWYgKG5vZGVJbmZvLmV2ZW50cyAmJiBub2RlSW5mby5ldmVudHMubGVuZ3RoKSB7CiAgICAgICAgZm9yIChsZXQgaj0wLCBlJD1ub2RlSW5mby5ldmVudHMsIGU7IChqPGUkLmxlbmd0aCkgJiYgKGU9ZSRbal0pOyBqKyspIHsKICAgICAgICAgIGluc3QuX2FkZE1ldGhvZEV2ZW50TGlzdGVuZXJUb05vZGUobm9kZSwgZS5uYW1lLCBlLnZhbHVlLCBpbnN0KTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvLyBwdXNoIGNvbmZpZ3VyYXRpb24gcmVmZXJlbmNlcyBhdCBjb25maWd1cmUgdGltZQogICAgZnVuY3Rpb24gYXBwbHlUZW1wbGF0ZUluZm8oaW5zdCwgbm9kZSwgbm9kZUluZm8sIHBhcmVudFRlbXBsYXRlSW5mbykgewogICAgICBpZiAobm9kZUluZm8udGVtcGxhdGVJbmZvKSB7CiAgICAgICAgLy8gR2l2ZSB0aGUgbm9kZSBhbiBpbnN0YW5jZSBvZiB0aGlzIHRlbXBsYXRlSW5mbyBhbmQgc2V0IGl0cyBwYXJlbnQKICAgICAgICBub2RlLl90ZW1wbGF0ZUluZm8gPSBub2RlSW5mby50ZW1wbGF0ZUluZm87CiAgICAgICAgbm9kZS5fcGFyZW50VGVtcGxhdGVJbmZvID0gcGFyZW50VGVtcGxhdGVJbmZvOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlTm9kZUV2ZW50SGFuZGxlcihjb250ZXh0LCBldmVudE5hbWUsIG1ldGhvZE5hbWUpIHsKICAgICAgLy8gSW5zdGFuY2VzIGNhbiBvcHRpb25hbGx5IGhhdmUgYSBfbWV0aG9kSG9zdCB3aGljaCBhbGxvd3MgcmVkaXJlY3Rpbmcgd2hlcmUKICAgICAgLy8gdG8gZmluZCBtZXRob2RzLiBDdXJyZW50bHkgdXNlZCBieSBgdGVtcGxhdGl6ZWAuCiAgICAgIGNvbnRleHQgPSBjb250ZXh0Ll9tZXRob2RIb3N0IHx8IGNvbnRleHQ7CiAgICAgIGxldCBoYW5kbGVyID0gZnVuY3Rpb24oZSkgewogICAgICAgIGlmIChjb250ZXh0W21ldGhvZE5hbWVdKSB7CiAgICAgICAgICBjb250ZXh0W21ldGhvZE5hbWVdKGUsIGUuZGV0YWlsKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY29uc29sZS53YXJuKCdsaXN0ZW5lciBtZXRob2QgYCcgKyBtZXRob2ROYW1lICsgJ2Agbm90IGRlZmluZWQnKTsKICAgICAgICB9CiAgICAgIH07CiAgICAgIHJldHVybiBoYW5kbGVyOwogICAgfQoKICAgIC8qKgogICAgICogRWxlbWVudCBtaXhpbiB0aGF0IHByb3ZpZGVzIGJhc2ljIHRlbXBsYXRlIHBhcnNpbmcgYW5kIHN0YW1waW5nLCBpbmNsdWRpbmcKICAgICAqIHRoZSBmb2xsb3dpbmcgdGVtcGxhdGUtcmVsYXRlZCBmZWF0dXJlcyBmb3Igc3RhbXBlZCB0ZW1wbGF0ZXM6CiAgICAgKgogICAgICogLSBEZWNsYXJhdGl2ZSBldmVudCBsaXN0ZW5lcnMgKGBvbi1ldmVudG5hbWU9Imxpc3RlbmVyImApCiAgICAgKiAtIE1hcCBvZiBub2RlIGlkJ3MgdG8gc3RhbXBlZCBub2RlIGluc3RhbmNlcyAoYHRoaXMuJC5pZGApCiAgICAgKiAtIE5lc3RlZCB0ZW1wbGF0ZSBjb250ZW50IGNhY2hpbmcvcmVtb3ZhbCBhbmQgcmUtaW5zdGFsbGF0aW9uIChwZXJmb3JtYW5jZQogICAgICogICBvcHRpbWl6YXRpb24pCiAgICAgKgogICAgICogQG1peGluRnVuY3Rpb24KICAgICAqIEBwb2x5bWVyCiAgICAgKiBAc3VtbWFyeSBFbGVtZW50IGNsYXNzIG1peGluIHRoYXQgcHJvdmlkZXMgYmFzaWMgdGVtcGxhdGUgcGFyc2luZyBhbmQgc3RhbXBpbmcKICAgICAqLwogICAgY29uc3QgVGVtcGxhdGVTdGFtcCA9IGRlZHVwaW5nTWl4aW4oCiAgICAgICAgLyoqCiAgICAgICAgICogQHRlbXBsYXRlIFQKICAgICAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyBDbGFzcyB0byBhcHBseSBtaXhpbiB0by4KICAgICAgICAgKiBAcmV0dXJuIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3Mgd2l0aCBtaXhpbiBhcHBsaWVkLgogICAgICAgICAqLwogICAgICAgIChzdXBlckNsYXNzKSA9PiB7CgogICAgICAvKioKICAgICAgICogQHBvbHltZXIKICAgICAgICogQG1peGluQ2xhc3MKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfVGVtcGxhdGVTdGFtcH0KICAgICAgICovCiAgICAgIGNsYXNzIFRlbXBsYXRlU3RhbXAgZXh0ZW5kcyBzdXBlckNsYXNzIHsKCiAgICAgICAgLyoqCiAgICAgICAgICogU2NhbnMgYSB0ZW1wbGF0ZSB0byBwcm9kdWNlIHRlbXBsYXRlIG1ldGFkYXRhLgogICAgICAgICAqCiAgICAgICAgICogVGVtcGxhdGUtc3BlY2lmaWMgbWV0YWRhdGEgYXJlIHN0b3JlZCBpbiB0aGUgb2JqZWN0IHJldHVybmVkLCBhbmQgbm9kZS0KICAgICAgICAgKiBzcGVjaWZpYyBtZXRhZGF0YSBhcmUgc3RvcmVkIGluIG9iamVjdHMgaW4gaXRzIGZsYXR0ZW5lZCBgbm9kZUluZm9MaXN0YAogICAgICAgICAqIGFycmF5LiAgT25seSBub2RlcyBpbiB0aGUgdGVtcGxhdGUgdGhhdCB3ZXJlIHBhcnNlZCBhcyBub2RlcyBvZgogICAgICAgICAqIGludGVyZXN0IGNvbnRhaW4gYW4gb2JqZWN0IGluIGBub2RlSW5mb0xpc3RgLiAgRWFjaCBgbm9kZUluZm9gIG9iamVjdAogICAgICAgICAqIGNvbnRhaW5zIGFuIGBpbmRleGAgKGBjaGlsZE5vZGVzYCBpbmRleCBpbiBwYXJlbnQpIGFuZCBvcHRpb25hbGx5CiAgICAgICAgICogYHBhcmVudGAsIHdoaWNoIHBvaW50cyB0byBub2RlIGluZm8gb2YgaXRzIHBhcmVudCAoaW5jbHVkaW5nIGl0cyBpbmRleCkuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgdGVtcGxhdGUgbWV0YWRhdGEgb2JqZWN0IHJldHVybmVkIGZyb20gdGhpcyBtZXRob2QgaGFzIHRoZSBmb2xsb3dpbmcKICAgICAgICAgKiBzdHJ1Y3R1cmUgKG1hbnkgZmllbGRzIG9wdGlvbmFsKToKICAgICAgICAgKgogICAgICAgICAqIGBgYGpzCiAgICAgICAgICogICB7CiAgICAgICAgICogICAgIC8vIEZsYXR0ZW5lZCBsaXN0IG9mIG5vZGUgbWV0YWRhdGEgKGZvciBub2RlcyB0aGF0IGdlbmVyYXRlZCBtZXRhZGF0YSkKICAgICAgICAgKiAgICAgbm9kZUluZm9MaXN0OiBbCiAgICAgICAgICogICAgICAgewogICAgICAgICAqICAgICAgICAgLy8gYGlkYCBhdHRyaWJ1dGUgZm9yIGFueSBub2RlcyB3aXRoIGlkJ3MgZm9yIGdlbmVyYXRpbmcgYCRgIG1hcAogICAgICAgICAqICAgICAgICAgaWQ6IHtzdHJpbmd9LAogICAgICAgICAqICAgICAgICAgLy8gYG9uLWV2ZW50PSJoYW5kbGVyImAgbWV0YWRhdGEKICAgICAgICAgKiAgICAgICAgIGV2ZW50czogWwogICAgICAgICAqICAgICAgICAgICB7CiAgICAgICAgICogICAgICAgICAgICAgbmFtZToge3N0cmluZ30sICAgLy8gZXZlbnQgbmFtZQogICAgICAgICAqICAgICAgICAgICAgIHZhbHVlOiB7c3RyaW5nfSwgIC8vIGhhbmRsZXIgbWV0aG9kIG5hbWUKICAgICAgICAgKiAgICAgICAgICAgfSwgLi4uCiAgICAgICAgICogICAgICAgICBdLAogICAgICAgICAqICAgICAgICAgLy8gTm90ZXMgd2hlbiB0aGUgdGVtcGxhdGUgY29udGFpbmVkIGEgYDxzbG90PmAgZm9yIHNoYWR5IERPTQogICAgICAgICAqICAgICAgICAgLy8gb3B0aW1pemF0aW9uIHB1cnBvc2VzCiAgICAgICAgICogICAgICAgICBoYXNJbnNlcnRpb25Qb2ludDoge2Jvb2xlYW59LAogICAgICAgICAqICAgICAgICAgLy8gRm9yIG5lc3RlZCBgPHRlbXBsYXRlPmBgIG5vZGVzLCBuZXN0ZWQgdGVtcGxhdGUgbWV0YWRhdGEKICAgICAgICAgKiAgICAgICAgIHRlbXBsYXRlSW5mbzoge29iamVjdH0sIC8vIG5lc3RlZCB0ZW1wbGF0ZSBtZXRhZGF0YQogICAgICAgICAqICAgICAgICAgLy8gTWV0YWRhdGEgdG8gYWxsb3cgZWZmaWNpZW50IHJldHJpZXZhbCBvZiBpbnN0YW5jZWQgbm9kZQogICAgICAgICAqICAgICAgICAgLy8gY29ycmVzcG9uZGluZyB0byB0aGlzIG1ldGFkYXRhCiAgICAgICAgICogICAgICAgICBwYXJlbnRJbmZvOiB7bnVtYmVyfSwgICAvLyByZWZlcmVuY2UgdG8gcGFyZW50IG5vZGVJbmZvPgogICAgICAgICAqICAgICAgICAgcGFyZW50SW5kZXg6IHtudW1iZXJ9LCAgLy8gaW5kZXggaW4gcGFyZW50J3MgYGNoaWxkTm9kZXNgIGNvbGxlY3Rpb24KICAgICAgICAgKiAgICAgICAgIGluZm9JbmRleDoge251bWJlcn0sICAgIC8vIGluZGV4IG9mIHRoaXMgYG5vZGVJbmZvYCBpbiBgdGVtcGxhdGVJbmZvLm5vZGVJbmZvTGlzdGAKICAgICAgICAgKiAgICAgICB9LAogICAgICAgICAqICAgICAgIC4uLgogICAgICAgICAqICAgICBdLAogICAgICAgICAqICAgICAvLyBXaGVuIHRydWUsIHRoZSB0ZW1wbGF0ZSBoYWQgdGhlIGBzdHJpcC13aGl0ZXNwYWNlYCBhdHRyaWJ1dGUKICAgICAgICAgKiAgICAgLy8gb3Igd2FzIG5lc3RlZCBpbiBhIHRlbXBsYXRlIHdpdGggdGhhdCBzZXR0aW5nCiAgICAgICAgICogICAgIHN0cmlwV2hpdGVzcGFjZToge2Jvb2xlYW59LAogICAgICAgICAqICAgICAvLyBGb3IgbmVzdGVkIHRlbXBsYXRlcywgbmVzdGVkIHRlbXBsYXRlIGNvbnRlbnQgaXMgbW92ZWQgaW50bwogICAgICAgICAqICAgICAvLyBhIGRvY3VtZW50IGZyYWdtZW50IHN0b3JlZCBoZXJlOyB0aGlzIGlzIGFuIG9wdGltaXphdGlvbiB0bwogICAgICAgICAqICAgICAvLyBhdm9pZCB0aGUgY29zdCBvZiBuZXN0ZWQgdGVtcGxhdGUgY2xvbmluZwogICAgICAgICAqICAgICBjb250ZW50OiB7RG9jdW1lbnRGcmFnbWVudH0KICAgICAgICAgKiAgIH0KICAgICAgICAgKiBgYGAKICAgICAgICAgKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGtpY2tzIG9mZiBhIHJlY3Vyc2l2ZSB0cmVld2FsayBhcyBmb2xsb3dzOgogICAgICAgICAqCiAgICAgICAgICogYGBgCiAgICAgICAgICogICAgX3BhcnNlVGVtcGxhdGUgPC0tLS0tLS0tLS0tLS0tLS0tLS0tLSsKICAgICAgICAgKiAgICAgIF9wYXJzZVRlbXBsYXRlQ29udGVudCAgICAgICAgICAgICAgfAogICAgICAgICAqICAgICAgICBfcGFyc2VUZW1wbGF0ZU5vZGUgIDwtLS0tLS0tLS0tLS18LS0rCiAgICAgICAgICogICAgICAgICAgX3BhcnNlVGVtcGxhdGVOZXN0ZWRUZW1wbGF0ZSAtLSsgIHwKICAgICAgICAgKiAgICAgICAgICBfcGFyc2VUZW1wbGF0ZUNoaWxkTm9kZXMgLS0tLS0tLS0tKwogICAgICAgICAqICAgICAgICAgIF9wYXJzZVRlbXBsYXRlTm9kZUF0dHJpYnV0ZXMKICAgICAgICAgKiAgICAgICAgICAgIF9wYXJzZVRlbXBsYXRlTm9kZUF0dHJpYnV0ZQogICAgICAgICAqCiAgICAgICAgICogYGBgCiAgICAgICAgICoKICAgICAgICAgKiBUaGVzZSBtZXRob2RzIG1heSBiZSBvdmVycmlkZGVuIHRvIGFkZCBjdXN0b20gbWV0YWRhdGEgYWJvdXQgdGVtcGxhdGVzCiAgICAgICAgICogdG8gZWl0aGVyIGB0ZW1wbGF0ZUluZm9gIG9yIGBub2RlSW5mb2AuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlIHRoYXQgdGhpcyBtZXRob2QgbWF5IGJlIGRlc3RydWN0aXZlIHRvIHRoZSB0ZW1wbGF0ZSwgaW4gdGhhdAogICAgICAgICAqIGUuZy4gZXZlbnQgYW5ub3RhdGlvbnMgbWF5IGJlIHJlbW92ZWQgYWZ0ZXIgYmVpbmcgbm90ZWQgaW4gdGhlCiAgICAgICAgICogdGVtcGxhdGUgbWV0YWRhdGEuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZSBUZW1wbGF0ZSB0byBwYXJzZQogICAgICAgICAqIEBwYXJhbSB7VGVtcGxhdGVJbmZvPX0gb3V0ZXJUZW1wbGF0ZUluZm8gVGVtcGxhdGUgbWV0YWRhdGEgZnJvbSB0aGUgb3V0ZXIKICAgICAgICAgKiAgIHRlbXBsYXRlLCBmb3IgcGFyc2luZyBuZXN0ZWQgdGVtcGxhdGVzCiAgICAgICAgICogQHJldHVybiB7IVRlbXBsYXRlSW5mb30gUGFyc2VkIHRlbXBsYXRlIG1ldGFkYXRhCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3BhcnNlVGVtcGxhdGUodGVtcGxhdGUsIG91dGVyVGVtcGxhdGVJbmZvKSB7CiAgICAgICAgICAvLyBzaW5jZSBhIHRlbXBsYXRlIG1heSBiZSByZS11c2VkLCBtZW1vLWl6ZSBtZXRhZGF0YQogICAgICAgICAgaWYgKCF0ZW1wbGF0ZS5fdGVtcGxhdGVJbmZvKSB7CiAgICAgICAgICAgIC8vIFRPRE8ocmljdGljKTogZml4IHR5cGluZwogICAgICAgICAgICBsZXQgLyoqID8gKi8gdGVtcGxhdGVJbmZvID0gdGVtcGxhdGUuX3RlbXBsYXRlSW5mbyA9IHt9OwogICAgICAgICAgICB0ZW1wbGF0ZUluZm8ubm9kZUluZm9MaXN0ID0gW107CiAgICAgICAgICAgIHRlbXBsYXRlSW5mby5uZXN0ZWRUZW1wbGF0ZSA9IEJvb2xlYW4ob3V0ZXJUZW1wbGF0ZUluZm8pOwogICAgICAgICAgICB0ZW1wbGF0ZUluZm8uc3RyaXBXaGl0ZVNwYWNlID0KICAgICAgICAgICAgICAob3V0ZXJUZW1wbGF0ZUluZm8gJiYgb3V0ZXJUZW1wbGF0ZUluZm8uc3RyaXBXaGl0ZVNwYWNlKSB8fAogICAgICAgICAgICAgIHRlbXBsYXRlLmhhc0F0dHJpYnV0ZSgnc3RyaXAtd2hpdGVzcGFjZScpOwogICAgICAgICAgICAgLy8gVE9ETyhyaWN0aWMpOiBmaXggdHlwaW5nCiAgICAgICAgICAgICB0aGlzLl9wYXJzZVRlbXBsYXRlQ29udGVudCgKICAgICAgICAgICAgICAgICB0ZW1wbGF0ZSwgdGVtcGxhdGVJbmZvLCAvKiogQHR5cGUgez99ICovICh7cGFyZW50OiBudWxsfSkpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRlbXBsYXRlLl90ZW1wbGF0ZUluZm87CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZWUgZG9jcyBmb3IgX3BhcnNlVGVtcGxhdGVOb2RlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUgLgogICAgICAgICAqIEBwYXJhbSB7IVRlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIC4KICAgICAgICAgKiBAcGFyYW0geyFOb2RlSW5mb30gbm9kZUluZm8gLgogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IC4KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZUNvbnRlbnQodGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9wYXJzZVRlbXBsYXRlTm9kZSh0ZW1wbGF0ZS5jb250ZW50LCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBhcnNlcyB0ZW1wbGF0ZSBub2RlIGFuZCBhZGRzIHRlbXBsYXRlIGFuZCBub2RlIG1ldGFkYXRhIGJhc2VkIG9uCiAgICAgICAgICogdGhlIGN1cnJlbnQgbm9kZSwgYW5kIGl0cyBgY2hpbGROb2Rlc2AgYW5kIGBhdHRyaWJ1dGVzYC4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgbWV0aG9kIG1heSBiZSBvdmVycmlkZGVuIHRvIGFkZCBjdXN0b20gbm9kZSBvciB0ZW1wbGF0ZSBzcGVjaWZpYwogICAgICAgICAqIG1ldGFkYXRhIGJhc2VkIG9uIHRoaXMgbm9kZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7Tm9kZX0gbm9kZSBOb2RlIHRvIHBhcnNlCiAgICAgICAgICogQHBhcmFtIHshVGVtcGxhdGVJbmZvfSB0ZW1wbGF0ZUluZm8gVGVtcGxhdGUgbWV0YWRhdGEgZm9yIGN1cnJlbnQgdGVtcGxhdGUKICAgICAgICAgKiBAcGFyYW0geyFOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZS4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBgdHJ1ZWAgaWYgdGhlIHZpc2l0ZWQgbm9kZSBhZGRlZCBub2RlLXNwZWNpZmljCiAgICAgICAgICogICBtZXRhZGF0YSB0byBgbm9kZUluZm9gCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3BhcnNlVGVtcGxhdGVOb2RlKG5vZGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pIHsKICAgICAgICAgIGxldCBub3RlZCA9IGZhbHNlOwogICAgICAgICAgbGV0IGVsZW1lbnQgPSAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fSAqLyAobm9kZSk7CiAgICAgICAgICBpZiAoZWxlbWVudC5sb2NhbE5hbWUgPT0gJ3RlbXBsYXRlJyAmJiAhZWxlbWVudC5oYXNBdHRyaWJ1dGUoJ3ByZXNlcnZlLWNvbnRlbnQnKSkgewogICAgICAgICAgICBub3RlZCA9IHRoaXMuX3BhcnNlVGVtcGxhdGVOZXN0ZWRUZW1wbGF0ZShlbGVtZW50LCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKSB8fCBub3RlZDsKICAgICAgICAgIH0gZWxzZSBpZiAoZWxlbWVudC5sb2NhbE5hbWUgPT09ICdzbG90JykgewogICAgICAgICAgICAvLyBGb3IgU2hhZHlEb20gb3B0aW1pemF0aW9uLCBpbmRpY2F0aW5nIHRoZXJlIGlzIGFuIGluc2VydGlvbiBwb2ludAogICAgICAgICAgICB0ZW1wbGF0ZUluZm8uaGFzSW5zZXJ0aW9uUG9pbnQgPSB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgZml4UGxhY2Vob2xkZXIoZWxlbWVudCk7CiAgICAgICAgICBpZiAoZWxlbWVudC5maXJzdENoaWxkKSB7CiAgICAgICAgICAgIHRoaXMuX3BhcnNlVGVtcGxhdGVDaGlsZE5vZGVzKGVsZW1lbnQsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGVsZW1lbnQuaGFzQXR0cmlidXRlcyAmJiBlbGVtZW50Lmhhc0F0dHJpYnV0ZXMoKSkgewogICAgICAgICAgICBub3RlZCA9IHRoaXMuX3BhcnNlVGVtcGxhdGVOb2RlQXR0cmlidXRlcyhlbGVtZW50LCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKSB8fCBub3RlZDsKICAgICAgICAgIH0KICAgICAgICAgIC8vIENoZWNraW5nIGBub2RlSW5mby5ub3RlZGAgYWxsb3dzIGEgY2hpbGQgbm9kZSBvZiB0aGlzIG5vZGUgKHdobyBnZXRzCiAgICAgICAgICAvLyBhY2Nlc3MgdG8gYHBhcmVudEluZm9gKSB0byBjYXVzZSB0aGUgcGFyZW50IHRvIGJlIG5vdGVkLCB3aGljaAogICAgICAgICAgLy8gb3RoZXJ3aXNlIGhhcyBubyByZXR1cm4gcGF0aCB2aWEgYF9wYXJzZVRlbXBsYXRlQ2hpbGROb2Rlc2AgKHVzZWQgYnkKICAgICAgICAgIC8vIHNvbWUgb3B0aW1pemF0aW9ucykKICAgICAgICAgIHJldHVybiBub3RlZCB8fCBub2RlSW5mby5ub3RlZDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBhcnNlcyB0ZW1wbGF0ZSBjaGlsZCBub2RlcyBmb3IgdGhlIGdpdmVuIHJvb3Qgbm9kZS4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGFsc28gd3JhcHMgd2hpdGVsaXN0ZWQgbGVnYWN5IHRlbXBsYXRlIGV4dGVuc2lvbnMKICAgICAgICAgKiAoYGlzPSJkb20taWYiYCBhbmQgYGlzPSJkb20tcmVwZWF0ImApIHdpdGggdGhlaXIgZXF1aXZhbGVudCBlbGVtZW50CiAgICAgICAgICogd3JhcHBlcnMsIGNvbGxhcHNlcyB0ZXh0IG5vZGVzLCBhbmQgc3RyaXBzIHdoaXRlc3BhY2UgZnJvbSB0aGUgdGVtcGxhdGUKICAgICAgICAgKiBpZiB0aGUgYHRlbXBsYXRlSW5mby5zdHJpcFdoaXRlc3BhY2VgIHNldHRpbmcgd2FzIHByb3ZpZGVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtOb2RlfSByb290IFJvb3Qgbm9kZSB3aG9zZSBgY2hpbGROb2Rlc2Agd2lsbCBiZSBwYXJzZWQKICAgICAgICAgKiBAcGFyYW0geyFUZW1wbGF0ZUluZm99IHRlbXBsYXRlSW5mbyBUZW1wbGF0ZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZQogICAgICAgICAqIEBwYXJhbSB7IU5vZGVJbmZvfSBub2RlSW5mbyBOb2RlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgc3RhdGljIF9wYXJzZVRlbXBsYXRlQ2hpbGROb2Rlcyhyb290LCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKSB7CiAgICAgICAgICBpZiAocm9vdC5sb2NhbE5hbWUgPT09ICdzY3JpcHQnIHx8IHJvb3QubG9jYWxOYW1lID09PSAnc3R5bGUnKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIGZvciAobGV0IG5vZGU9cm9vdC5maXJzdENoaWxkLCBwYXJlbnRJbmRleD0wLCBuZXh0OyBub2RlOyBub2RlPW5leHQpIHsKICAgICAgICAgICAgLy8gV3JhcCB0ZW1wbGF0ZXMKICAgICAgICAgICAgaWYgKG5vZGUubG9jYWxOYW1lID09ICd0ZW1wbGF0ZScpIHsKICAgICAgICAgICAgICBub2RlID0gd3JhcFRlbXBsYXRlRXh0ZW5zaW9uKG5vZGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIGNvbGxhcHNlIGFkamFjZW50IHRleHROb2RlczogZml4ZXMgYW4gSUUgaXNzdWUgdGhhdCBjYW4gY2F1c2UKICAgICAgICAgICAgLy8gdGV4dCBub2RlcyB0byBiZSBpbmV4cGxpY2FibHkgc3BsaXQgPSgKICAgICAgICAgICAgLy8gbm90ZSB0aGF0IHJvb3Qubm9ybWFsaXplKCkgc2hvdWxkIHdvcmsgYnV0IGRvZXMgbm90IHNvIHdlIGRvIHRoaXMKICAgICAgICAgICAgLy8gbWFudWFsbHkuCiAgICAgICAgICAgIG5leHQgPSBub2RlLm5leHRTaWJsaW5nOwogICAgICAgICAgICBpZiAobm9kZS5ub2RlVHlwZSA9PT0gTm9kZS5URVhUX05PREUpIHsKICAgICAgICAgICAgICBsZXQgLyoqIE5vZGUgKi8gbiA9IG5leHQ7CiAgICAgICAgICAgICAgd2hpbGUgKG4gJiYgKG4ubm9kZVR5cGUgPT09IE5vZGUuVEVYVF9OT0RFKSkgewogICAgICAgICAgICAgICAgbm9kZS50ZXh0Q29udGVudCArPSBuLnRleHRDb250ZW50OwogICAgICAgICAgICAgICAgbmV4dCA9IG4ubmV4dFNpYmxpbmc7CiAgICAgICAgICAgICAgICByb290LnJlbW92ZUNoaWxkKG4pOwogICAgICAgICAgICAgICAgbiA9IG5leHQ7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIC8vIG9wdGlvbmFsbHkgc3RyaXAgd2hpdGVzcGFjZQogICAgICAgICAgICAgIGlmICh0ZW1wbGF0ZUluZm8uc3RyaXBXaGl0ZVNwYWNlICYmICFub2RlLnRleHRDb250ZW50LnRyaW0oKSkgewogICAgICAgICAgICAgICAgcm9vdC5yZW1vdmVDaGlsZChub2RlKTsKICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgY2hpbGRJbmZvID0KICAgICAgICAgICAgICAgIC8qKiBAdHlwZSB7IU5vZGVJbmZvfSAqLyAoe3BhcmVudEluZGV4LCBwYXJlbnRJbmZvOiBub2RlSW5mb30pOwogICAgICAgICAgICBpZiAodGhpcy5fcGFyc2VUZW1wbGF0ZU5vZGUobm9kZSwgdGVtcGxhdGVJbmZvLCBjaGlsZEluZm8pKSB7CiAgICAgICAgICAgICAgY2hpbGRJbmZvLmluZm9JbmRleCA9IHRlbXBsYXRlSW5mby5ub2RlSW5mb0xpc3QucHVzaChjaGlsZEluZm8pIC0gMTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBJbmNyZW1lbnQgaWYgbm90IHJlbW92ZWQKICAgICAgICAgICAgaWYgKG5vZGUucGFyZW50Tm9kZSkgewogICAgICAgICAgICAgIHBhcmVudEluZGV4Kys7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBhcnNlcyB0ZW1wbGF0ZSBjb250ZW50IGZvciB0aGUgZ2l2ZW4gbmVzdGVkIGA8dGVtcGxhdGU+YC4KICAgICAgICAgKgogICAgICAgICAqIE5lc3RlZCB0ZW1wbGF0ZSBpbmZvIGlzIHN0b3JlZCBhcyBgdGVtcGxhdGVJbmZvYCBpbiB0aGUgY3VycmVudCBub2RlJ3MKICAgICAgICAgKiBgbm9kZUluZm9gLiBgdGVtcGxhdGUuY29udGVudGAgaXMgcmVtb3ZlZCBhbmQgc3RvcmVkIGluIGB0ZW1wbGF0ZUluZm9gLgogICAgICAgICAqIEl0IHdpbGwgdGhlbiBiZSB0aGUgcmVzcG9uc2liaWxpdHkgb2YgdGhlIGhvc3QgdG8gc2V0IGl0IGJhY2sgdG8gdGhlCiAgICAgICAgICogdGVtcGxhdGUgYW5kIGZvciB1c2VycyBzdGFtcGluZyBuZXN0ZWQgdGVtcGxhdGVzIHRvIHVzZSB0aGUKICAgICAgICAgKiBgX2NvbnRlbnRGb3JUZW1wbGF0ZWAgbWV0aG9kIHRvIHJldHJpZXZlIHRoZSBjb250ZW50IGZvciB0aGlzIHRlbXBsYXRlCiAgICAgICAgICogKGFuIG9wdGltaXphdGlvbiB0byBhdm9pZCB0aGUgY29zdCBvZiBjbG9uaW5nIG5lc3RlZCB0ZW1wbGF0ZSBjb250ZW50KS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7SFRNTFRlbXBsYXRlRWxlbWVudH0gbm9kZSBOb2RlIHRvIHBhcnNlIChhIDx0ZW1wbGF0ZT4pCiAgICAgICAgICogQHBhcmFtIHtUZW1wbGF0ZUluZm99IG91dGVyVGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgICAgICogICB0aGF0IGluY2x1ZGVzIHRoZSB0ZW1wbGF0ZSBgbm9kZWAKICAgICAgICAgKiBAcGFyYW0geyFOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZS4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBgdHJ1ZWAgaWYgdGhlIHZpc2l0ZWQgbm9kZSBhZGRlZCBub2RlLXNwZWNpZmljCiAgICAgICAgICogICBtZXRhZGF0YSB0byBgbm9kZUluZm9gCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3BhcnNlVGVtcGxhdGVOZXN0ZWRUZW1wbGF0ZShub2RlLCBvdXRlclRlbXBsYXRlSW5mbywgbm9kZUluZm8pIHsKICAgICAgICAgIC8vIFRPRE8ocmljdGljKTogdGhlIHR5cGUgb2Ygbm9kZSBzaG91bGQgYmUgbm9uLW51bGwKICAgICAgICAgIGxldCBlbGVtZW50ID0gLyoqIEB0eXBlIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKG5vZGUpOwogICAgICAgICAgbGV0IHRlbXBsYXRlSW5mbyA9IHRoaXMuX3BhcnNlVGVtcGxhdGUoZWxlbWVudCwgb3V0ZXJUZW1wbGF0ZUluZm8pOwogICAgICAgICAgbGV0IGNvbnRlbnQgPSB0ZW1wbGF0ZUluZm8uY29udGVudCA9CiAgICAgICAgICAgICAgZWxlbWVudC5jb250ZW50Lm93bmVyRG9jdW1lbnQuY3JlYXRlRG9jdW1lbnRGcmFnbWVudCgpOwogICAgICAgICAgY29udGVudC5hcHBlbmRDaGlsZChlbGVtZW50LmNvbnRlbnQpOwogICAgICAgICAgbm9kZUluZm8udGVtcGxhdGVJbmZvID0gdGVtcGxhdGVJbmZvOwogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQYXJzZXMgdGVtcGxhdGUgbm9kZSBhdHRyaWJ1dGVzIGFuZCBhZGRzIG5vZGUgbWV0YWRhdGEgdG8gYG5vZGVJbmZvYAogICAgICAgICAqIGZvciBub2RlcyBvZiBpbnRlcmVzdC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RWxlbWVudH0gbm9kZSBOb2RlIHRvIHBhcnNlCiAgICAgICAgICogQHBhcmFtIHshVGVtcGxhdGVJbmZvfSB0ZW1wbGF0ZUluZm8gVGVtcGxhdGUgbWV0YWRhdGEgZm9yIGN1cnJlbnQKICAgICAgICAgKiAgICAgdGVtcGxhdGUKICAgICAgICAgKiBAcGFyYW0geyFOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZS4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBgdHJ1ZWAgaWYgdGhlIHZpc2l0ZWQgbm9kZSBhZGRlZCBub2RlLXNwZWNpZmljCiAgICAgICAgICogICBtZXRhZGF0YSB0byBgbm9kZUluZm9gCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3BhcnNlVGVtcGxhdGVOb2RlQXR0cmlidXRlcyhub2RlLCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKSB7CiAgICAgICAgICAvLyBNYWtlIGNvcHkgb2Ygb3JpZ2luYWwgYXR0cmlidXRlIGxpc3QsIHNpbmNlIHRoZSBvcmRlciBtYXkgY2hhbmdlCiAgICAgICAgICAvLyBhcyBhdHRyaWJ1dGVzIGFyZSBhZGRlZCBhbmQgcmVtb3ZlZAogICAgICAgICAgbGV0IG5vdGVkID0gZmFsc2U7CiAgICAgICAgICBsZXQgYXR0cnMgPSBBcnJheS5mcm9tKG5vZGUuYXR0cmlidXRlcyk7CiAgICAgICAgICBmb3IgKGxldCBpPWF0dHJzLmxlbmd0aC0xLCBhOyAoYT1hdHRyc1tpXSk7IGktLSkgewogICAgICAgICAgICBub3RlZCA9IHRoaXMuX3BhcnNlVGVtcGxhdGVOb2RlQXR0cmlidXRlKG5vZGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8sIGEubmFtZSwgYS52YWx1ZSkgfHwgbm90ZWQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbm90ZWQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQYXJzZXMgYSBzaW5nbGUgdGVtcGxhdGUgbm9kZSBhdHRyaWJ1dGUgYW5kIGFkZHMgbm9kZSBtZXRhZGF0YSB0bwogICAgICAgICAqIGBub2RlSW5mb2AgZm9yIGF0dHJpYnV0ZXMgb2YgaW50ZXJlc3QuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIGltcGxlbWVudGF0aW9uIGFkZHMgbWV0YWRhdGEgZm9yIGBvbi1ldmVudD0iaGFuZGxlciJgIGF0dHJpYnV0ZXMKICAgICAgICAgKiBhbmQgYGlkYCBhdHRyaWJ1dGVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBub2RlIE5vZGUgdG8gcGFyc2UKICAgICAgICAgKiBAcGFyYW0geyFUZW1wbGF0ZUluZm99IHRlbXBsYXRlSW5mbyBUZW1wbGF0ZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZQogICAgICAgICAqIEBwYXJhbSB7IU5vZGVJbmZvfSBub2RlSW5mbyBOb2RlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIEF0dHJpYnV0ZSBuYW1lCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHZhbHVlIEF0dHJpYnV0ZSB2YWx1ZQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IGB0cnVlYCBpZiB0aGUgdmlzaXRlZCBub2RlIGFkZGVkIG5vZGUtc3BlY2lmaWMKICAgICAgICAgKiAgIG1ldGFkYXRhIHRvIGBub2RlSW5mb2AKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZU5vZGVBdHRyaWJ1dGUobm9kZSwgdGVtcGxhdGVJbmZvLCBub2RlSW5mbywgbmFtZSwgdmFsdWUpIHsKICAgICAgICAgIC8vIGV2ZW50cyAob24tKikKICAgICAgICAgIGlmIChuYW1lLnNsaWNlKDAsIDMpID09PSAnb24tJykgewogICAgICAgICAgICBub2RlLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICAgICAgbm9kZUluZm8uZXZlbnRzID0gbm9kZUluZm8uZXZlbnRzIHx8IFtdOwogICAgICAgICAgICBub2RlSW5mby5ldmVudHMucHVzaCh7CiAgICAgICAgICAgICAgbmFtZTogbmFtZS5zbGljZSgzKSwKICAgICAgICAgICAgICB2YWx1ZQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBzdGF0aWMgaWQKICAgICAgICAgIGVsc2UgaWYgKG5hbWUgPT09ICdpZCcpIHsKICAgICAgICAgICAgbm9kZUluZm8uaWQgPSB2YWx1ZTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBgY29udGVudGAgZG9jdW1lbnQgZnJhZ21lbnQgZm9yIGEgZ2l2ZW4gdGVtcGxhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgbmVzdGVkIHRlbXBsYXRlcywgUG9seW1lciBwZXJmb3JtcyBhbiBvcHRpbWl6YXRpb24gdG8gY2FjaGUgbmVzdGVkCiAgICAgICAgICogdGVtcGxhdGUgY29udGVudCB0byBhdm9pZCB0aGUgY29zdCBvZiBjbG9uaW5nIGRlZXBseSBuZXN0ZWQgdGVtcGxhdGVzLgogICAgICAgICAqIFRoaXMgbWV0aG9kIHJldHJpZXZlcyB0aGUgY2FjaGVkIGNvbnRlbnQgZm9yIGEgZ2l2ZW4gdGVtcGxhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0hUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlIFRlbXBsYXRlIHRvIHJldHJpZXZlIGBjb250ZW50YCBmb3IKICAgICAgICAgKiBAcmV0dXJuIHtEb2N1bWVudEZyYWdtZW50fSBDb250ZW50IGZyYWdtZW50CiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX2NvbnRlbnRGb3JUZW1wbGF0ZSh0ZW1wbGF0ZSkgewogICAgICAgICAgbGV0IHRlbXBsYXRlSW5mbyA9IC8qKiBAdHlwZSB7SFRNTFRlbXBsYXRlRWxlbWVudFdpdGhJbmZvfSAqLyAodGVtcGxhdGUpLl90ZW1wbGF0ZUluZm87CiAgICAgICAgICByZXR1cm4gKHRlbXBsYXRlSW5mbyAmJiB0ZW1wbGF0ZUluZm8uY29udGVudCkgfHwgdGVtcGxhdGUuY29udGVudDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENsb25lcyB0aGUgcHJvdmlkZWQgdGVtcGxhdGUgY29udGVudCBhbmQgcmV0dXJucyBhIGRvY3VtZW50IGZyYWdtZW50CiAgICAgICAgICogY29udGFpbmluZyB0aGUgY2xvbmVkIGRvbS4KICAgICAgICAgKgogICAgICAgICAqIFRoZSB0ZW1wbGF0ZSBpcyBwYXJzZWQgKG9uY2UgYW5kIG1lbW9pemVkKSB1c2luZyB0aGlzIGxpYnJhcnkncwogICAgICAgICAqIHRlbXBsYXRlIHBhcnNpbmcgZmVhdHVyZXMsIGFuZCBwcm92aWRlcyB0aGUgZm9sbG93aW5nIHZhbHVlLWFkZGVkCiAgICAgICAgICogZmVhdHVyZXM6CiAgICAgICAgICogKiBBZGRzIGRlY2xhcmF0aXZlIGV2ZW50IGxpc3RlbmVycyBmb3IgYG9uLWV2ZW50PSJoYW5kbGVyImAgYXR0cmlidXRlcwogICAgICAgICAqICogR2VuZXJhdGVzIGFuICJpZCBtYXAiIGZvciBhbGwgbm9kZXMgd2l0aCBpZCdzIHVuZGVyIGAkYCBvbiByZXR1cm5lZAogICAgICAgICAqICAgZG9jdW1lbnQgZnJhZ21lbnQKICAgICAgICAgKiAqIFBhc3NlcyB0ZW1wbGF0ZSBpbmZvIGluY2x1ZGluZyBgY29udGVudGAgYmFjayB0byB0ZW1wbGF0ZXMgYXMKICAgICAgICAgKiAgIGBfdGVtcGxhdGVJbmZvYCAoYSBwZXJmb3JtYW5jZSBvcHRpbWl6YXRpb24gdG8gYXZvaWQgZGVlcCB0ZW1wbGF0ZQogICAgICAgICAqICAgY2xvbmluZykKICAgICAgICAgKgogICAgICAgICAqIE5vdGUgdGhhdCB0aGUgbWVtb2l6ZWQgdGVtcGxhdGUgcGFyc2luZyBwcm9jZXNzIGlzIGRlc3RydWN0aXZlIHRvIHRoZQogICAgICAgICAqIHRlbXBsYXRlOiBhdHRyaWJ1dGVzIGZvciBiaW5kaW5ncyBhbmQgZGVjbGFyYXRpdmUgZXZlbnQgbGlzdGVuZXJzIGFyZQogICAgICAgICAqIHJlbW92ZWQgYWZ0ZXIgYmVpbmcgbm90ZWQgaW4gbm90ZXMsIGFuZCBhbnkgbmVzdGVkIGA8dGVtcGxhdGU+LmNvbnRlbnRgCiAgICAgICAgICogaXMgcmVtb3ZlZCBhbmQgc3RvcmVkIGluIG5vdGVzIGFzIHdlbGwuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZSBUZW1wbGF0ZSB0byBzdGFtcAogICAgICAgICAqIEBwYXJhbSB7VGVtcGxhdGVJbmZvPX0gdGVtcGxhdGVJbmZvIE9wdGlvbmFsIHRlbXBsYXRlIGluZm8gYXNzb2NpYXRlZAogICAgICAgICAqICAgd2l0aCB0aGUgdGVtcGxhdGUgdG8gYmUgc3RhbXBlZDsgaWYgb21pdHRlZCB0aGUgdGVtcGxhdGUgd2lsbCBiZQogICAgICAgICAqICAgYXV0b21hdGljYWxseSBwYXJzZWQuCiAgICAgICAgICogQHJldHVybiB7IVN0YW1wZWRUZW1wbGF0ZX0gQ2xvbmVkIHRlbXBsYXRlIGNvbnRlbnQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfc3RhbXBUZW1wbGF0ZSh0ZW1wbGF0ZSwgdGVtcGxhdGVJbmZvKSB7CiAgICAgICAgICAvLyBQb2x5ZmlsbCBzdXBwb3J0OiBib290c3RyYXAgdGhlIHRlbXBsYXRlIGlmIGl0IGhhcyBub3QgYWxyZWFkeSBiZWVuCiAgICAgICAgICBpZiAodGVtcGxhdGUgJiYgIXRlbXBsYXRlLmNvbnRlbnQgJiYKICAgICAgICAgICAgICB3aW5kb3cuSFRNTFRlbXBsYXRlRWxlbWVudCAmJiBIVE1MVGVtcGxhdGVFbGVtZW50LmRlY29yYXRlKSB7CiAgICAgICAgICAgIEhUTUxUZW1wbGF0ZUVsZW1lbnQuZGVjb3JhdGUodGVtcGxhdGUpOwogICAgICAgICAgfQogICAgICAgICAgLy8gQWNjZXB0aW5nIHRoZSBgdGVtcGxhdGVJbmZvYCB2aWEgYW4gYXJndW1lbnQgYWxsb3dzIGZvciBjcmVhdGluZwogICAgICAgICAgLy8gaW5zdGFuY2VzIG9mIHRoZSBgdGVtcGxhdGVJbmZvYCBieSB0aGUgY2FsbGVyLCB1c2VmdWwgZm9yIGFkZGluZwogICAgICAgICAgLy8gaW5zdGFuY2UtdGltZSBpbmZvcm1hdGlvbiB0byB0aGUgcHJvdG90eXBpY2FsIGRhdGEKICAgICAgICAgIHRlbXBsYXRlSW5mbyA9IHRlbXBsYXRlSW5mbyB8fCB0aGlzLmNvbnN0cnVjdG9yLl9wYXJzZVRlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgICAgIGxldCBub2RlSW5mbyA9IHRlbXBsYXRlSW5mby5ub2RlSW5mb0xpc3Q7CiAgICAgICAgICBsZXQgY29udGVudCA9IHRlbXBsYXRlSW5mby5jb250ZW50IHx8IHRlbXBsYXRlLmNvbnRlbnQ7CiAgICAgICAgICBsZXQgZG9tID0gLyoqIEB0eXBlIHtEb2N1bWVudEZyYWdtZW50fSAqLyAoZG9jdW1lbnQuaW1wb3J0Tm9kZShjb250ZW50LCB0cnVlKSk7CiAgICAgICAgICAvLyBOT1RFOiBTaGFkeURvbSBvcHRpbWl6YXRpb24gaW5kaWNhdGluZyB0aGVyZSBpcyBhbiBpbnNlcnRpb24gcG9pbnQKICAgICAgICAgIGRvbS5fX25vSW5zZXJ0aW9uUG9pbnQgPSAhdGVtcGxhdGVJbmZvLmhhc0luc2VydGlvblBvaW50OwogICAgICAgICAgbGV0IG5vZGVzID0gZG9tLm5vZGVMaXN0ID0gbmV3IEFycmF5KG5vZGVJbmZvLmxlbmd0aCk7CiAgICAgICAgICBkb20uJCA9IHt9OwogICAgICAgICAgZm9yIChsZXQgaT0wLCBsPW5vZGVJbmZvLmxlbmd0aCwgaW5mbzsgKGk8bCkgJiYgKGluZm89bm9kZUluZm9baV0pOyBpKyspIHsKICAgICAgICAgICAgbGV0IG5vZGUgPSBub2Rlc1tpXSA9IGZpbmRUZW1wbGF0ZU5vZGUoZG9tLCBpbmZvKTsKICAgICAgICAgICAgYXBwbHlJZFRvTWFwKHRoaXMsIGRvbS4kLCBub2RlLCBpbmZvKTsKICAgICAgICAgICAgYXBwbHlUZW1wbGF0ZUluZm8odGhpcywgbm9kZSwgaW5mbywgdGVtcGxhdGVJbmZvKTsKICAgICAgICAgICAgYXBwbHlFdmVudExpc3RlbmVyKHRoaXMsIG5vZGUsIGluZm8pOwogICAgICAgICAgfQogICAgICAgICAgZG9tID0gLyoqIEB0eXBlIHshU3RhbXBlZFRlbXBsYXRlfSAqLyhkb20pOyAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXNlbGYtYXNzaWduCiAgICAgICAgICByZXR1cm4gZG9tOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhbiBldmVudCBsaXN0ZW5lciBieSBtZXRob2QgbmFtZSBmb3IgdGhlIGV2ZW50IHByb3ZpZGVkLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBtZXRob2QgZ2VuZXJhdGVzIGEgaGFuZGxlciBmdW5jdGlvbiB0aGF0IGxvb2tzIHVwIHRoZSBtZXRob2QKICAgICAgICAgKiBuYW1lIGF0IGhhbmRsaW5nIHRpbWUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFFdmVudFRhcmdldH0gbm9kZSBOb2RlIHRvIGFkZCBsaXN0ZW5lciBvbgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldmVudE5hbWUgTmFtZSBvZiBldmVudAogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBtZXRob2ROYW1lIE5hbWUgb2YgbWV0aG9kCiAgICAgICAgICogQHBhcmFtIHsqPX0gY29udGV4dCBDb250ZXh0IHRoZSBtZXRob2Qgd2lsbCBiZSBjYWxsZWQgb24gKGRlZmF1bHRzCiAgICAgICAgICogICB0byBgbm9kZWApCiAgICAgICAgICogQHJldHVybiB7RnVuY3Rpb259IEdlbmVyYXRlZCBoYW5kbGVyIGZ1bmN0aW9uCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2FkZE1ldGhvZEV2ZW50TGlzdGVuZXJUb05vZGUobm9kZSwgZXZlbnROYW1lLCBtZXRob2ROYW1lLCBjb250ZXh0KSB7CiAgICAgICAgICBjb250ZXh0ID0gY29udGV4dCB8fCBub2RlOwogICAgICAgICAgbGV0IGhhbmRsZXIgPSBjcmVhdGVOb2RlRXZlbnRIYW5kbGVyKGNvbnRleHQsIGV2ZW50TmFtZSwgbWV0aG9kTmFtZSk7CiAgICAgICAgICB0aGlzLl9hZGRFdmVudExpc3RlbmVyVG9Ob2RlKG5vZGUsIGV2ZW50TmFtZSwgaGFuZGxlcik7CiAgICAgICAgICByZXR1cm4gaGFuZGxlcjsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlIHBvaW50IGZvciBhZGRpbmcgY3VzdG9tIG9yIHNpbXVsYXRlZCBldmVudCBoYW5kbGluZy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7IUV2ZW50VGFyZ2V0fSBub2RlIE5vZGUgdG8gYWRkIGV2ZW50IGxpc3RlbmVyIHRvCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGV2ZW50TmFtZSBOYW1lIG9mIGV2ZW50CiAgICAgICAgICogQHBhcmFtIHtmdW5jdGlvbighRXZlbnQpOnZvaWR9IGhhbmRsZXIgTGlzdGVuZXIgZnVuY3Rpb24gdG8gYWRkCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfYWRkRXZlbnRMaXN0ZW5lclRvTm9kZShub2RlLCBldmVudE5hbWUsIGhhbmRsZXIpIHsKICAgICAgICAgIG5vZGUuYWRkRXZlbnRMaXN0ZW5lcihldmVudE5hbWUsIGhhbmRsZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGUgcG9pbnQgZm9yIGFkZGluZyBjdXN0b20gb3Igc2ltdWxhdGVkIGV2ZW50IGhhbmRsaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshRXZlbnRUYXJnZXR9IG5vZGUgTm9kZSB0byByZW1vdmUgZXZlbnQgbGlzdGVuZXIgZnJvbQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldmVudE5hbWUgTmFtZSBvZiBldmVudAogICAgICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oIUV2ZW50KTp2b2lkfSBoYW5kbGVyIExpc3RlbmVyIGZ1bmN0aW9uIHRvIHJlbW92ZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3JlbW92ZUV2ZW50TGlzdGVuZXJGcm9tTm9kZShub2RlLCBldmVudE5hbWUsIGhhbmRsZXIpIHsKICAgICAgICAgIG5vZGUucmVtb3ZlRXZlbnRMaXN0ZW5lcihldmVudE5hbWUsIGhhbmRsZXIpOwogICAgICAgIH0KCiAgICAgIH0KCiAgICAgIHJldHVybiBUZW1wbGF0ZVN0YW1wOwoKICAgIH0pOwoKICAgIC8qKgogICAgICogQGZpbGVvdmVydmlldwogICAgICogQHN1cHByZXNzIHtjaGVja1Byb3RvdHlwYWxUeXBlc30KICAgICAqIEBsaWNlbnNlIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgICAqIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kCiAgICAgKiBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5CiAgICAgKiBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5CiAgICAgKiBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQCiAgICAgKiByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAgKi8KCiAgICAvLyBNb25vdG9uaWNhbGx5IGluY3JlYXNpbmcgdW5pcXVlIElEIHVzZWQgZm9yIGRlLWR1cGluZyBlZmZlY3RzIHRyaWdnZXJlZAogICAgLy8gZnJvbSBtdWx0aXBsZSBwcm9wZXJ0aWVzIGluIHRoZSBzYW1lIHR1cm4KICAgIGxldCBkZWR1cGVJZCQxID0gMDsKCiAgICBjb25zdCBOT09QID0gW107CgogICAgLyoqCiAgICAgKiBQcm9wZXJ0eSBlZmZlY3QgdHlwZXM7IGVmZmVjdHMgYXJlIHN0b3JlZCBvbiB0aGUgcHJvdG90eXBlIHVzaW5nIHRoZXNlIGtleXMKICAgICAqIEBlbnVtIHtzdHJpbmd9CiAgICAgKi8KICAgIGNvbnN0IFRZUEVTID0gewogICAgICBDT01QVVRFOiAnX19jb21wdXRlRWZmZWN0cycsCiAgICAgIFJFRkxFQ1Q6ICdfX3JlZmxlY3RFZmZlY3RzJywKICAgICAgTk9USUZZOiAnX19ub3RpZnlFZmZlY3RzJywKICAgICAgUFJPUEFHQVRFOiAnX19wcm9wYWdhdGVFZmZlY3RzJywKICAgICAgT0JTRVJWRTogJ19fb2JzZXJ2ZUVmZmVjdHMnLAogICAgICBSRUFEX09OTFk6ICdfX3JlYWRPbmx5JwogICAgfTsKCiAgICBjb25zdCBDT01QVVRFX0lORk8gPSAnX19jb21wdXRlSW5mbyc7CgogICAgLyoqIEBjb25zdCB7IVJlZ0V4cH0gKi8KICAgIGNvbnN0IGNhcGl0YWxBdHRyaWJ1dGVSZWdleCA9IC9bQS1aXS87CgogICAgLyoqCiAgICAgKiBFbnN1cmVzIHRoYXQgdGhlIG1vZGVsIGhhcyBhbiBvd24tcHJvcGVydHkgbWFwIG9mIGVmZmVjdHMgZm9yIHRoZSBnaXZlbiB0eXBlLgogICAgICogVGhlIG1vZGVsIG1heSBiZSBhIHByb3RvdHlwZSBvciBhbiBpbnN0YW5jZS4KICAgICAqCiAgICAgKiBQcm9wZXJ0eSBlZmZlY3RzIGFyZSBzdG9yZWQgYXMgYXJyYXlzIG9mIGVmZmVjdHMgYnkgcHJvcGVydHkgaW4gYSBtYXAsCiAgICAgKiBieSBuYW1lZCB0eXBlIG9uIHRoZSBtb2RlbC4gZS5nLgogICAgICoKICAgICAqICAgX19jb21wdXRlRWZmZWN0czogewogICAgICogICAgIGZvbzogWyAuLi4gXSwKICAgICAqICAgICBiYXI6IFsgLi4uIF0KICAgICAqICAgfQogICAgICoKICAgICAqIElmIHRoZSBtb2RlbCBkb2VzIG5vdCB5ZXQgaGF2ZSBhbiBlZmZlY3QgbWFwIGZvciB0aGUgdHlwZSwgb25lIGlzIGNyZWF0ZWQKICAgICAqIGFuZCByZXR1cm5lZC4gIElmIGl0IGRvZXMsIGJ1dCBpdCBpcyBub3QgYW4gb3duIHByb3BlcnR5IChpLmUuIHRoZQogICAgICogcHJvdG90eXBlIGhhZCBlZmZlY3RzKSwgdGhlIHRoZSBtYXAgaXMgZGVlcGx5IGNsb25lZCBhbmQgdGhlIGNvcHkgaXMKICAgICAqIHNldCBvbiB0aGUgbW9kZWwgYW5kIHJldHVybmVkLCByZWFkeSBmb3IgbmV3IGVmZmVjdHMgdG8gYmUgYWRkZWQuCiAgICAgKgogICAgICogQHBhcmFtIHtPYmplY3R9IG1vZGVsIFByb3RvdHlwZSBvciBpbnN0YW5jZQogICAgICogQHBhcmFtIHtzdHJpbmd9IHR5cGUgUHJvcGVydHkgZWZmZWN0IHR5cGUKICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IGNsb25lQXJyYXlzIENsb25lIGFueSBhcnJheXMgYXNzaWduZWQgdG8gdGhlIG1hcCB3aGVuCiAgICAgKiAgIGV4dGVuZGluZyBhIHN1cGVyY2xhc3MgbWFwIG9udG8gdGhpcyBzdWJjbGFzcwogICAgICogQHJldHVybiB7T2JqZWN0fSBUaGUgb3duLXByb3BlcnR5IG1hcCBvZiBlZmZlY3RzIGZvciB0aGUgZ2l2ZW4gdHlwZQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gZW5zdXJlT3duRWZmZWN0TWFwKG1vZGVsLCB0eXBlLCBjbG9uZUFycmF5cykgewogICAgICBsZXQgZWZmZWN0cyA9IG1vZGVsW3R5cGVdOwogICAgICBpZiAoIWVmZmVjdHMpIHsKICAgICAgICBlZmZlY3RzID0gbW9kZWxbdHlwZV0gPSB7fTsKICAgICAgfSBlbHNlIGlmICghbW9kZWwuaGFzT3duUHJvcGVydHkodHlwZSkpIHsKICAgICAgICBlZmZlY3RzID0gbW9kZWxbdHlwZV0gPSBPYmplY3QuY3JlYXRlKG1vZGVsW3R5cGVdKTsKICAgICAgICBpZiAoY2xvbmVBcnJheXMpIHsKICAgICAgICAgIGZvciAobGV0IHAgaW4gZWZmZWN0cykgewogICAgICAgICAgICBsZXQgcHJvdG9GeCA9IGVmZmVjdHNbcF07CiAgICAgICAgICAgIC8vIFBlcmYgb3B0aW1pemF0aW9uIG92ZXIgQXJyYXkuc2xpY2UKICAgICAgICAgICAgbGV0IGluc3RGeCA9IGVmZmVjdHNbcF0gPSBBcnJheShwcm90b0Z4Lmxlbmd0aCk7CiAgICAgICAgICAgIGZvciAobGV0IGk9MDsgaTxwcm90b0Z4Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgaW5zdEZ4W2ldID0gcHJvdG9GeFtpXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gZWZmZWN0czsKICAgIH0KCiAgICAvLyAtLSBlZmZlY3RzIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KCiAgICAvKioKICAgICAqIFJ1bnMgYWxsIGVmZmVjdHMgb2YgYSBnaXZlbiB0eXBlIGZvciB0aGUgZ2l2ZW4gc2V0IG9mIHByb3BlcnR5IGNoYW5nZXMKICAgICAqIG9uIGFuIGluc3RhbmNlLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB3aXRoIGVmZmVjdHMgdG8gcnVuCiAgICAgKiBAcGFyYW0gez9PYmplY3R9IGVmZmVjdHMgT2JqZWN0IG1hcCBvZiBwcm9wZXJ0eS10by1BcnJheSBvZiBlZmZlY3RzCiAgICAgKiBAcGFyYW0gez9PYmplY3R9IHByb3BzIEJhZyBvZiBjdXJyZW50IHByb3BlcnR5IGNoYW5nZXMKICAgICAqIEBwYXJhbSB7P09iamVjdD19IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICogQHBhcmFtIHtib29sZWFuPX0gaGFzUGF0aHMgVHJ1ZSB3aXRoIGBwcm9wc2AgY29udGFpbnMgb25lIG9yIG1vcmUgcGF0aHMKICAgICAqIEBwYXJhbSB7Kj19IGV4dHJhQXJncyBBZGRpdGlvbmFsIG1ldGFkYXRhIHRvIHBhc3MgdG8gZWZmZWN0IGZ1bmN0aW9uCiAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIGFuIGVmZmVjdCByYW4gZm9yIHRoaXMgcHJvcGVydHkKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1bkVmZmVjdHMoaW5zdCwgZWZmZWN0cywgcHJvcHMsIG9sZFByb3BzLCBoYXNQYXRocywgZXh0cmFBcmdzKSB7CiAgICAgIGlmIChlZmZlY3RzKSB7CiAgICAgICAgbGV0IHJhbiA9IGZhbHNlOwogICAgICAgIGNvbnN0IGlkID0gZGVkdXBlSWQkMSsrOwogICAgICAgIGZvciAobGV0IHByb3AgaW4gcHJvcHMpIHsKICAgICAgICAgIC8vIElubGluZSBgcnVuRWZmZWN0c0ZvclByb3BlcnR5YCBmb3IgcGVyZi4KICAgICAgICAgIGxldCByb290UHJvcGVydHkgPSBoYXNQYXRocyA/IHJvb3QocHJvcCkgOiBwcm9wOwogICAgICAgICAgbGV0IGZ4cyA9IGVmZmVjdHNbcm9vdFByb3BlcnR5XTsKICAgICAgICAgIGlmIChmeHMpIHsKICAgICAgICAgICAgZm9yIChsZXQgaT0wLCBsPWZ4cy5sZW5ndGgsIGZ4OyAoaTxsKSAmJiAoZng9ZnhzW2ldKTsgaSsrKSB7CiAgICAgICAgICAgICAgaWYgKCghZnguaW5mbyB8fCBmeC5pbmZvLmxhc3RSdW4gIT09IGlkKSAmJgogICAgICAgICAgICAgICAgICAoIWhhc1BhdGhzIHx8IHBhdGhNYXRjaGVzVHJpZ2dlcihwcm9wLCBmeC50cmlnZ2VyKSkpIHsKICAgICAgICAgICAgICAgIGlmIChmeC5pbmZvKSB7CiAgICAgICAgICAgICAgICAgIGZ4LmluZm8ubGFzdFJ1biA9IGlkOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZnguZm4oaW5zdCwgcHJvcCwgcHJvcHMsIG9sZFByb3BzLCBmeC5pbmZvLCBoYXNQYXRocywgZXh0cmFBcmdzKTsKICAgICAgICAgICAgICAgIHJhbiA9IHRydWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiByYW47CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQoKICAgIC8qKgogICAgICogUnVucyBhIGxpc3Qgb2YgZWZmZWN0cyBmb3IgYSBnaXZlbiBwcm9wZXJ0eS4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBUaGUgaW5zdGFuY2Ugd2l0aCBlZmZlY3RzIHRvIHJ1bgogICAgICogQHBhcmFtIHshT2JqZWN0fSBlZmZlY3RzIE9iamVjdCBtYXAgb2YgcHJvcGVydHktdG8tQXJyYXkgb2YgZWZmZWN0cwogICAgICogQHBhcmFtIHtudW1iZXJ9IGRlZHVwZUlkIENvdW50ZXIgdXNlZCBmb3IgZGUtZHVwaW5nIGVmZmVjdHMKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wIE5hbWUgb2YgY2hhbmdlZCBwcm9wZXJ0eQogICAgICogQHBhcmFtIHsqfSBwcm9wcyBDaGFuZ2VkIHByb3BlcnRpZXMKICAgICAqIEBwYXJhbSB7Kn0gb2xkUHJvcHMgT2xkIHByb3BlcnRpZXMKICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IGhhc1BhdGhzIFRydWUgd2l0aCBgcHJvcHNgIGNvbnRhaW5zIG9uZSBvciBtb3JlIHBhdGhzCiAgICAgKiBAcGFyYW0geyo9fSBleHRyYUFyZ3MgQWRkaXRpb25hbCBtZXRhZGF0YSB0byBwYXNzIHRvIGVmZmVjdCBmdW5jdGlvbgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBhbiBlZmZlY3QgcmFuIGZvciB0aGlzIHByb3BlcnR5CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBydW5FZmZlY3RzRm9yUHJvcGVydHkoaW5zdCwgZWZmZWN0cywgZGVkdXBlSWQsIHByb3AsIHByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMsIGV4dHJhQXJncykgewogICAgICBsZXQgcmFuID0gZmFsc2U7CiAgICAgIGxldCByb290UHJvcGVydHkgPSBoYXNQYXRocyA/IHJvb3QocHJvcCkgOiBwcm9wOwogICAgICBsZXQgZnhzID0gZWZmZWN0c1tyb290UHJvcGVydHldOwogICAgICBpZiAoZnhzKSB7CiAgICAgICAgZm9yIChsZXQgaT0wLCBsPWZ4cy5sZW5ndGgsIGZ4OyAoaTxsKSAmJiAoZng9ZnhzW2ldKTsgaSsrKSB7CiAgICAgICAgICBpZiAoKCFmeC5pbmZvIHx8IGZ4LmluZm8ubGFzdFJ1biAhPT0gZGVkdXBlSWQpICYmCiAgICAgICAgICAgICAgKCFoYXNQYXRocyB8fCBwYXRoTWF0Y2hlc1RyaWdnZXIocHJvcCwgZngudHJpZ2dlcikpKSB7CiAgICAgICAgICAgIGlmIChmeC5pbmZvKSB7CiAgICAgICAgICAgICAgZnguaW5mby5sYXN0UnVuID0gZGVkdXBlSWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZnguZm4oaW5zdCwgcHJvcCwgcHJvcHMsIG9sZFByb3BzLCBmeC5pbmZvLCBoYXNQYXRocywgZXh0cmFBcmdzKTsKICAgICAgICAgICAgcmFuID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHJhbjsKICAgIH0KCiAgICAvKioKICAgICAqIERldGVybWluZXMgd2hldGhlciBhIHByb3BlcnR5L3BhdGggdGhhdCBoYXMgY2hhbmdlZCBtYXRjaGVzIHRoZSB0cmlnZ2VyCiAgICAgKiBjcml0ZXJpYSBmb3IgYW4gZWZmZWN0LiAgQSB0cmlnZ2VyIGlzIGEgZGVzY3JpcHRvciB3aXRoIHRoZSBmb2xsb3dpbmcKICAgICAqIHN0cnVjdHVyZSwgd2hpY2ggbWF0Y2hlcyB0aGUgZGVzY3JpcHRvcnMgcmV0dXJuZWQgZnJvbSBgcGFyc2VBcmdgLgogICAgICogZS5nLiBmb3IgYGZvby5iYXIuKmA6CiAgICAgKiBgYGAKICAgICAqIHRyaWdnZXI6IHsKICAgICAqICAgbmFtZTogJ2EuYicsCiAgICAgKiAgIHN0cnVjdHVyZWQ6IHRydWUsCiAgICAgKiAgIHdpbGRjYXJkOiB0cnVlCiAgICAgKiB9CiAgICAgKiBgYGAKICAgICAqIElmIG5vIHRyaWdnZXIgaXMgZ2l2ZW4sIHRoZSBwYXRoIGlzIGRlZW1lZCB0byBtYXRjaC4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBQYXRoIG9yIHByb3BlcnR5IHRoYXQgY2hhbmdlZAogICAgICogQHBhcmFtIHs/RGF0YVRyaWdnZXJ9IHRyaWdnZXIgRGVzY3JpcHRvcgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB0aGUgcGF0aCBtYXRjaGVkIHRoZSB0cmlnZ2VyCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBhdGhNYXRjaGVzVHJpZ2dlcihwYXRoLCB0cmlnZ2VyKSB7CiAgICAgIGlmICh0cmlnZ2VyKSB7CiAgICAgICAgbGV0IHRyaWdnZXJQYXRoID0gLyoqIEB0eXBlIHtzdHJpbmd9ICovICh0cmlnZ2VyLm5hbWUpOwogICAgICAgIHJldHVybiAodHJpZ2dlclBhdGggPT0gcGF0aCkgfHwKICAgICAgICAgICAgISEodHJpZ2dlci5zdHJ1Y3R1cmVkICYmIGlzQW5jZXN0b3IodHJpZ2dlclBhdGgsIHBhdGgpKSB8fAogICAgICAgICAgICAhISh0cmlnZ2VyLndpbGRjYXJkICYmIGlzRGVzY2VuZGFudCh0cmlnZ2VyUGF0aCwgcGF0aCkpOwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBJbXBsZW1lbnRzIHRoZSAib2JzZXJ2ZXIiIGVmZmVjdC4KICAgICAqCiAgICAgKiBDYWxscyB0aGUgbWV0aG9kIHdpdGggYGluZm8ubWV0aG9kTmFtZWAgb24gdGhlIGluc3RhbmNlLCBwYXNzaW5nIHRoZQogICAgICogbmV3IGFuZCBvbGQgdmFsdWVzLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB0aGUgZWZmZWN0IHdpbGwgYmUgcnVuIG9uCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiBwcm9wZXJ0eQogICAgICogQHBhcmFtIHtPYmplY3R9IHByb3BzIEJhZyBvZiBjdXJyZW50IHByb3BlcnR5IGNoYW5nZXMKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvbGRQcm9wcyBCYWcgb2YgcHJldmlvdXMgdmFsdWVzIGZvciBjaGFuZ2VkIHByb3BlcnRpZXMKICAgICAqIEBwYXJhbSB7P30gaW5mbyBFZmZlY3QgbWV0YWRhdGEKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBydW5PYnNlcnZlckVmZmVjdChpbnN0LCBwcm9wZXJ0eSwgcHJvcHMsIG9sZFByb3BzLCBpbmZvKSB7CiAgICAgIGxldCBmbiA9IHR5cGVvZiBpbmZvLm1ldGhvZCA9PT0gInN0cmluZyIgPyBpbnN0W2luZm8ubWV0aG9kXSA6IGluZm8ubWV0aG9kOwogICAgICBsZXQgY2hhbmdlZFByb3AgPSBpbmZvLnByb3BlcnR5OwogICAgICBpZiAoZm4pIHsKICAgICAgICBmbi5jYWxsKGluc3QsIGluc3QuX19kYXRhW2NoYW5nZWRQcm9wXSwgb2xkUHJvcHNbY2hhbmdlZFByb3BdKTsKICAgICAgfSBlbHNlIGlmICghaW5mby5keW5hbWljRm4pIHsKICAgICAgICBjb25zb2xlLndhcm4oJ29ic2VydmVyIG1ldGhvZCBgJyArIGluZm8ubWV0aG9kICsgJ2Agbm90IGRlZmluZWQnKTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogUnVucyAibm90aWZ5IiBlZmZlY3RzIGZvciBhIHNldCBvZiBjaGFuZ2VkIHByb3BlcnRpZXMuCiAgICAgKgogICAgICogVGhpcyBtZXRob2QgZGlmZmVycyBmcm9tIHRoZSBnZW5lcmljIGBydW5FZmZlY3RzYCBtZXRob2QgaW4gdGhhdCBpdAogICAgICogd2lsbCBkaXNwYXRjaCBwYXRoIG5vdGlmaWNhdGlvbiBldmVudHMgaW4gdGhlIGNhc2UgdGhhdCB0aGUgcHJvcGVydHkKICAgICAqIGNoYW5nZWQgd2FzIGEgcGF0aCBhbmQgdGhlIHJvb3QgcHJvcGVydHkgZm9yIHRoYXQgcGF0aCBkaWRuJ3QgaGF2ZSBhCiAgICAgKiAibm90aWZ5IiBlZmZlY3QuICBUaGlzIGlzIHRvIG1haW50YWluIDEuMCBiZWhhdmlvciB0aGF0IGRpZCBub3QgcmVxdWlyZQogICAgICogYG5vdGlmeTogdHJ1ZWAgdG8gZW5zdXJlIG9iamVjdCBzdWItcHJvcGVydHkgbm90aWZpY2F0aW9ucyB3ZXJlCiAgICAgKiBzZW50LgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB3aXRoIGVmZmVjdHMgdG8gcnVuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gbm90aWZ5UHJvcHMgQmFnIG9mIHByb3BlcnRpZXMgdG8gbm90aWZ5CiAgICAgKiBAcGFyYW0ge09iamVjdH0gcHJvcHMgQmFnIG9mIGN1cnJlbnQgcHJvcGVydHkgY2hhbmdlcwogICAgICogQHBhcmFtIHtPYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICogQHBhcmFtIHtib29sZWFufSBoYXNQYXRocyBUcnVlIHdpdGggYHByb3BzYCBjb250YWlucyBvbmUgb3IgbW9yZSBwYXRocwogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1bk5vdGlmeUVmZmVjdHMoaW5zdCwgbm90aWZ5UHJvcHMsIHByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpIHsKICAgICAgLy8gTm90aWZ5CiAgICAgIGxldCBmeHMgPSBpbnN0W1RZUEVTLk5PVElGWV07CiAgICAgIGxldCBub3RpZmllZDsKICAgICAgbGV0IGlkID0gZGVkdXBlSWQkMSsrOwogICAgICAvLyBUcnkgbm9ybWFsIG5vdGlmeSBlZmZlY3RzOyBpZiBub25lLCBmYWxsIGJhY2sgdG8gdHJ5IHBhdGggbm90aWZpY2F0aW9uCiAgICAgIGZvciAobGV0IHByb3AgaW4gbm90aWZ5UHJvcHMpIHsKICAgICAgICBpZiAobm90aWZ5UHJvcHNbcHJvcF0pIHsKICAgICAgICAgIGlmIChmeHMgJiYgcnVuRWZmZWN0c0ZvclByb3BlcnR5KGluc3QsIGZ4cywgaWQsIHByb3AsIHByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpKSB7CiAgICAgICAgICAgIG5vdGlmaWVkID0gdHJ1ZTsKICAgICAgICAgIH0gZWxzZSBpZiAoaGFzUGF0aHMgJiYgbm90aWZ5UGF0aChpbnN0LCBwcm9wLCBwcm9wcykpIHsKICAgICAgICAgICAgbm90aWZpZWQgPSB0cnVlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICAvLyBGbHVzaCBob3N0IGlmIHdlIGFjdHVhbGx5IG5vdGlmaWVkIGFuZCBob3N0IHdhcyBiYXRjaGluZwogICAgICAvLyBBbmQgdGhlIGhvc3QgaGFzIGFscmVhZHkgaW5pdGlhbGl6ZWQgY2xpZW50czsgdGhpcyBwcmV2ZW50cwogICAgICAvLyBhbiBpc3N1ZSB3aXRoIGEgaG9zdCBvYnNlcnZpbmcgZGF0YSBjaGFuZ2VzIGJlZm9yZSBjbGllbnRzIGFyZSByZWFkeS4KICAgICAgbGV0IGhvc3Q7CiAgICAgIGlmIChub3RpZmllZCAmJiAoaG9zdCA9IGluc3QuX19kYXRhSG9zdCkgJiYgaG9zdC5faW52YWxpZGF0ZVByb3BlcnRpZXMpIHsKICAgICAgICBob3N0Ll9pbnZhbGlkYXRlUHJvcGVydGllcygpOwogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBEaXNwYXRjaGVzIHtwcm9wZXJ0eX0tY2hhbmdlZCBldmVudHMgd2l0aCBwYXRoIGluZm9ybWF0aW9uIGluIHRoZSBkZXRhaWwKICAgICAqIG9iamVjdCB0byBpbmRpY2F0ZSBhIHN1Yi1wYXRoIG9mIHRoZSBwcm9wZXJ0eSB3YXMgY2hhbmdlZC4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBUaGUgZWxlbWVudCBmcm9tIHdoaWNoIHRvIGZpcmUgdGhlCiAgICAgKiAgICAgZXZlbnQKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFRoZSBwYXRoIHRoYXQgd2FzIGNoYW5nZWQKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgY3VycmVudCBwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgKiBAcmV0dXJuIHtib29sZWFufSBSZXR1cm5zIHRydWUgaWYgdGhlIHBhdGggd2FzIG5vdGlmaWVkCiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBub3RpZnlQYXRoKGluc3QsIHBhdGgsIHByb3BzKSB7CiAgICAgIGxldCByb290UHJvcGVydHkgPSByb290KHBhdGgpOwogICAgICBpZiAocm9vdFByb3BlcnR5ICE9PSBwYXRoKSB7CiAgICAgICAgbGV0IGV2ZW50TmFtZSA9IGNhbWVsVG9EYXNoQ2FzZShyb290UHJvcGVydHkpICsgJy1jaGFuZ2VkJzsKICAgICAgICBkaXNwYXRjaE5vdGlmeUV2ZW50KGluc3QsIGV2ZW50TmFtZSwgcHJvcHNbcGF0aF0sIHBhdGgpOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KCiAgICAvKioKICAgICAqIERpc3BhdGNoZXMge3Byb3BlcnR5fS1jaGFuZ2VkIGV2ZW50cyB0byBpbmRpY2F0ZSBhIHByb3BlcnR5IChvciBwYXRoKQogICAgICogY2hhbmdlZC4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBUaGUgZWxlbWVudCBmcm9tIHdoaWNoIHRvIGZpcmUgdGhlCiAgICAgKiAgICAgZXZlbnQKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldmVudE5hbWUgVGhlIG5hbWUgb2YgdGhlIGV2ZW50IHRvIHNlbmQKICAgICAqICAgICAoJ3twcm9wZXJ0eX0tY2hhbmdlZCcpCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSBvZiB0aGUgY2hhbmdlZCBwcm9wZXJ0eQogICAgICogQHBhcmFtIHtzdHJpbmcgfCBudWxsIHwgdW5kZWZpbmVkfSBwYXRoIElmIGEgc3ViLXBhdGggb2YgdGhpcyBwcm9wZXJ0eQogICAgICogICAgIGNoYW5nZWQsIHRoZSBwYXRoIHRoYXQgY2hhbmdlZCAob3B0aW9uYWwpLgogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKiBAc3VwcHJlc3Mge2ludmFsaWRDYXN0c30KICAgICAqLwogICAgZnVuY3Rpb24gZGlzcGF0Y2hOb3RpZnlFdmVudChpbnN0LCBldmVudE5hbWUsIHZhbHVlLCBwYXRoKSB7CiAgICAgIGxldCBkZXRhaWwgPSB7CiAgICAgICAgdmFsdWU6IHZhbHVlLAogICAgICAgIHF1ZXVlUHJvcGVydHk6IHRydWUKICAgICAgfTsKICAgICAgaWYgKHBhdGgpIHsKICAgICAgICBkZXRhaWwucGF0aCA9IHBhdGg7CiAgICAgIH0KICAgICAgLy8gQXMgYSBwZXJmb3JtYW5jZSBvcHRpbWl6YXRpb24sIHdlIGNvdWxkIGVsaWRlIHRoZSB3cmFwIGhlcmUgc2luY2Ugbm90aWZ5aW5nCiAgICAgIC8vIGV2ZW50cyBhcmUgbm9uLWJ1YmJsaW5nIGFuZCBzaG91bGRuJ3QgbmVlZCByZXRhcmdldGluZy4gSG93ZXZlciwgYSB2ZXJ5CiAgICAgIC8vIHNtYWxsIG51bWJlciBvZiBpbnRlcm5hbCB0ZXN0cyBmYWlsZWQgaW4gb2JzY3VyZSB3YXlzLCB3aGljaCBtYXkgaW5kaWNhdGUKICAgICAgLy8gdXNlciBjb2RlIHJlbGllZCBvbiB0aW1pbmcgZGlmZmVyZW5jZXMgcmVzdWx0aW5nIGZyb20gU2hhZHlET00gZmx1c2hpbmcKICAgICAgLy8gYXMgYSByZXN1bHQgb2YgdGhlIHdyYXBwZWQgYGRpc3BhdGNoRXZlbnRgLgogICAgICB3cmFwKC8qKiBAdHlwZSB7IUhUTUxFbGVtZW50fSAqLyhpbnN0KSkuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoZXZlbnROYW1lLCB7IGRldGFpbCB9KSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBJbXBsZW1lbnRzIHRoZSAibm90aWZ5IiBlZmZlY3QuCiAgICAgKgogICAgICogRGlzcGF0Y2hlcyBhIG5vbi1idWJibGluZyBldmVudCBuYW1lZCBgaW5mby5ldmVudE5hbWVgIG9uIHRoZSBpbnN0YW5jZQogICAgICogd2l0aCBhIGRldGFpbCBvYmplY3QgY29udGFpbmluZyB0aGUgbmV3IGB2YWx1ZWAuCiAgICAgKgogICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgVGhlIGluc3RhbmNlIHRoZSBlZmZlY3Qgd2lsbCBiZSBydW4gb24KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIHByb3BlcnR5CiAgICAgKiBAcGFyYW0ge09iamVjdH0gcHJvcHMgQmFnIG9mIGN1cnJlbnQgcHJvcGVydHkgY2hhbmdlcwogICAgICogQHBhcmFtIHtPYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICogQHBhcmFtIHs/fSBpbmZvIEVmZmVjdCBtZXRhZGF0YQogICAgICogQHBhcmFtIHtib29sZWFufSBoYXNQYXRocyBUcnVlIHdpdGggYHByb3BzYCBjb250YWlucyBvbmUgb3IgbW9yZSBwYXRocwogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1bk5vdGlmeUVmZmVjdChpbnN0LCBwcm9wZXJ0eSwgcHJvcHMsIG9sZFByb3BzLCBpbmZvLCBoYXNQYXRocykgewogICAgICBsZXQgcm9vdFByb3BlcnR5ID0gaGFzUGF0aHMgPyByb290KHByb3BlcnR5KSA6IHByb3BlcnR5OwogICAgICBsZXQgcGF0aCA9IHJvb3RQcm9wZXJ0eSAhPSBwcm9wZXJ0eSA/IHByb3BlcnR5IDogbnVsbDsKICAgICAgbGV0IHZhbHVlID0gcGF0aCA/IGdldChpbnN0LCBwYXRoKSA6IGluc3QuX19kYXRhW3Byb3BlcnR5XTsKICAgICAgaWYgKHBhdGggJiYgdmFsdWUgPT09IHVuZGVmaW5lZCkgewogICAgICAgIHZhbHVlID0gcHJvcHNbcHJvcGVydHldOyAgLy8gc3BlY2lmaWNhbGx5IGZvciAuc3BsaWNlcwogICAgICB9CiAgICAgIGRpc3BhdGNoTm90aWZ5RXZlbnQoaW5zdCwgaW5mby5ldmVudE5hbWUsIHZhbHVlLCBwYXRoKTsKICAgIH0KCiAgICAvKioKICAgICAqIEhhbmRsZXIgZnVuY3Rpb24gZm9yIDItd2F5IG5vdGlmaWNhdGlvbiBldmVudHMuIFJlY2VpdmVzIGNvbnRleHQKICAgICAqIGluZm9ybWF0aW9uIGNhcHR1cmVkIGluIHRoZSBgYWRkTm90aWZ5TGlzdGVuZXJgIGNsb3N1cmUgZnJvbSB0aGUKICAgICAqIGBfX25vdGlmeUxpc3RlbmVyc2AgbWV0YWRhdGEuCiAgICAgKgogICAgICogU2V0cyB0aGUgdmFsdWUgb2YgdGhlIG5vdGlmaWVkIHByb3BlcnR5IHRvIHRoZSBob3N0IHByb3BlcnR5IG9yIHBhdGguICBJZgogICAgICogdGhlIGV2ZW50IGNvbnRhaW5lZCBwYXRoIGluZm9ybWF0aW9uLCB0cmFuc2xhdGUgdGhhdCBwYXRoIHRvIHRoZSBob3N0CiAgICAgKiBzY29wZSdzIG5hbWUgZm9yIHRoYXQgcGF0aCBmaXJzdC4KICAgICAqCiAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBOb3RpZmljYXRpb24gZXZlbnQgKGUuZy4gJzxwcm9wZXJ0eT4tY2hhbmdlZCcpCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBIb3N0IGVsZW1lbnQgaW5zdGFuY2UgaGFuZGxpbmcgdGhlCiAgICAgKiAgICAgbm90aWZpY2F0aW9uIGV2ZW50CiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZnJvbVByb3AgQ2hpbGQgZWxlbWVudCBwcm9wZXJ0eSB0aGF0IHdhcyBib3VuZAogICAgICogQHBhcmFtIHtzdHJpbmd9IHRvUGF0aCBIb3N0IHByb3BlcnR5L3BhdGggdGhhdCB3YXMgYm91bmQKICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gbmVnYXRlIFdoZXRoZXIgdGhlIGJpbmRpbmcgd2FzIG5lZ2F0ZWQKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBoYW5kbGVOb3RpZmljYXRpb24oZXZlbnQsIGluc3QsIGZyb21Qcm9wLCB0b1BhdGgsIG5lZ2F0ZSkgewogICAgICBsZXQgdmFsdWU7CiAgICAgIGxldCBkZXRhaWwgPSAvKiogQHR5cGUge09iamVjdH0gKi8oZXZlbnQuZGV0YWlsKTsKICAgICAgbGV0IGZyb21QYXRoID0gZGV0YWlsICYmIGRldGFpbC5wYXRoOwogICAgICBpZiAoZnJvbVBhdGgpIHsKICAgICAgICB0b1BhdGggPSB0cmFuc2xhdGUoZnJvbVByb3AsIHRvUGF0aCwgZnJvbVBhdGgpOwogICAgICAgIHZhbHVlID0gZGV0YWlsICYmIGRldGFpbC52YWx1ZTsKICAgICAgfSBlbHNlIHsKICAgICAgICB2YWx1ZSA9IGV2ZW50LmN1cnJlbnRUYXJnZXRbZnJvbVByb3BdOwogICAgICB9CiAgICAgIHZhbHVlID0gbmVnYXRlID8gIXZhbHVlIDogdmFsdWU7CiAgICAgIGlmICghaW5zdFtUWVBFUy5SRUFEX09OTFldIHx8ICFpbnN0W1RZUEVTLlJFQURfT05MWV1bdG9QYXRoXSkgewogICAgICAgIGlmIChpbnN0Ll9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgodG9QYXRoLCB2YWx1ZSwgdHJ1ZSwgQm9vbGVhbihmcm9tUGF0aCkpCiAgICAgICAgICAmJiAoIWRldGFpbCB8fCAhZGV0YWlsLnF1ZXVlUHJvcGVydHkpKSB7CiAgICAgICAgICBpbnN0Ll9pbnZhbGlkYXRlUHJvcGVydGllcygpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogSW1wbGVtZW50cyB0aGUgInJlZmxlY3QiIGVmZmVjdC4KICAgICAqCiAgICAgKiBTZXRzIHRoZSBhdHRyaWJ1dGUgbmFtZWQgYGluZm8uYXR0ck5hbWVgIHRvIHRoZSBnaXZlbiBwcm9wZXJ0eSB2YWx1ZS4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBUaGUgaW5zdGFuY2UgdGhlIGVmZmVjdCB3aWxsIGJlIHJ1biBvbgogICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IE5hbWUgb2YgcHJvcGVydHkKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgY3VycmVudCBwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2xkUHJvcHMgQmFnIG9mIHByZXZpb3VzIHZhbHVlcyBmb3IgY2hhbmdlZCBwcm9wZXJ0aWVzCiAgICAgKiBAcGFyYW0gez99IGluZm8gRWZmZWN0IG1ldGFkYXRhCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gcnVuUmVmbGVjdEVmZmVjdChpbnN0LCBwcm9wZXJ0eSwgcHJvcHMsIG9sZFByb3BzLCBpbmZvKSB7CiAgICAgIGxldCB2YWx1ZSA9IGluc3QuX19kYXRhW3Byb3BlcnR5XTsKICAgICAgaWYgKHNhbml0aXplRE9NVmFsdWUpIHsKICAgICAgICB2YWx1ZSA9IHNhbml0aXplRE9NVmFsdWUodmFsdWUsIGluZm8uYXR0ck5hbWUsICdhdHRyaWJ1dGUnLCAvKiogQHR5cGUge05vZGV9ICovKGluc3QpKTsKICAgICAgfQogICAgICBpbnN0Ll9wcm9wZXJ0eVRvQXR0cmlidXRlKHByb3BlcnR5LCBpbmZvLmF0dHJOYW1lLCB2YWx1ZSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBSdW5zICJjb21wdXRlZCIgZWZmZWN0cyBmb3IgYSBzZXQgb2YgY2hhbmdlZCBwcm9wZXJ0aWVzLgogICAgICoKICAgICAqIFRoaXMgbWV0aG9kIGRpZmZlcnMgZnJvbSB0aGUgZ2VuZXJpYyBgcnVuRWZmZWN0c2AgbWV0aG9kIGluIHRoYXQgaXQKICAgICAqIGNvbnRpbnVlcyB0byBydW4gY29tcHV0ZWQgZWZmZWN0cyBiYXNlZCBvbiB0aGUgb3V0cHV0IG9mIGVhY2ggcGFzcyB1bnRpbAogICAgICogdGhlcmUgYXJlIG5vIG1vcmUgbmV3bHkgY29tcHV0ZWQgcHJvcGVydGllcy4gIFRoaXMgZW5zdXJlcyB0aGF0IGFsbAogICAgICogcHJvcGVydGllcyB0aGF0IHdpbGwgYmUgY29tcHV0ZWQgYnkgdGhlIGluaXRpYWwgc2V0IG9mIGNoYW5nZXMgYXJlCiAgICAgKiBjb21wdXRlZCBiZWZvcmUgb3RoZXIgZWZmZWN0cyAoYmluZGluZyBwcm9wYWdhdGlvbiwgb2JzZXJ2ZXJzLCBhbmQgbm90aWZ5KQogICAgICogcnVuLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB0aGUgZWZmZWN0IHdpbGwgYmUgcnVuIG9uCiAgICAgKiBAcGFyYW0gez9PYmplY3R9IGNoYW5nZWRQcm9wcyBCYWcgb2YgY2hhbmdlZCBwcm9wZXJ0aWVzCiAgICAgKiBAcGFyYW0gez9PYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICogQHBhcmFtIHtib29sZWFufSBoYXNQYXRocyBUcnVlIHdpdGggYHByb3BzYCBjb250YWlucyBvbmUgb3IgbW9yZSBwYXRocwogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1bkNvbXB1dGVkRWZmZWN0cyhpbnN0LCBjaGFuZ2VkUHJvcHMsIG9sZFByb3BzLCBoYXNQYXRocykgewogICAgICBsZXQgY29tcHV0ZUVmZmVjdHMgPSBpbnN0W1RZUEVTLkNPTVBVVEVdOwogICAgICBpZiAoY29tcHV0ZUVmZmVjdHMpIHsKICAgICAgICBpZiAob3JkZXJlZENvbXB1dGVkKSB7CiAgICAgICAgICAvLyBSdW5zIGNvbXB1dGVkIGVmZmVjdHMgaW4gZWZmaWNpZW50IG9yZGVyIGJ5IGtlZXBpbmcgYSB0b3BvbG9naWNhbGx5LQogICAgICAgICAgLy8gc29ydGVkIHF1ZXVlIG9mIGNvbXB1dGUgZWZmZWN0cyB0byBydW4sIGFuZCBpbnNlcnRpbmcgc3Vic2VxdWVudGx5CiAgICAgICAgICAvLyBpbnZhbGlkYXRlZCBlZmZlY3RzIGFzIHRoZXkgYXJlIHJ1bgogICAgICAgICAgZGVkdXBlSWQkMSsrOwogICAgICAgICAgY29uc3Qgb3JkZXIgPSBnZXRDb21wdXRlZE9yZGVyKGluc3QpOwogICAgICAgICAgY29uc3QgcXVldWUgPSBbXTsKICAgICAgICAgIGZvciAobGV0IHAgaW4gY2hhbmdlZFByb3BzKSB7CiAgICAgICAgICAgIGVucXVldWVFZmZlY3RzRm9yKHAsIGNvbXB1dGVFZmZlY3RzLCBxdWV1ZSwgb3JkZXIsIGhhc1BhdGhzKTsKICAgICAgICAgIH0KICAgICAgICAgIGxldCBpbmZvOwogICAgICAgICAgd2hpbGUgKChpbmZvID0gcXVldWUuc2hpZnQoKSkpIHsKICAgICAgICAgICAgaWYgKHJ1bkNvbXB1dGVkRWZmZWN0KGluc3QsICcnLCBjaGFuZ2VkUHJvcHMsIG9sZFByb3BzLCBpbmZvKSkgewogICAgICAgICAgICAgIGVucXVldWVFZmZlY3RzRm9yKGluZm8ubWV0aG9kSW5mbywgY29tcHV0ZUVmZmVjdHMsIHF1ZXVlLCBvcmRlciwgaGFzUGF0aHMpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBPYmplY3QuYXNzaWduKC8qKiBAdHlwZSB7IU9iamVjdH0gKi8gKG9sZFByb3BzKSwgaW5zdC5fX2RhdGFPbGQpOwogICAgICAgICAgT2JqZWN0LmFzc2lnbigvKiogQHR5cGUgeyFPYmplY3R9ICovIChjaGFuZ2VkUHJvcHMpLCBpbnN0Ll9fZGF0YVBlbmRpbmcpOwogICAgICAgICAgaW5zdC5fX2RhdGFQZW5kaW5nID0gbnVsbDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gT3JpZ2luYWwgUG9seW1lciAyLnggY29tcHV0ZWQgZWZmZWN0cyBvcmRlciwgd2hpY2ggY29udGludWVzIHJ1bm5pbmcKICAgICAgICAgIC8vIGVmZmVjdHMgdW50aWwgbm8gZnVydGhlciBjb21wdXRlZCBwcm9wZXJ0aWVzIGhhdmUgYmVlbiBpbnZhbGlkYXRlZAogICAgICAgICAgbGV0IGlucHV0UHJvcHMgPSBjaGFuZ2VkUHJvcHM7CiAgICAgICAgICB3aGlsZSAocnVuRWZmZWN0cyhpbnN0LCBjb21wdXRlRWZmZWN0cywgaW5wdXRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKSkgewogICAgICAgICAgICBPYmplY3QuYXNzaWduKC8qKiBAdHlwZSB7IU9iamVjdH0gKi8gKG9sZFByb3BzKSwgaW5zdC5fX2RhdGFPbGQpOwogICAgICAgICAgICBPYmplY3QuYXNzaWduKC8qKiBAdHlwZSB7IU9iamVjdH0gKi8gKGNoYW5nZWRQcm9wcyksIGluc3QuX19kYXRhUGVuZGluZyk7CiAgICAgICAgICAgIGlucHV0UHJvcHMgPSBpbnN0Ll9fZGF0YVBlbmRpbmc7CiAgICAgICAgICAgIGluc3QuX19kYXRhUGVuZGluZyA9IG51bGw7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBJbnNlcnRzIGEgY29tcHV0ZWQgZWZmZWN0IGludG8gYSBxdWV1ZSwgZ2l2ZW4gdGhlIHNwZWNpZmllZCBvcmRlci4gUGVyZm9ybXMKICAgICAqIHRoZSBpbnNlcnQgdXNpbmcgYSBiaW5hcnkgc2VhcmNoLgogICAgICoKICAgICAqIFVzZWQgYnkgYG9yZGVyZWRDb21wdXRlZDogdHJ1ZWAgY29tcHV0ZWQgcHJvcGVydHkgYWxnb3JpdGhtLgogICAgICoKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBpbmZvIFByb3BlcnR5IGVmZmVjdHMgbWV0YWRhdGEKICAgICAqIEBwYXJhbSB7QXJyYXk8T2JqZWN0Pn0gcXVldWUgT3JkZXJlZCBxdWV1ZSBvZiBlZmZlY3RzCiAgICAgKiBAcGFyYW0ge01hcDxzdHJpbmcsbnVtYmVyPn0gb3JkZXIgTWFwIG9mIGNvbXB1dGVkIHByb3BlcnR5IG5hbWUtPnRvcG9sb2dpY2FsCiAgICAgKiAgIHNvcnQgb3JkZXIKICAgICAqLwogICAgY29uc3QgaW5zZXJ0RWZmZWN0ID0gKGluZm8sIHF1ZXVlLCBvcmRlcikgPT4gewogICAgICBsZXQgc3RhcnQgPSAwOwogICAgICBsZXQgZW5kID0gcXVldWUubGVuZ3RoIC0gMTsKICAgICAgbGV0IGlkeCA9IC0xOwogICAgICB3aGlsZSAoc3RhcnQgPD0gZW5kKSB7CiAgICAgICAgY29uc3QgbWlkID0gKHN0YXJ0ICsgZW5kKSA+PiAxOwogICAgICAgIC8vIE5vdGUgYG1ldGhvZEluZm9gIGlzIHdoZXJlIHRoZSBjb21wdXRlZCBwcm9wZXJ0eSBuYW1lIGlzIHN0b3JlZCBpbgogICAgICAgIC8vIHRoZSBlZmZlY3QgbWV0YWRhdGEKICAgICAgICBjb25zdCBjbXAgPSBvcmRlci5nZXQocXVldWVbbWlkXS5tZXRob2RJbmZvKSAtIG9yZGVyLmdldChpbmZvLm1ldGhvZEluZm8pOwogICAgICAgIGlmIChjbXAgPCAwKSB7CiAgICAgICAgICBzdGFydCA9IG1pZCArIDE7CiAgICAgICAgfSBlbHNlIGlmIChjbXAgPiAwKSB7CiAgICAgICAgICBlbmQgPSBtaWQgLSAxOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZHggPSBtaWQ7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKGlkeCA8IDApIHsKICAgICAgICBpZHggPSBlbmQgKyAxOwogICAgICB9CiAgICAgIHF1ZXVlLnNwbGljZShpZHgsIDAsIGluZm8pOwogICAgfTsKCiAgICAvKioKICAgICAqIEluc2VydHMgYWxsIGRvd25zdHJlYW0gY29tcHV0ZWQgZWZmZWN0cyBpbnZhbGlkYXRlZCBieSB0aGUgc3BlY2lmaWVkIHByb3BlcnR5CiAgICAgKiBpbnRvIHRoZSB0b3BvbG9naWNhbGx5LXNvcnRlZCBxdWV1ZSBvZiBlZmZlY3RzIHRvIGJlIHJ1bi4KICAgICAqCiAgICAgKiBVc2VkIGJ5IGBvcmRlcmVkQ29tcHV0ZWQ6IHRydWVgIGNvbXB1dGVkIHByb3BlcnR5IGFsZ29yaXRobS4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBQcm9wZXJ0eSBuYW1lCiAgICAgKiBAcGFyYW0ge09iamVjdH0gY29tcHV0ZUVmZmVjdHMgQ29tcHV0ZWQgZWZmZWN0cyBmb3IgdGhpcyBlbGVtZW50CiAgICAgKiBAcGFyYW0ge0FycmF5PE9iamVjdD59IHF1ZXVlIFRvcG9sb2dpY2FsbHktc29ydGVkIHF1ZXVlIG9mIGNvbXB1dGVkIGVmZmVjdHMKICAgICAqICAgdG8gYmUgcnVuCiAgICAgKiBAcGFyYW0ge01hcDxzdHJpbmcsbnVtYmVyPn0gb3JkZXIgTWFwIG9mIGNvbXB1dGVkIHByb3BlcnR5IG5hbWUtPnRvcG9sb2dpY2FsCiAgICAgKiAgIHNvcnQgb3JkZXIKICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaGFzUGF0aHMgVHJ1ZSB3aXRoIGBjaGFuZ2VkUHJvcHNgIGNvbnRhaW5zIG9uZSBvciBtb3JlIHBhdGhzCiAgICAgKi8KICAgIGNvbnN0IGVucXVldWVFZmZlY3RzRm9yID0gKHByb3AsIGNvbXB1dGVFZmZlY3RzLCBxdWV1ZSwgb3JkZXIsIGhhc1BhdGhzKSA9PiB7CiAgICAgIGNvbnN0IHJvb3RQcm9wZXJ0eSA9IGhhc1BhdGhzID8gcm9vdChwcm9wKSA6IHByb3A7CiAgICAgIGNvbnN0IGZ4cyA9IGNvbXB1dGVFZmZlY3RzW3Jvb3RQcm9wZXJ0eV07CiAgICAgIGlmIChmeHMpIHsKICAgICAgICBmb3IgKGxldCBpPTA7IGk8ZnhzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBjb25zdCBmeCA9IGZ4c1tpXTsKICAgICAgICAgIGlmICgoZnguaW5mby5sYXN0UnVuICE9PSBkZWR1cGVJZCQxKSAmJgogICAgICAgICAgICAgICghaGFzUGF0aHMgfHwgcGF0aE1hdGNoZXNUcmlnZ2VyKHByb3AsIGZ4LnRyaWdnZXIpKSkgewogICAgICAgICAgICBmeC5pbmZvLmxhc3RSdW4gPSBkZWR1cGVJZCQxOwogICAgICAgICAgICBpbnNlcnRFZmZlY3QoZnguaW5mbywgcXVldWUsIG9yZGVyKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICAgKiBHZW5lcmF0ZXMgYW5kIHJldHJpZXZlcyBhIG1lbW9pemVkIG1hcCBvZiBjb21wdXRlZCBwcm9wZXJ0eSBuYW1lIHRvIGl0cwogICAgICogdG9wb2xvZ2ljYWxseS1zb3J0ZWQgb3JkZXIuCiAgICAgKgogICAgICogVGhlIG1hcCBpcyBnZW5lcmF0ZWQgYnkgZmlyc3QgYXNzaWduaW5nIGEgImRlcGVuZGVuY3kgY291bnQiIHRvIGVhY2ggcHJvcGVydHkKICAgICAqIChkZWZpbmVkIGFzIG51bWJlciBwcm9wZXJ0aWVzIGl0IGRlcGVuZHMgb24sIGluY2x1ZGluZyBpdHMgbWV0aG9kIGZvcgogICAgICogImR5bmFtaWMgZnVuY3Rpb25zIikuIEFueSBwcm9wZXJ0aWVzIHRoYXQgaGF2ZSBubyBkZXBlbmRlbmNpZXMgYXJlIGFkZGVkIHRvCiAgICAgKiB0aGUgYHJlYWR5YCBxdWV1ZSwgd2hpY2ggYXJlIHByb3BlcnRpZXMgd2hvc2Ugb3JkZXIgY2FuIGJlIGFkZGVkIHRvIHRoZSBmaW5hbAogICAgICogb3JkZXIgbWFwLiBQcm9wZXJ0aWVzIGFyZSBwb3BwZWQgb2ZmIHRoZSBgcmVhZHlgIHF1ZXVlIG9uZSBieSBvbmUgYW5kIGEuKSBhZGRlZCBhcwogICAgICogdGhlIG5leHQgcHJvcGVydHkgaW4gdGhlIG9yZGVyIG1hcCwgYW5kIGIuKSBlYWNoIHByb3BlcnR5IHRoYXQgaXQgaXMgYQogICAgICogZGVwZW5kZW5jeSBmb3IgaGFzIGl0cyBkZXAgY291bnQgZGVjcmVtZW50ZWQgKGFuZCBpZiB0aGF0IHByb3BlcnR5J3MgZGVwCiAgICAgKiBjb3VudCBnb2VzIHRvIHplcm8sIGl0IGlzIGFkZGVkIHRvIHRoZSBgcmVhZHlgIHF1ZXVlKSwgdW50aWwgYWxsIHByb3BlcnRpZXMKICAgICAqIGhhdmUgYmVlbiB2aXNpdGVkIGFuZCBvcmRlcmVkLgogICAgICoKICAgICAqIFVzZWQgYnkgYG9yZGVyZWRDb21wdXRlZDogdHJ1ZWAgY29tcHV0ZWQgcHJvcGVydHkgYWxnb3JpdGhtLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB0byByZXRyaWV2ZSB0aGUgY29tcHV0ZWQKICAgICAqICAgZWZmZWN0IG9yZGVyIGZvci4KICAgICAqIEByZXR1cm4ge01hcDxzdHJpbmcsbnVtYmVyPn0gTWFwIG9mIGNvbXB1dGVkIHByb3BlcnR5IG5hbWUtPnRvcG9sb2dpY2FsIHNvcnQKICAgICAqICAgb3JkZXIKICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Q29tcHV0ZWRPcmRlcihpbnN0KSB7CiAgICAgIGxldCBvcmRlcmVkID0gaW5zdC5jb25zdHJ1Y3Rvci5fX29yZGVyZWRDb21wdXRlZERlcHM7CiAgICAgIGlmICghb3JkZXJlZCkgewogICAgICAgIG9yZGVyZWQgPSBuZXcgTWFwKCk7CiAgICAgICAgY29uc3QgZWZmZWN0cyA9IGluc3RbVFlQRVMuQ09NUFVURV07CiAgICAgICAgbGV0IHtjb3VudHMsIHJlYWR5LCB0b3RhbH0gPSBkZXBlbmRlbmN5Q291bnRzKGluc3QpOwogICAgICAgIGxldCBjdXJyOwogICAgICAgIHdoaWxlICgoY3VyciA9IHJlYWR5LnNoaWZ0KCkpKSB7CiAgICAgICAgICBvcmRlcmVkLnNldChjdXJyLCBvcmRlcmVkLnNpemUpOwogICAgICAgICAgY29uc3QgY29tcHV0ZWRCeUN1cnIgPSBlZmZlY3RzW2N1cnJdOwogICAgICAgICAgaWYgKGNvbXB1dGVkQnlDdXJyKSB7CiAgICAgICAgICAgIGNvbXB1dGVkQnlDdXJyLmZvckVhY2goZnggPT4gewogICAgICAgICAgICAgIC8vIE5vdGUgYG1ldGhvZEluZm9gIGlzIHdoZXJlIHRoZSBjb21wdXRlZCBwcm9wZXJ0eSBuYW1lIGlzIHN0b3JlZAogICAgICAgICAgICAgIGNvbnN0IGNvbXB1dGVkUHJvcCA9IGZ4LmluZm8ubWV0aG9kSW5mbzsKICAgICAgICAgICAgICAtLXRvdGFsOwogICAgICAgICAgICAgIGlmICgtLWNvdW50c1tjb21wdXRlZFByb3BdID09PSAwKSB7CiAgICAgICAgICAgICAgICByZWFkeS5wdXNoKGNvbXB1dGVkUHJvcCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKHRvdGFsICE9PSAwKSB7CiAgICAgICAgICBjb25zdCBlbCA9IC8qKiBAdHlwZSB7SFRNTEVsZW1lbnR9ICovIChpbnN0KTsKICAgICAgICAgIGNvbnNvbGUud2FybihgQ29tcHV0ZWQgZ3JhcGggZm9yICR7ZWwubG9jYWxOYW1lfSBpbmNvbXBsZXRlOyBjaXJjdWxhcj9gKTsKICAgICAgICB9CiAgICAgICAgaW5zdC5jb25zdHJ1Y3Rvci5fX29yZGVyZWRDb21wdXRlZERlcHMgPSBvcmRlcmVkOwogICAgICB9CiAgICAgIHJldHVybiBvcmRlcmVkOwogICAgfQoKICAgIC8qKgogICAgICogR2VuZXJhdGVzIGEgbWFwIG9mIHByb3BlcnR5LXRvLWRlcGVuZGVuY3kgY291bnQgKGBjb3VudHNgLCB3aGVyZSAiZGVwZW5kZW5jeQogICAgICogY291bnQiIGlzIHRoZSBudW1iZXIgb2YgZGVwZW5kZW5jaWVzIGEgZ2l2ZW4gcHJvcGVydHkgaGFzIGFzc3VtaW5nIGl0IGlzIGEKICAgICAqIGNvbXB1dGVkIHByb3BlcnR5LCBvdGhlcndpc2UgMCkuICBJdCBhbHNvIHJldHVybnMgYSBwcmUtcG9wdWxhdGVkIGxpc3Qgb2YKICAgICAqIGByZWFkeWAgcHJvcGVydGllcyB0aGF0IGhhdmUgbm8gZGVwZW5kZW5jaWVzIGFuZCBhIGB0b3RhbGAgY291bnQsIHdoaWNoIGlzCiAgICAgKiB1c2VkIGZvciBlcnJvci1jaGVja2luZyB0aGUgZ3JhcGguCiAgICAgKgogICAgICogVXNlZCBieSBgb3JkZXJlZENvbXB1dGVkOiB0cnVlYCBjb21wdXRlZCBwcm9wZXJ0eSBhbGdvcml0aG0uCiAgICAgKgogICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgVGhlIGluc3RhbmNlIHRvIGdlbmVyYXRlIGRlcGVuZGVuY3kKICAgICAqICAgY291bnRzIGZvci4KICAgICAqIEByZXR1cm4geyFPYmplY3R9IE9iamVjdCBjb250YWluaW5nIGBjb3VudHNgIG1hcCAocHJvcGVydHktdG8tZGVwZW5kZW5jeQogICAgICogICBjb3VudCkgYW5kIHByZS1wb3B1bGF0ZWQgYHJlYWR5YCBhcnJheSBvZiBwcm9wZXJ0aWVzIHRoYXQgaGFkIHplcm8KICAgICAqICAgZGVwZW5kZW5jaWVzLgogICAgICovCiAgICBmdW5jdGlvbiBkZXBlbmRlbmN5Q291bnRzKGluc3QpIHsKICAgICAgY29uc3QgaW5mb0ZvckNvbXB1dGVkID0gaW5zdFtDT01QVVRFX0lORk9dOwogICAgICBjb25zdCBjb3VudHMgPSB7fTsKICAgICAgY29uc3QgY29tcHV0ZWREZXBzID0gaW5zdFtUWVBFUy5DT01QVVRFXTsKICAgICAgY29uc3QgcmVhZHkgPSBbXTsKICAgICAgbGV0IHRvdGFsID0gMDsKICAgICAgLy8gQ291bnQgZGVwZW5kZW5jaWVzIGZvciBlYWNoIGNvbXB1dGVkIHByb3BlcnR5CiAgICAgIGZvciAobGV0IHAgaW4gaW5mb0ZvckNvbXB1dGVkKSB7CiAgICAgICAgY29uc3QgaW5mbyA9IGluZm9Gb3JDb21wdXRlZFtwXTsKICAgICAgICAvLyBCZSBzdXJlIHRvIGFkZCB0aGUgbWV0aG9kIG5hbWUgaXRzZWxmIGluIGNhc2Ugb2YgImR5bmFtaWMgZnVuY3Rpb25zIgogICAgICAgIHRvdGFsICs9IGNvdW50c1twXSA9CiAgICAgICAgICBpbmZvLmFyZ3MuZmlsdGVyKGEgPT4gIWEubGl0ZXJhbCkubGVuZ3RoICsgKGluZm8uZHluYW1pY0ZuID8gMSA6IDApOwogICAgICB9CiAgICAgIC8vIEJ1aWxkIGxpc3Qgb2YgcmVhZHkgcHJvcGVydGllcyAodGhhdCBhcmVuJ3QgdGhlbXNlbHZlcyBjb21wdXRlZCkKICAgICAgZm9yIChsZXQgcCBpbiBjb21wdXRlZERlcHMpIHsKICAgICAgICBpZiAoIWluZm9Gb3JDb21wdXRlZFtwXSkgewogICAgICAgICAgcmVhZHkucHVzaChwKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHtjb3VudHMsIHJlYWR5LCB0b3RhbH07CiAgICB9CgogICAgLyoqCiAgICAgKiBJbXBsZW1lbnRzIHRoZSAiY29tcHV0ZWQgcHJvcGVydHkiIGVmZmVjdCBieSBydW5uaW5nIHRoZSBtZXRob2Qgd2l0aCB0aGUKICAgICAqIHZhbHVlcyBvZiB0aGUgYXJndW1lbnRzIHNwZWNpZmllZCBpbiB0aGUgYGluZm9gIG9iamVjdCBhbmQgc2V0dGluZyB0aGUKICAgICAqIHJldHVybiB2YWx1ZSB0byB0aGUgY29tcHV0ZWQgcHJvcGVydHkgc3BlY2lmaWVkLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB0aGUgZWZmZWN0IHdpbGwgYmUgcnVuIG9uCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiBwcm9wZXJ0eQogICAgICogQHBhcmFtIHs/T2JqZWN0fSBjaGFuZ2VkUHJvcHMgQmFnIG9mIGN1cnJlbnQgcHJvcGVydHkgY2hhbmdlcwogICAgICogQHBhcmFtIHs/T2JqZWN0fSBvbGRQcm9wcyBCYWcgb2YgcHJldmlvdXMgdmFsdWVzIGZvciBjaGFuZ2VkIHByb3BlcnRpZXMKICAgICAqIEBwYXJhbSB7P30gaW5mbyBFZmZlY3QgbWV0YWRhdGEKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgd2hlbiB0aGUgcHJvcGVydHkgYmVpbmcgY29tcHV0ZWQgY2hhbmdlZAogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gcnVuQ29tcHV0ZWRFZmZlY3QoaW5zdCwgcHJvcGVydHksIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGluZm8pIHsKICAgICAgLy8gRGlydHkgY2hlY2sgZGVwZW5kZW5jaWVzIGFuZCBydW4gaWYgYW55IGludmFsaWQKICAgICAgbGV0IHJlc3VsdCA9IHJ1bk1ldGhvZEVmZmVjdChpbnN0LCBwcm9wZXJ0eSwgY2hhbmdlZFByb3BzLCBvbGRQcm9wcywgaW5mbyk7CiAgICAgIC8vIEFib3J0IGlmIG1ldGhvZCByZXR1cm5zIGEgbm8tb3AgcmVzdWx0CiAgICAgIGlmIChyZXN1bHQgPT09IE5PT1ApIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgbGV0IGNvbXB1dGVkUHJvcCA9IGluZm8ubWV0aG9kSW5mbzsKICAgICAgaWYgKGluc3QuX19kYXRhSGFzQWNjZXNzb3IgJiYgaW5zdC5fX2RhdGFIYXNBY2Nlc3Nvcltjb21wdXRlZFByb3BdKSB7CiAgICAgICAgcmV0dXJuIGluc3QuX3NldFBlbmRpbmdQcm9wZXJ0eShjb21wdXRlZFByb3AsIHJlc3VsdCwgdHJ1ZSk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgaW5zdFtjb21wdXRlZFByb3BdID0gcmVzdWx0OwogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQ29tcHV0ZXMgcGF0aCBjaGFuZ2VzIGJhc2VkIG9uIHBhdGggbGlua3Mgc2V0IHVwIHVzaW5nIHRoZSBgbGlua1BhdGhzYAogICAgICogQVBJLgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB3aG9zZSBwcm9wcyBhcmUgY2hhbmdpbmcKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFBhdGggdGhhdCBoYXMgY2hhbmdlZAogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSBvZiBjaGFuZ2VkIHBhdGgKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBjb21wdXRlTGlua2VkUGF0aHMoaW5zdCwgcGF0aCwgdmFsdWUpIHsKICAgICAgbGV0IGxpbmtzID0gaW5zdC5fX2RhdGFMaW5rZWRQYXRoczsKICAgICAgaWYgKGxpbmtzKSB7CiAgICAgICAgbGV0IGxpbms7CiAgICAgICAgZm9yIChsZXQgYSBpbiBsaW5rcykgewogICAgICAgICAgbGV0IGIgPSBsaW5rc1thXTsKICAgICAgICAgIGlmIChpc0Rlc2NlbmRhbnQoYSwgcGF0aCkpIHsKICAgICAgICAgICAgbGluayA9IHRyYW5zbGF0ZShhLCBiLCBwYXRoKTsKICAgICAgICAgICAgaW5zdC5fc2V0UGVuZGluZ1Byb3BlcnR5T3JQYXRoKGxpbmssIHZhbHVlLCB0cnVlLCB0cnVlKTsKICAgICAgICAgIH0gZWxzZSBpZiAoaXNEZXNjZW5kYW50KGIsIHBhdGgpKSB7CiAgICAgICAgICAgIGxpbmsgPSB0cmFuc2xhdGUoYiwgYSwgcGF0aCk7CiAgICAgICAgICAgIGluc3QuX3NldFBlbmRpbmdQcm9wZXJ0eU9yUGF0aChsaW5rLCB2YWx1ZSwgdHJ1ZSwgdHJ1ZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLy8gLS0gYmluZGluZ3MgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAgIC8qKgogICAgICogQWRkcyBiaW5kaW5nIG1ldGFkYXRhIHRvIHRoZSBjdXJyZW50IGBub2RlSW5mb2AsIGFuZCBiaW5kaW5nIGVmZmVjdHMKICAgICAqIGZvciBhbGwgcGFydCBkZXBlbmRlbmNpZXMgdG8gYHRlbXBsYXRlSW5mb2AuCiAgICAgKgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY29uc3RydWN0b3IgQ2xhc3MgdGhhdCBgX3BhcnNlVGVtcGxhdGVgIGlzIGN1cnJlbnRseQogICAgICogICBydW5uaW5nIG9uCiAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgKiBAcGFyYW0ge05vZGVJbmZvfSBub2RlSW5mbyBOb2RlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlIG5vZGUKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBraW5kIEJpbmRpbmcga2luZCwgZWl0aGVyICdwcm9wZXJ0eScsICdhdHRyaWJ1dGUnLCBvciAndGV4dCcKICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0YXJnZXQgVGFyZ2V0IHByb3BlcnR5IG5hbWUKICAgICAqIEBwYXJhbSB7IUFycmF5PCFCaW5kaW5nUGFydD59IHBhcnRzIEFycmF5IG9mIGJpbmRpbmcgcGFydCBtZXRhZGF0YQogICAgICogQHBhcmFtIHtzdHJpbmc9fSBsaXRlcmFsIExpdGVyYWwgdGV4dCBzdXJyb3VuZGluZyBiaW5kaW5nIHBhcnRzIChzcGVjaWZpZWQKICAgICAqICAgb25seSBmb3IgJ3Byb3BlcnR5JyBiaW5kaW5ncywgc2luY2UgdGhlc2UgbXVzdCBiZSBpbml0aWFsaXplZCBhcyBwYXJ0CiAgICAgKiAgIG9mIGJvb3QtdXApCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gYWRkQmluZGluZyhjb25zdHJ1Y3RvciwgdGVtcGxhdGVJbmZvLCBub2RlSW5mbywga2luZCwgdGFyZ2V0LCBwYXJ0cywgbGl0ZXJhbCkgewogICAgICAvLyBDcmVhdGUgYmluZGluZyBtZXRhZGF0YSBhbmQgYWRkIHRvIG5vZGVJbmZvCiAgICAgIG5vZGVJbmZvLmJpbmRpbmdzID0gbm9kZUluZm8uYmluZGluZ3MgfHwgW107CiAgICAgIGxldCAvKiogQmluZGluZyAqLyBiaW5kaW5nID0geyBraW5kLCB0YXJnZXQsIHBhcnRzLCBsaXRlcmFsLCBpc0NvbXBvdW5kOiAocGFydHMubGVuZ3RoICE9PSAxKSB9OwogICAgICBub2RlSW5mby5iaW5kaW5ncy5wdXNoKGJpbmRpbmcpOwogICAgICAvLyBBZGQgbGlzdGVuZXIgaW5mbyB0byBiaW5kaW5nIG1ldGFkYXRhCiAgICAgIGlmIChzaG91bGRBZGRMaXN0ZW5lcihiaW5kaW5nKSkgewogICAgICAgIGxldCB7ZXZlbnQsIG5lZ2F0ZX0gPSBiaW5kaW5nLnBhcnRzWzBdOwogICAgICAgIGJpbmRpbmcubGlzdGVuZXJFdmVudCA9IGV2ZW50IHx8IChjYW1lbFRvRGFzaENhc2UodGFyZ2V0KSArICctY2hhbmdlZCcpOwogICAgICAgIGJpbmRpbmcubGlzdGVuZXJOZWdhdGUgPSBuZWdhdGU7CiAgICAgIH0KICAgICAgLy8gQWRkICJwcm9wYWdhdGUiIHByb3BlcnR5IGVmZmVjdHMgdG8gdGVtcGxhdGVJbmZvCiAgICAgIGxldCBpbmRleCA9IHRlbXBsYXRlSW5mby5ub2RlSW5mb0xpc3QubGVuZ3RoOwogICAgICBmb3IgKGxldCBpPTA7IGk8YmluZGluZy5wYXJ0cy5sZW5ndGg7IGkrKykgewogICAgICAgIGxldCBwYXJ0ID0gYmluZGluZy5wYXJ0c1tpXTsKICAgICAgICBwYXJ0LmNvbXBvdW5kSW5kZXggPSBpOwogICAgICAgIGFkZEVmZmVjdEZvckJpbmRpbmdQYXJ0KGNvbnN0cnVjdG9yLCB0ZW1wbGF0ZUluZm8sIGJpbmRpbmcsIHBhcnQsIGluZGV4KTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQWRkcyBwcm9wZXJ0eSBlZmZlY3RzIHRvIHRoZSBnaXZlbiBgdGVtcGxhdGVJbmZvYCBmb3IgdGhlIGdpdmVuIGJpbmRpbmcKICAgICAqIHBhcnQuCiAgICAgKgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY29uc3RydWN0b3IgQ2xhc3MgdGhhdCBgX3BhcnNlVGVtcGxhdGVgIGlzIGN1cnJlbnRseQogICAgICogICBydW5uaW5nIG9uCiAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgKiBAcGFyYW0geyFCaW5kaW5nfSBiaW5kaW5nIEJpbmRpbmcgbWV0YWRhdGEKICAgICAqIEBwYXJhbSB7IUJpbmRpbmdQYXJ0fSBwYXJ0IEJpbmRpbmcgcGFydCBtZXRhZGF0YQogICAgICogQHBhcmFtIHtudW1iZXJ9IGluZGV4IEluZGV4IGludG8gYG5vZGVJbmZvTGlzdGAgZm9yIHRoaXMgbm9kZQogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gYWRkRWZmZWN0Rm9yQmluZGluZ1BhcnQoY29uc3RydWN0b3IsIHRlbXBsYXRlSW5mbywgYmluZGluZywgcGFydCwgaW5kZXgpIHsKICAgICAgaWYgKCFwYXJ0LmxpdGVyYWwpIHsKICAgICAgICBpZiAoYmluZGluZy5raW5kID09PSAnYXR0cmlidXRlJyAmJiBiaW5kaW5nLnRhcmdldFswXSA9PT0gJy0nKSB7CiAgICAgICAgICBjb25zb2xlLndhcm4oJ0Nhbm5vdCBzZXQgYXR0cmlidXRlICcgKyBiaW5kaW5nLnRhcmdldCArCiAgICAgICAgICAgICcgYmVjYXVzZSAiLSIgaXMgbm90IGEgdmFsaWQgYXR0cmlidXRlIHN0YXJ0aW5nIGNoYXJhY3RlcicpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBsZXQgZGVwZW5kZW5jaWVzID0gcGFydC5kZXBlbmRlbmNpZXM7CiAgICAgICAgICBsZXQgaW5mbyA9IHsgaW5kZXgsIGJpbmRpbmcsIHBhcnQsIGV2YWx1YXRvcjogY29uc3RydWN0b3IgfTsKICAgICAgICAgIGZvciAobGV0IGo9MDsgajxkZXBlbmRlbmNpZXMubGVuZ3RoOyBqKyspIHsKICAgICAgICAgICAgbGV0IHRyaWdnZXIgPSBkZXBlbmRlbmNpZXNbal07CiAgICAgICAgICAgIGlmICh0eXBlb2YgdHJpZ2dlciA9PSAnc3RyaW5nJykgewogICAgICAgICAgICAgIHRyaWdnZXIgPSBwYXJzZUFyZyh0cmlnZ2VyKTsKICAgICAgICAgICAgICB0cmlnZ2VyLndpbGRjYXJkID0gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdHJ1Y3Rvci5fYWRkVGVtcGxhdGVQcm9wZXJ0eUVmZmVjdCh0ZW1wbGF0ZUluZm8sIHRyaWdnZXIucm9vdFByb3BlcnR5LCB7CiAgICAgICAgICAgICAgZm46IHJ1bkJpbmRpbmdFZmZlY3QsCiAgICAgICAgICAgICAgaW5mbywgdHJpZ2dlcgogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEltcGxlbWVudHMgdGhlICJiaW5kaW5nIiAocHJvcGVydHkvcGF0aCBiaW5kaW5nKSBlZmZlY3QuCiAgICAgKgogICAgICogTm90ZSB0aGF0IGJpbmRpbmcgc3ludGF4IGlzIG92ZXJyaWRhYmxlIHZpYSBgX3BhcnNlQmluZGluZ3NgIGFuZAogICAgICogYF9ldmFsdWF0ZUJpbmRpbmdgLiAgVGhpcyBtZXRob2Qgd2lsbCBjYWxsIGBfZXZhbHVhdGVCaW5kaW5nYCBmb3IgYW55CiAgICAgKiBub24tbGl0ZXJhbCBwYXJ0cyByZXR1cm5lZCBmcm9tIGBfcGFyc2VCaW5kaW5nc2AuICBIb3dldmVyLAogICAgICogdGhlcmUgaXMgbm8gc3VwcG9ydCBmb3IgX3BhdGhfIGJpbmRpbmdzIHZpYSBjdXN0b20gYmluZGluZyBwYXJ0cywKICAgICAqIGFzIHRoaXMgaXMgc3BlY2lmaWMgdG8gUG9seW1lcidzIHBhdGggYmluZGluZyBzeW50YXguCiAgICAgKgogICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgVGhlIGluc3RhbmNlIHRoZSBlZmZlY3Qgd2lsbCBiZSBydW4gb24KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIE5hbWUgb2YgcHJvcGVydHkKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgY3VycmVudCBwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2xkUHJvcHMgQmFnIG9mIHByZXZpb3VzIHZhbHVlcyBmb3IgY2hhbmdlZCBwcm9wZXJ0aWVzCiAgICAgKiBAcGFyYW0gez99IGluZm8gRWZmZWN0IG1ldGFkYXRhCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IGhhc1BhdGhzIFRydWUgd2l0aCBgcHJvcHNgIGNvbnRhaW5zIG9uZSBvciBtb3JlIHBhdGhzCiAgICAgKiBAcGFyYW0ge0FycmF5fSBub2RlTGlzdCBMaXN0IG9mIG5vZGVzIGFzc29jaWF0ZWQgd2l0aCBgbm9kZUluZm9MaXN0YCB0ZW1wbGF0ZQogICAgICogICBtZXRhZGF0YQogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1bkJpbmRpbmdFZmZlY3QoaW5zdCwgcGF0aCwgcHJvcHMsIG9sZFByb3BzLCBpbmZvLCBoYXNQYXRocywgbm9kZUxpc3QpIHsKICAgICAgbGV0IG5vZGUgPSBub2RlTGlzdFtpbmZvLmluZGV4XTsKICAgICAgbGV0IGJpbmRpbmcgPSBpbmZvLmJpbmRpbmc7CiAgICAgIGxldCBwYXJ0ID0gaW5mby5wYXJ0OwogICAgICAvLyBTdWJwYXRoIG5vdGlmaWNhdGlvbjogdHJhbnNmb3JtIHBhdGggYW5kIHNldCB0byBjbGllbnQKICAgICAgLy8gZS5nLjogZm9vPSJ7e29iai5zdWJ9fSIsIHBhdGg6ICdvYmouc3ViLnByb3AnLCBzZXQgJ2Zvby5wcm9wJz1vYmouc3ViLnByb3AKICAgICAgaWYgKGhhc1BhdGhzICYmIHBhcnQuc291cmNlICYmIChwYXRoLmxlbmd0aCA+IHBhcnQuc291cmNlLmxlbmd0aCkgJiYKICAgICAgICAgIChiaW5kaW5nLmtpbmQgPT0gJ3Byb3BlcnR5JykgJiYgIWJpbmRpbmcuaXNDb21wb3VuZCAmJgogICAgICAgICAgbm9kZS5fX2lzUHJvcGVydHlFZmZlY3RzQ2xpZW50ICYmCiAgICAgICAgICBub2RlLl9fZGF0YUhhc0FjY2Vzc29yICYmIG5vZGUuX19kYXRhSGFzQWNjZXNzb3JbYmluZGluZy50YXJnZXRdKSB7CiAgICAgICAgbGV0IHZhbHVlID0gcHJvcHNbcGF0aF07CiAgICAgICAgcGF0aCA9IHRyYW5zbGF0ZShwYXJ0LnNvdXJjZSwgYmluZGluZy50YXJnZXQsIHBhdGgpOwogICAgICAgIGlmIChub2RlLl9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgocGF0aCwgdmFsdWUsIGZhbHNlLCB0cnVlKSkgewogICAgICAgICAgaW5zdC5fZW5xdWV1ZUNsaWVudChub2RlKTsKICAgICAgICB9CiAgICAgIH0gZWxzZSB7CiAgICAgICAgbGV0IHZhbHVlID0gaW5mby5ldmFsdWF0b3IuX2V2YWx1YXRlQmluZGluZyhpbnN0LCBwYXJ0LCBwYXRoLCBwcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKTsKICAgICAgICAvLyBQcm9wYWdhdGUgdmFsdWUgdG8gY2hpbGQKICAgICAgICAvLyBBYm9ydCBpZiB2YWx1ZSBpcyBhIG5vLW9wIHJlc3VsdAogICAgICAgIGlmICh2YWx1ZSAhPT0gTk9PUCkgewogICAgICAgICAgYXBwbHlCaW5kaW5nVmFsdWUoaW5zdCwgbm9kZSwgYmluZGluZywgcGFydCwgdmFsdWUpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogU2V0cyB0aGUgdmFsdWUgZm9yIGFuICJiaW5kaW5nIiAoYmluZGluZykgZWZmZWN0IHRvIGEgbm9kZSwKICAgICAqIGVpdGhlciBhcyBhIHByb3BlcnR5IG9yIGF0dHJpYnV0ZS4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBUaGUgaW5zdGFuY2Ugb3duaW5nIHRoZSBiaW5kaW5nIGVmZmVjdAogICAgICogQHBhcmFtIHtOb2RlfSBub2RlIFRhcmdldCBub2RlIGZvciBiaW5kaW5nCiAgICAgKiBAcGFyYW0geyFCaW5kaW5nfSBiaW5kaW5nIEJpbmRpbmcgbWV0YWRhdGEKICAgICAqIEBwYXJhbSB7IUJpbmRpbmdQYXJ0fSBwYXJ0IEJpbmRpbmcgcGFydCBtZXRhZGF0YQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSB0byBzZXQKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBhcHBseUJpbmRpbmdWYWx1ZShpbnN0LCBub2RlLCBiaW5kaW5nLCBwYXJ0LCB2YWx1ZSkgewogICAgICB2YWx1ZSA9IGNvbXB1dGVCaW5kaW5nVmFsdWUobm9kZSwgdmFsdWUsIGJpbmRpbmcsIHBhcnQpOwogICAgICBpZiAoc2FuaXRpemVET01WYWx1ZSkgewogICAgICAgIHZhbHVlID0gc2FuaXRpemVET01WYWx1ZSh2YWx1ZSwgYmluZGluZy50YXJnZXQsIGJpbmRpbmcua2luZCwgbm9kZSk7CiAgICAgIH0KICAgICAgaWYgKGJpbmRpbmcua2luZCA9PSAnYXR0cmlidXRlJykgewogICAgICAgIC8vIEF0dHJpYnV0ZSBiaW5kaW5nCiAgICAgICAgaW5zdC5fdmFsdWVUb05vZGVBdHRyaWJ1dGUoLyoqIEB0eXBlIHtFbGVtZW50fSAqLyhub2RlKSwgdmFsdWUsIGJpbmRpbmcudGFyZ2V0KTsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBQcm9wZXJ0eSBiaW5kaW5nCiAgICAgICAgbGV0IHByb3AgPSBiaW5kaW5nLnRhcmdldDsKICAgICAgICBpZiAobm9kZS5fX2lzUHJvcGVydHlFZmZlY3RzQ2xpZW50ICYmCiAgICAgICAgICAgIG5vZGUuX19kYXRhSGFzQWNjZXNzb3IgJiYgbm9kZS5fX2RhdGFIYXNBY2Nlc3Nvcltwcm9wXSkgewogICAgICAgICAgaWYgKCFub2RlW1RZUEVTLlJFQURfT05MWV0gfHwgIW5vZGVbVFlQRVMuUkVBRF9PTkxZXVtwcm9wXSkgewogICAgICAgICAgICBpZiAobm9kZS5fc2V0UGVuZGluZ1Byb3BlcnR5KHByb3AsIHZhbHVlKSkgewogICAgICAgICAgICAgIGluc3QuX2VucXVldWVDbGllbnQobm9kZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gSW4gbGVnYWN5IG5vLWJhdGNoaW5nIG1vZGUsIGJpbmRpbmdzIGFwcGxpZWQgYmVmb3JlIGRhdGFSZWFkeSBhcmUKICAgICAgICAgIC8vIGVxdWl2YWxlbnQgdG8gdGhlICJhcHBseSBjb25maWciIHBoYXNlLCB3aGljaCBvbmx5IHNldCBtYW5hZ2VkIHByb3BzCiAgICAgICAgICBpbnN0Ll9zZXRVbm1hbmFnZWRQcm9wZXJ0eVRvTm9kZShub2RlLCBwcm9wLCB2YWx1ZSk7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBUcmFuc2Zvcm1zIGFuICJiaW5kaW5nIiBlZmZlY3QgdmFsdWUgYmFzZWQgb24gY29tcG91bmQgJiBuZWdhdGlvbgogICAgICogZWZmZWN0IG1ldGFkYXRhLCBhcyB3ZWxsIGFzIGhhbmRsaW5nIGZvciBzcGVjaWFsLWNhc2UgcHJvcGVydGllcwogICAgICoKICAgICAqIEBwYXJhbSB7Tm9kZX0gbm9kZSBOb2RlIHRoZSB2YWx1ZSB3aWxsIGJlIHNldCB0bwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSB0byBzZXQKICAgICAqIEBwYXJhbSB7IUJpbmRpbmd9IGJpbmRpbmcgQmluZGluZyBtZXRhZGF0YQogICAgICogQHBhcmFtIHshQmluZGluZ1BhcnR9IHBhcnQgQmluZGluZyBwYXJ0IG1ldGFkYXRhCiAgICAgKiBAcmV0dXJuIHsqfSBUcmFuc2Zvcm1lZCB2YWx1ZSB0byBzZXQKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbXB1dGVCaW5kaW5nVmFsdWUobm9kZSwgdmFsdWUsIGJpbmRpbmcsIHBhcnQpIHsKICAgICAgaWYgKGJpbmRpbmcuaXNDb21wb3VuZCkgewogICAgICAgIGxldCBzdG9yYWdlID0gbm9kZS5fX2RhdGFDb21wb3VuZFN0b3JhZ2VbYmluZGluZy50YXJnZXRdOwogICAgICAgIHN0b3JhZ2VbcGFydC5jb21wb3VuZEluZGV4XSA9IHZhbHVlOwogICAgICAgIHZhbHVlID0gc3RvcmFnZS5qb2luKCcnKTsKICAgICAgfQogICAgICBpZiAoYmluZGluZy5raW5kICE9PSAnYXR0cmlidXRlJykgewogICAgICAgIC8vIFNvbWUgYnJvd3NlcnMgc2VyaWFsaXplIGB1bmRlZmluZWRgIHRvIGAidW5kZWZpbmVkImAKICAgICAgICBpZiAoYmluZGluZy50YXJnZXQgPT09ICd0ZXh0Q29udGVudCcgfHwKICAgICAgICAgICAgKGJpbmRpbmcudGFyZ2V0ID09PSAndmFsdWUnICYmCiAgICAgICAgICAgICAgKG5vZGUubG9jYWxOYW1lID09PSAnaW5wdXQnIHx8IG5vZGUubG9jYWxOYW1lID09PSAndGV4dGFyZWEnKSkpIHsKICAgICAgICAgIHZhbHVlID0gdmFsdWUgPT0gdW5kZWZpbmVkID8gJycgOiB2YWx1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHZhbHVlOwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyB0cnVlIGlmIGEgYmluZGluZydzIG1ldGFkYXRhIG1lZXRzIGFsbCB0aGUgcmVxdWlyZW1lbnRzIHRvIGFsbG93CiAgICAgKiAyLXdheSBiaW5kaW5nLCBhbmQgdGhlcmVmb3JlIGEgYDxwcm9wZXJ0eT4tY2hhbmdlZGAgZXZlbnQgbGlzdGVuZXIgc2hvdWxkIGJlCiAgICAgKiBhZGRlZDoKICAgICAqIC0gdXNlZCBjdXJseSBicmFjZXMKICAgICAqIC0gaXMgYSBwcm9wZXJ0eSAobm90IGF0dHJpYnV0ZSkgYmluZGluZwogICAgICogLSBpcyBub3QgYSB0ZXh0Q29udGVudCBiaW5kaW5nCiAgICAgKiAtIGlzIG5vdCBjb21wb3VuZAogICAgICoKICAgICAqIEBwYXJhbSB7IUJpbmRpbmd9IGJpbmRpbmcgQmluZGluZyBtZXRhZGF0YQogICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiAyLXdheSBsaXN0ZW5lciBzaG91bGQgYmUgYWRkZWQKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHNob3VsZEFkZExpc3RlbmVyKGJpbmRpbmcpIHsKICAgICAgcmV0dXJuIEJvb2xlYW4oYmluZGluZy50YXJnZXQpICYmCiAgICAgICAgICAgICBiaW5kaW5nLmtpbmQgIT0gJ2F0dHJpYnV0ZScgJiYKICAgICAgICAgICAgIGJpbmRpbmcua2luZCAhPSAndGV4dCcgJiYKICAgICAgICAgICAgICFiaW5kaW5nLmlzQ29tcG91bmQgJiYKICAgICAgICAgICAgIGJpbmRpbmcucGFydHNbMF0ubW9kZSA9PT0gJ3snOwogICAgfQoKICAgIC8qKgogICAgICogU2V0dXAgY29tcG91bmQgYmluZGluZyBzdG9yYWdlIHN0cnVjdHVyZXMsIG5vdGlmeSBsaXN0ZW5lcnMsIGFuZCBkYXRhSG9zdAogICAgICogcmVmZXJlbmNlcyBvbnRvIHRoZSBib3VuZCBub2RlTGlzdC4KICAgICAqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gaW5zdCBJbnN0YW5jZSB0aGF0IGJhcyBiZWVuIHByZXZpb3VzbHkKICAgICAqICAgICBib3VuZAogICAgICogQHBhcmFtIHtUZW1wbGF0ZUluZm99IHRlbXBsYXRlSW5mbyBUZW1wbGF0ZSBtZXRhZGF0YQogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHNldHVwQmluZGluZ3MoaW5zdCwgdGVtcGxhdGVJbmZvKSB7CiAgICAgIC8vIFNldHVwIGNvbXBvdW5kIHN0b3JhZ2UsIGRhdGFIb3N0LCBhbmQgbm90aWZ5IGxpc3RlbmVycwogICAgICBsZXQge25vZGVMaXN0LCBub2RlSW5mb0xpc3R9ID0gdGVtcGxhdGVJbmZvOwogICAgICBpZiAobm9kZUluZm9MaXN0Lmxlbmd0aCkgewogICAgICAgIGZvciAobGV0IGk9MDsgaSA8IG5vZGVJbmZvTGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgbGV0IGluZm8gPSBub2RlSW5mb0xpc3RbaV07CiAgICAgICAgICBsZXQgbm9kZSA9IG5vZGVMaXN0W2ldOwogICAgICAgICAgbGV0IGJpbmRpbmdzID0gaW5mby5iaW5kaW5nczsKICAgICAgICAgIGlmIChiaW5kaW5ncykgewogICAgICAgICAgICBmb3IgKGxldCBpPTA7IGk8YmluZGluZ3MubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICBsZXQgYmluZGluZyA9IGJpbmRpbmdzW2ldOwogICAgICAgICAgICAgIHNldHVwQ29tcG91bmRTdG9yYWdlKG5vZGUsIGJpbmRpbmcpOwogICAgICAgICAgICAgIGFkZE5vdGlmeUxpc3RlbmVyKG5vZGUsIGluc3QsIGJpbmRpbmcpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICAvLyBUaGlzIGVuc3VyZXMgYWxsIGJvdW5kIGVsZW1lbnRzIGhhdmUgYSBob3N0IHNldCwgcmVnYXJkbGVzcwogICAgICAgICAgLy8gb2Ygd2hldGhlciB0aGV5IHVwZ3JhZGUgc3luY2hyb25vdXMgdG8gY3JlYXRpb24KICAgICAgICAgIG5vZGUuX19kYXRhSG9zdCA9IGluc3Q7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBJbml0aWFsaXplcyBgX19kYXRhQ29tcG91bmRTdG9yYWdlYCBsb2NhbCBzdG9yYWdlIG9uIGEgYm91bmQgbm9kZSB3aXRoCiAgICAgKiBpbml0aWFsIGxpdGVyYWwgZGF0YSBmb3IgY29tcG91bmQgYmluZGluZ3MsIGFuZCBzZXRzIHRoZSBqb2luZWQKICAgICAqIGxpdGVyYWwgcGFydHMgdG8gdGhlIGJvdW5kIHByb3BlcnR5LgogICAgICoKICAgICAqIFdoZW4gY2hhbmdlcyB0byBjb21wb3VuZCBwYXJ0cyBvY2N1ciwgdGhleSBhcmUgZmlyc3Qgc2V0IGludG8gdGhlIGNvbXBvdW5kCiAgICAgKiBzdG9yYWdlIGFycmF5IGZvciB0aGF0IHByb3BlcnR5LCBhbmQgdGhlbiB0aGUgYXJyYXkgaXMgam9pbmVkIHRvIHJlc3VsdCBpbgogICAgICogdGhlIGZpbmFsIHZhbHVlIHNldCB0byB0aGUgcHJvcGVydHkvYXR0cmlidXRlLgogICAgICoKICAgICAqIEBwYXJhbSB7Tm9kZX0gbm9kZSBCb3VuZCBub2RlIHRvIGluaXRpYWxpemUKICAgICAqIEBwYXJhbSB7QmluZGluZ30gYmluZGluZyBCaW5kaW5nIG1ldGFkYXRhCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gc2V0dXBDb21wb3VuZFN0b3JhZ2Uobm9kZSwgYmluZGluZykgewogICAgICBpZiAoYmluZGluZy5pc0NvbXBvdW5kKSB7CiAgICAgICAgLy8gQ3JlYXRlIGNvbXBvdW5kIHN0b3JhZ2UgbWFwCiAgICAgICAgbGV0IHN0b3JhZ2UgPSBub2RlLl9fZGF0YUNvbXBvdW5kU3RvcmFnZSB8fAogICAgICAgICAgKG5vZGUuX19kYXRhQ29tcG91bmRTdG9yYWdlID0ge30pOwogICAgICAgIGxldCBwYXJ0cyA9IGJpbmRpbmcucGFydHM7CiAgICAgICAgLy8gQ29weSBsaXRlcmFscyBmcm9tIHBhcnRzIGludG8gc3RvcmFnZSBmb3IgdGhpcyBiaW5kaW5nCiAgICAgICAgbGV0IGxpdGVyYWxzID0gbmV3IEFycmF5KHBhcnRzLmxlbmd0aCk7CiAgICAgICAgZm9yIChsZXQgaj0wOyBqPHBhcnRzLmxlbmd0aDsgaisrKSB7CiAgICAgICAgICBsaXRlcmFsc1tqXSA9IHBhcnRzW2pdLmxpdGVyYWw7CiAgICAgICAgfQogICAgICAgIGxldCB0YXJnZXQgPSBiaW5kaW5nLnRhcmdldDsKICAgICAgICBzdG9yYWdlW3RhcmdldF0gPSBsaXRlcmFsczsKICAgICAgICAvLyBDb25maWd1cmUgcHJvcGVydGllcyB3aXRoIHRoZWlyIGxpdGVyYWwgcGFydHMKICAgICAgICBpZiAoYmluZGluZy5saXRlcmFsICYmIGJpbmRpbmcua2luZCA9PSAncHJvcGVydHknKSB7CiAgICAgICAgICAvLyBOb3RlLCBjbGFzc05hbWUgbmVlZHMgc3R5bGUgc2NvcGluZyBzbyB0aGlzIG5lZWRzIHdyYXBwaW5nLgogICAgICAgICAgLy8gV2UgbWF5IGFsc28gd2FudCB0byBjb25zaWRlciBkb2luZyB0aGlzIGZvciBgdGV4dENvbnRlbnRgIGFuZAogICAgICAgICAgLy8gYGlubmVySFRNTGAuCiAgICAgICAgICBpZiAodGFyZ2V0ID09PSAnY2xhc3NOYW1lJykgewogICAgICAgICAgICBub2RlID0gd3JhcChub2RlKTsKICAgICAgICAgIH0KICAgICAgICAgIG5vZGVbdGFyZ2V0XSA9IGJpbmRpbmcubGl0ZXJhbDsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEFkZHMgYSAyLXdheSBiaW5kaW5nIG5vdGlmaWNhdGlvbiBldmVudCBsaXN0ZW5lciB0byB0aGUgbm9kZSBzcGVjaWZpZWQKICAgICAqCiAgICAgKiBAcGFyYW0ge09iamVjdH0gbm9kZSBDaGlsZCBlbGVtZW50IHRvIGFkZCBsaXN0ZW5lciB0bwogICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgSG9zdCBlbGVtZW50IGluc3RhbmNlIHRvIGhhbmRsZQogICAgICogICAgIG5vdGlmaWNhdGlvbiBldmVudAogICAgICogQHBhcmFtIHtCaW5kaW5nfSBiaW5kaW5nIEJpbmRpbmcgbWV0YWRhdGEKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBhZGROb3RpZnlMaXN0ZW5lcihub2RlLCBpbnN0LCBiaW5kaW5nKSB7CiAgICAgIGlmIChiaW5kaW5nLmxpc3RlbmVyRXZlbnQpIHsKICAgICAgICBsZXQgcGFydCA9IGJpbmRpbmcucGFydHNbMF07CiAgICAgICAgbm9kZS5hZGRFdmVudExpc3RlbmVyKGJpbmRpbmcubGlzdGVuZXJFdmVudCwgZnVuY3Rpb24oZSkgewogICAgICAgICAgaGFuZGxlTm90aWZpY2F0aW9uKGUsIGluc3QsIGJpbmRpbmcudGFyZ2V0LCBwYXJ0LnNvdXJjZSwgcGFydC5uZWdhdGUpOwogICAgICAgIH0pOwogICAgICB9CiAgICB9CgogICAgLy8gLS0gZm9yIG1ldGhvZC1iYXNlZCBlZmZlY3RzIChjb21wbGV4T2JzZXJ2ZXIgJiBjb21wdXRlZCkgLS0tLS0tLS0tLS0tLS0KCiAgICAvKioKICAgICAqIEFkZHMgcHJvcGVydHkgZWZmZWN0cyBmb3IgZWFjaCBhcmd1bWVudCBpbiB0aGUgbWV0aG9kIHNpZ25hdHVyZSAoYW5kCiAgICAgKiBvcHRpb25hbGx5LCBmb3IgdGhlIG1ldGhvZCBuYW1lIGlmIGBkeW5hbWljYCBpcyB0cnVlKSB0aGF0IGNhbGxzIHRoZQogICAgICogcHJvdmlkZWQgZWZmZWN0IGZ1bmN0aW9uLgogICAgICoKICAgICAqIEBwYXJhbSB7RWxlbWVudCB8IE9iamVjdH0gbW9kZWwgUHJvdG90eXBlIG9yIGluc3RhbmNlCiAgICAgKiBAcGFyYW0geyFNZXRob2RTaWduYXR1cmV9IHNpZyBNZXRob2Qgc2lnbmF0dXJlIG1ldGFkYXRhCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gdHlwZSBUeXBlIG9mIHByb3BlcnR5IGVmZmVjdCB0byBhZGQKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVmZmVjdEZuIEZ1bmN0aW9uIHRvIHJ1biB3aGVuIGFyZ3VtZW50cyBjaGFuZ2UKICAgICAqIEBwYXJhbSB7Kj19IG1ldGhvZEluZm8gRWZmZWN0LXNwZWNpZmljIGluZm9ybWF0aW9uIHRvIGJlIGluY2x1ZGVkIGluCiAgICAgKiAgIG1ldGhvZCBlZmZlY3QgbWV0YWRhdGEKICAgICAqIEBwYXJhbSB7Ym9vbGVhbnxPYmplY3Q9fSBkeW5hbWljRm4gQm9vbGVhbiBvciBvYmplY3QgbWFwIGluZGljYXRpbmcgd2hldGhlcgogICAgICogICBtZXRob2QgbmFtZXMgc2hvdWxkIGJlIGluY2x1ZGVkIGFzIGEgZGVwZW5kZW5jeSB0byB0aGUgZWZmZWN0LiBOb3RlLAogICAgICogICBkZWZhdWx0cyB0byB0cnVlIGlmIHRoZSBzaWduYXR1cmUgaXMgc3RhdGljIChzaWcuc3RhdGljIGlzIHRydWUpLgogICAgICogQHJldHVybiB7IU9iamVjdH0gRWZmZWN0IG1ldGFkYXRhIGZvciB0aGlzIG1ldGhvZCBlZmZlY3QKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNyZWF0ZU1ldGhvZEVmZmVjdChtb2RlbCwgc2lnLCB0eXBlLCBlZmZlY3RGbiwgbWV0aG9kSW5mbywgZHluYW1pY0ZuKSB7CiAgICAgIGR5bmFtaWNGbiA9IHNpZy5zdGF0aWMgfHwgKGR5bmFtaWNGbiAmJgogICAgICAgICh0eXBlb2YgZHluYW1pY0ZuICE9PSAnb2JqZWN0JyB8fCBkeW5hbWljRm5bc2lnLm1ldGhvZE5hbWVdKSk7CiAgICAgIGxldCBpbmZvID0gewogICAgICAgIG1ldGhvZE5hbWU6IHNpZy5tZXRob2ROYW1lLAogICAgICAgIGFyZ3M6IHNpZy5hcmdzLAogICAgICAgIG1ldGhvZEluZm8sCiAgICAgICAgZHluYW1pY0ZuCiAgICAgIH07CiAgICAgIGZvciAobGV0IGk9MCwgYXJnOyAoaTxzaWcuYXJncy5sZW5ndGgpICYmIChhcmc9c2lnLmFyZ3NbaV0pOyBpKyspIHsKICAgICAgICBpZiAoIWFyZy5saXRlcmFsKSB7CiAgICAgICAgICBtb2RlbC5fYWRkUHJvcGVydHlFZmZlY3QoYXJnLnJvb3RQcm9wZXJ0eSwgdHlwZSwgewogICAgICAgICAgICBmbjogZWZmZWN0Rm4sIGluZm86IGluZm8sIHRyaWdnZXI6IGFyZwogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmIChkeW5hbWljRm4pIHsKICAgICAgICBtb2RlbC5fYWRkUHJvcGVydHlFZmZlY3Qoc2lnLm1ldGhvZE5hbWUsIHR5cGUsIHsKICAgICAgICAgIGZuOiBlZmZlY3RGbiwgaW5mbzogaW5mbwogICAgICAgIH0pOwogICAgICB9CiAgICAgIHJldHVybiBpbmZvOwogICAgfQoKICAgIC8qKgogICAgICogQ2FsbHMgYSBtZXRob2Qgd2l0aCBhcmd1bWVudHMgbWFyc2hhbGVkIGZyb20gcHJvcGVydGllcyBvbiB0aGUgaW5zdGFuY2UKICAgICAqIGJhc2VkIG9uIHRoZSBtZXRob2Qgc2lnbmF0dXJlIGNvbnRhaW5lZCBpbiB0aGUgZWZmZWN0IG1ldGFkYXRhLgogICAgICoKICAgICAqIE11bHRpLXByb3BlcnR5IG9ic2VydmVycywgY29tcHV0ZWQgcHJvcGVydGllcywgYW5kIGlubGluZSBjb21wdXRpbmcKICAgICAqIGZ1bmN0aW9ucyBjYWxsIHRoaXMgZnVuY3Rpb24gdG8gaW52b2tlIHRoZSBtZXRob2QsIHRoZW4gdXNlIHRoZSByZXR1cm4KICAgICAqIHZhbHVlIGFjY29yZGluZ2x5LgogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IFRoZSBpbnN0YW5jZSB0aGUgZWZmZWN0IHdpbGwgYmUgcnVuIG9uCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiBwcm9wZXJ0eQogICAgICogQHBhcmFtIHtPYmplY3R9IHByb3BzIEJhZyBvZiBjdXJyZW50IHByb3BlcnR5IGNoYW5nZXMKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvbGRQcm9wcyBCYWcgb2YgcHJldmlvdXMgdmFsdWVzIGZvciBjaGFuZ2VkIHByb3BlcnRpZXMKICAgICAqIEBwYXJhbSB7P30gaW5mbyBFZmZlY3QgbWV0YWRhdGEKICAgICAqIEByZXR1cm4geyp9IFJldHVybnMgdGhlIHJldHVybiB2YWx1ZSBmcm9tIHRoZSBtZXRob2QgaW52b2NhdGlvbgogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gcnVuTWV0aG9kRWZmZWN0KGluc3QsIHByb3BlcnR5LCBwcm9wcywgb2xkUHJvcHMsIGluZm8pIHsKICAgICAgLy8gSW5zdGFuY2VzIGNhbiBvcHRpb25hbGx5IGhhdmUgYSBfbWV0aG9kSG9zdCB3aGljaCBhbGxvd3MgcmVkaXJlY3Rpbmcgd2hlcmUKICAgICAgLy8gdG8gZmluZCBtZXRob2RzLiBDdXJyZW50bHkgdXNlZCBieSBgdGVtcGxhdGl6ZWAuCiAgICAgIGxldCBjb250ZXh0ID0gaW5zdC5fbWV0aG9kSG9zdCB8fCBpbnN0OwogICAgICBsZXQgZm4gPSBjb250ZXh0W2luZm8ubWV0aG9kTmFtZV07CiAgICAgIGlmIChmbikgewogICAgICAgIGxldCBhcmdzID0gaW5zdC5fbWFyc2hhbEFyZ3MoaW5mby5hcmdzLCBwcm9wZXJ0eSwgcHJvcHMpOwogICAgICAgIHJldHVybiBhcmdzID09PSBOT09QID8gTk9PUCA6IGZuLmFwcGx5KGNvbnRleHQsIGFyZ3MpOwogICAgICB9IGVsc2UgaWYgKCFpbmZvLmR5bmFtaWNGbikgewogICAgICAgIGNvbnNvbGUud2FybignbWV0aG9kIGAnICsgaW5mby5tZXRob2ROYW1lICsgJ2Agbm90IGRlZmluZWQnKTsKICAgICAgfQogICAgfQoKICAgIGNvbnN0IGVtcHR5QXJyYXkgPSBbXTsKCiAgICAvLyBSZWd1bGFyIGV4cHJlc3Npb25zIHVzZWQgZm9yIGJpbmRpbmcKICAgIGNvbnN0IElERU5UICA9ICcoPzonICsgJ1thLXpBLVpfJF1bXFx3LjokXFwtKl0qJyArICcpJzsKICAgIGNvbnN0IE5VTUJFUiA9ICcoPzonICsgJ1stK10/WzAtOV0qXFwuP1swLTldKyg/OltlRV1bLStdP1swLTldKyk/JyArICcpJzsKICAgIGNvbnN0IFNRVU9URV9TVFJJTkcgPSAnKD86JyArICdcJyg/OlteXCdcXFxcXXxcXFxcLikqXCcnICsgJyknOwogICAgY29uc3QgRFFVT1RFX1NUUklORyA9ICcoPzonICsgJyIoPzpbXiJcXFxcXXxcXFxcLikqIicgKyAnKSc7CiAgICBjb25zdCBTVFJJTkcgPSAnKD86JyArIFNRVU9URV9TVFJJTkcgKyAnfCcgKyBEUVVPVEVfU1RSSU5HICsgJyknOwogICAgY29uc3QgQVJHVU1FTlQgPSAnKD86KCcgKyBJREVOVCArICd8JyArIE5VTUJFUiArICd8JyArICBTVFJJTkcgKyAnKVxccyonICsgJyknOwogICAgY29uc3QgQVJHVU1FTlRTID0gJyg/OicgKyBBUkdVTUVOVCArICcoPzosXFxzKicgKyBBUkdVTUVOVCArICcpKicgKyAnKSc7CiAgICBjb25zdCBBUkdVTUVOVF9MSVNUID0gJyg/OicgKyAnXFwoXFxzKicgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgJyg/OicgKyBBUkdVTUVOVFMgKyAnPycgKyAnKScgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICdcXClcXHMqJyArICcpJzsKICAgIGNvbnN0IEJJTkRJTkcgPSAnKCcgKyBJREVOVCArICdcXHMqJyArIEFSR1VNRU5UX0xJU1QgKyAnPycgKyAnKSc7IC8vIEdyb3VwIDMKICAgIGNvbnN0IE9QRU5fQlJBQ0tFVCA9ICcoXFxbXFxbfHt7KScgKyAnXFxzKic7CiAgICBjb25zdCBDTE9TRV9CUkFDS0VUID0gJyg/Ol1dfH19KSc7CiAgICBjb25zdCBORUdBVEUgPSAnKD86KCEpXFxzKik/JzsgLy8gR3JvdXAgMgogICAgY29uc3QgRVhQUkVTU0lPTiA9IE9QRU5fQlJBQ0tFVCArIE5FR0FURSArIEJJTkRJTkcgKyBDTE9TRV9CUkFDS0VUOwogICAgY29uc3QgYmluZGluZ1JlZ2V4ID0gbmV3IFJlZ0V4cChFWFBSRVNTSU9OLCAiZyIpOwoKICAgIC8qKgogICAgICogQ3JlYXRlIGEgc3RyaW5nIGZyb20gYmluZGluZyBwYXJ0cyBvZiBhbGwgdGhlIGxpdGVyYWwgcGFydHMKICAgICAqCiAgICAgKiBAcGFyYW0geyFBcnJheTxCaW5kaW5nUGFydD59IHBhcnRzIEFsbCBwYXJ0cyB0byBzdHJpbmdpZnkKICAgICAqIEByZXR1cm4ge3N0cmluZ30gU3RyaW5nIG1hZGUgZnJvbSB0aGUgbGl0ZXJhbCBwYXJ0cwogICAgICovCiAgICBmdW5jdGlvbiBsaXRlcmFsRnJvbVBhcnRzKHBhcnRzKSB7CiAgICAgIGxldCBzID0gJyc7CiAgICAgIGZvciAobGV0IGk9MDsgaTxwYXJ0cy5sZW5ndGg7IGkrKykgewogICAgICAgIGxldCBsaXRlcmFsID0gcGFydHNbaV0ubGl0ZXJhbDsKICAgICAgICBzICs9IGxpdGVyYWwgfHwgJyc7CiAgICAgIH0KICAgICAgcmV0dXJuIHM7CiAgICB9CgogICAgLyoqCiAgICAgKiBQYXJzZXMgYW4gZXhwcmVzc2lvbiBzdHJpbmcgZm9yIGEgbWV0aG9kIHNpZ25hdHVyZSwgYW5kIHJldHVybnMgYSBtZXRhZGF0YQogICAgICogZGVzY3JpYmluZyB0aGUgbWV0aG9kIGluIHRlcm1zIG9mIGBtZXRob2ROYW1lYCwgYHN0YXRpY2AgKHdoZXRoZXIgYWxsIHRoZQogICAgICogYXJndW1lbnRzIGFyZSBsaXRlcmFscyksIGFuZCBhbiBhcnJheSBvZiBgYXJnc2AKICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXhwcmVzc2lvbiBUaGUgZXhwcmVzc2lvbiB0byBwYXJzZQogICAgICogQHJldHVybiB7P01ldGhvZFNpZ25hdHVyZX0gVGhlIG1ldGhvZCBtZXRhZGF0YSBvYmplY3QgaWYgYSBtZXRob2QgZXhwcmVzc2lvbiB3YXMKICAgICAqICAgZm91bmQsIG90aGVyd2lzZSBgdW5kZWZpbmVkYAogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2VNZXRob2QoZXhwcmVzc2lvbikgewogICAgICAvLyB0cmllcyB0byBtYXRjaCB2YWxpZCBqYXZhc2NyaXB0IHByb3BlcnR5IG5hbWVzCiAgICAgIGxldCBtID0gZXhwcmVzc2lvbi5tYXRjaCgvKFteXHNdKz8pXCgoW1xzXFNdKilcKS8pOwogICAgICBpZiAobSkgewogICAgICAgIGxldCBtZXRob2ROYW1lID0gbVsxXTsKICAgICAgICBsZXQgc2lnID0geyBtZXRob2ROYW1lLCBzdGF0aWM6IHRydWUsIGFyZ3M6IGVtcHR5QXJyYXkgfTsKICAgICAgICBpZiAobVsyXS50cmltKCkpIHsKICAgICAgICAgIC8vIHJlcGxhY2UgZXNjYXBlZCBjb21tYXMgd2l0aCBjb21tYSBlbnRpdHksIHNwbGl0IG9uIHVuLWVzY2FwZWQgY29tbWFzCiAgICAgICAgICBsZXQgYXJncyA9IG1bMl0ucmVwbGFjZSgvXFwsL2csICcmY29tbWE7Jykuc3BsaXQoJywnKTsKICAgICAgICAgIHJldHVybiBwYXJzZUFyZ3MoYXJncywgc2lnKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIHNpZzsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgLyoqCiAgICAgKiBQYXJzZXMgYW4gYXJyYXkgb2YgYXJndW1lbnRzIGFuZCBzZXRzIHRoZSBgYXJnc2AgcHJvcGVydHkgb2YgdGhlIHN1cHBsaWVkCiAgICAgKiBzaWduYXR1cmUgbWV0YWRhdGEgb2JqZWN0LiBTZXRzIHRoZSBgc3RhdGljYCBwcm9wZXJ0eSB0byBmYWxzZSBpZiBhbnkKICAgICAqIGFyZ3VtZW50IGlzIGEgbm9uLWxpdGVyYWwuCiAgICAgKgogICAgICogQHBhcmFtIHshQXJyYXk8c3RyaW5nPn0gYXJnTGlzdCBBcnJheSBvZiBhcmd1bWVudCBuYW1lcwogICAgICogQHBhcmFtIHshTWV0aG9kU2lnbmF0dXJlfSBzaWcgTWV0aG9kIHNpZ25hdHVyZSBtZXRhZGF0YSBvYmplY3QKICAgICAqIEByZXR1cm4geyFNZXRob2RTaWduYXR1cmV9IFRoZSB1cGRhdGVkIHNpZ25hdHVyZSBtZXRhZGF0YSBvYmplY3QKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBhcnNlQXJncyhhcmdMaXN0LCBzaWcpIHsKICAgICAgc2lnLmFyZ3MgPSBhcmdMaXN0Lm1hcChmdW5jdGlvbihyYXdBcmcpIHsKICAgICAgICBsZXQgYXJnID0gcGFyc2VBcmcocmF3QXJnKTsKICAgICAgICBpZiAoIWFyZy5saXRlcmFsKSB7CiAgICAgICAgICBzaWcuc3RhdGljID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIHJldHVybiBhcmc7CiAgICAgIH0sIHRoaXMpOwogICAgICByZXR1cm4gc2lnOwogICAgfQoKICAgIC8qKgogICAgICogUGFyc2VzIGFuIGluZGl2aWR1YWwgYXJndW1lbnQsIGFuZCByZXR1cm5zIGFuIGFyZ3VtZW50IG1ldGFkYXRhIG9iamVjdAogICAgICogd2l0aCB0aGUgZm9sbG93aW5nIGZpZWxkczoKICAgICAqCiAgICAgKiAgIHsKICAgICAqICAgICB2YWx1ZTogJ3Byb3AnLCAgICAgICAgLy8gcHJvcGVydHkvcGF0aCBvciBsaXRlcmFsIHZhbHVlCiAgICAgKiAgICAgbGl0ZXJhbDogZmFsc2UsICAgICAgIC8vIHdoZXRoZXIgYXJndW1lbnQgaXMgYSBsaXRlcmFsCiAgICAgKiAgICAgc3RydWN0dXJlZDogZmFsc2UsICAgIC8vIHdoZXRoZXIgdGhlIHByb3BlcnR5IGlzIGEgcGF0aAogICAgICogICAgIHJvb3RQcm9wZXJ0eTogJ3Byb3AnLCAvLyB0aGUgcm9vdCBwcm9wZXJ0eSBvZiB0aGUgcGF0aAogICAgICogICAgIHdpbGRjYXJkOiBmYWxzZSAgICAgICAvLyB3aGV0aGVyIHRoZSBhcmd1bWVudCB3YXMgYSB3aWxkY2FyZCAnLionIHBhdGgKICAgICAqICAgfQogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSByYXdBcmcgVGhlIHN0cmluZyB2YWx1ZSBvZiB0aGUgYXJndW1lbnQKICAgICAqIEByZXR1cm4geyFNZXRob2RBcmd9IEFyZ3VtZW50IG1ldGFkYXRhIG9iamVjdAogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2VBcmcocmF3QXJnKSB7CiAgICAgIC8vIGNsZWFuIHVwIHdoaXRlc3BhY2UKICAgICAgbGV0IGFyZyA9IHJhd0FyZy50cmltKCkKICAgICAgICAvLyByZXBsYWNlIGNvbW1hIGVudGl0eSB3aXRoIGNvbW1hCiAgICAgICAgLnJlcGxhY2UoLyZjb21tYTsvZywgJywnKQogICAgICAgIC8vIHJlcGFpciBleHRyYSBlc2NhcGUgc2VxdWVuY2VzOyBub3RlIG9ubHkgY29tbWFzIHN0cmljdGx5IG5lZWQKICAgICAgICAvLyBlc2NhcGluZywgYnV0IHdlIGFsbG93IGFueSBvdGhlciBjaGFyIHRvIGJlIGVzY2FwZWQgc2luY2UgaXRzCiAgICAgICAgLy8gbGlrZWx5IHVzZXJzIHdpbGwgZG8gdGhpcwogICAgICAgIC5yZXBsYWNlKC9cXCguKS9nLCAnXCQxJykKICAgICAgICA7CiAgICAgIC8vIGJhc2ljIGFyZ3VtZW50IGRlc2NyaXB0b3IKICAgICAgbGV0IGEgPSB7CiAgICAgICAgbmFtZTogYXJnLAogICAgICAgIHZhbHVlOiAnJywKICAgICAgICBsaXRlcmFsOiBmYWxzZQogICAgICB9OwogICAgICAvLyBkZXRlY3QgbGl0ZXJhbCB2YWx1ZSAobXVzdCBiZSBTdHJpbmcgb3IgTnVtYmVyKQogICAgICBsZXQgZmMgPSBhcmdbMF07CiAgICAgIGlmIChmYyA9PT0gJy0nKSB7CiAgICAgICAgZmMgPSBhcmdbMV07CiAgICAgIH0KICAgICAgaWYgKGZjID49ICcwJyAmJiBmYyA8PSAnOScpIHsKICAgICAgICBmYyA9ICcjJzsKICAgICAgfQogICAgICBzd2l0Y2goZmMpIHsKICAgICAgICBjYXNlICInIjoKICAgICAgICBjYXNlICciJzoKICAgICAgICAgIGEudmFsdWUgPSBhcmcuc2xpY2UoMSwgLTEpOwogICAgICAgICAgYS5saXRlcmFsID0gdHJ1ZTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIGNhc2UgJyMnOgogICAgICAgICAgYS52YWx1ZSA9IE51bWJlcihhcmcpOwogICAgICAgICAgYS5saXRlcmFsID0gdHJ1ZTsKICAgICAgICAgIGJyZWFrOwogICAgICB9CiAgICAgIC8vIGlmIG5vdCBsaXRlcmFsLCBsb29rIGZvciBzdHJ1Y3R1cmVkIHBhdGgKICAgICAgaWYgKCFhLmxpdGVyYWwpIHsKICAgICAgICBhLnJvb3RQcm9wZXJ0eSA9IHJvb3QoYXJnKTsKICAgICAgICAvLyBkZXRlY3Qgc3RydWN0dXJlZCBwYXRoIChoYXMgZG90cykKICAgICAgICBhLnN0cnVjdHVyZWQgPSBpc1BhdGgoYXJnKTsKICAgICAgICBpZiAoYS5zdHJ1Y3R1cmVkKSB7CiAgICAgICAgICBhLndpbGRjYXJkID0gKGFyZy5zbGljZSgtMikgPT0gJy4qJyk7CiAgICAgICAgICBpZiAoYS53aWxkY2FyZCkgewogICAgICAgICAgICBhLm5hbWUgPSBhcmcuc2xpY2UoMCwgLTIpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gYTsKICAgIH0KCiAgICBmdW5jdGlvbiBnZXRBcmdWYWx1ZShkYXRhLCBwcm9wcywgcGF0aCkgewogICAgICBsZXQgdmFsdWUgPSBnZXQoZGF0YSwgcGF0aCk7CiAgICAgIC8vIHdoZW4gZGF0YSBpcyBub3Qgc3RvcmVkIGUuZy4gYHNwbGljZXNgLCBnZXQgdGhlIHZhbHVlIGZyb20gY2hhbmdlZFByb3BzCiAgICAgIC8vIFRPRE8oa3NjaGFhZik6IE5vdGUsIHRoaXMgY2FuIGNhdXNlIGEgcmFyZSBpc3N1ZSB3aGVyZSB0aGUgd2lsZGNhcmQKICAgICAgLy8gaW5mby52YWx1ZSBjb3VsZCBwdWxsIGEgc3RhbGUgdmFsdWUgb3V0IG9mIGNoYW5nZWRQcm9wcyBkdXJpbmcgYSByZWVudHJhbnQKICAgICAgLy8gY2hhbmdlIHRoYXQgc2V0cyB0aGUgdmFsdWUgYmFjayB0byB1bmRlZmluZWQuCiAgICAgIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyL3BvbHltZXIvaXNzdWVzLzU0NzkKICAgICAgaWYgKHZhbHVlID09PSB1bmRlZmluZWQpIHsKICAgICAgICB2YWx1ZSA9IHByb3BzW3BhdGhdOwogICAgICB9CiAgICAgIHJldHVybiB2YWx1ZTsKICAgIH0KCiAgICAvLyBkYXRhIGFwaQoKICAgIC8qKgogICAgICogU2VuZHMgYXJyYXkgc3BsaWNlIG5vdGlmaWNhdGlvbnMgKGAuc3BsaWNlc2AgYW5kIGAubGVuZ3RoYCkKICAgICAqCiAgICAgKiBOb3RlOiB0aGlzIGltcGxlbWVudGF0aW9uIG9ubHkgYWNjZXB0cyBub3JtYWxpemVkIHBhdGhzCiAgICAgKgogICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgSW5zdGFuY2UgdG8gc2VuZCBub3RpZmljYXRpb25zIHRvCiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdGhlIG11dGF0aW9ucyBvY2N1cnJlZCBvbgogICAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggVGhlIHBhdGggdG8gdGhlIGFycmF5IHRoYXQgd2FzIG11dGF0ZWQKICAgICAqIEBwYXJhbSB7QXJyYXl9IHNwbGljZXMgQXJyYXkgb2Ygc3BsaWNlIHJlY29yZHMKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBub3RpZnlTcGxpY2VzKGluc3QsIGFycmF5LCBwYXRoLCBzcGxpY2VzKSB7CiAgICAgIGNvbnN0IHNwbGljZXNEYXRhID0geyBpbmRleFNwbGljZXM6IHNwbGljZXMgfTsKICAgICAgLy8gTGVnYWN5IGJlaGF2aW9yIHN0b3JlZCBzcGxpY2VzIGluIGBfX2RhdGFfX2Agc28gaXQgd2FzICpub3QqIGVwaGVtZXJhbC4KICAgICAgLy8gVG8gbWF0Y2ggdGhpcyBiZWhhdmlvciwgd2Ugc3RvcmUgc3BsaWNlcyBkaXJlY3RseSBvbiB0aGUgYXJyYXkuCiAgICAgIGlmIChsZWdhY3lVbmRlZmluZWQgJiYgIWluc3QuX292ZXJyaWRlTGVnYWN5VW5kZWZpbmVkKSB7CiAgICAgICAgYXJyYXkuc3BsaWNlcyA9IHNwbGljZXNEYXRhOwogICAgICB9CiAgICAgIGluc3Qubm90aWZ5UGF0aChwYXRoICsgJy5zcGxpY2VzJywgc3BsaWNlc0RhdGEpOwogICAgICBpbnN0Lm5vdGlmeVBhdGgocGF0aCArICcubGVuZ3RoJywgYXJyYXkubGVuZ3RoKTsKICAgICAgLy8gQ2xlYXIgc3BsaWNlIGRhdGEgb25seSB3aGVuIGl0J3Mgc3RvcmVkIG9uIHRoZSBhcnJheS4KICAgICAgaWYgKGxlZ2FjeVVuZGVmaW5lZCAmJiAhaW5zdC5fb3ZlcnJpZGVMZWdhY3lVbmRlZmluZWQpIHsKICAgICAgICBzcGxpY2VzRGF0YS5pbmRleFNwbGljZXMgPSBbXTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIHNwbGljZSByZWNvcmQgYW5kIHNlbmRzIGFuIGFycmF5IHNwbGljZSBub3RpZmljYXRpb24gZm9yCiAgICAgKiB0aGUgZGVzY3JpYmVkIG11dGF0aW9uCiAgICAgKgogICAgICogTm90ZTogdGhpcyBpbXBsZW1lbnRhdGlvbiBvbmx5IGFjY2VwdHMgbm9ybWFsaXplZCBwYXRocwogICAgICoKICAgICAqIEBwYXJhbSB7IVBvbHltZXJfUHJvcGVydHlFZmZlY3RzfSBpbnN0IEluc3RhbmNlIHRvIHNlbmQgbm90aWZpY2F0aW9ucyB0bwogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRoZSBtdXRhdGlvbnMgb2NjdXJyZWQgb24KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFRoZSBwYXRoIHRvIHRoZSBhcnJheSB0aGF0IHdhcyBtdXRhdGVkCiAgICAgKiBAcGFyYW0ge251bWJlcn0gaW5kZXggSW5kZXggYXQgd2hpY2ggdGhlIGFycmF5IG11dGF0aW9uIG9jY3VycmVkCiAgICAgKiBAcGFyYW0ge251bWJlcn0gYWRkZWRDb3VudCBOdW1iZXIgb2YgYWRkZWQgaXRlbXMKICAgICAqIEBwYXJhbSB7QXJyYXl9IHJlbW92ZWQgQXJyYXkgb2YgcmVtb3ZlZCBpdGVtcwogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIG5vdGlmeVNwbGljZShpbnN0LCBhcnJheSwgcGF0aCwgaW5kZXgsIGFkZGVkQ291bnQsIHJlbW92ZWQpIHsKICAgICAgbm90aWZ5U3BsaWNlcyhpbnN0LCBhcnJheSwgcGF0aCwgW3sKICAgICAgICBpbmRleDogaW5kZXgsCiAgICAgICAgYWRkZWRDb3VudDogYWRkZWRDb3VudCwKICAgICAgICByZW1vdmVkOiByZW1vdmVkLAogICAgICAgIG9iamVjdDogYXJyYXksCiAgICAgICAgdHlwZTogJ3NwbGljZScKICAgICAgfV0pOwogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyBhbiB1cHBlci1jYXNlZCB2ZXJzaW9uIG9mIHRoZSBzdHJpbmcuCiAgICAgKgogICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgU3RyaW5nIHRvIHVwcGVyY2FzZQogICAgICogQHJldHVybiB7c3RyaW5nfSBVcHBlcmNhc2VkIHN0cmluZwogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gdXBwZXIobmFtZSkgewogICAgICByZXR1cm4gbmFtZVswXS50b1VwcGVyQ2FzZSgpICsgbmFtZS5zdWJzdHJpbmcoMSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBFbGVtZW50IGNsYXNzIG1peGluIHRoYXQgcHJvdmlkZXMgbWV0YS1wcm9ncmFtbWluZyBmb3IgUG9seW1lcidzIHRlbXBsYXRlCiAgICAgKiBiaW5kaW5nIGFuZCBkYXRhIG9ic2VydmF0aW9uIChjb2xsZWN0aXZlbHksICJwcm9wZXJ0eSBlZmZlY3RzIikgc3lzdGVtLgogICAgICoKICAgICAqIFRoaXMgbWl4aW4gdXNlcyBwcm92aWRlcyB0aGUgZm9sbG93aW5nIGtleSBzdGF0aWMgbWV0aG9kcyBmb3IgYWRkaW5nCiAgICAgKiBwcm9wZXJ0eSBlZmZlY3RzIHRvIGFuIGVsZW1lbnQgY2xhc3M6CiAgICAgKiAtIGBhZGRQcm9wZXJ0eUVmZmVjdGAKICAgICAqIC0gYGNyZWF0ZVByb3BlcnR5T2JzZXJ2ZXJgCiAgICAgKiAtIGBjcmVhdGVNZXRob2RPYnNlcnZlcmAKICAgICAqIC0gYGNyZWF0ZU5vdGlmeWluZ1Byb3BlcnR5YAogICAgICogLSBgY3JlYXRlUmVhZE9ubHlQcm9wZXJ0eWAKICAgICAqIC0gYGNyZWF0ZVJlZmxlY3RlZFByb3BlcnR5YAogICAgICogLSBgY3JlYXRlQ29tcHV0ZWRQcm9wZXJ0eWAKICAgICAqIC0gYGJpbmRUZW1wbGF0ZWAKICAgICAqCiAgICAgKiBFYWNoIG1ldGhvZCBjcmVhdGVzIG9uZSBvciBtb3JlIHByb3BlcnR5IGFjY2Vzc29ycywgYWxvbmcgd2l0aCBtZXRhZGF0YQogICAgICogdXNlZCBieSB0aGlzIG1peGluJ3MgaW1wbGVtZW50YXRpb24gb2YgYF9wcm9wZXJ0aWVzQ2hhbmdlZGAgdG8gcGVyZm9ybQogICAgICogdGhlIHByb3BlcnR5IGVmZmVjdHMuCiAgICAgKgogICAgICogVW5kZXJzY29yZWQgdmVyc2lvbnMgb2YgdGhlIGFib3ZlIG1ldGhvZHMgYWxzbyBleGlzdCBvbiB0aGUgZWxlbWVudAogICAgICogcHJvdG90eXBlIGZvciBhZGRpbmcgcHJvcGVydHkgZWZmZWN0cyBvbiBpbnN0YW5jZXMgYXQgcnVudGltZS4KICAgICAqCiAgICAgKiBOb3RlIHRoYXQgdGhpcyBtaXhpbiBvdmVycmlkZXMgc2V2ZXJhbCBgUHJvcGVydHlBY2Nlc3NvcnNgIG1ldGhvZHMsIGluCiAgICAgKiBtYW55IGNhc2VzIHRvIG1haW50YWluIGd1YXJhbnRlZXMgcHJvdmlkZWQgYnkgdGhlIFBvbHltZXIgMS54IGZlYXR1cmVzOwogICAgICogbm90YWJseSBpdCBjaGFuZ2VzIHByb3BlcnR5IGFjY2Vzc29ycyB0byBiZSBzeW5jaHJvbm91cyBieSBkZWZhdWx0CiAgICAgKiB3aGVyZWFzIHRoZSBkZWZhdWx0IHdoZW4gdXNpbmcgYFByb3BlcnR5QWNjZXNzb3JzYCBzdGFuZGFsb25lIGlzIHRvIGJlCiAgICAgKiBhc3luYyBieSBkZWZhdWx0LgogICAgICoKICAgICAqIEBtaXhpbkZ1bmN0aW9uCiAgICAgKiBAcG9seW1lcgogICAgICogQGFwcGxpZXNNaXhpbiBUZW1wbGF0ZVN0YW1wCiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnR5QWNjZXNzb3JzCiAgICAgKiBAc3VtbWFyeSBFbGVtZW50IGNsYXNzIG1peGluIHRoYXQgcHJvdmlkZXMgbWV0YS1wcm9ncmFtbWluZyBmb3IgUG9seW1lcidzCiAgICAgKiB0ZW1wbGF0ZSBiaW5kaW5nIGFuZCBkYXRhIG9ic2VydmF0aW9uIHN5c3RlbS4KICAgICAqLwogICAgY29uc3QgUHJvcGVydHlFZmZlY3RzID0gZGVkdXBpbmdNaXhpbihzdXBlckNsYXNzID0+IHsKCiAgICAgIC8qKgogICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfUHJvcGVydHlBY2Nlc3NvcnN9CiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1RlbXBsYXRlU3RhbXB9CiAgICAgICAqIEB1bnJlc3RyaWN0ZWQKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIGNvbnN0IHByb3BlcnR5RWZmZWN0c0Jhc2UgPSBUZW1wbGF0ZVN0YW1wKFByb3BlcnR5QWNjZXNzb3JzKHN1cGVyQ2xhc3MpKTsKCiAgICAgIC8qKgogICAgICAgKiBAcG9seW1lcgogICAgICAgKiBAbWl4aW5DbGFzcwogICAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9CiAgICAgICAqIEBleHRlbmRzIHtwcm9wZXJ0eUVmZmVjdHNCYXNlfQogICAgICAgKiBAdW5yZXN0cmljdGVkCiAgICAgICAqLwogICAgICBjbGFzcyBQcm9wZXJ0eUVmZmVjdHMgZXh0ZW5kcyBwcm9wZXJ0eUVmZmVjdHNCYXNlIHsKCiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgLyoqIEB0eXBlIHtib29sZWFufSAqLwogICAgICAgICAgLy8gVXNlZCB0byBpZGVudGlmeSB1c2VycyBvZiB0aGlzIG1peGluLCBhbGEgaW5zdGFuY2VvZgogICAgICAgICAgdGhpcy5fX2lzUHJvcGVydHlFZmZlY3RzQ2xpZW50ID0gdHJ1ZTsKICAgICAgICAgIC8qKiBAdHlwZSB7Ym9vbGVhbn0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhQ2xpZW50c1JlYWR5OwogICAgICAgICAgLyoqIEB0eXBlIHtBcnJheX0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhUGVuZGluZ0NsaWVudHM7CiAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhVG9Ob3RpZnk7CiAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhTGlua2VkUGF0aHM7CiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgICB0aGlzLl9fZGF0YUhhc1BhdGhzOwogICAgICAgICAgLyoqIEB0eXBlIHtPYmplY3R9ICovCiAgICAgICAgICB0aGlzLl9fZGF0YUNvbXBvdW5kU3RvcmFnZTsKICAgICAgICAgIC8qKiBAdHlwZSB7UG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9ICovCiAgICAgICAgICB0aGlzLl9fZGF0YUhvc3Q7CiAgICAgICAgICAvKiogQHR5cGUgeyFPYmplY3R9ICovCiAgICAgICAgICB0aGlzLl9fZGF0YVRlbXA7CiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgICB0aGlzLl9fZGF0YUNsaWVudHNJbml0aWFsaXplZDsKICAgICAgICAgIC8qKiBAdHlwZSB7IU9iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19kYXRhOwogICAgICAgICAgLyoqIEB0eXBlIHshT2JqZWN0fG51bGx9ICovCiAgICAgICAgICB0aGlzLl9fZGF0YVBlbmRpbmc7CiAgICAgICAgICAvKiogQHR5cGUgeyFPYmplY3R9ICovCiAgICAgICAgICB0aGlzLl9fZGF0YU9sZDsKICAgICAgICAgIC8qKiBAdHlwZSB7T2JqZWN0fSAqLwogICAgICAgICAgdGhpcy5fX2NvbXB1dGVFZmZlY3RzOwogICAgICAgICAgLyoqIEB0eXBlIHtPYmplY3R9ICovCiAgICAgICAgICB0aGlzLl9fY29tcHV0ZUluZm87CiAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19yZWZsZWN0RWZmZWN0czsKICAgICAgICAgIC8qKiBAdHlwZSB7T2JqZWN0fSAqLwogICAgICAgICAgdGhpcy5fX25vdGlmeUVmZmVjdHM7CiAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19wcm9wYWdhdGVFZmZlY3RzOwogICAgICAgICAgLyoqIEB0eXBlIHtPYmplY3R9ICovCiAgICAgICAgICB0aGlzLl9fb2JzZXJ2ZUVmZmVjdHM7CiAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gKi8KICAgICAgICAgIHRoaXMuX19yZWFkT25seTsKICAgICAgICAgIC8qKiBAdHlwZSB7IVRlbXBsYXRlSW5mb30gKi8KICAgICAgICAgIHRoaXMuX190ZW1wbGF0ZUluZm87CiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgICB0aGlzLl9vdmVycmlkZUxlZ2FjeVVuZGVmaW5lZDsKICAgICAgICB9CgogICAgICAgIGdldCBQUk9QRVJUWV9FRkZFQ1RfVFlQRVMoKSB7CiAgICAgICAgICByZXR1cm4gVFlQRVM7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIF9pbml0aWFsaXplUHJvcGVydGllcygpIHsKICAgICAgICAgIHN1cGVyLl9pbml0aWFsaXplUHJvcGVydGllcygpOwogICAgICAgICAgdGhpcy5fcmVnaXN0ZXJIb3N0KCk7CiAgICAgICAgICB0aGlzLl9fZGF0YUNsaWVudHNSZWFkeSA9IGZhbHNlOwogICAgICAgICAgdGhpcy5fX2RhdGFQZW5kaW5nQ2xpZW50cyA9IG51bGw7CiAgICAgICAgICB0aGlzLl9fZGF0YVRvTm90aWZ5ID0gbnVsbDsKICAgICAgICAgIHRoaXMuX19kYXRhTGlua2VkUGF0aHMgPSBudWxsOwogICAgICAgICAgdGhpcy5fX2RhdGFIYXNQYXRocyA9IGZhbHNlOwogICAgICAgICAgLy8gTWF5IGJlIHNldCBvbiBpbnN0YW5jZSBwcmlvciB0byB1cGdyYWRlCiAgICAgICAgICB0aGlzLl9fZGF0YUNvbXBvdW5kU3RvcmFnZSA9IHRoaXMuX19kYXRhQ29tcG91bmRTdG9yYWdlIHx8IG51bGw7CiAgICAgICAgICB0aGlzLl9fZGF0YUhvc3QgPSB0aGlzLl9fZGF0YUhvc3QgfHwgbnVsbDsKICAgICAgICAgIHRoaXMuX19kYXRhVGVtcCA9IHt9OwogICAgICAgICAgdGhpcy5fX2RhdGFDbGllbnRzSW5pdGlhbGl6ZWQgPSBmYWxzZTsKICAgICAgICB9CgogICAgICAgIF9yZWdpc3Rlckhvc3QoKSB7CiAgICAgICAgICBpZiAoaG9zdFN0YWNrLmxlbmd0aCkgewogICAgICAgICAgICBsZXQgaG9zdCA9IGhvc3RTdGFja1tob3N0U3RhY2subGVuZ3RoLTFdOwogICAgICAgICAgICBob3N0Ll9lbnF1ZXVlQ2xpZW50KHRoaXMpOwogICAgICAgICAgICAvLyBUaGlzIGVuc3VyZXMgZXZlbiBub24tYm91bmQgZWxlbWVudHMgaGF2ZSBhIGhvc3Qgc2V0LCBhcwogICAgICAgICAgICAvLyBsb25nIGFzIHRoZXkgdXBncmFkZSBzeW5jaHJvbm91c2x5CiAgICAgICAgICAgIHRoaXMuX19kYXRhSG9zdCA9IGhvc3Q7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgYFByb3BlcnR5QWNjZXNzb3JzYCBpbXBsZW1lbnRhdGlvbiB0byBwcm92aWRlIGEKICAgICAgICAgKiBtb3JlIGVmZmljaWVudCBpbXBsZW1lbnRhdGlvbiBvZiBpbml0aWFsaXppbmcgcHJvcGVydGllcyBmcm9tCiAgICAgICAgICogdGhlIHByb3RvdHlwZSBvbiB0aGUgaW5zdGFuY2UuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gcHJvcHMgUHJvcGVydGllcyB0byBpbml0aWFsaXplIG9uIHRoZSBwcm90b3R5cGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIF9pbml0aWFsaXplUHJvdG9Qcm9wZXJ0aWVzKHByb3BzKSB7CiAgICAgICAgICB0aGlzLl9fZGF0YSA9IE9iamVjdC5jcmVhdGUocHJvcHMpOwogICAgICAgICAgdGhpcy5fX2RhdGFQZW5kaW5nID0gT2JqZWN0LmNyZWF0ZShwcm9wcyk7CiAgICAgICAgICB0aGlzLl9fZGF0YU9sZCA9IHt9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIGBQcm9wZXJ0eUFjY2Vzc29yc2AgaW1wbGVtZW50YXRpb24gdG8gYXZvaWQgc2V0dGluZwogICAgICAgICAqIGBfc2V0UHJvcGVydHlgJ3MgYHNob3VsZE5vdGlmeTogdHJ1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gcHJvcHMgUHJvcGVydGllcyB0byBpbml0aWFsaXplIG9uIHRoZSBpbnN0YW5jZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgX2luaXRpYWxpemVJbnN0YW5jZVByb3BlcnRpZXMocHJvcHMpIHsKICAgICAgICAgIGxldCByZWFkT25seSA9IHRoaXNbVFlQRVMuUkVBRF9PTkxZXTsKICAgICAgICAgIGZvciAobGV0IHByb3AgaW4gcHJvcHMpIHsKICAgICAgICAgICAgaWYgKCFyZWFkT25seSB8fCAhcmVhZE9ubHlbcHJvcF0pIHsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YVBlbmRpbmcgPSB0aGlzLl9fZGF0YVBlbmRpbmcgfHwge307CiAgICAgICAgICAgICAgdGhpcy5fX2RhdGFPbGQgPSB0aGlzLl9fZGF0YU9sZCB8fCB7fTsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YVtwcm9wXSA9IHRoaXMuX19kYXRhUGVuZGluZ1twcm9wXSA9IHByb3BzW3Byb3BdOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBQcm90b3R5cGUgc2V0dXAgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAgICAgICAvKioKICAgICAgICAgKiBFcXVpdmFsZW50IHRvIHN0YXRpYyBgYWRkUHJvcGVydHlFZmZlY3RgIEFQSSBidXQgY2FuIGJlIGNhbGxlZCBvbgogICAgICAgICAqIGFuIGluc3RhbmNlIHRvIGFkZCBlZmZlY3RzIGF0IHJ1bnRpbWUuICBTZWUgdGhhdCBtZXRob2QgZm9yCiAgICAgICAgICogZnVsbCBBUEkgZG9jcy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSB0aGF0IHNob3VsZCB0cmlnZ2VyIHRoZSBlZmZlY3QKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdHlwZSBFZmZlY3QgdHlwZSwgZnJvbSB0aGlzLlBST1BFUlRZX0VGRkVDVF9UWVBFUwogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gZWZmZWN0IEVmZmVjdCBtZXRhZGF0YSBvYmplY3QKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBfYWRkUHJvcGVydHlFZmZlY3QocHJvcGVydHksIHR5cGUsIGVmZmVjdCkgewogICAgICAgICAgdGhpcy5fY3JlYXRlUHJvcGVydHlBY2Nlc3Nvcihwcm9wZXJ0eSwgdHlwZSA9PSBUWVBFUy5SRUFEX09OTFkpOwogICAgICAgICAgLy8gZWZmZWN0cyBhcmUgYWNjdW11bGF0ZWQgaW50byBhcnJheXMgcGVyIHByb3BlcnR5IGJhc2VkIG9uIHR5cGUKICAgICAgICAgIGxldCBlZmZlY3RzID0gZW5zdXJlT3duRWZmZWN0TWFwKHRoaXMsIHR5cGUsIHRydWUpW3Byb3BlcnR5XTsKICAgICAgICAgIGlmICghZWZmZWN0cykgewogICAgICAgICAgICBlZmZlY3RzID0gdGhpc1t0eXBlXVtwcm9wZXJ0eV0gPSBbXTsKICAgICAgICAgIH0KICAgICAgICAgIGVmZmVjdHMucHVzaChlZmZlY3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyB0aGUgZ2l2ZW4gcHJvcGVydHkgZWZmZWN0LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IFByb3BlcnR5IHRoZSBlZmZlY3Qgd2FzIGFzc29jaWF0ZWQgd2l0aAogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0eXBlIEVmZmVjdCB0eXBlLCBmcm9tIHRoaXMuUFJPUEVSVFlfRUZGRUNUX1RZUEVTCiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSBlZmZlY3QgRWZmZWN0IG1ldGFkYXRhIG9iamVjdCB0byByZW1vdmUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIF9yZW1vdmVQcm9wZXJ0eUVmZmVjdChwcm9wZXJ0eSwgdHlwZSwgZWZmZWN0KSB7CiAgICAgICAgICBsZXQgZWZmZWN0cyA9IGVuc3VyZU93bkVmZmVjdE1hcCh0aGlzLCB0eXBlLCB0cnVlKVtwcm9wZXJ0eV07CiAgICAgICAgICBsZXQgaWR4ID0gZWZmZWN0cy5pbmRleE9mKGVmZmVjdCk7CiAgICAgICAgICBpZiAoaWR4ID49IDApIHsKICAgICAgICAgICAgZWZmZWN0cy5zcGxpY2UoaWR4LCAxKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgY3VycmVudCBwcm90b3R5cGUvaW5zdGFuY2UgaGFzIGEgcHJvcGVydHkgZWZmZWN0CiAgICAgICAgICogb2YgYSBjZXJ0YWluIHR5cGUuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gdHlwZSBFZmZlY3QgdHlwZSwgZnJvbSB0aGlzLlBST1BFUlRZX0VGRkVDVF9UWVBFUwogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgdGhlIHByb3RvdHlwZS9pbnN0YW5jZSBoYXMgYW4gZWZmZWN0IG9mIHRoaXMKICAgICAgICAgKiAgICAgdHlwZQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBfaGFzUHJvcGVydHlFZmZlY3QocHJvcGVydHksIHR5cGUpIHsKICAgICAgICAgIGxldCBlZmZlY3RzID0gdGhpc1t0eXBlXTsKICAgICAgICAgIHJldHVybiBCb29sZWFuKGVmZmVjdHMgJiYgZWZmZWN0c1twcm9wZXJ0eV0pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB3aGV0aGVyIHRoZSBjdXJyZW50IHByb3RvdHlwZS9pbnN0YW5jZSBoYXMgYSAicmVhZCBvbmx5IgogICAgICAgICAqIGFjY2Vzc29yIGZvciB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgdGhlIHByb3RvdHlwZS9pbnN0YW5jZSBoYXMgYW4gZWZmZWN0IG9mIHRoaXMKICAgICAgICAgKiAgICAgdHlwZQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBfaGFzUmVhZE9ubHlFZmZlY3QocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9oYXNQcm9wZXJ0eUVmZmVjdChwcm9wZXJ0eSwgVFlQRVMuUkVBRF9PTkxZKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgY3VycmVudCBwcm90b3R5cGUvaW5zdGFuY2UgaGFzIGEgIm5vdGlmeSIKICAgICAgICAgKiBwcm9wZXJ0eSBlZmZlY3QgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiB0aGUgcHJvdG90eXBlL2luc3RhbmNlIGhhcyBhbiBlZmZlY3Qgb2YgdGhpcwogICAgICAgICAqICAgICB0eXBlCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9oYXNOb3RpZnlFZmZlY3QocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9oYXNQcm9wZXJ0eUVmZmVjdChwcm9wZXJ0eSwgVFlQRVMuTk9USUZZKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgY3VycmVudCBwcm90b3R5cGUvaW5zdGFuY2UgaGFzIGEgInJlZmxlY3QgdG8KICAgICAgICAgKiBhdHRyaWJ1dGUiIHByb3BlcnR5IGVmZmVjdCBmb3IgdGhlIGdpdmVuIHByb3BlcnR5LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IFByb3BlcnR5IG5hbWUKICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHRoZSBwcm90b3R5cGUvaW5zdGFuY2UgaGFzIGFuIGVmZmVjdCBvZiB0aGlzCiAgICAgICAgICogICAgIHR5cGUKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2hhc1JlZmxlY3RFZmZlY3QocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9oYXNQcm9wZXJ0eUVmZmVjdChwcm9wZXJ0eSwgVFlQRVMuUkVGTEVDVCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHdoZXRoZXIgdGhlIGN1cnJlbnQgcHJvdG90eXBlL2luc3RhbmNlIGhhcyBhICJjb21wdXRlZCIKICAgICAgICAgKiBwcm9wZXJ0eSBlZmZlY3QgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiB0aGUgcHJvdG90eXBlL2luc3RhbmNlIGhhcyBhbiBlZmZlY3Qgb2YgdGhpcwogICAgICAgICAqICAgICB0eXBlCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9oYXNDb21wdXRlZEVmZmVjdChwcm9wZXJ0eSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX2hhc1Byb3BlcnR5RWZmZWN0KHByb3BlcnR5LCBUWVBFUy5DT01QVVRFKTsKICAgICAgICB9CgogICAgICAgIC8vIFJ1bnRpbWUgLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIGEgcGVuZGluZyBwcm9wZXJ0eSBvciBwYXRoLiAgSWYgdGhlIHJvb3QgcHJvcGVydHkgb2YgdGhlIHBhdGggaW4KICAgICAgICAgKiBxdWVzdGlvbiBoYWQgbm8gYWNjZXNzb3IsIHRoZSBwYXRoIGlzIHNldCwgb3RoZXJ3aXNlIGl0IGlzIGVucXVldWVkCiAgICAgICAgICogdmlhIGBfc2V0UGVuZGluZ1Byb3BlcnR5YC4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgZnVuY3Rpb24gaXNvbGF0ZXMgcmVsYXRpdmVseSBleHBlbnNpdmUgZnVuY3Rpb25hbGl0eSBuZWNlc3NhcnkKICAgICAgICAgKiBmb3IgdGhlIHB1YmxpYyBBUEkgKGBzZXRgLCBgc2V0UHJvcGVydGllc2AsIGBub3RpZnlQYXRoYCwgYW5kIHByb3BlcnR5CiAgICAgICAgICogY2hhbmdlIGxpc3RlbmVycyB2aWEge3suLi59fSBiaW5kaW5ncyksIHN1Y2ggdGhhdCBpdCBpcyBvbmx5IGRvbmUKICAgICAgICAgKiB3aGVuIHBhdGhzIGVudGVyIHRoZSBzeXN0ZW0sIGFuZCBub3QgYXQgZXZlcnkgcHJvcGFnYXRpb24gc3RlcC4gIEl0CiAgICAgICAgICogYWxzbyBzZXRzIGEgYF9fZGF0YUhhc1BhdGhzYCBmbGFnIG9uIHRoZSBpbnN0YW5jZSB3aGljaCBpcyB1c2VkIHRvCiAgICAgICAgICogZmFzdC1wYXRoIHNsb3dlciBwYXRoLW1hdGNoaW5nIGNvZGUgaW4gdGhlIHByb3BlcnR5IGVmZmVjdHMgaG9zdCBwYXRocy4KICAgICAgICAgKgogICAgICAgICAqIGBwYXRoYCBjYW4gYmUgYSBwYXRoIHN0cmluZyBvciBhcnJheSBvZiBwYXRoIHBhcnRzIGFzIGFjY2VwdGVkIGJ5IHRoZQogICAgICAgICAqIHB1YmxpYyBBUEkuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxudW1iZXJ8c3RyaW5nPn0gcGF0aCBQYXRoIHRvIHNldAogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVmFsdWUgdG8gc2V0CiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gc2hvdWxkTm90aWZ5IFNldCB0byB0cnVlIGlmIHRoaXMgY2hhbmdlIHNob3VsZAogICAgICAgICAqICBjYXVzZSBhIHByb3BlcnR5IG5vdGlmaWNhdGlvbiBldmVudCBkaXNwYXRjaAogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IGlzUGF0aE5vdGlmaWNhdGlvbiBJZiB0aGUgcGF0aCBiZWluZyBzZXQgaXMgYSBwYXRoCiAgICAgICAgICogICBub3RpZmljYXRpb24gb2YgYW4gYWxyZWFkeSBjaGFuZ2VkIHZhbHVlLCBhcyBvcHBvc2VkIHRvIGEgcmVxdWVzdAogICAgICAgICAqICAgdG8gc2V0IGFuZCBub3RpZnkgdGhlIGNoYW5nZS4gIEluIHRoZSBsYXR0ZXIgYGZhbHNlYCBjYXNlLCBhIGRpcnR5CiAgICAgICAgICogICBjaGVjayBpcyBwZXJmb3JtZWQgYW5kIHRoZW4gdGhlIHZhbHVlIGlzIHNldCB0byB0aGUgcGF0aCBiZWZvcmUKICAgICAgICAgKiAgIGVucXVldWluZyB0aGUgcGVuZGluZyBwcm9wZXJ0eSBjaGFuZ2UuCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIHRoZSBwcm9wZXJ0eS9wYXRoIHdhcyBlbnF1ZXVlZCBpbgogICAgICAgICAqICAgdGhlIHBlbmRpbmcgY2hhbmdlcyBiYWcuCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgocGF0aCwgdmFsdWUsIHNob3VsZE5vdGlmeSwgaXNQYXRoTm90aWZpY2F0aW9uKSB7CiAgICAgICAgICBpZiAoaXNQYXRoTm90aWZpY2F0aW9uIHx8CiAgICAgICAgICAgICAgcm9vdChBcnJheS5pc0FycmF5KHBhdGgpID8gcGF0aFswXSA6IHBhdGgpICE9PSBwYXRoKSB7CiAgICAgICAgICAgIC8vIERpcnR5IGNoZWNrIGNoYW5nZXMgYmVpbmcgc2V0IHRvIGEgcGF0aCBhZ2FpbnN0IHRoZSBhY3R1YWwgb2JqZWN0LAogICAgICAgICAgICAvLyBzaW5jZSB0aGlzIGlzIHRoZSBlbnRyeSBwb2ludCBmb3IgcGF0aHMgaW50byB0aGUgc3lzdGVtOyBmcm9tIGhlcmUKICAgICAgICAgICAgLy8gdGhlIG9ubHkgZGlydHkgY2hlY2tzIGFyZSBhZ2FpbnN0IHRoZSBgX19kYXRhVGVtcGAgY2FjaGUgdG8gcHJldmVudAogICAgICAgICAgICAvLyBkdXBsaWNhdGUgd29yayBpbiB0aGUgc2FtZSB0dXJuIG9ubHkuIE5vdGUsIGlmIHRoaXMgd2FzIGEgbm90aWZpY2F0aW9uCiAgICAgICAgICAgIC8vIG9mIGEgY2hhbmdlIGFscmVhZHkgc2V0IHRvIGEgcGF0aCAoaXNQYXRoTm90aWZpY2F0aW9uOiB0cnVlKSwKICAgICAgICAgICAgLy8gd2UgYWx3YXlzIGxldCB0aGUgY2hhbmdlIHRocm91Z2ggYW5kIHNraXAgdGhlIGBzZXRgIHNpbmNlIGl0IHdhcwogICAgICAgICAgICAvLyBhbHJlYWR5IGRpcnR5IGNoZWNrZWQgYXQgdGhlIHBvaW50IG9mIGVudHJ5IGFuZCB0aGUgdW5kZXJseWluZwogICAgICAgICAgICAvLyBvYmplY3QgaGFzIGFscmVhZHkgYmVlbiB1cGRhdGVkCiAgICAgICAgICAgIGlmICghaXNQYXRoTm90aWZpY2F0aW9uKSB7CiAgICAgICAgICAgICAgbGV0IG9sZCA9IGdldCh0aGlzLCBwYXRoKTsKICAgICAgICAgICAgICBwYXRoID0gLyoqIEB0eXBlIHtzdHJpbmd9ICovIChzZXQodGhpcywgcGF0aCwgdmFsdWUpKTsKICAgICAgICAgICAgICAvLyBVc2UgcHJvcGVydHktYWNjZXNzb3IncyBzaW1wbGVyIGRpcnR5IGNoZWNrCiAgICAgICAgICAgICAgaWYgKCFwYXRoIHx8ICFzdXBlci5fc2hvdWxkUHJvcGVydHlDaGFuZ2UocGF0aCwgdmFsdWUsIG9sZCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fX2RhdGFIYXNQYXRocyA9IHRydWU7CiAgICAgICAgICAgIGlmICh0aGlzLl9zZXRQZW5kaW5nUHJvcGVydHkoLyoqQHR5cGV7c3RyaW5nfSovKHBhdGgpLCB2YWx1ZSwgc2hvdWxkTm90aWZ5KSkgewogICAgICAgICAgICAgIGNvbXB1dGVMaW5rZWRQYXRocyh0aGlzLCAvKipAdHlwZXtzdHJpbmd9Ki8gKHBhdGgpLCB2YWx1ZSk7CiAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9fZGF0YUhhc0FjY2Vzc29yICYmIHRoaXMuX19kYXRhSGFzQWNjZXNzb3JbcGF0aF0pIHsKICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fc2V0UGVuZGluZ1Byb3BlcnR5KC8qKkB0eXBle3N0cmluZ30qLyhwYXRoKSwgdmFsdWUsIHNob3VsZE5vdGlmeSk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdGhpc1twYXRoXSA9IHZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBBcHBsaWVzIGEgdmFsdWUgdG8gYSBub24tUG9seW1lciBlbGVtZW50L25vZGUncyBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBpbXBsZW1lbnRhdGlvbiBtYWtlcyBhIGJlc3QtZWZmb3J0IGF0IGJpbmRpbmcgaW50ZXJvcDoKICAgICAgICAgKiBTb21lIG5hdGl2ZSBlbGVtZW50IHByb3BlcnRpZXMgaGF2ZSBzaWRlLWVmZmVjdHMgd2hlbgogICAgICAgICAqIHJlLXNldHRpbmcgdGhlIHNhbWUgdmFsdWUgKGUuZy4gc2V0dGluZyBgPGlucHV0Pi52YWx1ZWAgcmVzZXRzIHRoZQogICAgICAgICAqIGN1cnNvciBwb3NpdGlvbiksIHNvIHdlIGRvIGEgZGlydHktY2hlY2sgYmVmb3JlIHNldHRpbmcgdGhlIHZhbHVlLgogICAgICAgICAqIEhvd2V2ZXIsIGZvciBiZXR0ZXIgaW50ZXJvcCB3aXRoIG5vbi1Qb2x5bWVyIGN1c3RvbSBlbGVtZW50cyB0aGF0CiAgICAgICAgICogYWNjZXB0IG9iamVjdHMsIHdlIGV4cGxpY2l0bHkgcmUtc2V0IG9iamVjdCBjaGFuZ2VzIGNvbWluZyBmcm9tIHRoZQogICAgICAgICAqIFBvbHltZXIgd29ybGQgKHdoaWNoIG1heSBpbmNsdWRlIGRlZXAgb2JqZWN0IGNoYW5nZXMgd2l0aG91dCB0aGUKICAgICAgICAgKiB0b3AgcmVmZXJlbmNlIGNoYW5naW5nKSwgZXJyaW5nIG9uIHRoZSBzaWRlIG9mIHByb3ZpZGluZyBtb3JlCiAgICAgICAgICogaW5mb3JtYXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiBVc2VycyBtYXkgb3ZlcnJpZGUgdGhpcyBtZXRob2QgdG8gcHJvdmlkZSBhbHRlcm5hdGUgYXBwcm9hY2hlcy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7IU5vZGV9IG5vZGUgVGhlIG5vZGUgdG8gc2V0IGEgcHJvcGVydHkgb24KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBUaGUgcHJvcGVydHkgdG8gc2V0CiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0CiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX3NldFVubWFuYWdlZFByb3BlcnR5VG9Ob2RlKG5vZGUsIHByb3AsIHZhbHVlKSB7CiAgICAgICAgICAvLyBJdCBpcyBhIGp1ZGdtZW50IGNhbGwgdGhhdCByZXNldHRpbmcgcHJpbWl0aXZlcyBpcwogICAgICAgICAgLy8gImJhZCIgYW5kIHJlc2V0dGluZ3Mgb2JqZWN0cyBpcyBhbHNvICJnb29kIjsgYWx0ZXJuYXRpdmVseSB3ZSBjb3VsZAogICAgICAgICAgLy8gaW1wbGVtZW50IGEgd2hpdGVsaXN0IG9mIHRhZyAmIHByb3BlcnR5IHZhbHVlcyB0aGF0IHNob3VsZCBuZXZlcgogICAgICAgICAgLy8gYmUgcmVzZXQgKGUuZy4gPGlucHV0Pi52YWx1ZSAmJiA8c2VsZWN0Pi52YWx1ZSkKICAgICAgICAgIGlmICh2YWx1ZSAhPT0gbm9kZVtwcm9wXSB8fCB0eXBlb2YgdmFsdWUgPT0gJ29iamVjdCcpIHsKICAgICAgICAgICAgLy8gTm90ZSwgY2xhc3NOYW1lIG5lZWRzIHN0eWxlIHNjb3Bpbmcgc28gdGhpcyBuZWVkcyB3cmFwcGluZy4KICAgICAgICAgICAgaWYgKHByb3AgPT09ICdjbGFzc05hbWUnKSB7CiAgICAgICAgICAgICAgbm9kZSA9IC8qKiBAdHlwZSB7IU5vZGV9ICovKHdyYXAobm9kZSkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG5vZGVbcHJvcF0gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyB0aGUgYFByb3BlcnRpZXNDaGFuZ2VkYCBpbXBsZW1lbnRhdGlvbiB0byBpbnRyb2R1Y2Ugc3BlY2lhbAogICAgICAgICAqIGRpcnR5IGNoZWNrIGxvZ2ljIGRlcGVuZGluZyBvbiB0aGUgcHJvcGVydHkgJiB2YWx1ZSBiZWluZyBzZXQ6CiAgICAgICAgICoKICAgICAgICAgKiAxLiBBbnkgdmFsdWUgc2V0IHRvIGEgcGF0aCAoZS5nLiAnb2JqLnByb3AnOiA0MiBvciAnb2JqLnByb3AnOiB7Li4ufSkKICAgICAgICAgKiAgICBTdG9yZWQgaW4gYF9fZGF0YVRlbXBgLCBkaXJ0eSBjaGVja2VkIGFnYWluc3QgYF9fZGF0YVRlbXBgCiAgICAgICAgICogMi4gT2JqZWN0IHNldCB0byBzaW1wbGUgcHJvcGVydHkgKGUuZy4gJ3Byb3AnOiB7Li4ufSkKICAgICAgICAgKiAgICBTdG9yZWQgaW4gYF9fZGF0YVRlbXBgIGFuZCBgX19kYXRhYCwgZGlydHkgY2hlY2tlZCBhZ2FpbnN0CiAgICAgICAgICogICAgYF9fZGF0YVRlbXBgIGJ5IGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgYF9zaG91bGRQcm9wZXJ0eUNoYW5nZWAKICAgICAgICAgKiAzLiBQcmltaXRpdmUgdmFsdWUgc2V0IHRvIHNpbXBsZSBwcm9wZXJ0eSAoZS5nLiAncHJvcCc6IDQyKQogICAgICAgICAqICAgIFN0b3JlZCBpbiBgX19kYXRhYCwgZGlydHkgY2hlY2tlZCBhZ2FpbnN0IGBfX2RhdGFgCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZGlydHktY2hlY2sgaXMgaW1wb3J0YW50IHRvIHByZXZlbnQgY3ljbGVzIGR1ZSB0byB0d28td2F5CiAgICAgICAgICogbm90aWZpY2F0aW9uLCBidXQgcGF0aHMgYW5kIG9iamVjdHMgYXJlIG9ubHkgZGlydHkgY2hlY2tlZCBhZ2FpbnN0IGFueQogICAgICAgICAqIHByZXZpb3VzIHZhbHVlIHNldCBkdXJpbmcgdGhpcyB0dXJuIHZpYSBhICJ0ZW1wb3JhcnkgY2FjaGUiIHRoYXQgaXMKICAgICAgICAgKiBjbGVhcmVkIHdoZW4gdGhlIGxhc3QgYF9wcm9wZXJ0aWVzQ2hhbmdlZGAgZXhpdHMuIFRoaXMgaXMgc286CiAgICAgICAgICogYS4gYW55IGNhY2hlZCBhcnJheSBwYXRocyAoZS5nLiAnYXJyYXkuMy5wcm9wJykgbWF5IGJlIGludmFsaWRhdGVkCiAgICAgICAgICogICAgZHVlIHRvIGFycmF5IG11dGF0aW9ucyBsaWtlIHNoaWZ0L3Vuc2hpZnQvc3BsaWNlOyB0aGlzIGlzIGZpbmUKICAgICAgICAgKiAgICBzaW5jZSBwYXRoIGNoYW5nZXMgYXJlIGRpcnR5LWNoZWNrZWQgYXQgdXNlciBlbnRyeSBwb2ludHMgbGlrZSBgc2V0YAogICAgICAgICAqIGIuIGRpcnR5LWNoZWNraW5nIGZvciBvYmplY3RzIG9ubHkgbGFzdHMgb25lIHR1cm4gdG8gYWxsb3cgdGhlIHVzZXIKICAgICAgICAgKiAgICB0byBtdXRhdGUgdGhlIG9iamVjdCBpbi1wbGFjZSBhbmQgcmUtc2V0IGl0IHdpdGggdGhlIHNhbWUgaWRlbnRpdHkKICAgICAgICAgKiAgICBhbmQgaGF2ZSBhbGwgc3ViLXByb3BlcnRpZXMgcmUtcHJvcGFnYXRlZCBpbiBhIHN1YnNlcXVlbnQgdHVybi4KICAgICAgICAgKgogICAgICAgICAqIFRoZSB0ZW1wIGNhY2hlIGlzIG5vdCBuZWNlc3NhcmlseSBzdWZmaWNpZW50IHRvIHByZXZlbnQgaW52YWxpZCBhcnJheQogICAgICAgICAqIHBhdGhzLCBzaW5jZSBhIHNwbGljZSBjYW4gaGFwcGVuIGR1cmluZyB0aGUgc2FtZSB0dXJuICh3aXRoIHBhdGhvbG9naWNhbAogICAgICAgICAqIHVzZXIgY29kZSk7IHdlIGNvdWxkIGludHJvZHVjZSBhICJmaXh1cCIgZm9yIHRlbXBvcmFyaWx5IGNhY2hlZCBhcnJheQogICAgICAgICAqIHBhdGhzIGlmIG5lZWRlZDogaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXIvcG9seW1lci9pc3N1ZXMvNDIyNwogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IE5hbWUgb2YgdGhlIHByb3BlcnR5CiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSB0byBzZXQKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW49fSBzaG91bGROb3RpZnkgVHJ1ZSBpZiBwcm9wZXJ0eSBzaG91bGQgZmlyZSBub3RpZmljYXRpb24KICAgICAgICAgKiAgIGV2ZW50IChhcHBsaWVzIG9ubHkgZm9yIGBub3RpZnk6IHRydWVgIHByb3BlcnRpZXMpCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIHRoZSBwcm9wZXJ0eSBjaGFuZ2VkCiAgICAgICAgICovCiAgICAgICAgX3NldFBlbmRpbmdQcm9wZXJ0eShwcm9wZXJ0eSwgdmFsdWUsIHNob3VsZE5vdGlmeSkgewogICAgICAgICAgbGV0IHByb3BJc1BhdGggPSB0aGlzLl9fZGF0YUhhc1BhdGhzICYmIGlzUGF0aChwcm9wZXJ0eSk7CiAgICAgICAgICBsZXQgcHJldlByb3BzID0gcHJvcElzUGF0aCA/IHRoaXMuX19kYXRhVGVtcCA6IHRoaXMuX19kYXRhOwogICAgICAgICAgaWYgKHRoaXMuX3Nob3VsZFByb3BlcnR5Q2hhbmdlKHByb3BlcnR5LCB2YWx1ZSwgcHJldlByb3BzW3Byb3BlcnR5XSkpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9fZGF0YVBlbmRpbmcpIHsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YVBlbmRpbmcgPSB7fTsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YU9sZCA9IHt9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEVuc3VyZSBvbGQgaXMgY2FwdHVyZWQgZnJvbSB0aGUgbGFzdCB0dXJuCiAgICAgICAgICAgIGlmICghKHByb3BlcnR5IGluIHRoaXMuX19kYXRhT2xkKSkgewogICAgICAgICAgICAgIHRoaXMuX19kYXRhT2xkW3Byb3BlcnR5XSA9IHRoaXMuX19kYXRhW3Byb3BlcnR5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBQYXRocyBhcmUgc3RvcmVkIGluIHRlbXBvcmFyeSBjYWNoZSAoY2xlYXJlZCBhdCBlbmQgb2YgdHVybiksCiAgICAgICAgICAgIC8vIHdoaWNoIGlzIHVzZWQgZm9yIGRpcnR5LWNoZWNraW5nLCBhbGwgb3RoZXJzIHN0b3JlZCBpbiBfX2RhdGEKICAgICAgICAgICAgaWYgKHByb3BJc1BhdGgpIHsKICAgICAgICAgICAgICB0aGlzLl9fZGF0YVRlbXBbcHJvcGVydHldID0gdmFsdWU7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdGhpcy5fX2RhdGFbcHJvcGVydHldID0gdmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQWxsIGNoYW5nZXMgZ28gaW50byBwZW5kaW5nIHByb3BlcnR5IGJhZywgcGFzc2VkIHRvIF9wcm9wZXJ0aWVzQ2hhbmdlZAogICAgICAgICAgICB0aGlzLl9fZGF0YVBlbmRpbmdbcHJvcGVydHldID0gdmFsdWU7CiAgICAgICAgICAgIC8vIFRyYWNrIHByb3BlcnRpZXMgdGhhdCBzaG91bGQgbm90aWZ5IHNlcGFyYXRlbHkKICAgICAgICAgICAgaWYgKHByb3BJc1BhdGggfHwgKHRoaXNbVFlQRVMuTk9USUZZXSAmJiB0aGlzW1RZUEVTLk5PVElGWV1bcHJvcGVydHldKSkgewogICAgICAgICAgICAgIHRoaXMuX19kYXRhVG9Ob3RpZnkgPSB0aGlzLl9fZGF0YVRvTm90aWZ5IHx8IHt9OwogICAgICAgICAgICAgIHRoaXMuX19kYXRhVG9Ob3RpZnlbcHJvcGVydHldID0gc2hvdWxkTm90aWZ5OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIGJhc2UgaW1wbGVtZW50YXRpb24gdG8gZW5zdXJlIGFsbCBhY2Nlc3NvcnMgc2V0IGBzaG91bGROb3RpZnlgCiAgICAgICAgICogdG8gdHJ1ZSwgZm9yIHBlci1wcm9wZXJ0eSBub3RpZmljYXRpb24gdHJhY2tpbmcuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgTmFtZSBvZiB0aGUgcHJvcGVydHkKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIHNldAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgX3NldFByb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSkgewogICAgICAgICAgaWYgKHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eShwcm9wZXJ0eSwgdmFsdWUsIHRydWUpKSB7CiAgICAgICAgICAgIHRoaXMuX2ludmFsaWRhdGVQcm9wZXJ0aWVzKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgYFByb3BlcnR5QWNjZXNzb3JgJ3MgZGVmYXVsdCBhc3luYyBxdWV1aW5nIG9mCiAgICAgICAgICogYF9wcm9wZXJ0aWVzQ2hhbmdlZGA6IGlmIGBfX2RhdGFSZWFkeWAgaXMgZmFsc2UgKGhhcyBub3QgeWV0IGJlZW4KICAgICAgICAgKiBtYW51YWxseSBmbHVzaGVkKSwgdGhlIGZ1bmN0aW9uIG5vLW9wczsgb3RoZXJ3aXNlIGZsdXNoZXMKICAgICAgICAgKiBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBzeW5jaHJvbm91c2x5LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBfaW52YWxpZGF0ZVByb3BlcnRpZXMoKSB7CiAgICAgICAgICBpZiAodGhpcy5fX2RhdGFSZWFkeSkgewogICAgICAgICAgICB0aGlzLl9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEVucXVldWVzIHRoZSBnaXZlbiBjbGllbnQgb24gYSBsaXN0IG9mIHBlbmRpbmcgY2xpZW50cywgd2hvc2UKICAgICAgICAgKiBwZW5kaW5nIHByb3BlcnR5IGNoYW5nZXMgY2FuIGxhdGVyIGJlIGZsdXNoZWQgdmlhIGEgY2FsbCB0bwogICAgICAgICAqIGBfZmx1c2hDbGllbnRzYC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBjbGllbnQgUHJvcGVydHlFZmZlY3RzIGNsaWVudCB0byBlbnF1ZXVlCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2VucXVldWVDbGllbnQoY2xpZW50KSB7CiAgICAgICAgICB0aGlzLl9fZGF0YVBlbmRpbmdDbGllbnRzID0gdGhpcy5fX2RhdGFQZW5kaW5nQ2xpZW50cyB8fCBbXTsKICAgICAgICAgIGlmIChjbGllbnQgIT09IHRoaXMpIHsKICAgICAgICAgICAgdGhpcy5fX2RhdGFQZW5kaW5nQ2xpZW50cy5wdXNoKGNsaWVudCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBGbHVzaGVzIGFueSBjbGllbnRzIHByZXZpb3VzbHkgZW5xdWV1ZWQgdmlhIGBfZW5xdWV1ZUNsaWVudGAsIGNhdXNpbmcKICAgICAgICAgKiB0aGVpciBgX2ZsdXNoUHJvcGVydGllc2AgbWV0aG9kIHRvIHJ1bi4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9mbHVzaENsaWVudHMoKSB7CiAgICAgICAgICBpZiAoIXRoaXMuX19kYXRhQ2xpZW50c1JlYWR5KSB7CiAgICAgICAgICAgIHRoaXMuX19kYXRhQ2xpZW50c1JlYWR5ID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fcmVhZHlDbGllbnRzKCk7CiAgICAgICAgICAgIC8vIE92ZXJyaWRlIHBvaW50IHdoZXJlIGFjY2Vzc29ycyBhcmUgdHVybmVkIG9uOyBpbXBvcnRhbnRseSwKICAgICAgICAgICAgLy8gdGhpcyBpcyBhZnRlciBjbGllbnRzIGhhdmUgZnVsbHkgcmVhZGllZCwgcHJvdmlkaW5nIGEgZ3VhcmFudGVlCiAgICAgICAgICAgIC8vIHRoYXQgYW55IHByb3BlcnR5IGVmZmVjdHMgb2NjdXIgb25seSBhZnRlciBhbGwgY2xpZW50cyBhcmUgcmVhZHkuCiAgICAgICAgICAgIHRoaXMuX19kYXRhUmVhZHkgPSB0cnVlOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fX2VuYWJsZU9yRmx1c2hDbGllbnRzKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBOT1RFOiBXZSBlbnN1cmUgY2xpZW50cyBlaXRoZXIgZW5hYmxlIG9yIGZsdXNoIGFzIGFwcHJvcHJpYXRlLiBUaGlzCiAgICAgICAgLy8gaGFuZGxlcyB0d28gY29ybmVyIGNhc2VzOgogICAgICAgIC8vICgxKSBjbGllbnRzIGZsdXNoIHByb3Blcmx5IHdoZW4gY29ubmVjdGVkL2VuYWJsZWQgYmVmb3JlIHRoZSBob3N0CiAgICAgICAgLy8gZW5hYmxlczsgZS5nLgogICAgICAgIC8vICAgKGEpIFRlbXBsYXRpemUgc3RhbXBzIHdpdGggbm8gcHJvcGVydGllcyBhbmQgZG9lcyBub3QgZmx1c2ggYW5kCiAgICAgICAgLy8gICAoYikgdGhlIGluc3RhbmNlIGlzIGluc2VydGVkIGludG8gZG9tIGFuZAogICAgICAgIC8vICAgKGMpIHRoZW4gdGhlIGluc3RhbmNlIGZsdXNoZXMuCiAgICAgICAgLy8gKDIpIGNsaWVudHMgZW5hYmxlIHByb3Blcmx5IHdoZW4gbm90IGNvbm5lY3RlZC9lbmFibGVkIHdoZW4gdGhlIGhvc3QKICAgICAgICAvLyBmbHVzaGVzOyBlLmcuCiAgICAgICAgLy8gICAoYSkgYSB0ZW1wbGF0ZSBpcyBydW50aW1lIHN0YW1wZWQgYW5kIG5vdCB5ZXQgY29ubmVjdGVkL2VuYWJsZWQKICAgICAgICAvLyAgIChiKSBhIGhvc3Qgc2V0cyBhIHByb3BlcnR5LCBjYXVzaW5nIHN0YW1wZWQgZG9tIHRvIGZsdXNoCiAgICAgICAgLy8gICAoYykgdGhlIHN0YW1wZWQgZG9tIGVuYWJsZXMuCiAgICAgICAgX19lbmFibGVPckZsdXNoQ2xpZW50cygpIHsKICAgICAgICAgIGxldCBjbGllbnRzID0gdGhpcy5fX2RhdGFQZW5kaW5nQ2xpZW50czsKICAgICAgICAgIGlmIChjbGllbnRzKSB7CiAgICAgICAgICAgIHRoaXMuX19kYXRhUGVuZGluZ0NsaWVudHMgPSBudWxsOwogICAgICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBjbGllbnRzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgbGV0IGNsaWVudCA9IGNsaWVudHNbaV07CiAgICAgICAgICAgICAgaWYgKCFjbGllbnQuX19kYXRhRW5hYmxlZCkgewogICAgICAgICAgICAgICAgY2xpZW50Ll9lbmFibGVQcm9wZXJ0aWVzKCk7CiAgICAgICAgICAgICAgfSBlbHNlIGlmIChjbGllbnQuX19kYXRhUGVuZGluZykgewogICAgICAgICAgICAgICAgY2xpZW50Ll9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBlcmZvcm0gYW55IGluaXRpYWwgc2V0dXAgb24gY2xpZW50IGRvbS4gQ2FsbGVkIGJlZm9yZSB0aGUgZmlyc3QKICAgICAgICAgKiBgX2ZsdXNoUHJvcGVydGllc2AgY2FsbCBvbiBjbGllbnQgZG9tIGFuZCBiZWZvcmUgYW55IGVsZW1lbnQKICAgICAgICAgKiBvYnNlcnZlcnMgYXJlIGNhbGxlZC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9yZWFkeUNsaWVudHMoKSB7CiAgICAgICAgICB0aGlzLl9fZW5hYmxlT3JGbHVzaENsaWVudHMoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgYSBiYWcgb2YgcHJvcGVydHkgY2hhbmdlcyB0byB0aGlzIGluc3RhbmNlLCBhbmQKICAgICAgICAgKiBzeW5jaHJvbm91c2x5IHByb2Nlc3NlcyBhbGwgZWZmZWN0cyBvZiB0aGUgcHJvcGVydGllcyBhcyBhIGJhdGNoLgogICAgICAgICAqCiAgICAgICAgICogUHJvcGVydHkgbmFtZXMgbXVzdCBiZSBzaW1wbGUgcHJvcGVydGllcywgbm90IHBhdGhzLiAgQmF0Y2hlZAogICAgICAgICAqIHBhdGggcHJvcGFnYXRpb24gaXMgbm90IHN1cHBvcnRlZC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2Ygb25lIG9yIG1vcmUga2V5LXZhbHVlIHBhaXJzIHdob3NlIGtleSBpcwogICAgICAgICAqICAgYSBwcm9wZXJ0eSBhbmQgdmFsdWUgaXMgdGhlIG5ldyB2YWx1ZSB0byBzZXQgZm9yIHRoYXQgcHJvcGVydHkuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gc2V0UmVhZE9ubHkgV2hlbiB0cnVlLCBhbnkgcHJpdmF0ZSB2YWx1ZXMgc2V0IGluCiAgICAgICAgICogICBgcHJvcHNgIHdpbGwgYmUgc2V0LiBCeSBkZWZhdWx0LCBgc2V0UHJvcGVydGllc2Agd2lsbCBub3Qgc2V0CiAgICAgICAgICogICBgcmVhZE9ubHk6IHRydWVgIHJvb3QgcHJvcGVydGllcy4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKi8KICAgICAgICBzZXRQcm9wZXJ0aWVzKHByb3BzLCBzZXRSZWFkT25seSkgewogICAgICAgICAgZm9yIChsZXQgcGF0aCBpbiBwcm9wcykgewogICAgICAgICAgICBpZiAoc2V0UmVhZE9ubHkgfHwgIXRoaXNbVFlQRVMuUkVBRF9PTkxZXSB8fCAhdGhpc1tUWVBFUy5SRUFEX09OTFldW3BhdGhdKSB7CiAgICAgICAgICAgICAgLy9UT0RPKGtzY2hhYWYpOiBleHBsaWNpdGx5IGRpc2FsbG93IHBhdGhzIGluIHNldFByb3BlcnR5PwogICAgICAgICAgICAgIC8vIHdpbGRjYXJkIG9ic2VydmVycyBjdXJyZW50bHkgb25seSBwYXNzIHRoZSBmaXJzdCBjaGFuZ2VkIHBhdGgKICAgICAgICAgICAgICAvLyBpbiB0aGUgYGluZm9gIG9iamVjdCwgYW5kIHlvdSBjb3VsZCBkbyBzb21lIG9kZCB0aGluZ3MgYmF0Y2hpbmcKICAgICAgICAgICAgICAvLyBwYXRocywgZS5nLiB7J2Zvby5iYXInOiB7Li4ufSwgJ2Zvbyc6IG51bGx9CiAgICAgICAgICAgICAgdGhpcy5fc2V0UGVuZGluZ1Byb3BlcnR5T3JQYXRoKHBhdGgsIHByb3BzW3BhdGhdLCB0cnVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgdGhpcy5faW52YWxpZGF0ZVByb3BlcnRpZXMoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyBgUHJvcGVydHlBY2Nlc3NvcnNgIHNvIHRoYXQgcHJvcGVydHkgYWNjZXNzb3IKICAgICAgICAgKiBzaWRlIGVmZmVjdHMgYXJlIG5vdCBlbmFibGVkIHVudGlsIGFmdGVyIGNsaWVudCBkb20gaXMgZnVsbHkgcmVhZHkuCiAgICAgICAgICogQWxzbyBjYWxscyBgX2ZsdXNoQ2xpZW50c2AgY2FsbGJhY2sgdG8gZW5zdXJlIGNsaWVudCBkb20gaXMgZW5hYmxlZAogICAgICAgICAqIHRoYXQgd2FzIG5vdCBlbmFibGVkIGFzIGEgcmVzdWx0IG9mIGZsdXNoaW5nIHByb3BlcnRpZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgLy8gSXQgaXMgaW1wb3J0YW50IHRoYXQgYHN1cGVyLnJlYWR5KClgIGlzIG5vdCBjYWxsZWQgaGVyZSBhcyBpdAogICAgICAgICAgLy8gaW1tZWRpYXRlbHkgdHVybnMgb24gYWNjZXNzb3JzLiBJbnN0ZWFkLCB3ZSB3YWl0IHVudGlsIGByZWFkeUNsaWVudHNgCiAgICAgICAgICAvLyB0byBlbmFibGUgYWNjZXNzb3JzIHRvIHByb3ZpZGUgYSBndWFyYW50ZWUgdGhhdCBjbGllbnRzIGFyZSByZWFkeQogICAgICAgICAgLy8gYmVmb3JlIHByb2Nlc3NpbmcgYW55IGFjY2Vzc29ycyBzaWRlIGVmZmVjdHMuCiAgICAgICAgICB0aGlzLl9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICAgIC8vIElmIG5vIGRhdGEgd2FzIHBlbmRpbmcsIGBfZmx1c2hQcm9wZXJ0aWVzYCB3aWxsIG5vdCBgZmx1c2hDbGllbnRzYAogICAgICAgICAgLy8gc28gZW5zdXJlIHRoaXMgaXMgZG9uZS4KICAgICAgICAgIGlmICghdGhpcy5fX2RhdGFDbGllbnRzUmVhZHkpIHsKICAgICAgICAgICAgdGhpcy5fZmx1c2hDbGllbnRzKCk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBCZWZvcmUgcmVhZHksIGNsaWVudCBub3RpZmljYXRpb25zIGRvIG5vdCB0cmlnZ2VyIF9mbHVzaFByb3BlcnRpZXMuCiAgICAgICAgICAvLyBUaGVyZWZvcmUgYSBmbHVzaCBpcyBuZWNlc3NhcnkgaGVyZSBpZiBkYXRhIGhhcyBiZWVuIHNldC4KICAgICAgICAgIGlmICh0aGlzLl9fZGF0YVBlbmRpbmcpIHsKICAgICAgICAgICAgdGhpcy5fZmx1c2hQcm9wZXJ0aWVzKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJbXBsZW1lbnRzIGBQcm9wZXJ0eUFjY2Vzc29yc2AncyBwcm9wZXJ0aWVzIGNoYW5nZWQgY2FsbGJhY2suCiAgICAgICAgICoKICAgICAgICAgKiBSdW5zIGVhY2ggY2xhc3Mgb2YgZWZmZWN0cyBmb3IgdGhlIGJhdGNoIG9mIGNoYW5nZWQgcHJvcGVydGllcyBpbgogICAgICAgICAqIGEgc3BlY2lmaWMgb3JkZXIgKGNvbXB1dGUsIHByb3BhZ2F0ZSwgcmVmbGVjdCwgb2JzZXJ2ZSwgbm90aWZ5KS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7IU9iamVjdH0gY3VycmVudFByb3BzIEJhZyBvZiBhbGwgY3VycmVudCBhY2Nlc3NvciB2YWx1ZXMKICAgICAgICAgKiBAcGFyYW0gez9PYmplY3R9IGNoYW5nZWRQcm9wcyBCYWcgb2YgcHJvcGVydGllcyBjaGFuZ2VkIHNpbmNlIHRoZSBsYXN0CiAgICAgICAgICogICBjYWxsIHRvIGBfcHJvcGVydGllc0NoYW5nZWRgCiAgICAgICAgICogQHBhcmFtIHs/T2JqZWN0fSBvbGRQcm9wcyBCYWcgb2YgcHJldmlvdXMgdmFsdWVzIGZvciBlYWNoIHByb3BlcnR5CiAgICAgICAgICogICBpbiBgY2hhbmdlZFByb3BzYAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgX3Byb3BlcnRpZXNDaGFuZ2VkKGN1cnJlbnRQcm9wcywgY2hhbmdlZFByb3BzLCBvbGRQcm9wcykgewogICAgICAgICAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgLy8gbGV0IGMgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhjaGFuZ2VkUHJvcHMgfHwge30pOwogICAgICAgICAgLy8gd2luZG93LmRlYnVnICYmIGNvbnNvbGUuZ3JvdXAodGhpcy5sb2NhbE5hbWUgKyAnIycgKyB0aGlzLmlkICsgJzogJyArIGMpOwogICAgICAgICAgLy8gaWYgKHdpbmRvdy5kZWJ1ZykgeyBkZWJ1Z2dlcjsgfQogICAgICAgICAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgbGV0IGhhc1BhdGhzID0gdGhpcy5fX2RhdGFIYXNQYXRoczsKICAgICAgICAgIHRoaXMuX19kYXRhSGFzUGF0aHMgPSBmYWxzZTsKICAgICAgICAgIGxldCBub3RpZnlQcm9wczsKICAgICAgICAgIC8vIENvbXB1dGUgcHJvcGVydGllcwogICAgICAgICAgcnVuQ29tcHV0ZWRFZmZlY3RzKHRoaXMsIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKTsKICAgICAgICAgIC8vIENsZWFyIG5vdGlmeSBwcm9wZXJ0aWVzIHByaW9yIHRvIHBvc3NpYmxlIHJlZW50cnkgKHByb3BhZ2F0ZSwgb2JzZXJ2ZSksCiAgICAgICAgICAvLyBidXQgYWZ0ZXIgY29tcHV0aW5nIGVmZmVjdHMgaGF2ZSBhIGNoYW5jZSB0byBhZGQgdG8gdGhlbQogICAgICAgICAgbm90aWZ5UHJvcHMgPSB0aGlzLl9fZGF0YVRvTm90aWZ5OwogICAgICAgICAgdGhpcy5fX2RhdGFUb05vdGlmeSA9IG51bGw7CiAgICAgICAgICAvLyBQcm9wYWdhdGUgcHJvcGVydGllcyB0byBjbGllbnRzCiAgICAgICAgICB0aGlzLl9wcm9wYWdhdGVQcm9wZXJ0eUNoYW5nZXMoY2hhbmdlZFByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpOwogICAgICAgICAgLy8gRmx1c2ggY2xpZW50cwogICAgICAgICAgdGhpcy5fZmx1c2hDbGllbnRzKCk7CiAgICAgICAgICAvLyBSZWZsZWN0IHByb3BlcnRpZXMKICAgICAgICAgIHJ1bkVmZmVjdHModGhpcywgdGhpc1tUWVBFUy5SRUZMRUNUXSwgY2hhbmdlZFByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpOwogICAgICAgICAgLy8gT2JzZXJ2ZSBwcm9wZXJ0aWVzCiAgICAgICAgICBydW5FZmZlY3RzKHRoaXMsIHRoaXNbVFlQRVMuT0JTRVJWRV0sIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKTsKICAgICAgICAgIC8vIE5vdGlmeSBwcm9wZXJ0aWVzIHRvIGhvc3QKICAgICAgICAgIGlmIChub3RpZnlQcm9wcykgewogICAgICAgICAgICBydW5Ob3RpZnlFZmZlY3RzKHRoaXMsIG5vdGlmeVByb3BzLCBjaGFuZ2VkUHJvcHMsIG9sZFByb3BzLCBoYXNQYXRocyk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDbGVhciB0ZW1wb3JhcnkgY2FjaGUgYXQgZW5kIG9mIHR1cm4KICAgICAgICAgIGlmICh0aGlzLl9fZGF0YUNvdW50ZXIgPT0gMSkgewogICAgICAgICAgICB0aGlzLl9fZGF0YVRlbXAgPSB7fTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICAgIC8vIHdpbmRvdy5kZWJ1ZyAmJiBjb25zb2xlLmdyb3VwRW5kKHRoaXMubG9jYWxOYW1lICsgJyMnICsgdGhpcy5pZCArICc6ICcgKyBjKTsKICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxlZCB0byBwcm9wYWdhdGUgYW55IHByb3BlcnR5IGNoYW5nZXMgdG8gc3RhbXBlZCB0ZW1wbGF0ZSBub2RlcwogICAgICAgICAqIG1hbmFnZWQgYnkgdGhpcyBlbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IGNoYW5nZWRQcm9wcyBCYWcgb2YgY2hhbmdlZCBwcm9wZXJ0aWVzCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaGFzUGF0aHMgVHJ1ZSB3aXRoIGBwcm9wc2AgY29udGFpbnMgb25lIG9yIG1vcmUgcGF0aHMKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBfcHJvcGFnYXRlUHJvcGVydHlDaGFuZ2VzKGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKSB7CiAgICAgICAgICBpZiAodGhpc1tUWVBFUy5QUk9QQUdBVEVdKSB7CiAgICAgICAgICAgIHJ1bkVmZmVjdHModGhpcywgdGhpc1tUWVBFUy5QUk9QQUdBVEVdLCBjaGFuZ2VkUHJvcHMsIG9sZFByb3BzLCBoYXNQYXRocyk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodGhpcy5fX3RlbXBsYXRlSW5mbykgewogICAgICAgICAgICB0aGlzLl9ydW5FZmZlY3RzRm9yVGVtcGxhdGUodGhpcy5fX3RlbXBsYXRlSW5mbywgY2hhbmdlZFByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgX3J1bkVmZmVjdHNGb3JUZW1wbGF0ZSh0ZW1wbGF0ZUluZm8sIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKSB7CiAgICAgICAgICBjb25zdCBiYXNlUnVuRWZmZWN0cyA9IChjaGFuZ2VkUHJvcHMsIGhhc1BhdGhzKSA9PiB7CiAgICAgICAgICAgIHJ1bkVmZmVjdHModGhpcywgdGVtcGxhdGVJbmZvLnByb3BlcnR5RWZmZWN0cywgY2hhbmdlZFByb3BzLCBvbGRQcm9wcywKICAgICAgICAgICAgICBoYXNQYXRocywgdGVtcGxhdGVJbmZvLm5vZGVMaXN0KTsKICAgICAgICAgICAgZm9yIChsZXQgaW5mbz10ZW1wbGF0ZUluZm8uZmlyc3RDaGlsZDsgaW5mbzsgaW5mbz1pbmZvLm5leHRTaWJsaW5nKSB7CiAgICAgICAgICAgICAgdGhpcy5fcnVuRWZmZWN0c0ZvclRlbXBsYXRlKGluZm8sIGNoYW5nZWRQcm9wcywgb2xkUHJvcHMsIGhhc1BhdGhzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfTsKICAgICAgICAgIGlmICh0ZW1wbGF0ZUluZm8ucnVuRWZmZWN0cykgewogICAgICAgICAgICB0ZW1wbGF0ZUluZm8ucnVuRWZmZWN0cyhiYXNlUnVuRWZmZWN0cywgY2hhbmdlZFByb3BzLCBoYXNQYXRocyk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBiYXNlUnVuRWZmZWN0cyhjaGFuZ2VkUHJvcHMsIGhhc1BhdGhzKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEFsaWFzZXMgb25lIGRhdGEgcGF0aCBhcyBhbm90aGVyLCBzdWNoIHRoYXQgcGF0aCBub3RpZmljYXRpb25zIGZyb20gb25lCiAgICAgICAgICogYXJlIHJvdXRlZCB0byB0aGUgb3RoZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxzdHJpbmd8bnVtYmVyPn0gdG8gVGFyZ2V0IHBhdGggdG8gbGluay4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxzdHJpbmd8bnVtYmVyPn0gZnJvbSBTb3VyY2UgcGF0aCB0byBsaW5rLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHB1YmxpYwogICAgICAgICAqLwogICAgICAgIGxpbmtQYXRocyh0bywgZnJvbSkgewogICAgICAgICAgdG8gPSBub3JtYWxpemUodG8pOwogICAgICAgICAgZnJvbSA9IG5vcm1hbGl6ZShmcm9tKTsKICAgICAgICAgIHRoaXMuX19kYXRhTGlua2VkUGF0aHMgPSB0aGlzLl9fZGF0YUxpbmtlZFBhdGhzIHx8IHt9OwogICAgICAgICAgdGhpcy5fX2RhdGFMaW5rZWRQYXRoc1t0b10gPSBmcm9tOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGRhdGEgcGF0aCBhbGlhcyBwcmV2aW91c2x5IGVzdGFibGlzaGVkIHdpdGggYF9saW5rUGF0aHNgLgogICAgICAgICAqCiAgICAgICAgICogTm90ZSwgdGhlIHBhdGggdG8gdW5saW5rIHNob3VsZCBiZSB0aGUgdGFyZ2V0IChgdG9gKSB1c2VkIHdoZW4KICAgICAgICAgKiBsaW5raW5nIHRoZSBwYXRocy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nIHwgIUFycmF5PHN0cmluZ3xudW1iZXI+fSBwYXRoIFRhcmdldCBwYXRoIHRvIHVubGluay4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKi8KICAgICAgICB1bmxpbmtQYXRocyhwYXRoKSB7CiAgICAgICAgICBwYXRoID0gbm9ybWFsaXplKHBhdGgpOwogICAgICAgICAgaWYgKHRoaXMuX19kYXRhTGlua2VkUGF0aHMpIHsKICAgICAgICAgICAgZGVsZXRlIHRoaXMuX19kYXRhTGlua2VkUGF0aHNbcGF0aF07CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBOb3RpZnkgdGhhdCBhbiBhcnJheSBoYXMgY2hhbmdlZC4KICAgICAgICAgKgogICAgICAgICAqIEV4YW1wbGU6CiAgICAgICAgICoKICAgICAgICAgKiAgICAgdGhpcy5pdGVtcyA9IFsge25hbWU6ICdKaW0nfSwge25hbWU6ICdUb2RkJ30sIHtuYW1lOiAnQmlsbCd9IF07CiAgICAgICAgICogICAgIC4uLgogICAgICAgICAqICAgICB0aGlzLml0ZW1zLnNwbGljZSgxLCAxLCB7bmFtZTogJ1NhbSd9KTsKICAgICAgICAgKiAgICAgdGhpcy5pdGVtcy5wdXNoKHtuYW1lOiAnQm9iJ30pOwogICAgICAgICAqICAgICB0aGlzLm5vdGlmeVNwbGljZXMoJ2l0ZW1zJywgWwogICAgICAgICAqICAgICAgIHsgaW5kZXg6IDEsIHJlbW92ZWQ6IFt7bmFtZTogJ1RvZGQnfV0sIGFkZGVkQ291bnQ6IDEsCiAgICAgICAgICogICAgICAgICBvYmplY3Q6IHRoaXMuaXRlbXMsIHR5cGU6ICdzcGxpY2UnIH0sCiAgICAgICAgICogICAgICAgeyBpbmRleDogMywgcmVtb3ZlZDogW10sIGFkZGVkQ291bnQ6IDEsCiAgICAgICAgICogICAgICAgICBvYmplY3Q6IHRoaXMuaXRlbXMsIHR5cGU6ICdzcGxpY2UnfQogICAgICAgICAqICAgICBdKTsKICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFBhdGggdGhhdCBzaG91bGQgYmUgbm90aWZpZWQuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gc3BsaWNlcyBBcnJheSBvZiBzcGxpY2UgcmVjb3JkcyBpbmRpY2F0aW5nIG9yZGVyZWQKICAgICAgICAgKiAgIGNoYW5nZXMgdGhhdCBvY2N1cnJlZCB0byB0aGUgYXJyYXkuIEVhY2ggcmVjb3JkIHNob3VsZCBoYXZlIHRoZQogICAgICAgICAqICAgZm9sbG93aW5nIGZpZWxkczoKICAgICAgICAgKiAgICAqIGluZGV4OiBpbmRleCBhdCB3aGljaCB0aGUgY2hhbmdlIG9jY3VycmVkCiAgICAgICAgICogICAgKiByZW1vdmVkOiBhcnJheSBvZiBpdGVtcyB0aGF0IHdlcmUgcmVtb3ZlZCBmcm9tIHRoaXMgaW5kZXgKICAgICAgICAgKiAgICAqIGFkZGVkQ291bnQ6IG51bWJlciBvZiBuZXcgaXRlbXMgYWRkZWQgYXQgdGhpcyBpbmRleAogICAgICAgICAqICAgICogb2JqZWN0OiBhIHJlZmVyZW5jZSB0byB0aGUgYXJyYXkgaW4gcXVlc3Rpb24KICAgICAgICAgKiAgICAqIHR5cGU6IHRoZSBzdHJpbmcgbGl0ZXJhbCAnc3BsaWNlJwogICAgICAgICAqCiAgICAgICAgICogICBOb3RlIHRoYXQgc3BsaWNlIHJlY29yZHMgX211c3RfIGJlIG5vcm1hbGl6ZWQgc3VjaCB0aGF0IHRoZXkgYXJlCiAgICAgICAgICogICByZXBvcnRlZCBpbiBpbmRleCBvcmRlciAocmF3IHJlc3VsdHMgZnJvbSBgT2JqZWN0Lm9ic2VydmVgIGFyZSBub3QKICAgICAgICAgKiAgIG9yZGVyZWQgYW5kIG11c3QgYmUgbm9ybWFsaXplZC9tZXJnZWQgYmVmb3JlIG5vdGlmeWluZykuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKi8KICAgICAgICBub3RpZnlTcGxpY2VzKHBhdGgsIHNwbGljZXMpIHsKICAgICAgICAgIGxldCBpbmZvID0ge3BhdGg6ICcnfTsKICAgICAgICAgIGxldCBhcnJheSA9IC8qKiBAdHlwZSB7QXJyYXl9ICovKGdldCh0aGlzLCBwYXRoLCBpbmZvKSk7CiAgICAgICAgICBub3RpZnlTcGxpY2VzKHRoaXMsIGFycmF5LCBpbmZvLnBhdGgsIHNwbGljZXMpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVuaWVuY2UgbWV0aG9kIGZvciByZWFkaW5nIGEgdmFsdWUgZnJvbSBhIHBhdGguCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlLCBpZiBhbnkgcGFydCBpbiB0aGUgcGF0aCBpcyB1bmRlZmluZWQsIHRoaXMgbWV0aG9kIHJldHVybnMKICAgICAgICAgKiBgdW5kZWZpbmVkYCAodGhpcyBtZXRob2QgZG9lcyBub3QgdGhyb3cgd2hlbiBkZXJlZmVyZW5jaW5nIHVuZGVmaW5lZAogICAgICAgICAqIHBhdGhzKS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7KHN0cmluZ3whQXJyYXk8KHN0cmluZ3xudW1iZXIpPil9IHBhdGggUGF0aCB0byB0aGUgdmFsdWUKICAgICAgICAgKiAgIHRvIHJlYWQuICBUaGUgcGF0aCBtYXkgYmUgc3BlY2lmaWVkIGFzIGEgc3RyaW5nIChlLmcuIGBmb28uYmFyLmJhemApCiAgICAgICAgICogICBvciBhbiBhcnJheSBvZiBwYXRoIHBhcnRzIChlLmcuIGBbJ2Zvby5iYXInLCAnYmF6J11gKS4gIE5vdGUgdGhhdAogICAgICAgICAqICAgYnJhY2tldGVkIGV4cHJlc3Npb25zIGFyZSBub3Qgc3VwcG9ydGVkOyBzdHJpbmctYmFzZWQgcGF0aCBwYXJ0cwogICAgICAgICAqICAgKm11c3QqIGJlIHNlcGFyYXRlZCBieSBkb3RzLiAgTm90ZSB0aGF0IHdoZW4gZGVyZWZlcmVuY2luZyBhcnJheQogICAgICAgICAqICAgaW5kaWNlcywgdGhlIGluZGV4IG1heSBiZSB1c2VkIGFzIGEgZG90dGVkIHBhcnQgZGlyZWN0bHkKICAgICAgICAgKiAgIChlLmcuIGB1c2Vycy4xMi5uYW1lYCBvciBgWyd1c2VycycsIDEyLCAnbmFtZSddYCkuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSByb290IFJvb3Qgb2JqZWN0IGZyb20gd2hpY2ggdGhlIHBhdGggaXMgZXZhbHVhdGVkLgogICAgICAgICAqIEByZXR1cm4geyp9IFZhbHVlIGF0IHRoZSBwYXRoLCBvciBgdW5kZWZpbmVkYCBpZiBhbnkgcGFydCBvZiB0aGUgcGF0aAogICAgICAgICAqICAgaXMgdW5kZWZpbmVkLgogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKi8KICAgICAgICBnZXQocGF0aCwgcm9vdCkgewogICAgICAgICAgcmV0dXJuIGdldChyb290IHx8IHRoaXMsIHBhdGgpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVuaWVuY2UgbWV0aG9kIGZvciBzZXR0aW5nIGEgdmFsdWUgdG8gYSBwYXRoIGFuZCBub3RpZnlpbmcgYW55CiAgICAgICAgICogZWxlbWVudHMgYm91bmQgdG8gdGhlIHNhbWUgcGF0aC4KICAgICAgICAgKgogICAgICAgICAqIE5vdGUsIGlmIGFueSBwYXJ0IGluIHRoZSBwYXRoIGV4Y2VwdCBmb3IgdGhlIGxhc3QgaXMgdW5kZWZpbmVkLAogICAgICAgICAqIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZyAodGhpcyBtZXRob2QgZG9lcyBub3QgdGhyb3cgd2hlbgogICAgICAgICAqIGRlcmVmZXJlbmNpbmcgdW5kZWZpbmVkIHBhdGhzKS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7KHN0cmluZ3whQXJyYXk8KHN0cmluZ3xudW1iZXIpPil9IHBhdGggUGF0aCB0byB0aGUgdmFsdWUKICAgICAgICAgKiAgIHRvIHdyaXRlLiAgVGhlIHBhdGggbWF5IGJlIHNwZWNpZmllZCBhcyBhIHN0cmluZyAoZS5nLiBgJ2Zvby5iYXIuYmF6J2ApCiAgICAgICAgICogICBvciBhbiBhcnJheSBvZiBwYXRoIHBhcnRzIChlLmcuIGBbJ2Zvby5iYXInLCAnYmF6J11gKS4gIE5vdGUgdGhhdAogICAgICAgICAqICAgYnJhY2tldGVkIGV4cHJlc3Npb25zIGFyZSBub3Qgc3VwcG9ydGVkOyBzdHJpbmctYmFzZWQgcGF0aCBwYXJ0cwogICAgICAgICAqICAgKm11c3QqIGJlIHNlcGFyYXRlZCBieSBkb3RzLiAgTm90ZSB0aGF0IHdoZW4gZGVyZWZlcmVuY2luZyBhcnJheQogICAgICAgICAqICAgaW5kaWNlcywgdGhlIGluZGV4IG1heSBiZSB1c2VkIGFzIGEgZG90dGVkIHBhcnQgZGlyZWN0bHkKICAgICAgICAgKiAgIChlLmcuIGAndXNlcnMuMTIubmFtZSdgIG9yIGBbJ3VzZXJzJywgMTIsICduYW1lJ11gKS4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIHNldCBhdCB0aGUgc3BlY2lmaWVkIHBhdGguCiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSByb290IFJvb3Qgb2JqZWN0IGZyb20gd2hpY2ggdGhlIHBhdGggaXMgZXZhbHVhdGVkLgogICAgICAgICAqICAgV2hlbiBzcGVjaWZpZWQsIG5vIG5vdGlmaWNhdGlvbiB3aWxsIG9jY3VyLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHB1YmxpYwogICAgICAgICAqLwogICAgICAgIHNldChwYXRoLCB2YWx1ZSwgcm9vdCkgewogICAgICAgICAgaWYgKHJvb3QpIHsKICAgICAgICAgICAgc2V0KHJvb3QsIHBhdGgsIHZhbHVlKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGlmICghdGhpc1tUWVBFUy5SRUFEX09OTFldIHx8ICF0aGlzW1RZUEVTLlJFQURfT05MWV1bLyoqIEB0eXBlIHtzdHJpbmd9ICovKHBhdGgpXSkgewogICAgICAgICAgICAgIGlmICh0aGlzLl9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgocGF0aCwgdmFsdWUsIHRydWUpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9pbnZhbGlkYXRlUHJvcGVydGllcygpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBpdGVtcyBvbnRvIHRoZSBlbmQgb2YgdGhlIGFycmF5IGF0IHRoZSBwYXRoIHNwZWNpZmllZC4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBhcmd1bWVudHMgYWZ0ZXIgYHBhdGhgIGFuZCByZXR1cm4gdmFsdWUgbWF0Y2ggdGhhdCBvZgogICAgICAgICAqIGBBcnJheS5wcm90b3R5cGUucHVzaGAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBub3RpZmllcyBvdGhlciBwYXRocyB0byB0aGUgc2FtZSBhcnJheSB0aGF0IGEKICAgICAgICAgKiBzcGxpY2Ugb2NjdXJyZWQgdG8gdGhlIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmcgfCAhQXJyYXk8c3RyaW5nfG51bWJlcj59IHBhdGggUGF0aCB0byBhcnJheS4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IGl0ZW1zIEl0ZW1zIHRvIHB1c2ggb250byBhcnJheQogICAgICAgICAqIEByZXR1cm4ge251bWJlcn0gTmV3IGxlbmd0aCBvZiB0aGUgYXJyYXkuCiAgICAgICAgICogQHB1YmxpYwogICAgICAgICAqLwogICAgICAgIHB1c2gocGF0aCwgLi4uaXRlbXMpIHsKICAgICAgICAgIGxldCBpbmZvID0ge3BhdGg6ICcnfTsKICAgICAgICAgIGxldCBhcnJheSA9IC8qKiBAdHlwZSB7QXJyYXl9Ki8oZ2V0KHRoaXMsIHBhdGgsIGluZm8pKTsKICAgICAgICAgIGxldCBsZW4gPSBhcnJheS5sZW5ndGg7CiAgICAgICAgICBsZXQgcmV0ID0gYXJyYXkucHVzaCguLi5pdGVtcyk7CiAgICAgICAgICBpZiAoaXRlbXMubGVuZ3RoKSB7CiAgICAgICAgICAgIG5vdGlmeVNwbGljZSh0aGlzLCBhcnJheSwgaW5mby5wYXRoLCBsZW4sIGl0ZW1zLmxlbmd0aCwgW10pOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJldDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYW4gaXRlbSBmcm9tIHRoZSBlbmQgb2YgYXJyYXkgYXQgdGhlIHBhdGggc3BlY2lmaWVkLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGFyZ3VtZW50cyBhZnRlciBgcGF0aGAgYW5kIHJldHVybiB2YWx1ZSBtYXRjaCB0aGF0IG9mCiAgICAgICAgICogYEFycmF5LnByb3RvdHlwZS5wb3BgLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBtZXRob2Qgbm90aWZpZXMgb3RoZXIgcGF0aHMgdG8gdGhlIHNhbWUgYXJyYXkgdGhhdCBhCiAgICAgICAgICogc3BsaWNlIG9jY3VycmVkIHRvIHRoZSBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nIHwgIUFycmF5PHN0cmluZ3xudW1iZXI+fSBwYXRoIFBhdGggdG8gYXJyYXkuCiAgICAgICAgICogQHJldHVybiB7Kn0gSXRlbSB0aGF0IHdhcyByZW1vdmVkLgogICAgICAgICAqIEBwdWJsaWMKICAgICAgICAgKi8KICAgICAgICBwb3AocGF0aCkgewogICAgICAgICAgbGV0IGluZm8gPSB7cGF0aDogJyd9OwogICAgICAgICAgbGV0IGFycmF5ID0gLyoqIEB0eXBlIHtBcnJheX0gKi8oZ2V0KHRoaXMsIHBhdGgsIGluZm8pKTsKICAgICAgICAgIGxldCBoYWRMZW5ndGggPSBCb29sZWFuKGFycmF5Lmxlbmd0aCk7CiAgICAgICAgICBsZXQgcmV0ID0gYXJyYXkucG9wKCk7CiAgICAgICAgICBpZiAoaGFkTGVuZ3RoKSB7CiAgICAgICAgICAgIG5vdGlmeVNwbGljZSh0aGlzLCBhcnJheSwgaW5mby5wYXRoLCBhcnJheS5sZW5ndGgsIDAsIFtyZXRdKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTdGFydGluZyBmcm9tIHRoZSBzdGFydCBpbmRleCBzcGVjaWZpZWQsIHJlbW92ZXMgMCBvciBtb3JlIGl0ZW1zCiAgICAgICAgICogZnJvbSB0aGUgYXJyYXkgYW5kIGluc2VydHMgMCBvciBtb3JlIG5ldyBpdGVtcyBpbiB0aGVpciBwbGFjZS4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBhcmd1bWVudHMgYWZ0ZXIgYHBhdGhgIGFuZCByZXR1cm4gdmFsdWUgbWF0Y2ggdGhhdCBvZgogICAgICAgICAqIGBBcnJheS5wcm90b3R5cGUuc3BsaWNlYC4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgbWV0aG9kIG5vdGlmaWVzIG90aGVyIHBhdGhzIHRvIHRoZSBzYW1lIGFycmF5IHRoYXQgYQogICAgICAgICAqIHNwbGljZSBvY2N1cnJlZCB0byB0aGUgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxzdHJpbmd8bnVtYmVyPn0gcGF0aCBQYXRoIHRvIGFycmF5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzdGFydCBJbmRleCBmcm9tIHdoaWNoIHRvIHN0YXJ0IHJlbW92aW5nL2luc2VydGluZy4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcj19IGRlbGV0ZUNvdW50IE51bWJlciBvZiBpdGVtcyB0byByZW1vdmUuCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBpdGVtcyBJdGVtcyB0byBpbnNlcnQgaW50byBhcnJheS4KICAgICAgICAgKiBAcmV0dXJuIHshQXJyYXl9IEFycmF5IG9mIHJlbW92ZWQgaXRlbXMuCiAgICAgICAgICogQHB1YmxpYwogICAgICAgICAqLwogICAgICAgIHNwbGljZShwYXRoLCBzdGFydCwgZGVsZXRlQ291bnQsIC4uLml0ZW1zKSB7CiAgICAgICAgICBsZXQgaW5mbyA9IHtwYXRoIDogJyd9OwogICAgICAgICAgbGV0IGFycmF5ID0gLyoqIEB0eXBlIHtBcnJheX0gKi8oZ2V0KHRoaXMsIHBhdGgsIGluZm8pKTsKICAgICAgICAgIC8vIE5vcm1hbGl6ZSBmYW5jeSBuYXRpdmUgc3BsaWNlIGhhbmRsaW5nIG9mIGNyYXp5IHN0YXJ0IHZhbHVlcwogICAgICAgICAgaWYgKHN0YXJ0IDwgMCkgewogICAgICAgICAgICBzdGFydCA9IGFycmF5Lmxlbmd0aCAtIE1hdGguZmxvb3IoLXN0YXJ0KTsKICAgICAgICAgIH0gZWxzZSBpZiAoc3RhcnQpIHsKICAgICAgICAgICAgc3RhcnQgPSBNYXRoLmZsb29yKHN0YXJ0KTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIGFycmF5LnNwbGljZSBkb2VzIGRpZmZlcmVudCB0aGluZ3MgYmFzZWQgb24gdGhlIG51bWJlciBvZiBhcmd1bWVudHMKICAgICAgICAgIC8vIHlvdSBwYXNzIGluLiBUaGVyZWZvcmUsIGFycmF5LnNwbGljZSgwKSBhbmQgYXJyYXkuc3BsaWNlKDAsIHVuZGVmaW5lZCkKICAgICAgICAgIC8vIGRvIGRpZmZlcmVudCB0aGluZ3MuIEluIHRoZSBmb3JtZXIsIHRoZSB3aG9sZSBhcnJheSBpcyBjbGVhcmVkLiBJbiB0aGUKICAgICAgICAgIC8vIGxhdHRlciwgbm8gaXRlbXMgYXJlIHJlbW92ZWQuCiAgICAgICAgICAvLyBUaGlzIG1lYW5zIHRoYXQgd2UgbmVlZCB0byBkZXRlY3Qgd2hldGhlciAxLiBvbmUgb2YgdGhlIGFyZ3VtZW50cwogICAgICAgICAgLy8gaXMgYWN0dWFsbHkgcGFzc2VkIGluIGFuZCB0aGVuIDIuIGRldGVybWluZSBob3cgbWFueSBhcmd1bWVudHMKICAgICAgICAgIC8vIHdlIHNob3VsZCBwYXNzIG9uIHRvIHRoZSBuYXRpdmUgYXJyYXkuc3BsaWNlCiAgICAgICAgICAvLwogICAgICAgICAgbGV0IHJldDsKICAgICAgICAgIC8vIE9taXQgYW55IGFkZGl0aW9uYWwgYXJndW1lbnRzIGlmIHRoZXkgd2VyZSBub3QgcGFzc2VkIGluCiAgICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA9PT0gMikgewogICAgICAgICAgICByZXQgPSBhcnJheS5zcGxpY2Uoc3RhcnQpOwogICAgICAgICAgLy8gRWl0aGVyIHN0YXJ0IHdhcyB1bmRlZmluZWQgYW5kIHRoZSBvdGhlcnMgd2VyZSBkZWZpbmVkLCBidXQgaW4gdGhpcwogICAgICAgICAgLy8gY2FzZSB3ZSBjYW4gc2FmZWx5IHBhc3Mgb24gYWxsIGFyZ3VtZW50cwogICAgICAgICAgLy8KICAgICAgICAgIC8vIE5vdGU6IHRoaXMgaW5jbHVkZXMgdGhlIGNhc2Ugd2hlcmUgbm9uZSBvZiB0aGUgYXJndW1lbnRzIHdlcmUgcGFzc2VkIGluLAogICAgICAgICAgLy8gZS5nLiB0aGlzLnNwbGljZSgnYXJyYXknKS4gSG93ZXZlciwgaWYgYm90aCBzdGFydCBhbmQgZGVsZXRlQ291bnQKICAgICAgICAgIC8vIGFyZSB1bmRlZmluZWQsIGFycmF5LnNwbGljZSB3aWxsIG5vdCBtb2RpZnkgdGhlIGFycmF5IChhcyBleHBlY3RlZCkKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHJldCA9IGFycmF5LnNwbGljZShzdGFydCwgZGVsZXRlQ291bnQsIC4uLml0ZW1zKTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIEF0IHRoZSBlbmQsIGNoZWNrIHdoZXRoZXIgYW55IGl0ZW1zIHdlcmUgcGFzc2VkIGluIChlLmcuIGluc2VydGlvbnMpCiAgICAgICAgICAvLyBvciBpZiB0aGUgcmV0dXJuIGFycmF5IGNvbnRhaW5zIGl0ZW1zIChlLmcuIGRlbGV0aW9ucykuCiAgICAgICAgICAvLyBPbmx5IG5vdGlmeSBpZiBpdGVtcyB3ZXJlIGFkZGVkIG9yIGRlbGV0ZWQuCiAgICAgICAgICBpZiAoaXRlbXMubGVuZ3RoIHx8IHJldC5sZW5ndGgpIHsKICAgICAgICAgICAgbm90aWZ5U3BsaWNlKHRoaXMsIGFycmF5LCBpbmZvLnBhdGgsIHN0YXJ0LCBpdGVtcy5sZW5ndGgsIHJldCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmV0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbiBpdGVtIGZyb20gdGhlIGJlZ2lubmluZyBvZiBhcnJheSBhdCB0aGUgcGF0aCBzcGVjaWZpZWQuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgYXJndW1lbnRzIGFmdGVyIGBwYXRoYCBhbmQgcmV0dXJuIHZhbHVlIG1hdGNoIHRoYXQgb2YKICAgICAgICAgKiBgQXJyYXkucHJvdG90eXBlLnBvcGAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBub3RpZmllcyBvdGhlciBwYXRocyB0byB0aGUgc2FtZSBhcnJheSB0aGF0IGEKICAgICAgICAgKiBzcGxpY2Ugb2NjdXJyZWQgdG8gdGhlIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmcgfCAhQXJyYXk8c3RyaW5nfG51bWJlcj59IHBhdGggUGF0aCB0byBhcnJheS4KICAgICAgICAgKiBAcmV0dXJuIHsqfSBJdGVtIHRoYXQgd2FzIHJlbW92ZWQuCiAgICAgICAgICogQHB1YmxpYwogICAgICAgICAqLwogICAgICAgIHNoaWZ0KHBhdGgpIHsKICAgICAgICAgIGxldCBpbmZvID0ge3BhdGg6ICcnfTsKICAgICAgICAgIGxldCBhcnJheSA9IC8qKiBAdHlwZSB7QXJyYXl9ICovKGdldCh0aGlzLCBwYXRoLCBpbmZvKSk7CiAgICAgICAgICBsZXQgaGFkTGVuZ3RoID0gQm9vbGVhbihhcnJheS5sZW5ndGgpOwogICAgICAgICAgbGV0IHJldCA9IGFycmF5LnNoaWZ0KCk7CiAgICAgICAgICBpZiAoaGFkTGVuZ3RoKSB7CiAgICAgICAgICAgIG5vdGlmeVNwbGljZSh0aGlzLCBhcnJheSwgaW5mby5wYXRoLCAwLCAwLCBbcmV0XSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmV0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBpdGVtcyBvbnRvIHRoZSBiZWdpbm5pbmcgb2YgdGhlIGFycmF5IGF0IHRoZSBwYXRoIHNwZWNpZmllZC4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBhcmd1bWVudHMgYWZ0ZXIgYHBhdGhgIGFuZCByZXR1cm4gdmFsdWUgbWF0Y2ggdGhhdCBvZgogICAgICAgICAqIGBBcnJheS5wcm90b3R5cGUucHVzaGAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBub3RpZmllcyBvdGhlciBwYXRocyB0byB0aGUgc2FtZSBhcnJheSB0aGF0IGEKICAgICAgICAgKiBzcGxpY2Ugb2NjdXJyZWQgdG8gdGhlIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmcgfCAhQXJyYXk8c3RyaW5nfG51bWJlcj59IHBhdGggUGF0aCB0byBhcnJheS4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IGl0ZW1zIEl0ZW1zIHRvIGluc2VydCBpbmZvIGFycmF5CiAgICAgICAgICogQHJldHVybiB7bnVtYmVyfSBOZXcgbGVuZ3RoIG9mIHRoZSBhcnJheS4KICAgICAgICAgKiBAcHVibGljCiAgICAgICAgICovCiAgICAgICAgdW5zaGlmdChwYXRoLCAuLi5pdGVtcykgewogICAgICAgICAgbGV0IGluZm8gPSB7cGF0aDogJyd9OwogICAgICAgICAgbGV0IGFycmF5ID0gLyoqIEB0eXBlIHtBcnJheX0gKi8oZ2V0KHRoaXMsIHBhdGgsIGluZm8pKTsKICAgICAgICAgIGxldCByZXQgPSBhcnJheS51bnNoaWZ0KC4uLml0ZW1zKTsKICAgICAgICAgIGlmIChpdGVtcy5sZW5ndGgpIHsKICAgICAgICAgICAgbm90aWZ5U3BsaWNlKHRoaXMsIGFycmF5LCBpbmZvLnBhdGgsIDAsIGl0ZW1zLmxlbmd0aCwgW10pOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJldDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE5vdGlmeSB0aGF0IGEgcGF0aCBoYXMgY2hhbmdlZC4KICAgICAgICAgKgogICAgICAgICAqIEV4YW1wbGU6CiAgICAgICAgICoKICAgICAgICAgKiAgICAgdGhpcy5pdGVtLnVzZXIubmFtZSA9ICdCb2InOwogICAgICAgICAqICAgICB0aGlzLm5vdGlmeVBhdGgoJ2l0ZW0udXNlci5uYW1lJyk7CiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBQYXRoIHRoYXQgc2hvdWxkIGJlIG5vdGlmaWVkLgogICAgICAgICAqIEBwYXJhbSB7Kj19IHZhbHVlIFZhbHVlIGF0IHRoZSBwYXRoIChvcHRpb25hbCkuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHVibGljCiAgICAgICAgICovCiAgICAgICAgbm90aWZ5UGF0aChwYXRoLCB2YWx1ZSkgewogICAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd9ICovCiAgICAgICAgICBsZXQgcHJvcFBhdGg7CiAgICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA9PSAxKSB7CiAgICAgICAgICAgIC8vIEdldCB2YWx1ZSBpZiBub3Qgc3VwcGxpZWQKICAgICAgICAgICAgbGV0IGluZm8gPSB7cGF0aDogJyd9OwogICAgICAgICAgICB2YWx1ZSA9IGdldCh0aGlzLCBwYXRoLCBpbmZvKTsKICAgICAgICAgICAgcHJvcFBhdGggPSBpbmZvLnBhdGg7CiAgICAgICAgICB9IGVsc2UgaWYgKEFycmF5LmlzQXJyYXkocGF0aCkpIHsKICAgICAgICAgICAgLy8gTm9ybWFsaXplIHBhdGggaWYgbmVlZGVkCiAgICAgICAgICAgIHByb3BQYXRoID0gbm9ybWFsaXplKHBhdGgpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcHJvcFBhdGggPSAvKiogQHR5cGV7c3RyaW5nfSAqLyhwYXRoKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh0aGlzLl9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgocHJvcFBhdGgsIHZhbHVlLCB0cnVlLCB0cnVlKSkgewogICAgICAgICAgICB0aGlzLl9pbnZhbGlkYXRlUHJvcGVydGllcygpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRXF1aXZhbGVudCB0byBzdGF0aWMgYGNyZWF0ZVJlYWRPbmx5UHJvcGVydHlgIEFQSSBidXQgY2FuIGJlIGNhbGxlZCBvbgogICAgICAgICAqIGFuIGluc3RhbmNlIHRvIGFkZCBlZmZlY3RzIGF0IHJ1bnRpbWUuICBTZWUgdGhhdCBtZXRob2QgZm9yCiAgICAgICAgICogZnVsbCBBUEkgZG9jcy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gcHJvdGVjdGVkU2V0dGVyIENyZWF0ZXMgYSBjdXN0b20gcHJvdGVjdGVkIHNldHRlcgogICAgICAgICAqICAgd2hlbiBgdHJ1ZWAuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2NyZWF0ZVJlYWRPbmx5UHJvcGVydHkocHJvcGVydHksIHByb3RlY3RlZFNldHRlcikgewogICAgICAgICAgdGhpcy5fYWRkUHJvcGVydHlFZmZlY3QocHJvcGVydHksIFRZUEVTLlJFQURfT05MWSk7CiAgICAgICAgICBpZiAocHJvdGVjdGVkU2V0dGVyKSB7CiAgICAgICAgICAgIHRoaXNbJ19zZXQnICsgdXBwZXIocHJvcGVydHkpXSA9IC8qKiBAdGhpcyB7UHJvcGVydHlFZmZlY3RzfSAqL2Z1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICAgICAgdGhpcy5fc2V0UHJvcGVydHkocHJvcGVydHksIHZhbHVlKTsKICAgICAgICAgICAgfTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEVxdWl2YWxlbnQgdG8gc3RhdGljIGBjcmVhdGVQcm9wZXJ0eU9ic2VydmVyYCBBUEkgYnV0IGNhbiBiZSBjYWxsZWQgb24KICAgICAgICAgKiBhbiBpbnN0YW5jZSB0byBhZGQgZWZmZWN0cyBhdCBydW50aW1lLiAgU2VlIHRoYXQgbWV0aG9kIGZvcgogICAgICAgICAqIGZ1bGwgQVBJIGRvY3MuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfGZ1bmN0aW9uKCosKil9IG1ldGhvZCBGdW5jdGlvbiBvciBuYW1lIG9mIG9ic2VydmVyIG1ldGhvZAogICAgICAgICAqICAgICB0byBjYWxsCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gZHluYW1pY0ZuIFdoZXRoZXIgdGhlIG1ldGhvZCBuYW1lIHNob3VsZCBiZSBpbmNsdWRlZCBhcwogICAgICAgICAqICAgYSBkZXBlbmRlbmN5IHRvIHRoZSBlZmZlY3QuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2NyZWF0ZVByb3BlcnR5T2JzZXJ2ZXIocHJvcGVydHksIG1ldGhvZCwgZHluYW1pY0ZuKSB7CiAgICAgICAgICBsZXQgaW5mbyA9IHsgcHJvcGVydHksIG1ldGhvZCwgZHluYW1pY0ZuOiBCb29sZWFuKGR5bmFtaWNGbikgfTsKICAgICAgICAgIHRoaXMuX2FkZFByb3BlcnR5RWZmZWN0KHByb3BlcnR5LCBUWVBFUy5PQlNFUlZFLCB7CiAgICAgICAgICAgIGZuOiBydW5PYnNlcnZlckVmZmVjdCwgaW5mbywgdHJpZ2dlcjoge25hbWU6IHByb3BlcnR5fQogICAgICAgICAgfSk7CiAgICAgICAgICBpZiAoZHluYW1pY0ZuKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZFByb3BlcnR5RWZmZWN0KC8qKiBAdHlwZSB7c3RyaW5nfSAqLyhtZXRob2QpLCBUWVBFUy5PQlNFUlZFLCB7CiAgICAgICAgICAgICAgZm46IHJ1bk9ic2VydmVyRWZmZWN0LCBpbmZvLCB0cmlnZ2VyOiB7bmFtZTogbWV0aG9kfQogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEVxdWl2YWxlbnQgdG8gc3RhdGljIGBjcmVhdGVNZXRob2RPYnNlcnZlcmAgQVBJIGJ1dCBjYW4gYmUgY2FsbGVkIG9uCiAgICAgICAgICogYW4gaW5zdGFuY2UgdG8gYWRkIGVmZmVjdHMgYXQgcnVudGltZS4gIFNlZSB0aGF0IG1ldGhvZCBmb3IKICAgICAgICAgKiBmdWxsIEFQSSBkb2NzLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGV4cHJlc3Npb24gTWV0aG9kIGV4cHJlc3Npb24KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW58T2JqZWN0PX0gZHluYW1pY0ZuIEJvb2xlYW4gb3Igb2JqZWN0IG1hcCBpbmRpY2F0aW5nCiAgICAgICAgICogICB3aGV0aGVyIG1ldGhvZCBuYW1lcyBzaG91bGQgYmUgaW5jbHVkZWQgYXMgYSBkZXBlbmRlbmN5IHRvIHRoZSBlZmZlY3QuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2NyZWF0ZU1ldGhvZE9ic2VydmVyKGV4cHJlc3Npb24sIGR5bmFtaWNGbikgewogICAgICAgICAgbGV0IHNpZyA9IHBhcnNlTWV0aG9kKGV4cHJlc3Npb24pOwogICAgICAgICAgaWYgKCFzaWcpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJNYWxmb3JtZWQgb2JzZXJ2ZXIgZXhwcmVzc2lvbiAnIiArIGV4cHJlc3Npb24gKyAiJyIpOwogICAgICAgICAgfQogICAgICAgICAgY3JlYXRlTWV0aG9kRWZmZWN0KHRoaXMsIHNpZywgVFlQRVMuT0JTRVJWRSwgcnVuTWV0aG9kRWZmZWN0LCBudWxsLCBkeW5hbWljRm4pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRXF1aXZhbGVudCB0byBzdGF0aWMgYGNyZWF0ZU5vdGlmeWluZ1Byb3BlcnR5YCBBUEkgYnV0IGNhbiBiZSBjYWxsZWQgb24KICAgICAgICAgKiBhbiBpbnN0YW5jZSB0byBhZGQgZWZmZWN0cyBhdCBydW50aW1lLiAgU2VlIHRoYXQgbWV0aG9kIGZvcgogICAgICAgICAqIGZ1bGwgQVBJIGRvY3MuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9jcmVhdGVOb3RpZnlpbmdQcm9wZXJ0eShwcm9wZXJ0eSkgewogICAgICAgICAgdGhpcy5fYWRkUHJvcGVydHlFZmZlY3QocHJvcGVydHksIFRZUEVTLk5PVElGWSwgewogICAgICAgICAgICBmbjogcnVuTm90aWZ5RWZmZWN0LAogICAgICAgICAgICBpbmZvOiB7CiAgICAgICAgICAgICAgZXZlbnROYW1lOiBjYW1lbFRvRGFzaENhc2UocHJvcGVydHkpICsgJy1jaGFuZ2VkJywKICAgICAgICAgICAgICBwcm9wZXJ0eTogcHJvcGVydHkKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBFcXVpdmFsZW50IHRvIHN0YXRpYyBgY3JlYXRlUmVmbGVjdGVkUHJvcGVydHlgIEFQSSBidXQgY2FuIGJlIGNhbGxlZCBvbgogICAgICAgICAqIGFuIGluc3RhbmNlIHRvIGFkZCBlZmZlY3RzIGF0IHJ1bnRpbWUuICBTZWUgdGhhdCBtZXRob2QgZm9yCiAgICAgICAgICogZnVsbCBBUEkgZG9jcy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30gZ28vbWlzc2luZ2ZucHJvcHMKICAgICAgICAgKi8KICAgICAgICBfY3JlYXRlUmVmbGVjdGVkUHJvcGVydHkocHJvcGVydHkpIHsKICAgICAgICAgIGxldCBhdHRyID0gdGhpcy5jb25zdHJ1Y3Rvci5hdHRyaWJ1dGVOYW1lRm9yUHJvcGVydHkocHJvcGVydHkpOwogICAgICAgICAgaWYgKGF0dHJbMF0gPT09ICctJykgewogICAgICAgICAgICBjb25zb2xlLndhcm4oJ1Byb3BlcnR5ICcgKyBwcm9wZXJ0eSArICcgY2Fubm90IGJlIHJlZmxlY3RlZCB0byBhdHRyaWJ1dGUgJyArCiAgICAgICAgICAgICAgYXR0ciArICcgYmVjYXVzZSAiLSIgaXMgbm90IGEgdmFsaWQgc3RhcnRpbmcgYXR0cmlidXRlIG5hbWUuIFVzZSBhIGxvd2VyY2FzZSBmaXJzdCBsZXR0ZXIgZm9yIHRoZSBwcm9wZXJ0eSBpbnN0ZWFkLicpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fYWRkUHJvcGVydHlFZmZlY3QocHJvcGVydHksIFRZUEVTLlJFRkxFQ1QsIHsKICAgICAgICAgICAgICBmbjogcnVuUmVmbGVjdEVmZmVjdCwKICAgICAgICAgICAgICBpbmZvOiB7CiAgICAgICAgICAgICAgICBhdHRyTmFtZTogYXR0cgogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBFcXVpdmFsZW50IHRvIHN0YXRpYyBgY3JlYXRlQ29tcHV0ZWRQcm9wZXJ0eWAgQVBJIGJ1dCBjYW4gYmUgY2FsbGVkIG9uCiAgICAgICAgICogYW4gaW5zdGFuY2UgdG8gYWRkIGVmZmVjdHMgYXQgcnVudGltZS4gIFNlZSB0aGF0IG1ldGhvZCBmb3IKICAgICAgICAgKiBmdWxsIEFQSSBkb2NzLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IE5hbWUgb2YgY29tcHV0ZWQgcHJvcGVydHkgdG8gc2V0CiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGV4cHJlc3Npb24gTWV0aG9kIGV4cHJlc3Npb24KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW58T2JqZWN0PX0gZHluYW1pY0ZuIEJvb2xlYW4gb3Igb2JqZWN0IG1hcCBpbmRpY2F0aW5nCiAgICAgICAgICogICB3aGV0aGVyIG1ldGhvZCBuYW1lcyBzaG91bGQgYmUgaW5jbHVkZWQgYXMgYSBkZXBlbmRlbmN5IHRvIHRoZSBlZmZlY3QuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX2NyZWF0ZUNvbXB1dGVkUHJvcGVydHkocHJvcGVydHksIGV4cHJlc3Npb24sIGR5bmFtaWNGbikgewogICAgICAgICAgbGV0IHNpZyA9IHBhcnNlTWV0aG9kKGV4cHJlc3Npb24pOwogICAgICAgICAgaWYgKCFzaWcpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJNYWxmb3JtZWQgY29tcHV0ZWQgZXhwcmVzc2lvbiAnIiArIGV4cHJlc3Npb24gKyAiJyIpOwogICAgICAgICAgfQogICAgICAgICAgY29uc3QgaW5mbyA9IGNyZWF0ZU1ldGhvZEVmZmVjdCh0aGlzLCBzaWcsIFRZUEVTLkNPTVBVVEUsIHJ1bkNvbXB1dGVkRWZmZWN0LCBwcm9wZXJ0eSwgZHluYW1pY0ZuKTsKICAgICAgICAgIC8vIEVmZmVjdHMgYXJlIG5vcm1hbGx5IHN0b3JlZCBhcyBtYXAgb2YgZGVwZW5kZW5jeS0+ZWZmZWN0LCBidXQgZm9yCiAgICAgICAgICAvLyBvcmRlcmVkIGNvbXB1dGF0aW9uLCB3ZSBhbHNvIG5lZWQgdHJlZSBvZiBjb21wdXRlZFByb3AtPmRlcGVuZGVuY2llcwogICAgICAgICAgZW5zdXJlT3duRWZmZWN0TWFwKHRoaXMsIENPTVBVVEVfSU5GTylbcHJvcGVydHldID0gaW5mbzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEdhdGhlciB0aGUgYXJndW1lbnQgdmFsdWVzIGZvciBhIG1ldGhvZCBzcGVjaWZpZWQgaW4gdGhlIHByb3ZpZGVkIGFycmF5CiAgICAgICAgICogb2YgYXJndW1lbnQgbWV0YWRhdGEuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgYHBhdGhgIGFuZCBgdmFsdWVgIGFyZ3VtZW50cyBhcmUgdXNlZCB0byBmaWxsIGluIHdpbGRjYXJkIGRlc2NyaXB0b3IKICAgICAgICAgKiB3aGVuIHRoZSBtZXRob2QgaXMgYmVpbmcgY2FsbGVkIGFzIGEgcmVzdWx0IG9mIGEgcGF0aCBub3RpZmljYXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFBcnJheTwhTWV0aG9kQXJnPn0gYXJncyBBcnJheSBvZiBhcmd1bWVudCBtZXRhZGF0YQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFByb3BlcnR5L3BhdGggbmFtZSB0aGF0IHRyaWdnZXJlZCB0aGUgbWV0aG9kIGVmZmVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgY3VycmVudCBwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgICAgICogQHJldHVybiB7IUFycmF5PCo+fSBBcnJheSBvZiBhcmd1bWVudCB2YWx1ZXMKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIF9tYXJzaGFsQXJncyhhcmdzLCBwYXRoLCBwcm9wcykgewogICAgICAgICAgY29uc3QgZGF0YSA9IHRoaXMuX19kYXRhOwogICAgICAgICAgY29uc3QgdmFsdWVzID0gW107CiAgICAgICAgICBmb3IgKGxldCBpPTAsIGw9YXJncy5sZW5ndGg7IGk8bDsgaSsrKSB7CiAgICAgICAgICAgIGxldCB7bmFtZSwgc3RydWN0dXJlZCwgd2lsZGNhcmQsIHZhbHVlLCBsaXRlcmFsfSA9IGFyZ3NbaV07CiAgICAgICAgICAgIGlmICghbGl0ZXJhbCkgewogICAgICAgICAgICAgIGlmICh3aWxkY2FyZCkgewogICAgICAgICAgICAgICAgY29uc3QgbWF0Y2hlcyA9IGlzRGVzY2VuZGFudChuYW1lLCBwYXRoKTsKICAgICAgICAgICAgICAgIGNvbnN0IHBhdGhWYWx1ZSA9IGdldEFyZ1ZhbHVlKGRhdGEsIHByb3BzLCBtYXRjaGVzID8gcGF0aCA6IG5hbWUpOwogICAgICAgICAgICAgICAgdmFsdWUgPSB7CiAgICAgICAgICAgICAgICAgIHBhdGg6IG1hdGNoZXMgPyBwYXRoIDogbmFtZSwKICAgICAgICAgICAgICAgICAgdmFsdWU6IHBhdGhWYWx1ZSwKICAgICAgICAgICAgICAgICAgYmFzZTogbWF0Y2hlcyA/IGdldChkYXRhLCBuYW1lKSA6IHBhdGhWYWx1ZQogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgdmFsdWUgPSBzdHJ1Y3R1cmVkID8gZ2V0QXJnVmFsdWUoZGF0YSwgcHJvcHMsIG5hbWUpIDogZGF0YVtuYW1lXTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gV2hlbiB0aGUgYGxlZ2FjeVVuZGVmaW5lZGAgZmxhZyBpcyBlbmFibGVkLCBwYXNzIGEgbm8tb3AgdmFsdWUKICAgICAgICAgICAgLy8gc28gdGhhdCB0aGUgb2JzZXJ2ZXIsIGNvbXB1dGVkIHByb3BlcnR5LCBvciBjb21wb3VuZCBiaW5kaW5nIGlzIGFib3J0ZWQuCiAgICAgICAgICAgIGlmIChsZWdhY3lVbmRlZmluZWQgJiYgIXRoaXMuX292ZXJyaWRlTGVnYWN5VW5kZWZpbmVkICYmIHZhbHVlID09PSB1bmRlZmluZWQgJiYgYXJncy5sZW5ndGggPiAxKSB7CiAgICAgICAgICAgICAgcmV0dXJuIE5PT1A7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFsdWVzW2ldID0gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdmFsdWVzOwogICAgICAgIH0KCiAgICAgICAgLy8gLS0gc3RhdGljIGNsYXNzIG1ldGhvZHMgLS0tLS0tLS0tLS0tCgogICAgICAgIC8qKgogICAgICAgICAqIEVuc3VyZXMgYW4gYWNjZXNzb3IgZXhpc3RzIGZvciB0aGUgc3BlY2lmaWVkIHByb3BlcnR5LCBhbmQgYWRkcwogICAgICAgICAqIHRvIGEgbGlzdCBvZiAicHJvcGVydHkgZWZmZWN0cyIgdGhhdCB3aWxsIHJ1biB3aGVuIHRoZSBhY2Nlc3NvciBmb3IKICAgICAgICAgKiB0aGUgc3BlY2lmaWVkIHByb3BlcnR5IGlzIHNldC4gIEVmZmVjdHMgYXJlIGdyb3VwZWQgYnkgInR5cGUiLCB3aGljaAogICAgICAgICAqIHJvdWdobHkgY29ycmVzcG9uZHMgdG8gYSBwaGFzZSBpbiBlZmZlY3QgcHJvY2Vzc2luZy4gIFRoZSBlZmZlY3QKICAgICAgICAgKiBtZXRhZGF0YSBzaG91bGQgYmUgaW4gdGhlIGZvbGxvd2luZyBmb3JtOgogICAgICAgICAqCiAgICAgICAgICogICAgIHsKICAgICAgICAgKiAgICAgICBmbjogZWZmZWN0RnVuY3Rpb24sIC8vIFJlZmVyZW5jZSB0byBmdW5jdGlvbiB0byBjYWxsIHRvIHBlcmZvcm0gZWZmZWN0CiAgICAgICAgICogICAgICAgaW5mbzogeyAuLi4gfSAgICAgICAvLyBFZmZlY3QgbWV0YWRhdGEgcGFzc2VkIHRvIGZ1bmN0aW9uCiAgICAgICAgICogICAgICAgdHJpZ2dlcjogeyAgICAgICAgICAvLyBPcHRpb25hbCB0cmlnZ2VyaW5nIG1ldGFkYXRhOyBpZiBub3QgcHJvdmlkZWQKICAgICAgICAgKiAgICAgICAgIG5hbWU6IHN0cmluZyAgICAgIC8vIHRoZSBwcm9wZXJ0eSBpcyB0cmVhdGVkIGFzIGEgd2lsZGNhcmQKICAgICAgICAgKiAgICAgICAgIHN0cnVjdHVyZWQ6IGJvb2xlYW4KICAgICAgICAgKiAgICAgICAgIHdpbGRjYXJkOiBib29sZWFuCiAgICAgICAgICogICAgICAgfQogICAgICAgICAqICAgICB9CiAgICAgICAgICoKICAgICAgICAgKiBFZmZlY3RzIGFyZSBjYWxsZWQgZnJvbSBgX3Byb3BlcnRpZXNDaGFuZ2VkYCBpbiB0aGUgZm9sbG93aW5nIG9yZGVyIGJ5CiAgICAgICAgICogdHlwZToKICAgICAgICAgKgogICAgICAgICAqIDEuIENPTVBVVEUKICAgICAgICAgKiAyLiBQUk9QQUdBVEUKICAgICAgICAgKiAzLiBSRUZMRUNUCiAgICAgICAgICogNC4gT0JTRVJWRQogICAgICAgICAqIDUuIE5PVElGWQogICAgICAgICAqCiAgICAgICAgICogRWZmZWN0IGZ1bmN0aW9ucyBhcmUgY2FsbGVkIHdpdGggdGhlIGZvbGxvd2luZyBzaWduYXR1cmU6CiAgICAgICAgICoKICAgICAgICAgKiAgICAgZWZmZWN0RnVuY3Rpb24oaW5zdCwgcGF0aCwgcHJvcHMsIG9sZFByb3BzLCBpbmZvLCBoYXNQYXRocykKICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSB0aGF0IHNob3VsZCB0cmlnZ2VyIHRoZSBlZmZlY3QKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdHlwZSBFZmZlY3QgdHlwZSwgZnJvbSB0aGlzLlBST1BFUlRZX0VGRkVDVF9UWVBFUwogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gZWZmZWN0IEVmZmVjdCBtZXRhZGF0YSBvYmplY3QKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBhZGRQcm9wZXJ0eUVmZmVjdChwcm9wZXJ0eSwgdHlwZSwgZWZmZWN0KSB7CiAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fYWRkUHJvcGVydHlFZmZlY3QocHJvcGVydHksIHR5cGUsIGVmZmVjdCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2luZ2xlLXByb3BlcnR5IG9ic2VydmVyIGZvciB0aGUgZ2l2ZW4gcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfGZ1bmN0aW9uKCosKil9IG1ldGhvZCBGdW5jdGlvbiBvciBuYW1lIG9mIG9ic2VydmVyIG1ldGhvZCB0byBjYWxsCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gZHluYW1pY0ZuIFdoZXRoZXIgdGhlIG1ldGhvZCBuYW1lIHNob3VsZCBiZSBpbmNsdWRlZCBhcwogICAgICAgICAqICAgYSBkZXBlbmRlbmN5IHRvIHRoZSBlZmZlY3QuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgY3JlYXRlUHJvcGVydHlPYnNlcnZlcihwcm9wZXJ0eSwgbWV0aG9kLCBkeW5hbWljRm4pIHsKICAgICAgICAgIHRoaXMucHJvdG90eXBlLl9jcmVhdGVQcm9wZXJ0eU9ic2VydmVyKHByb3BlcnR5LCBtZXRob2QsIGR5bmFtaWNGbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgbXVsdGktcHJvcGVydHkgIm1ldGhvZCBvYnNlcnZlciIgYmFzZWQgb24gdGhlIHByb3ZpZGVkCiAgICAgICAgICogZXhwcmVzc2lvbiwgd2hpY2ggc2hvdWxkIGJlIGEgc3RyaW5nIGluIHRoZSBmb3JtIG9mIGEgbm9ybWFsIEphdmFTY3JpcHQKICAgICAgICAgKiBmdW5jdGlvbiBzaWduYXR1cmU6IGAnbWV0aG9kTmFtZShhcmcxLCBbLi4uLCBhcmduXSknYC4gIEVhY2ggYXJndW1lbnQKICAgICAgICAgKiBzaG91bGQgY29ycmVzcG9uZCB0byBhIHByb3BlcnR5IG9yIHBhdGggaW4gdGhlIGNvbnRleHQgb2YgdGhpcwogICAgICAgICAqIHByb3RvdHlwZSAob3IgaW5zdGFuY2UpLCBvciBtYXkgYmUgYSBsaXRlcmFsIHN0cmluZyBvciBudW1iZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXhwcmVzc2lvbiBNZXRob2QgZXhwcmVzc2lvbgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbnxPYmplY3Q9fSBkeW5hbWljRm4gQm9vbGVhbiBvciBvYmplY3QgbWFwIGluZGljYXRpbmcKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqICAgd2hldGhlciBtZXRob2QgbmFtZXMgc2hvdWxkIGJlIGluY2x1ZGVkIGFzIGEgZGVwZW5kZW5jeSB0byB0aGUgZWZmZWN0LgogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBjcmVhdGVNZXRob2RPYnNlcnZlcihleHByZXNzaW9uLCBkeW5hbWljRm4pIHsKICAgICAgICAgIHRoaXMucHJvdG90eXBlLl9jcmVhdGVNZXRob2RPYnNlcnZlcihleHByZXNzaW9uLCBkeW5hbWljRm4pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2F1c2VzIHRoZSBzZXR0ZXIgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eSB0byBkaXNwYXRjaCBgPHByb3BlcnR5Pi1jaGFuZ2VkYAogICAgICAgICAqIGV2ZW50cyB0byBub3RpZnkgb2YgY2hhbmdlcyB0byB0aGUgcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIGNyZWF0ZU5vdGlmeWluZ1Byb3BlcnR5KHByb3BlcnR5KSB7CiAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fY3JlYXRlTm90aWZ5aW5nUHJvcGVydHkocHJvcGVydHkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIHJlYWQtb25seSBhY2Nlc3NvciBmb3IgdGhlIGdpdmVuIHByb3BlcnR5LgogICAgICAgICAqCiAgICAgICAgICogVG8gc2V0IHRoZSBwcm9wZXJ0eSwgdXNlIHRoZSBwcm90ZWN0ZWQgYF9zZXRQcm9wZXJ0eWAgQVBJLgogICAgICAgICAqIFRvIGNyZWF0ZSBhIGN1c3RvbSBwcm90ZWN0ZWQgc2V0dGVyIChlLmcuIGBfc2V0TXlQcm9wKClgIGZvcgogICAgICAgICAqIHByb3BlcnR5IGBteVByb3BgKSwgcGFzcyBgdHJ1ZWAgZm9yIGBwcm90ZWN0ZWRTZXR0ZXJgLgogICAgICAgICAqCiAgICAgICAgICogTm90ZSwgaWYgdGhlIHByb3BlcnR5IHdpbGwgaGF2ZSBvdGhlciBwcm9wZXJ0eSBlZmZlY3RzLCB0aGlzIG1ldGhvZAogICAgICAgICAqIHNob3VsZCBiZSBjYWxsZWQgZmlyc3QsIGJlZm9yZSBhZGRpbmcgb3RoZXIgZWZmZWN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gcHJvdGVjdGVkU2V0dGVyIENyZWF0ZXMgYSBjdXN0b20gcHJvdGVjdGVkIHNldHRlcgogICAgICAgICAqICAgd2hlbiBgdHJ1ZWAuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgY3JlYXRlUmVhZE9ubHlQcm9wZXJ0eShwcm9wZXJ0eSwgcHJvdGVjdGVkU2V0dGVyKSB7CiAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fY3JlYXRlUmVhZE9ubHlQcm9wZXJ0eShwcm9wZXJ0eSwgcHJvdGVjdGVkU2V0dGVyKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhdXNlcyB0aGUgc2V0dGVyIGZvciB0aGUgZ2l2ZW4gcHJvcGVydHkgdG8gcmVmbGVjdCB0aGUgcHJvcGVydHkgdmFsdWUKICAgICAgICAgKiB0byBhIChkYXNoLWNhc2VkKSBhdHRyaWJ1dGUgb2YgdGhlIHNhbWUgbmFtZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgY3JlYXRlUmVmbGVjdGVkUHJvcGVydHkocHJvcGVydHkpIHsKICAgICAgICAgIHRoaXMucHJvdG90eXBlLl9jcmVhdGVSZWZsZWN0ZWRQcm9wZXJ0eShwcm9wZXJ0eSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY29tcHV0ZWQgcHJvcGVydHkgd2hvc2UgdmFsdWUgaXMgc2V0IHRvIHRoZSByZXN1bHQgb2YgdGhlCiAgICAgICAgICogbWV0aG9kIGRlc2NyaWJlZCBieSB0aGUgZ2l2ZW4gYGV4cHJlc3Npb25gIGVhY2ggdGltZSBvbmUgb3IgbW9yZQogICAgICAgICAqIGFyZ3VtZW50cyB0byB0aGUgbWV0aG9kIGNoYW5nZXMuICBUaGUgZXhwcmVzc2lvbiBzaG91bGQgYmUgYSBzdHJpbmcKICAgICAgICAgKiBpbiB0aGUgZm9ybSBvZiBhIG5vcm1hbCBKYXZhU2NyaXB0IGZ1bmN0aW9uIHNpZ25hdHVyZToKICAgICAgICAgKiBgJ21ldGhvZE5hbWUoYXJnMSwgWy4uLiwgYXJnbl0pJ2AKICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIGNvbXB1dGVkIHByb3BlcnR5IHRvIHNldAogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBleHByZXNzaW9uIE1ldGhvZCBleHByZXNzaW9uCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufE9iamVjdD19IGR5bmFtaWNGbiBCb29sZWFuIG9yIG9iamVjdCBtYXAgaW5kaWNhdGluZyB3aGV0aGVyCiAgICAgICAgICogICBtZXRob2QgbmFtZXMgc2hvdWxkIGJlIGluY2x1ZGVkIGFzIGEgZGVwZW5kZW5jeSB0byB0aGUgZWZmZWN0LgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIGNyZWF0ZUNvbXB1dGVkUHJvcGVydHkocHJvcGVydHksIGV4cHJlc3Npb24sIGR5bmFtaWNGbikgewogICAgICAgICAgdGhpcy5wcm90b3R5cGUuX2NyZWF0ZUNvbXB1dGVkUHJvcGVydHkocHJvcGVydHksIGV4cHJlc3Npb24sIGR5bmFtaWNGbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQYXJzZXMgdGhlIHByb3ZpZGVkIHRlbXBsYXRlIHRvIGVuc3VyZSBiaW5kaW5nIGVmZmVjdHMgYXJlIGNyZWF0ZWQKICAgICAgICAgKiBmb3IgdGhlbSwgYW5kIHRoZW4gZW5zdXJlcyBwcm9wZXJ0eSBhY2Nlc3NvcnMgYXJlIGNyZWF0ZWQgZm9yIGFueQogICAgICAgICAqIGRlcGVuZGVudCBwcm9wZXJ0aWVzIGluIHRoZSB0ZW1wbGF0ZS4gIEJpbmRpbmcgZWZmZWN0cyBmb3IgYm91bmQKICAgICAgICAgKiB0ZW1wbGF0ZXMgYXJlIHN0b3JlZCBpbiBhIGxpbmtlZCBsaXN0IG9uIHRoZSBpbnN0YW5jZSBzbyB0aGF0CiAgICAgICAgICogdGVtcGxhdGVzIGNhbiBiZSBlZmZpY2llbnRseSBzdGFtcGVkIGFuZCB1bnN0YW1wZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZSBUZW1wbGF0ZSBjb250YWluaW5nIGJpbmRpbmcKICAgICAgICAgKiAgIGJpbmRpbmdzCiAgICAgICAgICogQHJldHVybiB7IVRlbXBsYXRlSW5mb30gVGVtcGxhdGUgbWV0YWRhdGEgb2JqZWN0CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIGJpbmRUZW1wbGF0ZSh0ZW1wbGF0ZSkgewogICAgICAgICAgcmV0dXJuIHRoaXMucHJvdG90eXBlLl9iaW5kVGVtcGxhdGUodGVtcGxhdGUpOwogICAgICAgIH0KCiAgICAgICAgLy8gLS0gYmluZGluZyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCgogICAgICAgIC8qCiAgICAgICAgICogT3ZlcnZpZXcgb2YgYmluZGluZyBmbG93OgogICAgICAgICAqCiAgICAgICAgICogRHVyaW5nIGZpbmFsaXphdGlvbiAoYGluc3RhbmNlQmluZGluZz09ZmFsc2VgLCBgd2FzUHJlQm91bmQ9PWZhbHNlYCk6CiAgICAgICAgICogIGBfYmluZFRlbXBsYXRlKHQsIGZhbHNlKWAgY2FsbGVkIGRpcmVjdGx5IGR1cmluZyBmaW5hbGl6YXRpb24gLSBwYXJzZXMKICAgICAgICAgKiAgdGhlIHRlbXBsYXRlIChmb3IgdGhlIGZpcnN0IHRpbWUpLCBhbmQgdGhlbiBhc3NpZ25zIHRoYXQgX3Byb3RvdHlwaWNhbF8KICAgICAgICAgKiAgdGVtcGxhdGUgaW5mbyB0byBgX19wcmVib3VuZFRlbXBsYXRlSW5mb2AgX29uIHRoZSBwcm90b3R5cGVfOyBub3RlIGluCiAgICAgICAgICogIHRoaXMgY2FzZSBgd2FzUHJlQm91bmRgIGlzIGZhbHNlOyB0aGlzIGlzIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGJpbmRpbmcKICAgICAgICAgKiAgaXQsIHRodXMgd2UgY3JlYXRlIGFjY2Vzc29ycy4KICAgICAgICAgKgogICAgICAgICAqIER1cmluZyBmaXJzdCBzdGFtcGluZyAoYGluc3RhbmNlQmluZGluZz09dHJ1ZWAsIGB3YXNQcmVCb3VuZD09dHJ1ZWApOgogICAgICAgICAqICAgYF9zdGFtcFRlbXBsYXRlYCBjYWxscyBgX2JpbmRUZW1wbGF0ZSh0LCB0cnVlKWA6IHRoZSBgdGVtcGxhdGVJbmZvYAogICAgICAgICAqICAgcmV0dXJuZWQgbWF0Y2hlcyB0aGUgcHJlYm91bmQgb25lLCBhbmQgc28gdGhpcyBpcyBgd2FzUHJlQm91bmQgPT0gdHJ1ZWAKICAgICAgICAgKiAgIHN0YXRlOyB0aHVzIHdlIF9za2lwXyBjcmVhdGluZyBhY2Nlc3NvcnMsIGJ1dCBfZG9fIGNyZWF0ZSBhbiBpbnN0YW5jZQogICAgICAgICAqICAgb2YgdGhlIHRlbXBsYXRlIGluZm8gdG8gc2VydmUgYXMgdGhlIHN0YXJ0IG9mIG91ciBsaW5rZWQgbGlzdCAobmVlZHMgdG8KICAgICAgICAgKiAgIGJlIGFuIGluc3RhbmNlLCBub3QgdGhlIHByb3RvdHlwaWNhbCBvbmUsIHNvIHRoYXQgd2UgY2FuIGFkZCBgbm9kZUxpc3RgCiAgICAgICAgICogICB0byBpdCB0byBjb250YWluIHRoZSBgbm9kZUluZm9gLW9yZGVyZWQgbGlzdCBvZiBpbnN0YW5jZSBub2RlcyBmb3IKICAgICAgICAgKiAgIGJpbmRpbmdzLCBhbmQgc28gd2UgY2FuIGNoYWluIHJ1bnRpbWUtc3RhbXBlZCB0ZW1wbGF0ZSBpbmZvcyBvZmYgb2YKICAgICAgICAgKiAgIGl0KS4gQXQgdGhpcyBwb2ludCwgdGhlIGNhbGwgdG8gYF9zdGFtcFRlbXBsYXRlYCBjYWxscwogICAgICAgICAqICAgYGFwcGx5VGVtcGxhdGVJbmZvYCBmb3IgZWFjaCBuZXN0ZWQgYDx0ZW1wbGF0ZT5gIGZvdW5kIGR1cmluZyBwYXJzaW5nCiAgICAgICAgICogICB0byBoYW5kIHByb3RvdHlwaWNhbCBgX3RlbXBsYXRlSW5mb2AgdG8gdGhlbTsgd2UgYWxzbyBwYXNzIHRoZSBfcGFyZW50XwogICAgICAgICAqICAgYHRlbXBsYXRlSW5mb2AgdG8gdGhlIGA8dGVtcGxhdGU+YCBzbyB0aGF0IHdlIGhhdmUgdGhlIGluc3RhbmNlLXRpbWUKICAgICAgICAgKiAgIHBhcmVudCB0byBsaW5rIHRoZSBgdGVtcGxhdGVJbmZvYCB1bmRlciBpbiB0aGUgY2FzZSBpdCB3YXMKICAgICAgICAgKiAgIHJ1bnRpbWUtc3RhbXBlZC4KICAgICAgICAgKgogICAgICAgICAqIER1cmluZyBzdWJzZXF1ZW50IHJ1bnRpbWUgc3RhbXBpbmcgKGBpbnN0YW5jZUJpbmRpbmc9PXRydWVgLAogICAgICAgICAqICAgYHdhc1ByZUJvdW5kPT1mYWxzZWApOiBgX3N0YW1wVGVtcGxhdGVgIGNhbGxzIGBfYmluZFRlbXBsYXRlKHQsIHRydWUpYAogICAgICAgICAqICAgLSBoZXJlIGB0ZW1wbGF0ZUluZm9gIGlzIGd1YXJhbnRlZWQgdG8gX25vdF8gbWF0Y2ggdGhlIHByZWJvdW5kIG9uZSwKICAgICAgICAgKiAgIGJlY2F1c2UgaXQgd2FzIGVpdGhlciBhIGRpZmZlcmVudCB0ZW1wbGF0ZSBhbHRvZ2V0aGVyLCBvciBldmVuIGlmIGl0CiAgICAgICAgICogICB3YXMgdGhlIHNhbWUgdGVtcGxhdGUsIHRoZSBzdGVwIGFib3ZlIGNyZWF0ZWQgYSBpbnN0YW5jZSBvZiB0aGUgaW5mbzsKICAgICAgICAgKiAgIGluIHRoaXMgY2FzZSBgd2FzUHJlQm91bmQgPT0gZmFsc2VgLCBzbyB3ZSBfZG9fIGNyZWF0ZSBhY2Nlc3NvcnMsIF9hbmRfCiAgICAgICAgICogICBsaW5rIGEgaW5zdGFuY2UgaW50byB0aGUgbGlua2VkIGxpc3QuCiAgICAgICAgICovCgogICAgICAgIC8qKgogICAgICAgICAqIEVxdWl2YWxlbnQgdG8gc3RhdGljIGBiaW5kVGVtcGxhdGVgIEFQSSBidXQgY2FuIGJlIGNhbGxlZCBvbiBhbiBpbnN0YW5jZQogICAgICAgICAqIHRvIGFkZCBlZmZlY3RzIGF0IHJ1bnRpbWUuICBTZWUgdGhhdCBtZXRob2QgZm9yIGZ1bGwgQVBJIGRvY3MuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBtYXkgYmUgY2FsbGVkIG9uIHRoZSBwcm90b3R5cGUgKGZvciBwcm90b3R5cGljYWwgdGVtcGxhdGUKICAgICAgICAgKiBiaW5kaW5nLCB0byBhdm9pZCBjcmVhdGluZyBhY2Nlc3NvcnMgZXZlcnkgaW5zdGFuY2UpIG9uY2UgcGVyIHByb3RvdHlwZSwKICAgICAgICAgKiBhbmQgd2lsbCBiZSBjYWxsZWQgd2l0aCBgcnVudGltZUJpbmRpbmc6IHRydWVgIGJ5IGBfc3RhbXBUZW1wbGF0ZWAgdG8KICAgICAgICAgKiBjcmVhdGUgYW5kIGxpbmsgYW4gaW5zdGFuY2Ugb2YgdGhlIHRlbXBsYXRlIG1ldGFkYXRhIGFzc29jaWF0ZWQgd2l0aCBhCiAgICAgICAgICogcGFydGljdWxhciBzdGFtcGluZy4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlIFRlbXBsYXRlIGNvbnRhaW5pbmcgYmluZGluZwogICAgICAgICAqIGJpbmRpbmdzCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gaW5zdGFuY2VCaW5kaW5nIFdoZW4gZmFsc2UgKGRlZmF1bHQpLCBwZXJmb3JtcwogICAgICAgICAqICJwcm90b3R5cGljYWwiIGJpbmRpbmcgb2YgdGhlIHRlbXBsYXRlIGFuZCBvdmVyd3JpdGVzIGFueSBwcmV2aW91c2x5CiAgICAgICAgICogYm91bmQgdGVtcGxhdGUgZm9yIHRoZSBjbGFzcy4gV2hlbiB0cnVlIChhcyBwYXNzZWQgZnJvbQogICAgICAgICAqIGBfc3RhbXBUZW1wbGF0ZWApLCB0aGUgdGVtcGxhdGUgaW5mbyBpcyBpbnN0YW5jZWQgYW5kIGxpbmtlZCBpbnRvIHRoZQogICAgICAgICAqIGxpc3Qgb2YgYm91bmQgdGVtcGxhdGVzLgogICAgICAgICAqIEByZXR1cm4geyFUZW1wbGF0ZUluZm99IFRlbXBsYXRlIG1ldGFkYXRhIG9iamVjdDsgZm9yIGBydW50aW1lQmluZGluZ2AsCiAgICAgICAgICogdGhpcyBpcyBhbiBpbnN0YW5jZSBvZiB0aGUgcHJvdG90eXBpY2FsIHRlbXBsYXRlIGluZm8KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30gZ28vbWlzc2luZ2ZucHJvcHMKICAgICAgICAgKi8KICAgICAgICBfYmluZFRlbXBsYXRlKHRlbXBsYXRlLCBpbnN0YW5jZUJpbmRpbmcpIHsKICAgICAgICAgIGxldCB0ZW1wbGF0ZUluZm8gPSB0aGlzLmNvbnN0cnVjdG9yLl9wYXJzZVRlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgICAgIGxldCB3YXNQcmVCb3VuZCA9IHRoaXMuX19wcmVCb3VuZFRlbXBsYXRlSW5mbyA9PSB0ZW1wbGF0ZUluZm87CiAgICAgICAgICAvLyBPcHRpbWl6YXRpb246IHNpbmNlIHRoaXMgaXMgY2FsbGVkIHR3aWNlIGZvciBwcm90by1ib3VuZCB0ZW1wbGF0ZXMsCiAgICAgICAgICAvLyBkb24ndCBhdHRlbXB0IHRvIHJlY3JlYXRlIGFjY2Vzc29ycyBpZiB0aGlzIHRlbXBsYXRlIHdhcyBwcmUtYm91bmQKICAgICAgICAgIGlmICghd2FzUHJlQm91bmQpIHsKICAgICAgICAgICAgZm9yIChsZXQgcHJvcCBpbiB0ZW1wbGF0ZUluZm8ucHJvcGVydHlFZmZlY3RzKSB7CiAgICAgICAgICAgICAgdGhpcy5fY3JlYXRlUHJvcGVydHlBY2Nlc3Nvcihwcm9wKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGluc3RhbmNlQmluZGluZykgewogICAgICAgICAgICAvLyBGb3IgaW5zdGFuY2UtdGltZSBiaW5kaW5nLCBjcmVhdGUgaW5zdGFuY2Ugb2YgdGVtcGxhdGUgbWV0YWRhdGEKICAgICAgICAgICAgLy8gYW5kIGxpbmsgaW50byB0cmVlIG9mIHRlbXBsYXRlcyBpZiBuZWNlc3NhcnkKICAgICAgICAgICAgdGVtcGxhdGVJbmZvID0gLyoqIEB0eXBlIHshVGVtcGxhdGVJbmZvfSAqLyhPYmplY3QuY3JlYXRlKHRlbXBsYXRlSW5mbykpOwogICAgICAgICAgICB0ZW1wbGF0ZUluZm8ud2FzUHJlQm91bmQgPSB3YXNQcmVCb3VuZDsKICAgICAgICAgICAgaWYgKCF0aGlzLl9fdGVtcGxhdGVJbmZvKSB7CiAgICAgICAgICAgICAgLy8gU2V0IHRoZSBpbmZvIHRvIHRoZSByb290IG9mIHRoZSB0cmVlCiAgICAgICAgICAgICAgdGhpcy5fX3RlbXBsYXRlSW5mbyA9IHRlbXBsYXRlSW5mbzsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAvLyBBcHBlbmQgdGhpcyB0ZW1wbGF0ZSBpbmZvIG9udG8gdGhlIGVuZCBvZiBpdHMgcGFyZW50IHRlbXBsYXRlJ3MKICAgICAgICAgICAgICAvLyBsaXN0LCB3aGljaCB3aWxsIGRldGVybWluZSB0aGUgdHJlZSBzdHJ1Y3R1cmUgdmlhIHdoaWNoIHByb3BlcnR5CiAgICAgICAgICAgICAgLy8gZWZmZWN0cyBhcmUgcnVuOyBpZiB0aGlzIHRlbXBsYXRlIHdhcyBub3QgbmVzdGVkIGluIGFub3RoZXIKICAgICAgICAgICAgICAvLyB0ZW1wbGF0ZSwgdXNlIHRoZSByb290IHRlbXBsYXRlICh0aGUgZmlyc3Qgc3RhbXBlZCBvbmUpIGFzIHRoZQogICAgICAgICAgICAgIC8vIHBhcmVudC4gTm90ZSwgYHBhcmVudGAgaXMgdGhlIGB0ZW1wbGF0ZUluZm9gIGluc3RhbmNlIGZvciB0aGlzCiAgICAgICAgICAgICAgLy8gdGVtcGxhdGUncyBwYXJlbnQgKGNvbnRhaW5pbmcpIHRlbXBsYXRlLCB3aGljaCB3YXMgc2V0IHVwIGluCiAgICAgICAgICAgICAgLy8gYGFwcGx5VGVtcGxhdGVJbmZvYC4gIFdoaWxlIGEgZ2l2ZW4gdGVtcGxhdGUncyBgcGFyZW50YCBpcyBzZXQKICAgICAgICAgICAgICAvLyBhcHJpb3JpLCBpdCBpcyBvbmx5IGFkZGVkIHRvIHRoZSBwYXJlbnQncyBjaGlsZCBsaXN0IGF0IHRoZSBwb2ludAogICAgICAgICAgICAgIC8vIHRoYXQgaXQgaXMgYmVpbmcgYm91bmQsIHNpbmNlIGEgdGVtcGxhdGUgbWF5IG9yIG1heSBub3QgZXZlciBiZQogICAgICAgICAgICAgIC8vIHN0YW1wZWQsIGFuZCBtYXkgYmUgc3RhbXBlZCBtb3JlIHRoYW4gb25jZSAoaW4gd2hpY2ggY2FzZSBpbnN0YW5jZXMKICAgICAgICAgICAgICAvLyBvZiB0aGUgdGVtcGxhdGUgaW5mbyB3aWxsIGJlIGluIHRoZSB0cmVlIHVuZGVyIGl0cyBwYXJlbnQgbW9yZSB0aGFuCiAgICAgICAgICAgICAgLy8gb25jZSkuCiAgICAgICAgICAgICAgY29uc3QgcGFyZW50ID0gdGVtcGxhdGUuX3BhcmVudFRlbXBsYXRlSW5mbyB8fCB0aGlzLl9fdGVtcGxhdGVJbmZvOwogICAgICAgICAgICAgIGNvbnN0IHByZXZpb3VzID0gcGFyZW50Lmxhc3RDaGlsZDsKICAgICAgICAgICAgICB0ZW1wbGF0ZUluZm8ucGFyZW50ID0gcGFyZW50OwogICAgICAgICAgICAgIHBhcmVudC5sYXN0Q2hpbGQgPSB0ZW1wbGF0ZUluZm87CiAgICAgICAgICAgICAgdGVtcGxhdGVJbmZvLnByZXZpb3VzU2libGluZyA9IHByZXZpb3VzOwogICAgICAgICAgICAgIGlmIChwcmV2aW91cykgewogICAgICAgICAgICAgICAgcHJldmlvdXMubmV4dFNpYmxpbmcgPSB0ZW1wbGF0ZUluZm87CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHBhcmVudC5maXJzdENoaWxkID0gdGVtcGxhdGVJbmZvOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fX3ByZUJvdW5kVGVtcGxhdGVJbmZvID0gdGVtcGxhdGVJbmZvOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRlbXBsYXRlSW5mbzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBwcm9wZXJ0eSBlZmZlY3QgdG8gdGhlIGdpdmVuIHRlbXBsYXRlIG1ldGFkYXRhLCB3aGljaCBpcyBydW4KICAgICAgICAgKiBhdCB0aGUgInByb3BhZ2F0ZSIgc3RhZ2Ugb2YgYF9wcm9wZXJ0aWVzQ2hhbmdlZGAgd2hlbiB0aGUgdGVtcGxhdGUKICAgICAgICAgKiBoYXMgYmVlbiBib3VuZCB0byB0aGUgZWxlbWVudCB2aWEgYF9iaW5kVGVtcGxhdGVgLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGBlZmZlY3RgIG9iamVjdCBzaG91bGQgbWF0Y2ggdGhlIGZvcm1hdCBpbiBgX2FkZFByb3BlcnR5RWZmZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSB0ZW1wbGF0ZUluZm8gVGVtcGxhdGUgbWV0YWRhdGEgdG8gYWRkIGVmZmVjdCB0bwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wIFByb3BlcnR5IHRoYXQgc2hvdWxkIHRyaWdnZXIgdGhlIGVmZmVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gZWZmZWN0IEVmZmVjdCBtZXRhZGF0YSBvYmplY3QKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfYWRkVGVtcGxhdGVQcm9wZXJ0eUVmZmVjdCh0ZW1wbGF0ZUluZm8sIHByb3AsIGVmZmVjdCkgewogICAgICAgICAgbGV0IGhvc3RQcm9wcyA9IHRlbXBsYXRlSW5mby5ob3N0UHJvcHMgPSB0ZW1wbGF0ZUluZm8uaG9zdFByb3BzIHx8IHt9OwogICAgICAgICAgaG9zdFByb3BzW3Byb3BdID0gdHJ1ZTsKICAgICAgICAgIGxldCBlZmZlY3RzID0gdGVtcGxhdGVJbmZvLnByb3BlcnR5RWZmZWN0cyA9IHRlbXBsYXRlSW5mby5wcm9wZXJ0eUVmZmVjdHMgfHwge307CiAgICAgICAgICBsZXQgcHJvcEVmZmVjdHMgPSBlZmZlY3RzW3Byb3BdID0gZWZmZWN0c1twcm9wXSB8fCBbXTsKICAgICAgICAgIHByb3BFZmZlY3RzLnB1c2goZWZmZWN0KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFN0YW1wcyB0aGUgcHJvdmlkZWQgdGVtcGxhdGUgYW5kIHBlcmZvcm1zIGluc3RhbmNlLXRpbWUgc2V0dXAgZm9yCiAgICAgICAgICogUG9seW1lciB0ZW1wbGF0ZSBmZWF0dXJlcywgaW5jbHVkaW5nIGRhdGEgYmluZGluZ3MsIGRlY2xhcmF0aXZlIGV2ZW50CiAgICAgICAgICogbGlzdGVuZXJzLCBhbmQgdGhlIGB0aGlzLiRgIG1hcCBvZiBgaWRgJ3MgdG8gbm9kZXMuICBBIGRvY3VtZW50IGZyYWdtZW50CiAgICAgICAgICogaXMgcmV0dXJuZWQgY29udGFpbmluZyB0aGUgc3RhbXBlZCBET00sIHJlYWR5IGZvciBpbnNlcnRpb24gaW50byB0aGUKICAgICAgICAgKiBET00uCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBtYXkgYmUgY2FsbGVkIG1vcmUgdGhhbiBvbmNlOyBob3dldmVyIG5vdGUgdGhhdCBkdWUgdG8KICAgICAgICAgKiBgc2hhZHljc3NgIHBvbHlmaWxsIGxpbWl0YXRpb25zLCBvbmx5IHN0eWxlcyBmcm9tIHRlbXBsYXRlcyBwcmVwYXJlZAogICAgICAgICAqIHVzaW5nIGBTaGFkeUNTUy5wcmVwYXJlVGVtcGxhdGVgIHdpbGwgYmUgY29ycmVjdGx5IHBvbHlmaWxsZWQgKHNjb3BlZAogICAgICAgICAqIHRvIHRoZSBzaGFkb3cgcm9vdCBhbmQgc3VwcG9ydCBDU1MgY3VzdG9tIHByb3BlcnRpZXMpLCBhbmQgbm90ZSB0aGF0CiAgICAgICAgICogYFNoYWR5Q1NTLnByZXBhcmVUZW1wbGF0ZWAgbWF5IG9ubHkgYmUgY2FsbGVkIG9uY2UgcGVyIGVsZW1lbnQuIEFzIHN1Y2gsCiAgICAgICAgICogYW55IHN0eWxlcyByZXF1aXJlZCBieSBpbiBydW50aW1lLXN0YW1wZWQgdGVtcGxhdGVzIG11c3QgYmUgaW5jbHVkZWQKICAgICAgICAgKiBpbiB0aGUgbWFpbiBlbGVtZW50IHRlbXBsYXRlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUgVGVtcGxhdGUgdG8gc3RhbXAKICAgICAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mbz19IHRlbXBsYXRlSW5mbyBPcHRpb25hbCBib3VuZCB0ZW1wbGF0ZSBpbmZvIGFzc29jaWF0ZWQKICAgICAgICAgKiAgIHdpdGggdGhlIHRlbXBsYXRlIHRvIGJlIHN0YW1wZWQ7IGlmIG9taXR0ZWQgdGhlIHRlbXBsYXRlIHdpbGwgYmUKICAgICAgICAgKiAgIGF1dG9tYXRpY2FsbHkgYm91bmQuCiAgICAgICAgICogQHJldHVybiB7IVN0YW1wZWRUZW1wbGF0ZX0gQ2xvbmVkIHRlbXBsYXRlIGNvbnRlbnQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICovCiAgICAgICAgX3N0YW1wVGVtcGxhdGUodGVtcGxhdGUsIHRlbXBsYXRlSW5mbykgewogICAgICAgICAgdGVtcGxhdGVJbmZvID0gIHRlbXBsYXRlSW5mbyB8fCAvKiogQHR5cGUgeyFUZW1wbGF0ZUluZm99ICovKHRoaXMuX2JpbmRUZW1wbGF0ZSh0ZW1wbGF0ZSwgdHJ1ZSkpOwogICAgICAgICAgLy8gRW5zdXJlcyB0aGF0IGNyZWF0ZWQgZG9tIGlzIGBfZW5xdWV1ZUNsaWVudGAnZCB0byB0aGlzIGVsZW1lbnQgc28KICAgICAgICAgIC8vIHRoYXQgaXQgY2FuIGJlIGZsdXNoZWQgb24gbmV4dCBjYWxsIHRvIGBfZmx1c2hQcm9wZXJ0aWVzYAogICAgICAgICAgaG9zdFN0YWNrLnB1c2godGhpcyk7CiAgICAgICAgICBsZXQgZG9tID0gc3VwZXIuX3N0YW1wVGVtcGxhdGUodGVtcGxhdGUsIHRlbXBsYXRlSW5mbyk7CiAgICAgICAgICBob3N0U3RhY2sucG9wKCk7CiAgICAgICAgICAvLyBBZGQgdGVtcGxhdGUtaW5zdGFuY2Utc3BlY2lmaWMgZGF0YSB0byBpbnN0YW5jZWQgdGVtcGxhdGVJbmZvCiAgICAgICAgICB0ZW1wbGF0ZUluZm8ubm9kZUxpc3QgPSBkb20ubm9kZUxpc3Q7CiAgICAgICAgICAvLyBDYXB0dXJlIGNoaWxkIG5vZGVzIHRvIGFsbG93IHVuc3RhbXBpbmcgb2Ygbm9uLXByb3RvdHlwaWNhbCB0ZW1wbGF0ZXMKICAgICAgICAgIGlmICghdGVtcGxhdGVJbmZvLndhc1ByZUJvdW5kKSB7CiAgICAgICAgICAgIGxldCBub2RlcyA9IHRlbXBsYXRlSW5mby5jaGlsZE5vZGVzID0gW107CiAgICAgICAgICAgIGZvciAobGV0IG49ZG9tLmZpcnN0Q2hpbGQ7IG47IG49bi5uZXh0U2libGluZykgewogICAgICAgICAgICAgIG5vZGVzLnB1c2gobik7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGRvbS50ZW1wbGF0ZUluZm8gPSB0ZW1wbGF0ZUluZm87CiAgICAgICAgICAvLyBTZXR1cCBjb21wb3VuZCBzdG9yYWdlLCAyLXdheSBsaXN0ZW5lcnMsIGFuZCBkYXRhSG9zdCBmb3IgYmluZGluZ3MKICAgICAgICAgIHNldHVwQmluZGluZ3ModGhpcywgdGVtcGxhdGVJbmZvKTsKICAgICAgICAgIC8vIEZsdXNoIHByb3BlcnRpZXMgaW50byB0ZW1wbGF0ZSBub2RlczsgdGhlIGNoZWNrIG9uIGBfX2RhdGFDbGllbnRzUmVhZHlgCiAgICAgICAgICAvLyBlbnN1cmVzIHdlIGRvbid0IG5lZWRsZXNzbHkgcnVuIGVmZmVjdHMgZm9yIGFuIGVsZW1lbnQncyBpbml0aWFsCiAgICAgICAgICAvLyBwcm90b3R5cGljYWwgdGVtcGxhdGUgc3RhbXBpbmcgc2luY2UgdGhleSB3aWxsIGhhcHBlbiBhcyBhIHBhcnQgb2YgdGhlCiAgICAgICAgICAvLyBmaXJzdCBjYWxsIHRvIGBfcHJvcGVydGllc0NoYW5nZWRgLiBUaGlzIGZsYWcgaXMgc2V0IHRvIHRydWUKICAgICAgICAgIC8vIGFmdGVyIHJ1bm5pbmcgdGhlIGluaXRpYWwgcHJvcGFnYXRlIGVmZmVjdHMsIGFuZCBpbW1lZGlhdGVseSBiZWZvcmUKICAgICAgICAgIC8vIGZsdXNoaW5nIGNsaWVudHMuIFNpbmNlIGRvd25zdHJlYW0gY2xpZW50cyBjb3VsZCBjYXVzZSBzdGFtcGluZyBvbgogICAgICAgICAgLy8gdGhpcyBob3N0IChlLmcuIGEgZmFzdERvbUlmIGBkb20taWZgIGJlaW5nIGZvcmNlZCB0byByZW5kZXIKICAgICAgICAgIC8vIHN5bmNocm9ub3VzbHkpLCB0aGlzIGZsYWcgZW5zdXJlcyBlZmZlY3RzIGZvciBydW50aW1lLXN0YW1wZWQgdGVtcGxhdGVzCiAgICAgICAgICAvLyBhcmUgcnVuIGF0IHRoaXMgcG9pbnQgZHVyaW5nIHRoZSBpbml0aWFsIGVsZW1lbnQgYm9vdC11cC4KICAgICAgICAgIGlmICh0aGlzLl9fZGF0YUNsaWVudHNSZWFkeSkgewogICAgICAgICAgICB0aGlzLl9ydW5FZmZlY3RzRm9yVGVtcGxhdGUodGVtcGxhdGVJbmZvLCB0aGlzLl9fZGF0YSwgbnVsbCwgZmFsc2UpOwogICAgICAgICAgICB0aGlzLl9mbHVzaENsaWVudHMoKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBkb207CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGFuZCB1bmJpbmRzIHRoZSBub2RlcyBwcmV2aW91c2x5IGNvbnRhaW5lZCBpbiB0aGUgcHJvdmlkZWQKICAgICAgICAgKiBEb2N1bWVudEZyYWdtZW50IHJldHVybmVkIGZyb20gYF9zdGFtcFRlbXBsYXRlYC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7IVN0YW1wZWRUZW1wbGF0ZX0gZG9tIERvY3VtZW50RnJhZ21lbnQgcHJldmlvdXNseSByZXR1cm5lZAogICAgICAgICAqICAgZnJvbSBgX3N0YW1wVGVtcGxhdGVgIGFzc29jaWF0ZWQgd2l0aCB0aGUgbm9kZXMgdG8gYmUgcmVtb3ZlZAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9yZW1vdmVCb3VuZERvbShkb20pIHsKICAgICAgICAgIC8vIFVubGluayB0ZW1wbGF0ZSBpbmZvOyBOb3RlIHRoYXQgd2hpbGUgdGhlIGNoaWxkIGlzIHVubGlua2VkIGZyb20gaXRzCiAgICAgICAgICAvLyBwYXJlbnQgbGlzdCwgYSB0ZW1wbGF0ZSdzIGBwYXJlbnRgIHJlZmVyZW5jZSBpcyBuZXZlciByZW1vdmVkLCBzaW5jZQogICAgICAgICAgLy8gdGhpcyBpcyBpcyBkZXRlcm1pbmVkIGJ5IHRoZSB0cmVlIHN0cnVjdHVyZSBhbmQgYXBwbGllZCBhdAogICAgICAgICAgLy8gYGFwcGx5VGVtcGxhdGVJbmZvYCB0aW1lLgogICAgICAgICAgY29uc3QgdGVtcGxhdGVJbmZvID0gZG9tLnRlbXBsYXRlSW5mbzsKICAgICAgICAgIGNvbnN0IHtwcmV2aW91c1NpYmxpbmcsIG5leHRTaWJsaW5nLCBwYXJlbnR9ID0gdGVtcGxhdGVJbmZvOwogICAgICAgICAgaWYgKHByZXZpb3VzU2libGluZykgewogICAgICAgICAgICBwcmV2aW91c1NpYmxpbmcubmV4dFNpYmxpbmcgPSBuZXh0U2libGluZzsKICAgICAgICAgIH0gZWxzZSBpZiAocGFyZW50KSB7CiAgICAgICAgICAgIHBhcmVudC5maXJzdENoaWxkID0gbmV4dFNpYmxpbmc7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAobmV4dFNpYmxpbmcpIHsKICAgICAgICAgICAgbmV4dFNpYmxpbmcucHJldmlvdXNTaWJsaW5nID0gcHJldmlvdXNTaWJsaW5nOwogICAgICAgICAgfSBlbHNlIGlmIChwYXJlbnQpIHsKICAgICAgICAgICAgcGFyZW50Lmxhc3RDaGlsZCA9IHByZXZpb3VzU2libGluZzsKICAgICAgICAgIH0KICAgICAgICAgIHRlbXBsYXRlSW5mby5uZXh0U2libGluZyA9IHRlbXBsYXRlSW5mby5wcmV2aW91c1NpYmxpbmcgPSBudWxsOwogICAgICAgICAgLy8gUmVtb3ZlIHN0YW1wZWQgbm9kZXMKICAgICAgICAgIGxldCBub2RlcyA9IHRlbXBsYXRlSW5mby5jaGlsZE5vZGVzOwogICAgICAgICAgZm9yIChsZXQgaT0wOyBpPG5vZGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gbm9kZXNbaV07CiAgICAgICAgICAgIHdyYXAod3JhcChub2RlKS5wYXJlbnROb2RlKS5yZW1vdmVDaGlsZChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyBkZWZhdWx0IGBUZW1wbGF0ZVN0YW1wYCBpbXBsZW1lbnRhdGlvbiB0byBhZGQgc3VwcG9ydCBmb3IKICAgICAgICAgKiBwYXJzaW5nIGJpbmRpbmdzIGZyb20gYFRleHROb2RlYCdzJyBgdGV4dENvbnRlbnRgLiAgQSBgYmluZGluZ3NgCiAgICAgICAgICogYXJyYXkgaXMgYWRkZWQgdG8gYG5vZGVJbmZvYCBhbmQgcG9wdWxhdGVkIHdpdGggYmluZGluZyBtZXRhZGF0YQogICAgICAgICAqIHdpdGggaW5mb3JtYXRpb24gY2FwdHVyaW5nIHRoZSBiaW5kaW5nIHRhcmdldCwgYW5kIGEgYHBhcnRzYCBhcnJheQogICAgICAgICAqIHdpdGggb25lIG9yIG1vcmUgbWV0YWRhdGEgb2JqZWN0cyBjYXB0dXJpbmcgdGhlIHNvdXJjZShzKSBvZiB0aGUKICAgICAgICAgKiBiaW5kaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtOb2RlfSBub2RlIE5vZGUgdG8gcGFyc2UKICAgICAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZSBub2RlCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gYHRydWVgIGlmIHRoZSB2aXNpdGVkIG5vZGUgYWRkZWQgbm9kZS1zcGVjaWZpYwogICAgICAgICAqICAgbWV0YWRhdGEgdG8gYG5vZGVJbmZvYAogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZU5vZGUobm9kZSwgdGVtcGxhdGVJbmZvLCBub2RlSW5mbykgewogICAgICAgICAgLy8gVE9ETyhodHRwczovL2dpdGh1Yi5jb20vZ29vZ2xlL2Nsb3N1cmUtY29tcGlsZXIvaXNzdWVzLzMyNDApOgogICAgICAgICAgLy8gICAgIENoYW5nZSBiYWNrIHRvIGp1c3Qgc3VwZXIubWV0aG9kQ2FsbCgpCiAgICAgICAgICBsZXQgbm90ZWQgPSBwcm9wZXJ0eUVmZmVjdHNCYXNlLl9wYXJzZVRlbXBsYXRlTm9kZS5jYWxsKAogICAgICAgICAgICB0aGlzLCBub2RlLCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvKTsKICAgICAgICAgIGlmIChub2RlLm5vZGVUeXBlID09PSBOb2RlLlRFWFRfTk9ERSkgewogICAgICAgICAgICBsZXQgcGFydHMgPSB0aGlzLl9wYXJzZUJpbmRpbmdzKG5vZGUudGV4dENvbnRlbnQsIHRlbXBsYXRlSW5mbyk7CiAgICAgICAgICAgIGlmIChwYXJ0cykgewogICAgICAgICAgICAgIC8vIEluaXRpYWxpemUgdGhlIHRleHRDb250ZW50IHdpdGggYW55IGxpdGVyYWwgcGFydHMKICAgICAgICAgICAgICAvLyBOT1RFOiBkZWZhdWx0IHRvIGEgc3BhY2UgaGVyZSBzbyB0aGUgdGV4dE5vZGUgcmVtYWluczsgc29tZSBicm93c2VycwogICAgICAgICAgICAgIC8vIChJRSkgb21pdCBhbiBlbXB0eSB0ZXh0Tm9kZSBmb2xsb3dpbmcgY2xvbmVOb2RlL2ltcG9ydE5vZGUuCiAgICAgICAgICAgICAgbm9kZS50ZXh0Q29udGVudCA9IGxpdGVyYWxGcm9tUGFydHMocGFydHMpIHx8ICcgJzsKICAgICAgICAgICAgICBhZGRCaW5kaW5nKHRoaXMsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8sICd0ZXh0JywgJ3RleHRDb250ZW50JywgcGFydHMpOwogICAgICAgICAgICAgIG5vdGVkID0gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG5vdGVkOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIGRlZmF1bHQgYFRlbXBsYXRlU3RhbXBgIGltcGxlbWVudGF0aW9uIHRvIGFkZCBzdXBwb3J0IGZvcgogICAgICAgICAqIHBhcnNpbmcgYmluZGluZ3MgZnJvbSBhdHRyaWJ1dGVzLiAgQSBgYmluZGluZ3NgCiAgICAgICAgICogYXJyYXkgaXMgYWRkZWQgdG8gYG5vZGVJbmZvYCBhbmQgcG9wdWxhdGVkIHdpdGggYmluZGluZyBtZXRhZGF0YQogICAgICAgICAqIHdpdGggaW5mb3JtYXRpb24gY2FwdHVyaW5nIHRoZSBiaW5kaW5nIHRhcmdldCwgYW5kIGEgYHBhcnRzYCBhcnJheQogICAgICAgICAqIHdpdGggb25lIG9yIG1vcmUgbWV0YWRhdGEgb2JqZWN0cyBjYXB0dXJpbmcgdGhlIHNvdXJjZShzKSBvZiB0aGUKICAgICAgICAgKiBiaW5kaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBub2RlIE5vZGUgdG8gcGFyc2UKICAgICAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZSBub2RlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgQXR0cmlidXRlIG5hbWUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdmFsdWUgQXR0cmlidXRlIHZhbHVlCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gYHRydWVgIGlmIHRoZSB2aXNpdGVkIG5vZGUgYWRkZWQgbm9kZS1zcGVjaWZpYwogICAgICAgICAqICAgbWV0YWRhdGEgdG8gYG5vZGVJbmZvYAogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZU5vZGVBdHRyaWJ1dGUobm9kZSwgdGVtcGxhdGVJbmZvLCBub2RlSW5mbywgbmFtZSwgdmFsdWUpIHsKICAgICAgICAgIGxldCBwYXJ0cyA9IHRoaXMuX3BhcnNlQmluZGluZ3ModmFsdWUsIHRlbXBsYXRlSW5mbyk7CiAgICAgICAgICBpZiAocGFydHMpIHsKICAgICAgICAgICAgLy8gQXR0cmlidXRlIG9yIHByb3BlcnR5CiAgICAgICAgICAgIGxldCBvcmlnTmFtZSA9IG5hbWU7CiAgICAgICAgICAgIGxldCBraW5kID0gJ3Byb3BlcnR5JzsKICAgICAgICAgICAgLy8gVGhlIG9ubHkgd2F5IHdlIHNlZSBhIGNhcGl0YWwgbGV0dGVyIGhlcmUgaXMgaWYgdGhlIGF0dHIgaGFzCiAgICAgICAgICAgIC8vIGEgY2FwaXRhbCBsZXR0ZXIgaW4gaXQgcGVyIHNwZWMuIEluIHRoaXMgY2FzZSwgdG8gbWFrZSBzdXJlCiAgICAgICAgICAgIC8vIHRoaXMgYmluZGluZyB3b3Jrcywgd2UgZ28gYWhlYWQgYW5kIG1ha2UgdGhlIGJpbmRpbmcgdG8gdGhlIGF0dHJpYnV0ZS4KICAgICAgICAgICAgaWYgKGNhcGl0YWxBdHRyaWJ1dGVSZWdleC50ZXN0KG5hbWUpKSB7CiAgICAgICAgICAgICAga2luZCA9ICdhdHRyaWJ1dGUnOwogICAgICAgICAgICB9IGVsc2UgaWYgKG5hbWVbbmFtZS5sZW5ndGgtMV0gPT0gJyQnKSB7CiAgICAgICAgICAgICAgbmFtZSA9IG5hbWUuc2xpY2UoMCwgLTEpOwogICAgICAgICAgICAgIGtpbmQgPSAnYXR0cmlidXRlJzsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBJbml0aWFsaXplIGF0dHJpYnV0ZSBiaW5kaW5ncyB3aXRoIGFueSBsaXRlcmFsIHBhcnRzCiAgICAgICAgICAgIGxldCBsaXRlcmFsID0gbGl0ZXJhbEZyb21QYXJ0cyhwYXJ0cyk7CiAgICAgICAgICAgIGlmIChsaXRlcmFsICYmIGtpbmQgPT0gJ2F0dHJpYnV0ZScpIHsKICAgICAgICAgICAgICAvLyBFbnN1cmUgYSBTaGFkeUNTUyB0ZW1wbGF0ZSBzY29wZWQgc3R5bGUgaXMgbm90IHJlbW92ZWQKICAgICAgICAgICAgICAvLyB3aGVuIGEgY2xhc3MkIGJpbmRpbmcncyBpbml0aWFsIGxpdGVyYWwgdmFsdWUgaXMgc2V0LgogICAgICAgICAgICAgIGlmIChuYW1lID09ICdjbGFzcycgJiYgbm9kZS5oYXNBdHRyaWJ1dGUoJ2NsYXNzJykpIHsKICAgICAgICAgICAgICAgIGxpdGVyYWwgKz0gJyAnICsgbm9kZS5nZXRBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIG5vZGUuc2V0QXR0cmlidXRlKG5hbWUsIGxpdGVyYWwpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIHN1cHBvcnQgZGlzYWJsZS11cGdyYWRlCiAgICAgICAgICAgIGlmIChraW5kID09ICdhdHRyaWJ1dGUnICYmIG9yaWdOYW1lID09ICdkaXNhYmxlLXVwZ3JhZGUkJykgewogICAgICAgICAgICAgIG5vZGUuc2V0QXR0cmlidXRlKG5hbWUsICcnKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDbGVhciBhdHRyaWJ1dGUgYmVmb3JlIHJlbW92aW5nLCBzaW5jZSBJRSB3b24ndCBhbGxvdyByZW1vdmluZwogICAgICAgICAgICAvLyBgdmFsdWVgIGF0dHJpYnV0ZSBpZiBpdCBwcmV2aW91c2x5IGhhZCBhIHZhbHVlIChjYW4ndAogICAgICAgICAgICAvLyB1bmNvbmRpdGlvbmFsbHkgc2V0ICcnIGJlZm9yZSByZW1vdmluZyBzaW5jZSBhdHRyaWJ1dGVzIHdpdGggYCRgCiAgICAgICAgICAgIC8vIGNhbid0IGJlIHNldCB1c2luZyBzZXRBdHRyaWJ1dGUpCiAgICAgICAgICAgIGlmIChub2RlLmxvY2FsTmFtZSA9PT0gJ2lucHV0JyAmJiBvcmlnTmFtZSA9PT0gJ3ZhbHVlJykgewogICAgICAgICAgICAgIG5vZGUuc2V0QXR0cmlidXRlKG9yaWdOYW1lLCAnJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVtb3ZlIGFubm90YXRpb24KICAgICAgICAgICAgbm9kZS5yZW1vdmVBdHRyaWJ1dGUob3JpZ05hbWUpOwogICAgICAgICAgICAvLyBDYXNlIGhhY2tlcnk6IGF0dHJpYnV0ZXMgYXJlIGxvd2VyLWNhc2UsIGJ1dCBiaW5kIHRhcmdldHMKICAgICAgICAgICAgLy8gKHByb3BlcnRpZXMpIGFyZSBjYXNlIHNlbnNpdGl2ZS4gR2FtYml0IGlzIHRvIG1hcCBkYXNoLWNhc2UgdG8KICAgICAgICAgICAgLy8gY2FtZWwtY2FzZTogYGZvby1iYXJgIGJlY29tZXMgYGZvb0JhcmAuCiAgICAgICAgICAgIC8vIEF0dHJpYnV0ZSBiaW5kaW5ncyBhcmUgZXhjZXB0ZWQuCiAgICAgICAgICAgIGlmIChraW5kID09PSAncHJvcGVydHknKSB7CiAgICAgICAgICAgICAgbmFtZSA9IGRhc2hUb0NhbWVsQ2FzZShuYW1lKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBhZGRCaW5kaW5nKHRoaXMsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8sIGtpbmQsIG5hbWUsIHBhcnRzLCBsaXRlcmFsKTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvLyBUT0RPKGh0dHBzOi8vZ2l0aHViLmNvbS9nb29nbGUvY2xvc3VyZS1jb21waWxlci9pc3N1ZXMvMzI0MCk6CiAgICAgICAgICAgIC8vICAgICBDaGFuZ2UgYmFjayB0byBqdXN0IHN1cGVyLm1ldGhvZENhbGwoKQogICAgICAgICAgICByZXR1cm4gcHJvcGVydHlFZmZlY3RzQmFzZS5fcGFyc2VUZW1wbGF0ZU5vZGVBdHRyaWJ1dGUuY2FsbCgKICAgICAgICAgICAgICB0aGlzLCBub2RlLCB0ZW1wbGF0ZUluZm8sIG5vZGVJbmZvLCBuYW1lLCB2YWx1ZSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgZGVmYXVsdCBgVGVtcGxhdGVTdGFtcGAgaW1wbGVtZW50YXRpb24gdG8gYWRkIHN1cHBvcnQgZm9yCiAgICAgICAgICogYmluZGluZyB0aGUgcHJvcGVydGllcyB0aGF0IGEgbmVzdGVkIHRlbXBsYXRlIGRlcGVuZHMgb24gdG8gdGhlIHRlbXBsYXRlCiAgICAgICAgICogYXMgYF9ob3N0Xzxwcm9wZXJ0eT5gLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtOb2RlfSBub2RlIE5vZGUgdG8gcGFyc2UKICAgICAgICAgKiBAcGFyYW0ge1RlbXBsYXRlSW5mb30gdGVtcGxhdGVJbmZvIFRlbXBsYXRlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtOb2RlSW5mb30gbm9kZUluZm8gTm9kZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZSBub2RlCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gYHRydWVgIGlmIHRoZSB2aXNpdGVkIG5vZGUgYWRkZWQgbm9kZS1zcGVjaWZpYwogICAgICAgICAqICAgbWV0YWRhdGEgdG8gYG5vZGVJbmZvYAogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZU5lc3RlZFRlbXBsYXRlKG5vZGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pIHsKICAgICAgICAgIC8vIFRPRE8oaHR0cHM6Ly9naXRodWIuY29tL2dvb2dsZS9jbG9zdXJlLWNvbXBpbGVyL2lzc3Vlcy8zMjQwKToKICAgICAgICAgIC8vICAgICBDaGFuZ2UgYmFjayB0byBqdXN0IHN1cGVyLm1ldGhvZENhbGwoKQogICAgICAgICAgbGV0IG5vdGVkID0gcHJvcGVydHlFZmZlY3RzQmFzZS5fcGFyc2VUZW1wbGF0ZU5lc3RlZFRlbXBsYXRlLmNhbGwoCiAgICAgICAgICAgIHRoaXMsIG5vZGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pOwogICAgICAgICAgY29uc3QgcGFyZW50ID0gbm9kZS5wYXJlbnROb2RlOwogICAgICAgICAgY29uc3QgbmVzdGVkVGVtcGxhdGVJbmZvID0gbm9kZUluZm8udGVtcGxhdGVJbmZvOwogICAgICAgICAgY29uc3QgaXNEb21JZiA9IHBhcmVudC5sb2NhbE5hbWUgPT09ICdkb20taWYnOwogICAgICAgICAgY29uc3QgaXNEb21SZXBlYXQgPSBwYXJlbnQubG9jYWxOYW1lID09PSAnZG9tLXJlcGVhdCc7CiAgICAgICAgICAvLyBSZW1vdmUgbmVzdGVkIHRlbXBsYXRlIGFuZCByZWRpcmVjdCBpdHMgaG9zdCBiaW5kaW5ncyAmIHRlbXBsYXRlSW5mbwogICAgICAgICAgLy8gb250byB0aGUgcGFyZW50IChkb20taWYvcmVwZWF0IGVsZW1lbnQpJ3Mgbm9kZUluZm8KICAgICAgICAgIGlmIChyZW1vdmVOZXN0ZWRUZW1wbGF0ZXMgJiYgKGlzRG9tSWYgfHwgaXNEb21SZXBlYXQpKSB7CiAgICAgICAgICAgIHBhcmVudC5yZW1vdmVDaGlsZChub2RlKTsKICAgICAgICAgICAgLy8gVXNlIHRoZSBwYXJlbnQncyBub2RlSW5mbyAoZm9yIHRoZSBkb20taWYvcmVwZWF0KSB0byByZWNvcmQgdGhlCiAgICAgICAgICAgIC8vIHRlbXBsYXRlSW5mbywgYW5kIHVzZSB0aGF0IGZvciBhbnkgaG9zdCBwcm9wZXJ0eSBiaW5kaW5ncyBiZWxvdwogICAgICAgICAgICBub2RlSW5mbyA9IG5vZGVJbmZvLnBhcmVudEluZm87CiAgICAgICAgICAgIG5vZGVJbmZvLnRlbXBsYXRlSW5mbyA9IG5lc3RlZFRlbXBsYXRlSW5mbzsKICAgICAgICAgICAgLy8gRW5zdXJlIHRoZSBwYXJlbnQgZG9tLWlmL3JlcGVhdCBpcyBub3RlZCBzaW5jZSBpdCBub3cgbWF5IGhhdmUgaG9zdAogICAgICAgICAgICAvLyBiaW5kaW5nczsgaXQgbWF5IG5vdCBoYXZlIGJlZW4gaWYgaXQgZGlkIG5vdCBoYXZlIGl0cyBvd24gYmluZGluZ3MKICAgICAgICAgICAgbm9kZUluZm8ubm90ZWQgPSB0cnVlOwogICAgICAgICAgICBub3RlZCA9IGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgLy8gTWVyZ2UgaG9zdCBwcm9wcyBpbnRvIG91dGVyIHRlbXBsYXRlIGFuZCBhZGQgYmluZGluZ3MKICAgICAgICAgIGxldCBob3N0UHJvcHMgPSBuZXN0ZWRUZW1wbGF0ZUluZm8uaG9zdFByb3BzOwogICAgICAgICAgaWYgKGZhc3REb21JZiAmJiBpc0RvbUlmKSB7CiAgICAgICAgICAgIC8vIGBmYXN0RG9tSWZgIG1vZGUgdXNlcyBydW50aW1lLXRlbXBsYXRlIHN0YW1waW5nIHRvIGFkZCBhY2Nlc3NvcnMvCiAgICAgICAgICAgIC8vIGVmZmVjdHMgdG8gcHJvcGVydGllcyB1c2VkIGluIGl0cyB0ZW1wbGF0ZTsgYXMgc3VjaCB3ZSBkb24ndCBuZWVkIHRvCiAgICAgICAgICAgIC8vIHRheCB0aGUgaG9zdCBlbGVtZW50IHdpdGggYF9ob3N0X2AgYmluZGluZ3MgZm9yIHRoZSBgZG9tLWlmYC4KICAgICAgICAgICAgLy8gSG93ZXZlciwgaW4gdGhlIGV2ZW50IGl0IGlzIG5lc3RlZCBpbiBhIGBkb20tcmVwZWF0YCwgaXQgaXMgc3RpbGwKICAgICAgICAgICAgLy8gaW1wb3J0YW50IHRoYXQgaXRzIGhvc3QgcHJvcGVydGllcyBhcmUgYWRkZWQgdG8gdGhlCiAgICAgICAgICAgIC8vIFRlbXBsYXRlSW5zdGFuY2UncyBgaG9zdFByb3BzYCBzbyB0aGF0IHRoZXkgYXJlIGZvcndhcmRlZCB0byB0aGUKICAgICAgICAgICAgLy8gVGVtcGxhdGVJbnN0YW5jZS4KICAgICAgICAgICAgaWYgKGhvc3RQcm9wcykgewogICAgICAgICAgICAgIHRlbXBsYXRlSW5mby5ob3N0UHJvcHMgPQogICAgICAgICAgICAgICAgT2JqZWN0LmFzc2lnbih0ZW1wbGF0ZUluZm8uaG9zdFByb3BzIHx8IHt9LCBob3N0UHJvcHMpOwogICAgICAgICAgICAgIC8vIEVuc3VyZSB0aGUgZG9tLWlmIGlzIG5vdGVkIHNvIHRoYXQgaXQgaGFzIGEgX19kYXRhSG9zdCwgc2luY2UKICAgICAgICAgICAgICAvLyBgZmFzdERvbUlmYCB1c2VzIHRoZSBob3N0IGZvciBydW50aW1lIHRlbXBsYXRlIHN0YW1waW5nOyBub3RlIHRoaXMKICAgICAgICAgICAgICAvLyB3YXMgYWxyZWFkeSBlbnN1cmVkIGFib3ZlIGluIHRoZSBgcmVtb3ZlTmVzdGVkVGVtcGxhdGVzYCBjYXNlCiAgICAgICAgICAgICAgaWYgKCFyZW1vdmVOZXN0ZWRUZW1wbGF0ZXMpIHsKICAgICAgICAgICAgICAgIG5vZGVJbmZvLnBhcmVudEluZm8ubm90ZWQgPSB0cnVlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbGV0IG1vZGUgPSAneyc7CiAgICAgICAgICAgIGZvciAobGV0IHNvdXJjZSBpbiBob3N0UHJvcHMpIHsKICAgICAgICAgICAgICBsZXQgcGFydHMgPSBbeyBtb2RlLCBzb3VyY2UsIGRlcGVuZGVuY2llczogW3NvdXJjZV0sIGhvc3RQcm9wOiB0cnVlIH1dOwogICAgICAgICAgICAgIGFkZEJpbmRpbmcodGhpcywgdGVtcGxhdGVJbmZvLCBub2RlSW5mbywgJ3Byb3BlcnR5JywgJ19ob3N0XycgKyBzb3VyY2UsIHBhcnRzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG5vdGVkOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2FsbGVkIHRvIHBhcnNlIHRleHQgaW4gYSB0ZW1wbGF0ZSAoZWl0aGVyIGF0dHJpYnV0ZSB2YWx1ZXMgb3IKICAgICAgICAgKiB0ZXh0Q29udGVudCkgaW50byBiaW5kaW5nIG1ldGFkYXRhLgogICAgICAgICAqCiAgICAgICAgICogQW55IG92ZXJyaWRlcyBvZiB0aGlzIG1ldGhvZCBzaG91bGQgcmV0dXJuIGFuIGFycmF5IG9mIGJpbmRpbmcgcGFydAogICAgICAgICAqIG1ldGFkYXRhICByZXByZXNlbnRpbmcgb25lIG9yIG1vcmUgYmluZGluZ3MgZm91bmQgaW4gdGhlIHByb3ZpZGVkIHRleHQKICAgICAgICAgKiBhbmQgYW55ICJsaXRlcmFsIiB0ZXh0IGluIGJldHdlZW4uICBBbnkgbm9uLWxpdGVyYWwgcGFydHMgd2lsbCBiZSBwYXNzZWQKICAgICAgICAgKiB0byBgX2V2YWx1YXRlQmluZGluZ2Agd2hlbiBhbnkgZGVwZW5kZW5jaWVzIGNoYW5nZS4gIFRoZSBvbmx5IHJlcXVpcmVkCiAgICAgICAgICogZmllbGRzIG9mIGVhY2ggInBhcnQiIGluIHRoZSByZXR1cm5lZCBhcnJheSBhcmUgYXMgZm9sbG93czoKICAgICAgICAgKgogICAgICAgICAqIC0gYGRlcGVuZGVuY2llc2AgLSBBcnJheSBjb250YWluaW5nIHRyaWdnZXIgbWV0YWRhdGEgZm9yIGVhY2ggcHJvcGVydHkKICAgICAgICAgKiAgIHRoYXQgc2hvdWxkIHRyaWdnZXIgdGhlIGJpbmRpbmcgdG8gdXBkYXRlCiAgICAgICAgICogLSBgbGl0ZXJhbGAgLSBTdHJpbmcgY29udGFpbmluZyB0ZXh0IGlmIHRoZSBwYXJ0IHJlcHJlc2VudHMgYSBsaXRlcmFsOwogICAgICAgICAqICAgaW4gdGhpcyBjYXNlIG5vIGBkZXBlbmRlbmNpZXNgIGFyZSBuZWVkZWQKICAgICAgICAgKgogICAgICAgICAqIEFkZGl0aW9uYWwgbWV0YWRhdGEgZm9yIHVzZSBieSBgX2V2YWx1YXRlQmluZGluZ2AgbWF5IGJlIHByb3ZpZGVkIGluCiAgICAgICAgICogZWFjaCBwYXJ0IG9iamVjdCBhcyBuZWVkZWQuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBoYW5kbGVzIHRoZSBmb2xsb3dpbmcgdHlwZXMgb2YgYmluZGluZ3MKICAgICAgICAgKiAob25lIG9yIG1vcmUgbWF5IGJlIGludGVybWl4ZWQgd2l0aCBsaXRlcmFsIHN0cmluZ3MpOgogICAgICAgICAqIC0gUHJvcGVydHkgYmluZGluZzogYFtbcHJvcF1dYAogICAgICAgICAqIC0gUGF0aCBiaW5kaW5nOiBgW1tvYmplY3QucHJvcF1dYAogICAgICAgICAqIC0gTmVnYXRlZCBwcm9wZXJ0eSBvciBwYXRoIGJpbmRpbmdzOiBgW1shcHJvcF1dYCBvciBgW1shb2JqZWN0LnByb3BdXWAKICAgICAgICAgKiAtIFR3by13YXkgcHJvcGVydHkgb3IgcGF0aCBiaW5kaW5ncyAoc3VwcG9ydHMgbmVnYXRpb24pOgogICAgICAgICAqICAgYHt7cHJvcH19YCwgYHt7b2JqZWN0LnByb3B9fWAsIGB7eyFwcm9wfX1gIG9yIGB7eyFvYmplY3QucHJvcH19YAogICAgICAgICAqIC0gSW5saW5lIGNvbXB1dGVkIG1ldGhvZCAoc3VwcG9ydHMgbmVnYXRpb24pOgogICAgICAgICAqICAgYFtbY29tcHV0ZShhLCAnbGl0ZXJhbCcsIGIpXV1gLCBgW1shY29tcHV0ZShhLCAnbGl0ZXJhbCcsIGIpXV1gCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiB1c2VzIGEgcmVndWxhciBleHByZXNzaW9uIGZvciBiZXN0CiAgICAgICAgICogcGVyZm9ybWFuY2UuIEhvd2V2ZXIsIHRoZSByZWd1bGFyIGV4cHJlc3Npb24gdXNlcyBhIHdoaXRlLWxpc3Qgb2YKICAgICAgICAgKiBhbGxvd2VkIGNoYXJhY3RlcnMgaW4gYSBkYXRhLWJpbmRpbmcsIHdoaWNoIGNhdXNlcyBwcm9ibGVtcyBmb3IKICAgICAgICAgKiBkYXRhLWJpbmRpbmdzIHRoYXQgZG8gdXNlIGNoYXJhY3RlcnMgbm90IGluIHRoaXMgd2hpdGUtbGlzdC4KICAgICAgICAgKgogICAgICAgICAqIEluc3RlYWQgb2YgdXBkYXRpbmcgdGhlIHdoaXRlLWxpc3Qgd2l0aCBhbGwgYWxsb3dlZCBjaGFyYWN0ZXJzLAogICAgICAgICAqIHRoZXJlIGlzIGEgU3RyaWN0QmluZGluZ1BhcnNlciAoc2VlIGxpYi9taXhpbnMvc3RyaWN0LWJpbmRpbmctcGFyc2VyKQogICAgICAgICAqIHRoYXQgdXNlcyBhIHN0YXRlIG1hY2hpbmUgaW5zdGVhZC4gVGhpcyBzdGF0ZSBtYWNoaW5lIGlzIGFibGUgdG8gaGFuZGxlCiAgICAgICAgICogYWxsIGNoYXJhY3RlcnMuIEhvd2V2ZXIsIGl0IGlzIHNsaWdodGx5IGxlc3MgcGVyZm9ybWFudCwgdGhlcmVmb3JlIHdlCiAgICAgICAgICogZXh0cmFjdGVkIGl0IGludG8gYSBzZXBhcmF0ZSBvcHRpb25hbCBtaXhpbi4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0ZXh0IFRleHQgdG8gcGFyc2UgZnJvbSBhdHRyaWJ1dGUgb3IgdGV4dENvbnRlbnQKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gdGVtcGxhdGVJbmZvIEN1cnJlbnQgdGVtcGxhdGUgbWV0YWRhdGEKICAgICAgICAgKiBAcmV0dXJuIHtBcnJheTwhQmluZGluZ1BhcnQ+fSBBcnJheSBvZiBiaW5kaW5nIHBhcnQgbWV0YWRhdGEKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3BhcnNlQmluZGluZ3ModGV4dCwgdGVtcGxhdGVJbmZvKSB7CiAgICAgICAgICBsZXQgcGFydHMgPSBbXTsKICAgICAgICAgIGxldCBsYXN0SW5kZXggPSAwOwogICAgICAgICAgbGV0IG07CiAgICAgICAgICAvLyBFeGFtcGxlOiAibGl0ZXJhbDF7e3Byb3B9fWxpdGVyYWwyW1shY29tcHV0ZShmb28sYmFyKV1dZmluYWwiCiAgICAgICAgICAvLyBSZWdleCBtYXRjaGVzOgogICAgICAgICAgLy8gICAgICAgIEl0ZXJhdGlvbiAxOiAgSXRlcmF0aW9uIDI6CiAgICAgICAgICAvLyBtWzFdOiAne3snICAgICAgICAgICdbWycKICAgICAgICAgIC8vIG1bMl06ICcnICAgICAgICAgICAgJyEnCiAgICAgICAgICAvLyBtWzNdOiAncHJvcCcgICAgICAgICdjb21wdXRlKGZvbyxiYXIpJwogICAgICAgICAgd2hpbGUgKChtID0gYmluZGluZ1JlZ2V4LmV4ZWModGV4dCkpICE9PSBudWxsKSB7CiAgICAgICAgICAgIC8vIEFkZCBsaXRlcmFsIHBhcnQKICAgICAgICAgICAgaWYgKG0uaW5kZXggPiBsYXN0SW5kZXgpIHsKICAgICAgICAgICAgICBwYXJ0cy5wdXNoKHtsaXRlcmFsOiB0ZXh0LnNsaWNlKGxhc3RJbmRleCwgbS5pbmRleCl9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBBZGQgYmluZGluZyBwYXJ0CiAgICAgICAgICAgIGxldCBtb2RlID0gbVsxXVswXTsKICAgICAgICAgICAgbGV0IG5lZ2F0ZSA9IEJvb2xlYW4obVsyXSk7CiAgICAgICAgICAgIGxldCBzb3VyY2UgPSBtWzNdLnRyaW0oKTsKICAgICAgICAgICAgbGV0IGN1c3RvbUV2ZW50ID0gZmFsc2UsIG5vdGlmeUV2ZW50ID0gJycsIGNvbG9uID0gLTE7CiAgICAgICAgICAgIGlmIChtb2RlID09ICd7JyAmJiAoY29sb24gPSBzb3VyY2UuaW5kZXhPZignOjonKSkgPiAwKSB7CiAgICAgICAgICAgICAgbm90aWZ5RXZlbnQgPSBzb3VyY2Uuc3Vic3RyaW5nKGNvbG9uICsgMik7CiAgICAgICAgICAgICAgc291cmNlID0gc291cmNlLnN1YnN0cmluZygwLCBjb2xvbik7CiAgICAgICAgICAgICAgY3VzdG9tRXZlbnQgPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBzaWduYXR1cmUgPSBwYXJzZU1ldGhvZChzb3VyY2UpOwogICAgICAgICAgICBsZXQgZGVwZW5kZW5jaWVzID0gW107CiAgICAgICAgICAgIGlmIChzaWduYXR1cmUpIHsKICAgICAgICAgICAgICAvLyBJbmxpbmUgY29tcHV0ZWQgZnVuY3Rpb24KICAgICAgICAgICAgICBsZXQge2FyZ3MsIG1ldGhvZE5hbWV9ID0gc2lnbmF0dXJlOwogICAgICAgICAgICAgIGZvciAobGV0IGk9MDsgaTxhcmdzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBsZXQgYXJnID0gYXJnc1tpXTsKICAgICAgICAgICAgICAgIGlmICghYXJnLmxpdGVyYWwpIHsKICAgICAgICAgICAgICAgICAgZGVwZW5kZW5jaWVzLnB1c2goYXJnKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgbGV0IGR5bmFtaWNGbnMgPSB0ZW1wbGF0ZUluZm8uZHluYW1pY0ZuczsKICAgICAgICAgICAgICBpZiAoZHluYW1pY0ZucyAmJiBkeW5hbWljRm5zW21ldGhvZE5hbWVdIHx8IHNpZ25hdHVyZS5zdGF0aWMpIHsKICAgICAgICAgICAgICAgIGRlcGVuZGVuY2llcy5wdXNoKG1ldGhvZE5hbWUpOwogICAgICAgICAgICAgICAgc2lnbmF0dXJlLmR5bmFtaWNGbiA9IHRydWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIC8vIFByb3BlcnR5IG9yIHBhdGgKICAgICAgICAgICAgICBkZXBlbmRlbmNpZXMucHVzaChzb3VyY2UpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHBhcnRzLnB1c2goewogICAgICAgICAgICAgIHNvdXJjZSwgbW9kZSwgbmVnYXRlLCBjdXN0b21FdmVudCwgc2lnbmF0dXJlLCBkZXBlbmRlbmNpZXMsCiAgICAgICAgICAgICAgZXZlbnQ6IG5vdGlmeUV2ZW50CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBsYXN0SW5kZXggPSBiaW5kaW5nUmVnZXgubGFzdEluZGV4OwogICAgICAgICAgfQogICAgICAgICAgLy8gQWRkIGEgZmluYWwgbGl0ZXJhbCBwYXJ0CiAgICAgICAgICBpZiAobGFzdEluZGV4ICYmIGxhc3RJbmRleCA8IHRleHQubGVuZ3RoKSB7CiAgICAgICAgICAgIGxldCBsaXRlcmFsID0gdGV4dC5zdWJzdHJpbmcobGFzdEluZGV4KTsKICAgICAgICAgICAgaWYgKGxpdGVyYWwpIHsKICAgICAgICAgICAgICBwYXJ0cy5wdXNoKHsKICAgICAgICAgICAgICAgIGxpdGVyYWw6IGxpdGVyYWwKICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKHBhcnRzLmxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gcGFydHM7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxlZCB0byBldmFsdWF0ZSBhIHByZXZpb3VzbHkgcGFyc2VkIGJpbmRpbmcgcGFydCBiYXNlZCBvbiBhIHNldCBvZgogICAgICAgICAqIG9uZSBvciBtb3JlIGNoYW5nZWQgZGVwZW5kZW5jaWVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshUG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9IGluc3QgRWxlbWVudCB0aGF0IHNob3VsZCBiZSB1c2VkIGFzCiAgICAgICAgICogICAgIHNjb3BlIGZvciBiaW5kaW5nIGRlcGVuZGVuY2llcwogICAgICAgICAqIEBwYXJhbSB7QmluZGluZ1BhcnR9IHBhcnQgQmluZGluZyBwYXJ0IG1ldGFkYXRhCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHBhdGggUHJvcGVydHkvcGF0aCB0aGF0IHRyaWdnZXJlZCB0aGlzIGVmZmVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm9wcyBCYWcgb2YgY3VycmVudCBwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9sZFByb3BzIEJhZyBvZiBwcmV2aW91cyB2YWx1ZXMgZm9yIGNoYW5nZWQgcHJvcGVydGllcwogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaGFzUGF0aHMgVHJ1ZSB3aXRoIGBwcm9wc2AgY29udGFpbnMgb25lIG9yIG1vcmUgcGF0aHMKICAgICAgICAgKiBAcmV0dXJuIHsqfSBWYWx1ZSB0aGUgYmluZGluZyBwYXJ0IGV2YWx1YXRlZCB0bwogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfZXZhbHVhdGVCaW5kaW5nKGluc3QsIHBhcnQsIHBhdGgsIHByb3BzLCBvbGRQcm9wcywgaGFzUGF0aHMpIHsKICAgICAgICAgIGxldCB2YWx1ZTsKICAgICAgICAgIGlmIChwYXJ0LnNpZ25hdHVyZSkgewogICAgICAgICAgICB2YWx1ZSA9IHJ1bk1ldGhvZEVmZmVjdChpbnN0LCBwYXRoLCBwcm9wcywgb2xkUHJvcHMsIHBhcnQuc2lnbmF0dXJlKTsKICAgICAgICAgIH0gZWxzZSBpZiAocGF0aCAhPSBwYXJ0LnNvdXJjZSkgewogICAgICAgICAgICB2YWx1ZSA9IGdldChpbnN0LCBwYXJ0LnNvdXJjZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoaGFzUGF0aHMgJiYgaXNQYXRoKHBhdGgpKSB7CiAgICAgICAgICAgICAgdmFsdWUgPSBnZXQoaW5zdCwgcGF0aCk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdmFsdWUgPSBpbnN0Ll9fZGF0YVtwYXRoXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKHBhcnQubmVnYXRlKSB7CiAgICAgICAgICAgIHZhbHVlID0gIXZhbHVlOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICAgIH0KCiAgICAgIH0KCiAgICAgIHJldHVybiBQcm9wZXJ0eUVmZmVjdHM7CiAgICB9KTsKCiAgICAvKioKICAgICAqIFN0YWNrIGZvciBlbnF1ZXVpbmcgY2xpZW50IGRvbSBjcmVhdGVkIGJ5IGEgaG9zdCBlbGVtZW50LgogICAgICoKICAgICAqIEJ5IGRlZmF1bHQgZWxlbWVudHMgYXJlIGZsdXNoZWQgdmlhIGBfZmx1c2hQcm9wZXJ0aWVzYCB3aGVuCiAgICAgKiBgY29ubmVjdGVkQ2FsbGJhY2tgIGlzIGNhbGxlZC4gRWxlbWVudHMgYXR0YWNoIHRoZWlyIGNsaWVudCBkb20gdG8KICAgICAqIHRoZW1zZWx2ZXMgYXQgYHJlYWR5YCB0aW1lIHdoaWNoIHJlc3VsdHMgZnJvbSB0aGlzIGZpcnN0IGZsdXNoLgogICAgICogVGhpcyBwcm92aWRlcyBhbiBvcmRlcmluZyBndWFyYW50ZWUgdGhhdCB0aGUgY2xpZW50IGRvbSBhbiBlbGVtZW50CiAgICAgKiBjcmVhdGVzIGlzIGZsdXNoZWQgYmVmb3JlIHRoZSBlbGVtZW50IGl0c2VsZiAoaS5lLiBjbGllbnQgYHJlYWR5YAogICAgICogZmlyZXMgYmVmb3JlIGhvc3QgYHJlYWR5YCkuCiAgICAgKgogICAgICogSG93ZXZlciwgaWYgYF9mbHVzaFByb3BlcnRpZXNgIGlzIGNhbGxlZCAqYmVmb3JlKiBhbiBlbGVtZW50IGlzIGNvbm5lY3RlZCwKICAgICAqIGFzIGZvciBleGFtcGxlIGBUZW1wbGF0aXplYCBkb2VzLCB0aGlzIG9yZGVyaW5nIGd1YXJhbnRlZSBjYW5ub3QgYmUKICAgICAqIHNhdGlzZmllZCBiZWNhdXNlIG5vIGVsZW1lbnRzIGFyZSBjb25uZWN0ZWQuIChOb3RlOiBCb3VuZCBlbGVtZW50cyB0aGF0CiAgICAgKiByZWNlaXZlIGRhdGEgZG8gYmVjb21lIGVucXVldWVkIGNsaWVudHMgYW5kIGFyZSBwcm9wZXJseSBvcmRlcmVkIGJ1dAogICAgICogdW5ib3VuZCBlbGVtZW50cyBhcmUgbm90LikKICAgICAqCiAgICAgKiBUbyBtYWludGFpbiB0aGUgZGVzaXJlZCAiY2xpZW50IGJlZm9yZSBob3N0IiBvcmRlcmluZyBndWFyYW50ZWUgZm9yIHRoaXMKICAgICAqIGNhc2Ugd2UgcmVseSBvbiB0aGUgImhvc3Qgc3RhY2suIENsaWVudCBub2RlcyByZWdpc3RlcnMgdGhlbXNlbHZlcyB3aXRoCiAgICAgKiB0aGUgY3JlYXRpbmcgaG9zdCBlbGVtZW50IHdoZW4gY3JlYXRlZC4gVGhpcyBlbnN1cmVzIHRoYXQgYWxsIGNsaWVudCBkb20KICAgICAqIGlzIHJlYWRpZWQgaW4gdGhlIHByb3BlciBvcmRlciwgbWFpbnRhaW5pbmcgdGhlIGRlc2lyZWQgZ3VhcmFudGVlLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGNvbnN0IGhvc3RTdGFjayA9IFtdOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBSZWdpc3RlcnMgYSBjbGFzcyBwcm90b3R5cGUgZm9yIHRlbGVtZXRyeSBwdXJwb3Nlcy4KICAgICAqIEBwYXJhbSB7IVBvbHltZXJFbGVtZW50Q29uc3RydWN0b3J9IHByb3RvdHlwZSBFbGVtZW50IHByb3RvdHlwZSB0byByZWdpc3RlcgogICAgICogQHByb3RlY3RlZAogICAgICovCiAgICBmdW5jdGlvbiByZWdpc3Rlcihwcm90b3R5cGUpIHsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGNvcHkgb2YgYHByb3BzYCB3aXRoIGVhY2ggcHJvcGVydHkgbm9ybWFsaXplZCBzdWNoIHRoYXQKICAgICAqIHVwZ3JhZGVkIGl0IGlzIGFuIG9iamVjdCB3aXRoIGF0IGxlYXN0IGEgdHlwZSBwcm9wZXJ0eSB7IHR5cGU6IFR5cGV9LgogICAgICoKICAgICAqIEBwYXJhbSB7IU9iamVjdH0gcHJvcHMgUHJvcGVydGllcyB0byBub3JtYWxpemUKICAgICAqIEByZXR1cm4geyFPYmplY3R9IENvcHkgb2YgaW5wdXQgYHByb3BzYCB3aXRoIG5vcm1hbGl6ZWQgcHJvcGVydGllcyB0aGF0CiAgICAgKiBhcmUgaW4gdGhlIGZvcm0ge3R5cGU6IFR5cGV9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBub3JtYWxpemVQcm9wZXJ0aWVzKHByb3BzKSB7CiAgICAgIGNvbnN0IG91dHB1dCA9IHt9OwogICAgICBmb3IgKGxldCBwIGluIHByb3BzKSB7CiAgICAgICAgY29uc3QgbyA9IHByb3BzW3BdOwogICAgICAgIG91dHB1dFtwXSA9ICh0eXBlb2YgbyA9PT0gJ2Z1bmN0aW9uJykgPyB7dHlwZTogb30gOiBvOwogICAgICB9CiAgICAgIHJldHVybiBvdXRwdXQ7CiAgICB9CgogICAgLyoqCiAgICAgKiBNaXhpbiB0aGF0IHByb3ZpZGVzIGEgbWluaW1hbCBzdGFydGluZyBwb2ludCB0byB1c2luZyB0aGUgUHJvcGVydGllc0NoYW5nZWQKICAgICAqIG1peGluIGJ5IHByb3ZpZGluZyBhIG1lY2hhbmlzbSB0byBkZWNsYXJlIHByb3BlcnRpZXMgaW4gYSBzdGF0aWMKICAgICAqIGdldHRlciAoZS5nLiBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7IHJldHVybiB7IGZvbzogU3RyaW5nIH0gfSkuIENoYW5nZXMKICAgICAqIGFyZSByZXBvcnRlZCB2aWEgdGhlIGBfcHJvcGVydGllc0NoYW5nZWRgIG1ldGhvZC4KICAgICAqCiAgICAgKiBUaGlzIG1peGluIHByb3ZpZGVzIG5vIHNwZWNpZmljIHN1cHBvcnQgZm9yIHJlbmRlcmluZy4gVXNlcnMgYXJlIGV4cGVjdGVkCiAgICAgKiB0byBjcmVhdGUgYSBTaGFkb3dSb290IGFuZCBwdXQgY29udGVudCBpbnRvIGl0IGFuZCB1cGRhdGUgaXQgaW4gd2hhdGV2ZXIKICAgICAqIHdheSBtYWtlcyBzZW5zZS4gVGhpcyBjYW4gYmUgZG9uZSBpbiByZWFjdGlvbiB0byBwcm9wZXJ0aWVzIGNoYW5naW5nIGJ5CiAgICAgKiBpbXBsZW1lbnRpbmcgYF9wcm9wZXJ0aWVzQ2hhbmdlZGAuCiAgICAgKgogICAgICogQG1peGluRnVuY3Rpb24KICAgICAqIEBwb2x5bWVyCiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnRpZXNDaGFuZ2VkCiAgICAgKiBAc3VtbWFyeSBNaXhpbiB0aGF0IHByb3ZpZGVzIGEgbWluaW1hbCBzdGFydGluZyBwb2ludCBmb3IgdXNpbmcKICAgICAqIHRoZSBQcm9wZXJ0aWVzQ2hhbmdlZCBtaXhpbiBieSBwcm92aWRpbmcgYSBkZWNsYXJhdGl2ZSBgcHJvcGVydGllc2Agb2JqZWN0LgogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIENsYXNzIHRvIGFwcGx5IG1peGluIHRvLgogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIHdpdGggbWl4aW4gYXBwbGllZC4KICAgICAqLwogICAgY29uc3QgUHJvcGVydGllc01peGluID0gZGVkdXBpbmdNaXhpbihzdXBlckNsYXNzID0+IHsKCiAgICAgLyoqCiAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfUHJvcGVydGllc0NoYW5nZWR9CiAgICAgICogQHByaXZhdGUKICAgICAgKi8KICAgICBjb25zdCBiYXNlID0gUHJvcGVydGllc0NoYW5nZWQoc3VwZXJDbGFzcyk7CgogICAgIC8qKgogICAgICAqIFJldHVybnMgdGhlIHN1cGVyIGNsYXNzIGNvbnN0cnVjdG9yIGZvciB0aGUgZ2l2ZW4gY2xhc3MsIGlmIGl0IGlzIGFuCiAgICAgICogaW5zdGFuY2Ugb2YgdGhlIFByb3BlcnRpZXNNaXhpbi4KICAgICAgKgogICAgICAqIEBwYXJhbSB7IVByb3BlcnRpZXNNaXhpbkNvbnN0cnVjdG9yfSBjb25zdHJ1Y3RvciBQcm9wZXJ0aWVzTWl4aW4gY29uc3RydWN0b3IKICAgICAgKiBAcmV0dXJuIHs/UHJvcGVydGllc01peGluQ29uc3RydWN0b3J9IFN1cGVyIGNsYXNzIGNvbnN0cnVjdG9yCiAgICAgICovCiAgICAgZnVuY3Rpb24gc3VwZXJQcm9wZXJ0aWVzQ2xhc3MoY29uc3RydWN0b3IpIHsKICAgICAgIGNvbnN0IHN1cGVyQ3RvciA9IE9iamVjdC5nZXRQcm90b3R5cGVPZihjb25zdHJ1Y3Rvcik7CgogICAgICAgLy8gTm90ZSwgdGhlIGBQcm9wZXJ0aWVzTWl4aW5gIGNsYXNzIGJlbG93IG9ubHkgcmVmZXJzIHRvIHRoZSBjbGFzcwogICAgICAgLy8gZ2VuZXJhdGVkIGJ5IHRoaXMgY2FsbCB0byB0aGUgbWl4aW47IHRoZSBpbnN0YW5jZW9mIHRlc3Qgb25seSB3b3JrcwogICAgICAgLy8gYmVjYXVzZSB0aGUgbWl4aW4gaXMgZGVkdXBlZCBhbmQgZ3VhcmFudGVlZCBvbmx5IHRvIGFwcGx5IG9uY2UsIGhlbmNlCiAgICAgICAvLyBhbGwgY29uc3RydWN0b3JzIGluIGEgcHJvdG8gY2hhaW4gd2lsbCBzZWUgdGhlIHNhbWUgYFByb3BlcnRpZXNNaXhpbmAKICAgICAgIHJldHVybiAoc3VwZXJDdG9yLnByb3RvdHlwZSBpbnN0YW5jZW9mIFByb3BlcnRpZXNNaXhpbikgPwogICAgICAgICAvKiogQHR5cGUgeyFQcm9wZXJ0aWVzTWl4aW5Db25zdHJ1Y3Rvcn0gKi8gKHN1cGVyQ3RvcikgOiBudWxsOwogICAgIH0KCiAgICAgLyoqCiAgICAgICogUmV0dXJucyBhIG1lbW9pemVkIHZlcnNpb24gb2YgdGhlIGBwcm9wZXJ0aWVzYCBvYmplY3QgZm9yIHRoZQogICAgICAqIGdpdmVuIGNsYXNzLiBQcm9wZXJ0aWVzIG5vdCBpbiBvYmplY3QgZm9ybWF0IGFyZSBjb252ZXJ0ZWQgdG8gYXQKICAgICAgKiBsZWFzdCB7dHlwZX0uCiAgICAgICoKICAgICAgKiBAcGFyYW0ge1Byb3BlcnRpZXNNaXhpbkNvbnN0cnVjdG9yfSBjb25zdHJ1Y3RvciBQcm9wZXJ0aWVzTWl4aW4gY29uc3RydWN0b3IKICAgICAgKiBAcmV0dXJuIHtPYmplY3R9IE1lbW9pemVkIHByb3BlcnRpZXMgb2JqZWN0CiAgICAgICovCiAgICAgZnVuY3Rpb24gb3duUHJvcGVydGllcyhjb25zdHJ1Y3RvcikgewogICAgICAgaWYgKCFjb25zdHJ1Y3Rvci5oYXNPd25Qcm9wZXJ0eShKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdfX293blByb3BlcnRpZXMnLCBjb25zdHJ1Y3RvcikpKSB7CiAgICAgICAgIGxldCBwcm9wcyA9IG51bGw7CgogICAgICAgICBpZiAoY29uc3RydWN0b3IuaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgncHJvcGVydGllcycsIGNvbnN0cnVjdG9yKSkpIHsKICAgICAgICAgICBjb25zdCBwcm9wZXJ0aWVzID0gY29uc3RydWN0b3IucHJvcGVydGllczsKCiAgICAgICAgICAgaWYgKHByb3BlcnRpZXMpIHsKICAgICAgICAgICAgcHJvcHMgPSBub3JtYWxpemVQcm9wZXJ0aWVzKHByb3BlcnRpZXMpOwogICAgICAgICAgIH0KICAgICAgICAgfQoKICAgICAgICAgY29uc3RydWN0b3IuX19vd25Qcm9wZXJ0aWVzID0gcHJvcHM7CiAgICAgICB9CiAgICAgICByZXR1cm4gY29uc3RydWN0b3IuX19vd25Qcm9wZXJ0aWVzOwogICAgIH0KCiAgICAgLyoqCiAgICAgICogQHBvbHltZXIKICAgICAgKiBAbWl4aW5DbGFzcwogICAgICAqIEBleHRlbmRzIHtiYXNlfQogICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1Byb3BlcnRpZXNNaXhpbn0KICAgICAgKiBAdW5yZXN0cmljdGVkCiAgICAgICovCiAgICAgY2xhc3MgUHJvcGVydGllc01peGluIGV4dGVuZHMgYmFzZSB7CgogICAgICAgLyoqCiAgICAgICAgKiBJbXBsZW1lbnRzIHN0YW5kYXJkIGN1c3RvbSBlbGVtZW50cyBnZXR0ZXIgdG8gb2JzZXJ2ZXMgdGhlIGF0dHJpYnV0ZXMKICAgICAgICAqIGxpc3RlZCBpbiBgcHJvcGVydGllc2AuCiAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgKi8KICAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZWRBdHRyaWJ1dGVzKCkgewogICAgICAgICBpZiAoIXRoaXMuaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX19vYnNlcnZlZEF0dHJpYnV0ZXMnLCB0aGlzKSkpIHsKICAgICAgICAgICByZWdpc3Rlcih0aGlzLnByb3RvdHlwZSk7CiAgICAgICAgICAgY29uc3QgcHJvcHMgPSB0aGlzLl9wcm9wZXJ0aWVzOwogICAgICAgICAgIHRoaXMuX19vYnNlcnZlZEF0dHJpYnV0ZXMgPSBwcm9wcyA/IE9iamVjdC5rZXlzKHByb3BzKS5tYXAocCA9PiB0aGlzLnByb3RvdHlwZS5fYWRkUHJvcGVydHlUb0F0dHJpYnV0ZU1hcChwKSkgOiBbXTsKICAgICAgICAgfQogICAgICAgICByZXR1cm4gdGhpcy5fX29ic2VydmVkQXR0cmlidXRlczsKICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIEZpbmFsaXplcyBhbiBlbGVtZW50IGRlZmluaXRpb24sIGluY2x1ZGluZyBlbnN1cmluZyBhbnkgc3VwZXIgY2xhc3NlcwogICAgICAgICogYXJlIGFsc28gZmluYWxpemVkLiBUaGlzIGluY2x1ZGVzIGVuc3VyaW5nIHByb3BlcnR5CiAgICAgICAgKiBhY2Nlc3NvcnMgZXhpc3Qgb24gdGhlIGVsZW1lbnQgcHJvdG90eXBlLiBUaGlzIG1ldGhvZCBjYWxscwogICAgICAgICogYF9maW5hbGl6ZUNsYXNzYCB0byBmaW5hbGl6ZSBlYWNoIGNvbnN0cnVjdG9yIGluIHRoZSBwcm90b3R5cGUgY2hhaW4uCiAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAqLwogICAgICAgc3RhdGljIGZpbmFsaXplKCkgewogICAgICAgICBpZiAoIXRoaXMuaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX19maW5hbGl6ZWQnLCB0aGlzKSkpIHsKICAgICAgICAgICBjb25zdCBzdXBlckN0b3IgPSBzdXBlclByb3BlcnRpZXNDbGFzcygvKiogQHR5cGUgeyFQcm9wZXJ0aWVzTWl4aW5Db25zdHJ1Y3Rvcn0gKi8odGhpcykpOwogICAgICAgICAgIGlmIChzdXBlckN0b3IpIHsKICAgICAgICAgICAgIHN1cGVyQ3Rvci5maW5hbGl6ZSgpOwogICAgICAgICAgIH0KICAgICAgICAgICB0aGlzLl9fZmluYWxpemVkID0gdHJ1ZTsKICAgICAgICAgICB0aGlzLl9maW5hbGl6ZUNsYXNzKCk7CiAgICAgICAgIH0KICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIEZpbmFsaXplIGFuIGVsZW1lbnQgY2xhc3MuIFRoaXMgaW5jbHVkZXMgZW5zdXJpbmcgcHJvcGVydHkKICAgICAgICAqIGFjY2Vzc29ycyBleGlzdCBvbiB0aGUgZWxlbWVudCBwcm90b3R5cGUuIFRoaXMgbWV0aG9kIGlzIGNhbGxlZCBieQogICAgICAgICogYGZpbmFsaXplYCBhbmQgZmluYWxpemVzIHRoZSBjbGFzcyBjb25zdHJ1Y3Rvci4KICAgICAgICAqCiAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICovCiAgICAgICBzdGF0aWMgX2ZpbmFsaXplQ2xhc3MoKSB7CiAgICAgICAgIGNvbnN0IHByb3BzID0gb3duUHJvcGVydGllcygvKiogQHR5cGUgeyFQcm9wZXJ0aWVzTWl4aW5Db25zdHJ1Y3Rvcn0gKi8odGhpcykpOwogICAgICAgICBpZiAocHJvcHMpIHsKICAgICAgICAgICAvKiogQHR5cGUgez99ICovICh0aGlzKS5jcmVhdGVQcm9wZXJ0aWVzKHByb3BzKTsKICAgICAgICAgfQogICAgICAgfQoKICAgICAgIC8qKgogICAgICAgICogUmV0dXJucyBhIG1lbW9pemVkIHZlcnNpb24gb2YgYWxsIHByb3BlcnRpZXMsIGluY2x1ZGluZyB0aG9zZSBpbmhlcml0ZWQKICAgICAgICAqIGZyb20gc3VwZXIgY2xhc3Nlcy4gUHJvcGVydGllcyBub3QgaW4gb2JqZWN0IGZvcm1hdCBhcmUgY29udmVydGVkIHRvCiAgICAgICAgKiBhdCBsZWFzdCB7dHlwZX0uCiAgICAgICAgKgogICAgICAgICogQHJldHVybiB7T2JqZWN0fSBPYmplY3QgY29udGFpbmluZyBwcm9wZXJ0aWVzIGZvciB0aGlzIGNsYXNzCiAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICovCiAgICAgICBzdGF0aWMgZ2V0IF9wcm9wZXJ0aWVzKCkgewogICAgICAgICBpZiAoIXRoaXMuaGFzT3duUHJvcGVydHkoCiAgICAgICAgICAgSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX19wcm9wZXJ0aWVzJywgdGhpcykpKSB7CiAgICAgICAgICAgY29uc3Qgc3VwZXJDdG9yID0gc3VwZXJQcm9wZXJ0aWVzQ2xhc3MoLyoqIEB0eXBlIHshUHJvcGVydGllc01peGluQ29uc3RydWN0b3J9ICovKHRoaXMpKTsKICAgICAgICAgICB0aGlzLl9fcHJvcGVydGllcyA9IE9iamVjdC5hc3NpZ24oe30sCiAgICAgICAgICAgICBzdXBlckN0b3IgJiYgc3VwZXJDdG9yLl9wcm9wZXJ0aWVzLAogICAgICAgICAgICAgb3duUHJvcGVydGllcygvKiogQHR5cGUge1Byb3BlcnRpZXNNaXhpbkNvbnN0cnVjdG9yfSAqLyh0aGlzKSkpOwogICAgICAgICB9CiAgICAgICAgIHJldHVybiB0aGlzLl9fcHJvcGVydGllczsKICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIE92ZXJyaWRlcyBgUHJvcGVydGllc0NoYW5nZWRgIG1ldGhvZCB0byByZXR1cm4gdHlwZSBzcGVjaWZpZWQgaW4gdGhlCiAgICAgICAgKiBzdGF0aWMgYHByb3BlcnRpZXNgIG9iamVjdCBmb3IgdGhlIGdpdmVuIHByb3BlcnR5LgogICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgTmFtZSBvZiBwcm9wZXJ0eQogICAgICAgICogQHJldHVybiB7Kn0gVHlwZSB0byB3aGljaCB0byBkZXNlcmlhbGl6ZSBhdHRyaWJ1dGUKICAgICAgICAqCiAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICovCiAgICAgICBzdGF0aWMgdHlwZUZvclByb3BlcnR5KG5hbWUpIHsKICAgICAgICAgY29uc3QgaW5mbyA9IHRoaXMuX3Byb3BlcnRpZXNbbmFtZV07CiAgICAgICAgIHJldHVybiBpbmZvICYmIGluZm8udHlwZTsKICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIE92ZXJyaWRlcyBgUHJvcGVydGllc0NoYW5nZWRgIG1ldGhvZCBhbmQgYWRkcyBhIGNhbGwgdG8KICAgICAgICAqIGBmaW5hbGl6ZWAgd2hpY2ggbGF6aWx5IGNvbmZpZ3VyZXMgdGhlIGVsZW1lbnQncyBwcm9wZXJ0eSBhY2Nlc3NvcnMuCiAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgKi8KICAgICAgIF9pbml0aWFsaXplUHJvcGVydGllcygpIHsKICAgICAgICAgdGhpcy5jb25zdHJ1Y3Rvci5maW5hbGl6ZSgpOwogICAgICAgICBzdXBlci5faW5pdGlhbGl6ZVByb3BlcnRpZXMoKTsKICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIENhbGxlZCB3aGVuIHRoZSBlbGVtZW50IGlzIGFkZGVkIHRvIGEgZG9jdW1lbnQuCiAgICAgICAgKiBDYWxscyBgX2VuYWJsZVByb3BlcnRpZXNgIHRvIHR1cm4gb24gcHJvcGVydHkgc3lzdGVtIGZyb20KICAgICAgICAqIGBQcm9wZXJ0aWVzQ2hhbmdlZGAuCiAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBTdXBlciBtYXkgb3IgbWF5IG5vdCBpbXBsZW1lbnQgdGhlIGNhbGxiYWNrCiAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgKi8KICAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsKICAgICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICB9CiAgICAgICAgIHRoaXMuX2VuYWJsZVByb3BlcnRpZXMoKTsKICAgICAgIH0KCiAgICAgICAvKioKICAgICAgICAqIENhbGxlZCB3aGVuIHRoZSBlbGVtZW50IGlzIHJlbW92ZWQgZnJvbSBhIGRvY3VtZW50CiAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBTdXBlciBtYXkgb3IgbWF5IG5vdCBpbXBsZW1lbnQgdGhlIGNhbGxiYWNrCiAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgKi8KICAgICAgIGRpc2Nvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICBpZiAoc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2spIHsKICAgICAgICAgICBzdXBlci5kaXNjb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICB9CiAgICAgICB9CgogICAgIH0KCiAgICAgcmV0dXJuIFByb3BlcnRpZXNNaXhpbjsKCiAgICB9KTsKCiAgICAvKioKICAgICAqIEBmaWxlb3ZlcnZpZXcKICAgICAqIEBzdXBwcmVzcyB7Y2hlY2tQcm90b3R5cGFsVHlwZXN9CiAgICAgKiBAbGljZW5zZSBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICAgKiBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZAogICAgICogYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heQogICAgICogYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieQogICAgICogR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUAogICAgICogcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgICovCgogICAgLyoqCiAgICAgKiBDdXJyZW50IFBvbHltZXIgdmVyc2lvbiBpbiBTZW12ZXIgbm90YXRpb24uCiAgICAgKiBAdHlwZSB7c3RyaW5nfSBTZW12ZXIgbm90YXRpb24gb2YgdGhlIGN1cnJlbnQgdmVyc2lvbiBvZiBQb2x5bWVyLgogICAgICovCiAgICBjb25zdCB2ZXJzaW9uID0gJzMuNC4xJzsKCiAgICBjb25zdCBidWlsdENTUyA9IHdpbmRvdy5TaGFkeUNTUyAmJiB3aW5kb3cuU2hhZHlDU1NbJ2Nzc0J1aWxkJ107CgogICAgLyoqCiAgICAgKiBFbGVtZW50IGNsYXNzIG1peGluIHRoYXQgcHJvdmlkZXMgdGhlIGNvcmUgQVBJIGZvciBQb2x5bWVyJ3MgbWV0YS1wcm9ncmFtbWluZwogICAgICogZmVhdHVyZXMgaW5jbHVkaW5nIHRlbXBsYXRlIHN0YW1waW5nLCBkYXRhLWJpbmRpbmcsIGF0dHJpYnV0ZSBkZXNlcmlhbGl6YXRpb24sCiAgICAgKiBhbmQgcHJvcGVydHkgY2hhbmdlIG9ic2VydmF0aW9uLgogICAgICoKICAgICAqIFN1YmNsYXNzZXJzIG1heSBwcm92aWRlIHRoZSBmb2xsb3dpbmcgc3RhdGljIGdldHRlcnMgdG8gcmV0dXJuIG1ldGFkYXRhCiAgICAgKiB1c2VkIHRvIGNvbmZpZ3VyZSBQb2x5bWVyJ3MgZmVhdHVyZXMgZm9yIHRoZSBjbGFzczoKICAgICAqCiAgICAgKiAtIGBzdGF0aWMgZ2V0IGlzKClgOiBXaGVuIHRoZSB0ZW1wbGF0ZSBpcyBwcm92aWRlZCB2aWEgYSBgZG9tLW1vZHVsZWAsCiAgICAgKiAgIHVzZXJzIHNob3VsZCByZXR1cm4gdGhlIGBkb20tbW9kdWxlYCBpZCBmcm9tIGEgc3RhdGljIGBpc2AgZ2V0dGVyLiAgSWYKICAgICAqICAgbm8gdGVtcGxhdGUgaXMgbmVlZGVkIG9yIHRoZSB0ZW1wbGF0ZSBpcyBwcm92aWRlZCBkaXJlY3RseSB2aWEgdGhlCiAgICAgKiAgIGB0ZW1wbGF0ZWAgZ2V0dGVyLCB0aGVyZSBpcyBubyBuZWVkIHRvIGRlZmluZSBgaXNgIGZvciB0aGUgZWxlbWVudC4KICAgICAqCiAgICAgKiAtIGBzdGF0aWMgZ2V0IHRlbXBsYXRlKClgOiBVc2VycyBtYXkgcHJvdmlkZSB0aGUgdGVtcGxhdGUgZGlyZWN0bHkgKGFzCiAgICAgKiAgIG9wcG9zZWQgdG8gdmlhIGBkb20tbW9kdWxlYCkgYnkgaW1wbGVtZW50aW5nIGEgc3RhdGljIGB0ZW1wbGF0ZWAgZ2V0dGVyLgogICAgICogICBUaGUgZ2V0dGVyIG11c3QgcmV0dXJuIGFuIGBIVE1MVGVtcGxhdGVFbGVtZW50YC4KICAgICAqCiAgICAgKiAtIGBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKWA6IFNob3VsZCByZXR1cm4gYW4gb2JqZWN0IGRlc2NyaWJpbmcKICAgICAqICAgcHJvcGVydHktcmVsYXRlZCBtZXRhZGF0YSB1c2VkIGJ5IFBvbHltZXIgZmVhdHVyZXMgKGtleTogcHJvcGVydHkgbmFtZQogICAgICogICB2YWx1ZTogb2JqZWN0IGNvbnRhaW5pbmcgcHJvcGVydHkgbWV0YWRhdGEpLiBWYWxpZCBrZXlzIGluIHBlci1wcm9wZXJ0eQogICAgICogICBtZXRhZGF0YSBpbmNsdWRlOgogICAgICogICAtIGB0eXBlYCAoU3RyaW5nfE51bWJlcnxPYmplY3R8QXJyYXl8Li4uKTogVXNlZCBieQogICAgICogICAgIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHRvIGRldGVybWluZSBob3cgc3RyaW5nLWJhc2VkIGF0dHJpYnV0ZXMKICAgICAqICAgICBhcmUgZGVzZXJpYWxpemVkIHRvIEphdmFTY3JpcHQgcHJvcGVydHkgdmFsdWVzLgogICAgICogICAtIGBub3RpZnlgIChib29sZWFuKTogQ2F1c2VzIGEgY2hhbmdlIGluIHRoZSBwcm9wZXJ0eSB0byBmaXJlIGEKICAgICAqICAgICBub24tYnViYmxpbmcgZXZlbnQgY2FsbGVkIGA8cHJvcGVydHk+LWNoYW5nZWRgLiBFbGVtZW50cyB0aGF0IGhhdmUKICAgICAqICAgICBlbmFibGVkIHR3by13YXkgYmluZGluZyB0byB0aGUgcHJvcGVydHkgdXNlIHRoaXMgZXZlbnQgdG8gb2JzZXJ2ZSBjaGFuZ2VzLgogICAgICogICAtIGByZWFkT25seWAgKGJvb2xlYW4pOiBDcmVhdGVzIGEgZ2V0dGVyIGZvciB0aGUgcHJvcGVydHksIGJ1dCBubyBzZXR0ZXIuCiAgICAgKiAgICAgVG8gc2V0IGEgcmVhZC1vbmx5IHByb3BlcnR5LCB1c2UgdGhlIHByaXZhdGUgc2V0dGVyIG1ldGhvZAogICAgICogICAgIGBfc2V0UHJvcGVydHkocHJvcGVydHksIHZhbHVlKWAuCiAgICAgKiAgIC0gYG9ic2VydmVyYCAoc3RyaW5nKTogT2JzZXJ2ZXIgbWV0aG9kIG5hbWUgdGhhdCB3aWxsIGJlIGNhbGxlZCB3aGVuCiAgICAgKiAgICAgdGhlIHByb3BlcnR5IGNoYW5nZXMuIFRoZSBhcmd1bWVudHMgb2YgdGhlIG1ldGhvZCBhcmUKICAgICAqICAgICBgKHZhbHVlLCBwcmV2aW91c1ZhbHVlKWAuCiAgICAgKiAgIC0gYGNvbXB1dGVkYCAoc3RyaW5nKTogU3RyaW5nIGRlc2NyaWJpbmcgbWV0aG9kIGFuZCBkZXBlbmRlbnQgcHJvcGVydGllcwogICAgICogICAgIGZvciBjb21wdXRpbmcgdGhlIHZhbHVlIG9mIHRoaXMgcHJvcGVydHkgKGUuZy4gYCdjb21wdXRlRm9vKGJhciwgem90KSdgKS4KICAgICAqICAgICBDb21wdXRlZCBwcm9wZXJ0aWVzIGFyZSByZWFkLW9ubHkgYnkgZGVmYXVsdCBhbmQgY2FuIG9ubHkgYmUgY2hhbmdlZAogICAgICogICAgIHZpYSB0aGUgcmV0dXJuIHZhbHVlIG9mIHRoZSBjb21wdXRpbmcgbWV0aG9kLgogICAgICoKICAgICAqIC0gYHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKClgOiBBcnJheSBvZiBzdHJpbmdzIGRlc2NyaWJpbmcgbXVsdGktcHJvcGVydHkKICAgICAqICAgb2JzZXJ2ZXIgbWV0aG9kcyBhbmQgdGhlaXIgZGVwZW5kZW50IHByb3BlcnRpZXMgKGUuZy4KICAgICAqICAgYCdvYnNlcnZlQUJDKGEsIGIsIGMpJ2ApLgogICAgICoKICAgICAqIFRoZSBiYXNlIGNsYXNzIHByb3ZpZGVzIGRlZmF1bHQgaW1wbGVtZW50YXRpb25zIGZvciB0aGUgZm9sbG93aW5nIHN0YW5kYXJkCiAgICAgKiBjdXN0b20gZWxlbWVudCBsaWZlY3ljbGUgY2FsbGJhY2tzOyB1c2VycyBtYXkgb3ZlcnJpZGUgdGhlc2UsIGJ1dCBzaG91bGQKICAgICAqIGNhbGwgdGhlIHN1cGVyIG1ldGhvZCB0byBlbnN1cmUKICAgICAqIC0gYGNvbnN0cnVjdG9yYDogUnVuIHdoZW4gdGhlIGVsZW1lbnQgaXMgY3JlYXRlZCBvciB1cGdyYWRlZAogICAgICogLSBgY29ubmVjdGVkQ2FsbGJhY2tgOiBSdW4gZWFjaCB0aW1lIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUKICAgICAqICAgZG9jdW1lbnQKICAgICAqIC0gYGRpc2Nvbm5lY3RlZENhbGxiYWNrYDogUnVuIGVhY2ggdGltZSB0aGUgZWxlbWVudCBpcyBkaXNjb25uZWN0ZWQgZnJvbQogICAgICogICB0aGUgZG9jdW1lbnQKICAgICAqIC0gYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2A6IFJ1biBlYWNoIHRpbWUgYW4gYXR0cmlidXRlIGluCiAgICAgKiAgIGBvYnNlcnZlZEF0dHJpYnV0ZXNgIGlzIHNldCBvciByZW1vdmVkIChub3RlOiB0aGlzIGVsZW1lbnQncyBkZWZhdWx0CiAgICAgKiAgIGBvYnNlcnZlZEF0dHJpYnV0ZXNgIGltcGxlbWVudGF0aW9uIHdpbGwgYXV0b21hdGljYWxseSByZXR1cm4gYW4gYXJyYXkKICAgICAqICAgb2YgZGFzaC1jYXNlZCBhdHRyaWJ1dGVzIGJhc2VkIG9uIGBwcm9wZXJ0aWVzYCkKICAgICAqCiAgICAgKiBAbWl4aW5GdW5jdGlvbgogICAgICogQHBvbHltZXIKICAgICAqIEBhcHBsaWVzTWl4aW4gUHJvcGVydHlFZmZlY3RzCiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnRpZXNNaXhpbgogICAgICogQHByb3BlcnR5IHJvb3RQYXRoIHtzdHJpbmd9IFNldCB0byB0aGUgdmFsdWUgb2YgYHJvb3RQYXRoYCwKICAgICAqICAgd2hpY2ggZGVmYXVsdHMgdG8gdGhlIG1haW4gZG9jdW1lbnQgcGF0aAogICAgICogQHByb3BlcnR5IGltcG9ydFBhdGgge3N0cmluZ30gU2V0IHRvIHRoZSB2YWx1ZSBvZiB0aGUgY2xhc3MncyBzdGF0aWMKICAgICAqICAgYGltcG9ydFBhdGhgIHByb3BlcnR5LCB3aGljaCBkZWZhdWx0cyB0byB0aGUgcGF0aCBvZiB0aGlzIGVsZW1lbnQncwogICAgICogICBgZG9tLW1vZHVsZWAgKHdoZW4gYGlzYCBpcyB1c2VkKSwgYnV0IGNhbiBiZSBvdmVycmlkZGVuIGZvciBvdGhlcgogICAgICogICBpbXBvcnQgc3RyYXRlZ2llcy4KICAgICAqIEBzdW1tYXJ5IEVsZW1lbnQgY2xhc3MgbWl4aW4gdGhhdCBwcm92aWRlcyB0aGUgY29yZSBBUEkgZm9yIFBvbHltZXIncwogICAgICogbWV0YS1wcm9ncmFtbWluZyBmZWF0dXJlcy4KICAgICAqIEB0ZW1wbGF0ZSBUCiAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyBDbGFzcyB0byBhcHBseSBtaXhpbiB0by4KICAgICAqIEByZXR1cm4ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyB3aXRoIG1peGluIGFwcGxpZWQuCiAgICAgKi8KICAgIGNvbnN0IEVsZW1lbnRNaXhpbiA9IGRlZHVwaW5nTWl4aW4oYmFzZSA9PiB7CiAgICAgIC8qKgogICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfUHJvcGVydHlFZmZlY3RzfQogICAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9Qcm9wZXJ0aWVzTWl4aW59CiAgICAgICAqIEBleHRlbmRzIHtIVE1MRWxlbWVudH0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIGNvbnN0IHBvbHltZXJFbGVtZW50QmFzZSA9IFByb3BlcnRpZXNNaXhpbihQcm9wZXJ0eUVmZmVjdHMoYmFzZSkpOwoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgYSBsaXN0IG9mIHByb3BlcnRpZXMgd2l0aCBkZWZhdWx0IHZhbHVlcy4KICAgICAgICogVGhpcyBsaXN0IGlzIGNyZWF0ZWQgYXMgYW4gb3B0aW1pemF0aW9uIHNpbmNlIGl0IGlzIGEgc3Vic2V0IG9mCiAgICAgICAqIHRoZSBsaXN0IHJldHVybmVkIGZyb20gYF9wcm9wZXJ0aWVzYC4KICAgICAgICogVGhpcyBsaXN0IGlzIHVzZWQgaW4gYF9pbml0aWFsaXplUHJvcGVydGllc2AgdG8gc2V0IHByb3BlcnR5IGRlZmF1bHRzLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge1BvbHltZXJFbGVtZW50Q29uc3RydWN0b3J9IGNvbnN0cnVjdG9yIEVsZW1lbnQgY2xhc3MKICAgICAgICogQHJldHVybiB7UG9seW1lckVsZW1lbnRQcm9wZXJ0aWVzfSBGbGF0dGVuZWQgcHJvcGVydGllcyBmb3IgdGhpcyBjbGFzcwogICAgICAgKiAgIHRoYXQgaGF2ZSBkZWZhdWx0IHZhbHVlcwogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgZnVuY3Rpb24gcHJvcGVydHlEZWZhdWx0cyhjb25zdHJ1Y3RvcikgewogICAgICAgIGlmICghY29uc3RydWN0b3IuaGFzT3duUHJvcGVydHkoCiAgICAgICAgICBKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdfX3Byb3BlcnR5RGVmYXVsdHMnLCBjb25zdHJ1Y3RvcikpKSB7CiAgICAgICAgICBjb25zdHJ1Y3Rvci5fX3Byb3BlcnR5RGVmYXVsdHMgPSBudWxsOwogICAgICAgICAgbGV0IHByb3BzID0gY29uc3RydWN0b3IuX3Byb3BlcnRpZXM7CiAgICAgICAgICBmb3IgKGxldCBwIGluIHByb3BzKSB7CiAgICAgICAgICAgIGxldCBpbmZvID0gcHJvcHNbcF07CiAgICAgICAgICAgIGlmICgndmFsdWUnIGluIGluZm8pIHsKICAgICAgICAgICAgICBjb25zdHJ1Y3Rvci5fX3Byb3BlcnR5RGVmYXVsdHMgPSBjb25zdHJ1Y3Rvci5fX3Byb3BlcnR5RGVmYXVsdHMgfHwge307CiAgICAgICAgICAgICAgY29uc3RydWN0b3IuX19wcm9wZXJ0eURlZmF1bHRzW3BdID0gaW5mbzsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gY29uc3RydWN0b3IuX19wcm9wZXJ0eURlZmF1bHRzOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyBhIG1lbW9pemVkIHZlcnNpb24gb2YgdGhlIGBvYnNlcnZlcnNgIGFycmF5LgogICAgICAgKiBAcGFyYW0ge1BvbHltZXJFbGVtZW50Q29uc3RydWN0b3J9IGNvbnN0cnVjdG9yIEVsZW1lbnQgY2xhc3MKICAgICAgICogQHJldHVybiB7QXJyYXl9IEFycmF5IGNvbnRhaW5pbmcgb3duIG9ic2VydmVycyBmb3IgdGhlIGdpdmVuIGNsYXNzCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIGZ1bmN0aW9uIG93bk9ic2VydmVycyhjb25zdHJ1Y3RvcikgewogICAgICAgIGlmICghY29uc3RydWN0b3IuaGFzT3duUHJvcGVydHkoCiAgICAgICAgICBKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdfX293bk9ic2VydmVycycsIGNvbnN0cnVjdG9yKSkpIHsKICAgICAgICAgIGNvbnN0cnVjdG9yLl9fb3duT2JzZXJ2ZXJzID0KICAgICAgICAgICAgICBjb25zdHJ1Y3Rvci5oYXNPd25Qcm9wZXJ0eSgKICAgICAgICAgICAgICAgICAgSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnb2JzZXJ2ZXJzJywgY29uc3RydWN0b3IpKSA/CiAgICAgICAgICAgICAgLyoqIEB0eXBlIHtQb2x5bWVyRWxlbWVudENvbnN0cnVjdG9yfSAqLyAoY29uc3RydWN0b3IpLm9ic2VydmVycyA6CiAgICAgICAgICAgICAgbnVsbDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGNvbnN0cnVjdG9yLl9fb3duT2JzZXJ2ZXJzOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ3JlYXRlcyBlZmZlY3RzIGZvciBhIHByb3BlcnR5LgogICAgICAgKgogICAgICAgKiBOb3RlLCBvbmNlIGEgcHJvcGVydHkgaGFzIGJlZW4gc2V0IHRvCiAgICAgICAqIGByZWFkT25seWAsIGBjb21wdXRlZGAsIGByZWZsZWN0VG9BdHRyaWJ1dGVgLCBvciBgbm90aWZ5YAogICAgICAgKiB0aGVzZSB2YWx1ZXMgbWF5IG5vdCBiZSBjaGFuZ2VkLiBGb3IgZXhhbXBsZSwgYSBzdWJjbGFzcyBjYW5ub3QKICAgICAgICogYWx0ZXIgdGhlc2Ugc2V0dGluZ3MuIEhvd2V2ZXIsIGFkZGl0aW9uYWwgYG9ic2VydmVyc2AgbWF5IGJlIGFkZGVkCiAgICAgICAqIGJ5IHN1YmNsYXNzZXMuCiAgICAgICAqCiAgICAgICAqIFRoZSBpbmZvIG9iamVjdCBzaG91bGQgY29udGFpbiBwcm9wZXJ0eSBtZXRhZGF0YSBhcyBmb2xsb3dzOgogICAgICAgKgogICAgICAgKiAqIGB0eXBlYDoge2Z1bmN0aW9ufSB0eXBlIHRvIHdoaWNoIGFuIGF0dHJpYnV0ZSBtYXRjaGluZyB0aGUgcHJvcGVydHkKICAgICAgICogaXMgZGVzZXJpYWxpemVkLiBOb3RlIHRoZSBwcm9wZXJ0eSBpcyBjYW1lbC1jYXNlZCBmcm9tIGEgZGFzaC1jYXNlZAogICAgICAgKiBhdHRyaWJ1dGUuIEZvciBleGFtcGxlLCAnZm9vLWJhcicgYXR0cmlidXRlIGlzIGRlc2VyaWFsaXplZCB0byBhCiAgICAgICAqIHByb3BlcnR5IG5hbWVkICdmb29CYXInLgogICAgICAgKgogICAgICAgKiAqIGByZWFkT25seWA6IHtib29sZWFufSBjcmVhdGVzIGEgcmVhZE9ubHkgcHJvcGVydHkgYW5kCiAgICAgICAqIG1ha2VzIGEgcHJpdmF0ZSBzZXR0ZXIgZm9yIHRoZSBwcml2YXRlIG9mIHRoZSBmb3JtICdfc2V0Rm9vJyBmb3IgYQogICAgICAgKiBwcm9wZXJ0eSAnZm9vJywKICAgICAgICoKICAgICAgICogKiBgY29tcHV0ZWRgOiB7c3RyaW5nfSBjcmVhdGVzIGEgY29tcHV0ZWQgcHJvcGVydHkuIEEgY29tcHV0ZWQgcHJvcGVydHkKICAgICAgICogaXMgYWxzbyBhdXRvbWF0aWNhbGx5IHNldCB0byBgcmVhZE9ubHk6IHRydWVgLiBUaGUgdmFsdWUgaXMgY2FsY3VsYXRlZAogICAgICAgKiBieSBydW5uaW5nIGEgbWV0aG9kIGFuZCBhcmd1bWVudHMgcGFyc2VkIGZyb20gdGhlIGdpdmVuIHN0cmluZy4gRm9yCiAgICAgICAqIGV4YW1wbGUgJ2NvbXB1dGUoZm9vKScgd2lsbCBjb21wdXRlIGEgZ2l2ZW4gcHJvcGVydHkgd2hlbiB0aGUKICAgICAgICogJ2ZvbycgcHJvcGVydHkgY2hhbmdlcyBieSBleGVjdXRpbmcgdGhlICdjb21wdXRlJyBtZXRob2QuIFRoaXMgbWV0aG9kCiAgICAgICAqIG11c3QgcmV0dXJuIHRoZSBjb21wdXRlZCB2YWx1ZS4KICAgICAgICoKICAgICAgICogKiBgcmVmbGVjdFRvQXR0cmlidXRlYDoge2Jvb2xlYW59IElmIHRydWUsIHRoZSBwcm9wZXJ0eSB2YWx1ZSBpcyByZWZsZWN0ZWQKICAgICAgICogdG8gYW4gYXR0cmlidXRlIG9mIHRoZSBzYW1lIG5hbWUuIE5vdGUsIHRoZSBhdHRyaWJ1dGUgaXMgZGFzaC1jYXNlZAogICAgICAgKiBzbyBhIHByb3BlcnR5IG5hbWVkICdmb29CYXInIGlzIHJlZmxlY3RlZCBhcyAnZm9vLWJhcicuCiAgICAgICAqCiAgICAgICAqICogYG5vdGlmeWA6IHtib29sZWFufSBzZW5kcyBhIG5vbi1idWJibGluZyBub3RpZmljYXRpb24gZXZlbnQgd2hlbgogICAgICAgKiB0aGUgcHJvcGVydHkgY2hhbmdlcy4gRm9yIGV4YW1wbGUsIGEgcHJvcGVydHkgbmFtZWQgJ2Zvbycgc2VuZHMgYW4KICAgICAgICogZXZlbnQgbmFtZWQgJ2Zvby1jaGFuZ2VkJyB3aXRoIGBldmVudC5kZXRhaWxgIHNldCB0byB0aGUgdmFsdWUgb2YKICAgICAgICogdGhlIHByb3BlcnR5LgogICAgICAgKgogICAgICAgKiAqIG9ic2VydmVyOiB7c3RyaW5nfSBuYW1lIG9mIGEgbWV0aG9kIHRoYXQgcnVucyB3aGVuIHRoZSBwcm9wZXJ0eQogICAgICAgKiBjaGFuZ2VzLiBUaGUgYXJndW1lbnRzIG9mIHRoZSBtZXRob2QgYXJlICh2YWx1ZSwgcHJldmlvdXNWYWx1ZSkuCiAgICAgICAqCiAgICAgICAqIE5vdGU6IFVzZXJzIG1heSB3YW50IGNvbnRyb2wgb3ZlciBtb2RpZnlpbmcgcHJvcGVydHkKICAgICAgICogZWZmZWN0cyB2aWEgc3ViY2xhc3NpbmcuIEZvciBleGFtcGxlLCBhIHVzZXIgbWlnaHQgd2FudCB0byBtYWtlIGEKICAgICAgICogcmVmbGVjdFRvQXR0cmlidXRlIHByb3BlcnR5IG5vdCBkbyBzbyBpbiBhIHN1YmNsYXNzLiBXZSd2ZSBjaG9zZW4gdG8KICAgICAgICogZGlzYWJsZSB0aGlzIGJlY2F1c2UgaXQgbGVhZHMgdG8gYWRkaXRpb25hbCBjb21wbGljYXRpb24uCiAgICAgICAqIEZvciBleGFtcGxlLCBhIHJlYWRPbmx5IGVmZmVjdCBnZW5lcmF0ZXMgYSBzcGVjaWFsIHNldHRlci4gSWYgYSBzdWJjbGFzcwogICAgICAgKiBkaXNhYmxlcyB0aGUgZWZmZWN0LCB0aGUgc2V0dGVyIHdvdWxkIGZhaWwgdW5leHBlY3RlZGx5LgogICAgICAgKiBCYXNlZCBvbiBmZWVkYmFjaywgd2UgbWF5IHdhbnQgdG8gdHJ5IHRvIG1ha2UgZWZmZWN0cyBtb3JlIG1hbGxlYWJsZQogICAgICAgKiBhbmQvb3IgcHJvdmlkZSBhbiBhZHZhbmNlZCBhcGkgZm9yIG1hbmlwdWxhdGluZyB0aGVtLgogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFQb2x5bWVyRWxlbWVudH0gcHJvdG8gRWxlbWVudCBjbGFzcyBwcm90b3R5cGUgdG8gYWRkIGFjY2Vzc29ycwogICAgICAgKiAgIGFuZCBlZmZlY3RzIHRvCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgdGhlIHByb3BlcnR5LgogICAgICAgKiBAcGFyYW0ge09iamVjdH0gaW5mbyBJbmZvIG9iamVjdCBmcm9tIHdoaWNoIHRvIGNyZWF0ZSBwcm9wZXJ0eSBlZmZlY3RzLgogICAgICAgKiBTdXBwb3J0ZWQga2V5czoKICAgICAgICogQHBhcmFtIHtPYmplY3R9IGFsbFByb3BzIEZsYXR0ZW5lZCBtYXAgb2YgYWxsIHByb3BlcnRpZXMgZGVmaW5lZCBpbiB0aGlzCiAgICAgICAqICAgZWxlbWVudCAoaW5jbHVkaW5nIGluaGVyaXRlZCBwcm9wZXJ0aWVzKQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgZnVuY3Rpb24gY3JlYXRlUHJvcGVydHlGcm9tQ29uZmlnKHByb3RvLCBuYW1lLCBpbmZvLCBhbGxQcm9wcykgewogICAgICAgIC8vIGNvbXB1dGVkIGZvcmNlcyByZWFkT25seS4uLgogICAgICAgIGlmIChpbmZvLmNvbXB1dGVkKSB7CiAgICAgICAgICBpbmZvLnJlYWRPbmx5ID0gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgLy8gTm90ZSwgc2luY2UgYWxsIGNvbXB1dGVkIHByb3BlcnRpZXMgYXJlIHJlYWRPbmx5LCB0aGlzIHByZXZlbnRzCiAgICAgICAgLy8gYWRkaW5nIGFkZGl0aW9uYWwgY29tcHV0ZWQgcHJvcGVydHkgZWZmZWN0cyAod2hpY2ggbGVhZHMgdG8gYSBjb25mdXNpbmcKICAgICAgICAvLyBzZXR1cCB3aGVyZSBtdWx0aXBsZSB0cmlnZ2VycyBmb3Igc2V0dGluZyBhIHByb3BlcnR5KQogICAgICAgIC8vIFdoaWxlIHdlIGRvIGhhdmUgYGhhc0NvbXB1dGVkRWZmZWN0YCB0aGlzIGlzIHNldCBvbiB0aGUgcHJvcGVydHkncwogICAgICAgIC8vIGRlcGVuZGVuY2llcyByYXRoZXIgdGhhbiBpdHNlbGYuCiAgICAgICAgaWYgKGluZm8uY29tcHV0ZWQpIHsKICAgICAgICAgIGlmIChwcm90by5faGFzUmVhZE9ubHlFZmZlY3QobmFtZSkpIHsKICAgICAgICAgICAgY29uc29sZS53YXJuKGBDYW5ub3QgcmVkZWZpbmUgY29tcHV0ZWQgcHJvcGVydHkgJyR7bmFtZX0nLmApOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcHJvdG8uX2NyZWF0ZUNvbXB1dGVkUHJvcGVydHkobmFtZSwgaW5mby5jb21wdXRlZCwgYWxsUHJvcHMpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoaW5mby5yZWFkT25seSAmJiAhcHJvdG8uX2hhc1JlYWRPbmx5RWZmZWN0KG5hbWUpKSB7CiAgICAgICAgICBwcm90by5fY3JlYXRlUmVhZE9ubHlQcm9wZXJ0eShuYW1lLCAhaW5mby5jb21wdXRlZCk7CiAgICAgICAgfSBlbHNlIGlmIChpbmZvLnJlYWRPbmx5ID09PSBmYWxzZSAmJiBwcm90by5faGFzUmVhZE9ubHlFZmZlY3QobmFtZSkpIHsKICAgICAgICAgIGNvbnNvbGUud2FybihgQ2Fubm90IG1ha2UgcmVhZE9ubHkgcHJvcGVydHkgJyR7bmFtZX0nIG5vbi1yZWFkT25seS5gKTsKICAgICAgICB9CiAgICAgICAgaWYgKGluZm8ucmVmbGVjdFRvQXR0cmlidXRlICYmICFwcm90by5faGFzUmVmbGVjdEVmZmVjdChuYW1lKSkgewogICAgICAgICAgcHJvdG8uX2NyZWF0ZVJlZmxlY3RlZFByb3BlcnR5KG5hbWUpOwogICAgICAgIH0gZWxzZSBpZiAoaW5mby5yZWZsZWN0VG9BdHRyaWJ1dGUgPT09IGZhbHNlICYmIHByb3RvLl9oYXNSZWZsZWN0RWZmZWN0KG5hbWUpKSB7CiAgICAgICAgICBjb25zb2xlLndhcm4oYENhbm5vdCBtYWtlIHJlZmxlY3RlZCBwcm9wZXJ0eSAnJHtuYW1lfScgbm9uLXJlZmxlY3RlZC5gKTsKICAgICAgICB9CiAgICAgICAgaWYgKGluZm8ubm90aWZ5ICYmICFwcm90by5faGFzTm90aWZ5RWZmZWN0KG5hbWUpKSB7CiAgICAgICAgICBwcm90by5fY3JlYXRlTm90aWZ5aW5nUHJvcGVydHkobmFtZSk7CiAgICAgICAgfSBlbHNlIGlmIChpbmZvLm5vdGlmeSA9PT0gZmFsc2UgJiYgcHJvdG8uX2hhc05vdGlmeUVmZmVjdChuYW1lKSkgewogICAgICAgICAgY29uc29sZS53YXJuKGBDYW5ub3QgbWFrZSBub3RpZnkgcHJvcGVydHkgJyR7bmFtZX0nIG5vbi1ub3RpZnkuYCk7CiAgICAgICAgfQogICAgICAgIC8vIGFsd2F5cyBhZGQgb2JzZXJ2ZXIKICAgICAgICBpZiAoaW5mby5vYnNlcnZlcikgewogICAgICAgICAgcHJvdG8uX2NyZWF0ZVByb3BlcnR5T2JzZXJ2ZXIobmFtZSwgaW5mby5vYnNlcnZlciwgYWxsUHJvcHNbaW5mby5vYnNlcnZlcl0pOwogICAgICAgIH0KICAgICAgICAvLyBhbHdheXMgY3JlYXRlIHRoZSBtYXBwaW5nIGZyb20gYXR0cmlidXRlIGJhY2sgdG8gcHJvcGVydHkgZm9yIGRlc2VyaWFsaXphdGlvbi4KICAgICAgICBwcm90by5fYWRkUHJvcGVydHlUb0F0dHJpYnV0ZU1hcChuYW1lKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFByb2Nlc3MgYWxsIHN0eWxlIGVsZW1lbnRzIGluIHRoZSBlbGVtZW50IHRlbXBsYXRlLiBTdHlsZXMgd2l0aCB0aGUKICAgICAgICogYGluY2x1ZGVgIGF0dHJpYnV0ZSBhcmUgcHJvY2Vzc2VkIHN1Y2ggdGhhdCBhbnkgc3R5bGVzIGluCiAgICAgICAqIHRoZSBhc3NvY2lhdGVkICJzdHlsZSBtb2R1bGVzIiBhcmUgaW5jbHVkZWQgaW4gdGhlIGVsZW1lbnQgdGVtcGxhdGUuCiAgICAgICAqIEBwYXJhbSB7UG9seW1lckVsZW1lbnRDb25zdHJ1Y3Rvcn0ga2xhc3MgRWxlbWVudCBjbGFzcwogICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZSBUZW1wbGF0ZSB0byBwcm9jZXNzCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBpcyBOYW1lIG9mIGVsZW1lbnQKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGJhc2VVUkkgQmFzZSBVUkkgZm9yIGVsZW1lbnQKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHByb2Nlc3NFbGVtZW50U3R5bGVzKGtsYXNzLCB0ZW1wbGF0ZSwgaXMsIGJhc2VVUkkpIHsKICAgICAgICBpZiAoIWJ1aWx0Q1NTKSB7CiAgICAgICAgICBjb25zdCB0ZW1wbGF0ZVN0eWxlcyA9IHRlbXBsYXRlLmNvbnRlbnQucXVlcnlTZWxlY3RvckFsbCgnc3R5bGUnKTsKICAgICAgICAgIGNvbnN0IHN0eWxlc1dpdGhJbXBvcnRzID0gc3R5bGVzRnJvbVRlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgICAgIC8vIGluc2VydCBzdHlsZXMgZnJvbSA8bGluayByZWw9ImltcG9ydCIgdHlwZT0iY3NzIj4gYXQgdGhlIHRvcCBvZiB0aGUgdGVtcGxhdGUKICAgICAgICAgIGNvbnN0IGxpbmtlZFN0eWxlcyA9IHN0eWxlc0Zyb21Nb2R1bGVJbXBvcnRzKGlzKTsKICAgICAgICAgIGNvbnN0IGZpcnN0VGVtcGxhdGVDaGlsZCA9IHRlbXBsYXRlLmNvbnRlbnQuZmlyc3RFbGVtZW50Q2hpbGQ7CiAgICAgICAgICBmb3IgKGxldCBpZHggPSAwOyBpZHggPCBsaW5rZWRTdHlsZXMubGVuZ3RoOyBpZHgrKykgewogICAgICAgICAgICBsZXQgcyA9IGxpbmtlZFN0eWxlc1tpZHhdOwogICAgICAgICAgICBzLnRleHRDb250ZW50ID0ga2xhc3MuX3Byb2Nlc3NTdHlsZVRleHQocy50ZXh0Q29udGVudCwgYmFzZVVSSSk7CiAgICAgICAgICAgIHRlbXBsYXRlLmNvbnRlbnQuaW5zZXJ0QmVmb3JlKHMsIGZpcnN0VGVtcGxhdGVDaGlsZCk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBrZWVwIHRyYWNrIG9mIHRoZSBsYXN0ICJjb25jcmV0ZSIgc3R5bGUgaW4gdGhlIHRlbXBsYXRlIHdlIGhhdmUgZW5jb3VudGVyZWQKICAgICAgICAgIGxldCB0ZW1wbGF0ZVN0eWxlSW5kZXggPSAwOwogICAgICAgICAgLy8gZW5zdXJlIGFsbCBnYXRoZXJlZCBzdHlsZXMgYXJlIGFjdHVhbGx5IGluIHRoaXMgdGVtcGxhdGUuCiAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHN0eWxlc1dpdGhJbXBvcnRzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGxldCBzID0gc3R5bGVzV2l0aEltcG9ydHNbaV07CiAgICAgICAgICAgIGxldCB0ZW1wbGF0ZVN0eWxlID0gdGVtcGxhdGVTdHlsZXNbdGVtcGxhdGVTdHlsZUluZGV4XTsKICAgICAgICAgICAgLy8gaWYgdGhlIHN0eWxlIGlzIG5vdCBpbiB0aGlzIHRlbXBsYXRlLCBpdCdzIGJlZW4gImluY2x1ZGVkIiBhbmQKICAgICAgICAgICAgLy8gd2UgcHV0IGEgY2xvbmUgb2YgaXQgaW4gdGhlIHRlbXBsYXRlIGJlZm9yZSB0aGUgc3R5bGUgdGhhdCBpbmNsdWRlZCBpdAogICAgICAgICAgICBpZiAodGVtcGxhdGVTdHlsZSAhPT0gcykgewogICAgICAgICAgICAgIHMgPSBzLmNsb25lTm9kZSh0cnVlKTsKICAgICAgICAgICAgICB0ZW1wbGF0ZVN0eWxlLnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKHMsIHRlbXBsYXRlU3R5bGUpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHRlbXBsYXRlU3R5bGVJbmRleCsrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHMudGV4dENvbnRlbnQgPSBrbGFzcy5fcHJvY2Vzc1N0eWxlVGV4dChzLnRleHRDb250ZW50LCBiYXNlVVJJKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKHdpbmRvdy5TaGFkeUNTUykgewogICAgICAgICAgd2luZG93LlNoYWR5Q1NTLnByZXBhcmVUZW1wbGF0ZSh0ZW1wbGF0ZSwgaXMpOwogICAgICAgIH0KICAgICAgICAvLyBTdXBwb3J0IGZvciBgYWRvcHRlZFN0eWxlc2hlZXRzYCByZWxpZXMgb24gdXNpbmcgbmF0aXZlIFNoYWRvdyBET00KICAgICAgICAvLyBhbmQgYnVpbHQgQ1NTLiBCdWlsdCBDU1MgaXMgcmVxdWlyZWQgYmVjYXVzZSBydW50aW1lIHRyYW5zZm9ybWF0aW9uIG9mCiAgICAgICAgLy8gYEBhcHBseWAgaXMgbm90IHN1cHBvcnRlZC4gVGhpcyBpcyBiZWNhdXNlIFNoYWR5Q1NTIHJlbGllcyBvbiBiZWluZyBhYmxlCiAgICAgICAgLy8gdG8gdXBkYXRlIGEgYHN0eWxlYCBlbGVtZW50IGluIHRoZSBlbGVtZW50IHRlbXBsYXRlIGFuZCB0aGlzIGlzCiAgICAgICAgLy8gcmVtb3ZlZCB3aGVuIHVzaW5nIGBhZG9wdGVkU3R5bGVTaGVldHNgLgogICAgICAgIC8vIE5vdGUsIGl0IHdvdWxkIGJlIG1vcmUgZWZmaWNpZW50IHRvIGFsbG93IHN0eWxlIGluY2x1ZGVzIHRvIGJlY29tZQogICAgICAgIC8vIHNlcGFyYXRlIHN0eWxlc2hlZXRzOyBob3dldmVyLCBiZWNhdXNlIG9mIGBAYXBwbHlgIHRoZXNlIGFyZQogICAgICAgIC8vIHBvdGVudGlhbGx5IG5vdCBzaGFyZWFibGUgYW5kIHNoYXJpbmcgdGhlIG9uZXMgdGhhdCBjb3VsZCBiZSBzaGFyZWQKICAgICAgICAvLyB3b3VsZCByZXF1aXJlIHNvbWUgY29vcmRpbmF0aW9uLiBUbyBrZWVwIGl0IHNpbXBsZSwgYWxsIHRoZSBpbmNsdWRlcwogICAgICAgIC8vIGFuZCBzdHlsZXMgYXJlIGNvbGxhcHNlZCBpbnRvIGEgc2luZ2xlIHNoYXJlYWJsZSBzdHlsZXNoZWV0LgogICAgICAgIGlmICh1c2VBZG9wdGVkU3R5bGVTaGVldHNXaXRoQnVpbHRDU1MgJiYgYnVpbHRDU1MgJiYKICAgICAgICAgICAgc3VwcG9ydHNBZG9wdGluZ1N0eWxlU2hlZXRzKSB7CiAgICAgICAgICAvLyBSZW1vdmUgc3R5bGVzIGluIHRlbXBsYXRlIGFuZCBtYWtlIGEgc2hhcmVhYmxlIHN0eWxlc2hlZXQKICAgICAgICAgIGNvbnN0IHN0eWxlcyA9IHRlbXBsYXRlLmNvbnRlbnQucXVlcnlTZWxlY3RvckFsbCgnc3R5bGUnKTsKICAgICAgICAgIGlmIChzdHlsZXMpIHsKICAgICAgICAgICAgbGV0IGNzcyA9ICcnOwogICAgICAgICAgICBBcnJheS5mcm9tKHN0eWxlcykuZm9yRWFjaChzID0+IHsKICAgICAgICAgICAgICBjc3MgKz0gcy50ZXh0Q29udGVudDsKICAgICAgICAgICAgICBzLnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQocyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBrbGFzcy5fc3R5bGVTaGVldCA9IG5ldyBDU1NTdHlsZVNoZWV0KCk7CiAgICAgICAgICAgIGtsYXNzLl9zdHlsZVNoZWV0LnJlcGxhY2VTeW5jKGNzcyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogTG9vayB1cCB0ZW1wbGF0ZSBmcm9tIGRvbS1tb2R1bGUgZm9yIGVsZW1lbnQKICAgICAgICoKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGlzIEVsZW1lbnQgbmFtZSB0byBsb29rIHVwCiAgICAgICAqIEByZXR1cm4gez9IVE1MVGVtcGxhdGVFbGVtZW50fHVuZGVmaW5lZH0gVGVtcGxhdGUgZm91bmQgaW4gZG9tIG1vZHVsZSwgb3IKICAgICAgICogICB1bmRlZmluZWQgaWYgbm90IGZvdW5kCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGdldFRlbXBsYXRlRnJvbURvbU1vZHVsZShpcykgewogICAgICAgIGxldCB0ZW1wbGF0ZSA9IG51bGw7CiAgICAgICAgLy8gVW5kZXIgc3RyaWN0VGVtcGxhdGVQb2xpY3kgaW4gMy54KywgZG9tLW1vZHVsZSBsb29rdXAgaXMgb25seSBhbGxvd2VkCiAgICAgICAgLy8gd2hlbiBvcHRlZC1pbiB2aWEgYWxsb3dUZW1wbGF0ZUZyb21Eb21Nb2R1bGUKICAgICAgICBpZiAoaXMgJiYgKCFzdHJpY3RUZW1wbGF0ZVBvbGljeSB8fCBhbGxvd1RlbXBsYXRlRnJvbURvbU1vZHVsZSkpIHsKICAgICAgICAgIHRlbXBsYXRlID0gLyoqIEB0eXBlIHs/SFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKAogICAgICAgICAgICAgIERvbU1vZHVsZS5pbXBvcnQoaXMsICd0ZW1wbGF0ZScpKTsKICAgICAgICAgIC8vIFVuZGVyIHN0cmljdFRlbXBsYXRlUG9saWN5LCByZXF1aXJlIGFueSBlbGVtZW50IHdpdGggYW4gYGlzYAogICAgICAgICAgLy8gc3BlY2lmaWVkIHRvIGhhdmUgYSBkb20tbW9kdWxlCiAgICAgICAgICBpZiAoc3RyaWN0VGVtcGxhdGVQb2xpY3kgJiYgIXRlbXBsYXRlKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgc3RyaWN0VGVtcGxhdGVQb2xpY3k6IGV4cGVjdGluZyBkb20tbW9kdWxlIG9yIG51bGwgdGVtcGxhdGUgZm9yICR7aXN9YCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiB0ZW1wbGF0ZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwb2x5bWVyCiAgICAgICAqIEBtaXhpbkNsYXNzCiAgICAgICAqIEB1bnJlc3RyaWN0ZWQKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfRWxlbWVudE1peGlufQogICAgICAgKiBAZXh0ZW5kcyB7cG9seW1lckVsZW1lbnRCYXNlfQogICAgICAgKi8KICAgICAgY2xhc3MgUG9seW1lckVsZW1lbnQgZXh0ZW5kcyBwb2x5bWVyRWxlbWVudEJhc2UgewoKICAgICAgICAvKioKICAgICAgICAgKiBDdXJyZW50IFBvbHltZXIgdmVyc2lvbiBpbiBTZW12ZXIgbm90YXRpb24uCiAgICAgICAgICogQHR5cGUge3N0cmluZ30gU2VtdmVyIG5vdGF0aW9uIG9mIHRoZSBjdXJyZW50IHZlcnNpb24gb2YgUG9seW1lci4KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBnZXQgcG9seW1lckVsZW1lbnRWZXJzaW9uKCkgewogICAgICAgICAgcmV0dXJuIHZlcnNpb247CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZSBvZiBQcm9wZXJ0aWVzTWl4aW4gX2ZpbmFsaXplQ2xhc3MgdG8gY3JlYXRlIG9ic2VydmVycyBhbmQKICAgICAgICAgKiBmaW5kIHRoZSB0ZW1wbGF0ZS4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfZmluYWxpemVDbGFzcygpIHsKICAgICAgICAgIC8vIFRPRE8oaHR0cHM6Ly9naXRodWIuY29tL2dvb2dsZS9jbG9zdXJlLWNvbXBpbGVyL2lzc3Vlcy8zMjQwKToKICAgICAgICAgIC8vICAgICBDaGFuZ2UgYmFjayB0byBqdXN0IHN1cGVyLm1ldGhvZENhbGwoKQogICAgICAgICAgcG9seW1lckVsZW1lbnRCYXNlLl9maW5hbGl6ZUNsYXNzLmNhbGwodGhpcyk7CiAgICAgICAgICBjb25zdCBvYnNlcnZlcnMgPSBvd25PYnNlcnZlcnModGhpcyk7CiAgICAgICAgICBpZiAob2JzZXJ2ZXJzKSB7CiAgICAgICAgICAgIHRoaXMuY3JlYXRlT2JzZXJ2ZXJzKG9ic2VydmVycywgdGhpcy5fcHJvcGVydGllcyk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9wcmVwYXJlVGVtcGxhdGUoKTsKICAgICAgICB9CgogICAgICAgIC8qKiBAbm9jb2xsYXBzZSAqLwogICAgICAgIHN0YXRpYyBfcHJlcGFyZVRlbXBsYXRlKCkgewogICAgICAgICAgLy8gbm90ZTogY3JlYXRlICJ3b3JraW5nIiB0ZW1wbGF0ZSB0aGF0IGlzIGZpbmFsaXplZCBhdCBpbnN0YW5jZSB0aW1lCiAgICAgICAgICBsZXQgdGVtcGxhdGUgPSAvKiogQHR5cGUge1BvbHltZXJFbGVtZW50Q29uc3RydWN0b3J9ICovICh0aGlzKS50ZW1wbGF0ZTsKICAgICAgICAgIGlmICh0ZW1wbGF0ZSkgewogICAgICAgICAgICBpZiAodHlwZW9mIHRlbXBsYXRlID09PSAnc3RyaW5nJykgewogICAgICAgICAgICAgIGNvbnNvbGUuZXJyb3IoJ3RlbXBsYXRlIGdldHRlciBtdXN0IHJldHVybiBIVE1MVGVtcGxhdGVFbGVtZW50Jyk7CiAgICAgICAgICAgICAgdGVtcGxhdGUgPSBudWxsOwogICAgICAgICAgICB9IGVsc2UgaWYgKCFsZWdhY3lPcHRpbWl6YXRpb25zKSB7CiAgICAgICAgICAgICAgdGVtcGxhdGUgPSB0ZW1wbGF0ZS5jbG9uZU5vZGUodHJ1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fdGVtcGxhdGUgPSB0ZW1wbGF0ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlIG9mIFByb3BlcnRpZXNDaGFuZ2VkIGNyZWF0ZVByb3BlcnRpZXMgdG8gY3JlYXRlIGFjY2Vzc29ycwogICAgICAgICAqIGFuZCBwcm9wZXJ0eSBlZmZlY3RzIGZvciBhbGwgb2YgdGhlIHByb3BlcnRpZXMuCiAgICAgICAgICogQHBhcmFtIHshT2JqZWN0fSBwcm9wcyAuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgY3JlYXRlUHJvcGVydGllcyhwcm9wcykgewogICAgICAgICAgZm9yIChsZXQgcCBpbiBwcm9wcykgewogICAgICAgICAgICBjcmVhdGVQcm9wZXJ0eUZyb21Db25maWcoCiAgICAgICAgICAgICAgICAvKiogQHR5cGUgez99ICovICh0aGlzLnByb3RvdHlwZSksIHAsIHByb3BzW3BdLCBwcm9wcyk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIG9ic2VydmVycyBmb3IgdGhlIGdpdmVuIGBvYnNlcnZlcnNgIGFycmF5LgogICAgICAgICAqIExldmVyYWdlcyBgUHJvcGVydHlFZmZlY3RzYCB0byBjcmVhdGUgb2JzZXJ2ZXJzLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYnNlcnZlcnMgQXJyYXkgb2Ygb2JzZXJ2ZXIgZGVzY3JpcHRvcnMgZm9yCiAgICAgICAgICogICB0aGlzIGNsYXNzCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IGR5bmFtaWNGbnMgT2JqZWN0IGNvbnRhaW5pbmcga2V5cyBmb3IgYW55IHByb3BlcnRpZXMKICAgICAgICAgKiAgIHRoYXQgYXJlIGZ1bmN0aW9ucyBhbmQgc2hvdWxkIHRyaWdnZXIgdGhlIGVmZmVjdCB3aGVuIHRoZSBmdW5jdGlvbgogICAgICAgICAqICAgcmVmZXJlbmNlIGlzIGNoYW5nZWQKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBjcmVhdGVPYnNlcnZlcnMob2JzZXJ2ZXJzLCBkeW5hbWljRm5zKSB7CiAgICAgICAgICBjb25zdCBwcm90byA9IHRoaXMucHJvdG90eXBlOwogICAgICAgICAgZm9yIChsZXQgaT0wOyBpIDwgb2JzZXJ2ZXJzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIHByb3RvLl9jcmVhdGVNZXRob2RPYnNlcnZlcihvYnNlcnZlcnNbaV0sIGR5bmFtaWNGbnMpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgdGVtcGxhdGUgdGhhdCB3aWxsIGJlIHN0YW1wZWQgaW50byB0aGlzIGVsZW1lbnQncyBzaGFkb3cgcm9vdC4KICAgICAgICAgKgogICAgICAgICAqIElmIGEgYHN0YXRpYyBnZXQgaXMoKWAgZ2V0dGVyIGlzIGRlZmluZWQsIHRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIHdpbGwKICAgICAgICAgKiByZXR1cm4gdGhlIGZpcnN0IGA8dGVtcGxhdGU+YCBpbiBhIGBkb20tbW9kdWxlYCB3aG9zZSBgaWRgIG1hdGNoZXMgdGhpcwogICAgICAgICAqIGVsZW1lbnQncyBgaXNgIChub3RlIHRoYXQgYSBgX3RlbXBsYXRlYCBwcm9wZXJ0eSBvbiB0aGUgY2xhc3MgcHJvdG90eXBlCiAgICAgICAgICogdGFrZXMgcHJlY2VkZW5jZSBvdmVyIHRoZSBgZG9tLW1vZHVsZWAgdGVtcGxhdGUsIHRvIG1haW50YWluIGxlZ2FjeQogICAgICAgICAqIGVsZW1lbnQgc2VtYW50aWNzOyBhIHN1YmNsYXNzIHdpbGwgc3Vic2VxdWVudGx5IGZhbGwgYmFjayB0byBpdHMgc3VwZXIKICAgICAgICAgKiBjbGFzcyB0ZW1wbGF0ZSBpZiBuZWl0aGVyIGEgYHByb3RvdHlwZS5fdGVtcGxhdGVgIG9yIGEgYGRvbS1tb2R1bGVgIGZvcgogICAgICAgICAqIHRoZSBjbGFzcydzIGBpc2Agd2FzIGZvdW5kKS4KICAgICAgICAgKgogICAgICAgICAqIFVzZXJzIG1heSBvdmVycmlkZSB0aGlzIGdldHRlciB0byByZXR1cm4gYW4gYXJiaXRyYXJ5IHRlbXBsYXRlCiAgICAgICAgICogKGluIHdoaWNoIGNhc2UgdGhlIGBpc2AgZ2V0dGVyIGlzIHVubmVjZXNzYXJ5KS4gVGhlIHRlbXBsYXRlIHJldHVybmVkCiAgICAgICAgICogbXVzdCBiZSBhbiBgSFRNTFRlbXBsYXRlRWxlbWVudGAuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlIHRoYXQgd2hlbiBzdWJjbGFzc2luZywgaWYgdGhlIHN1cGVyIGNsYXNzIG92ZXJyb2RlIHRoZSBkZWZhdWx0CiAgICAgICAgICogaW1wbGVtZW50YXRpb24gYW5kIHRoZSBzdWJjbGFzcyB3b3VsZCBsaWtlIHRvIHByb3ZpZGUgYW4gYWx0ZXJuYXRlCiAgICAgICAgICogdGVtcGxhdGUgdmlhIGEgYGRvbS1tb2R1bGVgLCBpdCBzaG91bGQgb3ZlcnJpZGUgdGhpcyBnZXR0ZXIgYW5kCiAgICAgICAgICogcmV0dXJuIGBEb21Nb2R1bGUuaW1wb3J0KHRoaXMuaXMsICd0ZW1wbGF0ZScpYC4KICAgICAgICAgKgogICAgICAgICAqIElmIGEgc3ViY2xhc3Mgd291bGQgbGlrZSB0byBtb2RpZnkgdGhlIHN1cGVyIGNsYXNzIHRlbXBsYXRlLCBpdCBzaG91bGQKICAgICAgICAgKiBjbG9uZSBpdCByYXRoZXIgdGhhbiBtb2RpZnkgaXQgaW4gcGxhY2UuICBJZiB0aGUgZ2V0dGVyIGRvZXMgZXhwZW5zaXZlCiAgICAgICAgICogd29yayBzdWNoIGFzIGNsb25pbmcvbW9kaWZ5aW5nIGEgdGVtcGxhdGUsIGl0IHNob3VsZCBtZW1vaXplIHRoZQogICAgICAgICAqIHRlbXBsYXRlIGZvciBtYXhpbXVtIHBlcmZvcm1hbmNlOgogICAgICAgICAqCiAgICAgICAgICogICBsZXQgbWVtb2l6ZWRUZW1wbGF0ZTsKICAgICAgICAgKiAgIGNsYXNzIE15U3ViQ2xhc3MgZXh0ZW5kcyBNeVN1cGVyQ2xhc3MgewogICAgICAgICAqICAgICBzdGF0aWMgZ2V0IHRlbXBsYXRlKCkgewogICAgICAgICAqICAgICAgIGlmICghbWVtb2l6ZWRUZW1wbGF0ZSkgewogICAgICAgICAqICAgICAgICAgbWVtb2l6ZWRUZW1wbGF0ZSA9IHN1cGVyLnRlbXBsYXRlLmNsb25lTm9kZSh0cnVlKTsKICAgICAgICAgKiAgICAgICAgIGxldCBzdWJDb250ZW50ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgICogICAgICAgICBzdWJDb250ZW50LnRleHRDb250ZW50ID0gJ1RoaXMgY2FtZSBmcm9tIE15U3ViQ2xhc3MnOwogICAgICAgICAqICAgICAgICAgbWVtb2l6ZWRUZW1wbGF0ZS5jb250ZW50LmFwcGVuZENoaWxkKHN1YkNvbnRlbnQpOwogICAgICAgICAqICAgICAgIH0KICAgICAgICAgKiAgICAgICByZXR1cm4gbWVtb2l6ZWRUZW1wbGF0ZTsKICAgICAgICAgKiAgICAgfQogICAgICAgICAqICAgfQogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR8c3RyaW5nfSBUZW1wbGF0ZSB0byBiZSBzdGFtcGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgZ2V0IHRlbXBsYXRlKCkgewogICAgICAgICAgLy8gRXhwbGFuYXRpb24gb2YgdGVtcGxhdGUtcmVsYXRlZCBwcm9wZXJ0aWVzOgogICAgICAgICAgLy8gLSBjb25zdHJ1Y3Rvci50ZW1wbGF0ZSAodGhpcyBnZXR0ZXIpOiB0aGUgdGVtcGxhdGUgZm9yIHRoZSBjbGFzcy4KICAgICAgICAgIC8vICAgICBUaGlzIGNhbiBjb21lIGZyb20gdGhlIHByb3RvdHlwZSAoZm9yIGxlZ2FjeSBlbGVtZW50cyksIGZyb20gYQogICAgICAgICAgLy8gICAgIGRvbS1tb2R1bGUsIG9yIGZyb20gdGhlIHN1cGVyIGNsYXNzJ3MgdGVtcGxhdGUgKG9yIGNhbiBiZSBvdmVycmlkZGVuCiAgICAgICAgICAvLyAgICAgYWx0b2dldGhlciBieSB0aGUgdXNlcikKICAgICAgICAgIC8vIC0gY29uc3RydWN0b3IuX3RlbXBsYXRlOiBtZW1vaXplZCB2ZXJzaW9uIG9mIGNvbnN0cnVjdG9yLnRlbXBsYXRlCiAgICAgICAgICAvLyAtIHByb3RvdHlwZS5fdGVtcGxhdGU6IHdvcmtpbmcgdGVtcGxhdGUgZm9yIHRoZSBlbGVtZW50LCB3aGljaCB3aWxsIGJlCiAgICAgICAgICAvLyAgICAgcGFyc2VkIGFuZCBtb2RpZmllZCBpbiBwbGFjZS4gSXQgaXMgYSBjbG9uZWQgdmVyc2lvbiBvZgogICAgICAgICAgLy8gICAgIGNvbnN0cnVjdG9yLnRlbXBsYXRlLCBzYXZlZCBpbiBfZmluYWxpemVDbGFzcygpLiBOb3RlIHRoYXQgYmVmb3JlCiAgICAgICAgICAvLyAgICAgdGhpcyBnZXR0ZXIgaXMgY2FsbGVkLCBmb3IgbGVnYWN5IGVsZW1lbnRzIHRoaXMgY291bGQgYmUgZnJvbSBhCiAgICAgICAgICAvLyAgICAgX3RlbXBsYXRlIGZpZWxkIG9uIHRoZSBpbmZvIG9iamVjdCBwYXNzZWQgdG8gUG9seW1lcigpLCBhIGJlaGF2aW9yLAogICAgICAgICAgLy8gICAgIG9yIHNldCBpbiByZWdpc3RlcmVkKCk7IG9uY2UgdGhlIHN0YXRpYyBnZXR0ZXIgcnVucywgYSBjbG9uZSBvZiBpdAogICAgICAgICAgLy8gICAgIHdpbGwgb3ZlcndyaXRlIGl0IG9uIHRoZSBwcm90b3R5cGUgYXMgdGhlIHdvcmtpbmcgdGVtcGxhdGUuCiAgICAgICAgICBpZiAoIXRoaXMuaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX3RlbXBsYXRlJywgdGhpcykpKSB7CiAgICAgICAgICAgIGNvbnN0IHByb3RvVGVtcGxhdGUgPSB0aGlzLnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eSgKICAgICAgICAgICAgICBKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdfdGVtcGxhdGUnLCB0aGlzLnByb3RvdHlwZSkpID8KICAgICAgICAgICAgICB0aGlzLnByb3RvdHlwZS5fdGVtcGxhdGUgOiB1bmRlZmluZWQ7CiAgICAgICAgICAgIHRoaXMuX3RlbXBsYXRlID0KICAgICAgICAgICAgICAvLyBJZiB1c2VyIGhhcyBwdXQgdGVtcGxhdGUgb24gcHJvdG90eXBlIChlLmcuIGluIGxlZ2FjeSB2aWEgcmVnaXN0ZXJlZAogICAgICAgICAgICAgIC8vIGNhbGxiYWNrIG9yIGluZm8gb2JqZWN0KSwgcHJlZmVyIHRoYXQgZmlyc3QuIE5vdGUgdGhhdCBgbnVsbGAgaXMKICAgICAgICAgICAgICAvLyB1c2VkIGFzIGEgc2VudGluZWwgdG8gaW5kaWNhdGUgIm5vIHRlbXBsYXRlIiBhbmQgY2FuIGJlIHVzZWQgdG8KICAgICAgICAgICAgICAvLyBvdmVycmlkZSBhIHN1cGVyIHRlbXBsYXRlLCB3aGVyZWFzIGB1bmRlZmluZWRgIGlzIHVzZWQgYXMgYQogICAgICAgICAgICAgIC8vIHNlbnRpbmVsIHRvIG1lYW4gImZhbGwtYmFjayB0byBkZWZhdWx0IHRlbXBsYXRlIGxvb2t1cCIgdmlhCiAgICAgICAgICAgICAgLy8gZG9tLW1vZHVsZSBhbmQvb3Igc3VwZXIudGVtcGxhdGUuCiAgICAgICAgICAgICAgcHJvdG9UZW1wbGF0ZSAhPT0gdW5kZWZpbmVkID8gcHJvdG9UZW1wbGF0ZSA6CiAgICAgICAgICAgICAgLy8gTG9vayBpbiBkb20tbW9kdWxlIGFzc29jaWF0ZWQgd2l0aCB0aGlzIGVsZW1lbnQncyBpcwogICAgICAgICAgICAgICgodGhpcy5oYXNPd25Qcm9wZXJ0eShKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdpcycsIHRoaXMpKSAmJgogICAgICAgICAgICAgIChnZXRUZW1wbGF0ZUZyb21Eb21Nb2R1bGUoLyoqIEB0eXBlIHtQb2x5bWVyRWxlbWVudENvbnN0cnVjdG9yfSovICh0aGlzKS5pcykpKSB8fAogICAgICAgICAgICAgIC8vIE5leHQgbG9vayBmb3Igc3VwZXJjbGFzcyB0ZW1wbGF0ZSAoY2FsbCB0aGUgc3VwZXIgaW1wbCB0aGlzCiAgICAgICAgICAgICAgLy8gd2F5IHNvIHRoYXQgYHRoaXNgIHBvaW50cyB0byB0aGUgc3VwZXJjbGFzcykKICAgICAgICAgICAgICBPYmplY3QuZ2V0UHJvdG90eXBlT2YoLyoqIEB0eXBlIHtQb2x5bWVyRWxlbWVudENvbnN0cnVjdG9yfSovICh0aGlzKS5wcm90b3R5cGUpLmNvbnN0cnVjdG9yLnRlbXBsYXRlKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0aGlzLl90ZW1wbGF0ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0aGUgdGVtcGxhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fHN0cmluZ30gdmFsdWUgVGVtcGxhdGUgdG8gc2V0LgogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIHNldCB0ZW1wbGF0ZSh2YWx1ZSkgewogICAgICAgICAgdGhpcy5fdGVtcGxhdGUgPSB2YWx1ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBhdGggbWF0Y2hpbmcgdGhlIHVybCBmcm9tIHdoaWNoIHRoZSBlbGVtZW50IHdhcyBpbXBvcnRlZC4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgcGF0aCBpcyB1c2VkIHRvIHJlc29sdmUgdXJsJ3MgaW4gdGVtcGxhdGUgc3R5bGUgY3NzVGV4dC4KICAgICAgICAgKiBUaGUgYGltcG9ydFBhdGhgIHByb3BlcnR5IGlzIGFsc28gc2V0IG9uIGVsZW1lbnQgaW5zdGFuY2VzIGFuZCBjYW4gYmUKICAgICAgICAgKiB1c2VkIHRvIGNyZWF0ZSBiaW5kaW5ncyByZWxhdGl2ZSB0byB0aGUgaW1wb3J0IHBhdGguCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgZWxlbWVudHMgZGVmaW5lZCBpbiBFUyBtb2R1bGVzLCB1c2VycyBzaG91bGQgaW1wbGVtZW50CiAgICAgICAgICogYHN0YXRpYyBnZXQgaW1wb3J0TWV0YSgpIHsgcmV0dXJuIGltcG9ydC5tZXRhOyB9YCwgYW5kIHRoZSBkZWZhdWx0CiAgICAgICAgICogaW1wbGVtZW50YXRpb24gb2YgYGltcG9ydFBhdGhgIHdpbGwgIHJldHVybiBgaW1wb3J0Lm1ldGEudXJsYCdzIHBhdGguCiAgICAgICAgICogRm9yIGVsZW1lbnRzIGRlZmluZWQgaW4gSFRNTCBpbXBvcnRzLCB0aGlzIGdldHRlciB3aWxsIHJldHVybiB0aGUgcGF0aAogICAgICAgICAqIHRvIHRoZSBkb2N1bWVudCBjb250YWluaW5nIGEgYGRvbS1tb2R1bGVgIGVsZW1lbnQgbWF0Y2hpbmcgdGhpcwogICAgICAgICAqIGVsZW1lbnQncyBzdGF0aWMgYGlzYCBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIE5vdGUsIHRoaXMgcGF0aCBzaG91bGQgY29udGFpbiBhIHRyYWlsaW5nIGAvYC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gVGhlIGltcG9ydCBwYXRoIGZvciB0aGlzIGVsZW1lbnQgY2xhc3MKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfQogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIGdldCBpbXBvcnRQYXRoKCkgewogICAgICAgICAgaWYgKCF0aGlzLmhhc093blByb3BlcnR5KEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ19pbXBvcnRQYXRoJywgdGhpcykpKSB7CiAgICAgICAgICAgIGNvbnN0IG1ldGEgPSB0aGlzLmltcG9ydE1ldGE7CiAgICAgICAgICAgIGlmIChtZXRhKSB7CiAgICAgICAgICAgICAgdGhpcy5faW1wb3J0UGF0aCA9IHBhdGhGcm9tVXJsKG1ldGEudXJsKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBjb25zdCBtb2R1bGUgPSBEb21Nb2R1bGUuaW1wb3J0KC8qKiBAdHlwZSB7UG9seW1lckVsZW1lbnRDb25zdHJ1Y3Rvcn0gKi8gKHRoaXMpLmlzKTsKICAgICAgICAgICAgICB0aGlzLl9pbXBvcnRQYXRoID0gKG1vZHVsZSAmJiBtb2R1bGUuYXNzZXRwYXRoKSB8fAogICAgICAgICAgICAgICAgT2JqZWN0LmdldFByb3RvdHlwZU9mKC8qKiBAdHlwZSB7UG9seW1lckVsZW1lbnRDb25zdHJ1Y3Rvcn0qLyAodGhpcykucHJvdG90eXBlKS5jb25zdHJ1Y3Rvci5pbXBvcnRQYXRoOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdGhpcy5faW1wb3J0UGF0aDsKICAgICAgICB9CgogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgc3VwZXIoKTsKICAgICAgICAgIC8qKiBAdHlwZSB7SFRNTFRlbXBsYXRlRWxlbWVudH0gKi8KICAgICAgICAgIHRoaXMuX3RlbXBsYXRlOwogICAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd9ICovCiAgICAgICAgICB0aGlzLl9pbXBvcnRQYXRoOwogICAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd9ICovCiAgICAgICAgICB0aGlzLnJvb3RQYXRoOwogICAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd9ICovCiAgICAgICAgICB0aGlzLmltcG9ydFBhdGg7CiAgICAgICAgICAvKiogQHR5cGUge1N0YW1wZWRUZW1wbGF0ZSB8IEhUTUxFbGVtZW50IHwgU2hhZG93Um9vdH0gKi8KICAgICAgICAgIHRoaXMucm9vdDsKICAgICAgICAgIC8qKiBAdHlwZSB7IU9iamVjdDxzdHJpbmcsICFFbGVtZW50Pn0gKi8KICAgICAgICAgIHRoaXMuJDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyB0aGUgZGVmYXVsdCBgUHJvcGVydHlBY2Nlc3NvcnNgIHRvIGVuc3VyZSBjbGFzcwogICAgICAgICAqIG1ldGFwcm9ncmFtbWluZyByZWxhdGVkIHRvIHByb3BlcnR5IGFjY2Vzc29ycyBhbmQgZWZmZWN0cyBoYXMKICAgICAgICAgKiBjb21wbGV0ZWQgKGNhbGxzIGBmaW5hbGl6ZWApLgogICAgICAgICAqCiAgICAgICAgICogSXQgYWxzbyBpbml0aWFsaXplcyBhbnkgcHJvcGVydHkgZGVmYXVsdHMgcHJvdmlkZWQgdmlhIGB2YWx1ZWAgaW4KICAgICAgICAgKiBgcHJvcGVydGllc2AgbWV0YWRhdGEuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzLG1pc3NpbmdQcm9wZXJ0aWVzfSBnby9taXNzaW5nZm5wcm9wcwogICAgICAgICAqLwogICAgICAgIF9pbml0aWFsaXplUHJvcGVydGllcygpIHsKICAgICAgICAgIHRoaXMuY29uc3RydWN0b3IuZmluYWxpemUoKTsKICAgICAgICAgIC8vIG5vdGU6IGZpbmFsaXplIHRlbXBsYXRlIHdoZW4gd2UgaGF2ZSBhY2Nlc3MgdG8gYGxvY2FsTmFtZWAgdG8KICAgICAgICAgIC8vIGF2b2lkIGRlcGVuZGVuY2Ugb24gYGlzYCBmb3IgcG9seWZpbGxpbmcgc3R5bGluZy4KICAgICAgICAgIHRoaXMuY29uc3RydWN0b3IuX2ZpbmFsaXplVGVtcGxhdGUoLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovKHRoaXMpLmxvY2FsTmFtZSk7CiAgICAgICAgICBzdXBlci5faW5pdGlhbGl6ZVByb3BlcnRpZXMoKTsKICAgICAgICAgIC8vIHNldCBwYXRoIGRlZmF1bHRzCiAgICAgICAgICB0aGlzLnJvb3RQYXRoID0gcm9vdFBhdGg7CiAgICAgICAgICB0aGlzLmltcG9ydFBhdGggPSB0aGlzLmNvbnN0cnVjdG9yLmltcG9ydFBhdGg7CiAgICAgICAgICAvLyBhcHBseSBwcm9wZXJ0eSBkZWZhdWx0cy4uLgogICAgICAgICAgbGV0IHAkID0gcHJvcGVydHlEZWZhdWx0cyh0aGlzLmNvbnN0cnVjdG9yKTsKICAgICAgICAgIGlmICghcCQpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgZm9yIChsZXQgcCBpbiBwJCkgewogICAgICAgICAgICBsZXQgaW5mbyA9IHAkW3BdOwogICAgICAgICAgICBpZiAodGhpcy5fY2FuQXBwbHlQcm9wZXJ0eURlZmF1bHQocCkpIHsKICAgICAgICAgICAgICBsZXQgdmFsdWUgPSB0eXBlb2YgaW5mby52YWx1ZSA9PSAnZnVuY3Rpb24nID8KICAgICAgICAgICAgICAgIGluZm8udmFsdWUuY2FsbCh0aGlzKSA6CiAgICAgICAgICAgICAgICBpbmZvLnZhbHVlOwogICAgICAgICAgICAgIC8vIFNldCB2aWEgYF9zZXRQcm9wZXJ0eWAgaWYgdGhlcmUgaXMgYW4gYWNjZXNzb3IsIHRvIGVuYWJsZQogICAgICAgICAgICAgIC8vIGluaXRpYWxpemluZyByZWFkT25seSBwcm9wZXJ0eSBkZWZhdWx0cwogICAgICAgICAgICAgIGlmICh0aGlzLl9oYXNBY2Nlc3NvcihwKSkgewogICAgICAgICAgICAgICAgdGhpcy5fc2V0UGVuZGluZ1Byb3BlcnR5KHAsIHZhbHVlLCB0cnVlKTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgdGhpc1twXSA9IHZhbHVlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRGV0ZXJtaW5lcyBpZiBhIHByb3BlcnR5IGRmZWF1bHQgY2FuIGJlIGFwcGxpZWQuIEZvciBleGFtcGxlLCB0aGlzCiAgICAgICAgICogcHJldmVudHMgYSBkZWZhdWx0IGZyb20gYmVpbmcgYXBwbGllZCB3aGVuIGEgcHJvcGVydHkgdGhhdCBoYXMgbm8KICAgICAgICAgKiBhY2Nlc3NvciBpcyBvdmVycmlkZGVuIGJ5IGl0cyBob3N0IGJlZm9yZSB1cGdyYWRlIChlLmcuIHZpYSBhIGJpbmRpbmcpLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBOYW1lIG9mIHRoZSBwcm9wZXJ0eQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFJldHVybnMgdHJ1ZSBpZiB0aGUgcHJvcGVydHkgZGVmYXVsdCBjYW4gYmUgYXBwbGllZC4KICAgICAgICAgKi8KICAgICAgICBfY2FuQXBwbHlQcm9wZXJ0eURlZmF1bHQocHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiAhdGhpcy5oYXNPd25Qcm9wZXJ0eShwcm9wZXJ0eSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHYXRoZXIgc3R5bGUgdGV4dCBmb3IgYSBzdHlsZSBlbGVtZW50IGluIHRoZSB0ZW1wbGF0ZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NUZXh0IFRleHQgY29udGFpbmluZyBzdHlsaW5nIHRvIHByb2Nlc3MKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gYmFzZVVSSSBCYXNlIFVSSSB0byByZWJhc2UgQ1NTIHBhdGhzIGFnYWluc3QKICAgICAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSBwcm9jZXNzZWQgQ1NTIHRleHQKICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3Byb2Nlc3NTdHlsZVRleHQoY3NzVGV4dCwgYmFzZVVSSSkgewogICAgICAgICAgcmV0dXJuIHJlc29sdmVDc3MoY3NzVGV4dCwgYmFzZVVSSSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAqIENvbmZpZ3VyZXMgYW4gZWxlbWVudCBgcHJvdG9gIHRvIGZ1bmN0aW9uIHdpdGggYSBnaXZlbiBgdGVtcGxhdGVgLgogICAgICAgICogVGhlIGVsZW1lbnQgbmFtZSBgaXNgIGFuZCBleHRlbmRzIGBleHRgIG11c3QgYmUgc3BlY2lmaWVkIGZvciBTaGFkeUNTUwogICAgICAgICogc3R5bGUgc2NvcGluZy4KICAgICAgICAqCiAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gaXMgVGFnIG5hbWUgKG9yIHR5cGUgZXh0ZW5zaW9uIG5hbWUpIGZvciB0aGlzIGVsZW1lbnQKICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICovCiAgICAgICAgc3RhdGljIF9maW5hbGl6ZVRlbXBsYXRlKGlzKSB7CiAgICAgICAgICAvKiogQGNvbnN0IHtIVE1MVGVtcGxhdGVFbGVtZW50fSAqLwogICAgICAgICAgY29uc3QgdGVtcGxhdGUgPSB0aGlzLnByb3RvdHlwZS5fdGVtcGxhdGU7CiAgICAgICAgICBpZiAodGVtcGxhdGUgJiYgIXRlbXBsYXRlLl9fcG9seW1lckZpbmFsaXplZCkgewogICAgICAgICAgICB0ZW1wbGF0ZS5fX3BvbHltZXJGaW5hbGl6ZWQgPSB0cnVlOwogICAgICAgICAgICBjb25zdCBpbXBvcnRQYXRoID0gdGhpcy5pbXBvcnRQYXRoOwogICAgICAgICAgICBjb25zdCBiYXNlVVJJID0gaW1wb3J0UGF0aCA/IHJlc29sdmVVcmwoaW1wb3J0UGF0aCkgOiAnJzsKICAgICAgICAgICAgLy8gZS5nLiBzdXBwb3J0IGBpbmNsdWRlPSJtb2R1bGUtbmFtZSJgLCBhbmQgU2hhZHlDU1MKICAgICAgICAgICAgcHJvY2Vzc0VsZW1lbnRTdHlsZXModGhpcywgdGVtcGxhdGUsIGlzLCBiYXNlVVJJKTsKICAgICAgICAgICAgdGhpcy5wcm90b3R5cGUuX2JpbmRUZW1wbGF0ZSh0ZW1wbGF0ZSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQcm92aWRlcyBhIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhlIHN0YW5kYXJkIEN1c3RvbSBFbGVtZW50cwogICAgICAgICAqIGBjb25uZWN0ZWRDYWxsYmFja2AuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBlbmFibGVzIHRoZSBwcm9wZXJ0eSBlZmZlY3RzIHN5c3RlbSBhbmQKICAgICAgICAgKiBmbHVzaGVzIGFueSBwZW5kaW5nIHByb3BlcnRpZXMsIGFuZCB1cGRhdGVzIHNoaW1tZWQgQ1NTIHByb3BlcnRpZXMKICAgICAgICAgKiB3aGVuIHVzaW5nIHRoZSBTaGFkeUNTUyBzY29waW5nL2N1c3RvbSBwcm9wZXJ0aWVzIHBvbHlmaWxsLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllcywgaW52YWxpZENhc3RzfSBTdXBlciBtYXkgb3IgbWF5IG5vdAogICAgICAgICAqICAgICBpbXBsZW1lbnQgdGhlIGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICAgIGlmICh3aW5kb3cuU2hhZHlDU1MgJiYgdGhpcy5fdGVtcGxhdGUpIHsKICAgICAgICAgICAgd2luZG93LlNoYWR5Q1NTLnN0eWxlRWxlbWVudCgvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8odGhpcykpOwogICAgICAgICAgfQogICAgICAgICAgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFN0YW1wcyB0aGUgZWxlbWVudCB0ZW1wbGF0ZS4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgcmVhZHkoKSB7CiAgICAgICAgICBpZiAodGhpcy5fdGVtcGxhdGUpIHsKICAgICAgICAgICAgdGhpcy5yb290ID0gdGhpcy5fc3RhbXBUZW1wbGF0ZSh0aGlzLl90ZW1wbGF0ZSk7CiAgICAgICAgICAgIHRoaXMuJCA9IHRoaXMucm9vdC4kOwogICAgICAgICAgfQogICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEltcGxlbWVudHMgYFByb3BlcnR5RWZmZWN0c2AncyBgX3JlYWR5Q2xpZW50c2AgY2FsbC4gQXR0YWNoZXMKICAgICAgICAgKiBlbGVtZW50IGRvbSBieSBjYWxsaW5nIGBfYXR0YWNoRG9tYCB3aXRoIHRoZSBkb20gc3RhbXBlZCBmcm9tIHRoZQogICAgICAgICAqIGVsZW1lbnQncyB0ZW1wbGF0ZSB2aWEgYF9zdGFtcFRlbXBsYXRlYC4gTm90ZSB0aGF0IHRoaXMgYWxsb3dzCiAgICAgICAgICogY2xpZW50IGRvbSB0byBiZSBhdHRhY2hlZCB0byB0aGUgZWxlbWVudCBwcmlvciB0byBhbnkgb2JzZXJ2ZXJzCiAgICAgICAgICogcnVubmluZy4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX3JlYWR5Q2xpZW50cygpIHsKICAgICAgICAgIGlmICh0aGlzLl90ZW1wbGF0ZSkgewogICAgICAgICAgICB0aGlzLnJvb3QgPSB0aGlzLl9hdHRhY2hEb20oLyoqIEB0eXBlIHtTdGFtcGVkVGVtcGxhdGV9ICovKHRoaXMucm9vdCkpOwogICAgICAgICAgfQogICAgICAgICAgLy8gVGhlIHN1cGVyLl9yZWFkeUNsaWVudHMgaGVyZSBzZXRzIHRoZSBjbGllbnRzIGluaXRpYWxpemVkIGZsYWcuCiAgICAgICAgICAvLyBXZSBtdXN0IHdhaXQgdG8gZG8gdGhpcyB1bnRpbCBhZnRlciBjbGllbnQgZG9tIGlzIGNyZWF0ZWQvYXR0YWNoZWQKICAgICAgICAgIC8vIHNvIHRoYXQgdGhpcyBmbGFnIGNhbiBiZSBjaGVja2VkIHRvIHByZXZlbnQgbm90aWZpY2F0aW9ucyBmaXJlZAogICAgICAgICAgLy8gZHVyaW5nIHRoaXMgcHJvY2VzcyBmcm9tIGJlaW5nIGhhbmRsZWQgYmVmb3JlIGNsaWVudHMgYXJlIHJlYWR5LgogICAgICAgICAgc3VwZXIuX3JlYWR5Q2xpZW50cygpOwogICAgICAgIH0KCgogICAgICAgIC8qKgogICAgICAgICAqIEF0dGFjaGVzIGFuIGVsZW1lbnQncyBzdGFtcGVkIGRvbSB0byBpdHNlbGYuIEJ5IGRlZmF1bHQsCiAgICAgICAgICogdGhpcyBtZXRob2QgY3JlYXRlcyBhIGBzaGFkb3dSb290YCBhbmQgYWRkcyB0aGUgZG9tIHRvIGl0LgogICAgICAgICAqIEhvd2V2ZXIsIHRoaXMgbWV0aG9kIG1heSBiZSBvdmVycmlkZGVuIHRvIGFsbG93IGFuIGVsZW1lbnQKICAgICAgICAgKiB0byBwdXQgaXRzIGRvbSBpbiBhbm90aGVyIGxvY2F0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHRocm93cyB7RXJyb3J9CiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUmV0dXJufQogICAgICAgICAqIEBwYXJhbSB7U3RhbXBlZFRlbXBsYXRlfSBkb20gdG8gYXR0YWNoIHRvIHRoZSBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm4ge1NoYWRvd1Jvb3R9IG5vZGUgdG8gd2hpY2ggdGhlIGRvbSBoYXMgYmVlbiBhdHRhY2hlZC4KICAgICAgICAgKi8KICAgICAgICBfYXR0YWNoRG9tKGRvbSkgewogICAgICAgICAgY29uc3QgbiA9IHdyYXAodGhpcyk7CiAgICAgICAgICBpZiAobi5hdHRhY2hTaGFkb3cpIHsKICAgICAgICAgICAgaWYgKGRvbSkgewogICAgICAgICAgICAgIGlmICghbi5zaGFkb3dSb290KSB7CiAgICAgICAgICAgICAgICBuLmF0dGFjaFNoYWRvdyh7bW9kZTogJ29wZW4nLCBzaGFkeVVwZ3JhZGVGcmFnbWVudDogZG9tfSk7CiAgICAgICAgICAgICAgICBuLnNoYWRvd1Jvb3QuYXBwZW5kQ2hpbGQoZG9tKTsKICAgICAgICAgICAgICAgIC8vIFdoZW4gYGFkb3B0ZWRTdHlsZVNoZWV0c2AgaXMgc3VwcG9ydGVkIGEgc3R5bGVzaGVldCBpcyBtYWRlCiAgICAgICAgICAgICAgICAvLyBhdmFpbGFibGUgb24gdGhlIGVsZW1lbnQgY29uc3RydWN0b3IuCiAgICAgICAgICAgICAgICBpZiAodGhpcy5jb25zdHJ1Y3Rvci5fc3R5bGVTaGVldCkgewogICAgICAgICAgICAgICAgICBuLnNoYWRvd1Jvb3QuYWRvcHRlZFN0eWxlU2hlZXRzID0gW3RoaXMuY29uc3RydWN0b3IuX3N0eWxlU2hlZXRdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBpZiAoc3luY0luaXRpYWxSZW5kZXIgJiYgd2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgICAgICAgICB3aW5kb3cuU2hhZHlET00uZmx1c2hJbml0aWFsKG4uc2hhZG93Um9vdCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHJldHVybiBuLnNoYWRvd1Jvb3Q7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ1NoYWRvd0RPTSBub3QgYXZhaWxhYmxlLiAnICsKICAgICAgICAgICAgICAvLyBUT0RPKHNvcnZlbGwpOiBtb3ZlIHRvIGNvbXBpbGUtdGltZSBjb25kaXRpb25hbCB3aGVuIHN1cHBvcnRlZAogICAgICAgICAgICAnUG9seW1lckVsZW1lbnQgY2FuIGNyZWF0ZSBkb20gYXMgY2hpbGRyZW4gaW5zdGVhZCBvZiBpbiAnICsKICAgICAgICAgICAgJ1NoYWRvd0RPTSBieSBzZXR0aW5nIGB0aGlzLnJvb3QgPSB0aGlzO1xgIGJlZm9yZSBcYHJlYWR5XGAuJyk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBXaGVuIHVzaW5nIHRoZSBTaGFkeUNTUyBzY29waW5nIGFuZCBjdXN0b20gcHJvcGVydHkgc2hpbSwgY2F1c2VzIGFsbAogICAgICAgICAqIHNoaW1tZWQgc3R5bGVzIGluIHRoaXMgZWxlbWVudCAoYW5kIGl0cyBzdWJ0cmVlKSB0byBiZSB1cGRhdGVkCiAgICAgICAgICogYmFzZWQgb24gY3VycmVudCBjdXN0b20gcHJvcGVydHkgdmFsdWVzLgogICAgICAgICAqCiAgICAgICAgICogVGhlIG9wdGlvbmFsIHBhcmFtZXRlciBvdmVycmlkZXMgaW5saW5lIGN1c3RvbSBwcm9wZXJ0eSBzdHlsZXMgd2l0aCBhbgogICAgICAgICAqIG9iamVjdCBvZiBwcm9wZXJ0aWVzIHdoZXJlIHRoZSBrZXlzIGFyZSBDU1MgcHJvcGVydGllcywgYW5kIHRoZSB2YWx1ZXMKICAgICAgICAgKiBhcmUgc3RyaW5ncy4KICAgICAgICAgKgogICAgICAgICAqIEV4YW1wbGU6IGB0aGlzLnVwZGF0ZVN0eWxlcyh7Jy0tY29sb3InOiAnYmx1ZSd9KWAKICAgICAgICAgKgogICAgICAgICAqIFRoZXNlIHByb3BlcnRpZXMgYXJlIHJldGFpbmVkIHVubGVzcyBhIHZhbHVlIG9mIGBudWxsYCBpcyBzZXQuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlOiBUaGlzIGZ1bmN0aW9uIGRvZXMgbm90IHN1cHBvcnQgdXBkYXRpbmcgQ1NTIG1peGlucy4KICAgICAgICAgKiBZb3UgY2FuIG5vdCBkeW5hbWljYWxseSBjaGFuZ2UgdGhlIHZhbHVlIG9mIGFuIGBAYXBwbHlgLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSBwcm9wZXJ0aWVzIEJhZyBvZiBjdXN0b20gcHJvcGVydHkga2V5L3ZhbHVlcyB0bwogICAgICAgICAqICAgYXBwbHkgdG8gdGhpcyBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9CiAgICAgICAgICovCiAgICAgICAgdXBkYXRlU3R5bGVzKHByb3BlcnRpZXMpIHsKICAgICAgICAgIGlmICh3aW5kb3cuU2hhZHlDU1MpIHsKICAgICAgICAgICAgd2luZG93LlNoYWR5Q1NTLnN0eWxlU3VidHJlZSgvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8odGhpcyksIHByb3BlcnRpZXMpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV3cml0ZXMgYSBnaXZlbiBVUkwgcmVsYXRpdmUgdG8gYSBiYXNlIFVSTC4gVGhlIGJhc2UgVVJMIGRlZmF1bHRzIHRvCiAgICAgICAgICogdGhlIG9yaWdpbmFsIGxvY2F0aW9uIG9mIHRoZSBkb2N1bWVudCBjb250YWluaW5nIHRoZSBgZG9tLW1vZHVsZWAgZm9yCiAgICAgICAgICogdGhpcyBlbGVtZW50LiBUaGlzIG1ldGhvZCB3aWxsIHJldHVybiB0aGUgc2FtZSBVUkwgYmVmb3JlIGFuZCBhZnRlcgogICAgICAgICAqIGJ1bmRsaW5nLgogICAgICAgICAqCiAgICAgICAgICogTm90ZSB0aGF0IHRoaXMgZnVuY3Rpb24gcGVyZm9ybXMgbm8gcmVzb2x1dGlvbiBmb3IgVVJMcyB0aGF0IHN0YXJ0CiAgICAgICAgICogd2l0aCBgL2AgKGFic29sdXRlIFVSTHMpIG9yIGAjYCAoaGFzaCBpZGVudGlmaWVycykuICBGb3IgZ2VuZXJhbCBwdXJwb3NlCiAgICAgICAgICogVVJMIHJlc29sdXRpb24sIHVzZSBgd2luZG93LlVSTGAuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdXJsIFVSTCB0byByZXNvbHZlLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gYmFzZSBPcHRpb25hbCBiYXNlIFVSTCB0byByZXNvbHZlIGFnYWluc3QsIGRlZmF1bHRzCiAgICAgICAgICogdG8gdGhlIGVsZW1lbnQncyBgaW1wb3J0UGF0aGAKICAgICAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IFJld3JpdHRlbiBVUkwgcmVsYXRpdmUgdG8gYmFzZQogICAgICAgICAqLwogICAgICAgIHJlc29sdmVVcmwodXJsLCBiYXNlKSB7CiAgICAgICAgICBpZiAoIWJhc2UgJiYgdGhpcy5pbXBvcnRQYXRoKSB7CiAgICAgICAgICAgIGJhc2UgPSByZXNvbHZlVXJsKHRoaXMuaW1wb3J0UGF0aCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzb2x2ZVVybCh1cmwsIGJhc2UpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIGBQcm9wZXJ0eUVmZmVjdHNgIHRvIGFkZCBtYXAgb2YgZHluYW1pYyBmdW5jdGlvbnMgb24KICAgICAgICAgKiB0ZW1wbGF0ZSBpbmZvLCBmb3IgY29uc3VtcHRpb24gYnkgYFByb3BlcnR5RWZmZWN0c2AgdGVtcGxhdGUgYmluZGluZwogICAgICAgICAqIGNvZGUuIFRoaXMgbWFwIGRldGVybWluZXMgd2hpY2ggbWV0aG9kIHRlbXBsYXRlcyBzaG91bGQgaGF2ZSBhY2Nlc3NvcnMKICAgICAgICAgKiBjcmVhdGVkIGZvciB0aGVtLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUgVGVtcGxhdGUKICAgICAgICAgKiBAcGFyYW0geyFUZW1wbGF0ZUluZm99IHRlbXBsYXRlSW5mbyBUZW1wbGF0ZSBtZXRhZGF0YSBmb3IgY3VycmVudCB0ZW1wbGF0ZQogICAgICAgICAqIEBwYXJhbSB7IU5vZGVJbmZvfSBub2RlSW5mbyBOb2RlIG1ldGFkYXRhIGZvciBjdXJyZW50IHRlbXBsYXRlLgogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IC4KICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcGFyc2VUZW1wbGF0ZUNvbnRlbnQodGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pIHsKICAgICAgICAgIHRlbXBsYXRlSW5mby5keW5hbWljRm5zID0gdGVtcGxhdGVJbmZvLmR5bmFtaWNGbnMgfHwgdGhpcy5fcHJvcGVydGllczsKICAgICAgICAgIC8vIFRPRE8oaHR0cHM6Ly9naXRodWIuY29tL2dvb2dsZS9jbG9zdXJlLWNvbXBpbGVyL2lzc3Vlcy8zMjQwKToKICAgICAgICAgIC8vICAgICBDaGFuZ2UgYmFjayB0byBqdXN0IHN1cGVyLm1ldGhvZENhbGwoKQogICAgICAgICAgcmV0dXJuIHBvbHltZXJFbGVtZW50QmFzZS5fcGFyc2VUZW1wbGF0ZUNvbnRlbnQuY2FsbCgKICAgICAgICAgICAgdGhpcywgdGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgbm9kZUluZm8pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIGBQcm9wZXJ0eUVmZmVjdHNgIHRvIHdhcm4gb24gdXNlIG9mIHVuZGVjbGFyZWQgcHJvcGVydGllcyBpbgogICAgICAgICAqIHRlbXBsYXRlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHRlbXBsYXRlSW5mbyBUZW1wbGF0ZSBtZXRhZGF0YSB0byBhZGQgZWZmZWN0IHRvCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3AgUHJvcGVydHkgdGhhdCBzaG91bGQgdHJpZ2dlciB0aGUgZWZmZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSBlZmZlY3QgRWZmZWN0IG1ldGFkYXRhIG9iamVjdAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqIEBzdXBwcmVzcyB7bWlzc2luZ1Byb3BlcnRpZXN9IEludGVyZmFjZXMgaW4gY2xvc3VyZSBkbyBub3QgaW5oZXJpdCBzdGF0aWNzLCBidXQgY2xhc3NlcyBkbwogICAgICAgICAqIEBub2NvbGxhcHNlCiAgICAgICAgICovCiAgICAgICAgc3RhdGljIF9hZGRUZW1wbGF0ZVByb3BlcnR5RWZmZWN0KHRlbXBsYXRlSW5mbywgcHJvcCwgZWZmZWN0KSB7CiAgICAgICAgICAvLyBXYXJuIGlmIHByb3BlcnRpZXMgYXJlIHVzZWQgaW4gdGVtcGxhdGUgd2l0aG91dCBiZWluZyBkZWNsYXJlZC4KICAgICAgICAgIC8vIFByb3BlcnRpZXMgbXVzdCBiZSBsaXN0ZWQgaW4gYHByb3BlcnRpZXNgIHRvIGJlIGluY2x1ZGVkIGluCiAgICAgICAgICAvLyBgb2JzZXJ2ZWRBdHRyaWJ1dGVzYCBzaW5jZSBDRSBWMSByZWFkcyB0aGF0IGF0IHJlZ2lzdHJhdGlvbiB0aW1lLCBhbmQKICAgICAgICAgIC8vIHNpbmNlIHdlIHdhbnQgdG8ga2VlcCB0ZW1wbGF0ZSBwYXJzaW5nIGxhenksIHdlIGNhbid0IGF1dG9tYXRpY2FsbHkKICAgICAgICAgIC8vIGFkZCB1bmRlY2xhcmVkIHByb3BlcnRpZXMgdXNlZCBpbiB0ZW1wbGF0ZXMgdG8gYG9ic2VydmVkQXR0cmlidXRlc2AuCiAgICAgICAgICAvLyBUaGUgd2FybmluZyBpcyBvbmx5IGVuYWJsZWQgaW4gYGxlZ2FjeU9wdGltaXphdGlvbnNgIG1vZGUsIHNpbmNlCiAgICAgICAgICAvLyB3ZSBkb24ndCB3YW50IHRvIHNwYW0gZXhpc3RpbmcgdXNlcnMgd2hvIG1pZ2h0IGhhdmUgYWRvcHRlZCB0aGUKICAgICAgICAgIC8vIHNob3J0aGFuZCB3aGVuIGF0dHJpYnV0ZSBkZXNlcmlhbGl6YXRpb24gaXMgbm90IGltcG9ydGFudC4KICAgICAgICAgIGlmIChsZWdhY3lXYXJuaW5ncyAmJiAhKHByb3AgaW4gdGhpcy5fcHJvcGVydGllcykgJiYKICAgICAgICAgICAgICAvLyBNZXRob2RzIHVzZWQgaW4gdGVtcGxhdGVzIHdpdGggbm8gZGVwZW5kZW5jaWVzIChvciBvbmx5IGxpdGVyYWwKICAgICAgICAgICAgICAvLyBkZXBlbmRlbmNpZXMpIGJlY29tZSBhY2Nlc3NvcnMgd2l0aCB0ZW1wbGF0ZSBlZmZlY3RzOyBpZ25vcmUgdGhlc2UKICAgICAgICAgICAgICAhKGVmZmVjdC5pbmZvLnBhcnQuc2lnbmF0dXJlICYmIGVmZmVjdC5pbmZvLnBhcnQuc2lnbmF0dXJlLnN0YXRpYykgJiYKICAgICAgICAgICAgICAvLyBXYXJuaW5ncyBmb3IgYmluZGluZ3MgYWRkZWQgdG8gbmVzdGVkIHRlbXBsYXRlcyBhcmUgaGFuZGxlZCBieQogICAgICAgICAgICAgIC8vIHRlbXBsYXRpemVyIHNvIGlnbm9yZSBib3RoIHRoZSBob3N0LXRvLXRlbXBsYXRlIGJpbmRpbmdzCiAgICAgICAgICAgICAgLy8gKGBob3N0UHJvcGApIGFuZCBUZW1wbGF0ZUluc3RhbmNlLXRvLWNoaWxkIGJpbmRpbmdzCiAgICAgICAgICAgICAgLy8gKGBuZXN0ZWRUZW1wbGF0ZWApCiAgICAgICAgICAgICAgIWVmZmVjdC5pbmZvLnBhcnQuaG9zdFByb3AgJiYgIXRlbXBsYXRlSW5mby5uZXN0ZWRUZW1wbGF0ZSkgewogICAgICAgICAgICBjb25zb2xlLndhcm4oYFByb3BlcnR5ICcke3Byb3B9JyB1c2VkIGluIHRlbXBsYXRlIGJ1dCBub3QgZGVjbGFyZWQgaW4gJ3Byb3BlcnRpZXMnOyBgICsKICAgICAgICAgICAgICBgYXR0cmlidXRlIHdpbGwgbm90IGJlIG9ic2VydmVkLmApOwogICAgICAgICAgfQogICAgICAgICAgLy8gVE9ETyhodHRwczovL2dpdGh1Yi5jb20vZ29vZ2xlL2Nsb3N1cmUtY29tcGlsZXIvaXNzdWVzLzMyNDApOgogICAgICAgICAgLy8gICAgIENoYW5nZSBiYWNrIHRvIGp1c3Qgc3VwZXIubWV0aG9kQ2FsbCgpCiAgICAgICAgICByZXR1cm4gcG9seW1lckVsZW1lbnRCYXNlLl9hZGRUZW1wbGF0ZVByb3BlcnR5RWZmZWN0LmNhbGwoCiAgICAgICAgICAgIHRoaXMsIHRlbXBsYXRlSW5mbywgcHJvcCwgZWZmZWN0KTsKICAgICAgICB9CgogICAgICB9CgogICAgICByZXR1cm4gUG9seW1lckVsZW1lbnQ7CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQ2xhc3MgcmVwcmVzZW50aW5nIGEgc3RhdGljIHN0cmluZyB2YWx1ZSB3aGljaCBjYW4gYmUgdXNlZCB0byBmaWx0ZXIKICAgICAqIHN0cmluZ3MgYnkgYXNzZXRpbmcgdGhhdCB0aGV5IGhhdmUgYmVlbiBjcmVhdGVkIHZpYSB0aGlzIGNsYXNzLiBUaGUKICAgICAqIGB2YWx1ZWAgcHJvcGVydHkgcmV0dXJucyB0aGUgc3RyaW5nIHBhc3NlZCB0byB0aGUgY29uc3RydWN0b3IuCiAgICAgKi8KICAgIGNsYXNzIExpdGVyYWxTdHJpbmcgewogICAgICBjb25zdHJ1Y3RvcihzdHJpbmcpIHsKICAgICAgICAvKiogQHR5cGUge3N0cmluZ30gKi8KICAgICAgICB0aGlzLnZhbHVlID0gc3RyaW5nLnRvU3RyaW5nKCk7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gTGl0ZXJhbFN0cmluZyBzdHJpbmcgdmFsdWUKICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqLwogICAgICB0b1N0cmluZygpIHsKICAgICAgICByZXR1cm4gdGhpcy52YWx1ZTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBPYmplY3QgdG8gc3RyaW5naWZ5IGludG8gSFRNTAogICAgICogQHJldHVybiB7c3RyaW5nfSBIVE1MIHN0cmluZ2lmaWVkIGZvcm0gb2YgYG9iamAKICAgICAqLwogICAgZnVuY3Rpb24gbGl0ZXJhbFZhbHVlKHZhbHVlKSB7CiAgICAgIGlmICh2YWx1ZSBpbnN0YW5jZW9mIExpdGVyYWxTdHJpbmcpIHsKICAgICAgICByZXR1cm4gLyoqIEB0eXBlIHshTGl0ZXJhbFN0cmluZ30gKi8odmFsdWUpLnZhbHVlOwogICAgICB9IGVsc2UgewogICAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICAgYG5vbi1saXRlcmFsIHZhbHVlIHBhc3NlZCB0byBQb2x5bWVyJ3MgaHRtbExpdGVyYWwgZnVuY3Rpb246ICR7dmFsdWV9YAogICAgICAgICk7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgT2JqZWN0IHRvIHN0cmluZ2lmeSBpbnRvIEhUTUwKICAgICAqIEByZXR1cm4ge3N0cmluZ30gSFRNTCBzdHJpbmdpZmllZCBmb3JtIG9mIGBvYmpgCiAgICAgKi8KICAgIGZ1bmN0aW9uIGh0bWxWYWx1ZSh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgaW5zdGFuY2VvZiBIVE1MVGVtcGxhdGVFbGVtZW50KSB7CiAgICAgICAgcmV0dXJuIC8qKiBAdHlwZSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnQgfSAqLyh2YWx1ZSkuaW5uZXJIVE1MOwogICAgICB9IGVsc2UgaWYgKHZhbHVlIGluc3RhbmNlb2YgTGl0ZXJhbFN0cmluZykgewogICAgICAgIHJldHVybiBsaXRlcmFsVmFsdWUodmFsdWUpOwogICAgICB9IGVsc2UgewogICAgICAgIHRocm93IG5ldyBFcnJvcigKICAgICAgICAgICAgYG5vbi10ZW1wbGF0ZSB2YWx1ZSBwYXNzZWQgdG8gUG9seW1lcidzIGh0bWwgZnVuY3Rpb246ICR7dmFsdWV9YCk7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEEgdGVtcGxhdGUgbGl0ZXJhbCB0YWcgdGhhdCBjcmVhdGVzIGFuIEhUTUwgPHRlbXBsYXRlPiBlbGVtZW50IGZyb20gdGhlCiAgICAgKiBjb250ZW50cyBvZiB0aGUgc3RyaW5nLgogICAgICoKICAgICAqIFRoaXMgYWxsb3dzIHlvdSB0byB3cml0ZSBhIFBvbHltZXIgVGVtcGxhdGUgaW4gSmF2YVNjcmlwdC4KICAgICAqCiAgICAgKiBUZW1wbGF0ZXMgY2FuIGJlIGNvbXBvc2VkIGJ5IGludGVycG9sYXRpbmcgYEhUTUxUZW1wbGF0ZUVsZW1lbnRgcyBpbgogICAgICogZXhwcmVzc2lvbnMgaW4gdGhlIEphdmFTY3JpcHQgdGVtcGxhdGUgbGl0ZXJhbC4gVGhlIG5lc3RlZCB0ZW1wbGF0ZSdzCiAgICAgKiBgaW5uZXJIVE1MYCBpcyBpbmNsdWRlZCBpbiB0aGUgY29udGFpbmluZyB0ZW1wbGF0ZS4gIFRoZSBvbmx5IG90aGVyCiAgICAgKiB2YWx1ZXMgYWxsb3dlZCBpbiBleHByZXNzaW9ucyBhcmUgdGhvc2UgcmV0dXJuZWQgZnJvbSBgaHRtbExpdGVyYWxgCiAgICAgKiB3aGljaCBlbnN1cmVzIG9ubHkgbGl0ZXJhbCB2YWx1ZXMgZnJvbSBKUyBzb3VyY2UgZXZlciByZWFjaCB0aGUgSFRNTCwgdG8KICAgICAqIGd1YXJkIGFnYWluc3QgWFNTIHJpc2tzLgogICAgICoKICAgICAqIEFsbCBvdGhlciB2YWx1ZXMgYXJlIGRpc2FsbG93ZWQgaW4gZXhwcmVzc2lvbnMgdG8gaGVscCBwcmV2ZW50IFhTUwogICAgICogYXR0YWNrczsgaG93ZXZlciwgYGh0bWxMaXRlcmFsYCBjYW4gYmUgdXNlZCB0byBjb21wb3NlIHN0YXRpYwogICAgICogc3RyaW5nIHZhbHVlcyBpbnRvIHRlbXBsYXRlcy4gVGhpcyBpcyB1c2VmdWwgdG8gY29tcG9zZSBzdHJpbmdzIGludG8KICAgICAqIHBsYWNlcyB0aGF0IGRvIG5vdCBhY2NlcHQgaHRtbCwgbGlrZSB0aGUgY3NzIHRleHQgb2YgYSBgc3R5bGVgCiAgICAgKiBlbGVtZW50LgogICAgICoKICAgICAqIEV4YW1wbGU6CiAgICAgKgogICAgICogICAgIHN0YXRpYyBnZXQgdGVtcGxhdGUoKSB7CiAgICAgKiAgICAgICByZXR1cm4gaHRtbGAKICAgICAqICAgICAgICAgPHN0eWxlPjpob3N0eyBjb250ZW50OiIuLi4iIH08L3N0eWxlPgogICAgICogICAgICAgICA8ZGl2IGNsYXNzPSJzaGFkb3dlZCI+JHt0aGlzLnBhcnRpYWxUZW1wbGF0ZX08L2Rpdj4KICAgICAqICAgICAgICAgJHtzdXBlci50ZW1wbGF0ZX0KICAgICAqICAgICAgIGA7CiAgICAgKiAgICAgfQogICAgICogICAgIHN0YXRpYyBnZXQgcGFydGlhbFRlbXBsYXRlKCkgeyByZXR1cm4gaHRtbGA8c3Bhbj5QYXJ0aWFsITwvc3Bhbj5gOyB9CiAgICAgKgogICAgICogQHBhcmFtIHshSVRlbXBsYXRlQXJyYXl9IHN0cmluZ3MgQ29uc3RhbnQgcGFydHMgb2YgdGFnZ2VkIHRlbXBsYXRlIGxpdGVyYWwKICAgICAqIEBwYXJhbSB7Li4uKn0gdmFsdWVzIFZhcmlhYmxlIHBhcnRzIG9mIHRhZ2dlZCB0ZW1wbGF0ZSBsaXRlcmFsCiAgICAgKiBAcmV0dXJuIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gQ29uc3RydWN0ZWQgSFRNTFRlbXBsYXRlRWxlbWVudAogICAgICovCiAgICBjb25zdCBodG1sID0gZnVuY3Rpb24gaHRtbChzdHJpbmdzLCAuLi52YWx1ZXMpIHsKICAgICAgY29uc3QgdGVtcGxhdGUgPSAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fSAqLyhkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpKTsKICAgICAgdGVtcGxhdGUuaW5uZXJIVE1MID0gdmFsdWVzLnJlZHVjZSgoYWNjLCB2LCBpZHgpID0+CiAgICAgICAgICBhY2MgKyBodG1sVmFsdWUodikgKyBzdHJpbmdzW2lkeCArIDFdLCBzdHJpbmdzWzBdKTsKICAgICAgcmV0dXJuIHRlbXBsYXRlOwogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQmFzZSBjbGFzcyB0aGF0IHByb3ZpZGVzIHRoZSBjb3JlIEFQSSBmb3IgUG9seW1lcidzIG1ldGEtcHJvZ3JhbW1pbmcKICAgICAqIGZlYXR1cmVzIGluY2x1ZGluZyB0ZW1wbGF0ZSBzdGFtcGluZywgZGF0YS1iaW5kaW5nLCBhdHRyaWJ1dGUgZGVzZXJpYWxpemF0aW9uLAogICAgICogYW5kIHByb3BlcnR5IGNoYW5nZSBvYnNlcnZhdGlvbi4KICAgICAqCiAgICAgKiBAY3VzdG9tRWxlbWVudAogICAgICogQHBvbHltZXIKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQGltcGxlbWVudHMge1BvbHltZXJfRWxlbWVudE1peGlufQogICAgICogQGV4dGVuZHMgSFRNTEVsZW1lbnQKICAgICAqIEBhcHBsaWVzTWl4aW4gRWxlbWVudE1peGluCiAgICAgKiBAc3VtbWFyeSBDdXN0b20gZWxlbWVudCBiYXNlIGNsYXNzIHRoYXQgcHJvdmlkZXMgdGhlIGNvcmUgQVBJIGZvciBQb2x5bWVyJ3MKICAgICAqICAga2V5IG1ldGEtcHJvZ3JhbW1pbmcgZmVhdHVyZXMgaW5jbHVkaW5nIHRlbXBsYXRlIHN0YW1waW5nLCBkYXRhLWJpbmRpbmcsCiAgICAgKiAgIGF0dHJpYnV0ZSBkZXNlcmlhbGl6YXRpb24sIGFuZCBwcm9wZXJ0eSBjaGFuZ2Ugb2JzZXJ2YXRpb24KICAgICAqLwogICAgY29uc3QgUG9seW1lckVsZW1lbnQgPSBFbGVtZW50TWl4aW4oSFRNTEVsZW1lbnQpOwoKICAgIHZhciBjb21tb25qc0dsb2JhbCA9IHR5cGVvZiBnbG9iYWxUaGlzICE9PSAndW5kZWZpbmVkJyA/IGdsb2JhbFRoaXMgOiB0eXBlb2Ygd2luZG93ICE9PSAndW5kZWZpbmVkJyA/IHdpbmRvdyA6IHR5cGVvZiBnbG9iYWwgIT09ICd1bmRlZmluZWQnID8gZ2xvYmFsIDogdHlwZW9mIHNlbGYgIT09ICd1bmRlZmluZWQnID8gc2VsZiA6IHt9OwoKICAgIGZ1bmN0aW9uIGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZuLCBiYXNlZGlyLCBtb2R1bGUpIHsKICAgIAlyZXR1cm4gbW9kdWxlID0gewogICAgCSAgcGF0aDogYmFzZWRpciwKICAgIAkgIGV4cG9ydHM6IHt9LAogICAgCSAgcmVxdWlyZTogZnVuY3Rpb24gKHBhdGgsIGJhc2UpIHsKICAgICAgICAgIHJldHVybiBjb21tb25qc1JlcXVpcmUocGF0aCwgKGJhc2UgPT09IHVuZGVmaW5lZCB8fCBiYXNlID09PSBudWxsKSA/IG1vZHVsZS5wYXRoIDogYmFzZSk7CiAgICAgICAgfQogICAgCX0sIGZuKG1vZHVsZSwgbW9kdWxlLmV4cG9ydHMpLCBtb2R1bGUuZXhwb3J0czsKICAgIH0KCiAgICBmdW5jdGlvbiBjb21tb25qc1JlcXVpcmUgKCkgewogICAgCXRocm93IG5ldyBFcnJvcignRHluYW1pYyByZXF1aXJlcyBhcmUgbm90IGN1cnJlbnRseSBzdXBwb3J0ZWQgYnkgQHJvbGx1cC9wbHVnaW4tY29tbW9uanMnKTsKICAgIH0KCiAgICB2YXIgbG9kYXNoID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgKGZ1bmN0aW9uKCkgewoKICAgICAgLyoqIFVzZWQgYXMgYSBzYWZlIHJlZmVyZW5jZSBmb3IgYHVuZGVmaW5lZGAgaW4gcHJlLUVTNSBlbnZpcm9ubWVudHMuICovCiAgICAgIHZhciB1bmRlZmluZWQkMTsKCiAgICAgIC8qKiBVc2VkIGFzIHRoZSBzZW1hbnRpYyB2ZXJzaW9uIG51bWJlci4gKi8KICAgICAgdmFyIFZFUlNJT04gPSAnNC4xNy4xOSc7CgogICAgICAvKiogVXNlZCBhcyB0aGUgc2l6ZSB0byBlbmFibGUgbGFyZ2UgYXJyYXkgb3B0aW1pemF0aW9ucy4gKi8KICAgICAgdmFyIExBUkdFX0FSUkFZX1NJWkUgPSAyMDA7CgogICAgICAvKiogRXJyb3IgbWVzc2FnZSBjb25zdGFudHMuICovCiAgICAgIHZhciBDT1JFX0VSUk9SX1RFWFQgPSAnVW5zdXBwb3J0ZWQgY29yZS1qcyB1c2UuIFRyeSBodHRwczovL25wbXMuaW8vc2VhcmNoP3E9cG9ueWZpbGwuJywKICAgICAgICAgIEZVTkNfRVJST1JfVEVYVCA9ICdFeHBlY3RlZCBhIGZ1bmN0aW9uJzsKCiAgICAgIC8qKiBVc2VkIHRvIHN0YW5kLWluIGZvciBgdW5kZWZpbmVkYCBoYXNoIHZhbHVlcy4gKi8KICAgICAgdmFyIEhBU0hfVU5ERUZJTkVEID0gJ19fbG9kYXNoX2hhc2hfdW5kZWZpbmVkX18nOwoKICAgICAgLyoqIFVzZWQgYXMgdGhlIG1heGltdW0gbWVtb2l6ZSBjYWNoZSBzaXplLiAqLwogICAgICB2YXIgTUFYX01FTU9JWkVfU0laRSA9IDUwMDsKCiAgICAgIC8qKiBVc2VkIGFzIHRoZSBpbnRlcm5hbCBhcmd1bWVudCBwbGFjZWhvbGRlci4gKi8KICAgICAgdmFyIFBMQUNFSE9MREVSID0gJ19fbG9kYXNoX3BsYWNlaG9sZGVyX18nOwoKICAgICAgLyoqIFVzZWQgdG8gY29tcG9zZSBiaXRtYXNrcyBmb3IgY2xvbmluZy4gKi8KICAgICAgdmFyIENMT05FX0RFRVBfRkxBRyA9IDEsCiAgICAgICAgICBDTE9ORV9GTEFUX0ZMQUcgPSAyLAogICAgICAgICAgQ0xPTkVfU1lNQk9MU19GTEFHID0gNDsKCiAgICAgIC8qKiBVc2VkIHRvIGNvbXBvc2UgYml0bWFza3MgZm9yIHZhbHVlIGNvbXBhcmlzb25zLiAqLwogICAgICB2YXIgQ09NUEFSRV9QQVJUSUFMX0ZMQUcgPSAxLAogICAgICAgICAgQ09NUEFSRV9VTk9SREVSRURfRkxBRyA9IDI7CgogICAgICAvKiogVXNlZCB0byBjb21wb3NlIGJpdG1hc2tzIGZvciBmdW5jdGlvbiBtZXRhZGF0YS4gKi8KICAgICAgdmFyIFdSQVBfQklORF9GTEFHID0gMSwKICAgICAgICAgIFdSQVBfQklORF9LRVlfRkxBRyA9IDIsCiAgICAgICAgICBXUkFQX0NVUlJZX0JPVU5EX0ZMQUcgPSA0LAogICAgICAgICAgV1JBUF9DVVJSWV9GTEFHID0gOCwKICAgICAgICAgIFdSQVBfQ1VSUllfUklHSFRfRkxBRyA9IDE2LAogICAgICAgICAgV1JBUF9QQVJUSUFMX0ZMQUcgPSAzMiwKICAgICAgICAgIFdSQVBfUEFSVElBTF9SSUdIVF9GTEFHID0gNjQsCiAgICAgICAgICBXUkFQX0FSWV9GTEFHID0gMTI4LAogICAgICAgICAgV1JBUF9SRUFSR19GTEFHID0gMjU2LAogICAgICAgICAgV1JBUF9GTElQX0ZMQUcgPSA1MTI7CgogICAgICAvKiogVXNlZCBhcyBkZWZhdWx0IG9wdGlvbnMgZm9yIGBfLnRydW5jYXRlYC4gKi8KICAgICAgdmFyIERFRkFVTFRfVFJVTkNfTEVOR1RIID0gMzAsCiAgICAgICAgICBERUZBVUxUX1RSVU5DX09NSVNTSU9OID0gJy4uLic7CgogICAgICAvKiogVXNlZCB0byBkZXRlY3QgaG90IGZ1bmN0aW9ucyBieSBudW1iZXIgb2YgY2FsbHMgd2l0aGluIGEgc3BhbiBvZiBtaWxsaXNlY29uZHMuICovCiAgICAgIHZhciBIT1RfQ09VTlQgPSA4MDAsCiAgICAgICAgICBIT1RfU1BBTiA9IDE2OwoKICAgICAgLyoqIFVzZWQgdG8gaW5kaWNhdGUgdGhlIHR5cGUgb2YgbGF6eSBpdGVyYXRlZXMuICovCiAgICAgIHZhciBMQVpZX0ZJTFRFUl9GTEFHID0gMSwKICAgICAgICAgIExBWllfTUFQX0ZMQUcgPSAyLAogICAgICAgICAgTEFaWV9XSElMRV9GTEFHID0gMzsKCiAgICAgIC8qKiBVc2VkIGFzIHJlZmVyZW5jZXMgZm9yIHZhcmlvdXMgYE51bWJlcmAgY29uc3RhbnRzLiAqLwogICAgICB2YXIgSU5GSU5JVFkgPSAxIC8gMCwKICAgICAgICAgIE1BWF9TQUZFX0lOVEVHRVIgPSA5MDA3MTk5MjU0NzQwOTkxLAogICAgICAgICAgTUFYX0lOVEVHRVIgPSAxLjc5NzY5MzEzNDg2MjMxNTdlKzMwOCwKICAgICAgICAgIE5BTiA9IDAgLyAwOwoKICAgICAgLyoqIFVzZWQgYXMgcmVmZXJlbmNlcyBmb3IgdGhlIG1heGltdW0gbGVuZ3RoIGFuZCBpbmRleCBvZiBhbiBhcnJheS4gKi8KICAgICAgdmFyIE1BWF9BUlJBWV9MRU5HVEggPSA0Mjk0OTY3Mjk1LAogICAgICAgICAgTUFYX0FSUkFZX0lOREVYID0gTUFYX0FSUkFZX0xFTkdUSCAtIDEsCiAgICAgICAgICBIQUxGX01BWF9BUlJBWV9MRU5HVEggPSBNQVhfQVJSQVlfTEVOR1RIID4+PiAxOwoKICAgICAgLyoqIFVzZWQgdG8gYXNzb2NpYXRlIHdyYXAgbWV0aG9kcyB3aXRoIHRoZWlyIGJpdCBmbGFncy4gKi8KICAgICAgdmFyIHdyYXBGbGFncyA9IFsKICAgICAgICBbJ2FyeScsIFdSQVBfQVJZX0ZMQUddLAogICAgICAgIFsnYmluZCcsIFdSQVBfQklORF9GTEFHXSwKICAgICAgICBbJ2JpbmRLZXknLCBXUkFQX0JJTkRfS0VZX0ZMQUddLAogICAgICAgIFsnY3VycnknLCBXUkFQX0NVUlJZX0ZMQUddLAogICAgICAgIFsnY3VycnlSaWdodCcsIFdSQVBfQ1VSUllfUklHSFRfRkxBR10sCiAgICAgICAgWydmbGlwJywgV1JBUF9GTElQX0ZMQUddLAogICAgICAgIFsncGFydGlhbCcsIFdSQVBfUEFSVElBTF9GTEFHXSwKICAgICAgICBbJ3BhcnRpYWxSaWdodCcsIFdSQVBfUEFSVElBTF9SSUdIVF9GTEFHXSwKICAgICAgICBbJ3JlYXJnJywgV1JBUF9SRUFSR19GTEFHXQogICAgICBdOwoKICAgICAgLyoqIGBPYmplY3QjdG9TdHJpbmdgIHJlc3VsdCByZWZlcmVuY2VzLiAqLwogICAgICB2YXIgYXJnc1RhZyA9ICdbb2JqZWN0IEFyZ3VtZW50c10nLAogICAgICAgICAgYXJyYXlUYWcgPSAnW29iamVjdCBBcnJheV0nLAogICAgICAgICAgYXN5bmNUYWcgPSAnW29iamVjdCBBc3luY0Z1bmN0aW9uXScsCiAgICAgICAgICBib29sVGFnID0gJ1tvYmplY3QgQm9vbGVhbl0nLAogICAgICAgICAgZGF0ZVRhZyA9ICdbb2JqZWN0IERhdGVdJywKICAgICAgICAgIGRvbUV4Y1RhZyA9ICdbb2JqZWN0IERPTUV4Y2VwdGlvbl0nLAogICAgICAgICAgZXJyb3JUYWcgPSAnW29iamVjdCBFcnJvcl0nLAogICAgICAgICAgZnVuY1RhZyA9ICdbb2JqZWN0IEZ1bmN0aW9uXScsCiAgICAgICAgICBnZW5UYWcgPSAnW29iamVjdCBHZW5lcmF0b3JGdW5jdGlvbl0nLAogICAgICAgICAgbWFwVGFnID0gJ1tvYmplY3QgTWFwXScsCiAgICAgICAgICBudW1iZXJUYWcgPSAnW29iamVjdCBOdW1iZXJdJywKICAgICAgICAgIG51bGxUYWcgPSAnW29iamVjdCBOdWxsXScsCiAgICAgICAgICBvYmplY3RUYWcgPSAnW29iamVjdCBPYmplY3RdJywKICAgICAgICAgIHByb21pc2VUYWcgPSAnW29iamVjdCBQcm9taXNlXScsCiAgICAgICAgICBwcm94eVRhZyA9ICdbb2JqZWN0IFByb3h5XScsCiAgICAgICAgICByZWdleHBUYWcgPSAnW29iamVjdCBSZWdFeHBdJywKICAgICAgICAgIHNldFRhZyA9ICdbb2JqZWN0IFNldF0nLAogICAgICAgICAgc3RyaW5nVGFnID0gJ1tvYmplY3QgU3RyaW5nXScsCiAgICAgICAgICBzeW1ib2xUYWcgPSAnW29iamVjdCBTeW1ib2xdJywKICAgICAgICAgIHVuZGVmaW5lZFRhZyA9ICdbb2JqZWN0IFVuZGVmaW5lZF0nLAogICAgICAgICAgd2Vha01hcFRhZyA9ICdbb2JqZWN0IFdlYWtNYXBdJywKICAgICAgICAgIHdlYWtTZXRUYWcgPSAnW29iamVjdCBXZWFrU2V0XSc7CgogICAgICB2YXIgYXJyYXlCdWZmZXJUYWcgPSAnW29iamVjdCBBcnJheUJ1ZmZlcl0nLAogICAgICAgICAgZGF0YVZpZXdUYWcgPSAnW29iamVjdCBEYXRhVmlld10nLAogICAgICAgICAgZmxvYXQzMlRhZyA9ICdbb2JqZWN0IEZsb2F0MzJBcnJheV0nLAogICAgICAgICAgZmxvYXQ2NFRhZyA9ICdbb2JqZWN0IEZsb2F0NjRBcnJheV0nLAogICAgICAgICAgaW50OFRhZyA9ICdbb2JqZWN0IEludDhBcnJheV0nLAogICAgICAgICAgaW50MTZUYWcgPSAnW29iamVjdCBJbnQxNkFycmF5XScsCiAgICAgICAgICBpbnQzMlRhZyA9ICdbb2JqZWN0IEludDMyQXJyYXldJywKICAgICAgICAgIHVpbnQ4VGFnID0gJ1tvYmplY3QgVWludDhBcnJheV0nLAogICAgICAgICAgdWludDhDbGFtcGVkVGFnID0gJ1tvYmplY3QgVWludDhDbGFtcGVkQXJyYXldJywKICAgICAgICAgIHVpbnQxNlRhZyA9ICdbb2JqZWN0IFVpbnQxNkFycmF5XScsCiAgICAgICAgICB1aW50MzJUYWcgPSAnW29iamVjdCBVaW50MzJBcnJheV0nOwoKICAgICAgLyoqIFVzZWQgdG8gbWF0Y2ggZW1wdHkgc3RyaW5nIGxpdGVyYWxzIGluIGNvbXBpbGVkIHRlbXBsYXRlIHNvdXJjZS4gKi8KICAgICAgdmFyIHJlRW1wdHlTdHJpbmdMZWFkaW5nID0gL1xiX19wIFwrPSAnJzsvZywKICAgICAgICAgIHJlRW1wdHlTdHJpbmdNaWRkbGUgPSAvXGIoX19wIFwrPSkgJycgXCsvZywKICAgICAgICAgIHJlRW1wdHlTdHJpbmdUcmFpbGluZyA9IC8oX19lXCguKj9cKXxcYl9fdFwpKSBcK1xuJyc7L2c7CgogICAgICAvKiogVXNlZCB0byBtYXRjaCBIVE1MIGVudGl0aWVzIGFuZCBIVE1MIGNoYXJhY3RlcnMuICovCiAgICAgIHZhciByZUVzY2FwZWRIdG1sID0gLyYoPzphbXB8bHR8Z3R8cXVvdHwjMzkpOy9nLAogICAgICAgICAgcmVVbmVzY2FwZWRIdG1sID0gL1smPD4iJ10vZywKICAgICAgICAgIHJlSGFzRXNjYXBlZEh0bWwgPSBSZWdFeHAocmVFc2NhcGVkSHRtbC5zb3VyY2UpLAogICAgICAgICAgcmVIYXNVbmVzY2FwZWRIdG1sID0gUmVnRXhwKHJlVW5lc2NhcGVkSHRtbC5zb3VyY2UpOwoKICAgICAgLyoqIFVzZWQgdG8gbWF0Y2ggdGVtcGxhdGUgZGVsaW1pdGVycy4gKi8KICAgICAgdmFyIHJlRXNjYXBlID0gLzwlLShbXHNcU10rPyklPi9nLAogICAgICAgICAgcmVFdmFsdWF0ZSA9IC88JShbXHNcU10rPyklPi9nLAogICAgICAgICAgcmVJbnRlcnBvbGF0ZSA9IC88JT0oW1xzXFNdKz8pJT4vZzsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIHByb3BlcnR5IG5hbWVzIHdpdGhpbiBwcm9wZXJ0eSBwYXRocy4gKi8KICAgICAgdmFyIHJlSXNEZWVwUHJvcCA9IC9cLnxcWyg/OlteW1xdXSp8KFsiJ10pKD86KD8hXDEpW15cXF18XFwuKSo/XDEpXF0vLAogICAgICAgICAgcmVJc1BsYWluUHJvcCA9IC9eXHcqJC8sCiAgICAgICAgICByZVByb3BOYW1lID0gL1teLltcXV0rfFxbKD86KC0/XGQrKD86XC5cZCspPyl8KFsiJ10pKCg/Oig/IVwyKVteXFxdfFxcLikqPylcMilcXXwoPz0oPzpcLnxcW1xdKSg/OlwufFxbXF18JCkpL2c7CgogICAgICAvKioKICAgICAgICogVXNlZCB0byBtYXRjaCBgUmVnRXhwYAogICAgICAgKiBbc3ludGF4IGNoYXJhY3RlcnNdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXBhdHRlcm5zKS4KICAgICAgICovCiAgICAgIHZhciByZVJlZ0V4cENoYXIgPSAvW1xcXiQuKis/KClbXF17fXxdL2csCiAgICAgICAgICByZUhhc1JlZ0V4cENoYXIgPSBSZWdFeHAocmVSZWdFeHBDaGFyLnNvdXJjZSk7CgogICAgICAvKiogVXNlZCB0byBtYXRjaCBsZWFkaW5nIGFuZCB0cmFpbGluZyB3aGl0ZXNwYWNlLiAqLwogICAgICB2YXIgcmVUcmltID0gL15ccyt8XHMrJC9nLAogICAgICAgICAgcmVUcmltU3RhcnQgPSAvXlxzKy8sCiAgICAgICAgICByZVRyaW1FbmQgPSAvXHMrJC87CgogICAgICAvKiogVXNlZCB0byBtYXRjaCB3cmFwIGRldGFpbCBjb21tZW50cy4gKi8KICAgICAgdmFyIHJlV3JhcENvbW1lbnQgPSAvXHsoPzpcblwvXCogXFt3cmFwcGVkIHdpdGggLitcXSBcKlwvKT9cbj8vLAogICAgICAgICAgcmVXcmFwRGV0YWlscyA9IC9ce1xuXC9cKiBcW3dyYXBwZWQgd2l0aCAoLispXF0gXCovLAogICAgICAgICAgcmVTcGxpdERldGFpbHMgPSAvLD8gJiAvOwoKICAgICAgLyoqIFVzZWQgdG8gbWF0Y2ggd29yZHMgY29tcG9zZWQgb2YgYWxwaGFudW1lcmljIGNoYXJhY3RlcnMuICovCiAgICAgIHZhciByZUFzY2lpV29yZCA9IC9bXlx4MDAtXHgyZlx4M2EtXHg0MFx4NWItXHg2MFx4N2ItXHg3Zl0rL2c7CgogICAgICAvKiogVXNlZCB0byBtYXRjaCBiYWNrc2xhc2hlcyBpbiBwcm9wZXJ0eSBwYXRocy4gKi8KICAgICAgdmFyIHJlRXNjYXBlQ2hhciA9IC9cXChcXCk/L2c7CgogICAgICAvKioKICAgICAgICogVXNlZCB0byBtYXRjaAogICAgICAgKiBbRVMgdGVtcGxhdGUgZGVsaW1pdGVyc10oaHR0cDovL2VjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtdGVtcGxhdGUtbGl0ZXJhbC1sZXhpY2FsLWNvbXBvbmVudHMpLgogICAgICAgKi8KICAgICAgdmFyIHJlRXNUZW1wbGF0ZSA9IC9cJFx7KFteXFx9XSooPzpcXC5bXlxcfV0qKSopXH0vZzsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIGBSZWdFeHBgIGZsYWdzIGZyb20gdGhlaXIgY29lcmNlZCBzdHJpbmcgdmFsdWVzLiAqLwogICAgICB2YXIgcmVGbGFncyA9IC9cdyokLzsKCiAgICAgIC8qKiBVc2VkIHRvIGRldGVjdCBiYWQgc2lnbmVkIGhleGFkZWNpbWFsIHN0cmluZyB2YWx1ZXMuICovCiAgICAgIHZhciByZUlzQmFkSGV4ID0gL15bLStdMHhbMC05YS1mXSskL2k7CgogICAgICAvKiogVXNlZCB0byBkZXRlY3QgYmluYXJ5IHN0cmluZyB2YWx1ZXMuICovCiAgICAgIHZhciByZUlzQmluYXJ5ID0gL14wYlswMV0rJC9pOwoKICAgICAgLyoqIFVzZWQgdG8gZGV0ZWN0IGhvc3QgY29uc3RydWN0b3JzIChTYWZhcmkpLiAqLwogICAgICB2YXIgcmVJc0hvc3RDdG9yID0gL15cW29iamVjdCAuKz9Db25zdHJ1Y3RvclxdJC87CgogICAgICAvKiogVXNlZCB0byBkZXRlY3Qgb2N0YWwgc3RyaW5nIHZhbHVlcy4gKi8KICAgICAgdmFyIHJlSXNPY3RhbCA9IC9eMG9bMC03XSskL2k7CgogICAgICAvKiogVXNlZCB0byBkZXRlY3QgdW5zaWduZWQgaW50ZWdlciB2YWx1ZXMuICovCiAgICAgIHZhciByZUlzVWludCA9IC9eKD86MHxbMS05XVxkKikkLzsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIExhdGluIFVuaWNvZGUgbGV0dGVycyAoZXhjbHVkaW5nIG1hdGhlbWF0aWNhbCBvcGVyYXRvcnMpLiAqLwogICAgICB2YXIgcmVMYXRpbiA9IC9bXHhjMC1ceGQ2XHhkOC1ceGY2XHhmOC1ceGZmXHUwMTAwLVx1MDE3Zl0vZzsKCiAgICAgIC8qKiBVc2VkIHRvIGVuc3VyZSBjYXB0dXJpbmcgb3JkZXIgb2YgdGVtcGxhdGUgZGVsaW1pdGVycy4gKi8KICAgICAgdmFyIHJlTm9NYXRjaCA9IC8oJF4pLzsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIHVuZXNjYXBlZCBjaGFyYWN0ZXJzIGluIGNvbXBpbGVkIHN0cmluZyBsaXRlcmFscy4gKi8KICAgICAgdmFyIHJlVW5lc2NhcGVkU3RyaW5nID0gL1snXG5cclx1MjAyOFx1MjAyOVxcXS9nOwoKICAgICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIGNoYXJhY3RlciBjbGFzc2VzLiAqLwogICAgICB2YXIgcnNBc3RyYWxSYW5nZSA9ICdcXHVkODAwLVxcdWRmZmYnLAogICAgICAgICAgcnNDb21ib01hcmtzUmFuZ2UgPSAnXFx1MDMwMC1cXHUwMzZmJywKICAgICAgICAgIHJlQ29tYm9IYWxmTWFya3NSYW5nZSA9ICdcXHVmZTIwLVxcdWZlMmYnLAogICAgICAgICAgcnNDb21ib1N5bWJvbHNSYW5nZSA9ICdcXHUyMGQwLVxcdTIwZmYnLAogICAgICAgICAgcnNDb21ib1JhbmdlID0gcnNDb21ib01hcmtzUmFuZ2UgKyByZUNvbWJvSGFsZk1hcmtzUmFuZ2UgKyByc0NvbWJvU3ltYm9sc1JhbmdlLAogICAgICAgICAgcnNEaW5nYmF0UmFuZ2UgPSAnXFx1MjcwMC1cXHUyN2JmJywKICAgICAgICAgIHJzTG93ZXJSYW5nZSA9ICdhLXpcXHhkZi1cXHhmNlxceGY4LVxceGZmJywKICAgICAgICAgIHJzTWF0aE9wUmFuZ2UgPSAnXFx4YWNcXHhiMVxceGQ3XFx4ZjcnLAogICAgICAgICAgcnNOb25DaGFyUmFuZ2UgPSAnXFx4MDAtXFx4MmZcXHgzYS1cXHg0MFxceDViLVxceDYwXFx4N2ItXFx4YmYnLAogICAgICAgICAgcnNQdW5jdHVhdGlvblJhbmdlID0gJ1xcdTIwMDAtXFx1MjA2ZicsCiAgICAgICAgICByc1NwYWNlUmFuZ2UgPSAnIFxcdFxceDBiXFxmXFx4YTBcXHVmZWZmXFxuXFxyXFx1MjAyOFxcdTIwMjlcXHUxNjgwXFx1MTgwZVxcdTIwMDBcXHUyMDAxXFx1MjAwMlxcdTIwMDNcXHUyMDA0XFx1MjAwNVxcdTIwMDZcXHUyMDA3XFx1MjAwOFxcdTIwMDlcXHUyMDBhXFx1MjAyZlxcdTIwNWZcXHUzMDAwJywKICAgICAgICAgIHJzVXBwZXJSYW5nZSA9ICdBLVpcXHhjMC1cXHhkNlxceGQ4LVxceGRlJywKICAgICAgICAgIHJzVmFyUmFuZ2UgPSAnXFx1ZmUwZVxcdWZlMGYnLAogICAgICAgICAgcnNCcmVha1JhbmdlID0gcnNNYXRoT3BSYW5nZSArIHJzTm9uQ2hhclJhbmdlICsgcnNQdW5jdHVhdGlvblJhbmdlICsgcnNTcGFjZVJhbmdlOwoKICAgICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIGNhcHR1cmUgZ3JvdXBzLiAqLwogICAgICB2YXIgcnNBcG9zID0gIlsnXHUyMDE5XSIsCiAgICAgICAgICByc0FzdHJhbCA9ICdbJyArIHJzQXN0cmFsUmFuZ2UgKyAnXScsCiAgICAgICAgICByc0JyZWFrID0gJ1snICsgcnNCcmVha1JhbmdlICsgJ10nLAogICAgICAgICAgcnNDb21ibyA9ICdbJyArIHJzQ29tYm9SYW5nZSArICddJywKICAgICAgICAgIHJzRGlnaXRzID0gJ1xcZCsnLAogICAgICAgICAgcnNEaW5nYmF0ID0gJ1snICsgcnNEaW5nYmF0UmFuZ2UgKyAnXScsCiAgICAgICAgICByc0xvd2VyID0gJ1snICsgcnNMb3dlclJhbmdlICsgJ10nLAogICAgICAgICAgcnNNaXNjID0gJ1teJyArIHJzQXN0cmFsUmFuZ2UgKyByc0JyZWFrUmFuZ2UgKyByc0RpZ2l0cyArIHJzRGluZ2JhdFJhbmdlICsgcnNMb3dlclJhbmdlICsgcnNVcHBlclJhbmdlICsgJ10nLAogICAgICAgICAgcnNGaXR6ID0gJ1xcdWQ4M2NbXFx1ZGZmYi1cXHVkZmZmXScsCiAgICAgICAgICByc01vZGlmaWVyID0gJyg/OicgKyByc0NvbWJvICsgJ3wnICsgcnNGaXR6ICsgJyknLAogICAgICAgICAgcnNOb25Bc3RyYWwgPSAnW14nICsgcnNBc3RyYWxSYW5nZSArICddJywKICAgICAgICAgIHJzUmVnaW9uYWwgPSAnKD86XFx1ZDgzY1tcXHVkZGU2LVxcdWRkZmZdKXsyfScsCiAgICAgICAgICByc1N1cnJQYWlyID0gJ1tcXHVkODAwLVxcdWRiZmZdW1xcdWRjMDAtXFx1ZGZmZl0nLAogICAgICAgICAgcnNVcHBlciA9ICdbJyArIHJzVXBwZXJSYW5nZSArICddJywKICAgICAgICAgIHJzWldKID0gJ1xcdTIwMGQnOwoKICAgICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIHJlZ2V4ZXMuICovCiAgICAgIHZhciByc01pc2NMb3dlciA9ICcoPzonICsgcnNMb3dlciArICd8JyArIHJzTWlzYyArICcpJywKICAgICAgICAgIHJzTWlzY1VwcGVyID0gJyg/OicgKyByc1VwcGVyICsgJ3wnICsgcnNNaXNjICsgJyknLAogICAgICAgICAgcnNPcHRDb250ckxvd2VyID0gJyg/OicgKyByc0Fwb3MgKyAnKD86ZHxsbHxtfHJlfHN8dHx2ZSkpPycsCiAgICAgICAgICByc09wdENvbnRyVXBwZXIgPSAnKD86JyArIHJzQXBvcyArICcoPzpEfExMfE18UkV8U3xUfFZFKSk/JywKICAgICAgICAgIHJlT3B0TW9kID0gcnNNb2RpZmllciArICc/JywKICAgICAgICAgIHJzT3B0VmFyID0gJ1snICsgcnNWYXJSYW5nZSArICddPycsCiAgICAgICAgICByc09wdEpvaW4gPSAnKD86JyArIHJzWldKICsgJyg/OicgKyBbcnNOb25Bc3RyYWwsIHJzUmVnaW9uYWwsIHJzU3VyclBhaXJdLmpvaW4oJ3wnKSArICcpJyArIHJzT3B0VmFyICsgcmVPcHRNb2QgKyAnKSonLAogICAgICAgICAgcnNPcmRMb3dlciA9ICdcXGQqKD86MXN0fDJuZHwzcmR8KD8hWzEyM10pXFxkdGgpKD89XFxifFtBLVpfXSknLAogICAgICAgICAgcnNPcmRVcHBlciA9ICdcXGQqKD86MVNUfDJORHwzUkR8KD8hWzEyM10pXFxkVEgpKD89XFxifFthLXpfXSknLAogICAgICAgICAgcnNTZXEgPSByc09wdFZhciArIHJlT3B0TW9kICsgcnNPcHRKb2luLAogICAgICAgICAgcnNFbW9qaSA9ICcoPzonICsgW3JzRGluZ2JhdCwgcnNSZWdpb25hbCwgcnNTdXJyUGFpcl0uam9pbignfCcpICsgJyknICsgcnNTZXEsCiAgICAgICAgICByc1N5bWJvbCA9ICcoPzonICsgW3JzTm9uQXN0cmFsICsgcnNDb21ibyArICc/JywgcnNDb21ibywgcnNSZWdpb25hbCwgcnNTdXJyUGFpciwgcnNBc3RyYWxdLmpvaW4oJ3wnKSArICcpJzsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIGFwb3N0cm9waGVzLiAqLwogICAgICB2YXIgcmVBcG9zID0gUmVnRXhwKHJzQXBvcywgJ2cnKTsKCiAgICAgIC8qKgogICAgICAgKiBVc2VkIHRvIG1hdGNoIFtjb21iaW5pbmcgZGlhY3JpdGljYWwgbWFya3NdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0NvbWJpbmluZ19EaWFjcml0aWNhbF9NYXJrcykgYW5kCiAgICAgICAqIFtjb21iaW5pbmcgZGlhY3JpdGljYWwgbWFya3MgZm9yIHN5bWJvbHNdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0NvbWJpbmluZ19EaWFjcml0aWNhbF9NYXJrc19mb3JfU3ltYm9scykuCiAgICAgICAqLwogICAgICB2YXIgcmVDb21ib01hcmsgPSBSZWdFeHAocnNDb21ibywgJ2cnKTsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIFtzdHJpbmcgc3ltYm9sc10oaHR0cHM6Ly9tYXRoaWFzYnluZW5zLmJlL25vdGVzL2phdmFzY3JpcHQtdW5pY29kZSkuICovCiAgICAgIHZhciByZVVuaWNvZGUgPSBSZWdFeHAocnNGaXR6ICsgJyg/PScgKyByc0ZpdHogKyAnKXwnICsgcnNTeW1ib2wgKyByc1NlcSwgJ2cnKTsKCiAgICAgIC8qKiBVc2VkIHRvIG1hdGNoIGNvbXBsZXggb3IgY29tcG91bmQgd29yZHMuICovCiAgICAgIHZhciByZVVuaWNvZGVXb3JkID0gUmVnRXhwKFsKICAgICAgICByc1VwcGVyICsgJz8nICsgcnNMb3dlciArICcrJyArIHJzT3B0Q29udHJMb3dlciArICcoPz0nICsgW3JzQnJlYWssIHJzVXBwZXIsICckJ10uam9pbignfCcpICsgJyknLAogICAgICAgIHJzTWlzY1VwcGVyICsgJysnICsgcnNPcHRDb250clVwcGVyICsgJyg/PScgKyBbcnNCcmVhaywgcnNVcHBlciArIHJzTWlzY0xvd2VyLCAnJCddLmpvaW4oJ3wnKSArICcpJywKICAgICAgICByc1VwcGVyICsgJz8nICsgcnNNaXNjTG93ZXIgKyAnKycgKyByc09wdENvbnRyTG93ZXIsCiAgICAgICAgcnNVcHBlciArICcrJyArIHJzT3B0Q29udHJVcHBlciwKICAgICAgICByc09yZFVwcGVyLAogICAgICAgIHJzT3JkTG93ZXIsCiAgICAgICAgcnNEaWdpdHMsCiAgICAgICAgcnNFbW9qaQogICAgICBdLmpvaW4oJ3wnKSwgJ2cnKTsKCiAgICAgIC8qKiBVc2VkIHRvIGRldGVjdCBzdHJpbmdzIHdpdGggW3plcm8td2lkdGggam9pbmVycyBvciBjb2RlIHBvaW50cyBmcm9tIHRoZSBhc3RyYWwgcGxhbmVzXShodHRwOi8vZWV2LmVlL2Jsb2cvMjAxNS8wOS8xMi9kYXJrLWNvcm5lcnMtb2YtdW5pY29kZS8pLiAqLwogICAgICB2YXIgcmVIYXNVbmljb2RlID0gUmVnRXhwKCdbJyArIHJzWldKICsgcnNBc3RyYWxSYW5nZSAgKyByc0NvbWJvUmFuZ2UgKyByc1ZhclJhbmdlICsgJ10nKTsKCiAgICAgIC8qKiBVc2VkIHRvIGRldGVjdCBzdHJpbmdzIHRoYXQgbmVlZCBhIG1vcmUgcm9idXN0IHJlZ2V4cCB0byBtYXRjaCB3b3Jkcy4gKi8KICAgICAgdmFyIHJlSGFzVW5pY29kZVdvcmQgPSAvW2Etel1bQS1aXXxbQS1aXXsyfVthLXpdfFswLTldW2EtekEtWl18W2EtekEtWl1bMC05XXxbXmEtekEtWjAtOSBdLzsKCiAgICAgIC8qKiBVc2VkIHRvIGFzc2lnbiBkZWZhdWx0IGBjb250ZXh0YCBvYmplY3QgcHJvcGVydGllcy4gKi8KICAgICAgdmFyIGNvbnRleHRQcm9wcyA9IFsKICAgICAgICAnQXJyYXknLCAnQnVmZmVyJywgJ0RhdGFWaWV3JywgJ0RhdGUnLCAnRXJyb3InLCAnRmxvYXQzMkFycmF5JywgJ0Zsb2F0NjRBcnJheScsCiAgICAgICAgJ0Z1bmN0aW9uJywgJ0ludDhBcnJheScsICdJbnQxNkFycmF5JywgJ0ludDMyQXJyYXknLCAnTWFwJywgJ01hdGgnLCAnT2JqZWN0JywKICAgICAgICAnUHJvbWlzZScsICdSZWdFeHAnLCAnU2V0JywgJ1N0cmluZycsICdTeW1ib2wnLCAnVHlwZUVycm9yJywgJ1VpbnQ4QXJyYXknLAogICAgICAgICdVaW50OENsYW1wZWRBcnJheScsICdVaW50MTZBcnJheScsICdVaW50MzJBcnJheScsICdXZWFrTWFwJywKICAgICAgICAnXycsICdjbGVhclRpbWVvdXQnLCAnaXNGaW5pdGUnLCAncGFyc2VJbnQnLCAnc2V0VGltZW91dCcKICAgICAgXTsKCiAgICAgIC8qKiBVc2VkIHRvIG1ha2UgdGVtcGxhdGUgc291cmNlVVJMcyBlYXNpZXIgdG8gaWRlbnRpZnkuICovCiAgICAgIHZhciB0ZW1wbGF0ZUNvdW50ZXIgPSAtMTsKCiAgICAgIC8qKiBVc2VkIHRvIGlkZW50aWZ5IGB0b1N0cmluZ1RhZ2AgdmFsdWVzIG9mIHR5cGVkIGFycmF5cy4gKi8KICAgICAgdmFyIHR5cGVkQXJyYXlUYWdzID0ge307CiAgICAgIHR5cGVkQXJyYXlUYWdzW2Zsb2F0MzJUYWddID0gdHlwZWRBcnJheVRhZ3NbZmxvYXQ2NFRhZ10gPQogICAgICB0eXBlZEFycmF5VGFnc1tpbnQ4VGFnXSA9IHR5cGVkQXJyYXlUYWdzW2ludDE2VGFnXSA9CiAgICAgIHR5cGVkQXJyYXlUYWdzW2ludDMyVGFnXSA9IHR5cGVkQXJyYXlUYWdzW3VpbnQ4VGFnXSA9CiAgICAgIHR5cGVkQXJyYXlUYWdzW3VpbnQ4Q2xhbXBlZFRhZ10gPSB0eXBlZEFycmF5VGFnc1t1aW50MTZUYWddID0KICAgICAgdHlwZWRBcnJheVRhZ3NbdWludDMyVGFnXSA9IHRydWU7CiAgICAgIHR5cGVkQXJyYXlUYWdzW2FyZ3NUYWddID0gdHlwZWRBcnJheVRhZ3NbYXJyYXlUYWddID0KICAgICAgdHlwZWRBcnJheVRhZ3NbYXJyYXlCdWZmZXJUYWddID0gdHlwZWRBcnJheVRhZ3NbYm9vbFRhZ10gPQogICAgICB0eXBlZEFycmF5VGFnc1tkYXRhVmlld1RhZ10gPSB0eXBlZEFycmF5VGFnc1tkYXRlVGFnXSA9CiAgICAgIHR5cGVkQXJyYXlUYWdzW2Vycm9yVGFnXSA9IHR5cGVkQXJyYXlUYWdzW2Z1bmNUYWddID0KICAgICAgdHlwZWRBcnJheVRhZ3NbbWFwVGFnXSA9IHR5cGVkQXJyYXlUYWdzW251bWJlclRhZ10gPQogICAgICB0eXBlZEFycmF5VGFnc1tvYmplY3RUYWddID0gdHlwZWRBcnJheVRhZ3NbcmVnZXhwVGFnXSA9CiAgICAgIHR5cGVkQXJyYXlUYWdzW3NldFRhZ10gPSB0eXBlZEFycmF5VGFnc1tzdHJpbmdUYWddID0KICAgICAgdHlwZWRBcnJheVRhZ3Nbd2Vha01hcFRhZ10gPSBmYWxzZTsKCiAgICAgIC8qKiBVc2VkIHRvIGlkZW50aWZ5IGB0b1N0cmluZ1RhZ2AgdmFsdWVzIHN1cHBvcnRlZCBieSBgXy5jbG9uZWAuICovCiAgICAgIHZhciBjbG9uZWFibGVUYWdzID0ge307CiAgICAgIGNsb25lYWJsZVRhZ3NbYXJnc1RhZ10gPSBjbG9uZWFibGVUYWdzW2FycmF5VGFnXSA9CiAgICAgIGNsb25lYWJsZVRhZ3NbYXJyYXlCdWZmZXJUYWddID0gY2xvbmVhYmxlVGFnc1tkYXRhVmlld1RhZ10gPQogICAgICBjbG9uZWFibGVUYWdzW2Jvb2xUYWddID0gY2xvbmVhYmxlVGFnc1tkYXRlVGFnXSA9CiAgICAgIGNsb25lYWJsZVRhZ3NbZmxvYXQzMlRhZ10gPSBjbG9uZWFibGVUYWdzW2Zsb2F0NjRUYWddID0KICAgICAgY2xvbmVhYmxlVGFnc1tpbnQ4VGFnXSA9IGNsb25lYWJsZVRhZ3NbaW50MTZUYWddID0KICAgICAgY2xvbmVhYmxlVGFnc1tpbnQzMlRhZ10gPSBjbG9uZWFibGVUYWdzW21hcFRhZ10gPQogICAgICBjbG9uZWFibGVUYWdzW251bWJlclRhZ10gPSBjbG9uZWFibGVUYWdzW29iamVjdFRhZ10gPQogICAgICBjbG9uZWFibGVUYWdzW3JlZ2V4cFRhZ10gPSBjbG9uZWFibGVUYWdzW3NldFRhZ10gPQogICAgICBjbG9uZWFibGVUYWdzW3N0cmluZ1RhZ10gPSBjbG9uZWFibGVUYWdzW3N5bWJvbFRhZ10gPQogICAgICBjbG9uZWFibGVUYWdzW3VpbnQ4VGFnXSA9IGNsb25lYWJsZVRhZ3NbdWludDhDbGFtcGVkVGFnXSA9CiAgICAgIGNsb25lYWJsZVRhZ3NbdWludDE2VGFnXSA9IGNsb25lYWJsZVRhZ3NbdWludDMyVGFnXSA9IHRydWU7CiAgICAgIGNsb25lYWJsZVRhZ3NbZXJyb3JUYWddID0gY2xvbmVhYmxlVGFnc1tmdW5jVGFnXSA9CiAgICAgIGNsb25lYWJsZVRhZ3Nbd2Vha01hcFRhZ10gPSBmYWxzZTsKCiAgICAgIC8qKiBVc2VkIHRvIG1hcCBMYXRpbiBVbmljb2RlIGxldHRlcnMgdG8gYmFzaWMgTGF0aW4gbGV0dGVycy4gKi8KICAgICAgdmFyIGRlYnVycmVkTGV0dGVycyA9IHsKICAgICAgICAvLyBMYXRpbi0xIFN1cHBsZW1lbnQgYmxvY2suCiAgICAgICAgJ1x4YzAnOiAnQScsICAnXHhjMSc6ICdBJywgJ1x4YzInOiAnQScsICdceGMzJzogJ0EnLCAnXHhjNCc6ICdBJywgJ1x4YzUnOiAnQScsCiAgICAgICAgJ1x4ZTAnOiAnYScsICAnXHhlMSc6ICdhJywgJ1x4ZTInOiAnYScsICdceGUzJzogJ2EnLCAnXHhlNCc6ICdhJywgJ1x4ZTUnOiAnYScsCiAgICAgICAgJ1x4YzcnOiAnQycsICAnXHhlNyc6ICdjJywKICAgICAgICAnXHhkMCc6ICdEJywgICdceGYwJzogJ2QnLAogICAgICAgICdceGM4JzogJ0UnLCAgJ1x4YzknOiAnRScsICdceGNhJzogJ0UnLCAnXHhjYic6ICdFJywKICAgICAgICAnXHhlOCc6ICdlJywgICdceGU5JzogJ2UnLCAnXHhlYSc6ICdlJywgJ1x4ZWInOiAnZScsCiAgICAgICAgJ1x4Y2MnOiAnSScsICAnXHhjZCc6ICdJJywgJ1x4Y2UnOiAnSScsICdceGNmJzogJ0knLAogICAgICAgICdceGVjJzogJ2knLCAgJ1x4ZWQnOiAnaScsICdceGVlJzogJ2knLCAnXHhlZic6ICdpJywKICAgICAgICAnXHhkMSc6ICdOJywgICdceGYxJzogJ24nLAogICAgICAgICdceGQyJzogJ08nLCAgJ1x4ZDMnOiAnTycsICdceGQ0JzogJ08nLCAnXHhkNSc6ICdPJywgJ1x4ZDYnOiAnTycsICdceGQ4JzogJ08nLAogICAgICAgICdceGYyJzogJ28nLCAgJ1x4ZjMnOiAnbycsICdceGY0JzogJ28nLCAnXHhmNSc6ICdvJywgJ1x4ZjYnOiAnbycsICdceGY4JzogJ28nLAogICAgICAgICdceGQ5JzogJ1UnLCAgJ1x4ZGEnOiAnVScsICdceGRiJzogJ1UnLCAnXHhkYyc6ICdVJywKICAgICAgICAnXHhmOSc6ICd1JywgICdceGZhJzogJ3UnLCAnXHhmYic6ICd1JywgJ1x4ZmMnOiAndScsCiAgICAgICAgJ1x4ZGQnOiAnWScsICAnXHhmZCc6ICd5JywgJ1x4ZmYnOiAneScsCiAgICAgICAgJ1x4YzYnOiAnQWUnLCAnXHhlNic6ICdhZScsCiAgICAgICAgJ1x4ZGUnOiAnVGgnLCAnXHhmZSc6ICd0aCcsCiAgICAgICAgJ1x4ZGYnOiAnc3MnLAogICAgICAgIC8vIExhdGluIEV4dGVuZGVkLUEgYmxvY2suCiAgICAgICAgJ1x1MDEwMCc6ICdBJywgICdcdTAxMDInOiAnQScsICdcdTAxMDQnOiAnQScsCiAgICAgICAgJ1x1MDEwMSc6ICdhJywgICdcdTAxMDMnOiAnYScsICdcdTAxMDUnOiAnYScsCiAgICAgICAgJ1x1MDEwNic6ICdDJywgICdcdTAxMDgnOiAnQycsICdcdTAxMGEnOiAnQycsICdcdTAxMGMnOiAnQycsCiAgICAgICAgJ1x1MDEwNyc6ICdjJywgICdcdTAxMDknOiAnYycsICdcdTAxMGInOiAnYycsICdcdTAxMGQnOiAnYycsCiAgICAgICAgJ1x1MDEwZSc6ICdEJywgICdcdTAxMTAnOiAnRCcsICdcdTAxMGYnOiAnZCcsICdcdTAxMTEnOiAnZCcsCiAgICAgICAgJ1x1MDExMic6ICdFJywgICdcdTAxMTQnOiAnRScsICdcdTAxMTYnOiAnRScsICdcdTAxMTgnOiAnRScsICdcdTAxMWEnOiAnRScsCiAgICAgICAgJ1x1MDExMyc6ICdlJywgICdcdTAxMTUnOiAnZScsICdcdTAxMTcnOiAnZScsICdcdTAxMTknOiAnZScsICdcdTAxMWInOiAnZScsCiAgICAgICAgJ1x1MDExYyc6ICdHJywgICdcdTAxMWUnOiAnRycsICdcdTAxMjAnOiAnRycsICdcdTAxMjInOiAnRycsCiAgICAgICAgJ1x1MDExZCc6ICdnJywgICdcdTAxMWYnOiAnZycsICdcdTAxMjEnOiAnZycsICdcdTAxMjMnOiAnZycsCiAgICAgICAgJ1x1MDEyNCc6ICdIJywgICdcdTAxMjYnOiAnSCcsICdcdTAxMjUnOiAnaCcsICdcdTAxMjcnOiAnaCcsCiAgICAgICAgJ1x1MDEyOCc6ICdJJywgICdcdTAxMmEnOiAnSScsICdcdTAxMmMnOiAnSScsICdcdTAxMmUnOiAnSScsICdcdTAxMzAnOiAnSScsCiAgICAgICAgJ1x1MDEyOSc6ICdpJywgICdcdTAxMmInOiAnaScsICdcdTAxMmQnOiAnaScsICdcdTAxMmYnOiAnaScsICdcdTAxMzEnOiAnaScsCiAgICAgICAgJ1x1MDEzNCc6ICdKJywgICdcdTAxMzUnOiAnaicsCiAgICAgICAgJ1x1MDEzNic6ICdLJywgICdcdTAxMzcnOiAnaycsICdcdTAxMzgnOiAnaycsCiAgICAgICAgJ1x1MDEzOSc6ICdMJywgICdcdTAxM2InOiAnTCcsICdcdTAxM2QnOiAnTCcsICdcdTAxM2YnOiAnTCcsICdcdTAxNDEnOiAnTCcsCiAgICAgICAgJ1x1MDEzYSc6ICdsJywgICdcdTAxM2MnOiAnbCcsICdcdTAxM2UnOiAnbCcsICdcdTAxNDAnOiAnbCcsICdcdTAxNDInOiAnbCcsCiAgICAgICAgJ1x1MDE0Myc6ICdOJywgICdcdTAxNDUnOiAnTicsICdcdTAxNDcnOiAnTicsICdcdTAxNGEnOiAnTicsCiAgICAgICAgJ1x1MDE0NCc6ICduJywgICdcdTAxNDYnOiAnbicsICdcdTAxNDgnOiAnbicsICdcdTAxNGInOiAnbicsCiAgICAgICAgJ1x1MDE0Yyc6ICdPJywgICdcdTAxNGUnOiAnTycsICdcdTAxNTAnOiAnTycsCiAgICAgICAgJ1x1MDE0ZCc6ICdvJywgICdcdTAxNGYnOiAnbycsICdcdTAxNTEnOiAnbycsCiAgICAgICAgJ1x1MDE1NCc6ICdSJywgICdcdTAxNTYnOiAnUicsICdcdTAxNTgnOiAnUicsCiAgICAgICAgJ1x1MDE1NSc6ICdyJywgICdcdTAxNTcnOiAncicsICdcdTAxNTknOiAncicsCiAgICAgICAgJ1x1MDE1YSc6ICdTJywgICdcdTAxNWMnOiAnUycsICdcdTAxNWUnOiAnUycsICdcdTAxNjAnOiAnUycsCiAgICAgICAgJ1x1MDE1Yic6ICdzJywgICdcdTAxNWQnOiAncycsICdcdTAxNWYnOiAncycsICdcdTAxNjEnOiAncycsCiAgICAgICAgJ1x1MDE2Mic6ICdUJywgICdcdTAxNjQnOiAnVCcsICdcdTAxNjYnOiAnVCcsCiAgICAgICAgJ1x1MDE2Myc6ICd0JywgICdcdTAxNjUnOiAndCcsICdcdTAxNjcnOiAndCcsCiAgICAgICAgJ1x1MDE2OCc6ICdVJywgICdcdTAxNmEnOiAnVScsICdcdTAxNmMnOiAnVScsICdcdTAxNmUnOiAnVScsICdcdTAxNzAnOiAnVScsICdcdTAxNzInOiAnVScsCiAgICAgICAgJ1x1MDE2OSc6ICd1JywgICdcdTAxNmInOiAndScsICdcdTAxNmQnOiAndScsICdcdTAxNmYnOiAndScsICdcdTAxNzEnOiAndScsICdcdTAxNzMnOiAndScsCiAgICAgICAgJ1x1MDE3NCc6ICdXJywgICdcdTAxNzUnOiAndycsCiAgICAgICAgJ1x1MDE3Nic6ICdZJywgICdcdTAxNzcnOiAneScsICdcdTAxNzgnOiAnWScsCiAgICAgICAgJ1x1MDE3OSc6ICdaJywgICdcdTAxN2InOiAnWicsICdcdTAxN2QnOiAnWicsCiAgICAgICAgJ1x1MDE3YSc6ICd6JywgICdcdTAxN2MnOiAneicsICdcdTAxN2UnOiAneicsCiAgICAgICAgJ1x1MDEzMic6ICdJSicsICdcdTAxMzMnOiAnaWonLAogICAgICAgICdcdTAxNTInOiAnT2UnLCAnXHUwMTUzJzogJ29lJywKICAgICAgICAnXHUwMTQ5JzogIiduIiwgJ1x1MDE3Zic6ICdzJwogICAgICB9OwoKICAgICAgLyoqIFVzZWQgdG8gbWFwIGNoYXJhY3RlcnMgdG8gSFRNTCBlbnRpdGllcy4gKi8KICAgICAgdmFyIGh0bWxFc2NhcGVzID0gewogICAgICAgICcmJzogJyZhbXA7JywKICAgICAgICAnPCc6ICcmbHQ7JywKICAgICAgICAnPic6ICcmZ3Q7JywKICAgICAgICAnIic6ICcmcXVvdDsnLAogICAgICAgICInIjogJyYjMzk7JwogICAgICB9OwoKICAgICAgLyoqIFVzZWQgdG8gbWFwIEhUTUwgZW50aXRpZXMgdG8gY2hhcmFjdGVycy4gKi8KICAgICAgdmFyIGh0bWxVbmVzY2FwZXMgPSB7CiAgICAgICAgJyZhbXA7JzogJyYnLAogICAgICAgICcmbHQ7JzogJzwnLAogICAgICAgICcmZ3Q7JzogJz4nLAogICAgICAgICcmcXVvdDsnOiAnIicsCiAgICAgICAgJyYjMzk7JzogIiciCiAgICAgIH07CgogICAgICAvKiogVXNlZCB0byBlc2NhcGUgY2hhcmFjdGVycyBmb3IgaW5jbHVzaW9uIGluIGNvbXBpbGVkIHN0cmluZyBsaXRlcmFscy4gKi8KICAgICAgdmFyIHN0cmluZ0VzY2FwZXMgPSB7CiAgICAgICAgJ1xcJzogJ1xcJywKICAgICAgICAiJyI6ICInIiwKICAgICAgICAnXG4nOiAnbicsCiAgICAgICAgJ1xyJzogJ3InLAogICAgICAgICdcdTIwMjgnOiAndTIwMjgnLAogICAgICAgICdcdTIwMjknOiAndTIwMjknCiAgICAgIH07CgogICAgICAvKiogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgd2l0aG91dCBhIGRlcGVuZGVuY3kgb24gYHJvb3RgLiAqLwogICAgICB2YXIgZnJlZVBhcnNlRmxvYXQgPSBwYXJzZUZsb2F0LAogICAgICAgICAgZnJlZVBhcnNlSW50ID0gcGFyc2VJbnQ7CgogICAgICAvKiogRGV0ZWN0IGZyZWUgdmFyaWFibGUgYGdsb2JhbGAgZnJvbSBOb2RlLmpzLiAqLwogICAgICB2YXIgZnJlZUdsb2JhbCA9IHR5cGVvZiBjb21tb25qc0dsb2JhbCA9PSAnb2JqZWN0JyAmJiBjb21tb25qc0dsb2JhbCAmJiBjb21tb25qc0dsb2JhbC5PYmplY3QgPT09IE9iamVjdCAmJiBjb21tb25qc0dsb2JhbDsKCiAgICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgc2VsZmAuICovCiAgICAgIHZhciBmcmVlU2VsZiA9IHR5cGVvZiBzZWxmID09ICdvYmplY3QnICYmIHNlbGYgJiYgc2VsZi5PYmplY3QgPT09IE9iamVjdCAmJiBzZWxmOwoKICAgICAgLyoqIFVzZWQgYXMgYSByZWZlcmVuY2UgdG8gdGhlIGdsb2JhbCBvYmplY3QuICovCiAgICAgIHZhciByb290ID0gZnJlZUdsb2JhbCB8fCBmcmVlU2VsZiB8fCBGdW5jdGlvbigncmV0dXJuIHRoaXMnKSgpOwoKICAgICAgLyoqIERldGVjdCBmcmVlIHZhcmlhYmxlIGBleHBvcnRzYC4gKi8KICAgICAgdmFyIGZyZWVFeHBvcnRzID0gIGV4cG9ydHMgJiYgIWV4cG9ydHMubm9kZVR5cGUgJiYgZXhwb3J0czsKCiAgICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgbW9kdWxlYC4gKi8KICAgICAgdmFyIGZyZWVNb2R1bGUgPSBmcmVlRXhwb3J0cyAmJiAnb2JqZWN0JyA9PSAnb2JqZWN0JyAmJiBtb2R1bGUgJiYgIW1vZHVsZS5ub2RlVHlwZSAmJiBtb2R1bGU7CgogICAgICAvKiogRGV0ZWN0IHRoZSBwb3B1bGFyIENvbW1vbkpTIGV4dGVuc2lvbiBgbW9kdWxlLmV4cG9ydHNgLiAqLwogICAgICB2YXIgbW9kdWxlRXhwb3J0cyA9IGZyZWVNb2R1bGUgJiYgZnJlZU1vZHVsZS5leHBvcnRzID09PSBmcmVlRXhwb3J0czsKCiAgICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgcHJvY2Vzc2AgZnJvbSBOb2RlLmpzLiAqLwogICAgICB2YXIgZnJlZVByb2Nlc3MgPSBtb2R1bGVFeHBvcnRzICYmIGZyZWVHbG9iYWwucHJvY2VzczsKCiAgICAgIC8qKiBVc2VkIHRvIGFjY2VzcyBmYXN0ZXIgTm9kZS5qcyBoZWxwZXJzLiAqLwogICAgICB2YXIgbm9kZVV0aWwgPSAoZnVuY3Rpb24oKSB7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIC8vIFVzZSBgdXRpbC50eXBlc2AgZm9yIE5vZGUuanMgMTArLgogICAgICAgICAgdmFyIHR5cGVzID0gZnJlZU1vZHVsZSAmJiBmcmVlTW9kdWxlLnJlcXVpcmUgJiYgZnJlZU1vZHVsZS5yZXF1aXJlKCd1dGlsJykudHlwZXM7CgogICAgICAgICAgaWYgKHR5cGVzKSB7CiAgICAgICAgICAgIHJldHVybiB0eXBlczsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBMZWdhY3kgYHByb2Nlc3MuYmluZGluZygndXRpbCcpYCBmb3IgTm9kZS5qcyA8IDEwLgogICAgICAgICAgcmV0dXJuIGZyZWVQcm9jZXNzICYmIGZyZWVQcm9jZXNzLmJpbmRpbmcgJiYgZnJlZVByb2Nlc3MuYmluZGluZygndXRpbCcpOwogICAgICAgIH0gY2F0Y2ggKGUpIHt9CiAgICAgIH0oKSk7CgogICAgICAvKiBOb2RlLmpzIGhlbHBlciByZWZlcmVuY2VzLiAqLwogICAgICB2YXIgbm9kZUlzQXJyYXlCdWZmZXIgPSBub2RlVXRpbCAmJiBub2RlVXRpbC5pc0FycmF5QnVmZmVyLAogICAgICAgICAgbm9kZUlzRGF0ZSA9IG5vZGVVdGlsICYmIG5vZGVVdGlsLmlzRGF0ZSwKICAgICAgICAgIG5vZGVJc01hcCA9IG5vZGVVdGlsICYmIG5vZGVVdGlsLmlzTWFwLAogICAgICAgICAgbm9kZUlzUmVnRXhwID0gbm9kZVV0aWwgJiYgbm9kZVV0aWwuaXNSZWdFeHAsCiAgICAgICAgICBub2RlSXNTZXQgPSBub2RlVXRpbCAmJiBub2RlVXRpbC5pc1NldCwKICAgICAgICAgIG5vZGVJc1R5cGVkQXJyYXkgPSBub2RlVXRpbCAmJiBub2RlVXRpbC5pc1R5cGVkQXJyYXk7CgogICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgIC8qKgogICAgICAgKiBBIGZhc3RlciBhbHRlcm5hdGl2ZSB0byBgRnVuY3Rpb24jYXBwbHlgLCB0aGlzIGZ1bmN0aW9uIGludm9rZXMgYGZ1bmNgCiAgICAgICAqIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIGB0aGlzQXJnYCBhbmQgdGhlIGFyZ3VtZW50cyBvZiBgYXJnc2AuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGludm9rZS4KICAgICAgICogQHBhcmFtIHsqfSB0aGlzQXJnIFRoZSBgdGhpc2AgYmluZGluZyBvZiBgZnVuY2AuCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFyZ3MgVGhlIGFyZ3VtZW50cyB0byBpbnZva2UgYGZ1bmNgIHdpdGguCiAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXN1bHQgb2YgYGZ1bmNgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYXBwbHkoZnVuYywgdGhpc0FyZywgYXJncykgewogICAgICAgIHN3aXRjaCAoYXJncy5sZW5ndGgpIHsKICAgICAgICAgIGNhc2UgMDogcmV0dXJuIGZ1bmMuY2FsbCh0aGlzQXJnKTsKICAgICAgICAgIGNhc2UgMTogcmV0dXJuIGZ1bmMuY2FsbCh0aGlzQXJnLCBhcmdzWzBdKTsKICAgICAgICAgIGNhc2UgMjogcmV0dXJuIGZ1bmMuY2FsbCh0aGlzQXJnLCBhcmdzWzBdLCBhcmdzWzFdKTsKICAgICAgICAgIGNhc2UgMzogcmV0dXJuIGZ1bmMuY2FsbCh0aGlzQXJnLCBhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGZ1bmMuYXBwbHkodGhpc0FyZywgYXJncyk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYGJhc2VBZ2dyZWdhdG9yYCBmb3IgYXJyYXlzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHNldHRlciBUaGUgZnVuY3Rpb24gdG8gc2V0IGBhY2N1bXVsYXRvcmAgdmFsdWVzLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgaXRlcmF0ZWUgdG8gdHJhbnNmb3JtIGtleXMuCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBhY2N1bXVsYXRvciBUaGUgaW5pdGlhbCBhZ2dyZWdhdGVkIG9iamVjdC4KICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIGBhY2N1bXVsYXRvcmAuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBhcnJheUFnZ3JlZ2F0b3IoYXJyYXksIHNldHRlciwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yKSB7CiAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdOwogICAgICAgICAgc2V0dGVyKGFjY3VtdWxhdG9yLCB2YWx1ZSwgaXRlcmF0ZWUodmFsdWUpLCBhcnJheSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBhY2N1bXVsYXRvcjsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5mb3JFYWNoYCBmb3IgYXJyYXlzIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAgICogaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gW2FycmF5XSBUaGUgYXJyYXkgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGFycmF5RWFjaChhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICBpZiAoaXRlcmF0ZWUoYXJyYXlbaW5kZXhdLCBpbmRleCwgYXJyYXkpID09PSBmYWxzZSkgewogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGFycmF5OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLmZvckVhY2hSaWdodGAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgICAqIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIGBhcnJheWAuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBhcnJheUVhY2hSaWdodChhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CgogICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgaWYgKGl0ZXJhdGVlKGFycmF5W2xlbmd0aF0sIGxlbmd0aCwgYXJyYXkpID09PSBmYWxzZSkgewogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGFycmF5OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLmV2ZXJ5YCBmb3IgYXJyYXlzIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAgICogaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gW2FycmF5XSBUaGUgYXJyYXkgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBwcmVkaWNhdGUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGFsbCBlbGVtZW50cyBwYXNzIHRoZSBwcmVkaWNhdGUgY2hlY2ssCiAgICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBhcnJheUV2ZXJ5KGFycmF5LCBwcmVkaWNhdGUpIHsKICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICBpZiAoIXByZWRpY2F0ZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSkpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5maWx0ZXJgIGZvciBhcnJheXMgd2l0aG91dCBzdXBwb3J0IGZvcgogICAgICAgKiBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBmaWx0ZXJlZCBhcnJheS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGFycmF5RmlsdGVyKGFycmF5LCBwcmVkaWNhdGUpIHsKICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgIHJlc0luZGV4ID0gMCwKICAgICAgICAgICAgcmVzdWx0ID0gW107CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF07CiAgICAgICAgICBpZiAocHJlZGljYXRlKHZhbHVlLCBpbmRleCwgYXJyYXkpKSB7CiAgICAgICAgICAgIHJlc3VsdFtyZXNJbmRleCsrXSA9IHZhbHVlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLmluY2x1ZGVzYCBmb3IgYXJyYXlzIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAgICogc3BlY2lmeWluZyBhbiBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gW2FycmF5XSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICogQHBhcmFtIHsqfSB0YXJnZXQgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdGFyZ2V0YCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYXJyYXlJbmNsdWRlcyhhcnJheSwgdmFsdWUpIHsKICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgcmV0dXJuICEhbGVuZ3RoICYmIGJhc2VJbmRleE9mKGFycmF5LCB2YWx1ZSwgMCkgPiAtMTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoaXMgZnVuY3Rpb24gaXMgbGlrZSBgYXJyYXlJbmNsdWRlc2AgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBhIGNvbXBhcmF0b3IuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAqIEBwYXJhbSB7Kn0gdGFyZ2V0IFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjb21wYXJhdG9yIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdGFyZ2V0YCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYXJyYXlJbmNsdWRlc1dpdGgoYXJyYXksIHZhbHVlLCBjb21wYXJhdG9yKSB7CiAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgaWYgKGNvbXBhcmF0b3IodmFsdWUsIGFycmF5W2luZGV4XSkpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5tYXBgIGZvciBhcnJheXMgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZQogICAgICAgKiBzaG9ydGhhbmRzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IG1hcHBlZCBhcnJheS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGFycmF5TWFwKGFycmF5LCBpdGVyYXRlZSkgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aCwKICAgICAgICAgICAgcmVzdWx0ID0gQXJyYXkobGVuZ3RoKTsKCiAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgIHJlc3VsdFtpbmRleF0gPSBpdGVyYXRlZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBBcHBlbmRzIHRoZSBlbGVtZW50cyBvZiBgdmFsdWVzYCB0byBgYXJyYXlgLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gbW9kaWZ5LgogICAgICAgKiBAcGFyYW0ge0FycmF5fSB2YWx1ZXMgVGhlIHZhbHVlcyB0byBhcHBlbmQuCiAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYXJyYXlQdXNoKGFycmF5LCB2YWx1ZXMpIHsKICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgbGVuZ3RoID0gdmFsdWVzLmxlbmd0aCwKICAgICAgICAgICAgb2Zmc2V0ID0gYXJyYXkubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgYXJyYXlbb2Zmc2V0ICsgaW5kZXhdID0gdmFsdWVzW2luZGV4XTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGFycmF5OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLnJlZHVjZWAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgICAqIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICogQHBhcmFtIHsqfSBbYWNjdW11bGF0b3JdIFRoZSBpbml0aWFsIHZhbHVlLgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpbml0QWNjdW1dIFNwZWNpZnkgdXNpbmcgdGhlIGZpcnN0IGVsZW1lbnQgb2YgYGFycmF5YCBhcwogICAgICAgKiAgdGhlIGluaXRpYWwgdmFsdWUuCiAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBhY2N1bXVsYXRlZCB2YWx1ZS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGFycmF5UmVkdWNlKGFycmF5LCBpdGVyYXRlZSwgYWNjdW11bGF0b3IsIGluaXRBY2N1bSkgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKCiAgICAgICAgaWYgKGluaXRBY2N1bSAmJiBsZW5ndGgpIHsKICAgICAgICAgIGFjY3VtdWxhdG9yID0gYXJyYXlbKytpbmRleF07CiAgICAgICAgfQogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICBhY2N1bXVsYXRvciA9IGl0ZXJhdGVlKGFjY3VtdWxhdG9yLCBhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBhY2N1bXVsYXRvcjsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5yZWR1Y2VSaWdodGAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgICAqIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICogQHBhcmFtIHsqfSBbYWNjdW11bGF0b3JdIFRoZSBpbml0aWFsIHZhbHVlLgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpbml0QWNjdW1dIFNwZWNpZnkgdXNpbmcgdGhlIGxhc3QgZWxlbWVudCBvZiBgYXJyYXlgIGFzCiAgICAgICAqICB0aGUgaW5pdGlhbCB2YWx1ZS4KICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGFjY3VtdWxhdGVkIHZhbHVlLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYXJyYXlSZWR1Y2VSaWdodChhcnJheSwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yLCBpbml0QWNjdW0pIHsKICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgaWYgKGluaXRBY2N1bSAmJiBsZW5ndGgpIHsKICAgICAgICAgIGFjY3VtdWxhdG9yID0gYXJyYXlbLS1sZW5ndGhdOwogICAgICAgIH0KICAgICAgICB3aGlsZSAobGVuZ3RoLS0pIHsKICAgICAgICAgIGFjY3VtdWxhdG9yID0gaXRlcmF0ZWUoYWNjdW11bGF0b3IsIGFycmF5W2xlbmd0aF0sIGxlbmd0aCwgYXJyYXkpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gYWNjdW11bGF0b3I7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uc29tZWAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlCiAgICAgICAqIHNob3J0aGFuZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcHJlZGljYXRlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbnkgZWxlbWVudCBwYXNzZXMgdGhlIHByZWRpY2F0ZSBjaGVjaywKICAgICAgICogIGVsc2UgYGZhbHNlYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGFycmF5U29tZShhcnJheSwgcHJlZGljYXRlKSB7CiAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgaWYgKHByZWRpY2F0ZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSkpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEdldHMgdGhlIHNpemUgb2YgYW4gQVNDSUkgYHN0cmluZ2AuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzdHJpbmcgVGhlIHN0cmluZyBpbnNwZWN0LgogICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzdHJpbmcgc2l6ZS4KICAgICAgICovCiAgICAgIHZhciBhc2NpaVNpemUgPSBiYXNlUHJvcGVydHkoJ2xlbmd0aCcpOwoKICAgICAgLyoqCiAgICAgICAqIENvbnZlcnRzIGFuIEFTQ0lJIGBzdHJpbmdgIHRvIGFuIGFycmF5LgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBjb252ZXJ0ZWQgYXJyYXkuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBhc2NpaVRvQXJyYXkoc3RyaW5nKSB7CiAgICAgICAgcmV0dXJuIHN0cmluZy5zcGxpdCgnJyk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBTcGxpdHMgYW4gQVNDSUkgYHN0cmluZ2AgaW50byBhbiBhcnJheSBvZiBpdHMgd29yZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBUaGUgc3RyaW5nIHRvIGluc3BlY3QuCiAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgd29yZHMgb2YgYHN0cmluZ2AuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBhc2NpaVdvcmRzKHN0cmluZykgewogICAgICAgIHJldHVybiBzdHJpbmcubWF0Y2gocmVBc2NpaVdvcmQpIHx8IFtdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgbWV0aG9kcyBsaWtlIGBfLmZpbmRLZXlgIGFuZCBgXy5maW5kTGFzdEtleWAsCiAgICAgICAqIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcywgd2hpY2ggaXRlcmF0ZXMgb3ZlciBgY29sbGVjdGlvbmAKICAgICAgICogdXNpbmcgYGVhY2hGdW5jYC4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaW5zcGVjdC4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcHJlZGljYXRlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVhY2hGdW5jIFRoZSBmdW5jdGlvbiB0byBpdGVyYXRlIG92ZXIgYGNvbGxlY3Rpb25gLgogICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgZm91bmQgZWxlbWVudCBvciBpdHMga2V5LCBlbHNlIGB1bmRlZmluZWRgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZUZpbmRLZXkoY29sbGVjdGlvbiwgcHJlZGljYXRlLCBlYWNoRnVuYykgewogICAgICAgIHZhciByZXN1bHQ7CiAgICAgICAgZWFjaEZ1bmMoY29sbGVjdGlvbiwgZnVuY3Rpb24odmFsdWUsIGtleSwgY29sbGVjdGlvbikgewogICAgICAgICAgaWYgKHByZWRpY2F0ZSh2YWx1ZSwga2V5LCBjb2xsZWN0aW9uKSkgewogICAgICAgICAgICByZXN1bHQgPSBrZXk7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZmluZEluZGV4YCBhbmQgYF8uZmluZExhc3RJbmRleGAgd2l0aG91dAogICAgICAgKiBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcHJlZGljYXRlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBmcm9tSW5kZXggVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtmcm9tUmlnaHRdIFNwZWNpZnkgaXRlcmF0aW5nIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VGaW5kSW5kZXgoYXJyYXksIHByZWRpY2F0ZSwgZnJvbUluZGV4LCBmcm9tUmlnaHQpIHsKICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICBpbmRleCA9IGZyb21JbmRleCArIChmcm9tUmlnaHQgPyAxIDogLTEpOwoKICAgICAgICB3aGlsZSAoKGZyb21SaWdodCA/IGluZGV4LS0gOiArK2luZGV4IDwgbGVuZ3RoKSkgewogICAgICAgICAgaWYgKHByZWRpY2F0ZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSkpIHsKICAgICAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gLTE7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pbmRleE9mYCB3aXRob3V0IGBmcm9tSW5kZXhgIGJvdW5kcyBjaGVja3MuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICAgKiBAcGFyYW0ge251bWJlcn0gZnJvbUluZGV4IFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VJbmRleE9mKGFycmF5LCB2YWx1ZSwgZnJvbUluZGV4KSB7CiAgICAgICAgcmV0dXJuIHZhbHVlID09PSB2YWx1ZQogICAgICAgICAgPyBzdHJpY3RJbmRleE9mKGFycmF5LCB2YWx1ZSwgZnJvbUluZGV4KQogICAgICAgICAgOiBiYXNlRmluZEluZGV4KGFycmF5LCBiYXNlSXNOYU4sIGZyb21JbmRleCk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGxpa2UgYGJhc2VJbmRleE9mYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGEgY29tcGFyYXRvci4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBmcm9tSW5kZXggVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjb21wYXJhdG9yIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBtYXRjaGVkIHZhbHVlLCBlbHNlIGAtMWAuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBiYXNlSW5kZXhPZldpdGgoYXJyYXksIHZhbHVlLCBmcm9tSW5kZXgsIGNvbXBhcmF0b3IpIHsKICAgICAgICB2YXIgaW5kZXggPSBmcm9tSW5kZXggLSAxLAogICAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICBpZiAoY29tcGFyYXRvcihhcnJheVtpbmRleF0sIHZhbHVlKSkgewogICAgICAgICAgICByZXR1cm4gaW5kZXg7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiAtMTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmlzTmFOYCB3aXRob3V0IHN1cHBvcnQgZm9yIG51bWJlciBvYmplY3RzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYE5hTmAsIGVsc2UgYGZhbHNlYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VJc05hTih2YWx1ZSkgewogICAgICAgIHJldHVybiB2YWx1ZSAhPT0gdmFsdWU7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5tZWFuYCBhbmQgYF8ubWVhbkJ5YCB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgICAqIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIG1lYW4uCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBiYXNlTWVhbihhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgcmV0dXJuIGxlbmd0aCA/IChiYXNlU3VtKGFycmF5LCBpdGVyYXRlZSkgLyBsZW5ndGgpIDogTkFOOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ucHJvcGVydHlgIHdpdGhvdXQgc3VwcG9ydCBmb3IgZGVlcCBwYXRocy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFjY2Vzc29yIGZ1bmN0aW9uLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZVByb3BlcnR5KGtleSkgewogICAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IHVuZGVmaW5lZCQxIDogb2JqZWN0W2tleV07CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnByb3BlcnR5T2ZgIHdpdGhvdXQgc3VwcG9ydCBmb3IgZGVlcCBwYXRocy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBhY2Nlc3NvciBmdW5jdGlvbi4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VQcm9wZXJ0eU9mKG9iamVjdCkgewogICAgICAgIHJldHVybiBmdW5jdGlvbihrZXkpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IHVuZGVmaW5lZCQxIDogb2JqZWN0W2tleV07CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnJlZHVjZWAgYW5kIGBfLnJlZHVjZVJpZ2h0YCwgd2l0aG91dCBzdXBwb3J0CiAgICAgICAqIGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLCB3aGljaCBpdGVyYXRlcyBvdmVyIGBjb2xsZWN0aW9uYCB1c2luZyBgZWFjaEZ1bmNgLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAqIEBwYXJhbSB7Kn0gYWNjdW11bGF0b3IgVGhlIGluaXRpYWwgdmFsdWUuCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaW5pdEFjY3VtIFNwZWNpZnkgdXNpbmcgdGhlIGZpcnN0IG9yIGxhc3QgZWxlbWVudCBvZgogICAgICAgKiAgYGNvbGxlY3Rpb25gIGFzIHRoZSBpbml0aWFsIHZhbHVlLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBlYWNoRnVuYyBUaGUgZnVuY3Rpb24gdG8gaXRlcmF0ZSBvdmVyIGBjb2xsZWN0aW9uYC4KICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGFjY3VtdWxhdGVkIHZhbHVlLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZVJlZHVjZShjb2xsZWN0aW9uLCBpdGVyYXRlZSwgYWNjdW11bGF0b3IsIGluaXRBY2N1bSwgZWFjaEZ1bmMpIHsKICAgICAgICBlYWNoRnVuYyhjb2xsZWN0aW9uLCBmdW5jdGlvbih2YWx1ZSwgaW5kZXgsIGNvbGxlY3Rpb24pIHsKICAgICAgICAgIGFjY3VtdWxhdG9yID0gaW5pdEFjY3VtCiAgICAgICAgICAgID8gKGluaXRBY2N1bSA9IGZhbHNlLCB2YWx1ZSkKICAgICAgICAgICAgOiBpdGVyYXRlZShhY2N1bXVsYXRvciwgdmFsdWUsIGluZGV4LCBjb2xsZWN0aW9uKTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gYWNjdW11bGF0b3I7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5zb3J0QnlgIHdoaWNoIHVzZXMgYGNvbXBhcmVyYCB0byBkZWZpbmUgdGhlCiAgICAgICAqIHNvcnQgb3JkZXIgb2YgYGFycmF5YCBhbmQgcmVwbGFjZXMgY3JpdGVyaWEgb2JqZWN0cyB3aXRoIHRoZWlyIGNvcnJlc3BvbmRpbmcKICAgICAgICogdmFsdWVzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gc29ydC4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY29tcGFyZXIgVGhlIGZ1bmN0aW9uIHRvIGRlZmluZSBzb3J0IG9yZGVyLgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VTb3J0QnkoYXJyYXksIGNvbXBhcmVyKSB7CiAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKCiAgICAgICAgYXJyYXkuc29ydChjb21wYXJlcik7CiAgICAgICAgd2hpbGUgKGxlbmd0aC0tKSB7CiAgICAgICAgICBhcnJheVtsZW5ndGhdID0gYXJyYXlbbGVuZ3RoXS52YWx1ZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGFycmF5OwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc3VtYCBhbmQgYF8uc3VtQnlgIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAgICogaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgc3VtLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZVN1bShhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICB2YXIgcmVzdWx0LAogICAgICAgICAgICBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICB2YXIgY3VycmVudCA9IGl0ZXJhdGVlKGFycmF5W2luZGV4XSk7CiAgICAgICAgICBpZiAoY3VycmVudCAhPT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgcmVzdWx0ID0gcmVzdWx0ID09PSB1bmRlZmluZWQkMSA/IGN1cnJlbnQgOiAocmVzdWx0ICsgY3VycmVudCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy50aW1lc2Agd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzCiAgICAgICAqIG9yIG1heCBhcnJheSBsZW5ndGggY2hlY2tzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge251bWJlcn0gbiBUaGUgbnVtYmVyIG9mIHRpbWVzIHRvIGludm9rZSBgaXRlcmF0ZWVgLgogICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHJlc3VsdHMuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBiYXNlVGltZXMobiwgaXRlcmF0ZWUpIHsKICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgcmVzdWx0ID0gQXJyYXkobik7CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbikgewogICAgICAgICAgcmVzdWx0W2luZGV4XSA9IGl0ZXJhdGVlKGluZGV4KTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnRvUGFpcnNgIGFuZCBgXy50b1BhaXJzSW5gIHdoaWNoIGNyZWF0ZXMgYW4gYXJyYXkKICAgICAgICogb2Yga2V5LXZhbHVlIHBhaXJzIGZvciBgb2JqZWN0YCBjb3JyZXNwb25kaW5nIHRvIHRoZSBwcm9wZXJ0eSBuYW1lcyBvZiBgcHJvcHNgLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHByb3BzIFRoZSBwcm9wZXJ0eSBuYW1lcyB0byBnZXQgdmFsdWVzIGZvci4KICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUga2V5LXZhbHVlIHBhaXJzLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZVRvUGFpcnMob2JqZWN0LCBwcm9wcykgewogICAgICAgIHJldHVybiBhcnJheU1hcChwcm9wcywgZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgICByZXR1cm4gW2tleSwgb2JqZWN0W2tleV1dOwogICAgICAgIH0pOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8udW5hcnlgIHdpdGhvdXQgc3VwcG9ydCBmb3Igc3RvcmluZyBtZXRhZGF0YS4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gY2FwIGFyZ3VtZW50cyBmb3IuCiAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGNhcHBlZCBmdW5jdGlvbi4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGJhc2VVbmFyeShmdW5jKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gZnVuYyh2YWx1ZSk7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnZhbHVlc2AgYW5kIGBfLnZhbHVlc0luYCB3aGljaCBjcmVhdGVzIGFuCiAgICAgICAqIGFycmF5IG9mIGBvYmplY3RgIHByb3BlcnR5IHZhbHVlcyBjb3JyZXNwb25kaW5nIHRvIHRoZSBwcm9wZXJ0eSBuYW1lcwogICAgICAgKiBvZiBgcHJvcHNgLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHByb3BzIFRoZSBwcm9wZXJ0eSBuYW1lcyB0byBnZXQgdmFsdWVzIGZvci4KICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgdmFsdWVzLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gYmFzZVZhbHVlcyhvYmplY3QsIHByb3BzKSB7CiAgICAgICAgcmV0dXJuIGFycmF5TWFwKHByb3BzLCBmdW5jdGlvbihrZXkpIHsKICAgICAgICAgIHJldHVybiBvYmplY3Rba2V5XTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIENoZWNrcyBpZiBhIGBjYWNoZWAgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtPYmplY3R9IGNhY2hlIFRoZSBjYWNoZSB0byBxdWVyeS4KICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBlbnRyeSB0byBjaGVjay4KICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGFuIGVudHJ5IGZvciBga2V5YCBleGlzdHMsIGVsc2UgYGZhbHNlYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGNhY2hlSGFzKGNhY2hlLCBrZXkpIHsKICAgICAgICByZXR1cm4gY2FjaGUuaGFzKGtleSk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBVc2VkIGJ5IGBfLnRyaW1gIGFuZCBgXy50cmltU3RhcnRgIHRvIGdldCB0aGUgaW5kZXggb2YgdGhlIGZpcnN0IHN0cmluZyBzeW1ib2wKICAgICAgICogdGhhdCBpcyBub3QgZm91bmQgaW4gdGhlIGNoYXJhY3RlciBzeW1ib2xzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBzdHJTeW1ib2xzIFRoZSBzdHJpbmcgc3ltYm9scyB0byBpbnNwZWN0LgogICAgICAgKiBAcGFyYW0ge0FycmF5fSBjaHJTeW1ib2xzIFRoZSBjaGFyYWN0ZXIgc3ltYm9scyB0byBmaW5kLgogICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgZmlyc3QgdW5tYXRjaGVkIHN0cmluZyBzeW1ib2wuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBjaGFyc1N0YXJ0SW5kZXgoc3RyU3ltYm9scywgY2hyU3ltYm9scykgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBzdHJTeW1ib2xzLmxlbmd0aDsKCiAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGggJiYgYmFzZUluZGV4T2YoY2hyU3ltYm9scywgc3RyU3ltYm9sc1tpbmRleF0sIDApID4gLTEpIHt9CiAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICB9CgogICAgICAvKioKICAgICAgICogVXNlZCBieSBgXy50cmltYCBhbmQgYF8udHJpbUVuZGAgdG8gZ2V0IHRoZSBpbmRleCBvZiB0aGUgbGFzdCBzdHJpbmcgc3ltYm9sCiAgICAgICAqIHRoYXQgaXMgbm90IGZvdW5kIGluIHRoZSBjaGFyYWN0ZXIgc3ltYm9scy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gc3RyU3ltYm9scyBUaGUgc3RyaW5nIHN5bWJvbHMgdG8gaW5zcGVjdC4KICAgICAgICogQHBhcmFtIHtBcnJheX0gY2hyU3ltYm9scyBUaGUgY2hhcmFjdGVyIHN5bWJvbHMgdG8gZmluZC4KICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIGxhc3QgdW5tYXRjaGVkIHN0cmluZyBzeW1ib2wuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBjaGFyc0VuZEluZGV4KHN0clN5bWJvbHMsIGNoclN5bWJvbHMpIHsKICAgICAgICB2YXIgaW5kZXggPSBzdHJTeW1ib2xzLmxlbmd0aDsKCiAgICAgICAgd2hpbGUgKGluZGV4LS0gJiYgYmFzZUluZGV4T2YoY2hyU3ltYm9scywgc3RyU3ltYm9sc1tpbmRleF0sIDApID4gLTEpIHt9CiAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICB9CgogICAgICAvKioKICAgICAgICogR2V0cyB0aGUgbnVtYmVyIG9mIGBwbGFjZWhvbGRlcmAgb2NjdXJyZW5jZXMgaW4gYGFycmF5YC4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAqIEBwYXJhbSB7Kn0gcGxhY2Vob2xkZXIgVGhlIHBsYWNlaG9sZGVyIHRvIHNlYXJjaCBmb3IuCiAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHBsYWNlaG9sZGVyIGNvdW50LgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gY291bnRIb2xkZXJzKGFycmF5LCBwbGFjZWhvbGRlcikgewogICAgICAgIHZhciBsZW5ndGggPSBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgIHJlc3VsdCA9IDA7CgogICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgaWYgKGFycmF5W2xlbmd0aF0gPT09IHBsYWNlaG9sZGVyKSB7CiAgICAgICAgICAgICsrcmVzdWx0OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogVXNlZCBieSBgXy5kZWJ1cnJgIHRvIGNvbnZlcnQgTGF0aW4tMSBTdXBwbGVtZW50IGFuZCBMYXRpbiBFeHRlbmRlZC1BCiAgICAgICAqIGxldHRlcnMgdG8gYmFzaWMgTGF0aW4gbGV0dGVycy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGxldHRlciBUaGUgbWF0Y2hlZCBsZXR0ZXIgdG8gZGVidXJyLgogICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBkZWJ1cnJlZCBsZXR0ZXIuCiAgICAgICAqLwogICAgICB2YXIgZGVidXJyTGV0dGVyID0gYmFzZVByb3BlcnR5T2YoZGVidXJyZWRMZXR0ZXJzKTsKCiAgICAgIC8qKgogICAgICAgKiBVc2VkIGJ5IGBfLmVzY2FwZWAgdG8gY29udmVydCBjaGFyYWN0ZXJzIHRvIEhUTUwgZW50aXRpZXMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjaHIgVGhlIG1hdGNoZWQgY2hhcmFjdGVyIHRvIGVzY2FwZS4KICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgZXNjYXBlZCBjaGFyYWN0ZXIuCiAgICAgICAqLwogICAgICB2YXIgZXNjYXBlSHRtbENoYXIgPSBiYXNlUHJvcGVydHlPZihodG1sRXNjYXBlcyk7CgogICAgICAvKioKICAgICAgICogVXNlZCBieSBgXy50ZW1wbGF0ZWAgdG8gZXNjYXBlIGNoYXJhY3RlcnMgZm9yIGluY2x1c2lvbiBpbiBjb21waWxlZCBzdHJpbmcgbGl0ZXJhbHMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjaHIgVGhlIG1hdGNoZWQgY2hhcmFjdGVyIHRvIGVzY2FwZS4KICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgZXNjYXBlZCBjaGFyYWN0ZXIuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBlc2NhcGVTdHJpbmdDaGFyKGNocikgewogICAgICAgIHJldHVybiAnXFwnICsgc3RyaW5nRXNjYXBlc1tjaHJdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogR2V0cyB0aGUgdmFsdWUgYXQgYGtleWAgb2YgYG9iamVjdGAuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0XSBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHByb3BlcnR5IHZhbHVlLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gZ2V0VmFsdWUob2JqZWN0LCBrZXkpIHsKICAgICAgICByZXR1cm4gb2JqZWN0ID09IG51bGwgPyB1bmRlZmluZWQkMSA6IG9iamVjdFtrZXldOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ2hlY2tzIGlmIGBzdHJpbmdgIGNvbnRhaW5zIFVuaWNvZGUgc3ltYm9scy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIHRvIGluc3BlY3QuCiAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhIHN5bWJvbCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gaGFzVW5pY29kZShzdHJpbmcpIHsKICAgICAgICByZXR1cm4gcmVIYXNVbmljb2RlLnRlc3Qoc3RyaW5nKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIENoZWNrcyBpZiBgc3RyaW5nYCBjb250YWlucyBhIHdvcmQgY29tcG9zZWQgb2YgVW5pY29kZSBzeW1ib2xzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgdG8gaW5zcGVjdC4KICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGEgd29yZCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gaGFzVW5pY29kZVdvcmQoc3RyaW5nKSB7CiAgICAgICAgcmV0dXJuIHJlSGFzVW5pY29kZVdvcmQudGVzdChzdHJpbmcpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ29udmVydHMgYGl0ZXJhdG9yYCB0byBhbiBhcnJheS4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZXJhdG9yIFRoZSBpdGVyYXRvciB0byBjb252ZXJ0LgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBhcnJheS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIGl0ZXJhdG9yVG9BcnJheShpdGVyYXRvcikgewogICAgICAgIHZhciBkYXRhLAogICAgICAgICAgICByZXN1bHQgPSBbXTsKCiAgICAgICAgd2hpbGUgKCEoZGF0YSA9IGl0ZXJhdG9yLm5leHQoKSkuZG9uZSkgewogICAgICAgICAgcmVzdWx0LnB1c2goZGF0YS52YWx1ZSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBDb252ZXJ0cyBgbWFwYCB0byBpdHMga2V5LXZhbHVlIHBhaXJzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge09iamVjdH0gbWFwIFRoZSBtYXAgdG8gY29udmVydC4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBrZXktdmFsdWUgcGFpcnMuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBtYXBUb0FycmF5KG1hcCkgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICByZXN1bHQgPSBBcnJheShtYXAuc2l6ZSk7CgogICAgICAgIG1hcC5mb3JFYWNoKGZ1bmN0aW9uKHZhbHVlLCBrZXkpIHsKICAgICAgICAgIHJlc3VsdFsrK2luZGV4XSA9IFtrZXksIHZhbHVlXTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ3JlYXRlcyBhIHVuYXJ5IGZ1bmN0aW9uIHRoYXQgaW52b2tlcyBgZnVuY2Agd2l0aCBpdHMgYXJndW1lbnQgdHJhbnNmb3JtZWQuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHdyYXAuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHRyYW5zZm9ybSBUaGUgYXJndW1lbnQgdHJhbnNmb3JtLgogICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIG92ZXJBcmcoZnVuYywgdHJhbnNmb3JtKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKGFyZykgewogICAgICAgICAgcmV0dXJuIGZ1bmModHJhbnNmb3JtKGFyZykpOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXBsYWNlcyBhbGwgYHBsYWNlaG9sZGVyYCBlbGVtZW50cyBpbiBgYXJyYXlgIHdpdGggYW4gaW50ZXJuYWwgcGxhY2Vob2xkZXIKICAgICAgICogYW5kIHJldHVybnMgYW4gYXJyYXkgb2YgdGhlaXIgaW5kZXhlcy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIG1vZGlmeS4KICAgICAgICogQHBhcmFtIHsqfSBwbGFjZWhvbGRlciBUaGUgcGxhY2Vob2xkZXIgdG8gcmVwbGFjZS4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgcGxhY2Vob2xkZXIgaW5kZXhlcy4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHJlcGxhY2VIb2xkZXJzKGFycmF5LCBwbGFjZWhvbGRlcikgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgIHJlc0luZGV4ID0gMCwKICAgICAgICAgICAgcmVzdWx0ID0gW107CgogICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF07CiAgICAgICAgICBpZiAodmFsdWUgPT09IHBsYWNlaG9sZGVyIHx8IHZhbHVlID09PSBQTEFDRUhPTERFUikgewogICAgICAgICAgICBhcnJheVtpbmRleF0gPSBQTEFDRUhPTERFUjsKICAgICAgICAgICAgcmVzdWx0W3Jlc0luZGV4KytdID0gaW5kZXg7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBDb252ZXJ0cyBgc2V0YCB0byBhbiBhcnJheSBvZiBpdHMgdmFsdWVzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge09iamVjdH0gc2V0IFRoZSBzZXQgdG8gY29udmVydC4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSB2YWx1ZXMuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBzZXRUb0FycmF5KHNldCkgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICByZXN1bHQgPSBBcnJheShzZXQuc2l6ZSk7CgogICAgICAgIHNldC5mb3JFYWNoKGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICByZXN1bHRbKytpbmRleF0gPSB2YWx1ZTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ29udmVydHMgYHNldGAgdG8gaXRzIHZhbHVlLXZhbHVlIHBhaXJzLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge09iamVjdH0gc2V0IFRoZSBzZXQgdG8gY29udmVydC4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSB2YWx1ZS12YWx1ZSBwYWlycy4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHNldFRvUGFpcnMoc2V0KSB7CiAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgIHJlc3VsdCA9IEFycmF5KHNldC5zaXplKTsKCiAgICAgICAgc2V0LmZvckVhY2goZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIHJlc3VsdFsrK2luZGV4XSA9IFt2YWx1ZSwgdmFsdWVdOwogICAgICAgIH0pOwogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uaW5kZXhPZmAgd2hpY2ggcGVyZm9ybXMgc3RyaWN0IGVxdWFsaXR5CiAgICAgICAqIGNvbXBhcmlzb25zIG9mIHZhbHVlcywgaS5lLiBgPT09YC4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBmcm9tSW5kZXggVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgbWF0Y2hlZCB2YWx1ZSwgZWxzZSBgLTFgLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gc3RyaWN0SW5kZXhPZihhcnJheSwgdmFsdWUsIGZyb21JbmRleCkgewogICAgICAgIHZhciBpbmRleCA9IGZyb21JbmRleCAtIDEsCiAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKCiAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgIGlmIChhcnJheVtpbmRleF0gPT09IHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiBpbmRleDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIC0xOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLmxhc3RJbmRleE9mYCB3aGljaCBwZXJmb3JtcyBzdHJpY3QgZXF1YWxpdHkKICAgICAgICogY29tcGFyaXNvbnMgb2YgdmFsdWVzLCBpLmUuIGA9PT1gLgogICAgICAgKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2VhcmNoIGZvci4KICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGZyb21JbmRleCBUaGUgaW5kZXggdG8gc2VhcmNoIGZyb20uCiAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBtYXRjaGVkIHZhbHVlLCBlbHNlIGAtMWAuCiAgICAgICAqLwogICAgICBmdW5jdGlvbiBzdHJpY3RMYXN0SW5kZXhPZihhcnJheSwgdmFsdWUsIGZyb21JbmRleCkgewogICAgICAgIHZhciBpbmRleCA9IGZyb21JbmRleCArIDE7CiAgICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICAgIGlmIChhcnJheVtpbmRleF0gPT09IHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiBpbmRleDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICB9CgogICAgICAvKioKICAgICAgICogR2V0cyB0aGUgbnVtYmVyIG9mIHN5bWJvbHMgaW4gYHN0cmluZ2AuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzdHJpbmcgVGhlIHN0cmluZyB0byBpbnNwZWN0LgogICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzdHJpbmcgc2l6ZS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHN0cmluZ1NpemUoc3RyaW5nKSB7CiAgICAgICAgcmV0dXJuIGhhc1VuaWNvZGUoc3RyaW5nKQogICAgICAgICAgPyB1bmljb2RlU2l6ZShzdHJpbmcpCiAgICAgICAgICA6IGFzY2lpU2l6ZShzdHJpbmcpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ29udmVydHMgYHN0cmluZ2AgdG8gYW4gYXJyYXkuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzdHJpbmcgVGhlIHN0cmluZyB0byBjb252ZXJ0LgogICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBhcnJheS4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHN0cmluZ1RvQXJyYXkoc3RyaW5nKSB7CiAgICAgICAgcmV0dXJuIGhhc1VuaWNvZGUoc3RyaW5nKQogICAgICAgICAgPyB1bmljb2RlVG9BcnJheShzdHJpbmcpCiAgICAgICAgICA6IGFzY2lpVG9BcnJheShzdHJpbmcpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVXNlZCBieSBgXy51bmVzY2FwZWAgdG8gY29udmVydCBIVE1MIGVudGl0aWVzIHRvIGNoYXJhY3RlcnMuCiAgICAgICAqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjaHIgVGhlIG1hdGNoZWQgY2hhcmFjdGVyIHRvIHVuZXNjYXBlLgogICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSB1bmVzY2FwZWQgY2hhcmFjdGVyLgogICAgICAgKi8KICAgICAgdmFyIHVuZXNjYXBlSHRtbENoYXIgPSBiYXNlUHJvcGVydHlPZihodG1sVW5lc2NhcGVzKTsKCiAgICAgIC8qKgogICAgICAgKiBHZXRzIHRoZSBzaXplIG9mIGEgVW5pY29kZSBgc3RyaW5nYC4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIGluc3BlY3QuCiAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHN0cmluZyBzaXplLgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gdW5pY29kZVNpemUoc3RyaW5nKSB7CiAgICAgICAgdmFyIHJlc3VsdCA9IHJlVW5pY29kZS5sYXN0SW5kZXggPSAwOwogICAgICAgIHdoaWxlIChyZVVuaWNvZGUudGVzdChzdHJpbmcpKSB7CiAgICAgICAgICArK3Jlc3VsdDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIENvbnZlcnRzIGEgVW5pY29kZSBgc3RyaW5nYCB0byBhbiBhcnJheS4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgY29udmVydGVkIGFycmF5LgogICAgICAgKi8KICAgICAgZnVuY3Rpb24gdW5pY29kZVRvQXJyYXkoc3RyaW5nKSB7CiAgICAgICAgcmV0dXJuIHN0cmluZy5tYXRjaChyZVVuaWNvZGUpIHx8IFtdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogU3BsaXRzIGEgVW5pY29kZSBgc3RyaW5nYCBpbnRvIGFuIGFycmF5IG9mIGl0cyB3b3Jkcy4KICAgICAgICoKICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFRoZSBzdHJpbmcgdG8gaW5zcGVjdC4KICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSB3b3JkcyBvZiBgc3RyaW5nYC4KICAgICAgICovCiAgICAgIGZ1bmN0aW9uIHVuaWNvZGVXb3JkcyhzdHJpbmcpIHsKICAgICAgICByZXR1cm4gc3RyaW5nLm1hdGNoKHJlVW5pY29kZVdvcmQpIHx8IFtdOwogICAgICB9CgogICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgIC8qKgogICAgICAgKiBDcmVhdGUgYSBuZXcgcHJpc3RpbmUgYGxvZGFzaGAgZnVuY3Rpb24gdXNpbmcgdGhlIGBjb250ZXh0YCBvYmplY3QuCiAgICAgICAqCiAgICAgICAqIEBzdGF0aWMKICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICogQHNpbmNlIDEuMS4wCiAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbY29udGV4dD1yb290XSBUaGUgY29udGV4dCBvYmplY3QuCiAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyBhIG5ldyBgbG9kYXNoYCBmdW5jdGlvbi4KICAgICAgICogQGV4YW1wbGUKICAgICAgICoKICAgICAgICogXy5taXhpbih7ICdmb28nOiBfLmNvbnN0YW50KCdmb28nKSB9KTsKICAgICAgICoKICAgICAgICogdmFyIGxvZGFzaCA9IF8ucnVuSW5Db250ZXh0KCk7CiAgICAgICAqIGxvZGFzaC5taXhpbih7ICdiYXInOiBsb2Rhc2guY29uc3RhbnQoJ2JhcicpIH0pOwogICAgICAgKgogICAgICAgKiBfLmlzRnVuY3Rpb24oXy5mb28pOwogICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAqIF8uaXNGdW5jdGlvbihfLmJhcik7CiAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAqCiAgICAgICAqIGxvZGFzaC5pc0Z1bmN0aW9uKGxvZGFzaC5mb28pOwogICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgKiBsb2Rhc2guaXNGdW5jdGlvbihsb2Rhc2guYmFyKTsKICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgKgogICAgICAgKiAvLyBDcmVhdGUgYSBzdXBlZC11cCBgZGVmZXJgIGluIE5vZGUuanMuCiAgICAgICAqIHZhciBkZWZlciA9IF8ucnVuSW5Db250ZXh0KHsgJ3NldFRpbWVvdXQnOiBzZXRJbW1lZGlhdGUgfSkuZGVmZXI7CiAgICAgICAqLwogICAgICB2YXIgcnVuSW5Db250ZXh0ID0gKGZ1bmN0aW9uIHJ1bkluQ29udGV4dChjb250ZXh0KSB7CiAgICAgICAgY29udGV4dCA9IGNvbnRleHQgPT0gbnVsbCA/IHJvb3QgOiBfLmRlZmF1bHRzKHJvb3QuT2JqZWN0KCksIGNvbnRleHQsIF8ucGljayhyb290LCBjb250ZXh0UHJvcHMpKTsKCiAgICAgICAgLyoqIEJ1aWx0LWluIGNvbnN0cnVjdG9yIHJlZmVyZW5jZXMuICovCiAgICAgICAgdmFyIEFycmF5ID0gY29udGV4dC5BcnJheSwKICAgICAgICAgICAgRGF0ZSA9IGNvbnRleHQuRGF0ZSwKICAgICAgICAgICAgRXJyb3IgPSBjb250ZXh0LkVycm9yLAogICAgICAgICAgICBGdW5jdGlvbiA9IGNvbnRleHQuRnVuY3Rpb24sCiAgICAgICAgICAgIE1hdGggPSBjb250ZXh0Lk1hdGgsCiAgICAgICAgICAgIE9iamVjdCA9IGNvbnRleHQuT2JqZWN0LAogICAgICAgICAgICBSZWdFeHAgPSBjb250ZXh0LlJlZ0V4cCwKICAgICAgICAgICAgU3RyaW5nID0gY29udGV4dC5TdHJpbmcsCiAgICAgICAgICAgIFR5cGVFcnJvciA9IGNvbnRleHQuVHlwZUVycm9yOwoKICAgICAgICAvKiogVXNlZCBmb3IgYnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMuICovCiAgICAgICAgdmFyIGFycmF5UHJvdG8gPSBBcnJheS5wcm90b3R5cGUsCiAgICAgICAgICAgIGZ1bmNQcm90byA9IEZ1bmN0aW9uLnByb3RvdHlwZSwKICAgICAgICAgICAgb2JqZWN0UHJvdG8gPSBPYmplY3QucHJvdG90eXBlOwoKICAgICAgICAvKiogVXNlZCB0byBkZXRlY3Qgb3ZlcnJlYWNoaW5nIGNvcmUtanMgc2hpbXMuICovCiAgICAgICAgdmFyIGNvcmVKc0RhdGEgPSBjb250ZXh0WydfX2NvcmUtanNfc2hhcmVkX18nXTsKCiAgICAgICAgLyoqIFVzZWQgdG8gcmVzb2x2ZSB0aGUgZGVjb21waWxlZCBzb3VyY2Ugb2YgZnVuY3Rpb25zLiAqLwogICAgICAgIHZhciBmdW5jVG9TdHJpbmcgPSBmdW5jUHJvdG8udG9TdHJpbmc7CgogICAgICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgICAgIHZhciBoYXNPd25Qcm9wZXJ0eSA9IG9iamVjdFByb3RvLmhhc093blByb3BlcnR5OwoKICAgICAgICAvKiogVXNlZCB0byBnZW5lcmF0ZSB1bmlxdWUgSURzLiAqLwogICAgICAgIHZhciBpZENvdW50ZXIgPSAwOwoKICAgICAgICAvKiogVXNlZCB0byBkZXRlY3QgbWV0aG9kcyBtYXNxdWVyYWRpbmcgYXMgbmF0aXZlLiAqLwogICAgICAgIHZhciBtYXNrU3JjS2V5ID0gKGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIHVpZCA9IC9bXi5dKyQvLmV4ZWMoY29yZUpzRGF0YSAmJiBjb3JlSnNEYXRhLmtleXMgJiYgY29yZUpzRGF0YS5rZXlzLklFX1BST1RPIHx8ICcnKTsKICAgICAgICAgIHJldHVybiB1aWQgPyAoJ1N5bWJvbChzcmMpXzEuJyArIHVpZCkgOiAnJzsKICAgICAgICB9KCkpOwoKICAgICAgICAvKioKICAgICAgICAgKiBVc2VkIHRvIHJlc29sdmUgdGhlCiAgICAgICAgICogW2B0b1N0cmluZ1RhZ2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLW9iamVjdC5wcm90b3R5cGUudG9zdHJpbmcpCiAgICAgICAgICogb2YgdmFsdWVzLgogICAgICAgICAqLwogICAgICAgIHZhciBuYXRpdmVPYmplY3RUb1N0cmluZyA9IG9iamVjdFByb3RvLnRvU3RyaW5nOwoKICAgICAgICAvKiogVXNlZCB0byBpbmZlciB0aGUgYE9iamVjdGAgY29uc3RydWN0b3IuICovCiAgICAgICAgdmFyIG9iamVjdEN0b3JTdHJpbmcgPSBmdW5jVG9TdHJpbmcuY2FsbChPYmplY3QpOwoKICAgICAgICAvKiogVXNlZCB0byByZXN0b3JlIHRoZSBvcmlnaW5hbCBgX2AgcmVmZXJlbmNlIGluIGBfLm5vQ29uZmxpY3RgLiAqLwogICAgICAgIHZhciBvbGREYXNoID0gcm9vdC5fOwoKICAgICAgICAvKiogVXNlZCB0byBkZXRlY3QgaWYgYSBtZXRob2QgaXMgbmF0aXZlLiAqLwogICAgICAgIHZhciByZUlzTmF0aXZlID0gUmVnRXhwKCdeJyArCiAgICAgICAgICBmdW5jVG9TdHJpbmcuY2FsbChoYXNPd25Qcm9wZXJ0eSkucmVwbGFjZShyZVJlZ0V4cENoYXIsICdcXCQmJykKICAgICAgICAgIC5yZXBsYWNlKC9oYXNPd25Qcm9wZXJ0eXwoZnVuY3Rpb24pLio/KD89XFxcKCl8IGZvciAuKz8oPz1cXFxdKS9nLCAnJDEuKj8nKSArICckJwogICAgICAgICk7CgogICAgICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgICAgIHZhciBCdWZmZXIgPSBtb2R1bGVFeHBvcnRzID8gY29udGV4dC5CdWZmZXIgOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgU3ltYm9sID0gY29udGV4dC5TeW1ib2wsCiAgICAgICAgICAgIFVpbnQ4QXJyYXkgPSBjb250ZXh0LlVpbnQ4QXJyYXksCiAgICAgICAgICAgIGFsbG9jVW5zYWZlID0gQnVmZmVyID8gQnVmZmVyLmFsbG9jVW5zYWZlIDogdW5kZWZpbmVkJDEsCiAgICAgICAgICAgIGdldFByb3RvdHlwZSA9IG92ZXJBcmcoT2JqZWN0LmdldFByb3RvdHlwZU9mLCBPYmplY3QpLAogICAgICAgICAgICBvYmplY3RDcmVhdGUgPSBPYmplY3QuY3JlYXRlLAogICAgICAgICAgICBwcm9wZXJ0eUlzRW51bWVyYWJsZSA9IG9iamVjdFByb3RvLnByb3BlcnR5SXNFbnVtZXJhYmxlLAogICAgICAgICAgICBzcGxpY2UgPSBhcnJheVByb3RvLnNwbGljZSwKICAgICAgICAgICAgc3ByZWFkYWJsZVN5bWJvbCA9IFN5bWJvbCA/IFN5bWJvbC5pc0NvbmNhdFNwcmVhZGFibGUgOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgc3ltSXRlcmF0b3IgPSBTeW1ib2wgPyBTeW1ib2wuaXRlcmF0b3IgOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgc3ltVG9TdHJpbmdUYWcgPSBTeW1ib2wgPyBTeW1ib2wudG9TdHJpbmdUYWcgOiB1bmRlZmluZWQkMTsKCiAgICAgICAgdmFyIGRlZmluZVByb3BlcnR5ID0gKGZ1bmN0aW9uKCkgewogICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgdmFyIGZ1bmMgPSBnZXROYXRpdmUoT2JqZWN0LCAnZGVmaW5lUHJvcGVydHknKTsKICAgICAgICAgICAgZnVuYyh7fSwgJycsIHt9KTsKICAgICAgICAgICAgcmV0dXJuIGZ1bmM7CiAgICAgICAgICB9IGNhdGNoIChlKSB7fQogICAgICAgIH0oKSk7CgogICAgICAgIC8qKiBNb2NrZWQgYnVpbHQtaW5zLiAqLwogICAgICAgIHZhciBjdHhDbGVhclRpbWVvdXQgPSBjb250ZXh0LmNsZWFyVGltZW91dCAhPT0gcm9vdC5jbGVhclRpbWVvdXQgJiYgY29udGV4dC5jbGVhclRpbWVvdXQsCiAgICAgICAgICAgIGN0eE5vdyA9IERhdGUgJiYgRGF0ZS5ub3cgIT09IHJvb3QuRGF0ZS5ub3cgJiYgRGF0ZS5ub3csCiAgICAgICAgICAgIGN0eFNldFRpbWVvdXQgPSBjb250ZXh0LnNldFRpbWVvdXQgIT09IHJvb3Quc2V0VGltZW91dCAmJiBjb250ZXh0LnNldFRpbWVvdXQ7CgogICAgICAgIC8qIEJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzIGZvciB0aG9zZSB3aXRoIHRoZSBzYW1lIG5hbWUgYXMgb3RoZXIgYGxvZGFzaGAgbWV0aG9kcy4gKi8KICAgICAgICB2YXIgbmF0aXZlQ2VpbCA9IE1hdGguY2VpbCwKICAgICAgICAgICAgbmF0aXZlRmxvb3IgPSBNYXRoLmZsb29yLAogICAgICAgICAgICBuYXRpdmVHZXRTeW1ib2xzID0gT2JqZWN0LmdldE93blByb3BlcnR5U3ltYm9scywKICAgICAgICAgICAgbmF0aXZlSXNCdWZmZXIgPSBCdWZmZXIgPyBCdWZmZXIuaXNCdWZmZXIgOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgbmF0aXZlSXNGaW5pdGUgPSBjb250ZXh0LmlzRmluaXRlLAogICAgICAgICAgICBuYXRpdmVKb2luID0gYXJyYXlQcm90by5qb2luLAogICAgICAgICAgICBuYXRpdmVLZXlzID0gb3ZlckFyZyhPYmplY3Qua2V5cywgT2JqZWN0KSwKICAgICAgICAgICAgbmF0aXZlTWF4ID0gTWF0aC5tYXgsCiAgICAgICAgICAgIG5hdGl2ZU1pbiA9IE1hdGgubWluLAogICAgICAgICAgICBuYXRpdmVOb3cgPSBEYXRlLm5vdywKICAgICAgICAgICAgbmF0aXZlUGFyc2VJbnQgPSBjb250ZXh0LnBhcnNlSW50LAogICAgICAgICAgICBuYXRpdmVSYW5kb20gPSBNYXRoLnJhbmRvbSwKICAgICAgICAgICAgbmF0aXZlUmV2ZXJzZSA9IGFycmF5UHJvdG8ucmV2ZXJzZTsKCiAgICAgICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgdGhhdCBhcmUgdmVyaWZpZWQgdG8gYmUgbmF0aXZlLiAqLwogICAgICAgIHZhciBEYXRhVmlldyA9IGdldE5hdGl2ZShjb250ZXh0LCAnRGF0YVZpZXcnKSwKICAgICAgICAgICAgTWFwID0gZ2V0TmF0aXZlKGNvbnRleHQsICdNYXAnKSwKICAgICAgICAgICAgUHJvbWlzZSA9IGdldE5hdGl2ZShjb250ZXh0LCAnUHJvbWlzZScpLAogICAgICAgICAgICBTZXQgPSBnZXROYXRpdmUoY29udGV4dCwgJ1NldCcpLAogICAgICAgICAgICBXZWFrTWFwID0gZ2V0TmF0aXZlKGNvbnRleHQsICdXZWFrTWFwJyksCiAgICAgICAgICAgIG5hdGl2ZUNyZWF0ZSA9IGdldE5hdGl2ZShPYmplY3QsICdjcmVhdGUnKTsKCiAgICAgICAgLyoqIFVzZWQgdG8gc3RvcmUgZnVuY3Rpb24gbWV0YWRhdGEuICovCiAgICAgICAgdmFyIG1ldGFNYXAgPSBXZWFrTWFwICYmIG5ldyBXZWFrTWFwOwoKICAgICAgICAvKiogVXNlZCB0byBsb29rdXAgdW5taW5pZmllZCBmdW5jdGlvbiBuYW1lcy4gKi8KICAgICAgICB2YXIgcmVhbE5hbWVzID0ge307CgogICAgICAgIC8qKiBVc2VkIHRvIGRldGVjdCBtYXBzLCBzZXRzLCBhbmQgd2Vha21hcHMuICovCiAgICAgICAgdmFyIGRhdGFWaWV3Q3RvclN0cmluZyA9IHRvU291cmNlKERhdGFWaWV3KSwKICAgICAgICAgICAgbWFwQ3RvclN0cmluZyA9IHRvU291cmNlKE1hcCksCiAgICAgICAgICAgIHByb21pc2VDdG9yU3RyaW5nID0gdG9Tb3VyY2UoUHJvbWlzZSksCiAgICAgICAgICAgIHNldEN0b3JTdHJpbmcgPSB0b1NvdXJjZShTZXQpLAogICAgICAgICAgICB3ZWFrTWFwQ3RvclN0cmluZyA9IHRvU291cmNlKFdlYWtNYXApOwoKICAgICAgICAvKiogVXNlZCB0byBjb252ZXJ0IHN5bWJvbHMgdG8gcHJpbWl0aXZlcyBhbmQgc3RyaW5ncy4gKi8KICAgICAgICB2YXIgc3ltYm9sUHJvdG8gPSBTeW1ib2wgPyBTeW1ib2wucHJvdG90eXBlIDogdW5kZWZpbmVkJDEsCiAgICAgICAgICAgIHN5bWJvbFZhbHVlT2YgPSBzeW1ib2xQcm90byA/IHN5bWJvbFByb3RvLnZhbHVlT2YgOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgc3ltYm9sVG9TdHJpbmcgPSBzeW1ib2xQcm90byA/IHN5bWJvbFByb3RvLnRvU3RyaW5nIDogdW5kZWZpbmVkJDE7CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGBsb2Rhc2hgIG9iamVjdCB3aGljaCB3cmFwcyBgdmFsdWVgIHRvIGVuYWJsZSBpbXBsaWNpdCBtZXRob2QKICAgICAgICAgKiBjaGFpbiBzZXF1ZW5jZXMuIE1ldGhvZHMgdGhhdCBvcGVyYXRlIG9uIGFuZCByZXR1cm4gYXJyYXlzLCBjb2xsZWN0aW9ucywKICAgICAgICAgKiBhbmQgZnVuY3Rpb25zIGNhbiBiZSBjaGFpbmVkIHRvZ2V0aGVyLiBNZXRob2RzIHRoYXQgcmV0cmlldmUgYSBzaW5nbGUgdmFsdWUKICAgICAgICAgKiBvciBtYXkgcmV0dXJuIGEgcHJpbWl0aXZlIHZhbHVlIHdpbGwgYXV0b21hdGljYWxseSBlbmQgdGhlIGNoYWluIHNlcXVlbmNlCiAgICAgICAgICogYW5kIHJldHVybiB0aGUgdW53cmFwcGVkIHZhbHVlLiBPdGhlcndpc2UsIHRoZSB2YWx1ZSBtdXN0IGJlIHVud3JhcHBlZAogICAgICAgICAqIHdpdGggYF8jdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogRXhwbGljaXQgY2hhaW4gc2VxdWVuY2VzLCB3aGljaCBtdXN0IGJlIHVud3JhcHBlZCB3aXRoIGBfI3ZhbHVlYCwgbWF5IGJlCiAgICAgICAgICogZW5hYmxlZCB1c2luZyBgXy5jaGFpbmAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZXhlY3V0aW9uIG9mIGNoYWluZWQgbWV0aG9kcyBpcyBsYXp5LCB0aGF0IGlzLCBpdCdzIGRlZmVycmVkIHVudGlsCiAgICAgICAgICogYF8jdmFsdWVgIGlzIGltcGxpY2l0bHkgb3IgZXhwbGljaXRseSBjYWxsZWQuCiAgICAgICAgICoKICAgICAgICAgKiBMYXp5IGV2YWx1YXRpb24gYWxsb3dzIHNldmVyYWwgbWV0aG9kcyB0byBzdXBwb3J0IHNob3J0Y3V0IGZ1c2lvbi4KICAgICAgICAgKiBTaG9ydGN1dCBmdXNpb24gaXMgYW4gb3B0aW1pemF0aW9uIHRvIG1lcmdlIGl0ZXJhdGVlIGNhbGxzOyB0aGlzIGF2b2lkcwogICAgICAgICAqIHRoZSBjcmVhdGlvbiBvZiBpbnRlcm1lZGlhdGUgYXJyYXlzIGFuZCBjYW4gZ3JlYXRseSByZWR1Y2UgdGhlIG51bWJlciBvZgogICAgICAgICAqIGl0ZXJhdGVlIGV4ZWN1dGlvbnMuIFNlY3Rpb25zIG9mIGEgY2hhaW4gc2VxdWVuY2UgcXVhbGlmeSBmb3Igc2hvcnRjdXQKICAgICAgICAgKiBmdXNpb24gaWYgdGhlIHNlY3Rpb24gaXMgYXBwbGllZCB0byBhbiBhcnJheSBhbmQgaXRlcmF0ZWVzIGFjY2VwdCBvbmx5CiAgICAgICAgICogb25lIGFyZ3VtZW50LiBUaGUgaGV1cmlzdGljIGZvciB3aGV0aGVyIGEgc2VjdGlvbiBxdWFsaWZpZXMgZm9yIHNob3J0Y3V0CiAgICAgICAgICogZnVzaW9uIGlzIHN1YmplY3QgdG8gY2hhbmdlLgogICAgICAgICAqCiAgICAgICAgICogQ2hhaW5pbmcgaXMgc3VwcG9ydGVkIGluIGN1c3RvbSBidWlsZHMgYXMgbG9uZyBhcyB0aGUgYF8jdmFsdWVgIG1ldGhvZCBpcwogICAgICAgICAqIGRpcmVjdGx5IG9yIGluZGlyZWN0bHkgaW5jbHVkZWQgaW4gdGhlIGJ1aWxkLgogICAgICAgICAqCiAgICAgICAgICogSW4gYWRkaXRpb24gdG8gbG9kYXNoIG1ldGhvZHMsIHdyYXBwZXJzIGhhdmUgYEFycmF5YCBhbmQgYFN0cmluZ2AgbWV0aG9kcy4KICAgICAgICAgKgogICAgICAgICAqIFRoZSB3cmFwcGVyIGBBcnJheWAgbWV0aG9kcyBhcmU6CiAgICAgICAgICogYGNvbmNhdGAsIGBqb2luYCwgYHBvcGAsIGBwdXNoYCwgYHNoaWZ0YCwgYHNvcnRgLCBgc3BsaWNlYCwgYW5kIGB1bnNoaWZ0YAogICAgICAgICAqCiAgICAgICAgICogVGhlIHdyYXBwZXIgYFN0cmluZ2AgbWV0aG9kcyBhcmU6CiAgICAgICAgICogYHJlcGxhY2VgIGFuZCBgc3BsaXRgCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgd3JhcHBlciBtZXRob2RzIHRoYXQgc3VwcG9ydCBzaG9ydGN1dCBmdXNpb24gYXJlOgogICAgICAgICAqIGBhdGAsIGBjb21wYWN0YCwgYGRyb3BgLCBgZHJvcFJpZ2h0YCwgYGRyb3BXaGlsZWAsIGBmaWx0ZXJgLCBgZmluZGAsCiAgICAgICAgICogYGZpbmRMYXN0YCwgYGhlYWRgLCBgaW5pdGlhbGAsIGBsYXN0YCwgYG1hcGAsIGByZWplY3RgLCBgcmV2ZXJzZWAsIGBzbGljZWAsCiAgICAgICAgICogYHRhaWxgLCBgdGFrZWAsIGB0YWtlUmlnaHRgLCBgdGFrZVJpZ2h0V2hpbGVgLCBgdGFrZVdoaWxlYCwgYW5kIGB0b0FycmF5YAogICAgICAgICAqCiAgICAgICAgICogVGhlIGNoYWluYWJsZSB3cmFwcGVyIG1ldGhvZHMgYXJlOgogICAgICAgICAqIGBhZnRlcmAsIGBhcnlgLCBgYXNzaWduYCwgYGFzc2lnbkluYCwgYGFzc2lnbkluV2l0aGAsIGBhc3NpZ25XaXRoYCwgYGF0YCwKICAgICAgICAgKiBgYmVmb3JlYCwgYGJpbmRgLCBgYmluZEFsbGAsIGBiaW5kS2V5YCwgYGNhc3RBcnJheWAsIGBjaGFpbmAsIGBjaHVua2AsCiAgICAgICAgICogYGNvbW1pdGAsIGBjb21wYWN0YCwgYGNvbmNhdGAsIGBjb25mb3Jtc2AsIGBjb25zdGFudGAsIGBjb3VudEJ5YCwgYGNyZWF0ZWAsCiAgICAgICAgICogYGN1cnJ5YCwgYGRlYm91bmNlYCwgYGRlZmF1bHRzYCwgYGRlZmF1bHRzRGVlcGAsIGBkZWZlcmAsIGBkZWxheWAsCiAgICAgICAgICogYGRpZmZlcmVuY2VgLCBgZGlmZmVyZW5jZUJ5YCwgYGRpZmZlcmVuY2VXaXRoYCwgYGRyb3BgLCBgZHJvcFJpZ2h0YCwKICAgICAgICAgKiBgZHJvcFJpZ2h0V2hpbGVgLCBgZHJvcFdoaWxlYCwgYGV4dGVuZGAsIGBleHRlbmRXaXRoYCwgYGZpbGxgLCBgZmlsdGVyYCwKICAgICAgICAgKiBgZmxhdE1hcGAsIGBmbGF0TWFwRGVlcGAsIGBmbGF0TWFwRGVwdGhgLCBgZmxhdHRlbmAsIGBmbGF0dGVuRGVlcGAsCiAgICAgICAgICogYGZsYXR0ZW5EZXB0aGAsIGBmbGlwYCwgYGZsb3dgLCBgZmxvd1JpZ2h0YCwgYGZyb21QYWlyc2AsIGBmdW5jdGlvbnNgLAogICAgICAgICAqIGBmdW5jdGlvbnNJbmAsIGBncm91cEJ5YCwgYGluaXRpYWxgLCBgaW50ZXJzZWN0aW9uYCwgYGludGVyc2VjdGlvbkJ5YCwKICAgICAgICAgKiBgaW50ZXJzZWN0aW9uV2l0aGAsIGBpbnZlcnRgLCBgaW52ZXJ0QnlgLCBgaW52b2tlTWFwYCwgYGl0ZXJhdGVlYCwgYGtleUJ5YCwKICAgICAgICAgKiBga2V5c2AsIGBrZXlzSW5gLCBgbWFwYCwgYG1hcEtleXNgLCBgbWFwVmFsdWVzYCwgYG1hdGNoZXNgLCBgbWF0Y2hlc1Byb3BlcnR5YCwKICAgICAgICAgKiBgbWVtb2l6ZWAsIGBtZXJnZWAsIGBtZXJnZVdpdGhgLCBgbWV0aG9kYCwgYG1ldGhvZE9mYCwgYG1peGluYCwgYG5lZ2F0ZWAsCiAgICAgICAgICogYG50aEFyZ2AsIGBvbWl0YCwgYG9taXRCeWAsIGBvbmNlYCwgYG9yZGVyQnlgLCBgb3ZlcmAsIGBvdmVyQXJnc2AsCiAgICAgICAgICogYG92ZXJFdmVyeWAsIGBvdmVyU29tZWAsIGBwYXJ0aWFsYCwgYHBhcnRpYWxSaWdodGAsIGBwYXJ0aXRpb25gLCBgcGlja2AsCiAgICAgICAgICogYHBpY2tCeWAsIGBwbGFudGAsIGBwcm9wZXJ0eWAsIGBwcm9wZXJ0eU9mYCwgYHB1bGxgLCBgcHVsbEFsbGAsIGBwdWxsQWxsQnlgLAogICAgICAgICAqIGBwdWxsQWxsV2l0aGAsIGBwdWxsQXRgLCBgcHVzaGAsIGByYW5nZWAsIGByYW5nZVJpZ2h0YCwgYHJlYXJnYCwgYHJlamVjdGAsCiAgICAgICAgICogYHJlbW92ZWAsIGByZXN0YCwgYHJldmVyc2VgLCBgc2FtcGxlU2l6ZWAsIGBzZXRgLCBgc2V0V2l0aGAsIGBzaHVmZmxlYCwKICAgICAgICAgKiBgc2xpY2VgLCBgc29ydGAsIGBzb3J0QnlgLCBgc3BsaWNlYCwgYHNwcmVhZGAsIGB0YWlsYCwgYHRha2VgLCBgdGFrZVJpZ2h0YCwKICAgICAgICAgKiBgdGFrZVJpZ2h0V2hpbGVgLCBgdGFrZVdoaWxlYCwgYHRhcGAsIGB0aHJvdHRsZWAsIGB0aHJ1YCwgYHRvQXJyYXlgLAogICAgICAgICAqIGB0b1BhaXJzYCwgYHRvUGFpcnNJbmAsIGB0b1BhdGhgLCBgdG9QbGFpbk9iamVjdGAsIGB0cmFuc2Zvcm1gLCBgdW5hcnlgLAogICAgICAgICAqIGB1bmlvbmAsIGB1bmlvbkJ5YCwgYHVuaW9uV2l0aGAsIGB1bmlxYCwgYHVuaXFCeWAsIGB1bmlxV2l0aGAsIGB1bnNldGAsCiAgICAgICAgICogYHVuc2hpZnRgLCBgdW56aXBgLCBgdW56aXBXaXRoYCwgYHVwZGF0ZWAsIGB1cGRhdGVXaXRoYCwgYHZhbHVlc2AsCiAgICAgICAgICogYHZhbHVlc0luYCwgYHdpdGhvdXRgLCBgd3JhcGAsIGB4b3JgLCBgeG9yQnlgLCBgeG9yV2l0aGAsIGB6aXBgLAogICAgICAgICAqIGB6aXBPYmplY3RgLCBgemlwT2JqZWN0RGVlcGAsIGFuZCBgemlwV2l0aGAKICAgICAgICAgKgogICAgICAgICAqIFRoZSB3cmFwcGVyIG1ldGhvZHMgdGhhdCBhcmUgKipub3QqKiBjaGFpbmFibGUgYnkgZGVmYXVsdCBhcmU6CiAgICAgICAgICogYGFkZGAsIGBhdHRlbXB0YCwgYGNhbWVsQ2FzZWAsIGBjYXBpdGFsaXplYCwgYGNlaWxgLCBgY2xhbXBgLCBgY2xvbmVgLAogICAgICAgICAqIGBjbG9uZURlZXBgLCBgY2xvbmVEZWVwV2l0aGAsIGBjbG9uZVdpdGhgLCBgY29uZm9ybXNUb2AsIGBkZWJ1cnJgLAogICAgICAgICAqIGBkZWZhdWx0VG9gLCBgZGl2aWRlYCwgYGVhY2hgLCBgZWFjaFJpZ2h0YCwgYGVuZHNXaXRoYCwgYGVxYCwgYGVzY2FwZWAsCiAgICAgICAgICogYGVzY2FwZVJlZ0V4cGAsIGBldmVyeWAsIGBmaW5kYCwgYGZpbmRJbmRleGAsIGBmaW5kS2V5YCwgYGZpbmRMYXN0YCwKICAgICAgICAgKiBgZmluZExhc3RJbmRleGAsIGBmaW5kTGFzdEtleWAsIGBmaXJzdGAsIGBmbG9vcmAsIGBmb3JFYWNoYCwgYGZvckVhY2hSaWdodGAsCiAgICAgICAgICogYGZvckluYCwgYGZvckluUmlnaHRgLCBgZm9yT3duYCwgYGZvck93blJpZ2h0YCwgYGdldGAsIGBndGAsIGBndGVgLCBgaGFzYCwKICAgICAgICAgKiBgaGFzSW5gLCBgaGVhZGAsIGBpZGVudGl0eWAsIGBpbmNsdWRlc2AsIGBpbmRleE9mYCwgYGluUmFuZ2VgLCBgaW52b2tlYCwKICAgICAgICAgKiBgaXNBcmd1bWVudHNgLCBgaXNBcnJheWAsIGBpc0FycmF5QnVmZmVyYCwgYGlzQXJyYXlMaWtlYCwgYGlzQXJyYXlMaWtlT2JqZWN0YCwKICAgICAgICAgKiBgaXNCb29sZWFuYCwgYGlzQnVmZmVyYCwgYGlzRGF0ZWAsIGBpc0VsZW1lbnRgLCBgaXNFbXB0eWAsIGBpc0VxdWFsYCwKICAgICAgICAgKiBgaXNFcXVhbFdpdGhgLCBgaXNFcnJvcmAsIGBpc0Zpbml0ZWAsIGBpc0Z1bmN0aW9uYCwgYGlzSW50ZWdlcmAsIGBpc0xlbmd0aGAsCiAgICAgICAgICogYGlzTWFwYCwgYGlzTWF0Y2hgLCBgaXNNYXRjaFdpdGhgLCBgaXNOYU5gLCBgaXNOYXRpdmVgLCBgaXNOaWxgLCBgaXNOdWxsYCwKICAgICAgICAgKiBgaXNOdW1iZXJgLCBgaXNPYmplY3RgLCBgaXNPYmplY3RMaWtlYCwgYGlzUGxhaW5PYmplY3RgLCBgaXNSZWdFeHBgLAogICAgICAgICAqIGBpc1NhZmVJbnRlZ2VyYCwgYGlzU2V0YCwgYGlzU3RyaW5nYCwgYGlzVW5kZWZpbmVkYCwgYGlzVHlwZWRBcnJheWAsCiAgICAgICAgICogYGlzV2Vha01hcGAsIGBpc1dlYWtTZXRgLCBgam9pbmAsIGBrZWJhYkNhc2VgLCBgbGFzdGAsIGBsYXN0SW5kZXhPZmAsCiAgICAgICAgICogYGxvd2VyQ2FzZWAsIGBsb3dlckZpcnN0YCwgYGx0YCwgYGx0ZWAsIGBtYXhgLCBgbWF4QnlgLCBgbWVhbmAsIGBtZWFuQnlgLAogICAgICAgICAqIGBtaW5gLCBgbWluQnlgLCBgbXVsdGlwbHlgLCBgbm9Db25mbGljdGAsIGBub29wYCwgYG5vd2AsIGBudGhgLCBgcGFkYCwKICAgICAgICAgKiBgcGFkRW5kYCwgYHBhZFN0YXJ0YCwgYHBhcnNlSW50YCwgYHBvcGAsIGByYW5kb21gLCBgcmVkdWNlYCwgYHJlZHVjZVJpZ2h0YCwKICAgICAgICAgKiBgcmVwZWF0YCwgYHJlc3VsdGAsIGByb3VuZGAsIGBydW5JbkNvbnRleHRgLCBgc2FtcGxlYCwgYHNoaWZ0YCwgYHNpemVgLAogICAgICAgICAqIGBzbmFrZUNhc2VgLCBgc29tZWAsIGBzb3J0ZWRJbmRleGAsIGBzb3J0ZWRJbmRleEJ5YCwgYHNvcnRlZExhc3RJbmRleGAsCiAgICAgICAgICogYHNvcnRlZExhc3RJbmRleEJ5YCwgYHN0YXJ0Q2FzZWAsIGBzdGFydHNXaXRoYCwgYHN0dWJBcnJheWAsIGBzdHViRmFsc2VgLAogICAgICAgICAqIGBzdHViT2JqZWN0YCwgYHN0dWJTdHJpbmdgLCBgc3R1YlRydWVgLCBgc3VidHJhY3RgLCBgc3VtYCwgYHN1bUJ5YCwKICAgICAgICAgKiBgdGVtcGxhdGVgLCBgdGltZXNgLCBgdG9GaW5pdGVgLCBgdG9JbnRlZ2VyYCwgYHRvSlNPTmAsIGB0b0xlbmd0aGAsCiAgICAgICAgICogYHRvTG93ZXJgLCBgdG9OdW1iZXJgLCBgdG9TYWZlSW50ZWdlcmAsIGB0b1N0cmluZ2AsIGB0b1VwcGVyYCwgYHRyaW1gLAogICAgICAgICAqIGB0cmltRW5kYCwgYHRyaW1TdGFydGAsIGB0cnVuY2F0ZWAsIGB1bmVzY2FwZWAsIGB1bmlxdWVJZGAsIGB1cHBlckNhc2VgLAogICAgICAgICAqIGB1cHBlckZpcnN0YCwgYHZhbHVlYCwgYW5kIGB3b3Jkc2AKICAgICAgICAgKgogICAgICAgICAqIEBuYW1lIF8KICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAY2F0ZWdvcnkgU2VxCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gd3JhcCBpbiBhIGBsb2Rhc2hgIGluc3RhbmNlLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBgbG9kYXNoYCB3cmFwcGVyIGluc3RhbmNlLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBzcXVhcmUobikgewogICAgICAgICAqICAgcmV0dXJuIG4gKiBuOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciB3cmFwcGVkID0gXyhbMSwgMiwgM10pOwogICAgICAgICAqCiAgICAgICAgICogLy8gUmV0dXJucyBhbiB1bndyYXBwZWQgdmFsdWUuCiAgICAgICAgICogd3JhcHBlZC5yZWR1Y2UoXy5hZGQpOwogICAgICAgICAqIC8vID0+IDYKICAgICAgICAgKgogICAgICAgICAqIC8vIFJldHVybnMgYSB3cmFwcGVkIHZhbHVlLgogICAgICAgICAqIHZhciBzcXVhcmVzID0gd3JhcHBlZC5tYXAoc3F1YXJlKTsKICAgICAgICAgKgogICAgICAgICAqIF8uaXNBcnJheShzcXVhcmVzKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5KHNxdWFyZXMudmFsdWUoKSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGxvZGFzaCh2YWx1ZSkgewogICAgICAgICAgaWYgKGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYgIWlzQXJyYXkodmFsdWUpICYmICEodmFsdWUgaW5zdGFuY2VvZiBMYXp5V3JhcHBlcikpIHsKICAgICAgICAgICAgaWYgKHZhbHVlIGluc3RhbmNlb2YgTG9kYXNoV3JhcHBlcikgewogICAgICAgICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaGFzT3duUHJvcGVydHkuY2FsbCh2YWx1ZSwgJ19fd3JhcHBlZF9fJykpIHsKICAgICAgICAgICAgICByZXR1cm4gd3JhcHBlckNsb25lKHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG5ldyBMb2Rhc2hXcmFwcGVyKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmNyZWF0ZWAgd2l0aG91dCBzdXBwb3J0IGZvciBhc3NpZ25pbmcKICAgICAgICAgKiBwcm9wZXJ0aWVzIHRvIHRoZSBjcmVhdGVkIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHByb3RvIFRoZSBvYmplY3QgdG8gaW5oZXJpdCBmcm9tLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICovCiAgICAgICAgdmFyIGJhc2VDcmVhdGUgPSAoZnVuY3Rpb24oKSB7CiAgICAgICAgICBmdW5jdGlvbiBvYmplY3QoKSB7fQogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHByb3RvKSB7CiAgICAgICAgICAgIGlmICghaXNPYmplY3QocHJvdG8pKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHt9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChvYmplY3RDcmVhdGUpIHsKICAgICAgICAgICAgICByZXR1cm4gb2JqZWN0Q3JlYXRlKHByb3RvKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBvYmplY3QucHJvdG90eXBlID0gcHJvdG87CiAgICAgICAgICAgIHZhciByZXN1bHQgPSBuZXcgb2JqZWN0OwogICAgICAgICAgICBvYmplY3QucHJvdG90eXBlID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9OwogICAgICAgIH0oKSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBmdW5jdGlvbiB3aG9zZSBwcm90b3R5cGUgY2hhaW4gc2VxdWVuY2Ugd3JhcHBlcnMgaW5oZXJpdCBmcm9tLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlTG9kYXNoKCkgewogICAgICAgICAgLy8gTm8gb3BlcmF0aW9uIHBlcmZvcm1lZC4KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGNvbnN0cnVjdG9yIGZvciBjcmVhdGluZyBgbG9kYXNoYCB3cmFwcGVyIG9iamVjdHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbY2hhaW5BbGxdIEVuYWJsZSBleHBsaWNpdCBtZXRob2QgY2hhaW4gc2VxdWVuY2VzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIExvZGFzaFdyYXBwZXIodmFsdWUsIGNoYWluQWxsKSB7CiAgICAgICAgICB0aGlzLl9fd3JhcHBlZF9fID0gdmFsdWU7CiAgICAgICAgICB0aGlzLl9fYWN0aW9uc19fID0gW107CiAgICAgICAgICB0aGlzLl9fY2hhaW5fXyA9ICEhY2hhaW5BbGw7CiAgICAgICAgICB0aGlzLl9faW5kZXhfXyA9IDA7CiAgICAgICAgICB0aGlzLl9fdmFsdWVzX18gPSB1bmRlZmluZWQkMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEJ5IGRlZmF1bHQsIHRoZSB0ZW1wbGF0ZSBkZWxpbWl0ZXJzIHVzZWQgYnkgbG9kYXNoIGFyZSBsaWtlIHRob3NlIGluCiAgICAgICAgICogZW1iZWRkZWQgUnVieSAoRVJCKSBhcyB3ZWxsIGFzIEVTMjAxNSB0ZW1wbGF0ZSBzdHJpbmdzLiBDaGFuZ2UgdGhlCiAgICAgICAgICogZm9sbG93aW5nIHRlbXBsYXRlIHNldHRpbmdzIHRvIHVzZSBhbHRlcm5hdGl2ZSBkZWxpbWl0ZXJzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHR5cGUge09iamVjdH0KICAgICAgICAgKi8KICAgICAgICBsb2Rhc2gudGVtcGxhdGVTZXR0aW5ncyA9IHsKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFVzZWQgdG8gZGV0ZWN0IGBkYXRhYCBwcm9wZXJ0eSB2YWx1ZXMgdG8gYmUgSFRNTC1lc2NhcGVkLgogICAgICAgICAgICoKICAgICAgICAgICAqIEBtZW1iZXJPZiBfLnRlbXBsYXRlU2V0dGluZ3MKICAgICAgICAgICAqIEB0eXBlIHtSZWdFeHB9CiAgICAgICAgICAgKi8KICAgICAgICAgICdlc2NhcGUnOiByZUVzY2FwZSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFVzZWQgdG8gZGV0ZWN0IGNvZGUgdG8gYmUgZXZhbHVhdGVkLgogICAgICAgICAgICoKICAgICAgICAgICAqIEBtZW1iZXJPZiBfLnRlbXBsYXRlU2V0dGluZ3MKICAgICAgICAgICAqIEB0eXBlIHtSZWdFeHB9CiAgICAgICAgICAgKi8KICAgICAgICAgICdldmFsdWF0ZSc6IHJlRXZhbHVhdGUsCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBVc2VkIHRvIGRldGVjdCBgZGF0YWAgcHJvcGVydHkgdmFsdWVzIHRvIGluamVjdC4KICAgICAgICAgICAqCiAgICAgICAgICAgKiBAbWVtYmVyT2YgXy50ZW1wbGF0ZVNldHRpbmdzCiAgICAgICAgICAgKiBAdHlwZSB7UmVnRXhwfQogICAgICAgICAgICovCiAgICAgICAgICAnaW50ZXJwb2xhdGUnOiByZUludGVycG9sYXRlLAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogVXNlZCB0byByZWZlcmVuY2UgdGhlIGRhdGEgb2JqZWN0IGluIHRoZSB0ZW1wbGF0ZSB0ZXh0LgogICAgICAgICAgICoKICAgICAgICAgICAqIEBtZW1iZXJPZiBfLnRlbXBsYXRlU2V0dGluZ3MKICAgICAgICAgICAqIEB0eXBlIHtzdHJpbmd9CiAgICAgICAgICAgKi8KICAgICAgICAgICd2YXJpYWJsZSc6ICcnLAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogVXNlZCB0byBpbXBvcnQgdmFyaWFibGVzIGludG8gdGhlIGNvbXBpbGVkIHRlbXBsYXRlLgogICAgICAgICAgICoKICAgICAgICAgICAqIEBtZW1iZXJPZiBfLnRlbXBsYXRlU2V0dGluZ3MKICAgICAgICAgICAqIEB0eXBlIHtPYmplY3R9CiAgICAgICAgICAgKi8KICAgICAgICAgICdpbXBvcnRzJzogewoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEEgcmVmZXJlbmNlIHRvIHRoZSBgbG9kYXNoYCBmdW5jdGlvbi4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICogQG1lbWJlck9mIF8udGVtcGxhdGVTZXR0aW5ncy5pbXBvcnRzCiAgICAgICAgICAgICAqIEB0eXBlIHtGdW5jdGlvbn0KICAgICAgICAgICAgICovCiAgICAgICAgICAgICdfJzogbG9kYXNoCiAgICAgICAgICB9CiAgICAgICAgfTsKCiAgICAgICAgLy8gRW5zdXJlIHdyYXBwZXJzIGFyZSBpbnN0YW5jZXMgb2YgYGJhc2VMb2Rhc2hgLgogICAgICAgIGxvZGFzaC5wcm90b3R5cGUgPSBiYXNlTG9kYXNoLnByb3RvdHlwZTsKICAgICAgICBsb2Rhc2gucHJvdG90eXBlLmNvbnN0cnVjdG9yID0gbG9kYXNoOwoKICAgICAgICBMb2Rhc2hXcmFwcGVyLnByb3RvdHlwZSA9IGJhc2VDcmVhdGUoYmFzZUxvZGFzaC5wcm90b3R5cGUpOwogICAgICAgIExvZGFzaFdyYXBwZXIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0gTG9kYXNoV3JhcHBlcjsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgbGF6eSB3cmFwcGVyIG9iamVjdCB3aGljaCB3cmFwcyBgdmFsdWVgIHRvIGVuYWJsZSBsYXp5IGV2YWx1YXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHdyYXAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gTGF6eVdyYXBwZXIodmFsdWUpIHsKICAgICAgICAgIHRoaXMuX193cmFwcGVkX18gPSB2YWx1ZTsKICAgICAgICAgIHRoaXMuX19hY3Rpb25zX18gPSBbXTsKICAgICAgICAgIHRoaXMuX19kaXJfXyA9IDE7CiAgICAgICAgICB0aGlzLl9fZmlsdGVyZWRfXyA9IGZhbHNlOwogICAgICAgICAgdGhpcy5fX2l0ZXJhdGVlc19fID0gW107CiAgICAgICAgICB0aGlzLl9fdGFrZUNvdW50X18gPSBNQVhfQVJSQVlfTEVOR1RIOwogICAgICAgICAgdGhpcy5fX3ZpZXdzX18gPSBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBjbG9uZSBvZiB0aGUgbGF6eSB3cmFwcGVyIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgY2xvbmUKICAgICAgICAgKiBAbWVtYmVyT2YgTGF6eVdyYXBwZXIKICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgYExhenlXcmFwcGVyYCBvYmplY3QuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbGF6eUNsb25lKCkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IG5ldyBMYXp5V3JhcHBlcih0aGlzLl9fd3JhcHBlZF9fKTsKICAgICAgICAgIHJlc3VsdC5fX2FjdGlvbnNfXyA9IGNvcHlBcnJheSh0aGlzLl9fYWN0aW9uc19fKTsKICAgICAgICAgIHJlc3VsdC5fX2Rpcl9fID0gdGhpcy5fX2Rpcl9fOwogICAgICAgICAgcmVzdWx0Ll9fZmlsdGVyZWRfXyA9IHRoaXMuX19maWx0ZXJlZF9fOwogICAgICAgICAgcmVzdWx0Ll9faXRlcmF0ZWVzX18gPSBjb3B5QXJyYXkodGhpcy5fX2l0ZXJhdGVlc19fKTsKICAgICAgICAgIHJlc3VsdC5fX3Rha2VDb3VudF9fID0gdGhpcy5fX3Rha2VDb3VudF9fOwogICAgICAgICAgcmVzdWx0Ll9fdmlld3NfXyA9IGNvcHlBcnJheSh0aGlzLl9fdmlld3NfXyk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV2ZXJzZXMgdGhlIGRpcmVjdGlvbiBvZiBsYXp5IGl0ZXJhdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgcmV2ZXJzZQogICAgICAgICAqIEBtZW1iZXJPZiBMYXp5V3JhcHBlcgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyByZXZlcnNlZCBgTGF6eVdyYXBwZXJgIG9iamVjdC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsYXp5UmV2ZXJzZSgpIHsKICAgICAgICAgIGlmICh0aGlzLl9fZmlsdGVyZWRfXykgewogICAgICAgICAgICB2YXIgcmVzdWx0ID0gbmV3IExhenlXcmFwcGVyKHRoaXMpOwogICAgICAgICAgICByZXN1bHQuX19kaXJfXyA9IC0xOwogICAgICAgICAgICByZXN1bHQuX19maWx0ZXJlZF9fID0gdHJ1ZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHJlc3VsdCA9IHRoaXMuY2xvbmUoKTsKICAgICAgICAgICAgcmVzdWx0Ll9fZGlyX18gKj0gLTE7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRXh0cmFjdHMgdGhlIHVud3JhcHBlZCB2YWx1ZSBmcm9tIGl0cyBsYXp5IHdyYXBwZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIHZhbHVlCiAgICAgICAgICogQG1lbWJlck9mIExhenlXcmFwcGVyCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHVud3JhcHBlZCB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsYXp5VmFsdWUoKSB7CiAgICAgICAgICB2YXIgYXJyYXkgPSB0aGlzLl9fd3JhcHBlZF9fLnZhbHVlKCksCiAgICAgICAgICAgICAgZGlyID0gdGhpcy5fX2Rpcl9fLAogICAgICAgICAgICAgIGlzQXJyID0gaXNBcnJheShhcnJheSksCiAgICAgICAgICAgICAgaXNSaWdodCA9IGRpciA8IDAsCiAgICAgICAgICAgICAgYXJyTGVuZ3RoID0gaXNBcnIgPyBhcnJheS5sZW5ndGggOiAwLAogICAgICAgICAgICAgIHZpZXcgPSBnZXRWaWV3KDAsIGFyckxlbmd0aCwgdGhpcy5fX3ZpZXdzX18pLAogICAgICAgICAgICAgIHN0YXJ0ID0gdmlldy5zdGFydCwKICAgICAgICAgICAgICBlbmQgPSB2aWV3LmVuZCwKICAgICAgICAgICAgICBsZW5ndGggPSBlbmQgLSBzdGFydCwKICAgICAgICAgICAgICBpbmRleCA9IGlzUmlnaHQgPyBlbmQgOiAoc3RhcnQgLSAxKSwKICAgICAgICAgICAgICBpdGVyYXRlZXMgPSB0aGlzLl9faXRlcmF0ZWVzX18sCiAgICAgICAgICAgICAgaXRlckxlbmd0aCA9IGl0ZXJhdGVlcy5sZW5ndGgsCiAgICAgICAgICAgICAgcmVzSW5kZXggPSAwLAogICAgICAgICAgICAgIHRha2VDb3VudCA9IG5hdGl2ZU1pbihsZW5ndGgsIHRoaXMuX190YWtlQ291bnRfXyk7CgogICAgICAgICAgaWYgKCFpc0FyciB8fCAoIWlzUmlnaHQgJiYgYXJyTGVuZ3RoID09IGxlbmd0aCAmJiB0YWtlQ291bnQgPT0gbGVuZ3RoKSkgewogICAgICAgICAgICByZXR1cm4gYmFzZVdyYXBwZXJWYWx1ZShhcnJheSwgdGhpcy5fX2FjdGlvbnNfXyk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcmVzdWx0ID0gW107CgogICAgICAgICAgb3V0ZXI6CiAgICAgICAgICB3aGlsZSAobGVuZ3RoLS0gJiYgcmVzSW5kZXggPCB0YWtlQ291bnQpIHsKICAgICAgICAgICAgaW5kZXggKz0gZGlyOwoKICAgICAgICAgICAgdmFyIGl0ZXJJbmRleCA9IC0xLAogICAgICAgICAgICAgICAgdmFsdWUgPSBhcnJheVtpbmRleF07CgogICAgICAgICAgICB3aGlsZSAoKytpdGVySW5kZXggPCBpdGVyTGVuZ3RoKSB7CiAgICAgICAgICAgICAgdmFyIGRhdGEgPSBpdGVyYXRlZXNbaXRlckluZGV4XSwKICAgICAgICAgICAgICAgICAgaXRlcmF0ZWUgPSBkYXRhLml0ZXJhdGVlLAogICAgICAgICAgICAgICAgICB0eXBlID0gZGF0YS50eXBlLAogICAgICAgICAgICAgICAgICBjb21wdXRlZCA9IGl0ZXJhdGVlKHZhbHVlKTsKCiAgICAgICAgICAgICAgaWYgKHR5cGUgPT0gTEFaWV9NQVBfRkxBRykgewogICAgICAgICAgICAgICAgdmFsdWUgPSBjb21wdXRlZDsKICAgICAgICAgICAgICB9IGVsc2UgaWYgKCFjb21wdXRlZCkgewogICAgICAgICAgICAgICAgaWYgKHR5cGUgPT0gTEFaWV9GSUxURVJfRkxBRykgewogICAgICAgICAgICAgICAgICBjb250aW51ZSBvdXRlcjsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgIGJyZWFrIG91dGVyOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXN1bHRbcmVzSW5kZXgrK10gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvLyBFbnN1cmUgYExhenlXcmFwcGVyYCBpcyBhbiBpbnN0YW5jZSBvZiBgYmFzZUxvZGFzaGAuCiAgICAgICAgTGF6eVdyYXBwZXIucHJvdG90eXBlID0gYmFzZUNyZWF0ZShiYXNlTG9kYXNoLnByb3RvdHlwZSk7CiAgICAgICAgTGF6eVdyYXBwZXIucHJvdG90eXBlLmNvbnN0cnVjdG9yID0gTGF6eVdyYXBwZXI7CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGhhc2ggb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBbZW50cmllc10gVGhlIGtleS12YWx1ZSBwYWlycyB0byBjYWNoZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBIYXNoKGVudHJpZXMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGVudHJpZXMgPT0gbnVsbCA/IDAgOiBlbnRyaWVzLmxlbmd0aDsKCiAgICAgICAgICB0aGlzLmNsZWFyKCk7CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgZW50cnkgPSBlbnRyaWVzW2luZGV4XTsKICAgICAgICAgICAgdGhpcy5zZXQoZW50cnlbMF0sIGVudHJ5WzFdKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIGhhc2guCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGNsZWFyCiAgICAgICAgICogQG1lbWJlck9mIEhhc2gKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBoYXNoQ2xlYXIoKSB7CiAgICAgICAgICB0aGlzLl9fZGF0YV9fID0gbmF0aXZlQ3JlYXRlID8gbmF0aXZlQ3JlYXRlKG51bGwpIDoge307CiAgICAgICAgICB0aGlzLnNpemUgPSAwOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBga2V5YCBhbmQgaXRzIHZhbHVlIGZyb20gdGhlIGhhc2guCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGRlbGV0ZQogICAgICAgICAqIEBtZW1iZXJPZiBIYXNoCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IGhhc2ggVGhlIGhhc2ggdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gcmVtb3ZlLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgZW50cnkgd2FzIHJlbW92ZWQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBoYXNoRGVsZXRlKGtleSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IHRoaXMuaGFzKGtleSkgJiYgZGVsZXRlIHRoaXMuX19kYXRhX19ba2V5XTsKICAgICAgICAgIHRoaXMuc2l6ZSAtPSByZXN1bHQgPyAxIDogMDsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBoYXNoIHZhbHVlIGZvciBga2V5YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgZ2V0CiAgICAgICAgICogQG1lbWJlck9mIEhhc2gKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIGdldC4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgZW50cnkgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaGFzaEdldChrZXkpIHsKICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXzsKICAgICAgICAgIGlmIChuYXRpdmVDcmVhdGUpIHsKICAgICAgICAgICAgdmFyIHJlc3VsdCA9IGRhdGFba2V5XTsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdCA9PT0gSEFTSF9VTkRFRklORUQgPyB1bmRlZmluZWQkMSA6IHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBoYXNPd25Qcm9wZXJ0eS5jYWxsKGRhdGEsIGtleSkgPyBkYXRhW2tleV0gOiB1bmRlZmluZWQkMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBhIGhhc2ggdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgaGFzCiAgICAgICAgICogQG1lbWJlck9mIEhhc2gKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIGVudHJ5IHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbiBlbnRyeSBmb3IgYGtleWAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaGFzaEhhcyhrZXkpIHsKICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXzsKICAgICAgICAgIHJldHVybiBuYXRpdmVDcmVhdGUgPyAoZGF0YVtrZXldICE9PSB1bmRlZmluZWQkMSkgOiBoYXNPd25Qcm9wZXJ0eS5jYWxsKGRhdGEsIGtleSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBoYXNoIGBrZXlgIHRvIGB2YWx1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIHNldAogICAgICAgICAqIEBtZW1iZXJPZiBIYXNoCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byBzZXQuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGhhc2ggaW5zdGFuY2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaGFzaFNldChrZXksIHZhbHVlKSB7CiAgICAgICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX187CiAgICAgICAgICB0aGlzLnNpemUgKz0gdGhpcy5oYXMoa2V5KSA/IDAgOiAxOwogICAgICAgICAgZGF0YVtrZXldID0gKG5hdGl2ZUNyZWF0ZSAmJiB2YWx1ZSA9PT0gdW5kZWZpbmVkJDEpID8gSEFTSF9VTkRFRklORUQgOiB2YWx1ZTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KCiAgICAgICAgLy8gQWRkIG1ldGhvZHMgdG8gYEhhc2hgLgogICAgICAgIEhhc2gucHJvdG90eXBlLmNsZWFyID0gaGFzaENsZWFyOwogICAgICAgIEhhc2gucHJvdG90eXBlWydkZWxldGUnXSA9IGhhc2hEZWxldGU7CiAgICAgICAgSGFzaC5wcm90b3R5cGUuZ2V0ID0gaGFzaEdldDsKICAgICAgICBIYXNoLnByb3RvdHlwZS5oYXMgPSBoYXNoSGFzOwogICAgICAgIEhhc2gucHJvdG90eXBlLnNldCA9IGhhc2hTZXQ7CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBsaXN0IGNhY2hlIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW2VudHJpZXNdIFRoZSBrZXktdmFsdWUgcGFpcnMgdG8gY2FjaGUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gTGlzdENhY2hlKGVudHJpZXMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGVudHJpZXMgPT0gbnVsbCA/IDAgOiBlbnRyaWVzLmxlbmd0aDsKCiAgICAgICAgICB0aGlzLmNsZWFyKCk7CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgZW50cnkgPSBlbnRyaWVzW2luZGV4XTsKICAgICAgICAgICAgdGhpcy5zZXQoZW50cnlbMF0sIGVudHJ5WzFdKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIGxpc3QgY2FjaGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGNsZWFyCiAgICAgICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGxpc3RDYWNoZUNsZWFyKCkgewogICAgICAgICAgdGhpcy5fX2RhdGFfXyA9IFtdOwogICAgICAgICAgdGhpcy5zaXplID0gMDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYGtleWAgYW5kIGl0cyB2YWx1ZSBmcm9tIHRoZSBsaXN0IGNhY2hlLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAbmFtZSBkZWxldGUKICAgICAgICAgKiBAbWVtYmVyT2YgTGlzdENhY2hlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byByZW1vdmUuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBlbnRyeSB3YXMgcmVtb3ZlZCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGxpc3RDYWNoZURlbGV0ZShrZXkpIHsKICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXywKICAgICAgICAgICAgICBpbmRleCA9IGFzc29jSW5kZXhPZihkYXRhLCBrZXkpOwoKICAgICAgICAgIGlmIChpbmRleCA8IDApIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGxhc3RJbmRleCA9IGRhdGEubGVuZ3RoIC0gMTsKICAgICAgICAgIGlmIChpbmRleCA9PSBsYXN0SW5kZXgpIHsKICAgICAgICAgICAgZGF0YS5wb3AoKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHNwbGljZS5jYWxsKGRhdGEsIGluZGV4LCAxKTsKICAgICAgICAgIH0KICAgICAgICAgIC0tdGhpcy5zaXplOwogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBsaXN0IGNhY2hlIHZhbHVlIGZvciBga2V5YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgZ2V0CiAgICAgICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBlbnRyeSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsaXN0Q2FjaGVHZXQoa2V5KSB7CiAgICAgICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX18sCiAgICAgICAgICAgICAgaW5kZXggPSBhc3NvY0luZGV4T2YoZGF0YSwga2V5KTsKCiAgICAgICAgICByZXR1cm4gaW5kZXggPCAwID8gdW5kZWZpbmVkJDEgOiBkYXRhW2luZGV4XVsxXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBhIGxpc3QgY2FjaGUgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgaGFzCiAgICAgICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgZW50cnkgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGFuIGVudHJ5IGZvciBga2V5YCBleGlzdHMsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsaXN0Q2FjaGVIYXMoa2V5KSB7CiAgICAgICAgICByZXR1cm4gYXNzb2NJbmRleE9mKHRoaXMuX19kYXRhX18sIGtleSkgPiAtMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIGxpc3QgY2FjaGUgYGtleWAgdG8gYHZhbHVlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgc2V0CiAgICAgICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gc2V0LgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHNldC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBsaXN0IGNhY2hlIGluc3RhbmNlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGxpc3RDYWNoZVNldChrZXksIHZhbHVlKSB7CiAgICAgICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX18sCiAgICAgICAgICAgICAgaW5kZXggPSBhc3NvY0luZGV4T2YoZGF0YSwga2V5KTsKCiAgICAgICAgICBpZiAoaW5kZXggPCAwKSB7CiAgICAgICAgICAgICsrdGhpcy5zaXplOwogICAgICAgICAgICBkYXRhLnB1c2goW2tleSwgdmFsdWVdKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGRhdGFbaW5kZXhdWzFdID0gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9CgogICAgICAgIC8vIEFkZCBtZXRob2RzIHRvIGBMaXN0Q2FjaGVgLgogICAgICAgIExpc3RDYWNoZS5wcm90b3R5cGUuY2xlYXIgPSBsaXN0Q2FjaGVDbGVhcjsKICAgICAgICBMaXN0Q2FjaGUucHJvdG90eXBlWydkZWxldGUnXSA9IGxpc3RDYWNoZURlbGV0ZTsKICAgICAgICBMaXN0Q2FjaGUucHJvdG90eXBlLmdldCA9IGxpc3RDYWNoZUdldDsKICAgICAgICBMaXN0Q2FjaGUucHJvdG90eXBlLmhhcyA9IGxpc3RDYWNoZUhhczsKICAgICAgICBMaXN0Q2FjaGUucHJvdG90eXBlLnNldCA9IGxpc3RDYWNoZVNldDsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgbWFwIGNhY2hlIG9iamVjdCB0byBzdG9yZSBrZXktdmFsdWUgcGFpcnMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFtlbnRyaWVzXSBUaGUga2V5LXZhbHVlIHBhaXJzIHRvIGNhY2hlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIE1hcENhY2hlKGVudHJpZXMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGVudHJpZXMgPT0gbnVsbCA/IDAgOiBlbnRyaWVzLmxlbmd0aDsKCiAgICAgICAgICB0aGlzLmNsZWFyKCk7CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgZW50cnkgPSBlbnRyaWVzW2luZGV4XTsKICAgICAgICAgICAgdGhpcy5zZXQoZW50cnlbMF0sIGVudHJ5WzFdKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIG1hcC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgY2xlYXIKICAgICAgICAgKiBAbWVtYmVyT2YgTWFwQ2FjaGUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXBDYWNoZUNsZWFyKCkgewogICAgICAgICAgdGhpcy5zaXplID0gMDsKICAgICAgICAgIHRoaXMuX19kYXRhX18gPSB7CiAgICAgICAgICAgICdoYXNoJzogbmV3IEhhc2gsCiAgICAgICAgICAgICdtYXAnOiBuZXcgKE1hcCB8fCBMaXN0Q2FjaGUpLAogICAgICAgICAgICAnc3RyaW5nJzogbmV3IEhhc2gKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGBrZXlgIGFuZCBpdHMgdmFsdWUgZnJvbSB0aGUgbWFwLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAbmFtZSBkZWxldGUKICAgICAgICAgKiBAbWVtYmVyT2YgTWFwQ2FjaGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIHJlbW92ZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIGVudHJ5IHdhcyByZW1vdmVkLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbWFwQ2FjaGVEZWxldGUoa2V5KSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gZ2V0TWFwRGF0YSh0aGlzLCBrZXkpWydkZWxldGUnXShrZXkpOwogICAgICAgICAgdGhpcy5zaXplIC09IHJlc3VsdCA/IDEgOiAwOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIG1hcCB2YWx1ZSBmb3IgYGtleWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGdldAogICAgICAgICAqIEBtZW1iZXJPZiBNYXBDYWNoZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBlbnRyeSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXBDYWNoZUdldChrZXkpIHsKICAgICAgICAgIHJldHVybiBnZXRNYXBEYXRhKHRoaXMsIGtleSkuZ2V0KGtleSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYSBtYXAgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgaGFzCiAgICAgICAgICogQG1lbWJlck9mIE1hcENhY2hlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBlbnRyeSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYW4gZW50cnkgZm9yIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1hcENhY2hlSGFzKGtleSkgewogICAgICAgICAgcmV0dXJuIGdldE1hcERhdGEodGhpcywga2V5KS5oYXMoa2V5KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIG1hcCBga2V5YCB0byBgdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAbmFtZSBzZXQKICAgICAgICAgKiBAbWVtYmVyT2YgTWFwQ2FjaGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIHNldC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbWFwIGNhY2hlIGluc3RhbmNlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1hcENhY2hlU2V0KGtleSwgdmFsdWUpIHsKICAgICAgICAgIHZhciBkYXRhID0gZ2V0TWFwRGF0YSh0aGlzLCBrZXkpLAogICAgICAgICAgICAgIHNpemUgPSBkYXRhLnNpemU7CgogICAgICAgICAgZGF0YS5zZXQoa2V5LCB2YWx1ZSk7CiAgICAgICAgICB0aGlzLnNpemUgKz0gZGF0YS5zaXplID09IHNpemUgPyAwIDogMTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KCiAgICAgICAgLy8gQWRkIG1ldGhvZHMgdG8gYE1hcENhY2hlYC4KICAgICAgICBNYXBDYWNoZS5wcm90b3R5cGUuY2xlYXIgPSBtYXBDYWNoZUNsZWFyOwogICAgICAgIE1hcENhY2hlLnByb3RvdHlwZVsnZGVsZXRlJ10gPSBtYXBDYWNoZURlbGV0ZTsKICAgICAgICBNYXBDYWNoZS5wcm90b3R5cGUuZ2V0ID0gbWFwQ2FjaGVHZXQ7CiAgICAgICAgTWFwQ2FjaGUucHJvdG90eXBlLmhhcyA9IG1hcENhY2hlSGFzOwogICAgICAgIE1hcENhY2hlLnByb3RvdHlwZS5zZXQgPSBtYXBDYWNoZVNldDsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgY2FjaGUgb2JqZWN0IHRvIHN0b3JlIHVuaXF1ZSB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFt2YWx1ZXNdIFRoZSB2YWx1ZXMgdG8gY2FjaGUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gU2V0Q2FjaGUodmFsdWVzKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSB2YWx1ZXMgPT0gbnVsbCA/IDAgOiB2YWx1ZXMubGVuZ3RoOwoKICAgICAgICAgIHRoaXMuX19kYXRhX18gPSBuZXcgTWFwQ2FjaGU7CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB0aGlzLmFkZCh2YWx1ZXNbaW5kZXhdKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYHZhbHVlYCB0byB0aGUgYXJyYXkgY2FjaGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGFkZAogICAgICAgICAqIEBtZW1iZXJPZiBTZXRDYWNoZQogICAgICAgICAqIEBhbGlhcyBwdXNoCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2FjaGUuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY2FjaGUgaW5zdGFuY2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc2V0Q2FjaGVBZGQodmFsdWUpIHsKICAgICAgICAgIHRoaXMuX19kYXRhX18uc2V0KHZhbHVlLCBIQVNIX1VOREVGSU5FRCk7CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGluIHRoZSBhcnJheSBjYWNoZS4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgaGFzCiAgICAgICAgICogQG1lbWJlck9mIFNldENhY2hlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2VhcmNoIGZvci4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGZvdW5kLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc2V0Q2FjaGVIYXModmFsdWUpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9fZGF0YV9fLmhhcyh2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvLyBBZGQgbWV0aG9kcyB0byBgU2V0Q2FjaGVgLgogICAgICAgIFNldENhY2hlLnByb3RvdHlwZS5hZGQgPSBTZXRDYWNoZS5wcm90b3R5cGUucHVzaCA9IHNldENhY2hlQWRkOwogICAgICAgIFNldENhY2hlLnByb3RvdHlwZS5oYXMgPSBzZXRDYWNoZUhhczsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc3RhY2sgY2FjaGUgb2JqZWN0IHRvIHN0b3JlIGtleS12YWx1ZSBwYWlycy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW2VudHJpZXNdIFRoZSBrZXktdmFsdWUgcGFpcnMgdG8gY2FjaGUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gU3RhY2soZW50cmllcykgewogICAgICAgICAgdmFyIGRhdGEgPSB0aGlzLl9fZGF0YV9fID0gbmV3IExpc3RDYWNoZShlbnRyaWVzKTsKICAgICAgICAgIHRoaXMuc2l6ZSA9IGRhdGEuc2l6ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIHN0YWNrLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAbmFtZSBjbGVhcgogICAgICAgICAqIEBtZW1iZXJPZiBTdGFjawogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0YWNrQ2xlYXIoKSB7CiAgICAgICAgICB0aGlzLl9fZGF0YV9fID0gbmV3IExpc3RDYWNoZTsKICAgICAgICAgIHRoaXMuc2l6ZSA9IDA7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGBrZXlgIGFuZCBpdHMgdmFsdWUgZnJvbSB0aGUgc3RhY2suCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGRlbGV0ZQogICAgICAgICAqIEBtZW1iZXJPZiBTdGFjawogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gcmVtb3ZlLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgZW50cnkgd2FzIHJlbW92ZWQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzdGFja0RlbGV0ZShrZXkpIHsKICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXywKICAgICAgICAgICAgICByZXN1bHQgPSBkYXRhWydkZWxldGUnXShrZXkpOwoKICAgICAgICAgIHRoaXMuc2l6ZSA9IGRhdGEuc2l6ZTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBzdGFjayB2YWx1ZSBmb3IgYGtleWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBuYW1lIGdldAogICAgICAgICAqIEBtZW1iZXJPZiBTdGFjawogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBlbnRyeSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzdGFja0dldChrZXkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9fZGF0YV9fLmdldChrZXkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGEgc3RhY2sgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQG5hbWUgaGFzCiAgICAgICAgICogQG1lbWJlck9mIFN0YWNrCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBlbnRyeSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYW4gZW50cnkgZm9yIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0YWNrSGFzKGtleSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX19kYXRhX18uaGFzKGtleSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBzdGFjayBga2V5YCB0byBgdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAbmFtZSBzZXQKICAgICAgICAgKiBAbWVtYmVyT2YgU3RhY2sKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIHNldC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgc3RhY2sgY2FjaGUgaW5zdGFuY2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc3RhY2tTZXQoa2V5LCB2YWx1ZSkgewogICAgICAgICAgdmFyIGRhdGEgPSB0aGlzLl9fZGF0YV9fOwogICAgICAgICAgaWYgKGRhdGEgaW5zdGFuY2VvZiBMaXN0Q2FjaGUpIHsKICAgICAgICAgICAgdmFyIHBhaXJzID0gZGF0YS5fX2RhdGFfXzsKICAgICAgICAgICAgaWYgKCFNYXAgfHwgKHBhaXJzLmxlbmd0aCA8IExBUkdFX0FSUkFZX1NJWkUgLSAxKSkgewogICAgICAgICAgICAgIHBhaXJzLnB1c2goW2tleSwgdmFsdWVdKTsKICAgICAgICAgICAgICB0aGlzLnNpemUgPSArK2RhdGEuc2l6ZTsKICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgICAgICBkYXRhID0gdGhpcy5fX2RhdGFfXyA9IG5ldyBNYXBDYWNoZShwYWlycyk7CiAgICAgICAgICB9CiAgICAgICAgICBkYXRhLnNldChrZXksIHZhbHVlKTsKICAgICAgICAgIHRoaXMuc2l6ZSA9IGRhdGEuc2l6ZTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KCiAgICAgICAgLy8gQWRkIG1ldGhvZHMgdG8gYFN0YWNrYC4KICAgICAgICBTdGFjay5wcm90b3R5cGUuY2xlYXIgPSBzdGFja0NsZWFyOwogICAgICAgIFN0YWNrLnByb3RvdHlwZVsnZGVsZXRlJ10gPSBzdGFja0RlbGV0ZTsKICAgICAgICBTdGFjay5wcm90b3R5cGUuZ2V0ID0gc3RhY2tHZXQ7CiAgICAgICAgU3RhY2sucHJvdG90eXBlLmhhcyA9IHN0YWNrSGFzOwogICAgICAgIFN0YWNrLnByb3RvdHlwZS5zZXQgPSBzdGFja1NldDsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHRoZSBlbnVtZXJhYmxlIHByb3BlcnR5IG5hbWVzIG9mIHRoZSBhcnJheS1saWtlIGB2YWx1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaW5oZXJpdGVkIFNwZWNpZnkgcmV0dXJuaW5nIGluaGVyaXRlZCBwcm9wZXJ0eSBuYW1lcy4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGFycmF5TGlrZUtleXModmFsdWUsIGluaGVyaXRlZCkgewogICAgICAgICAgdmFyIGlzQXJyID0gaXNBcnJheSh2YWx1ZSksCiAgICAgICAgICAgICAgaXNBcmcgPSAhaXNBcnIgJiYgaXNBcmd1bWVudHModmFsdWUpLAogICAgICAgICAgICAgIGlzQnVmZiA9ICFpc0FyciAmJiAhaXNBcmcgJiYgaXNCdWZmZXIodmFsdWUpLAogICAgICAgICAgICAgIGlzVHlwZSA9ICFpc0FyciAmJiAhaXNBcmcgJiYgIWlzQnVmZiAmJiBpc1R5cGVkQXJyYXkodmFsdWUpLAogICAgICAgICAgICAgIHNraXBJbmRleGVzID0gaXNBcnIgfHwgaXNBcmcgfHwgaXNCdWZmIHx8IGlzVHlwZSwKICAgICAgICAgICAgICByZXN1bHQgPSBza2lwSW5kZXhlcyA/IGJhc2VUaW1lcyh2YWx1ZS5sZW5ndGgsIFN0cmluZykgOiBbXSwKICAgICAgICAgICAgICBsZW5ndGggPSByZXN1bHQubGVuZ3RoOwoKICAgICAgICAgIGZvciAodmFyIGtleSBpbiB2YWx1ZSkgewogICAgICAgICAgICBpZiAoKGluaGVyaXRlZCB8fCBoYXNPd25Qcm9wZXJ0eS5jYWxsKHZhbHVlLCBrZXkpKSAmJgogICAgICAgICAgICAgICAgIShza2lwSW5kZXhlcyAmJiAoCiAgICAgICAgICAgICAgICAgICAvLyBTYWZhcmkgOSBoYXMgZW51bWVyYWJsZSBgYXJndW1lbnRzLmxlbmd0aGAgaW4gc3RyaWN0IG1vZGUuCiAgICAgICAgICAgICAgICAgICBrZXkgPT0gJ2xlbmd0aCcgfHwKICAgICAgICAgICAgICAgICAgIC8vIE5vZGUuanMgMC4xMCBoYXMgZW51bWVyYWJsZSBub24taW5kZXggcHJvcGVydGllcyBvbiBidWZmZXJzLgogICAgICAgICAgICAgICAgICAgKGlzQnVmZiAmJiAoa2V5ID09ICdvZmZzZXQnIHx8IGtleSA9PSAncGFyZW50JykpIHx8CiAgICAgICAgICAgICAgICAgICAvLyBQaGFudG9tSlMgMiBoYXMgZW51bWVyYWJsZSBub24taW5kZXggcHJvcGVydGllcyBvbiB0eXBlZCBhcnJheXMuCiAgICAgICAgICAgICAgICAgICAoaXNUeXBlICYmIChrZXkgPT0gJ2J1ZmZlcicgfHwga2V5ID09ICdieXRlTGVuZ3RoJyB8fCBrZXkgPT0gJ2J5dGVPZmZzZXQnKSkgfHwKICAgICAgICAgICAgICAgICAgIC8vIFNraXAgaW5kZXggcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgIGlzSW5kZXgoa2V5LCBsZW5ndGgpCiAgICAgICAgICAgICAgICApKSkgewogICAgICAgICAgICAgIHJlc3VsdC5wdXNoKGtleSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uc2FtcGxlYCBmb3IgYXJyYXlzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gc2FtcGxlLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByYW5kb20gZWxlbWVudC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBhcnJheVNhbXBsZShhcnJheSkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIHJldHVybiBsZW5ndGggPyBhcnJheVtiYXNlUmFuZG9tKDAsIGxlbmd0aCAtIDEpXSA6IHVuZGVmaW5lZCQxOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLnNhbXBsZVNpemVgIGZvciBhcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBzYW1wbGUuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IG4gVGhlIG51bWJlciBvZiBlbGVtZW50cyB0byBzYW1wbGUuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSByYW5kb20gZWxlbWVudHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYXJyYXlTYW1wbGVTaXplKGFycmF5LCBuKSB7CiAgICAgICAgICByZXR1cm4gc2h1ZmZsZVNlbGYoY29weUFycmF5KGFycmF5KSwgYmFzZUNsYW1wKG4sIDAsIGFycmF5Lmxlbmd0aCkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLnNodWZmbGVgIGZvciBhcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBzaHVmZmxlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IHNodWZmbGVkIGFycmF5LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGFycmF5U2h1ZmZsZShhcnJheSkgewogICAgICAgICAgcmV0dXJuIHNodWZmbGVTZWxmKGNvcHlBcnJheShhcnJheSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBmdW5jdGlvbiBpcyBsaWtlIGBhc3NpZ25WYWx1ZWAgZXhjZXB0IHRoYXQgaXQgZG9lc24ndCBhc3NpZ24KICAgICAgICAgKiBgdW5kZWZpbmVkYCB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBhc3NpZ24uCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gYXNzaWduLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGFzc2lnbk1lcmdlVmFsdWUob2JqZWN0LCBrZXksIHZhbHVlKSB7CiAgICAgICAgICBpZiAoKHZhbHVlICE9PSB1bmRlZmluZWQkMSAmJiAhZXEob2JqZWN0W2tleV0sIHZhbHVlKSkgfHwKICAgICAgICAgICAgICAodmFsdWUgPT09IHVuZGVmaW5lZCQxICYmICEoa2V5IGluIG9iamVjdCkpKSB7CiAgICAgICAgICAgIGJhc2VBc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgdmFsdWUpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQXNzaWducyBgdmFsdWVgIHRvIGBrZXlgIG9mIGBvYmplY3RgIGlmIHRoZSBleGlzdGluZyB2YWx1ZSBpcyBub3QgZXF1aXZhbGVudAogICAgICAgICAqIHVzaW5nIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgcHJvcGVydHkgdG8gYXNzaWduLgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGFzc2lnbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBhc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgdmFsdWUpIHsKICAgICAgICAgIHZhciBvYmpWYWx1ZSA9IG9iamVjdFtrZXldOwogICAgICAgICAgaWYgKCEoaGFzT3duUHJvcGVydHkuY2FsbChvYmplY3QsIGtleSkgJiYgZXEob2JqVmFsdWUsIHZhbHVlKSkgfHwKICAgICAgICAgICAgICAodmFsdWUgPT09IHVuZGVmaW5lZCQxICYmICEoa2V5IGluIG9iamVjdCkpKSB7CiAgICAgICAgICAgIGJhc2VBc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgdmFsdWUpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgaW5kZXggYXQgd2hpY2ggdGhlIGBrZXlgIGlzIGZvdW5kIGluIGBhcnJheWAgb2Yga2V5LXZhbHVlIHBhaXJzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IGtleSBUaGUga2V5IHRvIHNlYXJjaCBmb3IuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBhc3NvY0luZGV4T2YoYXJyYXksIGtleSkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICBpZiAoZXEoYXJyYXlbbGVuZ3RoXVswXSwga2V5KSkgewogICAgICAgICAgICAgIHJldHVybiBsZW5ndGg7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEFnZ3JlZ2F0ZXMgZWxlbWVudHMgb2YgYGNvbGxlY3Rpb25gIG9uIGBhY2N1bXVsYXRvcmAgd2l0aCBrZXlzIHRyYW5zZm9ybWVkCiAgICAgICAgICogYnkgYGl0ZXJhdGVlYCBhbmQgdmFsdWVzIHNldCBieSBgc2V0dGVyYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHNldHRlciBUaGUgZnVuY3Rpb24gdG8gc2V0IGBhY2N1bXVsYXRvcmAgdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBpdGVyYXRlZSB0byB0cmFuc2Zvcm0ga2V5cy4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gYWNjdW11bGF0b3IgVGhlIGluaXRpYWwgYWdncmVnYXRlZCBvYmplY3QuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIGBhY2N1bXVsYXRvcmAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUFnZ3JlZ2F0b3IoY29sbGVjdGlvbiwgc2V0dGVyLCBpdGVyYXRlZSwgYWNjdW11bGF0b3IpIHsKICAgICAgICAgIGJhc2VFYWNoKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBrZXksIGNvbGxlY3Rpb24pIHsKICAgICAgICAgICAgc2V0dGVyKGFjY3VtdWxhdG9yLCB2YWx1ZSwgaXRlcmF0ZWUodmFsdWUpLCBjb2xsZWN0aW9uKTsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIGFjY3VtdWxhdG9yOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uYXNzaWduYCB3aXRob3V0IHN1cHBvcnQgZm9yIG11bHRpcGxlIHNvdXJjZXMKICAgICAgICAgKiBvciBgY3VzdG9taXplcmAgZnVuY3Rpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgc291cmNlIG9iamVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VBc3NpZ24ob2JqZWN0LCBzb3VyY2UpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgJiYgY29weU9iamVjdChzb3VyY2UsIGtleXMoc291cmNlKSwgb2JqZWN0KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmFzc2lnbkluYCB3aXRob3V0IHN1cHBvcnQgZm9yIG11bHRpcGxlIHNvdXJjZXMKICAgICAgICAgKiBvciBgY3VzdG9taXplcmAgZnVuY3Rpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgc291cmNlIG9iamVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VBc3NpZ25JbihvYmplY3QsIHNvdXJjZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCAmJiBjb3B5T2JqZWN0KHNvdXJjZSwga2V5c0luKHNvdXJjZSksIG9iamVjdCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgYXNzaWduVmFsdWVgIGFuZCBgYXNzaWduTWVyZ2VWYWx1ZWAgd2l0aG91dAogICAgICAgICAqIHZhbHVlIGNoZWNrcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIGFzc2lnbi4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBhc3NpZ24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCB2YWx1ZSkgewogICAgICAgICAgaWYgKGtleSA9PSAnX19wcm90b19fJyAmJiBkZWZpbmVQcm9wZXJ0eSkgewogICAgICAgICAgICBkZWZpbmVQcm9wZXJ0eShvYmplY3QsIGtleSwgewogICAgICAgICAgICAgICdjb25maWd1cmFibGUnOiB0cnVlLAogICAgICAgICAgICAgICdlbnVtZXJhYmxlJzogdHJ1ZSwKICAgICAgICAgICAgICAndmFsdWUnOiB2YWx1ZSwKICAgICAgICAgICAgICAnd3JpdGFibGUnOiB0cnVlCiAgICAgICAgICAgIH0pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgb2JqZWN0W2tleV0gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmF0YCB3aXRob3V0IHN1cHBvcnQgZm9yIGluZGl2aWR1YWwgcGF0aHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmdbXX0gcGF0aHMgVGhlIHByb3BlcnR5IHBhdGhzIHRvIHBpY2suCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBwaWNrZWQgZWxlbWVudHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUF0KG9iamVjdCwgcGF0aHMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IHBhdGhzLmxlbmd0aCwKICAgICAgICAgICAgICByZXN1bHQgPSBBcnJheShsZW5ndGgpLAogICAgICAgICAgICAgIHNraXAgPSBvYmplY3QgPT0gbnVsbDsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICByZXN1bHRbaW5kZXhdID0gc2tpcCA/IHVuZGVmaW5lZCQxIDogZ2V0KG9iamVjdCwgcGF0aHNbaW5kZXhdKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5jbGFtcGAgd2hpY2ggZG9lc24ndCBjb2VyY2UgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbnVtYmVyIFRoZSBudW1iZXIgdG8gY2xhbXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtsb3dlcl0gVGhlIGxvd2VyIGJvdW5kLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSB1cHBlciBUaGUgdXBwZXIgYm91bmQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY2xhbXBlZCBudW1iZXIuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUNsYW1wKG51bWJlciwgbG93ZXIsIHVwcGVyKSB7CiAgICAgICAgICBpZiAobnVtYmVyID09PSBudW1iZXIpIHsKICAgICAgICAgICAgaWYgKHVwcGVyICE9PSB1bmRlZmluZWQkMSkgewogICAgICAgICAgICAgIG51bWJlciA9IG51bWJlciA8PSB1cHBlciA/IG51bWJlciA6IHVwcGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChsb3dlciAhPT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICBudW1iZXIgPSBudW1iZXIgPj0gbG93ZXIgPyBudW1iZXIgOiBsb3dlcjsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG51bWJlcjsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmNsb25lYCBhbmQgYF8uY2xvbmVEZWVwYCB3aGljaCB0cmFja3MKICAgICAgICAgKiB0cmF2ZXJzZWQgb2JqZWN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2xvbmUuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBiaXRtYXNrIFRoZSBiaXRtYXNrIGZsYWdzLgogICAgICAgICAqICAxIC0gRGVlcCBjbG9uZQogICAgICAgICAqICAyIC0gRmxhdHRlbiBpbmhlcml0ZWQgcHJvcGVydGllcwogICAgICAgICAqICA0IC0gQ2xvbmUgc3ltYm9scwogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNsb25pbmcuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtrZXldIFRoZSBrZXkgb2YgYHZhbHVlYC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29iamVjdF0gVGhlIHBhcmVudCBvYmplY3Qgb2YgYHZhbHVlYC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIG9iamVjdHMgYW5kIHRoZWlyIGNsb25lIGNvdW50ZXJwYXJ0cy4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgY2xvbmVkIHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VDbG9uZSh2YWx1ZSwgYml0bWFzaywgY3VzdG9taXplciwga2V5LCBvYmplY3QsIHN0YWNrKSB7CiAgICAgICAgICB2YXIgcmVzdWx0LAogICAgICAgICAgICAgIGlzRGVlcCA9IGJpdG1hc2sgJiBDTE9ORV9ERUVQX0ZMQUcsCiAgICAgICAgICAgICAgaXNGbGF0ID0gYml0bWFzayAmIENMT05FX0ZMQVRfRkxBRywKICAgICAgICAgICAgICBpc0Z1bGwgPSBiaXRtYXNrICYgQ0xPTkVfU1lNQk9MU19GTEFHOwoKICAgICAgICAgIGlmIChjdXN0b21pemVyKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IG9iamVjdCA/IGN1c3RvbWl6ZXIodmFsdWUsIGtleSwgb2JqZWN0LCBzdGFjaykgOiBjdXN0b21pemVyKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChyZXN1bHQgIT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoIWlzT2JqZWN0KHZhbHVlKSkgewogICAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgaXNBcnIgPSBpc0FycmF5KHZhbHVlKTsKICAgICAgICAgIGlmIChpc0FycikgewogICAgICAgICAgICByZXN1bHQgPSBpbml0Q2xvbmVBcnJheSh2YWx1ZSk7CiAgICAgICAgICAgIGlmICghaXNEZWVwKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGNvcHlBcnJheSh2YWx1ZSwgcmVzdWx0KTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdmFyIHRhZyA9IGdldFRhZyh2YWx1ZSksCiAgICAgICAgICAgICAgICBpc0Z1bmMgPSB0YWcgPT0gZnVuY1RhZyB8fCB0YWcgPT0gZ2VuVGFnOwoKICAgICAgICAgICAgaWYgKGlzQnVmZmVyKHZhbHVlKSkgewogICAgICAgICAgICAgIHJldHVybiBjbG9uZUJ1ZmZlcih2YWx1ZSwgaXNEZWVwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGFnID09IG9iamVjdFRhZyB8fCB0YWcgPT0gYXJnc1RhZyB8fCAoaXNGdW5jICYmICFvYmplY3QpKSB7CiAgICAgICAgICAgICAgcmVzdWx0ID0gKGlzRmxhdCB8fCBpc0Z1bmMpID8ge30gOiBpbml0Q2xvbmVPYmplY3QodmFsdWUpOwogICAgICAgICAgICAgIGlmICghaXNEZWVwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gaXNGbGF0CiAgICAgICAgICAgICAgICAgID8gY29weVN5bWJvbHNJbih2YWx1ZSwgYmFzZUFzc2lnbkluKHJlc3VsdCwgdmFsdWUpKQogICAgICAgICAgICAgICAgICA6IGNvcHlTeW1ib2xzKHZhbHVlLCBiYXNlQXNzaWduKHJlc3VsdCwgdmFsdWUpKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgaWYgKCFjbG9uZWFibGVUYWdzW3RhZ10pIHsKICAgICAgICAgICAgICAgIHJldHVybiBvYmplY3QgPyB2YWx1ZSA6IHt9OwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXN1bHQgPSBpbml0Q2xvbmVCeVRhZyh2YWx1ZSwgdGFnLCBpc0RlZXApOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDaGVjayBmb3IgY2lyY3VsYXIgcmVmZXJlbmNlcyBhbmQgcmV0dXJuIGl0cyBjb3JyZXNwb25kaW5nIGNsb25lLgogICAgICAgICAgc3RhY2sgfHwgKHN0YWNrID0gbmV3IFN0YWNrKTsKICAgICAgICAgIHZhciBzdGFja2VkID0gc3RhY2suZ2V0KHZhbHVlKTsKICAgICAgICAgIGlmIChzdGFja2VkKSB7CiAgICAgICAgICAgIHJldHVybiBzdGFja2VkOwogICAgICAgICAgfQogICAgICAgICAgc3RhY2suc2V0KHZhbHVlLCByZXN1bHQpOwoKICAgICAgICAgIGlmIChpc1NldCh2YWx1ZSkpIHsKICAgICAgICAgICAgdmFsdWUuZm9yRWFjaChmdW5jdGlvbihzdWJWYWx1ZSkgewogICAgICAgICAgICAgIHJlc3VsdC5hZGQoYmFzZUNsb25lKHN1YlZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdWJWYWx1ZSwgdmFsdWUsIHN0YWNrKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfSBlbHNlIGlmIChpc01hcCh2YWx1ZSkpIHsKICAgICAgICAgICAgdmFsdWUuZm9yRWFjaChmdW5jdGlvbihzdWJWYWx1ZSwga2V5KSB7CiAgICAgICAgICAgICAgcmVzdWx0LnNldChrZXksIGJhc2VDbG9uZShzdWJWYWx1ZSwgYml0bWFzaywgY3VzdG9taXplciwga2V5LCB2YWx1ZSwgc3RhY2spKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CgogICAgICAgICAgdmFyIGtleXNGdW5jID0gaXNGdWxsCiAgICAgICAgICAgID8gKGlzRmxhdCA/IGdldEFsbEtleXNJbiA6IGdldEFsbEtleXMpCiAgICAgICAgICAgIDogKGlzRmxhdCA/IGtleXNJbiA6IGtleXMpOwoKICAgICAgICAgIHZhciBwcm9wcyA9IGlzQXJyID8gdW5kZWZpbmVkJDEgOiBrZXlzRnVuYyh2YWx1ZSk7CiAgICAgICAgICBhcnJheUVhY2gocHJvcHMgfHwgdmFsdWUsIGZ1bmN0aW9uKHN1YlZhbHVlLCBrZXkpIHsKICAgICAgICAgICAgaWYgKHByb3BzKSB7CiAgICAgICAgICAgICAga2V5ID0gc3ViVmFsdWU7CiAgICAgICAgICAgICAgc3ViVmFsdWUgPSB2YWx1ZVtrZXldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFJlY3Vyc2l2ZWx5IHBvcHVsYXRlIGNsb25lIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgICAgIGFzc2lnblZhbHVlKHJlc3VsdCwga2V5LCBiYXNlQ2xvbmUoc3ViVmFsdWUsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGtleSwgdmFsdWUsIHN0YWNrKSk7CiAgICAgICAgICB9KTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5jb25mb3Jtc2Agd2hpY2ggZG9lc24ndCBjbG9uZSBgc291cmNlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IG9mIHByb3BlcnR5IHByZWRpY2F0ZXMgdG8gY29uZm9ybSB0by4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBzcGVjIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VDb25mb3Jtcyhzb3VyY2UpIHsKICAgICAgICAgIHZhciBwcm9wcyA9IGtleXMoc291cmNlKTsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICAgICAgcmV0dXJuIGJhc2VDb25mb3Jtc1RvKG9iamVjdCwgc291cmNlLCBwcm9wcyk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uY29uZm9ybXNUb2Agd2hpY2ggYWNjZXB0cyBgcHJvcHNgIHRvIGNoZWNrLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3Qgb2YgcHJvcGVydHkgcHJlZGljYXRlcyB0byBjb25mb3JtIHRvLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgb2JqZWN0YCBjb25mb3JtcywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VDb25mb3Jtc1RvKG9iamVjdCwgc291cmNlLCBwcm9wcykgewogICAgICAgICAgdmFyIGxlbmd0aCA9IHByb3BzLmxlbmd0aDsKICAgICAgICAgIGlmIChvYmplY3QgPT0gbnVsbCkgewogICAgICAgICAgICByZXR1cm4gIWxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIG9iamVjdCA9IE9iamVjdChvYmplY3QpOwogICAgICAgICAgd2hpbGUgKGxlbmd0aC0tKSB7CiAgICAgICAgICAgIHZhciBrZXkgPSBwcm9wc1tsZW5ndGhdLAogICAgICAgICAgICAgICAgcHJlZGljYXRlID0gc291cmNlW2tleV0sCiAgICAgICAgICAgICAgICB2YWx1ZSA9IG9iamVjdFtrZXldOwoKICAgICAgICAgICAgaWYgKCh2YWx1ZSA9PT0gdW5kZWZpbmVkJDEgJiYgIShrZXkgaW4gb2JqZWN0KSkgfHwgIXByZWRpY2F0ZSh2YWx1ZSkpIHsKICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZGVsYXlgIGFuZCBgXy5kZWZlcmAgd2hpY2ggYWNjZXB0cyBgYXJnc2AKICAgICAgICAgKiB0byBwcm92aWRlIHRvIGBmdW5jYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gZGVsYXkuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHdhaXQgVGhlIG51bWJlciBvZiBtaWxsaXNlY29uZHMgdG8gZGVsYXkgaW52b2NhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcmdzIFRoZSBhcmd1bWVudHMgdG8gcHJvdmlkZSB0byBgZnVuY2AuCiAgICAgICAgICogQHJldHVybnMge251bWJlcnxPYmplY3R9IFJldHVybnMgdGhlIHRpbWVyIGlkIG9yIHRpbWVvdXQgb2JqZWN0LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VEZWxheShmdW5jLCB3YWl0LCBhcmdzKSB7CiAgICAgICAgICBpZiAodHlwZW9mIGZ1bmMgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKEZVTkNfRVJST1JfVEVYVCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gc2V0VGltZW91dChmdW5jdGlvbigpIHsgZnVuYy5hcHBseSh1bmRlZmluZWQkMSwgYXJncyk7IH0sIHdhaXQpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgbWV0aG9kcyBsaWtlIGBfLmRpZmZlcmVuY2VgIHdpdGhvdXQgc3VwcG9ydAogICAgICAgICAqIGZvciBleGNsdWRpbmcgbXVsdGlwbGUgYXJyYXlzIG9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHZhbHVlcyBUaGUgdmFsdWVzIHRvIGV4Y2x1ZGUuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlXSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBmaWx0ZXJlZCB2YWx1ZXMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZURpZmZlcmVuY2UoYXJyYXksIHZhbHVlcywgaXRlcmF0ZWUsIGNvbXBhcmF0b3IpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGluY2x1ZGVzID0gYXJyYXlJbmNsdWRlcywKICAgICAgICAgICAgICBpc0NvbW1vbiA9IHRydWUsCiAgICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIHJlc3VsdCA9IFtdLAogICAgICAgICAgICAgIHZhbHVlc0xlbmd0aCA9IHZhbHVlcy5sZW5ndGg7CgogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChpdGVyYXRlZSkgewogICAgICAgICAgICB2YWx1ZXMgPSBhcnJheU1hcCh2YWx1ZXMsIGJhc2VVbmFyeShpdGVyYXRlZSkpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGNvbXBhcmF0b3IpIHsKICAgICAgICAgICAgaW5jbHVkZXMgPSBhcnJheUluY2x1ZGVzV2l0aDsKICAgICAgICAgICAgaXNDb21tb24gPSBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIGVsc2UgaWYgKHZhbHVlcy5sZW5ndGggPj0gTEFSR0VfQVJSQVlfU0laRSkgewogICAgICAgICAgICBpbmNsdWRlcyA9IGNhY2hlSGFzOwogICAgICAgICAgICBpc0NvbW1vbiA9IGZhbHNlOwogICAgICAgICAgICB2YWx1ZXMgPSBuZXcgU2V0Q2FjaGUodmFsdWVzKTsKICAgICAgICAgIH0KICAgICAgICAgIG91dGVyOgogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdLAogICAgICAgICAgICAgICAgY29tcHV0ZWQgPSBpdGVyYXRlZSA9PSBudWxsID8gdmFsdWUgOiBpdGVyYXRlZSh2YWx1ZSk7CgogICAgICAgICAgICB2YWx1ZSA9IChjb21wYXJhdG9yIHx8IHZhbHVlICE9PSAwKSA/IHZhbHVlIDogMDsKICAgICAgICAgICAgaWYgKGlzQ29tbW9uICYmIGNvbXB1dGVkID09PSBjb21wdXRlZCkgewogICAgICAgICAgICAgIHZhciB2YWx1ZXNJbmRleCA9IHZhbHVlc0xlbmd0aDsKICAgICAgICAgICAgICB3aGlsZSAodmFsdWVzSW5kZXgtLSkgewogICAgICAgICAgICAgICAgaWYgKHZhbHVlc1t2YWx1ZXNJbmRleF0gPT09IGNvbXB1dGVkKSB7CiAgICAgICAgICAgICAgICAgIGNvbnRpbnVlIG91dGVyOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXN1bHQucHVzaCh2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoIWluY2x1ZGVzKHZhbHVlcywgY29tcHV0ZWQsIGNvbXBhcmF0b3IpKSB7CiAgICAgICAgICAgICAgcmVzdWx0LnB1c2godmFsdWUpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZm9yRWFjaGAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl8T2JqZWN0fSBSZXR1cm5zIGBjb2xsZWN0aW9uYC4KICAgICAgICAgKi8KICAgICAgICB2YXIgYmFzZUVhY2ggPSBjcmVhdGVCYXNlRWFjaChiYXNlRm9yT3duKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZm9yRWFjaFJpZ2h0YCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheXxPYmplY3R9IFJldHVybnMgYGNvbGxlY3Rpb25gLgogICAgICAgICAqLwogICAgICAgIHZhciBiYXNlRWFjaFJpZ2h0ID0gY3JlYXRlQmFzZUVhY2goYmFzZUZvck93blJpZ2h0LCB0cnVlKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZXZlcnlgIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbGwgZWxlbWVudHMgcGFzcyB0aGUgcHJlZGljYXRlIGNoZWNrLAogICAgICAgICAqICBlbHNlIGBmYWxzZWAKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlRXZlcnkoY29sbGVjdGlvbiwgcHJlZGljYXRlKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gdHJ1ZTsKICAgICAgICAgIGJhc2VFYWNoKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBpbmRleCwgY29sbGVjdGlvbikgewogICAgICAgICAgICByZXN1bHQgPSAhIXByZWRpY2F0ZSh2YWx1ZSwgaW5kZXgsIGNvbGxlY3Rpb24pOwogICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgfSk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgbWV0aG9kcyBsaWtlIGBfLm1heGAgYW5kIGBfLm1pbmAgd2hpY2ggYWNjZXB0cyBhCiAgICAgICAgICogYGNvbXBhcmF0b3JgIHRvIGRldGVybWluZSB0aGUgZXh0cmVtdW0gdmFsdWUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjb21wYXJhdG9yIFRoZSBjb21wYXJhdG9yIHVzZWQgdG8gY29tcGFyZSB2YWx1ZXMuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGV4dHJlbXVtIHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VFeHRyZW11bShhcnJheSwgaXRlcmF0ZWUsIGNvbXBhcmF0b3IpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF0sCiAgICAgICAgICAgICAgICBjdXJyZW50ID0gaXRlcmF0ZWUodmFsdWUpOwoKICAgICAgICAgICAgaWYgKGN1cnJlbnQgIT0gbnVsbCAmJiAoY29tcHV0ZWQgPT09IHVuZGVmaW5lZCQxCiAgICAgICAgICAgICAgICAgID8gKGN1cnJlbnQgPT09IGN1cnJlbnQgJiYgIWlzU3ltYm9sKGN1cnJlbnQpKQogICAgICAgICAgICAgICAgICA6IGNvbXBhcmF0b3IoY3VycmVudCwgY29tcHV0ZWQpCiAgICAgICAgICAgICAgICApKSB7CiAgICAgICAgICAgICAgdmFyIGNvbXB1dGVkID0gY3VycmVudCwKICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gdmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5maWxsYCB3aXRob3V0IGFuIGl0ZXJhdGVlIGNhbGwgZ3VhcmQuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBmaWxsLgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGZpbGwgYGFycmF5YCB3aXRoLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbc3RhcnQ9MF0gVGhlIHN0YXJ0IHBvc2l0aW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZW5kPWFycmF5Lmxlbmd0aF0gVGhlIGVuZCBwb3NpdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlRmlsbChhcnJheSwgdmFsdWUsIHN0YXJ0LCBlbmQpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICAgICAgc3RhcnQgPSB0b0ludGVnZXIoc3RhcnQpOwogICAgICAgICAgaWYgKHN0YXJ0IDwgMCkgewogICAgICAgICAgICBzdGFydCA9IC1zdGFydCA+IGxlbmd0aCA/IDAgOiAobGVuZ3RoICsgc3RhcnQpOwogICAgICAgICAgfQogICAgICAgICAgZW5kID0gKGVuZCA9PT0gdW5kZWZpbmVkJDEgfHwgZW5kID4gbGVuZ3RoKSA/IGxlbmd0aCA6IHRvSW50ZWdlcihlbmQpOwogICAgICAgICAgaWYgKGVuZCA8IDApIHsKICAgICAgICAgICAgZW5kICs9IGxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIGVuZCA9IHN0YXJ0ID4gZW5kID8gMCA6IHRvTGVuZ3RoKGVuZCk7CiAgICAgICAgICB3aGlsZSAoc3RhcnQgPCBlbmQpIHsKICAgICAgICAgICAgYXJyYXlbc3RhcnQrK10gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBhcnJheTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmZpbHRlcmAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcHJlZGljYXRlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZmlsdGVyZWQgYXJyYXkuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUZpbHRlcihjb2xsZWN0aW9uLCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBbXTsKICAgICAgICAgIGJhc2VFYWNoKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBpbmRleCwgY29sbGVjdGlvbikgewogICAgICAgICAgICBpZiAocHJlZGljYXRlKHZhbHVlLCBpbmRleCwgY29sbGVjdGlvbikpIHsKICAgICAgICAgICAgICByZXN1bHQucHVzaCh2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmZsYXR0ZW5gIHdpdGggc3VwcG9ydCBmb3IgcmVzdHJpY3RpbmcgZmxhdHRlbmluZy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGZsYXR0ZW4uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGRlcHRoIFRoZSBtYXhpbXVtIHJlY3Vyc2lvbiBkZXB0aC4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtwcmVkaWNhdGU9aXNGbGF0dGVuYWJsZV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpc1N0cmljdF0gUmVzdHJpY3QgdG8gdmFsdWVzIHRoYXQgcGFzcyBgcHJlZGljYXRlYCBjaGVja3MuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW3Jlc3VsdD1bXV0gVGhlIGluaXRpYWwgcmVzdWx0IHZhbHVlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZsYXR0ZW5lZCBhcnJheS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlRmxhdHRlbihhcnJheSwgZGVwdGgsIHByZWRpY2F0ZSwgaXNTdHJpY3QsIHJlc3VsdCkgewogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoOwoKICAgICAgICAgIHByZWRpY2F0ZSB8fCAocHJlZGljYXRlID0gaXNGbGF0dGVuYWJsZSk7CiAgICAgICAgICByZXN1bHQgfHwgKHJlc3VsdCA9IFtdKTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF07CiAgICAgICAgICAgIGlmIChkZXB0aCA+IDAgJiYgcHJlZGljYXRlKHZhbHVlKSkgewogICAgICAgICAgICAgIGlmIChkZXB0aCA+IDEpIHsKICAgICAgICAgICAgICAgIC8vIFJlY3Vyc2l2ZWx5IGZsYXR0ZW4gYXJyYXlzIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgICAgICAgICBiYXNlRmxhdHRlbih2YWx1ZSwgZGVwdGggLSAxLCBwcmVkaWNhdGUsIGlzU3RyaWN0LCByZXN1bHQpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBhcnJheVB1c2gocmVzdWx0LCB2YWx1ZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9IGVsc2UgaWYgKCFpc1N0cmljdCkgewogICAgICAgICAgICAgIHJlc3VsdFtyZXN1bHQubGVuZ3RoXSA9IHZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYGJhc2VGb3JPd25gIHdoaWNoIGl0ZXJhdGVzIG92ZXIgYG9iamVjdGAKICAgICAgICAgKiBwcm9wZXJ0aWVzIHJldHVybmVkIGJ5IGBrZXlzRnVuY2AgYW5kIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgZWFjaCBwcm9wZXJ0eS4KICAgICAgICAgKiBJdGVyYXRlZSBmdW5jdGlvbnMgbWF5IGV4aXQgaXRlcmF0aW9uIGVhcmx5IGJ5IGV4cGxpY2l0bHkgcmV0dXJuaW5nIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBrZXlzRnVuYyBUaGUgZnVuY3Rpb24gdG8gZ2V0IHRoZSBrZXlzIG9mIGBvYmplY3RgLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICovCiAgICAgICAgdmFyIGJhc2VGb3IgPSBjcmVhdGVCYXNlRm9yKCk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgZnVuY3Rpb24gaXMgbGlrZSBgYmFzZUZvcmAgZXhjZXB0IHRoYXQgaXQgaXRlcmF0ZXMgb3ZlciBwcm9wZXJ0aWVzCiAgICAgICAgICogaW4gdGhlIG9wcG9zaXRlIG9yZGVyLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0ga2V5c0Z1bmMgVGhlIGZ1bmN0aW9uIHRvIGdldCB0aGUga2V5cyBvZiBgb2JqZWN0YC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqLwogICAgICAgIHZhciBiYXNlRm9yUmlnaHQgPSBjcmVhdGVCYXNlRm9yKHRydWUpOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5mb3JPd25gIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUZvck93bihvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ICYmIGJhc2VGb3Iob2JqZWN0LCBpdGVyYXRlZSwga2V5cyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5mb3JPd25SaWdodGAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlRm9yT3duUmlnaHQob2JqZWN0LCBpdGVyYXRlZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCAmJiBiYXNlRm9yUmlnaHQob2JqZWN0LCBpdGVyYXRlZSwga2V5cyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5mdW5jdGlvbnNgIHdoaWNoIGNyZWF0ZXMgYW4gYXJyYXkgb2YKICAgICAgICAgKiBgb2JqZWN0YCBmdW5jdGlvbiBwcm9wZXJ0eSBuYW1lcyBmaWx0ZXJlZCBmcm9tIGBwcm9wc2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHByb3BzIFRoZSBwcm9wZXJ0eSBuYW1lcyB0byBmaWx0ZXIuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBmdW5jdGlvbiBuYW1lcy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlRnVuY3Rpb25zKG9iamVjdCwgcHJvcHMpIHsKICAgICAgICAgIHJldHVybiBhcnJheUZpbHRlcihwcm9wcywgZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgICAgIHJldHVybiBpc0Z1bmN0aW9uKG9iamVjdFtrZXldKTsKICAgICAgICAgIH0pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZ2V0YCB3aXRob3V0IHN1cHBvcnQgZm9yIGRlZmF1bHQgdmFsdWVzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgcmVzb2x2ZWQgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUdldChvYmplY3QsIHBhdGgpIHsKICAgICAgICAgIHBhdGggPSBjYXN0UGF0aChwYXRoLCBvYmplY3QpOwoKICAgICAgICAgIHZhciBpbmRleCA9IDAsCiAgICAgICAgICAgICAgbGVuZ3RoID0gcGF0aC5sZW5ndGg7CgogICAgICAgICAgd2hpbGUgKG9iamVjdCAhPSBudWxsICYmIGluZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIG9iamVjdCA9IG9iamVjdFt0b0tleShwYXRoW2luZGV4KytdKV07CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gKGluZGV4ICYmIGluZGV4ID09IGxlbmd0aCkgPyBvYmplY3QgOiB1bmRlZmluZWQkMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBnZXRBbGxLZXlzYCBhbmQgYGdldEFsbEtleXNJbmAgd2hpY2ggdXNlcwogICAgICAgICAqIGBrZXlzRnVuY2AgYW5kIGBzeW1ib2xzRnVuY2AgdG8gZ2V0IHRoZSBlbnVtZXJhYmxlIHByb3BlcnR5IG5hbWVzIGFuZAogICAgICAgICAqIHN5bWJvbHMgb2YgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBrZXlzRnVuYyBUaGUgZnVuY3Rpb24gdG8gZ2V0IHRoZSBrZXlzIG9mIGBvYmplY3RgLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHN5bWJvbHNGdW5jIFRoZSBmdW5jdGlvbiB0byBnZXQgdGhlIHN5bWJvbHMgb2YgYG9iamVjdGAuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcyBhbmQgc3ltYm9scy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlR2V0QWxsS2V5cyhvYmplY3QsIGtleXNGdW5jLCBzeW1ib2xzRnVuYykgewogICAgICAgICAgdmFyIHJlc3VsdCA9IGtleXNGdW5jKG9iamVjdCk7CiAgICAgICAgICByZXR1cm4gaXNBcnJheShvYmplY3QpID8gcmVzdWx0IDogYXJyYXlQdXNoKHJlc3VsdCwgc3ltYm9sc0Z1bmMob2JqZWN0KSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgZ2V0VGFnYCB3aXRob3V0IGZhbGxiYWNrcyBmb3IgYnVnZ3kgZW52aXJvbm1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBgdG9TdHJpbmdUYWdgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VHZXRUYWcodmFsdWUpIHsKICAgICAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiB2YWx1ZSA9PT0gdW5kZWZpbmVkJDEgPyB1bmRlZmluZWRUYWcgOiBudWxsVGFnOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIChzeW1Ub1N0cmluZ1RhZyAmJiBzeW1Ub1N0cmluZ1RhZyBpbiBPYmplY3QodmFsdWUpKQogICAgICAgICAgICA/IGdldFJhd1RhZyh2YWx1ZSkKICAgICAgICAgICAgOiBvYmplY3RUb1N0cmluZyh2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5ndGAgd2hpY2ggZG9lc24ndCBjb2VyY2UgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7Kn0gb3RoZXIgVGhlIG90aGVyIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgZ3JlYXRlciB0aGFuIGBvdGhlcmAsCiAgICAgICAgICogIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlR3QodmFsdWUsIG90aGVyKSB7CiAgICAgICAgICByZXR1cm4gdmFsdWUgPiBvdGhlcjsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmhhc2Agd2l0aG91dCBzdXBwb3J0IGZvciBkZWVwIHBhdGhzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29iamVjdF0gVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30ga2V5IFRoZSBrZXkgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VIYXMob2JqZWN0LCBrZXkpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgIT0gbnVsbCAmJiBoYXNPd25Qcm9wZXJ0eS5jYWxsKG9iamVjdCwga2V5KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmhhc0luYCB3aXRob3V0IHN1cHBvcnQgZm9yIGRlZXAgcGF0aHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0XSBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBrZXkgVGhlIGtleSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYGtleWAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUhhc0luKG9iamVjdCwga2V5KSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ICE9IG51bGwgJiYga2V5IGluIE9iamVjdChvYmplY3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaW5SYW5nZWAgd2hpY2ggZG9lc24ndCBjb2VyY2UgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbnVtYmVyIFRoZSBudW1iZXIgdG8gY2hlY2suCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHN0YXJ0IFRoZSBzdGFydCBvZiB0aGUgcmFuZ2UuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGVuZCBUaGUgZW5kIG9mIHRoZSByYW5nZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYG51bWJlcmAgaXMgaW4gdGhlIHJhbmdlLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUluUmFuZ2UobnVtYmVyLCBzdGFydCwgZW5kKSB7CiAgICAgICAgICByZXR1cm4gbnVtYmVyID49IG5hdGl2ZU1pbihzdGFydCwgZW5kKSAmJiBudW1iZXIgPCBuYXRpdmVNYXgoc3RhcnQsIGVuZCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBtZXRob2RzIGxpa2UgYF8uaW50ZXJzZWN0aW9uYCwgd2l0aG91dCBzdXBwb3J0CiAgICAgICAgICogZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMsIHRoYXQgYWNjZXB0cyBhbiBhcnJheSBvZiBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXlzIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWVdIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjb21wYXJhdG9yXSBUaGUgY29tcGFyYXRvciBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIHNoYXJlZCB2YWx1ZXMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUludGVyc2VjdGlvbihhcnJheXMsIGl0ZXJhdGVlLCBjb21wYXJhdG9yKSB7CiAgICAgICAgICB2YXIgaW5jbHVkZXMgPSBjb21wYXJhdG9yID8gYXJyYXlJbmNsdWRlc1dpdGggOiBhcnJheUluY2x1ZGVzLAogICAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5c1swXS5sZW5ndGgsCiAgICAgICAgICAgICAgb3RoTGVuZ3RoID0gYXJyYXlzLmxlbmd0aCwKICAgICAgICAgICAgICBvdGhJbmRleCA9IG90aExlbmd0aCwKICAgICAgICAgICAgICBjYWNoZXMgPSBBcnJheShvdGhMZW5ndGgpLAogICAgICAgICAgICAgIG1heExlbmd0aCA9IEluZmluaXR5LAogICAgICAgICAgICAgIHJlc3VsdCA9IFtdOwoKICAgICAgICAgIHdoaWxlIChvdGhJbmRleC0tKSB7CiAgICAgICAgICAgIHZhciBhcnJheSA9IGFycmF5c1tvdGhJbmRleF07CiAgICAgICAgICAgIGlmIChvdGhJbmRleCAmJiBpdGVyYXRlZSkgewogICAgICAgICAgICAgIGFycmF5ID0gYXJyYXlNYXAoYXJyYXksIGJhc2VVbmFyeShpdGVyYXRlZSkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG1heExlbmd0aCA9IG5hdGl2ZU1pbihhcnJheS5sZW5ndGgsIG1heExlbmd0aCk7CiAgICAgICAgICAgIGNhY2hlc1tvdGhJbmRleF0gPSAhY29tcGFyYXRvciAmJiAoaXRlcmF0ZWUgfHwgKGxlbmd0aCA+PSAxMjAgJiYgYXJyYXkubGVuZ3RoID49IDEyMCkpCiAgICAgICAgICAgICAgPyBuZXcgU2V0Q2FjaGUob3RoSW5kZXggJiYgYXJyYXkpCiAgICAgICAgICAgICAgOiB1bmRlZmluZWQkMTsKICAgICAgICAgIH0KICAgICAgICAgIGFycmF5ID0gYXJyYXlzWzBdOwoKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIHNlZW4gPSBjYWNoZXNbMF07CgogICAgICAgICAgb3V0ZXI6CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCAmJiByZXN1bHQubGVuZ3RoIDwgbWF4TGVuZ3RoKSB7CiAgICAgICAgICAgIHZhciB2YWx1ZSA9IGFycmF5W2luZGV4XSwKICAgICAgICAgICAgICAgIGNvbXB1dGVkID0gaXRlcmF0ZWUgPyBpdGVyYXRlZSh2YWx1ZSkgOiB2YWx1ZTsKCiAgICAgICAgICAgIHZhbHVlID0gKGNvbXBhcmF0b3IgfHwgdmFsdWUgIT09IDApID8gdmFsdWUgOiAwOwogICAgICAgICAgICBpZiAoIShzZWVuCiAgICAgICAgICAgICAgICAgID8gY2FjaGVIYXMoc2VlbiwgY29tcHV0ZWQpCiAgICAgICAgICAgICAgICAgIDogaW5jbHVkZXMocmVzdWx0LCBjb21wdXRlZCwgY29tcGFyYXRvcikKICAgICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgICBvdGhJbmRleCA9IG90aExlbmd0aDsKICAgICAgICAgICAgICB3aGlsZSAoLS1vdGhJbmRleCkgewogICAgICAgICAgICAgICAgdmFyIGNhY2hlID0gY2FjaGVzW290aEluZGV4XTsKICAgICAgICAgICAgICAgIGlmICghKGNhY2hlCiAgICAgICAgICAgICAgICAgICAgICA/IGNhY2hlSGFzKGNhY2hlLCBjb21wdXRlZCkKICAgICAgICAgICAgICAgICAgICAgIDogaW5jbHVkZXMoYXJyYXlzW290aEluZGV4XSwgY29tcHV0ZWQsIGNvbXBhcmF0b3IpKQogICAgICAgICAgICAgICAgICAgICkgewogICAgICAgICAgICAgICAgICBjb250aW51ZSBvdXRlcjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKHNlZW4pIHsKICAgICAgICAgICAgICAgIHNlZW4ucHVzaChjb21wdXRlZCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHJlc3VsdC5wdXNoKHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmludmVydGAgYW5kIGBfLmludmVydEJ5YCB3aGljaCBpbnZlcnRzCiAgICAgICAgICogYG9iamVjdGAgd2l0aCB2YWx1ZXMgdHJhbnNmb3JtZWQgYnkgYGl0ZXJhdGVlYCBhbmQgc2V0IGJ5IGBzZXR0ZXJgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHNldHRlciBUaGUgZnVuY3Rpb24gdG8gc2V0IGBhY2N1bXVsYXRvcmAgdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBpdGVyYXRlZSB0byB0cmFuc2Zvcm0gdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBhY2N1bXVsYXRvciBUaGUgaW5pdGlhbCBpbnZlcnRlZCBvYmplY3QuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIGBhY2N1bXVsYXRvcmAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUludmVydGVyKG9iamVjdCwgc2V0dGVyLCBpdGVyYXRlZSwgYWNjdW11bGF0b3IpIHsKICAgICAgICAgIGJhc2VGb3JPd24ob2JqZWN0LCBmdW5jdGlvbih2YWx1ZSwga2V5LCBvYmplY3QpIHsKICAgICAgICAgICAgc2V0dGVyKGFjY3VtdWxhdG9yLCBpdGVyYXRlZSh2YWx1ZSksIGtleSwgb2JqZWN0KTsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIGFjY3VtdWxhdG9yOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaW52b2tlYCB3aXRob3V0IHN1cHBvcnQgZm9yIGluZGl2aWR1YWwKICAgICAgICAgKiBtZXRob2QgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIG1ldGhvZCB0byBpbnZva2UuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJncyBUaGUgYXJndW1lbnRzIHRvIGludm9rZSB0aGUgbWV0aG9kIHdpdGguCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHJlc3VsdCBvZiB0aGUgaW52b2tlZCBtZXRob2QuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUludm9rZShvYmplY3QsIHBhdGgsIGFyZ3MpIHsKICAgICAgICAgIHBhdGggPSBjYXN0UGF0aChwYXRoLCBvYmplY3QpOwogICAgICAgICAgb2JqZWN0ID0gcGFyZW50KG9iamVjdCwgcGF0aCk7CiAgICAgICAgICB2YXIgZnVuYyA9IG9iamVjdCA9PSBudWxsID8gb2JqZWN0IDogb2JqZWN0W3RvS2V5KGxhc3QocGF0aCkpXTsKICAgICAgICAgIHJldHVybiBmdW5jID09IG51bGwgPyB1bmRlZmluZWQkMSA6IGFwcGx5KGZ1bmMsIG9iamVjdCwgYXJncyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc0FyZ3VtZW50c2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIGBhcmd1bWVudHNgIG9iamVjdCwKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlSXNBcmd1bWVudHModmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGJhc2VHZXRUYWcodmFsdWUpID09IGFyZ3NUYWc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc0FycmF5QnVmZmVyYCB3aXRob3V0IE5vZGUuanMgb3B0aW1pemF0aW9ucy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYW4gYXJyYXkgYnVmZmVyLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUlzQXJyYXlCdWZmZXIodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGJhc2VHZXRUYWcodmFsdWUpID09IGFycmF5QnVmZmVyVGFnOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNEYXRlYCB3aXRob3V0IE5vZGUuanMgb3B0aW1pemF0aW9ucy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBkYXRlIG9iamVjdCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VJc0RhdGUodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGJhc2VHZXRUYWcodmFsdWUpID09IGRhdGVUYWc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc0VxdWFsYCB3aGljaCBzdXBwb3J0cyBwYXJ0aWFsIGNvbXBhcmlzb25zCiAgICAgICAgICogYW5kIHRyYWNrcyB0cmF2ZXJzZWQgb2JqZWN0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4KICAgICAgICAgKiAgMSAtIFVub3JkZXJlZCBjb21wYXJpc29uCiAgICAgICAgICogIDIgLSBQYXJ0aWFsIGNvbXBhcmlzb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb21wYXJpc29ucy4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIGB2YWx1ZWAgYW5kIGBvdGhlcmAgb2JqZWN0cy4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIHZhbHVlcyBhcmUgZXF1aXZhbGVudCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VJc0VxdWFsKHZhbHVlLCBvdGhlciwgYml0bWFzaywgY3VzdG9taXplciwgc3RhY2spIHsKICAgICAgICAgIGlmICh2YWx1ZSA9PT0gb3RoZXIpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodmFsdWUgPT0gbnVsbCB8fCBvdGhlciA9PSBudWxsIHx8ICghaXNPYmplY3RMaWtlKHZhbHVlKSAmJiAhaXNPYmplY3RMaWtlKG90aGVyKSkpIHsKICAgICAgICAgICAgcmV0dXJuIHZhbHVlICE9PSB2YWx1ZSAmJiBvdGhlciAhPT0gb3RoZXI7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYmFzZUlzRXF1YWxEZWVwKHZhbHVlLCBvdGhlciwgYml0bWFzaywgY3VzdG9taXplciwgYmFzZUlzRXF1YWwsIHN0YWNrKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZUlzRXF1YWxgIGZvciBhcnJheXMgYW5kIG9iamVjdHMgd2hpY2ggcGVyZm9ybXMKICAgICAgICAgKiBkZWVwIGNvbXBhcmlzb25zIGFuZCB0cmFja3MgdHJhdmVyc2VkIG9iamVjdHMgZW5hYmxpbmcgb2JqZWN0cyB3aXRoIGNpcmN1bGFyCiAgICAgICAgICogcmVmZXJlbmNlcyB0byBiZSBjb21wYXJlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG90aGVyIFRoZSBvdGhlciBvYmplY3QgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4gU2VlIGBiYXNlSXNFcXVhbGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjdXN0b21pemVyIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgY29tcGFyaXNvbnMuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZXF1YWxGdW5jIFRoZSBmdW5jdGlvbiB0byBkZXRlcm1pbmUgZXF1aXZhbGVudHMgb2YgdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbc3RhY2tdIFRyYWNrcyB0cmF2ZXJzZWQgYG9iamVjdGAgYW5kIGBvdGhlcmAgb2JqZWN0cy4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIG9iamVjdHMgYXJlIGVxdWl2YWxlbnQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlSXNFcXVhbERlZXAob2JqZWN0LCBvdGhlciwgYml0bWFzaywgY3VzdG9taXplciwgZXF1YWxGdW5jLCBzdGFjaykgewogICAgICAgICAgdmFyIG9iaklzQXJyID0gaXNBcnJheShvYmplY3QpLAogICAgICAgICAgICAgIG90aElzQXJyID0gaXNBcnJheShvdGhlciksCiAgICAgICAgICAgICAgb2JqVGFnID0gb2JqSXNBcnIgPyBhcnJheVRhZyA6IGdldFRhZyhvYmplY3QpLAogICAgICAgICAgICAgIG90aFRhZyA9IG90aElzQXJyID8gYXJyYXlUYWcgOiBnZXRUYWcob3RoZXIpOwoKICAgICAgICAgIG9ialRhZyA9IG9ialRhZyA9PSBhcmdzVGFnID8gb2JqZWN0VGFnIDogb2JqVGFnOwogICAgICAgICAgb3RoVGFnID0gb3RoVGFnID09IGFyZ3NUYWcgPyBvYmplY3RUYWcgOiBvdGhUYWc7CgogICAgICAgICAgdmFyIG9iaklzT2JqID0gb2JqVGFnID09IG9iamVjdFRhZywKICAgICAgICAgICAgICBvdGhJc09iaiA9IG90aFRhZyA9PSBvYmplY3RUYWcsCiAgICAgICAgICAgICAgaXNTYW1lVGFnID0gb2JqVGFnID09IG90aFRhZzsKCiAgICAgICAgICBpZiAoaXNTYW1lVGFnICYmIGlzQnVmZmVyKG9iamVjdCkpIHsKICAgICAgICAgICAgaWYgKCFpc0J1ZmZlcihvdGhlcikpIHsKICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgb2JqSXNBcnIgPSB0cnVlOwogICAgICAgICAgICBvYmpJc09iaiA9IGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzU2FtZVRhZyAmJiAhb2JqSXNPYmopIHsKICAgICAgICAgICAgc3RhY2sgfHwgKHN0YWNrID0gbmV3IFN0YWNrKTsKICAgICAgICAgICAgcmV0dXJuIChvYmpJc0FyciB8fCBpc1R5cGVkQXJyYXkob2JqZWN0KSkKICAgICAgICAgICAgICA/IGVxdWFsQXJyYXlzKG9iamVjdCwgb3RoZXIsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spCiAgICAgICAgICAgICAgOiBlcXVhbEJ5VGFnKG9iamVjdCwgb3RoZXIsIG9ialRhZywgYml0bWFzaywgY3VzdG9taXplciwgZXF1YWxGdW5jLCBzdGFjayk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoIShiaXRtYXNrICYgQ09NUEFSRV9QQVJUSUFMX0ZMQUcpKSB7CiAgICAgICAgICAgIHZhciBvYmpJc1dyYXBwZWQgPSBvYmpJc09iaiAmJiBoYXNPd25Qcm9wZXJ0eS5jYWxsKG9iamVjdCwgJ19fd3JhcHBlZF9fJyksCiAgICAgICAgICAgICAgICBvdGhJc1dyYXBwZWQgPSBvdGhJc09iaiAmJiBoYXNPd25Qcm9wZXJ0eS5jYWxsKG90aGVyLCAnX193cmFwcGVkX18nKTsKCiAgICAgICAgICAgIGlmIChvYmpJc1dyYXBwZWQgfHwgb3RoSXNXcmFwcGVkKSB7CiAgICAgICAgICAgICAgdmFyIG9ialVud3JhcHBlZCA9IG9iaklzV3JhcHBlZCA/IG9iamVjdC52YWx1ZSgpIDogb2JqZWN0LAogICAgICAgICAgICAgICAgICBvdGhVbndyYXBwZWQgPSBvdGhJc1dyYXBwZWQgPyBvdGhlci52YWx1ZSgpIDogb3RoZXI7CgogICAgICAgICAgICAgIHN0YWNrIHx8IChzdGFjayA9IG5ldyBTdGFjayk7CiAgICAgICAgICAgICAgcmV0dXJuIGVxdWFsRnVuYyhvYmpVbndyYXBwZWQsIG90aFVud3JhcHBlZCwgYml0bWFzaywgY3VzdG9taXplciwgc3RhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoIWlzU2FtZVRhZykgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICBzdGFjayB8fCAoc3RhY2sgPSBuZXcgU3RhY2spOwogICAgICAgICAgcmV0dXJuIGVxdWFsT2JqZWN0cyhvYmplY3QsIG90aGVyLCBiaXRtYXNrLCBjdXN0b21pemVyLCBlcXVhbEZ1bmMsIHN0YWNrKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmlzTWFwYCB3aXRob3V0IE5vZGUuanMgb3B0aW1pemF0aW9ucy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBtYXAsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlSXNNYXAodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGdldFRhZyh2YWx1ZSkgPT0gbWFwVGFnOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNNYXRjaGAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3Qgb2YgcHJvcGVydHkgdmFsdWVzIHRvIG1hdGNoLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IG1hdGNoRGF0YSBUaGUgcHJvcGVydHkgbmFtZXMsIHZhbHVlcywgYW5kIGNvbXBhcmUgZmxhZ3MgdG8gbWF0Y2guCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgY29tcGFyaXNvbnMuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBvYmplY3RgIGlzIGEgbWF0Y2gsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlSXNNYXRjaChvYmplY3QsIHNvdXJjZSwgbWF0Y2hEYXRhLCBjdXN0b21pemVyKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSBtYXRjaERhdGEubGVuZ3RoLAogICAgICAgICAgICAgIGxlbmd0aCA9IGluZGV4LAogICAgICAgICAgICAgIG5vQ3VzdG9taXplciA9ICFjdXN0b21pemVyOwoKICAgICAgICAgIGlmIChvYmplY3QgPT0gbnVsbCkgewogICAgICAgICAgICByZXR1cm4gIWxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIG9iamVjdCA9IE9iamVjdChvYmplY3QpOwogICAgICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICAgICAgdmFyIGRhdGEgPSBtYXRjaERhdGFbaW5kZXhdOwogICAgICAgICAgICBpZiAoKG5vQ3VzdG9taXplciAmJiBkYXRhWzJdKQogICAgICAgICAgICAgICAgICA/IGRhdGFbMV0gIT09IG9iamVjdFtkYXRhWzBdXQogICAgICAgICAgICAgICAgICA6ICEoZGF0YVswXSBpbiBvYmplY3QpCiAgICAgICAgICAgICAgICApIHsKICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIGRhdGEgPSBtYXRjaERhdGFbaW5kZXhdOwogICAgICAgICAgICB2YXIga2V5ID0gZGF0YVswXSwKICAgICAgICAgICAgICAgIG9ialZhbHVlID0gb2JqZWN0W2tleV0sCiAgICAgICAgICAgICAgICBzcmNWYWx1ZSA9IGRhdGFbMV07CgogICAgICAgICAgICBpZiAobm9DdXN0b21pemVyICYmIGRhdGFbMl0pIHsKICAgICAgICAgICAgICBpZiAob2JqVmFsdWUgPT09IHVuZGVmaW5lZCQxICYmICEoa2V5IGluIG9iamVjdCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdmFyIHN0YWNrID0gbmV3IFN0YWNrOwogICAgICAgICAgICAgIGlmIChjdXN0b21pemVyKSB7CiAgICAgICAgICAgICAgICB2YXIgcmVzdWx0ID0gY3VzdG9taXplcihvYmpWYWx1ZSwgc3JjVmFsdWUsIGtleSwgb2JqZWN0LCBzb3VyY2UsIHN0YWNrKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKCEocmVzdWx0ID09PSB1bmRlZmluZWQkMQogICAgICAgICAgICAgICAgICAgID8gYmFzZUlzRXF1YWwoc3JjVmFsdWUsIG9ialZhbHVlLCBDT01QQVJFX1BBUlRJQUxfRkxBRyB8IENPTVBBUkVfVU5PUkRFUkVEX0ZMQUcsIGN1c3RvbWl6ZXIsIHN0YWNrKQogICAgICAgICAgICAgICAgICAgIDogcmVzdWx0CiAgICAgICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNOYXRpdmVgIHdpdGhvdXQgYmFkIHNoaW0gY2hlY2tzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIG5hdGl2ZSBmdW5jdGlvbiwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VJc05hdGl2ZSh2YWx1ZSkgewogICAgICAgICAgaWYgKCFpc09iamVjdCh2YWx1ZSkgfHwgaXNNYXNrZWQodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBwYXR0ZXJuID0gaXNGdW5jdGlvbih2YWx1ZSkgPyByZUlzTmF0aXZlIDogcmVJc0hvc3RDdG9yOwogICAgICAgICAgcmV0dXJuIHBhdHRlcm4udGVzdCh0b1NvdXJjZSh2YWx1ZSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNSZWdFeHBgIHdpdGhvdXQgTm9kZS5qcyBvcHRpbWl6YXRpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHJlZ2V4cCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VJc1JlZ0V4cCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYgYmFzZUdldFRhZyh2YWx1ZSkgPT0gcmVnZXhwVGFnOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNTZXRgIHdpdGhvdXQgTm9kZS5qcyBvcHRpbWl6YXRpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHNldCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VJc1NldCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYgZ2V0VGFnKHZhbHVlKSA9PSBzZXRUYWc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc1R5cGVkQXJyYXlgIHdpdGhvdXQgTm9kZS5qcyBvcHRpbWl6YXRpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHR5cGVkIGFycmF5LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZUlzVHlwZWRBcnJheSh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYKICAgICAgICAgICAgaXNMZW5ndGgodmFsdWUubGVuZ3RoKSAmJiAhIXR5cGVkQXJyYXlUYWdzW2Jhc2VHZXRUYWcodmFsdWUpXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLml0ZXJhdGVlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSBbdmFsdWU9Xy5pZGVudGl0eV0gVGhlIHZhbHVlIHRvIGNvbnZlcnQgdG8gYW4gaXRlcmF0ZWUuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBpdGVyYXRlZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlSXRlcmF0ZWUodmFsdWUpIHsKICAgICAgICAgIC8vIERvbid0IHN0b3JlIHRoZSBgdHlwZW9mYCByZXN1bHQgaW4gYSB2YXJpYWJsZSB0byBhdm9pZCBhIEpJVCBidWcgaW4gU2FmYXJpIDkuCiAgICAgICAgICAvLyBTZWUgaHR0cHM6Ly9idWdzLndlYmtpdC5vcmcvc2hvd19idWcuY2dpP2lkPTE1NjAzNCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiBpZGVudGl0eTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh0eXBlb2YgdmFsdWUgPT0gJ29iamVjdCcpIHsKICAgICAgICAgICAgcmV0dXJuIGlzQXJyYXkodmFsdWUpCiAgICAgICAgICAgICAgPyBiYXNlTWF0Y2hlc1Byb3BlcnR5KHZhbHVlWzBdLCB2YWx1ZVsxXSkKICAgICAgICAgICAgICA6IGJhc2VNYXRjaGVzKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBwcm9wZXJ0eSh2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5rZXlzYCB3aGljaCBkb2Vzbid0IHRyZWF0IHNwYXJzZSBhcnJheXMgYXMgZGVuc2UuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VLZXlzKG9iamVjdCkgewogICAgICAgICAgaWYgKCFpc1Byb3RvdHlwZShvYmplY3QpKSB7CiAgICAgICAgICAgIHJldHVybiBuYXRpdmVLZXlzKG9iamVjdCk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcmVzdWx0ID0gW107CiAgICAgICAgICBmb3IgKHZhciBrZXkgaW4gT2JqZWN0KG9iamVjdCkpIHsKICAgICAgICAgICAgaWYgKGhhc093blByb3BlcnR5LmNhbGwob2JqZWN0LCBrZXkpICYmIGtleSAhPSAnY29uc3RydWN0b3InKSB7CiAgICAgICAgICAgICAgcmVzdWx0LnB1c2goa2V5KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmtleXNJbmAgd2hpY2ggZG9lc24ndCB0cmVhdCBzcGFyc2UgYXJyYXlzIGFzIGRlbnNlLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlS2V5c0luKG9iamVjdCkgewogICAgICAgICAgaWYgKCFpc09iamVjdChvYmplY3QpKSB7CiAgICAgICAgICAgIHJldHVybiBuYXRpdmVLZXlzSW4ob2JqZWN0KTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBpc1Byb3RvID0gaXNQcm90b3R5cGUob2JqZWN0KSwKICAgICAgICAgICAgICByZXN1bHQgPSBbXTsKCiAgICAgICAgICBmb3IgKHZhciBrZXkgaW4gb2JqZWN0KSB7CiAgICAgICAgICAgIGlmICghKGtleSA9PSAnY29uc3RydWN0b3InICYmIChpc1Byb3RvIHx8ICFoYXNPd25Qcm9wZXJ0eS5jYWxsKG9iamVjdCwga2V5KSkpKSB7CiAgICAgICAgICAgICAgcmVzdWx0LnB1c2goa2V5KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmx0YCB3aGljaCBkb2Vzbid0IGNvZXJjZSBhcmd1bWVudHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHsqfSBvdGhlciBUaGUgb3RoZXIgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBsZXNzIHRoYW4gYG90aGVyYCwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VMdCh2YWx1ZSwgb3RoZXIpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSA8IG90aGVyOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ubWFwYCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IG1hcHBlZCBhcnJheS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlTWFwKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICByZXN1bHQgPSBpc0FycmF5TGlrZShjb2xsZWN0aW9uKSA/IEFycmF5KGNvbGxlY3Rpb24ubGVuZ3RoKSA6IFtdOwoKICAgICAgICAgIGJhc2VFYWNoKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBrZXksIGNvbGxlY3Rpb24pIHsKICAgICAgICAgICAgcmVzdWx0WysraW5kZXhdID0gaXRlcmF0ZWUodmFsdWUsIGtleSwgY29sbGVjdGlvbik7CiAgICAgICAgICB9KTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5tYXRjaGVzYCB3aGljaCBkb2Vzbid0IGNsb25lIGBzb3VyY2VgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3Qgb2YgcHJvcGVydHkgdmFsdWVzIHRvIG1hdGNoLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHNwZWMgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZU1hdGNoZXMoc291cmNlKSB7CiAgICAgICAgICB2YXIgbWF0Y2hEYXRhID0gZ2V0TWF0Y2hEYXRhKHNvdXJjZSk7CiAgICAgICAgICBpZiAobWF0Y2hEYXRhLmxlbmd0aCA9PSAxICYmIG1hdGNoRGF0YVswXVsyXSkgewogICAgICAgICAgICByZXR1cm4gbWF0Y2hlc1N0cmljdENvbXBhcmFibGUobWF0Y2hEYXRhWzBdWzBdLCBtYXRjaERhdGFbMF1bMV0pOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgICAgICByZXR1cm4gb2JqZWN0ID09PSBzb3VyY2UgfHwgYmFzZUlzTWF0Y2gob2JqZWN0LCBzb3VyY2UsIG1hdGNoRGF0YSk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ubWF0Y2hlc1Byb3BlcnR5YCB3aGljaCBkb2Vzbid0IGNsb25lIGBzcmNWYWx1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAgICogQHBhcmFtIHsqfSBzcmNWYWx1ZSBUaGUgdmFsdWUgdG8gbWF0Y2guCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlTWF0Y2hlc1Byb3BlcnR5KHBhdGgsIHNyY1ZhbHVlKSB7CiAgICAgICAgICBpZiAoaXNLZXkocGF0aCkgJiYgaXNTdHJpY3RDb21wYXJhYmxlKHNyY1ZhbHVlKSkgewogICAgICAgICAgICByZXR1cm4gbWF0Y2hlc1N0cmljdENvbXBhcmFibGUodG9LZXkocGF0aCksIHNyY1ZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICAgICAgdmFyIG9ialZhbHVlID0gZ2V0KG9iamVjdCwgcGF0aCk7CiAgICAgICAgICAgIHJldHVybiAob2JqVmFsdWUgPT09IHVuZGVmaW5lZCQxICYmIG9ialZhbHVlID09PSBzcmNWYWx1ZSkKICAgICAgICAgICAgICA/IGhhc0luKG9iamVjdCwgcGF0aCkKICAgICAgICAgICAgICA6IGJhc2VJc0VxdWFsKHNyY1ZhbHVlLCBvYmpWYWx1ZSwgQ09NUEFSRV9QQVJUSUFMX0ZMQUcgfCBDT01QQVJFX1VOT1JERVJFRF9GTEFHKTsKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5tZXJnZWAgd2l0aG91dCBzdXBwb3J0IGZvciBtdWx0aXBsZSBzb3VyY2VzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgc291cmNlIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gc3JjSW5kZXggVGhlIGluZGV4IG9mIGBzb3VyY2VgLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIG1lcmdlZCB2YWx1ZXMuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IFtzdGFja10gVHJhY2tzIHRyYXZlcnNlZCBzb3VyY2UgdmFsdWVzIGFuZCB0aGVpciBtZXJnZWQKICAgICAgICAgKiAgY291bnRlcnBhcnRzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VNZXJnZShvYmplY3QsIHNvdXJjZSwgc3JjSW5kZXgsIGN1c3RvbWl6ZXIsIHN0YWNrKSB7CiAgICAgICAgICBpZiAob2JqZWN0ID09PSBzb3VyY2UpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgYmFzZUZvcihzb3VyY2UsIGZ1bmN0aW9uKHNyY1ZhbHVlLCBrZXkpIHsKICAgICAgICAgICAgc3RhY2sgfHwgKHN0YWNrID0gbmV3IFN0YWNrKTsKICAgICAgICAgICAgaWYgKGlzT2JqZWN0KHNyY1ZhbHVlKSkgewogICAgICAgICAgICAgIGJhc2VNZXJnZURlZXAob2JqZWN0LCBzb3VyY2UsIGtleSwgc3JjSW5kZXgsIGJhc2VNZXJnZSwgY3VzdG9taXplciwgc3RhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgIHZhciBuZXdWYWx1ZSA9IGN1c3RvbWl6ZXIKICAgICAgICAgICAgICAgID8gY3VzdG9taXplcihzYWZlR2V0KG9iamVjdCwga2V5KSwgc3JjVmFsdWUsIChrZXkgKyAnJyksIG9iamVjdCwgc291cmNlLCBzdGFjaykKICAgICAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgICAgIGlmIChuZXdWYWx1ZSA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICAgIG5ld1ZhbHVlID0gc3JjVmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGFzc2lnbk1lcmdlVmFsdWUob2JqZWN0LCBrZXksIG5ld1ZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSwga2V5c0luKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZU1lcmdlYCBmb3IgYXJyYXlzIGFuZCBvYmplY3RzIHdoaWNoIHBlcmZvcm1zCiAgICAgICAgICogZGVlcCBtZXJnZXMgYW5kIHRyYWNrcyB0cmF2ZXJzZWQgb2JqZWN0cyBlbmFibGluZyBvYmplY3RzIHdpdGggY2lyY3VsYXIKICAgICAgICAgKiByZWZlcmVuY2VzIHRvIGJlIG1lcmdlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIHNvdXJjZSBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byBtZXJnZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gc3JjSW5kZXggVGhlIGluZGV4IG9mIGBzb3VyY2VgLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IG1lcmdlRnVuYyBUaGUgZnVuY3Rpb24gdG8gbWVyZ2UgdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGFzc2lnbmVkIHZhbHVlcy4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIHNvdXJjZSB2YWx1ZXMgYW5kIHRoZWlyIG1lcmdlZAogICAgICAgICAqICBjb3VudGVycGFydHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZU1lcmdlRGVlcChvYmplY3QsIHNvdXJjZSwga2V5LCBzcmNJbmRleCwgbWVyZ2VGdW5jLCBjdXN0b21pemVyLCBzdGFjaykgewogICAgICAgICAgdmFyIG9ialZhbHVlID0gc2FmZUdldChvYmplY3QsIGtleSksCiAgICAgICAgICAgICAgc3JjVmFsdWUgPSBzYWZlR2V0KHNvdXJjZSwga2V5KSwKICAgICAgICAgICAgICBzdGFja2VkID0gc3RhY2suZ2V0KHNyY1ZhbHVlKTsKCiAgICAgICAgICBpZiAoc3RhY2tlZCkgewogICAgICAgICAgICBhc3NpZ25NZXJnZVZhbHVlKG9iamVjdCwga2V5LCBzdGFja2VkKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgdmFyIG5ld1ZhbHVlID0gY3VzdG9taXplcgogICAgICAgICAgICA/IGN1c3RvbWl6ZXIob2JqVmFsdWUsIHNyY1ZhbHVlLCAoa2V5ICsgJycpLCBvYmplY3QsIHNvdXJjZSwgc3RhY2spCiAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgdmFyIGlzQ29tbW9uID0gbmV3VmFsdWUgPT09IHVuZGVmaW5lZCQxOwoKICAgICAgICAgIGlmIChpc0NvbW1vbikgewogICAgICAgICAgICB2YXIgaXNBcnIgPSBpc0FycmF5KHNyY1ZhbHVlKSwKICAgICAgICAgICAgICAgIGlzQnVmZiA9ICFpc0FyciAmJiBpc0J1ZmZlcihzcmNWYWx1ZSksCiAgICAgICAgICAgICAgICBpc1R5cGVkID0gIWlzQXJyICYmICFpc0J1ZmYgJiYgaXNUeXBlZEFycmF5KHNyY1ZhbHVlKTsKCiAgICAgICAgICAgIG5ld1ZhbHVlID0gc3JjVmFsdWU7CiAgICAgICAgICAgIGlmIChpc0FyciB8fCBpc0J1ZmYgfHwgaXNUeXBlZCkgewogICAgICAgICAgICAgIGlmIChpc0FycmF5KG9ialZhbHVlKSkgewogICAgICAgICAgICAgICAgbmV3VmFsdWUgPSBvYmpWYWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgZWxzZSBpZiAoaXNBcnJheUxpa2VPYmplY3Qob2JqVmFsdWUpKSB7CiAgICAgICAgICAgICAgICBuZXdWYWx1ZSA9IGNvcHlBcnJheShvYmpWYWx1ZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGVsc2UgaWYgKGlzQnVmZikgewogICAgICAgICAgICAgICAgaXNDb21tb24gPSBmYWxzZTsKICAgICAgICAgICAgICAgIG5ld1ZhbHVlID0gY2xvbmVCdWZmZXIoc3JjVmFsdWUsIHRydWUpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBlbHNlIGlmIChpc1R5cGVkKSB7CiAgICAgICAgICAgICAgICBpc0NvbW1vbiA9IGZhbHNlOwogICAgICAgICAgICAgICAgbmV3VmFsdWUgPSBjbG9uZVR5cGVkQXJyYXkoc3JjVmFsdWUsIHRydWUpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIG5ld1ZhbHVlID0gW107CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGlzUGxhaW5PYmplY3Qoc3JjVmFsdWUpIHx8IGlzQXJndW1lbnRzKHNyY1ZhbHVlKSkgewogICAgICAgICAgICAgIG5ld1ZhbHVlID0gb2JqVmFsdWU7CiAgICAgICAgICAgICAgaWYgKGlzQXJndW1lbnRzKG9ialZhbHVlKSkgewogICAgICAgICAgICAgICAgbmV3VmFsdWUgPSB0b1BsYWluT2JqZWN0KG9ialZhbHVlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgZWxzZSBpZiAoIWlzT2JqZWN0KG9ialZhbHVlKSB8fCBpc0Z1bmN0aW9uKG9ialZhbHVlKSkgewogICAgICAgICAgICAgICAgbmV3VmFsdWUgPSBpbml0Q2xvbmVPYmplY3Qoc3JjVmFsdWUpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICBpc0NvbW1vbiA9IGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNDb21tb24pIHsKICAgICAgICAgICAgLy8gUmVjdXJzaXZlbHkgbWVyZ2Ugb2JqZWN0cyBhbmQgYXJyYXlzIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgICAgIHN0YWNrLnNldChzcmNWYWx1ZSwgbmV3VmFsdWUpOwogICAgICAgICAgICBtZXJnZUZ1bmMobmV3VmFsdWUsIHNyY1ZhbHVlLCBzcmNJbmRleCwgY3VzdG9taXplciwgc3RhY2spOwogICAgICAgICAgICBzdGFja1snZGVsZXRlJ10oc3JjVmFsdWUpOwogICAgICAgICAgfQogICAgICAgICAgYXNzaWduTWVyZ2VWYWx1ZShvYmplY3QsIGtleSwgbmV3VmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ubnRoYCB3aGljaCBkb2Vzbid0IGNvZXJjZSBhcmd1bWVudHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbiBUaGUgaW5kZXggb2YgdGhlIGVsZW1lbnQgdG8gcmV0dXJuLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBudGggZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VOdGgoYXJyYXksIG4pIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheS5sZW5ndGg7CiAgICAgICAgICBpZiAoIWxlbmd0aCkgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBuICs9IG4gPCAwID8gbGVuZ3RoIDogMDsKICAgICAgICAgIHJldHVybiBpc0luZGV4KG4sIGxlbmd0aCkgPyBhcnJheVtuXSA6IHVuZGVmaW5lZCQxOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ub3JkZXJCeWAgd2l0aG91dCBwYXJhbSBndWFyZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9uW118T2JqZWN0W118c3RyaW5nW119IGl0ZXJhdGVlcyBUaGUgaXRlcmF0ZWVzIHRvIHNvcnQgYnkuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmdbXX0gb3JkZXJzIFRoZSBzb3J0IG9yZGVycyBvZiBgaXRlcmF0ZWVzYC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBzb3J0ZWQgYXJyYXkuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZU9yZGVyQnkoY29sbGVjdGlvbiwgaXRlcmF0ZWVzLCBvcmRlcnMpIHsKICAgICAgICAgIGlmIChpdGVyYXRlZXMubGVuZ3RoKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlcyA9IGFycmF5TWFwKGl0ZXJhdGVlcywgZnVuY3Rpb24oaXRlcmF0ZWUpIHsKICAgICAgICAgICAgICBpZiAoaXNBcnJheShpdGVyYXRlZSkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgICAgICAgICByZXR1cm4gYmFzZUdldCh2YWx1ZSwgaXRlcmF0ZWUubGVuZ3RoID09PSAxID8gaXRlcmF0ZWVbMF0gOiBpdGVyYXRlZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHJldHVybiBpdGVyYXRlZTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpdGVyYXRlZXMgPSBbaWRlbnRpdHldOwogICAgICAgICAgfQoKICAgICAgICAgIHZhciBpbmRleCA9IC0xOwogICAgICAgICAgaXRlcmF0ZWVzID0gYXJyYXlNYXAoaXRlcmF0ZWVzLCBiYXNlVW5hcnkoZ2V0SXRlcmF0ZWUoKSkpOwoKICAgICAgICAgIHZhciByZXN1bHQgPSBiYXNlTWFwKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBrZXksIGNvbGxlY3Rpb24pIHsKICAgICAgICAgICAgdmFyIGNyaXRlcmlhID0gYXJyYXlNYXAoaXRlcmF0ZWVzLCBmdW5jdGlvbihpdGVyYXRlZSkgewogICAgICAgICAgICAgIHJldHVybiBpdGVyYXRlZSh2YWx1ZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4geyAnY3JpdGVyaWEnOiBjcml0ZXJpYSwgJ2luZGV4JzogKytpbmRleCwgJ3ZhbHVlJzogdmFsdWUgfTsKICAgICAgICAgIH0pOwoKICAgICAgICAgIHJldHVybiBiYXNlU29ydEJ5KHJlc3VsdCwgZnVuY3Rpb24ob2JqZWN0LCBvdGhlcikgewogICAgICAgICAgICByZXR1cm4gY29tcGFyZU11bHRpcGxlKG9iamVjdCwgb3RoZXIsIG9yZGVycyk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnBpY2tgIHdpdGhvdXQgc3VwcG9ydCBmb3IgaW5kaXZpZHVhbAogICAgICAgICAqIHByb3BlcnR5IGlkZW50aWZpZXJzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nW119IHBhdGhzIFRoZSBwcm9wZXJ0eSBwYXRocyB0byBwaWNrLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVBpY2sob2JqZWN0LCBwYXRocykgewogICAgICAgICAgcmV0dXJuIGJhc2VQaWNrQnkob2JqZWN0LCBwYXRocywgZnVuY3Rpb24odmFsdWUsIHBhdGgpIHsKICAgICAgICAgICAgcmV0dXJuIGhhc0luKG9iamVjdCwgcGF0aCk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mICBgXy5waWNrQnlgIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgc291cmNlIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ1tdfSBwYXRocyBUaGUgcHJvcGVydHkgcGF0aHMgdG8gcGljay4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBwcmVkaWNhdGUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIHByb3BlcnR5LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVBpY2tCeShvYmplY3QsIHBhdGhzLCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IHBhdGhzLmxlbmd0aCwKICAgICAgICAgICAgICByZXN1bHQgPSB7fTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgcGF0aCA9IHBhdGhzW2luZGV4XSwKICAgICAgICAgICAgICAgIHZhbHVlID0gYmFzZUdldChvYmplY3QsIHBhdGgpOwoKICAgICAgICAgICAgaWYgKHByZWRpY2F0ZSh2YWx1ZSwgcGF0aCkpIHsKICAgICAgICAgICAgICBiYXNlU2V0KHJlc3VsdCwgY2FzdFBhdGgocGF0aCwgb2JqZWN0KSwgdmFsdWUpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlUHJvcGVydHlgIHdoaWNoIHN1cHBvcnRzIGRlZXAgcGF0aHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgYWNjZXNzb3IgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVByb3BlcnR5RGVlcChwYXRoKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlR2V0KG9iamVjdCwgcGF0aCk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ucHVsbEFsbEJ5YCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlCiAgICAgICAgICogc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSB2YWx1ZXMgVGhlIHZhbHVlcyB0byByZW1vdmUuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlXSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlUHVsbEFsbChhcnJheSwgdmFsdWVzLCBpdGVyYXRlZSwgY29tcGFyYXRvcikgewogICAgICAgICAgdmFyIGluZGV4T2YgPSBjb21wYXJhdG9yID8gYmFzZUluZGV4T2ZXaXRoIDogYmFzZUluZGV4T2YsCiAgICAgICAgICAgICAgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgICAgIHNlZW4gPSBhcnJheTsKCiAgICAgICAgICBpZiAoYXJyYXkgPT09IHZhbHVlcykgewogICAgICAgICAgICB2YWx1ZXMgPSBjb3B5QXJyYXkodmFsdWVzKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChpdGVyYXRlZSkgewogICAgICAgICAgICBzZWVuID0gYXJyYXlNYXAoYXJyYXksIGJhc2VVbmFyeShpdGVyYXRlZSkpOwogICAgICAgICAgfQogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGZyb21JbmRleCA9IDAsCiAgICAgICAgICAgICAgICB2YWx1ZSA9IHZhbHVlc1tpbmRleF0sCiAgICAgICAgICAgICAgICBjb21wdXRlZCA9IGl0ZXJhdGVlID8gaXRlcmF0ZWUodmFsdWUpIDogdmFsdWU7CgogICAgICAgICAgICB3aGlsZSAoKGZyb21JbmRleCA9IGluZGV4T2Yoc2VlbiwgY29tcHV0ZWQsIGZyb21JbmRleCwgY29tcGFyYXRvcikpID4gLTEpIHsKICAgICAgICAgICAgICBpZiAoc2VlbiAhPT0gYXJyYXkpIHsKICAgICAgICAgICAgICAgIHNwbGljZS5jYWxsKHNlZW4sIGZyb21JbmRleCwgMSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHNwbGljZS5jYWxsKGFycmF5LCBmcm9tSW5kZXgsIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYXJyYXk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5wdWxsQXRgIHdpdGhvdXQgc3VwcG9ydCBmb3IgaW5kaXZpZHVhbAogICAgICAgICAqIGluZGV4ZXMgb3IgY2FwdHVyaW5nIHRoZSByZW1vdmVkIGVsZW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyW119IGluZGV4ZXMgVGhlIGluZGV4ZXMgb2YgZWxlbWVudHMgdG8gcmVtb3ZlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VQdWxsQXQoYXJyYXksIGluZGV4ZXMpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA/IGluZGV4ZXMubGVuZ3RoIDogMCwKICAgICAgICAgICAgICBsYXN0SW5kZXggPSBsZW5ndGggLSAxOwoKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICB2YXIgaW5kZXggPSBpbmRleGVzW2xlbmd0aF07CiAgICAgICAgICAgIGlmIChsZW5ndGggPT0gbGFzdEluZGV4IHx8IGluZGV4ICE9PSBwcmV2aW91cykgewogICAgICAgICAgICAgIHZhciBwcmV2aW91cyA9IGluZGV4OwogICAgICAgICAgICAgIGlmIChpc0luZGV4KGluZGV4KSkgewogICAgICAgICAgICAgICAgc3BsaWNlLmNhbGwoYXJyYXksIGluZGV4LCAxKTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgYmFzZVVuc2V0KGFycmF5LCBpbmRleCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYXJyYXk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5yYW5kb21gIHdpdGhvdXQgc3VwcG9ydCBmb3IgcmV0dXJuaW5nCiAgICAgICAgICogZmxvYXRpbmctcG9pbnQgbnVtYmVycy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGxvd2VyIFRoZSBsb3dlciBib3VuZC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gdXBwZXIgVGhlIHVwcGVyIGJvdW5kLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHJhbmRvbSBudW1iZXIuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVJhbmRvbShsb3dlciwgdXBwZXIpIHsKICAgICAgICAgIHJldHVybiBsb3dlciArIG5hdGl2ZUZsb29yKG5hdGl2ZVJhbmRvbSgpICogKHVwcGVyIC0gbG93ZXIgKyAxKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5yYW5nZWAgYW5kIGBfLnJhbmdlUmlnaHRgIHdoaWNoIGRvZXNuJ3QKICAgICAgICAgKiBjb2VyY2UgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gc3RhcnQgVGhlIHN0YXJ0IG9mIHRoZSByYW5nZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gZW5kIFRoZSBlbmQgb2YgdGhlIHJhbmdlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzdGVwIFRoZSB2YWx1ZSB0byBpbmNyZW1lbnQgb3IgZGVjcmVtZW50IGJ5LgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2Zyb21SaWdodF0gU3BlY2lmeSBpdGVyYXRpbmcgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgcmFuZ2Ugb2YgbnVtYmVycy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlUmFuZ2Uoc3RhcnQsIGVuZCwgc3RlcCwgZnJvbVJpZ2h0KSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSBuYXRpdmVNYXgobmF0aXZlQ2VpbCgoZW5kIC0gc3RhcnQpIC8gKHN0ZXAgfHwgMSkpLCAwKSwKICAgICAgICAgICAgICByZXN1bHQgPSBBcnJheShsZW5ndGgpOwoKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICByZXN1bHRbZnJvbVJpZ2h0ID8gbGVuZ3RoIDogKytpbmRleF0gPSBzdGFydDsKICAgICAgICAgICAgc3RhcnQgKz0gc3RlcDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5yZXBlYXRgIHdoaWNoIGRvZXNuJ3QgY29lcmNlIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIHRvIHJlcGVhdC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbiBUaGUgbnVtYmVyIG9mIHRpbWVzIHRvIHJlcGVhdCB0aGUgc3RyaW5nLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHJlcGVhdGVkIHN0cmluZy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlUmVwZWF0KHN0cmluZywgbikgewogICAgICAgICAgdmFyIHJlc3VsdCA9ICcnOwogICAgICAgICAgaWYgKCFzdHJpbmcgfHwgbiA8IDEgfHwgbiA+IE1BWF9TQUZFX0lOVEVHRVIpIHsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIC8vIExldmVyYWdlIHRoZSBleHBvbmVudGlhdGlvbiBieSBzcXVhcmluZyBhbGdvcml0aG0gZm9yIGEgZmFzdGVyIHJlcGVhdC4KICAgICAgICAgIC8vIFNlZSBodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9FeHBvbmVudGlhdGlvbl9ieV9zcXVhcmluZyBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAgZG8gewogICAgICAgICAgICBpZiAobiAlIDIpIHsKICAgICAgICAgICAgICByZXN1bHQgKz0gc3RyaW5nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG4gPSBuYXRpdmVGbG9vcihuIC8gMik7CiAgICAgICAgICAgIGlmIChuKSB7CiAgICAgICAgICAgICAgc3RyaW5nICs9IHN0cmluZzsKICAgICAgICAgICAgfQogICAgICAgICAgfSB3aGlsZSAobik7CgogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnJlc3RgIHdoaWNoIGRvZXNuJ3QgdmFsaWRhdGUgb3IgY29lcmNlIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gYXBwbHkgYSByZXN0IHBhcmFtZXRlciB0by4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PWZ1bmMubGVuZ3RoLTFdIFRoZSBzdGFydCBwb3NpdGlvbiBvZiB0aGUgcmVzdCBwYXJhbWV0ZXIuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVJlc3QoZnVuYywgc3RhcnQpIHsKICAgICAgICAgIHJldHVybiBzZXRUb1N0cmluZyhvdmVyUmVzdChmdW5jLCBzdGFydCwgaWRlbnRpdHkpLCBmdW5jICsgJycpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc2FtcGxlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gc2FtcGxlLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByYW5kb20gZWxlbWVudC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlU2FtcGxlKGNvbGxlY3Rpb24pIHsKICAgICAgICAgIHJldHVybiBhcnJheVNhbXBsZSh2YWx1ZXMoY29sbGVjdGlvbikpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc2FtcGxlU2l6ZWAgd2l0aG91dCBwYXJhbSBndWFyZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIHNhbXBsZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbiBUaGUgbnVtYmVyIG9mIGVsZW1lbnRzIHRvIHNhbXBsZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHJhbmRvbSBlbGVtZW50cy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlU2FtcGxlU2l6ZShjb2xsZWN0aW9uLCBuKSB7CiAgICAgICAgICB2YXIgYXJyYXkgPSB2YWx1ZXMoY29sbGVjdGlvbik7CiAgICAgICAgICByZXR1cm4gc2h1ZmZsZVNlbGYoYXJyYXksIGJhc2VDbGFtcChuLCAwLCBhcnJheS5sZW5ndGgpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnNldGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIHNldC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgcGF0aCBjcmVhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VTZXQob2JqZWN0LCBwYXRoLCB2YWx1ZSwgY3VzdG9taXplcikgewogICAgICAgICAgaWYgKCFpc09iamVjdChvYmplY3QpKSB7CiAgICAgICAgICAgIHJldHVybiBvYmplY3Q7CiAgICAgICAgICB9CiAgICAgICAgICBwYXRoID0gY2FzdFBhdGgocGF0aCwgb2JqZWN0KTsKCiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSBwYXRoLmxlbmd0aCwKICAgICAgICAgICAgICBsYXN0SW5kZXggPSBsZW5ndGggLSAxLAogICAgICAgICAgICAgIG5lc3RlZCA9IG9iamVjdDsKCiAgICAgICAgICB3aGlsZSAobmVzdGVkICE9IG51bGwgJiYgKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIga2V5ID0gdG9LZXkocGF0aFtpbmRleF0pLAogICAgICAgICAgICAgICAgbmV3VmFsdWUgPSB2YWx1ZTsKCiAgICAgICAgICAgIGlmIChrZXkgPT09ICdfX3Byb3RvX18nIHx8IGtleSA9PT0gJ2NvbnN0cnVjdG9yJyB8fCBrZXkgPT09ICdwcm90b3R5cGUnKSB7CiAgICAgICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgaWYgKGluZGV4ICE9IGxhc3RJbmRleCkgewogICAgICAgICAgICAgIHZhciBvYmpWYWx1ZSA9IG5lc3RlZFtrZXldOwogICAgICAgICAgICAgIG5ld1ZhbHVlID0gY3VzdG9taXplciA/IGN1c3RvbWl6ZXIob2JqVmFsdWUsIGtleSwgbmVzdGVkKSA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgICAgIGlmIChuZXdWYWx1ZSA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICAgIG5ld1ZhbHVlID0gaXNPYmplY3Qob2JqVmFsdWUpCiAgICAgICAgICAgICAgICAgID8gb2JqVmFsdWUKICAgICAgICAgICAgICAgICAgOiAoaXNJbmRleChwYXRoW2luZGV4ICsgMV0pID8gW10gOiB7fSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGFzc2lnblZhbHVlKG5lc3RlZCwga2V5LCBuZXdWYWx1ZSk7CiAgICAgICAgICAgIG5lc3RlZCA9IG5lc3RlZFtrZXldOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBzZXREYXRhYCB3aXRob3V0IHN1cHBvcnQgZm9yIGhvdCBsb29wIHNob3J0aW5nLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBhc3NvY2lhdGUgbWV0YWRhdGEgd2l0aC4KICAgICAgICAgKiBAcGFyYW0geyp9IGRhdGEgVGhlIG1ldGFkYXRhLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyBgZnVuY2AuCiAgICAgICAgICovCiAgICAgICAgdmFyIGJhc2VTZXREYXRhID0gIW1ldGFNYXAgPyBpZGVudGl0eSA6IGZ1bmN0aW9uKGZ1bmMsIGRhdGEpIHsKICAgICAgICAgIG1ldGFNYXAuc2V0KGZ1bmMsIGRhdGEpOwogICAgICAgICAgcmV0dXJuIGZ1bmM7CiAgICAgICAgfTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYHNldFRvU3RyaW5nYCB3aXRob3V0IHN1cHBvcnQgZm9yIGhvdCBsb29wIHNob3J0aW5nLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gc3RyaW5nIFRoZSBgdG9TdHJpbmdgIHJlc3VsdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgYGZ1bmNgLgogICAgICAgICAqLwogICAgICAgIHZhciBiYXNlU2V0VG9TdHJpbmcgPSAhZGVmaW5lUHJvcGVydHkgPyBpZGVudGl0eSA6IGZ1bmN0aW9uKGZ1bmMsIHN0cmluZykgewogICAgICAgICAgcmV0dXJuIGRlZmluZVByb3BlcnR5KGZ1bmMsICd0b1N0cmluZycsIHsKICAgICAgICAgICAgJ2NvbmZpZ3VyYWJsZSc6IHRydWUsCiAgICAgICAgICAgICdlbnVtZXJhYmxlJzogZmFsc2UsCiAgICAgICAgICAgICd2YWx1ZSc6IGNvbnN0YW50KHN0cmluZyksCiAgICAgICAgICAgICd3cml0YWJsZSc6IHRydWUKICAgICAgICAgIH0pOwogICAgICAgIH07CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnNodWZmbGVgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBzaHVmZmxlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IHNodWZmbGVkIGFycmF5LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VTaHVmZmxlKGNvbGxlY3Rpb24pIHsKICAgICAgICAgIHJldHVybiBzaHVmZmxlU2VsZih2YWx1ZXMoY29sbGVjdGlvbikpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc2xpY2VgIHdpdGhvdXQgYW4gaXRlcmF0ZWUgY2FsbCBndWFyZC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHNsaWNlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbc3RhcnQ9MF0gVGhlIHN0YXJ0IHBvc2l0aW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZW5kPWFycmF5Lmxlbmd0aF0gVGhlIGVuZCBwb3NpdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHNsaWNlIG9mIGBhcnJheWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVNsaWNlKGFycmF5LCBzdGFydCwgZW5kKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICAgICAgaWYgKHN0YXJ0IDwgMCkgewogICAgICAgICAgICBzdGFydCA9IC1zdGFydCA+IGxlbmd0aCA/IDAgOiAobGVuZ3RoICsgc3RhcnQpOwogICAgICAgICAgfQogICAgICAgICAgZW5kID0gZW5kID4gbGVuZ3RoID8gbGVuZ3RoIDogZW5kOwogICAgICAgICAgaWYgKGVuZCA8IDApIHsKICAgICAgICAgICAgZW5kICs9IGxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIGxlbmd0aCA9IHN0YXJ0ID4gZW5kID8gMCA6ICgoZW5kIC0gc3RhcnQpID4+PiAwKTsKICAgICAgICAgIHN0YXJ0ID4+Pj0gMDsKCiAgICAgICAgICB2YXIgcmVzdWx0ID0gQXJyYXkobGVuZ3RoKTsKICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIHJlc3VsdFtpbmRleF0gPSBhcnJheVtpbmRleCArIHN0YXJ0XTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5zb21lYCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBwcmVkaWNhdGUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYW55IGVsZW1lbnQgcGFzc2VzIHRoZSBwcmVkaWNhdGUgY2hlY2ssCiAgICAgICAgICogIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlU29tZShjb2xsZWN0aW9uLCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHZhciByZXN1bHQ7CgogICAgICAgICAgYmFzZUVhY2goY29sbGVjdGlvbiwgZnVuY3Rpb24odmFsdWUsIGluZGV4LCBjb2xsZWN0aW9uKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IHByZWRpY2F0ZSh2YWx1ZSwgaW5kZXgsIGNvbGxlY3Rpb24pOwogICAgICAgICAgICByZXR1cm4gIXJlc3VsdDsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuICEhcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc29ydGVkSW5kZXhgIGFuZCBgXy5zb3J0ZWRMYXN0SW5kZXhgIHdoaWNoCiAgICAgICAgICogcGVyZm9ybXMgYSBiaW5hcnkgc2VhcmNoIG9mIGBhcnJheWAgdG8gZGV0ZXJtaW5lIHRoZSBpbmRleCBhdCB3aGljaCBgdmFsdWVgCiAgICAgICAgICogc2hvdWxkIGJlIGluc2VydGVkIGludG8gYGFycmF5YCBpbiBvcmRlciB0byBtYWludGFpbiBpdHMgc29ydCBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIHNvcnRlZCBhcnJheSB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGV2YWx1YXRlLgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW3JldEhpZ2hlc3RdIFNwZWNpZnkgcmV0dXJuaW5nIHRoZSBoaWdoZXN0IHF1YWxpZmllZCBpbmRleC4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBhdCB3aGljaCBgdmFsdWVgIHNob3VsZCBiZSBpbnNlcnRlZAogICAgICAgICAqICBpbnRvIGBhcnJheWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVNvcnRlZEluZGV4KGFycmF5LCB2YWx1ZSwgcmV0SGlnaGVzdCkgewogICAgICAgICAgdmFyIGxvdyA9IDAsCiAgICAgICAgICAgICAgaGlnaCA9IGFycmF5ID09IG51bGwgPyBsb3cgOiBhcnJheS5sZW5ndGg7CgogICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnbnVtYmVyJyAmJiB2YWx1ZSA9PT0gdmFsdWUgJiYgaGlnaCA8PSBIQUxGX01BWF9BUlJBWV9MRU5HVEgpIHsKICAgICAgICAgICAgd2hpbGUgKGxvdyA8IGhpZ2gpIHsKICAgICAgICAgICAgICB2YXIgbWlkID0gKGxvdyArIGhpZ2gpID4+PiAxLAogICAgICAgICAgICAgICAgICBjb21wdXRlZCA9IGFycmF5W21pZF07CgogICAgICAgICAgICAgIGlmIChjb21wdXRlZCAhPT0gbnVsbCAmJiAhaXNTeW1ib2woY29tcHV0ZWQpICYmCiAgICAgICAgICAgICAgICAgIChyZXRIaWdoZXN0ID8gKGNvbXB1dGVkIDw9IHZhbHVlKSA6IChjb21wdXRlZCA8IHZhbHVlKSkpIHsKICAgICAgICAgICAgICAgIGxvdyA9IG1pZCArIDE7CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIGhpZ2ggPSBtaWQ7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBoaWdoOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VTb3J0ZWRJbmRleEJ5KGFycmF5LCB2YWx1ZSwgaWRlbnRpdHksIHJldEhpZ2hlc3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uc29ydGVkSW5kZXhCeWAgYW5kIGBfLnNvcnRlZExhc3RJbmRleEJ5YAogICAgICAgICAqIHdoaWNoIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgYHZhbHVlYCBhbmQgZWFjaCBlbGVtZW50IG9mIGBhcnJheWAgdG8gY29tcHV0ZQogICAgICAgICAqIHRoZWlyIHNvcnQgcmFua2luZy4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ7ICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBzb3J0ZWQgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBldmFsdWF0ZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtyZXRIaWdoZXN0XSBTcGVjaWZ5IHJldHVybmluZyB0aGUgaGlnaGVzdCBxdWFsaWZpZWQgaW5kZXguCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggYXQgd2hpY2ggYHZhbHVlYCBzaG91bGQgYmUgaW5zZXJ0ZWQKICAgICAgICAgKiAgaW50byBgYXJyYXlgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VTb3J0ZWRJbmRleEJ5KGFycmF5LCB2YWx1ZSwgaXRlcmF0ZWUsIHJldEhpZ2hlc3QpIHsKICAgICAgICAgIHZhciBsb3cgPSAwLAogICAgICAgICAgICAgIGhpZ2ggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmIChoaWdoID09PSAwKSB7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgfQoKICAgICAgICAgIHZhbHVlID0gaXRlcmF0ZWUodmFsdWUpOwogICAgICAgICAgdmFyIHZhbElzTmFOID0gdmFsdWUgIT09IHZhbHVlLAogICAgICAgICAgICAgIHZhbElzTnVsbCA9IHZhbHVlID09PSBudWxsLAogICAgICAgICAgICAgIHZhbElzU3ltYm9sID0gaXNTeW1ib2wodmFsdWUpLAogICAgICAgICAgICAgIHZhbElzVW5kZWZpbmVkID0gdmFsdWUgPT09IHVuZGVmaW5lZCQxOwoKICAgICAgICAgIHdoaWxlIChsb3cgPCBoaWdoKSB7CiAgICAgICAgICAgIHZhciBtaWQgPSBuYXRpdmVGbG9vcigobG93ICsgaGlnaCkgLyAyKSwKICAgICAgICAgICAgICAgIGNvbXB1dGVkID0gaXRlcmF0ZWUoYXJyYXlbbWlkXSksCiAgICAgICAgICAgICAgICBvdGhJc0RlZmluZWQgPSBjb21wdXRlZCAhPT0gdW5kZWZpbmVkJDEsCiAgICAgICAgICAgICAgICBvdGhJc051bGwgPSBjb21wdXRlZCA9PT0gbnVsbCwKICAgICAgICAgICAgICAgIG90aElzUmVmbGV4aXZlID0gY29tcHV0ZWQgPT09IGNvbXB1dGVkLAogICAgICAgICAgICAgICAgb3RoSXNTeW1ib2wgPSBpc1N5bWJvbChjb21wdXRlZCk7CgogICAgICAgICAgICBpZiAodmFsSXNOYU4pIHsKICAgICAgICAgICAgICB2YXIgc2V0TG93ID0gcmV0SGlnaGVzdCB8fCBvdGhJc1JlZmxleGl2ZTsKICAgICAgICAgICAgfSBlbHNlIGlmICh2YWxJc1VuZGVmaW5lZCkgewogICAgICAgICAgICAgIHNldExvdyA9IG90aElzUmVmbGV4aXZlICYmIChyZXRIaWdoZXN0IHx8IG90aElzRGVmaW5lZCk7CiAgICAgICAgICAgIH0gZWxzZSBpZiAodmFsSXNOdWxsKSB7CiAgICAgICAgICAgICAgc2V0TG93ID0gb3RoSXNSZWZsZXhpdmUgJiYgb3RoSXNEZWZpbmVkICYmIChyZXRIaWdoZXN0IHx8ICFvdGhJc051bGwpOwogICAgICAgICAgICB9IGVsc2UgaWYgKHZhbElzU3ltYm9sKSB7CiAgICAgICAgICAgICAgc2V0TG93ID0gb3RoSXNSZWZsZXhpdmUgJiYgb3RoSXNEZWZpbmVkICYmICFvdGhJc051bGwgJiYgKHJldEhpZ2hlc3QgfHwgIW90aElzU3ltYm9sKTsKICAgICAgICAgICAgfSBlbHNlIGlmIChvdGhJc051bGwgfHwgb3RoSXNTeW1ib2wpIHsKICAgICAgICAgICAgICBzZXRMb3cgPSBmYWxzZTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBzZXRMb3cgPSByZXRIaWdoZXN0ID8gKGNvbXB1dGVkIDw9IHZhbHVlKSA6IChjb21wdXRlZCA8IHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc2V0TG93KSB7CiAgICAgICAgICAgICAgbG93ID0gbWlkICsgMTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBoaWdoID0gbWlkOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbmF0aXZlTWluKGhpZ2gsIE1BWF9BUlJBWV9JTkRFWCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5zb3J0ZWRVbmlxYCBhbmQgYF8uc29ydGVkVW5pcUJ5YCB3aXRob3V0CiAgICAgICAgICogc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlXSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBkdXBsaWNhdGUgZnJlZSBhcnJheS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlU29ydGVkVW5pcShhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5Lmxlbmd0aCwKICAgICAgICAgICAgICByZXNJbmRleCA9IDAsCiAgICAgICAgICAgICAgcmVzdWx0ID0gW107CgogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdLAogICAgICAgICAgICAgICAgY29tcHV0ZWQgPSBpdGVyYXRlZSA/IGl0ZXJhdGVlKHZhbHVlKSA6IHZhbHVlOwoKICAgICAgICAgICAgaWYgKCFpbmRleCB8fCAhZXEoY29tcHV0ZWQsIHNlZW4pKSB7CiAgICAgICAgICAgICAgdmFyIHNlZW4gPSBjb21wdXRlZDsKICAgICAgICAgICAgICByZXN1bHRbcmVzSW5kZXgrK10gPSB2YWx1ZSA9PT0gMCA/IDAgOiB2YWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnRvTnVtYmVyYCB3aGljaCBkb2Vzbid0IGVuc3VyZSBjb3JyZWN0CiAgICAgICAgICogY29udmVyc2lvbnMgb2YgYmluYXJ5LCBoZXhhZGVjaW1hbCwgb3Igb2N0YWwgc3RyaW5nIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcHJvY2Vzcy4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBudW1iZXIuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVRvTnVtYmVyKHZhbHVlKSB7CiAgICAgICAgICBpZiAodHlwZW9mIHZhbHVlID09ICdudW1iZXInKSB7CiAgICAgICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChpc1N5bWJvbCh2YWx1ZSkpIHsKICAgICAgICAgICAgcmV0dXJuIE5BTjsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiArdmFsdWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy50b1N0cmluZ2Agd2hpY2ggZG9lc24ndCBjb252ZXJ0IG51bGxpc2gKICAgICAgICAgKiB2YWx1ZXMgdG8gZW1wdHkgc3RyaW5ncy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcHJvY2Vzcy4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBzdHJpbmcuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVRvU3RyaW5nKHZhbHVlKSB7CiAgICAgICAgICAvLyBFeGl0IGVhcmx5IGZvciBzdHJpbmdzIHRvIGF2b2lkIGEgcGVyZm9ybWFuY2UgaGl0IGluIHNvbWUgZW52aXJvbm1lbnRzLgogICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJykgewogICAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNBcnJheSh2YWx1ZSkpIHsKICAgICAgICAgICAgLy8gUmVjdXJzaXZlbHkgY29udmVydCB2YWx1ZXMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgcmV0dXJuIGFycmF5TWFwKHZhbHVlLCBiYXNlVG9TdHJpbmcpICsgJyc7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNTeW1ib2wodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiBzeW1ib2xUb1N0cmluZyA/IHN5bWJvbFRvU3RyaW5nLmNhbGwodmFsdWUpIDogJyc7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcmVzdWx0ID0gKHZhbHVlICsgJycpOwogICAgICAgICAgcmV0dXJuIChyZXN1bHQgPT0gJzAnICYmICgxIC8gdmFsdWUpID09IC1JTkZJTklUWSkgPyAnLTAnIDogcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8udW5pcUJ5YCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2NvbXBhcmF0b3JdIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZHVwbGljYXRlIGZyZWUgYXJyYXkuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVVuaXEoYXJyYXksIGl0ZXJhdGVlLCBjb21wYXJhdG9yKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBpbmNsdWRlcyA9IGFycmF5SW5jbHVkZXMsCiAgICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIGlzQ29tbW9uID0gdHJ1ZSwKICAgICAgICAgICAgICByZXN1bHQgPSBbXSwKICAgICAgICAgICAgICBzZWVuID0gcmVzdWx0OwoKICAgICAgICAgIGlmIChjb21wYXJhdG9yKSB7CiAgICAgICAgICAgIGlzQ29tbW9uID0gZmFsc2U7CiAgICAgICAgICAgIGluY2x1ZGVzID0gYXJyYXlJbmNsdWRlc1dpdGg7CiAgICAgICAgICB9CiAgICAgICAgICBlbHNlIGlmIChsZW5ndGggPj0gTEFSR0VfQVJSQVlfU0laRSkgewogICAgICAgICAgICB2YXIgc2V0ID0gaXRlcmF0ZWUgPyBudWxsIDogY3JlYXRlU2V0KGFycmF5KTsKICAgICAgICAgICAgaWYgKHNldCkgewogICAgICAgICAgICAgIHJldHVybiBzZXRUb0FycmF5KHNldCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaXNDb21tb24gPSBmYWxzZTsKICAgICAgICAgICAgaW5jbHVkZXMgPSBjYWNoZUhhczsKICAgICAgICAgICAgc2VlbiA9IG5ldyBTZXRDYWNoZTsKICAgICAgICAgIH0KICAgICAgICAgIGVsc2UgewogICAgICAgICAgICBzZWVuID0gaXRlcmF0ZWUgPyBbXSA6IHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIG91dGVyOgogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdLAogICAgICAgICAgICAgICAgY29tcHV0ZWQgPSBpdGVyYXRlZSA/IGl0ZXJhdGVlKHZhbHVlKSA6IHZhbHVlOwoKICAgICAgICAgICAgdmFsdWUgPSAoY29tcGFyYXRvciB8fCB2YWx1ZSAhPT0gMCkgPyB2YWx1ZSA6IDA7CiAgICAgICAgICAgIGlmIChpc0NvbW1vbiAmJiBjb21wdXRlZCA9PT0gY29tcHV0ZWQpIHsKICAgICAgICAgICAgICB2YXIgc2VlbkluZGV4ID0gc2Vlbi5sZW5ndGg7CiAgICAgICAgICAgICAgd2hpbGUgKHNlZW5JbmRleC0tKSB7CiAgICAgICAgICAgICAgICBpZiAoc2VlbltzZWVuSW5kZXhdID09PSBjb21wdXRlZCkgewogICAgICAgICAgICAgICAgICBjb250aW51ZSBvdXRlcjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKGl0ZXJhdGVlKSB7CiAgICAgICAgICAgICAgICBzZWVuLnB1c2goY29tcHV0ZWQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXN1bHQucHVzaCh2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoIWluY2x1ZGVzKHNlZW4sIGNvbXB1dGVkLCBjb21wYXJhdG9yKSkgewogICAgICAgICAgICAgIGlmIChzZWVuICE9PSByZXN1bHQpIHsKICAgICAgICAgICAgICAgIHNlZW4ucHVzaChjb21wdXRlZCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHJlc3VsdC5wdXNoKHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnVuc2V0YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcHJvcGVydHkgcGF0aCB0byB1bnNldC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIHByb3BlcnR5IGlzIGRlbGV0ZWQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlVW5zZXQob2JqZWN0LCBwYXRoKSB7CiAgICAgICAgICBwYXRoID0gY2FzdFBhdGgocGF0aCwgb2JqZWN0KTsKICAgICAgICAgIG9iamVjdCA9IHBhcmVudChvYmplY3QsIHBhdGgpOwogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsIHx8IGRlbGV0ZSBvYmplY3RbdG9LZXkobGFzdChwYXRoKSldOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8udXBkYXRlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gdXBkYXRlLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHVwZGF0ZXIgVGhlIGZ1bmN0aW9uIHRvIHByb2R1Y2UgdGhlIHVwZGF0ZWQgdmFsdWUuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgcGF0aCBjcmVhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VVcGRhdGUob2JqZWN0LCBwYXRoLCB1cGRhdGVyLCBjdXN0b21pemVyKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVNldChvYmplY3QsIHBhdGgsIHVwZGF0ZXIoYmFzZUdldChvYmplY3QsIHBhdGgpKSwgY3VzdG9taXplcik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBtZXRob2RzIGxpa2UgYF8uZHJvcFdoaWxlYCBhbmQgYF8udGFrZVdoaWxlYAogICAgICAgICAqIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2lzRHJvcF0gU3BlY2lmeSBkcm9wcGluZyBlbGVtZW50cyBpbnN0ZWFkIG9mIHRha2luZyB0aGVtLgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2Zyb21SaWdodF0gU3BlY2lmeSBpdGVyYXRpbmcgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc2xpY2Ugb2YgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlV2hpbGUoYXJyYXksIHByZWRpY2F0ZSwgaXNEcm9wLCBmcm9tUmlnaHQpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgICAgaW5kZXggPSBmcm9tUmlnaHQgPyBsZW5ndGggOiAtMTsKCiAgICAgICAgICB3aGlsZSAoKGZyb21SaWdodCA/IGluZGV4LS0gOiArK2luZGV4IDwgbGVuZ3RoKSAmJgogICAgICAgICAgICBwcmVkaWNhdGUoYXJyYXlbaW5kZXhdLCBpbmRleCwgYXJyYXkpKSB7fQoKICAgICAgICAgIHJldHVybiBpc0Ryb3AKICAgICAgICAgICAgPyBiYXNlU2xpY2UoYXJyYXksIChmcm9tUmlnaHQgPyAwIDogaW5kZXgpLCAoZnJvbVJpZ2h0ID8gaW5kZXggKyAxIDogbGVuZ3RoKSkKICAgICAgICAgICAgOiBiYXNlU2xpY2UoYXJyYXksIChmcm9tUmlnaHQgPyBpbmRleCArIDEgOiAwKSwgKGZyb21SaWdodCA/IGxlbmd0aCA6IGluZGV4KSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgd3JhcHBlclZhbHVlYCB3aGljaCByZXR1cm5zIHRoZSByZXN1bHQgb2YKICAgICAgICAgKiBwZXJmb3JtaW5nIGEgc2VxdWVuY2Ugb2YgYWN0aW9ucyBvbiB0aGUgdW53cmFwcGVkIGB2YWx1ZWAsIHdoZXJlIGVhY2gKICAgICAgICAgKiBzdWNjZXNzaXZlIGFjdGlvbiBpcyBzdXBwbGllZCB0aGUgcmV0dXJuIHZhbHVlIG9mIHRoZSBwcmV2aW91cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdW53cmFwcGVkIHZhbHVlLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFjdGlvbnMgQWN0aW9ucyB0byBwZXJmb3JtIHRvIHJlc29sdmUgdGhlIHVud3JhcHBlZCB2YWx1ZS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgcmVzb2x2ZWQgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYmFzZVdyYXBwZXJWYWx1ZSh2YWx1ZSwgYWN0aW9ucykgewogICAgICAgICAgdmFyIHJlc3VsdCA9IHZhbHVlOwogICAgICAgICAgaWYgKHJlc3VsdCBpbnN0YW5jZW9mIExhenlXcmFwcGVyKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IHJlc3VsdC52YWx1ZSgpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGFycmF5UmVkdWNlKGFjdGlvbnMsIGZ1bmN0aW9uKHJlc3VsdCwgYWN0aW9uKSB7CiAgICAgICAgICAgIHJldHVybiBhY3Rpb24uZnVuYy5hcHBseShhY3Rpb24udGhpc0FyZywgYXJyYXlQdXNoKFtyZXN1bHRdLCBhY3Rpb24uYXJncykpOwogICAgICAgICAgfSwgcmVzdWx0KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIG1ldGhvZHMgbGlrZSBgXy54b3JgLCB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgICAgICogaXRlcmF0ZWUgc2hvcnRoYW5kcywgdGhhdCBhY2NlcHRzIGFuIGFycmF5IG9mIGFycmF5cyB0byBpbnNwZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheXMgVGhlIGFycmF5cyB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2NvbXBhcmF0b3JdIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgdmFsdWVzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJhc2VYb3IoYXJyYXlzLCBpdGVyYXRlZSwgY29tcGFyYXRvcikgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5cy5sZW5ndGg7CiAgICAgICAgICBpZiAobGVuZ3RoIDwgMikgewogICAgICAgICAgICByZXR1cm4gbGVuZ3RoID8gYmFzZVVuaXEoYXJyYXlzWzBdKSA6IFtdOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgcmVzdWx0ID0gQXJyYXkobGVuZ3RoKTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgYXJyYXkgPSBhcnJheXNbaW5kZXhdLAogICAgICAgICAgICAgICAgb3RoSW5kZXggPSAtMTsKCiAgICAgICAgICAgIHdoaWxlICgrK290aEluZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgICAgaWYgKG90aEluZGV4ICE9IGluZGV4KSB7CiAgICAgICAgICAgICAgICByZXN1bHRbaW5kZXhdID0gYmFzZURpZmZlcmVuY2UocmVzdWx0W2luZGV4XSB8fCBhcnJheSwgYXJyYXlzW290aEluZGV4XSwgaXRlcmF0ZWUsIGNvbXBhcmF0b3IpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VVbmlxKGJhc2VGbGF0dGVuKHJlc3VsdCwgMSksIGl0ZXJhdGVlLCBjb21wYXJhdG9yKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy56aXBPYmplY3RgIHdoaWNoIGFzc2lnbnMgdmFsdWVzIHVzaW5nIGBhc3NpZ25GdW5jYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gcHJvcHMgVGhlIHByb3BlcnR5IGlkZW50aWZpZXJzLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHZhbHVlcyBUaGUgcHJvcGVydHkgdmFsdWVzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGFzc2lnbkZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGFzc2lnbiB2YWx1ZXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV3IG9iamVjdC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBiYXNlWmlwT2JqZWN0KHByb3BzLCB2YWx1ZXMsIGFzc2lnbkZ1bmMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IHByb3BzLmxlbmd0aCwKICAgICAgICAgICAgICB2YWxzTGVuZ3RoID0gdmFsdWVzLmxlbmd0aCwKICAgICAgICAgICAgICByZXN1bHQgPSB7fTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSBpbmRleCA8IHZhbHNMZW5ndGggPyB2YWx1ZXNbaW5kZXhdIDogdW5kZWZpbmVkJDE7CiAgICAgICAgICAgIGFzc2lnbkZ1bmMocmVzdWx0LCBwcm9wc1tpbmRleF0sIHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDYXN0cyBgdmFsdWVgIHRvIGFuIGVtcHR5IGFycmF5IGlmIGl0J3Mgbm90IGFuIGFycmF5IGxpa2Ugb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBpbnNwZWN0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheXxPYmplY3R9IFJldHVybnMgdGhlIGNhc3QgYXJyYXktbGlrZSBvYmplY3QuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2FzdEFycmF5TGlrZU9iamVjdCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlT2JqZWN0KHZhbHVlKSA/IHZhbHVlIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDYXN0cyBgdmFsdWVgIHRvIGBpZGVudGl0eWAgaWYgaXQncyBub3QgYSBmdW5jdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgY2FzdCBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjYXN0RnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIHJldHVybiB0eXBlb2YgdmFsdWUgPT0gJ2Z1bmN0aW9uJyA/IHZhbHVlIDogaWRlbnRpdHk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDYXN0cyBgdmFsdWVgIHRvIGEgcGF0aCBhcnJheSBpZiBpdCdzIG5vdCBvbmUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3RdIFRoZSBvYmplY3QgdG8gcXVlcnkga2V5cyBvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGNhc3QgcHJvcGVydHkgcGF0aCBhcnJheS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjYXN0UGF0aCh2YWx1ZSwgb2JqZWN0KSB7CiAgICAgICAgICBpZiAoaXNBcnJheSh2YWx1ZSkpIHsKICAgICAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGlzS2V5KHZhbHVlLCBvYmplY3QpID8gW3ZhbHVlXSA6IHN0cmluZ1RvUGF0aCh0b1N0cmluZyh2YWx1ZSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBgYmFzZVJlc3RgIGFsaWFzIHdoaWNoIGNhbiBiZSByZXBsYWNlZCB3aXRoIGBpZGVudGl0eWAgYnkgbW9kdWxlCiAgICAgICAgICogcmVwbGFjZW1lbnQgcGx1Z2lucy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHR5cGUge0Z1bmN0aW9ufQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGFwcGx5IGEgcmVzdCBwYXJhbWV0ZXIgdG8uCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgdmFyIGNhc3RSZXN0ID0gYmFzZVJlc3Q7CgogICAgICAgIC8qKgogICAgICAgICAqIENhc3RzIGBhcnJheWAgdG8gYSBzbGljZSBpZiBpdCdzIG5lZWRlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHN0YXJ0IFRoZSBzdGFydCBwb3NpdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2VuZD1hcnJheS5sZW5ndGhdIFRoZSBlbmQgcG9zaXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBjYXN0IHNsaWNlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNhc3RTbGljZShhcnJheSwgc3RhcnQsIGVuZCkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGVuZCA9IGVuZCA9PT0gdW5kZWZpbmVkJDEgPyBsZW5ndGggOiBlbmQ7CiAgICAgICAgICByZXR1cm4gKCFzdGFydCAmJiBlbmQgPj0gbGVuZ3RoKSA/IGFycmF5IDogYmFzZVNsaWNlKGFycmF5LCBzdGFydCwgZW5kKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEEgc2ltcGxlIHdyYXBwZXIgYXJvdW5kIHRoZSBnbG9iYWwgW2BjbGVhclRpbWVvdXRgXShodHRwczovL21kbi5pby9jbGVhclRpbWVvdXQpLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge251bWJlcnxPYmplY3R9IGlkIFRoZSB0aW1lciBpZCBvciB0aW1lb3V0IG9iamVjdCBvZiB0aGUgdGltZXIgdG8gY2xlYXIuCiAgICAgICAgICovCiAgICAgICAgdmFyIGNsZWFyVGltZW91dCA9IGN0eENsZWFyVGltZW91dCB8fCBmdW5jdGlvbihpZCkgewogICAgICAgICAgcmV0dXJuIHJvb3QuY2xlYXJUaW1lb3V0KGlkKTsKICAgICAgICB9OwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgIGBidWZmZXJgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0J1ZmZlcn0gYnVmZmVyIFRoZSBidWZmZXIgdG8gY2xvbmUuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbaXNEZWVwXSBTcGVjaWZ5IGEgZGVlcCBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7QnVmZmVyfSBSZXR1cm5zIHRoZSBjbG9uZWQgYnVmZmVyLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNsb25lQnVmZmVyKGJ1ZmZlciwgaXNEZWVwKSB7CiAgICAgICAgICBpZiAoaXNEZWVwKSB7CiAgICAgICAgICAgIHJldHVybiBidWZmZXIuc2xpY2UoKTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBsZW5ndGggPSBidWZmZXIubGVuZ3RoLAogICAgICAgICAgICAgIHJlc3VsdCA9IGFsbG9jVW5zYWZlID8gYWxsb2NVbnNhZmUobGVuZ3RoKSA6IG5ldyBidWZmZXIuY29uc3RydWN0b3IobGVuZ3RoKTsKCiAgICAgICAgICBidWZmZXIuY29weShyZXN1bHQpOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBjbG9uZSBvZiBgYXJyYXlCdWZmZXJgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5QnVmZmVyfSBhcnJheUJ1ZmZlciBUaGUgYXJyYXkgYnVmZmVyIHRvIGNsb25lLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheUJ1ZmZlcn0gUmV0dXJucyB0aGUgY2xvbmVkIGFycmF5IGJ1ZmZlci4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjbG9uZUFycmF5QnVmZmVyKGFycmF5QnVmZmVyKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gbmV3IGFycmF5QnVmZmVyLmNvbnN0cnVjdG9yKGFycmF5QnVmZmVyLmJ5dGVMZW5ndGgpOwogICAgICAgICAgbmV3IFVpbnQ4QXJyYXkocmVzdWx0KS5zZXQobmV3IFVpbnQ4QXJyYXkoYXJyYXlCdWZmZXIpKTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgYGRhdGFWaWV3YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IGRhdGFWaWV3IFRoZSBkYXRhIHZpZXcgdG8gY2xvbmUuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbaXNEZWVwXSBTcGVjaWZ5IGEgZGVlcCBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgZGF0YSB2aWV3LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNsb25lRGF0YVZpZXcoZGF0YVZpZXcsIGlzRGVlcCkgewogICAgICAgICAgdmFyIGJ1ZmZlciA9IGlzRGVlcCA/IGNsb25lQXJyYXlCdWZmZXIoZGF0YVZpZXcuYnVmZmVyKSA6IGRhdGFWaWV3LmJ1ZmZlcjsKICAgICAgICAgIHJldHVybiBuZXcgZGF0YVZpZXcuY29uc3RydWN0b3IoYnVmZmVyLCBkYXRhVmlldy5ieXRlT2Zmc2V0LCBkYXRhVmlldy5ieXRlTGVuZ3RoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBjbG9uZSBvZiBgcmVnZXhwYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHJlZ2V4cCBUaGUgcmVnZXhwIHRvIGNsb25lLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGNsb25lZCByZWdleHAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2xvbmVSZWdFeHAocmVnZXhwKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gbmV3IHJlZ2V4cC5jb25zdHJ1Y3RvcihyZWdleHAuc291cmNlLCByZUZsYWdzLmV4ZWMocmVnZXhwKSk7CiAgICAgICAgICByZXN1bHQubGFzdEluZGV4ID0gcmVnZXhwLmxhc3RJbmRleDsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgdGhlIGBzeW1ib2xgIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHN5bWJvbCBUaGUgc3ltYm9sIG9iamVjdCB0byBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgc3ltYm9sIG9iamVjdC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjbG9uZVN5bWJvbChzeW1ib2wpIHsKICAgICAgICAgIHJldHVybiBzeW1ib2xWYWx1ZU9mID8gT2JqZWN0KHN5bWJvbFZhbHVlT2YuY2FsbChzeW1ib2wpKSA6IHt9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGNsb25lIG9mIGB0eXBlZEFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHR5cGVkQXJyYXkgVGhlIHR5cGVkIGFycmF5IHRvIGNsb25lLgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2lzRGVlcF0gU3BlY2lmeSBhIGRlZXAgY2xvbmUuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY2xvbmVkIHR5cGVkIGFycmF5LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNsb25lVHlwZWRBcnJheSh0eXBlZEFycmF5LCBpc0RlZXApIHsKICAgICAgICAgIHZhciBidWZmZXIgPSBpc0RlZXAgPyBjbG9uZUFycmF5QnVmZmVyKHR5cGVkQXJyYXkuYnVmZmVyKSA6IHR5cGVkQXJyYXkuYnVmZmVyOwogICAgICAgICAgcmV0dXJuIG5ldyB0eXBlZEFycmF5LmNvbnN0cnVjdG9yKGJ1ZmZlciwgdHlwZWRBcnJheS5ieXRlT2Zmc2V0LCB0eXBlZEFycmF5Lmxlbmd0aCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wYXJlcyB2YWx1ZXMgdG8gc29ydCB0aGVtIGluIGFzY2VuZGluZyBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHNvcnQgb3JkZXIgaW5kaWNhdG9yIGZvciBgdmFsdWVgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNvbXBhcmVBc2NlbmRpbmcodmFsdWUsIG90aGVyKSB7CiAgICAgICAgICBpZiAodmFsdWUgIT09IG90aGVyKSB7CiAgICAgICAgICAgIHZhciB2YWxJc0RlZmluZWQgPSB2YWx1ZSAhPT0gdW5kZWZpbmVkJDEsCiAgICAgICAgICAgICAgICB2YWxJc051bGwgPSB2YWx1ZSA9PT0gbnVsbCwKICAgICAgICAgICAgICAgIHZhbElzUmVmbGV4aXZlID0gdmFsdWUgPT09IHZhbHVlLAogICAgICAgICAgICAgICAgdmFsSXNTeW1ib2wgPSBpc1N5bWJvbCh2YWx1ZSk7CgogICAgICAgICAgICB2YXIgb3RoSXNEZWZpbmVkID0gb3RoZXIgIT09IHVuZGVmaW5lZCQxLAogICAgICAgICAgICAgICAgb3RoSXNOdWxsID0gb3RoZXIgPT09IG51bGwsCiAgICAgICAgICAgICAgICBvdGhJc1JlZmxleGl2ZSA9IG90aGVyID09PSBvdGhlciwKICAgICAgICAgICAgICAgIG90aElzU3ltYm9sID0gaXNTeW1ib2wob3RoZXIpOwoKICAgICAgICAgICAgaWYgKCghb3RoSXNOdWxsICYmICFvdGhJc1N5bWJvbCAmJiAhdmFsSXNTeW1ib2wgJiYgdmFsdWUgPiBvdGhlcikgfHwKICAgICAgICAgICAgICAgICh2YWxJc1N5bWJvbCAmJiBvdGhJc0RlZmluZWQgJiYgb3RoSXNSZWZsZXhpdmUgJiYgIW90aElzTnVsbCAmJiAhb3RoSXNTeW1ib2wpIHx8CiAgICAgICAgICAgICAgICAodmFsSXNOdWxsICYmIG90aElzRGVmaW5lZCAmJiBvdGhJc1JlZmxleGl2ZSkgfHwKICAgICAgICAgICAgICAgICghdmFsSXNEZWZpbmVkICYmIG90aElzUmVmbGV4aXZlKSB8fAogICAgICAgICAgICAgICAgIXZhbElzUmVmbGV4aXZlKSB7CiAgICAgICAgICAgICAgcmV0dXJuIDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCghdmFsSXNOdWxsICYmICF2YWxJc1N5bWJvbCAmJiAhb3RoSXNTeW1ib2wgJiYgdmFsdWUgPCBvdGhlcikgfHwKICAgICAgICAgICAgICAgIChvdGhJc1N5bWJvbCAmJiB2YWxJc0RlZmluZWQgJiYgdmFsSXNSZWZsZXhpdmUgJiYgIXZhbElzTnVsbCAmJiAhdmFsSXNTeW1ib2wpIHx8CiAgICAgICAgICAgICAgICAob3RoSXNOdWxsICYmIHZhbElzRGVmaW5lZCAmJiB2YWxJc1JlZmxleGl2ZSkgfHwKICAgICAgICAgICAgICAgICghb3RoSXNEZWZpbmVkICYmIHZhbElzUmVmbGV4aXZlKSB8fAogICAgICAgICAgICAgICAgIW90aElzUmVmbGV4aXZlKSB7CiAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFVzZWQgYnkgYF8ub3JkZXJCeWAgdG8gY29tcGFyZSBtdWx0aXBsZSBwcm9wZXJ0aWVzIG9mIGEgdmFsdWUgdG8gYW5vdGhlcgogICAgICAgICAqIGFuZCBzdGFibGUgc29ydCB0aGVtLgogICAgICAgICAqCiAgICAgICAgICogSWYgYG9yZGVyc2AgaXMgdW5zcGVjaWZpZWQsIGFsbCB2YWx1ZXMgYXJlIHNvcnRlZCBpbiBhc2NlbmRpbmcgb3JkZXIuIE90aGVyd2lzZSwKICAgICAgICAgKiBzcGVjaWZ5IGFuIG9yZGVyIG9mICJkZXNjIiBmb3IgZGVzY2VuZGluZyBvciAiYXNjIiBmb3IgYXNjZW5kaW5nIHNvcnQgb3JkZXIKICAgICAgICAgKiBvZiBjb3JyZXNwb25kaW5nIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG90aGVyIFRoZSBvdGhlciBvYmplY3QgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW5bXXxzdHJpbmdbXX0gb3JkZXJzIFRoZSBvcmRlciB0byBzb3J0IGJ5IGZvciBlYWNoIHByb3BlcnR5LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHNvcnQgb3JkZXIgaW5kaWNhdG9yIGZvciBgb2JqZWN0YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb21wYXJlTXVsdGlwbGUob2JqZWN0LCBvdGhlciwgb3JkZXJzKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBvYmpDcml0ZXJpYSA9IG9iamVjdC5jcml0ZXJpYSwKICAgICAgICAgICAgICBvdGhDcml0ZXJpYSA9IG90aGVyLmNyaXRlcmlhLAogICAgICAgICAgICAgIGxlbmd0aCA9IG9iakNyaXRlcmlhLmxlbmd0aCwKICAgICAgICAgICAgICBvcmRlcnNMZW5ndGggPSBvcmRlcnMubGVuZ3RoOwoKICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIHZhciByZXN1bHQgPSBjb21wYXJlQXNjZW5kaW5nKG9iakNyaXRlcmlhW2luZGV4XSwgb3RoQ3JpdGVyaWFbaW5kZXhdKTsKICAgICAgICAgICAgaWYgKHJlc3VsdCkgewogICAgICAgICAgICAgIGlmIChpbmRleCA+PSBvcmRlcnNMZW5ndGgpIHsKICAgICAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHZhciBvcmRlciA9IG9yZGVyc1tpbmRleF07CiAgICAgICAgICAgICAgcmV0dXJuIHJlc3VsdCAqIChvcmRlciA9PSAnZGVzYycgPyAtMSA6IDEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICAvLyBGaXhlcyBhbiBgQXJyYXkjc29ydGAgYnVnIGluIHRoZSBKUyBlbmdpbmUgZW1iZWRkZWQgaW4gQWRvYmUgYXBwbGljYXRpb25zCiAgICAgICAgICAvLyB0aGF0IGNhdXNlcyBpdCwgdW5kZXIgY2VydGFpbiBjaXJjdW1zdGFuY2VzLCB0byBwcm92aWRlIHRoZSBzYW1lIHZhbHVlIGZvcgogICAgICAgICAgLy8gYG9iamVjdGAgYW5kIGBvdGhlcmAuIFNlZSBodHRwczovL2dpdGh1Yi5jb20vamFzaGtlbmFzL3VuZGVyc2NvcmUvcHVsbC8xMjQ3CiAgICAgICAgICAvLyBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAgLy8KICAgICAgICAgIC8vIFRoaXMgYWxzbyBlbnN1cmVzIGEgc3RhYmxlIHNvcnQgaW4gVjggYW5kIG90aGVyIGVuZ2luZXMuCiAgICAgICAgICAvLyBTZWUgaHR0cHM6Ly9idWdzLmNocm9taXVtLm9yZy9wL3Y4L2lzc3Vlcy9kZXRhaWw/aWQ9OTAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgIHJldHVybiBvYmplY3QuaW5kZXggLSBvdGhlci5pbmRleDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgdGhhdCBpcyB0aGUgY29tcG9zaXRpb24gb2YgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzLAogICAgICAgICAqIHBsYWNlaG9sZGVycywgYW5kIHByb3ZpZGVkIGFyZ3VtZW50cyBpbnRvIGEgc2luZ2xlIGFycmF5IG9mIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJncyBUaGUgcHJvdmlkZWQgYXJndW1lbnRzLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHBhcnRpYWxzIFRoZSBhcmd1bWVudHMgdG8gcHJlcGVuZCB0byB0aG9zZSBwcm92aWRlZC4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBob2xkZXJzIFRoZSBgcGFydGlhbHNgIHBsYWNlaG9sZGVyIGluZGV4ZXMuCiAgICAgICAgICogQHBhcmFtcyB7Ym9vbGVhbn0gW2lzQ3VycmllZF0gU3BlY2lmeSBjb21wb3NpbmcgZm9yIGEgY3VycmllZCBmdW5jdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBjb21wb3NlZCBhcmd1bWVudHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29tcG9zZUFyZ3MoYXJncywgcGFydGlhbHMsIGhvbGRlcnMsIGlzQ3VycmllZCkgewogICAgICAgICAgdmFyIGFyZ3NJbmRleCA9IC0xLAogICAgICAgICAgICAgIGFyZ3NMZW5ndGggPSBhcmdzLmxlbmd0aCwKICAgICAgICAgICAgICBob2xkZXJzTGVuZ3RoID0gaG9sZGVycy5sZW5ndGgsCiAgICAgICAgICAgICAgbGVmdEluZGV4ID0gLTEsCiAgICAgICAgICAgICAgbGVmdExlbmd0aCA9IHBhcnRpYWxzLmxlbmd0aCwKICAgICAgICAgICAgICByYW5nZUxlbmd0aCA9IG5hdGl2ZU1heChhcmdzTGVuZ3RoIC0gaG9sZGVyc0xlbmd0aCwgMCksCiAgICAgICAgICAgICAgcmVzdWx0ID0gQXJyYXkobGVmdExlbmd0aCArIHJhbmdlTGVuZ3RoKSwKICAgICAgICAgICAgICBpc1VuY3VycmllZCA9ICFpc0N1cnJpZWQ7CgogICAgICAgICAgd2hpbGUgKCsrbGVmdEluZGV4IDwgbGVmdExlbmd0aCkgewogICAgICAgICAgICByZXN1bHRbbGVmdEluZGV4XSA9IHBhcnRpYWxzW2xlZnRJbmRleF07CiAgICAgICAgICB9CiAgICAgICAgICB3aGlsZSAoKythcmdzSW5kZXggPCBob2xkZXJzTGVuZ3RoKSB7CiAgICAgICAgICAgIGlmIChpc1VuY3VycmllZCB8fCBhcmdzSW5kZXggPCBhcmdzTGVuZ3RoKSB7CiAgICAgICAgICAgICAgcmVzdWx0W2hvbGRlcnNbYXJnc0luZGV4XV0gPSBhcmdzW2FyZ3NJbmRleF07CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHdoaWxlIChyYW5nZUxlbmd0aC0tKSB7CiAgICAgICAgICAgIHJlc3VsdFtsZWZ0SW5kZXgrK10gPSBhcmdzW2FyZ3NJbmRleCsrXTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGxpa2UgYGNvbXBvc2VBcmdzYCBleGNlcHQgdGhhdCB0aGUgYXJndW1lbnRzIGNvbXBvc2l0aW9uCiAgICAgICAgICogaXMgdGFpbG9yZWQgZm9yIGBfLnBhcnRpYWxSaWdodGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFyZ3MgVGhlIHByb3ZpZGVkIGFyZ3VtZW50cy4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBwYXJ0aWFscyBUaGUgYXJndW1lbnRzIHRvIGFwcGVuZCB0byB0aG9zZSBwcm92aWRlZC4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBob2xkZXJzIFRoZSBgcGFydGlhbHNgIHBsYWNlaG9sZGVyIGluZGV4ZXMuCiAgICAgICAgICogQHBhcmFtcyB7Ym9vbGVhbn0gW2lzQ3VycmllZF0gU3BlY2lmeSBjb21wb3NpbmcgZm9yIGEgY3VycmllZCBmdW5jdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBjb21wb3NlZCBhcmd1bWVudHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29tcG9zZUFyZ3NSaWdodChhcmdzLCBwYXJ0aWFscywgaG9sZGVycywgaXNDdXJyaWVkKSB7CiAgICAgICAgICB2YXIgYXJnc0luZGV4ID0gLTEsCiAgICAgICAgICAgICAgYXJnc0xlbmd0aCA9IGFyZ3MubGVuZ3RoLAogICAgICAgICAgICAgIGhvbGRlcnNJbmRleCA9IC0xLAogICAgICAgICAgICAgIGhvbGRlcnNMZW5ndGggPSBob2xkZXJzLmxlbmd0aCwKICAgICAgICAgICAgICByaWdodEluZGV4ID0gLTEsCiAgICAgICAgICAgICAgcmlnaHRMZW5ndGggPSBwYXJ0aWFscy5sZW5ndGgsCiAgICAgICAgICAgICAgcmFuZ2VMZW5ndGggPSBuYXRpdmVNYXgoYXJnc0xlbmd0aCAtIGhvbGRlcnNMZW5ndGgsIDApLAogICAgICAgICAgICAgIHJlc3VsdCA9IEFycmF5KHJhbmdlTGVuZ3RoICsgcmlnaHRMZW5ndGgpLAogICAgICAgICAgICAgIGlzVW5jdXJyaWVkID0gIWlzQ3VycmllZDsKCiAgICAgICAgICB3aGlsZSAoKythcmdzSW5kZXggPCByYW5nZUxlbmd0aCkgewogICAgICAgICAgICByZXN1bHRbYXJnc0luZGV4XSA9IGFyZ3NbYXJnc0luZGV4XTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBvZmZzZXQgPSBhcmdzSW5kZXg7CiAgICAgICAgICB3aGlsZSAoKytyaWdodEluZGV4IDwgcmlnaHRMZW5ndGgpIHsKICAgICAgICAgICAgcmVzdWx0W29mZnNldCArIHJpZ2h0SW5kZXhdID0gcGFydGlhbHNbcmlnaHRJbmRleF07CiAgICAgICAgICB9CiAgICAgICAgICB3aGlsZSAoKytob2xkZXJzSW5kZXggPCBob2xkZXJzTGVuZ3RoKSB7CiAgICAgICAgICAgIGlmIChpc1VuY3VycmllZCB8fCBhcmdzSW5kZXggPCBhcmdzTGVuZ3RoKSB7CiAgICAgICAgICAgICAgcmVzdWx0W29mZnNldCArIGhvbGRlcnNbaG9sZGVyc0luZGV4XV0gPSBhcmdzW2FyZ3NJbmRleCsrXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvcGllcyB0aGUgdmFsdWVzIG9mIGBzb3VyY2VgIHRvIGBhcnJheWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHNvdXJjZSBUaGUgYXJyYXkgdG8gY29weSB2YWx1ZXMgZnJvbS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXk9W11dIFRoZSBhcnJheSB0byBjb3B5IHZhbHVlcyB0by4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb3B5QXJyYXkoc291cmNlLCBhcnJheSkgewogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgbGVuZ3RoID0gc291cmNlLmxlbmd0aDsKCiAgICAgICAgICBhcnJheSB8fCAoYXJyYXkgPSBBcnJheShsZW5ndGgpKTsKICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIGFycmF5W2luZGV4XSA9IHNvdXJjZVtpbmRleF07CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYXJyYXk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb3BpZXMgcHJvcGVydGllcyBvZiBgc291cmNlYCB0byBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IHRvIGNvcHkgcHJvcGVydGllcyBmcm9tLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHByb3BzIFRoZSBwcm9wZXJ0eSBpZGVudGlmaWVycyB0byBjb3B5LgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0PXt9XSBUaGUgb2JqZWN0IHRvIGNvcHkgcHJvcGVydGllcyB0by4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb3BpZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29weU9iamVjdChzb3VyY2UsIHByb3BzLCBvYmplY3QsIGN1c3RvbWl6ZXIpIHsKICAgICAgICAgIHZhciBpc05ldyA9ICFvYmplY3Q7CiAgICAgICAgICBvYmplY3QgfHwgKG9iamVjdCA9IHt9KTsKCiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSBwcm9wcy5sZW5ndGg7CgogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGtleSA9IHByb3BzW2luZGV4XTsKCiAgICAgICAgICAgIHZhciBuZXdWYWx1ZSA9IGN1c3RvbWl6ZXIKICAgICAgICAgICAgICA/IGN1c3RvbWl6ZXIob2JqZWN0W2tleV0sIHNvdXJjZVtrZXldLCBrZXksIG9iamVjdCwgc291cmNlKQogICAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgICBpZiAobmV3VmFsdWUgPT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgbmV3VmFsdWUgPSBzb3VyY2Vba2V5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaXNOZXcpIHsKICAgICAgICAgICAgICBiYXNlQXNzaWduVmFsdWUob2JqZWN0LCBrZXksIG5ld1ZhbHVlKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBhc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgbmV3VmFsdWUpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gb2JqZWN0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29waWVzIG93biBzeW1ib2xzIG9mIGBzb3VyY2VgIHRvIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3QgdG8gY29weSBzeW1ib2xzIGZyb20uCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3Q9e31dIFRoZSBvYmplY3QgdG8gY29weSBzeW1ib2xzIHRvLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29weVN5bWJvbHMoc291cmNlLCBvYmplY3QpIHsKICAgICAgICAgIHJldHVybiBjb3B5T2JqZWN0KHNvdXJjZSwgZ2V0U3ltYm9scyhzb3VyY2UpLCBvYmplY3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29waWVzIG93biBhbmQgaW5oZXJpdGVkIHN5bWJvbHMgb2YgYHNvdXJjZWAgdG8gYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIG9iamVjdCB0byBjb3B5IHN5bWJvbHMgZnJvbS4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29iamVjdD17fV0gVGhlIG9iamVjdCB0byBjb3B5IHN5bWJvbHMgdG8uCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb3B5U3ltYm9sc0luKHNvdXJjZSwgb2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gY29weU9iamVjdChzb3VyY2UsIGdldFN5bWJvbHNJbihzb3VyY2UpLCBvYmplY3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIGxpa2UgYF8uZ3JvdXBCeWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHNldHRlciBUaGUgZnVuY3Rpb24gdG8gc2V0IGFjY3VtdWxhdG9yIHZhbHVlcy4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaW5pdGlhbGl6ZXJdIFRoZSBhY2N1bXVsYXRvciBvYmplY3QgaW5pdGlhbGl6ZXIuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgYWdncmVnYXRvciBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVBZ2dyZWdhdG9yKHNldHRlciwgaW5pdGlhbGl6ZXIpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihjb2xsZWN0aW9uLCBpdGVyYXRlZSkgewogICAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheUFnZ3JlZ2F0b3IgOiBiYXNlQWdncmVnYXRvciwKICAgICAgICAgICAgICAgIGFjY3VtdWxhdG9yID0gaW5pdGlhbGl6ZXIgPyBpbml0aWFsaXplcigpIDoge307CgogICAgICAgICAgICByZXR1cm4gZnVuYyhjb2xsZWN0aW9uLCBzZXR0ZXIsIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAyKSwgYWNjdW11bGF0b3IpOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiBsaWtlIGBfLmFzc2lnbmAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGFzc2lnbmVyIFRoZSBmdW5jdGlvbiB0byBhc3NpZ24gdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFzc2lnbmVyIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUFzc2lnbmVyKGFzc2lnbmVyKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVJlc3QoZnVuY3Rpb24ob2JqZWN0LCBzb3VyY2VzKSB7CiAgICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgICAgbGVuZ3RoID0gc291cmNlcy5sZW5ndGgsCiAgICAgICAgICAgICAgICBjdXN0b21pemVyID0gbGVuZ3RoID4gMSA/IHNvdXJjZXNbbGVuZ3RoIC0gMV0gOiB1bmRlZmluZWQkMSwKICAgICAgICAgICAgICAgIGd1YXJkID0gbGVuZ3RoID4gMiA/IHNvdXJjZXNbMl0gOiB1bmRlZmluZWQkMTsKCiAgICAgICAgICAgIGN1c3RvbWl6ZXIgPSAoYXNzaWduZXIubGVuZ3RoID4gMyAmJiB0eXBlb2YgY3VzdG9taXplciA9PSAnZnVuY3Rpb24nKQogICAgICAgICAgICAgID8gKGxlbmd0aC0tLCBjdXN0b21pemVyKQogICAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgICBpZiAoZ3VhcmQgJiYgaXNJdGVyYXRlZUNhbGwoc291cmNlc1swXSwgc291cmNlc1sxXSwgZ3VhcmQpKSB7CiAgICAgICAgICAgICAgY3VzdG9taXplciA9IGxlbmd0aCA8IDMgPyB1bmRlZmluZWQkMSA6IGN1c3RvbWl6ZXI7CiAgICAgICAgICAgICAgbGVuZ3RoID0gMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBvYmplY3QgPSBPYmplY3Qob2JqZWN0KTsKICAgICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgICB2YXIgc291cmNlID0gc291cmNlc1tpbmRleF07CiAgICAgICAgICAgICAgaWYgKHNvdXJjZSkgewogICAgICAgICAgICAgICAgYXNzaWduZXIob2JqZWN0LCBzb3VyY2UsIGluZGV4LCBjdXN0b21pemVyKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICAgIH0pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGBiYXNlRWFjaGAgb3IgYGJhc2VFYWNoUmlnaHRgIGZ1bmN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBlYWNoRnVuYyBUaGUgZnVuY3Rpb24gdG8gaXRlcmF0ZSBvdmVyIGEgY29sbGVjdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtmcm9tUmlnaHRdIFNwZWNpZnkgaXRlcmF0aW5nIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBiYXNlIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUJhc2VFYWNoKGVhY2hGdW5jLCBmcm9tUmlnaHQpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihjb2xsZWN0aW9uLCBpdGVyYXRlZSkgewogICAgICAgICAgICBpZiAoY29sbGVjdGlvbiA9PSBudWxsKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGNvbGxlY3Rpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCFpc0FycmF5TGlrZShjb2xsZWN0aW9uKSkgewogICAgICAgICAgICAgIHJldHVybiBlYWNoRnVuYyhjb2xsZWN0aW9uLCBpdGVyYXRlZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGxlbmd0aCA9IGNvbGxlY3Rpb24ubGVuZ3RoLAogICAgICAgICAgICAgICAgaW5kZXggPSBmcm9tUmlnaHQgPyBsZW5ndGggOiAtMSwKICAgICAgICAgICAgICAgIGl0ZXJhYmxlID0gT2JqZWN0KGNvbGxlY3Rpb24pOwoKICAgICAgICAgICAgd2hpbGUgKChmcm9tUmlnaHQgPyBpbmRleC0tIDogKytpbmRleCA8IGxlbmd0aCkpIHsKICAgICAgICAgICAgICBpZiAoaXRlcmF0ZWUoaXRlcmFibGVbaW5kZXhdLCBpbmRleCwgaXRlcmFibGUpID09PSBmYWxzZSkgewogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBjb2xsZWN0aW9uOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBiYXNlIGZ1bmN0aW9uIGZvciBtZXRob2RzIGxpa2UgYF8uZm9ySW5gIGFuZCBgXy5mb3JPd25gLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtmcm9tUmlnaHRdIFNwZWNpZnkgaXRlcmF0aW5nIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBiYXNlIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUJhc2VGb3IoZnJvbVJpZ2h0KSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0LCBpdGVyYXRlZSwga2V5c0Z1bmMpIHsKICAgICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgICBpdGVyYWJsZSA9IE9iamVjdChvYmplY3QpLAogICAgICAgICAgICAgICAgcHJvcHMgPSBrZXlzRnVuYyhvYmplY3QpLAogICAgICAgICAgICAgICAgbGVuZ3RoID0gcHJvcHMubGVuZ3RoOwoKICAgICAgICAgICAgd2hpbGUgKGxlbmd0aC0tKSB7CiAgICAgICAgICAgICAgdmFyIGtleSA9IHByb3BzW2Zyb21SaWdodCA/IGxlbmd0aCA6ICsraW5kZXhdOwogICAgICAgICAgICAgIGlmIChpdGVyYXRlZShpdGVyYWJsZVtrZXldLCBrZXksIGl0ZXJhYmxlKSA9PT0gZmFsc2UpIHsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gb2JqZWN0OwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IHdyYXBzIGBmdW5jYCB0byBpbnZva2UgaXQgd2l0aCB0aGUgb3B0aW9uYWwgYHRoaXNgCiAgICAgICAgICogYmluZGluZyBvZiBgdGhpc0FyZ2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgY3JlYXRlV3JhcGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKiBAcGFyYW0geyp9IFt0aGlzQXJnXSBUaGUgYHRoaXNgIGJpbmRpbmcgb2YgYGZ1bmNgLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHdyYXBwZWQgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlQmluZChmdW5jLCBiaXRtYXNrLCB0aGlzQXJnKSB7CiAgICAgICAgICB2YXIgaXNCaW5kID0gYml0bWFzayAmIFdSQVBfQklORF9GTEFHLAogICAgICAgICAgICAgIEN0b3IgPSBjcmVhdGVDdG9yKGZ1bmMpOwoKICAgICAgICAgIGZ1bmN0aW9uIHdyYXBwZXIoKSB7CiAgICAgICAgICAgIHZhciBmbiA9ICh0aGlzICYmIHRoaXMgIT09IHJvb3QgJiYgdGhpcyBpbnN0YW5jZW9mIHdyYXBwZXIpID8gQ3RvciA6IGZ1bmM7CiAgICAgICAgICAgIHJldHVybiBmbi5hcHBseShpc0JpbmQgPyB0aGlzQXJnIDogdGhpcywgYXJndW1lbnRzKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB3cmFwcGVyOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIGxpa2UgYF8ubG93ZXJGaXJzdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBtZXRob2ROYW1lIFRoZSBuYW1lIG9mIHRoZSBgU3RyaW5nYCBjYXNlIG1ldGhvZCB0byB1c2UuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgY2FzZSBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVDYXNlRmlyc3QobWV0aG9kTmFtZSkgewogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmluZykgewogICAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwoKICAgICAgICAgICAgdmFyIHN0clN5bWJvbHMgPSBoYXNVbmljb2RlKHN0cmluZykKICAgICAgICAgICAgICA/IHN0cmluZ1RvQXJyYXkoc3RyaW5nKQogICAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgICB2YXIgY2hyID0gc3RyU3ltYm9scwogICAgICAgICAgICAgID8gc3RyU3ltYm9sc1swXQogICAgICAgICAgICAgIDogc3RyaW5nLmNoYXJBdCgwKTsKCiAgICAgICAgICAgIHZhciB0cmFpbGluZyA9IHN0clN5bWJvbHMKICAgICAgICAgICAgICA/IGNhc3RTbGljZShzdHJTeW1ib2xzLCAxKS5qb2luKCcnKQogICAgICAgICAgICAgIDogc3RyaW5nLnNsaWNlKDEpOwoKICAgICAgICAgICAgcmV0dXJuIGNoclttZXRob2ROYW1lXSgpICsgdHJhaWxpbmc7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIGxpa2UgYF8uY2FtZWxDYXNlYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY2FsbGJhY2sgVGhlIGZ1bmN0aW9uIHRvIGNvbWJpbmUgZWFjaCB3b3JkLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGNvbXBvdW5kZXIgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlQ29tcG91bmRlcihjYWxsYmFjaykgewogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmluZykgewogICAgICAgICAgICByZXR1cm4gYXJyYXlSZWR1Y2Uod29yZHMoZGVidXJyKHN0cmluZykucmVwbGFjZShyZUFwb3MsICcnKSksIGNhbGxiYWNrLCAnJyk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcHJvZHVjZXMgYW4gaW5zdGFuY2Ugb2YgYEN0b3JgIHJlZ2FyZGxlc3Mgb2YKICAgICAgICAgKiB3aGV0aGVyIGl0IHdhcyBpbnZva2VkIGFzIHBhcnQgb2YgYSBgbmV3YCBleHByZXNzaW9uIG9yIGJ5IGBjYWxsYCBvciBgYXBwbHlgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBDdG9yIFRoZSBjb25zdHJ1Y3RvciB0byB3cmFwLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHdyYXBwZWQgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlQ3RvcihDdG9yKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIC8vIFVzZSBhIGBzd2l0Y2hgIHN0YXRlbWVudCB0byB3b3JrIHdpdGggY2xhc3MgY29uc3RydWN0b3JzLiBTZWUKICAgICAgICAgICAgLy8gaHR0cDovL2VjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtZWNtYXNjcmlwdC1mdW5jdGlvbi1vYmplY3RzLWNhbGwtdGhpc2FyZ3VtZW50LWFyZ3VtZW50c2xpc3QKICAgICAgICAgICAgLy8gZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHM7CiAgICAgICAgICAgIHN3aXRjaCAoYXJncy5sZW5ndGgpIHsKICAgICAgICAgICAgICBjYXNlIDA6IHJldHVybiBuZXcgQ3RvcjsKICAgICAgICAgICAgICBjYXNlIDE6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdKTsKICAgICAgICAgICAgICBjYXNlIDI6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdKTsKICAgICAgICAgICAgICBjYXNlIDM6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdKTsKICAgICAgICAgICAgICBjYXNlIDQ6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdLCBhcmdzWzNdKTsKICAgICAgICAgICAgICBjYXNlIDU6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdLCBhcmdzWzNdLCBhcmdzWzRdKTsKICAgICAgICAgICAgICBjYXNlIDY6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdLCBhcmdzWzNdLCBhcmdzWzRdLCBhcmdzWzVdKTsKICAgICAgICAgICAgICBjYXNlIDc6IHJldHVybiBuZXcgQ3RvcihhcmdzWzBdLCBhcmdzWzFdLCBhcmdzWzJdLCBhcmdzWzNdLCBhcmdzWzRdLCBhcmdzWzVdLCBhcmdzWzZdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgdGhpc0JpbmRpbmcgPSBiYXNlQ3JlYXRlKEN0b3IucHJvdG90eXBlKSwKICAgICAgICAgICAgICAgIHJlc3VsdCA9IEN0b3IuYXBwbHkodGhpc0JpbmRpbmcsIGFyZ3MpOwoKICAgICAgICAgICAgLy8gTWltaWMgdGhlIGNvbnN0cnVjdG9yJ3MgYHJldHVybmAgYmVoYXZpb3IuCiAgICAgICAgICAgIC8vIFNlZSBodHRwczovL2VzNS5naXRodWIuaW8vI3gxMy4yLjIgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgICAgcmV0dXJuIGlzT2JqZWN0KHJlc3VsdCkgPyByZXN1bHQgOiB0aGlzQmluZGluZzsKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCB3cmFwcyBgZnVuY2AgdG8gZW5hYmxlIGN1cnJ5aW5nLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byB3cmFwLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBiaXRtYXNrIFRoZSBiaXRtYXNrIGZsYWdzLiBTZWUgYGNyZWF0ZVdyYXBgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGFyaXR5IFRoZSBhcml0eSBvZiBgZnVuY2AuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgd3JhcHBlZCBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVDdXJyeShmdW5jLCBiaXRtYXNrLCBhcml0eSkgewogICAgICAgICAgdmFyIEN0b3IgPSBjcmVhdGVDdG9yKGZ1bmMpOwoKICAgICAgICAgIGZ1bmN0aW9uIHdyYXBwZXIoKSB7CiAgICAgICAgICAgIHZhciBsZW5ndGggPSBhcmd1bWVudHMubGVuZ3RoLAogICAgICAgICAgICAgICAgYXJncyA9IEFycmF5KGxlbmd0aCksCiAgICAgICAgICAgICAgICBpbmRleCA9IGxlbmd0aCwKICAgICAgICAgICAgICAgIHBsYWNlaG9sZGVyID0gZ2V0SG9sZGVyKHdyYXBwZXIpOwoKICAgICAgICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICAgICAgICBhcmdzW2luZGV4XSA9IGFyZ3VtZW50c1tpbmRleF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGhvbGRlcnMgPSAobGVuZ3RoIDwgMyAmJiBhcmdzWzBdICE9PSBwbGFjZWhvbGRlciAmJiBhcmdzW2xlbmd0aCAtIDFdICE9PSBwbGFjZWhvbGRlcikKICAgICAgICAgICAgICA/IFtdCiAgICAgICAgICAgICAgOiByZXBsYWNlSG9sZGVycyhhcmdzLCBwbGFjZWhvbGRlcik7CgogICAgICAgICAgICBsZW5ndGggLT0gaG9sZGVycy5sZW5ndGg7CiAgICAgICAgICAgIGlmIChsZW5ndGggPCBhcml0eSkgewogICAgICAgICAgICAgIHJldHVybiBjcmVhdGVSZWN1cnJ5KAogICAgICAgICAgICAgICAgZnVuYywgYml0bWFzaywgY3JlYXRlSHlicmlkLCB3cmFwcGVyLnBsYWNlaG9sZGVyLCB1bmRlZmluZWQkMSwKICAgICAgICAgICAgICAgIGFyZ3MsIGhvbGRlcnMsIHVuZGVmaW5lZCQxLCB1bmRlZmluZWQkMSwgYXJpdHkgLSBsZW5ndGgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBmbiA9ICh0aGlzICYmIHRoaXMgIT09IHJvb3QgJiYgdGhpcyBpbnN0YW5jZW9mIHdyYXBwZXIpID8gQ3RvciA6IGZ1bmM7CiAgICAgICAgICAgIHJldHVybiBhcHBseShmbiwgdGhpcywgYXJncyk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gd3JhcHBlcjsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBgXy5maW5kYCBvciBgXy5maW5kTGFzdGAgZnVuY3Rpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZpbmRJbmRleEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGZpbmQgdGhlIGNvbGxlY3Rpb24gaW5kZXguCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZmluZCBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVGaW5kKGZpbmRJbmRleEZ1bmMpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihjb2xsZWN0aW9uLCBwcmVkaWNhdGUsIGZyb21JbmRleCkgewogICAgICAgICAgICB2YXIgaXRlcmFibGUgPSBPYmplY3QoY29sbGVjdGlvbik7CiAgICAgICAgICAgIGlmICghaXNBcnJheUxpa2UoY29sbGVjdGlvbikpIHsKICAgICAgICAgICAgICB2YXIgaXRlcmF0ZWUgPSBnZXRJdGVyYXRlZShwcmVkaWNhdGUsIDMpOwogICAgICAgICAgICAgIGNvbGxlY3Rpb24gPSBrZXlzKGNvbGxlY3Rpb24pOwogICAgICAgICAgICAgIHByZWRpY2F0ZSA9IGZ1bmN0aW9uKGtleSkgeyByZXR1cm4gaXRlcmF0ZWUoaXRlcmFibGVba2V5XSwga2V5LCBpdGVyYWJsZSk7IH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGluZGV4ID0gZmluZEluZGV4RnVuYyhjb2xsZWN0aW9uLCBwcmVkaWNhdGUsIGZyb21JbmRleCk7CiAgICAgICAgICAgIHJldHVybiBpbmRleCA+IC0xID8gaXRlcmFibGVbaXRlcmF0ZWUgPyBjb2xsZWN0aW9uW2luZGV4XSA6IGluZGV4XSA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBgXy5mbG93YCBvciBgXy5mbG93UmlnaHRgIGZ1bmN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtmcm9tUmlnaHRdIFNwZWNpZnkgaXRlcmF0aW5nIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmbG93IGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUZsb3coZnJvbVJpZ2h0KSB7CiAgICAgICAgICByZXR1cm4gZmxhdFJlc3QoZnVuY3Rpb24oZnVuY3MpIHsKICAgICAgICAgICAgdmFyIGxlbmd0aCA9IGZ1bmNzLmxlbmd0aCwKICAgICAgICAgICAgICAgIGluZGV4ID0gbGVuZ3RoLAogICAgICAgICAgICAgICAgcHJlcmVxID0gTG9kYXNoV3JhcHBlci5wcm90b3R5cGUudGhydTsKCiAgICAgICAgICAgIGlmIChmcm9tUmlnaHQpIHsKICAgICAgICAgICAgICBmdW5jcy5yZXZlcnNlKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICAgICAgICB2YXIgZnVuYyA9IGZ1bmNzW2luZGV4XTsKICAgICAgICAgICAgICBpZiAodHlwZW9mIGZ1bmMgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcihGVU5DX0VSUk9SX1RFWFQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBpZiAocHJlcmVxICYmICF3cmFwcGVyICYmIGdldEZ1bmNOYW1lKGZ1bmMpID09ICd3cmFwcGVyJykgewogICAgICAgICAgICAgICAgdmFyIHdyYXBwZXIgPSBuZXcgTG9kYXNoV3JhcHBlcihbXSwgdHJ1ZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGluZGV4ID0gd3JhcHBlciA/IGluZGV4IDogbGVuZ3RoOwogICAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICAgIGZ1bmMgPSBmdW5jc1tpbmRleF07CgogICAgICAgICAgICAgIHZhciBmdW5jTmFtZSA9IGdldEZ1bmNOYW1lKGZ1bmMpLAogICAgICAgICAgICAgICAgICBkYXRhID0gZnVuY05hbWUgPT0gJ3dyYXBwZXInID8gZ2V0RGF0YShmdW5jKSA6IHVuZGVmaW5lZCQxOwoKICAgICAgICAgICAgICBpZiAoZGF0YSAmJiBpc0xhemlhYmxlKGRhdGFbMF0pICYmCiAgICAgICAgICAgICAgICAgICAgZGF0YVsxXSA9PSAoV1JBUF9BUllfRkxBRyB8IFdSQVBfQ1VSUllfRkxBRyB8IFdSQVBfUEFSVElBTF9GTEFHIHwgV1JBUF9SRUFSR19GTEFHKSAmJgogICAgICAgICAgICAgICAgICAgICFkYXRhWzRdLmxlbmd0aCAmJiBkYXRhWzldID09IDEKICAgICAgICAgICAgICAgICAgKSB7CiAgICAgICAgICAgICAgICB3cmFwcGVyID0gd3JhcHBlcltnZXRGdW5jTmFtZShkYXRhWzBdKV0uYXBwbHkod3JhcHBlciwgZGF0YVszXSk7CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHdyYXBwZXIgPSAoZnVuYy5sZW5ndGggPT0gMSAmJiBpc0xhemlhYmxlKGZ1bmMpKQogICAgICAgICAgICAgICAgICA/IHdyYXBwZXJbZnVuY05hbWVdKCkKICAgICAgICAgICAgICAgICAgOiB3cmFwcGVyLnRocnUoZnVuYyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICB2YXIgYXJncyA9IGFyZ3VtZW50cywKICAgICAgICAgICAgICAgICAgdmFsdWUgPSBhcmdzWzBdOwoKICAgICAgICAgICAgICBpZiAod3JhcHBlciAmJiBhcmdzLmxlbmd0aCA9PSAxICYmIGlzQXJyYXkodmFsdWUpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gd3JhcHBlci5wbGFudCh2YWx1ZSkudmFsdWUoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgdmFyIGluZGV4ID0gMCwKICAgICAgICAgICAgICAgICAgcmVzdWx0ID0gbGVuZ3RoID8gZnVuY3NbaW5kZXhdLmFwcGx5KHRoaXMsIGFyZ3MpIDogdmFsdWU7CgogICAgICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgICAgICByZXN1bHQgPSBmdW5jc1tpbmRleF0uY2FsbCh0aGlzLCByZXN1bHQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgICB9OwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCB3cmFwcyBgZnVuY2AgdG8gaW52b2tlIGl0IHdpdGggb3B0aW9uYWwgYHRoaXNgCiAgICAgICAgICogYmluZGluZyBvZiBgdGhpc0FyZ2AsIHBhcnRpYWwgYXBwbGljYXRpb24sIGFuZCBjdXJyeWluZy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbnxzdHJpbmd9IGZ1bmMgVGhlIGZ1bmN0aW9uIG9yIG1ldGhvZCBuYW1lIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgY3JlYXRlV3JhcGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKiBAcGFyYW0geyp9IFt0aGlzQXJnXSBUaGUgYHRoaXNgIGJpbmRpbmcgb2YgYGZ1bmNgLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFtwYXJ0aWFsc10gVGhlIGFyZ3VtZW50cyB0byBwcmVwZW5kIHRvIHRob3NlIHByb3ZpZGVkIHRvCiAgICAgICAgICogIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW2hvbGRlcnNdIFRoZSBgcGFydGlhbHNgIHBsYWNlaG9sZGVyIGluZGV4ZXMuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW3BhcnRpYWxzUmlnaHRdIFRoZSBhcmd1bWVudHMgdG8gYXBwZW5kIHRvIHRob3NlIHByb3ZpZGVkCiAgICAgICAgICogIHRvIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW2hvbGRlcnNSaWdodF0gVGhlIGBwYXJ0aWFsc1JpZ2h0YCBwbGFjZWhvbGRlciBpbmRleGVzLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcmdQb3NdIFRoZSBhcmd1bWVudCBwb3NpdGlvbnMgb2YgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2FyeV0gVGhlIGFyaXR5IGNhcCBvZiBgZnVuY2AuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFthcml0eV0gVGhlIGFyaXR5IG9mIGBmdW5jYC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyB3cmFwcGVkIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUh5YnJpZChmdW5jLCBiaXRtYXNrLCB0aGlzQXJnLCBwYXJ0aWFscywgaG9sZGVycywgcGFydGlhbHNSaWdodCwgaG9sZGVyc1JpZ2h0LCBhcmdQb3MsIGFyeSwgYXJpdHkpIHsKICAgICAgICAgIHZhciBpc0FyeSA9IGJpdG1hc2sgJiBXUkFQX0FSWV9GTEFHLAogICAgICAgICAgICAgIGlzQmluZCA9IGJpdG1hc2sgJiBXUkFQX0JJTkRfRkxBRywKICAgICAgICAgICAgICBpc0JpbmRLZXkgPSBiaXRtYXNrICYgV1JBUF9CSU5EX0tFWV9GTEFHLAogICAgICAgICAgICAgIGlzQ3VycmllZCA9IGJpdG1hc2sgJiAoV1JBUF9DVVJSWV9GTEFHIHwgV1JBUF9DVVJSWV9SSUdIVF9GTEFHKSwKICAgICAgICAgICAgICBpc0ZsaXAgPSBiaXRtYXNrICYgV1JBUF9GTElQX0ZMQUcsCiAgICAgICAgICAgICAgQ3RvciA9IGlzQmluZEtleSA/IHVuZGVmaW5lZCQxIDogY3JlYXRlQ3RvcihmdW5jKTsKCiAgICAgICAgICBmdW5jdGlvbiB3cmFwcGVyKCkgewogICAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJndW1lbnRzLmxlbmd0aCwKICAgICAgICAgICAgICAgIGFyZ3MgPSBBcnJheShsZW5ndGgpLAogICAgICAgICAgICAgICAgaW5kZXggPSBsZW5ndGg7CgogICAgICAgICAgICB3aGlsZSAoaW5kZXgtLSkgewogICAgICAgICAgICAgIGFyZ3NbaW5kZXhdID0gYXJndW1lbnRzW2luZGV4XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaXNDdXJyaWVkKSB7CiAgICAgICAgICAgICAgdmFyIHBsYWNlaG9sZGVyID0gZ2V0SG9sZGVyKHdyYXBwZXIpLAogICAgICAgICAgICAgICAgICBob2xkZXJzQ291bnQgPSBjb3VudEhvbGRlcnMoYXJncywgcGxhY2Vob2xkZXIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChwYXJ0aWFscykgewogICAgICAgICAgICAgIGFyZ3MgPSBjb21wb3NlQXJncyhhcmdzLCBwYXJ0aWFscywgaG9sZGVycywgaXNDdXJyaWVkKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAocGFydGlhbHNSaWdodCkgewogICAgICAgICAgICAgIGFyZ3MgPSBjb21wb3NlQXJnc1JpZ2h0KGFyZ3MsIHBhcnRpYWxzUmlnaHQsIGhvbGRlcnNSaWdodCwgaXNDdXJyaWVkKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZW5ndGggLT0gaG9sZGVyc0NvdW50OwogICAgICAgICAgICBpZiAoaXNDdXJyaWVkICYmIGxlbmd0aCA8IGFyaXR5KSB7CiAgICAgICAgICAgICAgdmFyIG5ld0hvbGRlcnMgPSByZXBsYWNlSG9sZGVycyhhcmdzLCBwbGFjZWhvbGRlcik7CiAgICAgICAgICAgICAgcmV0dXJuIGNyZWF0ZVJlY3VycnkoCiAgICAgICAgICAgICAgICBmdW5jLCBiaXRtYXNrLCBjcmVhdGVIeWJyaWQsIHdyYXBwZXIucGxhY2Vob2xkZXIsIHRoaXNBcmcsCiAgICAgICAgICAgICAgICBhcmdzLCBuZXdIb2xkZXJzLCBhcmdQb3MsIGFyeSwgYXJpdHkgLSBsZW5ndGgKICAgICAgICAgICAgICApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB0aGlzQmluZGluZyA9IGlzQmluZCA/IHRoaXNBcmcgOiB0aGlzLAogICAgICAgICAgICAgICAgZm4gPSBpc0JpbmRLZXkgPyB0aGlzQmluZGluZ1tmdW5jXSA6IGZ1bmM7CgogICAgICAgICAgICBsZW5ndGggPSBhcmdzLmxlbmd0aDsKICAgICAgICAgICAgaWYgKGFyZ1BvcykgewogICAgICAgICAgICAgIGFyZ3MgPSByZW9yZGVyKGFyZ3MsIGFyZ1Bvcyk7CiAgICAgICAgICAgIH0gZWxzZSBpZiAoaXNGbGlwICYmIGxlbmd0aCA+IDEpIHsKICAgICAgICAgICAgICBhcmdzLnJldmVyc2UoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaXNBcnkgJiYgYXJ5IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgICAgYXJncy5sZW5ndGggPSBhcnk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMgJiYgdGhpcyAhPT0gcm9vdCAmJiB0aGlzIGluc3RhbmNlb2Ygd3JhcHBlcikgewogICAgICAgICAgICAgIGZuID0gQ3RvciB8fCBjcmVhdGVDdG9yKGZuKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZm4uYXBwbHkodGhpc0JpbmRpbmcsIGFyZ3MpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHdyYXBwZXI7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gbGlrZSBgXy5pbnZlcnRCeWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHNldHRlciBUaGUgZnVuY3Rpb24gdG8gc2V0IGFjY3VtdWxhdG9yIHZhbHVlcy4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSB0b0l0ZXJhdGVlIFRoZSBmdW5jdGlvbiB0byByZXNvbHZlIGl0ZXJhdGVlcy4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBpbnZlcnRlciBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVJbnZlcnRlcihzZXR0ZXIsIHRvSXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlSW52ZXJ0ZXIob2JqZWN0LCBzZXR0ZXIsIHRvSXRlcmF0ZWUoaXRlcmF0ZWUpLCB7fSk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcGVyZm9ybXMgYSBtYXRoZW1hdGljYWwgb3BlcmF0aW9uIG9uIHR3byB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IG9wZXJhdG9yIFRoZSBmdW5jdGlvbiB0byBwZXJmb3JtIHRoZSBvcGVyYXRpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtkZWZhdWx0VmFsdWVdIFRoZSB2YWx1ZSB1c2VkIGZvciBgdW5kZWZpbmVkYCBhcmd1bWVudHMuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgbWF0aGVtYXRpY2FsIG9wZXJhdGlvbiBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVNYXRoT3BlcmF0aW9uKG9wZXJhdG9yLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbih2YWx1ZSwgb3RoZXIpIHsKICAgICAgICAgICAgdmFyIHJlc3VsdDsKICAgICAgICAgICAgaWYgKHZhbHVlID09PSB1bmRlZmluZWQkMSAmJiBvdGhlciA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICByZXR1cm4gZGVmYXVsdFZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICByZXN1bHQgPSB2YWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob3RoZXIgIT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgaWYgKHJlc3VsdCA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICAgIHJldHVybiBvdGhlcjsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJyB8fCB0eXBlb2Ygb3RoZXIgPT0gJ3N0cmluZycpIHsKICAgICAgICAgICAgICAgIHZhbHVlID0gYmFzZVRvU3RyaW5nKHZhbHVlKTsKICAgICAgICAgICAgICAgIG90aGVyID0gYmFzZVRvU3RyaW5nKG90aGVyKTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgdmFsdWUgPSBiYXNlVG9OdW1iZXIodmFsdWUpOwogICAgICAgICAgICAgICAgb3RoZXIgPSBiYXNlVG9OdW1iZXIob3RoZXIpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXN1bHQgPSBvcGVyYXRvcih2YWx1ZSwgb3RoZXIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIGxpa2UgYF8ub3ZlcmAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGFycmF5RnVuYyBUaGUgZnVuY3Rpb24gdG8gaXRlcmF0ZSBvdmVyIGl0ZXJhdGVlcy4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBvdmVyIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZU92ZXIoYXJyYXlGdW5jKSB7CiAgICAgICAgICByZXR1cm4gZmxhdFJlc3QoZnVuY3Rpb24oaXRlcmF0ZWVzKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlcyA9IGFycmF5TWFwKGl0ZXJhdGVlcywgYmFzZVVuYXJ5KGdldEl0ZXJhdGVlKCkpKTsKICAgICAgICAgICAgcmV0dXJuIGJhc2VSZXN0KGZ1bmN0aW9uKGFyZ3MpIHsKICAgICAgICAgICAgICB2YXIgdGhpc0FyZyA9IHRoaXM7CiAgICAgICAgICAgICAgcmV0dXJuIGFycmF5RnVuYyhpdGVyYXRlZXMsIGZ1bmN0aW9uKGl0ZXJhdGVlKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gYXBwbHkoaXRlcmF0ZWUsIHRoaXNBcmcsIGFyZ3MpOwogICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9KTsKICAgICAgICAgIH0pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyB0aGUgcGFkZGluZyBmb3IgYHN0cmluZ2AgYmFzZWQgb24gYGxlbmd0aGAuIFRoZSBgY2hhcnNgIHN0cmluZwogICAgICAgICAqIGlzIHRydW5jYXRlZCBpZiB0aGUgbnVtYmVyIG9mIGNoYXJhY3RlcnMgZXhjZWVkcyBgbGVuZ3RoYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGxlbmd0aCBUaGUgcGFkZGluZyBsZW5ndGguCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz0nICddIFRoZSBzdHJpbmcgdXNlZCBhcyBwYWRkaW5nLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHBhZGRpbmcgZm9yIGBzdHJpbmdgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZVBhZGRpbmcobGVuZ3RoLCBjaGFycykgewogICAgICAgICAgY2hhcnMgPSBjaGFycyA9PT0gdW5kZWZpbmVkJDEgPyAnICcgOiBiYXNlVG9TdHJpbmcoY2hhcnMpOwoKICAgICAgICAgIHZhciBjaGFyc0xlbmd0aCA9IGNoYXJzLmxlbmd0aDsKICAgICAgICAgIGlmIChjaGFyc0xlbmd0aCA8IDIpIHsKICAgICAgICAgICAgcmV0dXJuIGNoYXJzTGVuZ3RoID8gYmFzZVJlcGVhdChjaGFycywgbGVuZ3RoKSA6IGNoYXJzOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHJlc3VsdCA9IGJhc2VSZXBlYXQoY2hhcnMsIG5hdGl2ZUNlaWwobGVuZ3RoIC8gc3RyaW5nU2l6ZShjaGFycykpKTsKICAgICAgICAgIHJldHVybiBoYXNVbmljb2RlKGNoYXJzKQogICAgICAgICAgICA/IGNhc3RTbGljZShzdHJpbmdUb0FycmF5KHJlc3VsdCksIDAsIGxlbmd0aCkuam9pbignJykKICAgICAgICAgICAgOiByZXN1bHQuc2xpY2UoMCwgbGVuZ3RoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IHdyYXBzIGBmdW5jYCB0byBpbnZva2UgaXQgd2l0aCB0aGUgYHRoaXNgIGJpbmRpbmcKICAgICAgICAgKiBvZiBgdGhpc0FyZ2AgYW5kIGBwYXJ0aWFsc2AgcHJlcGVuZGVkIHRvIHRoZSBhcmd1bWVudHMgaXQgcmVjZWl2ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgY3JlYXRlV3JhcGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKiBAcGFyYW0geyp9IHRoaXNBcmcgVGhlIGB0aGlzYCBiaW5kaW5nIG9mIGBmdW5jYC4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBwYXJ0aWFscyBUaGUgYXJndW1lbnRzIHRvIHByZXBlbmQgdG8gdGhvc2UgcHJvdmlkZWQgdG8KICAgICAgICAgKiAgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyB3cmFwcGVkIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZVBhcnRpYWwoZnVuYywgYml0bWFzaywgdGhpc0FyZywgcGFydGlhbHMpIHsKICAgICAgICAgIHZhciBpc0JpbmQgPSBiaXRtYXNrICYgV1JBUF9CSU5EX0ZMQUcsCiAgICAgICAgICAgICAgQ3RvciA9IGNyZWF0ZUN0b3IoZnVuYyk7CgogICAgICAgICAgZnVuY3Rpb24gd3JhcHBlcigpIHsKICAgICAgICAgICAgdmFyIGFyZ3NJbmRleCA9IC0xLAogICAgICAgICAgICAgICAgYXJnc0xlbmd0aCA9IGFyZ3VtZW50cy5sZW5ndGgsCiAgICAgICAgICAgICAgICBsZWZ0SW5kZXggPSAtMSwKICAgICAgICAgICAgICAgIGxlZnRMZW5ndGggPSBwYXJ0aWFscy5sZW5ndGgsCiAgICAgICAgICAgICAgICBhcmdzID0gQXJyYXkobGVmdExlbmd0aCArIGFyZ3NMZW5ndGgpLAogICAgICAgICAgICAgICAgZm4gPSAodGhpcyAmJiB0aGlzICE9PSByb290ICYmIHRoaXMgaW5zdGFuY2VvZiB3cmFwcGVyKSA/IEN0b3IgOiBmdW5jOwoKICAgICAgICAgICAgd2hpbGUgKCsrbGVmdEluZGV4IDwgbGVmdExlbmd0aCkgewogICAgICAgICAgICAgIGFyZ3NbbGVmdEluZGV4XSA9IHBhcnRpYWxzW2xlZnRJbmRleF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgd2hpbGUgKGFyZ3NMZW5ndGgtLSkgewogICAgICAgICAgICAgIGFyZ3NbbGVmdEluZGV4KytdID0gYXJndW1lbnRzWysrYXJnc0luZGV4XTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gYXBwbHkoZm4sIGlzQmluZCA/IHRoaXNBcmcgOiB0aGlzLCBhcmdzKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB3cmFwcGVyOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGBfLnJhbmdlYCBvciBgXy5yYW5nZVJpZ2h0YCBmdW5jdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbZnJvbVJpZ2h0XSBTcGVjaWZ5IGl0ZXJhdGluZyBmcm9tIHJpZ2h0IHRvIGxlZnQuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgcmFuZ2UgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlUmFuZ2UoZnJvbVJpZ2h0KSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24oc3RhcnQsIGVuZCwgc3RlcCkgewogICAgICAgICAgICBpZiAoc3RlcCAmJiB0eXBlb2Ygc3RlcCAhPSAnbnVtYmVyJyAmJiBpc0l0ZXJhdGVlQ2FsbChzdGFydCwgZW5kLCBzdGVwKSkgewogICAgICAgICAgICAgIGVuZCA9IHN0ZXAgPSB1bmRlZmluZWQkMTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBFbnN1cmUgdGhlIHNpZ24gb2YgYC0wYCBpcyBwcmVzZXJ2ZWQuCiAgICAgICAgICAgIHN0YXJ0ID0gdG9GaW5pdGUoc3RhcnQpOwogICAgICAgICAgICBpZiAoZW5kID09PSB1bmRlZmluZWQkMSkgewogICAgICAgICAgICAgIGVuZCA9IHN0YXJ0OwogICAgICAgICAgICAgIHN0YXJ0ID0gMDsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBlbmQgPSB0b0Zpbml0ZShlbmQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHN0ZXAgPSBzdGVwID09PSB1bmRlZmluZWQkMSA/IChzdGFydCA8IGVuZCA/IDEgOiAtMSkgOiB0b0Zpbml0ZShzdGVwKTsKICAgICAgICAgICAgcmV0dXJuIGJhc2VSYW5nZShzdGFydCwgZW5kLCBzdGVwLCBmcm9tUmlnaHQpOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IHBlcmZvcm1zIGEgcmVsYXRpb25hbCBvcGVyYXRpb24gb24gdHdvIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gb3BlcmF0b3IgVGhlIGZ1bmN0aW9uIHRvIHBlcmZvcm0gdGhlIG9wZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyByZWxhdGlvbmFsIG9wZXJhdGlvbiBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVSZWxhdGlvbmFsT3BlcmF0aW9uKG9wZXJhdG9yKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUsIG90aGVyKSB7CiAgICAgICAgICAgIGlmICghKHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJyAmJiB0eXBlb2Ygb3RoZXIgPT0gJ3N0cmluZycpKSB7CiAgICAgICAgICAgICAgdmFsdWUgPSB0b051bWJlcih2YWx1ZSk7CiAgICAgICAgICAgICAgb3RoZXIgPSB0b051bWJlcihvdGhlcik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG9wZXJhdG9yKHZhbHVlLCBvdGhlcik7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgd3JhcHMgYGZ1bmNgIHRvIGNvbnRpbnVlIGN1cnJ5aW5nLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byB3cmFwLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBiaXRtYXNrIFRoZSBiaXRtYXNrIGZsYWdzLiBTZWUgYGNyZWF0ZVdyYXBgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gd3JhcEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNyZWF0ZSB0aGUgYGZ1bmNgIHdyYXBwZXIuCiAgICAgICAgICogQHBhcmFtIHsqfSBwbGFjZWhvbGRlciBUaGUgcGxhY2Vob2xkZXIgdmFsdWUuCiAgICAgICAgICogQHBhcmFtIHsqfSBbdGhpc0FyZ10gVGhlIGB0aGlzYCBiaW5kaW5nIG9mIGBmdW5jYC4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBbcGFydGlhbHNdIFRoZSBhcmd1bWVudHMgdG8gcHJlcGVuZCB0byB0aG9zZSBwcm92aWRlZCB0bwogICAgICAgICAqICB0aGUgbmV3IGZ1bmN0aW9uLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFtob2xkZXJzXSBUaGUgYHBhcnRpYWxzYCBwbGFjZWhvbGRlciBpbmRleGVzLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcmdQb3NdIFRoZSBhcmd1bWVudCBwb3NpdGlvbnMgb2YgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2FyeV0gVGhlIGFyaXR5IGNhcCBvZiBgZnVuY2AuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFthcml0eV0gVGhlIGFyaXR5IG9mIGBmdW5jYC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyB3cmFwcGVkIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZVJlY3VycnkoZnVuYywgYml0bWFzaywgd3JhcEZ1bmMsIHBsYWNlaG9sZGVyLCB0aGlzQXJnLCBwYXJ0aWFscywgaG9sZGVycywgYXJnUG9zLCBhcnksIGFyaXR5KSB7CiAgICAgICAgICB2YXIgaXNDdXJyeSA9IGJpdG1hc2sgJiBXUkFQX0NVUlJZX0ZMQUcsCiAgICAgICAgICAgICAgbmV3SG9sZGVycyA9IGlzQ3VycnkgPyBob2xkZXJzIDogdW5kZWZpbmVkJDEsCiAgICAgICAgICAgICAgbmV3SG9sZGVyc1JpZ2h0ID0gaXNDdXJyeSA/IHVuZGVmaW5lZCQxIDogaG9sZGVycywKICAgICAgICAgICAgICBuZXdQYXJ0aWFscyA9IGlzQ3VycnkgPyBwYXJ0aWFscyA6IHVuZGVmaW5lZCQxLAogICAgICAgICAgICAgIG5ld1BhcnRpYWxzUmlnaHQgPSBpc0N1cnJ5ID8gdW5kZWZpbmVkJDEgOiBwYXJ0aWFsczsKCiAgICAgICAgICBiaXRtYXNrIHw9IChpc0N1cnJ5ID8gV1JBUF9QQVJUSUFMX0ZMQUcgOiBXUkFQX1BBUlRJQUxfUklHSFRfRkxBRyk7CiAgICAgICAgICBiaXRtYXNrICY9IH4oaXNDdXJyeSA/IFdSQVBfUEFSVElBTF9SSUdIVF9GTEFHIDogV1JBUF9QQVJUSUFMX0ZMQUcpOwoKICAgICAgICAgIGlmICghKGJpdG1hc2sgJiBXUkFQX0NVUlJZX0JPVU5EX0ZMQUcpKSB7CiAgICAgICAgICAgIGJpdG1hc2sgJj0gfihXUkFQX0JJTkRfRkxBRyB8IFdSQVBfQklORF9LRVlfRkxBRyk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgbmV3RGF0YSA9IFsKICAgICAgICAgICAgZnVuYywgYml0bWFzaywgdGhpc0FyZywgbmV3UGFydGlhbHMsIG5ld0hvbGRlcnMsIG5ld1BhcnRpYWxzUmlnaHQsCiAgICAgICAgICAgIG5ld0hvbGRlcnNSaWdodCwgYXJnUG9zLCBhcnksIGFyaXR5CiAgICAgICAgICBdOwoKICAgICAgICAgIHZhciByZXN1bHQgPSB3cmFwRnVuYy5hcHBseSh1bmRlZmluZWQkMSwgbmV3RGF0YSk7CiAgICAgICAgICBpZiAoaXNMYXppYWJsZShmdW5jKSkgewogICAgICAgICAgICBzZXREYXRhKHJlc3VsdCwgbmV3RGF0YSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXN1bHQucGxhY2Vob2xkZXIgPSBwbGFjZWhvbGRlcjsKICAgICAgICAgIHJldHVybiBzZXRXcmFwVG9TdHJpbmcocmVzdWx0LCBmdW5jLCBiaXRtYXNrKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiBsaWtlIGBfLnJvdW5kYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG1ldGhvZE5hbWUgVGhlIG5hbWUgb2YgdGhlIGBNYXRoYCBtZXRob2QgdG8gdXNlIHdoZW4gcm91bmRpbmcuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgcm91bmQgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlUm91bmQobWV0aG9kTmFtZSkgewogICAgICAgICAgdmFyIGZ1bmMgPSBNYXRoW21ldGhvZE5hbWVdOwogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKG51bWJlciwgcHJlY2lzaW9uKSB7CiAgICAgICAgICAgIG51bWJlciA9IHRvTnVtYmVyKG51bWJlcik7CiAgICAgICAgICAgIHByZWNpc2lvbiA9IHByZWNpc2lvbiA9PSBudWxsID8gMCA6IG5hdGl2ZU1pbih0b0ludGVnZXIocHJlY2lzaW9uKSwgMjkyKTsKICAgICAgICAgICAgaWYgKHByZWNpc2lvbiAmJiBuYXRpdmVJc0Zpbml0ZShudW1iZXIpKSB7CiAgICAgICAgICAgICAgLy8gU2hpZnQgd2l0aCBleHBvbmVudGlhbCBub3RhdGlvbiB0byBhdm9pZCBmbG9hdGluZy1wb2ludCBpc3N1ZXMuCiAgICAgICAgICAgICAgLy8gU2VlIFtNRE5dKGh0dHBzOi8vbWRuLmlvL3JvdW5kI0V4YW1wbGVzKSBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAgICAgIHZhciBwYWlyID0gKHRvU3RyaW5nKG51bWJlcikgKyAnZScpLnNwbGl0KCdlJyksCiAgICAgICAgICAgICAgICAgIHZhbHVlID0gZnVuYyhwYWlyWzBdICsgJ2UnICsgKCtwYWlyWzFdICsgcHJlY2lzaW9uKSk7CgogICAgICAgICAgICAgIHBhaXIgPSAodG9TdHJpbmcodmFsdWUpICsgJ2UnKS5zcGxpdCgnZScpOwogICAgICAgICAgICAgIHJldHVybiArKHBhaXJbMF0gKyAnZScgKyAoK3BhaXJbMV0gLSBwcmVjaXNpb24pKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZnVuYyhudW1iZXIpOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBzZXQgb2JqZWN0IG9mIGB2YWx1ZXNgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSB2YWx1ZXMgVGhlIHZhbHVlcyB0byBhZGQgdG8gdGhlIHNldC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgc2V0LgogICAgICAgICAqLwogICAgICAgIHZhciBjcmVhdGVTZXQgPSAhKFNldCAmJiAoMSAvIHNldFRvQXJyYXkobmV3IFNldChbLC0wXSkpWzFdKSA9PSBJTkZJTklUWSkgPyBub29wIDogZnVuY3Rpb24odmFsdWVzKSB7CiAgICAgICAgICByZXR1cm4gbmV3IFNldCh2YWx1ZXMpOwogICAgICAgIH07CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBgXy50b1BhaXJzYCBvciBgXy50b1BhaXJzSW5gIGZ1bmN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBrZXlzRnVuYyBUaGUgZnVuY3Rpb24gdG8gZ2V0IHRoZSBrZXlzIG9mIGEgZ2l2ZW4gb2JqZWN0LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHBhaXJzIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNyZWF0ZVRvUGFpcnMoa2V5c0Z1bmMpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICAgICAgdmFyIHRhZyA9IGdldFRhZyhvYmplY3QpOwogICAgICAgICAgICBpZiAodGFnID09IG1hcFRhZykgewogICAgICAgICAgICAgIHJldHVybiBtYXBUb0FycmF5KG9iamVjdCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRhZyA9PSBzZXRUYWcpIHsKICAgICAgICAgICAgICByZXR1cm4gc2V0VG9QYWlycyhvYmplY3QpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBiYXNlVG9QYWlycyhvYmplY3QsIGtleXNGdW5jKG9iamVjdCkpOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGVpdGhlciBjdXJyaWVzIG9yIGludm9rZXMgYGZ1bmNgIHdpdGggb3B0aW9uYWwKICAgICAgICAgKiBgdGhpc2AgYmluZGluZyBhbmQgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufHN0cmluZ30gZnVuYyBUaGUgZnVuY3Rpb24gb3IgbWV0aG9kIG5hbWUgdG8gd3JhcC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4KICAgICAgICAgKiAgICAxIC0gYF8uYmluZGAKICAgICAgICAgKiAgICAyIC0gYF8uYmluZEtleWAKICAgICAgICAgKiAgICA0IC0gYF8uY3VycnlgIG9yIGBfLmN1cnJ5UmlnaHRgIG9mIGEgYm91bmQgZnVuY3Rpb24KICAgICAgICAgKiAgICA4IC0gYF8uY3VycnlgCiAgICAgICAgICogICAxNiAtIGBfLmN1cnJ5UmlnaHRgCiAgICAgICAgICogICAzMiAtIGBfLnBhcnRpYWxgCiAgICAgICAgICogICA2NCAtIGBfLnBhcnRpYWxSaWdodGAKICAgICAgICAgKiAgMTI4IC0gYF8ucmVhcmdgCiAgICAgICAgICogIDI1NiAtIGBfLmFyeWAKICAgICAgICAgKiAgNTEyIC0gYF8uZmxpcGAKICAgICAgICAgKiBAcGFyYW0geyp9IFt0aGlzQXJnXSBUaGUgYHRoaXNgIGJpbmRpbmcgb2YgYGZ1bmNgLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFtwYXJ0aWFsc10gVGhlIGFyZ3VtZW50cyB0byBiZSBwYXJ0aWFsbHkgYXBwbGllZC4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBbaG9sZGVyc10gVGhlIGBwYXJ0aWFsc2AgcGxhY2Vob2xkZXIgaW5kZXhlcy4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJnUG9zXSBUaGUgYXJndW1lbnQgcG9zaXRpb25zIG9mIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFthcnldIFRoZSBhcml0eSBjYXAgb2YgYGZ1bmNgLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbYXJpdHldIFRoZSBhcml0eSBvZiBgZnVuY2AuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgd3JhcHBlZCBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjcmVhdGVXcmFwKGZ1bmMsIGJpdG1hc2ssIHRoaXNBcmcsIHBhcnRpYWxzLCBob2xkZXJzLCBhcmdQb3MsIGFyeSwgYXJpdHkpIHsKICAgICAgICAgIHZhciBpc0JpbmRLZXkgPSBiaXRtYXNrICYgV1JBUF9CSU5EX0tFWV9GTEFHOwogICAgICAgICAgaWYgKCFpc0JpbmRLZXkgJiYgdHlwZW9mIGZ1bmMgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKEZVTkNfRVJST1JfVEVYVCk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgbGVuZ3RoID0gcGFydGlhbHMgPyBwYXJ0aWFscy5sZW5ndGggOiAwOwogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgYml0bWFzayAmPSB+KFdSQVBfUEFSVElBTF9GTEFHIHwgV1JBUF9QQVJUSUFMX1JJR0hUX0ZMQUcpOwogICAgICAgICAgICBwYXJ0aWFscyA9IGhvbGRlcnMgPSB1bmRlZmluZWQkMTsKICAgICAgICAgIH0KICAgICAgICAgIGFyeSA9IGFyeSA9PT0gdW5kZWZpbmVkJDEgPyBhcnkgOiBuYXRpdmVNYXgodG9JbnRlZ2VyKGFyeSksIDApOwogICAgICAgICAgYXJpdHkgPSBhcml0eSA9PT0gdW5kZWZpbmVkJDEgPyBhcml0eSA6IHRvSW50ZWdlcihhcml0eSk7CiAgICAgICAgICBsZW5ndGggLT0gaG9sZGVycyA/IGhvbGRlcnMubGVuZ3RoIDogMDsKCiAgICAgICAgICBpZiAoYml0bWFzayAmIFdSQVBfUEFSVElBTF9SSUdIVF9GTEFHKSB7CiAgICAgICAgICAgIHZhciBwYXJ0aWFsc1JpZ2h0ID0gcGFydGlhbHMsCiAgICAgICAgICAgICAgICBob2xkZXJzUmlnaHQgPSBob2xkZXJzOwoKICAgICAgICAgICAgcGFydGlhbHMgPSBob2xkZXJzID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgZGF0YSA9IGlzQmluZEtleSA/IHVuZGVmaW5lZCQxIDogZ2V0RGF0YShmdW5jKTsKCiAgICAgICAgICB2YXIgbmV3RGF0YSA9IFsKICAgICAgICAgICAgZnVuYywgYml0bWFzaywgdGhpc0FyZywgcGFydGlhbHMsIGhvbGRlcnMsIHBhcnRpYWxzUmlnaHQsIGhvbGRlcnNSaWdodCwKICAgICAgICAgICAgYXJnUG9zLCBhcnksIGFyaXR5CiAgICAgICAgICBdOwoKICAgICAgICAgIGlmIChkYXRhKSB7CiAgICAgICAgICAgIG1lcmdlRGF0YShuZXdEYXRhLCBkYXRhKTsKICAgICAgICAgIH0KICAgICAgICAgIGZ1bmMgPSBuZXdEYXRhWzBdOwogICAgICAgICAgYml0bWFzayA9IG5ld0RhdGFbMV07CiAgICAgICAgICB0aGlzQXJnID0gbmV3RGF0YVsyXTsKICAgICAgICAgIHBhcnRpYWxzID0gbmV3RGF0YVszXTsKICAgICAgICAgIGhvbGRlcnMgPSBuZXdEYXRhWzRdOwogICAgICAgICAgYXJpdHkgPSBuZXdEYXRhWzldID0gbmV3RGF0YVs5XSA9PT0gdW5kZWZpbmVkJDEKICAgICAgICAgICAgPyAoaXNCaW5kS2V5ID8gMCA6IGZ1bmMubGVuZ3RoKQogICAgICAgICAgICA6IG5hdGl2ZU1heChuZXdEYXRhWzldIC0gbGVuZ3RoLCAwKTsKCiAgICAgICAgICBpZiAoIWFyaXR5ICYmIGJpdG1hc2sgJiAoV1JBUF9DVVJSWV9GTEFHIHwgV1JBUF9DVVJSWV9SSUdIVF9GTEFHKSkgewogICAgICAgICAgICBiaXRtYXNrICY9IH4oV1JBUF9DVVJSWV9GTEFHIHwgV1JBUF9DVVJSWV9SSUdIVF9GTEFHKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICghYml0bWFzayB8fCBiaXRtYXNrID09IFdSQVBfQklORF9GTEFHKSB7CiAgICAgICAgICAgIHZhciByZXN1bHQgPSBjcmVhdGVCaW5kKGZ1bmMsIGJpdG1hc2ssIHRoaXNBcmcpOwogICAgICAgICAgfSBlbHNlIGlmIChiaXRtYXNrID09IFdSQVBfQ1VSUllfRkxBRyB8fCBiaXRtYXNrID09IFdSQVBfQ1VSUllfUklHSFRfRkxBRykgewogICAgICAgICAgICByZXN1bHQgPSBjcmVhdGVDdXJyeShmdW5jLCBiaXRtYXNrLCBhcml0eSk7CiAgICAgICAgICB9IGVsc2UgaWYgKChiaXRtYXNrID09IFdSQVBfUEFSVElBTF9GTEFHIHx8IGJpdG1hc2sgPT0gKFdSQVBfQklORF9GTEFHIHwgV1JBUF9QQVJUSUFMX0ZMQUcpKSAmJiAhaG9sZGVycy5sZW5ndGgpIHsKICAgICAgICAgICAgcmVzdWx0ID0gY3JlYXRlUGFydGlhbChmdW5jLCBiaXRtYXNrLCB0aGlzQXJnLCBwYXJ0aWFscyk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXN1bHQgPSBjcmVhdGVIeWJyaWQuYXBwbHkodW5kZWZpbmVkJDEsIG5ld0RhdGEpOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHNldHRlciA9IGRhdGEgPyBiYXNlU2V0RGF0YSA6IHNldERhdGE7CiAgICAgICAgICByZXR1cm4gc2V0V3JhcFRvU3RyaW5nKHNldHRlcihyZXN1bHQsIG5ld0RhdGEpLCBmdW5jLCBiaXRtYXNrKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFVzZWQgYnkgYF8uZGVmYXVsdHNgIHRvIGN1c3RvbWl6ZSBpdHMgYF8uYXNzaWduSW5gIHVzZSB0byBhc3NpZ24gcHJvcGVydGllcwogICAgICAgICAqIG9mIHNvdXJjZSBvYmplY3RzIHRvIHRoZSBkZXN0aW5hdGlvbiBvYmplY3QgZm9yIGFsbCBkZXN0aW5hdGlvbiBwcm9wZXJ0aWVzCiAgICAgICAgICogdGhhdCByZXNvbHZlIHRvIGB1bmRlZmluZWRgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IG9ialZhbHVlIFRoZSBkZXN0aW5hdGlvbiB2YWx1ZS4KICAgICAgICAgKiBAcGFyYW0geyp9IHNyY1ZhbHVlIFRoZSBzb3VyY2UgdmFsdWUuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBhc3NpZ24uCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgcGFyZW50IG9iamVjdCBvZiBgb2JqVmFsdWVgLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSB2YWx1ZSB0byBhc3NpZ24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3VzdG9tRGVmYXVsdHNBc3NpZ25JbihvYmpWYWx1ZSwgc3JjVmFsdWUsIGtleSwgb2JqZWN0KSB7CiAgICAgICAgICBpZiAob2JqVmFsdWUgPT09IHVuZGVmaW5lZCQxIHx8CiAgICAgICAgICAgICAgKGVxKG9ialZhbHVlLCBvYmplY3RQcm90b1trZXldKSAmJiAhaGFzT3duUHJvcGVydHkuY2FsbChvYmplY3QsIGtleSkpKSB7CiAgICAgICAgICAgIHJldHVybiBzcmNWYWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBvYmpWYWx1ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFVzZWQgYnkgYF8uZGVmYXVsdHNEZWVwYCB0byBjdXN0b21pemUgaXRzIGBfLm1lcmdlYCB1c2UgdG8gbWVyZ2Ugc291cmNlCiAgICAgICAgICogb2JqZWN0cyBpbnRvIGRlc3RpbmF0aW9uIG9iamVjdHMgdGhhdCBhcmUgcGFzc2VkIHRocnUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gb2JqVmFsdWUgVGhlIGRlc3RpbmF0aW9uIHZhbHVlLgogICAgICAgICAqIEBwYXJhbSB7Kn0gc3JjVmFsdWUgVGhlIHNvdXJjZSB2YWx1ZS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIG1lcmdlLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIHBhcmVudCBvYmplY3Qgb2YgYG9ialZhbHVlYC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBwYXJlbnQgb2JqZWN0IG9mIGBzcmNWYWx1ZWAuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IFtzdGFja10gVHJhY2tzIHRyYXZlcnNlZCBzb3VyY2UgdmFsdWVzIGFuZCB0aGVpciBtZXJnZWQKICAgICAgICAgKiAgY291bnRlcnBhcnRzLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSB2YWx1ZSB0byBhc3NpZ24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3VzdG9tRGVmYXVsdHNNZXJnZShvYmpWYWx1ZSwgc3JjVmFsdWUsIGtleSwgb2JqZWN0LCBzb3VyY2UsIHN0YWNrKSB7CiAgICAgICAgICBpZiAoaXNPYmplY3Qob2JqVmFsdWUpICYmIGlzT2JqZWN0KHNyY1ZhbHVlKSkgewogICAgICAgICAgICAvLyBSZWN1cnNpdmVseSBtZXJnZSBvYmplY3RzIGFuZCBhcnJheXMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgc3RhY2suc2V0KHNyY1ZhbHVlLCBvYmpWYWx1ZSk7CiAgICAgICAgICAgIGJhc2VNZXJnZShvYmpWYWx1ZSwgc3JjVmFsdWUsIHVuZGVmaW5lZCQxLCBjdXN0b21EZWZhdWx0c01lcmdlLCBzdGFjayk7CiAgICAgICAgICAgIHN0YWNrWydkZWxldGUnXShzcmNWYWx1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gb2JqVmFsdWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBVc2VkIGJ5IGBfLm9taXRgIHRvIGN1c3RvbWl6ZSBpdHMgYF8uY2xvbmVEZWVwYCB1c2UgdG8gb25seSBjbG9uZSBwbGFpbgogICAgICAgICAqIG9iamVjdHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBpbnNwZWN0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSB1bmNsb25lZCB2YWx1ZSBvciBgdW5kZWZpbmVkYCB0byBkZWZlciBjbG9uaW5nIHRvIGBfLmNsb25lRGVlcGAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3VzdG9tT21pdENsb25lKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gaXNQbGFpbk9iamVjdCh2YWx1ZSkgPyB1bmRlZmluZWQkMSA6IHZhbHVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlSXNFcXVhbERlZXBgIGZvciBhcnJheXMgd2l0aCBzdXBwb3J0IGZvcgogICAgICAgICAqIHBhcnRpYWwgZGVlcCBjb21wYXJpc29ucy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gb3RoZXIgVGhlIG90aGVyIGFycmF5IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgYmFzZUlzRXF1YWxgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY3VzdG9taXplciBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNvbXBhcmlzb25zLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVxdWFsRnVuYyBUaGUgZnVuY3Rpb24gdG8gZGV0ZXJtaW5lIGVxdWl2YWxlbnRzIG9mIHZhbHVlcy4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc3RhY2sgVHJhY2tzIHRyYXZlcnNlZCBgYXJyYXlgIGFuZCBgb3RoZXJgIG9iamVjdHMuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBhcnJheXMgYXJlIGVxdWl2YWxlbnQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBlcXVhbEFycmF5cyhhcnJheSwgb3RoZXIsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spIHsKICAgICAgICAgIHZhciBpc1BhcnRpYWwgPSBiaXRtYXNrICYgQ09NUEFSRV9QQVJUSUFMX0ZMQUcsCiAgICAgICAgICAgICAgYXJyTGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIG90aExlbmd0aCA9IG90aGVyLmxlbmd0aDsKCiAgICAgICAgICBpZiAoYXJyTGVuZ3RoICE9IG90aExlbmd0aCAmJiAhKGlzUGFydGlhbCAmJiBvdGhMZW5ndGggPiBhcnJMZW5ndGgpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIENoZWNrIHRoYXQgY3ljbGljIHZhbHVlcyBhcmUgZXF1YWwuCiAgICAgICAgICB2YXIgYXJyU3RhY2tlZCA9IHN0YWNrLmdldChhcnJheSk7CiAgICAgICAgICB2YXIgb3RoU3RhY2tlZCA9IHN0YWNrLmdldChvdGhlcik7CiAgICAgICAgICBpZiAoYXJyU3RhY2tlZCAmJiBvdGhTdGFja2VkKSB7CiAgICAgICAgICAgIHJldHVybiBhcnJTdGFja2VkID09IG90aGVyICYmIG90aFN0YWNrZWQgPT0gYXJyYXk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICByZXN1bHQgPSB0cnVlLAogICAgICAgICAgICAgIHNlZW4gPSAoYml0bWFzayAmIENPTVBBUkVfVU5PUkRFUkVEX0ZMQUcpID8gbmV3IFNldENhY2hlIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgc3RhY2suc2V0KGFycmF5LCBvdGhlcik7CiAgICAgICAgICBzdGFjay5zZXQob3RoZXIsIGFycmF5KTsKCiAgICAgICAgICAvLyBJZ25vcmUgbm9uLWluZGV4IHByb3BlcnRpZXMuCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGFyckxlbmd0aCkgewogICAgICAgICAgICB2YXIgYXJyVmFsdWUgPSBhcnJheVtpbmRleF0sCiAgICAgICAgICAgICAgICBvdGhWYWx1ZSA9IG90aGVyW2luZGV4XTsKCiAgICAgICAgICAgIGlmIChjdXN0b21pemVyKSB7CiAgICAgICAgICAgICAgdmFyIGNvbXBhcmVkID0gaXNQYXJ0aWFsCiAgICAgICAgICAgICAgICA/IGN1c3RvbWl6ZXIob3RoVmFsdWUsIGFyclZhbHVlLCBpbmRleCwgb3RoZXIsIGFycmF5LCBzdGFjaykKICAgICAgICAgICAgICAgIDogY3VzdG9taXplcihhcnJWYWx1ZSwgb3RoVmFsdWUsIGluZGV4LCBhcnJheSwgb3RoZXIsIHN0YWNrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoY29tcGFyZWQgIT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgaWYgKGNvbXBhcmVkKSB7CiAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcmVzdWx0ID0gZmFsc2U7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVjdXJzaXZlbHkgY29tcGFyZSBhcnJheXMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgaWYgKHNlZW4pIHsKICAgICAgICAgICAgICBpZiAoIWFycmF5U29tZShvdGhlciwgZnVuY3Rpb24ob3RoVmFsdWUsIG90aEluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKCFjYWNoZUhhcyhzZWVuLCBvdGhJbmRleCkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgKGFyclZhbHVlID09PSBvdGhWYWx1ZSB8fCBlcXVhbEZ1bmMoYXJyVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykpKSB7CiAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gc2Vlbi5wdXNoKG90aEluZGV4KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgIH0pKSB7CiAgICAgICAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSBlbHNlIGlmICghKAogICAgICAgICAgICAgICAgICBhcnJWYWx1ZSA9PT0gb3RoVmFsdWUgfHwKICAgICAgICAgICAgICAgICAgICBlcXVhbEZ1bmMoYXJyVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykKICAgICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgc3RhY2tbJ2RlbGV0ZSddKGFycmF5KTsKICAgICAgICAgIHN0YWNrWydkZWxldGUnXShvdGhlcik7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlSXNFcXVhbERlZXBgIGZvciBjb21wYXJpbmcgb2JqZWN0cyBvZgogICAgICAgICAqIHRoZSBzYW1lIGB0b1N0cmluZ1RhZ2AuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBmdW5jdGlvbiBvbmx5IHN1cHBvcnRzIGNvbXBhcmluZyB2YWx1ZXMgd2l0aCB0YWdzIG9mCiAgICAgICAgICogYEJvb2xlYW5gLCBgRGF0ZWAsIGBFcnJvcmAsIGBOdW1iZXJgLCBgUmVnRXhwYCwgb3IgYFN0cmluZ2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvdGhlciBUaGUgb3RoZXIgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHRhZyBUaGUgYHRvU3RyaW5nVGFnYCBvZiB0aGUgb2JqZWN0cyB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBiaXRtYXNrIFRoZSBiaXRtYXNrIGZsYWdzLiBTZWUgYGJhc2VJc0VxdWFsYCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGN1c3RvbWl6ZXIgVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb21wYXJpc29ucy4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBlcXVhbEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRldGVybWluZSBlcXVpdmFsZW50cyBvZiB2YWx1ZXMuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHN0YWNrIFRyYWNrcyB0cmF2ZXJzZWQgYG9iamVjdGAgYW5kIGBvdGhlcmAgb2JqZWN0cy4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIG9iamVjdHMgYXJlIGVxdWl2YWxlbnQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBlcXVhbEJ5VGFnKG9iamVjdCwgb3RoZXIsIHRhZywgYml0bWFzaywgY3VzdG9taXplciwgZXF1YWxGdW5jLCBzdGFjaykgewogICAgICAgICAgc3dpdGNoICh0YWcpIHsKICAgICAgICAgICAgY2FzZSBkYXRhVmlld1RhZzoKICAgICAgICAgICAgICBpZiAoKG9iamVjdC5ieXRlTGVuZ3RoICE9IG90aGVyLmJ5dGVMZW5ndGgpIHx8CiAgICAgICAgICAgICAgICAgIChvYmplY3QuYnl0ZU9mZnNldCAhPSBvdGhlci5ieXRlT2Zmc2V0KSkgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBvYmplY3QgPSBvYmplY3QuYnVmZmVyOwogICAgICAgICAgICAgIG90aGVyID0gb3RoZXIuYnVmZmVyOwoKICAgICAgICAgICAgY2FzZSBhcnJheUJ1ZmZlclRhZzoKICAgICAgICAgICAgICBpZiAoKG9iamVjdC5ieXRlTGVuZ3RoICE9IG90aGVyLmJ5dGVMZW5ndGgpIHx8CiAgICAgICAgICAgICAgICAgICFlcXVhbEZ1bmMobmV3IFVpbnQ4QXJyYXkob2JqZWN0KSwgbmV3IFVpbnQ4QXJyYXkob3RoZXIpKSkgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKCiAgICAgICAgICAgIGNhc2UgYm9vbFRhZzoKICAgICAgICAgICAgY2FzZSBkYXRlVGFnOgogICAgICAgICAgICBjYXNlIG51bWJlclRhZzoKICAgICAgICAgICAgICAvLyBDb2VyY2UgYm9vbGVhbnMgdG8gYDFgIG9yIGAwYCBhbmQgZGF0ZXMgdG8gbWlsbGlzZWNvbmRzLgogICAgICAgICAgICAgIC8vIEludmFsaWQgZGF0ZXMgYXJlIGNvZXJjZWQgdG8gYE5hTmAuCiAgICAgICAgICAgICAgcmV0dXJuIGVxKCtvYmplY3QsICtvdGhlcik7CgogICAgICAgICAgICBjYXNlIGVycm9yVGFnOgogICAgICAgICAgICAgIHJldHVybiBvYmplY3QubmFtZSA9PSBvdGhlci5uYW1lICYmIG9iamVjdC5tZXNzYWdlID09IG90aGVyLm1lc3NhZ2U7CgogICAgICAgICAgICBjYXNlIHJlZ2V4cFRhZzoKICAgICAgICAgICAgY2FzZSBzdHJpbmdUYWc6CiAgICAgICAgICAgICAgLy8gQ29lcmNlIHJlZ2V4ZXMgdG8gc3RyaW5ncyBhbmQgdHJlYXQgc3RyaW5ncywgcHJpbWl0aXZlcyBhbmQgb2JqZWN0cywKICAgICAgICAgICAgICAvLyBhcyBlcXVhbC4gU2VlIGh0dHA6Ly93d3cuZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1yZWdleHAucHJvdG90eXBlLnRvc3RyaW5nCiAgICAgICAgICAgICAgLy8gZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgICAgICByZXR1cm4gb2JqZWN0ID09IChvdGhlciArICcnKTsKCiAgICAgICAgICAgIGNhc2UgbWFwVGFnOgogICAgICAgICAgICAgIHZhciBjb252ZXJ0ID0gbWFwVG9BcnJheTsKCiAgICAgICAgICAgIGNhc2Ugc2V0VGFnOgogICAgICAgICAgICAgIHZhciBpc1BhcnRpYWwgPSBiaXRtYXNrICYgQ09NUEFSRV9QQVJUSUFMX0ZMQUc7CiAgICAgICAgICAgICAgY29udmVydCB8fCAoY29udmVydCA9IHNldFRvQXJyYXkpOwoKICAgICAgICAgICAgICBpZiAob2JqZWN0LnNpemUgIT0gb3RoZXIuc2l6ZSAmJiAhaXNQYXJ0aWFsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIC8vIEFzc3VtZSBjeWNsaWMgdmFsdWVzIGFyZSBlcXVhbC4KICAgICAgICAgICAgICB2YXIgc3RhY2tlZCA9IHN0YWNrLmdldChvYmplY3QpOwogICAgICAgICAgICAgIGlmIChzdGFja2VkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gc3RhY2tlZCA9PSBvdGhlcjsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgYml0bWFzayB8PSBDT01QQVJFX1VOT1JERVJFRF9GTEFHOwoKICAgICAgICAgICAgICAvLyBSZWN1cnNpdmVseSBjb21wYXJlIG9iamVjdHMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgICBzdGFjay5zZXQob2JqZWN0LCBvdGhlcik7CiAgICAgICAgICAgICAgdmFyIHJlc3VsdCA9IGVxdWFsQXJyYXlzKGNvbnZlcnQob2JqZWN0KSwgY29udmVydChvdGhlciksIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spOwogICAgICAgICAgICAgIHN0YWNrWydkZWxldGUnXShvYmplY3QpOwogICAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CgogICAgICAgICAgICBjYXNlIHN5bWJvbFRhZzoKICAgICAgICAgICAgICBpZiAoc3ltYm9sVmFsdWVPZikgewogICAgICAgICAgICAgICAgcmV0dXJuIHN5bWJvbFZhbHVlT2YuY2FsbChvYmplY3QpID09IHN5bWJvbFZhbHVlT2YuY2FsbChvdGhlcik7CiAgICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlSXNFcXVhbERlZXBgIGZvciBvYmplY3RzIHdpdGggc3VwcG9ydCBmb3IKICAgICAgICAgKiBwYXJ0aWFsIGRlZXAgY29tcGFyaXNvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvdGhlciBUaGUgb3RoZXIgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgYmFzZUlzRXF1YWxgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY3VzdG9taXplciBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNvbXBhcmlzb25zLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVxdWFsRnVuYyBUaGUgZnVuY3Rpb24gdG8gZGV0ZXJtaW5lIGVxdWl2YWxlbnRzIG9mIHZhbHVlcy4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc3RhY2sgVHJhY2tzIHRyYXZlcnNlZCBgb2JqZWN0YCBhbmQgYG90aGVyYCBvYmplY3RzLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgb2JqZWN0cyBhcmUgZXF1aXZhbGVudCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGVxdWFsT2JqZWN0cyhvYmplY3QsIG90aGVyLCBiaXRtYXNrLCBjdXN0b21pemVyLCBlcXVhbEZ1bmMsIHN0YWNrKSB7CiAgICAgICAgICB2YXIgaXNQYXJ0aWFsID0gYml0bWFzayAmIENPTVBBUkVfUEFSVElBTF9GTEFHLAogICAgICAgICAgICAgIG9ialByb3BzID0gZ2V0QWxsS2V5cyhvYmplY3QpLAogICAgICAgICAgICAgIG9iakxlbmd0aCA9IG9ialByb3BzLmxlbmd0aCwKICAgICAgICAgICAgICBvdGhQcm9wcyA9IGdldEFsbEtleXMob3RoZXIpLAogICAgICAgICAgICAgIG90aExlbmd0aCA9IG90aFByb3BzLmxlbmd0aDsKCiAgICAgICAgICBpZiAob2JqTGVuZ3RoICE9IG90aExlbmd0aCAmJiAhaXNQYXJ0aWFsKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBpbmRleCA9IG9iakxlbmd0aDsKICAgICAgICAgIHdoaWxlIChpbmRleC0tKSB7CiAgICAgICAgICAgIHZhciBrZXkgPSBvYmpQcm9wc1tpbmRleF07CiAgICAgICAgICAgIGlmICghKGlzUGFydGlhbCA/IGtleSBpbiBvdGhlciA6IGhhc093blByb3BlcnR5LmNhbGwob3RoZXIsIGtleSkpKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDaGVjayB0aGF0IGN5Y2xpYyB2YWx1ZXMgYXJlIGVxdWFsLgogICAgICAgICAgdmFyIG9ialN0YWNrZWQgPSBzdGFjay5nZXQob2JqZWN0KTsKICAgICAgICAgIHZhciBvdGhTdGFja2VkID0gc3RhY2suZ2V0KG90aGVyKTsKICAgICAgICAgIGlmIChvYmpTdGFja2VkICYmIG90aFN0YWNrZWQpIHsKICAgICAgICAgICAgcmV0dXJuIG9ialN0YWNrZWQgPT0gb3RoZXIgJiYgb3RoU3RhY2tlZCA9PSBvYmplY3Q7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcmVzdWx0ID0gdHJ1ZTsKICAgICAgICAgIHN0YWNrLnNldChvYmplY3QsIG90aGVyKTsKICAgICAgICAgIHN0YWNrLnNldChvdGhlciwgb2JqZWN0KTsKCiAgICAgICAgICB2YXIgc2tpcEN0b3IgPSBpc1BhcnRpYWw7CiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IG9iakxlbmd0aCkgewogICAgICAgICAgICBrZXkgPSBvYmpQcm9wc1tpbmRleF07CiAgICAgICAgICAgIHZhciBvYmpWYWx1ZSA9IG9iamVjdFtrZXldLAogICAgICAgICAgICAgICAgb3RoVmFsdWUgPSBvdGhlcltrZXldOwoKICAgICAgICAgICAgaWYgKGN1c3RvbWl6ZXIpIHsKICAgICAgICAgICAgICB2YXIgY29tcGFyZWQgPSBpc1BhcnRpYWwKICAgICAgICAgICAgICAgID8gY3VzdG9taXplcihvdGhWYWx1ZSwgb2JqVmFsdWUsIGtleSwgb3RoZXIsIG9iamVjdCwgc3RhY2spCiAgICAgICAgICAgICAgICA6IGN1c3RvbWl6ZXIob2JqVmFsdWUsIG90aFZhbHVlLCBrZXksIG9iamVjdCwgb3RoZXIsIHN0YWNrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZWN1cnNpdmVseSBjb21wYXJlIG9iamVjdHMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgaWYgKCEoY29tcGFyZWQgPT09IHVuZGVmaW5lZCQxCiAgICAgICAgICAgICAgICAgID8gKG9ialZhbHVlID09PSBvdGhWYWx1ZSB8fCBlcXVhbEZ1bmMob2JqVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykpCiAgICAgICAgICAgICAgICAgIDogY29tcGFyZWQKICAgICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBza2lwQ3RvciB8fCAoc2tpcEN0b3IgPSBrZXkgPT0gJ2NvbnN0cnVjdG9yJyk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAocmVzdWx0ICYmICFza2lwQ3RvcikgewogICAgICAgICAgICB2YXIgb2JqQ3RvciA9IG9iamVjdC5jb25zdHJ1Y3RvciwKICAgICAgICAgICAgICAgIG90aEN0b3IgPSBvdGhlci5jb25zdHJ1Y3RvcjsKCiAgICAgICAgICAgIC8vIE5vbiBgT2JqZWN0YCBvYmplY3QgaW5zdGFuY2VzIHdpdGggZGlmZmVyZW50IGNvbnN0cnVjdG9ycyBhcmUgbm90IGVxdWFsLgogICAgICAgICAgICBpZiAob2JqQ3RvciAhPSBvdGhDdG9yICYmCiAgICAgICAgICAgICAgICAoJ2NvbnN0cnVjdG9yJyBpbiBvYmplY3QgJiYgJ2NvbnN0cnVjdG9yJyBpbiBvdGhlcikgJiYKICAgICAgICAgICAgICAgICEodHlwZW9mIG9iakN0b3IgPT0gJ2Z1bmN0aW9uJyAmJiBvYmpDdG9yIGluc3RhbmNlb2Ygb2JqQ3RvciAmJgogICAgICAgICAgICAgICAgICB0eXBlb2Ygb3RoQ3RvciA9PSAnZnVuY3Rpb24nICYmIG90aEN0b3IgaW5zdGFuY2VvZiBvdGhDdG9yKSkgewogICAgICAgICAgICAgIHJlc3VsdCA9IGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBzdGFja1snZGVsZXRlJ10ob2JqZWN0KTsKICAgICAgICAgIHN0YWNrWydkZWxldGUnXShvdGhlcik7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlUmVzdGAgd2hpY2ggZmxhdHRlbnMgdGhlIHJlc3QgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGFwcGx5IGEgcmVzdCBwYXJhbWV0ZXIgdG8uCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZmxhdFJlc3QoZnVuYykgewogICAgICAgICAgcmV0dXJuIHNldFRvU3RyaW5nKG92ZXJSZXN0KGZ1bmMsIHVuZGVmaW5lZCQxLCBmbGF0dGVuKSwgZnVuYyArICcnKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2Ygb3duIGVudW1lcmFibGUgcHJvcGVydHkgbmFtZXMgYW5kIHN5bWJvbHMgb2YgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzIGFuZCBzeW1ib2xzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldEFsbEtleXMob2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gYmFzZUdldEFsbEtleXMob2JqZWN0LCBrZXlzLCBnZXRTeW1ib2xzKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2Ygb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBwcm9wZXJ0eSBuYW1lcyBhbmQKICAgICAgICAgKiBzeW1ib2xzIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcyBhbmQgc3ltYm9scy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBnZXRBbGxLZXlzSW4ob2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gYmFzZUdldEFsbEtleXMob2JqZWN0LCBrZXlzSW4sIGdldFN5bWJvbHNJbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIG1ldGFkYXRhIGZvciBgZnVuY2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBtZXRhZGF0YSBmb3IgYGZ1bmNgLgogICAgICAgICAqLwogICAgICAgIHZhciBnZXREYXRhID0gIW1ldGFNYXAgPyBub29wIDogZnVuY3Rpb24oZnVuYykgewogICAgICAgICAgcmV0dXJuIG1ldGFNYXAuZ2V0KGZ1bmMpOwogICAgICAgIH07CgogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIG5hbWUgb2YgYGZ1bmNgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBmdW5jdGlvbiBuYW1lLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldEZ1bmNOYW1lKGZ1bmMpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSAoZnVuYy5uYW1lICsgJycpLAogICAgICAgICAgICAgIGFycmF5ID0gcmVhbE5hbWVzW3Jlc3VsdF0sCiAgICAgICAgICAgICAgbGVuZ3RoID0gaGFzT3duUHJvcGVydHkuY2FsbChyZWFsTmFtZXMsIHJlc3VsdCkgPyBhcnJheS5sZW5ndGggOiAwOwoKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICB2YXIgZGF0YSA9IGFycmF5W2xlbmd0aF0sCiAgICAgICAgICAgICAgICBvdGhlckZ1bmMgPSBkYXRhLmZ1bmM7CiAgICAgICAgICAgIGlmIChvdGhlckZ1bmMgPT0gbnVsbCB8fCBvdGhlckZ1bmMgPT0gZnVuYykgewogICAgICAgICAgICAgIHJldHVybiBkYXRhLm5hbWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBhcmd1bWVudCBwbGFjZWhvbGRlciB2YWx1ZSBmb3IgYGZ1bmNgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBpbnNwZWN0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBwbGFjZWhvbGRlciB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBnZXRIb2xkZXIoZnVuYykgewogICAgICAgICAgdmFyIG9iamVjdCA9IGhhc093blByb3BlcnR5LmNhbGwobG9kYXNoLCAncGxhY2Vob2xkZXInKSA/IGxvZGFzaCA6IGZ1bmM7CiAgICAgICAgICByZXR1cm4gb2JqZWN0LnBsYWNlaG9sZGVyOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgYXBwcm9wcmlhdGUgIml0ZXJhdGVlIiBmdW5jdGlvbi4gSWYgYF8uaXRlcmF0ZWVgIGlzIGN1c3RvbWl6ZWQsCiAgICAgICAgICogdGhpcyBmdW5jdGlvbiByZXR1cm5zIHRoZSBjdXN0b20gbWV0aG9kLCBvdGhlcndpc2UgaXQgcmV0dXJucyBgYmFzZUl0ZXJhdGVlYC4KICAgICAgICAgKiBJZiBhcmd1bWVudHMgYXJlIHByb3ZpZGVkLCB0aGUgY2hvc2VuIGZ1bmN0aW9uIGlzIGludm9rZWQgd2l0aCB0aGVtIGFuZAogICAgICAgICAqIGl0cyByZXN1bHQgaXMgcmV0dXJuZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gW3ZhbHVlXSBUaGUgdmFsdWUgdG8gY29udmVydCB0byBhbiBpdGVyYXRlZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2FyaXR5XSBUaGUgYXJpdHkgb2YgdGhlIGNyZWF0ZWQgaXRlcmF0ZWUuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBjaG9zZW4gZnVuY3Rpb24gb3IgaXRzIHJlc3VsdC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBnZXRJdGVyYXRlZSgpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBsb2Rhc2guaXRlcmF0ZWUgfHwgaXRlcmF0ZWU7CiAgICAgICAgICByZXN1bHQgPSByZXN1bHQgPT09IGl0ZXJhdGVlID8gYmFzZUl0ZXJhdGVlIDogcmVzdWx0OwogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyByZXN1bHQoYXJndW1lbnRzWzBdLCBhcmd1bWVudHNbMV0pIDogcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgZGF0YSBmb3IgYG1hcGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBtYXAgVGhlIG1hcCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSByZWZlcmVuY2Uga2V5LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBtYXAgZGF0YS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBnZXRNYXBEYXRhKG1hcCwga2V5KSB7CiAgICAgICAgICB2YXIgZGF0YSA9IG1hcC5fX2RhdGFfXzsKICAgICAgICAgIHJldHVybiBpc0tleWFibGUoa2V5KQogICAgICAgICAgICA/IGRhdGFbdHlwZW9mIGtleSA9PSAnc3RyaW5nJyA/ICdzdHJpbmcnIDogJ2hhc2gnXQogICAgICAgICAgICA6IGRhdGEubWFwOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgcHJvcGVydHkgbmFtZXMsIHZhbHVlcywgYW5kIGNvbXBhcmUgZmxhZ3Mgb2YgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG1hdGNoIGRhdGEgb2YgYG9iamVjdGAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZ2V0TWF0Y2hEYXRhKG9iamVjdCkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IGtleXMob2JqZWN0KSwKICAgICAgICAgICAgICBsZW5ndGggPSByZXN1bHQubGVuZ3RoOwoKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICB2YXIga2V5ID0gcmVzdWx0W2xlbmd0aF0sCiAgICAgICAgICAgICAgICB2YWx1ZSA9IG9iamVjdFtrZXldOwoKICAgICAgICAgICAgcmVzdWx0W2xlbmd0aF0gPSBba2V5LCB2YWx1ZSwgaXNTdHJpY3RDb21wYXJhYmxlKHZhbHVlKV07CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgbmF0aXZlIGZ1bmN0aW9uIGF0IGBrZXlgIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBtZXRob2QgdG8gZ2V0LgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBmdW5jdGlvbiBpZiBpdCdzIG5hdGl2ZSwgZWxzZSBgdW5kZWZpbmVkYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBnZXROYXRpdmUob2JqZWN0LCBrZXkpIHsKICAgICAgICAgIHZhciB2YWx1ZSA9IGdldFZhbHVlKG9iamVjdCwga2V5KTsKICAgICAgICAgIHJldHVybiBiYXNlSXNOYXRpdmUodmFsdWUpID8gdmFsdWUgOiB1bmRlZmluZWQkMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZUdldFRhZ2Agd2hpY2ggaWdub3JlcyBgU3ltYm9sLnRvU3RyaW5nVGFnYCB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHJhdyBgdG9TdHJpbmdUYWdgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldFJhd1RhZyh2YWx1ZSkgewogICAgICAgICAgdmFyIGlzT3duID0gaGFzT3duUHJvcGVydHkuY2FsbCh2YWx1ZSwgc3ltVG9TdHJpbmdUYWcpLAogICAgICAgICAgICAgIHRhZyA9IHZhbHVlW3N5bVRvU3RyaW5nVGFnXTsKCiAgICAgICAgICB0cnkgewogICAgICAgICAgICB2YWx1ZVtzeW1Ub1N0cmluZ1RhZ10gPSB1bmRlZmluZWQkMTsKICAgICAgICAgICAgdmFyIHVubWFza2VkID0gdHJ1ZTsKICAgICAgICAgIH0gY2F0Y2ggKGUpIHt9CgogICAgICAgICAgdmFyIHJlc3VsdCA9IG5hdGl2ZU9iamVjdFRvU3RyaW5nLmNhbGwodmFsdWUpOwogICAgICAgICAgaWYgKHVubWFza2VkKSB7CiAgICAgICAgICAgIGlmIChpc093bikgewogICAgICAgICAgICAgIHZhbHVlW3N5bVRvU3RyaW5nVGFnXSA9IHRhZzsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBkZWxldGUgdmFsdWVbc3ltVG9TdHJpbmdUYWddOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGVudW1lcmFibGUgc3ltYm9scyBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgYXJyYXkgb2Ygc3ltYm9scy4KICAgICAgICAgKi8KICAgICAgICB2YXIgZ2V0U3ltYm9scyA9ICFuYXRpdmVHZXRTeW1ib2xzID8gc3R1YkFycmF5IDogZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgICBpZiAob2JqZWN0ID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgb2JqZWN0ID0gT2JqZWN0KG9iamVjdCk7CiAgICAgICAgICByZXR1cm4gYXJyYXlGaWx0ZXIobmF0aXZlR2V0U3ltYm9scyhvYmplY3QpLCBmdW5jdGlvbihzeW1ib2wpIHsKICAgICAgICAgICAgcmV0dXJuIHByb3BlcnR5SXNFbnVtZXJhYmxlLmNhbGwob2JqZWN0LCBzeW1ib2wpOwogICAgICAgICAgfSk7CiAgICAgICAgfTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBzeW1ib2xzIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBzeW1ib2xzLgogICAgICAgICAqLwogICAgICAgIHZhciBnZXRTeW1ib2xzSW4gPSAhbmF0aXZlR2V0U3ltYm9scyA/IHN0dWJBcnJheSA6IGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICAgICAgd2hpbGUgKG9iamVjdCkgewogICAgICAgICAgICBhcnJheVB1c2gocmVzdWx0LCBnZXRTeW1ib2xzKG9iamVjdCkpOwogICAgICAgICAgICBvYmplY3QgPSBnZXRQcm90b3R5cGUob2JqZWN0KTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfTsKCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgYHRvU3RyaW5nVGFnYCBvZiBgdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBgdG9TdHJpbmdUYWdgLgogICAgICAgICAqLwogICAgICAgIHZhciBnZXRUYWcgPSBiYXNlR2V0VGFnOwoKICAgICAgICAvLyBGYWxsYmFjayBmb3IgZGF0YSB2aWV3cywgbWFwcywgc2V0cywgYW5kIHdlYWsgbWFwcyBpbiBJRSAxMSBhbmQgcHJvbWlzZXMgaW4gTm9kZS5qcyA8IDYuCiAgICAgICAgaWYgKChEYXRhVmlldyAmJiBnZXRUYWcobmV3IERhdGFWaWV3KG5ldyBBcnJheUJ1ZmZlcigxKSkpICE9IGRhdGFWaWV3VGFnKSB8fAogICAgICAgICAgICAoTWFwICYmIGdldFRhZyhuZXcgTWFwKSAhPSBtYXBUYWcpIHx8CiAgICAgICAgICAgIChQcm9taXNlICYmIGdldFRhZyhQcm9taXNlLnJlc29sdmUoKSkgIT0gcHJvbWlzZVRhZykgfHwKICAgICAgICAgICAgKFNldCAmJiBnZXRUYWcobmV3IFNldCkgIT0gc2V0VGFnKSB8fAogICAgICAgICAgICAoV2Vha01hcCAmJiBnZXRUYWcobmV3IFdlYWtNYXApICE9IHdlYWtNYXBUYWcpKSB7CiAgICAgICAgICBnZXRUYWcgPSBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgICB2YXIgcmVzdWx0ID0gYmFzZUdldFRhZyh2YWx1ZSksCiAgICAgICAgICAgICAgICBDdG9yID0gcmVzdWx0ID09IG9iamVjdFRhZyA/IHZhbHVlLmNvbnN0cnVjdG9yIDogdW5kZWZpbmVkJDEsCiAgICAgICAgICAgICAgICBjdG9yU3RyaW5nID0gQ3RvciA/IHRvU291cmNlKEN0b3IpIDogJyc7CgogICAgICAgICAgICBpZiAoY3RvclN0cmluZykgewogICAgICAgICAgICAgIHN3aXRjaCAoY3RvclN0cmluZykgewogICAgICAgICAgICAgICAgY2FzZSBkYXRhVmlld0N0b3JTdHJpbmc6IHJldHVybiBkYXRhVmlld1RhZzsKICAgICAgICAgICAgICAgIGNhc2UgbWFwQ3RvclN0cmluZzogcmV0dXJuIG1hcFRhZzsKICAgICAgICAgICAgICAgIGNhc2UgcHJvbWlzZUN0b3JTdHJpbmc6IHJldHVybiBwcm9taXNlVGFnOwogICAgICAgICAgICAgICAgY2FzZSBzZXRDdG9yU3RyaW5nOiByZXR1cm4gc2V0VGFnOwogICAgICAgICAgICAgICAgY2FzZSB3ZWFrTWFwQ3RvclN0cmluZzogcmV0dXJuIHdlYWtNYXBUYWc7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgdmlldywgYXBwbHlpbmcgYW55IGB0cmFuc2Zvcm1zYCB0byB0aGUgYHN0YXJ0YCBhbmQgYGVuZGAgcG9zaXRpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gc3RhcnQgVGhlIHN0YXJ0IG9mIHRoZSB2aWV3LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBlbmQgVGhlIGVuZCBvZiB0aGUgdmlldy4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSB0cmFuc2Zvcm1zIFRoZSB0cmFuc2Zvcm1hdGlvbnMgdG8gYXBwbHkgdG8gdGhlIHZpZXcuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBhbiBvYmplY3QgY29udGFpbmluZyB0aGUgYHN0YXJ0YCBhbmQgYGVuZGAKICAgICAgICAgKiAgcG9zaXRpb25zIG9mIHRoZSB2aWV3LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldFZpZXcoc3RhcnQsIGVuZCwgdHJhbnNmb3JtcykgewogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgbGVuZ3RoID0gdHJhbnNmb3Jtcy5sZW5ndGg7CgogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGRhdGEgPSB0cmFuc2Zvcm1zW2luZGV4XSwKICAgICAgICAgICAgICAgIHNpemUgPSBkYXRhLnNpemU7CgogICAgICAgICAgICBzd2l0Y2ggKGRhdGEudHlwZSkgewogICAgICAgICAgICAgIGNhc2UgJ2Ryb3AnOiAgICAgIHN0YXJ0ICs9IHNpemU7IGJyZWFrOwogICAgICAgICAgICAgIGNhc2UgJ2Ryb3BSaWdodCc6IGVuZCAtPSBzaXplOyBicmVhazsKICAgICAgICAgICAgICBjYXNlICd0YWtlJzogICAgICBlbmQgPSBuYXRpdmVNaW4oZW5kLCBzdGFydCArIHNpemUpOyBicmVhazsKICAgICAgICAgICAgICBjYXNlICd0YWtlUmlnaHQnOiBzdGFydCA9IG5hdGl2ZU1heChzdGFydCwgZW5kIC0gc2l6ZSk7IGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4geyAnc3RhcnQnOiBzdGFydCwgJ2VuZCc6IGVuZCB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRXh0cmFjdHMgd3JhcHBlciBkZXRhaWxzIGZyb20gdGhlIGBzb3VyY2VgIGJvZHkgY29tbWVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHNvdXJjZSBUaGUgc291cmNlIHRvIGluc3BlY3QuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSB3cmFwcGVyIGRldGFpbHMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZ2V0V3JhcERldGFpbHMoc291cmNlKSB7CiAgICAgICAgICB2YXIgbWF0Y2ggPSBzb3VyY2UubWF0Y2gocmVXcmFwRGV0YWlscyk7CiAgICAgICAgICByZXR1cm4gbWF0Y2ggPyBtYXRjaFsxXS5zcGxpdChyZVNwbGl0RGV0YWlscykgOiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgcGF0aGAgZXhpc3RzIG9uIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggdG8gY2hlY2suCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaGFzRnVuYyBUaGUgZnVuY3Rpb24gdG8gY2hlY2sgcHJvcGVydGllcy4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHBhdGhgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGhhc1BhdGgob2JqZWN0LCBwYXRoLCBoYXNGdW5jKSB7CiAgICAgICAgICBwYXRoID0gY2FzdFBhdGgocGF0aCwgb2JqZWN0KTsKCiAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICBsZW5ndGggPSBwYXRoLmxlbmd0aCwKICAgICAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIga2V5ID0gdG9LZXkocGF0aFtpbmRleF0pOwogICAgICAgICAgICBpZiAoIShyZXN1bHQgPSBvYmplY3QgIT0gbnVsbCAmJiBoYXNGdW5jKG9iamVjdCwga2V5KSkpIHsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBvYmplY3QgPSBvYmplY3Rba2V5XTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChyZXN1bHQgfHwgKytpbmRleCAhPSBsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIGxlbmd0aCA9IG9iamVjdCA9PSBudWxsID8gMCA6IG9iamVjdC5sZW5ndGg7CiAgICAgICAgICByZXR1cm4gISFsZW5ndGggJiYgaXNMZW5ndGgobGVuZ3RoKSAmJiBpc0luZGV4KGtleSwgbGVuZ3RoKSAmJgogICAgICAgICAgICAoaXNBcnJheShvYmplY3QpIHx8IGlzQXJndW1lbnRzKG9iamVjdCkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogSW5pdGlhbGl6ZXMgYW4gYXJyYXkgY2xvbmUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGluaXRpYWxpemVkIGNsb25lLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGluaXRDbG9uZUFycmF5KGFycmF5KSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIHJlc3VsdCA9IG5ldyBhcnJheS5jb25zdHJ1Y3RvcihsZW5ndGgpOwoKICAgICAgICAgIC8vIEFkZCBwcm9wZXJ0aWVzIGFzc2lnbmVkIGJ5IGBSZWdFeHAjZXhlY2AuCiAgICAgICAgICBpZiAobGVuZ3RoICYmIHR5cGVvZiBhcnJheVswXSA9PSAnc3RyaW5nJyAmJiBoYXNPd25Qcm9wZXJ0eS5jYWxsKGFycmF5LCAnaW5kZXgnKSkgewogICAgICAgICAgICByZXN1bHQuaW5kZXggPSBhcnJheS5pbmRleDsKICAgICAgICAgICAgcmVzdWx0LmlucHV0ID0gYXJyYXkuaW5wdXQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogSW5pdGlhbGl6ZXMgYW4gb2JqZWN0IGNsb25lLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gY2xvbmUuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgaW5pdGlhbGl6ZWQgY2xvbmUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaW5pdENsb25lT2JqZWN0KG9iamVjdCkgewogICAgICAgICAgcmV0dXJuICh0eXBlb2Ygb2JqZWN0LmNvbnN0cnVjdG9yID09ICdmdW5jdGlvbicgJiYgIWlzUHJvdG90eXBlKG9iamVjdCkpCiAgICAgICAgICAgID8gYmFzZUNyZWF0ZShnZXRQcm90b3R5cGUob2JqZWN0KSkKICAgICAgICAgICAgOiB7fTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEluaXRpYWxpemVzIGFuIG9iamVjdCBjbG9uZSBiYXNlZCBvbiBpdHMgYHRvU3RyaW5nVGFnYC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIGZ1bmN0aW9uIG9ubHkgc3VwcG9ydHMgY2xvbmluZyB2YWx1ZXMgd2l0aCB0YWdzIG9mCiAgICAgICAgICogYEJvb2xlYW5gLCBgRGF0ZWAsIGBFcnJvcmAsIGBNYXBgLCBgTnVtYmVyYCwgYFJlZ0V4cGAsIGBTZXRgLCBvciBgU3RyaW5nYC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGNsb25lLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0YWcgVGhlIGB0b1N0cmluZ1RhZ2Agb2YgdGhlIG9iamVjdCB0byBjbG9uZS4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpc0RlZXBdIFNwZWNpZnkgYSBkZWVwIGNsb25lLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGluaXRpYWxpemVkIGNsb25lLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGluaXRDbG9uZUJ5VGFnKG9iamVjdCwgdGFnLCBpc0RlZXApIHsKICAgICAgICAgIHZhciBDdG9yID0gb2JqZWN0LmNvbnN0cnVjdG9yOwogICAgICAgICAgc3dpdGNoICh0YWcpIHsKICAgICAgICAgICAgY2FzZSBhcnJheUJ1ZmZlclRhZzoKICAgICAgICAgICAgICByZXR1cm4gY2xvbmVBcnJheUJ1ZmZlcihvYmplY3QpOwoKICAgICAgICAgICAgY2FzZSBib29sVGFnOgogICAgICAgICAgICBjYXNlIGRhdGVUYWc6CiAgICAgICAgICAgICAgcmV0dXJuIG5ldyBDdG9yKCtvYmplY3QpOwoKICAgICAgICAgICAgY2FzZSBkYXRhVmlld1RhZzoKICAgICAgICAgICAgICByZXR1cm4gY2xvbmVEYXRhVmlldyhvYmplY3QsIGlzRGVlcCk7CgogICAgICAgICAgICBjYXNlIGZsb2F0MzJUYWc6IGNhc2UgZmxvYXQ2NFRhZzoKICAgICAgICAgICAgY2FzZSBpbnQ4VGFnOiBjYXNlIGludDE2VGFnOiBjYXNlIGludDMyVGFnOgogICAgICAgICAgICBjYXNlIHVpbnQ4VGFnOiBjYXNlIHVpbnQ4Q2xhbXBlZFRhZzogY2FzZSB1aW50MTZUYWc6IGNhc2UgdWludDMyVGFnOgogICAgICAgICAgICAgIHJldHVybiBjbG9uZVR5cGVkQXJyYXkob2JqZWN0LCBpc0RlZXApOwoKICAgICAgICAgICAgY2FzZSBtYXBUYWc6CiAgICAgICAgICAgICAgcmV0dXJuIG5ldyBDdG9yOwoKICAgICAgICAgICAgY2FzZSBudW1iZXJUYWc6CiAgICAgICAgICAgIGNhc2Ugc3RyaW5nVGFnOgogICAgICAgICAgICAgIHJldHVybiBuZXcgQ3RvcihvYmplY3QpOwoKICAgICAgICAgICAgY2FzZSByZWdleHBUYWc6CiAgICAgICAgICAgICAgcmV0dXJuIGNsb25lUmVnRXhwKG9iamVjdCk7CgogICAgICAgICAgICBjYXNlIHNldFRhZzoKICAgICAgICAgICAgICByZXR1cm4gbmV3IEN0b3I7CgogICAgICAgICAgICBjYXNlIHN5bWJvbFRhZzoKICAgICAgICAgICAgICByZXR1cm4gY2xvbmVTeW1ib2wob2JqZWN0KTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEluc2VydHMgd3JhcHBlciBgZGV0YWlsc2AgaW4gYSBjb21tZW50IGF0IHRoZSB0b3Agb2YgdGhlIGBzb3VyY2VgIGJvZHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzb3VyY2UgVGhlIHNvdXJjZSB0byBtb2RpZnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBkZXRhaWxzIFRoZSBkZXRhaWxzIHRvIGluc2VydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBtb2RpZmllZCBzb3VyY2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaW5zZXJ0V3JhcERldGFpbHMoc291cmNlLCBkZXRhaWxzKSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gZGV0YWlscy5sZW5ndGg7CiAgICAgICAgICBpZiAoIWxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gc291cmNlOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGxhc3RJbmRleCA9IGxlbmd0aCAtIDE7CiAgICAgICAgICBkZXRhaWxzW2xhc3RJbmRleF0gPSAobGVuZ3RoID4gMSA/ICcmICcgOiAnJykgKyBkZXRhaWxzW2xhc3RJbmRleF07CiAgICAgICAgICBkZXRhaWxzID0gZGV0YWlscy5qb2luKGxlbmd0aCA+IDIgPyAnLCAnIDogJyAnKTsKICAgICAgICAgIHJldHVybiBzb3VyY2UucmVwbGFjZShyZVdyYXBDb21tZW50LCAne1xuLyogW3dyYXBwZWQgd2l0aCAnICsgZGV0YWlscyArICddICovXG4nKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgZmxhdHRlbmFibGUgYGFyZ3VtZW50c2Agb2JqZWN0IG9yIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBmbGF0dGVuYWJsZSwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzRmxhdHRlbmFibGUodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc0FycmF5KHZhbHVlKSB8fCBpc0FyZ3VtZW50cyh2YWx1ZSkgfHwKICAgICAgICAgICAgISEoc3ByZWFkYWJsZVN5bWJvbCAmJiB2YWx1ZSAmJiB2YWx1ZVtzcHJlYWRhYmxlU3ltYm9sXSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIHZhbGlkIGFycmF5LWxpa2UgaW5kZXguCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbGVuZ3RoPU1BWF9TQUZFX0lOVEVHRVJdIFRoZSB1cHBlciBib3VuZHMgb2YgYSB2YWxpZCBpbmRleC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHZhbGlkIGluZGV4LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNJbmRleCh2YWx1ZSwgbGVuZ3RoKSB7CiAgICAgICAgICB2YXIgdHlwZSA9IHR5cGVvZiB2YWx1ZTsKICAgICAgICAgIGxlbmd0aCA9IGxlbmd0aCA9PSBudWxsID8gTUFYX1NBRkVfSU5URUdFUiA6IGxlbmd0aDsKCiAgICAgICAgICByZXR1cm4gISFsZW5ndGggJiYKICAgICAgICAgICAgKHR5cGUgPT0gJ251bWJlcicgfHwKICAgICAgICAgICAgICAodHlwZSAhPSAnc3ltYm9sJyAmJiByZUlzVWludC50ZXN0KHZhbHVlKSkpICYmCiAgICAgICAgICAgICAgICAodmFsdWUgPiAtMSAmJiB2YWx1ZSAlIDEgPT0gMCAmJiB2YWx1ZSA8IGxlbmd0aCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgdGhlIGdpdmVuIGFyZ3VtZW50cyBhcmUgZnJvbSBhbiBpdGVyYXRlZSBjYWxsLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSBwb3RlbnRpYWwgaXRlcmF0ZWUgdmFsdWUgYXJndW1lbnQuCiAgICAgICAgICogQHBhcmFtIHsqfSBpbmRleCBUaGUgcG90ZW50aWFsIGl0ZXJhdGVlIGluZGV4IG9yIGtleSBhcmd1bWVudC4KICAgICAgICAgKiBAcGFyYW0geyp9IG9iamVjdCBUaGUgcG90ZW50aWFsIGl0ZXJhdGVlIG9iamVjdCBhcmd1bWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIGFyZ3VtZW50cyBhcmUgZnJvbSBhbiBpdGVyYXRlZSBjYWxsLAogICAgICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNJdGVyYXRlZUNhbGwodmFsdWUsIGluZGV4LCBvYmplY3QpIHsKICAgICAgICAgIGlmICghaXNPYmplY3Qob2JqZWN0KSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgdHlwZSA9IHR5cGVvZiBpbmRleDsKICAgICAgICAgIGlmICh0eXBlID09ICdudW1iZXInCiAgICAgICAgICAgICAgICA/IChpc0FycmF5TGlrZShvYmplY3QpICYmIGlzSW5kZXgoaW5kZXgsIG9iamVjdC5sZW5ndGgpKQogICAgICAgICAgICAgICAgOiAodHlwZSA9PSAnc3RyaW5nJyAmJiBpbmRleCBpbiBvYmplY3QpCiAgICAgICAgICAgICAgKSB7CiAgICAgICAgICAgIHJldHVybiBlcShvYmplY3RbaW5kZXhdLCB2YWx1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIHByb3BlcnR5IG5hbWUgYW5kIG5vdCBhIHByb3BlcnR5IHBhdGguCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0XSBUaGUgb2JqZWN0IHRvIHF1ZXJ5IGtleXMgb24uCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBwcm9wZXJ0eSBuYW1lLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNLZXkodmFsdWUsIG9iamVjdCkgewogICAgICAgICAgaWYgKGlzQXJyYXkodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciB0eXBlID0gdHlwZW9mIHZhbHVlOwogICAgICAgICAgaWYgKHR5cGUgPT0gJ251bWJlcicgfHwgdHlwZSA9PSAnc3ltYm9sJyB8fCB0eXBlID09ICdib29sZWFuJyB8fAogICAgICAgICAgICAgIHZhbHVlID09IG51bGwgfHwgaXNTeW1ib2wodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlSXNQbGFpblByb3AudGVzdCh2YWx1ZSkgfHwgIXJlSXNEZWVwUHJvcC50ZXN0KHZhbHVlKSB8fAogICAgICAgICAgICAob2JqZWN0ICE9IG51bGwgJiYgdmFsdWUgaW4gT2JqZWN0KG9iamVjdCkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgc3VpdGFibGUgZm9yIHVzZSBhcyB1bmlxdWUgb2JqZWN0IGtleS4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgc3VpdGFibGUsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc0tleWFibGUodmFsdWUpIHsKICAgICAgICAgIHZhciB0eXBlID0gdHlwZW9mIHZhbHVlOwogICAgICAgICAgcmV0dXJuICh0eXBlID09ICdzdHJpbmcnIHx8IHR5cGUgPT0gJ251bWJlcicgfHwgdHlwZSA9PSAnc3ltYm9sJyB8fCB0eXBlID09ICdib29sZWFuJykKICAgICAgICAgICAgPyAodmFsdWUgIT09ICdfX3Byb3RvX18nKQogICAgICAgICAgICA6ICh2YWx1ZSA9PT0gbnVsbCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYGZ1bmNgIGhhcyBhIGxhenkgY291bnRlcnBhcnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgZnVuY2AgaGFzIGEgbGF6eSBjb3VudGVycGFydCwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTGF6aWFibGUoZnVuYykgewogICAgICAgICAgdmFyIGZ1bmNOYW1lID0gZ2V0RnVuY05hbWUoZnVuYyksCiAgICAgICAgICAgICAgb3RoZXIgPSBsb2Rhc2hbZnVuY05hbWVdOwoKICAgICAgICAgIGlmICh0eXBlb2Ygb3RoZXIgIT0gJ2Z1bmN0aW9uJyB8fCAhKGZ1bmNOYW1lIGluIExhenlXcmFwcGVyLnByb3RvdHlwZSkpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGZ1bmMgPT09IG90aGVyKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGRhdGEgPSBnZXREYXRhKG90aGVyKTsKICAgICAgICAgIHJldHVybiAhIWRhdGEgJiYgZnVuYyA9PT0gZGF0YVswXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgZnVuY2AgaGFzIGl0cyBzb3VyY2UgbWFza2VkLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYGZ1bmNgIGlzIG1hc2tlZCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTWFza2VkKGZ1bmMpIHsKICAgICAgICAgIHJldHVybiAhIW1hc2tTcmNLZXkgJiYgKG1hc2tTcmNLZXkgaW4gZnVuYyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYGZ1bmNgIGlzIGNhcGFibGUgb2YgYmVpbmcgbWFza2VkLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYGZ1bmNgIGlzIG1hc2thYmxlLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICovCiAgICAgICAgdmFyIGlzTWFza2FibGUgPSBjb3JlSnNEYXRhID8gaXNGdW5jdGlvbiA6IHN0dWJGYWxzZTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgbGlrZWx5IGEgcHJvdG90eXBlIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBwcm90b3R5cGUsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc1Byb3RvdHlwZSh2YWx1ZSkgewogICAgICAgICAgdmFyIEN0b3IgPSB2YWx1ZSAmJiB2YWx1ZS5jb25zdHJ1Y3RvciwKICAgICAgICAgICAgICBwcm90byA9ICh0eXBlb2YgQ3RvciA9PSAnZnVuY3Rpb24nICYmIEN0b3IucHJvdG90eXBlKSB8fCBvYmplY3RQcm90bzsKCiAgICAgICAgICByZXR1cm4gdmFsdWUgPT09IHByb3RvOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgc3VpdGFibGUgZm9yIHN0cmljdCBlcXVhbGl0eSBjb21wYXJpc29ucywgaS5lLiBgPT09YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaWYgc3VpdGFibGUgZm9yIHN0cmljdAogICAgICAgICAqICBlcXVhbGl0eSBjb21wYXJpc29ucywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzU3RyaWN0Q29tcGFyYWJsZSh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIHZhbHVlID09PSB2YWx1ZSAmJiAhaXNPYmplY3QodmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBtYXRjaGVzUHJvcGVydHlgIGZvciBzb3VyY2UgdmFsdWVzIHN1aXRhYmxlCiAgICAgICAgICogZm9yIHN0cmljdCBlcXVhbGl0eSBjb21wYXJpc29ucywgaS5lLiBgPT09YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAgICogQHBhcmFtIHsqfSBzcmNWYWx1ZSBUaGUgdmFsdWUgdG8gbWF0Y2guCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXRjaGVzU3RyaWN0Q29tcGFyYWJsZShrZXksIHNyY1ZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgICAgIGlmIChvYmplY3QgPT0gbnVsbCkgewogICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gb2JqZWN0W2tleV0gPT09IHNyY1ZhbHVlICYmCiAgICAgICAgICAgICAgKHNyY1ZhbHVlICE9PSB1bmRlZmluZWQkMSB8fCAoa2V5IGluIE9iamVjdChvYmplY3QpKSk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLm1lbW9pemVgIHdoaWNoIGNsZWFycyB0aGUgbWVtb2l6ZWQgZnVuY3Rpb24ncwogICAgICAgICAqIGNhY2hlIHdoZW4gaXQgZXhjZWVkcyBgTUFYX01FTU9JWkVfU0laRWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGhhdmUgaXRzIG91dHB1dCBtZW1vaXplZC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBtZW1vaXplZCBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtZW1vaXplQ2FwcGVkKGZ1bmMpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBtZW1vaXplKGZ1bmMsIGZ1bmN0aW9uKGtleSkgewogICAgICAgICAgICBpZiAoY2FjaGUuc2l6ZSA9PT0gTUFYX01FTU9JWkVfU0laRSkgewogICAgICAgICAgICAgIGNhY2hlLmNsZWFyKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGtleTsKICAgICAgICAgIH0pOwoKICAgICAgICAgIHZhciBjYWNoZSA9IHJlc3VsdC5jYWNoZTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBNZXJnZXMgdGhlIGZ1bmN0aW9uIG1ldGFkYXRhIG9mIGBzb3VyY2VgIGludG8gYGRhdGFgLgogICAgICAgICAqCiAgICAgICAgICogTWVyZ2luZyBtZXRhZGF0YSByZWR1Y2VzIHRoZSBudW1iZXIgb2Ygd3JhcHBlcnMgdXNlZCB0byBpbnZva2UgYSBmdW5jdGlvbi4KICAgICAgICAgKiBUaGlzIGlzIHBvc3NpYmxlIGJlY2F1c2UgbWV0aG9kcyBsaWtlIGBfLmJpbmRgLCBgXy5jdXJyeWAsIGFuZCBgXy5wYXJ0aWFsYAogICAgICAgICAqIG1heSBiZSBhcHBsaWVkIHJlZ2FyZGxlc3Mgb2YgZXhlY3V0aW9uIG9yZGVyLiBNZXRob2RzIGxpa2UgYF8uYXJ5YCBhbmQKICAgICAgICAgKiBgXy5yZWFyZ2AgbW9kaWZ5IGZ1bmN0aW9uIGFyZ3VtZW50cywgbWFraW5nIHRoZSBvcmRlciBpbiB3aGljaCB0aGV5IGFyZQogICAgICAgICAqIGV4ZWN1dGVkIGltcG9ydGFudCwgcHJldmVudGluZyB0aGUgbWVyZ2luZyBvZiBtZXRhZGF0YS4gSG93ZXZlciwgd2UgbWFrZQogICAgICAgICAqIGFuIGV4Y2VwdGlvbiBmb3IgYSBzYWZlIGNvbWJpbmVkIGNhc2Ugd2hlcmUgY3VycmllZCBmdW5jdGlvbnMgaGF2ZSBgXy5hcnlgCiAgICAgICAgICogYW5kIG9yIGBfLnJlYXJnYCBhcHBsaWVkLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBkYXRhIFRoZSBkZXN0aW5hdGlvbiBtZXRhZGF0YS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBzb3VyY2UgVGhlIHNvdXJjZSBtZXRhZGF0YS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGRhdGFgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1lcmdlRGF0YShkYXRhLCBzb3VyY2UpIHsKICAgICAgICAgIHZhciBiaXRtYXNrID0gZGF0YVsxXSwKICAgICAgICAgICAgICBzcmNCaXRtYXNrID0gc291cmNlWzFdLAogICAgICAgICAgICAgIG5ld0JpdG1hc2sgPSBiaXRtYXNrIHwgc3JjQml0bWFzaywKICAgICAgICAgICAgICBpc0NvbW1vbiA9IG5ld0JpdG1hc2sgPCAoV1JBUF9CSU5EX0ZMQUcgfCBXUkFQX0JJTkRfS0VZX0ZMQUcgfCBXUkFQX0FSWV9GTEFHKTsKCiAgICAgICAgICB2YXIgaXNDb21ibyA9CiAgICAgICAgICAgICgoc3JjQml0bWFzayA9PSBXUkFQX0FSWV9GTEFHKSAmJiAoYml0bWFzayA9PSBXUkFQX0NVUlJZX0ZMQUcpKSB8fAogICAgICAgICAgICAoKHNyY0JpdG1hc2sgPT0gV1JBUF9BUllfRkxBRykgJiYgKGJpdG1hc2sgPT0gV1JBUF9SRUFSR19GTEFHKSAmJiAoZGF0YVs3XS5sZW5ndGggPD0gc291cmNlWzhdKSkgfHwKICAgICAgICAgICAgKChzcmNCaXRtYXNrID09IChXUkFQX0FSWV9GTEFHIHwgV1JBUF9SRUFSR19GTEFHKSkgJiYgKHNvdXJjZVs3XS5sZW5ndGggPD0gc291cmNlWzhdKSAmJiAoYml0bWFzayA9PSBXUkFQX0NVUlJZX0ZMQUcpKTsKCiAgICAgICAgICAvLyBFeGl0IGVhcmx5IGlmIG1ldGFkYXRhIGNhbid0IGJlIG1lcmdlZC4KICAgICAgICAgIGlmICghKGlzQ29tbW9uIHx8IGlzQ29tYm8pKSB7CiAgICAgICAgICAgIHJldHVybiBkYXRhOwogICAgICAgICAgfQogICAgICAgICAgLy8gVXNlIHNvdXJjZSBgdGhpc0FyZ2AgaWYgYXZhaWxhYmxlLgogICAgICAgICAgaWYgKHNyY0JpdG1hc2sgJiBXUkFQX0JJTkRfRkxBRykgewogICAgICAgICAgICBkYXRhWzJdID0gc291cmNlWzJdOwogICAgICAgICAgICAvLyBTZXQgd2hlbiBjdXJyeWluZyBhIGJvdW5kIGZ1bmN0aW9uLgogICAgICAgICAgICBuZXdCaXRtYXNrIHw9IGJpdG1hc2sgJiBXUkFQX0JJTkRfRkxBRyA/IDAgOiBXUkFQX0NVUlJZX0JPVU5EX0ZMQUc7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDb21wb3NlIHBhcnRpYWwgYXJndW1lbnRzLgogICAgICAgICAgdmFyIHZhbHVlID0gc291cmNlWzNdOwogICAgICAgICAgaWYgKHZhbHVlKSB7CiAgICAgICAgICAgIHZhciBwYXJ0aWFscyA9IGRhdGFbM107CiAgICAgICAgICAgIGRhdGFbM10gPSBwYXJ0aWFscyA/IGNvbXBvc2VBcmdzKHBhcnRpYWxzLCB2YWx1ZSwgc291cmNlWzRdKSA6IHZhbHVlOwogICAgICAgICAgICBkYXRhWzRdID0gcGFydGlhbHMgPyByZXBsYWNlSG9sZGVycyhkYXRhWzNdLCBQTEFDRUhPTERFUikgOiBzb3VyY2VbNF07CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDb21wb3NlIHBhcnRpYWwgcmlnaHQgYXJndW1lbnRzLgogICAgICAgICAgdmFsdWUgPSBzb3VyY2VbNV07CiAgICAgICAgICBpZiAodmFsdWUpIHsKICAgICAgICAgICAgcGFydGlhbHMgPSBkYXRhWzVdOwogICAgICAgICAgICBkYXRhWzVdID0gcGFydGlhbHMgPyBjb21wb3NlQXJnc1JpZ2h0KHBhcnRpYWxzLCB2YWx1ZSwgc291cmNlWzZdKSA6IHZhbHVlOwogICAgICAgICAgICBkYXRhWzZdID0gcGFydGlhbHMgPyByZXBsYWNlSG9sZGVycyhkYXRhWzVdLCBQTEFDRUhPTERFUikgOiBzb3VyY2VbNl07CiAgICAgICAgICB9CiAgICAgICAgICAvLyBVc2Ugc291cmNlIGBhcmdQb3NgIGlmIGF2YWlsYWJsZS4KICAgICAgICAgIHZhbHVlID0gc291cmNlWzddOwogICAgICAgICAgaWYgKHZhbHVlKSB7CiAgICAgICAgICAgIGRhdGFbN10gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIFVzZSBzb3VyY2UgYGFyeWAgaWYgaXQncyBzbWFsbGVyLgogICAgICAgICAgaWYgKHNyY0JpdG1hc2sgJiBXUkFQX0FSWV9GTEFHKSB7CiAgICAgICAgICAgIGRhdGFbOF0gPSBkYXRhWzhdID09IG51bGwgPyBzb3VyY2VbOF0gOiBuYXRpdmVNaW4oZGF0YVs4XSwgc291cmNlWzhdKTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIFVzZSBzb3VyY2UgYGFyaXR5YCBpZiBvbmUgaXMgbm90IHByb3ZpZGVkLgogICAgICAgICAgaWYgKGRhdGFbOV0gPT0gbnVsbCkgewogICAgICAgICAgICBkYXRhWzldID0gc291cmNlWzldOwogICAgICAgICAgfQogICAgICAgICAgLy8gVXNlIHNvdXJjZSBgZnVuY2AgYW5kIG1lcmdlIGJpdG1hc2tzLgogICAgICAgICAgZGF0YVswXSA9IHNvdXJjZVswXTsKICAgICAgICAgIGRhdGFbMV0gPSBuZXdCaXRtYXNrOwoKICAgICAgICAgIHJldHVybiBkYXRhOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBmdW5jdGlvbiBpcyBsaWtlCiAgICAgICAgICogW2BPYmplY3Qua2V5c2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLW9iamVjdC5rZXlzKQogICAgICAgICAqIGV4Y2VwdCB0aGF0IGl0IGluY2x1ZGVzIGluaGVyaXRlZCBlbnVtZXJhYmxlIHByb3BlcnRpZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG5hdGl2ZUtleXNJbihvYmplY3QpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBbXTsKICAgICAgICAgIGlmIChvYmplY3QgIT0gbnVsbCkgewogICAgICAgICAgICBmb3IgKHZhciBrZXkgaW4gT2JqZWN0KG9iamVjdCkpIHsKICAgICAgICAgICAgICByZXN1bHQucHVzaChrZXkpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHZhbHVlYCB0byBhIHN0cmluZyB1c2luZyBgT2JqZWN0LnByb3RvdHlwZS50b1N0cmluZ2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgY29udmVydGVkIHN0cmluZy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBvYmplY3RUb1N0cmluZyh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIG5hdGl2ZU9iamVjdFRvU3RyaW5nLmNhbGwodmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlUmVzdGAgd2hpY2ggdHJhbnNmb3JtcyB0aGUgcmVzdCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gYXBwbHkgYSByZXN0IHBhcmFtZXRlciB0by4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PWZ1bmMubGVuZ3RoLTFdIFRoZSBzdGFydCBwb3NpdGlvbiBvZiB0aGUgcmVzdCBwYXJhbWV0ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gdHJhbnNmb3JtIFRoZSByZXN0IGFycmF5IHRyYW5zZm9ybS4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBvdmVyUmVzdChmdW5jLCBzdGFydCwgdHJhbnNmb3JtKSB7CiAgICAgICAgICBzdGFydCA9IG5hdGl2ZU1heChzdGFydCA9PT0gdW5kZWZpbmVkJDEgPyAoZnVuYy5sZW5ndGggLSAxKSA6IHN0YXJ0LCAwKTsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHMsCiAgICAgICAgICAgICAgICBpbmRleCA9IC0xLAogICAgICAgICAgICAgICAgbGVuZ3RoID0gbmF0aXZlTWF4KGFyZ3MubGVuZ3RoIC0gc3RhcnQsIDApLAogICAgICAgICAgICAgICAgYXJyYXkgPSBBcnJheShsZW5ndGgpOwoKICAgICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgICBhcnJheVtpbmRleF0gPSBhcmdzW3N0YXJ0ICsgaW5kZXhdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGluZGV4ID0gLTE7CiAgICAgICAgICAgIHZhciBvdGhlckFyZ3MgPSBBcnJheShzdGFydCArIDEpOwogICAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IHN0YXJ0KSB7CiAgICAgICAgICAgICAgb3RoZXJBcmdzW2luZGV4XSA9IGFyZ3NbaW5kZXhdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG90aGVyQXJnc1tzdGFydF0gPSB0cmFuc2Zvcm0oYXJyYXkpOwogICAgICAgICAgICByZXR1cm4gYXBwbHkoZnVuYywgdGhpcywgb3RoZXJBcmdzKTsKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBwYXJlbnQgdmFsdWUgYXQgYHBhdGhgIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gcGF0aCBUaGUgcGF0aCB0byBnZXQgdGhlIHBhcmVudCB2YWx1ZSBvZi4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgcGFyZW50IHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHBhcmVudChvYmplY3QsIHBhdGgpIHsKICAgICAgICAgIHJldHVybiBwYXRoLmxlbmd0aCA8IDIgPyBvYmplY3QgOiBiYXNlR2V0KG9iamVjdCwgYmFzZVNsaWNlKHBhdGgsIDAsIC0xKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW9yZGVyIGBhcnJheWAgYWNjb3JkaW5nIHRvIHRoZSBzcGVjaWZpZWQgaW5kZXhlcyB3aGVyZSB0aGUgZWxlbWVudCBhdAogICAgICAgICAqIHRoZSBmaXJzdCBpbmRleCBpcyBhc3NpZ25lZCBhcyB0aGUgZmlyc3QgZWxlbWVudCwgdGhlIGVsZW1lbnQgYXQKICAgICAgICAgKiB0aGUgc2Vjb25kIGluZGV4IGlzIGFzc2lnbmVkIGFzIHRoZSBzZWNvbmQgZWxlbWVudCwgYW5kIHNvIG9uLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gcmVvcmRlci4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBpbmRleGVzIFRoZSBhcnJhbmdlZCBhcnJheSBpbmRleGVzLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHJlb3JkZXIoYXJyYXksIGluZGV4ZXMpIHsKICAgICAgICAgIHZhciBhcnJMZW5ndGggPSBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgICAgbGVuZ3RoID0gbmF0aXZlTWluKGluZGV4ZXMubGVuZ3RoLCBhcnJMZW5ndGgpLAogICAgICAgICAgICAgIG9sZEFycmF5ID0gY29weUFycmF5KGFycmF5KTsKCiAgICAgICAgICB3aGlsZSAobGVuZ3RoLS0pIHsKICAgICAgICAgICAgdmFyIGluZGV4ID0gaW5kZXhlc1tsZW5ndGhdOwogICAgICAgICAgICBhcnJheVtsZW5ndGhdID0gaXNJbmRleChpbmRleCwgYXJyTGVuZ3RoKSA/IG9sZEFycmF5W2luZGV4XSA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGFycmF5OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgdmFsdWUgYXQgYGtleWAsIHVubGVzcyBga2V5YCBpcyAiX19wcm90b19fIiBvciAiY29uc3RydWN0b3IiLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHByb3BlcnR5IHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNhZmVHZXQob2JqZWN0LCBrZXkpIHsKICAgICAgICAgIGlmIChrZXkgPT09ICdjb25zdHJ1Y3RvcicgJiYgdHlwZW9mIG9iamVjdFtrZXldID09PSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAoa2V5ID09ICdfX3Byb3RvX18nKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICByZXR1cm4gb2JqZWN0W2tleV07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIG1ldGFkYXRhIGZvciBgZnVuY2AuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogSWYgdGhpcyBmdW5jdGlvbiBiZWNvbWVzIGhvdCwgaS5lLiBpcyBpbnZva2VkIGEgbG90IGluIGEgc2hvcnQKICAgICAgICAgKiBwZXJpb2Qgb2YgdGltZSwgaXQgd2lsbCB0cmlwIGl0cyBicmVha2VyIGFuZCB0cmFuc2l0aW9uIHRvIGFuIGlkZW50aXR5CiAgICAgICAgICogZnVuY3Rpb24gdG8gYXZvaWQgZ2FyYmFnZSBjb2xsZWN0aW9uIHBhdXNlcyBpbiBWOC4gU2VlCiAgICAgICAgICogW1Y4IGlzc3VlIDIwNzBdKGh0dHBzOi8vYnVncy5jaHJvbWl1bS5vcmcvcC92OC9pc3N1ZXMvZGV0YWlsP2lkPTIwNzApCiAgICAgICAgICogZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gYXNzb2NpYXRlIG1ldGFkYXRhIHdpdGguCiAgICAgICAgICogQHBhcmFtIHsqfSBkYXRhIFRoZSBtZXRhZGF0YS4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgYGZ1bmNgLgogICAgICAgICAqLwogICAgICAgIHZhciBzZXREYXRhID0gc2hvcnRPdXQoYmFzZVNldERhdGEpOwoKICAgICAgICAvKioKICAgICAgICAgKiBBIHNpbXBsZSB3cmFwcGVyIGFyb3VuZCB0aGUgZ2xvYmFsIFtgc2V0VGltZW91dGBdKGh0dHBzOi8vbWRuLmlvL3NldFRpbWVvdXQpLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBkZWxheS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gd2FpdCBUaGUgbnVtYmVyIG9mIG1pbGxpc2Vjb25kcyB0byBkZWxheSBpbnZvY2F0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ8T2JqZWN0fSBSZXR1cm5zIHRoZSB0aW1lciBpZCBvciB0aW1lb3V0IG9iamVjdC4KICAgICAgICAgKi8KICAgICAgICB2YXIgc2V0VGltZW91dCA9IGN0eFNldFRpbWVvdXQgfHwgZnVuY3Rpb24oZnVuYywgd2FpdCkgewogICAgICAgICAgcmV0dXJuIHJvb3Quc2V0VGltZW91dChmdW5jLCB3YWl0KTsKICAgICAgICB9OwoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBgdG9TdHJpbmdgIG1ldGhvZCBvZiBgZnVuY2AgdG8gcmV0dXJuIGBzdHJpbmdgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gc3RyaW5nIFRoZSBgdG9TdHJpbmdgIHJlc3VsdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgYGZ1bmNgLgogICAgICAgICAqLwogICAgICAgIHZhciBzZXRUb1N0cmluZyA9IHNob3J0T3V0KGJhc2VTZXRUb1N0cmluZyk7CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIGB0b1N0cmluZ2AgbWV0aG9kIG9mIGB3cmFwcGVyYCB0byBtaW1pYyB0aGUgc291cmNlIG9mIGByZWZlcmVuY2VgCiAgICAgICAgICogd2l0aCB3cmFwcGVyIGRldGFpbHMgaW4gYSBjb21tZW50IGF0IHRoZSB0b3Agb2YgdGhlIHNvdXJjZSBib2R5LgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSB3cmFwcGVyIFRoZSBmdW5jdGlvbiB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcmVmZXJlbmNlIFRoZSByZWZlcmVuY2UgZnVuY3Rpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgY3JlYXRlV3JhcGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgYHdyYXBwZXJgLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNldFdyYXBUb1N0cmluZyh3cmFwcGVyLCByZWZlcmVuY2UsIGJpdG1hc2spIHsKICAgICAgICAgIHZhciBzb3VyY2UgPSAocmVmZXJlbmNlICsgJycpOwogICAgICAgICAgcmV0dXJuIHNldFRvU3RyaW5nKHdyYXBwZXIsIGluc2VydFdyYXBEZXRhaWxzKHNvdXJjZSwgdXBkYXRlV3JhcERldGFpbHMoZ2V0V3JhcERldGFpbHMoc291cmNlKSwgYml0bWFzaykpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0J2xsIHNob3J0IG91dCBhbmQgaW52b2tlIGBpZGVudGl0eWAgaW5zdGVhZAogICAgICAgICAqIG9mIGBmdW5jYCB3aGVuIGl0J3MgY2FsbGVkIGBIT1RfQ09VTlRgIG9yIG1vcmUgdGltZXMgaW4gYEhPVF9TUEFOYAogICAgICAgICAqIG1pbGxpc2Vjb25kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gcmVzdHJpY3QuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc2hvcnRhYmxlIGZ1bmN0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNob3J0T3V0KGZ1bmMpIHsKICAgICAgICAgIHZhciBjb3VudCA9IDAsCiAgICAgICAgICAgICAgbGFzdENhbGxlZCA9IDA7CgogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgICB2YXIgc3RhbXAgPSBuYXRpdmVOb3coKSwKICAgICAgICAgICAgICAgIHJlbWFpbmluZyA9IEhPVF9TUEFOIC0gKHN0YW1wIC0gbGFzdENhbGxlZCk7CgogICAgICAgICAgICBsYXN0Q2FsbGVkID0gc3RhbXA7CiAgICAgICAgICAgIGlmIChyZW1haW5pbmcgPiAwKSB7CiAgICAgICAgICAgICAgaWYgKCsrY291bnQgPj0gSE9UX0NPVU5UKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gYXJndW1lbnRzWzBdOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBjb3VudCA9IDA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZ1bmMuYXBwbHkodW5kZWZpbmVkJDEsIGFyZ3VtZW50cyk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLnNodWZmbGVgIHdoaWNoIG11dGF0ZXMgYW5kIHNldHMgdGhlIHNpemUgb2YgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHNodWZmbGUuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzaXplPWFycmF5Lmxlbmd0aF0gVGhlIHNpemUgb2YgYGFycmF5YC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzaHVmZmxlU2VsZihhcnJheSwgc2l6ZSkgewogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIGxhc3RJbmRleCA9IGxlbmd0aCAtIDE7CgogICAgICAgICAgc2l6ZSA9IHNpemUgPT09IHVuZGVmaW5lZCQxID8gbGVuZ3RoIDogc2l6ZTsKICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgc2l6ZSkgewogICAgICAgICAgICB2YXIgcmFuZCA9IGJhc2VSYW5kb20oaW5kZXgsIGxhc3RJbmRleCksCiAgICAgICAgICAgICAgICB2YWx1ZSA9IGFycmF5W3JhbmRdOwoKICAgICAgICAgICAgYXJyYXlbcmFuZF0gPSBhcnJheVtpbmRleF07CiAgICAgICAgICAgIGFycmF5W2luZGV4XSA9IHZhbHVlOwogICAgICAgICAgfQogICAgICAgICAgYXJyYXkubGVuZ3RoID0gc2l6ZTsKICAgICAgICAgIHJldHVybiBhcnJheTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGBzdHJpbmdgIHRvIGEgcHJvcGVydHkgcGF0aCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBwcm9wZXJ0eSBwYXRoIGFycmF5LgogICAgICAgICAqLwogICAgICAgIHZhciBzdHJpbmdUb1BhdGggPSBtZW1vaXplQ2FwcGVkKGZ1bmN0aW9uKHN0cmluZykgewogICAgICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICAgICAgaWYgKHN0cmluZy5jaGFyQ29kZUF0KDApID09PSA0NiAvKiAuICovKSB7CiAgICAgICAgICAgIHJlc3VsdC5wdXNoKCcnKTsKICAgICAgICAgIH0KICAgICAgICAgIHN0cmluZy5yZXBsYWNlKHJlUHJvcE5hbWUsIGZ1bmN0aW9uKG1hdGNoLCBudW1iZXIsIHF1b3RlLCBzdWJTdHJpbmcpIHsKICAgICAgICAgICAgcmVzdWx0LnB1c2gocXVvdGUgPyBzdWJTdHJpbmcucmVwbGFjZShyZUVzY2FwZUNoYXIsICckMScpIDogKG51bWJlciB8fCBtYXRjaCkpOwogICAgICAgICAgfSk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGEgc3RyaW5nIGtleSBpZiBpdCdzIG5vdCBhIHN0cmluZyBvciBzeW1ib2wuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGluc3BlY3QuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ3xzeW1ib2x9IFJldHVybnMgdGhlIGtleS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0b0tleSh2YWx1ZSkgewogICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJyB8fCBpc1N5bWJvbCh2YWx1ZSkpIHsKICAgICAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHJlc3VsdCA9ICh2YWx1ZSArICcnKTsKICAgICAgICAgIHJldHVybiAocmVzdWx0ID09ICcwJyAmJiAoMSAvIHZhbHVlKSA9PSAtSU5GSU5JVFkpID8gJy0wJyA6IHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGBmdW5jYCB0byBpdHMgc291cmNlIGNvZGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgc291cmNlIGNvZGUuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdG9Tb3VyY2UoZnVuYykgewogICAgICAgICAgaWYgKGZ1bmMgIT0gbnVsbCkgewogICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgIHJldHVybiBmdW5jVG9TdHJpbmcuY2FsbChmdW5jKTsKICAgICAgICAgICAgfSBjYXRjaCAoZSkge30KICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICByZXR1cm4gKGZ1bmMgKyAnJyk7CiAgICAgICAgICAgIH0gY2F0Y2ggKGUpIHt9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBVcGRhdGVzIHdyYXBwZXIgYGRldGFpbHNgIGJhc2VkIG9uIGBiaXRtYXNrYCBmbGFncy4KICAgICAgICAgKgogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBkZXRhaWxzIFRoZSBkZXRhaWxzIHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4gU2VlIGBjcmVhdGVXcmFwYCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgZGV0YWlsc2AuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdXBkYXRlV3JhcERldGFpbHMoZGV0YWlscywgYml0bWFzaykgewogICAgICAgICAgYXJyYXlFYWNoKHdyYXBGbGFncywgZnVuY3Rpb24ocGFpcikgewogICAgICAgICAgICB2YXIgdmFsdWUgPSAnXy4nICsgcGFpclswXTsKICAgICAgICAgICAgaWYgKChiaXRtYXNrICYgcGFpclsxXSkgJiYgIWFycmF5SW5jbHVkZXMoZGV0YWlscywgdmFsdWUpKSB7CiAgICAgICAgICAgICAgZGV0YWlscy5wdXNoKHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgICByZXR1cm4gZGV0YWlscy5zb3J0KCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgYHdyYXBwZXJgLgogICAgICAgICAqCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gd3JhcHBlciBUaGUgd3JhcHBlciB0byBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgd3JhcHBlci4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB3cmFwcGVyQ2xvbmUod3JhcHBlcikgewogICAgICAgICAgaWYgKHdyYXBwZXIgaW5zdGFuY2VvZiBMYXp5V3JhcHBlcikgewogICAgICAgICAgICByZXR1cm4gd3JhcHBlci5jbG9uZSgpOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHJlc3VsdCA9IG5ldyBMb2Rhc2hXcmFwcGVyKHdyYXBwZXIuX193cmFwcGVkX18sIHdyYXBwZXIuX19jaGFpbl9fKTsKICAgICAgICAgIHJlc3VsdC5fX2FjdGlvbnNfXyA9IGNvcHlBcnJheSh3cmFwcGVyLl9fYWN0aW9uc19fKTsKICAgICAgICAgIHJlc3VsdC5fX2luZGV4X18gID0gd3JhcHBlci5fX2luZGV4X187CiAgICAgICAgICByZXN1bHQuX192YWx1ZXNfXyA9IHdyYXBwZXIuX192YWx1ZXNfXzsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgZWxlbWVudHMgc3BsaXQgaW50byBncm91cHMgdGhlIGxlbmd0aCBvZiBgc2l6ZWAuCiAgICAgICAgICogSWYgYGFycmF5YCBjYW4ndCBiZSBzcGxpdCBldmVubHksIHRoZSBmaW5hbCBjaHVuayB3aWxsIGJlIHRoZSByZW1haW5pbmcKICAgICAgICAgKiBlbGVtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBwcm9jZXNzLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbc2l6ZT0xXSBUaGUgbGVuZ3RoIG9mIGVhY2ggY2h1bmsKICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5tYXBgLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIGNodW5rcy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5jaHVuayhbJ2EnLCAnYicsICdjJywgJ2QnXSwgMik7CiAgICAgICAgICogLy8gPT4gW1snYScsICdiJ10sIFsnYycsICdkJ11dCiAgICAgICAgICoKICAgICAgICAgKiBfLmNodW5rKFsnYScsICdiJywgJ2MnLCAnZCddLCAzKTsKICAgICAgICAgKiAvLyA9PiBbWydhJywgJ2InLCAnYyddLCBbJ2QnXV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjaHVuayhhcnJheSwgc2l6ZSwgZ3VhcmQpIHsKICAgICAgICAgIGlmICgoZ3VhcmQgPyBpc0l0ZXJhdGVlQ2FsbChhcnJheSwgc2l6ZSwgZ3VhcmQpIDogc2l6ZSA9PT0gdW5kZWZpbmVkJDEpKSB7CiAgICAgICAgICAgIHNpemUgPSAxOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc2l6ZSA9IG5hdGl2ZU1heCh0b0ludGVnZXIoc2l6ZSksIDApOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKCFsZW5ndGggfHwgc2l6ZSA8IDEpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGluZGV4ID0gMCwKICAgICAgICAgICAgICByZXNJbmRleCA9IDAsCiAgICAgICAgICAgICAgcmVzdWx0ID0gQXJyYXkobmF0aXZlQ2VpbChsZW5ndGggLyBzaXplKSk7CgogICAgICAgICAgd2hpbGUgKGluZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIHJlc3VsdFtyZXNJbmRleCsrXSA9IGJhc2VTbGljZShhcnJheSwgaW5kZXgsIChpbmRleCArPSBzaXplKSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSB3aXRoIGFsbCBmYWxzZXkgdmFsdWVzIHJlbW92ZWQuIFRoZSB2YWx1ZXMgYGZhbHNlYCwgYG51bGxgLAogICAgICAgICAqIGAwYCwgYCIiYCwgYHVuZGVmaW5lZGAsIGFuZCBgTmFOYCBhcmUgZmFsc2V5LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGNvbXBhY3QuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgZmlsdGVyZWQgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmNvbXBhY3QoWzAsIDEsIGZhbHNlLCAyLCAnJywgM10pOwogICAgICAgICAqIC8vID0+IFsxLCAyLCAzXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNvbXBhY3QoYXJyYXkpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoLAogICAgICAgICAgICAgIHJlc0luZGV4ID0gMCwKICAgICAgICAgICAgICByZXN1bHQgPSBbXTsKCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF07CiAgICAgICAgICAgIGlmICh2YWx1ZSkgewogICAgICAgICAgICAgIHJlc3VsdFtyZXNJbmRleCsrXSA9IHZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIG5ldyBhcnJheSBjb25jYXRlbmF0aW5nIGBhcnJheWAgd2l0aCBhbnkgYWRkaXRpb25hbCBhcnJheXMKICAgICAgICAgKiBhbmQvb3IgdmFsdWVzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGNvbmNhdGVuYXRlLgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gW3ZhbHVlc10gVGhlIHZhbHVlcyB0byBjb25jYXRlbmF0ZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBjb25jYXRlbmF0ZWQgYXJyYXkuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IFsxXTsKICAgICAgICAgKiB2YXIgb3RoZXIgPSBfLmNvbmNhdChhcnJheSwgMiwgWzNdLCBbWzRdXSk7CiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhvdGhlcik7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDMsIFs0XV0KICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5KTsKICAgICAgICAgKiAvLyA9PiBbMV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb25jYXQoKSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJndW1lbnRzLmxlbmd0aDsKICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBhcmdzID0gQXJyYXkobGVuZ3RoIC0gMSksCiAgICAgICAgICAgICAgYXJyYXkgPSBhcmd1bWVudHNbMF0sCiAgICAgICAgICAgICAgaW5kZXggPSBsZW5ndGg7CgogICAgICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICAgICAgYXJnc1tpbmRleCAtIDFdID0gYXJndW1lbnRzW2luZGV4XTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBhcnJheVB1c2goaXNBcnJheShhcnJheSkgPyBjb3B5QXJyYXkoYXJyYXkpIDogW2FycmF5XSwgYmFzZUZsYXR0ZW4oYXJncywgMSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBgYXJyYXlgIHZhbHVlcyBub3QgaW5jbHVkZWQgaW4gdGhlIG90aGVyIGdpdmVuIGFycmF5cwogICAgICAgICAqIHVzaW5nIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLiBUaGUgb3JkZXIgYW5kIHJlZmVyZW5jZXMgb2YgcmVzdWx0IHZhbHVlcyBhcmUKICAgICAgICAgKiBkZXRlcm1pbmVkIGJ5IHRoZSBmaXJzdCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBVbmxpa2UgYF8ucHVsbEFsbGAsIHRoaXMgbWV0aG9kIHJldHVybnMgYSBuZXcgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbdmFsdWVzXSBUaGUgdmFsdWVzIHRvIGV4Y2x1ZGUuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgZmlsdGVyZWQgdmFsdWVzLgogICAgICAgICAqIEBzZWUgXy53aXRob3V0LCBfLnhvcgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRpZmZlcmVuY2UoWzIsIDFdLCBbMiwgM10pOwogICAgICAgICAqIC8vID0+IFsxXQogICAgICAgICAqLwogICAgICAgIHZhciBkaWZmZXJlbmNlID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXksIHZhbHVlcykgewogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlT2JqZWN0KGFycmF5KQogICAgICAgICAgICA/IGJhc2VEaWZmZXJlbmNlKGFycmF5LCBiYXNlRmxhdHRlbih2YWx1ZXMsIDEsIGlzQXJyYXlMaWtlT2JqZWN0LCB0cnVlKSkKICAgICAgICAgICAgOiBbXTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5kaWZmZXJlbmNlYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAgd2hpY2gKICAgICAgICAgKiBpcyBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgb2YgYGFycmF5YCBhbmQgYHZhbHVlc2AgdG8gZ2VuZXJhdGUgdGhlIGNyaXRlcmlvbgogICAgICAgICAqIGJ5IHdoaWNoIHRoZXkncmUgY29tcGFyZWQuIFRoZSBvcmRlciBhbmQgcmVmZXJlbmNlcyBvZiByZXN1bHQgdmFsdWVzIGFyZQogICAgICAgICAqIGRldGVybWluZWQgYnkgdGhlIGZpcnN0IGFycmF5LiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDoKICAgICAgICAgKiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy5wdWxsQWxsQnlgLCB0aGlzIG1ldGhvZCByZXR1cm5zIGEgbmV3IGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi5BcnJheX0gW3ZhbHVlc10gVGhlIHZhbHVlcyB0byBleGNsdWRlLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBmaWx0ZXJlZCB2YWx1ZXMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZGlmZmVyZW5jZUJ5KFsyLjEsIDEuMl0sIFsyLjMsIDMuNF0sIE1hdGguZmxvb3IpOwogICAgICAgICAqIC8vID0+IFsxLjJdCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmRpZmZlcmVuY2VCeShbeyAneCc6IDIgfSwgeyAneCc6IDEgfV0sIFt7ICd4JzogMSB9XSwgJ3gnKTsKICAgICAgICAgKiAvLyA9PiBbeyAneCc6IDIgfV0KICAgICAgICAgKi8KICAgICAgICB2YXIgZGlmZmVyZW5jZUJ5ID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXksIHZhbHVlcykgewogICAgICAgICAgdmFyIGl0ZXJhdGVlID0gbGFzdCh2YWx1ZXMpOwogICAgICAgICAgaWYgKGlzQXJyYXlMaWtlT2JqZWN0KGl0ZXJhdGVlKSkgewogICAgICAgICAgICBpdGVyYXRlZSA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlT2JqZWN0KGFycmF5KQogICAgICAgICAgICA/IGJhc2VEaWZmZXJlbmNlKGFycmF5LCBiYXNlRmxhdHRlbih2YWx1ZXMsIDEsIGlzQXJyYXlMaWtlT2JqZWN0LCB0cnVlKSwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpKQogICAgICAgICAgICA6IFtdOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmRpZmZlcmVuY2VgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGNvbXBhcmF0b3JgCiAgICAgICAgICogd2hpY2ggaXMgaW52b2tlZCB0byBjb21wYXJlIGVsZW1lbnRzIG9mIGBhcnJheWAgdG8gYHZhbHVlc2AuIFRoZSBvcmRlciBhbmQKICAgICAgICAgKiByZWZlcmVuY2VzIG9mIHJlc3VsdCB2YWx1ZXMgYXJlIGRldGVybWluZWQgYnkgdGhlIGZpcnN0IGFycmF5LiBUaGUgY29tcGFyYXRvcgogICAgICAgICAqIGlzIGludm9rZWQgd2l0aCB0d28gYXJndW1lbnRzOiAoYXJyVmFsLCBvdGhWYWwpLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy5wdWxsQWxsV2l0aGAsIHRoaXMgbWV0aG9kIHJldHVybnMgYSBuZXcgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbdmFsdWVzXSBUaGUgdmFsdWVzIHRvIGV4Y2x1ZGUuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2NvbXBhcmF0b3JdIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgZmlsdGVyZWQgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IFt7ICd4JzogMSwgJ3knOiAyIH0sIHsgJ3gnOiAyLCAneSc6IDEgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLmRpZmZlcmVuY2VXaXRoKG9iamVjdHMsIFt7ICd4JzogMSwgJ3knOiAyIH1dLCBfLmlzRXF1YWwpOwogICAgICAgICAqIC8vID0+IFt7ICd4JzogMiwgJ3knOiAxIH1dCiAgICAgICAgICovCiAgICAgICAgdmFyIGRpZmZlcmVuY2VXaXRoID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXksIHZhbHVlcykgewogICAgICAgICAgdmFyIGNvbXBhcmF0b3IgPSBsYXN0KHZhbHVlcyk7CiAgICAgICAgICBpZiAoaXNBcnJheUxpa2VPYmplY3QoY29tcGFyYXRvcikpIHsKICAgICAgICAgICAgY29tcGFyYXRvciA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlT2JqZWN0KGFycmF5KQogICAgICAgICAgICA/IGJhc2VEaWZmZXJlbmNlKGFycmF5LCBiYXNlRmxhdHRlbih2YWx1ZXMsIDEsIGlzQXJyYXlMaWtlT2JqZWN0LCB0cnVlKSwgdW5kZWZpbmVkJDEsIGNvbXBhcmF0b3IpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBzbGljZSBvZiBgYXJyYXlgIHdpdGggYG5gIGVsZW1lbnRzIGRyb3BwZWQgZnJvbSB0aGUgYmVnaW5uaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuNS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbj0xXSBUaGUgbnVtYmVyIG9mIGVsZW1lbnRzIHRvIGRyb3AuCiAgICAgICAgICogQHBhcmFtLSB7T2JqZWN0fSBbZ3VhcmRdIEVuYWJsZXMgdXNlIGFzIGFuIGl0ZXJhdGVlIGZvciBtZXRob2RzIGxpa2UgYF8ubWFwYC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHNsaWNlIG9mIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZHJvcChbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IFsyLCAzXQogICAgICAgICAqCiAgICAgICAgICogXy5kcm9wKFsxLCAyLCAzXSwgMik7CiAgICAgICAgICogLy8gPT4gWzNdCiAgICAgICAgICoKICAgICAgICAgKiBfLmRyb3AoWzEsIDIsIDNdLCA1KTsKICAgICAgICAgKiAvLyA9PiBbXQogICAgICAgICAqCiAgICAgICAgICogXy5kcm9wKFsxLCAyLCAzXSwgMCk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZHJvcChhcnJheSwgbiwgZ3VhcmQpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIG4gPSAoZ3VhcmQgfHwgbiA9PT0gdW5kZWZpbmVkJDEpID8gMSA6IHRvSW50ZWdlcihuKTsKICAgICAgICAgIHJldHVybiBiYXNlU2xpY2UoYXJyYXksIG4gPCAwID8gMCA6IG4sIGxlbmd0aCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2xpY2Ugb2YgYGFycmF5YCB3aXRoIGBuYCBlbGVtZW50cyBkcm9wcGVkIGZyb20gdGhlIGVuZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW249MV0gVGhlIG51bWJlciBvZiBlbGVtZW50cyB0byBkcm9wLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBzbGljZSBvZiBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRyb3BSaWdodChbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IFsxLCAyXQogICAgICAgICAqCiAgICAgICAgICogXy5kcm9wUmlnaHQoWzEsIDIsIDNdLCAyKTsKICAgICAgICAgKiAvLyA9PiBbMV0KICAgICAgICAgKgogICAgICAgICAqIF8uZHJvcFJpZ2h0KFsxLCAyLCAzXSwgNSk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKgogICAgICAgICAqIF8uZHJvcFJpZ2h0KFsxLCAyLCAzXSwgMCk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZHJvcFJpZ2h0KGFycmF5LCBuLCBndWFyZCkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgbiA9IChndWFyZCB8fCBuID09PSB1bmRlZmluZWQkMSkgPyAxIDogdG9JbnRlZ2VyKG4pOwogICAgICAgICAgbiA9IGxlbmd0aCAtIG47CiAgICAgICAgICByZXR1cm4gYmFzZVNsaWNlKGFycmF5LCAwLCBuIDwgMCA/IDAgOiBuKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBzbGljZSBvZiBgYXJyYXlgIGV4Y2x1ZGluZyBlbGVtZW50cyBkcm9wcGVkIGZyb20gdGhlIGVuZC4KICAgICAgICAgKiBFbGVtZW50cyBhcmUgZHJvcHBlZCB1bnRpbCBgcHJlZGljYXRlYCByZXR1cm5zIGZhbHNleS4gVGhlIHByZWRpY2F0ZSBpcwogICAgICAgICAqIGludm9rZWQgd2l0aCB0aHJlZSBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXgsIGFycmF5KS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBzbGljZSBvZiBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICAnYWN0aXZlJzogdHJ1ZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWN0aXZlJzogZmFsc2UgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiBfLmRyb3BSaWdodFdoaWxlKHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiAhby5hY3RpdmU7IH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5J10KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzYCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5kcm9wUmlnaHRXaGlsZSh1c2VycywgeyAndXNlcic6ICdwZWJibGVzJywgJ2FjdGl2ZSc6IGZhbHNlIH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5JywgJ2ZyZWQnXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZHJvcFJpZ2h0V2hpbGUodXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ2Jhcm5leSddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmRyb3BSaWdodFdoaWxlKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydiYXJuZXknLCAnZnJlZCcsICdwZWJibGVzJ10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBkcm9wUmlnaHRXaGlsZShhcnJheSwgcHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlV2hpbGUoYXJyYXksIGdldEl0ZXJhdGVlKHByZWRpY2F0ZSwgMyksIHRydWUsIHRydWUpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2xpY2Ugb2YgYGFycmF5YCBleGNsdWRpbmcgZWxlbWVudHMgZHJvcHBlZCBmcm9tIHRoZSBiZWdpbm5pbmcuCiAgICAgICAgICogRWxlbWVudHMgYXJlIGRyb3BwZWQgdW50aWwgYHByZWRpY2F0ZWAgcmV0dXJucyBmYWxzZXkuIFRoZSBwcmVkaWNhdGUgaXMKICAgICAgICAgKiBpbnZva2VkIHdpdGggdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGluZGV4LCBhcnJheSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW3ByZWRpY2F0ZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc2xpY2Ugb2YgYGFycmF5YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gWwogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICAnYWN0aXZlJzogZmFsc2UgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAncGViYmxlcycsICdhY3RpdmUnOiB0cnVlIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogXy5kcm9wV2hpbGUodXNlcnMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuICFvLmFjdGl2ZTsgfSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydwZWJibGVzJ10KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzYCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5kcm9wV2hpbGUodXNlcnMsIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FjdGl2ZSc6IGZhbHNlIH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnZnJlZCcsICdwZWJibGVzJ10KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzUHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmRyb3BXaGlsZSh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsncGViYmxlcyddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmRyb3BXaGlsZSh1c2VycywgJ2FjdGl2ZScpOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5JywgJ2ZyZWQnLCAncGViYmxlcyddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZHJvcFdoaWxlKGFycmF5LCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VXaGlsZShhcnJheSwgZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSwgdHJ1ZSkKICAgICAgICAgICAgOiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEZpbGxzIGVsZW1lbnRzIG9mIGBhcnJheWAgd2l0aCBgdmFsdWVgIGZyb20gYHN0YXJ0YCB1cCB0bywgYnV0IG5vdAogICAgICAgICAqIGluY2x1ZGluZywgYGVuZGAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgYXJyYXlgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMi4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGZpbGwuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gZmlsbCBgYXJyYXlgIHdpdGguCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGFydD0wXSBUaGUgc3RhcnQgcG9zaXRpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtlbmQ9YXJyYXkubGVuZ3RoXSBUaGUgZW5kIHBvc2l0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbMSwgMiwgM107CiAgICAgICAgICoKICAgICAgICAgKiBfLmZpbGwoYXJyYXksICdhJyk7CiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFsnYScsICdhJywgJ2EnXQogICAgICAgICAqCiAgICAgICAgICogXy5maWxsKEFycmF5KDMpLCAyKTsKICAgICAgICAgKiAvLyA9PiBbMiwgMiwgMl0KICAgICAgICAgKgogICAgICAgICAqIF8uZmlsbChbNCwgNiwgOCwgMTBdLCAnKicsIDEsIDMpOwogICAgICAgICAqIC8vID0+IFs0LCAnKicsICcqJywgMTBdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZmlsbChhcnJheSwgdmFsdWUsIHN0YXJ0LCBlbmQpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChzdGFydCAmJiB0eXBlb2Ygc3RhcnQgIT0gJ251bWJlcicgJiYgaXNJdGVyYXRlZUNhbGwoYXJyYXksIHZhbHVlLCBzdGFydCkpIHsKICAgICAgICAgICAgc3RhcnQgPSAwOwogICAgICAgICAgICBlbmQgPSBsZW5ndGg7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYmFzZUZpbGwoYXJyYXksIHZhbHVlLCBzdGFydCwgZW5kKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZmluZGAgZXhjZXB0IHRoYXQgaXQgcmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIGZpcnN0CiAgICAgICAgICogZWxlbWVudCBgcHJlZGljYXRlYCByZXR1cm5zIHRydXRoeSBmb3IgaW5zdGVhZCBvZiB0aGUgZWxlbWVudCBpdHNlbGYuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMS4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtmcm9tSW5kZXg9MF0gVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBmb3VuZCBlbGVtZW50LCBlbHNlIGAtMWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhY3RpdmUnOiBmYWxzZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWN0aXZlJzogdHJ1ZSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmluZEluZGV4KHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiBvLnVzZXIgPT0gJ2Jhcm5leSc7IH0pOwogICAgICAgICAqIC8vID0+IDAKICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzYCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5maW5kSW5kZXgodXNlcnMsIHsgJ3VzZXInOiAnZnJlZCcsICdhY3RpdmUnOiBmYWxzZSB9KTsKICAgICAgICAgKiAvLyA9PiAxCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc1Byb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5maW5kSW5kZXgodXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiAwCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmZpbmRJbmRleCh1c2VycywgJ2FjdGl2ZScpOwogICAgICAgICAqIC8vID0+IDIKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmaW5kSW5kZXgoYXJyYXksIHByZWRpY2F0ZSwgZnJvbUluZGV4KSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgICBpZiAoIWxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgaW5kZXggPSBmcm9tSW5kZXggPT0gbnVsbCA/IDAgOiB0b0ludGVnZXIoZnJvbUluZGV4KTsKICAgICAgICAgIGlmIChpbmRleCA8IDApIHsKICAgICAgICAgICAgaW5kZXggPSBuYXRpdmVNYXgobGVuZ3RoICsgaW5kZXgsIDApOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VGaW5kSW5kZXgoYXJyYXksIGdldEl0ZXJhdGVlKHByZWRpY2F0ZSwgMyksIGluZGV4KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZmluZEluZGV4YCBleGNlcHQgdGhhdCBpdCBpdGVyYXRlcyBvdmVyIGVsZW1lbnRzCiAgICAgICAgICogb2YgYGNvbGxlY3Rpb25gIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2Zyb21JbmRleD1hcnJheS5sZW5ndGgtMV0gVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBmb3VuZCBlbGVtZW50LCBlbHNlIGAtMWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhY3RpdmUnOiB0cnVlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICAnYWN0aXZlJzogZmFsc2UgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAncGViYmxlcycsICdhY3RpdmUnOiBmYWxzZSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmluZExhc3RJbmRleCh1c2VycywgZnVuY3Rpb24obykgeyByZXR1cm4gby51c2VyID09ICdwZWJibGVzJzsgfSk7CiAgICAgICAgICogLy8gPT4gMgogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmZpbmRMYXN0SW5kZXgodXNlcnMsIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FjdGl2ZSc6IHRydWUgfSk7CiAgICAgICAgICogLy8gPT4gMAogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZExhc3RJbmRleCh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICAgICAqIC8vID0+IDIKICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZExhc3RJbmRleCh1c2VycywgJ2FjdGl2ZScpOwogICAgICAgICAqIC8vID0+IDAKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmaW5kTGFzdEluZGV4KGFycmF5LCBwcmVkaWNhdGUsIGZyb21JbmRleCkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGluZGV4ID0gbGVuZ3RoIC0gMTsKICAgICAgICAgIGlmIChmcm9tSW5kZXggIT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgIGluZGV4ID0gdG9JbnRlZ2VyKGZyb21JbmRleCk7CiAgICAgICAgICAgIGluZGV4ID0gZnJvbUluZGV4IDwgMAogICAgICAgICAgICAgID8gbmF0aXZlTWF4KGxlbmd0aCArIGluZGV4LCAwKQogICAgICAgICAgICAgIDogbmF0aXZlTWluKGluZGV4LCBsZW5ndGggLSAxKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBiYXNlRmluZEluZGV4KGFycmF5LCBnZXRJdGVyYXRlZShwcmVkaWNhdGUsIDMpLCBpbmRleCwgdHJ1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBGbGF0dGVucyBgYXJyYXlgIGEgc2luZ2xlIGxldmVsIGRlZXAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gZmxhdHRlbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBmbGF0dGVuZWQgYXJyYXkuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZmxhdHRlbihbMSwgWzIsIFszLCBbNF1dLCA1XV0pOwogICAgICAgICAqIC8vID0+IFsxLCAyLCBbMywgWzRdXSwgNV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmbGF0dGVuKGFycmF5KSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgICByZXR1cm4gbGVuZ3RoID8gYmFzZUZsYXR0ZW4oYXJyYXksIDEpIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZWN1cnNpdmVseSBmbGF0dGVucyBgYXJyYXlgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGZsYXR0ZW4uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZmxhdHRlbmVkIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmZsYXR0ZW5EZWVwKFsxLCBbMiwgWzMsIFs0XV0sIDVdXSk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDMsIDQsIDVdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZmxhdHRlbkRlZXAoYXJyYXkpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIHJldHVybiBsZW5ndGggPyBiYXNlRmxhdHRlbihhcnJheSwgSU5GSU5JVFkpIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZWN1cnNpdmVseSBmbGF0dGVuIGBhcnJheWAgdXAgdG8gYGRlcHRoYCB0aW1lcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBmbGF0dGVuLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZGVwdGg9MV0gVGhlIG1heGltdW0gcmVjdXJzaW9uIGRlcHRoLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZsYXR0ZW5lZCBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gWzEsIFsyLCBbMywgWzRdXSwgNV1dOwogICAgICAgICAqCiAgICAgICAgICogXy5mbGF0dGVuRGVwdGgoYXJyYXksIDEpOwogICAgICAgICAqIC8vID0+IFsxLCAyLCBbMywgWzRdXSwgNV0KICAgICAgICAgKgogICAgICAgICAqIF8uZmxhdHRlbkRlcHRoKGFycmF5LCAyKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMiwgMywgWzRdLCA1XQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGZsYXR0ZW5EZXB0aChhcnJheSwgZGVwdGgpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIGRlcHRoID0gZGVwdGggPT09IHVuZGVmaW5lZCQxID8gMSA6IHRvSW50ZWdlcihkZXB0aCk7CiAgICAgICAgICByZXR1cm4gYmFzZUZsYXR0ZW4oYXJyYXksIGRlcHRoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBpbnZlcnNlIG9mIGBfLnRvUGFpcnNgOyB0aGlzIG1ldGhvZCByZXR1cm5zIGFuIG9iamVjdCBjb21wb3NlZAogICAgICAgICAqIGZyb20ga2V5LXZhbHVlIGBwYWlyc2AuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBwYWlycyBUaGUga2V5LXZhbHVlIHBhaXJzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZnJvbVBhaXJzKFtbJ2EnLCAxXSwgWydiJywgMl1dKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmcm9tUGFpcnMocGFpcnMpIHsKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IHBhaXJzID09IG51bGwgPyAwIDogcGFpcnMubGVuZ3RoLAogICAgICAgICAgICAgIHJlc3VsdCA9IHt9OwoKICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgIHZhciBwYWlyID0gcGFpcnNbaW5kZXhdOwogICAgICAgICAgICByZXN1bHRbcGFpclswXV0gPSBwYWlyWzFdOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIGZpcnN0IGVsZW1lbnQgb2YgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBhbGlhcyBmaXJzdAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgZmlyc3QgZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmhlYWQoWzEsIDIsIDNdKTsKICAgICAgICAgKiAvLyA9PiAxCiAgICAgICAgICoKICAgICAgICAgKiBfLmhlYWQoW10pOwogICAgICAgICAqIC8vID0+IHVuZGVmaW5lZAogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGhlYWQoYXJyYXkpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKSA/IGFycmF5WzBdIDogdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBpbmRleCBhdCB3aGljaCB0aGUgZmlyc3Qgb2NjdXJyZW5jZSBvZiBgdmFsdWVgIGlzIGZvdW5kIGluIGBhcnJheWAKICAgICAgICAgKiB1c2luZyBbYFNhbWVWYWx1ZVplcm9gXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1zYW1ldmFsdWV6ZXJvKQogICAgICAgICAqIGZvciBlcXVhbGl0eSBjb21wYXJpc29ucy4gSWYgYGZyb21JbmRleGAgaXMgbmVnYXRpdmUsIGl0J3MgdXNlZCBhcyB0aGUKICAgICAgICAgKiBvZmZzZXQgZnJvbSB0aGUgZW5kIG9mIGBhcnJheWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZnJvbUluZGV4PTBdIFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgbWF0Y2hlZCB2YWx1ZSwgZWxzZSBgLTFgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmluZGV4T2YoWzEsIDIsIDEsIDJdLCAyKTsKICAgICAgICAgKiAvLyA9PiAxCiAgICAgICAgICoKICAgICAgICAgKiAvLyBTZWFyY2ggZnJvbSB0aGUgYGZyb21JbmRleGAuCiAgICAgICAgICogXy5pbmRleE9mKFsxLCAyLCAxLCAyXSwgMiwgMik7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGluZGV4T2YoYXJyYXksIHZhbHVlLCBmcm9tSW5kZXgpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBpbmRleCA9IGZyb21JbmRleCA9PSBudWxsID8gMCA6IHRvSW50ZWdlcihmcm9tSW5kZXgpOwogICAgICAgICAgaWYgKGluZGV4IDwgMCkgewogICAgICAgICAgICBpbmRleCA9IG5hdGl2ZU1heChsZW5ndGggKyBpbmRleCwgMCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYmFzZUluZGV4T2YoYXJyYXksIHZhbHVlLCBpbmRleCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIGFsbCBidXQgdGhlIGxhc3QgZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc2xpY2Ugb2YgYGFycmF5YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pbml0aWFsKFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gWzEsIDJdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaW5pdGlhbChhcnJheSkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgcmV0dXJuIGxlbmd0aCA/IGJhc2VTbGljZShhcnJheSwgMCwgLTEpIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHVuaXF1ZSB2YWx1ZXMgdGhhdCBhcmUgaW5jbHVkZWQgaW4gYWxsIGdpdmVuIGFycmF5cwogICAgICAgICAqIHVzaW5nIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLiBUaGUgb3JkZXIgYW5kIHJlZmVyZW5jZXMgb2YgcmVzdWx0IHZhbHVlcyBhcmUKICAgICAgICAgKiBkZXRlcm1pbmVkIGJ5IHRoZSBmaXJzdCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7Li4uQXJyYXl9IFthcnJheXNdIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBpbnRlcnNlY3RpbmcgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmludGVyc2VjdGlvbihbMiwgMV0sIFsyLCAzXSk7CiAgICAgICAgICogLy8gPT4gWzJdCiAgICAgICAgICovCiAgICAgICAgdmFyIGludGVyc2VjdGlvbiA9IGJhc2VSZXN0KGZ1bmN0aW9uKGFycmF5cykgewogICAgICAgICAgdmFyIG1hcHBlZCA9IGFycmF5TWFwKGFycmF5cywgY2FzdEFycmF5TGlrZU9iamVjdCk7CiAgICAgICAgICByZXR1cm4gKG1hcHBlZC5sZW5ndGggJiYgbWFwcGVkWzBdID09PSBhcnJheXNbMF0pCiAgICAgICAgICAgID8gYmFzZUludGVyc2VjdGlvbihtYXBwZWQpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaW50ZXJzZWN0aW9uYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAKICAgICAgICAgKiB3aGljaCBpcyBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgb2YgZWFjaCBgYXJyYXlzYCB0byBnZW5lcmF0ZSB0aGUgY3JpdGVyaW9uCiAgICAgICAgICogYnkgd2hpY2ggdGhleSdyZSBjb21wYXJlZC4gVGhlIG9yZGVyIGFuZCByZWZlcmVuY2VzIG9mIHJlc3VsdCB2YWx1ZXMgYXJlCiAgICAgICAgICogZGV0ZXJtaW5lZCBieSB0aGUgZmlyc3QgYXJyYXkuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OgogICAgICAgICAqICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbYXJyYXlzXSBUaGUgYXJyYXlzIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIGludGVyc2VjdGluZyB2YWx1ZXMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaW50ZXJzZWN0aW9uQnkoWzIuMSwgMS4yXSwgWzIuMywgMy40XSwgTWF0aC5mbG9vcik7CiAgICAgICAgICogLy8gPT4gWzIuMV0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uaW50ZXJzZWN0aW9uQnkoW3sgJ3gnOiAxIH1dLCBbeyAneCc6IDIgfSwgeyAneCc6IDEgfV0sICd4Jyk7CiAgICAgICAgICogLy8gPT4gW3sgJ3gnOiAxIH1dCiAgICAgICAgICovCiAgICAgICAgdmFyIGludGVyc2VjdGlvbkJ5ID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICB2YXIgaXRlcmF0ZWUgPSBsYXN0KGFycmF5cyksCiAgICAgICAgICAgICAgbWFwcGVkID0gYXJyYXlNYXAoYXJyYXlzLCBjYXN0QXJyYXlMaWtlT2JqZWN0KTsKCiAgICAgICAgICBpZiAoaXRlcmF0ZWUgPT09IGxhc3QobWFwcGVkKSkgewogICAgICAgICAgICBpdGVyYXRlZSA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbWFwcGVkLnBvcCgpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIChtYXBwZWQubGVuZ3RoICYmIG1hcHBlZFswXSA9PT0gYXJyYXlzWzBdKQogICAgICAgICAgICA/IGJhc2VJbnRlcnNlY3Rpb24obWFwcGVkLCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMikpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaW50ZXJzZWN0aW9uYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjb21wYXJhdG9yYAogICAgICAgICAqIHdoaWNoIGlzIGludm9rZWQgdG8gY29tcGFyZSBlbGVtZW50cyBvZiBgYXJyYXlzYC4gVGhlIG9yZGVyIGFuZCByZWZlcmVuY2VzCiAgICAgICAgICogb2YgcmVzdWx0IHZhbHVlcyBhcmUgZGV0ZXJtaW5lZCBieSB0aGUgZmlyc3QgYXJyYXkuIFRoZSBjb21wYXJhdG9yIGlzCiAgICAgICAgICogaW52b2tlZCB3aXRoIHR3byBhcmd1bWVudHM6IChhcnJWYWwsIG90aFZhbCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbYXJyYXlzXSBUaGUgYXJyYXlzIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2NvbXBhcmF0b3JdIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgaW50ZXJzZWN0aW5nIHZhbHVlcy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAneCc6IDEsICd5JzogMiB9LCB7ICd4JzogMiwgJ3knOiAxIH1dOwogICAgICAgICAqIHZhciBvdGhlcnMgPSBbeyAneCc6IDEsICd5JzogMSB9LCB7ICd4JzogMSwgJ3knOiAyIH1dOwogICAgICAgICAqCiAgICAgICAgICogXy5pbnRlcnNlY3Rpb25XaXRoKG9iamVjdHMsIG90aGVycywgXy5pc0VxdWFsKTsKICAgICAgICAgKiAvLyA9PiBbeyAneCc6IDEsICd5JzogMiB9XQogICAgICAgICAqLwogICAgICAgIHZhciBpbnRlcnNlY3Rpb25XaXRoID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICB2YXIgY29tcGFyYXRvciA9IGxhc3QoYXJyYXlzKSwKICAgICAgICAgICAgICBtYXBwZWQgPSBhcnJheU1hcChhcnJheXMsIGNhc3RBcnJheUxpa2VPYmplY3QpOwoKICAgICAgICAgIGNvbXBhcmF0b3IgPSB0eXBlb2YgY29tcGFyYXRvciA9PSAnZnVuY3Rpb24nID8gY29tcGFyYXRvciA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgaWYgKGNvbXBhcmF0b3IpIHsKICAgICAgICAgICAgbWFwcGVkLnBvcCgpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIChtYXBwZWQubGVuZ3RoICYmIG1hcHBlZFswXSA9PT0gYXJyYXlzWzBdKQogICAgICAgICAgICA/IGJhc2VJbnRlcnNlY3Rpb24obWFwcGVkLCB1bmRlZmluZWQkMSwgY29tcGFyYXRvcikKICAgICAgICAgICAgOiBbXTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYWxsIGVsZW1lbnRzIGluIGBhcnJheWAgaW50byBhIHN0cmluZyBzZXBhcmF0ZWQgYnkgYHNlcGFyYXRvcmAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gY29udmVydC4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3NlcGFyYXRvcj0nLCddIFRoZSBlbGVtZW50IHNlcGFyYXRvci4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBqb2luZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmpvaW4oWydhJywgJ2InLCAnYyddLCAnficpOwogICAgICAgICAqIC8vID0+ICdhfmJ+YycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBqb2luKGFycmF5LCBzZXBhcmF0b3IpIHsKICAgICAgICAgIHJldHVybiBhcnJheSA9PSBudWxsID8gJycgOiBuYXRpdmVKb2luLmNhbGwoYXJyYXksIHNlcGFyYXRvcik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBsYXN0IGVsZW1lbnQgb2YgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbGFzdCBlbGVtZW50IG9mIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ubGFzdChbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IDMKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsYXN0KGFycmF5KSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgICByZXR1cm4gbGVuZ3RoID8gYXJyYXlbbGVuZ3RoIC0gMV0gOiB1bmRlZmluZWQkMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaW5kZXhPZmAgZXhjZXB0IHRoYXQgaXQgaXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZgogICAgICAgICAqIGBhcnJheWAgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2VhcmNoIGZvci4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2Zyb21JbmRleD1hcnJheS5sZW5ndGgtMV0gVGhlIGluZGV4IHRvIHNlYXJjaCBmcm9tLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBtYXRjaGVkIHZhbHVlLCBlbHNlIGAtMWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ubGFzdEluZGV4T2YoWzEsIDIsIDEsIDJdLCAyKTsKICAgICAgICAgKiAvLyA9PiAzCiAgICAgICAgICoKICAgICAgICAgKiAvLyBTZWFyY2ggZnJvbSB0aGUgYGZyb21JbmRleGAuCiAgICAgICAgICogXy5sYXN0SW5kZXhPZihbMSwgMiwgMSwgMl0sIDIsIDIpOwogICAgICAgICAqIC8vID0+IDEKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBsYXN0SW5kZXhPZihhcnJheSwgdmFsdWUsIGZyb21JbmRleCkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGluZGV4ID0gbGVuZ3RoOwogICAgICAgICAgaWYgKGZyb21JbmRleCAhPT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgaW5kZXggPSB0b0ludGVnZXIoZnJvbUluZGV4KTsKICAgICAgICAgICAgaW5kZXggPSBpbmRleCA8IDAgPyBuYXRpdmVNYXgobGVuZ3RoICsgaW5kZXgsIDApIDogbmF0aXZlTWluKGluZGV4LCBsZW5ndGggLSAxKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB2YWx1ZSA9PT0gdmFsdWUKICAgICAgICAgICAgPyBzdHJpY3RMYXN0SW5kZXhPZihhcnJheSwgdmFsdWUsIGluZGV4KQogICAgICAgICAgICA6IGJhc2VGaW5kSW5kZXgoYXJyYXksIGJhc2VJc05hTiwgaW5kZXgsIHRydWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgZWxlbWVudCBhdCBpbmRleCBgbmAgb2YgYGFycmF5YC4gSWYgYG5gIGlzIG5lZ2F0aXZlLCB0aGUgbnRoCiAgICAgICAgICogZWxlbWVudCBmcm9tIHRoZSBlbmQgaXMgcmV0dXJuZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4xMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbj0wXSBUaGUgaW5kZXggb2YgdGhlIGVsZW1lbnQgdG8gcmV0dXJuLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBudGggZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbJ2EnLCAnYicsICdjJywgJ2QnXTsKICAgICAgICAgKgogICAgICAgICAqIF8ubnRoKGFycmF5LCAxKTsKICAgICAgICAgKiAvLyA9PiAnYicKICAgICAgICAgKgogICAgICAgICAqIF8ubnRoKGFycmF5LCAtMik7CiAgICAgICAgICogLy8gPT4gJ2MnOwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG50aChhcnJheSwgbikgewogICAgICAgICAgcmV0dXJuIChhcnJheSAmJiBhcnJheS5sZW5ndGgpID8gYmFzZU50aChhcnJheSwgdG9JbnRlZ2VyKG4pKSA6IHVuZGVmaW5lZCQxOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbGwgZ2l2ZW4gdmFsdWVzIGZyb20gYGFycmF5YCB1c2luZwogICAgICAgICAqIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy53aXRob3V0YCwgdGhpcyBtZXRob2QgbXV0YXRlcyBgYXJyYXlgLiBVc2UgYF8ucmVtb3ZlYAogICAgICAgICAqIHRvIHJlbW92ZSBlbGVtZW50cyBmcm9tIGFuIGFycmF5IGJ5IHByZWRpY2F0ZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBbdmFsdWVzXSBUaGUgdmFsdWVzIHRvIHJlbW92ZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gWydhJywgJ2InLCAnYycsICdhJywgJ2InLCAnYyddOwogICAgICAgICAqCiAgICAgICAgICogXy5wdWxsKGFycmF5LCAnYScsICdjJyk7CiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFsnYicsICdiJ10KICAgICAgICAgKi8KICAgICAgICB2YXIgcHVsbCA9IGJhc2VSZXN0KHB1bGxBbGwpOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnB1bGxgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYW4gYXJyYXkgb2YgdmFsdWVzIHRvIHJlbW92ZS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBVbmxpa2UgYF8uZGlmZmVyZW5jZWAsIHRoaXMgbWV0aG9kIG11dGF0ZXMgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gdmFsdWVzIFRoZSB2YWx1ZXMgdG8gcmVtb3ZlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbJ2EnLCAnYicsICdjJywgJ2EnLCAnYicsICdjJ107CiAgICAgICAgICoKICAgICAgICAgKiBfLnB1bGxBbGwoYXJyYXksIFsnYScsICdjJ10pOwogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5KTsKICAgICAgICAgKiAvLyA9PiBbJ2InLCAnYiddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gcHVsbEFsbChhcnJheSwgdmFsdWVzKSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCAmJiB2YWx1ZXMgJiYgdmFsdWVzLmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlUHVsbEFsbChhcnJheSwgdmFsdWVzKQogICAgICAgICAgICA6IGFycmF5OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5wdWxsQWxsYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAgd2hpY2ggaXMKICAgICAgICAgKiBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgb2YgYGFycmF5YCBhbmQgYHZhbHVlc2AgdG8gZ2VuZXJhdGUgdGhlIGNyaXRlcmlvbgogICAgICAgICAqIGJ5IHdoaWNoIHRoZXkncmUgY29tcGFyZWQuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy5kaWZmZXJlbmNlQnlgLCB0aGlzIG1ldGhvZCBtdXRhdGVzIGBhcnJheWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IHZhbHVlcyBUaGUgdmFsdWVzIHRvIHJlbW92ZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IFt7ICd4JzogMSB9LCB7ICd4JzogMiB9LCB7ICd4JzogMyB9LCB7ICd4JzogMSB9XTsKICAgICAgICAgKgogICAgICAgICAqIF8ucHVsbEFsbEJ5KGFycmF5LCBbeyAneCc6IDEgfSwgeyAneCc6IDMgfV0sICd4Jyk7CiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFt7ICd4JzogMiB9XQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHB1bGxBbGxCeShhcnJheSwgdmFsdWVzLCBpdGVyYXRlZSkgewogICAgICAgICAgcmV0dXJuIChhcnJheSAmJiBhcnJheS5sZW5ndGggJiYgdmFsdWVzICYmIHZhbHVlcy5sZW5ndGgpCiAgICAgICAgICAgID8gYmFzZVB1bGxBbGwoYXJyYXksIHZhbHVlcywgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpKQogICAgICAgICAgICA6IGFycmF5OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5wdWxsQWxsYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjb21wYXJhdG9yYCB3aGljaAogICAgICAgICAqIGlzIGludm9rZWQgdG8gY29tcGFyZSBlbGVtZW50cyBvZiBgYXJyYXlgIHRvIGB2YWx1ZXNgLiBUaGUgY29tcGFyYXRvciBpcwogICAgICAgICAqIGludm9rZWQgd2l0aCB0d28gYXJndW1lbnRzOiAoYXJyVmFsLCBvdGhWYWwpLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy5kaWZmZXJlbmNlV2l0aGAsIHRoaXMgbWV0aG9kIG11dGF0ZXMgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjYuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gdmFsdWVzIFRoZSB2YWx1ZXMgdG8gcmVtb3ZlLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjb21wYXJhdG9yXSBUaGUgY29tcGFyYXRvciBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbeyAneCc6IDEsICd5JzogMiB9LCB7ICd4JzogMywgJ3knOiA0IH0sIHsgJ3gnOiA1LCAneSc6IDYgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLnB1bGxBbGxXaXRoKGFycmF5LCBbeyAneCc6IDMsICd5JzogNCB9XSwgXy5pc0VxdWFsKTsKICAgICAgICAgKiBjb25zb2xlLmxvZyhhcnJheSk7CiAgICAgICAgICogLy8gPT4gW3sgJ3gnOiAxLCAneSc6IDIgfSwgeyAneCc6IDUsICd5JzogNiB9XQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHB1bGxBbGxXaXRoKGFycmF5LCB2YWx1ZXMsIGNvbXBhcmF0b3IpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoICYmIHZhbHVlcyAmJiB2YWx1ZXMubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VQdWxsQWxsKGFycmF5LCB2YWx1ZXMsIHVuZGVmaW5lZCQxLCBjb21wYXJhdG9yKQogICAgICAgICAgICA6IGFycmF5OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBlbGVtZW50cyBmcm9tIGBhcnJheWAgY29ycmVzcG9uZGluZyB0byBgaW5kZXhlc2AgYW5kIHJldHVybnMgYW4KICAgICAgICAgKiBhcnJheSBvZiByZW1vdmVkIGVsZW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBgXy5hdGAsIHRoaXMgbWV0aG9kIG11dGF0ZXMgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHsuLi4obnVtYmVyfG51bWJlcltdKX0gW2luZGV4ZXNdIFRoZSBpbmRleGVzIG9mIGVsZW1lbnRzIHRvIHJlbW92ZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiByZW1vdmVkIGVsZW1lbnRzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbJ2EnLCAnYicsICdjJywgJ2QnXTsKICAgICAgICAgKiB2YXIgcHVsbGVkID0gXy5wdWxsQXQoYXJyYXksIFsxLCAzXSk7CiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhhcnJheSk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2MnXQogICAgICAgICAqCiAgICAgICAgICogY29uc29sZS5sb2cocHVsbGVkKTsKICAgICAgICAgKiAvLyA9PiBbJ2InLCAnZCddCiAgICAgICAgICovCiAgICAgICAgdmFyIHB1bGxBdCA9IGZsYXRSZXN0KGZ1bmN0aW9uKGFycmF5LCBpbmRleGVzKSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgICAgcmVzdWx0ID0gYmFzZUF0KGFycmF5LCBpbmRleGVzKTsKCiAgICAgICAgICBiYXNlUHVsbEF0KGFycmF5LCBhcnJheU1hcChpbmRleGVzLCBmdW5jdGlvbihpbmRleCkgewogICAgICAgICAgICByZXR1cm4gaXNJbmRleChpbmRleCwgbGVuZ3RoKSA/ICtpbmRleCA6IGluZGV4OwogICAgICAgICAgfSkuc29ydChjb21wYXJlQXNjZW5kaW5nKSk7CgogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbGwgZWxlbWVudHMgZnJvbSBgYXJyYXlgIHRoYXQgYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yCiAgICAgICAgICogYW5kIHJldHVybnMgYW4gYXJyYXkgb2YgdGhlIHJlbW92ZWQgZWxlbWVudHMuIFRoZSBwcmVkaWNhdGUgaXMgaW52b2tlZAogICAgICAgICAqIHdpdGggdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGluZGV4LCBhcnJheSkuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVW5saWtlIGBfLmZpbHRlcmAsIHRoaXMgbWV0aG9kIG11dGF0ZXMgYGFycmF5YC4gVXNlIGBfLnB1bGxgCiAgICAgICAgICogdG8gcHVsbCBlbGVtZW50cyBmcm9tIGFuIGFycmF5IGJ5IHZhbHVlLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgcmVtb3ZlZCBlbGVtZW50cy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gWzEsIDIsIDMsIDRdOwogICAgICAgICAqIHZhciBldmVucyA9IF8ucmVtb3ZlKGFycmF5LCBmdW5jdGlvbihuKSB7CiAgICAgICAgICogICByZXR1cm4gbiAlIDIgPT0gMDsKICAgICAgICAgKiB9KTsKICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5KTsKICAgICAgICAgKiAvLyA9PiBbMSwgM10KICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGV2ZW5zKTsKICAgICAgICAgKiAvLyA9PiBbMiwgNF0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZW1vdmUoYXJyYXksIHByZWRpY2F0ZSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICAgICAgaWYgKCEoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKSkgewogICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgfQogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgaW5kZXhlcyA9IFtdLAogICAgICAgICAgICAgIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKCiAgICAgICAgICBwcmVkaWNhdGUgPSBnZXRJdGVyYXRlZShwcmVkaWNhdGUsIDMpOwogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdOwogICAgICAgICAgICBpZiAocHJlZGljYXRlKHZhbHVlLCBpbmRleCwgYXJyYXkpKSB7CiAgICAgICAgICAgICAgcmVzdWx0LnB1c2godmFsdWUpOwogICAgICAgICAgICAgIGluZGV4ZXMucHVzaChpbmRleCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGJhc2VQdWxsQXQoYXJyYXksIGluZGV4ZXMpOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldmVyc2VzIGBhcnJheWAgc28gdGhhdCB0aGUgZmlyc3QgZWxlbWVudCBiZWNvbWVzIHRoZSBsYXN0LCB0aGUgc2Vjb25kCiAgICAgICAgICogZWxlbWVudCBiZWNvbWVzIHRoZSBzZWNvbmQgdG8gbGFzdCwgYW5kIHNvIG9uLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIG11dGF0ZXMgYGFycmF5YCBhbmQgaXMgYmFzZWQgb24KICAgICAgICAgKiBbYEFycmF5I3JldmVyc2VgXShodHRwczovL21kbi5pby9BcnJheS9yZXZlcnNlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBtb2RpZnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IFsxLCAyLCAzXTsKICAgICAgICAgKgogICAgICAgICAqIF8ucmV2ZXJzZShhcnJheSk7CiAgICAgICAgICogLy8gPT4gWzMsIDIsIDFdCiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhhcnJheSk7CiAgICAgICAgICogLy8gPT4gWzMsIDIsIDFdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gcmV2ZXJzZShhcnJheSkgewogICAgICAgICAgcmV0dXJuIGFycmF5ID09IG51bGwgPyBhcnJheSA6IG5hdGl2ZVJldmVyc2UuY2FsbChhcnJheSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2xpY2Ugb2YgYGFycmF5YCBmcm9tIGBzdGFydGAgdXAgdG8sIGJ1dCBub3QgaW5jbHVkaW5nLCBgZW5kYC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyB1c2VkIGluc3RlYWQgb2YKICAgICAgICAgKiBbYEFycmF5I3NsaWNlYF0oaHR0cHM6Ly9tZG4uaW8vQXJyYXkvc2xpY2UpIHRvIGVuc3VyZSBkZW5zZSBhcnJheXMgYXJlCiAgICAgICAgICogcmV0dXJuZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gc2xpY2UuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGFydD0wXSBUaGUgc3RhcnQgcG9zaXRpb24uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtlbmQ9YXJyYXkubGVuZ3RoXSBUaGUgZW5kIHBvc2l0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc2xpY2Ugb2YgYGFycmF5YC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzbGljZShhcnJheSwgc3RhcnQsIGVuZCkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGVuZCAmJiB0eXBlb2YgZW5kICE9ICdudW1iZXInICYmIGlzSXRlcmF0ZWVDYWxsKGFycmF5LCBzdGFydCwgZW5kKSkgewogICAgICAgICAgICBzdGFydCA9IDA7CiAgICAgICAgICAgIGVuZCA9IGxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIGVsc2UgewogICAgICAgICAgICBzdGFydCA9IHN0YXJ0ID09IG51bGwgPyAwIDogdG9JbnRlZ2VyKHN0YXJ0KTsKICAgICAgICAgICAgZW5kID0gZW5kID09PSB1bmRlZmluZWQkMSA/IGxlbmd0aCA6IHRvSW50ZWdlcihlbmQpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VTbGljZShhcnJheSwgc3RhcnQsIGVuZCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBVc2VzIGEgYmluYXJ5IHNlYXJjaCB0byBkZXRlcm1pbmUgdGhlIGxvd2VzdCBpbmRleCBhdCB3aGljaCBgdmFsdWVgCiAgICAgICAgICogc2hvdWxkIGJlIGluc2VydGVkIGludG8gYGFycmF5YCBpbiBvcmRlciB0byBtYWludGFpbiBpdHMgc29ydCBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBzb3J0ZWQgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBldmFsdWF0ZS4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBhdCB3aGljaCBgdmFsdWVgIHNob3VsZCBiZSBpbnNlcnRlZAogICAgICAgICAqICBpbnRvIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uc29ydGVkSW5kZXgoWzMwLCA1MF0sIDQwKTsKICAgICAgICAgKiAvLyA9PiAxCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc29ydGVkSW5kZXgoYXJyYXksIHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVNvcnRlZEluZGV4KGFycmF5LCB2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnNvcnRlZEluZGV4YCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAKICAgICAgICAgKiB3aGljaCBpcyBpbnZva2VkIGZvciBgdmFsdWVgIGFuZCBlYWNoIGVsZW1lbnQgb2YgYGFycmF5YCB0byBjb21wdXRlIHRoZWlyCiAgICAgICAgICogc29ydCByYW5raW5nLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBzb3J0ZWQgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBldmFsdWF0ZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggYXQgd2hpY2ggYHZhbHVlYCBzaG91bGQgYmUgaW5zZXJ0ZWQKICAgICAgICAgKiAgaW50byBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IFt7ICd4JzogNCB9LCB7ICd4JzogNSB9XTsKICAgICAgICAgKgogICAgICAgICAqIF8uc29ydGVkSW5kZXhCeShvYmplY3RzLCB7ICd4JzogNCB9LCBmdW5jdGlvbihvKSB7IHJldHVybiBvLng7IH0pOwogICAgICAgICAqIC8vID0+IDAKICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uc29ydGVkSW5kZXhCeShvYmplY3RzLCB7ICd4JzogNCB9LCAneCcpOwogICAgICAgICAqIC8vID0+IDAKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzb3J0ZWRJbmRleEJ5KGFycmF5LCB2YWx1ZSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiBiYXNlU29ydGVkSW5kZXhCeShhcnJheSwgdmFsdWUsIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAyKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmluZGV4T2ZgIGV4Y2VwdCB0aGF0IGl0IHBlcmZvcm1zIGEgYmluYXJ5CiAgICAgICAgICogc2VhcmNoIG9uIGEgc29ydGVkIGBhcnJheWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBtYXRjaGVkIHZhbHVlLCBlbHNlIGAtMWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uc29ydGVkSW5kZXhPZihbNCwgNSwgNSwgNSwgNl0sIDUpOwogICAgICAgICAqIC8vID0+IDEKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzb3J0ZWRJbmRleE9mKGFycmF5LCB2YWx1ZSkgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICAgICAgaWYgKGxlbmd0aCkgewogICAgICAgICAgICB2YXIgaW5kZXggPSBiYXNlU29ydGVkSW5kZXgoYXJyYXksIHZhbHVlKTsKICAgICAgICAgICAgaWYgKGluZGV4IDwgbGVuZ3RoICYmIGVxKGFycmF5W2luZGV4XSwgdmFsdWUpKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnNvcnRlZEluZGV4YCBleGNlcHQgdGhhdCBpdCByZXR1cm5zIHRoZSBoaWdoZXN0CiAgICAgICAgICogaW5kZXggYXQgd2hpY2ggYHZhbHVlYCBzaG91bGQgYmUgaW5zZXJ0ZWQgaW50byBgYXJyYXlgIGluIG9yZGVyIHRvCiAgICAgICAgICogbWFpbnRhaW4gaXRzIHNvcnQgb3JkZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgc29ydGVkIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gZXZhbHVhdGUuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggYXQgd2hpY2ggYHZhbHVlYCBzaG91bGQgYmUgaW5zZXJ0ZWQKICAgICAgICAgKiAgaW50byBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNvcnRlZExhc3RJbmRleChbNCwgNSwgNSwgNSwgNl0sIDUpOwogICAgICAgICAqIC8vID0+IDQKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzb3J0ZWRMYXN0SW5kZXgoYXJyYXksIHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVNvcnRlZEluZGV4KGFycmF5LCB2YWx1ZSwgdHJ1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnNvcnRlZExhc3RJbmRleGAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgCiAgICAgICAgICogd2hpY2ggaXMgaW52b2tlZCBmb3IgYHZhbHVlYCBhbmQgZWFjaCBlbGVtZW50IG9mIGBhcnJheWAgdG8gY29tcHV0ZSB0aGVpcgogICAgICAgICAqIHNvcnQgcmFua2luZy4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ6ICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgc29ydGVkIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gZXZhbHVhdGUuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IGF0IHdoaWNoIGB2YWx1ZWAgc2hvdWxkIGJlIGluc2VydGVkCiAgICAgICAgICogIGludG8gYGFycmF5YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAneCc6IDQgfSwgeyAneCc6IDUgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLnNvcnRlZExhc3RJbmRleEJ5KG9iamVjdHMsIHsgJ3gnOiA0IH0sIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8ueDsgfSk7CiAgICAgICAgICogLy8gPT4gMQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5zb3J0ZWRMYXN0SW5kZXhCeShvYmplY3RzLCB7ICd4JzogNCB9LCAneCcpOwogICAgICAgICAqIC8vID0+IDEKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzb3J0ZWRMYXN0SW5kZXhCeShhcnJheSwgdmFsdWUsIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVNvcnRlZEluZGV4QnkoYXJyYXksIHZhbHVlLCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMiksIHRydWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5sYXN0SW5kZXhPZmAgZXhjZXB0IHRoYXQgaXQgcGVyZm9ybXMgYSBiaW5hcnkKICAgICAgICAgKiBzZWFyY2ggb24gYSBzb3J0ZWQgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5zb3J0ZWRMYXN0SW5kZXhPZihbNCwgNSwgNSwgNSwgNl0sIDUpOwogICAgICAgICAqIC8vID0+IDMKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzb3J0ZWRMYXN0SW5kZXhPZihhcnJheSwgdmFsdWUpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIGlmIChsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGluZGV4ID0gYmFzZVNvcnRlZEluZGV4KGFycmF5LCB2YWx1ZSwgdHJ1ZSkgLSAxOwogICAgICAgICAgICBpZiAoZXEoYXJyYXlbaW5kZXhdLCB2YWx1ZSkpIHsKICAgICAgICAgICAgICByZXR1cm4gaW5kZXg7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8udW5pcWAgZXhjZXB0IHRoYXQgaXQncyBkZXNpZ25lZCBhbmQgb3B0aW1pemVkCiAgICAgICAgICogZm9yIHNvcnRlZCBhcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBkdXBsaWNhdGUgZnJlZSBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5zb3J0ZWRVbmlxKFsxLCAxLCAyXSk7CiAgICAgICAgICogLy8gPT4gWzEsIDJdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc29ydGVkVW5pcShhcnJheSkgewogICAgICAgICAgcmV0dXJuIChhcnJheSAmJiBhcnJheS5sZW5ndGgpCiAgICAgICAgICAgID8gYmFzZVNvcnRlZFVuaXEoYXJyYXkpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnVuaXFCeWAgZXhjZXB0IHRoYXQgaXQncyBkZXNpZ25lZCBhbmQgb3B0aW1pemVkCiAgICAgICAgICogZm9yIHNvcnRlZCBhcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWVdIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGR1cGxpY2F0ZSBmcmVlIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNvcnRlZFVuaXFCeShbMS4xLCAxLjIsIDIuMywgMi40XSwgTWF0aC5mbG9vcik7CiAgICAgICAgICogLy8gPT4gWzEuMSwgMi4zXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNvcnRlZFVuaXFCeShhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VTb3J0ZWRVbmlxKGFycmF5LCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMikpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIGFsbCBidXQgdGhlIGZpcnN0IGVsZW1lbnQgb2YgYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHNsaWNlIG9mIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udGFpbChbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IFsyLCAzXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRhaWwoYXJyYXkpIHsKICAgICAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgICAgIHJldHVybiBsZW5ndGggPyBiYXNlU2xpY2UoYXJyYXksIDEsIGxlbmd0aCkgOiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBzbGljZSBvZiBgYXJyYXlgIHdpdGggYG5gIGVsZW1lbnRzIHRha2VuIGZyb20gdGhlIGJlZ2lubmluZy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW249MV0gVGhlIG51bWJlciBvZiBlbGVtZW50cyB0byB0YWtlLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBzbGljZSBvZiBgYXJyYXlgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRha2UoWzEsIDIsIDNdKTsKICAgICAgICAgKiAvLyA9PiBbMV0KICAgICAgICAgKgogICAgICAgICAqIF8udGFrZShbMSwgMiwgM10sIDIpOwogICAgICAgICAqIC8vID0+IFsxLCAyXQogICAgICAgICAqCiAgICAgICAgICogXy50YWtlKFsxLCAyLCAzXSwgNSk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICoKICAgICAgICAgKiBfLnRha2UoWzEsIDIsIDNdLCAwKTsKICAgICAgICAgKiAvLyA9PiBbXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRha2UoYXJyYXksIG4sIGd1YXJkKSB7CiAgICAgICAgICBpZiAoIShhcnJheSAmJiBhcnJheS5sZW5ndGgpKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIG4gPSAoZ3VhcmQgfHwgbiA9PT0gdW5kZWZpbmVkJDEpID8gMSA6IHRvSW50ZWdlcihuKTsKICAgICAgICAgIHJldHVybiBiYXNlU2xpY2UoYXJyYXksIDAsIG4gPCAwID8gMCA6IG4pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIHNsaWNlIG9mIGBhcnJheWAgd2l0aCBgbmAgZWxlbWVudHMgdGFrZW4gZnJvbSB0aGUgZW5kLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbj0xXSBUaGUgbnVtYmVyIG9mIGVsZW1lbnRzIHRvIHRha2UuCiAgICAgICAgICogQHBhcmFtLSB7T2JqZWN0fSBbZ3VhcmRdIEVuYWJsZXMgdXNlIGFzIGFuIGl0ZXJhdGVlIGZvciBtZXRob2RzIGxpa2UgYF8ubWFwYC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHNsaWNlIG9mIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udGFrZVJpZ2h0KFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gWzNdCiAgICAgICAgICoKICAgICAgICAgKiBfLnRha2VSaWdodChbMSwgMiwgM10sIDIpOwogICAgICAgICAqIC8vID0+IFsyLCAzXQogICAgICAgICAqCiAgICAgICAgICogXy50YWtlUmlnaHQoWzEsIDIsIDNdLCA1KTsKICAgICAgICAgKiAvLyA9PiBbMSwgMiwgM10KICAgICAgICAgKgogICAgICAgICAqIF8udGFrZVJpZ2h0KFsxLCAyLCAzXSwgMCk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0YWtlUmlnaHQoYXJyYXksIG4sIGd1YXJkKSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgICAgICBpZiAoIWxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICB9CiAgICAgICAgICBuID0gKGd1YXJkIHx8IG4gPT09IHVuZGVmaW5lZCQxKSA/IDEgOiB0b0ludGVnZXIobik7CiAgICAgICAgICBuID0gbGVuZ3RoIC0gbjsKICAgICAgICAgIHJldHVybiBiYXNlU2xpY2UoYXJyYXksIG4gPCAwID8gMCA6IG4sIGxlbmd0aCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgc2xpY2Ugb2YgYGFycmF5YCB3aXRoIGVsZW1lbnRzIHRha2VuIGZyb20gdGhlIGVuZC4gRWxlbWVudHMgYXJlCiAgICAgICAgICogdGFrZW4gdW50aWwgYHByZWRpY2F0ZWAgcmV0dXJucyBmYWxzZXkuIFRoZSBwcmVkaWNhdGUgaXMgaW52b2tlZCB3aXRoCiAgICAgICAgICogdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGluZGV4LCBhcnJheSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW3ByZWRpY2F0ZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc2xpY2Ugb2YgYGFycmF5YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gWwogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgICdhY3RpdmUnOiBmYWxzZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdwZWJibGVzJywgJ2FjdGl2ZSc6IGZhbHNlIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogXy50YWtlUmlnaHRXaGlsZSh1c2VycywgZnVuY3Rpb24obykgeyByZXR1cm4gIW8uYWN0aXZlOyB9KTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ2ZyZWQnLCAncGViYmxlcyddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8udGFrZVJpZ2h0V2hpbGUodXNlcnMsIHsgJ3VzZXInOiAncGViYmxlcycsICdhY3RpdmUnOiBmYWxzZSB9KTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ3BlYmJsZXMnXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8udGFrZVJpZ2h0V2hpbGUodXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ2ZyZWQnLCAncGViYmxlcyddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnRha2VSaWdodFdoaWxlKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0YWtlUmlnaHRXaGlsZShhcnJheSwgcHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlV2hpbGUoYXJyYXksIGdldEl0ZXJhdGVlKHByZWRpY2F0ZSwgMyksIGZhbHNlLCB0cnVlKQogICAgICAgICAgICA6IFtdOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIHNsaWNlIG9mIGBhcnJheWAgd2l0aCBlbGVtZW50cyB0YWtlbiBmcm9tIHRoZSBiZWdpbm5pbmcuIEVsZW1lbnRzCiAgICAgICAgICogYXJlIHRha2VuIHVudGlsIGBwcmVkaWNhdGVgIHJldHVybnMgZmFsc2V5LiBUaGUgcHJlZGljYXRlIGlzIGludm9rZWQgd2l0aAogICAgICAgICAqIHRocmVlIGFyZ3VtZW50czogKHZhbHVlLCBpbmRleCwgYXJyYXkpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHNsaWNlIG9mIGBhcnJheWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhY3RpdmUnOiBmYWxzZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWN0aXZlJzogdHJ1ZSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8udGFrZVdoaWxlKHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiAhby5hY3RpdmU7IH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5JywgJ2ZyZWQnXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnRha2VXaGlsZSh1c2VycywgeyAndXNlcic6ICdiYXJuZXknLCAnYWN0aXZlJzogZmFsc2UgfSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydiYXJuZXknXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8udGFrZVdoaWxlKHVzZXJzLCBbJ2FjdGl2ZScsIGZhbHNlXSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydiYXJuZXknLCAnZnJlZCddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnRha2VXaGlsZSh1c2VycywgJ2FjdGl2ZScpOwogICAgICAgICAqIC8vID0+IFtdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdGFrZVdoaWxlKGFycmF5LCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VXaGlsZShhcnJheSwgZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSkKICAgICAgICAgICAgOiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgdW5pcXVlIHZhbHVlcywgaW4gb3JkZXIsIGZyb20gYWxsIGdpdmVuIGFycmF5cyB1c2luZwogICAgICAgICAqIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHsuLi5BcnJheX0gW2FycmF5c10gVGhlIGFycmF5cyB0byBpbnNwZWN0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIGNvbWJpbmVkIHZhbHVlcy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy51bmlvbihbMl0sIFsxLCAyXSk7CiAgICAgICAgICogLy8gPT4gWzIsIDFdCiAgICAgICAgICovCiAgICAgICAgdmFyIHVuaW9uID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICByZXR1cm4gYmFzZVVuaXEoYmFzZUZsYXR0ZW4oYXJyYXlzLCAxLCBpc0FycmF5TGlrZU9iamVjdCwgdHJ1ZSkpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnVuaW9uYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAgd2hpY2ggaXMKICAgICAgICAgKiBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgb2YgZWFjaCBgYXJyYXlzYCB0byBnZW5lcmF0ZSB0aGUgY3JpdGVyaW9uIGJ5CiAgICAgICAgICogd2hpY2ggdW5pcXVlbmVzcyBpcyBjb21wdXRlZC4gUmVzdWx0IHZhbHVlcyBhcmUgY2hvc2VuIGZyb20gdGhlIGZpcnN0CiAgICAgICAgICogYXJyYXkgaW4gd2hpY2ggdGhlIHZhbHVlIG9jY3Vycy4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ6CiAgICAgICAgICogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7Li4uQXJyYXl9IFthcnJheXNdIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgY29tYmluZWQgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnVuaW9uQnkoWzIuMV0sIFsxLjIsIDIuM10sIE1hdGguZmxvb3IpOwogICAgICAgICAqIC8vID0+IFsyLjEsIDEuMl0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8udW5pb25CeShbeyAneCc6IDEgfV0sIFt7ICd4JzogMiB9LCB7ICd4JzogMSB9XSwgJ3gnKTsKICAgICAgICAgKiAvLyA9PiBbeyAneCc6IDEgfSwgeyAneCc6IDIgfV0KICAgICAgICAgKi8KICAgICAgICB2YXIgdW5pb25CeSA9IGJhc2VSZXN0KGZ1bmN0aW9uKGFycmF5cykgewogICAgICAgICAgdmFyIGl0ZXJhdGVlID0gbGFzdChhcnJheXMpOwogICAgICAgICAgaWYgKGlzQXJyYXlMaWtlT2JqZWN0KGl0ZXJhdGVlKSkgewogICAgICAgICAgICBpdGVyYXRlZSA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VVbmlxKGJhc2VGbGF0dGVuKGFycmF5cywgMSwgaXNBcnJheUxpa2VPYmplY3QsIHRydWUpLCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMikpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnVuaW9uYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjb21wYXJhdG9yYCB3aGljaAogICAgICAgICAqIGlzIGludm9rZWQgdG8gY29tcGFyZSBlbGVtZW50cyBvZiBgYXJyYXlzYC4gUmVzdWx0IHZhbHVlcyBhcmUgY2hvc2VuIGZyb20KICAgICAgICAgKiB0aGUgZmlyc3QgYXJyYXkgaW4gd2hpY2ggdGhlIHZhbHVlIG9jY3Vycy4gVGhlIGNvbXBhcmF0b3IgaXMgaW52b2tlZAogICAgICAgICAqIHdpdGggdHdvIGFyZ3VtZW50czogKGFyclZhbCwgb3RoVmFsKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7Li4uQXJyYXl9IFthcnJheXNdIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBjb21iaW5lZCB2YWx1ZXMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3RzID0gW3sgJ3gnOiAxLCAneSc6IDIgfSwgeyAneCc6IDIsICd5JzogMSB9XTsKICAgICAgICAgKiB2YXIgb3RoZXJzID0gW3sgJ3gnOiAxLCAneSc6IDEgfSwgeyAneCc6IDEsICd5JzogMiB9XTsKICAgICAgICAgKgogICAgICAgICAqIF8udW5pb25XaXRoKG9iamVjdHMsIG90aGVycywgXy5pc0VxdWFsKTsKICAgICAgICAgKiAvLyA9PiBbeyAneCc6IDEsICd5JzogMiB9LCB7ICd4JzogMiwgJ3knOiAxIH0sIHsgJ3gnOiAxLCAneSc6IDEgfV0KICAgICAgICAgKi8KICAgICAgICB2YXIgdW5pb25XaXRoID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICB2YXIgY29tcGFyYXRvciA9IGxhc3QoYXJyYXlzKTsKICAgICAgICAgIGNvbXBhcmF0b3IgPSB0eXBlb2YgY29tcGFyYXRvciA9PSAnZnVuY3Rpb24nID8gY29tcGFyYXRvciA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgcmV0dXJuIGJhc2VVbmlxKGJhc2VGbGF0dGVuKGFycmF5cywgMSwgaXNBcnJheUxpa2VPYmplY3QsIHRydWUpLCB1bmRlZmluZWQkMSwgY29tcGFyYXRvcik7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBkdXBsaWNhdGUtZnJlZSB2ZXJzaW9uIG9mIGFuIGFycmF5LCB1c2luZwogICAgICAgICAqIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLCBpbiB3aGljaCBvbmx5IHRoZSBmaXJzdCBvY2N1cnJlbmNlIG9mIGVhY2ggZWxlbWVudAogICAgICAgICAqIGlzIGtlcHQuIFRoZSBvcmRlciBvZiByZXN1bHQgdmFsdWVzIGlzIGRldGVybWluZWQgYnkgdGhlIG9yZGVyIHRoZXkgb2NjdXIKICAgICAgICAgKiBpbiB0aGUgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBkdXBsaWNhdGUgZnJlZSBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy51bmlxKFsyLCAxLCAyXSk7CiAgICAgICAgICogLy8gPT4gWzIsIDFdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdW5pcShhcnJheSkgewogICAgICAgICAgcmV0dXJuIChhcnJheSAmJiBhcnJheS5sZW5ndGgpID8gYmFzZVVuaXEoYXJyYXkpIDogW107CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnVuaXFgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGl0ZXJhdGVlYCB3aGljaCBpcwogICAgICAgICAqIGludm9rZWQgZm9yIGVhY2ggZWxlbWVudCBpbiBgYXJyYXlgIHRvIGdlbmVyYXRlIHRoZSBjcml0ZXJpb24gYnkgd2hpY2gKICAgICAgICAgKiB1bmlxdWVuZXNzIGlzIGNvbXB1dGVkLiBUaGUgb3JkZXIgb2YgcmVzdWx0IHZhbHVlcyBpcyBkZXRlcm1pbmVkIGJ5IHRoZQogICAgICAgICAqIG9yZGVyIHRoZXkgb2NjdXIgaW4gdGhlIGFycmF5LiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDoKICAgICAgICAgKiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGR1cGxpY2F0ZSBmcmVlIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnVuaXFCeShbMi4xLCAxLjIsIDIuM10sIE1hdGguZmxvb3IpOwogICAgICAgICAqIC8vID0+IFsyLjEsIDEuMl0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8udW5pcUJ5KFt7ICd4JzogMSB9LCB7ICd4JzogMiB9LCB7ICd4JzogMSB9XSwgJ3gnKTsKICAgICAgICAgKiAvLyA9PiBbeyAneCc6IDEgfSwgeyAneCc6IDIgfV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB1bmlxQnkoYXJyYXksIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkgPyBiYXNlVW5pcShhcnJheSwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpKSA6IFtdOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy51bmlxYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjb21wYXJhdG9yYCB3aGljaAogICAgICAgICAqIGlzIGludm9rZWQgdG8gY29tcGFyZSBlbGVtZW50cyBvZiBgYXJyYXlgLiBUaGUgb3JkZXIgb2YgcmVzdWx0IHZhbHVlcyBpcwogICAgICAgICAqIGRldGVybWluZWQgYnkgdGhlIG9yZGVyIHRoZXkgb2NjdXIgaW4gdGhlIGFycmF5LlRoZSBjb21wYXJhdG9yIGlzIGludm9rZWQKICAgICAgICAgKiB3aXRoIHR3byBhcmd1bWVudHM6IChhcnJWYWwsIG90aFZhbCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBkdXBsaWNhdGUgZnJlZSBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAneCc6IDEsICd5JzogMiB9LCB7ICd4JzogMiwgJ3knOiAxIH0sIHsgJ3gnOiAxLCAneSc6IDIgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLnVuaXFXaXRoKG9iamVjdHMsIF8uaXNFcXVhbCk7CiAgICAgICAgICogLy8gPT4gW3sgJ3gnOiAxLCAneSc6IDIgfSwgeyAneCc6IDIsICd5JzogMSB9XQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVuaXFXaXRoKGFycmF5LCBjb21wYXJhdG9yKSB7CiAgICAgICAgICBjb21wYXJhdG9yID0gdHlwZW9mIGNvbXBhcmF0b3IgPT0gJ2Z1bmN0aW9uJyA/IGNvbXBhcmF0b3IgOiB1bmRlZmluZWQkMTsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKSA/IGJhc2VVbmlxKGFycmF5LCB1bmRlZmluZWQkMSwgY29tcGFyYXRvcikgOiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uemlwYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGFuIGFycmF5IG9mIGdyb3VwZWQKICAgICAgICAgKiBlbGVtZW50cyBhbmQgY3JlYXRlcyBhbiBhcnJheSByZWdyb3VwaW5nIHRoZSBlbGVtZW50cyB0byB0aGVpciBwcmUtemlwCiAgICAgICAgICogY29uZmlndXJhdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAxLjIuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSBvZiBncm91cGVkIGVsZW1lbnRzIHRvIHByb2Nlc3MuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgcmVncm91cGVkIGVsZW1lbnRzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgemlwcGVkID0gXy56aXAoWydhJywgJ2InXSwgWzEsIDJdLCBbdHJ1ZSwgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiBbWydhJywgMSwgdHJ1ZV0sIFsnYicsIDIsIGZhbHNlXV0KICAgICAgICAgKgogICAgICAgICAqIF8udW56aXAoemlwcGVkKTsKICAgICAgICAgKiAvLyA9PiBbWydhJywgJ2InXSwgWzEsIDJdLCBbdHJ1ZSwgZmFsc2VdXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVuemlwKGFycmF5KSB7CiAgICAgICAgICBpZiAoIShhcnJheSAmJiBhcnJheS5sZW5ndGgpKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBsZW5ndGggPSAwOwogICAgICAgICAgYXJyYXkgPSBhcnJheUZpbHRlcihhcnJheSwgZnVuY3Rpb24oZ3JvdXApIHsKICAgICAgICAgICAgaWYgKGlzQXJyYXlMaWtlT2JqZWN0KGdyb3VwKSkgewogICAgICAgICAgICAgIGxlbmd0aCA9IG5hdGl2ZU1heChncm91cC5sZW5ndGgsIGxlbmd0aCk7CiAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIGJhc2VUaW1lcyhsZW5ndGgsIGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgICAgIHJldHVybiBhcnJheU1hcChhcnJheSwgYmFzZVByb3BlcnR5KGluZGV4KSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8udW56aXBgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGl0ZXJhdGVlYCB0byBzcGVjaWZ5CiAgICAgICAgICogaG93IHJlZ3JvdXBlZCB2YWx1ZXMgc2hvdWxkIGJlIGNvbWJpbmVkLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIHRoZQogICAgICAgICAqIGVsZW1lbnRzIG9mIGVhY2ggZ3JvdXA6ICguLi5ncm91cCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy44LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgb2YgZ3JvdXBlZCBlbGVtZW50cyB0byBwcm9jZXNzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gdG8gY29tYmluZQogICAgICAgICAqICByZWdyb3VwZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIHJlZ3JvdXBlZCBlbGVtZW50cy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHppcHBlZCA9IF8uemlwKFsxLCAyXSwgWzEwLCAyMF0sIFsxMDAsIDIwMF0pOwogICAgICAgICAqIC8vID0+IFtbMSwgMTAsIDEwMF0sIFsyLCAyMCwgMjAwXV0KICAgICAgICAgKgogICAgICAgICAqIF8udW56aXBXaXRoKHppcHBlZCwgXy5hZGQpOwogICAgICAgICAqIC8vID0+IFszLCAzMCwgMzAwXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVuemlwV2l0aChhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIGlmICghKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHJlc3VsdCA9IHVuemlwKGFycmF5KTsKICAgICAgICAgIGlmIChpdGVyYXRlZSA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYXJyYXlNYXAocmVzdWx0LCBmdW5jdGlvbihncm91cCkgewogICAgICAgICAgICByZXR1cm4gYXBwbHkoaXRlcmF0ZWUsIHVuZGVmaW5lZCQxLCBncm91cCk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgZXhjbHVkaW5nIGFsbCBnaXZlbiB2YWx1ZXMgdXNpbmcKICAgICAgICAgKiBbYFNhbWVWYWx1ZVplcm9gXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1zYW1ldmFsdWV6ZXJvKQogICAgICAgICAqIGZvciBlcXVhbGl0eSBjb21wYXJpc29ucy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBVbmxpa2UgYF8ucHVsbGAsIHRoaXMgbWV0aG9kIHJldHVybnMgYSBuZXcgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IFt2YWx1ZXNdIFRoZSB2YWx1ZXMgdG8gZXhjbHVkZS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBmaWx0ZXJlZCB2YWx1ZXMuCiAgICAgICAgICogQHNlZSBfLmRpZmZlcmVuY2UsIF8ueG9yCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ud2l0aG91dChbMiwgMSwgMiwgM10sIDEsIDIpOwogICAgICAgICAqIC8vID0+IFszXQogICAgICAgICAqLwogICAgICAgIHZhciB3aXRob3V0ID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXksIHZhbHVlcykgewogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlT2JqZWN0KGFycmF5KQogICAgICAgICAgICA/IGJhc2VEaWZmZXJlbmNlKGFycmF5LCB2YWx1ZXMpCiAgICAgICAgICAgIDogW107CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgdW5pcXVlIHZhbHVlcyB0aGF0IGlzIHRoZQogICAgICAgICAqIFtzeW1tZXRyaWMgZGlmZmVyZW5jZV0oaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvU3ltbWV0cmljX2RpZmZlcmVuY2UpCiAgICAgICAgICogb2YgdGhlIGdpdmVuIGFycmF5cy4gVGhlIG9yZGVyIG9mIHJlc3VsdCB2YWx1ZXMgaXMgZGV0ZXJtaW5lZCBieSB0aGUgb3JkZXIKICAgICAgICAgKiB0aGV5IG9jY3VyIGluIHRoZSBhcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMi40LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbYXJyYXlzXSBUaGUgYXJyYXlzIHRvIGluc3BlY3QuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgZmlsdGVyZWQgdmFsdWVzLgogICAgICAgICAqIEBzZWUgXy5kaWZmZXJlbmNlLCBfLndpdGhvdXQKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy54b3IoWzIsIDFdLCBbMiwgM10pOwogICAgICAgICAqIC8vID0+IFsxLCAzXQogICAgICAgICAqLwogICAgICAgIHZhciB4b3IgPSBiYXNlUmVzdChmdW5jdGlvbihhcnJheXMpIHsKICAgICAgICAgIHJldHVybiBiYXNlWG9yKGFycmF5RmlsdGVyKGFycmF5cywgaXNBcnJheUxpa2VPYmplY3QpKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy54b3JgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGl0ZXJhdGVlYCB3aGljaCBpcwogICAgICAgICAqIGludm9rZWQgZm9yIGVhY2ggZWxlbWVudCBvZiBlYWNoIGBhcnJheXNgIHRvIGdlbmVyYXRlIHRoZSBjcml0ZXJpb24gYnkKICAgICAgICAgKiB3aGljaCBieSB3aGljaCB0aGV5J3JlIGNvbXBhcmVkLiBUaGUgb3JkZXIgb2YgcmVzdWx0IHZhbHVlcyBpcyBkZXRlcm1pbmVkCiAgICAgICAgICogYnkgdGhlIG9yZGVyIHRoZXkgb2NjdXIgaW4gdGhlIGFycmF5cy4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUKICAgICAgICAgKiBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7Li4uQXJyYXl9IFthcnJheXNdIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgYXJyYXkgb2YgZmlsdGVyZWQgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnhvckJ5KFsyLjEsIDEuMl0sIFsyLjMsIDMuNF0sIE1hdGguZmxvb3IpOwogICAgICAgICAqIC8vID0+IFsxLjIsIDMuNF0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8ueG9yQnkoW3sgJ3gnOiAxIH1dLCBbeyAneCc6IDIgfSwgeyAneCc6IDEgfV0sICd4Jyk7CiAgICAgICAgICogLy8gPT4gW3sgJ3gnOiAyIH1dCiAgICAgICAgICovCiAgICAgICAgdmFyIHhvckJ5ID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICB2YXIgaXRlcmF0ZWUgPSBsYXN0KGFycmF5cyk7CiAgICAgICAgICBpZiAoaXNBcnJheUxpa2VPYmplY3QoaXRlcmF0ZWUpKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYmFzZVhvcihhcnJheUZpbHRlcihhcnJheXMsIGlzQXJyYXlMaWtlT2JqZWN0KSwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy54b3JgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGNvbXBhcmF0b3JgIHdoaWNoIGlzCiAgICAgICAgICogaW52b2tlZCB0byBjb21wYXJlIGVsZW1lbnRzIG9mIGBhcnJheXNgLiBUaGUgb3JkZXIgb2YgcmVzdWx0IHZhbHVlcyBpcwogICAgICAgICAqIGRldGVybWluZWQgYnkgdGhlIG9yZGVyIHRoZXkgb2NjdXIgaW4gdGhlIGFycmF5cy4gVGhlIGNvbXBhcmF0b3IgaXMgaW52b2tlZAogICAgICAgICAqIHdpdGggdHdvIGFyZ3VtZW50czogKGFyclZhbCwgb3RoVmFsKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7Li4uQXJyYXl9IFthcnJheXNdIFRoZSBhcnJheXMgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBmaWx0ZXJlZCB2YWx1ZXMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3RzID0gW3sgJ3gnOiAxLCAneSc6IDIgfSwgeyAneCc6IDIsICd5JzogMSB9XTsKICAgICAgICAgKiB2YXIgb3RoZXJzID0gW3sgJ3gnOiAxLCAneSc6IDEgfSwgeyAneCc6IDEsICd5JzogMiB9XTsKICAgICAgICAgKgogICAgICAgICAqIF8ueG9yV2l0aChvYmplY3RzLCBvdGhlcnMsIF8uaXNFcXVhbCk7CiAgICAgICAgICogLy8gPT4gW3sgJ3gnOiAyLCAneSc6IDEgfSwgeyAneCc6IDEsICd5JzogMSB9XQogICAgICAgICAqLwogICAgICAgIHZhciB4b3JXaXRoID0gYmFzZVJlc3QoZnVuY3Rpb24oYXJyYXlzKSB7CiAgICAgICAgICB2YXIgY29tcGFyYXRvciA9IGxhc3QoYXJyYXlzKTsKICAgICAgICAgIGNvbXBhcmF0b3IgPSB0eXBlb2YgY29tcGFyYXRvciA9PSAnZnVuY3Rpb24nID8gY29tcGFyYXRvciA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgcmV0dXJuIGJhc2VYb3IoYXJyYXlGaWx0ZXIoYXJyYXlzLCBpc0FycmF5TGlrZU9iamVjdCksIHVuZGVmaW5lZCQxLCBjb21wYXJhdG9yKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBncm91cGVkIGVsZW1lbnRzLCB0aGUgZmlyc3Qgb2Ygd2hpY2ggY29udGFpbnMgdGhlCiAgICAgICAgICogZmlyc3QgZWxlbWVudHMgb2YgdGhlIGdpdmVuIGFycmF5cywgdGhlIHNlY29uZCBvZiB3aGljaCBjb250YWlucyB0aGUKICAgICAgICAgKiBzZWNvbmQgZWxlbWVudHMgb2YgdGhlIGdpdmVuIGFycmF5cywgYW5kIHNvIG9uLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHsuLi5BcnJheX0gW2FycmF5c10gVGhlIGFycmF5cyB0byBwcm9jZXNzLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIGdyb3VwZWQgZWxlbWVudHMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uemlwKFsnYScsICdiJ10sIFsxLCAyXSwgW3RydWUsIGZhbHNlXSk7CiAgICAgICAgICogLy8gPT4gW1snYScsIDEsIHRydWVdLCBbJ2InLCAyLCBmYWxzZV1dCiAgICAgICAgICovCiAgICAgICAgdmFyIHppcCA9IGJhc2VSZXN0KHVuemlwKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5mcm9tUGFpcnNgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgdHdvIGFycmF5cywKICAgICAgICAgKiBvbmUgb2YgcHJvcGVydHkgaWRlbnRpZmllcnMgYW5kIG9uZSBvZiBjb3JyZXNwb25kaW5nIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFtwcm9wcz1bXV0gVGhlIHByb3BlcnR5IGlkZW50aWZpZXJzLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IFt2YWx1ZXM9W11dIFRoZSBwcm9wZXJ0eSB2YWx1ZXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV3IG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy56aXBPYmplY3QoWydhJywgJ2InXSwgWzEsIDJdKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB6aXBPYmplY3QocHJvcHMsIHZhbHVlcykgewogICAgICAgICAgcmV0dXJuIGJhc2VaaXBPYmplY3QocHJvcHMgfHwgW10sIHZhbHVlcyB8fCBbXSwgYXNzaWduVmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy56aXBPYmplY3RgIGV4Y2VwdCB0aGF0IGl0IHN1cHBvcnRzIHByb3BlcnR5IHBhdGhzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW3Byb3BzPVtdXSBUaGUgcHJvcGVydHkgaWRlbnRpZmllcnMuCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gW3ZhbHVlcz1bXV0gVGhlIHByb3BlcnR5IHZhbHVlcy4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgb2JqZWN0LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnppcE9iamVjdERlZXAoWydhLmJbMF0uYycsICdhLmJbMV0uZCddLCBbMSwgMl0pOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiB7ICdiJzogW3sgJ2MnOiAxIH0sIHsgJ2QnOiAyIH1dIH0gfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHppcE9iamVjdERlZXAocHJvcHMsIHZhbHVlcykgewogICAgICAgICAgcmV0dXJuIGJhc2VaaXBPYmplY3QocHJvcHMgfHwgW10sIHZhbHVlcyB8fCBbXSwgYmFzZVNldCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnppcGAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgIHRvIHNwZWNpZnkKICAgICAgICAgKiBob3cgZ3JvdXBlZCB2YWx1ZXMgc2hvdWxkIGJlIGNvbWJpbmVkLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIHRoZQogICAgICAgICAqIGVsZW1lbnRzIG9mIGVhY2ggZ3JvdXA6ICguLi5ncm91cCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy44LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbYXJyYXlzXSBUaGUgYXJyYXlzIHRvIHByb2Nlc3MuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiB0byBjb21iaW5lCiAgICAgICAgICogIGdyb3VwZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGFycmF5IG9mIGdyb3VwZWQgZWxlbWVudHMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uemlwV2l0aChbMSwgMl0sIFsxMCwgMjBdLCBbMTAwLCAyMDBdLCBmdW5jdGlvbihhLCBiLCBjKSB7CiAgICAgICAgICogICByZXR1cm4gYSArIGIgKyBjOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IFsxMTEsIDIyMl0KICAgICAgICAgKi8KICAgICAgICB2YXIgemlwV2l0aCA9IGJhc2VSZXN0KGZ1bmN0aW9uKGFycmF5cykgewogICAgICAgICAgdmFyIGxlbmd0aCA9IGFycmF5cy5sZW5ndGgsCiAgICAgICAgICAgICAgaXRlcmF0ZWUgPSBsZW5ndGggPiAxID8gYXJyYXlzW2xlbmd0aCAtIDFdIDogdW5kZWZpbmVkJDE7CgogICAgICAgICAgaXRlcmF0ZWUgPSB0eXBlb2YgaXRlcmF0ZWUgPT0gJ2Z1bmN0aW9uJyA/IChhcnJheXMucG9wKCksIGl0ZXJhdGVlKSA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgcmV0dXJuIHVuemlwV2l0aChhcnJheXMsIGl0ZXJhdGVlKTsKICAgICAgICB9KTsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgYGxvZGFzaGAgd3JhcHBlciBpbnN0YW5jZSB0aGF0IHdyYXBzIGB2YWx1ZWAgd2l0aCBleHBsaWNpdCBtZXRob2QKICAgICAgICAgKiBjaGFpbiBzZXF1ZW5jZXMgZW5hYmxlZC4gVGhlIHJlc3VsdCBvZiBzdWNoIHNlcXVlbmNlcyBtdXN0IGJlIHVud3JhcHBlZAogICAgICAgICAqIHdpdGggYF8jdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDEuMy4wCiAgICAgICAgICogQGNhdGVnb3J5IFNlcQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHdyYXAuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV3IGBsb2Rhc2hgIHdyYXBwZXIgaW5zdGFuY2UuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhZ2UnOiAzNiB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FnZSc6IDQwIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWdlJzogMSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIHZhciB5b3VuZ2VzdCA9IF8KICAgICAgICAgKiAgIC5jaGFpbih1c2VycykKICAgICAgICAgKiAgIC5zb3J0QnkoJ2FnZScpCiAgICAgICAgICogICAubWFwKGZ1bmN0aW9uKG8pIHsKICAgICAgICAgKiAgICAgcmV0dXJuIG8udXNlciArICcgaXMgJyArIG8uYWdlOwogICAgICAgICAqICAgfSkKICAgICAgICAgKiAgIC5oZWFkKCkKICAgICAgICAgKiAgIC52YWx1ZSgpOwogICAgICAgICAqIC8vID0+ICdwZWJibGVzIGlzIDEnCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2hhaW4odmFsdWUpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBsb2Rhc2godmFsdWUpOwogICAgICAgICAgcmVzdWx0Ll9fY2hhaW5fXyA9IHRydWU7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaW52b2tlcyBgaW50ZXJjZXB0b3JgIGFuZCByZXR1cm5zIGB2YWx1ZWAuIFRoZSBpbnRlcmNlcHRvcgogICAgICAgICAqIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ7ICh2YWx1ZSkuIFRoZSBwdXJwb3NlIG9mIHRoaXMgbWV0aG9kIGlzIHRvCiAgICAgICAgICogInRhcCBpbnRvIiBhIG1ldGhvZCBjaGFpbiBzZXF1ZW5jZSBpbiBvcmRlciB0byBtb2RpZnkgaW50ZXJtZWRpYXRlIHJlc3VsdHMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU2VxCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcHJvdmlkZSB0byBgaW50ZXJjZXB0b3JgLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGludGVyY2VwdG9yIFRoZSBmdW5jdGlvbiB0byBpbnZva2UuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgYHZhbHVlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXyhbMSwgMiwgM10pCiAgICAgICAgICogIC50YXAoZnVuY3Rpb24oYXJyYXkpIHsKICAgICAgICAgKiAgICAvLyBNdXRhdGUgaW5wdXQgYXJyYXkuCiAgICAgICAgICogICAgYXJyYXkucG9wKCk7CiAgICAgICAgICogIH0pCiAgICAgICAgICogIC5yZXZlcnNlKCkKICAgICAgICAgKiAgLnZhbHVlKCk7CiAgICAgICAgICogLy8gPT4gWzIsIDFdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdGFwKHZhbHVlLCBpbnRlcmNlcHRvcikgewogICAgICAgICAgaW50ZXJjZXB0b3IodmFsdWUpOwogICAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy50YXBgIGV4Y2VwdCB0aGF0IGl0IHJldHVybnMgdGhlIHJlc3VsdCBvZiBgaW50ZXJjZXB0b3JgLgogICAgICAgICAqIFRoZSBwdXJwb3NlIG9mIHRoaXMgbWV0aG9kIGlzIHRvICJwYXNzIHRocnUiIHZhbHVlcyByZXBsYWNpbmcgaW50ZXJtZWRpYXRlCiAgICAgICAgICogcmVzdWx0cyBpbiBhIG1ldGhvZCBjaGFpbiBzZXF1ZW5jZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTZXEKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBwcm92aWRlIHRvIGBpbnRlcmNlcHRvcmAuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaW50ZXJjZXB0b3IgVGhlIGZ1bmN0aW9uIHRvIGludm9rZS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgcmVzdWx0IG9mIGBpbnRlcmNlcHRvcmAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8oJyAgYWJjICAnKQogICAgICAgICAqICAuY2hhaW4oKQogICAgICAgICAqICAudHJpbSgpCiAgICAgICAgICogIC50aHJ1KGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICogICAgcmV0dXJuIFt2YWx1ZV07CiAgICAgICAgICogIH0pCiAgICAgICAgICogIC52YWx1ZSgpOwogICAgICAgICAqIC8vID0+IFsnYWJjJ10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0aHJ1KHZhbHVlLCBpbnRlcmNlcHRvcikgewogICAgICAgICAgcmV0dXJuIGludGVyY2VwdG9yKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIHRoZSB3cmFwcGVyIHZlcnNpb24gb2YgYF8uYXRgLgogICAgICAgICAqCiAgICAgICAgICogQG5hbWUgYXQKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAxLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTZXEKICAgICAgICAgKiBAcGFyYW0gey4uLihzdHJpbmd8c3RyaW5nW10pfSBbcGF0aHNdIFRoZSBwcm9wZXJ0eSBwYXRocyB0byBwaWNrLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBgbG9kYXNoYCB3cmFwcGVyIGluc3RhbmNlLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IFt7ICdiJzogeyAnYyc6IDMgfSB9LCA0XSB9OwogICAgICAgICAqCiAgICAgICAgICogXyhvYmplY3QpLmF0KFsnYVswXS5iLmMnLCAnYVsxXSddKS52YWx1ZSgpOwogICAgICAgICAqIC8vID0+IFszLCA0XQogICAgICAgICAqLwogICAgICAgIHZhciB3cmFwcGVyQXQgPSBmbGF0UmVzdChmdW5jdGlvbihwYXRocykgewogICAgICAgICAgdmFyIGxlbmd0aCA9IHBhdGhzLmxlbmd0aCwKICAgICAgICAgICAgICBzdGFydCA9IGxlbmd0aCA/IHBhdGhzWzBdIDogMCwKICAgICAgICAgICAgICB2YWx1ZSA9IHRoaXMuX193cmFwcGVkX18sCiAgICAgICAgICAgICAgaW50ZXJjZXB0b3IgPSBmdW5jdGlvbihvYmplY3QpIHsgcmV0dXJuIGJhc2VBdChvYmplY3QsIHBhdGhzKTsgfTsKCiAgICAgICAgICBpZiAobGVuZ3RoID4gMSB8fCB0aGlzLl9fYWN0aW9uc19fLmxlbmd0aCB8fAogICAgICAgICAgICAgICEodmFsdWUgaW5zdGFuY2VvZiBMYXp5V3JhcHBlcikgfHwgIWlzSW5kZXgoc3RhcnQpKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnRocnUoaW50ZXJjZXB0b3IpOwogICAgICAgICAgfQogICAgICAgICAgdmFsdWUgPSB2YWx1ZS5zbGljZShzdGFydCwgK3N0YXJ0ICsgKGxlbmd0aCA/IDEgOiAwKSk7CiAgICAgICAgICB2YWx1ZS5fX2FjdGlvbnNfXy5wdXNoKHsKICAgICAgICAgICAgJ2Z1bmMnOiB0aHJ1LAogICAgICAgICAgICAnYXJncyc6IFtpbnRlcmNlcHRvcl0sCiAgICAgICAgICAgICd0aGlzQXJnJzogdW5kZWZpbmVkJDEKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIG5ldyBMb2Rhc2hXcmFwcGVyKHZhbHVlLCB0aGlzLl9fY2hhaW5fXykudGhydShmdW5jdGlvbihhcnJheSkgewogICAgICAgICAgICBpZiAobGVuZ3RoICYmICFhcnJheS5sZW5ndGgpIHsKICAgICAgICAgICAgICBhcnJheS5wdXNoKHVuZGVmaW5lZCQxKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gYXJyYXk7CiAgICAgICAgICB9KTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGBsb2Rhc2hgIHdyYXBwZXIgaW5zdGFuY2Ugd2l0aCBleHBsaWNpdCBtZXRob2QgY2hhaW4gc2VxdWVuY2VzIGVuYWJsZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAbmFtZSBjaGFpbgogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IFNlcQogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBgbG9kYXNoYCB3cmFwcGVyIGluc3RhbmNlLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAnYWdlJzogNDAgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiAvLyBBIHNlcXVlbmNlIHdpdGhvdXQgZXhwbGljaXQgY2hhaW5pbmcuCiAgICAgICAgICogXyh1c2VycykuaGVhZCgpOwogICAgICAgICAqIC8vID0+IHsgJ3VzZXInOiAnYmFybmV5JywgJ2FnZSc6IDM2IH0KICAgICAgICAgKgogICAgICAgICAqIC8vIEEgc2VxdWVuY2Ugd2l0aCBleHBsaWNpdCBjaGFpbmluZy4KICAgICAgICAgKiBfKHVzZXJzKQogICAgICAgICAqICAgLmNoYWluKCkKICAgICAgICAgKiAgIC5oZWFkKCkKICAgICAgICAgKiAgIC5waWNrKCd1c2VyJykKICAgICAgICAgKiAgIC52YWx1ZSgpOwogICAgICAgICAqIC8vID0+IHsgJ3VzZXInOiAnYmFybmV5JyB9CiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gd3JhcHBlckNoYWluKCkgewogICAgICAgICAgcmV0dXJuIGNoYWluKHRoaXMpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRXhlY3V0ZXMgdGhlIGNoYWluIHNlcXVlbmNlIGFuZCByZXR1cm5zIHRoZSB3cmFwcGVkIHJlc3VsdC4KICAgICAgICAgKgogICAgICAgICAqIEBuYW1lIGNvbW1pdAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMi4wCiAgICAgICAgICogQGNhdGVnb3J5IFNlcQogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBgbG9kYXNoYCB3cmFwcGVyIGluc3RhbmNlLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbMSwgMl07CiAgICAgICAgICogdmFyIHdyYXBwZWQgPSBfKGFycmF5KS5wdXNoKDMpOwogICAgICAgICAqCiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFsxLCAyXQogICAgICAgICAqCiAgICAgICAgICogd3JhcHBlZCA9IHdyYXBwZWQuY29tbWl0KCk7CiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFsxLCAyLCAzXQogICAgICAgICAqCiAgICAgICAgICogd3JhcHBlZC5sYXN0KCk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqCiAgICAgICAgICogY29uc29sZS5sb2coYXJyYXkpOwogICAgICAgICAqIC8vID0+IFsxLCAyLCAzXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHdyYXBwZXJDb21taXQoKSB7CiAgICAgICAgICByZXR1cm4gbmV3IExvZGFzaFdyYXBwZXIodGhpcy52YWx1ZSgpLCB0aGlzLl9fY2hhaW5fXyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBuZXh0IHZhbHVlIG9uIGEgd3JhcHBlZCBvYmplY3QgZm9sbG93aW5nIHRoZQogICAgICAgICAqIFtpdGVyYXRvciBwcm90b2NvbF0oaHR0cHM6Ly9tZG4uaW8vaXRlcmF0aW9uX3Byb3RvY29scyNpdGVyYXRvcikuCiAgICAgICAgICoKICAgICAgICAgKiBAbmFtZSBuZXh0CiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU2VxCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV4dCBpdGVyYXRvciB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHdyYXBwZWQgPSBfKFsxLCAyXSk7CiAgICAgICAgICoKICAgICAgICAgKiB3cmFwcGVkLm5leHQoKTsKICAgICAgICAgKiAvLyA9PiB7ICdkb25lJzogZmFsc2UsICd2YWx1ZSc6IDEgfQogICAgICAgICAqCiAgICAgICAgICogd3JhcHBlZC5uZXh0KCk7CiAgICAgICAgICogLy8gPT4geyAnZG9uZSc6IGZhbHNlLCAndmFsdWUnOiAyIH0KICAgICAgICAgKgogICAgICAgICAqIHdyYXBwZWQubmV4dCgpOwogICAgICAgICAqIC8vID0+IHsgJ2RvbmUnOiB0cnVlLCAndmFsdWUnOiB1bmRlZmluZWQgfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHdyYXBwZXJOZXh0KCkgewogICAgICAgICAgaWYgKHRoaXMuX192YWx1ZXNfXyA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgdGhpcy5fX3ZhbHVlc19fID0gdG9BcnJheSh0aGlzLnZhbHVlKCkpOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGRvbmUgPSB0aGlzLl9faW5kZXhfXyA+PSB0aGlzLl9fdmFsdWVzX18ubGVuZ3RoLAogICAgICAgICAgICAgIHZhbHVlID0gZG9uZSA/IHVuZGVmaW5lZCQxIDogdGhpcy5fX3ZhbHVlc19fW3RoaXMuX19pbmRleF9fKytdOwoKICAgICAgICAgIHJldHVybiB7ICdkb25lJzogZG9uZSwgJ3ZhbHVlJzogdmFsdWUgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEVuYWJsZXMgdGhlIHdyYXBwZXIgdG8gYmUgaXRlcmFibGUuCiAgICAgICAgICoKICAgICAgICAgKiBAbmFtZSBTeW1ib2wuaXRlcmF0b3IKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTZXEKICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSB3cmFwcGVyIG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHdyYXBwZWQgPSBfKFsxLCAyXSk7CiAgICAgICAgICoKICAgICAgICAgKiB3cmFwcGVkW1N5bWJvbC5pdGVyYXRvcl0oKSA9PT0gd3JhcHBlZDsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBBcnJheS5mcm9tKHdyYXBwZWQpOwogICAgICAgICAqIC8vID0+IFsxLCAyXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHdyYXBwZXJUb0l0ZXJhdG9yKCkgewogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgdGhlIGNoYWluIHNlcXVlbmNlIHBsYW50aW5nIGB2YWx1ZWAgYXMgdGhlIHdyYXBwZWQgdmFsdWUuCiAgICAgICAgICoKICAgICAgICAgKiBAbmFtZSBwbGFudAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMi4wCiAgICAgICAgICogQGNhdGVnb3J5IFNlcQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHBsYW50LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBgbG9kYXNoYCB3cmFwcGVyIGluc3RhbmNlLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBzcXVhcmUobikgewogICAgICAgICAqICAgcmV0dXJuIG4gKiBuOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciB3cmFwcGVkID0gXyhbMSwgMl0pLm1hcChzcXVhcmUpOwogICAgICAgICAqIHZhciBvdGhlciA9IHdyYXBwZWQucGxhbnQoWzMsIDRdKTsKICAgICAgICAgKgogICAgICAgICAqIG90aGVyLnZhbHVlKCk7CiAgICAgICAgICogLy8gPT4gWzksIDE2XQogICAgICAgICAqCiAgICAgICAgICogd3JhcHBlZC52YWx1ZSgpOwogICAgICAgICAqIC8vID0+IFsxLCA0XQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHdyYXBwZXJQbGFudCh2YWx1ZSkgewogICAgICAgICAgdmFyIHJlc3VsdCwKICAgICAgICAgICAgICBwYXJlbnQgPSB0aGlzOwoKICAgICAgICAgIHdoaWxlIChwYXJlbnQgaW5zdGFuY2VvZiBiYXNlTG9kYXNoKSB7CiAgICAgICAgICAgIHZhciBjbG9uZSA9IHdyYXBwZXJDbG9uZShwYXJlbnQpOwogICAgICAgICAgICBjbG9uZS5fX2luZGV4X18gPSAwOwogICAgICAgICAgICBjbG9uZS5fX3ZhbHVlc19fID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICAgIGlmIChyZXN1bHQpIHsKICAgICAgICAgICAgICBwcmV2aW91cy5fX3dyYXBwZWRfXyA9IGNsb25lOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHJlc3VsdCA9IGNsb25lOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBwcmV2aW91cyA9IGNsb25lOwogICAgICAgICAgICBwYXJlbnQgPSBwYXJlbnQuX193cmFwcGVkX187CiAgICAgICAgICB9CiAgICAgICAgICBwcmV2aW91cy5fX3dyYXBwZWRfXyA9IHZhbHVlOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIHRoZSB3cmFwcGVyIHZlcnNpb24gb2YgYF8ucmV2ZXJzZWAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyB0aGUgd3JhcHBlZCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBuYW1lIHJldmVyc2UKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBTZXEKICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgYGxvZGFzaGAgd3JhcHBlciBpbnN0YW5jZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gWzEsIDIsIDNdOwogICAgICAgICAqCiAgICAgICAgICogXyhhcnJheSkucmV2ZXJzZSgpLnZhbHVlKCkKICAgICAgICAgKiAvLyA9PiBbMywgMiwgMV0KICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5KTsKICAgICAgICAgKiAvLyA9PiBbMywgMiwgMV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB3cmFwcGVyUmV2ZXJzZSgpIHsKICAgICAgICAgIHZhciB2YWx1ZSA9IHRoaXMuX193cmFwcGVkX187CiAgICAgICAgICBpZiAodmFsdWUgaW5zdGFuY2VvZiBMYXp5V3JhcHBlcikgewogICAgICAgICAgICB2YXIgd3JhcHBlZCA9IHZhbHVlOwogICAgICAgICAgICBpZiAodGhpcy5fX2FjdGlvbnNfXy5sZW5ndGgpIHsKICAgICAgICAgICAgICB3cmFwcGVkID0gbmV3IExhenlXcmFwcGVyKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHdyYXBwZWQgPSB3cmFwcGVkLnJldmVyc2UoKTsKICAgICAgICAgICAgd3JhcHBlZC5fX2FjdGlvbnNfXy5wdXNoKHsKICAgICAgICAgICAgICAnZnVuYyc6IHRocnUsCiAgICAgICAgICAgICAgJ2FyZ3MnOiBbcmV2ZXJzZV0sCiAgICAgICAgICAgICAgJ3RoaXNBcmcnOiB1bmRlZmluZWQkMQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIG5ldyBMb2Rhc2hXcmFwcGVyKHdyYXBwZWQsIHRoaXMuX19jaGFpbl9fKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0aGlzLnRocnUocmV2ZXJzZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBFeGVjdXRlcyB0aGUgY2hhaW4gc2VxdWVuY2UgdG8gcmVzb2x2ZSB0aGUgdW53cmFwcGVkIHZhbHVlLgogICAgICAgICAqCiAgICAgICAgICogQG5hbWUgdmFsdWUKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBhbGlhcyB0b0pTT04sIHZhbHVlT2YKICAgICAgICAgKiBAY2F0ZWdvcnkgU2VxCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHJlc29sdmVkIHVud3JhcHBlZCB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXyhbMSwgMiwgM10pLnZhbHVlKCk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gd3JhcHBlclZhbHVlKCkgewogICAgICAgICAgcmV0dXJuIGJhc2VXcmFwcGVyVmFsdWUodGhpcy5fX3dyYXBwZWRfXywgdGhpcy5fX2FjdGlvbnNfXyk7CiAgICAgICAgfQoKICAgICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gb2JqZWN0IGNvbXBvc2VkIG9mIGtleXMgZ2VuZXJhdGVkIGZyb20gdGhlIHJlc3VsdHMgb2YgcnVubmluZwogICAgICAgICAqIGVhY2ggZWxlbWVudCBvZiBgY29sbGVjdGlvbmAgdGhydSBgaXRlcmF0ZWVgLiBUaGUgY29ycmVzcG9uZGluZyB2YWx1ZSBvZgogICAgICAgICAqIGVhY2gga2V5IGlzIHRoZSBudW1iZXIgb2YgdGltZXMgdGhlIGtleSB3YXMgcmV0dXJuZWQgYnkgYGl0ZXJhdGVlYC4gVGhlCiAgICAgICAgICogaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjUuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgdG8gdHJhbnNmb3JtIGtleXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY29tcG9zZWQgYWdncmVnYXRlIG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5jb3VudEJ5KFs2LjEsIDQuMiwgNi4zXSwgTWF0aC5mbG9vcik7CiAgICAgICAgICogLy8gPT4geyAnNCc6IDEsICc2JzogMiB9CiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmNvdW50QnkoWydvbmUnLCAndHdvJywgJ3RocmVlJ10sICdsZW5ndGgnKTsKICAgICAgICAgKiAvLyA9PiB7ICczJzogMiwgJzUnOiAxIH0KICAgICAgICAgKi8KICAgICAgICB2YXIgY291bnRCeSA9IGNyZWF0ZUFnZ3JlZ2F0b3IoZnVuY3Rpb24ocmVzdWx0LCB2YWx1ZSwga2V5KSB7CiAgICAgICAgICBpZiAoaGFzT3duUHJvcGVydHkuY2FsbChyZXN1bHQsIGtleSkpIHsKICAgICAgICAgICAgKytyZXN1bHRba2V5XTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGJhc2VBc3NpZ25WYWx1ZShyZXN1bHQsIGtleSwgMSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgcHJlZGljYXRlYCByZXR1cm5zIHRydXRoeSBmb3IgKiphbGwqKiBlbGVtZW50cyBvZiBgY29sbGVjdGlvbmAuCiAgICAgICAgICogSXRlcmF0aW9uIGlzIHN0b3BwZWQgb25jZSBgcHJlZGljYXRlYCByZXR1cm5zIGZhbHNleS4gVGhlIHByZWRpY2F0ZSBpcwogICAgICAgICAqIGludm9rZWQgd2l0aCB0aHJlZSBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXh8a2V5LCBjb2xsZWN0aW9uKS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCByZXR1cm5zIGB0cnVlYCBmb3IKICAgICAgICAgKiBbZW1wdHkgY29sbGVjdGlvbnNdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0VtcHR5X3NldCkgYmVjYXVzZQogICAgICAgICAqIFtldmVyeXRoaW5nIGlzIHRydWVdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL1ZhY3VvdXNfdHJ1dGgpIG9mCiAgICAgICAgICogZWxlbWVudHMgb2YgZW1wdHkgY29sbGVjdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHBhcmFtLSB7T2JqZWN0fSBbZ3VhcmRdIEVuYWJsZXMgdXNlIGFzIGFuIGl0ZXJhdGVlIGZvciBtZXRob2RzIGxpa2UgYF8ubWFwYC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYWxsIGVsZW1lbnRzIHBhc3MgdGhlIHByZWRpY2F0ZSBjaGVjaywKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmV2ZXJ5KFt0cnVlLCAxLCBudWxsLCAneWVzJ10sIEJvb2xlYW4pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICdhZ2UnOiA0MCwgJ2FjdGl2ZSc6IGZhbHNlIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmV2ZXJ5KHVzZXJzLCB7ICd1c2VyJzogJ2Jhcm5leScsICdhY3RpdmUnOiBmYWxzZSB9KTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZXZlcnkodXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmV2ZXJ5KHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBldmVyeShjb2xsZWN0aW9uLCBwcmVkaWNhdGUsIGd1YXJkKSB7CiAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheUV2ZXJ5IDogYmFzZUV2ZXJ5OwogICAgICAgICAgaWYgKGd1YXJkICYmIGlzSXRlcmF0ZWVDYWxsKGNvbGxlY3Rpb24sIHByZWRpY2F0ZSwgZ3VhcmQpKSB7CiAgICAgICAgICAgIHByZWRpY2F0ZSA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbiwgZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJdGVyYXRlcyBvdmVyIGVsZW1lbnRzIG9mIGBjb2xsZWN0aW9uYCwgcmV0dXJuaW5nIGFuIGFycmF5IG9mIGFsbCBlbGVtZW50cwogICAgICAgICAqIGBwcmVkaWNhdGVgIHJldHVybnMgdHJ1dGh5IGZvci4gVGhlIHByZWRpY2F0ZSBpcyBpbnZva2VkIHdpdGggdGhyZWUKICAgICAgICAgKiBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXh8a2V5LCBjb2xsZWN0aW9uKS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBVbmxpa2UgYF8ucmVtb3ZlYCwgdGhpcyBtZXRob2QgcmV0dXJucyBhIG5ldyBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBmaWx0ZXJlZCBhcnJheS4KICAgICAgICAgKiBAc2VlIF8ucmVqZWN0CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FnZSc6IDM2LCAnYWN0aXZlJzogdHJ1ZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAnYWdlJzogNDAsICdhY3RpdmUnOiBmYWxzZSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmlsdGVyKHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiAhby5hY3RpdmU7IH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnZnJlZCddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmlsdGVyKHVzZXJzLCB7ICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydiYXJuZXknXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmlsdGVyKHVzZXJzLCBbJ2FjdGl2ZScsIGZhbHNlXSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydmcmVkJ10KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmlsdGVyKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydiYXJuZXknXQogICAgICAgICAqCiAgICAgICAgICogLy8gQ29tYmluaW5nIHNldmVyYWwgcHJlZGljYXRlcyB1c2luZyBgXy5vdmVyRXZlcnlgIG9yIGBfLm92ZXJTb21lYC4KICAgICAgICAgKiBfLmZpbHRlcih1c2VycywgXy5vdmVyU29tZShbeyAnYWdlJzogMzYgfSwgWydhZ2UnLCA0MF1dKSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydmcmVkJywgJ2Jhcm5leSddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZmlsdGVyKGNvbGxlY3Rpb24sIHByZWRpY2F0ZSkgewogICAgICAgICAgdmFyIGZ1bmMgPSBpc0FycmF5KGNvbGxlY3Rpb24pID8gYXJyYXlGaWx0ZXIgOiBiYXNlRmlsdGVyOwogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbiwgZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJdGVyYXRlcyBvdmVyIGVsZW1lbnRzIG9mIGBjb2xsZWN0aW9uYCwgcmV0dXJuaW5nIHRoZSBmaXJzdCBlbGVtZW50CiAgICAgICAgICogYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yLiBUaGUgcHJlZGljYXRlIGlzIGludm9rZWQgd2l0aCB0aHJlZQogICAgICAgICAqIGFyZ3VtZW50czogKHZhbHVlLCBpbmRleHxrZXksIGNvbGxlY3Rpb24pLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2Zyb21JbmRleD0wXSBUaGUgaW5kZXggdG8gc2VhcmNoIGZyb20uCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIG1hdGNoZWQgZWxlbWVudCwgZWxzZSBgdW5kZWZpbmVkYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gWwogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAgJ2FnZSc6IDM2LCAnYWN0aXZlJzogdHJ1ZSB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FnZSc6IDQwLCAnYWN0aXZlJzogZmFsc2UgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAncGViYmxlcycsICdhZ2UnOiAxLCAgJ2FjdGl2ZSc6IHRydWUgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiBfLmZpbmQodXNlcnMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8uYWdlIDwgNDA7IH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdCBmb3IgJ2Jhcm5leScKICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzYCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5maW5kKHVzZXJzLCB7ICdhZ2UnOiAxLCAnYWN0aXZlJzogdHJ1ZSB9KTsKICAgICAgICAgKiAvLyA9PiBvYmplY3QgZm9yICdwZWJibGVzJwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZCh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICAgICAqIC8vID0+IG9iamVjdCBmb3IgJ2ZyZWQnCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmZpbmQodXNlcnMsICdhY3RpdmUnKTsKICAgICAgICAgKiAvLyA9PiBvYmplY3QgZm9yICdiYXJuZXknCiAgICAgICAgICovCiAgICAgICAgdmFyIGZpbmQgPSBjcmVhdGVGaW5kKGZpbmRJbmRleCk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZmluZGAgZXhjZXB0IHRoYXQgaXQgaXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZgogICAgICAgICAqIGBjb2xsZWN0aW9uYCBmcm9tIHJpZ2h0IHRvIGxlZnQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMi4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW3ByZWRpY2F0ZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZnJvbUluZGV4PWNvbGxlY3Rpb24ubGVuZ3RoLTFdIFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWF0Y2hlZCBlbGVtZW50LCBlbHNlIGB1bmRlZmluZWRgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmZpbmRMYXN0KFsxLCAyLCAzLCA0XSwgZnVuY3Rpb24obikgewogICAgICAgICAqICAgcmV0dXJuIG4gJSAyID09IDE7CiAgICAgICAgICogfSk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqLwogICAgICAgIHZhciBmaW5kTGFzdCA9IGNyZWF0ZUZpbmQoZmluZExhc3RJbmRleCk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmbGF0dGVuZWQgYXJyYXkgb2YgdmFsdWVzIGJ5IHJ1bm5pbmcgZWFjaCBlbGVtZW50IGluIGBjb2xsZWN0aW9uYAogICAgICAgICAqIHRocnUgYGl0ZXJhdGVlYCBhbmQgZmxhdHRlbmluZyB0aGUgbWFwcGVkIHJlc3VsdHMuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkCiAgICAgICAgICogd2l0aCB0aHJlZSBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXh8a2V5LCBjb2xsZWN0aW9uKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZsYXR0ZW5lZCBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gZHVwbGljYXRlKG4pIHsKICAgICAgICAgKiAgIHJldHVybiBbbiwgbl07CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogXy5mbGF0TWFwKFsxLCAyXSwgZHVwbGljYXRlKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMSwgMiwgMl0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmbGF0TWFwKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUZsYXR0ZW4obWFwKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSwgMSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmZsYXRNYXBgIGV4Y2VwdCB0aGF0IGl0IHJlY3Vyc2l2ZWx5IGZsYXR0ZW5zIHRoZQogICAgICAgICAqIG1hcHBlZCByZXN1bHRzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZmxhdHRlbmVkIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBkdXBsaWNhdGUobikgewogICAgICAgICAqICAgcmV0dXJuIFtbW24sIG5dXV07CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogXy5mbGF0TWFwRGVlcChbMSwgMl0sIGR1cGxpY2F0ZSk7CiAgICAgICAgICogLy8gPT4gWzEsIDEsIDIsIDJdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZmxhdE1hcERlZXAoY29sbGVjdGlvbiwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiBiYXNlRmxhdHRlbihtYXAoY29sbGVjdGlvbiwgaXRlcmF0ZWUpLCBJTkZJTklUWSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmZsYXRNYXBgIGV4Y2VwdCB0aGF0IGl0IHJlY3Vyc2l2ZWx5IGZsYXR0ZW5zIHRoZQogICAgICAgICAqIG1hcHBlZCByZXN1bHRzIHVwIHRvIGBkZXB0aGAgdGltZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC43LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2RlcHRoPTFdIFRoZSBtYXhpbXVtIHJlY3Vyc2lvbiBkZXB0aC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBmbGF0dGVuZWQgYXJyYXkuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGR1cGxpY2F0ZShuKSB7CiAgICAgICAgICogICByZXR1cm4gW1tbbiwgbl1dXTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBfLmZsYXRNYXBEZXB0aChbMSwgMl0sIGR1cGxpY2F0ZSwgMik7CiAgICAgICAgICogLy8gPT4gW1sxLCAxXSwgWzIsIDJdXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGZsYXRNYXBEZXB0aChjb2xsZWN0aW9uLCBpdGVyYXRlZSwgZGVwdGgpIHsKICAgICAgICAgIGRlcHRoID0gZGVwdGggPT09IHVuZGVmaW5lZCQxID8gMSA6IHRvSW50ZWdlcihkZXB0aCk7CiAgICAgICAgICByZXR1cm4gYmFzZUZsYXR0ZW4obWFwKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSwgZGVwdGgpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogSXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZiBgY29sbGVjdGlvbmAgYW5kIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgZWFjaCBlbGVtZW50LgogICAgICAgICAqIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGluZGV4fGtleSwgY29sbGVjdGlvbikuCiAgICAgICAgICogSXRlcmF0ZWUgZnVuY3Rpb25zIG1heSBleGl0IGl0ZXJhdGlvbiBlYXJseSBieSBleHBsaWNpdGx5IHJldHVybmluZyBgZmFsc2VgLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIEFzIHdpdGggb3RoZXIgIkNvbGxlY3Rpb25zIiBtZXRob2RzLCBvYmplY3RzIHdpdGggYSAibGVuZ3RoIgogICAgICAgICAqIHByb3BlcnR5IGFyZSBpdGVyYXRlZCBsaWtlIGFycmF5cy4gVG8gYXZvaWQgdGhpcyBiZWhhdmlvciB1c2UgYF8uZm9ySW5gCiAgICAgICAgICogb3IgYF8uZm9yT3duYCBmb3Igb2JqZWN0IGl0ZXJhdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBhbGlhcyBlYWNoCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fE9iamVjdH0gUmV0dXJucyBgY29sbGVjdGlvbmAuCiAgICAgICAgICogQHNlZSBfLmZvckVhY2hSaWdodAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmZvckVhY2goWzEsIDJdLCBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAqICAgY29uc29sZS5sb2codmFsdWUpOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IExvZ3MgYDFgIHRoZW4gYDJgLgogICAgICAgICAqCiAgICAgICAgICogXy5mb3JFYWNoKHsgJ2EnOiAxLCAnYic6IDIgfSwgZnVuY3Rpb24odmFsdWUsIGtleSkgewogICAgICAgICAqICAgY29uc29sZS5sb2coa2V5KTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKiAvLyA9PiBMb2dzICdhJyB0aGVuICdiJyAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmb3JFYWNoKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSB7CiAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheUVhY2ggOiBiYXNlRWFjaDsKICAgICAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAzKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmZvckVhY2hgIGV4Y2VwdCB0aGF0IGl0IGl0ZXJhdGVzIG92ZXIgZWxlbWVudHMgb2YKICAgICAgICAgKiBgY29sbGVjdGlvbmAgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuMC4wCiAgICAgICAgICogQGFsaWFzIGVhY2hSaWdodAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheXxPYmplY3R9IFJldHVybnMgYGNvbGxlY3Rpb25gLgogICAgICAgICAqIEBzZWUgXy5mb3JFYWNoCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZm9yRWFjaFJpZ2h0KFsxLCAyXSwgZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgKiAgIGNvbnNvbGUubG9nKHZhbHVlKTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKiAvLyA9PiBMb2dzIGAyYCB0aGVuIGAxYC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmb3JFYWNoUmlnaHQoY29sbGVjdGlvbiwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHZhciBmdW5jID0gaXNBcnJheShjb2xsZWN0aW9uKSA/IGFycmF5RWFjaFJpZ2h0IDogYmFzZUVhY2hSaWdodDsKICAgICAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAzKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIG9iamVjdCBjb21wb3NlZCBvZiBrZXlzIGdlbmVyYXRlZCBmcm9tIHRoZSByZXN1bHRzIG9mIHJ1bm5pbmcKICAgICAgICAgKiBlYWNoIGVsZW1lbnQgb2YgYGNvbGxlY3Rpb25gIHRocnUgYGl0ZXJhdGVlYC4gVGhlIG9yZGVyIG9mIGdyb3VwZWQgdmFsdWVzCiAgICAgICAgICogaXMgZGV0ZXJtaW5lZCBieSB0aGUgb3JkZXIgdGhleSBvY2N1ciBpbiBgY29sbGVjdGlvbmAuIFRoZSBjb3JyZXNwb25kaW5nCiAgICAgICAgICogdmFsdWUgb2YgZWFjaCBrZXkgaXMgYW4gYXJyYXkgb2YgZWxlbWVudHMgcmVzcG9uc2libGUgZm9yIGdlbmVyYXRpbmcgdGhlCiAgICAgICAgICoga2V5LiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgdG8gdHJhbnNmb3JtIGtleXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY29tcG9zZWQgYWdncmVnYXRlIG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5ncm91cEJ5KFs2LjEsIDQuMiwgNi4zXSwgTWF0aC5mbG9vcik7CiAgICAgICAgICogLy8gPT4geyAnNCc6IFs0LjJdLCAnNic6IFs2LjEsIDYuM10gfQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5ncm91cEJ5KFsnb25lJywgJ3R3bycsICd0aHJlZSddLCAnbGVuZ3RoJyk7CiAgICAgICAgICogLy8gPT4geyAnMyc6IFsnb25lJywgJ3R3byddLCAnNSc6IFsndGhyZWUnXSB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGdyb3VwQnkgPSBjcmVhdGVBZ2dyZWdhdG9yKGZ1bmN0aW9uKHJlc3VsdCwgdmFsdWUsIGtleSkgewogICAgICAgICAgaWYgKGhhc093blByb3BlcnR5LmNhbGwocmVzdWx0LCBrZXkpKSB7CiAgICAgICAgICAgIHJlc3VsdFtrZXldLnB1c2godmFsdWUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgYmFzZUFzc2lnblZhbHVlKHJlc3VsdCwga2V5LCBbdmFsdWVdKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgaW4gYGNvbGxlY3Rpb25gLiBJZiBgY29sbGVjdGlvbmAgaXMgYSBzdHJpbmcsIGl0J3MKICAgICAgICAgKiBjaGVja2VkIGZvciBhIHN1YnN0cmluZyBvZiBgdmFsdWVgLCBvdGhlcndpc2UKICAgICAgICAgKiBbYFNhbWVWYWx1ZVplcm9gXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1zYW1ldmFsdWV6ZXJvKQogICAgICAgICAqIGlzIHVzZWQgZm9yIGVxdWFsaXR5IGNvbXBhcmlzb25zLiBJZiBgZnJvbUluZGV4YCBpcyBuZWdhdGl2ZSwgaXQncyB1c2VkIGFzCiAgICAgICAgICogdGhlIG9mZnNldCBmcm9tIHRoZSBlbmQgb2YgYGNvbGxlY3Rpb25gLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdHxzdHJpbmd9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZnJvbUluZGV4PTBdIFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5yZWR1Y2VgLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGZvdW5kLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaW5jbHVkZXMoWzEsIDIsIDNdLCAxKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmluY2x1ZGVzKFsxLCAyLCAzXSwgMSwgMik7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaW5jbHVkZXMoeyAnYSc6IDEsICdiJzogMiB9LCAxKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmluY2x1ZGVzKCdhYmNkJywgJ2JjJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGluY2x1ZGVzKGNvbGxlY3Rpb24sIHZhbHVlLCBmcm9tSW5kZXgsIGd1YXJkKSB7CiAgICAgICAgICBjb2xsZWN0aW9uID0gaXNBcnJheUxpa2UoY29sbGVjdGlvbikgPyBjb2xsZWN0aW9uIDogdmFsdWVzKGNvbGxlY3Rpb24pOwogICAgICAgICAgZnJvbUluZGV4ID0gKGZyb21JbmRleCAmJiAhZ3VhcmQpID8gdG9JbnRlZ2VyKGZyb21JbmRleCkgOiAwOwoKICAgICAgICAgIHZhciBsZW5ndGggPSBjb2xsZWN0aW9uLmxlbmd0aDsKICAgICAgICAgIGlmIChmcm9tSW5kZXggPCAwKSB7CiAgICAgICAgICAgIGZyb21JbmRleCA9IG5hdGl2ZU1heChsZW5ndGggKyBmcm9tSW5kZXgsIDApOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGlzU3RyaW5nKGNvbGxlY3Rpb24pCiAgICAgICAgICAgID8gKGZyb21JbmRleCA8PSBsZW5ndGggJiYgY29sbGVjdGlvbi5pbmRleE9mKHZhbHVlLCBmcm9tSW5kZXgpID4gLTEpCiAgICAgICAgICAgIDogKCEhbGVuZ3RoICYmIGJhc2VJbmRleE9mKGNvbGxlY3Rpb24sIHZhbHVlLCBmcm9tSW5kZXgpID4gLTEpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogSW52b2tlcyB0aGUgbWV0aG9kIGF0IGBwYXRoYCBvZiBlYWNoIGVsZW1lbnQgaW4gYGNvbGxlY3Rpb25gLCByZXR1cm5pbmcKICAgICAgICAgKiBhbiBhcnJheSBvZiB0aGUgcmVzdWx0cyBvZiBlYWNoIGludm9rZWQgbWV0aG9kLiBBbnkgYWRkaXRpb25hbCBhcmd1bWVudHMKICAgICAgICAgKiBhcmUgcHJvdmlkZWQgdG8gZWFjaCBpbnZva2VkIG1ldGhvZC4gSWYgYHBhdGhgIGlzIGEgZnVuY3Rpb24sIGl0J3MgaW52b2tlZAogICAgICAgICAqIGZvciwgYW5kIGB0aGlzYCBib3VuZCB0bywgZWFjaCBlbGVtZW50IGluIGBjb2xsZWN0aW9uYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8RnVuY3Rpb258c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBtZXRob2QgdG8gaW52b2tlIG9yCiAgICAgICAgICogIHRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBbYXJnc10gVGhlIGFyZ3VtZW50cyB0byBpbnZva2UgZWFjaCBtZXRob2Qgd2l0aC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHJlc3VsdHMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaW52b2tlTWFwKFtbNSwgMSwgN10sIFszLCAyLCAxXV0sICdzb3J0Jyk7CiAgICAgICAgICogLy8gPT4gW1sxLCA1LCA3XSwgWzEsIDIsIDNdXQogICAgICAgICAqCiAgICAgICAgICogXy5pbnZva2VNYXAoWzEyMywgNDU2XSwgU3RyaW5nLnByb3RvdHlwZS5zcGxpdCwgJycpOwogICAgICAgICAqIC8vID0+IFtbJzEnLCAnMicsICczJ10sIFsnNCcsICc1JywgJzYnXV0KICAgICAgICAgKi8KICAgICAgICB2YXIgaW52b2tlTWFwID0gYmFzZVJlc3QoZnVuY3Rpb24oY29sbGVjdGlvbiwgcGF0aCwgYXJncykgewogICAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgICAgaXNGdW5jID0gdHlwZW9mIHBhdGggPT0gJ2Z1bmN0aW9uJywKICAgICAgICAgICAgICByZXN1bHQgPSBpc0FycmF5TGlrZShjb2xsZWN0aW9uKSA/IEFycmF5KGNvbGxlY3Rpb24ubGVuZ3RoKSA6IFtdOwoKICAgICAgICAgIGJhc2VFYWNoKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICAgIHJlc3VsdFsrK2luZGV4XSA9IGlzRnVuYyA/IGFwcGx5KHBhdGgsIHZhbHVlLCBhcmdzKSA6IGJhc2VJbnZva2UodmFsdWUsIHBhdGgsIGFyZ3MpOwogICAgICAgICAgfSk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIG9iamVjdCBjb21wb3NlZCBvZiBrZXlzIGdlbmVyYXRlZCBmcm9tIHRoZSByZXN1bHRzIG9mIHJ1bm5pbmcKICAgICAgICAgKiBlYWNoIGVsZW1lbnQgb2YgYGNvbGxlY3Rpb25gIHRocnUgYGl0ZXJhdGVlYC4gVGhlIGNvcnJlc3BvbmRpbmcgdmFsdWUgb2YKICAgICAgICAgKiBlYWNoIGtleSBpcyB0aGUgbGFzdCBlbGVtZW50IHJlc3BvbnNpYmxlIGZvciBnZW5lcmF0aW5nIHRoZSBrZXkuIFRoZQogICAgICAgICAqIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ6ICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIHRvIHRyYW5zZm9ybSBrZXlzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGNvbXBvc2VkIGFnZ3JlZ2F0ZSBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IFsKICAgICAgICAgKiAgIHsgJ2Rpcic6ICdsZWZ0JywgJ2NvZGUnOiA5NyB9LAogICAgICAgICAqICAgeyAnZGlyJzogJ3JpZ2h0JywgJ2NvZGUnOiAxMDAgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiBfLmtleUJ5KGFycmF5LCBmdW5jdGlvbihvKSB7CiAgICAgICAgICogICByZXR1cm4gU3RyaW5nLmZyb21DaGFyQ29kZShvLmNvZGUpOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiB7ICdkaXInOiAnbGVmdCcsICdjb2RlJzogOTcgfSwgJ2QnOiB7ICdkaXInOiAncmlnaHQnLCAnY29kZSc6IDEwMCB9IH0KICAgICAgICAgKgogICAgICAgICAqIF8ua2V5QnkoYXJyYXksICdkaXInKTsKICAgICAgICAgKiAvLyA9PiB7ICdsZWZ0JzogeyAnZGlyJzogJ2xlZnQnLCAnY29kZSc6IDk3IH0sICdyaWdodCc6IHsgJ2Rpcic6ICdyaWdodCcsICdjb2RlJzogMTAwIH0gfQogICAgICAgICAqLwogICAgICAgIHZhciBrZXlCeSA9IGNyZWF0ZUFnZ3JlZ2F0b3IoZnVuY3Rpb24ocmVzdWx0LCB2YWx1ZSwga2V5KSB7CiAgICAgICAgICBiYXNlQXNzaWduVmFsdWUocmVzdWx0LCBrZXksIHZhbHVlKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB2YWx1ZXMgYnkgcnVubmluZyBlYWNoIGVsZW1lbnQgaW4gYGNvbGxlY3Rpb25gIHRocnUKICAgICAgICAgKiBgaXRlcmF0ZWVgLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIHRocmVlIGFyZ3VtZW50czoKICAgICAgICAgKiAodmFsdWUsIGluZGV4fGtleSwgY29sbGVjdGlvbikuCiAgICAgICAgICoKICAgICAgICAgKiBNYW55IGxvZGFzaCBtZXRob2RzIGFyZSBndWFyZGVkIHRvIHdvcmsgYXMgaXRlcmF0ZWVzIGZvciBtZXRob2RzIGxpa2UKICAgICAgICAgKiBgXy5ldmVyeWAsIGBfLmZpbHRlcmAsIGBfLm1hcGAsIGBfLm1hcFZhbHVlc2AsIGBfLnJlamVjdGAsIGFuZCBgXy5zb21lYC4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBndWFyZGVkIG1ldGhvZHMgYXJlOgogICAgICAgICAqIGBhcnlgLCBgY2h1bmtgLCBgY3VycnlgLCBgY3VycnlSaWdodGAsIGBkcm9wYCwgYGRyb3BSaWdodGAsIGBldmVyeWAsCiAgICAgICAgICogYGZpbGxgLCBgaW52ZXJ0YCwgYHBhcnNlSW50YCwgYHJhbmRvbWAsIGByYW5nZWAsIGByYW5nZVJpZ2h0YCwgYHJlcGVhdGAsCiAgICAgICAgICogYHNhbXBsZVNpemVgLCBgc2xpY2VgLCBgc29tZWAsIGBzb3J0QnlgLCBgc3BsaXRgLCBgdGFrZWAsIGB0YWtlUmlnaHRgLAogICAgICAgICAqIGB0ZW1wbGF0ZWAsIGB0cmltYCwgYHRyaW1FbmRgLCBgdHJpbVN0YXJ0YCwgYW5kIGB3b3Jkc2AKICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IG1hcHBlZCBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gc3F1YXJlKG4pIHsKICAgICAgICAgKiAgIHJldHVybiBuICogbjsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBfLm1hcChbNCwgOF0sIHNxdWFyZSk7CiAgICAgICAgICogLy8gPT4gWzE2LCA2NF0KICAgICAgICAgKgogICAgICAgICAqIF8ubWFwKHsgJ2EnOiA0LCAnYic6IDggfSwgc3F1YXJlKTsKICAgICAgICAgKiAvLyA9PiBbMTYsIDY0XSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gWwogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5tYXAodXNlcnMsICd1c2VyJyk7CiAgICAgICAgICogLy8gPT4gWydiYXJuZXknLCAnZnJlZCddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbWFwKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSB7CiAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheU1hcCA6IGJhc2VNYXA7CiAgICAgICAgICByZXR1cm4gZnVuYyhjb2xsZWN0aW9uLCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5zb3J0QnlgIGV4Y2VwdCB0aGF0IGl0IGFsbG93cyBzcGVjaWZ5aW5nIHRoZSBzb3J0CiAgICAgICAgICogb3JkZXJzIG9mIHRoZSBpdGVyYXRlZXMgdG8gc29ydCBieS4gSWYgYG9yZGVyc2AgaXMgdW5zcGVjaWZpZWQsIGFsbCB2YWx1ZXMKICAgICAgICAgKiBhcmUgc29ydGVkIGluIGFzY2VuZGluZyBvcmRlci4gT3RoZXJ3aXNlLCBzcGVjaWZ5IGFuIG9yZGVyIG9mICJkZXNjIiBmb3IKICAgICAgICAgKiBkZXNjZW5kaW5nIG9yICJhc2MiIGZvciBhc2NlbmRpbmcgc29ydCBvcmRlciBvZiBjb3JyZXNwb25kaW5nIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7QXJyYXlbXXxGdW5jdGlvbltdfE9iamVjdFtdfHN0cmluZ1tdfSBbaXRlcmF0ZWVzPVtfLmlkZW50aXR5XV0KICAgICAgICAgKiAgVGhlIGl0ZXJhdGVlcyB0byBzb3J0IGJ5LgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nW119IFtvcmRlcnNdIFRoZSBzb3J0IG9yZGVycyBvZiBgaXRlcmF0ZWVzYC4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5yZWR1Y2VgLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IHNvcnRlZCBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gWwogICAgICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAnYWdlJzogNDggfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FnZSc6IDM0IH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICdhZ2UnOiA0MCB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAnYWdlJzogMzYgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiAvLyBTb3J0IGJ5IGB1c2VyYCBpbiBhc2NlbmRpbmcgb3JkZXIgYW5kIGJ5IGBhZ2VgIGluIGRlc2NlbmRpbmcgb3JkZXIuCiAgICAgICAgICogXy5vcmRlckJ5KHVzZXJzLCBbJ3VzZXInLCAnYWdlJ10sIFsnYXNjJywgJ2Rlc2MnXSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1snYmFybmV5JywgMzZdLCBbJ2Jhcm5leScsIDM0XSwgWydmcmVkJywgNDhdLCBbJ2ZyZWQnLCA0MF1dCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gb3JkZXJCeShjb2xsZWN0aW9uLCBpdGVyYXRlZXMsIG9yZGVycywgZ3VhcmQpIHsKICAgICAgICAgIGlmIChjb2xsZWN0aW9uID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgaWYgKCFpc0FycmF5KGl0ZXJhdGVlcykpIHsKICAgICAgICAgICAgaXRlcmF0ZWVzID0gaXRlcmF0ZWVzID09IG51bGwgPyBbXSA6IFtpdGVyYXRlZXNdOwogICAgICAgICAgfQogICAgICAgICAgb3JkZXJzID0gZ3VhcmQgPyB1bmRlZmluZWQkMSA6IG9yZGVyczsKICAgICAgICAgIGlmICghaXNBcnJheShvcmRlcnMpKSB7CiAgICAgICAgICAgIG9yZGVycyA9IG9yZGVycyA9PSBudWxsID8gW10gOiBbb3JkZXJzXTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBiYXNlT3JkZXJCeShjb2xsZWN0aW9uLCBpdGVyYXRlZXMsIG9yZGVycyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIGVsZW1lbnRzIHNwbGl0IGludG8gdHdvIGdyb3VwcywgdGhlIGZpcnN0IG9mIHdoaWNoCiAgICAgICAgICogY29udGFpbnMgZWxlbWVudHMgYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yLCB0aGUgc2Vjb25kIG9mIHdoaWNoCiAgICAgICAgICogY29udGFpbnMgZWxlbWVudHMgYHByZWRpY2F0ZWAgcmV0dXJucyBmYWxzZXkgZm9yLiBUaGUgcHJlZGljYXRlIGlzCiAgICAgICAgICogaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIGdyb3VwZWQgZWxlbWVudHMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICAnYWdlJzogNDAsICdhY3RpdmUnOiB0cnVlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWdlJzogMSwgICdhY3RpdmUnOiBmYWxzZSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8ucGFydGl0aW9uKHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiBvLmFjdGl2ZTsgfSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1snZnJlZCddLCBbJ2Jhcm5leScsICdwZWJibGVzJ11dCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8ucGFydGl0aW9uKHVzZXJzLCB7ICdhZ2UnOiAxLCAnYWN0aXZlJzogZmFsc2UgfSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1sncGViYmxlcyddLCBbJ2Jhcm5leScsICdmcmVkJ11dCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc1Byb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5wYXJ0aXRpb24odXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbWydiYXJuZXknLCAncGViYmxlcyddLCBbJ2ZyZWQnXV0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8ucGFydGl0aW9uKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1snZnJlZCddLCBbJ2Jhcm5leScsICdwZWJibGVzJ11dCiAgICAgICAgICovCiAgICAgICAgdmFyIHBhcnRpdGlvbiA9IGNyZWF0ZUFnZ3JlZ2F0b3IoZnVuY3Rpb24ocmVzdWx0LCB2YWx1ZSwga2V5KSB7CiAgICAgICAgICByZXN1bHRba2V5ID8gMCA6IDFdLnB1c2godmFsdWUpOwogICAgICAgIH0sIGZ1bmN0aW9uKCkgeyByZXR1cm4gW1tdLCBbXV07IH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBSZWR1Y2VzIGBjb2xsZWN0aW9uYCB0byBhIHZhbHVlIHdoaWNoIGlzIHRoZSBhY2N1bXVsYXRlZCByZXN1bHQgb2YgcnVubmluZwogICAgICAgICAqIGVhY2ggZWxlbWVudCBpbiBgY29sbGVjdGlvbmAgdGhydSBgaXRlcmF0ZWVgLCB3aGVyZSBlYWNoIHN1Y2Nlc3NpdmUKICAgICAgICAgKiBpbnZvY2F0aW9uIGlzIHN1cHBsaWVkIHRoZSByZXR1cm4gdmFsdWUgb2YgdGhlIHByZXZpb3VzLiBJZiBgYWNjdW11bGF0b3JgCiAgICAgICAgICogaXMgbm90IGdpdmVuLCB0aGUgZmlyc3QgZWxlbWVudCBvZiBgY29sbGVjdGlvbmAgaXMgdXNlZCBhcyB0aGUgaW5pdGlhbAogICAgICAgICAqIHZhbHVlLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIGZvdXIgYXJndW1lbnRzOgogICAgICAgICAqIChhY2N1bXVsYXRvciwgdmFsdWUsIGluZGV4fGtleSwgY29sbGVjdGlvbikuCiAgICAgICAgICoKICAgICAgICAgKiBNYW55IGxvZGFzaCBtZXRob2RzIGFyZSBndWFyZGVkIHRvIHdvcmsgYXMgaXRlcmF0ZWVzIGZvciBtZXRob2RzIGxpa2UKICAgICAgICAgKiBgXy5yZWR1Y2VgLCBgXy5yZWR1Y2VSaWdodGAsIGFuZCBgXy50cmFuc2Zvcm1gLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGd1YXJkZWQgbWV0aG9kcyBhcmU6CiAgICAgICAgICogYGFzc2lnbmAsIGBkZWZhdWx0c2AsIGBkZWZhdWx0c0RlZXBgLCBgaW5jbHVkZXNgLCBgbWVyZ2VgLCBgb3JkZXJCeWAsCiAgICAgICAgICogYW5kIGBzb3J0QnlgCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0geyp9IFthY2N1bXVsYXRvcl0gVGhlIGluaXRpYWwgdmFsdWUuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGFjY3VtdWxhdGVkIHZhbHVlLgogICAgICAgICAqIEBzZWUgXy5yZWR1Y2VSaWdodAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnJlZHVjZShbMSwgMl0sIGZ1bmN0aW9uKHN1bSwgbikgewogICAgICAgICAqICAgcmV0dXJuIHN1bSArIG47CiAgICAgICAgICogfSwgMCk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqCiAgICAgICAgICogXy5yZWR1Y2UoeyAnYSc6IDEsICdiJzogMiwgJ2MnOiAxIH0sIGZ1bmN0aW9uKHJlc3VsdCwgdmFsdWUsIGtleSkgewogICAgICAgICAqICAgKHJlc3VsdFt2YWx1ZV0gfHwgKHJlc3VsdFt2YWx1ZV0gPSBbXSkpLnB1c2goa2V5KTsKICAgICAgICAgKiAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICogfSwge30pOwogICAgICAgICAqIC8vID0+IHsgJzEnOiBbJ2EnLCAnYyddLCAnMic6IFsnYiddIH0gKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZWR1Y2UoY29sbGVjdGlvbiwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yKSB7CiAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheVJlZHVjZSA6IGJhc2VSZWR1Y2UsCiAgICAgICAgICAgICAgaW5pdEFjY3VtID0gYXJndW1lbnRzLmxlbmd0aCA8IDM7CgogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbiwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDQpLCBhY2N1bXVsYXRvciwgaW5pdEFjY3VtLCBiYXNlRWFjaCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnJlZHVjZWAgZXhjZXB0IHRoYXQgaXQgaXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZgogICAgICAgICAqIGBjb2xsZWN0aW9uYCBmcm9tIHJpZ2h0IHRvIGxlZnQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0geyp9IFthY2N1bXVsYXRvcl0gVGhlIGluaXRpYWwgdmFsdWUuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGFjY3VtdWxhdGVkIHZhbHVlLgogICAgICAgICAqIEBzZWUgXy5yZWR1Y2UKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gW1swLCAxXSwgWzIsIDNdLCBbNCwgNV1dOwogICAgICAgICAqCiAgICAgICAgICogXy5yZWR1Y2VSaWdodChhcnJheSwgZnVuY3Rpb24oZmxhdHRlbmVkLCBvdGhlcikgewogICAgICAgICAqICAgcmV0dXJuIGZsYXR0ZW5lZC5jb25jYXQob3RoZXIpOwogICAgICAgICAqIH0sIFtdKTsKICAgICAgICAgKiAvLyA9PiBbNCwgNSwgMiwgMywgMCwgMV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZWR1Y2VSaWdodChjb2xsZWN0aW9uLCBpdGVyYXRlZSwgYWNjdW11bGF0b3IpIHsKICAgICAgICAgIHZhciBmdW5jID0gaXNBcnJheShjb2xsZWN0aW9uKSA/IGFycmF5UmVkdWNlUmlnaHQgOiBiYXNlUmVkdWNlLAogICAgICAgICAgICAgIGluaXRBY2N1bSA9IGFyZ3VtZW50cy5sZW5ndGggPCAzOwoKICAgICAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCA0KSwgYWNjdW11bGF0b3IsIGluaXRBY2N1bSwgYmFzZUVhY2hSaWdodCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3Bwb3NpdGUgb2YgYF8uZmlsdGVyYDsgdGhpcyBtZXRob2QgcmV0dXJucyB0aGUgZWxlbWVudHMgb2YgYGNvbGxlY3Rpb25gCiAgICAgICAgICogdGhhdCBgcHJlZGljYXRlYCBkb2VzICoqbm90KiogcmV0dXJuIHRydXRoeSBmb3IuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZmlsdGVyZWQgYXJyYXkuCiAgICAgICAgICogQHNlZSBfLmZpbHRlcgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICdhZ2UnOiA0MCwgJ2FjdGl2ZSc6IHRydWUgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiBfLnJlamVjdCh1c2VycywgZnVuY3Rpb24obykgeyByZXR1cm4gIW8uYWN0aXZlOyB9KTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ2ZyZWQnXQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnJlamVjdCh1c2VycywgeyAnYWdlJzogNDAsICdhY3RpdmUnOiB0cnVlIH0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5J10KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzUHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnJlamVjdCh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnZnJlZCddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnJlamVjdCh1c2VycywgJ2FjdGl2ZScpOwogICAgICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5J10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZWplY3QoY29sbGVjdGlvbiwgcHJlZGljYXRlKSB7CiAgICAgICAgICB2YXIgZnVuYyA9IGlzQXJyYXkoY29sbGVjdGlvbikgPyBhcnJheUZpbHRlciA6IGJhc2VGaWx0ZXI7CiAgICAgICAgICByZXR1cm4gZnVuYyhjb2xsZWN0aW9uLCBuZWdhdGUoZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyBhIHJhbmRvbSBlbGVtZW50IGZyb20gYGNvbGxlY3Rpb25gLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBzYW1wbGUuCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHJhbmRvbSBlbGVtZW50LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNhbXBsZShbMSwgMiwgMywgNF0pOwogICAgICAgICAqIC8vID0+IDIKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzYW1wbGUoY29sbGVjdGlvbikgewogICAgICAgICAgdmFyIGZ1bmMgPSBpc0FycmF5KGNvbGxlY3Rpb24pID8gYXJyYXlTYW1wbGUgOiBiYXNlU2FtcGxlOwogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIGBuYCByYW5kb20gZWxlbWVudHMgYXQgdW5pcXVlIGtleXMgZnJvbSBgY29sbGVjdGlvbmAgdXAgdG8gdGhlCiAgICAgICAgICogc2l6ZSBvZiBgY29sbGVjdGlvbmAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgQ29sbGVjdGlvbgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIHNhbXBsZS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW249MV0gVGhlIG51bWJlciBvZiBlbGVtZW50cyB0byBzYW1wbGUuCiAgICAgICAgICogQHBhcmFtLSB7T2JqZWN0fSBbZ3VhcmRdIEVuYWJsZXMgdXNlIGFzIGFuIGl0ZXJhdGVlIGZvciBtZXRob2RzIGxpa2UgYF8ubWFwYC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIHJhbmRvbSBlbGVtZW50cy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5zYW1wbGVTaXplKFsxLCAyLCAzXSwgMik7CiAgICAgICAgICogLy8gPT4gWzMsIDFdCiAgICAgICAgICoKICAgICAgICAgKiBfLnNhbXBsZVNpemUoWzEsIDIsIDNdLCA0KTsKICAgICAgICAgKiAvLyA9PiBbMiwgMywgMV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzYW1wbGVTaXplKGNvbGxlY3Rpb24sIG4sIGd1YXJkKSB7CiAgICAgICAgICBpZiAoKGd1YXJkID8gaXNJdGVyYXRlZUNhbGwoY29sbGVjdGlvbiwgbiwgZ3VhcmQpIDogbiA9PT0gdW5kZWZpbmVkJDEpKSB7CiAgICAgICAgICAgIG4gPSAxOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbiA9IHRvSW50ZWdlcihuKTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBmdW5jID0gaXNBcnJheShjb2xsZWN0aW9uKSA/IGFycmF5U2FtcGxlU2l6ZSA6IGJhc2VTYW1wbGVTaXplOwogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbiwgbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHNodWZmbGVkIHZhbHVlcywgdXNpbmcgYSB2ZXJzaW9uIG9mIHRoZQogICAgICAgICAqIFtGaXNoZXItWWF0ZXMgc2h1ZmZsZV0oaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvRmlzaGVyLVlhdGVzX3NodWZmbGUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBzaHVmZmxlLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IHNodWZmbGVkIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNodWZmbGUoWzEsIDIsIDMsIDRdKTsKICAgICAgICAgKiAvLyA9PiBbNCwgMSwgMywgMl0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzaHVmZmxlKGNvbGxlY3Rpb24pIHsKICAgICAgICAgIHZhciBmdW5jID0gaXNBcnJheShjb2xsZWN0aW9uKSA/IGFycmF5U2h1ZmZsZSA6IGJhc2VTaHVmZmxlOwogICAgICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBzaXplIG9mIGBjb2xsZWN0aW9uYCBieSByZXR1cm5pbmcgaXRzIGxlbmd0aCBmb3IgYXJyYXktbGlrZQogICAgICAgICAqIHZhbHVlcyBvciB0aGUgbnVtYmVyIG9mIG93biBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIGZvciBvYmplY3RzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdHxzdHJpbmd9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBjb2xsZWN0aW9uIHNpemUuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uc2l6ZShbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IDMKICAgICAgICAgKgogICAgICAgICAqIF8uc2l6ZSh7ICdhJzogMSwgJ2InOiAyIH0pOwogICAgICAgICAqIC8vID0+IDIKICAgICAgICAgKgogICAgICAgICAqIF8uc2l6ZSgncGViYmxlcycpOwogICAgICAgICAqIC8vID0+IDcKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzaXplKGNvbGxlY3Rpb24pIHsKICAgICAgICAgIGlmIChjb2xsZWN0aW9uID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNBcnJheUxpa2UoY29sbGVjdGlvbikpIHsKICAgICAgICAgICAgcmV0dXJuIGlzU3RyaW5nKGNvbGxlY3Rpb24pID8gc3RyaW5nU2l6ZShjb2xsZWN0aW9uKSA6IGNvbGxlY3Rpb24ubGVuZ3RoOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHRhZyA9IGdldFRhZyhjb2xsZWN0aW9uKTsKICAgICAgICAgIGlmICh0YWcgPT0gbWFwVGFnIHx8IHRhZyA9PSBzZXRUYWcpIHsKICAgICAgICAgICAgcmV0dXJuIGNvbGxlY3Rpb24uc2l6ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBiYXNlS2V5cyhjb2xsZWN0aW9uKS5sZW5ndGg7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yICoqYW55KiogZWxlbWVudCBvZiBgY29sbGVjdGlvbmAuCiAgICAgICAgICogSXRlcmF0aW9uIGlzIHN0b3BwZWQgb25jZSBgcHJlZGljYXRlYCByZXR1cm5zIHRydXRoeS4gVGhlIHByZWRpY2F0ZSBpcwogICAgICAgICAqIGludm9rZWQgd2l0aCB0aHJlZSBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXh8a2V5LCBjb2xsZWN0aW9uKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5tYXBgLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbnkgZWxlbWVudCBwYXNzZXMgdGhlIHByZWRpY2F0ZSBjaGVjaywKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNvbWUoW251bGwsIDAsICd5ZXMnLCBmYWxzZV0sIEJvb2xlYW4pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IFsKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgJ2FjdGl2ZSc6IGZhbHNlIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLnNvbWUodXNlcnMsIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FjdGl2ZSc6IGZhbHNlIH0pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc1Byb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5zb21lKHVzZXJzLCBbJ2FjdGl2ZScsIGZhbHNlXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5zb21lKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNvbWUoY29sbGVjdGlvbiwgcHJlZGljYXRlLCBndWFyZCkgewogICAgICAgICAgdmFyIGZ1bmMgPSBpc0FycmF5KGNvbGxlY3Rpb24pID8gYXJyYXlTb21lIDogYmFzZVNvbWU7CiAgICAgICAgICBpZiAoZ3VhcmQgJiYgaXNJdGVyYXRlZUNhbGwoY29sbGVjdGlvbiwgcHJlZGljYXRlLCBndWFyZCkpIHsKICAgICAgICAgICAgcHJlZGljYXRlID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gZnVuYyhjb2xsZWN0aW9uLCBnZXRJdGVyYXRlZShwcmVkaWNhdGUsIDMpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgZWxlbWVudHMsIHNvcnRlZCBpbiBhc2NlbmRpbmcgb3JkZXIgYnkgdGhlIHJlc3VsdHMgb2YKICAgICAgICAgKiBydW5uaW5nIGVhY2ggZWxlbWVudCBpbiBhIGNvbGxlY3Rpb24gdGhydSBlYWNoIGl0ZXJhdGVlLiBUaGlzIG1ldGhvZAogICAgICAgICAqIHBlcmZvcm1zIGEgc3RhYmxlIHNvcnQsIHRoYXQgaXMsIGl0IHByZXNlcnZlcyB0aGUgb3JpZ2luYWwgc29ydCBvcmRlciBvZgogICAgICAgICAqIGVxdWFsIGVsZW1lbnRzLiBUaGUgaXRlcmF0ZWVzIGFyZSBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHsuLi4oRnVuY3Rpb258RnVuY3Rpb25bXSl9IFtpdGVyYXRlZXM9W18uaWRlbnRpdHldXQogICAgICAgICAqICBUaGUgaXRlcmF0ZWVzIHRvIHNvcnQgYnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgc29ydGVkIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2ZyZWQnLCAgICdhZ2UnOiA0OCB9LAogICAgICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAnYWdlJzogMzYgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgJ2FnZSc6IDMwIH0sCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNCB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uc29ydEJ5KHVzZXJzLCBbZnVuY3Rpb24obykgeyByZXR1cm4gby51c2VyOyB9XSk7CiAgICAgICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1snYmFybmV5JywgMzZdLCBbJ2Jhcm5leScsIDM0XSwgWydmcmVkJywgNDhdLCBbJ2ZyZWQnLCAzMF1dCiAgICAgICAgICoKICAgICAgICAgKiBfLnNvcnRCeSh1c2VycywgWyd1c2VyJywgJ2FnZSddKTsKICAgICAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbWydiYXJuZXknLCAzNF0sIFsnYmFybmV5JywgMzZdLCBbJ2ZyZWQnLCAzMF0sIFsnZnJlZCcsIDQ4XV0KICAgICAgICAgKi8KICAgICAgICB2YXIgc29ydEJ5ID0gYmFzZVJlc3QoZnVuY3Rpb24oY29sbGVjdGlvbiwgaXRlcmF0ZWVzKSB7CiAgICAgICAgICBpZiAoY29sbGVjdGlvbiA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBsZW5ndGggPSBpdGVyYXRlZXMubGVuZ3RoOwogICAgICAgICAgaWYgKGxlbmd0aCA+IDEgJiYgaXNJdGVyYXRlZUNhbGwoY29sbGVjdGlvbiwgaXRlcmF0ZWVzWzBdLCBpdGVyYXRlZXNbMV0pKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlcyA9IFtdOwogICAgICAgICAgfSBlbHNlIGlmIChsZW5ndGggPiAyICYmIGlzSXRlcmF0ZWVDYWxsKGl0ZXJhdGVlc1swXSwgaXRlcmF0ZWVzWzFdLCBpdGVyYXRlZXNbMl0pKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlcyA9IFtpdGVyYXRlZXNbMF1dOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VPcmRlckJ5KGNvbGxlY3Rpb24sIGJhc2VGbGF0dGVuKGl0ZXJhdGVlcywgMSksIFtdKTsKICAgICAgICB9KTsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSB0aW1lc3RhbXAgb2YgdGhlIG51bWJlciBvZiBtaWxsaXNlY29uZHMgdGhhdCBoYXZlIGVsYXBzZWQgc2luY2UKICAgICAgICAgKiB0aGUgVW5peCBlcG9jaCAoMSBKYW51YXJ5IDE5NzAgMDA6MDA6MDAgVVRDKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBEYXRlCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgdGltZXN0YW1wLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRlZmVyKGZ1bmN0aW9uKHN0YW1wKSB7CiAgICAgICAgICogICBjb25zb2xlLmxvZyhfLm5vdygpIC0gc3RhbXApOwogICAgICAgICAqIH0sIF8ubm93KCkpOwogICAgICAgICAqIC8vID0+IExvZ3MgdGhlIG51bWJlciBvZiBtaWxsaXNlY29uZHMgaXQgdG9vayBmb3IgdGhlIGRlZmVycmVkIGludm9jYXRpb24uCiAgICAgICAgICovCiAgICAgICAgdmFyIG5vdyA9IGN0eE5vdyB8fCBmdW5jdGlvbigpIHsKICAgICAgICAgIHJldHVybiByb290LkRhdGUubm93KCk7CiAgICAgICAgfTsKCiAgICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0qLwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3Bwb3NpdGUgb2YgYF8uYmVmb3JlYDsgdGhpcyBtZXRob2QgY3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaW52b2tlcwogICAgICAgICAqIGBmdW5jYCBvbmNlIGl0J3MgY2FsbGVkIGBuYCBvciBtb3JlIHRpbWVzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IG4gVGhlIG51bWJlciBvZiBjYWxscyBiZWZvcmUgYGZ1bmNgIGlzIGludm9rZWQuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gcmVzdHJpY3QuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgcmVzdHJpY3RlZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHNhdmVzID0gWydwcm9maWxlJywgJ3NldHRpbmdzJ107CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZG9uZSA9IF8uYWZ0ZXIoc2F2ZXMubGVuZ3RoLCBmdW5jdGlvbigpIHsKICAgICAgICAgKiAgIGNvbnNvbGUubG9nKCdkb25lIHNhdmluZyEnKTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKgogICAgICAgICAqIF8uZm9yRWFjaChzYXZlcywgZnVuY3Rpb24odHlwZSkgewogICAgICAgICAqICAgYXN5bmNTYXZlKHsgJ3R5cGUnOiB0eXBlLCAnY29tcGxldGUnOiBkb25lIH0pOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IExvZ3MgJ2RvbmUgc2F2aW5nIScgYWZ0ZXIgdGhlIHR3byBhc3luYyBzYXZlcyBoYXZlIGNvbXBsZXRlZC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBhZnRlcihuLCBmdW5jKSB7CiAgICAgICAgICBpZiAodHlwZW9mIGZ1bmMgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKEZVTkNfRVJST1JfVEVYVCk7CiAgICAgICAgICB9CiAgICAgICAgICBuID0gdG9JbnRlZ2VyKG4pOwogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgICBpZiAoLS1uIDwgMSkgewogICAgICAgICAgICAgIHJldHVybiBmdW5jLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBpbnZva2VzIGBmdW5jYCwgd2l0aCB1cCB0byBgbmAgYXJndW1lbnRzLAogICAgICAgICAqIGlnbm9yaW5nIGFueSBhZGRpdGlvbmFsIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNhcCBhcmd1bWVudHMgZm9yLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbj1mdW5jLmxlbmd0aF0gVGhlIGFyaXR5IGNhcC4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5tYXBgLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGNhcHBlZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5tYXAoWyc2JywgJzgnLCAnMTAnXSwgXy5hcnkocGFyc2VJbnQsIDEpKTsKICAgICAgICAgKiAvLyA9PiBbNiwgOCwgMTBdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gYXJ5KGZ1bmMsIG4sIGd1YXJkKSB7CiAgICAgICAgICBuID0gZ3VhcmQgPyB1bmRlZmluZWQkMSA6IG47CiAgICAgICAgICBuID0gKGZ1bmMgJiYgbiA9PSBudWxsKSA/IGZ1bmMubGVuZ3RoIDogbjsKICAgICAgICAgIHJldHVybiBjcmVhdGVXcmFwKGZ1bmMsIFdSQVBfQVJZX0ZMQUcsIHVuZGVmaW5lZCQxLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIHVuZGVmaW5lZCQxLCBuKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgYGZ1bmNgLCB3aXRoIHRoZSBgdGhpc2AgYmluZGluZyBhbmQgYXJndW1lbnRzCiAgICAgICAgICogb2YgdGhlIGNyZWF0ZWQgZnVuY3Rpb24sIHdoaWxlIGl0J3MgY2FsbGVkIGxlc3MgdGhhbiBgbmAgdGltZXMuIFN1YnNlcXVlbnQKICAgICAgICAgKiBjYWxscyB0byB0aGUgY3JlYXRlZCBmdW5jdGlvbiByZXR1cm4gdGhlIHJlc3VsdCBvZiB0aGUgbGFzdCBgZnVuY2AgaW52b2NhdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBuIFRoZSBudW1iZXIgb2YgY2FsbHMgYXQgd2hpY2ggYGZ1bmNgIGlzIG5vIGxvbmdlciBpbnZva2VkLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHJlc3RyaWN0LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHJlc3RyaWN0ZWQgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGpRdWVyeShlbGVtZW50KS5vbignY2xpY2snLCBfLmJlZm9yZSg1LCBhZGRDb250YWN0VG9MaXN0KSk7CiAgICAgICAgICogLy8gPT4gQWxsb3dzIGFkZGluZyB1cCB0byA0IGNvbnRhY3RzIHRvIHRoZSBsaXN0LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGJlZm9yZShuLCBmdW5jKSB7CiAgICAgICAgICB2YXIgcmVzdWx0OwogICAgICAgICAgaWYgKHR5cGVvZiBmdW5jICE9ICdmdW5jdGlvbicpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcihGVU5DX0VSUk9SX1RFWFQpOwogICAgICAgICAgfQogICAgICAgICAgbiA9IHRvSW50ZWdlcihuKTsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgaWYgKC0tbiA+IDApIHsKICAgICAgICAgICAgICByZXN1bHQgPSBmdW5jLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG4gPD0gMSkgewogICAgICAgICAgICAgIGZ1bmMgPSB1bmRlZmluZWQkMTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgYGZ1bmNgIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIGB0aGlzQXJnYAogICAgICAgICAqIGFuZCBgcGFydGlhbHNgIHByZXBlbmRlZCB0byB0aGUgYXJndW1lbnRzIGl0IHJlY2VpdmVzLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGBfLmJpbmQucGxhY2Vob2xkZXJgIHZhbHVlLCB3aGljaCBkZWZhdWx0cyB0byBgX2AgaW4gbW9ub2xpdGhpYyBidWlsZHMsCiAgICAgICAgICogbWF5IGJlIHVzZWQgYXMgYSBwbGFjZWhvbGRlciBmb3IgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVubGlrZSBuYXRpdmUgYEZ1bmN0aW9uI2JpbmRgLCB0aGlzIG1ldGhvZCBkb2Vzbid0IHNldCB0aGUgImxlbmd0aCIKICAgICAgICAgKiBwcm9wZXJ0eSBvZiBib3VuZCBmdW5jdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBiaW5kLgogICAgICAgICAqIEBwYXJhbSB7Kn0gdGhpc0FyZyBUaGUgYHRoaXNgIGJpbmRpbmcgb2YgYGZ1bmNgLgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gW3BhcnRpYWxzXSBUaGUgYXJndW1lbnRzIHRvIGJlIHBhcnRpYWxseSBhcHBsaWVkLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGJvdW5kIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBncmVldChncmVldGluZywgcHVuY3R1YXRpb24pIHsKICAgICAgICAgKiAgIHJldHVybiBncmVldGluZyArICcgJyArIHRoaXMudXNlciArIHB1bmN0dWF0aW9uOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICd1c2VyJzogJ2ZyZWQnIH07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYm91bmQgPSBfLmJpbmQoZ3JlZXQsIG9iamVjdCwgJ2hpJyk7CiAgICAgICAgICogYm91bmQoJyEnKTsKICAgICAgICAgKiAvLyA9PiAnaGkgZnJlZCEnCiAgICAgICAgICoKICAgICAgICAgKiAvLyBCb3VuZCB3aXRoIHBsYWNlaG9sZGVycy4KICAgICAgICAgKiB2YXIgYm91bmQgPSBfLmJpbmQoZ3JlZXQsIG9iamVjdCwgXywgJyEnKTsKICAgICAgICAgKiBib3VuZCgnaGknKTsKICAgICAgICAgKiAvLyA9PiAnaGkgZnJlZCEnCiAgICAgICAgICovCiAgICAgICAgdmFyIGJpbmQgPSBiYXNlUmVzdChmdW5jdGlvbihmdW5jLCB0aGlzQXJnLCBwYXJ0aWFscykgewogICAgICAgICAgdmFyIGJpdG1hc2sgPSBXUkFQX0JJTkRfRkxBRzsKICAgICAgICAgIGlmIChwYXJ0aWFscy5sZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGhvbGRlcnMgPSByZXBsYWNlSG9sZGVycyhwYXJ0aWFscywgZ2V0SG9sZGVyKGJpbmQpKTsKICAgICAgICAgICAgYml0bWFzayB8PSBXUkFQX1BBUlRJQUxfRkxBRzsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBjcmVhdGVXcmFwKGZ1bmMsIGJpdG1hc2ssIHRoaXNBcmcsIHBhcnRpYWxzLCBob2xkZXJzKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaW52b2tlcyB0aGUgbWV0aG9kIGF0IGBvYmplY3Rba2V5XWAgd2l0aCBgcGFydGlhbHNgCiAgICAgICAgICogcHJlcGVuZGVkIHRvIHRoZSBhcmd1bWVudHMgaXQgcmVjZWl2ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBkaWZmZXJzIGZyb20gYF8uYmluZGAgYnkgYWxsb3dpbmcgYm91bmQgZnVuY3Rpb25zIHRvIHJlZmVyZW5jZQogICAgICAgICAqIG1ldGhvZHMgdGhhdCBtYXkgYmUgcmVkZWZpbmVkIG9yIGRvbid0IHlldCBleGlzdC4gU2VlCiAgICAgICAgICogW1BldGVyIE1pY2hhdXgncyBhcnRpY2xlXShodHRwOi8vcGV0ZXIubWljaGF1eC5jYS9hcnRpY2xlcy9sYXp5LWZ1bmN0aW9uLWRlZmluaXRpb24tcGF0dGVybikKICAgICAgICAgKiBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGBfLmJpbmRLZXkucGxhY2Vob2xkZXJgIHZhbHVlLCB3aGljaCBkZWZhdWx0cyB0byBgX2AgaW4gbW9ub2xpdGhpYwogICAgICAgICAqIGJ1aWxkcywgbWF5IGJlIHVzZWQgYXMgYSBwbGFjZWhvbGRlciBmb3IgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMTAuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnZva2UgdGhlIG1ldGhvZCBvbi4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIG1ldGhvZC4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IFtwYXJ0aWFsc10gVGhlIGFyZ3VtZW50cyB0byBiZSBwYXJ0aWFsbHkgYXBwbGllZC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBib3VuZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsKICAgICAgICAgKiAgICd1c2VyJzogJ2ZyZWQnLAogICAgICAgICAqICAgJ2dyZWV0JzogZnVuY3Rpb24oZ3JlZXRpbmcsIHB1bmN0dWF0aW9uKSB7CiAgICAgICAgICogICAgIHJldHVybiBncmVldGluZyArICcgJyArIHRoaXMudXNlciArIHB1bmN0dWF0aW9uOwogICAgICAgICAqICAgfQogICAgICAgICAqIH07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYm91bmQgPSBfLmJpbmRLZXkob2JqZWN0LCAnZ3JlZXQnLCAnaGknKTsKICAgICAgICAgKiBib3VuZCgnIScpOwogICAgICAgICAqIC8vID0+ICdoaSBmcmVkIScKICAgICAgICAgKgogICAgICAgICAqIG9iamVjdC5ncmVldCA9IGZ1bmN0aW9uKGdyZWV0aW5nLCBwdW5jdHVhdGlvbikgewogICAgICAgICAqICAgcmV0dXJuIGdyZWV0aW5nICsgJ3lhICcgKyB0aGlzLnVzZXIgKyBwdW5jdHVhdGlvbjsKICAgICAgICAgKiB9OwogICAgICAgICAqCiAgICAgICAgICogYm91bmQoJyEnKTsKICAgICAgICAgKiAvLyA9PiAnaGl5YSBmcmVkIScKICAgICAgICAgKgogICAgICAgICAqIC8vIEJvdW5kIHdpdGggcGxhY2Vob2xkZXJzLgogICAgICAgICAqIHZhciBib3VuZCA9IF8uYmluZEtleShvYmplY3QsICdncmVldCcsIF8sICchJyk7CiAgICAgICAgICogYm91bmQoJ2hpJyk7CiAgICAgICAgICogLy8gPT4gJ2hpeWEgZnJlZCEnCiAgICAgICAgICovCiAgICAgICAgdmFyIGJpbmRLZXkgPSBiYXNlUmVzdChmdW5jdGlvbihvYmplY3QsIGtleSwgcGFydGlhbHMpIHsKICAgICAgICAgIHZhciBiaXRtYXNrID0gV1JBUF9CSU5EX0ZMQUcgfCBXUkFQX0JJTkRfS0VZX0ZMQUc7CiAgICAgICAgICBpZiAocGFydGlhbHMubGVuZ3RoKSB7CiAgICAgICAgICAgIHZhciBob2xkZXJzID0gcmVwbGFjZUhvbGRlcnMocGFydGlhbHMsIGdldEhvbGRlcihiaW5kS2V5KSk7CiAgICAgICAgICAgIGJpdG1hc2sgfD0gV1JBUF9QQVJUSUFMX0ZMQUc7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gY3JlYXRlV3JhcChrZXksIGJpdG1hc2ssIG9iamVjdCwgcGFydGlhbHMsIGhvbGRlcnMpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBhY2NlcHRzIGFyZ3VtZW50cyBvZiBgZnVuY2AgYW5kIGVpdGhlciBpbnZva2VzCiAgICAgICAgICogYGZ1bmNgIHJldHVybmluZyBpdHMgcmVzdWx0LCBpZiBhdCBsZWFzdCBgYXJpdHlgIG51bWJlciBvZiBhcmd1bWVudHMgaGF2ZQogICAgICAgICAqIGJlZW4gcHJvdmlkZWQsIG9yIHJldHVybnMgYSBmdW5jdGlvbiB0aGF0IGFjY2VwdHMgdGhlIHJlbWFpbmluZyBgZnVuY2AKICAgICAgICAgKiBhcmd1bWVudHMsIGFuZCBzbyBvbi4gVGhlIGFyaXR5IG9mIGBmdW5jYCBtYXkgYmUgc3BlY2lmaWVkIGlmIGBmdW5jLmxlbmd0aGAKICAgICAgICAgKiBpcyBub3Qgc3VmZmljaWVudC4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBgXy5jdXJyeS5wbGFjZWhvbGRlcmAgdmFsdWUsIHdoaWNoIGRlZmF1bHRzIHRvIGBfYCBpbiBtb25vbGl0aGljIGJ1aWxkcywKICAgICAgICAgKiBtYXkgYmUgdXNlZCBhcyBhIHBsYWNlaG9sZGVyIGZvciBwcm92aWRlZCBhcmd1bWVudHMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgZG9lc24ndCBzZXQgdGhlICJsZW5ndGgiIHByb3BlcnR5IG9mIGN1cnJpZWQgZnVuY3Rpb25zLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gY3VycnkuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFthcml0eT1mdW5jLmxlbmd0aF0gVGhlIGFyaXR5IG9mIGBmdW5jYC4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5tYXBgLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGN1cnJpZWQgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhYmMgPSBmdW5jdGlvbihhLCBiLCBjKSB7CiAgICAgICAgICogICByZXR1cm4gW2EsIGIsIGNdOwogICAgICAgICAqIH07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgY3VycmllZCA9IF8uY3VycnkoYWJjKTsKICAgICAgICAgKgogICAgICAgICAqIGN1cnJpZWQoMSkoMikoMyk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICoKICAgICAgICAgKiBjdXJyaWVkKDEsIDIpKDMpOwogICAgICAgICAqIC8vID0+IFsxLCAyLCAzXQogICAgICAgICAqCiAgICAgICAgICogY3VycmllZCgxLCAyLCAzKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMiwgM10KICAgICAgICAgKgogICAgICAgICAqIC8vIEN1cnJpZWQgd2l0aCBwbGFjZWhvbGRlcnMuCiAgICAgICAgICogY3VycmllZCgxKShfLCAzKSgyKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMiwgM10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjdXJyeShmdW5jLCBhcml0eSwgZ3VhcmQpIHsKICAgICAgICAgIGFyaXR5ID0gZ3VhcmQgPyB1bmRlZmluZWQkMSA6IGFyaXR5OwogICAgICAgICAgdmFyIHJlc3VsdCA9IGNyZWF0ZVdyYXAoZnVuYywgV1JBUF9DVVJSWV9GTEFHLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIHVuZGVmaW5lZCQxLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIGFyaXR5KTsKICAgICAgICAgIHJlc3VsdC5wbGFjZWhvbGRlciA9IGN1cnJ5LnBsYWNlaG9sZGVyOwogICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uY3VycnlgIGV4Y2VwdCB0aGF0IGFyZ3VtZW50cyBhcmUgYXBwbGllZCB0byBgZnVuY2AKICAgICAgICAgKiBpbiB0aGUgbWFubmVyIG9mIGBfLnBhcnRpYWxSaWdodGAgaW5zdGVhZCBvZiBgXy5wYXJ0aWFsYC4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBgXy5jdXJyeVJpZ2h0LnBsYWNlaG9sZGVyYCB2YWx1ZSwgd2hpY2ggZGVmYXVsdHMgdG8gYF9gIGluIG1vbm9saXRoaWMKICAgICAgICAgKiBidWlsZHMsIG1heSBiZSB1c2VkIGFzIGEgcGxhY2Vob2xkZXIgZm9yIHByb3ZpZGVkIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBkb2Vzbid0IHNldCB0aGUgImxlbmd0aCIgcHJvcGVydHkgb2YgY3VycmllZCBmdW5jdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBjdXJyeS4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2FyaXR5PWZ1bmMubGVuZ3RoXSBUaGUgYXJpdHkgb2YgYGZ1bmNgLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgY3VycmllZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFiYyA9IGZ1bmN0aW9uKGEsIGIsIGMpIHsKICAgICAgICAgKiAgIHJldHVybiBbYSwgYiwgY107CiAgICAgICAgICogfTsKICAgICAgICAgKgogICAgICAgICAqIHZhciBjdXJyaWVkID0gXy5jdXJyeVJpZ2h0KGFiYyk7CiAgICAgICAgICoKICAgICAgICAgKiBjdXJyaWVkKDMpKDIpKDEpOwogICAgICAgICAqIC8vID0+IFsxLCAyLCAzXQogICAgICAgICAqCiAgICAgICAgICogY3VycmllZCgyLCAzKSgxKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMiwgM10KICAgICAgICAgKgogICAgICAgICAqIGN1cnJpZWQoMSwgMiwgMyk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICoKICAgICAgICAgKiAvLyBDdXJyaWVkIHdpdGggcGxhY2Vob2xkZXJzLgogICAgICAgICAqIGN1cnJpZWQoMykoMSwgXykoMik7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3VycnlSaWdodChmdW5jLCBhcml0eSwgZ3VhcmQpIHsKICAgICAgICAgIGFyaXR5ID0gZ3VhcmQgPyB1bmRlZmluZWQkMSA6IGFyaXR5OwogICAgICAgICAgdmFyIHJlc3VsdCA9IGNyZWF0ZVdyYXAoZnVuYywgV1JBUF9DVVJSWV9SSUdIVF9GTEFHLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIHVuZGVmaW5lZCQxLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIGFyaXR5KTsKICAgICAgICAgIHJlc3VsdC5wbGFjZWhvbGRlciA9IGN1cnJ5UmlnaHQucGxhY2Vob2xkZXI7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGRlYm91bmNlZCBmdW5jdGlvbiB0aGF0IGRlbGF5cyBpbnZva2luZyBgZnVuY2AgdW50aWwgYWZ0ZXIgYHdhaXRgCiAgICAgICAgICogbWlsbGlzZWNvbmRzIGhhdmUgZWxhcHNlZCBzaW5jZSB0aGUgbGFzdCB0aW1lIHRoZSBkZWJvdW5jZWQgZnVuY3Rpb24gd2FzCiAgICAgICAgICogaW52b2tlZC4gVGhlIGRlYm91bmNlZCBmdW5jdGlvbiBjb21lcyB3aXRoIGEgYGNhbmNlbGAgbWV0aG9kIHRvIGNhbmNlbAogICAgICAgICAqIGRlbGF5ZWQgYGZ1bmNgIGludm9jYXRpb25zIGFuZCBhIGBmbHVzaGAgbWV0aG9kIHRvIGltbWVkaWF0ZWx5IGludm9rZSB0aGVtLgogICAgICAgICAqIFByb3ZpZGUgYG9wdGlvbnNgIHRvIGluZGljYXRlIHdoZXRoZXIgYGZ1bmNgIHNob3VsZCBiZSBpbnZva2VkIG9uIHRoZQogICAgICAgICAqIGxlYWRpbmcgYW5kL29yIHRyYWlsaW5nIGVkZ2Ugb2YgdGhlIGB3YWl0YCB0aW1lb3V0LiBUaGUgYGZ1bmNgIGlzIGludm9rZWQKICAgICAgICAgKiB3aXRoIHRoZSBsYXN0IGFyZ3VtZW50cyBwcm92aWRlZCB0byB0aGUgZGVib3VuY2VkIGZ1bmN0aW9uLiBTdWJzZXF1ZW50CiAgICAgICAgICogY2FsbHMgdG8gdGhlIGRlYm91bmNlZCBmdW5jdGlvbiByZXR1cm4gdGhlIHJlc3VsdCBvZiB0aGUgbGFzdCBgZnVuY2AKICAgICAgICAgKiBpbnZvY2F0aW9uLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIElmIGBsZWFkaW5nYCBhbmQgYHRyYWlsaW5nYCBvcHRpb25zIGFyZSBgdHJ1ZWAsIGBmdW5jYCBpcwogICAgICAgICAqIGludm9rZWQgb24gdGhlIHRyYWlsaW5nIGVkZ2Ugb2YgdGhlIHRpbWVvdXQgb25seSBpZiB0aGUgZGVib3VuY2VkIGZ1bmN0aW9uCiAgICAgICAgICogaXMgaW52b2tlZCBtb3JlIHRoYW4gb25jZSBkdXJpbmcgdGhlIGB3YWl0YCB0aW1lb3V0LgogICAgICAgICAqCiAgICAgICAgICogSWYgYHdhaXRgIGlzIGAwYCBhbmQgYGxlYWRpbmdgIGlzIGBmYWxzZWAsIGBmdW5jYCBpbnZvY2F0aW9uIGlzIGRlZmVycmVkCiAgICAgICAgICogdW50aWwgdG8gdGhlIG5leHQgdGljaywgc2ltaWxhciB0byBgc2V0VGltZW91dGAgd2l0aCBhIHRpbWVvdXQgb2YgYDBgLgogICAgICAgICAqCiAgICAgICAgICogU2VlIFtEYXZpZCBDb3JiYWNobydzIGFydGljbGVdKGh0dHBzOi8vY3NzLXRyaWNrcy5jb20vZGVib3VuY2luZy10aHJvdHRsaW5nLWV4cGxhaW5lZC1leGFtcGxlcy8pCiAgICAgICAgICogZm9yIGRldGFpbHMgb3ZlciB0aGUgZGlmZmVyZW5jZXMgYmV0d2VlbiBgXy5kZWJvdW5jZWAgYW5kIGBfLnRocm90dGxlYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRlYm91bmNlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbd2FpdD0wXSBUaGUgbnVtYmVyIG9mIG1pbGxpc2Vjb25kcyB0byBkZWxheS4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29wdGlvbnM9e31dIFRoZSBvcHRpb25zIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtvcHRpb25zLmxlYWRpbmc9ZmFsc2VdCiAgICAgICAgICogIFNwZWNpZnkgaW52b2tpbmcgb24gdGhlIGxlYWRpbmcgZWRnZSBvZiB0aGUgdGltZW91dC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW29wdGlvbnMubWF4V2FpdF0KICAgICAgICAgKiAgVGhlIG1heGltdW0gdGltZSBgZnVuY2AgaXMgYWxsb3dlZCB0byBiZSBkZWxheWVkIGJlZm9yZSBpdCdzIGludm9rZWQuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbb3B0aW9ucy50cmFpbGluZz10cnVlXQogICAgICAgICAqICBTcGVjaWZ5IGludm9raW5nIG9uIHRoZSB0cmFpbGluZyBlZGdlIG9mIHRoZSB0aW1lb3V0LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGRlYm91bmNlZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogLy8gQXZvaWQgY29zdGx5IGNhbGN1bGF0aW9ucyB3aGlsZSB0aGUgd2luZG93IHNpemUgaXMgaW4gZmx1eC4KICAgICAgICAgKiBqUXVlcnkod2luZG93KS5vbigncmVzaXplJywgXy5kZWJvdW5jZShjYWxjdWxhdGVMYXlvdXQsIDE1MCkpOwogICAgICAgICAqCiAgICAgICAgICogLy8gSW52b2tlIGBzZW5kTWFpbGAgd2hlbiBjbGlja2VkLCBkZWJvdW5jaW5nIHN1YnNlcXVlbnQgY2FsbHMuCiAgICAgICAgICogalF1ZXJ5KGVsZW1lbnQpLm9uKCdjbGljaycsIF8uZGVib3VuY2Uoc2VuZE1haWwsIDMwMCwgewogICAgICAgICAqICAgJ2xlYWRpbmcnOiB0cnVlLAogICAgICAgICAqICAgJ3RyYWlsaW5nJzogZmFsc2UKICAgICAgICAgKiB9KSk7CiAgICAgICAgICoKICAgICAgICAgKiAvLyBFbnN1cmUgYGJhdGNoTG9nYCBpcyBpbnZva2VkIG9uY2UgYWZ0ZXIgMSBzZWNvbmQgb2YgZGVib3VuY2VkIGNhbGxzLgogICAgICAgICAqIHZhciBkZWJvdW5jZWQgPSBfLmRlYm91bmNlKGJhdGNoTG9nLCAyNTAsIHsgJ21heFdhaXQnOiAxMDAwIH0pOwogICAgICAgICAqIHZhciBzb3VyY2UgPSBuZXcgRXZlbnRTb3VyY2UoJy9zdHJlYW0nKTsKICAgICAgICAgKiBqUXVlcnkoc291cmNlKS5vbignbWVzc2FnZScsIGRlYm91bmNlZCk7CiAgICAgICAgICoKICAgICAgICAgKiAvLyBDYW5jZWwgdGhlIHRyYWlsaW5nIGRlYm91bmNlZCBpbnZvY2F0aW9uLgogICAgICAgICAqIGpRdWVyeSh3aW5kb3cpLm9uKCdwb3BzdGF0ZScsIGRlYm91bmNlZC5jYW5jZWwpOwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGRlYm91bmNlKGZ1bmMsIHdhaXQsIG9wdGlvbnMpIHsKICAgICAgICAgIHZhciBsYXN0QXJncywKICAgICAgICAgICAgICBsYXN0VGhpcywKICAgICAgICAgICAgICBtYXhXYWl0LAogICAgICAgICAgICAgIHJlc3VsdCwKICAgICAgICAgICAgICB0aW1lcklkLAogICAgICAgICAgICAgIGxhc3RDYWxsVGltZSwKICAgICAgICAgICAgICBsYXN0SW52b2tlVGltZSA9IDAsCiAgICAgICAgICAgICAgbGVhZGluZyA9IGZhbHNlLAogICAgICAgICAgICAgIG1heGluZyA9IGZhbHNlLAogICAgICAgICAgICAgIHRyYWlsaW5nID0gdHJ1ZTsKCiAgICAgICAgICBpZiAodHlwZW9mIGZ1bmMgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKEZVTkNfRVJST1JfVEVYVCk7CiAgICAgICAgICB9CiAgICAgICAgICB3YWl0ID0gdG9OdW1iZXIod2FpdCkgfHwgMDsKICAgICAgICAgIGlmIChpc09iamVjdChvcHRpb25zKSkgewogICAgICAgICAgICBsZWFkaW5nID0gISFvcHRpb25zLmxlYWRpbmc7CiAgICAgICAgICAgIG1heGluZyA9ICdtYXhXYWl0JyBpbiBvcHRpb25zOwogICAgICAgICAgICBtYXhXYWl0ID0gbWF4aW5nID8gbmF0aXZlTWF4KHRvTnVtYmVyKG9wdGlvbnMubWF4V2FpdCkgfHwgMCwgd2FpdCkgOiBtYXhXYWl0OwogICAgICAgICAgICB0cmFpbGluZyA9ICd0cmFpbGluZycgaW4gb3B0aW9ucyA/ICEhb3B0aW9ucy50cmFpbGluZyA6IHRyYWlsaW5nOwogICAgICAgICAgfQoKICAgICAgICAgIGZ1bmN0aW9uIGludm9rZUZ1bmModGltZSkgewogICAgICAgICAgICB2YXIgYXJncyA9IGxhc3RBcmdzLAogICAgICAgICAgICAgICAgdGhpc0FyZyA9IGxhc3RUaGlzOwoKICAgICAgICAgICAgbGFzdEFyZ3MgPSBsYXN0VGhpcyA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgICBsYXN0SW52b2tlVGltZSA9IHRpbWU7CiAgICAgICAgICAgIHJlc3VsdCA9IGZ1bmMuYXBwbHkodGhpc0FyZywgYXJncyk7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9CgogICAgICAgICAgZnVuY3Rpb24gbGVhZGluZ0VkZ2UodGltZSkgewogICAgICAgICAgICAvLyBSZXNldCBhbnkgYG1heFdhaXRgIHRpbWVyLgogICAgICAgICAgICBsYXN0SW52b2tlVGltZSA9IHRpbWU7CiAgICAgICAgICAgIC8vIFN0YXJ0IHRoZSB0aW1lciBmb3IgdGhlIHRyYWlsaW5nIGVkZ2UuCiAgICAgICAgICAgIHRpbWVySWQgPSBzZXRUaW1lb3V0KHRpbWVyRXhwaXJlZCwgd2FpdCk7CiAgICAgICAgICAgIC8vIEludm9rZSB0aGUgbGVhZGluZyBlZGdlLgogICAgICAgICAgICByZXR1cm4gbGVhZGluZyA/IGludm9rZUZ1bmModGltZSkgOiByZXN1bHQ7CiAgICAgICAgICB9CgogICAgICAgICAgZnVuY3Rpb24gcmVtYWluaW5nV2FpdCh0aW1lKSB7CiAgICAgICAgICAgIHZhciB0aW1lU2luY2VMYXN0Q2FsbCA9IHRpbWUgLSBsYXN0Q2FsbFRpbWUsCiAgICAgICAgICAgICAgICB0aW1lU2luY2VMYXN0SW52b2tlID0gdGltZSAtIGxhc3RJbnZva2VUaW1lLAogICAgICAgICAgICAgICAgdGltZVdhaXRpbmcgPSB3YWl0IC0gdGltZVNpbmNlTGFzdENhbGw7CgogICAgICAgICAgICByZXR1cm4gbWF4aW5nCiAgICAgICAgICAgICAgPyBuYXRpdmVNaW4odGltZVdhaXRpbmcsIG1heFdhaXQgLSB0aW1lU2luY2VMYXN0SW52b2tlKQogICAgICAgICAgICAgIDogdGltZVdhaXRpbmc7CiAgICAgICAgICB9CgogICAgICAgICAgZnVuY3Rpb24gc2hvdWxkSW52b2tlKHRpbWUpIHsKICAgICAgICAgICAgdmFyIHRpbWVTaW5jZUxhc3RDYWxsID0gdGltZSAtIGxhc3RDYWxsVGltZSwKICAgICAgICAgICAgICAgIHRpbWVTaW5jZUxhc3RJbnZva2UgPSB0aW1lIC0gbGFzdEludm9rZVRpbWU7CgogICAgICAgICAgICAvLyBFaXRoZXIgdGhpcyBpcyB0aGUgZmlyc3QgY2FsbCwgYWN0aXZpdHkgaGFzIHN0b3BwZWQgYW5kIHdlJ3JlIGF0IHRoZQogICAgICAgICAgICAvLyB0cmFpbGluZyBlZGdlLCB0aGUgc3lzdGVtIHRpbWUgaGFzIGdvbmUgYmFja3dhcmRzIGFuZCB3ZSdyZSB0cmVhdGluZwogICAgICAgICAgICAvLyBpdCBhcyB0aGUgdHJhaWxpbmcgZWRnZSwgb3Igd2UndmUgaGl0IHRoZSBgbWF4V2FpdGAgbGltaXQuCiAgICAgICAgICAgIHJldHVybiAobGFzdENhbGxUaW1lID09PSB1bmRlZmluZWQkMSB8fCAodGltZVNpbmNlTGFzdENhbGwgPj0gd2FpdCkgfHwKICAgICAgICAgICAgICAodGltZVNpbmNlTGFzdENhbGwgPCAwKSB8fCAobWF4aW5nICYmIHRpbWVTaW5jZUxhc3RJbnZva2UgPj0gbWF4V2FpdCkpOwogICAgICAgICAgfQoKICAgICAgICAgIGZ1bmN0aW9uIHRpbWVyRXhwaXJlZCgpIHsKICAgICAgICAgICAgdmFyIHRpbWUgPSBub3coKTsKICAgICAgICAgICAgaWYgKHNob3VsZEludm9rZSh0aW1lKSkgewogICAgICAgICAgICAgIHJldHVybiB0cmFpbGluZ0VkZ2UodGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVzdGFydCB0aGUgdGltZXIuCiAgICAgICAgICAgIHRpbWVySWQgPSBzZXRUaW1lb3V0KHRpbWVyRXhwaXJlZCwgcmVtYWluaW5nV2FpdCh0aW1lKSk7CiAgICAgICAgICB9CgogICAgICAgICAgZnVuY3Rpb24gdHJhaWxpbmdFZGdlKHRpbWUpIHsKICAgICAgICAgICAgdGltZXJJZCA9IHVuZGVmaW5lZCQxOwoKICAgICAgICAgICAgLy8gT25seSBpbnZva2UgaWYgd2UgaGF2ZSBgbGFzdEFyZ3NgIHdoaWNoIG1lYW5zIGBmdW5jYCBoYXMgYmVlbgogICAgICAgICAgICAvLyBkZWJvdW5jZWQgYXQgbGVhc3Qgb25jZS4KICAgICAgICAgICAgaWYgKHRyYWlsaW5nICYmIGxhc3RBcmdzKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGludm9rZUZ1bmModGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGFzdEFyZ3MgPSBsYXN0VGhpcyA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgfQoKICAgICAgICAgIGZ1bmN0aW9uIGNhbmNlbCgpIHsKICAgICAgICAgICAgaWYgKHRpbWVySWQgIT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgY2xlYXJUaW1lb3V0KHRpbWVySWQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxhc3RJbnZva2VUaW1lID0gMDsKICAgICAgICAgICAgbGFzdEFyZ3MgPSBsYXN0Q2FsbFRpbWUgPSBsYXN0VGhpcyA9IHRpbWVySWQgPSB1bmRlZmluZWQkMTsKICAgICAgICAgIH0KCiAgICAgICAgICBmdW5jdGlvbiBmbHVzaCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRpbWVySWQgPT09IHVuZGVmaW5lZCQxID8gcmVzdWx0IDogdHJhaWxpbmdFZGdlKG5vdygpKTsKICAgICAgICAgIH0KCiAgICAgICAgICBmdW5jdGlvbiBkZWJvdW5jZWQoKSB7CiAgICAgICAgICAgIHZhciB0aW1lID0gbm93KCksCiAgICAgICAgICAgICAgICBpc0ludm9raW5nID0gc2hvdWxkSW52b2tlKHRpbWUpOwoKICAgICAgICAgICAgbGFzdEFyZ3MgPSBhcmd1bWVudHM7CiAgICAgICAgICAgIGxhc3RUaGlzID0gdGhpczsKICAgICAgICAgICAgbGFzdENhbGxUaW1lID0gdGltZTsKCiAgICAgICAgICAgIGlmIChpc0ludm9raW5nKSB7CiAgICAgICAgICAgICAgaWYgKHRpbWVySWQgPT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbGVhZGluZ0VkZ2UobGFzdENhbGxUaW1lKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKG1heGluZykgewogICAgICAgICAgICAgICAgLy8gSGFuZGxlIGludm9jYXRpb25zIGluIGEgdGlnaHQgbG9vcC4KICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dCh0aW1lcklkKTsKICAgICAgICAgICAgICAgIHRpbWVySWQgPSBzZXRUaW1lb3V0KHRpbWVyRXhwaXJlZCwgd2FpdCk7CiAgICAgICAgICAgICAgICByZXR1cm4gaW52b2tlRnVuYyhsYXN0Q2FsbFRpbWUpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGltZXJJZCA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICB0aW1lcklkID0gc2V0VGltZW91dCh0aW1lckV4cGlyZWQsIHdhaXQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9CiAgICAgICAgICBkZWJvdW5jZWQuY2FuY2VsID0gY2FuY2VsOwogICAgICAgICAgZGVib3VuY2VkLmZsdXNoID0gZmx1c2g7CiAgICAgICAgICByZXR1cm4gZGVib3VuY2VkOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRGVmZXJzIGludm9raW5nIHRoZSBgZnVuY2AgdW50aWwgdGhlIGN1cnJlbnQgY2FsbCBzdGFjayBoYXMgY2xlYXJlZC4gQW55CiAgICAgICAgICogYWRkaXRpb25hbCBhcmd1bWVudHMgYXJlIHByb3ZpZGVkIHRvIGBmdW5jYCB3aGVuIGl0J3MgaW52b2tlZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRlZmVyLgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gW2FyZ3NdIFRoZSBhcmd1bWVudHMgdG8gaW52b2tlIGBmdW5jYCB3aXRoLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHRpbWVyIGlkLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRlZmVyKGZ1bmN0aW9uKHRleHQpIHsKICAgICAgICAgKiAgIGNvbnNvbGUubG9nKHRleHQpOwogICAgICAgICAqIH0sICdkZWZlcnJlZCcpOwogICAgICAgICAqIC8vID0+IExvZ3MgJ2RlZmVycmVkJyBhZnRlciBvbmUgbWlsbGlzZWNvbmQuCiAgICAgICAgICovCiAgICAgICAgdmFyIGRlZmVyID0gYmFzZVJlc3QoZnVuY3Rpb24oZnVuYywgYXJncykgewogICAgICAgICAgcmV0dXJuIGJhc2VEZWxheShmdW5jLCAxLCBhcmdzKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogSW52b2tlcyBgZnVuY2AgYWZ0ZXIgYHdhaXRgIG1pbGxpc2Vjb25kcy4gQW55IGFkZGl0aW9uYWwgYXJndW1lbnRzIGFyZQogICAgICAgICAqIHByb3ZpZGVkIHRvIGBmdW5jYCB3aGVuIGl0J3MgaW52b2tlZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRlbGF5LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSB3YWl0IFRoZSBudW1iZXIgb2YgbWlsbGlzZWNvbmRzIHRvIGRlbGF5IGludm9jYXRpb24uCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBbYXJnc10gVGhlIGFyZ3VtZW50cyB0byBpbnZva2UgYGZ1bmNgIHdpdGguCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgdGltZXIgaWQuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZGVsYXkoZnVuY3Rpb24odGV4dCkgewogICAgICAgICAqICAgY29uc29sZS5sb2codGV4dCk7CiAgICAgICAgICogfSwgMTAwMCwgJ2xhdGVyJyk7CiAgICAgICAgICogLy8gPT4gTG9ncyAnbGF0ZXInIGFmdGVyIG9uZSBzZWNvbmQuCiAgICAgICAgICovCiAgICAgICAgdmFyIGRlbGF5ID0gYmFzZVJlc3QoZnVuY3Rpb24oZnVuYywgd2FpdCwgYXJncykgewogICAgICAgICAgcmV0dXJuIGJhc2VEZWxheShmdW5jLCB0b051bWJlcih3YWl0KSB8fCAwLCBhcmdzKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaW52b2tlcyBgZnVuY2Agd2l0aCBhcmd1bWVudHMgcmV2ZXJzZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBmbGlwIGFyZ3VtZW50cyBmb3IuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZmxpcHBlZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGZsaXBwZWQgPSBfLmZsaXAoZnVuY3Rpb24oKSB7CiAgICAgICAgICogICByZXR1cm4gXy50b0FycmF5KGFyZ3VtZW50cyk7CiAgICAgICAgICogfSk7CiAgICAgICAgICoKICAgICAgICAgKiBmbGlwcGVkKCdhJywgJ2InLCAnYycsICdkJyk7CiAgICAgICAgICogLy8gPT4gWydkJywgJ2MnLCAnYicsICdhJ10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmbGlwKGZ1bmMpIHsKICAgICAgICAgIHJldHVybiBjcmVhdGVXcmFwKGZ1bmMsIFdSQVBfRkxJUF9GTEFHKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IG1lbW9pemVzIHRoZSByZXN1bHQgb2YgYGZ1bmNgLiBJZiBgcmVzb2x2ZXJgIGlzCiAgICAgICAgICogcHJvdmlkZWQsIGl0IGRldGVybWluZXMgdGhlIGNhY2hlIGtleSBmb3Igc3RvcmluZyB0aGUgcmVzdWx0IGJhc2VkIG9uIHRoZQogICAgICAgICAqIGFyZ3VtZW50cyBwcm92aWRlZCB0byB0aGUgbWVtb2l6ZWQgZnVuY3Rpb24uIEJ5IGRlZmF1bHQsIHRoZSBmaXJzdCBhcmd1bWVudAogICAgICAgICAqIHByb3ZpZGVkIHRvIHRoZSBtZW1vaXplZCBmdW5jdGlvbiBpcyB1c2VkIGFzIHRoZSBtYXAgY2FjaGUga2V5LiBUaGUgYGZ1bmNgCiAgICAgICAgICogaXMgaW52b2tlZCB3aXRoIHRoZSBgdGhpc2AgYmluZGluZyBvZiB0aGUgbWVtb2l6ZWQgZnVuY3Rpb24uCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhlIGNhY2hlIGlzIGV4cG9zZWQgYXMgdGhlIGBjYWNoZWAgcHJvcGVydHkgb24gdGhlIG1lbW9pemVkCiAgICAgICAgICogZnVuY3Rpb24uIEl0cyBjcmVhdGlvbiBtYXkgYmUgY3VzdG9taXplZCBieSByZXBsYWNpbmcgdGhlIGBfLm1lbW9pemUuQ2FjaGVgCiAgICAgICAgICogY29uc3RydWN0b3Igd2l0aCBvbmUgd2hvc2UgaW5zdGFuY2VzIGltcGxlbWVudCB0aGUKICAgICAgICAgKiBbYE1hcGBdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXByb3BlcnRpZXMtb2YtdGhlLW1hcC1wcm90b3R5cGUtb2JqZWN0KQogICAgICAgICAqIG1ldGhvZCBpbnRlcmZhY2Ugb2YgYGNsZWFyYCwgYGRlbGV0ZWAsIGBnZXRgLCBgaGFzYCwgYW5kIGBzZXRgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gaGF2ZSBpdHMgb3V0cHV0IG1lbW9pemVkLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtyZXNvbHZlcl0gVGhlIGZ1bmN0aW9uIHRvIHJlc29sdmUgdGhlIGNhY2hlIGtleS4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBtZW1vaXplZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiAxLCAnYic6IDIgfTsKICAgICAgICAgKiB2YXIgb3RoZXIgPSB7ICdjJzogMywgJ2QnOiA0IH07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdmFsdWVzID0gXy5tZW1vaXplKF8udmFsdWVzKTsKICAgICAgICAgKiB2YWx1ZXMob2JqZWN0KTsKICAgICAgICAgKiAvLyA9PiBbMSwgMl0KICAgICAgICAgKgogICAgICAgICAqIHZhbHVlcyhvdGhlcik7CiAgICAgICAgICogLy8gPT4gWzMsIDRdCiAgICAgICAgICoKICAgICAgICAgKiBvYmplY3QuYSA9IDI7CiAgICAgICAgICogdmFsdWVzKG9iamVjdCk7CiAgICAgICAgICogLy8gPT4gWzEsIDJdCiAgICAgICAgICoKICAgICAgICAgKiAvLyBNb2RpZnkgdGhlIHJlc3VsdCBjYWNoZS4KICAgICAgICAgKiB2YWx1ZXMuY2FjaGUuc2V0KG9iamVjdCwgWydhJywgJ2InXSk7CiAgICAgICAgICogdmFsdWVzKG9iamVjdCk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InXQogICAgICAgICAqCiAgICAgICAgICogLy8gUmVwbGFjZSBgXy5tZW1vaXplLkNhY2hlYC4KICAgICAgICAgKiBfLm1lbW9pemUuQ2FjaGUgPSBXZWFrTWFwOwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1lbW9pemUoZnVuYywgcmVzb2x2ZXIpIHsKICAgICAgICAgIGlmICh0eXBlb2YgZnVuYyAhPSAnZnVuY3Rpb24nIHx8IChyZXNvbHZlciAhPSBudWxsICYmIHR5cGVvZiByZXNvbHZlciAhPSAnZnVuY3Rpb24nKSkgewogICAgICAgICAgICB0aHJvdyBuZXcgVHlwZUVycm9yKEZVTkNfRVJST1JfVEVYVCk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgbWVtb2l6ZWQgPSBmdW5jdGlvbigpIHsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHMsCiAgICAgICAgICAgICAgICBrZXkgPSByZXNvbHZlciA/IHJlc29sdmVyLmFwcGx5KHRoaXMsIGFyZ3MpIDogYXJnc1swXSwKICAgICAgICAgICAgICAgIGNhY2hlID0gbWVtb2l6ZWQuY2FjaGU7CgogICAgICAgICAgICBpZiAoY2FjaGUuaGFzKGtleSkpIHsKICAgICAgICAgICAgICByZXR1cm4gY2FjaGUuZ2V0KGtleSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHJlc3VsdCA9IGZ1bmMuYXBwbHkodGhpcywgYXJncyk7CiAgICAgICAgICAgIG1lbW9pemVkLmNhY2hlID0gY2FjaGUuc2V0KGtleSwgcmVzdWx0KSB8fCBjYWNoZTsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH07CiAgICAgICAgICBtZW1vaXplZC5jYWNoZSA9IG5ldyAobWVtb2l6ZS5DYWNoZSB8fCBNYXBDYWNoZSk7CiAgICAgICAgICByZXR1cm4gbWVtb2l6ZWQ7CiAgICAgICAgfQoKICAgICAgICAvLyBFeHBvc2UgYE1hcENhY2hlYC4KICAgICAgICBtZW1vaXplLkNhY2hlID0gTWFwQ2FjaGU7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IG5lZ2F0ZXMgdGhlIHJlc3VsdCBvZiB0aGUgcHJlZGljYXRlIGBmdW5jYC4gVGhlCiAgICAgICAgICogYGZ1bmNgIHByZWRpY2F0ZSBpcyBpbnZva2VkIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIGFuZCBhcmd1bWVudHMgb2YgdGhlCiAgICAgICAgICogY3JlYXRlZCBmdW5jdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgcHJlZGljYXRlIHRvIG5lZ2F0ZS4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBuZWdhdGVkIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBpc0V2ZW4obikgewogICAgICAgICAqICAgcmV0dXJuIG4gJSAyID09IDA7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogXy5maWx0ZXIoWzEsIDIsIDMsIDQsIDUsIDZdLCBfLm5lZ2F0ZShpc0V2ZW4pKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMywgNV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBuZWdhdGUocHJlZGljYXRlKSB7CiAgICAgICAgICBpZiAodHlwZW9mIHByZWRpY2F0ZSAhPSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoRlVOQ19FUlJPUl9URVhUKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHM7CiAgICAgICAgICAgIHN3aXRjaCAoYXJncy5sZW5ndGgpIHsKICAgICAgICAgICAgICBjYXNlIDA6IHJldHVybiAhcHJlZGljYXRlLmNhbGwodGhpcyk7CiAgICAgICAgICAgICAgY2FzZSAxOiByZXR1cm4gIXByZWRpY2F0ZS5jYWxsKHRoaXMsIGFyZ3NbMF0pOwogICAgICAgICAgICAgIGNhc2UgMjogcmV0dXJuICFwcmVkaWNhdGUuY2FsbCh0aGlzLCBhcmdzWzBdLCBhcmdzWzFdKTsKICAgICAgICAgICAgICBjYXNlIDM6IHJldHVybiAhcHJlZGljYXRlLmNhbGwodGhpcywgYXJnc1swXSwgYXJnc1sxXSwgYXJnc1syXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuICFwcmVkaWNhdGUuYXBwbHkodGhpcywgYXJncyk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaXMgcmVzdHJpY3RlZCB0byBpbnZva2luZyBgZnVuY2Agb25jZS4gUmVwZWF0IGNhbGxzCiAgICAgICAgICogdG8gdGhlIGZ1bmN0aW9uIHJldHVybiB0aGUgdmFsdWUgb2YgdGhlIGZpcnN0IGludm9jYXRpb24uIFRoZSBgZnVuY2AgaXMKICAgICAgICAgKiBpbnZva2VkIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIGFuZCBhcmd1bWVudHMgb2YgdGhlIGNyZWF0ZWQgZnVuY3Rpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byByZXN0cmljdC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyByZXN0cmljdGVkIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgaW5pdGlhbGl6ZSA9IF8ub25jZShjcmVhdGVBcHBsaWNhdGlvbik7CiAgICAgICAgICogaW5pdGlhbGl6ZSgpOwogICAgICAgICAqIGluaXRpYWxpemUoKTsKICAgICAgICAgKiAvLyA9PiBgY3JlYXRlQXBwbGljYXRpb25gIGlzIGludm9rZWQgb25jZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG9uY2UoZnVuYykgewogICAgICAgICAgcmV0dXJuIGJlZm9yZSgyLCBmdW5jKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgYGZ1bmNgIHdpdGggaXRzIGFyZ3VtZW50cyB0cmFuc2Zvcm1lZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHsuLi4oRnVuY3Rpb258RnVuY3Rpb25bXSl9IFt0cmFuc2Zvcm1zPVtfLmlkZW50aXR5XV0KICAgICAgICAgKiAgVGhlIGFyZ3VtZW50IHRyYW5zZm9ybXMuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGRvdWJsZWQobikgewogICAgICAgICAqICAgcmV0dXJuIG4gKiAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIHNxdWFyZShuKSB7CiAgICAgICAgICogICByZXR1cm4gbiAqIG47CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogdmFyIGZ1bmMgPSBfLm92ZXJBcmdzKGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICAgKiAgIHJldHVybiBbeCwgeV07CiAgICAgICAgICogfSwgW3NxdWFyZSwgZG91YmxlZF0pOwogICAgICAgICAqCiAgICAgICAgICogZnVuYyg5LCAzKTsKICAgICAgICAgKiAvLyA9PiBbODEsIDZdCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jKDEwLCA1KTsKICAgICAgICAgKiAvLyA9PiBbMTAwLCAxMF0KICAgICAgICAgKi8KICAgICAgICB2YXIgb3ZlckFyZ3MgPSBjYXN0UmVzdChmdW5jdGlvbihmdW5jLCB0cmFuc2Zvcm1zKSB7CiAgICAgICAgICB0cmFuc2Zvcm1zID0gKHRyYW5zZm9ybXMubGVuZ3RoID09IDEgJiYgaXNBcnJheSh0cmFuc2Zvcm1zWzBdKSkKICAgICAgICAgICAgPyBhcnJheU1hcCh0cmFuc2Zvcm1zWzBdLCBiYXNlVW5hcnkoZ2V0SXRlcmF0ZWUoKSkpCiAgICAgICAgICAgIDogYXJyYXlNYXAoYmFzZUZsYXR0ZW4odHJhbnNmb3JtcywgMSksIGJhc2VVbmFyeShnZXRJdGVyYXRlZSgpKSk7CgogICAgICAgICAgdmFyIGZ1bmNzTGVuZ3RoID0gdHJhbnNmb3Jtcy5sZW5ndGg7CiAgICAgICAgICByZXR1cm4gYmFzZVJlc3QoZnVuY3Rpb24oYXJncykgewogICAgICAgICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgICAgICAgIGxlbmd0aCA9IG5hdGl2ZU1pbihhcmdzLmxlbmd0aCwgZnVuY3NMZW5ndGgpOwoKICAgICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgICBhcmdzW2luZGV4XSA9IHRyYW5zZm9ybXNbaW5kZXhdLmNhbGwodGhpcywgYXJnc1tpbmRleF0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBhcHBseShmdW5jLCB0aGlzLCBhcmdzKTsKICAgICAgICAgIH0pOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBpbnZva2VzIGBmdW5jYCB3aXRoIGBwYXJ0aWFsc2AgcHJlcGVuZGVkIHRvIHRoZQogICAgICAgICAqIGFyZ3VtZW50cyBpdCByZWNlaXZlcy4gVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5iaW5kYCBleGNlcHQgaXQgZG9lcyAqKm5vdCoqCiAgICAgICAgICogYWx0ZXIgdGhlIGB0aGlzYCBiaW5kaW5nLgogICAgICAgICAqCiAgICAgICAgICogVGhlIGBfLnBhcnRpYWwucGxhY2Vob2xkZXJgIHZhbHVlLCB3aGljaCBkZWZhdWx0cyB0byBgX2AgaW4gbW9ub2xpdGhpYwogICAgICAgICAqIGJ1aWxkcywgbWF5IGJlIHVzZWQgYXMgYSBwbGFjZWhvbGRlciBmb3IgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIGRvZXNuJ3Qgc2V0IHRoZSAibGVuZ3RoIiBwcm9wZXJ0eSBvZiBwYXJ0aWFsbHkKICAgICAgICAgKiBhcHBsaWVkIGZ1bmN0aW9ucy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjIuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHBhcnRpYWxseSBhcHBseSBhcmd1bWVudHMgdG8uCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBbcGFydGlhbHNdIFRoZSBhcmd1bWVudHMgdG8gYmUgcGFydGlhbGx5IGFwcGxpZWQuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgcGFydGlhbGx5IGFwcGxpZWQgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGdyZWV0KGdyZWV0aW5nLCBuYW1lKSB7CiAgICAgICAgICogICByZXR1cm4gZ3JlZXRpbmcgKyAnICcgKyBuYW1lOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciBzYXlIZWxsb1RvID0gXy5wYXJ0aWFsKGdyZWV0LCAnaGVsbG8nKTsKICAgICAgICAgKiBzYXlIZWxsb1RvKCdmcmVkJyk7CiAgICAgICAgICogLy8gPT4gJ2hlbGxvIGZyZWQnCiAgICAgICAgICoKICAgICAgICAgKiAvLyBQYXJ0aWFsbHkgYXBwbGllZCB3aXRoIHBsYWNlaG9sZGVycy4KICAgICAgICAgKiB2YXIgZ3JlZXRGcmVkID0gXy5wYXJ0aWFsKGdyZWV0LCBfLCAnZnJlZCcpOwogICAgICAgICAqIGdyZWV0RnJlZCgnaGknKTsKICAgICAgICAgKiAvLyA9PiAnaGkgZnJlZCcKICAgICAgICAgKi8KICAgICAgICB2YXIgcGFydGlhbCA9IGJhc2VSZXN0KGZ1bmN0aW9uKGZ1bmMsIHBhcnRpYWxzKSB7CiAgICAgICAgICB2YXIgaG9sZGVycyA9IHJlcGxhY2VIb2xkZXJzKHBhcnRpYWxzLCBnZXRIb2xkZXIocGFydGlhbCkpOwogICAgICAgICAgcmV0dXJuIGNyZWF0ZVdyYXAoZnVuYywgV1JBUF9QQVJUSUFMX0ZMQUcsIHVuZGVmaW5lZCQxLCBwYXJ0aWFscywgaG9sZGVycyk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8ucGFydGlhbGAgZXhjZXB0IHRoYXQgcGFydGlhbGx5IGFwcGxpZWQgYXJndW1lbnRzCiAgICAgICAgICogYXJlIGFwcGVuZGVkIHRvIHRoZSBhcmd1bWVudHMgaXQgcmVjZWl2ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgYF8ucGFydGlhbFJpZ2h0LnBsYWNlaG9sZGVyYCB2YWx1ZSwgd2hpY2ggZGVmYXVsdHMgdG8gYF9gIGluIG1vbm9saXRoaWMKICAgICAgICAgKiBidWlsZHMsIG1heSBiZSB1c2VkIGFzIGEgcGxhY2Vob2xkZXIgZm9yIHBhcnRpYWxseSBhcHBsaWVkIGFyZ3VtZW50cy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBkb2Vzbid0IHNldCB0aGUgImxlbmd0aCIgcHJvcGVydHkgb2YgcGFydGlhbGx5CiAgICAgICAgICogYXBwbGllZCBmdW5jdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMS4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBwYXJ0aWFsbHkgYXBwbHkgYXJndW1lbnRzIHRvLgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gW3BhcnRpYWxzXSBUaGUgYXJndW1lbnRzIHRvIGJlIHBhcnRpYWxseSBhcHBsaWVkLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHBhcnRpYWxseSBhcHBsaWVkIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBncmVldChncmVldGluZywgbmFtZSkgewogICAgICAgICAqICAgcmV0dXJuIGdyZWV0aW5nICsgJyAnICsgbmFtZTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZ3JlZXRGcmVkID0gXy5wYXJ0aWFsUmlnaHQoZ3JlZXQsICdmcmVkJyk7CiAgICAgICAgICogZ3JlZXRGcmVkKCdoaScpOwogICAgICAgICAqIC8vID0+ICdoaSBmcmVkJwogICAgICAgICAqCiAgICAgICAgICogLy8gUGFydGlhbGx5IGFwcGxpZWQgd2l0aCBwbGFjZWhvbGRlcnMuCiAgICAgICAgICogdmFyIHNheUhlbGxvVG8gPSBfLnBhcnRpYWxSaWdodChncmVldCwgJ2hlbGxvJywgXyk7CiAgICAgICAgICogc2F5SGVsbG9UbygnZnJlZCcpOwogICAgICAgICAqIC8vID0+ICdoZWxsbyBmcmVkJwogICAgICAgICAqLwogICAgICAgIHZhciBwYXJ0aWFsUmlnaHQgPSBiYXNlUmVzdChmdW5jdGlvbihmdW5jLCBwYXJ0aWFscykgewogICAgICAgICAgdmFyIGhvbGRlcnMgPSByZXBsYWNlSG9sZGVycyhwYXJ0aWFscywgZ2V0SG9sZGVyKHBhcnRpYWxSaWdodCkpOwogICAgICAgICAgcmV0dXJuIGNyZWF0ZVdyYXAoZnVuYywgV1JBUF9QQVJUSUFMX1JJR0hUX0ZMQUcsIHVuZGVmaW5lZCQxLCBwYXJ0aWFscywgaG9sZGVycyk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgYGZ1bmNgIHdpdGggYXJndW1lbnRzIGFycmFuZ2VkIGFjY29yZGluZwogICAgICAgICAqIHRvIHRoZSBzcGVjaWZpZWQgYGluZGV4ZXNgIHdoZXJlIHRoZSBhcmd1bWVudCB2YWx1ZSBhdCB0aGUgZmlyc3QgaW5kZXggaXMKICAgICAgICAgKiBwcm92aWRlZCBhcyB0aGUgZmlyc3QgYXJndW1lbnQsIHRoZSBhcmd1bWVudCB2YWx1ZSBhdCB0aGUgc2Vjb25kIGluZGV4IGlzCiAgICAgICAgICogcHJvdmlkZWQgYXMgdGhlIHNlY29uZCBhcmd1bWVudCwgYW5kIHNvIG9uLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gcmVhcnJhbmdlIGFyZ3VtZW50cyBmb3IuCiAgICAgICAgICogQHBhcmFtIHsuLi4obnVtYmVyfG51bWJlcltdKX0gaW5kZXhlcyBUaGUgYXJyYW5nZWQgYXJndW1lbnQgaW5kZXhlcy4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHJlYXJnZWQgPSBfLnJlYXJnKGZ1bmN0aW9uKGEsIGIsIGMpIHsKICAgICAgICAgKiAgIHJldHVybiBbYSwgYiwgY107CiAgICAgICAgICogfSwgWzIsIDAsIDFdKTsKICAgICAgICAgKgogICAgICAgICAqIHJlYXJnZWQoJ2InLCAnYycsICdhJykKICAgICAgICAgKiAvLyA9PiBbJ2EnLCAnYicsICdjJ10KICAgICAgICAgKi8KICAgICAgICB2YXIgcmVhcmcgPSBmbGF0UmVzdChmdW5jdGlvbihmdW5jLCBpbmRleGVzKSB7CiAgICAgICAgICByZXR1cm4gY3JlYXRlV3JhcChmdW5jLCBXUkFQX1JFQVJHX0ZMQUcsIHVuZGVmaW5lZCQxLCB1bmRlZmluZWQkMSwgdW5kZWZpbmVkJDEsIGluZGV4ZXMpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBpbnZva2VzIGBmdW5jYCB3aXRoIHRoZSBgdGhpc2AgYmluZGluZyBvZiB0aGUKICAgICAgICAgKiBjcmVhdGVkIGZ1bmN0aW9uIGFuZCBhcmd1bWVudHMgZnJvbSBgc3RhcnRgIGFuZCBiZXlvbmQgcHJvdmlkZWQgYXMKICAgICAgICAgKiBhbiBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbiB0aGUKICAgICAgICAgKiBbcmVzdCBwYXJhbWV0ZXJdKGh0dHBzOi8vbWRuLmlvL3Jlc3RfcGFyYW1ldGVycykuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBhcHBseSBhIHJlc3QgcGFyYW1ldGVyIHRvLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbc3RhcnQ9ZnVuYy5sZW5ndGgtMV0gVGhlIHN0YXJ0IHBvc2l0aW9uIG9mIHRoZSByZXN0IHBhcmFtZXRlci4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHNheSA9IF8ucmVzdChmdW5jdGlvbih3aGF0LCBuYW1lcykgewogICAgICAgICAqICAgcmV0dXJuIHdoYXQgKyAnICcgKyBfLmluaXRpYWwobmFtZXMpLmpvaW4oJywgJykgKwogICAgICAgICAqICAgICAoXy5zaXplKG5hbWVzKSA+IDEgPyAnLCAmICcgOiAnJykgKyBfLmxhc3QobmFtZXMpOwogICAgICAgICAqIH0pOwogICAgICAgICAqCiAgICAgICAgICogc2F5KCdoZWxsbycsICdmcmVkJywgJ2Jhcm5leScsICdwZWJibGVzJyk7CiAgICAgICAgICogLy8gPT4gJ2hlbGxvIGZyZWQsIGJhcm5leSwgJiBwZWJibGVzJwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHJlc3QoZnVuYywgc3RhcnQpIHsKICAgICAgICAgIGlmICh0eXBlb2YgZnVuYyAhPSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoRlVOQ19FUlJPUl9URVhUKTsKICAgICAgICAgIH0KICAgICAgICAgIHN0YXJ0ID0gc3RhcnQgPT09IHVuZGVmaW5lZCQxID8gc3RhcnQgOiB0b0ludGVnZXIoc3RhcnQpOwogICAgICAgICAgcmV0dXJuIGJhc2VSZXN0KGZ1bmMsIHN0YXJ0KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgYGZ1bmNgIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIHRoZQogICAgICAgICAqIGNyZWF0ZSBmdW5jdGlvbiBhbmQgYW4gYXJyYXkgb2YgYXJndW1lbnRzIG11Y2ggbGlrZQogICAgICAgICAqIFtgRnVuY3Rpb24jYXBwbHlgXShodHRwOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtZnVuY3Rpb24ucHJvdG90eXBlLmFwcGx5KS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbiB0aGUKICAgICAgICAgKiBbc3ByZWFkIG9wZXJhdG9yXShodHRwczovL21kbi5pby9zcHJlYWRfb3BlcmF0b3IpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMi4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gc3ByZWFkIGFyZ3VtZW50cyBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbc3RhcnQ9MF0gVGhlIHN0YXJ0IHBvc2l0aW9uIG9mIHRoZSBzcHJlYWQuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBzYXkgPSBfLnNwcmVhZChmdW5jdGlvbih3aG8sIHdoYXQpIHsKICAgICAgICAgKiAgIHJldHVybiB3aG8gKyAnIHNheXMgJyArIHdoYXQ7CiAgICAgICAgICogfSk7CiAgICAgICAgICoKICAgICAgICAgKiBzYXkoWydmcmVkJywgJ2hlbGxvJ10pOwogICAgICAgICAqIC8vID0+ICdmcmVkIHNheXMgaGVsbG8nCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgbnVtYmVycyA9IFByb21pc2UuYWxsKFsKICAgICAgICAgKiAgIFByb21pc2UucmVzb2x2ZSg0MCksCiAgICAgICAgICogICBQcm9taXNlLnJlc29sdmUoMzYpCiAgICAgICAgICogXSk7CiAgICAgICAgICoKICAgICAgICAgKiBudW1iZXJzLnRoZW4oXy5zcHJlYWQoZnVuY3Rpb24oeCwgeSkgewogICAgICAgICAqICAgcmV0dXJuIHggKyB5OwogICAgICAgICAqIH0pKTsKICAgICAgICAgKiAvLyA9PiBhIFByb21pc2Ugb2YgNzYKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzcHJlYWQoZnVuYywgc3RhcnQpIHsKICAgICAgICAgIGlmICh0eXBlb2YgZnVuYyAhPSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoRlVOQ19FUlJPUl9URVhUKTsKICAgICAgICAgIH0KICAgICAgICAgIHN0YXJ0ID0gc3RhcnQgPT0gbnVsbCA/IDAgOiBuYXRpdmVNYXgodG9JbnRlZ2VyKHN0YXJ0KSwgMCk7CiAgICAgICAgICByZXR1cm4gYmFzZVJlc3QoZnVuY3Rpb24oYXJncykgewogICAgICAgICAgICB2YXIgYXJyYXkgPSBhcmdzW3N0YXJ0XSwKICAgICAgICAgICAgICAgIG90aGVyQXJncyA9IGNhc3RTbGljZShhcmdzLCAwLCBzdGFydCk7CgogICAgICAgICAgICBpZiAoYXJyYXkpIHsKICAgICAgICAgICAgICBhcnJheVB1c2gob3RoZXJBcmdzLCBhcnJheSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGFwcGx5KGZ1bmMsIHRoaXMsIG90aGVyQXJncyk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSB0aHJvdHRsZWQgZnVuY3Rpb24gdGhhdCBvbmx5IGludm9rZXMgYGZ1bmNgIGF0IG1vc3Qgb25jZSBwZXIKICAgICAgICAgKiBldmVyeSBgd2FpdGAgbWlsbGlzZWNvbmRzLiBUaGUgdGhyb3R0bGVkIGZ1bmN0aW9uIGNvbWVzIHdpdGggYSBgY2FuY2VsYAogICAgICAgICAqIG1ldGhvZCB0byBjYW5jZWwgZGVsYXllZCBgZnVuY2AgaW52b2NhdGlvbnMgYW5kIGEgYGZsdXNoYCBtZXRob2QgdG8KICAgICAgICAgKiBpbW1lZGlhdGVseSBpbnZva2UgdGhlbS4gUHJvdmlkZSBgb3B0aW9uc2AgdG8gaW5kaWNhdGUgd2hldGhlciBgZnVuY2AKICAgICAgICAgKiBzaG91bGQgYmUgaW52b2tlZCBvbiB0aGUgbGVhZGluZyBhbmQvb3IgdHJhaWxpbmcgZWRnZSBvZiB0aGUgYHdhaXRgCiAgICAgICAgICogdGltZW91dC4gVGhlIGBmdW5jYCBpcyBpbnZva2VkIHdpdGggdGhlIGxhc3QgYXJndW1lbnRzIHByb3ZpZGVkIHRvIHRoZQogICAgICAgICAqIHRocm90dGxlZCBmdW5jdGlvbi4gU3Vic2VxdWVudCBjYWxscyB0byB0aGUgdGhyb3R0bGVkIGZ1bmN0aW9uIHJldHVybiB0aGUKICAgICAgICAgKiByZXN1bHQgb2YgdGhlIGxhc3QgYGZ1bmNgIGludm9jYXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogSWYgYGxlYWRpbmdgIGFuZCBgdHJhaWxpbmdgIG9wdGlvbnMgYXJlIGB0cnVlYCwgYGZ1bmNgIGlzCiAgICAgICAgICogaW52b2tlZCBvbiB0aGUgdHJhaWxpbmcgZWRnZSBvZiB0aGUgdGltZW91dCBvbmx5IGlmIHRoZSB0aHJvdHRsZWQgZnVuY3Rpb24KICAgICAgICAgKiBpcyBpbnZva2VkIG1vcmUgdGhhbiBvbmNlIGR1cmluZyB0aGUgYHdhaXRgIHRpbWVvdXQuCiAgICAgICAgICoKICAgICAgICAgKiBJZiBgd2FpdGAgaXMgYDBgIGFuZCBgbGVhZGluZ2AgaXMgYGZhbHNlYCwgYGZ1bmNgIGludm9jYXRpb24gaXMgZGVmZXJyZWQKICAgICAgICAgKiB1bnRpbCB0byB0aGUgbmV4dCB0aWNrLCBzaW1pbGFyIHRvIGBzZXRUaW1lb3V0YCB3aXRoIGEgdGltZW91dCBvZiBgMGAuCiAgICAgICAgICoKICAgICAgICAgKiBTZWUgW0RhdmlkIENvcmJhY2hvJ3MgYXJ0aWNsZV0oaHR0cHM6Ly9jc3MtdHJpY2tzLmNvbS9kZWJvdW5jaW5nLXRocm90dGxpbmctZXhwbGFpbmVkLWV4YW1wbGVzLykKICAgICAgICAgKiBmb3IgZGV0YWlscyBvdmVyIHRoZSBkaWZmZXJlbmNlcyBiZXR3ZWVuIGBfLnRocm90dGxlYCBhbmQgYF8uZGVib3VuY2VgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gdGhyb3R0bGUuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFt3YWl0PTBdIFRoZSBudW1iZXIgb2YgbWlsbGlzZWNvbmRzIHRvIHRocm90dGxlIGludm9jYXRpb25zIHRvLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb3B0aW9ucz17fV0gVGhlIG9wdGlvbnMgb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW29wdGlvbnMubGVhZGluZz10cnVlXQogICAgICAgICAqICBTcGVjaWZ5IGludm9raW5nIG9uIHRoZSBsZWFkaW5nIGVkZ2Ugb2YgdGhlIHRpbWVvdXQuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbb3B0aW9ucy50cmFpbGluZz10cnVlXQogICAgICAgICAqICBTcGVjaWZ5IGludm9raW5nIG9uIHRoZSB0cmFpbGluZyBlZGdlIG9mIHRoZSB0aW1lb3V0LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHRocm90dGxlZCBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogLy8gQXZvaWQgZXhjZXNzaXZlbHkgdXBkYXRpbmcgdGhlIHBvc2l0aW9uIHdoaWxlIHNjcm9sbGluZy4KICAgICAgICAgKiBqUXVlcnkod2luZG93KS5vbignc2Nyb2xsJywgXy50aHJvdHRsZSh1cGRhdGVQb3NpdGlvbiwgMTAwKSk7CiAgICAgICAgICoKICAgICAgICAgKiAvLyBJbnZva2UgYHJlbmV3VG9rZW5gIHdoZW4gdGhlIGNsaWNrIGV2ZW50IGlzIGZpcmVkLCBidXQgbm90IG1vcmUgdGhhbiBvbmNlIGV2ZXJ5IDUgbWludXRlcy4KICAgICAgICAgKiB2YXIgdGhyb3R0bGVkID0gXy50aHJvdHRsZShyZW5ld1Rva2VuLCAzMDAwMDAsIHsgJ3RyYWlsaW5nJzogZmFsc2UgfSk7CiAgICAgICAgICogalF1ZXJ5KGVsZW1lbnQpLm9uKCdjbGljaycsIHRocm90dGxlZCk7CiAgICAgICAgICoKICAgICAgICAgKiAvLyBDYW5jZWwgdGhlIHRyYWlsaW5nIHRocm90dGxlZCBpbnZvY2F0aW9uLgogICAgICAgICAqIGpRdWVyeSh3aW5kb3cpLm9uKCdwb3BzdGF0ZScsIHRocm90dGxlZC5jYW5jZWwpOwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRocm90dGxlKGZ1bmMsIHdhaXQsIG9wdGlvbnMpIHsKICAgICAgICAgIHZhciBsZWFkaW5nID0gdHJ1ZSwKICAgICAgICAgICAgICB0cmFpbGluZyA9IHRydWU7CgogICAgICAgICAgaWYgKHR5cGVvZiBmdW5jICE9ICdmdW5jdGlvbicpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcihGVU5DX0VSUk9SX1RFWFQpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzT2JqZWN0KG9wdGlvbnMpKSB7CiAgICAgICAgICAgIGxlYWRpbmcgPSAnbGVhZGluZycgaW4gb3B0aW9ucyA/ICEhb3B0aW9ucy5sZWFkaW5nIDogbGVhZGluZzsKICAgICAgICAgICAgdHJhaWxpbmcgPSAndHJhaWxpbmcnIGluIG9wdGlvbnMgPyAhIW9wdGlvbnMudHJhaWxpbmcgOiB0cmFpbGluZzsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBkZWJvdW5jZShmdW5jLCB3YWl0LCB7CiAgICAgICAgICAgICdsZWFkaW5nJzogbGVhZGluZywKICAgICAgICAgICAgJ21heFdhaXQnOiB3YWl0LAogICAgICAgICAgICAndHJhaWxpbmcnOiB0cmFpbGluZwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBhY2NlcHRzIHVwIHRvIG9uZSBhcmd1bWVudCwgaWdub3JpbmcgYW55CiAgICAgICAgICogYWRkaXRpb25hbCBhcmd1bWVudHMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgRnVuY3Rpb24KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBjYXAgYXJndW1lbnRzIGZvci4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBjYXBwZWQgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ubWFwKFsnNicsICc4JywgJzEwJ10sIF8udW5hcnkocGFyc2VJbnQpKTsKICAgICAgICAgKiAvLyA9PiBbNiwgOCwgMTBdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdW5hcnkoZnVuYykgewogICAgICAgICAgcmV0dXJuIGFyeShmdW5jLCAxKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IHByb3ZpZGVzIGB2YWx1ZWAgdG8gYHdyYXBwZXJgIGFzIGl0cyBmaXJzdAogICAgICAgICAqIGFyZ3VtZW50LiBBbnkgYWRkaXRpb25hbCBhcmd1bWVudHMgcHJvdmlkZWQgdG8gdGhlIGZ1bmN0aW9uIGFyZSBhcHBlbmRlZAogICAgICAgICAqIHRvIHRob3NlIHByb3ZpZGVkIHRvIHRoZSBgd3JhcHBlcmAuIFRoZSB3cmFwcGVyIGlzIGludm9rZWQgd2l0aCB0aGUgYHRoaXNgCiAgICAgICAgICogYmluZGluZyBvZiB0aGUgY3JlYXRlZCBmdW5jdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBGdW5jdGlvbgogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHdyYXAuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW3dyYXBwZXI9aWRlbnRpdHldIFRoZSB3cmFwcGVyIGZ1bmN0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgcCA9IF8ud3JhcChfLmVzY2FwZSwgZnVuY3Rpb24oZnVuYywgdGV4dCkgewogICAgICAgICAqICAgcmV0dXJuICc8cD4nICsgZnVuYyh0ZXh0KSArICc8L3A+JzsKICAgICAgICAgKiB9KTsKICAgICAgICAgKgogICAgICAgICAqIHAoJ2ZyZWQsIGJhcm5leSwgJiBwZWJibGVzJyk7CiAgICAgICAgICogLy8gPT4gJzxwPmZyZWQsIGJhcm5leSwgJmFtcDsgcGViYmxlczwvcD4nCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gd3JhcCh2YWx1ZSwgd3JhcHBlcikgewogICAgICAgICAgcmV0dXJuIHBhcnRpYWwoY2FzdEZ1bmN0aW9uKHdyYXBwZXIpLCB2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAgIC8qKgogICAgICAgICAqIENhc3RzIGB2YWx1ZWAgYXMgYW4gYXJyYXkgaWYgaXQncyBub3Qgb25lLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuNC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBpbnNwZWN0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgY2FzdCBhcnJheS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5jYXN0QXJyYXkoMSk7CiAgICAgICAgICogLy8gPT4gWzFdCiAgICAgICAgICoKICAgICAgICAgKiBfLmNhc3RBcnJheSh7ICdhJzogMSB9KTsKICAgICAgICAgKiAvLyA9PiBbeyAnYSc6IDEgfV0KICAgICAgICAgKgogICAgICAgICAqIF8uY2FzdEFycmF5KCdhYmMnKTsKICAgICAgICAgKiAvLyA9PiBbJ2FiYyddCiAgICAgICAgICoKICAgICAgICAgKiBfLmNhc3RBcnJheShudWxsKTsKICAgICAgICAgKiAvLyA9PiBbbnVsbF0KICAgICAgICAgKgogICAgICAgICAqIF8uY2FzdEFycmF5KHVuZGVmaW5lZCk7CiAgICAgICAgICogLy8gPT4gW3VuZGVmaW5lZF0KICAgICAgICAgKgogICAgICAgICAqIF8uY2FzdEFycmF5KCk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IFsxLCAyLCAzXTsKICAgICAgICAgKiBjb25zb2xlLmxvZyhfLmNhc3RBcnJheShhcnJheSkgPT09IGFycmF5KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2FzdEFycmF5KCkgewogICAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciB2YWx1ZSA9IGFyZ3VtZW50c1swXTsKICAgICAgICAgIHJldHVybiBpc0FycmF5KHZhbHVlKSA/IHZhbHVlIDogW3ZhbHVlXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBzaGFsbG93IGNsb25lIG9mIGB2YWx1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgbG9vc2VseSBiYXNlZCBvbiB0aGUKICAgICAgICAgKiBbc3RydWN0dXJlZCBjbG9uZSBhbGdvcml0aG1dKGh0dHBzOi8vbWRuLmlvL1N0cnVjdHVyZWRfY2xvbmVfYWxnb3JpdGhtKQogICAgICAgICAqIGFuZCBzdXBwb3J0cyBjbG9uaW5nIGFycmF5cywgYXJyYXkgYnVmZmVycywgYm9vbGVhbnMsIGRhdGUgb2JqZWN0cywgbWFwcywKICAgICAgICAgKiBudW1iZXJzLCBgT2JqZWN0YCBvYmplY3RzLCByZWdleGVzLCBzZXRzLCBzdHJpbmdzLCBzeW1ib2xzLCBhbmQgdHlwZWQKICAgICAgICAgKiBhcnJheXMuIFRoZSBvd24gZW51bWVyYWJsZSBwcm9wZXJ0aWVzIG9mIGBhcmd1bWVudHNgIG9iamVjdHMgYXJlIGNsb25lZAogICAgICAgICAqIGFzIHBsYWluIG9iamVjdHMuIEFuIGVtcHR5IG9iamVjdCBpcyByZXR1cm5lZCBmb3IgdW5jbG9uZWFibGUgdmFsdWVzIHN1Y2gKICAgICAgICAgKiBhcyBlcnJvciBvYmplY3RzLCBmdW5jdGlvbnMsIERPTSBub2RlcywgYW5kIFdlYWtNYXBzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjbG9uZS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgY2xvbmVkIHZhbHVlLgogICAgICAgICAqIEBzZWUgXy5jbG9uZURlZXAKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAnYSc6IDEgfSwgeyAnYic6IDIgfV07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgc2hhbGxvdyA9IF8uY2xvbmUob2JqZWN0cyk7CiAgICAgICAgICogY29uc29sZS5sb2coc2hhbGxvd1swXSA9PT0gb2JqZWN0c1swXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNsb25lKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUNsb25lKHZhbHVlLCBDTE9ORV9TWU1CT0xTX0ZMQUcpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5jbG9uZWAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgY3VzdG9taXplcmAgd2hpY2gKICAgICAgICAgKiBpcyBpbnZva2VkIHRvIHByb2R1Y2UgdGhlIGNsb25lZCB2YWx1ZS4gSWYgYGN1c3RvbWl6ZXJgIHJldHVybnMgYHVuZGVmaW5lZGAsCiAgICAgICAgICogY2xvbmluZyBpcyBoYW5kbGVkIGJ5IHRoZSBtZXRob2QgaW5zdGVhZC4gVGhlIGBjdXN0b21pemVyYCBpcyBpbnZva2VkIHdpdGgKICAgICAgICAgKiB1cCB0byBmb3VyIGFyZ3VtZW50czsgKHZhbHVlIFssIGluZGV4fGtleSwgb2JqZWN0LCBzdGFja10pLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjbG9uZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjbG9uaW5nLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBjbG9uZWQgdmFsdWUuCiAgICAgICAgICogQHNlZSBfLmNsb25lRGVlcFdpdGgKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gY3VzdG9taXplcih2YWx1ZSkgewogICAgICAgICAqICAgaWYgKF8uaXNFbGVtZW50KHZhbHVlKSkgewogICAgICAgICAqICAgICByZXR1cm4gdmFsdWUuY2xvbmVOb2RlKGZhbHNlKTsKICAgICAgICAgKiAgIH0KICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZWwgPSBfLmNsb25lV2l0aChkb2N1bWVudC5ib2R5LCBjdXN0b21pemVyKTsKICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGVsID09PSBkb2N1bWVudC5ib2R5KTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqIGNvbnNvbGUubG9nKGVsLm5vZGVOYW1lKTsKICAgICAgICAgKiAvLyA9PiAnQk9EWScKICAgICAgICAgKiBjb25zb2xlLmxvZyhlbC5jaGlsZE5vZGVzLmxlbmd0aCk7CiAgICAgICAgICogLy8gPT4gMAogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGNsb25lV2l0aCh2YWx1ZSwgY3VzdG9taXplcikgewogICAgICAgICAgY3VzdG9taXplciA9IHR5cGVvZiBjdXN0b21pemVyID09ICdmdW5jdGlvbicgPyBjdXN0b21pemVyIDogdW5kZWZpbmVkJDE7CiAgICAgICAgICByZXR1cm4gYmFzZUNsb25lKHZhbHVlLCBDTE9ORV9TWU1CT0xTX0ZMQUcsIGN1c3RvbWl6ZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5jbG9uZWAgZXhjZXB0IHRoYXQgaXQgcmVjdXJzaXZlbHkgY2xvbmVzIGB2YWx1ZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMS4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHJlY3Vyc2l2ZWx5IGNsb25lLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBkZWVwIGNsb25lZCB2YWx1ZS4KICAgICAgICAgKiBAc2VlIF8uY2xvbmUKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAnYSc6IDEgfSwgeyAnYic6IDIgfV07CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZGVlcCA9IF8uY2xvbmVEZWVwKG9iamVjdHMpOwogICAgICAgICAqIGNvbnNvbGUubG9nKGRlZXBbMF0gPT09IG9iamVjdHNbMF0pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2xvbmVEZWVwKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUNsb25lKHZhbHVlLCBDTE9ORV9ERUVQX0ZMQUcgfCBDTE9ORV9TWU1CT0xTX0ZMQUcpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5jbG9uZVdpdGhgIGV4Y2VwdCB0aGF0IGl0IHJlY3Vyc2l2ZWx5IGNsb25lcyBgdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byByZWN1cnNpdmVseSBjbG9uZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjbG9uaW5nLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBkZWVwIGNsb25lZCB2YWx1ZS4KICAgICAgICAgKiBAc2VlIF8uY2xvbmVXaXRoCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGN1c3RvbWl6ZXIodmFsdWUpIHsKICAgICAgICAgKiAgIGlmIChfLmlzRWxlbWVudCh2YWx1ZSkpIHsKICAgICAgICAgKiAgICAgcmV0dXJuIHZhbHVlLmNsb25lTm9kZSh0cnVlKTsKICAgICAgICAgKiAgIH0KICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZWwgPSBfLmNsb25lRGVlcFdpdGgoZG9jdW1lbnQuYm9keSwgY3VzdG9taXplcik7CiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhlbCA9PT0gZG9jdW1lbnQuYm9keSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKiBjb25zb2xlLmxvZyhlbC5ub2RlTmFtZSk7CiAgICAgICAgICogLy8gPT4gJ0JPRFknCiAgICAgICAgICogY29uc29sZS5sb2coZWwuY2hpbGROb2Rlcy5sZW5ndGgpOwogICAgICAgICAqIC8vID0+IDIwCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2xvbmVEZWVwV2l0aCh2YWx1ZSwgY3VzdG9taXplcikgewogICAgICAgICAgY3VzdG9taXplciA9IHR5cGVvZiBjdXN0b21pemVyID09ICdmdW5jdGlvbicgPyBjdXN0b21pemVyIDogdW5kZWZpbmVkJDE7CiAgICAgICAgICByZXR1cm4gYmFzZUNsb25lKHZhbHVlLCBDTE9ORV9ERUVQX0ZMQUcgfCBDTE9ORV9TWU1CT0xTX0ZMQUcsIGN1c3RvbWl6ZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGBvYmplY3RgIGNvbmZvcm1zIHRvIGBzb3VyY2VgIGJ5IGludm9raW5nIHRoZSBwcmVkaWNhdGUKICAgICAgICAgKiBwcm9wZXJ0aWVzIG9mIGBzb3VyY2VgIHdpdGggdGhlIGNvcnJlc3BvbmRpbmcgcHJvcGVydHkgdmFsdWVzIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIGlzIGVxdWl2YWxlbnQgdG8gYF8uY29uZm9ybXNgIHdoZW4gYHNvdXJjZWAgaXMKICAgICAgICAgKiBwYXJ0aWFsbHkgYXBwbGllZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjE0LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIG9iamVjdCBvZiBwcm9wZXJ0eSBwcmVkaWNhdGVzIHRvIGNvbmZvcm0gdG8uCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBvYmplY3RgIGNvbmZvcm1zLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSwgJ2InOiAyIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLmNvbmZvcm1zVG8ob2JqZWN0LCB7ICdiJzogZnVuY3Rpb24obikgeyByZXR1cm4gbiA+IDE7IH0gfSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5jb25mb3Jtc1RvKG9iamVjdCwgeyAnYic6IGZ1bmN0aW9uKG4pIHsgcmV0dXJuIG4gPiAyOyB9IH0pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29uZm9ybXNUbyhvYmplY3QsIHNvdXJjZSkgewogICAgICAgICAgcmV0dXJuIHNvdXJjZSA9PSBudWxsIHx8IGJhc2VDb25mb3Jtc1RvKG9iamVjdCwgc291cmNlLCBrZXlzKHNvdXJjZSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUGVyZm9ybXMgYQogICAgICAgICAqIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgICAgICogY29tcGFyaXNvbiBiZXR3ZWVuIHR3byB2YWx1ZXMgdG8gZGV0ZXJtaW5lIGlmIHRoZXkgYXJlIGVxdWl2YWxlbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHsqfSBvdGhlciBUaGUgb3RoZXIgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIHZhbHVlcyBhcmUgZXF1aXZhbGVudCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IDEgfTsKICAgICAgICAgKiB2YXIgb3RoZXIgPSB7ICdhJzogMSB9OwogICAgICAgICAqCiAgICAgICAgICogXy5lcShvYmplY3QsIG9iamVjdCk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5lcShvYmplY3QsIG90aGVyKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5lcSgnYScsICdhJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5lcSgnYScsIE9iamVjdCgnYScpKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5lcShOYU4sIE5hTik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGVxKHZhbHVlLCBvdGhlcikgewogICAgICAgICAgcmV0dXJuIHZhbHVlID09PSBvdGhlciB8fCAodmFsdWUgIT09IHZhbHVlICYmIG90aGVyICE9PSBvdGhlcik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBncmVhdGVyIHRoYW4gYG90aGVyYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjkuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGdyZWF0ZXIgdGhhbiBgb3RoZXJgLAogICAgICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQHNlZSBfLmx0CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZ3QoMywgMSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5ndCgzLCAzKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5ndCgxLCAzKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBndCA9IGNyZWF0ZVJlbGF0aW9uYWxPcGVyYXRpb24oYmFzZUd0KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgZ3JlYXRlciB0aGFuIG9yIGVxdWFsIHRvIGBvdGhlcmAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy45LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHsqfSBvdGhlciBUaGUgb3RoZXIgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBncmVhdGVyIHRoYW4gb3IgZXF1YWwgdG8KICAgICAgICAgKiAgYG90aGVyYCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBzZWUgXy5sdGUKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5ndGUoMywgMSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5ndGUoMywgMyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5ndGUoMSwgMyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICB2YXIgZ3RlID0gY3JlYXRlUmVsYXRpb25hbE9wZXJhdGlvbihmdW5jdGlvbih2YWx1ZSwgb3RoZXIpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSA+PSBvdGhlcjsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgbGlrZWx5IGFuIGBhcmd1bWVudHNgIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYW4gYGFyZ3VtZW50c2Agb2JqZWN0LAogICAgICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNBcmd1bWVudHMoZnVuY3Rpb24oKSB7IHJldHVybiBhcmd1bWVudHM7IH0oKSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FyZ3VtZW50cyhbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgdmFyIGlzQXJndW1lbnRzID0gYmFzZUlzQXJndW1lbnRzKGZ1bmN0aW9uKCkgeyByZXR1cm4gYXJndW1lbnRzOyB9KCkpID8gYmFzZUlzQXJndW1lbnRzIDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGhhc093blByb3BlcnR5LmNhbGwodmFsdWUsICdjYWxsZWUnKSAmJgogICAgICAgICAgICAhcHJvcGVydHlJc0VudW1lcmFibGUuY2FsbCh2YWx1ZSwgJ2NhbGxlZScpOwogICAgICAgIH07CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYW4gYEFycmF5YCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIGFycmF5LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNBcnJheShbMSwgMiwgM10pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNBcnJheShkb2N1bWVudC5ib2R5LmNoaWxkcmVuKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5KCdhYmMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5KF8ubm9vcCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICB2YXIgaXNBcnJheSA9IEFycmF5LmlzQXJyYXk7CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYW4gYEFycmF5QnVmZmVyYCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4zLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIGFycmF5IGJ1ZmZlciwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlCdWZmZXIobmV3IEFycmF5QnVmZmVyKDIpKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlCdWZmZXIobmV3IEFycmF5KDIpKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBpc0FycmF5QnVmZmVyID0gbm9kZUlzQXJyYXlCdWZmZXIgPyBiYXNlVW5hcnkobm9kZUlzQXJyYXlCdWZmZXIpIDogYmFzZUlzQXJyYXlCdWZmZXI7CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGFycmF5LWxpa2UuIEEgdmFsdWUgaXMgY29uc2lkZXJlZCBhcnJheS1saWtlIGlmIGl0J3MKICAgICAgICAgKiBub3QgYSBmdW5jdGlvbiBhbmQgaGFzIGEgYHZhbHVlLmxlbmd0aGAgdGhhdCdzIGFuIGludGVnZXIgZ3JlYXRlciB0aGFuIG9yCiAgICAgICAgICogZXF1YWwgdG8gYDBgIGFuZCBsZXNzIHRoYW4gb3IgZXF1YWwgdG8gYE51bWJlci5NQVhfU0FGRV9JTlRFR0VSYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYXJyYXktbGlrZSwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlMaWtlKFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5TGlrZShkb2N1bWVudC5ib2R5LmNoaWxkcmVuKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlMaWtlKCdhYmMnKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlMaWtlKF8ubm9vcCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc0FycmF5TGlrZSh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIHZhbHVlICE9IG51bGwgJiYgaXNMZW5ndGgodmFsdWUubGVuZ3RoKSAmJiAhaXNGdW5jdGlvbih2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmlzQXJyYXlMaWtlYCBleGNlcHQgdGhhdCBpdCBhbHNvIGNoZWNrcyBpZiBgdmFsdWVgCiAgICAgICAgICogaXMgYW4gb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhbiBhcnJheS1saWtlIG9iamVjdCwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlMaWtlT2JqZWN0KFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5TGlrZU9iamVjdChkb2N1bWVudC5ib2R5LmNoaWxkcmVuKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQXJyYXlMaWtlT2JqZWN0KCdhYmMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0FycmF5TGlrZU9iamVjdChfLm5vb3ApOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNBcnJheUxpa2VPYmplY3QodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGlzQXJyYXlMaWtlKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBib29sZWFuIHByaW1pdGl2ZSBvciBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgYm9vbGVhbiwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQm9vbGVhbihmYWxzZSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0Jvb2xlYW4obnVsbCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc0Jvb2xlYW4odmFsdWUpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSA9PT0gdHJ1ZSB8fCB2YWx1ZSA9PT0gZmFsc2UgfHwKICAgICAgICAgICAgKGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYgYmFzZUdldFRhZyh2YWx1ZSkgPT0gYm9vbFRhZyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIGJ1ZmZlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjMuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBidWZmZXIsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0J1ZmZlcihuZXcgQnVmZmVyKDIpKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzQnVmZmVyKG5ldyBVaW50OEFycmF5KDIpKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBpc0J1ZmZlciA9IG5hdGl2ZUlzQnVmZmVyIHx8IHN0dWJGYWxzZTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIGBEYXRlYCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgZGF0ZSBvYmplY3QsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0RhdGUobmV3IERhdGUpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNEYXRlKCdNb24gQXByaWwgMjMgMjAxMicpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgdmFyIGlzRGF0ZSA9IG5vZGVJc0RhdGUgPyBiYXNlVW5hcnkobm9kZUlzRGF0ZSkgOiBiYXNlSXNEYXRlOwoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBsaWtlbHkgYSBET00gZWxlbWVudC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBET00gZWxlbWVudCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRWxlbWVudChkb2N1bWVudC5ib2R5KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRWxlbWVudCgnPGJvZHk+Jyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc0VsZW1lbnQodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIHZhbHVlLm5vZGVUeXBlID09PSAxICYmICFpc1BsYWluT2JqZWN0KHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGFuIGVtcHR5IG9iamVjdCwgY29sbGVjdGlvbiwgbWFwLCBvciBzZXQuCiAgICAgICAgICoKICAgICAgICAgKiBPYmplY3RzIGFyZSBjb25zaWRlcmVkIGVtcHR5IGlmIHRoZXkgaGF2ZSBubyBvd24gZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQKICAgICAgICAgKiBwcm9wZXJ0aWVzLgogICAgICAgICAqCiAgICAgICAgICogQXJyYXktbGlrZSB2YWx1ZXMgc3VjaCBhcyBgYXJndW1lbnRzYCBvYmplY3RzLCBhcnJheXMsIGJ1ZmZlcnMsIHN0cmluZ3MsIG9yCiAgICAgICAgICogalF1ZXJ5LWxpa2UgY29sbGVjdGlvbnMgYXJlIGNvbnNpZGVyZWQgZW1wdHkgaWYgdGhleSBoYXZlIGEgYGxlbmd0aGAgb2YgYDBgLgogICAgICAgICAqIFNpbWlsYXJseSwgbWFwcyBhbmQgc2V0cyBhcmUgY29uc2lkZXJlZCBlbXB0eSBpZiB0aGV5IGhhdmUgYSBgc2l6ZWAgb2YgYDBgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBlbXB0eSwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRW1wdHkobnVsbCk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0VtcHR5KHRydWUpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNFbXB0eSgxKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRW1wdHkoWzEsIDIsIDNdKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0VtcHR5KHsgJ2EnOiAxIH0pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNFbXB0eSh2YWx1ZSkgewogICAgICAgICAgaWYgKHZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNBcnJheUxpa2UodmFsdWUpICYmCiAgICAgICAgICAgICAgKGlzQXJyYXkodmFsdWUpIHx8IHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJyB8fCB0eXBlb2YgdmFsdWUuc3BsaWNlID09ICdmdW5jdGlvbicgfHwKICAgICAgICAgICAgICAgIGlzQnVmZmVyKHZhbHVlKSB8fCBpc1R5cGVkQXJyYXkodmFsdWUpIHx8IGlzQXJndW1lbnRzKHZhbHVlKSkpIHsKICAgICAgICAgICAgcmV0dXJuICF2YWx1ZS5sZW5ndGg7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgdGFnID0gZ2V0VGFnKHZhbHVlKTsKICAgICAgICAgIGlmICh0YWcgPT0gbWFwVGFnIHx8IHRhZyA9PSBzZXRUYWcpIHsKICAgICAgICAgICAgcmV0dXJuICF2YWx1ZS5zaXplOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzUHJvdG90eXBlKHZhbHVlKSkgewogICAgICAgICAgICByZXR1cm4gIWJhc2VLZXlzKHZhbHVlKS5sZW5ndGg7CiAgICAgICAgICB9CiAgICAgICAgICBmb3IgKHZhciBrZXkgaW4gdmFsdWUpIHsKICAgICAgICAgICAgaWYgKGhhc093blByb3BlcnR5LmNhbGwodmFsdWUsIGtleSkpIHsKICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUGVyZm9ybXMgYSBkZWVwIGNvbXBhcmlzb24gYmV0d2VlbiB0d28gdmFsdWVzIHRvIGRldGVybWluZSBpZiB0aGV5IGFyZQogICAgICAgICAqIGVxdWl2YWxlbnQuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2Qgc3VwcG9ydHMgY29tcGFyaW5nIGFycmF5cywgYXJyYXkgYnVmZmVycywgYm9vbGVhbnMsCiAgICAgICAgICogZGF0ZSBvYmplY3RzLCBlcnJvciBvYmplY3RzLCBtYXBzLCBudW1iZXJzLCBgT2JqZWN0YCBvYmplY3RzLCByZWdleGVzLAogICAgICAgICAqIHNldHMsIHN0cmluZ3MsIHN5bWJvbHMsIGFuZCB0eXBlZCBhcnJheXMuIGBPYmplY3RgIG9iamVjdHMgYXJlIGNvbXBhcmVkCiAgICAgICAgICogYnkgdGhlaXIgb3duLCBub3QgaW5oZXJpdGVkLCBlbnVtZXJhYmxlIHByb3BlcnRpZXMuIEZ1bmN0aW9ucyBhbmQgRE9NCiAgICAgICAgICogbm9kZXMgYXJlIGNvbXBhcmVkIGJ5IHN0cmljdCBlcXVhbGl0eSwgaS5lLiBgPT09YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgdmFsdWVzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSB9OwogICAgICAgICAqIHZhciBvdGhlciA9IHsgJ2EnOiAxIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRXF1YWwob2JqZWN0LCBvdGhlcik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogb2JqZWN0ID09PSBvdGhlcjsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzRXF1YWwodmFsdWUsIG90aGVyKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUlzRXF1YWwodmFsdWUsIG90aGVyKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaXNFcXVhbGAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgY3VzdG9taXplcmAgd2hpY2gKICAgICAgICAgKiBpcyBpbnZva2VkIHRvIGNvbXBhcmUgdmFsdWVzLiBJZiBgY3VzdG9taXplcmAgcmV0dXJucyBgdW5kZWZpbmVkYCwgY29tcGFyaXNvbnMKICAgICAgICAgKiBhcmUgaGFuZGxlZCBieSB0aGUgbWV0aG9kIGluc3RlYWQuIFRoZSBgY3VzdG9taXplcmAgaXMgaW52b2tlZCB3aXRoIHVwIHRvCiAgICAgICAgICogc2l4IGFyZ3VtZW50czogKG9ialZhbHVlLCBvdGhWYWx1ZSBbLCBpbmRleHxrZXksIG9iamVjdCwgb3RoZXIsIHN0YWNrXSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHBhcmFtIHsqfSBvdGhlciBUaGUgb3RoZXIgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb21wYXJpc29ucy4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIHZhbHVlcyBhcmUgZXF1aXZhbGVudCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBpc0dyZWV0aW5nKHZhbHVlKSB7CiAgICAgICAgICogICByZXR1cm4gL15oKD86aXxlbGxvKSQvLnRlc3QodmFsdWUpOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGN1c3RvbWl6ZXIob2JqVmFsdWUsIG90aFZhbHVlKSB7CiAgICAgICAgICogICBpZiAoaXNHcmVldGluZyhvYmpWYWx1ZSkgJiYgaXNHcmVldGluZyhvdGhWYWx1ZSkpIHsKICAgICAgICAgKiAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICogICB9CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFycmF5ID0gWydoZWxsbycsICdnb29kYnllJ107CiAgICAgICAgICogdmFyIG90aGVyID0gWydoaScsICdnb29kYnllJ107CiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRXF1YWxXaXRoKGFycmF5LCBvdGhlciwgY3VzdG9taXplcik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzRXF1YWxXaXRoKHZhbHVlLCBvdGhlciwgY3VzdG9taXplcikgewogICAgICAgICAgY3VzdG9taXplciA9IHR5cGVvZiBjdXN0b21pemVyID09ICdmdW5jdGlvbicgPyBjdXN0b21pemVyIDogdW5kZWZpbmVkJDE7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gY3VzdG9taXplciA/IGN1c3RvbWl6ZXIodmFsdWUsIG90aGVyKSA6IHVuZGVmaW5lZCQxOwogICAgICAgICAgcmV0dXJuIHJlc3VsdCA9PT0gdW5kZWZpbmVkJDEgPyBiYXNlSXNFcXVhbCh2YWx1ZSwgb3RoZXIsIHVuZGVmaW5lZCQxLCBjdXN0b21pemVyKSA6ICEhcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYW4gYEVycm9yYCwgYEV2YWxFcnJvcmAsIGBSYW5nZUVycm9yYCwgYFJlZmVyZW5jZUVycm9yYCwKICAgICAgICAgKiBgU3ludGF4RXJyb3JgLCBgVHlwZUVycm9yYCwgb3IgYFVSSUVycm9yYCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIGVycm9yIG9iamVjdCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRXJyb3IobmV3IEVycm9yKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRXJyb3IoRXJyb3IpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNFcnJvcih2YWx1ZSkgewogICAgICAgICAgaWYgKCFpc09iamVjdExpa2UodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciB0YWcgPSBiYXNlR2V0VGFnKHZhbHVlKTsKICAgICAgICAgIHJldHVybiB0YWcgPT0gZXJyb3JUYWcgfHwgdGFnID09IGRvbUV4Y1RhZyB8fAogICAgICAgICAgICAodHlwZW9mIHZhbHVlLm1lc3NhZ2UgPT0gJ3N0cmluZycgJiYgdHlwZW9mIHZhbHVlLm5hbWUgPT0gJ3N0cmluZycgJiYgIWlzUGxhaW5PYmplY3QodmFsdWUpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgZmluaXRlIHByaW1pdGl2ZSBudW1iZXIuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgYmFzZWQgb24KICAgICAgICAgKiBbYE51bWJlci5pc0Zpbml0ZWBdKGh0dHBzOi8vbWRuLmlvL051bWJlci9pc0Zpbml0ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgZmluaXRlIG51bWJlciwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRmluaXRlKDMpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNGaW5pdGUoTnVtYmVyLk1JTl9WQUxVRSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0Zpbml0ZShJbmZpbml0eSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaXNGaW5pdGUoJzMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzRmluaXRlKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdudW1iZXInICYmIG5hdGl2ZUlzRmluaXRlKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBgRnVuY3Rpb25gIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBmdW5jdGlvbiwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzRnVuY3Rpb24oXyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0Z1bmN0aW9uKC9hYmMvKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzRnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIGlmICghaXNPYmplY3QodmFsdWUpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIFRoZSB1c2Ugb2YgYE9iamVjdCN0b1N0cmluZ2AgYXZvaWRzIGlzc3VlcyB3aXRoIHRoZSBgdHlwZW9mYCBvcGVyYXRvcgogICAgICAgICAgLy8gaW4gU2FmYXJpIDkgd2hpY2ggcmV0dXJucyAnb2JqZWN0JyBmb3IgdHlwZWQgYXJyYXlzIGFuZCBvdGhlciBjb25zdHJ1Y3RvcnMuCiAgICAgICAgICB2YXIgdGFnID0gYmFzZUdldFRhZyh2YWx1ZSk7CiAgICAgICAgICByZXR1cm4gdGFnID09IGZ1bmNUYWcgfHwgdGFnID09IGdlblRhZyB8fCB0YWcgPT0gYXN5bmNUYWcgfHwgdGFnID09IHByb3h5VGFnOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYW4gaW50ZWdlci4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbgogICAgICAgICAqIFtgTnVtYmVyLmlzSW50ZWdlcmBdKGh0dHBzOi8vbWRuLmlvL051bWJlci9pc0ludGVnZXIpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhbiBpbnRlZ2VyLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNJbnRlZ2VyKDMpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNJbnRlZ2VyKE51bWJlci5NSU5fVkFMVUUpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzSW50ZWdlcihJbmZpbml0eSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaXNJbnRlZ2VyKCczJyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc0ludGVnZXIodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB0eXBlb2YgdmFsdWUgPT0gJ251bWJlcicgJiYgdmFsdWUgPT0gdG9JbnRlZ2VyKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgdmFsaWQgYXJyYXktbGlrZSBsZW5ndGguCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgbG9vc2VseSBiYXNlZCBvbgogICAgICAgICAqIFtgVG9MZW5ndGhgXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy10b2xlbmd0aCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgdmFsaWQgbGVuZ3RoLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNMZW5ndGgoMyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0xlbmd0aChOdW1iZXIuTUlOX1ZBTFVFKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc0xlbmd0aChJbmZpbml0eSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaXNMZW5ndGgoJzMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTGVuZ3RoKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdudW1iZXInICYmCiAgICAgICAgICAgIHZhbHVlID4gLTEgJiYgdmFsdWUgJSAxID09IDAgJiYgdmFsdWUgPD0gTUFYX1NBRkVfSU5URUdFUjsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIHRoZQogICAgICAgICAqIFtsYW5ndWFnZSB0eXBlXShodHRwOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtZWNtYXNjcmlwdC1sYW5ndWFnZS10eXBlcykKICAgICAgICAgKiBvZiBgT2JqZWN0YC4gKGUuZy4gYXJyYXlzLCBmdW5jdGlvbnMsIG9iamVjdHMsIHJlZ2V4ZXMsIGBuZXcgTnVtYmVyKDApYCwgYW5kIGBuZXcgU3RyaW5nKCcnKWApCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIG9iamVjdCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzT2JqZWN0KHt9KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzT2JqZWN0KFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc09iamVjdChfLm5vb3ApOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNPYmplY3QobnVsbCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc09iamVjdCh2YWx1ZSkgewogICAgICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgdmFsdWU7CiAgICAgICAgICByZXR1cm4gdmFsdWUgIT0gbnVsbCAmJiAodHlwZSA9PSAnb2JqZWN0JyB8fCB0eXBlID09ICdmdW5jdGlvbicpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgb2JqZWN0LWxpa2UuIEEgdmFsdWUgaXMgb2JqZWN0LWxpa2UgaWYgaXQncyBub3QgYG51bGxgCiAgICAgICAgICogYW5kIGhhcyBhIGB0eXBlb2ZgIHJlc3VsdCBvZiAib2JqZWN0Ii4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgb2JqZWN0LWxpa2UsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc09iamVjdExpa2Uoe30pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNPYmplY3RMaWtlKFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc09iamVjdExpa2UoXy5ub29wKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc09iamVjdExpa2UobnVsbCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc09iamVjdExpa2UodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSAhPSBudWxsICYmIHR5cGVvZiB2YWx1ZSA9PSAnb2JqZWN0JzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBgTWFwYCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4zLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgbWFwLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNNYXAobmV3IE1hcCk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc01hcChuZXcgV2Vha01hcCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICB2YXIgaXNNYXAgPSBub2RlSXNNYXAgPyBiYXNlVW5hcnkobm9kZUlzTWFwKSA6IGJhc2VJc01hcDsKCiAgICAgICAgLyoqCiAgICAgICAgICogUGVyZm9ybXMgYSBwYXJ0aWFsIGRlZXAgY29tcGFyaXNvbiBiZXR3ZWVuIGBvYmplY3RgIGFuZCBgc291cmNlYCB0bwogICAgICAgICAqIGRldGVybWluZSBpZiBgb2JqZWN0YCBjb250YWlucyBlcXVpdmFsZW50IHByb3BlcnR5IHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBlcXVpdmFsZW50IHRvIGBfLm1hdGNoZXNgIHdoZW4gYHNvdXJjZWAgaXMKICAgICAgICAgKiBwYXJ0aWFsbHkgYXBwbGllZC4KICAgICAgICAgKgogICAgICAgICAqIFBhcnRpYWwgY29tcGFyaXNvbnMgd2lsbCBtYXRjaCBlbXB0eSBhcnJheSBhbmQgZW1wdHkgb2JqZWN0IGBzb3VyY2VgCiAgICAgICAgICogdmFsdWVzIGFnYWluc3QgYW55IGFycmF5IG9yIG9iamVjdCB2YWx1ZSwgcmVzcGVjdGl2ZWx5LiBTZWUgYF8uaXNFcXVhbGAKICAgICAgICAgKiBmb3IgYSBsaXN0IG9mIHN1cHBvcnRlZCB2YWx1ZSBjb21wYXJpc29ucy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IG9mIHByb3BlcnR5IHZhbHVlcyB0byBtYXRjaC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYG9iamVjdGAgaXMgYSBtYXRjaCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IDEsICdiJzogMiB9OwogICAgICAgICAqCiAgICAgICAgICogXy5pc01hdGNoKG9iamVjdCwgeyAnYic6IDIgfSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc01hdGNoKG9iamVjdCwgeyAnYic6IDEgfSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc01hdGNoKG9iamVjdCwgc291cmNlKSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ID09PSBzb3VyY2UgfHwgYmFzZUlzTWF0Y2gob2JqZWN0LCBzb3VyY2UsIGdldE1hdGNoRGF0YShzb3VyY2UpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaXNNYXRjaGAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgY3VzdG9taXplcmAgd2hpY2gKICAgICAgICAgKiBpcyBpbnZva2VkIHRvIGNvbXBhcmUgdmFsdWVzLiBJZiBgY3VzdG9taXplcmAgcmV0dXJucyBgdW5kZWZpbmVkYCwgY29tcGFyaXNvbnMKICAgICAgICAgKiBhcmUgaGFuZGxlZCBieSB0aGUgbWV0aG9kIGluc3RlYWQuIFRoZSBgY3VzdG9taXplcmAgaXMgaW52b2tlZCB3aXRoIGZpdmUKICAgICAgICAgKiBhcmd1bWVudHM6IChvYmpWYWx1ZSwgc3JjVmFsdWUsIGluZGV4fGtleSwgb2JqZWN0LCBzb3VyY2UpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3Qgb2YgcHJvcGVydHkgdmFsdWVzIHRvIG1hdGNoLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNvbXBhcmlzb25zLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgb2JqZWN0YCBpcyBhIG1hdGNoLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIGlzR3JlZXRpbmcodmFsdWUpIHsKICAgICAgICAgKiAgIHJldHVybiAvXmgoPzppfGVsbG8pJC8udGVzdCh2YWx1ZSk7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gY3VzdG9taXplcihvYmpWYWx1ZSwgc3JjVmFsdWUpIHsKICAgICAgICAgKiAgIGlmIChpc0dyZWV0aW5nKG9ialZhbHVlKSAmJiBpc0dyZWV0aW5nKHNyY1ZhbHVlKSkgewogICAgICAgICAqICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgKiAgIH0KICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnZ3JlZXRpbmcnOiAnaGVsbG8nIH07CiAgICAgICAgICogdmFyIHNvdXJjZSA9IHsgJ2dyZWV0aW5nJzogJ2hpJyB9OwogICAgICAgICAqCiAgICAgICAgICogXy5pc01hdGNoV2l0aChvYmplY3QsIHNvdXJjZSwgY3VzdG9taXplcik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTWF0Y2hXaXRoKG9iamVjdCwgc291cmNlLCBjdXN0b21pemVyKSB7CiAgICAgICAgICBjdXN0b21pemVyID0gdHlwZW9mIGN1c3RvbWl6ZXIgPT0gJ2Z1bmN0aW9uJyA/IGN1c3RvbWl6ZXIgOiB1bmRlZmluZWQkMTsKICAgICAgICAgIHJldHVybiBiYXNlSXNNYXRjaChvYmplY3QsIHNvdXJjZSwgZ2V0TWF0Y2hEYXRhKHNvdXJjZSksIGN1c3RvbWl6ZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYE5hTmAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgYmFzZWQgb24KICAgICAgICAgKiBbYE51bWJlci5pc05hTmBdKGh0dHBzOi8vbWRuLmlvL051bWJlci9pc05hTikgYW5kIGlzIG5vdCB0aGUgc2FtZSBhcwogICAgICAgICAqIGdsb2JhbCBbYGlzTmFOYF0oaHR0cHM6Ly9tZG4uaW8vaXNOYU4pIHdoaWNoIHJldHVybnMgYHRydWVgIGZvcgogICAgICAgICAqIGB1bmRlZmluZWRgIGFuZCBvdGhlciBub24tbnVtYmVyIHZhbHVlcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYE5hTmAsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc05hTihOYU4pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOYU4obmV3IE51bWJlcihOYU4pKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBpc05hTih1bmRlZmluZWQpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOYU4odW5kZWZpbmVkKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTmFOKHZhbHVlKSB7CiAgICAgICAgICAvLyBBbiBgTmFOYCBwcmltaXRpdmUgaXMgdGhlIG9ubHkgdmFsdWUgdGhhdCBpcyBub3QgZXF1YWwgdG8gaXRzZWxmLgogICAgICAgICAgLy8gUGVyZm9ybSB0aGUgYHRvU3RyaW5nVGFnYCBjaGVjayBmaXJzdCB0byBhdm9pZCBlcnJvcnMgd2l0aCBzb21lCiAgICAgICAgICAvLyBBY3RpdmVYIG9iamVjdHMgaW4gSUUuCiAgICAgICAgICByZXR1cm4gaXNOdW1iZXIodmFsdWUpICYmIHZhbHVlICE9ICt2YWx1ZTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgcHJpc3RpbmUgbmF0aXZlIGZ1bmN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIGNhbid0IHJlbGlhYmx5IGRldGVjdCBuYXRpdmUgZnVuY3Rpb25zIGluIHRoZSBwcmVzZW5jZQogICAgICAgICAqIG9mIHRoZSBjb3JlLWpzIHBhY2thZ2UgYmVjYXVzZSBjb3JlLWpzIGNpcmN1bXZlbnRzIHRoaXMga2luZCBvZiBkZXRlY3Rpb24uCiAgICAgICAgICogRGVzcGl0ZSBtdWx0aXBsZSByZXF1ZXN0cywgdGhlIGNvcmUtanMgbWFpbnRhaW5lciBoYXMgbWFkZSBpdCBjbGVhcjogYW55CiAgICAgICAgICogYXR0ZW1wdCB0byBmaXggdGhlIGRldGVjdGlvbiB3aWxsIGJlIG9ic3RydWN0ZWQuIEFzIGEgcmVzdWx0LCB3ZSdyZSBsZWZ0CiAgICAgICAgICogd2l0aCBsaXR0bGUgY2hvaWNlIGJ1dCB0byB0aHJvdyBhbiBlcnJvci4gVW5mb3J0dW5hdGVseSwgdGhpcyBhbHNvIGFmZmVjdHMKICAgICAgICAgKiBwYWNrYWdlcywgbGlrZSBbYmFiZWwtcG9seWZpbGxdKGh0dHBzOi8vd3d3Lm5wbWpzLmNvbS9wYWNrYWdlL2JhYmVsLXBvbHlmaWxsKSwKICAgICAgICAgKiB3aGljaCByZWx5IG9uIGNvcmUtanMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgbmF0aXZlIGZ1bmN0aW9uLAogICAgICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOYXRpdmUoQXJyYXkucHJvdG90eXBlLnB1c2gpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOYXRpdmUoXyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc05hdGl2ZSh2YWx1ZSkgewogICAgICAgICAgaWYgKGlzTWFza2FibGUodmFsdWUpKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihDT1JFX0VSUk9SX1RFWFQpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VJc05hdGl2ZSh2YWx1ZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBgbnVsbGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGBudWxsYCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzTnVsbChudWxsKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzTnVsbCh2b2lkIDApOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNOdWxsKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdmFsdWUgPT09IG51bGw7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBgbnVsbGAgb3IgYHVuZGVmaW5lZGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIG51bGxpc2gsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc05pbChudWxsKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzTmlsKHZvaWQgMCk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc05pbChOYU4pOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNOaWwodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSA9PSBudWxsOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIGBOdW1iZXJgIHByaW1pdGl2ZSBvciBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVG8gZXhjbHVkZSBgSW5maW5pdHlgLCBgLUluZmluaXR5YCwgYW5kIGBOYU5gLCB3aGljaCBhcmUKICAgICAgICAgKiBjbGFzc2lmaWVkIGFzIG51bWJlcnMsIHVzZSB0aGUgYF8uaXNGaW5pdGVgIG1ldGhvZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBudW1iZXIsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc051bWJlcigzKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzTnVtYmVyKE51bWJlci5NSU5fVkFMVUUpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOdW1iZXIoSW5maW5pdHkpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNOdW1iZXIoJzMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzTnVtYmVyKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdudW1iZXInIHx8CiAgICAgICAgICAgIChpc09iamVjdExpa2UodmFsdWUpICYmIGJhc2VHZXRUYWcodmFsdWUpID09IG51bWJlclRhZyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIHBsYWluIG9iamVjdCwgdGhhdCBpcywgYW4gb2JqZWN0IGNyZWF0ZWQgYnkgdGhlCiAgICAgICAgICogYE9iamVjdGAgY29uc3RydWN0b3Igb3Igb25lIHdpdGggYSBgW1tQcm90b3R5cGVdXWAgb2YgYG51bGxgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuOC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHBsYWluIG9iamVjdCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgICAgICogICB0aGlzLmEgPSAxOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIF8uaXNQbGFpbk9iamVjdChuZXcgRm9vKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1BsYWluT2JqZWN0KFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaXNQbGFpbk9iamVjdCh7ICd4JzogMCwgJ3knOiAwIH0pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNQbGFpbk9iamVjdChPYmplY3QuY3JlYXRlKG51bGwpKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNQbGFpbk9iamVjdCh2YWx1ZSkgewogICAgICAgICAgaWYgKCFpc09iamVjdExpa2UodmFsdWUpIHx8IGJhc2VHZXRUYWcodmFsdWUpICE9IG9iamVjdFRhZykgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcHJvdG8gPSBnZXRQcm90b3R5cGUodmFsdWUpOwogICAgICAgICAgaWYgKHByb3RvID09PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgdmFyIEN0b3IgPSBoYXNPd25Qcm9wZXJ0eS5jYWxsKHByb3RvLCAnY29uc3RydWN0b3InKSAmJiBwcm90by5jb25zdHJ1Y3RvcjsKICAgICAgICAgIHJldHVybiB0eXBlb2YgQ3RvciA9PSAnZnVuY3Rpb24nICYmIEN0b3IgaW5zdGFuY2VvZiBDdG9yICYmCiAgICAgICAgICAgIGZ1bmNUb1N0cmluZy5jYWxsKEN0b3IpID09IG9iamVjdEN0b3JTdHJpbmc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgYFJlZ0V4cGAgb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHJlZ2V4cCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzUmVnRXhwKC9hYmMvKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzUmVnRXhwKCcvYWJjLycpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgdmFyIGlzUmVnRXhwID0gbm9kZUlzUmVnRXhwID8gYmFzZVVuYXJ5KG5vZGVJc1JlZ0V4cCkgOiBiYXNlSXNSZWdFeHA7CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgc2FmZSBpbnRlZ2VyLiBBbiBpbnRlZ2VyIGlzIHNhZmUgaWYgaXQncyBhbiBJRUVFLTc1NAogICAgICAgICAqIGRvdWJsZSBwcmVjaXNpb24gbnVtYmVyIHdoaWNoIGlzbid0IHRoZSByZXN1bHQgb2YgYSByb3VuZGVkIHVuc2FmZSBpbnRlZ2VyLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIGlzIGJhc2VkIG9uCiAgICAgICAgICogW2BOdW1iZXIuaXNTYWZlSW50ZWdlcmBdKGh0dHBzOi8vbWRuLmlvL051bWJlci9pc1NhZmVJbnRlZ2VyKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBzYWZlIGludGVnZXIsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1NhZmVJbnRlZ2VyKDMpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNTYWZlSW50ZWdlcihOdW1iZXIuTUlOX1ZBTFVFKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1NhZmVJbnRlZ2VyKEluZmluaXR5KTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1NhZmVJbnRlZ2VyKCczJyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc1NhZmVJbnRlZ2VyKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gaXNJbnRlZ2VyKHZhbHVlKSAmJiB2YWx1ZSA+PSAtTUFYX1NBRkVfSU5URUdFUiAmJiB2YWx1ZSA8PSBNQVhfU0FGRV9JTlRFR0VSOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIGBTZXRgIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjMuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBzZXQsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1NldChuZXcgU2V0KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzU2V0KG5ldyBXZWFrU2V0KTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBpc1NldCA9IG5vZGVJc1NldCA/IGJhc2VVbmFyeShub2RlSXNTZXQpIDogYmFzZUlzU2V0OwoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgYFN0cmluZ2AgcHJpbWl0aXZlIG9yIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBzdHJpbmcsIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1N0cmluZygnYWJjJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1N0cmluZygxKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzU3RyaW5nKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdzdHJpbmcnIHx8CiAgICAgICAgICAgICghaXNBcnJheSh2YWx1ZSkgJiYgaXNPYmplY3RMaWtlKHZhbHVlKSAmJiBiYXNlR2V0VGFnKHZhbHVlKSA9PSBzdHJpbmdUYWcpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIGBTeW1ib2xgIHByaW1pdGl2ZSBvciBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgc3ltYm9sLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNTeW1ib2woU3ltYm9sLml0ZXJhdG9yKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzU3ltYm9sKCdhYmMnKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzU3ltYm9sKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdzeW1ib2wnIHx8CiAgICAgICAgICAgIChpc09iamVjdExpa2UodmFsdWUpICYmIGJhc2VHZXRUYWcodmFsdWUpID09IHN5bWJvbFRhZyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgdHlwZWQgYXJyYXkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgdHlwZWQgYXJyYXksIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1R5cGVkQXJyYXkobmV3IFVpbnQ4QXJyYXkpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNUeXBlZEFycmF5KFtdKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBpc1R5cGVkQXJyYXkgPSBub2RlSXNUeXBlZEFycmF5ID8gYmFzZVVuYXJ5KG5vZGVJc1R5cGVkQXJyYXkpIDogYmFzZUlzVHlwZWRBcnJheTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYHVuZGVmaW5lZGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGB1bmRlZmluZWRgLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNVbmRlZmluZWQodm9pZCAwKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzVW5kZWZpbmVkKG51bGwpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXNVbmRlZmluZWQodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZSA9PT0gdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgYFdlYWtNYXBgIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjMuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSB3ZWFrIG1hcCwgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzV2Vha01hcChuZXcgV2Vha01hcCk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pc1dlYWtNYXAobmV3IE1hcCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpc1dlYWtNYXAodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBpc09iamVjdExpa2UodmFsdWUpICYmIGdldFRhZyh2YWx1ZSkgPT0gd2Vha01hcFRhZzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBgV2Vha1NldGAgb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMy4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHdlYWsgc2V0LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uaXNXZWFrU2V0KG5ldyBXZWFrU2V0KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmlzV2Vha1NldChuZXcgU2V0KTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGlzV2Vha1NldCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZSh2YWx1ZSkgJiYgYmFzZUdldFRhZyh2YWx1ZSkgPT0gd2Vha1NldFRhZzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGxlc3MgdGhhbiBgb3RoZXJgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuOS4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEBwYXJhbSB7Kn0gb3RoZXIgVGhlIG90aGVyIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgbGVzcyB0aGFuIGBvdGhlcmAsCiAgICAgICAgICogIGVsc2UgYGZhbHNlYC4KICAgICAgICAgKiBAc2VlIF8uZ3QKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5sdCgxLCAzKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmx0KDMsIDMpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICoKICAgICAgICAgKiBfLmx0KDMsIDEpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgdmFyIGx0ID0gY3JlYXRlUmVsYXRpb25hbE9wZXJhdGlvbihiYXNlTHQpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBsZXNzIHRoYW4gb3IgZXF1YWwgdG8gYG90aGVyYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjkuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGxlc3MgdGhhbiBvciBlcXVhbCB0bwogICAgICAgICAqICBgb3RoZXJgLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQHNlZSBfLmd0ZQogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmx0ZSgxLCAzKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmx0ZSgzLCAzKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmx0ZSgzLCAxKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBsdGUgPSBjcmVhdGVSZWxhdGlvbmFsT3BlcmF0aW9uKGZ1bmN0aW9uKHZhbHVlLCBvdGhlcikgewogICAgICAgICAgcmV0dXJuIHZhbHVlIDw9IG90aGVyOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGFuIGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgY29udmVydGVkIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvQXJyYXkoeyAnYSc6IDEsICdiJzogMiB9KTsKICAgICAgICAgKiAvLyA9PiBbMSwgMl0KICAgICAgICAgKgogICAgICAgICAqIF8udG9BcnJheSgnYWJjJyk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InLCAnYyddCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvQXJyYXkoMSk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKgogICAgICAgICAqIF8udG9BcnJheShudWxsKTsKICAgICAgICAgKiAvLyA9PiBbXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvQXJyYXkodmFsdWUpIHsKICAgICAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzQXJyYXlMaWtlKHZhbHVlKSkgewogICAgICAgICAgICByZXR1cm4gaXNTdHJpbmcodmFsdWUpID8gc3RyaW5nVG9BcnJheSh2YWx1ZSkgOiBjb3B5QXJyYXkodmFsdWUpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHN5bUl0ZXJhdG9yICYmIHZhbHVlW3N5bUl0ZXJhdG9yXSkgewogICAgICAgICAgICByZXR1cm4gaXRlcmF0b3JUb0FycmF5KHZhbHVlW3N5bUl0ZXJhdG9yXSgpKTsKICAgICAgICAgIH0KICAgICAgICAgIHZhciB0YWcgPSBnZXRUYWcodmFsdWUpLAogICAgICAgICAgICAgIGZ1bmMgPSB0YWcgPT0gbWFwVGFnID8gbWFwVG9BcnJheSA6ICh0YWcgPT0gc2V0VGFnID8gc2V0VG9BcnJheSA6IHZhbHVlcyk7CgogICAgICAgICAgcmV0dXJuIGZ1bmModmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHZhbHVlYCB0byBhIGZpbml0ZSBudW1iZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4xMi4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBudW1iZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udG9GaW5pdGUoMy4yKTsKICAgICAgICAgKiAvLyA9PiAzLjIKICAgICAgICAgKgogICAgICAgICAqIF8udG9GaW5pdGUoTnVtYmVyLk1JTl9WQUxVRSk7CiAgICAgICAgICogLy8gPT4gNWUtMzI0CiAgICAgICAgICoKICAgICAgICAgKiBfLnRvRmluaXRlKEluZmluaXR5KTsKICAgICAgICAgKiAvLyA9PiAxLjc5NzY5MzEzNDg2MjMxNTdlKzMwOAogICAgICAgICAqCiAgICAgICAgICogXy50b0Zpbml0ZSgnMy4yJyk7CiAgICAgICAgICogLy8gPT4gMy4yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdG9GaW5pdGUodmFsdWUpIHsKICAgICAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHZhbHVlID09PSAwID8gdmFsdWUgOiAwOwogICAgICAgICAgfQogICAgICAgICAgdmFsdWUgPSB0b051bWJlcih2YWx1ZSk7CiAgICAgICAgICBpZiAodmFsdWUgPT09IElORklOSVRZIHx8IHZhbHVlID09PSAtSU5GSU5JVFkpIHsKICAgICAgICAgICAgdmFyIHNpZ24gPSAodmFsdWUgPCAwID8gLTEgOiAxKTsKICAgICAgICAgICAgcmV0dXJuIHNpZ24gKiBNQVhfSU5URUdFUjsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB2YWx1ZSA9PT0gdmFsdWUgPyB2YWx1ZSA6IDA7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGFuIGludGVnZXIuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgbG9vc2VseSBiYXNlZCBvbgogICAgICAgICAqIFtgVG9JbnRlZ2VyYF0oaHR0cDovL3d3dy5lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXRvaW50ZWdlcikuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY29udmVydGVkIGludGVnZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udG9JbnRlZ2VyKDMuMik7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqCiAgICAgICAgICogXy50b0ludGVnZXIoTnVtYmVyLk1JTl9WQUxVRSk7CiAgICAgICAgICogLy8gPT4gMAogICAgICAgICAqCiAgICAgICAgICogXy50b0ludGVnZXIoSW5maW5pdHkpOwogICAgICAgICAqIC8vID0+IDEuNzk3NjkzMTM0ODYyMzE1N2UrMzA4CiAgICAgICAgICoKICAgICAgICAgKiBfLnRvSW50ZWdlcignMy4yJyk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvSW50ZWdlcih2YWx1ZSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IHRvRmluaXRlKHZhbHVlKSwKICAgICAgICAgICAgICByZW1haW5kZXIgPSByZXN1bHQgJSAxOwoKICAgICAgICAgIHJldHVybiByZXN1bHQgPT09IHJlc3VsdCA/IChyZW1haW5kZXIgPyByZXN1bHQgLSByZW1haW5kZXIgOiByZXN1bHQpIDogMDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYW4gaW50ZWdlciBzdWl0YWJsZSBmb3IgdXNlIGFzIHRoZSBsZW5ndGggb2YgYW4KICAgICAgICAgKiBhcnJheS1saWtlIG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbgogICAgICAgICAqIFtgVG9MZW5ndGhgXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy10b2xlbmd0aCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY29udmVydGVkIGludGVnZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udG9MZW5ndGgoMy4yKTsKICAgICAgICAgKiAvLyA9PiAzCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvTGVuZ3RoKE51bWJlci5NSU5fVkFMVUUpOwogICAgICAgICAqIC8vID0+IDAKICAgICAgICAgKgogICAgICAgICAqIF8udG9MZW5ndGgoSW5maW5pdHkpOwogICAgICAgICAqIC8vID0+IDQyOTQ5NjcyOTUKICAgICAgICAgKgogICAgICAgICAqIF8udG9MZW5ndGgoJzMuMicpOwogICAgICAgICAqIC8vID0+IDMKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0b0xlbmd0aCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIHZhbHVlID8gYmFzZUNsYW1wKHRvSW50ZWdlcih2YWx1ZSksIDAsIE1BWF9BUlJBWV9MRU5HVEgpIDogMDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYSBudW1iZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHByb2Nlc3MuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgbnVtYmVyLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvTnVtYmVyKDMuMik7CiAgICAgICAgICogLy8gPT4gMy4yCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvTnVtYmVyKE51bWJlci5NSU5fVkFMVUUpOwogICAgICAgICAqIC8vID0+IDVlLTMyNAogICAgICAgICAqCiAgICAgICAgICogXy50b051bWJlcihJbmZpbml0eSk7CiAgICAgICAgICogLy8gPT4gSW5maW5pdHkKICAgICAgICAgKgogICAgICAgICAqIF8udG9OdW1iZXIoJzMuMicpOwogICAgICAgICAqIC8vID0+IDMuMgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvTnVtYmVyKHZhbHVlKSB7CiAgICAgICAgICBpZiAodHlwZW9mIHZhbHVlID09ICdudW1iZXInKSB7CiAgICAgICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChpc1N5bWJvbCh2YWx1ZSkpIHsKICAgICAgICAgICAgcmV0dXJuIE5BTjsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChpc09iamVjdCh2YWx1ZSkpIHsKICAgICAgICAgICAgdmFyIG90aGVyID0gdHlwZW9mIHZhbHVlLnZhbHVlT2YgPT0gJ2Z1bmN0aW9uJyA/IHZhbHVlLnZhbHVlT2YoKSA6IHZhbHVlOwogICAgICAgICAgICB2YWx1ZSA9IGlzT2JqZWN0KG90aGVyKSA/IChvdGhlciArICcnKSA6IG90aGVyOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPSAnc3RyaW5nJykgewogICAgICAgICAgICByZXR1cm4gdmFsdWUgPT09IDAgPyB2YWx1ZSA6ICt2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhbHVlID0gdmFsdWUucmVwbGFjZShyZVRyaW0sICcnKTsKICAgICAgICAgIHZhciBpc0JpbmFyeSA9IHJlSXNCaW5hcnkudGVzdCh2YWx1ZSk7CiAgICAgICAgICByZXR1cm4gKGlzQmluYXJ5IHx8IHJlSXNPY3RhbC50ZXN0KHZhbHVlKSkKICAgICAgICAgICAgPyBmcmVlUGFyc2VJbnQodmFsdWUuc2xpY2UoMiksIGlzQmluYXJ5ID8gMiA6IDgpCiAgICAgICAgICAgIDogKHJlSXNCYWRIZXgudGVzdCh2YWx1ZSkgPyBOQU4gOiArdmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHZhbHVlYCB0byBhIHBsYWluIG9iamVjdCBmbGF0dGVuaW5nIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZwogICAgICAgICAqIGtleWVkIHByb3BlcnRpZXMgb2YgYHZhbHVlYCB0byBvd24gcHJvcGVydGllcyBvZiB0aGUgcGxhaW4gb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IExhbmcKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBwbGFpbiBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYiA9IDI7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogRm9vLnByb3RvdHlwZS5jID0gMzsKICAgICAgICAgKgogICAgICAgICAqIF8uYXNzaWduKHsgJ2EnOiAxIH0sIG5ldyBGb28pOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiAxLCAnYic6IDIgfQogICAgICAgICAqCiAgICAgICAgICogXy5hc3NpZ24oeyAnYSc6IDEgfSwgXy50b1BsYWluT2JqZWN0KG5ldyBGb28pKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyLCAnYyc6IDMgfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvUGxhaW5PYmplY3QodmFsdWUpIHsKICAgICAgICAgIHJldHVybiBjb3B5T2JqZWN0KHZhbHVlLCBrZXlzSW4odmFsdWUpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYSBzYWZlIGludGVnZXIuIEEgc2FmZSBpbnRlZ2VyIGNhbiBiZSBjb21wYXJlZCBhbmQKICAgICAgICAgKiByZXByZXNlbnRlZCBjb3JyZWN0bHkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY29udmVydGVkIGludGVnZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udG9TYWZlSW50ZWdlcigzLjIpOwogICAgICAgICAqIC8vID0+IDMKICAgICAgICAgKgogICAgICAgICAqIF8udG9TYWZlSW50ZWdlcihOdW1iZXIuTUlOX1ZBTFVFKTsKICAgICAgICAgKiAvLyA9PiAwCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvU2FmZUludGVnZXIoSW5maW5pdHkpOwogICAgICAgICAqIC8vID0+IDkwMDcxOTkyNTQ3NDA5OTEKICAgICAgICAgKgogICAgICAgICAqIF8udG9TYWZlSW50ZWdlcignMy4yJyk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvU2FmZUludGVnZXIodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB2YWx1ZQogICAgICAgICAgICA/IGJhc2VDbGFtcCh0b0ludGVnZXIodmFsdWUpLCAtTUFYX1NBRkVfSU5URUdFUiwgTUFYX1NBRkVfSU5URUdFUikKICAgICAgICAgICAgOiAodmFsdWUgPT09IDAgPyB2YWx1ZSA6IDApOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHZhbHVlYCB0byBhIHN0cmluZy4gQW4gZW1wdHkgc3RyaW5nIGlzIHJldHVybmVkIGZvciBgbnVsbGAKICAgICAgICAgKiBhbmQgYHVuZGVmaW5lZGAgdmFsdWVzLiBUaGUgc2lnbiBvZiBgLTBgIGlzIHByZXNlcnZlZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBjb252ZXJ0ZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvU3RyaW5nKG51bGwpOwogICAgICAgICAqIC8vID0+ICcnCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvU3RyaW5nKC0wKTsKICAgICAgICAgKiAvLyA9PiAnLTAnCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvU3RyaW5nKFsxLCAyLCAzXSk7CiAgICAgICAgICogLy8gPT4gJzEsMiwzJwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvU3RyaW5nKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdmFsdWUgPT0gbnVsbCA/ICcnIDogYmFzZVRvU3RyaW5nKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQXNzaWducyBvd24gZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgcHJvcGVydGllcyBvZiBzb3VyY2Ugb2JqZWN0cyB0byB0aGUKICAgICAgICAgKiBkZXN0aW5hdGlvbiBvYmplY3QuIFNvdXJjZSBvYmplY3RzIGFyZSBhcHBsaWVkIGZyb20gbGVmdCB0byByaWdodC4KICAgICAgICAgKiBTdWJzZXF1ZW50IHNvdXJjZXMgb3ZlcndyaXRlIHByb3BlcnR5IGFzc2lnbm1lbnRzIG9mIHByZXZpb3VzIHNvdXJjZXMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YCBhbmQgaXMgbG9vc2VseSBiYXNlZCBvbgogICAgICAgICAqIFtgT2JqZWN0LmFzc2lnbmBdKGh0dHBzOi8vbWRuLmlvL09iamVjdC9hc3NpZ24pLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuMTAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi5PYmplY3R9IFtzb3VyY2VzXSBUaGUgc291cmNlIG9iamVjdHMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAc2VlIF8uYXNzaWduSW4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICAgICAqICAgdGhpcy5hID0gMTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBCYXIoKSB7CiAgICAgICAgICogICB0aGlzLmMgPSAzOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYiA9IDI7CiAgICAgICAgICogQmFyLnByb3RvdHlwZS5kID0gNDsKICAgICAgICAgKgogICAgICAgICAqIF8uYXNzaWduKHsgJ2EnOiAwIH0sIG5ldyBGb28sIG5ldyBCYXIpOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiAxLCAnYyc6IDMgfQogICAgICAgICAqLwogICAgICAgIHZhciBhc3NpZ24gPSBjcmVhdGVBc3NpZ25lcihmdW5jdGlvbihvYmplY3QsIHNvdXJjZSkgewogICAgICAgICAgaWYgKGlzUHJvdG90eXBlKHNvdXJjZSkgfHwgaXNBcnJheUxpa2Uoc291cmNlKSkgewogICAgICAgICAgICBjb3B5T2JqZWN0KHNvdXJjZSwga2V5cyhzb3VyY2UpLCBvYmplY3QpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBmb3IgKHZhciBrZXkgaW4gc291cmNlKSB7CiAgICAgICAgICAgIGlmIChoYXNPd25Qcm9wZXJ0eS5jYWxsKHNvdXJjZSwga2V5KSkgewogICAgICAgICAgICAgIGFzc2lnblZhbHVlKG9iamVjdCwga2V5LCBzb3VyY2Vba2V5XSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5hc3NpZ25gIGV4Y2VwdCB0aGF0IGl0IGl0ZXJhdGVzIG92ZXIgb3duIGFuZAogICAgICAgICAqIGluaGVyaXRlZCBzb3VyY2UgcHJvcGVydGllcy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBtdXRhdGVzIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGFsaWFzIGV4dGVuZAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi5PYmplY3R9IFtzb3VyY2VzXSBUaGUgc291cmNlIG9iamVjdHMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAc2VlIF8uYXNzaWduCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gQmFyKCkgewogICAgICAgICAqICAgdGhpcy5jID0gMzsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBGb28ucHJvdG90eXBlLmIgPSAyOwogICAgICAgICAqIEJhci5wcm90b3R5cGUuZCA9IDQ7CiAgICAgICAgICoKICAgICAgICAgKiBfLmFzc2lnbkluKHsgJ2EnOiAwIH0sIG5ldyBGb28sIG5ldyBCYXIpOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiAxLCAnYic6IDIsICdjJzogMywgJ2QnOiA0IH0KICAgICAgICAgKi8KICAgICAgICB2YXIgYXNzaWduSW4gPSBjcmVhdGVBc3NpZ25lcihmdW5jdGlvbihvYmplY3QsIHNvdXJjZSkgewogICAgICAgICAgY29weU9iamVjdChzb3VyY2UsIGtleXNJbihzb3VyY2UpLCBvYmplY3QpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmFzc2lnbkluYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjdXN0b21pemVyYAogICAgICAgICAqIHdoaWNoIGlzIGludm9rZWQgdG8gcHJvZHVjZSB0aGUgYXNzaWduZWQgdmFsdWVzLiBJZiBgY3VzdG9taXplcmAgcmV0dXJucwogICAgICAgICAqIGB1bmRlZmluZWRgLCBhc3NpZ25tZW50IGlzIGhhbmRsZWQgYnkgdGhlIG1ldGhvZCBpbnN0ZWFkLiBUaGUgYGN1c3RvbWl6ZXJgCiAgICAgICAgICogaXMgaW52b2tlZCB3aXRoIGZpdmUgYXJndW1lbnRzOiAob2JqVmFsdWUsIHNyY1ZhbHVlLCBrZXksIG9iamVjdCwgc291cmNlKS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBtdXRhdGVzIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGFsaWFzIGV4dGVuZFdpdGgKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7Li4uT2JqZWN0fSBzb3VyY2VzIFRoZSBzb3VyY2Ugb2JqZWN0cy4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBhc3NpZ25lZCB2YWx1ZXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAc2VlIF8uYXNzaWduV2l0aAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBjdXN0b21pemVyKG9ialZhbHVlLCBzcmNWYWx1ZSkgewogICAgICAgICAqICAgcmV0dXJuIF8uaXNVbmRlZmluZWQob2JqVmFsdWUpID8gc3JjVmFsdWUgOiBvYmpWYWx1ZTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZGVmYXVsdHMgPSBfLnBhcnRpYWxSaWdodChfLmFzc2lnbkluV2l0aCwgY3VzdG9taXplcik7CiAgICAgICAgICoKICAgICAgICAgKiBkZWZhdWx0cyh7ICdhJzogMSB9LCB7ICdiJzogMiB9LCB7ICdhJzogMyB9KTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAgICAgKi8KICAgICAgICB2YXIgYXNzaWduSW5XaXRoID0gY3JlYXRlQXNzaWduZXIoZnVuY3Rpb24ob2JqZWN0LCBzb3VyY2UsIHNyY0luZGV4LCBjdXN0b21pemVyKSB7CiAgICAgICAgICBjb3B5T2JqZWN0KHNvdXJjZSwga2V5c0luKHNvdXJjZSksIG9iamVjdCwgY3VzdG9taXplcik7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uYXNzaWduYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjdXN0b21pemVyYAogICAgICAgICAqIHdoaWNoIGlzIGludm9rZWQgdG8gcHJvZHVjZSB0aGUgYXNzaWduZWQgdmFsdWVzLiBJZiBgY3VzdG9taXplcmAgcmV0dXJucwogICAgICAgICAqIGB1bmRlZmluZWRgLCBhc3NpZ25tZW50IGlzIGhhbmRsZWQgYnkgdGhlIG1ldGhvZCBpbnN0ZWFkLiBUaGUgYGN1c3RvbWl6ZXJgCiAgICAgICAgICogaXMgaW52b2tlZCB3aXRoIGZpdmUgYXJndW1lbnRzOiAob2JqVmFsdWUsIHNyY1ZhbHVlLCBrZXksIG9iamVjdCwgc291cmNlKS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBtdXRhdGVzIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIGRlc3RpbmF0aW9uIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0gey4uLk9iamVjdH0gc291cmNlcyBUaGUgc291cmNlIG9iamVjdHMuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgYXNzaWduZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmFzc2lnbkluV2l0aAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBjdXN0b21pemVyKG9ialZhbHVlLCBzcmNWYWx1ZSkgewogICAgICAgICAqICAgcmV0dXJuIF8uaXNVbmRlZmluZWQob2JqVmFsdWUpID8gc3JjVmFsdWUgOiBvYmpWYWx1ZTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZGVmYXVsdHMgPSBfLnBhcnRpYWxSaWdodChfLmFzc2lnbldpdGgsIGN1c3RvbWl6ZXIpOwogICAgICAgICAqCiAgICAgICAgICogZGVmYXVsdHMoeyAnYSc6IDEgfSwgeyAnYic6IDIgfSwgeyAnYSc6IDMgfSk7CiAgICAgICAgICogLy8gPT4geyAnYSc6IDEsICdiJzogMiB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGFzc2lnbldpdGggPSBjcmVhdGVBc3NpZ25lcihmdW5jdGlvbihvYmplY3QsIHNvdXJjZSwgc3JjSW5kZXgsIGN1c3RvbWl6ZXIpIHsKICAgICAgICAgIGNvcHlPYmplY3Qoc291cmNlLCBrZXlzKHNvdXJjZSksIG9iamVjdCwgY3VzdG9taXplcik7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgdmFsdWVzIGNvcnJlc3BvbmRpbmcgdG8gYHBhdGhzYCBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAxLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7Li4uKHN0cmluZ3xzdHJpbmdbXSl9IFtwYXRoc10gVGhlIHByb3BlcnR5IHBhdGhzIHRvIHBpY2suCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBwaWNrZWQgdmFsdWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IFt7ICdiJzogeyAnYyc6IDMgfSB9LCA0XSB9OwogICAgICAgICAqCiAgICAgICAgICogXy5hdChvYmplY3QsIFsnYVswXS5iLmMnLCAnYVsxXSddKTsKICAgICAgICAgKiAvLyA9PiBbMywgNF0KICAgICAgICAgKi8KICAgICAgICB2YXIgYXQgPSBmbGF0UmVzdChiYXNlQXQpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIG9iamVjdCB0aGF0IGluaGVyaXRzIGZyb20gdGhlIGBwcm90b3R5cGVgIG9iamVjdC4gSWYgYQogICAgICAgICAqIGBwcm9wZXJ0aWVzYCBvYmplY3QgaXMgZ2l2ZW4sIGl0cyBvd24gZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgcHJvcGVydGllcwogICAgICAgICAqIGFyZSBhc3NpZ25lZCB0byB0aGUgY3JlYXRlZCBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMi4zLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHByb3RvdHlwZSBUaGUgb2JqZWN0IHRvIGluaGVyaXQgZnJvbS4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW3Byb3BlcnRpZXNdIFRoZSBwcm9wZXJ0aWVzIHRvIGFzc2lnbiB0byB0aGUgb2JqZWN0LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIFNoYXBlKCkgewogICAgICAgICAqICAgdGhpcy54ID0gMDsKICAgICAgICAgKiAgIHRoaXMueSA9IDA7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gQ2lyY2xlKCkgewogICAgICAgICAqICAgU2hhcGUuY2FsbCh0aGlzKTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBDaXJjbGUucHJvdG90eXBlID0gXy5jcmVhdGUoU2hhcGUucHJvdG90eXBlLCB7CiAgICAgICAgICogICAnY29uc3RydWN0b3InOiBDaXJjbGUKICAgICAgICAgKiB9KTsKICAgICAgICAgKgogICAgICAgICAqIHZhciBjaXJjbGUgPSBuZXcgQ2lyY2xlOwogICAgICAgICAqIGNpcmNsZSBpbnN0YW5jZW9mIENpcmNsZTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBjaXJjbGUgaW5zdGFuY2VvZiBTaGFwZTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY3JlYXRlKHByb3RvdHlwZSwgcHJvcGVydGllcykgewogICAgICAgICAgdmFyIHJlc3VsdCA9IGJhc2VDcmVhdGUocHJvdG90eXBlKTsKICAgICAgICAgIHJldHVybiBwcm9wZXJ0aWVzID09IG51bGwgPyByZXN1bHQgOiBiYXNlQXNzaWduKHJlc3VsdCwgcHJvcGVydGllcyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBBc3NpZ25zIG93biBhbmQgaW5oZXJpdGVkIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnRpZXMgb2Ygc291cmNlCiAgICAgICAgICogb2JqZWN0cyB0byB0aGUgZGVzdGluYXRpb24gb2JqZWN0IGZvciBhbGwgZGVzdGluYXRpb24gcHJvcGVydGllcyB0aGF0CiAgICAgICAgICogcmVzb2x2ZSB0byBgdW5kZWZpbmVkYC4gU291cmNlIG9iamVjdHMgYXJlIGFwcGxpZWQgZnJvbSBsZWZ0IHRvIHJpZ2h0LgogICAgICAgICAqIE9uY2UgYSBwcm9wZXJ0eSBpcyBzZXQsIGFkZGl0aW9uYWwgdmFsdWVzIG9mIHRoZSBzYW1lIHByb3BlcnR5IGFyZSBpZ25vcmVkLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIG11dGF0ZXMgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7Li4uT2JqZWN0fSBbc291cmNlc10gVGhlIHNvdXJjZSBvYmplY3RzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmRlZmF1bHRzRGVlcAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRlZmF1bHRzKHsgJ2EnOiAxIH0sIHsgJ2InOiAyIH0sIHsgJ2EnOiAzIH0pOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiAxLCAnYic6IDIgfQogICAgICAgICAqLwogICAgICAgIHZhciBkZWZhdWx0cyA9IGJhc2VSZXN0KGZ1bmN0aW9uKG9iamVjdCwgc291cmNlcykgewogICAgICAgICAgb2JqZWN0ID0gT2JqZWN0KG9iamVjdCk7CgogICAgICAgICAgdmFyIGluZGV4ID0gLTE7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gc291cmNlcy5sZW5ndGg7CiAgICAgICAgICB2YXIgZ3VhcmQgPSBsZW5ndGggPiAyID8gc291cmNlc1syXSA6IHVuZGVmaW5lZCQxOwoKICAgICAgICAgIGlmIChndWFyZCAmJiBpc0l0ZXJhdGVlQ2FsbChzb3VyY2VzWzBdLCBzb3VyY2VzWzFdLCBndWFyZCkpIHsKICAgICAgICAgICAgbGVuZ3RoID0gMTsKICAgICAgICAgIH0KCiAgICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgICB2YXIgc291cmNlID0gc291cmNlc1tpbmRleF07CiAgICAgICAgICAgIHZhciBwcm9wcyA9IGtleXNJbihzb3VyY2UpOwogICAgICAgICAgICB2YXIgcHJvcHNJbmRleCA9IC0xOwogICAgICAgICAgICB2YXIgcHJvcHNMZW5ndGggPSBwcm9wcy5sZW5ndGg7CgogICAgICAgICAgICB3aGlsZSAoKytwcm9wc0luZGV4IDwgcHJvcHNMZW5ndGgpIHsKICAgICAgICAgICAgICB2YXIga2V5ID0gcHJvcHNbcHJvcHNJbmRleF07CiAgICAgICAgICAgICAgdmFyIHZhbHVlID0gb2JqZWN0W2tleV07CgogICAgICAgICAgICAgIGlmICh2YWx1ZSA9PT0gdW5kZWZpbmVkJDEgfHwKICAgICAgICAgICAgICAgICAgKGVxKHZhbHVlLCBvYmplY3RQcm90b1trZXldKSAmJiAhaGFzT3duUHJvcGVydHkuY2FsbChvYmplY3QsIGtleSkpKSB7CiAgICAgICAgICAgICAgICBvYmplY3Rba2V5XSA9IHNvdXJjZVtrZXldOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQoKICAgICAgICAgIHJldHVybiBvYmplY3Q7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZGVmYXVsdHNgIGV4Y2VwdCB0aGF0IGl0IHJlY3Vyc2l2ZWx5IGFzc2lnbnMKICAgICAgICAgKiBkZWZhdWx0IHByb3BlcnRpZXMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjEwLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7Li4uT2JqZWN0fSBbc291cmNlc10gVGhlIHNvdXJjZSBvYmplY3RzLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmRlZmF1bHRzCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZGVmYXVsdHNEZWVwKHsgJ2EnOiB7ICdiJzogMiB9IH0sIHsgJ2EnOiB7ICdiJzogMSwgJ2MnOiAzIH0gfSk7CiAgICAgICAgICogLy8gPT4geyAnYSc6IHsgJ2InOiAyLCAnYyc6IDMgfSB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGRlZmF1bHRzRGVlcCA9IGJhc2VSZXN0KGZ1bmN0aW9uKGFyZ3MpIHsKICAgICAgICAgIGFyZ3MucHVzaCh1bmRlZmluZWQkMSwgY3VzdG9tRGVmYXVsdHNNZXJnZSk7CiAgICAgICAgICByZXR1cm4gYXBwbHkobWVyZ2VXaXRoLCB1bmRlZmluZWQkMSwgYXJncyk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZmluZGAgZXhjZXB0IHRoYXQgaXQgcmV0dXJucyB0aGUga2V5IG9mIHRoZSBmaXJzdAogICAgICAgICAqIGVsZW1lbnQgYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yIGluc3RlYWQgb2YgdGhlIGVsZW1lbnQgaXRzZWxmLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDEuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfHVuZGVmaW5lZH0gUmV0dXJucyB0aGUga2V5IG9mIHRoZSBtYXRjaGVkIGVsZW1lbnQsCiAgICAgICAgICogIGVsc2UgYHVuZGVmaW5lZGAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IHsKICAgICAgICAgKiAgICdiYXJuZXknOiAgeyAnYWdlJzogMzYsICdhY3RpdmUnOiB0cnVlIH0sCiAgICAgICAgICogICAnZnJlZCc6ICAgIHsgJ2FnZSc6IDQwLCAnYWN0aXZlJzogZmFsc2UgfSwKICAgICAgICAgKiAgICdwZWJibGVzJzogeyAnYWdlJzogMSwgICdhY3RpdmUnOiB0cnVlIH0KICAgICAgICAgKiB9OwogICAgICAgICAqCiAgICAgICAgICogXy5maW5kS2V5KHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiBvLmFnZSA8IDQwOyB9KTsKICAgICAgICAgKiAvLyA9PiAnYmFybmV5JyAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmZpbmRLZXkodXNlcnMsIHsgJ2FnZSc6IDEsICdhY3RpdmUnOiB0cnVlIH0pOwogICAgICAgICAqIC8vID0+ICdwZWJibGVzJwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZEtleSh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICAgICAqIC8vID0+ICdmcmVkJwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5maW5kS2V5KHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgICAgICogLy8gPT4gJ2Jhcm5leScKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmaW5kS2V5KG9iamVjdCwgcHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUZpbmRLZXkob2JqZWN0LCBnZXRJdGVyYXRlZShwcmVkaWNhdGUsIDMpLCBiYXNlRm9yT3duKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZmluZEtleWAgZXhjZXB0IHRoYXQgaXQgaXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZgogICAgICAgICAqIGEgY29sbGVjdGlvbiBpbiB0aGUgb3Bwb3NpdGUgb3JkZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMi4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW3ByZWRpY2F0ZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd8dW5kZWZpbmVkfSBSZXR1cm5zIHRoZSBrZXkgb2YgdGhlIG1hdGNoZWQgZWxlbWVudCwKICAgICAgICAgKiAgZWxzZSBgdW5kZWZpbmVkYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIHVzZXJzID0gewogICAgICAgICAqICAgJ2Jhcm5leSc6ICB7ICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAgICAgKiAgICdmcmVkJzogICAgeyAnYWdlJzogNDAsICdhY3RpdmUnOiBmYWxzZSB9LAogICAgICAgICAqICAgJ3BlYmJsZXMnOiB7ICdhZ2UnOiAxLCAgJ2FjdGl2ZSc6IHRydWUgfQogICAgICAgICAqIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLmZpbmRMYXN0S2V5KHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiBvLmFnZSA8IDQwOyB9KTsKICAgICAgICAgKiAvLyA9PiByZXR1cm5zICdwZWJibGVzJyBhc3N1bWluZyBgXy5maW5kS2V5YCByZXR1cm5zICdiYXJuZXknCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZExhc3RLZXkodXNlcnMsIHsgJ2FnZSc6IDM2LCAnYWN0aXZlJzogdHJ1ZSB9KTsKICAgICAgICAgKiAvLyA9PiAnYmFybmV5JwogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLm1hdGNoZXNQcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZExhc3RLZXkodXNlcnMsIFsnYWN0aXZlJywgZmFsc2VdKTsKICAgICAgICAgKiAvLyA9PiAnZnJlZCcKICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5wcm9wZXJ0eWAgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmluZExhc3RLZXkodXNlcnMsICdhY3RpdmUnKTsKICAgICAgICAgKiAvLyA9PiAncGViYmxlcycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBmaW5kTGFzdEtleShvYmplY3QsIHByZWRpY2F0ZSkgewogICAgICAgICAgcmV0dXJuIGJhc2VGaW5kS2V5KG9iamVjdCwgZ2V0SXRlcmF0ZWUocHJlZGljYXRlLCAzKSwgYmFzZUZvck93blJpZ2h0KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEl0ZXJhdGVzIG92ZXIgb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgcHJvcGVydGllcyBvZiBhbgogICAgICAgICAqIG9iamVjdCBhbmQgaW52b2tlcyBgaXRlcmF0ZWVgIGZvciBlYWNoIHByb3BlcnR5LiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZAogICAgICAgICAqIHdpdGggdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGtleSwgb2JqZWN0KS4gSXRlcmF0ZWUgZnVuY3Rpb25zIG1heSBleGl0CiAgICAgICAgICogaXRlcmF0aW9uIGVhcmx5IGJ5IGV4cGxpY2l0bHkgcmV0dXJuaW5nIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC4zLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqIEBzZWUgXy5mb3JJblJpZ2h0CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogICB0aGlzLmIgPSAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgICAgICoKICAgICAgICAgKiBfLmZvckluKG5ldyBGb28sIGZ1bmN0aW9uKHZhbHVlLCBrZXkpIHsKICAgICAgICAgKiAgIGNvbnNvbGUubG9nKGtleSk7CiAgICAgICAgICogfSk7CiAgICAgICAgICogLy8gPT4gTG9ncyAnYScsICdiJywgdGhlbiAnYycgKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZm9ySW4ob2JqZWN0LCBpdGVyYXRlZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsCiAgICAgICAgICAgID8gb2JqZWN0CiAgICAgICAgICAgIDogYmFzZUZvcihvYmplY3QsIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAzKSwga2V5c0luKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZm9ySW5gIGV4Y2VwdCB0aGF0IGl0IGl0ZXJhdGVzIG92ZXIgcHJvcGVydGllcyBvZgogICAgICAgICAqIGBvYmplY3RgIGluIHRoZSBvcHBvc2l0ZSBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmZvckluCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogICB0aGlzLmIgPSAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgICAgICoKICAgICAgICAgKiBfLmZvckluUmlnaHQobmV3IEZvbywgZnVuY3Rpb24odmFsdWUsIGtleSkgewogICAgICAgICAqICAgY29uc29sZS5sb2coa2V5KTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKiAvLyA9PiBMb2dzICdjJywgJ2InLCB0aGVuICdhJyBhc3N1bWluZyBgXy5mb3JJbmAgbG9ncyAnYScsICdiJywgdGhlbiAnYycuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZm9ySW5SaWdodChvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ID09IG51bGwKICAgICAgICAgICAgPyBvYmplY3QKICAgICAgICAgICAgOiBiYXNlRm9yUmlnaHQob2JqZWN0LCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMyksIGtleXNJbik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJdGVyYXRlcyBvdmVyIG93biBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIG9mIGFuIG9iamVjdCBhbmQKICAgICAgICAgKiBpbnZva2VzIGBpdGVyYXRlZWAgZm9yIGVhY2ggcHJvcGVydHkuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggdGhyZWUKICAgICAgICAgKiBhcmd1bWVudHM6ICh2YWx1ZSwga2V5LCBvYmplY3QpLiBJdGVyYXRlZSBmdW5jdGlvbnMgbWF5IGV4aXQgaXRlcmF0aW9uCiAgICAgICAgICogZWFybHkgYnkgZXhwbGljaXRseSByZXR1cm5pbmcgYGZhbHNlYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjMuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmZvck93blJpZ2h0CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogICB0aGlzLmIgPSAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgICAgICoKICAgICAgICAgKiBfLmZvck93bihuZXcgRm9vLCBmdW5jdGlvbih2YWx1ZSwga2V5KSB7CiAgICAgICAgICogICBjb25zb2xlLmxvZyhrZXkpOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IExvZ3MgJ2EnIHRoZW4gJ2InIChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGZvck93bihvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ICYmIGJhc2VGb3JPd24ob2JqZWN0LCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5mb3JPd25gIGV4Y2VwdCB0aGF0IGl0IGl0ZXJhdGVzIG92ZXIgcHJvcGVydGllcyBvZgogICAgICAgICAqIGBvYmplY3RgIGluIHRoZSBvcHBvc2l0ZSBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQHNlZSBfLmZvck93bgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgICAgICogICB0aGlzLmEgPSAxOwogICAgICAgICAqICAgdGhpcy5iID0gMjsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBGb28ucHJvdG90eXBlLmMgPSAzOwogICAgICAgICAqCiAgICAgICAgICogXy5mb3JPd25SaWdodChuZXcgRm9vLCBmdW5jdGlvbih2YWx1ZSwga2V5KSB7CiAgICAgICAgICogICBjb25zb2xlLmxvZyhrZXkpOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IExvZ3MgJ2InIHRoZW4gJ2EnIGFzc3VtaW5nIGBfLmZvck93bmAgbG9ncyAnYScgdGhlbiAnYicuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZm9yT3duUmlnaHQob2JqZWN0LCBpdGVyYXRlZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCAmJiBiYXNlRm9yT3duUmlnaHQob2JqZWN0LCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBmdW5jdGlvbiBwcm9wZXJ0eSBuYW1lcyBmcm9tIG93biBlbnVtZXJhYmxlIHByb3BlcnRpZXMKICAgICAgICAgKiBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGZ1bmN0aW9uIG5hbWVzLgogICAgICAgICAqIEBzZWUgXy5mdW5jdGlvbnNJbgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgICAgICogICB0aGlzLmEgPSBfLmNvbnN0YW50KCdhJyk7CiAgICAgICAgICogICB0aGlzLmIgPSBfLmNvbnN0YW50KCdiJyk7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogRm9vLnByb3RvdHlwZS5jID0gXy5jb25zdGFudCgnYycpOwogICAgICAgICAqCiAgICAgICAgICogXy5mdW5jdGlvbnMobmV3IEZvbyk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGZ1bmN0aW9ucyhvYmplY3QpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IFtdIDogYmFzZUZ1bmN0aW9ucyhvYmplY3QsIGtleXMob2JqZWN0KSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIGZ1bmN0aW9uIHByb3BlcnR5IG5hbWVzIGZyb20gb3duIGFuZCBpbmhlcml0ZWQKICAgICAgICAgKiBlbnVtZXJhYmxlIHByb3BlcnRpZXMgb2YgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGluc3BlY3QuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBmdW5jdGlvbiBuYW1lcy4KICAgICAgICAgKiBAc2VlIF8uZnVuY3Rpb25zCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IF8uY29uc3RhbnQoJ2EnKTsKICAgICAgICAgKiAgIHRoaXMuYiA9IF8uY29uc3RhbnQoJ2InKTsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBGb28ucHJvdG90eXBlLmMgPSBfLmNvbnN0YW50KCdjJyk7CiAgICAgICAgICoKICAgICAgICAgKiBfLmZ1bmN0aW9uc0luKG5ldyBGb28pOwogICAgICAgICAqIC8vID0+IFsnYScsICdiJywgJ2MnXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGZ1bmN0aW9uc0luKG9iamVjdCkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8gW10gOiBiYXNlRnVuY3Rpb25zKG9iamVjdCwga2V5c0luKG9iamVjdCkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgdmFsdWUgYXQgYHBhdGhgIG9mIGBvYmplY3RgLiBJZiB0aGUgcmVzb2x2ZWQgdmFsdWUgaXMKICAgICAgICAgKiBgdW5kZWZpbmVkYCwgdGhlIGBkZWZhdWx0VmFsdWVgIGlzIHJldHVybmVkIGluIGl0cyBwbGFjZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjcuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAgICAgKiBAcGFyYW0geyp9IFtkZWZhdWx0VmFsdWVdIFRoZSB2YWx1ZSByZXR1cm5lZCBmb3IgYHVuZGVmaW5lZGAgcmVzb2x2ZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXNvbHZlZCB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiBbeyAnYic6IHsgJ2MnOiAzIH0gfV0gfTsKICAgICAgICAgKgogICAgICAgICAqIF8uZ2V0KG9iamVjdCwgJ2FbMF0uYi5jJyk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqCiAgICAgICAgICogXy5nZXQob2JqZWN0LCBbJ2EnLCAnMCcsICdiJywgJ2MnXSk7CiAgICAgICAgICogLy8gPT4gMwogICAgICAgICAqCiAgICAgICAgICogXy5nZXQob2JqZWN0LCAnYS5iLmMnLCAnZGVmYXVsdCcpOwogICAgICAgICAqIC8vID0+ICdkZWZhdWx0JwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGdldChvYmplY3QsIHBhdGgsIGRlZmF1bHRWYWx1ZSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IG9iamVjdCA9PSBudWxsID8gdW5kZWZpbmVkJDEgOiBiYXNlR2V0KG9iamVjdCwgcGF0aCk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0ID09PSB1bmRlZmluZWQkMSA/IGRlZmF1bHRWYWx1ZSA6IHJlc3VsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgcGF0aGAgaXMgYSBkaXJlY3QgcHJvcGVydHkgb2YgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgcGF0aGAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogeyAnYic6IDIgfSB9OwogICAgICAgICAqIHZhciBvdGhlciA9IF8uY3JlYXRlKHsgJ2EnOiBfLmNyZWF0ZSh7ICdiJzogMiB9KSB9KTsKICAgICAgICAgKgogICAgICAgICAqIF8uaGFzKG9iamVjdCwgJ2EnKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmhhcyhvYmplY3QsICdhLmInKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmhhcyhvYmplY3QsIFsnYScsICdiJ10pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaGFzKG90aGVyLCAnYScpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaGFzKG9iamVjdCwgcGF0aCkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCAhPSBudWxsICYmIGhhc1BhdGgob2JqZWN0LCBwYXRoLCBiYXNlSGFzKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiBgcGF0aGAgaXMgYSBkaXJlY3Qgb3IgaW5oZXJpdGVkIHByb3BlcnR5IG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCB0byBjaGVjay4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHBhdGhgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0gXy5jcmVhdGUoeyAnYSc6IF8uY3JlYXRlKHsgJ2InOiAyIH0pIH0pOwogICAgICAgICAqCiAgICAgICAgICogXy5oYXNJbihvYmplY3QsICdhJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5oYXNJbihvYmplY3QsICdhLmInKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmhhc0luKG9iamVjdCwgWydhJywgJ2InXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5oYXNJbihvYmplY3QsICdiJyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBoYXNJbihvYmplY3QsIHBhdGgpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgIT0gbnVsbCAmJiBoYXNQYXRoKG9iamVjdCwgcGF0aCwgYmFzZUhhc0luKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gb2JqZWN0IGNvbXBvc2VkIG9mIHRoZSBpbnZlcnRlZCBrZXlzIGFuZCB2YWx1ZXMgb2YgYG9iamVjdGAuCiAgICAgICAgICogSWYgYG9iamVjdGAgY29udGFpbnMgZHVwbGljYXRlIHZhbHVlcywgc3Vic2VxdWVudCB2YWx1ZXMgb3ZlcndyaXRlCiAgICAgICAgICogcHJvcGVydHkgYXNzaWdubWVudHMgb2YgcHJldmlvdXMgdmFsdWVzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV3IGludmVydGVkIG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiAxLCAnYic6IDIsICdjJzogMSB9OwogICAgICAgICAqCiAgICAgICAgICogXy5pbnZlcnQob2JqZWN0KTsKICAgICAgICAgKiAvLyA9PiB7ICcxJzogJ2MnLCAnMic6ICdiJyB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGludmVydCA9IGNyZWF0ZUludmVydGVyKGZ1bmN0aW9uKHJlc3VsdCwgdmFsdWUsIGtleSkgewogICAgICAgICAgaWYgKHZhbHVlICE9IG51bGwgJiYKICAgICAgICAgICAgICB0eXBlb2YgdmFsdWUudG9TdHJpbmcgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICB2YWx1ZSA9IG5hdGl2ZU9iamVjdFRvU3RyaW5nLmNhbGwodmFsdWUpOwogICAgICAgICAgfQoKICAgICAgICAgIHJlc3VsdFt2YWx1ZV0gPSBrZXk7CiAgICAgICAgfSwgY29uc3RhbnQoaWRlbnRpdHkpKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5pbnZlcnRgIGV4Y2VwdCB0aGF0IHRoZSBpbnZlcnRlZCBvYmplY3QgaXMgZ2VuZXJhdGVkCiAgICAgICAgICogZnJvbSB0aGUgcmVzdWx0cyBvZiBydW5uaW5nIGVhY2ggZWxlbWVudCBvZiBgb2JqZWN0YCB0aHJ1IGBpdGVyYXRlZWAuIFRoZQogICAgICAgICAqIGNvcnJlc3BvbmRpbmcgaW52ZXJ0ZWQgdmFsdWUgb2YgZWFjaCBpbnZlcnRlZCBrZXkgaXMgYW4gYXJyYXkgb2Yga2V5cwogICAgICAgICAqIHJlc3BvbnNpYmxlIGZvciBnZW5lcmF0aW5nIHRoZSBpbnZlcnRlZCB2YWx1ZS4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQKICAgICAgICAgKiB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjEuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaW52ZXJ0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgaW52ZXJ0ZWQgb2JqZWN0LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IDEsICdiJzogMiwgJ2MnOiAxIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLmludmVydEJ5KG9iamVjdCk7CiAgICAgICAgICogLy8gPT4geyAnMSc6IFsnYScsICdjJ10sICcyJzogWydiJ10gfQogICAgICAgICAqCiAgICAgICAgICogXy5pbnZlcnRCeShvYmplY3QsIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICogICByZXR1cm4gJ2dyb3VwJyArIHZhbHVlOwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+IHsgJ2dyb3VwMSc6IFsnYScsICdjJ10sICdncm91cDInOiBbJ2InXSB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGludmVydEJ5ID0gY3JlYXRlSW52ZXJ0ZXIoZnVuY3Rpb24ocmVzdWx0LCB2YWx1ZSwga2V5KSB7CiAgICAgICAgICBpZiAodmFsdWUgIT0gbnVsbCAmJgogICAgICAgICAgICAgIHR5cGVvZiB2YWx1ZS50b1N0cmluZyAhPSAnZnVuY3Rpb24nKSB7CiAgICAgICAgICAgIHZhbHVlID0gbmF0aXZlT2JqZWN0VG9TdHJpbmcuY2FsbCh2YWx1ZSk7CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKGhhc093blByb3BlcnR5LmNhbGwocmVzdWx0LCB2YWx1ZSkpIHsKICAgICAgICAgICAgcmVzdWx0W3ZhbHVlXS5wdXNoKGtleSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXN1bHRbdmFsdWVdID0gW2tleV07CiAgICAgICAgICB9CiAgICAgICAgfSwgZ2V0SXRlcmF0ZWUpOwoKICAgICAgICAvKioKICAgICAgICAgKiBJbnZva2VzIHRoZSBtZXRob2QgYXQgYHBhdGhgIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgbWV0aG9kIHRvIGludm9rZS4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IFthcmdzXSBUaGUgYXJndW1lbnRzIHRvIGludm9rZSB0aGUgbWV0aG9kIHdpdGguCiAgICAgICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHJlc3VsdCBvZiB0aGUgaW52b2tlZCBtZXRob2QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogW3sgJ2InOiB7ICdjJzogWzEsIDIsIDMsIDRdIH0gfV0gfTsKICAgICAgICAgKgogICAgICAgICAqIF8uaW52b2tlKG9iamVjdCwgJ2FbMF0uYi5jLnNsaWNlJywgMSwgMyk7CiAgICAgICAgICogLy8gPT4gWzIsIDNdCiAgICAgICAgICovCiAgICAgICAgdmFyIGludm9rZSA9IGJhc2VSZXN0KGJhc2VJbnZva2UpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHRoZSBvd24gZW51bWVyYWJsZSBwcm9wZXJ0eSBuYW1lcyBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBOb24tb2JqZWN0IHZhbHVlcyBhcmUgY29lcmNlZCB0byBvYmplY3RzLiBTZWUgdGhlCiAgICAgICAgICogW0VTIHNwZWNdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLW9iamVjdC5rZXlzKQogICAgICAgICAqIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgbmFtZXMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogICB0aGlzLmIgPSAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgICAgICoKICAgICAgICAgKiBfLmtleXMobmV3IEZvbyk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InXSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICAgICAqCiAgICAgICAgICogXy5rZXlzKCdoaScpOwogICAgICAgICAqIC8vID0+IFsnMCcsICcxJ10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBrZXlzKG9iamVjdCkgewogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlKG9iamVjdCkgPyBhcnJheUxpa2VLZXlzKG9iamVjdCkgOiBiYXNlS2V5cyhvYmplY3QpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBwcm9wZXJ0eSBuYW1lcyBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBOb24tb2JqZWN0IHZhbHVlcyBhcmUgY29lcmNlZCB0byBvYmplY3RzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgICAgICogICB0aGlzLmEgPSAxOwogICAgICAgICAqICAgdGhpcy5iID0gMjsKICAgICAgICAgKiB9CiAgICAgICAgICoKICAgICAgICAgKiBGb28ucHJvdG90eXBlLmMgPSAzOwogICAgICAgICAqCiAgICAgICAgICogXy5rZXlzSW4obmV3IEZvbyk7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InLCAnYyddIChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24ga2V5c0luKG9iamVjdCkgewogICAgICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlKG9iamVjdCkgPyBhcnJheUxpa2VLZXlzKG9iamVjdCwgdHJ1ZSkgOiBiYXNlS2V5c0luKG9iamVjdCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3Bwb3NpdGUgb2YgYF8ubWFwVmFsdWVzYDsgdGhpcyBtZXRob2QgY3JlYXRlcyBhbiBvYmplY3Qgd2l0aCB0aGUKICAgICAgICAgKiBzYW1lIHZhbHVlcyBhcyBgb2JqZWN0YCBhbmQga2V5cyBnZW5lcmF0ZWQgYnkgcnVubmluZyBlYWNoIG93biBlbnVtZXJhYmxlCiAgICAgICAgICogc3RyaW5nIGtleWVkIHByb3BlcnR5IG9mIGBvYmplY3RgIHRocnUgYGl0ZXJhdGVlYC4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQKICAgICAgICAgKiB3aXRoIHRocmVlIGFyZ3VtZW50czogKHZhbHVlLCBrZXksIG9iamVjdCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy44LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgbWFwcGVkIG9iamVjdC4KICAgICAgICAgKiBAc2VlIF8ubWFwVmFsdWVzCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ubWFwS2V5cyh7ICdhJzogMSwgJ2InOiAyIH0sIGZ1bmN0aW9uKHZhbHVlLCBrZXkpIHsKICAgICAgICAgKiAgIHJldHVybiBrZXkgKyB2YWx1ZTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKiAvLyA9PiB7ICdhMSc6IDEsICdiMic6IDIgfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1hcEtleXMob2JqZWN0LCBpdGVyYXRlZSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IHt9OwogICAgICAgICAgaXRlcmF0ZWUgPSBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMyk7CgogICAgICAgICAgYmFzZUZvck93bihvYmplY3QsIGZ1bmN0aW9uKHZhbHVlLCBrZXksIG9iamVjdCkgewogICAgICAgICAgICBiYXNlQXNzaWduVmFsdWUocmVzdWx0LCBpdGVyYXRlZSh2YWx1ZSwga2V5LCBvYmplY3QpLCB2YWx1ZSk7CiAgICAgICAgICB9KTsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIG9iamVjdCB3aXRoIHRoZSBzYW1lIGtleXMgYXMgYG9iamVjdGAgYW5kIHZhbHVlcyBnZW5lcmF0ZWQKICAgICAgICAgKiBieSBydW5uaW5nIGVhY2ggb3duIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnR5IG9mIGBvYmplY3RgIHRocnUKICAgICAgICAgKiBgaXRlcmF0ZWVgLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIHRocmVlIGFyZ3VtZW50czoKICAgICAgICAgKiAodmFsdWUsIGtleSwgb2JqZWN0KS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAyLjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBtYXBwZWQgb2JqZWN0LgogICAgICAgICAqIEBzZWUgXy5tYXBLZXlzCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB1c2VycyA9IHsKICAgICAgICAgKiAgICdmcmVkJzogICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FnZSc6IDQwIH0sCiAgICAgICAgICogICAncGViYmxlcyc6IHsgJ3VzZXInOiAncGViYmxlcycsICdhZ2UnOiAxIH0KICAgICAgICAgKiB9OwogICAgICAgICAqCiAgICAgICAgICogXy5tYXBWYWx1ZXModXNlcnMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8uYWdlOyB9KTsKICAgICAgICAgKiAvLyA9PiB7ICdmcmVkJzogNDAsICdwZWJibGVzJzogMSB9IChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpCiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLm1hcFZhbHVlcyh1c2VycywgJ2FnZScpOwogICAgICAgICAqIC8vID0+IHsgJ2ZyZWQnOiA0MCwgJ3BlYmJsZXMnOiAxIH0gKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXBWYWx1ZXMob2JqZWN0LCBpdGVyYXRlZSkgewogICAgICAgICAgdmFyIHJlc3VsdCA9IHt9OwogICAgICAgICAgaXRlcmF0ZWUgPSBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMyk7CgogICAgICAgICAgYmFzZUZvck93bihvYmplY3QsIGZ1bmN0aW9uKHZhbHVlLCBrZXksIG9iamVjdCkgewogICAgICAgICAgICBiYXNlQXNzaWduVmFsdWUocmVzdWx0LCBrZXksIGl0ZXJhdGVlKHZhbHVlLCBrZXksIG9iamVjdCkpOwogICAgICAgICAgfSk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5hc3NpZ25gIGV4Y2VwdCB0aGF0IGl0IHJlY3Vyc2l2ZWx5IG1lcmdlcyBvd24gYW5kCiAgICAgICAgICogaW5oZXJpdGVkIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnRpZXMgb2Ygc291cmNlIG9iamVjdHMgaW50byB0aGUKICAgICAgICAgKiBkZXN0aW5hdGlvbiBvYmplY3QuIFNvdXJjZSBwcm9wZXJ0aWVzIHRoYXQgcmVzb2x2ZSB0byBgdW5kZWZpbmVkYCBhcmUKICAgICAgICAgKiBza2lwcGVkIGlmIGEgZGVzdGluYXRpb24gdmFsdWUgZXhpc3RzLiBBcnJheSBhbmQgcGxhaW4gb2JqZWN0IHByb3BlcnRpZXMKICAgICAgICAgKiBhcmUgbWVyZ2VkIHJlY3Vyc2l2ZWx5LiBPdGhlciBvYmplY3RzIGFuZCB2YWx1ZSB0eXBlcyBhcmUgb3ZlcnJpZGRlbiBieQogICAgICAgICAqIGFzc2lnbm1lbnQuIFNvdXJjZSBvYmplY3RzIGFyZSBhcHBsaWVkIGZyb20gbGVmdCB0byByaWdodC4gU3Vic2VxdWVudAogICAgICAgICAqIHNvdXJjZXMgb3ZlcndyaXRlIHByb3BlcnR5IGFzc2lnbm1lbnRzIG9mIHByZXZpb3VzIHNvdXJjZXMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAwLjUuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi5PYmplY3R9IFtzb3VyY2VzXSBUaGUgc291cmNlIG9iamVjdHMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsKICAgICAgICAgKiAgICdhJzogW3sgJ2InOiAyIH0sIHsgJ2QnOiA0IH1dCiAgICAgICAgICogfTsKICAgICAgICAgKgogICAgICAgICAqIHZhciBvdGhlciA9IHsKICAgICAgICAgKiAgICdhJzogW3sgJ2MnOiAzIH0sIHsgJ2UnOiA1IH1dCiAgICAgICAgICogfTsKICAgICAgICAgKgogICAgICAgICAqIF8ubWVyZ2Uob2JqZWN0LCBvdGhlcik7CiAgICAgICAgICogLy8gPT4geyAnYSc6IFt7ICdiJzogMiwgJ2MnOiAzIH0sIHsgJ2QnOiA0LCAnZSc6IDUgfV0gfQogICAgICAgICAqLwogICAgICAgIHZhciBtZXJnZSA9IGNyZWF0ZUFzc2lnbmVyKGZ1bmN0aW9uKG9iamVjdCwgc291cmNlLCBzcmNJbmRleCkgewogICAgICAgICAgYmFzZU1lcmdlKG9iamVjdCwgc291cmNlLCBzcmNJbmRleCk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8ubWVyZ2VgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGN1c3RvbWl6ZXJgIHdoaWNoCiAgICAgICAgICogaXMgaW52b2tlZCB0byBwcm9kdWNlIHRoZSBtZXJnZWQgdmFsdWVzIG9mIHRoZSBkZXN0aW5hdGlvbiBhbmQgc291cmNlCiAgICAgICAgICogcHJvcGVydGllcy4gSWYgYGN1c3RvbWl6ZXJgIHJldHVybnMgYHVuZGVmaW5lZGAsIG1lcmdpbmcgaXMgaGFuZGxlZCBieSB0aGUKICAgICAgICAgKiBtZXRob2QgaW5zdGVhZC4gVGhlIGBjdXN0b21pemVyYCBpcyBpbnZva2VkIHdpdGggc2l4IGFyZ3VtZW50czoKICAgICAgICAgKiAob2JqVmFsdWUsIHNyY1ZhbHVlLCBrZXksIG9iamVjdCwgc291cmNlLCBzdGFjaykuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi5PYmplY3R9IHNvdXJjZXMgVGhlIHNvdXJjZSBvYmplY3RzLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGN1c3RvbWl6ZXIgVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBhc3NpZ25lZCB2YWx1ZXMuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gY3VzdG9taXplcihvYmpWYWx1ZSwgc3JjVmFsdWUpIHsKICAgICAgICAgKiAgIGlmIChfLmlzQXJyYXkob2JqVmFsdWUpKSB7CiAgICAgICAgICogICAgIHJldHVybiBvYmpWYWx1ZS5jb25jYXQoc3JjVmFsdWUpOwogICAgICAgICAqICAgfQogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogWzFdLCAnYic6IFsyXSB9OwogICAgICAgICAqIHZhciBvdGhlciA9IHsgJ2EnOiBbM10sICdiJzogWzRdIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLm1lcmdlV2l0aChvYmplY3QsIG90aGVyLCBjdXN0b21pemVyKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogWzEsIDNdLCAnYic6IFsyLCA0XSB9CiAgICAgICAgICovCiAgICAgICAgdmFyIG1lcmdlV2l0aCA9IGNyZWF0ZUFzc2lnbmVyKGZ1bmN0aW9uKG9iamVjdCwgc291cmNlLCBzcmNJbmRleCwgY3VzdG9taXplcikgewogICAgICAgICAgYmFzZU1lcmdlKG9iamVjdCwgc291cmNlLCBzcmNJbmRleCwgY3VzdG9taXplcik7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBvcHBvc2l0ZSBvZiBgXy5waWNrYDsgdGhpcyBtZXRob2QgY3JlYXRlcyBhbiBvYmplY3QgY29tcG9zZWQgb2YgdGhlCiAgICAgICAgICogb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBwcm9wZXJ0eSBwYXRocyBvZiBgb2JqZWN0YCB0aGF0IGFyZSBub3Qgb21pdHRlZC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBjb25zaWRlcmFibHkgc2xvd2VyIHRoYW4gYF8ucGlja2AuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgc291cmNlIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0gey4uLihzdHJpbmd8c3RyaW5nW10pfSBbcGF0aHNdIFRoZSBwcm9wZXJ0eSBwYXRocyB0byBvbWl0LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSwgJ2InOiAnMicsICdjJzogMyB9OwogICAgICAgICAqCiAgICAgICAgICogXy5vbWl0KG9iamVjdCwgWydhJywgJ2MnXSk7CiAgICAgICAgICogLy8gPT4geyAnYic6ICcyJyB9CiAgICAgICAgICovCiAgICAgICAgdmFyIG9taXQgPSBmbGF0UmVzdChmdW5jdGlvbihvYmplY3QsIHBhdGhzKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0ge307CiAgICAgICAgICBpZiAob2JqZWN0ID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBpc0RlZXAgPSBmYWxzZTsKICAgICAgICAgIHBhdGhzID0gYXJyYXlNYXAocGF0aHMsIGZ1bmN0aW9uKHBhdGgpIHsKICAgICAgICAgICAgcGF0aCA9IGNhc3RQYXRoKHBhdGgsIG9iamVjdCk7CiAgICAgICAgICAgIGlzRGVlcCB8fCAoaXNEZWVwID0gcGF0aC5sZW5ndGggPiAxKTsKICAgICAgICAgICAgcmV0dXJuIHBhdGg7CiAgICAgICAgICB9KTsKICAgICAgICAgIGNvcHlPYmplY3Qob2JqZWN0LCBnZXRBbGxLZXlzSW4ob2JqZWN0KSwgcmVzdWx0KTsKICAgICAgICAgIGlmIChpc0RlZXApIHsKICAgICAgICAgICAgcmVzdWx0ID0gYmFzZUNsb25lKHJlc3VsdCwgQ0xPTkVfREVFUF9GTEFHIHwgQ0xPTkVfRkxBVF9GTEFHIHwgQ0xPTkVfU1lNQk9MU19GTEFHLCBjdXN0b21PbWl0Q2xvbmUpOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGxlbmd0aCA9IHBhdGhzLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChsZW5ndGgtLSkgewogICAgICAgICAgICBiYXNlVW5zZXQocmVzdWx0LCBwYXRoc1tsZW5ndGhdKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBvcHBvc2l0ZSBvZiBgXy5waWNrQnlgOyB0aGlzIG1ldGhvZCBjcmVhdGVzIGFuIG9iamVjdCBjb21wb3NlZCBvZgogICAgICAgICAqIHRoZSBvd24gYW5kIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIG9mIGBvYmplY3RgIHRoYXQKICAgICAgICAgKiBgcHJlZGljYXRlYCBkb2Vzbid0IHJldHVybiB0cnV0aHkgZm9yLiBUaGUgcHJlZGljYXRlIGlzIGludm9rZWQgd2l0aCB0d28KICAgICAgICAgKiBhcmd1bWVudHM6ICh2YWx1ZSwga2V5KS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIHByb3BlcnR5LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSwgJ2InOiAnMicsICdjJzogMyB9OwogICAgICAgICAqCiAgICAgICAgICogXy5vbWl0Qnkob2JqZWN0LCBfLmlzTnVtYmVyKTsKICAgICAgICAgKiAvLyA9PiB7ICdiJzogJzInIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBvbWl0Qnkob2JqZWN0LCBwcmVkaWNhdGUpIHsKICAgICAgICAgIHJldHVybiBwaWNrQnkob2JqZWN0LCBuZWdhdGUoZ2V0SXRlcmF0ZWUocHJlZGljYXRlKSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBvYmplY3QgY29tcG9zZWQgb2YgdGhlIHBpY2tlZCBgb2JqZWN0YCBwcm9wZXJ0aWVzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIHNvdXJjZSBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHsuLi4oc3RyaW5nfHN0cmluZ1tdKX0gW3BhdGhzXSBUaGUgcHJvcGVydHkgcGF0aHMgdG8gcGljay4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgb2JqZWN0LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IDEsICdiJzogJzInLCAnYyc6IDMgfTsKICAgICAgICAgKgogICAgICAgICAqIF8ucGljayhvYmplY3QsIFsnYScsICdjJ10pOwogICAgICAgICAqIC8vID0+IHsgJ2EnOiAxLCAnYyc6IDMgfQogICAgICAgICAqLwogICAgICAgIHZhciBwaWNrID0gZmxhdFJlc3QoZnVuY3Rpb24ob2JqZWN0LCBwYXRocykgewogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8ge30gOiBiYXNlUGljayhvYmplY3QsIHBhdGhzKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBvYmplY3QgY29tcG9zZWQgb2YgdGhlIGBvYmplY3RgIHByb3BlcnRpZXMgYHByZWRpY2F0ZWAgcmV0dXJucwogICAgICAgICAqIHRydXRoeSBmb3IuIFRoZSBwcmVkaWNhdGUgaXMgaW52b2tlZCB3aXRoIHR3byBhcmd1bWVudHM6ICh2YWx1ZSwga2V5KS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIHByb3BlcnR5LgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSwgJ2InOiAnMicsICdjJzogMyB9OwogICAgICAgICAqCiAgICAgICAgICogXy5waWNrQnkob2JqZWN0LCBfLmlzTnVtYmVyKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2MnOiAzIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBwaWNrQnkob2JqZWN0LCBwcmVkaWNhdGUpIHsKICAgICAgICAgIGlmIChvYmplY3QgPT0gbnVsbCkgewogICAgICAgICAgICByZXR1cm4ge307CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgcHJvcHMgPSBhcnJheU1hcChnZXRBbGxLZXlzSW4ob2JqZWN0KSwgZnVuY3Rpb24ocHJvcCkgewogICAgICAgICAgICByZXR1cm4gW3Byb3BdOwogICAgICAgICAgfSk7CiAgICAgICAgICBwcmVkaWNhdGUgPSBnZXRJdGVyYXRlZShwcmVkaWNhdGUpOwogICAgICAgICAgcmV0dXJuIGJhc2VQaWNrQnkob2JqZWN0LCBwcm9wcywgZnVuY3Rpb24odmFsdWUsIHBhdGgpIHsKICAgICAgICAgICAgcmV0dXJuIHByZWRpY2F0ZSh2YWx1ZSwgcGF0aFswXSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZ2V0YCBleGNlcHQgdGhhdCBpZiB0aGUgcmVzb2x2ZWQgdmFsdWUgaXMgYQogICAgICAgICAqIGZ1bmN0aW9uIGl0J3MgaW52b2tlZCB3aXRoIHRoZSBgdGhpc2AgYmluZGluZyBvZiBpdHMgcGFyZW50IG9iamVjdCBhbmQKICAgICAgICAgKiBpdHMgcmVzdWx0IGlzIHJldHVybmVkLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gcmVzb2x2ZS4KICAgICAgICAgKiBAcGFyYW0geyp9IFtkZWZhdWx0VmFsdWVdIFRoZSB2YWx1ZSByZXR1cm5lZCBmb3IgYHVuZGVmaW5lZGAgcmVzb2x2ZWQgdmFsdWVzLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXNvbHZlZCB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiBbeyAnYic6IHsgJ2MxJzogMywgJ2MyJzogXy5jb25zdGFudCg0KSB9IH1dIH07CiAgICAgICAgICoKICAgICAgICAgKiBfLnJlc3VsdChvYmplY3QsICdhWzBdLmIuYzEnKTsKICAgICAgICAgKiAvLyA9PiAzCiAgICAgICAgICoKICAgICAgICAgKiBfLnJlc3VsdChvYmplY3QsICdhWzBdLmIuYzInKTsKICAgICAgICAgKiAvLyA9PiA0CiAgICAgICAgICoKICAgICAgICAgKiBfLnJlc3VsdChvYmplY3QsICdhWzBdLmIuYzMnLCAnZGVmYXVsdCcpOwogICAgICAgICAqIC8vID0+ICdkZWZhdWx0JwogICAgICAgICAqCiAgICAgICAgICogXy5yZXN1bHQob2JqZWN0LCAnYVswXS5iLmMzJywgXy5jb25zdGFudCgnZGVmYXVsdCcpKTsKICAgICAgICAgKiAvLyA9PiAnZGVmYXVsdCcKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZXN1bHQob2JqZWN0LCBwYXRoLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgICAgIHBhdGggPSBjYXN0UGF0aChwYXRoLCBvYmplY3QpOwoKICAgICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICAgIGxlbmd0aCA9IHBhdGgubGVuZ3RoOwoKICAgICAgICAgIC8vIEVuc3VyZSB0aGUgbG9vcCBpcyBlbnRlcmVkIHdoZW4gcGF0aCBpcyBlbXB0eS4KICAgICAgICAgIGlmICghbGVuZ3RoKSB7CiAgICAgICAgICAgIGxlbmd0aCA9IDE7CiAgICAgICAgICAgIG9iamVjdCA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gb2JqZWN0ID09IG51bGwgPyB1bmRlZmluZWQkMSA6IG9iamVjdFt0b0tleShwYXRoW2luZGV4XSldOwogICAgICAgICAgICBpZiAodmFsdWUgPT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgICAgaW5kZXggPSBsZW5ndGg7CiAgICAgICAgICAgICAgdmFsdWUgPSBkZWZhdWx0VmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgb2JqZWN0ID0gaXNGdW5jdGlvbih2YWx1ZSkgPyB2YWx1ZS5jYWxsKG9iamVjdCkgOiB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBvYmplY3Q7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSB2YWx1ZSBhdCBgcGF0aGAgb2YgYG9iamVjdGAuIElmIGEgcG9ydGlvbiBvZiBgcGF0aGAgZG9lc24ndCBleGlzdCwKICAgICAgICAgKiBpdCdzIGNyZWF0ZWQuIEFycmF5cyBhcmUgY3JlYXRlZCBmb3IgbWlzc2luZyBpbmRleCBwcm9wZXJ0aWVzIHdoaWxlIG9iamVjdHMKICAgICAgICAgKiBhcmUgY3JlYXRlZCBmb3IgYWxsIG90aGVyIG1pc3NpbmcgcHJvcGVydGllcy4gVXNlIGBfLnNldFdpdGhgIHRvIGN1c3RvbWl6ZQogICAgICAgICAqIGBwYXRoYCBjcmVhdGlvbi4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBtdXRhdGVzIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIHNldC4KICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiBbeyAnYic6IHsgJ2MnOiAzIH0gfV0gfTsKICAgICAgICAgKgogICAgICAgICAqIF8uc2V0KG9iamVjdCwgJ2FbMF0uYi5jJywgNCk7CiAgICAgICAgICogY29uc29sZS5sb2cob2JqZWN0LmFbMF0uYi5jKTsKICAgICAgICAgKiAvLyA9PiA0CiAgICAgICAgICoKICAgICAgICAgKiBfLnNldChvYmplY3QsIFsneCcsICcwJywgJ3knLCAneiddLCA1KTsKICAgICAgICAgKiBjb25zb2xlLmxvZyhvYmplY3QueFswXS55LnopOwogICAgICAgICAqIC8vID0+IDUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzZXQob2JqZWN0LCBwYXRoLCB2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8gb2JqZWN0IDogYmFzZVNldChvYmplY3QsIHBhdGgsIHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uc2V0YCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBjdXN0b21pemVyYCB3aGljaCBpcwogICAgICAgICAqIGludm9rZWQgdG8gcHJvZHVjZSB0aGUgb2JqZWN0cyBvZiBgcGF0aGAuICBJZiBgY3VzdG9taXplcmAgcmV0dXJucyBgdW5kZWZpbmVkYAogICAgICAgICAqIHBhdGggY3JlYXRpb24gaXMgaGFuZGxlZCBieSB0aGUgbWV0aG9kIGluc3RlYWQuIFRoZSBgY3VzdG9taXplcmAgaXMgaW52b2tlZAogICAgICAgICAqIHdpdGggdGhyZWUgYXJndW1lbnRzOiAobnNWYWx1ZSwga2V5LCBuc09iamVjdCkuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBzZXQuCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0LgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGFzc2lnbmVkIHZhbHVlcy4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0ge307CiAgICAgICAgICoKICAgICAgICAgKiBfLnNldFdpdGgob2JqZWN0LCAnWzBdWzFdJywgJ2EnLCBPYmplY3QpOwogICAgICAgICAqIC8vID0+IHsgJzAnOiB7ICcxJzogJ2EnIH0gfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNldFdpdGgob2JqZWN0LCBwYXRoLCB2YWx1ZSwgY3VzdG9taXplcikgewogICAgICAgICAgY3VzdG9taXplciA9IHR5cGVvZiBjdXN0b21pemVyID09ICdmdW5jdGlvbicgPyBjdXN0b21pemVyIDogdW5kZWZpbmVkJDE7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ID09IG51bGwgPyBvYmplY3QgOiBiYXNlU2V0KG9iamVjdCwgcGF0aCwgdmFsdWUsIGN1c3RvbWl6ZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBvd24gZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQtdmFsdWUgcGFpcnMgZm9yIGBvYmplY3RgCiAgICAgICAgICogd2hpY2ggY2FuIGJlIGNvbnN1bWVkIGJ5IGBfLmZyb21QYWlyc2AuIElmIGBvYmplY3RgIGlzIGEgbWFwIG9yIHNldCwgaXRzCiAgICAgICAgICogZW50cmllcyBhcmUgcmV0dXJuZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAYWxpYXMgZW50cmllcwogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBrZXktdmFsdWUgcGFpcnMuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIEZvbygpIHsKICAgICAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgICAgICogICB0aGlzLmIgPSAyOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgICAgICoKICAgICAgICAgKiBfLnRvUGFpcnMobmV3IEZvbyk7CiAgICAgICAgICogLy8gPT4gW1snYScsIDFdLCBbJ2InLCAyXV0gKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkKICAgICAgICAgKi8KICAgICAgICB2YXIgdG9QYWlycyA9IGNyZWF0ZVRvUGFpcnMoa2V5cyk7CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2Ygb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQtdmFsdWUgcGFpcnMKICAgICAgICAgKiBmb3IgYG9iamVjdGAgd2hpY2ggY2FuIGJlIGNvbnN1bWVkIGJ5IGBfLmZyb21QYWlyc2AuIElmIGBvYmplY3RgIGlzIGEgbWFwCiAgICAgICAgICogb3Igc2V0LCBpdHMgZW50cmllcyBhcmUgcmV0dXJuZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAYWxpYXMgZW50cmllc0luCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGtleS12YWx1ZSBwYWlycy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICAgICAqICAgdGhpcy5hID0gMTsKICAgICAgICAgKiAgIHRoaXMuYiA9IDI7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogRm9vLnByb3RvdHlwZS5jID0gMzsKICAgICAgICAgKgogICAgICAgICAqIF8udG9QYWlyc0luKG5ldyBGb28pOwogICAgICAgICAqIC8vID0+IFtbJ2EnLCAxXSwgWydiJywgMl0sIFsnYycsIDNdXSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICAgICAqLwogICAgICAgIHZhciB0b1BhaXJzSW4gPSBjcmVhdGVUb1BhaXJzKGtleXNJbik7CgogICAgICAgIC8qKgogICAgICAgICAqIEFuIGFsdGVybmF0aXZlIHRvIGBfLnJlZHVjZWA7IHRoaXMgbWV0aG9kIHRyYW5zZm9ybXMgYG9iamVjdGAgdG8gYSBuZXcKICAgICAgICAgKiBgYWNjdW11bGF0b3JgIG9iamVjdCB3aGljaCBpcyB0aGUgcmVzdWx0IG9mIHJ1bm5pbmcgZWFjaCBvZiBpdHMgb3duCiAgICAgICAgICogZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgcHJvcGVydGllcyB0aHJ1IGBpdGVyYXRlZWAsIHdpdGggZWFjaCBpbnZvY2F0aW9uCiAgICAgICAgICogcG90ZW50aWFsbHkgbXV0YXRpbmcgdGhlIGBhY2N1bXVsYXRvcmAgb2JqZWN0LiBJZiBgYWNjdW11bGF0b3JgIGlzIG5vdAogICAgICAgICAqIHByb3ZpZGVkLCBhIG5ldyBvYmplY3Qgd2l0aCB0aGUgc2FtZSBgW1tQcm90b3R5cGVdXWAgd2lsbCBiZSB1c2VkLiBUaGUKICAgICAgICAgKiBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggZm91ciBhcmd1bWVudHM6IChhY2N1bXVsYXRvciwgdmFsdWUsIGtleSwgb2JqZWN0KS4KICAgICAgICAgKiBJdGVyYXRlZSBmdW5jdGlvbnMgbWF5IGV4aXQgaXRlcmF0aW9uIGVhcmx5IGJ5IGV4cGxpY2l0bHkgcmV0dXJuaW5nIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMS4zLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAgICAgKiBAcGFyYW0geyp9IFthY2N1bXVsYXRvcl0gVGhlIGN1c3RvbSBhY2N1bXVsYXRvciB2YWx1ZS4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgYWNjdW11bGF0ZWQgdmFsdWUuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udHJhbnNmb3JtKFsyLCAzLCA0XSwgZnVuY3Rpb24ocmVzdWx0LCBuKSB7CiAgICAgICAgICogICByZXN1bHQucHVzaChuICo9IG4pOwogICAgICAgICAqICAgcmV0dXJuIG4gJSAyID09IDA7CiAgICAgICAgICogfSwgW10pOwogICAgICAgICAqIC8vID0+IFs0LCA5XQogICAgICAgICAqCiAgICAgICAgICogXy50cmFuc2Zvcm0oeyAnYSc6IDEsICdiJzogMiwgJ2MnOiAxIH0sIGZ1bmN0aW9uKHJlc3VsdCwgdmFsdWUsIGtleSkgewogICAgICAgICAqICAgKHJlc3VsdFt2YWx1ZV0gfHwgKHJlc3VsdFt2YWx1ZV0gPSBbXSkpLnB1c2goa2V5KTsKICAgICAgICAgKiB9LCB7fSk7CiAgICAgICAgICogLy8gPT4geyAnMSc6IFsnYScsICdjJ10sICcyJzogWydiJ10gfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRyYW5zZm9ybShvYmplY3QsIGl0ZXJhdGVlLCBhY2N1bXVsYXRvcikgewogICAgICAgICAgdmFyIGlzQXJyID0gaXNBcnJheShvYmplY3QpLAogICAgICAgICAgICAgIGlzQXJyTGlrZSA9IGlzQXJyIHx8IGlzQnVmZmVyKG9iamVjdCkgfHwgaXNUeXBlZEFycmF5KG9iamVjdCk7CgogICAgICAgICAgaXRlcmF0ZWUgPSBnZXRJdGVyYXRlZShpdGVyYXRlZSwgNCk7CiAgICAgICAgICBpZiAoYWNjdW11bGF0b3IgPT0gbnVsbCkgewogICAgICAgICAgICB2YXIgQ3RvciA9IG9iamVjdCAmJiBvYmplY3QuY29uc3RydWN0b3I7CiAgICAgICAgICAgIGlmIChpc0Fyckxpa2UpIHsKICAgICAgICAgICAgICBhY2N1bXVsYXRvciA9IGlzQXJyID8gbmV3IEN0b3IgOiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmIChpc09iamVjdChvYmplY3QpKSB7CiAgICAgICAgICAgICAgYWNjdW11bGF0b3IgPSBpc0Z1bmN0aW9uKEN0b3IpID8gYmFzZUNyZWF0ZShnZXRQcm90b3R5cGUob2JqZWN0KSkgOiB7fTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICBhY2N1bXVsYXRvciA9IHt9OwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICAoaXNBcnJMaWtlID8gYXJyYXlFYWNoIDogYmFzZUZvck93bikob2JqZWN0LCBmdW5jdGlvbih2YWx1ZSwgaW5kZXgsIG9iamVjdCkgewogICAgICAgICAgICByZXR1cm4gaXRlcmF0ZWUoYWNjdW11bGF0b3IsIHZhbHVlLCBpbmRleCwgb2JqZWN0KTsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIGFjY3VtdWxhdG9yOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyB0aGUgcHJvcGVydHkgYXQgYHBhdGhgIG9mIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIG11dGF0ZXMgYG9iamVjdGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIG1vZGlmeS4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gdW5zZXQuCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBwcm9wZXJ0eSBpcyBkZWxldGVkLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogW3sgJ2InOiB7ICdjJzogNyB9IH1dIH07CiAgICAgICAgICogXy51bnNldChvYmplY3QsICdhWzBdLmIuYycpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKG9iamVjdCk7CiAgICAgICAgICogLy8gPT4geyAnYSc6IFt7ICdiJzoge30gfV0gfTsKICAgICAgICAgKgogICAgICAgICAqIF8udW5zZXQob2JqZWN0LCBbJ2EnLCAnMCcsICdiJywgJ2MnXSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogY29uc29sZS5sb2cob2JqZWN0KTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogW3sgJ2InOiB7fSB9XSB9OwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVuc2V0KG9iamVjdCwgcGF0aCkgewogICAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8gdHJ1ZSA6IGJhc2VVbnNldChvYmplY3QsIHBhdGgpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5zZXRgIGV4Y2VwdCB0aGF0IGFjY2VwdHMgYHVwZGF0ZXJgIHRvIHByb2R1Y2UgdGhlCiAgICAgICAgICogdmFsdWUgdG8gc2V0LiBVc2UgYF8udXBkYXRlV2l0aGAgdG8gY3VzdG9taXplIGBwYXRoYCBjcmVhdGlvbi4gVGhlIGB1cGRhdGVyYAogICAgICAgICAqIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ6ICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjYuMAogICAgICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBzZXQuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gdXBkYXRlciBUaGUgZnVuY3Rpb24gdG8gcHJvZHVjZSB0aGUgdXBkYXRlZCB2YWx1ZS4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0geyAnYSc6IFt7ICdiJzogeyAnYyc6IDMgfSB9XSB9OwogICAgICAgICAqCiAgICAgICAgICogXy51cGRhdGUob2JqZWN0LCAnYVswXS5iLmMnLCBmdW5jdGlvbihuKSB7IHJldHVybiBuICogbjsgfSk7CiAgICAgICAgICogY29uc29sZS5sb2cob2JqZWN0LmFbMF0uYi5jKTsKICAgICAgICAgKiAvLyA9PiA5CiAgICAgICAgICoKICAgICAgICAgKiBfLnVwZGF0ZShvYmplY3QsICd4WzBdLnkueicsIGZ1bmN0aW9uKG4pIHsgcmV0dXJuIG4gPyBuICsgMSA6IDA7IH0pOwogICAgICAgICAqIGNvbnNvbGUubG9nKG9iamVjdC54WzBdLnkueik7CiAgICAgICAgICogLy8gPT4gMAogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVwZGF0ZShvYmplY3QsIHBhdGgsIHVwZGF0ZXIpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IG9iamVjdCA6IGJhc2VVcGRhdGUob2JqZWN0LCBwYXRoLCBjYXN0RnVuY3Rpb24odXBkYXRlcikpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy51cGRhdGVgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYGN1c3RvbWl6ZXJgIHdoaWNoIGlzCiAgICAgICAgICogaW52b2tlZCB0byBwcm9kdWNlIHRoZSBvYmplY3RzIG9mIGBwYXRoYC4gIElmIGBjdXN0b21pemVyYCByZXR1cm5zIGB1bmRlZmluZWRgCiAgICAgICAgICogcGF0aCBjcmVhdGlvbiBpcyBoYW5kbGVkIGJ5IHRoZSBtZXRob2QgaW5zdGVhZC4gVGhlIGBjdXN0b21pemVyYCBpcyBpbnZva2VkCiAgICAgICAgICogd2l0aCB0aHJlZSBhcmd1bWVudHM6IChuc1ZhbHVlLCBrZXksIG5zT2JqZWN0KS4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBtdXRhdGVzIGBvYmplY3RgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuNi4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIHNldC4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSB1cGRhdGVyIFRoZSBmdW5jdGlvbiB0byBwcm9kdWNlIHRoZSB1cGRhdGVkIHZhbHVlLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGFzc2lnbmVkIHZhbHVlcy4KICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0ID0ge307CiAgICAgICAgICoKICAgICAgICAgKiBfLnVwZGF0ZVdpdGgob2JqZWN0LCAnWzBdWzFdJywgXy5jb25zdGFudCgnYScpLCBPYmplY3QpOwogICAgICAgICAqIC8vID0+IHsgJzAnOiB7ICcxJzogJ2EnIH0gfQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHVwZGF0ZVdpdGgob2JqZWN0LCBwYXRoLCB1cGRhdGVyLCBjdXN0b21pemVyKSB7CiAgICAgICAgICBjdXN0b21pemVyID0gdHlwZW9mIGN1c3RvbWl6ZXIgPT0gJ2Z1bmN0aW9uJyA/IGN1c3RvbWl6ZXIgOiB1bmRlZmluZWQkMTsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IG9iamVjdCA6IGJhc2VVcGRhdGUob2JqZWN0LCBwYXRoLCBjYXN0RnVuY3Rpb24odXBkYXRlciksIGN1c3RvbWl6ZXIpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnR5IHZhbHVlcyBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBOb24tb2JqZWN0IHZhbHVlcyBhcmUgY29lcmNlZCB0byBvYmplY3RzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IHZhbHVlcy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICAgICAqICAgdGhpcy5hID0gMTsKICAgICAgICAgKiAgIHRoaXMuYiA9IDI7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogRm9vLnByb3RvdHlwZS5jID0gMzsKICAgICAgICAgKgogICAgICAgICAqIF8udmFsdWVzKG5ldyBGb28pOwogICAgICAgICAqIC8vID0+IFsxLCAyXSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICAgICAqCiAgICAgICAgICogXy52YWx1ZXMoJ2hpJyk7CiAgICAgICAgICogLy8gPT4gWydoJywgJ2knXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHZhbHVlcyhvYmplY3QpIHsKICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IFtdIDogYmFzZVZhbHVlcyhvYmplY3QsIGtleXMob2JqZWN0KSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHRoZSBvd24gYW5kIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0eQogICAgICAgICAqIHZhbHVlcyBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBOb24tb2JqZWN0IHZhbHVlcyBhcmUgY29lcmNlZCB0byBvYmplY3RzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IHZhbHVlcy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICAgICAqICAgdGhpcy5hID0gMTsKICAgICAgICAgKiAgIHRoaXMuYiA9IDI7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogRm9vLnByb3RvdHlwZS5jID0gMzsKICAgICAgICAgKgogICAgICAgICAqIF8udmFsdWVzSW4obmV3IEZvbyk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDNdIChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdmFsdWVzSW4ob2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gb2JqZWN0ID09IG51bGwgPyBbXSA6IGJhc2VWYWx1ZXMob2JqZWN0LCBrZXlzSW4ob2JqZWN0KSk7CiAgICAgICAgfQoKICAgICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAgIC8qKgogICAgICAgICAqIENsYW1wcyBgbnVtYmVyYCB3aXRoaW4gdGhlIGluY2x1c2l2ZSBgbG93ZXJgIGFuZCBgdXBwZXJgIGJvdW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBOdW1iZXIKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbnVtYmVyIFRoZSBudW1iZXIgdG8gY2xhbXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtsb3dlcl0gVGhlIGxvd2VyIGJvdW5kLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSB1cHBlciBUaGUgdXBwZXIgYm91bmQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY2xhbXBlZCBudW1iZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uY2xhbXAoLTEwLCAtNSwgNSk7CiAgICAgICAgICogLy8gPT4gLTUKICAgICAgICAgKgogICAgICAgICAqIF8uY2xhbXAoMTAsIC01LCA1KTsKICAgICAgICAgKiAvLyA9PiA1CiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY2xhbXAobnVtYmVyLCBsb3dlciwgdXBwZXIpIHsKICAgICAgICAgIGlmICh1cHBlciA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgdXBwZXIgPSBsb3dlcjsKICAgICAgICAgICAgbG93ZXIgPSB1bmRlZmluZWQkMTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh1cHBlciAhPT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgdXBwZXIgPSB0b051bWJlcih1cHBlcik7CiAgICAgICAgICAgIHVwcGVyID0gdXBwZXIgPT09IHVwcGVyID8gdXBwZXIgOiAwOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGxvd2VyICE9PSB1bmRlZmluZWQkMSkgewogICAgICAgICAgICBsb3dlciA9IHRvTnVtYmVyKGxvd2VyKTsKICAgICAgICAgICAgbG93ZXIgPSBsb3dlciA9PT0gbG93ZXIgPyBsb3dlciA6IDA7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gYmFzZUNsYW1wKHRvTnVtYmVyKG51bWJlciksIGxvd2VyLCB1cHBlcik7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYG5gIGlzIGJldHdlZW4gYHN0YXJ0YCBhbmQgdXAgdG8sIGJ1dCBub3QgaW5jbHVkaW5nLCBgZW5kYC4gSWYKICAgICAgICAgKiBgZW5kYCBpcyBub3Qgc3BlY2lmaWVkLCBpdCdzIHNldCB0byBgc3RhcnRgIHdpdGggYHN0YXJ0YCB0aGVuIHNldCB0byBgMGAuCiAgICAgICAgICogSWYgYHN0YXJ0YCBpcyBncmVhdGVyIHRoYW4gYGVuZGAgdGhlIHBhcmFtcyBhcmUgc3dhcHBlZCB0byBzdXBwb3J0CiAgICAgICAgICogbmVnYXRpdmUgcmFuZ2VzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMy4wCiAgICAgICAgICogQGNhdGVnb3J5IE51bWJlcgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBudW1iZXIgVGhlIG51bWJlciB0byBjaGVjay4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PTBdIFRoZSBzdGFydCBvZiB0aGUgcmFuZ2UuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGVuZCBUaGUgZW5kIG9mIHRoZSByYW5nZS4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYG51bWJlcmAgaXMgaW4gdGhlIHJhbmdlLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICogQHNlZSBfLnJhbmdlLCBfLnJhbmdlUmlnaHQKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5pblJhbmdlKDMsIDIsIDQpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uaW5SYW5nZSg0LCA4KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBfLmluUmFuZ2UoNCwgMik7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaW5SYW5nZSgyLCAyKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogXy5pblJhbmdlKDEuMiwgMik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5pblJhbmdlKDUuMiwgNCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uaW5SYW5nZSgtMywgLTIsIC02KTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaW5SYW5nZShudW1iZXIsIHN0YXJ0LCBlbmQpIHsKICAgICAgICAgIHN0YXJ0ID0gdG9GaW5pdGUoc3RhcnQpOwogICAgICAgICAgaWYgKGVuZCA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgZW5kID0gc3RhcnQ7CiAgICAgICAgICAgIHN0YXJ0ID0gMDsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGVuZCA9IHRvRmluaXRlKGVuZCk7CiAgICAgICAgICB9CiAgICAgICAgICBudW1iZXIgPSB0b051bWJlcihudW1iZXIpOwogICAgICAgICAgcmV0dXJuIGJhc2VJblJhbmdlKG51bWJlciwgc3RhcnQsIGVuZCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQcm9kdWNlcyBhIHJhbmRvbSBudW1iZXIgYmV0d2VlbiB0aGUgaW5jbHVzaXZlIGBsb3dlcmAgYW5kIGB1cHBlcmAgYm91bmRzLgogICAgICAgICAqIElmIG9ubHkgb25lIGFyZ3VtZW50IGlzIHByb3ZpZGVkIGEgbnVtYmVyIGJldHdlZW4gYDBgIGFuZCB0aGUgZ2l2ZW4gbnVtYmVyCiAgICAgICAgICogaXMgcmV0dXJuZWQuIElmIGBmbG9hdGluZ2AgaXMgYHRydWVgLCBvciBlaXRoZXIgYGxvd2VyYCBvciBgdXBwZXJgIGFyZQogICAgICAgICAqIGZsb2F0cywgYSBmbG9hdGluZy1wb2ludCBudW1iZXIgaXMgcmV0dXJuZWQgaW5zdGVhZCBvZiBhbiBpbnRlZ2VyLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIEphdmFTY3JpcHQgZm9sbG93cyB0aGUgSUVFRS03NTQgc3RhbmRhcmQgZm9yIHJlc29sdmluZwogICAgICAgICAqIGZsb2F0aW5nLXBvaW50IHZhbHVlcyB3aGljaCBjYW4gcHJvZHVjZSB1bmV4cGVjdGVkIHJlc3VsdHMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMC43LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTnVtYmVyCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtsb3dlcj0wXSBUaGUgbG93ZXIgYm91bmQuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFt1cHBlcj0xXSBUaGUgdXBwZXIgYm91bmQuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbZmxvYXRpbmddIFNwZWNpZnkgcmV0dXJuaW5nIGEgZmxvYXRpbmctcG9pbnQgbnVtYmVyLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHJhbmRvbSBudW1iZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucmFuZG9tKDAsIDUpOwogICAgICAgICAqIC8vID0+IGFuIGludGVnZXIgYmV0d2VlbiAwIGFuZCA1CiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmRvbSg1KTsKICAgICAgICAgKiAvLyA9PiBhbHNvIGFuIGludGVnZXIgYmV0d2VlbiAwIGFuZCA1CiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmRvbSg1LCB0cnVlKTsKICAgICAgICAgKiAvLyA9PiBhIGZsb2F0aW5nLXBvaW50IG51bWJlciBiZXR3ZWVuIDAgYW5kIDUKICAgICAgICAgKgogICAgICAgICAqIF8ucmFuZG9tKDEuMiwgNS4yKTsKICAgICAgICAgKiAvLyA9PiBhIGZsb2F0aW5nLXBvaW50IG51bWJlciBiZXR3ZWVuIDEuMiBhbmQgNS4yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gcmFuZG9tKGxvd2VyLCB1cHBlciwgZmxvYXRpbmcpIHsKICAgICAgICAgIGlmIChmbG9hdGluZyAmJiB0eXBlb2YgZmxvYXRpbmcgIT0gJ2Jvb2xlYW4nICYmIGlzSXRlcmF0ZWVDYWxsKGxvd2VyLCB1cHBlciwgZmxvYXRpbmcpKSB7CiAgICAgICAgICAgIHVwcGVyID0gZmxvYXRpbmcgPSB1bmRlZmluZWQkMTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChmbG9hdGluZyA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgaWYgKHR5cGVvZiB1cHBlciA9PSAnYm9vbGVhbicpIHsKICAgICAgICAgICAgICBmbG9hdGluZyA9IHVwcGVyOwogICAgICAgICAgICAgIHVwcGVyID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAodHlwZW9mIGxvd2VyID09ICdib29sZWFuJykgewogICAgICAgICAgICAgIGZsb2F0aW5nID0gbG93ZXI7CiAgICAgICAgICAgICAgbG93ZXIgPSB1bmRlZmluZWQkMTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGxvd2VyID09PSB1bmRlZmluZWQkMSAmJiB1cHBlciA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgbG93ZXIgPSAwOwogICAgICAgICAgICB1cHBlciA9IDE7CiAgICAgICAgICB9CiAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgbG93ZXIgPSB0b0Zpbml0ZShsb3dlcik7CiAgICAgICAgICAgIGlmICh1cHBlciA9PT0gdW5kZWZpbmVkJDEpIHsKICAgICAgICAgICAgICB1cHBlciA9IGxvd2VyOwogICAgICAgICAgICAgIGxvd2VyID0gMDsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICB1cHBlciA9IHRvRmluaXRlKHVwcGVyKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGxvd2VyID4gdXBwZXIpIHsKICAgICAgICAgICAgdmFyIHRlbXAgPSBsb3dlcjsKICAgICAgICAgICAgbG93ZXIgPSB1cHBlcjsKICAgICAgICAgICAgdXBwZXIgPSB0ZW1wOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGZsb2F0aW5nIHx8IGxvd2VyICUgMSB8fCB1cHBlciAlIDEpIHsKICAgICAgICAgICAgdmFyIHJhbmQgPSBuYXRpdmVSYW5kb20oKTsKICAgICAgICAgICAgcmV0dXJuIG5hdGl2ZU1pbihsb3dlciArIChyYW5kICogKHVwcGVyIC0gbG93ZXIgKyBmcmVlUGFyc2VGbG9hdCgnMWUtJyArICgocmFuZCArICcnKS5sZW5ndGggLSAxKSkpKSwgdXBwZXIpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGJhc2VSYW5kb20obG93ZXIsIHVwcGVyKTsKICAgICAgICB9CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHN0cmluZ2AgdG8gW2NhbWVsIGNhc2VdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0NhbWVsQ2FzZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBjYW1lbCBjYXNlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uY2FtZWxDYXNlKCdGb28gQmFyJyk7CiAgICAgICAgICogLy8gPT4gJ2Zvb0JhcicKICAgICAgICAgKgogICAgICAgICAqIF8uY2FtZWxDYXNlKCctLWZvby1iYXItLScpOwogICAgICAgICAqIC8vID0+ICdmb29CYXInCiAgICAgICAgICoKICAgICAgICAgKiBfLmNhbWVsQ2FzZSgnX19GT09fQkFSX18nKTsKICAgICAgICAgKiAvLyA9PiAnZm9vQmFyJwogICAgICAgICAqLwogICAgICAgIHZhciBjYW1lbENhc2UgPSBjcmVhdGVDb21wb3VuZGVyKGZ1bmN0aW9uKHJlc3VsdCwgd29yZCwgaW5kZXgpIHsKICAgICAgICAgIHdvcmQgPSB3b3JkLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0ICsgKGluZGV4ID8gY2FwaXRhbGl6ZSh3b3JkKSA6IHdvcmQpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyB0aGUgZmlyc3QgY2hhcmFjdGVyIG9mIGBzdHJpbmdgIHRvIHVwcGVyIGNhc2UgYW5kIHRoZSByZW1haW5pbmcKICAgICAgICAgKiB0byBsb3dlciBjYXNlLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIGNhcGl0YWxpemUuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgY2FwaXRhbGl6ZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmNhcGl0YWxpemUoJ0ZSRUQnKTsKICAgICAgICAgKiAvLyA9PiAnRnJlZCcKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjYXBpdGFsaXplKHN0cmluZykgewogICAgICAgICAgcmV0dXJuIHVwcGVyRmlyc3QodG9TdHJpbmcoc3RyaW5nKS50b0xvd2VyQ2FzZSgpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIERlYnVycnMgYHN0cmluZ2AgYnkgY29udmVydGluZwogICAgICAgICAqIFtMYXRpbi0xIFN1cHBsZW1lbnRdKGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0xhdGluLTFfU3VwcGxlbWVudF8oVW5pY29kZV9ibG9jaykjQ2hhcmFjdGVyX3RhYmxlKQogICAgICAgICAqIGFuZCBbTGF0aW4gRXh0ZW5kZWQtQV0oaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvTGF0aW5fRXh0ZW5kZWQtQSkKICAgICAgICAgKiBsZXR0ZXJzIHRvIGJhc2ljIExhdGluIGxldHRlcnMgYW5kIHJlbW92aW5nCiAgICAgICAgICogW2NvbWJpbmluZyBkaWFjcml0aWNhbCBtYXJrc10oaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvQ29tYmluaW5nX0RpYWNyaXRpY2FsX01hcmtzKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBkZWJ1cnIuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgZGVidXJyZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmRlYnVycignZMOpasOgIHZ1Jyk7CiAgICAgICAgICogLy8gPT4gJ2RlamEgdnUnCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZGVidXJyKHN0cmluZykgewogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIHJldHVybiBzdHJpbmcgJiYgc3RyaW5nLnJlcGxhY2UocmVMYXRpbiwgZGVidXJyTGV0dGVyKS5yZXBsYWNlKHJlQ29tYm9NYXJrLCAnJyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHN0cmluZ2AgZW5kcyB3aXRoIHRoZSBnaXZlbiB0YXJnZXQgc3RyaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIGluc3BlY3QuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFt0YXJnZXRdIFRoZSBzdHJpbmcgdG8gc2VhcmNoIGZvci4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3Bvc2l0aW9uPXN0cmluZy5sZW5ndGhdIFRoZSBwb3NpdGlvbiB0byBzZWFyY2ggdXAgdG8uCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBzdHJpbmdgIGVuZHMgd2l0aCBgdGFyZ2V0YCwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmVuZHNXaXRoKCdhYmMnLCAnYycpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIF8uZW5kc1dpdGgoJ2FiYycsICdiJyk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIF8uZW5kc1dpdGgoJ2FiYycsICdiJywgMik7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGVuZHNXaXRoKHN0cmluZywgdGFyZ2V0LCBwb3NpdGlvbikgewogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIHRhcmdldCA9IGJhc2VUb1N0cmluZyh0YXJnZXQpOwoKICAgICAgICAgIHZhciBsZW5ndGggPSBzdHJpbmcubGVuZ3RoOwogICAgICAgICAgcG9zaXRpb24gPSBwb3NpdGlvbiA9PT0gdW5kZWZpbmVkJDEKICAgICAgICAgICAgPyBsZW5ndGgKICAgICAgICAgICAgOiBiYXNlQ2xhbXAodG9JbnRlZ2VyKHBvc2l0aW9uKSwgMCwgbGVuZ3RoKTsKCiAgICAgICAgICB2YXIgZW5kID0gcG9zaXRpb247CiAgICAgICAgICBwb3NpdGlvbiAtPSB0YXJnZXQubGVuZ3RoOwogICAgICAgICAgcmV0dXJuIHBvc2l0aW9uID49IDAgJiYgc3RyaW5nLnNsaWNlKHBvc2l0aW9uLCBlbmQpID09IHRhcmdldDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIHRoZSBjaGFyYWN0ZXJzICImIiwgIjwiLCAiPiIsICciJywgYW5kICInIiBpbiBgc3RyaW5nYCB0byB0aGVpcgogICAgICAgICAqIGNvcnJlc3BvbmRpbmcgSFRNTCBlbnRpdGllcy4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBObyBvdGhlciBjaGFyYWN0ZXJzIGFyZSBlc2NhcGVkLiBUbyBlc2NhcGUgYWRkaXRpb25hbAogICAgICAgICAqIGNoYXJhY3RlcnMgdXNlIGEgdGhpcmQtcGFydHkgbGlicmFyeSBsaWtlIFtfaGVfXShodHRwczovL210aHMuYmUvaGUpLgogICAgICAgICAqCiAgICAgICAgICogVGhvdWdoIHRoZSAiPiIgY2hhcmFjdGVyIGlzIGVzY2FwZWQgZm9yIHN5bW1ldHJ5LCBjaGFyYWN0ZXJzIGxpa2UKICAgICAgICAgKiAiPiIgYW5kICIvIiBkb24ndCBuZWVkIGVzY2FwaW5nIGluIEhUTUwgYW5kIGhhdmUgbm8gc3BlY2lhbCBtZWFuaW5nCiAgICAgICAgICogdW5sZXNzIHRoZXkncmUgcGFydCBvZiBhIHRhZyBvciB1bnF1b3RlZCBhdHRyaWJ1dGUgdmFsdWUuIFNlZQogICAgICAgICAqIFtNYXRoaWFzIEJ5bmVucydzIGFydGljbGVdKGh0dHBzOi8vbWF0aGlhc2J5bmVucy5iZS9ub3Rlcy9hbWJpZ3VvdXMtYW1wZXJzYW5kcykKICAgICAgICAgKiAodW5kZXIgInNlbWktcmVsYXRlZCBmdW4gZmFjdCIpIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICoKICAgICAgICAgKiBXaGVuIHdvcmtpbmcgd2l0aCBIVE1MIHlvdSBzaG91bGQgYWx3YXlzCiAgICAgICAgICogW3F1b3RlIGF0dHJpYnV0ZSB2YWx1ZXNdKGh0dHA6Ly93b25rby5jb20vcG9zdC9odG1sLWVzY2FwaW5nKSB0byByZWR1Y2UKICAgICAgICAgKiBYU1MgdmVjdG9ycy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBlc2NhcGUuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgZXNjYXBlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZXNjYXBlKCdmcmVkLCBiYXJuZXksICYgcGViYmxlcycpOwogICAgICAgICAqIC8vID0+ICdmcmVkLCBiYXJuZXksICZhbXA7IHBlYmJsZXMnCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZXNjYXBlKHN0cmluZykgewogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIHJldHVybiAoc3RyaW5nICYmIHJlSGFzVW5lc2NhcGVkSHRtbC50ZXN0KHN0cmluZykpCiAgICAgICAgICAgID8gc3RyaW5nLnJlcGxhY2UocmVVbmVzY2FwZWRIdG1sLCBlc2NhcGVIdG1sQ2hhcikKICAgICAgICAgICAgOiBzdHJpbmc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBFc2NhcGVzIHRoZSBgUmVnRXhwYCBzcGVjaWFsIGNoYXJhY3RlcnMgIl4iLCAiJCIsICJcIiwgIi4iLCAiKiIsICIrIiwKICAgICAgICAgKiAiPyIsICIoIiwgIikiLCAiWyIsICJdIiwgInsiLCAifSIsIGFuZCAifCIgaW4gYHN0cmluZ2AuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gZXNjYXBlLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGVzY2FwZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLmVzY2FwZVJlZ0V4cCgnW2xvZGFzaF0oaHR0cHM6Ly9sb2Rhc2guY29tLyknKTsKICAgICAgICAgKiAvLyA9PiAnXFtsb2Rhc2hcXVwoaHR0cHM6Ly9sb2Rhc2hcLmNvbS9cKScKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBlc2NhcGVSZWdFeHAoc3RyaW5nKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgcmV0dXJuIChzdHJpbmcgJiYgcmVIYXNSZWdFeHBDaGFyLnRlc3Qoc3RyaW5nKSkKICAgICAgICAgICAgPyBzdHJpbmcucmVwbGFjZShyZVJlZ0V4cENoYXIsICdcXCQmJykKICAgICAgICAgICAgOiBzdHJpbmc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgc3RyaW5nYCB0bwogICAgICAgICAqIFtrZWJhYiBjYXNlXShodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9MZXR0ZXJfY2FzZSNTcGVjaWFsX2Nhc2Vfc3R5bGVzKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGtlYmFiIGNhc2VkIHN0cmluZy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5rZWJhYkNhc2UoJ0ZvbyBCYXInKTsKICAgICAgICAgKiAvLyA9PiAnZm9vLWJhcicKICAgICAgICAgKgogICAgICAgICAqIF8ua2ViYWJDYXNlKCdmb29CYXInKTsKICAgICAgICAgKiAvLyA9PiAnZm9vLWJhcicKICAgICAgICAgKgogICAgICAgICAqIF8ua2ViYWJDYXNlKCdfX0ZPT19CQVJfXycpOwogICAgICAgICAqIC8vID0+ICdmb28tYmFyJwogICAgICAgICAqLwogICAgICAgIHZhciBrZWJhYkNhc2UgPSBjcmVhdGVDb21wb3VuZGVyKGZ1bmN0aW9uKHJlc3VsdCwgd29yZCwgaW5kZXgpIHsKICAgICAgICAgIHJldHVybiByZXN1bHQgKyAoaW5kZXggPyAnLScgOiAnJykgKyB3b3JkLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGBzdHJpbmdgLCBhcyBzcGFjZSBzZXBhcmF0ZWQgd29yZHMsIHRvIGxvd2VyIGNhc2UuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBsb3dlciBjYXNlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ubG93ZXJDYXNlKCctLUZvby1CYXItLScpOwogICAgICAgICAqIC8vID0+ICdmb28gYmFyJwogICAgICAgICAqCiAgICAgICAgICogXy5sb3dlckNhc2UoJ2Zvb0JhcicpOwogICAgICAgICAqIC8vID0+ICdmb28gYmFyJwogICAgICAgICAqCiAgICAgICAgICogXy5sb3dlckNhc2UoJ19fRk9PX0JBUl9fJyk7CiAgICAgICAgICogLy8gPT4gJ2ZvbyBiYXInCiAgICAgICAgICovCiAgICAgICAgdmFyIGxvd2VyQ2FzZSA9IGNyZWF0ZUNvbXBvdW5kZXIoZnVuY3Rpb24ocmVzdWx0LCB3b3JkLCBpbmRleCkgewogICAgICAgICAgcmV0dXJuIHJlc3VsdCArIChpbmRleCA/ICcgJyA6ICcnKSArIHdvcmQudG9Mb3dlckNhc2UoKTsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgdGhlIGZpcnN0IGNoYXJhY3RlciBvZiBgc3RyaW5nYCB0byBsb3dlciBjYXNlLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgY29udmVydGVkIHN0cmluZy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5sb3dlckZpcnN0KCdGcmVkJyk7CiAgICAgICAgICogLy8gPT4gJ2ZyZWQnCiAgICAgICAgICoKICAgICAgICAgKiBfLmxvd2VyRmlyc3QoJ0ZSRUQnKTsKICAgICAgICAgKiAvLyA9PiAnZlJFRCcKICAgICAgICAgKi8KICAgICAgICB2YXIgbG93ZXJGaXJzdCA9IGNyZWF0ZUNhc2VGaXJzdCgndG9Mb3dlckNhc2UnKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogUGFkcyBgc3RyaW5nYCBvbiB0aGUgbGVmdCBhbmQgcmlnaHQgc2lkZXMgaWYgaXQncyBzaG9ydGVyIHRoYW4gYGxlbmd0aGAuCiAgICAgICAgICogUGFkZGluZyBjaGFyYWN0ZXJzIGFyZSB0cnVuY2F0ZWQgaWYgdGhleSBjYW4ndCBiZSBldmVubHkgZGl2aWRlZCBieSBgbGVuZ3RoYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBwYWQuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtsZW5ndGg9MF0gVGhlIHBhZGRpbmcgbGVuZ3RoLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbY2hhcnM9JyAnXSBUaGUgc3RyaW5nIHVzZWQgYXMgcGFkZGluZy4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBwYWRkZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnBhZCgnYWJjJywgOCk7CiAgICAgICAgICogLy8gPT4gJyAgYWJjICAgJwogICAgICAgICAqCiAgICAgICAgICogXy5wYWQoJ2FiYycsIDgsICdfLScpOwogICAgICAgICAqIC8vID0+ICdfLWFiY18tXycKICAgICAgICAgKgogICAgICAgICAqIF8ucGFkKCdhYmMnLCAzKTsKICAgICAgICAgKiAvLyA9PiAnYWJjJwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHBhZChzdHJpbmcsIGxlbmd0aCwgY2hhcnMpIHsKICAgICAgICAgIHN0cmluZyA9IHRvU3RyaW5nKHN0cmluZyk7CiAgICAgICAgICBsZW5ndGggPSB0b0ludGVnZXIobGVuZ3RoKTsKCiAgICAgICAgICB2YXIgc3RyTGVuZ3RoID0gbGVuZ3RoID8gc3RyaW5nU2l6ZShzdHJpbmcpIDogMDsKICAgICAgICAgIGlmICghbGVuZ3RoIHx8IHN0ckxlbmd0aCA+PSBsZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIHN0cmluZzsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBtaWQgPSAobGVuZ3RoIC0gc3RyTGVuZ3RoKSAvIDI7CiAgICAgICAgICByZXR1cm4gKAogICAgICAgICAgICBjcmVhdGVQYWRkaW5nKG5hdGl2ZUZsb29yKG1pZCksIGNoYXJzKSArCiAgICAgICAgICAgIHN0cmluZyArCiAgICAgICAgICAgIGNyZWF0ZVBhZGRpbmcobmF0aXZlQ2VpbChtaWQpLCBjaGFycykKICAgICAgICAgICk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBQYWRzIGBzdHJpbmdgIG9uIHRoZSByaWdodCBzaWRlIGlmIGl0J3Mgc2hvcnRlciB0aGFuIGBsZW5ndGhgLiBQYWRkaW5nCiAgICAgICAgICogY2hhcmFjdGVycyBhcmUgdHJ1bmNhdGVkIGlmIHRoZXkgZXhjZWVkIGBsZW5ndGhgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHBhZC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2xlbmd0aD0wXSBUaGUgcGFkZGluZyBsZW5ndGguCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz0nICddIFRoZSBzdHJpbmcgdXNlZCBhcyBwYWRkaW5nLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHBhZGRlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucGFkRW5kKCdhYmMnLCA2KTsKICAgICAgICAgKiAvLyA9PiAnYWJjICAgJwogICAgICAgICAqCiAgICAgICAgICogXy5wYWRFbmQoJ2FiYycsIDYsICdfLScpOwogICAgICAgICAqIC8vID0+ICdhYmNfLV8nCiAgICAgICAgICoKICAgICAgICAgKiBfLnBhZEVuZCgnYWJjJywgMyk7CiAgICAgICAgICogLy8gPT4gJ2FiYycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBwYWRFbmQoc3RyaW5nLCBsZW5ndGgsIGNoYXJzKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgbGVuZ3RoID0gdG9JbnRlZ2VyKGxlbmd0aCk7CgogICAgICAgICAgdmFyIHN0ckxlbmd0aCA9IGxlbmd0aCA/IHN0cmluZ1NpemUoc3RyaW5nKSA6IDA7CiAgICAgICAgICByZXR1cm4gKGxlbmd0aCAmJiBzdHJMZW5ndGggPCBsZW5ndGgpCiAgICAgICAgICAgID8gKHN0cmluZyArIGNyZWF0ZVBhZGRpbmcobGVuZ3RoIC0gc3RyTGVuZ3RoLCBjaGFycykpCiAgICAgICAgICAgIDogc3RyaW5nOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUGFkcyBgc3RyaW5nYCBvbiB0aGUgbGVmdCBzaWRlIGlmIGl0J3Mgc2hvcnRlciB0aGFuIGBsZW5ndGhgLiBQYWRkaW5nCiAgICAgICAgICogY2hhcmFjdGVycyBhcmUgdHJ1bmNhdGVkIGlmIHRoZXkgZXhjZWVkIGBsZW5ndGhgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHBhZC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2xlbmd0aD0wXSBUaGUgcGFkZGluZyBsZW5ndGguCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz0nICddIFRoZSBzdHJpbmcgdXNlZCBhcyBwYWRkaW5nLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHBhZGRlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucGFkU3RhcnQoJ2FiYycsIDYpOwogICAgICAgICAqIC8vID0+ICcgICBhYmMnCiAgICAgICAgICoKICAgICAgICAgKiBfLnBhZFN0YXJ0KCdhYmMnLCA2LCAnXy0nKTsKICAgICAgICAgKiAvLyA9PiAnXy1fYWJjJwogICAgICAgICAqCiAgICAgICAgICogXy5wYWRTdGFydCgnYWJjJywgMyk7CiAgICAgICAgICogLy8gPT4gJ2FiYycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBwYWRTdGFydChzdHJpbmcsIGxlbmd0aCwgY2hhcnMpIHsKICAgICAgICAgIHN0cmluZyA9IHRvU3RyaW5nKHN0cmluZyk7CiAgICAgICAgICBsZW5ndGggPSB0b0ludGVnZXIobGVuZ3RoKTsKCiAgICAgICAgICB2YXIgc3RyTGVuZ3RoID0gbGVuZ3RoID8gc3RyaW5nU2l6ZShzdHJpbmcpIDogMDsKICAgICAgICAgIHJldHVybiAobGVuZ3RoICYmIHN0ckxlbmd0aCA8IGxlbmd0aCkKICAgICAgICAgICAgPyAoY3JlYXRlUGFkZGluZyhsZW5ndGggLSBzdHJMZW5ndGgsIGNoYXJzKSArIHN0cmluZykKICAgICAgICAgICAgOiBzdHJpbmc7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgc3RyaW5nYCB0byBhbiBpbnRlZ2VyIG9mIHRoZSBzcGVjaWZpZWQgcmFkaXguIElmIGByYWRpeGAgaXMKICAgICAgICAgKiBgdW5kZWZpbmVkYCBvciBgMGAsIGEgYHJhZGl4YCBvZiBgMTBgIGlzIHVzZWQgdW5sZXNzIGB2YWx1ZWAgaXMgYQogICAgICAgICAqIGhleGFkZWNpbWFsLCBpbiB3aGljaCBjYXNlIGEgYHJhZGl4YCBvZiBgMTZgIGlzIHVzZWQuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgYWxpZ25zIHdpdGggdGhlCiAgICAgICAgICogW0VTNSBpbXBsZW1lbnRhdGlvbl0oaHR0cHM6Ly9lczUuZ2l0aHViLmlvLyN4MTUuMS4yLjIpIG9mIGBwYXJzZUludGAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMS4xLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtyYWRpeD0xMF0gVGhlIHJhZGl4IHRvIGludGVycHJldCBgdmFsdWVgIGJ5LgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY29udmVydGVkIGludGVnZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucGFyc2VJbnQoJzA4Jyk7CiAgICAgICAgICogLy8gPT4gOAogICAgICAgICAqCiAgICAgICAgICogXy5tYXAoWyc2JywgJzA4JywgJzEwJ10sIF8ucGFyc2VJbnQpOwogICAgICAgICAqIC8vID0+IFs2LCA4LCAxMF0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBwYXJzZUludChzdHJpbmcsIHJhZGl4LCBndWFyZCkgewogICAgICAgICAgaWYgKGd1YXJkIHx8IHJhZGl4ID09IG51bGwpIHsKICAgICAgICAgICAgcmFkaXggPSAwOwogICAgICAgICAgfSBlbHNlIGlmIChyYWRpeCkgewogICAgICAgICAgICByYWRpeCA9ICtyYWRpeDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBuYXRpdmVQYXJzZUludCh0b1N0cmluZyhzdHJpbmcpLnJlcGxhY2UocmVUcmltU3RhcnQsICcnKSwgcmFkaXggfHwgMCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXBlYXRzIHRoZSBnaXZlbiBzdHJpbmcgYG5gIHRpbWVzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHJlcGVhdC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW249MV0gVGhlIG51bWJlciBvZiB0aW1lcyB0byByZXBlYXQgdGhlIHN0cmluZy4KICAgICAgICAgKiBAcGFyYW0tIHtPYmplY3R9IFtndWFyZF0gRW5hYmxlcyB1c2UgYXMgYW4gaXRlcmF0ZWUgZm9yIG1ldGhvZHMgbGlrZSBgXy5tYXBgLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHJlcGVhdGVkIHN0cmluZy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5yZXBlYXQoJyonLCAzKTsKICAgICAgICAgKiAvLyA9PiAnKioqJwogICAgICAgICAqCiAgICAgICAgICogXy5yZXBlYXQoJ2FiYycsIDIpOwogICAgICAgICAqIC8vID0+ICdhYmNhYmMnCiAgICAgICAgICoKICAgICAgICAgKiBfLnJlcGVhdCgnYWJjJywgMCk7CiAgICAgICAgICogLy8gPT4gJycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiByZXBlYXQoc3RyaW5nLCBuLCBndWFyZCkgewogICAgICAgICAgaWYgKChndWFyZCA/IGlzSXRlcmF0ZWVDYWxsKHN0cmluZywgbiwgZ3VhcmQpIDogbiA9PT0gdW5kZWZpbmVkJDEpKSB7CiAgICAgICAgICAgIG4gPSAxOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbiA9IHRvSW50ZWdlcihuKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBiYXNlUmVwZWF0KHRvU3RyaW5nKHN0cmluZyksIG4pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVwbGFjZXMgbWF0Y2hlcyBmb3IgYHBhdHRlcm5gIGluIGBzdHJpbmdgIHdpdGggYHJlcGxhY2VtZW50YC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbgogICAgICAgICAqIFtgU3RyaW5nI3JlcGxhY2VgXShodHRwczovL21kbi5pby9TdHJpbmcvcmVwbGFjZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gbW9kaWZ5LgogICAgICAgICAqIEBwYXJhbSB7UmVnRXhwfHN0cmluZ30gcGF0dGVybiBUaGUgcGF0dGVybiB0byByZXBsYWNlLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb258c3RyaW5nfSByZXBsYWNlbWVudCBUaGUgbWF0Y2ggcmVwbGFjZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgbW9kaWZpZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnJlcGxhY2UoJ0hpIEZyZWQnLCAnRnJlZCcsICdCYXJuZXknKTsKICAgICAgICAgKiAvLyA9PiAnSGkgQmFybmV5JwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHJlcGxhY2UoKSB7CiAgICAgICAgICB2YXIgYXJncyA9IGFyZ3VtZW50cywKICAgICAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhhcmdzWzBdKTsKCiAgICAgICAgICByZXR1cm4gYXJncy5sZW5ndGggPCAzID8gc3RyaW5nIDogc3RyaW5nLnJlcGxhY2UoYXJnc1sxXSwgYXJnc1syXSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgc3RyaW5nYCB0bwogICAgICAgICAqIFtzbmFrZSBjYXNlXShodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9TbmFrZV9jYXNlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHNuYWtlIGNhc2VkIHN0cmluZy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5zbmFrZUNhc2UoJ0ZvbyBCYXInKTsKICAgICAgICAgKiAvLyA9PiAnZm9vX2JhcicKICAgICAgICAgKgogICAgICAgICAqIF8uc25ha2VDYXNlKCdmb29CYXInKTsKICAgICAgICAgKiAvLyA9PiAnZm9vX2JhcicKICAgICAgICAgKgogICAgICAgICAqIF8uc25ha2VDYXNlKCctLUZPTy1CQVItLScpOwogICAgICAgICAqIC8vID0+ICdmb29fYmFyJwogICAgICAgICAqLwogICAgICAgIHZhciBzbmFrZUNhc2UgPSBjcmVhdGVDb21wb3VuZGVyKGZ1bmN0aW9uKHJlc3VsdCwgd29yZCwgaW5kZXgpIHsKICAgICAgICAgIHJldHVybiByZXN1bHQgKyAoaW5kZXggPyAnXycgOiAnJykgKyB3b3JkLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIFNwbGl0cyBgc3RyaW5nYCBieSBgc2VwYXJhdG9yYC4KICAgICAgICAgKgogICAgICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBiYXNlZCBvbgogICAgICAgICAqIFtgU3RyaW5nI3NwbGl0YF0oaHR0cHM6Ly9tZG4uaW8vU3RyaW5nL3NwbGl0KS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBzcGxpdC4KICAgICAgICAgKiBAcGFyYW0ge1JlZ0V4cHxzdHJpbmd9IHNlcGFyYXRvciBUaGUgc2VwYXJhdG9yIHBhdHRlcm4gdG8gc3BsaXQgYnkuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtsaW1pdF0gVGhlIGxlbmd0aCB0byB0cnVuY2F0ZSByZXN1bHRzIHRvLgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgc3RyaW5nIHNlZ21lbnRzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnNwbGl0KCdhLWItYycsICctJywgMik7CiAgICAgICAgICogLy8gPT4gWydhJywgJ2InXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHNwbGl0KHN0cmluZywgc2VwYXJhdG9yLCBsaW1pdCkgewogICAgICAgICAgaWYgKGxpbWl0ICYmIHR5cGVvZiBsaW1pdCAhPSAnbnVtYmVyJyAmJiBpc0l0ZXJhdGVlQ2FsbChzdHJpbmcsIHNlcGFyYXRvciwgbGltaXQpKSB7CiAgICAgICAgICAgIHNlcGFyYXRvciA9IGxpbWl0ID0gdW5kZWZpbmVkJDE7CiAgICAgICAgICB9CiAgICAgICAgICBsaW1pdCA9IGxpbWl0ID09PSB1bmRlZmluZWQkMSA/IE1BWF9BUlJBWV9MRU5HVEggOiBsaW1pdCA+Pj4gMDsKICAgICAgICAgIGlmICghbGltaXQpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIGlmIChzdHJpbmcgJiYgKAogICAgICAgICAgICAgICAgdHlwZW9mIHNlcGFyYXRvciA9PSAnc3RyaW5nJyB8fAogICAgICAgICAgICAgICAgKHNlcGFyYXRvciAhPSBudWxsICYmICFpc1JlZ0V4cChzZXBhcmF0b3IpKQogICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgc2VwYXJhdG9yID0gYmFzZVRvU3RyaW5nKHNlcGFyYXRvcik7CiAgICAgICAgICAgIGlmICghc2VwYXJhdG9yICYmIGhhc1VuaWNvZGUoc3RyaW5nKSkgewogICAgICAgICAgICAgIHJldHVybiBjYXN0U2xpY2Uoc3RyaW5nVG9BcnJheShzdHJpbmcpLCAwLCBsaW1pdCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBzdHJpbmcuc3BsaXQoc2VwYXJhdG9yLCBsaW1pdCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgc3RyaW5nYCB0bwogICAgICAgICAqIFtzdGFydCBjYXNlXShodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9MZXR0ZXJfY2FzZSNTdHlsaXN0aWNfb3Jfc3BlY2lhbGlzZWRfdXNhZ2UpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMS4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgc3RhcnQgY2FzZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnN0YXJ0Q2FzZSgnLS1mb28tYmFyLS0nKTsKICAgICAgICAgKiAvLyA9PiAnRm9vIEJhcicKICAgICAgICAgKgogICAgICAgICAqIF8uc3RhcnRDYXNlKCdmb29CYXInKTsKICAgICAgICAgKiAvLyA9PiAnRm9vIEJhcicKICAgICAgICAgKgogICAgICAgICAqIF8uc3RhcnRDYXNlKCdfX0ZPT19CQVJfXycpOwogICAgICAgICAqIC8vID0+ICdGT08gQkFSJwogICAgICAgICAqLwogICAgICAgIHZhciBzdGFydENhc2UgPSBjcmVhdGVDb21wb3VuZGVyKGZ1bmN0aW9uKHJlc3VsdCwgd29yZCwgaW5kZXgpIHsKICAgICAgICAgIHJldHVybiByZXN1bHQgKyAoaW5kZXggPyAnICcgOiAnJykgKyB1cHBlckZpcnN0KHdvcmQpOwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgYHN0cmluZ2Agc3RhcnRzIHdpdGggdGhlIGdpdmVuIHRhcmdldCBzdHJpbmcuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gaW5zcGVjdC4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3RhcmdldF0gVGhlIHN0cmluZyB0byBzZWFyY2ggZm9yLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbcG9zaXRpb249MF0gVGhlIHBvc2l0aW9uIHRvIHNlYXJjaCBmcm9tLgogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgc3RyaW5nYCBzdGFydHMgd2l0aCBgdGFyZ2V0YCwKICAgICAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnN0YXJ0c1dpdGgoJ2FiYycsICdhJyk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqCiAgICAgICAgICogXy5zdGFydHNXaXRoKCdhYmMnLCAnYicpOwogICAgICAgICAqIC8vID0+IGZhbHNlCiAgICAgICAgICoKICAgICAgICAgKiBfLnN0YXJ0c1dpdGgoJ2FiYycsICdiJywgMSk7CiAgICAgICAgICogLy8gPT4gdHJ1ZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0YXJ0c1dpdGgoc3RyaW5nLCB0YXJnZXQsIHBvc2l0aW9uKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgcG9zaXRpb24gPSBwb3NpdGlvbiA9PSBudWxsCiAgICAgICAgICAgID8gMAogICAgICAgICAgICA6IGJhc2VDbGFtcCh0b0ludGVnZXIocG9zaXRpb24pLCAwLCBzdHJpbmcubGVuZ3RoKTsKCiAgICAgICAgICB0YXJnZXQgPSBiYXNlVG9TdHJpbmcodGFyZ2V0KTsKICAgICAgICAgIHJldHVybiBzdHJpbmcuc2xpY2UocG9zaXRpb24sIHBvc2l0aW9uICsgdGFyZ2V0Lmxlbmd0aCkgPT0gdGFyZ2V0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGNvbXBpbGVkIHRlbXBsYXRlIGZ1bmN0aW9uIHRoYXQgY2FuIGludGVycG9sYXRlIGRhdGEgcHJvcGVydGllcwogICAgICAgICAqIGluICJpbnRlcnBvbGF0ZSIgZGVsaW1pdGVycywgSFRNTC1lc2NhcGUgaW50ZXJwb2xhdGVkIGRhdGEgcHJvcGVydGllcyBpbgogICAgICAgICAqICJlc2NhcGUiIGRlbGltaXRlcnMsIGFuZCBleGVjdXRlIEphdmFTY3JpcHQgaW4gImV2YWx1YXRlIiBkZWxpbWl0ZXJzLiBEYXRhCiAgICAgICAgICogcHJvcGVydGllcyBtYXkgYmUgYWNjZXNzZWQgYXMgZnJlZSB2YXJpYWJsZXMgaW4gdGhlIHRlbXBsYXRlLiBJZiBhIHNldHRpbmcKICAgICAgICAgKiBvYmplY3QgaXMgZ2l2ZW4sIGl0IHRha2VzIHByZWNlZGVuY2Ugb3ZlciBgXy50ZW1wbGF0ZVNldHRpbmdzYCB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogSW4gdGhlIGRldmVsb3BtZW50IGJ1aWxkIGBfLnRlbXBsYXRlYCB1dGlsaXplcwogICAgICAgICAqIFtzb3VyY2VVUkxzXShodHRwOi8vd3d3Lmh0bWw1cm9ja3MuY29tL2VuL3R1dG9yaWFscy9kZXZlbG9wZXJ0b29scy9zb3VyY2VtYXBzLyN0b2Mtc291cmNldXJsKQogICAgICAgICAqIGZvciBlYXNpZXIgZGVidWdnaW5nLgogICAgICAgICAqCiAgICAgICAgICogRm9yIG1vcmUgaW5mb3JtYXRpb24gb24gcHJlY29tcGlsaW5nIHRlbXBsYXRlcyBzZWUKICAgICAgICAgKiBbbG9kYXNoJ3MgY3VzdG9tIGJ1aWxkcyBkb2N1bWVudGF0aW9uXShodHRwczovL2xvZGFzaC5jb20vY3VzdG9tLWJ1aWxkcykuCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgbW9yZSBpbmZvcm1hdGlvbiBvbiBDaHJvbWUgZXh0ZW5zaW9uIHNhbmRib3hlcyBzZWUKICAgICAgICAgKiBbQ2hyb21lJ3MgZXh0ZW5zaW9ucyBkb2N1bWVudGF0aW9uXShodHRwczovL2RldmVsb3Blci5jaHJvbWUuY29tL2V4dGVuc2lvbnMvc2FuZGJveGluZ0V2YWwpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgdGVtcGxhdGUgc3RyaW5nLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb3B0aW9ucz17fV0gVGhlIG9wdGlvbnMgb2JqZWN0LgogICAgICAgICAqIEBwYXJhbSB7UmVnRXhwfSBbb3B0aW9ucy5lc2NhcGU9Xy50ZW1wbGF0ZVNldHRpbmdzLmVzY2FwZV0KICAgICAgICAgKiAgVGhlIEhUTUwgImVzY2FwZSIgZGVsaW1pdGVyLgogICAgICAgICAqIEBwYXJhbSB7UmVnRXhwfSBbb3B0aW9ucy5ldmFsdWF0ZT1fLnRlbXBsYXRlU2V0dGluZ3MuZXZhbHVhdGVdCiAgICAgICAgICogIFRoZSAiZXZhbHVhdGUiIGRlbGltaXRlci4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29wdGlvbnMuaW1wb3J0cz1fLnRlbXBsYXRlU2V0dGluZ3MuaW1wb3J0c10KICAgICAgICAgKiAgQW4gb2JqZWN0IHRvIGltcG9ydCBpbnRvIHRoZSB0ZW1wbGF0ZSBhcyBmcmVlIHZhcmlhYmxlcy4KICAgICAgICAgKiBAcGFyYW0ge1JlZ0V4cH0gW29wdGlvbnMuaW50ZXJwb2xhdGU9Xy50ZW1wbGF0ZVNldHRpbmdzLmludGVycG9sYXRlXQogICAgICAgICAqICBUaGUgImludGVycG9sYXRlIiBkZWxpbWl0ZXIuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtvcHRpb25zLnNvdXJjZVVSTD0nbG9kYXNoLnRlbXBsYXRlU291cmNlc1tuXSddCiAgICAgICAgICogIFRoZSBzb3VyY2VVUkwgb2YgdGhlIGNvbXBpbGVkIHRlbXBsYXRlLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbb3B0aW9ucy52YXJpYWJsZT0nb2JqJ10KICAgICAgICAgKiAgVGhlIGRhdGEgb2JqZWN0IHZhcmlhYmxlIG5hbWUuCiAgICAgICAgICogQHBhcmFtLSB7T2JqZWN0fSBbZ3VhcmRdIEVuYWJsZXMgdXNlIGFzIGFuIGl0ZXJhdGVlIGZvciBtZXRob2RzIGxpa2UgYF8ubWFwYC4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIGNvbXBpbGVkIHRlbXBsYXRlIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiAvLyBVc2UgdGhlICJpbnRlcnBvbGF0ZSIgZGVsaW1pdGVyIHRvIGNyZWF0ZSBhIGNvbXBpbGVkIHRlbXBsYXRlLgogICAgICAgICAqIHZhciBjb21waWxlZCA9IF8udGVtcGxhdGUoJ2hlbGxvIDwlPSB1c2VyICU+IScpOwogICAgICAgICAqIGNvbXBpbGVkKHsgJ3VzZXInOiAnZnJlZCcgfSk7CiAgICAgICAgICogLy8gPT4gJ2hlbGxvIGZyZWQhJwogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIHRoZSBIVE1MICJlc2NhcGUiIGRlbGltaXRlciB0byBlc2NhcGUgZGF0YSBwcm9wZXJ0eSB2YWx1ZXMuCiAgICAgICAgICogdmFyIGNvbXBpbGVkID0gXy50ZW1wbGF0ZSgnPGI+PCUtIHZhbHVlICU+PC9iPicpOwogICAgICAgICAqIGNvbXBpbGVkKHsgJ3ZhbHVlJzogJzxzY3JpcHQ+JyB9KTsKICAgICAgICAgKiAvLyA9PiAnPGI+Jmx0O3NjcmlwdCZndDs8L2I+JwogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIHRoZSAiZXZhbHVhdGUiIGRlbGltaXRlciB0byBleGVjdXRlIEphdmFTY3JpcHQgYW5kIGdlbmVyYXRlIEhUTUwuCiAgICAgICAgICogdmFyIGNvbXBpbGVkID0gXy50ZW1wbGF0ZSgnPCUgXy5mb3JFYWNoKHVzZXJzLCBmdW5jdGlvbih1c2VyKSB7ICU+PGxpPjwlLSB1c2VyICU+PC9saT48JSB9KTsgJT4nKTsKICAgICAgICAgKiBjb21waWxlZCh7ICd1c2Vycyc6IFsnZnJlZCcsICdiYXJuZXknXSB9KTsKICAgICAgICAgKiAvLyA9PiAnPGxpPmZyZWQ8L2xpPjxsaT5iYXJuZXk8L2xpPicKICAgICAgICAgKgogICAgICAgICAqIC8vIFVzZSB0aGUgaW50ZXJuYWwgYHByaW50YCBmdW5jdGlvbiBpbiAiZXZhbHVhdGUiIGRlbGltaXRlcnMuCiAgICAgICAgICogdmFyIGNvbXBpbGVkID0gXy50ZW1wbGF0ZSgnPCUgcHJpbnQoImhlbGxvICIgKyB1c2VyKTsgJT4hJyk7CiAgICAgICAgICogY29tcGlsZWQoeyAndXNlcic6ICdiYXJuZXknIH0pOwogICAgICAgICAqIC8vID0+ICdoZWxsbyBiYXJuZXkhJwogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIHRoZSBFUyB0ZW1wbGF0ZSBsaXRlcmFsIGRlbGltaXRlciBhcyBhbiAiaW50ZXJwb2xhdGUiIGRlbGltaXRlci4KICAgICAgICAgKiAvLyBEaXNhYmxlIHN1cHBvcnQgYnkgcmVwbGFjaW5nIHRoZSAiaW50ZXJwb2xhdGUiIGRlbGltaXRlci4KICAgICAgICAgKiB2YXIgY29tcGlsZWQgPSBfLnRlbXBsYXRlKCdoZWxsbyAkeyB1c2VyIH0hJyk7CiAgICAgICAgICogY29tcGlsZWQoeyAndXNlcic6ICdwZWJibGVzJyB9KTsKICAgICAgICAgKiAvLyA9PiAnaGVsbG8gcGViYmxlcyEnCiAgICAgICAgICoKICAgICAgICAgKiAvLyBVc2UgYmFja3NsYXNoZXMgdG8gdHJlYXQgZGVsaW1pdGVycyBhcyBwbGFpbiB0ZXh0LgogICAgICAgICAqIHZhciBjb21waWxlZCA9IF8udGVtcGxhdGUoJzwlPSAiXFw8JS0gdmFsdWUgJVxcPiIgJT4nKTsKICAgICAgICAgKiBjb21waWxlZCh7ICd2YWx1ZSc6ICdpZ25vcmVkJyB9KTsKICAgICAgICAgKiAvLyA9PiAnPCUtIHZhbHVlICU+JwogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIHRoZSBgaW1wb3J0c2Agb3B0aW9uIHRvIGltcG9ydCBgalF1ZXJ5YCBhcyBganFgLgogICAgICAgICAqIHZhciB0ZXh0ID0gJzwlIGpxLmVhY2godXNlcnMsIGZ1bmN0aW9uKHVzZXIpIHsgJT48bGk+PCUtIHVzZXIgJT48L2xpPjwlIH0pOyAlPic7CiAgICAgICAgICogdmFyIGNvbXBpbGVkID0gXy50ZW1wbGF0ZSh0ZXh0LCB7ICdpbXBvcnRzJzogeyAnanEnOiBqUXVlcnkgfSB9KTsKICAgICAgICAgKiBjb21waWxlZCh7ICd1c2Vycyc6IFsnZnJlZCcsICdiYXJuZXknXSB9KTsKICAgICAgICAgKiAvLyA9PiAnPGxpPmZyZWQ8L2xpPjxsaT5iYXJuZXk8L2xpPicKICAgICAgICAgKgogICAgICAgICAqIC8vIFVzZSB0aGUgYHNvdXJjZVVSTGAgb3B0aW9uIHRvIHNwZWNpZnkgYSBjdXN0b20gc291cmNlVVJMIGZvciB0aGUgdGVtcGxhdGUuCiAgICAgICAgICogdmFyIGNvbXBpbGVkID0gXy50ZW1wbGF0ZSgnaGVsbG8gPCU9IHVzZXIgJT4hJywgeyAnc291cmNlVVJMJzogJy9iYXNpYy9ncmVldGluZy5qc3QnIH0pOwogICAgICAgICAqIGNvbXBpbGVkKGRhdGEpOwogICAgICAgICAqIC8vID0+IEZpbmQgdGhlIHNvdXJjZSBvZiAiZ3JlZXRpbmcuanN0IiB1bmRlciB0aGUgU291cmNlcyB0YWIgb3IgUmVzb3VyY2VzIHBhbmVsIG9mIHRoZSB3ZWIgaW5zcGVjdG9yLgogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIHRoZSBgdmFyaWFibGVgIG9wdGlvbiB0byBlbnN1cmUgYSB3aXRoLXN0YXRlbWVudCBpc24ndCB1c2VkIGluIHRoZSBjb21waWxlZCB0ZW1wbGF0ZS4KICAgICAgICAgKiB2YXIgY29tcGlsZWQgPSBfLnRlbXBsYXRlKCdoaSA8JT0gZGF0YS51c2VyICU+IScsIHsgJ3ZhcmlhYmxlJzogJ2RhdGEnIH0pOwogICAgICAgICAqIGNvbXBpbGVkLnNvdXJjZTsKICAgICAgICAgKiAvLyA9PiBmdW5jdGlvbihkYXRhKSB7CiAgICAgICAgICogLy8gICB2YXIgX190LCBfX3AgPSAnJzsKICAgICAgICAgKiAvLyAgIF9fcCArPSAnaGkgJyArICgoX190ID0gKCBkYXRhLnVzZXIgKSkgPT0gbnVsbCA/ICcnIDogX190KSArICchJzsKICAgICAgICAgKiAvLyAgIHJldHVybiBfX3A7CiAgICAgICAgICogLy8gfQogICAgICAgICAqCiAgICAgICAgICogLy8gVXNlIGN1c3RvbSB0ZW1wbGF0ZSBkZWxpbWl0ZXJzLgogICAgICAgICAqIF8udGVtcGxhdGVTZXR0aW5ncy5pbnRlcnBvbGF0ZSA9IC97eyhbXHNcU10rPyl9fS9nOwogICAgICAgICAqIHZhciBjb21waWxlZCA9IF8udGVtcGxhdGUoJ2hlbGxvIHt7IHVzZXIgfX0hJyk7CiAgICAgICAgICogY29tcGlsZWQoeyAndXNlcic6ICdtdXN0YWNoZScgfSk7CiAgICAgICAgICogLy8gPT4gJ2hlbGxvIG11c3RhY2hlIScKICAgICAgICAgKgogICAgICAgICAqIC8vIFVzZSB0aGUgYHNvdXJjZWAgcHJvcGVydHkgdG8gaW5saW5lIGNvbXBpbGVkIHRlbXBsYXRlcyBmb3IgbWVhbmluZ2Z1bAogICAgICAgICAqIC8vIGxpbmUgbnVtYmVycyBpbiBlcnJvciBtZXNzYWdlcyBhbmQgc3RhY2sgdHJhY2VzLgogICAgICAgICAqIGZzLndyaXRlRmlsZVN5bmMocGF0aC5qb2luKHByb2Nlc3MuY3dkKCksICdqc3QuanMnKSwgJ1wKICAgICAgICAgKiAgIHZhciBKU1QgPSB7XAogICAgICAgICAqICAgICAibWFpbiI6ICcgKyBfLnRlbXBsYXRlKG1haW5UZXh0KS5zb3VyY2UgKyAnXAogICAgICAgICAqICAgfTtcCiAgICAgICAgICogJyk7CiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdGVtcGxhdGUoc3RyaW5nLCBvcHRpb25zLCBndWFyZCkgewogICAgICAgICAgLy8gQmFzZWQgb24gSm9obiBSZXNpZydzIGB0bXBsYCBpbXBsZW1lbnRhdGlvbgogICAgICAgICAgLy8gKGh0dHA6Ly9lam9obi5vcmcvYmxvZy9qYXZhc2NyaXB0LW1pY3JvLXRlbXBsYXRpbmcvKQogICAgICAgICAgLy8gYW5kIExhdXJhIERva3Rvcm92YSdzIGRvVC5qcyAoaHR0cHM6Ly9naXRodWIuY29tL29sYWRvL2RvVCkuCiAgICAgICAgICB2YXIgc2V0dGluZ3MgPSBsb2Rhc2gudGVtcGxhdGVTZXR0aW5nczsKCiAgICAgICAgICBpZiAoZ3VhcmQgJiYgaXNJdGVyYXRlZUNhbGwoc3RyaW5nLCBvcHRpb25zLCBndWFyZCkpIHsKICAgICAgICAgICAgb3B0aW9ucyA9IHVuZGVmaW5lZCQxOwogICAgICAgICAgfQogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIG9wdGlvbnMgPSBhc3NpZ25JbldpdGgoe30sIG9wdGlvbnMsIHNldHRpbmdzLCBjdXN0b21EZWZhdWx0c0Fzc2lnbkluKTsKCiAgICAgICAgICB2YXIgaW1wb3J0cyA9IGFzc2lnbkluV2l0aCh7fSwgb3B0aW9ucy5pbXBvcnRzLCBzZXR0aW5ncy5pbXBvcnRzLCBjdXN0b21EZWZhdWx0c0Fzc2lnbkluKSwKICAgICAgICAgICAgICBpbXBvcnRzS2V5cyA9IGtleXMoaW1wb3J0cyksCiAgICAgICAgICAgICAgaW1wb3J0c1ZhbHVlcyA9IGJhc2VWYWx1ZXMoaW1wb3J0cywgaW1wb3J0c0tleXMpOwoKICAgICAgICAgIHZhciBpc0VzY2FwaW5nLAogICAgICAgICAgICAgIGlzRXZhbHVhdGluZywKICAgICAgICAgICAgICBpbmRleCA9IDAsCiAgICAgICAgICAgICAgaW50ZXJwb2xhdGUgPSBvcHRpb25zLmludGVycG9sYXRlIHx8IHJlTm9NYXRjaCwKICAgICAgICAgICAgICBzb3VyY2UgPSAiX19wICs9ICciOwoKICAgICAgICAgIC8vIENvbXBpbGUgdGhlIHJlZ2V4cCB0byBtYXRjaCBlYWNoIGRlbGltaXRlci4KICAgICAgICAgIHZhciByZURlbGltaXRlcnMgPSBSZWdFeHAoCiAgICAgICAgICAgIChvcHRpb25zLmVzY2FwZSB8fCByZU5vTWF0Y2gpLnNvdXJjZSArICd8JyArCiAgICAgICAgICAgIGludGVycG9sYXRlLnNvdXJjZSArICd8JyArCiAgICAgICAgICAgIChpbnRlcnBvbGF0ZSA9PT0gcmVJbnRlcnBvbGF0ZSA/IHJlRXNUZW1wbGF0ZSA6IHJlTm9NYXRjaCkuc291cmNlICsgJ3wnICsKICAgICAgICAgICAgKG9wdGlvbnMuZXZhbHVhdGUgfHwgcmVOb01hdGNoKS5zb3VyY2UgKyAnfCQnCiAgICAgICAgICAsICdnJyk7CgogICAgICAgICAgLy8gVXNlIGEgc291cmNlVVJMIGZvciBlYXNpZXIgZGVidWdnaW5nLgogICAgICAgICAgLy8gVGhlIHNvdXJjZVVSTCBnZXRzIGluamVjdGVkIGludG8gdGhlIHNvdXJjZSB0aGF0J3MgZXZhbC1lZCwgc28gYmUgY2FyZWZ1bAogICAgICAgICAgLy8gdG8gbm9ybWFsaXplIGFsbCBraW5kcyBvZiB3aGl0ZXNwYWNlLCBzbyBlLmcuIG5ld2xpbmVzIChhbmQgdW5pY29kZSB2ZXJzaW9ucyBvZiBpdCkgY2FuJ3Qgc25lYWsgaW4KICAgICAgICAgIC8vIGFuZCBlc2NhcGUgdGhlIGNvbW1lbnQsIHRodXMgaW5qZWN0aW5nIGNvZGUgdGhhdCBnZXRzIGV2YWxlZC4KICAgICAgICAgIHZhciBzb3VyY2VVUkwgPSAnLy8jIHNvdXJjZVVSTD0nICsKICAgICAgICAgICAgKGhhc093blByb3BlcnR5LmNhbGwob3B0aW9ucywgJ3NvdXJjZVVSTCcpCiAgICAgICAgICAgICAgPyAob3B0aW9ucy5zb3VyY2VVUkwgKyAnJykucmVwbGFjZSgvXHMvZywgJyAnKQogICAgICAgICAgICAgIDogKCdsb2Rhc2gudGVtcGxhdGVTb3VyY2VzWycgKyAoKyt0ZW1wbGF0ZUNvdW50ZXIpICsgJ10nKQogICAgICAgICAgICApICsgJ1xuJzsKCiAgICAgICAgICBzdHJpbmcucmVwbGFjZShyZURlbGltaXRlcnMsIGZ1bmN0aW9uKG1hdGNoLCBlc2NhcGVWYWx1ZSwgaW50ZXJwb2xhdGVWYWx1ZSwgZXNUZW1wbGF0ZVZhbHVlLCBldmFsdWF0ZVZhbHVlLCBvZmZzZXQpIHsKICAgICAgICAgICAgaW50ZXJwb2xhdGVWYWx1ZSB8fCAoaW50ZXJwb2xhdGVWYWx1ZSA9IGVzVGVtcGxhdGVWYWx1ZSk7CgogICAgICAgICAgICAvLyBFc2NhcGUgY2hhcmFjdGVycyB0aGF0IGNhbid0IGJlIGluY2x1ZGVkIGluIHN0cmluZyBsaXRlcmFscy4KICAgICAgICAgICAgc291cmNlICs9IHN0cmluZy5zbGljZShpbmRleCwgb2Zmc2V0KS5yZXBsYWNlKHJlVW5lc2NhcGVkU3RyaW5nLCBlc2NhcGVTdHJpbmdDaGFyKTsKCiAgICAgICAgICAgIC8vIFJlcGxhY2UgZGVsaW1pdGVycyB3aXRoIHNuaXBwZXRzLgogICAgICAgICAgICBpZiAoZXNjYXBlVmFsdWUpIHsKICAgICAgICAgICAgICBpc0VzY2FwaW5nID0gdHJ1ZTsKICAgICAgICAgICAgICBzb3VyY2UgKz0gIicgK1xuX19lKCIgKyBlc2NhcGVWYWx1ZSArICIpICtcbiciOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChldmFsdWF0ZVZhbHVlKSB7CiAgICAgICAgICAgICAgaXNFdmFsdWF0aW5nID0gdHJ1ZTsKICAgICAgICAgICAgICBzb3VyY2UgKz0gIic7XG4iICsgZXZhbHVhdGVWYWx1ZSArICI7XG5fX3AgKz0gJyI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGludGVycG9sYXRlVmFsdWUpIHsKICAgICAgICAgICAgICBzb3VyY2UgKz0gIicgK1xuKChfX3QgPSAoIiArIGludGVycG9sYXRlVmFsdWUgKyAiKSkgPT0gbnVsbCA/ICcnIDogX190KSArXG4nIjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpbmRleCA9IG9mZnNldCArIG1hdGNoLmxlbmd0aDsKCiAgICAgICAgICAgIC8vIFRoZSBKUyBlbmdpbmUgZW1iZWRkZWQgaW4gQWRvYmUgcHJvZHVjdHMgbmVlZHMgYG1hdGNoYCByZXR1cm5lZCBpbgogICAgICAgICAgICAvLyBvcmRlciB0byBwcm9kdWNlIHRoZSBjb3JyZWN0IGBvZmZzZXRgIHZhbHVlLgogICAgICAgICAgICByZXR1cm4gbWF0Y2g7CiAgICAgICAgICB9KTsKCiAgICAgICAgICBzb3VyY2UgKz0gIic7XG4iOwoKICAgICAgICAgIC8vIElmIGB2YXJpYWJsZWAgaXMgbm90IHNwZWNpZmllZCB3cmFwIGEgd2l0aC1zdGF0ZW1lbnQgYXJvdW5kIHRoZSBnZW5lcmF0ZWQKICAgICAgICAgIC8vIGNvZGUgdG8gYWRkIHRoZSBkYXRhIG9iamVjdCB0byB0aGUgdG9wIG9mIHRoZSBzY29wZSBjaGFpbi4KICAgICAgICAgIHZhciB2YXJpYWJsZSA9IGhhc093blByb3BlcnR5LmNhbGwob3B0aW9ucywgJ3ZhcmlhYmxlJykgJiYgb3B0aW9ucy52YXJpYWJsZTsKICAgICAgICAgIGlmICghdmFyaWFibGUpIHsKICAgICAgICAgICAgc291cmNlID0gJ3dpdGggKG9iaikge1xuJyArIHNvdXJjZSArICdcbn1cbic7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBDbGVhbnVwIGNvZGUgYnkgc3RyaXBwaW5nIGVtcHR5IHN0cmluZ3MuCiAgICAgICAgICBzb3VyY2UgPSAoaXNFdmFsdWF0aW5nID8gc291cmNlLnJlcGxhY2UocmVFbXB0eVN0cmluZ0xlYWRpbmcsICcnKSA6IHNvdXJjZSkKICAgICAgICAgICAgLnJlcGxhY2UocmVFbXB0eVN0cmluZ01pZGRsZSwgJyQxJykKICAgICAgICAgICAgLnJlcGxhY2UocmVFbXB0eVN0cmluZ1RyYWlsaW5nLCAnJDE7Jyk7CgogICAgICAgICAgLy8gRnJhbWUgY29kZSBhcyB0aGUgZnVuY3Rpb24gYm9keS4KICAgICAgICAgIHNvdXJjZSA9ICdmdW5jdGlvbignICsgKHZhcmlhYmxlIHx8ICdvYmonKSArICcpIHtcbicgKwogICAgICAgICAgICAodmFyaWFibGUKICAgICAgICAgICAgICA/ICcnCiAgICAgICAgICAgICAgOiAnb2JqIHx8IChvYmogPSB7fSk7XG4nCiAgICAgICAgICAgICkgKwogICAgICAgICAgICAidmFyIF9fdCwgX19wID0gJyciICsKICAgICAgICAgICAgKGlzRXNjYXBpbmcKICAgICAgICAgICAgICAgPyAnLCBfX2UgPSBfLmVzY2FwZScKICAgICAgICAgICAgICAgOiAnJwogICAgICAgICAgICApICsKICAgICAgICAgICAgKGlzRXZhbHVhdGluZwogICAgICAgICAgICAgID8gJywgX19qID0gQXJyYXkucHJvdG90eXBlLmpvaW47XG4nICsKICAgICAgICAgICAgICAgICJmdW5jdGlvbiBwcmludCgpIHsgX19wICs9IF9fai5jYWxsKGFyZ3VtZW50cywgJycpIH1cbiIKICAgICAgICAgICAgICA6ICc7XG4nCiAgICAgICAgICAgICkgKwogICAgICAgICAgICBzb3VyY2UgKwogICAgICAgICAgICAncmV0dXJuIF9fcFxufSc7CgogICAgICAgICAgdmFyIHJlc3VsdCA9IGF0dGVtcHQoZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBGdW5jdGlvbihpbXBvcnRzS2V5cywgc291cmNlVVJMICsgJ3JldHVybiAnICsgc291cmNlKQogICAgICAgICAgICAgIC5hcHBseSh1bmRlZmluZWQkMSwgaW1wb3J0c1ZhbHVlcyk7CiAgICAgICAgICB9KTsKCiAgICAgICAgICAvLyBQcm92aWRlIHRoZSBjb21waWxlZCBmdW5jdGlvbidzIHNvdXJjZSBieSBpdHMgYHRvU3RyaW5nYCBtZXRob2Qgb3IKICAgICAgICAgIC8vIHRoZSBgc291cmNlYCBwcm9wZXJ0eSBhcyBhIGNvbnZlbmllbmNlIGZvciBpbmxpbmluZyBjb21waWxlZCB0ZW1wbGF0ZXMuCiAgICAgICAgICByZXN1bHQuc291cmNlID0gc291cmNlOwogICAgICAgICAgaWYgKGlzRXJyb3IocmVzdWx0KSkgewogICAgICAgICAgICB0aHJvdyByZXN1bHQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYHN0cmluZ2AsIGFzIGEgd2hvbGUsIHRvIGxvd2VyIGNhc2UganVzdCBsaWtlCiAgICAgICAgICogW1N0cmluZyN0b0xvd2VyQ2FzZV0oaHR0cHM6Ly9tZG4uaW8vdG9Mb3dlckNhc2UpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIGNvbnZlcnQuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgbG93ZXIgY2FzZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvTG93ZXIoJy0tRm9vLUJhci0tJyk7CiAgICAgICAgICogLy8gPT4gJy0tZm9vLWJhci0tJwogICAgICAgICAqCiAgICAgICAgICogXy50b0xvd2VyKCdmb29CYXInKTsKICAgICAgICAgKiAvLyA9PiAnZm9vYmFyJwogICAgICAgICAqCiAgICAgICAgICogXy50b0xvd2VyKCdfX0ZPT19CQVJfXycpOwogICAgICAgICAqIC8vID0+ICdfX2Zvb19iYXJfXycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0b0xvd2VyKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdG9TdHJpbmcodmFsdWUpLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgc3RyaW5nYCwgYXMgYSB3aG9sZSwgdG8gdXBwZXIgY2FzZSBqdXN0IGxpa2UKICAgICAgICAgKiBbU3RyaW5nI3RvVXBwZXJDYXNlXShodHRwczovL21kbi5pby90b1VwcGVyQ2FzZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSB1cHBlciBjYXNlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udG9VcHBlcignLS1mb28tYmFyLS0nKTsKICAgICAgICAgKiAvLyA9PiAnLS1GT08tQkFSLS0nCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvVXBwZXIoJ2Zvb0JhcicpOwogICAgICAgICAqIC8vID0+ICdGT09CQVInCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvVXBwZXIoJ19fZm9vX2Jhcl9fJyk7CiAgICAgICAgICogLy8gPT4gJ19fRk9PX0JBUl9fJwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRvVXBwZXIodmFsdWUpIHsKICAgICAgICAgIHJldHVybiB0b1N0cmluZyh2YWx1ZSkudG9VcHBlckNhc2UoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgbGVhZGluZyBhbmQgdHJhaWxpbmcgd2hpdGVzcGFjZSBvciBzcGVjaWZpZWQgY2hhcmFjdGVycyBmcm9tIGBzdHJpbmdgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHRyaW0uCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz13aGl0ZXNwYWNlXSBUaGUgY2hhcmFjdGVycyB0byB0cmltLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgdHJpbW1lZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udHJpbSgnICBhYmMgICcpOwogICAgICAgICAqIC8vID0+ICdhYmMnCiAgICAgICAgICoKICAgICAgICAgKiBfLnRyaW0oJy1fLWFiYy1fLScsICdfLScpOwogICAgICAgICAqIC8vID0+ICdhYmMnCiAgICAgICAgICoKICAgICAgICAgKiBfLm1hcChbJyAgZm9vICAnLCAnICBiYXIgICddLCBfLnRyaW0pOwogICAgICAgICAqIC8vID0+IFsnZm9vJywgJ2JhciddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdHJpbShzdHJpbmcsIGNoYXJzLCBndWFyZCkgewogICAgICAgICAgc3RyaW5nID0gdG9TdHJpbmcoc3RyaW5nKTsKICAgICAgICAgIGlmIChzdHJpbmcgJiYgKGd1YXJkIHx8IGNoYXJzID09PSB1bmRlZmluZWQkMSkpIHsKICAgICAgICAgICAgcmV0dXJuIHN0cmluZy5yZXBsYWNlKHJlVHJpbSwgJycpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKCFzdHJpbmcgfHwgIShjaGFycyA9IGJhc2VUb1N0cmluZyhjaGFycykpKSB7CiAgICAgICAgICAgIHJldHVybiBzdHJpbmc7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgc3RyU3ltYm9scyA9IHN0cmluZ1RvQXJyYXkoc3RyaW5nKSwKICAgICAgICAgICAgICBjaHJTeW1ib2xzID0gc3RyaW5nVG9BcnJheShjaGFycyksCiAgICAgICAgICAgICAgc3RhcnQgPSBjaGFyc1N0YXJ0SW5kZXgoc3RyU3ltYm9scywgY2hyU3ltYm9scyksCiAgICAgICAgICAgICAgZW5kID0gY2hhcnNFbmRJbmRleChzdHJTeW1ib2xzLCBjaHJTeW1ib2xzKSArIDE7CgogICAgICAgICAgcmV0dXJuIGNhc3RTbGljZShzdHJTeW1ib2xzLCBzdGFydCwgZW5kKS5qb2luKCcnKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgdHJhaWxpbmcgd2hpdGVzcGFjZSBvciBzcGVjaWZpZWQgY2hhcmFjdGVycyBmcm9tIGBzdHJpbmdgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHRyaW0uCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz13aGl0ZXNwYWNlXSBUaGUgY2hhcmFjdGVycyB0byB0cmltLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgdHJpbW1lZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udHJpbUVuZCgnICBhYmMgICcpOwogICAgICAgICAqIC8vID0+ICcgIGFiYycKICAgICAgICAgKgogICAgICAgICAqIF8udHJpbUVuZCgnLV8tYWJjLV8tJywgJ18tJyk7CiAgICAgICAgICogLy8gPT4gJy1fLWFiYycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0cmltRW5kKHN0cmluZywgY2hhcnMsIGd1YXJkKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgaWYgKHN0cmluZyAmJiAoZ3VhcmQgfHwgY2hhcnMgPT09IHVuZGVmaW5lZCQxKSkgewogICAgICAgICAgICByZXR1cm4gc3RyaW5nLnJlcGxhY2UocmVUcmltRW5kLCAnJyk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoIXN0cmluZyB8fCAhKGNoYXJzID0gYmFzZVRvU3RyaW5nKGNoYXJzKSkpIHsKICAgICAgICAgICAgcmV0dXJuIHN0cmluZzsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBzdHJTeW1ib2xzID0gc3RyaW5nVG9BcnJheShzdHJpbmcpLAogICAgICAgICAgICAgIGVuZCA9IGNoYXJzRW5kSW5kZXgoc3RyU3ltYm9scywgc3RyaW5nVG9BcnJheShjaGFycykpICsgMTsKCiAgICAgICAgICByZXR1cm4gY2FzdFNsaWNlKHN0clN5bWJvbHMsIDAsIGVuZCkuam9pbignJyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGxlYWRpbmcgd2hpdGVzcGFjZSBvciBzcGVjaWZpZWQgY2hhcmFjdGVycyBmcm9tIGBzdHJpbmdgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHRyaW0uCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtjaGFycz13aGl0ZXNwYWNlXSBUaGUgY2hhcmFjdGVycyB0byB0cmltLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgdHJpbW1lZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udHJpbVN0YXJ0KCcgIGFiYyAgJyk7CiAgICAgICAgICogLy8gPT4gJ2FiYyAgJwogICAgICAgICAqCiAgICAgICAgICogXy50cmltU3RhcnQoJy1fLWFiYy1fLScsICdfLScpOwogICAgICAgICAqIC8vID0+ICdhYmMtXy0nCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdHJpbVN0YXJ0KHN0cmluZywgY2hhcnMsIGd1YXJkKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgaWYgKHN0cmluZyAmJiAoZ3VhcmQgfHwgY2hhcnMgPT09IHVuZGVmaW5lZCQxKSkgewogICAgICAgICAgICByZXR1cm4gc3RyaW5nLnJlcGxhY2UocmVUcmltU3RhcnQsICcnKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICghc3RyaW5nIHx8ICEoY2hhcnMgPSBiYXNlVG9TdHJpbmcoY2hhcnMpKSkgewogICAgICAgICAgICByZXR1cm4gc3RyaW5nOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHN0clN5bWJvbHMgPSBzdHJpbmdUb0FycmF5KHN0cmluZyksCiAgICAgICAgICAgICAgc3RhcnQgPSBjaGFyc1N0YXJ0SW5kZXgoc3RyU3ltYm9scywgc3RyaW5nVG9BcnJheShjaGFycykpOwoKICAgICAgICAgIHJldHVybiBjYXN0U2xpY2Uoc3RyU3ltYm9scywgc3RhcnQpLmpvaW4oJycpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVHJ1bmNhdGVzIGBzdHJpbmdgIGlmIGl0J3MgbG9uZ2VyIHRoYW4gdGhlIGdpdmVuIG1heGltdW0gc3RyaW5nIGxlbmd0aC4KICAgICAgICAgKiBUaGUgbGFzdCBjaGFyYWN0ZXJzIG9mIHRoZSB0cnVuY2F0ZWQgc3RyaW5nIGFyZSByZXBsYWNlZCB3aXRoIHRoZSBvbWlzc2lvbgogICAgICAgICAqIHN0cmluZyB3aGljaCBkZWZhdWx0cyB0byAiLi4uIi4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byB0cnVuY2F0ZS4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gW29wdGlvbnM9e31dIFRoZSBvcHRpb25zIG9iamVjdC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW29wdGlvbnMubGVuZ3RoPTMwXSBUaGUgbWF4aW11bSBzdHJpbmcgbGVuZ3RoLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbb3B0aW9ucy5vbWlzc2lvbj0nLi4uJ10gVGhlIHN0cmluZyB0byBpbmRpY2F0ZSB0ZXh0IGlzIG9taXR0ZWQuCiAgICAgICAgICogQHBhcmFtIHtSZWdFeHB8c3RyaW5nfSBbb3B0aW9ucy5zZXBhcmF0b3JdIFRoZSBzZXBhcmF0b3IgcGF0dGVybiB0byB0cnVuY2F0ZSB0by4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSB0cnVuY2F0ZWQgc3RyaW5nLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRydW5jYXRlKCdoaS1kaWRkbHktaG8gdGhlcmUsIG5laWdoYm9yaW5vJyk7CiAgICAgICAgICogLy8gPT4gJ2hpLWRpZGRseS1obyB0aGVyZSwgbmVpZ2hiby4uLicKICAgICAgICAgKgogICAgICAgICAqIF8udHJ1bmNhdGUoJ2hpLWRpZGRseS1obyB0aGVyZSwgbmVpZ2hib3Jpbm8nLCB7CiAgICAgICAgICogICAnbGVuZ3RoJzogMjQsCiAgICAgICAgICogICAnc2VwYXJhdG9yJzogJyAnCiAgICAgICAgICogfSk7CiAgICAgICAgICogLy8gPT4gJ2hpLWRpZGRseS1obyB0aGVyZSwuLi4nCiAgICAgICAgICoKICAgICAgICAgKiBfLnRydW5jYXRlKCdoaS1kaWRkbHktaG8gdGhlcmUsIG5laWdoYm9yaW5vJywgewogICAgICAgICAqICAgJ2xlbmd0aCc6IDI0LAogICAgICAgICAqICAgJ3NlcGFyYXRvcic6IC8sPyArLwogICAgICAgICAqIH0pOwogICAgICAgICAqIC8vID0+ICdoaS1kaWRkbHktaG8gdGhlcmUuLi4nCiAgICAgICAgICoKICAgICAgICAgKiBfLnRydW5jYXRlKCdoaS1kaWRkbHktaG8gdGhlcmUsIG5laWdoYm9yaW5vJywgewogICAgICAgICAqICAgJ29taXNzaW9uJzogJyBbLi4uXScKICAgICAgICAgKiB9KTsKICAgICAgICAgKiAvLyA9PiAnaGktZGlkZGx5LWhvIHRoZXJlLCBuZWlnIFsuLi5dJwogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHRydW5jYXRlKHN0cmluZywgb3B0aW9ucykgewogICAgICAgICAgdmFyIGxlbmd0aCA9IERFRkFVTFRfVFJVTkNfTEVOR1RILAogICAgICAgICAgICAgIG9taXNzaW9uID0gREVGQVVMVF9UUlVOQ19PTUlTU0lPTjsKCiAgICAgICAgICBpZiAoaXNPYmplY3Qob3B0aW9ucykpIHsKICAgICAgICAgICAgdmFyIHNlcGFyYXRvciA9ICdzZXBhcmF0b3InIGluIG9wdGlvbnMgPyBvcHRpb25zLnNlcGFyYXRvciA6IHNlcGFyYXRvcjsKICAgICAgICAgICAgbGVuZ3RoID0gJ2xlbmd0aCcgaW4gb3B0aW9ucyA/IHRvSW50ZWdlcihvcHRpb25zLmxlbmd0aCkgOiBsZW5ndGg7CiAgICAgICAgICAgIG9taXNzaW9uID0gJ29taXNzaW9uJyBpbiBvcHRpb25zID8gYmFzZVRvU3RyaW5nKG9wdGlvbnMub21pc3Npb24pIDogb21pc3Npb247CiAgICAgICAgICB9CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwoKICAgICAgICAgIHZhciBzdHJMZW5ndGggPSBzdHJpbmcubGVuZ3RoOwogICAgICAgICAgaWYgKGhhc1VuaWNvZGUoc3RyaW5nKSkgewogICAgICAgICAgICB2YXIgc3RyU3ltYm9scyA9IHN0cmluZ1RvQXJyYXkoc3RyaW5nKTsKICAgICAgICAgICAgc3RyTGVuZ3RoID0gc3RyU3ltYm9scy5sZW5ndGg7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAobGVuZ3RoID49IHN0ckxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gc3RyaW5nOwogICAgICAgICAgfQogICAgICAgICAgdmFyIGVuZCA9IGxlbmd0aCAtIHN0cmluZ1NpemUob21pc3Npb24pOwogICAgICAgICAgaWYgKGVuZCA8IDEpIHsKICAgICAgICAgICAgcmV0dXJuIG9taXNzaW9uOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHJlc3VsdCA9IHN0clN5bWJvbHMKICAgICAgICAgICAgPyBjYXN0U2xpY2Uoc3RyU3ltYm9scywgMCwgZW5kKS5qb2luKCcnKQogICAgICAgICAgICA6IHN0cmluZy5zbGljZSgwLCBlbmQpOwoKICAgICAgICAgIGlmIChzZXBhcmF0b3IgPT09IHVuZGVmaW5lZCQxKSB7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQgKyBvbWlzc2lvbjsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChzdHJTeW1ib2xzKSB7CiAgICAgICAgICAgIGVuZCArPSAocmVzdWx0Lmxlbmd0aCAtIGVuZCk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXNSZWdFeHAoc2VwYXJhdG9yKSkgewogICAgICAgICAgICBpZiAoc3RyaW5nLnNsaWNlKGVuZCkuc2VhcmNoKHNlcGFyYXRvcikpIHsKICAgICAgICAgICAgICB2YXIgbWF0Y2gsCiAgICAgICAgICAgICAgICAgIHN1YnN0cmluZyA9IHJlc3VsdDsKCiAgICAgICAgICAgICAgaWYgKCFzZXBhcmF0b3IuZ2xvYmFsKSB7CiAgICAgICAgICAgICAgICBzZXBhcmF0b3IgPSBSZWdFeHAoc2VwYXJhdG9yLnNvdXJjZSwgdG9TdHJpbmcocmVGbGFncy5leGVjKHNlcGFyYXRvcikpICsgJ2cnKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgc2VwYXJhdG9yLmxhc3RJbmRleCA9IDA7CiAgICAgICAgICAgICAgd2hpbGUgKChtYXRjaCA9IHNlcGFyYXRvci5leGVjKHN1YnN0cmluZykpKSB7CiAgICAgICAgICAgICAgICB2YXIgbmV3RW5kID0gbWF0Y2guaW5kZXg7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHJlc3VsdCA9IHJlc3VsdC5zbGljZSgwLCBuZXdFbmQgPT09IHVuZGVmaW5lZCQxID8gZW5kIDogbmV3RW5kKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIGlmIChzdHJpbmcuaW5kZXhPZihiYXNlVG9TdHJpbmcoc2VwYXJhdG9yKSwgZW5kKSAhPSBlbmQpIHsKICAgICAgICAgICAgdmFyIGluZGV4ID0gcmVzdWx0Lmxhc3RJbmRleE9mKHNlcGFyYXRvcik7CiAgICAgICAgICAgIGlmIChpbmRleCA+IC0xKSB7CiAgICAgICAgICAgICAgcmVzdWx0ID0gcmVzdWx0LnNsaWNlKDAsIGluZGV4KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHJlc3VsdCArIG9taXNzaW9uOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGludmVyc2Ugb2YgYF8uZXNjYXBlYDsgdGhpcyBtZXRob2QgY29udmVydHMgdGhlIEhUTUwgZW50aXRpZXMKICAgICAgICAgKiBgJmFtcDtgLCBgJmx0O2AsIGAmZ3Q7YCwgYCZxdW90O2AsIGFuZCBgJiMzOTtgIGluIGBzdHJpbmdgIHRvCiAgICAgICAgICogdGhlaXIgY29ycmVzcG9uZGluZyBjaGFyYWN0ZXJzLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIE5vIG90aGVyIEhUTUwgZW50aXRpZXMgYXJlIHVuZXNjYXBlZC4gVG8gdW5lc2NhcGUgYWRkaXRpb25hbAogICAgICAgICAqIEhUTUwgZW50aXRpZXMgdXNlIGEgdGhpcmQtcGFydHkgbGlicmFyeSBsaWtlIFtfaGVfXShodHRwczovL210aHMuYmUvaGUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDAuNi4wCiAgICAgICAgICogQGNhdGVnb3J5IFN0cmluZwogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3RyaW5nPScnXSBUaGUgc3RyaW5nIHRvIHVuZXNjYXBlLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHVuZXNjYXBlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udW5lc2NhcGUoJ2ZyZWQsIGJhcm5leSwgJmFtcDsgcGViYmxlcycpOwogICAgICAgICAqIC8vID0+ICdmcmVkLCBiYXJuZXksICYgcGViYmxlcycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB1bmVzY2FwZShzdHJpbmcpIHsKICAgICAgICAgIHN0cmluZyA9IHRvU3RyaW5nKHN0cmluZyk7CiAgICAgICAgICByZXR1cm4gKHN0cmluZyAmJiByZUhhc0VzY2FwZWRIdG1sLnRlc3Qoc3RyaW5nKSkKICAgICAgICAgICAgPyBzdHJpbmcucmVwbGFjZShyZUVzY2FwZWRIdG1sLCB1bmVzY2FwZUh0bWxDaGFyKQogICAgICAgICAgICA6IHN0cmluZzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGBzdHJpbmdgLCBhcyBzcGFjZSBzZXBhcmF0ZWQgd29yZHMsIHRvIHVwcGVyIGNhc2UuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgU3RyaW5nCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzdHJpbmc9JyddIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSB1cHBlciBjYXNlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udXBwZXJDYXNlKCctLWZvby1iYXInKTsKICAgICAgICAgKiAvLyA9PiAnRk9PIEJBUicKICAgICAgICAgKgogICAgICAgICAqIF8udXBwZXJDYXNlKCdmb29CYXInKTsKICAgICAgICAgKiAvLyA9PiAnRk9PIEJBUicKICAgICAgICAgKgogICAgICAgICAqIF8udXBwZXJDYXNlKCdfX2Zvb19iYXJfXycpOwogICAgICAgICAqIC8vID0+ICdGT08gQkFSJwogICAgICAgICAqLwogICAgICAgIHZhciB1cHBlckNhc2UgPSBjcmVhdGVDb21wb3VuZGVyKGZ1bmN0aW9uKHJlc3VsdCwgd29yZCwgaW5kZXgpIHsKICAgICAgICAgIHJldHVybiByZXN1bHQgKyAoaW5kZXggPyAnICcgOiAnJykgKyB3b3JkLnRvVXBwZXJDYXNlKCk7CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIHRoZSBmaXJzdCBjaGFyYWN0ZXIgb2YgYHN0cmluZ2AgdG8gdXBwZXIgY2FzZS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBjb252ZXJ0LgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBzdHJpbmcuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udXBwZXJGaXJzdCgnZnJlZCcpOwogICAgICAgICAqIC8vID0+ICdGcmVkJwogICAgICAgICAqCiAgICAgICAgICogXy51cHBlckZpcnN0KCdGUkVEJyk7CiAgICAgICAgICogLy8gPT4gJ0ZSRUQnCiAgICAgICAgICovCiAgICAgICAgdmFyIHVwcGVyRmlyc3QgPSBjcmVhdGVDYXNlRmlyc3QoJ3RvVXBwZXJDYXNlJyk7CgogICAgICAgIC8qKgogICAgICAgICAqIFNwbGl0cyBgc3RyaW5nYCBpbnRvIGFuIGFycmF5IG9mIGl0cyB3b3Jkcy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBTdHJpbmcKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3N0cmluZz0nJ10gVGhlIHN0cmluZyB0byBpbnNwZWN0LgogICAgICAgICAqIEBwYXJhbSB7UmVnRXhwfHN0cmluZ30gW3BhdHRlcm5dIFRoZSBwYXR0ZXJuIHRvIG1hdGNoIHdvcmRzLgogICAgICAgICAqIEBwYXJhbS0ge09iamVjdH0gW2d1YXJkXSBFbmFibGVzIHVzZSBhcyBhbiBpdGVyYXRlZSBmb3IgbWV0aG9kcyBsaWtlIGBfLm1hcGAuCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSB3b3JkcyBvZiBgc3RyaW5nYC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy53b3JkcygnZnJlZCwgYmFybmV5LCAmIHBlYmJsZXMnKTsKICAgICAgICAgKiAvLyA9PiBbJ2ZyZWQnLCAnYmFybmV5JywgJ3BlYmJsZXMnXQogICAgICAgICAqCiAgICAgICAgICogXy53b3JkcygnZnJlZCwgYmFybmV5LCAmIHBlYmJsZXMnLCAvW14sIF0rL2cpOwogICAgICAgICAqIC8vID0+IFsnZnJlZCcsICdiYXJuZXknLCAnJicsICdwZWJibGVzJ10KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB3b3JkcyhzdHJpbmcsIHBhdHRlcm4sIGd1YXJkKSB7CiAgICAgICAgICBzdHJpbmcgPSB0b1N0cmluZyhzdHJpbmcpOwogICAgICAgICAgcGF0dGVybiA9IGd1YXJkID8gdW5kZWZpbmVkJDEgOiBwYXR0ZXJuOwoKICAgICAgICAgIGlmIChwYXR0ZXJuID09PSB1bmRlZmluZWQkMSkgewogICAgICAgICAgICByZXR1cm4gaGFzVW5pY29kZVdvcmQoc3RyaW5nKSA/IHVuaWNvZGVXb3JkcyhzdHJpbmcpIDogYXNjaWlXb3JkcyhzdHJpbmcpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHN0cmluZy5tYXRjaChwYXR0ZXJuKSB8fCBbXTsKICAgICAgICB9CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQXR0ZW1wdHMgdG8gaW52b2tlIGBmdW5jYCwgcmV0dXJuaW5nIGVpdGhlciB0aGUgcmVzdWx0IG9yIHRoZSBjYXVnaHQgZXJyb3IKICAgICAgICAgKiBvYmplY3QuIEFueSBhZGRpdGlvbmFsIGFyZ3VtZW50cyBhcmUgcHJvdmlkZWQgdG8gYGZ1bmNgIHdoZW4gaXQncyBpbnZva2VkLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBhdHRlbXB0LgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gW2FyZ3NdIFRoZSBhcmd1bWVudHMgdG8gaW52b2tlIGBmdW5jYCB3aXRoLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBgZnVuY2AgcmVzdWx0IG9yIGVycm9yIG9iamVjdC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogLy8gQXZvaWQgdGhyb3dpbmcgZXJyb3JzIGZvciBpbnZhbGlkIHNlbGVjdG9ycy4KICAgICAgICAgKiB2YXIgZWxlbWVudHMgPSBfLmF0dGVtcHQoZnVuY3Rpb24oc2VsZWN0b3IpIHsKICAgICAgICAgKiAgIHJldHVybiBkb2N1bWVudC5xdWVyeVNlbGVjdG9yQWxsKHNlbGVjdG9yKTsKICAgICAgICAgKiB9LCAnPl8+Jyk7CiAgICAgICAgICoKICAgICAgICAgKiBpZiAoXy5pc0Vycm9yKGVsZW1lbnRzKSkgewogICAgICAgICAqICAgZWxlbWVudHMgPSBbXTsKICAgICAgICAgKiB9CiAgICAgICAgICovCiAgICAgICAgdmFyIGF0dGVtcHQgPSBiYXNlUmVzdChmdW5jdGlvbihmdW5jLCBhcmdzKSB7CiAgICAgICAgICB0cnkgewogICAgICAgICAgICByZXR1cm4gYXBwbHkoZnVuYywgdW5kZWZpbmVkJDEsIGFyZ3MpOwogICAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgICByZXR1cm4gaXNFcnJvcihlKSA/IGUgOiBuZXcgRXJyb3IoZSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8qKgogICAgICAgICAqIEJpbmRzIG1ldGhvZHMgb2YgYW4gb2JqZWN0IHRvIHRoZSBvYmplY3QgaXRzZWxmLCBvdmVyd3JpdGluZyB0aGUgZXhpc3RpbmcKICAgICAgICAgKiBtZXRob2QuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgZG9lc24ndCBzZXQgdGhlICJsZW5ndGgiIHByb3BlcnR5IG9mIGJvdW5kIGZ1bmN0aW9ucy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGJpbmQgYW5kIGFzc2lnbiB0aGUgYm91bmQgbWV0aG9kcyB0by4KICAgICAgICAgKiBAcGFyYW0gey4uLihzdHJpbmd8c3RyaW5nW10pfSBtZXRob2ROYW1lcyBUaGUgb2JqZWN0IG1ldGhvZCBuYW1lcyB0byBiaW5kLgogICAgICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciB2aWV3ID0gewogICAgICAgICAqICAgJ2xhYmVsJzogJ2RvY3MnLAogICAgICAgICAqICAgJ2NsaWNrJzogZnVuY3Rpb24oKSB7CiAgICAgICAgICogICAgIGNvbnNvbGUubG9nKCdjbGlja2VkICcgKyB0aGlzLmxhYmVsKTsKICAgICAgICAgKiAgIH0KICAgICAgICAgKiB9OwogICAgICAgICAqCiAgICAgICAgICogXy5iaW5kQWxsKHZpZXcsIFsnY2xpY2snXSk7CiAgICAgICAgICogalF1ZXJ5KGVsZW1lbnQpLm9uKCdjbGljaycsIHZpZXcuY2xpY2spOwogICAgICAgICAqIC8vID0+IExvZ3MgJ2NsaWNrZWQgZG9jcycgd2hlbiBjbGlja2VkLgogICAgICAgICAqLwogICAgICAgIHZhciBiaW5kQWxsID0gZmxhdFJlc3QoZnVuY3Rpb24ob2JqZWN0LCBtZXRob2ROYW1lcykgewogICAgICAgICAgYXJyYXlFYWNoKG1ldGhvZE5hbWVzLCBmdW5jdGlvbihrZXkpIHsKICAgICAgICAgICAga2V5ID0gdG9LZXkoa2V5KTsKICAgICAgICAgICAgYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCBiaW5kKG9iamVjdFtrZXldLCBvYmplY3QpKTsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICB9KTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaXRlcmF0ZXMgb3ZlciBgcGFpcnNgIGFuZCBpbnZva2VzIHRoZSBjb3JyZXNwb25kaW5nCiAgICAgICAgICogZnVuY3Rpb24gb2YgdGhlIGZpcnN0IHByZWRpY2F0ZSB0byByZXR1cm4gdHJ1dGh5LiBUaGUgcHJlZGljYXRlLWZ1bmN0aW9uCiAgICAgICAgICogcGFpcnMgYXJlIGludm9rZWQgd2l0aCB0aGUgYHRoaXNgIGJpbmRpbmcgYW5kIGFyZ3VtZW50cyBvZiB0aGUgY3JlYXRlZAogICAgICAgICAqIGZ1bmN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBwYWlycyBUaGUgcHJlZGljYXRlLWZ1bmN0aW9uIHBhaXJzLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGNvbXBvc2l0ZSBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIGZ1bmMgPSBfLmNvbmQoWwogICAgICAgICAqICAgW18ubWF0Y2hlcyh7ICdhJzogMSB9KSwgICAgICAgICAgIF8uY29uc3RhbnQoJ21hdGNoZXMgQScpXSwKICAgICAgICAgKiAgIFtfLmNvbmZvcm1zKHsgJ2InOiBfLmlzTnVtYmVyIH0pLCBfLmNvbnN0YW50KCdtYXRjaGVzIEInKV0sCiAgICAgICAgICogICBbXy5zdHViVHJ1ZSwgICAgICAgICAgICAgICAgICAgICAgXy5jb25zdGFudCgnbm8gbWF0Y2gnKV0KICAgICAgICAgKiBdKTsKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMoeyAnYSc6IDEsICdiJzogMiB9KTsKICAgICAgICAgKiAvLyA9PiAnbWF0Y2hlcyBBJwogICAgICAgICAqCiAgICAgICAgICogZnVuYyh7ICdhJzogMCwgJ2InOiAxIH0pOwogICAgICAgICAqIC8vID0+ICdtYXRjaGVzIEInCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jKHsgJ2EnOiAnMScsICdiJzogJzInIH0pOwogICAgICAgICAqIC8vID0+ICdubyBtYXRjaCcKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb25kKHBhaXJzKSB7CiAgICAgICAgICB2YXIgbGVuZ3RoID0gcGFpcnMgPT0gbnVsbCA/IDAgOiBwYWlycy5sZW5ndGgsCiAgICAgICAgICAgICAgdG9JdGVyYXRlZSA9IGdldEl0ZXJhdGVlKCk7CgogICAgICAgICAgcGFpcnMgPSAhbGVuZ3RoID8gW10gOiBhcnJheU1hcChwYWlycywgZnVuY3Rpb24ocGFpcikgewogICAgICAgICAgICBpZiAodHlwZW9mIHBhaXJbMV0gIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoRlVOQ19FUlJPUl9URVhUKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gW3RvSXRlcmF0ZWUocGFpclswXSksIHBhaXJbMV1dOwogICAgICAgICAgfSk7CgogICAgICAgICAgcmV0dXJuIGJhc2VSZXN0KGZ1bmN0aW9uKGFyZ3MpIHsKICAgICAgICAgICAgdmFyIGluZGV4ID0gLTE7CiAgICAgICAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgICAgICAgdmFyIHBhaXIgPSBwYWlyc1tpbmRleF07CiAgICAgICAgICAgICAgaWYgKGFwcGx5KHBhaXJbMF0sIHRoaXMsIGFyZ3MpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gYXBwbHkocGFpclsxXSwgdGhpcywgYXJncyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGludm9rZXMgdGhlIHByZWRpY2F0ZSBwcm9wZXJ0aWVzIG9mIGBzb3VyY2VgIHdpdGgKICAgICAgICAgKiB0aGUgY29ycmVzcG9uZGluZyBwcm9wZXJ0eSB2YWx1ZXMgb2YgYSBnaXZlbiBvYmplY3QsIHJldHVybmluZyBgdHJ1ZWAgaWYKICAgICAgICAgKiBhbGwgcHJlZGljYXRlcyByZXR1cm4gdHJ1dGh5LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhlIGNyZWF0ZWQgZnVuY3Rpb24gaXMgZXF1aXZhbGVudCB0byBgXy5jb25mb3Jtc1RvYCB3aXRoCiAgICAgICAgICogYHNvdXJjZWAgcGFydGlhbGx5IGFwcGxpZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIG9iamVjdCBvZiBwcm9wZXJ0eSBwcmVkaWNhdGVzIHRvIGNvbmZvcm0gdG8uCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbCiAgICAgICAgICogICB7ICdhJzogMiwgJ2InOiAxIH0sCiAgICAgICAgICogICB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAgICAgKiBdOwogICAgICAgICAqCiAgICAgICAgICogXy5maWx0ZXIob2JqZWN0cywgXy5jb25mb3Jtcyh7ICdiJzogZnVuY3Rpb24obikgeyByZXR1cm4gbiA+IDE7IH0gfSkpOwogICAgICAgICAqIC8vID0+IFt7ICdhJzogMSwgJ2InOiAyIH1dCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gY29uZm9ybXMoc291cmNlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZUNvbmZvcm1zKGJhc2VDbG9uZShzb3VyY2UsIENMT05FX0RFRVBfRkxBRykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyBgdmFsdWVgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuNC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byByZXR1cm4gZnJvbSB0aGUgbmV3IGZ1bmN0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGNvbnN0YW50IGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IF8udGltZXMoMiwgXy5jb25zdGFudCh7ICdhJzogMSB9KSk7CiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhvYmplY3RzKTsKICAgICAgICAgKiAvLyA9PiBbeyAnYSc6IDEgfSwgeyAnYSc6IDEgfV0KICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKG9iamVjdHNbMF0gPT09IG9iamVjdHNbMV0pOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBjb25zdGFudCh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGB2YWx1ZWAgdG8gZGV0ZXJtaW5lIHdoZXRoZXIgYSBkZWZhdWx0IHZhbHVlIHNob3VsZCBiZSByZXR1cm5lZCBpbgogICAgICAgICAqIGl0cyBwbGFjZS4gVGhlIGBkZWZhdWx0VmFsdWVgIGlzIHJldHVybmVkIGlmIGB2YWx1ZWAgaXMgYE5hTmAsIGBudWxsYCwKICAgICAgICAgKiBvciBgdW5kZWZpbmVkYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjE0LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICAgICAqIEBwYXJhbSB7Kn0gZGVmYXVsdFZhbHVlIFRoZSBkZWZhdWx0IHZhbHVlLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXNvbHZlZCB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5kZWZhdWx0VG8oMSwgMTApOwogICAgICAgICAqIC8vID0+IDEKICAgICAgICAgKgogICAgICAgICAqIF8uZGVmYXVsdFRvKHVuZGVmaW5lZCwgMTApOwogICAgICAgICAqIC8vID0+IDEwCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZGVmYXVsdFRvKHZhbHVlLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgICAgIHJldHVybiAodmFsdWUgPT0gbnVsbCB8fCB2YWx1ZSAhPT0gdmFsdWUpID8gZGVmYXVsdFZhbHVlIDogdmFsdWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCByZXR1cm5zIHRoZSByZXN1bHQgb2YgaW52b2tpbmcgdGhlIGdpdmVuIGZ1bmN0aW9ucwogICAgICAgICAqIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIHRoZSBjcmVhdGVkIGZ1bmN0aW9uLCB3aGVyZSBlYWNoIHN1Y2Nlc3NpdmUKICAgICAgICAgKiBpbnZvY2F0aW9uIGlzIHN1cHBsaWVkIHRoZSByZXR1cm4gdmFsdWUgb2YgdGhlIHByZXZpb3VzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0gey4uLihGdW5jdGlvbnxGdW5jdGlvbltdKX0gW2Z1bmNzXSBUaGUgZnVuY3Rpb25zIHRvIGludm9rZS4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBjb21wb3NpdGUgZnVuY3Rpb24uCiAgICAgICAgICogQHNlZSBfLmZsb3dSaWdodAogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jdGlvbiBzcXVhcmUobikgewogICAgICAgICAqICAgcmV0dXJuIG4gKiBuOwogICAgICAgICAqIH0KICAgICAgICAgKgogICAgICAgICAqIHZhciBhZGRTcXVhcmUgPSBfLmZsb3coW18uYWRkLCBzcXVhcmVdKTsKICAgICAgICAgKiBhZGRTcXVhcmUoMSwgMik7CiAgICAgICAgICogLy8gPT4gOQogICAgICAgICAqLwogICAgICAgIHZhciBmbG93ID0gY3JlYXRlRmxvdygpOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmZsb3dgIGV4Y2VwdCB0aGF0IGl0IGNyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0CiAgICAgICAgICogaW52b2tlcyB0aGUgZ2l2ZW4gZnVuY3Rpb25zIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHsuLi4oRnVuY3Rpb258RnVuY3Rpb25bXSl9IFtmdW5jc10gVGhlIGZ1bmN0aW9ucyB0byBpbnZva2UuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgY29tcG9zaXRlIGZ1bmN0aW9uLgogICAgICAgICAqIEBzZWUgXy5mbG93CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmN0aW9uIHNxdWFyZShuKSB7CiAgICAgICAgICogICByZXR1cm4gbiAqIG47CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogdmFyIGFkZFNxdWFyZSA9IF8uZmxvd1JpZ2h0KFtzcXVhcmUsIF8uYWRkXSk7CiAgICAgICAgICogYWRkU3F1YXJlKDEsIDIpOwogICAgICAgICAqIC8vID0+IDkKICAgICAgICAgKi8KICAgICAgICB2YXIgZmxvd1JpZ2h0ID0gY3JlYXRlRmxvdyh0cnVlKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgcmV0dXJucyB0aGUgZmlyc3QgYXJndW1lbnQgaXQgcmVjZWl2ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgQW55IHZhbHVlLgogICAgICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIGB2YWx1ZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSB9OwogICAgICAgICAqCiAgICAgICAgICogY29uc29sZS5sb2coXy5pZGVudGl0eShvYmplY3QpID09PSBvYmplY3QpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBpZGVudGl0eSh2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaW52b2tlcyBgZnVuY2Agd2l0aCB0aGUgYXJndW1lbnRzIG9mIHRoZSBjcmVhdGVkCiAgICAgICAgICogZnVuY3Rpb24uIElmIGBmdW5jYCBpcyBhIHByb3BlcnR5IG5hbWUsIHRoZSBjcmVhdGVkIGZ1bmN0aW9uIHJldHVybnMgdGhlCiAgICAgICAgICogcHJvcGVydHkgdmFsdWUgZm9yIGEgZ2l2ZW4gZWxlbWVudC4gSWYgYGZ1bmNgIGlzIGFuIGFycmF5IG9yIG9iamVjdCwgdGhlCiAgICAgICAgICogY3JlYXRlZCBmdW5jdGlvbiByZXR1cm5zIGB0cnVlYCBmb3IgZWxlbWVudHMgdGhhdCBjb250YWluIHRoZSBlcXVpdmFsZW50CiAgICAgICAgICogc291cmNlIHByb3BlcnRpZXMsIG90aGVyd2lzZSBpdCByZXR1cm5zIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7Kn0gW2Z1bmM9Xy5pZGVudGl0eV0gVGhlIHZhbHVlIHRvIGNvbnZlcnQgdG8gYSBjYWxsYmFjay4KICAgICAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIGNhbGxiYWNrLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgJ2FnZSc6IDQwLCAnYWN0aXZlJzogZmFsc2UgfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICAgICAqIF8uZmlsdGVyKHVzZXJzLCBfLml0ZXJhdGVlKHsgJ3VzZXInOiAnYmFybmV5JywgJ2FjdGl2ZSc6IHRydWUgfSkpOwogICAgICAgICAqIC8vID0+IFt7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfV0KICAgICAgICAgKgogICAgICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzUHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLmZpbHRlcih1c2VycywgXy5pdGVyYXRlZShbJ3VzZXInLCAnZnJlZCddKSk7CiAgICAgICAgICogLy8gPT4gW3sgJ3VzZXInOiAnZnJlZCcsICdhZ2UnOiA0MCB9XQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5tYXAodXNlcnMsIF8uaXRlcmF0ZWUoJ3VzZXInKSk7CiAgICAgICAgICogLy8gPT4gWydiYXJuZXknLCAnZnJlZCddCiAgICAgICAgICoKICAgICAgICAgKiAvLyBDcmVhdGUgY3VzdG9tIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgICAgICogXy5pdGVyYXRlZSA9IF8ud3JhcChfLml0ZXJhdGVlLCBmdW5jdGlvbihpdGVyYXRlZSwgZnVuYykgewogICAgICAgICAqICAgcmV0dXJuICFfLmlzUmVnRXhwKGZ1bmMpID8gaXRlcmF0ZWUoZnVuYykgOiBmdW5jdGlvbihzdHJpbmcpIHsKICAgICAgICAgKiAgICAgcmV0dXJuIGZ1bmMudGVzdChzdHJpbmcpOwogICAgICAgICAqICAgfTsKICAgICAgICAgKiB9KTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmlsdGVyKFsnYWJjJywgJ2RlZiddLCAvZWYvKTsKICAgICAgICAgKiAvLyA9PiBbJ2RlZiddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gaXRlcmF0ZWUoZnVuYykgewogICAgICAgICAgcmV0dXJuIGJhc2VJdGVyYXRlZSh0eXBlb2YgZnVuYyA9PSAnZnVuY3Rpb24nID8gZnVuYyA6IGJhc2VDbG9uZShmdW5jLCBDTE9ORV9ERUVQX0ZMQUcpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IHBlcmZvcm1zIGEgcGFydGlhbCBkZWVwIGNvbXBhcmlzb24gYmV0d2VlbiBhIGdpdmVuCiAgICAgICAgICogb2JqZWN0IGFuZCBgc291cmNlYCwgcmV0dXJuaW5nIGB0cnVlYCBpZiB0aGUgZ2l2ZW4gb2JqZWN0IGhhcyBlcXVpdmFsZW50CiAgICAgICAgICogcHJvcGVydHkgdmFsdWVzLCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogVGhlIGNyZWF0ZWQgZnVuY3Rpb24gaXMgZXF1aXZhbGVudCB0byBgXy5pc01hdGNoYCB3aXRoIGBzb3VyY2VgCiAgICAgICAgICogcGFydGlhbGx5IGFwcGxpZWQuCiAgICAgICAgICoKICAgICAgICAgKiBQYXJ0aWFsIGNvbXBhcmlzb25zIHdpbGwgbWF0Y2ggZW1wdHkgYXJyYXkgYW5kIGVtcHR5IG9iamVjdCBgc291cmNlYAogICAgICAgICAqIHZhbHVlcyBhZ2FpbnN0IGFueSBhcnJheSBvciBvYmplY3QgdmFsdWUsIHJlc3BlY3RpdmVseS4gU2VlIGBfLmlzRXF1YWxgCiAgICAgICAgICogZm9yIGEgbGlzdCBvZiBzdXBwb3J0ZWQgdmFsdWUgY29tcGFyaXNvbnMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogTXVsdGlwbGUgdmFsdWVzIGNhbiBiZSBjaGVja2VkIGJ5IGNvbWJpbmluZyBzZXZlcmFsIG1hdGNoZXJzCiAgICAgICAgICogdXNpbmcgYF8ub3ZlclNvbWVgCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIG9iamVjdCBvZiBwcm9wZXJ0eSB2YWx1ZXMgdG8gbWF0Y2guCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbCiAgICAgICAgICogICB7ICdhJzogMSwgJ2InOiAyLCAnYyc6IDMgfSwKICAgICAgICAgKiAgIHsgJ2EnOiA0LCAnYic6IDUsICdjJzogNiB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmlsdGVyKG9iamVjdHMsIF8ubWF0Y2hlcyh7ICdhJzogNCwgJ2MnOiA2IH0pKTsKICAgICAgICAgKiAvLyA9PiBbeyAnYSc6IDQsICdiJzogNSwgJ2MnOiA2IH1dCiAgICAgICAgICoKICAgICAgICAgKiAvLyBDaGVja2luZyBmb3Igc2V2ZXJhbCBwb3NzaWJsZSB2YWx1ZXMKICAgICAgICAgKiBfLmZpbHRlcih1c2VycywgXy5vdmVyU29tZShbXy5tYXRjaGVzKHsgJ2EnOiAxIH0pLCBfLm1hdGNoZXMoeyAnYSc6IDQgfSldKSk7CiAgICAgICAgICogLy8gPT4gW3sgJ2EnOiAxLCAnYic6IDIsICdjJzogMyB9LCB7ICdhJzogNCwgJ2InOiA1LCAnYyc6IDYgfV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXRjaGVzKHNvdXJjZSkgewogICAgICAgICAgcmV0dXJuIGJhc2VNYXRjaGVzKGJhc2VDbG9uZShzb3VyY2UsIENMT05FX0RFRVBfRkxBRykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcGVyZm9ybXMgYSBwYXJ0aWFsIGRlZXAgY29tcGFyaXNvbiBiZXR3ZWVuIHRoZQogICAgICAgICAqIHZhbHVlIGF0IGBwYXRoYCBvZiBhIGdpdmVuIG9iamVjdCB0byBgc3JjVmFsdWVgLCByZXR1cm5pbmcgYHRydWVgIGlmIHRoZQogICAgICAgICAqIG9iamVjdCB2YWx1ZSBpcyBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogUGFydGlhbCBjb21wYXJpc29ucyB3aWxsIG1hdGNoIGVtcHR5IGFycmF5IGFuZCBlbXB0eSBvYmplY3QKICAgICAgICAgKiBgc3JjVmFsdWVgIHZhbHVlcyBhZ2FpbnN0IGFueSBhcnJheSBvciBvYmplY3QgdmFsdWUsIHJlc3BlY3RpdmVseS4gU2VlCiAgICAgICAgICogYF8uaXNFcXVhbGAgZm9yIGEgbGlzdCBvZiBzdXBwb3J0ZWQgdmFsdWUgY29tcGFyaXNvbnMuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogTXVsdGlwbGUgdmFsdWVzIGNhbiBiZSBjaGVja2VkIGJ5IGNvbWJpbmluZyBzZXZlcmFsIG1hdGNoZXJzCiAgICAgICAgICogdXNpbmcgYF8ub3ZlclNvbWVgCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4yLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgICAgICogQHBhcmFtIHsqfSBzcmNWYWx1ZSBUaGUgdmFsdWUgdG8gbWF0Y2guCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbCiAgICAgICAgICogICB7ICdhJzogMSwgJ2InOiAyLCAnYyc6IDMgfSwKICAgICAgICAgKiAgIHsgJ2EnOiA0LCAnYic6IDUsICdjJzogNiB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8uZmluZChvYmplY3RzLCBfLm1hdGNoZXNQcm9wZXJ0eSgnYScsIDQpKTsKICAgICAgICAgKiAvLyA9PiB7ICdhJzogNCwgJ2InOiA1LCAnYyc6IDYgfQogICAgICAgICAqCiAgICAgICAgICogLy8gQ2hlY2tpbmcgZm9yIHNldmVyYWwgcG9zc2libGUgdmFsdWVzCiAgICAgICAgICogXy5maWx0ZXIodXNlcnMsIF8ub3ZlclNvbWUoW18ubWF0Y2hlc1Byb3BlcnR5KCdhJywgMSksIF8ubWF0Y2hlc1Byb3BlcnR5KCdhJywgNCldKSk7CiAgICAgICAgICogLy8gPT4gW3sgJ2EnOiAxLCAnYic6IDIsICdjJzogMyB9LCB7ICdhJzogNCwgJ2InOiA1LCAnYyc6IDYgfV0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXRjaGVzUHJvcGVydHkocGF0aCwgc3JjVmFsdWUpIHsKICAgICAgICAgIHJldHVybiBiYXNlTWF0Y2hlc1Byb3BlcnR5KHBhdGgsIGJhc2VDbG9uZShzcmNWYWx1ZSwgQ0xPTkVfREVFUF9GTEFHKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBpbnZva2VzIHRoZSBtZXRob2QgYXQgYHBhdGhgIG9mIGEgZ2l2ZW4gb2JqZWN0LgogICAgICAgICAqIEFueSBhZGRpdGlvbmFsIGFyZ3VtZW50cyBhcmUgcHJvdmlkZWQgdG8gdGhlIGludm9rZWQgbWV0aG9kLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgbWV0aG9kIHRvIGludm9rZS4KICAgICAgICAgKiBAcGFyYW0gey4uLip9IFthcmdzXSBUaGUgYXJndW1lbnRzIHRvIGludm9rZSB0aGUgbWV0aG9kIHdpdGguCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgaW52b2tlciBmdW5jdGlvbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbCiAgICAgICAgICogICB7ICdhJzogeyAnYic6IF8uY29uc3RhbnQoMikgfSB9LAogICAgICAgICAqICAgeyAnYSc6IHsgJ2InOiBfLmNvbnN0YW50KDEpIH0gfQogICAgICAgICAqIF07CiAgICAgICAgICoKICAgICAgICAgKiBfLm1hcChvYmplY3RzLCBfLm1ldGhvZCgnYS5iJykpOwogICAgICAgICAqIC8vID0+IFsyLCAxXQogICAgICAgICAqCiAgICAgICAgICogXy5tYXAob2JqZWN0cywgXy5tZXRob2QoWydhJywgJ2InXSkpOwogICAgICAgICAqIC8vID0+IFsyLCAxXQogICAgICAgICAqLwogICAgICAgIHZhciBtZXRob2QgPSBiYXNlUmVzdChmdW5jdGlvbihwYXRoLCBhcmdzKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlSW52b2tlKG9iamVjdCwgcGF0aCwgYXJncyk7CiAgICAgICAgICB9OwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3Bwb3NpdGUgb2YgYF8ubWV0aG9kYDsgdGhpcyBtZXRob2QgY3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgaW52b2tlcwogICAgICAgICAqIHRoZSBtZXRob2QgYXQgYSBnaXZlbiBwYXRoIG9mIGBvYmplY3RgLiBBbnkgYWRkaXRpb25hbCBhcmd1bWVudHMgYXJlCiAgICAgICAgICogcHJvdmlkZWQgdG8gdGhlIGludm9rZWQgbWV0aG9kLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBbYXJnc10gVGhlIGFyZ3VtZW50cyB0byBpbnZva2UgdGhlIG1ldGhvZCB3aXRoLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGludm9rZXIgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheSA9IF8udGltZXMoMywgXy5jb25zdGFudCksCiAgICAgICAgICogICAgIG9iamVjdCA9IHsgJ2EnOiBhcnJheSwgJ2InOiBhcnJheSwgJ2MnOiBhcnJheSB9OwogICAgICAgICAqCiAgICAgICAgICogXy5tYXAoWydhWzJdJywgJ2NbMF0nXSwgXy5tZXRob2RPZihvYmplY3QpKTsKICAgICAgICAgKiAvLyA9PiBbMiwgMF0KICAgICAgICAgKgogICAgICAgICAqIF8ubWFwKFtbJ2EnLCAnMiddLCBbJ2MnLCAnMCddXSwgXy5tZXRob2RPZihvYmplY3QpKTsKICAgICAgICAgKiAvLyA9PiBbMiwgMF0KICAgICAgICAgKi8KICAgICAgICB2YXIgbWV0aG9kT2YgPSBiYXNlUmVzdChmdW5jdGlvbihvYmplY3QsIGFyZ3MpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihwYXRoKSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlSW52b2tlKG9iamVjdCwgcGF0aCwgYXJncyk7CiAgICAgICAgICB9OwogICAgICAgIH0pOwoKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGFsbCBvd24gZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgZnVuY3Rpb24gcHJvcGVydGllcyBvZiBhIHNvdXJjZQogICAgICAgICAqIG9iamVjdCB0byB0aGUgZGVzdGluYXRpb24gb2JqZWN0LiBJZiBgb2JqZWN0YCBpcyBhIGZ1bmN0aW9uLCB0aGVuIG1ldGhvZHMKICAgICAgICAgKiBhcmUgYWRkZWQgdG8gaXRzIHByb3RvdHlwZSBhcyB3ZWxsLgogICAgICAgICAqCiAgICAgICAgICogKipOb3RlOioqIFVzZSBgXy5ydW5JbkNvbnRleHRgIHRvIGNyZWF0ZSBhIHByaXN0aW5lIGBsb2Rhc2hgIGZ1bmN0aW9uIHRvCiAgICAgICAgICogYXZvaWQgY29uZmxpY3RzIGNhdXNlZCBieSBtb2RpZnlpbmcgdGhlIG9yaWdpbmFsLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBzaW5jZSAwLjEuMAogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufE9iamVjdH0gW29iamVjdD1sb2Rhc2hdIFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IG9mIGZ1bmN0aW9ucyB0byBhZGQuCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IFtvcHRpb25zPXt9XSBUaGUgb3B0aW9ucyBvYmplY3QuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbb3B0aW9ucy5jaGFpbj10cnVlXSBTcGVjaWZ5IHdoZXRoZXIgbWl4aW5zIGFyZSBjaGFpbmFibGUuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufE9iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogZnVuY3Rpb24gdm93ZWxzKHN0cmluZykgewogICAgICAgICAqICAgcmV0dXJuIF8uZmlsdGVyKHN0cmluZywgZnVuY3Rpb24odikgewogICAgICAgICAqICAgICByZXR1cm4gL1thZWlvdV0vaS50ZXN0KHYpOwogICAgICAgICAqICAgfSk7CiAgICAgICAgICogfQogICAgICAgICAqCiAgICAgICAgICogXy5taXhpbih7ICd2b3dlbHMnOiB2b3dlbHMgfSk7CiAgICAgICAgICogXy52b3dlbHMoJ2ZyZWQnKTsKICAgICAgICAgKiAvLyA9PiBbJ2UnXQogICAgICAgICAqCiAgICAgICAgICogXygnZnJlZCcpLnZvd2VscygpLnZhbHVlKCk7CiAgICAgICAgICogLy8gPT4gWydlJ10KICAgICAgICAgKgogICAgICAgICAqIF8ubWl4aW4oeyAndm93ZWxzJzogdm93ZWxzIH0sIHsgJ2NoYWluJzogZmFsc2UgfSk7CiAgICAgICAgICogXygnZnJlZCcpLnZvd2VscygpOwogICAgICAgICAqIC8vID0+IFsnZSddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbWl4aW4ob2JqZWN0LCBzb3VyY2UsIG9wdGlvbnMpIHsKICAgICAgICAgIHZhciBwcm9wcyA9IGtleXMoc291cmNlKSwKICAgICAgICAgICAgICBtZXRob2ROYW1lcyA9IGJhc2VGdW5jdGlvbnMoc291cmNlLCBwcm9wcyk7CgogICAgICAgICAgaWYgKG9wdGlvbnMgPT0gbnVsbCAmJgogICAgICAgICAgICAgICEoaXNPYmplY3Qoc291cmNlKSAmJiAobWV0aG9kTmFtZXMubGVuZ3RoIHx8ICFwcm9wcy5sZW5ndGgpKSkgewogICAgICAgICAgICBvcHRpb25zID0gc291cmNlOwogICAgICAgICAgICBzb3VyY2UgPSBvYmplY3Q7CiAgICAgICAgICAgIG9iamVjdCA9IHRoaXM7CiAgICAgICAgICAgIG1ldGhvZE5hbWVzID0gYmFzZUZ1bmN0aW9ucyhzb3VyY2UsIGtleXMoc291cmNlKSk7CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgY2hhaW4gPSAhKGlzT2JqZWN0KG9wdGlvbnMpICYmICdjaGFpbicgaW4gb3B0aW9ucykgfHwgISFvcHRpb25zLmNoYWluLAogICAgICAgICAgICAgIGlzRnVuYyA9IGlzRnVuY3Rpb24ob2JqZWN0KTsKCiAgICAgICAgICBhcnJheUVhY2gobWV0aG9kTmFtZXMsIGZ1bmN0aW9uKG1ldGhvZE5hbWUpIHsKICAgICAgICAgICAgdmFyIGZ1bmMgPSBzb3VyY2VbbWV0aG9kTmFtZV07CiAgICAgICAgICAgIG9iamVjdFttZXRob2ROYW1lXSA9IGZ1bmM7CiAgICAgICAgICAgIGlmIChpc0Z1bmMpIHsKICAgICAgICAgICAgICBvYmplY3QucHJvdG90eXBlW21ldGhvZE5hbWVdID0gZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgICB2YXIgY2hhaW5BbGwgPSB0aGlzLl9fY2hhaW5fXzsKICAgICAgICAgICAgICAgIGlmIChjaGFpbiB8fCBjaGFpbkFsbCkgewogICAgICAgICAgICAgICAgICB2YXIgcmVzdWx0ID0gb2JqZWN0KHRoaXMuX193cmFwcGVkX18pLAogICAgICAgICAgICAgICAgICAgICAgYWN0aW9ucyA9IHJlc3VsdC5fX2FjdGlvbnNfXyA9IGNvcHlBcnJheSh0aGlzLl9fYWN0aW9uc19fKTsKCiAgICAgICAgICAgICAgICAgIGFjdGlvbnMucHVzaCh7ICdmdW5jJzogZnVuYywgJ2FyZ3MnOiBhcmd1bWVudHMsICd0aGlzQXJnJzogb2JqZWN0IH0pOwogICAgICAgICAgICAgICAgICByZXN1bHQuX19jaGFpbl9fID0gY2hhaW5BbGw7CiAgICAgICAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gZnVuYy5hcHBseShvYmplY3QsIGFycmF5UHVzaChbdGhpcy52YWx1ZSgpXSwgYXJndW1lbnRzKSk7CiAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CgogICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldmVydHMgdGhlIGBfYCB2YXJpYWJsZSB0byBpdHMgcHJldmlvdXMgdmFsdWUgYW5kIHJldHVybnMgYSByZWZlcmVuY2UgdG8KICAgICAgICAgKiB0aGUgYGxvZGFzaGAgZnVuY3Rpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgYGxvZGFzaGAgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBsb2Rhc2ggPSBfLm5vQ29uZmxpY3QoKTsKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBub0NvbmZsaWN0KCkgewogICAgICAgICAgaWYgKHJvb3QuXyA9PT0gdGhpcykgewogICAgICAgICAgICByb290Ll8gPSBvbGREYXNoOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCByZXR1cm5zIGB1bmRlZmluZWRgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuMy4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy50aW1lcygyLCBfLm5vb3ApOwogICAgICAgICAqIC8vID0+IFt1bmRlZmluZWQsIHVuZGVmaW5lZF0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBub29wKCkgewogICAgICAgICAgLy8gTm8gb3BlcmF0aW9uIHBlcmZvcm1lZC4KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IGdldHMgdGhlIGFyZ3VtZW50IGF0IGluZGV4IGBuYC4gSWYgYG5gIGlzIG5lZ2F0aXZlLAogICAgICAgICAqIHRoZSBudGggYXJndW1lbnQgZnJvbSB0aGUgZW5kIGlzIHJldHVybmVkLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW249MF0gVGhlIGluZGV4IG9mIHRoZSBhcmd1bWVudCB0byByZXR1cm4uCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgcGFzcy10aHJ1IGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZnVuYyA9IF8ubnRoQXJnKDEpOwogICAgICAgICAqIGZ1bmMoJ2EnLCAnYicsICdjJywgJ2QnKTsKICAgICAgICAgKiAvLyA9PiAnYicKICAgICAgICAgKgogICAgICAgICAqIHZhciBmdW5jID0gXy5udGhBcmcoLTIpOwogICAgICAgICAqIGZ1bmMoJ2EnLCAnYicsICdjJywgJ2QnKTsKICAgICAgICAgKiAvLyA9PiAnYycKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBudGhBcmcobikgewogICAgICAgICAgbiA9IHRvSW50ZWdlcihuKTsKICAgICAgICAgIHJldHVybiBiYXNlUmVzdChmdW5jdGlvbihhcmdzKSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlTnRoKGFyZ3MsIG4pOwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBpbnZva2VzIGBpdGVyYXRlZXNgIHdpdGggdGhlIGFyZ3VtZW50cyBpdCByZWNlaXZlcwogICAgICAgICAqIGFuZCByZXR1cm5zIHRoZWlyIHJlc3VsdHMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7Li4uKEZ1bmN0aW9ufEZ1bmN0aW9uW10pfSBbaXRlcmF0ZWVzPVtfLmlkZW50aXR5XV0KICAgICAgICAgKiAgVGhlIGl0ZXJhdGVlcyB0byBpbnZva2UuCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBmdW5jID0gXy5vdmVyKFtNYXRoLm1heCwgTWF0aC5taW5dKTsKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMoMSwgMiwgMywgNCk7CiAgICAgICAgICogLy8gPT4gWzQsIDFdCiAgICAgICAgICovCiAgICAgICAgdmFyIG92ZXIgPSBjcmVhdGVPdmVyKGFycmF5TWFwKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgY2hlY2tzIGlmICoqYWxsKiogb2YgdGhlIGBwcmVkaWNhdGVzYCByZXR1cm4KICAgICAgICAgKiB0cnV0aHkgd2hlbiBpbnZva2VkIHdpdGggdGhlIGFyZ3VtZW50cyBpdCByZWNlaXZlcy4KICAgICAgICAgKgogICAgICAgICAqIEZvbGxvd2luZyBzaG9ydGhhbmRzIGFyZSBwb3NzaWJsZSBmb3IgcHJvdmlkaW5nIHByZWRpY2F0ZXMuCiAgICAgICAgICogUGFzcyBhbiBgT2JqZWN0YCBhbmQgaXQgd2lsbCBiZSB1c2VkIGFzIGFuIHBhcmFtZXRlciBmb3IgYF8ubWF0Y2hlc2AgdG8gY3JlYXRlIHRoZSBwcmVkaWNhdGUuCiAgICAgICAgICogUGFzcyBhbiBgQXJyYXlgIG9mIHBhcmFtZXRlcnMgZm9yIGBfLm1hdGNoZXNQcm9wZXJ0eWAgYW5kIHRoZSBwcmVkaWNhdGUgd2lsbCBiZSBjcmVhdGVkIHVzaW5nIHRoZW0uCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7Li4uKEZ1bmN0aW9ufEZ1bmN0aW9uW10pfSBbcHJlZGljYXRlcz1bXy5pZGVudGl0eV1dCiAgICAgICAgICogIFRoZSBwcmVkaWNhdGVzIHRvIGNoZWNrLgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgZnVuYyA9IF8ub3ZlckV2ZXJ5KFtCb29sZWFuLCBpc0Zpbml0ZV0pOwogICAgICAgICAqCiAgICAgICAgICogZnVuYygnMScpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMobnVsbCk7CiAgICAgICAgICogLy8gPT4gZmFsc2UKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMoTmFOKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIHZhciBvdmVyRXZlcnkgPSBjcmVhdGVPdmVyKGFycmF5RXZlcnkpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCBjaGVja3MgaWYgKiphbnkqKiBvZiB0aGUgYHByZWRpY2F0ZXNgIHJldHVybgogICAgICAgICAqIHRydXRoeSB3aGVuIGludm9rZWQgd2l0aCB0aGUgYXJndW1lbnRzIGl0IHJlY2VpdmVzLgogICAgICAgICAqCiAgICAgICAgICogRm9sbG93aW5nIHNob3J0aGFuZHMgYXJlIHBvc3NpYmxlIGZvciBwcm92aWRpbmcgcHJlZGljYXRlcy4KICAgICAgICAgKiBQYXNzIGFuIGBPYmplY3RgIGFuZCBpdCB3aWxsIGJlIHVzZWQgYXMgYW4gcGFyYW1ldGVyIGZvciBgXy5tYXRjaGVzYCB0byBjcmVhdGUgdGhlIHByZWRpY2F0ZS4KICAgICAgICAgKiBQYXNzIGFuIGBBcnJheWAgb2YgcGFyYW1ldGVycyBmb3IgYF8ubWF0Y2hlc1Byb3BlcnR5YCBhbmQgdGhlIHByZWRpY2F0ZSB3aWxsIGJlIGNyZWF0ZWQgdXNpbmcgdGhlbS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHsuLi4oRnVuY3Rpb258RnVuY3Rpb25bXSl9IFtwcmVkaWNhdGVzPVtfLmlkZW50aXR5XV0KICAgICAgICAgKiAgVGhlIHByZWRpY2F0ZXMgdG8gY2hlY2suCiAgICAgICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBmdW5jID0gXy5vdmVyU29tZShbQm9vbGVhbiwgaXNGaW5pdGVdKTsKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMoJzEnKTsKICAgICAgICAgKiAvLyA9PiB0cnVlCiAgICAgICAgICoKICAgICAgICAgKiBmdW5jKG51bGwpOwogICAgICAgICAqIC8vID0+IHRydWUKICAgICAgICAgKgogICAgICAgICAqIGZ1bmMoTmFOKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG1hdGNoZXNGdW5jID0gXy5vdmVyU29tZShbeyAnYSc6IDEgfSwgeyAnYSc6IDIgfV0pCiAgICAgICAgICogdmFyIG1hdGNoZXNQcm9wZXJ0eUZ1bmMgPSBfLm92ZXJTb21lKFtbJ2EnLCAxXSwgWydhJywgMl1dKQogICAgICAgICAqLwogICAgICAgIHZhciBvdmVyU29tZSA9IGNyZWF0ZU92ZXIoYXJyYXlTb21lKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyB0aGUgdmFsdWUgYXQgYHBhdGhgIG9mIGEgZ2l2ZW4gb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDIuNC4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gZ2V0LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFjY2Vzc29yIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IFsKICAgICAgICAgKiAgIHsgJ2EnOiB7ICdiJzogMiB9IH0sCiAgICAgICAgICogICB7ICdhJzogeyAnYic6IDEgfSB9CiAgICAgICAgICogXTsKICAgICAgICAgKgogICAgICAgICAqIF8ubWFwKG9iamVjdHMsIF8ucHJvcGVydHkoJ2EuYicpKTsKICAgICAgICAgKiAvLyA9PiBbMiwgMV0KICAgICAgICAgKgogICAgICAgICAqIF8ubWFwKF8uc29ydEJ5KG9iamVjdHMsIF8ucHJvcGVydHkoWydhJywgJ2InXSkpLCAnYS5iJyk7CiAgICAgICAgICogLy8gPT4gWzEsIDJdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gcHJvcGVydHkocGF0aCkgewogICAgICAgICAgcmV0dXJuIGlzS2V5KHBhdGgpID8gYmFzZVByb3BlcnR5KHRvS2V5KHBhdGgpKSA6IGJhc2VQcm9wZXJ0eURlZXAocGF0aCk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3Bwb3NpdGUgb2YgYF8ucHJvcGVydHlgOyB0aGlzIG1ldGhvZCBjcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCByZXR1cm5zCiAgICAgICAgICogdGhlIHZhbHVlIGF0IGEgZ2l2ZW4gcGF0aCBvZiBgb2JqZWN0YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFjY2Vzc29yIGZ1bmN0aW9uLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgYXJyYXkgPSBbMCwgMSwgMl0sCiAgICAgICAgICogICAgIG9iamVjdCA9IHsgJ2EnOiBhcnJheSwgJ2InOiBhcnJheSwgJ2MnOiBhcnJheSB9OwogICAgICAgICAqCiAgICAgICAgICogXy5tYXAoWydhWzJdJywgJ2NbMF0nXSwgXy5wcm9wZXJ0eU9mKG9iamVjdCkpOwogICAgICAgICAqIC8vID0+IFsyLCAwXQogICAgICAgICAqCiAgICAgICAgICogXy5tYXAoW1snYScsICcyJ10sIFsnYycsICcwJ11dLCBfLnByb3BlcnR5T2Yob2JqZWN0KSk7CiAgICAgICAgICogLy8gPT4gWzIsIDBdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gcHJvcGVydHlPZihvYmplY3QpIHsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbihwYXRoKSB7CiAgICAgICAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IHVuZGVmaW5lZCQxIDogYmFzZUdldChvYmplY3QsIHBhdGgpOwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgbnVtYmVycyAocG9zaXRpdmUgYW5kL29yIG5lZ2F0aXZlKSBwcm9ncmVzc2luZyBmcm9tCiAgICAgICAgICogYHN0YXJ0YCB1cCB0bywgYnV0IG5vdCBpbmNsdWRpbmcsIGBlbmRgLiBBIHN0ZXAgb2YgYC0xYCBpcyB1c2VkIGlmIGEgbmVnYXRpdmUKICAgICAgICAgKiBgc3RhcnRgIGlzIHNwZWNpZmllZCB3aXRob3V0IGFuIGBlbmRgIG9yIGBzdGVwYC4gSWYgYGVuZGAgaXMgbm90IHNwZWNpZmllZCwKICAgICAgICAgKiBpdCdzIHNldCB0byBgc3RhcnRgIHdpdGggYHN0YXJ0YCB0aGVuIHNldCB0byBgMGAuCiAgICAgICAgICoKICAgICAgICAgKiAqKk5vdGU6KiogSmF2YVNjcmlwdCBmb2xsb3dzIHRoZSBJRUVFLTc1NCBzdGFuZGFyZCBmb3IgcmVzb2x2aW5nCiAgICAgICAgICogZmxvYXRpbmctcG9pbnQgdmFsdWVzIHdoaWNoIGNhbiBwcm9kdWNlIHVuZXhwZWN0ZWQgcmVzdWx0cy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGFydD0wXSBUaGUgc3RhcnQgb2YgdGhlIHJhbmdlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBlbmQgVGhlIGVuZCBvZiB0aGUgcmFuZ2UuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGVwPTFdIFRoZSB2YWx1ZSB0byBpbmNyZW1lbnQgb3IgZGVjcmVtZW50IGJ5LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgcmFuZ2Ugb2YgbnVtYmVycy4KICAgICAgICAgKiBAc2VlIF8uaW5SYW5nZSwgXy5yYW5nZVJpZ2h0CiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucmFuZ2UoNCk7CiAgICAgICAgICogLy8gPT4gWzAsIDEsIDIsIDNdCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlKC00KTsKICAgICAgICAgKiAvLyA9PiBbMCwgLTEsIC0yLCAtM10KICAgICAgICAgKgogICAgICAgICAqIF8ucmFuZ2UoMSwgNSk7CiAgICAgICAgICogLy8gPT4gWzEsIDIsIDMsIDRdCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlKDAsIDIwLCA1KTsKICAgICAgICAgKiAvLyA9PiBbMCwgNSwgMTAsIDE1XQogICAgICAgICAqCiAgICAgICAgICogXy5yYW5nZSgwLCAtNCwgLTEpOwogICAgICAgICAqIC8vID0+IFswLCAtMSwgLTIsIC0zXQogICAgICAgICAqCiAgICAgICAgICogXy5yYW5nZSgxLCA0LCAwKTsKICAgICAgICAgKiAvLyA9PiBbMSwgMSwgMV0KICAgICAgICAgKgogICAgICAgICAqIF8ucmFuZ2UoMCk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKi8KICAgICAgICB2YXIgcmFuZ2UgPSBjcmVhdGVSYW5nZSgpOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnJhbmdlYCBleGNlcHQgdGhhdCBpdCBwb3B1bGF0ZXMgdmFsdWVzIGluCiAgICAgICAgICogZGVzY2VuZGluZyBvcmRlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGFydD0wXSBUaGUgc3RhcnQgb2YgdGhlIHJhbmdlLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBlbmQgVGhlIGVuZCBvZiB0aGUgcmFuZ2UuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGVwPTFdIFRoZSB2YWx1ZSB0byBpbmNyZW1lbnQgb3IgZGVjcmVtZW50IGJ5LgogICAgICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgcmFuZ2Ugb2YgbnVtYmVycy4KICAgICAgICAgKiBAc2VlIF8uaW5SYW5nZSwgXy5yYW5nZQogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlUmlnaHQoNCk7CiAgICAgICAgICogLy8gPT4gWzMsIDIsIDEsIDBdCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlUmlnaHQoLTQpOwogICAgICAgICAqIC8vID0+IFstMywgLTIsIC0xLCAwXQogICAgICAgICAqCiAgICAgICAgICogXy5yYW5nZVJpZ2h0KDEsIDUpOwogICAgICAgICAqIC8vID0+IFs0LCAzLCAyLCAxXQogICAgICAgICAqCiAgICAgICAgICogXy5yYW5nZVJpZ2h0KDAsIDIwLCA1KTsKICAgICAgICAgKiAvLyA9PiBbMTUsIDEwLCA1LCAwXQogICAgICAgICAqCiAgICAgICAgICogXy5yYW5nZVJpZ2h0KDAsIC00LCAtMSk7CiAgICAgICAgICogLy8gPT4gWy0zLCAtMiwgLTEsIDBdCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlUmlnaHQoMSwgNCwgMCk7CiAgICAgICAgICogLy8gPT4gWzEsIDEsIDFdCiAgICAgICAgICoKICAgICAgICAgKiBfLnJhbmdlUmlnaHQoMCk7CiAgICAgICAgICogLy8gPT4gW10KICAgICAgICAgKi8KICAgICAgICB2YXIgcmFuZ2VSaWdodCA9IGNyZWF0ZVJhbmdlKHRydWUpOwoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCByZXR1cm5zIGEgbmV3IGVtcHR5IGFycmF5LgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMTMuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZW1wdHkgYXJyYXkuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBhcnJheXMgPSBfLnRpbWVzKDIsIF8uc3R1YkFycmF5KTsKICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5cyk7CiAgICAgICAgICogLy8gPT4gW1tdLCBbXV0KICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKGFycmF5c1swXSA9PT0gYXJyYXlzWzFdKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0dWJBcnJheSgpIHsKICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIHJldHVybnMgYGZhbHNlYC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjEzLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGBmYWxzZWAuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8udGltZXMoMiwgXy5zdHViRmFsc2UpOwogICAgICAgICAqIC8vID0+IFtmYWxzZSwgZmFsc2VdCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc3R1YkZhbHNlKCkgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgcmV0dXJucyBhIG5ldyBlbXB0eSBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4xMy4wCiAgICAgICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgZW1wdHkgb2JqZWN0LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IF8udGltZXMoMiwgXy5zdHViT2JqZWN0KTsKICAgICAgICAgKgogICAgICAgICAqIGNvbnNvbGUubG9nKG9iamVjdHMpOwogICAgICAgICAqIC8vID0+IFt7fSwge31dCiAgICAgICAgICoKICAgICAgICAgKiBjb25zb2xlLmxvZyhvYmplY3RzWzBdID09PSBvYmplY3RzWzFdKTsKICAgICAgICAgKiAvLyA9PiBmYWxzZQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0dWJPYmplY3QoKSB7CiAgICAgICAgICByZXR1cm4ge307CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCByZXR1cm5zIGFuIGVtcHR5IHN0cmluZy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjEzLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGVtcHR5IHN0cmluZy4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy50aW1lcygyLCBfLnN0dWJTdHJpbmcpOwogICAgICAgICAqIC8vID0+IFsnJywgJyddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc3R1YlN0cmluZygpIHsKICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgbWV0aG9kIHJldHVybnMgYHRydWVgLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMTMuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRpbWVzKDIsIF8uc3R1YlRydWUpOwogICAgICAgICAqIC8vID0+IFt0cnVlLCB0cnVlXQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0dWJUcnVlKCkgewogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBJbnZva2VzIHRoZSBpdGVyYXRlZSBgbmAgdGltZXMsIHJldHVybmluZyBhbiBhcnJheSBvZiB0aGUgcmVzdWx0cyBvZgogICAgICAgICAqIGVhY2ggaW52b2NhdGlvbi4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ7IChpbmRleCkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBuIFRoZSBudW1iZXIgb2YgdGltZXMgdG8gaW52b2tlIGBpdGVyYXRlZWAuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiByZXN1bHRzLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRpbWVzKDMsIFN0cmluZyk7CiAgICAgICAgICogLy8gPT4gWycwJywgJzEnLCAnMiddCiAgICAgICAgICoKICAgICAgICAgKiAgXy50aW1lcyg0LCBfLmNvbnN0YW50KDApKTsKICAgICAgICAgKiAvLyA9PiBbMCwgMCwgMCwgMF0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB0aW1lcyhuLCBpdGVyYXRlZSkgewogICAgICAgICAgbiA9IHRvSW50ZWdlcihuKTsKICAgICAgICAgIGlmIChuIDwgMSB8fCBuID4gTUFYX1NBRkVfSU5URUdFUikgewogICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICB9CiAgICAgICAgICB2YXIgaW5kZXggPSBNQVhfQVJSQVlfTEVOR1RILAogICAgICAgICAgICAgIGxlbmd0aCA9IG5hdGl2ZU1pbihuLCBNQVhfQVJSQVlfTEVOR1RIKTsKCiAgICAgICAgICBpdGVyYXRlZSA9IGdldEl0ZXJhdGVlKGl0ZXJhdGVlKTsKICAgICAgICAgIG4gLT0gTUFYX0FSUkFZX0xFTkdUSDsKCiAgICAgICAgICB2YXIgcmVzdWx0ID0gYmFzZVRpbWVzKGxlbmd0aCwgaXRlcmF0ZWUpOwogICAgICAgICAgd2hpbGUgKCsraW5kZXggPCBuKSB7CiAgICAgICAgICAgIGl0ZXJhdGVlKGluZGV4KTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGEgcHJvcGVydHkgcGF0aCBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29udmVydC4KICAgICAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBwcm9wZXJ0eSBwYXRoIGFycmF5LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLnRvUGF0aCgnYS5iLmMnKTsKICAgICAgICAgKiAvLyA9PiBbJ2EnLCAnYicsICdjJ10KICAgICAgICAgKgogICAgICAgICAqIF8udG9QYXRoKCdhWzBdLmIuYycpOwogICAgICAgICAqIC8vID0+IFsnYScsICcwJywgJ2InLCAnYyddCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gdG9QYXRoKHZhbHVlKSB7CiAgICAgICAgICBpZiAoaXNBcnJheSh2YWx1ZSkpIHsKICAgICAgICAgICAgcmV0dXJuIGFycmF5TWFwKHZhbHVlLCB0b0tleSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gaXNTeW1ib2wodmFsdWUpID8gW3ZhbHVlXSA6IGNvcHlBcnJheShzdHJpbmdUb1BhdGgodG9TdHJpbmcodmFsdWUpKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBHZW5lcmF0ZXMgYSB1bmlxdWUgSUQuIElmIGBwcmVmaXhgIGlzIGdpdmVuLCB0aGUgSUQgaXMgYXBwZW5kZWQgdG8gaXQuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQHNpbmNlIDAuMS4wCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAY2F0ZWdvcnkgVXRpbAogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbcHJlZml4PScnXSBUaGUgdmFsdWUgdG8gcHJlZml4IHRoZSBJRCB3aXRoLgogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIHVuaXF1ZSBJRC4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy51bmlxdWVJZCgnY29udGFjdF8nKTsKICAgICAgICAgKiAvLyA9PiAnY29udGFjdF8xMDQnCiAgICAgICAgICoKICAgICAgICAgKiBfLnVuaXF1ZUlkKCk7CiAgICAgICAgICogLy8gPT4gJzEwNScKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiB1bmlxdWVJZChwcmVmaXgpIHsKICAgICAgICAgIHZhciBpZCA9ICsraWRDb3VudGVyOwogICAgICAgICAgcmV0dXJuIHRvU3RyaW5nKHByZWZpeCkgKyBpZDsKICAgICAgICB9CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyB0d28gbnVtYmVycy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGF1Z2VuZCBUaGUgZmlyc3QgbnVtYmVyIGluIGFuIGFkZGl0aW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBhZGRlbmQgVGhlIHNlY29uZCBudW1iZXIgaW4gYW4gYWRkaXRpb24uCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgdG90YWwuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uYWRkKDYsIDQpOwogICAgICAgICAqIC8vID0+IDEwCiAgICAgICAgICovCiAgICAgICAgdmFyIGFkZCA9IGNyZWF0ZU1hdGhPcGVyYXRpb24oZnVuY3Rpb24oYXVnZW5kLCBhZGRlbmQpIHsKICAgICAgICAgIHJldHVybiBhdWdlbmQgKyBhZGRlbmQ7CiAgICAgICAgfSwgMCk7CgogICAgICAgIC8qKgogICAgICAgICAqIENvbXB1dGVzIGBudW1iZXJgIHJvdW5kZWQgdXAgdG8gYHByZWNpc2lvbmAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4xMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE1hdGgKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbnVtYmVyIFRoZSBudW1iZXIgdG8gcm91bmQgdXAuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtwcmVjaXNpb249MF0gVGhlIHByZWNpc2lvbiB0byByb3VuZCB1cCB0by4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSByb3VuZGVkIHVwIG51bWJlci4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5jZWlsKDQuMDA2KTsKICAgICAgICAgKiAvLyA9PiA1CiAgICAgICAgICoKICAgICAgICAgKiBfLmNlaWwoNi4wMDQsIDIpOwogICAgICAgICAqIC8vID0+IDYuMDEKICAgICAgICAgKgogICAgICAgICAqIF8uY2VpbCg2MDQwLCAtMik7CiAgICAgICAgICogLy8gPT4gNjEwMAogICAgICAgICAqLwogICAgICAgIHZhciBjZWlsID0gY3JlYXRlUm91bmQoJ2NlaWwnKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogRGl2aWRlIHR3byBudW1iZXJzLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuNy4wCiAgICAgICAgICogQGNhdGVnb3J5IE1hdGgKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gZGl2aWRlbmQgVGhlIGZpcnN0IG51bWJlciBpbiBhIGRpdmlzaW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBkaXZpc29yIFRoZSBzZWNvbmQgbnVtYmVyIGluIGEgZGl2aXNpb24uCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgcXVvdGllbnQuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uZGl2aWRlKDYsIDQpOwogICAgICAgICAqIC8vID0+IDEuNQogICAgICAgICAqLwogICAgICAgIHZhciBkaXZpZGUgPSBjcmVhdGVNYXRoT3BlcmF0aW9uKGZ1bmN0aW9uKGRpdmlkZW5kLCBkaXZpc29yKSB7CiAgICAgICAgICByZXR1cm4gZGl2aWRlbmQgLyBkaXZpc29yOwogICAgICAgIH0sIDEpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyBgbnVtYmVyYCByb3VuZGVkIGRvd24gdG8gYHByZWNpc2lvbmAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgMy4xMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE1hdGgKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbnVtYmVyIFRoZSBudW1iZXIgdG8gcm91bmQgZG93bi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3ByZWNpc2lvbj0wXSBUaGUgcHJlY2lzaW9uIHRvIHJvdW5kIGRvd24gdG8uCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgcm91bmRlZCBkb3duIG51bWJlci4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5mbG9vcig0LjAwNik7CiAgICAgICAgICogLy8gPT4gNAogICAgICAgICAqCiAgICAgICAgICogXy5mbG9vcigwLjA0NiwgMik7CiAgICAgICAgICogLy8gPT4gMC4wNAogICAgICAgICAqCiAgICAgICAgICogXy5mbG9vcig0MDYwLCAtMik7CiAgICAgICAgICogLy8gPT4gNDAwMAogICAgICAgICAqLwogICAgICAgIHZhciBmbG9vciA9IGNyZWF0ZVJvdW5kKCdmbG9vcicpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgbWF4aW11bSB2YWx1ZSBvZiBgYXJyYXlgLiBJZiBgYXJyYXlgIGlzIGVtcHR5IG9yIGZhbHNleSwKICAgICAgICAgKiBgdW5kZWZpbmVkYCBpcyByZXR1cm5lZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWF4aW11bSB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5tYXgoWzQsIDIsIDgsIDZdKTsKICAgICAgICAgKiAvLyA9PiA4CiAgICAgICAgICoKICAgICAgICAgKiBfLm1heChbXSk7CiAgICAgICAgICogLy8gPT4gdW5kZWZpbmVkCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbWF4KGFycmF5KSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlRXh0cmVtdW0oYXJyYXksIGlkZW50aXR5LCBiYXNlR3QpCiAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLm1heGAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgIHdoaWNoIGlzCiAgICAgICAgICogaW52b2tlZCBmb3IgZWFjaCBlbGVtZW50IGluIGBhcnJheWAgdG8gZ2VuZXJhdGUgdGhlIGNyaXRlcmlvbiBieSB3aGljaAogICAgICAgICAqIHRoZSB2YWx1ZSBpcyByYW5rZWQuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE1hdGgKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWF4aW11bSB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAnbic6IDEgfSwgeyAnbic6IDIgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLm1heEJ5KG9iamVjdHMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8ubjsgfSk7CiAgICAgICAgICogLy8gPT4geyAnbic6IDIgfQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5tYXhCeShvYmplY3RzLCAnbicpOwogICAgICAgICAqIC8vID0+IHsgJ24nOiAyIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtYXhCeShhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VFeHRyZW11bShhcnJheSwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpLCBiYXNlR3QpCiAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgbWVhbiBvZiB0aGUgdmFsdWVzIGluIGBhcnJheWAuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgbWVhbi4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5tZWFuKFs0LCAyLCA4LCA2XSk7CiAgICAgICAgICogLy8gPT4gNQogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIG1lYW4oYXJyYXkpIHsKICAgICAgICAgIHJldHVybiBiYXNlTWVhbihhcnJheSwgaWRlbnRpdHkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgaXMgbGlrZSBgXy5tZWFuYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIGBpdGVyYXRlZWAgd2hpY2ggaXMKICAgICAgICAgKiBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgaW4gYGFycmF5YCB0byBnZW5lcmF0ZSB0aGUgdmFsdWUgdG8gYmUgYXZlcmFnZWQuCiAgICAgICAgICogVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCBvbmUgYXJndW1lbnQ6ICh2YWx1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC43LjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBpdGVyYXRlZSBpbnZva2VkIHBlciBlbGVtZW50LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIG1lYW4uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIHZhciBvYmplY3RzID0gW3sgJ24nOiA0IH0sIHsgJ24nOiAyIH0sIHsgJ24nOiA4IH0sIHsgJ24nOiA2IH1dOwogICAgICAgICAqCiAgICAgICAgICogXy5tZWFuQnkob2JqZWN0cywgZnVuY3Rpb24obykgeyByZXR1cm4gby5uOyB9KTsKICAgICAgICAgKiAvLyA9PiA1CiAgICAgICAgICoKICAgICAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAgICAgKiBfLm1lYW5CeShvYmplY3RzLCAnbicpOwogICAgICAgICAqIC8vID0+IDUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtZWFuQnkoYXJyYXksIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gYmFzZU1lYW4oYXJyYXksIGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAyKSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgbWluaW11bSB2YWx1ZSBvZiBgYXJyYXlgLiBJZiBgYXJyYXlgIGlzIGVtcHR5IG9yIGZhbHNleSwKICAgICAgICAgKiBgdW5kZWZpbmVkYCBpcyByZXR1cm5lZC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAc2luY2UgMC4xLjAKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWluaW11bSB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogXy5taW4oWzQsIDIsIDgsIDZdKTsKICAgICAgICAgKiAvLyA9PiAyCiAgICAgICAgICoKICAgICAgICAgKiBfLm1pbihbXSk7CiAgICAgICAgICogLy8gPT4gdW5kZWZpbmVkCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gbWluKGFycmF5KSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlRXh0cmVtdW0oYXJyYXksIGlkZW50aXR5LCBiYXNlTHQpCiAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLm1pbmAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgIHdoaWNoIGlzCiAgICAgICAgICogaW52b2tlZCBmb3IgZWFjaCBlbGVtZW50IGluIGBhcnJheWAgdG8gZ2VuZXJhdGUgdGhlIGNyaXRlcmlvbiBieSB3aGljaAogICAgICAgICAqIHRoZSB2YWx1ZSBpcyByYW5rZWQuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OiAodmFsdWUpLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDQuMC4wCiAgICAgICAgICogQGNhdGVnb3J5IE1hdGgKICAgICAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaXRlcmF0ZSBvdmVyLgogICAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWluaW11bSB2YWx1ZS4KICAgICAgICAgKiBAZXhhbXBsZQogICAgICAgICAqCiAgICAgICAgICogdmFyIG9iamVjdHMgPSBbeyAnbic6IDEgfSwgeyAnbic6IDIgfV07CiAgICAgICAgICoKICAgICAgICAgKiBfLm1pbkJ5KG9iamVjdHMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8ubjsgfSk7CiAgICAgICAgICogLy8gPT4geyAnbic6IDEgfQogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5taW5CeShvYmplY3RzLCAnbicpOwogICAgICAgICAqIC8vID0+IHsgJ24nOiAxIH0KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBtaW5CeShhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VFeHRyZW11bShhcnJheSwgZ2V0SXRlcmF0ZWUoaXRlcmF0ZWUsIDIpLCBiYXNlTHQpCiAgICAgICAgICAgIDogdW5kZWZpbmVkJDE7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBNdWx0aXBseSB0d28gbnVtYmVycy4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjcuMAogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IG11bHRpcGxpZXIgVGhlIGZpcnN0IG51bWJlciBpbiBhIG11bHRpcGxpY2F0aW9uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBtdWx0aXBsaWNhbmQgVGhlIHNlY29uZCBudW1iZXIgaW4gYSBtdWx0aXBsaWNhdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBwcm9kdWN0LgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiBfLm11bHRpcGx5KDYsIDQpOwogICAgICAgICAqIC8vID0+IDI0CiAgICAgICAgICovCiAgICAgICAgdmFyIG11bHRpcGx5ID0gY3JlYXRlTWF0aE9wZXJhdGlvbihmdW5jdGlvbihtdWx0aXBsaWVyLCBtdWx0aXBsaWNhbmQpIHsKICAgICAgICAgIHJldHVybiBtdWx0aXBsaWVyICogbXVsdGlwbGljYW5kOwogICAgICAgIH0sIDEpOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyBgbnVtYmVyYCByb3VuZGVkIHRvIGBwcmVjaXNpb25gLgogICAgICAgICAqCiAgICAgICAgICogQHN0YXRpYwogICAgICAgICAqIEBtZW1iZXJPZiBfCiAgICAgICAgICogQHNpbmNlIDMuMTAuMAogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IG51bWJlciBUaGUgbnVtYmVyIHRvIHJvdW5kLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbcHJlY2lzaW9uPTBdIFRoZSBwcmVjaXNpb24gdG8gcm91bmQgdG8uCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgcm91bmRlZCBudW1iZXIuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8ucm91bmQoNC4wMDYpOwogICAgICAgICAqIC8vID0+IDQKICAgICAgICAgKgogICAgICAgICAqIF8ucm91bmQoNC4wMDYsIDIpOwogICAgICAgICAqIC8vID0+IDQuMDEKICAgICAgICAgKgogICAgICAgICAqIF8ucm91bmQoNDA2MCwgLTIpOwogICAgICAgICAqIC8vID0+IDQxMDAKICAgICAgICAgKi8KICAgICAgICB2YXIgcm91bmQgPSBjcmVhdGVSb3VuZCgncm91bmQnKTsKCiAgICAgICAgLyoqCiAgICAgICAgICogU3VidHJhY3QgdHdvIG51bWJlcnMuCiAgICAgICAgICoKICAgICAgICAgKiBAc3RhdGljCiAgICAgICAgICogQG1lbWJlck9mIF8KICAgICAgICAgKiBAc2luY2UgNC4wLjAKICAgICAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBtaW51ZW5kIFRoZSBmaXJzdCBudW1iZXIgaW4gYSBzdWJ0cmFjdGlvbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gc3VidHJhaGVuZCBUaGUgc2Vjb25kIG51bWJlciBpbiBhIHN1YnRyYWN0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGRpZmZlcmVuY2UuCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uc3VidHJhY3QoNiwgNCk7CiAgICAgICAgICogLy8gPT4gMgogICAgICAgICAqLwogICAgICAgIHZhciBzdWJ0cmFjdCA9IGNyZWF0ZU1hdGhPcGVyYXRpb24oZnVuY3Rpb24obWludWVuZCwgc3VidHJhaGVuZCkgewogICAgICAgICAgcmV0dXJuIG1pbnVlbmQgLSBzdWJ0cmFoZW5kOwogICAgICAgIH0sIDApOwoKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgc3VtIG9mIHRoZSB2YWx1ZXMgaW4gYGFycmF5YC4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSAzLjQuMAogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzdW0uCiAgICAgICAgICogQGV4YW1wbGUKICAgICAgICAgKgogICAgICAgICAqIF8uc3VtKFs0LCAyLCA4LCA2XSk7CiAgICAgICAgICogLy8gPT4gMjAKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBzdW0oYXJyYXkpIHsKICAgICAgICAgIHJldHVybiAoYXJyYXkgJiYgYXJyYXkubGVuZ3RoKQogICAgICAgICAgICA/IGJhc2VTdW0oYXJyYXksIGlkZW50aXR5KQogICAgICAgICAgICA6IDA7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLnN1bWAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgIHdoaWNoIGlzCiAgICAgICAgICogaW52b2tlZCBmb3IgZWFjaCBlbGVtZW50IGluIGBhcnJheWAgdG8gZ2VuZXJhdGUgdGhlIHZhbHVlIHRvIGJlIHN1bW1lZC4KICAgICAgICAgKiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEBzaW5jZSA0LjAuMAogICAgICAgICAqIEBjYXRlZ29yeSBNYXRoCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgc3VtLgogICAgICAgICAqIEBleGFtcGxlCiAgICAgICAgICoKICAgICAgICAgKiB2YXIgb2JqZWN0cyA9IFt7ICduJzogNCB9LCB7ICduJzogMiB9LCB7ICduJzogOCB9LCB7ICduJzogNiB9XTsKICAgICAgICAgKgogICAgICAgICAqIF8uc3VtQnkob2JqZWN0cywgZnVuY3Rpb24obykgeyByZXR1cm4gby5uOyB9KTsKICAgICAgICAgKiAvLyA9PiAyMAogICAgICAgICAqCiAgICAgICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgICAgICogXy5zdW1CeShvYmplY3RzLCAnbicpOwogICAgICAgICAqIC8vID0+IDIwCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gc3VtQnkoYXJyYXksIGl0ZXJhdGVlKSB7CiAgICAgICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICAgICAgPyBiYXNlU3VtKGFycmF5LCBnZXRJdGVyYXRlZShpdGVyYXRlZSwgMikpCiAgICAgICAgICAgIDogMDsKICAgICAgICB9CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLy8gQWRkIG1ldGhvZHMgdGhhdCByZXR1cm4gd3JhcHBlZCB2YWx1ZXMgaW4gY2hhaW4gc2VxdWVuY2VzLgogICAgICAgIGxvZGFzaC5hZnRlciA9IGFmdGVyOwogICAgICAgIGxvZGFzaC5hcnkgPSBhcnk7CiAgICAgICAgbG9kYXNoLmFzc2lnbiA9IGFzc2lnbjsKICAgICAgICBsb2Rhc2guYXNzaWduSW4gPSBhc3NpZ25JbjsKICAgICAgICBsb2Rhc2guYXNzaWduSW5XaXRoID0gYXNzaWduSW5XaXRoOwogICAgICAgIGxvZGFzaC5hc3NpZ25XaXRoID0gYXNzaWduV2l0aDsKICAgICAgICBsb2Rhc2guYXQgPSBhdDsKICAgICAgICBsb2Rhc2guYmVmb3JlID0gYmVmb3JlOwogICAgICAgIGxvZGFzaC5iaW5kID0gYmluZDsKICAgICAgICBsb2Rhc2guYmluZEFsbCA9IGJpbmRBbGw7CiAgICAgICAgbG9kYXNoLmJpbmRLZXkgPSBiaW5kS2V5OwogICAgICAgIGxvZGFzaC5jYXN0QXJyYXkgPSBjYXN0QXJyYXk7CiAgICAgICAgbG9kYXNoLmNoYWluID0gY2hhaW47CiAgICAgICAgbG9kYXNoLmNodW5rID0gY2h1bms7CiAgICAgICAgbG9kYXNoLmNvbXBhY3QgPSBjb21wYWN0OwogICAgICAgIGxvZGFzaC5jb25jYXQgPSBjb25jYXQ7CiAgICAgICAgbG9kYXNoLmNvbmQgPSBjb25kOwogICAgICAgIGxvZGFzaC5jb25mb3JtcyA9IGNvbmZvcm1zOwogICAgICAgIGxvZGFzaC5jb25zdGFudCA9IGNvbnN0YW50OwogICAgICAgIGxvZGFzaC5jb3VudEJ5ID0gY291bnRCeTsKICAgICAgICBsb2Rhc2guY3JlYXRlID0gY3JlYXRlOwogICAgICAgIGxvZGFzaC5jdXJyeSA9IGN1cnJ5OwogICAgICAgIGxvZGFzaC5jdXJyeVJpZ2h0ID0gY3VycnlSaWdodDsKICAgICAgICBsb2Rhc2guZGVib3VuY2UgPSBkZWJvdW5jZTsKICAgICAgICBsb2Rhc2guZGVmYXVsdHMgPSBkZWZhdWx0czsKICAgICAgICBsb2Rhc2guZGVmYXVsdHNEZWVwID0gZGVmYXVsdHNEZWVwOwogICAgICAgIGxvZGFzaC5kZWZlciA9IGRlZmVyOwogICAgICAgIGxvZGFzaC5kZWxheSA9IGRlbGF5OwogICAgICAgIGxvZGFzaC5kaWZmZXJlbmNlID0gZGlmZmVyZW5jZTsKICAgICAgICBsb2Rhc2guZGlmZmVyZW5jZUJ5ID0gZGlmZmVyZW5jZUJ5OwogICAgICAgIGxvZGFzaC5kaWZmZXJlbmNlV2l0aCA9IGRpZmZlcmVuY2VXaXRoOwogICAgICAgIGxvZGFzaC5kcm9wID0gZHJvcDsKICAgICAgICBsb2Rhc2guZHJvcFJpZ2h0ID0gZHJvcFJpZ2h0OwogICAgICAgIGxvZGFzaC5kcm9wUmlnaHRXaGlsZSA9IGRyb3BSaWdodFdoaWxlOwogICAgICAgIGxvZGFzaC5kcm9wV2hpbGUgPSBkcm9wV2hpbGU7CiAgICAgICAgbG9kYXNoLmZpbGwgPSBmaWxsOwogICAgICAgIGxvZGFzaC5maWx0ZXIgPSBmaWx0ZXI7CiAgICAgICAgbG9kYXNoLmZsYXRNYXAgPSBmbGF0TWFwOwogICAgICAgIGxvZGFzaC5mbGF0TWFwRGVlcCA9IGZsYXRNYXBEZWVwOwogICAgICAgIGxvZGFzaC5mbGF0TWFwRGVwdGggPSBmbGF0TWFwRGVwdGg7CiAgICAgICAgbG9kYXNoLmZsYXR0ZW4gPSBmbGF0dGVuOwogICAgICAgIGxvZGFzaC5mbGF0dGVuRGVlcCA9IGZsYXR0ZW5EZWVwOwogICAgICAgIGxvZGFzaC5mbGF0dGVuRGVwdGggPSBmbGF0dGVuRGVwdGg7CiAgICAgICAgbG9kYXNoLmZsaXAgPSBmbGlwOwogICAgICAgIGxvZGFzaC5mbG93ID0gZmxvdzsKICAgICAgICBsb2Rhc2guZmxvd1JpZ2h0ID0gZmxvd1JpZ2h0OwogICAgICAgIGxvZGFzaC5mcm9tUGFpcnMgPSBmcm9tUGFpcnM7CiAgICAgICAgbG9kYXNoLmZ1bmN0aW9ucyA9IGZ1bmN0aW9uczsKICAgICAgICBsb2Rhc2guZnVuY3Rpb25zSW4gPSBmdW5jdGlvbnNJbjsKICAgICAgICBsb2Rhc2guZ3JvdXBCeSA9IGdyb3VwQnk7CiAgICAgICAgbG9kYXNoLmluaXRpYWwgPSBpbml0aWFsOwogICAgICAgIGxvZGFzaC5pbnRlcnNlY3Rpb24gPSBpbnRlcnNlY3Rpb247CiAgICAgICAgbG9kYXNoLmludGVyc2VjdGlvbkJ5ID0gaW50ZXJzZWN0aW9uQnk7CiAgICAgICAgbG9kYXNoLmludGVyc2VjdGlvbldpdGggPSBpbnRlcnNlY3Rpb25XaXRoOwogICAgICAgIGxvZGFzaC5pbnZlcnQgPSBpbnZlcnQ7CiAgICAgICAgbG9kYXNoLmludmVydEJ5ID0gaW52ZXJ0Qnk7CiAgICAgICAgbG9kYXNoLmludm9rZU1hcCA9IGludm9rZU1hcDsKICAgICAgICBsb2Rhc2guaXRlcmF0ZWUgPSBpdGVyYXRlZTsKICAgICAgICBsb2Rhc2gua2V5QnkgPSBrZXlCeTsKICAgICAgICBsb2Rhc2gua2V5cyA9IGtleXM7CiAgICAgICAgbG9kYXNoLmtleXNJbiA9IGtleXNJbjsKICAgICAgICBsb2Rhc2gubWFwID0gbWFwOwogICAgICAgIGxvZGFzaC5tYXBLZXlzID0gbWFwS2V5czsKICAgICAgICBsb2Rhc2gubWFwVmFsdWVzID0gbWFwVmFsdWVzOwogICAgICAgIGxvZGFzaC5tYXRjaGVzID0gbWF0Y2hlczsKICAgICAgICBsb2Rhc2gubWF0Y2hlc1Byb3BlcnR5ID0gbWF0Y2hlc1Byb3BlcnR5OwogICAgICAgIGxvZGFzaC5tZW1vaXplID0gbWVtb2l6ZTsKICAgICAgICBsb2Rhc2gubWVyZ2UgPSBtZXJnZTsKICAgICAgICBsb2Rhc2gubWVyZ2VXaXRoID0gbWVyZ2VXaXRoOwogICAgICAgIGxvZGFzaC5tZXRob2QgPSBtZXRob2Q7CiAgICAgICAgbG9kYXNoLm1ldGhvZE9mID0gbWV0aG9kT2Y7CiAgICAgICAgbG9kYXNoLm1peGluID0gbWl4aW47CiAgICAgICAgbG9kYXNoLm5lZ2F0ZSA9IG5lZ2F0ZTsKICAgICAgICBsb2Rhc2gubnRoQXJnID0gbnRoQXJnOwogICAgICAgIGxvZGFzaC5vbWl0ID0gb21pdDsKICAgICAgICBsb2Rhc2gub21pdEJ5ID0gb21pdEJ5OwogICAgICAgIGxvZGFzaC5vbmNlID0gb25jZTsKICAgICAgICBsb2Rhc2gub3JkZXJCeSA9IG9yZGVyQnk7CiAgICAgICAgbG9kYXNoLm92ZXIgPSBvdmVyOwogICAgICAgIGxvZGFzaC5vdmVyQXJncyA9IG92ZXJBcmdzOwogICAgICAgIGxvZGFzaC5vdmVyRXZlcnkgPSBvdmVyRXZlcnk7CiAgICAgICAgbG9kYXNoLm92ZXJTb21lID0gb3ZlclNvbWU7CiAgICAgICAgbG9kYXNoLnBhcnRpYWwgPSBwYXJ0aWFsOwogICAgICAgIGxvZGFzaC5wYXJ0aWFsUmlnaHQgPSBwYXJ0aWFsUmlnaHQ7CiAgICAgICAgbG9kYXNoLnBhcnRpdGlvbiA9IHBhcnRpdGlvbjsKICAgICAgICBsb2Rhc2gucGljayA9IHBpY2s7CiAgICAgICAgbG9kYXNoLnBpY2tCeSA9IHBpY2tCeTsKICAgICAgICBsb2Rhc2gucHJvcGVydHkgPSBwcm9wZXJ0eTsKICAgICAgICBsb2Rhc2gucHJvcGVydHlPZiA9IHByb3BlcnR5T2Y7CiAgICAgICAgbG9kYXNoLnB1bGwgPSBwdWxsOwogICAgICAgIGxvZGFzaC5wdWxsQWxsID0gcHVsbEFsbDsKICAgICAgICBsb2Rhc2gucHVsbEFsbEJ5ID0gcHVsbEFsbEJ5OwogICAgICAgIGxvZGFzaC5wdWxsQWxsV2l0aCA9IHB1bGxBbGxXaXRoOwogICAgICAgIGxvZGFzaC5wdWxsQXQgPSBwdWxsQXQ7CiAgICAgICAgbG9kYXNoLnJhbmdlID0gcmFuZ2U7CiAgICAgICAgbG9kYXNoLnJhbmdlUmlnaHQgPSByYW5nZVJpZ2h0OwogICAgICAgIGxvZGFzaC5yZWFyZyA9IHJlYXJnOwogICAgICAgIGxvZGFzaC5yZWplY3QgPSByZWplY3Q7CiAgICAgICAgbG9kYXNoLnJlbW92ZSA9IHJlbW92ZTsKICAgICAgICBsb2Rhc2gucmVzdCA9IHJlc3Q7CiAgICAgICAgbG9kYXNoLnJldmVyc2UgPSByZXZlcnNlOwogICAgICAgIGxvZGFzaC5zYW1wbGVTaXplID0gc2FtcGxlU2l6ZTsKICAgICAgICBsb2Rhc2guc2V0ID0gc2V0OwogICAgICAgIGxvZGFzaC5zZXRXaXRoID0gc2V0V2l0aDsKICAgICAgICBsb2Rhc2guc2h1ZmZsZSA9IHNodWZmbGU7CiAgICAgICAgbG9kYXNoLnNsaWNlID0gc2xpY2U7CiAgICAgICAgbG9kYXNoLnNvcnRCeSA9IHNvcnRCeTsKICAgICAgICBsb2Rhc2guc29ydGVkVW5pcSA9IHNvcnRlZFVuaXE7CiAgICAgICAgbG9kYXNoLnNvcnRlZFVuaXFCeSA9IHNvcnRlZFVuaXFCeTsKICAgICAgICBsb2Rhc2guc3BsaXQgPSBzcGxpdDsKICAgICAgICBsb2Rhc2guc3ByZWFkID0gc3ByZWFkOwogICAgICAgIGxvZGFzaC50YWlsID0gdGFpbDsKICAgICAgICBsb2Rhc2gudGFrZSA9IHRha2U7CiAgICAgICAgbG9kYXNoLnRha2VSaWdodCA9IHRha2VSaWdodDsKICAgICAgICBsb2Rhc2gudGFrZVJpZ2h0V2hpbGUgPSB0YWtlUmlnaHRXaGlsZTsKICAgICAgICBsb2Rhc2gudGFrZVdoaWxlID0gdGFrZVdoaWxlOwogICAgICAgIGxvZGFzaC50YXAgPSB0YXA7CiAgICAgICAgbG9kYXNoLnRocm90dGxlID0gdGhyb3R0bGU7CiAgICAgICAgbG9kYXNoLnRocnUgPSB0aHJ1OwogICAgICAgIGxvZGFzaC50b0FycmF5ID0gdG9BcnJheTsKICAgICAgICBsb2Rhc2gudG9QYWlycyA9IHRvUGFpcnM7CiAgICAgICAgbG9kYXNoLnRvUGFpcnNJbiA9IHRvUGFpcnNJbjsKICAgICAgICBsb2Rhc2gudG9QYXRoID0gdG9QYXRoOwogICAgICAgIGxvZGFzaC50b1BsYWluT2JqZWN0ID0gdG9QbGFpbk9iamVjdDsKICAgICAgICBsb2Rhc2gudHJhbnNmb3JtID0gdHJhbnNmb3JtOwogICAgICAgIGxvZGFzaC51bmFyeSA9IHVuYXJ5OwogICAgICAgIGxvZGFzaC51bmlvbiA9IHVuaW9uOwogICAgICAgIGxvZGFzaC51bmlvbkJ5ID0gdW5pb25CeTsKICAgICAgICBsb2Rhc2gudW5pb25XaXRoID0gdW5pb25XaXRoOwogICAgICAgIGxvZGFzaC51bmlxID0gdW5pcTsKICAgICAgICBsb2Rhc2gudW5pcUJ5ID0gdW5pcUJ5OwogICAgICAgIGxvZGFzaC51bmlxV2l0aCA9IHVuaXFXaXRoOwogICAgICAgIGxvZGFzaC51bnNldCA9IHVuc2V0OwogICAgICAgIGxvZGFzaC51bnppcCA9IHVuemlwOwogICAgICAgIGxvZGFzaC51bnppcFdpdGggPSB1bnppcFdpdGg7CiAgICAgICAgbG9kYXNoLnVwZGF0ZSA9IHVwZGF0ZTsKICAgICAgICBsb2Rhc2gudXBkYXRlV2l0aCA9IHVwZGF0ZVdpdGg7CiAgICAgICAgbG9kYXNoLnZhbHVlcyA9IHZhbHVlczsKICAgICAgICBsb2Rhc2gudmFsdWVzSW4gPSB2YWx1ZXNJbjsKICAgICAgICBsb2Rhc2gud2l0aG91dCA9IHdpdGhvdXQ7CiAgICAgICAgbG9kYXNoLndvcmRzID0gd29yZHM7CiAgICAgICAgbG9kYXNoLndyYXAgPSB3cmFwOwogICAgICAgIGxvZGFzaC54b3IgPSB4b3I7CiAgICAgICAgbG9kYXNoLnhvckJ5ID0geG9yQnk7CiAgICAgICAgbG9kYXNoLnhvcldpdGggPSB4b3JXaXRoOwogICAgICAgIGxvZGFzaC56aXAgPSB6aXA7CiAgICAgICAgbG9kYXNoLnppcE9iamVjdCA9IHppcE9iamVjdDsKICAgICAgICBsb2Rhc2guemlwT2JqZWN0RGVlcCA9IHppcE9iamVjdERlZXA7CiAgICAgICAgbG9kYXNoLnppcFdpdGggPSB6aXBXaXRoOwoKICAgICAgICAvLyBBZGQgYWxpYXNlcy4KICAgICAgICBsb2Rhc2guZW50cmllcyA9IHRvUGFpcnM7CiAgICAgICAgbG9kYXNoLmVudHJpZXNJbiA9IHRvUGFpcnNJbjsKICAgICAgICBsb2Rhc2guZXh0ZW5kID0gYXNzaWduSW47CiAgICAgICAgbG9kYXNoLmV4dGVuZFdpdGggPSBhc3NpZ25JbldpdGg7CgogICAgICAgIC8vIEFkZCBtZXRob2RzIHRvIGBsb2Rhc2gucHJvdG90eXBlYC4KICAgICAgICBtaXhpbihsb2Rhc2gsIGxvZGFzaCk7CgogICAgICAgIC8qLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKi8KCiAgICAgICAgLy8gQWRkIG1ldGhvZHMgdGhhdCByZXR1cm4gdW53cmFwcGVkIHZhbHVlcyBpbiBjaGFpbiBzZXF1ZW5jZXMuCiAgICAgICAgbG9kYXNoLmFkZCA9IGFkZDsKICAgICAgICBsb2Rhc2guYXR0ZW1wdCA9IGF0dGVtcHQ7CiAgICAgICAgbG9kYXNoLmNhbWVsQ2FzZSA9IGNhbWVsQ2FzZTsKICAgICAgICBsb2Rhc2guY2FwaXRhbGl6ZSA9IGNhcGl0YWxpemU7CiAgICAgICAgbG9kYXNoLmNlaWwgPSBjZWlsOwogICAgICAgIGxvZGFzaC5jbGFtcCA9IGNsYW1wOwogICAgICAgIGxvZGFzaC5jbG9uZSA9IGNsb25lOwogICAgICAgIGxvZGFzaC5jbG9uZURlZXAgPSBjbG9uZURlZXA7CiAgICAgICAgbG9kYXNoLmNsb25lRGVlcFdpdGggPSBjbG9uZURlZXBXaXRoOwogICAgICAgIGxvZGFzaC5jbG9uZVdpdGggPSBjbG9uZVdpdGg7CiAgICAgICAgbG9kYXNoLmNvbmZvcm1zVG8gPSBjb25mb3Jtc1RvOwogICAgICAgIGxvZGFzaC5kZWJ1cnIgPSBkZWJ1cnI7CiAgICAgICAgbG9kYXNoLmRlZmF1bHRUbyA9IGRlZmF1bHRUbzsKICAgICAgICBsb2Rhc2guZGl2aWRlID0gZGl2aWRlOwogICAgICAgIGxvZGFzaC5lbmRzV2l0aCA9IGVuZHNXaXRoOwogICAgICAgIGxvZGFzaC5lcSA9IGVxOwogICAgICAgIGxvZGFzaC5lc2NhcGUgPSBlc2NhcGU7CiAgICAgICAgbG9kYXNoLmVzY2FwZVJlZ0V4cCA9IGVzY2FwZVJlZ0V4cDsKICAgICAgICBsb2Rhc2guZXZlcnkgPSBldmVyeTsKICAgICAgICBsb2Rhc2guZmluZCA9IGZpbmQ7CiAgICAgICAgbG9kYXNoLmZpbmRJbmRleCA9IGZpbmRJbmRleDsKICAgICAgICBsb2Rhc2guZmluZEtleSA9IGZpbmRLZXk7CiAgICAgICAgbG9kYXNoLmZpbmRMYXN0ID0gZmluZExhc3Q7CiAgICAgICAgbG9kYXNoLmZpbmRMYXN0SW5kZXggPSBmaW5kTGFzdEluZGV4OwogICAgICAgIGxvZGFzaC5maW5kTGFzdEtleSA9IGZpbmRMYXN0S2V5OwogICAgICAgIGxvZGFzaC5mbG9vciA9IGZsb29yOwogICAgICAgIGxvZGFzaC5mb3JFYWNoID0gZm9yRWFjaDsKICAgICAgICBsb2Rhc2guZm9yRWFjaFJpZ2h0ID0gZm9yRWFjaFJpZ2h0OwogICAgICAgIGxvZGFzaC5mb3JJbiA9IGZvckluOwogICAgICAgIGxvZGFzaC5mb3JJblJpZ2h0ID0gZm9ySW5SaWdodDsKICAgICAgICBsb2Rhc2guZm9yT3duID0gZm9yT3duOwogICAgICAgIGxvZGFzaC5mb3JPd25SaWdodCA9IGZvck93blJpZ2h0OwogICAgICAgIGxvZGFzaC5nZXQgPSBnZXQ7CiAgICAgICAgbG9kYXNoLmd0ID0gZ3Q7CiAgICAgICAgbG9kYXNoLmd0ZSA9IGd0ZTsKICAgICAgICBsb2Rhc2guaGFzID0gaGFzOwogICAgICAgIGxvZGFzaC5oYXNJbiA9IGhhc0luOwogICAgICAgIGxvZGFzaC5oZWFkID0gaGVhZDsKICAgICAgICBsb2Rhc2guaWRlbnRpdHkgPSBpZGVudGl0eTsKICAgICAgICBsb2Rhc2guaW5jbHVkZXMgPSBpbmNsdWRlczsKICAgICAgICBsb2Rhc2guaW5kZXhPZiA9IGluZGV4T2Y7CiAgICAgICAgbG9kYXNoLmluUmFuZ2UgPSBpblJhbmdlOwogICAgICAgIGxvZGFzaC5pbnZva2UgPSBpbnZva2U7CiAgICAgICAgbG9kYXNoLmlzQXJndW1lbnRzID0gaXNBcmd1bWVudHM7CiAgICAgICAgbG9kYXNoLmlzQXJyYXkgPSBpc0FycmF5OwogICAgICAgIGxvZGFzaC5pc0FycmF5QnVmZmVyID0gaXNBcnJheUJ1ZmZlcjsKICAgICAgICBsb2Rhc2guaXNBcnJheUxpa2UgPSBpc0FycmF5TGlrZTsKICAgICAgICBsb2Rhc2guaXNBcnJheUxpa2VPYmplY3QgPSBpc0FycmF5TGlrZU9iamVjdDsKICAgICAgICBsb2Rhc2guaXNCb29sZWFuID0gaXNCb29sZWFuOwogICAgICAgIGxvZGFzaC5pc0J1ZmZlciA9IGlzQnVmZmVyOwogICAgICAgIGxvZGFzaC5pc0RhdGUgPSBpc0RhdGU7CiAgICAgICAgbG9kYXNoLmlzRWxlbWVudCA9IGlzRWxlbWVudDsKICAgICAgICBsb2Rhc2guaXNFbXB0eSA9IGlzRW1wdHk7CiAgICAgICAgbG9kYXNoLmlzRXF1YWwgPSBpc0VxdWFsOwogICAgICAgIGxvZGFzaC5pc0VxdWFsV2l0aCA9IGlzRXF1YWxXaXRoOwogICAgICAgIGxvZGFzaC5pc0Vycm9yID0gaXNFcnJvcjsKICAgICAgICBsb2Rhc2guaXNGaW5pdGUgPSBpc0Zpbml0ZTsKICAgICAgICBsb2Rhc2guaXNGdW5jdGlvbiA9IGlzRnVuY3Rpb247CiAgICAgICAgbG9kYXNoLmlzSW50ZWdlciA9IGlzSW50ZWdlcjsKICAgICAgICBsb2Rhc2guaXNMZW5ndGggPSBpc0xlbmd0aDsKICAgICAgICBsb2Rhc2guaXNNYXAgPSBpc01hcDsKICAgICAgICBsb2Rhc2guaXNNYXRjaCA9IGlzTWF0Y2g7CiAgICAgICAgbG9kYXNoLmlzTWF0Y2hXaXRoID0gaXNNYXRjaFdpdGg7CiAgICAgICAgbG9kYXNoLmlzTmFOID0gaXNOYU47CiAgICAgICAgbG9kYXNoLmlzTmF0aXZlID0gaXNOYXRpdmU7CiAgICAgICAgbG9kYXNoLmlzTmlsID0gaXNOaWw7CiAgICAgICAgbG9kYXNoLmlzTnVsbCA9IGlzTnVsbDsKICAgICAgICBsb2Rhc2guaXNOdW1iZXIgPSBpc051bWJlcjsKICAgICAgICBsb2Rhc2guaXNPYmplY3QgPSBpc09iamVjdDsKICAgICAgICBsb2Rhc2guaXNPYmplY3RMaWtlID0gaXNPYmplY3RMaWtlOwogICAgICAgIGxvZGFzaC5pc1BsYWluT2JqZWN0ID0gaXNQbGFpbk9iamVjdDsKICAgICAgICBsb2Rhc2guaXNSZWdFeHAgPSBpc1JlZ0V4cDsKICAgICAgICBsb2Rhc2guaXNTYWZlSW50ZWdlciA9IGlzU2FmZUludGVnZXI7CiAgICAgICAgbG9kYXNoLmlzU2V0ID0gaXNTZXQ7CiAgICAgICAgbG9kYXNoLmlzU3RyaW5nID0gaXNTdHJpbmc7CiAgICAgICAgbG9kYXNoLmlzU3ltYm9sID0gaXNTeW1ib2w7CiAgICAgICAgbG9kYXNoLmlzVHlwZWRBcnJheSA9IGlzVHlwZWRBcnJheTsKICAgICAgICBsb2Rhc2guaXNVbmRlZmluZWQgPSBpc1VuZGVmaW5lZDsKICAgICAgICBsb2Rhc2guaXNXZWFrTWFwID0gaXNXZWFrTWFwOwogICAgICAgIGxvZGFzaC5pc1dlYWtTZXQgPSBpc1dlYWtTZXQ7CiAgICAgICAgbG9kYXNoLmpvaW4gPSBqb2luOwogICAgICAgIGxvZGFzaC5rZWJhYkNhc2UgPSBrZWJhYkNhc2U7CiAgICAgICAgbG9kYXNoLmxhc3QgPSBsYXN0OwogICAgICAgIGxvZGFzaC5sYXN0SW5kZXhPZiA9IGxhc3RJbmRleE9mOwogICAgICAgIGxvZGFzaC5sb3dlckNhc2UgPSBsb3dlckNhc2U7CiAgICAgICAgbG9kYXNoLmxvd2VyRmlyc3QgPSBsb3dlckZpcnN0OwogICAgICAgIGxvZGFzaC5sdCA9IGx0OwogICAgICAgIGxvZGFzaC5sdGUgPSBsdGU7CiAgICAgICAgbG9kYXNoLm1heCA9IG1heDsKICAgICAgICBsb2Rhc2gubWF4QnkgPSBtYXhCeTsKICAgICAgICBsb2Rhc2gubWVhbiA9IG1lYW47CiAgICAgICAgbG9kYXNoLm1lYW5CeSA9IG1lYW5CeTsKICAgICAgICBsb2Rhc2gubWluID0gbWluOwogICAgICAgIGxvZGFzaC5taW5CeSA9IG1pbkJ5OwogICAgICAgIGxvZGFzaC5zdHViQXJyYXkgPSBzdHViQXJyYXk7CiAgICAgICAgbG9kYXNoLnN0dWJGYWxzZSA9IHN0dWJGYWxzZTsKICAgICAgICBsb2Rhc2guc3R1Yk9iamVjdCA9IHN0dWJPYmplY3Q7CiAgICAgICAgbG9kYXNoLnN0dWJTdHJpbmcgPSBzdHViU3RyaW5nOwogICAgICAgIGxvZGFzaC5zdHViVHJ1ZSA9IHN0dWJUcnVlOwogICAgICAgIGxvZGFzaC5tdWx0aXBseSA9IG11bHRpcGx5OwogICAgICAgIGxvZGFzaC5udGggPSBudGg7CiAgICAgICAgbG9kYXNoLm5vQ29uZmxpY3QgPSBub0NvbmZsaWN0OwogICAgICAgIGxvZGFzaC5ub29wID0gbm9vcDsKICAgICAgICBsb2Rhc2gubm93ID0gbm93OwogICAgICAgIGxvZGFzaC5wYWQgPSBwYWQ7CiAgICAgICAgbG9kYXNoLnBhZEVuZCA9IHBhZEVuZDsKICAgICAgICBsb2Rhc2gucGFkU3RhcnQgPSBwYWRTdGFydDsKICAgICAgICBsb2Rhc2gucGFyc2VJbnQgPSBwYXJzZUludDsKICAgICAgICBsb2Rhc2gucmFuZG9tID0gcmFuZG9tOwogICAgICAgIGxvZGFzaC5yZWR1Y2UgPSByZWR1Y2U7CiAgICAgICAgbG9kYXNoLnJlZHVjZVJpZ2h0ID0gcmVkdWNlUmlnaHQ7CiAgICAgICAgbG9kYXNoLnJlcGVhdCA9IHJlcGVhdDsKICAgICAgICBsb2Rhc2gucmVwbGFjZSA9IHJlcGxhY2U7CiAgICAgICAgbG9kYXNoLnJlc3VsdCA9IHJlc3VsdDsKICAgICAgICBsb2Rhc2gucm91bmQgPSByb3VuZDsKICAgICAgICBsb2Rhc2gucnVuSW5Db250ZXh0ID0gcnVuSW5Db250ZXh0OwogICAgICAgIGxvZGFzaC5zYW1wbGUgPSBzYW1wbGU7CiAgICAgICAgbG9kYXNoLnNpemUgPSBzaXplOwogICAgICAgIGxvZGFzaC5zbmFrZUNhc2UgPSBzbmFrZUNhc2U7CiAgICAgICAgbG9kYXNoLnNvbWUgPSBzb21lOwogICAgICAgIGxvZGFzaC5zb3J0ZWRJbmRleCA9IHNvcnRlZEluZGV4OwogICAgICAgIGxvZGFzaC5zb3J0ZWRJbmRleEJ5ID0gc29ydGVkSW5kZXhCeTsKICAgICAgICBsb2Rhc2guc29ydGVkSW5kZXhPZiA9IHNvcnRlZEluZGV4T2Y7CiAgICAgICAgbG9kYXNoLnNvcnRlZExhc3RJbmRleCA9IHNvcnRlZExhc3RJbmRleDsKICAgICAgICBsb2Rhc2guc29ydGVkTGFzdEluZGV4QnkgPSBzb3J0ZWRMYXN0SW5kZXhCeTsKICAgICAgICBsb2Rhc2guc29ydGVkTGFzdEluZGV4T2YgPSBzb3J0ZWRMYXN0SW5kZXhPZjsKICAgICAgICBsb2Rhc2guc3RhcnRDYXNlID0gc3RhcnRDYXNlOwogICAgICAgIGxvZGFzaC5zdGFydHNXaXRoID0gc3RhcnRzV2l0aDsKICAgICAgICBsb2Rhc2guc3VidHJhY3QgPSBzdWJ0cmFjdDsKICAgICAgICBsb2Rhc2guc3VtID0gc3VtOwogICAgICAgIGxvZGFzaC5zdW1CeSA9IHN1bUJ5OwogICAgICAgIGxvZGFzaC50ZW1wbGF0ZSA9IHRlbXBsYXRlOwogICAgICAgIGxvZGFzaC50aW1lcyA9IHRpbWVzOwogICAgICAgIGxvZGFzaC50b0Zpbml0ZSA9IHRvRmluaXRlOwogICAgICAgIGxvZGFzaC50b0ludGVnZXIgPSB0b0ludGVnZXI7CiAgICAgICAgbG9kYXNoLnRvTGVuZ3RoID0gdG9MZW5ndGg7CiAgICAgICAgbG9kYXNoLnRvTG93ZXIgPSB0b0xvd2VyOwogICAgICAgIGxvZGFzaC50b051bWJlciA9IHRvTnVtYmVyOwogICAgICAgIGxvZGFzaC50b1NhZmVJbnRlZ2VyID0gdG9TYWZlSW50ZWdlcjsKICAgICAgICBsb2Rhc2gudG9TdHJpbmcgPSB0b1N0cmluZzsKICAgICAgICBsb2Rhc2gudG9VcHBlciA9IHRvVXBwZXI7CiAgICAgICAgbG9kYXNoLnRyaW0gPSB0cmltOwogICAgICAgIGxvZGFzaC50cmltRW5kID0gdHJpbUVuZDsKICAgICAgICBsb2Rhc2gudHJpbVN0YXJ0ID0gdHJpbVN0YXJ0OwogICAgICAgIGxvZGFzaC50cnVuY2F0ZSA9IHRydW5jYXRlOwogICAgICAgIGxvZGFzaC51bmVzY2FwZSA9IHVuZXNjYXBlOwogICAgICAgIGxvZGFzaC51bmlxdWVJZCA9IHVuaXF1ZUlkOwogICAgICAgIGxvZGFzaC51cHBlckNhc2UgPSB1cHBlckNhc2U7CiAgICAgICAgbG9kYXNoLnVwcGVyRmlyc3QgPSB1cHBlckZpcnN0OwoKICAgICAgICAvLyBBZGQgYWxpYXNlcy4KICAgICAgICBsb2Rhc2guZWFjaCA9IGZvckVhY2g7CiAgICAgICAgbG9kYXNoLmVhY2hSaWdodCA9IGZvckVhY2hSaWdodDsKICAgICAgICBsb2Rhc2guZmlyc3QgPSBoZWFkOwoKICAgICAgICBtaXhpbihsb2Rhc2gsIChmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciBzb3VyY2UgPSB7fTsKICAgICAgICAgIGJhc2VGb3JPd24obG9kYXNoLCBmdW5jdGlvbihmdW5jLCBtZXRob2ROYW1lKSB7CiAgICAgICAgICAgIGlmICghaGFzT3duUHJvcGVydHkuY2FsbChsb2Rhc2gucHJvdG90eXBlLCBtZXRob2ROYW1lKSkgewogICAgICAgICAgICAgIHNvdXJjZVttZXRob2ROYW1lXSA9IGZ1bmM7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIHNvdXJjZTsKICAgICAgICB9KCkpLCB7ICdjaGFpbic6IGZhbHNlIH0pOwoKICAgICAgICAvKi0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBzZW1hbnRpYyB2ZXJzaW9uIG51bWJlci4KICAgICAgICAgKgogICAgICAgICAqIEBzdGF0aWMKICAgICAgICAgKiBAbWVtYmVyT2YgXwogICAgICAgICAqIEB0eXBlIHtzdHJpbmd9CiAgICAgICAgICovCiAgICAgICAgbG9kYXNoLlZFUlNJT04gPSBWRVJTSU9OOwoKICAgICAgICAvLyBBc3NpZ24gZGVmYXVsdCBwbGFjZWhvbGRlcnMuCiAgICAgICAgYXJyYXlFYWNoKFsnYmluZCcsICdiaW5kS2V5JywgJ2N1cnJ5JywgJ2N1cnJ5UmlnaHQnLCAncGFydGlhbCcsICdwYXJ0aWFsUmlnaHQnXSwgZnVuY3Rpb24obWV0aG9kTmFtZSkgewogICAgICAgICAgbG9kYXNoW21ldGhvZE5hbWVdLnBsYWNlaG9sZGVyID0gbG9kYXNoOwogICAgICAgIH0pOwoKICAgICAgICAvLyBBZGQgYExhenlXcmFwcGVyYCBtZXRob2RzIGZvciBgXy5kcm9wYCBhbmQgYF8udGFrZWAgdmFyaWFudHMuCiAgICAgICAgYXJyYXlFYWNoKFsnZHJvcCcsICd0YWtlJ10sIGZ1bmN0aW9uKG1ldGhvZE5hbWUsIGluZGV4KSB7CiAgICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGVbbWV0aG9kTmFtZV0gPSBmdW5jdGlvbihuKSB7CiAgICAgICAgICAgIG4gPSBuID09PSB1bmRlZmluZWQkMSA/IDEgOiBuYXRpdmVNYXgodG9JbnRlZ2VyKG4pLCAwKTsKCiAgICAgICAgICAgIHZhciByZXN1bHQgPSAodGhpcy5fX2ZpbHRlcmVkX18gJiYgIWluZGV4KQogICAgICAgICAgICAgID8gbmV3IExhenlXcmFwcGVyKHRoaXMpCiAgICAgICAgICAgICAgOiB0aGlzLmNsb25lKCk7CgogICAgICAgICAgICBpZiAocmVzdWx0Ll9fZmlsdGVyZWRfXykgewogICAgICAgICAgICAgIHJlc3VsdC5fX3Rha2VDb3VudF9fID0gbmF0aXZlTWluKG4sIHJlc3VsdC5fX3Rha2VDb3VudF9fKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICByZXN1bHQuX192aWV3c19fLnB1c2goewogICAgICAgICAgICAgICAgJ3NpemUnOiBuYXRpdmVNaW4obiwgTUFYX0FSUkFZX0xFTkdUSCksCiAgICAgICAgICAgICAgICAndHlwZSc6IG1ldGhvZE5hbWUgKyAocmVzdWx0Ll9fZGlyX18gPCAwID8gJ1JpZ2h0JyA6ICcnKQogICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICB9OwoKICAgICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZVttZXRob2ROYW1lICsgJ1JpZ2h0J10gPSBmdW5jdGlvbihuKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJldmVyc2UoKVttZXRob2ROYW1lXShuKS5yZXZlcnNlKCk7CiAgICAgICAgICB9OwogICAgICAgIH0pOwoKICAgICAgICAvLyBBZGQgYExhenlXcmFwcGVyYCBtZXRob2RzIHRoYXQgYWNjZXB0IGFuIGBpdGVyYXRlZWAgdmFsdWUuCiAgICAgICAgYXJyYXlFYWNoKFsnZmlsdGVyJywgJ21hcCcsICd0YWtlV2hpbGUnXSwgZnVuY3Rpb24obWV0aG9kTmFtZSwgaW5kZXgpIHsKICAgICAgICAgIHZhciB0eXBlID0gaW5kZXggKyAxLAogICAgICAgICAgICAgIGlzRmlsdGVyID0gdHlwZSA9PSBMQVpZX0ZJTFRFUl9GTEFHIHx8IHR5cGUgPT0gTEFaWV9XSElMRV9GTEFHOwoKICAgICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZVttZXRob2ROYW1lXSA9IGZ1bmN0aW9uKGl0ZXJhdGVlKSB7CiAgICAgICAgICAgIHZhciByZXN1bHQgPSB0aGlzLmNsb25lKCk7CiAgICAgICAgICAgIHJlc3VsdC5fX2l0ZXJhdGVlc19fLnB1c2goewogICAgICAgICAgICAgICdpdGVyYXRlZSc6IGdldEl0ZXJhdGVlKGl0ZXJhdGVlLCAzKSwKICAgICAgICAgICAgICAndHlwZSc6IHR5cGUKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJlc3VsdC5fX2ZpbHRlcmVkX18gPSByZXN1bHQuX19maWx0ZXJlZF9fIHx8IGlzRmlsdGVyOwogICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgfTsKICAgICAgICB9KTsKCiAgICAgICAgLy8gQWRkIGBMYXp5V3JhcHBlcmAgbWV0aG9kcyBmb3IgYF8uaGVhZGAgYW5kIGBfLmxhc3RgLgogICAgICAgIGFycmF5RWFjaChbJ2hlYWQnLCAnbGFzdCddLCBmdW5jdGlvbihtZXRob2ROYW1lLCBpbmRleCkgewogICAgICAgICAgdmFyIHRha2VOYW1lID0gJ3Rha2UnICsgKGluZGV4ID8gJ1JpZ2h0JyA6ICcnKTsKCiAgICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGVbbWV0aG9kTmFtZV0gPSBmdW5jdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXNbdGFrZU5hbWVdKDEpLnZhbHVlKClbMF07CiAgICAgICAgICB9OwogICAgICAgIH0pOwoKICAgICAgICAvLyBBZGQgYExhenlXcmFwcGVyYCBtZXRob2RzIGZvciBgXy5pbml0aWFsYCBhbmQgYF8udGFpbGAuCiAgICAgICAgYXJyYXlFYWNoKFsnaW5pdGlhbCcsICd0YWlsJ10sIGZ1bmN0aW9uKG1ldGhvZE5hbWUsIGluZGV4KSB7CiAgICAgICAgICB2YXIgZHJvcE5hbWUgPSAnZHJvcCcgKyAoaW5kZXggPyAnJyA6ICdSaWdodCcpOwoKICAgICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZVttZXRob2ROYW1lXSA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fX2ZpbHRlcmVkX18gPyBuZXcgTGF6eVdyYXBwZXIodGhpcykgOiB0aGlzW2Ryb3BOYW1lXSgxKTsKICAgICAgICAgIH07CiAgICAgICAgfSk7CgogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS5jb21wYWN0ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5maWx0ZXIoaWRlbnRpdHkpOwogICAgICAgIH07CgogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS5maW5kID0gZnVuY3Rpb24ocHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5maWx0ZXIocHJlZGljYXRlKS5oZWFkKCk7CiAgICAgICAgfTsKCiAgICAgICAgTGF6eVdyYXBwZXIucHJvdG90eXBlLmZpbmRMYXN0ID0gZnVuY3Rpb24ocHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5yZXZlcnNlKCkuZmluZChwcmVkaWNhdGUpOwogICAgICAgIH07CgogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS5pbnZva2VNYXAgPSBiYXNlUmVzdChmdW5jdGlvbihwYXRoLCBhcmdzKSB7CiAgICAgICAgICBpZiAodHlwZW9mIHBhdGggPT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICByZXR1cm4gbmV3IExhenlXcmFwcGVyKHRoaXMpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRoaXMubWFwKGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiBiYXNlSW52b2tlKHZhbHVlLCBwYXRoLCBhcmdzKTsKICAgICAgICAgIH0pOwogICAgICAgIH0pOwoKICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGUucmVqZWN0ID0gZnVuY3Rpb24ocHJlZGljYXRlKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5maWx0ZXIobmVnYXRlKGdldEl0ZXJhdGVlKHByZWRpY2F0ZSkpKTsKICAgICAgICB9OwoKICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGUuc2xpY2UgPSBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgICBzdGFydCA9IHRvSW50ZWdlcihzdGFydCk7CgogICAgICAgICAgdmFyIHJlc3VsdCA9IHRoaXM7CiAgICAgICAgICBpZiAocmVzdWx0Ll9fZmlsdGVyZWRfXyAmJiAoc3RhcnQgPiAwIHx8IGVuZCA8IDApKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgTGF6eVdyYXBwZXIocmVzdWx0KTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChzdGFydCA8IDApIHsKICAgICAgICAgICAgcmVzdWx0ID0gcmVzdWx0LnRha2VSaWdodCgtc3RhcnQpOwogICAgICAgICAgfSBlbHNlIGlmIChzdGFydCkgewogICAgICAgICAgICByZXN1bHQgPSByZXN1bHQuZHJvcChzdGFydCk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoZW5kICE9PSB1bmRlZmluZWQkMSkgewogICAgICAgICAgICBlbmQgPSB0b0ludGVnZXIoZW5kKTsKICAgICAgICAgICAgcmVzdWx0ID0gZW5kIDwgMCA/IHJlc3VsdC5kcm9wUmlnaHQoLWVuZCkgOiByZXN1bHQudGFrZShlbmQgLSBzdGFydCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH07CgogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS50YWtlUmlnaHRXaGlsZSA9IGZ1bmN0aW9uKHByZWRpY2F0ZSkgewogICAgICAgICAgcmV0dXJuIHRoaXMucmV2ZXJzZSgpLnRha2VXaGlsZShwcmVkaWNhdGUpLnJldmVyc2UoKTsKICAgICAgICB9OwoKICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGUudG9BcnJheSA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHRoaXMudGFrZShNQVhfQVJSQVlfTEVOR1RIKTsKICAgICAgICB9OwoKICAgICAgICAvLyBBZGQgYExhenlXcmFwcGVyYCBtZXRob2RzIHRvIGBsb2Rhc2gucHJvdG90eXBlYC4KICAgICAgICBiYXNlRm9yT3duKExhenlXcmFwcGVyLnByb3RvdHlwZSwgZnVuY3Rpb24oZnVuYywgbWV0aG9kTmFtZSkgewogICAgICAgICAgdmFyIGNoZWNrSXRlcmF0ZWUgPSAvXig/OmZpbHRlcnxmaW5kfG1hcHxyZWplY3QpfFdoaWxlJC8udGVzdChtZXRob2ROYW1lKSwKICAgICAgICAgICAgICBpc1Rha2VyID0gL14oPzpoZWFkfGxhc3QpJC8udGVzdChtZXRob2ROYW1lKSwKICAgICAgICAgICAgICBsb2Rhc2hGdW5jID0gbG9kYXNoW2lzVGFrZXIgPyAoJ3Rha2UnICsgKG1ldGhvZE5hbWUgPT0gJ2xhc3QnID8gJ1JpZ2h0JyA6ICcnKSkgOiBtZXRob2ROYW1lXSwKICAgICAgICAgICAgICByZXRVbndyYXBwZWQgPSBpc1Rha2VyIHx8IC9eZmluZC8udGVzdChtZXRob2ROYW1lKTsKCiAgICAgICAgICBpZiAoIWxvZGFzaEZ1bmMpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgbG9kYXNoLnByb3RvdHlwZVttZXRob2ROYW1lXSA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSB0aGlzLl9fd3JhcHBlZF9fLAogICAgICAgICAgICAgICAgYXJncyA9IGlzVGFrZXIgPyBbMV0gOiBhcmd1bWVudHMsCiAgICAgICAgICAgICAgICBpc0xhenkgPSB2YWx1ZSBpbnN0YW5jZW9mIExhenlXcmFwcGVyLAogICAgICAgICAgICAgICAgaXRlcmF0ZWUgPSBhcmdzWzBdLAogICAgICAgICAgICAgICAgdXNlTGF6eSA9IGlzTGF6eSB8fCBpc0FycmF5KHZhbHVlKTsKCiAgICAgICAgICAgIHZhciBpbnRlcmNlcHRvciA9IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICAgICAgdmFyIHJlc3VsdCA9IGxvZGFzaEZ1bmMuYXBwbHkobG9kYXNoLCBhcnJheVB1c2goW3ZhbHVlXSwgYXJncykpOwogICAgICAgICAgICAgIHJldHVybiAoaXNUYWtlciAmJiBjaGFpbkFsbCkgPyByZXN1bHRbMF0gOiByZXN1bHQ7CiAgICAgICAgICAgIH07CgogICAgICAgICAgICBpZiAodXNlTGF6eSAmJiBjaGVja0l0ZXJhdGVlICYmIHR5cGVvZiBpdGVyYXRlZSA9PSAnZnVuY3Rpb24nICYmIGl0ZXJhdGVlLmxlbmd0aCAhPSAxKSB7CiAgICAgICAgICAgICAgLy8gQXZvaWQgbGF6eSB1c2UgaWYgdGhlIGl0ZXJhdGVlIGhhcyBhICJsZW5ndGgiIHZhbHVlIG90aGVyIHRoYW4gYDFgLgogICAgICAgICAgICAgIGlzTGF6eSA9IHVzZUxhenkgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgY2hhaW5BbGwgPSB0aGlzLl9fY2hhaW5fXywKICAgICAgICAgICAgICAgIGlzSHlicmlkID0gISF0aGlzLl9fYWN0aW9uc19fLmxlbmd0aCwKICAgICAgICAgICAgICAgIGlzVW53cmFwcGVkID0gcmV0VW53cmFwcGVkICYmICFjaGFpbkFsbCwKICAgICAgICAgICAgICAgIG9ubHlMYXp5ID0gaXNMYXp5ICYmICFpc0h5YnJpZDsKCiAgICAgICAgICAgIGlmICghcmV0VW53cmFwcGVkICYmIHVzZUxhenkpIHsKICAgICAgICAgICAgICB2YWx1ZSA9IG9ubHlMYXp5ID8gdmFsdWUgOiBuZXcgTGF6eVdyYXBwZXIodGhpcyk7CiAgICAgICAgICAgICAgdmFyIHJlc3VsdCA9IGZ1bmMuYXBwbHkodmFsdWUsIGFyZ3MpOwogICAgICAgICAgICAgIHJlc3VsdC5fX2FjdGlvbnNfXy5wdXNoKHsgJ2Z1bmMnOiB0aHJ1LCAnYXJncyc6IFtpbnRlcmNlcHRvcl0sICd0aGlzQXJnJzogdW5kZWZpbmVkJDEgfSk7CiAgICAgICAgICAgICAgcmV0dXJuIG5ldyBMb2Rhc2hXcmFwcGVyKHJlc3VsdCwgY2hhaW5BbGwpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChpc1Vud3JhcHBlZCAmJiBvbmx5TGF6eSkgewogICAgICAgICAgICAgIHJldHVybiBmdW5jLmFwcGx5KHRoaXMsIGFyZ3MpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJlc3VsdCA9IHRoaXMudGhydShpbnRlcmNlcHRvcik7CiAgICAgICAgICAgIHJldHVybiBpc1Vud3JhcHBlZCA/IChpc1Rha2VyID8gcmVzdWx0LnZhbHVlKClbMF0gOiByZXN1bHQudmFsdWUoKSkgOiByZXN1bHQ7CiAgICAgICAgICB9OwogICAgICAgIH0pOwoKICAgICAgICAvLyBBZGQgYEFycmF5YCBtZXRob2RzIHRvIGBsb2Rhc2gucHJvdG90eXBlYC4KICAgICAgICBhcnJheUVhY2goWydwb3AnLCAncHVzaCcsICdzaGlmdCcsICdzb3J0JywgJ3NwbGljZScsICd1bnNoaWZ0J10sIGZ1bmN0aW9uKG1ldGhvZE5hbWUpIHsKICAgICAgICAgIHZhciBmdW5jID0gYXJyYXlQcm90b1ttZXRob2ROYW1lXSwKICAgICAgICAgICAgICBjaGFpbk5hbWUgPSAvXig/OnB1c2h8c29ydHx1bnNoaWZ0KSQvLnRlc3QobWV0aG9kTmFtZSkgPyAndGFwJyA6ICd0aHJ1JywKICAgICAgICAgICAgICByZXRVbndyYXBwZWQgPSAvXig/OnBvcHxzaGlmdCkkLy50ZXN0KG1ldGhvZE5hbWUpOwoKICAgICAgICAgIGxvZGFzaC5wcm90b3R5cGVbbWV0aG9kTmFtZV0gPSBmdW5jdGlvbigpIHsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHM7CiAgICAgICAgICAgIGlmIChyZXRVbndyYXBwZWQgJiYgIXRoaXMuX19jaGFpbl9fKSB7CiAgICAgICAgICAgICAgdmFyIHZhbHVlID0gdGhpcy52YWx1ZSgpOwogICAgICAgICAgICAgIHJldHVybiBmdW5jLmFwcGx5KGlzQXJyYXkodmFsdWUpID8gdmFsdWUgOiBbXSwgYXJncyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXNbY2hhaW5OYW1lXShmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgICAgIHJldHVybiBmdW5jLmFwcGx5KGlzQXJyYXkodmFsdWUpID8gdmFsdWUgOiBbXSwgYXJncyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfTsKICAgICAgICB9KTsKCiAgICAgICAgLy8gTWFwIG1pbmlmaWVkIG1ldGhvZCBuYW1lcyB0byB0aGVpciByZWFsIG5hbWVzLgogICAgICAgIGJhc2VGb3JPd24oTGF6eVdyYXBwZXIucHJvdG90eXBlLCBmdW5jdGlvbihmdW5jLCBtZXRob2ROYW1lKSB7CiAgICAgICAgICB2YXIgbG9kYXNoRnVuYyA9IGxvZGFzaFttZXRob2ROYW1lXTsKICAgICAgICAgIGlmIChsb2Rhc2hGdW5jKSB7CiAgICAgICAgICAgIHZhciBrZXkgPSBsb2Rhc2hGdW5jLm5hbWUgKyAnJzsKICAgICAgICAgICAgaWYgKCFoYXNPd25Qcm9wZXJ0eS5jYWxsKHJlYWxOYW1lcywga2V5KSkgewogICAgICAgICAgICAgIHJlYWxOYW1lc1trZXldID0gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmVhbE5hbWVzW2tleV0ucHVzaCh7ICduYW1lJzogbWV0aG9kTmFtZSwgJ2Z1bmMnOiBsb2Rhc2hGdW5jIH0pOwogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICByZWFsTmFtZXNbY3JlYXRlSHlicmlkKHVuZGVmaW5lZCQxLCBXUkFQX0JJTkRfS0VZX0ZMQUcpLm5hbWVdID0gW3sKICAgICAgICAgICduYW1lJzogJ3dyYXBwZXInLAogICAgICAgICAgJ2Z1bmMnOiB1bmRlZmluZWQkMQogICAgICAgIH1dOwoKICAgICAgICAvLyBBZGQgbWV0aG9kcyB0byBgTGF6eVdyYXBwZXJgLgogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS5jbG9uZSA9IGxhenlDbG9uZTsKICAgICAgICBMYXp5V3JhcHBlci5wcm90b3R5cGUucmV2ZXJzZSA9IGxhenlSZXZlcnNlOwogICAgICAgIExhenlXcmFwcGVyLnByb3RvdHlwZS52YWx1ZSA9IGxhenlWYWx1ZTsKCiAgICAgICAgLy8gQWRkIGNoYWluIHNlcXVlbmNlIG1ldGhvZHMgdG8gdGhlIGBsb2Rhc2hgIHdyYXBwZXIuCiAgICAgICAgbG9kYXNoLnByb3RvdHlwZS5hdCA9IHdyYXBwZXJBdDsKICAgICAgICBsb2Rhc2gucHJvdG90eXBlLmNoYWluID0gd3JhcHBlckNoYWluOwogICAgICAgIGxvZGFzaC5wcm90b3R5cGUuY29tbWl0ID0gd3JhcHBlckNvbW1pdDsKICAgICAgICBsb2Rhc2gucHJvdG90eXBlLm5leHQgPSB3cmFwcGVyTmV4dDsKICAgICAgICBsb2Rhc2gucHJvdG90eXBlLnBsYW50ID0gd3JhcHBlclBsYW50OwogICAgICAgIGxvZGFzaC5wcm90b3R5cGUucmV2ZXJzZSA9IHdyYXBwZXJSZXZlcnNlOwogICAgICAgIGxvZGFzaC5wcm90b3R5cGUudG9KU09OID0gbG9kYXNoLnByb3RvdHlwZS52YWx1ZU9mID0gbG9kYXNoLnByb3RvdHlwZS52YWx1ZSA9IHdyYXBwZXJWYWx1ZTsKCiAgICAgICAgLy8gQWRkIGxhenkgYWxpYXNlcy4KICAgICAgICBsb2Rhc2gucHJvdG90eXBlLmZpcnN0ID0gbG9kYXNoLnByb3RvdHlwZS5oZWFkOwoKICAgICAgICBpZiAoc3ltSXRlcmF0b3IpIHsKICAgICAgICAgIGxvZGFzaC5wcm90b3R5cGVbc3ltSXRlcmF0b3JdID0gd3JhcHBlclRvSXRlcmF0b3I7CiAgICAgICAgfQogICAgICAgIHJldHVybiBsb2Rhc2g7CiAgICAgIH0pOwoKICAgICAgLyotLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSovCgogICAgICAvLyBFeHBvcnQgbG9kYXNoLgogICAgICB2YXIgXyA9IHJ1bkluQ29udGV4dCgpOwoKICAgICAgLy8gU29tZSBBTUQgYnVpbGQgb3B0aW1pemVycywgbGlrZSByLmpzLCBjaGVjayBmb3IgY29uZGl0aW9uIHBhdHRlcm5zIGxpa2U6CiAgICAgIGlmIChmcmVlTW9kdWxlKSB7CiAgICAgICAgLy8gRXhwb3J0IGZvciBOb2RlLmpzLgogICAgICAgIChmcmVlTW9kdWxlLmV4cG9ydHMgPSBfKS5fID0gXzsKICAgICAgICAvLyBFeHBvcnQgZm9yIENvbW1vbkpTIHN1cHBvcnQuCiAgICAgICAgZnJlZUV4cG9ydHMuXyA9IF87CiAgICAgIH0KICAgICAgZWxzZSB7CiAgICAgICAgLy8gRXhwb3J0IHRvIHRoZSBnbG9iYWwgb2JqZWN0LgogICAgICAgIHJvb3QuXyA9IF87CiAgICAgIH0KICAgIH0uY2FsbChjb21tb25qc0dsb2JhbCkpOwogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCBuYXRpdmVTaGFkb3cgPSAhKHdpbmRvd1snU2hhZHlET00nXSAmJiB3aW5kb3dbJ1NoYWR5RE9NJ11bJ2luVXNlJ10pOwogICAgbGV0IG5hdGl2ZUNzc1ZhcmlhYmxlc187CgogICAgLyoqCiAgICAgKiBAcGFyYW0geyhTaGFkeUNTU09wdGlvbnMgfCBTaGFkeUNTU0ludGVyZmFjZSk9fSBzZXR0aW5ncwogICAgICovCiAgICBmdW5jdGlvbiBjYWxjQ3NzVmFyaWFibGVzKHNldHRpbmdzKSB7CiAgICAgIGlmIChzZXR0aW5ncyAmJiBzZXR0aW5nc1snc2hpbWNzc3Byb3BlcnRpZXMnXSkgewogICAgICAgIG5hdGl2ZUNzc1ZhcmlhYmxlc18gPSBmYWxzZTsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBjaHJvbWUgNDkgaGFzIHNlbWktd29ya2luZyBjc3MgdmFycywgY2hlY2sgaWYgYm94LXNoYWRvdyB3b3JrcwogICAgICAgIC8vIHNhZmFyaSA5LjEgaGFzIGEgcmVjYWxjIGJ1ZzogaHR0cHM6Ly9idWdzLndlYmtpdC5vcmcvc2hvd19idWcuY2dpP2lkPTE1NTc4MgogICAgICAgIC8vIEhvd2V2ZXIsIHNoaW0gY3NzIGN1c3RvbSBwcm9wZXJ0aWVzIGFyZSBvbmx5IHN1cHBvcnRlZCB3aXRoIFNoYWR5RE9NIGVuYWJsZWQsCiAgICAgICAgLy8gc28gZmFsbCBiYWNrIG9uIG5hdGl2ZSBpZiB3ZSBkbyBub3QgZGV0ZWN0IFNoYWR5RE9NCiAgICAgICAgLy8gRWRnZSAxNTogY3VzdG9tIHByb3BlcnRpZXMgdXNlZCBpbiA6OmJlZm9yZSBhbmQgOjphZnRlciB3aWxsIGFsc28gYmUgdXNlZCBpbiB0aGUgcGFyZW50IGVsZW1lbnQKICAgICAgICAvLyBodHRwczovL2RldmVsb3Blci5taWNyb3NvZnQuY29tL2VuLXVzL21pY3Jvc29mdC1lZGdlL3BsYXRmb3JtL2lzc3Vlcy8xMjQxNDI1Ny8KICAgICAgICBuYXRpdmVDc3NWYXJpYWJsZXNfID0gbmF0aXZlU2hhZG93IHx8IEJvb2xlYW4oIW5hdmlnYXRvci51c2VyQWdlbnQubWF0Y2goL0FwcGxlV2ViS2l0XC82MDF8RWRnZVwvMTUvKSAmJgogICAgICAgICAgd2luZG93LkNTUyAmJiBDU1Muc3VwcG9ydHMgJiYgQ1NTLnN1cHBvcnRzKCdib3gtc2hhZG93JywgJzAgMCAwIHZhcigtLWZvbyknKSk7CiAgICAgIH0KICAgIH0KCiAgICAvKiogQHR5cGUge3N0cmluZyB8IHVuZGVmaW5lZH0gKi8KICAgIGxldCBjc3NCdWlsZDsKICAgIGlmICh3aW5kb3cuU2hhZHlDU1MgJiYgd2luZG93LlNoYWR5Q1NTLmNzc0J1aWxkICE9PSB1bmRlZmluZWQpIHsKICAgICAgY3NzQnVpbGQgPSB3aW5kb3cuU2hhZHlDU1MuY3NzQnVpbGQ7CiAgICB9CgogICAgLyoqIEB0eXBlIHtib29sZWFufSAqLwogICAgY29uc3QgZGlzYWJsZVJ1bnRpbWUgPSBCb29sZWFuKHdpbmRvdy5TaGFkeUNTUyAmJiB3aW5kb3cuU2hhZHlDU1MuZGlzYWJsZVJ1bnRpbWUpOwoKICAgIGlmICh3aW5kb3cuU2hhZHlDU1MgJiYgd2luZG93LlNoYWR5Q1NTLm5hdGl2ZUNzcyAhPT0gdW5kZWZpbmVkKSB7CiAgICAgIG5hdGl2ZUNzc1ZhcmlhYmxlc18gPSB3aW5kb3cuU2hhZHlDU1MubmF0aXZlQ3NzOwogICAgfSBlbHNlIGlmICh3aW5kb3cuU2hhZHlDU1MpIHsKICAgICAgY2FsY0Nzc1ZhcmlhYmxlcyh3aW5kb3cuU2hhZHlDU1MpOwogICAgICAvLyByZXNldCB3aW5kb3cgdmFyaWFibGUgdG8gbGV0IFNoYWR5Q1NTIEFQSSB0YWtlIGl0cyBwbGFjZQogICAgICB3aW5kb3cuU2hhZHlDU1MgPSB1bmRlZmluZWQ7CiAgICB9IGVsc2UgewogICAgICBjYWxjQ3NzVmFyaWFibGVzKHdpbmRvd1snV2ViQ29tcG9uZW50cyddICYmIHdpbmRvd1snV2ViQ29tcG9uZW50cyddWydmbGFncyddKTsKICAgIH0KCiAgICAvLyBIYWNrIGZvciB0eXBlIGVycm9yIHVuZGVyIG5ldyB0eXBlIGluZmVyZW5jZSB3aGljaCBkb2Vzbid0IGxpa2UgdGhhdAogICAgLy8gbmF0aXZlQ3NzVmFyaWFibGVzIGlzIHVwZGF0ZWQgaW4gYSBmdW5jdGlvbiBhbmQgYXNzaWducyB0aGUgdHlwZQogICAgLy8gYGZ1bmN0aW9uKCk6ID9gIGluc3RlYWQgb2YgYGJvb2xlYW5gLgogICAgY29uc3QgbmF0aXZlQ3NzVmFyaWFibGVzID0gLyoqIEB0eXBlIHtib29sZWFufSAqLyhuYXRpdmVDc3NWYXJpYWJsZXNfKTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKiBAdW5yZXN0cmljdGVkICovCiAgICBjbGFzcyBTdHlsZU5vZGUgewogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAvKiogQHR5cGUge251bWJlcn0gKi8KICAgICAgICB0aGlzWydzdGFydCddID0gMDsKICAgICAgICAvKiogQHR5cGUge251bWJlcn0gKi8KICAgICAgICB0aGlzWydlbmQnXSA9IDA7CiAgICAgICAgLyoqIEB0eXBlIHtTdHlsZU5vZGV9ICovCiAgICAgICAgdGhpc1sncHJldmlvdXMnXSA9IG51bGw7CiAgICAgICAgLyoqIEB0eXBlIHtTdHlsZU5vZGV9ICovCiAgICAgICAgdGhpc1sncGFyZW50J10gPSBudWxsOwogICAgICAgIC8qKiBAdHlwZSB7QXJyYXk8U3R5bGVOb2RlPn0gKi8KICAgICAgICB0aGlzWydydWxlcyddID0gbnVsbDsKICAgICAgICAvKiogQHR5cGUge3N0cmluZ30gKi8KICAgICAgICB0aGlzWydwYXJzZWRDc3NUZXh0J10gPSAnJzsKICAgICAgICAvKiogQHR5cGUge3N0cmluZ30gKi8KICAgICAgICB0aGlzWydjc3NUZXh0J10gPSAnJzsKICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgdGhpc1snYXRSdWxlJ10gPSBmYWxzZTsKICAgICAgICAvKiogQHR5cGUge251bWJlcn0gKi8KICAgICAgICB0aGlzWyd0eXBlJ10gPSAwOwogICAgICAgIC8qKiBAdHlwZSB7c3RyaW5nfSAqLwogICAgICAgIHRoaXNbJ2tleWZyYW1lc05hbWUnXSA9ICcnOwogICAgICAgIC8qKiBAdHlwZSB7c3RyaW5nfSAqLwogICAgICAgIHRoaXNbJ3NlbGVjdG9yJ10gPSAnJzsKICAgICAgICAvKiogQHR5cGUge3N0cmluZ30gKi8KICAgICAgICB0aGlzWydwYXJzZWRTZWxlY3RvciddID0gJyc7CiAgICAgIH0KICAgIH0KCiAgICAvLyBnaXZlbiBhIHN0cmluZyBvZiBjc3MsIHJldHVybiBhIHNpbXBsZSBydWxlIHRyZWUKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IHRleHQKICAgICAqIEByZXR1cm4ge1N0eWxlTm9kZX0KICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2UodGV4dCkgewogICAgICB0ZXh0ID0gY2xlYW4odGV4dCk7CiAgICAgIHJldHVybiBwYXJzZUNzcyhsZXgodGV4dCksIHRleHQpOwogICAgfQoKICAgIC8vIHJlbW92ZSBzdHVmZiB3ZSBkb24ndCBjYXJlIGFib3V0IHRoYXQgbWF5IGhpbmRlciBwYXJzaW5nCiAgICAvKioKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NUZXh0CiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgKi8KICAgIGZ1bmN0aW9uIGNsZWFuKGNzc1RleHQpIHsKICAgICAgcmV0dXJuIGNzc1RleHQucmVwbGFjZShSWC5jb21tZW50cywgJycpLnJlcGxhY2UoUlgucG9ydCwgJycpOwogICAgfQoKICAgIC8vIHN1cGVyIHNpbXBsZSB7Li4ufSBsZXhlciB0aGF0IHJldHVybnMgYSBub2RlIHRyZWUKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IHRleHQKICAgICAqIEByZXR1cm4geyFTdHlsZU5vZGV9CiAgICAgKi8KICAgIGZ1bmN0aW9uIGxleCh0ZXh0KSB7CiAgICAgIGxldCByb290ID0gbmV3IFN0eWxlTm9kZSgpOwogICAgICByb290WydzdGFydCddID0gMDsKICAgICAgcm9vdFsnZW5kJ10gPSB0ZXh0Lmxlbmd0aDsKICAgICAgbGV0IG4gPSByb290OwogICAgICBmb3IgKGxldCBpID0gMCwgbCA9IHRleHQubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgaWYgKHRleHRbaV0gPT09IE9QRU5fQlJBQ0UpIHsKICAgICAgICAgIGlmICghblsncnVsZXMnXSkgewogICAgICAgICAgICBuWydydWxlcyddID0gW107CiAgICAgICAgICB9CiAgICAgICAgICBsZXQgcCA9IG47CiAgICAgICAgICBsZXQgcHJldmlvdXMgPSBwWydydWxlcyddW3BbJ3J1bGVzJ10ubGVuZ3RoIC0gMV0gfHwgbnVsbDsKICAgICAgICAgIG4gPSBuZXcgU3R5bGVOb2RlKCk7CiAgICAgICAgICBuWydzdGFydCddID0gaSArIDE7CiAgICAgICAgICBuWydwYXJlbnQnXSA9IHA7CiAgICAgICAgICBuWydwcmV2aW91cyddID0gcHJldmlvdXM7CiAgICAgICAgICBwWydydWxlcyddLnB1c2gobik7CiAgICAgICAgfSBlbHNlIGlmICh0ZXh0W2ldID09PSBDTE9TRV9CUkFDRSkgewogICAgICAgICAgblsnZW5kJ10gPSBpICsgMTsKICAgICAgICAgIG4gPSBuWydwYXJlbnQnXSB8fCByb290OwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcm9vdDsKICAgIH0KCiAgICAvLyBhZGQgc2VsZWN0b3JzL2Nzc1RleHQgdG8gbm9kZSB0cmVlCiAgICAvKioKICAgICAqIEBwYXJhbSB7U3R5bGVOb2RlfSBub2RlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGV4dAogICAgICogQHJldHVybiB7IVN0eWxlTm9kZX0KICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2VDc3Mobm9kZSwgdGV4dCkgewogICAgICBsZXQgdCA9IHRleHQuc3Vic3RyaW5nKG5vZGVbJ3N0YXJ0J10sIG5vZGVbJ2VuZCddIC0gMSk7CiAgICAgIG5vZGVbJ3BhcnNlZENzc1RleHQnXSA9IG5vZGVbJ2Nzc1RleHQnXSA9IHQudHJpbSgpOwogICAgICBpZiAobm9kZVsncGFyZW50J10pIHsKICAgICAgICBsZXQgc3MgPSBub2RlWydwcmV2aW91cyddID8gbm9kZVsncHJldmlvdXMnXVsnZW5kJ10gOiBub2RlWydwYXJlbnQnXVsnc3RhcnQnXTsKICAgICAgICB0ID0gdGV4dC5zdWJzdHJpbmcoc3MsIG5vZGVbJ3N0YXJ0J10gLSAxKTsKICAgICAgICB0ID0gX2V4cGFuZFVuaWNvZGVFc2NhcGVzKHQpOwogICAgICAgIHQgPSB0LnJlcGxhY2UoUlgubXVsdGlwbGVTcGFjZXMsICcgJyk7CiAgICAgICAgLy8gVE9ETyhzb3J2ZWxsKTogYWQgaG9jOyBtYWtlIHNlbGVjdG9yIGluY2x1ZGUgb25seSBhZnRlciBsYXN0IDsKICAgICAgICAvLyBoZWxwcyB3aXRoIG1peGluIHN5bnRheAogICAgICAgIHQgPSB0LnN1YnN0cmluZyh0Lmxhc3RJbmRleE9mKCc7JykgKyAxKTsKICAgICAgICBsZXQgcyA9IG5vZGVbJ3BhcnNlZFNlbGVjdG9yJ10gPSBub2RlWydzZWxlY3RvciddID0gdC50cmltKCk7CiAgICAgICAgbm9kZVsnYXRSdWxlJ10gPSAocy5pbmRleE9mKEFUX1NUQVJUKSA9PT0gMCk7CiAgICAgICAgLy8gbm90ZSwgc3VwcG9ydCBhIHN1YnNldCBvZiBydWxlIHR5cGVzLi4uCiAgICAgICAgaWYgKG5vZGVbJ2F0UnVsZSddKSB7CiAgICAgICAgICBpZiAocy5pbmRleE9mKE1FRElBX1NUQVJUKSA9PT0gMCkgewogICAgICAgICAgICBub2RlWyd0eXBlJ10gPSB0eXBlcy5NRURJQV9SVUxFOwogICAgICAgICAgfSBlbHNlIGlmIChzLm1hdGNoKFJYLmtleWZyYW1lc1J1bGUpKSB7CiAgICAgICAgICAgIG5vZGVbJ3R5cGUnXSA9IHR5cGVzLktFWUZSQU1FU19SVUxFOwogICAgICAgICAgICBub2RlWydrZXlmcmFtZXNOYW1lJ10gPQogICAgICAgICAgICAgIG5vZGVbJ3NlbGVjdG9yJ10uc3BsaXQoUlgubXVsdGlwbGVTcGFjZXMpLnBvcCgpOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAocy5pbmRleE9mKFZBUl9TVEFSVCkgPT09IDApIHsKICAgICAgICAgICAgbm9kZVsndHlwZSddID0gdHlwZXMuTUlYSU5fUlVMRTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vZGVbJ3R5cGUnXSA9IHR5cGVzLlNUWUxFX1JVTEU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIGxldCByJCA9IG5vZGVbJ3J1bGVzJ107CiAgICAgIGlmIChyJCkgewogICAgICAgIGZvciAobGV0IGkgPSAwLCBsID0gciQubGVuZ3RoLCByOwogICAgICAgICAgKGkgPCBsKSAmJiAociA9IHIkW2ldKTsgaSsrKSB7CiAgICAgICAgICBwYXJzZUNzcyhyLCB0ZXh0KTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgLyoqCiAgICAgKiBjb252ZXJzaW9uIG9mIHNvcnQgdW5pY29kZSBlc2NhcGVzIHdpdGggc3BhY2VzIGxpa2UgYFwzMyBgIChhbmQgbG9uZ2VyKSBpbnRvCiAgICAgKiBleHBhbmRlZCBmb3JtIHRoYXQgZG9lc24ndCByZXF1aXJlIHRyYWlsaW5nIHNwYWNlIGBcMDAwMDMzYAogICAgICogQHBhcmFtIHtzdHJpbmd9IHMKICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAqLwogICAgZnVuY3Rpb24gX2V4cGFuZFVuaWNvZGVFc2NhcGVzKHMpIHsKICAgICAgcmV0dXJuIHMucmVwbGFjZSgvXFwoWzAtOWEtZl17MSw2fSlccy9naSwgZnVuY3Rpb24oKSB7CiAgICAgICAgbGV0IGNvZGUgPSBhcmd1bWVudHNbMV0sCiAgICAgICAgICByZXBlYXQgPSA2IC0gY29kZS5sZW5ndGg7CiAgICAgICAgd2hpbGUgKHJlcGVhdC0tKSB7CiAgICAgICAgICBjb2RlID0gJzAnICsgY29kZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuICdcXCcgKyBjb2RlOwogICAgICB9KTsKICAgIH0KCiAgICAvKioKICAgICAqIHN0cmluZ2lmeSBwYXJzZWQgY3NzLgogICAgICogQHBhcmFtIHtTdHlsZU5vZGV9IG5vZGUKICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IHByZXNlcnZlUHJvcGVydGllcwogICAgICogQHBhcmFtIHtzdHJpbmc9fSB0ZXh0CiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0cmluZ2lmeShub2RlLCBwcmVzZXJ2ZVByb3BlcnRpZXMsIHRleHQgPSAnJykgewogICAgICAvLyBjYWxjIHJ1bGUgY3NzVGV4dAogICAgICBsZXQgY3NzVGV4dCA9ICcnOwogICAgICBpZiAobm9kZVsnY3NzVGV4dCddIHx8IG5vZGVbJ3J1bGVzJ10pIHsKICAgICAgICBsZXQgciQgPSBub2RlWydydWxlcyddOwogICAgICAgIGlmIChyJCAmJiAhX2hhc01peGluUnVsZXMociQpKSB7CiAgICAgICAgICBmb3IgKGxldCBpID0gMCwgbCA9IHIkLmxlbmd0aCwgcjsKICAgICAgICAgICAgKGkgPCBsKSAmJiAociA9IHIkW2ldKTsgaSsrKSB7CiAgICAgICAgICAgIGNzc1RleHQgPSBzdHJpbmdpZnkociwgcHJlc2VydmVQcm9wZXJ0aWVzLCBjc3NUZXh0KTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgY3NzVGV4dCA9IHByZXNlcnZlUHJvcGVydGllcyA/IG5vZGVbJ2Nzc1RleHQnXSA6CiAgICAgICAgICAgIHJlbW92ZUN1c3RvbVByb3BzKG5vZGVbJ2Nzc1RleHQnXSk7CiAgICAgICAgICBjc3NUZXh0ID0gY3NzVGV4dC50cmltKCk7CiAgICAgICAgICBpZiAoY3NzVGV4dCkgewogICAgICAgICAgICBjc3NUZXh0ID0gJyAgJyArIGNzc1RleHQgKyAnXG4nOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICAvLyBlbWl0IHJ1bGUgaWYgdGhlcmUgaXMgY3NzVGV4dAogICAgICBpZiAoY3NzVGV4dCkgewogICAgICAgIGlmIChub2RlWydzZWxlY3RvciddKSB7CiAgICAgICAgICB0ZXh0ICs9IG5vZGVbJ3NlbGVjdG9yJ10gKyAnICcgKyBPUEVOX0JSQUNFICsgJ1xuJzsKICAgICAgICB9CiAgICAgICAgdGV4dCArPSBjc3NUZXh0OwogICAgICAgIGlmIChub2RlWydzZWxlY3RvciddKSB7CiAgICAgICAgICB0ZXh0ICs9IENMT1NFX0JSQUNFICsgJ1xuXG4nOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGV4dDsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7QXJyYXk8U3R5bGVOb2RlPn0gcnVsZXMKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgKi8KICAgIGZ1bmN0aW9uIF9oYXNNaXhpblJ1bGVzKHJ1bGVzKSB7CiAgICAgIGxldCByID0gcnVsZXNbMF07CiAgICAgIHJldHVybiBCb29sZWFuKHIpICYmIEJvb2xlYW4oclsnc2VsZWN0b3InXSkgJiYgclsnc2VsZWN0b3InXS5pbmRleE9mKFZBUl9TVEFSVCkgPT09IDA7CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY3NzVGV4dAogICAgICogQHJldHVybiB7c3RyaW5nfQogICAgICovCiAgICBmdW5jdGlvbiByZW1vdmVDdXN0b21Qcm9wcyhjc3NUZXh0KSB7CiAgICAgIGNzc1RleHQgPSByZW1vdmVDdXN0b21Qcm9wQXNzaWdubWVudChjc3NUZXh0KTsKICAgICAgcmV0dXJuIHJlbW92ZUN1c3RvbVByb3BBcHBseShjc3NUZXh0KTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NUZXh0CiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHJlbW92ZUN1c3RvbVByb3BBc3NpZ25tZW50KGNzc1RleHQpIHsKICAgICAgcmV0dXJuIGNzc1RleHQKICAgICAgICAucmVwbGFjZShSWC5jdXN0b21Qcm9wLCAnJykKICAgICAgICAucmVwbGFjZShSWC5taXhpblByb3AsICcnKTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NUZXh0CiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHJlbW92ZUN1c3RvbVByb3BBcHBseShjc3NUZXh0KSB7CiAgICAgIHJldHVybiBjc3NUZXh0CiAgICAgICAgLnJlcGxhY2UoUlgubWl4aW5BcHBseSwgJycpCiAgICAgICAgLnJlcGxhY2UoUlgudmFyQXBwbHksICcnKTsKICAgIH0KCiAgICAvKiogQGVudW0ge251bWJlcn0gKi8KICAgIGNvbnN0IHR5cGVzID0gewogICAgICBTVFlMRV9SVUxFOiAxLAogICAgICBLRVlGUkFNRVNfUlVMRTogNywKICAgICAgTUVESUFfUlVMRTogNCwKICAgICAgTUlYSU5fUlVMRTogMTAwMAogICAgfTsKCiAgICBjb25zdCBPUEVOX0JSQUNFID0gJ3snOwogICAgY29uc3QgQ0xPU0VfQlJBQ0UgPSAnfSc7CgogICAgLy8gaGVscGVyIHJlZ2V4cCdzCiAgICBjb25zdCBSWCA9IHsKICAgICAgY29tbWVudHM6IC9cL1wqW14qXSpcKisoW14vKl1bXipdKlwqKykqXC8vZ2ltLAogICAgICBwb3J0OiAvQGltcG9ydFteO10qOy9naW0sCiAgICAgIGN1c3RvbVByb3A6IC8oPzpeW147XC1cc31dKyk/LS1bXjt7fV0qPzpbXnt9O10qPyg/Ols7XG5dfCQpL2dpbSwKICAgICAgbWl4aW5Qcm9wOiAvKD86XlteO1wtXHN9XSspPy0tW147e31dKj86W157fTtdKj97W159XSo/fSg/Ols7XG5dfCQpPy9naW0sCiAgICAgIG1peGluQXBwbHk6IC9AYXBwbHlccypcKD9bXik7XSpcKT9ccyooPzpbO1xuXXwkKT8vZ2ltLAogICAgICB2YXJBcHBseTogL1teOzpdKj86W147XSo/dmFyXChbXjtdKlwpKD86Wztcbl18JCk/L2dpbSwKICAgICAga2V5ZnJhbWVzUnVsZTogL15AW15cc10qa2V5ZnJhbWVzLywKICAgICAgbXVsdGlwbGVTcGFjZXM6IC9ccysvZwogICAgfTsKCiAgICBjb25zdCBWQVJfU1RBUlQgPSAnLS0nOwogICAgY29uc3QgTUVESUFfU1RBUlQgPSAnQG1lZGlhJzsKICAgIGNvbnN0IEFUX1NUQVJUID0gJ0AnOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgVkFSX0FTU0lHTiA9IC8oPzpefFs7XHN7XVxzKikoLS1bXHctXSo/KVxzKjpccyooPzooKD86Jyg/OlxcJ3wuKSo/J3wiKD86XFwifC4pKj8ifFwoW14pXSo/XCl8W159O3tdKSspfFx7KFtefV0qKVx9KD86KD89Wztcc31dKXwkKSkvZ2k7CiAgICBjb25zdCBNSVhJTl9NQVRDSCA9IC8oPzpefFxXKylAYXBwbHlccypcKD8oW14pO1xuXSopXCk/L2dpOwogICAgY29uc3QgTUVESUFfTUFUQ0ggPSAvQG1lZGlhXHMoLiopLzsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKiBAdHlwZSB7IVNldDxzdHJpbmc+fSAqLwogICAgY29uc3Qgc3R5bGVUZXh0U2V0ID0gbmV3IFNldCgpOwoKICAgIGNvbnN0IHNjb3BpbmdBdHRyaWJ1dGUgPSAnc2hhZHktdW5zY29wZWQnOwoKICAgIC8qKgogICAgICogQWRkIGEgc3BlY2lmaWNhbGx5LW1hcmtlZCBzdHlsZSB0byB0aGUgZG9jdW1lbnQgZGlyZWN0bHksIGFuZCBvbmx5IG9uZSBjb3B5IG9mIHRoYXQgc3R5bGUuCiAgICAgKgogICAgICogQHBhcmFtIHshSFRNTFN0eWxlRWxlbWVudH0gc3R5bGUKICAgICAqIEByZXR1cm4ge3VuZGVmaW5lZH0KICAgICAqLwogICAgZnVuY3Rpb24gcHJvY2Vzc1Vuc2NvcGVkU3R5bGUoc3R5bGUpIHsKICAgICAgY29uc3QgdGV4dCA9IHN0eWxlLnRleHRDb250ZW50OwogICAgICBpZiAoIXN0eWxlVGV4dFNldC5oYXModGV4dCkpIHsKICAgICAgICBzdHlsZVRleHRTZXQuYWRkKHRleHQpOwogICAgICAgIGNvbnN0IG5ld1N0eWxlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKTsKICAgICAgICBuZXdTdHlsZS5zZXRBdHRyaWJ1dGUoJ3NoYWR5LXVuc2NvcGVkJywgJycpOwogICAgICAgIG5ld1N0eWxlLnRleHRDb250ZW50ID0gdGV4dDsKICAgICAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKG5ld1N0eWxlKTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQ2hlY2sgaWYgYSBzdHlsZSBpcyBzdXBwb3NlZCB0byBiZSB1bnNjb3BlZAogICAgICogQHBhcmFtIHshSFRNTFN0eWxlRWxlbWVudH0gc3R5bGUKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IHRydWUgaWYgdGhlIHN0eWxlIGhhcyB0aGUgdW5zY29waW5nIGF0dHJpYnV0ZQogICAgICovCiAgICBmdW5jdGlvbiBpc1Vuc2NvcGVkU3R5bGUoc3R5bGUpIHsKICAgICAgcmV0dXJuIHN0eWxlLmhhc0F0dHJpYnV0ZShzY29waW5nQXR0cmlidXRlKTsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd8U3R5bGVOb2RlfSBydWxlcwogICAgICogQHBhcmFtIHtmdW5jdGlvbihTdHlsZU5vZGUpPX0gY2FsbGJhY2sKICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAqLwogICAgZnVuY3Rpb24gdG9Dc3NUZXh0IChydWxlcywgY2FsbGJhY2spIHsKICAgICAgaWYgKCFydWxlcykgewogICAgICAgIHJldHVybiAnJzsKICAgICAgfQogICAgICBpZiAodHlwZW9mIHJ1bGVzID09PSAnc3RyaW5nJykgewogICAgICAgIHJ1bGVzID0gcGFyc2UocnVsZXMpOwogICAgICB9CiAgICAgIGlmIChjYWxsYmFjaykgewogICAgICAgIGZvckVhY2hSdWxlKHJ1bGVzLCBjYWxsYmFjayk7CiAgICAgIH0KICAgICAgcmV0dXJuIHN0cmluZ2lmeShydWxlcywgbmF0aXZlQ3NzVmFyaWFibGVzKTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7SFRNTFN0eWxlRWxlbWVudH0gc3R5bGUKICAgICAqIEByZXR1cm4ge1N0eWxlTm9kZX0KICAgICAqLwogICAgZnVuY3Rpb24gcnVsZXNGb3JTdHlsZShzdHlsZSkgewogICAgICBpZiAoIXN0eWxlWydfX2Nzc1J1bGVzJ10gJiYgc3R5bGUudGV4dENvbnRlbnQpIHsKICAgICAgICBzdHlsZVsnX19jc3NSdWxlcyddID0gcGFyc2Uoc3R5bGUudGV4dENvbnRlbnQpOwogICAgICB9CiAgICAgIHJldHVybiBzdHlsZVsnX19jc3NSdWxlcyddIHx8IG51bGw7CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0ge1N0eWxlTm9kZX0gbm9kZQogICAgICogQHBhcmFtIHtGdW5jdGlvbj19IHN0eWxlUnVsZUNhbGxiYWNrCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9uPX0ga2V5ZnJhbWVzUnVsZUNhbGxiYWNrCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW49fSBvbmx5QWN0aXZlUnVsZXMKICAgICAqLwogICAgZnVuY3Rpb24gZm9yRWFjaFJ1bGUobm9kZSwgc3R5bGVSdWxlQ2FsbGJhY2ssIGtleWZyYW1lc1J1bGVDYWxsYmFjaywgb25seUFjdGl2ZVJ1bGVzKSB7CiAgICAgIGlmICghbm9kZSkgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICBsZXQgc2tpcFJ1bGVzID0gZmFsc2U7CiAgICAgIGxldCB0eXBlID0gbm9kZVsndHlwZSddOwogICAgICBpZiAob25seUFjdGl2ZVJ1bGVzKSB7CiAgICAgICAgaWYgKHR5cGUgPT09IHR5cGVzLk1FRElBX1JVTEUpIHsKICAgICAgICAgIGxldCBtYXRjaE1lZGlhID0gbm9kZVsnc2VsZWN0b3InXS5tYXRjaChNRURJQV9NQVRDSCk7CiAgICAgICAgICBpZiAobWF0Y2hNZWRpYSkgewogICAgICAgICAgICAvLyBpZiBydWxlIGlzIGEgbm9uIG1hdGNoaW5nIEBtZWRpYSBydWxlLCBza2lwIHN1YnJ1bGVzCiAgICAgICAgICAgIGlmICghd2luZG93Lm1hdGNoTWVkaWEobWF0Y2hNZWRpYVsxXSkubWF0Y2hlcykgewogICAgICAgICAgICAgIHNraXBSdWxlcyA9IHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKHR5cGUgPT09IHR5cGVzLlNUWUxFX1JVTEUpIHsKICAgICAgICBzdHlsZVJ1bGVDYWxsYmFjayhub2RlKTsKICAgICAgfSBlbHNlIGlmIChrZXlmcmFtZXNSdWxlQ2FsbGJhY2sgJiYKICAgICAgICB0eXBlID09PSB0eXBlcy5LRVlGUkFNRVNfUlVMRSkgewogICAgICAgIGtleWZyYW1lc1J1bGVDYWxsYmFjayhub2RlKTsKICAgICAgfSBlbHNlIGlmICh0eXBlID09PSB0eXBlcy5NSVhJTl9SVUxFKSB7CiAgICAgICAgc2tpcFJ1bGVzID0gdHJ1ZTsKICAgICAgfQogICAgICBsZXQgciQgPSBub2RlWydydWxlcyddOwogICAgICBpZiAociQgJiYgIXNraXBSdWxlcykgewogICAgICAgIGZvciAobGV0IGk9MCwgbD1yJC5sZW5ndGgsIHI7IChpPGwpICYmIChyPXIkW2ldKTsgaSsrKSB7CiAgICAgICAgICBmb3JFYWNoUnVsZShyLCBzdHlsZVJ1bGVDYWxsYmFjaywga2V5ZnJhbWVzUnVsZUNhbGxiYWNrLCBvbmx5QWN0aXZlUnVsZXMpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogV2FsayBmcm9tIHRleHRbc3RhcnRdIG1hdGNoaW5nIHBhcmVucyBhbmQKICAgICAqIHJldHVybnMgcG9zaXRpb24gb2YgdGhlIG91dGVyIGVuZCBwYXJlbgogICAgICogQHBhcmFtIHtzdHJpbmd9IHRleHQKICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzdGFydAogICAgICogQHJldHVybiB7bnVtYmVyfQogICAgICovCiAgICBmdW5jdGlvbiBmaW5kTWF0Y2hpbmdQYXJlbih0ZXh0LCBzdGFydCkgewogICAgICBsZXQgbGV2ZWwgPSAwOwogICAgICBmb3IgKGxldCBpPXN0YXJ0LCBsPXRleHQubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgaWYgKHRleHRbaV0gPT09ICcoJykgewogICAgICAgICAgbGV2ZWwrKzsKICAgICAgICB9IGVsc2UgaWYgKHRleHRbaV0gPT09ICcpJykgewogICAgICAgICAgaWYgKC0tbGV2ZWwgPT09IDApIHsKICAgICAgICAgICAgcmV0dXJuIGk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiAtMTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzdHIKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oc3RyaW5nLCBzdHJpbmcsIHN0cmluZywgc3RyaW5nKX0gY2FsbGJhY2sKICAgICAqLwogICAgZnVuY3Rpb24gcHJvY2Vzc1ZhcmlhYmxlQW5kRmFsbGJhY2soc3RyLCBjYWxsYmFjaykgewogICAgICAvLyBmaW5kICd2YXIoJwogICAgICBsZXQgc3RhcnQgPSBzdHIuaW5kZXhPZigndmFyKCcpOwogICAgICBpZiAoc3RhcnQgPT09IC0xKSB7CiAgICAgICAgLy8gbm8gdmFyPywgZXZlcnl0aGluZyBpcyBwcmVmaXgKICAgICAgICByZXR1cm4gY2FsbGJhY2soc3RyLCAnJywgJycsICcnKTsKICAgICAgfQogICAgICAvLyR7cHJlZml4fXZhcigke2lubmVyfSkke3N1ZmZpeH0KICAgICAgbGV0IGVuZCA9IGZpbmRNYXRjaGluZ1BhcmVuKHN0ciwgc3RhcnQgKyAzKTsKICAgICAgbGV0IGlubmVyID0gc3RyLnN1YnN0cmluZyhzdGFydCArIDQsIGVuZCk7CiAgICAgIGxldCBwcmVmaXggPSBzdHIuc3Vic3RyaW5nKDAsIHN0YXJ0KTsKICAgICAgLy8gc3VmZml4IG1heSBoYXZlIG90aGVyIHZhcmlhYmxlcwogICAgICBsZXQgc3VmZml4ID0gcHJvY2Vzc1ZhcmlhYmxlQW5kRmFsbGJhY2soc3RyLnN1YnN0cmluZyhlbmQgKyAxKSwgY2FsbGJhY2spOwogICAgICBsZXQgY29tbWEgPSBpbm5lci5pbmRleE9mKCcsJyk7CiAgICAgIC8vIHZhbHVlIGFuZCBmYWxsYmFjayBhcmdzIHNob3VsZCBiZSB0cmltbWVkIHRvIG1hdGNoIGluIHByb3BlcnR5IGxvb2t1cAogICAgICBpZiAoY29tbWEgPT09IC0xKSB7CiAgICAgICAgLy8gdmFyaWFibGUsIG5vIGZhbGxiYWNrCiAgICAgICAgcmV0dXJuIGNhbGxiYWNrKHByZWZpeCwgaW5uZXIudHJpbSgpLCAnJywgc3VmZml4KTsKICAgICAgfQogICAgICAvLyB2YXIoJHt2YWx1ZX0sJHtmYWxsYmFja30pCiAgICAgIGxldCB2YWx1ZSA9IGlubmVyLnN1YnN0cmluZygwLCBjb21tYSkudHJpbSgpOwogICAgICBsZXQgZmFsbGJhY2sgPSBpbm5lci5zdWJzdHJpbmcoY29tbWEgKyAxKS50cmltKCk7CiAgICAgIHJldHVybiBjYWxsYmFjayhwcmVmaXgsIHZhbHVlLCBmYWxsYmFjaywgc3VmZml4KTsKICAgIH0KCiAgICAvKioKICAgICAqIEB0eXBlIHtmdW5jdGlvbigqKToqfQogICAgICovCiAgICBjb25zdCB3cmFwJDEgPSB3aW5kb3dbJ1NoYWR5RE9NJ10gJiYgd2luZG93WydTaGFkeURPTSddWyd3cmFwJ10gfHwgKChub2RlKSA9PiBub2RlKTsKCiAgICAvKioKICAgICAqIEBwYXJhbSB7RWxlbWVudCB8IHtpczogc3RyaW5nLCBleHRlbmRzOiBzdHJpbmd9fSBlbGVtZW50CiAgICAgKiBAcmV0dXJuIHt7aXM6IHN0cmluZywgdHlwZUV4dGVuc2lvbjogc3RyaW5nfX0KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0SXNFeHRlbmRzKGVsZW1lbnQpIHsKICAgICAgbGV0IGxvY2FsTmFtZSA9IGVsZW1lbnRbJ2xvY2FsTmFtZSddOwogICAgICBsZXQgaXMgPSAnJywgdHlwZUV4dGVuc2lvbiA9ICcnOwogICAgICAvKgogICAgICBOT1RFOiB0ZWNobmljYWxseSwgdGhpcyBjYW4gYmUgd3JvbmcgZm9yIGNlcnRhaW4gc3ZnIGVsZW1lbnRzCiAgICAgIHdpdGggYC1gIGluIHRoZSBuYW1lIGxpa2UgYDxmb250LWZhY2U+YAogICAgICAqLwogICAgICBpZiAobG9jYWxOYW1lKSB7CiAgICAgICAgaWYgKGxvY2FsTmFtZS5pbmRleE9mKCctJykgPiAtMSkgewogICAgICAgICAgaXMgPSBsb2NhbE5hbWU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHR5cGVFeHRlbnNpb24gPSBsb2NhbE5hbWU7CiAgICAgICAgICBpcyA9IChlbGVtZW50LmdldEF0dHJpYnV0ZSAmJiBlbGVtZW50LmdldEF0dHJpYnV0ZSgnaXMnKSkgfHwgJyc7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIGlzID0gLyoqIEB0eXBlIHs/fSAqLyhlbGVtZW50KS5pczsKICAgICAgICB0eXBlRXh0ZW5zaW9uID0gLyoqIEB0eXBlIHs/fSAqLyhlbGVtZW50KS5leHRlbmRzOwogICAgICB9CiAgICAgIHJldHVybiB7aXMsIHR5cGVFeHRlbnNpb259OwogICAgfQoKICAgIC8qKgogICAgICogQHBhcmFtIHtFbGVtZW50fERvY3VtZW50RnJhZ21lbnR9IGVsZW1lbnQKICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAqLwogICAgZnVuY3Rpb24gZ2F0aGVyU3R5bGVUZXh0KGVsZW1lbnQpIHsKICAgICAgLyoqIEB0eXBlIHshQXJyYXk8c3RyaW5nPn0gKi8KICAgICAgY29uc3Qgc3R5bGVUZXh0UGFydHMgPSBbXTsKICAgICAgY29uc3Qgc3R5bGVzID0gLyoqIEB0eXBlIHshTm9kZUxpc3Q8IUhUTUxTdHlsZUVsZW1lbnQ+fSAqLyhlbGVtZW50LnF1ZXJ5U2VsZWN0b3JBbGwoJ3N0eWxlJykpOwogICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHN0eWxlcy5sZW5ndGg7IGkrKykgewogICAgICAgIGNvbnN0IHN0eWxlID0gc3R5bGVzW2ldOwogICAgICAgIGlmIChpc1Vuc2NvcGVkU3R5bGUoc3R5bGUpKSB7CiAgICAgICAgICBpZiAoIW5hdGl2ZVNoYWRvdykgewogICAgICAgICAgICBwcm9jZXNzVW5zY29wZWRTdHlsZShzdHlsZSk7CiAgICAgICAgICAgIHN0eWxlLnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQoc3R5bGUpOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBzdHlsZVRleHRQYXJ0cy5wdXNoKHN0eWxlLnRleHRDb250ZW50KTsKICAgICAgICAgIHN0eWxlLnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQoc3R5bGUpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gc3R5bGVUZXh0UGFydHMuam9pbignJykudHJpbSgpOwogICAgfQoKICAgIGNvbnN0IENTU19CVUlMRF9BVFRSID0gJ2Nzcy1idWlsZCc7CgogICAgLyoqCiAgICAgKiBSZXR1cm4gdGhlIHBvbHltZXItY3NzLWJ1aWxkICJidWlsZCB0eXBlIiBhcHBsaWVkIHRvIHRoaXMgZWxlbWVudAogICAgICoKICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSBlbGVtZW50CiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IENhbiBiZSAiIiwgInNoYWR5Iiwgb3IgInNoYWRvdyIKICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Q3NzQnVpbGQoZWxlbWVudCkgewogICAgICBpZiAoY3NzQnVpbGQgIT09IHVuZGVmaW5lZCkgewogICAgICAgIHJldHVybiAvKiogQHR5cGUge3N0cmluZ30gKi8oY3NzQnVpbGQpOwogICAgICB9CiAgICAgIGlmIChlbGVtZW50Ll9fY3NzQnVpbGQgPT09IHVuZGVmaW5lZCkgewogICAgICAgIC8vIHRyeSBhdHRyaWJ1dGUgZmlyc3QsIGFzIGl0IGlzIHRoZSBjb21tb24gY2FzZQogICAgICAgIGNvbnN0IGF0dHJWYWx1ZSA9IGVsZW1lbnQuZ2V0QXR0cmlidXRlKENTU19CVUlMRF9BVFRSKTsKICAgICAgICBpZiAoYXR0clZhbHVlKSB7CiAgICAgICAgICBlbGVtZW50Ll9fY3NzQnVpbGQgPSBhdHRyVmFsdWU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGNvbnN0IGJ1aWxkQ29tbWVudCA9IGdldEJ1aWxkQ29tbWVudChlbGVtZW50KTsKICAgICAgICAgIGlmIChidWlsZENvbW1lbnQgIT09ICcnKSB7CiAgICAgICAgICAgIC8vIHJlbW92ZSBidWlsZCBjb21tZW50IHNvIGl0IGlzIG5vdCBuZWVkbGVzc2x5IGNvcGllZCBpbnRvIGV2ZXJ5IGVsZW1lbnQgaW5zdGFuY2UKICAgICAgICAgICAgcmVtb3ZlQnVpbGRDb21tZW50KGVsZW1lbnQpOwogICAgICAgICAgfQogICAgICAgICAgZWxlbWVudC5fX2Nzc0J1aWxkID0gYnVpbGRDb21tZW50OwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gZWxlbWVudC5fX2Nzc0J1aWxkIHx8ICcnOwogICAgfQoKICAgIC8qKgogICAgICogQ2hlY2sgaWYgdGhlIGdpdmVuIGVsZW1lbnQsIGVpdGhlciBhIDx0ZW1wbGF0ZT4gb3IgPHN0eWxlPiwgaGFzIGJlZW4gcHJvY2Vzc2VkCiAgICAgKiBieSBwb2x5bWVyLWNzcy1idWlsZC4KICAgICAqCiAgICAgKiBJZiBzbywgdGhlbiB3ZSBjYW4gbWFrZSBhIG51bWJlciBvZiBvcHRpbWl6YXRpb25zOgogICAgICogLSBwb2x5bWVyLWNzcy1idWlsZCB3aWxsIGRlY29tcG9zZSBtaXhpbnMgaW50byBpbmRpdmlkdWFsIENTUyBDdXN0b20gUHJvcGVydGllcywKICAgICAqIHNvIHRoZSBBcHBseVNoaW0gY2FuIGJlIHNraXBwZWQgZW50aXJlbHkuCiAgICAgKiAtIFVuZGVyIG5hdGl2ZSBTaGFkb3dET00sIHRoZSBzdHlsZSB0ZXh0IGNhbiBqdXN0IGJlIGNvcGllZCBpbnRvIGVhY2ggaW5zdGFuY2UKICAgICAqIHdpdGhvdXQgbW9kaWZpY2F0aW9uCiAgICAgKiAtIElmIHRoZSBidWlsZCBpcyAic2hhZHkiIGFuZCBTaGFkeURPTSBpcyBpbiB1c2UsIHRoZSBzdHlsaW5nIGRvZXMgbm90IG5lZWQKICAgICAqIHNjb3BpbmcgYmV5b25kIHRoZSBzaGltbWluZyBvZiBDU1MgQ3VzdG9tIFByb3BlcnRpZXMKICAgICAqCiAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWxlbWVudAogICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAqLwogICAgZnVuY3Rpb24gZWxlbWVudEhhc0J1aWx0Q3NzKGVsZW1lbnQpIHsKICAgICAgcmV0dXJuIGdldENzc0J1aWxkKGVsZW1lbnQpICE9PSAnJzsKICAgIH0KCiAgICAvKioKICAgICAqIEZvciB0ZW1wbGF0ZXMgbWFkZSB3aXRoIHRhZ2dlZCB0ZW1wbGF0ZSBsaXRlcmFscywgcG9seW1lci1jc3MtYnVpbGQgd2lsbAogICAgICogaW5zZXJ0IGEgY29tbWVudCBvZiB0aGUgZm9ybSBgPCEtLWNzcy1idWlsZDpzaGFkb3ctLT5gCiAgICAgKgogICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0QnVpbGRDb21tZW50KGVsZW1lbnQpIHsKICAgICAgY29uc3QgYnVpbGRDb21tZW50ID0gZWxlbWVudC5sb2NhbE5hbWUgPT09ICd0ZW1wbGF0ZScgPwogICAgICAgICAgLyoqIEB0eXBlIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKGVsZW1lbnQpLmNvbnRlbnQuZmlyc3RDaGlsZCA6CiAgICAgICAgICBlbGVtZW50LmZpcnN0Q2hpbGQ7CiAgICAgIGlmIChidWlsZENvbW1lbnQgaW5zdGFuY2VvZiBDb21tZW50KSB7CiAgICAgICAgY29uc3QgY29tbWVudFBhcnRzID0gYnVpbGRDb21tZW50LnRleHRDb250ZW50LnRyaW0oKS5zcGxpdCgnOicpOwogICAgICAgIGlmIChjb21tZW50UGFydHNbMF0gPT09IENTU19CVUlMRF9BVFRSKSB7CiAgICAgICAgICByZXR1cm4gY29tbWVudFBhcnRzWzFdOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gJyc7CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWxlbWVudAogICAgICovCiAgICBmdW5jdGlvbiByZW1vdmVCdWlsZENvbW1lbnQoZWxlbWVudCkgewogICAgICBjb25zdCBidWlsZENvbW1lbnQgPSBlbGVtZW50LmxvY2FsTmFtZSA9PT0gJ3RlbXBsYXRlJyA/CiAgICAgICAgICAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fSAqLyAoZWxlbWVudCkuY29udGVudC5maXJzdENoaWxkIDoKICAgICAgICAgIGVsZW1lbnQuZmlyc3RDaGlsZDsKICAgICAgYnVpbGRDb21tZW50LnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQoYnVpbGRDb21tZW50KTsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgKiBAcGFyYW0ge09iamVjdD19IHByb3BlcnRpZXMKICAgICAqLwogICAgZnVuY3Rpb24gdXBkYXRlTmF0aXZlUHJvcGVydGllcyhlbGVtZW50LCBwcm9wZXJ0aWVzKSB7CiAgICAgIC8vIHJlbW92ZSBwcmV2aW91cyBwcm9wZXJ0aWVzCiAgICAgIGZvciAobGV0IHAgaW4gcHJvcGVydGllcykgewogICAgICAgIC8vIE5PVEU6IGZvciBiYyB3aXRoIHNoaW0sIGRvbid0IGFwcGx5IG51bGwgdmFsdWVzLgogICAgICAgIGlmIChwID09PSBudWxsKSB7CiAgICAgICAgICBlbGVtZW50LnN0eWxlLnJlbW92ZVByb3BlcnR5KHApOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlbGVtZW50LnN0eWxlLnNldFByb3BlcnR5KHAsIHByb3BlcnRpZXNbcF0pOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkKICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Q29tcHV0ZWRTdHlsZVZhbHVlKGVsZW1lbnQsIHByb3BlcnR5KSB7CiAgICAgIC8qKgogICAgICAgKiBAY29uc3Qge3N0cmluZ30KICAgICAgICovCiAgICAgIGNvbnN0IHZhbHVlID0gd2luZG93LmdldENvbXB1dGVkU3R5bGUoZWxlbWVudCkuZ2V0UHJvcGVydHlWYWx1ZShwcm9wZXJ0eSk7CiAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICByZXR1cm4gJyc7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHZhbHVlLnRyaW0oKTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogcmV0dXJuIHRydWUgaWYgYGNzc1RleHRgIGNvbnRhaW5zIGEgbWl4aW4gZGVmaW5pdGlvbiBvciBjb25zdW1wdGlvbgogICAgICogQHBhcmFtIHtzdHJpbmd9IGNzc1RleHQKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgKi8KICAgIGZ1bmN0aW9uIGRldGVjdE1peGluKGNzc1RleHQpIHsKICAgICAgY29uc3QgaGFzID0gTUlYSU5fTUFUQ0gudGVzdChjc3NUZXh0KSB8fCBWQVJfQVNTSUdOLnRlc3QoY3NzVGV4dCk7CiAgICAgIC8vIHJlc2V0IHN0YXRlIG9mIHRoZSByZWdleGVzCiAgICAgIE1JWElOX01BVENILmxhc3RJbmRleCA9IDA7CiAgICAgIFZBUl9BU1NJR04ubGFzdEluZGV4ID0gMDsKICAgICAgcmV0dXJuIGhhczsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNvbnN0IEFQUExZX05BTUVfQ0xFQU4gPSAvO1xzKi9tOwogICAgY29uc3QgSU5JVElBTF9JTkhFUklUID0gL15ccyooaW5pdGlhbCl8KGluaGVyaXQpXHMqJC87CiAgICBjb25zdCBJTVBPUlRBTlQgPSAvXHMqIWltcG9ydGFudC87CgogICAgLy8gc2VwYXJhdG9yIHVzZWQgYmV0d2VlbiBtaXhpbi1uYW1lIGFuZCBtaXhpbi1wcm9wZXJ0eS1uYW1lIHdoZW4gcHJvZHVjaW5nIHByb3BlcnRpZXMKICAgIC8vIE5PVEU6IHBsYWluICctJyBtYXkgY2F1c2UgY29sbGlzaW9ucyBpbiB1c2VyIHN0eWxlcwogICAgY29uc3QgTUlYSU5fVkFSX1NFUCA9ICdfLV8nOwoKICAgIC8vIG1hcCBvZiBtaXhpbiB0byBwcm9wZXJ0eSBuYW1lcwogICAgLy8gLS1mb286IHtib3JkZXI6IDJweH0gLT4ge3Byb3BlcnRpZXM6IHsoLS1mb28sIFsnYm9yZGVyJ10pfSwgZGVwZW5kYW50czogeydlbGVtZW50LW5hbWUnOiBwcm90b319CiAgICBjbGFzcyBNaXhpbk1hcCB7CiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIC8qKiBAdHlwZSB7IU9iamVjdDxzdHJpbmcsICFNaXhpbk1hcEVudHJ5Pn0gKi8KICAgICAgICB0aGlzLl9tYXAgPSB7fTsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUKICAgICAgICogQHBhcmFtIHshUHJvcGVydHlFbnRyeX0gcHJvcHMKICAgICAgICovCiAgICAgIHNldChuYW1lLCBwcm9wcykgewogICAgICAgIG5hbWUgPSBuYW1lLnRyaW0oKTsKICAgICAgICB0aGlzLl9tYXBbbmFtZV0gPSB7CiAgICAgICAgICBwcm9wZXJ0aWVzOiBwcm9wcywKICAgICAgICAgIGRlcGVuZGFudHM6IHt9CiAgICAgICAgfTsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUKICAgICAgICogQHJldHVybiB7TWl4aW5NYXBFbnRyeX0KICAgICAgICovCiAgICAgIGdldChuYW1lKSB7CiAgICAgICAgbmFtZSA9IG5hbWUudHJpbSgpOwogICAgICAgIHJldHVybiB0aGlzLl9tYXBbbmFtZV0gfHwgbnVsbDsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQ2FsbGJhY2sgZm9yIHdoZW4gYW4gZWxlbWVudCBpcyBtYXJrZWQgaW52YWxpZAogICAgICogQHR5cGUgez9mdW5jdGlvbihzdHJpbmcpfQogICAgICovCiAgICBsZXQgaW52YWxpZENhbGxiYWNrID0gbnVsbDsKCiAgICAvKiogQHVucmVzdHJpY3RlZCAqLwogICAgY2xhc3MgQXBwbHlTaGltIHsKICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgLyoqIEB0eXBlIHs/c3RyaW5nfSAqLwogICAgICAgIHRoaXMuX2N1cnJlbnRFbGVtZW50ID0gbnVsbDsKICAgICAgICAvKiogQHR5cGUge0hUTUxNZXRhRWxlbWVudH0gKi8KICAgICAgICB0aGlzLl9tZWFzdXJlRWxlbWVudCA9IG51bGw7CiAgICAgICAgdGhpcy5fbWFwID0gbmV3IE1peGluTWFwKCk7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIHJldHVybiB0cnVlIGlmIGBjc3NUZXh0YCBjb250YWlucyBhIG1peGluIGRlZmluaXRpb24gb3IgY29uc3VtcHRpb24KICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGNzc1RleHQKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICovCiAgICAgIGRldGVjdE1peGluKGNzc1RleHQpIHsKICAgICAgICByZXR1cm4gZGV0ZWN0TWl4aW4oY3NzVGV4dCk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBHYXRoZXIgc3R5bGVzIGludG8gb25lIHN0eWxlIGZvciBlYXNpZXIgcHJvY2Vzc2luZwogICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZQogICAgICAgKiBAcmV0dXJuIHtIVE1MU3R5bGVFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2F0aGVyU3R5bGVzKHRlbXBsYXRlKSB7CiAgICAgICAgY29uc3Qgc3R5bGVUZXh0ID0gZ2F0aGVyU3R5bGVUZXh0KHRlbXBsYXRlLmNvbnRlbnQpOwogICAgICAgIGlmIChzdHlsZVRleHQpIHsKICAgICAgICAgIGNvbnN0IHN0eWxlID0gLyoqIEB0eXBlIHshSFRNTFN0eWxlRWxlbWVudH0gKi8oZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKSk7CiAgICAgICAgICBzdHlsZS50ZXh0Q29udGVudCA9IHN0eWxlVGV4dDsKICAgICAgICAgIHRlbXBsYXRlLmNvbnRlbnQuaW5zZXJ0QmVmb3JlKHN0eWxlLCB0ZW1wbGF0ZS5jb250ZW50LmZpcnN0Q2hpbGQpOwogICAgICAgICAgcmV0dXJuIHN0eWxlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAqIEByZXR1cm4ge1N0eWxlTm9kZX0KICAgICAgICovCiAgICAgIHRyYW5zZm9ybVRlbXBsYXRlKHRlbXBsYXRlLCBlbGVtZW50TmFtZSkgewogICAgICAgIGlmICh0ZW1wbGF0ZS5fZ2F0aGVyZWRTdHlsZSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICB0ZW1wbGF0ZS5fZ2F0aGVyZWRTdHlsZSA9IHRoaXMuZ2F0aGVyU3R5bGVzKHRlbXBsYXRlKTsKICAgICAgICB9CiAgICAgICAgLyoqIEB0eXBlIHtIVE1MU3R5bGVFbGVtZW50fSAqLwogICAgICAgIGNvbnN0IHN0eWxlID0gdGVtcGxhdGUuX2dhdGhlcmVkU3R5bGU7CiAgICAgICAgcmV0dXJuIHN0eWxlID8gdGhpcy50cmFuc2Zvcm1TdHlsZShzdHlsZSwgZWxlbWVudE5hbWUpIDogbnVsbDsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHshSFRNTFN0eWxlRWxlbWVudH0gc3R5bGUKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAqIEByZXR1cm4ge1N0eWxlTm9kZX0KICAgICAgICovCiAgICAgIHRyYW5zZm9ybVN0eWxlKHN0eWxlLCBlbGVtZW50TmFtZSA9ICcnKSB7CiAgICAgICAgbGV0IGFzdCA9IHJ1bGVzRm9yU3R5bGUoc3R5bGUpOwogICAgICAgIHRoaXMudHJhbnNmb3JtUnVsZXMoYXN0LCBlbGVtZW50TmFtZSk7CiAgICAgICAgc3R5bGUudGV4dENvbnRlbnQgPSB0b0Nzc1RleHQoYXN0KTsKICAgICAgICByZXR1cm4gYXN0OwogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0geyFIVE1MU3R5bGVFbGVtZW50fSBzdHlsZQogICAgICAgKiBAcmV0dXJuIHtTdHlsZU5vZGV9CiAgICAgICAqLwogICAgICB0cmFuc2Zvcm1DdXN0b21TdHlsZShzdHlsZSkgewogICAgICAgIGxldCBhc3QgPSBydWxlc0ZvclN0eWxlKHN0eWxlKTsKICAgICAgICBmb3JFYWNoUnVsZShhc3QsIChydWxlKSA9PiB7CiAgICAgICAgICBpZiAocnVsZVsnc2VsZWN0b3InXSA9PT0gJzpyb290JykgewogICAgICAgICAgICBydWxlWydzZWxlY3RvciddID0gJ2h0bWwnOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy50cmFuc2Zvcm1SdWxlKHJ1bGUpOwogICAgICAgIH0pOwogICAgICAgIHN0eWxlLnRleHRDb250ZW50ID0gdG9Dc3NUZXh0KGFzdCk7CiAgICAgICAgcmV0dXJuIGFzdDsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHtTdHlsZU5vZGV9IHJ1bGVzCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBlbGVtZW50TmFtZQogICAgICAgKi8KICAgICAgdHJhbnNmb3JtUnVsZXMocnVsZXMsIGVsZW1lbnROYW1lKSB7CiAgICAgICAgdGhpcy5fY3VycmVudEVsZW1lbnQgPSBlbGVtZW50TmFtZTsKICAgICAgICBmb3JFYWNoUnVsZShydWxlcywgKHIpID0+IHsKICAgICAgICAgIHRoaXMudHJhbnNmb3JtUnVsZShyKTsKICAgICAgICB9KTsKICAgICAgICB0aGlzLl9jdXJyZW50RWxlbWVudCA9IG51bGw7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IVN0eWxlTm9kZX0gcnVsZQogICAgICAgKi8KICAgICAgdHJhbnNmb3JtUnVsZShydWxlKSB7CiAgICAgICAgcnVsZVsnY3NzVGV4dCddID0gdGhpcy50cmFuc2Zvcm1Dc3NUZXh0KHJ1bGVbJ3BhcnNlZENzc1RleHQnXSwgcnVsZSk7CiAgICAgICAgLy8gOnJvb3Qgd2FzIG9ubHkgdXNlZCBmb3IgdmFyaWFibGUgYXNzaWdubWVudCBpbiBwcm9wZXJ0eSBzaGltLAogICAgICAgIC8vIGJ1dCBnZW5lcmF0ZXMgaW52YWxpZCBzZWxlY3RvcnMgd2l0aCByZWFsIHByb3BlcnRpZXMuCiAgICAgICAgLy8gcmVwbGFjZSB3aXRoIGA6aG9zdCA+ICpgLCB3aGljaCBzZXJ2ZXMgdGhlIHNhbWUgZWZmZWN0CiAgICAgICAgaWYgKHJ1bGVbJ3NlbGVjdG9yJ10gPT09ICc6cm9vdCcpIHsKICAgICAgICAgIHJ1bGVbJ3NlbGVjdG9yJ10gPSAnOmhvc3QgPiAqJzsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NUZXh0CiAgICAgICAqIEBwYXJhbSB7IVN0eWxlTm9kZX0gcnVsZQogICAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgICAqLwogICAgICB0cmFuc2Zvcm1Dc3NUZXh0KGNzc1RleHQsIHJ1bGUpIHsKICAgICAgICAvLyBwcm9kdWNlIHZhcmlhYmxlcwogICAgICAgIGNzc1RleHQgPSBjc3NUZXh0LnJlcGxhY2UoVkFSX0FTU0lHTiwgKG1hdGNoVGV4dCwgcHJvcGVydHlOYW1lLCB2YWx1ZVByb3BlcnR5LCB2YWx1ZU1peGluKSA9PgogICAgICAgICAgdGhpcy5fcHJvZHVjZUNzc1Byb3BlcnRpZXMobWF0Y2hUZXh0LCBwcm9wZXJ0eU5hbWUsIHZhbHVlUHJvcGVydHksIHZhbHVlTWl4aW4sIHJ1bGUpKTsKICAgICAgICAvLyBjb25zdW1lIG1peGlucwogICAgICAgIHJldHVybiB0aGlzLl9jb25zdW1lQ3NzUHJvcGVydGllcyhjc3NUZXh0LCBydWxlKTsKICAgICAgfQogICAgICAvKioKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5CiAgICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAgICovCiAgICAgIF9nZXRJbml0aWFsVmFsdWVGb3JQcm9wZXJ0eShwcm9wZXJ0eSkgewogICAgICAgIGlmICghdGhpcy5fbWVhc3VyZUVsZW1lbnQpIHsKICAgICAgICAgIHRoaXMuX21lYXN1cmVFbGVtZW50ID0gLyoqIEB0eXBlIHtIVE1MTWV0YUVsZW1lbnR9ICovKGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ21ldGEnKSk7CiAgICAgICAgICB0aGlzLl9tZWFzdXJlRWxlbWVudC5zZXRBdHRyaWJ1dGUoJ2FwcGx5LXNoaW0tbWVhc3VyZScsICcnKTsKICAgICAgICAgIHRoaXMuX21lYXN1cmVFbGVtZW50LnN0eWxlLmFsbCA9ICdpbml0aWFsJzsKICAgICAgICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGhpcy5fbWVhc3VyZUVsZW1lbnQpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gd2luZG93LmdldENvbXB1dGVkU3R5bGUodGhpcy5fbWVhc3VyZUVsZW1lbnQpLmdldFByb3BlcnR5VmFsdWUocHJvcGVydHkpOwogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBXYWxrIG92ZXIgYWxsIHJ1bGVzIGJlZm9yZSB0aGlzIHJ1bGUgdG8gZmluZCBmYWxsYmFja3MgZm9yIG1peGlucwogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFTdHlsZU5vZGV9IHN0YXJ0UnVsZQogICAgICAgKiBAcmV0dXJuIHshT2JqZWN0fQogICAgICAgKi8KICAgICAgX2ZhbGxiYWNrc0Zyb21QcmV2aW91c1J1bGVzKHN0YXJ0UnVsZSkgewogICAgICAgIC8vIGZpbmQgdGhlICJ0b3AiIHJ1bGUKICAgICAgICBsZXQgdG9wUnVsZSA9IHN0YXJ0UnVsZTsKICAgICAgICB3aGlsZSAodG9wUnVsZVsncGFyZW50J10pIHsKICAgICAgICAgIHRvcFJ1bGUgPSB0b3BSdWxlWydwYXJlbnQnXTsKICAgICAgICB9CiAgICAgICAgY29uc3QgZmFsbGJhY2tzID0ge307CiAgICAgICAgbGV0IHNlZW5TdGFydFJ1bGUgPSBmYWxzZTsKICAgICAgICBmb3JFYWNoUnVsZSh0b3BSdWxlLCAocikgPT4gewogICAgICAgICAgLy8gc3RvcCB3aGVuIHdlIGhpdCB0aGUgaW5wdXQgcnVsZQogICAgICAgICAgc2VlblN0YXJ0UnVsZSA9IHNlZW5TdGFydFJ1bGUgfHwgciA9PT0gc3RhcnRSdWxlOwogICAgICAgICAgaWYgKHNlZW5TdGFydFJ1bGUpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgLy8gTk9URTogT25seSBtYXRjaGluZyBzZWxlY3RvcnMgYXJlICJzYWZlIiBmb3IgdGhpcyBmYWxsYmFjayBwcm9jZXNzaW5nCiAgICAgICAgICAvLyBJdCB3b3VsZCBiZSBwcm9oaWJpdGl2ZSB0byBydW4gYG1hdGNoZXNTZWxlY3RvcigpYCBvbiBlYWNoIHNlbGVjdG9yLAogICAgICAgICAgLy8gc28gd2UgY2hlYXQgYW5kIG9ubHkgY2hlY2sgaWYgdGhlIHNhbWUgc2VsZWN0b3Igc3RyaW5nIGlzIHVzZWQsIHdoaWNoCiAgICAgICAgICAvLyBndWFyYW50ZWVzIHRoaW5ncyBsaWtlIHNwZWNpZmljaXR5IG1hdGNoaW5nCiAgICAgICAgICBpZiAoclsnc2VsZWN0b3InXSA9PT0gc3RhcnRSdWxlWydzZWxlY3RvciddKSB7CiAgICAgICAgICAgIE9iamVjdC5hc3NpZ24oZmFsbGJhY2tzLCB0aGlzLl9jc3NUZXh0VG9NYXAoclsncGFyc2VkQ3NzVGV4dCddKSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGZhbGxiYWNrczsKICAgICAgfQogICAgICAvKioKICAgICAgICogcmVwbGFjZSBtaXhpbiBjb25zdW1wdGlvbiB3aXRoIHZhcmlhYmxlIGNvbnN1bXB0aW9uCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0ZXh0CiAgICAgICAqIEBwYXJhbSB7IVN0eWxlTm9kZT19IHJ1bGUKICAgICAgICogQHJldHVybiB7c3RyaW5nfQogICAgICAgKi8KICAgICAgX2NvbnN1bWVDc3NQcm9wZXJ0aWVzKHRleHQsIHJ1bGUpIHsKICAgICAgICAvKiogQHR5cGUge0FycmF5fSAqLwogICAgICAgIGxldCBtID0gbnVsbDsKICAgICAgICAvLyBsb29wIG92ZXIgdGV4dCB1bnRpbCBhbGwgbWl4aW5zIHdpdGggZGVmaW50aW9ucyBoYXZlIGJlZW4gYXBwbGllZAogICAgICAgIHdoaWxlKChtID0gTUlYSU5fTUFUQ0guZXhlYyh0ZXh0KSkpIHsKICAgICAgICAgIGxldCBtYXRjaFRleHQgPSBtWzBdOwogICAgICAgICAgbGV0IG1peGluTmFtZSA9IG1bMV07CiAgICAgICAgICBsZXQgaWR4ID0gbS5pbmRleDsKICAgICAgICAgIC8vIGNvbGxlY3QgcHJvcGVydGllcyBiZWZvcmUgYXBwbHkgdG8gYmUgImRlZmF1bHRzIiBpZiBtaXhpbiBtaWdodCBvdmVycmlkZSB0aGVtCiAgICAgICAgICAvLyBtYXRjaCBpbmNsdWRlcyBhICJwcmVmaXgiLCBzbyBmaW5kIHRoZSBzdGFydCBhbmQgZW5kIHBvc2l0aW9ucyBvZiBAYXBwbHkKICAgICAgICAgIGxldCBhcHBseVBvcyA9IGlkeCArIG1hdGNoVGV4dC5pbmRleE9mKCdAYXBwbHknKTsKICAgICAgICAgIGxldCBhZnRlckFwcGx5UG9zID0gaWR4ICsgbWF0Y2hUZXh0Lmxlbmd0aDsKICAgICAgICAgIC8vIGZpbmQgcHJvcHMgZGVmaW5lZCBiZWZvcmUgdGhpcyBAYXBwbHkKICAgICAgICAgIGxldCB0ZXh0QmVmb3JlQXBwbHkgPSB0ZXh0LnNsaWNlKDAsIGFwcGx5UG9zKTsKICAgICAgICAgIGxldCB0ZXh0QWZ0ZXJBcHBseSA9IHRleHQuc2xpY2UoYWZ0ZXJBcHBseVBvcyk7CiAgICAgICAgICBsZXQgZGVmYXVsdHMgPSBydWxlID8gdGhpcy5fZmFsbGJhY2tzRnJvbVByZXZpb3VzUnVsZXMocnVsZSkgOiB7fTsKICAgICAgICAgIE9iamVjdC5hc3NpZ24oZGVmYXVsdHMsIHRoaXMuX2Nzc1RleHRUb01hcCh0ZXh0QmVmb3JlQXBwbHkpKTsKICAgICAgICAgIGxldCByZXBsYWNlbWVudCA9IHRoaXMuX2F0QXBwbHlUb0Nzc1Byb3BlcnRpZXMobWl4aW5OYW1lLCBkZWZhdWx0cyk7CiAgICAgICAgICAvLyB1c2UgcmVnZXggbWF0Y2ggcG9zaXRpb24gdG8gcmVwbGFjZSBtaXhpbiwga2VlcCBsaW5lYXIgcHJvY2Vzc2luZyB0aW1lCiAgICAgICAgICB0ZXh0ID0gYCR7dGV4dEJlZm9yZUFwcGx5fSR7cmVwbGFjZW1lbnR9JHt0ZXh0QWZ0ZXJBcHBseX1gOwogICAgICAgICAgLy8gbW92ZSByZWdleCBzZWFyY2ggdG8gX2FmdGVyXyByZXBsYWNlbWVudAogICAgICAgICAgTUlYSU5fTUFUQ0gubGFzdEluZGV4ID0gaWR4ICsgcmVwbGFjZW1lbnQubGVuZ3RoOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGV4dDsKICAgICAgfQogICAgICAvKioKICAgICAgICogcHJvZHVjZSB2YXJpYWJsZSBjb25zdW1wdGlvbiBhdCB0aGUgc2l0ZSBvZiBtaXhpbiBjb25zdW1wdGlvbgogICAgICAgKiBgQGFwcGx5YCAtLWZvbzsgLT4gZm9yIGFsbCBwcm9wcyAoJHtwcm9wbmFtZX06IHZhcigtLWZvb18tXyR7cHJvcG5hbWV9LCAke2ZhbGxiYWNrW3Byb3BuYW1lXX19KSkKICAgICAgICogRXhhbXBsZToKICAgICAgICogIGJvcmRlcjogdmFyKC0tZm9vXy1fYm9yZGVyKTsgcGFkZGluZzogdmFyKC0tZm9vXy1fcGFkZGluZywgMnB4KQogICAgICAgKgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gbWl4aW5OYW1lCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBmYWxsYmFja3MKICAgICAgICogQHJldHVybiB7c3RyaW5nfQogICAgICAgKi8KICAgICAgX2F0QXBwbHlUb0Nzc1Byb3BlcnRpZXMobWl4aW5OYW1lLCBmYWxsYmFja3MpIHsKICAgICAgICBtaXhpbk5hbWUgPSBtaXhpbk5hbWUucmVwbGFjZShBUFBMWV9OQU1FX0NMRUFOLCAnJyk7CiAgICAgICAgbGV0IHZhcnMgPSBbXTsKICAgICAgICBsZXQgbWl4aW5FbnRyeSA9IHRoaXMuX21hcC5nZXQobWl4aW5OYW1lKTsKICAgICAgICAvLyBpZiB3ZSBkZXBlbmQgb24gYSBtaXhpbiBiZWZvcmUgaXQgaXMgY3JlYXRlZAogICAgICAgIC8vIG1ha2UgYSBzZW50aW5lbCBlbnRyeSBpbiB0aGUgbWFwIHRvIGFkZCB0aGlzIGVsZW1lbnQgYXMgYSBkZXBlbmRlbmN5IGZvciB3aGVuIGl0IGlzIGRlZmluZWQuCiAgICAgICAgaWYgKCFtaXhpbkVudHJ5KSB7CiAgICAgICAgICB0aGlzLl9tYXAuc2V0KG1peGluTmFtZSwge30pOwogICAgICAgICAgbWl4aW5FbnRyeSA9IHRoaXMuX21hcC5nZXQobWl4aW5OYW1lKTsKICAgICAgICB9CiAgICAgICAgaWYgKG1peGluRW50cnkpIHsKICAgICAgICAgIGlmICh0aGlzLl9jdXJyZW50RWxlbWVudCkgewogICAgICAgICAgICBtaXhpbkVudHJ5LmRlcGVuZGFudHNbdGhpcy5fY3VycmVudEVsZW1lbnRdID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICAgIGxldCBwLCBwYXJ0cywgZjsKICAgICAgICAgIGNvbnN0IHByb3BlcnRpZXMgPSBtaXhpbkVudHJ5LnByb3BlcnRpZXM7CiAgICAgICAgICBmb3IgKHAgaW4gcHJvcGVydGllcykgewogICAgICAgICAgICBmID0gZmFsbGJhY2tzICYmIGZhbGxiYWNrc1twXTsKICAgICAgICAgICAgcGFydHMgPSBbcCwgJzogdmFyKCcsIG1peGluTmFtZSwgTUlYSU5fVkFSX1NFUCwgcF07CiAgICAgICAgICAgIGlmIChmKSB7CiAgICAgICAgICAgICAgcGFydHMucHVzaCgnLCcsIGYucmVwbGFjZShJTVBPUlRBTlQsICcnKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcGFydHMucHVzaCgnKScpOwogICAgICAgICAgICBpZiAoSU1QT1JUQU5ULnRlc3QocHJvcGVydGllc1twXSkpIHsKICAgICAgICAgICAgICBwYXJ0cy5wdXNoKCcgIWltcG9ydGFudCcpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhcnMucHVzaChwYXJ0cy5qb2luKCcnKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiB2YXJzLmpvaW4oJzsgJyk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHZhbHVlCiAgICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAgICovCiAgICAgIF9yZXBsYWNlSW5pdGlhbE9ySW5oZXJpdChwcm9wZXJ0eSwgdmFsdWUpIHsKICAgICAgICBsZXQgbWF0Y2ggPSBJTklUSUFMX0lOSEVSSVQuZXhlYyh2YWx1ZSk7CiAgICAgICAgaWYgKG1hdGNoKSB7CiAgICAgICAgICBpZiAobWF0Y2hbMV0pIHsKICAgICAgICAgICAgLy8gaW5pdGlhbAogICAgICAgICAgICAvLyByZXBsYWNlIGBpbml0aWFsYCB3aXRoIHRoZSBjb25jcmV0ZSBpbml0aWFsIHZhbHVlIGZvciB0aGlzIHByb3BlcnR5CiAgICAgICAgICAgIHZhbHVlID0gdGhpcy5fZ2V0SW5pdGlhbFZhbHVlRm9yUHJvcGVydHkocHJvcGVydHkpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gaW5oZXJpdAogICAgICAgICAgICAvLyB3aXRoIHRoaXMgcHVycG9zZnVsbHkgaWxsZWdhbCB2YWx1ZSwgdGhlIHZhcmlhYmxlIHdpbGwgYmUgaW52YWxpZCBhdAogICAgICAgICAgICAvLyBjb21wdXRlIHRpbWUgKGh0dHBzOi8vd3d3LnczLm9yZy9UUi9jc3MtdmFyaWFibGVzLyNpbnZhbGlkLWF0LWNvbXB1dGVkLXZhbHVlLXRpbWUpCiAgICAgICAgICAgIC8vIGFuZCBmb3IgaW5oZXJpdGluZyB2YWx1ZXMsIHdpbGwgYmVoYXZlIHNpbWlsYXJseQogICAgICAgICAgICAvLyB3ZSBjYW5ub3Qgc3VwcG9ydCB0aGUgc2FtZSBiZWhhdmlvciBmb3Igbm9uIGluaGVyaXRpbmcgdmFsdWVzIGxpa2UgJ2JvcmRlcicKICAgICAgICAgICAgdmFsdWUgPSAnYXBwbHktc2hpbS1pbmhlcml0JzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogInBhcnNlIiBhIG1peGluIGRlZmluaXRpb24gaW50byBhIG1hcCBvZiBwcm9wZXJ0aWVzIGFuZCB2YWx1ZXMKICAgICAgICogY3NzVGV4dFRvTWFwKCdib3JkZXI6IDJweCBzb2xpZCBibGFjaycpIC0+ICgnYm9yZGVyJywgJzJweCBzb2xpZCBibGFjaycpCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0ZXh0CiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IHJlcGxhY2VJbml0aWFsT3JJbmhlcml0CiAgICAgICAqIEByZXR1cm4geyFPYmplY3Q8c3RyaW5nLCBzdHJpbmc+fQogICAgICAgKi8KICAgICAgX2Nzc1RleHRUb01hcCh0ZXh0LCByZXBsYWNlSW5pdGlhbE9ySW5oZXJpdCA9IGZhbHNlKSB7CiAgICAgICAgbGV0IHByb3BzID0gdGV4dC5zcGxpdCgnOycpOwogICAgICAgIGxldCBwcm9wZXJ0eSwgdmFsdWU7CiAgICAgICAgbGV0IG91dCA9IHt9OwogICAgICAgIGZvciAobGV0IGkgPSAwLCBwLCBzcDsgaSA8IHByb3BzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBwID0gcHJvcHNbaV07CiAgICAgICAgICBpZiAocCkgewogICAgICAgICAgICBzcCA9IHAuc3BsaXQoJzonKTsKICAgICAgICAgICAgLy8gaWdub3JlIGxpbmVzIHRoYXQgYXJlbid0IGRlZmluaXRpb25zIGxpa2UgQG1lZGlhCiAgICAgICAgICAgIGlmIChzcC5sZW5ndGggPiAxKSB7CiAgICAgICAgICAgICAgcHJvcGVydHkgPSBzcFswXS50cmltKCk7CiAgICAgICAgICAgICAgLy8gc29tZSBwcm9wZXJ0aWVzIG1heSBoYXZlICc6JyBpbiB0aGUgdmFsdWUsIGxpa2UgZGF0YSB1cmxzCiAgICAgICAgICAgICAgdmFsdWUgPSBzcC5zbGljZSgxKS5qb2luKCc6Jyk7CiAgICAgICAgICAgICAgaWYgKHJlcGxhY2VJbml0aWFsT3JJbmhlcml0KSB7CiAgICAgICAgICAgICAgICB2YWx1ZSA9IHRoaXMuX3JlcGxhY2VJbml0aWFsT3JJbmhlcml0KHByb3BlcnR5LCB2YWx1ZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIG91dFtwcm9wZXJ0eV0gPSB2YWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gb3V0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHtNaXhpbk1hcEVudHJ5fSBtaXhpbkVudHJ5CiAgICAgICAqLwogICAgICBfaW52YWxpZGF0ZU1peGluRW50cnkobWl4aW5FbnRyeSkgewogICAgICAgIGlmICghaW52YWxpZENhbGxiYWNrKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGZvciAobGV0IGVsZW1lbnROYW1lIGluIG1peGluRW50cnkuZGVwZW5kYW50cykgewogICAgICAgICAgaWYgKGVsZW1lbnROYW1lICE9PSB0aGlzLl9jdXJyZW50RWxlbWVudCkgewogICAgICAgICAgICBpbnZhbGlkQ2FsbGJhY2soZWxlbWVudE5hbWUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBtYXRjaFRleHQKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5TmFtZQogICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlUHJvcGVydHkKICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSB2YWx1ZU1peGluCiAgICAgICAqIEBwYXJhbSB7IVN0eWxlTm9kZX0gcnVsZQogICAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgICAqLwogICAgICBfcHJvZHVjZUNzc1Byb3BlcnRpZXMobWF0Y2hUZXh0LCBwcm9wZXJ0eU5hbWUsIHZhbHVlUHJvcGVydHksIHZhbHVlTWl4aW4sIHJ1bGUpIHsKICAgICAgICAvLyBoYW5kbGUgY2FzZSB3aGVyZSBwcm9wZXJ0eSB2YWx1ZSBpcyBhIG1peGluCiAgICAgICAgaWYgKHZhbHVlUHJvcGVydHkpIHsKICAgICAgICAgIC8vIGZvcm06IC0tbWl4aW4yOiB2YXIoLS1taXhpbjEpLCB3aGVyZSAtLW1peGluMSBpcyBpbiB0aGUgbWFwCiAgICAgICAgICBwcm9jZXNzVmFyaWFibGVBbmRGYWxsYmFjayh2YWx1ZVByb3BlcnR5LCAocHJlZml4LCB2YWx1ZSkgPT4gewogICAgICAgICAgICBpZiAodmFsdWUgJiYgdGhpcy5fbWFwLmdldCh2YWx1ZSkpIHsKICAgICAgICAgICAgICB2YWx1ZU1peGluID0gYEBhcHBseSAke3ZhbHVlfTtgOwogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgaWYgKCF2YWx1ZU1peGluKSB7CiAgICAgICAgICByZXR1cm4gbWF0Y2hUZXh0OwogICAgICAgIH0KICAgICAgICBsZXQgbWl4aW5Bc1Byb3BlcnRpZXMgPSB0aGlzLl9jb25zdW1lQ3NzUHJvcGVydGllcygnJyArIHZhbHVlTWl4aW4sIHJ1bGUpOwogICAgICAgIGxldCBwcmVmaXggPSBtYXRjaFRleHQuc2xpY2UoMCwgbWF0Y2hUZXh0LmluZGV4T2YoJy0tJykpOwogICAgICAgIC8vIGBpbml0aWFsYCBhbmQgYGluaGVyaXRgIGFzIHByb3BlcnRpZXMgaW4gYSBtYXAgc2hvdWxkIGJlIHJlcGxhY2VkIGJlY2F1c2UKICAgICAgICAvLyB0aGVzZSBrZXl3b3JkcyBhcmUgZWFnZXJseSBldmFsdWF0ZWQgd2hlbiB0aGUgbWl4aW4gYmVjb21lcyBDU1MgQ3VzdG9tIFByb3BlcnRpZXMsCiAgICAgICAgLy8gYW5kIHdvdWxkIHNldCB0aGUgdmFyaWFibGUgdmFsdWUsIHJhdGhlciB0aGFuIGNhcnJ5IHRoZSBrZXl3b3JkIHRvIHRoZSBgdmFyKClgIHVzYWdlLgogICAgICAgIGxldCBtaXhpblZhbHVlcyA9IHRoaXMuX2Nzc1RleHRUb01hcChtaXhpbkFzUHJvcGVydGllcywgdHJ1ZSk7CiAgICAgICAgbGV0IGNvbWJpbmVkUHJvcHMgPSBtaXhpblZhbHVlczsKICAgICAgICBsZXQgbWl4aW5FbnRyeSA9IHRoaXMuX21hcC5nZXQocHJvcGVydHlOYW1lKTsKICAgICAgICBsZXQgb2xkUHJvcHMgPSBtaXhpbkVudHJ5ICYmIG1peGluRW50cnkucHJvcGVydGllczsKICAgICAgICBpZiAob2xkUHJvcHMpIHsKICAgICAgICAgIC8vIE5PVEU6IHNpbmNlIHdlIHVzZSBtaXhpbiwgdGhlIG1hcCBvZiBwcm9wZXJ0aWVzIGlzIHVwZGF0ZWQgaGVyZQogICAgICAgICAgLy8gYW5kIHRoaXMgaXMgd2hhdCB3ZSB3YW50LgogICAgICAgICAgY29tYmluZWRQcm9wcyA9IE9iamVjdC5hc3NpZ24oT2JqZWN0LmNyZWF0ZShvbGRQcm9wcyksIG1peGluVmFsdWVzKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fbWFwLnNldChwcm9wZXJ0eU5hbWUsIGNvbWJpbmVkUHJvcHMpOwogICAgICAgIH0KICAgICAgICBsZXQgb3V0ID0gW107CiAgICAgICAgbGV0IHAsIHY7CiAgICAgICAgLy8gc2V0IHZhcmlhYmxlcyBkZWZpbmVkIGJ5IGN1cnJlbnQgbWl4aW4KICAgICAgICBsZXQgbmVlZFRvSW52YWxpZGF0ZSA9IGZhbHNlOwogICAgICAgIGZvciAocCBpbiBjb21iaW5lZFByb3BzKSB7CiAgICAgICAgICB2ID0gbWl4aW5WYWx1ZXNbcF07CiAgICAgICAgICAvLyBpZiBwcm9wZXJ0eSBub3QgZGVmaW5lZCBieSBjdXJyZW50IG1peGluLCBzZXQgaW5pdGlhbAogICAgICAgICAgaWYgKHYgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICB2ID0gJ2luaXRpYWwnOwogICAgICAgICAgfQogICAgICAgICAgaWYgKG9sZFByb3BzICYmICEocCBpbiBvbGRQcm9wcykpIHsKICAgICAgICAgICAgbmVlZFRvSW52YWxpZGF0ZSA9IHRydWU7CiAgICAgICAgICB9CiAgICAgICAgICBvdXQucHVzaChgJHtwcm9wZXJ0eU5hbWV9JHtNSVhJTl9WQVJfU0VQfSR7cH06ICR7dn1gKTsKICAgICAgICB9CiAgICAgICAgaWYgKG5lZWRUb0ludmFsaWRhdGUpIHsKICAgICAgICAgIHRoaXMuX2ludmFsaWRhdGVNaXhpbkVudHJ5KG1peGluRW50cnkpOwogICAgICAgIH0KICAgICAgICBpZiAobWl4aW5FbnRyeSkgewogICAgICAgICAgbWl4aW5FbnRyeS5wcm9wZXJ0aWVzID0gY29tYmluZWRQcm9wczsKICAgICAgICB9CiAgICAgICAgLy8gYmVjYXVzZSB0aGUgbWl4aW5NYXAgaXMgZ2xvYmFsLCB0aGUgbWl4aW4gbWlnaHQgY29uZmxpY3Qgd2l0aAogICAgICAgIC8vIGEgZGlmZmVyZW50IHNjb3BlJ3Mgc2ltcGxlIHZhcmlhYmxlIGRlZmluaXRpb246CiAgICAgICAgLy8gRXhhbXBsZToKICAgICAgICAvLyBzb21lIHN0eWxlIHNvbWV3aGVyZToKICAgICAgICAvLyAtLW1peGluMTp7IC4uLiB9CiAgICAgICAgLy8gLS1taXhpbjI6IHZhcigtLW1peGluMSk7CiAgICAgICAgLy8gc29tZSBvdGhlciBlbGVtZW50OgogICAgICAgIC8vIC0tbWl4aW4xOiAxMHB4IHNvbGlkIHJlZDsKICAgICAgICAvLyAtLWZvbzogdmFyKC0tbWl4aW4xKTsKICAgICAgICAvLyBJbiB0aGlzIGNhc2UsIHdlIGxlYXZlIHRoZSBvcmlnaW5hbCB2YXJpYWJsZSBkZWZpbml0aW9uIGluIHBsYWNlLgogICAgICAgIGlmICh2YWx1ZVByb3BlcnR5KSB7CiAgICAgICAgICBwcmVmaXggPSBgJHttYXRjaFRleHR9OyR7cHJlZml4fWA7CiAgICAgICAgfQogICAgICAgIHJldHVybiBgJHtwcmVmaXh9JHtvdXQuam9pbignOyAnKX07YDsKICAgICAgfQogICAgfQoKICAgIC8qIGV4cG9ydHMgKi8KICAgIC8qIGVzbGludC1kaXNhYmxlIG5vLXNlbGYtYXNzaWduICovCiAgICBBcHBseVNoaW0ucHJvdG90eXBlWydkZXRlY3RNaXhpbiddID0gQXBwbHlTaGltLnByb3RvdHlwZS5kZXRlY3RNaXhpbjsKICAgIEFwcGx5U2hpbS5wcm90b3R5cGVbJ3RyYW5zZm9ybVN0eWxlJ10gPSBBcHBseVNoaW0ucHJvdG90eXBlLnRyYW5zZm9ybVN0eWxlOwogICAgQXBwbHlTaGltLnByb3RvdHlwZVsndHJhbnNmb3JtQ3VzdG9tU3R5bGUnXSA9IEFwcGx5U2hpbS5wcm90b3R5cGUudHJhbnNmb3JtQ3VzdG9tU3R5bGU7CiAgICBBcHBseVNoaW0ucHJvdG90eXBlWyd0cmFuc2Zvcm1SdWxlcyddID0gQXBwbHlTaGltLnByb3RvdHlwZS50cmFuc2Zvcm1SdWxlczsKICAgIEFwcGx5U2hpbS5wcm90b3R5cGVbJ3RyYW5zZm9ybVJ1bGUnXSA9IEFwcGx5U2hpbS5wcm90b3R5cGUudHJhbnNmb3JtUnVsZTsKICAgIEFwcGx5U2hpbS5wcm90b3R5cGVbJ3RyYW5zZm9ybVRlbXBsYXRlJ10gPSBBcHBseVNoaW0ucHJvdG90eXBlLnRyYW5zZm9ybVRlbXBsYXRlOwogICAgQXBwbHlTaGltLnByb3RvdHlwZVsnX3NlcGFyYXRvciddID0gTUlYSU5fVkFSX1NFUDsKICAgIC8qIGVzbGludC1lbmFibGUgbm8tc2VsZi1hc3NpZ24gKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShBcHBseVNoaW0ucHJvdG90eXBlLCAnaW52YWxpZENhbGxiYWNrJywgewogICAgICAvKiogQHJldHVybiB7P2Z1bmN0aW9uKHN0cmluZyl9ICovCiAgICAgIGdldCgpIHsKICAgICAgICByZXR1cm4gaW52YWxpZENhbGxiYWNrOwogICAgICB9LAogICAgICAvKiogQHBhcmFtIHs/ZnVuY3Rpb24oc3RyaW5nKX0gY2IgKi8KICAgICAgc2V0KGNiKSB7CiAgICAgICAgaW52YWxpZENhbGxiYWNrID0gY2I7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAY29uc3QgeyFPYmplY3Q8c3RyaW5nLCAhSFRNTFRlbXBsYXRlRWxlbWVudD59CiAgICAgKi8KICAgIGNvbnN0IHRlbXBsYXRlTWFwID0ge307CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKgogICAgICogVXRpbGl0aWVzIGZvciBoYW5kbGluZyBpbnZhbGlkYXRpbmcgYXBwbHktc2hpbSBtaXhpbnMgZm9yIGEgZ2l2ZW4gdGVtcGxhdGUuCiAgICAgKgogICAgICogVGhlIGludmFsaWRhdGlvbiBzdHJhdGVneSBpbnZvbHZlcyBrZWVwaW5nIHRyYWNrIG9mIHRoZSAiY3VycmVudCIgdmVyc2lvbiBvZiBhIHRlbXBsYXRlJ3MgbWl4aW5zLCBhbmQgdXBkYXRpbmcgdGhhdCBjb3VudCB3aGVuIGEgbWl4aW4gaXMgaW52YWxpZGF0ZWQuCiAgICAgKiBUaGUgdGVtcGxhdGUKICAgICAqLwoKICAgIC8qKiBAY29uc3Qge3N0cmluZ30gKi8KICAgIGNvbnN0IENVUlJFTlRfVkVSU0lPTiA9ICdfYXBwbHlTaGltQ3VycmVudFZlcnNpb24nOwoKICAgIC8qKiBAY29uc3Qge3N0cmluZ30gKi8KICAgIGNvbnN0IE5FWFRfVkVSU0lPTiA9ICdfYXBwbHlTaGltTmV4dFZlcnNpb24nOwoKICAgIC8qKiBAY29uc3Qge3N0cmluZ30gKi8KICAgIGNvbnN0IFZBTElEQVRJTkdfVkVSU0lPTiA9ICdfYXBwbHlTaGltVmFsaWRhdGluZ1ZlcnNpb24nOwoKICAgIC8qKgogICAgICogQGNvbnN0IHtQcm9taXNlPHZvaWQ+fQogICAgICovCiAgICBjb25zdCBwcm9taXNlID0gUHJvbWlzZS5yZXNvbHZlKCk7CgogICAgLyoqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZWxlbWVudE5hbWUKICAgICAqLwogICAgZnVuY3Rpb24gaW52YWxpZGF0ZShlbGVtZW50TmFtZSl7CiAgICAgIGxldCB0ZW1wbGF0ZSA9IHRlbXBsYXRlTWFwW2VsZW1lbnROYW1lXTsKICAgICAgaWYgKHRlbXBsYXRlKSB7CiAgICAgICAgaW52YWxpZGF0ZVRlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogVGhpcyBmdW5jdGlvbiBjYW4gYmUgY2FsbGVkIG11bHRpcGxlIHRpbWVzIHRvIG1hcmsgYSB0ZW1wbGF0ZSBpbnZhbGlkCiAgICAgKiBhbmQgc2lnbmFsIHRoYXQgdGhlIHN0eWxlIGluc2lkZSBtdXN0IGJlIHJlZ2VuZXJhdGVkLgogICAgICoKICAgICAqIFVzZSBgc3RhcnRWYWxpZGF0aW5nVGVtcGxhdGVgIHRvIGJlZ2luIGFuIGFzeW5jaHJvbm91cyB2YWxpZGF0aW9uIGN5Y2xlLgogICAgICogRHVyaW5nIHRoYXQgY3ljbGUsIGNhbGwgYHRlbXBsYXRlSXNWYWxpZGF0aW5nYCB0byBzZWUgaWYgdGhlIHRlbXBsYXRlIG11c3QKICAgICAqIGJlIHJldmFsaWRhdGVkCiAgICAgKiBAcGFyYW0ge0hUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGludmFsaWRhdGVUZW1wbGF0ZSh0ZW1wbGF0ZSkgewogICAgICAvLyBkZWZhdWx0IHRoZSBjdXJyZW50IHZlcnNpb24gdG8gMAogICAgICB0ZW1wbGF0ZVtDVVJSRU5UX1ZFUlNJT05dID0gdGVtcGxhdGVbQ1VSUkVOVF9WRVJTSU9OXSB8fCAwOwogICAgICAvLyBlbnN1cmUgdGhlICJ2YWxpZGF0aW5nIGZvciIgZmxhZyBleGlzdHMKICAgICAgdGVtcGxhdGVbVkFMSURBVElOR19WRVJTSU9OXSA9IHRlbXBsYXRlW1ZBTElEQVRJTkdfVkVSU0lPTl0gfHwgMDsKICAgICAgLy8gaW5jcmVtZW50IHRoZSBuZXh0IHZlcnNpb24KICAgICAgdGVtcGxhdGVbTkVYVF9WRVJTSU9OXSA9ICh0ZW1wbGF0ZVtORVhUX1ZFUlNJT05dIHx8IDApICsgMTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7SFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgKi8KICAgIGZ1bmN0aW9uIHRlbXBsYXRlSXNWYWxpZCh0ZW1wbGF0ZSkgewogICAgICByZXR1cm4gdGVtcGxhdGVbQ1VSUkVOVF9WRVJTSU9OXSA9PT0gdGVtcGxhdGVbTkVYVF9WRVJTSU9OXTsKICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgdGVtcGxhdGUgaXMgY3VycmVudGx5IGludmFsaWQgYW5kIGBzdGFydFZhbGlkYXRpbmdgIGhhcyBiZWVuIGNhbGxlZCBzaW5jZSB0aGUgbGFzdCBpbnZhbGlkYXRpb24uCiAgICAgKiBJZiBmYWxzZSwgdGhlIHRlbXBsYXRlIG11c3QgYmUgdmFsaWRhdGVkLgogICAgICogQHBhcmFtIHtIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZQogICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAqLwogICAgZnVuY3Rpb24gdGVtcGxhdGVJc1ZhbGlkYXRpbmcodGVtcGxhdGUpIHsKICAgICAgcmV0dXJuICF0ZW1wbGF0ZUlzVmFsaWQodGVtcGxhdGUpICYmIHRlbXBsYXRlW1ZBTElEQVRJTkdfVkVSU0lPTl0gPT09IHRlbXBsYXRlW05FWFRfVkVSU0lPTl07CiAgICB9CgogICAgLyoqCiAgICAgKiBCZWdpbiBhbiBhc3luY2hyb25vdXMgaW52YWxpZGF0aW9uIGN5Y2xlLgogICAgICogVGhpcyBzaG91bGQgYmUgY2FsbGVkIGFmdGVyIGV2ZXJ5IHZhbGlkYXRpb24gb2YgYSB0ZW1wbGF0ZQogICAgICoKICAgICAqIEFmdGVyIG9uZSBtaWNyb3Rhc2ssIHRoZSB0ZW1wbGF0ZSB3aWxsIGJlIG1hcmtlZCBhcyB2YWxpZCB1bnRpbCB0aGUgbmV4dCBjYWxsIHRvIGBpbnZhbGlkYXRlVGVtcGxhdGVgCiAgICAgKiBAcGFyYW0ge0hUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0YXJ0VmFsaWRhdGluZ1RlbXBsYXRlKHRlbXBsYXRlKSB7CiAgICAgIC8vIHJlbWVtYmVyIHRoYXQgdGhlIGN1cnJlbnQgIm5leHQgdmVyc2lvbiIgaXMgdGhlIHJlYXNvbiBmb3IgdGhpcyB2YWxpZGF0aW9uIGN5Y2xlCiAgICAgIHRlbXBsYXRlW1ZBTElEQVRJTkdfVkVSU0lPTl0gPSB0ZW1wbGF0ZVtORVhUX1ZFUlNJT05dOwogICAgICAvLyBob3dldmVyLCB0aGVyZSBvbmx5IG5lZWRzIHRvIGJlIG9uZSBhc3luYyB0YXNrIHRvIGNsZWFyIHRoZSBjb3VudGVycwogICAgICBpZiAoIXRlbXBsYXRlLl92YWxpZGF0aW5nKSB7CiAgICAgICAgdGVtcGxhdGUuX3ZhbGlkYXRpbmcgPSB0cnVlOwogICAgICAgIHByb21pc2UudGhlbihmdW5jdGlvbigpIHsKICAgICAgICAgIC8vIHN5bmMgdGhlIGN1cnJlbnQgdmVyc2lvbiB0byBsZXQgZnV0dXJlIGludmFsaWRhdGlvbnMgY2F1c2UgYSByZWZyZXNoIGN5Y2xlCiAgICAgICAgICB0ZW1wbGF0ZVtDVVJSRU5UX1ZFUlNJT05dID0gdGVtcGxhdGVbTkVYVF9WRVJTSU9OXTsKICAgICAgICAgIHRlbXBsYXRlLl92YWxpZGF0aW5nID0gZmFsc2U7CiAgICAgICAgfSk7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKiBAdHlwZSB7UHJvbWlzZTx2b2lkPn0gKi8KICAgIGxldCByZWFkeVByb21pc2UgPSBudWxsOwoKICAgIC8qKiBAdHlwZSB7P2Z1bmN0aW9uKD9mdW5jdGlvbigpKX0gKi8KICAgIGxldCB3aGVuUmVhZHkgPSB3aW5kb3dbJ0hUTUxJbXBvcnRzJ10gJiYgd2luZG93WydIVE1MSW1wb3J0cyddWyd3aGVuUmVhZHknXSB8fCBudWxsOwoKICAgIC8qKiBAdHlwZSB7ZnVuY3Rpb24oKX0gKi8KICAgIGxldCByZXNvbHZlRm47CgogICAgLyoqCiAgICAgKiBAcGFyYW0gez9mdW5jdGlvbigpfSBjYWxsYmFjawogICAgICovCiAgICBmdW5jdGlvbiBkb2N1bWVudFdhaXQoY2FsbGJhY2spIHsKICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh3aGVuUmVhZHkpIHsKICAgICAgICAgIHdoZW5SZWFkeShjYWxsYmFjayk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmICghcmVhZHlQcm9taXNlKSB7CiAgICAgICAgICAgIHJlYWR5UHJvbWlzZSA9IG5ldyBQcm9taXNlKChyZXNvbHZlKSA9PiB7cmVzb2x2ZUZuID0gcmVzb2x2ZTt9KTsKICAgICAgICAgICAgaWYgKGRvY3VtZW50LnJlYWR5U3RhdGUgPT09ICdjb21wbGV0ZScpIHsKICAgICAgICAgICAgICByZXNvbHZlRm4oKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBkb2N1bWVudC5hZGRFdmVudExpc3RlbmVyKCdyZWFkeXN0YXRlY2hhbmdlJywgKCkgPT4gewogICAgICAgICAgICAgICAgaWYgKGRvY3VtZW50LnJlYWR5U3RhdGUgPT09ICdjb21wbGV0ZScpIHsKICAgICAgICAgICAgICAgICAgcmVzb2x2ZUZuKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJlYWR5UHJvbWlzZS50aGVuKGZ1bmN0aW9uKCl7IGNhbGxiYWNrICYmIGNhbGxiYWNrKCk7IH0pOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCBTRUVOX01BUktFUiA9ICdfX3NlZW5CeVNoYWR5Q1NTJzsKICAgIGNvbnN0IENBQ0hFRF9TVFlMRSA9ICdfX3NoYWR5Q1NTQ2FjaGVkU3R5bGUnOwoKICAgIC8qKiBAdHlwZSB7P2Z1bmN0aW9uKCFIVE1MU3R5bGVFbGVtZW50KX0gKi8KICAgIGxldCB0cmFuc2Zvcm1GbiA9IG51bGw7CgogICAgLyoqIEB0eXBlIHs/ZnVuY3Rpb24oKX0gKi8KICAgIGxldCB2YWxpZGF0ZUZuID0gbnVsbDsKCiAgICAvKioKICAgIFRoaXMgaW50ZXJmYWNlIGlzIHByb3ZpZGVkIHRvIGFkZCBkb2N1bWVudC1sZXZlbCA8c3R5bGU+IGVsZW1lbnRzIHRvIFNoYWR5Q1NTIGZvciBwcm9jZXNzaW5nLgogICAgVGhlc2Ugc3R5bGVzIG11c3QgYmUgcHJvY2Vzc2VkIGJ5IFNoYWR5Q1NTIHRvIHNpbXVsYXRlIFNoYWRvd1Jvb3QgdXBwZXItYm91bmQgZW5jYXBzdWxhdGlvbiBmcm9tIG91dHNpZGUgc3R5bGVzCiAgICBJbiBhZGRpdGlvbiwgdGhlc2Ugc3R5bGVzIG1heSBhbHNvIG5lZWQgdG8gYmUgcHJvY2Vzc2VkIGZvciBAYXBwbHkgcnVsZXMgYW5kIENTUyBDdXN0b20gUHJvcGVydGllcwoKICAgIFRvIGFkZCBkb2N1bWVudC1sZXZlbCBzdHlsZXMgdG8gU2hhZHlDU1MsIG9uZSBjYW4gY2FsbCBgU2hhZHlDU1MuYWRkRG9jdW1lbnRTdHlsZShzdHlsZUVsZW1lbnQpYCBvciBgU2hhZHlDU1MuYWRkRG9jdW1lbnRTdHlsZSh7Z2V0U3R5bGU6ICgpID0+IHN0eWxlRWxlbWVudH0pYAoKICAgIEluIGFkZGl0aW9uLCBpZiB0aGUgcHJvY2VzcyB1c2VkIHRvIGRpc2NvdmVyIGRvY3VtZW50LWxldmVsIHN0eWxlcyBjYW4gYmUgc3luY2hyb25vdXNseSBmbHVzaGVkLCBvbmUgc2hvdWxkIHNldCBgU2hhZHlDU1MuZG9jdW1lbnRTdHlsZUZsdXNoYC4KICAgIFRoaXMgZnVuY3Rpb24gd2lsbCBiZSBjYWxsZWQgd2hlbiBjYWxjdWxhdGluZyBzdHlsZXMuCgogICAgQW4gZXhhbXBsZSB1c2FnZSBvZiB0aGUgZG9jdW1lbnQtbGV2ZWwgc3R5bGluZyBhcGkgY2FuIGJlIGZvdW5kIGluIGBleGFtcGxlcy9kb2N1bWVudC1zdHlsZS1saWIuanNgCgogICAgQHVucmVzdHJpY3RlZAogICAgKi8KICAgIGNsYXNzIEN1c3RvbVN0eWxlSW50ZXJmYWNlIHsKICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgLyoqIEB0eXBlIHshQXJyYXk8IUN1c3RvbVN0eWxlUHJvdmlkZXI+fSAqLwogICAgICAgIHRoaXNbJ2N1c3RvbVN0eWxlcyddID0gW107CiAgICAgICAgdGhpc1snZW5xdWV1ZWQnXSA9IGZhbHNlOwogICAgICAgIC8vIE5PVEUoZGZyZWVkbSk6IHVzZSBxdW90ZXMgaGVyZSB0byBwcmV2ZW50IGNsb3N1cmUgaW5saW5pbmcgdG8gYGZ1bmN0aW9uKCl7fWA7CiAgICAgICAgZG9jdW1lbnRXYWl0KCgpID0+IHsKICAgICAgICAgIGlmICh3aW5kb3dbJ1NoYWR5Q1NTJ11bJ2ZsdXNoQ3VzdG9tU3R5bGVzJ10pIHsKICAgICAgICAgICAgd2luZG93WydTaGFkeUNTUyddWydmbHVzaEN1c3RvbVN0eWxlcyddKCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIFF1ZXVlIGEgdmFsaWRhdGlvbiBmb3IgbmV3IGN1c3RvbSBzdHlsZXMgdG8gYmF0Y2ggc3R5bGUgcmVjYWxjdWxhdGlvbnMKICAgICAgICovCiAgICAgIGVucXVldWVEb2N1bWVudFZhbGlkYXRpb24oKSB7CiAgICAgICAgaWYgKHRoaXNbJ2VucXVldWVkJ10gfHwgIXZhbGlkYXRlRm4pIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpc1snZW5xdWV1ZWQnXSA9IHRydWU7CiAgICAgICAgZG9jdW1lbnRXYWl0KHZhbGlkYXRlRm4pOwogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0geyFIVE1MU3R5bGVFbGVtZW50fSBzdHlsZQogICAgICAgKi8KICAgICAgYWRkQ3VzdG9tU3R5bGUoc3R5bGUpIHsKICAgICAgICBpZiAoIXN0eWxlW1NFRU5fTUFSS0VSXSkgewogICAgICAgICAgc3R5bGVbU0VFTl9NQVJLRVJdID0gdHJ1ZTsKICAgICAgICAgIHRoaXNbJ2N1c3RvbVN0eWxlcyddLnB1c2goc3R5bGUpOwogICAgICAgICAgdGhpcy5lbnF1ZXVlRG9jdW1lbnRWYWxpZGF0aW9uKCk7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0geyFDdXN0b21TdHlsZVByb3ZpZGVyfSBjdXN0b21TdHlsZQogICAgICAgKiBAcmV0dXJuIHtIVE1MU3R5bGVFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2V0U3R5bGVGb3JDdXN0b21TdHlsZShjdXN0b21TdHlsZSkgewogICAgICAgIGlmIChjdXN0b21TdHlsZVtDQUNIRURfU1RZTEVdKSB7CiAgICAgICAgICByZXR1cm4gY3VzdG9tU3R5bGVbQ0FDSEVEX1NUWUxFXTsKICAgICAgICB9CiAgICAgICAgbGV0IHN0eWxlOwogICAgICAgIGlmIChjdXN0b21TdHlsZVsnZ2V0U3R5bGUnXSkgewogICAgICAgICAgc3R5bGUgPSBjdXN0b21TdHlsZVsnZ2V0U3R5bGUnXSgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBzdHlsZSA9IGN1c3RvbVN0eWxlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gc3R5bGU7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4geyFBcnJheTwhQ3VzdG9tU3R5bGVQcm92aWRlcj59CiAgICAgICAqLwogICAgICBwcm9jZXNzU3R5bGVzKCkgewogICAgICAgIGNvbnN0IGNzID0gdGhpc1snY3VzdG9tU3R5bGVzJ107CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBjcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgY29uc3QgY3VzdG9tU3R5bGUgPSBjc1tpXTsKICAgICAgICAgIGlmIChjdXN0b21TdHlsZVtDQUNIRURfU1RZTEVdKSB7CiAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgfQogICAgICAgICAgY29uc3Qgc3R5bGUgPSB0aGlzLmdldFN0eWxlRm9yQ3VzdG9tU3R5bGUoY3VzdG9tU3R5bGUpOwogICAgICAgICAgaWYgKHN0eWxlKSB7CiAgICAgICAgICAgIC8vIEhUTUxJbXBvcnRzIHBvbHlmaWxsIG1heSBoYXZlIGNsb25lZCB0aGUgc3R5bGUgaW50byB0aGUgbWFpbiBkb2N1bWVudCwKICAgICAgICAgICAgLy8gd2hpY2ggaXMgcmVmZXJlbmNlZCB3aXRoIF9fYXBwbGllZEVsZW1lbnQuCiAgICAgICAgICAgIGNvbnN0IHN0eWxlVG9UcmFuc2Zvcm0gPSAvKiogQHR5cGUgeyFIVE1MU3R5bGVFbGVtZW50fSAqLyhzdHlsZVsnX19hcHBsaWVkRWxlbWVudCddIHx8IHN0eWxlKTsKICAgICAgICAgICAgaWYgKHRyYW5zZm9ybUZuKSB7CiAgICAgICAgICAgICAgdHJhbnNmb3JtRm4oc3R5bGVUb1RyYW5zZm9ybSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY3VzdG9tU3R5bGVbQ0FDSEVEX1NUWUxFXSA9IHN0eWxlVG9UcmFuc2Zvcm07CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBjczsKICAgICAgfQogICAgfQoKICAgIC8qIGVzbGludC1kaXNhYmxlIG5vLXNlbGYtYXNzaWduICovCiAgICBDdXN0b21TdHlsZUludGVyZmFjZS5wcm90b3R5cGVbJ2FkZEN1c3RvbVN0eWxlJ10gPSBDdXN0b21TdHlsZUludGVyZmFjZS5wcm90b3R5cGUuYWRkQ3VzdG9tU3R5bGU7CiAgICBDdXN0b21TdHlsZUludGVyZmFjZS5wcm90b3R5cGVbJ2dldFN0eWxlRm9yQ3VzdG9tU3R5bGUnXSA9IEN1c3RvbVN0eWxlSW50ZXJmYWNlLnByb3RvdHlwZS5nZXRTdHlsZUZvckN1c3RvbVN0eWxlOwogICAgQ3VzdG9tU3R5bGVJbnRlcmZhY2UucHJvdG90eXBlWydwcm9jZXNzU3R5bGVzJ10gPSBDdXN0b21TdHlsZUludGVyZmFjZS5wcm90b3R5cGUucHJvY2Vzc1N0eWxlczsKICAgIC8qIGVzbGludC1lbmFibGUgbm8tc2VsZi1hc3NpZ24gKi8KCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydGllcyhDdXN0b21TdHlsZUludGVyZmFjZS5wcm90b3R5cGUsIHsKICAgICAgJ3RyYW5zZm9ybUNhbGxiYWNrJzogewogICAgICAgIC8qKiBAcmV0dXJuIHs/ZnVuY3Rpb24oIUhUTUxTdHlsZUVsZW1lbnQpfSAqLwogICAgICAgIGdldCgpIHsKICAgICAgICAgIHJldHVybiB0cmFuc2Zvcm1GbjsKICAgICAgICB9LAogICAgICAgIC8qKiBAcGFyYW0gez9mdW5jdGlvbighSFRNTFN0eWxlRWxlbWVudCl9IGZuICovCiAgICAgICAgc2V0KGZuKSB7CiAgICAgICAgICB0cmFuc2Zvcm1GbiA9IGZuOwogICAgICAgIH0KICAgICAgfSwKICAgICAgJ3ZhbGlkYXRlQ2FsbGJhY2snOiB7CiAgICAgICAgLyoqIEByZXR1cm4gez9mdW5jdGlvbigpfSAqLwogICAgICAgIGdldCgpIHsKICAgICAgICAgIHJldHVybiB2YWxpZGF0ZUZuOwogICAgICAgIH0sCiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHs/ZnVuY3Rpb24oKX0gZm4KICAgICAgICAgKiBAdGhpcyB7Q3VzdG9tU3R5bGVJbnRlcmZhY2V9CiAgICAgICAgICovCiAgICAgICAgc2V0KGZuKSB7CiAgICAgICAgICBsZXQgbmVlZHNFbnF1ZXVlID0gZmFsc2U7CiAgICAgICAgICBpZiAoIXZhbGlkYXRlRm4pIHsKICAgICAgICAgICAgbmVlZHNFbnF1ZXVlID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHZhbGlkYXRlRm4gPSBmbjsKICAgICAgICAgIGlmIChuZWVkc0VucXVldWUpIHsKICAgICAgICAgICAgdGhpcy5lbnF1ZXVlRG9jdW1lbnRWYWxpZGF0aW9uKCk7CiAgICAgICAgICB9CiAgICAgICAgfSwKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKiogQGNvbnN0IHtBcHBseVNoaW19ICovCiAgICBjb25zdCBhcHBseVNoaW0gPSBuZXcgQXBwbHlTaGltKCk7CgogICAgY2xhc3MgQXBwbHlTaGltSW50ZXJmYWNlIHsKICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgLyoqIEB0eXBlIHs/Q3VzdG9tU3R5bGVJbnRlcmZhY2VJbnRlcmZhY2V9ICovCiAgICAgICAgdGhpcy5jdXN0b21TdHlsZUludGVyZmFjZSA9IG51bGw7CiAgICAgICAgYXBwbHlTaGltWydpbnZhbGlkQ2FsbGJhY2snXSA9IGludmFsaWRhdGU7CiAgICAgIH0KICAgICAgZW5zdXJlKCkgewogICAgICAgIGlmICh0aGlzLmN1c3RvbVN0eWxlSW50ZXJmYWNlKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlmICh3aW5kb3cuU2hhZHlDU1MuQ3VzdG9tU3R5bGVJbnRlcmZhY2UpIHsKICAgICAgICAgIHRoaXMuY3VzdG9tU3R5bGVJbnRlcmZhY2UgPQogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IUN1c3RvbVN0eWxlSW50ZXJmYWNlSW50ZXJmYWNlfSAqLyAoCiAgICAgICAgICAgICAgICAgIHdpbmRvdy5TaGFkeUNTUy5DdXN0b21TdHlsZUludGVyZmFjZSk7CiAgICAgICAgICB0aGlzLmN1c3RvbVN0eWxlSW50ZXJmYWNlWyd0cmFuc2Zvcm1DYWxsYmFjayddID0gKHN0eWxlKSA9PiB7CiAgICAgICAgICAgIGFwcGx5U2hpbS50cmFuc2Zvcm1DdXN0b21TdHlsZShzdHlsZSk7CiAgICAgICAgICB9OwogICAgICAgICAgdGhpcy5jdXN0b21TdHlsZUludGVyZmFjZVsndmFsaWRhdGVDYWxsYmFjayddID0gKCkgPT4gewogICAgICAgICAgICByZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gewogICAgICAgICAgICAgIGlmICh0aGlzLmN1c3RvbVN0eWxlSW50ZXJmYWNlWydlbnF1ZXVlZCddKSB7CiAgICAgICAgICAgICAgICB0aGlzLmZsdXNoQ3VzdG9tU3R5bGVzKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgIH07CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZQogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZWxlbWVudE5hbWUKICAgICAgICovCiAgICAgIHByZXBhcmVUZW1wbGF0ZSh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUpIHsKICAgICAgICB0aGlzLmVuc3VyZSgpOwogICAgICAgIGlmIChlbGVtZW50SGFzQnVpbHRDc3ModGVtcGxhdGUpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRlbXBsYXRlTWFwW2VsZW1lbnROYW1lXSA9IHRlbXBsYXRlOwogICAgICAgIGxldCBhc3QgPSBhcHBseVNoaW0udHJhbnNmb3JtVGVtcGxhdGUodGVtcGxhdGUsIGVsZW1lbnROYW1lKTsKICAgICAgICAvLyBzYXZlIG9yaWdpbmFsIHN0eWxlIGFzdCB0byB1c2UgZm9yIHJldmFsaWRhdGluZyBpbnN0YW5jZXMKICAgICAgICB0ZW1wbGF0ZVsnX3N0eWxlQXN0J10gPSBhc3Q7CiAgICAgIH0KICAgICAgZmx1c2hDdXN0b21TdHlsZXMoKSB7CiAgICAgICAgdGhpcy5lbnN1cmUoKTsKICAgICAgICBpZiAoIXRoaXMuY3VzdG9tU3R5bGVJbnRlcmZhY2UpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgbGV0IHN0eWxlcyA9IHRoaXMuY3VzdG9tU3R5bGVJbnRlcmZhY2VbJ3Byb2Nlc3NTdHlsZXMnXSgpOwogICAgICAgIGlmICghdGhpcy5jdXN0b21TdHlsZUludGVyZmFjZVsnZW5xdWV1ZWQnXSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHN0eWxlcy5sZW5ndGg7IGkrKyApIHsKICAgICAgICAgIGxldCBjcyA9IHN0eWxlc1tpXTsKICAgICAgICAgIGxldCBzdHlsZSA9IHRoaXMuY3VzdG9tU3R5bGVJbnRlcmZhY2VbJ2dldFN0eWxlRm9yQ3VzdG9tU3R5bGUnXShjcyk7CiAgICAgICAgICBpZiAoc3R5bGUpIHsKICAgICAgICAgICAgYXBwbHlTaGltLnRyYW5zZm9ybUN1c3RvbVN0eWxlKHN0eWxlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdGhpcy5jdXN0b21TdHlsZUludGVyZmFjZVsnZW5xdWV1ZWQnXSA9IGZhbHNlOwogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50CiAgICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gcHJvcGVydGllcwogICAgICAgKi8KICAgICAgc3R5bGVTdWJ0cmVlKGVsZW1lbnQsIHByb3BlcnRpZXMpIHsKICAgICAgICB0aGlzLmVuc3VyZSgpOwogICAgICAgIGlmIChwcm9wZXJ0aWVzKSB7CiAgICAgICAgICB1cGRhdGVOYXRpdmVQcm9wZXJ0aWVzKGVsZW1lbnQsIHByb3BlcnRpZXMpOwogICAgICAgIH0KICAgICAgICBpZiAoZWxlbWVudC5zaGFkb3dSb290KSB7CiAgICAgICAgICB0aGlzLnN0eWxlRWxlbWVudChlbGVtZW50KTsKICAgICAgICAgIGxldCBzaGFkb3dDaGlsZHJlbiA9CiAgICAgICAgICAgICAgLyoqIEB0eXBlIHshUGFyZW50Tm9kZX0gKi8gKGVsZW1lbnQuc2hhZG93Um9vdCkuY2hpbGRyZW4gfHwKICAgICAgICAgICAgICBlbGVtZW50LnNoYWRvd1Jvb3QuY2hpbGROb2RlczsKICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgc2hhZG93Q2hpbGRyZW4ubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgdGhpcy5zdHlsZVN1YnRyZWUoLyoqIEB0eXBlIHtIVE1MRWxlbWVudH0gKi8oc2hhZG93Q2hpbGRyZW5baV0pKTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgbGV0IGNoaWxkcmVuID0gZWxlbWVudC5jaGlsZHJlbiB8fCBlbGVtZW50LmNoaWxkTm9kZXM7CiAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGNoaWxkcmVuLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIHRoaXMuc3R5bGVTdWJ0cmVlKC8qKiBAdHlwZSB7SFRNTEVsZW1lbnR9ICovKGNoaWxkcmVuW2ldKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50CiAgICAgICAqLwogICAgICBzdHlsZUVsZW1lbnQoZWxlbWVudCkgewogICAgICAgIHRoaXMuZW5zdXJlKCk7CiAgICAgICAgbGV0IHtpc30gPSBnZXRJc0V4dGVuZHMoZWxlbWVudCk7CiAgICAgICAgbGV0IHRlbXBsYXRlID0gdGVtcGxhdGVNYXBbaXNdOwogICAgICAgIGlmICh0ZW1wbGF0ZSAmJiBlbGVtZW50SGFzQnVpbHRDc3ModGVtcGxhdGUpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlmICh0ZW1wbGF0ZSAmJiAhdGVtcGxhdGVJc1ZhbGlkKHRlbXBsYXRlKSkgewogICAgICAgICAgLy8gb25seSByZXZhbGlkYXRlIHRlbXBsYXRlIG9uY2UKICAgICAgICAgIGlmICghdGVtcGxhdGVJc1ZhbGlkYXRpbmcodGVtcGxhdGUpKSB7CiAgICAgICAgICAgIHRoaXMucHJlcGFyZVRlbXBsYXRlKHRlbXBsYXRlLCBpcyk7CiAgICAgICAgICAgIHN0YXJ0VmFsaWRhdGluZ1RlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIHVwZGF0ZSB0aGlzIGVsZW1lbnQgaW5zdGFuY2UKICAgICAgICAgIGxldCByb290ID0gZWxlbWVudC5zaGFkb3dSb290OwogICAgICAgICAgaWYgKHJvb3QpIHsKICAgICAgICAgICAgbGV0IHN0eWxlID0gLyoqIEB0eXBlIHtIVE1MU3R5bGVFbGVtZW50fSAqLyhyb290LnF1ZXJ5U2VsZWN0b3IoJ3N0eWxlJykpOwogICAgICAgICAgICBpZiAoc3R5bGUpIHsKICAgICAgICAgICAgICAvLyByZXVzZSB0aGUgdGVtcGxhdGUncyBzdHlsZSBhc3QsIGl0IGhhcyBhbGwgdGhlIG9yaWdpbmFsIGNzcyB0ZXh0CiAgICAgICAgICAgICAgc3R5bGVbJ19fY3NzUnVsZXMnXSA9IHRlbXBsYXRlWydfc3R5bGVBc3QnXTsKICAgICAgICAgICAgICBzdHlsZS50ZXh0Q29udGVudCA9IHRvQ3NzVGV4dCh0ZW1wbGF0ZVsnX3N0eWxlQXN0J10pOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge09iamVjdD19IHByb3BlcnRpZXMKICAgICAgICovCiAgICAgIHN0eWxlRG9jdW1lbnQocHJvcGVydGllcykgewogICAgICAgIHRoaXMuZW5zdXJlKCk7CiAgICAgICAgdGhpcy5zdHlsZVN1YnRyZWUoZG9jdW1lbnQuYm9keSwgcHJvcGVydGllcyk7CiAgICAgIH0KICAgIH0KCiAgICBpZiAoIXdpbmRvdy5TaGFkeUNTUyB8fCAhd2luZG93LlNoYWR5Q1NTLlNjb3BpbmdTaGltKSB7CiAgICAgIGNvbnN0IGFwcGx5U2hpbUludGVyZmFjZSA9IG5ldyBBcHBseVNoaW1JbnRlcmZhY2UoKTsKICAgICAgbGV0IEN1c3RvbVN0eWxlSW50ZXJmYWNlID0gd2luZG93LlNoYWR5Q1NTICYmIHdpbmRvdy5TaGFkeUNTUy5DdXN0b21TdHlsZUludGVyZmFjZTsKCiAgICAgIC8qKiBAc3VwcHJlc3Mge2R1cGxpY2F0ZX0gKi8KICAgICAgd2luZG93LlNoYWR5Q1NTID0gewogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBlbGVtZW50RXh0ZW5kcwogICAgICAgICAqLwogICAgICAgIHByZXBhcmVUZW1wbGF0ZSh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUsIGVsZW1lbnRFeHRlbmRzKSB7IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKICAgICAgICAgIGFwcGx5U2hpbUludGVyZmFjZS5mbHVzaEN1c3RvbVN0eWxlcygpOwogICAgICAgICAgYXBwbHlTaGltSW50ZXJmYWNlLnByZXBhcmVUZW1wbGF0ZSh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUpOwogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBlbGVtZW50RXh0ZW5kcwogICAgICAgICAqLwogICAgICAgIHByZXBhcmVUZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUsIGVsZW1lbnRFeHRlbmRzKSB7CiAgICAgICAgICB3aW5kb3cuU2hhZHlDU1MucHJlcGFyZVRlbXBsYXRlKHRlbXBsYXRlLCBlbGVtZW50TmFtZSwgZWxlbWVudEV4dGVuZHMpOwogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAgICovCiAgICAgICAgcHJlcGFyZVRlbXBsYXRlRG9tKHRlbXBsYXRlLCBlbGVtZW50TmFtZSkge30sIC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKCiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAgICAgKiBAcGFyYW0ge09iamVjdD19IHByb3BlcnRpZXMKICAgICAgICAgKi8KICAgICAgICBzdHlsZVN1YnRyZWUoZWxlbWVudCwgcHJvcGVydGllcykgewogICAgICAgICAgYXBwbHlTaGltSW50ZXJmYWNlLmZsdXNoQ3VzdG9tU3R5bGVzKCk7CiAgICAgICAgICBhcHBseVNoaW1JbnRlcmZhY2Uuc3R5bGVTdWJ0cmVlKGVsZW1lbnQsIHByb3BlcnRpZXMpOwogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSBlbGVtZW50CiAgICAgICAgICovCiAgICAgICAgc3R5bGVFbGVtZW50KGVsZW1lbnQpIHsKICAgICAgICAgIGFwcGx5U2hpbUludGVyZmFjZS5mbHVzaEN1c3RvbVN0eWxlcygpOwogICAgICAgICAgYXBwbHlTaGltSW50ZXJmYWNlLnN0eWxlRWxlbWVudChlbGVtZW50KTsKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBAcGFyYW0ge09iamVjdD19IHByb3BlcnRpZXMKICAgICAgICAgKi8KICAgICAgICBzdHlsZURvY3VtZW50KHByb3BlcnRpZXMpIHsKICAgICAgICAgIGFwcGx5U2hpbUludGVyZmFjZS5mbHVzaEN1c3RvbVN0eWxlcygpOwogICAgICAgICAgYXBwbHlTaGltSW50ZXJmYWNlLnN0eWxlRG9jdW1lbnQocHJvcGVydGllcyk7CiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5CiAgICAgICAgICogQHJldHVybiB7c3RyaW5nfQogICAgICAgICAqLwogICAgICAgIGdldENvbXB1dGVkU3R5bGVWYWx1ZShlbGVtZW50LCBwcm9wZXJ0eSkgewogICAgICAgICAgcmV0dXJuIGdldENvbXB1dGVkU3R5bGVWYWx1ZShlbGVtZW50LCBwcm9wZXJ0eSk7CiAgICAgICAgfSwKCiAgICAgICAgZmx1c2hDdXN0b21TdHlsZXMoKSB7CiAgICAgICAgICBhcHBseVNoaW1JbnRlcmZhY2UuZmx1c2hDdXN0b21TdHlsZXMoKTsKICAgICAgICB9LAoKICAgICAgICBuYXRpdmVDc3M6IG5hdGl2ZUNzc1ZhcmlhYmxlcywKICAgICAgICBuYXRpdmVTaGFkb3c6IG5hdGl2ZVNoYWRvdywKICAgICAgICBjc3NCdWlsZDogY3NzQnVpbGQsCiAgICAgICAgZGlzYWJsZVJ1bnRpbWU6IGRpc2FibGVSdW50aW1lLAogICAgICB9OwoKICAgICAgaWYgKEN1c3RvbVN0eWxlSW50ZXJmYWNlKSB7CiAgICAgICAgd2luZG93LlNoYWR5Q1NTLkN1c3RvbVN0eWxlSW50ZXJmYWNlID0gQ3VzdG9tU3R5bGVJbnRlcmZhY2U7CiAgICAgIH0KICAgIH0KCiAgICB3aW5kb3cuU2hhZHlDU1MuQXBwbHlTaGltID0gYXBwbHlTaGltOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAc3VtbWFyeSBDb2xsYXBzZSBtdWx0aXBsZSBjYWxsYmFja3MgaW50byBvbmUgaW52b2NhdGlvbiBhZnRlciBhIHRpbWVyLgogICAgICovCiAgICBjbGFzcyBEZWJvdW5jZXIgewogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICB0aGlzLl9hc3luY01vZHVsZSA9IG51bGw7CiAgICAgICAgdGhpcy5fY2FsbGJhY2sgPSBudWxsOwogICAgICAgIHRoaXMuX3RpbWVyID0gbnVsbDsKICAgICAgfQogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgc2NoZWR1bGVyOyB0aGF0IGlzLCBhIG1vZHVsZSB3aXRoIHRoZSBBc3luYyBpbnRlcmZhY2UsCiAgICAgICAqIGEgY2FsbGJhY2sgYW5kIG9wdGlvbmFsIGFyZ3VtZW50cyB0byBiZSBwYXNzZWQgdG8gdGhlIHJ1biBmdW5jdGlvbgogICAgICAgKiBmcm9tIHRoZSBhc3luYyBtb2R1bGUuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUFzeW5jSW50ZXJmYWNlfSBhc3luY01vZHVsZSBPYmplY3Qgd2l0aCBBc3luYyBpbnRlcmZhY2UuCiAgICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oKX0gY2FsbGJhY2sgQ2FsbGJhY2sgdG8gcnVuLgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgc2V0Q29uZmlnKGFzeW5jTW9kdWxlLCBjYWxsYmFjaykgewogICAgICAgIHRoaXMuX2FzeW5jTW9kdWxlID0gYXN5bmNNb2R1bGU7CiAgICAgICAgdGhpcy5fY2FsbGJhY2sgPSBjYWxsYmFjazsKICAgICAgICB0aGlzLl90aW1lciA9IHRoaXMuX2FzeW5jTW9kdWxlLnJ1bigoKSA9PiB7CiAgICAgICAgICB0aGlzLl90aW1lciA9IG51bGw7CiAgICAgICAgICBkZWJvdW5jZXJRdWV1ZS5kZWxldGUodGhpcyk7CiAgICAgICAgICB0aGlzLl9jYWxsYmFjaygpOwogICAgICAgIH0pOwogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBDYW5jZWxzIGFuIGFjdGl2ZSBkZWJvdW5jZXIgYW5kIHJldHVybnMgYSByZWZlcmVuY2UgdG8gaXRzZWxmLgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgY2FuY2VsKCkgewogICAgICAgIGlmICh0aGlzLmlzQWN0aXZlKCkpIHsKICAgICAgICAgIHRoaXMuX2NhbmNlbEFzeW5jKCk7CiAgICAgICAgICAvLyBDYW5jZWxpbmcgYSBkZWJvdW5jZXIgcmVtb3ZlcyBpdHMgc3BvdCBmcm9tIHRoZSBmbHVzaCBxdWV1ZSwKICAgICAgICAgIC8vIHNvIGlmIGEgZGVib3VuY2VyIGlzIG1hbnVhbGx5IGNhbmNlbGVkIGFuZCByZS1kZWJvdW5jZWQsIGl0CiAgICAgICAgICAvLyB3aWxsIHJlc2V0IGl0cyBmbHVzaCBvcmRlciAodGhpcyBpcyBhIHZlcnkgbWlub3IgZGlmZmVyZW5jZSBmcm9tIDEueCkKICAgICAgICAgIC8vIFJlLWRlYm91bmNpbmcgdmlhIHRoZSBgZGVib3VuY2VgIEFQSSByZXRhaW5zIHRoZSAxLnggRklGTyBmbHVzaCBvcmRlcgogICAgICAgICAgZGVib3VuY2VyUXVldWUuZGVsZXRlKHRoaXMpOwogICAgICAgIH0KICAgICAgfQogICAgICAvKioKICAgICAgICogQ2FuY2VscyBhIGRlYm91bmNlcidzIGFzeW5jIGNhbGxiYWNrLgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX2NhbmNlbEFzeW5jKCkgewogICAgICAgIGlmICh0aGlzLmlzQWN0aXZlKCkpIHsKICAgICAgICAgIHRoaXMuX2FzeW5jTW9kdWxlLmNhbmNlbCgvKiogQHR5cGUge251bWJlcn0gKi8odGhpcy5fdGltZXIpKTsKICAgICAgICAgIHRoaXMuX3RpbWVyID0gbnVsbDsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEZsdXNoZXMgYW4gYWN0aXZlIGRlYm91bmNlciBhbmQgcmV0dXJucyBhIHJlZmVyZW5jZSB0byBpdHNlbGYuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBmbHVzaCgpIHsKICAgICAgICBpZiAodGhpcy5pc0FjdGl2ZSgpKSB7CiAgICAgICAgICB0aGlzLmNhbmNlbCgpOwogICAgICAgICAgdGhpcy5fY2FsbGJhY2soKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgZGVib3VuY2VyIGlzIGFjdGl2ZS4KICAgICAgICoKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBhY3RpdmUuCiAgICAgICAqLwogICAgICBpc0FjdGl2ZSgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fdGltZXIgIT0gbnVsbDsKICAgICAgfQogICAgICAvKioKICAgICAgICogQ3JlYXRlcyBhIGRlYm91bmNlciBpZiBubyBkZWJvdW5jZXIgaXMgcGFzc2VkIGFzIGEgcGFyYW1ldGVyCiAgICAgICAqIG9yIGl0IGNhbmNlbHMgYW4gYWN0aXZlIGRlYm91bmNlciBvdGhlcndpc2UuIFRoZSBmb2xsb3dpbmcKICAgICAgICogZXhhbXBsZSBzaG93cyBob3cgYSBkZWJvdW5jZXIgY2FuIGJlIGNhbGxlZCBtdWx0aXBsZSB0aW1lcyB3aXRoaW4gYQogICAgICAgKiBtaWNyb3Rhc2sgYW5kICJkZWJvdW5jZWQiIHN1Y2ggdGhhdCB0aGUgcHJvdmlkZWQgY2FsbGJhY2sgZnVuY3Rpb24gaXMKICAgICAgICogY2FsbGVkIG9uY2UuIEFkZCB0aGlzIG1ldGhvZCB0byBhIGN1c3RvbSBlbGVtZW50OgogICAgICAgKgogICAgICAgKiBgYGBqcwogICAgICAgKiBpbXBvcnQge21pY3JvVGFza30gZnJvbSAnQHBvbHltZXIvcG9seW1lci9saWIvdXRpbHMvYXN5bmMuanMnOwogICAgICAgKiBpbXBvcnQge0RlYm91bmNlcn0gZnJvbSAnQHBvbHltZXIvcG9seW1lci9saWIvdXRpbHMvZGVib3VuY2UuanMnOwogICAgICAgKiAvLyAuLi4KICAgICAgICoKICAgICAgICogX2RlYm91bmNlV29yaygpIHsKICAgICAgICogICB0aGlzLl9kZWJvdW5jZUpvYiA9IERlYm91bmNlci5kZWJvdW5jZSh0aGlzLl9kZWJvdW5jZUpvYiwKICAgICAgICogICAgICAgbWljcm9UYXNrLCAoKSA9PiB0aGlzLl9kb1dvcmsoKSk7CiAgICAgICAqIH0KICAgICAgICogYGBgCiAgICAgICAqCiAgICAgICAqIElmIHRoZSBgX2RlYm91bmNlV29ya2AgbWV0aG9kIGlzIGNhbGxlZCBtdWx0aXBsZSB0aW1lcyB3aXRoaW4gdGhlIHNhbWUKICAgICAgICogbWljcm90YXNrLCB0aGUgYF9kb1dvcmtgIGZ1bmN0aW9uIHdpbGwgYmUgY2FsbGVkIG9ubHkgb25jZSBhdCB0aGUgbmV4dAogICAgICAgKiBtaWNyb3Rhc2sgY2hlY2twb2ludC4KICAgICAgICoKICAgICAgICogTm90ZTogSW4gdGVzdGluZyBpdCBpcyBvZnRlbiBjb252ZW5pZW50IHRvIGF2b2lkIGFzeW5jaHJvbnkuIFRvIGFjY29tcGxpc2gKICAgICAgICogdGhpcyB3aXRoIGEgZGVib3VuY2VyLCB5b3UgY2FuIHVzZSBgZW5xdWV1ZURlYm91bmNlcmAgYW5kCiAgICAgICAqIGBmbHVzaGAuIEZvciBleGFtcGxlLCBleHRlbmQgdGhlIGFib3ZlIGV4YW1wbGUgYnkgYWRkaW5nCiAgICAgICAqIGBlbnF1ZXVlRGVib3VuY2VyKHRoaXMuX2RlYm91bmNlSm9iKWAgYXQgdGhlIGVuZCBvZiB0aGUKICAgICAgICogYF9kZWJvdW5jZVdvcmtgIG1ldGhvZC4gVGhlbiBpbiBhIHRlc3QsIGNhbGwgYGZsdXNoYCB0byBlbnN1cmUKICAgICAgICogdGhlIGRlYm91bmNlciBoYXMgY29tcGxldGVkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0RlYm91bmNlcj99IGRlYm91bmNlciBEZWJvdW5jZXIgb2JqZWN0LgogICAgICAgKiBAcGFyYW0geyFBc3luY0ludGVyZmFjZX0gYXN5bmNNb2R1bGUgT2JqZWN0IHdpdGggQXN5bmMgaW50ZXJmYWNlCiAgICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oKX0gY2FsbGJhY2sgQ2FsbGJhY2sgdG8gcnVuLgogICAgICAgKiBAcmV0dXJuIHshRGVib3VuY2VyfSBSZXR1cm5zIGEgZGVib3VuY2VyIG9iamVjdC4KICAgICAgICovCiAgICAgIHN0YXRpYyBkZWJvdW5jZShkZWJvdW5jZXIsIGFzeW5jTW9kdWxlLCBjYWxsYmFjaykgewogICAgICAgIGlmIChkZWJvdW5jZXIgaW5zdGFuY2VvZiBEZWJvdW5jZXIpIHsKICAgICAgICAgIC8vIENhbmNlbCB0aGUgYXN5bmMgY2FsbGJhY2ssIGJ1dCBsZWF2ZSBpbiBkZWJvdW5jZXJRdWV1ZSBpZiBpdCB3YXMKICAgICAgICAgIC8vIGVucXVldWVkLCB0byBtYWludGFpbiAxLnggZmx1c2ggb3JkZXIKICAgICAgICAgIGRlYm91bmNlci5fY2FuY2VsQXN5bmMoKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZGVib3VuY2VyID0gbmV3IERlYm91bmNlcigpOwogICAgICAgIH0KICAgICAgICBkZWJvdW5jZXIuc2V0Q29uZmlnKGFzeW5jTW9kdWxlLCBjYWxsYmFjayk7CiAgICAgICAgcmV0dXJuIGRlYm91bmNlcjsKICAgICAgfQogICAgfQoKICAgIGxldCBkZWJvdW5jZXJRdWV1ZSA9IG5ldyBTZXQoKTsKCiAgICAvKioKICAgICAqIEFkZHMgYSBgRGVib3VuY2VyYCB0byBhIGxpc3Qgb2YgZ2xvYmFsbHkgZmx1c2hhYmxlIHRhc2tzLgogICAgICoKICAgICAqIEBwYXJhbSB7IURlYm91bmNlcn0gZGVib3VuY2VyIERlYm91bmNlciB0byBlbnF1ZXVlCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICovCiAgICBjb25zdCBlbnF1ZXVlRGVib3VuY2VyID0gZnVuY3Rpb24oZGVib3VuY2VyKSB7CiAgICAgIGRlYm91bmNlclF1ZXVlLmFkZChkZWJvdW5jZXIpOwogICAgfTsKCiAgICAvKioKICAgICAqIEZsdXNoZXMgYW55IGVucXVldWVkIGRlYm91bmNlcnMKICAgICAqCiAgICAgKiBAcmV0dXJuIHtib29sZWFufSBSZXR1cm5zIHdoZXRoZXIgYW55IGRlYm91bmNlcnMgd2VyZSBmbHVzaGVkCiAgICAgKi8KICAgIGNvbnN0IGZsdXNoRGVib3VuY2VycyA9IGZ1bmN0aW9uKCkgewogICAgICBjb25zdCBkaWRGbHVzaCA9IEJvb2xlYW4oZGVib3VuY2VyUXVldWUuc2l6ZSk7CiAgICAgIC8vIElmIG5ldyBkZWJvdW5jZXJzIGFyZSBhZGRlZCB3aGlsZSBmbHVzaGluZywgU2V0LmZvckVhY2ggd2lsbCBlbnN1cmUKICAgICAgLy8gbmV3bHkgYWRkZWQgb25lcyBhcmUgYWxzbyBmbHVzaGVkCiAgICAgIGRlYm91bmNlclF1ZXVlLmZvckVhY2goZGVib3VuY2VyID0+IHsKICAgICAgICB0cnkgewogICAgICAgICAgZGVib3VuY2VyLmZsdXNoKCk7CiAgICAgICAgfSBjYXRjaChlKSB7CiAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHsKICAgICAgICAgICAgdGhyb3cgZTsKICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfSk7CiAgICAgIHJldHVybiBkaWRGbHVzaDsKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyBkZXRlY3QgbmF0aXZlIHRvdWNoIGFjdGlvbiBzdXBwb3J0CiAgICBsZXQgSEFTX05BVElWRV9UQSA9IHR5cGVvZiBkb2N1bWVudC5oZWFkLnN0eWxlLnRvdWNoQWN0aW9uID09PSAnc3RyaW5nJzsKICAgIGxldCBHRVNUVVJFX0tFWSA9ICdfX3BvbHltZXJHZXN0dXJlcyc7CiAgICBsZXQgSEFORExFRF9PQkogPSAnX19wb2x5bWVyR2VzdHVyZXNIYW5kbGVkJzsKICAgIGxldCBUT1VDSF9BQ1RJT04gPSAnX19wb2x5bWVyR2VzdHVyZXNUb3VjaEFjdGlvbic7CiAgICAvLyByYWRpdXMgZm9yIHRhcCBhbmQgdHJhY2sKICAgIGxldCBUQVBfRElTVEFOQ0UgPSAyNTsKICAgIGxldCBUUkFDS19ESVNUQU5DRSA9IDU7CiAgICAvLyBudW1iZXIgb2YgbGFzdCBOIHRyYWNrIHBvc2l0aW9ucyB0byBrZWVwCiAgICBsZXQgVFJBQ0tfTEVOR1RIID0gMjsKCiAgICAvLyBEaXNhYmxpbmcgIm1vdXNlIiBoYW5kbGVycyBmb3IgMjUwMG1zIGlzIGVub3VnaAogICAgbGV0IE1PVVNFX1RJTUVPVVQgPSAyNTAwOwogICAgbGV0IE1PVVNFX0VWRU5UUyA9IFsnbW91c2Vkb3duJywgJ21vdXNlbW92ZScsICdtb3VzZXVwJywgJ2NsaWNrJ107CiAgICAvLyBhbiBhcnJheSBvZiBiaXRtYXNrIHZhbHVlcyBmb3IgbWFwcGluZyBNb3VzZUV2ZW50LndoaWNoIHRvIE1vdXNlRXZlbnQuYnV0dG9ucwogICAgbGV0IE1PVVNFX1dISUNIX1RPX0JVVFRPTlMgPSBbMCwgMSwgNCwgMl07CiAgICBsZXQgTU9VU0VfSEFTX0JVVFRPTlMgPSAoZnVuY3Rpb24oKSB7CiAgICAgIHRyeSB7CiAgICAgICAgcmV0dXJuIG5ldyBNb3VzZUV2ZW50KCd0ZXN0Jywge2J1dHRvbnM6IDF9KS5idXR0b25zID09PSAxOwogICAgICB9IGNhdGNoIChlKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICB9KSgpOwoKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgUG9zc2libGUgbW91c2UgZXZlbnQgbmFtZQogICAgICogQHJldHVybiB7Ym9vbGVhbn0gdHJ1ZSBpZiBtb3VzZSBldmVudCwgZmFsc2UgaWYgbm90CiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzTW91c2VFdmVudChuYW1lKSB7CiAgICAgIHJldHVybiBNT1VTRV9FVkVOVFMuaW5kZXhPZihuYW1lKSA+IC0xOwogICAgfQoKICAgIC8qIGVzbGludCBuby1lbXB0eTogWyJlcnJvciIsIHsgImFsbG93RW1wdHlDYXRjaCI6IHRydWUgfV0gKi8KICAgIC8vIGNoZWNrIGZvciBwYXNzaXZlIGV2ZW50IGxpc3RlbmVycwogICAgbGV0IHN1cHBvcnRzUGFzc2l2ZSA9IGZhbHNlOwogICAgKGZ1bmN0aW9uKCkgewogICAgICB0cnkgewogICAgICAgIGxldCBvcHRzID0gT2JqZWN0LmRlZmluZVByb3BlcnR5KHt9LCAncGFzc2l2ZScsIHtnZXQoKSB7c3VwcG9ydHNQYXNzaXZlID0gdHJ1ZTt9fSk7CiAgICAgICAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ3Rlc3QnLCBudWxsLCBvcHRzKTsKICAgICAgICB3aW5kb3cucmVtb3ZlRXZlbnRMaXN0ZW5lcigndGVzdCcsIG51bGwsIG9wdHMpOwogICAgICB9IGNhdGNoKGUpIHt9CiAgICB9KSgpOwoKICAgIC8qKgogICAgICogR2VuZXJhdGUgc2V0dGluZ3MgZm9yIGV2ZW50IGxpc3RlbmVycywgZGVwZW5kYW50IG9uIGBwYXNzaXZlVG91Y2hHZXN0dXJlc2AKICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZlbnROYW1lIEV2ZW50IG5hbWUgdG8gZGV0ZXJtaW5lIGlmIGB7cGFzc2l2ZX1gIG9wdGlvbiBpcwogICAgICogICBuZWVkZWQKICAgICAqIEByZXR1cm4ge3twYXNzaXZlOiBib29sZWFufSB8IHVuZGVmaW5lZH0gT3B0aW9ucyB0byB1c2UgZm9yIGFkZEV2ZW50TGlzdGVuZXIKICAgICAqICAgYW5kIHJlbW92ZUV2ZW50TGlzdGVuZXIKICAgICAqLwogICAgZnVuY3Rpb24gUEFTU0lWRV9UT1VDSChldmVudE5hbWUpIHsKICAgICAgaWYgKGlzTW91c2VFdmVudChldmVudE5hbWUpIHx8IGV2ZW50TmFtZSA9PT0gJ3RvdWNoZW5kJykgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICBpZiAoSEFTX05BVElWRV9UQSAmJiBzdXBwb3J0c1Bhc3NpdmUgJiYgcGFzc2l2ZVRvdWNoR2VzdHVyZXMpIHsKICAgICAgICByZXR1cm4ge3Bhc3NpdmU6IHRydWV9OwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgfQoKICAgIC8vIENoZWNrIGZvciB0b3VjaC1vbmx5IGRldmljZXMKICAgIGxldCBJU19UT1VDSF9PTkxZID0gbmF2aWdhdG9yLnVzZXJBZ2VudC5tYXRjaCgvaVAoPzpbb2FdZHxob25lKXxBbmRyb2lkLyk7CgogICAgLy8ga2VlcCB0cmFjayBvZiBhbnkgbGFiZWxzIGhpdCBieSB0aGUgbW91c2VDYW5jZWxsZXIKICAgIC8qKiBAdHlwZSB7IUFycmF5PCFIVE1MTGFiZWxFbGVtZW50Pn0gKi8KICAgIGNvbnN0IGNsaWNrZWRMYWJlbHMgPSBbXTsKCiAgICAvKiogQHR5cGUgeyFPYmplY3Q8Ym9vbGVhbj59ICovCiAgICBjb25zdCBsYWJlbGxhYmxlID0gewogICAgICAnYnV0dG9uJzogdHJ1ZSwKICAgICAgJ2lucHV0JzogdHJ1ZSwKICAgICAgJ2tleWdlbic6IHRydWUsCiAgICAgICdtZXRlcic6IHRydWUsCiAgICAgICdvdXRwdXQnOiB0cnVlLAogICAgICAndGV4dGFyZWEnOiB0cnVlLAogICAgICAncHJvZ3Jlc3MnOiB0cnVlLAogICAgICAnc2VsZWN0JzogdHJ1ZQogICAgfTsKCiAgICAvLyBEZWZpbmVkIGF0IGh0dHBzOi8vaHRtbC5zcGVjLndoYXR3Zy5vcmcvbXVsdGlwYWdlL2Zvcm0tY29udHJvbC1pbmZyYXN0cnVjdHVyZS5odG1sI2VuYWJsaW5nLWFuZC1kaXNhYmxpbmctZm9ybS1jb250cm9sczotdGhlLWRpc2FibGVkLWF0dHJpYnV0ZQogICAgLyoqIEB0eXBlIHshT2JqZWN0PGJvb2xlYW4+fSAqLwogICAgY29uc3QgY2FuQmVEaXNhYmxlZCA9IHsKICAgICAgJ2J1dHRvbic6IHRydWUsCiAgICAgICdjb21tYW5kJzogdHJ1ZSwKICAgICAgJ2ZpZWxkc2V0JzogdHJ1ZSwKICAgICAgJ2lucHV0JzogdHJ1ZSwKICAgICAgJ2tleWdlbic6IHRydWUsCiAgICAgICdvcHRncm91cCc6IHRydWUsCiAgICAgICdvcHRpb24nOiB0cnVlLAogICAgICAnc2VsZWN0JzogdHJ1ZSwKICAgICAgJ3RleHRhcmVhJzogdHJ1ZQogICAgfTsKCiAgICAvKioKICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsIEVsZW1lbnQgdG8gY2hlY2sgbGFiZWxsaW5nIHN0YXR1cwogICAgICogQHJldHVybiB7Ym9vbGVhbn0gZWxlbWVudCBjYW4gaGF2ZSBsYWJlbHMKICAgICAqLwogICAgZnVuY3Rpb24gY2FuQmVMYWJlbGxlZChlbCkgewogICAgICByZXR1cm4gbGFiZWxsYWJsZVtlbC5sb2NhbE5hbWVdIHx8IGZhbHNlOwogICAgfQoKICAgIC8qKgogICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWwgRWxlbWVudCB0aGF0IG1heSBiZSBsYWJlbGxlZC4KICAgICAqIEByZXR1cm4geyFBcnJheTwhSFRNTExhYmVsRWxlbWVudD59IFJlbGV2YW50IGxhYmVsIGZvciBgZWxgCiAgICAgKi8KICAgIGZ1bmN0aW9uIG1hdGNoaW5nTGFiZWxzKGVsKSB7CiAgICAgIGxldCBsYWJlbHMgPSBBcnJheS5wcm90b3R5cGUuc2xpY2UuY2FsbCgvKiogQHR5cGUge0hUTUxJbnB1dEVsZW1lbnR9ICovKGVsKS5sYWJlbHMgfHwgW10pOwogICAgICAvLyBJRSBkb2Vzbid0IGhhdmUgYGxhYmVsc2AgYW5kIFNhZmFyaSBkb2Vzbid0IHBvcHVsYXRlIGBsYWJlbHNgCiAgICAgIC8vIGlmIGVsZW1lbnQgaXMgaW4gYSBzaGFkb3dyb290LgogICAgICAvLyBJbiB0aGlzIGluc3RhbmNlLCBmaW5kaW5nIHRoZSBub24tYW5jZXN0b3IgbGFiZWxzIGlzIGVub3VnaCwKICAgICAgLy8gYXMgdGhlIG1vdXNlQ2FuY2VsbG9yIGNvZGUgd2lsbCBoYW5kbGUgYW5jc3RvciBsYWJlbHMKICAgICAgaWYgKCFsYWJlbHMubGVuZ3RoKSB7CiAgICAgICAgbGFiZWxzID0gW107CiAgICAgICAgbGV0IHJvb3QgPSBlbC5nZXRSb290Tm9kZSgpOwogICAgICAgIC8vIGlmIHRoZXJlIGlzIGFuIGlkIG9uIGBlbGAsIGNoZWNrIGZvciBhbGwgbGFiZWxzIHdpdGggYSBtYXRjaGluZyBgZm9yYCBhdHRyaWJ1dGUKICAgICAgICBpZiAoZWwuaWQpIHsKICAgICAgICAgIGxldCBtYXRjaGluZyA9IHJvb3QucXVlcnlTZWxlY3RvckFsbChgbGFiZWxbZm9yID0gJHtlbC5pZH1dYCk7CiAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IG1hdGNoaW5nLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGxhYmVscy5wdXNoKC8qKiBAdHlwZSB7IUhUTUxMYWJlbEVsZW1lbnR9ICovKG1hdGNoaW5nW2ldKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBsYWJlbHM7CiAgICB9CgogICAgLy8gdG91Y2ggd2lsbCBtYWtlIHN5bnRoZXRpYyBtb3VzZSBldmVudHMKICAgIC8vIGBwcmV2ZW50RGVmYXVsdGAgb24gdG91Y2hlbmQgd2lsbCBjYW5jZWwgdGhlbSwKICAgIC8vIGJ1dCB0aGlzIGJyZWFrcyBgPGlucHV0PmAgZm9jdXMgYW5kIGxpbmsgY2xpY2tzCiAgICAvLyBkaXNhYmxlIG1vdXNlIGhhbmRsZXJzIGZvciBNT1VTRV9USU1FT1VUIG1zIGFmdGVyCiAgICAvLyBhIHRvdWNoZW5kIHRvIGlnbm9yZSBzeW50aGV0aWMgbW91c2UgZXZlbnRzCiAgICBsZXQgbW91c2VDYW5jZWxsZXIgPSBmdW5jdGlvbihtb3VzZUV2ZW50KSB7CiAgICAgIC8vIENoZWNrIGZvciBzb3VyY2VDYXBhYmlsaXRpZXMsIHVzZWQgdG8gZGlzdGluZ3Vpc2ggc3ludGhldGljIGV2ZW50cwogICAgICAvLyBpZiBtb3VzZUV2ZW50IGRpZCBub3QgY29tZSBmcm9tIGEgZGV2aWNlIHRoYXQgZmlyZXMgdG91Y2ggZXZlbnRzLAogICAgICAvLyBpdCB3YXMgbWFkZSBieSBhIHJlYWwgbW91c2UgYW5kIHNob3VsZCBiZSBjb3VudGVkCiAgICAgIC8vIGh0dHA6Ly93aWNnLmdpdGh1Yi5pby9JbnB1dERldmljZUNhcGFiaWxpdGllcy8jZG9tLWlucHV0ZGV2aWNlY2FwYWJpbGl0aWVzLWZpcmVzdG91Y2hldmVudHMKICAgICAgbGV0IHNjID0gbW91c2VFdmVudC5zb3VyY2VDYXBhYmlsaXRpZXM7CiAgICAgIGlmIChzYyAmJiAhc2MuZmlyZXNUb3VjaEV2ZW50cykgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICAvLyBza2lwIHN5bnRoZXRpYyBtb3VzZSBldmVudHMKICAgICAgbW91c2VFdmVudFtIQU5ETEVEX09CSl0gPSB7c2tpcDogdHJ1ZX07CiAgICAgIC8vIGRpc2FibGUgImdob3N0IGNsaWNrcyIKICAgICAgaWYgKG1vdXNlRXZlbnQudHlwZSA9PT0gJ2NsaWNrJykgewogICAgICAgIGxldCBjbGlja0Zyb21MYWJlbCA9IGZhbHNlOwogICAgICAgIGxldCBwYXRoID0gZ2V0Q29tcG9zZWRQYXRoKG1vdXNlRXZlbnQpOwogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcGF0aC5sZW5ndGg7IGkrKykgewogICAgICAgICAgaWYgKHBhdGhbaV0ubm9kZVR5cGUgPT09IE5vZGUuRUxFTUVOVF9OT0RFKSB7CiAgICAgICAgICAgIGlmIChwYXRoW2ldLmxvY2FsTmFtZSA9PT0gJ2xhYmVsJykgewogICAgICAgICAgICAgIGNsaWNrZWRMYWJlbHMucHVzaCgvKiogQHR5cGUgeyFIVE1MTGFiZWxFbGVtZW50fSAqLyAocGF0aFtpXSkpOwogICAgICAgICAgICB9IGVsc2UgaWYgKGNhbkJlTGFiZWxsZWQoLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovIChwYXRoW2ldKSkpIHsKICAgICAgICAgICAgICBsZXQgb3duZXJMYWJlbHMgPQogICAgICAgICAgICAgICAgICBtYXRjaGluZ0xhYmVscygvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8gKHBhdGhbaV0pKTsKICAgICAgICAgICAgICAvLyBjaGVjayBpZiBvbmUgb2YgdGhlIGNsaWNrZWQgbGFiZWxzIGlzIGxhYmVsbGluZyB0aGlzIGVsZW1lbnQKICAgICAgICAgICAgICBmb3IgKGxldCBqID0gMDsgaiA8IG93bmVyTGFiZWxzLmxlbmd0aDsgaisrKSB7CiAgICAgICAgICAgICAgICBjbGlja0Zyb21MYWJlbCA9IGNsaWNrRnJvbUxhYmVsIHx8IGNsaWNrZWRMYWJlbHMuaW5kZXhPZihvd25lckxhYmVsc1tqXSkgPiAtMTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGlmIChwYXRoW2ldID09PSBQT0lOVEVSU1RBVEUubW91c2UudGFyZ2V0KSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gaWYgb25lIG9mIHRoZSBjbGlja2VkIGxhYmVscyB3YXMgbGFiZWxsaW5nIHRoZSB0YXJnZXQgZWxlbWVudCwKICAgICAgICAvLyB0aGlzIGlzIG5vdCBhIGdob3N0IGNsaWNrCiAgICAgICAgaWYgKGNsaWNrRnJvbUxhYmVsKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIG1vdXNlRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgICBtb3VzZUV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgICogQHBhcmFtIHtib29sZWFuPX0gc2V0dXAgVHJ1ZSB0byBhZGQsIGZhbHNlIHRvIHJlbW92ZS4KICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHNldHVwVGVhcmRvd25Nb3VzZUNhbmNlbGxlcihzZXR1cCkgewogICAgICBsZXQgZXZlbnRzID0gSVNfVE9VQ0hfT05MWSA/IFsnY2xpY2snXSA6IE1PVVNFX0VWRU5UUzsKICAgICAgZm9yIChsZXQgaSA9IDAsIGVuOyBpIDwgZXZlbnRzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgZW4gPSBldmVudHNbaV07CiAgICAgICAgaWYgKHNldHVwKSB7CiAgICAgICAgICAvLyByZXNldCBjbGlja0xhYmVscyBhcnJheQogICAgICAgICAgY2xpY2tlZExhYmVscy5sZW5ndGggPSAwOwogICAgICAgICAgZG9jdW1lbnQuYWRkRXZlbnRMaXN0ZW5lcihlbiwgbW91c2VDYW5jZWxsZXIsIHRydWUpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBkb2N1bWVudC5yZW1vdmVFdmVudExpc3RlbmVyKGVuLCBtb3VzZUNhbmNlbGxlciwgdHJ1ZSk7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gaWdub3JlTW91c2UoZSkgewogICAgICBpZiAoIVBPSU5URVJTVEFURS5tb3VzZS5tb3VzZUlnbm9yZUpvYikgewogICAgICAgIHNldHVwVGVhcmRvd25Nb3VzZUNhbmNlbGxlcih0cnVlKTsKICAgICAgfQogICAgICBsZXQgdW5zZXQgPSBmdW5jdGlvbigpIHsKICAgICAgICBzZXR1cFRlYXJkb3duTW91c2VDYW5jZWxsZXIoKTsKICAgICAgICBQT0lOVEVSU1RBVEUubW91c2UudGFyZ2V0ID0gbnVsbDsKICAgICAgICBQT0lOVEVSU1RBVEUubW91c2UubW91c2VJZ25vcmVKb2IgPSBudWxsOwogICAgICB9OwogICAgICBQT0lOVEVSU1RBVEUubW91c2UudGFyZ2V0ID0gZ2V0Q29tcG9zZWRQYXRoKGUpWzBdOwogICAgICBQT0lOVEVSU1RBVEUubW91c2UubW91c2VJZ25vcmVKb2IgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgIFBPSU5URVJTVEFURS5tb3VzZS5tb3VzZUlnbm9yZUpvYgogICAgICAgICAgLCB0aW1lT3V0LmFmdGVyKE1PVVNFX1RJTUVPVVQpCiAgICAgICAgICAsIHVuc2V0KTsKICAgIH0KCiAgICAvKioKICAgICAqIEBwYXJhbSB7TW91c2VFdmVudH0gZXYgZXZlbnQgdG8gdGVzdCBmb3IgbGVmdCBtb3VzZSBidXR0b24gZG93bgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gaGFzIGxlZnQgbW91c2UgYnV0dG9uIGRvd24KICAgICAqLwogICAgZnVuY3Rpb24gaGFzTGVmdE1vdXNlQnV0dG9uKGV2KSB7CiAgICAgIGxldCB0eXBlID0gZXYudHlwZTsKICAgICAgLy8gZXhpdCBlYXJseSBpZiB0aGUgZXZlbnQgaXMgbm90IGEgbW91c2UgZXZlbnQKICAgICAgaWYgKCFpc01vdXNlRXZlbnQodHlwZSkpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgLy8gZXYuYnV0dG9uIGlzIG5vdCByZWxpYWJsZSBmb3IgbW91c2Vtb3ZlICgwIGlzIG92ZXJsb2FkZWQgYXMgYm90aCBsZWZ0IGJ1dHRvbiBhbmQgbm8gYnV0dG9ucykKICAgICAgLy8gaW5zdGVhZCB3ZSB1c2UgZXYuYnV0dG9ucyAoYml0bWFzayBvZiBidXR0b25zKSBvciBmYWxsIGJhY2sgdG8gZXYud2hpY2ggKGRlcHJlY2F0ZWQsIDAgZm9yIG5vIGJ1dHRvbnMsIDEgZm9yIGxlZnQgYnV0dG9uKQogICAgICBpZiAodHlwZSA9PT0gJ21vdXNlbW92ZScpIHsKICAgICAgICAvLyBhbGxvdyB1bmRlZmluZWQgZm9yIHRlc3RpbmcgZXZlbnRzCiAgICAgICAgbGV0IGJ1dHRvbnMgPSBldi5idXR0b25zID09PSB1bmRlZmluZWQgPyAxIDogZXYuYnV0dG9uczsKICAgICAgICBpZiAoKGV2IGluc3RhbmNlb2Ygd2luZG93Lk1vdXNlRXZlbnQpICYmICFNT1VTRV9IQVNfQlVUVE9OUykgewogICAgICAgICAgYnV0dG9ucyA9IE1PVVNFX1dISUNIX1RPX0JVVFRPTlNbZXYud2hpY2hdIHx8IDA7CiAgICAgICAgfQogICAgICAgIC8vIGJ1dHRvbnMgaXMgYSBiaXRtYXNrLCBjaGVjayB0aGF0IHRoZSBsZWZ0IGJ1dHRvbiBiaXQgaXMgc2V0ICgxKQogICAgICAgIHJldHVybiBCb29sZWFuKGJ1dHRvbnMgJiAxKTsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBhbGxvdyB1bmRlZmluZWQgZm9yIHRlc3RpbmcgZXZlbnRzCiAgICAgICAgbGV0IGJ1dHRvbiA9IGV2LmJ1dHRvbiA9PT0gdW5kZWZpbmVkID8gMCA6IGV2LmJ1dHRvbjsKICAgICAgICAvLyBldi5idXR0b24gaXMgMCBpbiBtb3VzZWRvd24vbW91c2V1cC9jbGljayBmb3IgbGVmdCBidXR0b24gYWN0aXZhdGlvbgogICAgICAgIHJldHVybiBidXR0b24gPT09IDA7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpc1N5bnRoZXRpY0NsaWNrKGV2KSB7CiAgICAgIGlmIChldi50eXBlID09PSAnY2xpY2snKSB7CiAgICAgICAgLy8gZXYuZGV0YWlsIGlzIDAgZm9yIEhUTUxFbGVtZW50LmNsaWNrIGluIG1vc3QgYnJvd3NlcnMKICAgICAgICBpZiAoZXYuZGV0YWlsID09PSAwKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgLy8gaW4gdGhlIHdvcnN0IGNhc2UsIGNoZWNrIHRoYXQgdGhlIHgveSBwb3NpdGlvbiBvZiB0aGUgY2xpY2sgaXMgd2l0aGluCiAgICAgICAgLy8gdGhlIGJvdW5kaW5nIGJveCBvZiB0aGUgdGFyZ2V0IG9mIHRoZSBldmVudAogICAgICAgIC8vIFRoYW5rcyBJRSAxMCA+OigKICAgICAgICBsZXQgdCA9IF9maW5kT3JpZ2luYWxUYXJnZXQoZXYpOwogICAgICAgIC8vIG1ha2Ugc3VyZSB0aGUgdGFyZ2V0IG9mIHRoZSBldmVudCBpcyBhbiBlbGVtZW50IHNvIHdlIGNhbiB1c2UgZ2V0Qm91bmRpbmdDbGllbnRSZWN0LAogICAgICAgIC8vIGlmIG5vdCwganVzdCBhc3N1bWUgaXQgaXMgYSBzeW50aGV0aWMgY2xpY2sKICAgICAgICBpZiAoIXQubm9kZVR5cGUgfHwgLyoqIEB0eXBlIHtFbGVtZW50fSAqLyh0KS5ub2RlVHlwZSAhPT0gTm9kZS5FTEVNRU5UX05PREUpIHsKICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KICAgICAgICBsZXQgYmNyID0gLyoqIEB0eXBlIHtFbGVtZW50fSAqLyh0KS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAvLyB1c2UgcGFnZSB4L3kgdG8gYWNjb3VudCBmb3Igc2Nyb2xsaW5nCiAgICAgICAgbGV0IHggPSBldi5wYWdlWCwgeSA9IGV2LnBhZ2VZOwogICAgICAgIC8vIGV2IGlzIGEgc3ludGhldGljIGNsaWNrIGlmIHRoZSBwb3NpdGlvbiBpcyBvdXRzaWRlIHRoZSBib3VuZGluZyBib3ggb2YgdGhlIHRhcmdldAogICAgICAgIHJldHVybiAhKCh4ID49IGJjci5sZWZ0ICYmIHggPD0gYmNyLnJpZ2h0KSAmJiAoeSA+PSBiY3IudG9wICYmIHkgPD0gYmNyLmJvdHRvbSkpOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KCiAgICBsZXQgUE9JTlRFUlNUQVRFID0gewogICAgICBtb3VzZTogewogICAgICAgIHRhcmdldDogbnVsbCwKICAgICAgICBtb3VzZUlnbm9yZUpvYjogbnVsbAogICAgICB9LAogICAgICB0b3VjaDogewogICAgICAgIHg6IDAsCiAgICAgICAgeTogMCwKICAgICAgICBpZDogLTEsCiAgICAgICAgc2Nyb2xsRGVjaWRlZDogZmFsc2UKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBmaXJzdFRvdWNoQWN0aW9uKGV2KSB7CiAgICAgIGxldCB0YSA9ICdhdXRvJzsKICAgICAgbGV0IHBhdGggPSBnZXRDb21wb3NlZFBhdGgoZXYpOwogICAgICBmb3IgKGxldCBpID0gMCwgbjsgaSA8IHBhdGgubGVuZ3RoOyBpKyspIHsKICAgICAgICBuID0gcGF0aFtpXTsKICAgICAgICBpZiAobltUT1VDSF9BQ1RJT05dKSB7CiAgICAgICAgICB0YSA9IG5bVE9VQ0hfQUNUSU9OXTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGE7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhY2tEb2N1bWVudChzdGF0ZU9iaiwgbW92ZWZuLCB1cGZuKSB7CiAgICAgIHN0YXRlT2JqLm1vdmVmbiA9IG1vdmVmbjsKICAgICAgc3RhdGVPYmoudXBmbiA9IHVwZm47CiAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlbW92ZScsIG1vdmVmbik7CiAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNldXAnLCB1cGZuKTsKICAgIH0KCiAgICBmdW5jdGlvbiB1bnRyYWNrRG9jdW1lbnQoc3RhdGVPYmopIHsKICAgICAgZG9jdW1lbnQucmVtb3ZlRXZlbnRMaXN0ZW5lcignbW91c2Vtb3ZlJywgc3RhdGVPYmoubW92ZWZuKTsKICAgICAgZG9jdW1lbnQucmVtb3ZlRXZlbnRMaXN0ZW5lcignbW91c2V1cCcsIHN0YXRlT2JqLnVwZm4pOwogICAgICBzdGF0ZU9iai5tb3ZlZm4gPSBudWxsOwogICAgICBzdGF0ZU9iai51cGZuID0gbnVsbDsKICAgIH0KCiAgICB7CiAgICAgIC8vIHVzZSBhIGRvY3VtZW50LXdpZGUgdG91Y2hlbmQgbGlzdGVuZXIgdG8gc3RhcnQgdGhlIGdob3N0LWNsaWNrIHByZXZlbnRpb24gbWVjaGFuaXNtCiAgICAgIC8vIFVzZSBwYXNzaXZlIGV2ZW50IGxpc3RlbmVycywgaWYgc3VwcG9ydGVkLCB0byBub3QgYWZmZWN0IHNjcm9sbGluZyBwZXJmb3JtYW5jZQogICAgICBkb2N1bWVudC5hZGRFdmVudExpc3RlbmVyKCd0b3VjaGVuZCcsIGlnbm9yZU1vdXNlLCBzdXBwb3J0c1Bhc3NpdmUgPyB7cGFzc2l2ZTogdHJ1ZX0gOiBmYWxzZSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRoZSBjb21wb3NlZFBhdGggZm9yIHRoZSBnaXZlbiBldmVudC4KICAgICAqIEBwYXJhbSB7RXZlbnR9IGV2ZW50IHRvIHByb2Nlc3MKICAgICAqIEByZXR1cm4geyFBcnJheTwhRXZlbnRUYXJnZXQ+fSBQYXRoIG9mIHRoZSBldmVudAogICAgICovCiAgICBjb25zdCBnZXRDb21wb3NlZFBhdGggPSB3aW5kb3cuU2hhZHlET00gJiYgd2luZG93LlNoYWR5RE9NLm5vUGF0Y2ggPwogICAgICB3aW5kb3cuU2hhZHlET00uY29tcG9zZWRQYXRoIDoKICAgICAgKGV2ZW50KSA9PiBldmVudC5jb21wb3NlZFBhdGggJiYgZXZlbnQuY29tcG9zZWRQYXRoKCkgfHwgW107CgogICAgLyoqIEB0eXBlIHshT2JqZWN0PHN0cmluZywgIUdlc3R1cmVSZWNvZ25pemVyPn0gKi8KICAgIGNvbnN0IGdlc3R1cmVzID0ge307CgogICAgLyoqIEB0eXBlIHshQXJyYXk8IUdlc3R1cmVSZWNvZ25pemVyPn0gKi8KICAgIGNvbnN0IHJlY29nbml6ZXJzID0gW107CgogICAgLyoqCiAgICAgKiBGaW5kcyB0aGUgZWxlbWVudCByZW5kZXJlZCBvbiB0aGUgc2NyZWVuIGF0IHRoZSBwcm92aWRlZCBjb29yZGluYXRlcy4KICAgICAqCiAgICAgKiBTaW1pbGFyIHRvIGBkb2N1bWVudC5lbGVtZW50RnJvbVBvaW50YCwgYnV0IHBpZXJjZXMgdGhyb3VnaAogICAgICogc2hhZG93IHJvb3RzLgogICAgICoKICAgICAqIEBwYXJhbSB7bnVtYmVyfSB4IEhvcml6b250YWwgcGl4ZWwgY29vcmRpbmF0ZQogICAgICogQHBhcmFtIHtudW1iZXJ9IHkgVmVydGljYWwgcGl4ZWwgY29vcmRpbmF0ZQogICAgICogQHJldHVybiB7RWxlbWVudH0gUmV0dXJucyB0aGUgZGVlcGVzdCBzaGFkb3dSb290IGluY2x1c2l2ZSBlbGVtZW50CiAgICAgKiBmb3VuZCBhdCB0aGUgc2NyZWVuIHBvc2l0aW9uIGdpdmVuLgogICAgICovCiAgICBmdW5jdGlvbiBkZWVwVGFyZ2V0RmluZCh4LCB5KSB7CiAgICAgIGxldCBub2RlID0gZG9jdW1lbnQuZWxlbWVudEZyb21Qb2ludCh4LCB5KTsKICAgICAgbGV0IG5leHQgPSBub2RlOwogICAgICAvLyB0aGlzIGNvZGUgcGF0aCBpcyBvbmx5IHRha2VuIHdoZW4gbmF0aXZlIFNoYWRvd0RPTSBpcyB1c2VkCiAgICAgIC8vIGlmIHRoZXJlIGlzIGEgc2hhZG93cm9vdCwgaXQgbWF5IGhhdmUgYSBub2RlIGF0IHgveQogICAgICAvLyBpZiB0aGVyZSBpcyBub3QgYSBzaGFkb3dyb290LCBleGl0IHRoZSBsb29wCiAgICAgIHdoaWxlIChuZXh0ICYmIG5leHQuc2hhZG93Um9vdCAmJiAhd2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgLy8gaWYgdGhlcmUgaXMgYSBub2RlIGF0IHgveSBpbiB0aGUgc2hhZG93cm9vdCwgbG9vayBkZWVwZXIKICAgICAgICBsZXQgb2xkTmV4dCA9IG5leHQ7CiAgICAgICAgbmV4dCA9IG5leHQuc2hhZG93Um9vdC5lbGVtZW50RnJvbVBvaW50KHgsIHkpOwogICAgICAgIC8vIG9uIFNhZmFyaSwgZWxlbWVudEZyb21Qb2ludCBtYXkgcmV0dXJuIHRoZSBzaGFkb3dSb290IGhvc3QKICAgICAgICBpZiAob2xkTmV4dCA9PT0gbmV4dCkgewogICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGlmIChuZXh0KSB7CiAgICAgICAgICBub2RlID0gbmV4dDsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgLyoqCiAgICAgKiBhIGNoZWFwZXIgY2hlY2sgdGhhbiBldi5jb21wb3NlZFBhdGgoKVswXTsKICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtFdmVudHxUb3VjaH0gZXYgRXZlbnQuCiAgICAgKiBAcmV0dXJuIHtFdmVudFRhcmdldH0gUmV0dXJucyB0aGUgZXZlbnQgdGFyZ2V0LgogICAgICovCiAgICBmdW5jdGlvbiBfZmluZE9yaWdpbmFsVGFyZ2V0KGV2KSB7CiAgICAgIGNvbnN0IHBhdGggPSBnZXRDb21wb3NlZFBhdGgoLyoqIEB0eXBlIHs/RXZlbnR9ICovIChldikpOwogICAgICAvLyBJdCBzaG91bGRuJ3QgYmUsIGJ1dCBzb21ldGltZXMgcGF0aCBpcyBlbXB0eSAod2luZG93IG9uIFNhZmFyaSkuCiAgICAgIHJldHVybiBwYXRoLmxlbmd0aCA+IDAgPyBwYXRoWzBdIDogZXYudGFyZ2V0OwogICAgfQoKICAgIC8qKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RXZlbnR9IGV2IEV2ZW50LgogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gX2hhbmRsZU5hdGl2ZShldikgewogICAgICBsZXQgaGFuZGxlZDsKICAgICAgbGV0IHR5cGUgPSBldi50eXBlOwogICAgICBsZXQgbm9kZSA9IGV2LmN1cnJlbnRUYXJnZXQ7CiAgICAgIGxldCBnb2JqID0gbm9kZVtHRVNUVVJFX0tFWV07CiAgICAgIGlmICghZ29iaikgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICBsZXQgZ3MgPSBnb2JqW3R5cGVdOwogICAgICBpZiAoIWdzKSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICAgIGlmICghZXZbSEFORExFRF9PQkpdKSB7CiAgICAgICAgZXZbSEFORExFRF9PQkpdID0ge307CiAgICAgICAgaWYgKHR5cGUuc2xpY2UoMCwgNSkgPT09ICd0b3VjaCcpIHsKICAgICAgICAgIGV2ID0gLyoqIEB0eXBlIHtUb3VjaEV2ZW50fSAqLyhldik7IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tc2VsZi1hc3NpZ24KICAgICAgICAgIGxldCB0ID0gZXYuY2hhbmdlZFRvdWNoZXNbMF07CiAgICAgICAgICBpZiAodHlwZSA9PT0gJ3RvdWNoc3RhcnQnKSB7CiAgICAgICAgICAgIC8vIG9ubHkgaGFuZGxlIHRoZSBmaXJzdCBmaW5nZXIKICAgICAgICAgICAgaWYgKGV2LnRvdWNoZXMubGVuZ3RoID09PSAxKSB7CiAgICAgICAgICAgICAgUE9JTlRFUlNUQVRFLnRvdWNoLmlkID0gdC5pZGVudGlmaWVyOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoUE9JTlRFUlNUQVRFLnRvdWNoLmlkICE9PSB0LmlkZW50aWZpZXIpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgaWYgKCFIQVNfTkFUSVZFX1RBKSB7CiAgICAgICAgICAgIGlmICh0eXBlID09PSAndG91Y2hzdGFydCcgfHwgdHlwZSA9PT0gJ3RvdWNobW92ZScpIHsKICAgICAgICAgICAgICBfaGFuZGxlVG91Y2hBY3Rpb24oZXYpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIGhhbmRsZWQgPSBldltIQU5ETEVEX09CSl07CiAgICAgIC8vIHVzZWQgdG8gaWdub3JlIHN5bnRoZXRpYyBtb3VzZSBldmVudHMKICAgICAgaWYgKGhhbmRsZWQuc2tpcCkgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICAvLyByZXNldCByZWNvZ25pemVyIHN0YXRlCiAgICAgIGZvciAobGV0IGkgPSAwLCByOyBpIDwgcmVjb2duaXplcnMubGVuZ3RoOyBpKyspIHsKICAgICAgICByID0gcmVjb2duaXplcnNbaV07CiAgICAgICAgaWYgKGdzW3IubmFtZV0gJiYgIWhhbmRsZWRbci5uYW1lXSkgewogICAgICAgICAgaWYgKHIuZmxvdyAmJiByLmZsb3cuc3RhcnQuaW5kZXhPZihldi50eXBlKSA+IC0xICYmIHIucmVzZXQpIHsKICAgICAgICAgICAgci5yZXNldCgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICAvLyBlbmZvcmNlIGdlc3R1cmUgcmVjb2duaXplciBvcmRlcgogICAgICBmb3IgKGxldCBpID0gMCwgcjsgaSA8IHJlY29nbml6ZXJzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgciA9IHJlY29nbml6ZXJzW2ldOwogICAgICAgIGlmIChnc1tyLm5hbWVdICYmICFoYW5kbGVkW3IubmFtZV0pIHsKICAgICAgICAgIGhhbmRsZWRbci5uYW1lXSA9IHRydWU7CiAgICAgICAgICByW3R5cGVdKGV2KTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge1RvdWNoRXZlbnR9IGV2IEV2ZW50LgogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gX2hhbmRsZVRvdWNoQWN0aW9uKGV2KSB7CiAgICAgIGxldCB0ID0gZXYuY2hhbmdlZFRvdWNoZXNbMF07CiAgICAgIGxldCB0eXBlID0gZXYudHlwZTsKICAgICAgaWYgKHR5cGUgPT09ICd0b3VjaHN0YXJ0JykgewogICAgICAgIFBPSU5URVJTVEFURS50b3VjaC54ID0gdC5jbGllbnRYOwogICAgICAgIFBPSU5URVJTVEFURS50b3VjaC55ID0gdC5jbGllbnRZOwogICAgICAgIFBPSU5URVJTVEFURS50b3VjaC5zY3JvbGxEZWNpZGVkID0gZmFsc2U7CiAgICAgIH0gZWxzZSBpZiAodHlwZSA9PT0gJ3RvdWNobW92ZScpIHsKICAgICAgICBpZiAoUE9JTlRFUlNUQVRFLnRvdWNoLnNjcm9sbERlY2lkZWQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgUE9JTlRFUlNUQVRFLnRvdWNoLnNjcm9sbERlY2lkZWQgPSB0cnVlOwogICAgICAgIGxldCB0YSA9IGZpcnN0VG91Y2hBY3Rpb24oZXYpOwogICAgICAgIGxldCBzaG91bGRQcmV2ZW50ID0gZmFsc2U7CiAgICAgICAgbGV0IGR4ID0gTWF0aC5hYnMoUE9JTlRFUlNUQVRFLnRvdWNoLnggLSB0LmNsaWVudFgpOwogICAgICAgIGxldCBkeSA9IE1hdGguYWJzKFBPSU5URVJTVEFURS50b3VjaC55IC0gdC5jbGllbnRZKTsKICAgICAgICBpZiAoIWV2LmNhbmNlbGFibGUpIDsgZWxzZSBpZiAodGEgPT09ICdub25lJykgewogICAgICAgICAgc2hvdWxkUHJldmVudCA9IHRydWU7CiAgICAgICAgfSBlbHNlIGlmICh0YSA9PT0gJ3Bhbi14JykgewogICAgICAgICAgc2hvdWxkUHJldmVudCA9IGR5ID4gZHg7CiAgICAgICAgfSBlbHNlIGlmICh0YSA9PT0gJ3Bhbi15JykgewogICAgICAgICAgc2hvdWxkUHJldmVudCA9IGR4ID4gZHk7CiAgICAgICAgfQogICAgICAgIGlmIChzaG91bGRQcmV2ZW50KSB7CiAgICAgICAgICBldi5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBwcmV2ZW50KCd0cmFjaycpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQWRkcyBhbiBldmVudCBsaXN0ZW5lciB0byBhIG5vZGUgZm9yIHRoZSBnaXZlbiBnZXN0dXJlIHR5cGUuCiAgICAgKgogICAgICogQHBhcmFtIHshRXZlbnRUYXJnZXR9IG5vZGUgTm9kZSB0byBhZGQgbGlzdGVuZXIgb24KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldlR5cGUgR2VzdHVyZSB0eXBlOiBgZG93bmAsIGB1cGAsIGB0cmFja2AsIG9yIGB0YXBgCiAgICAgKiBAcGFyYW0geyFmdW5jdGlvbighRXZlbnQpOnZvaWR9IGhhbmRsZXIgRXZlbnQgbGlzdGVuZXIgZnVuY3Rpb24gdG8gY2FsbAogICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIGEgZ2VzdHVyZSBldmVudCBsaXN0ZW5lciB3YXMgYWRkZWQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFkZExpc3RlbmVyKG5vZGUsIGV2VHlwZSwgaGFuZGxlcikgewogICAgICBpZiAoZ2VzdHVyZXNbZXZUeXBlXSkgewogICAgICAgIF9hZGQobm9kZSwgZXZUeXBlLCBoYW5kbGVyKTsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZW1vdmVzIGFuIGV2ZW50IGxpc3RlbmVyIGZyb20gYSBub2RlIGZvciB0aGUgZ2l2ZW4gZ2VzdHVyZSB0eXBlLgogICAgICoKICAgICAqIEBwYXJhbSB7IUV2ZW50VGFyZ2V0fSBub2RlIE5vZGUgdG8gcmVtb3ZlIGxpc3RlbmVyIGZyb20KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldlR5cGUgR2VzdHVyZSB0eXBlOiBgZG93bmAsIGB1cGAsIGB0cmFja2AsIG9yIGB0YXBgCiAgICAgKiBAcGFyYW0geyFmdW5jdGlvbighRXZlbnQpOnZvaWR9IGhhbmRsZXIgRXZlbnQgbGlzdGVuZXIgZnVuY3Rpb24gcHJldmlvdXNseSBwYXNzZWQgdG8KICAgICAqICBgYWRkTGlzdGVuZXJgLgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIGEgZ2VzdHVyZSBldmVudCBsaXN0ZW5lciB3YXMgcmVtb3ZlZC4KICAgICAqLwogICAgZnVuY3Rpb24gcmVtb3ZlTGlzdGVuZXIobm9kZSwgZXZUeXBlLCBoYW5kbGVyKSB7CiAgICAgIGlmIChnZXN0dXJlc1tldlR5cGVdKSB7CiAgICAgICAgX3JlbW92ZShub2RlLCBldlR5cGUsIGhhbmRsZXIpOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KCiAgICAvKioKICAgICAqIGF1dG9tYXRlIHRoZSBldmVudCBsaXN0ZW5lcnMgZm9yIHRoZSBuYXRpdmUgZXZlbnRzCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7IUV2ZW50VGFyZ2V0fSBub2RlIE5vZGUgb24gd2hpY2ggdG8gYWRkIHRoZSBldmVudC4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldlR5cGUgRXZlbnQgdHlwZSB0byBhZGQuCiAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCFFdmVudCl9IGhhbmRsZXIgRXZlbnQgaGFuZGxlciBmdW5jdGlvbi4KICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIF9hZGQobm9kZSwgZXZUeXBlLCBoYW5kbGVyKSB7CiAgICAgIGxldCByZWNvZ25pemVyID0gZ2VzdHVyZXNbZXZUeXBlXTsKICAgICAgbGV0IGRlcHMgPSByZWNvZ25pemVyLmRlcHM7CiAgICAgIGxldCBuYW1lID0gcmVjb2duaXplci5uYW1lOwogICAgICBsZXQgZ29iaiA9IG5vZGVbR0VTVFVSRV9LRVldOwogICAgICBpZiAoIWdvYmopIHsKICAgICAgICBub2RlW0dFU1RVUkVfS0VZXSA9IGdvYmogPSB7fTsKICAgICAgfQogICAgICBmb3IgKGxldCBpID0gMCwgZGVwLCBnZDsgaSA8IGRlcHMubGVuZ3RoOyBpKyspIHsKICAgICAgICBkZXAgPSBkZXBzW2ldOwogICAgICAgIC8vIGRvbid0IGFkZCBtb3VzZSBoYW5kbGVycyBvbiBpT1MgYmVjYXVzZSB0aGV5IGNhdXNlIGdyYXkgc2VsZWN0aW9uIG92ZXJsYXlzCiAgICAgICAgaWYgKElTX1RPVUNIX09OTFkgJiYgaXNNb3VzZUV2ZW50KGRlcCkgJiYgZGVwICE9PSAnY2xpY2snKSB7CiAgICAgICAgICBjb250aW51ZTsKICAgICAgICB9CiAgICAgICAgZ2QgPSBnb2JqW2RlcF07CiAgICAgICAgaWYgKCFnZCkgewogICAgICAgICAgZ29ialtkZXBdID0gZ2QgPSB7X2NvdW50OiAwfTsKICAgICAgICB9CiAgICAgICAgaWYgKGdkLl9jb3VudCA9PT0gMCkgewogICAgICAgICAgbm9kZS5hZGRFdmVudExpc3RlbmVyKGRlcCwgX2hhbmRsZU5hdGl2ZSwgUEFTU0lWRV9UT1VDSChkZXApKTsKICAgICAgICB9CiAgICAgICAgZ2RbbmFtZV0gPSAoZ2RbbmFtZV0gfHwgMCkgKyAxOwogICAgICAgIGdkLl9jb3VudCA9IChnZC5fY291bnQgfHwgMCkgKyAxOwogICAgICB9CiAgICAgIG5vZGUuYWRkRXZlbnRMaXN0ZW5lcihldlR5cGUsIGhhbmRsZXIpOwogICAgICBpZiAocmVjb2duaXplci50b3VjaEFjdGlvbikgewogICAgICAgIHNldFRvdWNoQWN0aW9uKG5vZGUsIHJlY29nbml6ZXIudG91Y2hBY3Rpb24pOwogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBhdXRvbWF0ZSBldmVudCBsaXN0ZW5lciByZW1vdmFsIGZvciBuYXRpdmUgZXZlbnRzCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7IUV2ZW50VGFyZ2V0fSBub2RlIE5vZGUgb24gd2hpY2ggdG8gcmVtb3ZlIHRoZSBldmVudC4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldlR5cGUgRXZlbnQgdHlwZSB0byByZW1vdmUuCiAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCFFdmVudCk6IHZvaWR9IGhhbmRsZXIgRXZlbnQgaGFuZGxlciBmdW5jdGlvbi4KICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIF9yZW1vdmUobm9kZSwgZXZUeXBlLCBoYW5kbGVyKSB7CiAgICAgIGxldCByZWNvZ25pemVyID0gZ2VzdHVyZXNbZXZUeXBlXTsKICAgICAgbGV0IGRlcHMgPSByZWNvZ25pemVyLmRlcHM7CiAgICAgIGxldCBuYW1lID0gcmVjb2duaXplci5uYW1lOwogICAgICBsZXQgZ29iaiA9IG5vZGVbR0VTVFVSRV9LRVldOwogICAgICBpZiAoZ29iaikgewogICAgICAgIGZvciAobGV0IGkgPSAwLCBkZXAsIGdkOyBpIDwgZGVwcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgZGVwID0gZGVwc1tpXTsKICAgICAgICAgIGdkID0gZ29ialtkZXBdOwogICAgICAgICAgaWYgKGdkICYmIGdkW25hbWVdKSB7CiAgICAgICAgICAgIGdkW25hbWVdID0gKGdkW25hbWVdIHx8IDEpIC0gMTsKICAgICAgICAgICAgZ2QuX2NvdW50ID0gKGdkLl9jb3VudCB8fCAxKSAtIDE7CiAgICAgICAgICAgIGlmIChnZC5fY291bnQgPT09IDApIHsKICAgICAgICAgICAgICBub2RlLnJlbW92ZUV2ZW50TGlzdGVuZXIoZGVwLCBfaGFuZGxlTmF0aXZlLCBQQVNTSVZFX1RPVUNIKGRlcCkpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICAgIG5vZGUucmVtb3ZlRXZlbnRMaXN0ZW5lcihldlR5cGUsIGhhbmRsZXIpOwogICAgfQoKICAgIC8qKgogICAgICogUmVnaXN0ZXJzIGEgbmV3IGdlc3R1cmUgZXZlbnQgcmVjb2duaXplciBmb3IgYWRkaW5nIG5ldyBjdXN0b20KICAgICAqIGdlc3R1cmUgZXZlbnQgdHlwZXMuCiAgICAgKgogICAgICogQHBhcmFtIHshR2VzdHVyZVJlY29nbml6ZXJ9IHJlY29nIEdlc3R1cmUgcmVjb2duaXplciBkZXNjcmlwdG9yCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICovCiAgICBmdW5jdGlvbiByZWdpc3RlciQxKHJlY29nKSB7CiAgICAgIHJlY29nbml6ZXJzLnB1c2gocmVjb2cpOwogICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHJlY29nLmVtaXRzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgZ2VzdHVyZXNbcmVjb2cuZW1pdHNbaV1dID0gcmVjb2c7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZOYW1lIEV2ZW50IG5hbWUuCiAgICAgKiBAcmV0dXJuIHtPYmplY3R9IFJldHVybnMgdGhlIGdlc3R1cmUgZm9yIHRoZSBnaXZlbiBldmVudCBuYW1lLgogICAgICovCiAgICBmdW5jdGlvbiBfZmluZFJlY29nbml6ZXJCeUV2ZW50KGV2TmFtZSkgewogICAgICBmb3IgKGxldCBpID0gMCwgcjsgaSA8IHJlY29nbml6ZXJzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgciA9IHJlY29nbml6ZXJzW2ldOwogICAgICAgIGZvciAobGV0IGogPSAwLCBuOyBqIDwgci5lbWl0cy5sZW5ndGg7IGorKykgewogICAgICAgICAgbiA9IHIuZW1pdHNbal07CiAgICAgICAgICBpZiAobiA9PT0gZXZOYW1lKSB7CiAgICAgICAgICAgIHJldHVybiByOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICAvKioKICAgICAqIFNldHMgc2Nyb2xsaW5nIGRpcmVjdGlvbiBvbiBub2RlLgogICAgICoKICAgICAqIFRoaXMgdmFsdWUgaXMgY2hlY2tlZCBvbiBmaXJzdCBtb3ZlLCB0aHVzIGl0IHNob3VsZCBiZSBjYWxsZWQgcHJpb3IgdG8KICAgICAqIGFkZGluZyBldmVudCBsaXN0ZW5lcnMuCiAgICAgKgogICAgICogQHBhcmFtIHshRXZlbnRUYXJnZXR9IG5vZGUgTm9kZSB0byBzZXQgdG91Y2ggYWN0aW9uIHNldHRpbmcgb24KICAgICAqIEBwYXJhbSB7c3RyaW5nfSB2YWx1ZSBUb3VjaCBhY3Rpb24gdmFsdWUKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHNldFRvdWNoQWN0aW9uKG5vZGUsIHZhbHVlKSB7CiAgICAgIGlmIChIQVNfTkFUSVZFX1RBICYmIG5vZGUgaW5zdGFuY2VvZiBIVE1MRWxlbWVudCkgewogICAgICAgIC8vIE5PVEU6IGFkZCB0b3VjaEFjdGlvbiBhc3luYyBzbyB0aGF0IGV2ZW50cyBjYW4gYmUgYWRkZWQgaW4KICAgICAgICAvLyBjdXN0b20gZWxlbWVudCBjb25zdHJ1Y3RvcnMuIE90aGVyd2lzZSB3ZSBydW4gYWZvdWwgb2YgY3VzdG9tCiAgICAgICAgLy8gZWxlbWVudHMgcmVzdHJpY3Rpb24gYWdhaW5zdCBzZXR0aW5ncyBhdHRyaWJ1dGVzIChzdHlsZSkgaW4gdGhlCiAgICAgICAgLy8gY29uc3RydWN0b3IuCiAgICAgICAgbWljcm9UYXNrLnJ1bigoKSA9PiB7CiAgICAgICAgICBub2RlLnN0eWxlLnRvdWNoQWN0aW9uID0gdmFsdWU7CiAgICAgICAgfSk7CiAgICAgIH0KICAgICAgbm9kZVtUT1VDSF9BQ1RJT05dID0gdmFsdWU7CiAgICB9CgogICAgLyoqCiAgICAgKiBEaXNwYXRjaGVzIGFuIGV2ZW50IG9uIHRoZSBgdGFyZ2V0YCBlbGVtZW50IG9mIGB0eXBlYCB3aXRoIHRoZSBnaXZlbgogICAgICogYGRldGFpbGAuCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHshRXZlbnRUYXJnZXR9IHRhcmdldCBUaGUgZWxlbWVudCBvbiB3aGljaCB0byBmaXJlIGFuIGV2ZW50LgogICAgICogQHBhcmFtIHtzdHJpbmd9IHR5cGUgVGhlIHR5cGUgb2YgZXZlbnQgdG8gZmlyZS4KICAgICAqIEBwYXJhbSB7IU9iamVjdD19IGRldGFpbCBUaGUgZGV0YWlsIG9iamVjdCB0byBwb3B1bGF0ZSBvbiB0aGUgZXZlbnQuCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICovCiAgICBmdW5jdGlvbiBfZmlyZSh0YXJnZXQsIHR5cGUsIGRldGFpbCkgewogICAgICBsZXQgZXYgPSBuZXcgRXZlbnQodHlwZSwgeyBidWJibGVzOiB0cnVlLCBjYW5jZWxhYmxlOiB0cnVlLCBjb21wb3NlZDogdHJ1ZSB9KTsKICAgICAgZXYuZGV0YWlsID0gZGV0YWlsOwogICAgICB3cmFwKC8qKiBAdHlwZSB7IU5vZGV9ICovKHRhcmdldCkpLmRpc3BhdGNoRXZlbnQoZXYpOwogICAgICAvLyBmb3J3YXJkIGBwcmV2ZW50RGVmYXVsdGAgaW4gYSBjbGVhbiB3YXkKICAgICAgaWYgKGV2LmRlZmF1bHRQcmV2ZW50ZWQpIHsKICAgICAgICBsZXQgcHJldmVudGVyID0gZGV0YWlsLnByZXZlbnRlciB8fCBkZXRhaWwuc291cmNlRXZlbnQ7CiAgICAgICAgaWYgKHByZXZlbnRlciAmJiBwcmV2ZW50ZXIucHJldmVudERlZmF1bHQpIHsKICAgICAgICAgIHByZXZlbnRlci5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogUHJldmVudHMgdGhlIGRpc3BhdGNoIGFuZCBkZWZhdWx0IGFjdGlvbiBvZiB0aGUgZ2l2ZW4gZXZlbnQgbmFtZS4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZOYW1lIEV2ZW50IG5hbWUuCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICovCiAgICBmdW5jdGlvbiBwcmV2ZW50KGV2TmFtZSkgewogICAgICBsZXQgcmVjb2duaXplciA9IF9maW5kUmVjb2duaXplckJ5RXZlbnQoZXZOYW1lKTsKICAgICAgaWYgKHJlY29nbml6ZXIuaW5mbykgewogICAgICAgIHJlY29nbml6ZXIuaW5mby5wcmV2ZW50ID0gdHJ1ZTsKICAgICAgfQogICAgfQoKICAgIC8qIGVzbGludC1kaXNhYmxlIHZhbGlkLWpzZG9jICovCgogICAgcmVnaXN0ZXIkMSh7CiAgICAgIG5hbWU6ICdkb3dudXAnLAogICAgICBkZXBzOiBbJ21vdXNlZG93bicsICd0b3VjaHN0YXJ0JywgJ3RvdWNoZW5kJ10sCiAgICAgIGZsb3c6IHsKICAgICAgICBzdGFydDogWydtb3VzZWRvd24nLCAndG91Y2hzdGFydCddLAogICAgICAgIGVuZDogWydtb3VzZXVwJywgJ3RvdWNoZW5kJ10KICAgICAgfSwKICAgICAgZW1pdHM6IFsnZG93bicsICd1cCddLAoKICAgICAgaW5mbzogewogICAgICAgIG1vdmVmbjogbnVsbCwKICAgICAgICB1cGZuOiBudWxsCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHRoaXMge0dlc3R1cmVSZWNvZ25pemVyfQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgcmVzZXQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHVudHJhY2tEb2N1bWVudCh0aGlzLmluZm8pOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtNb3VzZUV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBtb3VzZWRvd246IGZ1bmN0aW9uKGUpIHsKICAgICAgICBpZiAoIWhhc0xlZnRNb3VzZUJ1dHRvbihlKSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBsZXQgdCA9IF9maW5kT3JpZ2luYWxUYXJnZXQoZSk7CiAgICAgICAgbGV0IHNlbGYgPSB0aGlzOwogICAgICAgIGxldCBtb3ZlZm4gPSBmdW5jdGlvbiBtb3ZlZm4oZSkgewogICAgICAgICAgaWYgKCFoYXNMZWZ0TW91c2VCdXR0b24oZSkpIHsKICAgICAgICAgICAgZG93bnVwRmlyZSgndXAnLCB0LCBlKTsKICAgICAgICAgICAgdW50cmFja0RvY3VtZW50KHNlbGYuaW5mbyk7CiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBsZXQgdXBmbiA9IGZ1bmN0aW9uIHVwZm4oZSkgewogICAgICAgICAgaWYgKGhhc0xlZnRNb3VzZUJ1dHRvbihlKSkgewogICAgICAgICAgICBkb3dudXBGaXJlKCd1cCcsIHQsIGUpOwogICAgICAgICAgfQogICAgICAgICAgdW50cmFja0RvY3VtZW50KHNlbGYuaW5mbyk7CiAgICAgICAgfTsKICAgICAgICB0cmFja0RvY3VtZW50KHRoaXMuaW5mbywgbW92ZWZuLCB1cGZuKTsKICAgICAgICBkb3dudXBGaXJlKCdkb3duJywgdCwgZSk7CiAgICAgIH0sCiAgICAgIC8qKgogICAgICAgKiBAdGhpcyB7R2VzdHVyZVJlY29nbml6ZXJ9CiAgICAgICAqIEBwYXJhbSB7VG91Y2hFdmVudH0gZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgdG91Y2hzdGFydDogZnVuY3Rpb24oZSkgewogICAgICAgIGRvd251cEZpcmUoJ2Rvd24nLCBfZmluZE9yaWdpbmFsVGFyZ2V0KGUpLCBlLmNoYW5nZWRUb3VjaGVzWzBdLCBlKTsKICAgICAgfSwKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtUb3VjaEV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICB0b3VjaGVuZDogZnVuY3Rpb24oZSkgewogICAgICAgIGRvd251cEZpcmUoJ3VwJywgX2ZpbmRPcmlnaW5hbFRhcmdldChlKSwgZS5jaGFuZ2VkVG91Y2hlc1swXSwgZSk7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgICogQHBhcmFtIHtzdHJpbmd9IHR5cGUKICAgICAqIEBwYXJhbSB7RXZlbnRUYXJnZXR9IHRhcmdldAogICAgICogQHBhcmFtIHtFdmVudHxUb3VjaH0gZXZlbnQKICAgICAqIEBwYXJhbSB7RXZlbnQ9fSBwcmV2ZW50ZXIKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIGRvd251cEZpcmUodHlwZSwgdGFyZ2V0LCBldmVudCwgcHJldmVudGVyKSB7CiAgICAgIGlmICghdGFyZ2V0KSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICAgIF9maXJlKHRhcmdldCwgdHlwZSwgewogICAgICAgIHg6IGV2ZW50LmNsaWVudFgsCiAgICAgICAgeTogZXZlbnQuY2xpZW50WSwKICAgICAgICBzb3VyY2VFdmVudDogZXZlbnQsCiAgICAgICAgcHJldmVudGVyOiBwcmV2ZW50ZXIsCiAgICAgICAgcHJldmVudDogZnVuY3Rpb24oZSkgewogICAgICAgICAgcmV0dXJuIHByZXZlbnQoZSk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICByZWdpc3RlciQxKHsKICAgICAgbmFtZTogJ3RyYWNrJywKICAgICAgdG91Y2hBY3Rpb246ICdub25lJywKICAgICAgZGVwczogWydtb3VzZWRvd24nLCAndG91Y2hzdGFydCcsICd0b3VjaG1vdmUnLCAndG91Y2hlbmQnXSwKICAgICAgZmxvdzogewogICAgICAgIHN0YXJ0OiBbJ21vdXNlZG93bicsICd0b3VjaHN0YXJ0J10sCiAgICAgICAgZW5kOiBbJ21vdXNldXAnLCAndG91Y2hlbmQnXQogICAgICB9LAogICAgICBlbWl0czogWyd0cmFjayddLAoKICAgICAgaW5mbzogewogICAgICAgIHg6IDAsCiAgICAgICAgeTogMCwKICAgICAgICBzdGF0ZTogJ3N0YXJ0JywKICAgICAgICBzdGFydGVkOiBmYWxzZSwKICAgICAgICBtb3ZlczogW10sCiAgICAgICAgLyoqIEB0aGlzIHtHZXN0dXJlSW5mb30gKi8KICAgICAgICBhZGRNb3ZlOiBmdW5jdGlvbihtb3ZlKSB7CiAgICAgICAgICBpZiAodGhpcy5tb3Zlcy5sZW5ndGggPiBUUkFDS19MRU5HVEgpIHsKICAgICAgICAgICAgdGhpcy5tb3Zlcy5zaGlmdCgpOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5tb3Zlcy5wdXNoKG1vdmUpOwogICAgICAgIH0sCiAgICAgICAgbW92ZWZuOiBudWxsLAogICAgICAgIHVwZm46IG51bGwsCiAgICAgICAgcHJldmVudDogZmFsc2UKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAdGhpcyB7R2VzdHVyZVJlY29nbml6ZXJ9CiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICByZXNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5pbmZvLnN0YXRlID0gJ3N0YXJ0JzsKICAgICAgICB0aGlzLmluZm8uc3RhcnRlZCA9IGZhbHNlOwogICAgICAgIHRoaXMuaW5mby5tb3ZlcyA9IFtdOwogICAgICAgIHRoaXMuaW5mby54ID0gMDsKICAgICAgICB0aGlzLmluZm8ueSA9IDA7CiAgICAgICAgdGhpcy5pbmZvLnByZXZlbnQgPSBmYWxzZTsKICAgICAgICB1bnRyYWNrRG9jdW1lbnQodGhpcy5pbmZvKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAdGhpcyB7R2VzdHVyZVJlY29nbml6ZXJ9CiAgICAgICAqIEBwYXJhbSB7TW91c2VFdmVudH0gZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgbW91c2Vkb3duOiBmdW5jdGlvbihlKSB7CiAgICAgICAgaWYgKCFoYXNMZWZ0TW91c2VCdXR0b24oZSkpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgbGV0IHQgPSBfZmluZE9yaWdpbmFsVGFyZ2V0KGUpOwogICAgICAgIGxldCBzZWxmID0gdGhpczsKICAgICAgICBsZXQgbW92ZWZuID0gZnVuY3Rpb24gbW92ZWZuKGUpIHsKICAgICAgICAgIGxldCB4ID0gZS5jbGllbnRYLCB5ID0gZS5jbGllbnRZOwogICAgICAgICAgaWYgKHRyYWNrSGFzTW92ZWRFbm91Z2goc2VsZi5pbmZvLCB4LCB5KSkgewogICAgICAgICAgICAvLyBmaXJzdCBtb3ZlIGlzICdzdGFydCcsIHN1YnNlcXVlbnQgbW92ZXMgYXJlICdtb3ZlJywgbW91c2V1cCBpcyAnZW5kJwogICAgICAgICAgICBzZWxmLmluZm8uc3RhdGUgPSBzZWxmLmluZm8uc3RhcnRlZCA/IChlLnR5cGUgPT09ICdtb3VzZXVwJyA/ICdlbmQnIDogJ3RyYWNrJykgOiAnc3RhcnQnOwogICAgICAgICAgICBpZiAoc2VsZi5pbmZvLnN0YXRlID09PSAnc3RhcnQnKSB7CiAgICAgICAgICAgICAgLy8gaWYgYW5kIG9ubHkgaWYgdHJhY2tpbmcsIGFsd2F5cyBwcmV2ZW50IHRhcAogICAgICAgICAgICAgIHByZXZlbnQoJ3RhcCcpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHNlbGYuaW5mby5hZGRNb3ZlKHt4OiB4LCB5OiB5fSk7CiAgICAgICAgICAgIGlmICghaGFzTGVmdE1vdXNlQnV0dG9uKGUpKSB7CiAgICAgICAgICAgICAgLy8gYWx3YXlzIGZpcmUgImVuZCIKICAgICAgICAgICAgICBzZWxmLmluZm8uc3RhdGUgPSAnZW5kJzsKICAgICAgICAgICAgICB1bnRyYWNrRG9jdW1lbnQoc2VsZi5pbmZvKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodCkgewogICAgICAgICAgICAgIHRyYWNrRmlyZShzZWxmLmluZm8sIHQsIGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHNlbGYuaW5mby5zdGFydGVkID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIGxldCB1cGZuID0gZnVuY3Rpb24gdXBmbihlKSB7CiAgICAgICAgICBpZiAoc2VsZi5pbmZvLnN0YXJ0ZWQpIHsKICAgICAgICAgICAgbW92ZWZuKGUpOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIHJlbW92ZSB0aGUgdGVtcG9yYXJ5IGxpc3RlbmVycwogICAgICAgICAgdW50cmFja0RvY3VtZW50KHNlbGYuaW5mbyk7CiAgICAgICAgfTsKICAgICAgICAvLyBhZGQgdGVtcG9yYXJ5IGRvY3VtZW50IGxpc3RlbmVycyBhcyBtb3VzZSByZXRhcmdldHMKICAgICAgICB0cmFja0RvY3VtZW50KHRoaXMuaW5mbywgbW92ZWZuLCB1cGZuKTsKICAgICAgICB0aGlzLmluZm8ueCA9IGUuY2xpZW50WDsKICAgICAgICB0aGlzLmluZm8ueSA9IGUuY2xpZW50WTsKICAgICAgfSwKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtUb3VjaEV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICB0b3VjaHN0YXJ0OiBmdW5jdGlvbihlKSB7CiAgICAgICAgbGV0IGN0ID0gZS5jaGFuZ2VkVG91Y2hlc1swXTsKICAgICAgICB0aGlzLmluZm8ueCA9IGN0LmNsaWVudFg7CiAgICAgICAgdGhpcy5pbmZvLnkgPSBjdC5jbGllbnRZOwogICAgICB9LAogICAgICAvKioKICAgICAgICogQHRoaXMge0dlc3R1cmVSZWNvZ25pemVyfQogICAgICAgKiBAcGFyYW0ge1RvdWNoRXZlbnR9IGUKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIHRvdWNobW92ZTogZnVuY3Rpb24oZSkgewogICAgICAgIGxldCB0ID0gX2ZpbmRPcmlnaW5hbFRhcmdldChlKTsKICAgICAgICBsZXQgY3QgPSBlLmNoYW5nZWRUb3VjaGVzWzBdOwogICAgICAgIGxldCB4ID0gY3QuY2xpZW50WCwgeSA9IGN0LmNsaWVudFk7CiAgICAgICAgaWYgKHRyYWNrSGFzTW92ZWRFbm91Z2godGhpcy5pbmZvLCB4LCB5KSkgewogICAgICAgICAgaWYgKHRoaXMuaW5mby5zdGF0ZSA9PT0gJ3N0YXJ0JykgewogICAgICAgICAgICAvLyBpZiBhbmQgb25seSBpZiB0cmFja2luZywgYWx3YXlzIHByZXZlbnQgdGFwCiAgICAgICAgICAgIHByZXZlbnQoJ3RhcCcpOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5pbmZvLmFkZE1vdmUoe3g6IHgsIHk6IHl9KTsKICAgICAgICAgIHRyYWNrRmlyZSh0aGlzLmluZm8sIHQsIGN0KTsKICAgICAgICAgIHRoaXMuaW5mby5zdGF0ZSA9ICd0cmFjayc7CiAgICAgICAgICB0aGlzLmluZm8uc3RhcnRlZCA9IHRydWU7CiAgICAgICAgfQogICAgICB9LAogICAgICAvKioKICAgICAgICogQHRoaXMge0dlc3R1cmVSZWNvZ25pemVyfQogICAgICAgKiBAcGFyYW0ge1RvdWNoRXZlbnR9IGUKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIHRvdWNoZW5kOiBmdW5jdGlvbihlKSB7CiAgICAgICAgbGV0IHQgPSBfZmluZE9yaWdpbmFsVGFyZ2V0KGUpOwogICAgICAgIGxldCBjdCA9IGUuY2hhbmdlZFRvdWNoZXNbMF07CiAgICAgICAgLy8gb25seSB0cmFja2VuZCBpZiB0cmFjayB3YXMgc3RhcnRlZCBhbmQgbm90IGFib3J0ZWQKICAgICAgICBpZiAodGhpcy5pbmZvLnN0YXJ0ZWQpIHsKICAgICAgICAgIC8vIHJlc2V0IHN0YXJ0ZWQgc3RhdGUgb24gdXAKICAgICAgICAgIHRoaXMuaW5mby5zdGF0ZSA9ICdlbmQnOwogICAgICAgICAgdGhpcy5pbmZvLmFkZE1vdmUoe3g6IGN0LmNsaWVudFgsIHk6IGN0LmNsaWVudFl9KTsKICAgICAgICAgIHRyYWNrRmlyZSh0aGlzLmluZm8sIHQsIGN0KTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgICogQHBhcmFtIHshR2VzdHVyZUluZm99IGluZm8KICAgICAqIEBwYXJhbSB7bnVtYmVyfSB4CiAgICAgKiBAcGFyYW0ge251bWJlcn0geQogICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAqLwogICAgZnVuY3Rpb24gdHJhY2tIYXNNb3ZlZEVub3VnaChpbmZvLCB4LCB5KSB7CiAgICAgIGlmIChpbmZvLnByZXZlbnQpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgaWYgKGluZm8uc3RhcnRlZCkgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIGxldCBkeCA9IE1hdGguYWJzKGluZm8ueCAtIHgpOwogICAgICBsZXQgZHkgPSBNYXRoLmFicyhpbmZvLnkgLSB5KTsKICAgICAgcmV0dXJuIChkeCA+PSBUUkFDS19ESVNUQU5DRSB8fCBkeSA+PSBUUkFDS19ESVNUQU5DRSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0geyFHZXN0dXJlSW5mb30gaW5mbwogICAgICogQHBhcmFtIHs/RXZlbnRUYXJnZXR9IHRhcmdldAogICAgICogQHBhcmFtIHtUb3VjaH0gdG91Y2gKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHRyYWNrRmlyZShpbmZvLCB0YXJnZXQsIHRvdWNoKSB7CiAgICAgIGlmICghdGFyZ2V0KSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICAgIGxldCBzZWNvbmRsYXN0ID0gaW5mby5tb3Zlc1tpbmZvLm1vdmVzLmxlbmd0aCAtIDJdOwogICAgICBsZXQgbGFzdG1vdmUgPSBpbmZvLm1vdmVzW2luZm8ubW92ZXMubGVuZ3RoIC0gMV07CiAgICAgIGxldCBkeCA9IGxhc3Rtb3ZlLnggLSBpbmZvLng7CiAgICAgIGxldCBkeSA9IGxhc3Rtb3ZlLnkgLSBpbmZvLnk7CiAgICAgIGxldCBkZHgsIGRkeSA9IDA7CiAgICAgIGlmIChzZWNvbmRsYXN0KSB7CiAgICAgICAgZGR4ID0gbGFzdG1vdmUueCAtIHNlY29uZGxhc3QueDsKICAgICAgICBkZHkgPSBsYXN0bW92ZS55IC0gc2Vjb25kbGFzdC55OwogICAgICB9CiAgICAgIF9maXJlKHRhcmdldCwgJ3RyYWNrJywgewogICAgICAgIHN0YXRlOiBpbmZvLnN0YXRlLAogICAgICAgIHg6IHRvdWNoLmNsaWVudFgsCiAgICAgICAgeTogdG91Y2guY2xpZW50WSwKICAgICAgICBkeDogZHgsCiAgICAgICAgZHk6IGR5LAogICAgICAgIGRkeDogZGR4LAogICAgICAgIGRkeTogZGR5LAogICAgICAgIHNvdXJjZUV2ZW50OiB0b3VjaCwKICAgICAgICBob3ZlcjogZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gZGVlcFRhcmdldEZpbmQodG91Y2guY2xpZW50WCwgdG91Y2guY2xpZW50WSk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICByZWdpc3RlciQxKHsKICAgICAgbmFtZTogJ3RhcCcsCiAgICAgIGRlcHM6IFsnbW91c2Vkb3duJywgJ2NsaWNrJywgJ3RvdWNoc3RhcnQnLCAndG91Y2hlbmQnXSwKICAgICAgZmxvdzogewogICAgICAgIHN0YXJ0OiBbJ21vdXNlZG93bicsICd0b3VjaHN0YXJ0J10sCiAgICAgICAgZW5kOiBbJ2NsaWNrJywgJ3RvdWNoZW5kJ10KICAgICAgfSwKICAgICAgZW1pdHM6IFsndGFwJ10sCiAgICAgIGluZm86IHsKICAgICAgICB4OiBOYU4sCiAgICAgICAgeTogTmFOLAogICAgICAgIHByZXZlbnQ6IGZhbHNlCiAgICAgIH0sCiAgICAgIC8qKgogICAgICAgKiBAdGhpcyB7R2VzdHVyZVJlY29nbml6ZXJ9CiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICByZXNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5pbmZvLnggPSBOYU47CiAgICAgICAgdGhpcy5pbmZvLnkgPSBOYU47CiAgICAgICAgdGhpcy5pbmZvLnByZXZlbnQgPSBmYWxzZTsKICAgICAgfSwKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtNb3VzZUV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBtb3VzZWRvd246IGZ1bmN0aW9uKGUpIHsKICAgICAgICBpZiAoaGFzTGVmdE1vdXNlQnV0dG9uKGUpKSB7CiAgICAgICAgICB0aGlzLmluZm8ueCA9IGUuY2xpZW50WDsKICAgICAgICAgIHRoaXMuaW5mby55ID0gZS5jbGllbnRZOwogICAgICAgIH0KICAgICAgfSwKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtNb3VzZUV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBjbGljazogZnVuY3Rpb24oZSkgewogICAgICAgIGlmIChoYXNMZWZ0TW91c2VCdXR0b24oZSkpIHsKICAgICAgICAgIHRyYWNrRm9yd2FyZCh0aGlzLmluZm8sIGUpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgLyoqCiAgICAgICAqIEB0aGlzIHtHZXN0dXJlUmVjb2duaXplcn0KICAgICAgICogQHBhcmFtIHtUb3VjaEV2ZW50fSBlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICB0b3VjaHN0YXJ0OiBmdW5jdGlvbihlKSB7CiAgICAgICAgY29uc3QgdG91Y2ggPSBlLmNoYW5nZWRUb3VjaGVzWzBdOwogICAgICAgIHRoaXMuaW5mby54ID0gdG91Y2guY2xpZW50WDsKICAgICAgICB0aGlzLmluZm8ueSA9IHRvdWNoLmNsaWVudFk7CiAgICAgIH0sCiAgICAgIC8qKgogICAgICAgKiBAdGhpcyB7R2VzdHVyZVJlY29nbml6ZXJ9CiAgICAgICAqIEBwYXJhbSB7VG91Y2hFdmVudH0gZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgdG91Y2hlbmQ6IGZ1bmN0aW9uKGUpIHsKICAgICAgICB0cmFja0ZvcndhcmQodGhpcy5pbmZvLCBlLmNoYW5nZWRUb3VjaGVzWzBdLCBlKTsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICAgKiBAcGFyYW0geyFHZXN0dXJlSW5mb30gaW5mbwogICAgICogQHBhcmFtIHtFdmVudCB8IFRvdWNofSBlCiAgICAgKiBAcGFyYW0ge0V2ZW50PX0gcHJldmVudGVyCiAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICovCiAgICBmdW5jdGlvbiB0cmFja0ZvcndhcmQoaW5mbywgZSwgcHJldmVudGVyKSB7CiAgICAgIGxldCBkeCA9IE1hdGguYWJzKGUuY2xpZW50WCAtIGluZm8ueCk7CiAgICAgIGxldCBkeSA9IE1hdGguYWJzKGUuY2xpZW50WSAtIGluZm8ueSk7CiAgICAgIC8vIGZpbmQgb3JpZ2luYWwgdGFyZ2V0IGZyb20gYHByZXZlbnRlcmAgZm9yIFRvdWNoRXZlbnRzLCBvciBgZWAgZm9yIE1vdXNlRXZlbnRzCiAgICAgIGxldCB0ID0gX2ZpbmRPcmlnaW5hbFRhcmdldCgocHJldmVudGVyIHx8IGUpKTsKICAgICAgaWYgKCF0IHx8IChjYW5CZURpc2FibGVkWy8qKiBAdHlwZSB7IUhUTUxFbGVtZW50fSAqLyh0KS5sb2NhbE5hbWVdICYmIHQuaGFzQXR0cmlidXRlKCdkaXNhYmxlZCcpKSkgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICAvLyBkeCxkeSBjYW4gYmUgTmFOIGlmIGBjbGlja2AgaGFzIGJlZW4gc2ltdWxhdGVkIGFuZCB0aGVyZSB3YXMgbm8gYGRvd25gIGZvciBgc3RhcnRgCiAgICAgIGlmIChpc05hTihkeCkgfHwgaXNOYU4oZHkpIHx8IChkeCA8PSBUQVBfRElTVEFOQ0UgJiYgZHkgPD0gVEFQX0RJU1RBTkNFKSB8fCBpc1N5bnRoZXRpY0NsaWNrKGUpKSB7CiAgICAgICAgLy8gcHJldmVudCB0YXBzIGZyb20gYmVpbmcgZ2VuZXJhdGVkIGlmIGFuIGV2ZW50IGhhcyBjYW5jZWxlZCB0aGVtCiAgICAgICAgaWYgKCFpbmZvLnByZXZlbnQpIHsKICAgICAgICAgIF9maXJlKHQsICd0YXAnLCB7CiAgICAgICAgICAgIHg6IGUuY2xpZW50WCwKICAgICAgICAgICAgeTogZS5jbGllbnRZLAogICAgICAgICAgICBzb3VyY2VFdmVudDogZSwKICAgICAgICAgICAgcHJldmVudGVyOiBwcmV2ZW50ZXIKICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qIGVzbGludC1lbmFibGUgdmFsaWQtanNkb2MgKi8KCiAgICAvKiogQGRlcHJlY2F0ZWQgKi8KICAgIGNvbnN0IGZpbmRPcmlnaW5hbFRhcmdldCA9IF9maW5kT3JpZ2luYWxUYXJnZXQ7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIEVsZW1lbnQgY2xhc3MgbWl4aW4gdGhhdCBwcm92aWRlcyBBUEkgZm9yIGFkZGluZyBQb2x5bWVyJ3MgY3Jvc3MtcGxhdGZvcm0KICAgICAqIGdlc3R1cmUgZXZlbnRzIHRvIG5vZGVzLgogICAgICoKICAgICAqIFRoZSBBUEkgaXMgZGVzaWduZWQgdG8gYmUgY29tcGF0aWJsZSB3aXRoIG92ZXJyaWRlIHBvaW50cyBpbXBsZW1lbnRlZAogICAgICogaW4gYFRlbXBsYXRlU3RhbXBgIHN1Y2ggdGhhdCBkZWNsYXJhdGl2ZSBldmVudCBsaXN0ZW5lcnMgaW4KICAgICAqIHRlbXBsYXRlcyB3aWxsIHN1cHBvcnQgZ2VzdHVyZSBldmVudHMgd2hlbiB0aGlzIG1peGluIGlzIGFwcGxpZWQgYWxvbmcgd2l0aAogICAgICogYFRlbXBsYXRlU3RhbXBgLgogICAgICoKICAgICAqIEBtaXhpbkZ1bmN0aW9uCiAgICAgKiBAcG9seW1lcgogICAgICogQHN1bW1hcnkgRWxlbWVudCBjbGFzcyBtaXhpbiB0aGF0IHByb3ZpZGVzIEFQSSBmb3IgYWRkaW5nIFBvbHltZXIncwogICAgICogICBjcm9zcy1wbGF0Zm9ybSBnZXN0dXJlIGV2ZW50cyB0byBub2RlcwogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIENsYXNzIHRvIGFwcGx5IG1peGluIHRvLgogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIHdpdGggbWl4aW4gYXBwbGllZC4KICAgICAqLwogICAgY29uc3QgR2VzdHVyZUV2ZW50TGlzdGVuZXJzID0gZGVkdXBpbmdNaXhpbigoc3VwZXJDbGFzcykgPT4gewogICAgICAvKioKICAgICAgICogQHBvbHltZXIKICAgICAgICogQG1peGluQ2xhc3MKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfR2VzdHVyZUV2ZW50TGlzdGVuZXJzfQogICAgICAgKi8KICAgICAgY2xhc3MgR2VzdHVyZUV2ZW50TGlzdGVuZXJzIGV4dGVuZHMgc3VwZXJDbGFzcyB7CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkIHRoZSBldmVudCBsaXN0ZW5lciB0byB0aGUgbm9kZSBpZiBpdCBpcyBhIGdlc3R1cmVzIGV2ZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshRXZlbnRUYXJnZXR9IG5vZGUgTm9kZSB0byBhZGQgZXZlbnQgbGlzdGVuZXIgdG8KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZlbnROYW1lIE5hbWUgb2YgZXZlbnQKICAgICAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCFFdmVudCk6dm9pZH0gaGFuZGxlciBMaXN0ZW5lciBmdW5jdGlvbiB0byBhZGQKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9hZGRFdmVudExpc3RlbmVyVG9Ob2RlKG5vZGUsIGV2ZW50TmFtZSwgaGFuZGxlcikgewogICAgICAgICAgaWYgKCFhZGRMaXN0ZW5lcihub2RlLCBldmVudE5hbWUsIGhhbmRsZXIpKSB7CiAgICAgICAgICAgIHN1cGVyLl9hZGRFdmVudExpc3RlbmVyVG9Ob2RlKG5vZGUsIGV2ZW50TmFtZSwgaGFuZGxlcik7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmUgdGhlIGV2ZW50IGxpc3RlbmVyIHRvIHRoZSBub2RlIGlmIGl0IGlzIGEgZ2VzdHVyZXMgZXZlbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyFFdmVudFRhcmdldH0gbm9kZSBOb2RlIHRvIHJlbW92ZSBldmVudCBsaXN0ZW5lciBmcm9tCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGV2ZW50TmFtZSBOYW1lIG9mIGV2ZW50CiAgICAgICAgICogQHBhcmFtIHtmdW5jdGlvbighRXZlbnQpOnZvaWR9IGhhbmRsZXIgTGlzdGVuZXIgZnVuY3Rpb24gdG8gcmVtb3ZlCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfcmVtb3ZlRXZlbnRMaXN0ZW5lckZyb21Ob2RlKG5vZGUsIGV2ZW50TmFtZSwgaGFuZGxlcikgewogICAgICAgICAgaWYgKCFyZW1vdmVMaXN0ZW5lcihub2RlLCBldmVudE5hbWUsIGhhbmRsZXIpKSB7CiAgICAgICAgICAgIHN1cGVyLl9yZW1vdmVFdmVudExpc3RlbmVyRnJvbU5vZGUobm9kZSwgZXZlbnROYW1lLCBoYW5kbGVyKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBHZXN0dXJlRXZlbnRMaXN0ZW5lcnM7CiAgICB9KTsKCiAgICAvKioKICAgICAqIEBmaWxlb3ZlcnZpZXcKICAgICAqIEBzdXBwcmVzcyB7Y2hlY2tQcm90b3R5cGFsVHlwZXN9CiAgICAgKiBAbGljZW5zZSBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICAgKiBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZAogICAgICogYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heQogICAgICogYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieQogICAgICogR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUAogICAgICogcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgICovCgogICAgY29uc3QgSE9TVF9ESVIgPSAvOmhvc3RcKDpkaXJcKChsdHJ8cnRsKVwpXCkvZzsKICAgIGNvbnN0IEhPU1RfRElSX1JFUExBQ01FTlQgPSAnOmhvc3QoW2Rpcj0iJDEiXSknOwoKICAgIGNvbnN0IEVMX0RJUiA9IC8oW1xzXHctI1wuXFtcXVwqXSopOmRpclwoKGx0cnxydGwpXCkvZzsKICAgIGNvbnN0IEVMX0RJUl9SRVBMQUNNRU5UID0gJzpob3N0KFtkaXI9IiQyIl0pICQxJzsKCiAgICBjb25zdCBESVJfQ0hFQ0sgPSAvOmRpclwoKD86bHRyfHJ0bClcKS87CgogICAgY29uc3QgU0hJTV9TSEFET1cgPSBCb29sZWFuKHdpbmRvd1snU2hhZHlET00nXSAmJiB3aW5kb3dbJ1NoYWR5RE9NJ11bJ2luVXNlJ10pOwoKICAgIC8qKgogICAgICogQHR5cGUgeyFBcnJheTwhUG9seW1lcl9EaXJNaXhpbj59CiAgICAgKi8KICAgIGNvbnN0IERJUl9JTlNUQU5DRVMgPSBbXTsKCiAgICAvKiogQHR5cGUgez9NdXRhdGlvbk9ic2VydmVyfSAqLwogICAgbGV0IG9ic2VydmVyID0gbnVsbDsKCiAgICBsZXQgZG9jdW1lbnREaXIgPSAnJzsKCiAgICBmdW5jdGlvbiBnZXRSVEwoKSB7CiAgICAgIGRvY3VtZW50RGlyID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LmdldEF0dHJpYnV0ZSgnZGlyJyk7CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVyX0Rpck1peGlufSBpbnN0YW5jZSBJbnN0YW5jZSB0byBzZXQgUlRMIHN0YXR1cyBvbgogICAgICovCiAgICBmdW5jdGlvbiBzZXRSVEwoaW5zdGFuY2UpIHsKICAgICAgaWYgKCFpbnN0YW5jZS5fX2F1dG9EaXJPcHRPdXQpIHsKICAgICAgICBjb25zdCBlbCA9IC8qKiBAdHlwZSB7IUhUTUxFbGVtZW50fSAqLyhpbnN0YW5jZSk7CiAgICAgICAgZWwuc2V0QXR0cmlidXRlKCdkaXInLCBkb2N1bWVudERpcik7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiB1cGRhdGVEaXJlY3Rpb24oKSB7CiAgICAgIGdldFJUTCgpOwogICAgICBkb2N1bWVudERpciA9IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5nZXRBdHRyaWJ1dGUoJ2RpcicpOwogICAgICBmb3IgKGxldCBpID0gMDsgaSA8IERJUl9JTlNUQU5DRVMubGVuZ3RoOyBpKyspIHsKICAgICAgICBzZXRSVEwoRElSX0lOU1RBTkNFU1tpXSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiB0YWtlUmVjb3JkcygpIHsKICAgICAgaWYgKG9ic2VydmVyICYmIG9ic2VydmVyLnRha2VSZWNvcmRzKCkubGVuZ3RoKSB7CiAgICAgICAgdXBkYXRlRGlyZWN0aW9uKCk7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEVsZW1lbnQgY2xhc3MgbWl4aW4gdGhhdCBhbGxvd3MgZWxlbWVudHMgdG8gdXNlIHRoZSBgOmRpcmAgQ1NTIFNlbGVjdG9yIHRvCiAgICAgKiBoYXZlIHRleHQgZGlyZWN0aW9uIHNwZWNpZmljIHN0eWxpbmcuCiAgICAgKgogICAgICogV2l0aCB0aGlzIG1peGluLCBhbnkgc3R5bGVzaGVldCBwcm92aWRlZCBpbiB0aGUgdGVtcGxhdGUgd2lsbCB0cmFuc2Zvcm0KICAgICAqIGA6ZGlyYCBpbnRvIGA6aG9zdChbZGlyXSlgIGFuZCBzeW5jIGRpcmVjdGlvbiB3aXRoIHRoZSBwYWdlIHZpYSB0aGUKICAgICAqIGVsZW1lbnQncyBgZGlyYCBhdHRyaWJ1dGUuCiAgICAgKgogICAgICogRWxlbWVudHMgY2FuIG9wdCBvdXQgb2YgdGhlIGdsb2JhbCBwYWdlIHRleHQgZGlyZWN0aW9uIGJ5IHNldHRpbmcgdGhlIGBkaXJgCiAgICAgKiBhdHRyaWJ1dGUgZGlyZWN0bHkgaW4gYHJlYWR5KClgIG9yIGluIEhUTUwuCiAgICAgKgogICAgICogQ2F2ZWF0czoKICAgICAqIC0gQXBwbGljYXRpb25zIG11c3Qgc2V0IGA8aHRtbCBkaXI9Imx0ciI+YCBvciBgPGh0bWwgZGlyPSJydGwiPmAgdG8gc3luYwogICAgICogICBkaXJlY3Rpb24KICAgICAqIC0gQXV0b21hdGljIGxlZnQtdG8tcmlnaHQgb3IgcmlnaHQtdG8tbGVmdCBzdHlsaW5nIGlzIHN5bmMnZCB3aXRoIHRoZQogICAgICogICBgPGh0bWw+YCBlbGVtZW50IG9ubHkuCiAgICAgKiAtIENoYW5naW5nIGBkaXJgIGF0IHJ1bnRpbWUgaXMgc3VwcG9ydGVkLgogICAgICogLSBPcHRpbmcgb3V0IG9mIHRoZSBnbG9iYWwgZGlyZWN0aW9uIHN0eWxpbmcgaXMgcGVybWFuZW50CiAgICAgKgogICAgICogQG1peGluRnVuY3Rpb24KICAgICAqIEBwb2x5bWVyCiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnR5QWNjZXNzb3JzCiAgICAgKiBAdGVtcGxhdGUgVAogICAgICogQHBhcmFtIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3MgQ2xhc3MgdG8gYXBwbHkgbWl4aW4gdG8uCiAgICAgKiBAcmV0dXJuIHtmdW5jdGlvbihuZXc6VCl9IHN1cGVyQ2xhc3Mgd2l0aCBtaXhpbiBhcHBsaWVkLgogICAgICovCiAgICBjb25zdCBEaXJNaXhpbiA9IGRlZHVwaW5nTWl4aW4oKGJhc2UpID0+IHsKCiAgICAgIGlmICghU0hJTV9TSEFET1cpIHsKICAgICAgICBpZiAoIW9ic2VydmVyKSB7CiAgICAgICAgICBnZXRSVEwoKTsKICAgICAgICAgIG9ic2VydmVyID0gbmV3IE11dGF0aW9uT2JzZXJ2ZXIodXBkYXRlRGlyZWN0aW9uKTsKICAgICAgICAgIG9ic2VydmVyLm9ic2VydmUoZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LCB7YXR0cmlidXRlczogdHJ1ZSwgYXR0cmlidXRlRmlsdGVyOiBbJ2RpciddfSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1Byb3BlcnR5QWNjZXNzb3JzfQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgY29uc3QgZWxlbWVudEJhc2UgPSBQcm9wZXJ0eUFjY2Vzc29ycyhiYXNlKTsKCiAgICAgIC8qKgogICAgICAgKiBAcG9seW1lcgogICAgICAgKiBAbWl4aW5DbGFzcwogICAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9EaXJNaXhpbn0KICAgICAgICovCiAgICAgIGNsYXNzIERpciBleHRlbmRzIGVsZW1lbnRCYXNlIHsKCiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGNzc1RleHQgLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBiYXNlVVJJIC4KICAgICAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IC4KICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBJbnRlcmZhY2VzIGluIGNsb3N1cmUgZG8gbm90IGluaGVyaXQgc3RhdGljcywgYnV0IGNsYXNzZXMgZG8KICAgICAgICAgKiBAbm9jb2xsYXBzZQogICAgICAgICAqLwogICAgICAgIHN0YXRpYyBfcHJvY2Vzc1N0eWxlVGV4dChjc3NUZXh0LCBiYXNlVVJJKSB7CiAgICAgICAgICAvLyBUT0RPKGh0dHBzOi8vZ2l0aHViLmNvbS9nb29nbGUvY2xvc3VyZS1jb21waWxlci9pc3N1ZXMvMzI0MCk6CiAgICAgICAgICAvLyAgICAgQ2hhbmdlIGJhY2sgdG8ganVzdCBzdXBlci5tZXRob2RDYWxsKCkKICAgICAgICAgIGNzc1RleHQgPSBlbGVtZW50QmFzZS5fcHJvY2Vzc1N0eWxlVGV4dC5jYWxsKHRoaXMsIGNzc1RleHQsIGJhc2VVUkkpOwogICAgICAgICAgaWYgKCFTSElNX1NIQURPVyAmJiBESVJfQ0hFQ0sudGVzdChjc3NUZXh0KSkgewogICAgICAgICAgICBjc3NUZXh0ID0gdGhpcy5fcmVwbGFjZURpckluQ3NzVGV4dChjc3NUZXh0KTsKICAgICAgICAgICAgdGhpcy5fX2FjdGl2YXRlRGlyID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBjc3NUZXh0OwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVwbGFjZSBgOmRpcmAgaW4gdGhlIGdpdmVuIENTUyB0ZXh0CiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGV4dCBDU1MgdGV4dCB0byByZXBsYWNlIERJUgogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gTW9kaWZpZWQgQ1NTCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgX3JlcGxhY2VEaXJJbkNzc1RleHQodGV4dCkgewogICAgICAgICAgbGV0IHJlcGxhY2VkVGV4dCA9IHRleHQ7CiAgICAgICAgICByZXBsYWNlZFRleHQgPSByZXBsYWNlZFRleHQucmVwbGFjZShIT1NUX0RJUiwgSE9TVF9ESVJfUkVQTEFDTUVOVCk7CiAgICAgICAgICByZXBsYWNlZFRleHQgPSByZXBsYWNlZFRleHQucmVwbGFjZShFTF9ESVIsIEVMX0RJUl9SRVBMQUNNRU5UKTsKICAgICAgICAgIHJldHVybiByZXBsYWNlZFRleHQ7CiAgICAgICAgfQoKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgIHN1cGVyKCk7CiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgICB0aGlzLl9fYXV0b0Rpck9wdE91dCA9IGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9IENsb3N1cmUgZG9lc24ndCB1bmRlcnN0YW5kIHRoYXQgYHRoaXNgIGlzIGFuCiAgICAgICAgICogICAgIEhUTUxFbGVtZW50CiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgICB0aGlzLl9fYXV0b0Rpck9wdE91dCA9IC8qKiBAdHlwZSB7IUhUTUxFbGVtZW50fSAqLyh0aGlzKS5oYXNBdHRyaWJ1dGUoJ2RpcicpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30gSWYgaXQgZXhpc3RzIG9uIGVsZW1lbnRCYXNlLCBpdCBjYW4gYmUKICAgICAgICAgKiAgIHN1cGVyJ2QKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICAgaWYgKGVsZW1lbnRCYXNlLnByb3RvdHlwZS5jb25uZWN0ZWRDYWxsYmFjaykgewogICAgICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHRoaXMuY29uc3RydWN0b3IuX19hY3RpdmF0ZURpcikgewogICAgICAgICAgICB0YWtlUmVjb3JkcygpOwogICAgICAgICAgICBESVJfSU5TVEFOQ0VTLnB1c2godGhpcyk7CiAgICAgICAgICAgIHNldFJUTCh0aGlzKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBzdXBwcmVzcyB7bWlzc2luZ1Byb3BlcnRpZXN9IElmIGl0IGV4aXN0cyBvbiBlbGVtZW50QmFzZSwgaXQgY2FuIGJlCiAgICAgICAgICogICBzdXBlcidkCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBkaXNjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICAgIGlmIChlbGVtZW50QmFzZS5wcm90b3R5cGUuZGlzY29ubmVjdGVkQ2FsbGJhY2spIHsKICAgICAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh0aGlzLmNvbnN0cnVjdG9yLl9fYWN0aXZhdGVEaXIpIHsKICAgICAgICAgICAgY29uc3QgaWR4ID0gRElSX0lOU1RBTkNFUy5pbmRleE9mKHRoaXMpOwogICAgICAgICAgICBpZiAoaWR4ID4gLTEpIHsKICAgICAgICAgICAgICBESVJfSU5TVEFOQ0VTLnNwbGljZShpZHgsIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBEaXIuX19hY3RpdmF0ZURpciA9IGZhbHNlOwoKICAgICAgcmV0dXJuIERpcjsKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgbGV0IHNjaGVkdWxlZCA9IGZhbHNlOwogICAgbGV0IGJlZm9yZVJlbmRlclF1ZXVlID0gW107CiAgICBsZXQgYWZ0ZXJSZW5kZXJRdWV1ZSA9IFtdOwoKICAgIGZ1bmN0aW9uIHNjaGVkdWxlKCkgewogICAgICBzY2hlZHVsZWQgPSB0cnVlOwogICAgICAvLyBiZWZvcmUgbmV4dCByZW5kZXIKICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKGZ1bmN0aW9uKCkgewogICAgICAgIHNjaGVkdWxlZCA9IGZhbHNlOwogICAgICAgIGZsdXNoUXVldWUoYmVmb3JlUmVuZGVyUXVldWUpOwogICAgICAgIC8vIGFmdGVyIHRoZSByZW5kZXIKICAgICAgICBzZXRUaW1lb3V0KGZ1bmN0aW9uKCkgewogICAgICAgICAgcnVuUXVldWUoYWZ0ZXJSZW5kZXJRdWV1ZSk7CiAgICAgICAgfSk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGZsdXNoUXVldWUocXVldWUpIHsKICAgICAgd2hpbGUgKHF1ZXVlLmxlbmd0aCkgewogICAgICAgIGNhbGxNZXRob2QocXVldWUuc2hpZnQoKSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBydW5RdWV1ZShxdWV1ZSkgewogICAgICBmb3IgKGxldCBpPTAsIGw9cXVldWUubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgY2FsbE1ldGhvZChxdWV1ZS5zaGlmdCgpKTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGNhbGxNZXRob2QoaW5mbykgewogICAgICBjb25zdCBjb250ZXh0ID0gaW5mb1swXTsKICAgICAgY29uc3QgY2FsbGJhY2sgPSBpbmZvWzFdOwogICAgICBjb25zdCBhcmdzID0gaW5mb1syXTsKICAgICAgdHJ5IHsKICAgICAgICBjYWxsYmFjay5hcHBseShjb250ZXh0LCBhcmdzKTsKICAgICAgfSBjYXRjaChlKSB7CiAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7CiAgICAgICAgICB0aHJvdyBlOwogICAgICAgIH0pOwogICAgICB9CiAgICB9CgoKICAgIC8qKgogICAgICogRW5xdWV1ZXMgYSBjYWxsYmFjayB3aGljaCB3aWxsIGJlIHJ1biBiZWZvcmUgdGhlIG5leHQgcmVuZGVyLCBhdAogICAgICogYHJlcXVlc3RBbmltYXRpb25GcmFtZWAgdGltaW5nLgogICAgICoKICAgICAqIFRoaXMgbWV0aG9kIGlzIHVzZWZ1bCBmb3IgZW5xdWV1aW5nIHdvcmsgdGhhdCByZXF1aXJlcyBET00gbWVhc3VyZW1lbnQsCiAgICAgKiBzaW5jZSBtZWFzdXJlbWVudCBtYXkgbm90IGJlIHJlbGlhYmxlIGluIGN1c3RvbSBlbGVtZW50IGNhbGxiYWNrcyBiZWZvcmUKICAgICAqIHRoZSBmaXJzdCByZW5kZXIsIGFzIHdlbGwgYXMgZm9yIGJhdGNoaW5nIG1lYXN1cmVtZW50IHRhc2tzIGluIGdlbmVyYWwuCiAgICAgKgogICAgICogVGFza3MgaW4gdGhpcyBxdWV1ZSBtYXkgYmUgZmx1c2hlZCBieSBjYWxsaW5nIGBmbHVzaCgpYC4KICAgICAqCiAgICAgKiBAcGFyYW0geyp9IGNvbnRleHQgQ29udGV4dCBvYmplY3QgdGhlIGNhbGxiYWNrIGZ1bmN0aW9uIHdpbGwgYmUgYm91bmQgdG8KICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oLi4uKik6dm9pZH0gY2FsbGJhY2sgQ2FsbGJhY2sgZnVuY3Rpb24KICAgICAqIEBwYXJhbSB7IUFycmF5PX0gYXJncyBBbiBhcnJheSBvZiBhcmd1bWVudHMgdG8gY2FsbCB0aGUgY2FsbGJhY2sgZnVuY3Rpb24gd2l0aAogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gYmVmb3JlTmV4dFJlbmRlcihjb250ZXh0LCBjYWxsYmFjaywgYXJncykgewogICAgICBpZiAoIXNjaGVkdWxlZCkgewogICAgICAgIHNjaGVkdWxlKCk7CiAgICAgIH0KICAgICAgYmVmb3JlUmVuZGVyUXVldWUucHVzaChbY29udGV4dCwgY2FsbGJhY2ssIGFyZ3NdKTsKICAgIH0KCiAgICAvKioKICAgICAqIEVucXVldWVzIGEgY2FsbGJhY2sgd2hpY2ggd2lsbCBiZSBydW4gYWZ0ZXIgdGhlIG5leHQgcmVuZGVyLCBlcXVpdmFsZW50CiAgICAgKiB0byBvbmUgdGFzayAoYHNldFRpbWVvdXRgKSBhZnRlciB0aGUgbmV4dCBgcmVxdWVzdEFuaW1hdGlvbkZyYW1lYC4KICAgICAqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyB1c2VmdWwgZm9yIHR1bmluZyB0aGUgZmlyc3QtcmVuZGVyIHBlcmZvcm1hbmNlIG9mIGFuCiAgICAgKiBlbGVtZW50IG9yIGFwcGxpY2F0aW9uIGJ5IGRlZmVycmluZyBub24tY3JpdGljYWwgd29yayB1bnRpbCBhZnRlciB0aGUKICAgICAqIGZpcnN0IHBhaW50LiAgVHlwaWNhbCBub24tcmVuZGVyLWNyaXRpY2FsIHdvcmsgbWF5IGluY2x1ZGUgYWRkaW5nIFVJCiAgICAgKiBldmVudCBsaXN0ZW5lcnMgYW5kIGFyaWEgYXR0cmlidXRlcy4KICAgICAqCiAgICAgKiBAcGFyYW0geyp9IGNvbnRleHQgQ29udGV4dCBvYmplY3QgdGhlIGNhbGxiYWNrIGZ1bmN0aW9uIHdpbGwgYmUgYm91bmQgdG8KICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oLi4uKik6dm9pZH0gY2FsbGJhY2sgQ2FsbGJhY2sgZnVuY3Rpb24KICAgICAqIEBwYXJhbSB7IUFycmF5PX0gYXJncyBBbiBhcnJheSBvZiBhcmd1bWVudHMgdG8gY2FsbCB0aGUgY2FsbGJhY2sgZnVuY3Rpb24gd2l0aAogICAgICogQHJldHVybiB7dm9pZH0KICAgICAqLwogICAgZnVuY3Rpb24gYWZ0ZXJOZXh0UmVuZGVyKGNvbnRleHQsIGNhbGxiYWNrLCBhcmdzKSB7CiAgICAgIGlmICghc2NoZWR1bGVkKSB7CiAgICAgICAgc2NoZWR1bGUoKTsKICAgICAgfQogICAgICBhZnRlclJlbmRlclF1ZXVlLnB1c2goW2NvbnRleHQsIGNhbGxiYWNrLCBhcmdzXSk7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBmdW5jdGlvbiByZXNvbHZlKCkgewogICAgICBkb2N1bWVudC5ib2R5LnJlbW92ZUF0dHJpYnV0ZSgndW5yZXNvbHZlZCcpOwogICAgfQoKICAgIGlmIChkb2N1bWVudC5yZWFkeVN0YXRlID09PSAnaW50ZXJhY3RpdmUnIHx8IGRvY3VtZW50LnJlYWR5U3RhdGUgPT09ICdjb21wbGV0ZScpIHsKICAgICAgcmVzb2x2ZSgpOwogICAgfSBlbHNlIHsKICAgICAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ0RPTUNvbnRlbnRMb2FkZWQnLCByZXNvbHZlKTsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGZ1bmN0aW9uIG5ld1NwbGljZShpbmRleCwgcmVtb3ZlZCwgYWRkZWRDb3VudCkgewogICAgICByZXR1cm4gewogICAgICAgIGluZGV4OiBpbmRleCwKICAgICAgICByZW1vdmVkOiByZW1vdmVkLAogICAgICAgIGFkZGVkQ291bnQ6IGFkZGVkQ291bnQKICAgICAgfTsKICAgIH0KCiAgICBjb25zdCBFRElUX0xFQVZFID0gMDsKICAgIGNvbnN0IEVESVRfVVBEQVRFID0gMTsKICAgIGNvbnN0IEVESVRfQUREID0gMjsKICAgIGNvbnN0IEVESVRfREVMRVRFID0gMzsKCiAgICAvLyBOb3RlOiBUaGlzIGZ1bmN0aW9uIGlzICpiYXNlZCogb24gdGhlIGNvbXB1dGF0aW9uIG9mIHRoZSBMZXZlbnNodGVpbgogICAgLy8gImVkaXQiIGRpc3RhbmNlLiBUaGUgb25lIGNoYW5nZSBpcyB0aGF0ICJ1cGRhdGVzIiBhcmUgdHJlYXRlZCBhcyB0d28KICAgIC8vIGVkaXRzIC0gbm90IG9uZS4gV2l0aCBBcnJheSBzcGxpY2VzLCBhbiB1cGRhdGUgaXMgcmVhbGx5IGEgZGVsZXRlCiAgICAvLyBmb2xsb3dlZCBieSBhbiBhZGQuIEJ5IHJldGFpbmluZyB0aGlzLCB3ZSBvcHRpbWl6ZSBmb3IgImtlZXBpbmciIHRoZQogICAgLy8gbWF4aW11bSBhcnJheSBpdGVtcyBpbiB0aGUgb3JpZ2luYWwgYXJyYXkuIEZvciBleGFtcGxlOgogICAgLy8KICAgIC8vICAgJ3h4eHgxMjMnIC0+ICcxMjN5eXl5JwogICAgLy8KICAgIC8vIFdpdGggMS1lZGl0IHVwZGF0ZXMsIHRoZSBzaG9ydGVzdCBwYXRoIHdvdWxkIGJlIGp1c3QgdG8gdXBkYXRlIGFsbCBzZXZlbgogICAgLy8gY2hhcmFjdGVycy4gV2l0aCAyLWVkaXQgdXBkYXRlcywgd2UgZGVsZXRlIDQsIGxlYXZlIDMsIGFuZCBhZGQgNC4gVGhpcwogICAgLy8gbGVhdmVzIHRoZSBzdWJzdHJpbmcgJzEyMycgaW50YWN0LgogICAgZnVuY3Rpb24gY2FsY0VkaXREaXN0YW5jZXMoY3VycmVudCwgY3VycmVudFN0YXJ0LCBjdXJyZW50RW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9sZCwgb2xkU3RhcnQsIG9sZEVuZCkgewogICAgICAvLyAiRGVsZXRpb24iIGNvbHVtbnMKICAgICAgbGV0IHJvd0NvdW50ID0gb2xkRW5kIC0gb2xkU3RhcnQgKyAxOwogICAgICBsZXQgY29sdW1uQ291bnQgPSBjdXJyZW50RW5kIC0gY3VycmVudFN0YXJ0ICsgMTsKICAgICAgbGV0IGRpc3RhbmNlcyA9IG5ldyBBcnJheShyb3dDb3VudCk7CgogICAgICAvLyAiQWRkaXRpb24iIHJvd3MuIEluaXRpYWxpemUgbnVsbCBjb2x1bW4uCiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcm93Q291bnQ7IGkrKykgewogICAgICAgIGRpc3RhbmNlc1tpXSA9IG5ldyBBcnJheShjb2x1bW5Db3VudCk7CiAgICAgICAgZGlzdGFuY2VzW2ldWzBdID0gaTsKICAgICAgfQoKICAgICAgLy8gSW5pdGlhbGl6ZSBudWxsIHJvdwogICAgICBmb3IgKGxldCBqID0gMDsgaiA8IGNvbHVtbkNvdW50OyBqKyspCiAgICAgICAgZGlzdGFuY2VzWzBdW2pdID0gajsKCiAgICAgIGZvciAobGV0IGkgPSAxOyBpIDwgcm93Q291bnQ7IGkrKykgewogICAgICAgIGZvciAobGV0IGogPSAxOyBqIDwgY29sdW1uQ291bnQ7IGorKykgewogICAgICAgICAgaWYgKGVxdWFscyhjdXJyZW50W2N1cnJlbnRTdGFydCArIGogLSAxXSwgb2xkW29sZFN0YXJ0ICsgaSAtIDFdKSkKICAgICAgICAgICAgZGlzdGFuY2VzW2ldW2pdID0gZGlzdGFuY2VzW2kgLSAxXVtqIC0gMV07CiAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgbGV0IG5vcnRoID0gZGlzdGFuY2VzW2kgLSAxXVtqXSArIDE7CiAgICAgICAgICAgIGxldCB3ZXN0ID0gZGlzdGFuY2VzW2ldW2ogLSAxXSArIDE7CiAgICAgICAgICAgIGRpc3RhbmNlc1tpXVtqXSA9IG5vcnRoIDwgd2VzdCA/IG5vcnRoIDogd2VzdDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBkaXN0YW5jZXM7CiAgICB9CgogICAgLy8gVGhpcyBzdGFydHMgYXQgdGhlIGZpbmFsIHdlaWdodCwgYW5kIHdhbGtzICJiYWNrd2FyZCIgYnkgZmluZGluZwogICAgLy8gdGhlIG1pbmltdW0gcHJldmlvdXMgd2VpZ2h0IHJlY3Vyc2l2ZWx5IHVudGlsIHRoZSBvcmlnaW4gb2YgdGhlIHdlaWdodAogICAgLy8gbWF0cml4LgogICAgZnVuY3Rpb24gc3BsaWNlT3BlcmF0aW9uc0Zyb21FZGl0RGlzdGFuY2VzKGRpc3RhbmNlcykgewogICAgICBsZXQgaSA9IGRpc3RhbmNlcy5sZW5ndGggLSAxOwogICAgICBsZXQgaiA9IGRpc3RhbmNlc1swXS5sZW5ndGggLSAxOwogICAgICBsZXQgY3VycmVudCA9IGRpc3RhbmNlc1tpXVtqXTsKICAgICAgbGV0IGVkaXRzID0gW107CiAgICAgIHdoaWxlIChpID4gMCB8fCBqID4gMCkgewogICAgICAgIGlmIChpID09IDApIHsKICAgICAgICAgIGVkaXRzLnB1c2goRURJVF9BREQpOwogICAgICAgICAgai0tOwogICAgICAgICAgY29udGludWU7CiAgICAgICAgfQogICAgICAgIGlmIChqID09IDApIHsKICAgICAgICAgIGVkaXRzLnB1c2goRURJVF9ERUxFVEUpOwogICAgICAgICAgaS0tOwogICAgICAgICAgY29udGludWU7CiAgICAgICAgfQogICAgICAgIGxldCBub3J0aFdlc3QgPSBkaXN0YW5jZXNbaSAtIDFdW2ogLSAxXTsKICAgICAgICBsZXQgd2VzdCA9IGRpc3RhbmNlc1tpIC0gMV1bal07CiAgICAgICAgbGV0IG5vcnRoID0gZGlzdGFuY2VzW2ldW2ogLSAxXTsKCiAgICAgICAgbGV0IG1pbjsKICAgICAgICBpZiAod2VzdCA8IG5vcnRoKQogICAgICAgICAgbWluID0gd2VzdCA8IG5vcnRoV2VzdCA/IHdlc3QgOiBub3J0aFdlc3Q7CiAgICAgICAgZWxzZQogICAgICAgICAgbWluID0gbm9ydGggPCBub3J0aFdlc3QgPyBub3J0aCA6IG5vcnRoV2VzdDsKCiAgICAgICAgaWYgKG1pbiA9PSBub3J0aFdlc3QpIHsKICAgICAgICAgIGlmIChub3J0aFdlc3QgPT0gY3VycmVudCkgewogICAgICAgICAgICBlZGl0cy5wdXNoKEVESVRfTEVBVkUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgZWRpdHMucHVzaChFRElUX1VQREFURSk7CiAgICAgICAgICAgIGN1cnJlbnQgPSBub3J0aFdlc3Q7CiAgICAgICAgICB9CiAgICAgICAgICBpLS07CiAgICAgICAgICBqLS07CiAgICAgICAgfSBlbHNlIGlmIChtaW4gPT0gd2VzdCkgewogICAgICAgICAgZWRpdHMucHVzaChFRElUX0RFTEVURSk7CiAgICAgICAgICBpLS07CiAgICAgICAgICBjdXJyZW50ID0gd2VzdDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZWRpdHMucHVzaChFRElUX0FERCk7CiAgICAgICAgICBqLS07CiAgICAgICAgICBjdXJyZW50ID0gbm9ydGg7CiAgICAgICAgfQogICAgICB9CgogICAgICBlZGl0cy5yZXZlcnNlKCk7CiAgICAgIHJldHVybiBlZGl0czsKICAgIH0KCiAgICAvKioKICAgICAqIFNwbGljZSBQcm9qZWN0aW9uIGZ1bmN0aW9uczoKICAgICAqCiAgICAgKiBBIHNwbGljZSBtYXAgaXMgYSByZXByZXNlbnRhdGlvbiBvZiBob3cgYSBwcmV2aW91cyBhcnJheSBvZiBpdGVtcwogICAgICogd2FzIHRyYW5zZm9ybWVkIGludG8gYSBuZXcgYXJyYXkgb2YgaXRlbXMuIENvbmNlcHR1YWxseSBpdCBpcyBhIGxpc3Qgb2YKICAgICAqIHR1cGxlcyBvZgogICAgICoKICAgICAqICAgPGluZGV4LCByZW1vdmVkLCBhZGRlZENvdW50PgogICAgICoKICAgICAqIHdoaWNoIGFyZSBrZXB0IGluIGFzY2VuZGluZyBpbmRleCBvcmRlciBvZi4gVGhlIHR1cGxlIHJlcHJlc2VudHMgdGhhdCBhdAogICAgICogdGhlIHxpbmRleHwsIHxyZW1vdmVkfCBzZXF1ZW5jZSBvZiBpdGVtcyB3ZXJlIHJlbW92ZWQsIGFuZCBjb3VudGluZyBmb3J3YXJkCiAgICAgKiBmcm9tIHxpbmRleHwsIHxhZGRlZENvdW50fCBpdGVtcyB3ZXJlIGFkZGVkLgogICAgICovCgogICAgLyoqCiAgICAgKiBMYWNraW5nIGluZGl2aWR1YWwgc3BsaWNlIG11dGF0aW9uIGluZm9ybWF0aW9uLCB0aGUgbWluaW1hbCBzZXQgb2YKICAgICAqIHNwbGljZXMgY2FuIGJlIHN5bnRoZXNpemVkIGdpdmVuIHRoZSBwcmV2aW91cyBzdGF0ZSBhbmQgZmluYWwgc3RhdGUgb2YgYW4KICAgICAqIGFycmF5LiBUaGUgYmFzaWMgYXBwcm9hY2ggaXMgdG8gY2FsY3VsYXRlIHRoZSBlZGl0IGRpc3RhbmNlIG1hdHJpeCBhbmQKICAgICAqIGNob29zZSB0aGUgc2hvcnRlc3QgcGF0aCB0aHJvdWdoIGl0LgogICAgICoKICAgICAqIENvbXBsZXhpdHk6IE8obCAqIHApCiAgICAgKiAgIGw6IFRoZSBsZW5ndGggb2YgdGhlIGN1cnJlbnQgYXJyYXkKICAgICAqICAgcDogVGhlIGxlbmd0aCBvZiB0aGUgb2xkIGFycmF5CiAgICAgKgogICAgICogQHBhcmFtIHshQXJyYXl9IGN1cnJlbnQgVGhlIGN1cnJlbnQgImNoYW5nZWQiIGFycmF5IGZvciB3aGljaCB0bwogICAgICogY2FsY3VsYXRlIHNwbGljZXMuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gY3VycmVudFN0YXJ0IFN0YXJ0aW5nIGluZGV4IGluIHRoZSBgY3VycmVudGAgYXJyYXkgZm9yCiAgICAgKiB3aGljaCBzcGxpY2VzIGFyZSBjYWxjdWxhdGVkLgogICAgICogQHBhcmFtIHtudW1iZXJ9IGN1cnJlbnRFbmQgRW5kaW5nIGluZGV4IGluIHRoZSBgY3VycmVudGAgYXJyYXkgZm9yCiAgICAgKiB3aGljaCBzcGxpY2VzIGFyZSBjYWxjdWxhdGVkLgogICAgICogQHBhcmFtIHshQXJyYXl9IG9sZCBUaGUgb3JpZ2luYWwgInVuY2hhbmdlZCIgYXJyYXkgdG8gY29tcGFyZSBgY3VycmVudGAKICAgICAqIGFnYWluc3QgdG8gZGV0ZXJtaW5lIHNwbGljZXMuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gb2xkU3RhcnQgU3RhcnRpbmcgaW5kZXggaW4gdGhlIGBvbGRgIGFycmF5IGZvcgogICAgICogd2hpY2ggc3BsaWNlcyBhcmUgY2FsY3VsYXRlZC4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBvbGRFbmQgRW5kaW5nIGluZGV4IGluIHRoZSBgb2xkYCBhcnJheSBmb3IKICAgICAqIHdoaWNoIHNwbGljZXMgYXJlIGNhbGN1bGF0ZWQuCiAgICAgKiBAcmV0dXJuIHshQXJyYXl9IFJldHVybnMgYW4gYXJyYXkgb2Ygc3BsaWNlIHJlY29yZCBvYmplY3RzLiBFYWNoIG9mIHRoZXNlCiAgICAgKiBjb250YWluczogYGluZGV4YCB0aGUgbG9jYXRpb24gd2hlcmUgdGhlIHNwbGljZSBvY2N1cnJlZDsgYHJlbW92ZWRgCiAgICAgKiB0aGUgYXJyYXkgb2YgcmVtb3ZlZCBpdGVtcyBmcm9tIHRoaXMgbG9jYXRpb247IGBhZGRlZENvdW50YCB0aGUgbnVtYmVyCiAgICAgKiBvZiBpdGVtcyBhZGRlZCBhdCB0aGlzIGxvY2F0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjYWxjU3BsaWNlcyhjdXJyZW50LCBjdXJyZW50U3RhcnQsIGN1cnJlbnRFbmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgb2xkLCBvbGRTdGFydCwgb2xkRW5kKSB7CiAgICAgIGxldCBwcmVmaXhDb3VudCA9IDA7CiAgICAgIGxldCBzdWZmaXhDb3VudCA9IDA7CiAgICAgIGxldCBzcGxpY2U7CgogICAgICBsZXQgbWluTGVuZ3RoID0gTWF0aC5taW4oY3VycmVudEVuZCAtIGN1cnJlbnRTdGFydCwgb2xkRW5kIC0gb2xkU3RhcnQpOwogICAgICBpZiAoY3VycmVudFN0YXJ0ID09IDAgJiYgb2xkU3RhcnQgPT0gMCkKICAgICAgICBwcmVmaXhDb3VudCA9IHNoYXJlZFByZWZpeChjdXJyZW50LCBvbGQsIG1pbkxlbmd0aCk7CgogICAgICBpZiAoY3VycmVudEVuZCA9PSBjdXJyZW50Lmxlbmd0aCAmJiBvbGRFbmQgPT0gb2xkLmxlbmd0aCkKICAgICAgICBzdWZmaXhDb3VudCA9IHNoYXJlZFN1ZmZpeChjdXJyZW50LCBvbGQsIG1pbkxlbmd0aCAtIHByZWZpeENvdW50KTsKCiAgICAgIGN1cnJlbnRTdGFydCArPSBwcmVmaXhDb3VudDsKICAgICAgb2xkU3RhcnQgKz0gcHJlZml4Q291bnQ7CiAgICAgIGN1cnJlbnRFbmQgLT0gc3VmZml4Q291bnQ7CiAgICAgIG9sZEVuZCAtPSBzdWZmaXhDb3VudDsKCiAgICAgIGlmIChjdXJyZW50RW5kIC0gY3VycmVudFN0YXJ0ID09IDAgJiYgb2xkRW5kIC0gb2xkU3RhcnQgPT0gMCkKICAgICAgICByZXR1cm4gW107CgogICAgICBpZiAoY3VycmVudFN0YXJ0ID09IGN1cnJlbnRFbmQpIHsKICAgICAgICBzcGxpY2UgPSBuZXdTcGxpY2UoY3VycmVudFN0YXJ0LCBbXSwgMCk7CiAgICAgICAgd2hpbGUgKG9sZFN0YXJ0IDwgb2xkRW5kKQogICAgICAgICAgc3BsaWNlLnJlbW92ZWQucHVzaChvbGRbb2xkU3RhcnQrK10pOwoKICAgICAgICByZXR1cm4gWyBzcGxpY2UgXTsKICAgICAgfSBlbHNlIGlmIChvbGRTdGFydCA9PSBvbGRFbmQpCiAgICAgICAgcmV0dXJuIFsgbmV3U3BsaWNlKGN1cnJlbnRTdGFydCwgW10sIGN1cnJlbnRFbmQgLSBjdXJyZW50U3RhcnQpIF07CgogICAgICBsZXQgb3BzID0gc3BsaWNlT3BlcmF0aW9uc0Zyb21FZGl0RGlzdGFuY2VzKAogICAgICAgICAgY2FsY0VkaXREaXN0YW5jZXMoY3VycmVudCwgY3VycmVudFN0YXJ0LCBjdXJyZW50RW5kLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvbGQsIG9sZFN0YXJ0LCBvbGRFbmQpKTsKCiAgICAgIHNwbGljZSA9IHVuZGVmaW5lZDsKICAgICAgbGV0IHNwbGljZXMgPSBbXTsKICAgICAgbGV0IGluZGV4ID0gY3VycmVudFN0YXJ0OwogICAgICBsZXQgb2xkSW5kZXggPSBvbGRTdGFydDsKICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBvcHMubGVuZ3RoOyBpKyspIHsKICAgICAgICBzd2l0Y2gob3BzW2ldKSB7CiAgICAgICAgICBjYXNlIEVESVRfTEVBVkU6CiAgICAgICAgICAgIGlmIChzcGxpY2UpIHsKICAgICAgICAgICAgICBzcGxpY2VzLnB1c2goc3BsaWNlKTsKICAgICAgICAgICAgICBzcGxpY2UgPSB1bmRlZmluZWQ7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIGluZGV4Kys7CiAgICAgICAgICAgIG9sZEluZGV4Kys7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSBFRElUX1VQREFURToKICAgICAgICAgICAgaWYgKCFzcGxpY2UpCiAgICAgICAgICAgICAgc3BsaWNlID0gbmV3U3BsaWNlKGluZGV4LCBbXSwgMCk7CgogICAgICAgICAgICBzcGxpY2UuYWRkZWRDb3VudCsrOwogICAgICAgICAgICBpbmRleCsrOwoKICAgICAgICAgICAgc3BsaWNlLnJlbW92ZWQucHVzaChvbGRbb2xkSW5kZXhdKTsKICAgICAgICAgICAgb2xkSW5kZXgrKzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlIEVESVRfQUREOgogICAgICAgICAgICBpZiAoIXNwbGljZSkKICAgICAgICAgICAgICBzcGxpY2UgPSBuZXdTcGxpY2UoaW5kZXgsIFtdLCAwKTsKCiAgICAgICAgICAgIHNwbGljZS5hZGRlZENvdW50Kys7CiAgICAgICAgICAgIGluZGV4Kys7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSBFRElUX0RFTEVURToKICAgICAgICAgICAgaWYgKCFzcGxpY2UpCiAgICAgICAgICAgICAgc3BsaWNlID0gbmV3U3BsaWNlKGluZGV4LCBbXSwgMCk7CgogICAgICAgICAgICBzcGxpY2UucmVtb3ZlZC5wdXNoKG9sZFtvbGRJbmRleF0pOwogICAgICAgICAgICBvbGRJbmRleCsrOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGlmIChzcGxpY2UpIHsKICAgICAgICBzcGxpY2VzLnB1c2goc3BsaWNlKTsKICAgICAgfQogICAgICByZXR1cm4gc3BsaWNlczsKICAgIH0KCiAgICBmdW5jdGlvbiBzaGFyZWRQcmVmaXgoY3VycmVudCwgb2xkLCBzZWFyY2hMZW5ndGgpIHsKICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBzZWFyY2hMZW5ndGg7IGkrKykKICAgICAgICBpZiAoIWVxdWFscyhjdXJyZW50W2ldLCBvbGRbaV0pKQogICAgICAgICAgcmV0dXJuIGk7CiAgICAgIHJldHVybiBzZWFyY2hMZW5ndGg7CiAgICB9CgogICAgZnVuY3Rpb24gc2hhcmVkU3VmZml4KGN1cnJlbnQsIG9sZCwgc2VhcmNoTGVuZ3RoKSB7CiAgICAgIGxldCBpbmRleDEgPSBjdXJyZW50Lmxlbmd0aDsKICAgICAgbGV0IGluZGV4MiA9IG9sZC5sZW5ndGg7CiAgICAgIGxldCBjb3VudCA9IDA7CiAgICAgIHdoaWxlIChjb3VudCA8IHNlYXJjaExlbmd0aCAmJiBlcXVhbHMoY3VycmVudFstLWluZGV4MV0sIG9sZFstLWluZGV4Ml0pKQogICAgICAgIGNvdW50Kys7CgogICAgICByZXR1cm4gY291bnQ7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZXR1cm5zIGFuIGFycmF5IG9mIHNwbGljZSByZWNvcmRzIGluZGljYXRpbmcgdGhlIG1pbmltdW0gZWRpdHMgcmVxdWlyZWQKICAgICAqIHRvIHRyYW5zZm9ybSB0aGUgYHByZXZpb3VzYCBhcnJheSBpbnRvIHRoZSBgY3VycmVudGAgYXJyYXkuCiAgICAgKgogICAgICogU3BsaWNlIHJlY29yZHMgYXJlIG9yZGVyZWQgYnkgaW5kZXggYW5kIGNvbnRhaW4gdGhlIGZvbGxvd2luZyBmaWVsZHM6CiAgICAgKiAtIGBpbmRleGA6IGluZGV4IHdoZXJlIGVkaXQgc3RhcnRlZAogICAgICogLSBgcmVtb3ZlZGA6IGFycmF5IG9mIHJlbW92ZWQgaXRlbXMgZnJvbSB0aGlzIGluZGV4CiAgICAgKiAtIGBhZGRlZENvdW50YDogbnVtYmVyIG9mIGl0ZW1zIGFkZGVkIGF0IHRoaXMgaW5kZXgKICAgICAqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGJhc2VkIG9uIHRoZSBMZXZlbnNodGVpbiAibWluaW11bSBlZGl0IGRpc3RhbmNlIgogICAgICogYWxnb3JpdGhtLiBOb3RlIHRoYXQgdXBkYXRlcyBhcmUgdHJlYXRlZCBhcyByZW1vdmFsIGZvbGxvd2VkIGJ5IGFkZGl0aW9uLgogICAgICoKICAgICAqIFRoZSB3b3JzdC1jYXNlIHRpbWUgY29tcGxleGl0eSBvZiB0aGlzIGFsZ29yaXRobSBpcyBgTyhsICogcClgCiAgICAgKiAgIGw6IFRoZSBsZW5ndGggb2YgdGhlIGN1cnJlbnQgYXJyYXkKICAgICAqICAgcDogVGhlIGxlbmd0aCBvZiB0aGUgcHJldmlvdXMgYXJyYXkKICAgICAqCiAgICAgKiBIb3dldmVyLCB0aGUgd29yc3QtY2FzZSBjb21wbGV4aXR5IGlzIHJlZHVjZWQgYnkgYW4gYE8obilgIG9wdGltaXphdGlvbgogICAgICogdG8gZGV0ZWN0IGFueSBzaGFyZWQgcHJlZml4ICYgc3VmZml4IGJldHdlZW4gdGhlIHR3byBhcnJheXMgYW5kIG9ubHkKICAgICAqIHBlcmZvcm0gdGhlIG1vcmUgZXhwZW5zaXZlIG1pbmltdW0gZWRpdCBkaXN0YW5jZSBjYWxjdWxhdGlvbiBvdmVyIHRoZQogICAgICogbm9uLXNoYXJlZCBwb3J0aW9ucyBvZiB0aGUgYXJyYXlzLgogICAgICoKICAgICAqIEBmdW5jdGlvbgogICAgICogQHBhcmFtIHshQXJyYXl9IGN1cnJlbnQgVGhlICJjaGFuZ2VkIiBhcnJheSBmb3Igd2hpY2ggc3BsaWNlcyB3aWxsIGJlCiAgICAgKiBjYWxjdWxhdGVkLgogICAgICogQHBhcmFtIHshQXJyYXl9IHByZXZpb3VzIFRoZSAidW5jaGFuZ2VkIiBvcmlnaW5hbCBhcnJheSB0byBjb21wYXJlCiAgICAgKiBgY3VycmVudGAgYWdhaW5zdCB0byBkZXRlcm1pbmUgdGhlIHNwbGljZXMuCiAgICAgKiBAcmV0dXJuIHshQXJyYXl9IFJldHVybnMgYW4gYXJyYXkgb2Ygc3BsaWNlIHJlY29yZCBvYmplY3RzLiBFYWNoIG9mIHRoZXNlCiAgICAgKiBjb250YWluczogYGluZGV4YCB0aGUgbG9jYXRpb24gd2hlcmUgdGhlIHNwbGljZSBvY2N1cnJlZDsgYHJlbW92ZWRgCiAgICAgKiB0aGUgYXJyYXkgb2YgcmVtb3ZlZCBpdGVtcyBmcm9tIHRoaXMgbG9jYXRpb247IGBhZGRlZENvdW50YCB0aGUgbnVtYmVyCiAgICAgKiBvZiBpdGVtcyBhZGRlZCBhdCB0aGlzIGxvY2F0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjYWxjdWxhdGVTcGxpY2VzKGN1cnJlbnQsIHByZXZpb3VzKSB7CiAgICAgIHJldHVybiBjYWxjU3BsaWNlcyhjdXJyZW50LCAwLCBjdXJyZW50Lmxlbmd0aCwgcHJldmlvdXMsIDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHByZXZpb3VzLmxlbmd0aCk7CiAgICB9CgogICAgZnVuY3Rpb24gZXF1YWxzKGN1cnJlbnRWYWx1ZSwgcHJldmlvdXNWYWx1ZSkgewogICAgICByZXR1cm4gY3VycmVudFZhbHVlID09PSBwcmV2aW91c1ZhbHVlOwogICAgfQoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRydWUgaWYgYG5vZGVgIGlzIGEgc2xvdCBlbGVtZW50CiAgICAgKiBAcGFyYW0geyFOb2RlfSBub2RlIE5vZGUgdG8gdGVzdC4KICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFJldHVybnMgdHJ1ZSBpZiB0aGUgZ2l2ZW4gYG5vZGVgIGlzIGEgc2xvdAogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gaXNTbG90KG5vZGUpIHsKICAgICAgcmV0dXJuIChub2RlLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnKTsKICAgIH0KCiAgICAvKioKICAgICAqIENsYXNzIHRoYXQgbGlzdGVucyBmb3IgY2hhbmdlcyAoYWRkaXRpb25zIG9yIHJlbW92YWxzKSB0bwogICAgICogImZsYXR0ZW5lZCBub2RlcyIgb24gYSBnaXZlbiBgbm9kZWAuIFRoZSBsaXN0IG9mIGZsYXR0ZW5lZCBub2RlcyBjb25zaXN0cwogICAgICogb2YgYSBub2RlJ3MgY2hpbGRyZW4gYW5kLCBmb3IgYW55IGNoaWxkcmVuIHRoYXQgYXJlIGA8c2xvdD5gIGVsZW1lbnRzLAogICAgICogdGhlIGV4cGFuZGVkIGZsYXR0ZW5lZCBsaXN0IG9mIGBhc3NpZ25lZE5vZGVzYC4KICAgICAqIEZvciBleGFtcGxlLCBpZiB0aGUgb2JzZXJ2ZWQgbm9kZSBoYXMgY2hpbGRyZW4gYDxhPjwvYT48c2xvdD48L3Nsb3Q+PGI+PC9iPmAKICAgICAqIGFuZCB0aGUgYDxzbG90PmAgaGFzIG9uZSBgPGRpdj5gIGFzc2lnbmVkIHRvIGl0LCB0aGVuIHRoZSBmbGF0dGVuZWQKICAgICAqIG5vZGVzIGxpc3QgaXMgYDxhPjwvYT48ZGl2PjwvZGl2PjxiPjwvYj5gLiBJZiB0aGUgYDxzbG90PmAgaGFzIG90aGVyCiAgICAgKiBgPHNsb3Q+YCBlbGVtZW50cyBhc3NpZ25lZCB0byBpdCwgdGhlc2UgYXJlIGZsYXR0ZW5lZCBhcyB3ZWxsLgogICAgICoKICAgICAqIFRoZSBwcm92aWRlZCBgY2FsbGJhY2tgIGlzIGNhbGxlZCB3aGVuZXZlciBhbnkgY2hhbmdlIHRvIHRoaXMgbGlzdAogICAgICogb2YgZmxhdHRlbmVkIG5vZGVzIG9jY3Vycywgd2hlcmUgYW4gYWRkaXRpb24gb3IgcmVtb3ZhbCBvZiBhIG5vZGUgaXMKICAgICAqIGNvbnNpZGVyZWQgYSBjaGFuZ2UuIFRoZSBgY2FsbGJhY2tgIGlzIGNhbGxlZCB3aXRoIG9uZSBhcmd1bWVudCwgYW4gb2JqZWN0CiAgICAgKiBjb250YWluaW5nIGFuIGFycmF5IG9mIGFueSBgYWRkZWROb2Rlc2AgYW5kIGByZW1vdmVkTm9kZXNgLgogICAgICoKICAgICAqIE5vdGU6IHRoZSBjYWxsYmFjayBpcyBjYWxsZWQgYXN5bmNocm9ub3VzIHRvIGFueSBjaGFuZ2VzCiAgICAgKiBhdCBhIG1pY3JvdGFzayBjaGVja3BvaW50LiBUaGlzIGlzIGJlY2F1c2Ugb2JzZXJ2YXRpb24gaXMgcGVyZm9ybWVkIHVzaW5nCiAgICAgKiBgTXV0YXRpb25PYnNlcnZlcmAgYW5kIHRoZSBgPHNsb3Q+YCBlbGVtZW50J3MgYHNsb3RjaGFuZ2VgIGV2ZW50IHdoaWNoCiAgICAgKiBhcmUgYXN5bmNocm9ub3VzLgogICAgICoKICAgICAqIEFuIGV4YW1wbGU6CiAgICAgKiBgYGBqcwogICAgICogY2xhc3MgVGVzdFNlbGZPYnNlcnZlIGV4dGVuZHMgUG9seW1lckVsZW1lbnQgewogICAgICogICBzdGF0aWMgZ2V0IGlzKCkgeyByZXR1cm4gJ3Rlc3Qtc2VsZi1vYnNlcnZlJzt9CiAgICAgKiAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICogICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgKiAgICAgdGhpcy5fb2JzZXJ2ZXIgPSBuZXcgRmxhdHRlbmVkTm9kZXNPYnNlcnZlcih0aGlzLCAoaW5mbykgPT4gewogICAgICogICAgICAgdGhpcy5pbmZvID0gaW5mbzsKICAgICAqICAgICB9KTsKICAgICAqICAgfQogICAgICogICBkaXNjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAqICAgICBzdXBlci5kaXNjb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICogICAgIHRoaXMuX29ic2VydmVyLmRpc2Nvbm5lY3QoKTsKICAgICAqICAgfQogICAgICogfQogICAgICogY3VzdG9tRWxlbWVudHMuZGVmaW5lKFRlc3RTZWxmT2JzZXJ2ZS5pcywgVGVzdFNlbGZPYnNlcnZlKTsKICAgICAqIGBgYAogICAgICoKICAgICAqIEBzdW1tYXJ5IENsYXNzIHRoYXQgbGlzdGVucyBmb3IgY2hhbmdlcyAoYWRkaXRpb25zIG9yIHJlbW92YWxzKSB0bwogICAgICogImZsYXR0ZW5lZCBub2RlcyIgb24gYSBnaXZlbiBgbm9kZWAuCiAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lckRvbUFwaS5PYnNlcnZlSGFuZGxlfQogICAgICovCiAgICBsZXQgRmxhdHRlbmVkTm9kZXNPYnNlcnZlciA9IGNsYXNzIHsKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBsaXN0IG9mIGZsYXR0ZW5lZCBub2RlcyBmb3IgdGhlIGdpdmVuIGBub2RlYC4KICAgICAgICogVGhpcyBsaXN0IGNvbnNpc3RzIG9mIGEgbm9kZSdzIGNoaWxkcmVuIGFuZCwgZm9yIGFueSBjaGlsZHJlbgogICAgICAgKiB0aGF0IGFyZSBgPHNsb3Q+YCBlbGVtZW50cywgdGhlIGV4cGFuZGVkIGZsYXR0ZW5lZCBsaXN0IG9mIGBhc3NpZ25lZE5vZGVzYC4KICAgICAgICogRm9yIGV4YW1wbGUsIGlmIHRoZSBvYnNlcnZlZCBub2RlIGhhcyBjaGlsZHJlbiBgPGE+PC9hPjxzbG90Pjwvc2xvdD48Yj48L2I+YAogICAgICAgKiBhbmQgdGhlIGA8c2xvdD5gIGhhcyBvbmUgYDxkaXY+YCBhc3NpZ25lZCB0byBpdCwgdGhlbiB0aGUgZmxhdHRlbmVkCiAgICAgICAqIG5vZGVzIGxpc3QgaXMgYDxhPjwvYT48ZGl2PjwvZGl2PjxiPjwvYj5gLiBJZiB0aGUgYDxzbG90PmAgaGFzIG90aGVyCiAgICAgICAqIGA8c2xvdD5gIGVsZW1lbnRzIGFzc2lnbmVkIHRvIGl0LCB0aGVzZSBhcmUgZmxhdHRlbmVkIGFzIHdlbGwuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fCFIVE1MU2xvdEVsZW1lbnR9IG5vZGUgVGhlIG5vZGUgZm9yIHdoaWNoIHRvCiAgICAgICAqICAgICAgcmV0dXJuIHRoZSBsaXN0IG9mIGZsYXR0ZW5lZCBub2Rlcy4KICAgICAgICogQHJldHVybiB7IUFycmF5PCFOb2RlPn0gVGhlIGxpc3Qgb2YgZmxhdHRlbmVkIG5vZGVzIGZvciB0aGUgZ2l2ZW4gYG5vZGVgLgogICAgICAgKiBAbm9jb2xsYXBzZSBTZWUgaHR0cHM6Ly9naXRodWIuY29tL2dvb2dsZS9jbG9zdXJlLWNvbXBpbGVyL2lzc3Vlcy8yNzYzCiAgICAgICAqLwogICAgICAvLyBlc2xpbnQtZGlzYWJsZS1uZXh0LWxpbmUKICAgICAgc3RhdGljIGdldEZsYXR0ZW5lZE5vZGVzKG5vZGUpIHsKICAgICAgICBjb25zdCB3cmFwcGVkID0gd3JhcChub2RlKTsKICAgICAgICBpZiAoaXNTbG90KG5vZGUpKSB7CiAgICAgICAgICBub2RlID0gLyoqIEB0eXBlIHshSFRNTFNsb3RFbGVtZW50fSAqLyhub2RlKTsgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby1zZWxmLWFzc2lnbgogICAgICAgICAgcmV0dXJuIHdyYXBwZWQuYXNzaWduZWROb2Rlcyh7ZmxhdHRlbjogdHJ1ZX0pOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICByZXR1cm4gQXJyYXkuZnJvbSh3cmFwcGVkLmNoaWxkTm9kZXMpLm1hcCgobm9kZSkgPT4gewogICAgICAgICAgICBpZiAoaXNTbG90KG5vZGUpKSB7CiAgICAgICAgICAgICAgbm9kZSA9IC8qKiBAdHlwZSB7IUhUTUxTbG90RWxlbWVudH0gKi8obm9kZSk7IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tc2VsZi1hc3NpZ24KICAgICAgICAgICAgICByZXR1cm4gd3JhcChub2RlKS5hc3NpZ25lZE5vZGVzKHtmbGF0dGVuOiB0cnVlfSk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgcmV0dXJuIFtub2RlXTsKICAgICAgICAgICAgfQogICAgICAgICAgfSkucmVkdWNlKChhLCBiKSA9PiBhLmNvbmNhdChiKSwgW10pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSB0YXJnZXQgTm9kZSBvbiB3aGljaCB0byBsaXN0ZW4gZm9yIGNoYW5nZXMuCiAgICAgICAqIEBwYXJhbSB7P2Z1bmN0aW9uKHRoaXM6IEVsZW1lbnQsIHsgdGFyZ2V0OiAhSFRNTEVsZW1lbnQsIGFkZGVkTm9kZXM6ICFBcnJheTwhRWxlbWVudD4sIHJlbW92ZWROb2RlczogIUFycmF5PCFFbGVtZW50PiB9KTp2b2lkfSBjYWxsYmFjayBGdW5jdGlvbiBjYWxsZWQgd2hlbiB0aGVyZSBhcmUgYWRkaXRpb25zCiAgICAgICAqIG9yIHJlbW92YWxzIGZyb20gdGhlIHRhcmdldCdzIGxpc3Qgb2YgZmxhdHRlbmVkIG5vZGVzLgogICAgICAgKi8KICAgICAgLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lCiAgICAgIGNvbnN0cnVjdG9yKHRhcmdldCwgY2FsbGJhY2spIHsKICAgICAgICAvKioKICAgICAgICAgKiBAdHlwZSB7TXV0YXRpb25PYnNlcnZlcn0KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIHRoaXMuX3NoYWR5Q2hpbGRyZW5PYnNlcnZlciA9IG51bGw7CiAgICAgICAgLyoqCiAgICAgICAgICogQHR5cGUge011dGF0aW9uT2JzZXJ2ZXJ9CiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKi8KICAgICAgICB0aGlzLl9uYXRpdmVDaGlsZHJlbk9ic2VydmVyID0gbnVsbDsKICAgICAgICB0aGlzLl9jb25uZWN0ZWQgPSBmYWxzZTsKICAgICAgICAvKioKICAgICAgICAgKiBAdHlwZSB7IUhUTUxFbGVtZW50fQogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICovCiAgICAgICAgdGhpcy5fdGFyZ2V0ID0gdGFyZ2V0OwogICAgICAgIHRoaXMuY2FsbGJhY2sgPSBjYWxsYmFjazsKICAgICAgICB0aGlzLl9lZmZlY3RpdmVOb2RlcyA9IFtdOwogICAgICAgIHRoaXMuX29ic2VydmVyID0gbnVsbDsKICAgICAgICB0aGlzLl9zY2hlZHVsZWQgPSBmYWxzZTsKICAgICAgICAvKioKICAgICAgICAgKiBAdHlwZSB7ZnVuY3Rpb24oKX0KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIHRoaXMuX2JvdW5kU2NoZWR1bGUgPSAoKSA9PiB7CiAgICAgICAgICB0aGlzLl9zY2hlZHVsZSgpOwogICAgICAgIH07CiAgICAgICAgdGhpcy5jb25uZWN0KCk7CiAgICAgICAgdGhpcy5fc2NoZWR1bGUoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEFjdGl2YXRlcyBhbiBvYnNlcnZlci4gVGhpcyBtZXRob2QgaXMgYXV0b21hdGljYWxseSBjYWxsZWQgd2hlbgogICAgICAgKiBhIGBGbGF0dGVuZWROb2Rlc09ic2VydmVyYCBpcyBjcmVhdGVkLiBJdCBzaG91bGQgb25seSBiZSBjYWxsZWQgdG8KICAgICAgICogcmUtYWN0aXZhdGUgYW4gb2JzZXJ2ZXIgdGhhdCBoYXMgYmVlbiBkZWFjdGl2YXRlZCB2aWEgdGhlIGBkaXNjb25uZWN0YCBtZXRob2QuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBjb25uZWN0KCkgewogICAgICAgIGlmIChpc1Nsb3QodGhpcy5fdGFyZ2V0KSkgewogICAgICAgICAgdGhpcy5fbGlzdGVuU2xvdHMoW3RoaXMuX3RhcmdldF0pOwogICAgICAgIH0gZWxzZSBpZiAod3JhcCh0aGlzLl90YXJnZXQpLmNoaWxkcmVuKSB7CiAgICAgICAgICB0aGlzLl9saXN0ZW5TbG90cygKICAgICAgICAgICAgICAvKiogQHR5cGUgeyFOb2RlTGlzdDwhTm9kZT59ICovICh3cmFwKHRoaXMuX3RhcmdldCkuY2hpbGRyZW4pKTsKICAgICAgICAgIGlmICh3aW5kb3cuU2hhZHlET00pIHsKICAgICAgICAgICAgdGhpcy5fc2hhZHlDaGlsZHJlbk9ic2VydmVyID0KICAgICAgICAgICAgICB3aW5kb3cuU2hhZHlET00ub2JzZXJ2ZUNoaWxkcmVuKHRoaXMuX3RhcmdldCwgKG11dGF0aW9ucykgPT4gewogICAgICAgICAgICAgICAgdGhpcy5fcHJvY2Vzc011dGF0aW9ucyhtdXRhdGlvbnMpOwogICAgICAgICAgICAgIH0pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fbmF0aXZlQ2hpbGRyZW5PYnNlcnZlciA9CiAgICAgICAgICAgICAgbmV3IE11dGF0aW9uT2JzZXJ2ZXIoKG11dGF0aW9ucykgPT4gewogICAgICAgICAgICAgICAgdGhpcy5fcHJvY2Vzc011dGF0aW9ucyhtdXRhdGlvbnMpOwogICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9uYXRpdmVDaGlsZHJlbk9ic2VydmVyLm9ic2VydmUodGhpcy5fdGFyZ2V0LCB7Y2hpbGRMaXN0OiB0cnVlfSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuX2Nvbm5lY3RlZCA9IHRydWU7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBEZWFjdGl2YXRlcyB0aGUgZmxhdHRlbmVkIG5vZGVzIG9ic2VydmVyLiBBZnRlciBjYWxsaW5nIHRoaXMgbWV0aG9kCiAgICAgICAqIHRoZSBvYnNlcnZlciBjYWxsYmFjayB3aWxsIG5vdCBiZSBjYWxsZWQgd2hlbiBjaGFuZ2VzIHRvIGZsYXR0ZW5lZCBub2RlcwogICAgICAgKiBvY2N1ci4gVGhlIGBjb25uZWN0YCBtZXRob2QgbWF5IGJlIHN1YnNlcXVlbnRseSBjYWxsZWQgdG8gcmVhY3RpdmF0ZQogICAgICAgKiB0aGUgb2JzZXJ2ZXIuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgZGlzY29ubmVjdCgpIHsKICAgICAgICBpZiAoaXNTbG90KHRoaXMuX3RhcmdldCkpIHsKICAgICAgICAgIHRoaXMuX3VubGlzdGVuU2xvdHMoW3RoaXMuX3RhcmdldF0pOwogICAgICAgIH0gZWxzZSBpZiAod3JhcCh0aGlzLl90YXJnZXQpLmNoaWxkcmVuKSB7CiAgICAgICAgICB0aGlzLl91bmxpc3RlblNsb3RzKAogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IU5vZGVMaXN0PCFOb2RlPn0gKi8gKHdyYXAodGhpcy5fdGFyZ2V0KS5jaGlsZHJlbikpOwogICAgICAgICAgaWYgKHdpbmRvdy5TaGFkeURPTSAmJiB0aGlzLl9zaGFkeUNoaWxkcmVuT2JzZXJ2ZXIpIHsKICAgICAgICAgICAgd2luZG93LlNoYWR5RE9NLnVub2JzZXJ2ZUNoaWxkcmVuKHRoaXMuX3NoYWR5Q2hpbGRyZW5PYnNlcnZlcik7CiAgICAgICAgICAgIHRoaXMuX3NoYWR5Q2hpbGRyZW5PYnNlcnZlciA9IG51bGw7CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX25hdGl2ZUNoaWxkcmVuT2JzZXJ2ZXIpIHsKICAgICAgICAgICAgdGhpcy5fbmF0aXZlQ2hpbGRyZW5PYnNlcnZlci5kaXNjb25uZWN0KCk7CiAgICAgICAgICAgIHRoaXMuX25hdGl2ZUNoaWxkcmVuT2JzZXJ2ZXIgPSBudWxsOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0aGlzLl9jb25uZWN0ZWQgPSBmYWxzZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfc2NoZWR1bGUoKSB7CiAgICAgICAgaWYgKCF0aGlzLl9zY2hlZHVsZWQpIHsKICAgICAgICAgIHRoaXMuX3NjaGVkdWxlZCA9IHRydWU7CiAgICAgICAgICBtaWNyb1Rhc2sucnVuKCgpID0+IHRoaXMuZmx1c2goKSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHtBcnJheTxNdXRhdGlvblJlY29yZD59IG11dGF0aW9ucyBNdXRhdGlvbnMgc2lnbmFsZWQgYnkgdGhlIG11dGF0aW9uIG9ic2VydmVyCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfcHJvY2Vzc011dGF0aW9ucyhtdXRhdGlvbnMpIHsKICAgICAgICB0aGlzLl9wcm9jZXNzU2xvdE11dGF0aW9ucyhtdXRhdGlvbnMpOwogICAgICAgIHRoaXMuZmx1c2goKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7QXJyYXk8TXV0YXRpb25SZWNvcmQ+fSBtdXRhdGlvbnMgTXV0YXRpb25zIHNpZ25hbGVkIGJ5IHRoZSBtdXRhdGlvbiBvYnNlcnZlcgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX3Byb2Nlc3NTbG90TXV0YXRpb25zKG11dGF0aW9ucykgewogICAgICAgIGlmIChtdXRhdGlvbnMpIHsKICAgICAgICAgIGZvciAobGV0IGk9MDsgaSA8IG11dGF0aW9ucy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICBsZXQgbXV0YXRpb24gPSBtdXRhdGlvbnNbaV07CiAgICAgICAgICAgIGlmIChtdXRhdGlvbi5hZGRlZE5vZGVzKSB7CiAgICAgICAgICAgICAgdGhpcy5fbGlzdGVuU2xvdHMobXV0YXRpb24uYWRkZWROb2Rlcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG11dGF0aW9uLnJlbW92ZWROb2RlcykgewogICAgICAgICAgICAgIHRoaXMuX3VubGlzdGVuU2xvdHMobXV0YXRpb24ucmVtb3ZlZE5vZGVzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEZsdXNoZXMgdGhlIG9ic2VydmVyIGNhdXNpbmcgYW55IHBlbmRpbmcgY2hhbmdlcyB0byBiZSBpbW1lZGlhdGVseQogICAgICAgKiBkZWxpdmVyZWQgdGhlIG9ic2VydmVyIGNhbGxiYWNrLiBCeSBkZWZhdWx0IHRoZXNlIGNoYW5nZXMgYXJlIGRlbGl2ZXJlZAogICAgICAgKiBhc3luY2hyb25vdXNseSBhdCB0aGUgbmV4dCBtaWNyb3Rhc2sgY2hlY2twb2ludC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIGFueSBwZW5kaW5nIGNoYW5nZXMgY2F1c2VkIHRoZSBvYnNlcnZlcgogICAgICAgKiBjYWxsYmFjayB0byBydW4uCiAgICAgICAqLwogICAgICBmbHVzaCgpIHsKICAgICAgICBpZiAoIXRoaXMuX2Nvbm5lY3RlZCkgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICBpZiAod2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgICBTaGFkeURPTS5mbHVzaCgpOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fbmF0aXZlQ2hpbGRyZW5PYnNlcnZlcikgewogICAgICAgICAgdGhpcy5fcHJvY2Vzc1Nsb3RNdXRhdGlvbnModGhpcy5fbmF0aXZlQ2hpbGRyZW5PYnNlcnZlci50YWtlUmVjb3JkcygpKTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX3NoYWR5Q2hpbGRyZW5PYnNlcnZlcikgewogICAgICAgICAgdGhpcy5fcHJvY2Vzc1Nsb3RNdXRhdGlvbnModGhpcy5fc2hhZHlDaGlsZHJlbk9ic2VydmVyLnRha2VSZWNvcmRzKCkpOwogICAgICAgIH0KICAgICAgICB0aGlzLl9zY2hlZHVsZWQgPSBmYWxzZTsKICAgICAgICBsZXQgaW5mbyA9IHsKICAgICAgICAgIHRhcmdldDogdGhpcy5fdGFyZ2V0LAogICAgICAgICAgYWRkZWROb2RlczogW10sCiAgICAgICAgICByZW1vdmVkTm9kZXM6IFtdCiAgICAgICAgfTsKICAgICAgICBsZXQgbmV3Tm9kZXMgPSB0aGlzLmNvbnN0cnVjdG9yLmdldEZsYXR0ZW5lZE5vZGVzKHRoaXMuX3RhcmdldCk7CiAgICAgICAgbGV0IHNwbGljZXMgPSBjYWxjdWxhdGVTcGxpY2VzKG5ld05vZGVzLAogICAgICAgICAgdGhpcy5fZWZmZWN0aXZlTm9kZXMpOwogICAgICAgIC8vIHByb2Nlc3MgcmVtb3ZhbHMKICAgICAgICBmb3IgKGxldCBpPTAsIHM7IChpPHNwbGljZXMubGVuZ3RoKSAmJiAocz1zcGxpY2VzW2ldKTsgaSsrKSB7CiAgICAgICAgICBmb3IgKGxldCBqPTAsIG47IChqIDwgcy5yZW1vdmVkLmxlbmd0aCkgJiYgKG49cy5yZW1vdmVkW2pdKTsgaisrKSB7CiAgICAgICAgICAgIGluZm8ucmVtb3ZlZE5vZGVzLnB1c2gobik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIHByb2Nlc3MgYWRkcwogICAgICAgIGZvciAobGV0IGk9MCwgczsgKGk8c3BsaWNlcy5sZW5ndGgpICYmIChzPXNwbGljZXNbaV0pOyBpKyspIHsKICAgICAgICAgIGZvciAobGV0IGo9cy5pbmRleDsgaiA8IHMuaW5kZXggKyBzLmFkZGVkQ291bnQ7IGorKykgewogICAgICAgICAgICBpbmZvLmFkZGVkTm9kZXMucHVzaChuZXdOb2Rlc1tqXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIHVwZGF0ZSBjYWNoZQogICAgICAgIHRoaXMuX2VmZmVjdGl2ZU5vZGVzID0gbmV3Tm9kZXM7CiAgICAgICAgbGV0IGRpZEZsdXNoID0gZmFsc2U7CiAgICAgICAgaWYgKGluZm8uYWRkZWROb2Rlcy5sZW5ndGggfHwgaW5mby5yZW1vdmVkTm9kZXMubGVuZ3RoKSB7CiAgICAgICAgICBkaWRGbHVzaCA9IHRydWU7CiAgICAgICAgICB0aGlzLmNhbGxiYWNrLmNhbGwodGhpcy5fdGFyZ2V0LCBpbmZvKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGRpZEZsdXNoOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHshQXJyYXk8IU5vZGU+fCFOb2RlTGlzdDwhTm9kZT59IG5vZGVMaXN0IE5vZGVzIHRoYXQgY291bGQgY2hhbmdlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfbGlzdGVuU2xvdHMobm9kZUxpc3QpIHsKICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBub2RlTGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgbGV0IG4gPSBub2RlTGlzdFtpXTsKICAgICAgICAgIGlmIChpc1Nsb3QobikpIHsKICAgICAgICAgICAgbi5hZGRFdmVudExpc3RlbmVyKCdzbG90Y2hhbmdlJywgdGhpcy5fYm91bmRTY2hlZHVsZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHshQXJyYXk8IU5vZGU+fCFOb2RlTGlzdDwhTm9kZT59IG5vZGVMaXN0IE5vZGVzIHRoYXQgY291bGQgY2hhbmdlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfdW5saXN0ZW5TbG90cyhub2RlTGlzdCkgewogICAgICAgIGZvciAobGV0IGk9MDsgaSA8IG5vZGVMaXN0Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBsZXQgbiA9IG5vZGVMaXN0W2ldOwogICAgICAgICAgaWYgKGlzU2xvdChuKSkgewogICAgICAgICAgICBuLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3Nsb3RjaGFuZ2UnLCB0aGlzLl9ib3VuZFNjaGVkdWxlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBGb3JjZXMgc2V2ZXJhbCBjbGFzc2VzIG9mIGFzeW5jaHJvbm91c2x5IHF1ZXVlZCB0YXNrcyB0byBmbHVzaDoKICAgICAqIC0gRGVib3VuY2VycyBhZGRlZCB2aWEgYGVucXVldWVEZWJvdW5jZXJgCiAgICAgKiAtIFNoYWR5RE9NIGRpc3RyaWJ1dGlvbgogICAgICoKICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgKi8KICAgIGNvbnN0IGZsdXNoID0gZnVuY3Rpb24oKSB7CiAgICAgIGxldCBzaGFkeURPTSwgZGVib3VuY2VyczsKICAgICAgZG8gewogICAgICAgIHNoYWR5RE9NID0gd2luZG93LlNoYWR5RE9NICYmIFNoYWR5RE9NLmZsdXNoKCk7CiAgICAgICAgaWYgKHdpbmRvdy5TaGFkeUNTUyAmJiB3aW5kb3cuU2hhZHlDU1MuU2NvcGluZ1NoaW0pIHsKICAgICAgICAgIHdpbmRvdy5TaGFkeUNTUy5TY29waW5nU2hpbS5mbHVzaCgpOwogICAgICAgIH0KICAgICAgICBkZWJvdW5jZXJzID0gZmx1c2hEZWJvdW5jZXJzKCk7CiAgICAgIH0gd2hpbGUgKHNoYWR5RE9NIHx8IGRlYm91bmNlcnMpOwogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgLyogZXNsaW50LWVuYWJsZSBuby11bnVzZWQtdmFycyAqLwoKICAgIGNvbnN0IHAgPSBFbGVtZW50LnByb3RvdHlwZTsKICAgIC8qKgogICAgICogQGNvbnN0IHtmdW5jdGlvbih0aGlzOk5vZGUsIHN0cmluZyk6IGJvb2xlYW59CiAgICAgKi8KICAgIGNvbnN0IG5vcm1hbGl6ZWRNYXRjaGVzU2VsZWN0b3IgPSBwLm1hdGNoZXMgfHwgcC5tYXRjaGVzU2VsZWN0b3IgfHwKICAgICAgcC5tb3pNYXRjaGVzU2VsZWN0b3IgfHwgcC5tc01hdGNoZXNTZWxlY3RvciB8fAogICAgICBwLm9NYXRjaGVzU2VsZWN0b3IgfHwgcC53ZWJraXRNYXRjaGVzU2VsZWN0b3I7CgogICAgLyoqCiAgICAgKiBDcm9zcy1wbGF0Zm9ybSBgZWxlbWVudC5tYXRjaGVzYCBzaGltLgogICAgICoKICAgICAqIEBmdW5jdGlvbiBtYXRjaGVzU2VsZWN0b3IKICAgICAqIEBwYXJhbSB7IU5vZGV9IG5vZGUgTm9kZSB0byBjaGVjayBzZWxlY3RvciBhZ2FpbnN0CiAgICAgKiBAcGFyYW0ge3N0cmluZ30gc2VsZWN0b3IgU2VsZWN0b3IgdG8gbWF0Y2gKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgbm9kZSBtYXRjaGVkIHNlbGVjdG9yCiAgICAgKi8KICAgIGNvbnN0IG1hdGNoZXNTZWxlY3RvciA9IGZ1bmN0aW9uKG5vZGUsIHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBub3JtYWxpemVkTWF0Y2hlc1NlbGVjdG9yLmNhbGwobm9kZSwgc2VsZWN0b3IpOwogICAgfTsKCiAgICAvKioKICAgICAqIE5vZGUgQVBJIHdyYXBwZXIgY2xhc3MgcmV0dXJuZWQgZnJvbSBgUG9seW1lci5kb20uKHRhcmdldClgIHdoZW4KICAgICAqIGB0YXJnZXRgIGlzIGEgYE5vZGVgLgogICAgICogQGltcGxlbWVudHMge1BvbHltZXJEb21BcGl9CiAgICAgKiBAdW5yZXN0cmljdGVkCiAgICAgKi8KICAgIGNsYXNzIERvbUFwaU5hdGl2ZSB7CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHshTm9kZX0gbm9kZSBOb2RlIGZvciB3aGljaCB0byBjcmVhdGUgYSBQb2x5bWVyLmRvbSBoZWxwZXIgb2JqZWN0LgogICAgICAgKi8KICAgICAgY29uc3RydWN0b3Iobm9kZSkgewogICAgICAgIGlmICh3aW5kb3dbJ1NoYWR5RE9NJ10gJiYgd2luZG93WydTaGFkeURPTSddWydpblVzZSddKSB7CiAgICAgICAgICB3aW5kb3dbJ1NoYWR5RE9NJ11bJ3BhdGNoJ10obm9kZSk7CiAgICAgICAgfQogICAgICAgIHRoaXMubm9kZSA9IG5vZGU7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGFuIGluc3RhbmNlIG9mIGBGbGF0dGVuZWROb2Rlc09ic2VydmVyYCB0aGF0CiAgICAgICAqIGxpc3RlbnMgZm9yIG5vZGUgY2hhbmdlcyBvbiB0aGlzIGVsZW1lbnQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24odGhpczpIVE1MRWxlbWVudCwgeyB0YXJnZXQ6ICFIVE1MRWxlbWVudCwgYWRkZWROb2RlczogIUFycmF5PCFFbGVtZW50PiwgcmVtb3ZlZE5vZGVzOiAhQXJyYXk8IUVsZW1lbnQ+IH0pOnZvaWR9IGNhbGxiYWNrIENhbGxlZCB3aGVuIGRpcmVjdCBvciBkaXN0cmlidXRlZCBjaGlsZHJlbgogICAgICAgKiAgIG9mIHRoaXMgZWxlbWVudCBjaGFuZ2VzCiAgICAgICAqIEByZXR1cm4geyFQb2x5bWVyRG9tQXBpLk9ic2VydmVIYW5kbGV9IE9ic2VydmVyIGluc3RhbmNlCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgb2JzZXJ2ZU5vZGVzKGNhbGxiYWNrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBGbGF0dGVuZWROb2Rlc09ic2VydmVyKAogICAgICAgICAgICAvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8odGhpcy5ub2RlKSwgY2FsbGJhY2spOwogICAgICB9CgogICAgICAvKioKICAgICAgICogRGlzY29ubmVjdHMgYW4gb2JzZXJ2ZXIgcHJldmlvdXNseSBjcmVhdGVkIHZpYSBgb2JzZXJ2ZU5vZGVzYAogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFQb2x5bWVyRG9tQXBpLk9ic2VydmVIYW5kbGV9IG9ic2VydmVySGFuZGxlIE9ic2VydmVyIGluc3RhbmNlCiAgICAgICAqICAgdG8gZGlzY29ubmVjdC4KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqLwogICAgICB1bm9ic2VydmVOb2RlcyhvYnNlcnZlckhhbmRsZSkgewogICAgICAgIG9ic2VydmVySGFuZGxlLmRpc2Nvbm5lY3QoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFByb3ZpZGVkIGFzIGEgYmFja3dhcmRzLWNvbXBhdGlibGUgQVBJIG9ubHkuICBUaGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBub3RpZnlPYnNlcnZlcigpIHt9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBwcm92aWRlZCBub2RlIGlzIGNvbnRhaW5lZCB3aXRoIHRoaXMgZWxlbWVudCdzCiAgICAgICAqIGxpZ2h0LURPTSBjaGlsZHJlbiBvciBzaGFkb3cgcm9vdCwgaW5jbHVkaW5nIGFueSBuZXN0ZWQgc2hhZG93IHJvb3RzCiAgICAgICAqIG9mIGNoaWxkcmVuIHRoZXJlaW4uCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Tm9kZX0gbm9kZSBOb2RlIHRvIHRlc3QKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gUmV0dXJucyB0cnVlIGlmIHRoZSBnaXZlbiBgbm9kZWAgaXMgY29udGFpbmVkIHdpdGhpbgogICAgICAgKiAgIHRoaXMgZWxlbWVudCdzIGxpZ2h0IG9yIHNoYWRvdyBET00uCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgZGVlcENvbnRhaW5zKG5vZGUpIHsKICAgICAgICBpZiAod3JhcCh0aGlzLm5vZGUpLmNvbnRhaW5zKG5vZGUpKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgbGV0IG4gPSBub2RlOwogICAgICAgIGxldCBkb2MgPSBub2RlLm93bmVyRG9jdW1lbnQ7CiAgICAgICAgLy8gd2FsayBmcm9tIG5vZGUgdG8gYHRoaXNgIG9yIGBkb2N1bWVudGAKICAgICAgICB3aGlsZSAobiAmJiBuICE9PSBkb2MgJiYgbiAhPT0gdGhpcy5ub2RlKSB7CiAgICAgICAgICAvLyB1c2UgbG9naWNhbCBwYXJlbnRub2RlLCBvciBuYXRpdmUgU2hhZG93Um9vdCBob3N0CiAgICAgICAgICBuID0gd3JhcChuKS5wYXJlbnROb2RlIHx8IHdyYXAobikuaG9zdDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIG4gPT09IHRoaXMubm9kZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIHJvb3Qgbm9kZSBvZiB0aGlzIG5vZGUuICBFcXVpdmFsZW50IHRvIGBnZXRSb290Tm9kZSgpYC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IU5vZGV9IFRvcCBtb3N0IGVsZW1lbnQgaW4gdGhlIGRvbSB0cmVlIGluIHdoaWNoIHRoZSBub2RlCiAgICAgICAqIGV4aXN0cy4gSWYgdGhlIG5vZGUgaXMgY29ubmVjdGVkIHRvIGEgZG9jdW1lbnQgdGhpcyBpcyBlaXRoZXIgYQogICAgICAgKiBzaGFkb3dSb290IG9yIHRoZSBkb2N1bWVudDsgb3RoZXJ3aXNlLCBpdCBtYXkgYmUgdGhlIG5vZGUKICAgICAgICogaXRzZWxmIG9yIGEgbm9kZSBvciBkb2N1bWVudCBmcmFnbWVudCBjb250YWluaW5nIGl0LgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgIGdldE93bmVyUm9vdCgpIHsKICAgICAgICByZXR1cm4gd3JhcCh0aGlzLm5vZGUpLmdldFJvb3ROb2RlKCk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBGb3Igc2xvdCBlbGVtZW50cywgcmV0dXJucyB0aGUgbm9kZXMgYXNzaWduZWQgdG8gdGhlIHNsb3Q7IG90aGVyd2lzZQogICAgICAgKiBhbiBlbXB0eSBhcnJheS4gSXQgaXMgZXF1aXZhbGVudCB0byBgPHNsb3Q+LmFkZGlnbmVkTm9kZXMoe2ZsYXR0ZW46dHJ1ZX0pYC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IUFycmF5PCFOb2RlPn0gQXJyYXkgb2YgYXNzaWduZWQgbm9kZXMKICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqLwogICAgICBnZXREaXN0cmlidXRlZE5vZGVzKCkgewogICAgICAgIHJldHVybiAodGhpcy5ub2RlLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnKSA/CiAgICAgICAgICB3cmFwKHRoaXMubm9kZSkuYXNzaWduZWROb2Rlcyh7ZmxhdHRlbjogdHJ1ZX0pIDoKICAgICAgICAgIFtdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyBhbiBhcnJheSBvZiBhbGwgc2xvdHMgdGhpcyBlbGVtZW50IHdhcyBkaXN0cmlidXRlZCB0by4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IUFycmF5PCFIVE1MU2xvdEVsZW1lbnQ+fSBEZXNjcmlwdGlvbgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgIGdldERlc3RpbmF0aW9uSW5zZXJ0aW9uUG9pbnRzKCkgewogICAgICAgIGxldCBpcCQgPSBbXTsKICAgICAgICBsZXQgbiA9IHdyYXAodGhpcy5ub2RlKS5hc3NpZ25lZFNsb3Q7CiAgICAgICAgd2hpbGUgKG4pIHsKICAgICAgICAgIGlwJC5wdXNoKG4pOwogICAgICAgICAgbiA9IHdyYXAobikuYXNzaWduZWRTbG90OwogICAgICAgIH0KICAgICAgICByZXR1cm4gaXAkOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ2FsbHMgYGltcG9ydE5vZGVgIG9uIHRoZSBgb3duZXJEb2N1bWVudGAgZm9yIHRoaXMgbm9kZS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHshTm9kZX0gbm9kZSBOb2RlIHRvIGltcG9ydAogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IGRlZXAgVHJ1ZSBpZiB0aGUgbm9kZSBzaG91bGQgYmUgY2xvbmVkIGRlZXBseSBkdXJpbmcKICAgICAgICogICBpbXBvcnQKICAgICAgICogQHJldHVybiB7Tm9kZX0gQ2xvbmUgb2YgZ2l2ZW4gbm9kZSBpbXBvcnRlZCB0byB0aGlzIG93bmVyIGRvY3VtZW50CiAgICAgICAqLwogICAgICBpbXBvcnROb2RlKG5vZGUsIGRlZXApIHsKICAgICAgICBsZXQgZG9jID0gdGhpcy5ub2RlIGluc3RhbmNlb2YgRG9jdW1lbnQgPyB0aGlzLm5vZGUgOgogICAgICAgICAgdGhpcy5ub2RlLm93bmVyRG9jdW1lbnQ7CiAgICAgICAgcmV0dXJuIHdyYXAoZG9jKS5pbXBvcnROb2RlKG5vZGUsIGRlZXApOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHJldHVybiB7IUFycmF5PCFOb2RlPn0gUmV0dXJucyBhIGZsYXR0ZW5lZCBsaXN0IG9mIGFsbCBjaGlsZCBub2RlcyBhbmQKICAgICAgICogbm9kZXMgYXNzaWduZWQgdG8gY2hpbGQgc2xvdHMuCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgZ2V0RWZmZWN0aXZlQ2hpbGROb2RlcygpIHsKICAgICAgICByZXR1cm4gRmxhdHRlbmVkTm9kZXNPYnNlcnZlci5nZXRGbGF0dGVuZWROb2RlcygKICAgICAgICAgICAgLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovICh0aGlzLm5vZGUpKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgYSBmaWx0ZXJlZCBsaXN0IG9mIGZsYXR0ZW5lZCBjaGlsZCBlbGVtZW50cyBmb3IgdGhpcyBlbGVtZW50IGJhc2VkCiAgICAgICAqIG9uIHRoZSBnaXZlbiBzZWxlY3Rvci4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHNlbGVjdG9yIFNlbGVjdG9yIHRvIGZpbHRlciBub2RlcyBhZ2FpbnN0CiAgICAgICAqIEByZXR1cm4geyFBcnJheTwhSFRNTEVsZW1lbnQ+fSBMaXN0IG9mIGZsYXR0ZW5lZCBjaGlsZCBlbGVtZW50cwogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgIHF1ZXJ5RGlzdHJpYnV0ZWRFbGVtZW50cyhzZWxlY3RvcikgewogICAgICAgIGxldCBjJCA9IHRoaXMuZ2V0RWZmZWN0aXZlQ2hpbGROb2RlcygpOwogICAgICAgIGxldCBsaXN0ID0gW107CiAgICAgICAgZm9yIChsZXQgaT0wLCBsPWMkLmxlbmd0aCwgYzsgKGk8bCkgJiYgKGM9YyRbaV0pOyBpKyspIHsKICAgICAgICAgIGlmICgoYy5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpICYmCiAgICAgICAgICAgICAgbWF0Y2hlc1NlbGVjdG9yKGMsIHNlbGVjdG9yKSkgewogICAgICAgICAgICBsaXN0LnB1c2goYyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBsaXN0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogRm9yIHNoYWRvdyByb290cywgcmV0dXJucyB0aGUgY3VycmVudGx5IGZvY3VzZWQgZWxlbWVudCB3aXRoaW4gdGhpcwogICAgICAgKiBzaGFkb3cgcm9vdC4KICAgICAgICoKICAgICAgICogcmV0dXJuIHtOb2RlfHVuZGVmaW5lZH0gQ3VycmVudGx5IGZvY3VzZWQgZWxlbWVudAogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgIGdldCBhY3RpdmVFbGVtZW50KCkgewogICAgICAgIGxldCBub2RlID0gdGhpcy5ub2RlOwogICAgICAgIHJldHVybiBub2RlLl9hY3RpdmVFbGVtZW50ICE9PSB1bmRlZmluZWQgPyBub2RlLl9hY3RpdmVFbGVtZW50IDogbm9kZS5hY3RpdmVFbGVtZW50OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZm9yd2FyZE1ldGhvZHMocHJvdG8sIG1ldGhvZHMpIHsKICAgICAgZm9yIChsZXQgaT0wOyBpIDwgbWV0aG9kcy5sZW5ndGg7IGkrKykgewogICAgICAgIGxldCBtZXRob2QgPSBtZXRob2RzW2ldOwogICAgICAgIC8qIGVzbGludC1kaXNhYmxlIHZhbGlkLWpzZG9jICovCiAgICAgICAgcHJvdG9bbWV0aG9kXSA9IC8qKiBAdGhpcyB7RG9tQXBpTmF0aXZlfSAqLyBmdW5jdGlvbigpIHsKICAgICAgICAgIHJldHVybiB0aGlzLm5vZGVbbWV0aG9kXS5hcHBseSh0aGlzLm5vZGUsIGFyZ3VtZW50cyk7CiAgICAgICAgfTsKICAgICAgICAvKiBlc2xpbnQtZW5hYmxlICovCiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBmb3J3YXJkUmVhZE9ubHlQcm9wZXJ0aWVzKHByb3RvLCBwcm9wZXJ0aWVzKSB7CiAgICAgIGZvciAobGV0IGk9MDsgaSA8IHByb3BlcnRpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICBsZXQgbmFtZSA9IHByb3BlcnRpZXNbaV07CiAgICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHByb3RvLCBuYW1lLCB7CiAgICAgICAgICBnZXQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBjb25zdCBkb21BcGkgPSAvKiogQHR5cGUge0RvbUFwaU5hdGl2ZX0gKi8odGhpcyk7CiAgICAgICAgICAgIHJldHVybiBkb21BcGkubm9kZVtuYW1lXTsKICAgICAgICAgIH0sCiAgICAgICAgICBjb25maWd1cmFibGU6IHRydWUKICAgICAgICB9KTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGZvcndhcmRQcm9wZXJ0aWVzKHByb3RvLCBwcm9wZXJ0aWVzKSB7CiAgICAgIGZvciAobGV0IGk9MDsgaSA8IHByb3BlcnRpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICBsZXQgbmFtZSA9IHByb3BlcnRpZXNbaV07CiAgICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHByb3RvLCBuYW1lLCB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEB0aGlzIHtEb21BcGlOYXRpdmV9CiAgICAgICAgICAgKiBAcmV0dXJuIHsqfSAuCiAgICAgICAgICAgKi8KICAgICAgICAgIGdldDogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLm5vZGVbbmFtZV07CiAgICAgICAgICB9LAogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBAdGhpcyB7RG9tQXBpTmF0aXZlfQogICAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSAuCiAgICAgICAgICAgKi8KICAgICAgICAgIHNldDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgICAgdGhpcy5ub2RlW25hbWVdID0gdmFsdWU7CiAgICAgICAgICB9LAogICAgICAgICAgY29uZmlndXJhYmxlOiB0cnVlCiAgICAgICAgfSk7CiAgICAgIH0KICAgIH0KCgogICAgLyoqCiAgICAgKiBFdmVudCBBUEkgd3JhcHBlciBjbGFzcyByZXR1cm5lZCBmcm9tIGBkb20uKHRhcmdldClgIHdoZW4KICAgICAqIGB0YXJnZXRgIGlzIGFuIGBFdmVudGAuCiAgICAgKi8KICAgIGNsYXNzIEV2ZW50QXBpIHsKICAgICAgY29uc3RydWN0b3IoZXZlbnQpIHsKICAgICAgICB0aGlzLmV2ZW50ID0gZXZlbnQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBmaXJzdCBub2RlIG9uIHRoZSBgY29tcG9zZWRQYXRoYCBvZiB0aGlzIGV2ZW50LgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHshRXZlbnRUYXJnZXR9IFRoZSBub2RlIHRoaXMgZXZlbnQgd2FzIGRpc3BhdGNoZWQgdG8KICAgICAgICovCiAgICAgIGdldCByb290VGFyZ2V0KCkgewogICAgICAgIHJldHVybiB0aGlzLnBhdGhbMF07CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBsb2NhbCAocmUtdGFyZ2V0ZWQpIHRhcmdldCBmb3IgdGhpcyBldmVudC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IUV2ZW50VGFyZ2V0fSBUaGUgbG9jYWwgKHJlLXRhcmdldGVkKSB0YXJnZXQgZm9yIHRoaXMgZXZlbnQuCiAgICAgICAqLwogICAgICBnZXQgbG9jYWxUYXJnZXQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZXZlbnQudGFyZ2V0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgYGNvbXBvc2VkUGF0aGAgZm9yIHRoaXMgZXZlbnQuCiAgICAgICAqIEByZXR1cm4geyFBcnJheTwhRXZlbnRUYXJnZXQ+fSBUaGUgbm9kZXMgdGhpcyBldmVudCBwcm9wYWdhdGVkIHRocm91Z2gKICAgICAgICovCiAgICAgIGdldCBwYXRoKCkgewogICAgICAgIHJldHVybiB0aGlzLmV2ZW50LmNvbXBvc2VkUGF0aCgpOwogICAgICB9CiAgICB9CgogICAgbGV0IERvbUFwaUltcGwgPSBEb21BcGlOYXRpdmU7CgogICAgaWYgKHdpbmRvd1snU2hhZHlET00nXSAmJiB3aW5kb3dbJ1NoYWR5RE9NJ11bJ2luVXNlJ10gJiYgd2luZG93WydTaGFkeURPTSddWydub1BhdGNoJ10gJiYgd2luZG93WydTaGFkeURPTSddWydXcmFwcGVyJ10pIHsKCiAgICAgIC8qKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKiBAZXh0ZW5kcyB7SFRNTEVsZW1lbnR9CiAgICAgICAqLwogICAgICBjbGFzcyBXcmFwcGVyIGV4dGVuZHMgd2luZG93WydTaGFkeURPTSddWydXcmFwcGVyJ10ge30KCiAgICAgIC8vIGNvcHkgYmVzcG9rZSBBUEkgb250byB3cmFwcGVyCiAgICAgIE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKERvbUFwaU5hdGl2ZS5wcm90b3R5cGUpLmZvckVhY2goKHByb3ApID0+IHsKICAgICAgICBpZiAocHJvcCAhPSAnYWN0aXZlRWxlbWVudCcpIHsKICAgICAgICAgIFdyYXBwZXIucHJvdG90eXBlW3Byb3BdID0gRG9tQXBpTmF0aXZlLnByb3RvdHlwZVtwcm9wXTsKICAgICAgICB9CiAgICAgIH0pOwoKICAgICAgLy8gTm90ZSwgYGNsYXNzTGlzdGAgaXMgaGVyZSBvbmx5IGZvciBsZWdhY3kgY29tcGF0aWJpbGl0eSBzaW5jZSBpdCBkb2VzIG5vdAogICAgICAvLyB0cmlnZ2VyIGRpc3RyaWJ1dGlvbiBpbiB2MSBTaGFkb3cgRE9NLgogICAgICBmb3J3YXJkUmVhZE9ubHlQcm9wZXJ0aWVzKFdyYXBwZXIucHJvdG90eXBlLCBbCiAgICAgICAgJ2NsYXNzTGlzdCcKICAgICAgXSk7CgogICAgICBEb21BcGlJbXBsID0gV3JhcHBlcjsKCiAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0aWVzKEV2ZW50QXBpLnByb3RvdHlwZSwgewoKICAgICAgICAvLyBSZXR1cm5zIHRoZSAibG93ZXN0IiBub2RlIGluIHRoZSBzYW1lIHJvb3QgYXMgdGhlIGV2ZW50J3MgY3VycmVudFRhcmdldC4KICAgICAgICAvLyBXaGVuIGluIGBub1BhdGNoYCBtb2RlLCB0aGlzIG11c3QgYmUgY2FsY3VsYXRlZCBieSB3YWxraW5nIHRoZSBldmVudCdzCiAgICAgICAgLy8gcGF0aC4KICAgICAgICBsb2NhbFRhcmdldDogewogICAgICAgICAgZ2V0KCkgewogICAgICAgICAgICBjb25zdCBjdXJyZW50ID0gdGhpcy5ldmVudC5jdXJyZW50VGFyZ2V0OwogICAgICAgICAgICBjb25zdCBjdXJyZW50Um9vdCA9IGN1cnJlbnQgJiYgZG9tKGN1cnJlbnQpLmdldE93bmVyUm9vdCgpOwogICAgICAgICAgICBjb25zdCBwJCA9IHRoaXMucGF0aDsKICAgICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBwJC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgIGNvbnN0IGUgPSBwJFtpXTsKICAgICAgICAgICAgICBpZiAoZG9tKGUpLmdldE93bmVyUm9vdCgpID09PSBjdXJyZW50Um9vdCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9LAogICAgICAgICAgY29uZmlndXJhYmxlOiB0cnVlCiAgICAgICAgfSwKCiAgICAgICAgcGF0aDogewogICAgICAgICAgZ2V0KCkgewogICAgICAgICAgICByZXR1cm4gd2luZG93WydTaGFkeURPTSddWydjb21wb3NlZFBhdGgnXSh0aGlzLmV2ZW50KTsKICAgICAgICAgIH0sCiAgICAgICAgICBjb25maWd1cmFibGU6IHRydWUKICAgICAgICB9CiAgICAgIH0pOwoKICAgIH0gZWxzZSB7CgogICAgICAvLyBNZXRob2RzIHRoYXQgY2FuIHByb3Zva2UgZGlzdHJpYnV0aW9uIG9yIG11c3QgcmV0dXJuIHRoZSBsb2dpY2FsLCBub3QKICAgICAgLy8gY29tcG9zZWQgdHJlZS4KICAgICAgZm9yd2FyZE1ldGhvZHMoRG9tQXBpTmF0aXZlLnByb3RvdHlwZSwgWwogICAgICAgICdjbG9uZU5vZGUnLCAnYXBwZW5kQ2hpbGQnLCAnaW5zZXJ0QmVmb3JlJywgJ3JlbW92ZUNoaWxkJywKICAgICAgICAncmVwbGFjZUNoaWxkJywgJ3NldEF0dHJpYnV0ZScsICdyZW1vdmVBdHRyaWJ1dGUnLAogICAgICAgICdxdWVyeVNlbGVjdG9yJywgJ3F1ZXJ5U2VsZWN0b3JBbGwnCiAgICAgIF0pOwoKICAgICAgLy8gUHJvcGVydGllcyB0aGF0IHNob3VsZCByZXR1cm4gdGhlIGxvZ2ljYWwsIG5vdCBjb21wb3NlZCB0cmVlLiBOb3RlLCBgY2xhc3NMaXN0YAogICAgICAvLyBpcyBoZXJlIG9ubHkgZm9yIGxlZ2FjeSBjb21wYXRpYmlsaXR5IHNpbmNlIGl0IGRvZXMgbm90IHRyaWdnZXIgZGlzdHJpYnV0aW9uCiAgICAgIC8vIGluIHYxIFNoYWRvdyBET00uCiAgICAgIGZvcndhcmRSZWFkT25seVByb3BlcnRpZXMoRG9tQXBpTmF0aXZlLnByb3RvdHlwZSwgWwogICAgICAgICdwYXJlbnROb2RlJywgJ2ZpcnN0Q2hpbGQnLCAnbGFzdENoaWxkJywKICAgICAgICAnbmV4dFNpYmxpbmcnLCAncHJldmlvdXNTaWJsaW5nJywgJ2ZpcnN0RWxlbWVudENoaWxkJywKICAgICAgICAnbGFzdEVsZW1lbnRDaGlsZCcsICduZXh0RWxlbWVudFNpYmxpbmcnLCAncHJldmlvdXNFbGVtZW50U2libGluZycsCiAgICAgICAgJ2NoaWxkTm9kZXMnLCAnY2hpbGRyZW4nLCAnY2xhc3NMaXN0JwogICAgICBdKTsKCiAgICAgIGZvcndhcmRQcm9wZXJ0aWVzKERvbUFwaU5hdGl2ZS5wcm90b3R5cGUsIFsKICAgICAgICAndGV4dENvbnRlbnQnLCAnaW5uZXJIVE1MJywgJ2NsYXNzTmFtZScKICAgICAgXSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBMZWdhY3kgRE9NIGFuZCBFdmVudCBtYW5pcHVsYXRpb24gQVBJIHdyYXBwZXIgZmFjdG9yeSB1c2VkIHRvIGFic3RyYWN0CiAgICAgKiBkaWZmZXJlbmNlcyBiZXR3ZWVuIG5hdGl2ZSBTaGFkb3cgRE9NIGFuZCAiU2hhZHkgRE9NIiB3aGVuIHBvbHlmaWxsaW5nIG9uCiAgICAgKiBvbGRlciBicm93c2Vycy4KICAgICAqCiAgICAgKiBOb3RlIHRoYXQgaW4gUG9seW1lciAyLnggdXNlIG9mIGBQb2x5bWVyLmRvbWAgaXMgbm8gbG9uZ2VyIHJlcXVpcmVkIGFuZAogICAgICogaW4gdGhlIG1ham9yaXR5IG9mIGNhc2VzIHNpbXBseSBmYWNhZGVzIGRpcmVjdGx5IHRvIHRoZSBzdGFuZGFyZCBuYXRpdmUKICAgICAqIEFQSS4KICAgICAqCiAgICAgKiBAc3VtbWFyeSBMZWdhY3kgRE9NIGFuZCBFdmVudCBtYW5pcHVsYXRpb24gQVBJIHdyYXBwZXIgZmFjdG9yeSB1c2VkIHRvCiAgICAgKiBhYnN0cmFjdCBkaWZmZXJlbmNlcyBiZXR3ZWVuIG5hdGl2ZSBTaGFkb3cgRE9NIGFuZCAiU2hhZHkgRE9NLiIKICAgICAqIEBwYXJhbSB7KE5vZGV8RXZlbnR8RG9tQXBpTmF0aXZlfEV2ZW50QXBpKT19IG9iaiBOb2RlIG9yIGV2ZW50IHRvIG9wZXJhdGUgb24KICAgICAqIEByZXR1cm4geyFEb21BcGlOYXRpdmV8IUV2ZW50QXBpfSBXcmFwcGVyIHByb3ZpZGluZyBlaXRoZXIgbm9kZSBBUEkgb3IgZXZlbnQgQVBJCiAgICAgKi8KICAgIGNvbnN0IGRvbSA9IGZ1bmN0aW9uKG9iaikgewogICAgICBvYmogPSBvYmogfHwgZG9jdW1lbnQ7CiAgICAgIGlmIChvYmogaW5zdGFuY2VvZiBEb21BcGlJbXBsKSB7CiAgICAgICAgcmV0dXJuIC8qKiBAdHlwZSB7IURvbUFwaX0gKi8ob2JqKTsKICAgICAgfQogICAgICBpZiAob2JqIGluc3RhbmNlb2YgRXZlbnRBcGkpIHsKICAgICAgICByZXR1cm4gLyoqIEB0eXBlIHshRXZlbnRBcGl9ICovKG9iaik7CiAgICAgIH0KICAgICAgbGV0IGhlbHBlciA9IG9ialsnX19kb21BcGknXTsKICAgICAgaWYgKCFoZWxwZXIpIHsKICAgICAgICBpZiAob2JqIGluc3RhbmNlb2YgRXZlbnQpIHsKICAgICAgICAgIGhlbHBlciA9IG5ldyBFdmVudEFwaShvYmopOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBoZWxwZXIgPSBuZXcgRG9tQXBpSW1wbCgvKiogQHR5cGUge05vZGV9ICovKG9iaikpOwogICAgICAgIH0KICAgICAgICBvYmpbJ19fZG9tQXBpJ10gPSBoZWxwZXI7CiAgICAgIH0KICAgICAgcmV0dXJuIGhlbHBlcjsKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE5IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCBTaGFkeURPTSQxID0gd2luZG93LlNoYWR5RE9NOwogICAgY29uc3QgU2hhZHlDU1MgPSB3aW5kb3cuU2hhZHlDU1M7CgogICAgLyoqCiAgICAgKiBSZXR1cm4gdHJ1ZSBpZiBub2RlIHNjb3BlIGlzIGNvcnJlY3QuCiAgICAgKgogICAgICogQHBhcmFtIHshRWxlbWVudH0gbm9kZSBOb2RlIHRvIGNoZWNrIHNjb3BlCiAgICAgKiBAcGFyYW0geyFOb2RlfSBzY29wZSBTY29wZSByZWZlcmVuY2UKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgbm9kZSBpcyBpbiBzY29wZQogICAgICovCiAgICBmdW5jdGlvbiBzYW1lU2NvcGUobm9kZSwgc2NvcGUpIHsKICAgICAgcmV0dXJuIHdyYXAobm9kZSkuZ2V0Um9vdE5vZGUoKSA9PT0gc2NvcGU7CiAgICB9CgogICAgLyoqCiAgICAgKiBFbnN1cmUgdGhhdCBlbGVtZW50cyBpbiBhIFNoYWRvd0RPTSBjb250YWluZXIgYXJlIHNjb3BlZCBjb3JyZWN0bHkuCiAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIG9ubHkgbmVlZGVkIHdoZW4gU2hhZHlET00gaXMgdXNlZCBhbmQgdW5wYXRjaGVkIERPTSBBUElzIGFyZSB1c2VkIGluIHRoaXJkIHBhcnR5IGNvZGUuCiAgICAgKiBUaGlzIGNhbiBoYXBwZW4gaW4gbm9QYXRjaCBtb2RlIG9yIHdoZW4gc3BlY2lhbGl6ZWQgQVBJcyBsaWtlIHJhbmdlcyBvciB0YWJsZXMgYXJlIHVzZWQgdG8gbXV0YXRlIERPTS4KICAgICAqCiAgICAgKiBAcGFyYW0gIHshRWxlbWVudH0gY29udGFpbmVyIENvbnRhaW5lciBlbGVtZW50IHRvIHNjb3BlCiAgICAgKiBAcGFyYW0gIHtib29sZWFuPX0gc2hvdWxkT2JzZXJ2ZSBpZiB0cnVlLCBzdGFydCBhIG11dGF0aW9uIG9ic2VydmVyIGZvciBhZGRlZCBub2RlcyB0byB0aGUgY29udGFpbmVyCiAgICAgKiBAcmV0dXJuIHs/TXV0YXRpb25PYnNlcnZlcn0gUmV0dXJucyBhIG5ldyBNdXRhdGlvbk9ic2VydmVyIG9uIGBjb250YWluZXJgIGlmIGBzaG91bGRPYnNlcnZlYCBpcyB0cnVlLgogICAgICovCiAgICBmdW5jdGlvbiBzY29wZVN1YnRyZWUoY29udGFpbmVyLCBzaG91bGRPYnNlcnZlID0gZmFsc2UpIHsKICAgICAgLy8gSWYgdXNpbmcgbmF0aXZlIFNoYWRvd0RPTSwgYWJvcnQKICAgICAgaWYgKCFTaGFkeURPTSQxIHx8ICFTaGFkeUNTUykgewogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CiAgICAgIC8vIFNoYWR5Q1NTIGhhbmRsZXMgRE9NIG11dGF0aW9ucyB3aGVuIFNoYWR5RE9NIGRvZXMgbm90IGhhbmRsZSBzY29waW5nIGl0c2VsZgogICAgICBpZiAoIVNoYWR5RE9NJDFbJ2hhbmRsZXNEeW5hbWljU2NvcGluZyddKSB7CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0KICAgICAgY29uc3QgU2NvcGluZ1NoaW0gPSBTaGFkeUNTU1snU2NvcGluZ1NoaW0nXTsKICAgICAgLy8gaWYgU2NvcGluZ1NoaW0gaXMgbm90IGF2YWlsYWJsZSwgYWJvcnQKICAgICAgaWYgKCFTY29waW5nU2hpbSkgewogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CiAgICAgIC8vIGNhcHR1cmUgY29ycmVjdCBzY29wZSBmb3IgY29udGFpbmVyCiAgICAgIGNvbnN0IGNvbnRhaW5lclNjb3BlID0gU2NvcGluZ1NoaW1bJ3Njb3BlRm9yTm9kZSddKGNvbnRhaW5lcik7CiAgICAgIGNvbnN0IHJvb3QgPSB3cmFwKGNvbnRhaW5lcikuZ2V0Um9vdE5vZGUoKTsKCiAgICAgIGNvbnN0IHNjb3BpZnkgPSAobm9kZSkgPT4gewogICAgICAgIGlmICghc2FtZVNjb3BlKG5vZGUsIHJvb3QpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIC8vIE5PVEU6IG5hdGl2ZSBxU0EgZG9lcyBub3QgaG9ub3Igc2NvcGVkIERPTSwgYnV0IGl0IGlzIGZhc3RlciwgYW5kIHRoZSBzYW1lIGJlaGF2aW9yIGFzIFBvbHltZXIgdjEKICAgICAgICBjb25zdCBlbGVtZW50cyA9IEFycmF5LmZyb20oU2hhZHlET00kMVsnbmF0aXZlTWV0aG9kcyddWydxdWVyeVNlbGVjdG9yQWxsJ10uY2FsbChub2RlLCAnKicpKTsKICAgICAgICBlbGVtZW50cy5wdXNoKG5vZGUpOwogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgZWxlbWVudHMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGNvbnN0IGVsID0gZWxlbWVudHNbaV07CiAgICAgICAgICBpZiAoIXNhbWVTY29wZShlbCwgcm9vdCkpIHsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICB9CiAgICAgICAgICBjb25zdCBjdXJyZW50U2NvcGUgPSBTY29waW5nU2hpbVsnY3VycmVudFNjb3BlRm9yTm9kZSddKGVsKTsKICAgICAgICAgIGlmIChjdXJyZW50U2NvcGUgIT09IGNvbnRhaW5lclNjb3BlKSB7CiAgICAgICAgICAgIGlmIChjdXJyZW50U2NvcGUgIT09ICcnKSB7CiAgICAgICAgICAgICAgU2NvcGluZ1NoaW1bJ3Vuc2NvcGVOb2RlJ10oZWwsIGN1cnJlbnRTY29wZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgU2NvcGluZ1NoaW1bJ3Njb3BlTm9kZSddKGVsLCBjb250YWluZXJTY29wZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9OwoKICAgICAgLy8gc2NvcGUgZXZlcnl0aGluZyBpbiBjb250YWluZXIKICAgICAgc2NvcGlmeShjb250YWluZXIpOwoKICAgICAgaWYgKHNob3VsZE9ic2VydmUpIHsKICAgICAgICBjb25zdCBtbyA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKChteG5zKSA9PiB7CiAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IG14bnMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgY29uc3QgbXhuID0gbXhuc1tpXTsKICAgICAgICAgICAgZm9yIChsZXQgaiA9IDA7IGogPCBteG4uYWRkZWROb2Rlcy5sZW5ndGg7IGorKykgewogICAgICAgICAgICAgIGNvbnN0IGFkZGVkTm9kZSA9IG14bi5hZGRlZE5vZGVzW2pdOwogICAgICAgICAgICAgIGlmIChhZGRlZE5vZGUubm9kZVR5cGUgPT09IE5vZGUuRUxFTUVOVF9OT0RFKSB7CiAgICAgICAgICAgICAgICBzY29waWZ5KGFkZGVkTm9kZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgbW8ub2JzZXJ2ZShjb250YWluZXIsIHtjaGlsZExpc3Q6IHRydWUsIHN1YnRyZWU6IHRydWV9KTsKICAgICAgICByZXR1cm4gbW87CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEBmaWxlb3ZlcnZpZXcKICAgICAqIEBzdXBwcmVzcyB7Y2hlY2tQcm90b3R5cGFsVHlwZXN9CiAgICAgKiBAbGljZW5zZSBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICAgKiBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZAogICAgICogYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heQogICAgICogYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieQogICAgICogR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUAogICAgICogcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgICovCgogICAgY29uc3QgRElTQUJMRURfQVRUUiA9ICdkaXNhYmxlLXVwZ3JhZGUnOwoKICAgIGNvbnN0IGZpbmRPYnNlcnZlZEF0dHJpYnV0ZXNHZXR0ZXIgPSAoY3RvcikgPT4gewogICAgICB3aGlsZSAoY3RvcikgewogICAgICAgIGNvbnN0IGRlc2MgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKGN0b3IsICdvYnNlcnZlZEF0dHJpYnV0ZXMnKTsKICAgICAgICBpZiAoZGVzYykgewogICAgICAgICAgcmV0dXJuIGRlc2MuZ2V0OwogICAgICAgIH0KICAgICAgICBjdG9yID0gT2JqZWN0LmdldFByb3RvdHlwZU9mKGN0b3IucHJvdG90eXBlKS5jb25zdHJ1Y3RvcjsKICAgICAgfQogICAgICByZXR1cm4gKCkgPT4gW107CiAgICB9OwoKICAgIC8qKgogICAgICogRWxlbWVudCBjbGFzcyBtaXhpbiB0aGF0IGFsbG93cyB0aGUgZWxlbWVudCB0byBib290IHVwIGluIGEgbm9uLWVuYWJsZWQKICAgICAqIHN0YXRlIHdoZW4gdGhlIGBkaXNhYmxlLXVwZ3JhZGVgIGF0dHJpYnV0ZSBpcyBwcmVzZW50LiBUaGlzIG1peGluIGlzCiAgICAgKiBkZXNpZ25lZCB0byBiZSB1c2VkIHdpdGggZWxlbWVudCBjbGFzc2VzIGxpa2UgUG9seW1lckVsZW1lbnQgdGhhdCBwZXJmb3JtCiAgICAgKiBpbml0aWFsIHN0YXJ0dXAgd29yayB3aGVuIHRoZXkgYXJlIGZpcnN0IGNvbm5lY3RlZC4gV2hlbiB0aGUKICAgICAqIGBkaXNhYmxlLXVwZ3JhZGVgIGF0dHJpYnV0ZSBpcyByZW1vdmVkLCBpZiB0aGUgZWxlbWVudCBpcyBjb25uZWN0ZWQsIGl0CiAgICAgKiBib290cyB1cCBhbmQgImVuYWJsZXMiIGFzIGl0IG90aGVyd2lzZSB3b3VsZDsgaWYgaXQgaXMgbm90IGNvbm5lY3RlZCwgdGhlCiAgICAgKiBlbGVtZW50IGJvb3RzIHVwIHdoZW4gaXQgaXMgbmV4dCBjb25uZWN0ZWQuCiAgICAgKgogICAgICogVXNpbmcgYGRpc2FibGUtdXBncmFkZWAgd2l0aCBQb2x5bWVyRWxlbWVudCBwcmV2ZW50cyBhbnkgZGF0YSBwcm9wYWdhdGlvbgogICAgICogdG8gdGhlIGVsZW1lbnQsIGFueSBlbGVtZW50IERPTSBmcm9tIHN0YW1waW5nLCBvciBhbnkgd29yayBkb25lIGluCiAgICAgKiBjb25uZWN0ZWQvZGlzY29ubmN0ZWRDYWxsYmFjayBmcm9tIG9jY3VyaW5nLCBidXQgaXQgZG9lcyBub3QgcHJldmVudCB3b3JrCiAgICAgKiBkb25lIGluIHRoZSBlbGVtZW50IGNvbnN0cnVjdG9yLgogICAgICoKICAgICAqIE5vdGUsIHRoaXMgbWl4aW4gbXVzdCBiZSBhcHBsaWVkIG9uIHRvcCBvZiBhbnkgZWxlbWVudCBjbGFzcyB0aGF0CiAgICAgKiBpdHNlbGYgaW1wbGVtZW50cyBhIGBjb25uZWN0ZWRDYWxsYmFja2Agc28gdGhhdCBpdCBjYW4gY29udHJvbCB0aGUgd29yawogICAgICogZG9uZSBpbiBgY29ubmVjdGVkQ2FsbGJhY2tgLiBGb3IgZXhhbXBsZSwKICAgICAqCiAgICAgKiAgICAgTXlDbGFzcyA9IERpc2FibGVVcGdyYWRlTWl4aW4oY2xhc3MgZXh0ZW5kcyBCYXNlQ2xhc3Mgey4uLn0pOwogICAgICoKICAgICAqIEBtaXhpbkZ1bmN0aW9uCiAgICAgKiBAcG9seW1lcgogICAgICogQGFwcGxpZXNNaXhpbiBFbGVtZW50TWl4aW4KICAgICAqIEB0ZW1wbGF0ZSBUCiAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyBDbGFzcyB0byBhcHBseSBtaXhpbiB0by4KICAgICAqIEByZXR1cm4ge2Z1bmN0aW9uKG5ldzpUKX0gc3VwZXJDbGFzcyB3aXRoIG1peGluIGFwcGxpZWQuCiAgICAgKi8KICAgIGNvbnN0IERpc2FibGVVcGdyYWRlTWl4aW4gPSBkZWR1cGluZ01peGluKChiYXNlKSA9PiB7CiAgICAgIC8qKgogICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfRWxlbWVudE1peGlufQogICAgICAgKiBAZXh0ZW5kcyB7SFRNTEVsZW1lbnR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBjb25zdCBzdXBlckNsYXNzID0gRWxlbWVudE1peGluKGJhc2UpOwoKICAgICAgLy8gV29yayBhcm91bmQgZm9yIGNsb3N1cmUgYnVnICMxMjY5MzQ0NTguIFVzaW5nIGBzdXBlcmAgaW4gYSBwcm9wZXJ0eQogICAgICAvLyBnZXR0ZXIgZG9lcyBub3Qgd29yayBzbyBpbnN0ZWFkIHdlIHNlYXJjaCB0aGUgQmFzZSBwcm90b3R5cGUgZm9yIGFuCiAgICAgIC8vIGltcGxlbWVudGF0aW9uIG9mIG9ic2VydmVkQXR0cmlidXRlcyBzbyB0aGF0IHdlIGNhbiBvdmVycmlkZSBhbmQgY2FsbAogICAgICAvLyB0aGUgYHN1cGVyYCBnZXR0ZXIuIE5vdGUsIHRoaXMgaXMgZG9uZSBvbmUgdGltZSBldmVyIGJlY2F1c2Ugd2UgYXNzdW1lCiAgICAgIC8vIHRoYXQgYEJhc2VgIGlzIGFsd2F5cyBjb21lcyBmcm9tIGBQb2x5bWVyLkxlZ2FjeUVsZW1lbnRNaXhuYC4KICAgICAgbGV0IG9ic2VydmVkQXR0cmlidXRlc0dldHRlciA9IGZpbmRPYnNlcnZlZEF0dHJpYnV0ZXNHZXR0ZXIoc3VwZXJDbGFzcyk7CgogICAgICAvKioKICAgICAgICogQHBvbHltZXIKICAgICAgICogQG1peGluQ2xhc3MKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfRGlzYWJsZVVwZ3JhZGVNaXhpbn0KICAgICAgICovCiAgICAgIGNsYXNzIERpc2FibGVVcGdyYWRlQ2xhc3MgZXh0ZW5kcyBzdXBlckNsYXNzIHsKCiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgLyoqIEB0eXBlIHtib29sZWFufHVuZGVmaW5lZH0gKi8KICAgICAgICAgIHRoaXMuX19pc1VwZ3JhZGVEaXNhYmxlZDsKICAgICAgICB9CgogICAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZWRBdHRyaWJ1dGVzKCkgewogICAgICAgICAgcmV0dXJuIG9ic2VydmVkQXR0cmlidXRlc0dldHRlci5jYWxsKHRoaXMpLmNvbmNhdChESVNBQkxFRF9BVFRSKTsKICAgICAgICB9CgogICAgICAgIC8vIFByZXZlbnQgZWxlbWVudCBmcm9tIGluaXRpYWxpemluZyBwcm9wZXJ0aWVzIHdoZW4gaXQncyB1cGdyYWRlIGRpc2FibGVkLgogICAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgICBfaW5pdGlhbGl6ZVByb3BlcnRpZXMoKSB7CiAgICAgICAgICBpZiAodGhpcy5oYXNBdHRyaWJ1dGUoRElTQUJMRURfQVRUUikpIHsKICAgICAgICAgICAgdGhpcy5fX2lzVXBncmFkZURpc2FibGVkID0gdHJ1ZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHN1cGVyLl9pbml0aWFsaXplUHJvcGVydGllcygpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gUHJldmVudCBlbGVtZW50IGZyb20gZW5hYmxpbmcgcHJvcGVydGllcyB3aGVuIGl0J3MgdXBncmFkZSBkaXNhYmxlZC4KICAgICAgICAvLyBOb3JtYWxseSBvdmVycmlkaW5nIGNvbm5lY3RlZENhbGxiYWNrIHdvdWxkIGJlIGVub3VnaCwgYnV0IGRvbS0qIGVsZW1lbnRzCiAgICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICAgIF9lbmFibGVQcm9wZXJ0aWVzKCkgewogICAgICAgICAgaWYgKCF0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQpIHsKICAgICAgICAgICAgc3VwZXIuX2VuYWJsZVByb3BlcnRpZXMoKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIElmIHRoZSBlbGVtZW50IHN0YXJ0cyB1cGdyYWRlLWRpc2FibGVkIGFuZCBhIHByb3BlcnR5IGlzIHNldCBmb3IKICAgICAgICAvLyB3aGljaCBhbiBhY2Nlc3NvciBleGlzdHMsIHRoZSBkZWZhdWx0IHNob3VsZCBub3QgYmUgYXBwbGllZC4KICAgICAgICAvLyBUaGlzIGFkZGl0aW9uYWwgY2hlY2sgaXMgbmVlZGVkIGJlY2F1c2UgZGVmYXVsdHMgYXJlIGFwcGxpZWQgdmlhCiAgICAgICAgLy8gYF9pbml0aWFsaXplUHJvcGVydGllc2Agd2hpY2ggaXMgY2FsbGVkIGFmdGVyIGluaXRpYWwgcHJvcGVydGllcwogICAgICAgIC8vIGhhdmUgYmVlbiBzZXQgd2hlbiB0aGUgZWxlbWVudCBzdGFydHMgdXBncmFkZS1kaXNhYmxlZC4KICAgICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgICAgX2NhbkFwcGx5UHJvcGVydHlEZWZhdWx0KHByb3BlcnR5KSB7CiAgICAgICAgICByZXR1cm4gc3VwZXIuX2NhbkFwcGx5UHJvcGVydHlEZWZhdWx0KHByb3BlcnR5KSAmJgogICAgICAgICAgICAhKHRoaXMuX19pc1VwZ3JhZGVEaXNhYmxlZCAmJiB0aGlzLl9pc1Byb3BlcnR5UGVuZGluZyhwcm9wZXJ0eSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgQXR0cmlidXRlIG5hbWUuCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSBvbGQgVGhlIHByZXZpb3VzIHZhbHVlIGZvciB0aGUgYXR0cmlidXRlLgogICAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gdmFsdWUgVGhlIG5ldyB2YWx1ZSBmb3IgdGhlIGF0dHJpYnV0ZS4KICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IG5hbWVzcGFjZSBUaGUgWE1MIG5hbWVzcGFjZSBmb3IgdGhlIGF0dHJpYnV0ZS4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGQsIHZhbHVlLCBuYW1lc3BhY2UpIHsKICAgICAgICAgIGlmIChuYW1lID09IERJU0FCTEVEX0FUVFIpIHsKICAgICAgICAgICAgLy8gV2hlbiBkaXNhYmxlLXVwZ3JhZGUgaXMgcmVtb3ZlZCwgaW50aWFsaXplIHByb3BlcnRpZXMgYW5kCiAgICAgICAgICAgIC8vIHByb3Zva2UgY29ubmVjdGVkQ2FsbGJhY2sgaWYgdGhlIGVsZW1lbnQgaXMgYWxyZWFkeSBjb25uZWN0ZWQuCiAgICAgICAgICAgIGlmICh0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQgJiYgdmFsdWUgPT0gbnVsbCkgewogICAgICAgICAgICAgIHN1cGVyLl9pbml0aWFsaXplUHJvcGVydGllcygpOwogICAgICAgICAgICAgIHRoaXMuX19pc1VwZ3JhZGVEaXNhYmxlZCA9IGZhbHNlOwogICAgICAgICAgICAgIGlmICh3cmFwKHRoaXMpLmlzQ29ubmVjdGVkKSB7CiAgICAgICAgICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKAogICAgICAgICAgICAgICAgbmFtZSwgb2xkLCB2YWx1ZSwgLyoqIEB0eXBlIHtudWxsfHN0cmluZ30gKi8gKG5hbWVzcGFjZSkpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gUHJldmVudCBlbGVtZW50IGZyb20gY29ubmVjdGluZyB3aGVuIGl0J3MgdXBncmFkZSBkaXNhYmxlZC4KICAgICAgICAvLyBUaGlzIHByZXZlbnRzIHVzZXIgY29kZSBpbiBgYXR0YWNoZWRgIGZyb20gYmVpbmcgY2FsbGVkLgogICAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICAgIGlmICghdGhpcy5fX2lzVXBncmFkZURpc2FibGVkKSB7CiAgICAgICAgICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBQcmV2ZW50IGVsZW1lbnQgZnJvbSBkaXNjb25uZWN0aW5nIHdoZW4gaXQncyB1cGdyYWRlIGRpc2FibGVkLgogICAgICAgIC8vIFRoaXMgYXZvaWRzIGFsbG93aW5nIHVzZXIgY29kZSBgZGV0YWNoZWRgIGZyb20gYmVpbmcgY2FsbGVkIHdpdGhvdXQgYQogICAgICAgIC8vIHBhaXJlZCBjYWxsIHRvIGBhdHRhY2hlZGAuCiAgICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICAgIGRpc2Nvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICAgaWYgKCF0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQpIHsKICAgICAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICB9CgogICAgICByZXR1cm4gRGlzYWJsZVVwZ3JhZGVDbGFzczsKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgRElTQUJMRURfQVRUUiQxID0gJ2Rpc2FibGUtdXBncmFkZSc7CgogICAgbGV0IHN0eWxlSW50ZXJmYWNlID0gd2luZG93LlNoYWR5Q1NTOwoKICAgIC8qKgogICAgICogRWxlbWVudCBjbGFzcyBtaXhpbiB0aGF0IHByb3ZpZGVzIFBvbHltZXIncyAibGVnYWN5IiBBUEkgaW50ZW5kZWQgdG8gYmUKICAgICAqIGJhY2t3YXJkLWNvbXBhdGlibGUgdG8gdGhlIGdyZWF0ZXN0IGV4dGVudCBwb3NzaWJsZSB3aXRoIHRoZSBBUEkKICAgICAqIGZvdW5kIG9uIHRoZSBQb2x5bWVyIDEueCBgUG9seW1lci5CYXNlYCBwcm90b3R5cGUgYXBwbGllZCB0byBhbGwgZWxlbWVudHMKICAgICAqIGRlZmluZWQgdXNpbmcgdGhlIGBQb2x5bWVyKHsuLi59KWAgZnVuY3Rpb24uCiAgICAgKgogICAgICogQG1peGluRnVuY3Rpb24KICAgICAqIEBwb2x5bWVyCiAgICAgKiBAYXBwbGllc01peGluIEVsZW1lbnRNaXhpbgogICAgICogQGFwcGxpZXNNaXhpbiBHZXN0dXJlRXZlbnRMaXN0ZW5lcnMKICAgICAqIEBhcHBsaWVzTWl4aW4gRGlyTWl4aW4KICAgICAqIEBwcm9wZXJ0eSBpc0F0dGFjaGVkIHtib29sZWFufSBTZXQgdG8gYHRydWVgIGluIHRoaXMgZWxlbWVudCdzCiAgICAgKiAgIGBjb25uZWN0ZWRDYWxsYmFja2AgYW5kIGBmYWxzZWAgaW4gYGRpc2Nvbm5lY3RlZENhbGxiYWNrYAogICAgICogQHN1bW1hcnkgRWxlbWVudCBjbGFzcyBtaXhpbiB0aGF0IHByb3ZpZGVzIFBvbHltZXIncyAibGVnYWN5IiBBUEkKICAgICAqLwogICAgY29uc3QgTGVnYWN5RWxlbWVudE1peGluID0gZGVkdXBpbmdNaXhpbigoYmFzZSkgPT4gewoKICAgICAgLy8gVE9ETyhrc2NoYWFmKTogTm90ZSwgdGhlIGBAaW1wbGVtZW50cyB7UG9seW1lcl9EaXJNaXhpbn1gIGlzIHJlcXVpcmVkIGhlcmUKICAgICAgLy8gKHJhdGhlciB0aGFuIG9uIGxlZ2FjeUVsZW1lbnRCYXNlKSBmb3IgdW5rbm93biByZWFzb25zLgogICAgICAvKioKICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX0VsZW1lbnRNaXhpbn0KICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfR2VzdHVyZUV2ZW50TGlzdGVuZXJzfQogICAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9EaXJNaXhpbn0KICAgICAgICogQGV4dGVuZHMge0hUTUxFbGVtZW50fQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgY29uc3QgR2VzdHVyZXNFbGVtZW50ID0gR2VzdHVyZUV2ZW50TGlzdGVuZXJzKEVsZW1lbnRNaXhpbihiYXNlKSk7CgogICAgICAvLyBOb3RlLCB0aGUgRGlyTWl4aW4gZG9lcyBub3RoaW5nIGlmIGNzcyBpcyBidWlsdCBzbyBhdm9pZCBpbmNsdWRpbmcgaXQKICAgICAgLy8gaW4gdGhhdCBjYXNlLgoKICAgICAgLyoqCiAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgKiBAZXh0ZW5kcyB7R2VzdHVyZXNFbGVtZW50fQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgY29uc3QgbGVnYWN5RWxlbWVudEJhc2UgPSBidWlsdENTUyA/IEdlc3R1cmVzRWxlbWVudCA6CiAgICAgICAgRGlyTWl4aW4oR2VzdHVyZXNFbGVtZW50KTsKCiAgICAgIGNvbnN0IG9ic2VydmVkQXR0cmlidXRlc0dldHRlciA9IGZpbmRPYnNlcnZlZEF0dHJpYnV0ZXNHZXR0ZXIobGVnYWN5RWxlbWVudEJhc2UpOwoKICAgICAgLyoqCiAgICAgICAqIE1hcCBvZiBzaW1wbGUgbmFtZXMgdG8gdG91Y2ggYWN0aW9uIG5hbWVzCiAgICAgICAqIEBkaWN0CiAgICAgICAqLwogICAgICBjb25zdCBESVJFQ1RJT05fTUFQID0gewogICAgICAgICd4JzogJ3Bhbi14JywKICAgICAgICAneSc6ICdwYW4teScsCiAgICAgICAgJ25vbmUnOiAnbm9uZScsCiAgICAgICAgJ2FsbCc6ICdhdXRvJwogICAgICB9OwoKICAgICAgLyoqCiAgICAgICAqIEBwb2x5bWVyCiAgICAgICAqIEBtaXhpbkNsYXNzCiAgICAgICAqIEBleHRlbmRzIHtsZWdhY3lFbGVtZW50QmFzZX0KICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfTGVnYWN5RWxlbWVudE1peGlufQogICAgICAgKiBAdW5yZXN0cmljdGVkCiAgICAgICAqLwogICAgICBjbGFzcyBMZWdhY3lFbGVtZW50IGV4dGVuZHMgbGVnYWN5RWxlbWVudEJhc2UgewoKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgIHN1cGVyKCk7CiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW59ICovCiAgICAgICAgICB0aGlzLmlzQXR0YWNoZWQ7CiAgICAgICAgICAvKiogQHR5cGUgez9XZWFrTWFwPCFFbGVtZW50LCAhT2JqZWN0PHN0cmluZywgIUZ1bmN0aW9uPj59ICovCiAgICAgICAgICB0aGlzLl9fYm91bmRMaXN0ZW5lcnM7CiAgICAgICAgICAvKiogQHR5cGUgez9PYmplY3Q8c3RyaW5nLCA/RnVuY3Rpb24+fSAqLwogICAgICAgICAgdGhpcy5fZGVib3VuY2VyczsKICAgICAgICAgIC8vIE5PVEU6IElubGluZWQgZm9yIHBlcmYgZnJvbSB2ZXJzaW9uIG9mIERpc2FibGVVcGdyYWRlTWl4aW4uCiAgICAgICAgICAvKiogQHR5cGUge2Jvb2xlYW58dW5kZWZpbmVkfSAqLwogICAgICAgICAgdGhpcy5fX2lzVXBncmFkZURpc2FibGVkOwogICAgICAgICAgLyoqIEB0eXBlIHtib29sZWFufHVuZGVmaW5lZH0gKi8KICAgICAgICAgIHRoaXMuX19uZWVkc0F0dHJpYnV0ZXNBdENvbm5lY3RlZDsKICAgICAgICAgIC8qKiBAdHlwZSB7Ym9vbGVhbnx1bmRlZmluZWR9ICovCiAgICAgICAgICB0aGlzLl9sZWdhY3lGb3JjZU9ic2VydmVkQXR0cmlidXRlczsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEZvcndhcmRzIGBpbXBvcnRNZXRhYCBmcm9tIHRoZSBwcm90b3R5cGUgKGkuZS4gZnJvbSB0aGUgaW5mbyBvYmplY3QKICAgICAgICAgKiBwYXNzZWQgdG8gYFBvbHltZXIoey4uLn0pYCkgdG8gdGhlIHN0YXRpYyBBUEkuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHshT2JqZWN0fSBUaGUgYGltcG9ydC5tZXRhYCBvYmplY3Qgc2V0IG9uIHRoZSBwcm90b3R5cGUKICAgICAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBgdGhpc2AgaXMgYWx3YXlzIGluIHRoZSBpbnN0YW5jZSBpbgogICAgICAgICAqICBjbG9zdXJlIGZvciBzb21lIHJlYXNvbiBldmVuIGluIGEgc3RhdGljIG1ldGhvZCwgcmF0aGVyIHRoYW4gdGhlIGNsYXNzCiAgICAgICAgICogQG5vY29sbGFwc2UKICAgICAgICAgKi8KICAgICAgICBzdGF0aWMgZ2V0IGltcG9ydE1ldGEoKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5wcm90b3R5cGUuaW1wb3J0TWV0YTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIExlZ2FjeSBjYWxsYmFjayBjYWxsZWQgZHVyaW5nIHRoZSBgY29uc3RydWN0b3JgLCBmb3Igb3ZlcnJpZGluZwogICAgICAgICAqIGJ5IHRoZSB1c2VyLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgY3JlYXRlZCgpIHt9CgogICAgICAgIC8qKgogICAgICAgICAqIFByb2Nlc3NlcyBhbiBhdHRyaWJ1dGUgcmVhY3Rpb24gd2hlbiB0aGUgYGxlZ2FjeU5vT2JzZXJ2ZWRBdHRyaWJ1dGVzYAogICAgICAgICAqIHNldHRpbmcgaXMgaW4gdXNlLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgYXR0cmlidXRlIHRoYXQgY2hhbmdlZAogICAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gb2xkIE9sZCBhdHRyaWJ1dGUgdmFsdWUKICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlIE5ldyBhdHRyaWJ1dGUgdmFsdWUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIF9fYXR0cmlidXRlUmVhY3Rpb24obmFtZSwgb2xkLCB2YWx1ZSkgewogICAgICAgICAgaWYgKCh0aGlzLl9fZGF0YUF0dHJpYnV0ZXMgJiYgdGhpcy5fX2RhdGFBdHRyaWJ1dGVzW25hbWVdKSB8fCBuYW1lID09PSBESVNBQkxFRF9BVFRSJDEpIHsKICAgICAgICAgICAgdGhpcy5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sobmFtZSwgb2xkLCB2YWx1ZSwgbnVsbCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSB2YWx1ZSBvZiBhbiBhdHRyaWJ1dGUuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgVGhlIG5hbWUgb2YgdGhlIGF0dHJpYnV0ZSB0byBjaGFuZ2UuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd8bnVtYmVyfGJvb2xlYW58IVRydXN0ZWRIVE1MfCFUcnVzdGVkU2NyaXB0VVJMfCFUcnVzdGVkVVJMfSB2YWx1ZSBUaGUgbmV3IGF0dHJpYnV0ZSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBzZXRBdHRyaWJ1dGUobmFtZSwgdmFsdWUpIHsKICAgICAgICAgIGlmIChsZWdhY3lOb09ic2VydmVkQXR0cmlidXRlcyAmJiAhdGhpcy5fbGVnYWN5Rm9yY2VPYnNlcnZlZEF0dHJpYnV0ZXMpIHsKICAgICAgICAgICAgY29uc3Qgb2xkVmFsdWUgPSB0aGlzLmdldEF0dHJpYnV0ZShuYW1lKTsKICAgICAgICAgICAgc3VwZXIuc2V0QXR0cmlidXRlKG5hbWUsIHZhbHVlKTsKICAgICAgICAgICAgLy8gdmFsdWUgY29lcmNlZCB0byBTdHJpbmcgZm9yIGNsb3N1cmUncyBiZW5lZml0CiAgICAgICAgICAgIHRoaXMuX19hdHRyaWJ1dGVSZWFjdGlvbihuYW1lLCBvbGRWYWx1ZSwgU3RyaW5nKHZhbHVlKSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBzdXBlci5zZXRBdHRyaWJ1dGUobmFtZSwgdmFsdWUpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbiBhdHRyaWJ1dGUuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgVGhlIG5hbWUgb2YgdGhlIGF0dHJpYnV0ZSB0byByZW1vdmUuCiAgICAgICAgICovCiAgICAgICAgcmVtb3ZlQXR0cmlidXRlKG5hbWUpIHsKICAgICAgICAgIGlmIChsZWdhY3lOb09ic2VydmVkQXR0cmlidXRlcyAmJiAhdGhpcy5fbGVnYWN5Rm9yY2VPYnNlcnZlZEF0dHJpYnV0ZXMpIHsKICAgICAgICAgICAgY29uc3Qgb2xkVmFsdWUgPSB0aGlzLmdldEF0dHJpYnV0ZShuYW1lKTsKICAgICAgICAgICAgc3VwZXIucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgICAgICB0aGlzLl9fYXR0cmlidXRlUmVhY3Rpb24obmFtZSwgb2xkVmFsdWUsIG51bGwpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc3VwZXIucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gTk9URTogSW5saW5lZCBmb3IgcGVyZiBmcm9tIHZlcnNpb24gb2YgRGlzYWJsZVVwZ3JhZGVNaXhpbi4KICAgICAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHsKICAgICAgICAgIGlmIChsZWdhY3lOb09ic2VydmVkQXR0cmlidXRlcyAmJiAhdGhpcy5wcm90b3R5cGUuX2xlZ2FjeUZvcmNlT2JzZXJ2ZWRBdHRyaWJ1dGVzKSB7CiAgICAgICAgICAgIC8vIEVuc3VyZSB0aGlzIGVsZW1lbnQgaXMgcHJvcGVydHkgcmVnaXN0ZXJlZCB3aXRoIHRoZSB0ZWxlbWV0cnkgc3lzdGVtLgogICAgICAgICAgICBpZiAoIXRoaXMuaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX19vYnNlcnZlZEF0dHJpYnV0ZXMnLCB0aGlzKSkpIHsKICAgICAgICAgICAgICB0aGlzLl9fb2JzZXJ2ZWRBdHRyaWJ1dGVzID0gW107CiAgICAgICAgICAgICAgcmVnaXN0ZXIodGhpcy5wcm90b3R5cGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9fb2JzZXJ2ZWRBdHRyaWJ1dGVzOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcmV0dXJuIG9ic2VydmVkQXR0cmlidXRlc0dldHRlci5jYWxsKHRoaXMpLmNvbmNhdChESVNBQkxFRF9BVFRSJDEpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gTk9URTogSW5saW5lZCBmb3IgcGVyZiBmcm9tIHZlcnNpb24gb2YgRGlzYWJsZVVwZ3JhZGVNaXhpbi4KICAgICAgICAvLyBQcmV2ZW50IGVsZW1lbnQgZnJvbSBlbmFibGluZyBwcm9wZXJ0aWVzIHdoZW4gaXQncyB1cGdyYWRlIGRpc2FibGVkLgogICAgICAgIC8vIE5vcm1hbGx5IG92ZXJyaWRpbmcgY29ubmVjdGVkQ2FsbGJhY2sgd291bGQgYmUgZW5vdWdoLCBidXQgZG9tLSogZWxlbWVudHMKICAgICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgICAgX2VuYWJsZVByb3BlcnRpZXMoKSB7CiAgICAgICAgICBpZiAoIXRoaXMuX19pc1VwZ3JhZGVEaXNhYmxlZCkgewogICAgICAgICAgICBzdXBlci5fZW5hYmxlUHJvcGVydGllcygpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gTk9URTogSW5saW5lZCBmb3IgcGVyZiBmcm9tIHZlcnNpb24gb2YgRGlzYWJsZVVwZ3JhZGVNaXhpbi4KICAgICAgICAvLyBJZiB0aGUgZWxlbWVudCBzdGFydHMgdXBncmFkZS1kaXNhYmxlZCBhbmQgYSBwcm9wZXJ0eSBpcyBzZXQgZm9yCiAgICAgICAgLy8gd2hpY2ggYW4gYWNjZXNzb3IgZXhpc3RzLCB0aGUgZGVmYXVsdCBzaG91bGQgbm90IGJlIGFwcGxpZWQuCiAgICAgICAgLy8gVGhpcyBhZGRpdGlvbmFsIGNoZWNrIGlzIG5lZWRlZCBiZWNhdXNlIGRlZmF1bHRzIGFyZSBhcHBsaWVkIHZpYQogICAgICAgIC8vIGBfaW5pdGlhbGl6ZVByb3BlcnRpZXNgIHdoaWNoIGlzIGNhbGxlZCBhZnRlciBpbml0aWFsIHByb3BlcnRpZXMKICAgICAgICAvLyBoYXZlIGJlZW4gc2V0IHdoZW4gdGhlIGVsZW1lbnQgc3RhcnRzIHVwZ3JhZGUtZGlzYWJsZWQuCiAgICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICAgIF9jYW5BcHBseVByb3BlcnR5RGVmYXVsdChwcm9wZXJ0eSkgewogICAgICAgICAgcmV0dXJuIHN1cGVyLl9jYW5BcHBseVByb3BlcnR5RGVmYXVsdChwcm9wZXJ0eSkgJiYKICAgICAgICAgICAgISh0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQgJiYgdGhpcy5faXNQcm9wZXJ0eVBlbmRpbmcocHJvcGVydHkpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFByb3ZpZGVzIGFuIGltcGxlbWVudGF0aW9uIG9mIGBjb25uZWN0ZWRDYWxsYmFja2AKICAgICAgICAgKiB3aGljaCBhZGRzIFBvbHltZXIgbGVnYWN5IEFQSSdzIGBhdHRhY2hlZGAgbWV0aG9kLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgICBpZiAodGhpcy5fX25lZWRzQXR0cmlidXRlc0F0Q29ubmVjdGVkKSB7CiAgICAgICAgICAgIHRoaXMuX3Rha2VBdHRyaWJ1dGVzKCk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBOT1RFOiBJbmxpbmVkIGZvciBwZXJmIGZyb20gdmVyc2lvbiBvZiBEaXNhYmxlVXBncmFkZU1peGluLgogICAgICAgICAgaWYgKCF0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQpIHsKICAgICAgICAgICAgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICAgICAgdGhpcy5pc0F0dGFjaGVkID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5hdHRhY2hlZCgpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogTGVnYWN5IGNhbGxiYWNrIGNhbGxlZCBkdXJpbmcgYGNvbm5lY3RlZENhbGxiYWNrYCwgZm9yIG92ZXJyaWRpbmcKICAgICAgICAgKiBieSB0aGUgdXNlci4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGF0dGFjaGVkKCkge30KCiAgICAgICAgLyoqCiAgICAgICAgICogUHJvdmlkZXMgYW4gaW1wbGVtZW50YXRpb24gb2YgYGRpc2Nvbm5lY3RlZENhbGxiYWNrYAogICAgICAgICAqIHdoaWNoIGFkZHMgUG9seW1lciBsZWdhY3kgQVBJJ3MgYGRldGFjaGVkYCBtZXRob2QuCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBkaXNjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICAgIC8vIE5PVEU6IElubGluZWQgZm9yIHBlcmYgZnJvbSB2ZXJzaW9uIG9mIERpc2FibGVVcGdyYWRlTWl4aW4uCiAgICAgICAgICBpZiAoIXRoaXMuX19pc1VwZ3JhZGVEaXNhYmxlZCkgewogICAgICAgICAgICBzdXBlci5kaXNjb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICAgICB0aGlzLmlzQXR0YWNoZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5kZXRhY2hlZCgpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogTGVnYWN5IGNhbGxiYWNrIGNhbGxlZCBkdXJpbmcgYGRpc2Nvbm5lY3RlZENhbGxiYWNrYCwgZm9yIG92ZXJyaWRpbmcKICAgICAgICAgKiBieSB0aGUgdXNlci4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGRldGFjaGVkKCkge30KCiAgICAgICAgLyoqCiAgICAgICAgICogUHJvdmlkZXMgYW4gb3ZlcnJpZGUgaW1wbGVtZW50YXRpb24gb2YgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AKICAgICAgICAgKiB3aGljaCBhZGRzIHRoZSBQb2x5bWVyIGxlZ2FjeSBBUEkncyBgYXR0cmlidXRlQ2hhbmdlZGAgbWV0aG9kLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgYXR0cmlidXRlLgogICAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gb2xkIE9sZCB2YWx1ZSBvZiBhdHRyaWJ1dGUuCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSB2YWx1ZSBDdXJyZW50IHZhbHVlIG9mIGF0dHJpYnV0ZS4KICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IG5hbWVzcGFjZSBBdHRyaWJ1dGUgbmFtZXNwYWNlLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZCwgdmFsdWUsIG5hbWVzcGFjZSkgewogICAgICAgICAgaWYgKG9sZCAhPT0gdmFsdWUpIHsKICAgICAgICAgICAgLy8gTk9URTogSW5saW5lZCBmb3IgcGVyZiBmcm9tIHZlcnNpb24gb2YgRGlzYWJsZVVwZ3JhZGVNaXhpbi4KICAgICAgICAgICAgaWYgKG5hbWUgPT0gRElTQUJMRURfQVRUUiQxKSB7CiAgICAgICAgICAgICAgLy8gV2hlbiBkaXNhYmxlLXVwZ3JhZGUgaXMgcmVtb3ZlZCwgaW50aWFsaXplIHByb3BlcnRpZXMgYW5kCiAgICAgICAgICAgICAgLy8gcHJvdm9rZSBjb25uZWN0ZWRDYWxsYmFjayBpZiB0aGUgZWxlbWVudCBpcyBhbHJlYWR5IGNvbm5lY3RlZC4KICAgICAgICAgICAgICBpZiAodGhpcy5fX2lzVXBncmFkZURpc2FibGVkICYmIHZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2luaXRpYWxpemVQcm9wZXJ0aWVzKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9faXNVcGdyYWRlRGlzYWJsZWQgPSBmYWxzZTsKICAgICAgICAgICAgICAgIGlmICh3cmFwKHRoaXMpLmlzQ29ubmVjdGVkKSB7CiAgICAgICAgICAgICAgICAgIHRoaXMuY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZCwgdmFsdWUsIG5hbWVzcGFjZSk7CiAgICAgICAgICAgICAgdGhpcy5hdHRyaWJ1dGVDaGFuZ2VkKG5hbWUsIG9sZCwgdmFsdWUpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBMZWdhY3kgY2FsbGJhY2sgY2FsbGVkIGR1cmluZyBgYXR0cmlidXRlQ2hhbmdlZENoYWxsYmFja2AsIGZvciBvdmVycmlkaW5nCiAgICAgICAgICogYnkgdGhlIHVzZXIuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgTmFtZSBvZiBhdHRyaWJ1dGUuCiAgICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSBvbGQgT2xkIHZhbHVlIG9mIGF0dHJpYnV0ZS4KICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlIEN1cnJlbnQgdmFsdWUgb2YgYXR0cmlidXRlLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgYXR0cmlidXRlQ2hhbmdlZChuYW1lLCBvbGQsIHZhbHVlKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXVudXNlZC12YXJzCgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyB0aGUgZGVmYXVsdCBgUG9seW1lci5Qcm9wZXJ0eUVmZmVjdHNgIGltcGxlbWVudGF0aW9uIHRvCiAgICAgICAgICogYWRkIHN1cHBvcnQgZm9yIGNsYXNzIGluaXRpYWxpemF0aW9uIHZpYSB0aGUgYF9yZWdpc3RlcmVkYCBjYWxsYmFjay4KICAgICAgICAgKiBUaGlzIGlzIGNhbGxlZCBvbmx5IHdoZW4gdGhlIGZpcnN0IGluc3RhbmNlIG9mIHRoZSBlbGVtZW50IGlzIGNyZWF0ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfQogICAgICAgICAqLwogICAgICAgIF9pbml0aWFsaXplUHJvcGVydGllcygpIHsKICAgICAgICAgIC8vIE5PVEU6IElubGluZWQgZm9yIHBlcmYgZnJvbSB2ZXJzaW9uIG9mIERpc2FibGVVcGdyYWRlTWl4aW4uCiAgICAgICAgICAvLyBPbmx5IGF1dG8tdXNlIGRpc2FibGUtdXBncmFkZSBpZiBsZWdhY3lPcHRpbWl6YXRpb25zIGlzIHNldC4KICAgICAgICAgIGlmIChsZWdhY3lPcHRpbWl6YXRpb25zICYmIHRoaXMuaGFzQXR0cmlidXRlKERJU0FCTEVEX0FUVFIkMSkpIHsKICAgICAgICAgICAgdGhpcy5fX2lzVXBncmFkZURpc2FibGVkID0gdHJ1ZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGxldCBwcm90byA9IE9iamVjdC5nZXRQcm90b3R5cGVPZih0aGlzKTsKICAgICAgICAgICAgaWYgKCFwcm90by5oYXNPd25Qcm9wZXJ0eShKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdfX2hhc1JlZ2lzdGVyRmluaXNoZWQnLCBwcm90bykpKSB7CiAgICAgICAgICAgICAgdGhpcy5fcmVnaXN0ZXJlZCgpOwogICAgICAgICAgICAgIC8vIGJhY2tzdG9wIGluIGNhc2UgdGhlIGBfcmVnaXN0ZXJlZGAgaW1wbGVtZW50YXRpb24gZG9lcyBub3Qgc2V0IHRoaXMKICAgICAgICAgICAgICBwcm90by5fX2hhc1JlZ2lzdGVyRmluaXNoZWQgPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHN1cGVyLl9pbml0aWFsaXplUHJvcGVydGllcygpOwogICAgICAgICAgICB0aGlzLnJvb3QgPSAvKiogQHR5cGUge0hUTUxFbGVtZW50fSAqLyh0aGlzKTsKICAgICAgICAgICAgdGhpcy5jcmVhdGVkKCk7CiAgICAgICAgICAgIC8vIFB1bGwgYWxsIGF0dHJpYnV0ZSB2YWx1ZXMgMXggaWYgYGxlZ2FjeU5vT2JzZXJ2ZWRBdHRyaWJ1dGVzYCBpcyBzZXQuCiAgICAgICAgICAgIGlmIChsZWdhY3lOb09ic2VydmVkQXR0cmlidXRlcyAmJiAhdGhpcy5fbGVnYWN5Rm9yY2VPYnNlcnZlZEF0dHJpYnV0ZXMpIHsKICAgICAgICAgICAgICBpZiAodGhpcy5oYXNBdHRyaWJ1dGVzKCkpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3Rha2VBdHRyaWJ1dGVzKCk7CiAgICAgICAgICAgICAgLy8gRWxlbWVudCBjcmVhdGVkIGZyb20gc2NyYXRjaCBvciBwYXJzZXIgZ2VuZXJhdGVkCiAgICAgICAgICAgICAgfSBlbHNlIGlmICghdGhpcy5wYXJlbnROb2RlKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9fbmVlZHNBdHRyaWJ1dGVzQXRDb25uZWN0ZWQgPSB0cnVlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBFbnN1cmUgbGlzdGVuZXJzIGFyZSBhcHBsaWVkIGltbWVkaWF0ZWx5IHNvIHRoYXQgdGhleSBhcmUKICAgICAgICAgICAgLy8gYWRkZWQgYmVmb3JlIGRlY2xhcmF0aXZlIGV2ZW50IGxpc3RlbmVycy4gVGhpcyBhbGxvd3MgYW4gZWxlbWVudCB0bwogICAgICAgICAgICAvLyBkZWNvcmF0ZSBpdHNlbGYgdmlhIGFuIGV2ZW50IHByaW9yIHRvIGFueSBkZWNsYXJhdGl2ZSBsaXN0ZW5lcnMKICAgICAgICAgICAgLy8gc2VlaW5nIHRoZSBldmVudC4gTm90ZSwgdGhpcyBlbnN1cmVzIGNvbXBhdGliaWxpdHkgd2l0aCAxLnggb3JkZXJpbmcuCiAgICAgICAgICAgIHRoaXMuX2FwcGx5TGlzdGVuZXJzKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBfdGFrZUF0dHJpYnV0ZXMoKSB7CiAgICAgICAgICBjb25zdCBhID0gdGhpcy5hdHRyaWJ1dGVzOwogICAgICAgICAgZm9yIChsZXQgaT0wLCBsPWEubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgICAgIGNvbnN0IGF0dHIgPSBhW2ldOwogICAgICAgICAgICB0aGlzLl9fYXR0cmlidXRlUmVhY3Rpb24oYXR0ci5uYW1lLCBudWxsLCBhdHRyLnZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbGxlZCBhdXRvbWF0aWNhbGx5IHdoZW4gYW4gZWxlbWVudCBpcyBpbml0aWFsaXppbmcuCiAgICAgICAgICogVXNlcnMgbWF5IG92ZXJyaWRlIHRoaXMgbWV0aG9kIHRvIHBlcmZvcm0gY2xhc3MgcmVnaXN0cmF0aW9uIHRpbWUKICAgICAgICAgKiB3b3JrLiBUaGUgaW1wbGVtZW50YXRpb24gc2hvdWxkIGVuc3VyZSB0aGUgd29yayBpcyBwZXJmb3JtZWQKICAgICAgICAgKiBvbmx5IG9uY2UgZm9yIHRoZSBjbGFzcy4KICAgICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfcmVnaXN0ZXJlZCgpIHt9CgogICAgICAgIC8qKgogICAgICAgICAqIE92ZXJyaWRlcyB0aGUgZGVmYXVsdCBgUG9seW1lci5Qcm9wZXJ0eUVmZmVjdHNgIGltcGxlbWVudGF0aW9uIHRvCiAgICAgICAgICogYWRkIHN1cHBvcnQgZm9yIGluc3RhbGxpbmcgYGhvc3RBdHRyaWJ1dGVzYCBhbmQgYGxpc3RlbmVyc2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgdGhpcy5fZW5zdXJlQXR0cmlidXRlcygpOwogICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEVuc3VyZXMgYW4gZWxlbWVudCBoYXMgcmVxdWlyZWQgYXR0cmlidXRlcy4gQ2FsbGVkIHdoZW4gdGhlIGVsZW1lbnQKICAgICAgICAgKiBpcyBiZWluZyByZWFkaWVkIHZpYSBgcmVhZHlgLiBVc2VycyBzaG91bGQgb3ZlcnJpZGUgdG8gc2V0IHRoZQogICAgICAgICAqIGVsZW1lbnQncyByZXF1aXJlZCBhdHRyaWJ1dGVzLiBUaGUgaW1wbGVtZW50YXRpb24gc2hvdWxkIGJlIHN1cmUKICAgICAgICAgKiB0byBjaGVjayBhbmQgbm90IG92ZXJyaWRlIGV4aXN0aW5nIGF0dHJpYnV0ZXMgYWRkZWQgYnkKICAgICAgICAgKiB0aGUgdXNlciBvZiB0aGUgZWxlbWVudC4gVHlwaWNhbGx5LCBzZXR0aW5nIGF0dHJpYnV0ZXMgc2hvdWxkIGJlIGxlZnQKICAgICAgICAgKiB0byB0aGUgZWxlbWVudCB1c2VyIGFuZCBub3QgZG9uZSBoZXJlOyByZWFzb25hYmxlIGV4Y2VwdGlvbnMgaW5jbHVkZQogICAgICAgICAqIHNldHRpbmcgYXJpYSByb2xlcyBhbmQgZm9jdXNhYmlsaXR5LgogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9lbnN1cmVBdHRyaWJ1dGVzKCkge30KCiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBlbGVtZW50IGV2ZW50IGxpc3RlbmVycy4gQ2FsbGVkIHdoZW4gdGhlIGVsZW1lbnQKICAgICAgICAgKiBpcyBiZWluZyByZWFkaWVkIHZpYSBgcmVhZHlgLiBVc2VycyBzaG91bGQgb3ZlcnJpZGUgdG8KICAgICAgICAgKiBhZGQgYW55IHJlcXVpcmVkIGVsZW1lbnQgZXZlbnQgbGlzdGVuZXJzLgogICAgICAgICAqIEluIHBlcmZvcm1hbmNlIGNyaXRpY2FsIGVsZW1lbnRzLCB0aGUgd29yayBkb25lIGhlcmUgc2hvdWxkIGJlIGtlcHQKICAgICAgICAgKiB0byBhIG1pbmltdW0gc2luY2UgaXQgaXMgZG9uZSBiZWZvcmUgdGhlIGVsZW1lbnQgaXMgcmVuZGVyZWQuIEluCiAgICAgICAgICogdGhlc2UgZWxlbWVudHMsIGNvbnNpZGVyIGFkZGluZyBsaXN0ZW5lcnMgYXN5bmNocm9ub3VzbHkgc28gYXMgbm90IHRvCiAgICAgICAgICogYmxvY2sgcmVuZGVyLgogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9hcHBseUxpc3RlbmVycygpIHt9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGEgdHlwZWQgSmF2YVNjcmlwdCB2YWx1ZSB0byBhIHN0cmluZy4KICAgICAgICAgKgogICAgICAgICAqIE5vdGUgdGhpcyBtZXRob2QgaXMgcHJvdmlkZWQgYXMgYmFja3dhcmQtY29tcGF0aWJsZSBsZWdhY3kgQVBJCiAgICAgICAgICogb25seS4gIEl0IGlzIG5vdCBkaXJlY3RseSBjYWxsZWQgYnkgYW55IFBvbHltZXIgZmVhdHVyZXMuIFRvIGN1c3RvbWl6ZQogICAgICAgICAqIGhvdyBwcm9wZXJ0aWVzIGFyZSBzZXJpYWxpemVkIHRvIGF0dHJpYnV0ZXMgZm9yIGF0dHJpYnV0ZSBiaW5kaW5ncyBhbmQKICAgICAgICAgKiBgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlYCBwcm9wZXJ0aWVzIGFzIHdlbGwgYXMgdGhpcyBtZXRob2QsIG92ZXJyaWRlCiAgICAgICAgICogdGhlIGBfc2VyaWFsaXplVmFsdWVgIG1ldGhvZCBwcm92aWRlZCBieSBgUG9seW1lci5Qcm9wZXJ0eUFjY2Vzc29yc2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIGRlc2VyaWFsaXplCiAgICAgICAgICogQHJldHVybiB7c3RyaW5nIHwgdW5kZWZpbmVkfSBTZXJpYWxpemVkIHZhbHVlCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgc2VyaWFsaXplKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5fc2VyaWFsaXplVmFsdWUodmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVydHMgYSBzdHJpbmcgdG8gYSB0eXBlZCBKYXZhU2NyaXB0IHZhbHVlLgogICAgICAgICAqCiAgICAgICAgICogTm90ZSB0aGlzIG1ldGhvZCBpcyBwcm92aWRlZCBhcyBiYWNrd2FyZC1jb21wYXRpYmxlIGxlZ2FjeSBBUEkKICAgICAgICAgKiBvbmx5LiAgSXQgaXMgbm90IGRpcmVjdGx5IGNhbGxlZCBieSBhbnkgUG9seW1lciBmZWF0dXJlcy4gIFRvIGN1c3RvbWl6ZQogICAgICAgICAqIGhvdyBhdHRyaWJ1dGVzIGFyZSBkZXNlcmlhbGl6ZWQgdG8gcHJvcGVydGllcyBmb3IgaW4KICAgICAgICAgKiBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCwgb3ZlcnJpZGUgYF9kZXNlcmlhbGl6ZVZhbHVlYCBtZXRob2QKICAgICAgICAgKiBwcm92aWRlZCBieSBgUG9seW1lci5Qcm9wZXJ0eUFjY2Vzc29yc2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdmFsdWUgU3RyaW5nIHRvIGRlc2VyaWFsaXplCiAgICAgICAgICogQHBhcmFtIHsqfSB0eXBlIFR5cGUgdG8gZGVzZXJpYWxpemUgdGhlIHN0cmluZyB0bwogICAgICAgICAqIEByZXR1cm4geyp9IFJldHVybnMgdGhlIGRlc2VyaWFsaXplZCB2YWx1ZSBpbiB0aGUgYHR5cGVgIGdpdmVuLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGRlc2VyaWFsaXplKHZhbHVlLCB0eXBlKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5fZGVzZXJpYWxpemVWYWx1ZSh2YWx1ZSwgdHlwZSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZXJpYWxpemVzIGEgcHJvcGVydHkgdG8gaXRzIGFzc29jaWF0ZWQgYXR0cmlidXRlLgogICAgICAgICAqCiAgICAgICAgICogTm90ZSB0aGlzIG1ldGhvZCBpcyBwcm92aWRlZCBhcyBiYWNrd2FyZC1jb21wYXRpYmxlIGxlZ2FjeSBBUEkKICAgICAgICAgKiBvbmx5LiAgSXQgaXMgbm90IGRpcmVjdGx5IGNhbGxlZCBieSBhbnkgUG9seW1lciBmZWF0dXJlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lIHRvIHJlZmxlY3QuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBhdHRyaWJ1dGUgQXR0cmlidXRlIG5hbWUgdG8gcmVmbGVjdC4KICAgICAgICAgKiBAcGFyYW0geyo9fSB2YWx1ZSBQcm9wZXJ0eSB2YWx1ZSB0byByZWZsZWN0LgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgcmVmbGVjdFByb3BlcnR5VG9BdHRyaWJ1dGUocHJvcGVydHksIGF0dHJpYnV0ZSwgdmFsdWUpIHsKICAgICAgICAgIHRoaXMuX3Byb3BlcnR5VG9BdHRyaWJ1dGUocHJvcGVydHksIGF0dHJpYnV0ZSwgdmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyBhIHR5cGVkIHZhbHVlIHRvIGFuIEhUTUwgYXR0cmlidXRlIG9uIGEgbm9kZS4KICAgICAgICAgKgogICAgICAgICAqIE5vdGUgdGhpcyBtZXRob2QgaXMgcHJvdmlkZWQgYXMgYmFja3dhcmQtY29tcGF0aWJsZSBsZWdhY3kgQVBJCiAgICAgICAgICogb25seS4gIEl0IGlzIG5vdCBkaXJlY3RseSBjYWxsZWQgYnkgYW55IFBvbHltZXIgZmVhdHVyZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIHRvIHNlcmlhbGl6ZS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIEF0dHJpYnV0ZSBuYW1lIHRvIHNlcmlhbGl6ZSB0by4KICAgICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IG5vZGUgRWxlbWVudCB0byBzZXQgYXR0cmlidXRlIHRvLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgc2VyaWFsaXplVmFsdWVUb0F0dHJpYnV0ZSh2YWx1ZSwgYXR0cmlidXRlLCBub2RlKSB7CiAgICAgICAgICB0aGlzLl92YWx1ZVRvTm9kZUF0dHJpYnV0ZSgvKiogQHR5cGUge0VsZW1lbnR9ICovIChub2RlIHx8IHRoaXMpLCB2YWx1ZSwgYXR0cmlidXRlKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvcGllcyBvd24gcHJvcGVydGllcyAoaW5jbHVkaW5nIGFjY2Vzc29yIGRlc2NyaXB0b3JzKSBmcm9tIGEgc291cmNlCiAgICAgICAgICogb2JqZWN0IHRvIGEgdGFyZ2V0IG9iamVjdC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBwcm90b3R5cGUgVGFyZ2V0IG9iamVjdCB0byBjb3B5IHByb3BlcnRpZXMgdG8uCiAgICAgICAgICogQHBhcmFtIHtPYmplY3R9IGFwaSBTb3VyY2Ugb2JqZWN0IHRvIGNvcHkgcHJvcGVydGllcyBmcm9tLgogICAgICAgICAqIEByZXR1cm4ge09iamVjdH0gcHJvdG90eXBlIG9iamVjdCB0aGF0IHdhcyBwYXNzZWQgYXMgZmlyc3QgYXJndW1lbnQuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgZXh0ZW5kKHByb3RvdHlwZSwgYXBpKSB7CiAgICAgICAgICBpZiAoIShwcm90b3R5cGUgJiYgYXBpKSkgewogICAgICAgICAgICByZXR1cm4gcHJvdG90eXBlIHx8IGFwaTsKICAgICAgICAgIH0KICAgICAgICAgIGxldCBuJCA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKGFwaSk7CiAgICAgICAgICBmb3IgKGxldCBpPTAsIG47IChpPG4kLmxlbmd0aCkgJiYgKG49biRbaV0pOyBpKyspIHsKICAgICAgICAgICAgbGV0IHBkID0gT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihhcGksIG4pOwogICAgICAgICAgICBpZiAocGQpIHsKICAgICAgICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkocHJvdG90eXBlLCBuLCBwZCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBwcm90b3R5cGU7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb3BpZXMgcHJvcHMgZnJvbSBhIHNvdXJjZSBvYmplY3QgdG8gYSB0YXJnZXQgb2JqZWN0LgogICAgICAgICAqCiAgICAgICAgICogTm90ZSwgdGhpcyBtZXRob2QgdXNlcyBhIHNpbXBsZSBgZm9yLi4uaW5gIHN0cmF0ZWd5IGZvciBlbnVtZXJhdGluZwogICAgICAgICAqIHByb3BlcnRpZXMuICBUbyBlbnN1cmUgb25seSBgb3duUHJvcGVydGllc2AgYXJlIGNvcGllZCBmcm9tIHNvdXJjZQogICAgICAgICAqIHRvIHRhcmdldCBhbmQgdGhhdCBhY2Nlc3NvciBpbXBsZW1lbnRhdGlvbnMgYXJlIGNvcGllZCwgdXNlIGBleHRlbmRgLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshT2JqZWN0fSB0YXJnZXQgVGFyZ2V0IG9iamVjdCB0byBjb3B5IHByb3BlcnRpZXMgdG8uCiAgICAgICAgICogQHBhcmFtIHshT2JqZWN0fSBzb3VyY2UgU291cmNlIG9iamVjdCB0byBjb3B5IHByb3BlcnRpZXMgZnJvbS4KICAgICAgICAgKiBAcmV0dXJuIHshT2JqZWN0fSBUYXJnZXQgb2JqZWN0IHRoYXQgd2FzIHBhc3NlZCBhcyBmaXJzdCBhcmd1bWVudC4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBtaXhpbih0YXJnZXQsIHNvdXJjZSkgewogICAgICAgICAgZm9yIChsZXQgaSBpbiBzb3VyY2UpIHsKICAgICAgICAgICAgdGFyZ2V0W2ldID0gc291cmNlW2ldOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRhcmdldDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIHByb3RvdHlwZSBvZiBhbiBvYmplY3QuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlIHRoaXMgbWV0aG9kIGlzIHByb3ZpZGVkIGFzIGJhY2t3YXJkLWNvbXBhdGlibGUgbGVnYWN5IEFQSQogICAgICAgICAqIG9ubHkuICBJdCBpcyBub3QgZGlyZWN0bHkgY2FsbGVkIGJ5IGFueSBQb2x5bWVyIGZlYXR1cmVzLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCBvbiB3aGljaCB0byBzZXQgdGhlIHByb3RvdHlwZS4KICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gcHJvdG90eXBlIFRoZSBwcm90b3R5cGUgdGhhdCB3aWxsIGJlIHNldCBvbiB0aGUgZ2l2ZW4KICAgICAgICAgKiBgb2JqZWN0YC4KICAgICAgICAgKiBAcmV0dXJuIHtPYmplY3R9IFJldHVybnMgdGhlIGdpdmVuIGBvYmplY3RgIHdpdGggaXRzIHByb3RvdHlwZSBzZXQKICAgICAgICAgKiB0byB0aGUgZ2l2ZW4gYHByb3RvdHlwZWAgb2JqZWN0LgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGNoYWluT2JqZWN0KG9iamVjdCwgcHJvdG90eXBlKSB7CiAgICAgICAgICBpZiAob2JqZWN0ICYmIHByb3RvdHlwZSAmJiBvYmplY3QgIT09IHByb3RvdHlwZSkgewogICAgICAgICAgICBvYmplY3QuX19wcm90b19fID0gcHJvdG90eXBlOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIG9iamVjdDsKICAgICAgICB9CgogICAgICAgIC8qICoqKiogQmVnaW4gVGVtcGxhdGUgKioqKiAqLwoKICAgICAgICAvKioKICAgICAgICAgKiBDYWxscyBgaW1wb3J0Tm9kZWAgb24gdGhlIGBjb250ZW50YCBvZiB0aGUgYHRlbXBsYXRlYCBzcGVjaWZpZWQgYW5kCiAgICAgICAgICogcmV0dXJucyBhIGRvY3VtZW50IGZyYWdtZW50IGNvbnRhaW5pbmcgdGhlIGltcG9ydGVkIGNvbnRlbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0hUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlIEhUTUwgdGVtcGxhdGUgZWxlbWVudCB0byBpbnN0YW5jZS4KICAgICAgICAgKiBAcmV0dXJuIHshRG9jdW1lbnRGcmFnbWVudH0gRG9jdW1lbnQgZnJhZ21lbnQgY29udGFpbmluZyB0aGUgaW1wb3J0ZWQKICAgICAgICAgKiAgIHRlbXBsYXRlIGNvbnRlbnQuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30gZ28vbWlzc2luZ2ZucHJvcHMKICAgICAgICAgKi8KICAgICAgICBpbnN0YW5jZVRlbXBsYXRlKHRlbXBsYXRlKSB7CiAgICAgICAgICBsZXQgY29udGVudCA9IHRoaXMuY29uc3RydWN0b3IuX2NvbnRlbnRGb3JUZW1wbGF0ZSh0ZW1wbGF0ZSk7CiAgICAgICAgICBsZXQgZG9tID0gLyoqIEB0eXBlIHshRG9jdW1lbnRGcmFnbWVudH0gKi8KICAgICAgICAgICAgKGRvY3VtZW50LmltcG9ydE5vZGUoY29udGVudCwgdHJ1ZSkpOwogICAgICAgICAgcmV0dXJuIGRvbTsKICAgICAgICB9CgogICAgICAgIC8qICoqKiogQmVnaW4gRXZlbnRzICoqKiogKi8KCgoKICAgICAgICAvKioKICAgICAgICAgKiBEaXNwYXRjaGVzIGEgY3VzdG9tIGV2ZW50IHdpdGggYW4gb3B0aW9uYWwgZGV0YWlsIHZhbHVlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHR5cGUgTmFtZSBvZiBldmVudCB0eXBlLgogICAgICAgICAqIEBwYXJhbSB7Kj19IGRldGFpbCBEZXRhaWwgdmFsdWUgY29udGFpbmluZyBldmVudC1zcGVjaWZpYwogICAgICAgICAqICAgcGF5bG9hZC4KICAgICAgICAgKiBAcGFyYW0ge3sgYnViYmxlczogKGJvb2xlYW58dW5kZWZpbmVkKSwgY2FuY2VsYWJsZTogKGJvb2xlYW58dW5kZWZpbmVkKSwKICAgICAgICAgKiAgICAgY29tcG9zZWQ6IChib29sZWFufHVuZGVmaW5lZCkgfT19CiAgICAgICAgICogIG9wdGlvbnMgT2JqZWN0IHNwZWNpZnlpbmcgb3B0aW9ucy4gIFRoZXNlIG1heSBpbmNsdWRlOgogICAgICAgICAqICBgYnViYmxlc2AgKGJvb2xlYW4sIGRlZmF1bHRzIHRvIGB0cnVlYCksCiAgICAgICAgICogIGBjYW5jZWxhYmxlYCAoYm9vbGVhbiwgZGVmYXVsdHMgdG8gZmFsc2UpLCBhbmQKICAgICAgICAgKiAgYG5vZGVgIG9uIHdoaWNoIHRvIGZpcmUgdGhlIGV2ZW50IChIVE1MRWxlbWVudCwgZGVmYXVsdHMgdG8gYHRoaXNgKS4KICAgICAgICAgKiBAcmV0dXJuIHshRXZlbnR9IFRoZSBuZXcgZXZlbnQgdGhhdCB3YXMgZmlyZWQuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgZmlyZSh0eXBlLCBkZXRhaWwsIG9wdGlvbnMpIHsKICAgICAgICAgIG9wdGlvbnMgPSBvcHRpb25zIHx8IHt9OwogICAgICAgICAgZGV0YWlsID0gKGRldGFpbCA9PT0gbnVsbCB8fCBkZXRhaWwgPT09IHVuZGVmaW5lZCkgPyB7fSA6IGRldGFpbDsKICAgICAgICAgIGxldCBldmVudCA9IG5ldyBFdmVudCh0eXBlLCB7CiAgICAgICAgICAgIGJ1YmJsZXM6IG9wdGlvbnMuYnViYmxlcyA9PT0gdW5kZWZpbmVkID8gdHJ1ZSA6IG9wdGlvbnMuYnViYmxlcywKICAgICAgICAgICAgY2FuY2VsYWJsZTogQm9vbGVhbihvcHRpb25zLmNhbmNlbGFibGUpLAogICAgICAgICAgICBjb21wb3NlZDogb3B0aW9ucy5jb21wb3NlZCA9PT0gdW5kZWZpbmVkID8gdHJ1ZTogb3B0aW9ucy5jb21wb3NlZAogICAgICAgICAgfSk7CiAgICAgICAgICBldmVudC5kZXRhaWwgPSBkZXRhaWw7CiAgICAgICAgICBsZXQgbm9kZSA9IG9wdGlvbnMubm9kZSB8fCB0aGlzOwogICAgICAgICAgd3JhcChub2RlKS5kaXNwYXRjaEV2ZW50KGV2ZW50KTsKICAgICAgICAgIHJldHVybiBldmVudDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlbmllbmNlIG1ldGhvZCB0byBhZGQgYW4gZXZlbnQgbGlzdGVuZXIgb24gYSBnaXZlbiBlbGVtZW50LAogICAgICAgICAqIGxhdGUgYm91bmQgdG8gYSBuYW1lZCBtZXRob2Qgb24gdGhpcyBlbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHs/RXZlbnRUYXJnZXR9IG5vZGUgRWxlbWVudCB0byBhZGQgZXZlbnQgbGlzdGVuZXIgdG8uCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGV2ZW50TmFtZSBOYW1lIG9mIGV2ZW50IHRvIGxpc3RlbiBmb3IuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG1ldGhvZE5hbWUgTmFtZSBvZiBoYW5kbGVyIG1ldGhvZCBvbiBgdGhpc2AgdG8gY2FsbC4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGxpc3Rlbihub2RlLCBldmVudE5hbWUsIG1ldGhvZE5hbWUpIHsKICAgICAgICAgIG5vZGUgPSAvKiogQHR5cGUgeyFFdmVudFRhcmdldH0gKi8gKG5vZGUgfHwgdGhpcyk7CiAgICAgICAgICBsZXQgaGJsID0gdGhpcy5fX2JvdW5kTGlzdGVuZXJzIHx8CiAgICAgICAgICAgICh0aGlzLl9fYm91bmRMaXN0ZW5lcnMgPSBuZXcgV2Vha01hcCgpKTsKICAgICAgICAgIGxldCBibCA9IGhibC5nZXQobm9kZSk7CiAgICAgICAgICBpZiAoIWJsKSB7CiAgICAgICAgICAgIGJsID0ge307CiAgICAgICAgICAgIGhibC5zZXQobm9kZSwgYmwpOwogICAgICAgICAgfQogICAgICAgICAgbGV0IGtleSA9IGV2ZW50TmFtZSArIG1ldGhvZE5hbWU7CiAgICAgICAgICBpZiAoIWJsW2tleV0pIHsKICAgICAgICAgICAgYmxba2V5XSA9IHRoaXMuX2FkZE1ldGhvZEV2ZW50TGlzdGVuZXJUb05vZGUoCiAgICAgICAgICAgICAgICAvKiogQHR5cGUgeyFOb2RlfSAqLyAobm9kZSksIGV2ZW50TmFtZSwgbWV0aG9kTmFtZSwgdGhpcyk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDb252ZW5pZW5jZSBtZXRob2QgdG8gcmVtb3ZlIGFuIGV2ZW50IGxpc3RlbmVyIGZyb20gYSBnaXZlbiBlbGVtZW50LAogICAgICAgICAqIGxhdGUgYm91bmQgdG8gYSBuYW1lZCBtZXRob2Qgb24gdGhpcyBlbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHs/RXZlbnRUYXJnZXR9IG5vZGUgRWxlbWVudCB0byByZW1vdmUgZXZlbnQgbGlzdGVuZXIgZnJvbS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZlbnROYW1lIE5hbWUgb2YgZXZlbnQgdG8gc3RvcCBsaXN0ZW5pbmcgdG8uCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG1ldGhvZE5hbWUgTmFtZSBvZiBoYW5kbGVyIG1ldGhvZCBvbiBgdGhpc2AgdG8gbm90IGNhbGwKICAgICAgICAgYW55bW9yZS4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHVubGlzdGVuKG5vZGUsIGV2ZW50TmFtZSwgbWV0aG9kTmFtZSkgewogICAgICAgICAgbm9kZSA9IC8qKiBAdHlwZSB7IUV2ZW50VGFyZ2V0fSAqLyAobm9kZSB8fCB0aGlzKTsKICAgICAgICAgIGxldCBibCA9IHRoaXMuX19ib3VuZExpc3RlbmVycyAmJgogICAgICAgICAgICAgIHRoaXMuX19ib3VuZExpc3RlbmVycy5nZXQoLyoqIEB0eXBlIHshRWxlbWVudH0gKi8gKG5vZGUpKTsKICAgICAgICAgIGxldCBrZXkgPSBldmVudE5hbWUgKyBtZXRob2ROYW1lOwogICAgICAgICAgbGV0IGhhbmRsZXIgPSBibCAmJiBibFtrZXldOwogICAgICAgICAgaWYgKGhhbmRsZXIpIHsKICAgICAgICAgICAgdGhpcy5fcmVtb3ZlRXZlbnRMaXN0ZW5lckZyb21Ob2RlKAogICAgICAgICAgICAgICAgLyoqIEB0eXBlIHshTm9kZX0gKi8gKG5vZGUpLCBldmVudE5hbWUsIGhhbmRsZXIpOwogICAgICAgICAgICBibFtrZXldID0gLyoqIEB0eXBlIHs/fSAqLyAobnVsbCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZSBzY3JvbGxpbmcgYmVoYXZpb3IgdG8gYWxsIGRpcmVjdGlvbiwgb25lIGRpcmVjdGlvbiwgb3Igbm9uZS4KICAgICAgICAgKgogICAgICAgICAqIFZhbGlkIHNjcm9sbCBkaXJlY3Rpb25zOgogICAgICAgICAqICAgLSAnYWxsJzogc2Nyb2xsIGluIGFueSBkaXJlY3Rpb24KICAgICAgICAgKiAgIC0gJ3gnOiBzY3JvbGwgb25seSBpbiB0aGUgJ3gnIGRpcmVjdGlvbgogICAgICAgICAqICAgLSAneSc6IHNjcm9sbCBvbmx5IGluIHRoZSAneScgZGlyZWN0aW9uCiAgICAgICAgICogICAtICdub25lJzogZGlzYWJsZSBzY3JvbGxpbmcgZm9yIHRoaXMgbm9kZQogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBkaXJlY3Rpb24gRGlyZWN0aW9uIHRvIGFsbG93IHNjcm9sbGluZwogICAgICAgICAqIERlZmF1bHRzIHRvIGBhbGxgLgogICAgICAgICAqIEBwYXJhbSB7RWxlbWVudD19IG5vZGUgRWxlbWVudCB0byBhcHBseSBzY3JvbGwgZGlyZWN0aW9uIHNldHRpbmcuCiAgICAgICAgICogRGVmYXVsdHMgdG8gYHRoaXNgLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgc2V0U2Nyb2xsRGlyZWN0aW9uKGRpcmVjdGlvbiwgbm9kZSkgewogICAgICAgICAgc2V0VG91Y2hBY3Rpb24oCiAgICAgICAgICAgICAgLyoqIEB0eXBlIHshRWxlbWVudH0gKi8gKG5vZGUgfHwgdGhpcyksCiAgICAgICAgICAgICAgRElSRUNUSU9OX01BUFtkaXJlY3Rpb25dIHx8ICdhdXRvJyk7CiAgICAgICAgfQogICAgICAgIC8qICoqKiogRW5kIEV2ZW50cyAqKioqICovCgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlbmllbmNlIG1ldGhvZCB0byBydW4gYHF1ZXJ5U2VsZWN0b3JgIG9uIHRoaXMgbG9jYWwgRE9NIHNjb3BlLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBmdW5jdGlvbiBjYWxscyBgUG9seW1lci5kb20odGhpcy5yb290KS5xdWVyeVNlbGVjdG9yKHNsY3RyKWAuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gc2xjdHIgU2VsZWN0b3IgdG8gcnVuIG9uIHRoaXMgbG9jYWwgRE9NIHNjb3BlCiAgICAgICAgICogQHJldHVybiB7RWxlbWVudH0gRWxlbWVudCBmb3VuZCBieSB0aGUgc2VsZWN0b3IsIG9yIG51bGwgaWYgbm90IGZvdW5kLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgICQkKHNsY3RyKSB7CiAgICAgICAgICAvLyBOb3RlLCBubyBuZWVkIHRvIGB3cmFwYCB0aGlzIGJlY2F1c2Ugcm9vdCBpcyBhbHdheXMgcGF0Y2hlZAogICAgICAgICAgcmV0dXJuIHRoaXMucm9vdC5xdWVyeVNlbGVjdG9yKHNsY3RyKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiB0aGUgZWxlbWVudCB3aG9zZSBsb2NhbCBkb20gd2l0aGluIHdoaWNoIHRoaXMgZWxlbWVudAogICAgICAgICAqIGlzIGNvbnRhaW5lZC4gVGhpcyBpcyBhIHNob3J0aGFuZCBmb3IKICAgICAgICAgKiBgdGhpcy5nZXRSb290Tm9kZSgpLmhvc3RgLgogICAgICAgICAqIEB0aGlzIHtFbGVtZW50fQogICAgICAgICAqIEByZXR1cm4gez9Ob2RlfSBUaGUgZWxlbWVudCB3aG9zZSBsb2NhbCBkb20gd2l0aGluIHdoaWNoIHRoaXMgZWxlbWVudCBpcwogICAgICAgICAqIGNvbnRhaW5lZC4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBnZXQgZG9tSG9zdCgpIHsKICAgICAgICAgIGxldCByb290ID0gd3JhcCh0aGlzKS5nZXRSb290Tm9kZSgpOwogICAgICAgICAgcmV0dXJuIChyb290IGluc3RhbmNlb2YgRG9jdW1lbnRGcmFnbWVudCkgPyAvKiogQHR5cGUge1NoYWRvd1Jvb3R9ICovIChyb290KS5ob3N0IDogcm9vdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEZvcmNlIHRoaXMgZWxlbWVudCB0byBkaXN0cmlidXRlIGl0cyBjaGlsZHJlbiB0byBpdHMgbG9jYWwgZG9tLgogICAgICAgICAqIFRoaXMgc2hvdWxkIG5vdCBiZSBuZWNlc3NhcnkgYXMgb2YgUG9seW1lciAyLjAuMiBhbmQgaXMgcHJvdmlkZWQgb25seQogICAgICAgICAqIGZvciBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eS4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGRpc3RyaWJ1dGVDb250ZW50KCkgewogICAgICAgICAgY29uc3QgdGhpc0VsID0gLyoqIEB0eXBlIHtFbGVtZW50fSAqLyAodGhpcyk7CiAgICAgICAgICBjb25zdCBkb21BcGkgPSAvKiogQHR5cGUge1BvbHltZXJEb21BcGl9ICovKGRvbSh0aGlzRWwpKTsKICAgICAgICAgIGlmICh3aW5kb3cuU2hhZHlET00gJiYgZG9tQXBpLnNoYWRvd1Jvb3QpIHsKICAgICAgICAgICAgU2hhZHlET00uZmx1c2goKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYSBsaXN0IG9mIG5vZGVzIHRoYXQgYXJlIHRoZSBlZmZlY3RpdmUgY2hpbGROb2Rlcy4gVGhlIGVmZmVjdGl2ZQogICAgICAgICAqIGNoaWxkTm9kZXMgbGlzdCBpcyB0aGUgc2FtZSBhcyB0aGUgZWxlbWVudCdzIGNoaWxkTm9kZXMgZXhjZXB0IHRoYXQKICAgICAgICAgKiBhbnkgYDxjb250ZW50PmAgZWxlbWVudHMgYXJlIHJlcGxhY2VkIHdpdGggdGhlIGxpc3Qgb2Ygbm9kZXMgZGlzdHJpYnV0ZWQKICAgICAgICAgKiB0byB0aGUgYDxjb250ZW50PmAsIHRoZSByZXN1bHQgb2YgaXRzIGBnZXREaXN0cmlidXRlZE5vZGVzYCBtZXRob2QuCiAgICAgICAgICogQHJldHVybiB7IUFycmF5PCFOb2RlPn0gTGlzdCBvZiBlZmZlY3RpdmUgY2hpbGQgbm9kZXMuCiAgICAgICAgICogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9IExlZ2FjeUVsZW1lbnRNaXhpbiBtdXN0IGJlIGFwcGxpZWQgdG8gYW4KICAgICAgICAgKiAgICAgSFRNTEVsZW1lbnQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBnZXRFZmZlY3RpdmVDaGlsZE5vZGVzKCkgewogICAgICAgICAgY29uc3QgdGhpc0VsID0gLyoqIEB0eXBlIHtFbGVtZW50fSAqLyAodGhpcyk7CiAgICAgICAgICBjb25zdCBkb21BcGkgPSAvKiogQHR5cGUge1BvbHltZXJEb21BcGl9ICovIChkb20odGhpc0VsKSk7CiAgICAgICAgICByZXR1cm4gZG9tQXBpLmdldEVmZmVjdGl2ZUNoaWxkTm9kZXMoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYSBsaXN0IG9mIG5vZGVzIGRpc3RyaWJ1dGVkIHdpdGhpbiB0aGlzIGVsZW1lbnQgdGhhdCBtYXRjaAogICAgICAgICAqIGBzZWxlY3RvcmAuIFRoZXNlIGNhbiBiZSBkb20gY2hpbGRyZW4gb3IgZWxlbWVudHMgZGlzdHJpYnV0ZWQgdG8KICAgICAgICAgKiBjaGlsZHJlbiB0aGF0IGFyZSBpbnNlcnRpb24gcG9pbnRzLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzZWxlY3RvciBTZWxlY3RvciB0byBydW4uCiAgICAgICAgICogQHJldHVybiB7IUFycmF5PCFOb2RlPn0gTGlzdCBvZiBkaXN0cmlidXRlZCBlbGVtZW50cyB0aGF0IG1hdGNoIHNlbGVjdG9yLgogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfSBMZWdhY3lFbGVtZW50TWl4aW4gbXVzdCBiZSBhcHBsaWVkIHRvIGFuCiAgICAgICAgICogSFRNTEVsZW1lbnQKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBxdWVyeURpc3RyaWJ1dGVkRWxlbWVudHMoc2VsZWN0b3IpIHsKICAgICAgICAgIGNvbnN0IHRoaXNFbCA9IC8qKiBAdHlwZSB7RWxlbWVudH0gKi8gKHRoaXMpOwogICAgICAgICAgY29uc3QgZG9tQXBpID0gLyoqIEB0eXBlIHtQb2x5bWVyRG9tQXBpfSAqLyAoZG9tKHRoaXNFbCkpOwogICAgICAgICAgcmV0dXJuIGRvbUFwaS5xdWVyeURpc3RyaWJ1dGVkRWxlbWVudHMoc2VsZWN0b3IpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBhIGxpc3Qgb2YgZWxlbWVudHMgdGhhdCBhcmUgdGhlIGVmZmVjdGl2ZSBjaGlsZHJlbi4gVGhlIGVmZmVjdGl2ZQogICAgICAgICAqIGNoaWxkcmVuIGxpc3QgaXMgdGhlIHNhbWUgYXMgdGhlIGVsZW1lbnQncyBjaGlsZHJlbiBleGNlcHQgdGhhdAogICAgICAgICAqIGFueSBgPGNvbnRlbnQ+YCBlbGVtZW50cyBhcmUgcmVwbGFjZWQgd2l0aCB0aGUgbGlzdCBvZiBlbGVtZW50cwogICAgICAgICAqIGRpc3RyaWJ1dGVkIHRvIHRoZSBgPGNvbnRlbnQ+YC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4geyFBcnJheTwhTm9kZT59IExpc3Qgb2YgZWZmZWN0aXZlIGNoaWxkcmVuLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGdldEVmZmVjdGl2ZUNoaWxkcmVuKCkgewogICAgICAgICAgbGV0IGxpc3QgPSB0aGlzLmdldEVmZmVjdGl2ZUNoaWxkTm9kZXMoKTsKICAgICAgICAgIHJldHVybiBsaXN0LmZpbHRlcihmdW5jdGlvbigvKiogQHR5cGUgeyFOb2RlfSAqLyBuKSB7CiAgICAgICAgICAgIHJldHVybiAobi5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpOwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGEgc3RyaW5nIG9mIHRleHQgY29udGVudCB0aGF0IGlzIHRoZSBjb25jYXRlbmF0aW9uIG9mIHRoZQogICAgICAgICAqIHRleHQgY29udGVudCdzIG9mIHRoZSBlbGVtZW50J3MgZWZmZWN0aXZlIGNoaWxkTm9kZXMgKHRoZSBlbGVtZW50cwogICAgICAgICAqIHJldHVybmVkIGJ5IDxhIGhyZWY9IiNnZXRFZmZlY3RpdmVDaGlsZE5vZGVzPmdldEVmZmVjdGl2ZUNoaWxkTm9kZXM8L2E+LgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7c3RyaW5nfSBMaXN0IG9mIGVmZmVjdGl2ZSBjaGlsZHJlbi4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBnZXRFZmZlY3RpdmVUZXh0Q29udGVudCgpIHsKICAgICAgICAgIGxldCBjbiA9IHRoaXMuZ2V0RWZmZWN0aXZlQ2hpbGROb2RlcygpOwogICAgICAgICAgbGV0IHRjID0gW107CiAgICAgICAgICBmb3IgKGxldCBpPTAsIGM7IChjID0gY25baV0pOyBpKyspIHsKICAgICAgICAgICAgaWYgKGMubm9kZVR5cGUgIT09IE5vZGUuQ09NTUVOVF9OT0RFKSB7CiAgICAgICAgICAgICAgdGMucHVzaChjLnRleHRDb250ZW50KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRjLmpvaW4oJycpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgZmlyc3QgZWZmZWN0aXZlIGNoaWxkTm9kZSB3aXRoaW4gdGhpcyBlbGVtZW50IHRoYXQKICAgICAgICAgKiBtYXRjaCBgc2VsZWN0b3JgLiBUaGVzZSBjYW4gYmUgZG9tIGNoaWxkIG5vZGVzIG9yIGVsZW1lbnRzIGRpc3RyaWJ1dGVkCiAgICAgICAgICogdG8gY2hpbGRyZW4gdGhhdCBhcmUgaW5zZXJ0aW9uIHBvaW50cy4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gc2VsZWN0b3IgU2VsZWN0b3IgdG8gcnVuLgogICAgICAgICAqIEByZXR1cm4ge05vZGV9IEZpcnN0IGVmZmVjdGl2ZSBjaGlsZCBub2RlIHRoYXQgbWF0Y2hlcyBzZWxlY3Rvci4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBxdWVyeUVmZmVjdGl2ZUNoaWxkcmVuKHNlbGVjdG9yKSB7CiAgICAgICAgICBsZXQgZSQgPSB0aGlzLnF1ZXJ5RGlzdHJpYnV0ZWRFbGVtZW50cyhzZWxlY3Rvcik7CiAgICAgICAgICByZXR1cm4gZSQgJiYgZSRbMF07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGEgbGlzdCBvZiBlZmZlY3RpdmUgY2hpbGROb2RlcyB3aXRoaW4gdGhpcyBlbGVtZW50IHRoYXQKICAgICAgICAgKiBtYXRjaCBgc2VsZWN0b3JgLiBUaGVzZSBjYW4gYmUgZG9tIGNoaWxkIG5vZGVzIG9yIGVsZW1lbnRzIGRpc3RyaWJ1dGVkCiAgICAgICAgICogdG8gY2hpbGRyZW4gdGhhdCBhcmUgaW5zZXJ0aW9uIHBvaW50cy4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gc2VsZWN0b3IgU2VsZWN0b3IgdG8gcnVuLgogICAgICAgICAqIEByZXR1cm4geyFBcnJheTwhTm9kZT59IExpc3Qgb2YgZWZmZWN0aXZlIGNoaWxkIG5vZGVzIHRoYXQgbWF0Y2gKICAgICAgICAgKiAgICAgc2VsZWN0b3IuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgcXVlcnlBbGxFZmZlY3RpdmVDaGlsZHJlbihzZWxlY3RvcikgewogICAgICAgICAgcmV0dXJuIHRoaXMucXVlcnlEaXN0cmlidXRlZEVsZW1lbnRzKHNlbGVjdG9yKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYSBsaXN0IG9mIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoaXMgZWxlbWVudCdzIGA8c2xvdD5gLgogICAgICAgICAqCiAgICAgICAgICogSWYgdGhpcyBlbGVtZW50IGNvbnRhaW5zIG1vcmUgdGhhbiBvbmUgYDxzbG90PmAgaW4gaXRzIGxvY2FsIERPTSwKICAgICAgICAgKiBhbiBvcHRpb25hbCBzZWxlY3RvciBtYXkgYmUgcGFzc2VkIHRvIGNob29zZSB0aGUgZGVzaXJlZCBjb250ZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBzbGN0ciBDU1Mgc2VsZWN0b3IgdG8gY2hvb3NlIHRoZSBkZXNpcmVkCiAgICAgICAgICogICBgPHNsb3Q+YC4gIERlZmF1bHRzIHRvIGBjb250ZW50YC4KICAgICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IU5vZGU+fSBMaXN0IG9mIGRpc3RyaWJ1dGVkIG5vZGVzIGZvciB0aGUgYDxzbG90PmAuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgZ2V0Q29udGVudENoaWxkTm9kZXMoc2xjdHIpIHsKICAgICAgICAgIC8vIE5vdGUsIG5vIG5lZWQgdG8gYHdyYXBgIHRoaXMgYmVjYXVzZSByb290IGlzIGFsd2F5cwogICAgICAgICAgbGV0IGNvbnRlbnQgPSB0aGlzLnJvb3QucXVlcnlTZWxlY3RvcihzbGN0ciB8fCAnc2xvdCcpOwogICAgICAgICAgcmV0dXJuIGNvbnRlbnQgPwogICAgICAgICAgICAgIC8qKiBAdHlwZSB7UG9seW1lckRvbUFwaX0gKi8gKGRvbShjb250ZW50KSkuZ2V0RGlzdHJpYnV0ZWROb2RlcygpIDoKICAgICAgICAgICAgICBbXTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYSBsaXN0IG9mIGVsZW1lbnQgY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8gdGhpcyBlbGVtZW50J3MKICAgICAgICAgKiBgPHNsb3Q+YC4KICAgICAgICAgKgogICAgICAgICAqIElmIHRoaXMgZWxlbWVudCBjb250YWlucyBtb3JlIHRoYW4gb25lIGA8c2xvdD5gIGluIGl0cwogICAgICAgICAqIGxvY2FsIERPTSwgYW4gb3B0aW9uYWwgc2VsZWN0b3IgbWF5IGJlIHBhc3NlZCB0byBjaG9vc2UgdGhlIGRlc2lyZWQKICAgICAgICAgKiBjb250ZW50LiAgVGhpcyBtZXRob2QgZGlmZmVycyBmcm9tIGBnZXRDb250ZW50Q2hpbGROb2Rlc2AgaW4gdGhhdCBvbmx5CiAgICAgICAgICogZWxlbWVudHMgYXJlIHJldHVybmVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBzbGN0ciBDU1Mgc2VsZWN0b3IgdG8gY2hvb3NlIHRoZSBkZXNpcmVkCiAgICAgICAgICogICBgPGNvbnRlbnQ+YC4gIERlZmF1bHRzIHRvIGBjb250ZW50YC4KICAgICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IUhUTUxFbGVtZW50Pn0gTGlzdCBvZiBkaXN0cmlidXRlZCBub2RlcyBmb3IgdGhlCiAgICAgICAgICogICBgPHNsb3Q+YC4KICAgICAgICAgKiBAc3VwcHJlc3Mge2ludmFsaWRDYXN0c30KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBnZXRDb250ZW50Q2hpbGRyZW4oc2xjdHIpIHsKICAgICAgICAgIGxldCBjaGlsZHJlbiA9IC8qKiBAdHlwZSB7IUFycmF5PCFIVE1MRWxlbWVudD59ICovKHRoaXMuZ2V0Q29udGVudENoaWxkTm9kZXMoc2xjdHIpLmZpbHRlcihmdW5jdGlvbihuKSB7CiAgICAgICAgICAgIHJldHVybiAobi5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpOwogICAgICAgICAgfSkpOwogICAgICAgICAgcmV0dXJuIGNoaWxkcmVuOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIHdoZXRoZXIgYW4gZWxlbWVudCBpcyBpbiB0aGlzIGVsZW1lbnQncyBsaWdodCBET00gdHJlZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7P05vZGV9IG5vZGUgVGhlIGVsZW1lbnQgdG8gYmUgY2hlY2tlZC4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSB0cnVlIGlmIG5vZGUgaXMgaW4gdGhpcyBlbGVtZW50J3MgbGlnaHQgRE9NIHRyZWUuCiAgICAgICAgICogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9IExlZ2FjeUVsZW1lbnRNaXhpbiBtdXN0IGJlIGFwcGxpZWQgdG8gYW4KICAgICAgICAgKiBIVE1MRWxlbWVudAogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGlzTGlnaHREZXNjZW5kYW50KG5vZGUpIHsKICAgICAgICAgIGNvbnN0IHRoaXNOb2RlID0gLyoqIEB0eXBlIHtOb2RlfSAqLyAodGhpcyk7CiAgICAgICAgICByZXR1cm4gdGhpc05vZGUgIT09IG5vZGUgJiYgd3JhcCh0aGlzTm9kZSkuY29udGFpbnMobm9kZSkgJiYKICAgICAgICAgICAgd3JhcCh0aGlzTm9kZSkuZ2V0Um9vdE5vZGUoKSA9PT0gd3JhcChub2RlKS5nZXRSb290Tm9kZSgpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIHdoZXRoZXIgYW4gZWxlbWVudCBpcyBpbiB0aGlzIGVsZW1lbnQncyBsb2NhbCBET00gdHJlZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7IUVsZW1lbnR9IG5vZGUgVGhlIGVsZW1lbnQgdG8gYmUgY2hlY2tlZC4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSB0cnVlIGlmIG5vZGUgaXMgaW4gdGhpcyBlbGVtZW50J3MgbG9jYWwgRE9NIHRyZWUuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgaXNMb2NhbERlc2NlbmRhbnQobm9kZSkgewogICAgICAgICAgcmV0dXJuIHRoaXMucm9vdCA9PT0gd3JhcChub2RlKS5nZXRSb290Tm9kZSgpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogTm8tb3AgZm9yIGJhY2t3YXJkcyBjb21wYXRpYmlsaXR5LiBUaGlzIHNob3VsZCBub3cgYmUgaGFuZGxlZCBieQogICAgICAgICAqIFNoYWR5Q3NzIGxpYnJhcnkuCiAgICAgICAgICogQHBhcmFtICB7IUVsZW1lbnR9IGNvbnRhaW5lciBDb250YWluZXIgZWxlbWVudCB0byBzY29wZQogICAgICAgICAqIEBwYXJhbSAge2Jvb2xlYW49fSBzaG91bGRPYnNlcnZlIGlmIHRydWUsIHN0YXJ0IGEgbXV0YXRpb24gb2JzZXJ2ZXIgZm9yIGFkZGVkIG5vZGVzIHRvIHRoZSBjb250YWluZXIKICAgICAgICAgKiBAcmV0dXJuIHs/TXV0YXRpb25PYnNlcnZlcn0gUmV0dXJucyBhIG5ldyBNdXRhdGlvbk9ic2VydmVyIG9uIGBjb250YWluZXJgIGlmIGBzaG91bGRPYnNlcnZlYCBpcyB0cnVlLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHNjb3BlU3VidHJlZShjb250YWluZXIsIHNob3VsZE9ic2VydmUgPSBmYWxzZSkgewogICAgICAgICAgcmV0dXJuIHNjb3BlU3VidHJlZShjb250YWluZXIsIHNob3VsZE9ic2VydmUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgY29tcHV0ZWQgc3R5bGUgdmFsdWUgZm9yIHRoZSBnaXZlbiBwcm9wZXJ0eS4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgVGhlIGNzcyBwcm9wZXJ0eSBuYW1lLgogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gUmV0dXJucyB0aGUgY29tcHV0ZWQgY3NzIHByb3BlcnR5IHZhbHVlIGZvciB0aGUgZ2l2ZW4KICAgICAgICAgKiBgcHJvcGVydHlgLgogICAgICAgICAqIEBzdXBwcmVzcyB7aW52YWxpZENhc3RzfSBMZWdhY3lFbGVtZW50TWl4aW4gbXVzdCBiZSBhcHBsaWVkIHRvIGFuCiAgICAgICAgICogICAgIEhUTUxFbGVtZW50CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgZ2V0Q29tcHV0ZWRTdHlsZVZhbHVlKHByb3BlcnR5KSB7CiAgICAgICAgICByZXR1cm4gc3R5bGVJbnRlcmZhY2UuZ2V0Q29tcHV0ZWRTdHlsZVZhbHVlKC8qKiBAdHlwZSB7IUVsZW1lbnR9ICovKHRoaXMpLCBwcm9wZXJ0eSk7CiAgICAgICAgfQoKICAgICAgICAvLyBkZWJvdW5jZQoKICAgICAgICAvKioKICAgICAgICAgKiBDYWxsIGBkZWJvdW5jZWAgdG8gY29sbGFwc2UgbXVsdGlwbGUgcmVxdWVzdHMgZm9yIGEgbmFtZWQgdGFzayBpbnRvCiAgICAgICAgICogb25lIGludm9jYXRpb24gd2hpY2ggaXMgbWFkZSBhZnRlciB0aGUgd2FpdCB0aW1lIGhhcyBlbGFwc2VkIHdpdGgKICAgICAgICAgKiBubyBuZXcgcmVxdWVzdC4gIElmIG5vIHdhaXQgdGltZSBpcyBnaXZlbiwgdGhlIGNhbGxiYWNrIHdpbGwgYmUgY2FsbGVkCiAgICAgICAgICogYXQgbWljcm90YXNrIHRpbWluZyAoZ3VhcmFudGVlZCBiZWZvcmUgcGFpbnQpLgogICAgICAgICAqCiAgICAgICAgICogICAgIGRlYm91bmNlZENsaWNrQWN0aW9uKGUpIHsKICAgICAgICAgKiAgICAgICAvLyB3aWxsIG5vdCBjYWxsIGBwcm9jZXNzQ2xpY2tgIG1vcmUgdGhhbiBvbmNlIHBlciAxMDBtcwogICAgICAgICAqICAgICAgIHRoaXMuZGVib3VuY2UoJ2NsaWNrJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICogICAgICAgIHRoaXMucHJvY2Vzc0NsaWNrKCk7CiAgICAgICAgICogICAgICAgfSAxMDApOwogICAgICAgICAqICAgICB9CiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gam9iTmFtZSBTdHJpbmcgdG8gaWRlbnRpZnkgdGhlIGRlYm91bmNlIGpvYi4KICAgICAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKCk6dm9pZH0gY2FsbGJhY2sgRnVuY3Rpb24gdGhhdCBpcyBjYWxsZWQgKHdpdGggYHRoaXNgCiAgICAgICAgICogICBjb250ZXh0KSB3aGVuIHRoZSB3YWl0IHRpbWUgZWxhcHNlcy4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcj19IHdhaXQgT3B0aW9uYWwgd2FpdCB0aW1lIGluIG1pbGxpc2Vjb25kcyAobXMpIGFmdGVyIHRoZQogICAgICAgICAqICAgbGFzdCBzaWduYWwgdGhhdCBtdXN0IGVsYXBzZSBiZWZvcmUgaW52b2tpbmcgYGNhbGxiYWNrYAogICAgICAgICAqIEByZXR1cm4geyFPYmplY3R9IFJldHVybnMgYSBkZWJvdW5jZXIgb2JqZWN0IG9uIHdoaWNoIGV4aXN0cyB0aGUKICAgICAgICAgKiBmb2xsb3dpbmcgbWV0aG9kczogYGlzQWN0aXZlKClgIHJldHVybnMgdHJ1ZSBpZiB0aGUgZGVib3VuY2VyIGlzCiAgICAgICAgICogYWN0aXZlOyBgY2FuY2VsKClgIGNhbmNlbHMgdGhlIGRlYm91bmNlciBpZiBpdCBpcyBhY3RpdmU7CiAgICAgICAgICogYGZsdXNoKClgIGltbWVkaWF0ZWx5IGludm9rZXMgdGhlIGRlYm91bmNlZCBjYWxsYmFjayBpZiB0aGUgZGVib3VuY2VyCiAgICAgICAgICogaXMgYWN0aXZlLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGRlYm91bmNlKGpvYk5hbWUsIGNhbGxiYWNrLCB3YWl0KSB7CiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJzID0gdGhpcy5fZGVib3VuY2VycyB8fCB7fTsKICAgICAgICAgIHJldHVybiB0aGlzLl9kZWJvdW5jZXJzW2pvYk5hbWVdID0gRGVib3VuY2VyLmRlYm91bmNlKAogICAgICAgICAgICAgICAgdGhpcy5fZGVib3VuY2Vyc1tqb2JOYW1lXQogICAgICAgICAgICAgICwgd2FpdCA+IDAgPyB0aW1lT3V0LmFmdGVyKHdhaXQpIDogbWljcm9UYXNrCiAgICAgICAgICAgICAgLCBjYWxsYmFjay5iaW5kKHRoaXMpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciBhIG5hbWVkIGRlYm91bmNlciBpcyBhY3RpdmUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gam9iTmFtZSBUaGUgbmFtZSBvZiB0aGUgZGVib3VuY2VyIHN0YXJ0ZWQgd2l0aCBgZGVib3VuY2VgCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB0aGUgZGVib3VuY2VyIGlzIGFjdGl2ZSAoaGFzIG5vdCB5ZXQgZmlyZWQpLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGlzRGVib3VuY2VyQWN0aXZlKGpvYk5hbWUpIHsKICAgICAgICAgIHRoaXMuX2RlYm91bmNlcnMgPSB0aGlzLl9kZWJvdW5jZXJzIHx8IHt9OwogICAgICAgICAgbGV0IGRlYm91bmNlciA9IHRoaXMuX2RlYm91bmNlcnNbam9iTmFtZV07CiAgICAgICAgICByZXR1cm4gISEoZGVib3VuY2VyICYmIGRlYm91bmNlci5pc0FjdGl2ZSgpKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEltbWVkaWF0ZWx5IGNhbGxzIHRoZSBkZWJvdW5jZXIgYGNhbGxiYWNrYCBhbmQgaW5hY3RpdmF0ZXMgaXQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gam9iTmFtZSBUaGUgbmFtZSBvZiB0aGUgZGVib3VuY2VyIHN0YXJ0ZWQgd2l0aCBgZGVib3VuY2VgCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBmbHVzaERlYm91bmNlcihqb2JOYW1lKSB7CiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJzID0gdGhpcy5fZGVib3VuY2VycyB8fCB7fTsKICAgICAgICAgIGxldCBkZWJvdW5jZXIgPSB0aGlzLl9kZWJvdW5jZXJzW2pvYk5hbWVdOwogICAgICAgICAgaWYgKGRlYm91bmNlcikgewogICAgICAgICAgICBkZWJvdW5jZXIuZmx1c2goKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENhbmNlbHMgYW4gYWN0aXZlIGRlYm91bmNlci4gIFRoZSBgY2FsbGJhY2tgIHdpbGwgbm90IGJlIGNhbGxlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBqb2JOYW1lIFRoZSBuYW1lIG9mIHRoZSBkZWJvdW5jZXIgc3RhcnRlZCB3aXRoIGBkZWJvdW5jZWAKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGNhbmNlbERlYm91bmNlcihqb2JOYW1lKSB7CiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJzID0gdGhpcy5fZGVib3VuY2VycyB8fCB7fTsKICAgICAgICAgIGxldCBkZWJvdW5jZXIgPSB0aGlzLl9kZWJvdW5jZXJzW2pvYk5hbWVdOwogICAgICAgICAgaWYgKGRlYm91bmNlcikgewogICAgICAgICAgICBkZWJvdW5jZXIuY2FuY2VsKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBSdW5zIGEgY2FsbGJhY2sgZnVuY3Rpb24gYXN5bmNocm9ub3VzbHkuCiAgICAgICAgICoKICAgICAgICAgKiBCeSBkZWZhdWx0IChpZiBubyB3YWl0VGltZSBpcyBzcGVjaWZpZWQpLCBhc3luYyBjYWxsYmFja3MgYXJlIHJ1biBhdAogICAgICAgICAqIG1pY3JvdGFzayB0aW1pbmcsIHdoaWNoIHdpbGwgb2NjdXIgYmVmb3JlIHBhaW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHshRnVuY3Rpb259IGNhbGxiYWNrIFRoZSBjYWxsYmFjayBmdW5jdGlvbiB0byBydW4sIGJvdW5kIHRvCiAgICAgICAgICogICAgIGB0aGlzYC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcj19IHdhaXRUaW1lIFRpbWUgdG8gd2FpdCBiZWZvcmUgY2FsbGluZyB0aGUKICAgICAgICAgKiAgIGBjYWxsYmFja2AuICBJZiB1bnNwZWNpZmllZCBvciAwLCB0aGUgY2FsbGJhY2sgd2lsbCBiZSBydW4gYXQgbWljcm90YXNrCiAgICAgICAgICogICB0aW1pbmcgKGJlZm9yZSBwYWludCkuCiAgICAgICAgICogQHJldHVybiB7bnVtYmVyfSBIYW5kbGUgdGhhdCBtYXkgYmUgdXNlZCB0byBjYW5jZWwgdGhlIGFzeW5jIGpvYi4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBhc3luYyhjYWxsYmFjaywgd2FpdFRpbWUpIHsKICAgICAgICAgIHJldHVybiB3YWl0VGltZSA+IDAgPyB0aW1lT3V0LnJ1bihjYWxsYmFjay5iaW5kKHRoaXMpLCB3YWl0VGltZSkgOgogICAgICAgICAgICAgIH5taWNyb1Rhc2sucnVuKGNhbGxiYWNrLmJpbmQodGhpcykpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ2FuY2VscyBhbiBhc3luYyBvcGVyYXRpb24gc3RhcnRlZCB3aXRoIGBhc3luY2AuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gaGFuZGxlIEhhbmRsZSByZXR1cm5lZCBmcm9tIG9yaWdpbmFsIGBhc3luY2AgY2FsbCB0bwogICAgICAgICAqICAgY2FuY2VsLgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgY2FuY2VsQXN5bmMoaGFuZGxlKSB7CiAgICAgICAgICBoYW5kbGUgPCAwID8gbWljcm9UYXNrLmNhbmNlbCh+aGFuZGxlKSA6CiAgICAgICAgICAgICAgdGltZU91dC5jYW5jZWwoaGFuZGxlKTsKICAgICAgICB9CgogICAgICAgIC8vIG90aGVyCgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlbmllbmNlIG1ldGhvZCBmb3IgY3JlYXRpbmcgYW4gZWxlbWVudCBhbmQgY29uZmlndXJpbmcgaXQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGFnIEhUTUwgZWxlbWVudCB0YWcgdG8gY3JlYXRlLgogICAgICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gcHJvcHMgT2JqZWN0IG9mIHByb3BlcnRpZXMgdG8gY29uZmlndXJlIG9uIHRoZQogICAgICAgICAqICAgIGluc3RhbmNlLgogICAgICAgICAqIEByZXR1cm4geyFFbGVtZW50fSBOZXdseSBjcmVhdGVkIGFuZCBjb25maWd1cmVkIGVsZW1lbnQuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgY3JlYXRlKHRhZywgcHJvcHMpIHsKICAgICAgICAgIGxldCBlbHQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KHRhZyk7CiAgICAgICAgICBpZiAocHJvcHMpIHsKICAgICAgICAgICAgaWYgKGVsdC5zZXRQcm9wZXJ0aWVzKSB7CiAgICAgICAgICAgICAgZWx0LnNldFByb3BlcnRpZXMocHJvcHMpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGZvciAobGV0IG4gaW4gcHJvcHMpIHsKICAgICAgICAgICAgICAgIGVsdFtuXSA9IHByb3BzW25dOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGVsdDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFBvbHlmaWxsIGZvciBFbGVtZW50LnByb3RvdHlwZS5tYXRjaGVzLCB3aGljaCBpcyBzb21ldGltZXMgc3RpbGwKICAgICAgICAgKiBwcmVmaXhlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzZWxlY3RvciBTZWxlY3RvciB0byB0ZXN0LgogICAgICAgICAqIEBwYXJhbSB7IUVsZW1lbnQ9fSBub2RlIEVsZW1lbnQgdG8gdGVzdCB0aGUgc2VsZWN0b3IgYWdhaW5zdC4KICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHRoZSBlbGVtZW50IG1hdGNoZXMgdGhlIHNlbGVjdG9yLgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIGVsZW1lbnRNYXRjaGVzKHNlbGVjdG9yLCBub2RlKSB7CiAgICAgICAgICByZXR1cm4gbWF0Y2hlc1NlbGVjdG9yKCAobm9kZSB8fCB0aGlzKSwgc2VsZWN0b3IpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogVG9nZ2xlcyBhbiBIVE1MIGF0dHJpYnV0ZSBvbiBvciBvZmYuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBIVE1MIGF0dHJpYnV0ZSBuYW1lCiAgICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gYm9vbCBCb29sZWFuIHRvIGZvcmNlIHRoZSBhdHRyaWJ1dGUgb24gb3Igb2ZmLgogICAgICAgICAqICAgIFdoZW4gdW5zcGVjaWZpZWQsIHRoZSBzdGF0ZSBvZiB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmV2ZXJzZWQuCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gdHJ1ZSBpZiB0aGUgYXR0cmlidXRlIG5vdyBleGlzdHMKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICB0b2dnbGVBdHRyaWJ1dGUobmFtZSwgYm9vbCkgewogICAgICAgICAgbGV0IG5vZGUgPSAvKiogQHR5cGUge0VsZW1lbnR9ICovKHRoaXMpOwogICAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDMpIHsKICAgICAgICAgICAgbm9kZSA9IC8qKiBAdHlwZSB7RWxlbWVudH0gKi8oYXJndW1lbnRzWzJdKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID09IDEpIHsKICAgICAgICAgICAgYm9vbCA9ICFub2RlLmhhc0F0dHJpYnV0ZShuYW1lKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChib29sKSB7CiAgICAgICAgICAgIHdyYXAobm9kZSkuc2V0QXR0cmlidXRlKG5hbWUsICcnKTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB3cmFwKG5vZGUpLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0KCgogICAgICAgIC8qKgogICAgICAgICAqIFRvZ2dsZXMgYSBDU1MgY2xhc3Mgb24gb3Igb2ZmLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgQ1NTIGNsYXNzIG5hbWUKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW49fSBib29sIEJvb2xlYW4gdG8gZm9yY2UgdGhlIGNsYXNzIG9uIG9yIG9mZi4KICAgICAgICAgKiAgICBXaGVuIHVuc3BlY2lmaWVkLCB0aGUgc3RhdGUgb2YgdGhlIGNsYXNzIHdpbGwgYmUgcmV2ZXJzZWQuCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50PX0gbm9kZSBOb2RlIHRvIHRhcmdldC4gIERlZmF1bHRzIHRvIGB0aGlzYC4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHRvZ2dsZUNsYXNzKG5hbWUsIGJvb2wsIG5vZGUpIHsKICAgICAgICAgIG5vZGUgPSAvKiogQHR5cGUge0VsZW1lbnR9ICovIChub2RlIHx8IHRoaXMpOwogICAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT0gMSkgewogICAgICAgICAgICBib29sID0gIW5vZGUuY2xhc3NMaXN0LmNvbnRhaW5zKG5hbWUpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGJvb2wpIHsKICAgICAgICAgICAgbm9kZS5jbGFzc0xpc3QuYWRkKG5hbWUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZS5jbGFzc0xpc3QucmVtb3ZlKG5hbWUpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQ3Jvc3MtcGxhdGZvcm0gaGVscGVyIGZvciBzZXR0aW5nIGFuIGVsZW1lbnQncyBDU1MgYHRyYW5zZm9ybWAgcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdHJhbnNmb3JtVGV4dCBUcmFuc2Zvcm0gc2V0dGluZy4KICAgICAgICAgKiBAcGFyYW0ge0VsZW1lbnQ9fSBub2RlIEVsZW1lbnQgdG8gYXBwbHkgdGhlIHRyYW5zZm9ybSB0by4KICAgICAgICAgKiBEZWZhdWx0cyB0byBgdGhpc2AKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHRyYW5zZm9ybSh0cmFuc2Zvcm1UZXh0LCBub2RlKSB7CiAgICAgICAgICBub2RlID0gLyoqIEB0eXBlIHtFbGVtZW50fSAqLyAobm9kZSB8fCB0aGlzKTsKICAgICAgICAgIG5vZGUuc3R5bGUud2Via2l0VHJhbnNmb3JtID0gdHJhbnNmb3JtVGV4dDsKICAgICAgICAgIG5vZGUuc3R5bGUudHJhbnNmb3JtID0gdHJhbnNmb3JtVGV4dDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIENyb3NzLXBsYXRmb3JtIGhlbHBlciBmb3Igc2V0dGluZyBhbiBlbGVtZW50J3MgQ1NTIGB0cmFuc2xhdGUzZGAKICAgICAgICAgKiBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfHN0cmluZ30geCBYIG9mZnNldC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcnxzdHJpbmd9IHkgWSBvZmZzZXQuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ8c3RyaW5nfSB6IFogb2Zmc2V0LgogICAgICAgICAqIEBwYXJhbSB7RWxlbWVudD19IG5vZGUgRWxlbWVudCB0byBhcHBseSB0aGUgdHJhbnNmb3JtIHRvLgogICAgICAgICAqIERlZmF1bHRzIHRvIGB0aGlzYC4KICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIHRyYW5zbGF0ZTNkKHgsIHksIHosIG5vZGUpIHsKICAgICAgICAgIG5vZGUgPSAvKiogQHR5cGUge0VsZW1lbnR9ICovIChub2RlIHx8IHRoaXMpOwogICAgICAgICAgdGhpcy50cmFuc2Zvcm0oJ3RyYW5zbGF0ZTNkKCcgKyB4ICsgJywnICsgeSArICcsJyArIHogKyAnKScsIG5vZGUpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbiBpdGVtIGZyb20gYW4gYXJyYXksIGlmIGl0IGV4aXN0cy4KICAgICAgICAgKgogICAgICAgICAqIElmIHRoZSBhcnJheSBpcyBzcGVjaWZpZWQgYnkgcGF0aCwgYSBjaGFuZ2Ugbm90aWZpY2F0aW9uIGlzCiAgICAgICAgICogZ2VuZXJhdGVkLCBzbyB0aGF0IG9ic2VydmVycywgZGF0YSBiaW5kaW5ncyBhbmQgY29tcHV0ZWQKICAgICAgICAgKiBwcm9wZXJ0aWVzIHdhdGNoaW5nIHRoYXQgcGF0aCBjYW4gdXBkYXRlLgogICAgICAgICAqCiAgICAgICAgICogSWYgdGhlIGFycmF5IGlzIHBhc3NlZCBkaXJlY3RseSwgKipubyBjaGFuZ2UKICAgICAgICAgKiBub3RpZmljYXRpb24gaXMgZ2VuZXJhdGVkKiouCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZyB8ICFBcnJheTxudW1iZXJ8c3RyaW5nPn0gYXJyYXlPclBhdGggUGF0aCB0byBhcnJheSBmcm9tCiAgICAgICAgICogICAgIHdoaWNoIHRvIHJlbW92ZSB0aGUgaXRlbQogICAgICAgICAqICAgKG9yIHRoZSBhcnJheSBpdHNlbGYpLgogICAgICAgICAqIEBwYXJhbSB7Kn0gaXRlbSBJdGVtIHRvIHJlbW92ZS4KICAgICAgICAgKiBAcmV0dXJuIHtBcnJheX0gQXJyYXkgY29udGFpbmluZyBpdGVtIHJlbW92ZWQuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgYXJyYXlEZWxldGUoYXJyYXlPclBhdGgsIGl0ZW0pIHsKICAgICAgICAgIGxldCBpbmRleDsKICAgICAgICAgIGlmIChBcnJheS5pc0FycmF5KGFycmF5T3JQYXRoKSkgewogICAgICAgICAgICBpbmRleCA9IGFycmF5T3JQYXRoLmluZGV4T2YoaXRlbSk7CiAgICAgICAgICAgIGlmIChpbmRleCA+PSAwKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGFycmF5T3JQYXRoLnNwbGljZShpbmRleCwgMSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGxldCBhcnIgPSBnZXQodGhpcywgYXJyYXlPclBhdGgpOwogICAgICAgICAgICBpbmRleCA9IGFyci5pbmRleE9mKGl0ZW0pOwogICAgICAgICAgICBpZiAoaW5kZXggPj0gMCkgewogICAgICAgICAgICAgIHJldHVybiB0aGlzLnNwbGljZShhcnJheU9yUGF0aCwgaW5kZXgsIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CgogICAgICAgIC8vIGxvZ2dpbmcKCiAgICAgICAgLyoqCiAgICAgICAgICogRmFjYWRlcyBgY29uc29sZS5sb2dgL2B3YXJuYC9gZXJyb3JgIGFzIG92ZXJyaWRlIHBvaW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGxldmVsIE9uZSBvZiAnbG9nJywgJ3dhcm4nLCAnZXJyb3InCiAgICAgICAgICogQHBhcmFtIHtBcnJheX0gYXJncyBBcnJheSBvZiBzdHJpbmdzIG9yIG9iamVjdHMgdG8gbG9nCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfbG9nZ2VyKGxldmVsLCBhcmdzKSB7CiAgICAgICAgICAvLyBhY2NlcHQgWydmb28nLCAnYmFyJ10gYW5kIFtbJ2ZvbycsICdiYXInXV0KICAgICAgICAgIGlmIChBcnJheS5pc0FycmF5KGFyZ3MpICYmIGFyZ3MubGVuZ3RoID09PSAxICYmIEFycmF5LmlzQXJyYXkoYXJnc1swXSkpIHsKICAgICAgICAgICAgYXJncyA9IGFyZ3NbMF07CiAgICAgICAgICB9CiAgICAgICAgICBzd2l0Y2gobGV2ZWwpIHsKICAgICAgICAgICAgY2FzZSAnbG9nJzoKICAgICAgICAgICAgY2FzZSAnd2Fybic6CiAgICAgICAgICAgIGNhc2UgJ2Vycm9yJzoKICAgICAgICAgICAgICBjb25zb2xlW2xldmVsXSguLi5hcmdzKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEZhY2FkZXMgYGNvbnNvbGUubG9nYCBhcyBhbiBvdmVycmlkZSBwb2ludC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7Li4uKn0gYXJncyBBcnJheSBvZiBzdHJpbmdzIG9yIG9iamVjdHMgdG8gbG9nCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKi8KICAgICAgICBfbG9nKC4uLmFyZ3MpIHsKICAgICAgICAgIHRoaXMuX2xvZ2dlcignbG9nJywgYXJncyk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBGYWNhZGVzIGBjb25zb2xlLndhcm5gIGFzIGFuIG92ZXJyaWRlIHBvaW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHsuLi4qfSBhcmdzIEFycmF5IG9mIHN0cmluZ3Mgb3Igb2JqZWN0cyB0byBsb2cKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF93YXJuKC4uLmFyZ3MpIHsKICAgICAgICAgIHRoaXMuX2xvZ2dlcignd2FybicsIGFyZ3MpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRmFjYWRlcyBgY29uc29sZS5lcnJvcmAgYXMgYW4gb3ZlcnJpZGUgcG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gey4uLip9IGFyZ3MgQXJyYXkgb2Ygc3RyaW5ncyBvciBvYmplY3RzIHRvIGxvZwogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2Vycm9yKC4uLmFyZ3MpIHsKICAgICAgICAgIHRoaXMuX2xvZ2dlcignZXJyb3InLCBhcmdzKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEZvcm1hdHMgYSBtZXNzYWdlIHVzaW5nIHRoZSBlbGVtZW50IHR5cGUgYW4gYSBtZXRob2QgbmFtZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBtZXRob2ROYW1lIE1ldGhvZCBuYW1lIHRvIGFzc29jaWF0ZSB3aXRoIG1lc3NhZ2UKICAgICAgICAgKiBAcGFyYW0gey4uLip9IGFyZ3MgQXJyYXkgb2Ygc3RyaW5ncyBvciBvYmplY3RzIHRvIGxvZwogICAgICAgICAqIEByZXR1cm4geyFBcnJheX0gQXJyYXkgd2l0aCBmb3JtYXR0aW5nIGluZm9ybWF0aW9uIGZvciBgY29uc29sZWAKICAgICAgICAgKiAgIGxvZ2dpbmcuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2xvZ2YobWV0aG9kTmFtZSwgLi4uYXJncykgewogICAgICAgICAgcmV0dXJuIFsnWyVzOjolc10nLCB0aGlzLmlzLCBtZXRob2ROYW1lLCAuLi5hcmdzXTsKICAgICAgICB9CgogICAgICB9CgogICAgICBMZWdhY3lFbGVtZW50LnByb3RvdHlwZS5pcyA9ICcnOwoKICAgICAgcmV0dXJuIExlZ2FjeUVsZW1lbnQ7CiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogQ29tcGFyZXMgdGFnIG5hbWVzIGFzY2lpbnVtZXJpY2FsbHkgYnJva2VuIGludG8gY29tcG9uZW50cy4KICAgICAqCiAgICAgKiA8cD5UaGlzIGlzIHRoZSBjb21wYXJpc29uIGZ1bmN0aW9uIHVzZWQgZm9yIHNvcnRpbmcgbW9zdCBzdHJpbmcgdmFsdWVzIGluCiAgICAgKiBUZW5zb3JCb2FyZC4gVW5saWtlIHRoZSBzdGFuZGFyZCBhc2NpaWJldGljYWwgY29tcGFyYXRvciwgdGhpcyBmdW5jdGlvbgogICAgICoga25vd3MgdGhhdCAnYTEwYicgPiAnYTJiJy4gRml4ZWQgcG9pbnQgYW5kIGVuZ2luZWVyaW5nIG5vdGF0aW9uIGFyZQogICAgICogc3VwcG9ydGVkLiBUaGlzIGZ1bmN0aW9uIGFsc28gc3BsaXRzIHRoZSBpbnB1dCBieSBzbGFzaCBhbmQgdW5kZXJzY29yZSB0bwogICAgICogcGVyZm9ybSBhcnJheSBjb21wYXJpc29uLiBUaGVyZWZvcmUgaXQga25vd3MgdGhhdCAnYS9hJyA8ICdhKy9hJyBldmVuCiAgICAgKiB0aG91Z2ggJysnIDwgJy8nIGluIHRoZSBBU0NJSSB0YWJsZS4KICAgICAqLwogICAgZnVuY3Rpb24gY29tcGFyZVRhZ05hbWVzKGEsIGIpIHsKICAgICAgICBsZXQgYWkgPSAwOwogICAgICAgIGxldCBiaSA9IDA7CiAgICAgICAgd2hpbGUgKHRydWUpIHsKICAgICAgICAgICAgaWYgKGFpID09PSBhLmxlbmd0aCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGJpID09PSBiLmxlbmd0aCA/IDAgOiAtMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoYmkgPT09IGIubGVuZ3RoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaXNEaWdpdChhW2FpXSkgJiYgaXNEaWdpdChiW2JpXSkpIHsKICAgICAgICAgICAgICAgIGNvbnN0IGFpcyA9IGFpOwogICAgICAgICAgICAgICAgY29uc3QgYmlzID0gYmk7CiAgICAgICAgICAgICAgICBhaSA9IGNvbnN1bWVOdW1iZXIoYSwgYWkgKyAxKTsKICAgICAgICAgICAgICAgIGJpID0gY29uc3VtZU51bWJlcihiLCBiaSArIDEpOwogICAgICAgICAgICAgICAgY29uc3QgYW4gPSBwYXJzZUZsb2F0KGEuc2xpY2UoYWlzLCBhaSkpOwogICAgICAgICAgICAgICAgY29uc3QgYm4gPSBwYXJzZUZsb2F0KGIuc2xpY2UoYmlzLCBiaSkpOwogICAgICAgICAgICAgICAgaWYgKGFuIDwgYm4pIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoYW4gPiBibikgewogICAgICAgICAgICAgICAgICAgIHJldHVybiAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGlzQnJlYWsoYVthaV0pKSB7CiAgICAgICAgICAgICAgICBpZiAoIWlzQnJlYWsoYltiaV0pKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGlzQnJlYWsoYltiaV0pKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmIChhW2FpXSA8IGJbYmldKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoYVthaV0gPiBiW2JpXSkgewogICAgICAgICAgICAgICAgcmV0dXJuIDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYWkrKzsKICAgICAgICAgICAgYmkrKzsKICAgICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBjb25zdW1lTnVtYmVyKHMsIGkpIHsKICAgICAgICBsZXQgU3RhdGU7CiAgICAgICAgKGZ1bmN0aW9uIChTdGF0ZSkgewogICAgICAgICAgICBTdGF0ZVtTdGF0ZVsiTkFUVVJBTCJdID0gMF0gPSAiTkFUVVJBTCI7CiAgICAgICAgICAgIFN0YXRlW1N0YXRlWyJSRUFMIl0gPSAxXSA9ICJSRUFMIjsKICAgICAgICAgICAgU3RhdGVbU3RhdGVbIkVYUE9ORU5UX1NJR04iXSA9IDJdID0gIkVYUE9ORU5UX1NJR04iOwogICAgICAgICAgICBTdGF0ZVtTdGF0ZVsiRVhQT05FTlQiXSA9IDNdID0gIkVYUE9ORU5UIjsKICAgICAgICB9KShTdGF0ZSB8fCAoU3RhdGUgPSB7fSkpOwogICAgICAgIGxldCBzdGF0ZSA9IFN0YXRlLk5BVFVSQUw7CiAgICAgICAgZm9yICg7IGkgPCBzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGlmIChzdGF0ZSA9PT0gU3RhdGUuTkFUVVJBTCkgewogICAgICAgICAgICAgICAgaWYgKHNbaV0gPT09ICcuJykgewogICAgICAgICAgICAgICAgICAgIHN0YXRlID0gU3RhdGUuUkVBTDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKHNbaV0gPT09ICdlJyB8fCBzW2ldID09PSAnRScpIHsKICAgICAgICAgICAgICAgICAgICBzdGF0ZSA9IFN0YXRlLkVYUE9ORU5UX1NJR047CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmICghaXNEaWdpdChzW2ldKSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHN0YXRlID09PSBTdGF0ZS5SRUFMKSB7CiAgICAgICAgICAgICAgICBpZiAoc1tpXSA9PT0gJ2UnIHx8IHNbaV0gPT09ICdFJykgewogICAgICAgICAgICAgICAgICAgIHN0YXRlID0gU3RhdGUuRVhQT05FTlRfU0lHTjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKCFpc0RpZ2l0KHNbaV0pKSB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoc3RhdGUgPT09IFN0YXRlLkVYUE9ORU5UX1NJR04pIHsKICAgICAgICAgICAgICAgIGlmIChpc0RpZ2l0KHNbaV0pIHx8IHNbaV0gPT09ICcrJyB8fCBzW2ldID09PSAnLScpIHsKICAgICAgICAgICAgICAgICAgICBzdGF0ZSA9IFN0YXRlLkVYUE9ORU5UOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoc3RhdGUgPT09IFN0YXRlLkVYUE9ORU5UKSB7CiAgICAgICAgICAgICAgICBpZiAoIWlzRGlnaXQoc1tpXSkpIHsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gaTsKICAgIH0KICAgIGZ1bmN0aW9uIGlzRGlnaXQoYykgewogICAgICAgIHJldHVybiAnMCcgPD0gYyAmJiBjIDw9ICc5JzsKICAgIH0KICAgIGZ1bmN0aW9uIGlzQnJlYWsoYykgewogICAgICAgIC8vIFRPRE8oQGphcnQpOiBSZW1vdmUgdW5kZXJzY29yZSB3aGVuIHBlb3BsZSBzdG9wIHVzaW5nIGl0IGxpa2UgYSBzbGFzaC4KICAgICAgICByZXR1cm4gYyA9PT0gJy8nIHx8IGMgPT09ICdfJyB8fCBpc0RpZ2l0KGMpOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE1IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY29uc3QgVFlQRVMkMSA9IFtdOwogICAgLyoqIEdpdmVuIGEgUnVuVG9UYWcsIHJldHVybiBzb3J0ZWQgYXJyYXkgb2YgYWxsIHJ1bnMgKi8KICAgIGZ1bmN0aW9uIGdldFJ1bnNOYW1lZChyKSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaC5rZXlzKHIpLnNvcnQoY29tcGFyZVRhZ05hbWVzKTsKICAgIH0KICAgIC8qKiBHaXZlbiBhIFJ1blRvVGFnLCByZXR1cm4gYXJyYXkgb2YgYWxsIHRhZ3MgKHNvcnRlZCArIGRlZHVwJ2QpICovCiAgICBmdW5jdGlvbiBnZXRUYWdzKHIpIHsKICAgICAgICByZXR1cm4gbG9kYXNoLnVuaW9uLmFwcGx5KG51bGwsIGxvZGFzaC52YWx1ZXMocikpLnNvcnQoY29tcGFyZVRhZ05hbWVzKTsKICAgIH0KICAgIC8qKgogICAgICogR2l2ZW4gYSBSdW5Ub1RhZyBhbmQgYW4gYXJyYXkgb2YgcnVucywgcmV0dXJuIGV2ZXJ5IHRhZyB0aGF0IGFwcGVhcnMgZm9yCiAgICAgKiBhdCBsZWFzdCBvbmUgcnVuLgogICAgICogU29ydGVkLCBkZWR1cGxpY2F0ZWQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZpbHRlclRhZ3MociwgcnVucykgewogICAgICAgIGxldCByZXN1bHQgPSBbXTsKICAgICAgICBydW5zLmZvckVhY2goKHgpID0+IChyZXN1bHQgPSByZXN1bHQuY29uY2F0KHJbeF0pKSk7CiAgICAgICAgcmV0dXJuIGxvZGFzaC51bmlxKHJlc3VsdCkuc29ydChjb21wYXJlVGFnTmFtZXMpOwogICAgfQoKICAgIC8qKgogICAgICogTWFuYWdlcyBtYW55IGZldGNoIHJlcXVlc3RzLiBMYXVuY2hlcyB1cCB0byBuU2ltdWx0YW5lb3VzUmVxdWVzdHMKICAgICAqIHNpbXVsdGFuZW91c2x5LCBhbmQgbWFpbnRhaW5zIGEgTElGTyBxdWV1ZSBvZiByZXF1ZXN0cyB0byBwcm9jZXNzIHdoZW4KICAgICAqIG1vcmUgdXJscyBhcmUgcmVxdWVzdGVkIHRoYW4gY2FuIGJlIGhhbmRsZWQgYXQgb25jZS4gVGhlIHF1ZXVlIGNhbiBiZQogICAgICogY2xlYXJlZC4KICAgICAqCiAgICAgKiBXaGVuIGEgcmVxdWVzdCBpcyBtYWRlLCBhIFByb21pc2UgaXMgcmV0dXJuZWQgd2hpY2ggcmVzb2x2ZXMgd2l0aCB0aGUKICAgICAqIHBhcnNlZCBKU09OIHJlc3VsdCBmcm9tIHRoZSByZXF1ZXN0LgogICAgICovCiAgICBjbGFzcyBSZXF1ZXN0Q2FuY2VsbGF0aW9uRXJyb3IgZXh0ZW5kcyBFcnJvciB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMubmFtZSA9ICdSZXF1ZXN0Q2FuY2VsbGF0aW9uRXJyb3InOwogICAgICAgIH0KICAgIH0KICAgIGNsYXNzIEludmFsaWRSZXF1ZXN0T3B0aW9uc0Vycm9yIGV4dGVuZHMgRXJyb3IgewogICAgICAgIGNvbnN0cnVjdG9yKG1zZykgewogICAgICAgICAgICBzdXBlcihtc2cpOwogICAgICAgICAgICB0aGlzLm5hbWUgPSAnSW52YWxpZFJlcXVlc3RPcHRpb25zRXJyb3InOwogICAgICAgICAgICAvLyBUaGUgZm9sbG93aW5nIGlzIG5lZWRlZCBkdWUgdG8gYSBsaW1pdGF0aW9uIG9mIFR5cGVTY3JpcHQgd2hlbgogICAgICAgICAgICAvLyBleHRlbmRpbmcgJ0Vycm9yJy4gU2VlOiBodHRwczovL2dpdGh1Yi5jb20vTWljcm9zb2Z0L1R5cGVTY3JpcHQvd2lraS9CcmVha2luZy1DaGFuZ2VzI2V4dGVuZGluZy1idWlsdC1pbnMtbGlrZS1lcnJvci1hcnJheS1hbmQtbWFwLW1heS1uby1sb25nZXItd29yawogICAgICAgICAgICBPYmplY3Quc2V0UHJvdG90eXBlT2YodGhpcywgSW52YWxpZFJlcXVlc3RPcHRpb25zRXJyb3IucHJvdG90eXBlKTsKICAgICAgICB9CiAgICB9CiAgICBjbGFzcyBSZXF1ZXN0TmV0d29ya0Vycm9yIGV4dGVuZHMgRXJyb3IgewogICAgICAgIGNvbnN0cnVjdG9yKHJlcSwgdXJsKSB7CiAgICAgICAgICAgIHN1cGVyKCk7CiAgICAgICAgICAgIHRoaXMubWVzc2FnZSA9IGBSZXF1ZXN0TmV0d29ya0Vycm9yOiAke3JlcS5zdGF0dXN9IGF0ICR7dXJsfWA7CiAgICAgICAgICAgIHRoaXMubmFtZSA9ICdSZXF1ZXN0TmV0d29ya0Vycm9yJzsKICAgICAgICAgICAgdGhpcy5yZXEgPSByZXE7CiAgICAgICAgICAgIHRoaXMudXJsID0gdXJsOwogICAgICAgIH0KICAgIH0KICAgIC8qKiBUaGUgSFRUUCBtZXRob2QtdHlwZSB0byB1c2UuIEN1cnJlbnRseSBvbmx5ICdHRVQnIGFuZCAnUE9TVCcgYXJlCiAgICAgKiBzdXBwb3J0ZWQuCiAgICAgKi8KICAgIHZhciBIdHRwTWV0aG9kVHlwZTsKICAgIChmdW5jdGlvbiAoSHR0cE1ldGhvZFR5cGUpIHsKICAgICAgICBIdHRwTWV0aG9kVHlwZVsiR0VUIl0gPSAiR0VUIjsKICAgICAgICBIdHRwTWV0aG9kVHlwZVsiUE9TVCJdID0gIlBPU1QiOwogICAgfSkoSHR0cE1ldGhvZFR5cGUgfHwgKEh0dHBNZXRob2RUeXBlID0ge30pKTsKICAgIC8qKgogICAgICogSG9sZHMgb3B0aW9ucyB0aGF0IGNhbiBiZSB1c2VkIHRvIGNvbmZpZ3VyZSB0aGUgSFRUUCByZXF1ZXN0LgogICAgICovCiAgICBjbGFzcyBSZXF1ZXN0T3B0aW9ucyB7CiAgICAgICAgLy8gVmFsaWRhdGVzIHRoaXMgb2JqZWN0LiBUaHJvd3MgSW52YWxpZFJlcXVlc3RPcHRpb25zRXJyb3Igb24gZXJyb3IuCiAgICAgICAgdmFsaWRhdGUoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLm1ldGhvZFR5cGUgPT09IEh0dHBNZXRob2RUeXBlLkdFVCkgewogICAgICAgICAgICAgICAgLy8gV2UgZG9uJ3QgYWxsb3cgYSBib2R5IGZvciBhIEdFVC4KICAgICAgICAgICAgICAgIGlmICh0aGlzLmJvZHkpIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgSW52YWxpZFJlcXVlc3RPcHRpb25zRXJyb3IoJ2JvZHkgbXVzdCBiZSBtaXNzaW5nIGZvciBhIEdFVCByZXF1ZXN0LicpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFdlIGFsbG93IGJvZHktbGVzcyBvciBjb250ZW50VHlwZS1sZXNzIFBPU1RzIGV2ZW4gaWYgdGhleSBkb24ndAogICAgICAgICAgICAvLyBtYWtlIG11Y2ggc2Vuc2UuCiAgICAgICAgfQogICAgfQogICAgY2xhc3MgUmVxdWVzdE1hbmFnZXIgewogICAgICAgIGNvbnN0cnVjdG9yKG5TaW11bHRhbmVvdXNSZXF1ZXN0cyA9IDEwMDAsIG1heFJldHJpZXMgPSAzKSB7CiAgICAgICAgICAgIHRoaXMuX3F1ZXVlID0gW107CiAgICAgICAgICAgIHRoaXMuX25BY3RpdmVSZXF1ZXN0cyA9IDA7CiAgICAgICAgICAgIHRoaXMuX25TaW11bHRhbmVvdXNSZXF1ZXN0cyA9IG5TaW11bHRhbmVvdXNSZXF1ZXN0czsKICAgICAgICAgICAgdGhpcy5fbWF4UmV0cmllcyA9IG1heFJldHJpZXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdpdmVzIGEgcHJvbWlzZSB0aGF0IGxvYWRzIGFzc2V0cyBmcm9tIGdpdmVuIHVybCAocmVzcGVjdHMgcXVldWluZykuIElmCiAgICAgICAgICogcG9zdERhdGEgaXMgcHJvdmlkZWQsIHRoaXMgcmVxdWVzdCB3aWxsIHVzZSBQT1NULCBub3QgR0VULiBUaGlzIGlzIGFuCiAgICAgICAgICogb2JqZWN0IG1hcHBpbmcgUE9TVCBrZXlzIHRvIHN0cmluZyB2YWx1ZXMuCiAgICAgICAgICovCiAgICAgICAgcmVxdWVzdCh1cmwsIHBvc3REYXRhKSB7CiAgICAgICAgICAgIGNvbnN0IHJlcXVlc3RPcHRpb25zID0gcmVxdWVzdE9wdGlvbnNGcm9tUG9zdERhdGEocG9zdERhdGEpOwogICAgICAgICAgICByZXR1cm4gdGhpcy5yZXF1ZXN0V2l0aE9wdGlvbnModXJsLCByZXF1ZXN0T3B0aW9ucyk7CiAgICAgICAgfQogICAgICAgIHJlcXVlc3RXaXRoT3B0aW9ucyh1cmwsIHJlcXVlc3RPcHRpb25zKSB7CiAgICAgICAgICAgIHJlcXVlc3RPcHRpb25zLnZhbGlkYXRlKCk7CiAgICAgICAgICAgIGNvbnN0IHByb21pc2UgPSBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCByZXNvbHZlciA9IHsgcmVzb2x2ZTogcmVzb2x2ZSwgcmVqZWN0OiByZWplY3QgfTsKICAgICAgICAgICAgICAgIHRoaXMuX3F1ZXVlLnB1c2gocmVzb2x2ZXIpOwogICAgICAgICAgICAgICAgdGhpcy5sYXVuY2hSZXF1ZXN0cygpOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLnRoZW4oKCkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucHJvbWlzZVdpdGhSZXRyaWVzKHVybCwgdGhpcy5fbWF4UmV0cmllcywgcmVxdWVzdE9wdGlvbnMpOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLnRoZW4oKHJlc3BvbnNlKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBTdWNjZXNzIC0gTGV0J3MgZnJlZSBzcGFjZSBmb3IgYW5vdGhlciBhY3RpdmUKICAgICAgICAgICAgICAgIC8vIHJlcXVlc3QsIGFuZCBsYXVuY2ggaXQKICAgICAgICAgICAgICAgIHRoaXMuX25BY3RpdmVSZXF1ZXN0cy0tOwogICAgICAgICAgICAgICAgdGhpcy5sYXVuY2hSZXF1ZXN0cygpOwogICAgICAgICAgICAgICAgcmV0dXJuIHJlc3BvbnNlOwogICAgICAgICAgICB9LCAocmVqZWN0aW9uKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAocmVqZWN0aW9uLm5hbWUgPT09ICdSZXF1ZXN0TmV0d29ya0Vycm9yJykgewogICAgICAgICAgICAgICAgICAgIC8vIElmIHdlIGZhaWxlZCBkdWUgdG8gbmV0d29yayBlcnJvciwgd2Ugc2hvdWxkCiAgICAgICAgICAgICAgICAgICAgLy8gZGVjcmVtZW50CiAgICAgICAgICAgICAgICAgICAgLy8gX25BY3RpdmVSZXF1ZXN0cyBiZWNhdXNlIHRoaXMgcmVxdWVzdCB3YXMKICAgICAgICAgICAgICAgICAgICAvLyBhY3RpdmUKICAgICAgICAgICAgICAgICAgICB0aGlzLl9uQWN0aXZlUmVxdWVzdHMtLTsKICAgICAgICAgICAgICAgICAgICB0aGlzLmxhdW5jaFJlcXVlc3RzKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gUHJvbWlzZS5yZWplY3QocmVqZWN0aW9uKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBwcm9taXNlOwogICAgICAgIH0KICAgICAgICBmZXRjaCh1cmwsIGZldGNoT3B0aW9ucykgewogICAgICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgcmVzb2x2ZXIgPSB7IHJlc29sdmU6IHJlc29sdmUsIHJlamVjdDogcmVqZWN0IH07CiAgICAgICAgICAgICAgICB0aGlzLl9xdWV1ZS5wdXNoKHJlc29sdmVyKTsKICAgICAgICAgICAgICAgIHRoaXMubGF1bmNoUmVxdWVzdHMoKTsKICAgICAgICAgICAgfSkudGhlbigoKSA9PiB7CiAgICAgICAgICAgICAgICBsZXQgbnVtVHJpZXMgPSAxOwogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmV0cnlGZXRjaCA9ICgpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgZmV0Y2godXJsLCBmZXRjaE9wdGlvbnMpLnRoZW4oKHJlc3BvbnNlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoIXJlc3BvbnNlLm9rICYmIHRoaXMuX21heFJldHJpZXMgPiBudW1UcmllcykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG51bVRyaWVzKys7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0cnlGZXRjaCgpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc29sdmUocmVzcG9uc2UpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fbkFjdGl2ZVJlcXVlc3RzLS07CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmxhdW5jaFJlcXVlc3RzKCk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgcmV0cnlGZXRjaCgpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBjbGVhclF1ZXVlKCkgewogICAgICAgICAgICB3aGlsZSAodGhpcy5fcXVldWUubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fcXVldWUKICAgICAgICAgICAgICAgICAgICAucG9wKCkKICAgICAgICAgICAgICAgICAgICAucmVqZWN0KG5ldyBSZXF1ZXN0Q2FuY2VsbGF0aW9uRXJyb3IoJ1JlcXVlc3QgY2FuY2VsbGVkIGJ5IGNsZWFyUXVldWUnKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLyogUmV0dXJuIG51bWJlciBvZiBjdXJyZW50bHkgcGVuZGluZyByZXF1ZXN0cyAqLwogICAgICAgIGFjdGl2ZVJlcXVlc3RzKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fbkFjdGl2ZVJlcXVlc3RzOwogICAgICAgIH0KICAgICAgICAvKiBSZXR1cm4gdG90YWwgbnVtYmVyIG9mIG91dHN0YW5kaW5nIHJlcXVlc3RzIChpbmNsdWRlcyBxdWV1ZSkgKi8KICAgICAgICBvdXRzdGFuZGluZ1JlcXVlc3RzKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fbkFjdGl2ZVJlcXVlc3RzICsgdGhpcy5fcXVldWUubGVuZ3RoOwogICAgICAgIH0KICAgICAgICBsYXVuY2hSZXF1ZXN0cygpIHsKICAgICAgICAgICAgd2hpbGUgKHRoaXMuX25BY3RpdmVSZXF1ZXN0cyA8IHRoaXMuX25TaW11bHRhbmVvdXNSZXF1ZXN0cyAmJgogICAgICAgICAgICAgICAgdGhpcy5fcXVldWUubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fbkFjdGl2ZVJlcXVlc3RzKys7CiAgICAgICAgICAgICAgICB0aGlzLl9xdWV1ZS5wb3AoKS5yZXNvbHZlKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogVHJ5IHRvIHJlcXVlc3QgYSBnaXZlbiBVUkwgdXNpbmcgb3ZlcndyaXRhYmxlIF9wcm9taXNlRnJvbVVybCBtZXRob2QuCiAgICAgICAgICogSWYgdGhlIHJlcXVlc3QgZmFpbHMgZm9yIGFueSByZWFzb24sIHdlIHdpbGwgcmV0cnkgdXAgdG8gbWF4UmV0cmllcwogICAgICAgICAqIHRpbWVzLiBJbiBwcmFjdGljZSwgdGhpcyB3aWxsIGhlbHAgdXMgcGFwZXIgb3ZlciB0cmFuc2llbnQgbmV0d29yayBpc3N1ZXMKICAgICAgICAgKiBsaWtlICc1MDIgQmFkIEdhdGV3YXknLgogICAgICAgICAqIEJ5IGRlZmF1bHQsIENocm9tZSBkaXNwbGF5cyBuZXR3b3JrIGVycm9ycyBpbiBjb25zb2xlLCBzbwogICAgICAgICAqIHRoZSB1c2VyIHdpbGwgYmUgYWJsZSB0byB0ZWxsIHdoZW4gdGhlIHJlcXVlc3RzIGFyZSBmYWlsaW5nLiBJIHRoaW5rIHRoaXMKICAgICAgICAgKiBpcyBhIGZlYXR1cmUsIGlmIHRoZSByZXF1ZXN0IGZhaWx1cmVzIGFuZCByZXRyaWVzIGFyZSBjYXVzaW5nIGFueQogICAgICAgICAqIHBhaW4gdG8gdXNlcnMsIHRoZXkgY2FuIHNlZSBpdCBhbmQgZmlsZSBpc3N1ZXMuCiAgICAgICAgICovCiAgICAgICAgcHJvbWlzZVdpdGhSZXRyaWVzKHVybCwgbWF4UmV0cmllcywgcmVxdWVzdE9wdGlvbnMpIHsKICAgICAgICAgICAgdmFyIHN1Y2Nlc3MgPSAoeCkgPT4geDsKICAgICAgICAgICAgdmFyIGZhaWx1cmUgPSAoeCkgPT4gewogICAgICAgICAgICAgICAgaWYgKG1heFJldHJpZXMgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucHJvbWlzZVdpdGhSZXRyaWVzKHVybCwgbWF4UmV0cmllcyAtIDEsIHJlcXVlc3RPcHRpb25zKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBQcm9taXNlLnJlamVjdCh4KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb21pc2VGcm9tVXJsKHVybCwgcmVxdWVzdE9wdGlvbnMpLnRoZW4oc3VjY2VzcywgZmFpbHVyZSk7CiAgICAgICAgfQogICAgICAgIC8qIEFjdHVhbGx5IGdldCBwcm9taXNlIGZyb20gdXJsIHVzaW5nIFhNTEh0dHBSZXF1ZXN0ICovCiAgICAgICAgX3Byb21pc2VGcm9tVXJsKHVybCwgcmVxdWVzdE9wdGlvbnMpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IHJlcSA9IGJ1aWxkWE1MSHR0cFJlcXVlc3QocmVxdWVzdE9wdGlvbnMubWV0aG9kVHlwZSwgdXJsLCByZXF1ZXN0T3B0aW9ucy53aXRoQ3JlZGVudGlhbHMsIHJlcXVlc3RPcHRpb25zLmNvbnRlbnRUeXBlKTsKICAgICAgICAgICAgICAgIHJlcS5vbmxvYWQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHJlcS5zdGF0dXMgPT09IDIwMCkgewogICAgICAgICAgICAgICAgICAgICAgICByZXNvbHZlKEpTT04ucGFyc2UocmVxLnJlc3BvbnNlVGV4dCkpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmVqZWN0KG5ldyBSZXF1ZXN0TmV0d29ya0Vycm9yKHJlcSwgdXJsKSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIHJlcS5vbmVycm9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIHJlamVjdChuZXcgUmVxdWVzdE5ldHdvcmtFcnJvcihyZXEsIHVybCkpOwogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGlmIChyZXF1ZXN0T3B0aW9ucy5ib2R5KSB7CiAgICAgICAgICAgICAgICAgICAgcmVxLnNlbmQocmVxdWVzdE9wdGlvbnMuYm9keSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICByZXEuc2VuZCgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBidWlsZFhNTEh0dHBSZXF1ZXN0KG1ldGhvZFR5cGUsIHVybCwgd2l0aENyZWRlbnRpYWxzLCBjb250ZW50VHlwZSkgewogICAgICAgIGNvbnN0IHJlcSA9IG5ldyBYTUxIdHRwUmVxdWVzdCgpOwogICAgICAgIHJlcS5vcGVuKG1ldGhvZFR5cGUsIHVybCk7CiAgICAgICAgaWYgKHdpdGhDcmVkZW50aWFscykgewogICAgICAgICAgICByZXEud2l0aENyZWRlbnRpYWxzID0gd2l0aENyZWRlbnRpYWxzOwogICAgICAgIH0KICAgICAgICBpZiAoY29udGVudFR5cGUpIHsKICAgICAgICAgICAgcmVxLnNldFJlcXVlc3RIZWFkZXIoJ0NvbnRlbnQtVHlwZScsIGNvbnRlbnRUeXBlKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHJlcTsKICAgIH0KICAgIGZ1bmN0aW9uIHJlcXVlc3RPcHRpb25zRnJvbVBvc3REYXRhKHBvc3REYXRhKSB7CiAgICAgICAgY29uc3QgcmVzdWx0ID0gbmV3IFJlcXVlc3RPcHRpb25zKCk7CiAgICAgICAgaWYgKCFwb3N0RGF0YSkgewogICAgICAgICAgICByZXN1bHQubWV0aG9kVHlwZSA9IEh0dHBNZXRob2RUeXBlLkdFVDsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CiAgICAgICAgcmVzdWx0Lm1ldGhvZFR5cGUgPSBIdHRwTWV0aG9kVHlwZS5QT1NUOwogICAgICAgIHJlc3VsdC5ib2R5ID0gZm9ybURhdGFGcm9tRGljdGlvbmFyeShwb3N0RGF0YSk7CiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KICAgIGZ1bmN0aW9uIGZvcm1EYXRhRnJvbURpY3Rpb25hcnkocG9zdERhdGEpIHsKICAgICAgICBjb25zdCBmb3JtRGF0YSA9IG5ldyBGb3JtRGF0YSgpOwogICAgICAgIGZvciAoY29uc3QgW2tleSwgbWF5YmVWYWx1ZXNdIG9mIE9iamVjdC5lbnRyaWVzKHBvc3REYXRhKSkgewogICAgICAgICAgICBjb25zdCB2YWx1ZXMgPSBBcnJheS5pc0FycmF5KG1heWJlVmFsdWVzKSA/IG1heWJlVmFsdWVzIDogW21heWJlVmFsdWVzXTsKICAgICAgICAgICAgZm9yIChjb25zdCB2YWx1ZSBvZiB2YWx1ZXMpIHsKICAgICAgICAgICAgICAgIGZvcm1EYXRhLmFwcGVuZChrZXksIHZhbHVlKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gZm9ybURhdGE7CiAgICB9CgogICAgY29uc3QgRVhQRVJJTUVOVEFMX1BMVUdJTlNfUVVFUllfUEFSQU0gPSAnZXhwZXJpbWVudGFsUGx1Z2luJzsKICAgIC8qKgogICAgICogU2F2ZSB0aGUgaW5pdGlhbCBVUkwgcXVlcnkgcGFyYW1zLCBiZWZvcmUgdGhlIEFwcFJvdXRpbmdFZmZlY3RzIGluaXRpYWxpemUsCiAgICAgKiBhbmQgYmVmb3JlIGNyZWF0aW5nIHRoZSByb3V0ZXIuCiAgICAgKi8KICAgIGNvbnN0IGluaXRpYWxVUkxTZWFyY2hQYXJhbXMgPSBuZXcgVVJMU2VhcmNoUGFyYW1zKHdpbmRvdy5sb2NhdGlvbi5zZWFyY2gpOwogICAgbGV0IF9yb3V0ZXIgPSBjcmVhdGVSb3V0ZXIoKTsKICAgIC8qKgogICAgICogQ3JlYXRlIGEgcm91dGVyIGZvciBjb21tdW5pY2F0aW5nIHdpdGggdGhlIFRlbnNvckJvYXJkIGJhY2tlbmQuIFlvdQogICAgICogY2FuIHBhc3MgdGhpcyB0byBgc2V0Um91dGVyYCB0byBtYWtlIGl0IHRoZSBnbG9iYWwgcm91dGVyLgogICAgICoKICAgICAqIEBwYXJhbSBkYXRhRGlyIHtzdHJpbmc9fSBUaGUgYmFzZSBwcmVmaXggZm9yIGRhdGEgZW5kcG9pbnRzLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVSb3V0ZXIoZGF0YURpciA9ICdkYXRhJywgdXJsU2VhcmNoUGFyYW1zID0gaW5pdGlhbFVSTFNlYXJjaFBhcmFtcykgewogICAgICAgIGlmIChkYXRhRGlyW2RhdGFEaXIubGVuZ3RoIC0gMV0gPT09ICcvJykgewogICAgICAgICAgICBkYXRhRGlyID0gZGF0YURpci5zbGljZSgwLCBkYXRhRGlyLmxlbmd0aCAtIDEpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gewogICAgICAgICAgICBlbnZpcm9ubWVudDogKCkgPT4gY3JlYXRlRGF0YVBhdGgoZGF0YURpciwgJy9lbnZpcm9ubWVudCcpLAogICAgICAgICAgICBleHBlcmltZW50czogKCkgPT4gY3JlYXRlRGF0YVBhdGgoZGF0YURpciwgJy9leHBlcmltZW50cycpLAogICAgICAgICAgICBwbHVnaW5Sb3V0ZTogKHBsdWdpbk5hbWUsIHJvdXRlLCBwYXJhbXMpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBjcmVhdGVEYXRhUGF0aChkYXRhRGlyICsgJy9wbHVnaW4nLCBgLyR7cGx1Z2luTmFtZX0ke3JvdXRlfWAsIHBhcmFtcyk7CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIHBsdWdpbnNMaXN0aW5nOiAoKSA9PiBjcmVhdGVEYXRhUGF0aChkYXRhRGlyLCAnL3BsdWdpbnNfbGlzdGluZycsIGNyZWF0ZVNlYXJjaFBhcmFtKHsKICAgICAgICAgICAgICAgIFtFWFBFUklNRU5UQUxfUExVR0lOU19RVUVSWV9QQVJBTV06IHVybFNlYXJjaFBhcmFtcy5nZXRBbGwoRVhQRVJJTUVOVEFMX1BMVUdJTlNfUVVFUllfUEFSQU0pLAogICAgICAgICAgICB9KSksCiAgICAgICAgICAgIHJ1bnM6ICgpID0+IGNyZWF0ZURhdGFQYXRoKGRhdGFEaXIsICcvcnVucycpLAogICAgICAgICAgICBydW5zRm9yRXhwZXJpbWVudDogKGlkKSA9PiB7CiAgICAgICAgICAgICAgICByZXR1cm4gY3JlYXRlRGF0YVBhdGgoZGF0YURpciwgJy9leHBlcmltZW50X3J1bnMnLCBjcmVhdGVTZWFyY2hQYXJhbSh7IGV4cGVyaW1lbnQ6IFN0cmluZyhpZCkgfSkpOwogICAgICAgICAgICB9LAogICAgICAgIH07CiAgICB9CiAgICAvKioKICAgICAqIEByZXR1cm4ge1JvdXRlcn0gdGhlIGdsb2JhbCByb3V0ZXIKICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Um91dGVyKCkgewogICAgICAgIHJldHVybiBfcm91dGVyOwogICAgfQogICAgLyoqCiAgICAgKiBTZXQgdGhlIGdsb2JhbCByb3V0ZXIsIHRvIGJlIHJldHVybmVkIGJ5IGZ1dHVyZSBjYWxscyB0byBgZ2V0Um91dGVyYC4KICAgICAqIFlvdSBtYXkgd2lzaCB0byBpbnZva2UgdGhpcyBpZiB5b3UgYXJlIHJ1bm5pbmcgYSBkZW1vIHNlcnZlciB3aXRoIGEKICAgICAqIGN1c3RvbSBwYXRoIHByZWZpeCwgb3IgaWYgeW91IGhhdmUgY3VzdG9taXplZCB0aGUgVGVuc29yQm9hcmQgYmFja2VuZAogICAgICogdG8gdXNlIGEgZGlmZmVyZW50IHBhdGguCiAgICAgKgogICAgICogQHBhcmFtIHtSb3V0ZXJ9IHJvdXRlciB0aGUgbmV3IGdsb2JhbCByb3V0ZXIKICAgICAqLwogICAgZnVuY3Rpb24gc2V0Um91dGVyKHJvdXRlcikgewogICAgICAgIGlmIChyb3V0ZXIgPT0gbnVsbCkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ1JvdXRlciByZXF1aXJlZCwgYnV0IGdvdDogJyArIHJvdXRlcik7CiAgICAgICAgfQogICAgICAgIF9yb3V0ZXIgPSByb3V0ZXI7CiAgICB9CiAgICBmdW5jdGlvbiBjcmVhdGVEYXRhUGF0aChkYXRhRGlyLCByb3V0ZSwgcGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcygpKSB7CiAgICAgICAgbGV0IHJlbGF0aXZlUGF0aCA9IGRhdGFEaXIgKyByb3V0ZTsKICAgICAgICBpZiAoU3RyaW5nKHBhcmFtcykpIHsKICAgICAgICAgICAgY29uc3QgZGVsaW1pdGVyID0gcm91dGUuaW5jbHVkZXMoJz8nKSA/ICcmJyA6ICc/JzsKICAgICAgICAgICAgcmVsYXRpdmVQYXRoICs9IGRlbGltaXRlciArIFN0cmluZyhwYXJhbXMpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gcmVsYXRpdmVQYXRoOwogICAgfQogICAgZnVuY3Rpb24gY3JlYXRlU2VhcmNoUGFyYW0ocGFyYW1zID0ge30pIHsKICAgICAgICBjb25zdCBrZXlzID0gT2JqZWN0LmtleXMocGFyYW1zKQogICAgICAgICAgICAuc29ydCgpCiAgICAgICAgICAgIC5maWx0ZXIoKGspID0+IHBhcmFtc1trXSk7CiAgICAgICAgY29uc3Qgc2VhcmNoUGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcygpOwogICAgICAgIGtleXMuZm9yRWFjaCgoa2V5KSA9PiB7CiAgICAgICAgICAgIGNvbnN0IHZhbHVlcyA9IHBhcmFtc1trZXldOwogICAgICAgICAgICBjb25zdCBhcnJheSA9IEFycmF5LmlzQXJyYXkodmFsdWVzKSA/IHZhbHVlcyA6IFt2YWx1ZXNdOwogICAgICAgICAgICBhcnJheS5mb3JFYWNoKCh2YWwpID0+IHNlYXJjaFBhcmFtcy5hcHBlbmQoa2V5LCB2YWwpKTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gc2VhcmNoUGFyYW1zOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE3IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgdmFyIENhdGVnb3J5VHlwZTsKICAgIChmdW5jdGlvbiAoQ2F0ZWdvcnlUeXBlKSB7CiAgICAgICAgQ2F0ZWdvcnlUeXBlW0NhdGVnb3J5VHlwZVsiU0VBUkNIX1JFU1VMVFMiXSA9IDBdID0gIlNFQVJDSF9SRVNVTFRTIjsKICAgICAgICBDYXRlZ29yeVR5cGVbQ2F0ZWdvcnlUeXBlWyJQUkVGSVhfR1JPVVAiXSA9IDFdID0gIlBSRUZJWF9HUk9VUCI7CiAgICB9KShDYXRlZ29yeVR5cGUgfHwgKENhdGVnb3J5VHlwZSA9IHt9KSk7CiAgICAvKioKICAgICAqIENvbXB1dGUgYSBjYXRlZ29yeSBjb250YWluaW5nIHRoZSBzZWFyY2ggcmVzdWx0cyBmb3IgdGhlIGdpdmVuIHF1ZXJ5LgogICAgICovCiAgICBmdW5jdGlvbiBjYXRlZ29yaXplQnlTZWFyY2hRdWVyeSh4cywgcXVlcnkpIHsKICAgICAgICBjb25zdCByZSA9ICgoKSA9PiB7CiAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IFJlZ0V4cChxdWVyeSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgfSkoKTsKICAgICAgICByZXR1cm4gewogICAgICAgICAgICBuYW1lOiBxdWVyeSwKICAgICAgICAgICAgbWV0YWRhdGE6IHsKICAgICAgICAgICAgICAgIHR5cGU6IENhdGVnb3J5VHlwZS5TRUFSQ0hfUkVTVUxUUywKICAgICAgICAgICAgICAgIHZhbGlkUmVnZXg6ICEhcmUsCiAgICAgICAgICAgICAgICB1bml2ZXJzYWxSZWdleDogcXVlcnkgPT09ICcuKicsCiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIGl0ZW1zOiByZSA/IHhzLmZpbHRlcigoeCkgPT4geC5tYXRjaChyZSkpIDogW10sCiAgICAgICAgfTsKICAgIH0KICAgIC8qKgogICAgICogQ29tcHV0ZSB0aGUgcXVvdGllbnQgc2V0ICRYL3tcc2ltfSQsIHdoZXJlICRhIFxzaW0gYiQgaWYgJGEkIGFuZCAkYiQKICAgICAqIHNoYXJlIGEgY29tbW9uIGBzZXBhcmF0b3JgLXByZWZpeC4gT3JkZXIgaXMgcHJlc2VydmVkLgogICAgICovCiAgICBmdW5jdGlvbiBjYXRlZ29yaXplQnlQcmVmaXgoeHMsIHNlcGFyYXRvciA9ICcvJykgewogICAgICAgIGNvbnN0IGNhdGVnb3JpZXMgPSBbXTsKICAgICAgICBjb25zdCBjYXRlZ29yaWVzQnlOYW1lID0ge307CiAgICAgICAgeHMuZm9yRWFjaCgoeCkgPT4gewogICAgICAgICAgICBjb25zdCBpbmRleCA9IHguaW5kZXhPZihzZXBhcmF0b3IpOwogICAgICAgICAgICBjb25zdCBuYW1lID0gaW5kZXggPj0gMCA/IHguc2xpY2UoMCwgaW5kZXgpIDogeDsKICAgICAgICAgICAgaWYgKCFjYXRlZ29yaWVzQnlOYW1lW25hbWVdKSB7CiAgICAgICAgICAgICAgICBjb25zdCBjYXRlZ29yeSA9IHsKICAgICAgICAgICAgICAgICAgICBuYW1lLAogICAgICAgICAgICAgICAgICAgIG1ldGFkYXRhOiB7IHR5cGU6IENhdGVnb3J5VHlwZS5QUkVGSVhfR1JPVVAgfSwKICAgICAgICAgICAgICAgICAgICBpdGVtczogW10sCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgY2F0ZWdvcmllc0J5TmFtZVtuYW1lXSA9IGNhdGVnb3J5OwogICAgICAgICAgICAgICAgY2F0ZWdvcmllcy5wdXNoKGNhdGVnb3J5KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjYXRlZ29yaWVzQnlOYW1lW25hbWVdLml0ZW1zLnB1c2goeCk7CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGNhdGVnb3JpZXM7CiAgICB9CiAgICAvKgogICAgICogQ29tcHV0ZSB0aGUgc3RhbmRhcmQgY2F0ZWdvcml6YXRpb24gb2YgdGhlIGdpdmVuIGlucHV0LCBpbmNsdWRpbmcKICAgICAqIGJvdGggc2VhcmNoIGNhdGVnb3JpZXMgYW5kIHByZWZpeCBjYXRlZ29yaWVzLgogICAgICovCiAgICBmdW5jdGlvbiBjYXRlZ29yaXplKHhzLCBxdWVyeSA9ICcnKSB7CiAgICAgICAgY29uc3QgYnlGaWx0ZXIgPSBbY2F0ZWdvcml6ZUJ5U2VhcmNoUXVlcnkoeHMsIHF1ZXJ5KV07CiAgICAgICAgY29uc3QgYnlQcmVmaXggPSBjYXRlZ29yaXplQnlQcmVmaXgoeHMpOwogICAgICAgIHJldHVybiBbXS5jb25jYXQoYnlGaWx0ZXIsIGJ5UHJlZml4KTsKICAgIH0KICAgIGZ1bmN0aW9uIGNhdGVnb3JpemVUYWdzKHJ1blRvVGFnLCBzZWxlY3RlZFJ1bnMsIHF1ZXJ5KSB7CiAgICAgICAgY29uc3QgdGFncyA9IGdldFRhZ3MocnVuVG9UYWcpOwogICAgICAgIGNvbnN0IGNhdGVnb3JpZXMgPSBjYXRlZ29yaXplKHRhZ3MsIHF1ZXJ5KTsKICAgICAgICBjb25zdCB0YWdUb1J1bnMgPSBjcmVhdGVUYWdUb1J1bnMobG9kYXNoLnBpY2socnVuVG9UYWcsIHNlbGVjdGVkUnVucykpOwogICAgICAgIHJldHVybiBjYXRlZ29yaWVzLm1hcCgoeyBuYW1lLCBtZXRhZGF0YSwgaXRlbXMgfSkgPT4gKHsKICAgICAgICAgICAgbmFtZSwKICAgICAgICAgICAgbWV0YWRhdGEsCiAgICAgICAgICAgIGl0ZW1zOiBpdGVtcy5tYXAoKHRhZykgPT4gKHsKICAgICAgICAgICAgICAgIHRhZywKICAgICAgICAgICAgICAgIHJ1bnM6ICh0YWdUb1J1bnMuZ2V0KHRhZykgfHwgW10pLnNsaWNlKCksCiAgICAgICAgICAgIH0pKSwKICAgICAgICB9KSk7CiAgICB9CiAgICBmdW5jdGlvbiBjcmVhdGVUYWdUb1J1bnMocnVuVG9UYWcpIHsKICAgICAgICBjb25zdCB0YWdUb1J1biA9IG5ldyBNYXAoKTsKICAgICAgICBPYmplY3Qua2V5cyhydW5Ub1RhZykuZm9yRWFjaCgocnVuKSA9PiB7CiAgICAgICAgICAgIHJ1blRvVGFnW3J1bl0uZm9yRWFjaCgodGFnKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBydW5zID0gdGFnVG9SdW4uZ2V0KHRhZykgfHwgW107CiAgICAgICAgICAgICAgICBydW5zLnB1c2gocnVuKTsKICAgICAgICAgICAgICAgIHRhZ1RvUnVuLnNldCh0YWcsIHJ1bnMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gdGFnVG9SdW47CiAgICB9CiAgICBmdW5jdGlvbiBjb21wYXJlVGFnUnVuKGEsIGIpIHsKICAgICAgICBjb25zdCBjID0gY29tcGFyZVRhZ05hbWVzKGEudGFnLCBiLnRhZyk7CiAgICAgICAgaWYgKGMgIT0gMCkgewogICAgICAgICAgICByZXR1cm4gYzsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGNvbXBhcmVUYWdOYW1lcyhhLnJ1biwgYi5ydW4pOwogICAgfQogICAgZnVuY3Rpb24gY2F0ZWdvcml6ZVJ1blRhZ0NvbWJpbmF0aW9ucyhydW5Ub1RhZywgc2VsZWN0ZWRSdW5zLCBxdWVyeSkgewogICAgICAgIGNvbnN0IHRhZ0NhdGVnb3JpZXMgPSBjYXRlZ29yaXplVGFncyhydW5Ub1RhZywgc2VsZWN0ZWRSdW5zLCBxdWVyeSk7CiAgICAgICAgZnVuY3Rpb24gZXhwbG9kZUNhdGVnb3J5KHRhZ0NhdGVnb3J5KSB7CiAgICAgICAgICAgIGNvbnN0IGl0ZW1zID0gbG9kYXNoLmZsYXR0ZW4odGFnQ2F0ZWdvcnkuaXRlbXMubWFwKCh7IHRhZywgcnVucyB9KSA9PiBydW5zLm1hcCgocnVuKSA9PiAoeyB0YWcsIHJ1biB9KSkpKTsKICAgICAgICAgICAgaXRlbXMuc29ydChjb21wYXJlVGFnUnVuKTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIG5hbWU6IHRhZ0NhdGVnb3J5Lm5hbWUsCiAgICAgICAgICAgICAgICBtZXRhZGF0YTogdGFnQ2F0ZWdvcnkubWV0YWRhdGEsCiAgICAgICAgICAgICAgICBpdGVtcywKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRhZ0NhdGVnb3JpZXMubWFwKGV4cGxvZGVDYXRlZ29yeSk7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCBsaWZlY3ljbGVQcm9wcyA9IHsKICAgICAgYXR0YWNoZWQ6IHRydWUsCiAgICAgIGRldGFjaGVkOiB0cnVlLAogICAgICByZWFkeTogdHJ1ZSwKICAgICAgY3JlYXRlZDogdHJ1ZSwKICAgICAgYmVmb3JlUmVnaXN0ZXI6IHRydWUsCiAgICAgIHJlZ2lzdGVyZWQ6IHRydWUsCiAgICAgIGF0dHJpYnV0ZUNoYW5nZWQ6IHRydWUsCiAgICAgIGxpc3RlbmVyczogdHJ1ZSwKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHRydWUKICAgIH07CgogICAgY29uc3QgZXhjbHVkZU9uSW5mbyA9IHsKICAgICAgYXR0YWNoZWQ6IHRydWUsCiAgICAgIGRldGFjaGVkOiB0cnVlLAogICAgICByZWFkeTogdHJ1ZSwKICAgICAgY3JlYXRlZDogdHJ1ZSwKICAgICAgYmVmb3JlUmVnaXN0ZXI6IHRydWUsCiAgICAgIHJlZ2lzdGVyZWQ6IHRydWUsCiAgICAgIGF0dHJpYnV0ZUNoYW5nZWQ6IHRydWUsCiAgICAgIGJlaGF2aW9yczogdHJ1ZSwKICAgICAgX25vQWNjZXNzb3JzOiB0cnVlCiAgICB9OwoKICAgIGNvbnN0IGV4Y2x1ZGVPbkJlaGF2aW9ycyA9IE9iamVjdC5hc3NpZ24oewogICAgICBsaXN0ZW5lcnM6IHRydWUsCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB0cnVlLAogICAgICBwcm9wZXJ0aWVzOiB0cnVlLAogICAgICBvYnNlcnZlcnM6IHRydWUsCiAgICB9LCBleGNsdWRlT25JbmZvKTsKCiAgICBmdW5jdGlvbiBjb3B5UHJvcGVydGllcyhzb3VyY2UsIHRhcmdldCwgZXhjbHVkZVByb3BzKSB7CiAgICAgIGNvbnN0IG5vQWNjZXNzb3JzID0gc291cmNlLl9ub0FjY2Vzc29yczsKICAgICAgY29uc3QgcHJvcGVydHlOYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKHNvdXJjZSk7CiAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcHJvcGVydHlOYW1lcy5sZW5ndGg7IGkrKykgewogICAgICAgIGxldCBwID0gcHJvcGVydHlOYW1lc1tpXTsKICAgICAgICBpZiAocCBpbiBleGNsdWRlUHJvcHMpIHsKICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgIH0KICAgICAgICBpZiAobm9BY2Nlc3NvcnMpIHsKICAgICAgICAgIHRhcmdldFtwXSA9IHNvdXJjZVtwXTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgbGV0IHBkID0gT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihzb3VyY2UsIHApOwogICAgICAgICAgaWYgKHBkKSB7CiAgICAgICAgICAgIC8vIGVuc3VyZSBwcm9wZXJ0eSBpcyBjb25maWd1cmFibGUgc28gdGhhdCBhIGxhdGVyIGJlaGF2aW9yIGNhbgogICAgICAgICAgICAvLyByZS1jb25maWd1cmUgaXQuCiAgICAgICAgICAgIHBkLmNvbmZpZ3VyYWJsZSA9IHRydWU7CiAgICAgICAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eSh0YXJnZXQsIHAsIHBkKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEFwcGxpZXMgYSAibGVnYWN5IiBiZWhhdmlvciBvciBhcnJheSBvZiBiZWhhdmlvcnMgdG8gdGhlIHByb3ZpZGVkIGNsYXNzLgogICAgICoKICAgICAqIE5vdGU6IHRoaXMgbWV0aG9kIHdpbGwgYXV0b21hdGljYWxseSBhbHNvIGFwcGx5IHRoZSBgTGVnYWN5RWxlbWVudE1peGluYAogICAgICogdG8gZW5zdXJlIHRoYXQgYW55IGxlZ2FjeSBiZWhhdmlvcnMgY2FuIHJlbHkgb24gbGVnYWN5IFBvbHltZXIgQVBJIG9uCiAgICAgKiB0aGUgdW5kZXJseWluZyBlbGVtZW50LgogICAgICoKICAgICAqIEBmdW5jdGlvbgogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7IU9iamVjdHwhQXJyYXk8IU9iamVjdD59IGJlaGF2aW9ycyBCZWhhdmlvciBvYmplY3Qgb3IgYXJyYXkgb2YgYmVoYXZpb3JzLgogICAgICogQHBhcmFtIHtmdW5jdGlvbihuZXc6VCl9IGtsYXNzIEVsZW1lbnQgY2xhc3MuCiAgICAgKiBAcmV0dXJuIHs/fSBSZXR1cm5zIGEgbmV3IEVsZW1lbnQgY2xhc3MgZXh0ZW5kZWQgYnkgdGhlCiAgICAgKiBwYXNzZWQgaW4gYGJlaGF2aW9yc2AgYW5kIGFsc28gYnkgYExlZ2FjeUVsZW1lbnRNaXhpbmAuCiAgICAgKiBAc3VwcHJlc3Mge2ludmFsaWRDYXN0cywgY2hlY2tUeXBlc30KICAgICAqLwogICAgZnVuY3Rpb24gbWl4aW5CZWhhdmlvcnMoYmVoYXZpb3JzLCBrbGFzcykgewogICAgICByZXR1cm4gR2VuZXJhdGVDbGFzc0Zyb21JbmZvKHt9LCBMZWdhY3lFbGVtZW50TWl4aW4oa2xhc3MpLCBiZWhhdmlvcnMpOwogICAgfQoKICAgIC8vIE5PVEU6CiAgICAvLyAxLngKICAgIC8vIEJlaGF2aW9ycyB3ZXJlIG1peGVkIGluICppbiByZXZlcnNlIG9yZGVyKiBhbmQgZGUtZHVwZWQgb24gdGhlIGZseS4KICAgIC8vIFRoZSBydWxlIHdhcyB0aGF0IGJlaGF2aW9yIHByb3BlcnRpZXMgd2VyZSBjb3BpZWQgb250byB0aGUgZWxlbWVudAogICAgLy8gcHJvdG90eXBlIGlmIGFuZCBvbmx5IGlmIHRoZSBwcm9wZXJ0eSBkaWQgbm90IGFscmVhZHkgZXhpc3QuCiAgICAvLyBHaXZlbjogUG9seW1lcnsgYmVoYXZpb3JzOiBbQSwgQiwgQywgQSwgQl19LCBwcm9wZXJ0eSBjb3B5IG9yZGVyIHdhczoKICAgIC8vICgxKSwgQiwgKDIpLCBBLCAoMykgQy4gVGhpcyBtZWFucyBwcm90b3R5cGUgcHJvcGVydGllcyB3aW4gb3ZlcgogICAgLy8gQiBwcm9wZXJ0aWVzIHdpbiBvdmVyIEEgd2luIG92ZXIgQy4gVGhpcyBtaXJyb3JzIHdoYXQgd291bGQgaGFwcGVuCiAgICAvLyB3aXRoIGluaGVyaXRhbmNlIGlmIGVsZW1lbnQgZXh0ZW5kZWQgQiBleHRlbmRlZCBBIGV4dGVuZGVkIEMuCiAgICAvLwogICAgLy8gQWdhaW4gZ2l2ZW4sIFBvbHltZXJ7IGJlaGF2aW9yczogW0EsIEIsIEMsIEEsIEJdfSwgdGhlIHJlc3VsdGluZwogICAgLy8gYGJlaGF2aW9yc2AgYXJyYXkgd2FzIFtDLCBBLCBCXS4KICAgIC8vIEJlaGF2aW9yIGxpZmVjeWNsZSBtZXRob2RzIHdlcmUgY2FsbGVkIGluIGJlaGF2aW9yIGFycmF5IG9yZGVyCiAgICAvLyBmb2xsb3dlZCBieSB0aGUgZWxlbWVudCwgZS5nLiAoMSkgQy5jcmVhdGVkLCAoMikgQS5jcmVhdGVkLAogICAgLy8gKDMpIEIuY3JlYXRlZCwgKDQpIGVsZW1lbnQuY3JlYXRlZC4gVGhlcmUgd2FzIG5vIHN1cHBvcnQgZm9yCiAgICAvLyBzdXBlciwgYW5kICJzdXBlci1iZWhhdmlvciIgbWV0aG9kcyB3ZXJlIGNhbGxhYmxlIG9ubHkgYnkgbmFtZSkuCiAgICAvLwogICAgLy8gMi54CiAgICAvLyBCZWhhdmlvcnMgYXJlIG1hZGUgaW50byBwcm9wZXIgbWl4aW5zIHdoaWNoIGxpdmUgaW4gdGhlCiAgICAvLyBlbGVtZW50J3MgcHJvdG90eXBlIGNoYWluLiBCZWhhdmlvcnMgYXJlIHBsYWNlZCBpbiB0aGUgZWxlbWVudCBwcm90b3R5cGUKICAgIC8vIGVsZGVzdCB0byB5b3VuZ2VzdCBhbmQgZGUtZHVwZWQgeW91bmdlc3QgdG8gb2xkZXN0OgogICAgLy8gU28sIGZpcnN0IFtBLCBCLCBDLCBBLCBCXSBiZWNvbWVzIFtDLCBBLCBCXSB0aGVuLAogICAgLy8gdGhlIGVsZW1lbnQgcHJvdG90eXBlIGJlY29tZXMgKG9sZGVzdCkgKDEpIFBvbHltZXJFbGVtZW50LCAoMikgY2xhc3MoQyksCiAgICAvLyAoMykgY2xhc3MoQSksICg0KSBjbGFzcyhCKSwgKDUpIGNsYXNzKFBvbHltZXIoey4uLn0pKS4KICAgIC8vIFJlc3VsdDoKICAgIC8vIFRoaXMgbWVhbnMgZWxlbWVudCBwcm9wZXJ0aWVzIHdpbiBvdmVyIEIgcHJvcGVydGllcyB3aW4gb3ZlciBBIHdpbgogICAgLy8gb3ZlciBDLiAoc2FtZSBhcyAxLngpCiAgICAvLyBJZiBsaWZlY3ljbGUgaXMgY2FsbGVkIChzdXBlciB0aGVuIG1lKSwgb3JkZXIgaXMKICAgIC8vICgxKSBDLmNyZWF0ZWQsICgyKSBBLmNyZWF0ZWQsICgzKSBCLmNyZWF0ZWQsICg0KSBlbGVtZW50LmNyZWF0ZWQKICAgIC8vIChhZ2FpbiBzYW1lIGFzIDEueCkKICAgIGZ1bmN0aW9uIGFwcGx5QmVoYXZpb3JzKHByb3RvLCBiZWhhdmlvcnMsIGxpZmVjeWNsZSkgewogICAgICBmb3IgKGxldCBpPTA7IGk8YmVoYXZpb3JzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgYXBwbHlJbmZvKHByb3RvLCBiZWhhdmlvcnNbaV0sIGxpZmVjeWNsZSwgZXhjbHVkZU9uQmVoYXZpb3JzKTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGFwcGx5SW5mbyhwcm90bywgaW5mbywgbGlmZWN5Y2xlLCBleGNsdWRlUHJvcHMpIHsKICAgICAgY29weVByb3BlcnRpZXMoaW5mbywgcHJvdG8sIGV4Y2x1ZGVQcm9wcyk7CiAgICAgIGZvciAobGV0IHAgaW4gbGlmZWN5Y2xlUHJvcHMpIHsKICAgICAgICBpZiAoaW5mb1twXSkgewogICAgICAgICAgbGlmZWN5Y2xlW3BdID0gbGlmZWN5Y2xlW3BdIHx8IFtdOwogICAgICAgICAgbGlmZWN5Y2xlW3BdLnB1c2goaW5mb1twXSk7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBAcGFyYW0ge0FycmF5fSBiZWhhdmlvcnMgTGlzdCBvZiBiZWhhdmlvcnMgdG8gZmxhdHRlbi4KICAgICAqIEBwYXJhbSB7QXJyYXk9fSBsaXN0IFRhcmdldCBsaXN0IHRvIGZsYXR0ZW4gYmVoYXZpb3JzIGludG8uCiAgICAgKiBAcGFyYW0ge0FycmF5PX0gZXhjbHVkZSBMaXN0IG9mIGJlaGF2aW9ycyB0byBleGNsdWRlIGZyb20gdGhlIGxpc3QuCiAgICAgKiBAcmV0dXJuIHshQXJyYXl9IFJldHVybnMgdGhlIGxpc3Qgb2YgZmxhdHRlbmVkIGJlaGF2aW9ycy4KICAgICAqLwogICAgZnVuY3Rpb24gZmxhdHRlbkJlaGF2aW9ycyhiZWhhdmlvcnMsIGxpc3QsIGV4Y2x1ZGUpIHsKICAgICAgbGlzdCA9IGxpc3QgfHwgW107CiAgICAgIGZvciAobGV0IGk9YmVoYXZpb3JzLmxlbmd0aC0xOyBpID49IDA7IGktLSkgewogICAgICAgIGxldCBiID0gYmVoYXZpb3JzW2ldOwogICAgICAgIGlmIChiKSB7CiAgICAgICAgICBpZiAoQXJyYXkuaXNBcnJheShiKSkgewogICAgICAgICAgICBmbGF0dGVuQmVoYXZpb3JzKGIsIGxpc3QpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gZGVkdXAKICAgICAgICAgICAgaWYgKGxpc3QuaW5kZXhPZihiKSA8IDAgJiYgKCFleGNsdWRlIHx8IGV4Y2x1ZGUuaW5kZXhPZihiKSA8IDApKSB7CiAgICAgICAgICAgICAgbGlzdC51bnNoaWZ0KGIpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGNvbnNvbGUud2FybignYmVoYXZpb3IgaXMgbnVsbCwgY2hlY2sgZm9yIG1pc3Npbmcgb3IgNDA0IGltcG9ydCcpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gbGlzdDsKICAgIH0KCiAgICAvKioKICAgICAqIENvcGllcyBwcm9wZXJ0eSBkZXNjcmlwdG9ycyBmcm9tIHNvdXJjZSB0byB0YXJnZXQsIG92ZXJ3cml0aW5nIGFsbCBmaWVsZHMKICAgICAqIG9mIGFueSBwcmV2aW91cyBkZXNjcmlwdG9yIGZvciBhIHByb3BlcnR5ICpleGNlcHQqIGZvciBgdmFsdWVgLCB3aGljaCBpcwogICAgICogbWVyZ2VkIGluIGZyb20gdGhlIHRhcmdldCBpZiBpdCBkb2VzIG5vdCBleGlzdCBvbiB0aGUgc291cmNlLgogICAgICoKICAgICAqIEBwYXJhbSB7Kn0gdGFyZ2V0IFRhcmdldCBwcm9wZXJ0aWVzIG9iamVjdAogICAgICogQHBhcmFtIHsqfSBzb3VyY2UgU291cmNlIHByb3BlcnRpZXMgb2JqZWN0CiAgICAgKi8KICAgIGZ1bmN0aW9uIG1lcmdlUHJvcGVydGllcyh0YXJnZXQsIHNvdXJjZSkgewogICAgICBmb3IgKGNvbnN0IHAgaW4gc291cmNlKSB7CiAgICAgICAgY29uc3QgdGFyZ2V0SW5mbyA9IHRhcmdldFtwXTsKICAgICAgICBjb25zdCBzb3VyY2VJbmZvID0gc291cmNlW3BdOwogICAgICAgIGlmICghKCd2YWx1ZScgaW4gc291cmNlSW5mbykgJiYgdGFyZ2V0SW5mbyAmJiAoJ3ZhbHVlJyBpbiB0YXJnZXRJbmZvKSkgewogICAgICAgICAgdGFyZ2V0W3BdID0gT2JqZWN0LmFzc2lnbih7dmFsdWU6IHRhcmdldEluZm8udmFsdWV9LCBzb3VyY2VJbmZvKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGFyZ2V0W3BdID0gc291cmNlSW5mbzsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBjb25zdCBMZWdhY3lFbGVtZW50ID0gTGVnYWN5RWxlbWVudE1peGluKEhUTUxFbGVtZW50KTsKCiAgICAvKiBOb3RlIGFib3V0IGNvbnN0cnVjdGlvbiBhbmQgZXh0ZW5zaW9uIG9mIGxlZ2FjeSBjbGFzc2VzLgogICAgICBbQ2hhbmdlZCBpbiBRNCAyMDE4IHRvIG9wdGltaXplIHBlcmZvcm1hbmNlLl0KCiAgICAgIFdoZW4gY2FsbGluZyBgUG9seW1lcmAgb3IgYG1peGluQmVoYXZpb3JzYCwgdGhlIGdlbmVyYXRlZCBjbGFzcyBiZWxvdyBpcwogICAgICBtYWRlLiBUaGUgbGlzdCBvZiBiZWhhdmlvcnMgd2FzIHByZXZpb3VzbHkgbWFkZSBpbnRvIG9uZSBnZW5lcmF0ZWQgY2xhc3MgcGVyCiAgICAgIGJlaGF2aW9yLCBidXQgdGhpcyBpcyBubyBsb25nZXIgdGhlIGNhc2UgYXMgYmVoYXZpb3JzIGFyZSBub3cgY2FsbGVkCiAgICAgIG1hbnVhbGx5LiBOb3RlLCB0aGVyZSBtYXkgKnN0aWxsKiBiZSBtdWx0aXBsZSBnZW5lcmF0ZWQgY2xhc3NlcyBpbiB0aGUKICAgICAgZWxlbWVudCdzIHByb3RvdHlwZSBjaGFpbiBpZiBleHRlbnNpb24gaXMgdXNlZCB3aXRoIGBtaXhpbkJlaGF2aW9yc2AuCgogICAgICBUaGUgZ2VuZXJhdGVkIGNsYXNzIGlzIGRpcmVjdGx5IHRpZWQgdG8gdGhlIGluZm8gb2JqZWN0IGFuZCBiZWhhdmlvcnMKICAgICAgdXNlZCB0byBjcmVhdGUgaXQuIFRoYXQgbGlzdCBvZiBiZWhhdmlvcnMgaXMgZmlsdGVyZWQgc28gaXQncyBvbmx5IHRoZQogICAgICBiZWhhdmlvcnMgbm90IGFjdGl2ZSBvbiB0aGUgc3VwZXJjbGFzcy4gSW4gb3JkZXIgdG8gY2FsbCB0aHJvdWdoIHRvIHRoZQogICAgICBlbnRpcmUgbGlzdCBvZiBsaWZlY3ljbGUgbWV0aG9kcywgaXQncyBpbXBvcnRhbnQgdG8gY2FsbCBgc3VwZXJgLgoKICAgICAgVGhlIGVsZW1lbnQncyBgcHJvcGVydGllc2AgYW5kIGBvYnNlcnZlcnNgIGFyZSBjb250cm9sbGVkIHZpYSB0aGUgZmluYWxpemF0aW9uCiAgICAgIG1lY2hhbmlzbSBwcm92aWRlZCBieSBgUHJvcGVydGllc01peGluYC4gYFByb3BlcnRpZXNgIGFuZCBgb2JzZXJ2ZXJzYCBhcmUKICAgICAgY29sbGVjdGVkIGJ5IG1hbnVhbGx5IHRyYXZlcnNpbmcgdGhlIHByb3RvdHlwZSBjaGFpbiBhbmQgbWVyZ2luZy4KCiAgICAgIFRvIGxpbWl0IGNoYW5nZXMsIHRoZSBgX3JlZ2lzdGVyZWRgIG1ldGhvZCBpcyBjYWxsZWQgdmlhIGBfaW5pdGlhbGl6ZVByb3BlcnRpZXNgCiAgICAgIGFuZCBub3QgYF9maW5hbGl6ZUNsYXNzYC4KCiAgICAqLwogICAgLyoqCiAgICAgKiBAcGFyYW0geyFQb2x5bWVySW5pdH0gaW5mbyBQb2x5bWVyIGluZm8gb2JqZWN0CiAgICAgKiBAcGFyYW0ge2Z1bmN0aW9uKG5ldzpIVE1MRWxlbWVudCl9IEJhc2UgYmFzZSBjbGFzcyB0byBleHRlbmQgd2l0aCBpbmZvIG9iamVjdAogICAgICogQHBhcmFtIHtPYmplY3Q9fSBiZWhhdmlvcnMgYmVoYXZpb3JzIHRvIGNvcHkgaW50byB0aGUgZWxlbWVudAogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OkhUTUxFbGVtZW50KX0gR2VuZXJhdGVkIGNsYXNzCiAgICAgKiBAc3VwcHJlc3Mge2NoZWNrVHlwZXN9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBHZW5lcmF0ZUNsYXNzRnJvbUluZm8oaW5mbywgQmFzZSwgYmVoYXZpb3JzKSB7CgogICAgICAvLyBtYW5hZ2VzIGJlaGF2aW9yIGFuZCBsaWZlY3ljbGUgcHJvY2Vzc2luZyAoZmlsbGVkIGluIGFmdGVyIGNsYXNzIGRlZmluaXRpb24pCiAgICAgIGxldCBiZWhhdmlvckxpc3Q7CiAgICAgIGNvbnN0IGxpZmVjeWNsZSA9IHt9OwoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGNsYXNzIFBvbHltZXJHZW5lcmF0ZWQgZXh0ZW5kcyBCYXNlIHsKCiAgICAgICAgLy8gZXhwbGljaXRseSBub3QgY2FsbGluZyBzdXBlci5fZmluYWxpemVDbGFzcwogICAgICAgIC8qKiBAbm9jb2xsYXBzZSAqLwogICAgICAgIHN0YXRpYyBfZmluYWxpemVDbGFzcygpIHsKICAgICAgICAgIC8vIGlmIGNhbGxpbmcgdmlhIGEgc3ViY2xhc3MgdGhhdCBoYXNuJ3QgYmVlbiBnZW5lcmF0ZWQsIHBhc3MgdGhyb3VnaCB0byBzdXBlcgogICAgICAgICAgaWYgKCF0aGlzLmhhc093blByb3BlcnR5KEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ2dlbmVyYXRlZEZyb20nLCB0aGlzKSkpIHsKICAgICAgICAgICAgLy8gVE9ETyhodHRwczovL2dpdGh1Yi5jb20vZ29vZ2xlL2Nsb3N1cmUtY29tcGlsZXIvaXNzdWVzLzMyNDApOgogICAgICAgICAgICAvLyAgICAgQ2hhbmdlIGJhY2sgdG8ganVzdCBzdXBlci5tZXRob2RDYWxsKCkKICAgICAgICAgICAgQmFzZS5fZmluYWxpemVDbGFzcy5jYWxsKHRoaXMpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gaW50ZXJsZWF2ZSBwcm9wZXJ0aWVzIGFuZCBvYnNlcnZlcnMgcGVyIGJlaGF2aW9yIGFuZCBgaW5mb2AKICAgICAgICAgICAgaWYgKGJlaGF2aW9yTGlzdCkgewogICAgICAgICAgICAgIGZvciAobGV0IGk9MCwgYjsgaSA8IGJlaGF2aW9yTGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgYiA9IGJlaGF2aW9yTGlzdFtpXTsKICAgICAgICAgICAgICAgIGlmIChiLnByb3BlcnRpZXMpIHsKICAgICAgICAgICAgICAgICAgdGhpcy5jcmVhdGVQcm9wZXJ0aWVzKGIucHJvcGVydGllcyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoYi5vYnNlcnZlcnMpIHsKICAgICAgICAgICAgICAgICAgdGhpcy5jcmVhdGVPYnNlcnZlcnMoYi5vYnNlcnZlcnMsIGIucHJvcGVydGllcyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChpbmZvLnByb3BlcnRpZXMpIHsKICAgICAgICAgICAgICB0aGlzLmNyZWF0ZVByb3BlcnRpZXMoaW5mby5wcm9wZXJ0aWVzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaW5mby5vYnNlcnZlcnMpIHsKICAgICAgICAgICAgICB0aGlzLmNyZWF0ZU9ic2VydmVycyhpbmZvLm9ic2VydmVycywgaW5mby5wcm9wZXJ0aWVzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBtYWtlIHN1cmUgdG8gcHJlcGFyZSB0aGUgZWxlbWVudCB0ZW1wbGF0ZQogICAgICAgICAgICB0aGlzLl9wcmVwYXJlVGVtcGxhdGUoKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKiBAbm9jb2xsYXBzZSAqLwogICAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICAgIGNvbnN0IHByb3BlcnRpZXMgPSB7fTsKICAgICAgICAgIGlmIChiZWhhdmlvckxpc3QpIHsKICAgICAgICAgICAgZm9yIChsZXQgaT0wOyBpIDwgYmVoYXZpb3JMaXN0Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgbWVyZ2VQcm9wZXJ0aWVzKHByb3BlcnRpZXMsIGJlaGF2aW9yTGlzdFtpXS5wcm9wZXJ0aWVzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgbWVyZ2VQcm9wZXJ0aWVzKHByb3BlcnRpZXMsIGluZm8ucHJvcGVydGllcyk7CiAgICAgICAgICByZXR1cm4gcHJvcGVydGllczsKICAgICAgICB9CgogICAgICAgIC8qKiBAbm9jb2xsYXBzZSAqLwogICAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgICAgbGV0IG9ic2VydmVycyA9IFtdOwogICAgICAgICAgaWYgKGJlaGF2aW9yTGlzdCkgewogICAgICAgICAgICBmb3IgKGxldCBpPTAsIGI7IGkgPCBiZWhhdmlvckxpc3QubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICBiID0gYmVoYXZpb3JMaXN0W2ldOwogICAgICAgICAgICAgIGlmIChiLm9ic2VydmVycykgewogICAgICAgICAgICAgICAgb2JzZXJ2ZXJzID0gb2JzZXJ2ZXJzLmNvbmNhdChiLm9ic2VydmVycyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaW5mby5vYnNlcnZlcnMpIHsKICAgICAgICAgICAgb2JzZXJ2ZXJzID0gb2JzZXJ2ZXJzLmNvbmNhdChpbmZvLm9ic2VydmVycyk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gb2JzZXJ2ZXJzOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBjcmVhdGVkKCkgewogICAgICAgICAgc3VwZXIuY3JlYXRlZCgpOwogICAgICAgICAgY29uc3QgbGlzdCA9IGxpZmVjeWNsZS5jcmVhdGVkOwogICAgICAgICAgaWYgKGxpc3QpIHsKICAgICAgICAgICAgZm9yIChsZXQgaT0wOyBpIDwgbGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgIGxpc3RbaV0uY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBfcmVnaXN0ZXJlZCgpIHsKICAgICAgICAgIC8qIE5PVEU6IGBiZWZvcmVSZWdpc3RlcmAgaXMgY2FsbGVkIGhlcmUgZm9yIGJjLCBidXQgdGhlIGJlaGF2aW9yCiAgICAgICAgICAgIGlzIGRpZmZlcmVudCB0aGFuIGluIDEueC4gSW4gMS4wLCB0aGUgbWV0aG9kIHdhcyBjYWxsZWQgKmFmdGVyKgogICAgICAgICAgICBtaXhpbmcgcHJvdG90eXBlcyB0b2dldGhlciBidXQgKmJlZm9yZSogcHJvY2Vzc2luZyBvZiBtZXRhLW9iamVjdHMuCiAgICAgICAgICAgIEhvd2V2ZXIsIGR5bmFtaWMgZWZmZWN0cyBjYW4gc3RpbGwgYmUgc2V0IGhlcmUgYW5kIGNhbiBiZSBkb25lIGVpdGhlcgogICAgICAgICAgICBpbiBgYmVmb3JlUmVnaXN0ZXJgIG9yIGByZWdpc3RlcmVkYC4gSXQgaXMgbm8gbG9uZ2VyIHBvc3NpYmxlIHRvIHNldAogICAgICAgICAgICBgaXNgIGluIGBiZWZvcmVSZWdpc3RlcmAgYXMgeW91IGNvdWxkIGluIDEueC4KICAgICAgICAgICovCiAgICAgICAgICAvLyBvbmx5IHByb2NlZWQgaWYgdGhlIGdlbmVyYXRlZCBjbGFzcycgcHJvdG90eXBlIGhhcyBub3QgYmVlbiByZWdpc3RlcmVkLgogICAgICAgICAgY29uc3QgZ2VuZXJhdGVkUHJvdG8gPSBQb2x5bWVyR2VuZXJhdGVkLnByb3RvdHlwZTsKICAgICAgICAgIGlmICghZ2VuZXJhdGVkUHJvdG8uaGFzT3duUHJvcGVydHkoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnX19oYXNSZWdpc3RlckZpbmlzaGVkJywgZ2VuZXJhdGVkUHJvdG8pKSkgewogICAgICAgICAgICBnZW5lcmF0ZWRQcm90by5fX2hhc1JlZ2lzdGVyRmluaXNoZWQgPSB0cnVlOwogICAgICAgICAgICAvLyBlbnN1cmUgc3VwZXJjbGFzcyBpcyByZWdpc3RlcmVkIGZpcnN0LgogICAgICAgICAgICBzdXBlci5fcmVnaXN0ZXJlZCgpOwogICAgICAgICAgICAvLyBjb3B5IHByb3BlcnRpZXMgb250byB0aGUgZ2VuZXJhdGVkIGNsYXNzIGxhemlseSBpZiB3ZSdyZSBvcHRpbWl6aW5nLAogICAgICAgICAgICBpZiAobGVnYWN5T3B0aW1pemF0aW9ucykgewogICAgICAgICAgICAgIGNvcHlQcm9wZXJ0aWVzVG9Qcm90byhnZW5lcmF0ZWRQcm90byk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gbWFrZSBzdXJlIGxlZ2FjeSBsaWZlY3ljbGUgaXMgY2FsbGVkIG9uIHRoZSAqZWxlbWVudConcyBwcm90b3R5cGUKICAgICAgICAgICAgLy8gYW5kIG5vdCB0aGUgZ2VuZXJhdGVkIGNsYXNzIHByb3RvdHlwZTsgaWYgdGhlIGVsZW1lbnQgaGFzIGJlZW4KICAgICAgICAgICAgLy8gZXh0ZW5kZWQsIHRoZXNlIGFyZSAqbm90KiB0aGUgc2FtZS4KICAgICAgICAgICAgY29uc3QgcHJvdG8gPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YodGhpcyk7CiAgICAgICAgICAgIGxldCBsaXN0ID0gbGlmZWN5Y2xlLmJlZm9yZVJlZ2lzdGVyOwogICAgICAgICAgICBpZiAobGlzdCkgewogICAgICAgICAgICAgIGZvciAobGV0IGk9MDsgaSA8IGxpc3QubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGxpc3RbaV0uY2FsbChwcm90byk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGxpc3QgPSBsaWZlY3ljbGUucmVnaXN0ZXJlZDsKICAgICAgICAgICAgaWYgKGxpc3QpIHsKICAgICAgICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBsaXN0Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBsaXN0W2ldLmNhbGwocHJvdG8pOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBfYXBwbHlMaXN0ZW5lcnMoKSB7CiAgICAgICAgICBzdXBlci5fYXBwbHlMaXN0ZW5lcnMoKTsKICAgICAgICAgIGNvbnN0IGxpc3QgPSBsaWZlY3ljbGUubGlzdGVuZXJzOwogICAgICAgICAgaWYgKGxpc3QpIHsKICAgICAgICAgICAgZm9yIChsZXQgaT0wOyBpIDwgbGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgIGNvbnN0IGxpc3RlbmVycyA9IGxpc3RbaV07CiAgICAgICAgICAgICAgaWYgKGxpc3RlbmVycykgewogICAgICAgICAgICAgICAgZm9yIChsZXQgbCBpbiBsaXN0ZW5lcnMpIHsKICAgICAgICAgICAgICAgICAgdGhpcy5fYWRkTWV0aG9kRXZlbnRMaXN0ZW5lclRvTm9kZSh0aGlzLCBsLCBsaXN0ZW5lcnNbbF0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gbm90ZTogZXhjZXB0aW9uIHRvICJzdXBlciB0aGVuIG1lIiBydWxlOwogICAgICAgIC8vIGRvIHdvcmsgYmVmb3JlIGNhbGxpbmcgc3VwZXIgc28gdGhhdCBzdXBlciBhdHRyaWJ1dGVzCiAgICAgICAgLy8gb25seSBhcHBseSBpZiBub3QgYWxyZWFkeSBzZXQuCiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBfZW5zdXJlQXR0cmlidXRlcygpIHsKICAgICAgICAgIGNvbnN0IGxpc3QgPSBsaWZlY3ljbGUuaG9zdEF0dHJpYnV0ZXM7CiAgICAgICAgICBpZiAobGlzdCkgewogICAgICAgICAgICBmb3IgKGxldCBpPWxpc3QubGVuZ3RoLTE7IGkgPj0gMDsgaS0tKSB7CiAgICAgICAgICAgICAgY29uc3QgaG9zdEF0dHJpYnV0ZXMgPSBsaXN0W2ldOwogICAgICAgICAgICAgIGZvciAobGV0IGEgaW4gaG9zdEF0dHJpYnV0ZXMpIHsKICAgICAgICAgICAgICAgICAgdGhpcy5fZW5zdXJlQXR0cmlidXRlKGEsIGhvc3RBdHRyaWJ1dGVzW2FdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgc3VwZXIuX2Vuc3VyZUF0dHJpYnV0ZXMoKTsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgcmVhZHkoKSB7CiAgICAgICAgICBzdXBlci5yZWFkeSgpOwogICAgICAgICAgbGV0IGxpc3QgPSBsaWZlY3ljbGUucmVhZHk7CiAgICAgICAgICBpZiAobGlzdCkgewogICAgICAgICAgICBmb3IgKGxldCBpPTA7IGkgPCBsaXN0Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgbGlzdFtpXS5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGF0dGFjaGVkKCkgewogICAgICAgICAgc3VwZXIuYXR0YWNoZWQoKTsKICAgICAgICAgIGxldCBsaXN0ID0gbGlmZWN5Y2xlLmF0dGFjaGVkOwogICAgICAgICAgaWYgKGxpc3QpIHsKICAgICAgICAgICAgZm9yIChsZXQgaT0wOyBpIDwgbGlzdC5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgIGxpc3RbaV0uY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBkZXRhY2hlZCgpIHsKICAgICAgICAgIHN1cGVyLmRldGFjaGVkKCk7CiAgICAgICAgICBsZXQgbGlzdCA9IGxpZmVjeWNsZS5kZXRhY2hlZDsKICAgICAgICAgIGlmIChsaXN0KSB7CiAgICAgICAgICAgIGZvciAobGV0IGk9MDsgaSA8IGxpc3QubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICBsaXN0W2ldLmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIEltcGxlbWVudHMgbmF0aXZlIEN1c3RvbSBFbGVtZW50cyBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCB0bwogICAgICAgICAqIHNldCBhbiBhdHRyaWJ1dGUgdmFsdWUgdG8gYSBwcm9wZXJ0eSB2aWEgYF9hdHRyaWJ1dGVUb1Byb3BlcnR5YC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgYXR0cmlidXRlIHRoYXQgY2hhbmdlZAogICAgICAgICAqIEBwYXJhbSB7P3N0cmluZ30gb2xkIE9sZCBhdHRyaWJ1dGUgdmFsdWUKICAgICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlIE5ldyBhdHRyaWJ1dGUgdmFsdWUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGF0dHJpYnV0ZUNoYW5nZWQobmFtZSwgb2xkLCB2YWx1ZSkgewogICAgICAgICAgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZCgpOwogICAgICAgICAgbGV0IGxpc3QgPSBsaWZlY3ljbGUuYXR0cmlidXRlQ2hhbmdlZDsKICAgICAgICAgIGlmIChsaXN0KSB7CiAgICAgICAgICAgIGZvciAobGV0IGk9MDsgaSA8IGxpc3QubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICBsaXN0W2ldLmNhbGwodGhpcywgbmFtZSwgb2xkLCB2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIGFwcGx5IGJlaGF2aW9ycywgbm90ZSBhY3R1YWwgY29weWluZyBpcyBkb25lIGxhemlseSBhdCBmaXJzdCBpbnN0YW5jZSBjcmVhdGlvbgogICAgICBpZiAoYmVoYXZpb3JzKSB7CiAgICAgICAgLy8gTk9URTogZW5zdXJlIHRoZSBiZWhhdmlvciBpcyBleHRlbmRpbmcgYSBjbGFzcyB3aXRoCiAgICAgICAgLy8gbGVnYWN5IGVsZW1lbnQgYXBpLiBUaGlzIGlzIG5lY2Vzc2FyeSBzaW5jZSBiZWhhdmlvcnMgZXhwZWN0IHRvIGJlIGFibGUKICAgICAgICAvLyB0byBhY2Nlc3MgMS54IGxlZ2FjeSBhcGkuCiAgICAgICAgaWYgKCFBcnJheS5pc0FycmF5KGJlaGF2aW9ycykpIHsKICAgICAgICAgIGJlaGF2aW9ycyA9IFtiZWhhdmlvcnNdOwogICAgICAgIH0KICAgICAgICBsZXQgc3VwZXJCZWhhdmlvcnMgPSBCYXNlLnByb3RvdHlwZS5iZWhhdmlvcnM7CiAgICAgICAgLy8gZ2V0IGZsYXR0ZW5lZCwgZGVkdXBlZCBsaXN0IG9mIGJlaGF2aW9ycyAqbm90KiBhbHJlYWR5IG9uIHN1cGVyIGNsYXNzCiAgICAgICAgYmVoYXZpb3JMaXN0ID0gZmxhdHRlbkJlaGF2aW9ycyhiZWhhdmlvcnMsIG51bGwsIHN1cGVyQmVoYXZpb3JzKTsKICAgICAgICBQb2x5bWVyR2VuZXJhdGVkLnByb3RvdHlwZS5iZWhhdmlvcnMgPSBzdXBlckJlaGF2aW9ycyA/CiAgICAgICAgICBzdXBlckJlaGF2aW9ycy5jb25jYXQoYmVoYXZpb3JzKSA6IGJlaGF2aW9yTGlzdDsKICAgICAgfQoKICAgICAgY29uc3QgY29weVByb3BlcnRpZXNUb1Byb3RvID0gKHByb3RvKSA9PiB7CiAgICAgICAgaWYgKGJlaGF2aW9yTGlzdCkgewogICAgICAgICAgYXBwbHlCZWhhdmlvcnMocHJvdG8sIGJlaGF2aW9yTGlzdCwgbGlmZWN5Y2xlKTsKICAgICAgICB9CiAgICAgICAgYXBwbHlJbmZvKHByb3RvLCBpbmZvLCBsaWZlY3ljbGUsIGV4Y2x1ZGVPbkluZm8pOwogICAgICB9OwoKICAgICAgLy8gY29weSBwcm9wZXJ0aWVzIGlmIHdlJ3JlIG5vdCBvcHRpbWl6aW5nCiAgICAgIGlmICghbGVnYWN5T3B0aW1pemF0aW9ucykgewogICAgICAgIGNvcHlQcm9wZXJ0aWVzVG9Qcm90byhQb2x5bWVyR2VuZXJhdGVkLnByb3RvdHlwZSk7CiAgICAgIH0KCiAgICAgIFBvbHltZXJHZW5lcmF0ZWQuZ2VuZXJhdGVkRnJvbSA9IGluZm87CgogICAgICByZXR1cm4gUG9seW1lckdlbmVyYXRlZDsKICAgIH0KCiAgICAvKioKICAgICAqIEdlbmVyYXRlcyBhIGNsYXNzIHRoYXQgZXh0ZW5kcyBgTGVnYWN5RWxlbWVudGAgYmFzZWQgb24gdGhlCiAgICAgKiBwcm92aWRlZCBpbmZvIG9iamVjdC4gIE1ldGFkYXRhIG9iamVjdHMgb24gdGhlIGBpbmZvYCBvYmplY3QKICAgICAqIChgcHJvcGVydGllc2AsIGBvYnNlcnZlcnNgLCBgbGlzdGVuZXJzYCwgYGJlaGF2aW9yc2AsIGBpc2ApIGFyZSB1c2VkCiAgICAgKiBmb3IgUG9seW1lcidzIG1ldGEtcHJvZ3JhbW1pbmcgc3lzdGVtcywgYW5kIGFueSBmdW5jdGlvbnMgYXJlIGNvcGllZAogICAgICogdG8gdGhlIGdlbmVyYXRlZCBjbGFzcy4KICAgICAqCiAgICAgKiBWYWxpZCAibWV0YWRhdGEiIHZhbHVlcyBhcmUgYXMgZm9sbG93czoKICAgICAqCiAgICAgKiBgaXNgOiBTdHJpbmcgcHJvdmlkaW5nIHRoZSB0YWcgbmFtZSB0byByZWdpc3RlciB0aGUgZWxlbWVudCB1bmRlci4gSW4KICAgICAqIGFkZGl0aW9uLCBpZiBhIGBkb20tbW9kdWxlYCB3aXRoIHRoZSBzYW1lIGlkIGV4aXN0cywgdGhlIGZpcnN0IHRlbXBsYXRlCiAgICAgKiBpbiB0aGF0IGBkb20tbW9kdWxlYCB3aWxsIGJlIHN0YW1wZWQgaW50byB0aGUgc2hhZG93IHJvb3Qgb2YgdGhpcyBlbGVtZW50LAogICAgICogd2l0aCBzdXBwb3J0IGZvciBkZWNsYXJhdGl2ZSBldmVudCBsaXN0ZW5lcnMgKGBvbi0uLi5gKSwgUG9seW1lciBkYXRhCiAgICAgKiBiaW5kaW5ncyAoYFtbLi4uXV1gIGFuZCBge3suLi59fWApLCBhbmQgaWQtYmFzZWQgbm9kZSBmaW5kaW5nIGludG8KICAgICAqIGB0aGlzLiRgLgogICAgICoKICAgICAqIGBwcm9wZXJ0aWVzYDogT2JqZWN0IGRlc2NyaWJpbmcgcHJvcGVydHktcmVsYXRlZCBtZXRhZGF0YSB1c2VkIGJ5IFBvbHltZXIKICAgICAqIGZlYXR1cmVzIChrZXk6IHByb3BlcnR5IG5hbWVzLCB2YWx1ZTogb2JqZWN0IGNvbnRhaW5pbmcgcHJvcGVydHkgbWV0YWRhdGEpLgogICAgICogVmFsaWQga2V5cyBpbiBwZXItcHJvcGVydHkgbWV0YWRhdGEgaW5jbHVkZToKICAgICAqIC0gYHR5cGVgIChTdHJpbmd8TnVtYmVyfE9iamVjdHxBcnJheXwuLi4pOiBVc2VkIGJ5CiAgICAgKiAgIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHRvIGRldGVybWluZSBob3cgc3RyaW5nLWJhc2VkIGF0dHJpYnV0ZXMKICAgICAqICAgYXJlIGRlc2VyaWFsaXplZCB0byBKYXZhU2NyaXB0IHByb3BlcnR5IHZhbHVlcy4KICAgICAqIC0gYG5vdGlmeWAgKGJvb2xlYW4pOiBDYXVzZXMgYSBjaGFuZ2UgaW4gdGhlIHByb3BlcnR5IHRvIGZpcmUgYQogICAgICogICBub24tYnViYmxpbmcgZXZlbnQgY2FsbGVkIGA8cHJvcGVydHk+LWNoYW5nZWRgLiBFbGVtZW50cyB0aGF0IGhhdmUKICAgICAqICAgZW5hYmxlZCB0d28td2F5IGJpbmRpbmcgdG8gdGhlIHByb3BlcnR5IHVzZSB0aGlzIGV2ZW50IHRvIG9ic2VydmUgY2hhbmdlcy4KICAgICAqIC0gYHJlYWRPbmx5YCAoYm9vbGVhbik6IENyZWF0ZXMgYSBnZXR0ZXIgZm9yIHRoZSBwcm9wZXJ0eSwgYnV0IG5vIHNldHRlci4KICAgICAqICAgVG8gc2V0IGEgcmVhZC1vbmx5IHByb3BlcnR5LCB1c2UgdGhlIHByaXZhdGUgc2V0dGVyIG1ldGhvZAogICAgICogICBgX3NldFByb3BlcnR5KHByb3BlcnR5LCB2YWx1ZSlgLgogICAgICogLSBgb2JzZXJ2ZXJgIChzdHJpbmcpOiBPYnNlcnZlciBtZXRob2QgbmFtZSB0aGF0IHdpbGwgYmUgY2FsbGVkIHdoZW4KICAgICAqICAgdGhlIHByb3BlcnR5IGNoYW5nZXMuIFRoZSBhcmd1bWVudHMgb2YgdGhlIG1ldGhvZCBhcmUKICAgICAqICAgYCh2YWx1ZSwgcHJldmlvdXNWYWx1ZSlgLgogICAgICogLSBgY29tcHV0ZWRgIChzdHJpbmcpOiBTdHJpbmcgZGVzY3JpYmluZyBtZXRob2QgYW5kIGRlcGVuZGVudCBwcm9wZXJ0aWVzCiAgICAgKiAgIGZvciBjb21wdXRpbmcgdGhlIHZhbHVlIG9mIHRoaXMgcHJvcGVydHkgKGUuZy4gYCdjb21wdXRlRm9vKGJhciwgem90KSdgKS4KICAgICAqICAgQ29tcHV0ZWQgcHJvcGVydGllcyBhcmUgcmVhZC1vbmx5IGJ5IGRlZmF1bHQgYW5kIGNhbiBvbmx5IGJlIGNoYW5nZWQKICAgICAqICAgdmlhIHRoZSByZXR1cm4gdmFsdWUgb2YgdGhlIGNvbXB1dGluZyBtZXRob2QuCiAgICAgKgogICAgICogYG9ic2VydmVyc2A6IEFycmF5IG9mIHN0cmluZ3MgZGVzY3JpYmluZyBtdWx0aS1wcm9wZXJ0eSBvYnNlcnZlciBtZXRob2RzCiAgICAgKiAgYW5kIHRoZWlyIGRlcGVuZGVudCBwcm9wZXJ0aWVzIChlLmcuIGAnb2JzZXJ2ZUFCQyhhLCBiLCBjKSdgKS4KICAgICAqCiAgICAgKiBgbGlzdGVuZXJzYDogT2JqZWN0IGRlc2NyaWJpbmcgZXZlbnQgbGlzdGVuZXJzIHRvIGJlIGFkZGVkIHRvIGVhY2gKICAgICAqICBpbnN0YW5jZSBvZiB0aGlzIGVsZW1lbnQgKGtleTogZXZlbnQgbmFtZSwgdmFsdWU6IG1ldGhvZCBuYW1lKS4KICAgICAqCiAgICAgKiBgYmVoYXZpb3JzYDogQXJyYXkgb2YgYWRkaXRpb25hbCBgaW5mb2Agb2JqZWN0cyBjb250YWluaW5nIG1ldGFkYXRhCiAgICAgKiBhbmQgY2FsbGJhY2tzIGluIHRoZSBzYW1lIGZvcm1hdCBhcyB0aGUgYGluZm9gIG9iamVjdCBoZXJlIHdoaWNoIGFyZQogICAgICogbWVyZ2VkIGludG8gdGhpcyBlbGVtZW50LgogICAgICoKICAgICAqIGBob3N0QXR0cmlidXRlc2A6IE9iamVjdCBsaXN0aW5nIGF0dHJpYnV0ZXMgdG8gYmUgYXBwbGllZCB0byB0aGUgaG9zdAogICAgICogIG9uY2UgY3JlYXRlZCAoa2V5OiBhdHRyaWJ1dGUgbmFtZSwgdmFsdWU6IGF0dHJpYnV0ZSB2YWx1ZSkuICBWYWx1ZXMKICAgICAqICBhcmUgc2VyaWFsaXplZCBiYXNlZCBvbiB0aGUgdHlwZSBvZiB0aGUgdmFsdWUuICBIb3N0IGF0dHJpYnV0ZXMgc2hvdWxkCiAgICAgKiAgZ2VuZXJhbGx5IGJlIGxpbWl0ZWQgdG8gYXR0cmlidXRlcyBzdWNoIGFzIGB0YWJJbmRleGAgYW5kIGBhcmlhLS4uLmAuCiAgICAgKiAgQXR0cmlidXRlcyBpbiBgaG9zdEF0dHJpYnV0ZXNgIGFyZSBvbmx5IGFwcGxpZWQgaWYgYSB1c2VyLXN1cHBsaWVkCiAgICAgKiAgYXR0cmlidXRlIGlzIG5vdCBhbHJlYWR5IHByZXNlbnQgKGF0dHJpYnV0ZXMgaW4gbWFya3VwIG92ZXJyaWRlCiAgICAgKiAgYGhvc3RBdHRyaWJ1dGVzYCkuCiAgICAgKgogICAgICogSW4gYWRkaXRpb24sIHRoZSBmb2xsb3dpbmcgUG9seW1lci1zcGVjaWZpYyBjYWxsYmFja3MgbWF5IGJlIHByb3ZpZGVkOgogICAgICogLSBgcmVnaXN0ZXJlZGA6IGNhbGxlZCBhZnRlciBmaXJzdCBpbnN0YW5jZSBvZiB0aGlzIGVsZW1lbnQsCiAgICAgKiAtIGBjcmVhdGVkYDogY2FsbGVkIGR1cmluZyBgY29uc3RydWN0b3JgCiAgICAgKiAtIGBhdHRhY2hlZGA6IGNhbGxlZCBkdXJpbmcgYGNvbm5lY3RlZENhbGxiYWNrYAogICAgICogLSBgZGV0YWNoZWRgOiBjYWxsZWQgZHVyaW5nIGBkaXNjb25uZWN0ZWRDYWxsYmFja2AKICAgICAqIC0gYHJlYWR5YDogY2FsbGVkIGJlZm9yZSBmaXJzdCBgYXR0YWNoZWRgLCBhZnRlciBhbGwgcHJvcGVydGllcyBvZgogICAgICogICB0aGlzIGVsZW1lbnQgaGF2ZSBiZWVuIHByb3BhZ2F0ZWQgdG8gaXRzIHRlbXBsYXRlIGFuZCBhbGwgb2JzZXJ2ZXJzCiAgICAgKiAgIGhhdmUgcnVuCiAgICAgKgogICAgICogQHBhcmFtIHshUG9seW1lckluaXR9IGluZm8gT2JqZWN0IGNvbnRhaW5pbmcgUG9seW1lciBtZXRhZGF0YSBhbmQgZnVuY3Rpb25zCiAgICAgKiAgIHRvIGJlY29tZSBjbGFzcyBtZXRob2RzLgogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24oVCk6VH0gbWl4aW4gT3B0aW9uYWwgbWl4aW4gdG8gYXBwbHkgdG8gbGVnYWN5IGJhc2UgY2xhc3MKICAgICAqICAgYmVmb3JlIGV4dGVuZGluZyB3aXRoIFBvbHltZXIgbWV0YXByb2dyYW1taW5nLgogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OkhUTUxFbGVtZW50KX0gR2VuZXJhdGVkIGNsYXNzCiAgICAgKi8KICAgIGNvbnN0IENsYXNzID0gZnVuY3Rpb24oaW5mbywgbWl4aW4pIHsKICAgICAgaWYgKCFpbmZvKSB7CiAgICAgICAgY29uc29sZS53YXJuKCdQb2x5bWVyLkNsYXNzIHJlcXVpcmVzIGBpbmZvYCBhcmd1bWVudCcpOwogICAgICB9CiAgICAgIGxldCBrbGFzcyA9IG1peGluID8gbWl4aW4oTGVnYWN5RWxlbWVudCkgOgogICAgICAgICAgTGVnYWN5RWxlbWVudDsKICAgICAga2xhc3MgPSBHZW5lcmF0ZUNsYXNzRnJvbUluZm8oaW5mbywga2xhc3MsIGluZm8uYmVoYXZpb3JzKTsKICAgICAgLy8gZGVjb3JhdGUga2xhc3Mgd2l0aCByZWdpc3RyYXRpb24gaW5mbwogICAgICBrbGFzcy5pcyA9IGtsYXNzLnByb3RvdHlwZS5pcyA9IGluZm8uaXM7CiAgICAgIHJldHVybiBrbGFzczsKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIExlZ2FjeSBjbGFzcyBmYWN0b3J5IGFuZCByZWdpc3RyYXRpb24gaGVscGVyIGZvciBkZWZpbmluZyBQb2x5bWVyCiAgICAgKiBlbGVtZW50cy4KICAgICAqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyBlcXVpdmFsZW50IHRvCiAgICAgKgogICAgICogICAgIGltcG9ydCB7Q2xhc3N9IGZyb20gJ0Bwb2x5bWVyL3BvbHltZXIvbGliL2xlZ2FjeS9jbGFzcy5qcyc7CiAgICAgKiAgICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKGluZm8uaXMsIENsYXNzKGluZm8pKTsKICAgICAqCiAgICAgKiBTZWUgYENsYXNzYCBmb3IgZGV0YWlscyBvbiB2YWxpZCBsZWdhY3kgbWV0YWRhdGEgZm9ybWF0IGZvciBgaW5mb2AuCiAgICAgKgogICAgICogQGdsb2JhbAogICAgICogQG92ZXJyaWRlCiAgICAgKiBAZnVuY3Rpb24KICAgICAqIEBwYXJhbSB7IVBvbHltZXJJbml0fSBpbmZvIE9iamVjdCBjb250YWluaW5nIFBvbHltZXIgbWV0YWRhdGEgYW5kIGZ1bmN0aW9ucwogICAgICogICB0byBiZWNvbWUgY2xhc3MgbWV0aG9kcy4KICAgICAqIEByZXR1cm4ge2Z1bmN0aW9uKG5ldzogSFRNTEVsZW1lbnQpfSBHZW5lcmF0ZWQgY2xhc3MKICAgICAqIEBzdXBwcmVzcyB7ZHVwbGljYXRlLCBpbnZhbGlkQ2FzdHMsIGNoZWNrVHlwZXN9CiAgICAgKi8KICAgIGNvbnN0IFBvbHltZXIgPSBmdW5jdGlvbihpbmZvKSB7CiAgICAgIC8vIGlmIGlucHV0IGlzIGEgYGNsYXNzYCAoYWthIGEgZnVuY3Rpb24gd2l0aCBhIHByb3RvdHlwZSksIHVzZSB0aGUgcHJvdG90eXBlCiAgICAgIC8vIHJlbWVtYmVyIHRoYXQgdGhlIGBjb25zdHJ1Y3RvcmAgd2lsbCBuZXZlciBiZSBjYWxsZWQKICAgICAgbGV0IGtsYXNzOwogICAgICBpZiAodHlwZW9mIGluZm8gPT09ICdmdW5jdGlvbicpIHsKICAgICAgICBrbGFzcyA9IGluZm87CiAgICAgIH0gZWxzZSB7CiAgICAgICAga2xhc3MgPSBQb2x5bWVyLkNsYXNzKGluZm8pOwogICAgICB9CiAgICAgIC8vIENvcHkgb3B0IG91dCBmb3IgYGxlZ2FjeU5vT2JzZXJ2ZWRBdHRyaWJ1dGVzYCBmcm9tIGluZm8gb2JqZWN0IHRvIGNsYXNzLgogICAgICBpZiAoaW5mby5fbGVnYWN5Rm9yY2VPYnNlcnZlZEF0dHJpYnV0ZXMpIHsKICAgICAgICBrbGFzcy5wcm90b3R5cGUuX2xlZ2FjeUZvcmNlT2JzZXJ2ZWRBdHRyaWJ1dGVzID0gaW5mby5fbGVnYWN5Rm9yY2VPYnNlcnZlZEF0dHJpYnV0ZXM7CiAgICAgIH0KICAgICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKGtsYXNzLmlzLCAvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8oa2xhc3MpKTsKICAgICAgcmV0dXJuIGtsYXNzOwogICAgfTsKCiAgICBQb2x5bWVyLkNsYXNzID0gQ2xhc3M7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyBDb21tb24gaW1wbGVtZW50YXRpb24gZm9yIG1peGluICYgYmVoYXZpb3IKICAgIGZ1bmN0aW9uIG11dGFibGVQcm9wZXJ0eUNoYW5nZShpbnN0LCBwcm9wZXJ0eSwgdmFsdWUsIG9sZCwgbXV0YWJsZURhdGEpIHsKICAgICAgbGV0IGlzT2JqZWN0OwogICAgICBpZiAobXV0YWJsZURhdGEpIHsKICAgICAgICBpc09iamVjdCA9ICh0eXBlb2YgdmFsdWUgPT09ICdvYmplY3QnICYmIHZhbHVlICE9PSBudWxsKTsKICAgICAgICAvLyBQdWxsIGBvbGRgIGZvciBPYmplY3RzIGZyb20gdGVtcCBjYWNoZSwgYnV0IHRyZWF0IGBudWxsYCBhcyBhIHByaW1pdGl2ZQogICAgICAgIGlmIChpc09iamVjdCkgewogICAgICAgICAgb2xkID0gaW5zdC5fX2RhdGFUZW1wW3Byb3BlcnR5XTsKICAgICAgICB9CiAgICAgIH0KICAgICAgLy8gU3RyaWN0IGVxdWFsaXR5IGNoZWNrLCBidXQgcmV0dXJuIGZhbHNlIGZvciBOYU49PT1OYU4KICAgICAgbGV0IHNob3VsZENoYW5nZSA9IChvbGQgIT09IHZhbHVlICYmIChvbGQgPT09IG9sZCB8fCB2YWx1ZSA9PT0gdmFsdWUpKTsKICAgICAgLy8gT2JqZWN0cyBhcmUgc3RvcmVkIGluIHRlbXBvcmFyeSBjYWNoZSAoY2xlYXJlZCBhdCBlbmQgb2YKICAgICAgLy8gdHVybiksIHdoaWNoIGlzIHVzZWQgZm9yIGRpcnR5LWNoZWNraW5nCiAgICAgIGlmIChpc09iamVjdCAmJiBzaG91bGRDaGFuZ2UpIHsKICAgICAgICBpbnN0Ll9fZGF0YVRlbXBbcHJvcGVydHldID0gdmFsdWU7CiAgICAgIH0KICAgICAgcmV0dXJuIHNob3VsZENoYW5nZTsKICAgIH0KCiAgICAvKioKICAgICAqIEVsZW1lbnQgY2xhc3MgbWl4aW4gdG8gc2tpcCBzdHJpY3QgZGlydHktY2hlY2tpbmcgZm9yIG9iamVjdHMgYW5kIGFycmF5cwogICAgICogKGFsd2F5cyBjb25zaWRlciB0aGVtIHRvIGJlICJkaXJ0eSIpLCBmb3IgdXNlIG9uIGVsZW1lbnRzIHV0aWxpemluZwogICAgICogYFByb3BlcnR5RWZmZWN0c2AKICAgICAqCiAgICAgKiBCeSBkZWZhdWx0LCBgUHJvcGVydHlFZmZlY3RzYCBwZXJmb3JtcyBzdHJpY3QgZGlydHkgY2hlY2tpbmcgb24KICAgICAqIG9iamVjdHMsIHdoaWNoIG1lYW5zIHRoYXQgYW55IGRlZXAgbW9kaWZpY2F0aW9ucyB0byBhbiBvYmplY3Qgb3IgYXJyYXkgd2lsbAogICAgICogbm90IGJlIHByb3BhZ2F0ZWQgdW5sZXNzICJpbW11dGFibGUiIGRhdGEgcGF0dGVybnMgYXJlIHVzZWQgKGkuZS4gYWxsIG9iamVjdAogICAgICogcmVmZXJlbmNlcyBmcm9tIHRoZSByb290IHRvIHRoZSBtdXRhdGlvbiB3ZXJlIGNoYW5nZWQpLgogICAgICoKICAgICAqIFBvbHltZXIgYWxzbyBwcm92aWRlcyBhIHByb3ByaWV0YXJ5IGRhdGEgbXV0YXRpb24gYW5kIHBhdGggbm90aWZpY2F0aW9uIEFQSQogICAgICogKGUuZy4gYG5vdGlmeVBhdGhgLCBgc2V0YCwgYW5kIGFycmF5IG11dGF0aW9uIEFQSSdzKSB0aGF0IGFsbG93IGVmZmljaWVudAogICAgICogbXV0YXRpb24gYW5kIG5vdGlmaWNhdGlvbiBvZiBkZWVwIGNoYW5nZXMgaW4gYW4gb2JqZWN0IGdyYXBoIHRvIGFsbCBlbGVtZW50cwogICAgICogYm91bmQgdG8gdGhlIHNhbWUgb2JqZWN0IGdyYXBoLgogICAgICoKICAgICAqIEluIGNhc2VzIHdoZXJlIG5laXRoZXIgaW1tdXRhYmxlIHBhdHRlcm5zIG5vciB0aGUgZGF0YSBtdXRhdGlvbiBBUEkgY2FuIGJlCiAgICAgKiB1c2VkLCBhcHBseWluZyB0aGlzIG1peGluIHdpbGwgY2F1c2UgUG9seW1lciB0byBza2lwIGRpcnR5IGNoZWNraW5nIGZvcgogICAgICogb2JqZWN0cyBhbmQgYXJyYXlzIChhbHdheXMgY29uc2lkZXIgdGhlbSB0byBiZSAiZGlydHkiKS4gIFRoaXMgYWxsb3dzIGEKICAgICAqIHVzZXIgdG8gbWFrZSBhIGRlZXAgbW9kaWZpY2F0aW9uIHRvIGEgYm91bmQgb2JqZWN0IGdyYXBoLCBhbmQgdGhlbiBlaXRoZXIKICAgICAqIHNpbXBseSByZS1zZXQgdGhlIG9iamVjdCAoZS5nLiBgdGhpcy5pdGVtcyA9IHRoaXMuaXRlbXNgKSBvciBjYWxsIGBub3RpZnlQYXRoYAogICAgICogKGUuZy4gYHRoaXMubm90aWZ5UGF0aCgnaXRlbXMnKWApIHRvIHVwZGF0ZSB0aGUgdHJlZS4gIE5vdGUgdGhhdCBhbGwKICAgICAqIGVsZW1lbnRzIHRoYXQgd2lzaCB0byBiZSB1cGRhdGVkIGJhc2VkIG9uIGRlZXAgbXV0YXRpb25zIG11c3QgYXBwbHkgdGhpcwogICAgICogbWl4aW4gb3Igb3RoZXJ3aXNlIHNraXAgc3RyaWN0IGRpcnR5IGNoZWNraW5nIGZvciBvYmplY3RzL2FycmF5cy4KICAgICAqIFNwZWNpZmljYWxseSwgYW55IGVsZW1lbnRzIGluIHRoZSBiaW5kaW5nIHRyZWUgYmV0d2VlbiB0aGUgc291cmNlIG9mIGEKICAgICAqIG11dGF0aW9uIGFuZCB0aGUgY29uc3VtcHRpb24gb2YgaXQgbXVzdCBhcHBseSB0aGlzIG1peGluIG9yIGVuYWJsZSB0aGUKICAgICAqIGBPcHRpb25hbE11dGFibGVEYXRhYCBtaXhpbi4KICAgICAqCiAgICAgKiBJbiBvcmRlciB0byBtYWtlIHRoZSBkaXJ0eSBjaGVjayBzdHJhdGVneSBjb25maWd1cmFibGUsIHNlZQogICAgICogYE9wdGlvbmFsTXV0YWJsZURhdGFgLgogICAgICoKICAgICAqIE5vdGUsIHRoZSBwZXJmb3JtYW5jZSBjaGFyYWN0ZXJpc3RpY3Mgb2YgcHJvcGFnYXRpbmcgbGFyZ2Ugb2JqZWN0IGdyYXBocwogICAgICogd2lsbCBiZSB3b3JzZSBhcyBvcHBvc2VkIHRvIHVzaW5nIHN0cmljdCBkaXJ0eSBjaGVja2luZyB3aXRoIGltbXV0YWJsZQogICAgICogcGF0dGVybnMgb3IgUG9seW1lcidzIHBhdGggbm90aWZpY2F0aW9uIEFQSS4KICAgICAqCiAgICAgKiBAbWl4aW5GdW5jdGlvbgogICAgICogQHBvbHltZXIKICAgICAqIEBzdW1tYXJ5IEVsZW1lbnQgY2xhc3MgbWl4aW4gdG8gc2tpcCBzdHJpY3QgZGlydHktY2hlY2tpbmcgZm9yIG9iamVjdHMKICAgICAqICAgYW5kIGFycmF5cwogICAgICogQHRlbXBsYXRlIFQKICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIENsYXNzIHRvIGFwcGx5IG1peGluIHRvLgogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OlQpfSBzdXBlckNsYXNzIHdpdGggbWl4aW4gYXBwbGllZC4KICAgICAqLwogICAgY29uc3QgTXV0YWJsZURhdGEgPSBkZWR1cGluZ01peGluKHN1cGVyQ2xhc3MgPT4gewoKICAgICAgLyoqCiAgICAgICAqIEBwb2x5bWVyCiAgICAgICAqIEBtaXhpbkNsYXNzCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX011dGFibGVEYXRhfQogICAgICAgKi8KICAgICAgY2xhc3MgTXV0YWJsZURhdGEgZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgYFByb3BlcnR5RWZmZWN0c2AgdG8gcHJvdmlkZSBvcHRpb24gZm9yIHNraXBwaW5nCiAgICAgICAgICogc3RyaWN0IGVxdWFsaXR5IGNoZWNraW5nIGZvciBPYmplY3RzIGFuZCBBcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG1ldGhvZCBwdWxscyB0aGUgdmFsdWUgdG8gZGlydHkgY2hlY2sgYWdhaW5zdCBmcm9tIHRoZSBgX19kYXRhVGVtcGAKICAgICAgICAgKiBjYWNoZSAocmF0aGVyIHRoYW4gdGhlIG5vcm1hbCBgX19kYXRhYCBjYWNoZSkgZm9yIE9iamVjdHMuICBTaW5jZSB0aGUgdGVtcAogICAgICAgICAqIGNhY2hlIGlzIGNsZWFyZWQgYXQgdGhlIGVuZCBvZiBhIHR1cm4sIHRoaXMgaW1wbGVtZW50YXRpb24gYWxsb3dzCiAgICAgICAgICogc2lkZS1lZmZlY3RzIG9mIGRlZXAgb2JqZWN0IGNoYW5nZXMgdG8gYmUgcHJvY2Vzc2VkIGJ5IHJlLXNldHRpbmcgdGhlCiAgICAgICAgICogc2FtZSBvYmplY3QgKHVzaW5nIHRoZSB0ZW1wIGNhY2hlIGFzIGFuIGluLXR1cm4gYmFja3N0b3AgdG8gcHJldmVudAogICAgICAgICAqIGN5Y2xlcyBkdWUgdG8gMi13YXkgbm90aWZpY2F0aW9uKS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eSBQcm9wZXJ0eSBuYW1lCiAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBOZXcgcHJvcGVydHkgdmFsdWUKICAgICAgICAgKiBAcGFyYW0geyp9IG9sZCBQcmV2aW91cyBwcm9wZXJ0eSB2YWx1ZQogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdGhlIHByb3BlcnR5IHNob3VsZCBiZSBjb25zaWRlcmVkIGEgY2hhbmdlCiAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAqLwogICAgICAgIF9zaG91bGRQcm9wZXJ0eUNoYW5nZShwcm9wZXJ0eSwgdmFsdWUsIG9sZCkgewogICAgICAgICAgcmV0dXJuIG11dGFibGVQcm9wZXJ0eUNoYW5nZSh0aGlzLCBwcm9wZXJ0eSwgdmFsdWUsIG9sZCwgdHJ1ZSk7CiAgICAgICAgfQoKICAgICAgfQoKICAgICAgcmV0dXJuIE11dGFibGVEYXRhOwoKICAgIH0pOwoKICAgIC8qKgogICAgICogRWxlbWVudCBjbGFzcyBtaXhpbiB0byBhZGQgdGhlIG9wdGlvbmFsIGFiaWxpdHkgdG8gc2tpcCBzdHJpY3QKICAgICAqIGRpcnR5LWNoZWNraW5nIGZvciBvYmplY3RzIGFuZCBhcnJheXMgKGFsd2F5cyBjb25zaWRlciB0aGVtIHRvIGJlCiAgICAgKiAiZGlydHkiKSBieSBzZXR0aW5nIGEgYG11dGFibGUtZGF0YWAgYXR0cmlidXRlIG9uIGFuIGVsZW1lbnQgaW5zdGFuY2UuCiAgICAgKgogICAgICogQnkgZGVmYXVsdCwgYFByb3BlcnR5RWZmZWN0c2AgcGVyZm9ybXMgc3RyaWN0IGRpcnR5IGNoZWNraW5nIG9uCiAgICAgKiBvYmplY3RzLCB3aGljaCBtZWFucyB0aGF0IGFueSBkZWVwIG1vZGlmaWNhdGlvbnMgdG8gYW4gb2JqZWN0IG9yIGFycmF5IHdpbGwKICAgICAqIG5vdCBiZSBwcm9wYWdhdGVkIHVubGVzcyAiaW1tdXRhYmxlIiBkYXRhIHBhdHRlcm5zIGFyZSB1c2VkIChpLmUuIGFsbCBvYmplY3QKICAgICAqIHJlZmVyZW5jZXMgZnJvbSB0aGUgcm9vdCB0byB0aGUgbXV0YXRpb24gd2VyZSBjaGFuZ2VkKS4KICAgICAqCiAgICAgKiBQb2x5bWVyIGFsc28gcHJvdmlkZXMgYSBwcm9wcmlldGFyeSBkYXRhIG11dGF0aW9uIGFuZCBwYXRoIG5vdGlmaWNhdGlvbiBBUEkKICAgICAqIChlLmcuIGBub3RpZnlQYXRoYCwgYHNldGAsIGFuZCBhcnJheSBtdXRhdGlvbiBBUEkncykgdGhhdCBhbGxvdyBlZmZpY2llbnQKICAgICAqIG11dGF0aW9uIGFuZCBub3RpZmljYXRpb24gb2YgZGVlcCBjaGFuZ2VzIGluIGFuIG9iamVjdCBncmFwaCB0byBhbGwgZWxlbWVudHMKICAgICAqIGJvdW5kIHRvIHRoZSBzYW1lIG9iamVjdCBncmFwaC4KICAgICAqCiAgICAgKiBJbiBjYXNlcyB3aGVyZSBuZWl0aGVyIGltbXV0YWJsZSBwYXR0ZXJucyBub3IgdGhlIGRhdGEgbXV0YXRpb24gQVBJIGNhbiBiZQogICAgICogdXNlZCwgYXBwbHlpbmcgdGhpcyBtaXhpbiB3aWxsIGFsbG93IFBvbHltZXIgdG8gc2tpcCBkaXJ0eSBjaGVja2luZyBmb3IKICAgICAqIG9iamVjdHMgYW5kIGFycmF5cyAoYWx3YXlzIGNvbnNpZGVyIHRoZW0gdG8gYmUgImRpcnR5IikuICBUaGlzIGFsbG93cyBhCiAgICAgKiB1c2VyIHRvIG1ha2UgYSBkZWVwIG1vZGlmaWNhdGlvbiB0byBhIGJvdW5kIG9iamVjdCBncmFwaCwgYW5kIHRoZW4gZWl0aGVyCiAgICAgKiBzaW1wbHkgcmUtc2V0IHRoZSBvYmplY3QgKGUuZy4gYHRoaXMuaXRlbXMgPSB0aGlzLml0ZW1zYCkgb3IgY2FsbCBgbm90aWZ5UGF0aGAKICAgICAqIChlLmcuIGB0aGlzLm5vdGlmeVBhdGgoJ2l0ZW1zJylgKSB0byB1cGRhdGUgdGhlIHRyZWUuICBOb3RlIHRoYXQgYWxsCiAgICAgKiBlbGVtZW50cyB0aGF0IHdpc2ggdG8gYmUgdXBkYXRlZCBiYXNlZCBvbiBkZWVwIG11dGF0aW9ucyBtdXN0IGFwcGx5IHRoaXMKICAgICAqIG1peGluIG9yIG90aGVyd2lzZSBza2lwIHN0cmljdCBkaXJ0eSBjaGVja2luZyBmb3Igb2JqZWN0cy9hcnJheXMuCiAgICAgKiBTcGVjaWZpY2FsbHksIGFueSBlbGVtZW50cyBpbiB0aGUgYmluZGluZyB0cmVlIGJldHdlZW4gdGhlIHNvdXJjZSBvZiBhCiAgICAgKiBtdXRhdGlvbiBhbmQgdGhlIGNvbnN1bXB0aW9uIG9mIGl0IG11c3QgZW5hYmxlIHRoaXMgbWl4aW4gb3IgYXBwbHkgdGhlCiAgICAgKiBgTXV0YWJsZURhdGFgIG1peGluLgogICAgICoKICAgICAqIFdoaWxlIHRoaXMgbWl4aW4gYWRkcyB0aGUgYWJpbGl0eSB0byBmb3JnbyBPYmplY3QvQXJyYXkgZGlydHkgY2hlY2tpbmcsCiAgICAgKiB0aGUgYG11dGFibGVEYXRhYCBmbGFnIGRlZmF1bHRzIHRvIGZhbHNlIGFuZCBtdXN0IGJlIHNldCBvbiB0aGUgaW5zdGFuY2UuCiAgICAgKgogICAgICogTm90ZSwgdGhlIHBlcmZvcm1hbmNlIGNoYXJhY3RlcmlzdGljcyBvZiBwcm9wYWdhdGluZyBsYXJnZSBvYmplY3QgZ3JhcGhzCiAgICAgKiB3aWxsIGJlIHdvcnNlIGJ5IHJlbHlpbmcgb24gYG11dGFibGVEYXRhOiB0cnVlYCBhcyBvcHBvc2VkIHRvIHVzaW5nCiAgICAgKiBzdHJpY3QgZGlydHkgY2hlY2tpbmcgd2l0aCBpbW11dGFibGUgcGF0dGVybnMgb3IgUG9seW1lcidzIHBhdGggbm90aWZpY2F0aW9uCiAgICAgKiBBUEkuCiAgICAgKgogICAgICogQG1peGluRnVuY3Rpb24KICAgICAqIEBwb2x5bWVyCiAgICAgKiBAc3VtbWFyeSBFbGVtZW50IGNsYXNzIG1peGluIHRvIG9wdGlvbmFsbHkgc2tpcCBzdHJpY3QgZGlydHktY2hlY2tpbmcKICAgICAqICAgZm9yIG9iamVjdHMgYW5kIGFycmF5cwogICAgICovCiAgICBjb25zdCBPcHRpb25hbE11dGFibGVEYXRhID0gZGVkdXBpbmdNaXhpbihzdXBlckNsYXNzID0+IHsKCiAgICAgIC8qKgogICAgICAgKiBAbWl4aW5DbGFzcwogICAgICAgKiBAcG9seW1lcgogICAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9PcHRpb25hbE11dGFibGVEYXRhfQogICAgICAgKi8KICAgICAgY2xhc3MgT3B0aW9uYWxNdXRhYmxlRGF0YSBleHRlbmRzIHN1cGVyQ2xhc3MgewoKICAgICAgICAvKiogQG5vY29sbGFwc2UgKi8KICAgICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogSW5zdGFuY2UtbGV2ZWwgZmxhZyBmb3IgY29uZmlndXJpbmcgdGhlIGRpcnR5LWNoZWNraW5nIHN0cmF0ZWd5CiAgICAgICAgICAgICAqIGZvciB0aGlzIGVsZW1lbnQuICBXaGVuIHRydWUsIE9iamVjdHMgYW5kIEFycmF5cyB3aWxsIHNraXAgZGlydHkKICAgICAgICAgICAgICogY2hlY2tpbmcsIG90aGVyd2lzZSBzdHJpY3QgZXF1YWxpdHkgY2hlY2tpbmcgd2lsbCBiZSB1c2VkLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgbXV0YWJsZURhdGE6IEJvb2xlYW4KICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZXMgYFByb3BlcnR5RWZmZWN0c2AgdG8gcHJvdmlkZSBvcHRpb24gZm9yIHNraXBwaW5nCiAgICAgICAgICogc3RyaWN0IGVxdWFsaXR5IGNoZWNraW5nIGZvciBPYmplY3RzIGFuZCBBcnJheXMuCiAgICAgICAgICoKICAgICAgICAgKiBXaGVuIGB0aGlzLm11dGFibGVEYXRhYCBpcyB0cnVlIG9uIHRoaXMgaW5zdGFuY2UsIHRoaXMgbWV0aG9kCiAgICAgICAgICogcHVsbHMgdGhlIHZhbHVlIHRvIGRpcnR5IGNoZWNrIGFnYWluc3QgZnJvbSB0aGUgYF9fZGF0YVRlbXBgIGNhY2hlCiAgICAgICAgICogKHJhdGhlciB0aGFuIHRoZSBub3JtYWwgYF9fZGF0YWAgY2FjaGUpIGZvciBPYmplY3RzLiAgU2luY2UgdGhlIHRlbXAKICAgICAgICAgKiBjYWNoZSBpcyBjbGVhcmVkIGF0IHRoZSBlbmQgb2YgYSB0dXJuLCB0aGlzIGltcGxlbWVudGF0aW9uIGFsbG93cwogICAgICAgICAqIHNpZGUtZWZmZWN0cyBvZiBkZWVwIG9iamVjdCBjaGFuZ2VzIHRvIGJlIHByb2Nlc3NlZCBieSByZS1zZXR0aW5nIHRoZQogICAgICAgICAqIHNhbWUgb2JqZWN0ICh1c2luZyB0aGUgdGVtcCBjYWNoZSBhcyBhbiBpbi10dXJuIGJhY2tzdG9wIHRvIHByZXZlbnQKICAgICAgICAgKiBjeWNsZXMgZHVlIHRvIDItd2F5IG5vdGlmaWNhdGlvbikuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcGVydHkgUHJvcGVydHkgbmFtZQogICAgICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgTmV3IHByb3BlcnR5IHZhbHVlCiAgICAgICAgICogQHBhcmFtIHsqfSBvbGQgUHJldmlvdXMgcHJvcGVydHkgdmFsdWUKICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHRoZSBwcm9wZXJ0eSBzaG91bGQgYmUgY29uc2lkZXJlZCBhIGNoYW5nZQogICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBfc2hvdWxkUHJvcGVydHlDaGFuZ2UocHJvcGVydHksIHZhbHVlLCBvbGQpIHsKICAgICAgICAgIHJldHVybiBtdXRhYmxlUHJvcGVydHlDaGFuZ2UodGhpcywgcHJvcGVydHksIHZhbHVlLCBvbGQsIHRoaXMubXV0YWJsZURhdGEpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIE9wdGlvbmFsTXV0YWJsZURhdGE7CgogICAgfSk7CgogICAgLy8gRXhwb3J0IGZvciB1c2UgYnkgbGVnYWN5IGJlaGF2aW9yCiAgICBNdXRhYmxlRGF0YS5fbXV0YWJsZVByb3BlcnR5Q2hhbmdlID0gbXV0YWJsZVByb3BlcnR5Q2hhbmdlOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLy8gQmFzZSBjbGFzcyBmb3IgSFRNTFRlbXBsYXRlRWxlbWVudCBleHRlbnNpb24gdGhhdCBoYXMgcHJvcGVydHkgZWZmZWN0cwogICAgLy8gbWFjaGluZXJ5IGZvciBwcm9wYWdhdGluZyBob3N0IHByb3BlcnRpZXMgdG8gY2hpbGRyZW4uIFRoaXMgaXMgYW4gRVM1CiAgICAvLyBjbGFzcyBvbmx5IGJlY2F1c2UgQmFiZWwgKGluY29ycmVjdGx5KSByZXF1aXJlcyBzdXBlcigpIGluIHRoZSBjbGFzcwogICAgLy8gY29uc3RydWN0b3IgZXZlbiB0aG91Z2ggbm8gYHRoaXNgIGlzIHVzZWQgYW5kIGl0IHJldHVybnMgYW4gaW5zdGFuY2UuCiAgICBsZXQgbmV3SW5zdGFuY2UgPSBudWxsOwoKICAgIC8qKgogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKiBAZXh0ZW5kcyB7SFRNTFRlbXBsYXRlRWxlbWVudH0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIEhUTUxUZW1wbGF0ZUVsZW1lbnRFeHRlbnNpb24oKSB7IHJldHVybiBuZXdJbnN0YW5jZTsgfQogICAgSFRNTFRlbXBsYXRlRWxlbWVudEV4dGVuc2lvbi5wcm90b3R5cGUgPSBPYmplY3QuY3JlYXRlKEhUTUxUZW1wbGF0ZUVsZW1lbnQucHJvdG90eXBlLCB7CiAgICAgIGNvbnN0cnVjdG9yOiB7CiAgICAgICAgdmFsdWU6IEhUTUxUZW1wbGF0ZUVsZW1lbnRFeHRlbnNpb24sCiAgICAgICAgd3JpdGFibGU6IHRydWUKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICAgKiBAY29uc3RydWN0b3IKICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30KICAgICAqIEBleHRlbmRzIHtIVE1MVGVtcGxhdGVFbGVtZW50RXh0ZW5zaW9ufQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgY29uc3QgRGF0YVRlbXBsYXRlID0gUHJvcGVydHlFZmZlY3RzKEhUTUxUZW1wbGF0ZUVsZW1lbnRFeHRlbnNpb24pOwoKICAgIC8qKgogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9NdXRhYmxlRGF0YX0KICAgICAqIEBleHRlbmRzIHtEYXRhVGVtcGxhdGV9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBjb25zdCBNdXRhYmxlRGF0YVRlbXBsYXRlID0gTXV0YWJsZURhdGEoRGF0YVRlbXBsYXRlKTsKCiAgICAvLyBBcHBsaWVzIGEgRGF0YVRlbXBsYXRlIHN1YmNsYXNzIHRvIGEgPHRlbXBsYXRlPiBpbnN0YW5jZQogICAgZnVuY3Rpb24gdXBncmFkZVRlbXBsYXRlKHRlbXBsYXRlLCBjb25zdHJ1Y3RvcikgewogICAgICBuZXdJbnN0YW5jZSA9IHRlbXBsYXRlOwogICAgICBPYmplY3Quc2V0UHJvdG90eXBlT2YodGVtcGxhdGUsIGNvbnN0cnVjdG9yLnByb3RvdHlwZSk7CiAgICAgIG5ldyBjb25zdHJ1Y3RvcigpOwogICAgICBuZXdJbnN0YW5jZSA9IG51bGw7CiAgICB9CgogICAgLyoqCiAgICAgKiBCYXNlIGNsYXNzIGZvciBUZW1wbGF0ZUluc3RhbmNlLgogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKiBAZXh0ZW5kcyB7SFRNTEVsZW1lbnR9CiAgICAgKiBAaW1wbGVtZW50cyB7UG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHN9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBjb25zdCB0ZW1wbGF0ZUluc3RhbmNlQmFzZSA9IFByb3BlcnR5RWZmZWN0cyhjbGFzcyB7fSk7CgogICAgZnVuY3Rpb24gc2hvd0hpZGVDaGlsZHJlbihoaWRlLCBjaGlsZHJlbikgewogICAgICBmb3IgKGxldCBpPTA7IGk8Y2hpbGRyZW4ubGVuZ3RoOyBpKyspIHsKICAgICAgICBsZXQgbiA9IGNoaWxkcmVuW2ldOwogICAgICAgIC8vIElnbm9yZSBub24tY2hhbmdlcwogICAgICAgIGlmIChCb29sZWFuKGhpZGUpICE9IEJvb2xlYW4obi5fX2hpZGVUZW1wbGF0ZUNoaWxkcmVuX18pKSB7CiAgICAgICAgICAvLyBjbGVhciBhbmQgcmVzdG9yZSB0ZXh0CiAgICAgICAgICBpZiAobi5ub2RlVHlwZSA9PT0gTm9kZS5URVhUX05PREUpIHsKICAgICAgICAgICAgaWYgKGhpZGUpIHsKICAgICAgICAgICAgICBuLl9fcG9seW1lclRleHRDb250ZW50X18gPSBuLnRleHRDb250ZW50OwogICAgICAgICAgICAgIG4udGV4dENvbnRlbnQgPSAnJzsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBuLnRleHRDb250ZW50ID0gbi5fX3BvbHltZXJUZXh0Q29udGVudF9fOwogICAgICAgICAgICB9CiAgICAgICAgICAvLyByZW1vdmUgYW5kIHJlcGxhY2Ugc2xvdAogICAgICAgICAgfSBlbHNlIGlmIChuLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnKSB7CiAgICAgICAgICAgIGlmIChoaWRlKSB7CiAgICAgICAgICAgICAgbi5fX3BvbHltZXJSZXBsYWNlZF9fID0gZG9jdW1lbnQuY3JlYXRlQ29tbWVudCgnaGlkZGVuLXNsb3QnKTsKICAgICAgICAgICAgICB3cmFwKHdyYXAobikucGFyZW50Tm9kZSkucmVwbGFjZUNoaWxkKG4uX19wb2x5bWVyUmVwbGFjZWRfXywgbik7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgY29uc3QgcmVwbGFjZSA9IG4uX19wb2x5bWVyUmVwbGFjZWRfXzsKICAgICAgICAgICAgICBpZiAocmVwbGFjZSkgewogICAgICAgICAgICAgICAgd3JhcCh3cmFwKHJlcGxhY2UpLnBhcmVudE5vZGUpLnJlcGxhY2VDaGlsZChuLCByZXBsYWNlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIC8vIGhpZGUgYW5kIHNob3cgbm9kZXMKICAgICAgICAgIGVsc2UgaWYgKG4uc3R5bGUpIHsKICAgICAgICAgICAgaWYgKGhpZGUpIHsKICAgICAgICAgICAgICBuLl9fcG9seW1lckRpc3BsYXlfXyA9IG4uc3R5bGUuZGlzcGxheTsKICAgICAgICAgICAgICBuLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgbi5zdHlsZS5kaXNwbGF5ID0gbi5fX3BvbHltZXJEaXNwbGF5X187CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgbi5fX2hpZGVUZW1wbGF0ZUNoaWxkcmVuX18gPSBoaWRlOwogICAgICAgIGlmIChuLl9zaG93SGlkZUNoaWxkcmVuKSB7CiAgICAgICAgICBuLl9zaG93SGlkZUNoaWxkcmVuKGhpZGUpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQHBvbHltZXIKICAgICAqIEBjdXN0b21FbGVtZW50CiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnR5RWZmZWN0cwogICAgICogQHVucmVzdHJpY3RlZAogICAgICovCiAgICBjbGFzcyBUZW1wbGF0ZUluc3RhbmNlQmFzZSBleHRlbmRzIHRlbXBsYXRlSW5zdGFuY2VCYXNlIHsKICAgICAgY29uc3RydWN0b3IocHJvcHMpIHsKICAgICAgICBzdXBlcigpOwogICAgICAgIHRoaXMuX2NvbmZpZ3VyZVByb3BlcnRpZXMocHJvcHMpOwogICAgICAgIC8qKiBAdHlwZSB7IVN0YW1wZWRUZW1wbGF0ZX0gKi8KICAgICAgICB0aGlzLnJvb3QgPSB0aGlzLl9zdGFtcFRlbXBsYXRlKHRoaXMuX19kYXRhSG9zdCk7CiAgICAgICAgLy8gU2F2ZSBsaXN0IG9mIHN0YW1wZWQgY2hpbGRyZW4KICAgICAgICBsZXQgY2hpbGRyZW4gPSBbXTsKICAgICAgICAvKiogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9ICovCiAgICAgICAgdGhpcy5jaGlsZHJlbiA9IC8qKiBAdHlwZSB7IU5vZGVMaXN0fSAqLyAoY2hpbGRyZW4pOwogICAgICAgIC8vIFBvbHltZXIgMS54IGRpZCBub3QgdXNlIGBQb2x5bWVyLmRvbWAgaGVyZSBzbyBub3QgYm90aGVyaW5nLgogICAgICAgIGZvciAobGV0IG4gPSB0aGlzLnJvb3QuZmlyc3RDaGlsZDsgbjsgbj1uLm5leHRTaWJsaW5nKSB7CiAgICAgICAgICBjaGlsZHJlbi5wdXNoKG4pOwogICAgICAgICAgbi5fX3RlbXBsYXRpemVJbnN0YW5jZSA9IHRoaXM7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9fdGVtcGxhdGl6ZU93bmVyICYmCiAgICAgICAgICB0aGlzLl9fdGVtcGxhdGl6ZU93bmVyLl9faGlkZVRlbXBsYXRlQ2hpbGRyZW5fXykgewogICAgICAgICAgdGhpcy5fc2hvd0hpZGVDaGlsZHJlbih0cnVlKTsKICAgICAgICB9CiAgICAgICAgLy8gRmx1c2ggcHJvcHMgb25seSB3aGVuIHByb3BzIGFyZSBwYXNzZWQgaWYgaW5zdGFuY2UgcHJvcHMgZXhpc3QKICAgICAgICAvLyBvciB3aGVuIHRoZXJlIGlzbid0IGluc3RhbmNlIHByb3BzLgogICAgICAgIGxldCBvcHRpb25zID0gdGhpcy5fX3RlbXBsYXRpemVPcHRpb25zOwogICAgICAgIGlmICgocHJvcHMgJiYgb3B0aW9ucy5pbnN0YW5jZVByb3BzKSB8fCAhb3B0aW9ucy5pbnN0YW5jZVByb3BzKSB7CiAgICAgICAgICB0aGlzLl9lbmFibGVQcm9wZXJ0aWVzKCk7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8qKgogICAgICAgKiBDb25maWd1cmUgdGhlIGdpdmVuIGBwcm9wc2AgYnkgY2FsbGluZyBgX3NldFBlbmRpbmdQcm9wZXJ0eWAuIEFsc28KICAgICAgICogc2V0cyBhbnkgcHJvcGVydGllcyBzdG9yZWQgaW4gYF9faG9zdFByb3BzYC4KICAgICAgICogQHByaXZhdGUKICAgICAgICogQHBhcmFtIHtPYmplY3R9IHByb3BzIE9iamVjdCBvZiBwcm9wZXJ0eSBuYW1lLXZhbHVlIHBhaXJzIHRvIHNldC4KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIF9jb25maWd1cmVQcm9wZXJ0aWVzKHByb3BzKSB7CiAgICAgICAgbGV0IG9wdGlvbnMgPSB0aGlzLl9fdGVtcGxhdGl6ZU9wdGlvbnM7CiAgICAgICAgaWYgKG9wdGlvbnMuZm9yd2FyZEhvc3RQcm9wKSB7CiAgICAgICAgICBmb3IgKGxldCBocHJvcCBpbiB0aGlzLl9faG9zdFByb3BzKSB7CiAgICAgICAgICAgIHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eShocHJvcCwgdGhpcy5fX2RhdGFIb3N0WydfaG9zdF8nICsgaHByb3BdKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gQW55IGluc3RhbmNlIHByb3BzIHBhc3NlZCBpbiB0aGUgY29uc3RydWN0b3Igd2lsbCBvdmVyd3JpdGUgaG9zdCBwcm9wczsKICAgICAgICAvLyBub3JtYWxseSB0aGlzIHdvdWxkIGJlIGEgdXNlciBlcnJvciBidXQgd2UgZG9uJ3Qgc3BlY2lmaWNhbGx5IGZpbHRlciB0aGVtCiAgICAgICAgZm9yIChsZXQgaXByb3AgaW4gcHJvcHMpIHsKICAgICAgICAgIHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eShpcHJvcCwgcHJvcHNbaXByb3BdKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEZvcndhcmRzIGEgaG9zdCBwcm9wZXJ0eSB0byB0aGlzIGluc3RhbmNlLiAgVGhpcyBtZXRob2Qgc2hvdWxkIGJlCiAgICAgICAqIGNhbGxlZCBvbiBpbnN0YW5jZXMgZnJvbSB0aGUgYG9wdGlvbnMuZm9yd2FyZEhvc3RQcm9wYCBjYWxsYmFjawogICAgICAgKiB0byBwcm9wYWdhdGUgY2hhbmdlcyBvZiBob3N0IHByb3BlcnRpZXMgdG8gZWFjaCBpbnN0YW5jZS4KICAgICAgICoKICAgICAgICogTm90ZSB0aGlzIG1ldGhvZCBlbnF1ZXVlcyB0aGUgY2hhbmdlLCB3aGljaCBhcmUgZmx1c2hlZCBhcyBhIGJhdGNoLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBQcm9wZXJ0eSBvciBwYXRoIG5hbWUKICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSBvZiB0aGUgcHJvcGVydHkgdG8gZm9yd2FyZAogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgZm9yd2FyZEhvc3RQcm9wKHByb3AsIHZhbHVlKSB7CiAgICAgICAgaWYgKHRoaXMuX3NldFBlbmRpbmdQcm9wZXJ0eU9yUGF0aChwcm9wLCB2YWx1ZSwgZmFsc2UsIHRydWUpKSB7CiAgICAgICAgICB0aGlzLl9fZGF0YUhvc3QuX2VucXVldWVDbGllbnQodGhpcyk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogT3ZlcnJpZGUgcG9pbnQgZm9yIGFkZGluZyBjdXN0b20gb3Igc2ltdWxhdGVkIGV2ZW50IGhhbmRsaW5nLgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHBhcmFtIHshTm9kZX0gbm9kZSBOb2RlIHRvIGFkZCBldmVudCBsaXN0ZW5lciB0bwogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZlbnROYW1lIE5hbWUgb2YgZXZlbnQKICAgICAgICogQHBhcmFtIHtmdW5jdGlvbighRXZlbnQpOnZvaWR9IGhhbmRsZXIgTGlzdGVuZXIgZnVuY3Rpb24gdG8gYWRkCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBfYWRkRXZlbnRMaXN0ZW5lclRvTm9kZShub2RlLCBldmVudE5hbWUsIGhhbmRsZXIpIHsKICAgICAgICBpZiAodGhpcy5fbWV0aG9kSG9zdCAmJiB0aGlzLl9fdGVtcGxhdGl6ZU9wdGlvbnMucGFyZW50TW9kZWwpIHsKICAgICAgICAgIC8vIElmIHRoaXMgaW5zdGFuY2Ugc2hvdWxkIGJlIGNvbnNpZGVyZWQgYSBwYXJlbnQgbW9kZWwsIGRlY29yYXRlCiAgICAgICAgICAvLyBldmVudHMgdGhpcyB0ZW1wbGF0ZSBpbnN0YW5jZSBhcyBgbW9kZWxgCiAgICAgICAgICB0aGlzLl9tZXRob2RIb3N0Ll9hZGRFdmVudExpc3RlbmVyVG9Ob2RlKG5vZGUsIGV2ZW50TmFtZSwgKGUpID0+IHsKICAgICAgICAgICAgZS5tb2RlbCA9IHRoaXM7CiAgICAgICAgICAgIGhhbmRsZXIoZSk7CiAgICAgICAgICB9KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gT3RoZXJ3aXNlIGRlbGVnYXRlIHRvIHRoZSB0ZW1wbGF0ZSdzIGhvc3QgKHdoaWNoIGNvdWxkIGJlKQogICAgICAgICAgLy8gYW5vdGhlciB0ZW1wbGF0ZSBpbnN0YW5jZQogICAgICAgICAgbGV0IHRlbXBsYXRlSG9zdCA9IHRoaXMuX19kYXRhSG9zdC5fX2RhdGFIb3N0OwogICAgICAgICAgaWYgKHRlbXBsYXRlSG9zdCkgewogICAgICAgICAgICB0ZW1wbGF0ZUhvc3QuX2FkZEV2ZW50TGlzdGVuZXJUb05vZGUobm9kZSwgZXZlbnROYW1lLCBoYW5kbGVyKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIFNob3dzIG9yIGhpZGVzIHRoZSB0ZW1wbGF0ZSBpbnN0YW5jZSB0b3AgbGV2ZWwgY2hpbGQgZWxlbWVudHMuIEZvcgogICAgICAgKiB0ZXh0IG5vZGVzLCBgdGV4dENvbnRlbnRgIGlzIHJlbW92ZWQgd2hpbGUgImhpZGRlbiIgYW5kIHJlcGxhY2VkIHdoZW4KICAgICAgICogInNob3duLiIKICAgICAgICogQHBhcmFtIHtib29sZWFufSBoaWRlIFNldCB0byB0cnVlIHRvIGhpZGUgdGhlIGNoaWxkcmVuOwogICAgICAgKiBzZXQgdG8gZmFsc2UgdG8gc2hvdyB0aGVtLgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfc2hvd0hpZGVDaGlsZHJlbihoaWRlKSB7CiAgICAgICAgc2hvd0hpZGVDaGlsZHJlbihoaWRlLCB0aGlzLmNoaWxkcmVuKTsKICAgICAgfQogICAgICAvKioKICAgICAgICogT3ZlcnJpZGVzIGRlZmF1bHQgcHJvcGVydHktZWZmZWN0cyBpbXBsZW1lbnRhdGlvbiB0byBpbnRlcmNlcHQKICAgICAgICogdGV4dENvbnRlbnQgYmluZGluZ3Mgd2hpbGUgY2hpbGRyZW4gYXJlICJoaWRkZW4iIGFuZCBjYWNoZSBpbgogICAgICAgKiBwcml2YXRlIHN0b3JhZ2UgZm9yIGxhdGVyIHJldHJpZXZhbC4KICAgICAgICoKICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqIEBwYXJhbSB7IU5vZGV9IG5vZGUgVGhlIG5vZGUgdG8gc2V0IGEgcHJvcGVydHkgb24KICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3AgVGhlIHByb3BlcnR5IHRvIHNldAogICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX3NldFVubWFuYWdlZFByb3BlcnR5VG9Ob2RlKG5vZGUsIHByb3AsIHZhbHVlKSB7CiAgICAgICAgaWYgKG5vZGUuX19oaWRlVGVtcGxhdGVDaGlsZHJlbl9fICYmCiAgICAgICAgICAgIG5vZGUubm9kZVR5cGUgPT0gTm9kZS5URVhUX05PREUgJiYgcHJvcCA9PSAndGV4dENvbnRlbnQnKSB7CiAgICAgICAgICBub2RlLl9fcG9seW1lclRleHRDb250ZW50X18gPSB2YWx1ZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgc3VwZXIuX3NldFVubWFuYWdlZFByb3BlcnR5VG9Ob2RlKG5vZGUsIHByb3AsIHZhbHVlKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEZpbmQgdGhlIHBhcmVudCBtb2RlbCBvZiB0aGlzIHRlbXBsYXRlIGluc3RhbmNlLiAgVGhlIHBhcmVudCBtb2RlbAogICAgICAgKiBpcyBlaXRoZXIgYW5vdGhlciB0ZW1wbGF0aXplIGluc3RhbmNlIHRoYXQgaGFkIG9wdGlvbiBgcGFyZW50TW9kZWw6IHRydWVgLAogICAgICAgKiBvciBlbHNlIHRoZSBob3N0IGVsZW1lbnQuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4geyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gVGhlIHBhcmVudCBtb2RlbCBvZiB0aGlzIGluc3RhbmNlCiAgICAgICAqLwogICAgICBnZXQgcGFyZW50TW9kZWwoKSB7CiAgICAgICAgbGV0IG1vZGVsID0gdGhpcy5fX3BhcmVudE1vZGVsOwogICAgICAgIGlmICghbW9kZWwpIHsKICAgICAgICAgIGxldCBvcHRpb25zOwogICAgICAgICAgbW9kZWwgPSB0aGlzOwogICAgICAgICAgZG8gewogICAgICAgICAgICAvLyBBIHRlbXBsYXRlIGluc3RhbmNlJ3MgYF9fZGF0YUhvc3RgIGlzIGEgPHRlbXBsYXRlPgogICAgICAgICAgICAvLyBgbW9kZWwuX19kYXRhSG9zdC5fX2RhdGFIb3N0YCBpcyB0aGUgdGVtcGxhdGUncyBob3N0CiAgICAgICAgICAgIG1vZGVsID0gbW9kZWwuX19kYXRhSG9zdC5fX2RhdGFIb3N0OwogICAgICAgICAgfSB3aGlsZSAoKG9wdGlvbnMgPSBtb2RlbC5fX3RlbXBsYXRpemVPcHRpb25zKSAmJiAhb3B0aW9ucy5wYXJlbnRNb2RlbCk7CiAgICAgICAgICB0aGlzLl9fcGFyZW50TW9kZWwgPSBtb2RlbDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIG1vZGVsOwogICAgICB9CgogICAgICAvKioKICAgICAgICogU3R1YiBvZiBIVE1MRWxlbWVudCdzIGBkaXNwYXRjaEV2ZW50YCwgc28gdGhhdCBlZmZlY3RzIHRoYXQgbWF5CiAgICAgICAqIGRpc3BhdGNoIGV2ZW50cyBzYWZlbHkgbm8tb3AuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7RXZlbnR9IGV2ZW50IEV2ZW50IHRvIGRpc3BhdGNoCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IEFsd2F5cyB0cnVlLgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgICBkaXNwYXRjaEV2ZW50KGV2ZW50KSB7IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQGV4dGVuZHMge1RlbXBsYXRlSW5zdGFuY2VCYXNlfQogICAgICogQGltcGxlbWVudHMge1BvbHltZXJfTXV0YWJsZURhdGF9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBjb25zdCBNdXRhYmxlVGVtcGxhdGVJbnN0YW5jZUJhc2UgPSBNdXRhYmxlRGF0YSgKICAgICAgICAvLyBUaGlzIGNhc3Qgc2hvdWxkbid0IGJlIG5lY2Nlc3NhcnksIGJ1dCBDbG9zdXJlIGRvZXNuJ3QgdW5kZXJzdGFuZCB0aGF0CiAgICAgICAgLy8gVGVtcGxhdGVJbnN0YW5jZUJhc2UgaXMgYSBjb25zdHJ1Y3RvciBmdW5jdGlvbi4KICAgICAgICAvKiogQHR5cGUge2Z1bmN0aW9uKG5ldzpUZW1wbGF0ZUluc3RhbmNlQmFzZSl9ICovIChUZW1wbGF0ZUluc3RhbmNlQmFzZSkpOwoKICAgIGZ1bmN0aW9uIGZpbmRNZXRob2RIb3N0KHRlbXBsYXRlKSB7CiAgICAgIC8vIFRlY2huaWNhbGx5IHRoaXMgc2hvdWxkIGJlIHRoZSBvd25lciBvZiB0aGUgb3V0ZXJtb3N0IHRlbXBsYXRlLgogICAgICAvLyBJbiBzaGFkb3cgZG9tLCB0aGlzIGlzIGFsd2F5cyBnZXRSb290Tm9kZSgpLmhvc3QsIGJ1dCB3ZSBjYW4KICAgICAgLy8gYXBwcm94aW1hdGUgdGhpcyB2aWEgY29vcGVyYXRpb24gd2l0aCBvdXIgZGF0YUhvc3QgYWx3YXlzIHNldHRpbmcKICAgICAgLy8gYF9tZXRob2RIb3N0YCBhcyBsb25nIGFzIHRoZXJlIHdlcmUgYmluZGluZ3MgKG9yIGlkJ3MpIG9uIHRoaXMKICAgICAgLy8gaW5zdGFuY2UgY2F1c2luZyBpdCB0byBnZXQgYSBkYXRhSG9zdC4KICAgICAgbGV0IHRlbXBsYXRlSG9zdCA9IHRlbXBsYXRlLl9fZGF0YUhvc3Q7CiAgICAgIHJldHVybiB0ZW1wbGF0ZUhvc3QgJiYgdGVtcGxhdGVIb3N0Ll9tZXRob2RIb3N0IHx8IHRlbXBsYXRlSG9zdDsKICAgIH0KCiAgICAvKiBlc2xpbnQtZGlzYWJsZSB2YWxpZC1qc2RvYyAqLwogICAgLyoqCiAgICAgKiBAc3VwcHJlc3Mge21pc3NpbmdQcm9wZXJ0aWVzfSBjbGFzcy5wcm90b3R5cGUgaXMgbm90IGRlZmluZWQgZm9yIHNvbWUgcmVhc29uCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNyZWF0ZVRlbXBsYXRpemVyQ2xhc3ModGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgb3B0aW9ucykgewogICAgICAvKioKICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAqIEBleHRlbmRzIHtUZW1wbGF0ZUluc3RhbmNlQmFzZX0KICAgICAgICovCiAgICAgIGxldCB0ZW1wbGF0aXplckJhc2UgPSBvcHRpb25zLm11dGFibGVEYXRhID8KICAgICAgICBNdXRhYmxlVGVtcGxhdGVJbnN0YW5jZUJhc2UgOiBUZW1wbGF0ZUluc3RhbmNlQmFzZTsKCiAgICAgIC8vIEFmZm9yZGFuY2UgZm9yIGdsb2JhbCBtaXhpbnMgb250byBUZW1wbGF0aXplSW5zdGFuY2UKICAgICAgaWYgKHRlbXBsYXRpemUubWl4aW4pIHsKICAgICAgICB0ZW1wbGF0aXplckJhc2UgPSB0ZW1wbGF0aXplLm1peGluKHRlbXBsYXRpemVyQmFzZSk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBBbm9ueW1vdXMgY2xhc3MgY3JlYXRlZCBieSB0aGUgdGVtcGxhdGl6ZQogICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIGxldCBrbGFzcyA9IGNsYXNzIGV4dGVuZHMgdGVtcGxhdGl6ZXJCYXNlIHsgfTsKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBrbGFzcy5wcm90b3R5cGUuX190ZW1wbGF0aXplT3B0aW9ucyA9IG9wdGlvbnM7CiAgICAgIGtsYXNzLnByb3RvdHlwZS5fYmluZFRlbXBsYXRlKHRlbXBsYXRlKTsKICAgICAgYWRkTm90aWZ5RWZmZWN0cyhrbGFzcywgdGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgb3B0aW9ucyk7CiAgICAgIHJldHVybiBrbGFzczsKICAgIH0KCiAgICAvKioKICAgICAqIEFkZHMgcHJvcGFnYXRlIGVmZmVjdHMgZnJvbSB0aGUgdGVtcGxhdGUgdG8gdGhlIHRlbXBsYXRlIGluc3RhbmNlIGZvcgogICAgICogcHJvcGVydGllcyB0aGF0IHRoZSBob3N0IGJpbmRzIHRvIHRoZSB0ZW1wbGF0ZSB1c2luZyB0aGUgYF9ob3N0X2AgcHJlZml4LgogICAgICoKICAgICAqIEBzdXBwcmVzcyB7bWlzc2luZ1Byb3BlcnRpZXN9IGNsYXNzLnByb3RvdHlwZSBpcyBub3QgZGVmaW5lZCBmb3Igc29tZSByZWFzb24KICAgICAqLwogICAgZnVuY3Rpb24gYWRkUHJvcGFnYXRlRWZmZWN0cyh0YXJnZXQsIHRlbXBsYXRlSW5mbywgb3B0aW9ucywgbWV0aG9kSG9zdCkgewogICAgICBsZXQgdXNlckZvcndhcmRIb3N0UHJvcCA9IG9wdGlvbnMuZm9yd2FyZEhvc3RQcm9wOwogICAgICBpZiAodXNlckZvcndhcmRIb3N0UHJvcCAmJiB0ZW1wbGF0ZUluZm8uaGFzSG9zdFByb3BzKSB7CiAgICAgICAgLy8gVW5kZXIgdGhlIGByZW1vdmVOZXN0ZWRUZW1wbGF0ZXNgIG9wdGltaXphdGlvbiwgYSBjdXN0b20gZWxlbWVudCBsaWtlCiAgICAgICAgLy8gYGRvbS1pZmAgb3IgYGRvbS1yZXBlYXRgIGNhbiBpdHNlbGYgYmUgdHJlYXRlZCBhcyB0aGUgInRlbXBsYXRlIjsgdGhpcwogICAgICAgIC8vIGZsYWcgaXMgdXNlZCB0byBzd2l0Y2ggYmV0d2VlbiB1cGdyYWRpbmcgYSBgPHRlbXBsYXRlPmAgdG8gYmUgYSBwcm9wZXJ0eQogICAgICAgIC8vIGVmZmVjdHMgY2xpZW50IHZzLiBhZGRpbmcgdGhlIGVmZmVjdHMgZGlyZWN0bHkgdG8gdGhlIGN1c3RvbSBlbGVtZW50CiAgICAgICAgY29uc3QgaXNUZW1wbGF0ZSA9IHRhcmdldC5sb2NhbE5hbWUgPT0gJ3RlbXBsYXRlJzsKICAgICAgICAvLyBQcm92aWRlIGRhdGEgQVBJIGFuZCBwcm9wZXJ0eSBlZmZlY3RzIG9uIG1lbW9pemVkIHRlbXBsYXRlIGNsYXNzCiAgICAgICAgbGV0IGtsYXNzID0gdGVtcGxhdGVJbmZvLnRlbXBsYXRpemVUZW1wbGF0ZUNsYXNzOwogICAgICAgIGlmICgha2xhc3MpIHsKICAgICAgICAgIGlmIChpc1RlbXBsYXRlKSB7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgICAgICogQGV4dGVuZHMge0RhdGFUZW1wbGF0ZX0KICAgICAgICAgICAgICovCiAgICAgICAgICAgIGxldCB0ZW1wbGF0aXplZEJhc2UgPQogICAgICAgICAgICAgICAgb3B0aW9ucy5tdXRhYmxlRGF0YSA/IE11dGFibGVEYXRhVGVtcGxhdGUgOiBEYXRhVGVtcGxhdGU7CgogICAgICAgICAgICAvLyBOT1RFOiBkdWUgdG8gaHR0cHM6Ly9naXRodWIuY29tL2dvb2dsZS9jbG9zdXJlLWNvbXBpbGVyL2lzc3Vlcy8yOTI4LAogICAgICAgICAgICAvLyBjb21iaW5pbmcgdGhlIG5leHQgdHdvIGxpbmVzIGludG8gb25lIGFzc2lnbm1lbnQgY2F1c2VzIGEgc3B1cmlvdXMKICAgICAgICAgICAgLy8gdHlwZSBlcnJvci4KICAgICAgICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgICAgICAgIGNsYXNzIFRlbXBsYXRpemVkVGVtcGxhdGUgZXh0ZW5kcyB0ZW1wbGF0aXplZEJhc2Uge30KICAgICAgICAgICAga2xhc3MgPSB0ZW1wbGF0ZUluZm8udGVtcGxhdGl6ZVRlbXBsYXRlQ2xhc3MgPSBUZW1wbGF0aXplZFRlbXBsYXRlOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAgICAgKiBAZXh0ZW5kcyB7UG9seW1lckVsZW1lbnR9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICBjb25zdCB0ZW1wbGF0aXplZEJhc2UgPSB0YXJnZXQuY29uc3RydWN0b3I7CgogICAgICAgICAgICAvLyBDcmVhdGUgYSBjYWNoZWQgc3ViY2xhc3Mgb2YgdGhlIGJhc2UgY3VzdG9tIGVsZW1lbnQgY2xhc3Mgb250byB3aGljaAogICAgICAgICAgICAvLyB0byBwdXQgdGhlIHRlbXBsYXRlLXNwZWNpZmljIHByb3BhZ2F0ZSBlZmZlY3RzCiAgICAgICAgICAgIC8vIE5PVEU6IGR1ZSB0byBodHRwczovL2dpdGh1Yi5jb20vZ29vZ2xlL2Nsb3N1cmUtY29tcGlsZXIvaXNzdWVzLzI5MjgsCiAgICAgICAgICAgIC8vIGNvbWJpbmluZyB0aGUgbmV4dCB0d28gbGluZXMgaW50byBvbmUgYXNzaWdubWVudCBjYXVzZXMgYSBzcHVyaW91cwogICAgICAgICAgICAvLyB0eXBlIGVycm9yLgogICAgICAgICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgICAgICAgY2xhc3MgVGVtcGxhdGl6ZWRUZW1wbGF0ZUV4dGVuc2lvbiBleHRlbmRzIHRlbXBsYXRpemVkQmFzZSB7fQogICAgICAgICAgICBrbGFzcyA9IHRlbXBsYXRlSW5mby50ZW1wbGF0aXplVGVtcGxhdGVDbGFzcyA9CiAgICAgICAgICAgICAgICBUZW1wbGF0aXplZFRlbXBsYXRlRXh0ZW5zaW9uOwogICAgICAgICAgfQogICAgICAgICAgLy8gQWRkIHRlbXBsYXRlIC0gPmluc3RhbmNlcyBlZmZlY3RzCiAgICAgICAgICAvLyBhbmQgaG9zdCA8LSB0ZW1wbGF0ZSBlZmZlY3RzCiAgICAgICAgICBsZXQgaG9zdFByb3BzID0gdGVtcGxhdGVJbmZvLmhvc3RQcm9wczsKICAgICAgICAgIGZvciAobGV0IHByb3AgaW4gaG9zdFByb3BzKSB7CiAgICAgICAgICAgIGtsYXNzLnByb3RvdHlwZS5fYWRkUHJvcGVydHlFZmZlY3QoJ19ob3N0XycgKyBwcm9wLAogICAgICAgICAgICAgIGtsYXNzLnByb3RvdHlwZS5QUk9QRVJUWV9FRkZFQ1RfVFlQRVMuUFJPUEFHQVRFLAogICAgICAgICAgICAgIHtmbjogY3JlYXRlRm9yd2FyZEhvc3RQcm9wRWZmZWN0KHByb3AsIHVzZXJGb3J3YXJkSG9zdFByb3ApfSk7CiAgICAgICAgICAgIGtsYXNzLnByb3RvdHlwZS5fY3JlYXRlTm90aWZ5aW5nUHJvcGVydHkoJ19ob3N0XycgKyBwcm9wKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChsZWdhY3lXYXJuaW5ncyAmJiBtZXRob2RIb3N0KSB7CiAgICAgICAgICAgIHdhcm5PblVuZGVjbGFyZWRQcm9wZXJ0aWVzKHRlbXBsYXRlSW5mbywgb3B0aW9ucywgbWV0aG9kSG9zdCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIE1peCBhbnkgcHJlLWJvdW5kIGRhdGEgaW50byBfX2RhdGE7IG5vIG5lZWQgdG8gZmx1c2ggdGhpcyB0bwogICAgICAgIC8vIGluc3RhbmNlcyBzaW5jZSB0aGV5IHB1bGwgZnJvbSB0aGUgdGVtcGxhdGUgYXQgaW5zdGFuY2UtdGltZQogICAgICAgIGlmICh0YXJnZXQuX19kYXRhUHJvdG8pIHsKICAgICAgICAgIC8vIE5vdGUsIGdlbmVyYWxseSBgX19kYXRhUHJvdG9gIGNvdWxkIGJlIGNoYWluZWQsIGJ1dCBpdCdzIGd1YXJhbnRlZWQKICAgICAgICAgIC8vIHRvIG5vdCBiZSBzaW5jZSB0aGlzIGlzIGEgdmFuaWxsYSB0ZW1wbGF0ZSB3ZSBqdXN0IGFkZGVkIGVmZmVjdHMgdG8KICAgICAgICAgIE9iamVjdC5hc3NpZ24odGFyZ2V0Ll9fZGF0YSwgdGFyZ2V0Ll9fZGF0YVByb3RvKTsKICAgICAgICB9CiAgICAgICAgaWYgKGlzVGVtcGxhdGUpIHsKICAgICAgICAgIHVwZ3JhZGVUZW1wbGF0ZSh0YXJnZXQsIGtsYXNzKTsKICAgICAgICAgIC8vIENsZWFyIGFueSBwZW5kaW5nIGRhdGEgZm9yIHBlcmZvcm1hbmNlCiAgICAgICAgICB0YXJnZXQuX19kYXRhVGVtcCA9IHt9OwogICAgICAgICAgdGFyZ2V0Ll9fZGF0YVBlbmRpbmcgPSBudWxsOwogICAgICAgICAgdGFyZ2V0Ll9fZGF0YU9sZCA9IG51bGw7CiAgICAgICAgICB0YXJnZXQuX2VuYWJsZVByb3BlcnRpZXMoKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gU3dpenpsZSB0aGUgY2FjaGVkIHN1YmNsYXNzIHByb3RvdHlwZSBvbnRvIHRoZSBjdXN0b20gZWxlbWVudAogICAgICAgICAgT2JqZWN0LnNldFByb3RvdHlwZU9mKHRhcmdldCwga2xhc3MucHJvdG90eXBlKTsKICAgICAgICAgIC8vIENoZWNrIGZvciBhbnkgcHJlLWJvdW5kIGluc3RhbmNlIGhvc3QgcHJvcGVydGllcywgYW5kIGRvIHRoZQogICAgICAgICAgLy8gaW5zdGFuY2UgcHJvcGVydHkgZGVsZXRlL2Fzc2lnbiBkYW5jZSBmb3IgdGhvc2UgKGRpcmVjdGx5IGludG8gZGF0YTsKICAgICAgICAgIC8vIG5vdCBuZWVkIHRvIGdvIHRocm91Z2ggYWNjZXNzb3Igc2luY2UgdGhleSBhcmUgcHVsbGVkIGF0IGluc3RhbmNlIHRpbWUpCiAgICAgICAgICBjb25zdCBob3N0UHJvcHMgPSB0ZW1wbGF0ZUluZm8uaG9zdFByb3BzOwogICAgICAgICAgZm9yIChsZXQgcHJvcCBpbiBob3N0UHJvcHMpIHsKICAgICAgICAgICAgcHJvcCA9ICdfaG9zdF8nICsgcHJvcDsKICAgICAgICAgICAgaWYgKHByb3AgaW4gdGFyZ2V0KSB7CiAgICAgICAgICAgICAgY29uc3QgdmFsID0gdGFyZ2V0W3Byb3BdOwogICAgICAgICAgICAgIGRlbGV0ZSB0YXJnZXRbcHJvcF07CiAgICAgICAgICAgICAgdGFyZ2V0Ll9fZGF0YVtwcm9wXSA9IHZhbDsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgfQogICAgLyogZXNsaW50LWVuYWJsZSB2YWxpZC1qc2RvYyAqLwoKICAgIGZ1bmN0aW9uIGNyZWF0ZUZvcndhcmRIb3N0UHJvcEVmZmVjdChob3N0UHJvcCwgdXNlckZvcndhcmRIb3N0UHJvcCkgewogICAgICByZXR1cm4gZnVuY3Rpb24gZm9yd2FyZEhvc3RQcm9wKHRlbXBsYXRlLCBwcm9wLCBwcm9wcykgewogICAgICAgIHVzZXJGb3J3YXJkSG9zdFByb3AuY2FsbCh0ZW1wbGF0ZS5fX3RlbXBsYXRpemVPd25lciwKICAgICAgICAgIHByb3Auc3Vic3RyaW5nKCdfaG9zdF8nLmxlbmd0aCksIHByb3BzW3Byb3BdKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhZGROb3RpZnlFZmZlY3RzKGtsYXNzLCB0ZW1wbGF0ZSwgdGVtcGxhdGVJbmZvLCBvcHRpb25zKSB7CiAgICAgIGxldCBob3N0UHJvcHMgPSB0ZW1wbGF0ZUluZm8uaG9zdFByb3BzIHx8IHt9OwogICAgICBmb3IgKGxldCBpcHJvcCBpbiBvcHRpb25zLmluc3RhbmNlUHJvcHMpIHsKICAgICAgICBkZWxldGUgaG9zdFByb3BzW2lwcm9wXTsKICAgICAgICBsZXQgdXNlck5vdGlmeUluc3RhbmNlUHJvcCA9IG9wdGlvbnMubm90aWZ5SW5zdGFuY2VQcm9wOwogICAgICAgIGlmICh1c2VyTm90aWZ5SW5zdGFuY2VQcm9wKSB7CiAgICAgICAgICBrbGFzcy5wcm90b3R5cGUuX2FkZFByb3BlcnR5RWZmZWN0KGlwcm9wLAogICAgICAgICAgICBrbGFzcy5wcm90b3R5cGUuUFJPUEVSVFlfRUZGRUNUX1RZUEVTLk5PVElGWSwKICAgICAgICAgICAge2ZuOiBjcmVhdGVOb3RpZnlJbnN0YW5jZVByb3BFZmZlY3QoaXByb3AsIHVzZXJOb3RpZnlJbnN0YW5jZVByb3ApfSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmIChvcHRpb25zLmZvcndhcmRIb3N0UHJvcCAmJiB0ZW1wbGF0ZS5fX2RhdGFIb3N0KSB7CiAgICAgICAgZm9yIChsZXQgaHByb3AgaW4gaG9zdFByb3BzKSB7CiAgICAgICAgICAvLyBBcyB3ZSdyZSBpdGVyYXRpbmcgaG9zdFByb3BzIGluIHRoaXMgZnVuY3Rpb24sIG5vdGUgd2hldGhlcgogICAgICAgICAgLy8gdGhlcmUgd2VyZSBhbnksIGZvciBhbiBvcHRpbWl6YXRpb24gaW4gYWRkUHJvcGFnYXRlRWZmZWN0cwogICAgICAgICAgaWYgKCF0ZW1wbGF0ZUluZm8uaGFzSG9zdFByb3BzKSB7CiAgICAgICAgICAgIHRlbXBsYXRlSW5mby5oYXNIb3N0UHJvcHMgPSB0cnVlOwogICAgICAgICAgfQogICAgICAgICAga2xhc3MucHJvdG90eXBlLl9hZGRQcm9wZXJ0eUVmZmVjdChocHJvcCwKICAgICAgICAgICAga2xhc3MucHJvdG90eXBlLlBST1BFUlRZX0VGRkVDVF9UWVBFUy5OT1RJRlksCiAgICAgICAgICAgIHtmbjogY3JlYXRlTm90aWZ5SG9zdFByb3BFZmZlY3QoKX0pOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZU5vdGlmeUluc3RhbmNlUHJvcEVmZmVjdChpbnN0UHJvcCwgdXNlck5vdGlmeUluc3RhbmNlUHJvcCkgewogICAgICByZXR1cm4gZnVuY3Rpb24gbm90aWZ5SW5zdGFuY2VQcm9wKGluc3QsIHByb3AsIHByb3BzKSB7CiAgICAgICAgdXNlck5vdGlmeUluc3RhbmNlUHJvcC5jYWxsKGluc3QuX190ZW1wbGF0aXplT3duZXIsCiAgICAgICAgICBpbnN0LCBwcm9wLCBwcm9wc1twcm9wXSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlTm90aWZ5SG9zdFByb3BFZmZlY3QoKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbiBub3RpZnlIb3N0UHJvcChpbnN0LCBwcm9wLCBwcm9wcykgewogICAgICAgIGluc3QuX19kYXRhSG9zdC5fc2V0UGVuZGluZ1Byb3BlcnR5T3JQYXRoKCdfaG9zdF8nICsgcHJvcCwgcHJvcHNbcHJvcF0sIHRydWUsIHRydWUpOwogICAgICB9OwogICAgfQoKCiAgICAvKioKICAgICAqIFJldHVybnMgYW4gYW5vbnltb3VzIGBQcm9wZXJ0eUVmZmVjdHNgIGNsYXNzIGJvdW5kIHRvIHRoZQogICAgICogYDx0ZW1wbGF0ZT5gIHByb3ZpZGVkLiAgSW5zdGFuY2luZyB0aGUgY2xhc3Mgd2lsbCByZXN1bHQgaW4gdGhlCiAgICAgKiB0ZW1wbGF0ZSBiZWluZyBzdGFtcGVkIGludG8gYSBkb2N1bWVudCBmcmFnbWVudCBzdG9yZWQgYXMgdGhlIGluc3RhbmNlJ3MKICAgICAqIGByb290YCBwcm9wZXJ0eSwgYWZ0ZXIgd2hpY2ggaXQgY2FuIGJlIGFwcGVuZGVkIHRvIHRoZSBET00uCiAgICAgKgogICAgICogVGVtcGxhdGVzIG1heSB1dGlsaXplIGFsbCBQb2x5bWVyIGRhdGEtYmluZGluZyBmZWF0dXJlcyBhcyB3ZWxsIGFzCiAgICAgKiBkZWNsYXJhdGl2ZSBldmVudCBsaXN0ZW5lcnMuICBFdmVudCBsaXN0ZW5lcnMgYW5kIGlubGluZSBjb21wdXRpbmcKICAgICAqIGZ1bmN0aW9ucyBpbiB0aGUgdGVtcGxhdGUgd2lsbCBiZSBjYWxsZWQgb24gdGhlIGhvc3Qgb2YgdGhlIHRlbXBsYXRlLgogICAgICoKICAgICAqIFRoZSBjb25zdHJ1Y3RvciByZXR1cm5lZCB0YWtlcyBhIHNpbmdsZSBhcmd1bWVudCBkaWN0aW9uYXJ5IG9mIGluaXRpYWwKICAgICAqIHByb3BlcnR5IHZhbHVlcyB0byBwcm9wYWdhdGUgaW50byB0ZW1wbGF0ZSBiaW5kaW5ncy4gIEFkZGl0aW9uYWxseQogICAgICogaG9zdCBwcm9wZXJ0aWVzIGNhbiBiZSBmb3J3YXJkZWQgaW4sIGFuZCBpbnN0YW5jZSBwcm9wZXJ0aWVzIGNhbiBiZQogICAgICogbm90aWZpZWQgb3V0IGJ5IHByb3ZpZGluZyBvcHRpb25hbCBjYWxsYmFja3MgaW4gdGhlIGBvcHRpb25zYCBkaWN0aW9uYXJ5LgogICAgICoKICAgICAqIFZhbGlkIGNvbmZpZ3VyYXRpb24gaW4gYG9wdGlvbnNgIGFyZSBhcyBmb2xsb3dzOgogICAgICoKICAgICAqIC0gYGZvcndhcmRIb3N0UHJvcChwcm9wZXJ0eSwgdmFsdWUpYDogQ2FsbGVkIHdoZW4gYSBwcm9wZXJ0eSByZWZlcmVuY2VkCiAgICAgKiAgIGluIHRoZSB0ZW1wbGF0ZSBjaGFuZ2VkIG9uIHRoZSB0ZW1wbGF0ZSdzIGhvc3QuIEFzIHRoaXMgbGlicmFyeSBkb2VzCiAgICAgKiAgIG5vdCByZXRhaW4gcmVmZXJlbmNlcyB0byB0ZW1wbGF0ZXMgaW5zdGFuY2VkIGJ5IHRoZSB1c2VyLCBpdCBpcyB0aGUKICAgICAqICAgdGVtcGxhdGl6ZSBvd25lcidzIHJlc3BvbnNpYmlsaXR5IHRvIGZvcndhcmQgaG9zdCBwcm9wZXJ0eSBjaGFuZ2VzIGludG8KICAgICAqICAgdXNlci1zdGFtcGVkIGluc3RhbmNlcy4gIFRoZSBgaW5zdGFuY2UuZm9yd2FyZEhvc3RQcm9wKHByb3BlcnR5LCB2YWx1ZSlgCiAgICAgKiAgICBtZXRob2Qgb24gdGhlIGdlbmVyYXRlZCBjbGFzcyBzaG91bGQgYmUgY2FsbGVkIHRvIGZvcndhcmQgaG9zdAogICAgICogICBwcm9wZXJ0aWVzIGludG8gdGhlIHRlbXBsYXRlIHRvIHByZXZlbnQgdW5uZWNlc3NhcnkgcHJvcGVydHktY2hhbmdlZAogICAgICogICBub3RpZmljYXRpb25zLiBBbnkgcHJvcGVydGllcyByZWZlcmVuY2VkIGluIHRoZSB0ZW1wbGF0ZSB0aGF0IGFyZSBub3QKICAgICAqICAgZGVmaW5lZCBpbiBgaW5zdGFuY2VQcm9wc2Agd2lsbCBiZSBub3RpZmllZCB1cCB0byB0aGUgdGVtcGxhdGUncyBob3N0CiAgICAgKiAgIGF1dG9tYXRpY2FsbHkuCiAgICAgKiAtIGBpbnN0YW5jZVByb3BzYDogRGljdGlvbmFyeSBvZiBwcm9wZXJ0eSBuYW1lcyB0aGF0IHdpbGwgYmUgYWRkZWQKICAgICAqICAgdG8gdGhlIGluc3RhbmNlIGJ5IHRoZSB0ZW1wbGF0aXplIG93bmVyLiAgVGhlc2UgcHJvcGVydGllcyBzaGFkb3cgYW55CiAgICAgKiAgIGhvc3QgcHJvcGVydGllcywgYW5kIGNoYW5nZXMgd2l0aGluIHRoZSB0ZW1wbGF0ZSB0byB0aGVzZSBwcm9wZXJ0aWVzCiAgICAgKiAgIHdpbGwgcmVzdWx0IGluIGBub3RpZnlJbnN0YW5jZVByb3BgIGJlaW5nIGNhbGxlZC4KICAgICAqIC0gYG11dGFibGVEYXRhYDogV2hlbiBgdHJ1ZWAsIHRoZSBnZW5lcmF0ZWQgY2xhc3Mgd2lsbCBza2lwIHN0cmljdAogICAgICogICBkaXJ0eS1jaGVja2luZyBmb3Igb2JqZWN0cyBhbmQgYXJyYXlzIChhbHdheXMgY29uc2lkZXIgdGhlbSB0byBiZQogICAgICogICAiZGlydHkiKS4KICAgICAqIC0gYG5vdGlmeUluc3RhbmNlUHJvcChpbnN0YW5jZSwgcHJvcGVydHksIHZhbHVlKWA6IENhbGxlZCB3aGVuCiAgICAgKiAgIGFuIGluc3RhbmNlIHByb3BlcnR5IGNoYW5nZXMuICBVc2VycyBtYXkgY2hvb3NlIHRvIGNhbGwgYG5vdGlmeVBhdGhgCiAgICAgKiAgIG9uIGUuZy4gdGhlIG93bmVyIHRvIG5vdGlmeSB0aGUgY2hhbmdlLgogICAgICogLSBgcGFyZW50TW9kZWxgOiBXaGVuIGB0cnVlYCwgZXZlbnRzIGhhbmRsZWQgYnkgZGVjbGFyYXRpdmUgZXZlbnQgbGlzdGVuZXJzCiAgICAgKiAgIChgb24tZXZlbnQ9ImhhbmRsZXIiYCkgd2lsbCBiZSBkZWNvcmF0ZWQgd2l0aCBhIGBtb2RlbGAgcHJvcGVydHkgcG9pbnRpbmcKICAgICAqICAgdG8gdGhlIHRlbXBsYXRlIGluc3RhbmNlIHRoYXQgc3RhbXBlZCBpdC4gIEl0IHdpbGwgYWxzbyBiZSByZXR1cm5lZAogICAgICogICBmcm9tIGBpbnN0YW5jZS5wYXJlbnRNb2RlbGAgaW4gY2FzZXMgd2hlcmUgdGVtcGxhdGUgaW5zdGFuY2UgbmVzdGluZwogICAgICogICBjYXVzZXMgYW4gaW5uZXIgbW9kZWwgdG8gc2hhZG93IGFuIG91dGVyIG1vZGVsLgogICAgICoKICAgICAqIEFsbCBjYWxsYmFja3MgYXJlIGNhbGxlZCBib3VuZCB0byB0aGUgYG93bmVyYC4gQW55IGNvbnRleHQKICAgICAqIG5lZWRlZCBmb3IgdGhlIGNhbGxiYWNrcyAoc3VjaCBhcyByZWZlcmVuY2VzIHRvIGBpbnN0YW5jZXNgIHN0YW1wZWQpCiAgICAgKiBzaG91bGQgYmUgc3RvcmVkIG9uIHRoZSBgb3duZXJgIHN1Y2ggdGhhdCB0aGV5IGNhbiBiZSByZXRyaWV2ZWQgdmlhCiAgICAgKiBgdGhpc2AuCiAgICAgKgogICAgICogV2hlbiBgb3B0aW9ucy5mb3J3YXJkSG9zdFByb3BgIGlzIGRlY2xhcmVkIGFzIGFuIG9wdGlvbiwgYW55IHByb3BlcnRpZXMKICAgICAqIHJlZmVyZW5jZWQgaW4gdGhlIHRlbXBsYXRlIHdpbGwgYmUgYXV0b21hdGljYWxseSBmb3J3YXJkZWQgZnJvbSB0aGUgaG9zdCBvZgogICAgICogdGhlIGA8dGVtcGxhdGU+YCB0byBpbnN0YW5jZXMsIHdpdGggdGhlIGV4Y2VwdGlvbiBvZiBhbnkgcHJvcGVydGllcyBsaXN0ZWQgaW4KICAgICAqIHRoZSBgb3B0aW9ucy5pbnN0YW5jZVByb3BzYCBvYmplY3QuICBgaW5zdGFuY2VQcm9wc2AgYXJlIGFzc3VtZWQgdG8gYmUKICAgICAqIG1hbmFnZWQgYnkgdGhlIG93bmVyIG9mIHRoZSBpbnN0YW5jZXMsIGVpdGhlciBwYXNzZWQgaW50byB0aGUgY29uc3RydWN0b3IKICAgICAqIG9yIHNldCBhZnRlciB0aGUgZmFjdC4gIE5vdGUsIGFueSBwcm9wZXJ0aWVzIHBhc3NlZCBpbnRvIHRoZSBjb25zdHJ1Y3RvciB3aWxsCiAgICAgKiBhbHdheXMgYmUgc2V0IHRvIHRoZSBpbnN0YW5jZSAocmVnYXJkbGVzcyBvZiB3aGV0aGVyIHRoZXkgd291bGQgbm9ybWFsbHkKICAgICAqIGJlIGZvcndhcmRlZCBmcm9tIHRoZSBob3N0KS4KICAgICAqCiAgICAgKiBOb3RlIHRoYXQgYHRlbXBsYXRpemUoKWAgY2FuIGJlIHJ1biBvbmx5IG9uY2UgZm9yIGEgZ2l2ZW4gYDx0ZW1wbGF0ZT5gLgogICAgICogRnVydGhlciBjYWxscyB3aWxsIHJlc3VsdCBpbiBhbiBlcnJvci4gQWxzbywgdGhlcmUgaXMgYSBzcGVjaWFsCiAgICAgKiBiZWhhdmlvciBpZiB0aGUgdGVtcGxhdGUgd2FzIGR1cGxpY2F0ZWQgdGhyb3VnaCBhIG1lY2hhbmlzbSBzdWNoIGFzCiAgICAgKiBgPGRvbS1yZXBlYXQ+YCBvciBgPHRlc3QtZml4dHVyZT5gLiBJbiB0aGlzIGNhc2UsIGFsbCBjYWxscyB0bwogICAgICogYHRlbXBsYXRpemUoKWAgcmV0dXJuIHRoZSBzYW1lIGNsYXNzIGZvciBhbGwgZHVwbGljYXRlcyBvZiBhIHRlbXBsYXRlLgogICAgICogVGhlIGNsYXNzIHJldHVybmVkIGZyb20gYHRlbXBsYXRpemUoKWAgaXMgZ2VuZXJhdGVkIG9ubHkgb25jZSB1c2luZwogICAgICogdGhlIGBvcHRpb25zYCBmcm9tIHRoZSBmaXJzdCBjYWxsLiBUaGlzIG1lYW5zIHRoYXQgYW55IGBvcHRpb25zYAogICAgICogcHJvdmlkZWQgdG8gc3Vic2VxdWVudCBjYWxscyB3aWxsIGJlIGlnbm9yZWQuIFRoZXJlZm9yZSwgaXQgaXMgdmVyeQogICAgICogaW1wb3J0YW50IG5vdCB0byBjbG9zZSBvdmVyIGFueSB2YXJpYWJsZXMgaW5zaWRlIHRoZSBjYWxsYmFja3MuIEFsc28sCiAgICAgKiBhcnJvdyBmdW5jdGlvbnMgbXVzdCBiZSBhdm9pZGVkIGJlY2F1c2UgdGhleSBiaW5kIHRoZSBvdXRlciBgdGhpc2AuCiAgICAgKiBJbnNpZGUgdGhlIGNhbGxiYWNrcywgYW55IGNvbnRleHR1YWwgaW5mb3JtYXRpb24gY2FuIGJlIGFjY2Vzc2VkCiAgICAgKiB0aHJvdWdoIGB0aGlzYCwgd2hpY2ggcG9pbnRzIHRvIHRoZSBgb3duZXJgLgogICAgICoKICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlIFRlbXBsYXRlIHRvIHRlbXBsYXRpemUKICAgICAqIEBwYXJhbSB7UG9seW1lcl9Qcm9wZXJ0eUVmZmVjdHM9fSBvd25lciBPd25lciBvZiB0aGUgdGVtcGxhdGUgaW5zdGFuY2VzOwogICAgICogICBhbnkgb3B0aW9uYWwgY2FsbGJhY2tzIHdpbGwgYmUgYm91bmQgdG8gdGhpcyBvd25lci4KICAgICAqIEBwYXJhbSB7T2JqZWN0PX0gb3B0aW9ucyBPcHRpb25zIGRpY3Rpb25hcnkgKHNlZSBzdW1tYXJ5IGZvciBkZXRhaWxzKQogICAgICogQHJldHVybiB7ZnVuY3Rpb24obmV3OlRlbXBsYXRlSW5zdGFuY2VCYXNlLCBPYmplY3Q9KX0gR2VuZXJhdGVkIGNsYXNzIGJvdW5kCiAgICAgKiAgIHRvIHRoZSB0ZW1wbGF0ZSBwcm92aWRlZAogICAgICogQHN1cHByZXNzIHtpbnZhbGlkQ2FzdHN9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHRlbXBsYXRpemUodGVtcGxhdGUsIG93bmVyLCBvcHRpb25zKSB7CiAgICAgIC8vIFVuZGVyIHN0cmljdFRlbXBsYXRlUG9saWN5LCB0aGUgdGVtcGxhdGl6ZWQgZWxlbWVudCBtdXN0IGJlIG93bmVkCiAgICAgIC8vIGJ5IGEgKHRydXN0ZWQpIFBvbHltZXIgZWxlbWVudCwgaW5kaWNhdGVkIGJ5IGV4aXN0ZW5jZSBvZiBfbWV0aG9kSG9zdDsKICAgICAgLy8gZS5nLiBmb3IgZG9tLWlmICYgZG9tLXJlcGVhdCBpbiBtYWluIGRvY3VtZW50LCBfbWV0aG9kSG9zdCBpcyBudWxsCiAgICAgIGlmIChzdHJpY3RUZW1wbGF0ZVBvbGljeSAmJiAhZmluZE1ldGhvZEhvc3QodGVtcGxhdGUpKSB7CiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdzdHJpY3RUZW1wbGF0ZVBvbGljeTogdGVtcGxhdGUgb3duZXIgbm90IHRydXN0ZWQnKTsKICAgICAgfQogICAgICBvcHRpb25zID0gLyoqIEB0eXBlIHshVGVtcGxhdGl6ZU9wdGlvbnN9ICovKG9wdGlvbnMgfHwge30pOwogICAgICBpZiAodGVtcGxhdGUuX190ZW1wbGF0aXplT3duZXIpIHsKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ0EgPHRlbXBsYXRlPiBjYW4gb25seSBiZSB0ZW1wbGF0aXplZCBvbmNlJyk7CiAgICAgIH0KICAgICAgdGVtcGxhdGUuX190ZW1wbGF0aXplT3duZXIgPSBvd25lcjsKICAgICAgY29uc3QgY3RvciA9IG93bmVyID8gb3duZXIuY29uc3RydWN0b3IgOiBUZW1wbGF0ZUluc3RhbmNlQmFzZTsKICAgICAgbGV0IHRlbXBsYXRlSW5mbyA9IGN0b3IuX3BhcnNlVGVtcGxhdGUodGVtcGxhdGUpOwogICAgICAvLyBHZXQgbWVtb2l6ZWQgYmFzZSBjbGFzcyBmb3IgdGhlIHByb3RvdHlwaWNhbCB0ZW1wbGF0ZSwgd2hpY2gKICAgICAgLy8gaW5jbHVkZXMgcHJvcGVydHkgZWZmZWN0cyBmb3IgYmluZGluZyB0ZW1wbGF0ZSAmIGZvcndhcmRpbmcKICAgICAgLyoqCiAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgKiBAZXh0ZW5kcyB7VGVtcGxhdGVJbnN0YW5jZUJhc2V9CiAgICAgICAqLwogICAgICBsZXQgYmFzZUNsYXNzID0gdGVtcGxhdGVJbmZvLnRlbXBsYXRpemVJbnN0YW5jZUNsYXNzOwogICAgICBpZiAoIWJhc2VDbGFzcykgewogICAgICAgIGJhc2VDbGFzcyA9IGNyZWF0ZVRlbXBsYXRpemVyQ2xhc3ModGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgb3B0aW9ucyk7CiAgICAgICAgdGVtcGxhdGVJbmZvLnRlbXBsYXRpemVJbnN0YW5jZUNsYXNzID0gYmFzZUNsYXNzOwogICAgICB9CiAgICAgIGNvbnN0IG1ldGhvZEhvc3QgPSBmaW5kTWV0aG9kSG9zdCh0ZW1wbGF0ZSk7CiAgICAgIC8vIEhvc3QgcHJvcGVydHkgZm9yd2FyZGluZyBtdXN0IGJlIGluc3RhbGxlZCBvbnRvIHRlbXBsYXRlIGluc3RhbmNlCiAgICAgIGFkZFByb3BhZ2F0ZUVmZmVjdHModGVtcGxhdGUsIHRlbXBsYXRlSW5mbywgb3B0aW9ucywgbWV0aG9kSG9zdCk7CiAgICAgIC8vIFN1YmNsYXNzIGJhc2UgY2xhc3MgYW5kIGFkZCByZWZlcmVuY2UgZm9yIHRoaXMgc3BlY2lmaWMgdGVtcGxhdGUKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGxldCBrbGFzcyA9IGNsYXNzIFRlbXBsYXRlSW5zdGFuY2UgZXh0ZW5kcyBiYXNlQ2xhc3Mge307CiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAga2xhc3MucHJvdG90eXBlLl9tZXRob2RIb3N0ID0gbWV0aG9kSG9zdDsKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBrbGFzcy5wcm90b3R5cGUuX19kYXRhSG9zdCA9IC8qKiBAdHlwZSB7IURhdGFUZW1wbGF0ZX0gKi8gKHRlbXBsYXRlKTsKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBrbGFzcy5wcm90b3R5cGUuX190ZW1wbGF0aXplT3duZXIgPSAvKiogQHR5cGUgeyFPYmplY3R9ICovIChvd25lcik7CiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAga2xhc3MucHJvdG90eXBlLl9faG9zdFByb3BzID0gdGVtcGxhdGVJbmZvLmhvc3RQcm9wczsKICAgICAga2xhc3MgPSAvKiogQHR5cGUge2Z1bmN0aW9uKG5ldzpUZW1wbGF0ZUluc3RhbmNlQmFzZSl9ICovKGtsYXNzKTsgLy9lc2xpbnQtZGlzYWJsZS1saW5lIG5vLXNlbGYtYXNzaWduCiAgICAgIHJldHVybiBrbGFzczsKICAgIH0KCiAgICBmdW5jdGlvbiB3YXJuT25VbmRlY2xhcmVkUHJvcGVydGllcyh0ZW1wbGF0ZUluZm8sIG9wdGlvbnMsIG1ldGhvZEhvc3QpIHsKICAgICAgY29uc3QgZGVjbGFyZWRQcm9wcyA9IG1ldGhvZEhvc3QuY29uc3RydWN0b3IuX3Byb3BlcnRpZXM7CiAgICAgIGNvbnN0IHtwcm9wZXJ0eUVmZmVjdHN9ID0gdGVtcGxhdGVJbmZvOwogICAgICBjb25zdCB7aW5zdGFuY2VQcm9wc30gPSBvcHRpb25zOwogICAgICBmb3IgKGxldCBwcm9wIGluIHByb3BlcnR5RWZmZWN0cykgewogICAgICAgIC8vIEVuc3VyZSBwcm9wZXJ0aWVzIHdpdGggdGVtcGxhdGUgZWZmZWN0cyBhcmUgZGVjbGFyZWQgb24gdGhlIG91dGVybW9zdAogICAgICAgIC8vIGhvc3QgKGBtZXRob2RIb3N0YCksIHVubGVzcyB0aGV5IGFyZSBpbnN0YW5jZSBwcm9wcyBvciBzdGF0aWMgZnVuY3Rpb25zCiAgICAgICAgaWYgKCFkZWNsYXJlZFByb3BzW3Byb3BdICYmICEoaW5zdGFuY2VQcm9wcyAmJiBpbnN0YW5jZVByb3BzW3Byb3BdKSkgewogICAgICAgICAgY29uc3QgZWZmZWN0cyA9IHByb3BlcnR5RWZmZWN0c1twcm9wXTsKICAgICAgICAgIGZvciAobGV0IGk9MDsgaTxlZmZlY3RzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGNvbnN0IHtwYXJ0fSA9IGVmZmVjdHNbaV0uaW5mbzsKICAgICAgICAgICAgaWYgKCEocGFydC5zaWduYXR1cmUgJiYgcGFydC5zaWduYXR1cmUuc3RhdGljKSkgewogICAgICAgICAgICAgIGNvbnNvbGUud2FybihgUHJvcGVydHkgJyR7cHJvcH0nIHVzZWQgaW4gdGVtcGxhdGUgYnV0IG5vdCBgICsKICAgICAgICAgICAgICAgIGBkZWNsYXJlZCBpbiAncHJvcGVydGllcyc7IGF0dHJpYnV0ZSB3aWxsIG5vdCBiZSBvYnNlcnZlZC5gKTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgdGVtcGxhdGUgIm1vZGVsIiBhc3NvY2lhdGVkIHdpdGggYSBnaXZlbiBlbGVtZW50LCB3aGljaAogICAgICogc2VydmVzIGFzIHRoZSBiaW5kaW5nIHNjb3BlIGZvciB0aGUgdGVtcGxhdGUgaW5zdGFuY2UgdGhlIGVsZW1lbnQgaXMKICAgICAqIGNvbnRhaW5lZCBpbi4gQSB0ZW1wbGF0ZSBtb2RlbCBpcyBhbiBpbnN0YW5jZSBvZgogICAgICogYFRlbXBsYXRlSW5zdGFuY2VCYXNlYCwgYW5kIHNob3VsZCBiZSB1c2VkIHRvIG1hbmlwdWxhdGUgZGF0YQogICAgICogYXNzb2NpYXRlZCB3aXRoIHRoaXMgdGVtcGxhdGUgaW5zdGFuY2UuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiAgIGxldCBtb2RlbCA9IG1vZGVsRm9yRWxlbWVudChlbCk7CiAgICAgKiAgIGlmIChtb2RlbC5pbmRleCA8IDEwKSB7CiAgICAgKiAgICAgbW9kZWwuc2V0KCdpdGVtLmNoZWNrZWQnLCB0cnVlKTsKICAgICAqICAgfQogICAgICoKICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IHRlbXBsYXRlIFRoZSBtb2RlbCB3aWxsIGJlIHJldHVybmVkIGZvcgogICAgICogICBlbGVtZW50cyBzdGFtcGVkIGZyb20gdGhpcyB0ZW1wbGF0ZSAoYWNjZXB0cyBlaXRoZXIgYW4gSFRNTFRlbXBsYXRlRWxlbWVudCkKICAgICAqICAgb3IgYSBgPGRvbS1pZj5gL2A8ZG9tLXJlcGVhdD5gIGVsZW1lbnQgd2hlbiB1c2luZyBgcmVtb3ZlTmVzdGVkVGVtcGxhdGVzYAogICAgICogICBvcHRpbWl6YXRpb24uCiAgICAgKiBAcGFyYW0ge05vZGU9fSBub2RlIE5vZGUgZm9yIHdoaWNoIHRvIHJldHVybiBhIHRlbXBsYXRlIG1vZGVsLgogICAgICogQHJldHVybiB7VGVtcGxhdGVJbnN0YW5jZUJhc2V9IFRlbXBsYXRlIGluc3RhbmNlIHJlcHJlc2VudGluZyB0aGUKICAgICAqICAgYmluZGluZyBzY29wZSBmb3IgdGhlIGVsZW1lbnQKICAgICAqLwogICAgZnVuY3Rpb24gbW9kZWxGb3JFbGVtZW50KHRlbXBsYXRlLCBub2RlKSB7CiAgICAgIGxldCBtb2RlbDsKICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICAvLyBBbiBlbGVtZW50IHdpdGggYSBfX3RlbXBsYXRpemVJbnN0YW5jZSBtYXJrcyB0aGUgdG9wIGJvdW5kYXJ5CiAgICAgICAgLy8gb2YgYSBzY29wZTsgd2FsayB1cCB1bnRpbCB3ZSBmaW5kIG9uZSwgYW5kIHRoZW4gZW5zdXJlIHRoYXQKICAgICAgICAvLyBpdHMgX19kYXRhSG9zdCBtYXRjaGVzIGB0aGlzYCwgbWVhbmluZyB0aGlzIGRvbS1yZXBlYXQgc3RhbXBlZCBpdAogICAgICAgIGlmICgobW9kZWwgPSBub2RlLl9fZGF0YUhvc3QgPyBub2RlIDogbm9kZS5fX3RlbXBsYXRpemVJbnN0YW5jZSkpIHsKICAgICAgICAgIC8vIEZvdW5kIGFuIGVsZW1lbnQgc3RhbXBlZCBieSBhbm90aGVyIHRlbXBsYXRlOyBrZWVwIHdhbGtpbmcgdXAKICAgICAgICAgIC8vIGZyb20gaXRzIF9fZGF0YUhvc3QKICAgICAgICAgIGlmIChtb2RlbC5fX2RhdGFIb3N0ICE9IHRlbXBsYXRlKSB7CiAgICAgICAgICAgIG5vZGUgPSBtb2RlbC5fX2RhdGFIb3N0OwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcmV0dXJuIG1vZGVsOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBTdGlsbCBpbiBhIHRlbXBsYXRlIHNjb3BlLCBrZWVwIGdvaW5nIHVwIHVudGlsCiAgICAgICAgICAvLyBhIF9fdGVtcGxhdGl6ZUluc3RhbmNlIGlzIGZvdW5kCiAgICAgICAgICBub2RlID0gd3JhcChub2RlKS5wYXJlbnROb2RlOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogVGhlIGBUZW1wbGF0aXplcmAgYmVoYXZpb3IgYWRkcyBtZXRob2RzIHRvIGdlbmVyYXRlIGluc3RhbmNlcyBvZgogICAgICogdGVtcGxhdGVzIHRoYXQgYXJlIGVhY2ggbWFuYWdlZCBieSBhbiBhbm9ueW1vdXMgYFByb3BlcnR5RWZmZWN0c2AKICAgICAqIGluc3RhbmNlIHdoZXJlIGRhdGEtYmluZGluZ3MgaW4gdGhlIHN0YW1wZWQgdGVtcGxhdGUgY29udGVudCBhcmUgYm91bmQgdG8KICAgICAqIGFjY2Vzc29ycyBvbiBpdHNlbGYuCiAgICAgKgogICAgICogVGhpcyBiZWhhdmlvciBpcyBwcm92aWRlZCBpbiBQb2x5bWVyIDIueC0zLnggYXMgYSBoeWJyaWQtZWxlbWVudCBjb252ZW5pZW5jZQogICAgICogb25seS4gIEZvciBub24taHlicmlkIHVzYWdlLCB0aGUgYFRlbXBsYXRpemVgIGxpYnJhcnkKICAgICAqIHNob3VsZCBiZSB1c2VkIGluc3RlYWQuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiAgICAgaW1wb3J0IHtkb219IGZyb20gJ0Bwb2x5bWVyL3BvbHltZXIvbGliL2xlZ2FjeS9wb2x5bWVyLmRvbS5qcyc7CiAgICAgKiAgICAgLy8gR2V0IGEgdGVtcGxhdGUgZnJvbSBzb21ld2hlcmUsIGUuZy4gbGlnaHQgRE9NCiAgICAgKiAgICAgbGV0IHRlbXBsYXRlID0gdGhpcy5xdWVyeVNlbGVjdG9yKCd0ZW1wbGF0ZScpOwogICAgICogICAgIC8vIFByZXBhcmUgdGhlIHRlbXBsYXRlCiAgICAgKiAgICAgdGhpcy50ZW1wbGF0aXplKHRlbXBsYXRlKTsKICAgICAqICAgICAvLyBJbnN0YW5jZSB0aGUgdGVtcGxhdGUgd2l0aCBhbiBpbml0aWFsIGRhdGEgbW9kZWwKICAgICAqICAgICBsZXQgaW5zdGFuY2UgPSB0aGlzLnN0YW1wKHtteVByb3A6ICdpbml0aWFsJ30pOwogICAgICogICAgIC8vIEluc2VydCB0aGUgaW5zdGFuY2UncyBET00gc29tZXdoZXJlLCBlLmcuIGxpZ2h0IERPTQogICAgICogICAgIGRvbSh0aGlzKS5hcHBlbmRDaGlsZChpbnN0YW5jZS5yb290KTsKICAgICAqICAgICAvLyBDaGFuZ2luZyBhIHByb3BlcnR5IG9uIHRoZSBpbnN0YW5jZSB3aWxsIHByb3BhZ2F0ZSB0byBiaW5kaW5ncwogICAgICogICAgIC8vIGluIHRoZSB0ZW1wbGF0ZQogICAgICogICAgIGluc3RhbmNlLm15UHJvcCA9ICduZXcgdmFsdWUnOwogICAgICoKICAgICAqIFVzZXJzIG9mIGBUZW1wbGF0aXplcmAgbWF5IG5lZWQgdG8gaW1wbGVtZW50IHRoZSBmb2xsb3dpbmcgYWJzdHJhY3QKICAgICAqIEFQSSdzIHRvIGRldGVybWluZSBob3cgcHJvcGVydGllcyBhbmQgcGF0aHMgZnJvbSB0aGUgaG9zdCBzaG91bGQgYmUKICAgICAqIGZvcndhcmRlZCBpbnRvIHRvIGluc3RhbmNlczoKICAgICAqCiAgICAgKiAgICAgX2ZvcndhcmRIb3N0UHJvcFYyOiBmdW5jdGlvbihwcm9wLCB2YWx1ZSkKICAgICAqCiAgICAgKiBMaWtld2lzZSwgdXNlcnMgbWF5IGltcGxlbWVudCB0aGVzZSBhZGRpdGlvbmFsIGFic3RyYWN0IEFQSSdzIHRvIGRldGVybWluZQogICAgICogaG93IGluc3RhbmNlLXNwZWNpZmljIHByb3BlcnRpZXMgdGhhdCBjaGFuZ2Ugb24gdGhlIGluc3RhbmNlIHNob3VsZCBiZQogICAgICogZm9yd2FyZGVkIG91dCB0byB0aGUgaG9zdCwgaWYgbmVjZXNzYXJ5LgogICAgICoKICAgICAqICAgICBfbm90aWZ5SW5zdGFuY2VQcm9wVjI6IGZ1bmN0aW9uKGluc3QsIHByb3AsIHZhbHVlKQogICAgICoKICAgICAqIEluIG9yZGVyIHRvIGRldGVybWluZSB3aGljaCBwcm9wZXJ0aWVzIGFyZSBpbnN0YW5jZS1zcGVjaWZpYyBhbmQgcmVxdWlyZQogICAgICogY3VzdG9tIG5vdGlmaWNhdGlvbiB2aWEgYF9ub3RpZnlJbnN0YW5jZVByb3BgLCBkZWZpbmUgYW4gYF9pbnN0YW5jZVByb3BzYAogICAgICogb2JqZWN0IGNvbnRhaW5pbmcga2V5cyBmb3IgZWFjaCBpbnN0YW5jZSBwcm9wLCBmb3IgZXhhbXBsZToKICAgICAqCiAgICAgKiAgICAgX2luc3RhbmNlUHJvcHM6IHsKICAgICAqICAgICAgIGl0ZW06IHRydWUsCiAgICAgKiAgICAgICBpbmRleDogdHJ1ZQogICAgICogICAgIH0KICAgICAqCiAgICAgKiBBbnkgcHJvcGVydGllcyB1c2VkIGluIHRoZSB0ZW1wbGF0ZSB0aGF0IGFyZSBub3QgZGVmaW5lZCBpbiBfaW5zdGFuY2VQcm9wCiAgICAgKiB3aWxsIGJlIGZvcndhcmRlZCBvdXQgdG8gdGhlIFRlbXBsYXRpemUgYG93bmVyYCBhdXRvbWF0aWNhbGx5LgogICAgICoKICAgICAqIFVzZXJzIG1heSBhbHNvIGltcGxlbWVudCB0aGUgZm9sbG93aW5nIGFic3RyYWN0IGZ1bmN0aW9uIHRvIHNob3cgb3IKICAgICAqIGhpZGUgYW55IERPTSBnZW5lcmF0ZWQgdXNpbmcgYHN0YW1wYDoKICAgICAqCiAgICAgKiAgICAgX3Nob3dIaWRlQ2hpbGRyZW46IGZ1bmN0aW9uKHNob3VsZEhpZGUpCiAgICAgKgogICAgICogTm90ZSB0aGF0IHNvbWUgY2FsbGJhY2tzIGFyZSBzdWZmaXhlZCB3aXRoIGBWMmAgaW4gdGhlIFBvbHltZXIgMi54IGJlaGF2aW9yCiAgICAgKiBhcyB0aGUgaW1wbGVtZW50YXRpb25zIHdpbGwgbmVlZCB0byBkaWZmZXIgZnJvbSB0aGUgY2FsbGJhY2tzIHJlcXVpcmVkCiAgICAgKiBieSB0aGUgMS54IFRlbXBsYXRpemVyIEFQSSBkdWUgdG8gY2hhbmdlcyBpbiB0aGUgYFRlbXBsYXRlSW5zdGFuY2VgIEFQSQogICAgICogYmV0d2VlbiB2ZXJzaW9ucyAxLnggYW5kIDIueC4KICAgICAqCiAgICAgKiBAcG9seW1lckJlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IFRlbXBsYXRpemVyID0gewoKICAgICAgLyoqCiAgICAgICAqIEdlbmVyYXRlcyBhbiBhbm9ueW1vdXMgYFRlbXBsYXRlSW5zdGFuY2VgIGNsYXNzIChzdG9yZWQgYXMgYHRoaXMuY3RvcmApCiAgICAgICAqIGZvciB0aGUgcHJvdmlkZWQgdGVtcGxhdGUuICBUaGlzIG1ldGhvZCBzaG91bGQgYmUgY2FsbGVkIG9uY2UgcGVyCiAgICAgICAqIHRlbXBsYXRlIHRvIHByZXBhcmUgYW4gZWxlbWVudCBmb3Igc3RhbXBpbmcgdGhlIHRlbXBsYXRlLCBmb2xsb3dlZAogICAgICAgKiBieSBgc3RhbXBgIHRvIGNyZWF0ZSBuZXcgaW5zdGFuY2VzIG9mIHRoZSB0ZW1wbGF0ZS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gdGVtcGxhdGUgVGVtcGxhdGUgdG8gcHJlcGFyZQogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW49fSBtdXRhYmxlRGF0YSBXaGVuIGB0cnVlYCwgdGhlIGdlbmVyYXRlZCBjbGFzcyB3aWxsIHNraXAKICAgICAgICogICBzdHJpY3QgZGlydHktY2hlY2tpbmcgZm9yIG9iamVjdHMgYW5kIGFycmF5cyAoYWx3YXlzIGNvbnNpZGVyIHRoZW0gdG8KICAgICAgICogICBiZSAiZGlydHkiKS4gRGVmYXVsdHMgdG8gZmFsc2UuCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqIEB0aGlzIHtUZW1wbGF0aXplclVzZXJ9CiAgICAgICAqLwogICAgICB0ZW1wbGF0aXplKHRlbXBsYXRlLCBtdXRhYmxlRGF0YSkgewogICAgICAgIHRoaXMuX3RlbXBsYXRpemVyVGVtcGxhdGUgPSB0ZW1wbGF0ZTsKICAgICAgICB0aGlzLmN0b3IgPQogICAgICAgICAgICB0ZW1wbGF0aXplKHRlbXBsYXRlLCAvKiogQHR5cGUgeyFQb2x5bWVyX1Byb3BlcnR5RWZmZWN0c30gKi8gKHRoaXMpLCB7CiAgICAgICAgICAgICAgbXV0YWJsZURhdGE6IEJvb2xlYW4obXV0YWJsZURhdGEpLAogICAgICAgICAgICAgIHBhcmVudE1vZGVsOiB0aGlzLl9wYXJlbnRNb2RlbCwKICAgICAgICAgICAgICBpbnN0YW5jZVByb3BzOiB0aGlzLl9pbnN0YW5jZVByb3BzLAogICAgICAgICAgICAgIGZvcndhcmRIb3N0UHJvcDogdGhpcy5fZm9yd2FyZEhvc3RQcm9wVjIsCiAgICAgICAgICAgICAgbm90aWZ5SW5zdGFuY2VQcm9wOiB0aGlzLl9ub3RpZnlJbnN0YW5jZVByb3BWMgogICAgICAgICAgICB9KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDcmVhdGVzIGFuIGluc3RhbmNlIG9mIHRoZSB0ZW1wbGF0ZSBwcmVwYXJlZCBieSBgdGVtcGxhdGl6ZWAuICBUaGUgb2JqZWN0CiAgICAgICAqIHJldHVybmVkIGlzIGFuIGluc3RhbmNlIG9mIHRoZSBhbm9ueW1vdXMgY2xhc3MgZ2VuZXJhdGVkIGJ5IGB0ZW1wbGF0aXplYAogICAgICAgKiB3aG9zZSBgcm9vdGAgcHJvcGVydHkgaXMgYSBkb2N1bWVudCBmcmFnbWVudCBjb250YWluaW5nIG5ld2x5IGNsb25lZAogICAgICAgKiB0ZW1wbGF0ZSBjb250ZW50LCBhbmQgd2hpY2ggaGFzIHByb3BlcnR5IGFjY2Vzc29ycyBjb3JyZXNwb25kaW5nIHRvCiAgICAgICAqIHByb3BlcnRpZXMgcmVmZXJlbmNlZCBpbiB0ZW1wbGF0ZSBiaW5kaW5ncy4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSBtb2RlbCBPYmplY3QgY29udGFpbmluZyBpbml0aWFsIHByb3BlcnR5IHZhbHVlcyB0bwogICAgICAgKiAgIHBvcHVsYXRlIGludG8gdGhlIHRlbXBsYXRlIGJpbmRpbmdzLgogICAgICAgKiBAcmV0dXJuIHtUZW1wbGF0ZUluc3RhbmNlQmFzZX0gUmV0dXJucyB0aGUgY3JlYXRlZCBpbnN0YW5jZSBvZgogICAgICAgKiB0aGUgdGVtcGxhdGUgcHJlcGFyZWQgYnkgYHRlbXBsYXRpemVgLgogICAgICAgKiBAdGhpcyB7VGVtcGxhdGl6ZXJVc2VyfQogICAgICAgKi8KICAgICAgc3RhbXAobW9kZWwpIHsKICAgICAgICByZXR1cm4gbmV3IHRoaXMuY3Rvcihtb2RlbCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgdGVtcGxhdGUgIm1vZGVsIiAoYFRlbXBsYXRlSW5zdGFuY2VgKSBhc3NvY2lhdGVkIHdpdGgKICAgICAgICogYSBnaXZlbiBlbGVtZW50LCB3aGljaCBzZXJ2ZXMgYXMgdGhlIGJpbmRpbmcgc2NvcGUgZm9yIHRoZSB0ZW1wbGF0ZQogICAgICAgKiBpbnN0YW5jZSB0aGUgZWxlbWVudCBpcyBjb250YWluZWQgaW4uICBBIHRlbXBsYXRlIG1vZGVsIHNob3VsZCBiZSB1c2VkCiAgICAgICAqIHRvIG1hbmlwdWxhdGUgZGF0YSBhc3NvY2lhdGVkIHdpdGggdGhpcyB0ZW1wbGF0ZSBpbnN0YW5jZS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWwgRWxlbWVudCBmb3Igd2hpY2ggdG8gcmV0dXJuIGEgdGVtcGxhdGUgbW9kZWwuCiAgICAgICAqIEByZXR1cm4ge1RlbXBsYXRlSW5zdGFuY2VCYXNlfSBNb2RlbCByZXByZXNlbnRpbmcgdGhlIGJpbmRpbmcgc2NvcGUgZm9yCiAgICAgICAqICAgdGhlIGVsZW1lbnQuCiAgICAgICAqIEB0aGlzIHtUZW1wbGF0aXplclVzZXJ9CiAgICAgICAqLwogICAgICBtb2RlbEZvckVsZW1lbnQoZWwpIHsKICAgICAgICByZXR1cm4gbW9kZWxGb3JFbGVtZW50KHRoaXMuX3RlbXBsYXRpemVyVGVtcGxhdGUsIGVsKTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGxldCBlbGVtZW50c0hpZGRlbiA9IGZhbHNlOwoKICAgIC8qKgogICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBlbGVtZW50cyB3aWxsIGJlIGhpZGRlbiBnbG9iYWxseQogICAgICovCiAgICBmdW5jdGlvbiBoaWRlRWxlbWVudHNHbG9iYWxseSgpIHsKICAgICAgaWYgKGxlZ2FjeU9wdGltaXphdGlvbnMgJiYgIXVzZVNoYWRvdykgewogICAgICAgIGlmICghZWxlbWVudHNIaWRkZW4pIHsKICAgICAgICAgIGVsZW1lbnRzSGlkZGVuID0gdHJ1ZTsKICAgICAgICAgIGNvbnN0IHN0eWxlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKTsKICAgICAgICAgIHN0eWxlLnRleHRDb250ZW50ID0gJ2RvbS1iaW5kLGRvbS1pZixkb20tcmVwZWF0e2Rpc3BsYXk6bm9uZTt9JzsKICAgICAgICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoc3R5bGUpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQGV4dGVuZHMge0hUTUxFbGVtZW50fQogICAgICogQGltcGxlbWVudHMge1BvbHltZXJfUHJvcGVydHlFZmZlY3RzfQogICAgICogQGltcGxlbWVudHMge1BvbHltZXJfT3B0aW9uYWxNdXRhYmxlRGF0YX0KICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX0dlc3R1cmVFdmVudExpc3RlbmVyc30KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGNvbnN0IGRvbUJpbmRCYXNlID0KICAgICAgR2VzdHVyZUV2ZW50TGlzdGVuZXJzKAogICAgICAgIE9wdGlvbmFsTXV0YWJsZURhdGEoCiAgICAgICAgICBQcm9wZXJ0eUVmZmVjdHMoSFRNTEVsZW1lbnQpKSk7CgogICAgLyoqCiAgICAgKiBDdXN0b20gZWxlbWVudCB0byBhbGxvdyB1c2luZyBQb2x5bWVyJ3MgdGVtcGxhdGUgZmVhdHVyZXMgKGRhdGEgYmluZGluZywKICAgICAqIGRlY2xhcmF0aXZlIGV2ZW50IGxpc3RlbmVycywgZXRjLikgaW4gdGhlIG1haW4gZG9jdW1lbnQgd2l0aG91dCBkZWZpbmluZwogICAgICogYSBuZXcgY3VzdG9tIGVsZW1lbnQuCiAgICAgKgogICAgICogYDx0ZW1wbGF0ZT5gIHRhZ3MgdXRpbGl6aW5nIGJpbmRpbmdzIG1heSBiZSB3cmFwcGVkIHdpdGggdGhlIGA8ZG9tLWJpbmQ+YAogICAgICogZWxlbWVudCwgd2hpY2ggd2lsbCBpbW1lZGlhdGVseSBzdGFtcCB0aGUgd3JhcHBlZCB0ZW1wbGF0ZSBpbnRvIHRoZSBtYWluCiAgICAgKiBkb2N1bWVudCBhbmQgYmluZCBlbGVtZW50cyB0byB0aGUgYGRvbS1iaW5kYCBlbGVtZW50IGl0c2VsZiBhcyB0aGUKICAgICAqIGJpbmRpbmcgc2NvcGUuCiAgICAgKgogICAgICogQHBvbHltZXIKICAgICAqIEBjdXN0b21FbGVtZW50CiAgICAgKiBAYXBwbGllc01peGluIFByb3BlcnR5RWZmZWN0cwogICAgICogQGFwcGxpZXNNaXhpbiBPcHRpb25hbE11dGFibGVEYXRhCiAgICAgKiBAYXBwbGllc01peGluIEdlc3R1cmVFdmVudExpc3RlbmVycwogICAgICogQGV4dGVuZHMge2RvbUJpbmRCYXNlfQogICAgICogQHN1bW1hcnkgQ3VzdG9tIGVsZW1lbnQgdG8gYWxsb3cgdXNpbmcgUG9seW1lcidzIHRlbXBsYXRlIGZlYXR1cmVzIChkYXRhCiAgICAgKiAgIGJpbmRpbmcsIGRlY2xhcmF0aXZlIGV2ZW50IGxpc3RlbmVycywgZXRjLikgaW4gdGhlIG1haW4gZG9jdW1lbnQuCiAgICAgKi8KICAgIGNsYXNzIERvbUJpbmQgZXh0ZW5kcyBkb21CaW5kQmFzZSB7CgogICAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHsgcmV0dXJuIFsnbXV0YWJsZS1kYXRhJ107IH0KCiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CiAgICAgICAgaWYgKHN0cmljdFRlbXBsYXRlUG9saWN5KSB7CiAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYHN0cmljdFRlbXBsYXRlUG9saWN5OiBkb20tYmluZCBub3QgYWxsb3dlZGApOwogICAgICAgIH0KICAgICAgICB0aGlzLnJvb3QgPSBudWxsOwogICAgICAgIHRoaXMuJCA9IG51bGw7CiAgICAgICAgdGhpcy5fX2NoaWxkcmVuID0gbnVsbDsKICAgICAgfQoKICAgICAgLyogZXNsaW50LWRpc2FibGUgbm8tdW51c2VkLXZhcnMgKi8KICAgICAgLyoqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gbmFtZSBOYW1lIG9mIGF0dHJpYnV0ZSB0aGF0IGNoYW5nZWQKICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSBvbGQgT2xkIGF0dHJpYnV0ZSB2YWx1ZQogICAgICAgKiBAcGFyYW0gez9zdHJpbmd9IHZhbHVlIE5ldyBhdHRyaWJ1dGUgdmFsdWUKICAgICAgICogQHBhcmFtIHs/c3RyaW5nfSBuYW1lc3BhY2UgQXR0cmlidXRlIG5hbWVzcGFjZS4KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGQsIHZhbHVlLCBuYW1lc3BhY2UpIHsKICAgICAgICAvLyBhc3N1bWVzIG9ubHkgb25lIG9ic2VydmVkIGF0dHJpYnV0ZQogICAgICAgIHRoaXMubXV0YWJsZURhdGEgPSB0cnVlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICBpZiAoIWhpZGVFbGVtZW50c0dsb2JhbGx5KCkpIHsKICAgICAgICAgIHRoaXMuc3R5bGUuZGlzcGxheSA9ICdub25lJzsKICAgICAgICB9CiAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgdGhpcy5fX3JlbW92ZUNoaWxkcmVuKCk7CiAgICAgIH0KCiAgICAgIF9faW5zZXJ0Q2hpbGRyZW4oKSB7CiAgICAgICAgd3JhcCh3cmFwKHRoaXMpLnBhcmVudE5vZGUpLmluc2VydEJlZm9yZSh0aGlzLnJvb3QsIHRoaXMpOwogICAgICB9CgogICAgICBfX3JlbW92ZUNoaWxkcmVuKCkgewogICAgICAgIGlmICh0aGlzLl9fY2hpbGRyZW4pIHsKICAgICAgICAgIGZvciAobGV0IGk9MDsgaTx0aGlzLl9fY2hpbGRyZW4ubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgdGhpcy5yb290LmFwcGVuZENoaWxkKHRoaXMuX19jaGlsZHJlbltpXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogRm9yY2VzIHRoZSBlbGVtZW50IHRvIHJlbmRlciBpdHMgY29udGVudC4gVGhpcyBpcyB0eXBpY2FsbHkgb25seQogICAgICAgKiBuZWNlc3NhcnkgdG8gY2FsbCBpZiBIVE1MSW1wb3J0cyB3aXRoIHRoZSBhc3luYyBhdHRyaWJ1dGUgYXJlIHVzZWQuCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICByZW5kZXIoKSB7CiAgICAgICAgbGV0IHRlbXBsYXRlOwogICAgICAgIGlmICghdGhpcy5fX2NoaWxkcmVuKSB7CiAgICAgICAgICB0ZW1wbGF0ZSA9IC8qKiBAdHlwZSB7P0hUTUxUZW1wbGF0ZUVsZW1lbnR9ICovKHRlbXBsYXRlIHx8IHRoaXMucXVlcnlTZWxlY3RvcigndGVtcGxhdGUnKSk7CiAgICAgICAgICBpZiAoIXRlbXBsYXRlKSB7CiAgICAgICAgICAgIC8vIFdhaXQgdW50aWwgY2hpbGRMaXN0IGNoYW5nZXMgYW5kIHRlbXBsYXRlIHNob3VsZCBiZSB0aGVyZSBieSB0aGVuCiAgICAgICAgICAgIGxldCBvYnNlcnZlciA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKCgpID0+IHsKICAgICAgICAgICAgICB0ZW1wbGF0ZSA9IC8qKiBAdHlwZSB7SFRNTFRlbXBsYXRlRWxlbWVudH0gKi8odGhpcy5xdWVyeVNlbGVjdG9yKCd0ZW1wbGF0ZScpKTsKICAgICAgICAgICAgICBpZiAodGVtcGxhdGUpIHsKICAgICAgICAgICAgICAgIG9ic2VydmVyLmRpc2Nvbm5lY3QoKTsKICAgICAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignZG9tLWJpbmQgcmVxdWlyZXMgYSA8dGVtcGxhdGU+IGNoaWxkJyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgb2JzZXJ2ZXIub2JzZXJ2ZSh0aGlzLCB7Y2hpbGRMaXN0OiB0cnVlfSk7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMucm9vdCA9IHRoaXMuX3N0YW1wVGVtcGxhdGUoCiAgICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9ICovKHRlbXBsYXRlKSk7CiAgICAgICAgICB0aGlzLiQgPSB0aGlzLnJvb3QuJDsKICAgICAgICAgIHRoaXMuX19jaGlsZHJlbiA9IFtdOwogICAgICAgICAgZm9yIChsZXQgbj10aGlzLnJvb3QuZmlyc3RDaGlsZDsgbjsgbj1uLm5leHRTaWJsaW5nKSB7CiAgICAgICAgICAgIHRoaXMuX19jaGlsZHJlblt0aGlzLl9fY2hpbGRyZW4ubGVuZ3RoXSA9IG47CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9lbmFibGVQcm9wZXJ0aWVzKCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX19pbnNlcnRDaGlsZHJlbigpOwogICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2RvbS1jaGFuZ2UnLCB7CiAgICAgICAgICBidWJibGVzOiB0cnVlLAogICAgICAgICAgY29tcG9zZWQ6IHRydWUKICAgICAgICB9KSk7CiAgICAgIH0KCiAgICB9CgogICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdkb20tYmluZCcsIERvbUJpbmQpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAY29uc3RydWN0b3IKICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX09wdGlvbmFsTXV0YWJsZURhdGF9CiAgICAgKiBAZXh0ZW5kcyB7UG9seW1lckVsZW1lbnR9CiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBjb25zdCBkb21SZXBlYXRCYXNlID0gT3B0aW9uYWxNdXRhYmxlRGF0YShQb2x5bWVyRWxlbWVudCk7CgogICAgLyoqCiAgICAgKiBUaGUgYDxkb20tcmVwZWF0PmAgZWxlbWVudCB3aWxsIGF1dG9tYXRpY2FsbHkgc3RhbXAgYW5kIGJpbmRzIG9uZSBpbnN0YW5jZQogICAgICogb2YgdGVtcGxhdGUgY29udGVudCB0byBlYWNoIG9iamVjdCBpbiBhIHVzZXItcHJvdmlkZWQgYXJyYXkuCiAgICAgKiBgZG9tLXJlcGVhdGAgYWNjZXB0cyBhbiBgaXRlbXNgIHByb3BlcnR5LCBhbmQgb25lIGluc3RhbmNlIG9mIHRoZSB0ZW1wbGF0ZQogICAgICogaXMgc3RhbXBlZCBmb3IgZWFjaCBpdGVtIGludG8gdGhlIERPTSBhdCB0aGUgbG9jYXRpb24gb2YgdGhlIGBkb20tcmVwZWF0YAogICAgICogZWxlbWVudC4gIFRoZSBgaXRlbWAgcHJvcGVydHkgd2lsbCBiZSBzZXQgb24gZWFjaCBpbnN0YW5jZSdzIGJpbmRpbmcKICAgICAqIHNjb3BlLCB0aHVzIHRlbXBsYXRlcyBzaG91bGQgYmluZCB0byBzdWItcHJvcGVydGllcyBvZiBgaXRlbWAuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiBgYGBodG1sCiAgICAgKiA8ZG9tLW1vZHVsZSBpZD0iZW1wbG95ZWUtbGlzdCI+CiAgICAgKgogICAgICogICA8dGVtcGxhdGU+CiAgICAgKgogICAgICogICAgIDxkaXY+IEVtcGxveWVlIGxpc3Q6IDwvZGl2PgogICAgICogICAgIDxkb20tcmVwZWF0IGl0ZW1zPSJ7e2VtcGxveWVlc319Ij4KICAgICAqICAgICAgIDx0ZW1wbGF0ZT4KICAgICAqICAgICAgICAgPGRpdj5GaXJzdCBuYW1lOiA8c3Bhbj57e2l0ZW0uZmlyc3R9fTwvc3Bhbj48L2Rpdj4KICAgICAqICAgICAgICAgPGRpdj5MYXN0IG5hbWU6IDxzcGFuPnt7aXRlbS5sYXN0fX08L3NwYW4+PC9kaXY+CiAgICAgKiAgICAgICA8L3RlbXBsYXRlPgogICAgICogICAgIDwvZG9tLXJlcGVhdD4KICAgICAqCiAgICAgKiAgIDwvdGVtcGxhdGU+CiAgICAgKgogICAgICogPC9kb20tbW9kdWxlPgogICAgICogYGBgCiAgICAgKgogICAgICogV2l0aCB0aGUgZm9sbG93aW5nIGN1c3RvbSBlbGVtZW50IGRlZmluaXRpb246CiAgICAgKgogICAgICogYGBganMKICAgICAqIGNsYXNzIEVtcGxveWVlTGlzdCBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAqICAgc3RhdGljIGdldCBpcygpIHsgcmV0dXJuICdlbXBsb3llZS1saXN0JzsgfQogICAgICogICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgKiAgICAgcmV0dXJuIHsKICAgICAqICAgICAgIGVtcGxveWVlczogewogICAgICogICAgICAgICB2YWx1ZSgpIHsKICAgICAqICAgICAgICAgICByZXR1cm4gWwogICAgICogICAgICAgICAgICAge2ZpcnN0OiAnQm9iJywgbGFzdDogJ1NtaXRoJ30sCiAgICAgKiAgICAgICAgICAgICB7Zmlyc3Q6ICdTYWxseScsIGxhc3Q6ICdKb2huc29uJ30sCiAgICAgKiAgICAgICAgICAgICAuLi4KICAgICAqICAgICAgICAgICBdOwogICAgICogICAgICAgICB9CiAgICAgKiAgICAgICB9CiAgICAgKiAgICAgfTsKICAgICAqICAgfQogICAgICogfQogICAgICogYGBgCiAgICAgKgogICAgICogTm90aWZpY2F0aW9ucyBmb3IgY2hhbmdlcyB0byBpdGVtcyBzdWItcHJvcGVydGllcyB3aWxsIGJlIGZvcndhcmRlZCB0byB0ZW1wbGF0ZQogICAgICogaW5zdGFuY2VzLCB3aGljaCB3aWxsIHVwZGF0ZSB2aWEgdGhlIG5vcm1hbCBzdHJ1Y3R1cmVkIGRhdGEgbm90aWZpY2F0aW9uIHN5c3RlbS4KICAgICAqCiAgICAgKiBNdXRhdGlvbnMgdG8gdGhlIGBpdGVtc2AgYXJyYXkgaXRzZWxmIHNob3VsZCBiZSBtYWRlIHVzaW5nIHRoZSBBcnJheQogICAgICogbXV0YXRpb24gQVBJJ3Mgb24gdGhlIFByb3BlcnR5RWZmZWN0cyBtaXhpbiAoYHB1c2hgLCBgcG9wYCwgYHNwbGljZWAsCiAgICAgKiBgc2hpZnRgLCBgdW5zaGlmdGApLCBhbmQgdGVtcGxhdGUgaW5zdGFuY2VzIHdpbGwgYmUga2VwdCBpbiBzeW5jIHdpdGggdGhlCiAgICAgKiBkYXRhIGluIHRoZSBhcnJheS4KICAgICAqCiAgICAgKiBFdmVudHMgY2F1Z2h0IGJ5IGV2ZW50IGhhbmRsZXJzIHdpdGhpbiB0aGUgYGRvbS1yZXBlYXRgIHRlbXBsYXRlIHdpbGwgYmUKICAgICAqIGRlY29yYXRlZCB3aXRoIGEgYG1vZGVsYCBwcm9wZXJ0eSwgd2hpY2ggcmVwcmVzZW50cyB0aGUgYmluZGluZyBzY29wZSBmb3IKICAgICAqIGVhY2ggdGVtcGxhdGUgaW5zdGFuY2UuICBUaGUgbW9kZWwgc2hvdWxkIGJlIHVzZWQgdG8gbWFuaXB1bGF0ZSBkYXRhIG9uIHRoZQogICAgICogaW5zdGFuY2UsIGZvciBleGFtcGxlIGBldmVudC5tb2RlbC5zZXQoJ2l0ZW0uY2hlY2tlZCcsIHRydWUpO2AuCiAgICAgKgogICAgICogQWx0ZXJuYXRpdmVseSwgdGhlIG1vZGVsIGZvciBhIHRlbXBsYXRlIGluc3RhbmNlIGZvciBhbiBlbGVtZW50IHN0YW1wZWQgYnkKICAgICAqIGEgYGRvbS1yZXBlYXRgIGNhbiBiZSBvYnRhaW5lZCB1c2luZyB0aGUgYG1vZGVsRm9yRWxlbWVudGAgQVBJIG9uIHRoZQogICAgICogYGRvbS1yZXBlYXRgIHRoYXQgc3RhbXBlZCBpdCwgZm9yIGV4YW1wbGUKICAgICAqIGB0aGlzLiQuZG9tUmVwZWF0Lm1vZGVsRm9yRWxlbWVudChldmVudC50YXJnZXQpLnNldCgnaXRlbS5jaGVja2VkJywgdHJ1ZSk7YC4KICAgICAqIFRoaXMgbWF5IGJlIHVzZWZ1bCBmb3IgbWFuaXB1bGF0aW5nIGluc3RhbmNlIGRhdGEgb2YgZXZlbnQgdGFyZ2V0cyBvYnRhaW5lZAogICAgICogYnkgZXZlbnQgaGFuZGxlcnMgb24gcGFyZW50cyBvZiB0aGUgYGRvbS1yZXBlYXRgIChldmVudCBkZWxlZ2F0aW9uKS4KICAgICAqCiAgICAgKiBBIHZpZXctc3BlY2lmaWMgZmlsdGVyL3NvcnQgbWF5IGJlIGFwcGxpZWQgdG8gZWFjaCBgZG9tLXJlcGVhdGAgYnkgc3VwcGx5aW5nIGEKICAgICAqIGBmaWx0ZXJgIGFuZC9vciBgc29ydGAgcHJvcGVydHkuICBUaGlzIG1heSBiZSBhIHN0cmluZyB0aGF0IG5hbWVzIGEgZnVuY3Rpb24gb24KICAgICAqIHRoZSBob3N0LCBvciBhIGZ1bmN0aW9uIG1heSBiZSBhc3NpZ25lZCB0byB0aGUgcHJvcGVydHkgZGlyZWN0bHkuICBUaGUgZnVuY3Rpb25zCiAgICAgKiBzaG91bGQgaW1wbGVtZW50ZWQgZm9sbG93aW5nIHRoZSBzdGFuZGFyZCBgQXJyYXlgIGZpbHRlci9zb3J0IEFQSS4KICAgICAqCiAgICAgKiBJbiBvcmRlciB0byByZS1ydW4gdGhlIGZpbHRlciBvciBzb3J0IGZ1bmN0aW9ucyBiYXNlZCBvbiBjaGFuZ2VzIHRvIHN1Yi1maWVsZHMKICAgICAqIG9mIGBpdGVtc2AsIHRoZSBgb2JzZXJ2ZWAgcHJvcGVydHkgbWF5IGJlIHNldCBhcyBhIHNwYWNlLXNlcGFyYXRlZCBsaXN0IG9mCiAgICAgKiBgaXRlbWAgc3ViLWZpZWxkcyB0aGF0IHNob3VsZCBjYXVzZSBhIHJlLWZpbHRlci9zb3J0IHdoZW4gbW9kaWZpZWQuICBJZgogICAgICogdGhlIGZpbHRlciBvciBzb3J0IGZ1bmN0aW9uIGRlcGVuZHMgb24gcHJvcGVydGllcyBub3QgY29udGFpbmVkIGluIGBpdGVtc2AsCiAgICAgKiB0aGUgdXNlciBzaG91bGQgb2JzZXJ2ZSBjaGFuZ2VzIHRvIHRob3NlIHByb3BlcnRpZXMgYW5kIGNhbGwgYHJlbmRlcmAgdG8gdXBkYXRlCiAgICAgKiB0aGUgdmlldyBiYXNlZCBvbiB0aGUgZGVwZW5kZW5jeSBjaGFuZ2UuCiAgICAgKgogICAgICogRm9yIGV4YW1wbGUsIGZvciBhbiBgZG9tLXJlcGVhdGAgd2l0aCBhIGZpbHRlciBvZiB0aGUgZm9sbG93aW5nOgogICAgICoKICAgICAqIGBgYGpzCiAgICAgKiBpc0VuZ2luZWVyKGl0ZW0pIHsKICAgICAqICAgcmV0dXJuIGl0ZW0udHlwZSA9PSAnZW5naW5lZXInIHx8IGl0ZW0ubWFuYWdlci50eXBlID09ICdlbmdpbmVlcic7CiAgICAgKiB9CiAgICAgKiBgYGAKICAgICAqCiAgICAgKiBUaGVuIHRoZSBgb2JzZXJ2ZWAgcHJvcGVydHkgc2hvdWxkIGJlIGNvbmZpZ3VyZWQgYXMgZm9sbG93czoKICAgICAqCiAgICAgKiBgYGBodG1sCiAgICAgKiA8ZG9tLXJlcGVhdCBpdGVtcz0ie3tlbXBsb3llZXN9fSIgZmlsdGVyPSJpc0VuZ2luZWVyIiBvYnNlcnZlPSJ0eXBlIG1hbmFnZXIudHlwZSI+CiAgICAgKiBgYGAKICAgICAqCiAgICAgKiBAY3VzdG9tRWxlbWVudAogICAgICogQHBvbHltZXIKICAgICAqIEBleHRlbmRzIHtkb21SZXBlYXRCYXNlfQogICAgICogQGFwcGxpZXNNaXhpbiBPcHRpb25hbE11dGFibGVEYXRhCiAgICAgKiBAc3VtbWFyeSBDdXN0b20gZWxlbWVudCBmb3Igc3RhbXBpbmcgaW5zdGFuY2Ugb2YgYSB0ZW1wbGF0ZSBib3VuZCB0bwogICAgICogICBpdGVtcyBpbiBhbiBhcnJheS4KICAgICAqLwogICAgY2xhc3MgRG9tUmVwZWF0IGV4dGVuZHMgZG9tUmVwZWF0QmFzZSB7CgogICAgICAvLyBOb3QgbmVlZGVkIHRvIGZpbmQgdGVtcGxhdGU7IGNhbiBiZSByZW1vdmVkIG9uY2UgdGhlIGFuYWx5emVyCiAgICAgIC8vIGNhbiBmaW5kIHRoZSB0YWcgbmFtZSBmcm9tIGN1c3RvbUVsZW1lbnRzLmRlZmluZSBjYWxsCiAgICAgIHN0YXRpYyBnZXQgaXMoKSB7IHJldHVybiAnZG9tLXJlcGVhdCc7IH0KCiAgICAgIHN0YXRpYyBnZXQgdGVtcGxhdGUoKSB7IHJldHVybiBudWxsOyB9CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CgogICAgICAgIC8qKgogICAgICAgICAqIEZpcmVkIHdoZW5ldmVyIERPTSBpcyBhZGRlZCBvciByZW1vdmVkIGJ5IHRoaXMgdGVtcGxhdGUgKGJ5CiAgICAgICAgICogZGVmYXVsdCwgcmVuZGVyaW5nIG9jY3VycyBsYXppbHkpLiAgVG8gZm9yY2UgaW1tZWRpYXRlIHJlbmRlcmluZywgY2FsbAogICAgICAgICAqIGByZW5kZXJgLgogICAgICAgICAqCiAgICAgICAgICogQGV2ZW50IGRvbS1jaGFuZ2UKICAgICAgICAgKi8KICAgICAgICByZXR1cm4gewoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQW4gYXJyYXkgY29udGFpbmluZyBpdGVtcyBkZXRlcm1pbmluZyBob3cgbWFueSBpbnN0YW5jZXMgb2YgdGhlIHRlbXBsYXRlCiAgICAgICAgICAgKiB0byBzdGFtcCBhbmQgdGhhdCB0aGF0IGVhY2ggdGVtcGxhdGUgaW5zdGFuY2Ugc2hvdWxkIGJpbmQgdG8uCiAgICAgICAgICAgKi8KICAgICAgICAgIGl0ZW1zOiB7CiAgICAgICAgICAgIHR5cGU6IEFycmF5CiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogVGhlIG5hbWUgb2YgdGhlIHZhcmlhYmxlIHRvIGFkZCB0byB0aGUgYmluZGluZyBzY29wZSBmb3IgdGhlIGFycmF5CiAgICAgICAgICAgKiBlbGVtZW50IGFzc29jaWF0ZWQgd2l0aCBhIGdpdmVuIHRlbXBsYXRlIGluc3RhbmNlLgogICAgICAgICAgICovCiAgICAgICAgICBhczogewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIHZhbHVlOiAnaXRlbScKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgdmFyaWFibGUgdG8gYWRkIHRvIHRoZSBiaW5kaW5nIHNjb3BlIHdpdGggdGhlIGluZGV4CiAgICAgICAgICAgKiBvZiB0aGUgaW5zdGFuY2UgaW4gdGhlIHNvcnRlZCBhbmQgZmlsdGVyZWQgbGlzdCBvZiByZW5kZXJlZCBpdGVtcy4KICAgICAgICAgICAqIE5vdGUsIGZvciB0aGUgaW5kZXggaW4gdGhlIGB0aGlzLml0ZW1zYCBhcnJheSwgdXNlIHRoZSB2YWx1ZSBvZiB0aGUKICAgICAgICAgICAqIGBpdGVtc0luZGV4QXNgIHByb3BlcnR5LgogICAgICAgICAgICovCiAgICAgICAgICBpbmRleEFzOiB7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgdmFsdWU6ICdpbmRleCcKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgdmFyaWFibGUgdG8gYWRkIHRvIHRoZSBiaW5kaW5nIHNjb3BlIHdpdGggdGhlIGluZGV4CiAgICAgICAgICAgKiBvZiB0aGUgaW5zdGFuY2UgaW4gdGhlIGB0aGlzLml0ZW1zYCBhcnJheS4gTm90ZSwgZm9yIHRoZSBpbmRleCBvZgogICAgICAgICAgICogdGhpcyBpbnN0YW5jZSBpbiB0aGUgc29ydGVkIGFuZCBmaWx0ZXJlZCBsaXN0IG9mIHJlbmRlcmVkIGl0ZW1zLAogICAgICAgICAgICogdXNlIHRoZSB2YWx1ZSBvZiB0aGUgYGluZGV4QXNgIHByb3BlcnR5LgogICAgICAgICAgICovCiAgICAgICAgICBpdGVtc0luZGV4QXM6IHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICB2YWx1ZTogJ2l0ZW1zSW5kZXgnCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQSBmdW5jdGlvbiB0aGF0IHNob3VsZCBkZXRlcm1pbmUgdGhlIHNvcnQgb3JkZXIgb2YgdGhlIGl0ZW1zLiAgVGhpcwogICAgICAgICAgICogcHJvcGVydHkgc2hvdWxkIGVpdGhlciBiZSBwcm92aWRlZCBhcyBhIHN0cmluZywgaW5kaWNhdGluZyBhIG1ldGhvZAogICAgICAgICAgICogbmFtZSBvbiB0aGUgZWxlbWVudCdzIGhvc3QsIG9yIGVsc2UgYmUgYW4gYWN0dWFsIGZ1bmN0aW9uLiAgVGhlCiAgICAgICAgICAgKiBmdW5jdGlvbiBzaG91bGQgbWF0Y2ggdGhlIHNvcnQgZnVuY3Rpb24gcGFzc2VkIHRvIGBBcnJheS5zb3J0YC4KICAgICAgICAgICAqIFVzaW5nIGEgc29ydCBmdW5jdGlvbiBoYXMgbm8gZWZmZWN0IG9uIHRoZSB1bmRlcmx5aW5nIGBpdGVtc2AgYXJyYXkuCiAgICAgICAgICAgKi8KICAgICAgICAgIHNvcnQ6IHsKICAgICAgICAgICAgdHlwZTogRnVuY3Rpb24sCiAgICAgICAgICAgIG9ic2VydmVyOiAnX19zb3J0Q2hhbmdlZCcKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBBIGZ1bmN0aW9uIHRoYXQgY2FuIGJlIHVzZWQgdG8gZmlsdGVyIGl0ZW1zIG91dCBvZiB0aGUgdmlldy4gIFRoaXMKICAgICAgICAgICAqIHByb3BlcnR5IHNob3VsZCBlaXRoZXIgYmUgcHJvdmlkZWQgYXMgYSBzdHJpbmcsIGluZGljYXRpbmcgYSBtZXRob2QKICAgICAgICAgICAqIG5hbWUgb24gdGhlIGVsZW1lbnQncyBob3N0LCBvciBlbHNlIGJlIGFuIGFjdHVhbCBmdW5jdGlvbi4gIFRoZQogICAgICAgICAgICogZnVuY3Rpb24gc2hvdWxkIG1hdGNoIHRoZSBzb3J0IGZ1bmN0aW9uIHBhc3NlZCB0byBgQXJyYXkuZmlsdGVyYC4KICAgICAgICAgICAqIFVzaW5nIGEgZmlsdGVyIGZ1bmN0aW9uIGhhcyBubyBlZmZlY3Qgb24gdGhlIHVuZGVybHlpbmcgYGl0ZW1zYCBhcnJheS4KICAgICAgICAgICAqLwogICAgICAgICAgZmlsdGVyOiB7CiAgICAgICAgICAgIHR5cGU6IEZ1bmN0aW9uLAogICAgICAgICAgICBvYnNlcnZlcjogJ19fZmlsdGVyQ2hhbmdlZCcKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIHVzaW5nIGEgYGZpbHRlcmAgb3IgYHNvcnRgIGZ1bmN0aW9uLCB0aGUgYG9ic2VydmVgIHByb3BlcnR5CiAgICAgICAgICAgKiBzaG91bGQgYmUgc2V0IHRvIGEgc3BhY2Utc2VwYXJhdGVkIGxpc3Qgb2YgdGhlIG5hbWVzIG9mIGl0ZW0KICAgICAgICAgICAqIHN1Yi1maWVsZHMgdGhhdCBzaG91bGQgdHJpZ2dlciBhIHJlLXNvcnQgb3IgcmUtZmlsdGVyIHdoZW4gY2hhbmdlZC4KICAgICAgICAgICAqIFRoZXNlIHNob3VsZCBnZW5lcmFsbHkgYmUgZmllbGRzIG9mIGBpdGVtYCB0aGF0IHRoZSBzb3J0IG9yIGZpbHRlcgogICAgICAgICAgICogZnVuY3Rpb24gZGVwZW5kcyBvbi4KICAgICAgICAgICAqLwogICAgICAgICAgb2JzZXJ2ZTogewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX19vYnNlcnZlQ2hhbmdlZCcKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIHVzaW5nIGEgYGZpbHRlcmAgb3IgYHNvcnRgIGZ1bmN0aW9uLCB0aGUgYGRlbGF5YCBwcm9wZXJ0eQogICAgICAgICAgICogZGV0ZXJtaW5lcyBhIGRlYm91bmNlIHRpbWUgaW4gbXMgYWZ0ZXIgYSBjaGFuZ2UgdG8gb2JzZXJ2ZWQgaXRlbQogICAgICAgICAgICogcHJvcGVydGllcyB0aGF0IG11c3QgcGFzcyBiZWZvcmUgdGhlIGZpbHRlciBvciBzb3J0IGlzIHJlLXJ1bi4KICAgICAgICAgICAqIFRoaXMgaXMgdXNlZnVsIGluIHJhdGUtbGltaXRpbmcgc2h1ZmZsaW5nIG9mIHRoZSB2aWV3IHdoZW4KICAgICAgICAgICAqIGl0ZW0gY2hhbmdlcyBtYXkgYmUgZnJlcXVlbnQuCiAgICAgICAgICAgKi8KICAgICAgICAgIGRlbGF5OiBOdW1iZXIsCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBDb3VudCBvZiBjdXJyZW50bHkgcmVuZGVyZWQgaXRlbXMgYWZ0ZXIgYGZpbHRlcmAgKGlmIGFueSkgaGFzIGJlZW4gYXBwbGllZC4KICAgICAgICAgICAqIElmICJjaHVua2luZyBtb2RlIiBpcyBlbmFibGVkLCBgcmVuZGVyZWRJdGVtQ291bnRgIGlzIHVwZGF0ZWQgZWFjaCB0aW1lIGEKICAgICAgICAgICAqIHNldCBvZiB0ZW1wbGF0ZSBpbnN0YW5jZXMgaXMgcmVuZGVyZWQuCiAgICAgICAgICAgKgogICAgICAgICAgICovCiAgICAgICAgICByZW5kZXJlZEl0ZW1Db3VudDogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG5vdGlmeTogIXN1cHByZXNzVGVtcGxhdGVOb3RpZmljYXRpb25zLAogICAgICAgICAgICByZWFkT25seTogdHJ1ZQogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFdoZW4gZ3JlYXRlciB0aGFuIHplcm8sIGRlZmluZXMgYW4gaW5pdGlhbCBjb3VudCBvZiB0ZW1wbGF0ZSBpbnN0YW5jZXMKICAgICAgICAgICAqIHRvIHJlbmRlciBhZnRlciBzZXR0aW5nIHRoZSBgaXRlbXNgIGFycmF5LCBiZWZvcmUgdGhlIG5leHQgcGFpbnQsIGFuZAogICAgICAgICAgICogcHV0cyB0aGUgYGRvbS1yZXBlYXRgIGludG8gImNodW5raW5nIG1vZGUiLiAgVGhlIHJlbWFpbmluZyBpdGVtcyAoYW5kCiAgICAgICAgICAgKiBhbnkgZnV0dXJlIGl0ZW1zIGFzIGEgcmVzdWx0IG9mIHB1c2hpbmcgb250byB0aGUgYXJyYXkpIHdpbGwgYmUgY3JlYXRlZAogICAgICAgICAgICogYW5kIHJlbmRlcmVkIGluY3JlbWVudGFsbHkgYXQgZWFjaCBhbmltYXRpb24gZnJhbWUgdGhlcmVvZiB1bnRpbCBhbGwKICAgICAgICAgICAqIGluc3RhbmNlcyBoYXZlIGJlZW4gcmVuZGVyZWQuCiAgICAgICAgICAgKi8KICAgICAgICAgIGluaXRpYWxDb3VudDogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIGBpbml0aWFsQ291bnRgIGlzIHVzZWQsIHRoaXMgcHJvcGVydHkgZGVmaW5lcyBhIGZyYW1lIHJhdGUgKGluCiAgICAgICAgICAgKiBmcHMpIHRvIHRhcmdldCBieSB0aHJvdHRsaW5nIHRoZSBudW1iZXIgb2YgaW5zdGFuY2VzIHJlbmRlcmVkIGVhY2gKICAgICAgICAgICAqIGZyYW1lIHRvIG5vdCBleGNlZWQgdGhlIGJ1ZGdldCBmb3IgdGhlIHRhcmdldCBmcmFtZSByYXRlLiAgVGhlCiAgICAgICAgICAgKiBmcmFtZXJhdGUgaXMgZWZmZWN0aXZlbHkgdGhlIG51bWJlciBvZiBgcmVxdWVzdEFuaW1hdGlvbkZyYW1lYHMgdGhhdAogICAgICAgICAgICogaXQgdHJpZXMgdG8gYWxsb3cgdG8gYWN0dWFsbHkgZmlyZSBpbiBhIGdpdmVuIHNlY29uZC4gSXQgZG9lcyB0aGlzCiAgICAgICAgICAgKiBieSBtZWFzdXJpbmcgdGhlIHRpbWUgYmV0d2VlbiBgckFGYHMgYW5kIGNvbnRpbnVvdXNseSBhZGp1c3RpbmcgdGhlCiAgICAgICAgICAgKiBudW1iZXIgb2YgaXRlbXMgY3JlYXRlZCBlYWNoIGByQUZgIHRvIG1haW50YWluIHRoZSB0YXJnZXQgZnJhbWVyYXRlLgogICAgICAgICAgICogU2V0dGluZyB0aGlzIHRvIGEgaGlnaGVyIG51bWJlciBhbGxvd3MgbG93ZXIgbGF0ZW5jeSBhbmQgaGlnaGVyCiAgICAgICAgICAgKiB0aHJvdWdocHV0IGZvciBldmVudCBoYW5kbGVycyBhbmQgb3RoZXIgdGFza3MsIGJ1dCByZXN1bHRzIGluIGEKICAgICAgICAgICAqIGxvbmdlciB0aW1lIGZvciB0aGUgcmVtYWluaW5nIGl0ZW1zIHRvIGNvbXBsZXRlIHJlbmRlcmluZy4KICAgICAgICAgICAqLwogICAgICAgICAgdGFyZ2V0RnJhbWVyYXRlOiB7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgdmFsdWU6IDIwCiAgICAgICAgICB9LAoKICAgICAgICAgIF90YXJnZXRGcmFtZVRpbWU6IHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBjb21wdXRlZDogJ19fY29tcHV0ZUZyYW1lVGltZSh0YXJnZXRGcmFtZXJhdGUpJwogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFdoZW4gdGhlIGdsb2JhbCBgc3VwcHJlc3NUZW1wbGF0ZU5vdGlmaWNhdGlvbnNgIHNldHRpbmcgaXMgdXNlZCwgc2V0dGluZwogICAgICAgICAgICogYG5vdGlmeURvbUNoYW5nZTogdHJ1ZWAgd2lsbCBlbmFibGUgZmlyaW5nIGBkb20tY2hhbmdlYCBldmVudHMgb24gdGhpcwogICAgICAgICAgICogZWxlbWVudC4KICAgICAgICAgICAqLwogICAgICAgICAgbm90aWZ5RG9tQ2hhbmdlOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4KICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIGNodW5raW5nIGlzIGVuYWJsZWQgdmlhIGBpbml0aWFsQ291bnRgIGFuZCB0aGUgYGl0ZW1zYCBhcnJheSBpcwogICAgICAgICAgICogc2V0IHRvIGEgbmV3IGFycmF5LCB0aGlzIGZsYWcgY29udHJvbHMgd2hldGhlciB0aGUgcHJldmlvdXNseSByZW5kZXJlZAogICAgICAgICAgICogaW5zdGFuY2VzIGFyZSByZXVzZWQgb3Igbm90LgogICAgICAgICAgICoKICAgICAgICAgICAqIFdoZW4gYHRydWVgLCBhbnkgcHJldmlvdXNseSByZW5kZXJlZCB0ZW1wbGF0ZSBpbnN0YW5jZXMgYXJlIHVwZGF0ZWQgaW4KICAgICAgICAgICAqIHBsYWNlIHRvIHRoZWlyIG5ldyBpdGVtIHZhbHVlcyBzeW5jaHJvbm91c2x5IGluIG9uZSBzaG90LCBhbmQgdGhlbiBhbnkKICAgICAgICAgICAqIGZ1cnRoZXIgaXRlbXMgKGlmIGFueSkgYXJlIGNodW5rZWQgb3V0LiAgV2hlbiBgZmFsc2VgLCB0aGUgbGlzdCBpcwogICAgICAgICAgICogcmV0dXJuZWQgYmFjayB0byBpdHMgYGluaXRpYWxDb3VudGAgKGFueSBpbnN0YW5jZXMgb3ZlciB0aGUgaW5pdGlhbAogICAgICAgICAgICogY291bnQgYXJlIGRpc2NhcmRlZCkgYW5kIHRoZSByZW1haW5kZXIgb2YgdGhlIGxpc3QgaXMgY2h1bmtlZCBiYWNrIGluLgogICAgICAgICAgICogU2V0IHRoaXMgdG8gYHRydWVgIHRvIGF2b2lkIHJlLWNyZWF0aW5nIHRoZSBsaXN0IGFuZCBsb3Npbmcgc2Nyb2xsCiAgICAgICAgICAgKiBwb3NpdGlvbiwgYWx0aG91Z2ggbm90ZSB0aGF0IHdoZW4gY2hhbmdpbmcgdGhlIGxpc3QgdG8gY29tcGxldGVseQogICAgICAgICAgICogZGlmZmVyZW50IGRhdGEgdGhlIHJlbmRlciB0aHJlYWQgd2lsbCBiZSBibG9ja2VkIHVudGlsIGFsbCBleGlzdGluZwogICAgICAgICAgICogaW5zdGFuY2VzIGFyZSB1cGRhdGVkIHRvIHRoZWlyIG5ldyBkYXRhLgogICAgICAgICAgICovCiAgICAgICAgICByZXVzZUNodW5rZWRJbnN0YW5jZXM6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbgogICAgICAgICAgfQoKICAgICAgICB9OwoKICAgICAgfQoKICAgICAgc3RhdGljIGdldCBvYnNlcnZlcnMoKSB7CiAgICAgICAgcmV0dXJuIFsgJ19faXRlbXNDaGFuZ2VkKGl0ZW1zLiopJyBdOwogICAgICB9CgogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICBzdXBlcigpOwogICAgICAgIHRoaXMuX19pbnN0YW5jZXMgPSBbXTsKICAgICAgICB0aGlzLl9fcmVuZGVyRGVib3VuY2VyID0gbnVsbDsKICAgICAgICB0aGlzLl9faXRlbXNJZHhUb0luc3RJZHggPSB7fTsKICAgICAgICB0aGlzLl9fY2h1bmtDb3VudCA9IG51bGw7CiAgICAgICAgdGhpcy5fX3JlbmRlclN0YXJ0VGltZSA9IG51bGw7CiAgICAgICAgdGhpcy5fX2l0ZW1zQXJyYXlDaGFuZ2VkID0gZmFsc2U7CiAgICAgICAgdGhpcy5fX3Nob3VsZE1lYXN1cmVDaHVuayA9IGZhbHNlOwogICAgICAgIHRoaXMuX19zaG91bGRDb250aW51ZUNodW5raW5nID0gZmFsc2U7CiAgICAgICAgdGhpcy5fX2NodW5raW5nSWQgPSAwOwogICAgICAgIHRoaXMuX19zb3J0Rm4gPSBudWxsOwogICAgICAgIHRoaXMuX19maWx0ZXJGbiA9IG51bGw7CiAgICAgICAgdGhpcy5fX29ic2VydmVQYXRocyA9IG51bGw7CiAgICAgICAgLyoqIEB0eXBlIHs/ZnVuY3Rpb24obmV3OlRlbXBsYXRlSW5zdGFuY2VCYXNlLCBPYmplY3Q9KX0gKi8KICAgICAgICB0aGlzLl9fY3RvciA9IG51bGw7CiAgICAgICAgdGhpcy5fX2lzRGV0YWNoZWQgPSB0cnVlOwogICAgICAgIHRoaXMudGVtcGxhdGUgPSBudWxsOwogICAgICAgIC8qKiBAdHlwZSB7VGVtcGxhdGVJbmZvfSAqLwogICAgICAgIHRoaXMuX3RlbXBsYXRlSW5mbzsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICB0aGlzLl9faXNEZXRhY2hlZCA9IHRydWU7CiAgICAgICAgZm9yIChsZXQgaT0wOyBpPHRoaXMuX19pbnN0YW5jZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIHRoaXMuX19kZXRhY2hJbnN0YW5jZShpKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgICAgaWYgKCFoaWRlRWxlbWVudHNHbG9iYWxseSgpKSB7CiAgICAgICAgICB0aGlzLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgICAgfQogICAgICAgIC8vIG9ubHkgcGVyZm9ybSBhdHRhY2htZW50IGlmIHRoZSBlbGVtZW50IHdhcyBwcmV2aW91c2x5IGRldGFjaGVkLgogICAgICAgIGlmICh0aGlzLl9faXNEZXRhY2hlZCkgewogICAgICAgICAgdGhpcy5fX2lzRGV0YWNoZWQgPSBmYWxzZTsKICAgICAgICAgIGxldCB3cmFwcGVkUGFyZW50ID0gd3JhcCh3cmFwKHRoaXMpLnBhcmVudE5vZGUpOwogICAgICAgICAgZm9yIChsZXQgaT0wOyBpPHRoaXMuX19pbnN0YW5jZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgdGhpcy5fX2F0dGFjaEluc3RhbmNlKGksIHdyYXBwZWRQYXJlbnQpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgX19lbnN1cmVUZW1wbGF0aXplZCgpIHsKICAgICAgICAvLyBUZW1wbGF0aXppbmcgKGdlbmVyYXRpbmcgdGhlIGluc3RhbmNlIGNvbnN0cnVjdG9yKSBuZWVkcyB0byB3YWl0CiAgICAgICAgLy8gdW50aWwgcmVhZHksIHNpbmNlIHdvbid0IGhhdmUgaXRzIHRlbXBsYXRlIGNvbnRlbnQgaGFuZGVkIGJhY2sgdG8KICAgICAgICAvLyBpdCB1bnRpbCB0aGVuCiAgICAgICAgaWYgKCF0aGlzLl9fY3RvcikgewogICAgICAgICAgLy8gV2hlbiBgcmVtb3ZlTmVzdGVkVGVtcGxhdGVzYCBpcyB0cnVlLCB0aGUgInRlbXBsYXRlIiBpcyB0aGUgZWxlbWVudAogICAgICAgICAgLy8gaXRzZWxmLCB3aGljaCBoYXMgYmVlbiBnaXZlbiBhIGBfdGVtcGxhdGVJbmZvYCBwcm9wZXJ0eQogICAgICAgICAgY29uc3QgdGhpc0FzVGVtcGxhdGUgPSAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fSAqLyAoCiAgICAgICAgICAgICAgLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovICh0aGlzKSk7CiAgICAgICAgICBsZXQgdGVtcGxhdGUgPSB0aGlzLnRlbXBsYXRlID0gdGhpc0FzVGVtcGxhdGUuX3RlbXBsYXRlSW5mbyA/CiAgICAgICAgICAgICAgdGhpc0FzVGVtcGxhdGUgOgogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9ICovICh0aGlzLnF1ZXJ5U2VsZWN0b3IoJ3RlbXBsYXRlJykpOwogICAgICAgICAgaWYgKCF0ZW1wbGF0ZSkgewogICAgICAgICAgICAvLyBXYWl0IHVudGlsIGNoaWxkTGlzdCBjaGFuZ2VzIGFuZCB0ZW1wbGF0ZSBzaG91bGQgYmUgdGhlcmUgYnkgdGhlbgogICAgICAgICAgICBsZXQgb2JzZXJ2ZXIgPSBuZXcgTXV0YXRpb25PYnNlcnZlcigoKSA9PiB7CiAgICAgICAgICAgICAgaWYgKHRoaXMucXVlcnlTZWxlY3RvcigndGVtcGxhdGUnKSkgewogICAgICAgICAgICAgICAgb2JzZXJ2ZXIuZGlzY29ubmVjdCgpOwogICAgICAgICAgICAgICAgdGhpcy5fX3JlbmRlcigpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2RvbS1yZXBlYXQgcmVxdWlyZXMgYSA8dGVtcGxhdGU+IGNoaWxkJyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgb2JzZXJ2ZXIub2JzZXJ2ZSh0aGlzLCB7Y2hpbGRMaXN0OiB0cnVlfSk7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIFRlbXBsYXRlIGluc3RhbmNlIHByb3BzIHRoYXQgc2hvdWxkIGJlIGV4Y2x1ZGVkIGZyb20gZm9yd2FyZGluZwogICAgICAgICAgbGV0IGluc3RhbmNlUHJvcHMgPSB7fTsKICAgICAgICAgIGluc3RhbmNlUHJvcHNbdGhpcy5hc10gPSB0cnVlOwogICAgICAgICAgaW5zdGFuY2VQcm9wc1t0aGlzLmluZGV4QXNdID0gdHJ1ZTsKICAgICAgICAgIGluc3RhbmNlUHJvcHNbdGhpcy5pdGVtc0luZGV4QXNdID0gdHJ1ZTsKICAgICAgICAgIHRoaXMuX19jdG9yID0gdGVtcGxhdGl6ZSh0ZW1wbGF0ZSwgdGhpcywgewogICAgICAgICAgICBtdXRhYmxlRGF0YTogdGhpcy5tdXRhYmxlRGF0YSwKICAgICAgICAgICAgcGFyZW50TW9kZWw6IHRydWUsCiAgICAgICAgICAgIGluc3RhbmNlUHJvcHM6IGluc3RhbmNlUHJvcHMsCiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBAdGhpcyB7RG9tUmVwZWF0fQogICAgICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBQcm9wZXJ0eSB0byBzZXQKICAgICAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSB0byBzZXQgcHJvcGVydHkgdG8KICAgICAgICAgICAgICovCiAgICAgICAgICAgIGZvcndhcmRIb3N0UHJvcDogZnVuY3Rpb24ocHJvcCwgdmFsdWUpIHsKICAgICAgICAgICAgICBsZXQgaSQgPSB0aGlzLl9faW5zdGFuY2VzOwogICAgICAgICAgICAgIGZvciAobGV0IGk9MCwgaW5zdDsgKGk8aSQubGVuZ3RoKSAmJiAoaW5zdD1pJFtpXSk7IGkrKykgewogICAgICAgICAgICAgICAgaW5zdC5mb3J3YXJkSG9zdFByb3AocHJvcCwgdmFsdWUpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEB0aGlzIHtEb21SZXBlYXR9CiAgICAgICAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBpbnN0IEluc3RhbmNlIHRvIG5vdGlmeQogICAgICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBQcm9wZXJ0eSB0byBub3RpZnkKICAgICAgICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBWYWx1ZSB0byBub3RpZnkKICAgICAgICAgICAgICovCiAgICAgICAgICAgIG5vdGlmeUluc3RhbmNlUHJvcDogZnVuY3Rpb24oaW5zdCwgcHJvcCwgdmFsdWUpIHsKICAgICAgICAgICAgICBpZiAobWF0Y2hlcyh0aGlzLmFzLCBwcm9wKSkgewogICAgICAgICAgICAgICAgbGV0IGlkeCA9IGluc3RbdGhpcy5pdGVtc0luZGV4QXNdOwogICAgICAgICAgICAgICAgaWYgKHByb3AgPT0gdGhpcy5hcykgewogICAgICAgICAgICAgICAgICB0aGlzLml0ZW1zW2lkeF0gPSB2YWx1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGxldCBwYXRoID0gdHJhbnNsYXRlKHRoaXMuYXMsIGAke0pTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ2l0ZW1zJywgdGhpcyl9LiR7aWR4fWAsIHByb3ApOwogICAgICAgICAgICAgICAgdGhpcy5ub3RpZnlQYXRoKHBhdGgsIHZhbHVlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQoKICAgICAgX19nZXRNZXRob2RIb3N0KCkgewogICAgICAgIC8vIFRlY2huaWNhbGx5IHRoaXMgc2hvdWxkIGJlIHRoZSBvd25lciBvZiB0aGUgb3V0ZXJtb3N0IHRlbXBsYXRlLgogICAgICAgIC8vIEluIHNoYWRvdyBkb20sIHRoaXMgaXMgYWx3YXlzIGdldFJvb3ROb2RlKCkuaG9zdCwgYnV0IHdlIGNhbgogICAgICAgIC8vIGFwcHJveGltYXRlIHRoaXMgdmlhIGNvb3BlcmF0aW9uIHdpdGggb3VyIGRhdGFIb3N0IGFsd2F5cyBzZXR0aW5nCiAgICAgICAgLy8gYF9tZXRob2RIb3N0YCBhcyBsb25nIGFzIHRoZXJlIHdlcmUgYmluZGluZ3MgKG9yIGlkJ3MpIG9uIHRoaXMKICAgICAgICAvLyBpbnN0YW5jZSBjYXVzaW5nIGl0IHRvIGdldCBhIGRhdGFIb3N0LgogICAgICAgIHJldHVybiB0aGlzLl9fZGF0YUhvc3QuX21ldGhvZEhvc3QgfHwgdGhpcy5fX2RhdGFIb3N0OwogICAgICB9CgogICAgICBfX2Z1bmN0aW9uRnJvbVByb3BlcnR5VmFsdWUoZnVuY3Rpb25Pck1ldGhvZE5hbWUpIHsKICAgICAgICBpZiAodHlwZW9mIGZ1bmN0aW9uT3JNZXRob2ROYW1lID09PSAnc3RyaW5nJykgewogICAgICAgICAgbGV0IG1ldGhvZE5hbWUgPSBmdW5jdGlvbk9yTWV0aG9kTmFtZTsKICAgICAgICAgIGxldCBvYmogPSB0aGlzLl9fZ2V0TWV0aG9kSG9zdCgpOwogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgeyByZXR1cm4gb2JqW21ldGhvZE5hbWVdLmFwcGx5KG9iaiwgYXJndW1lbnRzKTsgfTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBmdW5jdGlvbk9yTWV0aG9kTmFtZTsKICAgICAgfQoKICAgICAgX19zb3J0Q2hhbmdlZChzb3J0KSB7CiAgICAgICAgdGhpcy5fX3NvcnRGbiA9IHRoaXMuX19mdW5jdGlvbkZyb21Qcm9wZXJ0eVZhbHVlKHNvcnQpOwogICAgICAgIGlmICh0aGlzLml0ZW1zKSB7IHRoaXMuX19kZWJvdW5jZVJlbmRlcih0aGlzLl9fcmVuZGVyKTsgfQogICAgICB9CgogICAgICBfX2ZpbHRlckNoYW5nZWQoZmlsdGVyKSB7CiAgICAgICAgdGhpcy5fX2ZpbHRlckZuID0gdGhpcy5fX2Z1bmN0aW9uRnJvbVByb3BlcnR5VmFsdWUoZmlsdGVyKTsKICAgICAgICBpZiAodGhpcy5pdGVtcykgeyB0aGlzLl9fZGVib3VuY2VSZW5kZXIodGhpcy5fX3JlbmRlcik7IH0KICAgICAgfQoKICAgICAgX19jb21wdXRlRnJhbWVUaW1lKHJhdGUpIHsKICAgICAgICByZXR1cm4gTWF0aC5jZWlsKDEwMDAvcmF0ZSk7CiAgICAgIH0KCiAgICAgIF9fb2JzZXJ2ZUNoYW5nZWQoKSB7CiAgICAgICAgdGhpcy5fX29ic2VydmVQYXRocyA9IHRoaXMub2JzZXJ2ZSAmJgogICAgICAgICAgdGhpcy5vYnNlcnZlLnJlcGxhY2UoJy4qJywgJy4nKS5zcGxpdCgnICcpOwogICAgICB9CgogICAgICBfX2hhbmRsZU9ic2VydmVkUGF0aHMocGF0aCkgewogICAgICAgIC8vIEhhbmRsZSBjYXNlcyB3aGVyZSBwYXRoIGNoYW5nZXMgc2hvdWxkIGNhdXNlIGEgcmUtc29ydC9maWx0ZXIKICAgICAgICBpZiAodGhpcy5fX3NvcnRGbiB8fCB0aGlzLl9fZmlsdGVyRm4pIHsKICAgICAgICAgIGlmICghcGF0aCkgewogICAgICAgICAgICAvLyBBbHdheXMgcmUtcmVuZGVyIGlmIHRoZSBpdGVtIGl0c2VsZiBjaGFuZ2VkCiAgICAgICAgICAgIHRoaXMuX19kZWJvdW5jZVJlbmRlcih0aGlzLl9fcmVuZGVyLCB0aGlzLmRlbGF5KTsKICAgICAgICAgIH0gZWxzZSBpZiAodGhpcy5fX29ic2VydmVQYXRocykgewogICAgICAgICAgICAvLyBPdGhlcndpc2UsIHJlLXJlbmRlciBpZiB0aGUgcGF0aCBjaGFuZ2VkIG1hdGNoZXMgYW4gb2JzZXJ2ZWQgcGF0aAogICAgICAgICAgICBsZXQgcGF0aHMgPSB0aGlzLl9fb2JzZXJ2ZVBhdGhzOwogICAgICAgICAgICBmb3IgKGxldCBpPTA7IGk8cGF0aHMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICBpZiAocGF0aC5pbmRleE9mKHBhdGhzW2ldKSA9PT0gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fX2RlYm91bmNlUmVuZGVyKHRoaXMuX19yZW5kZXIsIHRoaXMuZGVsYXkpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgX19pdGVtc0NoYW5nZWQoY2hhbmdlKSB7CiAgICAgICAgaWYgKHRoaXMuaXRlbXMgJiYgIUFycmF5LmlzQXJyYXkodGhpcy5pdGVtcykpIHsKICAgICAgICAgIGNvbnNvbGUud2FybignZG9tLXJlcGVhdCBleHBlY3RlZCBhcnJheSBmb3IgYGl0ZW1zYCwgZm91bmQnLCB0aGlzLml0ZW1zKTsKICAgICAgICB9CiAgICAgICAgLy8gSWYgcGF0aCB3YXMgdG8gYW4gaXRlbSAoZS5nLiAnaXRlbXMuMycgb3IgJ2l0ZW1zLjMuZm9vJyksIGZvcndhcmQgdGhlCiAgICAgICAgLy8gcGF0aCB0byB0aGF0IGluc3RhbmNlIHN5bmNocm9ub3VzbHkgKHJldHVybnMgZmFsc2UgZm9yIG5vbi1pdGVtIHBhdGhzKQogICAgICAgIGlmICghdGhpcy5fX2hhbmRsZUl0ZW1QYXRoKGNoYW5nZS5wYXRoLCBjaGFuZ2UudmFsdWUpKSB7CiAgICAgICAgICAvLyBPdGhlcndpc2UsIHRoZSBhcnJheSB3YXMgcmVzZXQgKCdpdGVtcycpIG9yIHNwbGljZWQgKCdpdGVtcy5zcGxpY2VzJyksCiAgICAgICAgICAvLyBzbyBxdWV1ZSBhIHJlbmRlci4gIFJlc3RhcnQgY2h1bmtpbmcgd2hlbiB0aGUgaXRlbXMgY2hhbmdlZCAoZm9yCiAgICAgICAgICAvLyBiYWNrd2FyZCBjb21wYXRpYmlsaXR5KSwgdW5sZXNzIGByZXVzZUNodW5rZWRJbnN0YW5jZXNgIG9wdGlvbiBpcyBzZXQKICAgICAgICAgIGlmIChjaGFuZ2UucGF0aCA9PT0gJ2l0ZW1zJykgewogICAgICAgICAgICB0aGlzLl9faXRlbXNBcnJheUNoYW5nZWQgPSB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fX2RlYm91bmNlUmVuZGVyKHRoaXMuX19yZW5kZXIpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7ZnVuY3Rpb24odGhpczpEb21SZXBlYXQpfSBmbiBGdW5jdGlvbiB0byBkZWJvdW5jZS4KICAgICAgICogQHBhcmFtIHtudW1iZXI9fSBkZWxheSBEZWxheSBpbiBtcyB0byBkZWJvdW5jZSBieS4KICAgICAgICovCiAgICAgIF9fZGVib3VuY2VSZW5kZXIoZm4sIGRlbGF5ID0gMCkgewogICAgICAgIHRoaXMuX19yZW5kZXJEZWJvdW5jZXIgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgICAgdGhpcy5fX3JlbmRlckRlYm91bmNlcgogICAgICAgICAgICAsIGRlbGF5ID4gMCA/IHRpbWVPdXQuYWZ0ZXIoZGVsYXkpIDogbWljcm9UYXNrCiAgICAgICAgICAgICwgZm4uYmluZCh0aGlzKSk7CiAgICAgICAgZW5xdWV1ZURlYm91bmNlcih0aGlzLl9fcmVuZGVyRGVib3VuY2VyKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEZvcmNlcyB0aGUgZWxlbWVudCB0byByZW5kZXIgaXRzIGNvbnRlbnQuIE5vcm1hbGx5IHJlbmRlcmluZyBpcwogICAgICAgKiBhc3luY2hyb25vdXMgdG8gYSBwcm92b2tpbmcgY2hhbmdlLiBUaGlzIGlzIGRvbmUgZm9yIGVmZmljaWVuY3kgc28KICAgICAgICogdGhhdCBtdWx0aXBsZSBjaGFuZ2VzIHRyaWdnZXIgb25seSBhIHNpbmdsZSByZW5kZXIuIFRoZSByZW5kZXIgbWV0aG9kCiAgICAgICAqIHNob3VsZCBiZSBjYWxsZWQgaWYsIGZvciBleGFtcGxlLCB0ZW1wbGF0ZSByZW5kZXJpbmcgaXMgcmVxdWlyZWQgdG8KICAgICAgICogdmFsaWRhdGUgYXBwbGljYXRpb24gc3RhdGUuCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICByZW5kZXIoKSB7CiAgICAgICAgLy8gUXVldWUgdGhpcyByZXBlYXRlciwgdGhlbiBmbHVzaCBhbGwgaW4gb3JkZXIKICAgICAgICB0aGlzLl9fZGVib3VuY2VSZW5kZXIodGhpcy5fX3JlbmRlcik7CiAgICAgICAgZmx1c2goKTsKICAgICAgfQoKICAgICAgX19yZW5kZXIoKSB7CiAgICAgICAgaWYgKCF0aGlzLl9fZW5zdXJlVGVtcGxhdGl6ZWQoKSkgewogICAgICAgICAgLy8gTm8gdGVtcGxhdGUgZm91bmQgeWV0CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGxldCBpdGVtcyA9IHRoaXMuaXRlbXMgfHwgW107CiAgICAgICAgLy8gU29ydCBhbmQgZmlsdGVyIHRoZSBpdGVtcyBpbnRvIGEgbWFwcGluZyBhcnJheSBmcm9tIGluc3RhbmNlLT5pdGVtCiAgICAgICAgY29uc3QgaXNudElkeFRvSXRlbXNJZHggPSB0aGlzLl9fc29ydEFuZEZpbHRlckl0ZW1zKGl0ZW1zKTsKICAgICAgICAvLyBJZiB3ZSdyZSBjaHVua2luZywgaW5jcmVhc2UgdGhlIGxpbWl0IGlmIHRoZXJlIGFyZSBuZXcgaW5zdGFuY2VzIHRvCiAgICAgICAgLy8gY3JlYXRlIGFuZCBzY2hlZHVsZSB0aGUgbmV4dCBjaHVuawogICAgICAgIGNvbnN0IGxpbWl0ID0gdGhpcy5fX2NhbGN1bGF0ZUxpbWl0KGlzbnRJZHhUb0l0ZW1zSWR4Lmxlbmd0aCk7CiAgICAgICAgLy8gQ3JlYXRlLCB1cGRhdGUsIGFuZC9vciByZW1vdmUgaW5zdGFuY2VzCiAgICAgICAgdGhpcy5fX3VwZGF0ZUluc3RhbmNlcyhpdGVtcywgbGltaXQsIGlzbnRJZHhUb0l0ZW1zSWR4KTsKICAgICAgICAvLyBJZiB3ZSdyZSBjaHVua2luZywgc2NoZWR1bGUgYSByQUYgdGFzayB0byBtZWFzdXJlL2NvbnRpbnVlIGNodW5raW5nLiAgICAgCiAgICAgICAgLy8gRG8gdGhpcyBiZWZvcmUgYW55IG5vdGlmeWluZyBldmVudHMgKHJlbmRlcmVkSXRlbUNvdW50ICYgZG9tLWNoYW5nZSkKICAgICAgICAvLyBzaW5jZSB0aG9zZSBjb3VsZCBtb2RpZnkgaXRlbXMgYW5kIGVucXVldWUgYSBuZXcgZnVsbCByZW5kZXIgd2hpY2ggd2lsbAogICAgICAgIC8vIHByZS1lbXB0IHRoaXMgbWVhc3VyZW1lbnQuCiAgICAgICAgaWYgKHRoaXMuaW5pdGlhbENvdW50ICYmCiAgICAgICAgICAgKHRoaXMuX19zaG91bGRNZWFzdXJlQ2h1bmsgfHwgdGhpcy5fX3Nob3VsZENvbnRpbnVlQ2h1bmtpbmcpKSB7CiAgICAgICAgICBjYW5jZWxBbmltYXRpb25GcmFtZSh0aGlzLl9fY2h1bmtpbmdJZCk7CiAgICAgICAgICB0aGlzLl9fY2h1bmtpbmdJZCA9IHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB0aGlzLl9fY29udGludWVDaHVua2luZygpKTsKICAgICAgICB9CiAgICAgICAgLy8gU2V0IHJlbmRlcmVkIGl0ZW0gY291bnQKICAgICAgICB0aGlzLl9zZXRSZW5kZXJlZEl0ZW1Db3VudCh0aGlzLl9faW5zdGFuY2VzLmxlbmd0aCk7CiAgICAgICAgLy8gTm90aWZ5IHVzZXJzCiAgICAgICAgaWYgKCFzdXBwcmVzc1RlbXBsYXRlTm90aWZpY2F0aW9ucyB8fCB0aGlzLm5vdGlmeURvbUNoYW5nZSkgewogICAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnZG9tLWNoYW5nZScsIHsKICAgICAgICAgICAgYnViYmxlczogdHJ1ZSwKICAgICAgICAgICAgY29tcG9zZWQ6IHRydWUKICAgICAgICAgIH0pKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9fc29ydEFuZEZpbHRlckl0ZW1zKGl0ZW1zKSB7CiAgICAgICAgLy8gR2VuZXJhdGUgYXJyYXkgbWFwaW5nIHRoZSBpbnN0YW5jZSBpbmRleCB0byB0aGUgaXRlbXMgYXJyYXkgaW5kZXgKICAgICAgICBsZXQgaXNudElkeFRvSXRlbXNJZHggPSBuZXcgQXJyYXkoaXRlbXMubGVuZ3RoKTsKICAgICAgICBmb3IgKGxldCBpPTA7IGk8aXRlbXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGlzbnRJZHhUb0l0ZW1zSWR4W2ldID0gaTsKICAgICAgICB9CiAgICAgICAgLy8gQXBwbHkgdXNlciBmaWx0ZXIKICAgICAgICBpZiAodGhpcy5fX2ZpbHRlckZuKSB7CiAgICAgICAgICBpc250SWR4VG9JdGVtc0lkeCA9IGlzbnRJZHhUb0l0ZW1zSWR4LmZpbHRlcigoaSwgaWR4LCBhcnJheSkgPT4KICAgICAgICAgICAgdGhpcy5fX2ZpbHRlckZuKGl0ZW1zW2ldLCBpZHgsIGFycmF5KSk7CiAgICAgICAgfQogICAgICAgIC8vIEFwcGx5IHVzZXIgc29ydAogICAgICAgIGlmICh0aGlzLl9fc29ydEZuKSB7CiAgICAgICAgICBpc250SWR4VG9JdGVtc0lkeC5zb3J0KChhLCBiKSA9PiB0aGlzLl9fc29ydEZuKGl0ZW1zW2FdLCBpdGVtc1tiXSkpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gaXNudElkeFRvSXRlbXNJZHg7CiAgICAgIH0KCiAgICAgIF9fY2FsY3VsYXRlTGltaXQoZmlsdGVyZWRJdGVtQ291bnQpIHsKICAgICAgICBsZXQgbGltaXQgPSBmaWx0ZXJlZEl0ZW1Db3VudDsKICAgICAgICBjb25zdCBjdXJyZW50Q291bnQgPSB0aGlzLl9faW5zdGFuY2VzLmxlbmd0aDsKICAgICAgICAvLyBXaGVuIGNodW5raW5nLCB3ZSBpbmNyZWFzZSB0aGUgbGltaXQgZnJvbSB0aGUgY3VycmVudGx5IHJlbmRlcmVkIGNvdW50CiAgICAgICAgLy8gYnkgdGhlIGNodW5rIGNvdW50IHRoYXQgaXMgcmUtY2FsY3VsYXRlZCBhZnRlciBlYWNoIHJBRiAod2l0aCBzcGVjaWFsCiAgICAgICAgLy8gY2FzZXMgZm9yIHJlc2V0aW5nIHRoZSBsaW1pdCB0byBpbml0aWFsQ291bnQgYWZ0ZXIgY2hhbmdpbmcgaXRlbXMpCiAgICAgICAgaWYgKHRoaXMuaW5pdGlhbENvdW50KSB7CiAgICAgICAgICBsZXQgbmV3Q291bnQ7CiAgICAgICAgICBpZiAoIXRoaXMuX19jaHVua0NvdW50IHx8CiAgICAgICAgICAgICh0aGlzLl9faXRlbXNBcnJheUNoYW5nZWQgJiYgIXRoaXMucmV1c2VDaHVua2VkSW5zdGFuY2VzKSkgewogICAgICAgICAgICAvLyBMaW1pdCBuZXh0IHJlbmRlciB0byB0aGUgaW5pdGlhbCBjb3VudAogICAgICAgICAgICBsaW1pdCA9IE1hdGgubWluKGZpbHRlcmVkSXRlbUNvdW50LCB0aGlzLmluaXRpYWxDb3VudCk7CiAgICAgICAgICAgIC8vIFN1YnRyYWN0IG9mZiBhbnkgZXhpc3RpbmcgaW5zdGFuY2VzIHRvIGRldGVybWluZSB0aGUgbnVtYmVyIG9mCiAgICAgICAgICAgIC8vIGluc3RhbmNlcyB0aGF0IHdpbGwgYmUgY3JlYXRlZAogICAgICAgICAgICBuZXdDb3VudCA9IE1hdGgubWF4KGxpbWl0IC0gY3VycmVudENvdW50LCAwKTsKICAgICAgICAgICAgLy8gSW5pdGlhbGl6ZSB0aGUgY2h1bmsgc2l6ZSB3aXRoIGhvdyBtYW55IGl0ZW1zIHdlJ3JlIGNyZWF0aW5nCiAgICAgICAgICAgIHRoaXMuX19jaHVua0NvdW50ID0gbmV3Q291bnQgfHwgMTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIFRoZSBudW1iZXIgb2YgbmV3IGluc3RhbmNlcyB0aGF0IHdpbGwgYmUgY3JlYXRlZCBpcyBiYXNlZCBvbiB0aGUKICAgICAgICAgICAgLy8gZXhpc3RpbmcgaW5zdGFuY2VzLCB0aGUgbmV3IGxpc3Qgc2l6ZSwgYW5kIHRoZSBjaHVuayBzaXplCiAgICAgICAgICAgIG5ld0NvdW50ID0gTWF0aC5taW4oCiAgICAgICAgICAgICAgTWF0aC5tYXgoZmlsdGVyZWRJdGVtQ291bnQgLSBjdXJyZW50Q291bnQsIDApLCAKICAgICAgICAgICAgICB0aGlzLl9fY2h1bmtDb3VudCk7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgbGltaXQgYmFzZWQgb24gaG93IG1hbnkgbmV3IGl0ZW1zIHdlJ3JlIG1ha2luZywgbGltaXRlZAogICAgICAgICAgICAvLyBidXkgdGhlIHRvdGFsIHNpemUgb2YgdGhlIGxpc3QKICAgICAgICAgICAgbGltaXQgPSBNYXRoLm1pbihjdXJyZW50Q291bnQgKyBuZXdDb3VudCwgZmlsdGVyZWRJdGVtQ291bnQpOwogICAgICAgICAgfQogICAgICAgICAgLy8gUmVjb3JkIHNvbWUgc3RhdGUgYWJvdXQgY2h1bmtpbmcgZm9yIHVzZSBpbiBgX19jb250aW51ZUNodW5raW5nYAogICAgICAgICAgdGhpcy5fX3Nob3VsZE1lYXN1cmVDaHVuayA9IG5ld0NvdW50ID09PSB0aGlzLl9fY2h1bmtDb3VudDsKICAgICAgICAgIHRoaXMuX19zaG91bGRDb250aW51ZUNodW5raW5nID0gbGltaXQgPCBmaWx0ZXJlZEl0ZW1Db3VudDsKICAgICAgICAgIHRoaXMuX19yZW5kZXJTdGFydFRpbWUgPSBwZXJmb3JtYW5jZS5ub3coKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fX2l0ZW1zQXJyYXlDaGFuZ2VkID0gZmFsc2U7CiAgICAgICAgcmV0dXJuIGxpbWl0OwogICAgICB9CgogICAgICBfX2NvbnRpbnVlQ2h1bmtpbmcoKSB7CiAgICAgICAgLy8gU2ltcGxlIGF1dG8gY2h1bmtTaXplIHRocm90dGxpbmcgYWxnb3JpdGhtIGJhc2VkIG9uIGZlZWRiYWNrIGxvb3A6CiAgICAgICAgLy8gbWVhc3VyZSBhY3R1YWwgdGltZSBiZXR3ZWVuIGZyYW1lcyBhbmQgc2NhbGUgY2h1bmsgY291bnQgYnkgcmF0aW8gb2YKICAgICAgICAvLyB0YXJnZXQvYWN0dWFsIGZyYW1lIHRpbWUuICBPbmx5IG1vZGlmeSBjaHVuayBzaXplIGlmIG91ciBtZWFzdXJlbWVudAogICAgICAgIC8vIHJlZmxlY3RzIHRoZSBjb3N0IG9mIGEgY3JlYXRpbmcgYSBmdWxsIGNodW5rJ3Mgd29ydGggb2YgaW5zdGFuY2VzOyB0aGlzCiAgICAgICAgLy8gYXZvaWRzIHNjYWxpbmcgdXAgdGhlIGNodW5rIHNpemUgaWYgd2UgZS5nLiBxdWlja2x5IHJlLXJlbmRlcmVkIGluc3RhbmNlcwogICAgICAgIC8vIGluIHBsYWNlCiAgICAgICAgaWYgKHRoaXMuX19zaG91bGRNZWFzdXJlQ2h1bmspIHsKICAgICAgICAgIGNvbnN0IHJlbmRlclRpbWUgPSBwZXJmb3JtYW5jZS5ub3coKSAtIHRoaXMuX19yZW5kZXJTdGFydFRpbWU7CiAgICAgICAgICBjb25zdCByYXRpbyA9IHRoaXMuX3RhcmdldEZyYW1lVGltZSAvIHJlbmRlclRpbWU7CiAgICAgICAgICB0aGlzLl9fY2h1bmtDb3VudCA9IE1hdGgucm91bmQodGhpcy5fX2NodW5rQ291bnQgKiByYXRpbykgfHwgMTsKICAgICAgICB9CiAgICAgICAgLy8gRW5xdWV1ZSBhIG5ldyByZW5kZXIgaWYgd2UgaGF2ZW4ndCByZWFjaGVkIHRoZSBmdWxsIHNpemUgb2YgdGhlIGxpc3QKICAgICAgICBpZiAodGhpcy5fX3Nob3VsZENvbnRpbnVlQ2h1bmtpbmcpIHsKICAgICAgICAgIHRoaXMuX19kZWJvdW5jZVJlbmRlcih0aGlzLl9fcmVuZGVyKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgCiAgICAgIF9fdXBkYXRlSW5zdGFuY2VzKGl0ZW1zLCBsaW1pdCwgaXNudElkeFRvSXRlbXNJZHgpIHsKICAgICAgICAvLyBpdGVtcy0+aW5zdCBtYXAga2VwdCBmb3IgaXRlbSBwYXRoIGZvcndhcmRpbmcKICAgICAgICBjb25zdCBpdGVtc0lkeFRvSW5zdElkeCA9IHRoaXMuX19pdGVtc0lkeFRvSW5zdElkeCA9IHt9OwogICAgICAgIGxldCBpbnN0SWR4OwogICAgICAgIC8vIEdlbmVyYXRlIGluc3RhbmNlcyBhbmQgYXNzaWduIGl0ZW1zCiAgICAgICAgZm9yIChpbnN0SWR4PTA7IGluc3RJZHg8bGltaXQ7IGluc3RJZHgrKykgewogICAgICAgICAgbGV0IGluc3QgPSB0aGlzLl9faW5zdGFuY2VzW2luc3RJZHhdOwogICAgICAgICAgbGV0IGl0ZW1JZHggPSBpc250SWR4VG9JdGVtc0lkeFtpbnN0SWR4XTsKICAgICAgICAgIGxldCBpdGVtID0gaXRlbXNbaXRlbUlkeF07CiAgICAgICAgICBpdGVtc0lkeFRvSW5zdElkeFtpdGVtSWR4XSA9IGluc3RJZHg7CiAgICAgICAgICBpZiAoaW5zdCkgewogICAgICAgICAgICBpbnN0Ll9zZXRQZW5kaW5nUHJvcGVydHkodGhpcy5hcywgaXRlbSk7CiAgICAgICAgICAgIGluc3QuX3NldFBlbmRpbmdQcm9wZXJ0eSh0aGlzLmluZGV4QXMsIGluc3RJZHgpOwogICAgICAgICAgICBpbnN0Ll9zZXRQZW5kaW5nUHJvcGVydHkodGhpcy5pdGVtc0luZGV4QXMsIGl0ZW1JZHgpOwogICAgICAgICAgICBpbnN0Ll9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRoaXMuX19pbnNlcnRJbnN0YW5jZShpdGVtLCBpbnN0SWR4LCBpdGVtSWR4KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gUmVtb3ZlIGFueSBleHRyYSBpbnN0YW5jZXMgZnJvbSBwcmV2aW91cyBzdGF0ZQogICAgICAgIGZvciAobGV0IGk9dGhpcy5fX2luc3RhbmNlcy5sZW5ndGgtMTsgaT49aW5zdElkeDsgaS0tKSB7CiAgICAgICAgICB0aGlzLl9fZGV0YWNoQW5kUmVtb3ZlSW5zdGFuY2UoaSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfX2RldGFjaEluc3RhbmNlKGlkeCkgewogICAgICAgIGxldCBpbnN0ID0gdGhpcy5fX2luc3RhbmNlc1tpZHhdOwogICAgICAgIGNvbnN0IHdyYXBwZWRSb290ID0gd3JhcChpbnN0LnJvb3QpOwogICAgICAgIGZvciAobGV0IGk9MDsgaTxpbnN0LmNoaWxkcmVuLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBsZXQgZWwgPSBpbnN0LmNoaWxkcmVuW2ldOwogICAgICAgICAgd3JhcHBlZFJvb3QuYXBwZW5kQ2hpbGQoZWwpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gaW5zdDsKICAgICAgfQoKICAgICAgX19hdHRhY2hJbnN0YW5jZShpZHgsIHBhcmVudCkgewogICAgICAgIGxldCBpbnN0ID0gdGhpcy5fX2luc3RhbmNlc1tpZHhdOwogICAgICAgIC8vIE5vdGUsIHRoaXMgaXMgcHJlLXdyYXBwZWQgYXMgYW4gb3B0aW1pemF0aW9uCiAgICAgICAgcGFyZW50Lmluc2VydEJlZm9yZShpbnN0LnJvb3QsIHRoaXMpOwogICAgICB9CgogICAgICBfX2RldGFjaEFuZFJlbW92ZUluc3RhbmNlKGlkeCkgewogICAgICAgIHRoaXMuX19kZXRhY2hJbnN0YW5jZShpZHgpOwogICAgICAgIHRoaXMuX19pbnN0YW5jZXMuc3BsaWNlKGlkeCwgMSk7CiAgICAgIH0KCiAgICAgIF9fc3RhbXBJbnN0YW5jZShpdGVtLCBpbnN0SWR4LCBpdGVtSWR4KSB7CiAgICAgICAgbGV0IG1vZGVsID0ge307CiAgICAgICAgbW9kZWxbdGhpcy5hc10gPSBpdGVtOwogICAgICAgIG1vZGVsW3RoaXMuaW5kZXhBc10gPSBpbnN0SWR4OwogICAgICAgIG1vZGVsW3RoaXMuaXRlbXNJbmRleEFzXSA9IGl0ZW1JZHg7CiAgICAgICAgcmV0dXJuIG5ldyB0aGlzLl9fY3Rvcihtb2RlbCk7CiAgICAgIH0KCiAgICAgIF9faW5zZXJ0SW5zdGFuY2UoaXRlbSwgaW5zdElkeCwgaXRlbUlkeCkgewogICAgICAgIGNvbnN0IGluc3QgPSB0aGlzLl9fc3RhbXBJbnN0YW5jZShpdGVtLCBpbnN0SWR4LCBpdGVtSWR4KTsKICAgICAgICBsZXQgYmVmb3JlUm93ID0gdGhpcy5fX2luc3RhbmNlc1tpbnN0SWR4ICsgMV07CiAgICAgICAgbGV0IGJlZm9yZU5vZGUgPSBiZWZvcmVSb3cgPyBiZWZvcmVSb3cuY2hpbGRyZW5bMF0gOiB0aGlzOwogICAgICAgIHdyYXAod3JhcCh0aGlzKS5wYXJlbnROb2RlKS5pbnNlcnRCZWZvcmUoaW5zdC5yb290LCBiZWZvcmVOb2RlKTsKICAgICAgICB0aGlzLl9faW5zdGFuY2VzW2luc3RJZHhdID0gaW5zdDsKICAgICAgICByZXR1cm4gaW5zdDsKICAgICAgfQoKICAgICAgLy8gSW1wbGVtZW50cyBleHRlbnNpb24gcG9pbnQgZnJvbSBUZW1wbGF0aXplIG1peGluCiAgICAgIC8qKgogICAgICAgKiBTaG93cyBvciBoaWRlcyB0aGUgdGVtcGxhdGUgaW5zdGFuY2UgdG9wIGxldmVsIGNoaWxkIGVsZW1lbnRzLiBGb3IKICAgICAgICogdGV4dCBub2RlcywgYHRleHRDb250ZW50YCBpcyByZW1vdmVkIHdoaWxlICJoaWRkZW4iIGFuZCByZXBsYWNlZCB3aGVuCiAgICAgICAqICJzaG93bi4iCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaGlkZGVuIFNldCB0byB0cnVlIHRvIGhpZGUgdGhlIGNoaWxkcmVuOwogICAgICAgKiBzZXQgdG8gZmFsc2UgdG8gc2hvdyB0aGVtLgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfc2hvd0hpZGVDaGlsZHJlbihoaWRkZW4pIHsKICAgICAgICBmb3IgKGxldCBpPTA7IGk8dGhpcy5fX2luc3RhbmNlcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgdGhpcy5fX2luc3RhbmNlc1tpXS5fc2hvd0hpZGVDaGlsZHJlbihoaWRkZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gQ2FsbGVkIGFzIGEgc2lkZSBlZmZlY3Qgb2YgYSBob3N0IGl0ZW1zLjxrZXk+LjxwYXRoPiBwYXRoIGNoYW5nZSwKICAgICAgLy8gcmVzcG9uc2libGUgZm9yIG5vdGlmeWluZyBpdGVtLjxwYXRoPiBjaGFuZ2VzIHRvIGluc3QgZm9yIGtleQogICAgICBfX2hhbmRsZUl0ZW1QYXRoKHBhdGgsIHZhbHVlKSB7CiAgICAgICAgbGV0IGl0ZW1zUGF0aCA9IHBhdGguc2xpY2UoNik7IC8vICdpdGVtcy4nLmxlbmd0aCA9PSA2CiAgICAgICAgbGV0IGRvdCA9IGl0ZW1zUGF0aC5pbmRleE9mKCcuJyk7CiAgICAgICAgbGV0IGl0ZW1zSWR4ID0gZG90IDwgMCA/IGl0ZW1zUGF0aCA6IGl0ZW1zUGF0aC5zdWJzdHJpbmcoMCwgZG90KTsKICAgICAgICAvLyBJZiBwYXRoIHdhcyBpbmRleCBpbnRvIGFycmF5Li4uCiAgICAgICAgaWYgKGl0ZW1zSWR4ID09IHBhcnNlSW50KGl0ZW1zSWR4LCAxMCkpIHsKICAgICAgICAgIGxldCBpdGVtU3ViUGF0aCA9IGRvdCA8IDAgPyAnJyA6IGl0ZW1zUGF0aC5zdWJzdHJpbmcoZG90KzEpOwogICAgICAgICAgLy8gSWYgdGhlIHBhdGggaXMgb2JzZXJ2ZWQsIGl0IHdpbGwgdHJpZ2dlciBhIGZ1bGwgcmVmcmVzaAogICAgICAgICAgdGhpcy5fX2hhbmRsZU9ic2VydmVkUGF0aHMoaXRlbVN1YlBhdGgpOwogICAgICAgICAgLy8gTm90ZSwgZXZlbiBpZiBhIHJ1bGwgcmVmcmVzaCBpcyB0cmlnZ2VyZWQsIGFsd2F5cyBkbyB0aGUgcGF0aAogICAgICAgICAgLy8gbm90aWZpY2F0aW9uIGJlY2F1c2UgdW5sZXNzIG11dGFibGVEYXRhIGlzIHVzZWQgZm9yIGRvbS1yZXBlYXQKICAgICAgICAgIC8vIGFuZCBhbGwgZWxlbWVudHMgaW4gdGhlIGluc3RhbmNlIHN1YnRyZWUsIGEgZnVsbCByZWZyZXNoIG1heQogICAgICAgICAgLy8gbm90IHRyaWdnZXIgdGhlIHByb3BlciB1cGRhdGUuCiAgICAgICAgICBsZXQgaW5zdElkeCA9IHRoaXMuX19pdGVtc0lkeFRvSW5zdElkeFtpdGVtc0lkeF07CiAgICAgICAgICBsZXQgaW5zdCA9IHRoaXMuX19pbnN0YW5jZXNbaW5zdElkeF07CiAgICAgICAgICBpZiAoaW5zdCkgewogICAgICAgICAgICBsZXQgaXRlbVBhdGggPSB0aGlzLmFzICsgKGl0ZW1TdWJQYXRoID8gJy4nICsgaXRlbVN1YlBhdGggOiAnJyk7CiAgICAgICAgICAgIC8vIFRoaXMgaXMgZWZmZWN0aXZlbHkgYG5vdGlmeVBhdGhgLCBidXQgYXZvaWRzIHNvbWUgb2YgdGhlIG92ZXJoZWFkCiAgICAgICAgICAgIC8vIG9mIHRoZSBwdWJsaWMgQVBJCiAgICAgICAgICAgIGluc3QuX3NldFBlbmRpbmdQcm9wZXJ0eU9yUGF0aChpdGVtUGF0aCwgdmFsdWUsIGZhbHNlLCB0cnVlKTsKICAgICAgICAgICAgaW5zdC5fZmx1c2hQcm9wZXJ0aWVzKCk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBpdGVtIGFzc29jaWF0ZWQgd2l0aCBhIGdpdmVuIGVsZW1lbnQgc3RhbXBlZCBieQogICAgICAgKiB0aGlzIGBkb20tcmVwZWF0YC4KICAgICAgICoKICAgICAgICogTm90ZSwgdG8gbW9kaWZ5IHN1Yi1wcm9wZXJ0aWVzIG9mIHRoZSBpdGVtLAogICAgICAgKiBgbW9kZWxGb3JFbGVtZW50KGVsKS5zZXQoJ2l0ZW0uPHN1Yi1wcm9wPicsIHZhbHVlKWAKICAgICAgICogc2hvdWxkIGJlIHVzZWQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSBlbCBFbGVtZW50IGZvciB3aGljaCB0byByZXR1cm4gdGhlIGl0ZW0uCiAgICAgICAqIEByZXR1cm4geyp9IEl0ZW0gYXNzb2NpYXRlZCB3aXRoIHRoZSBlbGVtZW50LgogICAgICAgKi8KICAgICAgaXRlbUZvckVsZW1lbnQoZWwpIHsKICAgICAgICBsZXQgaW5zdGFuY2UgPSB0aGlzLm1vZGVsRm9yRWxlbWVudChlbCk7CiAgICAgICAgcmV0dXJuIGluc3RhbmNlICYmIGluc3RhbmNlW3RoaXMuYXNdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgaW5zdCBpbmRleCBmb3IgYSBnaXZlbiBlbGVtZW50IHN0YW1wZWQgYnkgdGhpcyBgZG9tLXJlcGVhdGAuCiAgICAgICAqIElmIGBzb3J0YCBpcyBwcm92aWRlZCwgdGhlIGluZGV4IHdpbGwgcmVmbGVjdCB0aGUgc29ydGVkIG9yZGVyIChyYXRoZXIKICAgICAgICogdGhhbiB0aGUgb3JpZ2luYWwgYXJyYXkgb3JkZXIpLgogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWwgRWxlbWVudCBmb3Igd2hpY2ggdG8gcmV0dXJuIHRoZSBpbmRleC4KICAgICAgICogQHJldHVybiB7P251bWJlcn0gUm93IGluZGV4IGFzc29jaWF0ZWQgd2l0aCB0aGUgZWxlbWVudCAobm90ZSB0aGlzIG1heQogICAgICAgKiAgIG5vdCBjb3JyZXNwb25kIHRvIHRoZSBhcnJheSBpbmRleCBpZiBhIHVzZXIgYHNvcnRgIGlzIGFwcGxpZWQpLgogICAgICAgKi8KICAgICAgaW5kZXhGb3JFbGVtZW50KGVsKSB7CiAgICAgICAgbGV0IGluc3RhbmNlID0gdGhpcy5tb2RlbEZvckVsZW1lbnQoZWwpOwogICAgICAgIHJldHVybiBpbnN0YW5jZSAmJiBpbnN0YW5jZVt0aGlzLmluZGV4QXNdOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgdGVtcGxhdGUgIm1vZGVsIiBhc3NvY2lhdGVkIHdpdGggYSBnaXZlbiBlbGVtZW50LCB3aGljaAogICAgICAgKiBzZXJ2ZXMgYXMgdGhlIGJpbmRpbmcgc2NvcGUgZm9yIHRoZSB0ZW1wbGF0ZSBpbnN0YW5jZSB0aGUgZWxlbWVudCBpcwogICAgICAgKiBjb250YWluZWQgaW4uIEEgdGVtcGxhdGUgbW9kZWwKICAgICAgICogc2hvdWxkIGJlIHVzZWQgdG8gbWFuaXB1bGF0ZSBkYXRhIGFzc29jaWF0ZWQgd2l0aCB0aGlzIHRlbXBsYXRlIGluc3RhbmNlLgogICAgICAgKgogICAgICAgKiBFeGFtcGxlOgogICAgICAgKgogICAgICAgKiAgIGxldCBtb2RlbCA9IG1vZGVsRm9yRWxlbWVudChlbCk7CiAgICAgICAqICAgaWYgKG1vZGVsLmluZGV4IDwgMTApIHsKICAgICAgICogICAgIG1vZGVsLnNldCgnaXRlbS5jaGVja2VkJywgdHJ1ZSk7CiAgICAgICAqICAgfQogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWwgRWxlbWVudCBmb3Igd2hpY2ggdG8gcmV0dXJuIGEgdGVtcGxhdGUgbW9kZWwuCiAgICAgICAqIEByZXR1cm4ge1RlbXBsYXRlSW5zdGFuY2VCYXNlfSBNb2RlbCByZXByZXNlbnRpbmcgdGhlIGJpbmRpbmcgc2NvcGUgZm9yCiAgICAgICAqICAgdGhlIGVsZW1lbnQuCiAgICAgICAqLwogICAgICBtb2RlbEZvckVsZW1lbnQoZWwpIHsKICAgICAgICByZXR1cm4gbW9kZWxGb3JFbGVtZW50KHRoaXMudGVtcGxhdGUsIGVsKTsKICAgICAgfQoKICAgIH0KCiAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoRG9tUmVwZWF0LmlzLCBEb21SZXBlYXQpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAY3VzdG9tRWxlbWVudAogICAgICogQHBvbHltZXIKICAgICAqIEBleHRlbmRzIFBvbHltZXJFbGVtZW50CiAgICAgKiBAc3VtbWFyeSBCYXNlIGNsYXNzIGZvciBkb20taWYgZWxlbWVudDsgc3ViY2xhc3NlZCBpbnRvIGNvbmNyZXRlCiAgICAgKiAgIGltcGxlbWVudGF0aW9uLgogICAgICovCiAgICBjbGFzcyBEb21JZkJhc2UgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CgogICAgICAvLyBOb3QgbmVlZGVkIHRvIGZpbmQgdGVtcGxhdGU7IGNhbiBiZSByZW1vdmVkIG9uY2UgdGhlIGFuYWx5emVyCiAgICAgIC8vIGNhbiBmaW5kIHRoZSB0YWcgbmFtZSBmcm9tIGN1c3RvbUVsZW1lbnRzLmRlZmluZSBjYWxsCiAgICAgIHN0YXRpYyBnZXQgaXMoKSB7IHJldHVybiAnZG9tLWlmJzsgfQoKICAgICAgc3RhdGljIGdldCB0ZW1wbGF0ZSgpIHsgcmV0dXJuIG51bGw7IH0KCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKCiAgICAgICAgcmV0dXJuIHsKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEZpcmVkIHdoZW5ldmVyIERPTSBpcyBhZGRlZCBvciByZW1vdmVkL2hpZGRlbiBieSB0aGlzIHRlbXBsYXRlIChieQogICAgICAgICAgICogZGVmYXVsdCwgcmVuZGVyaW5nIG9jY3VycyBsYXppbHkpLiAgVG8gZm9yY2UgaW1tZWRpYXRlIHJlbmRlcmluZywgY2FsbAogICAgICAgICAgICogYHJlbmRlcmAuCiAgICAgICAgICAgKgogICAgICAgICAgICogQGV2ZW50IGRvbS1jaGFuZ2UKICAgICAgICAgICAqLwoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQSBib29sZWFuIGluZGljYXRpbmcgd2hldGhlciB0aGlzIHRlbXBsYXRlIHNob3VsZCBzdGFtcC4KICAgICAgICAgICAqLwogICAgICAgICAgaWY6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfX2RlYm91bmNlUmVuZGVyJwogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFdoZW4gdHJ1ZSwgZWxlbWVudHMgd2lsbCBiZSByZW1vdmVkIGZyb20gRE9NIGFuZCBkaXNjYXJkZWQgd2hlbiBgaWZgCiAgICAgICAgICAgKiBiZWNvbWVzIGZhbHNlIGFuZCByZS1jcmVhdGVkIGFuZCBhZGRlZCBiYWNrIHRvIHRoZSBET00gd2hlbiBgaWZgCiAgICAgICAgICAgKiBiZWNvbWVzIHRydWUuICBCeSBkZWZhdWx0LCBzdGFtcGVkIGVsZW1lbnRzIHdpbGwgYmUgaGlkZGVuIGJ1dCBsZWZ0CiAgICAgICAgICAgKiBpbiB0aGUgRE9NIHdoZW4gYGlmYCBiZWNvbWVzIGZhbHNlLCB3aGljaCBpcyBnZW5lcmFsbHkgcmVzdWx0cwogICAgICAgICAgICogaW4gYmV0dGVyIHBlcmZvcm1hbmNlLgogICAgICAgICAgICovCiAgICAgICAgICByZXN0YW1wOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG9ic2VydmVyOiAnX19kZWJvdW5jZVJlbmRlcicKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIHRoZSBnbG9iYWwgYHN1cHByZXNzVGVtcGxhdGVOb3RpZmljYXRpb25zYCBzZXR0aW5nIGlzIHVzZWQsIHNldHRpbmcKICAgICAgICAgICAqIGBub3RpZnlEb21DaGFuZ2U6IHRydWVgIHdpbGwgZW5hYmxlIGZpcmluZyBgZG9tLWNoYW5nZWAgZXZlbnRzIG9uIHRoaXMKICAgICAgICAgICAqIGVsZW1lbnQuCiAgICAgICAgICAgKi8KICAgICAgICAgIG5vdGlmeURvbUNoYW5nZTogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuCiAgICAgICAgICB9CiAgICAgICAgfTsKCiAgICAgIH0KCiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CiAgICAgICAgdGhpcy5fX3JlbmRlckRlYm91bmNlciA9IG51bGw7CiAgICAgICAgdGhpcy5fbGFzdElmID0gZmFsc2U7CiAgICAgICAgdGhpcy5fX2hpZGVUZW1wbGF0ZUNoaWxkcmVuX18gPSBmYWxzZTsKICAgICAgICAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fHVuZGVmaW5lZH0gKi8KICAgICAgICB0aGlzLl9fdGVtcGxhdGU7CiAgICAgICAgLyoqIEB0eXBlIHshVGVtcGxhdGVJbmZvfHVuZGVmaW5lZH0gKi8KICAgICAgICB0aGlzLl90ZW1wbGF0ZUluZm87CiAgICAgIH0KCiAgICAgIF9fZGVib3VuY2VSZW5kZXIoKSB7CiAgICAgICAgLy8gUmVuZGVyIGlzIGFzeW5jIGZvciAyIHJlYXNvbnM6CiAgICAgICAgLy8gMS4gVG8gZWxpbWluYXRlIGRvbSBjcmVhdGlvbiB0cmFzaGluZyBpZiB1c2VyIGNvZGUgdGhyYXNoZXMgYGlmYCBpbiB0aGUKICAgICAgICAvLyAgICBzYW1lIHR1cm4uIFRoaXMgd2FzIG1vcmUgY29tbW9uIGluIDEueCB3aGVyZSBhIGNvbXBvdW5kIGNvbXB1dGVkCiAgICAgICAgLy8gICAgcHJvcGVydHkgY291bGQgcmVzdWx0IGluIHRoZSByZXN1bHQgY2hhbmdpbmcgbXVsdGlwbGUgdGltZXMsIGJ1dCBpcwogICAgICAgIC8vICAgIG1pdGlnYXRlZCB0byBhIGxhcmdlIGV4dGVudCBieSBiYXRjaGVkIHByb3BlcnR5IHByb2Nlc3NpbmcgaW4gMi54LgogICAgICAgIC8vIDIuIFRvIGF2b2lkIGRvdWJsZSBvYmplY3QgcHJvcGFnYXRpb24gd2hlbiBhIGJhZyBpbmNsdWRpbmcgdmFsdWVzIGJvdW5kCiAgICAgICAgLy8gICAgdG8gdGhlIGBpZmAgcHJvcGVydHkgYXMgd2VsbCBhcyBvbmUgb3IgbW9yZSBob3N0UHJvcHMgY291bGQgZW5xdWV1ZQogICAgICAgIC8vICAgIHRoZSA8ZG9tLWlmPiB0byBmbHVzaCBiZWZvcmUgdGhlIDx0ZW1wbGF0ZT4ncyBob3N0IHByb3BlcnR5CiAgICAgICAgLy8gICAgZm9yd2FyZGluZy4gSW4gdGhhdCBzY2VuYXJpbyBjcmVhdGluZyBhbiBpbnN0YW5jZSB3b3VsZCByZXN1bHQgaW4KICAgICAgICAvLyAgICB0aGUgaG9zdCBwcm9wcyBiZWluZyBzZXQgb25jZSwgYW5kIHRoZW4gdGhlIGVucXVldWVkIGNoYW5nZXMgb24gdGhlCiAgICAgICAgLy8gICAgdGVtcGxhdGUgd291bGQgc2V0IHByb3BlcnRpZXMgYSBzZWNvbmQgdGltZSwgcG90ZW50aWFsbHkgY2F1c2luZyBhbgogICAgICAgIC8vICAgIG9iamVjdCB0byBiZSBzZXQgdG8gYW4gaW5zdGFuY2UgbW9yZSB0aGFuIG9uY2UuICBDcmVhdGluZyB0aGUKICAgICAgICAvLyAgICBpbnN0YW5jZSBhc3luYyBmcm9tIGZsdXNoaW5nIGRhdGEgZW5zdXJlcyB0aGlzIGRvZXNuJ3QgaGFwcGVuLiBJZgogICAgICAgIC8vICAgIHdlIHdhbnRlZCBhIHN5bmMgb3B0aW9uIGluIHRoZSBmdXR1cmUsIHNpbXBseSBoYXZpbmcgPGRvbS1pZj4gZmx1c2gKICAgICAgICAvLyAgICAob3IgY2xlYXIpIGl0cyB0ZW1wbGF0ZSdzIHBlbmRpbmcgaG9zdCBwcm9wZXJ0aWVzIGJlZm9yZSBjcmVhdGluZwogICAgICAgIC8vICAgIHRoZSBpbnN0YW5jZSB3b3VsZCBhbHNvIGF2b2lkIHRoZSBwcm9ibGVtLgogICAgICAgIHRoaXMuX19yZW5kZXJEZWJvdW5jZXIgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgICAgdGhpcy5fX3JlbmRlckRlYm91bmNlcgogICAgICAgICAgICAsIG1pY3JvVGFzawogICAgICAgICAgICAsICgpID0+IHRoaXMuX19yZW5kZXIoKSk7CiAgICAgICAgZW5xdWV1ZURlYm91bmNlcih0aGlzLl9fcmVuZGVyRGVib3VuY2VyKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICBjb25zdCBwYXJlbnQgPSB3cmFwKHRoaXMpLnBhcmVudE5vZGU7CiAgICAgICAgaWYgKCFwYXJlbnQgfHwgKHBhcmVudC5ub2RlVHlwZSA9PSBOb2RlLkRPQ1VNRU5UX0ZSQUdNRU5UX05PREUgJiYKICAgICAgICAgICAgIXdyYXAocGFyZW50KS5ob3N0KSkgewogICAgICAgICAgdGhpcy5fX3RlYXJkb3duSW5zdGFuY2UoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgICAgaWYgKCFoaWRlRWxlbWVudHNHbG9iYWxseSgpKSB7CiAgICAgICAgICB0aGlzLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLmlmKSB7CiAgICAgICAgICB0aGlzLl9fZGVib3VuY2VSZW5kZXIoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBFbnN1cmVzIGEgdGVtcGxhdGUgaGFzIGJlZW4gYXNzaWduZWQgdG8gYHRoaXMuX190ZW1wbGF0ZWAuICBJZiBpdCBoYXMgbm90CiAgICAgICAqIHlldCBiZWVuLCBpdCBxdWVyeVNlbGVjdG9ycyBmb3IgaXQgaW4gaXRzIGNoaWxkcmVuIGFuZCBpZiBpdCBkb2VzIG5vdCB5ZXQKICAgICAgICogZXhpc3QgKGUuZy4gaW4gcGFyc2VyLWdlbmVyYXRlZCBjYXNlKSwgb3BlbnMgYSBtdXRhdGlvbiBvYnNlcnZlciBhbmQKICAgICAgICogd2FpdHMgZm9yIGl0IHRvIGFwcGVhciAocmV0dXJucyBmYWxzZSBpZiBpdCBoYXMgbm90IHlldCBiZWVuIGZvdW5kLAogICAgICAgKiBvdGhlcndpc2UgdHJ1ZSkuICBJbiB0aGUgYHJlbW92ZU5lc3RlZFRlbXBsYXRlc2AgY2FzZSwgdGhlICJ0ZW1wbGF0ZSIgd2lsbAogICAgICAgKiBiZSB0aGUgYGRvbS1pZmAgZWxlbWVudCBpdHNlbGYuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgd2hlbiBhIHRlbXBsYXRlIGhhcyBiZWVuIGZvdW5kLCBmYWxzZSBvdGhlcndpc2UKICAgICAgICovCiAgICAgIF9fZW5zdXJlVGVtcGxhdGUoKSB7CiAgICAgICAgaWYgKCF0aGlzLl9fdGVtcGxhdGUpIHsKICAgICAgICAgIC8vIFdoZW4gYHJlbW92ZU5lc3RlZFRlbXBsYXRlc2AgaXMgdHJ1ZSwgdGhlICJ0ZW1wbGF0ZSIgaXMgdGhlIGVsZW1lbnQKICAgICAgICAgIC8vIGl0c2VsZiwgd2hpY2ggaGFzIGJlZW4gZ2l2ZW4gYSBgX3RlbXBsYXRlSW5mb2AgcHJvcGVydHkKICAgICAgICAgIGNvbnN0IHRoaXNBc1RlbXBsYXRlID0gLyoqIEB0eXBlIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKAogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxFbGVtZW50fSAqLyAodGhpcykpOwogICAgICAgICAgbGV0IHRlbXBsYXRlID0gdGhpc0FzVGVtcGxhdGUuX3RlbXBsYXRlSW5mbyA/CiAgICAgICAgICAgICAgdGhpc0FzVGVtcGxhdGUgOgogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9ICovCiAgICAgICAgICAgICAgKHdyYXAodGhpc0FzVGVtcGxhdGUpLnF1ZXJ5U2VsZWN0b3IoJ3RlbXBsYXRlJykpOwogICAgICAgICAgaWYgKCF0ZW1wbGF0ZSkgewogICAgICAgICAgICAvLyBXYWl0IHVudGlsIGNoaWxkTGlzdCBjaGFuZ2VzIGFuZCB0ZW1wbGF0ZSBzaG91bGQgYmUgdGhlcmUgYnkgdGhlbgogICAgICAgICAgICBsZXQgb2JzZXJ2ZXIgPSBuZXcgTXV0YXRpb25PYnNlcnZlcigoKSA9PiB7CiAgICAgICAgICAgICAgaWYgKHdyYXAodGhpcykucXVlcnlTZWxlY3RvcigndGVtcGxhdGUnKSkgewogICAgICAgICAgICAgICAgb2JzZXJ2ZXIuZGlzY29ubmVjdCgpOwogICAgICAgICAgICAgICAgdGhpcy5fX3JlbmRlcigpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2RvbS1pZiByZXF1aXJlcyBhIDx0ZW1wbGF0ZT4gY2hpbGQnKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBvYnNlcnZlci5vYnNlcnZlKHRoaXMsIHtjaGlsZExpc3Q6IHRydWV9KTsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fX3RlbXBsYXRlID0gdGVtcGxhdGU7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogRW5zdXJlcyBhIGFuIGluc3RhbmNlIG9mIHRoZSB0ZW1wbGF0ZSBoYXMgYmVlbiBjcmVhdGVkIGFuZCBpbnNlcnRlZC4gVGhpcwogICAgICAgKiBtZXRob2QgbWF5IHJldHVybiBmYWxzZSBpZiB0aGUgdGVtcGxhdGUgaGFzIG5vdCB5ZXQgYmVlbiBmb3VuZCBvciBpZgogICAgICAgKiB0aGVyZSBpcyBubyBgcGFyZW50Tm9kZWAgdG8gaW5zZXJ0IHRoZSB0ZW1wbGF0ZSBpbnRvIChpbiBlaXRoZXIgY2FzZSwKICAgICAgICogY29ubmVjdGlvbiBvciB0aGUgdGVtcGxhdGUtZmluZGluZyBtdXRhdGlvbiBvYnNlcnZlciBmaXJpbmcgd2lsbCBxdWV1ZQogICAgICAgKiBhbm90aGVyIHJlbmRlciwgY2F1c2luZyB0aGlzIG1ldGhvZCB0byBiZSBjYWxsZWQgYWdhaW4gYXQgYSBtb3JlCiAgICAgICAqIGFwcHJvcHJpYXRlIHRpbWUpLgogICAgICAgKgogICAgICAgKiBTdWJjbGFzc2VzIHNob3VsZCBpbXBsZW1lbnQgdGhlIGZvbGxvd2luZyBtZXRob2RzIGNhbGxlZCBoZXJlOgogICAgICAgKiAtIGBfX2hhc0luc3RhbmNlYAogICAgICAgKiAtIGBfX2NyZWF0ZUFuZEluc2VydEluc3RhbmNlYAogICAgICAgKiAtIGBfX2dldEluc3RhbmNlTm9kZXNgCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFRydWUgaWYgdGhlIGluc3RhbmNlIHdhcyBjcmVhdGVkLCBmYWxzZSBvdGhlcndpc2UuCiAgICAgICAqLwogICAgICBfX2Vuc3VyZUluc3RhbmNlKCkgewogICAgICAgIGxldCBwYXJlbnROb2RlID0gd3JhcCh0aGlzKS5wYXJlbnROb2RlOwogICAgICAgIGlmICghdGhpcy5fX2hhc0luc3RhbmNlKCkpIHsKICAgICAgICAgIC8vIEd1YXJkIGFnYWluc3QgZWxlbWVudCBiZWluZyBkZXRhY2hlZCB3aGlsZSByZW5kZXIgd2FzIHF1ZXVlZAogICAgICAgICAgaWYgKCFwYXJlbnROb2RlKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIEZpbmQgdGhlIHRlbXBsYXRlICh3aGVuIGZhbHNlLCB0aGVyZSB3YXMgbm8gdGVtcGxhdGUgeWV0KQogICAgICAgICAgaWYgKCF0aGlzLl9fZW5zdXJlVGVtcGxhdGUoKSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9fY3JlYXRlQW5kSW5zZXJ0SW5zdGFuY2UocGFyZW50Tm9kZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIC8vIE1vdmUgaW5zdGFuY2UgY2hpbGRyZW4gaWYgbmVjZXNzYXJ5CiAgICAgICAgICBsZXQgY2hpbGRyZW4gPSB0aGlzLl9fZ2V0SW5zdGFuY2VOb2RlcygpOwogICAgICAgICAgaWYgKGNoaWxkcmVuICYmIGNoaWxkcmVuLmxlbmd0aCkgewogICAgICAgICAgICAvLyBEZXRlY3QgY2FzZSB3aGVyZSBkb20taWYgd2FzIHJlLWF0dGFjaGVkIGluIG5ldyBwb3NpdGlvbgogICAgICAgICAgICBsZXQgbGFzdENoaWxkID0gd3JhcCh0aGlzKS5wcmV2aW91c1NpYmxpbmc7CiAgICAgICAgICAgIGlmIChsYXN0Q2hpbGQgIT09IGNoaWxkcmVuW2NoaWxkcmVuLmxlbmd0aC0xXSkgewogICAgICAgICAgICAgIGZvciAobGV0IGk9MCwgbjsgKGk8Y2hpbGRyZW4ubGVuZ3RoKSAmJiAobj1jaGlsZHJlbltpXSk7IGkrKykgewogICAgICAgICAgICAgICAgd3JhcChwYXJlbnROb2RlKS5pbnNlcnRCZWZvcmUobiwgdGhpcyk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogRm9yY2VzIHRoZSBlbGVtZW50IHRvIHJlbmRlciBpdHMgY29udGVudC4gTm9ybWFsbHkgcmVuZGVyaW5nIGlzCiAgICAgICAqIGFzeW5jaHJvbm91cyB0byBhIHByb3Zva2luZyBjaGFuZ2UuIFRoaXMgaXMgZG9uZSBmb3IgZWZmaWNpZW5jeSBzbwogICAgICAgKiB0aGF0IG11bHRpcGxlIGNoYW5nZXMgdHJpZ2dlciBvbmx5IGEgc2luZ2xlIHJlbmRlci4gVGhlIHJlbmRlciBtZXRob2QKICAgICAgICogc2hvdWxkIGJlIGNhbGxlZCBpZiwgZm9yIGV4YW1wbGUsIHRlbXBsYXRlIHJlbmRlcmluZyBpcyByZXF1aXJlZCB0bwogICAgICAgKiB2YWxpZGF0ZSBhcHBsaWNhdGlvbiBzdGF0ZS4KICAgICAgICoKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIHJlbmRlcigpIHsKICAgICAgICBmbHVzaCgpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUGVyZm9ybXMgdGhlIGtleSByZW5kZXJpbmcgc3RlcHM6CiAgICAgICAqIDEuIEVuc3VyZSBhIHRlbXBsYXRlIGluc3RhbmNlIGhhcyBiZWVuIHN0YW1wZWQgKHdoZW4gdHJ1ZSkKICAgICAgICogMi4gUmVtb3ZlIHRoZSB0ZW1wbGF0ZSBpbnN0YW5jZSAod2hlbiBmYWxzZSBhbmQgcmVzdGFtcDp0cnVlKQogICAgICAgKiAzLiBTeW5jIHRoZSBoaWRkZW4gc3RhdGUgb2YgdGhlIGluc3RhbmNlIG5vZGVzIHdpdGggdGhlIGlmL3Jlc3RhbXAgc3RhdGUKICAgICAgICogNC4gRmlyZXMgdGhlIGBkb20tY2hhbmdlYCBldmVudCB3aGVuIG5lY2Vzc2FyeQogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX19yZW5kZXIoKSB7CiAgICAgICAgaWYgKHRoaXMuaWYpIHsKICAgICAgICAgIGlmICghdGhpcy5fX2Vuc3VyZUluc3RhbmNlKCkpIHsKICAgICAgICAgICAgLy8gTm8gdGVtcGxhdGUgZm91bmQgeWV0CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgaWYgKHRoaXMucmVzdGFtcCkgewogICAgICAgICAgdGhpcy5fX3RlYXJkb3duSW5zdGFuY2UoKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fc2hvd0hpZGVDaGlsZHJlbigpOwogICAgICAgIGlmICgoIXN1cHByZXNzVGVtcGxhdGVOb3RpZmljYXRpb25zIHx8IHRoaXMubm90aWZ5RG9tQ2hhbmdlKQogICAgICAgICAgICAmJiB0aGlzLmlmICE9IHRoaXMuX2xhc3RJZikgewogICAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnZG9tLWNoYW5nZScsIHsKICAgICAgICAgICAgYnViYmxlczogdHJ1ZSwKICAgICAgICAgICAgY29tcG9zZWQ6IHRydWUKICAgICAgICAgIH0pKTsKICAgICAgICAgIHRoaXMuX2xhc3RJZiA9IHRoaXMuaWY7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBJZGVhbGx5IHRoZXNlIHdvdWxkIGJlIGFubm90YXRlZCBhcyBhYnN0cmFjdCBtZXRob2RzIGluIGFuIGFic3RyYWN0IGNsYXNzLAogICAgICAvLyBidXQgY2xvc3VyZSBjb21waWxlciBpcyBmaW5uaWNreQogICAgICAvKiBlc2xpbnQtZGlzYWJsZSB2YWxpZC1qc2RvYyAqLwogICAgICAvKioKICAgICAgICogQWJzdHJhY3QgQVBJIHRvIGJlIGltcGxlbWVudGVkIGJ5IHN1YmNsYXNzOiBSZXR1cm5zIHRydWUgaWYgYSB0ZW1wbGF0ZQogICAgICAgKiBpbnN0YW5jZSBoYXMgYmVlbiBjcmVhdGVkIGFuZCBpbnNlcnRlZC4KICAgICAgICoKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIHdoZW4gYW4gaW5zdGFuY2UgaGFzIGJlZW4gY3JlYXRlZC4KICAgICAgICovCiAgICAgIF9faGFzSW5zdGFuY2UoKSB7IH0KCiAgICAgIC8qKgogICAgICAgKiBBYnN0cmFjdCBBUEkgdG8gYmUgaW1wbGVtZW50ZWQgYnkgc3ViY2xhc3M6IFJldHVybnMgdGhlIGNoaWxkIG5vZGVzIHN0YW1wZWQKICAgICAgICogZnJvbSBhIHRlbXBsYXRlIGluc3RhbmNlLgogICAgICAgKgogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqIEByZXR1cm4ge0FycmF5PE5vZGU+fSBBcnJheSBvZiBjaGlsZCBub2RlcyBzdGFtcGVkIGZyb20gdGhlIHRlbXBsYXRlCiAgICAgICAqIGluc3RhbmNlLgogICAgICAgKi8KICAgICAgX19nZXRJbnN0YW5jZU5vZGVzKCkgeyB9CgogICAgICAvKioKICAgICAgICogQWJzdHJhY3QgQVBJIHRvIGJlIGltcGxlbWVudGVkIGJ5IHN1YmNsYXNzOiBDcmVhdGVzIGFuIGluc3RhbmNlIG9mIHRoZQogICAgICAgKiB0ZW1wbGF0ZSBhbmQgaW5zZXJ0cyBpdCBpbnRvIHRoZSBnaXZlbiBwYXJlbnQgbm9kZS4KICAgICAgICoKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAcGFyYW0ge05vZGV9IHBhcmVudE5vZGUgVGhlIHBhcmVudCBub2RlIHRvIGluc2VydCB0aGUgaW5zdGFuY2UgaW50bwogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX19jcmVhdGVBbmRJbnNlcnRJbnN0YW5jZShwYXJlbnROb2RlKSB7IH0gLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtdmFycwoKICAgICAgLyoqCiAgICAgICAqIEFic3RyYWN0IEFQSSB0byBiZSBpbXBsZW1lbnRlZCBieSBzdWJjbGFzczogUmVtb3ZlcyBub2RlcyBjcmVhdGVkIGJ5IGFuCiAgICAgICAqIGluc3RhbmNlIG9mIGEgdGVtcGxhdGUgYW5kIGFueSBhc3NvY2lhdGVkIGNsZWFudXAuCiAgICAgICAqCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIF9fdGVhcmRvd25JbnN0YW5jZSgpIHsgfQoKICAgICAgLyoqCiAgICAgICAqIEFic3RyYWN0IEFQSSB0byBiZSBpbXBsZW1lbnRlZCBieSBzdWJjbGFzczogU2hvd3Mgb3IgaGlkZXMgYW55IHRlbXBsYXRlCiAgICAgICAqIGluc3RhbmNlIGNoaWxkTm9kZXMgYmFzZWQgb24gdGhlIGBpZmAgc3RhdGUgb2YgdGhlIGVsZW1lbnQgYW5kIGl0cwogICAgICAgKiBgX19oaWRlVGVtcGxhdGVDaGlsZHJlbl9fYCBwcm9wZXJ0eS4KICAgICAgICoKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX3Nob3dIaWRlQ2hpbGRyZW4oKSB7IH0KICAgICAgLyogZXNsaW50LWVuYWJsZSB2YWxpZC1qc2RvYyAqLwogICAgfQoKICAgIC8qKgogICAgICogVGhlIHZlcnNpb24gb2YgRG9tSWYgdXNlZCB3aGVuIGBmYXN0RG9tSWZgIHNldHRpbmcgaXMgaW4gdXNlLCB3aGljaCBpcwogICAgICogb3B0aW1pemVkIGZvciBmaXJzdC1yZW5kZXIgKGJ1dCBhZGRzIGEgdGF4IHRvIGFsbCBzdWJzZXF1ZW50IHByb3BlcnR5IHVwZGF0ZXMKICAgICAqIG9uIHRoZSBob3N0LCB3aGV0aGVyIHRoZXkgd2VyZSB1c2VkIGluIGEgZ2l2ZW4gYGRvbS1pZmAgb3Igbm90KS4KICAgICAqCiAgICAgKiBUaGlzIGltcGxlbWVudGF0aW9uIGF2b2lkcyB1c2Ugb2YgYFRlbXBsYXRpemVyYCwgd2hpY2ggaW50cm9kdWNlcyBhIG5ldyBzY29wZQogICAgICogKGEgbm9uLWVsZW1lbnQgUHJvcGVydHlFZmZlY3RzIGluc3RhbmNlKSwgd2hpY2ggaXMgbm90IHN0cmljdGx5IG5lY2Vzc2FyeQogICAgICogc2luY2UgYGRvbS1pZmAgbmV2ZXIgaW50cm9kdWNlcyBuZXcgcHJvcGVydGllcyB0byBpdHMgc2NvcGUgKHVubGlrZQogICAgICogYGRvbS1yZXBlYXRgKS4gVGFraW5nIGFkdmFudGFnZSBvZiB0aGlzIGZhY3QsIHRoZSBgZG9tLWlmYCByZWFjaGVzIHVwIHRvIGl0cwogICAgICogYF9fZGF0YUhvc3RgIGFuZCBzdGFtcHMgdGhlIHRlbXBsYXRlIGRpcmVjdGx5IGZyb20gdGhlIGhvc3QgdXNpbmcgdGhlIGhvc3QncwogICAgICogcnVudGltZSBgX3N0YW1wVGVtcGxhdGVgIEFQSSwgd2hpY2ggYmluZHMgdGhlIHByb3BlcnR5IGVmZmVjdHMgb2YgdGhlCiAgICAgKiB0ZW1wbGF0ZSBkaXJlY3RseSB0byB0aGUgaG9zdC4gVGhpcyBib3RoIGF2b2lkcyB0aGUgaW50ZXJtZWRpYXJ5CiAgICAgKiBgVGVtcGxhdGl6ZXJgIGluc3RhbmNlLCBidXQgYWxzbyBhdm9pZHMgdGhlIG5lZWQgdG8gYmluZCBob3N0IHByb3BlcnRpZXMgdG8KICAgICAqIHRoZSBgPHRlbXBsYXRlPmAgZWxlbWVudCBhbmQgZm9yd2FyZCB0aG9zZSBpbnRvIHRoZSB0ZW1wbGF0ZSBpbnN0YW5jZS4KICAgICAqCiAgICAgKiBJbiB0aGlzIHZlcnNpb24gb2YgYGRvbS1pZmAsIHRoZSBgdGhpcy5fX2luc3RhbmNlYCBtZXRob2QgaXMgdGhlCiAgICAgKiBgRG9jdW1lbnRGcmFnbWVudGAgcmV0dXJuZWQgZnJvbSBgX3N0YW1wVGVtcGxhdGVgLCB3aGljaCBhbHNvIHNlcnZlcyBhcyB0aGUKICAgICAqIGhhbmRsZSBmb3IgbGF0ZXIgcmVtb3ZpbmcgaXQgdXNpbmcgdGhlIGBfcmVtb3ZlQm91bmREb21gIG1ldGhvZC4KICAgICAqLwogICAgY2xhc3MgRG9tSWZGYXN0IGV4dGVuZHMgRG9tSWZCYXNlIHsKCiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CiAgICAgICAgdGhpcy5fX2luc3RhbmNlID0gbnVsbDsKICAgICAgICB0aGlzLl9fc3luY0luZm8gPSBudWxsOwogICAgICB9CgogICAgICAvKioKICAgICAgICogSW1wbGVtZW50YXRpb24gb2YgYWJzdHJhY3QgQVBJIG5lZWRlZCBieSBEb21JZkJhc2UuCiAgICAgICAqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIHdoZW4gYW4gaW5zdGFuY2UgaGFzIGJlZW4gY3JlYXRlZC4KICAgICAgICovCiAgICAgIF9faGFzSW5zdGFuY2UoKSB7CiAgICAgICAgcmV0dXJuIEJvb2xlYW4odGhpcy5fX2luc3RhbmNlKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEltcGxlbWVudGF0aW9uIG9mIGFic3RyYWN0IEFQSSBuZWVkZWQgYnkgRG9tSWZCYXNlLgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHJldHVybiB7QXJyYXk8Tm9kZT59IEFycmF5IG9mIGNoaWxkIG5vZGVzIHN0YW1wZWQgZnJvbSB0aGUgdGVtcGxhdGUKICAgICAgICogaW5zdGFuY2UuCiAgICAgICAqLwogICAgICBfX2dldEluc3RhbmNlTm9kZXMoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX19pbnN0YW5jZS50ZW1wbGF0ZUluZm8uY2hpbGROb2RlczsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEltcGxlbWVudGF0aW9uIG9mIGFic3RyYWN0IEFQSSBuZWVkZWQgYnkgRG9tSWZCYXNlLgogICAgICAgKgogICAgICAgKiBTdGFtcHMgdGhlIHRlbXBsYXRlIGJ5IGNhbGxpbmcgYF9zdGFtcFRlbXBsYXRlYCBvbiB0aGUgYF9fZGF0YUhvc3RgIG9mIHRoaXMKICAgICAgICogZWxlbWVudCBhbmQgdGhlbiBpbnNlcnRzIHRoZSByZXN1bHRpbmcgbm9kZXMgaW50byB0aGUgZ2l2ZW4gYHBhcmVudE5vZGVgLgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHBhcmFtIHtOb2RlfSBwYXJlbnROb2RlIFRoZSBwYXJlbnQgbm9kZSB0byBpbnNlcnQgdGhlIGluc3RhbmNlIGludG8KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIF9fY3JlYXRlQW5kSW5zZXJ0SW5zdGFuY2UocGFyZW50Tm9kZSkgewogICAgICAgIGNvbnN0IGhvc3QgPSB0aGlzLl9fZGF0YUhvc3QgfHwgdGhpczsKICAgICAgICBpZiAoc3RyaWN0VGVtcGxhdGVQb2xpY3kpIHsKICAgICAgICAgIGlmICghdGhpcy5fX2RhdGFIb3N0KSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignc3RyaWN0VGVtcGxhdGVQb2xpY3k6IHRlbXBsYXRlIG93bmVyIG5vdCB0cnVzdGVkJyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIFByZS1iaW5kIGFuZCBsaW5rIHRoZSB0ZW1wbGF0ZSBpbnRvIHRoZSBlZmZlY3RzIHN5c3RlbQogICAgICAgIGNvbnN0IHRlbXBsYXRlSW5mbyA9IGhvc3QuX2JpbmRUZW1wbGF0ZSgKICAgICAgICAgICAgLyoqIEB0eXBlIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKHRoaXMuX190ZW1wbGF0ZSksIHRydWUpOwogICAgICAgIC8vIEluc3RhbGwgcnVuRWZmZWN0cyBob29rIHRoYXQgcHJldmVudHMgcnVubmluZyBwcm9wZXJ0eSBlZmZlY3RzCiAgICAgICAgLy8gKGFuZCBhbnkgbmVzdGVkIHRlbXBsYXRlIGVmZmVjdHMpIHdoZW4gdGhlIGBpZmAgaXMgZmFsc2UKICAgICAgICB0ZW1wbGF0ZUluZm8ucnVuRWZmZWN0cyA9IChydW5FZmZlY3RzLCBjaGFuZ2VkUHJvcHMsIGhhc1BhdGhzKSA9PiB7CiAgICAgICAgICBsZXQgc3luY0luZm8gPSB0aGlzLl9fc3luY0luZm87CiAgICAgICAgICBpZiAodGhpcy5pZikgewogICAgICAgICAgICAvLyBNaXggYW55IHByb3BzIHRoYXQgY2hhbmdlZCB3aGlsZSB0aGUgYGlmYCB3YXMgZmFsc2UgaW50byBgY2hhbmdlZFByb3BzYAogICAgICAgICAgICBpZiAoc3luY0luZm8pIHsKICAgICAgICAgICAgICAvLyBJZiB0aGVyZSB3ZXJlIHByb3BlcnRpZXMgcmVjZWl2ZWQgd2hpbGUgdGhlIGBpZmAgd2FzIGZhbHNlLCBpdCBpcwogICAgICAgICAgICAgIC8vIGltcG9ydGFudCB0byBzeW5jIHRoZSBoaWRkZW4gc3RhdGUgd2l0aCB0aGUgZWxlbWVudCBfZmlyc3RfLCBzbyB0aGF0CiAgICAgICAgICAgICAgLy8gbmV3IGJpbmRpbmdzIHRvIGUuZy4gYHRleHRDb250ZW50YCBkbyBub3QgZ2V0IHN0b21wZWQgb24gYnkKICAgICAgICAgICAgICAvLyBwcmUtaGlkZGVuIHZhbHVlcyBpZiBgX3Nob3dIaWRlQ2hpbGRyZW5gIHdlcmUgdG8gYmUgY2FsbGVkIGxhdGVyIGF0CiAgICAgICAgICAgICAgLy8gdGhlIG5leHQgcmVuZGVyLiBDbGVhcmluZyBgX19pbnZhbGlkUHJvcHNgIGhlcmUgZW5zdXJlcwogICAgICAgICAgICAgIC8vIGBfc2hvd0hpZGVDaGlsZHJlbmAncyBjYWxsIHRvIGBfX3N5bmNIb3N0UHJvcGVydGllc2Agbm8tb3BzLCBzbwogICAgICAgICAgICAgIC8vIHRoYXQgd2UgZG9uJ3QgY2FsbCBgcnVuRWZmZWN0c2AgbW9yZSBvZnRlbiB0aGFuIG5lY2Vzc2FyeS4KICAgICAgICAgICAgICB0aGlzLl9fc3luY0luZm8gPSBudWxsOwogICAgICAgICAgICAgIHRoaXMuX3Nob3dIaWRlQ2hpbGRyZW4oKTsKICAgICAgICAgICAgICBjaGFuZ2VkUHJvcHMgPSBPYmplY3QuYXNzaWduKHN5bmNJbmZvLmNoYW5nZWRQcm9wcywgY2hhbmdlZFByb3BzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBydW5FZmZlY3RzKGNoYW5nZWRQcm9wcywgaGFzUGF0aHMpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gQWNjdW11bGF0ZSBhbnkgdmFsdWVzIGNoYW5nZWQgd2hpbGUgYGlmYCB3YXMgZmFsc2UsIGFsb25nIHdpdGggdGhlCiAgICAgICAgICAgIC8vIHJ1bkVmZmVjdHMgbWV0aG9kIHRvIHN5bmMgdGhlbSwgc28gdGhhdCB3ZSBjYW4gcmVwbGF5IHRoZW0gb25jZSBgaWZgCiAgICAgICAgICAgIC8vIGJlY29tZXMgdHJ1ZQogICAgICAgICAgICBpZiAodGhpcy5fX2luc3RhbmNlKSB7CiAgICAgICAgICAgICAgaWYgKCFzeW5jSW5mbykgewogICAgICAgICAgICAgICAgc3luY0luZm8gPSB0aGlzLl9fc3luY0luZm8gPSB7IHJ1bkVmZmVjdHMsIGNoYW5nZWRQcm9wczoge30gfTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgaWYgKGhhc1BhdGhzKSB7CiAgICAgICAgICAgICAgICAvLyBTdG9yZSByb290IG9iamVjdCBvZiBhbnkgcGF0aHM7IHRoaXMgd2lsbCBlbnN1cmUgZGlyZWN0IGJpbmRpbmdzCiAgICAgICAgICAgICAgICAvLyBsaWtlIFtbb2JqLmZvb11dIGJpbmRpbmdzIHJ1biBhZnRlciBhIGBzZXQoJ29iai5mb28nLCB2KWAsIGJ1dAogICAgICAgICAgICAgICAgLy8gbm90ZSB0aGF0IHBhdGggbm90aWZpY2F0aW9ucyBsaWtlIGBzZXQoJ29iai5mb28uYmFyJywgdilgIHdpbGwKICAgICAgICAgICAgICAgIC8vIG5vdCBwcm9wYWdhdGUuIFNpbmNlIGJhdGNoZWQgcGF0aCBub3RpZmljYXRpb25zIGFyZSBub3QKICAgICAgICAgICAgICAgIC8vIHN1cHBvcnRlZCwgd2UgY2Fubm90IHNpbXBseSBhY2N1bXVsYXRlIHBhdGggbm90aWZpY2F0aW9ucy4gVGhpcwogICAgICAgICAgICAgICAgLy8gaXMgZXF1aXZhbGVudCB0byB0aGUgbm9uLWZhc3REb21JZiBjYXNlLCB3aGljaCBzdG9yZXMgcm9vdChwKSBpbgogICAgICAgICAgICAgICAgLy8gX19pbnZhbGlkUHJvcHMuCiAgICAgICAgICAgICAgICBmb3IgKGNvbnN0IHAgaW4gY2hhbmdlZFByb3BzKSB7CiAgICAgICAgICAgICAgICAgIGNvbnN0IHJvb3RQcm9wID0gcm9vdChwKTsKICAgICAgICAgICAgICAgICAgc3luY0luZm8uY2hhbmdlZFByb3BzW3Jvb3RQcm9wXSA9IHRoaXMuX19kYXRhSG9zdFtyb290UHJvcF07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIE9iamVjdC5hc3NpZ24oc3luY0luZm8uY2hhbmdlZFByb3BzLCBjaGFuZ2VkUHJvcHMpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLy8gU3RhbXAgdGhlIHRlbXBsYXRlLCBhbmQgc2V0IGl0cyBEb2N1bWVudEZyYWdtZW50IHRvIHRoZSAiaW5zdGFuY2UiCiAgICAgICAgdGhpcy5fX2luc3RhbmNlID0gaG9zdC5fc3RhbXBUZW1wbGF0ZSgKICAgICAgICAgICAgLyoqIEB0eXBlIHshSFRNTFRlbXBsYXRlRWxlbWVudH0gKi8gKHRoaXMuX190ZW1wbGF0ZSksIHRlbXBsYXRlSW5mbyk7CiAgICAgICAgd3JhcChwYXJlbnROb2RlKS5pbnNlcnRCZWZvcmUodGhpcy5fX2luc3RhbmNlLCB0aGlzKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJ1biBlZmZlY3RzIGZvciBhbnkgcHJvcGVydGllcyB0aGF0IGNoYW5nZWQgd2hpbGUgdGhlIGBpZmAgd2FzIGZhbHNlLgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX19zeW5jSG9zdFByb3BlcnRpZXMoKSB7CiAgICAgICAgY29uc3Qgc3luY0luZm8gPSB0aGlzLl9fc3luY0luZm87CiAgICAgICAgaWYgKHN5bmNJbmZvKSB7CiAgICAgICAgICB0aGlzLl9fc3luY0luZm8gPSBudWxsOwogICAgICAgICAgc3luY0luZm8ucnVuRWZmZWN0cyhzeW5jSW5mby5jaGFuZ2VkUHJvcHMsIGZhbHNlKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBJbXBsZW1lbnRhdGlvbiBvZiBhYnN0cmFjdCBBUEkgbmVlZGVkIGJ5IERvbUlmQmFzZS4KICAgICAgICoKICAgICAgICogUmVtb3ZlIHRoZSBpbnN0YW5jZSBhbmQgYW55IG5vZGVzIGl0IGNyZWF0ZWQuICBVc2VzIHRoZSBgX19kYXRhSG9zdGAncwogICAgICAgKiBydW50aW1lIGBfcmVtb3ZlQm91bmREb21gIG1ldGhvZC4KICAgICAgICoKICAgICAgICogQG92ZXJyaWRlCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBfX3RlYXJkb3duSW5zdGFuY2UoKSB7CiAgICAgICAgY29uc3QgaG9zdCA9IHRoaXMuX19kYXRhSG9zdCB8fCB0aGlzOwogICAgICAgIGlmICh0aGlzLl9faW5zdGFuY2UpIHsKICAgICAgICAgIGhvc3QuX3JlbW92ZUJvdW5kRG9tKHRoaXMuX19pbnN0YW5jZSk7CiAgICAgICAgICB0aGlzLl9faW5zdGFuY2UgPSBudWxsOwogICAgICAgICAgdGhpcy5fX3N5bmNJbmZvID0gbnVsbDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBJbXBsZW1lbnRhdGlvbiBvZiBhYnN0cmFjdCBBUEkgbmVlZGVkIGJ5IERvbUlmQmFzZS4KICAgICAgICoKICAgICAgICogU2hvd3Mgb3IgaGlkZXMgdGhlIHRlbXBsYXRlIGluc3RhbmNlIHRvcCBsZXZlbCBjaGlsZCBub2Rlcy4gRm9yCiAgICAgICAqIHRleHQgbm9kZXMsIGB0ZXh0Q29udGVudGAgaXMgcmVtb3ZlZCB3aGlsZSAiaGlkZGVuIiBhbmQgcmVwbGFjZWQgd2hlbgogICAgICAgKiAic2hvd24uIgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAc3VwcHJlc3Mge3Zpc2liaWxpdHl9CiAgICAgICAqLwogICAgICBfc2hvd0hpZGVDaGlsZHJlbigpIHsKICAgICAgICBjb25zdCBoaWRkZW4gPSB0aGlzLl9faGlkZVRlbXBsYXRlQ2hpbGRyZW5fXyB8fCAhdGhpcy5pZjsKICAgICAgICBpZiAodGhpcy5fX2luc3RhbmNlICYmIEJvb2xlYW4odGhpcy5fX2luc3RhbmNlLl9faGlkZGVuKSAhPT0gaGlkZGVuKSB7CiAgICAgICAgICB0aGlzLl9faW5zdGFuY2UuX19oaWRkZW4gPSBoaWRkZW47CiAgICAgICAgICBzaG93SGlkZUNoaWxkcmVuKGhpZGRlbiwgdGhpcy5fX2luc3RhbmNlLnRlbXBsYXRlSW5mby5jaGlsZE5vZGVzKTsKICAgICAgICB9CiAgICAgICAgaWYgKCFoaWRkZW4pIHsKICAgICAgICAgIHRoaXMuX19zeW5jSG9zdFByb3BlcnRpZXMoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFRoZSAibGVnYWN5IiBpbXBsZW1lbnRhdGlvbiBvZiBgZG9tLWlmYCwgaW1wbGVtZW50ZWQgdXNpbmcgYFRlbXBsYXRpemVyYC4KICAgICAqCiAgICAgKiBJbiB0aGlzIHZlcnNpb24sIGB0aGlzLl9faW5zdGFuY2VgIGlzIHRoZSBgVGVtcGxhdGVJbnN0YW5jZWAgcmV0dXJuZWQKICAgICAqIGZyb20gdGhlIHRlbXBsYXRpemVkIGNvbnN0cnVjdG9yLgogICAgICovCiAgICBjbGFzcyBEb21JZkxlZ2FjeSBleHRlbmRzIERvbUlmQmFzZSB7CgogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICBzdXBlcigpOwogICAgICAgIHRoaXMuX19jdG9yID0gbnVsbDsKICAgICAgICB0aGlzLl9faW5zdGFuY2UgPSBudWxsOwogICAgICAgIHRoaXMuX19pbnZhbGlkUHJvcHMgPSBudWxsOwogICAgICB9CgogICAgICAvKioKICAgICAgICogSW1wbGVtZW50YXRpb24gb2YgYWJzdHJhY3QgQVBJIG5lZWRlZCBieSBEb21JZkJhc2UuCiAgICAgICAqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIHdoZW4gYW4gaW5zdGFuY2UgaGFzIGJlZW4gY3JlYXRlZC4KICAgICAgICovCiAgICAgIF9faGFzSW5zdGFuY2UoKSB7CiAgICAgICAgcmV0dXJuIEJvb2xlYW4odGhpcy5fX2luc3RhbmNlKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEltcGxlbWVudGF0aW9uIG9mIGFic3RyYWN0IEFQSSBuZWVkZWQgYnkgRG9tSWZCYXNlLgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHJldHVybiB7QXJyYXk8Tm9kZT59IEFycmF5IG9mIGNoaWxkIG5vZGVzIHN0YW1wZWQgZnJvbSB0aGUgdGVtcGxhdGUKICAgICAgICogaW5zdGFuY2UuCiAgICAgICAqLwogICAgICBfX2dldEluc3RhbmNlTm9kZXMoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX19pbnN0YW5jZS5jaGlsZHJlbjsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEltcGxlbWVudGF0aW9uIG9mIGFic3RyYWN0IEFQSSBuZWVkZWQgYnkgRG9tSWZCYXNlLgogICAgICAgKgogICAgICAgKiBTdGFtcHMgdGhlIHRlbXBsYXRlIGJ5IGNyZWF0aW5nIGEgbmV3IGluc3RhbmNlIG9mIHRoZSB0ZW1wbGF0aXplZAogICAgICAgKiBjb25zdHJ1Y3RvciAod2hpY2ggaXMgY3JlYXRlZCBsYXppbHkgaWYgaXQgZG9lcyBub3QgeWV0IGV4aXN0KSwgYW5kIHRoZW4KICAgICAgICogaW5zZXJ0cyBpdHMgcmVzdWx0aW5nIGByb290YCBkb2MgZnJhZ21lbnQgaW50byB0aGUgZ2l2ZW4gYHBhcmVudE5vZGVgLgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHBhcmFtIHtOb2RlfSBwYXJlbnROb2RlIFRoZSBwYXJlbnQgbm9kZSB0byBpbnNlcnQgdGhlIGluc3RhbmNlIGludG8KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIF9fY3JlYXRlQW5kSW5zZXJ0SW5zdGFuY2UocGFyZW50Tm9kZSkgewogICAgICAgIC8vIEVuc3VyZSB3ZSBoYXZlIGFuIGluc3RhbmNlIGNvbnN0cnVjdG9yCiAgICAgICAgaWYgKCF0aGlzLl9fY3RvcikgewogICAgICAgICAgdGhpcy5fX2N0b3IgPSB0ZW1wbGF0aXplKAogICAgICAgICAgICAgIC8qKiBAdHlwZSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9ICovICh0aGlzLl9fdGVtcGxhdGUpLCB0aGlzLCB7CiAgICAgICAgICAgICAgICAvLyBkb20taWYgdGVtcGxhdGl6ZXIgaW5zdGFuY2VzIHJlcXVpcmUgYG11dGFibGU6IHRydWVgLCBhcwogICAgICAgICAgICAgICAgLy8gYF9fc3luY0hvc3RQcm9wZXJ0aWVzYCByZWxpZXMgb24gdGhhdCBiZWhhdmlvciB0byBzeW5jIG9iamVjdHMKICAgICAgICAgICAgICAgIG11dGFibGVEYXRhOiB0cnVlLAogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcHJvcCBQcm9wZXJ0eSB0byBmb3J3YXJkCiAgICAgICAgICAgICAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFZhbHVlIG9mIHByb3BlcnR5CiAgICAgICAgICAgICAgICAgKiBAdGhpcyB7RG9tSWZMZWdhY3l9CiAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgIGZvcndhcmRIb3N0UHJvcDogZnVuY3Rpb24ocHJvcCwgdmFsdWUpIHsKICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuX19pbnN0YW5jZSkgewogICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLmlmKSB7CiAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9faW5zdGFuY2UuZm9yd2FyZEhvc3RQcm9wKHByb3AsIHZhbHVlKTsKICAgICAgICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgLy8gSWYgd2UgaGF2ZSBhbiBpbnN0YW5jZSBidXQgYXJlIHNxdWVsY2hpbmcgaG9zdCBwcm9wZXJ0eQogICAgICAgICAgICAgICAgICAgICAgLy8gZm9yd2FyZGluZyBkdWUgdG8gaWYgYmVpbmcgZmFsc2UsIG5vdGUgdGhlIGludmFsaWRhdGVkCiAgICAgICAgICAgICAgICAgICAgICAvLyBwcm9wZXJ0aWVzIHNvIGBfX3N5bmNIb3N0UHJvcGVydGllc2AgY2FuIHN5bmMgdGhlbSB0aGUgbmV4dAogICAgICAgICAgICAgICAgICAgICAgLy8gdGltZSBgaWZgIGJlY29tZXMgdHJ1ZQogICAgICAgICAgICAgICAgICAgICAgdGhpcy5fX2ludmFsaWRQcm9wcyA9CiAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fX2ludmFsaWRQcm9wcyB8fCBPYmplY3QuY3JlYXRlKG51bGwpOwogICAgICAgICAgICAgICAgICAgICAgdGhpcy5fX2ludmFsaWRQcm9wc1tyb290KHByb3ApXSA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIC8vIENyZWF0ZSBhbmQgaW5zZXJ0IHRoZSBpbnN0YW5jZQogICAgICAgIHRoaXMuX19pbnN0YW5jZSA9IG5ldyB0aGlzLl9fY3RvcigpOwogICAgICAgIHdyYXAocGFyZW50Tm9kZSkuaW5zZXJ0QmVmb3JlKHRoaXMuX19pbnN0YW5jZS5yb290LCB0aGlzKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEltcGxlbWVudGF0aW9uIG9mIGFic3RyYWN0IEFQSSBuZWVkZWQgYnkgRG9tSWZCYXNlLgogICAgICAgKgogICAgICAgKiBSZW1vdmVzIHRoZSBpbnN0YW5jZSBhbmQgYW55IG5vZGVzIGl0IGNyZWF0ZWQuCiAgICAgICAqCiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX190ZWFyZG93bkluc3RhbmNlKCkgewogICAgICAgIGlmICh0aGlzLl9faW5zdGFuY2UpIHsKICAgICAgICAgIGxldCBjJCA9IHRoaXMuX19pbnN0YW5jZS5jaGlsZHJlbjsKICAgICAgICAgIGlmIChjJCAmJiBjJC5sZW5ndGgpIHsKICAgICAgICAgICAgLy8gdXNlIGZpcnN0IGNoaWxkIHBhcmVudCwgZm9yIGNhc2Ugd2hlbiBkb20taWYgbWF5IGhhdmUgYmVlbiBkZXRhY2hlZAogICAgICAgICAgICBsZXQgcGFyZW50ID0gd3JhcChjJFswXSkucGFyZW50Tm9kZTsKICAgICAgICAgICAgLy8gSW5zdGFuY2UgY2hpbGRyZW4gbWF5IGJlIGRpc2Nvbm5lY3RlZCBmcm9tIHBhcmVudHMgd2hlbiBkb20taWYKICAgICAgICAgICAgLy8gZGV0YWNoZXMgaWYgYSB0cmVlIHdhcyBpbm5lckhUTUwnZWQKICAgICAgICAgICAgaWYgKHBhcmVudCkgewogICAgICAgICAgICAgIHBhcmVudCA9IHdyYXAocGFyZW50KTsKICAgICAgICAgICAgICBmb3IgKGxldCBpPTAsIG47IChpPGMkLmxlbmd0aCkgJiYgKG49YyRbaV0pOyBpKyspIHsKICAgICAgICAgICAgICAgIHBhcmVudC5yZW1vdmVDaGlsZChuKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX19pbnZhbGlkUHJvcHMgPSBudWxsOwogICAgICAgICAgdGhpcy5fX2luc3RhbmNlID0gbnVsbDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBGb3J3YXJkcyBhbnkgcHJvcGVydGllcyB0aGF0IGNoYW5nZWQgd2hpbGUgdGhlIGBpZmAgd2FzIGZhbHNlIGludG8gdGhlCiAgICAgICAqIHRlbXBsYXRlIGluc3RhbmNlIGFuZCBmbHVzaGVzIGl0LgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgX19zeW5jSG9zdFByb3BlcnRpZXMoKSB7CiAgICAgICAgbGV0IHByb3BzID0gdGhpcy5fX2ludmFsaWRQcm9wczsKICAgICAgICBpZiAocHJvcHMpIHsKICAgICAgICAgIHRoaXMuX19pbnZhbGlkUHJvcHMgPSBudWxsOwogICAgICAgICAgZm9yIChsZXQgcHJvcCBpbiBwcm9wcykgewogICAgICAgICAgICB0aGlzLl9faW5zdGFuY2UuX3NldFBlbmRpbmdQcm9wZXJ0eShwcm9wLCB0aGlzLl9fZGF0YUhvc3RbcHJvcF0pOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fX2luc3RhbmNlLl9mbHVzaFByb3BlcnRpZXMoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBJbXBsZW1lbnRhdGlvbiBvZiBhYnN0cmFjdCBBUEkgbmVlZGVkIGJ5IERvbUlmQmFzZS4KICAgICAgICoKICAgICAgICogU2hvd3Mgb3IgaGlkZXMgdGhlIHRlbXBsYXRlIGluc3RhbmNlIHRvcCBsZXZlbCBjaGlsZCBlbGVtZW50cy4gRm9yCiAgICAgICAqIHRleHQgbm9kZXMsIGB0ZXh0Q29udGVudGAgaXMgcmVtb3ZlZCB3aGlsZSAiaGlkZGVuIiBhbmQgcmVwbGFjZWQgd2hlbgogICAgICAgKiAic2hvd24uIgogICAgICAgKgogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKiBAc3VwcHJlc3Mge3Zpc2liaWxpdHl9CiAgICAgICAqLwogICAgICBfc2hvd0hpZGVDaGlsZHJlbigpIHsKICAgICAgICBjb25zdCBoaWRkZW4gPSB0aGlzLl9faGlkZVRlbXBsYXRlQ2hpbGRyZW5fXyB8fCAhdGhpcy5pZjsKICAgICAgICBpZiAodGhpcy5fX2luc3RhbmNlICYmIEJvb2xlYW4odGhpcy5fX2luc3RhbmNlLl9faGlkZGVuKSAhPT0gaGlkZGVuKSB7CiAgICAgICAgICB0aGlzLl9faW5zdGFuY2UuX19oaWRkZW4gPSBoaWRkZW47CiAgICAgICAgICB0aGlzLl9faW5zdGFuY2UuX3Nob3dIaWRlQ2hpbGRyZW4oaGlkZGVuKTsKICAgICAgICB9CiAgICAgICAgaWYgKCFoaWRkZW4pIHsKICAgICAgICAgIHRoaXMuX19zeW5jSG9zdFByb3BlcnRpZXMoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFRoZSBgPGRvbS1pZj5gIGVsZW1lbnQgd2lsbCBzdGFtcCBhIGxpZ2h0LWRvbSBgPHRlbXBsYXRlPmAgY2hpbGQgd2hlbgogICAgICogdGhlIGBpZmAgcHJvcGVydHkgYmVjb21lcyB0cnV0aHksIGFuZCB0aGUgdGVtcGxhdGUgY2FuIHVzZSBQb2x5bWVyCiAgICAgKiBkYXRhLWJpbmRpbmcgYW5kIGRlY2xhcmF0aXZlIGV2ZW50IGZlYXR1cmVzIHdoZW4gdXNlZCBpbiB0aGUgY29udGV4dCBvZgogICAgICogYSBQb2x5bWVyIGVsZW1lbnQncyB0ZW1wbGF0ZS4KICAgICAqCiAgICAgKiBXaGVuIGBpZmAgYmVjb21lcyBmYWxzeSwgdGhlIHN0YW1wZWQgY29udGVudCBpcyBoaWRkZW4gYnV0IG5vdAogICAgICogcmVtb3ZlZCBmcm9tIGRvbS4gV2hlbiBgaWZgIHN1YnNlcXVlbnRseSBiZWNvbWVzIHRydXRoeSBhZ2FpbiwgdGhlIGNvbnRlbnQKICAgICAqIGlzIHNpbXBseSByZS1zaG93bi4gVGhpcyBhcHByb2FjaCBpcyB1c2VkIGR1ZSB0byBpdHMgZmF2b3JhYmxlIHBlcmZvcm1hbmNlCiAgICAgKiBjaGFyYWN0ZXJpc3RpY3M6IHRoZSBleHBlbnNlIG9mIGNyZWF0aW5nIHRlbXBsYXRlIGNvbnRlbnQgaXMgcGFpZCBvbmx5CiAgICAgKiBvbmNlIGFuZCBsYXppbHkuCiAgICAgKgogICAgICogU2V0IHRoZSBgcmVzdGFtcGAgcHJvcGVydHkgdG8gdHJ1ZSB0byBmb3JjZSB0aGUgc3RhbXBlZCBjb250ZW50IHRvIGJlCiAgICAgKiBjcmVhdGVkIC8gZGVzdHJveWVkIHdoZW4gdGhlIGBpZmAgY29uZGl0aW9uIGNoYW5nZXMuCiAgICAgKgogICAgICogQGN1c3RvbUVsZW1lbnQKICAgICAqIEBwb2x5bWVyCiAgICAgKiBAZXh0ZW5kcyBEb21JZkJhc2UKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQHN1bW1hcnkgQ3VzdG9tIGVsZW1lbnQgdGhhdCBjb25kaXRpb25hbGx5IHN0YW1wcyBhbmQgaGlkZXMgb3IgcmVtb3ZlcwogICAgICogICB0ZW1wbGF0ZSBjb250ZW50IGJhc2VkIG9uIGEgYm9vbGVhbiBmbGFnLgogICAgICovCiAgICBjb25zdCBEb21JZiA9IGZhc3REb21JZiA/IERvbUlmRmFzdCA6IERvbUlmTGVnYWN5OwoKICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZShEb21JZi5pcywgRG9tSWYpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBFbGVtZW50IG1peGluIGZvciByZWNvcmRpbmcgZHluYW1pYyBhc3NvY2lhdGlvbnMgYmV0d2VlbiBpdGVtIHBhdGhzIGluIGEKICAgICAqIG1hc3RlciBgaXRlbXNgIGFycmF5IGFuZCBhIGBzZWxlY3RlZGAgYXJyYXkgc3VjaCB0aGF0IHBhdGggY2hhbmdlcyB0byB0aGUKICAgICAqIG1hc3RlciBhcnJheSAoYXQgdGhlIGhvc3QpIGVsZW1lbnQgb3IgZWxzZXdoZXJlIHZpYSBkYXRhLWJpbmRpbmcpIGFyZQogICAgICogY29ycmVjdGx5IHByb3BhZ2F0ZWQgdG8gaXRlbXMgaW4gdGhlIHNlbGVjdGVkIGFycmF5IGFuZCB2aWNlLXZlcnNhLgogICAgICoKICAgICAqIFRoZSBgaXRlbXNgIHByb3BlcnR5IGFjY2VwdHMgYW4gYXJyYXkgb2YgdXNlciBkYXRhLCBhbmQgdmlhIHRoZQogICAgICogYHNlbGVjdChpdGVtKWAgYW5kIGBkZXNlbGVjdChpdGVtKWAgQVBJLCB1cGRhdGVzIHRoZSBgc2VsZWN0ZWRgIHByb3BlcnR5CiAgICAgKiB3aGljaCBtYXkgYmUgYm91bmQgdG8gb3RoZXIgcGFydHMgb2YgdGhlIGFwcGxpY2F0aW9uLCBhbmQgYW55IGNoYW5nZXMgdG8KICAgICAqIHN1Yi1maWVsZHMgb2YgYHNlbGVjdGVkYCBpdGVtKHMpIHdpbGwgYmUga2VwdCBpbiBzeW5jIHdpdGggaXRlbXMgaW4gdGhlCiAgICAgKiBgaXRlbXNgIGFycmF5LiAgV2hlbiBgbXVsdGlgIGlzIGZhbHNlLCBgc2VsZWN0ZWRgIGlzIGEgcHJvcGVydHkKICAgICAqIHJlcHJlc2VudGluZyB0aGUgbGFzdCBzZWxlY3RlZCBpdGVtLiAgV2hlbiBgbXVsdGlgIGlzIHRydWUsIGBzZWxlY3RlZGAKICAgICAqIGlzIGFuIGFycmF5IG9mIG11bHRpcGx5IHNlbGVjdGVkIGl0ZW1zLgogICAgICoKICAgICAqIEBwb2x5bWVyCiAgICAgKiBAbWl4aW5GdW5jdGlvbgogICAgICogQGFwcGxpZXNNaXhpbiBFbGVtZW50TWl4aW4KICAgICAqIEBzdW1tYXJ5IEVsZW1lbnQgbWl4aW4gZm9yIHJlY29yZGluZyBkeW5hbWljIGFzc29jaWF0aW9ucyBiZXR3ZWVuIGl0ZW0gcGF0aHMgaW4gYQogICAgICogbWFzdGVyIGBpdGVtc2AgYXJyYXkgYW5kIGEgYHNlbGVjdGVkYCBhcnJheQogICAgICovCiAgICBsZXQgQXJyYXlTZWxlY3Rvck1peGluID0gZGVkdXBpbmdNaXhpbihzdXBlckNsYXNzID0+IHsKCiAgICAgIC8qKgogICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICogQGltcGxlbWVudHMge1BvbHltZXJfRWxlbWVudE1peGlufQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgbGV0IGVsZW1lbnRCYXNlID0gRWxlbWVudE1peGluKHN1cGVyQ2xhc3MpOwoKICAgICAgLyoqCiAgICAgICAqIEBwb2x5bWVyCiAgICAgICAqIEBtaXhpbkNsYXNzCiAgICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyX0FycmF5U2VsZWN0b3JNaXhpbn0KICAgICAgICogQHVucmVzdHJpY3RlZAogICAgICAgKi8KICAgICAgY2xhc3MgQXJyYXlTZWxlY3Rvck1peGluIGV4dGVuZHMgZWxlbWVudEJhc2UgewoKICAgICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgICByZXR1cm4gewoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEFuIGFycmF5IGNvbnRhaW5pbmcgaXRlbXMgZnJvbSB3aGljaCBzZWxlY3Rpb24gd2lsbCBiZSBtYWRlLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgaXRlbXM6IHsKICAgICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgfSwKCiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBXaGVuIGB0cnVlYCwgbXVsdGlwbGUgaXRlbXMgbWF5IGJlIHNlbGVjdGVkIGF0IG9uY2UgKGluIHRoaXMgY2FzZSwKICAgICAgICAgICAgICogYHNlbGVjdGVkYCBpcyBhbiBhcnJheSBvZiBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbXMpLiAgV2hlbiBgZmFsc2VgLAogICAgICAgICAgICAgKiBvbmx5IG9uZSBpdGVtIG1heSBiZSBzZWxlY3RlZCBhdCBhIHRpbWUuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBtdWx0aTogewogICAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgICAgICB9LAoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdoZW4gYG11bHRpYCBpcyB0cnVlLCB0aGlzIGlzIGFuIGFycmF5IHRoYXQgY29udGFpbnMgYW55IHNlbGVjdGVkLgogICAgICAgICAgICAgKiBXaGVuIGBtdWx0aWAgaXMgZmFsc2UsIHRoaXMgaXMgdGhlIGN1cnJlbnRseSBzZWxlY3RlZCBpdGVtLCBvciBgbnVsbGAKICAgICAgICAgICAgICogaWYgbm8gaXRlbSBpcyBzZWxlY3RlZC4KICAgICAgICAgICAgICogQHR5cGUgez9PYmplY3R8P0FycmF5PCFPYmplY3Q+fQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc2VsZWN0ZWQ6IHt0eXBlOiBPYmplY3QsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogV2hlbiBgbXVsdGlgIGlzIGZhbHNlLCB0aGlzIGlzIHRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbSwgb3IgYG51bGxgCiAgICAgICAgICAgICAqIGlmIG5vIGl0ZW0gaXMgc2VsZWN0ZWQuCiAgICAgICAgICAgICAqIEB0eXBlIHs/T2JqZWN0fQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgc2VsZWN0ZWRJdGVtOiB7dHlwZTogT2JqZWN0LCBub3RpZnk6IHRydWV9LAoKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdoZW4gYHRydWVgLCBjYWxsaW5nIGBzZWxlY3RgIG9uIGFuIGl0ZW0gdGhhdCBpcyBhbHJlYWR5IHNlbGVjdGVkCiAgICAgICAgICAgICAqIHdpbGwgZGVzZWxlY3QgdGhlIGl0ZW0uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0b2dnbGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9CgogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgICAgcmV0dXJuIFsnX191cGRhdGVTZWxlY3Rpb24obXVsdGksIGl0ZW1zLiopJ107CiAgICAgICAgfQoKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgIHN1cGVyKCk7CiAgICAgICAgICB0aGlzLl9fbGFzdEl0ZW1zID0gbnVsbDsKICAgICAgICAgIHRoaXMuX19sYXN0TXVsdGkgPSBudWxsOwogICAgICAgICAgdGhpcy5fX3NlbGVjdGVkTWFwID0gbnVsbDsKICAgICAgICB9CgogICAgICAgIF9fdXBkYXRlU2VsZWN0aW9uKG11bHRpLCBpdGVtc0luZm8pIHsKICAgICAgICAgIGxldCBwYXRoID0gaXRlbXNJbmZvLnBhdGg7CiAgICAgICAgICBpZiAocGF0aCA9PSBKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdpdGVtcycsIHRoaXMpKSB7CiAgICAgICAgICAgIC8vIENhc2UgMSAtIGl0ZW1zIGFycmF5IGNoYW5nZWQsIHNvIGRpZmYgYWdhaW5zdCBwcmV2aW91cyBhcnJheSBhbmQKICAgICAgICAgICAgLy8gZGVzZWxlY3QgYW55IHJlbW92ZWQgaXRlbXMgYW5kIGFkanVzdCBzZWxlY3RlZCBpbmRpY2VzCiAgICAgICAgICAgIGxldCBuZXdJdGVtcyA9IGl0ZW1zSW5mby5iYXNlIHx8IFtdOwogICAgICAgICAgICBsZXQgbGFzdEl0ZW1zID0gdGhpcy5fX2xhc3RJdGVtczsKICAgICAgICAgICAgbGV0IGxhc3RNdWx0aSA9IHRoaXMuX19sYXN0TXVsdGk7CiAgICAgICAgICAgIGlmIChtdWx0aSAhPT0gbGFzdE11bHRpKSB7CiAgICAgICAgICAgICAgdGhpcy5jbGVhclNlbGVjdGlvbigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChsYXN0SXRlbXMpIHsKICAgICAgICAgICAgICBsZXQgc3BsaWNlcyA9IGNhbGN1bGF0ZVNwbGljZXMobmV3SXRlbXMsIGxhc3RJdGVtcyk7CiAgICAgICAgICAgICAgdGhpcy5fX2FwcGx5U3BsaWNlcyhzcGxpY2VzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9fbGFzdEl0ZW1zID0gbmV3SXRlbXM7CiAgICAgICAgICAgIHRoaXMuX19sYXN0TXVsdGkgPSBtdWx0aTsKICAgICAgICAgIH0gZWxzZSBpZiAoaXRlbXNJbmZvLnBhdGggPT0gYCR7SlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnaXRlbXMnLCB0aGlzKX0uc3BsaWNlc2ApIHsKICAgICAgICAgICAgLy8gQ2FzZSAyIC0gZ290IHNwZWNpZmljIHNwbGljZSBpbmZvcm1hdGlvbiBkZXNjcmliaW5nIHRoZSBhcnJheSBtdXRhdGlvbjoKICAgICAgICAgICAgLy8gZGVzZWxlY3QgYW55IHJlbW92ZWQgaXRlbXMgYW5kIGFkanVzdCBzZWxlY3RlZCBpbmRpY2VzCiAgICAgICAgICAgIHRoaXMuX19hcHBseVNwbGljZXMoaXRlbXNJbmZvLnZhbHVlLmluZGV4U3BsaWNlcyk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvLyBDYXNlIDMgLSBhbiBhcnJheSBlbGVtZW50IHdhcyBjaGFuZ2VkLCBzbyBkZXNlbGVjdCB0aGUgcHJldmlvdXMKICAgICAgICAgICAgLy8gaXRlbSBmb3IgdGhhdCBpbmRleCBpZiBpdCB3YXMgcHJldmlvdXNseSBzZWxlY3RlZAogICAgICAgICAgICBsZXQgcGFydCA9IHBhdGguc2xpY2UoYCR7SlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnaXRlbXMnLCB0aGlzKX0uYC5sZW5ndGgpOwogICAgICAgICAgICBsZXQgaWR4ID0gcGFyc2VJbnQocGFydCwgMTApOwogICAgICAgICAgICBpZiAoKHBhcnQuaW5kZXhPZignLicpIDwgMCkgJiYgcGFydCA9PSBpZHgpIHsKICAgICAgICAgICAgICB0aGlzLl9fZGVzZWxlY3RDaGFuZ2VkSWR4KGlkeCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIF9fYXBwbHlTcGxpY2VzKHNwbGljZXMpIHsKICAgICAgICAgIGxldCBzZWxlY3RlZCA9IHRoaXMuX19zZWxlY3RlZE1hcDsKICAgICAgICAgIC8vIEFkanVzdCBzZWxlY3RlZCBpbmRpY2VzIGFuZCBtYXJrIHJlbW92YWxzCiAgICAgICAgICBmb3IgKGxldCBpPTA7IGk8c3BsaWNlcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICBsZXQgcyA9IHNwbGljZXNbaV07CiAgICAgICAgICAgIHNlbGVjdGVkLmZvckVhY2goKGlkeCwgaXRlbSkgPT4gewogICAgICAgICAgICAgIGlmIChpZHggPCBzLmluZGV4KSA7IGVsc2UgaWYgKGlkeCA+PSBzLmluZGV4ICsgcy5yZW1vdmVkLmxlbmd0aCkgewogICAgICAgICAgICAgICAgLy8gYWRqdXN0IGluZGV4CiAgICAgICAgICAgICAgICBzZWxlY3RlZC5zZXQoaXRlbSwgaWR4ICsgcy5hZGRlZENvdW50IC0gcy5yZW1vdmVkLmxlbmd0aCk7CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIHJlbW92ZSBpbmRleAogICAgICAgICAgICAgICAgc2VsZWN0ZWQuc2V0KGl0ZW0sIC0xKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBmb3IgKGxldCBqPTA7IGo8cy5hZGRlZENvdW50OyBqKyspIHsKICAgICAgICAgICAgICBsZXQgaWR4ID0gcy5pbmRleCArIGo7CiAgICAgICAgICAgICAgaWYgKHNlbGVjdGVkLmhhcyh0aGlzLml0ZW1zW2lkeF0pKSB7CiAgICAgICAgICAgICAgICBzZWxlY3RlZC5zZXQodGhpcy5pdGVtc1tpZHhdLCBpZHgpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgLy8gVXBkYXRlIGxpbmtlZCBwYXRocwogICAgICAgICAgdGhpcy5fX3VwZGF0ZUxpbmtzKCk7CiAgICAgICAgICAvLyBSZW1vdmUgc2VsZWN0ZWQgaXRlbXMgdGhhdCB3ZXJlIHJlbW92ZWQgZnJvbSB0aGUgaXRlbXMgYXJyYXkKICAgICAgICAgIGxldCBzaWR4ID0gMDsKICAgICAgICAgIHNlbGVjdGVkLmZvckVhY2goKGlkeCwgaXRlbSkgPT4gewogICAgICAgICAgICBpZiAoaWR4IDwgMCkgewogICAgICAgICAgICAgIGlmICh0aGlzLm11bHRpKSB7CiAgICAgICAgICAgICAgICB0aGlzLnNwbGljZShKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdzZWxlY3RlZCcsIHRoaXMpLCBzaWR4LCAxKTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5zZWxlY3RlZCA9IHRoaXMuc2VsZWN0ZWRJdGVtID0gbnVsbDsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgc2VsZWN0ZWQuZGVsZXRlKGl0ZW0pOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHNpZHgrKzsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICBfX3VwZGF0ZUxpbmtzKCkgewogICAgICAgICAgdGhpcy5fX2RhdGFMaW5rZWRQYXRocyA9IHt9OwogICAgICAgICAgaWYgKHRoaXMubXVsdGkpIHsKICAgICAgICAgICAgbGV0IHNpZHggPSAwOwogICAgICAgICAgICB0aGlzLl9fc2VsZWN0ZWRNYXAuZm9yRWFjaChpZHggPT4gewogICAgICAgICAgICAgIGlmIChpZHggPj0gMCkgewogICAgICAgICAgICAgICAgdGhpcy5saW5rUGF0aHMoCiAgICAgICAgICAgICAgICAgICAgYCR7SlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnaXRlbXMnLCB0aGlzKX0uJHtpZHh9YCwKICAgICAgICAgICAgICAgICAgICBgJHtKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdzZWxlY3RlZCcsIHRoaXMpfS4ke3NpZHgrK31gKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fX3NlbGVjdGVkTWFwLmZvckVhY2goaWR4ID0+IHsKICAgICAgICAgICAgICB0aGlzLmxpbmtQYXRocygKICAgICAgICAgICAgICAgICAgSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnc2VsZWN0ZWQnLCB0aGlzKSwKICAgICAgICAgICAgICAgICAgYCR7SlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnaXRlbXMnLCB0aGlzKX0uJHtpZHh9YCk7CiAgICAgICAgICAgICAgdGhpcy5saW5rUGF0aHMoCiAgICAgICAgICAgICAgICAgIEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ3NlbGVjdGVkSXRlbScsIHRoaXMpLAogICAgICAgICAgICAgICAgICBgJHtKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdpdGVtcycsIHRoaXMpfS4ke2lkeH1gKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBDbGVhcnMgdGhlIHNlbGVjdGlvbiBzdGF0ZS4KICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGNsZWFyU2VsZWN0aW9uKCkgewogICAgICAgICAgLy8gVW5iaW5kIHByZXZpb3VzIHNlbGVjdGlvbgogICAgICAgICAgdGhpcy5fX2RhdGFMaW5rZWRQYXRocyA9IHt9OwogICAgICAgICAgLy8gVGhlIHNlbGVjdGVkIG1hcCBzdG9yZXMgMyBwaWVjZXMgb2YgaW5mb3JtYXRpb246CiAgICAgICAgICAvLyBrZXk6IGl0ZW1zIGFycmF5IG9iamVjdAogICAgICAgICAgLy8gdmFsdWU6IGl0ZW1zIGFycmF5IGluZGV4CiAgICAgICAgICAvLyBvcmRlcjogc2VsZWN0ZWQgYXJyYXkgaW5kZXgKICAgICAgICAgIHRoaXMuX19zZWxlY3RlZE1hcCA9IG5ldyBNYXAoKTsKICAgICAgICAgIC8vIEluaXRpYWxpemUgc2VsZWN0aW9uCiAgICAgICAgICB0aGlzLnNlbGVjdGVkID0gdGhpcy5tdWx0aSA/IFtdIDogbnVsbDsKICAgICAgICAgIHRoaXMuc2VsZWN0ZWRJdGVtID0gbnVsbDsKICAgICAgICB9CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgaXRlbSBpcyBjdXJyZW50bHkgc2VsZWN0ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0geyp9IGl0ZW0gSXRlbSBmcm9tIGBpdGVtc2AgYXJyYXkgdG8gdGVzdAogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQKICAgICAgICAgKi8KICAgICAgICBpc1NlbGVjdGVkKGl0ZW0pIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9fc2VsZWN0ZWRNYXAuaGFzKGl0ZW0pOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB3aGV0aGVyIHRoZSBpdGVtIGlzIGN1cnJlbnRseSBzZWxlY3RlZC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBpZHggSW5kZXggZnJvbSBgaXRlbXNgIGFycmF5IHRvIHRlc3QKICAgICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBXaGV0aGVyIHRoZSBpdGVtIGlzIHNlbGVjdGVkCiAgICAgICAgICovCiAgICAgICAgaXNJbmRleFNlbGVjdGVkKGlkeCkgewogICAgICAgICAgcmV0dXJuIHRoaXMuaXNTZWxlY3RlZCh0aGlzLml0ZW1zW2lkeF0pOwogICAgICAgIH0KCiAgICAgICAgX19kZXNlbGVjdENoYW5nZWRJZHgoaWR4KSB7CiAgICAgICAgICBsZXQgc2lkeCA9IHRoaXMuX19zZWxlY3RlZEluZGV4Rm9ySXRlbUluZGV4KGlkeCk7CiAgICAgICAgICBpZiAoc2lkeCA+PSAwKSB7CiAgICAgICAgICAgIGxldCBpID0gMDsKICAgICAgICAgICAgdGhpcy5fX3NlbGVjdGVkTWFwLmZvckVhY2goKGlkeCwgaXRlbSkgPT4gewogICAgICAgICAgICAgIGlmIChzaWR4ID09IGkrKykgewogICAgICAgICAgICAgICAgdGhpcy5kZXNlbGVjdChpdGVtKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgX19zZWxlY3RlZEluZGV4Rm9ySXRlbUluZGV4KGlkeCkgewogICAgICAgICAgbGV0IHNlbGVjdGVkID0gdGhpcy5fX2RhdGFMaW5rZWRQYXRoc1tgJHtKU0NvbXBpbGVyX3JlbmFtZVByb3BlcnR5KCdpdGVtcycsIHRoaXMpfS4ke2lkeH1gXTsKICAgICAgICAgIGlmIChzZWxlY3RlZCkgewogICAgICAgICAgICByZXR1cm4gcGFyc2VJbnQoc2VsZWN0ZWQuc2xpY2UoYCR7SlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnc2VsZWN0ZWQnLCB0aGlzKX0uYC5sZW5ndGgpLCAxMCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBEZXNlbGVjdHMgdGhlIGdpdmVuIGl0ZW0gaWYgaXQgaXMgYWxyZWFkeSBzZWxlY3RlZC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7Kn0gaXRlbSBJdGVtIGZyb20gYGl0ZW1zYCBhcnJheSB0byBkZXNlbGVjdAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgZGVzZWxlY3QoaXRlbSkgewogICAgICAgICAgbGV0IGlkeCA9IHRoaXMuX19zZWxlY3RlZE1hcC5nZXQoaXRlbSk7CiAgICAgICAgICBpZiAoaWR4ID49IDApIHsKICAgICAgICAgICAgdGhpcy5fX3NlbGVjdGVkTWFwLmRlbGV0ZShpdGVtKTsKICAgICAgICAgICAgbGV0IHNpZHg7CiAgICAgICAgICAgIGlmICh0aGlzLm11bHRpKSB7CiAgICAgICAgICAgICAgc2lkeCA9IHRoaXMuX19zZWxlY3RlZEluZGV4Rm9ySXRlbUluZGV4KGlkeCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fX3VwZGF0ZUxpbmtzKCk7CiAgICAgICAgICAgIGlmICh0aGlzLm11bHRpKSB7CiAgICAgICAgICAgICAgdGhpcy5zcGxpY2UoSlNDb21waWxlcl9yZW5hbWVQcm9wZXJ0eSgnc2VsZWN0ZWQnLCB0aGlzKSwgc2lkeCwgMSk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdGhpcy5zZWxlY3RlZCA9IHRoaXMuc2VsZWN0ZWRJdGVtID0gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogRGVzZWxlY3RzIHRoZSBnaXZlbiBpbmRleCBpZiBpdCBpcyBhbHJlYWR5IHNlbGVjdGVkLgogICAgICAgICAqCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGlkeCBJbmRleCBmcm9tIGBpdGVtc2AgYXJyYXkgdG8gZGVzZWxlY3QKICAgICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgICAqLwogICAgICAgIGRlc2VsZWN0SW5kZXgoaWR4KSB7CiAgICAgICAgICB0aGlzLmRlc2VsZWN0KHRoaXMuaXRlbXNbaWR4XSk7CiAgICAgICAgfQoKICAgICAgICAvKioKICAgICAgICAgKiBTZWxlY3RzIHRoZSBnaXZlbiBpdGVtLiAgV2hlbiBgdG9nZ2xlYCBpcyB0cnVlLCB0aGlzIHdpbGwgYXV0b21hdGljYWxseQogICAgICAgICAqIGRlc2VsZWN0IHRoZSBpdGVtIGlmIGFscmVhZHkgc2VsZWN0ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICAgKiBAcGFyYW0geyp9IGl0ZW0gSXRlbSBmcm9tIGBpdGVtc2AgYXJyYXkgdG8gc2VsZWN0CiAgICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICAgKi8KICAgICAgICBzZWxlY3QoaXRlbSkgewogICAgICAgICAgdGhpcy5zZWxlY3RJbmRleCh0aGlzLml0ZW1zLmluZGV4T2YoaXRlbSkpOwogICAgICAgIH0KCiAgICAgICAgLyoqCiAgICAgICAgICogU2VsZWN0cyB0aGUgZ2l2ZW4gaW5kZXguICBXaGVuIGB0b2dnbGVgIGlzIHRydWUsIHRoaXMgd2lsbCBhdXRvbWF0aWNhbGx5CiAgICAgICAgICogZGVzZWxlY3QgdGhlIGl0ZW0gaWYgYWxyZWFkeSBzZWxlY3RlZC4KICAgICAgICAgKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBpZHggSW5kZXggZnJvbSBgaXRlbXNgIGFycmF5IHRvIHNlbGVjdAogICAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAgICovCiAgICAgICAgc2VsZWN0SW5kZXgoaWR4KSB7CiAgICAgICAgICBsZXQgaXRlbSA9IHRoaXMuaXRlbXNbaWR4XTsKICAgICAgICAgIGlmICghdGhpcy5pc1NlbGVjdGVkKGl0ZW0pKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5tdWx0aSkgewogICAgICAgICAgICAgIHRoaXMuX19zZWxlY3RlZE1hcC5jbGVhcigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX19zZWxlY3RlZE1hcC5zZXQoaXRlbSwgaWR4KTsKICAgICAgICAgICAgdGhpcy5fX3VwZGF0ZUxpbmtzKCk7CiAgICAgICAgICAgIGlmICh0aGlzLm11bHRpKSB7CiAgICAgICAgICAgICAgdGhpcy5wdXNoKEpTQ29tcGlsZXJfcmVuYW1lUHJvcGVydHkoJ3NlbGVjdGVkJywgdGhpcyksIGl0ZW0pOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHRoaXMuc2VsZWN0ZWQgPSB0aGlzLnNlbGVjdGVkSXRlbSA9IGl0ZW07CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAodGhpcy50b2dnbGUpIHsKICAgICAgICAgICAgdGhpcy5kZXNlbGVjdEluZGV4KGlkeCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgfQoKICAgICAgcmV0dXJuIEFycmF5U2VsZWN0b3JNaXhpbjsKCiAgICB9KTsKCiAgICAvKioKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQGV4dGVuZHMge1BvbHltZXJFbGVtZW50fQogICAgICogQGltcGxlbWVudHMge1BvbHltZXJfQXJyYXlTZWxlY3Rvck1peGlufQogICAgICogQHByaXZhdGUKICAgICAqLwogICAgbGV0IGJhc2VBcnJheVNlbGVjdG9yID0gQXJyYXlTZWxlY3Rvck1peGluKFBvbHltZXJFbGVtZW50KTsKCiAgICAvKioKICAgICAqIEVsZW1lbnQgaW1wbGVtZW50aW5nIHRoZSBgQXJyYXlTZWxlY3RvcmAgbWl4aW4sIHdoaWNoIHJlY29yZHMKICAgICAqIGR5bmFtaWMgYXNzb2NpYXRpb25zIGJldHdlZW4gaXRlbSBwYXRocyBpbiBhIG1hc3RlciBgaXRlbXNgIGFycmF5IGFuZCBhCiAgICAgKiBgc2VsZWN0ZWRgIGFycmF5IHN1Y2ggdGhhdCBwYXRoIGNoYW5nZXMgdG8gdGhlIG1hc3RlciBhcnJheSAoYXQgdGhlIGhvc3QpCiAgICAgKiBlbGVtZW50IG9yIGVsc2V3aGVyZSB2aWEgZGF0YS1iaW5kaW5nKSBhcmUgY29ycmVjdGx5IHByb3BhZ2F0ZWQgdG8gaXRlbXMKICAgICAqIGluIHRoZSBzZWxlY3RlZCBhcnJheSBhbmQgdmljZS12ZXJzYS4KICAgICAqCiAgICAgKiBUaGUgYGl0ZW1zYCBwcm9wZXJ0eSBhY2NlcHRzIGFuIGFycmF5IG9mIHVzZXIgZGF0YSwgYW5kIHZpYSB0aGUKICAgICAqIGBzZWxlY3QoaXRlbSlgIGFuZCBgZGVzZWxlY3QoaXRlbSlgIEFQSSwgdXBkYXRlcyB0aGUgYHNlbGVjdGVkYCBwcm9wZXJ0eQogICAgICogd2hpY2ggbWF5IGJlIGJvdW5kIHRvIG90aGVyIHBhcnRzIG9mIHRoZSBhcHBsaWNhdGlvbiwgYW5kIGFueSBjaGFuZ2VzIHRvCiAgICAgKiBzdWItZmllbGRzIG9mIGBzZWxlY3RlZGAgaXRlbShzKSB3aWxsIGJlIGtlcHQgaW4gc3luYyB3aXRoIGl0ZW1zIGluIHRoZQogICAgICogYGl0ZW1zYCBhcnJheS4gIFdoZW4gYG11bHRpYCBpcyBmYWxzZSwgYHNlbGVjdGVkYCBpcyBhIHByb3BlcnR5CiAgICAgKiByZXByZXNlbnRpbmcgdGhlIGxhc3Qgc2VsZWN0ZWQgaXRlbS4gIFdoZW4gYG11bHRpYCBpcyB0cnVlLCBgc2VsZWN0ZWRgCiAgICAgKiBpcyBhbiBhcnJheSBvZiBtdWx0aXBseSBzZWxlY3RlZCBpdGVtcy4KICAgICAqCiAgICAgKiBFeGFtcGxlOgogICAgICoKICAgICAqIGBgYGpzCiAgICAgKiBpbXBvcnQge1BvbHltZXJFbGVtZW50fSBmcm9tICdAcG9seW1lci9wb2x5bWVyJzsKICAgICAqIGltcG9ydCAnQHBvbHltZXIvcG9seW1lci9saWIvZWxlbWVudHMvYXJyYXktc2VsZWN0b3IuanMnOwogICAgICoKICAgICAqIGNsYXNzIEVtcGxveWVlTGlzdCBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAqICAgc3RhdGljIGdldCBfdGVtcGxhdGUoKSB7CiAgICAgKiAgICAgcmV0dXJuIGh0bWxgCiAgICAgKiAgICAgICAgIDxkaXY+IEVtcGxveWVlIGxpc3Q6IDwvZGl2PgogICAgICogICAgICAgICA8ZG9tLXJlcGVhdCBpZD0iZW1wbG95ZWVMaXN0IiBpdGVtcz0ie3tlbXBsb3llZXN9fSI+CiAgICAgKiAgICAgICAgICAgPHRlbXBsYXRlPgogICAgICogICAgICAgICAgICAgPGRpdj5GaXJzdCBuYW1lOiA8c3Bhbj57e2l0ZW0uZmlyc3R9fTwvc3Bhbj48L2Rpdj4KICAgICAqICAgICAgICAgICAgICAgPGRpdj5MYXN0IG5hbWU6IDxzcGFuPnt7aXRlbS5sYXN0fX08L3NwYW4+PC9kaXY+CiAgICAgKiAgICAgICAgICAgICAgIDxidXR0b24gb24tY2xpY2s9InRvZ2dsZVNlbGVjdGlvbiI+U2VsZWN0PC9idXR0b24+CiAgICAgKiAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAqICAgICAgICAgPC9kb20tcmVwZWF0PgogICAgICoKICAgICAqICAgICAgICAgPGFycmF5LXNlbGVjdG9yIGlkPSJzZWxlY3RvciIKICAgICAqICAgICAgICAgICAgICAgICAgICAgICAgIGl0ZW1zPSJ7e2VtcGxveWVlc319IgogICAgICogICAgICAgICAgICAgICAgICAgICAgICAgc2VsZWN0ZWQ9Int7c2VsZWN0ZWR9fSIKICAgICAqICAgICAgICAgICAgICAgICAgICAgICAgIG11bHRpIHRvZ2dsZT48L2FycmF5LXNlbGVjdG9yPgogICAgICoKICAgICAqICAgICAgICAgPGRpdj4gU2VsZWN0ZWQgZW1wbG95ZWVzOiA8L2Rpdj4KICAgICAqICAgICAgICAgPGRvbS1yZXBlYXQgaXRlbXM9Int7c2VsZWN0ZWR9fSI+CiAgICAgKiAgICAgICAgICAgPHRlbXBsYXRlPgogICAgICogICAgICAgICAgICAgPGRpdj5GaXJzdCBuYW1lOiA8c3Bhbj57e2l0ZW0uZmlyc3R9fTwvc3Bhbj48L2Rpdj4KICAgICAqICAgICAgICAgICAgIDxkaXY+TGFzdCBuYW1lOiA8c3Bhbj57e2l0ZW0ubGFzdH19PC9zcGFuPjwvZGl2PgogICAgICogICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgKiAgICAgICAgIDwvZG9tLXJlcGVhdD5gOwogICAgICogICB9CiAgICAgKiAgIHN0YXRpYyBnZXQgaXMoKSB7IHJldHVybiAnZW1wbG95ZWUtbGlzdCc7IH0KICAgICAqICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICogICAgIHJldHVybiB7CiAgICAgKiAgICAgICBlbXBsb3llZXM6IHsKICAgICAqICAgICAgICAgdmFsdWUoKSB7CiAgICAgKiAgICAgICAgICAgcmV0dXJuIFsKICAgICAqICAgICAgICAgICAgIHtmaXJzdDogJ0JvYicsIGxhc3Q6ICdTbWl0aCd9LAogICAgICogICAgICAgICAgICAge2ZpcnN0OiAnU2FsbHknLCBsYXN0OiAnSm9obnNvbid9LAogICAgICogICAgICAgICAgICAgLi4uCiAgICAgKiAgICAgICAgICAgXTsKICAgICAqICAgICAgICAgfQogICAgICogICAgICAgfQogICAgICogICAgIH07CiAgICAgKiAgIH0KICAgICAqICAgdG9nZ2xlU2VsZWN0aW9uKGUpIHsKICAgICAqICAgICBjb25zdCBpdGVtID0gdGhpcy4kLmVtcGxveWVlTGlzdC5pdGVtRm9yRWxlbWVudChlLnRhcmdldCk7CiAgICAgKiAgICAgdGhpcy4kLnNlbGVjdG9yLnNlbGVjdChpdGVtKTsKICAgICAqICAgfQogICAgICogfQogICAgICogYGBgCiAgICAgKgogICAgICogQHBvbHltZXIKICAgICAqIEBjdXN0b21FbGVtZW50CiAgICAgKiBAZXh0ZW5kcyB7YmFzZUFycmF5U2VsZWN0b3J9CiAgICAgKiBAYXBwbGllc01peGluIEFycmF5U2VsZWN0b3JNaXhpbgogICAgICogQHN1bW1hcnkgQ3VzdG9tIGVsZW1lbnQgdGhhdCBsaW5rcyBwYXRocyBiZXR3ZWVuIGFuIGlucHV0IGBpdGVtc2AgYXJyYXkgYW5kCiAgICAgKiAgIGFuIG91dHB1dCBgc2VsZWN0ZWRgIGl0ZW0gb3IgYXJyYXkgYmFzZWQgb24gY2FsbHMgdG8gaXRzIHNlbGVjdGlvbiBBUEkuCiAgICAgKi8KICAgIGNsYXNzIEFycmF5U2VsZWN0b3IgZXh0ZW5kcyBiYXNlQXJyYXlTZWxlY3RvciB7CiAgICAgIC8vIE5vdCBuZWVkZWQgdG8gZmluZCB0ZW1wbGF0ZTsgY2FuIGJlIHJlbW92ZWQgb25jZSB0aGUgYW5hbHl6ZXIKICAgICAgLy8gY2FuIGZpbmQgdGhlIHRhZyBuYW1lIGZyb20gY3VzdG9tRWxlbWVudHMuZGVmaW5lIGNhbGwKICAgICAgc3RhdGljIGdldCBpcygpIHsgcmV0dXJuICdhcnJheS1zZWxlY3Rvcic7IH0KICAgICAgc3RhdGljIGdldCB0ZW1wbGF0ZSgpIHsgcmV0dXJuIG51bGw7IH0KICAgIH0KICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZShBcnJheVNlbGVjdG9yLmlzLCBBcnJheVNlbGVjdG9yKTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNvbnN0IGN1c3RvbVN0eWxlSW50ZXJmYWNlID0gbmV3IEN1c3RvbVN0eWxlSW50ZXJmYWNlKCk7CgogICAgaWYgKCF3aW5kb3cuU2hhZHlDU1MpIHsKICAgICAgd2luZG93LlNoYWR5Q1NTID0gewogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBlbGVtZW50RXh0ZW5kcwogICAgICAgICAqLwogICAgICAgIHByZXBhcmVUZW1wbGF0ZSh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUsIGVsZW1lbnRFeHRlbmRzKSB7fSwgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtdmFycwoKICAgICAgICAvKioKICAgICAgICAgKiBAcGFyYW0geyFIVE1MVGVtcGxhdGVFbGVtZW50fSB0ZW1wbGF0ZQogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBlbGVtZW50TmFtZQogICAgICAgICAqLwogICAgICAgIHByZXBhcmVUZW1wbGF0ZURvbSh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUpIHt9LCAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXVudXNlZC12YXJzCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7IUhUTUxUZW1wbGF0ZUVsZW1lbnR9IHRlbXBsYXRlCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGVsZW1lbnROYW1lCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBlbGVtZW50RXh0ZW5kcwogICAgICAgICAqLwogICAgICAgIHByZXBhcmVUZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgZWxlbWVudE5hbWUsIGVsZW1lbnRFeHRlbmRzKSB7fSwgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby11bnVzZWQtdmFycwoKICAgICAgICAvKioKICAgICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IGVsZW1lbnQKICAgICAgICAgKiBAcGFyYW0ge09iamVjdD19IHByb3BlcnRpZXMKICAgICAgICAgKi8KICAgICAgICBzdHlsZVN1YnRyZWUoZWxlbWVudCwgcHJvcGVydGllcykgewogICAgICAgICAgY3VzdG9tU3R5bGVJbnRlcmZhY2UucHJvY2Vzc1N0eWxlcygpOwogICAgICAgICAgdXBkYXRlTmF0aXZlUHJvcGVydGllcyhlbGVtZW50LCBwcm9wZXJ0aWVzKTsKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IGVsZW1lbnQKICAgICAgICAgKi8KICAgICAgICBzdHlsZUVsZW1lbnQoZWxlbWVudCkgeyAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXVudXNlZC12YXJzCiAgICAgICAgICBjdXN0b21TdHlsZUludGVyZmFjZS5wcm9jZXNzU3R5bGVzKCk7CiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHtPYmplY3Q9fSBwcm9wZXJ0aWVzCiAgICAgICAgICovCiAgICAgICAgc3R5bGVEb2N1bWVudChwcm9wZXJ0aWVzKSB7CiAgICAgICAgICBjdXN0b21TdHlsZUludGVyZmFjZS5wcm9jZXNzU3R5bGVzKCk7CiAgICAgICAgICB1cGRhdGVOYXRpdmVQcm9wZXJ0aWVzKGRvY3VtZW50LmJvZHksIHByb3BlcnRpZXMpOwogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEBwYXJhbSB7RWxlbWVudH0gZWxlbWVudAogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBwcm9wZXJ0eQogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30KICAgICAgICAgKi8KICAgICAgICBnZXRDb21wdXRlZFN0eWxlVmFsdWUoZWxlbWVudCwgcHJvcGVydHkpIHsKICAgICAgICAgIHJldHVybiBnZXRDb21wdXRlZFN0eWxlVmFsdWUoZWxlbWVudCwgcHJvcGVydHkpOwogICAgICAgIH0sCgogICAgICAgIGZsdXNoQ3VzdG9tU3R5bGVzKCkge30sCiAgICAgICAgbmF0aXZlQ3NzOiBuYXRpdmVDc3NWYXJpYWJsZXMsCiAgICAgICAgbmF0aXZlU2hhZG93OiBuYXRpdmVTaGFkb3csCiAgICAgICAgY3NzQnVpbGQ6IGNzc0J1aWxkLAogICAgICAgIGRpc2FibGVSdW50aW1lOiBkaXNhYmxlUnVudGltZSwKICAgICAgfTsKICAgIH0KCiAgICB3aW5kb3cuU2hhZHlDU1MuQ3VzdG9tU3R5bGVJbnRlcmZhY2UgPSBjdXN0b21TdHlsZUludGVyZmFjZTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNvbnN0IGF0dHIgPSAnaW5jbHVkZSc7CgogICAgY29uc3QgQ3VzdG9tU3R5bGVJbnRlcmZhY2UkMSA9IHdpbmRvdy5TaGFkeUNTUy5DdXN0b21TdHlsZUludGVyZmFjZTsKCiAgICAvKioKICAgICAqIEN1c3RvbSBlbGVtZW50IGZvciBkZWZpbmluZyBzdHlsZXMgaW4gdGhlIG1haW4gZG9jdW1lbnQgdGhhdCBjYW4gdGFrZQogICAgICogYWR2YW50YWdlIG9mIFtzaGFkeSBET01dKGh0dHBzOi8vZ2l0aHViLmNvbS93ZWJjb21wb25lbnRzL3NoYWR5Y3NzKSBzaGltcwogICAgICogZm9yIHN0eWxlIGVuY2Fwc3VsYXRpb24sIGN1c3RvbSBwcm9wZXJ0aWVzLCBhbmQgY3VzdG9tIG1peGlucy4KICAgICAqCiAgICAgKiAtIERvY3VtZW50IHN0eWxlcyBkZWZpbmVkIGluIGEgYDxjdXN0b20tc3R5bGU+YCBhcmUgc2hpbW1lZCB0byBlbnN1cmUgdGhleQogICAgICogICBkbyBub3QgbGVhayBpbnRvIGxvY2FsIERPTSB3aGVuIHJ1bm5pbmcgb24gYnJvd3NlcnMgd2l0aG91dCBuYXRpdmUKICAgICAqICAgU2hhZG93IERPTS4KICAgICAqIC0gQ3VzdG9tIHByb3BlcnRpZXMgY2FuIGJlIGRlZmluZWQgaW4gYSBgPGN1c3RvbS1zdHlsZT5gLiBVc2UgdGhlIGBodG1sYCBzZWxlY3RvcgogICAgICogICB0byBkZWZpbmUgY3VzdG9tIHByb3BlcnRpZXMgdGhhdCBhcHBseSB0byBhbGwgY3VzdG9tIGVsZW1lbnRzLgogICAgICogLSBDdXN0b20gbWl4aW5zIGNhbiBiZSBkZWZpbmVkIGluIGEgYDxjdXN0b20tc3R5bGU+YCwgaWYgeW91IGltcG9ydCB0aGUgb3B0aW9uYWwKICAgICAqICAgW2FwcGx5IHNoaW1dKGh0dHBzOi8vZ2l0aHViLmNvbS93ZWJjb21wb25lbnRzL3NoYWR5Y3NzI2Fib3V0LWFwcGx5c2hpbSkKICAgICAqICAgKGBzaGFkeWNzcy9hcHBseS1zaGltLmh0bWxgKS4KICAgICAqCiAgICAgKiBUbyB1c2U6CiAgICAgKgogICAgICogLSBJbXBvcnQgYGN1c3RvbS1zdHlsZS5odG1sYC4KICAgICAqIC0gUGxhY2UgYSBgPGN1c3RvbS1zdHlsZT5gIGVsZW1lbnQgaW4gdGhlIG1haW4gZG9jdW1lbnQsIHdyYXBwaW5nIGFuIGlubGluZSBgPHN0eWxlPmAgdGFnIHRoYXQKICAgICAqICAgY29udGFpbnMgdGhlIENTUyBydWxlcyB5b3Ugd2FudCB0byBzaGltLgogICAgICoKICAgICAqIEZvciBleGFtcGxlOgogICAgICoKICAgICAqIGBgYGh0bWwKICAgICAqIDwhLS0gaW1wb3J0IGFwcGx5IHNoaW0tLW9ubHkgcmVxdWlyZWQgaWYgdXNpbmcgbWl4aW5zIC0tPgogICAgICogPGxpbmsgcmVsPSJpbXBvcnQiIGhyZWY9ImJvd2VyX2NvbXBvbmVudHMvc2hhZHljc3MvYXBwbHktc2hpbS5odG1sIj4KICAgICAqIDwhLS0gaW1wb3J0IGN1c3RvbS1zdHlsZSBlbGVtZW50IC0tPgogICAgICogPGxpbmsgcmVsPSJpbXBvcnQiIGhyZWY9ImJvd2VyX2NvbXBvbmVudHMvcG9seW1lci9saWIvZWxlbWVudHMvY3VzdG9tLXN0eWxlLmh0bWwiPgogICAgICoKICAgICAqIDxjdXN0b20tc3R5bGU+CiAgICAgKiAgIDxzdHlsZT4KICAgICAqICAgICBodG1sIHsKICAgICAqICAgICAgIC0tY3VzdG9tLWNvbG9yOiBibHVlOwogICAgICogICAgICAgLS1jdXN0b20tbWl4aW46IHsKICAgICAqICAgICAgICAgZm9udC13ZWlnaHQ6IGJvbGQ7CiAgICAgKiAgICAgICAgIGNvbG9yOiByZWQ7CiAgICAgKiAgICAgICB9OwogICAgICogICAgIH0KICAgICAqICAgPC9zdHlsZT4KICAgICAqIDwvY3VzdG9tLXN0eWxlPgogICAgICogYGBgCiAgICAgKgogICAgICogQGN1c3RvbUVsZW1lbnQKICAgICAqIEBleHRlbmRzIEhUTUxFbGVtZW50CiAgICAgKiBAc3VtbWFyeSBDdXN0b20gZWxlbWVudCBmb3IgZGVmaW5pbmcgc3R5bGVzIGluIHRoZSBtYWluIGRvY3VtZW50IHRoYXQgY2FuCiAgICAgKiAgIHRha2UgYWR2YW50YWdlIG9mIFBvbHltZXIncyBzdHlsZSBzY29waW5nIGFuZCBjdXN0b20gcHJvcGVydGllcyBzaGltcy4KICAgICAqLwogICAgY2xhc3MgQ3VzdG9tU3R5bGUgZXh0ZW5kcyBIVE1MRWxlbWVudCB7CiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CiAgICAgICAgdGhpcy5fc3R5bGUgPSBudWxsOwogICAgICAgIEN1c3RvbVN0eWxlSW50ZXJmYWNlJDEuYWRkQ3VzdG9tU3R5bGUodGhpcyk7CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIGxpZ2h0LURPTSBgPHN0eWxlPmAgY2hpbGQgdGhpcyBlbGVtZW50IHdyYXBzLiAgVXBvbiBmaXJzdAogICAgICAgKiBjYWxsIGFueSBzdHlsZSBtb2R1bGVzIHJlZmVyZW5jZWQgdmlhIHRoZSBgaW5jbHVkZWAgYXR0cmlidXRlIHdpbGwgYmUKICAgICAgICogY29uY2F0ZW5hdGVkIHRvIHRoaXMgZWxlbWVudCdzIGA8c3R5bGU+YC4KICAgICAgICoKICAgICAgICogQGV4cG9ydAogICAgICAgKiBAcmV0dXJuIHtIVE1MU3R5bGVFbGVtZW50fSBUaGlzIGVsZW1lbnQncyBsaWdodC1ET00gYDxzdHlsZT5gCiAgICAgICAqLwogICAgICBnZXRTdHlsZSgpIHsKICAgICAgICBpZiAodGhpcy5fc3R5bGUpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9zdHlsZTsKICAgICAgICB9CiAgICAgICAgY29uc3Qgc3R5bGUgPSAvKiogQHR5cGUge0hUTUxTdHlsZUVsZW1lbnR9ICovKHRoaXMucXVlcnlTZWxlY3Rvcignc3R5bGUnKSk7CiAgICAgICAgaWYgKCFzdHlsZSkgewogICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3N0eWxlID0gc3R5bGU7CiAgICAgICAgY29uc3QgaW5jbHVkZSA9IHN0eWxlLmdldEF0dHJpYnV0ZShhdHRyKTsKICAgICAgICBpZiAoaW5jbHVkZSkgewogICAgICAgICAgc3R5bGUucmVtb3ZlQXR0cmlidXRlKGF0dHIpOwogICAgICAgICAgLyoqIEBzdXBwcmVzcyB7ZGVwcmVjYXRlZH0gKi8KICAgICAgICAgIHN0eWxlLnRleHRDb250ZW50ID0gY3NzRnJvbU1vZHVsZXMoaW5jbHVkZSkgKyBzdHlsZS50ZXh0Q29udGVudDsKICAgICAgICB9CiAgICAgICAgLyoKICAgICAgICBIVE1MIEltcG9ydHMgc3R5bGluZyB0aGUgbWFpbiBkb2N1bWVudCBhcmUgZGVwcmVjYXRlZCBpbiBDaHJvbWUKICAgICAgICBodHRwczovL2NyYnVnLmNvbS81MjM5NTIKCiAgICAgICAgSWYgdGhpcyBlbGVtZW50IGlzIG5vdCBpbiB0aGUgbWFpbiBkb2N1bWVudCwgdGhlbiBpdCBtdXN0IGJlIGluIGFuIEhUTUwgSW1wb3J0IGRvY3VtZW50LgogICAgICAgIEluIHRoYXQgY2FzZSwgbW92ZSB0aGUgY3VzdG9tIHN0eWxlIHRvIHRoZSBtYWluIGRvY3VtZW50LgoKICAgICAgICBUaGUgb3JkZXJpbmcgb2YgYDxjdXN0b20tc3R5bGU+YCBzaG91bGQgc3RheSB0aGUgc2FtZSBhcyB3aGVuIGxvYWRlZCBieSBIVE1MIEltcG9ydHMsIGJ1dCB0aGVyZSBtYXkgYmUgb2RkCiAgICAgICAgY2FzZXMgb2Ygb3JkZXJpbmcgdy5yLnQgdGhlIG1haW4gZG9jdW1lbnQgc3R5bGVzLgogICAgICAgICovCiAgICAgICAgaWYgKHRoaXMub3duZXJEb2N1bWVudCAhPT0gd2luZG93LmRvY3VtZW50KSB7CiAgICAgICAgICB3aW5kb3cuZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCh0aGlzKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRoaXMuX3N0eWxlOwogICAgICB9CiAgICB9CgogICAgd2luZG93LmN1c3RvbUVsZW1lbnRzLmRlZmluZSgnY3VzdG9tLXN0eWxlJywgQ3VzdG9tU3R5bGUpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgbGV0IG11dGFibGVQcm9wZXJ0eUNoYW5nZSQxOwogICAgLyoqIEBzdXBwcmVzcyB7bWlzc2luZ1Byb3BlcnRpZXN9ICovCiAgICAoKCkgPT4gewogICAgICBtdXRhYmxlUHJvcGVydHlDaGFuZ2UkMSA9IE11dGFibGVEYXRhLl9tdXRhYmxlUHJvcGVydHlDaGFuZ2U7CiAgICB9KSgpOwoKICAgIC8qKgogICAgICogTGVnYWN5IGVsZW1lbnQgYmVoYXZpb3IgdG8gYWRkIHRoZSBvcHRpb25hbCBhYmlsaXR5IHRvIHNraXAgc3RyaWN0CiAgICAgKiBkaXJ0eS1jaGVja2luZyBmb3Igb2JqZWN0cyBhbmQgYXJyYXlzIChhbHdheXMgY29uc2lkZXIgdGhlbSB0byBiZQogICAgICogImRpcnR5IikgYnkgc2V0dGluZyBhIGBtdXRhYmxlLWRhdGFgIGF0dHJpYnV0ZSBvbiBhbiBlbGVtZW50IGluc3RhbmNlLgogICAgICoKICAgICAqIEJ5IGRlZmF1bHQsIGBQb2x5bWVyLlByb3BlcnR5RWZmZWN0c2AgcGVyZm9ybXMgc3RyaWN0IGRpcnR5IGNoZWNraW5nIG9uCiAgICAgKiBvYmplY3RzLCB3aGljaCBtZWFucyB0aGF0IGFueSBkZWVwIG1vZGlmaWNhdGlvbnMgdG8gYW4gb2JqZWN0IG9yIGFycmF5IHdpbGwKICAgICAqIG5vdCBiZSBwcm9wYWdhdGVkIHVubGVzcyAiaW1tdXRhYmxlIiBkYXRhIHBhdHRlcm5zIGFyZSB1c2VkIChpLmUuIGFsbCBvYmplY3QKICAgICAqIHJlZmVyZW5jZXMgZnJvbSB0aGUgcm9vdCB0byB0aGUgbXV0YXRpb24gd2VyZSBjaGFuZ2VkKS4KICAgICAqCiAgICAgKiBQb2x5bWVyIGFsc28gcHJvdmlkZXMgYSBwcm9wcmlldGFyeSBkYXRhIG11dGF0aW9uIGFuZCBwYXRoIG5vdGlmaWNhdGlvbiBBUEkKICAgICAqIChlLmcuIGBub3RpZnlQYXRoYCwgYHNldGAsIGFuZCBhcnJheSBtdXRhdGlvbiBBUEkncykgdGhhdCBhbGxvdyBlZmZpY2llbnQKICAgICAqIG11dGF0aW9uIGFuZCBub3RpZmljYXRpb24gb2YgZGVlcCBjaGFuZ2VzIGluIGFuIG9iamVjdCBncmFwaCB0byBhbGwgZWxlbWVudHMKICAgICAqIGJvdW5kIHRvIHRoZSBzYW1lIG9iamVjdCBncmFwaC4KICAgICAqCiAgICAgKiBJbiBjYXNlcyB3aGVyZSBuZWl0aGVyIGltbXV0YWJsZSBwYXR0ZXJucyBub3IgdGhlIGRhdGEgbXV0YXRpb24gQVBJIGNhbiBiZQogICAgICogdXNlZCwgYXBwbHlpbmcgdGhpcyBtaXhpbiB3aWxsIGFsbG93IFBvbHltZXIgdG8gc2tpcCBkaXJ0eSBjaGVja2luZyBmb3IKICAgICAqIG9iamVjdHMgYW5kIGFycmF5cyAoYWx3YXlzIGNvbnNpZGVyIHRoZW0gdG8gYmUgImRpcnR5IikuICBUaGlzIGFsbG93cyBhCiAgICAgKiB1c2VyIHRvIG1ha2UgYSBkZWVwIG1vZGlmaWNhdGlvbiB0byBhIGJvdW5kIG9iamVjdCBncmFwaCwgYW5kIHRoZW4gZWl0aGVyCiAgICAgKiBzaW1wbHkgcmUtc2V0IHRoZSBvYmplY3QgKGUuZy4gYHRoaXMuaXRlbXMgPSB0aGlzLml0ZW1zYCkgb3IgY2FsbCBgbm90aWZ5UGF0aGAKICAgICAqIChlLmcuIGB0aGlzLm5vdGlmeVBhdGgoJ2l0ZW1zJylgKSB0byB1cGRhdGUgdGhlIHRyZWUuICBOb3RlIHRoYXQgYWxsCiAgICAgKiBlbGVtZW50cyB0aGF0IHdpc2ggdG8gYmUgdXBkYXRlZCBiYXNlZCBvbiBkZWVwIG11dGF0aW9ucyBtdXN0IGFwcGx5IHRoaXMKICAgICAqIG1peGluIG9yIG90aGVyd2lzZSBza2lwIHN0cmljdCBkaXJ0eSBjaGVja2luZyBmb3Igb2JqZWN0cy9hcnJheXMuCiAgICAgKiBTcGVjaWZpY2FsbHksIGFueSBlbGVtZW50cyBpbiB0aGUgYmluZGluZyB0cmVlIGJldHdlZW4gdGhlIHNvdXJjZSBvZiBhCiAgICAgKiBtdXRhdGlvbiBhbmQgdGhlIGNvbnN1bXB0aW9uIG9mIGl0IG11c3QgZW5hYmxlIHRoaXMgYmVoYXZpb3Igb3IgYXBwbHkgdGhlCiAgICAgKiBgUG9seW1lci5PcHRpb25hbE11dGFibGVEYXRhQmVoYXZpb3JgLgogICAgICoKICAgICAqIFdoaWxlIHRoaXMgYmVoYXZpb3IgYWRkcyB0aGUgYWJpbGl0eSB0byBmb3JnbyBPYmplY3QvQXJyYXkgZGlydHkgY2hlY2tpbmcsCiAgICAgKiB0aGUgYG11dGFibGVEYXRhYCBmbGFnIGRlZmF1bHRzIHRvIGZhbHNlIGFuZCBtdXN0IGJlIHNldCBvbiB0aGUgaW5zdGFuY2UuCiAgICAgKgogICAgICogTm90ZSwgdGhlIHBlcmZvcm1hbmNlIGNoYXJhY3RlcmlzdGljcyBvZiBwcm9wYWdhdGluZyBsYXJnZSBvYmplY3QgZ3JhcGhzCiAgICAgKiB3aWxsIGJlIHdvcnNlIGJ5IHJlbHlpbmcgb24gYG11dGFibGVEYXRhOiB0cnVlYCBhcyBvcHBvc2VkIHRvIHVzaW5nCiAgICAgKiBzdHJpY3QgZGlydHkgY2hlY2tpbmcgd2l0aCBpbW11dGFibGUgcGF0dGVybnMgb3IgUG9seW1lcidzIHBhdGggbm90aWZpY2F0aW9uCiAgICAgKiBBUEkuCiAgICAgKgogICAgICogQHBvbHltZXJCZWhhdmlvcgogICAgICogQHN1bW1hcnkgQmVoYXZpb3IgdG8gb3B0aW9uYWxseSBza2lwIHN0cmljdCBkaXJ0eS1jaGVja2luZyBmb3Igb2JqZWN0cyBhbmQKICAgICAqICAgYXJyYXlzCiAgICAgKi8KICAgIGNvbnN0IE9wdGlvbmFsTXV0YWJsZURhdGFCZWhhdmlvciA9IHsKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBJbnN0YW5jZS1sZXZlbCBmbGFnIGZvciBjb25maWd1cmluZyB0aGUgZGlydHktY2hlY2tpbmcgc3RyYXRlZ3kKICAgICAgICAgKiBmb3IgdGhpcyBlbGVtZW50LiAgV2hlbiB0cnVlLCBPYmplY3RzIGFuZCBBcnJheXMgd2lsbCBza2lwIGRpcnR5CiAgICAgICAgICogY2hlY2tpbmcsIG90aGVyd2lzZSBzdHJpY3QgZXF1YWxpdHkgY2hlY2tpbmcgd2lsbCBiZSB1c2VkLgogICAgICAgICAqLwogICAgICAgIG11dGFibGVEYXRhOiBCb29sZWFuCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogT3ZlcnJpZGVzIGBQb2x5bWVyLlByb3BlcnR5RWZmZWN0c2AgdG8gc2tpcCBzdHJpY3QgZXF1YWxpdHkgY2hlY2tpbmcKICAgICAgICogZm9yIE9iamVjdHMgYW5kIEFycmF5cy4KICAgICAgICoKICAgICAgICogUHVsbHMgdGhlIHZhbHVlIHRvIGRpcnR5IGNoZWNrIGFnYWluc3QgZnJvbSB0aGUgYF9fZGF0YVRlbXBgIGNhY2hlCiAgICAgICAqIChyYXRoZXIgdGhhbiB0aGUgbm9ybWFsIGBfX2RhdGFgIGNhY2hlKSBmb3IgT2JqZWN0cy4gIFNpbmNlIHRoZSB0ZW1wCiAgICAgICAqIGNhY2hlIGlzIGNsZWFyZWQgYXQgdGhlIGVuZCBvZiBhIHR1cm4sIHRoaXMgaW1wbGVtZW50YXRpb24gYWxsb3dzCiAgICAgICAqIHNpZGUtZWZmZWN0cyBvZiBkZWVwIG9iamVjdCBjaGFuZ2VzIHRvIGJlIHByb2Nlc3NlZCBieSByZS1zZXR0aW5nIHRoZQogICAgICAgKiBzYW1lIG9iamVjdCAodXNpbmcgdGhlIHRlbXAgY2FjaGUgYXMgYW4gaW4tdHVybiBiYWNrc3RvcCB0byBwcmV2ZW50CiAgICAgICAqIGN5Y2xlcyBkdWUgdG8gMi13YXkgbm90aWZpY2F0aW9uKS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHByb3BlcnR5IFByb3BlcnR5IG5hbWUKICAgICAgICogQHBhcmFtIHsqfSB2YWx1ZSBOZXcgcHJvcGVydHkgdmFsdWUKICAgICAgICogQHBhcmFtIHsqfSBvbGQgUHJldmlvdXMgcHJvcGVydHkgdmFsdWUKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciB0aGUgcHJvcGVydHkgc2hvdWxkIGJlIGNvbnNpZGVyZWQgYSBjaGFuZ2UKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKiBAb3ZlcnJpZGUKICAgICAgICovCiAgICAgIF9zaG91bGRQcm9wZXJ0eUNoYW5nZShwcm9wZXJ0eSwgdmFsdWUsIG9sZCkgewogICAgICAgIHJldHVybiBtdXRhYmxlUHJvcGVydHlDaGFuZ2UkMSh0aGlzLCBwcm9wZXJ0eSwgdmFsdWUsIG9sZCwgdGhpcy5tdXRhYmxlRGF0YSk7CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyBiYwogICAgY29uc3QgQmFzZSA9IExlZ2FjeUVsZW1lbnRNaXhpbihIVE1MRWxlbWVudCkucHJvdG90eXBlOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8vIENvbnRhaW5zIGFsbCBjb25uZWN0ZWQgcmVzaXphYmxlcyB0aGF0IGRvIG5vdCBoYXZlIGEgcGFyZW50LgogICAgdmFyIE9SUEhBTlMgPSBuZXcgU2V0KCk7CgogICAgLyoqCiAgICAgKiBgSXJvblJlc2l6YWJsZUJlaGF2aW9yYCBpcyBhIGJlaGF2aW9yIHRoYXQgY2FuIGJlIHVzZWQgaW4gUG9seW1lciBlbGVtZW50cyB0bwogICAgICogY29vcmRpbmF0ZSB0aGUgZmxvdyBvZiByZXNpemUgZXZlbnRzIGJldHdlZW4gInJlc2l6ZXJzIiAoZWxlbWVudHMgdGhhdAogICAgICpjb250cm9sIHRoZSBzaXplIG9yIGhpZGRlbiBzdGF0ZSBvZiB0aGVpciBjaGlsZHJlbikgYW5kICJyZXNpemFibGVzIiAoZWxlbWVudHMKICAgICAqdGhhdCBuZWVkIHRvIGJlIG5vdGlmaWVkIHdoZW4gdGhleSBhcmUgcmVzaXplZCBvciB1bi1oaWRkZW4gYnkgdGhlaXIgcGFyZW50cwogICAgICppbiBvcmRlciB0byB0YWtlIGFjdGlvbiBvbiB0aGVpciBuZXcgbWVhc3VyZW1lbnRzKS4KICAgICAqCiAgICAgKiBFbGVtZW50cyB0aGF0IHBlcmZvcm0gbWVhc3VyZW1lbnQgc2hvdWxkIGFkZCB0aGUgYElyb25SZXNpemFibGVCZWhhdmlvcmAKICAgICAqYmVoYXZpb3IgdG8gdGhlaXIgZWxlbWVudCBkZWZpbml0aW9uIGFuZCBsaXN0ZW4gZm9yIHRoZSBgaXJvbi1yZXNpemVgIGV2ZW50IG9uCiAgICAgKnRoZW1zZWx2ZXMuIFRoaXMgZXZlbnQgd2lsbCBiZSBmaXJlZCB3aGVuIHRoZXkgYmVjb21lIHNob3dpbmcgYWZ0ZXIgaGF2aW5nCiAgICAgKmJlZW4gaGlkZGVuLCB3aGVuIHRoZXkgYXJlIHJlc2l6ZWQgZXhwbGljaXRseSBieSBhbm90aGVyIHJlc2l6YWJsZSwgb3Igd2hlbgogICAgICp0aGUgd2luZG93IGhhcyBiZWVuIHJlc2l6ZWQuCiAgICAgKgogICAgICogTm90ZSwgdGhlIGBpcm9uLXJlc2l6ZWAgZXZlbnQgaXMgbm9uLWJ1YmJsaW5nLgogICAgICoKICAgICAqIEBwb2x5bWVyQmVoYXZpb3IKICAgICAqIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgICoqLwogICAgY29uc3QgSXJvblJlc2l6YWJsZUJlaGF2aW9yID0gewogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGNsb3Nlc3QgYW5jZXN0b3IgZWxlbWVudCB0aGF0IGltcGxlbWVudHMgYElyb25SZXNpemFibGVCZWhhdmlvcmAuCiAgICAgICAgICovCiAgICAgICAgX3BhcmVudFJlc2l6YWJsZTogewogICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgb2JzZXJ2ZXI6ICdfcGFyZW50UmVzaXphYmxlQ2hhbmdlZCcsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVHJ1ZSBpZiB0aGlzIGVsZW1lbnQgaXMgY3VycmVudGx5IG5vdGlmeWluZyBpdHMgZGVzY2VuZGFudCBlbGVtZW50cyBvZgogICAgICAgICAqIHJlc2l6ZS4KICAgICAgICAgKi8KICAgICAgICBfbm90aWZ5aW5nRGVzY2VuZGFudDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICB9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsKICAgICAgICAnaXJvbi1yZXF1ZXN0LXJlc2l6ZS1ub3RpZmljYXRpb25zJzogJ19vbklyb25SZXF1ZXN0UmVzaXplTm90aWZpY2F0aW9ucycKICAgICAgfSwKCiAgICAgIGNyZWF0ZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFdlIGRvbid0IHJlYWxseSBuZWVkIHByb3BlcnR5IGVmZmVjdHMgb24gdGhlc2UsIGFuZCBhbHNvIHdlIHdhbnQgdGhlbQogICAgICAgIC8vIHRvIGJlIGNyZWF0ZWQgYmVmb3JlIHRoZSBgX3BhcmVudFJlc2l6YWJsZWAgb2JzZXJ2ZXIgZmlyZXM6CiAgICAgICAgdGhpcy5faW50ZXJlc3RlZFJlc2l6YWJsZXMgPSBbXTsKICAgICAgICB0aGlzLl9ib3VuZE5vdGlmeVJlc2l6ZSA9IHRoaXMubm90aWZ5UmVzaXplLmJpbmQodGhpcyk7CiAgICAgICAgdGhpcy5fYm91bmRPbkRlc2NlbmRhbnRJcm9uUmVzaXplID0gdGhpcy5fb25EZXNjZW5kYW50SXJvblJlc2l6ZS5iaW5kKHRoaXMpOwogICAgICB9LAoKICAgICAgYXR0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3JlcXVlc3RSZXNpemVOb3RpZmljYXRpb25zKCk7CiAgICAgIH0sCgogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX3BhcmVudFJlc2l6YWJsZSkgewogICAgICAgICAgdGhpcy5fcGFyZW50UmVzaXphYmxlLnN0b3BSZXNpemVOb3RpZmljYXRpb25zRm9yKHRoaXMpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBPUlBIQU5TLmRlbGV0ZSh0aGlzKTsKICAgICAgICAgIHdpbmRvdy5yZW1vdmVFdmVudExpc3RlbmVyKCdyZXNpemUnLCB0aGlzLl9ib3VuZE5vdGlmeVJlc2l6ZSk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9wYXJlbnRSZXNpemFibGUgPSBudWxsOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbiBiZSBjYWxsZWQgdG8gbWFudWFsbHkgbm90aWZ5IGEgcmVzaXphYmxlIGFuZCBpdHMgZGVzY2VuZGFudAogICAgICAgKiByZXNpemFibGVzIG9mIGEgcmVzaXplIGNoYW5nZS4KICAgICAgICovCiAgICAgIG5vdGlmeVJlc2l6ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2ludGVyZXN0ZWRSZXNpemFibGVzLmZvckVhY2goZnVuY3Rpb24ocmVzaXphYmxlKSB7CiAgICAgICAgICBpZiAodGhpcy5yZXNpemVyU2hvdWxkTm90aWZ5KHJlc2l6YWJsZSkpIHsKICAgICAgICAgICAgdGhpcy5fbm90aWZ5RGVzY2VuZGFudChyZXNpemFibGUpOwogICAgICAgICAgfQogICAgICAgIH0sIHRoaXMpOwoKICAgICAgICB0aGlzLl9maXJlUmVzaXplKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXNlZCB0byBhc3NpZ24gdGhlIGNsb3Nlc3QgcmVzaXphYmxlIGFuY2VzdG9yIHRvIHRoaXMgcmVzaXphYmxlCiAgICAgICAqIGlmIHRoZSBhbmNlc3RvciBkZXRlY3RzIGEgcmVxdWVzdCBmb3Igbm90aWZpY2F0aW9ucy4KICAgICAgICovCiAgICAgIGFzc2lnblBhcmVudFJlc2l6YWJsZTogZnVuY3Rpb24ocGFyZW50UmVzaXphYmxlKSB7CiAgICAgICAgaWYgKHRoaXMuX3BhcmVudFJlc2l6YWJsZSkgewogICAgICAgICAgdGhpcy5fcGFyZW50UmVzaXphYmxlLnN0b3BSZXNpemVOb3RpZmljYXRpb25zRm9yKHRoaXMpOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fcGFyZW50UmVzaXphYmxlID0gcGFyZW50UmVzaXphYmxlOwoKICAgICAgICBpZiAocGFyZW50UmVzaXphYmxlICYmCiAgICAgICAgICAgIHBhcmVudFJlc2l6YWJsZS5faW50ZXJlc3RlZFJlc2l6YWJsZXMuaW5kZXhPZih0aGlzKSA9PT0gLTEpIHsKICAgICAgICAgIHBhcmVudFJlc2l6YWJsZS5faW50ZXJlc3RlZFJlc2l6YWJsZXMucHVzaCh0aGlzKTsKICAgICAgICAgIHBhcmVudFJlc2l6YWJsZS5fc3Vic2NyaWJlSXJvblJlc2l6ZSh0aGlzKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXNlZCB0byByZW1vdmUgYSByZXNpemFibGUgZGVzY2VuZGFudCBmcm9tIHRoZSBsaXN0IG9mIGRlc2NlbmRhbnRzCiAgICAgICAqIHRoYXQgc2hvdWxkIGJlIG5vdGlmaWVkIG9mIGEgcmVzaXplIGNoYW5nZS4KICAgICAgICovCiAgICAgIHN0b3BSZXNpemVOb3RpZmljYXRpb25zRm9yOiBmdW5jdGlvbih0YXJnZXQpIHsKICAgICAgICB2YXIgaW5kZXggPSB0aGlzLl9pbnRlcmVzdGVkUmVzaXphYmxlcy5pbmRleE9mKHRhcmdldCk7CgogICAgICAgIGlmIChpbmRleCA+IC0xKSB7CiAgICAgICAgICB0aGlzLl9pbnRlcmVzdGVkUmVzaXphYmxlcy5zcGxpY2UoaW5kZXgsIDEpOwogICAgICAgICAgdGhpcy5fdW5zdWJzY3JpYmVJcm9uUmVzaXplKHRhcmdldCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFN1YnNjcmliZSB0aGlzIGVsZW1lbnQgdG8gbGlzdGVuIHRvIGlyb24tcmVzaXplIGV2ZW50cyBvbiB0aGUgZ2l2ZW4gdGFyZ2V0LgogICAgICAgKgogICAgICAgKiBQcmVmZXJyZWQgb3ZlciB0YXJnZXQubGlzdGVuIGJlY2F1c2UgdGhlIHByb3BlcnR5IHJlbmFtZXIgZG9lcyBub3QKICAgICAgICogdW5kZXJzdGFuZCB0byByZW5hbWUgd2hlbiB0aGUgdGFyZ2V0IGlzIG5vdCBzcGVjaWZpY2FsbHkgInRoaXMiCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSB0YXJnZXQgRWxlbWVudCB0byBsaXN0ZW4gdG8gZm9yIGlyb24tcmVzaXplIGV2ZW50cy4KICAgICAgICovCiAgICAgIF9zdWJzY3JpYmVJcm9uUmVzaXplOiBmdW5jdGlvbih0YXJnZXQpIHsKICAgICAgICB0YXJnZXQuYWRkRXZlbnRMaXN0ZW5lcignaXJvbi1yZXNpemUnLCB0aGlzLl9ib3VuZE9uRGVzY2VuZGFudElyb25SZXNpemUpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVuc3Vic2NyaWJlIHRoaXMgZWxlbWVudCBmcm9tIGxpc3RlbmluZyB0byB0byBpcm9uLXJlc2l6ZSBldmVudHMgb24gdGhlCiAgICAgICAqIGdpdmVuIHRhcmdldC4KICAgICAgICoKICAgICAgICogUHJlZmVycmVkIG92ZXIgdGFyZ2V0LnVubGlzdGVuIGJlY2F1c2UgdGhlIHByb3BlcnR5IHJlbmFtZXIgZG9lcyBub3QKICAgICAgICogdW5kZXJzdGFuZCB0byByZW5hbWUgd2hlbiB0aGUgdGFyZ2V0IGlzIG5vdCBzcGVjaWZpY2FsbHkgInRoaXMiCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSB0YXJnZXQgRWxlbWVudCB0byBsaXN0ZW4gdG8gZm9yIGlyb24tcmVzaXplIGV2ZW50cy4KICAgICAgICovCiAgICAgIF91bnN1YnNjcmliZUlyb25SZXNpemU6IGZ1bmN0aW9uKHRhcmdldCkgewogICAgICAgIHRhcmdldC5yZW1vdmVFdmVudExpc3RlbmVyKAogICAgICAgICAgICAnaXJvbi1yZXNpemUnLCB0aGlzLl9ib3VuZE9uRGVzY2VuZGFudElyb25SZXNpemUpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoaXMgbWV0aG9kIGNhbiBiZSBvdmVycmlkZGVuIHRvIGZpbHRlciBuZXN0ZWQgZWxlbWVudHMgdGhhdCBzaG91bGQgb3IKICAgICAgICogc2hvdWxkIG5vdCBiZSBub3RpZmllZCBieSB0aGUgY3VycmVudCBlbGVtZW50LiBSZXR1cm4gdHJ1ZSBpZiBhbiBlbGVtZW50CiAgICAgICAqIHNob3VsZCBiZSBub3RpZmllZCwgb3IgZmFsc2UgaWYgaXQgc2hvdWxkIG5vdCBiZSBub3RpZmllZC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudCBBIGNhbmRpZGF0ZSBkZXNjZW5kYW50IGVsZW1lbnQgdGhhdAogICAgICAgKiBpbXBsZW1lbnRzIGBJcm9uUmVzaXphYmxlQmVoYXZpb3JgLgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHRoZSBgZWxlbWVudGAgc2hvdWxkIGJlIG5vdGlmaWVkIG9mIHJlc2l6ZS4KICAgICAgICovCiAgICAgIHJlc2l6ZXJTaG91bGROb3RpZnk6IGZ1bmN0aW9uKGVsZW1lbnQpIHsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfSwKCiAgICAgIF9vbkRlc2NlbmRhbnRJcm9uUmVzaXplOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICh0aGlzLl9ub3RpZnlpbmdEZXNjZW5kYW50KSB7CiAgICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIG5vIG5lZWQgdG8gdXNlIHRoaXMgZHVyaW5nIHNoYWRvdyBkb20gYmVjYXVzZSBvZiBldmVudCByZXRhcmdldGluZwogICAgICAgIGlmICghdXNlU2hhZG93KSB7CiAgICAgICAgICB0aGlzLl9maXJlUmVzaXplKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2ZpcmVSZXNpemU6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuZmlyZSgnaXJvbi1yZXNpemUnLCBudWxsLCB7bm9kZTogdGhpcywgYnViYmxlczogZmFsc2V9KTsKICAgICAgfSwKCiAgICAgIF9vbklyb25SZXF1ZXN0UmVzaXplTm90aWZpY2F0aW9uczogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgdGFyZ2V0ID0gLyoqIEB0eXBlIHshRXZlbnRUYXJnZXR9ICovIChkb20oZXZlbnQpLnJvb3RUYXJnZXQpOwogICAgICAgIGlmICh0YXJnZXQgPT09IHRoaXMpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRhcmdldC5hc3NpZ25QYXJlbnRSZXNpemFibGUodGhpcyk7CiAgICAgICAgdGhpcy5fbm90aWZ5RGVzY2VuZGFudCh0YXJnZXQpOwoKICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgfSwKCiAgICAgIF9wYXJlbnRSZXNpemFibGVDaGFuZ2VkOiBmdW5jdGlvbihwYXJlbnRSZXNpemFibGUpIHsKICAgICAgICBpZiAocGFyZW50UmVzaXphYmxlKSB7CiAgICAgICAgICB3aW5kb3cucmVtb3ZlRXZlbnRMaXN0ZW5lcigncmVzaXplJywgdGhpcy5fYm91bmROb3RpZnlSZXNpemUpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9ub3RpZnlEZXNjZW5kYW50OiBmdW5jdGlvbihkZXNjZW5kYW50KSB7CiAgICAgICAgLy8gTk9URShjZGF0YSk6IEluIElFMTAsIGF0dGFjaGVkIGlzIGZpcmVkIG9uIGNoaWxkcmVuIGZpcnN0LCBzbyBpdCdzCiAgICAgICAgLy8gaW1wb3J0YW50IG5vdCB0byBub3RpZnkgdGhlbSBpZiB0aGUgcGFyZW50IGlzIG5vdCBhdHRhY2hlZCB5ZXQgKG9yCiAgICAgICAgLy8gZWxzZSB0aGV5IHdpbGwgZ2V0IHJlZHVuZGFudGx5IG5vdGlmaWVkIHdoZW4gdGhlIHBhcmVudCBhdHRhY2hlcykuCiAgICAgICAgaWYgKCF0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRoaXMuX25vdGlmeWluZ0Rlc2NlbmRhbnQgPSB0cnVlOwogICAgICAgIGRlc2NlbmRhbnQubm90aWZ5UmVzaXplKCk7CiAgICAgICAgdGhpcy5fbm90aWZ5aW5nRGVzY2VuZGFudCA9IGZhbHNlOwogICAgICB9LAoKICAgICAgX3JlcXVlc3RSZXNpemVOb3RpZmljYXRpb25zOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIXRoaXMuaXNBdHRhY2hlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKGRvY3VtZW50LnJlYWR5U3RhdGUgPT09ICdsb2FkaW5nJykgewogICAgICAgICAgdmFyIF9yZXF1ZXN0UmVzaXplTm90aWZpY2F0aW9ucyA9CiAgICAgICAgICAgICAgdGhpcy5fcmVxdWVzdFJlc2l6ZU5vdGlmaWNhdGlvbnMuYmluZCh0aGlzKTsKICAgICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoCiAgICAgICAgICAgICAgJ3JlYWR5c3RhdGVjaGFuZ2UnLCBmdW5jdGlvbiByZWFkeXN0YXRlY2hhbmdlZCgpIHsKICAgICAgICAgICAgICAgIGRvY3VtZW50LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3JlYWR5c3RhdGVjaGFuZ2UnLCByZWFkeXN0YXRlY2hhbmdlZCk7CiAgICAgICAgICAgICAgICBfcmVxdWVzdFJlc2l6ZU5vdGlmaWNhdGlvbnMoKTsKICAgICAgICAgICAgICB9KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fZmluZFBhcmVudCgpOwoKICAgICAgICAgIGlmICghdGhpcy5fcGFyZW50UmVzaXphYmxlKSB7CiAgICAgICAgICAgIC8vIElmIHRoaXMgcmVzaXphYmxlIGlzIGFuIG9ycGhhbiwgdGVsbCBvdGhlciBvcnBoYW5zIHRvIHRyeSB0byBmaW5kCiAgICAgICAgICAgIC8vIHRoZWlyIHBhcmVudCBhZ2FpbiwgaW4gY2FzZSBpdCdzIHRoaXMgcmVzaXphYmxlLgogICAgICAgICAgICBPUlBIQU5TLmZvckVhY2goZnVuY3Rpb24ob3JwaGFuKSB7CiAgICAgICAgICAgICAgaWYgKG9ycGhhbiAhPT0gdGhpcykgewogICAgICAgICAgICAgICAgb3JwaGFuLl9maW5kUGFyZW50KCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LCB0aGlzKTsKCiAgICAgICAgICAgIHdpbmRvdy5hZGRFdmVudExpc3RlbmVyKCdyZXNpemUnLCB0aGlzLl9ib3VuZE5vdGlmeVJlc2l6ZSk7CiAgICAgICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvLyBJZiB0aGlzIHJlc2l6YWJsZSBoYXMgYSBwYXJlbnQsIHRlbGwgb3RoZXIgY2hpbGQgcmVzaXphYmxlcyBvZgogICAgICAgICAgICAvLyB0aGF0IHBhcmVudCB0byB0cnkgZmluZGluZyB0aGVpciBwYXJlbnQgYWdhaW4sIGluIGNhc2UgaXQncyB0aGlzCiAgICAgICAgICAgIC8vIHJlc2l6YWJsZS4KICAgICAgICAgICAgdGhpcy5fcGFyZW50UmVzaXphYmxlLl9pbnRlcmVzdGVkUmVzaXphYmxlcwogICAgICAgICAgICAgICAgLmZvckVhY2goZnVuY3Rpb24ocmVzaXphYmxlKSB7CiAgICAgICAgICAgICAgICAgIGlmIChyZXNpemFibGUgIT09IHRoaXMpIHsKICAgICAgICAgICAgICAgICAgICByZXNpemFibGUuX2ZpbmRQYXJlbnQoKTsKICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSwgdGhpcyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2ZpbmRQYXJlbnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuYXNzaWduUGFyZW50UmVzaXphYmxlKG51bGwpOwogICAgICAgIHRoaXMuZmlyZSgKICAgICAgICAgICAgJ2lyb24tcmVxdWVzdC1yZXNpemUtbm90aWZpY2F0aW9ucycsCiAgICAgICAgICAgIG51bGwsCiAgICAgICAgICAgIHtub2RlOiB0aGlzLCBidWJibGVzOiB0cnVlLCBjYW5jZWxhYmxlOiB0cnVlfSk7CgogICAgICAgIGlmICghdGhpcy5fcGFyZW50UmVzaXphYmxlKSB7CiAgICAgICAgICBPUlBIQU5TLmFkZCh0aGlzKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgT1JQSEFOUy5kZWxldGUodGhpcyk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIHZhciBJcm9uUmVzaXphYmxlQmVoYXZpb3IkMSA9IC8qI19fUFVSRV9fKi9PYmplY3QuZnJlZXplKHsKICAgICAgICBfX3Byb3RvX186IG51bGwsCiAgICAgICAgSXJvblJlc2l6YWJsZUJlaGF2aW9yOiBJcm9uUmVzaXphYmxlQmVoYXZpb3IKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgYGlyb24tY29sbGFwc2VgIGNyZWF0ZXMgYSBjb2xsYXBzaWJsZSBibG9jayBvZiBjb250ZW50LiAgQnkgZGVmYXVsdCwgdGhlIGNvbnRlbnQKICAgIHdpbGwgYmUgY29sbGFwc2VkLiAgVXNlIGBvcGVuZWRgIG9yIGB0b2dnbGUoKWAgdG8gc2hvdy9oaWRlIHRoZSBjb250ZW50LgoKICAgICAgICA8YnV0dG9uIG9uLWNsaWNrPSJ0b2dnbGUiPnRvZ2dsZSBjb2xsYXBzZTwvYnV0dG9uPgoKICAgICAgICA8aXJvbi1jb2xsYXBzZSBpZD0iY29sbGFwc2UiPgogICAgICAgICAgPGRpdj5Db250ZW50IGdvZXMgaGVyZS4uLjwvZGl2PgogICAgICAgIDwvaXJvbi1jb2xsYXBzZT4KCiAgICAgICAgLi4uCgogICAgICAgIHRvZ2dsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLiQuY29sbGFwc2UudG9nZ2xlKCk7CiAgICAgICAgfQoKICAgIGBpcm9uLWNvbGxhcHNlYCBhZGp1c3RzIHRoZSBtYXgtaGVpZ2h0L21heC13aWR0aCBvZiB0aGUgY29sbGFwc2libGUgZWxlbWVudCB0bwogICAgc2hvdy9oaWRlIHRoZSBjb250ZW50LiAgU28gYXZvaWQgcHV0dGluZyBwYWRkaW5nL21hcmdpbi9ib3JkZXIgb24gdGhlCiAgICBjb2xsYXBzaWJsZSBkaXJlY3RseSwgYW5kIGluc3RlYWQgcHV0IGEgZGl2IGluc2lkZSBhbmQgc3R5bGUgdGhhdC4KCiAgICAgICAgPHN0eWxlPgogICAgICAgICAgLmNvbGxhcHNlLWNvbnRlbnQgewogICAgICAgICAgICBwYWRkaW5nOiAxNXB4OwogICAgICAgICAgICBib3JkZXI6IDFweCBzb2xpZCAjZGVkZWRlOwogICAgICAgICAgfQogICAgICAgIDwvc3R5bGU+CgogICAgICAgIDxpcm9uLWNvbGxhcHNlPgogICAgICAgICAgPGRpdiBjbGFzcz0iY29sbGFwc2UtY29udGVudCI+CiAgICAgICAgICAgIDxkaXY+Q29udGVudCBnb2VzIGhlcmUuLi48L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvaXJvbi1jb2xsYXBzZT4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLWlyb24tY29sbGFwc2UtdHJhbnNpdGlvbi1kdXJhdGlvbmAgfCBBbmltYXRpb24gdHJhbnNpdGlvbiBkdXJhdGlvbiB8IGAzMDBtc2AKCiAgICBAZ3JvdXAgSXJvbiBFbGVtZW50cwogICAgQGhlcm8gaGVyby5zdmcKICAgIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgQGVsZW1lbnQgaXJvbi1jb2xsYXBzZQogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICB0cmFuc2l0aW9uLWR1cmF0aW9uOiB2YXIoLS1pcm9uLWNvbGxhcHNlLXRyYW5zaXRpb24tZHVyYXRpb24sIDMwMG1zKTsKICAgICAgICAvKiBTYWZhcmkgMTAgbmVlZHMgdGhpcyBwcm9wZXJ0eSBwcmVmaXhlZCB0byBjb3JyZWN0bHkgYXBwbHkgdGhlIGN1c3RvbSBwcm9wZXJ0eSAqLwogICAgICAgIC13ZWJraXQtdHJhbnNpdGlvbi1kdXJhdGlvbjogdmFyKC0taXJvbi1jb2xsYXBzZS10cmFuc2l0aW9uLWR1cmF0aW9uLCAzMDBtcyk7CiAgICAgICAgb3ZlcmZsb3c6IHZpc2libGU7CiAgICAgIH0KCiAgICAgIDpob3N0KC5pcm9uLWNvbGxhcHNlLWNsb3NlZCkgewogICAgICAgIGRpc3BsYXk6IG5vbmU7CiAgICAgIH0KCiAgICAgIDpob3N0KDpub3QoLmlyb24tY29sbGFwc2Utb3BlbmVkKSkgewogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgLAoKICAgICAgaXM6ICdpcm9uLWNvbGxhcHNlJywKICAgICAgYmVoYXZpb3JzOiBbSXJvblJlc2l6YWJsZUJlaGF2aW9yXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIG9yaWVudGF0aW9uIGlzIGhvcml6b250YWw7IG90aGVyd2lzZSBpcyB2ZXJ0aWNhbC4KICAgICAgICAgKgogICAgICAgICAqIEBhdHRyaWJ1dGUgaG9yaXpvbnRhbAogICAgICAgICAqLwogICAgICAgIGhvcml6b250YWw6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG9ic2VydmVyOiAnX2hvcml6b250YWxDaGFuZ2VkJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCBvcGVuZWQgdG8gdHJ1ZSB0byBzaG93IHRoZSBjb2xsYXBzZSBlbGVtZW50IGFuZCB0byBmYWxzZSB0byBoaWRlIGl0LgogICAgICAgICAqCiAgICAgICAgICogQGF0dHJpYnV0ZSBvcGVuZWQKICAgICAgICAgKi8KICAgICAgICBvcGVuZWQ6CiAgICAgICAgICAgIHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG5vdGlmeTogdHJ1ZSwgb2JzZXJ2ZXI6ICdfb3BlbmVkQ2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBXaGVuIHRydWUsIHRoZSBlbGVtZW50IGlzIHRyYW5zaXRpb25pbmcgaXRzIG9wZW5lZCBzdGF0ZS4gV2hlbiBmYWxzZSwKICAgICAgICAgKiB0aGUgZWxlbWVudCBoYXMgZmluaXNoZWQgb3BlbmluZy9jbG9zaW5nLgogICAgICAgICAqCiAgICAgICAgICogQGF0dHJpYnV0ZSB0cmFuc2l0aW9uaW5nCiAgICAgICAgICovCiAgICAgICAgdHJhbnNpdGlvbmluZzoge3R5cGU6IEJvb2xlYW4sIG5vdGlmeTogdHJ1ZSwgcmVhZE9ubHk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgbm9BbmltYXRpb24gdG8gdHJ1ZSB0byBkaXNhYmxlIGFuaW1hdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAYXR0cmlidXRlIG5vQW5pbWF0aW9uCiAgICAgICAgICovCiAgICAgICAgbm9BbmltYXRpb246IHt0eXBlOiBCb29sZWFufSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU3RvcmVzIHRoZSBkZXNpcmVkIHNpemUgb2YgdGhlIGNvbGxhcHNlIGJvZHkuCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKi8KICAgICAgICBfZGVzaXJlZFNpemU6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnJ30KICAgICAgfSwKCiAgICAgIGdldCBkaW1lbnNpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaG9yaXpvbnRhbCA/ICd3aWR0aCcgOiAnaGVpZ2h0JzsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBgbWF4V2lkdGhgIG9yIGBtYXhIZWlnaHRgLgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgZ2V0IF9kaW1lbnNpb25NYXgoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaG9yaXpvbnRhbCA/ICdtYXhXaWR0aCcgOiAnbWF4SGVpZ2h0JzsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBgbWF4LXdpZHRoYCBvciBgbWF4LWhlaWdodGAuCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBnZXQgX2RpbWVuc2lvbk1heENzcygpIHsKICAgICAgICByZXR1cm4gdGhpcy5ob3Jpem9udGFsID8gJ21heC13aWR0aCcgOiAnbWF4LWhlaWdodCc7CiAgICAgIH0sCgogICAgICBob3N0QXR0cmlidXRlczogewogICAgICAgIHJvbGU6ICdncm91cCcsCiAgICAgICAgJ2FyaWEtaGlkZGVuJzogJ3RydWUnLAogICAgICB9LAoKICAgICAgbGlzdGVuZXJzOiB7dHJhbnNpdGlvbmVuZDogJ19vblRyYW5zaXRpb25FbmQnfSwKCiAgICAgIC8qKgogICAgICAgKiBUb2dnbGUgdGhlIG9wZW5lZCBzdGF0ZS4KICAgICAgICoKICAgICAgICogQG1ldGhvZCB0b2dnbGUKICAgICAgICovCiAgICAgIHRvZ2dsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5vcGVuZWQgPSAhdGhpcy5vcGVuZWQ7CiAgICAgIH0sCgogICAgICBzaG93OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLm9wZW5lZCA9IHRydWU7CiAgICAgIH0sCgogICAgICBoaWRlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLm9wZW5lZCA9IGZhbHNlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZXMgdGhlIHNpemUgb2YgdGhlIGVsZW1lbnQuCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBzaXplIFRoZSBuZXcgdmFsdWUgZm9yIGBtYXhXaWR0aGAvYG1heEhlaWdodGAgYXMgY3NzIHByb3BlcnR5IHZhbHVlLCB1c3VhbGx5IGBhdXRvYCBvciBgMHB4YC4KICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gYW5pbWF0ZWQgaWYgYHRydWVgIHVwZGF0ZXMgdGhlIHNpemUgd2l0aCBhbiBhbmltYXRpb24sIG90aGVyd2lzZSB3aXRob3V0LgogICAgICAgKi8KICAgICAgdXBkYXRlU2l6ZTogZnVuY3Rpb24oc2l6ZSwgYW5pbWF0ZWQpIHsKICAgICAgICAvLyBDb25zaWRlciAnYXV0bycgYXMgJycsIHRvIHRha2UgZnVsbCBzaXplLgogICAgICAgIHNpemUgPSBzaXplID09PSAnYXV0bycgPyAnJyA6IHNpemU7CgogICAgICAgIHZhciB3aWxsQW5pbWF0ZSA9IGFuaW1hdGVkICYmICF0aGlzLm5vQW5pbWF0aW9uICYmIHRoaXMuaXNBdHRhY2hlZCAmJgogICAgICAgICAgICB0aGlzLl9kZXNpcmVkU2l6ZSAhPT0gc2l6ZTsKCiAgICAgICAgdGhpcy5fZGVzaXJlZFNpemUgPSBzaXplOwoKICAgICAgICB0aGlzLl91cGRhdGVUcmFuc2l0aW9uKGZhbHNlKTsKICAgICAgICAvLyBJZiB3ZSBjYW4gYW5pbWF0ZSwgbXVzdCBkbyBzb21lIHByZXAgd29yay4KICAgICAgICBpZiAod2lsbEFuaW1hdGUpIHsKICAgICAgICAgIC8vIEFuaW1hdGlvbiB3aWxsIHN0YXJ0IGF0IHRoZSBjdXJyZW50IHNpemUuCiAgICAgICAgICB2YXIgc3RhcnRTaXplID0gdGhpcy5fY2FsY1NpemUoKTsKICAgICAgICAgIC8vIEZvciBgYXV0b2Agd2UgbXVzdCBjYWxjdWxhdGUgd2hhdCBpcyB0aGUgZmluYWwgc2l6ZSBmb3IgdGhlIGFuaW1hdGlvbi4KICAgICAgICAgIC8vIEFmdGVyIHRoZSB0cmFuc2l0aW9uIGlzIGRvbmUsIF90cmFuc2l0aW9uRW5kIHdpbGwgc2V0IHRoZSBzaXplIGJhY2sgdG8KICAgICAgICAgIC8vIGBhdXRvYC4KICAgICAgICAgIGlmIChzaXplID09PSAnJykgewogICAgICAgICAgICB0aGlzLnN0eWxlW3RoaXMuX2RpbWVuc2lvbk1heF0gPSAnJzsKICAgICAgICAgICAgc2l6ZSA9IHRoaXMuX2NhbGNTaXplKCk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBHbyB0byBzdGFydFNpemUgd2l0aG91dCBhbmltYXRpb24uCiAgICAgICAgICB0aGlzLnN0eWxlW3RoaXMuX2RpbWVuc2lvbk1heF0gPSBzdGFydFNpemU7CiAgICAgICAgICAvLyBGb3JjZSBsYXlvdXQgdG8gZW5zdXJlIHRyYW5zaXRpb24gd2lsbCBnby4gU2V0IHNjcm9sbFRvcCB0byBpdHNlbGYKICAgICAgICAgIC8vIHNvIHRoYXQgY29tcGlsZXJzIHdvbid0IHJlbW92ZSBpdC4KICAgICAgICAgIHRoaXMuc2Nyb2xsVG9wID0gdGhpcy5zY3JvbGxUb3A7CiAgICAgICAgICAvLyBFbmFibGUgYW5pbWF0aW9uLgogICAgICAgICAgdGhpcy5fdXBkYXRlVHJhbnNpdGlvbih0cnVlKTsKICAgICAgICAgIC8vIElmIGZpbmFsIHNpemUgaXMgdGhlIHNhbWUgYXMgc3RhcnRTaXplIGl0IHdpbGwgbm90IGFuaW1hdGUuCiAgICAgICAgICB3aWxsQW5pbWF0ZSA9IChzaXplICE9PSBzdGFydFNpemUpOwogICAgICAgIH0KICAgICAgICAvLyBTZXQgdGhlIGZpbmFsIHNpemUuCiAgICAgICAgdGhpcy5zdHlsZVt0aGlzLl9kaW1lbnNpb25NYXhdID0gc2l6ZTsKICAgICAgICAvLyBJZiBpdCB3b24ndCBhbmltYXRlLCBjYWxsIHRyYW5zaXRpb25FbmQgdG8gc2V0IGNvcnJlY3QgY2xhc3Nlcy4KICAgICAgICBpZiAoIXdpbGxBbmltYXRlKSB7CiAgICAgICAgICB0aGlzLl90cmFuc2l0aW9uRW5kKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIGVuYWJsZVRyYW5zaXRpb24oKSBpcyBkZXByZWNhdGVkLCBidXQgbGVmdCBvdmVyIHNvIGl0IGRvZXNuJ3QgYnJlYWsKICAgICAgICogZXhpc3RpbmcgY29kZS4gUGxlYXNlIHVzZSBgbm9BbmltYXRpb25gIHByb3BlcnR5IGluc3RlYWQuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgZW5hYmxlVHJhbnNpdGlvbgogICAgICAgKiBAZGVwcmVjYXRlZCBzaW5jZSB2ZXJzaW9uIDEuMC40CiAgICAgICAqLwogICAgICBlbmFibGVUcmFuc2l0aW9uOiBmdW5jdGlvbihlbmFibGVkKSB7CiAgICAgICAgQmFzZS5fd2FybigKICAgICAgICAgICAgJ2BlbmFibGVUcmFuc2l0aW9uKClgIGlzIGRlcHJlY2F0ZWQsIHVzZSBgbm9BbmltYXRpb25gIGluc3RlYWQuJyk7CiAgICAgICAgdGhpcy5ub0FuaW1hdGlvbiA9ICFlbmFibGVkOwogICAgICB9LAoKICAgICAgX3VwZGF0ZVRyYW5zaXRpb246IGZ1bmN0aW9uKGVuYWJsZWQpIHsKICAgICAgICB0aGlzLnN0eWxlLnRyYW5zaXRpb25EdXJhdGlvbiA9IChlbmFibGVkICYmICF0aGlzLm5vQW5pbWF0aW9uKSA/ICcnIDogJzBzJzsKICAgICAgfSwKCiAgICAgIF9ob3Jpem9udGFsQ2hhbmdlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS50cmFuc2l0aW9uUHJvcGVydHkgPSB0aGlzLl9kaW1lbnNpb25NYXhDc3M7CiAgICAgICAgdmFyIG90aGVyRGltZW5zaW9uID0KICAgICAgICAgICAgdGhpcy5fZGltZW5zaW9uTWF4ID09PSAnbWF4V2lkdGgnID8gJ21heEhlaWdodCcgOiAnbWF4V2lkdGgnOwogICAgICAgIHRoaXMuc3R5bGVbb3RoZXJEaW1lbnNpb25dID0gJyc7CiAgICAgICAgdGhpcy51cGRhdGVTaXplKHRoaXMub3BlbmVkID8gJ2F1dG8nIDogJzBweCcsIGZhbHNlKTsKICAgICAgfSwKCiAgICAgIF9vcGVuZWRDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1oaWRkZW4nLCAhdGhpcy5vcGVuZWQpOwoKICAgICAgICB0aGlzLl9zZXRUcmFuc2l0aW9uaW5nKHRydWUpOwogICAgICAgIHRoaXMudG9nZ2xlQ2xhc3MoJ2lyb24tY29sbGFwc2UtY2xvc2VkJywgZmFsc2UpOwogICAgICAgIHRoaXMudG9nZ2xlQ2xhc3MoJ2lyb24tY29sbGFwc2Utb3BlbmVkJywgZmFsc2UpOwogICAgICAgIHRoaXMudXBkYXRlU2l6ZSh0aGlzLm9wZW5lZCA/ICdhdXRvJyA6ICcwcHgnLCB0cnVlKTsKCiAgICAgICAgLy8gRm9jdXMgdGhlIGN1cnJlbnQgY29sbGFwc2UuCiAgICAgICAgaWYgKHRoaXMub3BlbmVkKSB7CiAgICAgICAgICB0aGlzLmZvY3VzKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3RyYW5zaXRpb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGVbdGhpcy5fZGltZW5zaW9uTWF4XSA9IHRoaXMuX2Rlc2lyZWRTaXplOwogICAgICAgIHRoaXMudG9nZ2xlQ2xhc3MoJ2lyb24tY29sbGFwc2UtY2xvc2VkJywgIXRoaXMub3BlbmVkKTsKICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdpcm9uLWNvbGxhcHNlLW9wZW5lZCcsIHRoaXMub3BlbmVkKTsKICAgICAgICB0aGlzLl91cGRhdGVUcmFuc2l0aW9uKGZhbHNlKTsKICAgICAgICB0aGlzLm5vdGlmeVJlc2l6ZSgpOwogICAgICAgIHRoaXMuX3NldFRyYW5zaXRpb25pbmcoZmFsc2UpOwogICAgICB9LAoKICAgICAgX29uVHJhbnNpdGlvbkVuZDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoZG9tKGV2ZW50KS5yb290VGFyZ2V0ID09PSB0aGlzKSB7CiAgICAgICAgICB0aGlzLl90cmFuc2l0aW9uRW5kKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2NhbGNTaXplOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKVt0aGlzLmRpbWVuc2lvbl0gKyAncHgnOwogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKgogICAgQSBzZXQgb2YgbGF5b3V0IGNsYXNzZXMgdGhhdCBsZXQgeW91IHNwZWNpZnkgbGF5b3V0IHByb3BlcnRpZXMgZGlyZWN0bHkgaW4KICAgIG1hcmt1cC4gWW91IG11c3QgaW5jbHVkZSB0aGlzIGZpbGUgaW4gZXZlcnkgZWxlbWVudCB0aGF0IG5lZWRzIHRvIHVzZSB0aGVtLgoKICAgIFNhbXBsZSB1c2U6CgogICAgICAgIGltcG9ydCAnQHBvbHltZXIvaXJvbi1mbGV4LWxheW91dC9pcm9uLWZsZXgtbGF5b3V0LWNsYXNzZXMuanMnOwoKICAgICAgICBjb25zdCB0ZW1wbGF0ZSA9IGh0bWxgCiAgICAgICAgICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSIgaW5jbHVkZT0iaXJvbi1mbGV4IGlyb24tZmxleC1hbGlnbm1lbnQiPjwvc3R5bGU+CiAgICAgICAgICA8c3R5bGU+CiAgICAgICAgICAgIC50ZXN0IHsgd2lkdGg6IDEwMHB4OyB9CiAgICAgICAgICA8L3N0eWxlPgogICAgICAgICAgPGRpdiBjbGFzcz0ibGF5b3V0IGhvcml6b250YWwgY2VudGVyLWNlbnRlciI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9InRlc3QiPmhvcml6b250YWwgbGF5b3V0IGNlbnRlciBhbGlnbm1lbnQ8L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIGA7CiAgICAgICAgZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZCh0ZW1wbGF0ZS5jb250ZW50KTsKCiAgICBUaGUgZm9sbG93aW5nIGltcG9ydHMgYXJlIGF2YWlsYWJsZToKICAgICAtIGlyb24tZmxleAogICAgIC0gaXJvbi1mbGV4LXJldmVyc2UKICAgICAtIGlyb24tZmxleC1hbGlnbm1lbnQKICAgICAtIGlyb24tZmxleC1mYWN0b3JzCiAgICAgLSBpcm9uLXBvc2l0aW9uaW5nCiAgICAqLwoKICAgIGNvbnN0IHRlbXBsYXRlID0gaHRtbGAKLyogTW9zdCBjb21tb24gdXNlZCBmbGV4IHN0eWxlcyovCjxkb20tbW9kdWxlIGlkPSJpcm9uLWZsZXgiPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgLmxheW91dC5ob3Jpem9udGFsLAogICAgICAubGF5b3V0LnZlcnRpY2FsIHsKICAgICAgICBkaXNwbGF5OiAtbXMtZmxleGJveDsKICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgfQoKICAgICAgLmxheW91dC5pbmxpbmUgewogICAgICAgIGRpc3BsYXk6IC1tcy1pbmxpbmUtZmxleGJveDsKICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWlubGluZS1mbGV4OwogICAgICAgIGRpc3BsYXk6IGlubGluZS1mbGV4OwogICAgICB9CgogICAgICAubGF5b3V0Lmhvcml6b250YWwgewogICAgICAgIC1tcy1mbGV4LWRpcmVjdGlvbjogcm93OwogICAgICAgIC13ZWJraXQtZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogICAgICB9CgogICAgICAubGF5b3V0LnZlcnRpY2FsIHsKICAgICAgICAtbXMtZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICAtd2Via2l0LWZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgfQoKICAgICAgLmxheW91dC53cmFwIHsKICAgICAgICAtbXMtZmxleC13cmFwOiB3cmFwOwogICAgICAgIC13ZWJraXQtZmxleC13cmFwOiB3cmFwOwogICAgICAgIGZsZXgtd3JhcDogd3JhcDsKICAgICAgfQoKICAgICAgLmxheW91dC5uby13cmFwIHsKICAgICAgICAtbXMtZmxleC13cmFwOiBub3dyYXA7CiAgICAgICAgLXdlYmtpdC1mbGV4LXdyYXA6IG5vd3JhcDsKICAgICAgICBmbGV4LXdyYXA6IG5vd3JhcDsKICAgICAgfQoKICAgICAgLmxheW91dC5jZW50ZXIsCiAgICAgIC5sYXlvdXQuY2VudGVyLWNlbnRlciB7CiAgICAgICAgLW1zLWZsZXgtYWxpZ246IGNlbnRlcjsKICAgICAgICAtd2Via2l0LWFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgfQoKICAgICAgLmxheW91dC5jZW50ZXItanVzdGlmaWVkLAogICAgICAubGF5b3V0LmNlbnRlci1jZW50ZXIgewogICAgICAgIC1tcy1mbGV4LXBhY2s6IGNlbnRlcjsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogY2VudGVyOwogICAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyOwogICAgICB9CgogICAgICAuZmxleCB7CiAgICAgICAgLW1zLWZsZXg6IDEgMSAwLjAwMDAwMDAwMXB4OwogICAgICAgIC13ZWJraXQtZmxleDogMTsKICAgICAgICBmbGV4OiAxOwogICAgICAgIC13ZWJraXQtZmxleC1iYXNpczogMC4wMDAwMDAwMDFweDsKICAgICAgICBmbGV4LWJhc2lzOiAwLjAwMDAwMDAwMXB4OwogICAgICB9CgogICAgICAuZmxleC1hdXRvIHsKICAgICAgICAtbXMtZmxleDogMSAxIGF1dG87CiAgICAgICAgLXdlYmtpdC1mbGV4OiAxIDEgYXV0bzsKICAgICAgICBmbGV4OiAxIDEgYXV0bzsKICAgICAgfQoKICAgICAgLmZsZXgtbm9uZSB7CiAgICAgICAgLW1zLWZsZXg6IG5vbmU7CiAgICAgICAgLXdlYmtpdC1mbGV4OiBub25lOwogICAgICAgIGZsZXg6IG5vbmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPgovKiBCYXNpYyBmbGV4Ym94IHJldmVyc2Ugc3R5bGVzICovCjxkb20tbW9kdWxlIGlkPSJpcm9uLWZsZXgtcmV2ZXJzZSI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICAubGF5b3V0Lmhvcml6b250YWwtcmV2ZXJzZSwKICAgICAgLmxheW91dC52ZXJ0aWNhbC1yZXZlcnNlIHsKICAgICAgICBkaXNwbGF5OiAtbXMtZmxleGJveDsKICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgfQoKICAgICAgLmxheW91dC5ob3Jpem9udGFsLXJldmVyc2UgewogICAgICAgIC1tcy1mbGV4LWRpcmVjdGlvbjogcm93LXJldmVyc2U7CiAgICAgICAgLXdlYmtpdC1mbGV4LWRpcmVjdGlvbjogcm93LXJldmVyc2U7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IHJvdy1yZXZlcnNlOwogICAgICB9CgogICAgICAubGF5b3V0LnZlcnRpY2FsLXJldmVyc2UgewogICAgICAgIC1tcy1mbGV4LWRpcmVjdGlvbjogY29sdW1uLXJldmVyc2U7CiAgICAgICAgLXdlYmtpdC1mbGV4LWRpcmVjdGlvbjogY29sdW1uLXJldmVyc2U7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbi1yZXZlcnNlOwogICAgICB9CgogICAgICAubGF5b3V0LndyYXAtcmV2ZXJzZSB7CiAgICAgICAgLW1zLWZsZXgtd3JhcDogd3JhcC1yZXZlcnNlOwogICAgICAgIC13ZWJraXQtZmxleC13cmFwOiB3cmFwLXJldmVyc2U7CiAgICAgICAgZmxleC13cmFwOiB3cmFwLXJldmVyc2U7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPgovKiBGbGV4Ym94IGFsaWdubWVudCAqLwo8ZG9tLW1vZHVsZSBpZD0iaXJvbi1mbGV4LWFsaWdubWVudCI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICAvKioKICAgICAgICogQWxpZ25tZW50IGluIGNyb3NzIGF4aXMuCiAgICAgICAqLwogICAgICAubGF5b3V0LnN0YXJ0IHsKICAgICAgICAtbXMtZmxleC1hbGlnbjogc3RhcnQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogZmxleC1zdGFydDsKICAgICAgICBhbGlnbi1pdGVtczogZmxleC1zdGFydDsKICAgICAgfQoKICAgICAgLmxheW91dC5jZW50ZXIsCiAgICAgIC5sYXlvdXQuY2VudGVyLWNlbnRlciB7CiAgICAgICAgLW1zLWZsZXgtYWxpZ246IGNlbnRlcjsKICAgICAgICAtd2Via2l0LWFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgfQoKICAgICAgLmxheW91dC5lbmQgewogICAgICAgIC1tcy1mbGV4LWFsaWduOiBlbmQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogZmxleC1lbmQ7CiAgICAgICAgYWxpZ24taXRlbXM6IGZsZXgtZW5kOwogICAgICB9CgogICAgICAubGF5b3V0LmJhc2VsaW5lIHsKICAgICAgICAtbXMtZmxleC1hbGlnbjogYmFzZWxpbmU7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogYmFzZWxpbmU7CiAgICAgICAgYWxpZ24taXRlbXM6IGJhc2VsaW5lOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQWxpZ25tZW50IGluIG1haW4gYXhpcy4KICAgICAgICovCiAgICAgIC5sYXlvdXQuc3RhcnQtanVzdGlmaWVkIHsKICAgICAgICAtbXMtZmxleC1wYWNrOiBzdGFydDsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogZmxleC1zdGFydDsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGZsZXgtc3RhcnQ7CiAgICAgIH0KCiAgICAgIC5sYXlvdXQuY2VudGVyLWp1c3RpZmllZCwKICAgICAgLmxheW91dC5jZW50ZXItY2VudGVyIHsKICAgICAgICAtbXMtZmxleC1wYWNrOiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1qdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgfQoKICAgICAgLmxheW91dC5lbmQtanVzdGlmaWVkIHsKICAgICAgICAtbXMtZmxleC1wYWNrOiBlbmQ7CiAgICAgICAgLXdlYmtpdC1qdXN0aWZ5LWNvbnRlbnQ6IGZsZXgtZW5kOwogICAgICAgIGp1c3RpZnktY29udGVudDogZmxleC1lbmQ7CiAgICAgIH0KCiAgICAgIC5sYXlvdXQuYXJvdW5kLWp1c3RpZmllZCB7CiAgICAgICAgLW1zLWZsZXgtcGFjazogZGlzdHJpYnV0ZTsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kOwogICAgICAgIGp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kOwogICAgICB9CgogICAgICAubGF5b3V0Lmp1c3RpZmllZCB7CiAgICAgICAgLW1zLWZsZXgtcGFjazoganVzdGlmeTsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBTZWxmIGFsaWdubWVudC4KICAgICAgICovCiAgICAgIC5zZWxmLXN0YXJ0IHsKICAgICAgICAtbXMtYWxpZ24tc2VsZjogZmxleC1zdGFydDsKICAgICAgICAtd2Via2l0LWFsaWduLXNlbGY6IGZsZXgtc3RhcnQ7CiAgICAgICAgYWxpZ24tc2VsZjogZmxleC1zdGFydDsKICAgICAgfQoKICAgICAgLnNlbGYtY2VudGVyIHsKICAgICAgICAtbXMtYWxpZ24tc2VsZjogY2VudGVyOwogICAgICAgIC13ZWJraXQtYWxpZ24tc2VsZjogY2VudGVyOwogICAgICAgIGFsaWduLXNlbGY6IGNlbnRlcjsKICAgICAgfQoKICAgICAgLnNlbGYtZW5kIHsKICAgICAgICAtbXMtYWxpZ24tc2VsZjogZmxleC1lbmQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBmbGV4LWVuZDsKICAgICAgICBhbGlnbi1zZWxmOiBmbGV4LWVuZDsKICAgICAgfQoKICAgICAgLnNlbGYtc3RyZXRjaCB7CiAgICAgICAgLW1zLWFsaWduLXNlbGY6IHN0cmV0Y2g7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBzdHJldGNoOwogICAgICAgIGFsaWduLXNlbGY6IHN0cmV0Y2g7CiAgICAgIH0KCiAgICAgIC5zZWxmLWJhc2VsaW5lIHsKICAgICAgICAtbXMtYWxpZ24tc2VsZjogYmFzZWxpbmU7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBiYXNlbGluZTsKICAgICAgICBhbGlnbi1zZWxmOiBiYXNlbGluZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIG11bHRpLWxpbmUgYWxpZ25tZW50IGluIG1haW4gYXhpcy4KICAgICAgICovCiAgICAgIC5sYXlvdXQuc3RhcnQtYWxpZ25lZCB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBzdGFydDsgIC8qIElFMTAgKi8KICAgICAgICAtbXMtYWxpZ24tY29udGVudDogZmxleC1zdGFydDsKICAgICAgICAtd2Via2l0LWFsaWduLWNvbnRlbnQ6IGZsZXgtc3RhcnQ7CiAgICAgICAgYWxpZ24tY29udGVudDogZmxleC1zdGFydDsKICAgICAgfQoKICAgICAgLmxheW91dC5lbmQtYWxpZ25lZCB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBlbmQ7ICAvKiBJRTEwICovCiAgICAgICAgLW1zLWFsaWduLWNvbnRlbnQ6IGZsZXgtZW5kOwogICAgICAgIC13ZWJraXQtYWxpZ24tY29udGVudDogZmxleC1lbmQ7CiAgICAgICAgYWxpZ24tY29udGVudDogZmxleC1lbmQ7CiAgICAgIH0KCiAgICAgIC5sYXlvdXQuY2VudGVyLWFsaWduZWQgewogICAgICAgIC1tcy1mbGV4LWxpbmUtcGFjazogY2VudGVyOyAgLyogSUUxMCAqLwogICAgICAgIC1tcy1hbGlnbi1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgYWxpZ24tY29udGVudDogY2VudGVyOwogICAgICB9CgogICAgICAubGF5b3V0LmJldHdlZW4tYWxpZ25lZCB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBqdXN0aWZ5OyAgLyogSUUxMCAqLwogICAgICAgIC1tcy1hbGlnbi1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICAgIC13ZWJraXQtYWxpZ24tY29udGVudDogc3BhY2UtYmV0d2VlbjsKICAgICAgICBhbGlnbi1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICB9CgogICAgICAubGF5b3V0LmFyb3VuZC1hbGlnbmVkIHsKICAgICAgICAtbXMtZmxleC1saW5lLXBhY2s6IGRpc3RyaWJ1dGU7ICAvKiBJRTEwICovCiAgICAgICAgLW1zLWFsaWduLWNvbnRlbnQ6IHNwYWNlLWFyb3VuZDsKICAgICAgICAtd2Via2l0LWFsaWduLWNvbnRlbnQ6IHNwYWNlLWFyb3VuZDsKICAgICAgICBhbGlnbi1jb250ZW50OiBzcGFjZS1hcm91bmQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPgovKiBOb24tZmxleGJveCBwb3NpdGlvbmluZyBoZWxwZXIgc3R5bGVzICovCjxkb20tbW9kdWxlIGlkPSJpcm9uLWZsZXgtZmFjdG9ycyI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICAuZmxleCwKICAgICAgLmZsZXgtMSB7CiAgICAgICAgLW1zLWZsZXg6IDEgMSAwLjAwMDAwMDAwMXB4OwogICAgICAgIC13ZWJraXQtZmxleDogMTsKICAgICAgICBmbGV4OiAxOwogICAgICAgIC13ZWJraXQtZmxleC1iYXNpczogMC4wMDAwMDAwMDFweDsKICAgICAgICBmbGV4LWJhc2lzOiAwLjAwMDAwMDAwMXB4OwogICAgICB9CgogICAgICAuZmxleC0yIHsKICAgICAgICAtbXMtZmxleDogMjsKICAgICAgICAtd2Via2l0LWZsZXg6IDI7CiAgICAgICAgZmxleDogMjsKICAgICAgfQoKICAgICAgLmZsZXgtMyB7CiAgICAgICAgLW1zLWZsZXg6IDM7CiAgICAgICAgLXdlYmtpdC1mbGV4OiAzOwogICAgICAgIGZsZXg6IDM7CiAgICAgIH0KCiAgICAgIC5mbGV4LTQgewogICAgICAgIC1tcy1mbGV4OiA0OwogICAgICAgIC13ZWJraXQtZmxleDogNDsKICAgICAgICBmbGV4OiA0OwogICAgICB9CgogICAgICAuZmxleC01IHsKICAgICAgICAtbXMtZmxleDogNTsKICAgICAgICAtd2Via2l0LWZsZXg6IDU7CiAgICAgICAgZmxleDogNTsKICAgICAgfQoKICAgICAgLmZsZXgtNiB7CiAgICAgICAgLW1zLWZsZXg6IDY7CiAgICAgICAgLXdlYmtpdC1mbGV4OiA2OwogICAgICAgIGZsZXg6IDY7CiAgICAgIH0KCiAgICAgIC5mbGV4LTcgewogICAgICAgIC1tcy1mbGV4OiA3OwogICAgICAgIC13ZWJraXQtZmxleDogNzsKICAgICAgICBmbGV4OiA3OwogICAgICB9CgogICAgICAuZmxleC04IHsKICAgICAgICAtbXMtZmxleDogODsKICAgICAgICAtd2Via2l0LWZsZXg6IDg7CiAgICAgICAgZmxleDogODsKICAgICAgfQoKICAgICAgLmZsZXgtOSB7CiAgICAgICAgLW1zLWZsZXg6IDk7CiAgICAgICAgLXdlYmtpdC1mbGV4OiA5OwogICAgICAgIGZsZXg6IDk7CiAgICAgIH0KCiAgICAgIC5mbGV4LTEwIHsKICAgICAgICAtbXMtZmxleDogMTA7CiAgICAgICAgLXdlYmtpdC1mbGV4OiAxMDsKICAgICAgICBmbGV4OiAxMDsKICAgICAgfQoKICAgICAgLmZsZXgtMTEgewogICAgICAgIC1tcy1mbGV4OiAxMTsKICAgICAgICAtd2Via2l0LWZsZXg6IDExOwogICAgICAgIGZsZXg6IDExOwogICAgICB9CgogICAgICAuZmxleC0xMiB7CiAgICAgICAgLW1zLWZsZXg6IDEyOwogICAgICAgIC13ZWJraXQtZmxleDogMTI7CiAgICAgICAgZmxleDogMTI7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPgo8ZG9tLW1vZHVsZSBpZD0iaXJvbi1wb3NpdGlvbmluZyI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICAuYmxvY2sgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CgogICAgICBbaGlkZGVuXSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICAuaW52aXNpYmxlIHsKICAgICAgICB2aXNpYmlsaXR5OiBoaWRkZW4gIWltcG9ydGFudDsKICAgICAgfQoKICAgICAgLnJlbGF0aXZlIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgIC5maXQgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgYm90dG9tOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgIH0KCiAgICAgIGJvZHkuZnVsbGJsZWVkIHsKICAgICAgICBtYXJnaW46IDA7CiAgICAgICAgaGVpZ2h0OiAxMDB2aDsKICAgICAgfQoKICAgICAgLnNjcm9sbCB7CiAgICAgICAgLXdlYmtpdC1vdmVyZmxvdy1zY3JvbGxpbmc6IHRvdWNoOwogICAgICAgIG92ZXJmbG93OiBhdXRvOwogICAgICB9CgogICAgICAvKiBmaXhlZCBwb3NpdGlvbiAqLwogICAgICAuZml4ZWQtYm90dG9tLAogICAgICAuZml4ZWQtbGVmdCwKICAgICAgLmZpeGVkLXJpZ2h0LAogICAgICAuZml4ZWQtdG9wIHsKICAgICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICAgIH0KCiAgICAgIC5maXhlZC10b3AgewogICAgICAgIHRvcDogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICB9CgogICAgICAuZml4ZWQtcmlnaHQgewogICAgICAgIHRvcDogMDsKICAgICAgICByaWdodDogMDsKICAgICAgICBib3R0b206IDA7CiAgICAgIH0KCiAgICAgIC5maXhlZC1ib3R0b20gewogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICB9CgogICAgICAuZml4ZWQtbGVmdCB7CiAgICAgICAgdG9wOiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICB9CiAgICA8L3N0eWxlPgogIDwvdGVtcGxhdGU+CjwvZG9tLW1vZHVsZT4KYDsKICAgIHRlbXBsYXRlLnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUuY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBUaGUgYDxpcm9uLWZsZXgtbGF5b3V0PmAgY29tcG9uZW50IHByb3ZpZGVzIHNpbXBsZSB3YXlzIHRvIHVzZQogICAgW0NTUyBmbGV4aWJsZSBib3gKICAgIGxheW91dF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvR3VpZGUvQ1NTL0ZsZXhpYmxlX2JveGVzKSwKICAgIGFsc28ga25vd24gYXMgZmxleGJveC4gTm90ZSB0aGF0IHRoaXMgaXMgYW4gb2xkIGVsZW1lbnQsIHRoYXQgd2FzIHdyaXR0ZW4KICAgIGJlZm9yZSBhbGwgbW9kZXJuIGJyb3dzZXJzIGhhZCBub24tcHJlZml4ZWQgZmxleCBzdHlsZXMuIEFzIHN1Y2gsIG5vd2FkYXlzIHlvdQogICAgZG9uJ3QgcmVhbGx5IG5lZWQgdG8gdXNlIHRoaXMgZWxlbWVudCBhbnltb3JlLCBhbmQgY2FuIHVzZSBDU1MgZmxleCBzdHlsZXMKICAgIGRpcmVjdGx5IGluIHlvdXIgY29kZS4KCiAgICBUaGlzIGNvbXBvbmVudCBwcm92aWRlcyB0d28gZGlmZmVyZW50IHdheXMgdG8gdXNlIGZsZXhib3g6CgogICAgMS4gW0xheW91dAogICAgY2xhc3Nlc10oaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9pcm9uLWZsZXgtbGF5b3V0L3RyZWUvbWFzdGVyL2lyb24tZmxleC1sYXlvdXQtY2xhc3Nlcy5odG1sKS4KICAgIFRoZSBsYXlvdXQgY2xhc3Mgc3R5bGVzaGVldCBwcm92aWRlcyBhIHNpbXBsZSBzZXQgb2YgY2xhc3MtYmFzZWQgZmxleGJveCBydWxlcywKICAgIHRoYXQgbGV0IHlvdSBzcGVjaWZ5IGxheW91dCBwcm9wZXJ0aWVzIGRpcmVjdGx5IGluIG1hcmt1cC4gWW91IG11c3QgaW5jbHVkZSB0aGlzCiAgICBmaWxlIGluIGV2ZXJ5IGVsZW1lbnQgdGhhdCBuZWVkcyB0byB1c2UgdGhlbS4KCiAgICAgICAgU2FtcGxlIHVzZToKCiAgICAgICAgYGBgCiAgICAgICAgPGN1c3RvbS1lbGVtZW50LWRlbW8+CiAgICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICAgIDxzY3JpcHQgc3JjPSIuLi93ZWJjb21wb25lbnRzanMvd2ViY29tcG9uZW50cy1saXRlLmpzIj48L0pBVkFfU0NSSUlJSVBULz4KICAgICAgICAgICAgPG5leHQtY29kZS1ibG9jaz48L25leHQtY29kZS1ibG9jaz4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC9jdXN0b20tZWxlbWVudC1kZW1vPgogICAgICAgIGBgYAoKICAgICAgICBgYGBqcwogICAgICAgIGltcG9ydCB7aHRtbH0gZnJvbSAnQHBvbHltZXIvcG9seW1lci9saWIvdXRpbHMvaHRtbC10YWcuanMnOwogICAgICAgIGltcG9ydCAnQHBvbHltZXIvaXJvbi1mbGV4LWxheW91dC9pcm9uLWZsZXgtbGF5b3V0LWNsYXNzZXMuanMnOwoKICAgICAgICBjb25zdCB0ZW1wbGF0ZSA9IGh0bWxgCiAgICAgICAgICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSIgaW5jbHVkZT0iaXJvbi1mbGV4IGlyb24tZmxleC1hbGlnbm1lbnQiPjwvc3R5bGU+CiAgICAgICAgICA8c3R5bGU+CiAgICAgICAgICAgIC50ZXN0IHsgd2lkdGg6IDEwMHB4OyB9CiAgICAgICAgICA8L3N0eWxlPgogICAgICAgICAgPGRpdiBjbGFzcz0ibGF5b3V0IGhvcml6b250YWwgY2VudGVyLWNlbnRlciI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9InRlc3QiPmhvcml6b250YWwgbGF5b3V0IGNlbnRlciBhbGlnbm1lbnQ8L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIGA7CiAgICAgICAgZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZCh0ZW1wbGF0ZS5jb250ZW50KTsKICAgICAgICBgYGAKCiAgICAyLiBbQ3VzdG9tIENTUwogICAgbWl4aW5zXShodHRwczovL2dpdGh1Yi5jb20vUG9seW1lckVsZW1lbnRzL2lyb24tZmxleC1sYXlvdXQvYmxvYi9tYXN0ZXIvaXJvbi1mbGV4LWxheW91dC5odG1sKS4KICAgIFRoZSBtaXhpbiBzdHlsZXNoZWV0IGluY2x1ZGVzIGN1c3RvbSBDU1MgbWl4aW5zIHRoYXQgY2FuIGJlIGFwcGxpZWQgaW5zaWRlIGEgQ1NTCiAgICBydWxlIHVzaW5nIHRoZSBgQGFwcGx5YCBmdW5jdGlvbi4KCiAgICBQbGVhc2Ugbm90ZSB0aGF0IHRoZSBvbGQgWy9kZWVwLyBsYXlvdXQKICAgIGNsYXNzZXNdKGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyRWxlbWVudHMvaXJvbi1mbGV4LWxheW91dC90cmVlL21hc3Rlci9jbGFzc2VzKQogICAgYXJlIGRlcHJlY2F0ZWQsIGFuZCBzaG91bGQgbm90IGJlIHVzZWQuIFRvIGNvbnRpbnVlIHVzaW5nIGxheW91dCBwcm9wZXJ0aWVzCiAgICBkaXJlY3RseSBpbiBtYXJrdXAsIHBsZWFzZSBzd2l0Y2ggdG8gdXNpbmcgdGhlIG5ldyBgZG9tLW1vZHVsZWAtYmFzZWQKICAgIFtsYXlvdXQKICAgIGNsYXNzZXNdKGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyRWxlbWVudHMvaXJvbi1mbGV4LWxheW91dC90cmVlL21hc3Rlci9pcm9uLWZsZXgtbGF5b3V0LWNsYXNzZXMuaHRtbCkuCiAgICBQbGVhc2Ugbm90ZSB0aGF0IHRoZSBuZXcgdmVyc2lvbiBkb2VzIG5vdCB1c2UgYC9kZWVwL2AsIGFuZCB0aGVyZWZvcmUgcmVxdWlyZXMKICAgIHlvdSB0byBpbXBvcnQgdGhlIGBkb20tbW9kdWxlc2AgaW4gZXZlcnkgZWxlbWVudCB0aGF0IG5lZWRzIHRvIHVzZSB0aGVtLgoKICAgIEBncm91cCBJcm9uIEVsZW1lbnRzCiAgICBAcHNldWRvRWxlbWVudCBpcm9uLWZsZXgtbGF5b3V0CiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBjb25zdCB0ZW1wbGF0ZSQxID0gaHRtbGAKPGN1c3RvbS1zdHlsZT4KICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSI+CiAgICBbaGlkZGVuXSB7CiAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgIH0KICA8L3N0eWxlPgo8L2N1c3RvbS1zdHlsZT4KPGN1c3RvbS1zdHlsZT4KICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSI+CiAgICBodG1sIHsKCiAgICAgIC0tbGF5b3V0OiB7CiAgICAgICAgZGlzcGxheTogLW1zLWZsZXhib3g7CiAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4OwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgIH07CgogICAgICAtLWxheW91dC1pbmxpbmU6IHsKICAgICAgICBkaXNwbGF5OiAtbXMtaW5saW5lLWZsZXhib3g7CiAgICAgICAgZGlzcGxheTogLXdlYmtpdC1pbmxpbmUtZmxleDsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtZmxleDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWhvcml6b250YWw6IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQ7CgogICAgICAgIC1tcy1mbGV4LWRpcmVjdGlvbjogcm93OwogICAgICAgIC13ZWJraXQtZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtaG9yaXpvbnRhbC1yZXZlcnNlOiB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0OwoKICAgICAgICAtbXMtZmxleC1kaXJlY3Rpb246IHJvdy1yZXZlcnNlOwogICAgICAgIC13ZWJraXQtZmxleC1kaXJlY3Rpb246IHJvdy1yZXZlcnNlOwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiByb3ctcmV2ZXJzZTsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LXZlcnRpY2FsOiB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0OwoKICAgICAgICAtbXMtZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICAtd2Via2l0LWZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LXZlcnRpY2FsLXJldmVyc2U6IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQ7CgogICAgICAgIC1tcy1mbGV4LWRpcmVjdGlvbjogY29sdW1uLXJldmVyc2U7CiAgICAgICAgLXdlYmtpdC1mbGV4LWRpcmVjdGlvbjogY29sdW1uLXJldmVyc2U7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbi1yZXZlcnNlOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtd3JhcDogewogICAgICAgIC1tcy1mbGV4LXdyYXA6IHdyYXA7CiAgICAgICAgLXdlYmtpdC1mbGV4LXdyYXA6IHdyYXA7CiAgICAgICAgZmxleC13cmFwOiB3cmFwOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtd3JhcC1yZXZlcnNlOiB7CiAgICAgICAgLW1zLWZsZXgtd3JhcDogd3JhcC1yZXZlcnNlOwogICAgICAgIC13ZWJraXQtZmxleC13cmFwOiB3cmFwLXJldmVyc2U7CiAgICAgICAgZmxleC13cmFwOiB3cmFwLXJldmVyc2U7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LWF1dG86IHsKICAgICAgICAtbXMtZmxleDogMSAxIGF1dG87CiAgICAgICAgLXdlYmtpdC1mbGV4OiAxIDEgYXV0bzsKICAgICAgICBmbGV4OiAxIDEgYXV0bzsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWZsZXgtbm9uZTogewogICAgICAgIC1tcy1mbGV4OiBub25lOwogICAgICAgIC13ZWJraXQtZmxleDogbm9uZTsKICAgICAgICBmbGV4OiBub25lOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZmxleDogewogICAgICAgIC1tcy1mbGV4OiAxIDEgMC4wMDAwMDAwMDFweDsKICAgICAgICAtd2Via2l0LWZsZXg6IDE7CiAgICAgICAgZmxleDogMTsKICAgICAgICAtd2Via2l0LWZsZXgtYmFzaXM6IDAuMDAwMDAwMDAxcHg7CiAgICAgICAgZmxleC1iYXNpczogMC4wMDAwMDAwMDFweDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWZsZXgtMjogewogICAgICAgIC1tcy1mbGV4OiAyOwogICAgICAgIC13ZWJraXQtZmxleDogMjsKICAgICAgICBmbGV4OiAyOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZmxleC0zOiB7CiAgICAgICAgLW1zLWZsZXg6IDM7CiAgICAgICAgLXdlYmtpdC1mbGV4OiAzOwogICAgICAgIGZsZXg6IDM7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LTQ6IHsKICAgICAgICAtbXMtZmxleDogNDsKICAgICAgICAtd2Via2l0LWZsZXg6IDQ7CiAgICAgICAgZmxleDogNDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWZsZXgtNTogewogICAgICAgIC1tcy1mbGV4OiA1OwogICAgICAgIC13ZWJraXQtZmxleDogNTsKICAgICAgICBmbGV4OiA1OwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZmxleC02OiB7CiAgICAgICAgLW1zLWZsZXg6IDY7CiAgICAgICAgLXdlYmtpdC1mbGV4OiA2OwogICAgICAgIGZsZXg6IDY7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LTc6IHsKICAgICAgICAtbXMtZmxleDogNzsKICAgICAgICAtd2Via2l0LWZsZXg6IDc7CiAgICAgICAgZmxleDogNzsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWZsZXgtODogewogICAgICAgIC1tcy1mbGV4OiA4OwogICAgICAgIC13ZWJraXQtZmxleDogODsKICAgICAgICBmbGV4OiA4OwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZmxleC05OiB7CiAgICAgICAgLW1zLWZsZXg6IDk7CiAgICAgICAgLXdlYmtpdC1mbGV4OiA5OwogICAgICAgIGZsZXg6IDk7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LTEwOiB7CiAgICAgICAgLW1zLWZsZXg6IDEwOwogICAgICAgIC13ZWJraXQtZmxleDogMTA7CiAgICAgICAgZmxleDogMTA7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LTExOiB7CiAgICAgICAgLW1zLWZsZXg6IDExOwogICAgICAgIC13ZWJraXQtZmxleDogMTE7CiAgICAgICAgZmxleDogMTE7CiAgICAgIH07CgogICAgICAtLWxheW91dC1mbGV4LTEyOiB7CiAgICAgICAgLW1zLWZsZXg6IDEyOwogICAgICAgIC13ZWJraXQtZmxleDogMTI7CiAgICAgICAgZmxleDogMTI7CiAgICAgIH07CgogICAgICAvKiBhbGlnbm1lbnQgaW4gY3Jvc3MgYXhpcyAqLwoKICAgICAgLS1sYXlvdXQtc3RhcnQ6IHsKICAgICAgICAtbXMtZmxleC1hbGlnbjogc3RhcnQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogZmxleC1zdGFydDsKICAgICAgICBhbGlnbi1pdGVtczogZmxleC1zdGFydDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWNlbnRlcjogewogICAgICAgIC1tcy1mbGV4LWFsaWduOiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogY2VudGVyOwogICAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgICAgIH07CgogICAgICAtLWxheW91dC1lbmQ6IHsKICAgICAgICAtbXMtZmxleC1hbGlnbjogZW5kOwogICAgICAgIC13ZWJraXQtYWxpZ24taXRlbXM6IGZsZXgtZW5kOwogICAgICAgIGFsaWduLWl0ZW1zOiBmbGV4LWVuZDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWJhc2VsaW5lOiB7CiAgICAgICAgLW1zLWZsZXgtYWxpZ246IGJhc2VsaW5lOwogICAgICAgIC13ZWJraXQtYWxpZ24taXRlbXM6IGJhc2VsaW5lOwogICAgICAgIGFsaWduLWl0ZW1zOiBiYXNlbGluZTsKICAgICAgfTsKCiAgICAgIC8qIGFsaWdubWVudCBpbiBtYWluIGF4aXMgKi8KCiAgICAgIC0tbGF5b3V0LXN0YXJ0LWp1c3RpZmllZDogewogICAgICAgIC1tcy1mbGV4LXBhY2s6IHN0YXJ0OwogICAgICAgIC13ZWJraXQtanVzdGlmeS1jb250ZW50OiBmbGV4LXN0YXJ0OwogICAgICAgIGp1c3RpZnktY29udGVudDogZmxleC1zdGFydDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWNlbnRlci1qdXN0aWZpZWQ6IHsKICAgICAgICAtbXMtZmxleC1wYWNrOiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1qdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWVuZC1qdXN0aWZpZWQ6IHsKICAgICAgICAtbXMtZmxleC1wYWNrOiBlbmQ7CiAgICAgICAgLXdlYmtpdC1qdXN0aWZ5LWNvbnRlbnQ6IGZsZXgtZW5kOwogICAgICAgIGp1c3RpZnktY29udGVudDogZmxleC1lbmQ7CiAgICAgIH07CgogICAgICAtLWxheW91dC1hcm91bmQtanVzdGlmaWVkOiB7CiAgICAgICAgLW1zLWZsZXgtcGFjazogZGlzdHJpYnV0ZTsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kOwogICAgICAgIGp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtanVzdGlmaWVkOiB7CiAgICAgICAgLW1zLWZsZXgtcGFjazoganVzdGlmeTsKICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47CiAgICAgIH07CgogICAgICAtLWxheW91dC1jZW50ZXItY2VudGVyOiB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlcjsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyLWp1c3RpZmllZDsKICAgICAgfTsKCiAgICAgIC8qIHNlbGYgYWxpZ25tZW50ICovCgogICAgICAtLWxheW91dC1zZWxmLXN0YXJ0OiB7CiAgICAgICAgLW1zLWFsaWduLXNlbGY6IGZsZXgtc3RhcnQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBmbGV4LXN0YXJ0OwogICAgICAgIGFsaWduLXNlbGY6IGZsZXgtc3RhcnQ7CiAgICAgIH07CgogICAgICAtLWxheW91dC1zZWxmLWNlbnRlcjogewogICAgICAgIC1tcy1hbGlnbi1zZWxmOiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBjZW50ZXI7CiAgICAgICAgYWxpZ24tc2VsZjogY2VudGVyOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtc2VsZi1lbmQ6IHsKICAgICAgICAtbXMtYWxpZ24tc2VsZjogZmxleC1lbmQ7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1zZWxmOiBmbGV4LWVuZDsKICAgICAgICBhbGlnbi1zZWxmOiBmbGV4LWVuZDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LXNlbGYtc3RyZXRjaDogewogICAgICAgIC1tcy1hbGlnbi1zZWxmOiBzdHJldGNoOwogICAgICAgIC13ZWJraXQtYWxpZ24tc2VsZjogc3RyZXRjaDsKICAgICAgICBhbGlnbi1zZWxmOiBzdHJldGNoOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtc2VsZi1iYXNlbGluZTogewogICAgICAgIC1tcy1hbGlnbi1zZWxmOiBiYXNlbGluZTsKICAgICAgICAtd2Via2l0LWFsaWduLXNlbGY6IGJhc2VsaW5lOwogICAgICAgIGFsaWduLXNlbGY6IGJhc2VsaW5lOwogICAgICB9OwoKICAgICAgLyogbXVsdGktbGluZSBhbGlnbm1lbnQgaW4gbWFpbiBheGlzICovCgogICAgICAtLWxheW91dC1zdGFydC1hbGlnbmVkOiB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBzdGFydDsgIC8qIElFMTAgKi8KICAgICAgICAtbXMtYWxpZ24tY29udGVudDogZmxleC1zdGFydDsKICAgICAgICAtd2Via2l0LWFsaWduLWNvbnRlbnQ6IGZsZXgtc3RhcnQ7CiAgICAgICAgYWxpZ24tY29udGVudDogZmxleC1zdGFydDsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWVuZC1hbGlnbmVkOiB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBlbmQ7ICAvKiBJRTEwICovCiAgICAgICAgLW1zLWFsaWduLWNvbnRlbnQ6IGZsZXgtZW5kOwogICAgICAgIC13ZWJraXQtYWxpZ24tY29udGVudDogZmxleC1lbmQ7CiAgICAgICAgYWxpZ24tY29udGVudDogZmxleC1lbmQ7CiAgICAgIH07CgogICAgICAtLWxheW91dC1jZW50ZXItYWxpZ25lZDogewogICAgICAgIC1tcy1mbGV4LWxpbmUtcGFjazogY2VudGVyOyAgLyogSUUxMCAqLwogICAgICAgIC1tcy1hbGlnbi1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC1hbGlnbi1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgYWxpZ24tY29udGVudDogY2VudGVyOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtYmV0d2Vlbi1hbGlnbmVkOiB7CiAgICAgICAgLW1zLWZsZXgtbGluZS1wYWNrOiBqdXN0aWZ5OyAgLyogSUUxMCAqLwogICAgICAgIC1tcy1hbGlnbi1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICAgIC13ZWJraXQtYWxpZ24tY29udGVudDogc3BhY2UtYmV0d2VlbjsKICAgICAgICBhbGlnbi1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtYXJvdW5kLWFsaWduZWQ6IHsKICAgICAgICAtbXMtZmxleC1saW5lLXBhY2s6IGRpc3RyaWJ1dGU7ICAvKiBJRTEwICovCiAgICAgICAgLW1zLWFsaWduLWNvbnRlbnQ6IHNwYWNlLWFyb3VuZDsKICAgICAgICAtd2Via2l0LWFsaWduLWNvbnRlbnQ6IHNwYWNlLWFyb3VuZDsKICAgICAgICBhbGlnbi1jb250ZW50OiBzcGFjZS1hcm91bmQ7CiAgICAgIH07CgogICAgICAvKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKgogICAgICAgICAgICAgICAgT3RoZXIgTGF5b3V0CiAgICAgICoqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiovCgogICAgICAtLWxheW91dC1ibG9jazogewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtaW52aXNpYmxlOiB7CiAgICAgICAgdmlzaWJpbGl0eTogaGlkZGVuICFpbXBvcnRhbnQ7CiAgICAgIH07CgogICAgICAtLWxheW91dC1yZWxhdGl2ZTogewogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgfTsKCiAgICAgIC0tbGF5b3V0LWZpdDogewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgYm90dG9tOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgIH07CgogICAgICAtLWxheW91dC1zY3JvbGw6IHsKICAgICAgICAtd2Via2l0LW92ZXJmbG93LXNjcm9sbGluZzogdG91Y2g7CiAgICAgICAgb3ZlcmZsb3c6IGF1dG87CiAgICAgIH07CgogICAgICAtLWxheW91dC1mdWxsYmxlZWQ6IHsKICAgICAgICBtYXJnaW46IDA7CiAgICAgICAgaGVpZ2h0OiAxMDB2aDsKICAgICAgfTsKCiAgICAgIC8qIGZpeGVkIHBvc2l0aW9uICovCgogICAgICAtLWxheW91dC1maXhlZC10b3A6IHsKICAgICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICAgICAgdG9wOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgIH07CgogICAgICAtLWxheW91dC1maXhlZC1yaWdodDogewogICAgICAgIHBvc2l0aW9uOiBmaXhlZDsKICAgICAgICB0b3A6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgYm90dG9tOiAwOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZml4ZWQtYm90dG9tOiB7CiAgICAgICAgcG9zaXRpb246IGZpeGVkOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICB9OwoKICAgICAgLS1sYXlvdXQtZml4ZWQtbGVmdDogewogICAgICAgIHBvc2l0aW9uOiBmaXhlZDsKICAgICAgICB0b3A6IDA7CiAgICAgICAgYm90dG9tOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgIH07CgogICAgfQogIDwvc3R5bGU+CjwvY3VzdG9tLXN0eWxlPmA7CgogICAgdGVtcGxhdGUkMS5zZXRBdHRyaWJ1dGUoJ3N0eWxlJywgJ2Rpc3BsYXk6IG5vbmU7Jyk7CiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKHRlbXBsYXRlJDEuY29udGVudCk7CgogICAgdmFyIHN0eWxlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKTsKICAgIHN0eWxlLnRleHRDb250ZW50ID0gJ1toaWRkZW5dIHsgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OyB9JzsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoc3R5bGUpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNsYXNzIElyb25NZXRhIHsKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7ewogICAgICAgKiAgIHR5cGU6IChzdHJpbmd8bnVsbHx1bmRlZmluZWQpLAogICAgICAgKiAgIGtleTogKHN0cmluZ3xudWxsfHVuZGVmaW5lZCksCiAgICAgICAqICAgdmFsdWU6ICosCiAgICAgICAqIH09fSBvcHRpb25zCiAgICAgICAqLwogICAgICBjb25zdHJ1Y3RvcihvcHRpb25zKSB7CiAgICAgICAgSXJvbk1ldGFbJyAnXShvcHRpb25zKTsKCiAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd9ICovCiAgICAgICAgdGhpcy50eXBlID0gKG9wdGlvbnMgJiYgb3B0aW9ucy50eXBlKSB8fCAnZGVmYXVsdCc7CiAgICAgICAgLyoqIEB0eXBlIHtzdHJpbmd8bnVsbHx1bmRlZmluZWR9ICovCiAgICAgICAgdGhpcy5rZXkgPSBvcHRpb25zICYmIG9wdGlvbnMua2V5OwogICAgICAgIGlmIChvcHRpb25zICYmICd2YWx1ZScgaW4gb3B0aW9ucykgewogICAgICAgICAgLyoqIEB0eXBlIHsqfSAqLwogICAgICAgICAgdGhpcy52YWx1ZSA9IG9wdGlvbnMudmFsdWU7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKiogQHJldHVybiB7Kn0gKi8KICAgICAgZ2V0IHZhbHVlKCkgewogICAgICAgIHZhciB0eXBlID0gdGhpcy50eXBlOwogICAgICAgIHZhciBrZXkgPSB0aGlzLmtleTsKCiAgICAgICAgaWYgKHR5cGUgJiYga2V5KSB7CiAgICAgICAgICByZXR1cm4gSXJvbk1ldGEudHlwZXNbdHlwZV0gJiYgSXJvbk1ldGEudHlwZXNbdHlwZV1ba2V5XTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKiBAcGFyYW0geyp9IHZhbHVlICovCiAgICAgIHNldCB2YWx1ZSh2YWx1ZSkgewogICAgICAgIHZhciB0eXBlID0gdGhpcy50eXBlOwogICAgICAgIHZhciBrZXkgPSB0aGlzLmtleTsKCiAgICAgICAgaWYgKHR5cGUgJiYga2V5KSB7CiAgICAgICAgICB0eXBlID0gSXJvbk1ldGEudHlwZXNbdHlwZV0gPSBJcm9uTWV0YS50eXBlc1t0eXBlXSB8fCB7fTsKICAgICAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgICAgIGRlbGV0ZSB0eXBlW2tleV07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0eXBlW2tleV0gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKiBAcmV0dXJuIHshQXJyYXk8Kj59ICovCiAgICAgIGdldCBsaXN0KCkgewogICAgICAgIHZhciB0eXBlID0gdGhpcy50eXBlOwoKICAgICAgICBpZiAodHlwZSkgewogICAgICAgICAgdmFyIGl0ZW1zID0gSXJvbk1ldGEudHlwZXNbdGhpcy50eXBlXTsKICAgICAgICAgIGlmICghaXRlbXMpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQoKICAgICAgICAgIHJldHVybiBPYmplY3Qua2V5cyhpdGVtcykubWFwKGZ1bmN0aW9uKGtleSkgewogICAgICAgICAgICByZXR1cm4gbWV0YURhdGFzW3RoaXMudHlwZV1ba2V5XTsKICAgICAgICAgIH0sIHRoaXMpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkKICAgICAgICogQHJldHVybiB7Kn0KICAgICAgICovCiAgICAgIGJ5S2V5KGtleSkgewogICAgICAgIHRoaXMua2V5ID0ga2V5OwogICAgICAgIHJldHVybiB0aGlzLnZhbHVlOwogICAgICB9CiAgICB9CiAgICAvLyBUaGlzIGZ1bmN0aW9uIGlzIHVzZWQgdG8gY29udmluY2UgQ2xvc3VyZSBub3QgdG8gcmVtb3ZlIGNvbnN0cnVjdG9yIGNhbGxzCiAgICAvLyBmb3IgaW5zdGFuY2VzIHRoYXQgYXJlIG5vdCBoZWxkIGFueXdoZXJlLiBGb3IgZXhhbXBsZSwgd2hlbgogICAgLy8gYG5ldyBJcm9uTWV0YSh7Li4ufSlgIGlzIHVzZWQgb25seSBmb3IgdGhlIHNpZGUgZWZmZWN0IG9mIGFkZGluZyBhIHZhbHVlLgogICAgSXJvbk1ldGFbJyAnXSA9IGZ1bmN0aW9uKCkge307CgogICAgSXJvbk1ldGEudHlwZXMgPSB7fTsKCiAgICB2YXIgbWV0YURhdGFzID0gSXJvbk1ldGEudHlwZXM7CgogICAgLyoqCiAgICBgaXJvbi1tZXRhYCBpcyBhIGdlbmVyaWMgZWxlbWVudCB5b3UgY2FuIHVzZSBmb3Igc2hhcmluZyBpbmZvcm1hdGlvbiBhY3Jvc3MgdGhlCiAgICBET00gdHJlZS4gSXQgdXNlcyBbbW9ub3N0YXRlIHBhdHRlcm5dKGh0dHA6Ly9jMi5jb20vY2dpL3dpa2k/TW9ub3N0YXRlUGF0dGVybikKICAgIHN1Y2ggdGhhdCBhbnkgaW5zdGFuY2Ugb2YgaXJvbi1tZXRhIGhhcyBhY2Nlc3MgdG8gdGhlIHNoYXJlZCBpbmZvcm1hdGlvbi4gWW91CiAgICBjYW4gdXNlIGBpcm9uLW1ldGFgIHRvIHNoYXJlIHdoYXRldmVyIHlvdSB3YW50IChvciBjcmVhdGUgYW4gZXh0ZW5zaW9uIFtsaWtlCiAgICB4LW1ldGFdIGZvciBlbmhhbmNlbWVudHMpLgoKICAgIFRoZSBgaXJvbi1tZXRhYCBpbnN0YW5jZXMgY29udGFpbmluZyB5b3VyIGFjdHVhbCBkYXRhIGNhbiBiZSBsb2FkZWQgaW4gYW4KICAgIGltcG9ydCwgb3IgY29uc3RydWN0ZWQgaW4gYW55IHdheSB5b3Ugc2VlIGZpdC4gVGhlIG9ubHkgcmVxdWlyZW1lbnQgaXMgdGhhdCB5b3UKICAgIGNyZWF0ZSB0aGVtIGJlZm9yZSB5b3UgdHJ5IHRvIGFjY2VzcyB0aGVtLgoKICAgIEV4YW1wbGVzOgoKICAgIElmIEkgY3JlYXRlIGFuIGluc3RhbmNlIGxpa2UgdGhpczoKCiAgICAgICAgPGlyb24tbWV0YSBrZXk9ImluZm8iIHZhbHVlPSJmb28vYmFyIj48L2lyb24tbWV0YT4KCiAgICBOb3RlIHRoYXQgdmFsdWU9ImZvby9iYXIiIGlzIHRoZSBtZXRhZGF0YSBJJ3ZlIGRlZmluZWQuIEkgY291bGQgZGVmaW5lIG1vcmUKICAgIGF0dHJpYnV0ZXMgb3IgdXNlIGNoaWxkIG5vZGVzIHRvIGRlZmluZSBhZGRpdGlvbmFsIG1ldGFkYXRhLgoKICAgIE5vdyBJIGNhbiBhY2Nlc3MgdGhhdCBlbGVtZW50IChhbmQgaXQncyBtZXRhZGF0YSkgZnJvbSBhbnkgaXJvbi1tZXRhIGluc3RhbmNlCiAgICB2aWEgdGhlIGJ5S2V5IG1ldGhvZCwgZS5nLgoKICAgICAgICBtZXRhLmJ5S2V5KCdpbmZvJyk7CgogICAgUHVyZSBpbXBlcmF0aXZlIGZvcm0gd291bGQgYmUgbGlrZToKCiAgICAgICAgZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnaXJvbi1tZXRhJykuYnlLZXkoJ2luZm8nKTsKCiAgICBPciwgaW4gYSBQb2x5bWVyIGVsZW1lbnQsIHlvdSBjYW4gaW5jbHVkZSBhIG1ldGEgaW4geW91ciB0ZW1wbGF0ZToKCiAgICAgICAgPGlyb24tbWV0YSBpZD0ibWV0YSI+PC9pcm9uLW1ldGE+CiAgICAgICAgLi4uCiAgICAgICAgdGhpcy4kLm1ldGEuYnlLZXkoJ2luZm8nKTsKCiAgICBAZ3JvdXAgSXJvbiBFbGVtZW50cwogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICBAZWxlbWVudCBpcm9uLW1ldGEKICAgICovCiAgICBQb2x5bWVyKHsKCiAgICAgIGlzOiAnaXJvbi1tZXRhJywKCiAgICAgIHByb3BlcnRpZXM6IHsKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIHR5cGUgb2YgbWV0YS1kYXRhLiAgQWxsIG1ldGEtZGF0YSBvZiB0aGUgc2FtZSB0eXBlIGlzIHN0b3JlZAogICAgICAgICAqIHRvZ2V0aGVyLgogICAgICAgICAqIEB0eXBlIHtzdHJpbmd9CiAgICAgICAgICovCiAgICAgICAgdHlwZTogewogICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgdmFsdWU6ICdkZWZhdWx0JywKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUga2V5IHVzZWQgdG8gc3RvcmUgYHZhbHVlYCB1bmRlciB0aGUgYHR5cGVgIG5hbWVzcGFjZS4KICAgICAgICAgKiBAdHlwZSB7P3N0cmluZ30KICAgICAgICAgKi8KICAgICAgICBrZXk6IHsKICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbWV0YS1kYXRhIHRvIHN0b3JlIG9yIHJldHJpZXZlLgogICAgICAgICAqIEB0eXBlIHsqfQogICAgICAgICAqLwogICAgICAgIHZhbHVlOiB7CiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgYHZhbHVlYCBpcyBzZXQgdG8gdGhlIGlyb24tbWV0YSBpbnN0YW5jZSBpdHNlbGYuCiAgICAgICAgICovCiAgICAgICAgc2VsZjoge3R5cGU6IEJvb2xlYW4sIG9ic2VydmVyOiAnX3NlbGZDaGFuZ2VkJ30sCgogICAgICAgIF9fbWV0YToge3R5cGU6IEJvb2xlYW4sIGNvbXB1dGVkOiAnX19jb21wdXRlTWV0YSh0eXBlLCBrZXksIHZhbHVlKSd9CiAgICAgIH0sCgogICAgICBob3N0QXR0cmlidXRlczoge2hpZGRlbjogdHJ1ZX0sCgogICAgICBfX2NvbXB1dGVNZXRhOiBmdW5jdGlvbih0eXBlLCBrZXksIHZhbHVlKSB7CiAgICAgICAgdmFyIG1ldGEgPSBuZXcgSXJvbk1ldGEoe3R5cGU6IHR5cGUsIGtleToga2V5fSk7CgogICAgICAgIGlmICh2YWx1ZSAhPT0gdW5kZWZpbmVkICYmIHZhbHVlICE9PSBtZXRhLnZhbHVlKSB7CiAgICAgICAgICBtZXRhLnZhbHVlID0gdmFsdWU7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLnZhbHVlICE9PSBtZXRhLnZhbHVlKSB7CiAgICAgICAgICB0aGlzLnZhbHVlID0gbWV0YS52YWx1ZTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBtZXRhOwogICAgICB9LAoKICAgICAgZ2V0IGxpc3QoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX19tZXRhICYmIHRoaXMuX19tZXRhLmxpc3Q7CiAgICAgIH0sCgogICAgICBfc2VsZkNoYW5nZWQ6IGZ1bmN0aW9uKHNlbGYpIHsKICAgICAgICBpZiAoc2VsZikgewogICAgICAgICAgdGhpcy52YWx1ZSA9IHRoaXM7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHJpZXZlcyBtZXRhIGRhdGEgdmFsdWUgYnkga2V5LgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIGJ5S2V5CiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgbWV0YS1kYXRhIHRvIGJlIHJldHVybmVkLgogICAgICAgKiBAcmV0dXJuIHsqfQogICAgICAgKi8KICAgICAgYnlLZXk6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHJldHVybiBuZXcgSXJvbk1ldGEoe3R5cGU6IHRoaXMudHlwZSwga2V5OiBrZXl9KS52YWx1ZTsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCgogICAgVGhlIGBpcm9uLWljb25gIGVsZW1lbnQgZGlzcGxheXMgYW4gaWNvbi4gQnkgZGVmYXVsdCBhbiBpY29uIHJlbmRlcnMgYXMgYSAyNHB4CiAgICBzcXVhcmUuCgogICAgRXhhbXBsZSB1c2luZyBzcmM6CgogICAgICAgIDxpcm9uLWljb24gc3JjPSJzdGFyLnBuZyI+PC9pcm9uLWljb24+CgogICAgRXhhbXBsZSBzZXR0aW5nIHNpemUgdG8gMzJweCB4IDMycHg6CgogICAgICAgIDxpcm9uLWljb24gY2xhc3M9ImJpZyIgc3JjPSJiaWdfc3Rhci5wbmciPjwvaXJvbi1pY29uPgoKICAgICAgICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSI+CiAgICAgICAgICAuYmlnIHsKICAgICAgICAgICAgLS1pcm9uLWljb24taGVpZ2h0OiAzMnB4OwogICAgICAgICAgICAtLWlyb24taWNvbi13aWR0aDogMzJweDsKICAgICAgICAgIH0KICAgICAgICA8L3N0eWxlPgoKICAgIFRoZSBpcm9uIGVsZW1lbnRzIGluY2x1ZGUgc2V2ZXJhbCBzZXRzIG9mIGljb25zLiBUbyB1c2UgdGhlIGRlZmF1bHQgc2V0IG9mCiAgICBpY29ucywgaW1wb3J0IGBpcm9uLWljb25zLmpzYCBhbmQgdXNlIHRoZSBgaWNvbmAgYXR0cmlidXRlIHRvIHNwZWNpZnkgYW4gaWNvbjoKCiAgICAgICAgPHNjcmlwdCB0eXBlPSJtb2R1bGUiPgogICAgICAgICAgaW1wb3J0ICJAcG9seW1lci9pcm9uLWljb25zL2lyb24taWNvbnMuanMiOwogICAgICAgIDwvSkFWQV9TQ1JJSUlJUFQvPgoKICAgICAgICA8aXJvbi1pY29uIGljb249Im1lbnUiPjwvaXJvbi1pY29uPgoKICAgIFRvIHVzZSBhIGRpZmZlcmVudCBidWlsdC1pbiBzZXQgb2YgaWNvbnMsIGltcG9ydCB0aGUgc3BlY2lmaWMKICAgIGBpcm9uLWljb25zLzxpY29uc2V0Pi1pY29ucy5qc2AsIGFuZCBzcGVjaWZ5IHRoZSBpY29uIGFzIGA8aWNvbnNldD46PGljb24+YC4KICAgIEZvciBleGFtcGxlLCB0byB1c2UgYSBjb21tdW5pY2F0aW9uIGljb24sIHlvdSB3b3VsZCB1c2U6CgogICAgICAgIDxzY3JpcHQgdHlwZT0ibW9kdWxlIj4KICAgICAgICAgIGltcG9ydCAiQHBvbHltZXIvaXJvbi1pY29ucy9jb21tdW5pY2F0aW9uLWljb25zLmpzIjsKICAgICAgICA8L0pBVkFfU0NSSUlJSVBULz4KCiAgICAgICAgPGlyb24taWNvbiBpY29uPSJjb21tdW5pY2F0aW9uOmVtYWlsIj48L2lyb24taWNvbj4KCiAgICBZb3UgY2FuIGFsc28gY3JlYXRlIGN1c3RvbSBpY29uIHNldHMgb2YgYml0bWFwIG9yIFNWRyBpY29ucy4KCiAgICBFeGFtcGxlIG9mIHVzaW5nIGFuIGljb24gbmFtZWQgYGNoZXJyeWAgZnJvbSBhIGN1c3RvbSBpY29uc2V0IHdpdGggdGhlIElECiAgICBgZnJ1aXRgOgoKICAgICAgICA8aXJvbi1pY29uIGljb249ImZydWl0OmNoZXJyeSI+PC9pcm9uLWljb24+CgogICAgU2VlIGA8aXJvbi1pY29uc2V0PmAgYW5kIGA8aXJvbi1pY29uc2V0LXN2Zz5gIGZvciBtb3JlIGluZm9ybWF0aW9uIGFib3V0IGhvdyB0bwogICAgY3JlYXRlIGEgY3VzdG9tIGljb25zZXQuCgogICAgU2VlIHRoZSBgaXJvbi1pY29uc2AgZGVtbyB0byBzZWUgdGhlIGljb25zIGF2YWlsYWJsZSBpbiB0aGUgdmFyaW91cyBpY29uc2V0cy4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1pcm9uLWljb25gIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgaWNvbiB8IHt9CiAgICBgLS1pcm9uLWljb24td2lkdGhgIHwgV2lkdGggb2YgdGhlIGljb24gfCBgMjRweGAKICAgIGAtLWlyb24taWNvbi1oZWlnaHRgIHwgSGVpZ2h0IG9mIHRoZSBpY29uIHwgYDI0cHhgCiAgICBgLS1pcm9uLWljb24tZmlsbC1jb2xvcmAgfCBGaWxsIGNvbG9yIG9mIHRoZSBzdmcgaWNvbiB8IGBjdXJyZW50Y29sb3JgCiAgICBgLS1pcm9uLWljb24tc3Ryb2tlLWNvbG9yYCB8IFN0cm9rZSBjb2xvciBvZiB0aGUgc3ZnIGljb24gfCBub25lCgogICAgQGdyb3VwIElyb24gRWxlbWVudHMKICAgIEBlbGVtZW50IGlyb24taWNvbgogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICBAaGVybyBoZXJvLnN2ZwogICAgQGhvbWVwYWdlIHBvbHltZXIuZ2l0aHViLmlvCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIEBhcHBseSAtLWxheW91dC1pbmxpbmU7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlci1jZW50ZXI7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwoKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwoKICAgICAgICBmaWxsOiB2YXIoLS1pcm9uLWljb24tZmlsbC1jb2xvciwgY3VycmVudGNvbG9yKTsKICAgICAgICBzdHJva2U6IHZhcigtLWlyb24taWNvbi1zdHJva2UtY29sb3IsIG5vbmUpOwoKICAgICAgICB3aWR0aDogdmFyKC0taXJvbi1pY29uLXdpZHRoLCAyNHB4KTsKICAgICAgICBoZWlnaHQ6IHZhcigtLWlyb24taWNvbi1oZWlnaHQsIDI0cHgpOwogICAgICAgIEBhcHBseSAtLWlyb24taWNvbjsKICAgICAgfQoKICAgICAgOmhvc3QoW2hpZGRlbl0pIHsKICAgICAgICBkaXNwbGF5OiBub25lOwogICAgICB9CiAgICA8L3N0eWxlPgpgLAoKICAgICAgaXM6ICdpcm9uLWljb24nLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgaWNvbiB0byB1c2UuIFRoZSBuYW1lIHNob3VsZCBiZSBvZiB0aGUgZm9ybToKICAgICAgICAgKiBgaWNvbnNldF9uYW1lOmljb25fbmFtZWAuCiAgICAgICAgICovCiAgICAgICAgaWNvbjoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBuYW1lIG9mIHRoZSB0aGVtZSB0byB1c2VkLCBpZiBvbmUgaXMgc3BlY2lmaWVkIGJ5IHRoZQogICAgICAgICAqIGljb25zZXQuCiAgICAgICAgICovCiAgICAgICAgdGhlbWU6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB1c2luZyBpcm9uLWljb24gd2l0aG91dCBhbiBpY29uc2V0LCB5b3UgY2FuIHNldCB0aGUgc3JjIHRvIGJlCiAgICAgICAgICogdGhlIFVSTCBvZiBhbiBpbmRpdmlkdWFsIGljb24gaW1hZ2UgZmlsZS4gTm90ZSB0aGF0IHRoaXMgd2lsbCB0YWtlCiAgICAgICAgICogcHJlY2VkZW5jZSBvdmVyIGEgZ2l2ZW4gaWNvbiBhdHRyaWJ1dGUuCiAgICAgICAgICovCiAgICAgICAgc3JjOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQHR5cGUgeyFJcm9uTWV0YX0KICAgICAgICAgKi8KICAgICAgICBfbWV0YToge3ZhbHVlOiBCYXNlLmNyZWF0ZSgnaXJvbi1tZXRhJywge3R5cGU6ICdpY29uc2V0J30pfQoKICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWwogICAgICAgICdfdXBkYXRlSWNvbihfbWV0YSwgaXNBdHRhY2hlZCknLAogICAgICAgICdfdXBkYXRlSWNvbih0aGVtZSwgaXNBdHRhY2hlZCknLAogICAgICAgICdfc3JjQ2hhbmdlZChzcmMsIGlzQXR0YWNoZWQpJywKICAgICAgICAnX2ljb25DaGFuZ2VkKGljb24sIGlzQXR0YWNoZWQpJwogICAgICBdLAoKICAgICAgX0RFRkFVTFRfSUNPTlNFVDogJ2ljb25zJywKCiAgICAgIF9pY29uQ2hhbmdlZDogZnVuY3Rpb24oaWNvbikgewogICAgICAgIHZhciBwYXJ0cyA9IChpY29uIHx8ICcnKS5zcGxpdCgnOicpOwogICAgICAgIHRoaXMuX2ljb25OYW1lID0gcGFydHMucG9wKCk7CiAgICAgICAgdGhpcy5faWNvbnNldE5hbWUgPSBwYXJ0cy5wb3AoKSB8fCB0aGlzLl9ERUZBVUxUX0lDT05TRVQ7CiAgICAgICAgdGhpcy5fdXBkYXRlSWNvbigpOwogICAgICB9LAoKICAgICAgX3NyY0NoYW5nZWQ6IGZ1bmN0aW9uKHNyYykgewogICAgICAgIHRoaXMuX3VwZGF0ZUljb24oKTsKICAgICAgfSwKCiAgICAgIF91c2VzSWNvbnNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaWNvbiB8fCAhdGhpcy5zcmM7CiAgICAgIH0sCgogICAgICAvKiogQHN1cHByZXNzIHt2aXNpYmlsaXR5fSAqLwogICAgICBfdXBkYXRlSWNvbjogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX3VzZXNJY29uc2V0KCkpIHsKICAgICAgICAgIGlmICh0aGlzLl9pbWcgJiYgdGhpcy5faW1nLnBhcmVudE5vZGUpIHsKICAgICAgICAgICAgZG9tKHRoaXMucm9vdCkucmVtb3ZlQ2hpbGQodGhpcy5faW1nKTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh0aGlzLl9pY29uTmFtZSA9PT0gJycpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2ljb25zZXQpIHsKICAgICAgICAgICAgICB0aGlzLl9pY29uc2V0LnJlbW92ZUljb24odGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAodGhpcy5faWNvbnNldE5hbWUgJiYgdGhpcy5fbWV0YSkgewogICAgICAgICAgICB0aGlzLl9pY29uc2V0ID0gLyoqIEB0eXBlIHs/UG9seW1lci5JY29uc2V0fSAqLyAoCiAgICAgICAgICAgICAgICB0aGlzLl9tZXRhLmJ5S2V5KHRoaXMuX2ljb25zZXROYW1lKSk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pY29uc2V0KSB7CiAgICAgICAgICAgICAgdGhpcy5faWNvbnNldC5hcHBseUljb24odGhpcywgdGhpcy5faWNvbk5hbWUsIHRoaXMudGhlbWUpOwogICAgICAgICAgICAgIHRoaXMudW5saXN0ZW4od2luZG93LCAnaXJvbi1pY29uc2V0LWFkZGVkJywgJ191cGRhdGVJY29uJyk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgdGhpcy5saXN0ZW4od2luZG93LCAnaXJvbi1pY29uc2V0LWFkZGVkJywgJ191cGRhdGVJY29uJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgaWYgKHRoaXMuX2ljb25zZXQpIHsKICAgICAgICAgICAgdGhpcy5faWNvbnNldC5yZW1vdmVJY29uKHRoaXMpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKCF0aGlzLl9pbWcpIHsKICAgICAgICAgICAgdGhpcy5faW1nID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnaW1nJyk7CiAgICAgICAgICAgIHRoaXMuX2ltZy5zdHlsZS53aWR0aCA9ICcxMDAlJzsKICAgICAgICAgICAgdGhpcy5faW1nLnN0eWxlLmhlaWdodCA9ICcxMDAlJzsKICAgICAgICAgICAgdGhpcy5faW1nLmRyYWdnYWJsZSA9IGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5faW1nLnNyYyA9IHRoaXMuc3JjOwogICAgICAgICAgZG9tKHRoaXMucm9vdCkuYXBwZW5kQ2hpbGQodGhpcy5faW1nKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgLyoqCiAgICAgKiBUaGUgYGlyb24taWNvbnNldC1zdmdgIGVsZW1lbnQgYWxsb3dzIHVzZXJzIHRvIGRlZmluZSB0aGVpciBvd24gaWNvbiBzZXRzCiAgICAgKiB0aGF0IGNvbnRhaW4gc3ZnIGljb25zLiBUaGUgc3ZnIGljb24gZWxlbWVudHMgc2hvdWxkIGJlIGNoaWxkcmVuIG9mIHRoZQogICAgICogYGlyb24taWNvbnNldC1zdmdgIGVsZW1lbnQuIE11bHRpcGxlIGljb25zIHNob3VsZCBiZSBnaXZlbiBkaXN0aW5jdCBpZCdzLgogICAgICoKICAgICAqIFVzaW5nIHN2ZyBlbGVtZW50cyB0byBjcmVhdGUgaWNvbnMgaGFzIGEgZmV3IGFkdmFudGFnZXMgb3ZlciB0cmFkaXRpb25hbAogICAgICogYml0bWFwIGdyYXBoaWNzIGxpa2UganBnIG9yIHBuZy4gSWNvbnMgdGhhdCB1c2Ugc3ZnIGFyZSB2ZWN0b3IgYmFzZWQgc28KICAgICAqIHRoZXkgYXJlIHJlc29sdXRpb24gaW5kZXBlbmRlbnQgYW5kIHNob3VsZCBsb29rIGdvb2Qgb24gYW55IGRldmljZS4gVGhleQogICAgICogYXJlIHN0eWxhYmxlIHZpYSBjc3MuIEljb25zIGNhbiBiZSB0aGVtZWQsIGNvbG9yaXplZCwgYW5kIGV2ZW4gYW5pbWF0ZWQuCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqCiAgICAgKiAgICAgPGlyb24taWNvbnNldC1zdmcgbmFtZT0ibXktc3ZnLWljb25zIiBzaXplPSIyNCI+CiAgICAgKiAgICAgICA8c3ZnPgogICAgICogICAgICAgICA8ZGVmcz4KICAgICAqICAgICAgICAgICA8ZyBpZD0ic2hhcGUiPgogICAgICogICAgICAgICAgICAgPHJlY3QgeD0iMTIiIHk9IjAiIHdpZHRoPSIxMiIgaGVpZ2h0PSIyNCIgLz4KICAgICAqICAgICAgICAgICAgIDxjaXJjbGUgY3g9IjEyIiBjeT0iMTIiIHI9IjEyIiAvPgogICAgICogICAgICAgICAgIDwvZz4KICAgICAqICAgICAgICAgPC9kZWZzPgogICAgICogICAgICAgPC9zdmc+CiAgICAgKiAgICAgPC9pcm9uLWljb25zZXQtc3ZnPgogICAgICoKICAgICAqIFRoaXMgd2lsbCBhdXRvbWF0aWNhbGx5IHJlZ2lzdGVyIHRoZSBpY29uIHNldCAibXktc3ZnLWljb25zIiB0byB0aGUgaWNvbnNldAogICAgICogZGF0YWJhc2UuICBUbyB1c2UgdGhlc2UgaWNvbnMgZnJvbSB3aXRoaW4gYW5vdGhlciBlbGVtZW50LCBtYWtlIGEKICAgICAqIGBpcm9uLWljb25zZXRgIGVsZW1lbnQgYW5kIGNhbGwgdGhlIGBieUlkYCBtZXRob2QKICAgICAqIHRvIHJldHJpZXZlIGEgZ2l2ZW4gaWNvbnNldC4gVG8gYXBwbHkgYSBwYXJ0aWN1bGFyIGljb24gaW5zaWRlIGFuCiAgICAgKiBlbGVtZW50IHVzZSB0aGUgYGFwcGx5SWNvbmAgbWV0aG9kLiBGb3IgZXhhbXBsZToKICAgICAqCiAgICAgKiAgICAgaWNvbnNldC5hcHBseUljb24oaWNvbk5vZGUsICdjYXInKTsKICAgICAqCiAgICAgKiBAZWxlbWVudCBpcm9uLWljb25zZXQtc3ZnCiAgICAgKiBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAqIEBpbXBsZW1lbnRzIHtQb2x5bWVyLkljb25zZXR9CiAgICAgKi8KICAgIFBvbHltZXIoewogICAgICBpczogJ2lyb24taWNvbnNldC1zdmcnLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgaWNvbnNldC4KICAgICAgICAgKi8KICAgICAgICBuYW1lOiB7dHlwZTogU3RyaW5nLCBvYnNlcnZlcjogJ19uYW1lQ2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgc2l6ZSBvZiBhbiBpbmRpdmlkdWFsIGljb24uIE5vdGUgdGhhdCBpY29ucyBtdXN0IGJlIHNxdWFyZS4KICAgICAgICAgKi8KICAgICAgICBzaXplOiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMjR9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBlbmFibGUgbWlycm9yaW5nIG9mIGljb25zIHdoZXJlIHNwZWNpZmllZCB3aGVuIHRoZXkgYXJlCiAgICAgICAgICogc3RhbXBlZC4gSWNvbnMgdGhhdCBzaG91bGQgYmUgbWlycm9yZWQgc2hvdWxkIGJlIGRlY29yYXRlZCB3aXRoIGEKICAgICAgICAgKiBgbWlycm9yLWluLXJ0bGAgYXR0cmlidXRlLgogICAgICAgICAqCiAgICAgICAgICogTk9URTogRm9yIHBlcmZvcm1hbmNlIHJlYXNvbnMsIGRpcmVjdGlvbiB3aWxsIGJlIHJlc29sdmVkIG9uY2UgcGVyCiAgICAgICAgICogZG9jdW1lbnQgcGVyIGljb25zZXQsIHNvIG1vdmluZyBpY29ucyBpbiBhbmQgb3V0IG9mIFJUTCBzdWJ0cmVlcyB3aWxsCiAgICAgICAgICogbm90IGNhdXNlIHRoZWlyIG1pcnJvcmVkIHN0YXRlIHRvIGNoYW5nZS4KICAgICAgICAgKi8KICAgICAgICBydGxNaXJyb3Jpbmc6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBtZWFzdXJlIFJUTCBiYXNlZCBvbiB0aGUgZGlyIGF0dHJpYnV0ZSBvbiB0aGUgYm9keSBvcgogICAgICAgICAqIGh0bWwgZWxlbWVudHMgKG1lYXN1cmVkIG9uIGRvY3VtZW50LmJvZHkgb3IgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50IGFzCiAgICAgICAgICogYXZhaWxhYmxlKS4KICAgICAgICAgKi8KICAgICAgICB1c2VHbG9iYWxSdGxBdHRyaWJ1dGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9CiAgICAgIH0sCgogICAgICBjcmVhdGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9tZXRhID0gbmV3IElyb25NZXRhKHt0eXBlOiAnaWNvbnNldCcsIGtleTogbnVsbCwgdmFsdWU6IG51bGx9KTsKICAgICAgfSwKCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ29uc3RydWN0IGFuIGFycmF5IG9mIGFsbCBpY29uIG5hbWVzIGluIHRoaXMgaWNvbnNldC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IUFycmF5fSBBcnJheSBvZiBpY29uIG5hbWVzLgogICAgICAgKi8KICAgICAgZ2V0SWNvbk5hbWVzOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9pY29ucyA9IHRoaXMuX2NyZWF0ZUljb25NYXAoKTsKICAgICAgICByZXR1cm4gT2JqZWN0LmtleXModGhpcy5faWNvbnMpLm1hcChmdW5jdGlvbihuKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5uYW1lICsgJzonICsgbjsKICAgICAgICB9LCB0aGlzKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBcHBsaWVzIGFuIGljb24gdG8gdGhlIGdpdmVuIGVsZW1lbnQuCiAgICAgICAqCiAgICAgICAqIEFuIHN2ZyBpY29uIGlzIHByZXBlbmRlZCB0byB0aGUgZWxlbWVudCdzIHNoYWRvd1Jvb3QgaWYgaXQgZXhpc3RzLAogICAgICAgKiBvdGhlcndpc2UgdG8gdGhlIGVsZW1lbnQgaXRzZWxmLgogICAgICAgKgogICAgICAgKiBJZiBSVEwgbWlycm9yaW5nIGlzIGVuYWJsZWQsIGFuZCB0aGUgaWNvbiBpcyBtYXJrZWQgdG8gYmUgbWlycm9yZWQgaW4KICAgICAgICogUlRMLCB0aGUgZWxlbWVudCB3aWxsIGJlIHRlc3RlZCAob25jZSBhbmQgb25seSBvbmNlIGV2ZXIgZm9yIGVhY2gKICAgICAgICogaWNvbnNldCkgdG8gZGV0ZXJtaW5lIHRoZSBkaXJlY3Rpb24gb2YgdGhlIHN1YnRyZWUgdGhlIGVsZW1lbnQgaXMgaW4uCiAgICAgICAqIFRoaXMgZGlyZWN0aW9uIHdpbGwgYXBwbHkgdG8gYWxsIGZ1dHVyZSBpY29uIGFwcGxpY2F0aW9ucywgYWx0aG91Z2ggb25seQogICAgICAgKiBpY29ucyBtYXJrZWQgdG8gYmUgbWlycm9yZWQgd2lsbCBiZSBhZmZlY3RlZC4KICAgICAgICoKICAgICAgICogQG1ldGhvZCBhcHBseUljb24KICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50IEVsZW1lbnQgdG8gd2hpY2ggdGhlIGljb24gaXMgYXBwbGllZC4KICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGljb25OYW1lIE5hbWUgb2YgdGhlIGljb24gdG8gYXBwbHkuCiAgICAgICAqIEByZXR1cm4gez9FbGVtZW50fSBUaGUgc3ZnIGVsZW1lbnQgd2hpY2ggcmVuZGVycyB0aGUgaWNvbi4KICAgICAgICovCiAgICAgIGFwcGx5SWNvbjogZnVuY3Rpb24oZWxlbWVudCwgaWNvbk5hbWUpIHsKICAgICAgICAvLyBSZW1vdmUgb2xkIHN2ZyBlbGVtZW50CiAgICAgICAgdGhpcy5yZW1vdmVJY29uKGVsZW1lbnQpOwogICAgICAgIC8vIGluc3RhbGwgbmV3IHN2ZyBlbGVtZW50CiAgICAgICAgdmFyIHN2ZyA9IHRoaXMuX2Nsb25lSWNvbigKICAgICAgICAgICAgaWNvbk5hbWUsIHRoaXMucnRsTWlycm9yaW5nICYmIHRoaXMuX3RhcmdldElzUlRMKGVsZW1lbnQpKTsKICAgICAgICBpZiAoc3ZnKSB7CiAgICAgICAgICAvLyBpbnNlcnQgc3ZnIGVsZW1lbnQgaW50byBzaGFkb3cgcm9vdCwgaWYgaXQgZXhpc3RzCiAgICAgICAgICB2YXIgcGRlID0gZG9tKGVsZW1lbnQucm9vdCB8fCBlbGVtZW50KTsKICAgICAgICAgIHBkZS5pbnNlcnRCZWZvcmUoc3ZnLCBwZGUuY2hpbGROb2Rlc1swXSk7CiAgICAgICAgICByZXR1cm4gZWxlbWVudC5fc3ZnSWNvbiA9IHN2ZzsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVtb3ZlIGFuIGljb24gZnJvbSB0aGUgZ2l2ZW4gZWxlbWVudCBieSB1bmRvaW5nIHRoZSBjaGFuZ2VzIGVmZmVjdGVkCiAgICAgICAqIGJ5IGBhcHBseUljb25gLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IGVsZW1lbnQgVGhlIGVsZW1lbnQgZnJvbSB3aGljaCB0aGUgaWNvbiBpcyByZW1vdmVkLgogICAgICAgKi8KICAgICAgcmVtb3ZlSWNvbjogZnVuY3Rpb24oZWxlbWVudCkgewogICAgICAgIC8vIFJlbW92ZSBvbGQgc3ZnIGVsZW1lbnQKICAgICAgICBpZiAoZWxlbWVudC5fc3ZnSWNvbikgewogICAgICAgICAgZG9tKGVsZW1lbnQucm9vdCB8fCBlbGVtZW50KS5yZW1vdmVDaGlsZChlbGVtZW50Ll9zdmdJY29uKTsKICAgICAgICAgIGVsZW1lbnQuX3N2Z0ljb24gPSBudWxsOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBNZWFzdXJlcyBhbmQgbWVtb2l6ZXMgdGhlIGRpcmVjdGlvbiBvZiB0aGUgZWxlbWVudC4gTm90ZSB0aGF0IHRoaXMKICAgICAgICogbWVhc3VyZW1lbnQgaXMgb25seSBkb25lIG9uY2UgYW5kIHRoZSByZXN1bHQgaXMgbWVtb2l6ZWQgZm9yIGZ1dHVyZQogICAgICAgKiBpbnZvY2F0aW9ucy4KICAgICAgICovCiAgICAgIF90YXJnZXRJc1JUTDogZnVuY3Rpb24odGFyZ2V0KSB7CiAgICAgICAgaWYgKHRoaXMuX190YXJnZXRJc1JUTCA9PSBudWxsKSB7CiAgICAgICAgICBpZiAodGhpcy51c2VHbG9iYWxSdGxBdHRyaWJ1dGUpIHsKICAgICAgICAgICAgdmFyIGdsb2JhbEVsZW1lbnQgPQogICAgICAgICAgICAgICAgKGRvY3VtZW50LmJvZHkgJiYgZG9jdW1lbnQuYm9keS5oYXNBdHRyaWJ1dGUoJ2RpcicpKSA/CiAgICAgICAgICAgICAgICBkb2N1bWVudC5ib2R5IDoKICAgICAgICAgICAgICAgIGRvY3VtZW50LmRvY3VtZW50RWxlbWVudDsKCiAgICAgICAgICAgIHRoaXMuX190YXJnZXRJc1JUTCA9IGdsb2JhbEVsZW1lbnQuZ2V0QXR0cmlidXRlKCdkaXInKSA9PT0gJ3J0bCc7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAodGFyZ2V0ICYmIHRhcmdldC5ub2RlVHlwZSAhPT0gTm9kZS5FTEVNRU5UX05PREUpIHsKICAgICAgICAgICAgICB0YXJnZXQgPSB0YXJnZXQuaG9zdDsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgdGhpcy5fX3RhcmdldElzUlRMID0KICAgICAgICAgICAgICAgIHRhcmdldCAmJiB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZSh0YXJnZXQpWydkaXJlY3Rpb24nXSA9PT0gJ3J0bCc7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdGhpcy5fX3RhcmdldElzUlRMOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqCiAgICAgICAqIFdoZW4gbmFtZSBpcyBjaGFuZ2VkLCByZWdpc3RlciBpY29uc2V0IG1ldGFkYXRhCiAgICAgICAqCiAgICAgICAqLwogICAgICBfbmFtZUNoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX21ldGEudmFsdWUgPSBudWxsOwogICAgICAgIHRoaXMuX21ldGEua2V5ID0gdGhpcy5uYW1lOwogICAgICAgIHRoaXMuX21ldGEudmFsdWUgPSB0aGlzOwoKICAgICAgICB0aGlzLmFzeW5jKGZ1bmN0aW9uKCkgewogICAgICAgICAgdGhpcy5maXJlKCdpcm9uLWljb25zZXQtYWRkZWQnLCB0aGlzLCB7bm9kZTogd2luZG93fSk7CiAgICAgICAgfSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ3JlYXRlIGEgbWFwIG9mIGNoaWxkIFNWRyBlbGVtZW50cyBieSBpZC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IU9iamVjdH0gTWFwIG9mIGlkJ3MgdG8gU1ZHIGVsZW1lbnRzLgogICAgICAgKi8KICAgICAgX2NyZWF0ZUljb25NYXA6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIE9iamVjdHMgY2hhaW5lZCB0byBPYmplY3QucHJvdG90eXBlIChge31gKSBoYXZlIG1lbWJlcnMuIFNwZWNpZmljYWxseSwKICAgICAgICAvLyBvbiBGRiB0aGVyZSBpcyBhIGB3YXRjaGAgbWV0aG9kIHRoYXQgY29uZnVzZXMgdGhlIGljb24gbWFwLCBzbyB3ZQogICAgICAgIC8vIG5lZWQgdG8gdXNlIGEgbnVsbC1iYXNlZCBvYmplY3QgaGVyZS4KICAgICAgICB2YXIgaWNvbnMgPSBPYmplY3QuY3JlYXRlKG51bGwpOwogICAgICAgIGRvbSh0aGlzKS5xdWVyeVNlbGVjdG9yQWxsKCdbaWRdJykuZm9yRWFjaChmdW5jdGlvbihpY29uKSB7CiAgICAgICAgICBpY29uc1tpY29uLmlkXSA9IGljb247CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGljb25zOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFByb2R1Y2UgaW5zdGFsbGFibGUgY2xvbmUgb2YgdGhlIFNWRyBlbGVtZW50IG1hdGNoaW5nIGBpZGAgaW4gdGhpcwogICAgICAgKiBpY29uc2V0LCBvciBgdW5kZWZpbmVkYCBpZiB0aGVyZSBpcyBubyBtYXRjaGluZyBlbGVtZW50LgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHtFbGVtZW50fSBSZXR1cm5zIGFuIGluc3RhbGxhYmxlIGNsb25lIG9mIHRoZSBTVkcgZWxlbWVudAogICAgICAgKiBtYXRjaGluZyBgaWRgLgogICAgICAgKi8KICAgICAgX2Nsb25lSWNvbjogZnVuY3Rpb24oaWQsIG1pcnJvckFsbG93ZWQpIHsKICAgICAgICAvLyBjcmVhdGUgdGhlIGljb24gbWFwIG9uLWRlbWFuZCwgc2luY2UgdGhlIGljb25zZXQgaXRzZWxmIGhhcyBubyBkaXNjcmV0ZQogICAgICAgIC8vIHNpZ25hbCB0byBrbm93IHdoZW4gaXQncyBjaGlsZHJlbiBhcmUgZnVsbHkgcGFyc2VkCiAgICAgICAgdGhpcy5faWNvbnMgPSB0aGlzLl9pY29ucyB8fCB0aGlzLl9jcmVhdGVJY29uTWFwKCk7CiAgICAgICAgcmV0dXJuIHRoaXMuX3ByZXBhcmVTdmdDbG9uZSh0aGlzLl9pY29uc1tpZF0sIHRoaXMuc2l6ZSwgbWlycm9yQWxsb3dlZCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBzb3VyY2VTdmcKICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHNpemUKICAgICAgICogQHBhcmFtIHtCb29sZWFufSBtaXJyb3JBbGxvd2VkCiAgICAgICAqIEByZXR1cm4ge0VsZW1lbnR9CiAgICAgICAqLwogICAgICBfcHJlcGFyZVN2Z0Nsb25lOiBmdW5jdGlvbihzb3VyY2VTdmcsIHNpemUsIG1pcnJvckFsbG93ZWQpIHsKICAgICAgICBpZiAoc291cmNlU3ZnKSB7CiAgICAgICAgICB2YXIgY29udGVudCA9IHNvdXJjZVN2Zy5jbG9uZU5vZGUodHJ1ZSksCiAgICAgICAgICAgICAgc3ZnID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCdodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZycsICdzdmcnKSwKICAgICAgICAgICAgICB2aWV3Qm94ID0KICAgICAgICAgICAgICAgICAgY29udGVudC5nZXRBdHRyaWJ1dGUoJ3ZpZXdCb3gnKSB8fCAnMCAwICcgKyBzaXplICsgJyAnICsgc2l6ZSwKICAgICAgICAgICAgICBjc3NUZXh0ID0KICAgICAgICAgICAgICAgICAgJ3BvaW50ZXItZXZlbnRzOiBub25lOyBkaXNwbGF5OiBibG9jazsgd2lkdGg6IDEwMCU7IGhlaWdodDogMTAwJTsnOwoKICAgICAgICAgIGlmIChtaXJyb3JBbGxvd2VkICYmIGNvbnRlbnQuaGFzQXR0cmlidXRlKCdtaXJyb3ItaW4tcnRsJykpIHsKICAgICAgICAgICAgY3NzVGV4dCArPQogICAgICAgICAgICAgICAgJy13ZWJraXQtdHJhbnNmb3JtOnNjYWxlKC0xLDEpO3RyYW5zZm9ybTpzY2FsZSgtMSwxKTt0cmFuc2Zvcm0tb3JpZ2luOmNlbnRlcjsnOwogICAgICAgICAgfQoKICAgICAgICAgIHN2Zy5zZXRBdHRyaWJ1dGUoJ3ZpZXdCb3gnLCB2aWV3Qm94KTsKICAgICAgICAgIHN2Zy5zZXRBdHRyaWJ1dGUoJ3ByZXNlcnZlQXNwZWN0UmF0aW8nLCAneE1pZFlNaWQgbWVldCcpOwogICAgICAgICAgc3ZnLnNldEF0dHJpYnV0ZSgnZm9jdXNhYmxlJywgJ2ZhbHNlJyk7CiAgICAgICAgICAvLyBUT0RPKGRmcmVlZG0pOiBgcG9pbnRlci1ldmVudHM6IG5vbmVgIHdvcmtzIGFyb3VuZAogICAgICAgICAgLy8gaHR0cHM6Ly9jcmJ1Zy5jb20vMzcwMTM2CiAgICAgICAgICAvLyBUT0RPKHNqbWlsZXMpOiBpbmxpbmUgc3R5bGUgbWF5IG5vdCBiZSBpZGVhbCwgYnV0IGF2b2lkcyByZXF1aXJpbmcgYQogICAgICAgICAgLy8gc2hhZG93LXJvb3QKICAgICAgICAgIHN2Zy5zdHlsZS5jc3NUZXh0ID0gY3NzVGV4dDsKICAgICAgICAgIHN2Zy5hcHBlbmRDaGlsZChjb250ZW50KS5yZW1vdmVBdHRyaWJ1dGUoJ2lkJyk7CiAgICAgICAgICByZXR1cm4gc3ZnOwogICAgICAgIH0KICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgfQoKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNCBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNvbnN0IHRlbXBsYXRlJDIgPSBodG1sYDxpcm9uLWljb25zZXQtc3ZnIG5hbWU9ImltYWdlIiBzaXplPSIyNCI+Cjxzdmc+PGRlZnM+CjxnIGlkPSJhZGQtYS1waG90byI+PHBhdGggZD0iTTMgNFYxaDJ2M2gzdjJINXYzSDNWNkgwVjRoM3ptMyA2VjdoM1Y0aDdsMS44MyAySDIxYzEuMSAwIDIgLjkgMiAydjEyYzAgMS4xLS45IDItMiAySDVjLTEuMSAwLTItLjktMi0yVjEwaDN6bTcgOWMyLjc2IDAgNS0yLjI0IDUtNXMtMi4yNC01LTUtNS01IDIuMjQtNSA1IDIuMjQgNSA1IDV6bS0zLjItNWMwIDEuNzcgMS40MyAzLjIgMy4yIDMuMnMzLjItMS40MyAzLjItMy4yLTEuNDMtMy4yLTMuMi0zLjItMy4yIDEuNDMtMy4yIDMuMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJhZGQtdG8tcGhvdG9zIj48cGF0aCBkPSJNNCA2SDJ2MTRjMCAxLjEuOSAyIDIgMmgxNHYtMkg0VjZ6bTE2LTRIOGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxMmMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tMSA5aC00djRoLTJ2LTRIOVY5aDRWNWgydjRoNHYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFkanVzdCI+PHBhdGggZD0iTTEyIDJDNi40OSAyIDIgNi40OSAyIDEyczQuNDkgMTAgMTAgMTAgMTAtNC40OSAxMC0xMFMxNy41MSAyIDEyIDJ6bTAgMThjLTQuNDEgMC04LTMuNTktOC04czMuNTktOCA4LTggOCAzLjU5IDggOC0zLjU5IDgtOCA4em0zLThjMCAxLjY2LTEuMzQgMy0zIDNzLTMtMS4zNC0zLTMgMS4zNC0zIDMtMyAzIDEuMzQgMyAzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFzc2lzdGFudCI+PHBhdGggZD0iTTE5IDJINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmg0bDMgMyAzLTNoNGMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tNS4xMiAxMC44OEwxMiAxN2wtMS44OC00LjEyTDYgMTFsNC4xMi0xLjg4TDEyIDVsMS44OCA0LjEyTDE4IDExbC00LjEyIDEuODh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXNzaXN0YW50LXBob3RvIj48cGF0aCBkPSJNMTQuNCA2TDE0IDRINXYxN2gydi03aDUuNmwuNCAyaDdWNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJhdWRpb3RyYWNrIj48cGF0aCBkPSJNMTIgM3Y5LjI4Yy0uNDctLjE3LS45Ny0uMjgtMS41LS4yOEM4LjAxIDEyIDYgMTQuMDEgNiAxNi41UzguMDEgMjEgMTAuNSAyMWMyLjMxIDAgNC4yLTEuNzUgNC40NS00SDE1VjZoNFYzaC03eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJsdXItY2lyY3VsYXIiPjxwYXRoIGQ9Ik0xMCA5Yy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6bTAgNGMtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTEtLjQ1LTEtMS0xek03IDkuNWMtLjI4IDAtLjUuMjItLjUuNXMuMjIuNS41LjUuNS0uMjIuNS0uNS0uMjItLjUtLjUtLjV6bTMgN2MtLjI4IDAtLjUuMjItLjUuNXMuMjIuNS41LjUuNS0uMjIuNS0uNS0uMjItLjUtLjUtLjV6bS0zLTNjLS4yOCAwLS41LjIyLS41LjVzLjIyLjUuNS41LjUtLjIyLjUtLjUtLjIyLS41LS41LS41em0zLTZjLjI4IDAgLjUtLjIyLjUtLjVzLS4yMi0uNS0uNS0uNS0uNS4yMi0uNS41LjIyLjUuNS41ek0xNCA5Yy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6bTAtMS41Yy4yOCAwIC41LS4yMi41LS41cy0uMjItLjUtLjUtLjUtLjUuMjItLjUuNS4yMi41LjUuNXptMyA2Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXptMC00Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXpNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MiAwLTgtMy41OC04LThzMy41OC04IDgtOCA4IDMuNTggOCA4LTMuNTggOC04IDh6bTItMy41Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXptMC0zLjVjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJibHVyLWxpbmVhciI+PHBhdGggZD0iTTUgMTcuNWMuODMgMCAxLjUtLjY3IDEuNS0xLjVzLS42Ny0xLjUtMS41LTEuNS0xLjUuNjctMS41IDEuNS42NyAxLjUgMS41IDEuNXpNOSAxM2MuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxem0wLTRjLjU1IDAgMS0uNDUgMS0xcy0uNDUtMS0xLTEtMSAuNDUtMSAxIC40NSAxIDEgMXpNMyAyMWgxOHYtMkgzdjJ6TTUgOS41Yy44MyAwIDEuNS0uNjcgMS41LTEuNVM1LjgzIDYuNSA1IDYuNSAzLjUgNy4xNyAzLjUgOCA0LjE3IDkuNSA1IDkuNXptMCA0Yy44MyAwIDEuNS0uNjcgMS41LTEuNXMtLjY3LTEuNS0xLjUtMS41LTEuNS42Ny0xLjUgMS41LjY3IDEuNSAxLjUgMS41ek05IDE3Yy41NSAwIDEtLjQ1IDEtMXMtLjQ1LTEtMS0xLTEgLjQ1LTEgMSAuNDUgMSAxIDF6bTgtLjVjLjI4IDAgLjUtLjIyLjUtLjVzLS4yMi0uNS0uNS0uNS0uNS4yMi0uNS41LjIyLjUuNS41ek0zIDN2MmgxOFYzSDN6bTE0IDUuNWMuMjggMCAuNS0uMjIuNS0uNXMtLjIyLS41LS41LS41LS41LjIyLS41LjUuMjIuNS41LjV6bTAgNGMuMjggMCAuNS0uMjIuNS0uNXMtLjIyLS41LS41LS41LS41LjIyLS41LjUuMjIuNS41LjV6TTEzIDljLjU1IDAgMS0uNDUgMS0xcy0uNDUtMS0xLTEtMSAuNDUtMSAxIC40NSAxIDEgMXptMCA0Yy41NSAwIDEtLjQ1IDEtMXMtLjQ1LTEtMS0xLTEgLjQ1LTEgMSAuNDUgMSAxIDF6bTAgNGMuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJsdXItb2ZmIj48cGF0aCBkPSJNMTQgN2MuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxem0tLjIgNC40OGwuMi4wMmMuODMgMCAxLjUtLjY3IDEuNS0xLjVzLS42Ny0xLjUtMS41LTEuNS0xLjUuNjctMS41IDEuNWwuMDIuMmMuMDkuNjcuNjEgMS4xOSAxLjI4IDEuMjh6TTE0IDMuNWMuMjggMCAuNS0uMjIuNS0uNXMtLjIyLS41LS41LS41LS41LjIyLS41LjUuMjIuNS41LjV6bS00IDBjLjI4IDAgLjUtLjIyLjUtLjVzLS4yMi0uNS0uNS0uNS0uNS4yMi0uNS41LjIyLjUuNS41em0xMSA3Yy4yOCAwIC41LS4yMi41LS41cy0uMjItLjUtLjUtLjUtLjUuMjItLjUuNS4yMi41LjUuNXpNMTAgN2MuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxem04IDhjLjU1IDAgMS0uNDUgMS0xcy0uNDUtMS0xLTEtMSAuNDUtMSAxIC40NSAxIDEgMXptMC00Yy41NSAwIDEtLjQ1IDEtMXMtLjQ1LTEtMS0xLTEgLjQ1LTEgMSAuNDUgMSAxIDF6bTAtNGMuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxem0tNCAxMy41Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXpNMi41IDUuMjdsMy43OCAzLjc4TDYgOWMtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTFjMC0uMS0uMDMtLjE5LS4wNi0uMjhsMi44MSAyLjgxYy0uNzEuMTEtMS4yNS43My0xLjI1IDEuNDcgMCAuODMuNjcgMS41IDEuNSAxLjUuNzQgMCAxLjM2LS41NCAxLjQ3LTEuMjVsMi44MSAyLjgxYy0uMDktLjAzLS4xOC0uMDYtLjI4LS4wNi0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMWMwLS4xLS4wMy0uMTktLjA2LS4yOGwzLjc4IDMuNzhMMjAgMjAuMjMgMy43NyA0IDIuNSA1LjI3ek0xMCAxN2MtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTEtLjQ1LTEtMS0xem0xMS0zLjVjLS4yOCAwLS41LjIyLS41LjVzLjIyLjUuNS41LjUtLjIyLjUtLjUtLjIyLS41LS41LS41ek02IDEzYy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6TTMgOS41Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXptNyAxMWMtLjI4IDAtLjUuMjItLjUuNXMuMjIuNS41LjUuNS0uMjIuNS0uNS0uMjItLjUtLjUtLjV6TTYgMTdjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXptLTMtMy41Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJibHVyLW9uIj48cGF0aCBkPSJNNiAxM2MtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTEtLjQ1LTEtMS0xem0wIDRjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXptMC04Yy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6bS0zIC41Yy0uMjggMC0uNS4yMi0uNS41cy4yMi41LjUuNS41LS4yMi41LS41LS4yMi0uNS0uNS0uNXpNNiA1Yy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6bTE1IDUuNWMuMjggMCAuNS0uMjIuNS0uNXMtLjIyLS41LS41LS41LS41LjIyLS41LjUuMjIuNS41LjV6TTE0IDdjLjU1IDAgMS0uNDUgMS0xcy0uNDUtMS0xLTEtMSAuNDUtMSAxIC40NSAxIDEgMXptMC0zLjVjLjI4IDAgLjUtLjIyLjUtLjVzLS4yMi0uNS0uNS0uNS0uNS4yMi0uNS41LjIyLjUuNS41em0tMTEgMTBjLS4yOCAwLS41LjIyLS41LjVzLjIyLjUuNS41LjUtLjIyLjUtLjUtLjIyLS41LS41LS41em03IDdjLS4yOCAwLS41LjIyLS41LjVzLjIyLjUuNS41LjUtLjIyLjUtLjUtLjIyLS41LS41LS41em0wLTE3Yy4yOCAwIC41LS4yMi41LS41cy0uMjItLjUtLjUtLjUtLjUuMjItLjUuNS4yMi41LjUuNXpNMTAgN2MuNTUgMCAxLS40NSAxLTFzLS40NS0xLTEtMS0xIC40NS0xIDEgLjQ1IDEgMSAxem0wIDUuNWMtLjgzIDAtMS41LjY3LTEuNSAxLjVzLjY3IDEuNSAxLjUgMS41IDEuNS0uNjcgMS41LTEuNS0uNjctMS41LTEuNS0xLjV6bTggLjVjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXptMCA0Yy0uNTUgMC0xIC40NS0xIDFzLjQ1IDEgMSAxIDEtLjQ1IDEtMS0uNDUtMS0xLTF6bTAtOGMtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTEtLjQ1LTEtMS0xem0wLTRjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXptMyA4LjVjLS4yOCAwLS41LjIyLS41LjVzLjIyLjUuNS41LjUtLjIyLjUtLjUtLjIyLS41LS41LS41ek0xNCAxN2MtLjU1IDAtMSAuNDUtMSAxcy40NSAxIDEgMSAxLS40NSAxLTEtLjQ1LTEtMS0xem0wIDMuNWMtLjI4IDAtLjUuMjItLjUuNXMuMjIuNS41LjUuNS0uMjIuNS0uNS0uMjItLjUtLjUtLjV6bS00LTEyYy0uODMgMC0xLjUuNjctMS41IDEuNXMuNjcgMS41IDEuNSAxLjUgMS41LS42NyAxLjUtMS41LS42Ny0xLjUtMS41LTEuNXptMCA4LjVjLS41NSAwLTEgLjQ1LTEgMXMuNDUgMSAxIDEgMS0uNDUgMS0xLS40NS0xLTEtMXptNC00LjVjLS44MyAwLTEuNS42Ny0xLjUgMS41cy42NyAxLjUgMS41IDEuNSAxLjUtLjY3IDEuNS0xLjUtLjY3LTEuNS0xLjUtMS41em0wLTRjLS44MyAwLTEuNS42Ny0xLjUgMS41cy42NyAxLjUgMS41IDEuNSAxLjUtLjY3IDEuNS0xLjUtLjY3LTEuNS0xLjUtMS41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtMSI+PGNpcmNsZSBjeD0iMTIiIGN5PSIxMiIgcj0iMTAiPjwvY2lyY2xlPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtMiI+PHBhdGggZD0iTTEwIDJjLTEuODIgMC0zLjUzLjUtNSAxLjM1QzcuOTkgNS4wOCAxMCA4LjMgMTAgMTJzLTIuMDEgNi45Mi01IDguNjVDNi40NyAyMS41IDguMTggMjIgMTAgMjJjNS41MiAwIDEwLTQuNDggMTAtMTBTMTUuNTIgMiAxMCAyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtMyI+PHBhdGggZD0iTTkgMmMtMS4wNSAwLTIuMDUuMTYtMyAuNDYgNC4wNiAxLjI3IDcgNS4wNiA3IDkuNTQgMCA0LjQ4LTIuOTQgOC4yNy03IDkuNTQuOTUuMyAxLjk1LjQ2IDMgLjQ2IDUuNTIgMCAxMC00LjQ4IDEwLTEwUzE0LjUyIDIgOSAyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtNCI+PHBhdGggZD0iTTIwIDguNjlWNGgtNC42OUwxMiAuNjkgOC42OSA0SDR2NC42OUwuNjkgMTIgNCAxNS4zMVYyMGg0LjY5TDEyIDIzLjMxIDE1LjMxIDIwSDIwdi00LjY5TDIzLjMxIDEyIDIwIDguNjl6TTEyIDE4Yy0uODkgMC0xLjc0LS4yLTIuNS0uNTVDMTEuNTYgMTYuNSAxMyAxNC40MiAxMyAxMnMtMS40NC00LjUtMy41LTUuNDVDMTAuMjYgNi4yIDExLjExIDYgMTIgNmMzLjMxIDAgNiAyLjY5IDYgNnMtMi42OSA2LTYgNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJicmlnaHRuZXNzLTUiPjxwYXRoIGQ9Ik0yMCAxNS4zMUwyMy4zMSAxMiAyMCA4LjY5VjRoLTQuNjlMMTIgLjY5IDguNjkgNEg0djQuNjlMLjY5IDEyIDQgMTUuMzFWMjBoNC42OUwxMiAyMy4zMSAxNS4zMSAyMEgyMHYtNC42OXpNMTIgMThjLTMuMzEgMC02LTIuNjktNi02czIuNjktNiA2LTYgNiAyLjY5IDYgNi0yLjY5IDYtNiA2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtNiI+PHBhdGggZD0iTTIwIDE1LjMxTDIzLjMxIDEyIDIwIDguNjlWNGgtNC42OUwxMiAuNjkgOC42OSA0SDR2NC42OUwuNjkgMTIgNCAxNS4zMVYyMGg0LjY5TDEyIDIzLjMxIDE1LjMxIDIwSDIwdi00LjY5ek0xMiAxOFY2YzMuMzEgMCA2IDIuNjkgNiA2cy0yLjY5IDYtNiA2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJyaWdodG5lc3MtNyI+PHBhdGggZD0iTTIwIDguNjlWNGgtNC42OUwxMiAuNjkgOC42OSA0SDR2NC42OUwuNjkgMTIgNCAxNS4zMVYyMGg0LjY5TDEyIDIzLjMxIDE1LjMxIDIwSDIwdi00LjY5TDIzLjMxIDEyIDIwIDguNjl6TTEyIDE4Yy0zLjMxIDAtNi0yLjY5LTYtNnMyLjY5LTYgNi02IDYgMi42OSA2IDYtMi42OSA2LTYgNnptMC0xMGMtMi4yMSAwLTQgMS43OS00IDRzMS43OSA0IDQgNCA0LTEuNzkgNC00LTEuNzktNC00LTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYnJva2VuLWltYWdlIj48cGF0aCBkPSJNMjEgNXY2LjU5bC0zLTMuMDEtNCA0LjAxLTQtNC00IDQtMy0zLjAxVjVjMC0xLjEuOS0yIDItMmgxNGMxLjEgMCAyIC45IDIgMnptLTMgNi40MmwzIDMuMDFWMTljMCAxLjEtLjkgMi0yIDJINWMtMS4xIDAtMi0uOS0yLTJ2LTYuNThsMyAyLjk5IDQtNCA0IDQgNC0zLjk5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJydXNoIj48cGF0aCBkPSJNNyAxNGMtMS42NiAwLTMgMS4zNC0zIDMgMCAxLjMxLTEuMTYgMi0yIDIgLjkyIDEuMjIgMi40OSAyIDQgMiAyLjIxIDAgNC0xLjc5IDQtNCAwLTEuNjYtMS4zNC0zLTMtM3ptMTMuNzEtOS4zN2wtMS4zNC0xLjM0Yy0uMzktLjM5LTEuMDItLjM5LTEuNDEgMEw5IDEyLjI1IDExLjc1IDE1bDguOTYtOC45NmMuMzktLjM5LjM5LTEuMDIgMC0xLjQxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJ1cnN0LW1vZGUiPjxwYXRoIGQ9Ik0xIDVoMnYxNEgxem00IDBoMnYxNEg1em0xNyAwSDEwYy0uNTUgMC0xIC40NS0xIDF2MTJjMCAuNTUuNDUgMSAxIDFoMTJjLjU1IDAgMS0uNDUgMS0xVjZjMC0uNTUtLjQ1LTEtMS0xek0xMSAxN2wyLjUtMy4xNUwxNS4yOSAxNmwyLjUtMy4yMkwyMSAxN0gxMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJjYW1lcmEiPjxwYXRoIGQ9Ik05LjQgMTAuNWw0Ljc3LTguMjZDMTMuNDcgMi4wOSAxMi43NSAyIDEyIDJjLTIuNCAwLTQuNi44NS02LjMyIDIuMjVsMy42NiA2LjM1LjA2LS4xek0yMS41NCA5Yy0uOTItMi45Mi0zLjE1LTUuMjYtNi02LjM0TDExLjg4IDloOS42NnptLjI2IDFoLTcuNDlsLjI5LjUgNC43NiA4LjI1QzIxIDE2Ljk3IDIyIDE0LjYxIDIyIDEyYzAtLjY5LS4wNy0xLjM1LS4yLTJ6TTguNTQgMTJsLTMuOS02Ljc1QzMuMDEgNy4wMyAyIDkuMzkgMiAxMmMwIC42OS4wNyAxLjM1LjIgMmg3LjQ5bC0xLjE1LTJ6bS02LjA4IDNjLjkyIDIuOTIgMy4xNSA1LjI2IDYgNi4zNEwxMi4xMiAxNUgyLjQ2em0xMS4yNyAwbC0zLjkgNi43NmMuNy4xNSAxLjQyLjI0IDIuMTcuMjQgMi40IDAgNC42LS44NSA2LjMyLTIuMjVsLTMuNjYtNi4zNS0uOTMgMS42eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhbWVyYS1hbHQiPjxjaXJjbGUgY3g9IjEyIiBjeT0iMTIiIHI9IjMuMiI+PC9jaXJjbGU+PHBhdGggZD0iTTkgMkw3LjE3IDRINGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY2YzAtMS4xLS45LTItMi0yaC0zLjE3TDE1IDJIOXptMyAxNWMtMi43NiAwLTUtMi4yNC01LTVzMi4yNC01IDUtNSA1IDIuMjQgNSA1LTIuMjQgNS01IDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2FtZXJhLWZyb250Ij48cGF0aCBkPSJNMTAgMjBINXYyaDV2MmwzLTMtMy0zdjJ6bTQgMHYyaDV2LTJoLTV6TTEyIDhjMS4xIDAgMi0uOSAyLTJzLS45LTItMi0yLTEuOTkuOS0xLjk5IDJTMTAuOSA4IDEyIDh6bTUtOEg3QzUuOSAwIDUgLjkgNSAydjE0YzAgMS4xLjkgMiAyIDJoMTBjMS4xIDAgMi0uOSAyLTJWMmMwLTEuMS0uOS0yLTItMnpNNyAyaDEwdjEwLjVjMC0xLjY3LTMuMzMtMi41LTUtMi41cy01IC44My01IDIuNVYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhbWVyYS1yZWFyIj48cGF0aCBkPSJNMTAgMjBINXYyaDV2MmwzLTMtMy0zdjJ6bTQgMHYyaDV2LTJoLTV6bTMtMjBIN0M1LjkgMCA1IC45IDUgMnYxNGMwIDEuMS45IDIgMiAyaDEwYzEuMSAwIDItLjkgMi0yVjJjMC0xLjEtLjktMi0yLTJ6bS01IDZjLTEuMTEgMC0yLS45LTItMnMuODktMiAxLjk5LTIgMiAuOSAyIDJDMTQgNS4xIDEzLjEgNiAxMiA2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhbWVyYS1yb2xsIj48cGF0aCBkPSJNMTQgNWMwLTEuMS0uOS0yLTItMmgtMVYyYzAtLjU1LS40NS0xLTEtMUg2Yy0uNTUgMC0xIC40NS0xIDF2MUg0Yy0xLjEgMC0yIC45LTIgMnYxNWMwIDEuMS45IDIgMiAyaDhjMS4xIDAgMi0uOSAyLTJoOFY1aC04em0tMiAxM2gtMnYtMmgydjJ6bTAtOWgtMlY3aDJ2MnptNCA5aC0ydi0yaDJ2MnptMC05aC0yVjdoMnYyem00IDloLTJ2LTJoMnYyem0wLTloLTJWN2gydjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2VudGVyLWZvY3VzLXN0cm9uZyI+PHBhdGggZD0iTTEyIDhjLTIuMjEgMC00IDEuNzktNCA0czEuNzkgNCA0IDQgNC0xLjc5IDQtNC0xLjc5LTQtNC00em0tNyA3SDN2NGMwIDEuMS45IDIgMiAyaDR2LTJINXYtNHpNNSA1aDRWM0g1Yy0xLjEgMC0yIC45LTIgMnY0aDJWNXptMTQtMmgtNHYyaDR2NGgyVjVjMC0xLjEtLjktMi0yLTJ6bTAgMTZoLTR2Mmg0YzEuMSAwIDItLjkgMi0ydi00aC0ydjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2VudGVyLWZvY3VzLXdlYWsiPjxwYXRoIGQ9Ik01IDE1SDN2NGMwIDEuMS45IDIgMiAyaDR2LTJINXYtNHpNNSA1aDRWM0g1Yy0xLjEgMC0yIC45LTIgMnY0aDJWNXptMTQtMmgtNHYyaDR2NGgyVjVjMC0xLjEtLjktMi0yLTJ6bTAgMTZoLTR2Mmg0YzEuMSAwIDItLjkgMi0ydi00aC0ydjR6TTEyIDhjLTIuMjEgMC00IDEuNzktNCA0czEuNzkgNCA0IDQgNC0xLjc5IDQtNC0xLjc5LTQtNC00em0wIDZjLTEuMSAwLTItLjktMi0ycy45LTIgMi0yIDIgLjkgMiAyLS45IDItMiAyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbGxlY3Rpb25zIj48cGF0aCBkPSJNMjIgMTZWNGMwLTEuMS0uOS0yLTItMkg4Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDEyYzEuMSAwIDItLjkgMi0yem0tMTEtNGwyLjAzIDIuNzFMMTYgMTFsNCA1SDhsMy00ek0yIDZ2MTRjMCAxLjEuOSAyIDIgMmgxNHYtMkg0VjZIMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjb2xsZWN0aW9ucy1ib29rbWFyayI+PHBhdGggZD0iTTQgNkgydjE0YzAgMS4xLjkgMiAyIDJoMTR2LTJINFY2em0xNi00SDhjLTEuMSAwLTIgLjktMiAydjEyYzAgMS4xLjkgMiAyIDJoMTJjMS4xIDAgMi0uOSAyLTJWNGMwLTEuMS0uOS0yLTItMnptMCAxMGwtMi41LTEuNUwxNSAxMlY0aDV2OHoiPjwvcGF0aD48L2c+CjxnIGlkPSJjb2xvci1sZW5zIj48cGF0aCBkPSJNMTIgM2MtNC45NyAwLTkgNC4wMy05IDlzNC4wMyA5IDkgOWMuODMgMCAxLjUtLjY3IDEuNS0xLjUgMC0uMzktLjE1LS43NC0uMzktMS4wMS0uMjMtLjI2LS4zOC0uNjEtLjM4LS45OSAwLS44My42Ny0xLjUgMS41LTEuNUgxNmMyLjc2IDAgNS0yLjI0IDUtNSAwLTQuNDItNC4wMy04LTktOHptLTUuNSA5Yy0uODMgMC0xLjUtLjY3LTEuNS0xLjVTNS42NyA5IDYuNSA5IDggOS42NyA4IDEwLjUgNy4zMyAxMiA2LjUgMTJ6bTMtNEM4LjY3IDggOCA3LjMzIDggNi41UzguNjcgNSA5LjUgNXMxLjUuNjcgMS41IDEuNVMxMC4zMyA4IDkuNSA4em01IDBjLS44MyAwLTEuNS0uNjctMS41LTEuNVMxMy42NyA1IDE0LjUgNXMxLjUuNjcgMS41IDEuNVMxNS4zMyA4IDE0LjUgOHptMyA0Yy0uODMgMC0xLjUtLjY3LTEuNS0xLjVTMTYuNjcgOSAxNy41IDlzMS41LjY3IDEuNSAxLjUtLjY3IDEuNS0xLjUgMS41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbG9yaXplIj48cGF0aCBkPSJNMjAuNzEgNS42M2wtMi4zNC0yLjM0Yy0uMzktLjM5LTEuMDItLjM5LTEuNDEgMGwtMy4xMiAzLjEyLTEuOTMtMS45MS0xLjQxIDEuNDEgMS40MiAxLjQyTDMgMTYuMjVWMjFoNC43NWw4LjkyLTguOTIgMS40MiAxLjQyIDEuNDEtMS40MS0xLjkyLTEuOTIgMy4xMi0zLjEyYy40LS40LjQtMS4wMy4wMS0xLjQyek02LjkyIDE5TDUgMTcuMDhsOC4wNi04LjA2IDEuOTIgMS45Mkw2LjkyIDE5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbXBhcmUiPjxwYXRoIGQ9Ik0xMCAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoNXYyaDJWMWgtMnYyem0wIDE1SDVsNS02djZ6bTktMTVoLTV2Mmg1djEzbC01LTZ2OWg1YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY29udHJvbC1wb2ludCI+PHBhdGggZD0iTTEzIDdoLTJ2NEg3djJoNHY0aDJ2LTRoNHYtMmgtNFY3em0tMS01QzYuNDkgMiAyIDYuNDkgMiAxMnM0LjQ5IDEwIDEwIDEwIDEwLTQuNDkgMTAtMTBTMTcuNTEgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOHMzLjU5LTggOC04IDggMy41OSA4IDgtMy41OSA4LTggOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJjb250cm9sLXBvaW50LWR1cGxpY2F0ZSI+PHBhdGggZD0iTTE2IDhoLTJ2M2gtM3YyaDN2M2gydi0zaDN2LTJoLTN6TTIgMTJjMC0yLjc5IDEuNjQtNS4yIDQuMDEtNi4zMlYzLjUyQzIuNTIgNC43NiAwIDguMDkgMCAxMnMyLjUyIDcuMjQgNi4wMSA4LjQ4di0yLjE2QzMuNjQgMTcuMiAyIDE0Ljc5IDIgMTJ6bTEzLTljLTQuOTYgMC05IDQuMDQtOSA5czQuMDQgOSA5IDkgOS00LjA0IDktOS00LjA0LTktOS05em0wIDE2Yy0zLjg2IDAtNy0zLjE0LTctN3MzLjE0LTcgNy03IDcgMy4xNCA3IDctMy4xNCA3LTcgN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJjcm9wIj48cGF0aCBkPSJNMTcgMTVoMlY3YzAtMS4xLS45LTItMi0ySDl2Mmg4djh6TTcgMTdWMUg1djRIMXYyaDR2MTBjMCAxLjEuOSAyIDIgMmgxMHY0aDJ2LTRoNHYtMkg3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNyb3AtMTYtOSI+PHBhdGggZD0iTTE5IDZINWMtMS4xIDAtMiAuOS0yIDJ2OGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjhjMC0xLjEtLjktMi0yLTJ6bTAgMTBINVY4aDE0djh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC0zLTIiPjxwYXRoIGQ9Ik0xOSA0SDVjLTEuMSAwLTIgLjktMiAydjEyYzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNmMwLTEuMS0uOS0yLTItMnptMCAxNEg1VjZoMTR2MTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC01LTQiPjxwYXRoIGQ9Ik0xOSA1SDVjLTEuMSAwLTIgLjktMiAydjEwYzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWN2MwLTEuMS0uOS0yLTItMnptMCAxMkg1VjdoMTR2MTB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC03LTUiPjxwYXRoIGQ9Ik0xOSA3SDVjLTEuMSAwLTIgLjktMiAydjZjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY5YzAtMS4xLS45LTItMi0yem0wIDhINVY5aDE0djZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC1kaW4iPjxwYXRoIGQ9Ik0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxNkg1VjVoMTR2MTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC1mcmVlIj48cGF0aCBkPSJNMyA1djRoMlY1aDRWM0g1Yy0xLjEgMC0yIC45LTIgMnptMiAxMEgzdjRjMCAxLjEuOSAyIDIgMmg0di0ySDV2LTR6bTE0IDRoLTR2Mmg0YzEuMSAwIDItLjkgMi0ydi00aC0ydjR6bTAtMTZoLTR2Mmg0djRoMlY1YzAtMS4xLS45LTItMi0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNyb3AtbGFuZHNjYXBlIj48cGF0aCBkPSJNMTkgNUg1Yy0xLjEgMC0yIC45LTIgMnYxMGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjdjMC0xLjEtLjktMi0yLTJ6bTAgMTJINVY3aDE0djEweiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNyb3Atb3JpZ2luYWwiPjxwYXRoIGQ9Ik0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxNkg1VjVoMTR2MTR6bS01LjA0LTYuNzFsLTIuNzUgMy41NC0xLjk2LTIuMzZMNi41IDE3aDExbC0zLjU0LTQuNzF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC1wb3J0cmFpdCI+PHBhdGggZD0iTTE3IDNIN2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxMGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2SDdWNWgxMHYxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJjcm9wLXJvdGF0ZSI+PHBhdGggZD0iTTcuNDcgMjEuNDlDNC4yIDE5LjkzIDEuODYgMTYuNzYgMS41IDEzSDBjLjUxIDYuMTYgNS42NiAxMSAxMS45NSAxMSAuMjMgMCAuNDQtLjAyLjY2LS4wM0w4LjggMjAuMTVsLTEuMzMgMS4zNHpNMTIuMDUgMGMtLjIzIDAtLjQ0LjAyLS42Ni4wNGwzLjgxIDMuODEgMS4zMy0xLjMzQzE5LjggNC4wNyAyMi4xNCA3LjI0IDIyLjUgMTFIMjRjLS41MS02LjE2LTUuNjYtMTEtMTEuOTUtMTF6TTE2IDE0aDJWOGMwLTEuMTEtLjktMi0yLTJoLTZ2Mmg2djZ6bS04IDJWNEg2djJINHYyaDJ2OGMwIDEuMS44OSAyIDIgMmg4djJoMnYtMmgydi0ySDh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY3JvcC1zcXVhcmUiPjxwYXRoIGQ9Ik0xOCA0SDZjLTEuMSAwLTIgLjktMiAydjEyYzAgMS4xLjkgMiAyIDJoMTJjMS4xIDAgMi0uOSAyLTJWNmMwLTEuMS0uOS0yLTItMnptMCAxNEg2VjZoMTJ2MTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZGVoYXplIj48cGF0aCBkPSJNMiAxNS41djJoMjB2LTJIMnptMC01djJoMjB2LTJIMnptMC01djJoMjB2LTJIMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJkZXRhaWxzIj48cGF0aCBkPSJNMyA0bDkgMTYgOS0xNkgzem0zLjM4IDJoMTEuMjVMMTIgMTYgNi4zOCA2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImVkaXQiPjxwYXRoIGQ9Ik0zIDE3LjI1VjIxaDMuNzVMMTcuODEgOS45NGwtMy43NS0zLjc1TDMgMTcuMjV6TTIwLjcxIDcuMDRjLjM5LS4zOS4zOS0xLjAyIDAtMS40MWwtMi4zNC0yLjM0Yy0uMzktLjM5LTEuMDItLjM5LTEuNDEgMGwtMS44MyAxLjgzIDMuNzUgMy43NSAxLjgzLTEuODN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwb3N1cmUiPjxwYXRoIGQ9Ik0xNSAxN3YyaDJ2LTJoMnYtMmgtMnYtMmgtMnYyaC0ydjJoMnptNS0xNUg0Yy0xLjEgMC0yIC45LTIgMnYxNmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjRjMC0xLjEtLjktMi0yLTJ6TTUgNWg2djJINVY1em0xNSAxNUg0TDIwIDR2MTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwb3N1cmUtbmVnLTEiPjxwYXRoIGQ9Ik00IDExdjJoOHYtMkg0em0xNSA3aC0yVjcuMzhMMTQgOC40VjYuN0wxOC43IDVoLjN2MTN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwb3N1cmUtbmVnLTIiPjxwYXRoIGQ9Ik0xNS4wNSAxNi4yOWwyLjg2LTMuMDdjLjM4LS4zOS43Mi0uNzkgMS4wNC0xLjE4LjMyLS4zOS41OS0uNzguODItMS4xNy4yMy0uMzkuNDEtLjc4LjU0LTEuMTdzLjE5LS43OS4xOS0xLjE4YzAtLjUzLS4wOS0xLjAyLS4yNy0xLjQ2LS4xOC0uNDQtLjQ0LS44MS0uNzgtMS4xMS0uMzQtLjMxLS43Ny0uNTQtMS4yNi0uNzEtLjUxLS4xNi0xLjA4LS4yNC0xLjcyLS4yNC0uNjkgMC0xLjMxLjExLTEuODUuMzItLjU0LjIxLTEgLjUxLTEuMzYuODgtLjM3LjM3LS42NS44LS44NCAxLjMtLjE4LjQ3LS4yNy45Ny0uMjggMS41aDIuMTRjLjAxLS4zMS4wNS0uNi4xMy0uODcuMDktLjI5LjIzLS41NC40LS43NS4xOC0uMjEuNDEtLjM3LjY4LS40OS4yNy0uMTIuNi0uMTguOTYtLjE4LjMxIDAgLjU4LjA1LjgxLjE1LjIzLjEuNDMuMjUuNTkuNDMuMTYuMTguMjguNC4zNy42NS4wOC4yNS4xMy41Mi4xMy44MSAwIC4yMi0uMDMuNDMtLjA4LjY1LS4wNi4yMi0uMTUuNDUtLjI5LjctLjE0LjI1LS4zMi41My0uNTYuODMtLjIzLjMtLjUyLjY1LS44OCAxLjAzbC00LjE3IDQuNTVWMThIMjF2LTEuNzFoLTUuOTV6TTIgMTF2Mmg4di0ySDJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwb3N1cmUtcGx1cy0xIj48cGF0aCBkPSJNMTAgN0g4djRINHYyaDR2NGgydi00aDR2LTJoLTRWN3ptMTAgMTFoLTJWNy4zOEwxNSA4LjRWNi43TDE5LjcgNWguM3YxM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJleHBvc3VyZS1wbHVzLTIiPjxwYXRoIGQ9Ik0xNi4wNSAxNi4yOWwyLjg2LTMuMDdjLjM4LS4zOS43Mi0uNzkgMS4wNC0xLjE4LjMyLS4zOS41OS0uNzguODItMS4xNy4yMy0uMzkuNDEtLjc4LjU0LTEuMTcuMTMtLjM5LjE5LS43OS4xOS0xLjE4IDAtLjUzLS4wOS0xLjAyLS4yNy0xLjQ2LS4xOC0uNDQtLjQ0LS44MS0uNzgtMS4xMS0uMzQtLjMxLS43Ny0uNTQtMS4yNi0uNzEtLjUxLS4xNi0xLjA4LS4yNC0xLjcyLS4yNC0uNjkgMC0xLjMxLjExLTEuODUuMzItLjU0LjIxLTEgLjUxLTEuMzYuODgtLjM3LjM3LS42NS44LS44NCAxLjMtLjE4LjQ3LS4yNy45Ny0uMjggMS41aDIuMTRjLjAxLS4zMS4wNS0uNi4xMy0uODcuMDktLjI5LjIzLS41NC40LS43NS4xOC0uMjEuNDEtLjM3LjY4LS40OS4yNy0uMTIuNi0uMTguOTYtLjE4LjMxIDAgLjU4LjA1LjgxLjE1LjIzLjEuNDMuMjUuNTkuNDMuMTYuMTguMjguNC4zNy42NS4wOC4yNS4xMy41Mi4xMy44MSAwIC4yMi0uMDMuNDMtLjA4LjY1LS4wNi4yMi0uMTUuNDUtLjI5LjctLjE0LjI1LS4zMi41My0uNTYuODMtLjIzLjMtLjUyLjY1LS44OCAxLjAzbC00LjE3IDQuNTVWMThIMjJ2LTEuNzFoLTUuOTV6TTggN0g2djRIMnYyaDR2NGgydi00aDR2LTJIOFY3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImV4cG9zdXJlLXplcm8iPjxwYXRoIGQ9Ik0xNi4xNCAxMi41YzAgMS0uMSAxLjg1LS4zIDIuNTUtLjIuNy0uNDggMS4yNy0uODMgMS43LS4zNi40NC0uNzkuNzUtMS4zLjk1LS41MS4yLTEuMDcuMy0xLjcuMy0uNjIgMC0xLjE4LS4xLTEuNjktLjMtLjUxLS4yLS45NS0uNTEtMS4zMS0uOTUtLjM2LS40NC0uNjUtMS4wMS0uODUtMS43LS4yLS43LS4zLTEuNTUtLjMtMi41NXYtMi4wNGMwLTEgLjEtMS44NS4zLTIuNTUuMi0uNy40OC0xLjI2Ljg0LTEuNjkuMzYtLjQzLjgtLjc0IDEuMzEtLjkzQzEwLjgxIDUuMSAxMS4zOCA1IDEyIDVjLjYzIDAgMS4xOS4xIDEuNy4yOS41MS4xOS45NS41IDEuMzEuOTMuMzYuNDMuNjQuOTkuODQgMS42OS4yLjcuMyAxLjU0LjMgMi41NXYyLjA0em0tMi4xMS0yLjM2YzAtLjY0LS4wNS0xLjE4LS4xMy0xLjYyLS4wOS0uNDQtLjIyLS43OS0uNC0xLjA2LS4xNy0uMjctLjM5LS40Ni0uNjQtLjU4LS4yNS0uMTMtLjU0LS4xOS0uODYtLjE5LS4zMiAwLS42MS4wNi0uODYuMThzLS40Ny4zMS0uNjQuNThjLS4xNy4yNy0uMzEuNjItLjQgMS4wNnMtLjEzLjk4LS4xMyAxLjYydjIuNjdjMCAuNjQuMDUgMS4xOC4xNCAxLjYyLjA5LjQ1LjIzLjgxLjQgMS4wOXMuMzkuNDguNjQuNjEuNTQuMTkuODcuMTljLjMzIDAgLjYyLS4wNi44Ny0uMTlzLjQ2LS4zMy42My0uNjFjLjE3LS4yOC4zLS42NC4zOS0xLjA5LjA5LS40NS4xMy0uOTkuMTMtMS42MnYtMi42NnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXIiPjxwYXRoIGQ9Ik0xNS45NiAxMC4yOWwtMi43NSAzLjU0LTEuOTYtMi4zNkw4LjUgMTVoMTFsLTMuNTQtNC43MXpNMyA1SDF2MTZjMCAxLjEuOSAyIDIgMmgxNnYtMkgzVjV6bTE4LTRIN2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlYzYzAtMS4xLS45LTItMi0yem0wIDE2SDdWM2gxNHYxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItMSI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xMSAxMGgyVjVoLTR2Mmgydjh6bTctMTRIN2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlYzYzAtMS4xLS45LTItMi0yem0wIDE2SDdWM2gxNHYxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItMiI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6bS00LTRoLTR2LTJoMmMxLjEgMCAyLS44OSAyLTJWN2MwLTEuMTEtLjktMi0yLTJoLTR2Mmg0djJoLTJjLTEuMSAwLTIgLjg5LTIgMnY0aDZ2LTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLTMiPjxwYXRoIGQ9Ik0yMSAxSDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6TTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xNCA4di0xLjVjMC0uODMtLjY3LTEuNS0xLjUtMS41LjgzIDAgMS41LS42NyAxLjUtMS41VjdjMC0xLjExLS45LTItMi0yaC00djJoNHYyaC0ydjJoMnYyaC00djJoNGMxLjEgMCAyLS44OSAyLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLTQiPjxwYXRoIGQ9Ik0zIDVIMXYxNmMwIDEuMS45IDIgMiAyaDE2di0ySDNWNXptMTIgMTBoMlY1aC0ydjRoLTJWNWgtMnY2aDR2NHptNi0xNEg3Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjNjMC0xLjEtLjktMi0yLTJ6bTAgMTZIN1YzaDE0djE0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZpbHRlci01Ij48cGF0aCBkPSJNMjEgMUg3Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjNjMC0xLjEtLjktMi0yLTJ6bTAgMTZIN1YzaDE0djE0ek0zIDVIMXYxNmMwIDEuMS45IDIgMiAyaDE2di0ySDNWNXptMTQgOHYtMmMwLTEuMTEtLjktMi0yLTJoLTJWN2g0VjVoLTZ2Nmg0djJoLTR2Mmg0YzEuMSAwIDItLjg5IDItMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItNiI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6bS04LTJoMmMxLjEgMCAyLS44OSAyLTJ2LTJjMC0xLjExLS45LTItMi0yaC0yVjdoNFY1aC00Yy0xLjEgMC0yIC44OS0yIDJ2NmMwIDEuMTEuOSAyIDIgMnptMC00aDJ2MmgtMnYtMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItNyI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6bS04LTJsNC04VjVoLTZ2Mmg0bC00IDhoMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItOCI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6bS04LTJoMmMxLjEgMCAyLS44OSAyLTJ2LTEuNWMwLS44My0uNjctMS41LTEuNS0xLjUuODMgMCAxLjUtLjY3IDEuNS0xLjVWN2MwLTEuMTEtLjktMi0yLTJoLTJjLTEuMSAwLTIgLjg5LTIgMnYxLjVjMCAuODMuNjcgMS41IDEuNSAxLjUtLjgzIDAtMS41LjY3LTEuNSAxLjVWMTNjMCAxLjExLjkgMiAyIDJ6bTAtOGgydjJoLTJWN3ptMCA0aDJ2MmgtMnYtMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItOSI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6TTE1IDVoLTJjLTEuMSAwLTIgLjg5LTIgMnYyYzAgMS4xMS45IDIgMiAyaDJ2MmgtNHYyaDRjMS4xIDAgMi0uODkgMi0yVjdjMC0xLjExLS45LTItMi0yem0wIDRoLTJWN2gydjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLTktcGx1cyI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xMSA3VjhjMC0xLjExLS45LTItMi0yaC0xYy0xLjEgMC0yIC44OS0yIDJ2MWMwIDEuMTEuOSAyIDIgMmgxdjFIOXYyaDNjMS4xIDAgMi0uODkgMi0yem0tMy0zVjhoMXYxaC0xem0xMC04SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCA4aC0yVjdoLTJ2MmgtMnYyaDJ2Mmgydi0yaDJ2Nkg3VjNoMTR2NnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItYi1hbmQtdyI+PHBhdGggZD0iTTE5IDNINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2bC03LTh2OEg1bDctOFY1aDd2MTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLWNlbnRlci1mb2N1cyI+PHBhdGggZD0iTTUgMTVIM3Y0YzAgMS4xLjkgMiAyIDJoNHYtMkg1di00ek01IDVoNFYzSDVjLTEuMSAwLTIgLjktMiAydjRoMlY1em0xNC0yaC00djJoNHY0aDJWNWMwLTEuMS0uOS0yLTItMnptMCAxNmgtNHYyaDRjMS4xIDAgMi0uOSAyLTJ2LTRoLTJ2NHpNMTIgOWMtMS42NiAwLTMgMS4zNC0zIDNzMS4zNCAzIDMgMyAzLTEuMzQgMy0zLTEuMzQtMy0zLTN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLWRyYW1hIj48cGF0aCBkPSJNMTkuMzUgMTAuMDRDMTguNjcgNi41OSAxNS42NCA0IDEyIDQgOS4xMSA0IDYuNjEgNS42NCA1LjM2IDguMDQgMi4zNSA4LjM2IDAgMTAuOSAwIDE0YzAgMy4zMSAyLjY5IDYgNiA2aDEzYzIuNzYgMCA1LTIuMjQgNS01IDAtMi42NC0yLjA1LTQuNzgtNC42NS00Ljk2ek0xOSAxOEg2Yy0yLjIxIDAtNC0xLjc5LTQtNHMxLjc5LTQgNC00IDQgMS43OSA0IDRoMmMwLTIuNzYtMS44Ni01LjA4LTQuNC01Ljc4QzguNjEgNi44OCAxMC4yIDYgMTIgNmMzLjAzIDAgNS41IDIuNDcgNS41IDUuNXYuNUgxOWMxLjY1IDAgMyAxLjM1IDMgM3MtMS4zNSAzLTMgM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItZnJhbWVzIj48cGF0aCBkPSJNMjAgNGgtNGwtNC00LTQgNEg0Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjZjMC0xLjEtLjktMi0yLTJ6bTAgMTZINFY2aDQuNTJsMy41Mi0zLjVMMTUuNTIgNkgyMHYxNHpNMTggOEg2djEwaDEyIj48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLWhkciI+PHBhdGggZD0iTTE0IDZsLTMuNzUgNSAyLjg1IDMuOC0xLjYgMS4yQzkuODEgMTMuNzUgNyAxMCA3IDEwbC02IDhoMjJMMTQgNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWx0ZXItbm9uZSI+PHBhdGggZD0iTTMgNUgxdjE2YzAgMS4xLjkgMiAyIDJoMTZ2LTJIM1Y1em0xOC00SDdjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWM2MwLTEuMS0uOS0yLTItMnptMCAxNkg3VjNoMTR2MTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLXRpbHQtc2hpZnQiPjxwYXRoIGQ9Ik0xMSA0LjA3VjIuMDVjLTIuMDEuMi0zLjg0IDEtNS4zMiAyLjIxTDcuMSA1LjY5YzEuMTEtLjg2IDIuNDQtMS40NCAzLjktMS42MnptNy4zMi4xOUMxNi44NCAzLjA1IDE1LjAxIDIuMjUgMTMgMi4wNXYyLjAyYzEuNDYuMTggMi43OS43NiAzLjkgMS42MmwxLjQyLTEuNDN6TTE5LjkzIDExaDIuMDJjLS4yLTIuMDEtMS0zLjg0LTIuMjEtNS4zMkwxOC4zMSA3LjFjLjg2IDEuMTEgMS40NCAyLjQ0IDEuNjIgMy45ek01LjY5IDcuMUw0LjI2IDUuNjhDMy4wNSA3LjE2IDIuMjUgOC45OSAyLjA1IDExaDIuMDJjLjE4LTEuNDYuNzYtMi43OSAxLjYyLTMuOXpNNC4wNyAxM0gyLjA1Yy4yIDIuMDEgMSAzLjg0IDIuMjEgNS4zMmwxLjQzLTEuNDNjLS44Ni0xLjEtMS40NC0yLjQzLTEuNjItMy44OXpNMTUgMTJjMC0xLjY2LTEuMzQtMy0zLTNzLTMgMS4zNC0zIDMgMS4zNCAzIDMgMyAzLTEuMzQgMy0zem0zLjMxIDQuOWwxLjQzIDEuNDNjMS4yMS0xLjQ4IDIuMDEtMy4zMiAyLjIxLTUuMzJoLTIuMDJjLS4xOCAxLjQ1LS43NiAyLjc4LTEuNjIgMy44OXpNMTMgMTkuOTN2Mi4wMmMyLjAxLS4yIDMuODQtMSA1LjMyLTIuMjFsLTEuNDMtMS40M2MtMS4xLjg2LTIuNDMgMS40NC0zLjg5IDEuNjJ6bS03LjMyLS4xOUM3LjE2IDIwLjk1IDkgMjEuNzUgMTEgMjEuOTV2LTIuMDJjLTEuNDYtLjE4LTIuNzktLjc2LTMuOS0xLjYybC0xLjQyIDEuNDN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLXZpbnRhZ2UiPjxwYXRoIGQ9Ik0xOC43IDEyLjRjLS4yOC0uMTYtLjU3LS4yOS0uODYtLjQuMjktLjExLjU4LS4yNC44Ni0uNCAxLjkyLTEuMTEgMi45OS0zLjEyIDMtNS4xOS0xLjc5LTEuMDMtNC4wNy0xLjExLTYgMC0uMjguMTYtLjU0LjM1LS43OC41NC4wNS0uMzEuMDgtLjYzLjA4LS45NSAwLTIuMjItMS4yMS00LjE1LTMtNS4xOUMxMC4yMSAxLjg1IDkgMy43OCA5IDZjMCAuMzIuMDMuNjQuMDguOTUtLjI0LS4yLS41LS4zOS0uNzgtLjU1LTEuOTItMS4xMS00LjItMS4wMy02IDAgMCAyLjA3IDEuMDcgNC4wOCAzIDUuMTkuMjguMTYuNTcuMjkuODYuNC0uMjkuMTEtLjU4LjI0LS44Ni40LTEuOTIgMS4xMS0yLjk5IDMuMTItMyA1LjE5IDEuNzkgMS4wMyA0LjA3IDEuMTEgNiAwIC4yOC0uMTYuNTQtLjM1Ljc4LS41NC0uMDUuMzItLjA4LjY0LS4wOC45NiAwIDIuMjIgMS4yMSA0LjE1IDMgNS4xOSAxLjc5LTEuMDQgMy0yLjk3IDMtNS4xOSAwLS4zMi0uMDMtLjY0LS4wOC0uOTUuMjQuMi41LjM4Ljc4LjU0IDEuOTIgMS4xMSA0LjIgMS4wMyA2IDAtLjAxLTIuMDctMS4wOC00LjA4LTMtNS4xOXpNMTIgMTZjLTIuMjEgMC00LTEuNzktNC00czEuNzktNCA0LTQgNCAxLjc5IDQgNC0xLjc5IDQtNCA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsYXJlIj48cGF0aCBkPSJNNyAxMUgxdjJoNnYtMnptMi4xNy0zLjI0TDcuMDUgNS42NCA1LjY0IDcuMDVsMi4xMiAyLjEyIDEuNDEtMS40MXpNMTMgMWgtMnY2aDJWMXptNS4zNiA2LjA1bC0xLjQxLTEuNDEtMi4xMiAyLjEyIDEuNDEgMS40MSAyLjEyLTIuMTJ6TTE3IDExdjJoNnYtMmgtNnptLTUtMmMtMS42NiAwLTMgMS4zNC0zIDNzMS4zNCAzIDMgMyAzLTEuMzQgMy0zLTEuMzQtMy0zLTN6bTIuODMgNy4yNGwyLjEyIDIuMTIgMS40MS0xLjQxLTIuMTItMi4xMi0xLjQxIDEuNDF6bS05LjE5LjcxbDEuNDEgMS40MSAyLjEyLTIuMTItMS40MS0xLjQxLTIuMTIgMi4xMnpNMTEgMjNoMnYtNmgtMnY2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsYXNoLWF1dG8iPjxwYXRoIGQ9Ik0zIDJ2MTJoM3Y5bDctMTJIOWw0LTlIM3ptMTYgMGgtMmwtMy4yIDloMS45bC43LTJoMy4ybC43IDJoMS45TDE5IDJ6bS0yLjE1IDUuNjVMMTggNGwxLjE1IDMuNjVoLTIuM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJmbGFzaC1vZmYiPjxwYXRoIGQ9Ik0zLjI3IDNMMiA0LjI3bDUgNVYxM2gzdjlsMy41OC02LjE0TDE3LjczIDIwIDE5IDE4LjczIDMuMjcgM3pNMTcgMTBoLTRsNC04SDd2Mi4xOGw4LjQ2IDguNDZMMTcgMTB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmxhc2gtb24iPjxwYXRoIGQ9Ik03IDJ2MTFoM3Y5bDctMTJoLTRsNC04eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsaXAiPjxwYXRoIGQ9Ik0xNSAyMWgydi0yaC0ydjJ6bTQtMTJoMlY3aC0ydjJ6TTMgNXYxNGMwIDEuMS45IDIgMiAyaDR2LTJINVY1aDRWM0g1Yy0xLjEgMC0yIC45LTIgMnptMTYtMnYyaDJjMC0xLjEtLjktMi0yLTJ6bS04IDIwaDJWMWgtMnYyMnptOC02aDJ2LTJoLTJ2MnpNMTUgNWgyVjNoLTJ2MnptNCA4aDJ2LTJoLTJ2MnptMCA4YzEuMSAwIDItLjkgMi0yaC0ydjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZ3JhZGllbnQiPjxwYXRoIGQ9Ik0xMSA5aDJ2MmgtMnptLTIgMmgydjJIOXptNCAwaDJ2MmgtMnptMi0yaDJ2MmgtMnpNNyA5aDJ2Mkg3em0xMi02SDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnpNOSAxOEg3di0yaDJ2MnptNCAwaC0ydi0yaDJ2MnptNCAwaC0ydi0yaDJ2MnptMi03aC0ydjJoMnYyaC0ydi0yaC0ydjJoLTJ2LTJoLTJ2Mkg5di0ySDd2Mkg1di0yaDJ2LTJINVY1aDE0djZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZ3JhaW4iPjxwYXRoIGQ9Ik0xMCAxMmMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6TTYgOGMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6bTAgOGMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6bTEyLThjMS4xIDAgMi0uOSAyLTJzLS45LTItMi0yLTIgLjktMiAyIC45IDIgMiAyem0tNCA4Yy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnptNC00Yy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnptLTQtNGMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6bS00LTRjLTEuMSAwLTIgLjktMiAycy45IDIgMiAyIDItLjkgMi0yLS45LTItMi0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImdyaWQtb2ZmIj48cGF0aCBkPSJNOCA0djEuNDVsMiAyVjRoNHY0aC0zLjQ1bDIgMkgxNHYxLjQ1bDIgMlYxMGg0djRoLTMuNDVsMiAySDIwdjEuNDVsMiAyVjRjMC0xLjEtLjktMi0yLTJINC41NWwyIDJIOHptOCAwaDR2NGgtNFY0ek0xLjI3IDEuMjdMMCAyLjU1bDIgMlYyMGMwIDEuMS45IDIgMiAyaDE1LjQ2bDIgMiAxLjI3LTEuMjdMMS4yNyAxLjI3ek0xMCAxMi41NUwxMS40NSAxNEgxMHYtMS40NXptLTYtNkw1LjQ1IDhINFY2LjU1ek04IDIwSDR2LTRoNHY0em0wLTZINHYtNGgzLjQ1bC41NS41NVYxNHptNiA2aC00di00aDMuNDVsLjU1LjU0VjIwem0yIDB2LTEuNDZMMTcuNDYgMjBIMTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZ3JpZC1vbiI+PHBhdGggZD0iTTIwIDJINGMtMS4xIDAtMiAuOS0yIDJ2MTZjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yek04IDIwSDR2LTRoNHY0em0wLTZINHYtNGg0djR6bTAtNkg0VjRoNHY0em02IDEyaC00di00aDR2NHptMC02aC00di00aDR2NHptMC02aC00VjRoNHY0em02IDEyaC00di00aDR2NHptMC02aC00di00aDR2NHptMC02aC00VjRoNHY0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imhkci1vZmYiPjxwYXRoIGQ9Ik0xNy41IDE1di0yaDEuMWwuOSAySDIxbC0uOS0yLjFjLjUtLjIuOS0uOC45LTEuNHYtMWMwLS44LS43LTEuNS0xLjUtMS41SDE2djQuOWwxLjEgMS4xaC40em0wLTQuNWgydjFoLTJ2LTF6bS00LjUgMHYuNGwxLjUgMS41di0xLjljMC0uOC0uNy0xLjUtMS41LTEuNWgtMS45bDEuNSAxLjVoLjR6bS0zLjUtMWwtNy03LTEuMSAxTDYuOSA5aC0uNHYyaC0yVjlIM3Y2aDEuNXYtMi41aDJWMTVIOHYtNC45bDEuNSAxLjVWMTVoMy40bDcuNiA3LjYgMS4xLTEuMS0xMi4xLTEyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imhkci1vbiI+PHBhdGggZD0iTTIxIDExLjV2LTFjMC0uOC0uNy0xLjUtMS41LTEuNUgxNnY2aDEuNXYtMmgxLjFsLjkgMkgyMWwtLjktMi4xYy41LS4zLjktLjguOS0xLjR6bS0xLjUgMGgtMnYtMWgydjF6bS0xMy0uNWgtMlY5SDN2NmgxLjV2LTIuNWgyVjE1SDhWOUg2LjV2MnpNMTMgOUg5LjV2NkgxM2MuOCAwIDEuNS0uNyAxLjUtMS41di0zYzAtLjgtLjctMS41LTEuNS0xLjV6bTAgNC41aC0ydi0zaDJ2M3oiPjwvcGF0aD48L2c+CjxnIGlkPSJoZHItc3Ryb25nIj48cGF0aCBkPSJNMTcgNmMtMy4zMSAwLTYgMi42OS02IDZzMi42OSA2IDYgNiA2LTIuNjkgNi02LTIuNjktNi02LTZ6TTUgOGMtMi4yMSAwLTQgMS43OS00IDRzMS43OSA0IDQgNCA0LTEuNzkgNC00LTEuNzktNC00LTR6bTAgNmMtMS4xIDAtMi0uOS0yLTJzLjktMiAyLTIgMiAuOSAyIDItLjkgMi0yIDJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iaGRyLXdlYWsiPjxwYXRoIGQ9Ik01IDhjLTIuMjEgMC00IDEuNzktNCA0czEuNzkgNCA0IDQgNC0xLjc5IDQtNC0xLjc5LTQtNC00em0xMi0yYy0zLjMxIDAtNiAyLjY5LTYgNnMyLjY5IDYgNiA2IDYtMi42OSA2LTYtMi42OS02LTYtNnptMCAxMGMtMi4yMSAwLTQtMS43OS00LTRzMS43OS00IDQtNCA0IDEuNzkgNCA0LTEuNzkgNC00IDR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iaGVhbGluZyI+PHBhdGggZD0iTTE3LjczIDEyLjAybDMuOTgtMy45OGMuMzktLjM5LjM5LTEuMDIgMC0xLjQxbC00LjM0LTQuMzRjLS4zOS0uMzktMS4wMi0uMzktMS40MSAwbC0zLjk4IDMuOThMOCAyLjI5QzcuOCAyLjEgNy41NSAyIDcuMjkgMmMtLjI1IDAtLjUxLjEtLjcuMjlMMi4yNSA2LjYzYy0uMzkuMzktLjM5IDEuMDIgMCAxLjQxbDMuOTggMy45OEwyLjI1IDE2Yy0uMzkuMzktLjM5IDEuMDIgMCAxLjQxbDQuMzQgNC4zNGMuMzkuMzkgMS4wMi4zOSAxLjQxIDBsMy45OC0zLjk4IDMuOTggMy45OGMuMi4yLjQ1LjI5LjcxLjI5LjI2IDAgLjUxLS4xLjcxLS4yOWw0LjM0LTQuMzRjLjM5LS4zOS4zOS0xLjAyIDAtMS40MWwtMy45OS0zLjk4ek0xMiA5Yy41NSAwIDEgLjQ1IDEgMXMtLjQ1IDEtMSAxLTEtLjQ1LTEtMSAuNDUtMSAxLTF6bS00LjcxIDEuOTZMMy42NiA3LjM0bDMuNjMtMy42MyAzLjYyIDMuNjItMy42MiAzLjYzek0xMCAxM2MtLjU1IDAtMS0uNDUtMS0xcy40NS0xIDEtMSAxIC40NSAxIDEtLjQ1IDEtMSAxem0yIDJjLS41NSAwLTEtLjQ1LTEtMXMuNDUtMSAxLTEgMSAuNDUgMSAxLS40NSAxLTEgMXptMi00Yy41NSAwIDEgLjQ1IDEgMXMtLjQ1IDEtMSAxLTEtLjQ1LTEtMSAuNDUtMSAxLTF6bTIuNjYgOS4zNGwtMy42My0zLjYyIDMuNjMtMy42MyAzLjYyIDMuNjItMy42MiAzLjYzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImltYWdlIj48cGF0aCBkPSJNMjEgMTlWNWMwLTEuMS0uOS0yLTItMkg1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yek04LjUgMTMuNWwyLjUgMy4wMUwxNC41IDEybDQuNSA2SDVsMy41LTQuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJpbWFnZS1hc3BlY3QtcmF0aW8iPjxwYXRoIGQ9Ik0xNiAxMGgtMnYyaDJ2LTJ6bTAgNGgtMnYyaDJ2LTJ6bS04LTRINnYyaDJ2LTJ6bTQgMGgtMnYyaDJ2LTJ6bTgtNkg0Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjZjMC0xLjEtLjktMi0yLTJ6bTAgMTRINFY2aDE2djEyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImlzbyI+PHBhdGggZD0iTTE5IDNINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yek01LjUgNy41aDJ2LTJIOXYyaDJWOUg5djJINy41VjloLTJWNy41ek0xOSAxOUg1TDE5IDV2MTR6bS0yLTJ2LTEuNWgtNVYxN2g1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImxhbmRzY2FwZSI+PHBhdGggZD0iTTE0IDZsLTMuNzUgNSAyLjg1IDMuOC0xLjYgMS4yQzkuODEgMTMuNzUgNyAxMCA3IDEwbC02IDhoMjJMMTQgNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJsZWFrLWFkZCI+PHBhdGggZD0iTTYgM0gzdjNjMS42NiAwIDMtMS4zNCAzLTN6bTggMGgtMmMwIDQuOTctNC4wMyA5LTkgOXYyYzYuMDggMCAxMS00LjkzIDExLTExem0tNCAwSDhjMCAyLjc2LTIuMjQgNS01IDV2MmMzLjg3IDAgNy0zLjEzIDctN3ptMCAxOGgyYzAtNC45NyA0LjAzLTkgOS05di0yYy02LjA3IDAtMTEgNC45My0xMSAxMXptOCAwaDN2LTNjLTEuNjYgMC0zIDEuMzQtMyAzem0tNCAwaDJjMC0yLjc2IDIuMjQtNSA1LTV2LTJjLTMuODcgMC03IDMuMTMtNyA3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImxlYWstcmVtb3ZlIj48cGF0aCBkPSJNMTAgM0g4YzAgLjM3LS4wNC43Mi0uMTIgMS4wNmwxLjU5IDEuNTlDOS44MSA0Ljg0IDEwIDMuOTQgMTAgM3pNMyA0LjI3bDIuODQgMi44NEM1LjAzIDcuNjcgNC4wNiA4IDMgOHYyYzEuNjEgMCAzLjA5LS41NSA0LjI3LTEuNDZMOC43IDkuOTdDNy4xNCAxMS4yNCA1LjE2IDEyIDMgMTJ2MmMyLjcxIDAgNS4xOS0uOTkgNy4xMS0yLjYybDIuNSAyLjVDMTAuOTkgMTUuODEgMTAgMTguMjkgMTAgMjFoMmMwLTIuMTYuNzYtNC4xNCAyLjAzLTUuNjlsMS40MyAxLjQzQzE0LjU1IDE3LjkxIDE0IDE5LjM5IDE0IDIxaDJjMC0xLjA2LjMzLTIuMDMuODktMi44NEwxOS43MyAyMSAyMSAxOS43MyA0LjI3IDMgMyA0LjI3ek0xNCAzaC0yYzAgMS41LS4zNyAyLjkxLTEuMDIgNC4xNmwxLjQ2IDEuNDZDMTMuNDIgNi45OCAxNCA1LjA2IDE0IDN6bTUuOTQgMTMuMTJjLjM0LS4wOC42OS0uMTIgMS4wNi0uMTJ2LTJjLS45NCAwLTEuODQuMTktMi42Ni41MmwxLjYgMS42em0tNC41Ni00LjU2bDEuNDYgMS40NkMxOC4wOSAxMi4zNyAxOS41IDEyIDIxIDEydi0yYy0yLjA2IDAtMy45OC41OC01LjYyIDEuNTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGVucyI+PHBhdGggZD0iTTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGlua2VkLWNhbWVyYSI+PGNpcmNsZSBjeD0iMTIiIGN5PSIxNCIgcj0iMy4yIj48L2NpcmNsZT48cGF0aCBkPSJNMTYgMy4zM2MyLjU4IDAgNC42NyAyLjA5IDQuNjcgNC42N0gyMmMwLTMuMzEtMi42OS02LTYtNnYxLjMzTTE2IDZjMS4xMSAwIDIgLjg5IDIgMmgxLjMzYzAtMS44NC0xLjQ5LTMuMzMtMy4zMy0zLjMzVjYiPjwvcGF0aD48cGF0aCBkPSJNMTcgOWMwLTEuMTEtLjg5LTItMi0yVjRIOUw3LjE3IDZINGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY5aC01em0tNSAxMGMtMi43NiAwLTUtMi4yNC01LTVzMi4yNC01IDUtNSA1IDIuMjQgNSA1LTIuMjQgNS01IDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibG9va3MiPjxwYXRoIGQ9Ik0xMiAxMGMtMy44NiAwLTcgMy4xNC03IDdoMmMwLTIuNzYgMi4yNC01IDUtNXM1IDIuMjQgNSA1aDJjMC0zLjg2LTMuMTQtNy03LTd6bTAtNEM1LjkzIDYgMSAxMC45MyAxIDE3aDJjMC00Ljk2IDQuMDQtOSA5LTlzOSA0LjA0IDkgOWgyYzAtNi4wNy00LjkzLTExLTExLTExeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imxvb2tzLTMiPjxwYXRoIGQ9Ik0xOS4wMSAzaC0xNGMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0tNCA3LjVjMCAuODMtLjY3IDEuNS0xLjUgMS41LjgzIDAgMS41LjY3IDEuNSAxLjVWMTVjMCAxLjExLS45IDItMiAyaC00di0yaDR2LTJoLTJ2LTJoMlY5aC00VjdoNGMxLjEgMCAyIC44OSAyIDJ2MS41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imxvb2tzLTQiPjxwYXRoIGQ9Ik0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTQgMTRoLTJ2LTRIOVY3aDJ2NGgyVjdoMnYxMHoiPjwvcGF0aD48L2c+CjxnIGlkPSJsb29rcy01Ij48cGF0aCBkPSJNMTkgM0g1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS00IDZoLTR2MmgyYzEuMSAwIDIgLjg5IDIgMnYyYzAgMS4xMS0uOSAyLTIgMkg5di0yaDR2LTJIOVY3aDZ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJsb29rcy02Ij48cGF0aCBkPSJNMTEgMTVoMnYtMmgtMnYyem04LTEySDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTQgNmgtNHYyaDJjMS4xIDAgMiAuODkgMiAydjJjMCAxLjExLS45IDItMiAyaC0yYy0xLjEgMC0yLS44OS0yLTJWOWMwLTEuMTEuOS0yIDItMmg0djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibG9va3Mtb25lIj48cGF0aCBkPSJNMTkgM0g1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS01IDE0aC0yVjloLTJWN2g0djEweiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imxvb2tzLXR3byI+PHBhdGggZD0iTTE5IDNINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0tNCA4YzAgMS4xMS0uOSAyLTIgMmgtMnYyaDR2Mkg5di00YzAtMS4xMS45LTIgMi0yaDJWOUg5VjdoNGMxLjEgMCAyIC44OSAyIDJ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJsb3VwZSI+PHBhdGggZD0iTTEzIDdoLTJ2NEg3djJoNHY0aDJ2LTRoNHYtMmgtNFY3em0tMS01QzYuNDkgMiAyIDYuNDkgMiAxMnM0LjQ5IDEwIDEwIDEwaDhjMS4xIDAgMi0uOSAyLTJ2LThjMC01LjUxLTQuNDktMTAtMTAtMTB6bTAgMThjLTQuNDEgMC04LTMuNTktOC04czMuNTktOCA4LTggOCAzLjU5IDggOC0zLjU5IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im1vbm9jaHJvbWUtcGhvdG9zIj48cGF0aCBkPSJNMjAgNWgtMy4yTDE1IDNIOUw3LjIgNUg0Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjdjMC0xLjEtLjktMi0yLTJ6bTAgMTRoLTh2LTFjLTIuOCAwLTUtMi4yLTUtNXMyLjItNSA1LTVWN2g4djEyem0tMy02YzAtMi44LTIuMi01LTUtNXYxLjhjMS44IDAgMy4yIDEuNCAzLjIgMy4ycy0xLjQgMy4yLTMuMiAzLjJWMThjMi44IDAgNS0yLjIgNS01em0tOC4yIDBjMCAxLjggMS40IDMuMiAzLjIgMy4yVjkuOGMtMS44IDAtMy4yIDEuNC0zLjIgMy4yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im1vdmllLWNyZWF0aW9uIj48cGF0aCBkPSJNMTggNGwyIDRoLTNsLTItNGgtMmwyIDRoLTNsLTItNEg4bDIgNEg3TDUgNEg0Yy0xLjEgMC0xLjk5LjktMS45OSAyTDIgMThjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY0aC00eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im1vdmllLWZpbHRlciI+PHBhdGggZD0iTTE4IDRsMiAzaC0zbC0yLTNoLTJsMiAzaC0zbC0yLTNIOGwyIDNIN0w1IDRINGMtMS4xIDAtMS45OS45LTEuOTkgMkwyIDE4YzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJWNGgtNHptLTYuNzUgMTEuMjVMMTAgMThsLTEuMjUtMi43NUw2IDE0bDIuNzUtMS4yNUwxMCAxMGwxLjI1IDIuNzVMMTQgMTRsLTIuNzUgMS4yNXptNS42OS0zLjMxTDE2IDE0bC0uOTQtMi4wNkwxMyAxMWwyLjA2LS45NEwxNiA4bC45NCAyLjA2TDE5IDExbC0yLjA2Ljk0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im11c2ljLW5vdGUiPjxwYXRoIGQ9Ik0xMiAzdjEwLjU1Yy0uNTktLjM0LTEuMjctLjU1LTItLjU1LTIuMjEgMC00IDEuNzktNCA0czEuNzkgNCA0IDQgNC0xLjc5IDQtNFY3aDRWM2gtNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJuYXR1cmUiPjxwYXRoIGQ9Ik0xMyAxNi4xMmMzLjQ3LS40MSA2LjE3LTMuMzYgNi4xNy02Ljk1IDAtMy44Ny0zLjEzLTctNy03cy03IDMuMTMtNyA3YzAgMy40NyAyLjUyIDYuMzQgNS44MyA2Ljg5VjIwSDV2MmgxNHYtMmgtNnYtMy44OHoiPjwvcGF0aD48L2c+CjxnIGlkPSJuYXR1cmUtcGVvcGxlIj48cGF0aCBkPSJNMjIuMTcgOS4xN2MwLTMuODctMy4xMy03LTctN3MtNyAzLjEzLTcgN2MwIDMuNDcgMi41MiA2LjM0IDUuODMgNi44OVYyMEg2di0zaDF2LTRjMC0uNTUtLjQ1LTEtMS0xSDNjLS41NSAwLTEgLjQ1LTEgMXY0aDF2NWgxNnYtMmgtM3YtMy44OGMzLjQ3LS40MSA2LjE3LTMuMzYgNi4xNy02Ljk1ek00LjUgMTFjLjgzIDAgMS41LS42NyAxLjUtMS41UzUuMzMgOCA0LjUgOCAzIDguNjcgMyA5LjUgMy42NyAxMSA0LjUgMTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibmF2aWdhdGUtYmVmb3JlIj48cGF0aCBkPSJNMTUuNDEgNy40MUwxNCA2bC02IDYgNiA2IDEuNDEtMS40MUwxMC44MyAxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJuYXZpZ2F0ZS1uZXh0Ij48cGF0aCBkPSJNMTAgNkw4LjU5IDcuNDEgMTMuMTcgMTJsLTQuNTggNC41OUwxMCAxOGw2LTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGFsZXR0ZSI+PHBhdGggZD0iTTEyIDNjLTQuOTcgMC05IDQuMDMtOSA5czQuMDMgOSA5IDljLjgzIDAgMS41LS42NyAxLjUtMS41IDAtLjM5LS4xNS0uNzQtLjM5LTEuMDEtLjIzLS4yNi0uMzgtLjYxLS4zOC0uOTkgMC0uODMuNjctMS41IDEuNS0xLjVIMTZjMi43NiAwIDUtMi4yNCA1LTUgMC00LjQyLTQuMDMtOC05LTh6bS01LjUgOWMtLjgzIDAtMS41LS42Ny0xLjUtMS41UzUuNjcgOSA2LjUgOSA4IDkuNjcgOCAxMC41IDcuMzMgMTIgNi41IDEyem0zLTRDOC42NyA4IDggNy4zMyA4IDYuNVM4LjY3IDUgOS41IDVzMS41LjY3IDEuNSAxLjVTMTAuMzMgOCA5LjUgOHptNSAwYy0uODMgMC0xLjUtLjY3LTEuNS0xLjVTMTMuNjcgNSAxNC41IDVzMS41LjY3IDEuNSAxLjVTMTUuMzMgOCAxNC41IDh6bTMgNGMtLjgzIDAtMS41LS42Ny0xLjUtMS41UzE2LjY3IDkgMTcuNSA5czEuNS42NyAxLjUgMS41LS42NyAxLjUtMS41IDEuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJwYW5vcmFtYSI+PHBhdGggZD0iTTIzIDE4VjZjMC0xLjEtLjktMi0yLTJIM2MtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxOGMxLjEgMCAyLS45IDItMnpNOC41IDEyLjVsMi41IDMuMDFMMTQuNSAxMWw0LjUgNkg1bDMuNS00LjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGFub3JhbWEtZmlzaC1leWUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDcgMiAyIDYuNDcgMiAxMnM0LjQ3IDEwIDEwIDEwIDEwLTQuNDcgMTAtMTBTMTcuNTMgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOHMzLjU5LTggOC04IDggMy41OSA4IDgtMy41OSA4LTggOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJwYW5vcmFtYS1ob3Jpem9udGFsIj48cGF0aCBkPSJNMjAgNi41NHYxMC45MWMtMi42LS43Ny01LjI4LTEuMTYtOC0xLjE2LTIuNzIgMC01LjQuMzktOCAxLjE2VjYuNTRjMi42Ljc3IDUuMjggMS4xNiA4IDEuMTYgMi43Mi4wMSA1LjQtLjM4IDgtMS4xNk0yMS40MyA0Yy0uMSAwLS4yLjAyLS4zMS4wNkMxOC4xOCA1LjE2IDE1LjA5IDUuNyAxMiA1LjdjLTMuMDkgMC02LjE4LS41NS05LjEyLTEuNjQtLjExLS4wNC0uMjItLjA2LS4zMS0uMDYtLjM0IDAtLjU3LjIzLS41Ny42M3YxNC43NWMwIC4zOS4yMy42Mi41Ny42Mi4xIDAgLjItLjAyLjMxLS4wNiAyLjk0LTEuMSA2LjAzLTEuNjQgOS4xMi0xLjY0IDMuMDkgMCA2LjE4LjU1IDkuMTIgMS42NC4xMS4wNC4yMS4wNi4zMS4wNi4zMyAwIC41Ny0uMjMuNTctLjYzVjQuNjNjMC0uNC0uMjQtLjYzLS41Ny0uNjN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGFub3JhbWEtdmVydGljYWwiPjxwYXRoIGQ9Ik0xOS45NCAyMS4xMmMtMS4xLTIuOTQtMS42NC02LjAzLTEuNjQtOS4xMiAwLTMuMDkuNTUtNi4xOCAxLjY0LTkuMTIuMDQtLjExLjA2LS4yMi4wNi0uMzEgMC0uMzQtLjIzLS41Ny0uNjMtLjU3SDQuNjNjLS40IDAtLjYzLjIzLS42My41NyAwIC4xLjAyLjIuMDYuMzFDNS4xNiA1LjgyIDUuNzEgOC45MSA1LjcxIDEyYzAgMy4wOS0uNTUgNi4xOC0xLjY0IDkuMTItLjA1LjExLS4wNy4yMi0uMDcuMzEgMCAuMzMuMjMuNTcuNjMuNTdoMTQuNzVjLjM5IDAgLjYzLS4yNC42My0uNTctLjAxLS4xLS4wMy0uMi0uMDctLjMxek02LjU0IDIwYy43Ny0yLjYgMS4xNi01LjI4IDEuMTYtOCAwLTIuNzItLjM5LTUuNC0xLjE2LThoMTAuOTFjLS43NyAyLjYtMS4xNiA1LjI4LTEuMTYgOCAwIDIuNzIuMzkgNS40IDEuMTYgOEg2LjU0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBhbm9yYW1hLXdpZGUtYW5nbGUiPjxwYXRoIGQ9Ik0xMiA2YzIuNDUgMCA0LjcxLjIgNy4yOS42NC40NyAxLjc4LjcxIDMuNTguNzEgNS4zNiAwIDEuNzgtLjI0IDMuNTgtLjcxIDUuMzYtMi41OC40NC00Ljg0LjY0LTcuMjkuNjRzLTQuNzEtLjItNy4yOS0uNjRDNC4yNCAxNS41OCA0IDEzLjc4IDQgMTJjMC0xLjc4LjI0LTMuNTguNzEtNS4zNkM3LjI5IDYuMiA5LjU1IDYgMTIgNm0wLTJjLTIuNzMgMC01LjIyLjI0LTcuOTUuNzJsLS45My4xNi0uMjUuOUMyLjI5IDcuODUgMiA5LjkzIDIgMTJzLjI5IDQuMTUuODcgNi4yMmwuMjUuODkuOTMuMTZjMi43My40OSA1LjIyLjczIDcuOTUuNzNzNS4yMi0uMjQgNy45NS0uNzJsLjkzLS4xNi4yNS0uODljLjU4LTIuMDguODctNC4xNi44Ny02LjIzcy0uMjktNC4xNS0uODctNi4yMmwtLjI1LS44OS0uOTMtLjE2QzE3LjIyIDQuMjQgMTQuNzMgNCAxMiA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBob3RvIj48cGF0aCBkPSJNMjEgMTlWNWMwLTEuMS0uOS0yLTItMkg1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yek04LjUgMTMuNWwyLjUgMy4wMUwxNC41IDEybDQuNSA2SDVsMy41LTQuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJwaG90by1hbGJ1bSI+PHBhdGggZD0iTTE4IDJINmMtMS4xIDAtMiAuOS0yIDJ2MTZjMCAxLjEuOSAyIDIgMmgxMmMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yek02IDRoNXY4bC0yLjUtMS41TDYgMTJWNHptMCAxNWwzLTMuODYgMi4xNCAyLjU4IDMtMy44NkwxOCAxOUg2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBob3RvLWNhbWVyYSI+PGNpcmNsZSBjeD0iMTIiIGN5PSIxMiIgcj0iMy4yIj48L2NpcmNsZT48cGF0aCBkPSJNOSAyTDcuMTcgNEg0Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjZjMC0xLjEtLjktMi0yLTJoLTMuMTdMMTUgMkg5em0zIDE1Yy0yLjc2IDAtNS0yLjI0LTUtNXMyLjI0LTUgNS01IDUgMi4yNCA1IDUtMi4yNCA1LTUgNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJwaG90by1maWx0ZXIiPjxwYXRoIGQ9Ik0xOS4wMiAxMHY5SDVWNWg5VjNINS4wMmMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMnYtOWgtMnpNMTcgMTBsLjk0LTIuMDZMMjAgN2wtMi4wNi0uOTRMMTcgNGwtLjk0IDIuMDZMMTQgN2wyLjA2Ljk0em0tMy43NS43NUwxMiA4bC0xLjI1IDIuNzVMOCAxMmwyLjc1IDEuMjVMMTIgMTZsMS4yNS0yLjc1TDE2IDEyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBob3RvLWxpYnJhcnkiPjxwYXRoIGQ9Ik0yMiAxNlY0YzAtMS4xLS45LTItMi0ySDhjLTEuMSAwLTIgLjktMiAydjEyYzAgMS4xLjkgMiAyIDJoMTJjMS4xIDAgMi0uOSAyLTJ6bS0xMS00bDIuMDMgMi43MUwxNiAxMWw0IDVIOGwzLTR6TTIgNnYxNGMwIDEuMS45IDIgMiAyaDE0di0ySDRWNkgyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBob3RvLXNpemUtc2VsZWN0LWFjdHVhbCI+PHBhdGggZD0iTTIxIDNIM0MyIDMgMSA0IDEgNXYxNGMwIDEuMS45IDIgMiAyaDE4YzEgMCAyLTEgMi0yVjVjMC0xLTEtMi0yLTJ6TTUgMTdsMy41LTQuNSAyLjUgMy4wMUwxNC41IDExbDQuNSA2SDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGhvdG8tc2l6ZS1zZWxlY3QtbGFyZ2UiPjxwYXRoIGQ9Ik0yMSAxNWgydjJoLTJ2LTJ6bTAtNGgydjJoLTJ2LTJ6bTIgOGgtMnYyYzEgMCAyLTEgMi0yek0xMyAzaDJ2MmgtMlYzem04IDRoMnYyaC0yVjd6bTAtNHYyaDJjMC0xLTEtMi0yLTJ6TTEgN2gydjJIMVY3em0xNi00aDJ2MmgtMlYzem0wIDE2aDJ2MmgtMnYtMnpNMyAzQzIgMyAxIDQgMSA1aDJWM3ptNiAwaDJ2Mkg5VjN6TTUgM2gydjJINVYzem0tNCA4djhjMCAxLjEuOSAyIDIgMmgxMlYxMUgxem0yIDhsMi41LTMuMjEgMS43OSAyLjE1IDIuNS0zLjIyTDEzIDE5SDN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGhvdG8tc2l6ZS1zZWxlY3Qtc21hbGwiPjxwYXRoIGQ9Ik0yMyAxNWgtMnYyaDJ2LTJ6bTAtNGgtMnYyaDJ2LTJ6bTAgOGgtMnYyYzEgMCAyLTEgMi0yek0xNSAzaC0ydjJoMlYzem04IDRoLTJ2MmgyVjd6bS0yLTR2MmgyYzAtMS0xLTItMi0yek0zIDIxaDh2LTZIMXY0YzAgMS4xLjkgMiAyIDJ6TTMgN0gxdjJoMlY3em0xMiAxMmgtMnYyaDJ2LTJ6bTQtMTZoLTJ2MmgyVjN6bTAgMTZoLTJ2Mmgydi0yek0zIDNDMiAzIDEgNCAxIDVoMlYzem0wIDhIMXYyaDJ2LTJ6bTgtOEg5djJoMlYzek03IDNINXYyaDJWM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJwaWN0dXJlLWFzLXBkZiI+PHBhdGggZD0iTTIwIDJIOGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxMmMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tOC41IDcuNWMwIC44My0uNjcgMS41LTEuNSAxLjVIOXYySDcuNVY3SDEwYy44MyAwIDEuNS42NyAxLjUgMS41djF6bTUgMmMwIC44My0uNjcgMS41LTEuNSAxLjVoLTIuNVY3SDE1Yy44MyAwIDEuNS42NyAxLjUgMS41djN6bTQtM0gxOXYxaDEuNVYxMUgxOXYyaC0xLjVWN2gzdjEuNXpNOSA5LjVoMXYtMUg5djF6TTQgNkgydjE0YzAgMS4xLjkgMiAyIDJoMTR2LTJINFY2em0xMCA1LjVoMXYtM2gtMXYzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBvcnRyYWl0Ij48cGF0aCBkPSJNMTIgMTIuMjVjMS4yNCAwIDIuMjUtMS4wMSAyLjI1LTIuMjVTMTMuMjQgNy43NSAxMiA3Ljc1IDkuNzUgOC43NiA5Ljc1IDEwczEuMDEgMi4yNSAyLjI1IDIuMjV6bTQuNSA0YzAtMS41LTMtMi4yNS00LjUtMi4yNXMtNC41Ljc1LTQuNSAyLjI1VjE3aDl2LS43NXpNMTkgM0g1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bTAgMTZINVY1aDE0djE0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJlbW92ZS1yZWQtZXllIj48cGF0aCBkPSJNMTIgNC41QzcgNC41IDIuNzMgNy42MSAxIDEyYzEuNzMgNC4zOSA2IDcuNSAxMSA3LjVzOS4yNy0zLjExIDExLTcuNWMtMS43My00LjM5LTYtNy41LTExLTcuNXpNMTIgMTdjLTIuNzYgMC01LTIuMjQtNS01czIuMjQtNSA1LTUgNSAyLjI0IDUgNS0yLjI0IDUtNSA1em0wLThjLTEuNjYgMC0zIDEuMzQtMyAzczEuMzQgMyAzIDMgMy0xLjM0IDMtMy0xLjM0LTMtMy0zeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJvdGF0ZS05MC1kZWdyZWVzLWNjdyI+PHBhdGggZD0iTTcuMzQgNi40MUwuODYgMTIuOWw2LjQ5IDYuNDggNi40OS02LjQ4LTYuNS02LjQ5ek0zLjY5IDEyLjlsMy42Ni0zLjY2TDExIDEyLjlsLTMuNjYgMy42Ni0zLjY1LTMuNjZ6bTE1LjY3LTYuMjZDMTcuNjEgNC44OCAxNS4zIDQgMTMgNFYuNzZMOC43NiA1IDEzIDkuMjRWNmMxLjc5IDAgMy41OC42OCA0Ljk1IDIuMDUgMi43MyAyLjczIDIuNzMgNy4xNyAwIDkuOUMxNi41OCAxOS4zMiAxNC43OSAyMCAxMyAyMGMtLjk3IDAtMS45NC0uMjEtMi44NC0uNjFsLTEuNDkgMS40OUMxMC4wMiAyMS42MiAxMS41MSAyMiAxMyAyMmMyLjMgMCA0LjYxLS44OCA2LjM2LTIuNjQgMy41Mi0zLjUxIDMuNTItOS4yMSAwLTEyLjcyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJvdGF0ZS1sZWZ0Ij48cGF0aCBkPSJNNy4xMSA4LjUzTDUuNyA3LjExQzQuOCA4LjI3IDQuMjQgOS42MSA0LjA3IDExaDIuMDJjLjE0LS44Ny40OS0xLjcyIDEuMDItMi40N3pNNi4wOSAxM0g0LjA3Yy4xNyAxLjM5LjcyIDIuNzMgMS42MiAzLjg5bDEuNDEtMS40MmMtLjUyLS43NS0uODctMS41OS0xLjAxLTIuNDd6bTEuMDEgNS4zMmMxLjE2LjkgMi41MSAxLjQ0IDMuOSAxLjYxVjE3LjljLS44Ny0uMTUtMS43MS0uNDktMi40Ni0xLjAzTDcuMSAxOC4zMnpNMTMgNC4wN1YxTDguNDUgNS41NSAxMyAxMFY2LjA5YzIuODQuNDggNSAyLjk0IDUgNS45MXMtMi4xNiA1LjQzLTUgNS45MXYyLjAyYzMuOTUtLjQ5IDctMy44NSA3LTcuOTNzLTMuMDUtNy40NC03LTcuOTN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icm90YXRlLXJpZ2h0Ij48cGF0aCBkPSJNMTUuNTUgNS41NUwxMSAxdjMuMDdDNy4wNiA0LjU2IDQgNy45MiA0IDEyczMuMDUgNy40NCA3IDcuOTN2LTIuMDJjLTIuODQtLjQ4LTUtMi45NC01LTUuOTFzMi4xNi01LjQzIDUtNS45MVYxMGw0LjU1LTQuNDV6TTE5LjkzIDExYy0uMTctMS4zOS0uNzItMi43My0xLjYyLTMuODlsLTEuNDIgMS40MmMuNTQuNzUuODggMS42IDEuMDIgMi40N2gyLjAyek0xMyAxNy45djIuMDJjMS4zOS0uMTcgMi43NC0uNzEgMy45LTEuNjFsLTEuNDQtMS40NGMtLjc1LjU0LTEuNTkuODktMi40NiAxLjAzem0zLjg5LTIuNDJsMS40MiAxLjQxYy45LTEuMTYgMS40NS0yLjUgMS42Mi0zLjg5aC0yLjAyYy0uMTQuODctLjQ4IDEuNzItMS4wMiAyLjQ4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNsaWRlc2hvdyI+PHBhdGggZD0iTTEwIDh2OGw1LTQtNS00em05LTVINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2SDVWNWgxNHYxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzdHJhaWdodGVuIj48cGF0aCBkPSJNMjEgNkgzYy0xLjEgMC0yIC45LTIgMnY4YzAgMS4xLjkgMiAyIDJoMThjMS4xIDAgMi0uOSAyLTJWOGMwLTEuMS0uOS0yLTItMnptMCAxMEgzVjhoMnY0aDJWOGgydjRoMlY4aDJ2NGgyVjhoMnY0aDJWOGgydjh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3R5bGUiPjxwYXRoIGQ9Ik0yLjUzIDE5LjY1bDEuMzQuNTZ2LTkuMDNsLTIuNDMgNS44NmMtLjQxIDEuMDIuMDggMi4xOSAxLjA5IDIuNjF6bTE5LjUtMy43TDE3LjA3IDMuOThjLS4zMS0uNzUtMS4wNC0xLjIxLTEuODEtMS4yMy0uMjYgMC0uNTMuMDQtLjc5LjE1TDcuMSA1Ljk1Yy0uNzUuMzEtMS4yMSAxLjAzLTEuMjMgMS44LS4wMS4yNy4wNC41NC4xNS44bDQuOTYgMTEuOTdjLjMxLjc2IDEuMDUgMS4yMiAxLjgzIDEuMjMuMjYgMCAuNTItLjA1Ljc3LS4xNWw3LjM2LTMuMDVjMS4wMi0uNDIgMS41MS0xLjU5IDEuMDktMi42ek03Ljg4IDguNzVjLS41NSAwLTEtLjQ1LTEtMXMuNDUtMSAxLTEgMSAuNDUgMSAxLS40NSAxLTEgMXptLTIgMTFjMCAxLjEuOSAyIDIgMmgxLjQ1bC0zLjQ1LTguMzR2Ni4zNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzd2l0Y2gtY2FtZXJhIj48cGF0aCBkPSJNMjAgNGgtMy4xN0wxNSAySDlMNy4xNyA0SDRjLTEuMSAwLTIgLjktMiAydjEyYzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJWNmMwLTEuMS0uOS0yLTItMnptLTUgMTEuNVYxM0g5djIuNUw1LjUgMTIgOSA4LjVWMTFoNlY4LjVsMy41IDMuNS0zLjUgMy41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN3aXRjaC12aWRlbyI+PHBhdGggZD0iTTE4IDkuNVY2YzAtLjU1LS40NS0xLTEtMUgzYy0uNTUgMC0xIC40NS0xIDF2MTJjMCAuNTUuNDUgMSAxIDFoMTRjLjU1IDAgMS0uNDUgMS0xdi0zLjVsNCA0di0xM2wtNCA0em0tNSA2VjEzSDd2Mi41TDMuNSAxMiA3IDguNVYxMWg2VjguNWwzLjUgMy41LTMuNSAzLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idGFnLWZhY2VzIj48cGF0aCBkPSJNMTEuOTkgMkM2LjQ3IDIgMiA2LjQ4IDIgMTJzNC40NyAxMCA5Ljk5IDEwQzE3LjUyIDIyIDIyIDE3LjUyIDIyIDEyUzE3LjUyIDIgMTEuOTkgMnpNMTIgMjBjLTQuNDIgMC04LTMuNTgtOC04czMuNTgtOCA4LTggOCAzLjU4IDggOC0zLjU4IDgtOCA4em0zLjUtOWMuODMgMCAxLjUtLjY3IDEuNS0xLjVTMTYuMzMgOCAxNS41IDggMTQgOC42NyAxNCA5LjVzLjY3IDEuNSAxLjUgMS41em0tNyAwYy44MyAwIDEuNS0uNjcgMS41LTEuNVM5LjMzIDggOC41IDggNyA4LjY3IDcgOS41IDcuNjcgMTEgOC41IDExem0zLjUgNi41YzIuMzMgMCA0LjMxLTEuNDYgNS4xMS0zLjVINi44OWMuOCAyLjA0IDIuNzggMy41IDUuMTEgMy41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRleHR1cmUiPjxwYXRoIGQ9Ik0xOS41MSAzLjA4TDMuMDggMTkuNTFjLjA5LjM0LjI3LjY1LjUxLjkuMjUuMjQuNTYuNDIuOS41MUwyMC45MyA0LjQ5Yy0uMTktLjY5LS43My0xLjIzLTEuNDItMS40MXpNMTEuODggM0wzIDExLjg4djIuODNMMTQuNzEgM2gtMi44M3pNNSAzYy0xLjEgMC0yIC45LTIgMnYybDQtNEg1em0xNCAxOGMuNTUgMCAxLjA1LS4yMiAxLjQxLS41OS4zNy0uMzYuNTktLjg2LjU5LTEuNDF2LTJsLTQgNGgyem0tOS43MSAwaDIuODNMMjEgMTIuMTJWOS4yOUw5LjI5IDIxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRpbWVsYXBzZSI+PHBhdGggZD0iTTE2LjI0IDcuNzZDMTUuMDcgNi41OSAxMy41NCA2IDEyIDZ2NmwtNC4yNCA0LjI0YzIuMzQgMi4zNCA2LjE0IDIuMzQgOC40OSAwIDIuMzQtMi4zNCAyLjM0LTYuMTQtLjAxLTguNDh6TTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTAgMThjLTQuNDIgMC04LTMuNTgtOC04czMuNTgtOCA4LTggOCAzLjU4IDggOC0zLjU4IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRpbWVyIj48cGF0aCBkPSJNMTUgMUg5djJoNlYxem0tNCAxM2gyVjhoLTJ2NnptOC4wMy02LjYxbDEuNDItMS40MmMtLjQzLS41MS0uOS0uOTktMS40MS0xLjQxbC0xLjQyIDEuNDJDMTYuMDcgNC43NCAxNC4xMiA0IDEyIDRjLTQuOTcgMC05IDQuMDMtOSA5czQuMDIgOSA5IDkgOS00LjAzIDktOWMwLTIuMTItLjc0LTQuMDctMS45Ny01LjYxek0xMiAyMGMtMy44NyAwLTctMy4xMy03LTdzMy4xMy03IDctNyA3IDMuMTMgNyA3LTMuMTMgNy03IDd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idGltZXItMTAiPjxwYXRoIGQ9Ik0wIDcuNzJWOS40bDMtMVYxOGgyVjZoLS4yNUwwIDcuNzJ6bTIzLjc4IDYuNjVjLS4xNC0uMjgtLjM1LS41My0uNjMtLjc0LS4yOC0uMjEtLjYxLS4zOS0xLjAxLS41M3MtLjg1LS4yNy0xLjM1LS4zOGMtLjM1LS4wNy0uNjQtLjE1LS44Ny0uMjMtLjIzLS4wOC0uNDEtLjE2LS41NS0uMjUtLjE0LS4wOS0uMjMtLjE5LS4yOC0uMy0uMDUtLjExLS4wOC0uMjQtLjA4LS4zOSAwLS4xNC4wMy0uMjguMDktLjQxLjA2LS4xMy4xNS0uMjUuMjctLjM0LjEyLS4xLjI3LS4xOC40NS0uMjRzLjQtLjA5LjY0LS4wOWMuMjUgMCAuNDcuMDQuNjYuMTEuMTkuMDcuMzUuMTcuNDguMjkuMTMuMTIuMjIuMjYuMjkuNDIuMDYuMTYuMS4zMi4xLjQ5aDEuOTVjMC0uMzktLjA4LS43NS0uMjQtMS4wOS0uMTYtLjM0LS4zOS0uNjMtLjY5LS44OC0uMy0uMjUtLjY2LS40NC0xLjA5LS41OUMyMS40OSA5LjA3IDIxIDkgMjAuNDYgOWMtLjUxIDAtLjk4LjA3LTEuMzkuMjEtLjQxLjE0LS43Ny4zMy0xLjA2LjU3LS4yOS4yNC0uNTEuNTItLjY3Ljg0LS4xNi4zMi0uMjMuNjUtLjIzIDEuMDFzLjA4LjY5LjIzLjk2Yy4xNS4yOC4zNi41Mi42NC43My4yNy4yMS42LjM4Ljk4LjUzLjM4LjE0LjgxLjI2IDEuMjcuMzYuMzkuMDguNzEuMTcuOTUuMjZzLjQzLjE5LjU3LjI5Yy4xMy4xLjIyLjIyLjI3LjM0LjA1LjEyLjA3LjI1LjA3LjM5IDAgLjMyLS4xMy41Ny0uNC43Ny0uMjcuMi0uNjYuMjktMS4xNy4yOS0uMjIgMC0uNDMtLjAyLS42NC0uMDgtLjIxLS4wNS0uNC0uMTMtLjU2LS4yNC0uMTctLjExLS4zLS4yNi0uNDEtLjQ0LS4xMS0uMTgtLjE3LS40MS0uMTgtLjY3aC0xLjg5YzAgLjM2LjA4LjcxLjI0IDEuMDUuMTYuMzQuMzkuNjUuNy45My4zMS4yNy42OS40OSAxLjE1LjY2LjQ2LjE3Ljk4LjI1IDEuNTguMjUuNTMgMCAxLjAxLS4wNiAxLjQ0LS4xOS40My0uMTMuOC0uMzEgMS4xMS0uNTQuMzEtLjIzLjU0LS41MS43MS0uODMuMTctLjMyLjI1LS42Ny4yNS0xLjA2LS4wMi0uNC0uMDktLjc0LS4yNC0xLjAyem0tOS45Ni03LjMyYy0uMzQtLjQtLjc1LS43LTEuMjMtLjg4LS40Ny0uMTgtMS4wMS0uMjctMS41OS0uMjctLjU4IDAtMS4xMS4wOS0xLjU5LjI3LS40OC4xOC0uODkuNDctMS4yMy44OC0uMzQuNDEtLjYuOTMtLjc5IDEuNTktLjE4LjY1LS4yOCAxLjQ1LS4yOCAyLjM5djEuOTJjMCAuOTQuMDkgMS43NC4yOCAyLjM5LjE5LjY2LjQ1IDEuMTkuOCAxLjYuMzQuNDEuNzUuNzEgMS4yMy44OS40OC4xOCAxLjAxLjI4IDEuNTkuMjguNTkgMCAxLjEyLS4wOSAxLjU5LS4yOC40OC0uMTguODgtLjQ4IDEuMjItLjg5LjM0LS40MS42LS45NC43OC0xLjYuMTgtLjY1LjI4LTEuNDUuMjgtMi4zOXYtMS45MmMwLS45NC0uMDktMS43NC0uMjgtMi4zOS0uMTgtLjY2LS40NC0xLjE5LS43OC0xLjU5em0tLjkyIDYuMTdjMCAuNi0uMDQgMS4xMS0uMTIgMS41My0uMDguNDItLjIuNzYtLjM2IDEuMDItLjE2LjI2LS4zNi40NS0uNTkuNTctLjIzLjEyLS41MS4xOC0uODIuMTgtLjMgMC0uNTgtLjA2LS44Mi0uMThzLS40NC0uMzEtLjYtLjU3Yy0uMTYtLjI2LS4yOS0uNi0uMzgtMS4wMi0uMDktLjQyLS4xMy0uOTMtLjEzLTEuNTN2LTIuNWMwLS42LjA0LTEuMTEuMTMtMS41Mi4wOS0uNDEuMjEtLjc0LjM4LTEgLjE2LS4yNS4zNi0uNDMuNi0uNTUuMjQtLjExLjUxLS4xNy44MS0uMTcuMzEgMCAuNTguMDYuODEuMTcuMjQuMTEuNDQuMjkuNi41NS4xNi4yNS4yOS41OC4zNy45OS4wOC40MS4xMy45Mi4xMyAxLjUydjIuNTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idGltZXItMyI+PHBhdGggZD0iTTExLjYxIDEyLjk3Yy0uMTYtLjI0LS4zNi0uNDYtLjYyLS42NS0uMjUtLjE5LS41Ni0uMzUtLjkzLS40OC4zLS4xNC41Ny0uMy44LS41LjIzLS4yLjQyLS40MS41Ny0uNjQuMTUtLjIzLjI3LS40Ni4zNC0uNzEuMDgtLjI0LjExLS40OS4xMS0uNzMgMC0uNTUtLjA5LTEuMDQtLjI4LTEuNDYtLjE4LS40Mi0uNDQtLjc3LS43OC0xLjA2LS4zMy0uMjgtLjczLS41LTEuMi0uNjQtLjQ1LS4xMy0uOTctLjItMS41My0uMi0uNTUgMC0xLjA2LjA4LTEuNTIuMjQtLjQ3LjE3LS44Ny40LTEuMi42OS0uMzMuMjktLjYuNjMtLjc4IDEuMDMtLjIuMzktLjI5LjgzLS4yOSAxLjI5aDEuOThjMC0uMjYuMDUtLjQ5LjE0LS42OS4wOS0uMi4yMi0uMzguMzgtLjUyLjE3LS4xNC4zNi0uMjUuNTgtLjMzLjIyLS4wOC40Ni0uMTIuNzMtLjEyLjYxIDAgMS4wNi4xNiAxLjM2LjQ3LjMuMzEuNDQuNzUuNDQgMS4zMiAwIC4yNy0uMDQuNTItLjEyLjc0LS4wOC4yMi0uMjEuNDEtLjM4LjU3LS4xNy4xNi0uMzguMjgtLjYzLjM3LS4yNS4wOS0uNTUuMTMtLjg5LjEzSDYuNzJ2MS41N0g3LjljLjM0IDAgLjY0LjA0LjkxLjExLjI3LjA4LjUuMTkuNjkuMzUuMTkuMTYuMzQuMzYuNDQuNjEuMS4yNC4xNi41NC4xNi44NyAwIC42Mi0uMTggMS4wOS0uNTMgMS40Mi0uMzUuMzMtLjg0LjQ5LTEuNDUuNDktLjI5IDAtLjU2LS4wNC0uOC0uMTMtLjI0LS4wOC0uNDQtLjItLjYxLS4zNi0uMTctLjE2LS4zLS4zNC0uMzktLjU2LS4wOS0uMjItLjE0LS40Ni0uMTQtLjcySDQuMTljMCAuNTUuMTEgMS4wMy4zMiAxLjQ1LjIxLjQyLjUuNzcuODYgMS4wNXMuNzcuNDkgMS4yNC42My45Ni4yMSAxLjQ4LjIxYy41NyAwIDEuMDktLjA4IDEuNTgtLjIzLjQ5LS4xNS45MS0uMzggMS4yNi0uNjguMzYtLjMuNjQtLjY2Ljg0LTEuMS4yLS40My4zLS45My4zLTEuNDggMC0uMjktLjA0LS41OC0uMTEtLjg2LS4wOC0uMjUtLjE5LS41MS0uMzUtLjc2em05LjI2IDEuNGMtLjE0LS4yOC0uMzUtLjUzLS42My0uNzQtLjI4LS4yMS0uNjEtLjM5LTEuMDEtLjUzcy0uODUtLjI3LTEuMzUtLjM4Yy0uMzUtLjA3LS42NC0uMTUtLjg3LS4yMy0uMjMtLjA4LS40MS0uMTYtLjU1LS4yNS0uMTQtLjA5LS4yMy0uMTktLjI4LS4zLS4wNS0uMTEtLjA4LS4yNC0uMDgtLjM5cy4wMy0uMjguMDktLjQxYy4wNi0uMTMuMTUtLjI1LjI3LS4zNC4xMi0uMS4yNy0uMTguNDUtLjI0cy40LS4wOS42NC0uMDljLjI1IDAgLjQ3LjA0LjY2LjExLjE5LjA3LjM1LjE3LjQ4LjI5LjEzLjEyLjIyLjI2LjI5LjQyLjA2LjE2LjEuMzIuMS40OWgxLjk1YzAtLjM5LS4wOC0uNzUtLjI0LTEuMDktLjE2LS4zNC0uMzktLjYzLS42OS0uODgtLjMtLjI1LS42Ni0uNDQtMS4wOS0uNTktLjQzLS4xNS0uOTItLjIyLTEuNDYtLjIyLS41MSAwLS45OC4wNy0xLjM5LjIxLS40MS4xNC0uNzcuMzMtMS4wNi41Ny0uMjkuMjQtLjUxLjUyLS42Ny44NC0uMTYuMzItLjIzLjY1LS4yMyAxLjAxcy4wOC42OC4yMy45NmMuMTUuMjguMzcuNTIuNjQuNzMuMjcuMjEuNi4zOC45OC41My4zOC4xNC44MS4yNiAxLjI3LjM2LjM5LjA4LjcxLjE3Ljk1LjI2cy40My4xOS41Ny4yOWMuMTMuMS4yMi4yMi4yNy4zNC4wNS4xMi4wNy4yNS4wNy4zOSAwIC4zMi0uMTMuNTctLjQuNzctLjI3LjItLjY2LjI5LTEuMTcuMjktLjIyIDAtLjQzLS4wMi0uNjQtLjA4LS4yMS0uMDUtLjQtLjEzLS41Ni0uMjQtLjE3LS4xMS0uMy0uMjYtLjQxLS40NC0uMTEtLjE4LS4xNy0uNDEtLjE4LS42N2gtMS44OWMwIC4zNi4wOC43MS4yNCAxLjA1LjE2LjM0LjM5LjY1LjcuOTMuMzEuMjcuNjkuNDkgMS4xNS42Ni40Ni4xNy45OC4yNSAxLjU4LjI1LjUzIDAgMS4wMS0uMDYgMS40NC0uMTkuNDMtLjEzLjgtLjMxIDEuMTEtLjU0LjMxLS4yMy41NC0uNTEuNzEtLjgzLjE3LS4zMi4yNS0uNjcuMjUtMS4wNi0uMDItLjQtLjA5LS43NC0uMjQtMS4wMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0aW1lci1vZmYiPjxwYXRoIGQ9Ik0xOS4wNCA0LjU1bC0xLjQyIDEuNDJDMTYuMDcgNC43NCAxNC4xMiA0IDEyIDRjLTEuODMgMC0zLjUzLjU1LTQuOTUgMS40OGwxLjQ2IDEuNDZDOS41MyA2LjM1IDEwLjczIDYgMTIgNmMzLjg3IDAgNyAzLjEzIDcgNyAwIDEuMjctLjM1IDIuNDctLjk0IDMuNDlsMS40NSAxLjQ1QzIwLjQ1IDE2LjUzIDIxIDE0LjgzIDIxIDEzYzAtMi4xMi0uNzQtNC4wNy0xLjk3LTUuNjFsMS40Mi0xLjQyLTEuNDEtMS40MnpNMTUgMUg5djJoNlYxem0tNCA4LjQ0bDIgMlY4aC0ydjEuNDR6TTMuMDIgNEwxLjc1IDUuMjcgNC41IDguMDNDMy41NSA5LjQ1IDMgMTEuMTYgMyAxM2MwIDQuOTcgNC4wMiA5IDkgOSAxLjg0IDAgMy41NS0uNTUgNC45OC0xLjVsMi41IDIuNSAxLjI3LTEuMjctNy43MS03LjcxTDMuMDIgNHpNMTIgMjBjLTMuODcgMC03LTMuMTMtNy03IDAtMS4yOC4zNS0yLjQ4Ljk1LTMuNTJsOS41NiA5LjU2Yy0xLjAzLjYxLTIuMjMuOTYtMy41MS45NnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0b25hbGl0eSI+PHBhdGggZD0iTTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bS0xIDE3LjkzYy0zLjk0LS40OS03LTMuODUtNy03LjkzczMuMDUtNy40NCA3LTcuOTN2MTUuODZ6bTItMTUuODZjMS4wMy4xMyAyIC40NSAyLjg3LjkzSDEzdi0uOTN6TTEzIDdoNS4yNGMuMjUuMzEuNDguNjUuNjggMUgxM1Y3em0wIDNoNi43NGMuMDguMzMuMTUuNjYuMTkgMUgxM3YtMXptMCA5LjkzVjE5aDIuODdjLS44Ny40OC0xLjg0LjgtMi44Ny45M3pNMTguMjQgMTdIMTN2LTFoNS45MmMtLjIuMzUtLjQzLjY5LS42OCAxem0xLjUtM0gxM3YtMWg2LjkzYy0uMDQuMzQtLjExLjY3LS4xOSAxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRyYW5zZm9ybSI+PHBhdGggZD0iTTIyIDE4di0ySDhWNGgyTDcgMSA0IDRoMnYySDJ2Mmg0djhjMCAxLjEuOSAyIDIgMmg4djJoLTJsMyAzIDMtM2gtMnYtMmg0ek0xMCA4aDZ2NmgyVjhjMC0xLjEtLjktMi0yLTJoLTZ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0dW5lIj48cGF0aCBkPSJNMyAxN3YyaDZ2LTJIM3pNMyA1djJoMTBWNUgzem0xMCAxNnYtMmg4di0yaC04di0yaC0ydjZoMnpNNyA5djJIM3YyaDR2MmgyVjlIN3ptMTQgNHYtMkgxMXYyaDEwem0tNi00aDJWN2g0VjVoLTRWM2gtMnY2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZXctY29tZnkiPjxwYXRoIGQ9Ik0zIDloNFY1SDN2NHptMCA1aDR2LTRIM3Y0em01IDBoNHYtNEg4djR6bTUgMGg0di00aC00djR6TTggOWg0VjVIOHY0em01LTR2NGg0VjVoLTR6bTUgOWg0di00aC00djR6TTMgMTloNHYtNEgzdjR6bTUgMGg0di00SDh2NHptNSAwaDR2LTRoLTR2NHptNSAwaDR2LTRoLTR2NHptMC0xNHY0aDRWNWgtNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJ2aWV3LWNvbXBhY3QiPjxwYXRoIGQ9Ik0zIDE5aDZ2LTdIM3Y3em03IDBoMTJ2LTdIMTB2N3pNMyA1djZoMTlWNUgzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZ25ldHRlIj48cGF0aCBkPSJNMjEgM0gzYy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE4YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS05IDE1Yy00LjQyIDAtOC0yLjY5LTgtNnMzLjU4LTYgOC02IDggMi42OSA4IDYtMy41OCA2LTggNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ3Yi1hdXRvIj48cGF0aCBkPSJNNi44NSAxMi42NWgyLjNMOCA5bC0xLjE1IDMuNjV6TTIyIDdsLTEuMiA2LjI5TDE5LjMgN2gtMS42bC0xLjQ5IDYuMjlMMTUgN2gtLjc2QzEyLjc3IDUuMTcgMTAuNTMgNCA4IDRjLTQuNDIgMC04IDMuNTgtOCA4czMuNTggOCA4IDhjMy4xMyAwIDUuODQtMS44MSA3LjE1LTQuNDNsLjEuNDNIMTdsMS41LTYuMUwyMCAxNmgxLjc1bDIuMDUtOUgyMnptLTExLjcgOWwtLjctMkg2LjRsLS43IDJIMy44TDcgN2gybDMuMiA5aC0xLjl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0id2ItY2xvdWR5Ij48cGF0aCBkPSJNMTkuMzYgMTAuMDRDMTguNjcgNi41OSAxNS42NCA0IDEyIDQgOS4xMSA0IDYuNiA1LjY0IDUuMzUgOC4wNCAyLjM0IDguMzYgMCAxMC45MSAwIDE0YzAgMy4zMSAyLjY5IDYgNiA2aDEzYzIuNzYgMCA1LTIuMjQgNS01IDAtMi42NC0yLjA1LTQuNzgtNC42NC00Ljk2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9IndiLWluY2FuZGVzY2VudCI+PHBhdGggZD0iTTMuNTUgMTguNTRsMS40MSAxLjQxIDEuNzktMS44LTEuNDEtMS40MS0xLjc5IDEuOHpNMTEgMjIuNDVoMlYxOS41aC0ydjIuOTV6TTQgMTAuNUgxdjJoM3YtMnptMTEtNC4xOVYxLjVIOXY0LjgxQzcuMjEgNy4zNSA2IDkuMjggNiAxMS41YzAgMy4zMSAyLjY5IDYgNiA2czYtMi42OSA2LTZjMC0yLjIyLTEuMjEtNC4xNS0zLTUuMTl6bTUgNC4xOXYyaDN2LTJoLTN6bS0yLjc2IDcuNjZsMS43OSAxLjggMS40MS0xLjQxLTEuOC0xLjc5LTEuNCAxLjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0id2ItaXJpZGVzY2VudCI+PHBhdGggZD0iTTUgMTQuNWgxNHYtNkg1djZ6TTExIC41NVYzLjVoMlYuNTVoLTJ6bTguMDQgMi41bC0xLjc5IDEuNzkgMS40MSAxLjQxIDEuOC0xLjc5LTEuNDItMS40MXpNMTMgMjIuNDVWMTkuNWgtMnYyLjk1aDJ6bTcuNDUtMy45MWwtMS44LTEuNzktMS40MSAxLjQxIDEuNzkgMS44IDEuNDItMS40MnpNMy41NSA0LjQ2bDEuNzkgMS43OSAxLjQxLTEuNDEtMS43OS0xLjc5LTEuNDEgMS40MXptMS40MSAxNS40OWwxLjc5LTEuOC0xLjQxLTEuNDEtMS43OSAxLjc5IDEuNDEgMS40MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ3Yi1zdW5ueSI+PHBhdGggZD0iTTYuNzYgNC44NGwtMS44LTEuNzktMS40MSAxLjQxIDEuNzkgMS43OSAxLjQyLTEuNDF6TTQgMTAuNUgxdjJoM3YtMnptOS05Ljk1aC0yVjMuNWgyVi41NXptNy40NSAzLjkxbC0xLjQxLTEuNDEtMS43OSAxLjc5IDEuNDEgMS40MSAxLjc5LTEuNzl6bS0zLjIxIDEzLjdsMS43OSAxLjggMS40MS0xLjQxLTEuOC0xLjc5LTEuNCAxLjR6TTIwIDEwLjV2Mmgzdi0yaC0zem0tOC01Yy0zLjMxIDAtNiAyLjY5LTYgNnMyLjY5IDYgNiA2IDYtMi42OSA2LTYtMi42OS02LTYtNnptLTEgMTYuOTVoMlYxOS41aC0ydjIuOTV6bS03LjQ1LTMuOTFsMS40MSAxLjQxIDEuNzktMS44LTEuNDEtMS40MS0xLjc5IDEuOHoiPjwvcGF0aD48L2c+CjwvZGVmcz48L3N2Zz4KPC9pcm9uLWljb25zZXQtc3ZnPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCh0ZW1wbGF0ZSQyLmNvbnRlbnQpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNCBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgoKICAgIGBpcm9uLWljb25zYCBpcyBhIHV0aWxpdHkgaW1wb3J0IHRoYXQgaW5jbHVkZXMgdGhlIGRlZmluaXRpb24gZm9yIHRoZQogICAgYGlyb24taWNvbmAgZWxlbWVudCwgYGlyb24taWNvbnNldC1zdmdgIGVsZW1lbnQsIGFzIHdlbGwgYXMgYW4gaW1wb3J0IGZvciB0aGUKICAgIGRlZmF1bHQgaWNvbiBzZXQuCgogICAgVGhlIGBpcm9uLWljb25zYCBkaXJlY3RvcnkgYWxzbyBpbmNsdWRlcyBpbXBvcnRzIGZvciBhZGRpdGlvbmFsIGljb24gc2V0cyB0aGF0CiAgICBjYW4gYmUgbG9hZGVkIGludG8geW91ciBwcm9qZWN0LgoKICAgIEV4YW1wbGUgbG9hZGluZyBpY29uIHNldDoKCiAgICAgICAgPHNjcmlwdCB0eXBlPSJtb2R1bGUiPgogICAgICAgICAgaW1wb3J0ICdAcG9seW1lci9pcm9uLWljb25zL21hcHMtaWNvbnMuanMnOwogICAgICAgIDwvSkFWQV9TQ1JJSUlJUFQvPgoKICAgIFRvIHVzZSBhbiBpY29uIGZyb20gb25lIG9mIHRoZXNlIHNldHMsIGZpcnN0IHByZWZpeCB5b3VyIGBpcm9uLWljb25gIHdpdGggdGhlCiAgICBpY29uIHNldCBuYW1lLCBmb2xsb3dlZCBieSBhIGNvbG9uLCAiOiIsIGFuZCB0aGVuIHRoZSBpY29uIGlkLgoKICAgIEV4YW1wbGUgdXNpbmcgdGhlIGRpcmVjdGlvbnMtYnVzIGljb24gZnJvbSB0aGUgbWFwcyBpY29uIHNldDoKCiAgICAgICAgPGlyb24taWNvbiBpY29uPSJtYXBzOmRpcmVjdGlvbnMtYnVzIj48L2lyb24taWNvbj4KCiAgICBTZWUgW2lyb24taWNvbl0oaHR0cHM6Ly93d3cud2ViY29tcG9uZW50cy5vcmcvZWxlbWVudC9AcG9seW1lci9pcm9uLWljb24pIGZvcgogICAgbW9yZSBpbmZvcm1hdGlvbiBhYm91dCB3b3JraW5nIHdpdGggaWNvbnMuCgogICAgU2VlIFtpcm9uLWljb25zZXRdKGh0dHBzOi8vd3d3LndlYmNvbXBvbmVudHMub3JnL2VsZW1lbnQvQHBvbHltZXIvaXJvbi1pY29uc2V0KQogICAgYW5kCiAgICBbaXJvbi1pY29uc2V0LXN2Z10oaHR0cHM6Ly93d3cud2ViY29tcG9uZW50cy5vcmcvZWxlbWVudC9AcG9seW1lci9pcm9uLWljb25zZXQtc3ZnKQogICAgZm9yIG1vcmUgaW5mb3JtYXRpb24gYWJvdXQgaG93IHRvIGNyZWF0ZSBhIGN1c3RvbSBpY29uc2V0LgoKICAgIEBncm91cCBJcm9uIEVsZW1lbnRzCiAgICBAcHNldWRvRWxlbWVudCBpcm9uLWljb25zCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCgogICAgY29uc3QgdGVtcGxhdGUkMyA9IGh0bWxgPGlyb24taWNvbnNldC1zdmcgbmFtZT0iaWNvbnMiIHNpemU9IjI0Ij4KPHN2Zz48ZGVmcz4KPGcgaWQ9IjNkLXJvdGF0aW9uIj48cGF0aCBkPSJNNy41MiAyMS40OEM0LjI1IDE5Ljk0IDEuOTEgMTYuNzYgMS41NSAxM0guMDVDLjU2IDE5LjE2IDUuNzEgMjQgMTIgMjRsLjY2LS4wMy0zLjgxLTMuODEtMS4zMyAxLjMyem0uODktNi41MmMtLjE5IDAtLjM3LS4wMy0uNTItLjA4LS4xNi0uMDYtLjI5LS4xMy0uNC0uMjQtLjExLS4xLS4yLS4yMi0uMjYtLjM3LS4wNi0uMTQtLjA5LS4zLS4wOS0uNDdoLTEuM2MwIC4zNi4wNy42OC4yMS45NS4xNC4yNy4zMy41LjU2LjY5LjI0LjE4LjUxLjMyLjgyLjQxLjMuMS42Mi4xNS45Ni4xNS4zNyAwIC43Mi0uMDUgMS4wMy0uMTUuMzItLjEuNi0uMjUuODMtLjQ0cy40Mi0uNDMuNTUtLjcyYy4xMy0uMjkuMi0uNjEuMi0uOTcgMC0uMTktLjAyLS4zOC0uMDctLjU2LS4wNS0uMTgtLjEyLS4zNS0uMjMtLjUxLS4xLS4xNi0uMjQtLjMtLjQtLjQzLS4xNy0uMTMtLjM3LS4yMy0uNjEtLjMxLjItLjA5LjM3LS4yLjUyLS4zMy4xNS0uMTMuMjctLjI3LjM3LS40Mi4xLS4xNS4xNy0uMy4yMi0uNDYuMDUtLjE2LjA3LS4zMi4wNy0uNDggMC0uMzYtLjA2LS42OC0uMTgtLjk2LS4xMi0uMjgtLjI5LS41MS0uNTEtLjY5LS4yLS4xOS0uNDctLjMzLS43Ny0uNDNDOS4xIDguMDUgOC43NiA4IDguMzkgOGMtLjM2IDAtLjY5LjA1LTEgLjE2LS4zLjExLS41Ny4yNi0uNzkuNDUtLjIxLjE5LS4zOC40MS0uNTEuNjctLjEyLjI2LS4xOC41NC0uMTguODVoMS4zYzAtLjE3LjAzLS4zMi4wOS0uNDVzLjE0LS4yNS4yNS0uMzRjLjExLS4wOS4yMy0uMTcuMzgtLjIyLjE1LS4wNS4zLS4wOC40OC0uMDguNCAwIC43LjEuODkuMzEuMTkuMi4yOS40OS4yOS44NiAwIC4xOC0uMDMuMzQtLjA4LjQ5LS4wNS4xNS0uMTQuMjctLjI1LjM3LS4xMS4xLS4yNS4xOC0uNDEuMjQtLjE2LjA2LS4zNi4wOS0uNTguMDlINy41djEuMDNoLjc3Yy4yMiAwIC40Mi4wMi42LjA3cy4zMy4xMy40NS4yM2MuMTIuMTEuMjIuMjQuMjkuNC4wNy4xNi4xLjM1LjEuNTcgMCAuNDEtLjEyLjcyLS4zNS45My0uMjMuMjMtLjU1LjMzLS45NS4zM3ptOC41NS01LjkyYy0uMzItLjMzLS43LS41OS0xLjE0LS43Ny0uNDMtLjE4LS45Mi0uMjctMS40Ni0uMjdIMTJ2OGgyLjNjLjU1IDAgMS4wNi0uMDkgMS41MS0uMjcuNDUtLjE4Ljg0LS40MyAxLjE2LS43Ni4zMi0uMzMuNTctLjczLjc0LTEuMTkuMTctLjQ3LjI2LS45OS4yNi0xLjU3di0uNGMwLS41OC0uMDktMS4xLS4yNi0xLjU3LS4xOC0uNDctLjQzLS44Ny0uNzUtMS4yem0tLjM5IDMuMTZjMCAuNDItLjA1Ljc5LS4xNCAxLjEzLS4xLjMzLS4yNC42Mi0uNDMuODUtLjE5LjIzLS40My40MS0uNzEuNTMtLjI5LjEyLS42Mi4xOC0uOTkuMThoLS45MVY5LjEyaC45N2MuNzIgMCAxLjI3LjIzIDEuNjQuNjkuMzguNDYuNTcgMS4xMi41NyAxLjk5di40ek0xMiAwbC0uNjYuMDMgMy44MSAzLjgxIDEuMzMtMS4zM2MzLjI3IDEuNTUgNS42MSA0LjcyIDUuOTYgOC40OGgxLjVDMjMuNDQgNC44NCAxOC4yOSAwIDEyIDB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWNjZXNzaWJpbGl0eSI+PHBhdGggZD0iTTEyIDJjMS4xIDAgMiAuOSAyIDJzLS45IDItMiAyLTItLjktMi0yIC45LTIgMi0yem05IDdoLTZ2MTNoLTJ2LTZoLTJ2Nkg5VjlIM1Y3aDE4djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWNjZXNzaWJsZSI+PGNpcmNsZSBjeD0iMTIiIGN5PSI0IiByPSIyIj48L2NpcmNsZT48cGF0aCBkPSJNMTkgMTN2LTJjLTEuNTQuMDItMy4wOS0uNzUtNC4wNy0xLjgzbC0xLjI5LTEuNDNjLS4xNy0uMTktLjM4LS4zNC0uNjEtLjQ1LS4wMSAwLS4wMS0uMDEtLjAyLS4wMUgxM2MtLjM1LS4yLS43NS0uMy0xLjE5LS4yNkMxMC43NiA3LjExIDEwIDguMDQgMTAgOS4wOVYxNWMwIDEuMS45IDIgMiAyaDV2NWgydi01LjVjMC0xLjEtLjktMi0yLTJoLTN2LTMuNDVjMS4yOSAxLjA3IDMuMjUgMS45NCA1IDEuOTV6bS02LjE3IDVjLS40MSAxLjE2LTEuNTIgMi0yLjgzIDItMS42NiAwLTMtMS4zNC0zLTMgMC0xLjMxLjg0LTIuNDEgMi0yLjgzVjEyLjFjLTIuMjguNDYtNCAyLjQ4LTQgNC45IDAgMi43NiAyLjI0IDUgNSA1IDIuNDIgMCA0LjQ0LTEuNzIgNC45LTRoLTIuMDd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWNjb3VudC1iYWxhbmNlIj48cGF0aCBkPSJNNCAxMHY3aDN2LTdINHptNiAwdjdoM3YtN2gtM3pNMiAyMmgxOXYtM0gydjN6bTE0LTEydjdoM3YtN2gtM3ptLTQuNS05TDIgNnYyaDE5VjZsLTkuNS01eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFjY291bnQtYmFsYW5jZS13YWxsZXQiPjxwYXRoIGQ9Ik0yMSAxOHYxYzAgMS4xLS45IDItMiAySDVjLTEuMTEgMC0yLS45LTItMlY1YzAtMS4xLjg5LTIgMi0yaDE0YzEuMSAwIDIgLjkgMiAydjFoLTljLTEuMTEgMC0yIC45LTIgMnY4YzAgMS4xLjg5IDIgMiAyaDl6bS05LTJoMTBWOEgxMnY4em00LTIuNWMtLjgzIDAtMS41LS42Ny0xLjUtMS41cy42Ny0xLjUgMS41LTEuNSAxLjUuNjcgMS41IDEuNS0uNjcgMS41LTEuNSAxLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWNjb3VudC1ib3giPjxwYXRoIGQ9Ik0zIDV2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMkg1Yy0xLjExIDAtMiAuOS0yIDJ6bTEyIDRjMCAxLjY2LTEuMzQgMy0zIDNzLTMtMS4zNC0zLTMgMS4zNC0zIDMtMyAzIDEuMzQgMyAzem0tOSA4YzAtMiA0LTMuMSA2LTMuMXM2IDEuMSA2IDMuMXYxSDZ2LTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWNjb3VudC1jaXJjbGUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDNjMS42NiAwIDMgMS4zNCAzIDNzLTEuMzQgMy0zIDMtMy0xLjM0LTMtMyAxLjM0LTMgMy0zem0wIDE0LjJjLTIuNSAwLTQuNzEtMS4yOC02LTMuMjIuMDMtMS45OSA0LTMuMDggNi0zLjA4IDEuOTkgMCA1Ljk3IDEuMDkgNiAzLjA4LTEuMjkgMS45NC0zLjUgMy4yMi02IDMuMjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWRkIj48cGF0aCBkPSJNMTkgMTNoLTZ2NmgtMnYtNkg1di0yaDZWNWgydjZoNnYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFkZC1hbGVydCI+PHBhdGggZD0iTTEwLjAxIDIxLjAxYzAgMS4xLjg5IDEuOTkgMS45OSAxLjk5czEuOTktLjg5IDEuOTktMS45OWgtMy45OHptOC44Ny00LjE5VjExYzAtMy4yNS0yLjI1LTUuOTctNS4yOS02LjY5di0uNzJDMTMuNTkgMi43MSAxMi44OCAyIDEyIDJzLTEuNTkuNzEtMS41OSAxLjU5di43MkM3LjM3IDUuMDMgNS4xMiA3Ljc1IDUuMTIgMTF2NS44MkwzIDE4Ljk0VjIwaDE4di0xLjA2bC0yLjEyLTIuMTJ6TTE2IDEzLjAxaC0zdjNoLTJ2LTNIOFYxMWgzVjhoMnYzaDN2Mi4wMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJhZGQtYm94Ij48cGF0aCBkPSJNMTkgM0g1Yy0xLjExIDAtMiAuOS0yIDJ2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTIgMTBoLTR2NGgtMnYtNEg3di0yaDRWN2gydjRoNHYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFkZC1jaXJjbGUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem01IDExaC00djRoLTJ2LTRIN3YtMmg0VjdoMnY0aDR2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJhZGQtY2lyY2xlLW91dGxpbmUiPjxwYXRoIGQ9Ik0xMyA3aC0ydjRIN3YyaDR2NGgydi00aDR2LTJoLTRWN3ptLTEtNUM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWRkLXNob3BwaW5nLWNhcnQiPjxwYXRoIGQ9Ik0xMSA5aDJWNmgzVjRoLTNWMWgtMnYzSDh2MmgzdjN6bS00IDljLTEuMSAwLTEuOTkuOS0xLjk5IDJTNS45IDIyIDcgMjJzMi0uOSAyLTItLjktMi0yLTJ6bTEwIDBjLTEuMSAwLTEuOTkuOS0xLjk5IDJzLjg5IDIgMS45OSAyIDItLjkgMi0yLS45LTItMi0yem0tOS44My0zLjI1bC4wMy0uMTIuOS0xLjYzaDcuNDVjLjc1IDAgMS40MS0uNDEgMS43NS0xLjAzbDMuODYtNy4wMUwxOS40MiA0aC0uMDFsLTEuMSAyLTIuNzYgNUg4LjUzbC0uMTMtLjI3TDYuMTYgNmwtLjk1LTItLjk0LTJIMXYyaDJsMy42IDcuNTktMS4zNSAyLjQ1Yy0uMTYuMjgtLjI1LjYxLS4yNS45NiAwIDEuMS45IDIgMiAyaDEydi0ySDcuNDJjLS4xMyAwLS4yNS0uMTEtLjI1LS4yNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJhbGFybSI+PHBhdGggZD0iTTIyIDUuNzJsLTQuNi0zLjg2LTEuMjkgMS41MyA0LjYgMy44NkwyMiA1Ljcyek03Ljg4IDMuMzlMNi42IDEuODYgMiA1LjcxbDEuMjkgMS41MyA0LjU5LTMuODV6TTEyLjUgOEgxMXY2bDQuNzUgMi44NS43NS0xLjIzLTQtMi4zN1Y4ek0xMiA0Yy00Ljk3IDAtOSA0LjAzLTkgOXM0LjAyIDkgOSA5YzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05em0wIDE2Yy0zLjg3IDAtNy0zLjEzLTctN3MzLjEzLTcgNy03IDcgMy4xMyA3IDctMy4xMyA3LTcgN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJhbGFybS1hZGQiPjxwYXRoIGQ9Ik03Ljg4IDMuMzlMNi42IDEuODYgMiA1LjcxbDEuMjkgMS41MyA0LjU5LTMuODV6TTIyIDUuNzJsLTQuNi0zLjg2LTEuMjkgMS41MyA0LjYgMy44NkwyMiA1Ljcyek0xMiA0Yy00Ljk3IDAtOSA0LjAzLTkgOXM0LjAyIDkgOSA5YzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05em0wIDE2Yy0zLjg3IDAtNy0zLjEzLTctN3MzLjEzLTcgNy03IDcgMy4xMyA3IDctMy4xMyA3LTcgN3ptMS0xMWgtMnYzSDh2MmgzdjNoMnYtM2gzdi0yaC0zVjl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWxhcm0tb2ZmIj48cGF0aCBkPSJNMTIgNmMzLjg3IDAgNyAzLjEzIDcgNyAwIC44NC0uMTYgMS42NS0uNDMgMi40bDEuNTIgMS41MmMuNTgtMS4xOS45MS0yLjUxLjkxLTMuOTIgMC00Ljk3LTQuMDMtOS05LTktMS40MSAwLTIuNzMuMzMtMy45Mi45MUw5LjYgNi40M0MxMC4zNSA2LjE2IDExLjE2IDYgMTIgNnptMTAtLjI4bC00LjYtMy44Ni0xLjI5IDEuNTMgNC42IDMuODZMMjIgNS43MnpNMi45MiAyLjI5TDEuNjUgMy41NyAyLjk4IDQuOWwtMS4xMS45MyAxLjQyIDEuNDIgMS4xMS0uOTQuOC44QzMuODMgOC42OSAzIDEwLjc1IDMgMTNjMCA0Ljk3IDQuMDIgOSA5IDkgMi4yNSAwIDQuMzEtLjgzIDUuODktMi4ybDIuMiAyLjIgMS4yNy0xLjI3TDMuODkgMy4yN2wtLjk3LS45OHptMTMuNTUgMTYuMUMxNS4yNiAxOS4zOSAxMy43IDIwIDEyIDIwYy0zLjg3IDAtNy0zLjEzLTctNyAwLTEuNy42MS0zLjI2IDEuNjEtNC40N2w5Ljg2IDkuODZ6TTguMDIgMy4yOEw2LjYgMS44NmwtLjg2LjcxIDEuNDIgMS40Mi44Ni0uNzF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWxhcm0tb24iPjxwYXRoIGQ9Ik0yMiA1LjcybC00LjYtMy44Ni0xLjI5IDEuNTMgNC42IDMuODZMMjIgNS43MnpNNy44OCAzLjM5TDYuNiAxLjg2IDIgNS43MWwxLjI5IDEuNTMgNC41OS0zLjg1ek0xMiA0Yy00Ljk3IDAtOSA0LjAzLTkgOXM0LjAyIDkgOSA5YzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05em0wIDE2Yy0zLjg3IDAtNy0zLjEzLTctN3MzLjEzLTcgNy03IDcgMy4xMyA3IDctMy4xMyA3LTcgN3ptLTEuNDYtNS40N0w4LjQxIDEyLjRsLTEuMDYgMS4wNiAzLjE4IDMuMTggNi02LTEuMDYtMS4wNi00LjkzIDQuOTV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYWxsLW91dCI+PHBhdGggZD0iTTE2LjIxIDQuMTZsNCA0di00em00IDEybC00IDRoNHptLTEyIDRsLTQtNHY0em0tNC0xMmw0LTRoLTR6bTEyLjk1LS45NWMtMi43My0yLjczLTcuMTctMi43My05LjkgMHMtMi43MyA3LjE3IDAgOS45IDcuMTcgMi43MyA5LjkgMCAyLjczLTcuMTYgMC05Ljl6bS0xLjEgOC44Yy0yLjEzIDIuMTMtNS41NyAyLjEzLTcuNyAwcy0yLjEzLTUuNTcgMC03LjcgNS41Ny0yLjEzIDcuNyAwIDIuMTMgNS41NyAwIDcuN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJhbmRyb2lkIj48cGF0aCBkPSJNNiAxOGMwIC41NS40NSAxIDEgMWgxdjMuNWMwIC44My42NyAxLjUgMS41IDEuNXMxLjUtLjY3IDEuNS0xLjVWMTloMnYzLjVjMCAuODMuNjcgMS41IDEuNSAxLjVzMS41LS42NyAxLjUtMS41VjE5aDFjLjU1IDAgMS0uNDUgMS0xVjhINnYxMHpNMy41IDhDMi42NyA4IDIgOC42NyAyIDkuNXY3YzAgLjgzLjY3IDEuNSAxLjUgMS41UzUgMTcuMzMgNSAxNi41di03QzUgOC42NyA0LjMzIDggMy41IDh6bTE3IDBjLS44MyAwLTEuNS42Ny0xLjUgMS41djdjMCAuODMuNjcgMS41IDEuNSAxLjVzMS41LS42NyAxLjUtMS41di03YzAtLjgzLS42Ny0xLjUtMS41LTEuNXptLTQuOTctNS44NGwxLjMtMS4zYy4yLS4yLjItLjUxIDAtLjcxLS4yLS4yLS41MS0uMi0uNzEgMGwtMS40OCAxLjQ4QzEzLjg1IDEuMjMgMTIuOTUgMSAxMiAxYy0uOTYgMC0xLjg2LjIzLTIuNjYuNjNMNy44NS4xNWMtLjItLjItLjUxLS4yLS43MSAwLS4yLjItLjIuNTEgMCAuNzFsMS4zMSAxLjMxQzYuOTcgMy4yNiA2IDUuMDEgNiA3aDEyYzAtMS45OS0uOTctMy43NS0yLjQ3LTQuODR6TTEwIDVIOVY0aDF2MXptNSAwaC0xVjRoMXYxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFubm91bmNlbWVudCI+PHBhdGggZD0iTTIwIDJINGMtMS4xIDAtMS45OS45LTEuOTkgMkwyIDIybDQtNGgxNGMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tNyA5aC0yVjVoMnY2em0wIDRoLTJ2LTJoMnYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFwcHMiPjxwYXRoIGQ9Ik00IDhoNFY0SDR2NHptNiAxMmg0di00aC00djR6bS02IDBoNHYtNEg0djR6bTAtNmg0di00SDR2NHptNiAwaDR2LTRoLTR2NHptNi0xMHY0aDRWNGgtNHptLTYgNGg0VjRoLTR2NHptNiA2aDR2LTRoLTR2NHptMCA2aDR2LTRoLTR2NHoiPjwvcGF0aD48L2c+CjxnIGlkPSJhcmNoaXZlIj48cGF0aCBkPSJNMjAuNTQgNS4yM2wtMS4zOS0xLjY4QzE4Ljg4IDMuMjEgMTguNDcgMyAxOCAzSDZjLS40NyAwLS44OC4yMS0xLjE2LjU1TDMuNDYgNS4yM0MzLjE3IDUuNTcgMyA2LjAyIDMgNi41VjE5YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNi41YzAtLjQ4LS4xNy0uOTMtLjQ2LTEuMjd6TTEyIDE3LjVMNi41IDEySDEwdi0yaDR2MmgzLjVMMTIgMTcuNXpNNS4xMiA1bC44MS0xaDEybC45NCAxSDUuMTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXJyb3ctYmFjayI+PHBhdGggZD0iTTIwIDExSDcuODNsNS41OS01LjU5TDEyIDRsLTggOCA4IDggMS40MS0xLjQxTDcuODMgMTNIMjB2LTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXJyb3ctZG93bndhcmQiPjxwYXRoIGQ9Ik0yMCAxMmwtMS40MS0xLjQxTDEzIDE2LjE3VjRoLTJ2MTIuMTdsLTUuNTgtNS41OUw0IDEybDggOCA4LTh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXJyb3ctZHJvcC1kb3duIj48cGF0aCBkPSJNNyAxMGw1IDUgNS01eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFycm93LWRyb3AtZG93bi1jaXJjbGUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDEybC00LTRoOGwtNCA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFycm93LWRyb3AtdXAiPjxwYXRoIGQ9Ik03IDE0bDUtNSA1IDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXJyb3ctZm9yd2FyZCI+PHBhdGggZD0iTTEyIDRsLTEuNDEgMS40MUwxNi4xNyAxMUg0djJoMTIuMTdsLTUuNTggNS41OUwxMiAyMGw4LTh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXJyb3ctdXB3YXJkIj48cGF0aCBkPSJNNCAxMmwxLjQxIDEuNDFMMTEgNy44M1YyMGgyVjcuODNsNS41OCA1LjU5TDIwIDEybC04LTgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFzcGVjdC1yYXRpbyI+PHBhdGggZD0iTTE5IDEyaC0ydjNoLTN2Mmg1di01ek03IDloM1Y3SDV2NWgyVjl6bTE0LTZIM2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxOGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2LjAxSDNWNC45OWgxOHYxNC4wMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJhc3Nlc3NtZW50Ij48cGF0aCBkPSJNMTkgM0g1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6TTkgMTdIN3YtN2gydjd6bTQgMGgtMlY3aDJ2MTB6bTQgMGgtMnYtNGgydjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXNzaWdubWVudCI+PHBhdGggZD0iTTE5IDNoLTQuMThDMTQuNCAxLjg0IDEzLjMgMSAxMiAxYy0xLjMgMC0yLjQuODQtMi44MiAySDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTcgMGMuNTUgMCAxIC40NSAxIDFzLS40NSAxLTEgMS0xLS40NS0xLTEgLjQ1LTEgMS0xem0yIDE0SDd2LTJoN3Yyem0zLTRIN3YtMmgxMHYyem0wLTRIN1Y3aDEwdjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXNzaWdubWVudC1pbmQiPjxwYXRoIGQ9Ik0xOSAzaC00LjE4QzE0LjQgMS44NCAxMy4zIDEgMTIgMWMtMS4zIDAtMi40Ljg0LTIuODIgMkg1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS03IDBjLjU1IDAgMSAuNDUgMSAxcy0uNDUgMS0xIDEtMS0uNDUtMS0xIC40NS0xIDEtMXptMCA0YzEuNjYgMCAzIDEuMzQgMyAzcy0xLjM0IDMtMyAzLTMtMS4zNC0zLTMgMS4zNC0zIDMtM3ptNiAxMkg2di0xLjRjMC0yIDQtMy4xIDYtMy4xczYgMS4xIDYgMy4xVjE5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImFzc2lnbm1lbnQtbGF0ZSI+PHBhdGggZD0iTTE5IDNoLTQuMThDMTQuNCAxLjg0IDEzLjMgMSAxMiAxYy0xLjMgMC0yLjQuODQtMi44MiAySDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTYgMTVoLTJ2LTJoMnYyem0wLTRoLTJWOGgydjZ6bS0xLTljLS41NSAwLTEtLjQ1LTEtMXMuNDUtMSAxLTEgMSAuNDUgMSAxLS40NSAxLTEgMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJhc3NpZ25tZW50LXJldHVybiI+PHBhdGggZD0iTTE5IDNoLTQuMThDMTQuNCAxLjg0IDEzLjMgMSAxMiAxYy0xLjMgMC0yLjQuODQtMi44MiAySDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTcgMGMuNTUgMCAxIC40NSAxIDFzLS40NSAxLTEgMS0xLS40NS0xLTEgLjQ1LTEgMS0xem00IDEyaC00djNsLTUtNSA1LTV2M2g0djR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXNzaWdubWVudC1yZXR1cm5lZCI+PHBhdGggZD0iTTE5IDNoLTQuMThDMTQuNCAxLjg0IDEzLjMgMSAxMiAxYy0xLjMgMC0yLjQuODQtMi44MiAySDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTcgMGMuNTUgMCAxIC40NSAxIDFzLS40NSAxLTEgMS0xLS40NS0xLTEgLjQ1LTEgMS0xem0wIDE1bC01LTVoM1Y5aDR2NGgzbC01IDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYXNzaWdubWVudC10dXJuZWQtaW4iPjxwYXRoIGQ9Ik0xOSAzaC00LjE4QzE0LjQgMS44NCAxMy4zIDEgMTIgMWMtMS4zIDAtMi40Ljg0LTIuODIgMkg1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS03IDBjLjU1IDAgMSAuNDUgMSAxcy0uNDUgMS0xIDEtMS0uNDUtMS0xIC40NS0xIDEtMXptLTIgMTRsLTQtNCAxLjQxLTEuNDFMMTAgMTQuMTdsNi41OS02LjU5TDE4IDlsLTggOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJhdHRhY2htZW50Ij48cGF0aCBkPSJNMiAxMi41QzIgOS40NiA0LjQ2IDcgNy41IDdIMThjMi4yMSAwIDQgMS43OSA0IDRzLTEuNzkgNC00IDRIOS41QzguMTIgMTUgNyAxMy44OCA3IDEyLjVTOC4xMiAxMCA5LjUgMTBIMTd2Mkg5LjQxYy0uNTUgMC0uNTUgMSAwIDFIMThjMS4xIDAgMi0uOSAyLTJzLS45LTItMi0ySDcuNUM1LjU3IDkgNCAxMC41NyA0IDEyLjVTNS41NyAxNiA3LjUgMTZIMTd2Mkg3LjVDNC40NiAxOCAyIDE1LjU0IDIgMTIuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJhdXRvcmVuZXciPjxwYXRoIGQ9Ik0xMiA2djNsNC00LTQtNHYzYy00LjQyIDAtOCAzLjU4LTggOCAwIDEuNTcuNDYgMy4wMyAxLjI0IDQuMjZMNi43IDE0LjhjLS40NS0uODMtLjctMS43OS0uNy0yLjggMC0zLjMxIDIuNjktNiA2LTZ6bTYuNzYgMS43NEwxNy4zIDkuMmMuNDQuODQuNyAxLjc5LjcgMi44IDAgMy4zMS0yLjY5IDYtNiA2di0zbC00IDQgNCA0di0zYzQuNDIgMCA4LTMuNTggOC04IDAtMS41Ny0uNDYtMy4wMy0xLjI0LTQuMjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYmFja3NwYWNlIj48cGF0aCBkPSJNMjIgM0g3Yy0uNjkgMC0xLjIzLjM1LTEuNTkuODhMMCAxMmw1LjQxIDguMTFjLjM2LjUzLjkuODkgMS41OS44OWgxNWMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0tMyAxMi41OUwxNy41OSAxNyAxNCAxMy40MSAxMC40MSAxNyA5IDE1LjU5IDEyLjU5IDEyIDkgOC40MSAxMC40MSA3IDE0IDEwLjU5IDE3LjU5IDcgMTkgOC40MSAxNS40MSAxMiAxOSAxNS41OXoiPjwvcGF0aD48L2c+CjxnIGlkPSJiYWNrdXAiPjxwYXRoIGQ9Ik0xOS4zNSAxMC4wNEMxOC42NyA2LjU5IDE1LjY0IDQgMTIgNCA5LjExIDQgNi42IDUuNjQgNS4zNSA4LjA0IDIuMzQgOC4zNiAwIDEwLjkxIDAgMTRjMCAzLjMxIDIuNjkgNiA2IDZoMTNjMi43NiAwIDUtMi4yNCA1LTUgMC0yLjY0LTIuMDUtNC43OC00LjY1LTQuOTZ6TTE0IDEzdjRoLTR2LTRIN2w1LTUgNSA1aC0zeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJsb2NrIj48cGF0aCBkPSJNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnpNNCAxMmMwLTQuNDIgMy41OC04IDgtOCAxLjg1IDAgMy41NS42MyA0LjkgMS42OUw1LjY5IDE2LjlDNC42MyAxNS41NSA0IDEzLjg1IDQgMTJ6bTggOGMtMS44NSAwLTMuNTUtLjYzLTQuOS0xLjY5TDE4LjMxIDcuMUMxOS4zNyA4LjQ1IDIwIDEwLjE1IDIwIDEyYzAgNC40Mi0zLjU4IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJvb2siPjxwYXRoIGQ9Ik0xOCAySDZjLTEuMSAwLTIgLjktMiAydjE2YzAgMS4xLjkgMiAyIDJoMTJjMS4xIDAgMi0uOSAyLTJWNGMwLTEuMS0uOS0yLTItMnpNNiA0aDV2OGwtMi41LTEuNUw2IDEyVjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYm9va21hcmsiPjxwYXRoIGQ9Ik0xNyAzSDdjLTEuMSAwLTEuOTkuOS0xLjk5IDJMNSAyMWw3LTMgNyAzVjVjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYm9va21hcmstYm9yZGVyIj48cGF0aCBkPSJNMTcgM0g3Yy0xLjEgMC0xLjk5LjktMS45OSAyTDUgMjFsNy0zIDcgM1Y1YzAtMS4xLS45LTItMi0yem0wIDE1bC01LTIuMThMNyAxOFY1aDEwdjEzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImJ1Zy1yZXBvcnQiPjxwYXRoIGQ9Ik0yMCA4aC0yLjgxYy0uNDUtLjc4LTEuMDctMS40NS0xLjgyLTEuOTZMMTcgNC40MSAxNS41OSAzbC0yLjE3IDIuMTdDMTIuOTYgNS4wNiAxMi40OSA1IDEyIDVjLS40OSAwLS45Ni4wNi0xLjQxLjE3TDguNDEgMyA3IDQuNDFsMS42MiAxLjYzQzcuODggNi41NSA3LjI2IDcuMjIgNi44MSA4SDR2MmgyLjA5Yy0uMDUuMzMtLjA5LjY2LS4wOSAxdjFINHYyaDJ2MWMwIC4zNC4wNC42Ny4wOSAxSDR2MmgyLjgxYzEuMDQgMS43OSAyLjk3IDMgNS4xOSAzczQuMTUtMS4yMSA1LjE5LTNIMjB2LTJoLTIuMDljLjA1LS4zMy4wOS0uNjYuMDktMXYtMWgydi0yaC0ydi0xYzAtLjM0LS4wNC0uNjctLjA5LTFIMjBWOHptLTYgOGgtNHYtMmg0djJ6bTAtNGgtNHYtMmg0djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iYnVpbGQiPjxwYXRoIGQ9Ik0yMi43IDE5bC05LjEtOS4xYy45LTIuMy40LTUtMS41LTYuOS0yLTItNS0yLjQtNy40LTEuM0w5IDYgNiA5IDEuNiA0LjdDLjQgNy4xLjkgMTAuMSAyLjkgMTIuMWMxLjkgMS45IDQuNiAyLjQgNi45IDEuNWw5LjEgOS4xYy40LjQgMSAuNCAxLjQgMGwyLjMtMi4zYy41LS40LjUtMS4xLjEtMS40eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhY2hlZCI+PHBhdGggZD0iTTE5IDhsLTQgNGgzYzAgMy4zMS0yLjY5IDYtNiA2LTEuMDEgMC0xLjk3LS4yNS0yLjgtLjdsLTEuNDYgMS40NkM4Ljk3IDE5LjU0IDEwLjQzIDIwIDEyIDIwYzQuNDIgMCA4LTMuNTggOC04aDNsLTQtNHpNNiAxMmMwLTMuMzEgMi42OS02IDYtNiAxLjAxIDAgMS45Ny4yNSAyLjguN2wxLjQ2LTEuNDZDMTUuMDMgNC40NiAxMy41NyA0IDEyIDRjLTQuNDIgMC04IDMuNTgtOCA4SDFsNCA0IDQtNEg2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhbWVyYS1lbmhhbmNlIj48cGF0aCBkPSJNOSAzTDcuMTcgNUg0Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjdjMC0xLjEtLjktMi0yLTJoLTMuMTdMMTUgM0g5em0zIDE1Yy0yLjc2IDAtNS0yLjI0LTUtNXMyLjI0LTUgNS01IDUgMi4yNCA1IDUtMi4yNCA1LTUgNXptMC0xbDEuMjUtMi43NUwxNiAxM2wtMi43NS0xLjI1TDEyIDlsLTEuMjUgMi43NUw4IDEzbDIuNzUgMS4yNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJjYW5jZWwiPjxwYXRoIGQ9Ik0xMiAyQzYuNDcgMiAyIDYuNDcgMiAxMnM0LjQ3IDEwIDEwIDEwIDEwLTQuNDcgMTAtMTBTMTcuNTMgMiAxMiAyem01IDEzLjU5TDE1LjU5IDE3IDEyIDEzLjQxIDguNDEgMTcgNyAxNS41OSAxMC41OSAxMiA3IDguNDEgOC40MSA3IDEyIDEwLjU5IDE1LjU5IDcgMTcgOC40MSAxMy40MSAxMiAxNyAxNS41OXoiPjwvcGF0aD48L2c+CjxnIGlkPSJjYXJkLWdpZnRjYXJkIj48cGF0aCBkPSJNMjAgNmgtMi4xOGMuMTEtLjMxLjE4LS42NS4xOC0xIDAtMS42Ni0xLjM0LTMtMy0zLTEuMDUgMC0xLjk2LjU0LTIuNSAxLjM1bC0uNS42Ny0uNS0uNjhDMTAuOTYgMi41NCAxMC4wNSAyIDkgMiA3LjM0IDIgNiAzLjM0IDYgNWMwIC4zNS4wNy42OS4xOCAxSDRjLTEuMTEgMC0xLjk5Ljg5LTEuOTkgMkwyIDE5YzAgMS4xMS44OSAyIDIgMmgxNmMxLjExIDAgMi0uODkgMi0yVjhjMC0xLjExLS44OS0yLTItMnptLTUtMmMuNTUgMCAxIC40NSAxIDFzLS40NSAxLTEgMS0xLS40NS0xLTEgLjQ1LTEgMS0xek05IDRjLjU1IDAgMSAuNDUgMSAxcy0uNDUgMS0xIDEtMS0uNDUtMS0xIC40NS0xIDEtMXptMTEgMTVINHYtMmgxNnYyem0wLTVINFY4aDUuMDhMNyAxMC44MyA4LjYyIDEyIDExIDguNzZsMS0xLjM2IDEgMS4zNkwxNS4zOCAxMiAxNyAxMC44MyAxNC45MiA4SDIwdjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2FyZC1tZW1iZXJzaGlwIj48cGF0aCBkPSJNMjAgMkg0Yy0xLjExIDAtMiAuODktMiAydjExYzAgMS4xMS44OSAyIDIgMmg0djVsNC0yIDQgMnYtNWg0YzEuMTEgMCAyLS44OSAyLTJWNGMwLTEuMTEtLjg5LTItMi0yem0wIDEzSDR2LTJoMTZ2MnptMC01SDRWNGgxNnY2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNhcmQtdHJhdmVsIj48cGF0aCBkPSJNMjAgNmgtM1Y0YzAtMS4xMS0uODktMi0yLTJIOWMtMS4xMSAwLTIgLjg5LTIgMnYySDRjLTEuMTEgMC0yIC44OS0yIDJ2MTFjMCAxLjExLjg5IDIgMiAyaDE2YzEuMTEgMCAyLS44OSAyLTJWOGMwLTEuMTEtLjg5LTItMi0yek05IDRoNnYySDlWNHptMTEgMTVINHYtMmgxNnYyem0wLTVINFY4aDN2MmgyVjhoNnYyaDJWOGgzdjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2hhbmdlLWhpc3RvcnkiPjxwYXRoIGQ9Ik0xMiA3Ljc3TDE4LjM5IDE4SDUuNjFMMTIgNy43N00xMiA0TDIgMjBoMjBMMTIgNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJjaGVjayI+PHBhdGggZD0iTTkgMTYuMTdMNC44MyAxMmwtMS40MiAxLjQxTDkgMTkgMjEgN2wtMS40MS0xLjQxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNoZWNrLWJveCI+PHBhdGggZD0iTTE5IDNINWMtMS4xMSAwLTIgLjktMiAydjE0YzAgMS4xLjg5IDIgMiAyaDE0YzEuMTEgMCAyLS45IDItMlY1YzAtMS4xLS44OS0yLTItMnptLTkgMTRsLTUtNSAxLjQxLTEuNDFMMTAgMTQuMTdsNy41OS03LjU5TDE5IDhsLTkgOXoiPjwvcGF0aD48L2c+CjxnIGlkPSJjaGVjay1ib3gtb3V0bGluZS1ibGFuayI+PHBhdGggZD0iTTE5IDV2MTRINVY1aDE0bTAtMkg1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2hlY2stY2lyY2xlIj48cGF0aCBkPSJNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptLTIgMTVsLTUtNSAxLjQxLTEuNDFMMTAgMTQuMTdsNy41OS03LjU5TDE5IDhsLTkgOXoiPjwvcGF0aD48L2c+CjxnIGlkPSJjaGV2cm9uLWxlZnQiPjxwYXRoIGQ9Ik0xNS40MSA3LjQxTDE0IDZsLTYgNiA2IDYgMS40MS0xLjQxTDEwLjgzIDEyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNoZXZyb24tcmlnaHQiPjxwYXRoIGQ9Ik0xMCA2TDguNTkgNy40MSAxMy4xNyAxMmwtNC41OCA0LjU5TDEwIDE4bDYtNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjaHJvbWUtcmVhZGVyLW1vZGUiPjxwYXRoIGQ9Ik0xMyAxMmg3djEuNWgtN3ptMC0yLjVoN1YxMWgtN3ptMCA1aDdWMTZoLTd6TTIxIDRIM2MtMS4xIDAtMiAuOS0yIDJ2MTNjMCAxLjEuOSAyIDIgMmgxOGMxLjEgMCAyLS45IDItMlY2YzAtMS4xLS45LTItMi0yem0wIDE1aC05VjZoOXYxM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJjbGFzcyI+PHBhdGggZD0iTTE4IDJINmMtMS4xIDAtMiAuOS0yIDJ2MTZjMCAxLjEuOSAyIDIgMmgxMmMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yek02IDRoNXY4bC0yLjUtMS41TDYgMTJWNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJjbGVhciI+PHBhdGggZD0iTTE5IDYuNDFMMTcuNTkgNSAxMiAxMC41OSA2LjQxIDUgNSA2LjQxIDEwLjU5IDEyIDUgMTcuNTkgNi40MSAxOSAxMiAxMy40MSAxNy41OSAxOSAxOSAxNy41OSAxMy40MSAxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjbG9zZSI+PHBhdGggZD0iTTE5IDYuNDFMMTcuNTkgNSAxMiAxMC41OSA2LjQxIDUgNSA2LjQxIDEwLjU5IDEyIDUgMTcuNTkgNi40MSAxOSAxMiAxMy40MSAxNy41OSAxOSAxOSAxNy41OSAxMy40MSAxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjbG91ZCI+PHBhdGggZD0iTTE5LjM1IDEwLjA0QzE4LjY3IDYuNTkgMTUuNjQgNCAxMiA0IDkuMTEgNCA2LjYgNS42NCA1LjM1IDguMDQgMi4zNCA4LjM2IDAgMTAuOTEgMCAxNGMwIDMuMzEgMi42OSA2IDYgNmgxM2MyLjc2IDAgNS0yLjI0IDUtNSAwLTIuNjQtMi4wNS00Ljc4LTQuNjUtNC45NnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjbG91ZC1jaXJjbGUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem00LjUgMTRIOGMtMS42NiAwLTMtMS4zNC0zLTNzMS4zNC0zIDMtM2wuMTQuMDFDOC41OCA4LjI4IDEwLjEzIDcgMTIgN2MyLjIxIDAgNCAxLjc5IDQgNGguNWMxLjM4IDAgMi41IDEuMTIgMi41IDIuNVMxNy44OCAxNiAxNi41IDE2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNsb3VkLWRvbmUiPjxwYXRoIGQ9Ik0xOS4zNSAxMC4wNEMxOC42NyA2LjU5IDE1LjY0IDQgMTIgNCA5LjExIDQgNi42IDUuNjQgNS4zNSA4LjA0IDIuMzQgOC4zNiAwIDEwLjkxIDAgMTRjMCAzLjMxIDIuNjkgNiA2IDZoMTNjMi43NiAwIDUtMi4yNCA1LTUgMC0yLjY0LTIuMDUtNC43OC00LjY1LTQuOTZ6TTEwIDE3bC0zLjUtMy41IDEuNDEtMS40MUwxMCAxNC4xNyAxNS4xOCA5bDEuNDEgMS40MUwxMCAxN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJjbG91ZC1kb3dubG9hZCI+PHBhdGggZD0iTTE5LjM1IDEwLjA0QzE4LjY3IDYuNTkgMTUuNjQgNCAxMiA0IDkuMTEgNCA2LjYgNS42NCA1LjM1IDguMDQgMi4zNCA4LjM2IDAgMTAuOTEgMCAxNGMwIDMuMzEgMi42OSA2IDYgNmgxM2MyLjc2IDAgNS0yLjI0IDUtNSAwLTIuNjQtMi4wNS00Ljc4LTQuNjUtNC45NnpNMTcgMTNsLTUgNS01LTVoM1Y5aDR2NGgzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNsb3VkLW9mZiI+PHBhdGggZD0iTTE5LjM1IDEwLjA0QzE4LjY3IDYuNTkgMTUuNjQgNCAxMiA0Yy0xLjQ4IDAtMi44NS40My00LjAxIDEuMTdsMS40NiAxLjQ2QzEwLjIxIDYuMjMgMTEuMDggNiAxMiA2YzMuMDQgMCA1LjUgMi40NiA1LjUgNS41di41SDE5YzEuNjYgMCAzIDEuMzQgMyAzIDAgMS4xMy0uNjQgMi4xMS0xLjU2IDIuNjJsMS40NSAxLjQ1QzIzLjE2IDE4LjE2IDI0IDE2LjY4IDI0IDE1YzAtMi42NC0yLjA1LTQuNzgtNC42NS00Ljk2ek0zIDUuMjdsMi43NSAyLjc0QzIuNTYgOC4xNSAwIDEwLjc3IDAgMTRjMCAzLjMxIDIuNjkgNiA2IDZoMTEuNzNsMiAyTDIxIDIwLjczIDQuMjcgNCAzIDUuMjd6TTcuNzMgMTBsOCA4SDZjLTIuMjEgMC00LTEuNzktNC00czEuNzktNCA0LTRoMS43M3oiPjwvcGF0aD48L2c+CjxnIGlkPSJjbG91ZC1xdWV1ZSI+PHBhdGggZD0iTTE5LjM1IDEwLjA0QzE4LjY3IDYuNTkgMTUuNjQgNCAxMiA0IDkuMTEgNCA2LjYgNS42NCA1LjM1IDguMDQgMi4zNCA4LjM2IDAgMTAuOTEgMCAxNGMwIDMuMzEgMi42OSA2IDYgNmgxM2MyLjc2IDAgNS0yLjI0IDUtNSAwLTIuNjQtMi4wNS00Ljc4LTQuNjUtNC45NnpNMTkgMThINmMtMi4yMSAwLTQtMS43OS00LTRzMS43OS00IDQtNGguNzFDNy4zNyA3LjY5IDkuNDggNiAxMiA2YzMuMDQgMCA1LjUgMi40NiA1LjUgNS41di41SDE5YzEuNjYgMCAzIDEuMzQgMyAzcy0xLjM0IDMtMyAzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNsb3VkLXVwbG9hZCI+PHBhdGggZD0iTTE5LjM1IDEwLjA0QzE4LjY3IDYuNTkgMTUuNjQgNCAxMiA0IDkuMTEgNCA2LjYgNS42NCA1LjM1IDguMDQgMi4zNCA4LjM2IDAgMTAuOTEgMCAxNGMwIDMuMzEgMi42OSA2IDYgNmgxM2MyLjc2IDAgNS0yLjI0IDUtNSAwLTIuNjQtMi4wNS00Ljc4LTQuNjUtNC45NnpNMTQgMTN2NGgtNHYtNEg3bDUtNSA1IDVoLTN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY29kZSI+PHBhdGggZD0iTTkuNCAxNi42TDQuOCAxMmw0LjYtNC42TDggNmwtNiA2IDYgNiAxLjQtMS40em01LjIgMGw0LjYtNC42LTQuNi00LjZMMTYgNmw2IDYtNiA2LTEuNC0xLjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY29tcGFyZS1hcnJvd3MiPjxwYXRoIGQ9Ik05LjAxIDE0SDJ2Mmg3LjAxdjNMMTMgMTVsLTMuOTktNHYzem01Ljk4LTF2LTNIMjJWOGgtNy4wMVY1TDExIDlsMy45OSA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbnRlbnQtY29weSI+PHBhdGggZD0iTTE2IDFINGMtMS4xIDAtMiAuOS0yIDJ2MTRoMlYzaDEyVjF6bTMgNEg4Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDExYzEuMSAwIDItLjkgMi0yVjdjMC0xLjEtLjktMi0yLTJ6bTAgMTZIOFY3aDExdjE0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbnRlbnQtY3V0Ij48cGF0aCBkPSJNOS42NCA3LjY0Yy4yMy0uNS4zNi0xLjA1LjM2LTEuNjQgMC0yLjIxLTEuNzktNC00LTRTMiAzLjc5IDIgNnMxLjc5IDQgNCA0Yy41OSAwIDEuMTQtLjEzIDEuNjQtLjM2TDEwIDEybC0yLjM2IDIuMzZDNy4xNCAxNC4xMyA2LjU5IDE0IDYgMTRjLTIuMjEgMC00IDEuNzktNCA0czEuNzkgNCA0IDQgNC0xLjc5IDQtNGMwLS41OS0uMTMtMS4xNC0uMzYtMS42NEwxMiAxNGw3IDdoM3YtMUw5LjY0IDcuNjR6TTYgOGMtMS4xIDAtMi0uODktMi0ycy45LTIgMi0yIDIgLjg5IDIgMi0uOSAyLTIgMnptMCAxMmMtMS4xIDAtMi0uODktMi0ycy45LTIgMi0yIDIgLjg5IDIgMi0uOSAyLTIgMnptNi03LjVjLS4yOCAwLS41LS4yMi0uNS0uNXMuMjItLjUuNS0uNS41LjIyLjUuNS0uMjIuNS0uNS41ek0xOSAzbC02IDYgMiAyIDctN1YzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNvbnRlbnQtcGFzdGUiPjxwYXRoIGQ9Ik0xOSAyaC00LjE4QzE0LjQuODQgMTMuMyAwIDEyIDBjLTEuMyAwLTIuNC44NC0yLjgyIDJINWMtMS4xIDAtMiAuOS0yIDJ2MTZjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tNyAwYy41NSAwIDEgLjQ1IDEgMXMtLjQ1IDEtMSAxLTEtLjQ1LTEtMSAuNDUtMSAxLTF6bTcgMThINVY0aDJ2M2gxMFY0aDJ2MTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY29weXJpZ2h0Ij48cGF0aCBkPSJNMTAuMDggMTAuODZjLjA1LS4zMy4xNi0uNjIuMy0uODdzLjM0LS40Ni41OS0uNjJjLjI0LS4xNS41NC0uMjIuOTEtLjIzLjIzLjAxLjQ0LjA1LjYzLjEzLjIuMDkuMzguMjEuNTIuMzZzLjI1LjMzLjM0LjUzLjEzLjQyLjE0LjY0aDEuNzljLS4wMi0uNDctLjExLS45LS4yOC0xLjI5cy0uNC0uNzMtLjctMS4wMS0uNjYtLjUtMS4wOC0uNjYtLjg4LS4yMy0xLjM5LS4yM2MtLjY1IDAtMS4yMi4xMS0xLjcuMzRzLS44OC41My0xLjIuOTItLjU2Ljg0LS43MSAxLjM2UzggMTEuMjkgOCAxMS44N3YuMjdjMCAuNTguMDggMS4xMi4yMyAxLjY0cy4zOS45Ny43MSAxLjM1LjcyLjY5IDEuMi45MSAxLjA1LjM0IDEuNy4zNGMuNDcgMCAuOTEtLjA4IDEuMzItLjIzcy43Ny0uMzYgMS4wOC0uNjMuNTYtLjU4Ljc0LS45NC4yOS0uNzQuMy0xLjE1aC0xLjc5Yy0uMDEuMjEtLjA2LjQtLjE1LjU4cy0uMjEuMzMtLjM2LjQ2LS4zMi4yMy0uNTIuM2MtLjE5LjA3LS4zOS4wOS0uNi4xLS4zNi0uMDEtLjY2LS4wOC0uODktLjIzLS4yNS0uMTYtLjQ1LS4zNy0uNTktLjYycy0uMjUtLjU1LS4zLS44OC0uMDgtLjY3LS4wOC0xdi0uMjdjMC0uMzUuMDMtLjY4LjA4LTEuMDF6TTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTAgMThjLTQuNDEgMC04LTMuNTktOC04czMuNTktOCA4LTggOCAzLjU5IDggOC0zLjU5IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImNyZWF0ZSI+PHBhdGggZD0iTTMgMTcuMjVWMjFoMy43NUwxNy44MSA5Ljk0bC0zLjc1LTMuNzVMMyAxNy4yNXpNMjAuNzEgNy4wNGMuMzktLjM5LjM5LTEuMDIgMC0xLjQxbC0yLjM0LTIuMzRjLS4zOS0uMzktMS4wMi0uMzktMS40MSAwbC0xLjgzIDEuODMgMy43NSAzLjc1IDEuODMtMS44M3oiPjwvcGF0aD48L2c+CjxnIGlkPSJjcmVhdGUtbmV3LWZvbGRlciI+PHBhdGggZD0iTTIwIDZoLThsLTItMkg0Yy0xLjExIDAtMS45OS44OS0xLjk5IDJMMiAxOGMwIDEuMTEuODkgMiAyIDJoMTZjMS4xMSAwIDItLjg5IDItMlY4YzAtMS4xMS0uODktMi0yLTJ6bS0xIDhoLTN2M2gtMnYtM2gtM3YtMmgzVjloMnYzaDN2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJjcmVkaXQtY2FyZCI+PHBhdGggZD0iTTIwIDRINGMtMS4xMSAwLTEuOTkuODktMS45OSAyTDIgMThjMCAxLjExLjg5IDIgMiAyaDE2YzEuMTEgMCAyLS44OSAyLTJWNmMwLTEuMTEtLjg5LTItMi0yem0wIDE0SDR2LTZoMTZ2NnptMC0xMEg0VjZoMTZ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJkYXNoYm9hcmQiPjxwYXRoIGQ9Ik0zIDEzaDhWM0gzdjEwem0wIDhoOHYtNkgzdjZ6bTEwIDBoOFYxMWgtOHYxMHptMC0xOHY2aDhWM2gtOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJkYXRlLXJhbmdlIj48cGF0aCBkPSJNOSAxMUg3djJoMnYtMnptNCAwaC0ydjJoMnYtMnptNCAwaC0ydjJoMnYtMnptMi03aC0xVjJoLTJ2Mkg4VjJINnYySDVjLTEuMTEgMC0xLjk5LjktMS45OSAyTDMgMjBjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNmMwLTEuMS0uOS0yLTItMnptMCAxNkg1VjloMTR2MTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZGVsZXRlIj48cGF0aCBkPSJNNiAxOWMwIDEuMS45IDIgMiAyaDhjMS4xIDAgMi0uOSAyLTJWN0g2djEyek0xOSA0aC0zLjVsLTEtMWgtNWwtMSAxSDV2MmgxNFY0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImRlbGV0ZS1mb3JldmVyIj48cGF0aCBkPSJNNiAxOWMwIDEuMS45IDIgMiAyaDhjMS4xIDAgMi0uOSAyLTJWN0g2djEyem0yLjQ2LTcuMTJsMS40MS0xLjQxTDEyIDEyLjU5bDIuMTItMi4xMiAxLjQxIDEuNDFMMTMuNDEgMTRsMi4xMiAyLjEyLTEuNDEgMS40MUwxMiAxNS40MWwtMi4xMiAyLjEyLTEuNDEtMS40MUwxMC41OSAxNGwtMi4xMy0yLjEyek0xNS41IDRsLTEtMWgtNWwtMSAxSDV2MmgxNFY0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImRlbGV0ZS1zd2VlcCI+PHBhdGggZD0iTTE1IDE2aDR2MmgtNHptMC04aDd2MmgtN3ptMCA0aDZ2MmgtNnpNMyAxOGMwIDEuMS45IDIgMiAyaDZjMS4xIDAgMi0uOSAyLTJWOEgzdjEwek0xNCA1aC0zbC0xLTFINkw1IDVIMnYyaDEyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImRlc2NyaXB0aW9uIj48cGF0aCBkPSJNMTQgMkg2Yy0xLjEgMC0xLjk5LjktMS45OSAyTDQgMjBjMCAxLjEuODkgMiAxLjk5IDJIMThjMS4xIDAgMi0uOSAyLTJWOGwtNi02em0yIDE2SDh2LTJoOHYyem0wLTRIOHYtMmg4djJ6bS0zLTVWMy41TDE4LjUgOUgxM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJkbnMiPjxwYXRoIGQ9Ik0yMCAxM0g0Yy0uNTUgMC0xIC40NS0xIDF2NmMwIC41NS40NSAxIDEgMWgxNmMuNTUgMCAxLS40NSAxLTF2LTZjMC0uNTUtLjQ1LTEtMS0xek03IDE5Yy0xLjEgMC0yLS45LTItMnMuOS0yIDItMiAyIC45IDIgMi0uOSAyLTIgMnpNMjAgM0g0Yy0uNTUgMC0xIC40NS0xIDF2NmMwIC41NS40NSAxIDEgMWgxNmMuNTUgMCAxLS40NSAxLTFWNGMwLS41NS0uNDUtMS0xLTF6TTcgOWMtMS4xIDAtMi0uOS0yLTJzLjktMiAyLTIgMiAuOSAyIDItLjkgMi0yIDJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZG9uZSI+PHBhdGggZD0iTTkgMTYuMkw0LjggMTJsLTEuNCAxLjRMOSAxOSAyMSA3bC0xLjQtMS40TDkgMTYuMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJkb25lLWFsbCI+PHBhdGggZD0iTTE4IDdsLTEuNDEtMS40MS02LjM0IDYuMzQgMS40MSAxLjQxTDE4IDd6bTQuMjQtMS40MUwxMS42NiAxNi4xNyA3LjQ4IDEybC0xLjQxIDEuNDFMMTEuNjYgMTlsMTItMTItMS40Mi0xLjQxek0uNDEgMTMuNDFMNiAxOWwxLjQxLTEuNDFMMS44MyAxMiAuNDEgMTMuNDF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZG9udXQtbGFyZ2UiPjxwYXRoIGQ9Ik0xMSA1LjA4VjJjLTUgLjUtOSA0LjgxLTkgMTBzNCA5LjUgOSAxMHYtMy4wOGMtMy0uNDgtNi0zLjQtNi02LjkyczMtNi40NCA2LTYuOTJ6TTE4Ljk3IDExSDIyYy0uNDctNS00LTguNTMtOS05djMuMDhDMTYgNS41MSAxOC41NCA4IDE4Ljk3IDExek0xMyAxOC45MlYyMmM1LS40NyA4LjUzLTQgOS05aC0zLjAzYy0uNDMgMy0yLjk3IDUuNDktNS45NyA1LjkyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImRvbnV0LXNtYWxsIj48cGF0aCBkPSJNMTEgOS4xNlYyYy01IC41LTkgNC43OS05IDEwczQgOS41IDkgMTB2LTcuMTZjLTEtLjQxLTItMS41Mi0yLTIuODRzMS0yLjQzIDItMi44NHpNMTQuODYgMTFIMjJjLS40OC00Ljc1LTQtOC41My05LTl2Ny4xNmMxIC4zIDEuNTIuOTggMS44NiAxLjg0ek0xMyAxNC44NFYyMmM1LS40NyA4LjUyLTQuMjUgOS05aC03LjE0Yy0uMzQuODYtLjg2IDEuNTQtMS44NiAxLjg0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImRyYWZ0cyI+PHBhdGggZD0iTTIxLjk5IDhjMC0uNzItLjM3LTEuMzUtLjk0LTEuN0wxMiAxIDIuOTUgNi4zQzIuMzggNi42NSAyIDcuMjggMiA4djEwYzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJsLS4wMS0xMHpNMTIgMTNMMy43NCA3Ljg0IDEyIDNsOC4yNiA0Ljg0TDEyIDEzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImVqZWN0Ij48cGF0aCBkPSJNNSAxN2gxNHYySDV6bTctMTJMNS4zMyAxNWgxMy4zNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJlcnJvciI+PHBhdGggZD0iTTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTEgMTVoLTJ2LTJoMnYyem0wLTRoLTJWN2gydjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXJyb3Itb3V0bGluZSI+PHBhdGggZD0iTTExIDE1aDJ2MmgtMnptMC04aDJ2NmgtMnptLjk5LTVDNi40NyAyIDIgNi40OCAyIDEyczQuNDcgMTAgOS45OSAxMEMxNy41MiAyMiAyMiAxNy41MiAyMiAxMlMxNy41MiAyIDExLjk5IDJ6TTEyIDIwYy00LjQyIDAtOC0zLjU4LTgtOHMzLjU4LTggOC04IDggMy41OCA4IDgtMy41OCA4LTggOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJldXJvLXN5bWJvbCI+PHBhdGggZD0iTTE1IDE4LjVjLTIuNTEgMC00LjY4LTEuNDItNS43Ni0zLjVIMTV2LTJIOC41OGMtLjA1LS4zMy0uMDgtLjY2LS4wOC0xcy4wMy0uNjcuMDgtMUgxNVY5SDkuMjRDMTAuMzIgNi45MiAxMi41IDUuNSAxNSA1LjVjMS42MSAwIDMuMDkuNTkgNC4yMyAxLjU3TDIxIDUuM0MxOS40MSAzLjg3IDE3LjMgMyAxNSAzYy0zLjkyIDAtNy4yNCAyLjUxLTguNDggNkgzdjJoMy4wNmMtLjA0LjMzLS4wNi42Ni0uMDYgMSAwIC4zNC4wMi42Ny4wNiAxSDN2MmgzLjUyYzEuMjQgMy40OSA0LjU2IDYgOC40OCA2IDIuMzEgMCA0LjQxLS44NyA2LTIuM2wtMS43OC0xLjc3Yy0xLjEzLjk4LTIuNiAxLjU3LTQuMjIgMS41N3oiPjwvcGF0aD48L2c+CjxnIGlkPSJldmVudCI+PHBhdGggZD0iTTE3IDEyaC01djVoNXYtNXpNMTYgMXYySDhWMUg2djJINWMtMS4xMSAwLTEuOTkuOS0xLjk5IDJMMyAxOWMwIDEuMS44OSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yaC0xVjFoLTJ6bTMgMThINVY4aDE0djExeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImV2ZW50LXNlYXQiPjxwYXRoIGQ9Ik00IDE4djNoM3YtM2gxMHYzaDN2LTZINHptMTUtOGgzdjNoLTN6TTIgMTBoM3YzSDJ6bTE1IDNIN1Y1YzAtMS4xLjktMiAyLTJoNmMxLjEgMCAyIC45IDIgMnY4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImV4aXQtdG8tYXBwIj48cGF0aCBkPSJNMTAuMDkgMTUuNTlMMTEuNSAxN2w1LTUtNS01LTEuNDEgMS40MUwxMi42NyAxMUgzdjJoOS42N2wtMi41OCAyLjU5ek0xOSAzSDVjLTEuMTEgMC0yIC45LTIgMnY0aDJWNWgxNHYxNEg1di00SDN2NGMwIDEuMS44OSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImV4cGFuZC1sZXNzIj48cGF0aCBkPSJNMTIgOGwtNiA2IDEuNDEgMS40MUwxMiAxMC44M2w0LjU5IDQuNThMMTggMTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwYW5kLW1vcmUiPjxwYXRoIGQ9Ik0xNi41OSA4LjU5TDEyIDEzLjE3IDcuNDEgOC41OSA2IDEwbDYgNiA2LTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXhwbG9yZSI+PHBhdGggZD0iTTEyIDEwLjljLS42MSAwLTEuMS40OS0xLjEgMS4xcy40OSAxLjEgMS4xIDEuMWMuNjEgMCAxLjEtLjQ5IDEuMS0xLjFzLS40OS0xLjEtMS4xLTEuMXpNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMi4xOSAxMi4xOUw2IDE4bDMuODEtOC4xOUwxOCA2bC0zLjgxIDguMTl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZXh0ZW5zaW9uIj48cGF0aCBkPSJNMjAuNSAxMUgxOVY3YzAtMS4xLS45LTItMi0yaC00VjMuNUMxMyAyLjEyIDExLjg4IDEgMTAuNSAxUzggMi4xMiA4IDMuNVY1SDRjLTEuMSAwLTEuOTkuOS0xLjk5IDJ2My44SDMuNWMxLjQ5IDAgMi43IDEuMjEgMi43IDIuN3MtMS4yMSAyLjctMi43IDIuN0gyVjIwYzAgMS4xLjkgMiAyIDJoMy44di0xLjVjMC0xLjQ5IDEuMjEtMi43IDIuNy0yLjcgMS40OSAwIDIuNyAxLjIxIDIuNyAyLjdWMjJIMTdjMS4xIDAgMi0uOSAyLTJ2LTRoMS41YzEuMzggMCAyLjUtMS4xMiAyLjUtMi41UzIxLjg4IDExIDIwLjUgMTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmFjZSI+PHBhdGggZD0iTTkgMTEuNzVjLS42OSAwLTEuMjUuNTYtMS4yNSAxLjI1cy41NiAxLjI1IDEuMjUgMS4yNSAxLjI1LS41NiAxLjI1LTEuMjUtLjU2LTEuMjUtMS4yNS0xLjI1em02IDBjLS42OSAwLTEuMjUuNTYtMS4yNSAxLjI1cy41NiAxLjI1IDEuMjUgMS4yNSAxLjI1LS41NiAxLjI1LTEuMjUtLjU2LTEuMjUtMS4yNS0xLjI1ek0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOCAwLS4yOS4wMi0uNTguMDUtLjg2IDIuMzYtMS4wNSA0LjIzLTIuOTggNS4yMS01LjM3QzExLjA3IDguMzMgMTQuMDUgMTAgMTcuNDIgMTBjLjc4IDAgMS41My0uMDkgMi4yNS0uMjYuMjEuNzEuMzMgMS40Ny4zMyAyLjI2IDAgNC40MS0zLjU5IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZhdm9yaXRlIj48cGF0aCBkPSJNMTIgMjEuMzVsLTEuNDUtMS4zMkM1LjQgMTUuMzYgMiAxMi4yOCAyIDguNSAyIDUuNDIgNC40MiAzIDcuNSAzYzEuNzQgMCAzLjQxLjgxIDQuNSAyLjA5QzEzLjA5IDMuODEgMTQuNzYgMyAxNi41IDMgMTkuNTggMyAyMiA1LjQyIDIyIDguNWMwIDMuNzgtMy40IDYuODYtOC41NSAxMS41NEwxMiAyMS4zNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJmYXZvcml0ZS1ib3JkZXIiPjxwYXRoIGQ9Ik0xNi41IDNjLTEuNzQgMC0zLjQxLjgxLTQuNSAyLjA5QzEwLjkxIDMuODEgOS4yNCAzIDcuNSAzIDQuNDIgMyAyIDUuNDIgMiA4LjVjMCAzLjc4IDMuNCA2Ljg2IDguNTUgMTEuNTRMMTIgMjEuMzVsMS40NS0xLjMyQzE4LjYgMTUuMzYgMjIgMTIuMjggMjIgOC41IDIyIDUuNDIgMTkuNTggMyAxNi41IDN6bS00LjQgMTUuNTVsLS4xLjEtLjEtLjFDNy4xNCAxNC4yNCA0IDExLjM5IDQgOC41IDQgNi41IDUuNSA1IDcuNSA1YzEuNTQgMCAzLjA0Ljk5IDMuNTcgMi4zNmgxLjg3QzEzLjQ2IDUuOTkgMTQuOTYgNSAxNi41IDVjMiAwIDMuNSAxLjUgMy41IDMuNSAwIDIuODktMy4xNCA1Ljc0LTcuOSAxMC4wNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJmZWVkYmFjayI+PHBhdGggZD0iTTIwIDJINGMtMS4xIDAtMS45OS45LTEuOTkgMkwyIDIybDQtNGgxNGMxLjEgMCAyLS45IDItMlY0YzAtMS4xLS45LTItMi0yem0tNyAxMmgtMnYtMmgydjJ6bTAtNGgtMlY2aDJ2NHoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaWxlLWRvd25sb2FkIj48cGF0aCBkPSJNMTkgOWgtNFYzSDl2Nkg1bDcgNyA3LTd6TTUgMTh2MmgxNHYtMkg1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZpbGUtdXBsb2FkIj48cGF0aCBkPSJNOSAxNmg2di02aDRsLTctNy03IDdoNHptLTQgMmgxNHYySDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlsdGVyLWxpc3QiPjxwYXRoIGQ9Ik0xMCAxOGg0di0yaC00djJ6TTMgNnYyaDE4VjZIM3ptMyA3aDEydi0ySDZ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaW5kLWluLXBhZ2UiPjxwYXRoIGQ9Ik0yMCAxOS41OVY4bC02LTZINmMtMS4xIDAtMS45OS45LTEuOTkgMkw0IDIwYzAgMS4xLjg5IDIgMS45OSAySDE4Yy40NSAwIC44NS0uMTUgMS4xOS0uNGwtNC40My00LjQzYy0uOC41Mi0xLjc0LjgzLTIuNzYuODMtMi43NiAwLTUtMi4yNC01LTVzMi4yNC01IDUtNSA1IDIuMjQgNSA1YzAgMS4wMi0uMzEgMS45Ni0uODMgMi43NUwyMCAxOS41OXpNOSAxM2MwIDEuNjYgMS4zNCAzIDMgM3MzLTEuMzQgMy0zLTEuMzQtMy0zLTMtMyAxLjM0LTMgM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJmaW5kLXJlcGxhY2UiPjxwYXRoIGQ9Ik0xMSA2YzEuMzggMCAyLjYzLjU2IDMuNTQgMS40NkwxMiAxMGg2VjRsLTIuMDUgMi4wNUMxNC42OCA0Ljc4IDEyLjkzIDQgMTEgNGMtMy41MyAwLTYuNDMgMi42MS02LjkyIDZINi4xYy40Ni0yLjI4IDIuNDgtNCA0LjktNHptNS42NCA5LjE0Yy42Ni0uOSAxLjEyLTEuOTcgMS4yOC0zLjE0SDE1LjljLS40NiAyLjI4LTIuNDggNC00LjkgNC0xLjM4IDAtMi42My0uNTYtMy41NC0xLjQ2TDEwIDEySDR2NmwyLjA1LTIuMDVDNy4zMiAxNy4yMiA5LjA3IDE4IDExIDE4YzEuNTUgMCAyLjk4LS41MSA0LjE0LTEuMzZMMjAgMjEuNDkgMjEuNDkgMjBsLTQuODUtNC44NnoiPjwvcGF0aD48L2c+CjxnIGlkPSJmaW5nZXJwcmludCI+PHBhdGggZD0iTTE3LjgxIDQuNDdjLS4wOCAwLS4xNi0uMDItLjIzLS4wNkMxNS42NiAzLjQyIDE0IDMgMTIuMDEgM2MtMS45OCAwLTMuODYuNDctNS41NyAxLjQxLS4yNC4xMy0uNTQuMDQtLjY4LS4yLS4xMy0uMjQtLjA0LS41NS4yLS42OEM3LjgyIDIuNTIgOS44NiAyIDEyLjAxIDJjMi4xMyAwIDMuOTkuNDcgNi4wMyAxLjUyLjI1LjEzLjM0LjQzLjIxLjY3LS4wOS4xOC0uMjYuMjgtLjQ0LjI4ek0zLjUgOS43MmMtLjEgMC0uMi0uMDMtLjI5LS4wOS0uMjMtLjE2LS4yOC0uNDctLjEyLS43Ljk5LTEuNCAyLjI1LTIuNSAzLjc1LTMuMjdDOS45OCA0LjA0IDE0IDQuMDMgMTcuMTUgNS42NWMxLjUuNzcgMi43NiAxLjg2IDMuNzUgMy4yNS4xNi4yMi4xMS41NC0uMTIuNy0uMjMuMTYtLjU0LjExLS43LS4xMi0uOS0xLjI2LTIuMDQtMi4yNS0zLjM5LTIuOTQtMi44Ny0xLjQ3LTYuNTQtMS40Ny05LjQuMDEtMS4zNi43LTIuNSAxLjctMy40IDIuOTYtLjA4LjE0LS4yMy4yMS0uMzkuMjF6bTYuMjUgMTIuMDdjLS4xMyAwLS4yNi0uMDUtLjM1LS4xNS0uODctLjg3LTEuMzQtMS40My0yLjAxLTIuNjQtLjY5LTEuMjMtMS4wNS0yLjczLTEuMDUtNC4zNCAwLTIuOTcgMi41NC01LjM5IDUuNjYtNS4zOXM1LjY2IDIuNDIgNS42NiA1LjM5YzAgLjI4LS4yMi41LS41LjVzLS41LS4yMi0uNS0uNWMwLTIuNDItMi4wOS00LjM5LTQuNjYtNC4zOS0yLjU3IDAtNC42NiAxLjk3LTQuNjYgNC4zOSAwIDEuNDQuMzIgMi43Ny45MyAzLjg1LjY0IDEuMTUgMS4wOCAxLjY0IDEuODUgMi40Mi4xOS4yLjE5LjUxIDAgLjcxLS4xMS4xLS4yNC4xNS0uMzcuMTV6bTcuMTctMS44NWMtMS4xOSAwLTIuMjQtLjMtMy4xLS44OS0xLjQ5LTEuMDEtMi4zOC0yLjY1LTIuMzgtNC4zOSAwLS4yOC4yMi0uNS41LS41cy41LjIyLjUuNWMwIDEuNDEuNzIgMi43NCAxLjk0IDMuNTYuNzEuNDggMS41NC43MSAyLjU0LjcxLjI0IDAgLjY0LS4wMyAxLjA0LS4xLjI3LS4wNS41My4xMy41OC40MS4wNS4yNy0uMTMuNTMtLjQxLjU4LS41Ny4xMS0xLjA3LjEyLTEuMjEuMTJ6TTE0LjkxIDIyYy0uMDQgMC0uMDktLjAxLS4xMy0uMDItMS41OS0uNDQtMi42My0xLjAzLTMuNzItMi4xLTEuNC0xLjM5LTIuMTctMy4yNC0yLjE3LTUuMjIgMC0xLjYyIDEuMzgtMi45NCAzLjA4LTIuOTQgMS43IDAgMy4wOCAxLjMyIDMuMDggMi45NCAwIDEuMDcuOTMgMS45NCAyLjA4IDEuOTRzMi4wOC0uODcgMi4wOC0xLjk0YzAtMy43Ny0zLjI1LTYuODMtNy4yNS02LjgzLTIuODQgMC01LjQ0IDEuNTgtNi42MSA0LjAzLS4zOS44MS0uNTkgMS43Ni0uNTkgMi44IDAgLjc4LjA3IDIuMDEuNjcgMy42MS4xLjI2LS4wMy41NS0uMjkuNjQtLjI2LjEtLjU1LS4wNC0uNjQtLjI5LS40OS0xLjMxLS43My0yLjYxLS43My0zLjk2IDAtMS4yLjIzLTIuMjkuNjgtMy4yNCAxLjMzLTIuNzkgNC4yOC00LjYgNy41MS00LjYgNC41NSAwIDguMjUgMy41MSA4LjI1IDcuODMgMCAxLjYyLTEuMzggMi45NC0zLjA4IDIuOTRzLTMuMDgtMS4zMi0zLjA4LTIuOTRjMC0xLjA3LS45My0xLjk0LTIuMDgtMS45NHMtMi4wOC44Ny0yLjA4IDEuOTRjMCAxLjcxLjY2IDMuMzEgMS44NyA0LjUxLjk1Ljk0IDEuODYgMS40NiAzLjI3IDEuODUuMjcuMDcuNDIuMzUuMzUuNjEtLjA1LjIzLS4yNi4zOC0uNDcuMzh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZmlyc3QtcGFnZSI+PHBhdGggZD0iTTE4LjQxIDE2LjU5TDEzLjgyIDEybDQuNTktNC41OUwxNyA2bC02IDYgNiA2ek02IDZoMnYxMkg2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsYWciPjxwYXRoIGQ9Ik0xNC40IDZMMTQgNEg1djE3aDJ2LTdoNS42bC40IDJoN1Y2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsaWdodC1sYW5kIj48cGF0aCBkPSJNMi41IDE5aDE5djJoLTE5em03LjE4LTUuNzNsNC4zNSAxLjE2IDUuMzEgMS40MmMuOC4yMSAxLjYyLS4yNiAxLjg0LTEuMDYuMjEtLjgtLjI2LTEuNjItMS4wNi0xLjg0bC01LjMxLTEuNDItMi43Ni05LjAyTDEwLjEyIDJ2OC4yOEw1LjE1IDguOTVsLS45My0yLjMyLTEuNDUtLjM5djUuMTdsMS42LjQzIDUuMzEgMS40M3oiPjwvcGF0aD48L2c+CjxnIGlkPSJmbGlnaHQtdGFrZW9mZiI+PHBhdGggZD0iTTIuNSAxOWgxOXYyaC0xOXptMTkuNTctOS4zNmMtLjIxLS44LTEuMDQtMS4yOC0xLjg0LTEuMDZMMTQuOTIgMTBsLTYuOS02LjQzLTEuOTMuNTEgNC4xNCA3LjE3LTQuOTcgMS4zMy0xLjk3LTEuNTQtMS40NS4zOSAxLjgyIDMuMTYuNzcgMS4zMyAxLjYtLjQzIDUuMzEtMS40MiA0LjM1LTEuMTZMMjEgMTEuNDljLjgxLS4yMyAxLjI4LTEuMDUgMS4wNy0xLjg1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsaXAtdG8tYmFjayI+PHBhdGggZD0iTTkgN0g3djJoMlY3em0wIDRIN3YyaDJ2LTJ6bTAtOGMtMS4xMSAwLTIgLjktMiAyaDJWM3ptNCAxMmgtMnYyaDJ2LTJ6bTYtMTJ2MmgyYzAtMS4xLS45LTItMi0yem0tNiAwaC0ydjJoMlYzek05IDE3di0ySDdjMCAxLjEuODkgMiAyIDJ6bTEwLTRoMnYtMmgtMnYyem0wLTRoMlY3aC0ydjJ6bTAgOGMxLjEgMCAyLS45IDItMmgtMnYyek01IDdIM3YxMmMwIDEuMS44OSAyIDIgMmgxMnYtMkg1Vjd6bTEwLTJoMlYzaC0ydjJ6bTAgMTJoMnYtMmgtMnYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZsaXAtdG8tZnJvbnQiPjxwYXRoIGQ9Ik0zIDEzaDJ2LTJIM3Yyem0wIDRoMnYtMkgzdjJ6bTIgNHYtMkgzYzAgMS4xLjg5IDIgMiAyek0zIDloMlY3SDN2MnptMTIgMTJoMnYtMmgtMnYyem00LTE4SDljLTEuMTEgMC0yIC45LTIgMnYxMGMwIDEuMS44OSAyIDIgMmgxMGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDEySDlWNWgxMHYxMHptLTggNmgydi0yaC0ydjJ6bS00IDBoMnYtMkg3djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZm9sZGVyIj48cGF0aCBkPSJNMTAgNEg0Yy0xLjEgMC0xLjk5LjktMS45OSAyTDIgMThjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY4YzAtMS4xLS45LTItMi0yaC04bC0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZm9sZGVyLW9wZW4iPjxwYXRoIGQ9Ik0yMCA2aC04bC0yLTJINGMtMS4xIDAtMS45OS45LTEuOTkgMkwyIDE4YzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJWOGMwLTEuMS0uOS0yLTItMnptMCAxMkg0VjhoMTZ2MTB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZm9sZGVyLXNoYXJlZCI+PHBhdGggZD0iTTIwIDZoLThsLTItMkg0Yy0xLjEgMC0xLjk5LjktMS45OSAyTDIgMThjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY4YzAtMS4xLS45LTItMi0yem0tNSAzYzEuMSAwIDIgLjkgMiAycy0uOSAyLTIgMi0yLS45LTItMiAuOS0yIDItMnptNCA4aC04di0xYzAtMS4zMyAyLjY3LTIgNC0yczQgLjY3IDQgMnYxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZvbnQtZG93bmxvYWQiPjxwYXRoIGQ9Ik05LjkzIDEzLjVoNC4xNEwxMiA3Ljk4ek0yMCAySDRjLTEuMSAwLTIgLjktMiAydjE2YzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJWNGMwLTEuMS0uOS0yLTItMnptLTQuMDUgMTYuNWwtMS4xNC0zSDkuMTdsLTEuMTIgM0g1Ljk2bDUuMTEtMTNoMS44Nmw1LjExIDEzaC0yLjA5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImZvcndhcmQiPjxwYXRoIGQ9Ik0xMiA4VjRsOCA4LTggOHYtNEg0Vjh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZnVsbHNjcmVlbiI+PHBhdGggZD0iTTcgMTRINXY1aDV2LTJIN3YtM3ptLTItNGgyVjdoM1Y1SDV2NXptMTIgN2gtM3YyaDV2LTVoLTJ2M3pNMTQgNXYyaDN2M2gyVjVoLTV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZnVsbHNjcmVlbi1leGl0Ij48cGF0aCBkPSJNNSAxNmgzdjNoMnYtNUg1djJ6bTMtOEg1djJoNVY1SDh2M3ptNiAxMWgydi0zaDN2LTJoLTV2NXptMi0xMVY1aC0ydjVoNVY4aC0zeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImctdHJhbnNsYXRlIj48cGF0aCBkPSJNMjAgNWgtOS4xMkwxMCAySDRjLTEuMSAwLTIgLjktMiAydjEzYzAgMS4xLjkgMiAyIDJoN2wxIDNoOGMxLjEgMCAyLS45IDItMlY3YzAtMS4xLS45LTItMi0yek03LjE3IDE0LjU5Yy0yLjI1IDAtNC4wOS0xLjgzLTQuMDktNC4wOXMxLjgzLTQuMDkgNC4wOS00LjA5YzEuMDQgMCAxLjk5LjM3IDIuNzQgMS4wN2wuMDcuMDYtMS4yMyAxLjE4LS4wNi0uMDVjLS4yOS0uMjctLjc4LS41OS0xLjUyLS41OS0xLjMxIDAtMi4zOCAxLjA5LTIuMzggMi40MnMxLjA3IDIuNDIgMi4zOCAyLjQyYzEuMzcgMCAxLjk2LS44NyAyLjEyLTEuNDZINy4wOFY5LjkxaDMuOTVsLjAxLjA3Yy4wNC4yMS4wNS40LjA1LjYxIDAgMi4zNS0xLjYxIDQtMy45MiA0em02LjAzLTEuNzFjLjMzLjYuNzQgMS4xOCAxLjE5IDEuN2wtLjU0LjUzLS42NS0yLjIzem0uNzctLjc2aC0uOTlsLS4zMS0xLjA0aDMuOTlzLS4zNCAxLjMxLTEuNTYgMi43NGMtLjUyLS42Mi0uODktMS4yMy0xLjEzLTEuN3pNMjEgMjBjMCAuNTUtLjQ1IDEtMSAxaC03bDItMi0uODEtMi43Ny45Mi0uOTJMMTcuNzkgMThsLjczLS43My0yLjcxLTIuNjhjLjktMS4wMyAxLjYtMi4yNSAxLjkyLTMuNTFIMTl2LTEuMDRoLTMuNjRWOWgtMS4wNHYxLjA0aC0xLjk2TDExLjE4IDZIMjBjLjU1IDAgMSAuNDUgMSAxdjEzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImdhdmVsIj48cGF0aCBkPSJNMSAyMWgxMnYySDF6TTUuMjQ1IDguMDdsMi44My0yLjgyNyAxNC4xNCAxNC4xNDItMi44MjggMi44Mjh6TTEyLjMxNyAxbDUuNjU3IDUuNjU2LTIuODMgMi44My01LjY1NC01LjY2ek0zLjgyNSA5LjQ4NWw1LjY1NyA1LjY1Ny0yLjgyOCAyLjgyOC01LjY1Ny01LjY1N3oiPjwvcGF0aD48L2c+CjxnIGlkPSJnZXN0dXJlIj48cGF0aCBkPSJNNC41OSA2Ljg5Yy43LS43MSAxLjQtMS4zNSAxLjcxLTEuMjIuNS4yIDAgMS4wMy0uMyAxLjUyLS4yNS40Mi0yLjg2IDMuODktMi44NiA2LjMxIDAgMS4yOC40OCAyLjM0IDEuMzQgMi45OC43NS41NiAxLjc0LjczIDIuNjQuNDYgMS4wNy0uMzEgMS45NS0xLjQgMy4wNi0yLjc3IDEuMjEtMS40OSAyLjgzLTMuNDQgNC4wOC0zLjQ0IDEuNjMgMCAxLjY1IDEuMDEgMS43NiAxLjc5LTMuNzguNjQtNS4zOCAzLjY3LTUuMzggNS4zNyAwIDEuNyAxLjQ0IDMuMDkgMy4yMSAzLjA5IDEuNjMgMCA0LjI5LTEuMzMgNC42OS02LjFIMjF2LTIuNWgtMi40N2MtLjE1LTEuNjUtMS4wOS00LjItNC4wMy00LjItMi4yNSAwLTQuMTggMS45MS00Ljk0IDIuODQtLjU4LjczLTIuMDYgMi40OC0yLjI5IDIuNzItLjI1LjMtLjY4Ljg0LTEuMTEuODQtLjQ1IDAtLjcyLS44My0uMzYtMS45Mi4zNS0xLjA5IDEuNC0yLjg2IDEuODUtMy41Mi43OC0xLjE0IDEuMy0xLjkyIDEuMy0zLjI4QzguOTUgMy42OSA3LjMxIDMgNi40NCAzIDUuMTIgMyAzLjk3IDQgMy43MiA0LjI1Yy0uMzYuMzYtLjY2LjY2LS44OC45M2wxLjc1IDEuNzF6bTkuMjkgMTEuNjZjLS4zMSAwLS43NC0uMjYtLjc0LS43MiAwLS42LjczLTIuMiAyLjg3LTIuNzYtLjMgMi42OS0xLjQzIDMuNDgtMi4xMyAzLjQ4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImdldC1hcHAiPjxwYXRoIGQ9Ik0xOSA5aC00VjNIOXY2SDVsNyA3IDctN3pNNSAxOHYyaDE0di0ySDV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iZ2lmIj48cGF0aCBkPSJNMTEuNSA5SDEzdjZoLTEuNXpNOSA5SDZjLS42IDAtMSAuNS0xIDF2NGMwIC41LjQgMSAxIDFoM2MuNiAwIDEtLjUgMS0xdi0ySDguNXYxLjVoLTJ2LTNIMTBWMTBjMC0uNS0uNC0xLTEtMXptMTAgMS41VjloLTQuNXY2SDE2di0yaDJ2LTEuNWgtMnYtMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJncmFkZSI+PHBhdGggZD0iTTEyIDE3LjI3TDE4LjE4IDIxbC0xLjY0LTcuMDNMMjIgOS4yNGwtNy4xOS0uNjFMMTIgMiA5LjE5IDguNjMgMiA5LjI0bDUuNDYgNC43M0w1LjgyIDIxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imdyb3VwLXdvcmsiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyek04IDE3LjVjLTEuMzggMC0yLjUtMS4xMi0yLjUtMi41czEuMTItMi41IDIuNS0yLjUgMi41IDEuMTIgMi41IDIuNS0xLjEyIDIuNS0yLjUgMi41ek05LjUgOGMwLTEuMzggMS4xMi0yLjUgMi41LTIuNXMyLjUgMS4xMiAyLjUgMi41LTEuMTIgMi41LTIuNSAyLjVTOS41IDkuMzggOS41IDh6bTYuNSA5LjVjLTEuMzggMC0yLjUtMS4xMi0yLjUtMi41czEuMTItMi41IDIuNS0yLjUgMi41IDEuMTIgMi41IDIuNS0xLjEyIDIuNS0yLjUgMi41eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImhlbHAiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0xIDE3aC0ydi0yaDJ2MnptMi4wNy03Ljc1bC0uOS45MkMxMy40NSAxMi45IDEzIDEzLjUgMTMgMTVoLTJ2LS41YzAtMS4xLjQ1LTIuMSAxLjE3LTIuODNsMS4yNC0xLjI2Yy4zNy0uMzYuNTktLjg2LjU5LTEuNDEgMC0xLjEtLjktMi0yLTJzLTIgLjktMiAySDhjMC0yLjIxIDEuNzktNCA0LTRzNCAxLjc5IDQgNGMwIC44OC0uMzYgMS42OC0uOTMgMi4yNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJoZWxwLW91dGxpbmUiPjxwYXRoIGQ9Ik0xMSAxOGgydi0yaC0ydjJ6bTEtMTZDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTAgMThjLTQuNDEgMC04LTMuNTktOC04czMuNTktOCA4LTggOCAzLjU5IDggOC0zLjU5IDgtOCA4em0wLTE0Yy0yLjIxIDAtNCAxLjc5LTQgNGgyYzAtMS4xLjktMiAyLTJzMiAuOSAyIDJjMCAyLTMgMS43NS0zIDVoMmMwLTIuMjUgMy0yLjUgMy01IDAtMi4yMS0xLjc5LTQtNC00eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImhpZ2hsaWdodC1vZmYiPjxwYXRoIGQ9Ik0xNC41OSA4TDEyIDEwLjU5IDkuNDEgOCA4IDkuNDEgMTAuNTkgMTIgOCAxNC41OSA5LjQxIDE2IDEyIDEzLjQxIDE0LjU5IDE2IDE2IDE0LjU5IDEzLjQxIDEyIDE2IDkuNDEgMTQuNTkgOHpNMTIgMkM2LjQ3IDIgMiA2LjQ3IDIgMTJzNC40NyAxMCAxMCAxMCAxMC00LjQ3IDEwLTEwUzE3LjUzIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iaGlzdG9yeSI+PHBhdGggZD0iTTEzIDNjLTQuOTcgMC05IDQuMDMtOSA5SDFsMy44OSAzLjg5LjA3LjE0TDkgMTJINmMwLTMuODcgMy4xMy03IDctN3M3IDMuMTMgNyA3LTMuMTMgNy03IDdjLTEuOTMgMC0zLjY4LS43OS00Ljk0LTIuMDZsLTEuNDIgMS40MkM4LjI3IDE5Ljk5IDEwLjUxIDIxIDEzIDIxYzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05em0tMSA1djVsNC4yOCAyLjU0LjcyLTEuMjEtMy41LTIuMDhWOEgxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJob21lIj48cGF0aCBkPSJNMTAgMjB2LTZoNHY2aDV2LThoM0wxMiAzIDIgMTJoM3Y4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImhvdXJnbGFzcy1lbXB0eSI+PHBhdGggZD0iTTYgMnY2aC4wMUw2IDguMDEgMTAgMTJsLTQgNCAuMDEuMDFINlYyMmgxMnYtNS45OWgtLjAxTDE4IDE2bC00LTQgNC0zLjk5LS4wMS0uMDFIMThWMkg2em0xMCAxNC41VjIwSDh2LTMuNWw0LTQgNCA0em0tNC01bC00LTRWNGg4djMuNWwtNCA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImhvdXJnbGFzcy1mdWxsIj48cGF0aCBkPSJNNiAydjZoLjAxTDYgOC4wMSAxMCAxMmwtNCA0IC4wMS4wMUg2VjIyaDEydi01Ljk5aC0uMDFMMTggMTZsLTQtNCA0LTMuOTktLjAxLS4wMUgxOFYySDZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iaHR0cCI+PHBhdGggZD0iTTQuNSAxMWgtMlY5SDF2NmgxLjV2LTIuNWgyVjE1SDZWOUg0LjV2MnptMi41LS41aDEuNVYxNUgxMHYtNC41aDEuNVY5SDd2MS41em01LjUgMEgxNFYxNWgxLjV2LTQuNUgxN1Y5aC00LjV2MS41em05LTEuNUgxOHY2aDEuNXYtMmgyYy44IDAgMS41LS43IDEuNS0xLjV2LTFjMC0uOC0uNy0xLjUtMS41LTEuNXptMCAyLjVoLTJ2LTFoMnYxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imh0dHBzIj48cGF0aCBkPSJNMTggOGgtMVY2YzAtMi43Ni0yLjI0LTUtNS01UzcgMy4yNCA3IDZ2Mkg2Yy0xLjEgMC0yIC45LTIgMnYxMGMwIDEuMS45IDIgMiAyaDEyYzEuMSAwIDItLjkgMi0yVjEwYzAtMS4xLS45LTItMi0yem0tNiA5Yy0xLjEgMC0yLS45LTItMnMuOS0yIDItMiAyIC45IDIgMi0uOSAyLTIgMnptMy4xLTlIOC45VjZjMC0xLjcxIDEuMzktMy4xIDMuMS0zLjEgMS43MSAwIDMuMSAxLjM5IDMuMSAzLjF2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJpbXBvcnRhbnQtZGV2aWNlcyI+PHBhdGggZD0iTTIzIDExLjAxTDE4IDExYy0uNTUgMC0xIC40NS0xIDF2OWMwIC41NS40NSAxIDEgMWg1Yy41NSAwIDEtLjQ1IDEtMXYtOWMwLS41NS0uNDUtLjk5LTEtLjk5ek0yMyAyMGgtNXYtN2g1djd6TTIwIDJIMkMuODkgMiAwIDIuODkgMCA0djEyYzAgMS4xLjg5IDIgMiAyaDd2Mkg3djJoOHYtMmgtMnYtMmgydi0ySDJWNGgxOHY1aDJWNGMwLTEuMTEtLjktMi0yLTJ6bS04LjAzIDdMMTEgNmwtLjk3IDNIN2wyLjQ3IDEuNzYtLjk0IDIuOTEgMi40Ny0xLjggMi40NyAxLjgtLjk0LTIuOTFMMTUgOWgtMy4wM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJpbmJveCI+PHBhdGggZD0iTTE5IDNINC45OWMtMS4xMSAwLTEuOTguODktMS45OCAyTDMgMTljMCAxLjEuODggMiAxLjk5IDJIMTljMS4xIDAgMi0uOSAyLTJWNWMwLTEuMTEtLjktMi0yLTJ6bTAgMTJoLTRjMCAxLjY2LTEuMzUgMy0zIDNzLTMtMS4zNC0zLTNINC45OVY1SDE5djEweiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImluZGV0ZXJtaW5hdGUtY2hlY2stYm94Ij48cGF0aCBkPSJNMTkgM0g1Yy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0yVjVjMC0xLjEtLjktMi0yLTJ6bS0yIDEwSDd2LTJoMTB2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJpbmZvIj48cGF0aCBkPSJNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMSAxNWgtMnYtNmgydjZ6bTAtOGgtMlY3aDJ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJpbmZvLW91dGxpbmUiPjxwYXRoIGQ9Ik0xMSAxN2gydi02aC0ydjZ6bTEtMTVDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTAgMThjLTQuNDEgMC04LTMuNTktOC04czMuNTktOCA4LTggOCAzLjU5IDggOC0zLjU5IDgtOCA4ek0xMSA5aDJWN2gtMnYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImlucHV0Ij48cGF0aCBkPSJNMjEgMy4wMUgzYy0xLjEgMC0yIC45LTIgMlY5aDJWNC45OWgxOHYxNC4wM0gzVjE1SDF2NC4wMWMwIDEuMS45IDEuOTggMiAxLjk4aDE4YzEuMSAwIDItLjg4IDItMS45OHYtMTRjMC0xLjExLS45LTItMi0yek0xMSAxNmw0LTQtNC00djNIMXYyaDEwdjN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iaW52ZXJ0LWNvbG9ycyI+PHBhdGggZD0iTTE3LjY2IDcuOTNMMTIgMi4yNyA2LjM0IDcuOTNjLTMuMTIgMy4xMi0zLjEyIDguMTkgMCAxMS4zMUM3LjkgMjAuOCA5Ljk1IDIxLjU4IDEyIDIxLjU4YzIuMDUgMCA0LjEtLjc4IDUuNjYtMi4zNCAzLjEyLTMuMTIgMy4xMi04LjE5IDAtMTEuMzF6TTEyIDE5LjU5Yy0xLjYgMC0zLjExLS42Mi00LjI0LTEuNzZDNi42MiAxNi42OSA2IDE1LjE5IDYgMTMuNTlzLjYyLTMuMTEgMS43Ni00LjI0TDEyIDUuMXYxNC40OXoiPjwvcGF0aD48L2c+CjxnIGlkPSJsYWJlbCI+PHBhdGggZD0iTTE3LjYzIDUuODRDMTcuMjcgNS4zMyAxNi42NyA1IDE2IDVMNSA1LjAxQzMuOSA1LjAxIDMgNS45IDMgN3YxMGMwIDEuMS45IDEuOTkgMiAxLjk5TDE2IDE5Yy42NyAwIDEuMjctLjMzIDEuNjMtLjg0TDIyIDEybC00LjM3LTYuMTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGFiZWwtb3V0bGluZSI+PHBhdGggZD0iTTE3LjYzIDUuODRDMTcuMjcgNS4zMyAxNi42NyA1IDE2IDVMNSA1LjAxQzMuOSA1LjAxIDMgNS45IDMgN3YxMGMwIDEuMS45IDEuOTkgMiAxLjk5TDE2IDE5Yy42NyAwIDEuMjctLjMzIDEuNjMtLjg0TDIyIDEybC00LjM3LTYuMTZ6TTE2IDE3SDVWN2gxMWwzLjU1IDVMMTYgMTd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGFuZ3VhZ2UiPjxwYXRoIGQ9Ik0xMS45OSAyQzYuNDcgMiAyIDYuNDggMiAxMnM0LjQ3IDEwIDkuOTkgMTBDMTcuNTIgMjIgMjIgMTcuNTIgMjIgMTJTMTcuNTIgMiAxMS45OSAyem02LjkzIDZoLTIuOTVjLS4zMi0xLjI1LS43OC0yLjQ1LTEuMzgtMy41NiAxLjg0LjYzIDMuMzcgMS45MSA0LjMzIDMuNTZ6TTEyIDQuMDRjLjgzIDEuMiAxLjQ4IDIuNTMgMS45MSAzLjk2aC0zLjgyYy40My0xLjQzIDEuMDgtMi43NiAxLjkxLTMuOTZ6TTQuMjYgMTRDNC4xIDEzLjM2IDQgMTIuNjkgNCAxMnMuMS0xLjM2LjI2LTJoMy4zOGMtLjA4LjY2LS4xNCAxLjMyLS4xNCAyIDAgLjY4LjA2IDEuMzQuMTQgMkg0LjI2em0uODIgMmgyLjk1Yy4zMiAxLjI1Ljc4IDIuNDUgMS4zOCAzLjU2LTEuODQtLjYzLTMuMzctMS45LTQuMzMtMy41NnptMi45NS04SDUuMDhjLjk2LTEuNjYgMi40OS0yLjkzIDQuMzMtMy41NkM4LjgxIDUuNTUgOC4zNSA2Ljc1IDguMDMgOHpNMTIgMTkuOTZjLS44My0xLjItMS40OC0yLjUzLTEuOTEtMy45NmgzLjgyYy0uNDMgMS40My0xLjA4IDIuNzYtMS45MSAzLjk2ek0xNC4zNCAxNEg5LjY2Yy0uMDktLjY2LS4xNi0xLjMyLS4xNi0yIDAtLjY4LjA3LTEuMzUuMTYtMmg0LjY4Yy4wOS42NS4xNiAxLjMyLjE2IDIgMCAuNjgtLjA3IDEuMzQtLjE2IDJ6bS4yNSA1LjU2Yy42LTEuMTEgMS4wNi0yLjMxIDEuMzgtMy41NmgyLjk1Yy0uOTYgMS42NS0yLjQ5IDIuOTMtNC4zMyAzLjU2ek0xNi4zNiAxNGMuMDgtLjY2LjE0LTEuMzIuMTQtMiAwLS42OC0uMDYtMS4zNC0uMTQtMmgzLjM4Yy4xNi42NC4yNiAxLjMxLjI2IDJzLS4xIDEuMzYtLjI2IDJoLTMuMzh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGFzdC1wYWdlIj48cGF0aCBkPSJNNS41OSA3LjQxTDEwLjE4IDEybC00LjU5IDQuNTlMNyAxOGw2LTYtNi02ek0xNiA2aDJ2MTJoLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGF1bmNoIj48cGF0aCBkPSJNMTkgMTlINVY1aDdWM0g1Yy0xLjExIDAtMiAuOS0yIDJ2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJ2LTdoLTJ2N3pNMTQgM3YyaDMuNTlsLTkuODMgOS44MyAxLjQxIDEuNDFMMTkgNi40MVYxMGgyVjNoLTd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGlnaHRidWxiLW91dGxpbmUiPjxwYXRoIGQ9Ik05IDIxYzAgLjU1LjQ1IDEgMSAxaDRjLjU1IDAgMS0uNDUgMS0xdi0xSDl2MXptMy0xOUM4LjE0IDIgNSA1LjE0IDUgOWMwIDIuMzggMS4xOSA0LjQ3IDMgNS43NFYxN2MwIC41NS40NSAxIDEgMWg2Yy41NSAwIDEtLjQ1IDEtMXYtMi4yNmMxLjgxLTEuMjcgMy0zLjM2IDMtNS43NCAwLTMuODYtMy4xNC03LTctN3ptMi44NSAxMS4xbC0uODUuNlYxNmgtNHYtMi4zbC0uODUtLjZDNy44IDEyLjE2IDcgMTAuNjMgNyA5YzAtMi43NiAyLjI0LTUgNS01czUgMi4yNCA1IDVjMCAxLjYzLS44IDMuMTYtMi4xNSA0LjF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGluZS1zdHlsZSI+PHBhdGggZD0iTTMgMTZoNXYtMkgzdjJ6bTYuNSAwaDV2LTJoLTV2MnptNi41IDBoNXYtMmgtNXYyek0zIDIwaDJ2LTJIM3Yyem00IDBoMnYtMkg3djJ6bTQgMGgydi0yaC0ydjJ6bTQgMGgydi0yaC0ydjJ6bTQgMGgydi0yaC0ydjJ6TTMgMTJoOHYtMkgzdjJ6bTEwIDBoOHYtMmgtOHYyek0zIDR2NGgxOFY0SDN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibGluZS13ZWlnaHQiPjxwYXRoIGQ9Ik0zIDE3aDE4di0ySDN2MnptMCAzaDE4di0xSDN2MXptMC03aDE4di0zSDN2M3ptMC05djRoMThWNEgzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImxpbmsiPjxwYXRoIGQ9Ik0zLjkgMTJjMC0xLjcxIDEuMzktMy4xIDMuMS0zLjFoNFY3SDdjLTIuNzYgMC01IDIuMjQtNSA1czIuMjQgNSA1IDVoNHYtMS45SDdjLTEuNzEgMC0zLjEtMS4zOS0zLjEtMy4xek04IDEzaDh2LTJIOHYyem05LTZoLTR2MS45aDRjMS43MSAwIDMuMSAxLjM5IDMuMSAzLjFzLTEuMzkgMy4xLTMuMSAzLjFoLTRWMTdoNGMyLjc2IDAgNS0yLjI0IDUtNXMtMi4yNC01LTUtNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJsaXN0Ij48cGF0aCBkPSJNMyAxM2gydi0ySDN2MnptMCA0aDJ2LTJIM3Yyem0wLThoMlY3SDN2MnptNCA0aDE0di0ySDd2MnptMCA0aDE0di0ySDd2MnpNNyA3djJoMTRWN0g3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImxvY2siPjxwYXRoIGQ9Ik0xOCA4aC0xVjZjMC0yLjc2LTIuMjQtNS01LTVTNyAzLjI0IDcgNnYySDZjLTEuMSAwLTIgLjktMiAydjEwYzAgMS4xLjkgMiAyIDJoMTJjMS4xIDAgMi0uOSAyLTJWMTBjMC0xLjEtLjktMi0yLTJ6bS02IDljLTEuMSAwLTItLjktMi0ycy45LTIgMi0yIDIgLjkgMiAyLS45IDItMiAyem0zLjEtOUg4LjlWNmMwLTEuNzEgMS4zOS0zLjEgMy4xLTMuMSAxLjcxIDAgMy4xIDEuMzkgMy4xIDMuMXYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9ImxvY2stb3BlbiI+PHBhdGggZD0iTTEyIDE3YzEuMSAwIDItLjkgMi0ycy0uOS0yLTItMi0yIC45LTIgMiAuOSAyIDIgMnptNi05aC0xVjZjMC0yLjc2LTIuMjQtNS01LTVTNyAzLjI0IDcgNmgxLjljMC0xLjcxIDEuMzktMy4xIDMuMS0zLjEgMS43MSAwIDMuMSAxLjM5IDMuMSAzLjF2Mkg2Yy0xLjEgMC0yIC45LTIgMnYxMGMwIDEuMS45IDIgMiAyaDEyYzEuMSAwIDItLjkgMi0yVjEwYzAtMS4xLS45LTItMi0yem0wIDEySDZWMTBoMTJ2MTB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibG9jay1vdXRsaW5lIj48cGF0aCBkPSJNMTIgMTdjMS4xIDAgMi0uOSAyLTJzLS45LTItMi0yLTIgLjktMiAyIC45IDIgMiAyem02LTloLTFWNmMwLTIuNzYtMi4yNC01LTUtNVM3IDMuMjQgNyA2djJINmMtMS4xIDAtMiAuOS0yIDJ2MTBjMCAxLjEuOSAyIDIgMmgxMmMxLjEgMCAyLS45IDItMlYxMGMwLTEuMS0uOS0yLTItMnpNOC45IDZjMC0xLjcxIDEuMzktMy4xIDMuMS0zLjFzMy4xIDEuMzkgMy4xIDMuMXYySDguOVY2ek0xOCAyMEg2VjEwaDEydjEweiI+PC9wYXRoPjwvZz4KPGcgaWQ9Imxvdy1wcmlvcml0eSI+PHBhdGggZD0iTTE0IDVoOHYyaC04em0wIDUuNWg4djJoLTh6bTAgNS41aDh2MmgtOHpNMiAxMS41QzIgMTUuMDggNC45MiAxOCA4LjUgMThIOXYybDMtMy0zLTN2MmgtLjVDNi4wMiAxNiA0IDEzLjk4IDQgMTEuNVM2LjAyIDcgOC41IDdIMTJWNUg4LjVDNC45MiA1IDIgNy45MiAyIDExLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibG95YWx0eSI+PHBhdGggZD0iTTIxLjQxIDExLjU4bC05LTlDMTIuMDUgMi4yMiAxMS41NSAyIDExIDJINGMtMS4xIDAtMiAuOS0yIDJ2N2MwIC41NS4yMiAxLjA1LjU5IDEuNDJsOSA5Yy4zNi4zNi44Ni41OCAxLjQxLjU4LjU1IDAgMS4wNS0uMjIgMS40MS0uNTlsNy03Yy4zNy0uMzYuNTktLjg2LjU5LTEuNDEgMC0uNTUtLjIzLTEuMDYtLjU5LTEuNDJ6TTUuNSA3QzQuNjcgNyA0IDYuMzMgNCA1LjVTNC42NyA0IDUuNSA0IDcgNC42NyA3IDUuNSA2LjMzIDcgNS41IDd6bTExLjc3IDguMjdMMTMgMTkuNTRsLTQuMjctNC4yN0M4LjI4IDE0LjgxIDggMTQuMTkgOCAxMy41YzAtMS4zOCAxLjEyLTIuNSAyLjUtMi41LjY5IDAgMS4zMi4yOCAxLjc3Ljc0bC43My43Mi43My0uNzNjLjQ1LS40NSAxLjA4LS43MyAxLjc3LS43MyAxLjM4IDAgMi41IDEuMTIgMi41IDIuNSAwIC42OS0uMjggMS4zMi0uNzMgMS43N3oiPjwvcGF0aD48L2c+CjxnIGlkPSJtYWlsIj48cGF0aCBkPSJNMjAgNEg0Yy0xLjEgMC0xLjk5LjktMS45OSAyTDIgMThjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY2YzAtMS4xLS45LTItMi0yem0wIDRsLTggNS04LTVWNmw4IDUgOC01djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibWFya3VucmVhZCI+PHBhdGggZD0iTTIwIDRINGMtMS4xIDAtMS45OS45LTEuOTkgMkwyIDE4YzAgMS4xLjkgMiAyIDJoMTZjMS4xIDAgMi0uOSAyLTJWNmMwLTEuMS0uOS0yLTItMnptMCA0bC04IDUtOC01VjZsOCA1IDgtNXYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im1hcmt1bnJlYWQtbWFpbGJveCI+PHBhdGggZD0iTTIwIDZIMTB2Nkg4VjRoNlYwSDZ2Nkg0Yy0xLjEgMC0yIC45LTIgMnYxMmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjhjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibWVudSI+PHBhdGggZD0iTTMgMThoMTh2LTJIM3Yyem0wLTVoMTh2LTJIM3Yyem0wLTd2MmgxOFY2SDN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibW9yZS1ob3JpeiI+PHBhdGggZD0iTTYgMTBjLTEuMSAwLTIgLjktMiAycy45IDIgMiAyIDItLjkgMi0yLS45LTItMi0yem0xMiAwYy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnptLTYgMGMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibW9yZS12ZXJ0Ij48cGF0aCBkPSJNMTIgOGMxLjEgMCAyLS45IDItMnMtLjktMi0yLTItMiAuOS0yIDIgLjkgMiAyIDJ6bTAgMmMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6bTAgNmMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ibW90b3JjeWNsZSI+PHBhdGggZD0iTTE5LjQ0IDkuMDNMMTUuNDEgNUgxMXYyaDMuNTlsMiAySDVjLTIuOCAwLTUgMi4yLTUgNXMyLjIgNSA1IDVjMi40NiAwIDQuNDUtMS42OSA0LjktNGgxLjY1bDIuNzctMi43N2MtLjIxLjU0LS4zMiAxLjE0LS4zMiAxLjc3IDAgMi44IDIuMiA1IDUgNXM1LTIuMiA1LTVjMC0yLjY1LTEuOTctNC43Ny00LjU2LTQuOTd6TTcuODIgMTVDNy40IDE2LjE1IDYuMjggMTcgNSAxN2MtMS42MyAwLTMtMS4zNy0zLTNzMS4zNy0zIDMtM2MxLjI4IDAgMi40Ljg1IDIuODIgMkg1djJoMi44MnpNMTkgMTdjLTEuNjYgMC0zLTEuMzQtMy0zczEuMzQtMyAzLTMgMyAxLjM0IDMgMy0xLjM0IDMtMyAzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im1vdmUtdG8taW5ib3giPjxwYXRoIGQ9Ik0xOSAzSDQuOTljLTEuMTEgMC0xLjk4LjktMS45OCAyTDMgMTljMCAxLjEuODggMiAxLjk5IDJIMTljMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxMmgtNGMwIDEuNjYtMS4zNSAzLTMgM3MtMy0xLjM0LTMtM0g0Ljk5VjVIMTl2MTB6bS0zLTVoLTJWN2gtNHYzSDhsNCA0IDQtNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJuZXh0LXdlZWsiPjxwYXRoIGQ9Ik0yMCA3aC00VjVjMC0uNTUtLjIyLTEuMDUtLjU5LTEuNDFDMTUuMDUgMy4yMiAxNC41NSAzIDE0IDNoLTRjLTEuMSAwLTIgLjktMiAydjJINGMtMS4xIDAtMiAuOS0yIDJ2MTFjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY5YzAtMS4xLS45LTItMi0yek0xMCA1aDR2MmgtNFY1em0xIDEzLjVsLTEtMSAzLTMtMy0zIDEtMSA0IDQtNCA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im5vdGUtYWRkIj48cGF0aCBkPSJNMTQgMkg2Yy0xLjEgMC0xLjk5LjktMS45OSAyTDQgMjBjMCAxLjEuODkgMiAxLjk5IDJIMThjMS4xIDAgMi0uOSAyLTJWOGwtNi02em0yIDE0aC0zdjNoLTJ2LTNIOHYtMmgzdi0zaDJ2M2gzdjJ6bS0zLTdWMy41TDE4LjUgOUgxM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJvZmZsaW5lLXBpbiI+PHBhdGggZD0iTTEyIDJDNi41IDIgMiA2LjUgMiAxMnM0LjUgMTAgMTAgMTAgMTAtNC41IDEwLTEwUzE3LjUgMiAxMiAyem01IDE2SDd2LTJoMTB2MnptLTYuNy00TDcgMTAuN2wxLjQtMS40IDEuOSAxLjkgNS4zLTUuM0wxNyA3LjMgMTAuMyAxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJvcGFjaXR5Ij48cGF0aCBkPSJNMTcuNjYgOEwxMiAyLjM1IDYuMzQgOEM0Ljc4IDkuNTYgNCAxMS42NCA0IDEzLjY0cy43OCA0LjExIDIuMzQgNS42NyAzLjYxIDIuMzUgNS42NiAyLjM1IDQuMS0uNzkgNS42Ni0yLjM1UzIwIDE1LjY0IDIwIDEzLjY0IDE5LjIyIDkuNTYgMTcuNjYgOHpNNiAxNGMuMDEtMiAuNjItMy4yNyAxLjc2LTQuNEwxMiA1LjI3bDQuMjQgNC4zOEMxNy4zOCAxMC43NyAxNy45OSAxMiAxOCAxNEg2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im9wZW4taW4tYnJvd3NlciI+PHBhdGggZD0iTTE5IDRINWMtMS4xMSAwLTIgLjktMiAydjEyYzAgMS4xLjg5IDIgMiAyaDR2LTJINVY4aDE0djEwaC00djJoNGMxLjEgMCAyLS45IDItMlY2YzAtMS4xLS44OS0yLTItMnptLTcgNmwtNCA0aDN2Nmgydi02aDNsLTQtNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJvcGVuLWluLW5ldyI+PHBhdGggZD0iTTE5IDE5SDVWNWg3VjNINWMtMS4xMSAwLTIgLjktMiAydjE0YzAgMS4xLjg5IDIgMiAyaDE0YzEuMSAwIDItLjkgMi0ydi03aC0ydjd6TTE0IDN2MmgzLjU5bC05LjgzIDkuODMgMS40MSAxLjQxTDE5IDYuNDFWMTBoMlYzaC03eiI+PC9wYXRoPjwvZz4KPGcgaWQ9Im9wZW4td2l0aCI+PHBhdGggZD0iTTEwIDloNFY2aDNsLTUtNS01IDVoM3Yzem0tMSAxSDZWN2wtNSA1IDUgNXYtM2gzdi00em0xNCAybC01LTV2M2gtM3Y0aDN2M2w1LTV6bS05IDNoLTR2M0g3bDUgNSA1LTVoLTN2LTN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGFnZXZpZXciPjxwYXRoIGQ9Ik0xMS41IDlDMTAuMTIgOSA5IDEwLjEyIDkgMTEuNXMxLjEyIDIuNSAyLjUgMi41IDIuNS0xLjEyIDIuNS0yLjVTMTIuODggOSAxMS41IDl6TTIwIDRINGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmgxNmMxLjEgMCAyLS45IDItMlY2YzAtMS4xLS45LTItMi0yem0tMy4yMSAxNC4yMWwtMi45MS0yLjkxYy0uNjkuNDQtMS41MS43LTIuMzkuN0M5LjAxIDE2IDcgMTMuOTkgNyAxMS41UzkuMDEgNyAxMS41IDcgMTYgOS4wMSAxNiAxMS41YzAgLjg4LS4yNiAxLjY5LS43IDIuMzlsMi45MSAyLjktMS40MiAxLjQyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBhbi10b29sIj48cGF0aCBkPSJNMjMgNS41VjIwYzAgMi4yLTEuOCA0LTQgNGgtNy4zYy0xLjA4IDAtMi4xLS40My0yLjg1LTEuMTlMMSAxNC44M3MxLjI2LTEuMjMgMS4zLTEuMjVjLjIyLS4xOS40OS0uMjkuNzktLjI5LjIyIDAgLjQyLjA2LjYuMTYuMDQuMDEgNC4zMSAyLjQ2IDQuMzEgMi40NlY0YzAtLjgzLjY3LTEuNSAxLjUtMS41UzExIDMuMTcgMTEgNHY3aDFWMS41YzAtLjgzLjY3LTEuNSAxLjUtMS41UzE1IC42NyAxNSAxLjVWMTFoMVYyLjVjMC0uODMuNjctMS41IDEuNS0xLjVzMS41LjY3IDEuNSAxLjVWMTFoMVY1LjVjMC0uODMuNjctMS41IDEuNS0xLjVzMS41LjY3IDEuNSAxLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGF5bWVudCI+PHBhdGggZD0iTTIwIDRINGMtMS4xMSAwLTEuOTkuODktMS45OSAyTDIgMThjMCAxLjExLjg5IDIgMiAyaDE2YzEuMTEgMCAyLS44OSAyLTJWNmMwLTEuMTEtLjg5LTItMi0yem0wIDE0SDR2LTZoMTZ2NnptMC0xMEg0VjZoMTZ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJwZXJtLWNhbWVyYS1taWMiPjxwYXRoIGQ9Ik0yMCA1aC0zLjE3TDE1IDNIOUw3LjE3IDVINGMtMS4xIDAtMiAuOS0yIDJ2MTJjMCAxLjEuOSAyIDIgMmg3di0yLjA5Yy0yLjgzLS40OC01LTIuOTQtNS01LjkxaDJjMCAyLjIxIDEuNzkgNCA0IDRzNC0xLjc5IDQtNGgyYzAgMi45Ny0yLjE3IDUuNDMtNSA1LjkxVjIxaDdjMS4xIDAgMi0uOSAyLTJWN2MwLTEuMS0uOS0yLTItMnptLTYgOGMwIDEuMS0uOSAyLTIgMnMtMi0uOS0yLTJWOWMwLTEuMS45LTIgMi0yczIgLjkgMiAydjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGVybS1jb250YWN0LWNhbGVuZGFyIj48cGF0aCBkPSJNMTkgM2gtMVYxaC0ydjJIOFYxSDZ2Mkg1Yy0xLjExIDAtMiAuOS0yIDJ2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptLTcgM2MxLjY2IDAgMyAxLjM0IDMgM3MtMS4zNCAzLTMgMy0zLTEuMzQtMy0zIDEuMzQtMyAzLTN6bTYgMTJINnYtMWMwLTIgNC0zLjEgNi0zLjFzNiAxLjEgNiAzLjF2MXoiPjwvcGF0aD48L2c+CjxnIGlkPSJwZXJtLWRhdGEtc2V0dGluZyI+PHBhdGggZD0iTTE4Ljk5IDExLjVjLjM0IDAgLjY3LjAzIDEgLjA3TDIwIDAgMCAyMGgxMS41NmMtLjA0LS4zMy0uMDctLjY2LS4wNy0xIDAtNC4xNCAzLjM2LTcuNSA3LjUtNy41em0zLjcxIDcuOTljLjAyLS4xNi4wNC0uMzIuMDQtLjQ5IDAtLjE3LS4wMS0uMzMtLjA0LS40OWwxLjA2LS44M2MuMDktLjA4LjEyLS4yMS4wNi0uMzJsLTEtMS43M2MtLjA2LS4xMS0uMTktLjE1LS4zMS0uMTFsLTEuMjQuNWMtLjI2LS4yLS41NC0uMzctLjg1LS40OWwtLjE5LTEuMzJjLS4wMS0uMTItLjEyLS4yMS0uMjQtLjIxaC0yYy0uMTIgMC0uMjMuMDktLjI1LjIxbC0uMTkgMS4zMmMtLjMuMTMtLjU5LjI5LS44NS40OWwtMS4yNC0uNWMtLjExLS4wNC0uMjQgMC0uMzEuMTFsLTEgMS43M2MtLjA2LjExLS4wNC4yNC4wNi4zMmwxLjA2LjgzYy0uMDIuMTYtLjAzLjMyLS4wMy40OSAwIC4xNy4wMS4zMy4wMy40OWwtMS4wNi44M2MtLjA5LjA4LS4xMi4yMS0uMDYuMzJsMSAxLjczYy4wNi4xMS4xOS4xNS4zMS4xMWwxLjI0LS41Yy4yNi4yLjU0LjM3Ljg1LjQ5bC4xOSAxLjMyYy4wMi4xMi4xMi4yMS4yNS4yMWgyYy4xMiAwIC4yMy0uMDkuMjUtLjIxbC4xOS0xLjMyYy4zLS4xMy41OS0uMjkuODQtLjQ5bDEuMjUuNWMuMTEuMDQuMjQgMCAuMzEtLjExbDEtMS43M2MuMDYtLjExLjAzLS4yNC0uMDYtLjMybC0xLjA3LS44M3ptLTMuNzEgMS4wMWMtLjgzIDAtMS41LS42Ny0xLjUtMS41cy42Ny0xLjUgMS41LTEuNSAxLjUuNjcgMS41IDEuNS0uNjcgMS41LTEuNSAxLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGVybS1kZXZpY2UtaW5mb3JtYXRpb24iPjxwYXRoIGQ9Ik0xMyA3aC0ydjJoMlY3em0wIDRoLTJ2Nmgydi02em00LTkuOTlMNyAxYy0xLjEgMC0yIC45LTIgMnYxOGMwIDEuMS45IDIgMiAyaDEwYzEuMSAwIDItLjkgMi0yVjNjMC0xLjEtLjktMS45OS0yLTEuOTl6TTE3IDE5SDdWNWgxMHYxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJwZXJtLWlkZW50aXR5Ij48cGF0aCBkPSJNMTIgNS45YzEuMTYgMCAyLjEuOTQgMi4xIDIuMXMtLjk0IDIuMS0yLjEgMi4xUzkuOSA5LjE2IDkuOSA4cy45NC0yLjEgMi4xLTIuMW0wIDljMi45NyAwIDYuMSAxLjQ2IDYuMSAyLjF2MS4xSDUuOVYxN2MwLS42NCAzLjEzLTIuMSA2LjEtMi4xTTEyIDRDOS43OSA0IDggNS43OSA4IDhzMS43OSA0IDQgNCA0LTEuNzkgNC00LTEuNzktNC00LTR6bTAgOWMtMi42NyAwLTggMS4zNC04IDR2M2gxNnYtM2MwLTIuNjYtNS4zMy00LTgtNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJwZXJtLW1lZGlhIj48cGF0aCBkPSJNMiA2SDB2NWguMDFMMCAyMGMwIDEuMS45IDIgMiAyaDE4di0ySDJWNnptMjAtMmgtOGwtMi0ySDZjLTEuMSAwLTEuOTkuOS0xLjk5IDJMNCAxNmMwIDEuMS45IDIgMiAyaDE2YzEuMSAwIDItLjkgMi0yVjZjMC0xLjEtLjktMi0yLTJ6TTcgMTVsNC41LTYgMy41IDQuNTEgMi41LTMuMDFMMjEgMTVIN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJwZXJtLXBob25lLW1zZyI+PHBhdGggZD0iTTIwIDE1LjVjLTEuMjUgMC0yLjQ1LS4yLTMuNTctLjU3LS4zNS0uMTEtLjc0LS4wMy0xLjAyLjI0bC0yLjIgMi4yYy0yLjgzLTEuNDQtNS4xNS0zLjc1LTYuNTktNi41OGwyLjItMi4yMWMuMjgtLjI3LjM2LS42Ni4yNS0xLjAxQzguNyA2LjQ1IDguNSA1LjI1IDguNSA0YzAtLjU1LS40NS0xLTEtMUg0Yy0uNTUgMC0xIC40NS0xIDEgMCA5LjM5IDcuNjEgMTcgMTcgMTcgLjU1IDAgMS0uNDUgMS0xdi0zLjVjMC0uNTUtLjQ1LTEtMS0xek0xMiAzdjEwbDMtM2g2VjNoLTl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icGVybS1zY2FuLXdpZmkiPjxwYXRoIGQ9Ik0xMiAzQzYuOTUgMyAzLjE1IDQuODUgMCA3LjIzTDEyIDIyIDI0IDcuMjVDMjAuODUgNC44NyAxNy4wNSAzIDEyIDN6bTEgMTNoLTJ2LTZoMnY2em0tMi04VjZoMnYyaC0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBldHMiPjxjaXJjbGUgY3g9IjQuNSIgY3k9IjkuNSIgcj0iMi41Ij48L2NpcmNsZT48Y2lyY2xlIGN4PSI5IiBjeT0iNS41IiByPSIyLjUiPjwvY2lyY2xlPjxjaXJjbGUgY3g9IjE1IiBjeT0iNS41IiByPSIyLjUiPjwvY2lyY2xlPjxjaXJjbGUgY3g9IjE5LjUiIGN5PSI5LjUiIHI9IjIuNSI+PC9jaXJjbGU+PHBhdGggZD0iTTE3LjM0IDE0Ljg2Yy0uODctMS4wMi0xLjYtMS44OS0yLjQ4LTIuOTEtLjQ2LS41NC0xLjA1LTEuMDgtMS43NS0xLjMyLS4xMS0uMDQtLjIyLS4wNy0uMzMtLjA5LS4yNS0uMDQtLjUyLS4wNC0uNzgtLjA0cy0uNTMgMC0uNzkuMDVjLS4xMS4wMi0uMjIuMDUtLjMzLjA5LS43LjI0LTEuMjguNzgtMS43NSAxLjMyLS44NyAxLjAyLTEuNiAxLjg5LTIuNDggMi45MS0xLjMxIDEuMzEtMi45MiAyLjc2LTIuNjIgNC43OS4yOSAxLjAyIDEuMDIgMi4wMyAyLjMzIDIuMzIuNzMuMTUgMy4wNi0uNDQgNS41NC0uNDRoLjE4YzIuNDggMCA0LjgxLjU4IDUuNTQuNDQgMS4zMS0uMjkgMi4wNC0xLjMxIDIuMzMtMi4zMi4zMS0yLjA0LTEuMy0zLjQ5LTIuNjEtNC44eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBpY3R1cmUtaW4tcGljdHVyZSI+PHBhdGggZD0iTTE5IDdoLTh2Nmg4Vjd6bTItNEgzYy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDEuOTggMiAxLjk4aDE4YzEuMSAwIDItLjg4IDItMS45OFY1YzAtMS4xLS45LTItMi0yem0wIDE2LjAxSDNWNC45OGgxOHYxNC4wM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJwaWN0dXJlLWluLXBpY3R1cmUtYWx0Ij48cGF0aCBkPSJNMTkgMTFoLTh2Nmg4di02em00IDhWNC45OEMyMyAzLjg4IDIyLjEgMyAyMSAzSDNjLTEuMSAwLTIgLjg4LTIgMS45OFYxOWMwIDEuMS45IDIgMiAyaDE4YzEuMSAwIDItLjkgMi0yem0tMiAuMDJIM1Y0Ljk3aDE4djE0LjA1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InBsYXktZm9yLXdvcmsiPjxwYXRoIGQ9Ik0xMSA1djUuNTlINy41bDQuNSA0LjUgNC41LTQuNUgxM1Y1aC0yem0tNSA5YzAgMy4zMSAyLjY5IDYgNiA2czYtMi42OSA2LTZoLTJjMCAyLjIxLTEuNzkgNC00IDRzLTQtMS43OS00LTRINnoiPjwvcGF0aD48L2c+CjxnIGlkPSJwb2x5bWVyIj48cGF0aCBkPSJNMTkgNGgtNEw3LjExIDE2LjYzIDQuNSAxMiA5IDRINUwuNSAxMiA1IDIwaDRsNy44OS0xMi42M0wxOS41IDEyIDE1IDIwaDRsNC41LTh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icG93ZXItc2V0dGluZ3MtbmV3Ij48cGF0aCBkPSJNMTMgM2gtMnYxMGgyVjN6bTQuODMgMi4xN2wtMS40MiAxLjQyQzE3Ljk5IDcuODYgMTkgOS44MSAxOSAxMmMwIDMuODctMy4xMyA3LTcgN3MtNy0zLjEzLTctN2MwLTIuMTkgMS4wMS00LjE0IDIuNTgtNS40Mkw2LjE3IDUuMTdDNC4yMyA2LjgyIDMgOS4yNiAzIDEyYzAgNC45NyA0LjAzIDkgOSA5czktNC4wMyA5LTljMC0yLjc0LTEuMjMtNS4xOC0zLjE3LTYuODN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icHJlZ25hbnQtd29tYW4iPjxwYXRoIGQ9Ik05IDRjMC0xLjExLjg5LTIgMi0yczIgLjg5IDIgMi0uODkgMi0yIDItMi0uODktMi0yem03IDljLS4wMS0xLjM0LS44My0yLjUxLTItMyAwLTEuNjYtMS4zNC0zLTMtM3MtMyAxLjM0LTMgM3Y3aDJ2NWgzdi01aDN2LTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icHJpbnQiPjxwYXRoIGQ9Ik0xOSA4SDVjLTEuNjYgMC0zIDEuMzQtMyAzdjZoNHY0aDEydi00aDR2LTZjMC0xLjY2LTEuMzQtMy0zLTN6bS0zIDExSDh2LTVoOHY1em0zLTdjLS41NSAwLTEtLjQ1LTEtMXMuNDUtMSAxLTEgMSAuNDUgMSAxLS40NSAxLTEgMXptLTEtOUg2djRoMTJWM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJxdWVyeS1idWlsZGVyIj48cGF0aCBkPSJNMTEuOTkgMkM2LjQ3IDIgMiA2LjQ4IDIgMTJzNC40NyAxMCA5Ljk5IDEwQzE3LjUyIDIyIDIyIDE3LjUyIDIyIDEyUzE3LjUyIDIgMTEuOTkgMnpNMTIgMjBjLTQuNDIgMC04LTMuNTgtOC04czMuNTgtOCA4LTggOCAzLjU4IDggOC0zLjU4IDgtOCA4em0uNS0xM0gxMXY2bDUuMjUgMy4xNS43NS0xLjIzLTQuNS0yLjY3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InF1ZXN0aW9uLWFuc3dlciI+PHBhdGggZD0iTTIxIDZoLTJ2OUg2djJjMCAuNTUuNDUgMSAxIDFoMTFsNCA0VjdjMC0uNTUtLjQ1LTEtMS0xem0tNCA2VjNjMC0uNTUtLjQ1LTEtMS0xSDNjLS41NSAwLTEgLjQ1LTEgMXYxNGw0LTRoMTBjLjU1IDAgMS0uNDUgMS0xeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJhZGlvLWJ1dHRvbi1jaGVja2VkIj48cGF0aCBkPSJNMTIgN2MtMi43NiAwLTUgMi4yNC01IDVzMi4yNCA1IDUgNSA1LTIuMjQgNS01LTIuMjQtNS01LTV6bTAtNUM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MiAwLTgtMy41OC04LThzMy41OC04IDgtOCA4IDMuNTggOCA4LTMuNTggOC04IDh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmFkaW8tYnV0dG9uLXVuY2hlY2tlZCI+PHBhdGggZD0iTTEyIDJDNi40OCAyIDIgNi40OCAyIDEyczQuNDggMTAgMTAgMTAgMTAtNC40OCAxMC0xMFMxNy41MiAyIDEyIDJ6bTAgMThjLTQuNDIgMC04LTMuNTgtOC04czMuNTgtOCA4LTggOCAzLjU4IDggOC0zLjU4IDgtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJlY2VpcHQiPjxwYXRoIGQ9Ik0xOCAxN0g2di0yaDEydjJ6bTAtNEg2di0yaDEydjJ6bTAtNEg2VjdoMTJ2MnpNMyAyMmwxLjUtMS41TDYgMjJsMS41LTEuNUw5IDIybDEuNS0xLjVMMTIgMjJsMS41LTEuNUwxNSAyMmwxLjUtMS41TDE4IDIybDEuNS0xLjVMMjEgMjJWMmwtMS41IDEuNUwxOCAybC0xLjUgMS41TDE1IDJsLTEuNSAxLjVMMTIgMmwtMS41IDEuNUw5IDIgNy41IDMuNSA2IDIgNC41IDMuNSAzIDJ2MjB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVjb3JkLXZvaWNlLW92ZXIiPjxjaXJjbGUgY3g9IjkiIGN5PSI5IiByPSI0Ij48L2NpcmNsZT48cGF0aCBkPSJNOSAxNWMtMi42NyAwLTggMS4zNC04IDR2MmgxNnYtMmMwLTIuNjYtNS4zMy00LTgtNHptNy43Ni05LjY0bC0xLjY4IDEuNjljLjg0IDEuMTguODQgMi43MSAwIDMuODlsMS42OCAxLjY5YzIuMDItMi4wMiAyLjAyLTUuMDcgMC03LjI3ek0yMC4wNyAybC0xLjYzIDEuNjNjMi43NyAzLjAyIDIuNzcgNy41NiAwIDEwLjc0TDIwLjA3IDE2YzMuOS0zLjg5IDMuOTEtOS45NSAwLTE0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJlZGVlbSI+PHBhdGggZD0iTTIwIDZoLTIuMThjLjExLS4zMS4xOC0uNjUuMTgtMSAwLTEuNjYtMS4zNC0zLTMtMy0xLjA1IDAtMS45Ni41NC0yLjUgMS4zNWwtLjUuNjctLjUtLjY4QzEwLjk2IDIuNTQgMTAuMDUgMiA5IDIgNy4zNCAyIDYgMy4zNCA2IDVjMCAuMzUuMDcuNjkuMTggMUg0Yy0xLjExIDAtMS45OS44OS0xLjk5IDJMMiAxOWMwIDEuMTEuODkgMiAyIDJoMTZjMS4xMSAwIDItLjg5IDItMlY4YzAtMS4xMS0uODktMi0yLTJ6bS01LTJjLjU1IDAgMSAuNDUgMSAxcy0uNDUgMS0xIDEtMS0uNDUtMS0xIC40NS0xIDEtMXpNOSA0Yy41NSAwIDEgLjQ1IDEgMXMtLjQ1IDEtMSAxLTEtLjQ1LTEtMSAuNDUtMSAxLTF6bTExIDE1SDR2LTJoMTZ2MnptMC01SDRWOGg1LjA4TDcgMTAuODMgOC42MiAxMiAxMSA4Ljc2bDEtMS4zNiAxIDEuMzZMMTUuMzggMTIgMTcgMTAuODMgMTQuOTIgOEgyMHY2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJlZG8iPjxwYXRoIGQ9Ik0xOC40IDEwLjZDMTYuNTUgOC45OSAxNC4xNSA4IDExLjUgOGMtNC42NSAwLTguNTggMy4wMy05Ljk2IDcuMjJMMy45IDE2YzEuMDUtMy4xOSA0LjA1LTUuNSA3LjYtNS41IDEuOTUgMCAzLjczLjcyIDUuMTIgMS44OEwxMyAxNmg5VjdsLTMuNiAzLjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVmcmVzaCI+PHBhdGggZD0iTTE3LjY1IDYuMzVDMTYuMiA0LjkgMTQuMjEgNCAxMiA0Yy00LjQyIDAtNy45OSAzLjU4LTcuOTkgOHMzLjU3IDggNy45OSA4YzMuNzMgMCA2Ljg0LTIuNTUgNy43My02aC0yLjA4Yy0uODIgMi4zMy0zLjA0IDQtNS42NSA0LTMuMzEgMC02LTIuNjktNi02czIuNjktNiA2LTZjMS42NiAwIDMuMTQuNjkgNC4yMiAxLjc4TDEzIDExaDdWNGwtMi4zNSAyLjM1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InJlbW92ZSI+PHBhdGggZD0iTTE5IDEzSDV2LTJoMTR2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJyZW1vdmUtY2lyY2xlIj48cGF0aCBkPSJNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptNSAxMUg3di0yaDEwdjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVtb3ZlLWNpcmNsZS1vdXRsaW5lIj48cGF0aCBkPSJNNyAxMXYyaDEwdi0ySDd6bTUtOUM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVtb3ZlLXNob3BwaW5nLWNhcnQiPjxwYXRoIGQ9Ik0yMi43MyAyMi43M0wyLjc3IDIuNzcgMiAybC0uNzMtLjczTDAgMi41NGw0LjM5IDQuMzkgMi4yMSA0LjY2LTEuMzUgMi40NWMtLjE2LjI4LS4yNS42MS0uMjUuOTYgMCAxLjEuOSAyIDIgMmg3LjQ2bDEuMzggMS4zOGMtLjUuMzYtLjgzLjk1LS44MyAxLjYyIDAgMS4xLjg5IDIgMS45OSAyIC42NyAwIDEuMjYtLjMzIDEuNjItLjg0TDIxLjQ2IDI0bDEuMjctMS4yN3pNNy40MiAxNWMtLjE0IDAtLjI1LS4xMS0uMjUtLjI1bC4wMy0uMTIuOS0xLjYzaDIuMzZsMiAySDcuNDJ6bTguMTMtMmMuNzUgMCAxLjQxLS40MSAxLjc1LTEuMDNsMy41OC02LjQ5Yy4wOC0uMTQuMTItLjMxLjEyLS40OCAwLS41NS0uNDUtMS0xLTFINi41NGw5LjAxIDl6TTcgMThjLTEuMSAwLTEuOTkuOS0xLjk5IDJTNS45IDIyIDcgMjJzMi0uOSAyLTItLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVvcmRlciI+PHBhdGggZD0iTTMgMTVoMTh2LTJIM3Yyem0wIDRoMTh2LTJIM3Yyem0wLThoMThWOUgzdjJ6bTAtNnYyaDE4VjVIM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJyZXBseSI+PHBhdGggZD0iTTEwIDlWNWwtNyA3IDcgN3YtNC4xYzUgMCA4LjUgMS42IDExIDUuMS0xLTUtNC0xMC0xMS0xMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJyZXBseS1hbGwiPjxwYXRoIGQ9Ik03IDhWNWwtNyA3IDcgN3YtM2wtNC00IDQtNHptNiAxVjVsLTcgNyA3IDd2LTQuMWM1IDAgOC41IDEuNiAxMSA1LjEtMS01LTQtMTAtMTEtMTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVwb3J0Ij48cGF0aCBkPSJNMTUuNzMgM0g4LjI3TDMgOC4yN3Y3LjQ2TDguMjcgMjFoNy40NkwyMSAxNS43M1Y4LjI3TDE1LjczIDN6TTEyIDE3LjNjLS43MiAwLTEuMy0uNTgtMS4zLTEuMyAwLS43Mi41OC0xLjMgMS4zLTEuMy43MiAwIDEuMy41OCAxLjMgMS4zIDAgLjcyLS41OCAxLjMtMS4zIDEuM3ptMS00LjNoLTJWN2gydjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVwb3J0LXByb2JsZW0iPjxwYXRoIGQ9Ik0xIDIxaDIyTDEyIDIgMSAyMXptMTItM2gtMnYtMmgydjJ6bTAtNGgtMnYtNGgydjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icmVzdG9yZSI+PHBhdGggZD0iTTEzIDNjLTQuOTcgMC05IDQuMDMtOSA5SDFsMy44OSAzLjg5LjA3LjE0TDkgMTJINmMwLTMuODcgMy4xMy03IDctN3M3IDMuMTMgNyA3LTMuMTMgNy03IDdjLTEuOTMgMC0zLjY4LS43OS00Ljk0LTIuMDZsLTEuNDIgMS40MkM4LjI3IDE5Ljk5IDEwLjUxIDIxIDEzIDIxYzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05em0tMSA1djVsNC4yOCAyLjU0LjcyLTEuMjEtMy41LTIuMDhWOEgxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJyZXN0b3JlLXBhZ2UiPjxwYXRoIGQ9Ik0xNCAySDZjLTEuMSAwLTEuOTkuOS0xLjk5IDJMNCAyMGMwIDEuMS44OSAyIDEuOTkgMkgxOGMxLjEgMCAyLS45IDItMlY4bC02LTZ6bS0yIDE2Yy0yLjA1IDAtMy44MS0xLjI0LTQuNTgtM2gxLjcxYy42My45IDEuNjggMS41IDIuODcgMS41IDEuOTMgMCAzLjUtMS41NyAzLjUtMy41UzEzLjkzIDkuNSAxMiA5LjVjLTEuMzUgMC0yLjUyLjc4LTMuMSAxLjlsMS42IDEuNmgtNFY5bDEuMyAxLjNDOC42OSA4LjkyIDEwLjIzIDggMTIgOGMyLjc2IDAgNSAyLjI0IDUgNXMtMi4yNCA1LTUgNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJyb29tIj48cGF0aCBkPSJNMTIgMkM4LjEzIDIgNSA1LjEzIDUgOWMwIDUuMjUgNyAxMyA3IDEzczctNy43NSA3LTEzYzAtMy44Ny0zLjEzLTctNy03em0wIDkuNWMtMS4zOCAwLTIuNS0xLjEyLTIuNS0yLjVzMS4xMi0yLjUgMi41LTIuNSAyLjUgMS4xMiAyLjUgMi41LTEuMTIgMi41LTIuNSAyLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0icm91bmRlZC1jb3JuZXIiPjxwYXRoIGQ9Ik0xOSAxOWgydjJoLTJ2LTJ6bTAtMmgydi0yaC0ydjJ6TTMgMTNoMnYtMkgzdjJ6bTAgNGgydi0ySDN2MnptMC04aDJWN0gzdjJ6bTAtNGgyVjNIM3Yyem00IDBoMlYzSDd2MnptOCAxNmgydi0yaC0ydjJ6bS00IDBoMnYtMmgtMnYyem00IDBoMnYtMmgtMnYyem0tOCAwaDJ2LTJIN3Yyem0tNCAwaDJ2LTJIM3Yyek0yMSA4YzAtMi43Ni0yLjI0LTUtNS01aC01djJoNWMxLjY1IDAgMyAxLjM1IDMgM3Y1aDJWOHoiPjwvcGF0aD48L2c+CjxnIGlkPSJyb3dpbmciPjxwYXRoIGQ9Ik04LjUgMTQuNUw0IDE5bDEuNSAxLjVMOSAxN2gybC0yLjUtMi41ek0xNSAxYy0xLjEgMC0yIC45LTIgMnMuOSAyIDIgMiAyLS45IDItMi0uOS0yLTItMnptNiAyMC4wMUwxOCAyNGwtMi45OS0zLjAxVjE5LjVsLTcuMS03LjA5Yy0uMzEuMDUtLjYxLjA3LS45MS4wN3YtMi4xNmMxLjY2LjAzIDMuNjEtLjg3IDQuNjctMi4wNGwxLjQtMS41NWMuMTktLjIxLjQzLS4zOC42OS0uNS4yOS0uMTQuNjItLjIzLjk2LS4yM2guMDNDMTUuOTkgNi4wMSAxNyA3LjAyIDE3IDguMjZ2NS43NWMwIC44NC0uMzUgMS42MS0uOTIgMi4xNmwtMy41OC0zLjU4di0yLjI3Yy0uNjMuNTItMS40MyAxLjAyLTIuMjkgMS4zOUwxNi41IDE4SDE4bDMgMy4wMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzYXZlIj48cGF0aCBkPSJNMTcgM0g1Yy0xLjExIDAtMiAuOS0yIDJ2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWN2wtNC00em0tNSAxNmMtMS42NiAwLTMtMS4zNC0zLTNzMS4zNC0zIDMtMyAzIDEuMzQgMyAzLTEuMzQgMy0zIDN6bTMtMTBINVY1aDEwdjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic2NoZWR1bGUiPjxwYXRoIGQ9Ik0xMS45OSAyQzYuNDcgMiAyIDYuNDggMiAxMnM0LjQ3IDEwIDkuOTkgMTBDMTcuNTIgMjIgMjIgMTcuNTIgMjIgMTJTMTcuNTIgMiAxMS45OSAyek0xMiAyMGMtNC40MiAwLTgtMy41OC04LThzMy41OC04IDgtOCA4IDMuNTggOCA4LTMuNTggOC04IDh6bS41LTEzSDExdjZsNS4yNSAzLjE1Ljc1LTEuMjMtNC41LTIuNjd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic2VhcmNoIj48cGF0aCBkPSJNMTUuNSAxNGgtLjc5bC0uMjgtLjI3QzE1LjQxIDEyLjU5IDE2IDExLjExIDE2IDkuNSAxNiA1LjkxIDEzLjA5IDMgOS41IDNTMyA1LjkxIDMgOS41IDUuOTEgMTYgOS41IDE2YzEuNjEgMCAzLjA5LS41OSA0LjIzLTEuNTdsLjI3LjI4di43OWw1IDQuOTlMMjAuNDkgMTlsLTQuOTktNXptLTYgMEM3LjAxIDE0IDUgMTEuOTkgNSA5LjVTNy4wMSA1IDkuNSA1IDE0IDcuMDEgMTQgOS41IDExLjk5IDE0IDkuNSAxNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZWxlY3QtYWxsIj48cGF0aCBkPSJNMyA1aDJWM2MtMS4xIDAtMiAuOS0yIDJ6bTAgOGgydi0ySDN2MnptNCA4aDJ2LTJIN3Yyek0zIDloMlY3SDN2MnptMTAtNmgtMnYyaDJWM3ptNiAwdjJoMmMwLTEuMS0uOS0yLTItMnpNNSAyMXYtMkgzYzAgMS4xLjkgMiAyIDJ6bS0yLTRoMnYtMkgzdjJ6TTkgM0g3djJoMlYzem0yIDE4aDJ2LTJoLTJ2MnptOC04aDJ2LTJoLTJ2MnptMCA4YzEuMSAwIDItLjkgMi0yaC0ydjJ6bTAtMTJoMlY3aC0ydjJ6bTAgOGgydi0yaC0ydjJ6bS00IDRoMnYtMmgtMnYyem0wLTE2aDJWM2gtMnYyek03IDE3aDEwVjdIN3YxMHptMi04aDZ2Nkg5Vjl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic2VuZCI+PHBhdGggZD0iTTIuMDEgMjFMMjMgMTIgMi4wMSAzIDIgMTBsMTUgMi0xNSAyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzIj48cGF0aCBkPSJNMTkuNDMgMTIuOThjLjA0LS4zMi4wNy0uNjQuMDctLjk4cy0uMDMtLjY2LS4wNy0uOThsMi4xMS0xLjY1Yy4xOS0uMTUuMjQtLjQyLjEyLS42NGwtMi0zLjQ2Yy0uMTItLjIyLS4zOS0uMy0uNjEtLjIybC0yLjQ5IDFjLS41Mi0uNC0xLjA4LS43My0xLjY5LS45OGwtLjM4LTIuNjVDMTQuNDYgMi4xOCAxNC4yNSAyIDE0IDJoLTRjLS4yNSAwLS40Ni4xOC0uNDkuNDJsLS4zOCAyLjY1Yy0uNjEuMjUtMS4xNy41OS0xLjY5Ljk4bC0yLjQ5LTFjLS4yMy0uMDktLjQ5IDAtLjYxLjIybC0yIDMuNDZjLS4xMy4yMi0uMDcuNDkuMTIuNjRsMi4xMSAxLjY1Yy0uMDQuMzItLjA3LjY1LS4wNy45OHMuMDMuNjYuMDcuOThsLTIuMTEgMS42NWMtLjE5LjE1LS4yNC40Mi0uMTIuNjRsMiAzLjQ2Yy4xMi4yMi4zOS4zLjYxLjIybDIuNDktMWMuNTIuNCAxLjA4LjczIDEuNjkuOThsLjM4IDIuNjVjLjAzLjI0LjI0LjQyLjQ5LjQyaDRjLjI1IDAgLjQ2LS4xOC40OS0uNDJsLjM4LTIuNjVjLjYxLS4yNSAxLjE3LS41OSAxLjY5LS45OGwyLjQ5IDFjLjIzLjA5LjQ5IDAgLjYxLS4yMmwyLTMuNDZjLjEyLS4yMi4wNy0uNDktLjEyLS42NGwtMi4xMS0xLjY1ek0xMiAxNS41Yy0xLjkzIDAtMy41LTEuNTctMy41LTMuNXMxLjU3LTMuNSAzLjUtMy41IDMuNSAxLjU3IDMuNSAzLjUtMS41NyAzLjUtMy41IDMuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1hcHBsaWNhdGlvbnMiPjxwYXRoIGQ9Ik0xMiAxMGMtMS4xIDAtMiAuOS0yIDJzLjkgMiAyIDIgMi0uOSAyLTItLjktMi0yLTJ6bTctN0g1Yy0xLjExIDAtMiAuOS0yIDJ2MTRjMCAxLjEuODkgMiAyIDJoMTRjMS4xMSAwIDItLjkgMi0yVjVjMC0xLjEtLjg5LTItMi0yem0tMS43NSA5YzAgLjIzLS4wMi40Ni0uMDUuNjhsMS40OCAxLjE2Yy4xMy4xMS4xNy4zLjA4LjQ1bC0xLjQgMi40MmMtLjA5LjE1LS4yNy4yMS0uNDMuMTVsLTEuNzQtLjdjLS4zNi4yOC0uNzYuNTEtMS4xOC42OWwtLjI2IDEuODVjLS4wMy4xNy0uMTguMy0uMzUuM2gtMi44Yy0uMTcgMC0uMzItLjEzLS4zNS0uMjlsLS4yNi0xLjg1Yy0uNDMtLjE4LS44Mi0uNDEtMS4xOC0uNjlsLTEuNzQuN2MtLjE2LjA2LS4zNCAwLS40My0uMTVsLTEuNC0yLjQyYy0uMDktLjE1LS4wNS0uMzQuMDgtLjQ1bDEuNDgtMS4xNmMtLjAzLS4yMy0uMDUtLjQ2LS4wNS0uNjkgMC0uMjMuMDItLjQ2LjA1LS42OGwtMS40OC0xLjE2Yy0uMTMtLjExLS4xNy0uMy0uMDgtLjQ1bDEuNC0yLjQyYy4wOS0uMTUuMjctLjIxLjQzLS4xNWwxLjc0LjdjLjM2LS4yOC43Ni0uNTEgMS4xOC0uNjlsLjI2LTEuODVjLjAzLS4xNy4xOC0uMy4zNS0uM2gyLjhjLjE3IDAgLjMyLjEzLjM1LjI5bC4yNiAxLjg1Yy40My4xOC44Mi40MSAxLjE4LjY5bDEuNzQtLjdjLjE2LS4wNi4zNCAwIC40My4xNWwxLjQgMi40MmMuMDkuMTUuMDUuMzQtLjA4LjQ1bC0xLjQ4IDEuMTZjLjAzLjIzLjA1LjQ2LjA1LjY5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLWJhY2t1cC1yZXN0b3JlIj48cGF0aCBkPSJNMTQgMTJjMC0xLjEtLjktMi0yLTJzLTIgLjktMiAyIC45IDIgMiAyIDItLjkgMi0yem0tMi05Yy00Ljk3IDAtOSA0LjAzLTkgOUgwbDQgNCA0LTRINWMwLTMuODcgMy4xMy03IDctN3M3IDMuMTMgNyA3LTMuMTMgNy03IDdjLTEuNTEgMC0yLjkxLS40OS00LjA2LTEuM2wtMS40MiAxLjQ0QzguMDQgMjAuMyA5Ljk0IDIxIDEyIDIxYzQuOTcgMCA5LTQuMDMgOS05cy00LjAzLTktOS05eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLWJsdWV0b290aCI+PHBhdGggZD0iTTExIDI0aDJ2LTJoLTJ2MnptLTQgMGgydi0ySDd2MnptOCAwaDJ2LTJoLTJ2MnptMi43MS0xOC4yOUwxMiAwaC0xdjcuNTlMNi40MSAzIDUgNC40MSAxMC41OSAxMCA1IDE1LjU5IDYuNDEgMTcgMTEgMTIuNDFWMjBoMWw1LjcxLTUuNzEtNC4zLTQuMjkgNC4zLTQuMjl6TTEzIDMuODNsMS44OCAxLjg4TDEzIDcuNTlWMy44M3ptMS44OCAxMC40NkwxMyAxNi4xN3YtMy43NmwxLjg4IDEuODh6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic2V0dGluZ3MtYnJpZ2h0bmVzcyI+PHBhdGggZD0iTTIxIDNIM2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxOGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2LjAxSDNWNC45OWgxOHYxNC4wMnpNOCAxNmgyLjVsMS41IDEuNSAxLjUtMS41SDE2di0yLjVsMS41LTEuNS0xLjUtMS41VjhoLTIuNUwxMiA2LjUgMTAuNSA4SDh2Mi41TDYuNSAxMiA4IDEzLjVWMTZ6bTQtN2MxLjY2IDAgMyAxLjM0IDMgM3MtMS4zNCAzLTMgM1Y5eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLWNlbGwiPjxwYXRoIGQ9Ik03IDI0aDJ2LTJIN3Yyem00IDBoMnYtMmgtMnYyem00IDBoMnYtMmgtMnYyek0xNiAuMDFMOCAwQzYuOSAwIDYgLjkgNiAydjE2YzAgMS4xLjkgMiAyIDJoOGMxLjEgMCAyLS45IDItMlYyYzAtMS4xLS45LTEuOTktMi0xLjk5ek0xNiAxNkg4VjRoOHYxMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1ldGhlcm5ldCI+PHBhdGggZD0iTTcuNzcgNi43Nkw2LjIzIDUuNDguODIgMTJsNS40MSA2LjUyIDEuNTQtMS4yOEwzLjQyIDEybDQuMzUtNS4yNHpNNyAxM2gydi0ySDd2MnptMTAtMmgtMnYyaDJ2LTJ6bS02IDJoMnYtMmgtMnYyem02Ljc3LTcuNTJsLTEuNTQgMS4yOEwyMC41OCAxMmwtNC4zNSA1LjI0IDEuNTQgMS4yOEwyMy4xOCAxMmwtNS40MS02LjUyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLWlucHV0LWFudGVubmEiPjxwYXRoIGQ9Ik0xMiA1Yy0zLjg3IDAtNyAzLjEzLTcgN2gyYzAtMi43NiAyLjI0LTUgNS01czUgMi4yNCA1IDVoMmMwLTMuODctMy4xMy03LTctN3ptMSA5LjI5Yy44OC0uMzkgMS41LTEuMjYgMS41LTIuMjkgMC0xLjM4LTEuMTItMi41LTIuNS0yLjVTOS41IDEwLjYyIDkuNSAxMmMwIDEuMDIuNjIgMS45IDEuNSAyLjI5djMuM0w3LjU5IDIxIDkgMjIuNDFsMy0zIDMgM0wxNi40MSAyMSAxMyAxNy41OXYtMy4zek0xMiAxQzUuOTMgMSAxIDUuOTMgMSAxMmgyYzAtNC45NyA0LjAzLTkgOS05czkgNC4wMyA5IDloMmMwLTYuMDctNC45My0xMS0xMS0xMXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1pbnB1dC1jb21wb25lbnQiPjxwYXRoIGQ9Ik01IDJjMC0uNTUtLjQ1LTEtMS0xcy0xIC40NS0xIDF2NEgxdjZoNlY2SDVWMnptNCAxNGMwIDEuMy44NCAyLjQgMiAyLjgyVjIzaDJ2LTQuMThjMS4xNi0uNDEgMi0xLjUxIDItMi44MnYtMkg5djJ6bS04IDBjMCAxLjMuODQgMi40IDIgMi44MlYyM2gydi00LjE4QzYuMTYgMTguNCA3IDE3LjMgNyAxNnYtMkgxdjJ6TTIxIDZWMmMwLS41NS0uNDUtMS0xLTFzLTEgLjQ1LTEgMXY0aC0ydjZoNlY2aC0yem0tOC00YzAtLjU1LS40NS0xLTEtMXMtMSAuNDUtMSAxdjRIOXY2aDZWNmgtMlYyem00IDE0YzAgMS4zLjg0IDIuNCAyIDIuODJWMjNoMnYtNC4xOGMxLjE2LS40MSAyLTEuNTEgMi0yLjgydi0yaC02djJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic2V0dGluZ3MtaW5wdXQtY29tcG9zaXRlIj48cGF0aCBkPSJNNSAyYzAtLjU1LS40NS0xLTEtMXMtMSAuNDUtMSAxdjRIMXY2aDZWNkg1VjJ6bTQgMTRjMCAxLjMuODQgMi40IDIgMi44MlYyM2gydi00LjE4YzEuMTYtLjQxIDItMS41MSAyLTIuODJ2LTJIOXYyem0tOCAwYzAgMS4zLjg0IDIuNCAyIDIuODJWMjNoMnYtNC4xOEM2LjE2IDE4LjQgNyAxNy4zIDcgMTZ2LTJIMXYyek0yMSA2VjJjMC0uNTUtLjQ1LTEtMS0xcy0xIC40NS0xIDF2NGgtMnY2aDZWNmgtMnptLTgtNGMwLS41NS0uNDUtMS0xLTFzLTEgLjQ1LTEgMXY0SDl2Nmg2VjZoLTJWMnptNCAxNGMwIDEuMy44NCAyLjQgMiAyLjgyVjIzaDJ2LTQuMThjMS4xNi0uNDEgMi0xLjUxIDItMi44MnYtMmgtNnYyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLWlucHV0LWhkbWkiPjxwYXRoIGQ9Ik0xOCA3VjRjMC0xLjEtLjktMi0yLTJIOGMtMS4xIDAtMiAuOS0yIDJ2M0g1djZsMyA2djNoOHYtM2wzLTZWN2gtMXpNOCA0aDh2M2gtMlY1aC0xdjJoLTJWNWgtMXYySDhWNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1pbnB1dC1zdmlkZW8iPjxwYXRoIGQ9Ik04IDExLjVjMC0uODMtLjY3LTEuNS0xLjUtMS41UzUgMTAuNjcgNSAxMS41IDUuNjcgMTMgNi41IDEzIDggMTIuMzMgOCAxMS41em03LTVjMC0uODMtLjY3LTEuNS0xLjUtMS41aC0zQzkuNjcgNSA5IDUuNjcgOSA2LjVTOS42NyA4IDEwLjUgOGgzYy44MyAwIDEuNS0uNjcgMS41LTEuNXpNOC41IDE1Yy0uODMgMC0xLjUuNjctMS41IDEuNVM3LjY3IDE4IDguNSAxOHMxLjUtLjY3IDEuNS0xLjVTOS4zMyAxNSA4LjUgMTV6TTEyIDFDNS45MyAxIDEgNS45MyAxIDEyczQuOTMgMTEgMTEgMTEgMTEtNC45MyAxMS0xMVMxOC4wNyAxIDEyIDF6bTAgMjBjLTQuOTYgMC05LTQuMDQtOS05czQuMDQtOSA5LTkgOSA0LjA0IDkgOS00LjA0IDktOSA5em01LjUtMTFjLS44MyAwLTEuNS42Ny0xLjUgMS41cy42NyAxLjUgMS41IDEuNSAxLjUtLjY3IDEuNS0xLjUtLjY3LTEuNS0xLjUtMS41em0tMiA1Yy0uODMgMC0xLjUuNjctMS41IDEuNXMuNjcgMS41IDEuNSAxLjUgMS41LS42NyAxLjUtMS41LS42Ny0xLjUtMS41LTEuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1vdmVyc2NhbiI+PHBhdGggZD0iTTEyLjAxIDUuNUwxMCA4aDRsLTEuOTktMi41ek0xOCAxMHY0bDIuNS0xLjk5TDE4IDEwek02IDEwbC0yLjUgMi4wMUw2IDE0di00em04IDZoLTRsMi4wMSAyLjVMMTQgMTZ6bTctMTNIM2MtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxOGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yem0wIDE2LjAxSDNWNC45OWgxOHYxNC4wMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1waG9uZSI+PHBhdGggZD0iTTEzIDloLTJ2MmgyVjl6bTQgMGgtMnYyaDJWOXptMyA2LjVjLTEuMjUgMC0yLjQ1LS4yLTMuNTctLjU3LS4zNS0uMTEtLjc0LS4wMy0xLjAyLjI0bC0yLjIgMi4yYy0yLjgzLTEuNDQtNS4xNS0zLjc1LTYuNTktNi41OGwyLjItMi4yMWMuMjgtLjI3LjM2LS42Ni4yNS0xLjAxQzguNyA2LjQ1IDguNSA1LjI1IDguNSA0YzAtLjU1LS40NS0xLTEtMUg0Yy0uNTUgMC0xIC40NS0xIDEgMCA5LjM5IDcuNjEgMTcgMTcgMTcgLjU1IDAgMS0uNDUgMS0xdi0zLjVjMC0uNTUtLjQ1LTEtMS0xek0xOSA5djJoMlY5aC0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLXBvd2VyIj48cGF0aCBkPSJNNyAyNGgydi0ySDd2MnptNCAwaDJ2LTJoLTJ2MnptMi0yMmgtMnYxMGgyVjJ6bTMuNTYgMi40NGwtMS40NSAxLjQ1QzE2Ljg0IDYuOTQgMTggOC44MyAxOCAxMWMwIDMuMzEtMi42OSA2LTYgNnMtNi0yLjY5LTYtNmMwLTIuMTcgMS4xNi00LjA2IDIuODgtNS4xMkw3LjQ0IDQuNDRDNS4zNiA1Ljg4IDQgOC4yOCA0IDExYzAgNC40MiAzLjU4IDggOCA4czgtMy41OCA4LThjMC0yLjcyLTEuMzYtNS4xMi0zLjQ0LTYuNTZ6TTE1IDI0aDJ2LTJoLTJ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzZXR0aW5ncy1yZW1vdGUiPjxwYXRoIGQ9Ik0xNSA5SDljLS41NSAwLTEgLjQ1LTEgMXYxMmMwIC41NS40NSAxIDEgMWg2Yy41NSAwIDEtLjQ1IDEtMVYxMGMwLS41NS0uNDUtMS0xLTF6bS0zIDZjLTEuMSAwLTItLjktMi0ycy45LTIgMi0yIDIgLjkgMiAyLS45IDItMiAyek03LjA1IDYuMDVsMS40MSAxLjQxQzkuMzcgNi41NiAxMC42MiA2IDEyIDZzMi42My41NiAzLjU0IDEuNDZsMS40MS0xLjQxQzE1LjY4IDQuNzggMTMuOTMgNCAxMiA0cy0zLjY4Ljc4LTQuOTUgMi4wNXpNMTIgMEM4Ljk2IDAgNi4yMSAxLjIzIDQuMjIgMy4yMmwxLjQxIDEuNDFDNy4yNiAzLjAxIDkuNTEgMiAxMiAyczQuNzQgMS4wMSA2LjM2IDIuNjRsMS40MS0xLjQxQzE3Ljc5IDEuMjMgMTUuMDQgMCAxMiAweiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNldHRpbmdzLXZvaWNlIj48cGF0aCBkPSJNNyAyNGgydi0ySDd2MnptNS0xMWMxLjY2IDAgMi45OS0xLjM0IDIuOTktM0wxNSA0YzAtMS42Ni0xLjM0LTMtMy0zUzkgMi4zNCA5IDR2NmMwIDEuNjYgMS4zNCAzIDMgM3ptLTEgMTFoMnYtMmgtMnYyem00IDBoMnYtMmgtMnYyem00LTE0aC0xLjdjMCAzLTIuNTQgNS4xLTUuMyA1LjFTNi43IDEzIDYuNyAxMEg1YzAgMy40MSAyLjcyIDYuMjMgNiA2LjcyVjIwaDJ2LTMuMjhjMy4yOC0uNDkgNi0zLjMxIDYtNi43MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzaG9wIj48cGF0aCBkPSJNMTYgNlY0YzAtMS4xMS0uODktMi0yLTJoLTRjLTEuMTEgMC0yIC44OS0yIDJ2MkgydjEzYzAgMS4xMS44OSAyIDIgMmgxNmMxLjExIDAgMi0uODkgMi0yVjZoLTZ6bS02LTJoNHYyaC00VjR6TTkgMThWOWw3LjUgNEw5IDE4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNob3AtdHdvIj48cGF0aCBkPSJNMyA5SDF2MTFjMCAxLjExLjg5IDIgMiAyaDE0YzEuMTEgMCAyLS44OSAyLTJIM1Y5em0xNS00VjNjMC0xLjExLS44OS0yLTItMmgtNGMtMS4xMSAwLTIgLjg5LTIgMnYySDV2MTFjMCAxLjExLjg5IDIgMiAyaDE0YzEuMTEgMCAyLS44OSAyLTJWNWgtNXptLTYtMmg0djJoLTRWM3ptMCAxMlY4bDUuNSAzLTUuNSA0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNob3BwaW5nLWJhc2tldCI+PHBhdGggZD0iTTE3LjIxIDlsLTQuMzgtNi41NmMtLjE5LS4yOC0uNTEtLjQyLS44My0uNDItLjMyIDAtLjY0LjE0LS44My40M0w2Ljc5IDlIMmMtLjU1IDAtMSAuNDUtMSAxIDAgLjA5LjAxLjE4LjA0LjI3bDIuNTQgOS4yN2MuMjMuODQgMSAxLjQ2IDEuOTIgMS40NmgxM2MuOTIgMCAxLjY5LS42MiAxLjkzLTEuNDZsMi41NC05LjI3TDIzIDEwYzAtLjU1LS40NS0xLTEtMWgtNC43OXpNOSA5bDMtNC40TDE1IDlIOXptMyA4Yy0xLjEgMC0yLS45LTItMnMuOS0yIDItMiAyIC45IDIgMi0uOSAyLTIgMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzaG9wcGluZy1jYXJ0Ij48cGF0aCBkPSJNNyAxOGMtMS4xIDAtMS45OS45LTEuOTkgMlM1LjkgMjIgNyAyMnMyLS45IDItMi0uOS0yLTItMnpNMSAydjJoMmwzLjYgNy41OS0xLjM1IDIuNDVjLS4xNi4yOC0uMjUuNjEtLjI1Ljk2IDAgMS4xLjkgMiAyIDJoMTJ2LTJINy40MmMtLjE0IDAtLjI1LS4xMS0uMjUtLjI1bC4wMy0uMTIuOS0xLjYzaDcuNDVjLjc1IDAgMS40MS0uNDEgMS43NS0xLjAzbDMuNTgtNi40OWMuMDgtLjE0LjEyLS4zMS4xMi0uNDggMC0uNTUtLjQ1LTEtMS0xSDUuMjFsLS45NC0ySDF6bTE2IDE2Yy0xLjEgMC0xLjk5LjktMS45OSAycy44OSAyIDEuOTkgMiAyLS45IDItMi0uOS0yLTItMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzb3J0Ij48cGF0aCBkPSJNMyAxOGg2di0ySDN2MnpNMyA2djJoMThWNkgzem0wIDdoMTJ2LTJIM3YyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InNwZWFrZXItbm90ZXMiPjxwYXRoIGQ9Ik0yMCAySDRjLTEuMSAwLTEuOTkuOS0xLjk5IDJMMiAyMmw0LTRoMTRjMS4xIDAgMi0uOSAyLTJWNGMwLTEuMS0uOS0yLTItMnpNOCAxNEg2di0yaDJ2MnptMC0zSDZWOWgydjJ6bTAtM0g2VjZoMnYyem03IDZoLTV2LTJoNXYyem0zLTNoLThWOWg4djJ6bTAtM2gtOFY2aDh2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJzcGVha2VyLW5vdGVzLW9mZiI+PHBhdGggZD0iTTEwLjU0IDExbC0uNTQtLjU0TDcuNTQgOCA2IDYuNDYgMi4zOCAyLjg0IDEuMjcgMS43MyAwIDNsMi4wMSAyLjAxTDIgMjJsNC00aDlsNS43MyA1LjczTDIyIDIyLjQ2IDE3LjU0IDE4bC03LTd6TTggMTRINnYtMmgydjJ6bS0yLTNWOWwyIDJINnptMTQtOUg0LjA4TDEwIDcuOTJWNmg4djJoLTcuOTJsMSAxSDE4djJoLTQuOTJsNi45OSA2Ljk5QzIxLjE0IDE3Ljk1IDIyIDE3LjA4IDIyIDE2VjRjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3BlbGxjaGVjayI+PHBhdGggZD0iTTEyLjQ1IDE2aDIuMDlMOS40MyAzSDcuNTdMMi40NiAxNmgyLjA5bDEuMTItM2g1LjY0bDEuMTQgM3ptLTYuMDItNUw4LjUgNS40OCAxMC41NyAxMUg2LjQzem0xNS4xNi41OWwtOC4wOSA4LjA5TDkuODMgMTZsLTEuNDEgMS40MSA1LjA5IDUuMDlMMjMgMTNsLTEuNDEtMS40MXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzdGFyIj48cGF0aCBkPSJNMTIgMTcuMjdMMTguMTggMjFsLTEuNjQtNy4wM0wyMiA5LjI0bC03LjE5LS42MUwxMiAyIDkuMTkgOC42MyAyIDkuMjRsNS40NiA0LjczTDUuODIgMjF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3Rhci1ib3JkZXIiPjxwYXRoIGQ9Ik0yMiA5LjI0bC03LjE5LS42MkwxMiAyIDkuMTkgOC42MyAyIDkuMjRsNS40NiA0LjczTDUuODIgMjEgMTIgMTcuMjcgMTguMTggMjFsLTEuNjMtNy4wM0wyMiA5LjI0ek0xMiAxNS40bC0zLjc2IDIuMjcgMS00LjI4LTMuMzItMi44OCA0LjM4LS4zOEwxMiA2LjFsMS43MSA0LjA0IDQuMzguMzgtMy4zMiAyLjg4IDEgNC4yOEwxMiAxNS40eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN0YXItaGFsZiI+PHBhdGggZD0iTTIyIDkuMjRsLTcuMTktLjYyTDEyIDIgOS4xOSA4LjYzIDIgOS4yNGw1LjQ2IDQuNzNMNS44MiAyMSAxMiAxNy4yNyAxOC4xOCAyMWwtMS42My03LjAzTDIyIDkuMjR6TTEyIDE1LjRWNi4xbDEuNzEgNC4wNCA0LjM4LjM4LTMuMzIgMi44OCAxIDQuMjhMMTIgMTUuNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzdGFycyI+PHBhdGggZD0iTTExLjk5IDJDNi40NyAyIDIgNi40OCAyIDEyczQuNDcgMTAgOS45OSAxMEMxNy41MiAyMiAyMiAxNy41MiAyMiAxMlMxNy41MiAyIDExLjk5IDJ6bTQuMjQgMTZMMTIgMTUuNDUgNy43NyAxOGwxLjEyLTQuODEtMy43My0zLjIzIDQuOTItLjQyTDEyIDVsMS45MiA0LjUzIDQuOTIuNDItMy43MyAzLjIzTDE2LjIzIDE4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN0b3JlIj48cGF0aCBkPSJNMjAgNEg0djJoMTZWNHptMSAxMHYtMmwtMS01SDRsLTEgNXYyaDF2NmgxMHYtNmg0djZoMnYtNmgxem0tOSA0SDZ2LTRoNnY0eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN1YmRpcmVjdG9yeS1hcnJvdy1sZWZ0Ij48cGF0aCBkPSJNMTEgOWwxLjQyIDEuNDJMOC44MyAxNEgxOFY0aDJ2MTJIOC44M2wzLjU5IDMuNThMMTEgMjFsLTYtNiA2LTZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3ViZGlyZWN0b3J5LWFycm93LXJpZ2h0Ij48cGF0aCBkPSJNMTkgMTVsLTYgNi0xLjQyLTEuNDJMMTUuMTcgMTZINFY0aDJ2MTBoOS4xN2wtMy41OS0zLjU4TDEzIDlsNiA2eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN1YmplY3QiPjxwYXRoIGQ9Ik0xNCAxN0g0djJoMTB2LTJ6bTYtOEg0djJoMTZWOXpNNCAxNWgxNnYtMkg0djJ6TTQgNXYyaDE2VjVINHoiPjwvcGF0aD48L2c+CjxnIGlkPSJzdXBlcnZpc29yLWFjY291bnQiPjxwYXRoIGQ9Ik0xNi41IDEyYzEuMzggMCAyLjQ5LTEuMTIgMi40OS0yLjVTMTcuODggNyAxNi41IDdDMTUuMTIgNyAxNCA4LjEyIDE0IDkuNXMxLjEyIDIuNSAyLjUgMi41ek05IDExYzEuNjYgMCAyLjk5LTEuMzQgMi45OS0zUzEwLjY2IDUgOSA1QzcuMzQgNSA2IDYuMzQgNiA4czEuMzQgMyAzIDN6bTcuNSAzYy0xLjgzIDAtNS41LjkyLTUuNSAyLjc1VjE5aDExdi0yLjI1YzAtMS44My0zLjY3LTIuNzUtNS41LTIuNzV6TTkgMTNjLTIuMzMgMC03IDEuMTctNyAzLjVWMTloN3YtMi4yNWMwLS44NS4zMy0yLjM0IDIuMzctMy40N0MxMC41IDEzLjEgOS42NiAxMyA5IDEzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InN3YXAtaG9yaXoiPjxwYXRoIGQ9Ik02Ljk5IDExTDMgMTVsMy45OSA0di0zSDE0di0ySDYuOTl2LTN6TTIxIDlsLTMuOTktNHYzSDEwdjJoNy4wMXYzTDIxIDl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3dhcC12ZXJ0Ij48cGF0aCBkPSJNMTYgMTcuMDFWMTBoLTJ2Ny4wMWgtM0wxNSAyMWw0LTMuOTloLTN6TTkgM0w1IDYuOTloM1YxNGgyVjYuOTloM0w5IDN6Ij48L3BhdGg+PC9nPgo8ZyBpZD0ic3dhcC12ZXJ0aWNhbC1jaXJjbGUiPjxwYXRoIGQ9Ik0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyek02LjUgOUwxMCA1LjUgMTMuNSA5SDExdjRIOVY5SDYuNXptMTEgNkwxNCAxOC41IDEwLjUgMTVIMTN2LTRoMnY0aDIuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJzeXN0ZW0tdXBkYXRlLWFsdCI+PHBhdGggZD0iTTEyIDE2LjVsNC00aC0zdi05aC0ydjlIOGw0IDR6bTktMTNoLTZ2MS45OWg2djE0LjAzSDNWNS40OWg2VjMuNUgzYy0xLjEgMC0yIC45LTIgMnYxNGMwIDEuMS45IDIgMiAyaDE4YzEuMSAwIDItLjkgMi0ydi0xNGMwLTEuMS0uOS0yLTItMnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0YWIiPjxwYXRoIGQ9Ik0yMSAzSDNjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMThjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxNkgzVjVoMTB2NGg4djEweiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRhYi11bnNlbGVjdGVkIj48cGF0aCBkPSJNMSA5aDJWN0gxdjJ6bTAgNGgydi0ySDF2MnptMC04aDJWM2MtMS4xIDAtMiAuOS0yIDJ6bTggMTZoMnYtMkg5djJ6bS04LTRoMnYtMkgxdjJ6bTIgNHYtMkgxYzAgMS4xLjkgMiAyIDJ6TTIxIDNoLTh2NmgxMFY1YzAtMS4xLS45LTItMi0yem0wIDE0aDJ2LTJoLTJ2MnpNOSA1aDJWM0g5djJ6TTUgMjFoMnYtMkg1djJ6TTUgNWgyVjNINXYyem0xNiAxNmMxLjEgMCAyLS45IDItMmgtMnYyem0wLThoMnYtMmgtMnYyem0tOCA4aDJ2LTJoLTJ2MnptNCAwaDJ2LTJoLTJ2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0ZXh0LWZvcm1hdCI+PHBhdGggZD0iTTUgMTd2MmgxNHYtMkg1em00LjUtNC4yaDVsLjkgMi4yaDIuMUwxMi43NSA0aC0xLjVMNi41IDE1aDIuMWwuOS0yLjJ6TTEyIDUuOThMMTMuODcgMTFoLTMuNzRMMTIgNS45OHoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0aGVhdGVycyI+PHBhdGggZD0iTTE4IDN2MmgtMlYzSDh2Mkg2VjNINHYxOGgydi0yaDJ2Mmg4di0yaDJ2MmgyVjNoLTJ6TTggMTdINnYtMmgydjJ6bTAtNEg2di0yaDJ2MnptMC00SDZWN2gydjJ6bTEwIDhoLTJ2LTJoMnYyem0wLTRoLTJ2LTJoMnYyem0wLTRoLTJWN2gydjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idGh1bWItZG93biI+PHBhdGggZD0iTTE1IDNINmMtLjgzIDAtMS41NC41LTEuODQgMS4yMmwtMy4wMiA3LjA1Yy0uMDkuMjMtLjE0LjQ3LS4xNC43M3YxLjkxbC4wMS4wMUwxIDE0YzAgMS4xLjkgMiAyIDJoNi4zMWwtLjk1IDQuNTctLjAzLjMyYzAgLjQxLjE3Ljc5LjQ0IDEuMDZMOS44MyAyM2w2LjU5LTYuNTljLjM2LS4zNi41OC0uODYuNTgtMS40MVY1YzAtMS4xLS45LTItMi0yem00IDB2MTJoNFYzaC00eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRodW1iLXVwIj48cGF0aCBkPSJNMSAyMWg0VjlIMXYxMnptMjItMTFjMC0xLjEtLjktMi0yLTJoLTYuMzFsLjk1LTQuNTcuMDMtLjMyYzAtLjQxLS4xNy0uNzktLjQ0LTEuMDZMMTQuMTcgMSA3LjU5IDcuNTlDNy4yMiA3Ljk1IDcgOC40NSA3IDl2MTBjMCAxLjEuOSAyIDIgMmg5Yy44MyAwIDEuNTQtLjUgMS44NC0xLjIybDMuMDItNy4wNWMuMDktLjIzLjE0LS40Ny4xNC0uNzN2LTEuOTFsLS4wMS0uMDFMMjMgMTB6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idGh1bWJzLXVwLWRvd24iPjxwYXRoIGQ9Ik0xMiA2YzAtLjU1LS40NS0xLTEtMUg1LjgybC42Ni0zLjE4LjAyLS4yM2MwLS4zMS0uMTMtLjU5LS4zMy0uOEw1LjM4IDAgLjQ0IDQuOTRDLjE3IDUuMjEgMCA1LjU5IDAgNnY2LjVjMCAuODMuNjcgMS41IDEuNSAxLjVoNi43NWMuNjIgMCAxLjE1LS4zOCAxLjM4LS45MWwyLjI2LTUuMjljLjA3LS4xNy4xMS0uMzYuMTEtLjU1VjZ6bTEwLjUgNGgtNi43NWMtLjYyIDAtMS4xNS4zOC0xLjM4LjkxbC0yLjI2IDUuMjljLS4wNy4xNy0uMTEuMzYtLjExLjU1VjE4YzAgLjU1LjQ1IDEgMSAxaDUuMThsLS42NiAzLjE4LS4wMi4yNGMwIC4zMS4xMy41OS4zMy44bC43OS43OCA0Ljk0LTQuOTRjLjI3LS4yNy40NC0uNjUuNDQtMS4wNnYtNi41YzAtLjgzLS42Ny0xLjUtMS41LTEuNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0aW1lbGluZSI+PHBhdGggZD0iTTIzIDhjMCAxLjEtLjkgMi0yIDItLjE4IDAtLjM1LS4wMi0uNTEtLjA3bC0zLjU2IDMuNTVjLjA1LjE2LjA3LjM0LjA3LjUyIDAgMS4xLS45IDItMiAycy0yLS45LTItMmMwLS4xOC4wMi0uMzYuMDctLjUybC0yLjU1LTIuNTVjLS4xNi4wNS0uMzQuMDctLjUyLjA3cy0uMzYtLjAyLS41Mi0uMDdsLTQuNTUgNC41NmMuMDUuMTYuMDcuMzMuMDcuNTEgMCAxLjEtLjkgMi0yIDJzLTItLjktMi0yIC45LTIgMi0yYy4xOCAwIC4zNS4wMi41MS4wN2w0LjU2LTQuNTVDOC4wMiA5LjM2IDggOS4xOCA4IDljMC0xLjEuOS0yIDItMnMyIC45IDIgMmMwIC4xOC0uMDIuMzYtLjA3LjUybDIuNTUgMi41NWMuMTYtLjA1LjM0LS4wNy41Mi0uMDdzLjM2LjAyLjUyLjA3bDMuNTUtMy41NkMxOS4wMiA4LjM1IDE5IDguMTggMTkgOGMwLTEuMS45LTIgMi0yczIgLjkgMiAyeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRvYyI+PHBhdGggZD0iTTMgOWgxNFY3SDN2MnptMCA0aDE0di0ySDN2MnptMCA0aDE0di0ySDN2MnptMTYgMGgydi0yaC0ydjJ6bTAtMTB2MmgyVjdoLTJ6bTAgNmgydi0yaC0ydjJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idG9kYXkiPjxwYXRoIGQ9Ik0xOSAzaC0xVjFoLTJ2Mkg4VjFINnYySDVjLTEuMTEgMC0xLjk5LjktMS45OSAyTDMgMTljMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnptMCAxNkg1VjhoMTR2MTF6TTcgMTBoNXY1SDd6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idG9sbCI+PHBhdGggZD0iTTE1IDRjLTQuNDIgMC04IDMuNTgtOCA4czMuNTggOCA4IDggOC0zLjU4IDgtOC0zLjU4LTgtOC04em0wIDE0Yy0zLjMxIDAtNi0yLjY5LTYtNnMyLjY5LTYgNi02IDYgMi42OSA2IDYtMi42OSA2LTYgNnpNMyAxMmMwLTIuNjEgMS42Ny00LjgzIDQtNS42NVY0LjI2QzMuNTUgNS4xNSAxIDguMjcgMSAxMnMyLjU1IDYuODUgNiA3Ljc0di0yLjA5Yy0yLjMzLS44Mi00LTMuMDQtNC01LjY1eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRvdWNoLWFwcCI+PHBhdGggZD0iTTkgMTEuMjRWNy41QzkgNi4xMiAxMC4xMiA1IDExLjUgNVMxNCA2LjEyIDE0IDcuNXYzLjc0YzEuMjEtLjgxIDItMi4xOCAyLTMuNzRDMTYgNS4wMSAxMy45OSAzIDExLjUgM1M3IDUuMDEgNyA3LjVjMCAxLjU2Ljc5IDIuOTMgMiAzLjc0em05Ljg0IDQuNjNsLTQuNTQtMi4yNmMtLjE3LS4wNy0uMzUtLjExLS41NC0uMTFIMTN2LTZjMC0uODMtLjY3LTEuNS0xLjUtMS41UzEwIDYuNjcgMTAgNy41djEwLjc0bC0zLjQzLS43MmMtLjA4LS4wMS0uMTUtLjAzLS4yNC0uMDMtLjMxIDAtLjU5LjEzLS43OS4zM2wtLjc5LjggNC45NCA0Ljk0Yy4yNy4yNy42NS40NCAxLjA2LjQ0aDYuNzljLjc1IDAgMS4zMy0uNTUgMS40NC0xLjI4bC43NS01LjI3Yy4wMS0uMDcuMDItLjE0LjAyLS4yIDAtLjYyLS4zOC0xLjE2LS45MS0xLjM4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRyYWNrLWNoYW5nZXMiPjxwYXRoIGQ9Ik0xOS4wNyA0LjkzbC0xLjQxIDEuNDFDMTkuMSA3Ljc5IDIwIDkuNzkgMjAgMTJjMCA0LjQyLTMuNTggOC04IDhzLTgtMy41OC04LThjMC00LjA4IDMuMDUtNy40NCA3LTcuOTN2Mi4wMkM4LjE2IDYuNTcgNiA5LjAzIDYgMTJjMCAzLjMxIDIuNjkgNiA2IDZzNi0yLjY5IDYtNmMwLTEuNjYtLjY3LTMuMTYtMS43Ni00LjI0bC0xLjQxIDEuNDFDMTUuNTUgOS45IDE2IDEwLjkgMTYgMTJjMCAyLjIxLTEuNzkgNC00IDRzLTQtMS43OS00LTRjMC0xLjg2IDEuMjgtMy40MSAzLTMuODZ2Mi4xNGMtLjYuMzUtMSAuOTgtMSAxLjcyIDAgMS4xLjkgMiAyIDJzMi0uOSAyLTJjMC0uNzQtLjQtMS4zOC0xLTEuNzJWMmgtMUM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwYzAtMi43Ni0xLjEyLTUuMjYtMi45My03LjA3eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InRyYW5zbGF0ZSI+PHBhdGggZD0iTTEyLjg3IDE1LjA3bC0yLjU0LTIuNTEuMDMtLjAzYzEuNzQtMS45NCAyLjk4LTQuMTcgMy43MS02LjUzSDE3VjRoLTdWMkg4djJIMXYxLjk5aDExLjE3QzExLjUgNy45MiAxMC40NCA5Ljc1IDkgMTEuMzUgOC4wNyAxMC4zMiA3LjMgOS4xOSA2LjY5IDhoLTJjLjczIDEuNjMgMS43MyAzLjE3IDIuOTggNC41NmwtNS4wOSA1LjAyTDQgMTlsNS01IDMuMTEgMy4xMS43Ni0yLjA0ek0xOC41IDEwaC0yTDEyIDIyaDJsMS4xMi0zaDQuNzVMMjEgMjJoMmwtNC41LTEyem0tMi42MiA3bDEuNjItNC4zM0wxOS4xMiAxN2gtMy4yNHoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0cmVuZGluZy1kb3duIj48cGF0aCBkPSJNMTYgMThsMi4yOS0yLjI5LTQuODgtNC44OC00IDRMMiA3LjQxIDMuNDEgNmw2IDYgNC00IDYuMyA2LjI5TDIyIDEydjZ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idHJlbmRpbmctZmxhdCI+PHBhdGggZD0iTTIyIDEybC00LTR2M0gzdjJoMTV2M3oiPjwvcGF0aD48L2c+CjxnIGlkPSJ0cmVuZGluZy11cCI+PHBhdGggZD0iTTE2IDZsMi4yOSAyLjI5LTQuODggNC44OC00LTRMMiAxNi41OSAzLjQxIDE4bDYtNiA0IDQgNi4zLTYuMjlMMjIgMTJWNnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ0dXJuZWQtaW4iPjxwYXRoIGQ9Ik0xNyAzSDdjLTEuMSAwLTEuOTkuOS0xLjk5IDJMNSAyMWw3LTMgNyAzVjVjMC0xLjEtLjktMi0yLTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idHVybmVkLWluLW5vdCI+PHBhdGggZD0iTTE3IDNIN2MtMS4xIDAtMS45OS45LTEuOTkgMkw1IDIxbDctMyA3IDNWNWMwLTEuMS0uOS0yLTItMnptMCAxNWwtNS0yLjE4TDcgMThWNWgxMHYxM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJ1bmFyY2hpdmUiPjxwYXRoIGQ9Ik0yMC41NSA1LjIybC0xLjM5LTEuNjhDMTguODggMy4yMSAxOC40NyAzIDE4IDNINmMtLjQ3IDAtLjg4LjIxLTEuMTUuNTVMMy40NiA1LjIyQzMuMTcgNS41NyAzIDYuMDEgMyA2LjVWMTljMCAxLjEuODkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNi41YzAtLjQ5LS4xNy0uOTMtLjQ1LTEuMjh6TTEyIDkuNWw1LjUgNS41SDE0djJoLTR2LTJINi41TDEyIDkuNXpNNS4xMiA1bC44Mi0xaDEybC45MyAxSDUuMTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idW5kbyI+PHBhdGggZD0iTTEyLjUgOGMtMi42NSAwLTUuMDUuOTktNi45IDIuNkwyIDd2OWg5bC0zLjYyLTMuNjJjMS4zOS0xLjE2IDMuMTYtMS44OCA1LjEyLTEuODggMy41NCAwIDYuNTUgMi4zMSA3LjYgNS41bDIuMzctLjc4QzIxLjA4IDExLjAzIDE3LjE1IDggMTIuNSA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InVuZm9sZC1sZXNzIj48cGF0aCBkPSJNNy40MSAxOC41OUw4LjgzIDIwIDEyIDE2LjgzIDE1LjE3IDIwbDEuNDEtMS40MUwxMiAxNGwtNC41OSA0LjU5em05LjE4LTEzLjE4TDE1LjE3IDQgMTIgNy4xNyA4LjgzIDQgNy40MSA1LjQxIDEyIDEwbDQuNTktNC41OXoiPjwvcGF0aD48L2c+CjxnIGlkPSJ1bmZvbGQtbW9yZSI+PHBhdGggZD0iTTEyIDUuODNMMTUuMTcgOWwxLjQxLTEuNDFMMTIgMyA3LjQxIDcuNTkgOC44MyA5IDEyIDUuODN6bTAgMTIuMzRMOC44MyAxNWwtMS40MSAxLjQxTDEyIDIxbDQuNTktNC41OUwxNS4xNyAxNSAxMiAxOC4xN3oiPjwvcGF0aD48L2c+CjxnIGlkPSJ1cGRhdGUiPjxwYXRoIGQ9Ik0yMSAxMC4xMmgtNi43OGwyLjc0LTIuODJjLTIuNzMtMi43LTcuMTUtMi44LTkuODgtLjEtMi43MyAyLjcxLTIuNzMgNy4wOCAwIDkuNzkgMi43MyAyLjcxIDcuMTUgMi43MSA5Ljg4IDBDMTguMzIgMTUuNjUgMTkgMTQuMDggMTkgMTIuMWgyYzAgMS45OC0uODggNC41NS0yLjY0IDYuMjktMy41MSAzLjQ4LTkuMjEgMy40OC0xMi43MiAwLTMuNS0zLjQ3LTMuNTMtOS4xMS0uMDItMTIuNTggMy41MS0zLjQ3IDkuMTQtMy40NyAxMi42NSAwTDIxIDN2Ny4xMnpNMTIuNSA4djQuMjVsMy41IDIuMDgtLjcyIDEuMjFMMTEgMTNWOGgxLjV6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmVyaWZpZWQtdXNlciI+PHBhdGggZD0iTTEyIDFMMyA1djZjMCA1LjU1IDMuODQgMTAuNzQgOSAxMiA1LjE2LTEuMjYgOS02LjQ1IDktMTJWNWwtOS00em0tMiAxNmwtNC00IDEuNDEtMS40MUwxMCAxNC4xN2w2LjU5LTYuNTlMMTggOWwtOCA4eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZXctYWdlbmRhIj48cGF0aCBkPSJNMjAgMTNIM2MtLjU1IDAtMSAuNDUtMSAxdjZjMCAuNTUuNDUgMSAxIDFoMTdjLjU1IDAgMS0uNDUgMS0xdi02YzAtLjU1LS40NS0xLTEtMXptMC0xMEgzYy0uNTUgMC0xIC40NS0xIDF2NmMwIC41NS40NSAxIDEgMWgxN2MuNTUgMCAxLS40NSAxLTFWNGMwLS41NS0uNDUtMS0xLTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlldy1hcnJheSI+PHBhdGggZD0iTTQgMThoM1Y1SDR2MTN6TTE4IDV2MTNoM1Y1aC0zek04IDE4aDlWNUg4djEzeiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZXctY2Fyb3VzZWwiPjxwYXRoIGQ9Ik03IDE5aDEwVjRIN3YxNXptLTUtMmg0VjZIMnYxMXpNMTggNnYxMWg0VjZoLTR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlldy1jb2x1bW4iPjxwYXRoIGQ9Ik0xMCAxOGg1VjVoLTV2MTN6bS02IDBoNVY1SDR2MTN6TTE2IDV2MTNoNVY1aC01eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZXctZGF5Ij48cGF0aCBkPSJNMiAyMWgxOXYtM0gydjN6TTIwIDhIM2MtLjU1IDAtMSAuNDUtMSAxdjZjMCAuNTUuNDUgMSAxIDFoMTdjLjU1IDAgMS0uNDUgMS0xVjljMC0uNTUtLjQ1LTEtMS0xek0yIDN2M2gxOVYzSDJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlldy1oZWFkbGluZSI+PHBhdGggZD0iTTQgMTVoMTZ2LTJINHYyem0wIDRoMTZ2LTJINHYyem0wLThoMTZWOUg0djJ6bTAtNnYyaDE2VjVINHoiPjwvcGF0aD48L2c+CjxnIGlkPSJ2aWV3LWxpc3QiPjxwYXRoIGQ9Ik00IDE0aDR2LTRINHY0em0wIDVoNHYtNEg0djR6TTQgOWg0VjVINHY0em01IDVoMTJ2LTRIOXY0em0wIDVoMTJ2LTRIOXY0ek05IDV2NGgxMlY1SDl6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlldy1tb2R1bGUiPjxwYXRoIGQ9Ik00IDExaDVWNUg0djZ6bTAgN2g1di02SDR2NnptNiAwaDV2LTZoLTV2NnptNiAwaDV2LTZoLTV2NnptLTYtN2g1VjVoLTV2NnptNi02djZoNVY1aC01eiI+PC9wYXRoPjwvZz4KPGcgaWQ9InZpZXctcXVpbHQiPjxwYXRoIGQ9Ik0xMCAxOGg1di02aC01djZ6bS02IDBoNVY1SDR2MTN6bTEyIDBoNXYtNmgtNXY2ek0xMCA1djZoMTFWNUgxMHoiPjwvcGF0aD48L2c+CjxnIGlkPSJ2aWV3LXN0cmVhbSI+PHBhdGggZD0iTTQgMThoMTd2LTZINHY2ek00IDV2NmgxN1Y1SDR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlldy13ZWVrIj48cGF0aCBkPSJNNiA1SDNjLS41NSAwLTEgLjQ1LTEgMXYxMmMwIC41NS40NSAxIDEgMWgzYy41NSAwIDEtLjQ1IDEtMVY2YzAtLjU1LS40NS0xLTEtMXptMTQgMGgtM2MtLjU1IDAtMSAuNDUtMSAxdjEyYzAgLjU1LjQ1IDEgMSAxaDNjLjU1IDAgMS0uNDUgMS0xVjZjMC0uNTUtLjQ1LTEtMS0xem0tNyAwaC0zYy0uNTUgMC0xIC40NS0xIDF2MTJjMCAuNTUuNDUgMSAxIDFoM2MuNTUgMCAxLS40NSAxLTFWNmMwLS41NS0uNDUtMS0xLTF6Ij48L3BhdGg+PC9nPgo8ZyBpZD0idmlzaWJpbGl0eSI+PHBhdGggZD0iTTEyIDQuNUM3IDQuNSAyLjczIDcuNjEgMSAxMmMxLjczIDQuMzkgNiA3LjUgMTEgNy41czkuMjctMy4xMSAxMS03LjVjLTEuNzMtNC4zOS02LTcuNS0xMS03LjV6TTEyIDE3Yy0yLjc2IDAtNS0yLjI0LTUtNXMyLjI0LTUgNS01IDUgMi4yNCA1IDUtMi4yNCA1LTUgNXptMC04Yy0xLjY2IDAtMyAxLjM0LTMgM3MxLjM0IDMgMyAzIDMtMS4zNCAzLTMtMS4zNC0zLTMtM3oiPjwvcGF0aD48L2c+CjxnIGlkPSJ2aXNpYmlsaXR5LW9mZiI+PHBhdGggZD0iTTEyIDdjMi43NiAwIDUgMi4yNCA1IDUgMCAuNjUtLjEzIDEuMjYtLjM2IDEuODNsMi45MiAyLjkyYzEuNTEtMS4yNiAyLjctMi44OSAzLjQzLTQuNzUtMS43My00LjM5LTYtNy41LTExLTcuNS0xLjQgMC0yLjc0LjI1LTMuOTguN2wyLjE2IDIuMTZDMTAuNzQgNy4xMyAxMS4zNSA3IDEyIDd6TTIgNC4yN2wyLjI4IDIuMjguNDYuNDZDMy4wOCA4LjMgMS43OCAxMC4wMiAxIDEyYzEuNzMgNC4zOSA2IDcuNSAxMSA3LjUgMS41NSAwIDMuMDMtLjMgNC4zOC0uODRsLjQyLjQyTDE5LjczIDIyIDIxIDIwLjczIDMuMjcgMyAyIDQuMjd6TTcuNTMgOS44bDEuNTUgMS41NWMtLjA1LjIxLS4wOC40My0uMDguNjUgMCAxLjY2IDEuMzQgMyAzIDMgLjIyIDAgLjQ0LS4wMy42NS0uMDhsMS41NSAxLjU1Yy0uNjcuMzMtMS40MS41My0yLjIuNTMtMi43NiAwLTUtMi4yNC01LTUgMC0uNzkuMi0xLjUzLjUzLTIuMnptNC4zMS0uNzhsMy4xNSAzLjE1LjAyLS4xNmMwLTEuNjYtMS4zNC0zLTMtM2wtLjE3LjAxeiI+PC9wYXRoPjwvZz4KPGcgaWQ9Indhcm5pbmciPjxwYXRoIGQ9Ik0xIDIxaDIyTDEyIDIgMSAyMXptMTItM2gtMnYtMmgydjJ6bTAtNGgtMnYtNGgydjR6Ij48L3BhdGg+PC9nPgo8ZyBpZD0id2F0Y2gtbGF0ZXIiPjxwYXRoIGQ9Ik0xMiAyQzYuNSAyIDIgNi41IDIgMTJzNC41IDEwIDEwIDEwIDEwLTQuNSAxMC0xMFMxNy41IDIgMTIgMnptNC4yIDE0LjJMMTEgMTNWN2gxLjV2NS4ybDQuNSAyLjctLjggMS4zeiI+PC9wYXRoPjwvZz4KPGcgaWQ9IndlZWtlbmQiPjxwYXRoIGQ9Ik0yMSAxMGMtMS4xIDAtMiAuOS0yIDJ2M0g1di0zYzAtMS4xLS45LTItMi0ycy0yIC45LTIgMnY1YzAgMS4xLjkgMiAyIDJoMThjMS4xIDAgMi0uOSAyLTJ2LTVjMC0xLjEtLjktMi0yLTJ6bS0zLTVINmMtMS4xIDAtMiAuOS0yIDJ2Mi4xNWMxLjE2LjQxIDIgMS41MSAyIDIuODJWMTRoMTJ2LTIuMDNjMC0xLjMuODQtMi40IDItMi44MlY3YzAtMS4xLS45LTItMi0yeiI+PC9wYXRoPjwvZz4KPGcgaWQ9IndvcmsiPjxwYXRoIGQ9Ik0yMCA2aC00VjRjMC0xLjExLS44OS0yLTItMmgtNGMtMS4xMSAwLTIgLjg5LTIgMnYySDRjLTEuMTEgMC0xLjk5Ljg5LTEuOTkgMkwyIDE5YzAgMS4xMS44OSAyIDIgMmgxNmMxLjExIDAgMi0uODkgMi0yVjhjMC0xLjExLS44OS0yLTItMnptLTYgMGgtNFY0aDR2MnoiPjwvcGF0aD48L2c+CjxnIGlkPSJ5b3V0dWJlLXNlYXJjaGVkLWZvciI+PHBhdGggZD0iTTE3LjAxIDE0aC0uOGwtLjI3LS4yN2MuOTgtMS4xNCAxLjU3LTIuNjEgMS41Ny00LjIzIDAtMy41OS0yLjkxLTYuNS02LjUtNi41cy02LjUgMy02LjUgNi41SDJsMy44NCA0IDQuMTYtNEg2LjUxQzYuNTEgNyA4LjUzIDUgMTEuMDEgNXM0LjUgMi4wMSA0LjUgNC41YzAgMi40OC0yLjAyIDQuNS00LjUgNC41LS42NSAwLTEuMjYtLjE0LTEuODItLjM4TDcuNzEgMTUuMWMuOTcuNTcgMi4wOS45IDMuMy45IDEuNjEgMCAzLjA4LS41OSA0LjIyLTEuNTdsLjI3LjI3di43OWw1LjAxIDQuOTlMMjIgMTlsLTQuOTktNXoiPjwvcGF0aD48L2c+CjxnIGlkPSJ6b29tLWluIj48cGF0aCBkPSJNMTUuNSAxNGgtLjc5bC0uMjgtLjI3QzE1LjQxIDEyLjU5IDE2IDExLjExIDE2IDkuNSAxNiA1LjkxIDEzLjA5IDMgOS41IDNTMyA1LjkxIDMgOS41IDUuOTEgMTYgOS41IDE2YzEuNjEgMCAzLjA5LS41OSA0LjIzLTEuNTdsLjI3LjI4di43OWw1IDQuOTlMMjAuNDkgMTlsLTQuOTktNXptLTYgMEM3LjAxIDE0IDUgMTEuOTkgNSA5LjVTNy4wMSA1IDkuNSA1IDE0IDcuMDEgMTQgOS41IDExLjk5IDE0IDkuNSAxNHptMi41LTRoLTJ2Mkg5di0ySDdWOWgyVjdoMXYyaDJ2MXoiPjwvcGF0aD48L2c+CjxnIGlkPSJ6b29tLW91dCI+PHBhdGggZD0iTTE1LjUgMTRoLS43OWwtLjI4LS4yN0MxNS40MSAxMi41OSAxNiAxMS4xMSAxNiA5LjUgMTYgNS45MSAxMy4wOSAzIDkuNSAzUzMgNS45MSAzIDkuNSA1LjkxIDE2IDkuNSAxNmMxLjYxIDAgMy4wOS0uNTkgNC4yMy0xLjU3bC4yNy4yOHYuNzlsNSA0Ljk5TDIwLjQ5IDE5bC00Ljk5LTV6bS02IDBDNy4wMSAxNCA1IDExLjk5IDUgOS41UzcuMDEgNSA5LjUgNSAxNCA3LjAxIDE0IDkuNSAxMS45OSAxNCA5LjUgMTR6TTcgOWg1djFIN3oiPjwvcGF0aD48L2c+CjwvZGVmcz48L3N2Zz4KPC9pcm9uLWljb25zZXQtc3ZnPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCh0ZW1wbGF0ZSQzLmNvbnRlbnQpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQ2hyb21lIHVzZXMgYW4gb2xkZXIgdmVyc2lvbiBvZiBET00gTGV2ZWwgMyBLZXlib2FyZCBFdmVudHMKICAgICAqCiAgICAgKiBNb3N0IGtleXMgYXJlIGxhYmVsZWQgYXMgdGV4dCwgYnV0IHNvbWUgYXJlIFVuaWNvZGUgY29kZXBvaW50cy4KICAgICAqIFZhbHVlcyB0YWtlbiBmcm9tOgogICAgICogaHR0cDovL3d3dy53My5vcmcvVFIvMjAwNy9XRC1ET00tTGV2ZWwtMy1FdmVudHMtMjAwNzEyMjEva2V5c2V0Lmh0bWwjS2V5U2V0LVNldAogICAgICovCiAgICB2YXIgS0VZX0lERU5USUZJRVIgPSB7CiAgICAgICdVKzAwMDgnOiAnYmFja3NwYWNlJywKICAgICAgJ1UrMDAwOSc6ICd0YWInLAogICAgICAnVSswMDFCJzogJ2VzYycsCiAgICAgICdVKzAwMjAnOiAnc3BhY2UnLAogICAgICAnVSswMDdGJzogJ2RlbCcKICAgIH07CgogICAgLyoqCiAgICAgKiBTcGVjaWFsIHRhYmxlIGZvciBLZXlib2FyZEV2ZW50LmtleUNvZGUuCiAgICAgKiBLZXlib2FyZEV2ZW50LmtleUlkZW50aWZpZXIgaXMgYmV0dGVyLCBhbmQgS2V5Qm9hcmRFdmVudC5rZXkgaXMgZXZlbiBiZXR0ZXIKICAgICAqIHRoYW4gdGhhdC4KICAgICAqCiAgICAgKiBWYWx1ZXMgZnJvbToKICAgICAqIGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9LZXlib2FyZEV2ZW50LmtleUNvZGUjVmFsdWVfb2Zfa2V5Q29kZQogICAgICovCiAgICB2YXIgS0VZX0NPREUgPSB7CiAgICAgIDg6ICdiYWNrc3BhY2UnLAogICAgICA5OiAndGFiJywKICAgICAgMTM6ICdlbnRlcicsCiAgICAgIDI3OiAnZXNjJywKICAgICAgMzM6ICdwYWdldXAnLAogICAgICAzNDogJ3BhZ2Vkb3duJywKICAgICAgMzU6ICdlbmQnLAogICAgICAzNjogJ2hvbWUnLAogICAgICAzMjogJ3NwYWNlJywKICAgICAgMzc6ICdsZWZ0JywKICAgICAgMzg6ICd1cCcsCiAgICAgIDM5OiAncmlnaHQnLAogICAgICA0MDogJ2Rvd24nLAogICAgICA0NjogJ2RlbCcsCiAgICAgIDEwNjogJyonCiAgICB9OwoKICAgIC8qKgogICAgICogTU9ESUZJRVJfS0VZUyBtYXBzIHRoZSBzaG9ydCBuYW1lIGZvciBtb2RpZmllciBrZXlzIHVzZWQgaW4gYSBrZXkKICAgICAqIGNvbWJvIHN0cmluZyB0byB0aGUgcHJvcGVydHkgbmFtZSB0aGF0IHJlZmVyZW5jZXMgdGhvc2Ugc2FtZSBrZXlzCiAgICAgKiBpbiBhIEtleWJvYXJkRXZlbnQgaW5zdGFuY2UuCiAgICAgKi8KICAgIHZhciBNT0RJRklFUl9LRVlTID0gewogICAgICAnc2hpZnQnOiAnc2hpZnRLZXknLAogICAgICAnY3RybCc6ICdjdHJsS2V5JywKICAgICAgJ2FsdCc6ICdhbHRLZXknLAogICAgICAnbWV0YSc6ICdtZXRhS2V5JwogICAgfTsKCiAgICAvKioKICAgICAqIEtleWJvYXJkRXZlbnQua2V5IGlzIG1vc3RseSByZXByZXNlbnRlZCBieSBwcmludGFibGUgY2hhcmFjdGVyIG1hZGUgYnkKICAgICAqIHRoZSBrZXlib2FyZCwgd2l0aCB1bnByaW50YWJsZSBrZXlzIGxhYmVsZWQgbmljZWx5LgogICAgICoKICAgICAqIEhvd2V2ZXIsIG9uIE9TIFgsIEFsdCtjaGFyIGNhbiBtYWtlIGEgVW5pY29kZSBjaGFyYWN0ZXIgdGhhdCBmb2xsb3dzIGFuCiAgICAgKiBBcHBsZS1zcGVjaWZpYyBtYXBwaW5nLiBJbiB0aGlzIGNhc2UsIHdlIGZhbGwgYmFjayB0byAua2V5Q29kZS4KICAgICAqLwogICAgdmFyIEtFWV9DSEFSID0gL1thLXowLTkqXS87CgogICAgLyoqCiAgICAgKiBNYXRjaGVzIGEga2V5SWRlbnRpZmllciBzdHJpbmcuCiAgICAgKi8KICAgIHZhciBJREVOVF9DSEFSID0gL1VcKy87CgogICAgLyoqCiAgICAgKiBNYXRjaGVzIGFycm93IGtleXMgaW4gR2Vja28gMjcuMCsKICAgICAqLwogICAgdmFyIEFSUk9XX0tFWSA9IC9eYXJyb3cvOwoKICAgIC8qKgogICAgICogTWF0Y2hlcyBzcGFjZSBrZXlzIGV2ZXJ5d2hlcmUgKG5vdGFibHkgaW5jbHVkaW5nIElFMTAncyBleGNlcHRpb25hbCBuYW1lCiAgICAgKiBgc3BhY2ViYXJgKS4KICAgICAqLwogICAgdmFyIFNQQUNFX0tFWSA9IC9ec3BhY2UoYmFyKT8vOwoKICAgIC8qKgogICAgICogTWF0Y2hlcyBFU0Mga2V5LgogICAgICoKICAgICAqIFZhbHVlIGZyb206IGh0dHA6Ly93M2MuZ2l0aHViLmlvL3VpZXZlbnRzLWtleS8ja2V5LUVzY2FwZQogICAgICovCiAgICB2YXIgRVNDX0tFWSA9IC9eZXNjYXBlJC87CgogICAgLyoqCiAgICAgKiBUcmFuc2Zvcm1zIHRoZSBrZXkuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBLZXlCb2FyZEV2ZW50LmtleQogICAgICogQHBhcmFtIHtCb29sZWFufSBbbm9TcGVjaWFsQ2hhcnNdIExpbWl0cyB0aGUgdHJhbnNmb3JtYXRpb24gdG8KICAgICAqIGFscGhhLW51bWVyaWMgY2hhcmFjdGVycy4KICAgICAqLwogICAgZnVuY3Rpb24gdHJhbnNmb3JtS2V5KGtleSwgbm9TcGVjaWFsQ2hhcnMpIHsKICAgICAgdmFyIHZhbGlkS2V5ID0gJyc7CiAgICAgIGlmIChrZXkpIHsKICAgICAgICB2YXIgbEtleSA9IGtleS50b0xvd2VyQ2FzZSgpOwogICAgICAgIGlmIChsS2V5ID09PSAnICcgfHwgU1BBQ0VfS0VZLnRlc3QobEtleSkpIHsKICAgICAgICAgIHZhbGlkS2V5ID0gJ3NwYWNlJzsKICAgICAgICB9IGVsc2UgaWYgKEVTQ19LRVkudGVzdChsS2V5KSkgewogICAgICAgICAgdmFsaWRLZXkgPSAnZXNjJzsKICAgICAgICB9IGVsc2UgaWYgKGxLZXkubGVuZ3RoID09IDEpIHsKICAgICAgICAgIGlmICghbm9TcGVjaWFsQ2hhcnMgfHwgS0VZX0NIQVIudGVzdChsS2V5KSkgewogICAgICAgICAgICB2YWxpZEtleSA9IGxLZXk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIGlmIChBUlJPV19LRVkudGVzdChsS2V5KSkgewogICAgICAgICAgdmFsaWRLZXkgPSBsS2V5LnJlcGxhY2UoJ2Fycm93JywgJycpOwogICAgICAgIH0gZWxzZSBpZiAobEtleSA9PSAnbXVsdGlwbHknKSB7CiAgICAgICAgICAvLyBudW1wYWQgJyonIGNhbiBtYXAgdG8gTXVsdGlwbHkgb24gSUUvV2luZG93cwogICAgICAgICAgdmFsaWRLZXkgPSAnKic7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHZhbGlkS2V5ID0gbEtleTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHZhbGlkS2V5OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybUtleUlkZW50aWZpZXIoa2V5SWRlbnQpIHsKICAgICAgdmFyIHZhbGlkS2V5ID0gJyc7CiAgICAgIGlmIChrZXlJZGVudCkgewogICAgICAgIGlmIChrZXlJZGVudCBpbiBLRVlfSURFTlRJRklFUikgewogICAgICAgICAgdmFsaWRLZXkgPSBLRVlfSURFTlRJRklFUltrZXlJZGVudF07CiAgICAgICAgfSBlbHNlIGlmIChJREVOVF9DSEFSLnRlc3Qoa2V5SWRlbnQpKSB7CiAgICAgICAgICBrZXlJZGVudCA9IHBhcnNlSW50KGtleUlkZW50LnJlcGxhY2UoJ1UrJywgJzB4JyksIDE2KTsKICAgICAgICAgIHZhbGlkS2V5ID0gU3RyaW5nLmZyb21DaGFyQ29kZShrZXlJZGVudCkudG9Mb3dlckNhc2UoKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFsaWRLZXkgPSBrZXlJZGVudC50b0xvd2VyQ2FzZSgpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdmFsaWRLZXk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtS2V5Q29kZShrZXlDb2RlKSB7CiAgICAgIHZhciB2YWxpZEtleSA9ICcnOwogICAgICBpZiAoTnVtYmVyKGtleUNvZGUpKSB7CiAgICAgICAgaWYgKGtleUNvZGUgPj0gNjUgJiYga2V5Q29kZSA8PSA5MCkgewogICAgICAgICAgLy8gYXNjaWkgYS16CiAgICAgICAgICAvLyBsb3dlcmNhc2UgaXMgMzIgb2Zmc2V0IGZyb20gdXBwZXJjYXNlCiAgICAgICAgICB2YWxpZEtleSA9IFN0cmluZy5mcm9tQ2hhckNvZGUoMzIgKyBrZXlDb2RlKTsKICAgICAgICB9IGVsc2UgaWYgKGtleUNvZGUgPj0gMTEyICYmIGtleUNvZGUgPD0gMTIzKSB7CiAgICAgICAgICAvLyBmdW5jdGlvbiBrZXlzIGYxLWYxMgogICAgICAgICAgdmFsaWRLZXkgPSAnZicgKyAoa2V5Q29kZSAtIDExMiArIDEpOwogICAgICAgIH0gZWxzZSBpZiAoa2V5Q29kZSA+PSA0OCAmJiBrZXlDb2RlIDw9IDU3KSB7CiAgICAgICAgICAvLyB0b3AgMC05IGtleXMKICAgICAgICAgIHZhbGlkS2V5ID0gU3RyaW5nKGtleUNvZGUgLSA0OCk7CiAgICAgICAgfSBlbHNlIGlmIChrZXlDb2RlID49IDk2ICYmIGtleUNvZGUgPD0gMTA1KSB7CiAgICAgICAgICAvLyBudW0gcGFkIDAtOQogICAgICAgICAgdmFsaWRLZXkgPSBTdHJpbmcoa2V5Q29kZSAtIDk2KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFsaWRLZXkgPSBLRVlfQ09ERVtrZXlDb2RlXTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHZhbGlkS2V5OwogICAgfQoKICAgIC8qKgogICAgICogQ2FsY3VsYXRlcyB0aGUgbm9ybWFsaXplZCBrZXkgZm9yIGEgS2V5Ym9hcmRFdmVudC4KICAgICAqIEBwYXJhbSB7S2V5Ym9hcmRFdmVudH0ga2V5RXZlbnQKICAgICAqIEBwYXJhbSB7Qm9vbGVhbn0gW25vU3BlY2lhbENoYXJzXSBTZXQgdG8gdHJ1ZSB0byBsaW1pdCBrZXlFdmVudC5rZXkKICAgICAqIHRyYW5zZm9ybWF0aW9uIHRvIGFscGhhLW51bWVyaWMgY2hhcnMuIFRoaXMgaXMgdXNlZnVsIHdpdGgga2V5CiAgICAgKiBjb21iaW5hdGlvbnMgbGlrZSBzaGlmdCArIDIsIHdoaWNoIG9uIEZGIGZvciBNYWNPUyBwcm9kdWNlcwogICAgICoga2V5RXZlbnQua2V5ID0gQAogICAgICogVG8gZ2V0IDIgcmV0dXJuZWQsIHNldCBub1NwZWNpYWxDaGFycyA9IHRydWUKICAgICAqIFRvIGdldCBAIHJldHVybmVkLCBzZXQgbm9TcGVjaWFsQ2hhcnMgPSBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBub3JtYWxpemVkS2V5Rm9yRXZlbnQoa2V5RXZlbnQsIG5vU3BlY2lhbENoYXJzKSB7CiAgICAgIC8vIEZhbGwgYmFjayBmcm9tIC5rZXksIHRvIC5kZXRhaWwua2V5IGZvciBhcnRpZmljYWwga2V5Ym9hcmQgZXZlbnRzLAogICAgICAvLyBhbmQgdGhlbiB0byBkZXByZWNhdGVkIC5rZXlJZGVudGlmaWVyIGFuZCAua2V5Q29kZS4KICAgICAgaWYgKGtleUV2ZW50LmtleSkgewogICAgICAgIHJldHVybiB0cmFuc2Zvcm1LZXkoa2V5RXZlbnQua2V5LCBub1NwZWNpYWxDaGFycyk7CiAgICAgIH0KICAgICAgaWYgKGtleUV2ZW50LmRldGFpbCAmJiBrZXlFdmVudC5kZXRhaWwua2V5KSB7CiAgICAgICAgcmV0dXJuIHRyYW5zZm9ybUtleShrZXlFdmVudC5kZXRhaWwua2V5LCBub1NwZWNpYWxDaGFycyk7CiAgICAgIH0KICAgICAgcmV0dXJuIHRyYW5zZm9ybUtleUlkZW50aWZpZXIoa2V5RXZlbnQua2V5SWRlbnRpZmllcikgfHwKICAgICAgICAgIHRyYW5zZm9ybUtleUNvZGUoa2V5RXZlbnQua2V5Q29kZSkgfHwgJyc7CiAgICB9CgogICAgZnVuY3Rpb24ga2V5Q29tYm9NYXRjaGVzRXZlbnQoa2V5Q29tYm8sIGV2ZW50KSB7CiAgICAgIC8vIEZvciBjb21ib3Mgd2l0aCBtb2RpZmllcnMgd2Ugc3VwcG9ydCBvbmx5IGFscGhhLW51bWVyaWMga2V5cwogICAgICB2YXIga2V5RXZlbnQgPSBub3JtYWxpemVkS2V5Rm9yRXZlbnQoZXZlbnQsIGtleUNvbWJvLmhhc01vZGlmaWVycyk7CiAgICAgIHJldHVybiBrZXlFdmVudCA9PT0ga2V5Q29tYm8ua2V5ICYmCiAgICAgICAgICAoIWtleUNvbWJvLmhhc01vZGlmaWVycyB8fAogICAgICAgICAgICghIWV2ZW50LnNoaWZ0S2V5ID09PSAhIWtleUNvbWJvLnNoaWZ0S2V5ICYmCiAgICAgICAgICAgICEhZXZlbnQuY3RybEtleSA9PT0gISFrZXlDb21iby5jdHJsS2V5ICYmCiAgICAgICAgICAgICEhZXZlbnQuYWx0S2V5ID09PSAhIWtleUNvbWJvLmFsdEtleSAmJgogICAgICAgICAgICAhIWV2ZW50Lm1ldGFLZXkgPT09ICEha2V5Q29tYm8ubWV0YUtleSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlS2V5Q29tYm9TdHJpbmcoa2V5Q29tYm9TdHJpbmcpIHsKICAgICAgaWYgKGtleUNvbWJvU3RyaW5nLmxlbmd0aCA9PT0gMSkgewogICAgICAgIHJldHVybiB7Y29tYm86IGtleUNvbWJvU3RyaW5nLCBrZXk6IGtleUNvbWJvU3RyaW5nLCBldmVudDogJ2tleWRvd24nfTsKICAgICAgfQogICAgICByZXR1cm4ga2V5Q29tYm9TdHJpbmcuc3BsaXQoJysnKQogICAgICAgICAgLnJlZHVjZShmdW5jdGlvbihwYXJzZWRLZXlDb21ibywga2V5Q29tYm9QYXJ0KSB7CiAgICAgICAgICAgIHZhciBldmVudFBhcnRzID0ga2V5Q29tYm9QYXJ0LnNwbGl0KCc6Jyk7CiAgICAgICAgICAgIHZhciBrZXlOYW1lID0gZXZlbnRQYXJ0c1swXTsKICAgICAgICAgICAgdmFyIGV2ZW50ID0gZXZlbnRQYXJ0c1sxXTsKCiAgICAgICAgICAgIGlmIChrZXlOYW1lIGluIE1PRElGSUVSX0tFWVMpIHsKICAgICAgICAgICAgICBwYXJzZWRLZXlDb21ib1tNT0RJRklFUl9LRVlTW2tleU5hbWVdXSA9IHRydWU7CiAgICAgICAgICAgICAgcGFyc2VkS2V5Q29tYm8uaGFzTW9kaWZpZXJzID0gdHJ1ZTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBwYXJzZWRLZXlDb21iby5rZXkgPSBrZXlOYW1lOwogICAgICAgICAgICAgIHBhcnNlZEtleUNvbWJvLmV2ZW50ID0gZXZlbnQgfHwgJ2tleWRvd24nOwogICAgICAgICAgICB9CgogICAgICAgICAgICByZXR1cm4gcGFyc2VkS2V5Q29tYm87CiAgICAgICAgICB9LCB7Y29tYm86IGtleUNvbWJvU3RyaW5nLnNwbGl0KCc6Jykuc2hpZnQoKX0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRXZlbnRTdHJpbmcoZXZlbnRTdHJpbmcpIHsKICAgICAgcmV0dXJuIGV2ZW50U3RyaW5nLnRyaW0oKS5zcGxpdCgnICcpLm1hcChmdW5jdGlvbihrZXlDb21ib1N0cmluZykgewogICAgICAgIHJldHVybiBwYXJzZUtleUNvbWJvU3RyaW5nKGtleUNvbWJvU3RyaW5nKTsKICAgICAgfSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBgUG9seW1lci5Jcm9uQTExeUtleXNCZWhhdmlvcmAgcHJvdmlkZXMgYSBub3JtYWxpemVkIGludGVyZmFjZSBmb3IgcHJvY2Vzc2luZwogICAgICoga2V5Ym9hcmQgY29tbWFuZHMgdGhhdCBwZXJ0YWluIHRvIFtXQUktQVJJQSBiZXN0CiAgICAgKiBwcmFjdGljZXNdKGh0dHA6Ly93d3cudzMub3JnL1RSL3dhaS1hcmlhLXByYWN0aWNlcy8ja2JkX2dlbmVyYWxfYmluZGluZykuIFRoZQogICAgICogZWxlbWVudCB0YWtlcyBjYXJlIG9mIGJyb3dzZXIgZGlmZmVyZW5jZXMgd2l0aCByZXNwZWN0IHRvIEtleWJvYXJkIGV2ZW50cyBhbmQKICAgICAqIHVzZXMgYW4gZXhwcmVzc2l2ZSBzeW50YXggdG8gZmlsdGVyIGtleSBwcmVzc2VzLgogICAgICoKICAgICAqIFVzZSB0aGUgYGtleUJpbmRpbmdzYCBwcm90b3R5cGUgcHJvcGVydHkgdG8gZXhwcmVzcyB3aGF0IGNvbWJpbmF0aW9uIG9mIGtleXMKICAgICAqIHdpbGwgdHJpZ2dlciB0aGUgY2FsbGJhY2suIEEga2V5IGJpbmRpbmcgaGFzIHRoZSBmb3JtYXQKICAgICAqIGAiS0VZK01PRElGSUVSOkVWRU5UIjogImNhbGxiYWNrImAgKGAiS0VZIjogImNhbGxiYWNrImAgb3IKICAgICAqIGAiS0VZOkVWRU5UIjogImNhbGxiYWNrImAgYXJlIHZhbGlkIGFzIHdlbGwpLiBTb21lIGV4YW1wbGVzOgogICAgICoKICAgICAqICAgICAga2V5QmluZGluZ3M6IHsKICAgICAqICAgICAgICAnc3BhY2UnOiAnX29uS2V5ZG93bicsIC8vIHNhbWUgYXMgJ3NwYWNlOmtleWRvd24nCiAgICAgKiAgICAgICAgJ3NoaWZ0K3RhYic6ICdfb25LZXlkb3duJywKICAgICAqICAgICAgICAnZW50ZXI6a2V5cHJlc3MnOiAnX29uS2V5cHJlc3MnLAogICAgICogICAgICAgICdlc2M6a2V5dXAnOiAnX29uS2V5dXAnCiAgICAgKiAgICAgIH0KICAgICAqCiAgICAgKiBUaGUgY2FsbGJhY2sgd2lsbCByZWNlaXZlIHdpdGggYW4gZXZlbnQgY29udGFpbmluZyB0aGUgZm9sbG93aW5nIGluZm9ybWF0aW9uCiAgICAgKiBpbiBgZXZlbnQuZGV0YWlsYDoKICAgICAqCiAgICAgKiAgICAgIF9vbktleWRvd246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgKiAgICAgICAgY29uc29sZS5sb2coZXZlbnQuZGV0YWlsLmNvbWJvKTsgLy8gS0VZK01PRElGSUVSLCBlLmcuICJzaGlmdCt0YWIiCiAgICAgKiAgICAgICAgY29uc29sZS5sb2coZXZlbnQuZGV0YWlsLmtleSk7IC8vIEtFWSBvbmx5LCBlLmcuICJ0YWIiCiAgICAgKiAgICAgICAgY29uc29sZS5sb2coZXZlbnQuZGV0YWlsLmV2ZW50KTsgLy8gRVZFTlQsIGUuZy4gImtleWRvd24iCiAgICAgKiAgICAgICAgY29uc29sZS5sb2coZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQpOyAvLyB0aGUgb3JpZ2luYWwgS2V5Ym9hcmRFdmVudAogICAgICogICAgICB9CiAgICAgKgogICAgICogVXNlIHRoZSBga2V5RXZlbnRUYXJnZXRgIGF0dHJpYnV0ZSB0byBzZXQgdXAgZXZlbnQgaGFuZGxlcnMgb24gYSBzcGVjaWZpYwogICAgICogbm9kZS4KICAgICAqCiAgICAgKiBTZWUgdGhlIFtkZW1vIHNvdXJjZQogICAgICogY29kZV0oaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9pcm9uLWExMXkta2V5cy1iZWhhdmlvci9ibG9iL21hc3Rlci9kZW1vL3gta2V5LWF3YXJlLmh0bWwpCiAgICAgKiBmb3IgYW4gZXhhbXBsZS4KICAgICAqCiAgICAgKiBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAqIEBwb2x5bWVyQmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgSXJvbkExMXlLZXlzQmVoYXZpb3IgPSB7CiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgRXZlbnRUYXJnZXQgdGhhdCB3aWxsIGJlIGZpcmluZyByZWxldmFudCBLZXlib2FyZEV2ZW50cy4gU2V0IGl0IHRvCiAgICAgICAgICogYG51bGxgIHRvIGRpc2FibGUgdGhlIGxpc3RlbmVycy4KICAgICAgICAgKiBAdHlwZSB7P0V2ZW50VGFyZ2V0fQogICAgICAgICAqLwogICAgICAgIGtleUV2ZW50VGFyZ2V0OiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgfQogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHRoaXMgcHJvcGVydHkgd2lsbCBjYXVzZSB0aGUgaW1wbGVtZW50aW5nIGVsZW1lbnQgdG8KICAgICAgICAgKiBhdXRvbWF0aWNhbGx5IHN0b3AgcHJvcGFnYXRpb24gb24gYW55IGhhbmRsZWQgS2V5Ym9hcmRFdmVudHMuCiAgICAgICAgICovCiAgICAgICAgc3RvcEtleWJvYXJkRXZlbnRQcm9wYWdhdGlvbjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIF9ib3VuZEtleUhhbmRsZXJzOiB7CiAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgIHZhbHVlOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgfQogICAgICAgIH0sCgogICAgICAgIC8vIFdlIHVzZSB0aGlzIGR1ZSB0byBhIGxpbWl0YXRpb24gaW4gSUUxMCB3aGVyZSBpbnN0YW5jZXMgd2lsbCBoYXZlCiAgICAgICAgLy8gb3duIHByb3BlcnRpZXMgb2YgZXZlcnl0aGluZyBvbiB0aGUgInByb3RvdHlwZSIuCiAgICAgICAgX2ltcGVyYXRpdmVLZXlCaW5kaW5nczogewogICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4ge307CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgb2JzZXJ2ZXJzOiBbJ19yZXNldEtleUV2ZW50TGlzdGVuZXJzKGtleUV2ZW50VGFyZ2V0LCBfYm91bmRLZXlIYW5kbGVycyknXSwKCgogICAgICAvKioKICAgICAgICogVG8gYmUgdXNlZCB0byBleHByZXNzIHdoYXQgY29tYmluYXRpb24gb2Yga2V5cyAgd2lsbCB0cmlnZ2VyIHRoZSByZWxhdGl2ZQogICAgICAgKiBjYWxsYmFjay4gZS5nLiBga2V5QmluZGluZ3M6IHsgJ2VzYyc6ICdfb25Fc2NQcmVzc2VkJ31gCiAgICAgICAqIEB0eXBlIHshT2JqZWN0fQogICAgICAgKi8KICAgICAga2V5QmluZGluZ3M6IHt9LAoKICAgICAgcmVnaXN0ZXJlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcHJlcEtleUJpbmRpbmdzKCk7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGlzdGVuS2V5RXZlbnRMaXN0ZW5lcnMoKTsKICAgICAgfSwKCiAgICAgIGRldGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl91bmxpc3RlbktleUV2ZW50TGlzdGVuZXJzKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FuIGJlIHVzZWQgdG8gaW1wZXJhdGl2ZWx5IGFkZCBhIGtleSBiaW5kaW5nIHRvIHRoZSBpbXBsZW1lbnRpbmcKICAgICAgICogZWxlbWVudC4gVGhpcyBpcyB0aGUgaW1wZXJhdGl2ZSBlcXVpdmFsZW50IG9mIGRlY2xhcmluZyBhIGtleWJpbmRpbmcKICAgICAgICogaW4gdGhlIGBrZXlCaW5kaW5nc2AgcHJvdG90eXBlIHByb3BlcnR5LgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZXZlbnRTdHJpbmcKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGhhbmRsZXJOYW1lCiAgICAgICAqLwogICAgICBhZGRPd25LZXlCaW5kaW5nOiBmdW5jdGlvbihldmVudFN0cmluZywgaGFuZGxlck5hbWUpIHsKICAgICAgICB0aGlzLl9pbXBlcmF0aXZlS2V5QmluZGluZ3NbZXZlbnRTdHJpbmddID0gaGFuZGxlck5hbWU7CiAgICAgICAgdGhpcy5fcHJlcEtleUJpbmRpbmdzKCk7CiAgICAgICAgdGhpcy5fcmVzZXRLZXlFdmVudExpc3RlbmVycygpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFdoZW4gY2FsbGVkLCB3aWxsIHJlbW92ZSBhbGwgaW1wZXJhdGl2ZWx5LWFkZGVkIGtleSBiaW5kaW5ncy4KICAgICAgICovCiAgICAgIHJlbW92ZU93bktleUJpbmRpbmdzOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9pbXBlcmF0aXZlS2V5QmluZGluZ3MgPSB7fTsKICAgICAgICB0aGlzLl9wcmVwS2V5QmluZGluZ3MoKTsKICAgICAgICB0aGlzLl9yZXNldEtleUV2ZW50TGlzdGVuZXJzKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0cnVlIGlmIGEga2V5Ym9hcmQgZXZlbnQgbWF0Y2hlcyBgZXZlbnRTdHJpbmdgLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0tleWJvYXJkRXZlbnR9IGV2ZW50CiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBldmVudFN0cmluZwogICAgICAgKiBAcmV0dXJuIHtib29sZWFufQogICAgICAgKi8KICAgICAga2V5Ym9hcmRFdmVudE1hdGNoZXNLZXlzOiBmdW5jdGlvbihldmVudCwgZXZlbnRTdHJpbmcpIHsKICAgICAgICB2YXIga2V5Q29tYm9zID0gcGFyc2VFdmVudFN0cmluZyhldmVudFN0cmluZyk7CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBrZXlDb21ib3MubGVuZ3RoOyArK2kpIHsKICAgICAgICAgIGlmIChrZXlDb21ib01hdGNoZXNFdmVudChrZXlDb21ib3NbaV0sIGV2ZW50KSkgewogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAoKICAgICAgX2NvbGxlY3RLZXlCaW5kaW5nczogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGtleUJpbmRpbmdzID0gdGhpcy5iZWhhdmlvcnMubWFwKGZ1bmN0aW9uKGJlaGF2aW9yKSB7CiAgICAgICAgICByZXR1cm4gYmVoYXZpb3Iua2V5QmluZGluZ3M7CiAgICAgICAgfSk7CgogICAgICAgIGlmIChrZXlCaW5kaW5ncy5pbmRleE9mKHRoaXMua2V5QmluZGluZ3MpID09PSAtMSkgewogICAgICAgICAga2V5QmluZGluZ3MucHVzaCh0aGlzLmtleUJpbmRpbmdzKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBrZXlCaW5kaW5nczsKICAgICAgfSwKCiAgICAgIF9wcmVwS2V5QmluZGluZ3M6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2tleUJpbmRpbmdzID0ge307CgogICAgICAgIHRoaXMuX2NvbGxlY3RLZXlCaW5kaW5ncygpLmZvckVhY2goZnVuY3Rpb24oa2V5QmluZGluZ3MpIHsKICAgICAgICAgIGZvciAodmFyIGV2ZW50U3RyaW5nIGluIGtleUJpbmRpbmdzKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZEtleUJpbmRpbmcoZXZlbnRTdHJpbmcsIGtleUJpbmRpbmdzW2V2ZW50U3RyaW5nXSk7CiAgICAgICAgICB9CiAgICAgICAgfSwgdGhpcyk7CgogICAgICAgIGZvciAodmFyIGV2ZW50U3RyaW5nIGluIHRoaXMuX2ltcGVyYXRpdmVLZXlCaW5kaW5ncykgewogICAgICAgICAgdGhpcy5fYWRkS2V5QmluZGluZygKICAgICAgICAgICAgICBldmVudFN0cmluZywgdGhpcy5faW1wZXJhdGl2ZUtleUJpbmRpbmdzW2V2ZW50U3RyaW5nXSk7CiAgICAgICAgfQoKICAgICAgICAvLyBHaXZlIHByZWNlZGVuY2UgdG8gY29tYm9zIHdpdGggbW9kaWZpZXJzIHRvIGJlIGNoZWNrZWQgZmlyc3QuCiAgICAgICAgZm9yICh2YXIgZXZlbnROYW1lIGluIHRoaXMuX2tleUJpbmRpbmdzKSB7CiAgICAgICAgICB0aGlzLl9rZXlCaW5kaW5nc1tldmVudE5hbWVdLnNvcnQoZnVuY3Rpb24oa2IxLCBrYjIpIHsKICAgICAgICAgICAgdmFyIGIxID0ga2IxWzBdLmhhc01vZGlmaWVyczsKICAgICAgICAgICAgdmFyIGIyID0ga2IyWzBdLmhhc01vZGlmaWVyczsKICAgICAgICAgICAgcmV0dXJuIChiMSA9PT0gYjIpID8gMCA6IGIxID8gLTEgOiAxOwogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2FkZEtleUJpbmRpbmc6IGZ1bmN0aW9uKGV2ZW50U3RyaW5nLCBoYW5kbGVyTmFtZSkgewogICAgICAgIHBhcnNlRXZlbnRTdHJpbmcoZXZlbnRTdHJpbmcpLmZvckVhY2goZnVuY3Rpb24oa2V5Q29tYm8pIHsKICAgICAgICAgIHRoaXMuX2tleUJpbmRpbmdzW2tleUNvbWJvLmV2ZW50XSA9CiAgICAgICAgICAgICAgdGhpcy5fa2V5QmluZGluZ3Nba2V5Q29tYm8uZXZlbnRdIHx8IFtdOwoKICAgICAgICAgIHRoaXMuX2tleUJpbmRpbmdzW2tleUNvbWJvLmV2ZW50XS5wdXNoKFtrZXlDb21ibywgaGFuZGxlck5hbWVdKTsKICAgICAgICB9LCB0aGlzKTsKICAgICAgfSwKCiAgICAgIF9yZXNldEtleUV2ZW50TGlzdGVuZXJzOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl91bmxpc3RlbktleUV2ZW50TGlzdGVuZXJzKCk7CgogICAgICAgIGlmICh0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgIHRoaXMuX2xpc3RlbktleUV2ZW50TGlzdGVuZXJzKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2xpc3RlbktleUV2ZW50TGlzdGVuZXJzOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIXRoaXMua2V5RXZlbnRUYXJnZXQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgT2JqZWN0LmtleXModGhpcy5fa2V5QmluZGluZ3MpLmZvckVhY2goZnVuY3Rpb24oZXZlbnROYW1lKSB7CiAgICAgICAgICB2YXIga2V5QmluZGluZ3MgPSB0aGlzLl9rZXlCaW5kaW5nc1tldmVudE5hbWVdOwogICAgICAgICAgdmFyIGJvdW5kS2V5SGFuZGxlciA9IHRoaXMuX29uS2V5QmluZGluZ0V2ZW50LmJpbmQodGhpcywga2V5QmluZGluZ3MpOwoKICAgICAgICAgIHRoaXMuX2JvdW5kS2V5SGFuZGxlcnMucHVzaCgKICAgICAgICAgICAgICBbdGhpcy5rZXlFdmVudFRhcmdldCwgZXZlbnROYW1lLCBib3VuZEtleUhhbmRsZXJdKTsKCiAgICAgICAgICB0aGlzLmtleUV2ZW50VGFyZ2V0LmFkZEV2ZW50TGlzdGVuZXIoZXZlbnROYW1lLCBib3VuZEtleUhhbmRsZXIpOwogICAgICAgIH0sIHRoaXMpOwogICAgICB9LAoKICAgICAgX3VubGlzdGVuS2V5RXZlbnRMaXN0ZW5lcnM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBrZXlIYW5kbGVyVHVwbGU7CiAgICAgICAgdmFyIGtleUV2ZW50VGFyZ2V0OwogICAgICAgIHZhciBldmVudE5hbWU7CiAgICAgICAgdmFyIGJvdW5kS2V5SGFuZGxlcjsKCiAgICAgICAgd2hpbGUgKHRoaXMuX2JvdW5kS2V5SGFuZGxlcnMubGVuZ3RoKSB7CiAgICAgICAgICAvLyBNeSBraW5nZG9tIGZvciBibG9jay1zY29wZSBiaW5kaW5nIGFuZCBkZXN0cnVjdHVyaW5nIGFzc2lnbm1lbnQuLgogICAgICAgICAga2V5SGFuZGxlclR1cGxlID0gdGhpcy5fYm91bmRLZXlIYW5kbGVycy5wb3AoKTsKICAgICAgICAgIGtleUV2ZW50VGFyZ2V0ID0ga2V5SGFuZGxlclR1cGxlWzBdOwogICAgICAgICAgZXZlbnROYW1lID0ga2V5SGFuZGxlclR1cGxlWzFdOwogICAgICAgICAgYm91bmRLZXlIYW5kbGVyID0ga2V5SGFuZGxlclR1cGxlWzJdOwoKICAgICAgICAgIGtleUV2ZW50VGFyZ2V0LnJlbW92ZUV2ZW50TGlzdGVuZXIoZXZlbnROYW1lLCBib3VuZEtleUhhbmRsZXIpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9vbktleUJpbmRpbmdFdmVudDogZnVuY3Rpb24oa2V5QmluZGluZ3MsIGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMuc3RvcEtleWJvYXJkRXZlbnRQcm9wYWdhdGlvbikgewogICAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgICAgfQoKICAgICAgICAvLyBpZiBldmVudCBoYXMgYmVlbiBhbHJlYWR5IHByZXZlbnRlZCwgZG9uJ3QgZG8gYW55dGhpbmcKICAgICAgICBpZiAoZXZlbnQuZGVmYXVsdFByZXZlbnRlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBrZXlCaW5kaW5ncy5sZW5ndGg7IGkrKykgewogICAgICAgICAgdmFyIGtleUNvbWJvID0ga2V5QmluZGluZ3NbaV1bMF07CiAgICAgICAgICB2YXIgaGFuZGxlck5hbWUgPSBrZXlCaW5kaW5nc1tpXVsxXTsKICAgICAgICAgIGlmIChrZXlDb21ib01hdGNoZXNFdmVudChrZXlDb21ibywgZXZlbnQpKSB7CiAgICAgICAgICAgIHRoaXMuX3RyaWdnZXJLZXlIYW5kbGVyKGtleUNvbWJvLCBoYW5kbGVyTmFtZSwgZXZlbnQpOwogICAgICAgICAgICAvLyBleGl0IHRoZSBsb29wIGlmIGV2ZW50RGVmYXVsdCB3YXMgcHJldmVudGVkCiAgICAgICAgICAgIGlmIChldmVudC5kZWZhdWx0UHJldmVudGVkKSB7CiAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3RyaWdnZXJLZXlIYW5kbGVyOiBmdW5jdGlvbihrZXlDb21ibywgaGFuZGxlck5hbWUsIGtleWJvYXJkRXZlbnQpIHsKICAgICAgICB2YXIgZGV0YWlsID0gT2JqZWN0LmNyZWF0ZShrZXlDb21ibyk7CiAgICAgICAgZGV0YWlsLmtleWJvYXJkRXZlbnQgPSBrZXlib2FyZEV2ZW50OwogICAgICAgIHZhciBldmVudCA9CiAgICAgICAgICAgIG5ldyBDdXN0b21FdmVudChrZXlDb21iby5ldmVudCwge2RldGFpbDogZGV0YWlsLCBjYW5jZWxhYmxlOiB0cnVlfSk7CiAgICAgICAgdGhpc1toYW5kbGVyTmFtZV0uY2FsbCh0aGlzLCBldmVudCk7CiAgICAgICAgaWYgKGV2ZW50LmRlZmF1bHRQcmV2ZW50ZWQpIHsKICAgICAgICAgIGtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE2IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBgUG9seW1lci5Jcm9uU2Nyb2xsVGFyZ2V0QmVoYXZpb3JgIGFsbG93cyBhbiBlbGVtZW50IHRvIHJlc3BvbmQgdG8gc2Nyb2xsCiAgICAgKiBldmVudHMgZnJvbSBhIGRlc2lnbmF0ZWQgc2Nyb2xsIHRhcmdldC4KICAgICAqCiAgICAgKiBFbGVtZW50cyB0aGF0IGNvbnN1bWUgdGhpcyBiZWhhdmlvciBjYW4gb3ZlcnJpZGUgdGhlIGBfc2Nyb2xsSGFuZGxlcmAKICAgICAqIG1ldGhvZCB0byBhZGQgbG9naWMgb24gdGhlIHNjcm9sbCBldmVudC4KICAgICAqCiAgICAgKiBAZGVtbyBkZW1vL3Njcm9sbGluZy1yZWdpb24uaHRtbCBTY3JvbGxpbmcgUmVnaW9uCiAgICAgKiBAZGVtbyBkZW1vL2RvY3VtZW50Lmh0bWwgRG9jdW1lbnQgRWxlbWVudAogICAgICogQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uU2Nyb2xsVGFyZ2V0QmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIFNwZWNpZmllcyB0aGUgZWxlbWVudCB0aGF0IHdpbGwgaGFuZGxlIHRoZSBzY3JvbGwgZXZlbnQKICAgICAgICAgKiBvbiB0aGUgYmVoYWxmIG9mIHRoZSBjdXJyZW50IGVsZW1lbnQuIFRoaXMgaXMgdHlwaWNhbGx5IGEgcmVmZXJlbmNlIHRvIGFuCiAgICAgICAgICplbGVtZW50LCBidXQgdGhlcmUgYXJlIGEgZmV3IG1vcmUgcG9zaWJpbGl0aWVzOgogICAgICAgICAqCiAgICAgICAgICogIyMjIEVsZW1lbnRzIGlkCiAgICAgICAgICoKICAgICAgICAgKmBgYGh0bWwKICAgICAgICAgKiA8ZGl2IGlkPSJzY3JvbGxhYmxlLWVsZW1lbnQiIHN0eWxlPSJvdmVyZmxvdzogYXV0bzsiPgogICAgICAgICAqICA8eC1lbGVtZW50IHNjcm9sbC10YXJnZXQ9InNjcm9sbGFibGUtZWxlbWVudCI+CiAgICAgICAgICogICAgPCEtLSBDb250ZW50LS0+CiAgICAgICAgICogIDwveC1lbGVtZW50PgogICAgICAgICAqIDwvZGl2PgogICAgICAgICAqYGBgCiAgICAgICAgICogSW4gdGhpcyBjYXNlLCB0aGUgYHNjcm9sbFRhcmdldGAgd2lsbCBwb2ludCB0byB0aGUgb3V0ZXIgZGl2IGVsZW1lbnQuCiAgICAgICAgICoKICAgICAgICAgKiAjIyMgRG9jdW1lbnQgc2Nyb2xsaW5nCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgZG9jdW1lbnQgc2Nyb2xsaW5nLCB5b3UgY2FuIHVzZSB0aGUgcmVzZXJ2ZWQgd29yZCBgZG9jdW1lbnRgOgogICAgICAgICAqCiAgICAgICAgICpgYGBodG1sCiAgICAgICAgICogPHgtZWxlbWVudCBzY3JvbGwtdGFyZ2V0PSJkb2N1bWVudCI+CiAgICAgICAgICogICA8IS0tIENvbnRlbnQgLS0+CiAgICAgICAgICogPC94LWVsZW1lbnQ+CiAgICAgICAgICpgYGAKICAgICAgICAgKgogICAgICAgICAqICMjIyBFbGVtZW50cyByZWZlcmVuY2UKICAgICAgICAgKgogICAgICAgICAqYGBganMKICAgICAgICAgKiBhcHBIZWFkZXIuc2Nyb2xsVGFyZ2V0ID0gZG9jdW1lbnQucXVlcnlTZWxlY3RvcignI3Njcm9sbGFibGUtZWxlbWVudCcpOwogICAgICAgICAqYGBgCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnR9CiAgICAgICAgICogQGRlZmF1bHQgZG9jdW1lbnQKICAgICAgICAgKi8KICAgICAgICBzY3JvbGxUYXJnZXQ6IHsKICAgICAgICAgIHR5cGU6IEhUTUxFbGVtZW50LAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZGVmYXVsdFNjcm9sbFRhcmdldDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6IFsnX3Njcm9sbFRhcmdldENoYW5nZWQoc2Nyb2xsVGFyZ2V0LCBpc0F0dGFjaGVkKSddLAoKICAgICAgLyoqCiAgICAgICAqIFRydWUgaWYgdGhlIGV2ZW50IGxpc3RlbmVyIHNob3VsZCBiZSBpbnN0YWxsZWQuCiAgICAgICAqLwogICAgICBfc2hvdWxkSGF2ZUxpc3RlbmVyOiB0cnVlLAoKICAgICAgX3Njcm9sbFRhcmdldENoYW5nZWQ6IGZ1bmN0aW9uKHNjcm9sbFRhcmdldCwgaXNBdHRhY2hlZCkgewoKICAgICAgICBpZiAodGhpcy5fb2xkU2Nyb2xsVGFyZ2V0KSB7CiAgICAgICAgICB0aGlzLl90b2dnbGVTY3JvbGxMaXN0ZW5lcihmYWxzZSwgdGhpcy5fb2xkU2Nyb2xsVGFyZ2V0KTsKICAgICAgICAgIHRoaXMuX29sZFNjcm9sbFRhcmdldCA9IG51bGw7CiAgICAgICAgfQogICAgICAgIGlmICghaXNBdHRhY2hlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICAvLyBTdXBwb3J0IGVsZW1lbnQgaWQgcmVmZXJlbmNlcwogICAgICAgIGlmIChzY3JvbGxUYXJnZXQgPT09ICdkb2N1bWVudCcpIHsKICAgICAgICAgIHRoaXMuc2Nyb2xsVGFyZ2V0ID0gdGhpcy5fZG9jOwoKICAgICAgICB9IGVsc2UgaWYgKHR5cGVvZiBzY3JvbGxUYXJnZXQgPT09ICdzdHJpbmcnKSB7CiAgICAgICAgICB2YXIgZG9tSG9zdCA9IHRoaXMuZG9tSG9zdDsKCiAgICAgICAgICB0aGlzLnNjcm9sbFRhcmdldCA9IGRvbUhvc3QgJiYgZG9tSG9zdC4kID8KICAgICAgICAgICAgICBkb21Ib3N0LiRbc2Nyb2xsVGFyZ2V0XSA6CiAgICAgICAgICAgICAgZG9tKHRoaXMub3duZXJEb2N1bWVudCkucXVlcnlTZWxlY3RvcignIycgKyBzY3JvbGxUYXJnZXQpOwoKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX2lzVmFsaWRTY3JvbGxUYXJnZXQoKSkgewogICAgICAgICAgdGhpcy5fb2xkU2Nyb2xsVGFyZ2V0ID0gc2Nyb2xsVGFyZ2V0OwogICAgICAgICAgdGhpcy5fdG9nZ2xlU2Nyb2xsTGlzdGVuZXIodGhpcy5fc2hvdWxkSGF2ZUxpc3RlbmVyLCBzY3JvbGxUYXJnZXQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSdW5zIG9uIGV2ZXJ5IHNjcm9sbCBldmVudC4gQ29uc3VtZXIgb2YgdGhpcyBiZWhhdmlvciBtYXkgb3ZlcnJpZGUgdGhpcwogICAgICAgKiBtZXRob2QuCiAgICAgICAqCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9zY3JvbGxIYW5kbGVyOiBmdW5jdGlvbiBzY3JvbGxIYW5kbGVyKCkge30sCgogICAgICAvKioKICAgICAgICogVGhlIGRlZmF1bHQgc2Nyb2xsIHRhcmdldC4gQ29uc3VtZXJzIG9mIHRoaXMgYmVoYXZpb3IgbWF5IHdhbnQgdG8gY3VzdG9taXplCiAgICAgICAqIHRoZSBkZWZhdWx0IHNjcm9sbCB0YXJnZXQuCiAgICAgICAqCiAgICAgICAqIEB0eXBlIHtFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2V0IF9kZWZhdWx0U2Nyb2xsVGFyZ2V0KCkgewogICAgICAgIHJldHVybiB0aGlzLl9kb2M7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2hvcnRjdXQgZm9yIHRoZSBkb2N1bWVudCBlbGVtZW50CiAgICAgICAqCiAgICAgICAqIEB0eXBlIHtFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2V0IF9kb2MoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMub3duZXJEb2N1bWVudC5kb2N1bWVudEVsZW1lbnQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogR2V0cyB0aGUgbnVtYmVyIG9mIHBpeGVscyB0aGF0IHRoZSBjb250ZW50IG9mIGFuIGVsZW1lbnQgaXMgc2Nyb2xsZWQKICAgICAgICogdXB3YXJkLgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IF9zY3JvbGxUb3AoKSB7CiAgICAgICAgaWYgKHRoaXMuX2lzVmFsaWRTY3JvbGxUYXJnZXQoKSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuc2Nyb2xsVGFyZ2V0ID09PSB0aGlzLl9kb2MgPyB3aW5kb3cucGFnZVlPZmZzZXQgOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLnNjcm9sbFRhcmdldC5zY3JvbGxUb3A7CiAgICAgICAgfQogICAgICAgIHJldHVybiAwOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEdldHMgdGhlIG51bWJlciBvZiBwaXhlbHMgdGhhdCB0aGUgY29udGVudCBvZiBhbiBlbGVtZW50IGlzIHNjcm9sbGVkIHRvIHRoZQogICAgICAgKiBsZWZ0LgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IF9zY3JvbGxMZWZ0KCkgewogICAgICAgIGlmICh0aGlzLl9pc1ZhbGlkU2Nyb2xsVGFyZ2V0KCkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLnNjcm9sbFRhcmdldCA9PT0gdGhpcy5fZG9jID8gd2luZG93LnBhZ2VYT2Zmc2V0IDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsTGVmdDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIDA7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgbnVtYmVyIG9mIHBpeGVscyB0aGF0IHRoZSBjb250ZW50IG9mIGFuIGVsZW1lbnQgaXMgc2Nyb2xsZWQKICAgICAgICogdXB3YXJkLgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgc2V0IF9zY3JvbGxUb3AodG9wKSB7CiAgICAgICAgaWYgKHRoaXMuc2Nyb2xsVGFyZ2V0ID09PSB0aGlzLl9kb2MpIHsKICAgICAgICAgIHdpbmRvdy5zY3JvbGxUbyh3aW5kb3cucGFnZVhPZmZzZXQsIHRvcCk7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl9pc1ZhbGlkU2Nyb2xsVGFyZ2V0KCkpIHsKICAgICAgICAgIHRoaXMuc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCA9IHRvcDsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgbnVtYmVyIG9mIHBpeGVscyB0aGF0IHRoZSBjb250ZW50IG9mIGFuIGVsZW1lbnQgaXMgc2Nyb2xsZWQgdG8gdGhlCiAgICAgICAqIGxlZnQuCiAgICAgICAqCiAgICAgICAqIEB0eXBlIHtudW1iZXJ9CiAgICAgICAqLwogICAgICBzZXQgX3Njcm9sbExlZnQobGVmdCkgewogICAgICAgIGlmICh0aGlzLnNjcm9sbFRhcmdldCA9PT0gdGhpcy5fZG9jKSB7CiAgICAgICAgICB3aW5kb3cuc2Nyb2xsVG8obGVmdCwgd2luZG93LnBhZ2VZT2Zmc2V0KTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX2lzVmFsaWRTY3JvbGxUYXJnZXQoKSkgewogICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsTGVmdCA9IGxlZnQ7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNjcm9sbHMgdGhlIGNvbnRlbnQgdG8gYSBwYXJ0aWN1bGFyIHBsYWNlLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHNjcm9sbAogICAgICAgKiBAcGFyYW0ge251bWJlcnwhe2xlZnQ6IG51bWJlciwgdG9wOiBudW1iZXJ9fSBsZWZ0T3JPcHRpb25zIFRoZSBsZWZ0IHBvc2l0aW9uIG9yIHNjcm9sbCBvcHRpb25zCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyPX0gdG9wIFRoZSB0b3AgcG9zaXRpb24KICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIHNjcm9sbDogZnVuY3Rpb24obGVmdE9yT3B0aW9ucywgdG9wKSB7CiAgICAgICAgdmFyIGxlZnQ7CgogICAgICAgIGlmICh0eXBlb2YgbGVmdE9yT3B0aW9ucyA9PT0gJ29iamVjdCcpIHsKICAgICAgICAgIGxlZnQgPSBsZWZ0T3JPcHRpb25zLmxlZnQ7CiAgICAgICAgICB0b3AgPSBsZWZ0T3JPcHRpb25zLnRvcDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgbGVmdCA9IGxlZnRPck9wdGlvbnM7CiAgICAgICAgfQoKICAgICAgICBsZWZ0ID0gbGVmdCB8fCAwOwogICAgICAgIHRvcCA9IHRvcCB8fCAwOwogICAgICAgIGlmICh0aGlzLnNjcm9sbFRhcmdldCA9PT0gdGhpcy5fZG9jKSB7CiAgICAgICAgICB3aW5kb3cuc2Nyb2xsVG8obGVmdCwgdG9wKTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX2lzVmFsaWRTY3JvbGxUYXJnZXQoKSkgewogICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsTGVmdCA9IGxlZnQ7CiAgICAgICAgICB0aGlzLnNjcm9sbFRhcmdldC5zY3JvbGxUb3AgPSB0b3A7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEdldHMgdGhlIHdpZHRoIG9mIHRoZSBzY3JvbGwgdGFyZ2V0LgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IF9zY3JvbGxUYXJnZXRXaWR0aCgpIHsKICAgICAgICBpZiAodGhpcy5faXNWYWxpZFNjcm9sbFRhcmdldCgpKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5zY3JvbGxUYXJnZXQgPT09IHRoaXMuX2RvYyA/IHdpbmRvdy5pbm5lcldpZHRoIDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQub2Zmc2V0V2lkdGg7CiAgICAgICAgfQogICAgICAgIHJldHVybiAwOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEdldHMgdGhlIGhlaWdodCBvZiB0aGUgc2Nyb2xsIHRhcmdldC4KICAgICAgICoKICAgICAgICogQHR5cGUge251bWJlcn0KICAgICAgICovCiAgICAgIGdldCBfc2Nyb2xsVGFyZ2V0SGVpZ2h0KCkgewogICAgICAgIGlmICh0aGlzLl9pc1ZhbGlkU2Nyb2xsVGFyZ2V0KCkpIHsKICAgICAgICAgIHJldHVybiB0aGlzLnNjcm9sbFRhcmdldCA9PT0gdGhpcy5fZG9jID8gd2luZG93LmlubmVySGVpZ2h0IDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQub2Zmc2V0SGVpZ2h0OwogICAgICAgIH0KICAgICAgICByZXR1cm4gMDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNjcm9sbCB0YXJnZXQgaXMgYSB2YWxpZCBIVE1MRWxlbWVudC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICovCiAgICAgIF9pc1ZhbGlkU2Nyb2xsVGFyZ2V0OiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5zY3JvbGxUYXJnZXQgaW5zdGFuY2VvZiBIVE1MRWxlbWVudDsKICAgICAgfSwKCiAgICAgIF90b2dnbGVTY3JvbGxMaXN0ZW5lcjogZnVuY3Rpb24oeWVzLCBzY3JvbGxUYXJnZXQpIHsKICAgICAgICB2YXIgZXZlbnRUYXJnZXQgPSBzY3JvbGxUYXJnZXQgPT09IHRoaXMuX2RvYyA/IHdpbmRvdyA6IHNjcm9sbFRhcmdldDsKICAgICAgICBpZiAoeWVzKSB7CiAgICAgICAgICBpZiAoIXRoaXMuX2JvdW5kU2Nyb2xsSGFuZGxlcikgewogICAgICAgICAgICB0aGlzLl9ib3VuZFNjcm9sbEhhbmRsZXIgPSB0aGlzLl9zY3JvbGxIYW5kbGVyLmJpbmQodGhpcyk7CiAgICAgICAgICAgIGV2ZW50VGFyZ2V0LmFkZEV2ZW50TGlzdGVuZXIoJ3Njcm9sbCcsIHRoaXMuX2JvdW5kU2Nyb2xsSGFuZGxlcik7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmICh0aGlzLl9ib3VuZFNjcm9sbEhhbmRsZXIpIHsKICAgICAgICAgICAgZXZlbnRUYXJnZXQucmVtb3ZlRXZlbnRMaXN0ZW5lcignc2Nyb2xsJywgdGhpcy5fYm91bmRTY3JvbGxIYW5kbGVyKTsKICAgICAgICAgICAgdGhpcy5fYm91bmRTY3JvbGxIYW5kbGVyID0gbnVsbDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRW5hYmxlcyBvciBkaXNhYmxlcyB0aGUgc2Nyb2xsIGV2ZW50IGxpc3RlbmVyLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IHllcyBUcnVlIHRvIGFkZCB0aGUgZXZlbnQsIEZhbHNlIHRvIHJlbW92ZSBpdC4KICAgICAgICovCiAgICAgIHRvZ2dsZVNjcm9sbExpc3RlbmVyOiBmdW5jdGlvbih5ZXMpIHsKICAgICAgICB0aGlzLl9zaG91bGRIYXZlTGlzdGVuZXIgPSB5ZXM7CiAgICAgICAgdGhpcy5fdG9nZ2xlU2Nyb2xsTGlzdGVuZXIoeWVzLCB0aGlzLnNjcm9sbFRhcmdldCk7CiAgICAgIH0KCiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNiBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIHZhciBJT1MgPSBuYXZpZ2F0b3IudXNlckFnZW50Lm1hdGNoKC9pUCg/OmhvbmV8YWQ7KD86IFU7KT8gQ1BVKSBPUyAoXGQrKS8pOwogICAgdmFyIElPU19UT1VDSF9TQ1JPTExJTkcgPSBJT1MgJiYgSU9TWzFdID49IDg7CiAgICB2YXIgREVGQVVMVF9QSFlTSUNBTF9DT1VOVCA9IDM7CiAgICB2YXIgSElEREVOX1kgPSAnLTEwMDAwcHgnOwogICAgdmFyIFNFQ1JFVF9UQUJJTkRFWCA9IC0xMDA7CgogICAgLyoqCgogICAgYGlyb24tbGlzdGAgZGlzcGxheXMgYSB2aXJ0dWFsLCAnaW5maW5pdGUnIGxpc3QuIFRoZSB0ZW1wbGF0ZSBpbnNpZGUKICAgIHRoZSBpcm9uLWxpc3QgZWxlbWVudCByZXByZXNlbnRzIHRoZSBET00gdG8gY3JlYXRlIGZvciBlYWNoIGxpc3QgaXRlbS4KICAgIFRoZSBgaXRlbXNgIHByb3BlcnR5IHNwZWNpZmllcyBhbiBhcnJheSBvZiBsaXN0IGl0ZW0gZGF0YS4KCiAgICBGb3IgcGVyZm9ybWFuY2UgcmVhc29ucywgbm90IGV2ZXJ5IGl0ZW0gaW4gdGhlIGxpc3QgaXMgcmVuZGVyZWQgYXQgb25jZTsKICAgIGluc3RlYWQgYSBzbWFsbCBzdWJzZXQgb2YgYWN0dWFsIHRlbXBsYXRlIGVsZW1lbnRzICooZW5vdWdoIHRvIGZpbGwgdGhlCiAgICB2aWV3cG9ydCkqIGFyZSByZW5kZXJlZCBhbmQgcmV1c2VkIGFzIHRoZSB1c2VyIHNjcm9sbHMuIEFzIHN1Y2gsIGl0IGlzIGltcG9ydGFudAogICAgdGhhdCBhbGwgc3RhdGUgb2YgdGhlIGxpc3QgdGVtcGxhdGUgaXMgYm91bmQgdG8gdGhlIG1vZGVsIGRyaXZpbmcgaXQsIHNpbmNlIHRoZQogICAgdmlldyBtYXkgYmUgcmV1c2VkIHdpdGggYSBuZXcgbW9kZWwgYXQgYW55IHRpbWUuIFBhcnRpY3VsYXJseSwgYW55IHN0YXRlIHRoYXQKICAgIG1heSBjaGFuZ2UgYXMgdGhlIHJlc3VsdCBvZiBhIHVzZXIgaW50ZXJhY3Rpb24gd2l0aCB0aGUgbGlzdCBpdGVtIG11c3QgYmUgYm91bmQKICAgIHRvIHRoZSBtb2RlbCB0byBhdm9pZCB2aWV3IHN0YXRlIGluY29uc2lzdGVuY3kuCgogICAgIyMjIFNpemluZyBpcm9uLWxpc3QKCiAgICBgaXJvbi1saXN0YCBtdXN0IGVpdGhlciBiZSBleHBsaWNpdGx5IHNpemVkLCBvciBkZWxlZ2F0ZSBzY3JvbGxpbmcgdG8gYW4KICAgIGV4cGxpY2l0bHkgc2l6ZWQgcGFyZW50LiBCeSAiZXhwbGljaXRseSBzaXplZCIsIHdlIG1lYW4gaXQgZWl0aGVyIGhhcyBhbgogICAgZXhwbGljaXQgQ1NTIGBoZWlnaHRgIHByb3BlcnR5IHNldCB2aWEgYSBjbGFzcyBvciBpbmxpbmUgc3R5bGUsIG9yIGVsc2UgaXMgc2l6ZWQKICAgIGJ5IG90aGVyIGxheW91dCBtZWFucyAoZS5nLiB0aGUgYGZsZXhgIG9yIGBmaXRgIGNsYXNzZXMpLgoKICAgICMjIyMgRmxleGJveCAtIFtqc2Jpbl0oaHR0cHM6Ly9qc2Jpbi5jb20vdmVqb25pL2VkaXQ/aHRtbCxvdXRwdXQpCgogICAgYGBgaHRtbAogICAgPHRlbXBsYXRlIGlzPSJ4LWxpc3QiPgogICAgICA8c3R5bGU+CiAgICAgICAgOmhvc3QgewogICAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgICBoZWlnaHQ6IDEwMHZoOwogICAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgfQoKICAgICAgICBpcm9uLWxpc3QgewogICAgICAgICAgZmxleDogMSAxIGF1dG87CiAgICAgICAgfQogICAgICA8L3N0eWxlPgogICAgICA8YXBwLXRvb2xiYXI+QXBwIG5hbWU8L2FwcC10b29sYmFyPgogICAgICA8aXJvbi1saXN0IGl0ZW1zPSJbW2l0ZW1zXV0iPgogICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgIDxkaXY+CiAgICAgICAgICAgIC4uLgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9pcm9uLWxpc3Q+CiAgICA8L3RlbXBsYXRlPgogICAgYGBgCiAgICAjIyMjIEV4cGxpY2l0IHNpemUgLSBbanNiaW5dKGh0dHBzOi8vanNiaW4uY29tL3ZvcHVjdXMvZWRpdD9odG1sLG91dHB1dCkKICAgIGBgYGh0bWwKICAgIDx0ZW1wbGF0ZSBpcz0ieC1saXN0Ij4KICAgICAgPHN0eWxlPgogICAgICAgIDpob3N0IHsKICAgICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIH0KCiAgICAgICAgaXJvbi1saXN0IHsKICAgICAgICAgIGhlaWdodDogMTAwdmg7IC8qIGRvbid0IHVzZSAlIHZhbHVlcyB1bmxlc3MgdGhlIHBhcmVudCBlbGVtZW50IGlzIHNpemVkLgogICAgKlwvCiAgICAgICAgfQogICAgICA8L3N0eWxlPgogICAgICA8aXJvbi1saXN0IGl0ZW1zPSJbW2l0ZW1zXV0iPgogICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgIDxkaXY+CiAgICAgICAgICAgIC4uLgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9pcm9uLWxpc3Q+CiAgICA8L3RlbXBsYXRlPgogICAgYGBgCiAgICAjIyMjIE1haW4gZG9jdW1lbnQgc2Nyb2xsaW5nIC0KICAgIFtqc2Jpbl0oaHR0cHM6Ly9qc2Jpbi5jb20vd2V2aXJvdy9lZGl0P2h0bWwsb3V0cHV0KQogICAgYGBgaHRtbAogICAgPGhlYWQ+CiAgICAgIDxzdHlsZT4KICAgICAgICBib2R5IHsKICAgICAgICAgIGhlaWdodDogMTAwdmg7CiAgICAgICAgICBtYXJnaW46IDA7CiAgICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICB9CgogICAgICAgIGFwcC10b29sYmFyIHsKICAgICAgICAgIHBvc2l0aW9uOiBmaXhlZDsKICAgICAgICAgIHRvcDogMDsKICAgICAgICAgIGxlZnQ6IDA7CiAgICAgICAgICByaWdodDogMDsKICAgICAgICB9CgogICAgICAgIGlyb24tbGlzdCB7CiAgICAgICAgICAvKiBhZGQgcGFkZGluZyBzaW5jZSB0aGUgYXBwLXRvb2xiYXIgaXMgZml4ZWQgYXQgdGhlIHRvcCAqXC8KICAgICAgICAgIHBhZGRpbmctdG9wOiA2NHB4OwogICAgICAgIH0KICAgICAgPC9zdHlsZT4KICAgIDwvaGVhZD4KICAgIDxib2R5PgogICAgICA8YXBwLXRvb2xiYXI+QXBwIG5hbWU8L2FwcC10b29sYmFyPgogICAgICA8aXJvbi1saXN0IHNjcm9sbC10YXJnZXQ9ImRvY3VtZW50Ij4KICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICA8ZGl2PgogICAgICAgICAgICAuLi4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvaXJvbi1saXN0PgogICAgPC9ib2R5PgogICAgYGBgCgogICAgYGlyb24tbGlzdGAgbXVzdCBiZSBnaXZlbiBhIGA8dGVtcGxhdGU+YCB3aGljaCBjb250YWlucyBleGFjdGx5IG9uZSBlbGVtZW50LiBJbgogICAgdGhlIGV4YW1wbGVzIGFib3ZlIHdlIHVzZWQgYSBgPGRpdj5gLCBidXQgeW91IGNhbiBwcm92aWRlIGFueSBlbGVtZW50IChpbmNsdWRpbmcKICAgIGN1c3RvbSBlbGVtZW50cykuCgogICAgIyMjIFRlbXBsYXRlIG1vZGVsCgogICAgTGlzdCBpdGVtIHRlbXBsYXRlcyBzaG91bGQgYmluZCB0byB0ZW1wbGF0ZSBtb2RlbHMgb2YgdGhlIGZvbGxvd2luZyBzdHJ1Y3R1cmU6CgogICAgYGBganMKICAgIHsKICAgICAgaW5kZXg6IDAsICAgICAgICAvLyBpbmRleCBpbiB0aGUgaXRlbSBhcnJheQogICAgICBzZWxlY3RlZDogZmFsc2UsIC8vIHRydWUgaWYgdGhlIGN1cnJlbnQgaXRlbSBpcyBzZWxlY3RlZAogICAgICB0YWJJbmRleDogLTEsICAgIC8vIGEgZHluYW1pY2FsbHkgZ2VuZXJhdGVkIHRhYkluZGV4IGZvciBmb2N1cyBtYW5hZ2VtZW50CiAgICAgIGl0ZW06IHt9ICAgICAgICAgLy8gdXNlciBkYXRhIGNvcnJlc3BvbmRpbmcgdG8gaXRlbXNbaW5kZXhdCiAgICB9CiAgICBgYGAKCiAgICBBbHRlcm5hdGl2ZWx5LCB5b3UgY2FuIGNoYW5nZSB0aGUgcHJvcGVydHkgbmFtZSB1c2VkIGFzIGRhdGEgaW5kZXggYnkgY2hhbmdpbmcKICAgIHRoZSBgaW5kZXhBc2AgcHJvcGVydHkuIFRoZSBgYXNgIHByb3BlcnR5IGRlZmluZXMgdGhlIG5hbWUgb2YgdGhlIHZhcmlhYmxlIHRvCiAgICBhZGQgdG8gdGhlIGJpbmRpbmcgc2NvcGUgZm9yIHRoZSBhcnJheS4KCiAgICBGb3IgZXhhbXBsZSwgZ2l2ZW4gdGhlIGZvbGxvd2luZyBgZGF0YWAgYXJyYXk6CgogICAgIyMjIyMgZGF0YS5qc29uCgogICAgYGBganMKICAgIFsKICAgICAgeyJuYW1lIjogIkJvYiJ9LAogICAgICB7Im5hbWUiOiAiVGltIn0sCiAgICAgIHsibmFtZSI6ICJNaWtlIn0KICAgIF0KICAgIGBgYAoKICAgIFRoZSBmb2xsb3dpbmcgY29kZSB3b3VsZCByZW5kZXIgdGhlIGxpc3QgKG5vdGUgdGhlIG5hbWUgcHJvcGVydHkgaXMgYm91bmQgZnJvbQogICAgdGhlIG1vZGVsIG9iamVjdCBwcm92aWRlZCB0byB0aGUgdGVtcGxhdGUgc2NvcGUpOgoKICAgIGBgYGh0bWwKICAgIDxpcm9uLWFqYXggdXJsPSJkYXRhLmpzb24iIGxhc3QtcmVzcG9uc2U9Int7ZGF0YX19IiBhdXRvPjwvaXJvbi1hamF4PgogICAgPGlyb24tbGlzdCBpdGVtcz0iW1tkYXRhXV0iIGFzPSJpdGVtIj4KICAgICAgPHRlbXBsYXRlPgogICAgICAgIDxkaXY+CiAgICAgICAgICBOYW1lOiBbW2l0ZW0ubmFtZV1dCiAgICAgICAgPC9kaXY+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L2lyb24tbGlzdD4KICAgIGBgYAoKICAgICMjIyBHcmlkIGxheW91dAoKICAgIGBpcm9uLWxpc3RgIHN1cHBvcnRzIGEgZ3JpZCBsYXlvdXQgaW4gYWRkaXRpb24gdG8gbGluZWFyIGxheW91dCBieSBzZXR0aW5nCiAgICB0aGUgYGdyaWRgIGF0dHJpYnV0ZS4gIEluIHRoaXMgY2FzZSwgdGhlIGxpc3QgdGVtcGxhdGUgaXRlbSBtdXN0IGhhdmUgYm90aCBmaXhlZAogICAgd2lkdGggYW5kIGhlaWdodCAoZS5nLiB2aWEgQ1NTKS4gQmFzZWQgb24gdGhpcywgdGhlIG51bWJlciBvZiBpdGVtcwogICAgcGVyIHJvdyBhcmUgZGV0ZXJtaW5lZCBhdXRvbWF0aWNhbGx5IGJhc2VkIG9uIHRoZSBzaXplIG9mIHRoZSBsaXN0IHZpZXdwb3J0LgoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgYGlyb24tbGlzdGAgYXV0b21hdGljYWxseSBtYW5hZ2VzIHRoZSBmb2N1cyBzdGF0ZSBmb3IgdGhlIGl0ZW1zLiBJdCBhbHNvCiAgICBwcm92aWRlcyBhIGB0YWJJbmRleGAgcHJvcGVydHkgd2l0aGluIHRoZSB0ZW1wbGF0ZSBzY29wZSB0aGF0IGNhbiBiZSB1c2VkIGZvcgogICAga2V5Ym9hcmQgbmF2aWdhdGlvbi4gRm9yIGV4YW1wbGUsIHVzZXJzIGNhbiBwcmVzcyB0aGUgdXAgYW5kIGRvd24ga2V5cyB0byBtb3ZlCiAgICB0byBwcmV2aW91cyBhbmQgbmV4dCBpdGVtcyBpbiB0aGUgbGlzdDoKCiAgICBgYGBodG1sCiAgICA8aXJvbi1saXN0IGl0ZW1zPSJbW2RhdGFdXSIgYXM9Iml0ZW0iPgogICAgICA8dGVtcGxhdGU+CiAgICAgICAgPGRpdiB0YWJpbmRleCQ9IltbdGFiSW5kZXhdXSI+CiAgICAgICAgICBOYW1lOiBbW2l0ZW0ubmFtZV1dCiAgICAgICAgPC9kaXY+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L2lyb24tbGlzdD4KICAgIGBgYAoKICAgICMjIyBTdHlsaW5nCgogICAgWW91IGNhbiB1c2UgdGhlIGAtLWlyb24tbGlzdC1pdGVtcy1jb250YWluZXJgIG1peGluIHRvIHN0eWxlIHRoZSBjb250YWluZXIgb2YKICAgIGl0ZW1zOgoKICAgIGBgYGNzcwogICAgaXJvbi1saXN0IHsKICAgICAtLWlyb24tbGlzdC1pdGVtcy1jb250YWluZXI6IHsKICAgICAgICBtYXJnaW46IGF1dG87CiAgICAgIH07CiAgICB9CiAgICBgYGAKCiAgICAjIyMgUmVzaXppbmcKCiAgICBgaXJvbi1saXN0YCBsYXlzIG91dCB0aGUgaXRlbXMgd2hlbiBpdCByZWNlaXZlcyBhIG5vdGlmaWNhdGlvbiB2aWEgdGhlCiAgICBgaXJvbi1yZXNpemVgIGV2ZW50LiBUaGlzIGV2ZW50IGlzIGZpcmVkIGJ5IGFueSBlbGVtZW50IHRoYXQgaW1wbGVtZW50cwogICAgYElyb25SZXNpemFibGVCZWhhdmlvcmAuCgogICAgQnkgZGVmYXVsdCwgZWxlbWVudHMgc3VjaCBhcyBgaXJvbi1wYWdlc2AsIGBwYXBlci10YWJzYCBvciBgcGFwZXItZGlhbG9nYCB3aWxsCiAgICB0cmlnZ2VyIHRoaXMgZXZlbnQgYXV0b21hdGljYWxseS4gSWYgeW91IGhpZGUgdGhlIGxpc3QgbWFudWFsbHkgKGUuZy4geW91IHVzZQogICAgYGRpc3BsYXk6IG5vbmVgKSB5b3UgbWlnaHQgd2FudCB0byBpbXBsZW1lbnQgYElyb25SZXNpemFibGVCZWhhdmlvcmAgb3IgZmlyZQogICAgdGhpcyBldmVudCBtYW51YWxseSByaWdodCBhZnRlciB0aGUgbGlzdCBiZWNhbWUgdmlzaWJsZSBhZ2Fpbi4gRm9yIGV4YW1wbGU6CgogICAgYGBganMKICAgIGRvY3VtZW50LnF1ZXJ5U2VsZWN0b3IoJ2lyb24tbGlzdCcpLmZpcmUoJ2lyb24tcmVzaXplJyk7CiAgICBgYGAKCiAgICAjIyMgV2hlbiBzaG91bGQgYDxpcm9uLWxpc3Q+YCBiZSB1c2VkPwoKICAgIGBpcm9uLWxpc3RgIHNob3VsZCBiZSB1c2VkIHdoZW4gYSBwYWdlIGhhcyBzaWduaWZpY2FudGx5IG1vcmUgRE9NIG5vZGVzIHRoYW4gdGhlCiAgICBvbmVzIHZpc2libGUgb24gdGhlIHNjcmVlbi4gZS5nLiB0aGUgcGFnZSBoYXMgNTAwIG5vZGVzLCBidXQgb25seSAyMCBhcmUgdmlzaWJsZQogICAgYXQgYSB0aW1lLiBUaGlzIGlzIHdoeSB3ZSByZWZlciB0byBpdCBhcyBhIGB2aXJ0dWFsYCBsaXN0LiBJbiB0aGlzIGNhc2UsIGEKICAgIGBkb20tcmVwZWF0YCB3aWxsIHN0aWxsIGNyZWF0ZSA1MDAgbm9kZXMgd2hpY2ggY291bGQgc2xvdyBkb3duIHRoZSB3ZWIgYXBwLCBidXQKICAgIGBpcm9uLWxpc3RgIHdpbGwgb25seSBjcmVhdGUgMjAuCgogICAgSG93ZXZlciwgaGF2aW5nIGFuIGBpcm9uLWxpc3RgIGRvZXMgbm90IG1lYW4gdGhhdCB5b3UgY2FuIGxvYWQgYWxsIHRoZSBkYXRhIGF0CiAgICBvbmNlLiBTYXkgeW91IGhhdmUgYSBtaWxsaW9uIHJlY29yZHMgaW4gdGhlIGRhdGFiYXNlLCB5b3Ugd2FudCB0byBzcGxpdCB0aGUgZGF0YQogICAgaW50byBwYWdlcyBzbyB5b3UgY2FuIGJyaW5nIGluIGEgcGFnZSBhdCB0aGUgdGltZS4gVGhlIHBhZ2UgY291bGQgY29udGFpbiA1MDAKICAgIGl0ZW1zLCBhbmQgaXJvbi1saXN0IHdpbGwgb25seSByZW5kZXIgMjAuCgogICAgQGVsZW1lbnQgaXJvbi1saXN0CiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KCiAgICAgIEBtZWRpYSBvbmx5IHNjcmVlbiBhbmQgKC13ZWJraXQtbWF4LWRldmljZS1waXhlbC1yYXRpbzogMSkgewogICAgICAgIDpob3N0IHsKICAgICAgICAgIHdpbGwtY2hhbmdlOiB0cmFuc2Zvcm07CiAgICAgICAgfQogICAgICB9CgogICAgICAjaXRlbXMgewogICAgICAgIEBhcHBseSAtLWlyb24tbGlzdC1pdGVtcy1jb250YWluZXI7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CgogICAgICA6aG9zdCg6bm90KFtncmlkXSkpICNpdGVtcyA+IDo6c2xvdHRlZCgqKSB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIH0KCiAgICAgICNpdGVtcyA+IDo6c2xvdHRlZCgqKSB7CiAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgICBtYXJnaW46IDA7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHRvcDogMDsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxhcnJheS1zZWxlY3RvciBpZD0ic2VsZWN0b3IiIGl0ZW1zPSJ7e2l0ZW1zfX0iIHNlbGVjdGVkPSJ7e3NlbGVjdGVkSXRlbXN9fSIgc2VsZWN0ZWQtaXRlbT0ie3tzZWxlY3RlZEl0ZW19fSI+PC9hcnJheS1zZWxlY3Rvcj4KCiAgICA8ZGl2IGlkPSJpdGVtcyI+CiAgICAgIDxzbG90Pjwvc2xvdD4KICAgIDwvZGl2PgpgLAoKICAgICAgaXM6ICdpcm9uLWxpc3QnLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBBbiBhcnJheSBjb250YWluaW5nIGl0ZW1zIGRldGVybWluaW5nIGhvdyBtYW55IGluc3RhbmNlcyBvZiB0aGUgdGVtcGxhdGUKICAgICAgICAgKiB0byBzdGFtcCBhbmQgdGhhdCB0aGF0IGVhY2ggdGVtcGxhdGUgaW5zdGFuY2Ugc2hvdWxkIGJpbmQgdG8uCiAgICAgICAgICovCiAgICAgICAgaXRlbXM6IHt0eXBlOiBBcnJheX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBuYW1lIG9mIHRoZSB2YXJpYWJsZSB0byBhZGQgdG8gdGhlIGJpbmRpbmcgc2NvcGUgZm9yIHRoZSBhcnJheQogICAgICAgICAqIGVsZW1lbnQgYXNzb2NpYXRlZCB3aXRoIGEgZ2l2ZW4gdGVtcGxhdGUgaW5zdGFuY2UuCiAgICAgICAgICovCiAgICAgICAgYXM6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnaXRlbSd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgdmFyaWFibGUgdG8gYWRkIHRvIHRoZSBiaW5kaW5nIHNjb3BlIHdpdGggdGhlIGluZGV4CiAgICAgICAgICogZm9yIHRoZSByb3cuCiAgICAgICAgICovCiAgICAgICAgaW5kZXhBczoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdpbmRleCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGUgdmFyaWFibGUgdG8gYWRkIHRvIHRoZSBiaW5kaW5nIHNjb3BlIHRvIGluZGljYXRlCiAgICAgICAgICogaWYgdGhlIHJvdyBpcyBzZWxlY3RlZC4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZEFzOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ3NlbGVjdGVkJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFdoZW4gdHJ1ZSwgdGhlIGxpc3QgaXMgcmVuZGVyZWQgYXMgYSBncmlkLiBHcmlkIGl0ZW1zIG11c3QgaGF2ZQogICAgICAgICAqIGZpeGVkIHdpZHRoIGFuZCBoZWlnaHQgc2V0IHZpYSBDU1MuIGUuZy4KICAgICAgICAgKgogICAgICAgICAqIGBgYGh0bWwKICAgICAgICAgKiA8aXJvbi1saXN0IGdyaWQ+CiAgICAgICAgICogICA8dGVtcGxhdGU+CiAgICAgICAgICogICAgICA8ZGl2IHN0eWxlPSJ3aWR0aDogMTAwcHg7IGhlaWdodDogMTAwcHg7Ij4gMTAweDEwMCA8L2Rpdj4KICAgICAgICAgKiAgIDwvdGVtcGxhdGU+CiAgICAgICAgICogPC9pcm9uLWxpc3Q+CiAgICAgICAgICogYGBgCiAgICAgICAgICovCiAgICAgICAgZ3JpZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgIG9ic2VydmVyOiAnX2dyaWRDaGFuZ2VkJwogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFdoZW4gdHJ1ZSwgdGFwcGluZyBhIHJvdyB3aWxsIHNlbGVjdCB0aGUgaXRlbSwgcGxhY2luZyBpdHMgZGF0YSBtb2RlbAogICAgICAgICAqIGluIHRoZSBzZXQgb2Ygc2VsZWN0ZWQgaXRlbXMgcmV0cmlldmFibGUgdmlhIHRoZSBzZWxlY3Rpb24gcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlIHRoYXQgdGFwcGluZyBmb2N1c2FibGUgZWxlbWVudHMgd2l0aGluIHRoZSBsaXN0IGl0ZW0gd2lsbCBub3QKICAgICAgICAgKiByZXN1bHQgaW4gc2VsZWN0aW9uLCBzaW5jZSB0aGV5IGFyZSBwcmVzdW1lZCB0byBoYXZlIHRoZWlyICogb3duIGFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3Rpb25FbmFibGVkOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogV2hlbiBgbXVsdGlTZWxlY3Rpb25gIGlzIGZhbHNlLCB0aGlzIGlzIHRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbSwgb3IKICAgICAgICAgKiBgbnVsbGAgaWYgbm8gaXRlbSBpcyBzZWxlY3RlZC4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZEl0ZW06IHt0eXBlOiBPYmplY3QsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFdoZW4gYG11bHRpU2VsZWN0aW9uYCBpcyB0cnVlLCB0aGlzIGlzIGFuIGFycmF5IHRoYXQgY29udGFpbnMgdGhlCiAgICAgICAgICogc2VsZWN0ZWQgaXRlbXMuCiAgICAgICAgICovCiAgICAgICAgc2VsZWN0ZWRJdGVtczoge3R5cGU6IE9iamVjdCwgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogV2hlbiBgdHJ1ZWAsIG11bHRpcGxlIGl0ZW1zIG1heSBiZSBzZWxlY3RlZCBhdCBvbmNlIChpbiB0aGlzIGNhc2UsCiAgICAgICAgICogYHNlbGVjdGVkYCBpcyBhbiBhcnJheSBvZiBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbXMpLiAgV2hlbiBgZmFsc2VgLAogICAgICAgICAqIG9ubHkgb25lIGl0ZW0gbWF5IGJlIHNlbGVjdGVkIGF0IGEgdGltZS4KICAgICAgICAgKi8KICAgICAgICBtdWx0aVNlbGVjdGlvbjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBvZmZzZXQgdG9wIGZyb20gdGhlIHNjcm9sbGluZyBlbGVtZW50IHRvIHRoZSBpcm9uLWxpc3QgZWxlbWVudC4KICAgICAgICAgKiBUaGlzIHZhbHVlIGNhbiBiZSBjb21wdXRlZCB1c2luZyB0aGUgcG9zaXRpb24gcmV0dXJuZWQgYnkKICAgICAgICAgKiBgZ2V0Qm91bmRpbmdDbGllbnRSZWN0KClgIGFsdGhvdWdoIGl0J3MgcHJlZmVycmVkIHRvIHVzZSBhIGNvbnN0YW50IHZhbHVlCiAgICAgICAgICogd2hlbiBwb3NzaWJsZS4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgcHJvcGVydHkgaXMgdXNlZnVsIHdoZW4gYW4gZXh0ZXJuYWwgc2Nyb2xsaW5nIGVsZW1lbnQgaXMgdXNlZCBhbmQKICAgICAgICAgKiB0aGVyZSdzIHNvbWUgb2Zmc2V0IGJldHdlZW4gdGhlIHNjcm9sbGluZyBlbGVtZW50IGFuZCB0aGUgbGlzdC4gRm9yCiAgICAgICAgICogZXhhbXBsZTogYSBoZWFkZXIgaXMgcGxhY2VkIGFib3ZlIHRoZSBsaXN0LgogICAgICAgICAqLwogICAgICAgIHNjcm9sbE9mZnNldDoge3R5cGU6IE51bWJlciwgdmFsdWU6IDB9CiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6IFsKICAgICAgICAnX2l0ZW1zQ2hhbmdlZChpdGVtcy4qKScsCiAgICAgICAgJ19zZWxlY3Rpb25FbmFibGVkQ2hhbmdlZChzZWxlY3Rpb25FbmFibGVkKScsCiAgICAgICAgJ19tdWx0aVNlbGVjdGlvbkNoYW5nZWQobXVsdGlTZWxlY3Rpb24pJywKICAgICAgICAnX3NldE92ZXJmbG93KHNjcm9sbFRhcmdldCwgc2Nyb2xsT2Zmc2V0KScKICAgICAgXSwKCiAgICAgIGJlaGF2aW9yczogWwogICAgICAgIFRlbXBsYXRpemVyLAogICAgICAgIElyb25SZXNpemFibGVCZWhhdmlvciwKICAgICAgICBJcm9uU2Nyb2xsVGFyZ2V0QmVoYXZpb3IsCiAgICAgICAgT3B0aW9uYWxNdXRhYmxlRGF0YUJlaGF2aW9yCiAgICAgIF0sCgogICAgICAvKioKICAgICAgICogVGhlIHJhdGlvIG9mIGhpZGRlbiB0aWxlcyB0aGF0IHNob3VsZCByZW1haW4gaW4gdGhlIHNjcm9sbCBkaXJlY3Rpb24uCiAgICAgICAqIFJlY29tbWVuZGVkIHZhbHVlIH4wLjUsIHNvIGl0IHdpbGwgZGlzdHJpYnV0ZSB0aWxlcyBldmVubHkgaW4gYm90aAogICAgICAgKiBkaXJlY3Rpb25zLgogICAgICAgKi8KICAgICAgX3JhdGlvOiAwLjUsCgogICAgICAvKioKICAgICAgICogVGhlIHBhZGRpbmctdG9wIHZhbHVlIGZvciB0aGUgbGlzdC4KICAgICAgICovCiAgICAgIF9zY3JvbGxlclBhZGRpbmdUb3A6IDAsCgogICAgICAvKioKICAgICAgICogVGhpcyB2YWx1ZSBpcyBhIGNhY2hlZCB2YWx1ZSBvZiBgc2Nyb2xsVG9wYCBmcm9tIHRoZSBsYXN0IGBzY3JvbGxgIGV2ZW50LgogICAgICAgKi8KICAgICAgX3Njcm9sbFBvc2l0aW9uOiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBzdW0gb2YgdGhlIGhlaWdodHMgb2YgYWxsIHRoZSB0aWxlcyBpbiB0aGUgRE9NLgogICAgICAgKi8KICAgICAgX3BoeXNpY2FsU2l6ZTogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgYXZlcmFnZSBgb2Zmc2V0SGVpZ2h0YCBvZiB0aGUgdGlsZXMgb2JzZXJ2ZWQgdGlsbCBub3cuCiAgICAgICAqLwogICAgICBfcGh5c2ljYWxBdmVyYWdlOiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBudW1iZXIgb2YgdGlsZXMgd2hpY2ggYG9mZnNldEhlaWdodGAgPiAwIG9ic2VydmVkIHVudGlsIG5vdy4KICAgICAgICovCiAgICAgIF9waHlzaWNhbEF2ZXJhZ2VDb3VudDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgWSBwb3NpdGlvbiBvZiB0aGUgaXRlbSByZW5kZXJlZCBpbiB0aGUgYF9waHlzaWNhbFN0YXJ0YAogICAgICAgKiB0aWxlIHJlbGF0aXZlIHRvIHRoZSBzY3JvbGxpbmcgbGlzdC4KICAgICAgICovCiAgICAgIF9waHlzaWNhbFRvcDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbnVtYmVyIG9mIGl0ZW1zIGluIHRoZSBsaXN0LgogICAgICAgKi8KICAgICAgX3ZpcnR1YWxDb3VudDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgZXN0aW1hdGVkIHNjcm9sbCBoZWlnaHQgYmFzZWQgb24gYF9waHlzaWNhbEF2ZXJhZ2VgCiAgICAgICAqLwogICAgICBfZXN0U2Nyb2xsSGVpZ2h0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBzY3JvbGwgaGVpZ2h0IG9mIHRoZSBkb20gbm9kZQogICAgICAgKi8KICAgICAgX3Njcm9sbEhlaWdodDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgaGVpZ2h0IG9mIHRoZSBsaXN0LiBUaGlzIGlzIHJlZmVycmVkIGFzIHRoZSB2aWV3cG9ydCBpbiB0aGUgY29udGV4dCBvZgogICAgICAgKiBsaXN0LgogICAgICAgKi8KICAgICAgX3ZpZXdwb3J0SGVpZ2h0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSB3aWR0aCBvZiB0aGUgbGlzdC4gVGhpcyBpcyByZWZlcnJlZCBhcyB0aGUgdmlld3BvcnQgaW4gdGhlIGNvbnRleHQgb2YKICAgICAgICogbGlzdC4KICAgICAgICovCiAgICAgIF92aWV3cG9ydFdpZHRoOiAwLAoKICAgICAgLyoqCiAgICAgICAqIEFuIGFycmF5IG9mIERPTSBub2RlcyB0aGF0IGFyZSBjdXJyZW50bHkgaW4gdGhlIHRyZWUKICAgICAgICogQHR5cGUgez9BcnJheTwhSFRNTEVsZW1lbnQ+fQogICAgICAgKi8KICAgICAgX3BoeXNpY2FsSXRlbXM6IG51bGwsCgogICAgICAvKioKICAgICAgICogQW4gYXJyYXkgb2YgaGVpZ2h0cyBmb3IgZWFjaCBpdGVtIGluIGBfcGh5c2ljYWxJdGVtc2AKICAgICAgICogQHR5cGUgez9BcnJheTxudW1iZXI+fQogICAgICAgKi8KICAgICAgX3BoeXNpY2FsU2l6ZXM6IG51bGwsCgogICAgICAvKioKICAgICAgICogQSBjYWNoZWQgdmFsdWUgZm9yIHRoZSBmaXJzdCB2aXNpYmxlIGluZGV4LgogICAgICAgKiBTZWUgYGZpcnN0VmlzaWJsZUluZGV4YAogICAgICAgKiBAdHlwZSB7P251bWJlcn0KICAgICAgICovCiAgICAgIF9maXJzdFZpc2libGVJbmRleFZhbDogbnVsbCwKCiAgICAgIC8qKgogICAgICAgKiBBIGNhY2hlZCB2YWx1ZSBmb3IgdGhlIGxhc3QgdmlzaWJsZSBpbmRleC4KICAgICAgICogU2VlIGBsYXN0VmlzaWJsZUluZGV4YAogICAgICAgKiBAdHlwZSB7P251bWJlcn0KICAgICAgICovCiAgICAgIF9sYXN0VmlzaWJsZUluZGV4VmFsOiBudWxsLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBtYXggbnVtYmVyIG9mIHBhZ2VzIHRvIHJlbmRlci4gT25lIHBhZ2UgaXMgZXF1aXZhbGVudCB0byB0aGUgaGVpZ2h0IG9mCiAgICAgICAqIHRoZSBsaXN0LgogICAgICAgKi8KICAgICAgX21heFBhZ2VzOiAyLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBjdXJyZW50bHkgZm9jdXNlZCBwaHlzaWNhbCBpdGVtLgogICAgICAgKi8KICAgICAgX2ZvY3VzZWRJdGVtOiBudWxsLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSB2aXJ0dWFsIGluZGV4IG9mIHRoZSBmb2N1c2VkIGl0ZW0uCiAgICAgICAqLwogICAgICBfZm9jdXNlZFZpcnR1YWxJbmRleDogLTEsCgogICAgICAvKioKICAgICAgICogVGhlIHBoeXNpY2FsIGluZGV4IG9mIHRoZSBmb2N1c2VkIGl0ZW0uCiAgICAgICAqLwogICAgICBfZm9jdXNlZFBoeXNpY2FsSW5kZXg6IC0xLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSB0aGUgaXRlbSB0aGF0IGlzIGZvY3VzZWQgaWYgaXQgaXMgbW92ZWQgb2Zmc2NyZWVuLgogICAgICAgKiBAcHJpdmF0ZSB7P0hUTUxFbGVtZW50fQogICAgICAgKi8KICAgICAgX29mZnNjcmVlbkZvY3VzZWRJdGVtOiBudWxsLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBpdGVtIHRoYXQgYmFja2ZpbGxzIHRoZSBgX29mZnNjcmVlbkZvY3VzZWRJdGVtYCBpbiB0aGUgcGh5c2ljYWwgaXRlbXMKICAgICAgICogbGlzdCB3aGVuIHRoYXQgaXRlbSBpcyBtb3ZlZCBvZmZzY3JlZW4uCiAgICAgICAqIEB0eXBlIHs/SFRNTEVsZW1lbnR9CiAgICAgICAqLwogICAgICBfZm9jdXNCYWNrZmlsbEl0ZW06IG51bGwsCgogICAgICAvKioKICAgICAgICogVGhlIG1heGltdW0gaXRlbXMgcGVyIHJvdwogICAgICAgKi8KICAgICAgX2l0ZW1zUGVyUm93OiAxLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSB3aWR0aCBvZiBlYWNoIGdyaWQgaXRlbQogICAgICAgKi8KICAgICAgX2l0ZW1XaWR0aDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgaGVpZ2h0IG9mIHRoZSByb3cgaW4gZ3JpZCBsYXlvdXQuCiAgICAgICAqLwogICAgICBfcm93SGVpZ2h0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBjb3N0IG9mIHN0YW1waW5nIGEgdGVtcGxhdGUgaW4gbXMuCiAgICAgICAqLwogICAgICBfdGVtcGxhdGVDb3N0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIE5lZWRlZCB0byBwYXNzIGV2ZW50Lm1vZGVsIHByb3BlcnR5IHRvIGRlY2xhcmF0aXZlIGV2ZW50IGhhbmRsZXJzIC0KICAgICAgICogc2VlIHBvbHltZXIvcG9seW1lciM0MzM5LgogICAgICAgKi8KICAgICAgX3BhcmVudE1vZGVsOiB0cnVlLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBib3R0b20gb2YgdGhlIHBoeXNpY2FsIGNvbnRlbnQuCiAgICAgICAqLwogICAgICBnZXQgX3BoeXNpY2FsQm90dG9tKCkgewogICAgICAgIHJldHVybiB0aGlzLl9waHlzaWNhbFRvcCArIHRoaXMuX3BoeXNpY2FsU2l6ZTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgYm90dG9tIG9mIHRoZSBzY3JvbGwuCiAgICAgICAqLwogICAgICBnZXQgX3Njcm9sbEJvdHRvbSgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fc2Nyb2xsUG9zaXRpb24gKyB0aGlzLl92aWV3cG9ydEhlaWdodDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbi10aCBpdGVtIHJlbmRlcmVkIGluIHRoZSBsYXN0IHBoeXNpY2FsIGl0ZW0uCiAgICAgICAqLwogICAgICBnZXQgX3ZpcnR1YWxFbmQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX3ZpcnR1YWxTdGFydCArIHRoaXMuX3BoeXNpY2FsQ291bnQgLSAxOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBoZWlnaHQgb2YgdGhlIHBoeXNpY2FsIGNvbnRlbnQgdGhhdCBpc24ndCBvbiB0aGUgc2NyZWVuLgogICAgICAgKi8KICAgICAgZ2V0IF9oaWRkZW5Db250ZW50U2l6ZSgpIHsKICAgICAgICB2YXIgc2l6ZSA9CiAgICAgICAgICAgIHRoaXMuZ3JpZCA/IHRoaXMuX3BoeXNpY2FsUm93cyAqIHRoaXMuX3Jvd0hlaWdodCA6IHRoaXMuX3BoeXNpY2FsU2l6ZTsKICAgICAgICByZXR1cm4gc2l6ZSAtIHRoaXMuX3ZpZXdwb3J0SGVpZ2h0OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBwYXJlbnQgbm9kZSBmb3IgdGhlIF91c2VyVGVtcGxhdGUuCiAgICAgICAqLwogICAgICBnZXQgX2l0ZW1zUGFyZW50KCkgewogICAgICAgIHJldHVybiBkb20oZG9tKHRoaXMuX3VzZXJUZW1wbGF0ZSkucGFyZW50Tm9kZSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIG1heGltdW0gc2Nyb2xsIHRvcCB2YWx1ZS4KICAgICAgICovCiAgICAgIGdldCBfbWF4U2Nyb2xsVG9wKCkgewogICAgICAgIHJldHVybiB0aGlzLl9lc3RTY3JvbGxIZWlnaHQgLSB0aGlzLl92aWV3cG9ydEhlaWdodCArIHRoaXMuX3Njcm9sbE9mZnNldDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbGFyZ2VzdCBuLXRoIHZhbHVlIGZvciBhbiBpdGVtIHN1Y2ggdGhhdCBpdCBjYW4gYmUgcmVuZGVyZWQgaW4KICAgICAgICogYF9waHlzaWNhbFN0YXJ0YC4KICAgICAgICovCiAgICAgIGdldCBfbWF4VmlydHVhbFN0YXJ0KCkgewogICAgICAgIHZhciB2aXJ0dWFsQ291bnQgPSB0aGlzLl9jb252ZXJ0SW5kZXhUb0NvbXBsZXRlUm93KHRoaXMuX3ZpcnR1YWxDb3VudCk7CiAgICAgICAgcmV0dXJuIE1hdGgubWF4KDAsIHZpcnR1YWxDb3VudCAtIHRoaXMuX3BoeXNpY2FsQ291bnQpOwogICAgICB9LAoKICAgICAgc2V0IF92aXJ0dWFsU3RhcnQodmFsKSB7CiAgICAgICAgdmFsID0gdGhpcy5fY2xhbXAodmFsLCAwLCB0aGlzLl9tYXhWaXJ0dWFsU3RhcnQpOwogICAgICAgIGlmICh0aGlzLmdyaWQpIHsKICAgICAgICAgIHZhbCA9IHZhbCAtICh2YWwgJSB0aGlzLl9pdGVtc1BlclJvdyk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydFZhbCA9IHZhbDsKICAgICAgfSwKCiAgICAgIGdldCBfdmlydHVhbFN0YXJ0KCkgewogICAgICAgIHJldHVybiB0aGlzLl92aXJ0dWFsU3RhcnRWYWwgfHwgMDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgay10aCB0aWxlIHRoYXQgaXMgYXQgdGhlIHRvcCBvZiB0aGUgc2Nyb2xsaW5nIGxpc3QuCiAgICAgICAqLwogICAgICBzZXQgX3BoeXNpY2FsU3RhcnQodmFsKSB7CiAgICAgICAgdmFsID0gdmFsICUgdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgICBpZiAodmFsIDwgMCkgewogICAgICAgICAgdmFsID0gdGhpcy5fcGh5c2ljYWxDb3VudCArIHZhbDsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuZ3JpZCkgewogICAgICAgICAgdmFsID0gdmFsIC0gKHZhbCAlIHRoaXMuX2l0ZW1zUGVyUm93KTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fcGh5c2ljYWxTdGFydFZhbCA9IHZhbDsKICAgICAgfSwKCiAgICAgIGdldCBfcGh5c2ljYWxTdGFydCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fcGh5c2ljYWxTdGFydFZhbCB8fCAwOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBrLXRoIHRpbGUgdGhhdCBpcyBhdCB0aGUgYm90dG9tIG9mIHRoZSBzY3JvbGxpbmcgbGlzdC4KICAgICAgICovCiAgICAgIGdldCBfcGh5c2ljYWxFbmQoKSB7CiAgICAgICAgcmV0dXJuICh0aGlzLl9waHlzaWNhbFN0YXJ0ICsgdGhpcy5fcGh5c2ljYWxDb3VudCAtIDEpICUKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgfSwKCiAgICAgIHNldCBfcGh5c2ljYWxDb3VudCh2YWwpIHsKICAgICAgICB0aGlzLl9waHlzaWNhbENvdW50VmFsID0gdmFsOwogICAgICB9LAoKICAgICAgZ2V0IF9waHlzaWNhbENvdW50KCkgewogICAgICAgIHJldHVybiB0aGlzLl9waHlzaWNhbENvdW50VmFsIHx8IDA7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQW4gb3B0aW1hbCBwaHlzaWNhbCBzaXplIHN1Y2ggdGhhdCB3ZSB3aWxsIGhhdmUgZW5vdWdoIHBoeXNpY2FsIGl0ZW1zCiAgICAgICAqIHRvIGZpbGwgdXAgdGhlIHZpZXdwb3J0IGFuZCByZWN5Y2xlIHdoZW4gdGhlIHVzZXIgc2Nyb2xscy4KICAgICAgICoKICAgICAgICogVGhpcyBkZWZhdWx0IHZhbHVlIGFzc3VtZXMgdGhhdCB3ZSB3aWxsIGF0IGxlYXN0IGhhdmUgdGhlIGVxdWl2YWxlbnQKICAgICAgICogdG8gYSB2aWV3cG9ydCBvZiBwaHlzaWNhbCBpdGVtcyBhYm92ZSBhbmQgYmVsb3cgdGhlIHVzZXIncyB2aWV3cG9ydC4KICAgICAgICovCiAgICAgIGdldCBfb3B0UGh5c2ljYWxTaXplKCkgewogICAgICAgIHJldHVybiB0aGlzLl92aWV3cG9ydEhlaWdodCA9PT0gMCA/IEluZmluaXR5IDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl92aWV3cG9ydEhlaWdodCAqIHRoaXMuX21heFBhZ2VzOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRydWUgaWYgdGhlIGN1cnJlbnQgbGlzdCBpcyB2aXNpYmxlLgogICAgICAgKi8KICAgICAgZ2V0IF9pc1Zpc2libGUoKSB7CiAgICAgICAgcmV0dXJuIEJvb2xlYW4odGhpcy5vZmZzZXRXaWR0aCB8fCB0aGlzLm9mZnNldEhlaWdodCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogR2V0cyB0aGUgaW5kZXggb2YgdGhlIGZpcnN0IHZpc2libGUgaXRlbSBpbiB0aGUgdmlld3BvcnQuCiAgICAgICAqCiAgICAgICAqIEB0eXBlIHtudW1iZXJ9CiAgICAgICAqLwogICAgICBnZXQgZmlyc3RWaXNpYmxlSW5kZXgoKSB7CiAgICAgICAgdmFyIGlkeCA9IHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4VmFsOwogICAgICAgIGlmIChpZHggPT0gbnVsbCkgewogICAgICAgICAgdmFyIHBoeXNpY2FsT2Zmc2V0ID0gdGhpcy5fcGh5c2ljYWxUb3AgKyB0aGlzLl9zY3JvbGxPZmZzZXQ7CgogICAgICAgICAgaWR4ID0gdGhpcy5faXRlcmF0ZUl0ZW1zKGZ1bmN0aW9uKHBpZHgsIHZpZHgpIHsKICAgICAgICAgICAgcGh5c2ljYWxPZmZzZXQgKz0gdGhpcy5fZ2V0UGh5c2ljYWxTaXplSW5jcmVtZW50KHBpZHgpOwoKICAgICAgICAgICAgaWYgKHBoeXNpY2FsT2Zmc2V0ID4gdGhpcy5fc2Nyb2xsUG9zaXRpb24pIHsKICAgICAgICAgICAgICByZXR1cm4gdGhpcy5ncmlkID8gdmlkeCAtICh2aWR4ICUgdGhpcy5faXRlbXNQZXJSb3cpIDogdmlkeDsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBIYW5kbGUgYSBwYXJ0aWFsbHkgcmVuZGVyZWQgZmluYWwgcm93IGluIGdyaWQgbW9kZQogICAgICAgICAgICBpZiAodGhpcy5ncmlkICYmIHRoaXMuX3ZpcnR1YWxDb3VudCAtIDEgPT09IHZpZHgpIHsKICAgICAgICAgICAgICByZXR1cm4gdmlkeCAtICh2aWR4ICUgdGhpcy5faXRlbXNQZXJSb3cpOwogICAgICAgICAgICB9CiAgICAgICAgICB9KSB8fAogICAgICAgICAgICAgIDA7CiAgICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IGlkeDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGlkeDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBHZXRzIHRoZSBpbmRleCBvZiB0aGUgbGFzdCB2aXNpYmxlIGl0ZW0gaW4gdGhlIHZpZXdwb3J0LgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IGxhc3RWaXNpYmxlSW5kZXgoKSB7CiAgICAgICAgdmFyIGlkeCA9IHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWw7CiAgICAgICAgaWYgKGlkeCA9PSBudWxsKSB7CiAgICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICAgIGlkeCA9IE1hdGgubWluKAogICAgICAgICAgICAgICAgdGhpcy5fdmlydHVhbENvdW50LAogICAgICAgICAgICAgICAgdGhpcy5maXJzdFZpc2libGVJbmRleCArIHRoaXMuX2VzdFJvd3NJblZpZXcgKiB0aGlzLl9pdGVtc1BlclJvdyAtCiAgICAgICAgICAgICAgICAgICAgMSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB2YXIgcGh5c2ljYWxPZmZzZXQgPSB0aGlzLl9waHlzaWNhbFRvcCArIHRoaXMuX3Njcm9sbE9mZnNldDsKICAgICAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKGZ1bmN0aW9uKHBpZHgsIHZpZHgpIHsKICAgICAgICAgICAgICBpZiAocGh5c2ljYWxPZmZzZXQgPCB0aGlzLl9zY3JvbGxCb3R0b20pIHsKICAgICAgICAgICAgICAgIGlkeCA9IHZpZHg7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHBoeXNpY2FsT2Zmc2V0ICs9IHRoaXMuX2dldFBoeXNpY2FsU2l6ZUluY3JlbWVudChwaWR4KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9sYXN0VmlzaWJsZUluZGV4VmFsID0gaWR4OwogICAgICAgIH0KICAgICAgICByZXR1cm4gaWR4OwogICAgICB9LAoKICAgICAgZ2V0IF9kZWZhdWx0U2Nyb2xsVGFyZ2V0KCkgewogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAoKICAgICAgZ2V0IF92aXJ0dWFsUm93Q291bnQoKSB7CiAgICAgICAgcmV0dXJuIE1hdGguY2VpbCh0aGlzLl92aXJ0dWFsQ291bnQgLyB0aGlzLl9pdGVtc1BlclJvdyk7CiAgICAgIH0sCgogICAgICBnZXQgX2VzdFJvd3NJblZpZXcoKSB7CiAgICAgICAgcmV0dXJuIE1hdGguY2VpbCh0aGlzLl92aWV3cG9ydEhlaWdodCAvIHRoaXMuX3Jvd0hlaWdodCk7CiAgICAgIH0sCgogICAgICBnZXQgX3BoeXNpY2FsUm93cygpIHsKICAgICAgICByZXR1cm4gTWF0aC5jZWlsKHRoaXMuX3BoeXNpY2FsQ291bnQgLyB0aGlzLl9pdGVtc1BlclJvdyk7CiAgICAgIH0sCgogICAgICBnZXQgX3Njcm9sbE9mZnNldCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fc2Nyb2xsZXJQYWRkaW5nVG9wICsgdGhpcy5zY3JvbGxPZmZzZXQ7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIHJlYWR5OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3VzJywgdGhpcy5fZGlkRm9jdXMuYmluZCh0aGlzKSwgdHJ1ZSk7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9kZWJvdW5jZSgnX3JlbmRlcicsIHRoaXMuX3JlbmRlciwgYW5pbWF0aW9uRnJhbWUpOwogICAgICAgIC8vIGBpcm9uLXJlc2l6ZWAgaXMgZmlyZWQgd2hlbiB0aGUgbGlzdCBpcyBhdHRhY2hlZCBpZiB0aGUgZXZlbnQgaXMgYWRkZWQKICAgICAgICAvLyBiZWZvcmUgYXR0YWNoZWQgY2F1c2luZyB1bm5lY2Vzc2FyeSB3b3JrLgogICAgICAgIHRoaXMubGlzdGVuKHRoaXMsICdpcm9uLXJlc2l6ZScsICdfcmVzaXplSGFuZGxlcicpOwogICAgICAgIHRoaXMubGlzdGVuKHRoaXMsICdrZXlkb3duJywgJ19rZXlkb3duSGFuZGxlcicpOwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy51bmxpc3Rlbih0aGlzLCAnaXJvbi1yZXNpemUnLCAnX3Jlc2l6ZUhhbmRsZXInKTsKICAgICAgICB0aGlzLnVubGlzdGVuKHRoaXMsICdrZXlkb3duJywgJ19rZXlkb3duSGFuZGxlcicpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNldCB0aGUgb3ZlcmZsb3cgcHJvcGVydHkgaWYgdGhpcyBlbGVtZW50IGhhcyBpdHMgb3duIHNjcm9sbGluZyByZWdpb24KICAgICAgICovCiAgICAgIF9zZXRPdmVyZmxvdzogZnVuY3Rpb24oc2Nyb2xsVGFyZ2V0KSB7CiAgICAgICAgdGhpcy5zdHlsZS53ZWJraXRPdmVyZmxvd1Njcm9sbGluZyA9IHNjcm9sbFRhcmdldCA9PT0gdGhpcyA/ICd0b3VjaCcgOiAnJzsKICAgICAgICB0aGlzLnN0eWxlLm92ZXJmbG93WSA9IHNjcm9sbFRhcmdldCA9PT0gdGhpcyA/ICdhdXRvJyA6ICcnOwogICAgICAgIC8vIENsZWFyIGNhY2hlLgogICAgICAgIHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWwgPSBudWxsOwogICAgICAgIHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICB0aGlzLl9kZWJvdW5jZSgnX3JlbmRlcicsIHRoaXMuX3JlbmRlciwgYW5pbWF0aW9uRnJhbWUpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEludm9rZSB0aGlzIG1ldGhvZCBpZiB5b3UgZHluYW1pY2FsbHkgdXBkYXRlIHRoZSB2aWV3cG9ydCdzCiAgICAgICAqIHNpemUgb3IgQ1NTIHBhZGRpbmcuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgdXBkYXRlVmlld3BvcnRCb3VuZGFyaWVzCiAgICAgICAqLwogICAgICB1cGRhdGVWaWV3cG9ydEJvdW5kYXJpZXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHlsZXMgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZSh0aGlzKTsKICAgICAgICB0aGlzLl9zY3JvbGxlclBhZGRpbmdUb3AgPQogICAgICAgICAgICB0aGlzLnNjcm9sbFRhcmdldCA9PT0gdGhpcyA/IDAgOiBwYXJzZUludChzdHlsZXNbJ3BhZGRpbmctdG9wJ10sIDEwKTsKICAgICAgICB0aGlzLl9pc1JUTCA9IEJvb2xlYW4oc3R5bGVzLmRpcmVjdGlvbiA9PT0gJ3J0bCcpOwogICAgICAgIHRoaXMuX3ZpZXdwb3J0V2lkdGggPSB0aGlzLiQuaXRlbXMub2Zmc2V0V2lkdGg7CiAgICAgICAgdGhpcy5fdmlld3BvcnRIZWlnaHQgPSB0aGlzLl9zY3JvbGxUYXJnZXRIZWlnaHQ7CiAgICAgICAgdGhpcy5ncmlkICYmIHRoaXMuX3VwZGF0ZUdyaWRNZXRyaWNzKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVjeWNsZXMgdGhlIHBoeXNpY2FsIGl0ZW1zIHdoZW4gbmVlZGVkLgogICAgICAgKi8KICAgICAgX3Njcm9sbEhhbmRsZXI6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY3JvbGxUb3AgPSBNYXRoLm1heCgwLCBNYXRoLm1pbih0aGlzLl9tYXhTY3JvbGxUb3AsIHRoaXMuX3Njcm9sbFRvcCkpOwogICAgICAgIHZhciBkZWx0YSA9IHNjcm9sbFRvcCAtIHRoaXMuX3Njcm9sbFBvc2l0aW9uOwogICAgICAgIHZhciBpc1Njcm9sbGluZ0Rvd24gPSBkZWx0YSA+PSAwOwogICAgICAgIC8vIFRyYWNrIHRoZSBjdXJyZW50IHNjcm9sbCBwb3NpdGlvbi4KICAgICAgICB0aGlzLl9zY3JvbGxQb3NpdGlvbiA9IHNjcm9sbFRvcDsKICAgICAgICAvLyBDbGVhciBpbmRleGVzIGZvciBmaXJzdCBhbmQgbGFzdCB2aXNpYmxlIGluZGV4ZXMuCiAgICAgICAgdGhpcy5fZmlyc3RWaXNpYmxlSW5kZXhWYWwgPSBudWxsOwogICAgICAgIHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWwgPSBudWxsOwogICAgICAgIC8vIFJhbmRvbSBhY2Nlc3MuCiAgICAgICAgaWYgKE1hdGguYWJzKGRlbHRhKSA+IHRoaXMuX3BoeXNpY2FsU2l6ZSAmJiB0aGlzLl9waHlzaWNhbFNpemUgPiAwKSB7CiAgICAgICAgICBkZWx0YSA9IGRlbHRhIC0gdGhpcy5fc2Nyb2xsT2Zmc2V0OwogICAgICAgICAgdmFyIGlkeEFkanVzdG1lbnQgPQogICAgICAgICAgICAgIE1hdGgucm91bmQoZGVsdGEgLyB0aGlzLl9waHlzaWNhbEF2ZXJhZ2UpICogdGhpcy5faXRlbXNQZXJSb3c7CiAgICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgKyBpZHhBZGp1c3RtZW50OwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTdGFydCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQgKyBpZHhBZGp1c3RtZW50OwogICAgICAgICAgLy8gRXN0aW1hdGUgbmV3IHBoeXNpY2FsIG9mZnNldCBiYXNlZCBvbiB0aGUgdmlydHVhbCBzdGFydCBpbmRleC4KICAgICAgICAgIC8vIGFkanVzdHMgdGhlIHBoeXNpY2FsIHN0YXJ0IHBvc2l0aW9uIHRvIHN0YXkgaW4gc3luYyB3aXRoIHRoZSBjbGFtcGVkCiAgICAgICAgICAvLyB2aXJ0dWFsIHN0YXJ0IGluZGV4LiBJdCdzIGNyaXRpY2FsIG5vdCB0byBsZXQgdGhpcyB2YWx1ZSBiZQogICAgICAgICAgLy8gbW9yZSB0aGFuIHRoZSBzY3JvbGwgcG9zaXRpb24gaG93ZXZlciwgc2luY2UgdGhhdCB3b3VsZCByZXN1bHQgaW4KICAgICAgICAgIC8vIHRoZSBwaHlzaWNhbCBpdGVtcyBub3QgY292ZXJpbmcgdGhlIHZpZXdwb3J0LCBhbmQgbGVhZGluZyB0bwogICAgICAgICAgLy8gX2luY3JlYXNlUG9vbElmTmVlZGVkIHRvIHJ1biBhd2F5IGNyZWF0aW5nIGl0ZW1zIHRvIHRyeSB0byBmaWxsIGl0LgogICAgICAgICAgdGhpcy5fcGh5c2ljYWxUb3AgPSBNYXRoLm1pbigKICAgICAgICAgICAgICBNYXRoLmZsb29yKHRoaXMuX3ZpcnR1YWxTdGFydCAvIHRoaXMuX2l0ZW1zUGVyUm93KSAqCiAgICAgICAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQXZlcmFnZSwKICAgICAgICAgICAgICB0aGlzLl9zY3JvbGxQb3NpdGlvbik7CiAgICAgICAgICB0aGlzLl91cGRhdGUoKTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX3BoeXNpY2FsQ291bnQgPiAwKSB7CiAgICAgICAgICB2YXIgcmV1c2FibGVzID0gdGhpcy5fZ2V0UmV1c2FibGVzKGlzU2Nyb2xsaW5nRG93bik7CiAgICAgICAgICBpZiAoaXNTY3JvbGxpbmdEb3duKSB7CiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsVG9wID0gcmV1c2FibGVzLnBoeXNpY2FsVG9wOwogICAgICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgKyByZXVzYWJsZXMuaW5kZXhlcy5sZW5ndGg7CiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnQgPSB0aGlzLl9waHlzaWNhbFN0YXJ0ICsgcmV1c2FibGVzLmluZGV4ZXMubGVuZ3RoOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fdmlydHVhbFN0YXJ0ID0gdGhpcy5fdmlydHVhbFN0YXJ0IC0gcmV1c2FibGVzLmluZGV4ZXMubGVuZ3RoOwogICAgICAgICAgICB0aGlzLl9waHlzaWNhbFN0YXJ0ID0gdGhpcy5fcGh5c2ljYWxTdGFydCAtIHJldXNhYmxlcy5pbmRleGVzLmxlbmd0aDsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX3VwZGF0ZSgKICAgICAgICAgICAgICByZXVzYWJsZXMuaW5kZXhlcywgaXNTY3JvbGxpbmdEb3duID8gbnVsbCA6IHJldXNhYmxlcy5pbmRleGVzKTsKICAgICAgICAgIHRoaXMuX2RlYm91bmNlKAogICAgICAgICAgICAgICdfaW5jcmVhc2VQb29sSWZOZWVkZWQnLAogICAgICAgICAgICAgIHRoaXMuX2luY3JlYXNlUG9vbElmTmVlZGVkLmJpbmQodGhpcywgMCksCiAgICAgICAgICAgICAgbWljcm9UYXNrKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyBhbiBvYmplY3QgdGhhdCBjb250YWlucyB0aGUgaW5kZXhlcyBvZiB0aGUgcGh5c2ljYWwgaXRlbXMKICAgICAgICogdGhhdCBtaWdodCBiZSByZXVzZWQgYW5kIHRoZSBwaHlzaWNhbFRvcC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtib29sZWFufSBmcm9tVG9wIElmIHRoZSBwb3RlbnRpYWwgcmV1c2FibGUgaXRlbXMgYXJlIGFib3ZlIHRoZSBzY3JvbGxpbmcgcmVnaW9uLgogICAgICAgKi8KICAgICAgX2dldFJldXNhYmxlczogZnVuY3Rpb24oZnJvbVRvcCkgewogICAgICAgIHZhciBpdGgsIGxhc3RJdGgsIG9mZnNldENvbnRlbnQsIHBoeXNpY2FsSXRlbUhlaWdodDsKICAgICAgICB2YXIgaWR4cyA9IFtdOwogICAgICAgIHZhciBwcm90ZWN0ZWRPZmZzZXRDb250ZW50ID0gdGhpcy5faGlkZGVuQ29udGVudFNpemUgKiB0aGlzLl9yYXRpbzsKICAgICAgICB2YXIgdmlydHVhbFN0YXJ0ID0gdGhpcy5fdmlydHVhbFN0YXJ0OwogICAgICAgIHZhciB2aXJ0dWFsRW5kID0gdGhpcy5fdmlydHVhbEVuZDsKICAgICAgICB2YXIgcGh5c2ljYWxDb3VudCA9IHRoaXMuX3BoeXNpY2FsQ291bnQ7CiAgICAgICAgdmFyIHRvcCA9IHRoaXMuX3BoeXNpY2FsVG9wICsgdGhpcy5fc2Nyb2xsT2Zmc2V0OwogICAgICAgIHZhciBib3R0b20gPSB0aGlzLl9waHlzaWNhbEJvdHRvbSArIHRoaXMuX3Njcm9sbE9mZnNldDsKICAgICAgICAvLyBUaGlzIG1heSBiZSBjYWxsZWQgb3V0c2lkZSBvZiBhIHNjcm9sbEhhbmRsZXIsIHNvIHVzZSBsYXN0IGNhY2hlZCBwb3NpdGlvbgogICAgICAgIHZhciBzY3JvbGxUb3AgPSB0aGlzLl9zY3JvbGxQb3NpdGlvbjsKICAgICAgICB2YXIgc2Nyb2xsQm90dG9tID0gdGhpcy5fc2Nyb2xsQm90dG9tOwoKICAgICAgICBpZiAoZnJvbVRvcCkgewogICAgICAgICAgaXRoID0gdGhpcy5fcGh5c2ljYWxTdGFydDsKICAgICAgICAgIGxhc3RJdGggPSB0aGlzLl9waHlzaWNhbEVuZDsKICAgICAgICAgIG9mZnNldENvbnRlbnQgPSBzY3JvbGxUb3AgLSB0b3A7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGl0aCA9IHRoaXMuX3BoeXNpY2FsRW5kOwogICAgICAgICAgbGFzdEl0aCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQ7CiAgICAgICAgICBvZmZzZXRDb250ZW50ID0gYm90dG9tIC0gc2Nyb2xsQm90dG9tOwogICAgICAgIH0KICAgICAgICB3aGlsZSAodHJ1ZSkgewogICAgICAgICAgcGh5c2ljYWxJdGVtSGVpZ2h0ID0gdGhpcy5fZ2V0UGh5c2ljYWxTaXplSW5jcmVtZW50KGl0aCk7CiAgICAgICAgICBvZmZzZXRDb250ZW50ID0gb2Zmc2V0Q29udGVudCAtIHBoeXNpY2FsSXRlbUhlaWdodDsKICAgICAgICAgIGlmIChpZHhzLmxlbmd0aCA+PSBwaHlzaWNhbENvdW50IHx8CiAgICAgICAgICAgICAgb2Zmc2V0Q29udGVudCA8PSBwcm90ZWN0ZWRPZmZzZXRDb250ZW50KSB7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGZyb21Ub3ApIHsKICAgICAgICAgICAgLy8gQ2hlY2sgdGhhdCBpbmRleCBpcyB3aXRoaW4gdGhlIHZhbGlkIHJhbmdlLgogICAgICAgICAgICBpZiAodmlydHVhbEVuZCArIGlkeHMubGVuZ3RoICsgMSA+PSB0aGlzLl92aXJ0dWFsQ291bnQpIHsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDaGVjayB0aGF0IHRoZSBpbmRleCBpcyBub3QgdmlzaWJsZS4KICAgICAgICAgICAgaWYgKHRvcCArIHBoeXNpY2FsSXRlbUhlaWdodCA+PSBzY3JvbGxUb3AgLSB0aGlzLl9zY3JvbGxPZmZzZXQpIHsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZHhzLnB1c2goaXRoKTsKICAgICAgICAgICAgdG9wID0gdG9wICsgcGh5c2ljYWxJdGVtSGVpZ2h0OwogICAgICAgICAgICBpdGggPSAoaXRoICsgMSkgJSBwaHlzaWNhbENvdW50OwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gQ2hlY2sgdGhhdCBpbmRleCBpcyB3aXRoaW4gdGhlIHZhbGlkIHJhbmdlLgogICAgICAgICAgICBpZiAodmlydHVhbFN0YXJ0IC0gaWR4cy5sZW5ndGggPD0gMCkgewogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENoZWNrIHRoYXQgdGhlIGluZGV4IGlzIG5vdCB2aXNpYmxlLgogICAgICAgICAgICBpZiAodG9wICsgdGhpcy5fcGh5c2ljYWxTaXplIC0gcGh5c2ljYWxJdGVtSGVpZ2h0IDw9IHNjcm9sbEJvdHRvbSkgewogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlkeHMucHVzaChpdGgpOwogICAgICAgICAgICB0b3AgPSB0b3AgLSBwaHlzaWNhbEl0ZW1IZWlnaHQ7CiAgICAgICAgICAgIGl0aCA9IChpdGggPT09IDApID8gcGh5c2ljYWxDb3VudCAtIDEgOiBpdGggLSAxOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4ge2luZGV4ZXM6IGlkeHMsIHBoeXNpY2FsVG9wOiB0b3AgLSB0aGlzLl9zY3JvbGxPZmZzZXR9OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZSB0aGUgbGlzdCBvZiBpdGVtcywgc3RhcnRpbmcgZnJvbSB0aGUgYF92aXJ0dWFsU3RhcnRgIGl0ZW0uCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PG51bWJlcj49fSBpdGVtU2V0CiAgICAgICAqIEBwYXJhbSB7IUFycmF5PG51bWJlcj49fSBtb3ZpbmdVcAogICAgICAgKi8KICAgICAgX3VwZGF0ZTogZnVuY3Rpb24oaXRlbVNldCwgbW92aW5nVXApIHsKICAgICAgICBpZiAoKGl0ZW1TZXQgJiYgaXRlbVNldC5sZW5ndGggPT09IDApIHx8IHRoaXMuX3BoeXNpY2FsQ291bnQgPT09IDApIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpcy5fbWFuYWdlRm9jdXMoKTsKICAgICAgICB0aGlzLl9hc3NpZ25Nb2RlbHMoaXRlbVNldCk7CiAgICAgICAgdGhpcy5fdXBkYXRlTWV0cmljcyhpdGVtU2V0KTsKICAgICAgICAvLyBBZGp1c3Qgb2Zmc2V0IGFmdGVyIG1lYXN1cmluZy4KICAgICAgICBpZiAobW92aW5nVXApIHsKICAgICAgICAgIHdoaWxlIChtb3ZpbmdVcC5sZW5ndGgpIHsKICAgICAgICAgICAgdmFyIGlkeCA9IG1vdmluZ1VwLnBvcCgpOwogICAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCAtPSB0aGlzLl9nZXRQaHlzaWNhbFNpemVJbmNyZW1lbnQoaWR4KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdGhpcy5fcG9zaXRpb25JdGVtcygpOwogICAgICAgIHRoaXMuX3VwZGF0ZVNjcm9sbGVyU2l6ZSgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENyZWF0ZXMgYSBwb29sIG9mIERPTSBlbGVtZW50cyBhbmQgYXR0YWNoZXMgdGhlbSB0byB0aGUgbG9jYWwgZG9tLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge251bWJlcn0gc2l6ZSBTaXplIG9mIHRoZSBwb29sCiAgICAgICAqLwogICAgICBfY3JlYXRlUG9vbDogZnVuY3Rpb24oc2l6ZSkgewogICAgICAgIHRoaXMuX2Vuc3VyZVRlbXBsYXRpemVkKCk7CiAgICAgICAgdmFyIGksIGluc3Q7CiAgICAgICAgdmFyIHBoeXNpY2FsSXRlbXMgPSBuZXcgQXJyYXkoc2l6ZSk7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IHNpemU7IGkrKykgewogICAgICAgICAgaW5zdCA9IHRoaXMuc3RhbXAobnVsbCk7CiAgICAgICAgICAvLyBUT0RPKGJsYXN0ZW4pOgogICAgICAgICAgLy8gRmlyc3QgZWxlbWVudCBjaGlsZCBpcyBpdGVtOyBTYWZhcmkgZG9lc24ndCBzdXBwb3J0IGNoaWxkcmVuWzBdCiAgICAgICAgICAvLyBvbiBhIGRvYyBmcmFnbWVudC4gVGVzdCB0aGlzIHRvIHNlZSBpZiBpdCBzdGlsbCBtYXR0ZXJzLgogICAgICAgICAgcGh5c2ljYWxJdGVtc1tpXSA9IGluc3Qucm9vdC5xdWVyeVNlbGVjdG9yKCcqJyk7CiAgICAgICAgICB0aGlzLl9pdGVtc1BhcmVudC5hcHBlbmRDaGlsZChpbnN0LnJvb3QpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gcGh5c2ljYWxJdGVtczsKICAgICAgfSwKCiAgICAgIF9pc0NsaWVudEZ1bGw6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl9zY3JvbGxCb3R0b20gIT0gMCAmJgogICAgICAgICAgICB0aGlzLl9waHlzaWNhbEJvdHRvbSAtIDEgPj0gdGhpcy5fc2Nyb2xsQm90dG9tICYmCiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsVG9wIDw9IHRoaXMuX3Njcm9sbFBvc2l0aW9uOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEluY3JlYXNlcyB0aGUgcG9vbCBzaXplLgogICAgICAgKi8KICAgICAgX2luY3JlYXNlUG9vbElmTmVlZGVkOiBmdW5jdGlvbihjb3VudCkgewogICAgICAgIHZhciBuZXh0UGh5c2ljYWxDb3VudCA9IHRoaXMuX2NsYW1wKAogICAgICAgICAgICB0aGlzLl9waHlzaWNhbENvdW50ICsgY291bnQsCiAgICAgICAgICAgIERFRkFVTFRfUEhZU0lDQUxfQ09VTlQsCiAgICAgICAgICAgIHRoaXMuX3ZpcnR1YWxDb3VudCAtIHRoaXMuX3ZpcnR1YWxTdGFydCk7CiAgICAgICAgbmV4dFBoeXNpY2FsQ291bnQgPSB0aGlzLl9jb252ZXJ0SW5kZXhUb0NvbXBsZXRlUm93KG5leHRQaHlzaWNhbENvdW50KTsKICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICB2YXIgY29ycmVjdGlvbiA9IG5leHRQaHlzaWNhbENvdW50ICUgdGhpcy5faXRlbXNQZXJSb3c7CiAgICAgICAgICBpZiAoY29ycmVjdGlvbiAmJiBuZXh0UGh5c2ljYWxDb3VudCAtIGNvcnJlY3Rpb24gPD0gdGhpcy5fcGh5c2ljYWxDb3VudCkgewogICAgICAgICAgICBuZXh0UGh5c2ljYWxDb3VudCArPSB0aGlzLl9pdGVtc1BlclJvdzsKICAgICAgICAgIH0KICAgICAgICAgIG5leHRQaHlzaWNhbENvdW50IC09IGNvcnJlY3Rpb247CiAgICAgICAgfQogICAgICAgIHZhciBkZWx0YSA9IG5leHRQaHlzaWNhbENvdW50IC0gdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgICB2YXIgbmV4dEluY3JlYXNlID0gTWF0aC5yb3VuZCh0aGlzLl9waHlzaWNhbENvdW50ICogMC41KTsKCiAgICAgICAgaWYgKGRlbHRhIDwgMCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAoZGVsdGEgPiAwKSB7CiAgICAgICAgICB2YXIgdHMgPSB3aW5kb3cucGVyZm9ybWFuY2Uubm93KCk7CiAgICAgICAgICAvLyBDb25jYXQgYXJyYXlzIGluIHBsYWNlLgogICAgICAgICAgW10ucHVzaC5hcHBseSh0aGlzLl9waHlzaWNhbEl0ZW1zLCB0aGlzLl9jcmVhdGVQb29sKGRlbHRhKSk7CiAgICAgICAgICAvLyBQdXNoIDBzIGludG8gcGh5c2ljYWxTaXplcy4gQ2FuJ3QgdXNlIEFycmF5LmZpbGwgYmVjYXVzZSBJRTExIGRvZXNuJ3QKICAgICAgICAgIC8vIHN1cHBvcnQgaXQuCiAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGRlbHRhOyBpKyspIHsKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxTaXplcy5wdXNoKDApOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fcGh5c2ljYWxDb3VudCA9IHRoaXMuX3BoeXNpY2FsQ291bnQgKyBkZWx0YTsKICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgcGh5c2ljYWwgc3RhcnQgaWYgaXQgbmVlZHMgdG8gcHJlc2VydmUgdGhlIG1vZGVsIG9mIHRoZQogICAgICAgICAgLy8gZm9jdXNlZCBpdGVtLiBJbiB0aGlzIHNpdHVhdGlvbiwgdGhlIGZvY3VzZWQgaXRlbSBpcyBjdXJyZW50bHkgcmVuZGVyZWQKICAgICAgICAgIC8vIGFuZCBpdHMgbW9kZWwgd291bGQgaGF2ZSBjaGFuZ2VkIGFmdGVyIGluY3JlYXNpbmcgdGhlIHBvb2wgaWYgdGhlCiAgICAgICAgICAvLyBwaHlzaWNhbCBzdGFydCByZW1haW5lZCB1bmNoYW5nZWQuCiAgICAgICAgICBpZiAodGhpcy5fcGh5c2ljYWxTdGFydCA+IHRoaXMuX3BoeXNpY2FsRW5kICYmCiAgICAgICAgICAgICAgdGhpcy5faXNJbmRleFJlbmRlcmVkKHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXgpICYmCiAgICAgICAgICAgICAgdGhpcy5fZ2V0UGh5c2ljYWxJbmRleCh0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4KSA8CiAgICAgICAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsRW5kKSB7CiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnQgPSB0aGlzLl9waHlzaWNhbFN0YXJ0ICsgZGVsdGE7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl91cGRhdGUoKTsKICAgICAgICAgIHRoaXMuX3RlbXBsYXRlQ29zdCA9ICh3aW5kb3cucGVyZm9ybWFuY2Uubm93KCkgLSB0cykgLyBkZWx0YTsKICAgICAgICAgIG5leHRJbmNyZWFzZSA9IE1hdGgucm91bmQodGhpcy5fcGh5c2ljYWxDb3VudCAqIDAuNSk7CiAgICAgICAgfQogICAgICAgIC8vIFRoZSB1cHBlciBib3VuZHMgaXMgbm90IGZpeGVkIHdoZW4gZGVhbGluZyB3aXRoIGEgZ3JpZCB0aGF0IGRvZXNuJ3QKICAgICAgICAvLyBmaWxsIGl0J3MgbGFzdCByb3cgd2l0aCB0aGUgZXhhY3QgbnVtYmVyIG9mIGl0ZW1zIHBlciByb3cuCiAgICAgICAgaWYgKHRoaXMuX3ZpcnR1YWxFbmQgPj0gdGhpcy5fdmlydHVhbENvdW50IC0gMSB8fCBuZXh0SW5jcmVhc2UgPT09IDApIDsgZWxzZSBpZiAoIXRoaXMuX2lzQ2xpZW50RnVsbCgpKSB7CiAgICAgICAgICB0aGlzLl9kZWJvdW5jZSgKICAgICAgICAgICAgICAnX2luY3JlYXNlUG9vbElmTmVlZGVkJywKICAgICAgICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZC5iaW5kKHRoaXMsIG5leHRJbmNyZWFzZSksCiAgICAgICAgICAgICAgbWljcm9UYXNrKTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX3BoeXNpY2FsU2l6ZSA8IHRoaXMuX29wdFBoeXNpY2FsU2l6ZSkgewogICAgICAgICAgLy8gWWllbGQgYW5kIGluY3JlYXNlIHRoZSBwb29sIGR1cmluZyBpZGxlIHRpbWUgdW50aWwgdGhlIHBoeXNpY2FsIHNpemUgaXMKICAgICAgICAgIC8vIG9wdGltYWwuCiAgICAgICAgICB0aGlzLl9kZWJvdW5jZSgKICAgICAgICAgICAgICAnX2luY3JlYXNlUG9vbElmTmVlZGVkJywKICAgICAgICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZC5iaW5kKAogICAgICAgICAgICAgICAgICB0aGlzLAogICAgICAgICAgICAgICAgICB0aGlzLl9jbGFtcCgKICAgICAgICAgICAgICAgICAgICAgIE1hdGgucm91bmQoNTAgLyB0aGlzLl90ZW1wbGF0ZUNvc3QpLCAxLCBuZXh0SW5jcmVhc2UpKSwKICAgICAgICAgICAgICBpZGxlUGVyaW9kKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVuZGVycyB0aGUgYSBuZXcgbGlzdC4KICAgICAgICovCiAgICAgIF9yZW5kZXI6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICghdGhpcy5pc0F0dGFjaGVkIHx8ICF0aGlzLl9pc1Zpc2libGUpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX3BoeXNpY2FsQ291bnQgIT09IDApIHsKICAgICAgICAgIHZhciByZXVzYWJsZXMgPSB0aGlzLl9nZXRSZXVzYWJsZXModHJ1ZSk7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IHJldXNhYmxlcy5waHlzaWNhbFRvcDsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydCA9IHRoaXMuX3ZpcnR1YWxTdGFydCArIHJldXNhYmxlcy5pbmRleGVzLmxlbmd0aDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnQgPSB0aGlzLl9waHlzaWNhbFN0YXJ0ICsgcmV1c2FibGVzLmluZGV4ZXMubGVuZ3RoOwogICAgICAgICAgdGhpcy5fdXBkYXRlKHJldXNhYmxlcy5pbmRleGVzKTsKICAgICAgICAgIHRoaXMuX3VwZGF0ZSgpOwogICAgICAgICAgdGhpcy5faW5jcmVhc2VQb29sSWZOZWVkZWQoMCk7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl92aXJ0dWFsQ291bnQgPiAwKSB7CiAgICAgICAgICAvLyBJbml0aWFsIHJlbmRlcgogICAgICAgICAgdGhpcy51cGRhdGVWaWV3cG9ydEJvdW5kYXJpZXMoKTsKICAgICAgICAgIHRoaXMuX2luY3JlYXNlUG9vbElmTmVlZGVkKERFRkFVTFRfUEhZU0lDQUxfQ09VTlQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUZW1wbGV0aXplcyB0aGUgdXNlciB0ZW1wbGF0ZS4KICAgICAgICovCiAgICAgIF9lbnN1cmVUZW1wbGF0aXplZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuY3RvcikgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB0aGlzLl91c2VyVGVtcGxhdGUgPSAvKiogQHR5cGUgeyFIVE1MVGVtcGxhdGVFbGVtZW50fSAqLyAoCiAgICAgICAgICAgIHRoaXMucXVlcnlFZmZlY3RpdmVDaGlsZHJlbigndGVtcGxhdGUnKSk7CiAgICAgICAgaWYgKCF0aGlzLl91c2VyVGVtcGxhdGUpIHsKICAgICAgICAgIGNvbnNvbGUud2FybignaXJvbi1saXN0IHJlcXVpcmVzIGEgdGVtcGxhdGUgdG8gYmUgcHJvdmlkZWQgaW4gbGlnaHQtZG9tJyk7CiAgICAgICAgfQogICAgICAgIHZhciBpbnN0YW5jZVByb3BzID0ge307CiAgICAgICAgaW5zdGFuY2VQcm9wcy5fX2tleV9fID0gdHJ1ZTsKICAgICAgICBpbnN0YW5jZVByb3BzW3RoaXMuYXNdID0gdHJ1ZTsKICAgICAgICBpbnN0YW5jZVByb3BzW3RoaXMuaW5kZXhBc10gPSB0cnVlOwogICAgICAgIGluc3RhbmNlUHJvcHNbdGhpcy5zZWxlY3RlZEFzXSA9IHRydWU7CiAgICAgICAgaW5zdGFuY2VQcm9wcy50YWJJbmRleCA9IHRydWU7CiAgICAgICAgdGhpcy5faW5zdGFuY2VQcm9wcyA9IGluc3RhbmNlUHJvcHM7CiAgICAgICAgdGhpcy50ZW1wbGF0aXplKHRoaXMuX3VzZXJUZW1wbGF0ZSwgdGhpcy5tdXRhYmxlRGF0YSk7CiAgICAgIH0sCgogICAgICBfZ3JpZENoYW5nZWQ6IGZ1bmN0aW9uKG5ld0dyaWQsIG9sZEdyaWQpIHsKICAgICAgICBpZiAodHlwZW9mIG9sZEdyaWQgPT09ICd1bmRlZmluZWQnKQogICAgICAgICAgcmV0dXJuOwogICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgZmx1c2goKTsKICAgICAgICBuZXdHcmlkICYmIHRoaXMuX3VwZGF0ZUdyaWRNZXRyaWNzKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FsbGVkIHdoZW4gdGhlIGl0ZW1zIGhhdmUgY2hhbmdlZC4gVGhhdCBpcywgcmVhc3NpZ25tZW50cwogICAgICAgKiB0byBgaXRlbXNgLCBzcGxpY2VzIG9yIHVwZGF0ZXMgdG8gYSBzaW5nbGUgaXRlbS4KICAgICAgICovCiAgICAgIF9pdGVtc0NoYW5nZWQ6IGZ1bmN0aW9uKGNoYW5nZSkgewogICAgICAgIGlmIChjaGFuZ2UucGF0aCA9PT0gJ2l0ZW1zJykgewogICAgICAgICAgdGhpcy5fdmlydHVhbFN0YXJ0ID0gMDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsVG9wID0gMDsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxDb3VudCA9IHRoaXMuaXRlbXMgPyB0aGlzLml0ZW1zLmxlbmd0aCA6IDA7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbEluZGV4Rm9yS2V5ID0ge307CiAgICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgICAgICB0aGlzLl9sYXN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQ291bnQgPSB0aGlzLl9waHlzaWNhbENvdW50IHx8IDA7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbEl0ZW1zID0gdGhpcy5fcGh5c2ljYWxJdGVtcyB8fCBbXTsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU2l6ZXMgPSB0aGlzLl9waHlzaWNhbFNpemVzIHx8IFtdOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTdGFydCA9IDA7CiAgICAgICAgICBpZiAodGhpcy5fc2Nyb2xsVG9wID4gdGhpcy5fc2Nyb2xsT2Zmc2V0KSB7CiAgICAgICAgICAgIHRoaXMuX3Jlc2V0U2Nyb2xsUG9zaXRpb24oMCk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9yZW1vdmVGb2N1c2VkSXRlbSgpOwogICAgICAgICAgdGhpcy5fZGVib3VuY2UoJ19yZW5kZXInLCB0aGlzLl9yZW5kZXIsIGFuaW1hdGlvbkZyYW1lKTsKICAgICAgICB9IGVsc2UgaWYgKGNoYW5nZS5wYXRoID09PSAnaXRlbXMuc3BsaWNlcycpIHsKICAgICAgICAgIHRoaXMuX2FkanVzdFZpcnR1YWxJbmRleChjaGFuZ2UudmFsdWUuaW5kZXhTcGxpY2VzKTsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxDb3VudCA9IHRoaXMuaXRlbXMgPyB0aGlzLml0ZW1zLmxlbmd0aCA6IDA7CiAgICAgICAgICAvLyBPbmx5IGJsdXIgaWYgYXQgbGVhc3Qgb25lIGl0ZW0gaXMgYWRkZWQgb3IgcmVtb3ZlZC4KICAgICAgICAgIHZhciBpdGVtQWRkZWRPclJlbW92ZWQgPSBjaGFuZ2UudmFsdWUuaW5kZXhTcGxpY2VzLnNvbWUoZnVuY3Rpb24oc3BsaWNlKSB7CiAgICAgICAgICAgIHJldHVybiBzcGxpY2UuYWRkZWRDb3VudCA+IDAgfHwgc3BsaWNlLnJlbW92ZWQubGVuZ3RoID4gMDsKICAgICAgICAgIH0pOwogICAgICAgICAgaWYgKGl0ZW1BZGRlZE9yUmVtb3ZlZCkgewogICAgICAgICAgICAvLyBPbmx5IGJsdXIgYWN0aXZlRWxlbWVudCBpZiBpdCBpcyBhIGRlc2NlbmRhbnQgb2YgdGhlIGxpc3QgKCM1MDUsCiAgICAgICAgICAgIC8vICM1MDcpLgogICAgICAgICAgICB2YXIgYWN0aXZlRWxlbWVudCA9IHRoaXMuX2dldEFjdGl2ZUVsZW1lbnQoKTsKICAgICAgICAgICAgaWYgKHRoaXMuY29udGFpbnMoYWN0aXZlRWxlbWVudCkpIHsKICAgICAgICAgICAgICBhY3RpdmVFbGVtZW50LmJsdXIoKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgLy8gUmVuZGVyIG9ubHkgaWYgdGhlIGFmZmVjdGVkIGluZGV4IGlzIHJlbmRlcmVkLgogICAgICAgICAgdmFyIGFmZmVjdGVkSW5kZXhSZW5kZXJlZCA9CiAgICAgICAgICAgICAgY2hhbmdlLnZhbHVlLmluZGV4U3BsaWNlcy5zb21lKGZ1bmN0aW9uKHNwbGljZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHNwbGljZS5pbmRleCArIHNwbGljZS5hZGRlZENvdW50ID49IHRoaXMuX3ZpcnR1YWxTdGFydCAmJgogICAgICAgICAgICAgICAgICAgIHNwbGljZS5pbmRleCA8PSB0aGlzLl92aXJ0dWFsRW5kOwogICAgICAgICAgICAgIH0sIHRoaXMpOwogICAgICAgICAgaWYgKCF0aGlzLl9pc0NsaWVudEZ1bGwoKSB8fCBhZmZlY3RlZEluZGV4UmVuZGVyZWQpIHsKICAgICAgICAgICAgdGhpcy5fZGVib3VuY2UoJ19yZW5kZXInLCB0aGlzLl9yZW5kZXIsIGFuaW1hdGlvbkZyYW1lKTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgaWYgKGNoYW5nZS5wYXRoICE9PSAnaXRlbXMubGVuZ3RoJykgewogICAgICAgICAgdGhpcy5fZm9yd2FyZEl0ZW1QYXRoKGNoYW5nZS5wYXRoLCBjaGFuZ2UudmFsdWUpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9mb3J3YXJkSXRlbVBhdGg6IGZ1bmN0aW9uKHBhdGgsIHZhbHVlKSB7CiAgICAgICAgcGF0aCA9IHBhdGguc2xpY2UoNik7ICAvLyAnaXRlbXMuJy5sZW5ndGggPT0gNgogICAgICAgIHZhciBkb3QgPSBwYXRoLmluZGV4T2YoJy4nKTsKICAgICAgICBpZiAoZG90ID09PSAtMSkgewogICAgICAgICAgZG90ID0gcGF0aC5sZW5ndGg7CiAgICAgICAgfQogICAgICAgIHZhciBpc0luZGV4UmVuZGVyZWQ7CiAgICAgICAgdmFyIHBpZHg7CiAgICAgICAgdmFyIGluc3Q7CiAgICAgICAgdmFyIG9mZnNjcmVlbkluc3RhbmNlID0gdGhpcy5tb2RlbEZvckVsZW1lbnQodGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0pOwogICAgICAgIHZhciB2aWR4ID0gcGFyc2VJbnQocGF0aC5zdWJzdHJpbmcoMCwgZG90KSwgMTApOwogICAgICAgIGlzSW5kZXhSZW5kZXJlZCA9IHRoaXMuX2lzSW5kZXhSZW5kZXJlZCh2aWR4KTsKICAgICAgICBpZiAoaXNJbmRleFJlbmRlcmVkKSB7CiAgICAgICAgICBwaWR4ID0gdGhpcy5fZ2V0UGh5c2ljYWxJbmRleCh2aWR4KTsKICAgICAgICAgIGluc3QgPSB0aGlzLm1vZGVsRm9yRWxlbWVudCh0aGlzLl9waHlzaWNhbEl0ZW1zW3BpZHhdKTsKICAgICAgICB9IGVsc2UgaWYgKG9mZnNjcmVlbkluc3RhbmNlKSB7CiAgICAgICAgICBpbnN0ID0gb2Zmc2NyZWVuSW5zdGFuY2U7CiAgICAgICAgfQoKICAgICAgICBpZiAoIWluc3QgfHwgaW5zdFt0aGlzLmluZGV4QXNdICE9PSB2aWR4KSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHBhdGggPSBwYXRoLnN1YnN0cmluZyhkb3QgKyAxKTsKICAgICAgICBwYXRoID0gdGhpcy5hcyArIChwYXRoID8gJy4nICsgcGF0aCA6ICcnKTsKICAgICAgICBpbnN0Ll9zZXRQZW5kaW5nUHJvcGVydHlPclBhdGgocGF0aCwgdmFsdWUsIGZhbHNlLCB0cnVlKTsKICAgICAgICBpbnN0Ll9mbHVzaFByb3BlcnRpZXMgJiYgaW5zdC5fZmx1c2hQcm9wZXJ0aWVzKCk7CiAgICAgICAgLy8gVE9ETyhibGFzdGVuKTogVjEgZG9lc24ndCBkbyB0aGlzIGFuZCBpdCdzIGEgYnVnCiAgICAgICAgaWYgKGlzSW5kZXhSZW5kZXJlZCkgewogICAgICAgICAgdGhpcy5fdXBkYXRlTWV0cmljcyhbcGlkeF0pOwogICAgICAgICAgdGhpcy5fcG9zaXRpb25JdGVtcygpOwogICAgICAgICAgdGhpcy5fdXBkYXRlU2Nyb2xsZXJTaXplKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PCFPYmplY3Q+fSBzcGxpY2VzCiAgICAgICAqLwogICAgICBfYWRqdXN0VmlydHVhbEluZGV4OiBmdW5jdGlvbihzcGxpY2VzKSB7CiAgICAgICAgc3BsaWNlcy5mb3JFYWNoKGZ1bmN0aW9uKHNwbGljZSkgewogICAgICAgICAgLy8gZGVzZWxlY3QgcmVtb3ZlZCBpdGVtcwogICAgICAgICAgc3BsaWNlLnJlbW92ZWQuZm9yRWFjaCh0aGlzLl9yZW1vdmVJdGVtLCB0aGlzKTsKICAgICAgICAgIC8vIFdlIG9ubHkgbmVlZCB0byBjYXJlIGFib3V0IGNoYW5nZXMgaGFwcGVuaW5nIGFib3ZlIHRoZSBjdXJyZW50IHBvc2l0aW9uCiAgICAgICAgICBpZiAoc3BsaWNlLmluZGV4IDwgdGhpcy5fdmlydHVhbFN0YXJ0KSB7CiAgICAgICAgICAgIHZhciBkZWx0YSA9IE1hdGgubWF4KAogICAgICAgICAgICAgICAgc3BsaWNlLmFkZGVkQ291bnQgLSBzcGxpY2UucmVtb3ZlZC5sZW5ndGgsCiAgICAgICAgICAgICAgICBzcGxpY2UuaW5kZXggLSB0aGlzLl92aXJ0dWFsU3RhcnQpOwogICAgICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgKyBkZWx0YTsKICAgICAgICAgICAgaWYgKHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXggPj0gMCkgewogICAgICAgICAgICAgIHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXggPSB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4ICsgZGVsdGE7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9LCB0aGlzKTsKICAgICAgfSwKCiAgICAgIF9yZW1vdmVJdGVtOiBmdW5jdGlvbihpdGVtKSB7CiAgICAgICAgdGhpcy4kLnNlbGVjdG9yLmRlc2VsZWN0KGl0ZW0pOwogICAgICAgIC8vIHJlbW92ZSB0aGUgY3VycmVudCBmb2N1c2VkIGl0ZW0KICAgICAgICBpZiAodGhpcy5fZm9jdXNlZEl0ZW0gJiYKICAgICAgICAgICAgdGhpcy5tb2RlbEZvckVsZW1lbnQodGhpcy5fZm9jdXNlZEl0ZW0pW3RoaXMuYXNdID09PSBpdGVtKSB7CiAgICAgICAgICB0aGlzLl9yZW1vdmVGb2N1c2VkSXRlbSgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBFeGVjdXRlcyBhIHByb3ZpZGVkIGZ1bmN0aW9uIHBlciBldmVyeSBwaHlzaWNhbCBpbmRleCBpbiBgaXRlbVNldGAKICAgICAgICogYGl0ZW1TZXRgIGRlZmF1bHQgdmFsdWUgaXMgZXF1aXZhbGVudCB0byB0aGUgZW50aXJlIHNldCBvZiBwaHlzaWNhbAogICAgICAgKiBpbmRleGVzLgogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFmdW5jdGlvbihudW1iZXIsIG51bWJlcil9IGZuCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PG51bWJlcj49fSBpdGVtU2V0CiAgICAgICAqLwogICAgICBfaXRlcmF0ZUl0ZW1zOiBmdW5jdGlvbihmbiwgaXRlbVNldCkgewogICAgICAgIHZhciBwaWR4LCB2aWR4LCBydG4sIGk7CgogICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID09PSAyICYmIGl0ZW1TZXQpIHsKICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBpdGVtU2V0Lmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIHBpZHggPSBpdGVtU2V0W2ldOwogICAgICAgICAgICB2aWR4ID0gdGhpcy5fY29tcHV0ZVZpZHgocGlkeCk7CiAgICAgICAgICAgIGlmICgocnRuID0gZm4uY2FsbCh0aGlzLCBwaWR4LCB2aWR4KSkgIT0gbnVsbCkgewogICAgICAgICAgICAgIHJldHVybiBydG47CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgcGlkeCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQ7CiAgICAgICAgICB2aWR4ID0gdGhpcy5fdmlydHVhbFN0YXJ0OwogICAgICAgICAgZm9yICg7IHBpZHggPCB0aGlzLl9waHlzaWNhbENvdW50OyBwaWR4KyssIHZpZHgrKykgewogICAgICAgICAgICBpZiAoKHJ0biA9IGZuLmNhbGwodGhpcywgcGlkeCwgdmlkeCkpICE9IG51bGwpIHsKICAgICAgICAgICAgICByZXR1cm4gcnRuOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBmb3IgKHBpZHggPSAwOyBwaWR4IDwgdGhpcy5fcGh5c2ljYWxTdGFydDsgcGlkeCsrLCB2aWR4KyspIHsKICAgICAgICAgICAgaWYgKChydG4gPSBmbi5jYWxsKHRoaXMsIHBpZHgsIHZpZHgpKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHJ0bjsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSB2aXJ0dWFsIGluZGV4IGZvciBhIGdpdmVuIHBoeXNpY2FsIGluZGV4CiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBwaWR4IFBoeXNpY2FsIGluZGV4CiAgICAgICAqIEByZXR1cm4ge251bWJlcn0KICAgICAgICovCiAgICAgIF9jb21wdXRlVmlkeDogZnVuY3Rpb24ocGlkeCkgewogICAgICAgIGlmIChwaWR4ID49IHRoaXMuX3BoeXNpY2FsU3RhcnQpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl92aXJ0dWFsU3RhcnQgKyAocGlkeCAtIHRoaXMuX3BoeXNpY2FsU3RhcnQpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy5fdmlydHVhbFN0YXJ0ICsgKHRoaXMuX3BoeXNpY2FsQ291bnQgLSB0aGlzLl9waHlzaWNhbFN0YXJ0KSArCiAgICAgICAgICAgIHBpZHg7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQXNzaWducyB0aGUgZGF0YSBtb2RlbHMgdG8gYSBnaXZlbiBzZXQgb2YgaXRlbXMuCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PG51bWJlcj49fSBpdGVtU2V0CiAgICAgICAqLwogICAgICBfYXNzaWduTW9kZWxzOiBmdW5jdGlvbihpdGVtU2V0KSB7CiAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKGZ1bmN0aW9uKHBpZHgsIHZpZHgpIHsKICAgICAgICAgIHZhciBlbCA9IHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF07CiAgICAgICAgICB2YXIgaXRlbSA9IHRoaXMuaXRlbXMgJiYgdGhpcy5pdGVtc1t2aWR4XTsKICAgICAgICAgIGlmIChpdGVtICE9IG51bGwpIHsKICAgICAgICAgICAgdmFyIGluc3QgPSB0aGlzLm1vZGVsRm9yRWxlbWVudChlbCk7CiAgICAgICAgICAgIGluc3QuX19rZXlfXyA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX2ZvcndhcmRQcm9wZXJ0eShpbnN0LCB0aGlzLmFzLCBpdGVtKTsKICAgICAgICAgICAgdGhpcy5fZm9yd2FyZFByb3BlcnR5KAogICAgICAgICAgICAgICAgaW5zdCwgdGhpcy5zZWxlY3RlZEFzLCB0aGlzLiQuc2VsZWN0b3IuaXNTZWxlY3RlZChpdGVtKSk7CiAgICAgICAgICAgIHRoaXMuX2ZvcndhcmRQcm9wZXJ0eShpbnN0LCB0aGlzLmluZGV4QXMsIHZpZHgpOwogICAgICAgICAgICB0aGlzLl9mb3J3YXJkUHJvcGVydHkoCiAgICAgICAgICAgICAgICBpbnN0LCAndGFiSW5kZXgnLCB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4ID09PSB2aWR4ID8gMCA6IC0xKTsKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxJbmRleEZvcktleVtpbnN0Ll9fa2V5X19dID0gcGlkeDsKICAgICAgICAgICAgaW5zdC5fZmx1c2hQcm9wZXJ0aWVzICYmIGluc3QuX2ZsdXNoUHJvcGVydGllcyh0cnVlKTsKICAgICAgICAgICAgZWwucmVtb3ZlQXR0cmlidXRlKCdoaWRkZW4nKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGVsLnNldEF0dHJpYnV0ZSgnaGlkZGVuJywgJycpOwogICAgICAgICAgfQogICAgICAgIH0sIGl0ZW1TZXQpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZXMgdGhlIGhlaWdodCBmb3IgYSBnaXZlbiBzZXQgb2YgaXRlbXMuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PG51bWJlcj49fSBpdGVtU2V0CiAgICAgICAqLwogICAgICBfdXBkYXRlTWV0cmljczogZnVuY3Rpb24oaXRlbVNldCkgewogICAgICAgIC8vIE1ha2Ugc3VyZSB3ZSBkaXN0cmlidXRlZCBhbGwgdGhlIHBoeXNpY2FsIGl0ZW1zCiAgICAgICAgLy8gc28gd2UgY2FuIG1lYXN1cmUgdGhlbS4KICAgICAgICBmbHVzaCgpOwoKICAgICAgICB2YXIgbmV3UGh5c2ljYWxTaXplID0gMDsKICAgICAgICB2YXIgb2xkUGh5c2ljYWxTaXplID0gMDsKICAgICAgICB2YXIgcHJldkF2Z0NvdW50ID0gdGhpcy5fcGh5c2ljYWxBdmVyYWdlQ291bnQ7CiAgICAgICAgdmFyIHByZXZQaHlzaWNhbEF2ZyA9IHRoaXMuX3BoeXNpY2FsQXZlcmFnZTsKCiAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKGZ1bmN0aW9uKHBpZHgsIHZpZHgpIHsKICAgICAgICAgIG9sZFBoeXNpY2FsU2l6ZSArPSB0aGlzLl9waHlzaWNhbFNpemVzW3BpZHhdOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTaXplc1twaWR4XSA9IHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF0ub2Zmc2V0SGVpZ2h0OwogICAgICAgICAgbmV3UGh5c2ljYWxTaXplICs9IHRoaXMuX3BoeXNpY2FsU2l6ZXNbcGlkeF07CiAgICAgICAgICB0aGlzLl9waHlzaWNhbEF2ZXJhZ2VDb3VudCArPSB0aGlzLl9waHlzaWNhbFNpemVzW3BpZHhdID8gMSA6IDA7CiAgICAgICAgfSwgaXRlbVNldCk7CgogICAgICAgIGlmICh0aGlzLmdyaWQpIHsKICAgICAgICAgIHRoaXMuX3VwZGF0ZUdyaWRNZXRyaWNzKCk7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFNpemUgPQogICAgICAgICAgICAgIE1hdGguY2VpbCh0aGlzLl9waHlzaWNhbENvdW50IC8gdGhpcy5faXRlbXNQZXJSb3cpICogdGhpcy5fcm93SGVpZ2h0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBvbGRQaHlzaWNhbFNpemUgPSAodGhpcy5faXRlbXNQZXJSb3cgPT09IDEpID8KICAgICAgICAgICAgICBvbGRQaHlzaWNhbFNpemUgOgogICAgICAgICAgICAgIE1hdGguY2VpbCh0aGlzLl9waHlzaWNhbENvdW50IC8gdGhpcy5faXRlbXNQZXJSb3cpICogdGhpcy5fcm93SGVpZ2h0OwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTaXplID0KICAgICAgICAgICAgICB0aGlzLl9waHlzaWNhbFNpemUgKyBuZXdQaHlzaWNhbFNpemUgLSBvbGRQaHlzaWNhbFNpemU7CiAgICAgICAgICB0aGlzLl9pdGVtc1BlclJvdyA9IDE7CiAgICAgICAgfQogICAgICAgIC8vIFVwZGF0ZSB0aGUgYXZlcmFnZSBpZiBpdCBtZWFzdXJlZCBzb21ldGhpbmcuCiAgICAgICAgaWYgKHRoaXMuX3BoeXNpY2FsQXZlcmFnZUNvdW50ICE9PSBwcmV2QXZnQ291bnQpIHsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQXZlcmFnZSA9IE1hdGgucm91bmQoCiAgICAgICAgICAgICAgKChwcmV2UGh5c2ljYWxBdmcgKiBwcmV2QXZnQ291bnQpICsgbmV3UGh5c2ljYWxTaXplKSAvCiAgICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlQ291bnQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF91cGRhdGVHcmlkTWV0cmljczogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5faXRlbVdpZHRoID0gdGhpcy5fcGh5c2ljYWxDb3VudCA+IDAgPwogICAgICAgICAgICB0aGlzLl9waHlzaWNhbEl0ZW1zWzBdLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLndpZHRoIDoKICAgICAgICAgICAgMjAwOwogICAgICAgIHRoaXMuX3Jvd0hlaWdodCA9CiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQ291bnQgPiAwID8gdGhpcy5fcGh5c2ljYWxJdGVtc1swXS5vZmZzZXRIZWlnaHQgOiAyMDA7CiAgICAgICAgdGhpcy5faXRlbXNQZXJSb3cgPSB0aGlzLl9pdGVtV2lkdGggPwogICAgICAgICAgICBNYXRoLmZsb29yKHRoaXMuX3ZpZXdwb3J0V2lkdGggLyB0aGlzLl9pdGVtV2lkdGgpIDoKICAgICAgICAgICAgdGhpcy5faXRlbXNQZXJSb3c7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXBkYXRlcyB0aGUgcG9zaXRpb24gb2YgdGhlIHBoeXNpY2FsIGl0ZW1zLgogICAgICAgKi8KICAgICAgX3Bvc2l0aW9uSXRlbXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2FkanVzdFNjcm9sbFBvc2l0aW9uKCk7CgogICAgICAgIHZhciB5ID0gdGhpcy5fcGh5c2ljYWxUb3A7CgogICAgICAgIGlmICh0aGlzLmdyaWQpIHsKICAgICAgICAgIHZhciB0b3RhbEl0ZW1XaWR0aCA9IHRoaXMuX2l0ZW1zUGVyUm93ICogdGhpcy5faXRlbVdpZHRoOwogICAgICAgICAgdmFyIHJvd09mZnNldCA9ICh0aGlzLl92aWV3cG9ydFdpZHRoIC0gdG90YWxJdGVtV2lkdGgpIC8gMjsKCiAgICAgICAgICB0aGlzLl9pdGVyYXRlSXRlbXMoZnVuY3Rpb24ocGlkeCwgdmlkeCkgewogICAgICAgICAgICB2YXIgbW9kdWx1cyA9IHZpZHggJSB0aGlzLl9pdGVtc1BlclJvdzsKICAgICAgICAgICAgdmFyIHggPSBNYXRoLmZsb29yKChtb2R1bHVzICogdGhpcy5faXRlbVdpZHRoKSArIHJvd09mZnNldCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc1JUTCkgewogICAgICAgICAgICAgIHggPSB4ICogLTE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy50cmFuc2xhdGUzZCh4ICsgJ3B4JywgeSArICdweCcsIDAsIHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF0pOwogICAgICAgICAgICBpZiAodGhpcy5fc2hvdWxkUmVuZGVyTmV4dFJvdyh2aWR4KSkgewogICAgICAgICAgICAgIHkgKz0gdGhpcy5fcm93SGVpZ2h0OwogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY29uc3Qgb3JkZXIgPSBbXTsKICAgICAgICAgIHRoaXMuX2l0ZXJhdGVJdGVtcyhmdW5jdGlvbihwaWR4LCB2aWR4KSB7CiAgICAgICAgICAgIGNvbnN0IGl0ZW0gPSB0aGlzLl9waHlzaWNhbEl0ZW1zW3BpZHhdOwogICAgICAgICAgICB0aGlzLnRyYW5zbGF0ZTNkKDAsIHkgKyAncHgnLCAwLCBpdGVtKTsKICAgICAgICAgICAgeSArPSB0aGlzLl9waHlzaWNhbFNpemVzW3BpZHhdOwogICAgICAgICAgICBjb25zdCBpdGVtSWQgPSBpdGVtLmlkOwogICAgICAgICAgICBpZiAoaXRlbUlkKSB7CiAgICAgICAgICAgICAgb3JkZXIucHVzaChpdGVtSWQpOwogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICAgIGlmIChvcmRlci5sZW5ndGgpIHsKICAgICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtb3ducycsIG9yZGVyLmpvaW4oJyAnKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2dldFBoeXNpY2FsU2l6ZUluY3JlbWVudDogZnVuY3Rpb24ocGlkeCkgewogICAgICAgIGlmICghdGhpcy5ncmlkKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5fcGh5c2ljYWxTaXplc1twaWR4XTsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX2NvbXB1dGVWaWR4KHBpZHgpICUgdGhpcy5faXRlbXNQZXJSb3cgIT09IHRoaXMuX2l0ZW1zUGVyUm93IC0gMSkgewogICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLl9yb3dIZWlnaHQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucywgYmFzZWQgb24gdGhlIGN1cnJlbnQgaW5kZXgsCiAgICAgICAqIHdoZXRoZXIgb3Igbm90IHRoZSBuZXh0IGluZGV4IHdpbGwgbmVlZAogICAgICAgKiB0byBiZSByZW5kZXJlZCBvbiBhIG5ldyByb3cuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSB2aWR4IFZpcnR1YWwgaW5kZXgKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICovCiAgICAgIF9zaG91bGRSZW5kZXJOZXh0Um93OiBmdW5jdGlvbih2aWR4KSB7CiAgICAgICAgcmV0dXJuIHZpZHggJSB0aGlzLl9pdGVtc1BlclJvdyA9PT0gdGhpcy5faXRlbXNQZXJSb3cgLSAxOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEFkanVzdHMgdGhlIHNjcm9sbCBwb3NpdGlvbiB3aGVuIGl0IHdhcyBvdmVyZXN0aW1hdGVkLgogICAgICAgKi8KICAgICAgX2FkanVzdFNjcm9sbFBvc2l0aW9uOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZGVsdGFIZWlnaHQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgPT09IDAgPwogICAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA6CiAgICAgICAgICAgIE1hdGgubWluKHRoaXMuX3Njcm9sbFBvc2l0aW9uICsgdGhpcy5fcGh5c2ljYWxUb3AsIDApOwogICAgICAgIC8vIE5vdGU6IHRoZSBkZWx0YSBjYW4gYmUgcG9zaXRpdmUgb3IgbmVnYXRpdmUuCiAgICAgICAgaWYgKGRlbHRhSGVpZ2h0ICE9PSAwKSB7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IHRoaXMuX3BoeXNpY2FsVG9wIC0gZGVsdGFIZWlnaHQ7CiAgICAgICAgICAvLyBUaGlzIG1heSBiZSBjYWxsZWQgb3V0c2lkZSBvZiBhIHNjcm9sbEhhbmRsZXIsIHNvIHVzZSBsYXN0IGNhY2hlZCBwb3NpdGlvbgogICAgICAgICAgdmFyIHNjcm9sbFRvcCA9IHRoaXMuX3Njcm9sbFBvc2l0aW9uOwogICAgICAgICAgLy8ganVraW5nIHNjcm9sbCBwb3NpdGlvbiBkdXJpbmcgaW50ZXJpYWwgc2Nyb2xsaW5nIG9uIGlPUyBpcyBubyBidWVubwogICAgICAgICAgaWYgKCFJT1NfVE9VQ0hfU0NST0xMSU5HICYmIHNjcm9sbFRvcCA+IDApIHsKICAgICAgICAgICAgdGhpcy5fcmVzZXRTY3JvbGxQb3NpdGlvbihzY3JvbGxUb3AgLSBkZWx0YUhlaWdodCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNldHMgdGhlIHBvc2l0aW9uIG9mIHRoZSBzY3JvbGwuCiAgICAgICAqLwogICAgICBfcmVzZXRTY3JvbGxQb3NpdGlvbjogZnVuY3Rpb24ocG9zKSB7CiAgICAgICAgaWYgKHRoaXMuc2Nyb2xsVGFyZ2V0ICYmIHBvcyA+PSAwKSB7CiAgICAgICAgICB0aGlzLl9zY3JvbGxUb3AgPSBwb3M7CiAgICAgICAgICB0aGlzLl9zY3JvbGxQb3NpdGlvbiA9IHRoaXMuX3Njcm9sbFRvcDsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgc2Nyb2xsIGhlaWdodCwgdGhhdCdzIHRoZSBoZWlnaHQgb2YgdGhlIGNvbnRlbnQsCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbj19IGZvcmNlVXBkYXRlIElmIHRydWUsIHVwZGF0ZXMgdGhlIGhlaWdodCBubyBtYXR0ZXIgd2hhdC4KICAgICAgICovCiAgICAgIF91cGRhdGVTY3JvbGxlclNpemU6IGZ1bmN0aW9uKGZvcmNlVXBkYXRlKSB7CiAgICAgICAgaWYgKHRoaXMuZ3JpZCkgewogICAgICAgICAgdGhpcy5fZXN0U2Nyb2xsSGVpZ2h0ID0gdGhpcy5fdmlydHVhbFJvd0NvdW50ICogdGhpcy5fcm93SGVpZ2h0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9lc3RTY3JvbGxIZWlnaHQgPQogICAgICAgICAgICAgICh0aGlzLl9waHlzaWNhbEJvdHRvbSArCiAgICAgICAgICAgICAgIE1hdGgubWF4KAogICAgICAgICAgICAgICAgICAgdGhpcy5fdmlydHVhbENvdW50IC0gdGhpcy5fcGh5c2ljYWxDb3VudCAtIHRoaXMuX3ZpcnR1YWxTdGFydCwKICAgICAgICAgICAgICAgICAgIDApICoKICAgICAgICAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQXZlcmFnZSk7CiAgICAgICAgfQogICAgICAgIGZvcmNlVXBkYXRlID0gZm9yY2VVcGRhdGUgfHwgdGhpcy5fc2Nyb2xsSGVpZ2h0ID09PSAwOwogICAgICAgIGZvcmNlVXBkYXRlID0gZm9yY2VVcGRhdGUgfHwKICAgICAgICAgICAgdGhpcy5fc2Nyb2xsUG9zaXRpb24gPj0gdGhpcy5fZXN0U2Nyb2xsSGVpZ2h0IC0gdGhpcy5fcGh5c2ljYWxTaXplOwogICAgICAgIGZvcmNlVXBkYXRlID0gZm9yY2VVcGRhdGUgfHwKICAgICAgICAgICAgdGhpcy5ncmlkICYmIHRoaXMuJC5pdGVtcy5zdHlsZS5oZWlnaHQgPCB0aGlzLl9lc3RTY3JvbGxIZWlnaHQ7CiAgICAgICAgLy8gQW1vcnRpemUgaGVpZ2h0IGFkanVzdG1lbnQsIHNvIGl0IHdvbid0IHRyaWdnZXIgbGFyZ2UgcmVwYWludHMgdG9vIG9mdGVuLgogICAgICAgIGlmIChmb3JjZVVwZGF0ZSB8fAogICAgICAgICAgICBNYXRoLmFicyh0aGlzLl9lc3RTY3JvbGxIZWlnaHQgLSB0aGlzLl9zY3JvbGxIZWlnaHQpID49CiAgICAgICAgICAgICAgICB0aGlzLl92aWV3cG9ydEhlaWdodCkgewogICAgICAgICAgdGhpcy4kLml0ZW1zLnN0eWxlLmhlaWdodCA9IHRoaXMuX2VzdFNjcm9sbEhlaWdodCArICdweCc7CiAgICAgICAgICB0aGlzLl9zY3JvbGxIZWlnaHQgPSB0aGlzLl9lc3RTY3JvbGxIZWlnaHQ7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNjcm9sbCB0byBhIHNwZWNpZmljIGl0ZW0gaW4gdGhlIHZpcnR1YWwgbGlzdCByZWdhcmRsZXNzCiAgICAgICAqIG9mIHRoZSBwaHlzaWNhbCBpdGVtcyBpbiB0aGUgRE9NIHRyZWUuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2Qgc2Nyb2xsVG9JdGVtCiAgICAgICAqIEBwYXJhbSB7KE9iamVjdCl9IGl0ZW0gVGhlIGl0ZW0gdG8gYmUgc2Nyb2xsZWQgdG8KICAgICAgICovCiAgICAgIHNjcm9sbFRvSXRlbTogZnVuY3Rpb24oaXRlbSkgewogICAgICAgIHJldHVybiB0aGlzLnNjcm9sbFRvSW5kZXgodGhpcy5pdGVtcy5pbmRleE9mKGl0ZW0pKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTY3JvbGwgdG8gYSBzcGVjaWZpYyBpbmRleCBpbiB0aGUgdmlydHVhbCBsaXN0IHJlZ2FyZGxlc3MKICAgICAgICogb2YgdGhlIHBoeXNpY2FsIGl0ZW1zIGluIHRoZSBET00gdHJlZS4KICAgICAgICoKICAgICAgICogQG1ldGhvZCBzY3JvbGxUb0luZGV4CiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBpZHggVGhlIGluZGV4IG9mIHRoZSBpdGVtCiAgICAgICAqLwogICAgICBzY3JvbGxUb0luZGV4OiBmdW5jdGlvbihpZHgpIHsKICAgICAgICBpZiAodHlwZW9mIGlkeCAhPT0gJ251bWJlcicgfHwgaWR4IDwgMCB8fCBpZHggPiB0aGlzLml0ZW1zLmxlbmd0aCAtIDEpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgZmx1c2goKTsKICAgICAgICAvLyBJdGVtcyBzaG91bGQgaGF2ZSBiZWVuIHJlbmRlcmVkIHByaW9yIHNjcm9sbGluZyB0byBhbiBpbmRleC4KICAgICAgICBpZiAodGhpcy5fcGh5c2ljYWxDb3VudCA9PT0gMCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZHggPSB0aGlzLl9jbGFtcChpZHgsIDAsIHRoaXMuX3ZpcnR1YWxDb3VudCAtIDEpOwogICAgICAgIC8vIFVwZGF0ZSB0aGUgdmlydHVhbCBzdGFydCBvbmx5IHdoZW4gbmVlZGVkLgogICAgICAgIGlmICghdGhpcy5faXNJbmRleFJlbmRlcmVkKGlkeCkgfHwgaWR4ID49IHRoaXMuX21heFZpcnR1YWxTdGFydCkgewogICAgICAgICAgdGhpcy5fdmlydHVhbFN0YXJ0ID0KICAgICAgICAgICAgICB0aGlzLmdyaWQgPyAoaWR4IC0gdGhpcy5faXRlbXNQZXJSb3cgKiAyKSA6IChpZHggLSAxKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fbWFuYWdlRm9jdXMoKTsKICAgICAgICB0aGlzLl9hc3NpZ25Nb2RlbHMoKTsKICAgICAgICB0aGlzLl91cGRhdGVNZXRyaWNzKCk7CiAgICAgICAgLy8gRXN0aW1hdGUgbmV3IHBoeXNpY2FsIG9mZnNldC4KICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IE1hdGguZmxvb3IodGhpcy5fdmlydHVhbFN0YXJ0IC8gdGhpcy5faXRlbXNQZXJSb3cpICoKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlOwoKICAgICAgICB2YXIgY3VycmVudFRvcEl0ZW0gPSB0aGlzLl9waHlzaWNhbFN0YXJ0OwogICAgICAgIHZhciBjdXJyZW50VmlydHVhbEl0ZW0gPSB0aGlzLl92aXJ0dWFsU3RhcnQ7CiAgICAgICAgdmFyIHRhcmdldE9mZnNldFRvcCA9IDA7CiAgICAgICAgdmFyIGhpZGRlbkNvbnRlbnRTaXplID0gdGhpcy5faGlkZGVuQ29udGVudFNpemU7CiAgICAgICAgLy8gc2Nyb2xsIHRvIHRoZSBpdGVtIGFzIG11Y2ggYXMgd2UgY2FuLgogICAgICAgIHdoaWxlIChjdXJyZW50VmlydHVhbEl0ZW0gPCBpZHggJiYgdGFyZ2V0T2Zmc2V0VG9wIDw9IGhpZGRlbkNvbnRlbnRTaXplKSB7CiAgICAgICAgICB0YXJnZXRPZmZzZXRUb3AgPQogICAgICAgICAgICAgIHRhcmdldE9mZnNldFRvcCArIHRoaXMuX2dldFBoeXNpY2FsU2l6ZUluY3JlbWVudChjdXJyZW50VG9wSXRlbSk7CiAgICAgICAgICBjdXJyZW50VG9wSXRlbSA9IChjdXJyZW50VG9wSXRlbSArIDEpICUgdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgICAgIGN1cnJlbnRWaXJ0dWFsSXRlbSsrOwogICAgICAgIH0KICAgICAgICB0aGlzLl91cGRhdGVTY3JvbGxlclNpemUodHJ1ZSk7CiAgICAgICAgdGhpcy5fcG9zaXRpb25JdGVtcygpOwogICAgICAgIHRoaXMuX3Jlc2V0U2Nyb2xsUG9zaXRpb24oCiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsVG9wICsgdGhpcy5fc2Nyb2xsT2Zmc2V0ICsgdGFyZ2V0T2Zmc2V0VG9wKTsKICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZCgwKTsKICAgICAgICAvLyBjbGVhciBjYWNoZWQgdmlzaWJsZSBpbmRleC4KICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgICAgdGhpcy5fbGFzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVzZXQgdGhlIHBoeXNpY2FsIGF2ZXJhZ2UgYW5kIHRoZSBhdmVyYWdlIGNvdW50LgogICAgICAgKi8KICAgICAgX3Jlc2V0QXZlcmFnZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlID0gMDsKICAgICAgICB0aGlzLl9waHlzaWNhbEF2ZXJhZ2VDb3VudCA9IDA7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQSBoYW5kbGVyIGZvciB0aGUgYGlyb24tcmVzaXplYCBldmVudCB0cmlnZ2VyZWQgYnkgYElyb25SZXNpemFibGVCZWhhdmlvcmAKICAgICAgICogd2hlbiB0aGUgZWxlbWVudCBpcyByZXNpemVkLgogICAgICAgKi8KICAgICAgX3Jlc2l6ZUhhbmRsZXI6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2RlYm91bmNlKCdfcmVuZGVyJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICAvLyBjbGVhciBjYWNoZWQgdmlzaWJsZSBpbmRleC4KICAgICAgICAgIHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWwgPSBudWxsOwogICAgICAgICAgaWYgKHRoaXMuX2lzVmlzaWJsZSkgewogICAgICAgICAgICB0aGlzLnVwZGF0ZVZpZXdwb3J0Qm91bmRhcmllcygpOwogICAgICAgICAgICAvLyBSZWluc3RhbGwgdGhlIHNjcm9sbCBldmVudCBsaXN0ZW5lci4KICAgICAgICAgICAgdGhpcy50b2dnbGVTY3JvbGxMaXN0ZW5lcih0cnVlKTsKICAgICAgICAgICAgdGhpcy5fcmVzZXRBdmVyYWdlKCk7CiAgICAgICAgICAgIHRoaXMuX3JlbmRlcigpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gVW5pbnN0YWxsIHRoZSBzY3JvbGwgZXZlbnQgbGlzdGVuZXIuCiAgICAgICAgICAgIHRoaXMudG9nZ2xlU2Nyb2xsTGlzdGVuZXIoZmFsc2UpOwogICAgICAgICAgfQogICAgICAgIH0sIGFuaW1hdGlvbkZyYW1lKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3RzIHRoZSBnaXZlbiBpdGVtLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHNlbGVjdEl0ZW0KICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZW0gVGhlIGl0ZW0gaW5zdGFuY2UuCiAgICAgICAqLwogICAgICBzZWxlY3RJdGVtOiBmdW5jdGlvbihpdGVtKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0SW5kZXgodGhpcy5pdGVtcy5pbmRleE9mKGl0ZW0pKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3RzIHRoZSBpdGVtIGF0IHRoZSBnaXZlbiBpbmRleCBpbiB0aGUgaXRlbXMgYXJyYXkuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2Qgc2VsZWN0SW5kZXgKICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGluZGV4IFRoZSBpbmRleCBvZiB0aGUgaXRlbSBpbiB0aGUgaXRlbXMgYXJyYXkuCiAgICAgICAqLwogICAgICBzZWxlY3RJbmRleDogZnVuY3Rpb24oaW5kZXgpIHsKICAgICAgICBpZiAoaW5kZXggPCAwIHx8IGluZGV4ID49IHRoaXMuX3ZpcnR1YWxDb3VudCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAoIXRoaXMubXVsdGlTZWxlY3Rpb24gJiYgdGhpcy5zZWxlY3RlZEl0ZW0pIHsKICAgICAgICAgIHRoaXMuY2xlYXJTZWxlY3Rpb24oKTsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX2lzSW5kZXhSZW5kZXJlZChpbmRleCkpIHsKICAgICAgICAgIHZhciBtb2RlbCA9IHRoaXMubW9kZWxGb3JFbGVtZW50KAogICAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsSXRlbXNbdGhpcy5fZ2V0UGh5c2ljYWxJbmRleChpbmRleCldKTsKICAgICAgICAgIGlmIChtb2RlbCkgewogICAgICAgICAgICBtb2RlbFt0aGlzLnNlbGVjdGVkQXNdID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMudXBkYXRlU2l6ZUZvckluZGV4KGluZGV4KTsKICAgICAgICB9CiAgICAgICAgdGhpcy4kLnNlbGVjdG9yLnNlbGVjdEluZGV4KGluZGV4KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBEZXNlbGVjdHMgdGhlIGdpdmVuIGl0ZW0uCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgZGVzZWxlY3QKICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZW0gVGhlIGl0ZW0gaW5zdGFuY2UuCiAgICAgICAqLwogICAgICBkZXNlbGVjdEl0ZW06IGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICByZXR1cm4gdGhpcy5kZXNlbGVjdEluZGV4KHRoaXMuaXRlbXMuaW5kZXhPZihpdGVtKSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRGVzZWxlY3RzIHRoZSBpdGVtIGF0IHRoZSBnaXZlbiBpbmRleCBpbiB0aGUgaXRlbXMgYXJyYXkuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgZGVzZWxlY3RJbmRleAogICAgICAgKiBAcGFyYW0ge251bWJlcn0gaW5kZXggVGhlIGluZGV4IG9mIHRoZSBpdGVtIGluIHRoZSBpdGVtcyBhcnJheS4KICAgICAgICovCiAgICAgIGRlc2VsZWN0SW5kZXg6IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgaWYgKGluZGV4IDwgMCB8fCBpbmRleCA+PSB0aGlzLl92aXJ0dWFsQ291bnQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX2lzSW5kZXhSZW5kZXJlZChpbmRleCkpIHsKICAgICAgICAgIHZhciBtb2RlbCA9IHRoaXMubW9kZWxGb3JFbGVtZW50KAogICAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsSXRlbXNbdGhpcy5fZ2V0UGh5c2ljYWxJbmRleChpbmRleCldKTsKICAgICAgICAgIG1vZGVsW3RoaXMuc2VsZWN0ZWRBc10gPSBmYWxzZTsKICAgICAgICAgIHRoaXMudXBkYXRlU2l6ZUZvckluZGV4KGluZGV4KTsKICAgICAgICB9CiAgICAgICAgdGhpcy4kLnNlbGVjdG9yLmRlc2VsZWN0SW5kZXgoaW5kZXgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNlbGVjdHMgb3IgZGVzZWxlY3RzIGEgZ2l2ZW4gaXRlbSBkZXBlbmRpbmcgb24gd2hldGhlciB0aGUgaXRlbQogICAgICAgKiBoYXMgYWxyZWFkeSBiZWVuIHNlbGVjdGVkLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHRvZ2dsZVNlbGVjdGlvbkZvckl0ZW0KICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZW0gVGhlIGl0ZW0gb2JqZWN0LgogICAgICAgKi8KICAgICAgdG9nZ2xlU2VsZWN0aW9uRm9ySXRlbTogZnVuY3Rpb24oaXRlbSkgewogICAgICAgIHJldHVybiB0aGlzLnRvZ2dsZVNlbGVjdGlvbkZvckluZGV4KHRoaXMuaXRlbXMuaW5kZXhPZihpdGVtKSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2VsZWN0cyBvciBkZXNlbGVjdHMgdGhlIGl0ZW0gYXQgdGhlIGdpdmVuIGluZGV4IGluIHRoZSBpdGVtcyBhcnJheQogICAgICAgKiBkZXBlbmRpbmcgb24gd2hldGhlciB0aGUgaXRlbSBoYXMgYWxyZWFkeSBiZWVuIHNlbGVjdGVkLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHRvZ2dsZVNlbGVjdGlvbkZvckluZGV4CiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBpbmRleCBUaGUgaW5kZXggb2YgdGhlIGl0ZW0gaW4gdGhlIGl0ZW1zIGFycmF5LgogICAgICAgKi8KICAgICAgdG9nZ2xlU2VsZWN0aW9uRm9ySW5kZXg6IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgdmFyIGlzU2VsZWN0ZWQgPSB0aGlzLiQuc2VsZWN0b3IuaXNJbmRleFNlbGVjdGVkID8KICAgICAgICAgICAgdGhpcy4kLnNlbGVjdG9yLmlzSW5kZXhTZWxlY3RlZChpbmRleCkgOgogICAgICAgICAgICB0aGlzLiQuc2VsZWN0b3IuaXNTZWxlY3RlZCh0aGlzLml0ZW1zW2luZGV4XSk7CiAgICAgICAgaXNTZWxlY3RlZCA/IHRoaXMuZGVzZWxlY3RJbmRleChpbmRleCkgOiB0aGlzLnNlbGVjdEluZGV4KGluZGV4KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDbGVhcnMgdGhlIGN1cnJlbnQgc2VsZWN0aW9uIGluIHRoZSBsaXN0LgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIGNsZWFyU2VsZWN0aW9uCiAgICAgICAqLwogICAgICBjbGVhclNlbGVjdGlvbjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKGZ1bmN0aW9uKHBpZHgsIHZpZHgpIHsKICAgICAgICAgIHRoaXMubW9kZWxGb3JFbGVtZW50KHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF0pW3RoaXMuc2VsZWN0ZWRBc10gPSBmYWxzZTsKICAgICAgICB9KTsKICAgICAgICB0aGlzLiQuc2VsZWN0b3IuY2xlYXJTZWxlY3Rpb24oKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBZGQgYW4gZXZlbnQgbGlzdGVuZXIgdG8gYHRhcGAgaWYgYHNlbGVjdGlvbkVuYWJsZWRgIGlzIHRydWUsCiAgICAgICAqIGl0IHdpbGwgcmVtb3ZlIHRoZSBsaXN0ZW5lciBvdGhlcndpc2UuCiAgICAgICAqLwogICAgICBfc2VsZWN0aW9uRW5hYmxlZENoYW5nZWQ6IGZ1bmN0aW9uKHNlbGVjdGlvbkVuYWJsZWQpIHsKICAgICAgICB2YXIgaGFuZGxlciA9IHNlbGVjdGlvbkVuYWJsZWQgPyB0aGlzLmxpc3RlbiA6IHRoaXMudW5saXN0ZW47CiAgICAgICAgaGFuZGxlci5jYWxsKHRoaXMsIHRoaXMsICd0YXAnLCAnX3NlbGVjdGlvbkhhbmRsZXInKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3QgYW4gaXRlbSBmcm9tIGFuIGV2ZW50IG9iamVjdC4KICAgICAgICovCiAgICAgIF9zZWxlY3Rpb25IYW5kbGVyOiBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIG1vZGVsID0gdGhpcy5tb2RlbEZvckVsZW1lbnQoZS50YXJnZXQpOwogICAgICAgIGlmICghbW9kZWwpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdmFyIG1vZGVsVGFiSW5kZXgsIGFjdGl2ZUVsVGFiSW5kZXg7CiAgICAgICAgdmFyIHRhcmdldCA9IGRvbShlKS5wYXRoWzBdOwogICAgICAgIHZhciBhY3RpdmVFbCA9IHRoaXMuX2dldEFjdGl2ZUVsZW1lbnQoKTsKICAgICAgICB2YXIgcGh5c2ljYWxJdGVtID0KICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxJdGVtc1t0aGlzLl9nZXRQaHlzaWNhbEluZGV4KG1vZGVsW3RoaXMuaW5kZXhBc10pXTsKICAgICAgICAvLyBTYWZhcmkgZG9lcyBub3QgZm9jdXMgY2VydGFpbiBmb3JtIGNvbnRyb2xzIHZpYSBtb3VzZQogICAgICAgIC8vIGh0dHBzOi8vYnVncy53ZWJraXQub3JnL3Nob3dfYnVnLmNnaT9pZD0xMTgwNDMKICAgICAgICBpZiAodGFyZ2V0LmxvY2FsTmFtZSA9PT0gJ2lucHV0JyB8fCB0YXJnZXQubG9jYWxOYW1lID09PSAnYnV0dG9uJyB8fAogICAgICAgICAgICB0YXJnZXQubG9jYWxOYW1lID09PSAnc2VsZWN0JykgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICAvLyBTZXQgYSB0ZW1wb3JhcnkgdGFiaW5kZXgKICAgICAgICBtb2RlbFRhYkluZGV4ID0gbW9kZWwudGFiSW5kZXg7CiAgICAgICAgbW9kZWwudGFiSW5kZXggPSBTRUNSRVRfVEFCSU5ERVg7CiAgICAgICAgYWN0aXZlRWxUYWJJbmRleCA9IGFjdGl2ZUVsID8gYWN0aXZlRWwudGFiSW5kZXggOiAtMTsKICAgICAgICBtb2RlbC50YWJJbmRleCA9IG1vZGVsVGFiSW5kZXg7CiAgICAgICAgLy8gT25seSBzZWxlY3QgdGhlIGl0ZW0gaWYgdGhlIHRhcCB3YXNuJ3Qgb24gYSBmb2N1c2FibGUgY2hpbGQKICAgICAgICAvLyBvciB0aGUgZWxlbWVudCBib3VuZCB0byBgdGFiSW5kZXhgCiAgICAgICAgaWYgKGFjdGl2ZUVsICYmIHBoeXNpY2FsSXRlbSAhPT0gYWN0aXZlRWwgJiYKICAgICAgICAgICAgcGh5c2ljYWxJdGVtLmNvbnRhaW5zKGFjdGl2ZUVsKSAmJgogICAgICAgICAgICBhY3RpdmVFbFRhYkluZGV4ICE9PSBTRUNSRVRfVEFCSU5ERVgpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpcy50b2dnbGVTZWxlY3Rpb25Gb3JJdGVtKG1vZGVsW3RoaXMuYXNdKTsKICAgICAgfSwKCiAgICAgIF9tdWx0aVNlbGVjdGlvbkNoYW5nZWQ6IGZ1bmN0aW9uKG11bHRpU2VsZWN0aW9uKSB7CiAgICAgICAgdGhpcy5jbGVhclNlbGVjdGlvbigpOwogICAgICAgIHRoaXMuJC5zZWxlY3Rvci5tdWx0aSA9IG11bHRpU2VsZWN0aW9uOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZXMgdGhlIHNpemUgb2YgYSBnaXZlbiBsaXN0IGl0ZW0uCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgdXBkYXRlU2l6ZUZvckl0ZW0KICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZW0gVGhlIGl0ZW0gaW5zdGFuY2UuCiAgICAgICAqLwogICAgICB1cGRhdGVTaXplRm9ySXRlbTogZnVuY3Rpb24oaXRlbSkgewogICAgICAgIHJldHVybiB0aGlzLnVwZGF0ZVNpemVGb3JJbmRleCh0aGlzLml0ZW1zLmluZGV4T2YoaXRlbSkpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZXMgdGhlIHNpemUgb2YgdGhlIGl0ZW0gYXQgdGhlIGdpdmVuIGluZGV4IGluIHRoZSBpdGVtcyBhcnJheS4KICAgICAgICoKICAgICAgICogQG1ldGhvZCB1cGRhdGVTaXplRm9ySW5kZXgKICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGluZGV4IFRoZSBpbmRleCBvZiB0aGUgaXRlbSBpbiB0aGUgaXRlbXMgYXJyYXkuCiAgICAgICAqLwogICAgICB1cGRhdGVTaXplRm9ySW5kZXg6IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgaWYgKCF0aGlzLl9pc0luZGV4UmVuZGVyZWQoaW5kZXgpKSB7CiAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgICAgdGhpcy5fdXBkYXRlTWV0cmljcyhbdGhpcy5fZ2V0UGh5c2ljYWxJbmRleChpbmRleCldKTsKICAgICAgICB0aGlzLl9wb3NpdGlvbkl0ZW1zKCk7CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ3JlYXRlcyBhIHRlbXBvcmFyeSBiYWNrZmlsbCBpdGVtIGluIHRoZSByZW5kZXJlZCBwb29sIG9mIHBoeXNpY2FsIGl0ZW1zCiAgICAgICAqIHRvIHJlcGxhY2UgdGhlIG1haW4gZm9jdXNlZCBpdGVtLiBUaGUgZm9jdXNlZCBpdGVtIGhhcyB0YWJJbmRleCA9IDAKICAgICAgICogYW5kIG1pZ2h0IGJlIGN1cnJlbnRseSBmb2N1c2VkIGJ5IHRoZSB1c2VyLgogICAgICAgKgogICAgICAgKiBUaGlzIGR5bmFtaWMgcmVwbGFjZW1lbnQgaGVscHMgdG8gcHJlc2VydmUgdGhlIGZvY3VzIHN0YXRlLgogICAgICAgKi8KICAgICAgX21hbmFnZUZvY3VzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZmlkeCA9IHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXg7CgogICAgICAgIGlmIChmaWR4ID49IDAgJiYgZmlkeCA8IHRoaXMuX3ZpcnR1YWxDb3VudCkgewogICAgICAgICAgLy8gaWYgaXQncyBhIHZhbGlkIGluZGV4LCBjaGVjayBpZiB0aGF0IGluZGV4IGlzIHJlbmRlcmVkCiAgICAgICAgICAvLyBpbiBhIHBoeXNpY2FsIGl0ZW0uCiAgICAgICAgICBpZiAodGhpcy5faXNJbmRleFJlbmRlcmVkKGZpZHgpKSB7CiAgICAgICAgICAgIHRoaXMuX3Jlc3RvcmVGb2N1c2VkSXRlbSgpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fY3JlYXRlRm9jdXNCYWNrZmlsbEl0ZW0oKTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX3ZpcnR1YWxDb3VudCA+IDAgJiYgdGhpcy5fcGh5c2ljYWxDb3VudCA+IDApIHsKICAgICAgICAgIC8vIG90aGVyd2lzZSwgYXNzaWduIHRoZSBpbml0aWFsIGZvY3VzZWQgaW5kZXguCiAgICAgICAgICB0aGlzLl9mb2N1c2VkUGh5c2ljYWxJbmRleCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQ7CiAgICAgICAgICB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4ID0gdGhpcy5fdmlydHVhbFN0YXJ0OwogICAgICAgICAgdGhpcy5fZm9jdXNlZEl0ZW0gPSB0aGlzLl9waHlzaWNhbEl0ZW1zW3RoaXMuX3BoeXNpY2FsU3RhcnRdOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDb252ZXJ0cyBhIHJhbmRvbSBpbmRleCB0byB0aGUgaW5kZXggb2YgdGhlIGl0ZW0gdGhhdCBjb21wbGV0ZXMgaXQncyByb3cuCiAgICAgICAqIEFsbG93cyBmb3IgYmV0dGVyIG9yZGVyIGFuZCBmaWxsIGNvbXB1dGF0aW9uIHdoZW4gZ3JpZCA9PSB0cnVlLgogICAgICAgKi8KICAgICAgX2NvbnZlcnRJbmRleFRvQ29tcGxldGVSb3c6IGZ1bmN0aW9uKGlkeCkgewogICAgICAgIC8vIHdoZW4gZ3JpZCA9PSBmYWxzZSBfaXRlbVBlclJvdyBjYW4gYmUgdW5zZXQuCiAgICAgICAgdGhpcy5faXRlbXNQZXJSb3cgPSB0aGlzLl9pdGVtc1BlclJvdyB8fCAxOwogICAgICAgIHJldHVybiB0aGlzLmdyaWQgPyBNYXRoLmNlaWwoaWR4IC8gdGhpcy5faXRlbXNQZXJSb3cpICogdGhpcy5faXRlbXNQZXJSb3cgOgogICAgICAgICAgICAgICAgICAgICAgICAgICBpZHg7CiAgICAgIH0sCgogICAgICBfaXNJbmRleFJlbmRlcmVkOiBmdW5jdGlvbihpZHgpIHsKICAgICAgICByZXR1cm4gaWR4ID49IHRoaXMuX3ZpcnR1YWxTdGFydCAmJiBpZHggPD0gdGhpcy5fdmlydHVhbEVuZDsKICAgICAgfSwKCiAgICAgIF9pc0luZGV4VmlzaWJsZTogZnVuY3Rpb24oaWR4KSB7CiAgICAgICAgcmV0dXJuIGlkeCA+PSB0aGlzLmZpcnN0VmlzaWJsZUluZGV4ICYmIGlkeCA8PSB0aGlzLmxhc3RWaXNpYmxlSW5kZXg7CiAgICAgIH0sCgogICAgICBfZ2V0UGh5c2ljYWxJbmRleDogZnVuY3Rpb24odmlkeCkgewogICAgICAgIHJldHVybiAodGhpcy5fcGh5c2ljYWxTdGFydCArICh2aWR4IC0gdGhpcy5fdmlydHVhbFN0YXJ0KSkgJQogICAgICAgICAgICB0aGlzLl9waHlzaWNhbENvdW50OwogICAgICB9LAoKICAgICAgZm9jdXNJdGVtOiBmdW5jdGlvbihpZHgpIHsKICAgICAgICB0aGlzLl9mb2N1c1BoeXNpY2FsSXRlbShpZHgpOwogICAgICB9LAoKICAgICAgX2ZvY3VzUGh5c2ljYWxJdGVtOiBmdW5jdGlvbihpZHgpIHsKICAgICAgICBpZiAoaWR4IDwgMCB8fCBpZHggPj0gdGhpcy5fdmlydHVhbENvdW50KSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuX3Jlc3RvcmVGb2N1c2VkSXRlbSgpOwogICAgICAgIC8vIHNjcm9sbCB0byBpbmRleCB0byBtYWtlIHN1cmUgaXQncyByZW5kZXJlZAogICAgICAgIGlmICghdGhpcy5faXNJbmRleFJlbmRlcmVkKGlkeCkpIHsKICAgICAgICAgIHRoaXMuc2Nyb2xsVG9JbmRleChpZHgpOwogICAgICAgIH0KICAgICAgICB2YXIgcGh5c2ljYWxJdGVtID0gdGhpcy5fcGh5c2ljYWxJdGVtc1t0aGlzLl9nZXRQaHlzaWNhbEluZGV4KGlkeCldOwogICAgICAgIHZhciBtb2RlbCA9IHRoaXMubW9kZWxGb3JFbGVtZW50KHBoeXNpY2FsSXRlbSk7CiAgICAgICAgdmFyIGZvY3VzYWJsZTsKICAgICAgICAvLyBzZXQgYSBzZWNyZXQgdGFiIGluZGV4CiAgICAgICAgbW9kZWwudGFiSW5kZXggPSBTRUNSRVRfVEFCSU5ERVg7CiAgICAgICAgLy8gY2hlY2sgaWYgZm9jdXNhYmxlIGVsZW1lbnQgaXMgdGhlIHBoeXNpY2FsIGl0ZW0KICAgICAgICBpZiAocGh5c2ljYWxJdGVtLnRhYkluZGV4ID09PSBTRUNSRVRfVEFCSU5ERVgpIHsKICAgICAgICAgIGZvY3VzYWJsZSA9IHBoeXNpY2FsSXRlbTsKICAgICAgICB9CiAgICAgICAgLy8gc2VhcmNoIGZvciB0aGUgZWxlbWVudCB3aGljaCB0YWJpbmRleCBpcyBib3VuZCB0byB0aGUgc2VjcmV0IHRhYiBpbmRleAogICAgICAgIGlmICghZm9jdXNhYmxlKSB7CiAgICAgICAgICBmb2N1c2FibGUgPSBkb20ocGh5c2ljYWxJdGVtKQogICAgICAgICAgICAgICAgICAgICAgICAgIC5xdWVyeVNlbGVjdG9yKCdbdGFiaW5kZXg9IicgKyBTRUNSRVRfVEFCSU5ERVggKyAnIl0nKTsKICAgICAgICB9CiAgICAgICAgLy8gcmVzdG9yZSB0aGUgdGFiIGluZGV4CiAgICAgICAgbW9kZWwudGFiSW5kZXggPSAwOwogICAgICAgIC8vIGZvY3VzIHRoZSBmb2N1c2FibGUgZWxlbWVudAogICAgICAgIHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXggPSBpZHg7CiAgICAgICAgZm9jdXNhYmxlICYmIGZvY3VzYWJsZS5mb2N1cygpOwogICAgICB9LAoKICAgICAgX3JlbW92ZUZvY3VzZWRJdGVtOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0pIHsKICAgICAgICAgIHRoaXMuX2l0ZW1zUGFyZW50LnJlbW92ZUNoaWxkKHRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0gPSBudWxsOwogICAgICAgIHRoaXMuX2ZvY3VzQmFja2ZpbGxJdGVtID0gbnVsbDsKICAgICAgICB0aGlzLl9mb2N1c2VkSXRlbSA9IG51bGw7CiAgICAgICAgdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCA9IC0xOwogICAgICAgIHRoaXMuX2ZvY3VzZWRQaHlzaWNhbEluZGV4ID0gLTE7CiAgICAgIH0sCgogICAgICBfY3JlYXRlRm9jdXNCYWNrZmlsbEl0ZW06IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBmcGlkeCA9IHRoaXMuX2ZvY3VzZWRQaHlzaWNhbEluZGV4OwoKICAgICAgICBpZiAodGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0gfHwgdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCA8IDApIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgaWYgKCF0aGlzLl9mb2N1c0JhY2tmaWxsSXRlbSkgewogICAgICAgICAgLy8gQ3JlYXRlIGEgcGh5c2ljYWwgaXRlbS4KICAgICAgICAgIHZhciBpbnN0ID0gdGhpcy5zdGFtcChudWxsKTsKICAgICAgICAgIHRoaXMuX2ZvY3VzQmFja2ZpbGxJdGVtID0KICAgICAgICAgICAgICAvKiogQHR5cGUgeyFIVE1MRWxlbWVudH0gKi8gKGluc3Qucm9vdC5xdWVyeVNlbGVjdG9yKCcqJykpOwogICAgICAgICAgdGhpcy5faXRlbXNQYXJlbnQuYXBwZW5kQ2hpbGQoaW5zdC5yb290KTsKICAgICAgICB9CiAgICAgICAgLy8gU2V0IHRoZSBvZmZjcmVlbiBmb2N1c2VkIHBoeXNpY2FsIGl0ZW0uCiAgICAgICAgdGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0gPSB0aGlzLl9waHlzaWNhbEl0ZW1zW2ZwaWR4XTsKICAgICAgICB0aGlzLm1vZGVsRm9yRWxlbWVudCh0aGlzLl9vZmZzY3JlZW5Gb2N1c2VkSXRlbSkudGFiSW5kZXggPSAwOwogICAgICAgIHRoaXMuX3BoeXNpY2FsSXRlbXNbZnBpZHhdID0gdGhpcy5fZm9jdXNCYWNrZmlsbEl0ZW07CiAgICAgICAgdGhpcy5fZm9jdXNlZFBoeXNpY2FsSW5kZXggPSBmcGlkeDsKICAgICAgICAvLyBIaWRlIHRoZSBmb2N1c2VkIHBoeXNpY2FsLgogICAgICAgIHRoaXMudHJhbnNsYXRlM2QoMCwgSElEREVOX1ksIDAsIHRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtKTsKICAgICAgfSwKCiAgICAgIF9yZXN0b3JlRm9jdXNlZEl0ZW06IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICghdGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0gfHwgdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCA8IDApIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgLy8gQXNzaWduIG1vZGVscyB0byB0aGUgZm9jdXNlZCBpbmRleC4KICAgICAgICB0aGlzLl9hc3NpZ25Nb2RlbHMoKTsKICAgICAgICAvLyBHZXQgdGhlIG5ldyBwaHlzaWNhbCBpbmRleCBmb3IgdGhlIGZvY3VzZWQgaW5kZXguCiAgICAgICAgdmFyIGZwaWR4ID0gdGhpcy5fZm9jdXNlZFBoeXNpY2FsSW5kZXggPQogICAgICAgICAgICB0aGlzLl9nZXRQaHlzaWNhbEluZGV4KHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXgpOwoKICAgICAgICB2YXIgb25TY3JlZW5JdGVtID0gdGhpcy5fcGh5c2ljYWxJdGVtc1tmcGlkeF07CiAgICAgICAgaWYgKCFvblNjcmVlbkl0ZW0pIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdmFyIG9uU2NyZWVuSW5zdGFuY2UgPSB0aGlzLm1vZGVsRm9yRWxlbWVudChvblNjcmVlbkl0ZW0pOwogICAgICAgIHZhciBvZmZTY3JlZW5JbnN0YW5jZSA9IHRoaXMubW9kZWxGb3JFbGVtZW50KHRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtKTsKICAgICAgICAvLyBSZXN0b3JlcyB0aGUgcGh5c2ljYWwgaXRlbSBvbmx5IHdoZW4gaXQgaGFzIHRoZSBzYW1lIG1vZGVsCiAgICAgICAgLy8gYXMgdGhlIG9mZnNjcmVlbiBvbmUuIFVzZSBrZXkgZm9yIGNvbXBhcmlzb24gc2luY2UgdXNlcnMgY2FuIHNldAogICAgICAgIC8vIGEgbmV3IGl0ZW0gdmlhIHNldCgnaXRlbXMuaWR4JykuCiAgICAgICAgaWYgKG9uU2NyZWVuSW5zdGFuY2VbdGhpcy5hc10gPT09IG9mZlNjcmVlbkluc3RhbmNlW3RoaXMuYXNdKSB7CiAgICAgICAgICAvLyBGbGlwIHRoZSBmb2N1cyBiYWNrZmlsbC4KICAgICAgICAgIHRoaXMuX2ZvY3VzQmFja2ZpbGxJdGVtID0gb25TY3JlZW5JdGVtOwogICAgICAgICAgb25TY3JlZW5JbnN0YW5jZS50YWJJbmRleCA9IC0xOwogICAgICAgICAgLy8gUmVzdG9yZSB0aGUgZm9jdXNlZCBwaHlzaWNhbCBpdGVtLgogICAgICAgICAgdGhpcy5fcGh5c2ljYWxJdGVtc1tmcGlkeF0gPSB0aGlzLl9vZmZzY3JlZW5Gb2N1c2VkSXRlbTsKICAgICAgICAgIC8vIEhpZGUgdGhlIHBoeXNpY2FsIGl0ZW0gdGhhdCBiYWNrZmlsbHMuCiAgICAgICAgICB0aGlzLnRyYW5zbGF0ZTNkKDAsIEhJRERFTl9ZLCAwLCB0aGlzLl9mb2N1c0JhY2tmaWxsSXRlbSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX3JlbW92ZUZvY3VzZWRJdGVtKCk7CiAgICAgICAgICB0aGlzLl9mb2N1c0JhY2tmaWxsSXRlbSA9IG51bGw7CiAgICAgICAgfQogICAgICAgIHRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtID0gbnVsbDsKICAgICAgfSwKCiAgICAgIF9kaWRGb2N1czogZnVuY3Rpb24oZSkgewogICAgICAgIHZhciB0YXJnZXRNb2RlbCA9IHRoaXMubW9kZWxGb3JFbGVtZW50KGUudGFyZ2V0KTsKICAgICAgICB2YXIgZm9jdXNlZE1vZGVsID0gdGhpcy5tb2RlbEZvckVsZW1lbnQodGhpcy5fZm9jdXNlZEl0ZW0pOwogICAgICAgIHZhciBoYXNPZmZzY3JlZW5Gb2N1c2VkSXRlbSA9IHRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtICE9PSBudWxsOwogICAgICAgIHZhciBmaWR4ID0gdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleDsKICAgICAgICBpZiAoIXRhcmdldE1vZGVsKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlmIChmb2N1c2VkTW9kZWwgPT09IHRhcmdldE1vZGVsKSB7CiAgICAgICAgICAvLyBJZiB0aGUgdXNlciBmb2N1c2VkIHRoZSBzYW1lIGl0ZW0sIHRoZW4gYnJpbmcgaXQgaW50byB2aWV3IGlmIGl0J3Mgbm90CiAgICAgICAgICAvLyB2aXNpYmxlLgogICAgICAgICAgaWYgKCF0aGlzLl9pc0luZGV4VmlzaWJsZShmaWR4KSkgewogICAgICAgICAgICB0aGlzLnNjcm9sbFRvSW5kZXgoZmlkeCk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX3Jlc3RvcmVGb2N1c2VkSXRlbSgpOwogICAgICAgICAgLy8gUmVzdG9yZSB0YWJJbmRleCBmb3IgdGhlIGN1cnJlbnRseSBmb2N1c2VkIGl0ZW0uCiAgICAgICAgICBpZiAoZm9jdXNlZE1vZGVsKSB7CiAgICAgICAgICAgIGZvY3VzZWRNb2RlbC50YWJJbmRleCA9IC0xOwogICAgICAgICAgfQogICAgICAgICAgLy8gU2V0IHRoZSB0YWJJbmRleCBmb3IgdGhlIG5leHQgZm9jdXNlZCBpdGVtLgogICAgICAgICAgdGFyZ2V0TW9kZWwudGFiSW5kZXggPSAwOwogICAgICAgICAgZmlkeCA9IHRhcmdldE1vZGVsW3RoaXMuaW5kZXhBc107CiAgICAgICAgICB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4ID0gZmlkeDsKICAgICAgICAgIHRoaXMuX2ZvY3VzZWRQaHlzaWNhbEluZGV4ID0gdGhpcy5fZ2V0UGh5c2ljYWxJbmRleChmaWR4KTsKICAgICAgICAgIHRoaXMuX2ZvY3VzZWRJdGVtID0gdGhpcy5fcGh5c2ljYWxJdGVtc1t0aGlzLl9mb2N1c2VkUGh5c2ljYWxJbmRleF07CiAgICAgICAgICBpZiAoaGFzT2Zmc2NyZWVuRm9jdXNlZEl0ZW0gJiYgIXRoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtKSB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZSgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9rZXlkb3duSGFuZGxlcjogZnVuY3Rpb24oZSkgewogICAgICAgIHN3aXRjaCAoZS5rZXlDb2RlKSB7CiAgICAgICAgICBjYXNlIC8qIEFSUk9XX0RPV04gKi8gNDA6CiAgICAgICAgICAgIGlmICh0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4IDwgdGhpcy5fdmlydHVhbENvdW50IC0gMSkKICAgICAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICAgIHRoaXMuX2ZvY3VzUGh5c2ljYWxJdGVtKAogICAgICAgICAgICAgICAgdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCArICh0aGlzLmdyaWQgPyB0aGlzLl9pdGVtc1BlclJvdyA6IDEpKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlIC8qIEFSUk9XX1JJR0hUICovIDM5OgogICAgICAgICAgICBpZiAodGhpcy5ncmlkKQogICAgICAgICAgICAgIHRoaXMuX2ZvY3VzUGh5c2ljYWxJdGVtKAogICAgICAgICAgICAgICAgICB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4ICsgKHRoaXMuX2lzUlRMID8gLTEgOiAxKSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAvKiBBUlJPV19VUCAqLyAzODoKICAgICAgICAgICAgaWYgKHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXggPiAwKQogICAgICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgICAgdGhpcy5fZm9jdXNQaHlzaWNhbEl0ZW0oCiAgICAgICAgICAgICAgICB0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4IC0gKHRoaXMuZ3JpZCA/IHRoaXMuX2l0ZW1zUGVyUm93IDogMSkpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgLyogQVJST1dfTEVGVCAqLyAzNzoKICAgICAgICAgICAgaWYgKHRoaXMuZ3JpZCkKICAgICAgICAgICAgICB0aGlzLl9mb2N1c1BoeXNpY2FsSXRlbSgKICAgICAgICAgICAgICAgICAgdGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCArICh0aGlzLl9pc1JUTCA/IDEgOiAtMSkpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgLyogRU5URVIgKi8gMTM6CiAgICAgICAgICAgIHRoaXMuX2ZvY3VzUGh5c2ljYWxJdGVtKHRoaXMuX2ZvY3VzZWRWaXJ0dWFsSW5kZXgpOwogICAgICAgICAgICBpZiAodGhpcy5zZWxlY3Rpb25FbmFibGVkKQogICAgICAgICAgICAgIHRoaXMuX3NlbGVjdGlvbkhhbmRsZXIoZSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9jbGFtcDogZnVuY3Rpb24odiwgbWluLCBtYXgpIHsKICAgICAgICByZXR1cm4gTWF0aC5taW4obWF4LCBNYXRoLm1heChtaW4sIHYpKTsKICAgICAgfSwKCiAgICAgIF9kZWJvdW5jZTogZnVuY3Rpb24obmFtZSwgY2IsIGFzeW5jTW9kdWxlKSB7CiAgICAgICAgdGhpcy5fZGVib3VuY2VycyA9IHRoaXMuX2RlYm91bmNlcnMgfHwge307CiAgICAgICAgdGhpcy5fZGVib3VuY2Vyc1tuYW1lXSA9CiAgICAgICAgICAgIERlYm91bmNlci5kZWJvdW5jZSh0aGlzLl9kZWJvdW5jZXJzW25hbWVdLCBhc3luY01vZHVsZSwgY2IuYmluZCh0aGlzKSk7CiAgICAgICAgZW5xdWV1ZURlYm91bmNlcih0aGlzLl9kZWJvdW5jZXJzW25hbWVdKTsKICAgICAgfSwKCiAgICAgIF9mb3J3YXJkUHJvcGVydHk6IGZ1bmN0aW9uKGluc3QsIG5hbWUsIHZhbHVlKSB7CiAgICAgICAgaW5zdC5fc2V0UGVuZGluZ1Byb3BlcnR5KG5hbWUsIHZhbHVlKTsKICAgICAgfSwKCiAgICAgIC8qIFRlbXBsYXRpemVyIGJpbmRpbmdzIGZvciB2MiAqLwogICAgICBfZm9yd2FyZEhvc3RQcm9wVjI6IGZ1bmN0aW9uKHByb3AsIHZhbHVlKSB7CiAgICAgICAgKHRoaXMuX3BoeXNpY2FsSXRlbXMgfHwgW10pCiAgICAgICAgICAgIC5jb25jYXQoW3RoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtLCB0aGlzLl9mb2N1c0JhY2tmaWxsSXRlbV0pCiAgICAgICAgICAgIC5mb3JFYWNoKGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICAgICAgICBpZiAoaXRlbSkgewogICAgICAgICAgICAgICAgdGhpcy5tb2RlbEZvckVsZW1lbnQoaXRlbSkuZm9yd2FyZEhvc3RQcm9wKHByb3AsIHZhbHVlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sIHRoaXMpOwogICAgICB9LAoKICAgICAgX25vdGlmeUluc3RhbmNlUHJvcFYyOiBmdW5jdGlvbihpbnN0LCBwcm9wLCB2YWx1ZSkgewogICAgICAgIGlmIChtYXRjaGVzKHRoaXMuYXMsIHByb3ApKSB7CiAgICAgICAgICB2YXIgaWR4ID0gaW5zdFt0aGlzLmluZGV4QXNdOwogICAgICAgICAgaWYgKHByb3AgPT0gdGhpcy5hcykgewogICAgICAgICAgICB0aGlzLml0ZW1zW2lkeF0gPSB2YWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMubm90aWZ5UGF0aCh0cmFuc2xhdGUodGhpcy5hcywgJ2l0ZW1zLicgKyBpZHgsIHByb3ApLCB2YWx1ZSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyogVGVtcGxhdGl6ZXIgYmluZGluZ3MgZm9yIHYxICovCiAgICAgIF9nZXRTdGFtcGVkQ2hpbGRyZW46IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl9waHlzaWNhbEl0ZW1zOwogICAgICB9LAoKICAgICAgX2ZvcndhcmRJbnN0YW5jZVBhdGg6IGZ1bmN0aW9uKGluc3QsIHBhdGgsIHZhbHVlKSB7CiAgICAgICAgaWYgKHBhdGguaW5kZXhPZih0aGlzLmFzICsgJy4nKSA9PT0gMCkgewogICAgICAgICAgdGhpcy5ub3RpZnlQYXRoKAogICAgICAgICAgICAgICdpdGVtcy4nICsgaW5zdC5fX2tleV9fICsgJy4nICsgcGF0aC5zbGljZSh0aGlzLmFzLmxlbmd0aCArIDEpLAogICAgICAgICAgICAgIHZhbHVlKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfZm9yd2FyZFBhcmVudFBhdGg6IGZ1bmN0aW9uKHBhdGgsIHZhbHVlKSB7CiAgICAgICAgKHRoaXMuX3BoeXNpY2FsSXRlbXMgfHwgW10pCiAgICAgICAgICAgIC5jb25jYXQoW3RoaXMuX29mZnNjcmVlbkZvY3VzZWRJdGVtLCB0aGlzLl9mb2N1c0JhY2tmaWxsSXRlbV0pCiAgICAgICAgICAgIC5mb3JFYWNoKGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICAgICAgICBpZiAoaXRlbSkgewogICAgICAgICAgICAgICAgdGhpcy5tb2RlbEZvckVsZW1lbnQoaXRlbSkubm90aWZ5UGF0aChwYXRoLCB2YWx1ZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LCB0aGlzKTsKICAgICAgfSwKCiAgICAgIF9mb3J3YXJkUGFyZW50UHJvcDogZnVuY3Rpb24ocHJvcCwgdmFsdWUpIHsKICAgICAgICAodGhpcy5fcGh5c2ljYWxJdGVtcyB8fCBbXSkKICAgICAgICAgICAgLmNvbmNhdChbdGhpcy5fb2Zmc2NyZWVuRm9jdXNlZEl0ZW0sIHRoaXMuX2ZvY3VzQmFja2ZpbGxJdGVtXSkKICAgICAgICAgICAgLmZvckVhY2goZnVuY3Rpb24oaXRlbSkgewogICAgICAgICAgICAgIGlmIChpdGVtKSB7CiAgICAgICAgICAgICAgICB0aGlzLm1vZGVsRm9yRWxlbWVudChpdGVtKVtwcm9wXSA9IHZhbHVlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwgdGhpcyk7CiAgICAgIH0sCgogICAgICAvKiBHZXRzIHRoZSBhY3RpdmVFbGVtZW50IG9mIHRoZSBzaGFkb3cgcm9vdC9ob3N0IHRoYXQgY29udGFpbnMgdGhlIGxpc3QuICovCiAgICAgIF9nZXRBY3RpdmVFbGVtZW50OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaXRlbXNIb3N0ID0gdGhpcy5faXRlbXNQYXJlbnQubm9kZS5kb21Ib3N0OwogICAgICAgIHJldHVybiBkb20oaXRlbXNIb3N0ID8gaXRlbXNIb3N0LnJvb3QgOiBkb2N1bWVudCkuYWN0aXZlRWxlbWVudDsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY2xhc3MgSXJvblNlbGVjdGlvbiB7CiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0geyFGdW5jdGlvbn0gc2VsZWN0Q2FsbGJhY2sKICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvdmlkZX0KICAgICAgICovCiAgICAgIGNvbnN0cnVjdG9yKHNlbGVjdENhbGxiYWNrKSB7CiAgICAgICAgdGhpcy5zZWxlY3Rpb24gPSBbXTsKICAgICAgICB0aGlzLnNlbGVjdENhbGxiYWNrID0gc2VsZWN0Q2FsbGJhY2s7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXRyaWV2ZXMgdGhlIHNlbGVjdGVkIGl0ZW0ocykuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm5zIFJldHVybnMgdGhlIHNlbGVjdGVkIGl0ZW0ocykuIElmIHRoZSBtdWx0aSBwcm9wZXJ0eSBpcyB0cnVlLAogICAgICAgKiBgZ2V0YCB3aWxsIHJldHVybiBhbiBhcnJheSwgb3RoZXJ3aXNlIGl0IHdpbGwgcmV0dXJuCiAgICAgICAqIHRoZSBzZWxlY3RlZCBpdGVtIG9yIHVuZGVmaW5lZCBpZiB0aGVyZSBpcyBubyBzZWxlY3Rpb24uCiAgICAgICAqLwogICAgICBnZXQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubXVsdGkgPyB0aGlzLnNlbGVjdGlvbi5zbGljZSgpIDogdGhpcy5zZWxlY3Rpb25bMF07CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBDbGVhcnMgYWxsIHRoZSBzZWxlY3Rpb24gZXhjZXB0IHRoZSBvbmVzIGluZGljYXRlZC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtBcnJheX0gZXhjbHVkZXMgaXRlbXMgdG8gYmUgZXhjbHVkZWQuCiAgICAgICAqLwogICAgICBjbGVhcihleGNsdWRlcykgewogICAgICAgIHRoaXMuc2VsZWN0aW9uLnNsaWNlKCkuZm9yRWFjaChmdW5jdGlvbihpdGVtKSB7CiAgICAgICAgICBpZiAoIWV4Y2x1ZGVzIHx8IGV4Y2x1ZGVzLmluZGV4T2YoaXRlbSkgPCAwKSB7CiAgICAgICAgICAgIHRoaXMuc2V0SXRlbVNlbGVjdGVkKGl0ZW0sIGZhbHNlKTsKICAgICAgICAgIH0KICAgICAgICB9LCB0aGlzKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEluZGljYXRlcyBpZiBhIGdpdmVuIGl0ZW0gaXMgc2VsZWN0ZWQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Kn0gaXRlbSBUaGUgaXRlbSB3aG9zZSBzZWxlY3Rpb24gc3RhdGUgc2hvdWxkIGJlIGNoZWNrZWQuCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFJldHVybnMgdHJ1ZSBpZiBgaXRlbWAgaXMgc2VsZWN0ZWQuCiAgICAgICAqLwogICAgICBpc1NlbGVjdGVkKGl0ZW0pIHsKICAgICAgICByZXR1cm4gdGhpcy5zZWxlY3Rpb24uaW5kZXhPZihpdGVtKSA+PSAwOwogICAgICB9CgogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgc2VsZWN0aW9uIHN0YXRlIGZvciBhIGdpdmVuIGl0ZW0gdG8gZWl0aGVyIHNlbGVjdGVkIG9yIGRlc2VsZWN0ZWQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Kn0gaXRlbSBUaGUgaXRlbSB0byBzZWxlY3QuCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gaXNTZWxlY3RlZCBUcnVlIGZvciBzZWxlY3RlZCwgZmFsc2UgZm9yIGRlc2VsZWN0ZWQuCiAgICAgICAqLwogICAgICBzZXRJdGVtU2VsZWN0ZWQoaXRlbSwgaXNTZWxlY3RlZCkgewogICAgICAgIGlmIChpdGVtICE9IG51bGwpIHsKICAgICAgICAgIGlmIChpc1NlbGVjdGVkICE9PSB0aGlzLmlzU2VsZWN0ZWQoaXRlbSkpIHsKICAgICAgICAgICAgLy8gcHJvY2VlZCB0byB1cGRhdGUgc2VsZWN0aW9uIG9ubHkgaWYgcmVxdWVzdGVkIHN0YXRlIGRpZmZlcnMgZnJvbQogICAgICAgICAgICAvLyBjdXJyZW50CiAgICAgICAgICAgIGlmIChpc1NlbGVjdGVkKSB7CiAgICAgICAgICAgICAgdGhpcy5zZWxlY3Rpb24ucHVzaChpdGVtKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICB2YXIgaSA9IHRoaXMuc2VsZWN0aW9uLmluZGV4T2YoaXRlbSk7CiAgICAgICAgICAgICAgaWYgKGkgPj0gMCkgewogICAgICAgICAgICAgICAgdGhpcy5zZWxlY3Rpb24uc3BsaWNlKGksIDEpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5zZWxlY3RDYWxsYmFjaykgewogICAgICAgICAgICAgIHRoaXMuc2VsZWN0Q2FsbGJhY2soaXRlbSwgaXNTZWxlY3RlZCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBTZXRzIHRoZSBzZWxlY3Rpb24gc3RhdGUgZm9yIGEgZ2l2ZW4gaXRlbS4gSWYgdGhlIGBtdWx0aWAgcHJvcGVydHkKICAgICAgICogaXMgdHJ1ZSwgdGhlbiB0aGUgc2VsZWN0ZWQgc3RhdGUgb2YgYGl0ZW1gIHdpbGwgYmUgdG9nZ2xlZDsgb3RoZXJ3aXNlCiAgICAgICAqIHRoZSBgaXRlbWAgd2lsbCBiZSBzZWxlY3RlZC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHsqfSBpdGVtIFRoZSBpdGVtIHRvIHNlbGVjdC4KICAgICAgICovCiAgICAgIHNlbGVjdChpdGVtKSB7CiAgICAgICAgaWYgKHRoaXMubXVsdGkpIHsKICAgICAgICAgIHRoaXMudG9nZ2xlKGl0ZW0pOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5nZXQoKSAhPT0gaXRlbSkgewogICAgICAgICAgdGhpcy5zZXRJdGVtU2VsZWN0ZWQodGhpcy5nZXQoKSwgZmFsc2UpOwogICAgICAgICAgdGhpcy5zZXRJdGVtU2VsZWN0ZWQoaXRlbSwgdHJ1ZSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogVG9nZ2xlcyB0aGUgc2VsZWN0aW9uIHN0YXRlIGZvciBgaXRlbWAuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Kn0gaXRlbSBUaGUgaXRlbSB0byB0b2dnbGUuCiAgICAgICAqLwogICAgICB0b2dnbGUoaXRlbSkgewogICAgICAgIHRoaXMuc2V0SXRlbVNlbGVjdGVkKGl0ZW0sICF0aGlzLmlzU2VsZWN0ZWQoaXRlbSkpOwogICAgICB9CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lckJlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IElyb25TZWxlY3RhYmxlQmVoYXZpb3IgPSB7CgogICAgICAvKioKICAgICAgICogRmlyZWQgd2hlbiBpcm9uLXNlbGVjdG9yIGlzIGFjdGl2YXRlZCAoc2VsZWN0ZWQgb3IgZGVzZWxlY3RlZCkuCiAgICAgICAqIEl0IGlzIGZpcmVkIGJlZm9yZSB0aGUgc2VsZWN0ZWQgaXRlbXMgYXJlIGNoYW5nZWQuCiAgICAgICAqIENhbmNlbCB0aGUgZXZlbnQgdG8gYWJvcnQgc2VsZWN0aW9uLgogICAgICAgKgogICAgICAgKiBAZXZlbnQgaXJvbi1hY3RpdmF0ZQogICAgICAgKi8KCiAgICAgIC8qKgogICAgICAgKiBGaXJlZCB3aGVuIGFuIGl0ZW0gaXMgc2VsZWN0ZWQKICAgICAgICoKICAgICAgICogQGV2ZW50IGlyb24tc2VsZWN0CiAgICAgICAqLwoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gYW4gaXRlbSBpcyBkZXNlbGVjdGVkCiAgICAgICAqCiAgICAgICAqIEBldmVudCBpcm9uLWRlc2VsZWN0CiAgICAgICAqLwoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gdGhlIGxpc3Qgb2Ygc2VsZWN0YWJsZSBpdGVtcyBjaGFuZ2VzIChlLmcuLCBpdGVtcyBhcmUKICAgICAgICogYWRkZWQgb3IgcmVtb3ZlZCkuIFRoZSBkZXRhaWwgb2YgdGhlIGV2ZW50IGlzIGEgbXV0YXRpb24gcmVjb3JkIHRoYXQKICAgICAgICogZGVzY3JpYmVzIHdoYXQgY2hhbmdlZC4KICAgICAgICoKICAgICAgICogQGV2ZW50IGlyb24taXRlbXMtY2hhbmdlZAogICAgICAgKi8KCiAgICAgIHByb3BlcnRpZXM6IHsKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91IHdhbnQgdG8gdXNlIGFuIGF0dHJpYnV0ZSB2YWx1ZSBvciBwcm9wZXJ0eSBvZiBhbiBlbGVtZW50IGZvcgogICAgICAgICAqIGBzZWxlY3RlZGAgaW5zdGVhZCBvZiB0aGUgaW5kZXgsIHNldCB0aGlzIHRvIHRoZSBuYW1lIG9mIHRoZSBhdHRyaWJ1dGUKICAgICAgICAgKiBvciBwcm9wZXJ0eS4gSHlwaGVuYXRlZCB2YWx1ZXMgYXJlIGNvbnZlcnRlZCB0byBjYW1lbCBjYXNlIHdoZW4gdXNlZCB0bwogICAgICAgICAqIGxvb2sgdXAgdGhlIHByb3BlcnR5IG9mIGEgc2VsZWN0YWJsZSBlbGVtZW50LiBDYW1lbCBjYXNlZCB2YWx1ZXMgYXJlCiAgICAgICAgICogKm5vdCogY29udmVydGVkIHRvIGh5cGhlbmF0ZWQgdmFsdWVzIGZvciBhdHRyaWJ1dGUgbG9va3VwLiBJdCdzCiAgICAgICAgICogcmVjb21tZW5kZWQgdGhhdCB5b3UgcHJvdmlkZSB0aGUgaHlwaGVuYXRlZCBmb3JtIG9mIHRoZSBuYW1lIHNvIHRoYXQKICAgICAgICAgKiBzZWxlY3Rpb24gd29ya3MgaW4gYm90aCBjYXNlcy4gKFVzZSBgYXR0ci1vci1wcm9wZXJ0eS1uYW1lYCBpbnN0ZWFkIG9mCiAgICAgICAgICogYGF0dHJPclByb3BlcnR5TmFtZWAuKQogICAgICAgICAqLwogICAgICAgIGF0dHJGb3JTZWxlY3RlZDoge3R5cGU6IFN0cmluZywgdmFsdWU6IG51bGx9LAoKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIG9yIHNldHMgdGhlIHNlbGVjdGVkIGVsZW1lbnQuIFRoZSBkZWZhdWx0IGlzIHRvIHVzZSB0aGUgaW5kZXggb2YgdGhlCiAgICAgICAgICogaXRlbS4KICAgICAgICAgKiBAdHlwZSB7c3RyaW5nfG51bWJlcn0KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZDoge3R5cGU6IFN0cmluZywgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgY3VycmVudGx5IHNlbGVjdGVkIGl0ZW0uCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSB7P09iamVjdH0KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZEl0ZW06IHt0eXBlOiBPYmplY3QsIHJlYWRPbmx5OiB0cnVlLCBub3RpZnk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZXZlbnQgdGhhdCBmaXJlcyBmcm9tIGl0ZW1zIHdoZW4gdGhleSBhcmUgc2VsZWN0ZWQuIFNlbGVjdGFibGUKICAgICAgICAgKiB3aWxsIGxpc3RlbiBmb3IgdGhpcyBldmVudCBmcm9tIGl0ZW1zIGFuZCB1cGRhdGUgdGhlIHNlbGVjdGlvbiBzdGF0ZS4KICAgICAgICAgKiBTZXQgdG8gZW1wdHkgc3RyaW5nIHRvIGxpc3RlbiB0byBubyBldmVudHMuCiAgICAgICAgICovCiAgICAgICAgYWN0aXZhdGVFdmVudDoKICAgICAgICAgICAge3R5cGU6IFN0cmluZywgdmFsdWU6ICd0YXAnLCBvYnNlcnZlcjogJ19hY3RpdmF0ZUV2ZW50Q2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIGlzIGEgQ1NTIHNlbGVjdG9yIHN0cmluZy4gIElmIHRoaXMgaXMgc2V0LCBvbmx5IGl0ZW1zIHRoYXQgbWF0Y2ggdGhlCiAgICAgICAgICogQ1NTIHNlbGVjdG9yIGFyZSBzZWxlY3RhYmxlLgogICAgICAgICAqLwogICAgICAgIHNlbGVjdGFibGU6IFN0cmluZywKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGNsYXNzIHRvIHNldCBvbiBlbGVtZW50cyB3aGVuIHNlbGVjdGVkLgogICAgICAgICAqLwogICAgICAgIHNlbGVjdGVkQ2xhc3M6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnaXJvbi1zZWxlY3RlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYXR0cmlidXRlIHRvIHNldCBvbiBlbGVtZW50cyB3aGVuIHNlbGVjdGVkLgogICAgICAgICAqLwogICAgICAgIHNlbGVjdGVkQXR0cmlidXRlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogbnVsbH0sCgogICAgICAgIC8qKgogICAgICAgICAqIERlZmF1bHQgZmFsbGJhY2sgaWYgdGhlIHNlbGVjdGlvbiBiYXNlZCBvbiBzZWxlY3RlZCB3aXRoCiAgICAgICAgICogYGF0dHJGb3JTZWxlY3RlZGAgaXMgbm90IGZvdW5kLgogICAgICAgICAqLwogICAgICAgIGZhbGxiYWNrU2VsZWN0aW9uOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogbnVsbH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBsaXN0IG9mIGl0ZW1zIGZyb20gd2hpY2ggYSBzZWxlY3Rpb24gY2FuIGJlIG1hZGUuCiAgICAgICAgICovCiAgICAgICAgaXRlbXM6IHsKICAgICAgICAgIHR5cGU6IEFycmF5LAogICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgc2V0IG9mIGV4Y2x1ZGVkIGVsZW1lbnRzIHdoZXJlIHRoZSBrZXkgaXMgdGhlIGBsb2NhbE5hbWVgCiAgICAgICAgICogb2YgdGhlIGVsZW1lbnQgdGhhdCB3aWxsIGJlIGlnbm9yZWQgZnJvbSB0aGUgaXRlbSBsaXN0LgogICAgICAgICAqCiAgICAgICAgICogQGRlZmF1bHQge3RlbXBsYXRlOiAxfQogICAgICAgICAqLwogICAgICAgIF9leGNsdWRlZExvY2FsTmFtZXM6IHsKICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgIHZhbHVlOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAndGVtcGxhdGUnOiAxLAogICAgICAgICAgICAgICdkb20tYmluZCc6IDEsCiAgICAgICAgICAgICAgJ2RvbS1pZic6IDEsCiAgICAgICAgICAgICAgJ2RvbS1yZXBlYXQnOiAxLAogICAgICAgICAgICB9OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWwogICAgICAgICdfdXBkYXRlQXR0ckZvclNlbGVjdGVkKGF0dHJGb3JTZWxlY3RlZCknLAogICAgICAgICdfdXBkYXRlU2VsZWN0ZWQoc2VsZWN0ZWQpJywKICAgICAgICAnX2NoZWNrRmFsbGJhY2soZmFsbGJhY2tTZWxlY3Rpb24pJwogICAgICBdLAoKICAgICAgY3JlYXRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fYmluZEZpbHRlckl0ZW0gPSB0aGlzLl9maWx0ZXJJdGVtLmJpbmQodGhpcyk7CiAgICAgICAgdGhpcy5fc2VsZWN0aW9uID0gbmV3IElyb25TZWxlY3Rpb24odGhpcy5fYXBwbHlTZWxlY3Rpb24uYmluZCh0aGlzKSk7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fb2JzZXJ2ZXIgPSB0aGlzLl9vYnNlcnZlSXRlbXModGhpcyk7CiAgICAgICAgdGhpcy5fYWRkTGlzdGVuZXIodGhpcy5hY3RpdmF0ZUV2ZW50KTsKICAgICAgfSwKCiAgICAgIGRldGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fb2JzZXJ2ZXIpIHsKICAgICAgICAgIGRvbSh0aGlzKS51bm9ic2VydmVOb2Rlcyh0aGlzLl9vYnNlcnZlcik7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3JlbW92ZUxpc3RlbmVyKHRoaXMuYWN0aXZhdGVFdmVudCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIGdpdmVuIGl0ZW0uCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgaW5kZXhPZgogICAgICAgKiBAcGFyYW0ge09iamVjdH0gaXRlbQogICAgICAgKiBAcmV0dXJucyBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgaXRlbQogICAgICAgKi8KICAgICAgaW5kZXhPZjogZnVuY3Rpb24oaXRlbSkgewogICAgICAgIHJldHVybiB0aGlzLml0ZW1zID8gdGhpcy5pdGVtcy5pbmRleE9mKGl0ZW0pIDogLTE7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2VsZWN0cyB0aGUgZ2l2ZW4gdmFsdWUuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2Qgc2VsZWN0CiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfG51bWJlcn0gdmFsdWUgdGhlIHZhbHVlIHRvIHNlbGVjdC4KICAgICAgICovCiAgICAgIHNlbGVjdDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICB0aGlzLnNlbGVjdGVkID0gdmFsdWU7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2VsZWN0cyB0aGUgcHJldmlvdXMgaXRlbS4KICAgICAgICoKICAgICAgICogQG1ldGhvZCBzZWxlY3RQcmV2aW91cwogICAgICAgKi8KICAgICAgc2VsZWN0UHJldmlvdXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBsZW5ndGggPSB0aGlzLml0ZW1zLmxlbmd0aDsKICAgICAgICB2YXIgaW5kZXggPSBsZW5ndGggLSAxOwogICAgICAgIGlmICh0aGlzLnNlbGVjdGVkICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgIGluZGV4ID0gKE51bWJlcih0aGlzLl92YWx1ZVRvSW5kZXgodGhpcy5zZWxlY3RlZCkpIC0gMSArIGxlbmd0aCkgJSBsZW5ndGg7CiAgICAgICAgfQogICAgICAgIHRoaXMuc2VsZWN0ZWQgPSB0aGlzLl9pbmRleFRvVmFsdWUoaW5kZXgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNlbGVjdHMgdGhlIG5leHQgaXRlbS4KICAgICAgICoKICAgICAgICogQG1ldGhvZCBzZWxlY3ROZXh0CiAgICAgICAqLwogICAgICBzZWxlY3ROZXh0OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaW5kZXggPSAwOwogICAgICAgIGlmICh0aGlzLnNlbGVjdGVkICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgIGluZGV4ID0KICAgICAgICAgICAgICAoTnVtYmVyKHRoaXMuX3ZhbHVlVG9JbmRleCh0aGlzLnNlbGVjdGVkKSkgKyAxKSAlIHRoaXMuaXRlbXMubGVuZ3RoOwogICAgICAgIH0KICAgICAgICB0aGlzLnNlbGVjdGVkID0gdGhpcy5faW5kZXhUb1ZhbHVlKGluZGV4KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3RzIHRoZSBpdGVtIGF0IHRoZSBnaXZlbiBpbmRleC4KICAgICAgICoKICAgICAgICogQG1ldGhvZCBzZWxlY3RJbmRleAogICAgICAgKi8KICAgICAgc2VsZWN0SW5kZXg6IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgdGhpcy5zZWxlY3QodGhpcy5faW5kZXhUb1ZhbHVlKGluZGV4KSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRm9yY2UgYSBzeW5jaHJvbm91cyB1cGRhdGUgb2YgdGhlIGBpdGVtc2AgcHJvcGVydHkuCiAgICAgICAqCiAgICAgICAqIE5PVEU6IENvbnNpZGVyIGxpc3RlbmluZyBmb3IgdGhlIGBpcm9uLWl0ZW1zLWNoYW5nZWRgIGV2ZW50IHRvIHJlc3BvbmQgdG8KICAgICAgICogdXBkYXRlcyB0byB0aGUgc2V0IG9mIHNlbGVjdGFibGUgaXRlbXMgYWZ0ZXIgdXBkYXRlcyB0byB0aGUgRE9NIGxpc3QgYW5kCiAgICAgICAqIHNlbGVjdGlvbiBzdGF0ZSBoYXZlIGJlZW4gbWFkZS4KICAgICAgICoKICAgICAgICogV0FSTklORzogSWYgeW91IGFyZSB1c2luZyB0aGlzIG1ldGhvZCwgeW91IHNob3VsZCBwcm9iYWJseSBjb25zaWRlciBhbgogICAgICAgKiBhbHRlcm5hdGUgYXBwcm9hY2guIFN5bmNocm9ub3VzbHkgcXVlcnlpbmcgZm9yIGl0ZW1zIGlzIHBvdGVudGlhbGx5CiAgICAgICAqIHNsb3cgZm9yIG1hbnkgdXNlIGNhc2VzLiBUaGUgYGl0ZW1zYCBwcm9wZXJ0eSB3aWxsIHVwZGF0ZSBhc3luY2hyb25vdXNseQogICAgICAgKiBvbiBpdHMgb3duIHRvIHJlZmxlY3Qgc2VsZWN0YWJsZSBpdGVtcyBpbiB0aGUgRE9NLgogICAgICAgKi8KICAgICAgZm9yY2VTeW5jaHJvbm91c0l0ZW1VcGRhdGU6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9vYnNlcnZlciAmJiB0eXBlb2YgdGhpcy5fb2JzZXJ2ZXIuZmx1c2ggPT09ICdmdW5jdGlvbicpIHsKICAgICAgICAgIC8vIE5PVEUoYmlja25lbGxyKTogYGRvbS5mbHVzaGAgYWJvdmUgaXMgbm8gbG9uZ2VyIHN1ZmZpY2llbnQgdG8gdHJpZ2dlcgogICAgICAgICAgLy8gYG9ic2VydmVOb2Rlc2AgY2FsbGJhY2tzLiBQb2x5bWVyIDIueCByZXR1cm5zIGFuIG9iamVjdCBmcm9tCiAgICAgICAgICAvLyBgb2JzZXJ2ZU5vZGVzYCB3aXRoIGEgYGZsdXNoYCB0aGF0IHN5bmNocm9ub3VzbHkgZ2l2ZXMgdGhlIGNhbGxiYWNrIGFueQogICAgICAgICAgLy8gcGVuZGluZyBNdXRhdGlvblJlY29yZHMgKHJldHJpZXZlZCB3aXRoIGB0YWtlUmVjb3Jkc2ApLiBBbnkgY2FzZSB3aGVyZQogICAgICAgICAgLy8gU2hhZHlET00gZmx1c2hlcyB3ZXJlIGV4cGVjdGVkIHRvIHN5bmNocm9ub3VzbHkgdHJpZ2dlciBpdGVtIHVwZGF0ZXMKICAgICAgICAgIC8vIHdpbGwgbm93IHJlcXVpcmUgY2FsbGluZyBgZm9yY2VTeW5jaHJvbm91c0l0ZW1VcGRhdGVgLgogICAgICAgICAgdGhpcy5fb2JzZXJ2ZXIuZmx1c2goKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fdXBkYXRlSXRlbXMoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvLyBVTlVTRUQsIEZPUiBBUEkgQ09NUEFUSUJJTElUWQogICAgICBnZXQgX3Nob3VsZFVwZGF0ZVNlbGVjdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5zZWxlY3RlZCAhPSBudWxsOwogICAgICB9LAoKICAgICAgX2NoZWNrRmFsbGJhY2s6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3VwZGF0ZVNlbGVjdGVkKCk7CiAgICAgIH0sCgogICAgICBfYWRkTGlzdGVuZXI6IGZ1bmN0aW9uKGV2ZW50TmFtZSkgewogICAgICAgIHRoaXMubGlzdGVuKHRoaXMsIGV2ZW50TmFtZSwgJ19hY3RpdmF0ZUhhbmRsZXInKTsKICAgICAgfSwKCiAgICAgIF9yZW1vdmVMaXN0ZW5lcjogZnVuY3Rpb24oZXZlbnROYW1lKSB7CiAgICAgICAgdGhpcy51bmxpc3Rlbih0aGlzLCBldmVudE5hbWUsICdfYWN0aXZhdGVIYW5kbGVyJyk7CiAgICAgIH0sCgogICAgICBfYWN0aXZhdGVFdmVudENoYW5nZWQ6IGZ1bmN0aW9uKGV2ZW50TmFtZSwgb2xkKSB7CiAgICAgICAgdGhpcy5fcmVtb3ZlTGlzdGVuZXIob2xkKTsKICAgICAgICB0aGlzLl9hZGRMaXN0ZW5lcihldmVudE5hbWUpOwogICAgICB9LAoKICAgICAgX3VwZGF0ZUl0ZW1zOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgbm9kZXMgPSBkb20odGhpcykucXVlcnlEaXN0cmlidXRlZEVsZW1lbnRzKHRoaXMuc2VsZWN0YWJsZSB8fCAnKicpOwogICAgICAgIG5vZGVzID0gQXJyYXkucHJvdG90eXBlLmZpbHRlci5jYWxsKG5vZGVzLCB0aGlzLl9iaW5kRmlsdGVySXRlbSk7CiAgICAgICAgdGhpcy5fc2V0SXRlbXMobm9kZXMpOwogICAgICB9LAoKICAgICAgX3VwZGF0ZUF0dHJGb3JTZWxlY3RlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuc2VsZWN0ZWRJdGVtKSB7CiAgICAgICAgICB0aGlzLnNlbGVjdGVkID0gdGhpcy5fdmFsdWVGb3JJdGVtKHRoaXMuc2VsZWN0ZWRJdGVtKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfdXBkYXRlU2VsZWN0ZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3NlbGVjdFNlbGVjdGVkKHRoaXMuc2VsZWN0ZWQpOwogICAgICB9LAoKICAgICAgX3NlbGVjdFNlbGVjdGVkOiBmdW5jdGlvbihzZWxlY3RlZCkgewogICAgICAgIGlmICghdGhpcy5pdGVtcykgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdmFyIGl0ZW0gPSB0aGlzLl92YWx1ZVRvSXRlbSh0aGlzLnNlbGVjdGVkKTsKICAgICAgICBpZiAoaXRlbSkgewogICAgICAgICAgdGhpcy5fc2VsZWN0aW9uLnNlbGVjdChpdGVtKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fc2VsZWN0aW9uLmNsZWFyKCk7CiAgICAgICAgfQogICAgICAgIC8vIENoZWNrIGZvciBpdGVtcywgc2luY2UgdGhpcyBhcnJheSBpcyBwb3B1bGF0ZWQgb25seSB3aGVuIGF0dGFjaGVkCiAgICAgICAgLy8gU2luY2UgTnVtYmVyKDApIGlzIGZhbHN5LCBleHBsaWNpdGx5IGNoZWNrIGZvciB1bmRlZmluZWQKICAgICAgICBpZiAodGhpcy5mYWxsYmFja1NlbGVjdGlvbiAmJiB0aGlzLml0ZW1zLmxlbmd0aCAmJgogICAgICAgICAgICAodGhpcy5fc2VsZWN0aW9uLmdldCgpID09PSB1bmRlZmluZWQpKSB7CiAgICAgICAgICB0aGlzLnNlbGVjdGVkID0gdGhpcy5mYWxsYmFja1NlbGVjdGlvbjsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfZmlsdGVySXRlbTogZnVuY3Rpb24obm9kZSkgewogICAgICAgIHJldHVybiAhdGhpcy5fZXhjbHVkZWRMb2NhbE5hbWVzW25vZGUubG9jYWxOYW1lXTsKICAgICAgfSwKCiAgICAgIF92YWx1ZVRvSXRlbTogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICByZXR1cm4gKHZhbHVlID09IG51bGwpID8gbnVsbCA6IHRoaXMuaXRlbXNbdGhpcy5fdmFsdWVUb0luZGV4KHZhbHVlKV07CiAgICAgIH0sCgogICAgICBfdmFsdWVUb0luZGV4OiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgIGlmICh0aGlzLmF0dHJGb3JTZWxlY3RlZCkgewogICAgICAgICAgZm9yICh2YXIgaSA9IDAsIGl0ZW07IGl0ZW0gPSB0aGlzLml0ZW1zW2ldOyBpKyspIHsKICAgICAgICAgICAgaWYgKHRoaXMuX3ZhbHVlRm9ySXRlbShpdGVtKSA9PSB2YWx1ZSkgewogICAgICAgICAgICAgIHJldHVybiBpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJldHVybiBOdW1iZXIodmFsdWUpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9pbmRleFRvVmFsdWU6IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgICAgaWYgKHRoaXMuYXR0ckZvclNlbGVjdGVkKSB7CiAgICAgICAgICB2YXIgaXRlbSA9IHRoaXMuaXRlbXNbaW5kZXhdOwogICAgICAgICAgaWYgKGl0ZW0pIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3ZhbHVlRm9ySXRlbShpdGVtKTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIGluZGV4OwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF92YWx1ZUZvckl0ZW06IGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICBpZiAoIWl0ZW0pIHsKICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICBpZiAoIXRoaXMuYXR0ckZvclNlbGVjdGVkKSB7CiAgICAgICAgICB2YXIgaSA9IHRoaXMuaW5kZXhPZihpdGVtKTsKICAgICAgICAgIHJldHVybiBpID09PSAtMSA/IG51bGwgOiBpOwogICAgICAgIH0KICAgICAgICB2YXIgcHJvcFZhbHVlID0gaXRlbVtkYXNoVG9DYW1lbENhc2UodGhpcy5hdHRyRm9yU2VsZWN0ZWQpXTsKICAgICAgICByZXR1cm4gcHJvcFZhbHVlICE9IHVuZGVmaW5lZCA/IHByb3BWYWx1ZSA6CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpdGVtLmdldEF0dHJpYnV0ZSh0aGlzLmF0dHJGb3JTZWxlY3RlZCk7CiAgICAgIH0sCgogICAgICBfYXBwbHlTZWxlY3Rpb246IGZ1bmN0aW9uKGl0ZW0sIGlzU2VsZWN0ZWQpIHsKICAgICAgICBpZiAodGhpcy5zZWxlY3RlZENsYXNzKSB7CiAgICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKHRoaXMuc2VsZWN0ZWRDbGFzcywgaXNTZWxlY3RlZCwgaXRlbSk7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLnNlbGVjdGVkQXR0cmlidXRlKSB7CiAgICAgICAgICB0aGlzLnRvZ2dsZUF0dHJpYnV0ZSh0aGlzLnNlbGVjdGVkQXR0cmlidXRlLCBpc1NlbGVjdGVkLCBpdGVtKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fc2VsZWN0aW9uQ2hhbmdlKCk7CiAgICAgICAgdGhpcy5maXJlKCdpcm9uLScgKyAoaXNTZWxlY3RlZCA/ICdzZWxlY3QnIDogJ2Rlc2VsZWN0JyksIHtpdGVtOiBpdGVtfSk7CiAgICAgIH0sCgogICAgICBfc2VsZWN0aW9uQ2hhbmdlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW0odGhpcy5fc2VsZWN0aW9uLmdldCgpKTsKICAgICAgfSwKCiAgICAgIC8vIG9ic2VydmUgaXRlbXMgY2hhbmdlIHVuZGVyIHRoZSBnaXZlbiBub2RlLgogICAgICBfb2JzZXJ2ZUl0ZW1zOiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgcmV0dXJuIGRvbShub2RlKS5vYnNlcnZlTm9kZXMoZnVuY3Rpb24obXV0YXRpb24pIHsKICAgICAgICAgIHRoaXMuX3VwZGF0ZUl0ZW1zKCk7CiAgICAgICAgICB0aGlzLl91cGRhdGVTZWxlY3RlZCgpOwoKICAgICAgICAgIC8vIExldCBvdGhlciBpbnRlcmVzdGVkIHBhcnRpZXMga25vdyBhYm91dCB0aGUgY2hhbmdlIHNvIHRoYXQKICAgICAgICAgIC8vIHdlIGRvbid0IGhhdmUgdG8gcmVjcmVhdGUgbXV0YXRpb24gb2JzZXJ2ZXJzIGV2ZXJ5d2hlcmUuCiAgICAgICAgICB0aGlzLmZpcmUoCiAgICAgICAgICAgICAgJ2lyb24taXRlbXMtY2hhbmdlZCcsIG11dGF0aW9uLCB7YnViYmxlczogZmFsc2UsIGNhbmNlbGFibGU6IGZhbHNlfSk7CiAgICAgICAgfSk7CiAgICAgIH0sCgogICAgICBfYWN0aXZhdGVIYW5kbGVyOiBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIHQgPSBlLnRhcmdldDsKICAgICAgICB2YXIgaXRlbXMgPSB0aGlzLml0ZW1zOwogICAgICAgIHdoaWxlICh0ICYmIHQgIT0gdGhpcykgewogICAgICAgICAgdmFyIGkgPSBpdGVtcy5pbmRleE9mKHQpOwogICAgICAgICAgaWYgKGkgPj0gMCkgewogICAgICAgICAgICB2YXIgdmFsdWUgPSB0aGlzLl9pbmRleFRvVmFsdWUoaSk7CiAgICAgICAgICAgIHRoaXMuX2l0ZW1BY3RpdmF0ZSh2YWx1ZSwgdCk7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIHQgPSB0LnBhcmVudE5vZGU7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2l0ZW1BY3RpdmF0ZTogZnVuY3Rpb24odmFsdWUsIGl0ZW0pIHsKICAgICAgICBpZiAoIXRoaXMuZmlyZSgnaXJvbi1hY3RpdmF0ZScsIHtzZWxlY3RlZDogdmFsdWUsIGl0ZW06IGl0ZW19LCB7CiAgICAgICAgICAgICAgICAgICBjYW5jZWxhYmxlOiB0cnVlCiAgICAgICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgICAuZGVmYXVsdFByZXZlbnRlZCkgewogICAgICAgICAgdGhpcy5zZWxlY3QodmFsdWUpOwogICAgICAgIH0KICAgICAgfQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBgaXJvbi1wYWdlc2AgaXMgdXNlZCB0byBzZWxlY3Qgb25lIG9mIGl0cyBjaGlsZHJlbiB0byBzaG93LiBPbmUgdXNlIGlzIHRvIGN5Y2xlCiAgICB0aHJvdWdoIGEgbGlzdCBvZiBjaGlsZHJlbiAicGFnZXMiLgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxpcm9uLXBhZ2VzIHNlbGVjdGVkPSIwIj4KICAgICAgICAgIDxkaXY+T25lPC9kaXY+CiAgICAgICAgICA8ZGl2PlR3bzwvZGl2PgogICAgICAgICAgPGRpdj5UaHJlZTwvZGl2PgogICAgICAgIDwvaXJvbi1wYWdlcz4KCiAgICAgICAgPHNjcmlwdD4KICAgICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZnVuY3Rpb24oZSkgewogICAgICAgICAgICB2YXIgcGFnZXMgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCdpcm9uLXBhZ2VzJyk7CiAgICAgICAgICAgIHBhZ2VzLnNlbGVjdE5leHQoKTsKICAgICAgICAgIH0pOwogICAgICAgIDwvSkFWQV9TQ1JJSUlJUFQvPgoKICAgIEBncm91cCBJcm9uIEVsZW1lbnRzCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKDpub3Qoc2xvdCk6bm90KC5pcm9uLXNlbGVjdGVkKSkgewogICAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8c2xvdD48L3Nsb3Q+CmAsCgogICAgICBpczogJ2lyb24tcGFnZXMnLAogICAgICBiZWhhdmlvcnM6IFtJcm9uUmVzaXphYmxlQmVoYXZpb3IsIElyb25TZWxlY3RhYmxlQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvLyBhcyB0aGUgc2VsZWN0ZWQgcGFnZSBpcyB0aGUgb25seSBvbmUgdmlzaWJsZSwgYWN0aXZhdGVFdmVudAogICAgICAgIC8vIGlzIGJvdGggbm9uLXNlbnNpY2FsIGFuZCBwcm9ibGVtYXRpYzsgZS5nLiBpbiBjYXNlcyB3aGVyZSBhIHVzZXIKICAgICAgICAvLyBoYW5kbGVyIGF0dGVtcHRzIHRvIGNoYW5nZSB0aGUgcGFnZSBhbmQgdGhlIGFjdGl2YXRlRXZlbnQKICAgICAgICAvLyBoYW5kbGVyIGltbWVkaWF0ZWx5IGNoYW5nZXMgaXQgYmFjawogICAgICAgIGFjdGl2YXRlRXZlbnQ6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiBudWxsfQoKICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWydfc2VsZWN0ZWRQYWdlQ2hhbmdlZChzZWxlY3RlZCknXSwKCiAgICAgIF9zZWxlY3RlZFBhZ2VDaGFuZ2VkOiBmdW5jdGlvbihzZWxlY3RlZCwgb2xkKSB7CiAgICAgICAgdGhpcy5hc3luYyh0aGlzLm5vdGlmeVJlc2l6ZSk7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgY29uc3QgdGVtcGxhdGUkNCA9IGh0bWxgCjxjdXN0b20tc3R5bGU+CiAgPHN0eWxlIGlzPSJjdXN0b20tc3R5bGUiPgogICAgaHRtbCB7CgogICAgICAtLXNoYWRvdy10cmFuc2l0aW9uOiB7CiAgICAgICAgdHJhbnNpdGlvbjogYm94LXNoYWRvdyAwLjI4cyBjdWJpYy1iZXppZXIoMC40LCAwLCAwLjIsIDEpOwogICAgICB9OwoKICAgICAgLS1zaGFkb3ctbm9uZTogewogICAgICAgIGJveC1zaGFkb3c6IG5vbmU7CiAgICAgIH07CgogICAgICAvKiBmcm9tIGh0dHA6Ly9jb2RlcGVuLmlvL3NoeW5kbWFuL3Blbi9jNTM5NGRkZjJlOGIyYTVjOTE4NTkwNGI1NzQyMWNkYiAqLwoKICAgICAgLS1zaGFkb3ctZWxldmF0aW9uLTJkcDogewogICAgICAgIGJveC1zaGFkb3c6IDAgMnB4IDJweCAwIHJnYmEoMCwgMCwgMCwgMC4xNCksCiAgICAgICAgICAgICAgICAgICAgMCAxcHggNXB4IDAgcmdiYSgwLCAwLCAwLCAwLjEyKSwKICAgICAgICAgICAgICAgICAgICAwIDNweCAxcHggLTJweCByZ2JhKDAsIDAsIDAsIDAuMik7CiAgICAgIH07CgogICAgICAtLXNoYWRvdy1lbGV2YXRpb24tM2RwOiB7CiAgICAgICAgYm94LXNoYWRvdzogMCAzcHggNHB4IDAgcmdiYSgwLCAwLCAwLCAwLjE0KSwKICAgICAgICAgICAgICAgICAgICAwIDFweCA4cHggMCByZ2JhKDAsIDAsIDAsIDAuMTIpLAogICAgICAgICAgICAgICAgICAgIDAgM3B4IDNweCAtMnB4IHJnYmEoMCwgMCwgMCwgMC40KTsKICAgICAgfTsKCiAgICAgIC0tc2hhZG93LWVsZXZhdGlvbi00ZHA6IHsKICAgICAgICBib3gtc2hhZG93OiAwIDRweCA1cHggMCByZ2JhKDAsIDAsIDAsIDAuMTQpLAogICAgICAgICAgICAgICAgICAgIDAgMXB4IDEwcHggMCByZ2JhKDAsIDAsIDAsIDAuMTIpLAogICAgICAgICAgICAgICAgICAgIDAgMnB4IDRweCAtMXB4IHJnYmEoMCwgMCwgMCwgMC40KTsKICAgICAgfTsKCiAgICAgIC0tc2hhZG93LWVsZXZhdGlvbi02ZHA6IHsKICAgICAgICBib3gtc2hhZG93OiAwIDZweCAxMHB4IDAgcmdiYSgwLCAwLCAwLCAwLjE0KSwKICAgICAgICAgICAgICAgICAgICAwIDFweCAxOHB4IDAgcmdiYSgwLCAwLCAwLCAwLjEyKSwKICAgICAgICAgICAgICAgICAgICAwIDNweCA1cHggLTFweCByZ2JhKDAsIDAsIDAsIDAuNCk7CiAgICAgIH07CgogICAgICAtLXNoYWRvdy1lbGV2YXRpb24tOGRwOiB7CiAgICAgICAgYm94LXNoYWRvdzogMCA4cHggMTBweCAxcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwKICAgICAgICAgICAgICAgICAgICAwIDNweCAxNHB4IDJweCByZ2JhKDAsIDAsIDAsIDAuMTIpLAogICAgICAgICAgICAgICAgICAgIDAgNXB4IDVweCAtM3B4IHJnYmEoMCwgMCwgMCwgMC40KTsKICAgICAgfTsKCiAgICAgIC0tc2hhZG93LWVsZXZhdGlvbi0xMmRwOiB7CiAgICAgICAgYm94LXNoYWRvdzogMCAxMnB4IDE2cHggMXB4IHJnYmEoMCwgMCwgMCwgMC4xNCksCiAgICAgICAgICAgICAgICAgICAgMCA0cHggMjJweCAzcHggcmdiYSgwLCAwLCAwLCAwLjEyKSwKICAgICAgICAgICAgICAgICAgICAwIDZweCA3cHggLTRweCByZ2JhKDAsIDAsIDAsIDAuNCk7CiAgICAgIH07CgogICAgICAtLXNoYWRvdy1lbGV2YXRpb24tMTZkcDogewogICAgICAgIGJveC1zaGFkb3c6IDAgMTZweCAyNHB4IDJweCByZ2JhKDAsIDAsIDAsIDAuMTQpLAogICAgICAgICAgICAgICAgICAgIDAgIDZweCAzMHB4IDVweCByZ2JhKDAsIDAsIDAsIDAuMTIpLAogICAgICAgICAgICAgICAgICAgIDAgIDhweCAxMHB4IC01cHggcmdiYSgwLCAwLCAwLCAwLjQpOwogICAgICB9OwoKICAgICAgLS1zaGFkb3ctZWxldmF0aW9uLTI0ZHA6IHsKICAgICAgICBib3gtc2hhZG93OiAwIDI0cHggMzhweCAzcHggcmdiYSgwLCAwLCAwLCAwLjE0KSwKICAgICAgICAgICAgICAgICAgICAwIDlweCA0NnB4IDhweCByZ2JhKDAsIDAsIDAsIDAuMTIpLAogICAgICAgICAgICAgICAgICAgIDAgMTFweCAxNXB4IC03cHggcmdiYSgwLCAwLCAwLCAwLjQpOwogICAgICB9OwogICAgfQogIDwvc3R5bGU+CjwvY3VzdG9tLXN0eWxlPmA7CiAgICB0ZW1wbGF0ZSQ0LnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkNC5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIGNvbnN0IHRlbXBsYXRlJDUgPSBodG1sYAo8ZG9tLW1vZHVsZSBpZD0icGFwZXItbWF0ZXJpYWwtc3R5bGVzIj4KICA8dGVtcGxhdGU+CiAgICA8c3R5bGU+CiAgICAgIGh0bWwgewogICAgICAgIC0tcGFwZXItbWF0ZXJpYWw6IHsKICAgICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIH07CiAgICAgICAgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tMTogewogICAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi0yZHA7CiAgICAgICAgfTsKICAgICAgICAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi0yOiB7CiAgICAgICAgICBAYXBwbHkgLS1zaGFkb3ctZWxldmF0aW9uLTRkcDsKICAgICAgICB9OwogICAgICAgIC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTM6IHsKICAgICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tNmRwOwogICAgICAgIH07CiAgICAgICAgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tNDogewogICAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi04ZHA7CiAgICAgICAgfTsKICAgICAgICAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi01OiB7CiAgICAgICAgICBAYXBwbHkgLS1zaGFkb3ctZWxldmF0aW9uLTE2ZHA7CiAgICAgICAgfTsKICAgICAgfQogICAgICAucGFwZXItbWF0ZXJpYWwgewogICAgICAgIEBhcHBseSAtLXBhcGVyLW1hdGVyaWFsOwogICAgICB9CiAgICAgIC5wYXBlci1tYXRlcmlhbFtlbGV2YXRpb249IjEiXSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTE7CiAgICAgIH0KICAgICAgLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iMiJdIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tMjsKICAgICAgfQogICAgICAucGFwZXItbWF0ZXJpYWxbZWxldmF0aW9uPSIzIl0gewogICAgICAgIEBhcHBseSAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi0zOwogICAgICB9CiAgICAgIC5wYXBlci1tYXRlcmlhbFtlbGV2YXRpb249IjQiXSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTQ7CiAgICAgIH0KICAgICAgLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iNSJdIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tNTsKICAgICAgfQoKICAgICAgLyogRHVwbGljYXRlIHRoZSBzdHlsZXMgYmVjYXVzZSBvZiBodHRwczovL2dpdGh1Yi5jb20vd2ViY29tcG9uZW50cy9zaGFkeWNzcy9pc3N1ZXMvMTkzICovCiAgICAgIDpob3N0IHsKICAgICAgICAtLXBhcGVyLW1hdGVyaWFsOiB7CiAgICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICB9OwogICAgICAgIC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTE6IHsKICAgICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tMmRwOwogICAgICAgIH07CiAgICAgICAgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tMjogewogICAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi00ZHA7CiAgICAgICAgfTsKICAgICAgICAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi0zOiB7CiAgICAgICAgICBAYXBwbHkgLS1zaGFkb3ctZWxldmF0aW9uLTZkcDsKICAgICAgICB9OwogICAgICAgIC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTQ6IHsKICAgICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tOGRwOwogICAgICAgIH07CiAgICAgICAgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tNTogewogICAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi0xNmRwOwogICAgICAgIH07CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWw7CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iMSJdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTE7CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iMiJdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTI7CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iMyJdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTM7CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iNCJdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTQ7CiAgICAgIH0KICAgICAgOmhvc3QoLnBhcGVyLW1hdGVyaWFsW2VsZXZhdGlvbj0iNSJdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CiAgICB0ZW1wbGF0ZSQ1LnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkNS5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgICogQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uQ29udHJvbFN0YXRlID0gewoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgZWxlbWVudCBjdXJyZW50bHkgaGFzIGZvY3VzLgogICAgICAgICAqLwogICAgICAgIGZvY3VzZWQ6IHsKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICByZWFkT25seTogdHJ1ZSwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZQogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHRoZSB1c2VyIGNhbm5vdCBpbnRlcmFjdCB3aXRoIHRoaXMgZWxlbWVudC4KICAgICAgICAgKi8KICAgICAgICBkaXNhYmxlZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgIG9ic2VydmVyOiAnX2Rpc2FibGVkQ2hhbmdlZCcsCiAgICAgICAgICByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWUKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBWYWx1ZSBvZiB0aGUgYHRhYmluZGV4YCBhdHRyaWJ1dGUgYmVmb3JlIGBkaXNhYmxlZGAgd2FzIGFjdGl2YXRlZC4KICAgICAgICAgKiBgbnVsbGAgbWVhbnMgdGhlIGF0dHJpYnV0ZSB3YXMgbm90IHByZXNlbnQuCiAgICAgICAgICogQHR5cGUgez9zdHJpbmd8dW5kZWZpbmVkfQogICAgICAgICAqLwogICAgICAgIF9vbGRUYWJJbmRleDoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIF9ib3VuZEZvY3VzQmx1ckhhbmRsZXI6IHsKICAgICAgICAgIHR5cGU6IEZ1bmN0aW9uLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZm9jdXNCbHVySGFuZGxlci5iaW5kKHRoaXMpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWydfY2hhbmdlZENvbnRyb2xTdGF0ZShmb2N1c2VkLCBkaXNhYmxlZCknXSwKCiAgICAgIC8qKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgcmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignZm9jdXMnLCB0aGlzLl9ib3VuZEZvY3VzQmx1ckhhbmRsZXIsIHRydWUpOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignYmx1cicsIHRoaXMuX2JvdW5kRm9jdXNCbHVySGFuZGxlciwgdHJ1ZSk7CiAgICAgIH0sCgogICAgICBfZm9jdXNCbHVySGFuZGxlcjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICAvLyBQb2x5bWVyIHRha2VzIGNhcmUgb2YgcmV0YXJnZXRpbmcgZXZlbnRzLgogICAgICAgIHRoaXMuX3NldEZvY3VzZWQoZXZlbnQudHlwZSA9PT0gJ2ZvY3VzJyk7CiAgICAgICAgcmV0dXJuOwogICAgICB9LAoKICAgICAgX2Rpc2FibGVkQ2hhbmdlZDogZnVuY3Rpb24oZGlzYWJsZWQsIG9sZCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdhcmlhLWRpc2FibGVkJywgZGlzYWJsZWQgPyAndHJ1ZScgOiAnZmFsc2UnKTsKICAgICAgICB0aGlzLnN0eWxlLnBvaW50ZXJFdmVudHMgPSBkaXNhYmxlZCA/ICdub25lJyA6ICcnOwogICAgICAgIGlmIChkaXNhYmxlZCkgewogICAgICAgICAgLy8gUmVhZCB0aGUgYHRhYmluZGV4YCBhdHRyaWJ1dGUgaW5zdGVhZCBvZiB0aGUgYHRhYkluZGV4YCBwcm9wZXJ0eS4KICAgICAgICAgIC8vIFRoZSBwcm9wZXJ0eSByZXR1cm5zIGAtMWAgaWYgdGhlcmUgaXMgbm8gYHRhYmluZGV4YCBhdHRyaWJ1dGUuCiAgICAgICAgICAvLyBUaGlzIGRpc3RpbmN0aW9uIGlzIGltcG9ydGFudCB3aGVuIHJlc3RvcmluZyB0aGUgdmFsdWUgYmVjYXVzZQogICAgICAgICAgLy8gbGVhdmluZyBgLTFgIGhpZGVzIHNoYWRvdyByb290IGNoaWxkcmVuIGZyb20gdGhlIHRhYiBvcmRlci4KICAgICAgICAgIHRoaXMuX29sZFRhYkluZGV4ID0gdGhpcy5nZXRBdHRyaWJ1dGUoJ3RhYmluZGV4Jyk7CiAgICAgICAgICB0aGlzLl9zZXRGb2N1c2VkKGZhbHNlKTsKICAgICAgICAgIHRoaXMudGFiSW5kZXggPSAtMTsKICAgICAgICAgIHRoaXMuYmx1cigpOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5fb2xkVGFiSW5kZXggIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgaWYgKHRoaXMuX29sZFRhYkluZGV4ID09PSBudWxsKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCd0YWJpbmRleCcpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgdGhpcy5fb2xkVGFiSW5kZXgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9jaGFuZ2VkQ29udHJvbFN0YXRlOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBfY29udHJvbFN0YXRlQ2hhbmdlZCBpcyBhYnN0cmFjdCwgZm9sbG93LW9uIGJlaGF2aW9ycyBtYXkgaW1wbGVtZW50IGl0CiAgICAgICAgaWYgKHRoaXMuX2NvbnRyb2xTdGF0ZUNoYW5nZWQpIHsKICAgICAgICAgIHRoaXMuX2NvbnRyb2xTdGF0ZUNoYW5nZWQoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAgKiBAcG9seW1lckJlaGF2aW9yIElyb25CdXR0b25TdGF0ZQogICAgICovCiAgICBjb25zdCBJcm9uQnV0dG9uU3RhdGVJbXBsID0gewoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgdXNlciBpcyBjdXJyZW50bHkgaG9sZGluZyBkb3duIHRoZSBidXR0b24uCiAgICAgICAgICovCiAgICAgICAgcHJlc3NlZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgICAgb2JzZXJ2ZXI6ICdfcHJlc3NlZENoYW5nZWQnCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIGJ1dHRvbiB0b2dnbGVzIHRoZSBhY3RpdmUgc3RhdGUgd2l0aCBlYWNoIHRhcCBvciBwcmVzcwogICAgICAgICAqIG9mIHRoZSBzcGFjZWJhci4KICAgICAgICAgKi8KICAgICAgICB0b2dnbGVzOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgYnV0dG9uIGlzIGEgdG9nZ2xlIGFuZCBpcyBjdXJyZW50bHkgaW4gdGhlIGFjdGl2ZSBzdGF0ZS4KICAgICAgICAgKi8KICAgICAgICBhY3RpdmU6CiAgICAgICAgICAgIHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG5vdGlmeTogdHJ1ZSwgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVHJ1ZSBpZiB0aGUgZWxlbWVudCBpcyBjdXJyZW50bHkgYmVpbmcgcHJlc3NlZCBieSBhICJwb2ludGVyLCIgd2hpY2gKICAgICAgICAgKiBpcyBsb29zZWx5IGRlZmluZWQgYXMgbW91c2Ugb3IgdG91Y2ggaW5wdXQgKGJ1dCBzcGVjaWZpY2FsbHkgZXhjbHVkaW5nCiAgICAgICAgICoga2V5Ym9hcmQgaW5wdXQpLgogICAgICAgICAqLwogICAgICAgIHBvaW50ZXJEb3duOiB7dHlwZTogQm9vbGVhbiwgcmVhZE9ubHk6IHRydWUsIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRydWUgaWYgdGhlIGlucHV0IGRldmljZSB0aGF0IGNhdXNlZCB0aGUgZWxlbWVudCB0byByZWNlaXZlIGZvY3VzCiAgICAgICAgICogd2FzIGEga2V5Ym9hcmQuCiAgICAgICAgICovCiAgICAgICAgcmVjZWl2ZWRGb2N1c0Zyb21LZXlib2FyZDoge3R5cGU6IEJvb2xlYW4sIHJlYWRPbmx5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGFyaWEgYXR0cmlidXRlIHRvIGJlIHNldCBpZiB0aGUgYnV0dG9uIGlzIGEgdG9nZ2xlIGFuZCBpbiB0aGUKICAgICAgICAgKiBhY3RpdmUgc3RhdGUuCiAgICAgICAgICovCiAgICAgICAgYXJpYUFjdGl2ZUF0dHJpYnV0ZTogewogICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgdmFsdWU6ICdhcmlhLXByZXNzZWQnLAogICAgICAgICAgb2JzZXJ2ZXI6ICdfYXJpYUFjdGl2ZUF0dHJpYnV0ZUNoYW5nZWQnCiAgICAgICAgfQogICAgICB9LAoKICAgICAgbGlzdGVuZXJzOiB7ZG93bjogJ19kb3duSGFuZGxlcicsIHVwOiAnX3VwSGFuZGxlcicsIHRhcDogJ190YXBIYW5kbGVyJ30sCgogICAgICBvYnNlcnZlcnM6CiAgICAgICAgICBbJ19mb2N1c0NoYW5nZWQoZm9jdXNlZCknLCAnX2FjdGl2ZUNoYW5nZWQoYWN0aXZlLCBhcmlhQWN0aXZlQXR0cmlidXRlKSddLAoKICAgICAgLyoqCiAgICAgICAqIEB0eXBlIHshT2JqZWN0fQogICAgICAgKi8KICAgICAga2V5QmluZGluZ3M6IHsKICAgICAgICAnZW50ZXI6a2V5ZG93bic6ICdfYXN5bmNDbGljaycsCiAgICAgICAgJ3NwYWNlOmtleWRvd24nOiAnX3NwYWNlS2V5RG93bkhhbmRsZXInLAogICAgICAgICdzcGFjZTprZXl1cCc6ICdfc3BhY2VLZXlVcEhhbmRsZXInLAogICAgICB9LAoKICAgICAgX21vdXNlRXZlbnRSZTogL15tb3VzZS8sCgogICAgICBfdGFwSGFuZGxlcjogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMudG9nZ2xlcykgewogICAgICAgICAgLy8gYSB0YXAgaXMgbmVlZGVkIHRvIHRvZ2dsZSB0aGUgYWN0aXZlIHN0YXRlCiAgICAgICAgICB0aGlzLl91c2VyQWN0aXZhdGUoIXRoaXMuYWN0aXZlKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5hY3RpdmUgPSBmYWxzZTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfZm9jdXNDaGFuZ2VkOiBmdW5jdGlvbihmb2N1c2VkKSB7CiAgICAgICAgdGhpcy5fZGV0ZWN0S2V5Ym9hcmRGb2N1cyhmb2N1c2VkKTsKCiAgICAgICAgaWYgKCFmb2N1c2VkKSB7CiAgICAgICAgICB0aGlzLl9zZXRQcmVzc2VkKGZhbHNlKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfZGV0ZWN0S2V5Ym9hcmRGb2N1czogZnVuY3Rpb24oZm9jdXNlZCkgewogICAgICAgIHRoaXMuX3NldFJlY2VpdmVkRm9jdXNGcm9tS2V5Ym9hcmQoIXRoaXMucG9pbnRlckRvd24gJiYgZm9jdXNlZCk7CiAgICAgIH0sCgogICAgICAvLyB0byBlbXVsYXRlIG5hdGl2ZSBjaGVja2JveCwgKGRlLSlhY3RpdmF0aW9ucyBmcm9tIGEgdXNlciBpbnRlcmFjdGlvbiBmaXJlCiAgICAgIC8vICdjaGFuZ2UnIGV2ZW50cwogICAgICBfdXNlckFjdGl2YXRlOiBmdW5jdGlvbihhY3RpdmUpIHsKICAgICAgICBpZiAodGhpcy5hY3RpdmUgIT09IGFjdGl2ZSkgewogICAgICAgICAgdGhpcy5hY3RpdmUgPSBhY3RpdmU7CiAgICAgICAgICB0aGlzLmZpcmUoJ2NoYW5nZScpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9kb3duSGFuZGxlcjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLl9zZXRQb2ludGVyRG93bih0cnVlKTsKICAgICAgICB0aGlzLl9zZXRQcmVzc2VkKHRydWUpOwogICAgICAgIHRoaXMuX3NldFJlY2VpdmVkRm9jdXNGcm9tS2V5Ym9hcmQoZmFsc2UpOwogICAgICB9LAoKICAgICAgX3VwSGFuZGxlcjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fc2V0UG9pbnRlckRvd24oZmFsc2UpOwogICAgICAgIHRoaXMuX3NldFByZXNzZWQoZmFsc2UpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IUtleWJvYXJkRXZlbnR9IGV2ZW50IC4KICAgICAgICovCiAgICAgIF9zcGFjZUtleURvd25IYW5kbGVyOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciBrZXlib2FyZEV2ZW50ID0gZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQ7CiAgICAgICAgdmFyIHRhcmdldCA9IGRvbShrZXlib2FyZEV2ZW50KS5sb2NhbFRhcmdldDsKCiAgICAgICAgLy8gSWdub3JlIHRoZSBldmVudCBpZiB0aGlzIGlzIGNvbWluZyBmcm9tIGEgZm9jdXNlZCBsaWdodCBjaGlsZCwgc2luY2UgdGhhdAogICAgICAgIC8vIGVsZW1lbnQgd2lsbCBkZWFsIHdpdGggaXQuCiAgICAgICAgaWYgKHRoaXMuaXNMaWdodERlc2NlbmRhbnQoLyoqIEB0eXBlIHtOb2RlfSAqLyAodGFyZ2V0KSkpCiAgICAgICAgICByZXR1cm47CgogICAgICAgIGtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgICBrZXlib2FyZEV2ZW50LnN0b3BJbW1lZGlhdGVQcm9wYWdhdGlvbigpOwogICAgICAgIHRoaXMuX3NldFByZXNzZWQodHJ1ZSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHBhcmFtIHshS2V5Ym9hcmRFdmVudH0gZXZlbnQgLgogICAgICAgKi8KICAgICAgX3NwYWNlS2V5VXBIYW5kbGVyOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciBrZXlib2FyZEV2ZW50ID0gZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQ7CiAgICAgICAgdmFyIHRhcmdldCA9IGRvbShrZXlib2FyZEV2ZW50KS5sb2NhbFRhcmdldDsKCiAgICAgICAgLy8gSWdub3JlIHRoZSBldmVudCBpZiB0aGlzIGlzIGNvbWluZyBmcm9tIGEgZm9jdXNlZCBsaWdodCBjaGlsZCwgc2luY2UgdGhhdAogICAgICAgIC8vIGVsZW1lbnQgd2lsbCBkZWFsIHdpdGggaXQuCiAgICAgICAgaWYgKHRoaXMuaXNMaWdodERlc2NlbmRhbnQoLyoqIEB0eXBlIHtOb2RlfSAqLyAodGFyZ2V0KSkpCiAgICAgICAgICByZXR1cm47CgogICAgICAgIGlmICh0aGlzLnByZXNzZWQpIHsKICAgICAgICAgIHRoaXMuX2FzeW5jQ2xpY2soKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fc2V0UHJlc3NlZChmYWxzZSk7CiAgICAgIH0sCgogICAgICAvLyB0cmlnZ2VyIGNsaWNrIGFzeW5jaHJvbm91c2x5LCB0aGUgYXN5bmNocm9ueSBpcyB1c2VmdWwgdG8gYWxsb3cgb25lCiAgICAgIC8vIGV2ZW50IGhhbmRsZXIgdG8gdW53aW5kIGJlZm9yZSB0cmlnZ2VyaW5nIGFub3RoZXIgZXZlbnQKICAgICAgX2FzeW5jQ2xpY2s6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLmNsaWNrKCk7CiAgICAgICAgfSwgMSk7CiAgICAgIH0sCgogICAgICAvLyBhbnkgb2YgdGhlc2UgY2hhbmdlcyBhcmUgY29uc2lkZXJlZCBhIGNoYW5nZSB0byBidXR0b24gc3RhdGUKCiAgICAgIF9wcmVzc2VkQ2hhbmdlZDogZnVuY3Rpb24ocHJlc3NlZCkgewogICAgICAgIHRoaXMuX2NoYW5nZWRCdXR0b25TdGF0ZSgpOwogICAgICB9LAoKICAgICAgX2FyaWFBY3RpdmVBdHRyaWJ1dGVDaGFuZ2VkOiBmdW5jdGlvbih2YWx1ZSwgb2xkVmFsdWUpIHsKICAgICAgICBpZiAob2xkVmFsdWUgJiYgb2xkVmFsdWUgIT0gdmFsdWUgJiYgdGhpcy5oYXNBdHRyaWJ1dGUob2xkVmFsdWUpKSB7CiAgICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZShvbGRWYWx1ZSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2FjdGl2ZUNoYW5nZWQ6IGZ1bmN0aW9uKGFjdGl2ZSwgYXJpYUFjdGl2ZUF0dHJpYnV0ZSkgewogICAgICAgIGlmICh0aGlzLnRvZ2dsZXMpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKHRoaXMuYXJpYUFjdGl2ZUF0dHJpYnV0ZSwgYWN0aXZlID8gJ3RydWUnIDogJ2ZhbHNlJyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKHRoaXMuYXJpYUFjdGl2ZUF0dHJpYnV0ZSk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX2NoYW5nZWRCdXR0b25TdGF0ZSgpOwogICAgICB9LAoKICAgICAgX2NvbnRyb2xTdGF0ZUNoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLmRpc2FibGVkKSB7CiAgICAgICAgICB0aGlzLl9zZXRQcmVzc2VkKGZhbHNlKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fY2hhbmdlZEJ1dHRvblN0YXRlKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLy8gcHJvdmlkZSBob29rIGZvciBmb2xsb3ctb24gYmVoYXZpb3JzIHRvIHJlYWN0IHRvIGJ1dHRvbi1zdGF0ZQoKICAgICAgX2NoYW5nZWRCdXR0b25TdGF0ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2J1dHRvblN0YXRlQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5fYnV0dG9uU3RhdGVDaGFuZ2VkKCk7ICAvLyBhYnN0cmFjdAogICAgICAgIH0KICAgICAgfQoKICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IElyb25CdXR0b25TdGF0ZSA9IFtJcm9uQTExeUtleXNCZWhhdmlvciwgSXJvbkJ1dHRvblN0YXRlSW1wbF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE0IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgdmFyIFV0aWxpdHkgPSB7CiAgICAgIGRpc3RhbmNlOiBmdW5jdGlvbih4MSwgeTEsIHgyLCB5MikgewogICAgICAgIHZhciB4RGVsdGEgPSAoeDEgLSB4Mik7CiAgICAgICAgdmFyIHlEZWx0YSA9ICh5MSAtIHkyKTsKCiAgICAgICAgcmV0dXJuIE1hdGguc3FydCh4RGVsdGEgKiB4RGVsdGEgKyB5RGVsdGEgKiB5RGVsdGEpOwogICAgICB9LAoKICAgICAgbm93OiB3aW5kb3cucGVyZm9ybWFuY2UgJiYgd2luZG93LnBlcmZvcm1hbmNlLm5vdyA/CiAgICAgICAgICB3aW5kb3cucGVyZm9ybWFuY2Uubm93LmJpbmQod2luZG93LnBlcmZvcm1hbmNlKSA6CiAgICAgICAgICBEYXRlLm5vdwogICAgfTsKCiAgICAvKioKICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICovCiAgICBmdW5jdGlvbiBFbGVtZW50TWV0cmljcyhlbGVtZW50KSB7CiAgICAgIHRoaXMuZWxlbWVudCA9IGVsZW1lbnQ7CiAgICAgIHRoaXMud2lkdGggPSB0aGlzLmJvdW5kaW5nUmVjdC53aWR0aDsKICAgICAgdGhpcy5oZWlnaHQgPSB0aGlzLmJvdW5kaW5nUmVjdC5oZWlnaHQ7CgogICAgICB0aGlzLnNpemUgPSBNYXRoLm1heCh0aGlzLndpZHRoLCB0aGlzLmhlaWdodCk7CiAgICB9CgogICAgRWxlbWVudE1ldHJpY3MucHJvdG90eXBlID0gewogICAgICBnZXQgYm91bmRpbmdSZWN0KCkgewogICAgICAgIHJldHVybiB0aGlzLmVsZW1lbnQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgIH0sCgogICAgICBmdXJ0aGVzdENvcm5lckRpc3RhbmNlRnJvbTogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciB0b3BMZWZ0ID0gVXRpbGl0eS5kaXN0YW5jZSh4LCB5LCAwLCAwKTsKICAgICAgICB2YXIgdG9wUmlnaHQgPSBVdGlsaXR5LmRpc3RhbmNlKHgsIHksIHRoaXMud2lkdGgsIDApOwogICAgICAgIHZhciBib3R0b21MZWZ0ID0gVXRpbGl0eS5kaXN0YW5jZSh4LCB5LCAwLCB0aGlzLmhlaWdodCk7CiAgICAgICAgdmFyIGJvdHRvbVJpZ2h0ID0gVXRpbGl0eS5kaXN0YW5jZSh4LCB5LCB0aGlzLndpZHRoLCB0aGlzLmhlaWdodCk7CgogICAgICAgIHJldHVybiBNYXRoLm1heCh0b3BMZWZ0LCB0b3BSaWdodCwgYm90dG9tTGVmdCwgYm90dG9tUmlnaHQpOwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudAogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKi8KICAgIGZ1bmN0aW9uIFJpcHBsZShlbGVtZW50KSB7CiAgICAgIHRoaXMuZWxlbWVudCA9IGVsZW1lbnQ7CiAgICAgIHRoaXMuY29sb3IgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZShlbGVtZW50KS5jb2xvcjsKCiAgICAgIHRoaXMud2F2ZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpOwogICAgICB0aGlzLndhdmVDb250YWluZXIgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgICAgdGhpcy53YXZlLnN0eWxlLmJhY2tncm91bmRDb2xvciA9IHRoaXMuY29sb3I7CiAgICAgIHRoaXMud2F2ZS5jbGFzc0xpc3QuYWRkKCd3YXZlJyk7CiAgICAgIHRoaXMud2F2ZUNvbnRhaW5lci5jbGFzc0xpc3QuYWRkKCd3YXZlLWNvbnRhaW5lcicpOwogICAgICBkb20odGhpcy53YXZlQ29udGFpbmVyKS5hcHBlbmRDaGlsZCh0aGlzLndhdmUpOwoKICAgICAgdGhpcy5yZXNldEludGVyYWN0aW9uU3RhdGUoKTsKICAgIH0KCiAgICBSaXBwbGUuTUFYX1JBRElVUyA9IDMwMDsKCiAgICBSaXBwbGUucHJvdG90eXBlID0gewogICAgICBnZXQgcmVjZW50ZXJzKCkgewogICAgICAgIHJldHVybiB0aGlzLmVsZW1lbnQucmVjZW50ZXJzOwogICAgICB9LAoKICAgICAgZ2V0IGNlbnRlcigpIHsKICAgICAgICByZXR1cm4gdGhpcy5lbGVtZW50LmNlbnRlcjsKICAgICAgfSwKCiAgICAgIGdldCBtb3VzZURvd25FbGFwc2VkKCkgewogICAgICAgIHZhciBlbGFwc2VkOwoKICAgICAgICBpZiAoIXRoaXMubW91c2VEb3duU3RhcnQpIHsKICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KCiAgICAgICAgZWxhcHNlZCA9IFV0aWxpdHkubm93KCkgLSB0aGlzLm1vdXNlRG93blN0YXJ0OwoKICAgICAgICBpZiAodGhpcy5tb3VzZVVwU3RhcnQpIHsKICAgICAgICAgIGVsYXBzZWQgLT0gdGhpcy5tb3VzZVVwRWxhcHNlZDsKICAgICAgICB9CgogICAgICAgIHJldHVybiBlbGFwc2VkOwogICAgICB9LAoKICAgICAgZ2V0IG1vdXNlVXBFbGFwc2VkKCkgewogICAgICAgIHJldHVybiB0aGlzLm1vdXNlVXBTdGFydCA/IFV0aWxpdHkubm93KCkgLSB0aGlzLm1vdXNlVXBTdGFydCA6IDA7CiAgICAgIH0sCgogICAgICBnZXQgbW91c2VEb3duRWxhcHNlZFNlY29uZHMoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubW91c2VEb3duRWxhcHNlZCAvIDEwMDA7CiAgICAgIH0sCgogICAgICBnZXQgbW91c2VVcEVsYXBzZWRTZWNvbmRzKCkgewogICAgICAgIHJldHVybiB0aGlzLm1vdXNlVXBFbGFwc2VkIC8gMTAwMDsKICAgICAgfSwKCiAgICAgIGdldCBtb3VzZUludGVyYWN0aW9uU2Vjb25kcygpIHsKICAgICAgICByZXR1cm4gdGhpcy5tb3VzZURvd25FbGFwc2VkU2Vjb25kcyArIHRoaXMubW91c2VVcEVsYXBzZWRTZWNvbmRzOwogICAgICB9LAoKICAgICAgZ2V0IGluaXRpYWxPcGFjaXR5KCkgewogICAgICAgIHJldHVybiB0aGlzLmVsZW1lbnQuaW5pdGlhbE9wYWNpdHk7CiAgICAgIH0sCgogICAgICBnZXQgb3BhY2l0eURlY2F5VmVsb2NpdHkoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZWxlbWVudC5vcGFjaXR5RGVjYXlWZWxvY2l0eTsKICAgICAgfSwKCiAgICAgIGdldCByYWRpdXMoKSB7CiAgICAgICAgdmFyIHdpZHRoMiA9IHRoaXMuY29udGFpbmVyTWV0cmljcy53aWR0aCAqIHRoaXMuY29udGFpbmVyTWV0cmljcy53aWR0aDsKICAgICAgICB2YXIgaGVpZ2h0MiA9IHRoaXMuY29udGFpbmVyTWV0cmljcy5oZWlnaHQgKiB0aGlzLmNvbnRhaW5lck1ldHJpY3MuaGVpZ2h0OwogICAgICAgIHZhciB3YXZlUmFkaXVzID0KICAgICAgICAgICAgTWF0aC5taW4oTWF0aC5zcXJ0KHdpZHRoMiArIGhlaWdodDIpLCBSaXBwbGUuTUFYX1JBRElVUykgKiAxLjEgKyA1OwoKICAgICAgICB2YXIgZHVyYXRpb24gPSAxLjEgLSAwLjIgKiAod2F2ZVJhZGl1cyAvIFJpcHBsZS5NQVhfUkFESVVTKTsKICAgICAgICB2YXIgdGltZU5vdyA9IHRoaXMubW91c2VJbnRlcmFjdGlvblNlY29uZHMgLyBkdXJhdGlvbjsKICAgICAgICB2YXIgc2l6ZSA9IHdhdmVSYWRpdXMgKiAoMSAtIE1hdGgucG93KDgwLCAtdGltZU5vdykpOwoKICAgICAgICByZXR1cm4gTWF0aC5hYnMoc2l6ZSk7CiAgICAgIH0sCgogICAgICBnZXQgb3BhY2l0eSgpIHsKICAgICAgICBpZiAoIXRoaXMubW91c2VVcFN0YXJ0KSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5pbml0aWFsT3BhY2l0eTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBNYXRoLm1heCgKICAgICAgICAgICAgMCwKICAgICAgICAgICAgdGhpcy5pbml0aWFsT3BhY2l0eSAtCiAgICAgICAgICAgICAgICB0aGlzLm1vdXNlVXBFbGFwc2VkU2Vjb25kcyAqIHRoaXMub3BhY2l0eURlY2F5VmVsb2NpdHkpOwogICAgICB9LAoKICAgICAgZ2V0IG91dGVyT3BhY2l0eSgpIHsKICAgICAgICAvLyBMaW5lYXIgaW5jcmVhc2UgaW4gYmFja2dyb3VuZCBvcGFjaXR5LCBjYXBwZWQgYXQgdGhlIG9wYWNpdHkKICAgICAgICAvLyBvZiB0aGUgd2F2ZWZyb250ICh3YXZlT3BhY2l0eSkuCiAgICAgICAgdmFyIG91dGVyT3BhY2l0eSA9IHRoaXMubW91c2VVcEVsYXBzZWRTZWNvbmRzICogMC4zOwogICAgICAgIHZhciB3YXZlT3BhY2l0eSA9IHRoaXMub3BhY2l0eTsKCiAgICAgICAgcmV0dXJuIE1hdGgubWF4KDAsIE1hdGgubWluKG91dGVyT3BhY2l0eSwgd2F2ZU9wYWNpdHkpKTsKICAgICAgfSwKCiAgICAgIGdldCBpc09wYWNpdHlGdWxseURlY2F5ZWQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMub3BhY2l0eSA8IDAuMDEgJiYKICAgICAgICAgICAgdGhpcy5yYWRpdXMgPj0gTWF0aC5taW4odGhpcy5tYXhSYWRpdXMsIFJpcHBsZS5NQVhfUkFESVVTKTsKICAgICAgfSwKCiAgICAgIGdldCBpc1Jlc3RpbmdBdE1heFJhZGl1cygpIHsKICAgICAgICByZXR1cm4gdGhpcy5vcGFjaXR5ID49IHRoaXMuaW5pdGlhbE9wYWNpdHkgJiYKICAgICAgICAgICAgdGhpcy5yYWRpdXMgPj0gTWF0aC5taW4odGhpcy5tYXhSYWRpdXMsIFJpcHBsZS5NQVhfUkFESVVTKTsKICAgICAgfSwKCiAgICAgIGdldCBpc0FuaW1hdGlvbkNvbXBsZXRlKCkgewogICAgICAgIHJldHVybiB0aGlzLm1vdXNlVXBTdGFydCA/IHRoaXMuaXNPcGFjaXR5RnVsbHlEZWNheWVkIDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmlzUmVzdGluZ0F0TWF4UmFkaXVzOwogICAgICB9LAoKICAgICAgZ2V0IHRyYW5zbGF0aW9uRnJhY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIE1hdGgubWluKAogICAgICAgICAgICAxLCB0aGlzLnJhZGl1cyAvIHRoaXMuY29udGFpbmVyTWV0cmljcy5zaXplICogMiAvIE1hdGguc3FydCgyKSk7CiAgICAgIH0sCgogICAgICBnZXQgeE5vdygpIHsKICAgICAgICBpZiAodGhpcy54RW5kKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy54U3RhcnQgKyB0aGlzLnRyYW5zbGF0aW9uRnJhY3Rpb24gKiAodGhpcy54RW5kIC0gdGhpcy54U3RhcnQpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHRoaXMueFN0YXJ0OwogICAgICB9LAoKICAgICAgZ2V0IHlOb3coKSB7CiAgICAgICAgaWYgKHRoaXMueUVuZCkgewogICAgICAgICAgcmV0dXJuIHRoaXMueVN0YXJ0ICsgdGhpcy50cmFuc2xhdGlvbkZyYWN0aW9uICogKHRoaXMueUVuZCAtIHRoaXMueVN0YXJ0KTsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0aGlzLnlTdGFydDsKICAgICAgfSwKCiAgICAgIGdldCBpc01vdXNlRG93bigpIHsKICAgICAgICByZXR1cm4gdGhpcy5tb3VzZURvd25TdGFydCAmJiAhdGhpcy5tb3VzZVVwU3RhcnQ7CiAgICAgIH0sCgogICAgICByZXNldEludGVyYWN0aW9uU3RhdGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMubWF4UmFkaXVzID0gMDsKICAgICAgICB0aGlzLm1vdXNlRG93blN0YXJ0ID0gMDsKICAgICAgICB0aGlzLm1vdXNlVXBTdGFydCA9IDA7CgogICAgICAgIHRoaXMueFN0YXJ0ID0gMDsKICAgICAgICB0aGlzLnlTdGFydCA9IDA7CiAgICAgICAgdGhpcy54RW5kID0gMDsKICAgICAgICB0aGlzLnlFbmQgPSAwOwogICAgICAgIHRoaXMuc2xpZGVEaXN0YW5jZSA9IDA7CgogICAgICAgIHRoaXMuY29udGFpbmVyTWV0cmljcyA9IG5ldyBFbGVtZW50TWV0cmljcyh0aGlzLmVsZW1lbnQpOwogICAgICB9LAoKICAgICAgZHJhdzogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjYWxlOwogICAgICAgIHZhciBkeDsKICAgICAgICB2YXIgZHk7CgogICAgICAgIHRoaXMud2F2ZS5zdHlsZS5vcGFjaXR5ID0gdGhpcy5vcGFjaXR5OwoKICAgICAgICBzY2FsZSA9IHRoaXMucmFkaXVzIC8gKHRoaXMuY29udGFpbmVyTWV0cmljcy5zaXplIC8gMik7CiAgICAgICAgZHggPSB0aGlzLnhOb3cgLSAodGhpcy5jb250YWluZXJNZXRyaWNzLndpZHRoIC8gMik7CiAgICAgICAgZHkgPSB0aGlzLnlOb3cgLSAodGhpcy5jb250YWluZXJNZXRyaWNzLmhlaWdodCAvIDIpOwoKCiAgICAgICAgLy8gMmQgdHJhbnNmb3JtIGZvciBzYWZhcmkgYmVjYXVzZSBvZiBib3JkZXItcmFkaXVzIGFuZCBvdmVyZmxvdzpoaWRkZW4KICAgICAgICAvLyBjbGlwcGluZyBidWcuIGh0dHBzOi8vYnVncy53ZWJraXQub3JnL3Nob3dfYnVnLmNnaT9pZD05ODUzOAogICAgICAgIHRoaXMud2F2ZUNvbnRhaW5lci5zdHlsZS53ZWJraXRUcmFuc2Zvcm0gPQogICAgICAgICAgICAndHJhbnNsYXRlKCcgKyBkeCArICdweCwgJyArIGR5ICsgJ3B4KSc7CiAgICAgICAgdGhpcy53YXZlQ29udGFpbmVyLnN0eWxlLnRyYW5zZm9ybSA9CiAgICAgICAgICAgICd0cmFuc2xhdGUzZCgnICsgZHggKyAncHgsICcgKyBkeSArICdweCwgMCknOwogICAgICAgIHRoaXMud2F2ZS5zdHlsZS53ZWJraXRUcmFuc2Zvcm0gPSAnc2NhbGUoJyArIHNjYWxlICsgJywnICsgc2NhbGUgKyAnKSc7CiAgICAgICAgdGhpcy53YXZlLnN0eWxlLnRyYW5zZm9ybSA9ICdzY2FsZTNkKCcgKyBzY2FsZSArICcsJyArIHNjYWxlICsgJywxKSc7CiAgICAgIH0sCgogICAgICAvKiogQHBhcmFtIHtFdmVudD19IGV2ZW50ICovCiAgICAgIGRvd25BY3Rpb246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdmFyIHhDZW50ZXIgPSB0aGlzLmNvbnRhaW5lck1ldHJpY3Mud2lkdGggLyAyOwogICAgICAgIHZhciB5Q2VudGVyID0gdGhpcy5jb250YWluZXJNZXRyaWNzLmhlaWdodCAvIDI7CgogICAgICAgIHRoaXMucmVzZXRJbnRlcmFjdGlvblN0YXRlKCk7CiAgICAgICAgdGhpcy5tb3VzZURvd25TdGFydCA9IFV0aWxpdHkubm93KCk7CgogICAgICAgIGlmICh0aGlzLmNlbnRlcikgewogICAgICAgICAgdGhpcy54U3RhcnQgPSB4Q2VudGVyOwogICAgICAgICAgdGhpcy55U3RhcnQgPSB5Q2VudGVyOwogICAgICAgICAgdGhpcy5zbGlkZURpc3RhbmNlID0KICAgICAgICAgICAgICBVdGlsaXR5LmRpc3RhbmNlKHRoaXMueFN0YXJ0LCB0aGlzLnlTdGFydCwgdGhpcy54RW5kLCB0aGlzLnlFbmQpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnhTdGFydCA9IGV2ZW50ID8KICAgICAgICAgICAgICBldmVudC5kZXRhaWwueCAtIHRoaXMuY29udGFpbmVyTWV0cmljcy5ib3VuZGluZ1JlY3QubGVmdCA6CiAgICAgICAgICAgICAgdGhpcy5jb250YWluZXJNZXRyaWNzLndpZHRoIC8gMjsKICAgICAgICAgIHRoaXMueVN0YXJ0ID0gZXZlbnQgPwogICAgICAgICAgICAgIGV2ZW50LmRldGFpbC55IC0gdGhpcy5jb250YWluZXJNZXRyaWNzLmJvdW5kaW5nUmVjdC50b3AgOgogICAgICAgICAgICAgIHRoaXMuY29udGFpbmVyTWV0cmljcy5oZWlnaHQgLyAyOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMucmVjZW50ZXJzKSB7CiAgICAgICAgICB0aGlzLnhFbmQgPSB4Q2VudGVyOwogICAgICAgICAgdGhpcy55RW5kID0geUNlbnRlcjsKICAgICAgICAgIHRoaXMuc2xpZGVEaXN0YW5jZSA9CiAgICAgICAgICAgICAgVXRpbGl0eS5kaXN0YW5jZSh0aGlzLnhTdGFydCwgdGhpcy55U3RhcnQsIHRoaXMueEVuZCwgdGhpcy55RW5kKTsKICAgICAgICB9CgogICAgICAgIHRoaXMubWF4UmFkaXVzID0gdGhpcy5jb250YWluZXJNZXRyaWNzLmZ1cnRoZXN0Q29ybmVyRGlzdGFuY2VGcm9tKAogICAgICAgICAgICB0aGlzLnhTdGFydCwgdGhpcy55U3RhcnQpOwoKICAgICAgICB0aGlzLndhdmVDb250YWluZXIuc3R5bGUudG9wID0KICAgICAgICAgICAgKHRoaXMuY29udGFpbmVyTWV0cmljcy5oZWlnaHQgLSB0aGlzLmNvbnRhaW5lck1ldHJpY3Muc2l6ZSkgLyAyICsgJ3B4JzsKICAgICAgICB0aGlzLndhdmVDb250YWluZXIuc3R5bGUubGVmdCA9CiAgICAgICAgICAgICh0aGlzLmNvbnRhaW5lck1ldHJpY3Mud2lkdGggLSB0aGlzLmNvbnRhaW5lck1ldHJpY3Muc2l6ZSkgLyAyICsgJ3B4JzsKCiAgICAgICAgdGhpcy53YXZlQ29udGFpbmVyLnN0eWxlLndpZHRoID0gdGhpcy5jb250YWluZXJNZXRyaWNzLnNpemUgKyAncHgnOwogICAgICAgIHRoaXMud2F2ZUNvbnRhaW5lci5zdHlsZS5oZWlnaHQgPSB0aGlzLmNvbnRhaW5lck1ldHJpY3Muc2l6ZSArICdweCc7CiAgICAgIH0sCgogICAgICAvKiogQHBhcmFtIHtFdmVudD19IGV2ZW50ICovCiAgICAgIHVwQWN0aW9uOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy5pc01vdXNlRG93bikgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5tb3VzZVVwU3RhcnQgPSBVdGlsaXR5Lm5vdygpOwogICAgICB9LAoKICAgICAgcmVtb3ZlOiBmdW5jdGlvbigpIHsKICAgICAgICBkb20oZG9tKHRoaXMud2F2ZUNvbnRhaW5lcikucGFyZW50Tm9kZSkucmVtb3ZlQ2hpbGQodGhpcy53YXZlQ29udGFpbmVyKTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIE1hdGVyaWFsIGRlc2lnbjogW1N1cmZhY2UKICAgIHJlYWN0aW9uXShodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2FuaW1hdGlvbi9yZXNwb25zaXZlLWludGVyYWN0aW9uLmh0bWwjcmVzcG9uc2l2ZS1pbnRlcmFjdGlvbi1zdXJmYWNlLXJlYWN0aW9uKQoKICAgIGBwYXBlci1yaXBwbGVgIHByb3ZpZGVzIGEgdmlzdWFsIGVmZmVjdCB0aGF0IG90aGVyIHBhcGVyIGVsZW1lbnRzIGNhbgogICAgdXNlIHRvIHNpbXVsYXRlIGEgcmlwcGxpbmcgZWZmZWN0IGVtYW5hdGluZyBmcm9tIHRoZSBwb2ludCBvZiBjb250YWN0LiAgVGhlCiAgICBlZmZlY3QgY2FuIGJlIHZpc3VhbGl6ZWQgYXMgYSBjb25jZW50cmljIGNpcmNsZSB3aXRoIG1vdGlvbi4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8ZGl2IHN0eWxlPSJwb3NpdGlvbjpyZWxhdGl2ZSI+CiAgICAgICAgICA8cGFwZXItcmlwcGxlPjwvcGFwZXItcmlwcGxlPgogICAgICAgIDwvZGl2PgoKICAgIE5vdGUsIGl0J3MgaW1wb3J0YW50IHRoYXQgdGhlIHBhcmVudCBjb250YWluZXIgb2YgdGhlIHJpcHBsZSBiZSByZWxhdGl2ZQogICAgcG9zaXRpb24sIG90aGVyd2lzZSB0aGUgcmlwcGxlIHdpbGwgZW1hbmF0ZSBvdXRzaWRlIG9mIHRoZSBkZXNpcmVkIGNvbnRhaW5lci4KCiAgICBgcGFwZXItcmlwcGxlYCBsaXN0ZW5zIHRvICJtb3VzZWRvd24iIGFuZCAibW91c2V1cCIgZXZlbnRzIHNvIGl0IHdvdWxkIGRpc3BsYXkKICAgIHJpcHBsZSBlZmZlY3Qgd2hlbiB0b3VjaGVzIG9uIGl0LiAgWW91IGNhbiBhbHNvIGRlZmVhdCB0aGUgZGVmYXVsdCBiZWhhdmlvciBhbmQKICAgIG1hbnVhbGx5IHJvdXRlIHRoZSBkb3duIGFuZCB1cCBhY3Rpb25zIHRvIHRoZSByaXBwbGUgZWxlbWVudC4gIE5vdGUgdGhhdCBpdCBpcwogICAgaW1wb3J0YW50IGlmIHlvdSBjYWxsIGBkb3duQWN0aW9uKClgIHlvdSB3aWxsIGhhdmUgdG8gbWFrZSBzdXJlIHRvIGNhbGwKICAgIGB1cEFjdGlvbigpYCBzbyB0aGF0IGBwYXBlci1yaXBwbGVgIHdvdWxkIGVuZCB0aGUgYW5pbWF0aW9uIGxvb3AuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLXJpcHBsZSBpZD0icmlwcGxlIiBzdHlsZT0icG9pbnRlci1ldmVudHM6IG5vbmU7Ij48L3BhcGVyLXJpcHBsZT4KICAgICAgICAuLi4KICAgICAgICBkb3duQWN0aW9uOiBmdW5jdGlvbihlKSB7CiAgICAgICAgICB0aGlzLiQucmlwcGxlLmRvd25BY3Rpb24oZS5kZXRhaWwpOwogICAgICAgIH0sCiAgICAgICAgdXBBY3Rpb246IGZ1bmN0aW9uKGUpIHsKICAgICAgICAgIHRoaXMuJC5yaXBwbGUudXBBY3Rpb24oKTsKICAgICAgICB9CgogICAgU3R5bGluZyByaXBwbGUgZWZmZWN0OgoKICAgICAgVXNlIENTUyBjb2xvciBwcm9wZXJ0eSB0byBzdHlsZSB0aGUgcmlwcGxlOgoKICAgICAgICBwYXBlci1yaXBwbGUgewogICAgICAgICAgY29sb3I6ICM0Mjg1ZjQ7CiAgICAgICAgfQoKICAgICAgTm90ZSB0aGF0IENTUyBjb2xvciBwcm9wZXJ0eSBpcyBpbmhlcml0ZWQgc28gaXQgaXMgbm90IHJlcXVpcmVkIHRvIHNldCBpdCBvbgogICAgICB0aGUgYHBhcGVyLXJpcHBsZWAgZWxlbWVudCBkaXJlY3RseS4KCiAgICBCeSBkZWZhdWx0LCB0aGUgcmlwcGxlIGlzIGNlbnRlcmVkIG9uIHRoZSBwb2ludCBvZiBjb250YWN0LiAgQXBwbHkgdGhlCiAgICBgcmVjZW50ZXJzYCBhdHRyaWJ1dGUgdG8gaGF2ZSB0aGUgcmlwcGxlIGdyb3cgdG93YXJkIHRoZSBjZW50ZXIgb2YgaXRzCiAgICBjb250YWluZXIuCgogICAgICAgIDxwYXBlci1yaXBwbGUgcmVjZW50ZXJzPjwvcGFwZXItcmlwcGxlPgoKICAgIFlvdSBjYW4gYWxzbyAgY2VudGVyIHRoZSByaXBwbGUgaW5zaWRlIGl0cyBjb250YWluZXIgZnJvbSB0aGUgc3RhcnQuCgogICAgICAgIDxwYXBlci1yaXBwbGUgY2VudGVyPjwvcGFwZXItcmlwcGxlPgoKICAgIEFwcGx5IGBjaXJjbGVgIGNsYXNzIHRvIG1ha2UgdGhlIHJpcHBsaW5nIGVmZmVjdCB3aXRoaW4gYSBjaXJjbGUuCgogICAgICAgIDxwYXBlci1yaXBwbGUgY2xhc3M9ImNpcmNsZSI+PC9wYXBlci1yaXBwbGU+CgogICAgQGVsZW1lbnQgcGFwZXItcmlwcGxlCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgYm9yZGVyLXJhZGl1czogaW5oZXJpdDsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICAgIHRvcDogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKCiAgICAgICAgLyogU2VlIFBvbHltZXJFbGVtZW50cy9wYXBlci1iZWhhdmlvcnMvaXNzdWVzLzM0LiBPbiBub24tQ2hyb21lIGJyb3dzZXJzLAogICAgICAgICAqIGNyZWF0aW5nIGEgbm9kZSAod2l0aCBhIHBvc2l0aW9uOmFic29sdXRlKSBpbiB0aGUgbWlkZGxlIG9mIGFuIGV2ZW50CiAgICAgICAgICogaGFuZGxlciAiaW50ZXJydXB0cyIgdGhhdCBldmVudCBoYW5kbGVyICh3aGljaCBoYXBwZW5zIHdoZW4gdGhlCiAgICAgICAgICogcmlwcGxlIGlzIGNyZWF0ZWQgb24gZGVtYW5kKSAqLwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICB9CgogICAgICA6aG9zdChbYW5pbWF0aW5nXSkgewogICAgICAgIC8qIFRoaXMgcmVzb2x2ZXMgYSByZW5kZXJpbmcgaXNzdWUgaW4gQ2hyb21lIChhcyBvZiA0MCkgd2hlcmUgdGhlCiAgICAgICAgICAgcmlwcGxlIGlzIG5vdCBwcm9wZXJseSBjbGlwcGVkIGJ5IGl0cyBwYXJlbnQgKHdoaWNoIG1heSBoYXZlCiAgICAgICAgICAgcm91bmRlZCBjb3JuZXJzKS4gU2VlOiBodHRwOi8vanNiaW4uY29tL3RlbWV4YS80CgogICAgICAgICAgIE5vdGU6IFdlIG9ubHkgYXBwbHkgdGhpcyBzdHlsZSBjb25kaXRpb25hbGx5LiBPdGhlcndpc2UsIHRoZSBicm93c2VyCiAgICAgICAgICAgd2lsbCBjcmVhdGUgYSBuZXcgY29tcG9zaXRpbmcgbGF5ZXIgZm9yIGV2ZXJ5IHJpcHBsZSBlbGVtZW50IG9uIHRoZQogICAgICAgICAgIHBhZ2UsIGFuZCB0aGF0IHdvdWxkIGJlIGJhZC4gKi8KICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogdHJhbnNsYXRlKDAsIDApOwogICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlM2QoMCwgMCwgMCk7CiAgICAgIH0KCiAgICAgICNiYWNrZ3JvdW5kLAogICAgICAjd2F2ZXMsCiAgICAgIC53YXZlLWNvbnRhaW5lciwKICAgICAgLndhdmUgewogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgIH0KCiAgICAgICNiYWNrZ3JvdW5kLAogICAgICAud2F2ZSB7CiAgICAgICAgb3BhY2l0eTogMDsKICAgICAgfQoKICAgICAgI3dhdmVzLAogICAgICAud2F2ZSB7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgfQoKICAgICAgLndhdmUtY29udGFpbmVyLAogICAgICAud2F2ZSB7CiAgICAgICAgYm9yZGVyLXJhZGl1czogNTAlOwogICAgICB9CgogICAgICA6aG9zdCguY2lyY2xlKSAjYmFja2dyb3VuZCwKICAgICAgOmhvc3QoLmNpcmNsZSkgI3dhdmVzIHsKICAgICAgICBib3JkZXItcmFkaXVzOiA1MCU7CiAgICAgIH0KCiAgICAgIDpob3N0KC5jaXJjbGUpIC53YXZlLWNvbnRhaW5lciB7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8ZGl2IGlkPSJiYWNrZ3JvdW5kIj48L2Rpdj4KICAgIDxkaXYgaWQ9IndhdmVzIj48L2Rpdj4KYCwKCiAgICAgIGlzOiAncGFwZXItcmlwcGxlJywKICAgICAgYmVoYXZpb3JzOiBbSXJvbkExMXlLZXlzQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBpbml0aWFsIG9wYWNpdHkgc2V0IG9uIHRoZSB3YXZlLgogICAgICAgICAqIEB0eXBlIG51bWJlcgogICAgICAgICAqIEBkZWZhdWx0IDAuMjUKICAgICAgICAgKi8KICAgICAgICBpbml0aWFsT3BhY2l0eToge3R5cGU6IE51bWJlciwgdmFsdWU6IDAuMjV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBIb3cgZmFzdCAob3BhY2l0eSBwZXIgc2Vjb25kKSB0aGUgd2F2ZSBmYWRlcyBvdXQuCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSBudW1iZXIKICAgICAgICAgKiBAZGVmYXVsdCAwLjgKICAgICAgICAgKi8KICAgICAgICBvcGFjaXR5RGVjYXlWZWxvY2l0eToge3R5cGU6IE51bWJlciwgdmFsdWU6IDAuOH0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHJpcHBsZXMgd2lsbCBleGhpYml0IGEgZ3Jhdml0YXRpb25hbCBwdWxsIHRvd2FyZHMKICAgICAgICAgKiB0aGUgY2VudGVyIG9mIHRoZWlyIGNvbnRhaW5lciBhcyB0aGV5IGZhZGUgYXdheS4KICAgICAgICAgKgogICAgICAgICAqIEB0eXBlIGJvb2xlYW4KICAgICAgICAgKiBAZGVmYXVsdCBmYWxzZQogICAgICAgICAqLwogICAgICAgIHJlY2VudGVyczoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHJpcHBsZXMgd2lsbCBjZW50ZXIgaW5zaWRlIGl0cyBjb250YWluZXIKICAgICAgICAgKgogICAgICAgICAqIEB0eXBlIGJvb2xlYW4KICAgICAgICAgKiBAZGVmYXVsdCBmYWxzZQogICAgICAgICAqLwogICAgICAgIGNlbnRlcjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIEEgbGlzdCBvZiB0aGUgdmlzdWFsIHJpcHBsZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSBBcnJheQogICAgICAgICAqIEBkZWZhdWx0IFtdCiAgICAgICAgICovCiAgICAgICAgcmlwcGxlczogewogICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIHdoZW4gdGhlcmUgYXJlIHZpc2libGUgcmlwcGxlcyBhbmltYXRpbmcgd2l0aGluIHRoZQogICAgICAgICAqIGVsZW1lbnQuCiAgICAgICAgICovCiAgICAgICAgYW5pbWF0aW5nOgogICAgICAgICAgICB7dHlwZTogQm9vbGVhbiwgcmVhZE9ubHk6IHRydWUsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIHJpcHBsZSB3aWxsIHJlbWFpbiBpbiB0aGUgImRvd24iIHN0YXRlIHVudGlsIGBob2xkRG93bmAKICAgICAgICAgKiBpcyBzZXQgdG8gZmFsc2UgYWdhaW4uCiAgICAgICAgICovCiAgICAgICAgaG9sZERvd246IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG9ic2VydmVyOiAnX2hvbGREb3duQ2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgcmlwcGxlIHdpbGwgbm90IGdlbmVyYXRlIGEgcmlwcGxlIGVmZmVjdAogICAgICAgICAqIHZpYSBwb2ludGVyIGludGVyYWN0aW9uLgogICAgICAgICAqIENhbGxpbmcgcmlwcGxlJ3MgaW1wZXJhdGl2ZSBhcGkgbGlrZSBgc2ltdWxhdGVkUmlwcGxlYCB3aWxsCiAgICAgICAgICogc3RpbGwgZ2VuZXJhdGUgdGhlIHJpcHBsZSBlZmZlY3QuCiAgICAgICAgICovCiAgICAgICAgbm9pbms6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICBfYW5pbWF0aW5nOiB7dHlwZTogQm9vbGVhbn0sCgogICAgICAgIF9ib3VuZEFuaW1hdGU6IHsKICAgICAgICAgIHR5cGU6IEZ1bmN0aW9uLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5hbmltYXRlLmJpbmQodGhpcyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgZ2V0IHRhcmdldCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5rZXlFdmVudFRhcmdldDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAdHlwZSB7IU9iamVjdH0KICAgICAgICovCiAgICAgIGtleUJpbmRpbmdzOiB7CiAgICAgICAgJ2VudGVyOmtleWRvd24nOiAnX29uRW50ZXJLZXlkb3duJywKICAgICAgICAnc3BhY2U6a2V5ZG93bic6ICdfb25TcGFjZUtleWRvd24nLAogICAgICAgICdzcGFjZTprZXl1cCc6ICdfb25TcGFjZUtleXVwJwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gU2V0IHVwIGExMXlLZXlzQmVoYXZpb3IgdG8gbGlzdGVuIHRvIGtleSBldmVudHMgb24gdGhlIHRhcmdldCwKICAgICAgICAvLyBzbyB0aGF0IHNwYWNlIGFuZCBlbnRlciBhY3RpdmF0ZSB0aGUgcmlwcGxlIGV2ZW4gaWYgdGhlIHRhcmdldCBkb2Vzbid0CiAgICAgICAgLy8gaGFuZGxlIGtleSBldmVudHMuIFRoZSBrZXkgaGFuZGxlcnMgZGVhbCB3aXRoIGBub2lua2AgdGhlbXNlbHZlcy4KICAgICAgICBpZiAoZG9tKHRoaXMpLnBhcmVudE5vZGUubm9kZVR5cGUgPT0gMTEpIHsgIC8vIERPQ1VNRU5UX0ZSQUdNRU5UX05PREUKICAgICAgICAgIHRoaXMua2V5RXZlbnRUYXJnZXQgPSBkb20odGhpcykuZ2V0T3duZXJSb290KCkuaG9zdDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5rZXlFdmVudFRhcmdldCA9IGRvbSh0aGlzKS5wYXJlbnROb2RlOwogICAgICAgIH0KICAgICAgICB2YXIga2V5RXZlbnRUYXJnZXQgPSAvKiogQHR5cGUgeyFFdmVudFRhcmdldH0gKi8gKHRoaXMua2V5RXZlbnRUYXJnZXQpOwogICAgICAgIHRoaXMubGlzdGVuKGtleUV2ZW50VGFyZ2V0LCAndXAnLCAndWlVcEFjdGlvbicpOwogICAgICAgIHRoaXMubGlzdGVuKGtleUV2ZW50VGFyZ2V0LCAnZG93bicsICd1aURvd25BY3Rpb24nKTsKICAgICAgfSwKCiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgZGV0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudW5saXN0ZW4odGhpcy5rZXlFdmVudFRhcmdldCwgJ3VwJywgJ3VpVXBBY3Rpb24nKTsKICAgICAgICB0aGlzLnVubGlzdGVuKHRoaXMua2V5RXZlbnRUYXJnZXQsICdkb3duJywgJ3VpRG93bkFjdGlvbicpOwogICAgICAgIHRoaXMua2V5RXZlbnRUYXJnZXQgPSBudWxsOwogICAgICB9LAoKICAgICAgZ2V0IHNob3VsZEtlZXBBbmltYXRpbmcoKSB7CiAgICAgICAgZm9yICh2YXIgaW5kZXggPSAwOyBpbmRleCA8IHRoaXMucmlwcGxlcy5sZW5ndGg7ICsraW5kZXgpIHsKICAgICAgICAgIGlmICghdGhpcy5yaXBwbGVzW2luZGV4XS5pc0FuaW1hdGlvbkNvbXBsZXRlKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAoKICAgICAgc2ltdWxhdGVkUmlwcGxlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmRvd25BY3Rpb24obnVsbCk7CgogICAgICAgIC8vIFBsZWFzZSBzZWUgcG9seW1lci9wb2x5bWVyIzEzMDUKICAgICAgICB0aGlzLmFzeW5jKGZ1bmN0aW9uKCkgewogICAgICAgICAgdGhpcy51cEFjdGlvbigpOwogICAgICAgIH0sIDEpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFByb3Zva2VzIGEgcmlwcGxlIGRvd24gZWZmZWN0IHZpYSBhIFVJIGV2ZW50LAogICAgICAgKiByZXNwZWN0aW5nIHRoZSBgbm9pbmtgIHByb3BlcnR5LgogICAgICAgKiBAcGFyYW0ge0V2ZW50PX0gZXZlbnQKICAgICAgICovCiAgICAgIHVpRG93bkFjdGlvbjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoIXRoaXMubm9pbmspIHsKICAgICAgICAgIHRoaXMuZG93bkFjdGlvbihldmVudCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFByb3Zva2VzIGEgcmlwcGxlIGRvd24gZWZmZWN0IHZpYSBhIFVJIGV2ZW50LAogICAgICAgKiAqbm90KiByZXNwZWN0aW5nIHRoZSBgbm9pbmtgIHByb3BlcnR5LgogICAgICAgKiBAcGFyYW0ge0V2ZW50PX0gZXZlbnQKICAgICAgICovCiAgICAgIGRvd25BY3Rpb246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMuaG9sZERvd24gJiYgdGhpcy5yaXBwbGVzLmxlbmd0aCA+IDApIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHZhciByaXBwbGUgPSB0aGlzLmFkZFJpcHBsZSgpOwoKICAgICAgICByaXBwbGUuZG93bkFjdGlvbihldmVudCk7CgogICAgICAgIGlmICghdGhpcy5fYW5pbWF0aW5nKSB7CiAgICAgICAgICB0aGlzLl9hbmltYXRpbmcgPSB0cnVlOwogICAgICAgICAgdGhpcy5hbmltYXRlKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFByb3Zva2VzIGEgcmlwcGxlIHVwIGVmZmVjdCB2aWEgYSBVSSBldmVudCwKICAgICAgICogcmVzcGVjdGluZyB0aGUgYG5vaW5rYCBwcm9wZXJ0eS4KICAgICAgICogQHBhcmFtIHtFdmVudD19IGV2ZW50CiAgICAgICAqLwogICAgICB1aVVwQWN0aW9uOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy5ub2luaykgewogICAgICAgICAgdGhpcy51cEFjdGlvbihldmVudCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFByb3Zva2VzIGEgcmlwcGxlIHVwIGVmZmVjdCB2aWEgYSBVSSBldmVudCwKICAgICAgICogKm5vdCogcmVzcGVjdGluZyB0aGUgYG5vaW5rYCBwcm9wZXJ0eS4KICAgICAgICogQHBhcmFtIHtFdmVudD19IGV2ZW50CiAgICAgICAqLwogICAgICB1cEFjdGlvbjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAodGhpcy5ob2xkRG93bikgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5yaXBwbGVzLmZvckVhY2goZnVuY3Rpb24ocmlwcGxlKSB7CiAgICAgICAgICByaXBwbGUudXBBY3Rpb24oZXZlbnQpOwogICAgICAgIH0pOwoKICAgICAgICB0aGlzLl9hbmltYXRpbmcgPSB0cnVlOwogICAgICAgIHRoaXMuYW5pbWF0ZSgpOwogICAgICB9LAoKICAgICAgb25BbmltYXRpb25Db21wbGV0ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fYW5pbWF0aW5nID0gZmFsc2U7CiAgICAgICAgdGhpcy4kLmJhY2tncm91bmQuc3R5bGUuYmFja2dyb3VuZENvbG9yID0gJyc7CiAgICAgICAgdGhpcy5maXJlKCd0cmFuc2l0aW9uZW5kJyk7CiAgICAgIH0sCgogICAgICBhZGRSaXBwbGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciByaXBwbGUgPSBuZXcgUmlwcGxlKHRoaXMpOwoKICAgICAgICBkb20odGhpcy4kLndhdmVzKS5hcHBlbmRDaGlsZChyaXBwbGUud2F2ZUNvbnRhaW5lcik7CiAgICAgICAgdGhpcy4kLmJhY2tncm91bmQuc3R5bGUuYmFja2dyb3VuZENvbG9yID0gcmlwcGxlLmNvbG9yOwogICAgICAgIHRoaXMucmlwcGxlcy5wdXNoKHJpcHBsZSk7CgogICAgICAgIHRoaXMuX3NldEFuaW1hdGluZyh0cnVlKTsKCiAgICAgICAgcmV0dXJuIHJpcHBsZTsKICAgICAgfSwKCiAgICAgIHJlbW92ZVJpcHBsZTogZnVuY3Rpb24ocmlwcGxlKSB7CiAgICAgICAgdmFyIHJpcHBsZUluZGV4ID0gdGhpcy5yaXBwbGVzLmluZGV4T2YocmlwcGxlKTsKCiAgICAgICAgaWYgKHJpcHBsZUluZGV4IDwgMCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5yaXBwbGVzLnNwbGljZShyaXBwbGVJbmRleCwgMSk7CgogICAgICAgIHJpcHBsZS5yZW1vdmUoKTsKCiAgICAgICAgaWYgKCF0aGlzLnJpcHBsZXMubGVuZ3RoKSB7CiAgICAgICAgICB0aGlzLl9zZXRBbmltYXRpbmcoZmFsc2UpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBEZXByZWNhdGVkLiBQbGVhc2UgdXNlIGFuaW1hdGVSaXBwbGUoKSBpbnN0ZWFkLgogICAgICAgKgogICAgICAgKiBUaGlzIG1ldGhvZCBuYW1lIGNvbmZsaWN0cyB3aXRoIEVsZW1lbnQjYW5pbWF0ZSgpLgogICAgICAgKiBodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9BUEkvRWxlbWVudC9hbmltYXRlLgogICAgICAgKgogICAgICAgKiBAc3VwcHJlc3Mge2NoZWNrVHlwZXN9CiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgYW5pbWF0ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLl9hbmltYXRpbmcpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdmFyIGluZGV4OwogICAgICAgIHZhciByaXBwbGU7CgogICAgICAgIGZvciAoaW5kZXggPSAwOyBpbmRleCA8IHRoaXMucmlwcGxlcy5sZW5ndGg7ICsraW5kZXgpIHsKICAgICAgICAgIHJpcHBsZSA9IHRoaXMucmlwcGxlc1tpbmRleF07CgogICAgICAgICAgcmlwcGxlLmRyYXcoKTsKCiAgICAgICAgICB0aGlzLiQuYmFja2dyb3VuZC5zdHlsZS5vcGFjaXR5ID0gcmlwcGxlLm91dGVyT3BhY2l0eTsKCiAgICAgICAgICBpZiAocmlwcGxlLmlzT3BhY2l0eUZ1bGx5RGVjYXllZCAmJiAhcmlwcGxlLmlzUmVzdGluZ0F0TWF4UmFkaXVzKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlUmlwcGxlKHJpcHBsZSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAoIXRoaXMuc2hvdWxkS2VlcEFuaW1hdGluZyAmJiB0aGlzLnJpcHBsZXMubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICB0aGlzLm9uQW5pbWF0aW9uQ29tcGxldGUoKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSh0aGlzLl9ib3VuZEFuaW1hdGUpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBbiBhbGlhcyBmb3IgYW5pbWF0ZSgpIHdob3NlIG5hbWUgZG9lcyBub3QgY29uZmxpY3Qgd2l0aCB0aGUgcGxhdGZvcm0KICAgICAgICogRWxlbWVudC5hbmltYXRlKCkgbWV0aG9kLgogICAgICAgKi8KICAgICAgYW5pbWF0ZVJpcHBsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuYW5pbWF0ZSgpOwogICAgICB9LAoKICAgICAgX29uRW50ZXJLZXlkb3duOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnVpRG93bkFjdGlvbigpOwogICAgICAgIHRoaXMuYXN5bmModGhpcy51aVVwQWN0aW9uLCAxKTsKICAgICAgfSwKCiAgICAgIF9vblNwYWNlS2V5ZG93bjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy51aURvd25BY3Rpb24oKTsKICAgICAgfSwKCiAgICAgIF9vblNwYWNlS2V5dXA6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudWlVcEFjdGlvbigpOwogICAgICB9LAoKICAgICAgLy8gbm90ZTogaG9sZERvd24gZG9lcyBub3QgcmVzcGVjdCBub2luayBzaW5jZSBpdCBjYW4gYmUgYSBmb2N1cyBiYXNlZAogICAgICAvLyBlZmZlY3QuCiAgICAgIF9ob2xkRG93bkNoYW5nZWQ6IGZ1bmN0aW9uKG5ld1ZhbCwgb2xkVmFsKSB7CiAgICAgICAgaWYgKG9sZFZhbCA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlmIChuZXdWYWwpIHsKICAgICAgICAgIHRoaXMuZG93bkFjdGlvbigpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnVwQWN0aW9uKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgRmlyZWQgd2hlbiB0aGUgYW5pbWF0aW9uIGZpbmlzaGVzLgogICAgICBUaGlzIGlzIHVzZWZ1bCBpZiB5b3Ugd2FudCB0byB3YWl0IHVudGlsCiAgICAgIHRoZSByaXBwbGUgYW5pbWF0aW9uIGZpbmlzaGVzIHRvIHBlcmZvcm0gc29tZSBhY3Rpb24uCgogICAgICBAZXZlbnQgdHJhbnNpdGlvbmVuZAogICAgICBAcGFyYW0ge3tub2RlOiBPYmplY3R9fSBkZXRhaWwgQ29udGFpbnMgdGhlIGFuaW1hdGVkIG5vZGUuCiAgICAgICovCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIGBQYXBlclJpcHBsZUJlaGF2aW9yYCBkeW5hbWljYWxseSBpbXBsZW1lbnRzIGEgcmlwcGxlIHdoZW4gdGhlIGVsZW1lbnQgaGFzCiAgICAgKiBmb2N1cyB2aWEgcG9pbnRlciBvciBrZXlib2FyZC4KICAgICAqCiAgICAgKiBOT1RFOiBUaGlzIGJlaGF2aW9yIGlzIGludGVuZGVkIHRvIGJlIHVzZWQgaW4gY29uanVuY3Rpb24gd2l0aCBhbmQgYWZ0ZXIKICAgICAqIGBJcm9uQnV0dG9uU3RhdGVgIGFuZCBgSXJvbkNvbnRyb2xTdGF0ZWAuCiAgICAgKgogICAgICogQHBvbHltZXJCZWhhdmlvciBQYXBlclJpcHBsZUJlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IFBhcGVyUmlwcGxlQmVoYXZpb3IgPSB7CiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgZWxlbWVudCB3aWxsIG5vdCBwcm9kdWNlIGEgcmlwcGxlIGVmZmVjdCB3aGVuIGludGVyYWN0ZWQKICAgICAgICAgKiB3aXRoIHZpYSB0aGUgcG9pbnRlci4KICAgICAgICAgKi8KICAgICAgICBub2luazoge3R5cGU6IEJvb2xlYW4sIG9ic2VydmVyOiAnX25vaW5rQ2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBAdHlwZSB7RWxlbWVudHx1bmRlZmluZWR9CiAgICAgICAgICovCiAgICAgICAgX3JpcHBsZUNvbnRhaW5lcjogewogICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBFbnN1cmVzIGEgYDxwYXBlci1yaXBwbGU+YCBlbGVtZW50IGlzIGF2YWlsYWJsZSB3aGVuIHRoZSBlbGVtZW50IGlzCiAgICAgICAqIGZvY3VzZWQuCiAgICAgICAqLwogICAgICBfYnV0dG9uU3RhdGVDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5mb2N1c2VkKSB7CiAgICAgICAgICB0aGlzLmVuc3VyZVJpcHBsZSgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBJbiBhZGRpdGlvbiB0byB0aGUgZnVuY3Rpb25hbGl0eSBwcm92aWRlZCBpbiBgSXJvbkJ1dHRvblN0YXRlYCwgZW5zdXJlcwogICAgICAgKiBhIHJpcHBsZSBlZmZlY3QgaXMgY3JlYXRlZCB3aGVuIHRoZSBlbGVtZW50IGlzIGluIGEgYHByZXNzZWRgIHN0YXRlLgogICAgICAgKi8KICAgICAgX2Rvd25IYW5kbGVyOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIElyb25CdXR0b25TdGF0ZUltcGwuX2Rvd25IYW5kbGVyLmNhbGwodGhpcywgZXZlbnQpOwogICAgICAgIGlmICh0aGlzLnByZXNzZWQpIHsKICAgICAgICAgIHRoaXMuZW5zdXJlUmlwcGxlKGV2ZW50KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRW5zdXJlcyB0aGlzIGVsZW1lbnQgY29udGFpbnMgYSByaXBwbGUgZWZmZWN0LiBGb3Igc3RhcnR1cCBlZmZpY2llbmN5CiAgICAgICAqIHRoZSByaXBwbGUgZWZmZWN0IGlzIGR5bmFtaWNhbGx5IG9uIGRlbWFuZCB3aGVuIG5lZWRlZC4KICAgICAgICogQHBhcmFtIHshRXZlbnQ9fSBvcHRUcmlnZ2VyaW5nRXZlbnQgKG9wdGlvbmFsKSBldmVudCB0aGF0IHRyaWdnZXJlZCB0aGUKICAgICAgICogcmlwcGxlLgogICAgICAgKi8KICAgICAgZW5zdXJlUmlwcGxlOiBmdW5jdGlvbihvcHRUcmlnZ2VyaW5nRXZlbnQpIHsKICAgICAgICBpZiAoIXRoaXMuaGFzUmlwcGxlKCkpIHsKICAgICAgICAgIHRoaXMuX3JpcHBsZSA9IHRoaXMuX2NyZWF0ZVJpcHBsZSgpOwogICAgICAgICAgdGhpcy5fcmlwcGxlLm5vaW5rID0gdGhpcy5ub2luazsKICAgICAgICAgIHZhciByaXBwbGVDb250YWluZXIgPSB0aGlzLl9yaXBwbGVDb250YWluZXIgfHwgdGhpcy5yb290OwogICAgICAgICAgaWYgKHJpcHBsZUNvbnRhaW5lcikgewogICAgICAgICAgICBkb20ocmlwcGxlQ29udGFpbmVyKS5hcHBlbmRDaGlsZCh0aGlzLl9yaXBwbGUpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKG9wdFRyaWdnZXJpbmdFdmVudCkgewogICAgICAgICAgICAvLyBDaGVjayBpZiB0aGUgZXZlbnQgaGFwcGVuZWQgaW5zaWRlIG9mIHRoZSByaXBwbGUgY29udGFpbmVyCiAgICAgICAgICAgIC8vIEZhbGwgYmFjayB0byBob3N0IGluc3RlYWQgb2YgdGhlIHJvb3QgYmVjYXVzZSBkaXN0cmlidXRlZCB0ZXh0CiAgICAgICAgICAgIC8vIG5vZGVzIGFyZSBub3QgdmFsaWQgZXZlbnQgdGFyZ2V0cwogICAgICAgICAgICB2YXIgZG9tQ29udGFpbmVyID0gZG9tKHRoaXMuX3JpcHBsZUNvbnRhaW5lciB8fCB0aGlzKTsKICAgICAgICAgICAgdmFyIHRhcmdldCA9IGRvbShvcHRUcmlnZ2VyaW5nRXZlbnQpLnJvb3RUYXJnZXQ7CiAgICAgICAgICAgIGlmIChkb21Db250YWluZXIuZGVlcENvbnRhaW5zKC8qKiBAdHlwZSB7Tm9kZX0gKi8gKHRhcmdldCkpKSB7CiAgICAgICAgICAgICAgdGhpcy5fcmlwcGxlLnVpRG93bkFjdGlvbihvcHRUcmlnZ2VyaW5nRXZlbnQpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIGA8cGFwZXItcmlwcGxlPmAgZWxlbWVudCB1c2VkIGJ5IHRoaXMgZWxlbWVudCB0byBjcmVhdGUKICAgICAgICogcmlwcGxlIGVmZmVjdHMuIFRoZSBlbGVtZW50J3MgcmlwcGxlIGlzIGNyZWF0ZWQgb24gZGVtYW5kLCB3aGVuCiAgICAgICAqIG5lY2Vzc2FyeSwgYW5kIGNhbGxpbmcgdGhpcyBtZXRob2Qgd2lsbCBmb3JjZSB0aGUKICAgICAgICogcmlwcGxlIHRvIGJlIGNyZWF0ZWQuCiAgICAgICAqLwogICAgICBnZXRSaXBwbGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuZW5zdXJlUmlwcGxlKCk7CiAgICAgICAgcmV0dXJuIHRoaXMuX3JpcHBsZTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhpcyBlbGVtZW50IGN1cnJlbnRseSBjb250YWlucyBhIHJpcHBsZSBlZmZlY3QuCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgICAqLwogICAgICBoYXNSaXBwbGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBCb29sZWFuKHRoaXMuX3JpcHBsZSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ3JlYXRlIHRoZSBlbGVtZW50J3MgcmlwcGxlIGVmZmVjdCB2aWEgY3JlYXRpbmcgYSBgPHBhcGVyLXJpcHBsZT5gLgogICAgICAgKiBPdmVycmlkZSB0aGlzIG1ldGhvZCB0byBjdXN0b21pemUgdGhlIHJpcHBsZSBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshUGFwZXJSaXBwbGVFbGVtZW50fSBSZXR1cm5zIGEgYDxwYXBlci1yaXBwbGU+YCBlbGVtZW50LgogICAgICAgKi8KICAgICAgX2NyZWF0ZVJpcHBsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGVsZW1lbnQgPSAvKiogQHR5cGUgeyFQYXBlclJpcHBsZUVsZW1lbnR9ICovICgKICAgICAgICAgICAgZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgncGFwZXItcmlwcGxlJykpOwogICAgICAgIHJldHVybiBlbGVtZW50OwogICAgICB9LAoKICAgICAgX25vaW5rQ2hhbmdlZDogZnVuY3Rpb24obm9pbmspIHsKICAgICAgICBpZiAodGhpcy5oYXNSaXBwbGUoKSkgewogICAgICAgICAgdGhpcy5fcmlwcGxlLm5vaW5rID0gbm9pbms7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKiBAcG9seW1lckJlaGF2aW9yIFBhcGVyQnV0dG9uQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVyQnV0dG9uQmVoYXZpb3JJbXBsID0gewogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIHotZGVwdGggb2YgdGhpcyBlbGVtZW50LCBmcm9tIDAtNS4gU2V0dGluZyB0byAwIHdpbGwgcmVtb3ZlIHRoZQogICAgICAgICAqIHNoYWRvdywgYW5kIGVhY2ggaW5jcmVhc2luZyBudW1iZXIgZ3JlYXRlciB0aGFuIDAgd2lsbCBiZSAiZGVlcGVyIgogICAgICAgICAqIHRoYW4gdGhlIGxhc3QuCiAgICAgICAgICoKICAgICAgICAgKiBAYXR0cmlidXRlIGVsZXZhdGlvbgogICAgICAgICAqIEB0eXBlIG51bWJlcgogICAgICAgICAqIEBkZWZhdWx0IDEKICAgICAgICAgKi8KICAgICAgICBlbGV2YXRpb246IHt0eXBlOiBOdW1iZXIsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwgcmVhZE9ubHk6IHRydWV9CiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6IFsKICAgICAgICAnX2NhbGN1bGF0ZUVsZXZhdGlvbihmb2N1c2VkLCBkaXNhYmxlZCwgYWN0aXZlLCBwcmVzc2VkLCByZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKScsCiAgICAgICAgJ19jb21wdXRlS2V5Ym9hcmRDbGFzcyhyZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKScKICAgICAgXSwKCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ2J1dHRvbicsIHRhYmluZGV4OiAnMCcsIGFuaW1hdGVkOiB0cnVlfSwKCiAgICAgIF9jYWxjdWxhdGVFbGV2YXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBlID0gMTsKICAgICAgICBpZiAodGhpcy5kaXNhYmxlZCkgewogICAgICAgICAgZSA9IDA7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLmFjdGl2ZSB8fCB0aGlzLnByZXNzZWQpIHsKICAgICAgICAgIGUgPSA0OwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5yZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKSB7CiAgICAgICAgICBlID0gMzsKICAgICAgICB9CiAgICAgICAgdGhpcy5fc2V0RWxldmF0aW9uKGUpOwogICAgICB9LAoKICAgICAgX2NvbXB1dGVLZXlib2FyZENsYXNzOiBmdW5jdGlvbihyZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKSB7CiAgICAgICAgdGhpcy50b2dnbGVDbGFzcygna2V5Ym9hcmQtZm9jdXMnLCByZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBJbiBhZGRpdGlvbiB0byBgSXJvbkJ1dHRvblN0YXRlYCBiZWhhdmlvciwgd2hlbiBzcGFjZSBrZXkgZ29lcyBkb3duLAogICAgICAgKiBjcmVhdGUgYSByaXBwbGUgZG93biBlZmZlY3QuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUtleWJvYXJkRXZlbnR9IGV2ZW50IC4KICAgICAgICovCiAgICAgIF9zcGFjZUtleURvd25IYW5kbGVyOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIElyb25CdXR0b25TdGF0ZUltcGwuX3NwYWNlS2V5RG93bkhhbmRsZXIuY2FsbCh0aGlzLCBldmVudCk7CiAgICAgICAgLy8gRW5zdXJlIHRoYXQgdGhlcmUgaXMgYXQgbW9zdCBvbmUgcmlwcGxlIHdoZW4gdGhlIHNwYWNlIGtleSBpcyBoZWxkIGRvd24uCiAgICAgICAgaWYgKHRoaXMuaGFzUmlwcGxlKCkgJiYgdGhpcy5nZXRSaXBwbGUoKS5yaXBwbGVzLmxlbmd0aCA8IDEpIHsKICAgICAgICAgIHRoaXMuX3JpcHBsZS51aURvd25BY3Rpb24oKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSW4gYWRkaXRpb24gdG8gYElyb25CdXR0b25TdGF0ZWAgYmVoYXZpb3IsIHdoZW4gc3BhY2Uga2V5IGdvZXMgdXAsCiAgICAgICAqIGNyZWF0ZSBhIHJpcHBsZSB1cCBlZmZlY3QuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IUtleWJvYXJkRXZlbnR9IGV2ZW50IC4KICAgICAgICovCiAgICAgIF9zcGFjZUtleVVwSGFuZGxlcjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBJcm9uQnV0dG9uU3RhdGVJbXBsLl9zcGFjZUtleVVwSGFuZGxlci5jYWxsKHRoaXMsIGV2ZW50KTsKICAgICAgICBpZiAodGhpcy5oYXNSaXBwbGUoKSkgewogICAgICAgICAgdGhpcy5fcmlwcGxlLnVpVXBBY3Rpb24oKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVyQnV0dG9uQmVoYXZpb3IgPSBbCiAgICAgIElyb25CdXR0b25TdGF0ZSwKICAgICAgSXJvbkNvbnRyb2xTdGF0ZSwKICAgICAgUGFwZXJSaXBwbGVCZWhhdmlvciwKICAgICAgUGFwZXJCdXR0b25CZWhhdmlvckltcGwKICAgIF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgdGVtcGxhdGUkNiA9IGh0bWxgCiAgPHN0eWxlIGluY2x1ZGU9InBhcGVyLW1hdGVyaWFsLXN0eWxlcyI+CiAgICAvKiBOZWVkIHRvIHNwZWNpZnkgdGhlIHNhbWUgc3BlY2lmaWNpdHkgYXMgdGhlIHN0eWxlcyBpbXBvcnRlZCBmcm9tIHBhcGVyLW1hdGVyaWFsLiAqLwogICAgOmhvc3QgewogICAgICBAYXBwbHkgLS1sYXlvdXQtaW5saW5lOwogICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyLWNlbnRlcjsKICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICBtaW4td2lkdGg6IDUuMTRlbTsKICAgICAgbWFyZ2luOiAwIDAuMjllbTsKICAgICAgYmFja2dyb3VuZDogdHJhbnNwYXJlbnQ7CiAgICAgIC13ZWJraXQtdGFwLWhpZ2hsaWdodC1jb2xvcjogcmdiYSgwLCAwLCAwLCAwKTsKICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKICAgICAgZm9udDogaW5oZXJpdDsKICAgICAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTsKICAgICAgb3V0bGluZS13aWR0aDogMDsKICAgICAgYm9yZGVyLXJhZGl1czogM3B4OwogICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgIC13ZWJraXQtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgIHVzZXItc2VsZWN0OiBub25lOwogICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgIHotaW5kZXg6IDA7CiAgICAgIHBhZGRpbmc6IDAuN2VtIDAuNTdlbTsKCiAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgIEBhcHBseSAtLXBhcGVyLWJ1dHRvbjsKICAgIH0KCiAgICA6aG9zdChbZWxldmF0aW9uPSIxIl0pIHsKICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTE7CiAgICB9CgogICAgOmhvc3QoW2VsZXZhdGlvbj0iMiJdKSB7CiAgICAgIEBhcHBseSAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi0yOwogICAgfQoKICAgIDpob3N0KFtlbGV2YXRpb249IjMiXSkgewogICAgICBAYXBwbHkgLS1wYXBlci1tYXRlcmlhbC1lbGV2YXRpb24tMzsKICAgIH0KCiAgICA6aG9zdChbZWxldmF0aW9uPSI0Il0pIHsKICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWwtZWxldmF0aW9uLTQ7CiAgICB9CgogICAgOmhvc3QoW2VsZXZhdGlvbj0iNSJdKSB7CiAgICAgIEBhcHBseSAtLXBhcGVyLW1hdGVyaWFsLWVsZXZhdGlvbi01OwogICAgfQoKICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgIH0KCiAgICA6aG9zdChbcmFpc2VkXS5rZXlib2FyZC1mb2N1cykgewogICAgICBmb250LXdlaWdodDogYm9sZDsKICAgICAgQGFwcGx5IC0tcGFwZXItYnV0dG9uLXJhaXNlZC1rZXlib2FyZC1mb2N1czsKICAgIH0KCiAgICA6aG9zdCg6bm90KFtyYWlzZWRdKS5rZXlib2FyZC1mb2N1cykgewogICAgICBmb250LXdlaWdodDogYm9sZDsKICAgICAgQGFwcGx5IC0tcGFwZXItYnV0dG9uLWZsYXQta2V5Ym9hcmQtZm9jdXM7CiAgICB9CgogICAgOmhvc3QoW2Rpc2FibGVkXSkgewogICAgICBiYWNrZ3JvdW5kOiBub25lOwogICAgICBjb2xvcjogI2E4YThhODsKICAgICAgY3Vyc29yOiBhdXRvOwogICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKCiAgICAgIEBhcHBseSAtLXBhcGVyLWJ1dHRvbi1kaXNhYmxlZDsKICAgIH0KCiAgICA6aG9zdChbZGlzYWJsZWRdW3JhaXNlZF0pIHsKICAgICAgYmFja2dyb3VuZDogI2VhZWFlYTsKICAgIH0KCgogICAgOmhvc3QoW2FuaW1hdGVkXSkgewogICAgICBAYXBwbHkgLS1zaGFkb3ctdHJhbnNpdGlvbjsKICAgIH0KCiAgICBwYXBlci1yaXBwbGUgewogICAgICBjb2xvcjogdmFyKC0tcGFwZXItYnV0dG9uLWluay1jb2xvcik7CiAgICB9CiAgPC9zdHlsZT4KCiAgPHNsb3Q+PC9zbG90PmA7CgogICAgdGVtcGxhdGUkNi5zZXRBdHRyaWJ1dGUoJ3N0cmlwLXdoaXRlc3BhY2UnLCAnJyk7CgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbQnV0dG9uc10oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL2J1dHRvbnMuaHRtbCkKCiAgICBgcGFwZXItYnV0dG9uYCBpcyBhIGJ1dHRvbi4gV2hlbiB0aGUgdXNlciB0b3VjaGVzIHRoZSBidXR0b24sIGEgcmlwcGxlIGVmZmVjdAogICAgZW1hbmF0ZXMgZnJvbSB0aGUgcG9pbnQgb2YgY29udGFjdC4gSXQgbWF5IGJlIGZsYXQgb3IgcmFpc2VkLiBBIHJhaXNlZCBidXR0b24gaXMKICAgIHN0eWxlZCB3aXRoIGEgc2hhZG93LgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1idXR0b24+RmxhdCBidXR0b248L3BhcGVyLWJ1dHRvbj4KICAgICAgICA8cGFwZXItYnV0dG9uIHJhaXNlZD5SYWlzZWQgYnV0dG9uPC9wYXBlci1idXR0b24+CiAgICAgICAgPHBhcGVyLWJ1dHRvbiBub2luaz5ObyByaXBwbGUgZWZmZWN0PC9wYXBlci1idXR0b24+CiAgICAgICAgPHBhcGVyLWJ1dHRvbiB0b2dnbGVzPlRvZ2dsZS1hYmxlIGJ1dHRvbjwvcGFwZXItYnV0dG9uPgoKICAgIEEgYnV0dG9uIHRoYXQgaGFzIGB0b2dnbGVzYCB0cnVlIHdpbGwgcmVtYWluIGBhY3RpdmVgIGFmdGVyIGJlaW5nIGNsaWNrZWQgKGFuZAogICAgd2lsbCBoYXZlIGFuIGBhY3RpdmVgIGF0dHJpYnV0ZSBzZXQpLiBGb3IgbW9yZSBpbmZvcm1hdGlvbiwgc2VlIHRoZQogICAgYElyb25CdXR0b25TdGF0ZWAgYmVoYXZpb3IuCgogICAgWW91IG1heSB1c2UgY3VzdG9tIERPTSBpbiB0aGUgYnV0dG9uIGJvZHkgdG8gY3JlYXRlIGEgdmFyaWV0eSBvZiBidXR0b25zLiBGb3IKICAgIGV4YW1wbGUsIHRvIGNyZWF0ZSBhIGJ1dHRvbiB3aXRoIGFuIGljb24gYW5kIHNvbWUgdGV4dDoKCiAgICAgICAgPHBhcGVyLWJ1dHRvbj4KICAgICAgICAgIDxpcm9uLWljb24gaWNvbj0iZmF2b3JpdGUiPjwvaXJvbi1pY29uPgogICAgICAgICAgY3VzdG9tIGJ1dHRvbiBjb250ZW50CiAgICAgICAgPC9wYXBlci1idXR0b24+CgogICAgVG8gdXNlIGBwYXBlci1idXR0b25gIGFzIGEgbGluaywgd3JhcCBpdCBpbiBhbiBhbmNob3IgdGFnLiBTaW5jZSBgcGFwZXItYnV0dG9uYAogICAgd2lsbCBhbHJlYWR5IHJlY2VpdmUgZm9jdXMsIHlvdSBtYXkgd2FudCB0byBwcmV2ZW50IHRoZSBhbmNob3IgdGFnIGZyb20KICAgIHJlY2VpdmluZyBmb2N1cyBhcyB3ZWxsIGJ5IHNldHRpbmcgaXRzIHRhYmluZGV4IHRvIC0xLgoKICAgICAgICA8YSBocmVmPSJodHRwczovL3d3dy5wb2x5bWVyLXByb2plY3Qub3JnLyIgdGFiaW5kZXg9Ii0xIj4KICAgICAgICAgIDxwYXBlci1idXR0b24gcmFpc2VkPlBvbHltZXIgUHJvamVjdDwvcGFwZXItYnV0dG9uPgogICAgICAgIDwvYT4KCiAgICAjIyMgU3R5bGluZwoKICAgIFN0eWxlIHRoZSBidXR0b24gd2l0aCBDU1MgYXMgeW91IHdvdWxkIGEgbm9ybWFsIERPTSBlbGVtZW50LgoKICAgICAgICBwYXBlci1idXR0b24uZmFuY3kgewogICAgICAgICAgYmFja2dyb3VuZDogZ3JlZW47CiAgICAgICAgICBjb2xvcjogeWVsbG93OwogICAgICAgIH0KCiAgICAgICAgcGFwZXItYnV0dG9uLmZhbmN5OmhvdmVyIHsKICAgICAgICAgIGJhY2tncm91bmQ6IGxpbWU7CiAgICAgICAgfQoKICAgICAgICBwYXBlci1idXR0b25bZGlzYWJsZWRdLAogICAgICAgIHBhcGVyLWJ1dHRvblt0b2dnbGVzXVthY3RpdmVdIHsKICAgICAgICAgIGJhY2tncm91bmQ6IHJlZDsKICAgICAgICB9CgogICAgQnkgZGVmYXVsdCwgdGhlIHJpcHBsZSBpcyB0aGUgc2FtZSBjb2xvciBhcyB0aGUgZm9yZWdyb3VuZCBhdCAyNSUgb3BhY2l0eS4gWW91CiAgICBtYXkgY3VzdG9taXplIHRoZSBjb2xvciB1c2luZyB0aGUgYC0tcGFwZXItYnV0dG9uLWluay1jb2xvcmAgY3VzdG9tIHByb3BlcnR5LgoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYWxzbyBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItYnV0dG9uLWluay1jb2xvcmAgfCBCYWNrZ3JvdW5kIGNvbG9yIG9mIHRoZSByaXBwbGUgfCBgQmFzZWQgb24gdGhlIGJ1dHRvbidzIGNvbG9yYAogICAgYC0tcGFwZXItYnV0dG9uYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGJ1dHRvbiB8IGB7fWAKICAgIGAtLXBhcGVyLWJ1dHRvbi1kaXNhYmxlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBkaXNhYmxlZCBidXR0b24uIE5vdGUgdGhhdCB5b3UgY2FuIGFsc28gdXNlIHRoZSBgcGFwZXItYnV0dG9uW2Rpc2FibGVkXWAgc2VsZWN0b3IgfCBge31gCiAgICBgLS1wYXBlci1idXR0b24tZmxhdC1rZXlib2FyZC1mb2N1c2AgfCBNaXhpbiBhcHBsaWVkIHRvIGEgZmxhdCBidXR0b24gYWZ0ZXIgaXQncyBiZWVuIGZvY3VzZWQgdXNpbmcgdGhlIGtleWJvYXJkIHwgYHt9YAogICAgYC0tcGFwZXItYnV0dG9uLXJhaXNlZC1rZXlib2FyZC1mb2N1c2AgfCBNaXhpbiBhcHBsaWVkIHRvIGEgcmFpc2VkIGJ1dHRvbiBhZnRlciBpdCdzIGJlZW4gZm9jdXNlZCB1c2luZyB0aGUga2V5Ym9hcmQgfCBge31gCgogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogdGVtcGxhdGUkNiwKCiAgICAgIGlzOiAncGFwZXItYnV0dG9uJywKCiAgICAgIGJlaGF2aW9yczogW1BhcGVyQnV0dG9uQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHRoZSBidXR0b24gc2hvdWxkIGJlIHN0eWxlZCB3aXRoIGEgc2hhZG93LgogICAgICAgICAqLwogICAgICAgIHJhaXNlZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIG9ic2VydmVyOiAnX2NhbGN1bGF0ZUVsZXZhdGlvbicsCiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2NhbGN1bGF0ZUVsZXZhdGlvbjogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLnJhaXNlZCkgewogICAgICAgICAgdGhpcy5fc2V0RWxldmF0aW9uKDApOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBQYXBlckJ1dHRvbkJlaGF2aW9ySW1wbC5fY2FsY3VsYXRlRWxldmF0aW9uLmFwcGx5KHRoaXMpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgIEZpcmVkIHdoZW4gdGhlIGFuaW1hdGlvbiBmaW5pc2hlcy4KICAgICAgVGhpcyBpcyB1c2VmdWwgaWYgeW91IHdhbnQgdG8gd2FpdCB1bnRpbAogICAgICB0aGUgcmlwcGxlIGFuaW1hdGlvbiBmaW5pc2hlcyB0byBwZXJmb3JtIHNvbWUgYWN0aW9uLgoKICAgICAgQGV2ZW50IHRyYW5zaXRpb25lbmQKICAgICAgRXZlbnQgcGFyYW06IHt7bm9kZTogT2JqZWN0fX0gZGV0YWlsIENvbnRhaW5zIHRoZSBhbmltYXRlZCBub2RlLgogICAgICAqLwogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICBjb25zdCB0ZW1wbGF0ZSQ3ID0gaHRtbGAKPGN1c3RvbS1zdHlsZT4KICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSI+CiAgICBodG1sIHsKCiAgICAgIC8qIE1hdGVyaWFsIERlc2lnbiBjb2xvciBwYWxldHRlIGZvciBHb29nbGUgcHJvZHVjdHMgKi8KCiAgICAgIC0tZ29vZ2xlLXJlZC0xMDA6ICNmNGM3YzM7CiAgICAgIC0tZ29vZ2xlLXJlZC0zMDA6ICNlNjdjNzM7CiAgICAgIC0tZ29vZ2xlLXJlZC01MDA6ICNkYjQ0Mzc7CiAgICAgIC0tZ29vZ2xlLXJlZC03MDA6ICNjNTM5Mjk7CgogICAgICAtLWdvb2dsZS1ibHVlLTEwMDogI2M2ZGFmYzsKICAgICAgLS1nb29nbGUtYmx1ZS0zMDA6ICM3YmFhZjc7CiAgICAgIC0tZ29vZ2xlLWJsdWUtNTAwOiAjNDI4NWY0OwogICAgICAtLWdvb2dsZS1ibHVlLTcwMDogIzMzNjdkNjsKCiAgICAgIC0tZ29vZ2xlLWdyZWVuLTEwMDogI2I3ZTFjZDsKICAgICAgLS1nb29nbGUtZ3JlZW4tMzAwOiAjNTdiYjhhOwogICAgICAtLWdvb2dsZS1ncmVlbi01MDA6ICMwZjlkNTg7CiAgICAgIC0tZ29vZ2xlLWdyZWVuLTcwMDogIzBiODA0MzsKCiAgICAgIC0tZ29vZ2xlLXllbGxvdy0xMDA6ICNmY2U4YjI7CiAgICAgIC0tZ29vZ2xlLXllbGxvdy0zMDA6ICNmN2NiNGQ7CiAgICAgIC0tZ29vZ2xlLXllbGxvdy01MDA6ICNmNGI0MDA7CiAgICAgIC0tZ29vZ2xlLXllbGxvdy03MDA6ICNmMDkzMDA7CgogICAgICAtLWdvb2dsZS1ncmV5LTEwMDogI2Y1ZjVmNTsKICAgICAgLS1nb29nbGUtZ3JleS0zMDA6ICNlMGUwZTA7CiAgICAgIC0tZ29vZ2xlLWdyZXktNTAwOiAjOWU5ZTllOwogICAgICAtLWdvb2dsZS1ncmV5LTcwMDogIzYxNjE2MTsKCiAgICAgIC8qIE1hdGVyaWFsIERlc2lnbiBjb2xvciBwYWxldHRlIGZyb20gb25saW5lIHNwZWMgZG9jdW1lbnQgKi8KCiAgICAgIC0tcGFwZXItcmVkLTUwOiAjZmZlYmVlOwogICAgICAtLXBhcGVyLXJlZC0xMDA6ICNmZmNkZDI7CiAgICAgIC0tcGFwZXItcmVkLTIwMDogI2VmOWE5YTsKICAgICAgLS1wYXBlci1yZWQtMzAwOiAjZTU3MzczOwogICAgICAtLXBhcGVyLXJlZC00MDA6ICNlZjUzNTA7CiAgICAgIC0tcGFwZXItcmVkLTUwMDogI2Y0NDMzNjsKICAgICAgLS1wYXBlci1yZWQtNjAwOiAjZTUzOTM1OwogICAgICAtLXBhcGVyLXJlZC03MDA6ICNkMzJmMmY7CiAgICAgIC0tcGFwZXItcmVkLTgwMDogI2M2MjgyODsKICAgICAgLS1wYXBlci1yZWQtOTAwOiAjYjcxYzFjOwogICAgICAtLXBhcGVyLXJlZC1hMTAwOiAjZmY4YTgwOwogICAgICAtLXBhcGVyLXJlZC1hMjAwOiAjZmY1MjUyOwogICAgICAtLXBhcGVyLXJlZC1hNDAwOiAjZmYxNzQ0OwogICAgICAtLXBhcGVyLXJlZC1hNzAwOiAjZDUwMDAwOwoKICAgICAgLS1wYXBlci1waW5rLTUwOiAjZmNlNGVjOwogICAgICAtLXBhcGVyLXBpbmstMTAwOiAjZjhiYmQwOwogICAgICAtLXBhcGVyLXBpbmstMjAwOiAjZjQ4ZmIxOwogICAgICAtLXBhcGVyLXBpbmstMzAwOiAjZjA2MjkyOwogICAgICAtLXBhcGVyLXBpbmstNDAwOiAjZWM0MDdhOwogICAgICAtLXBhcGVyLXBpbmstNTAwOiAjZTkxZTYzOwogICAgICAtLXBhcGVyLXBpbmstNjAwOiAjZDgxYjYwOwogICAgICAtLXBhcGVyLXBpbmstNzAwOiAjYzIxODViOwogICAgICAtLXBhcGVyLXBpbmstODAwOiAjYWQxNDU3OwogICAgICAtLXBhcGVyLXBpbmstOTAwOiAjODgwZTRmOwogICAgICAtLXBhcGVyLXBpbmstYTEwMDogI2ZmODBhYjsKICAgICAgLS1wYXBlci1waW5rLWEyMDA6ICNmZjQwODE7CiAgICAgIC0tcGFwZXItcGluay1hNDAwOiAjZjUwMDU3OwogICAgICAtLXBhcGVyLXBpbmstYTcwMDogI2M1MTE2MjsKCiAgICAgIC0tcGFwZXItcHVycGxlLTUwOiAjZjNlNWY1OwogICAgICAtLXBhcGVyLXB1cnBsZS0xMDA6ICNlMWJlZTc7CiAgICAgIC0tcGFwZXItcHVycGxlLTIwMDogI2NlOTNkODsKICAgICAgLS1wYXBlci1wdXJwbGUtMzAwOiAjYmE2OGM4OwogICAgICAtLXBhcGVyLXB1cnBsZS00MDA6ICNhYjQ3YmM7CiAgICAgIC0tcGFwZXItcHVycGxlLTUwMDogIzljMjdiMDsKICAgICAgLS1wYXBlci1wdXJwbGUtNjAwOiAjOGUyNGFhOwogICAgICAtLXBhcGVyLXB1cnBsZS03MDA6ICM3YjFmYTI7CiAgICAgIC0tcGFwZXItcHVycGxlLTgwMDogIzZhMWI5YTsKICAgICAgLS1wYXBlci1wdXJwbGUtOTAwOiAjNGExNDhjOwogICAgICAtLXBhcGVyLXB1cnBsZS1hMTAwOiAjZWE4MGZjOwogICAgICAtLXBhcGVyLXB1cnBsZS1hMjAwOiAjZTA0MGZiOwogICAgICAtLXBhcGVyLXB1cnBsZS1hNDAwOiAjZDUwMGY5OwogICAgICAtLXBhcGVyLXB1cnBsZS1hNzAwOiAjYWEwMGZmOwoKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS01MDogI2VkZTdmNjsKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS0xMDA6ICNkMWM0ZTk7CiAgICAgIC0tcGFwZXItZGVlcC1wdXJwbGUtMjAwOiAjYjM5ZGRiOwogICAgICAtLXBhcGVyLWRlZXAtcHVycGxlLTMwMDogIzk1NzVjZDsKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS00MDA6ICM3ZTU3YzI7CiAgICAgIC0tcGFwZXItZGVlcC1wdXJwbGUtNTAwOiAjNjczYWI3OwogICAgICAtLXBhcGVyLWRlZXAtcHVycGxlLTYwMDogIzVlMzViMTsKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS03MDA6ICM1MTJkYTg7CiAgICAgIC0tcGFwZXItZGVlcC1wdXJwbGUtODAwOiAjNDUyN2EwOwogICAgICAtLXBhcGVyLWRlZXAtcHVycGxlLTkwMDogIzMxMWI5MjsKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS1hMTAwOiAjYjM4OGZmOwogICAgICAtLXBhcGVyLWRlZXAtcHVycGxlLWEyMDA6ICM3YzRkZmY7CiAgICAgIC0tcGFwZXItZGVlcC1wdXJwbGUtYTQwMDogIzY1MWZmZjsKICAgICAgLS1wYXBlci1kZWVwLXB1cnBsZS1hNzAwOiAjNjIwMGVhOwoKICAgICAgLS1wYXBlci1pbmRpZ28tNTA6ICNlOGVhZjY7CiAgICAgIC0tcGFwZXItaW5kaWdvLTEwMDogI2M1Y2FlOTsKICAgICAgLS1wYXBlci1pbmRpZ28tMjAwOiAjOWZhOGRhOwogICAgICAtLXBhcGVyLWluZGlnby0zMDA6ICM3OTg2Y2I7CiAgICAgIC0tcGFwZXItaW5kaWdvLTQwMDogIzVjNmJjMDsKICAgICAgLS1wYXBlci1pbmRpZ28tNTAwOiAjM2Y1MWI1OwogICAgICAtLXBhcGVyLWluZGlnby02MDA6ICMzOTQ5YWI7CiAgICAgIC0tcGFwZXItaW5kaWdvLTcwMDogIzMwM2Y5ZjsKICAgICAgLS1wYXBlci1pbmRpZ28tODAwOiAjMjgzNTkzOwogICAgICAtLXBhcGVyLWluZGlnby05MDA6ICMxYTIzN2U7CiAgICAgIC0tcGFwZXItaW5kaWdvLWExMDA6ICM4YzllZmY7CiAgICAgIC0tcGFwZXItaW5kaWdvLWEyMDA6ICM1MzZkZmU7CiAgICAgIC0tcGFwZXItaW5kaWdvLWE0MDA6ICMzZDVhZmU7CiAgICAgIC0tcGFwZXItaW5kaWdvLWE3MDA6ICMzMDRmZmU7CgogICAgICAtLXBhcGVyLWJsdWUtNTA6ICNlM2YyZmQ7CiAgICAgIC0tcGFwZXItYmx1ZS0xMDA6ICNiYmRlZmI7CiAgICAgIC0tcGFwZXItYmx1ZS0yMDA6ICM5MGNhZjk7CiAgICAgIC0tcGFwZXItYmx1ZS0zMDA6ICM2NGI1ZjY7CiAgICAgIC0tcGFwZXItYmx1ZS00MDA6ICM0MmE1ZjU7CiAgICAgIC0tcGFwZXItYmx1ZS01MDA6ICMyMTk2ZjM7CiAgICAgIC0tcGFwZXItYmx1ZS02MDA6ICMxZTg4ZTU7CiAgICAgIC0tcGFwZXItYmx1ZS03MDA6ICMxOTc2ZDI7CiAgICAgIC0tcGFwZXItYmx1ZS04MDA6ICMxNTY1YzA7CiAgICAgIC0tcGFwZXItYmx1ZS05MDA6ICMwZDQ3YTE7CiAgICAgIC0tcGFwZXItYmx1ZS1hMTAwOiAjODJiMWZmOwogICAgICAtLXBhcGVyLWJsdWUtYTIwMDogIzQ0OGFmZjsKICAgICAgLS1wYXBlci1ibHVlLWE0MDA6ICMyOTc5ZmY7CiAgICAgIC0tcGFwZXItYmx1ZS1hNzAwOiAjMjk2MmZmOwoKICAgICAgLS1wYXBlci1saWdodC1ibHVlLTUwOiAjZTFmNWZlOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtMTAwOiAjYjNlNWZjOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtMjAwOiAjODFkNGZhOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtMzAwOiAjNGZjM2Y3OwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtNDAwOiAjMjliNmY2OwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtNTAwOiAjMDNhOWY0OwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtNjAwOiAjMDM5YmU1OwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtNzAwOiAjMDI4OGQxOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtODAwOiAjMDI3N2JkOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtOTAwOiAjMDE1NzliOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtYTEwMDogIzgwZDhmZjsKICAgICAgLS1wYXBlci1saWdodC1ibHVlLWEyMDA6ICM0MGM0ZmY7CiAgICAgIC0tcGFwZXItbGlnaHQtYmx1ZS1hNDAwOiAjMDBiMGZmOwogICAgICAtLXBhcGVyLWxpZ2h0LWJsdWUtYTcwMDogIzAwOTFlYTsKCiAgICAgIC0tcGFwZXItY3lhbi01MDogI2UwZjdmYTsKICAgICAgLS1wYXBlci1jeWFuLTEwMDogI2IyZWJmMjsKICAgICAgLS1wYXBlci1jeWFuLTIwMDogIzgwZGVlYTsKICAgICAgLS1wYXBlci1jeWFuLTMwMDogIzRkZDBlMTsKICAgICAgLS1wYXBlci1jeWFuLTQwMDogIzI2YzZkYTsKICAgICAgLS1wYXBlci1jeWFuLTUwMDogIzAwYmNkNDsKICAgICAgLS1wYXBlci1jeWFuLTYwMDogIzAwYWNjMTsKICAgICAgLS1wYXBlci1jeWFuLTcwMDogIzAwOTdhNzsKICAgICAgLS1wYXBlci1jeWFuLTgwMDogIzAwODM4ZjsKICAgICAgLS1wYXBlci1jeWFuLTkwMDogIzAwNjA2NDsKICAgICAgLS1wYXBlci1jeWFuLWExMDA6ICM4NGZmZmY7CiAgICAgIC0tcGFwZXItY3lhbi1hMjAwOiAjMThmZmZmOwogICAgICAtLXBhcGVyLWN5YW4tYTQwMDogIzAwZTVmZjsKICAgICAgLS1wYXBlci1jeWFuLWE3MDA6ICMwMGI4ZDQ7CgogICAgICAtLXBhcGVyLXRlYWwtNTA6ICNlMGYyZjE7CiAgICAgIC0tcGFwZXItdGVhbC0xMDA6ICNiMmRmZGI7CiAgICAgIC0tcGFwZXItdGVhbC0yMDA6ICM4MGNiYzQ7CiAgICAgIC0tcGFwZXItdGVhbC0zMDA6ICM0ZGI2YWM7CiAgICAgIC0tcGFwZXItdGVhbC00MDA6ICMyNmE2OWE7CiAgICAgIC0tcGFwZXItdGVhbC01MDA6ICMwMDk2ODg7CiAgICAgIC0tcGFwZXItdGVhbC02MDA6ICMwMDg5N2I7CiAgICAgIC0tcGFwZXItdGVhbC03MDA6ICMwMDc5NmI7CiAgICAgIC0tcGFwZXItdGVhbC04MDA6ICMwMDY5NWM7CiAgICAgIC0tcGFwZXItdGVhbC05MDA6ICMwMDRkNDA7CiAgICAgIC0tcGFwZXItdGVhbC1hMTAwOiAjYTdmZmViOwogICAgICAtLXBhcGVyLXRlYWwtYTIwMDogIzY0ZmZkYTsKICAgICAgLS1wYXBlci10ZWFsLWE0MDA6ICMxZGU5YjY7CiAgICAgIC0tcGFwZXItdGVhbC1hNzAwOiAjMDBiZmE1OwoKICAgICAgLS1wYXBlci1ncmVlbi01MDogI2U4ZjVlOTsKICAgICAgLS1wYXBlci1ncmVlbi0xMDA6ICNjOGU2Yzk7CiAgICAgIC0tcGFwZXItZ3JlZW4tMjAwOiAjYTVkNmE3OwogICAgICAtLXBhcGVyLWdyZWVuLTMwMDogIzgxYzc4NDsKICAgICAgLS1wYXBlci1ncmVlbi00MDA6ICM2NmJiNmE7CiAgICAgIC0tcGFwZXItZ3JlZW4tNTAwOiAjNGNhZjUwOwogICAgICAtLXBhcGVyLWdyZWVuLTYwMDogIzQzYTA0NzsKICAgICAgLS1wYXBlci1ncmVlbi03MDA6ICMzODhlM2M7CiAgICAgIC0tcGFwZXItZ3JlZW4tODAwOiAjMmU3ZDMyOwogICAgICAtLXBhcGVyLWdyZWVuLTkwMDogIzFiNWUyMDsKICAgICAgLS1wYXBlci1ncmVlbi1hMTAwOiAjYjlmNmNhOwogICAgICAtLXBhcGVyLWdyZWVuLWEyMDA6ICM2OWYwYWU7CiAgICAgIC0tcGFwZXItZ3JlZW4tYTQwMDogIzAwZTY3NjsKICAgICAgLS1wYXBlci1ncmVlbi1hNzAwOiAjMDBjODUzOwoKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi01MDogI2YxZjhlOTsKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi0xMDA6ICNkY2VkYzg7CiAgICAgIC0tcGFwZXItbGlnaHQtZ3JlZW4tMjAwOiAjYzVlMWE1OwogICAgICAtLXBhcGVyLWxpZ2h0LWdyZWVuLTMwMDogI2FlZDU4MTsKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi00MDA6ICM5Y2NjNjU7CiAgICAgIC0tcGFwZXItbGlnaHQtZ3JlZW4tNTAwOiAjOGJjMzRhOwogICAgICAtLXBhcGVyLWxpZ2h0LWdyZWVuLTYwMDogIzdjYjM0MjsKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi03MDA6ICM2ODlmMzg7CiAgICAgIC0tcGFwZXItbGlnaHQtZ3JlZW4tODAwOiAjNTU4YjJmOwogICAgICAtLXBhcGVyLWxpZ2h0LWdyZWVuLTkwMDogIzMzNjkxZTsKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi1hMTAwOiAjY2NmZjkwOwogICAgICAtLXBhcGVyLWxpZ2h0LWdyZWVuLWEyMDA6ICNiMmZmNTk7CiAgICAgIC0tcGFwZXItbGlnaHQtZ3JlZW4tYTQwMDogIzc2ZmYwMzsKICAgICAgLS1wYXBlci1saWdodC1ncmVlbi1hNzAwOiAjNjRkZDE3OwoKICAgICAgLS1wYXBlci1saW1lLTUwOiAjZjlmYmU3OwogICAgICAtLXBhcGVyLWxpbWUtMTAwOiAjZjBmNGMzOwogICAgICAtLXBhcGVyLWxpbWUtMjAwOiAjZTZlZTljOwogICAgICAtLXBhcGVyLWxpbWUtMzAwOiAjZGNlNzc1OwogICAgICAtLXBhcGVyLWxpbWUtNDAwOiAjZDRlMTU3OwogICAgICAtLXBhcGVyLWxpbWUtNTAwOiAjY2RkYzM5OwogICAgICAtLXBhcGVyLWxpbWUtNjAwOiAjYzBjYTMzOwogICAgICAtLXBhcGVyLWxpbWUtNzAwOiAjYWZiNDJiOwogICAgICAtLXBhcGVyLWxpbWUtODAwOiAjOWU5ZDI0OwogICAgICAtLXBhcGVyLWxpbWUtOTAwOiAjODI3NzE3OwogICAgICAtLXBhcGVyLWxpbWUtYTEwMDogI2Y0ZmY4MTsKICAgICAgLS1wYXBlci1saW1lLWEyMDA6ICNlZWZmNDE7CiAgICAgIC0tcGFwZXItbGltZS1hNDAwOiAjYzZmZjAwOwogICAgICAtLXBhcGVyLWxpbWUtYTcwMDogI2FlZWEwMDsKCiAgICAgIC0tcGFwZXIteWVsbG93LTUwOiAjZmZmZGU3OwogICAgICAtLXBhcGVyLXllbGxvdy0xMDA6ICNmZmY5YzQ7CiAgICAgIC0tcGFwZXIteWVsbG93LTIwMDogI2ZmZjU5ZDsKICAgICAgLS1wYXBlci15ZWxsb3ctMzAwOiAjZmZmMTc2OwogICAgICAtLXBhcGVyLXllbGxvdy00MDA6ICNmZmVlNTg7CiAgICAgIC0tcGFwZXIteWVsbG93LTUwMDogI2ZmZWIzYjsKICAgICAgLS1wYXBlci15ZWxsb3ctNjAwOiAjZmRkODM1OwogICAgICAtLXBhcGVyLXllbGxvdy03MDA6ICNmYmMwMmQ7CiAgICAgIC0tcGFwZXIteWVsbG93LTgwMDogI2Y5YTgyNTsKICAgICAgLS1wYXBlci15ZWxsb3ctOTAwOiAjZjU3ZjE3OwogICAgICAtLXBhcGVyLXllbGxvdy1hMTAwOiAjZmZmZjhkOwogICAgICAtLXBhcGVyLXllbGxvdy1hMjAwOiAjZmZmZjAwOwogICAgICAtLXBhcGVyLXllbGxvdy1hNDAwOiAjZmZlYTAwOwogICAgICAtLXBhcGVyLXllbGxvdy1hNzAwOiAjZmZkNjAwOwoKICAgICAgLS1wYXBlci1hbWJlci01MDogI2ZmZjhlMTsKICAgICAgLS1wYXBlci1hbWJlci0xMDA6ICNmZmVjYjM7CiAgICAgIC0tcGFwZXItYW1iZXItMjAwOiAjZmZlMDgyOwogICAgICAtLXBhcGVyLWFtYmVyLTMwMDogI2ZmZDU0ZjsKICAgICAgLS1wYXBlci1hbWJlci00MDA6ICNmZmNhMjg7CiAgICAgIC0tcGFwZXItYW1iZXItNTAwOiAjZmZjMTA3OwogICAgICAtLXBhcGVyLWFtYmVyLTYwMDogI2ZmYjMwMDsKICAgICAgLS1wYXBlci1hbWJlci03MDA6ICNmZmEwMDA7CiAgICAgIC0tcGFwZXItYW1iZXItODAwOiAjZmY4ZjAwOwogICAgICAtLXBhcGVyLWFtYmVyLTkwMDogI2ZmNmYwMDsKICAgICAgLS1wYXBlci1hbWJlci1hMTAwOiAjZmZlNTdmOwogICAgICAtLXBhcGVyLWFtYmVyLWEyMDA6ICNmZmQ3NDA7CiAgICAgIC0tcGFwZXItYW1iZXItYTQwMDogI2ZmYzQwMDsKICAgICAgLS1wYXBlci1hbWJlci1hNzAwOiAjZmZhYjAwOwoKICAgICAgLS1wYXBlci1vcmFuZ2UtNTA6ICNmZmYzZTA7CiAgICAgIC0tcGFwZXItb3JhbmdlLTEwMDogI2ZmZTBiMjsKICAgICAgLS1wYXBlci1vcmFuZ2UtMjAwOiAjZmZjYzgwOwogICAgICAtLXBhcGVyLW9yYW5nZS0zMDA6ICNmZmI3NGQ7CiAgICAgIC0tcGFwZXItb3JhbmdlLTQwMDogI2ZmYTcyNjsKICAgICAgLS1wYXBlci1vcmFuZ2UtNTAwOiAjZmY5ODAwOwogICAgICAtLXBhcGVyLW9yYW5nZS02MDA6ICNmYjhjMDA7CiAgICAgIC0tcGFwZXItb3JhbmdlLTcwMDogI2Y1N2MwMDsKICAgICAgLS1wYXBlci1vcmFuZ2UtODAwOiAjZWY2YzAwOwogICAgICAtLXBhcGVyLW9yYW5nZS05MDA6ICNlNjUxMDA7CiAgICAgIC0tcGFwZXItb3JhbmdlLWExMDA6ICNmZmQxODA7CiAgICAgIC0tcGFwZXItb3JhbmdlLWEyMDA6ICNmZmFiNDA7CiAgICAgIC0tcGFwZXItb3JhbmdlLWE0MDA6ICNmZjkxMDA7CiAgICAgIC0tcGFwZXItb3JhbmdlLWE3MDA6ICNmZjY1MDA7CgogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLTUwOiAjZmJlOWU3OwogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLTEwMDogI2ZmY2NiYzsKICAgICAgLS1wYXBlci1kZWVwLW9yYW5nZS0yMDA6ICNmZmFiOTE7CiAgICAgIC0tcGFwZXItZGVlcC1vcmFuZ2UtMzAwOiAjZmY4YTY1OwogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLTQwMDogI2ZmNzA0MzsKICAgICAgLS1wYXBlci1kZWVwLW9yYW5nZS01MDA6ICNmZjU3MjI7CiAgICAgIC0tcGFwZXItZGVlcC1vcmFuZ2UtNjAwOiAjZjQ1MTFlOwogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLTcwMDogI2U2NGExOTsKICAgICAgLS1wYXBlci1kZWVwLW9yYW5nZS04MDA6ICNkODQzMTU7CiAgICAgIC0tcGFwZXItZGVlcC1vcmFuZ2UtOTAwOiAjYmYzNjBjOwogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLWExMDA6ICNmZjllODA7CiAgICAgIC0tcGFwZXItZGVlcC1vcmFuZ2UtYTIwMDogI2ZmNmU0MDsKICAgICAgLS1wYXBlci1kZWVwLW9yYW5nZS1hNDAwOiAjZmYzZDAwOwogICAgICAtLXBhcGVyLWRlZXAtb3JhbmdlLWE3MDA6ICNkZDJjMDA7CgogICAgICAtLXBhcGVyLWJyb3duLTUwOiAjZWZlYmU5OwogICAgICAtLXBhcGVyLWJyb3duLTEwMDogI2Q3Y2NjODsKICAgICAgLS1wYXBlci1icm93bi0yMDA6ICNiY2FhYTQ7CiAgICAgIC0tcGFwZXItYnJvd24tMzAwOiAjYTE4ODdmOwogICAgICAtLXBhcGVyLWJyb3duLTQwMDogIzhkNmU2MzsKICAgICAgLS1wYXBlci1icm93bi01MDA6ICM3OTU1NDg7CiAgICAgIC0tcGFwZXItYnJvd24tNjAwOiAjNmQ0YzQxOwogICAgICAtLXBhcGVyLWJyb3duLTcwMDogIzVkNDAzNzsKICAgICAgLS1wYXBlci1icm93bi04MDA6ICM0ZTM0MmU7CiAgICAgIC0tcGFwZXItYnJvd24tOTAwOiAjM2UyNzIzOwoKICAgICAgLS1wYXBlci1ncmV5LTUwOiAjZmFmYWZhOwogICAgICAtLXBhcGVyLWdyZXktMTAwOiAjZjVmNWY1OwogICAgICAtLXBhcGVyLWdyZXktMjAwOiAjZWVlZWVlOwogICAgICAtLXBhcGVyLWdyZXktMzAwOiAjZTBlMGUwOwogICAgICAtLXBhcGVyLWdyZXktNDAwOiAjYmRiZGJkOwogICAgICAtLXBhcGVyLWdyZXktNTAwOiAjOWU5ZTllOwogICAgICAtLXBhcGVyLWdyZXktNjAwOiAjNzU3NTc1OwogICAgICAtLXBhcGVyLWdyZXktNzAwOiAjNjE2MTYxOwogICAgICAtLXBhcGVyLWdyZXktODAwOiAjNDI0MjQyOwogICAgICAtLXBhcGVyLWdyZXktOTAwOiAjMjEyMTIxOwoKICAgICAgLS1wYXBlci1ibHVlLWdyZXktNTA6ICNlY2VmZjE7CiAgICAgIC0tcGFwZXItYmx1ZS1ncmV5LTEwMDogI2NmZDhkYzsKICAgICAgLS1wYXBlci1ibHVlLWdyZXktMjAwOiAjYjBiZWM1OwogICAgICAtLXBhcGVyLWJsdWUtZ3JleS0zMDA6ICM5MGE0YWU7CiAgICAgIC0tcGFwZXItYmx1ZS1ncmV5LTQwMDogIzc4OTA5YzsKICAgICAgLS1wYXBlci1ibHVlLWdyZXktNTAwOiAjNjA3ZDhiOwogICAgICAtLXBhcGVyLWJsdWUtZ3JleS02MDA6ICM1NDZlN2E7CiAgICAgIC0tcGFwZXItYmx1ZS1ncmV5LTcwMDogIzQ1NWE2NDsKICAgICAgLS1wYXBlci1ibHVlLWdyZXktODAwOiAjMzc0NzRmOwogICAgICAtLXBhcGVyLWJsdWUtZ3JleS05MDA6ICMyNjMyMzg7CgogICAgICAvKiBvcGFjaXR5IGZvciBkYXJrIHRleHQgb24gYSBsaWdodCBiYWNrZ3JvdW5kICovCiAgICAgIC0tZGFyay1kaXZpZGVyLW9wYWNpdHk6IDAuMTI7CiAgICAgIC0tZGFyay1kaXNhYmxlZC1vcGFjaXR5OiAwLjM4OyAvKiBvciBoaW50IHRleHQgb3IgaWNvbiAqLwogICAgICAtLWRhcmstc2Vjb25kYXJ5LW9wYWNpdHk6IDAuNTQ7CiAgICAgIC0tZGFyay1wcmltYXJ5LW9wYWNpdHk6IDAuODc7CgogICAgICAvKiBvcGFjaXR5IGZvciBsaWdodCB0ZXh0IG9uIGEgZGFyayBiYWNrZ3JvdW5kICovCiAgICAgIC0tbGlnaHQtZGl2aWRlci1vcGFjaXR5OiAwLjEyOwogICAgICAtLWxpZ2h0LWRpc2FibGVkLW9wYWNpdHk6IDAuMzsgLyogb3IgaGludCB0ZXh0IG9yIGljb24gKi8KICAgICAgLS1saWdodC1zZWNvbmRhcnktb3BhY2l0eTogMC43OwogICAgICAtLWxpZ2h0LXByaW1hcnktb3BhY2l0eTogMS4wOwoKICAgIH0KCiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+CmA7CiAgICB0ZW1wbGF0ZSQ3LnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkNy5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIGNvbnN0IHRlbXBsYXRlJDggPSBodG1sYAo8Y3VzdG9tLXN0eWxlPgogIDxzdHlsZSBpcz0iY3VzdG9tLXN0eWxlIj4KICAgIGh0bWwgewogICAgICAvKgogICAgICAgKiBZb3UgY2FuIHVzZSB0aGVzZSBnZW5lcmljIHZhcmlhYmxlcyBpbiB5b3VyIGVsZW1lbnRzIGZvciBlYXN5IHRoZW1pbmcuCiAgICAgICAqIEZvciBleGFtcGxlLCBpZiBhbGwgeW91ciBlbGVtZW50cyB1c2UgXGAtLXByaW1hcnktdGV4dC1jb2xvclxgIGFzIGl0cyBtYWluCiAgICAgICAqIGNvbG9yLCB0aGVuIHN3aXRjaGluZyBmcm9tIGEgbGlnaHQgdG8gYSBkYXJrIHRoZW1lIGlzIGp1c3QgYSBtYXR0ZXIgb2YKICAgICAgICogY2hhbmdpbmcgdGhlIHZhbHVlIG9mIFxgLS1wcmltYXJ5LXRleHQtY29sb3JcYCBpbiB5b3VyIGFwcGxpY2F0aW9uLgogICAgICAgKi8KICAgICAgLS1wcmltYXJ5LXRleHQtY29sb3I6IHZhcigtLWxpZ2h0LXRoZW1lLXRleHQtY29sb3IpOwogICAgICAtLXByaW1hcnktYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbGlnaHQtdGhlbWUtYmFja2dyb3VuZC1jb2xvcik7CiAgICAgIC0tc2Vjb25kYXJ5LXRleHQtY29sb3I6IHZhcigtLWxpZ2h0LXRoZW1lLXNlY29uZGFyeS1jb2xvcik7CiAgICAgIC0tZGlzYWJsZWQtdGV4dC1jb2xvcjogdmFyKC0tbGlnaHQtdGhlbWUtZGlzYWJsZWQtY29sb3IpOwogICAgICAtLWRpdmlkZXItY29sb3I6IHZhcigtLWxpZ2h0LXRoZW1lLWRpdmlkZXItY29sb3IpOwogICAgICAtLWVycm9yLWNvbG9yOiB2YXIoLS1wYXBlci1kZWVwLW9yYW5nZS1hNzAwKTsKCiAgICAgIC8qCiAgICAgICAqIFByaW1hcnkgYW5kIGFjY2VudCBjb2xvcnMuIEFsc28gc2VlIGNvbG9yLmpzIGZvciBtb3JlIGNvbG9ycy4KICAgICAgICovCiAgICAgIC0tcHJpbWFyeS1jb2xvcjogdmFyKC0tcGFwZXItaW5kaWdvLTUwMCk7CiAgICAgIC0tbGlnaHQtcHJpbWFyeS1jb2xvcjogdmFyKC0tcGFwZXItaW5kaWdvLTEwMCk7CiAgICAgIC0tZGFyay1wcmltYXJ5LWNvbG9yOiB2YXIoLS1wYXBlci1pbmRpZ28tNzAwKTsKCiAgICAgIC0tYWNjZW50LWNvbG9yOiB2YXIoLS1wYXBlci1waW5rLWEyMDApOwogICAgICAtLWxpZ2h0LWFjY2VudC1jb2xvcjogdmFyKC0tcGFwZXItcGluay1hMTAwKTsKICAgICAgLS1kYXJrLWFjY2VudC1jb2xvcjogdmFyKC0tcGFwZXItcGluay1hNDAwKTsKCgogICAgICAvKgogICAgICAgKiBNYXRlcmlhbCBEZXNpZ24gTGlnaHQgYmFja2dyb3VuZCB0aGVtZQogICAgICAgKi8KICAgICAgLS1saWdodC10aGVtZS1iYWNrZ3JvdW5kLWNvbG9yOiAjZmZmZmZmOwogICAgICAtLWxpZ2h0LXRoZW1lLWJhc2UtY29sb3I6ICMwMDAwMDA7CiAgICAgIC0tbGlnaHQtdGhlbWUtdGV4dC1jb2xvcjogdmFyKC0tcGFwZXItZ3JleS05MDApOwogICAgICAtLWxpZ2h0LXRoZW1lLXNlY29uZGFyeS1jb2xvcjogIzczNzM3MzsgIC8qIGZvciBzZWNvbmRhcnkgdGV4dCBhbmQgaWNvbnMgKi8KICAgICAgLS1saWdodC10aGVtZS1kaXNhYmxlZC1jb2xvcjogIzliOWI5YjsgIC8qIGRpc2FibGVkL2hpbnQgdGV4dCAqLwogICAgICAtLWxpZ2h0LXRoZW1lLWRpdmlkZXItY29sb3I6ICNkYmRiZGI7CgogICAgICAvKgogICAgICAgKiBNYXRlcmlhbCBEZXNpZ24gRGFyayBiYWNrZ3JvdW5kIHRoZW1lCiAgICAgICAqLwogICAgICAtLWRhcmstdGhlbWUtYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItZ3JleS05MDApOwogICAgICAtLWRhcmstdGhlbWUtYmFzZS1jb2xvcjogI2ZmZmZmZjsKICAgICAgLS1kYXJrLXRoZW1lLXRleHQtY29sb3I6ICNmZmZmZmY7CiAgICAgIC0tZGFyay10aGVtZS1zZWNvbmRhcnktY29sb3I6ICNiY2JjYmM7ICAvKiBmb3Igc2Vjb25kYXJ5IHRleHQgYW5kIGljb25zICovCiAgICAgIC0tZGFyay10aGVtZS1kaXNhYmxlZC1jb2xvcjogIzY0NjQ2NDsgIC8qIGRpc2FibGVkL2hpbnQgdGV4dCAqLwogICAgICAtLWRhcmstdGhlbWUtZGl2aWRlci1jb2xvcjogIzNjM2MzYzsKCiAgICAgIC8qCiAgICAgICAqIERlcHJlY2F0ZWQgdmFsdWVzIGJlY2F1c2Ugb2YgdGhlaXIgY29uZnVzaW5nIG5hbWVzLgogICAgICAgKi8KICAgICAgLS10ZXh0LXByaW1hcnktY29sb3I6IHZhcigtLWRhcmstdGhlbWUtdGV4dC1jb2xvcik7CiAgICAgIC0tZGVmYXVsdC1wcmltYXJ5LWNvbG9yOiB2YXIoLS1wcmltYXJ5LWNvbG9yKTsKICAgIH0KICA8L3N0eWxlPgo8L2N1c3RvbS1zdHlsZT5gOwogICAgdGVtcGxhdGUkOC5zZXRBdHRyaWJ1dGUoJ3N0eWxlJywgJ2Rpc3BsYXk6IG5vbmU7Jyk7CiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKHRlbXBsYXRlJDguY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgIElyb25Gb3JtRWxlbWVudEJlaGF2aW9yIGFkZHMgYSBgbmFtZWAsIGB2YWx1ZWAgYW5kIGByZXF1aXJlZGAgcHJvcGVydGllcyB0bwogICAgICBhIGN1c3RvbSBlbGVtZW50LiBJdCBtb3N0bHkgZXhpc3RzIGZvciBiYWNrY29tcGF0aWJpbGl0eSB3aXRoIFBvbHltZXIgMS54LCBhbmQKICAgICAgaXMgcHJvYmFibHkgbm90IHNvbWV0aGluZyB5b3Ugd2FudCB0byB1c2UuCgogICAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAgQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uRm9ybUVsZW1lbnRCZWhhdmlvciA9IHsKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmFtZSBvZiB0aGlzIGVsZW1lbnQuCiAgICAgICAgICovCiAgICAgICAgbmFtZToge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSB2YWx1ZSBmb3IgdGhpcyBlbGVtZW50LgogICAgICAgICAqIEB0eXBlIHsqfQogICAgICAgICAqLwogICAgICAgIHZhbHVlOiB7bm90aWZ5OiB0cnVlLCB0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBtYXJrIHRoZSBpbnB1dCBhcyByZXF1aXJlZC4gSWYgdXNlZCBpbiBhIGZvcm0sIGEKICAgICAgICAgKiBjdXN0b20gZWxlbWVudCB0aGF0IHVzZXMgdGhpcyBiZWhhdmlvciBzaG91bGQgYWxzbyB1c2UKICAgICAgICAgKiBJcm9uVmFsaWRhdGFibGVCZWhhdmlvciBhbmQgZGVmaW5lIGEgY3VzdG9tIHZhbGlkYXRpb24gbWV0aG9kLgogICAgICAgICAqIE90aGVyd2lzZSwgYSBgcmVxdWlyZWRgIGVsZW1lbnQgd2lsbCBhbHdheXMgYmUgY29uc2lkZXJlZCB2YWxpZC4KICAgICAgICAgKiBJdCdzIGFsc28gc3Ryb25nbHkgcmVjb21tZW5kZWQgdG8gcHJvdmlkZSBhIHZpc3VhbCBzdHlsZSBmb3IgdGhlIGVsZW1lbnQKICAgICAgICAgKiB3aGVuIGl0cyB2YWx1ZSBpcyBpbnZhbGlkLgogICAgICAgICAqLwogICAgICAgIHJlcXVpcmVkOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKICAgICAgfSwKCiAgICAgIC8vIEVtcHR5IGltcGxlbWVudGF0aW9ucyBmb3IgYmFja2NvbXBhdGliaWxpdHkuCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHt9LAogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7fQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIFNpbmdsZXRvbiBJcm9uTWV0YSBpbnN0YW5jZS4KICAgICAqLwogICAgbGV0IElyb25WYWxpZGF0YWJsZUJlaGF2aW9yTWV0YSA9IG51bGw7CgogICAgLyoqCiAgICAgKiBgVXNlIElyb25WYWxpZGF0YWJsZUJlaGF2aW9yYCB0byBpbXBsZW1lbnQgYW4gZWxlbWVudCB0aGF0IHZhbGlkYXRlcwogICAgICogdXNlciBpbnB1dC4gVXNlIHRoZSByZWxhdGVkIGBJcm9uVmFsaWRhdG9yQmVoYXZpb3JgIHRvIGFkZCBjdXN0b20KICAgICAqIHZhbGlkYXRpb24gbG9naWMgdG8gYW4gaXJvbi1pbnB1dC4KICAgICAqCiAgICAgKiBCeSBkZWZhdWx0LCBhbiBgPGlyb24tZm9ybT5gIGVsZW1lbnQgdmFsaWRhdGVzIGl0cyBmaWVsZHMgd2hlbiB0aGUgdXNlcgogICAgICogcHJlc3NlcyB0aGUgc3VibWl0IGJ1dHRvbi4gVG8gdmFsaWRhdGUgYSBmb3JtIGltcGVyYXRpdmVseSwgY2FsbCB0aGUgZm9ybSdzCiAgICAgKiBgdmFsaWRhdGUoKWAgbWV0aG9kLCB3aGljaCBpbiB0dXJuIHdpbGwgY2FsbCBgdmFsaWRhdGUoKWAgb24gYWxsIGl0cwogICAgICogY2hpbGRyZW4uIEJ5IHVzaW5nIGBJcm9uVmFsaWRhdGFibGVCZWhhdmlvcmAsIHlvdXIgY3VzdG9tIGVsZW1lbnQKICAgICAqIHdpbGwgZ2V0IGEgcHVibGljIGB2YWxpZGF0ZSgpYCwgd2hpY2ggd2lsbCByZXR1cm4gdGhlIHZhbGlkaXR5IG9mIHRoZQogICAgICogZWxlbWVudCwgYW5kIGEgY29ycmVzcG9uZGluZyBgaW52YWxpZGAgYXR0cmlidXRlLCB3aGljaCBjYW4gYmUgdXNlZCBmb3IKICAgICAqIHN0eWxpbmcuCiAgICAgKgogICAgICogVG8gaW1wbGVtZW50IHRoZSBjdXN0b20gdmFsaWRhdGlvbiBsb2dpYyBvZiB5b3VyIGVsZW1lbnQsIHlvdSBtdXN0IG92ZXJyaWRlCiAgICAgKiB0aGUgcHJvdGVjdGVkIGBfZ2V0VmFsaWRpdHkoKWAgbWV0aG9kIG9mIHRoaXMgYmVoYXZpb3VyLCByYXRoZXIgdGhhbgogICAgICogYHZhbGlkYXRlKClgLiBTZWUKICAgICAqIFt0aGlzXShodHRwczovL2dpdGh1Yi5jb20vUG9seW1lckVsZW1lbnRzL2lyb24tZm9ybS9ibG9iL21hc3Rlci9kZW1vL3NpbXBsZS1lbGVtZW50Lmh0bWwpCiAgICAgKiBmb3IgYW4gZXhhbXBsZS4KICAgICAqCiAgICAgKiAjIyMgQWNjZXNzaWJpbGl0eQogICAgICoKICAgICAqIENoYW5naW5nIHRoZSBgaW52YWxpZGAgcHJvcGVydHksIGVpdGhlciBtYW51YWxseSBvciBieSBjYWxsaW5nIGB2YWxpZGF0ZSgpYAogICAgICogd2lsbCB1cGRhdGUgdGhlIGBhcmlhLWludmFsaWRgIGF0dHJpYnV0ZS4KICAgICAqCiAgICAgKiBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAqIEBwb2x5bWVyQmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgSXJvblZhbGlkYXRhYmxlQmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogTmFtZSBvZiB0aGUgdmFsaWRhdG9yIHRvIHVzZS4KICAgICAgICAgKi8KICAgICAgICB2YWxpZGF0b3I6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBsYXN0IGNhbGwgdG8gYHZhbGlkYXRlYCBpcyBpbnZhbGlkLgogICAgICAgICAqLwogICAgICAgIGludmFsaWQ6IHsKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICBvYnNlcnZlcjogJ19pbnZhbGlkQ2hhbmdlZCcKICAgICAgICB9LAogICAgICB9LAoKICAgICAgcmVnaXN0ZXJlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgSXJvblZhbGlkYXRhYmxlQmVoYXZpb3JNZXRhID0gbmV3IElyb25NZXRhKHt0eXBlOiAndmFsaWRhdG9yJ30pOwogICAgICB9LAoKICAgICAgX2ludmFsaWRDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5pbnZhbGlkKSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1pbnZhbGlkJywgJ3RydWUnKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoJ2FyaWEtaW52YWxpZCcpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qIFJlY29tcHV0ZSB0aGlzIGV2ZXJ5IHRpbWUgaXQncyBuZWVkZWQsIGJlY2F1c2Ugd2UgZG9uJ3Qga25vdyBpZiB0aGUKICAgICAgICogdW5kZXJseWluZyBJcm9uVmFsaWRhdGFibGVCZWhhdmlvck1ldGEgaGFzIGNoYW5nZWQuICovCiAgICAgIGdldCBfdmFsaWRhdG9yKCkgewogICAgICAgIHJldHVybiBJcm9uVmFsaWRhdGFibGVCZWhhdmlvck1ldGEgJiYKICAgICAgICAgICAgSXJvblZhbGlkYXRhYmxlQmVoYXZpb3JNZXRhLmJ5S2V5KHRoaXMudmFsaWRhdG9yKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHRoZSB2YWxpZGF0b3IgYHZhbGlkYXRvcmAgZXhpc3RzLgogICAgICAgKi8KICAgICAgaGFzVmFsaWRhdG9yOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5fdmFsaWRhdG9yICE9IG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBgdmFsdWVgIGlzIHZhbGlkLCBhbmQgdXBkYXRlcyBgaW52YWxpZGAuIElmIHlvdSB3YW50CiAgICAgICAqIHlvdXIgZWxlbWVudCB0byBoYXZlIGN1c3RvbSB2YWxpZGF0aW9uIGxvZ2ljLCBkbyBub3Qgb3ZlcnJpZGUgdGhpcyBtZXRob2Q7CiAgICAgICAqIG92ZXJyaWRlIGBfZ2V0VmFsaWRpdHkodmFsdWUpYCBpbnN0ZWFkLgoKICAgICAgICogQHBhcmFtIHtPYmplY3R9IHZhbHVlIERlcHJlY2F0ZWQ6IFRoZSB2YWx1ZSB0byBiZSB2YWxpZGF0ZWQuIEJ5IGRlZmF1bHQsCiAgICAgICAqIGl0IGlzIHBhc3NlZCB0byB0aGUgdmFsaWRhdG9yJ3MgYHZhbGlkYXRlKClgIGZ1bmN0aW9uLCBpZiBhIHZhbGlkYXRvciBpcwogICAgICAgc2V0LgogICAgICAgKiBJZiB0aGlzIGFyZ3VtZW50IGlzIG5vdCBzcGVjaWZpZWQsIHRoZW4gdGhlIGVsZW1lbnQncyBgdmFsdWVgIHByb3BlcnR5CiAgICAgICAqIGlzIHVzZWQsIGlmIGl0IGV4aXN0cy4KICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBgdmFsdWVgIGlzIHZhbGlkLgogICAgICAgKi8KICAgICAgdmFsaWRhdGU6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgLy8gSWYgdGhpcyBpcyBhbiBlbGVtZW50IHRoYXQgYWxzbyBoYXMgYSB2YWx1ZSBwcm9wZXJ0eSwgYW5kIHRoZXJlIHdhcwogICAgICAgIC8vIG5vIGV4cGxpY2l0IHZhbHVlIGFyZ3VtZW50IHBhc3NlZCwgdXNlIHRoZSBlbGVtZW50J3MgcHJvcGVydHkgaW5zdGVhZC4KICAgICAgICBpZiAodmFsdWUgPT09IHVuZGVmaW5lZCAmJiB0aGlzLnZhbHVlICE9PSB1bmRlZmluZWQpCiAgICAgICAgICB0aGlzLmludmFsaWQgPSAhdGhpcy5fZ2V0VmFsaWRpdHkodGhpcy52YWx1ZSk7CiAgICAgICAgZWxzZQogICAgICAgICAgdGhpcy5pbnZhbGlkID0gIXRoaXMuX2dldFZhbGlkaXR5KHZhbHVlKTsKICAgICAgICByZXR1cm4gIXRoaXMuaW52YWxpZDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRydWUgaWYgYHZhbHVlYCBpcyB2YWxpZC4gIEJ5IGRlZmF1bHQsIGl0IGlzIHBhc3NlZAogICAgICAgKiB0byB0aGUgdmFsaWRhdG9yJ3MgYHZhbGlkYXRlKClgIGZ1bmN0aW9uLCBpZiBhIHZhbGlkYXRvciBpcyBzZXQuIFlvdQogICAgICAgKiBzaG91bGQgb3ZlcnJpZGUgdGhpcyBtZXRob2QgaWYgeW91IHdhbnQgdG8gaW1wbGVtZW50IGN1c3RvbSB2YWxpZGl0eQogICAgICAgKiBsb2dpYyBmb3IgeW91ciBlbGVtZW50LgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge09iamVjdH0gdmFsdWUgVGhlIHZhbHVlIHRvIGJlIHZhbGlkYXRlZC4KICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gVHJ1ZSBpZiBgdmFsdWVgIGlzIHZhbGlkLgogICAgICAgKi8KCiAgICAgIF9nZXRWYWxpZGl0eTogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICBpZiAodGhpcy5oYXNWYWxpZGF0b3IoKSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX3ZhbGlkYXRvci52YWxpZGF0ZSh2YWx1ZSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogVXNlIGBJcm9uQ2hlY2tlZEVsZW1lbnRCZWhhdmlvcmAgdG8gaW1wbGVtZW50IGEgY3VzdG9tIGVsZW1lbnQgdGhhdCBoYXMgYQogICAgICogYGNoZWNrZWRgIHByb3BlcnR5LCB3aGljaCBjYW4gYmUgdXNlZCBmb3IgdmFsaWRhdGlvbiBpZiB0aGUgZWxlbWVudCBpcyBhbHNvCiAgICAgKiBgcmVxdWlyZWRgLiBFbGVtZW50IGluc3RhbmNlcyBpbXBsZW1lbnRpbmcgdGhpcyBiZWhhdmlvciB3aWxsIGFsc28gYmUKICAgICAqIHJlZ2lzdGVyZWQgZm9yIHVzZSBpbiBhbiBgaXJvbi1mb3JtYCBlbGVtZW50LgogICAgICoKICAgICAqIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgICogQHBvbHltZXJCZWhhdmlvciBJcm9uQ2hlY2tlZEVsZW1lbnRCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uQ2hlY2tlZEVsZW1lbnRCZWhhdmlvckltcGwgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogRmlyZWQgd2hlbiB0aGUgY2hlY2tlZCBzdGF0ZSBjaGFuZ2VzLgogICAgICAgICAqCiAgICAgICAgICogQGV2ZW50IGlyb24tY2hhbmdlCiAgICAgICAgICovCgogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgb3Igc2V0cyB0aGUgc3RhdGUsIGB0cnVlYCBpcyBjaGVja2VkIGFuZCBgZmFsc2VgIGlzIHVuY2hlY2tlZC4KICAgICAgICAgKi8KICAgICAgICBjaGVja2VkOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgb2JzZXJ2ZXI6ICdfY2hlY2tlZENoYW5nZWQnCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIGJ1dHRvbiB0b2dnbGVzIHRoZSBhY3RpdmUgc3RhdGUgd2l0aCBlYWNoIHRhcCBvciBwcmVzcwogICAgICAgICAqIG9mIHRoZSBzcGFjZWJhci4KICAgICAgICAgKi8KICAgICAgICB0b2dnbGVzOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IHRydWUsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZX0sCgogICAgICAgIC8qIE92ZXJyaWRlbiBmcm9tIElyb25Gb3JtRWxlbWVudEJlaGF2aW9yICovCiAgICAgICAgdmFsdWU6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnb24nLCBvYnNlcnZlcjogJ192YWx1ZUNoYW5nZWQnfQogICAgICB9LAoKICAgICAgb2JzZXJ2ZXJzOiBbJ19yZXF1aXJlZENoYW5nZWQocmVxdWlyZWQpJ10sCgogICAgICBjcmVhdGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBVc2VkIGJ5IGBpcm9uLWZvcm1gIHRvIGhhbmRsZSB0aGUgY2FzZSB0aGF0IGFuIGVsZW1lbnQgd2l0aCB0aGlzIGJlaGF2aW9yCiAgICAgICAgLy8gZG9lc24ndCBoYXZlIGEgcm9sZSBvZiAnY2hlY2tib3gnIG9yICdyYWRpbycsIGJ1dCBzaG91bGQgc3RpbGwgb25seSBiZQogICAgICAgIC8vIGluY2x1ZGVkIHdoZW4gdGhlIGZvcm0gaXMgc2VyaWFsaXplZCBpZiBgdGhpcy5jaGVja2VkID09PSB0cnVlYC4KICAgICAgICB0aGlzLl9oYXNJcm9uQ2hlY2tlZEVsZW1lbnRCZWhhdmlvciA9IHRydWU7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyBmYWxzZSBpZiB0aGUgZWxlbWVudCBpcyByZXF1aXJlZCBhbmQgbm90IGNoZWNrZWQsIGFuZCB0cnVlCiAgICAgICAqIG90aGVyd2lzZS4KICAgICAgICogQHBhcmFtIHsqPX0gX3ZhbHVlIElnbm9yZWQuCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IHRydWUgaWYgYHJlcXVpcmVkYCBpcyBmYWxzZSBvciBpZiBgY2hlY2tlZGAgaXMgdHJ1ZS4KICAgICAgICovCiAgICAgIF9nZXRWYWxpZGl0eTogZnVuY3Rpb24oX3ZhbHVlKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZGlzYWJsZWQgfHwgIXRoaXMucmVxdWlyZWQgfHwgdGhpcy5jaGVja2VkOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZSB0aGUgYXJpYS1yZXF1aXJlZCBsYWJlbCB3aGVuIGByZXF1aXJlZGAgaXMgY2hhbmdlZC4KICAgICAgICovCiAgICAgIF9yZXF1aXJlZENoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLnJlcXVpcmVkKSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1yZXF1aXJlZCcsICd0cnVlJyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhcmlhLXJlcXVpcmVkJyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEZpcmUgYGlyb24tY2hhbmdlZGAgd2hlbiB0aGUgY2hlY2tlZCBzdGF0ZSBjaGFuZ2VzLgogICAgICAgKi8KICAgICAgX2NoZWNrZWRDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmFjdGl2ZSA9IHRoaXMuY2hlY2tlZDsKICAgICAgICB0aGlzLmZpcmUoJ2lyb24tY2hhbmdlJyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVzZXQgdmFsdWUgdG8gJ29uJyBpZiBpdCBpcyBzZXQgdG8gYHVuZGVmaW5lZGAuCiAgICAgICAqLwogICAgICBfdmFsdWVDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy52YWx1ZSA9PT0gdW5kZWZpbmVkIHx8IHRoaXMudmFsdWUgPT09IG51bGwpIHsKICAgICAgICAgIHRoaXMudmFsdWUgPSAnb24nOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKiogQHBvbHltZXJCZWhhdmlvciAqLwogICAgY29uc3QgSXJvbkNoZWNrZWRFbGVtZW50QmVoYXZpb3IgPSBbCiAgICAgIElyb25Gb3JtRWxlbWVudEJlaGF2aW9yLAogICAgICBJcm9uVmFsaWRhdGFibGVCZWhhdmlvciwKICAgICAgSXJvbkNoZWNrZWRFbGVtZW50QmVoYXZpb3JJbXBsCiAgICBdOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogYFBhcGVySW5reUZvY3VzQmVoYXZpb3JgIGltcGxlbWVudHMgYSByaXBwbGUgd2hlbiB0aGUgZWxlbWVudCBoYXMga2V5Ym9hcmQKICAgICAqIGZvY3VzLgogICAgICoKICAgICAqIEBwb2x5bWVyQmVoYXZpb3IgUGFwZXJJbmt5Rm9jdXNCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBQYXBlcklua3lGb2N1c0JlaGF2aW9ySW1wbCA9IHsKICAgICAgb2JzZXJ2ZXJzOiBbJ19mb2N1c2VkQ2hhbmdlZChyZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKSddLAoKICAgICAgX2ZvY3VzZWRDaGFuZ2VkOiBmdW5jdGlvbihyZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKSB7CiAgICAgICAgaWYgKHJlY2VpdmVkRm9jdXNGcm9tS2V5Ym9hcmQpIHsKICAgICAgICAgIHRoaXMuZW5zdXJlUmlwcGxlKCk7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLmhhc1JpcHBsZSgpKSB7CiAgICAgICAgICB0aGlzLl9yaXBwbGUuaG9sZERvd24gPSByZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9jcmVhdGVSaXBwbGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciByaXBwbGUgPSBQYXBlclJpcHBsZUJlaGF2aW9yLl9jcmVhdGVSaXBwbGUoKTsKICAgICAgICByaXBwbGUuaWQgPSAnaW5rJzsKICAgICAgICByaXBwbGUuc2V0QXR0cmlidXRlKCdjZW50ZXInLCAnJyk7CiAgICAgICAgcmlwcGxlLmNsYXNzTGlzdC5hZGQoJ2NpcmNsZScpOwogICAgICAgIHJldHVybiByaXBwbGU7CiAgICAgIH0KICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVySW5reUZvY3VzQmVoYXZpb3IgPSBbCiAgICAgIElyb25CdXR0b25TdGF0ZSwKICAgICAgSXJvbkNvbnRyb2xTdGF0ZSwKICAgICAgUGFwZXJSaXBwbGVCZWhhdmlvciwKICAgICAgUGFwZXJJbmt5Rm9jdXNCZWhhdmlvckltcGwKICAgIF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBVc2UgYFBhcGVyQ2hlY2tlZEVsZW1lbnRCZWhhdmlvcmAgdG8gaW1wbGVtZW50IGEgY3VzdG9tIGVsZW1lbnQgdGhhdCBoYXMgYQogICAgICogYGNoZWNrZWRgIHByb3BlcnR5IHNpbWlsYXIgdG8gYElyb25DaGVja2VkRWxlbWVudEJlaGF2aW9yYCBhbmQgaXMgY29tcGF0aWJsZQogICAgICogd2l0aCBoYXZpbmcgYSByaXBwbGUgZWZmZWN0LgogICAgICogQHBvbHltZXJCZWhhdmlvciBQYXBlckNoZWNrZWRFbGVtZW50QmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgUGFwZXJDaGVja2VkRWxlbWVudEJlaGF2aW9ySW1wbCA9IHsKICAgICAgLyoqCiAgICAgICAqIFN5bmNocm9uaXplcyB0aGUgZWxlbWVudCdzIGNoZWNrZWQgc3RhdGUgd2l0aCBpdHMgcmlwcGxlIGVmZmVjdC4KICAgICAgICovCiAgICAgIF9jaGVja2VkQ2hhbmdlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgSXJvbkNoZWNrZWRFbGVtZW50QmVoYXZpb3JJbXBsLl9jaGVja2VkQ2hhbmdlZC5jYWxsKHRoaXMpOwogICAgICAgIGlmICh0aGlzLmhhc1JpcHBsZSgpKSB7CiAgICAgICAgICBpZiAodGhpcy5jaGVja2VkKSB7CiAgICAgICAgICAgIHRoaXMuX3JpcHBsZS5zZXRBdHRyaWJ1dGUoJ2NoZWNrZWQnLCAnJyk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLl9yaXBwbGUucmVtb3ZlQXR0cmlidXRlKCdjaGVja2VkJyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFN5bmNocm9uaXplcyB0aGUgZWxlbWVudCdzIGBhY3RpdmVgIGFuZCBgY2hlY2tlZGAgc3RhdGUuCiAgICAgICAqLwogICAgICBfYnV0dG9uU3RhdGVDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBQYXBlclJpcHBsZUJlaGF2aW9yLl9idXR0b25TdGF0ZUNoYW5nZWQuY2FsbCh0aGlzKTsKICAgICAgICBpZiAodGhpcy5kaXNhYmxlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5pc0F0dGFjaGVkKSB7CiAgICAgICAgICB0aGlzLmNoZWNrZWQgPSB0aGlzLmFjdGl2ZTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVyQ2hlY2tlZEVsZW1lbnRCZWhhdmlvciA9IFsKICAgICAgUGFwZXJJbmt5Rm9jdXNCZWhhdmlvciwKICAgICAgSXJvbkNoZWNrZWRFbGVtZW50QmVoYXZpb3IsCiAgICAgIFBhcGVyQ2hlY2tlZEVsZW1lbnRCZWhhdmlvckltcGwKICAgIF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE2IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCB0ZW1wbGF0ZSQ5ID0gaHRtbGA8c3R5bGU+CiAgOmhvc3QgewogICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgIGN1cnNvcjogcG9pbnRlcjsKICAgIC0tY2FsY3VsYXRlZC1wYXBlci1jaGVja2JveC1zaXplOiB2YXIoLS1wYXBlci1jaGVja2JveC1zaXplLCAxOHB4KTsKICAgIC8qIC0xcHggaXMgYSBzZW50aW5lbCBmb3IgdGhlIGRlZmF1bHQgYW5kIGlzIHJlcGxhY2VkIGluIFxgYXR0YWNoZWRcYC4gKi8KICAgIC0tY2FsY3VsYXRlZC1wYXBlci1jaGVja2JveC1pbmstc2l6ZTogdmFyKC0tcGFwZXItY2hlY2tib3gtaW5rLXNpemUsIC0xcHgpOwogICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKICAgIGxpbmUtaGVpZ2h0OiAwOwogICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKICB9CgogIDpob3N0KFtoaWRkZW5dKSB7CiAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgfQoKICA6aG9zdCg6Zm9jdXMpIHsKICAgIG91dGxpbmU6IG5vbmU7CiAgfQoKICAuaGlkZGVuIHsKICAgIGRpc3BsYXk6IG5vbmU7CiAgfQoKICAjY2hlY2tib3hDb250YWluZXIgewogICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgd2lkdGg6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItY2hlY2tib3gtc2l6ZSk7CiAgICBoZWlnaHQ6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItY2hlY2tib3gtc2l6ZSk7CiAgICBtaW4td2lkdGg6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItY2hlY2tib3gtc2l6ZSk7CiAgICBtYXJnaW46IHZhcigtLXBhcGVyLWNoZWNrYm94LW1hcmdpbiwgaW5pdGlhbCk7CiAgICB2ZXJ0aWNhbC1hbGlnbjogdmFyKC0tcGFwZXItY2hlY2tib3gtdmVydGljYWwtYWxpZ24sIG1pZGRsZSk7CiAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtYmFja2dyb3VuZC1jb2xvciwgdHJhbnNwYXJlbnQpOwogIH0KCiAgI2luayB7CiAgICBwb3NpdGlvbjogYWJzb2x1dGU7CgogICAgLyogQ2VudGVyIHRoZSByaXBwbGUgaW4gdGhlIGNoZWNrYm94IGJ5IG5lZ2F0aXZlIG9mZnNldHRpbmcgaXQgYnkKICAgICAqIChpbmtXaWR0aCAtIHJpcHBsZVdpZHRoKSAvIDIgKi8KICAgIHRvcDogY2FsYygwcHggLSAodmFyKC0tY2FsY3VsYXRlZC1wYXBlci1jaGVja2JveC1pbmstc2l6ZSkgLSB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LXNpemUpKSAvIDIpOwogICAgbGVmdDogY2FsYygwcHggLSAodmFyKC0tY2FsY3VsYXRlZC1wYXBlci1jaGVja2JveC1pbmstc2l6ZSkgLSB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LXNpemUpKSAvIDIpOwogICAgd2lkdGg6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItY2hlY2tib3gtaW5rLXNpemUpOwogICAgaGVpZ2h0OiB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LWluay1zaXplKTsKICAgIGNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtaW5rLWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgIG9wYWNpdHk6IDAuNjsKICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogIH0KCiAgI2luazpkaXIocnRsKSB7CiAgICByaWdodDogY2FsYygwcHggLSAodmFyKC0tY2FsY3VsYXRlZC1wYXBlci1jaGVja2JveC1pbmstc2l6ZSkgLSB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LXNpemUpKSAvIDIpOwogICAgbGVmdDogYXV0bzsKICB9CgogICNpbmtbY2hlY2tlZF0gewogICAgY29sb3I6IHZhcigtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CiAgfQoKICAjY2hlY2tib3ggewogICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgIGhlaWdodDogMTAwJTsKICAgIGJvcmRlcjogc29saWQgMnB4OwogICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwogICAgYm9yZGVyLXJhZGl1czogMnB4OwogICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAtd2Via2l0LXRyYW5zaXRpb246IGJhY2tncm91bmQtY29sb3IgMTQwbXMsIGJvcmRlci1jb2xvciAxNDBtczsKICAgIHRyYW5zaXRpb246IGJhY2tncm91bmQtY29sb3IgMTQwbXMsIGJvcmRlci1jb2xvciAxNDBtczsKCiAgICAtd2Via2l0LXRyYW5zaXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLWNoZWNrYm94LWFuaW1hdGlvbi1kdXJhdGlvbiwgMTQwbXMpOwogICAgdHJhbnNpdGlvbi1kdXJhdGlvbjogdmFyKC0tcGFwZXItY2hlY2tib3gtYW5pbWF0aW9uLWR1cmF0aW9uLCAxNDBtcyk7CiAgfQoKICAvKiBjaGVja2JveCBjaGVja2VkIGFuaW1hdGlvbnMgKi8KICAjY2hlY2tib3guY2hlY2tlZCAjY2hlY2ttYXJrIHsKICAgIC13ZWJraXQtYW5pbWF0aW9uOiBjaGVja21hcmstZXhwYW5kIDE0MG1zIGVhc2Utb3V0IGZvcndhcmRzOwogICAgYW5pbWF0aW9uOiBjaGVja21hcmstZXhwYW5kIDE0MG1zIGVhc2Utb3V0IGZvcndhcmRzOwoKICAgIC13ZWJraXQtYW5pbWF0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci1jaGVja2JveC1hbmltYXRpb24tZHVyYXRpb24sIDE0MG1zKTsKICAgIGFuaW1hdGlvbi1kdXJhdGlvbjogdmFyKC0tcGFwZXItY2hlY2tib3gtYW5pbWF0aW9uLWR1cmF0aW9uLCAxNDBtcyk7CiAgfQoKICBALXdlYmtpdC1rZXlmcmFtZXMgY2hlY2ttYXJrLWV4cGFuZCB7CiAgICAwJSB7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZSgwLCAwKSByb3RhdGUoNDVkZWcpOwogICAgfQogICAgMTAwJSB7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZSgxLCAxKSByb3RhdGUoNDVkZWcpOwogICAgfQogIH0KCiAgQGtleWZyYW1lcyBjaGVja21hcmstZXhwYW5kIHsKICAgIDAlIHsKICAgICAgdHJhbnNmb3JtOiBzY2FsZSgwLCAwKSByb3RhdGUoNDVkZWcpOwogICAgfQogICAgMTAwJSB7CiAgICAgIHRyYW5zZm9ybTogc2NhbGUoMSwgMSkgcm90YXRlKDQ1ZGVnKTsKICAgIH0KICB9CgogICNjaGVja2JveC5jaGVja2VkIHsKICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3IsIHZhcigtLXByaW1hcnktY29sb3IpKTsKICAgIGJvcmRlci1jb2xvcjogdmFyKC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1jb2xvciwgdmFyKC0tcHJpbWFyeS1jb2xvcikpOwogIH0KCiAgI2NoZWNrbWFyayB7CiAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICB3aWR0aDogMzYlOwogICAgaGVpZ2h0OiA3MCU7CiAgICBib3JkZXItc3R5bGU6IHNvbGlkOwogICAgYm9yZGVyLXRvcDogbm9uZTsKICAgIGJvcmRlci1sZWZ0OiBub25lOwogICAgYm9yZGVyLXJpZ2h0LXdpZHRoOiBjYWxjKDIvMTUgKiB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LXNpemUpKTsKICAgIGJvcmRlci1ib3R0b20td2lkdGg6IGNhbGMoMi8xNSAqIHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItY2hlY2tib3gtc2l6ZSkpOwogICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC1jaGVja21hcmstY29sb3IsIHdoaXRlKTsKICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogOTclIDg2JTsKICAgIHRyYW5zZm9ybS1vcmlnaW46IDk3JSA4NiU7CiAgICBib3gtc2l6aW5nOiBjb250ZW50LWJveDsgLyogcHJvdGVjdCBhZ2FpbnN0IHBhZ2UtbGV2ZWwgYm94LXNpemluZyAqLwogIH0KCiAgI2NoZWNrbWFyazpkaXIocnRsKSB7CiAgICAtd2Via2l0LXRyYW5zZm9ybS1vcmlnaW46IDUwJSAxNCU7CiAgICB0cmFuc2Zvcm0tb3JpZ2luOiA1MCUgMTQlOwogIH0KCiAgLyogbGFiZWwgKi8KICAjY2hlY2tib3hMYWJlbCB7CiAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwogICAgcGFkZGluZy1sZWZ0OiB2YXIoLS1wYXBlci1jaGVja2JveC1sYWJlbC1zcGFjaW5nLCA4cHgpOwogICAgd2hpdGUtc3BhY2U6IG5vcm1hbDsKICAgIGxpbmUtaGVpZ2h0OiBub3JtYWw7CiAgICBjb2xvcjogdmFyKC0tcGFwZXItY2hlY2tib3gtbGFiZWwtY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwogICAgQGFwcGx5IC0tcGFwZXItY2hlY2tib3gtbGFiZWw7CiAgfQoKICA6aG9zdChbY2hlY2tlZF0pICNjaGVja2JveExhYmVsIHsKICAgIGNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC1sYWJlbC1jaGVja2VkLWNvbG9yLCB2YXIoLS1wYXBlci1jaGVja2JveC1sYWJlbC1jb2xvciwgdmFyKC0tcHJpbWFyeS10ZXh0LWNvbG9yKSkpOwogICAgQGFwcGx5IC0tcGFwZXItY2hlY2tib3gtbGFiZWwtY2hlY2tlZDsKICB9CgogICNjaGVja2JveExhYmVsOmRpcihydGwpIHsKICAgIHBhZGRpbmctcmlnaHQ6IHZhcigtLXBhcGVyLWNoZWNrYm94LWxhYmVsLXNwYWNpbmcsIDhweCk7CiAgICBwYWRkaW5nLWxlZnQ6IDA7CiAgfQoKICAjY2hlY2tib3hMYWJlbFtoaWRkZW5dIHsKICAgIGRpc3BsYXk6IG5vbmU7CiAgfQoKICAvKiBkaXNhYmxlZCBzdGF0ZSAqLwoKICA6aG9zdChbZGlzYWJsZWRdKSAjY2hlY2tib3ggewogICAgb3BhY2l0eTogMC41OwogICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwogIH0KCiAgOmhvc3QoW2Rpc2FibGVkXVtjaGVja2VkXSkgI2NoZWNrYm94IHsKICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvciwgdmFyKC0tcHJpbWFyeS10ZXh0LWNvbG9yKSk7CiAgICBvcGFjaXR5OiAwLjU7CiAgfQoKICA6aG9zdChbZGlzYWJsZWRdKSAjY2hlY2tib3hMYWJlbCAgewogICAgb3BhY2l0eTogMC42NTsKICB9CgogIC8qIGludmFsaWQgc3RhdGUgKi8KICAjY2hlY2tib3guaW52YWxpZDpub3QoLmNoZWNrZWQpIHsKICAgIGJvcmRlci1jb2xvcjogdmFyKC0tcGFwZXItY2hlY2tib3gtZXJyb3ItY29sb3IsIHZhcigtLWVycm9yLWNvbG9yKSk7CiAgfQo8L3N0eWxlPgoKPGRpdiBpZD0iY2hlY2tib3hDb250YWluZXIiPgogIDxkaXYgaWQ9ImNoZWNrYm94IiBjbGFzcyQ9IltbX2NvbXB1dGVDaGVja2JveENsYXNzKGNoZWNrZWQsIGludmFsaWQpXV0iPgogICAgPGRpdiBpZD0iY2hlY2ttYXJrIiBjbGFzcyQ9IltbX2NvbXB1dGVDaGVja21hcmtDbGFzcyhjaGVja2VkKV1dIj48L2Rpdj4KICA8L2Rpdj4KPC9kaXY+Cgo8ZGl2IGlkPSJjaGVja2JveExhYmVsIj48c2xvdD48L3Nsb3Q+PC9kaXY+YDsKICAgIHRlbXBsYXRlJDkuc2V0QXR0cmlidXRlKCdzdHJpcC13aGl0ZXNwYWNlJywgJycpOwoKICAgIC8qKgogICAgTWF0ZXJpYWwgZGVzaWduOgogICAgW0NoZWNrYm94XShodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2NvbXBvbmVudHMvc2VsZWN0aW9uLWNvbnRyb2xzLmh0bWwjc2VsZWN0aW9uLWNvbnRyb2xzLWNoZWNrYm94KQoKICAgIGBwYXBlci1jaGVja2JveGAgaXMgYSBidXR0b24gdGhhdCBjYW4gYmUgZWl0aGVyIGNoZWNrZWQgb3IgdW5jaGVja2VkLiBVc2VyIGNhbgogICAgdGFwIHRoZSBjaGVja2JveCB0byBjaGVjayBvciB1bmNoZWNrIGl0LiBVc3VhbGx5IHlvdSB1c2UgY2hlY2tib3hlcyB0byBhbGxvdwogICAgdXNlciB0byBzZWxlY3QgbXVsdGlwbGUgb3B0aW9ucyBmcm9tIGEgc2V0LiBJZiB5b3UgaGF2ZSBhIHNpbmdsZSBPTi9PRkYgb3B0aW9uLAogICAgYXZvaWQgdXNpbmcgYSBzaW5nbGUgY2hlY2tib3ggYW5kIHVzZSBgcGFwZXItdG9nZ2xlLWJ1dHRvbmAgaW5zdGVhZC4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItY2hlY2tib3g+bGFiZWw8L3BhcGVyLWNoZWNrYm94PgoKICAgICAgICA8cGFwZXItY2hlY2tib3ggY2hlY2tlZD4gbGFiZWw8L3BhcGVyLWNoZWNrYm94PgoKICAgICMjIyBTdHlsaW5nCgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItY2hlY2tib3gtdW5jaGVja2VkLWJhY2tncm91bmQtY29sb3JgIHwgQ2hlY2tib3ggYmFja2dyb3VuZCBjb2xvciB3aGVuIHRoZSBpbnB1dCBpcyBub3QgY2hlY2tlZCB8IGB0cmFuc3BhcmVudGAKICAgIGAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcmAgfCBDaGVja2JveCBib3JkZXIgY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtaW5rLWNvbG9yYCB8IFNlbGVjdGVkL2ZvY3VzIHJpcHBsZSBjb2xvciB3aGVuIHRoZSBpbnB1dCBpcyBub3QgY2hlY2tlZCB8IGAtLXByaW1hcnktdGV4dC1jb2xvcmAKICAgIGAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3JgIHwgQ2hlY2tib3ggY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgY2hlY2tlZCB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWluay1jb2xvcmAgfCBTZWxlY3RlZC9mb2N1cyByaXBwbGUgY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgY2hlY2tlZCB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci1jaGVja2JveC1jaGVja21hcmstY29sb3JgIHwgQ2hlY2ttYXJrIGNvbG9yIHwgYHdoaXRlYAogICAgYC0tcGFwZXItY2hlY2tib3gtbGFiZWwtY29sb3JgIHwgTGFiZWwgY29sb3IgfCBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1jaGVja2JveC1sYWJlbC1jaGVja2VkLWNvbG9yYCB8IExhYmVsIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGNoZWNrZWQgfCBgLS1wYXBlci1jaGVja2JveC1sYWJlbC1jb2xvcmAKICAgIGAtLXBhcGVyLWNoZWNrYm94LWxhYmVsLXNwYWNpbmdgIHwgU3BhY2luZyBiZXR3ZWVuIHRoZSBsYWJlbCBhbmQgdGhlIGNoZWNrYm94IHwgYDhweGAKICAgIGAtLXBhcGVyLWNoZWNrYm94LWxhYmVsYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGxhYmVsIHwgYHt9YAogICAgYC0tcGFwZXItY2hlY2tib3gtbGFiZWwtY2hlY2tlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBsYWJlbCB3aGVuIHRoZSBpbnB1dCBpcyBjaGVja2VkIHwgYHt9YAogICAgYC0tcGFwZXItY2hlY2tib3gtZXJyb3ItY29sb3JgIHwgQ2hlY2tib3ggY29sb3Igd2hlbiBpbnZhbGlkIHwgYC0tZXJyb3ItY29sb3JgCiAgICBgLS1wYXBlci1jaGVja2JveC1zaXplYCB8IFNpemUgb2YgdGhlIGNoZWNrYm94IHwgYDE4cHhgCiAgICBgLS1wYXBlci1jaGVja2JveC1pbmstc2l6ZWAgfCBTaXplIG9mIHRoZSByaXBwbGUgfCBgNDhweGAKICAgIGAtLXBhcGVyLWNoZWNrYm94LW1hcmdpbmAgfCBNYXJnaW4gYXJvdW5kIHRoZSBjaGVja2JveCBjb250YWluZXIgfCBgaW5pdGlhbGAKICAgIGAtLXBhcGVyLWNoZWNrYm94LXZlcnRpY2FsLWFsaWduYCB8IFZlcnRpY2FsIGFsaWdubWVudCBvZiB0aGUgY2hlY2tib3ggY29udGFpbmVyIHwgYG1pZGRsZWAKCiAgICBUaGlzIGVsZW1lbnQgYXBwbGllcyB0aGUgbWl4aW4gYC0tcGFwZXItZm9udC1jb21tb24tYmFzZWAgYnV0IGRvZXMgbm90IGltcG9ydAogICAgYHBhcGVyLXN0eWxlcy90eXBvZ3JhcGh5Lmh0bWxgLiBJbiBvcmRlciB0byBhcHBseSB0aGUgYFJvYm90b2AgZm9udCB0byB0aGlzCiAgICBlbGVtZW50LCBtYWtlIHN1cmUgeW91J3ZlIGltcG9ydGVkIGBwYXBlci1zdHlsZXMvdHlwb2dyYXBoeS5odG1sYC4KCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiB0ZW1wbGF0ZSQ5LAoKICAgICAgaXM6ICdwYXBlci1jaGVja2JveCcsCgogICAgICBiZWhhdmlvcnM6IFtQYXBlckNoZWNrZWRFbGVtZW50QmVoYXZpb3JdLAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ2NoZWNrYm94JywgJ2FyaWEtY2hlY2tlZCc6IGZhbHNlLCB0YWJpbmRleDogMH0sCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogRmlyZWQgd2hlbiB0aGUgY2hlY2tlZCBzdGF0ZSBjaGFuZ2VzIGR1ZSB0byB1c2VyIGludGVyYWN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQGV2ZW50IGNoYW5nZQogICAgICAgICAqLwoKICAgICAgICAvKioKICAgICAgICAgKiBGaXJlZCB3aGVuIHRoZSBjaGVja2VkIHN0YXRlIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAZXZlbnQgaXJvbi1jaGFuZ2UKICAgICAgICAgKi8KICAgICAgICBhcmlhQWN0aXZlQXR0cmlidXRlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ2FyaWEtY2hlY2tlZCd9CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gV2FpdCB1bnRpbCBzdHlsZXMgaGF2ZSByZXNvbHZlZCB0byBjaGVjayBmb3IgdGhlIGRlZmF1bHQgc2VudGluZWwuCiAgICAgICAgLy8gU2VlIHBvbHltZXIjNDAwOSBmb3IgbW9yZSBkZXRhaWxzLgogICAgICAgIGFmdGVyTmV4dFJlbmRlcih0aGlzLCBmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciBpbmtTaXplID0KICAgICAgICAgICAgICB0aGlzLmdldENvbXB1dGVkU3R5bGVWYWx1ZSgnLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LWluay1zaXplJykKICAgICAgICAgICAgICAgICAgLnRyaW0oKTsKICAgICAgICAgIC8vIElmIHVuc2V0LCBjb21wdXRlIGFuZCBzZXQgdGhlIGRlZmF1bHQgYC0tcGFwZXItY2hlY2tib3gtaW5rLXNpemVgLgogICAgICAgICAgaWYgKGlua1NpemUgPT09ICctMXB4JykgewogICAgICAgICAgICB2YXIgY2hlY2tib3hTaXplVGV4dCA9CiAgICAgICAgICAgICAgICB0aGlzLmdldENvbXB1dGVkU3R5bGVWYWx1ZSgnLS1jYWxjdWxhdGVkLXBhcGVyLWNoZWNrYm94LXNpemUnKQogICAgICAgICAgICAgICAgICAgIC50cmltKCk7CgogICAgICAgICAgICB2YXIgdW5pdHMgPSAncHgnOwogICAgICAgICAgICB2YXIgdW5pdHNNYXRjaGVzID0gY2hlY2tib3hTaXplVGV4dC5tYXRjaCgvW0EtWmEtel0rJC8pOwogICAgICAgICAgICBpZiAodW5pdHNNYXRjaGVzICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgdW5pdHMgPSB1bml0c01hdGNoZXNbMF07CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIHZhciBjaGVja2JveFNpemUgPSBwYXJzZUZsb2F0KGNoZWNrYm94U2l6ZVRleHQpOwogICAgICAgICAgICB2YXIgZGVmYXVsdElua1NpemUgPSAoOCAvIDMpICogY2hlY2tib3hTaXplOwoKICAgICAgICAgICAgaWYgKHVuaXRzID09PSAncHgnKSB7CiAgICAgICAgICAgICAgZGVmYXVsdElua1NpemUgPSBNYXRoLmZsb29yKGRlZmF1bHRJbmtTaXplKTsKCiAgICAgICAgICAgICAgLy8gVGhlIGNoZWNrYm94IGFuZCByaXBwbGUgbmVlZCB0byBoYXZlIHRoZSBzYW1lIHBhcml0eSBzbyB0aGF0IHRoZWlyCiAgICAgICAgICAgICAgLy8gY2VudGVycyBhbGlnbi4KICAgICAgICAgICAgICBpZiAoZGVmYXVsdElua1NpemUgJSAyICE9PSBjaGVja2JveFNpemUgJSAyKSB7CiAgICAgICAgICAgICAgICBkZWZhdWx0SW5rU2l6ZSsrOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQoKICAgICAgICAgICAgdGhpcy51cGRhdGVTdHlsZXMoewogICAgICAgICAgICAgICctLXBhcGVyLWNoZWNrYm94LWluay1zaXplJzogZGVmYXVsdElua1NpemUgKyB1bml0cywKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0sCgogICAgICBfY29tcHV0ZUNoZWNrYm94Q2xhc3M6IGZ1bmN0aW9uKGNoZWNrZWQsIGludmFsaWQpIHsKICAgICAgICB2YXIgY2xhc3NOYW1lID0gJyc7CiAgICAgICAgaWYgKGNoZWNrZWQpIHsKICAgICAgICAgIGNsYXNzTmFtZSArPSAnY2hlY2tlZCAnOwogICAgICAgIH0KICAgICAgICBpZiAoaW52YWxpZCkgewogICAgICAgICAgY2xhc3NOYW1lICs9ICdpbnZhbGlkJzsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGNsYXNzTmFtZTsKICAgICAgfSwKCiAgICAgIF9jb21wdXRlQ2hlY2ttYXJrQ2xhc3M6IGZ1bmN0aW9uKGNoZWNrZWQpIHsKICAgICAgICByZXR1cm4gY2hlY2tlZCA/ICcnIDogJ2hpZGRlbic7CiAgICAgIH0sCgogICAgICAvLyBjcmVhdGUgcmlwcGxlIGluc2lkZSB0aGUgY2hlY2tib3hDb250YWluZXIKICAgICAgX2NyZWF0ZVJpcHBsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcmlwcGxlQ29udGFpbmVyID0gdGhpcy4kLmNoZWNrYm94Q29udGFpbmVyOwogICAgICAgIHJldHVybiBQYXBlcklua3lGb2N1c0JlaGF2aW9ySW1wbC5fY3JlYXRlUmlwcGxlLmNhbGwodGhpcyk7CiAgICAgIH0KCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgIGBQb2x5bWVyLklyb25GaXRCZWhhdmlvcmAgZml0cyBhbiBlbGVtZW50IGluIGFub3RoZXIgZWxlbWVudCB1c2luZyBgbWF4LWhlaWdodGAKICAgIGFuZCBgbWF4LXdpZHRoYCwgYW5kIG9wdGlvbmFsbHkgY2VudGVycyBpdCBpbiB0aGUgd2luZG93IG9yIGFub3RoZXIgZWxlbWVudC4KCiAgICBUaGUgZWxlbWVudCB3aWxsIG9ubHkgYmUgc2l6ZWQgYW5kL29yIHBvc2l0aW9uZWQgaWYgaXQgaGFzIG5vdCBhbHJlYWR5IGJlZW4KICAgIHNpemVkIGFuZC9vciBwb3NpdGlvbmVkIGJ5IENTUy4KCiAgICBDU1MgcHJvcGVydGllcyAgICAgICAgICAgIHwgQWN0aW9uCiAgICAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCiAgICBgcG9zaXRpb25gIHNldCAgICAgICAgICAgIHwgRWxlbWVudCBpcyBub3QgY2VudGVyZWQgaG9yaXpvbnRhbGx5IG9yIHZlcnRpY2FsbHkKICAgIGB0b3BgIG9yIGBib3R0b21gIHNldCAgICAgfCBFbGVtZW50IGlzIG5vdCB2ZXJ0aWNhbGx5IGNlbnRlcmVkCiAgICBgbGVmdGAgb3IgYHJpZ2h0YCBzZXQgICAgIHwgRWxlbWVudCBpcyBub3QgaG9yaXpvbnRhbGx5IGNlbnRlcmVkCiAgICBgbWF4LWhlaWdodGAgc2V0ICAgICAgICAgIHwgRWxlbWVudCByZXNwZWN0cyBgbWF4LWhlaWdodGAKICAgIGBtYXgtd2lkdGhgIHNldCAgICAgICAgICAgfCBFbGVtZW50IHJlc3BlY3RzIGBtYXgtd2lkdGhgCgogICAgYFBvbHltZXIuSXJvbkZpdEJlaGF2aW9yYCBjYW4gcG9zaXRpb24gYW4gZWxlbWVudCBpbnRvIGFub3RoZXIgZWxlbWVudCB1c2luZwogICAgYHZlcnRpY2FsQWxpZ25gIGFuZCBgaG9yaXpvbnRhbEFsaWduYC4gVGhpcyB3aWxsIG92ZXJyaWRlIHRoZSBlbGVtZW50J3MgY3NzCiAgICBwb3NpdGlvbi4KCiAgICAgICAgPGRpdiBjbGFzcz0iY29udGFpbmVyIj4KICAgICAgICAgIDxpcm9uLWZpdC1pbXBsIHZlcnRpY2FsLWFsaWduPSJ0b3AiIGhvcml6b250YWwtYWxpZ249ImF1dG8iPgogICAgICAgICAgICBQb3NpdGlvbmVkIGludG8gdGhlIGNvbnRhaW5lcgogICAgICAgICAgPC9pcm9uLWZpdC1pbXBsPgogICAgICAgIDwvZGl2PgoKICAgIFVzZSBgbm9PdmVybGFwYCB0byBwb3NpdGlvbiB0aGUgZWxlbWVudCBhcm91bmQgYW5vdGhlciBlbGVtZW50IHdpdGhvdXQKICAgIG92ZXJsYXBwaW5nIGl0LgoKICAgICAgICA8ZGl2IGNsYXNzPSJjb250YWluZXIiPgogICAgICAgICAgPGlyb24tZml0LWltcGwgbm8tb3ZlcmxhcCB2ZXJ0aWNhbC1hbGlnbj0iYXV0byIgaG9yaXpvbnRhbC1hbGlnbj0iYXV0byI+CiAgICAgICAgICAgIFBvc2l0aW9uZWQgYXJvdW5kIHRoZSBjb250YWluZXIKICAgICAgICAgIDwvaXJvbi1maXQtaW1wbD4KICAgICAgICA8L2Rpdj4KCiAgICBVc2UgYGhvcml6b250YWxPZmZzZXQsIHZlcnRpY2FsT2Zmc2V0YCB0byBvZmZzZXQgdGhlIGVsZW1lbnQgZnJvbSBpdHMKICAgIGBwb3NpdGlvblRhcmdldGA7IGBQb2x5bWVyLklyb25GaXRCZWhhdmlvcmAgd2lsbCBjb2xsYXBzZSB0aGVzZSBpbiBvcmRlciB0bwogICAga2VlcCB0aGUgZWxlbWVudCB3aXRoaW4gYGZpdEludG9gIGJvdW5kYXJpZXMsIHdoaWxlIHByZXNlcnZpbmcgdGhlIGVsZW1lbnQncwogICAgQ1NTIG1hcmdpbiB2YWx1ZXMuCgogICAgICAgIDxkaXYgY2xhc3M9ImNvbnRhaW5lciI+CiAgICAgICAgICA8aXJvbi1maXQtaW1wbCB2ZXJ0aWNhbC1hbGlnbj0idG9wIiB2ZXJ0aWNhbC1vZmZzZXQ9IjIwIj4KICAgICAgICAgICAgV2l0aCB2ZXJ0aWNhbCBvZmZzZXQKICAgICAgICAgIDwvaXJvbi1maXQtaW1wbD4KICAgICAgICA8L2Rpdj4KCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgIEBwb2x5bWVyQmVoYXZpb3IKICAgICovCiAgICBjb25zdCBJcm9uRml0QmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBlbGVtZW50IHRoYXQgd2lsbCByZWNlaXZlIGEgYG1heC1oZWlnaHRgL2B3aWR0aGAuIEJ5IGRlZmF1bHQgaXQgaXMKICAgICAgICAgKiB0aGUgc2FtZSBhcyBgdGhpc2AsIGJ1dCBpdCBjYW4gYmUgc2V0IHRvIGEgY2hpbGQgZWxlbWVudC4gVGhpcyBpcyB1c2VmdWwsCiAgICAgICAgICogZm9yIGV4YW1wbGUsIGZvciBpbXBsZW1lbnRpbmcgYSBzY3JvbGxpbmcgcmVnaW9uIGluc2lkZSB0aGUgZWxlbWVudC4KICAgICAgICAgKiBAdHlwZSB7IUVsZW1lbnR9CiAgICAgICAgICovCiAgICAgICAgc2l6aW5nVGFyZ2V0OiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgfQogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBlbGVtZW50IHRvIGZpdCBgdGhpc2AgaW50by4KICAgICAgICAgKi8KICAgICAgICBmaXRJbnRvOiB7dHlwZTogT2JqZWN0LCB2YWx1ZTogd2luZG93fSwKCiAgICAgICAgLyoqCiAgICAgICAgICogV2lsbCBwb3NpdGlvbiB0aGUgZWxlbWVudCBhcm91bmQgdGhlIHBvc2l0aW9uVGFyZ2V0IHdpdGhvdXQgb3ZlcmxhcHBpbmcKICAgICAgICAgKiBpdC4KICAgICAgICAgKi8KICAgICAgICBub092ZXJsYXA6IHt0eXBlOiBCb29sZWFufSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGVsZW1lbnQgdGhhdCBzaG91bGQgYmUgdXNlZCB0byBwb3NpdGlvbiB0aGUgZWxlbWVudC4gSWYgbm90IHNldCwgaXQKICAgICAgICAgKiB3aWxsIGRlZmF1bHQgdG8gdGhlIHBhcmVudCBub2RlLgogICAgICAgICAqIEB0eXBlIHshRWxlbWVudH0KICAgICAgICAgKi8KICAgICAgICBwb3NpdGlvblRhcmdldDoge3R5cGU6IEVsZW1lbnR9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3JpZW50YXRpb24gYWdhaW5zdCB3aGljaCB0byBhbGlnbiB0aGUgZWxlbWVudCBob3Jpem9udGFsbHkKICAgICAgICAgKiByZWxhdGl2ZSB0byB0aGUgYHBvc2l0aW9uVGFyZ2V0YC4gUG9zc2libGUgdmFsdWVzIGFyZSAibGVmdCIsICJyaWdodCIsCiAgICAgICAgICogImNlbnRlciIsICJhdXRvIi4KICAgICAgICAgKi8KICAgICAgICBob3Jpem9udGFsQWxpZ246IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3JpZW50YXRpb24gYWdhaW5zdCB3aGljaCB0byBhbGlnbiB0aGUgZWxlbWVudCB2ZXJ0aWNhbGx5CiAgICAgICAgICogcmVsYXRpdmUgdG8gdGhlIGBwb3NpdGlvblRhcmdldGAuIFBvc3NpYmxlIHZhbHVlcyBhcmUgInRvcCIsICJib3R0b20iLAogICAgICAgICAqICJtaWRkbGUiLCAiYXV0byIuCiAgICAgICAgICovCiAgICAgICAgdmVydGljYWxBbGlnbjoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIGl0IHdpbGwgdXNlIGBob3Jpem9udGFsQWxpZ25gIGFuZCBgdmVydGljYWxBbGlnbmAgdmFsdWVzIGFzCiAgICAgICAgICogcHJlZmVycmVkIGFsaWdubWVudCBhbmQgaWYgdGhlcmUncyBub3QgZW5vdWdoIHNwYWNlLCBpdCB3aWxsIHBpY2sgdGhlCiAgICAgICAgICogdmFsdWVzIHdoaWNoIG1pbmltaXplIHRoZSBjcm9wcGluZy4KICAgICAgICAgKi8KICAgICAgICBkeW5hbWljQWxpZ246IHt0eXBlOiBCb29sZWFufSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQSBwaXhlbCB2YWx1ZSB0aGF0IHdpbGwgYmUgYWRkZWQgdG8gdGhlIHBvc2l0aW9uIGNhbGN1bGF0ZWQgZm9yIHRoZQogICAgICAgICAqIGdpdmVuIGBob3Jpem9udGFsQWxpZ25gLCBpbiB0aGUgZGlyZWN0aW9uIG9mIGFsaWdubWVudC4gWW91IGNhbiB0aGluawogICAgICAgICAqIG9mIGl0IGFzIGluY3JlYXNpbmcgb3IgZGVjcmVhc2luZyB0aGUgZGlzdGFuY2UgdG8gdGhlIHNpZGUgb2YgdGhlCiAgICAgICAgICogc2NyZWVuIGdpdmVuIGJ5IGBob3Jpem9udGFsQWxpZ25gLgogICAgICAgICAqCiAgICAgICAgICogSWYgYGhvcml6b250YWxBbGlnbmAgaXMgImxlZnQiIG9yICJjZW50ZXIiLCB0aGlzIG9mZnNldCB3aWxsIGluY3JlYXNlIG9yCiAgICAgICAgICogZGVjcmVhc2UgdGhlIGRpc3RhbmNlIHRvIHRoZSBsZWZ0IHNpZGUgb2YgdGhlIHNjcmVlbjogYSBuZWdhdGl2ZSBvZmZzZXQKICAgICAgICAgKiB3aWxsIG1vdmUgdGhlIGRyb3Bkb3duIHRvIHRoZSBsZWZ0OyBhIHBvc2l0aXZlIG9uZSwgdG8gdGhlIHJpZ2h0LgogICAgICAgICAqCiAgICAgICAgICogQ29udmVyc2VseSBpZiBgaG9yaXpvbnRhbEFsaWduYCBpcyAicmlnaHQiLCB0aGlzIG9mZnNldCB3aWxsIGluY3JlYXNlCiAgICAgICAgICogb3IgZGVjcmVhc2UgdGhlIGRpc3RhbmNlIHRvIHRoZSByaWdodCBzaWRlIG9mIHRoZSBzY3JlZW46IGEgbmVnYXRpdmUKICAgICAgICAgKiBvZmZzZXQgd2lsbCBtb3ZlIHRoZSBkcm9wZG93biB0byB0aGUgcmlnaHQ7IGEgcG9zaXRpdmUgb25lLCB0byB0aGUgbGVmdC4KICAgICAgICAgKi8KICAgICAgICBob3Jpem9udGFsT2Zmc2V0OiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMCwgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQSBwaXhlbCB2YWx1ZSB0aGF0IHdpbGwgYmUgYWRkZWQgdG8gdGhlIHBvc2l0aW9uIGNhbGN1bGF0ZWQgZm9yIHRoZQogICAgICAgICAqIGdpdmVuIGB2ZXJ0aWNhbEFsaWduYCwgaW4gdGhlIGRpcmVjdGlvbiBvZiBhbGlnbm1lbnQuIFlvdSBjYW4gdGhpbmsKICAgICAgICAgKiBvZiBpdCBhcyBpbmNyZWFzaW5nIG9yIGRlY3JlYXNpbmcgdGhlIGRpc3RhbmNlIHRvIHRoZSBzaWRlIG9mIHRoZQogICAgICAgICAqIHNjcmVlbiBnaXZlbiBieSBgdmVydGljYWxBbGlnbmAuCiAgICAgICAgICoKICAgICAgICAgKiBJZiBgdmVydGljYWxBbGlnbmAgaXMgInRvcCIgb3IgIm1pZGRsZSIsIHRoaXMgb2Zmc2V0IHdpbGwgaW5jcmVhc2Ugb3IKICAgICAgICAgKiBkZWNyZWFzZSB0aGUgZGlzdGFuY2UgdG8gdGhlIHRvcCBzaWRlIG9mIHRoZSBzY3JlZW46IGEgbmVnYXRpdmUgb2Zmc2V0CiAgICAgICAgICogd2lsbCBtb3ZlIHRoZSBkcm9wZG93biB1cHdhcmRzOyBhIHBvc2l0aXZlIG9uZSwgZG93bndhcmRzLgogICAgICAgICAqCiAgICAgICAgICogQ29udmVyc2VseSBpZiBgdmVydGljYWxBbGlnbmAgaXMgImJvdHRvbSIsIHRoaXMgb2Zmc2V0IHdpbGwgaW5jcmVhc2UKICAgICAgICAgKiBvciBkZWNyZWFzZSB0aGUgZGlzdGFuY2UgdG8gdGhlIGJvdHRvbSBzaWRlIG9mIHRoZSBzY3JlZW46IGEgbmVnYXRpdmUKICAgICAgICAgKiBvZmZzZXQgd2lsbCBtb3ZlIHRoZSBkcm9wZG93biBkb3dud2FyZHM7IGEgcG9zaXRpdmUgb25lLCB1cHdhcmRzLgogICAgICAgICAqLwogICAgICAgIHZlcnRpY2FsT2Zmc2V0OiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMCwgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gYXV0by1maXQgb24gYXR0YWNoLgogICAgICAgICAqLwogICAgICAgIGF1dG9GaXRPbkF0dGFjaDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKiBAdHlwZSB7P09iamVjdH0gKi8KICAgICAgICBfZml0SW5mbzoge3R5cGU6IE9iamVjdH0KICAgICAgfSwKCiAgICAgIGdldCBfZml0V2lkdGgoKSB7CiAgICAgICAgdmFyIGZpdFdpZHRoOwogICAgICAgIGlmICh0aGlzLmZpdEludG8gPT09IHdpbmRvdykgewogICAgICAgICAgZml0V2lkdGggPSB0aGlzLmZpdEludG8uaW5uZXJXaWR0aDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZml0V2lkdGggPSB0aGlzLmZpdEludG8uZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkud2lkdGg7CiAgICAgICAgfQogICAgICAgIHJldHVybiBmaXRXaWR0aDsKICAgICAgfSwKCiAgICAgIGdldCBfZml0SGVpZ2h0KCkgewogICAgICAgIHZhciBmaXRIZWlnaHQ7CiAgICAgICAgaWYgKHRoaXMuZml0SW50byA9PT0gd2luZG93KSB7CiAgICAgICAgICBmaXRIZWlnaHQgPSB0aGlzLmZpdEludG8uaW5uZXJIZWlnaHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGZpdEhlaWdodCA9IHRoaXMuZml0SW50by5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5oZWlnaHQ7CiAgICAgICAgfQogICAgICAgIHJldHVybiBmaXRIZWlnaHQ7CiAgICAgIH0sCgogICAgICBnZXQgX2ZpdExlZnQoKSB7CiAgICAgICAgdmFyIGZpdExlZnQ7CiAgICAgICAgaWYgKHRoaXMuZml0SW50byA9PT0gd2luZG93KSB7CiAgICAgICAgICBmaXRMZWZ0ID0gMDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZml0TGVmdCA9IHRoaXMuZml0SW50by5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5sZWZ0OwogICAgICAgIH0KICAgICAgICByZXR1cm4gZml0TGVmdDsKICAgICAgfSwKCiAgICAgIGdldCBfZml0VG9wKCkgewogICAgICAgIHZhciBmaXRUb3A7CiAgICAgICAgaWYgKHRoaXMuZml0SW50byA9PT0gd2luZG93KSB7CiAgICAgICAgICBmaXRUb3AgPSAwOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBmaXRUb3AgPSB0aGlzLmZpdEludG8uZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkudG9wOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZml0VG9wOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBlbGVtZW50IHRoYXQgc2hvdWxkIGJlIHVzZWQgdG8gcG9zaXRpb24gdGhlIGVsZW1lbnQsCiAgICAgICAqIGlmIG5vIHBvc2l0aW9uIHRhcmdldCBpcyBjb25maWd1cmVkLgogICAgICAgKi8KICAgICAgZ2V0IF9kZWZhdWx0UG9zaXRpb25UYXJnZXQoKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IGRvbSh0aGlzKS5wYXJlbnROb2RlOwoKICAgICAgICBpZiAocGFyZW50ICYmIHBhcmVudC5ub2RlVHlwZSA9PT0gTm9kZS5ET0NVTUVOVF9GUkFHTUVOVF9OT0RFKSB7CiAgICAgICAgICBwYXJlbnQgPSBwYXJlbnQuaG9zdDsKICAgICAgICB9CgogICAgICAgIHJldHVybiBwYXJlbnQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIGhvcml6b250YWwgYWxpZ24gdmFsdWUsIGFjY291bnRpbmcgZm9yIHRoZSBSVEwvTFRSIHRleHQgZGlyZWN0aW9uLgogICAgICAgKi8KICAgICAgZ2V0IF9sb2NhbGVIb3Jpem9udGFsQWxpZ24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2lzUlRMKSB7CiAgICAgICAgICAvLyBJbiBSVEwsICJsZWZ0IiBiZWNvbWVzICJyaWdodCIuCiAgICAgICAgICBpZiAodGhpcy5ob3Jpem9udGFsQWxpZ24gPT09ICdyaWdodCcpIHsKICAgICAgICAgICAgcmV0dXJuICdsZWZ0JzsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh0aGlzLmhvcml6b250YWxBbGlnbiA9PT0gJ2xlZnQnKSB7CiAgICAgICAgICAgIHJldHVybiAncmlnaHQnOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy5ob3Jpem9udGFsQWxpZ247CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVHJ1ZSBpZiB0aGUgZWxlbWVudCBzaG91bGQgYmUgcG9zaXRpb25lZCBpbnN0ZWFkIG9mIGNlbnRlcmVkLgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgZ2V0IF9fc2hvdWxkUG9zaXRpb24oKSB7CiAgICAgICAgcmV0dXJuICh0aGlzLmhvcml6b250YWxBbGlnbiB8fCB0aGlzLnZlcnRpY2FsQWxpZ24pICYmIHRoaXMucG9zaXRpb25UYXJnZXQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVHJ1ZSBpZiB0aGUgY29tcG9uZW50IGlzIFJUTC4KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIGdldCBfaXNSVEwoKSB7CiAgICAgICAgLy8gTWVtb2l6ZSB0aGlzIHRvIGF2b2lkIGV4cGVuc2l2ZSBjYWxjdWxhdGlvbnMgJiByZWxheW91dHMuCiAgICAgICAgLy8gTWFrZSBzdXJlIHdlIGRvIGl0IG9ubHkgb25jZQogICAgICAgIGlmICh0eXBlb2YgdGhpcy5fbWVtb2l6ZWRJc1JUTCA9PT0gJ3VuZGVmaW5lZCcpIHsKICAgICAgICAgIHRoaXMuX21lbW9pemVkSXNSVEwgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZSh0aGlzKS5kaXJlY3Rpb24gPT0gJ3J0bCc7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLl9tZW1vaXplZElzUlRMOwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5wb3NpdGlvblRhcmdldCA9IHRoaXMucG9zaXRpb25UYXJnZXQgfHwgdGhpcy5fZGVmYXVsdFBvc2l0aW9uVGFyZ2V0OwogICAgICAgIGlmICh0aGlzLmF1dG9GaXRPbkF0dGFjaCkgewogICAgICAgICAgaWYgKHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKHRoaXMpLmRpc3BsYXkgPT09ICdub25lJykgewogICAgICAgICAgICBzZXRUaW1lb3V0KGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHRoaXMuZml0KCk7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvLyBOT1RFOiBzaGFkeWRvbSBhcHBsaWVzIGRpc3RyaWJ1dGlvbiBhc3luY2hyb25vdXNseQogICAgICAgICAgICAvLyBmb3IgcGVyZm9ybWFuY2UgcmVhc29ucyB3ZWJjb21wb25lbnRzL3NoYWR5ZG9tIzEyMAogICAgICAgICAgICAvLyBGbHVzaCB0byBnZXQgY29ycmVjdCBsYXlvdXQgaW5mby4KICAgICAgICAgICAgd2luZG93LlNoYWR5RE9NICYmIFNoYWR5RE9NLmZsdXNoKCk7CiAgICAgICAgICAgIHRoaXMuZml0KCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX19kZWZlcnJlZEZpdCkgewogICAgICAgICAgY2xlYXJUaW1lb3V0KHRoaXMuX19kZWZlcnJlZEZpdCk7CiAgICAgICAgICB0aGlzLl9fZGVmZXJyZWRGaXQgPSBudWxsOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBQb3NpdGlvbnMgYW5kIGZpdHMgdGhlIGVsZW1lbnQgaW50byB0aGUgYGZpdEludG9gIGVsZW1lbnQuCiAgICAgICAqLwogICAgICBmaXQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucG9zaXRpb24oKTsKICAgICAgICB0aGlzLmNvbnN0cmFpbigpOwogICAgICAgIHRoaXMuY2VudGVyKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogTWVtb2l6ZSBpbmZvcm1hdGlvbiBuZWVkZWQgdG8gcG9zaXRpb24gYW5kIHNpemUgdGhlIHRhcmdldCBlbGVtZW50LgogICAgICAgKiBAc3VwcHJlc3Mge2RlcHJlY2F0ZWR9CiAgICAgICAqLwogICAgICBfZGlzY292ZXJJbmZvOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fZml0SW5mbykgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB2YXIgdGFyZ2V0ID0gd2luZG93LmdldENvbXB1dGVkU3R5bGUodGhpcyk7CiAgICAgICAgdmFyIHNpemVyID0gd2luZG93LmdldENvbXB1dGVkU3R5bGUodGhpcy5zaXppbmdUYXJnZXQpOwoKICAgICAgICB0aGlzLl9maXRJbmZvID0gewogICAgICAgICAgaW5saW5lU3R5bGU6IHsKICAgICAgICAgICAgdG9wOiB0aGlzLnN0eWxlLnRvcCB8fCAnJywKICAgICAgICAgICAgbGVmdDogdGhpcy5zdHlsZS5sZWZ0IHx8ICcnLAogICAgICAgICAgICBwb3NpdGlvbjogdGhpcy5zdHlsZS5wb3NpdGlvbiB8fCAnJwogICAgICAgICAgfSwKICAgICAgICAgIHNpemVySW5saW5lU3R5bGU6IHsKICAgICAgICAgICAgbWF4V2lkdGg6IHRoaXMuc2l6aW5nVGFyZ2V0LnN0eWxlLm1heFdpZHRoIHx8ICcnLAogICAgICAgICAgICBtYXhIZWlnaHQ6IHRoaXMuc2l6aW5nVGFyZ2V0LnN0eWxlLm1heEhlaWdodCB8fCAnJywKICAgICAgICAgICAgYm94U2l6aW5nOiB0aGlzLnNpemluZ1RhcmdldC5zdHlsZS5ib3hTaXppbmcgfHwgJycKICAgICAgICAgIH0sCiAgICAgICAgICBwb3NpdGlvbmVkQnk6IHsKICAgICAgICAgICAgdmVydGljYWxseTogdGFyZ2V0LnRvcCAhPT0gJ2F1dG8nID8KICAgICAgICAgICAgICAgICd0b3AnIDoKICAgICAgICAgICAgICAgICh0YXJnZXQuYm90dG9tICE9PSAnYXV0bycgPyAnYm90dG9tJyA6IG51bGwpLAogICAgICAgICAgICBob3Jpem9udGFsbHk6IHRhcmdldC5sZWZ0ICE9PSAnYXV0bycgPwogICAgICAgICAgICAgICAgJ2xlZnQnIDoKICAgICAgICAgICAgICAgICh0YXJnZXQucmlnaHQgIT09ICdhdXRvJyA/ICdyaWdodCcgOiBudWxsKQogICAgICAgICAgfSwKICAgICAgICAgIHNpemVkQnk6IHsKICAgICAgICAgICAgaGVpZ2h0OiBzaXplci5tYXhIZWlnaHQgIT09ICdub25lJywKICAgICAgICAgICAgd2lkdGg6IHNpemVyLm1heFdpZHRoICE9PSAnbm9uZScsCiAgICAgICAgICAgIG1pbldpZHRoOiBwYXJzZUludChzaXplci5taW5XaWR0aCwgMTApIHx8IDAsCiAgICAgICAgICAgIG1pbkhlaWdodDogcGFyc2VJbnQoc2l6ZXIubWluSGVpZ2h0LCAxMCkgfHwgMAogICAgICAgICAgfSwKICAgICAgICAgIG1hcmdpbjogewogICAgICAgICAgICB0b3A6IHBhcnNlSW50KHRhcmdldC5tYXJnaW5Ub3AsIDEwKSB8fCAwLAogICAgICAgICAgICByaWdodDogcGFyc2VJbnQodGFyZ2V0Lm1hcmdpblJpZ2h0LCAxMCkgfHwgMCwKICAgICAgICAgICAgYm90dG9tOiBwYXJzZUludCh0YXJnZXQubWFyZ2luQm90dG9tLCAxMCkgfHwgMCwKICAgICAgICAgICAgbGVmdDogcGFyc2VJbnQodGFyZ2V0Lm1hcmdpbkxlZnQsIDEwKSB8fCAwCiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXNldHMgdGhlIHRhcmdldCBlbGVtZW50J3MgcG9zaXRpb24gYW5kIHNpemUgY29uc3RyYWludHMsIGFuZCBjbGVhcgogICAgICAgKiB0aGUgbWVtb2l6ZWQgZGF0YS4KICAgICAgICovCiAgICAgIHJlc2V0Rml0OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaW5mbyA9IHRoaXMuX2ZpdEluZm8gfHwge307CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gaW5mby5zaXplcklubGluZVN0eWxlKSB7CiAgICAgICAgICB0aGlzLnNpemluZ1RhcmdldC5zdHlsZVtwcm9wZXJ0eV0gPSBpbmZvLnNpemVySW5saW5lU3R5bGVbcHJvcGVydHldOwogICAgICAgIH0KICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiBpbmZvLmlubGluZVN0eWxlKSB7CiAgICAgICAgICB0aGlzLnN0eWxlW3Byb3BlcnR5XSA9IGluZm8uaW5saW5lU3R5bGVbcHJvcGVydHldOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fZml0SW5mbyA9IG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRXF1aXZhbGVudCB0byBjYWxsaW5nIGByZXNldEZpdCgpYCBhbmQgYGZpdCgpYC4gVXNlZnVsIHRvIGNhbGwgdGhpcyBhZnRlcgogICAgICAgKiB0aGUgZWxlbWVudCBvciB0aGUgYGZpdEludG9gIGVsZW1lbnQgaGFzIGJlZW4gcmVzaXplZCwgb3IgaWYgYW55IG9mIHRoZQogICAgICAgKiBwb3NpdGlvbmluZyBwcm9wZXJ0aWVzIChlLmcuIGBob3Jpem9udGFsQWxpZ24sIHZlcnRpY2FsQWxpZ25gKSBpcyB1cGRhdGVkLgogICAgICAgKiBJdCBwcmVzZXJ2ZXMgdGhlIHNjcm9sbCBwb3NpdGlvbiBvZiB0aGUgc2l6aW5nVGFyZ2V0LgogICAgICAgKi8KICAgICAgcmVmaXQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY3JvbGxMZWZ0ID0gdGhpcy5zaXppbmdUYXJnZXQuc2Nyb2xsTGVmdDsKICAgICAgICB2YXIgc2Nyb2xsVG9wID0gdGhpcy5zaXppbmdUYXJnZXQuc2Nyb2xsVG9wOwogICAgICAgIHRoaXMucmVzZXRGaXQoKTsKICAgICAgICB0aGlzLmZpdCgpOwogICAgICAgIHRoaXMuc2l6aW5nVGFyZ2V0LnNjcm9sbExlZnQgPSBzY3JvbGxMZWZ0OwogICAgICAgIHRoaXMuc2l6aW5nVGFyZ2V0LnNjcm9sbFRvcCA9IHNjcm9sbFRvcDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBQb3NpdGlvbnMgdGhlIGVsZW1lbnQgYWNjb3JkaW5nIHRvIGBob3Jpem9udGFsQWxpZ24sIHZlcnRpY2FsQWxpZ25gLgogICAgICAgKi8KICAgICAgcG9zaXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICghdGhpcy5fX3Nob3VsZFBvc2l0aW9uKSB7CiAgICAgICAgICAvLyBuZWVkcyB0byBiZSBjZW50ZXJlZCwgYW5kIGl0IGlzIGRvbmUgYWZ0ZXIgY29uc3RyYWluLgogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB0aGlzLl9kaXNjb3ZlckluZm8oKTsKCiAgICAgICAgdGhpcy5zdHlsZS5wb3NpdGlvbiA9ICdmaXhlZCc7CiAgICAgICAgLy8gTmVlZCBib3JkZXItYm94IGZvciBtYXJnaW4vcGFkZGluZy4KICAgICAgICB0aGlzLnNpemluZ1RhcmdldC5zdHlsZS5ib3hTaXppbmcgPSAnYm9yZGVyLWJveCc7CiAgICAgICAgLy8gU2V0IHRvIDAsIDAgaW4gb3JkZXIgdG8gZGlzY292ZXIgYW55IG9mZnNldCBjYXVzZWQgYnkgcGFyZW50IHN0YWNraW5nCiAgICAgICAgLy8gY29udGV4dHMuCiAgICAgICAgdGhpcy5zdHlsZS5sZWZ0ID0gJzBweCc7CiAgICAgICAgdGhpcy5zdHlsZS50b3AgPSAnMHB4JzsKCiAgICAgICAgdmFyIHJlY3QgPSB0aGlzLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciBwb3NpdGlvblJlY3QgPSB0aGlzLl9fZ2V0Tm9ybWFsaXplZFJlY3QodGhpcy5wb3NpdGlvblRhcmdldCk7CiAgICAgICAgdmFyIGZpdFJlY3QgPSB0aGlzLl9fZ2V0Tm9ybWFsaXplZFJlY3QodGhpcy5maXRJbnRvKTsKCiAgICAgICAgdmFyIG1hcmdpbiA9IHRoaXMuX2ZpdEluZm8ubWFyZ2luOwoKICAgICAgICAvLyBDb25zaWRlciB0aGUgbWFyZ2luIGFzIHBhcnQgb2YgdGhlIHNpemUgZm9yIHBvc2l0aW9uIGNhbGN1bGF0aW9ucy4KICAgICAgICB2YXIgc2l6ZSA9IHsKICAgICAgICAgIHdpZHRoOiByZWN0LndpZHRoICsgbWFyZ2luLmxlZnQgKyBtYXJnaW4ucmlnaHQsCiAgICAgICAgICBoZWlnaHQ6IHJlY3QuaGVpZ2h0ICsgbWFyZ2luLnRvcCArIG1hcmdpbi5ib3R0b20KICAgICAgICB9OwoKICAgICAgICB2YXIgcG9zaXRpb24gPSB0aGlzLl9fZ2V0UG9zaXRpb24oCiAgICAgICAgICAgIHRoaXMuX2xvY2FsZUhvcml6b250YWxBbGlnbiwKICAgICAgICAgICAgdGhpcy52ZXJ0aWNhbEFsaWduLAogICAgICAgICAgICBzaXplLAogICAgICAgICAgICByZWN0LAogICAgICAgICAgICBwb3NpdGlvblJlY3QsCiAgICAgICAgICAgIGZpdFJlY3QpOwoKICAgICAgICB2YXIgbGVmdCA9IHBvc2l0aW9uLmxlZnQgKyBtYXJnaW4ubGVmdDsKICAgICAgICB2YXIgdG9wID0gcG9zaXRpb24udG9wICsgbWFyZ2luLnRvcDsKCiAgICAgICAgLy8gV2UgZmlyc3QgbGltaXQgcmlnaHQvYm90dG9tIHdpdGhpbiBmaXRJbnRvIHJlc3BlY3RpbmcgdGhlIG1hcmdpbiwKICAgICAgICAvLyB0aGVuIHVzZSB0aG9zZSB2YWx1ZXMgdG8gbGltaXQgdG9wL2xlZnQuCiAgICAgICAgdmFyIHJpZ2h0ID0gTWF0aC5taW4oZml0UmVjdC5yaWdodCAtIG1hcmdpbi5yaWdodCwgbGVmdCArIHJlY3Qud2lkdGgpOwogICAgICAgIHZhciBib3R0b20gPSBNYXRoLm1pbihmaXRSZWN0LmJvdHRvbSAtIG1hcmdpbi5ib3R0b20sIHRvcCArIHJlY3QuaGVpZ2h0KTsKCiAgICAgICAgLy8gS2VlcCBsZWZ0L3RvcCB3aXRoaW4gZml0SW50byByZXNwZWN0aW5nIHRoZSBtYXJnaW4uCiAgICAgICAgbGVmdCA9IE1hdGgubWF4KAogICAgICAgICAgICBmaXRSZWN0LmxlZnQgKyBtYXJnaW4ubGVmdCwKICAgICAgICAgICAgTWF0aC5taW4obGVmdCwgcmlnaHQgLSB0aGlzLl9maXRJbmZvLnNpemVkQnkubWluV2lkdGgpKTsKICAgICAgICB0b3AgPSBNYXRoLm1heCgKICAgICAgICAgICAgZml0UmVjdC50b3AgKyBtYXJnaW4udG9wLAogICAgICAgICAgICBNYXRoLm1pbih0b3AsIGJvdHRvbSAtIHRoaXMuX2ZpdEluZm8uc2l6ZWRCeS5taW5IZWlnaHQpKTsKCiAgICAgICAgLy8gVXNlIHJpZ2h0L2JvdHRvbSB0byBzZXQgbWF4V2lkdGgvbWF4SGVpZ2h0LCBhbmQgcmVzcGVjdAogICAgICAgIC8vIG1pbldpZHRoL21pbkhlaWdodC4KICAgICAgICB0aGlzLnNpemluZ1RhcmdldC5zdHlsZS5tYXhXaWR0aCA9CiAgICAgICAgICAgIE1hdGgubWF4KHJpZ2h0IC0gbGVmdCwgdGhpcy5fZml0SW5mby5zaXplZEJ5Lm1pbldpZHRoKSArICdweCc7CiAgICAgICAgdGhpcy5zaXppbmdUYXJnZXQuc3R5bGUubWF4SGVpZ2h0ID0KICAgICAgICAgICAgTWF0aC5tYXgoYm90dG9tIC0gdG9wLCB0aGlzLl9maXRJbmZvLnNpemVkQnkubWluSGVpZ2h0KSArICdweCc7CgogICAgICAgIC8vIFJlbW92ZSB0aGUgb2Zmc2V0IGNhdXNlZCBieSBhbnkgc3RhY2tpbmcgY29udGV4dC4KICAgICAgICB0aGlzLnN0eWxlLmxlZnQgPSAobGVmdCAtIHJlY3QubGVmdCkgKyAncHgnOwogICAgICAgIHRoaXMuc3R5bGUudG9wID0gKHRvcCAtIHJlY3QudG9wKSArICdweCc7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ29uc3RyYWlucyB0aGUgc2l6ZSBvZiB0aGUgZWxlbWVudCB0byBgZml0SW50b2AgYnkgc2V0dGluZyBgbWF4LWhlaWdodGAKICAgICAgICogYW5kL29yIGBtYXgtd2lkdGhgLgogICAgICAgKi8KICAgICAgY29uc3RyYWluOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fX3Nob3VsZFBvc2l0aW9uKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuX2Rpc2NvdmVySW5mbygpOwoKICAgICAgICB2YXIgaW5mbyA9IHRoaXMuX2ZpdEluZm87CiAgICAgICAgLy8gcG9zaXRpb24gYXQgKDBweCwgMHB4KSBpZiBub3QgYWxyZWFkeSBwb3NpdGlvbmVkLCBzbyB3ZSBjYW4gbWVhc3VyZSB0aGUKICAgICAgICAvLyBuYXR1cmFsIHNpemUuCiAgICAgICAgaWYgKCFpbmZvLnBvc2l0aW9uZWRCeS52ZXJ0aWNhbGx5KSB7CiAgICAgICAgICB0aGlzLnN0eWxlLnBvc2l0aW9uID0gJ2ZpeGVkJzsKICAgICAgICAgIHRoaXMuc3R5bGUudG9wID0gJzBweCc7CiAgICAgICAgfQogICAgICAgIGlmICghaW5mby5wb3NpdGlvbmVkQnkuaG9yaXpvbnRhbGx5KSB7CiAgICAgICAgICB0aGlzLnN0eWxlLnBvc2l0aW9uID0gJ2ZpeGVkJzsKICAgICAgICAgIHRoaXMuc3R5bGUubGVmdCA9ICcwcHgnOwogICAgICAgIH0KCiAgICAgICAgLy8gbmVlZCBib3JkZXItYm94IGZvciBtYXJnaW4vcGFkZGluZwogICAgICAgIHRoaXMuc2l6aW5nVGFyZ2V0LnN0eWxlLmJveFNpemluZyA9ICdib3JkZXItYm94JzsKICAgICAgICAvLyBjb25zdHJhaW4gdGhlIHdpZHRoIGFuZCBoZWlnaHQgaWYgbm90IGFscmVhZHkgc2V0CiAgICAgICAgdmFyIHJlY3QgPSB0aGlzLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIGlmICghaW5mby5zaXplZEJ5LmhlaWdodCkgewogICAgICAgICAgdGhpcy5fX3NpemVEaW1lbnNpb24oCiAgICAgICAgICAgICAgcmVjdCwgaW5mby5wb3NpdGlvbmVkQnkudmVydGljYWxseSwgJ3RvcCcsICdib3R0b20nLCAnSGVpZ2h0Jyk7CiAgICAgICAgfQogICAgICAgIGlmICghaW5mby5zaXplZEJ5LndpZHRoKSB7CiAgICAgICAgICB0aGlzLl9fc2l6ZURpbWVuc2lvbigKICAgICAgICAgICAgICByZWN0LCBpbmZvLnBvc2l0aW9uZWRCeS5ob3Jpem9udGFsbHksICdsZWZ0JywgJ3JpZ2h0JywgJ1dpZHRoJyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICogQGRlcHJlY2F0ZWQKICAgICAgICovCiAgICAgIF9zaXplRGltZW5zaW9uOiBmdW5jdGlvbihyZWN0LCBwb3NpdGlvbmVkQnksIHN0YXJ0LCBlbmQsIGV4dGVudCkgewogICAgICAgIHRoaXMuX19zaXplRGltZW5zaW9uKHJlY3QsIHBvc2l0aW9uZWRCeSwgc3RhcnQsIGVuZCwgZXh0ZW50KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX19zaXplRGltZW5zaW9uOiBmdW5jdGlvbihyZWN0LCBwb3NpdGlvbmVkQnksIHN0YXJ0LCBlbmQsIGV4dGVudCkgewogICAgICAgIHZhciBpbmZvID0gdGhpcy5fZml0SW5mbzsKICAgICAgICB2YXIgZml0UmVjdCA9IHRoaXMuX19nZXROb3JtYWxpemVkUmVjdCh0aGlzLmZpdEludG8pOwogICAgICAgIHZhciBtYXggPSBleHRlbnQgPT09ICdXaWR0aCcgPyBmaXRSZWN0LndpZHRoIDogZml0UmVjdC5oZWlnaHQ7CiAgICAgICAgdmFyIGZsaXAgPSAocG9zaXRpb25lZEJ5ID09PSBlbmQpOwogICAgICAgIHZhciBvZmZzZXQgPSBmbGlwID8gbWF4IC0gcmVjdFtlbmRdIDogcmVjdFtzdGFydF07CiAgICAgICAgdmFyIG1hcmdpbiA9IGluZm8ubWFyZ2luW2ZsaXAgPyBzdGFydCA6IGVuZF07CiAgICAgICAgdmFyIG9mZnNldEV4dGVudCA9ICdvZmZzZXQnICsgZXh0ZW50OwogICAgICAgIHZhciBzaXppbmdPZmZzZXQgPSB0aGlzW29mZnNldEV4dGVudF0gLSB0aGlzLnNpemluZ1RhcmdldFtvZmZzZXRFeHRlbnRdOwogICAgICAgIHRoaXMuc2l6aW5nVGFyZ2V0LnN0eWxlWydtYXgnICsgZXh0ZW50XSA9CiAgICAgICAgICAgIChtYXggLSBtYXJnaW4gLSBvZmZzZXQgLSBzaXppbmdPZmZzZXQpICsgJ3B4JzsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDZW50ZXJzIGhvcml6b250YWxseSBhbmQgdmVydGljYWxseSBpZiBub3QgYWxyZWFkeSBwb3NpdGlvbmVkLiBUaGlzIGFsc28KICAgICAgICogc2V0cyBgcG9zaXRpb246Zml4ZWRgLgogICAgICAgKi8KICAgICAgY2VudGVyOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fX3Nob3VsZFBvc2l0aW9uKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuX2Rpc2NvdmVySW5mbygpOwoKICAgICAgICB2YXIgcG9zaXRpb25lZEJ5ID0gdGhpcy5fZml0SW5mby5wb3NpdGlvbmVkQnk7CiAgICAgICAgaWYgKHBvc2l0aW9uZWRCeS52ZXJ0aWNhbGx5ICYmIHBvc2l0aW9uZWRCeS5ob3Jpem9udGFsbHkpIHsKICAgICAgICAgIC8vIEFscmVhZHkgcG9zaXRpb25lZC4KICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgLy8gTmVlZCBwb3NpdGlvbjpmaXhlZCB0byBjZW50ZXIKICAgICAgICB0aGlzLnN0eWxlLnBvc2l0aW9uID0gJ2ZpeGVkJzsKICAgICAgICAvLyBUYWtlIGludG8gYWNjb3VudCB0aGUgb2Zmc2V0IGNhdXNlZCBieSBwYXJlbnRzIHRoYXQgY3JlYXRlIHN0YWNraW5nCiAgICAgICAgLy8gY29udGV4dHMgKGUuZy4gd2l0aCB0cmFuc2Zvcm06IHRyYW5zbGF0ZTNkKS4gVHJhbnNsYXRlIHRvIDAsMCBhbmQKICAgICAgICAvLyBtZWFzdXJlIHRoZSBib3VuZGluZyByZWN0LgogICAgICAgIGlmICghcG9zaXRpb25lZEJ5LnZlcnRpY2FsbHkpIHsKICAgICAgICAgIHRoaXMuc3R5bGUudG9wID0gJzBweCc7CiAgICAgICAgfQogICAgICAgIGlmICghcG9zaXRpb25lZEJ5Lmhvcml6b250YWxseSkgewogICAgICAgICAgdGhpcy5zdHlsZS5sZWZ0ID0gJzBweCc7CiAgICAgICAgfQogICAgICAgIC8vIEl0IHdpbGwgdGFrZSBpbiBjb25zaWRlcmF0aW9uIG1hcmdpbnMgYW5kIHRyYW5zZm9ybXMKICAgICAgICB2YXIgcmVjdCA9IHRoaXMuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgdmFyIGZpdFJlY3QgPSB0aGlzLl9fZ2V0Tm9ybWFsaXplZFJlY3QodGhpcy5maXRJbnRvKTsKICAgICAgICBpZiAoIXBvc2l0aW9uZWRCeS52ZXJ0aWNhbGx5KSB7CiAgICAgICAgICB2YXIgdG9wID0gZml0UmVjdC50b3AgLSByZWN0LnRvcCArIChmaXRSZWN0LmhlaWdodCAtIHJlY3QuaGVpZ2h0KSAvIDI7CiAgICAgICAgICB0aGlzLnN0eWxlLnRvcCA9IHRvcCArICdweCc7CiAgICAgICAgfQogICAgICAgIGlmICghcG9zaXRpb25lZEJ5Lmhvcml6b250YWxseSkgewogICAgICAgICAgdmFyIGxlZnQgPSBmaXRSZWN0LmxlZnQgLSByZWN0LmxlZnQgKyAoZml0UmVjdC53aWR0aCAtIHJlY3Qud2lkdGgpIC8gMjsKICAgICAgICAgIHRoaXMuc3R5bGUubGVmdCA9IGxlZnQgKyAncHgnOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9fZ2V0Tm9ybWFsaXplZFJlY3Q6IGZ1bmN0aW9uKHRhcmdldCkgewogICAgICAgIGlmICh0YXJnZXQgPT09IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCB8fCB0YXJnZXQgPT09IHdpbmRvdykgewogICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgdG9wOiAwLAogICAgICAgICAgICBsZWZ0OiAwLAogICAgICAgICAgICB3aWR0aDogd2luZG93LmlubmVyV2lkdGgsCiAgICAgICAgICAgIGhlaWdodDogd2luZG93LmlubmVySGVpZ2h0LAogICAgICAgICAgICByaWdodDogd2luZG93LmlubmVyV2lkdGgsCiAgICAgICAgICAgIGJvdHRvbTogd2luZG93LmlubmVySGVpZ2h0CiAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGFyZ2V0LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICB9LAoKICAgICAgX19nZXRPZmZzY3JlZW5BcmVhOiBmdW5jdGlvbihwb3NpdGlvbiwgc2l6ZSwgZml0UmVjdCkgewogICAgICAgIHZhciB2ZXJ0aWNhbENyb3AgPSBNYXRoLm1pbigwLCBwb3NpdGlvbi50b3ApICsKICAgICAgICAgICAgTWF0aC5taW4oMCwgZml0UmVjdC5ib3R0b20gLSAocG9zaXRpb24udG9wICsgc2l6ZS5oZWlnaHQpKTsKICAgICAgICB2YXIgaG9yaXpvbnRhbENyb3AgPSBNYXRoLm1pbigwLCBwb3NpdGlvbi5sZWZ0KSArCiAgICAgICAgICAgIE1hdGgubWluKDAsIGZpdFJlY3QucmlnaHQgLSAocG9zaXRpb24ubGVmdCArIHNpemUud2lkdGgpKTsKICAgICAgICByZXR1cm4gTWF0aC5hYnModmVydGljYWxDcm9wKSAqIHNpemUud2lkdGggKwogICAgICAgICAgICBNYXRoLmFicyhob3Jpem9udGFsQ3JvcCkgKiBzaXplLmhlaWdodDsKICAgICAgfSwKCgogICAgICBfX2dldFBvc2l0aW9uOiBmdW5jdGlvbigKICAgICAgICAgIGhBbGlnbiwgdkFsaWduLCBzaXplLCBzaXplTm9NYXJnaW5zLCBwb3NpdGlvblJlY3QsIGZpdFJlY3QpIHsKICAgICAgICAvLyBBbGwgdGhlIHBvc3NpYmxlIGNvbmZpZ3VyYXRpb25zLgogICAgICAgIC8vIE9yZGVyZWQgYXMgdG9wLWxlZnQsIHRvcC1yaWdodCwgYm90dG9tLWxlZnQsIGJvdHRvbS1yaWdodC4KICAgICAgICB2YXIgcG9zaXRpb25zID0gWwogICAgICAgICAgewogICAgICAgICAgICB2ZXJ0aWNhbEFsaWduOiAndG9wJywKICAgICAgICAgICAgaG9yaXpvbnRhbEFsaWduOiAnbGVmdCcsCiAgICAgICAgICAgIHRvcDogcG9zaXRpb25SZWN0LnRvcCArIHRoaXMudmVydGljYWxPZmZzZXQsCiAgICAgICAgICAgIGxlZnQ6IHBvc2l0aW9uUmVjdC5sZWZ0ICsgdGhpcy5ob3Jpem9udGFsT2Zmc2V0CiAgICAgICAgICB9LAogICAgICAgICAgewogICAgICAgICAgICB2ZXJ0aWNhbEFsaWduOiAndG9wJywKICAgICAgICAgICAgaG9yaXpvbnRhbEFsaWduOiAncmlnaHQnLAogICAgICAgICAgICB0b3A6IHBvc2l0aW9uUmVjdC50b3AgKyB0aGlzLnZlcnRpY2FsT2Zmc2V0LAogICAgICAgICAgICBsZWZ0OiBwb3NpdGlvblJlY3QucmlnaHQgLSBzaXplLndpZHRoIC0gdGhpcy5ob3Jpem9udGFsT2Zmc2V0CiAgICAgICAgICB9LAogICAgICAgICAgewogICAgICAgICAgICB2ZXJ0aWNhbEFsaWduOiAnYm90dG9tJywKICAgICAgICAgICAgaG9yaXpvbnRhbEFsaWduOiAnbGVmdCcsCiAgICAgICAgICAgIHRvcDogcG9zaXRpb25SZWN0LmJvdHRvbSAtIHNpemUuaGVpZ2h0IC0gdGhpcy52ZXJ0aWNhbE9mZnNldCwKICAgICAgICAgICAgbGVmdDogcG9zaXRpb25SZWN0LmxlZnQgKyB0aGlzLmhvcml6b250YWxPZmZzZXQKICAgICAgICAgIH0sCiAgICAgICAgICB7CiAgICAgICAgICAgIHZlcnRpY2FsQWxpZ246ICdib3R0b20nLAogICAgICAgICAgICBob3Jpem9udGFsQWxpZ246ICdyaWdodCcsCiAgICAgICAgICAgIHRvcDogcG9zaXRpb25SZWN0LmJvdHRvbSAtIHNpemUuaGVpZ2h0IC0gdGhpcy52ZXJ0aWNhbE9mZnNldCwKICAgICAgICAgICAgbGVmdDogcG9zaXRpb25SZWN0LnJpZ2h0IC0gc2l6ZS53aWR0aCAtIHRoaXMuaG9yaXpvbnRhbE9mZnNldAogICAgICAgICAgfQogICAgICAgIF07CgogICAgICAgIGlmICh0aGlzLm5vT3ZlcmxhcCkgewogICAgICAgICAgLy8gRHVwbGljYXRlLgogICAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBwb3NpdGlvbnMubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgICAgIHZhciBjb3B5ID0ge307CiAgICAgICAgICAgIGZvciAodmFyIGtleSBpbiBwb3NpdGlvbnNbaV0pIHsKICAgICAgICAgICAgICBjb3B5W2tleV0gPSBwb3NpdGlvbnNbaV1ba2V5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBwb3NpdGlvbnMucHVzaChjb3B5KTsKICAgICAgICAgIH0KICAgICAgICAgIC8vIEhvcml6b250YWwgb3ZlcmxhcCBvbmx5LgogICAgICAgICAgcG9zaXRpb25zWzBdLnRvcCA9IHBvc2l0aW9uc1sxXS50b3AgKz0gcG9zaXRpb25SZWN0LmhlaWdodDsKICAgICAgICAgIHBvc2l0aW9uc1syXS50b3AgPSBwb3NpdGlvbnNbM10udG9wIC09IHBvc2l0aW9uUmVjdC5oZWlnaHQ7CiAgICAgICAgICAvLyBWZXJ0aWNhbCBvdmVybGFwIG9ubHkuCiAgICAgICAgICBwb3NpdGlvbnNbNF0ubGVmdCA9IHBvc2l0aW9uc1s2XS5sZWZ0ICs9IHBvc2l0aW9uUmVjdC53aWR0aDsKICAgICAgICAgIHBvc2l0aW9uc1s1XS5sZWZ0ID0gcG9zaXRpb25zWzddLmxlZnQgLT0gcG9zaXRpb25SZWN0LndpZHRoOwogICAgICAgIH0KCiAgICAgICAgLy8gQ29uc2lkZXIgYXV0byBhcyBudWxsIGZvciBjb2RpbmcgY29udmVuaWVuY2UuCiAgICAgICAgdkFsaWduID0gdkFsaWduID09PSAnYXV0bycgPyBudWxsIDogdkFsaWduOwogICAgICAgIGhBbGlnbiA9IGhBbGlnbiA9PT0gJ2F1dG8nID8gbnVsbCA6IGhBbGlnbjsKCiAgICAgICAgaWYgKCFoQWxpZ24gfHwgaEFsaWduID09PSAnY2VudGVyJykgewogICAgICAgICAgcG9zaXRpb25zLnB1c2goewogICAgICAgICAgICB2ZXJ0aWNhbEFsaWduOiAndG9wJywKICAgICAgICAgICAgaG9yaXpvbnRhbEFsaWduOiAnY2VudGVyJywKICAgICAgICAgICAgdG9wOiBwb3NpdGlvblJlY3QudG9wICsgdGhpcy52ZXJ0aWNhbE9mZnNldCArCiAgICAgICAgICAgICAgICAodGhpcy5ub092ZXJsYXAgPyBwb3NpdGlvblJlY3QuaGVpZ2h0IDogMCksCiAgICAgICAgICAgIGxlZnQ6IHBvc2l0aW9uUmVjdC5sZWZ0IC0gc2l6ZU5vTWFyZ2lucy53aWR0aCAvIDIgKwogICAgICAgICAgICAgICAgcG9zaXRpb25SZWN0LndpZHRoIC8gMiArIHRoaXMuaG9yaXpvbnRhbE9mZnNldAogICAgICAgICAgfSk7CiAgICAgICAgICBwb3NpdGlvbnMucHVzaCh7CiAgICAgICAgICAgIHZlcnRpY2FsQWxpZ246ICdib3R0b20nLAogICAgICAgICAgICBob3Jpem9udGFsQWxpZ246ICdjZW50ZXInLAogICAgICAgICAgICB0b3A6IHBvc2l0aW9uUmVjdC5ib3R0b20gLSBzaXplLmhlaWdodCAtIHRoaXMudmVydGljYWxPZmZzZXQgLQogICAgICAgICAgICAgICAgKHRoaXMubm9PdmVybGFwID8gcG9zaXRpb25SZWN0LmhlaWdodCA6IDApLAogICAgICAgICAgICBsZWZ0OiBwb3NpdGlvblJlY3QubGVmdCAtIHNpemVOb01hcmdpbnMud2lkdGggLyAyICsKICAgICAgICAgICAgICAgIHBvc2l0aW9uUmVjdC53aWR0aCAvIDIgKyB0aGlzLmhvcml6b250YWxPZmZzZXQKICAgICAgICAgIH0pOwogICAgICAgIH0KCiAgICAgICAgaWYgKCF2QWxpZ24gfHwgdkFsaWduID09PSAnbWlkZGxlJykgewogICAgICAgICAgcG9zaXRpb25zLnB1c2goewogICAgICAgICAgICB2ZXJ0aWNhbEFsaWduOiAnbWlkZGxlJywKICAgICAgICAgICAgaG9yaXpvbnRhbEFsaWduOiAnbGVmdCcsCiAgICAgICAgICAgIHRvcDogcG9zaXRpb25SZWN0LnRvcCAtIHNpemVOb01hcmdpbnMuaGVpZ2h0IC8gMiArCiAgICAgICAgICAgICAgICBwb3NpdGlvblJlY3QuaGVpZ2h0IC8gMiArIHRoaXMudmVydGljYWxPZmZzZXQsCiAgICAgICAgICAgIGxlZnQ6IHBvc2l0aW9uUmVjdC5sZWZ0ICsgdGhpcy5ob3Jpem9udGFsT2Zmc2V0ICsKICAgICAgICAgICAgICAgICh0aGlzLm5vT3ZlcmxhcCA/IHBvc2l0aW9uUmVjdC53aWR0aCA6IDApCiAgICAgICAgICB9KTsKICAgICAgICAgIHBvc2l0aW9ucy5wdXNoKHsKICAgICAgICAgICAgdmVydGljYWxBbGlnbjogJ21pZGRsZScsCiAgICAgICAgICAgIGhvcml6b250YWxBbGlnbjogJ3JpZ2h0JywKICAgICAgICAgICAgdG9wOiBwb3NpdGlvblJlY3QudG9wIC0gc2l6ZU5vTWFyZ2lucy5oZWlnaHQgLyAyICsKICAgICAgICAgICAgICAgIHBvc2l0aW9uUmVjdC5oZWlnaHQgLyAyICsgdGhpcy52ZXJ0aWNhbE9mZnNldCwKICAgICAgICAgICAgbGVmdDogcG9zaXRpb25SZWN0LnJpZ2h0IC0gc2l6ZS53aWR0aCAtIHRoaXMuaG9yaXpvbnRhbE9mZnNldCAtCiAgICAgICAgICAgICAgICAodGhpcy5ub092ZXJsYXAgPyBwb3NpdGlvblJlY3Qud2lkdGggOiAwKQogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICBpZiAodkFsaWduID09PSAnbWlkZGxlJyAmJiBoQWxpZ24gPT09ICdjZW50ZXInKSB7CiAgICAgICAgICBwb3NpdGlvbnMucHVzaCh7CiAgICAgICAgICAgIHZlcnRpY2FsQWxpZ246ICdtaWRkbGUnLAogICAgICAgICAgICBob3Jpem9udGFsQWxpZ246ICdjZW50ZXInLAogICAgICAgICAgICB0b3A6IHBvc2l0aW9uUmVjdC50b3AgLSBzaXplTm9NYXJnaW5zLmhlaWdodCAvIDIgKwogICAgICAgICAgICAgICAgcG9zaXRpb25SZWN0LmhlaWdodCAvIDIgKyB0aGlzLnZlcnRpY2FsT2Zmc2V0LAogICAgICAgICAgICBsZWZ0OiBwb3NpdGlvblJlY3QubGVmdCAtIHNpemVOb01hcmdpbnMud2lkdGggLyAyICsKICAgICAgICAgICAgICAgIHBvc2l0aW9uUmVjdC53aWR0aCAvIDIgKyB0aGlzLmhvcml6b250YWxPZmZzZXQKICAgICAgICAgIH0pOwogICAgICAgIH0KCiAgICAgICAgdmFyIHBvc2l0aW9uOwogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcG9zaXRpb25zLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICB2YXIgY2FuZGlkYXRlID0gcG9zaXRpb25zW2ldOwogICAgICAgICAgdmFyIHZBbGlnbk9rID0gY2FuZGlkYXRlLnZlcnRpY2FsQWxpZ24gPT09IHZBbGlnbjsKICAgICAgICAgIHZhciBoQWxpZ25PayA9IGNhbmRpZGF0ZS5ob3Jpem9udGFsQWxpZ24gPT09IGhBbGlnbjsKCiAgICAgICAgICAvLyBJZiBib3RoIHZBbGlnbiBhbmQgaEFsaWduIGFyZSBkZWZpbmVkLCByZXR1cm4gZXhhY3QgbWF0Y2guCiAgICAgICAgICAvLyBGb3IgZHluYW1pY0FsaWduIGFuZCBub092ZXJsYXAgd2UnbGwgaGF2ZSBtb3JlIHRoYW4gb25lIGNhbmRpZGF0ZSwgc28KICAgICAgICAgIC8vIHdlJ2xsIGhhdmUgdG8gY2hlY2sgdGhlIG9mZnNjcmVlbkFyZWEgdG8gbWFrZSB0aGUgYmVzdCBjaG9pY2UuCiAgICAgICAgICBpZiAoIXRoaXMuZHluYW1pY0FsaWduICYmICF0aGlzLm5vT3ZlcmxhcCAmJiB2QWxpZ25PayAmJiBoQWxpZ25PaykgewogICAgICAgICAgICBwb3NpdGlvbiA9IGNhbmRpZGF0ZTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CgogICAgICAgICAgLy8gQWxpZ24gaXMgb2sgaWYgYWxpZ25tZW50IHByZWZlcmVuY2VzIGFyZSByZXNwZWN0ZWQuIElmIG5vIHByZWZlcmVuY2VzLAogICAgICAgICAgLy8gaXQgaXMgY29uc2lkZXJlZCBvay4KICAgICAgICAgIHZhciBhbGlnbk9rID0gKCF2QWxpZ24gfHwgdkFsaWduT2spICYmICghaEFsaWduIHx8IGhBbGlnbk9rKTsKCiAgICAgICAgICAvLyBGaWx0ZXIgb3V0IGVsZW1lbnRzIHRoYXQgZG9uJ3QgbWF0Y2ggdGhlIGFsaWdubWVudCAoaWYgZGVmaW5lZCkuCiAgICAgICAgICAvLyBXaXRoIGR5bmFtaWNBbGlnbiwgd2UgbmVlZCB0byBjb25zaWRlciBhbGwgdGhlIHBvc2l0aW9ucyB0byBmaW5kIHRoZQogICAgICAgICAgLy8gb25lIHRoYXQgbWluaW1pemVzIHRoZSBjcm9wcGVkIGFyZWEuCiAgICAgICAgICBpZiAoIXRoaXMuZHluYW1pY0FsaWduICYmICFhbGlnbk9rKSB7CiAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgfQoKICAgICAgICAgIGNhbmRpZGF0ZS5vZmZzY3JlZW5BcmVhID0KICAgICAgICAgICAgICB0aGlzLl9fZ2V0T2Zmc2NyZWVuQXJlYShjYW5kaWRhdGUsIHNpemUsIGZpdFJlY3QpOwogICAgICAgICAgLy8gSWYgbm90IGNyb3BwZWQgYW5kIHJlc3BlY3RzIHRoZSBhbGlnbiByZXF1aXJlbWVudHMsIGtlZXAgaXQuCiAgICAgICAgICAvLyBUaGlzIGFsbG93cyB0byBwcmVmZXIgcG9zaXRpb25zIG92ZXJsYXBwaW5nIGhvcml6b250YWxseSBvdmVyIHRoZQogICAgICAgICAgLy8gb25lcyBvdmVybGFwcGluZyB2ZXJ0aWNhbGx5LgogICAgICAgICAgaWYgKGNhbmRpZGF0ZS5vZmZzY3JlZW5BcmVhID09PSAwICYmIGFsaWduT2spIHsKICAgICAgICAgICAgcG9zaXRpb24gPSBjYW5kaWRhdGU7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgcG9zaXRpb24gPSBwb3NpdGlvbiB8fCBjYW5kaWRhdGU7CiAgICAgICAgICB2YXIgZGlmZiA9IGNhbmRpZGF0ZS5vZmZzY3JlZW5BcmVhIC0gcG9zaXRpb24ub2Zmc2NyZWVuQXJlYTsKICAgICAgICAgIC8vIENoZWNrIHdoaWNoIGNyb3BzIGxlc3MuIElmIGl0IGNyb3BzIGVxdWFsbHksIGNoZWNrIGlmIGF0IGxlYXN0IG9uZQogICAgICAgICAgLy8gYWxpZ24gc2V0dGluZyBpcyBvay4KICAgICAgICAgIGlmIChkaWZmIDwgMCB8fCAoZGlmZiA9PT0gMCAmJiAodkFsaWduT2sgfHwgaEFsaWduT2spKSkgewogICAgICAgICAgICBwb3NpdGlvbiA9IGNhbmRpZGF0ZTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHJldHVybiBwb3NpdGlvbjsKICAgICAgfQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE2IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgdmFyIHAkMSA9IEVsZW1lbnQucHJvdG90eXBlOwogICAgdmFyIG1hdGNoZXMkMSA9IHAkMS5tYXRjaGVzIHx8IHAkMS5tYXRjaGVzU2VsZWN0b3IgfHwgcCQxLm1vek1hdGNoZXNTZWxlY3RvciB8fAogICAgICAgIHAkMS5tc01hdGNoZXNTZWxlY3RvciB8fCBwJDEub01hdGNoZXNTZWxlY3RvciB8fCBwJDEud2Via2l0TWF0Y2hlc1NlbGVjdG9yOwoKICAgIGNsYXNzIElyb25Gb2N1c2FibGVzSGVscGVyQ2xhc3MgewogICAgICAvKioKICAgICAgICogUmV0dXJucyBhIHNvcnRlZCBhcnJheSBvZiB0YWJiYWJsZSBub2RlcywgaW5jbHVkaW5nIHRoZSByb290IG5vZGUuCiAgICAgICAqIEl0IHNlYXJjaGVzIHRoZSB0YWJiYWJsZSBub2RlcyBpbiB0aGUgbGlnaHQgYW5kIHNoYWRvdyBkb20gb2YgdGhlIGNoaWRyZW4sCiAgICAgICAqIHNvcnRpbmcgdGhlIHJlc3VsdCBieSB0YWJpbmRleC4KICAgICAgICogQHBhcmFtIHshTm9kZX0gbm9kZQogICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IUhUTUxFbGVtZW50Pn0KICAgICAgICovCiAgICAgIGdldFRhYmJhYmxlTm9kZXMobm9kZSkgewogICAgICAgIHZhciByZXN1bHQgPSBbXTsKICAgICAgICAvLyBJZiB0aGVyZSBpcyBhdCBsZWFzdCBvbmUgZWxlbWVudCB3aXRoIHRhYmluZGV4ID4gMCwgd2UgbmVlZCB0byBzb3J0CiAgICAgICAgLy8gdGhlIGZpbmFsIGFycmF5IGJ5IHRhYmluZGV4LgogICAgICAgIHZhciBuZWVkc1NvcnRCeVRhYkluZGV4ID0gdGhpcy5fY29sbGVjdFRhYmJhYmxlTm9kZXMobm9kZSwgcmVzdWx0KTsKICAgICAgICBpZiAobmVlZHNTb3J0QnlUYWJJbmRleCkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX3NvcnRCeVRhYkluZGV4KHJlc3VsdCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGlmIGEgZWxlbWVudCBpcyBmb2N1c2FibGUuCiAgICAgICAqIEBwYXJhbSB7IUhUTUxFbGVtZW50fSBlbGVtZW50CiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgICAqLwogICAgICBpc0ZvY3VzYWJsZShlbGVtZW50KSB7CiAgICAgICAgLy8gRnJvbSBodHRwOi8vc3RhY2tvdmVyZmxvdy5jb20vYS8xNjAwMTk0LzQyMjg3MDM6CiAgICAgICAgLy8gVGhlcmUgaXNuJ3QgYSBkZWZpbml0ZSBsaXN0LCBpdCdzIHVwIHRvIHRoZSBicm93c2VyLiBUaGUgb25seQogICAgICAgIC8vIHN0YW5kYXJkIHdlIGhhdmUgaXMgRE9NIExldmVsIDIgSFRNTAogICAgICAgIC8vIGh0dHBzOi8vd3d3LnczLm9yZy9UUi9ET00tTGV2ZWwtMi1IVE1ML2h0bWwuaHRtbCwgYWNjb3JkaW5nIHRvIHdoaWNoIHRoZQogICAgICAgIC8vIG9ubHkgZWxlbWVudHMgdGhhdCBoYXZlIGEgZm9jdXMoKSBtZXRob2QgYXJlIEhUTUxJbnB1dEVsZW1lbnQsCiAgICAgICAgLy8gSFRNTFNlbGVjdEVsZW1lbnQsIEhUTUxUZXh0QXJlYUVsZW1lbnQgYW5kIEhUTUxBbmNob3JFbGVtZW50LiBUaGlzCiAgICAgICAgLy8gbm90YWJseSBvbWl0cyBIVE1MQnV0dG9uRWxlbWVudCBhbmQgSFRNTEFyZWFFbGVtZW50LiBSZWZlcnJpbmcgdG8gdGhlc2UKICAgICAgICAvLyB0ZXN0cyB3aXRoIHRhYmJhYmxlcyBpbiBkaWZmZXJlbnQgYnJvd3NlcnMKICAgICAgICAvLyBodHRwOi8vYWxseWpzLmlvL2RhdGEtdGFibGVzL2ZvY3VzYWJsZS5odG1sCgogICAgICAgIC8vIEVsZW1lbnRzIHRoYXQgY2Fubm90IGJlIGZvY3VzZWQgaWYgdGhleSBoYXZlIFtkaXNhYmxlZF0gYXR0cmlidXRlLgogICAgICAgIGlmIChtYXRjaGVzJDEuY2FsbChlbGVtZW50LCAnaW5wdXQsIHNlbGVjdCwgdGV4dGFyZWEsIGJ1dHRvbiwgb2JqZWN0JykpIHsKICAgICAgICAgIHJldHVybiBtYXRjaGVzJDEuY2FsbChlbGVtZW50LCAnOm5vdChbZGlzYWJsZWRdKScpOwogICAgICAgIH0KICAgICAgICAvLyBFbGVtZW50cyB0aGF0IGNhbiBiZSBmb2N1c2VkIGV2ZW4gaWYgdGhleSBoYXZlIFtkaXNhYmxlZF0gYXR0cmlidXRlLgogICAgICAgIHJldHVybiBtYXRjaGVzJDEuY2FsbCgKICAgICAgICAgICAgZWxlbWVudCwgJ2FbaHJlZl0sIGFyZWFbaHJlZl0sIGlmcmFtZSwgW3RhYmluZGV4XSwgW2NvbnRlbnRFZGl0YWJsZV0nKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgaWYgYSBlbGVtZW50IGlzIHRhYmJhYmxlLiBUbyBiZSB0YWJiYWJsZSwgYSBlbGVtZW50IG11c3QgYmUKICAgICAgICogZm9jdXNhYmxlLCB2aXNpYmxlLCBhbmQgd2l0aCBhIHRhYmluZGV4ICE9PSAtMS4KICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICovCiAgICAgIGlzVGFiYmFibGUoZWxlbWVudCkgewogICAgICAgIHJldHVybiB0aGlzLmlzRm9jdXNhYmxlKGVsZW1lbnQpICYmCiAgICAgICAgICAgIG1hdGNoZXMkMS5jYWxsKGVsZW1lbnQsICc6bm90KFt0YWJpbmRleD0iLTEiXSknKSAmJgogICAgICAgICAgICB0aGlzLl9pc1Zpc2libGUoZWxlbWVudCk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBub3JtYWxpemVkIGVsZW1lbnQgdGFiaW5kZXguIElmIG5vdCBmb2N1c2FibGUsIHJldHVybnMgLTEuCiAgICAgICAqIEl0IGNoZWNrcyBmb3IgdGhlIGF0dHJpYnV0ZSAidGFiaW5kZXgiIGluc3RlYWQgb2YgdGhlIGVsZW1lbnQgcHJvcGVydHkKICAgICAgICogYHRhYkluZGV4YCBzaW5jZSBicm93c2VycyBhc3NpZ24gZGlmZmVyZW50IHZhbHVlcyB0byBpdC4KICAgICAgICogZS5nLiBpbiBGaXJlZm94IGA8ZGl2IGNvbnRlbnRlZGl0YWJsZT5gIGhhcyBgdGFiSW5kZXggPSAtMWAKICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAgICogQHJldHVybiB7IW51bWJlcn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9ub3JtYWxpemVkVGFiSW5kZXgoZWxlbWVudCkgewogICAgICAgIGlmICh0aGlzLmlzRm9jdXNhYmxlKGVsZW1lbnQpKSB7CiAgICAgICAgICB2YXIgdGFiSW5kZXggPSBlbGVtZW50LmdldEF0dHJpYnV0ZSgndGFiaW5kZXgnKSB8fCAwOwogICAgICAgICAgcmV0dXJuIE51bWJlcih0YWJJbmRleCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiAtMTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFNlYXJjaGVzIGZvciBub2RlcyB0aGF0IGFyZSB0YWJiYWJsZSBhbmQgYWRkcyB0aGVtIHRvIHRoZSBgcmVzdWx0YCBhcnJheS4KICAgICAgICogUmV0dXJucyBpZiB0aGUgYHJlc3VsdGAgYXJyYXkgbmVlZHMgdG8gYmUgc29ydGVkIGJ5IHRhYmluZGV4LgogICAgICAgKiBAcGFyYW0geyFOb2RlfSBub2RlIFRoZSBzdGFydGluZyBwb2ludCBmb3IgdGhlIHNlYXJjaDsgYWRkZWQgdG8gYHJlc3VsdGAKICAgICAgICogaWYgdGFiYmFibGUuCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PCFIVE1MRWxlbWVudD59IHJlc3VsdAogICAgICAgKiBAcmV0dXJuIHtib29sZWFufQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX2NvbGxlY3RUYWJiYWJsZU5vZGVzKG5vZGUsIHJlc3VsdCkgewogICAgICAgIC8vIElmIG5vdCBhbiBlbGVtZW50IG9yIG5vdCB2aXNpYmxlLCBubyBuZWVkIHRvIGV4cGxvcmUgY2hpbGRyZW4uCiAgICAgICAgaWYgKG5vZGUubm9kZVR5cGUgIT09IE5vZGUuRUxFTUVOVF9OT0RFKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIHZhciBlbGVtZW50ID0gLyoqIEB0eXBlIHshSFRNTEVsZW1lbnR9ICovIChub2RlKTsKICAgICAgICBpZiAoIXRoaXMuX2lzVmlzaWJsZShlbGVtZW50KSkgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICB2YXIgdGFiSW5kZXggPSB0aGlzLl9ub3JtYWxpemVkVGFiSW5kZXgoZWxlbWVudCk7CiAgICAgICAgdmFyIG5lZWRzU29ydCA9IHRhYkluZGV4ID4gMDsKICAgICAgICBpZiAodGFiSW5kZXggPj0gMCkgewogICAgICAgICAgcmVzdWx0LnB1c2goZWxlbWVudCk7CiAgICAgICAgfQogICAgICAgIC8vIEluIFNoYWRvd0RPTSB2MSwgdGFiIG9yZGVyIGlzIGFmZmVjdGVkIGJ5IHRoZSBvcmRlciBvZiBkaXN0cnVidXRpb24uCiAgICAgICAgLy8gRS5nLiBnZXRUYWJiYWJsZU5vZGVzKCNyb290KSBpbiBTaGFkb3dET00gdjEgc2hvdWxkIHJldHVybiBbI0EsICNCXTsKICAgICAgICAvLyBpbiBTaGFkb3dET00gdjAgdGFiIG9yZGVyIGlzIG5vdCBhZmZlY3RlZCBieSB0aGUgZGlzdHJ1YnV0aW9uIG9yZGVyLAogICAgICAgIC8vIGluIGZhY3QgZ2V0VGFiYmFibGVOb2Rlcygjcm9vdCkgcmV0dXJucyBbI0IsICNBXS4KICAgICAgICAvLyAgPGRpdiBpZD0icm9vdCI+CiAgICAgICAgLy8gICA8IS0tIHNoYWRvdyAtLT4KICAgICAgICAvLyAgICAgPHNsb3QgbmFtZT0iYSI+CiAgICAgICAgLy8gICAgIDxzbG90IG5hbWU9ImIiPgogICAgICAgIC8vICAgPCEtLSAvc2hhZG93IC0tPgogICAgICAgIC8vICAgPGlucHV0IGlkPSJBIiBzbG90PSJhIj4KICAgICAgICAvLyAgIDxpbnB1dCBpZD0iQiIgc2xvdD0iYiIgdGFiaW5kZXg9IjEiPgogICAgICAgIC8vICA8L2Rpdj4KICAgICAgICAvLyBUT0RPKHZhbGRyaW4pIHN1cHBvcnQgU2hhZG93RE9NIHYxIHdoZW4gdXBncmFkaW5nIHRvIFBvbHltZXIgdjIuMC4KICAgICAgICB2YXIgY2hpbGRyZW47CiAgICAgICAgaWYgKGVsZW1lbnQubG9jYWxOYW1lID09PSAnY29udGVudCcgfHwgZWxlbWVudC5sb2NhbE5hbWUgPT09ICdzbG90JykgewogICAgICAgICAgY2hpbGRyZW4gPSBkb20oZWxlbWVudCkuZ2V0RGlzdHJpYnV0ZWROb2RlcygpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBVc2Ugc2hhZG93IHJvb3QgaWYgcG9zc2libGUsIHdpbGwgY2hlY2sgZm9yIGRpc3RyaWJ1dGVkIG5vZGVzLgogICAgICAgICAgY2hpbGRyZW4gPSBkb20oZWxlbWVudC5yb290IHx8IGVsZW1lbnQpLmNoaWxkcmVuOwogICAgICAgIH0KICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGNoaWxkcmVuLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAvLyBFbnN1cmUgbWV0aG9kIGlzIGFsd2F5cyBpbnZva2VkIHRvIGNvbGxlY3QgdGFiYmFibGUgY2hpbGRyZW4uCiAgICAgICAgICBuZWVkc1NvcnQgPSB0aGlzLl9jb2xsZWN0VGFiYmFibGVOb2RlcyhjaGlsZHJlbltpXSwgcmVzdWx0KSB8fCBuZWVkc1NvcnQ7CiAgICAgICAgfQogICAgICAgIHJldHVybiBuZWVkc1NvcnQ7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGZhbHNlIGlmIHRoZSBlbGVtZW50IGhhcyBgdmlzaWJpbGl0eTogaGlkZGVuYCBvciBgZGlzcGxheTogbm9uZWAKICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGVsZW1lbnQKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9pc1Zpc2libGUoZWxlbWVudCkgewogICAgICAgIC8vIENoZWNrIGlubGluZSBzdHlsZSBmaXJzdCB0byBzYXZlIGEgcmUtZmxvdy4gSWYgbG9va3MgZ29vZCwgY2hlY2sgYWxzbwogICAgICAgIC8vIGNvbXB1dGVkIHN0eWxlLgogICAgICAgIHZhciBzdHlsZSA9IGVsZW1lbnQuc3R5bGU7CiAgICAgICAgaWYgKHN0eWxlLnZpc2liaWxpdHkgIT09ICdoaWRkZW4nICYmIHN0eWxlLmRpc3BsYXkgIT09ICdub25lJykgewogICAgICAgICAgc3R5bGUgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZShlbGVtZW50KTsKICAgICAgICAgIHJldHVybiAoc3R5bGUudmlzaWJpbGl0eSAhPT0gJ2hpZGRlbicgJiYgc3R5bGUuZGlzcGxheSAhPT0gJ25vbmUnKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogU29ydHMgYW4gYXJyYXkgb2YgdGFiYmFibGUgZWxlbWVudHMgYnkgdGFiaW5kZXguIFJldHVybnMgYSBuZXcgYXJyYXkuCiAgICAgICAqIEBwYXJhbSB7IUFycmF5PCFIVE1MRWxlbWVudD59IHRhYmJhYmxlcwogICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IUhUTUxFbGVtZW50Pn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9zb3J0QnlUYWJJbmRleCh0YWJiYWJsZXMpIHsKICAgICAgICAvLyBJbXBsZW1lbnQgYSBtZXJnZSBzb3J0IGFzIEFycmF5LnByb3RvdHlwZS5zb3J0IGRvZXMgYSBub24tc3RhYmxlIHNvcnQKICAgICAgICAvLyBodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9BcnJheS9zb3J0CiAgICAgICAgdmFyIGxlbiA9IHRhYmJhYmxlcy5sZW5ndGg7CiAgICAgICAgaWYgKGxlbiA8IDIpIHsKICAgICAgICAgIHJldHVybiB0YWJiYWJsZXM7CiAgICAgICAgfQogICAgICAgIHZhciBwaXZvdCA9IE1hdGguY2VpbChsZW4gLyAyKTsKICAgICAgICB2YXIgbGVmdCA9IHRoaXMuX3NvcnRCeVRhYkluZGV4KHRhYmJhYmxlcy5zbGljZSgwLCBwaXZvdCkpOwogICAgICAgIHZhciByaWdodCA9IHRoaXMuX3NvcnRCeVRhYkluZGV4KHRhYmJhYmxlcy5zbGljZShwaXZvdCkpOwogICAgICAgIHJldHVybiB0aGlzLl9tZXJnZVNvcnRCeVRhYkluZGV4KGxlZnQsIHJpZ2h0KTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIE1lcmdlIHNvcnQgaXRlcmF0b3IsIG1lcmdlcyB0aGUgdHdvIGFycmF5cyBpbnRvIG9uZSwgc29ydGVkIGJ5IHRhYiBpbmRleC4KICAgICAgICogQHBhcmFtIHshQXJyYXk8IUhUTUxFbGVtZW50Pn0gbGVmdAogICAgICAgKiBAcGFyYW0geyFBcnJheTwhSFRNTEVsZW1lbnQ+fSByaWdodAogICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IUhUTUxFbGVtZW50Pn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9tZXJnZVNvcnRCeVRhYkluZGV4KGxlZnQsIHJpZ2h0KSB7CiAgICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICAgIHdoaWxlICgobGVmdC5sZW5ndGggPiAwKSAmJiAocmlnaHQubGVuZ3RoID4gMCkpIHsKICAgICAgICAgIGlmICh0aGlzLl9oYXNMb3dlclRhYk9yZGVyKGxlZnRbMF0sIHJpZ2h0WzBdKSkgewogICAgICAgICAgICByZXN1bHQucHVzaChyaWdodC5zaGlmdCgpKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHJlc3VsdC5wdXNoKGxlZnQuc2hpZnQoKSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gcmVzdWx0LmNvbmNhdChsZWZ0LCByaWdodCk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGlmIGVsZW1lbnQgYGFgIGhhcyBsb3dlciB0YWIgb3JkZXIgY29tcGFyZWQgdG8gZWxlbWVudCBgYmAKICAgICAgICogKGJvdGggZWxlbWVudHMgYXJlIGFzc3VtZWQgdG8gYmUgZm9jdXNhYmxlIGFuZCB0YWJiYWJsZSkuCiAgICAgICAqIEVsZW1lbnRzIHdpdGggdGFiaW5kZXggPSAwIGhhdmUgbG93ZXIgdGFiIG9yZGVyIGNvbXBhcmVkIHRvIGVsZW1lbnRzCiAgICAgICAqIHdpdGggdGFiaW5kZXggPiAwLgogICAgICAgKiBJZiBib3RoIGhhdmUgc2FtZSB0YWJpbmRleCwgaXQgcmV0dXJucyBmYWxzZS4KICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGEKICAgICAgICogQHBhcmFtIHshSFRNTEVsZW1lbnR9IGIKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9oYXNMb3dlclRhYk9yZGVyKGEsIGIpIHsKICAgICAgICAvLyBOb3JtYWxpemUgdGFiSW5kZXhlcwogICAgICAgIC8vIGUuZy4gaW4gRmlyZWZveCBgPGRpdiBjb250ZW50ZWRpdGFibGU+YCBoYXMgYHRhYkluZGV4ID0gLTFgCiAgICAgICAgdmFyIGF0aSA9IE1hdGgubWF4KGEudGFiSW5kZXgsIDApOwogICAgICAgIHZhciBidGkgPSBNYXRoLm1heChiLnRhYkluZGV4LCAwKTsKICAgICAgICByZXR1cm4gKGF0aSA9PT0gMCB8fCBidGkgPT09IDApID8gYnRpID4gYXRpIDogYXRpID4gYnRpOwogICAgICB9CiAgICB9CgogICAgY29uc3QgSXJvbkZvY3VzYWJsZXNIZWxwZXIgPSBuZXcgSXJvbkZvY3VzYWJsZXNIZWxwZXJDbGFzcygpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qCiAgICBgaXJvbi1vdmVybGF5LWJhY2tkcm9wYCBpcyBhIGJhY2tkcm9wIHVzZWQgYnkgYFBvbHltZXIuSXJvbk92ZXJsYXlCZWhhdmlvcmAuIEl0CiAgICBzaG91bGQgYmUgYSBzaW5nbGV0b24uCgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZy4KCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLQogICAgYC0taXJvbi1vdmVybGF5LWJhY2tkcm9wLWJhY2tncm91bmQtY29sb3JgIHwgQmFja2Ryb3AgYmFja2dyb3VuZCBjb2xvciB8ICMwMDAKICAgIGAtLWlyb24tb3ZlcmxheS1iYWNrZHJvcC1vcGFjaXR5YCAgICAgICAgICB8IEJhY2tkcm9wIG9wYWNpdHkgfCAwLjYKICAgIGAtLWlyb24tb3ZlcmxheS1iYWNrZHJvcGAgICAgICAgICAgICAgICAgICB8IE1peGluIGFwcGxpZWQgdG8gYGlyb24tb3ZlcmxheS1iYWNrZHJvcGAuICAgICAgICAgICAgICAgICAgICAgIHwge30KICAgIGAtLWlyb24tb3ZlcmxheS1iYWNrZHJvcC1vcGVuZWRgICAgICAgICAgICB8IE1peGluIGFwcGxpZWQgdG8gYGlyb24tb3ZlcmxheS1iYWNrZHJvcGAgd2hlbiBpdCBpcyBkaXNwbGF5ZWQgfCB7fQogICAgKi8KICAgIFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIHBvc2l0aW9uOiBmaXhlZDsKICAgICAgICB0b3A6IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0taXJvbi1vdmVybGF5LWJhY2tkcm9wLWJhY2tncm91bmQtY29sb3IsICMwMDApOwogICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgdHJhbnNpdGlvbjogb3BhY2l0eSAwLjJzOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIEBhcHBseSAtLWlyb24tb3ZlcmxheS1iYWNrZHJvcDsKICAgICAgfQoKICAgICAgOmhvc3QoLm9wZW5lZCkgewogICAgICAgIG9wYWNpdHk6IHZhcigtLWlyb24tb3ZlcmxheS1iYWNrZHJvcC1vcGFjaXR5LCAwLjYpOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBhdXRvOwogICAgICAgIEBhcHBseSAtLWlyb24tb3ZlcmxheS1iYWNrZHJvcC1vcGVuZWQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgLAoKICAgICAgaXM6ICdpcm9uLW92ZXJsYXktYmFja2Ryb3AnLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhlIGJhY2tkcm9wIGlzIG9wZW5lZC4KICAgICAgICAgKi8KICAgICAgICBvcGVuZWQ6IHsKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICBvYnNlcnZlcjogJ19vcGVuZWRDaGFuZ2VkJywKICAgICAgICB9CgogICAgICB9LAoKICAgICAgbGlzdGVuZXJzOiB7CiAgICAgICAgJ3RyYW5zaXRpb25lbmQnOiAnX29uVHJhbnNpdGlvbmVuZCcsCiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGNyZWF0ZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFVzZWQgdG8gY2FuY2VsIHByZXZpb3VzIHJlcXVlc3RBbmltYXRpb25GcmFtZSBjYWxscyB3aGVuIG9wZW5lZCBjaGFuZ2VzLgogICAgICAgIHRoaXMuX19vcGVuZWRSYWYgPSBudWxsOwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5vcGVuZWQgJiYgdGhpcy5fb3BlbmVkQ2hhbmdlZCh0aGlzLm9wZW5lZCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQXBwZW5kcyB0aGUgYmFja2Ryb3AgdG8gZG9jdW1lbnQgYm9keSBpZiBuZWVkZWQuCiAgICAgICAqLwogICAgICBwcmVwYXJlOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5vcGVuZWQgJiYgIXRoaXMucGFyZW50Tm9kZSkgewogICAgICAgICAgZG9tKGRvY3VtZW50LmJvZHkpLmFwcGVuZENoaWxkKHRoaXMpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTaG93cyB0aGUgYmFja2Ryb3AuCiAgICAgICAqLwogICAgICBvcGVuOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLm9wZW5lZCA9IHRydWU7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSGlkZXMgdGhlIGJhY2tkcm9wLgogICAgICAgKi8KICAgICAgY2xvc2U6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMub3BlbmVkID0gZmFsc2U7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVtb3ZlcyB0aGUgYmFja2Ryb3AgZnJvbSBkb2N1bWVudCBib2R5IGlmIG5lZWRlZC4KICAgICAgICovCiAgICAgIGNvbXBsZXRlOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIXRoaXMub3BlbmVkICYmIHRoaXMucGFyZW50Tm9kZSA9PT0gZG9jdW1lbnQuYm9keSkgewogICAgICAgICAgZG9tKHRoaXMucGFyZW50Tm9kZSkucmVtb3ZlQ2hpbGQodGhpcyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX29uVHJhbnNpdGlvbmVuZDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoZXZlbnQgJiYgZXZlbnQudGFyZ2V0ID09PSB0aGlzKSB7CiAgICAgICAgICB0aGlzLmNvbXBsZXRlKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gb3BlbmVkCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfb3BlbmVkQ2hhbmdlZDogZnVuY3Rpb24ob3BlbmVkKSB7CiAgICAgICAgaWYgKG9wZW5lZCkgewogICAgICAgICAgLy8gQXV0by1hdHRhY2guCiAgICAgICAgICB0aGlzLnByZXBhcmUoKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gQW5pbWF0aW9uIG1pZ2h0IGJlIGRpc2FibGVkIHZpYSB0aGUgbWl4aW4gb3Igb3BhY2l0eSBjdXN0b20gcHJvcGVydHkuCiAgICAgICAgICAvLyBJZiBpdCBpcyBkaXNhYmxlZCBpbiBvdGhlciB3YXlzLCBpdCdzIHVwIHRvIHRoZSB1c2VyIHRvIGNhbGwgY29tcGxldGUuCiAgICAgICAgICB2YXIgY3MgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZSh0aGlzKTsKICAgICAgICAgIGlmIChjcy50cmFuc2l0aW9uRHVyYXRpb24gPT09ICcwcycgfHwgY3Mub3BhY2l0eSA9PSAwKSB7CiAgICAgICAgICAgIHRoaXMuY29tcGxldGUoKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmICghdGhpcy5pc0F0dGFjaGVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBBbHdheXMgY2FuY2VsIHByZXZpb3VzIHJlcXVlc3RBbmltYXRpb25GcmFtZS4KICAgICAgICBpZiAodGhpcy5fX29wZW5lZFJhZikgewogICAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX19vcGVuZWRSYWYpOwogICAgICAgICAgdGhpcy5fX29wZW5lZFJhZiA9IG51bGw7CiAgICAgICAgfQogICAgICAgIC8vIEZvcmNlIHJlbGF5b3V0IHRvIGVuc3VyZSBwcm9wZXIgdHJhbnNpdGlvbnMuCiAgICAgICAgdGhpcy5zY3JvbGxUb3AgPSB0aGlzLnNjcm9sbFRvcDsKICAgICAgICB0aGlzLl9fb3BlbmVkUmFmID0gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZShmdW5jdGlvbigpIHsKICAgICAgICAgIHRoaXMuX19vcGVuZWRSYWYgPSBudWxsOwogICAgICAgICAgdGhpcy50b2dnbGVDbGFzcygnb3BlbmVkJywgdGhpcy5vcGVuZWQpOwogICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogQHBhY2thZ2UKICAgICAqLwogICAgY2xhc3MgSXJvbk92ZXJsYXlNYW5hZ2VyQ2xhc3MgewogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAvKioKICAgICAgICAgKiBVc2VkIHRvIGtlZXAgdHJhY2sgb2YgdGhlIG9wZW5lZCBvdmVybGF5cy4KICAgICAgICAgKiBAcHJpdmF0ZSB7IUFycmF5PCFFbGVtZW50Pn0KICAgICAgICAgKi8KICAgICAgICB0aGlzLl9vdmVybGF5cyA9IFtdOwoKICAgICAgICAvKioKICAgICAgICAgKiBpZnJhbWVzIGhhdmUgYSBkZWZhdWx0IHotaW5kZXggb2YgMTAwLAogICAgICAgICAqIHNvIHRoaXMgZGVmYXVsdCBzaG91bGQgYmUgYXQgbGVhc3QgdGhhdC4KICAgICAgICAgKiBAcHJpdmF0ZSB7bnVtYmVyfQogICAgICAgICAqLwogICAgICAgIHRoaXMuX21pbmltdW1aID0gMTAxOwoKICAgICAgICAvKioKICAgICAgICAgKiBNZW1vaXplZCBiYWNrZHJvcCBlbGVtZW50LgogICAgICAgICAqIEBwcml2YXRlIHtFbGVtZW50fG51bGx9CiAgICAgICAgICovCiAgICAgICAgdGhpcy5fYmFja2Ryb3BFbGVtZW50ID0gbnVsbDsKCiAgICAgICAgLy8gRW5hYmxlIGRvY3VtZW50LXdpZGUgdGFwIHJlY29nbml6ZXIuCiAgICAgICAgLy8gTk9URTogVXNlIHVzZUNhcHR1cmU9dHJ1ZSB0byBhdm9pZCBhY2NpZGVudGFsbHkgcHJldmVudGlvbiBvZiB0aGUgY2xvc2luZwogICAgICAgIC8vIG9mIGFuIG92ZXJsYXkgdmlhIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpLiBUaGUgb25seSB3YXkgdG8gcHJldmVudAogICAgICAgIC8vIGNsb3Npbmcgb2YgYW4gb3ZlcmxheSBzaG91bGQgYmUgdGhyb3VnaCBpdHMgQVBJcy4KICAgICAgICAvLyBOT1RFOiBlbmFibGUgdGFwIG9uIDxodG1sPiB0byB3b3JrYXJvdW5kIFBvbHltZXIvcG9seW1lciM0NDU5CiAgICAgICAgLy8gUGFzcyBuby1vcCBmdW5jdGlvbiBiZWNhdXNlIE1TRWRnZSAxNSBkb2Vzbid0IGhhbmRsZSBudWxsIGFzIDJuZCBhcmd1bWVudAogICAgICAgIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS9NaWNyb3NvZnQvQ2hha3JhQ29yZS9pc3N1ZXMvMzg2MwogICAgICAgIGFkZExpc3RlbmVyKGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwgJ3RhcCcsIGZ1bmN0aW9uKCkge30pOwogICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ3RhcCcsIHRoaXMuX29uQ2FwdHVyZUNsaWNrLmJpbmQodGhpcyksIHRydWUpOwogICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3VzJywgdGhpcy5fb25DYXB0dXJlRm9jdXMuYmluZCh0aGlzKSwgdHJ1ZSk7CiAgICAgICAgZG9jdW1lbnQuYWRkRXZlbnRMaXN0ZW5lcigKICAgICAgICAgICAgJ2tleWRvd24nLCB0aGlzLl9vbkNhcHR1cmVLZXlEb3duLmJpbmQodGhpcyksIHRydWUpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIHNoYXJlZCBiYWNrZHJvcCBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshRWxlbWVudH0gYmFja2Ryb3BFbGVtZW50CiAgICAgICAqLwogICAgICBnZXQgYmFja2Ryb3BFbGVtZW50KCkgewogICAgICAgIGlmICghdGhpcy5fYmFja2Ryb3BFbGVtZW50KSB7CiAgICAgICAgICB0aGlzLl9iYWNrZHJvcEVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdpcm9uLW92ZXJsYXktYmFja2Ryb3AnKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRoaXMuX2JhY2tkcm9wRWxlbWVudDsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRoZSBkZWVwZXN0IGFjdGl2ZSBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshRWxlbWVudH0gYWN0aXZlRWxlbWVudCB0aGUgYWN0aXZlIGVsZW1lbnQKICAgICAgICovCiAgICAgIGdldCBkZWVwQWN0aXZlRWxlbWVudCgpIHsKICAgICAgICB2YXIgYWN0aXZlID0gZG9jdW1lbnQuYWN0aXZlRWxlbWVudDsKICAgICAgICAvLyBkb2N1bWVudC5hY3RpdmVFbGVtZW50IGNhbiBiZSBudWxsCiAgICAgICAgLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQVBJL0RvY3VtZW50L2FjdGl2ZUVsZW1lbnQKICAgICAgICAvLyBJbiBJRSAxMSwgaXQgY2FuIGFsc28gYmUgYW4gb2JqZWN0IHdoZW4gb3BlcmF0aW5nIGluIGlmcmFtZXMuCiAgICAgICAgLy8gSW4gdGhlc2UgY2FzZXMsIGRlZmF1bHQgaXQgdG8gZG9jdW1lbnQuYm9keS4KICAgICAgICBpZiAoIWFjdGl2ZSB8fCBhY3RpdmUgaW5zdGFuY2VvZiBFbGVtZW50ID09PSBmYWxzZSkgewogICAgICAgICAgYWN0aXZlID0gZG9jdW1lbnQuYm9keTsKICAgICAgICB9CiAgICAgICAgd2hpbGUgKGFjdGl2ZS5yb290ICYmIGRvbShhY3RpdmUucm9vdCkuYWN0aXZlRWxlbWVudCkgewogICAgICAgICAgYWN0aXZlID0gZG9tKGFjdGl2ZS5yb290KS5hY3RpdmVFbGVtZW50OwogICAgICAgIH0KICAgICAgICByZXR1cm4gYWN0aXZlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQnJpbmdzIHRoZSBvdmVybGF5IGF0IHRoZSBzcGVjaWZpZWQgaW5kZXggdG8gdGhlIGZyb250LgogICAgICAgKiBAcGFyYW0ge251bWJlcn0gaQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX2JyaW5nT3ZlcmxheUF0SW5kZXhUb0Zyb250KGkpIHsKICAgICAgICB2YXIgb3ZlcmxheSA9IHRoaXMuX292ZXJsYXlzW2ldOwogICAgICAgIGlmICghb3ZlcmxheSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB2YXIgbGFzdEkgPSB0aGlzLl9vdmVybGF5cy5sZW5ndGggLSAxOwogICAgICAgIHZhciBjdXJyZW50T3ZlcmxheSA9IHRoaXMuX292ZXJsYXlzW2xhc3RJXTsKICAgICAgICAvLyBFbnN1cmUgYWx3YXlzLW9uLXRvcCBvdmVybGF5IHN0YXlzIG9uIHRvcC4KICAgICAgICBpZiAoY3VycmVudE92ZXJsYXkgJiYKICAgICAgICAgICAgdGhpcy5fc2hvdWxkQmVCZWhpbmRPdmVybGF5KG92ZXJsYXksIGN1cnJlbnRPdmVybGF5KSkgewogICAgICAgICAgbGFzdEktLTsKICAgICAgICB9CiAgICAgICAgLy8gSWYgYWxyZWFkeSB0aGUgdG9wIGVsZW1lbnQsIHJldHVybi4KICAgICAgICBpZiAoaSA+PSBsYXN0SSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICAvLyBVcGRhdGUgei1pbmRleCB0byBiZSBvbiB0b3AuCiAgICAgICAgdmFyIG1pbmltdW1aID0gTWF0aC5tYXgodGhpcy5jdXJyZW50T3ZlcmxheVooKSwgdGhpcy5fbWluaW11bVopOwogICAgICAgIGlmICh0aGlzLl9nZXRaKG92ZXJsYXkpIDw9IG1pbmltdW1aKSB7CiAgICAgICAgICB0aGlzLl9hcHBseU92ZXJsYXlaKG92ZXJsYXksIG1pbmltdW1aKTsKICAgICAgICB9CgogICAgICAgIC8vIFNoaWZ0IG90aGVyIG92ZXJsYXlzIGJlaGluZCB0aGUgbmV3IG9uIHRvcC4KICAgICAgICB3aGlsZSAoaSA8IGxhc3RJKSB7CiAgICAgICAgICB0aGlzLl9vdmVybGF5c1tpXSA9IHRoaXMuX292ZXJsYXlzW2kgKyAxXTsKICAgICAgICAgIGkrKzsKICAgICAgICB9CiAgICAgICAgdGhpcy5fb3ZlcmxheXNbbGFzdEldID0gb3ZlcmxheTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEFkZHMgdGhlIG92ZXJsYXkgYW5kIHVwZGF0ZXMgaXRzIHotaW5kZXggaWYgaXQncyBvcGVuZWQsIG9yIHJlbW92ZXMgaXQgaWYKICAgICAgICogaXQncyBjbG9zZWQuIEFsc28gdXBkYXRlcyB0aGUgYmFja2Ryb3Agei1pbmRleC4KICAgICAgICogQHBhcmFtIHshRWxlbWVudH0gb3ZlcmxheQogICAgICAgKi8KICAgICAgYWRkT3JSZW1vdmVPdmVybGF5KG92ZXJsYXkpIHsKICAgICAgICBpZiAob3ZlcmxheS5vcGVuZWQpIHsKICAgICAgICAgIHRoaXMuYWRkT3ZlcmxheShvdmVybGF5KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5yZW1vdmVPdmVybGF5KG92ZXJsYXkpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFRyYWNrcyBvdmVybGF5cyBmb3Igei1pbmRleCBhbmQgZm9jdXMgbWFuYWdlbWVudC4KICAgICAgICogRW5zdXJlcyB0aGUgbGFzdCBhZGRlZCBvdmVybGF5IHdpdGggYWx3YXlzLW9uLXRvcCByZW1haW5zIG9uIHRvcC4KICAgICAgICogQHBhcmFtIHshRWxlbWVudH0gb3ZlcmxheQogICAgICAgKi8KICAgICAgYWRkT3ZlcmxheShvdmVybGF5KSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9vdmVybGF5cy5pbmRleE9mKG92ZXJsYXkpOwogICAgICAgIGlmIChpID49IDApIHsKICAgICAgICAgIHRoaXMuX2JyaW5nT3ZlcmxheUF0SW5kZXhUb0Zyb250KGkpOwogICAgICAgICAgdGhpcy50cmFja0JhY2tkcm9wKCk7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHZhciBpbnNlcnRpb25JbmRleCA9IHRoaXMuX292ZXJsYXlzLmxlbmd0aDsKICAgICAgICB2YXIgY3VycmVudE92ZXJsYXkgPSB0aGlzLl9vdmVybGF5c1tpbnNlcnRpb25JbmRleCAtIDFdOwogICAgICAgIHZhciBtaW5pbXVtWiA9IE1hdGgubWF4KHRoaXMuX2dldFooY3VycmVudE92ZXJsYXkpLCB0aGlzLl9taW5pbXVtWik7CiAgICAgICAgdmFyIG5ld1ogPSB0aGlzLl9nZXRaKG92ZXJsYXkpOwoKICAgICAgICAvLyBFbnN1cmUgYWx3YXlzLW9uLXRvcCBvdmVybGF5IHN0YXlzIG9uIHRvcC4KICAgICAgICBpZiAoY3VycmVudE92ZXJsYXkgJiYKICAgICAgICAgICAgdGhpcy5fc2hvdWxkQmVCZWhpbmRPdmVybGF5KG92ZXJsYXksIGN1cnJlbnRPdmVybGF5KSkgewogICAgICAgICAgLy8gVGhpcyBidW1wcyB0aGUgei1pbmRleCBvZiArMi4KICAgICAgICAgIHRoaXMuX2FwcGx5T3ZlcmxheVooY3VycmVudE92ZXJsYXksIG1pbmltdW1aKTsKICAgICAgICAgIGluc2VydGlvbkluZGV4LS07CiAgICAgICAgICAvLyBVcGRhdGUgbWluaW11bVogdG8gbWF0Y2ggcHJldmlvdXMgb3ZlcmxheSdzIHotaW5kZXguCiAgICAgICAgICB2YXIgcHJldmlvdXNPdmVybGF5ID0gdGhpcy5fb3ZlcmxheXNbaW5zZXJ0aW9uSW5kZXggLSAxXTsKICAgICAgICAgIG1pbmltdW1aID0gTWF0aC5tYXgodGhpcy5fZ2V0WihwcmV2aW91c092ZXJsYXkpLCB0aGlzLl9taW5pbXVtWik7CiAgICAgICAgfQoKICAgICAgICAvLyBVcGRhdGUgei1pbmRleCBhbmQgaW5zZXJ0IG92ZXJsYXkuCiAgICAgICAgaWYgKG5ld1ogPD0gbWluaW11bVopIHsKICAgICAgICAgIHRoaXMuX2FwcGx5T3ZlcmxheVoob3ZlcmxheSwgbWluaW11bVopOwogICAgICAgIH0KICAgICAgICB0aGlzLl9vdmVybGF5cy5zcGxpY2UoaW5zZXJ0aW9uSW5kZXgsIDAsIG92ZXJsYXkpOwoKICAgICAgICB0aGlzLnRyYWNrQmFja2Ryb3AoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IUVsZW1lbnR9IG92ZXJsYXkKICAgICAgICovCiAgICAgIHJlbW92ZU92ZXJsYXkob3ZlcmxheSkgewogICAgICAgIHZhciBpID0gdGhpcy5fb3ZlcmxheXMuaW5kZXhPZihvdmVybGF5KTsKICAgICAgICBpZiAoaSA9PT0gLTEpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpcy5fb3ZlcmxheXMuc3BsaWNlKGksIDEpOwoKICAgICAgICB0aGlzLnRyYWNrQmFja2Ryb3AoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIGN1cnJlbnQgb3ZlcmxheS4KICAgICAgICogQHJldHVybiB7IUVsZW1lbnR8dW5kZWZpbmVkfQogICAgICAgKi8KICAgICAgY3VycmVudE92ZXJsYXkoKSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9vdmVybGF5cy5sZW5ndGggLSAxOwogICAgICAgIHJldHVybiB0aGlzLl9vdmVybGF5c1tpXTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIGN1cnJlbnQgb3ZlcmxheSB6LWluZGV4LgogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9CiAgICAgICAqLwogICAgICBjdXJyZW50T3ZlcmxheVooKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2dldFoodGhpcy5jdXJyZW50T3ZlcmxheSgpKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEVuc3VyZXMgdGhhdCB0aGUgbWluaW11bSB6LWluZGV4IG9mIG5ldyBvdmVybGF5cyBpcyBhdCBsZWFzdCBgbWluaW11bVpgLgogICAgICAgKiBUaGlzIGRvZXMgbm90IGVmZmVjdCB0aGUgei1pbmRleCBvZiBhbnkgZXhpc3Rpbmcgb3ZlcmxheXMuCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBtaW5pbXVtWgogICAgICAgKi8KICAgICAgZW5zdXJlTWluaW11bVoobWluaW11bVopIHsKICAgICAgICB0aGlzLl9taW5pbXVtWiA9IE1hdGgubWF4KHRoaXMuX21pbmltdW1aLCBtaW5pbXVtWik7CiAgICAgIH0KCiAgICAgIGZvY3VzT3ZlcmxheSgpIHsKICAgICAgICB2YXIgY3VycmVudCA9IC8qKiBAdHlwZSB7P30gKi8gKHRoaXMuY3VycmVudE92ZXJsYXkoKSk7CiAgICAgICAgaWYgKGN1cnJlbnQpIHsKICAgICAgICAgIGN1cnJlbnQuX2FwcGx5Rm9jdXMoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBVcGRhdGVzIHRoZSBiYWNrZHJvcCB6LWluZGV4LgogICAgICAgKi8KICAgICAgdHJhY2tCYWNrZHJvcCgpIHsKICAgICAgICB2YXIgb3ZlcmxheSA9IHRoaXMuX292ZXJsYXlXaXRoQmFja2Ryb3AoKTsKICAgICAgICAvLyBBdm9pZCBjcmVhdGluZyB0aGUgYmFja2Ryb3AgaWYgdGhlcmUgaXMgbm8gb3ZlcmxheSB3aXRoIGJhY2tkcm9wLgogICAgICAgIGlmICghb3ZlcmxheSAmJiAhdGhpcy5fYmFja2Ryb3BFbGVtZW50KSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuYmFja2Ryb3BFbGVtZW50LnN0eWxlLnpJbmRleCA9IHRoaXMuX2dldFoob3ZlcmxheSkgLSAxOwogICAgICAgIHRoaXMuYmFja2Ryb3BFbGVtZW50Lm9wZW5lZCA9ICEhb3ZlcmxheTsKICAgICAgICAvLyBQcm9wZXJ0eSBvYnNlcnZlcnMgYXJlIG5vdCBmaXJlZCB1bnRpbCBlbGVtZW50IGlzIGF0dGFjaGVkCiAgICAgICAgLy8gaW4gUG9seW1lciAyLngsIHNvIHdlIGVuc3VyZSBlbGVtZW50IGlzIGF0dGFjaGVkIGlmIG5lZWRlZC4KICAgICAgICAvLyBodHRwczovL2dpdGh1Yi5jb20vUG9seW1lci9wb2x5bWVyL2lzc3Vlcy80NTI2CiAgICAgICAgdGhpcy5iYWNrZHJvcEVsZW1lbnQucHJlcGFyZSgpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHJldHVybiB7IUFycmF5PCFFbGVtZW50Pn0KICAgICAgICovCiAgICAgIGdldEJhY2tkcm9wcygpIHsKICAgICAgICB2YXIgYmFja2Ryb3BzID0gW107CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLl9vdmVybGF5cy5sZW5ndGg7IGkrKykgewogICAgICAgICAgaWYgKHRoaXMuX292ZXJsYXlzW2ldLndpdGhCYWNrZHJvcCkgewogICAgICAgICAgICBiYWNrZHJvcHMucHVzaCh0aGlzLl9vdmVybGF5c1tpXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBiYWNrZHJvcHM7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSB6LWluZGV4IGZvciB0aGUgYmFja2Ryb3AuCiAgICAgICAqIEByZXR1cm4ge251bWJlcn0KICAgICAgICovCiAgICAgIGJhY2tkcm9wWigpIHsKICAgICAgICByZXR1cm4gdGhpcy5fZ2V0Wih0aGlzLl9vdmVybGF5V2l0aEJhY2tkcm9wKCkpIC0gMTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIHRvcCBvcGVuZWQgb3ZlcmxheSB0aGF0IGhhcyBhIGJhY2tkcm9wLgogICAgICAgKiBAcmV0dXJuIHshRWxlbWVudHx1bmRlZmluZWR9CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfb3ZlcmxheVdpdGhCYWNrZHJvcCgpIHsKICAgICAgICBmb3IgKHZhciBpID0gdGhpcy5fb3ZlcmxheXMubGVuZ3RoIC0gMTsgaSA+PSAwOyBpLS0pIHsKICAgICAgICAgIGlmICh0aGlzLl9vdmVybGF5c1tpXS53aXRoQmFja2Ryb3ApIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX292ZXJsYXlzW2ldOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIENhbGN1bGF0ZXMgdGhlIG1pbmltdW0gei1pbmRleCBmb3IgdGhlIG92ZXJsYXkuCiAgICAgICAqIEBwYXJhbSB7RWxlbWVudD19IG92ZXJsYXkKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9nZXRaKG92ZXJsYXkpIHsKICAgICAgICB2YXIgeiA9IHRoaXMuX21pbmltdW1aOwogICAgICAgIGlmIChvdmVybGF5KSB7CiAgICAgICAgICB2YXIgejEgPSBOdW1iZXIoCiAgICAgICAgICAgICAgb3ZlcmxheS5zdHlsZS56SW5kZXggfHwgd2luZG93LmdldENvbXB1dGVkU3R5bGUob3ZlcmxheSkuekluZGV4KTsKICAgICAgICAgIC8vIENoZWNrIGlmIGlzIGEgbnVtYmVyCiAgICAgICAgICAvLyBOdW1iZXIuaXNOYU4gbm90IHN1cHBvcnRlZCBpbiBJRSAxMCsKICAgICAgICAgIGlmICh6MSA9PT0gejEpIHsKICAgICAgICAgICAgeiA9IHoxOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gejsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7IUVsZW1lbnR9IGVsZW1lbnQKICAgICAgICogQHBhcmFtIHtudW1iZXJ8c3RyaW5nfSB6CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfc2V0WihlbGVtZW50LCB6KSB7CiAgICAgICAgZWxlbWVudC5zdHlsZS56SW5kZXggPSB6OwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHshRWxlbWVudH0gb3ZlcmxheQogICAgICAgKiBAcGFyYW0ge251bWJlcn0gYWJvdmVaCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfYXBwbHlPdmVybGF5WihvdmVybGF5LCBhYm92ZVopIHsKICAgICAgICB0aGlzLl9zZXRaKG92ZXJsYXksIGFib3ZlWiArIDIpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgZGVlcGVzdCBvdmVybGF5IGluIHRoZSBwYXRoLgogICAgICAgKiBAcGFyYW0geyFBcnJheTwhRWxlbWVudD49fSBwYXRoCiAgICAgICAqIEByZXR1cm4geyFFbGVtZW50fHVuZGVmaW5lZH0KICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9vdmVybGF5SW5QYXRoKHBhdGgpIHsKICAgICAgICBwYXRoID0gcGF0aCB8fCBbXTsKICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHBhdGgubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGlmIChwYXRoW2ldLl9tYW5hZ2VyID09PSB0aGlzKSB7CiAgICAgICAgICAgIHJldHVybiBwYXRoW2ldOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEVuc3VyZXMgdGhlIGNsaWNrIGV2ZW50IGlzIGRlbGVnYXRlZCB0byB0aGUgcmlnaHQgb3ZlcmxheS4KICAgICAgICogQHBhcmFtIHshRXZlbnR9IGV2ZW50CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfb25DYXB0dXJlQ2xpY2soZXZlbnQpIHsKICAgICAgICB2YXIgaSA9IHRoaXMuX292ZXJsYXlzLmxlbmd0aCAtIDE7CiAgICAgICAgaWYgKGkgPT09IC0xKQogICAgICAgICAgcmV0dXJuOwogICAgICAgIHZhciBwYXRoID0gLyoqIEB0eXBlIHshQXJyYXk8IUV2ZW50VGFyZ2V0Pn0gKi8gKGRvbShldmVudCkucGF0aCk7CiAgICAgICAgdmFyIG92ZXJsYXk7CiAgICAgICAgLy8gQ2hlY2sgaWYgY2xpY2tlZCBvdXRzaWRlIG9mIG92ZXJsYXkuCiAgICAgICAgd2hpbGUgKChvdmVybGF5ID0gLyoqIEB0eXBlIHs/fSAqLyAodGhpcy5fb3ZlcmxheXNbaV0pKSAmJgogICAgICAgICAgICAgICB0aGlzLl9vdmVybGF5SW5QYXRoKHBhdGgpICE9PSBvdmVybGF5KSB7CiAgICAgICAgICBvdmVybGF5Ll9vbkNhcHR1cmVDbGljayhldmVudCk7CiAgICAgICAgICBpZiAob3ZlcmxheS5hbGxvd0NsaWNrVGhyb3VnaCkgewogICAgICAgICAgICBpLS07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBFbnN1cmVzIHRoZSBmb2N1cyBldmVudCBpcyBkZWxlZ2F0ZWQgdG8gdGhlIHJpZ2h0IG92ZXJsYXkuCiAgICAgICAqIEBwYXJhbSB7IUV2ZW50fSBldmVudAogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX29uQ2FwdHVyZUZvY3VzKGV2ZW50KSB7CiAgICAgICAgdmFyIG92ZXJsYXkgPSAvKiogQHR5cGUgez99ICovICh0aGlzLmN1cnJlbnRPdmVybGF5KCkpOwogICAgICAgIGlmIChvdmVybGF5KSB7CiAgICAgICAgICBvdmVybGF5Ll9vbkNhcHR1cmVGb2N1cyhldmVudCk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogRW5zdXJlcyBUQUIgYW5kIEVTQyBrZXlib2FyZCBldmVudHMgYXJlIGRlbGVnYXRlZCB0byB0aGUgcmlnaHQgb3ZlcmxheS4KICAgICAgICogQHBhcmFtIHshRXZlbnR9IGV2ZW50CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfb25DYXB0dXJlS2V5RG93bihldmVudCkgewogICAgICAgIHZhciBvdmVybGF5ID0gLyoqIEB0eXBlIHs/fSAqLyAodGhpcy5jdXJyZW50T3ZlcmxheSgpKTsKICAgICAgICBpZiAob3ZlcmxheSkgewogICAgICAgICAgaWYgKElyb25BMTF5S2V5c0JlaGF2aW9yLmtleWJvYXJkRXZlbnRNYXRjaGVzS2V5cyhldmVudCwgJ2VzYycpKSB7CiAgICAgICAgICAgIG92ZXJsYXkuX29uQ2FwdHVyZUVzYyhldmVudCk7CiAgICAgICAgICB9IGVsc2UgaWYgKElyb25BMTF5S2V5c0JlaGF2aW9yLmtleWJvYXJkRXZlbnRNYXRjaGVzS2V5cyhldmVudCwgJ3RhYicpKSB7CiAgICAgICAgICAgIG92ZXJsYXkuX29uQ2FwdHVyZVRhYihldmVudCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogUmV0dXJucyBpZiB0aGUgb3ZlcmxheTEgc2hvdWxkIGJlIGJlaGluZCBvdmVybGF5Mi4KICAgICAgICogQHBhcmFtIHshRWxlbWVudH0gb3ZlcmxheTEKICAgICAgICogQHBhcmFtIHshRWxlbWVudH0gb3ZlcmxheTIKICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICogQHN1cHByZXNzIHttaXNzaW5nUHJvcGVydGllc30KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9zaG91bGRCZUJlaGluZE92ZXJsYXkob3ZlcmxheTEsIG92ZXJsYXkyKSB7CiAgICAgICAgcmV0dXJuICFvdmVybGF5MS5hbHdheXNPblRvcCAmJiBvdmVybGF5Mi5hbHdheXNPblRvcDsKICAgICAgfQogICAgfQogICAgY29uc3QgSXJvbk92ZXJsYXlNYW5hZ2VyID0gbmV3IElyb25PdmVybGF5TWFuYWdlckNsYXNzKCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICAvKioKICAgICAqIFVzZWQgdG8gY2FsY3VsYXRlIHRoZSBzY3JvbGwgZGlyZWN0aW9uIGR1cmluZyB0b3VjaCBldmVudHMuCiAgICAgKiBAdHlwZSB7IU9iamVjdH0KICAgICAqLwogICAgdmFyIGxhc3RUb3VjaFBvc2l0aW9uID0ge3BhZ2VYOiAwLCBwYWdlWTogMH07CiAgICAvKioKICAgICAqIFVzZWQgdG8gYXZvaWQgY29tcHV0aW5nIGV2ZW50LnBhdGggYW5kIGZpbHRlciBzY3JvbGxhYmxlIG5vZGVzIChiZXR0ZXIgcGVyZikuCiAgICAgKiBAdHlwZSB7P0V2ZW50VGFyZ2V0fQogICAgICovCiAgICB2YXIgbGFzdFJvb3RUYXJnZXQgPSBudWxsOwogICAgLyoqCiAgICAgKiBAdHlwZSB7IUFycmF5PCFOb2RlPn0KICAgICAqLwogICAgdmFyIGxhc3RTY3JvbGxhYmxlTm9kZXMgPSBbXTsKICAgIC8qKgogICAgICogQHR5cGUgeyFBcnJheTxzdHJpbmc+fQogICAgICovCiAgICB2YXIgc2Nyb2xsRXZlbnRzID0gWwogICAgICAvLyBNb2Rlcm4gYHdoZWVsYCBldmVudCBmb3IgbW91c2Ugd2hlZWwgc2Nyb2xsaW5nOgogICAgICAnd2hlZWwnLAogICAgICAvLyBPbGRlciwgbm9uLXN0YW5kYXJkIGBtb3VzZXdoZWVsYCBldmVudCBmb3Igc29tZSBGRjoKICAgICAgJ21vdXNld2hlZWwnLAogICAgICAvLyBJRToKICAgICAgJ0RPTU1vdXNlU2Nyb2xsJywKICAgICAgLy8gVG91Y2ggZW5hYmxlZCBkZXZpY2VzCiAgICAgICd0b3VjaHN0YXJ0JywKICAgICAgJ3RvdWNobW92ZScKICAgIF07CiAgICAvLyBtdXN0IGJlIGRlZmluZWQgZm9yIG1vZHVsaXplcgogICAgdmFyIF9ib3VuZFNjcm9sbEhhbmRsZXI7CgogICAgLyoqCiAgICAgKiBUaGUgY3VycmVudCBlbGVtZW50IHRoYXQgZGVmaW5lcyB0aGUgRE9NIGJvdW5kYXJpZXMgb2YgdGhlCiAgICAgKiBzY3JvbGwgbG9jay4gVGhpcyBpcyBhbHdheXMgdGhlIG1vc3QgcmVjZW50bHkgbG9ja2luZyBlbGVtZW50LgogICAgICoKICAgICAqIEB0eXBlIHshTm9kZXx1bmRlZmluZWR9CiAgICAgKi8KICAgIHZhciBjdXJyZW50TG9ja2luZ0VsZW1lbnQ7CgogICAgLyoqCiAgICAgKiBQdXNoIGFuIGVsZW1lbnQgb250byB0aGUgY3VycmVudCBzY3JvbGwgbG9jayBzdGFjay4gVGhlIG1vc3QgcmVjZW50bHkKICAgICAqIHB1c2hlZCBlbGVtZW50IGFuZCBpdHMgY2hpbGRyZW4gd2lsbCBiZSBjb25zaWRlcmVkIHNjcm9sbGFibGUuIEFsbAogICAgICogb3RoZXIgZWxlbWVudHMgd2lsbCBub3QgYmUgc2Nyb2xsYWJsZS4KICAgICAqCiAgICAgKiBTY3JvbGwgbG9ja2luZyBpcyBpbXBsZW1lbnRlZCBhcyBhIHN0YWNrIHNvIHRoYXQgY2FzZXMgc3VjaCBhcwogICAgICogZHJvcGRvd25zIHdpdGhpbiBkcm9wZG93bnMgYXJlIGhhbmRsZWQgd2VsbC4KICAgICAqCiAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWxlbWVudCBUaGUgZWxlbWVudCB0aGF0IHNob3VsZCBsb2NrIHNjcm9sbC4KICAgICAqLwogICAgZnVuY3Rpb24gcHVzaFNjcm9sbExvY2soZWxlbWVudCkgewogICAgICAvLyBQcmV2ZW50IHB1c2hpbmcgdGhlIHNhbWUgZWxlbWVudCB0d2ljZQogICAgICBpZiAoX2xvY2tpbmdFbGVtZW50cy5pbmRleE9mKGVsZW1lbnQpID49IDApIHsKICAgICAgICByZXR1cm47CiAgICAgIH0KCiAgICAgIGlmIChfbG9ja2luZ0VsZW1lbnRzLmxlbmd0aCA9PT0gMCkgewogICAgICAgIF9sb2NrU2Nyb2xsSW50ZXJhY3Rpb25zKCk7CiAgICAgIH0KCiAgICAgIF9sb2NraW5nRWxlbWVudHMucHVzaChlbGVtZW50KTsKICAgICAgY3VycmVudExvY2tpbmdFbGVtZW50ID0gX2xvY2tpbmdFbGVtZW50c1tfbG9ja2luZ0VsZW1lbnRzLmxlbmd0aCAtIDFdOwogICAgfQoKICAgIC8qKgogICAgICogUmVtb3ZlIGFuIGVsZW1lbnQgZnJvbSB0aGUgc2Nyb2xsIGxvY2sgc3RhY2suIFRoZSBlbGVtZW50IGJlaW5nCiAgICAgKiByZW1vdmVkIGRvZXMgbm90IG5lZWQgdG8gYmUgdGhlIG1vc3QgcmVjZW50bHkgcHVzaGVkIGVsZW1lbnQuIEhvd2V2ZXIsCiAgICAgKiB0aGUgc2Nyb2xsIGxvY2sgY29uc3RyYWludHMgb25seSBjaGFuZ2Ugd2hlbiB0aGUgbW9zdCByZWNlbnRseSBwdXNoZWQKICAgICAqIGVsZW1lbnQgaXMgcmVtb3ZlZC4KICAgICAqCiAgICAgKiBAcGFyYW0geyFIVE1MRWxlbWVudH0gZWxlbWVudCBUaGUgZWxlbWVudCB0byByZW1vdmUgZnJvbSB0aGUgc2Nyb2xsCiAgICAgKiBsb2NrIHN0YWNrLgogICAgICovCiAgICBmdW5jdGlvbiByZW1vdmVTY3JvbGxMb2NrKGVsZW1lbnQpIHsKICAgICAgdmFyIGluZGV4ID0gX2xvY2tpbmdFbGVtZW50cy5pbmRleE9mKGVsZW1lbnQpOwoKICAgICAgaWYgKGluZGV4ID09PSAtMSkgewogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgX2xvY2tpbmdFbGVtZW50cy5zcGxpY2UoaW5kZXgsIDEpOwogICAgICBjdXJyZW50TG9ja2luZ0VsZW1lbnQgPSBfbG9ja2luZ0VsZW1lbnRzW19sb2NraW5nRWxlbWVudHMubGVuZ3RoIC0gMV07CgogICAgICBpZiAoX2xvY2tpbmdFbGVtZW50cy5sZW5ndGggPT09IDApIHsKICAgICAgICBfdW5sb2NrU2Nyb2xsSW50ZXJhY3Rpb25zKCk7CiAgICAgIH0KICAgIH0KCiAgICBjb25zdCBfbG9ja2luZ0VsZW1lbnRzID0gW107CgogICAgZnVuY3Rpb24gX3Njcm9sbEludGVyYWN0aW9uSGFuZGxlcihldmVudCkgewogICAgICAvLyBBdm9pZCBjYW5jZWxpbmcgYW4gZXZlbnQgd2l0aCBjYW5jZWxhYmxlPWZhbHNlLCBlLmcuIHNjcm9sbGluZyBpcyBpbgogICAgICAvLyBwcm9ncmVzcyBhbmQgY2Fubm90IGJlIGludGVycnVwdGVkLgogICAgICBpZiAoZXZlbnQuY2FuY2VsYWJsZSAmJiBfc2hvdWxkUHJldmVudFNjcm9sbGluZyhldmVudCkpIHsKICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICB9CiAgICAgIC8vIElmIGV2ZW50IGhhcyB0YXJnZXRUb3VjaGVzICh0b3VjaCBldmVudCksIHVwZGF0ZSBsYXN0IHRvdWNoIHBvc2l0aW9uLgogICAgICBpZiAoZXZlbnQudGFyZ2V0VG91Y2hlcykgewogICAgICAgIHZhciB0b3VjaCA9IGV2ZW50LnRhcmdldFRvdWNoZXNbMF07CiAgICAgICAgbGFzdFRvdWNoUG9zaXRpb24ucGFnZVggPSB0b3VjaC5wYWdlWDsKICAgICAgICBsYXN0VG91Y2hQb3NpdGlvbi5wYWdlWSA9IHRvdWNoLnBhZ2VZOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gX2xvY2tTY3JvbGxJbnRlcmFjdGlvbnMoKSB7CiAgICAgIF9ib3VuZFNjcm9sbEhhbmRsZXIgPQogICAgICAgICAgX2JvdW5kU2Nyb2xsSGFuZGxlciB8fCBfc2Nyb2xsSW50ZXJhY3Rpb25IYW5kbGVyLmJpbmQodW5kZWZpbmVkKTsKICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBzY3JvbGxFdmVudHMubGVuZ3RoOyBpIDwgbDsgaSsrKSB7CiAgICAgICAgLy8gTk9URTogYnJvd3NlcnMgdGhhdCBkb24ndCBzdXBwb3J0IG9iamVjdHMgYXMgdGhpcmQgYXJnIHdpbGwKICAgICAgICAvLyBpbnRlcnByZXQgaXQgYXMgYm9vbGVhbiwgaGVuY2UgdXNlQ2FwdHVyZSA9IHRydWUgaW4gdGhpcyBjYXNlLgogICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoCiAgICAgICAgICAgIHNjcm9sbEV2ZW50c1tpXSwgX2JvdW5kU2Nyb2xsSGFuZGxlciwge2NhcHR1cmU6IHRydWUsIHBhc3NpdmU6IGZhbHNlfSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBfdW5sb2NrU2Nyb2xsSW50ZXJhY3Rpb25zKCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbCA9IHNjcm9sbEV2ZW50cy5sZW5ndGg7IGkgPCBsOyBpKyspIHsKICAgICAgICAvLyBOT1RFOiBicm93c2VycyB0aGF0IGRvbid0IHN1cHBvcnQgb2JqZWN0cyBhcyB0aGlyZCBhcmcgd2lsbAogICAgICAgIC8vIGludGVycHJldCBpdCBhcyBib29sZWFuLCBoZW5jZSB1c2VDYXB0dXJlID0gdHJ1ZSBpbiB0aGlzIGNhc2UuCiAgICAgICAgZG9jdW1lbnQucmVtb3ZlRXZlbnRMaXN0ZW5lcigKICAgICAgICAgICAgc2Nyb2xsRXZlbnRzW2ldLCBfYm91bmRTY3JvbGxIYW5kbGVyLCB7Y2FwdHVyZTogdHJ1ZSwgcGFzc2l2ZTogZmFsc2V9KTsKICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBldmVudCBjYXVzZXMgc2Nyb2xsIG91dHNpZGUgdGhlIGN1cnJlbnQgbG9ja2luZwogICAgICogZWxlbWVudCwgZS5nLiBwb2ludGVyL2tleWJvYXJkIGludGVyYWN0aW9ucywgb3Igc2Nyb2xsICJsZWFraW5nIgogICAgICogb3V0c2lkZSB0aGUgbG9ja2luZyBlbGVtZW50IHdoZW4gaXQgaXMgYWxyZWFkeSBhdCBpdHMgc2Nyb2xsIGJvdW5kYXJpZXMuCiAgICAgKiBAcGFyYW0geyFFdmVudH0gZXZlbnQKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgKiBAcGFja2FnZQogICAgICovCiAgICBmdW5jdGlvbiBfc2hvdWxkUHJldmVudFNjcm9sbGluZyhldmVudCkgewogICAgICAvLyBVcGRhdGUgaWYgcm9vdCB0YXJnZXQgY2hhbmdlZC4gRm9yIHRvdWNoIGV2ZW50cywgZW5zdXJlIHdlIGRvbid0CiAgICAgIC8vIHVwZGF0ZSBkdXJpbmcgdG91Y2htb3ZlLgogICAgICB2YXIgdGFyZ2V0ID0gZG9tKGV2ZW50KS5yb290VGFyZ2V0OwogICAgICBpZiAoZXZlbnQudHlwZSAhPT0gJ3RvdWNobW92ZScgJiYgbGFzdFJvb3RUYXJnZXQgIT09IHRhcmdldCkgewogICAgICAgIGxhc3RSb290VGFyZ2V0ID0gdGFyZ2V0OwogICAgICAgIGxhc3RTY3JvbGxhYmxlTm9kZXMgPSBfZ2V0U2Nyb2xsYWJsZU5vZGVzKGRvbShldmVudCkucGF0aCk7CiAgICAgIH0KCiAgICAgIC8vIFByZXZlbnQgZXZlbnQgaWYgbm8gc2Nyb2xsYWJsZSBub2Rlcy4KICAgICAgaWYgKCFsYXN0U2Nyb2xsYWJsZU5vZGVzLmxlbmd0aCkgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIC8vIERvbid0IHByZXZlbnQgdG91Y2hzdGFydCBldmVudCBpbnNpZGUgdGhlIGxvY2tpbmcgZWxlbWVudCB3aGVuIGl0IGhhcwogICAgICAvLyBzY3JvbGxhYmxlIG5vZGVzLgogICAgICBpZiAoZXZlbnQudHlwZSA9PT0gJ3RvdWNoc3RhcnQnKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIC8vIEdldCBkZWx0YVgvWS4KICAgICAgdmFyIGluZm8gPSBfZ2V0U2Nyb2xsSW5mbyhldmVudCk7CiAgICAgIC8vIFByZXZlbnQgaWYgdGhlcmUgaXMgbm8gY2hpbGQgdGhhdCBjYW4gc2Nyb2xsLgogICAgICByZXR1cm4gIV9nZXRTY3JvbGxpbmdOb2RlKGxhc3RTY3JvbGxhYmxlTm9kZXMsIGluZm8uZGVsdGFYLCBpbmZvLmRlbHRhWSk7CiAgICB9CgogICAgLyoqCiAgICAgKiBSZXR1cm5zIGFuIGFycmF5IG9mIHNjcm9sbGFibGUgbm9kZXMgdXAgdG8gdGhlIGN1cnJlbnQgbG9ja2luZyBlbGVtZW50LAogICAgICogd2hpY2ggaXMgaW5jbHVkZWQgdG9vIGlmIHNjcm9sbGFibGUuCiAgICAgKiBAcGFyYW0geyFBcnJheTwhTm9kZT59IG5vZGVzCiAgICAgKiBAcmV0dXJuIHshQXJyYXk8IU5vZGU+fSBzY3JvbGxhYmxlcwogICAgICogQHBhY2thZ2UKICAgICAqLwogICAgZnVuY3Rpb24gX2dldFNjcm9sbGFibGVOb2Rlcyhub2RlcykgewogICAgICB2YXIgc2Nyb2xsYWJsZXMgPSBbXTsKICAgICAgdmFyIGxvY2tpbmdJbmRleCA9CiAgICAgICAgICBub2Rlcy5pbmRleE9mKC8qKiBAdHlwZSB7IU5vZGV9ICovIChjdXJyZW50TG9ja2luZ0VsZW1lbnQpKTsKICAgICAgLy8gTG9vcCBmcm9tIHJvb3QgdGFyZ2V0IHRvIGxvY2tpbmcgZWxlbWVudCAoaW5jbHVkZWQpLgogICAgICBmb3IgKHZhciBpID0gMDsgaSA8PSBsb2NraW5nSW5kZXg7IGkrKykgewogICAgICAgIC8vIFNraXAgbm9uLUVsZW1lbnQgbm9kZXMuCiAgICAgICAgaWYgKG5vZGVzW2ldLm5vZGVUeXBlICE9PSBOb2RlLkVMRU1FTlRfTk9ERSkgewogICAgICAgICAgY29udGludWU7CiAgICAgICAgfQogICAgICAgIHZhciBub2RlID0gLyoqIEB0eXBlIHshRWxlbWVudH0gKi8gKG5vZGVzW2ldKTsKICAgICAgICAvLyBDaGVjayBpbmxpbmUgc3R5bGUgYmVmb3JlIGNoZWNraW5nIGNvbXB1dGVkIHN0eWxlLgogICAgICAgIHZhciBzdHlsZSA9IG5vZGUuc3R5bGU7CiAgICAgICAgaWYgKHN0eWxlLm92ZXJmbG93ICE9PSAnc2Nyb2xsJyAmJiBzdHlsZS5vdmVyZmxvdyAhPT0gJ2F1dG8nKSB7CiAgICAgICAgICBzdHlsZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKG5vZGUpOwogICAgICAgIH0KICAgICAgICBpZiAoc3R5bGUub3ZlcmZsb3cgPT09ICdzY3JvbGwnIHx8IHN0eWxlLm92ZXJmbG93ID09PSAnYXV0bycpIHsKICAgICAgICAgIHNjcm9sbGFibGVzLnB1c2gobm9kZSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiBzY3JvbGxhYmxlczsKICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIG5vZGUgdGhhdCBpcyBzY3JvbGxpbmcuIElmIHRoZXJlIGlzIG5vIHNjcm9sbGluZywKICAgICAqIHJldHVybnMgdW5kZWZpbmVkLgogICAgICogQHBhcmFtIHshQXJyYXk8IU5vZGU+fSBub2RlcwogICAgICogQHBhcmFtIHtudW1iZXJ9IGRlbHRhWCBTY3JvbGwgZGVsdGEgb24gdGhlIHgtYXhpcwogICAgICogQHBhcmFtIHtudW1iZXJ9IGRlbHRhWSBTY3JvbGwgZGVsdGEgb24gdGhlIHktYXhpcwogICAgICogQHJldHVybiB7IU5vZGV8dW5kZWZpbmVkfQogICAgICogQHBhY2thZ2UKICAgICAqLwogICAgZnVuY3Rpb24gX2dldFNjcm9sbGluZ05vZGUobm9kZXMsIGRlbHRhWCwgZGVsdGFZKSB7CiAgICAgIC8vIE5vIHNjcm9sbC4KICAgICAgaWYgKCFkZWx0YVggJiYgIWRlbHRhWSkgewogICAgICAgIHJldHVybjsKICAgICAgfQogICAgICAvLyBDaGVjayBvbmx5IG9uZSBheGlzIGFjY29yZGluZyB0byB3aGVyZSB0aGVyZSBpcyBtb3JlIHNjcm9sbC4KICAgICAgLy8gUHJlZmVyIHZlcnRpY2FsIHRvIGhvcml6b250YWwuCiAgICAgIHZhciB2ZXJ0aWNhbFNjcm9sbCA9IE1hdGguYWJzKGRlbHRhWSkgPj0gTWF0aC5hYnMoZGVsdGFYKTsKICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBub2Rlcy5sZW5ndGg7IGkrKykgewogICAgICAgIHZhciBub2RlID0gbm9kZXNbaV07CiAgICAgICAgdmFyIGNhblNjcm9sbCA9IGZhbHNlOwogICAgICAgIGlmICh2ZXJ0aWNhbFNjcm9sbCkgewogICAgICAgICAgLy8gZGVsdGEgPCAwIGlzIHNjcm9sbCB1cCwgZGVsdGEgPiAwIGlzIHNjcm9sbCBkb3duLgogICAgICAgICAgY2FuU2Nyb2xsID0gZGVsdGFZIDwgMCA/CiAgICAgICAgICAgICAgbm9kZS5zY3JvbGxUb3AgPiAwIDoKICAgICAgICAgICAgICBub2RlLnNjcm9sbFRvcCA8IG5vZGUuc2Nyb2xsSGVpZ2h0IC0gbm9kZS5jbGllbnRIZWlnaHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIC8vIGRlbHRhIDwgMCBpcyBzY3JvbGwgbGVmdCwgZGVsdGEgPiAwIGlzIHNjcm9sbCByaWdodC4KICAgICAgICAgIGNhblNjcm9sbCA9IGRlbHRhWCA8IDAgPwogICAgICAgICAgICAgIG5vZGUuc2Nyb2xsTGVmdCA+IDAgOgogICAgICAgICAgICAgIG5vZGUuc2Nyb2xsTGVmdCA8IG5vZGUuc2Nyb2xsV2lkdGggLSBub2RlLmNsaWVudFdpZHRoOwogICAgICAgIH0KICAgICAgICBpZiAoY2FuU2Nyb2xsKSB7CiAgICAgICAgICByZXR1cm4gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgc2Nyb2xsIGBkZWx0YVhgIGFuZCBgZGVsdGFZYC4KICAgICAqIEBwYXJhbSB7IUV2ZW50fSBldmVudCBUaGUgc2Nyb2xsIGV2ZW50CiAgICAgKiBAcmV0dXJuIHt7ZGVsdGFYOiBudW1iZXIsIGRlbHRhWTogbnVtYmVyfX0gT2JqZWN0IGNvbnRhaW5pbmcgdGhlCiAgICAgKiB4LWF4aXMgc2Nyb2xsIGRlbHRhIChwb3NpdGl2ZTogc2Nyb2xsIHJpZ2h0LCBuZWdhdGl2ZTogc2Nyb2xsIGxlZnQsCiAgICAgKiAwOiBubyBzY3JvbGwpLCBhbmQgdGhlIHktYXhpcyBzY3JvbGwgZGVsdGEgKHBvc2l0aXZlOiBzY3JvbGwgZG93biwKICAgICAqIG5lZ2F0aXZlOiBzY3JvbGwgdXAsIDA6IG5vIHNjcm9sbCkuCiAgICAgKiBAcGFja2FnZQogICAgICovCiAgICBmdW5jdGlvbiBfZ2V0U2Nyb2xsSW5mbyhldmVudCkgewogICAgICB2YXIgaW5mbyA9IHtkZWx0YVg6IGV2ZW50LmRlbHRhWCwgZGVsdGFZOiBldmVudC5kZWx0YVl9OwogICAgICAvLyBBbHJlYWR5IGF2YWlsYWJsZS4KICAgICAgaWYgKCdkZWx0YVgnIGluIGV2ZW50KSA7CiAgICAgIC8vIFNhZmFyaSBoYXMgc2Nyb2xsIGluZm8gaW4gYHdoZWVsRGVsdGFYL1lgLgogICAgICBlbHNlIGlmICgnd2hlZWxEZWx0YVgnIGluIGV2ZW50ICYmICd3aGVlbERlbHRhWScgaW4gZXZlbnQpIHsKICAgICAgICBpbmZvLmRlbHRhWCA9IC1ldmVudC53aGVlbERlbHRhWDsKICAgICAgICBpbmZvLmRlbHRhWSA9IC1ldmVudC53aGVlbERlbHRhWTsKICAgICAgfQogICAgICAvLyBJRTEwIGhhcyBvbmx5IHZlcnRpY2FsIHNjcm9sbCBpbmZvIGluIGB3aGVlbERlbHRhYC4KICAgICAgZWxzZSBpZiAoJ3doZWVsRGVsdGEnIGluIGV2ZW50KSB7CiAgICAgICAgaW5mby5kZWx0YVggPSAwOwogICAgICAgIGluZm8uZGVsdGFZID0gLWV2ZW50LndoZWVsRGVsdGE7CiAgICAgIH0KICAgICAgLy8gRmlyZWZveCBoYXMgc2Nyb2xsIGluZm8gaW4gYGRldGFpbGAgYW5kIGBheGlzYC4KICAgICAgZWxzZSBpZiAoJ2F4aXMnIGluIGV2ZW50KSB7CiAgICAgICAgaW5mby5kZWx0YVggPSBldmVudC5heGlzID09PSAxID8gZXZlbnQuZGV0YWlsIDogMDsKICAgICAgICBpbmZvLmRlbHRhWSA9IGV2ZW50LmF4aXMgPT09IDIgPyBldmVudC5kZXRhaWwgOiAwOwogICAgICB9CiAgICAgIC8vIE9uIG1vYmlsZSBkZXZpY2VzLCBjYWxjdWxhdGUgc2Nyb2xsIGRpcmVjdGlvbi4KICAgICAgZWxzZSBpZiAoZXZlbnQudGFyZ2V0VG91Y2hlcykgewogICAgICAgIHZhciB0b3VjaCA9IGV2ZW50LnRhcmdldFRvdWNoZXNbMF07CiAgICAgICAgLy8gVG91Y2ggbW92ZXMgZnJvbSByaWdodCB0byBsZWZ0ID0+IHNjcm9sbGluZyBnb2VzIHJpZ2h0LgogICAgICAgIGluZm8uZGVsdGFYID0gbGFzdFRvdWNoUG9zaXRpb24ucGFnZVggLSB0b3VjaC5wYWdlWDsKICAgICAgICAvLyBUb3VjaCBtb3ZlcyBmcm9tIGRvd24gdG8gdXAgPT4gc2Nyb2xsaW5nIGdvZXMgZG93bi4KICAgICAgICBpbmZvLmRlbHRhWSA9IGxhc3RUb3VjaFBvc2l0aW9uLnBhZ2VZIC0gdG91Y2gucGFnZVk7CiAgICAgIH0KICAgICAgcmV0dXJuIGluZm87CiAgICB9CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IElyb25PdmVybGF5QmVoYXZpb3JJbXBsID0gewoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBvdmVybGF5IGlzIGN1cnJlbnRseSBkaXNwbGF5ZWQuCiAgICAgICAgICovCiAgICAgICAgb3BlbmVkOgogICAgICAgICAgICB7b2JzZXJ2ZXI6ICdfb3BlbmVkQ2hhbmdlZCcsIHR5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZSwgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVHJ1ZSBpZiB0aGUgb3ZlcmxheSB3YXMgY2FuY2VsZWQgd2hlbiBpdCB3YXMgbGFzdCBjbG9zZWQuCiAgICAgICAgICovCiAgICAgICAgY2FuY2VsZWQ6IHsKICAgICAgICAgIG9ic2VydmVyOiAnX2NhbmNlbGVkQ2hhbmdlZCcsCiAgICAgICAgICByZWFkT25seTogdHJ1ZSwKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNwbGF5IGEgYmFja2Ryb3AgYmVoaW5kIHRoZSBvdmVybGF5LiBJdCB0cmFwcyB0aGUgZm9jdXMKICAgICAgICAgKiB3aXRoaW4gdGhlIGxpZ2h0IERPTSBvZiB0aGUgb3ZlcmxheS4KICAgICAgICAgKi8KICAgICAgICB3aXRoQmFja2Ryb3A6IHsKICAgICAgICAgIG9ic2VydmVyOiAnX3dpdGhCYWNrZHJvcENoYW5nZWQnLAogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNhYmxlIGF1dG8tZm9jdXNpbmcgdGhlIG92ZXJsYXkgb3IgY2hpbGQgbm9kZXMgd2l0aAogICAgICAgICAqIHRoZSBgYXV0b2ZvY3VzYCBhdHRyaWJ1dGVgIHdoZW4gdGhlIG92ZXJsYXkgaXMgb3BlbmVkLgogICAgICAgICAqLwogICAgICAgIG5vQXV0b0ZvY3VzOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGRpc2FibGUgY2FuY2VsaW5nIHRoZSBvdmVybGF5IHdpdGggdGhlIEVTQyBrZXkuCiAgICAgICAgICovCiAgICAgICAgbm9DYW5jZWxPbkVzY0tleTogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNhYmxlIGNhbmNlbGluZyB0aGUgb3ZlcmxheSBieSBjbGlja2luZyBvdXRzaWRlIGl0LgogICAgICAgICAqLwogICAgICAgIG5vQ2FuY2VsT25PdXRzaWRlQ2xpY2s6IHsKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udGFpbnMgdGhlIHJlYXNvbihzKSB0aGlzIG92ZXJsYXkgd2FzIGxhc3QgY2xvc2VkIChzZWUKICAgICAgICAgKiBgaXJvbi1vdmVybGF5LWNsb3NlZGApLiBgSXJvbk92ZXJsYXlCZWhhdmlvcmAgcHJvdmlkZXMgdGhlIGBjYW5jZWxlZGAKICAgICAgICAgKiByZWFzb247IGltcGxlbWVudGVycyBvZiB0aGUgYmVoYXZpb3IgY2FuIHByb3ZpZGUgb3RoZXIgcmVhc29ucyBpbgogICAgICAgICAqIGFkZGl0aW9uIHRvIGBjYW5jZWxlZGAuCiAgICAgICAgICovCiAgICAgICAgY2xvc2luZ1JlYXNvbjogewogICAgICAgICAgLy8gd2FzIGEgZ2V0dGVyIGJlZm9yZSwgYnV0IG5lZWRzIHRvIGJlIGEgcHJvcGVydHkgc28gb3RoZXIKICAgICAgICAgIC8vIGJlaGF2aW9ycyBjYW4gb3ZlcnJpZGUgdGhpcy4KICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBlbmFibGUgcmVzdG9yaW5nIG9mIGZvY3VzIHdoZW4gb3ZlcmxheSBpcyBjbG9zZWQuCiAgICAgICAgICovCiAgICAgICAgcmVzdG9yZUZvY3VzT25DbG9zZTogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBhbGxvdyBjbGlja3MgdG8gZ28gdGhyb3VnaCBvdmVybGF5cy4KICAgICAgICAgKiBXaGVuIHRoZSB1c2VyIGNsaWNrcyBvdXRzaWRlIHRoaXMgb3ZlcmxheSwgdGhlIGNsaWNrIG1heQogICAgICAgICAqIGNsb3NlIHRoZSBvdmVybGF5IGJlbG93LgogICAgICAgICAqLwogICAgICAgIGFsbG93Q2xpY2tUaHJvdWdoOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGtlZXAgb3ZlcmxheSBhbHdheXMgb24gdG9wLgogICAgICAgICAqLwogICAgICAgIGFsd2F5c09uVG9wOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIERldGVybWluZXMgd2hpY2ggYWN0aW9uIHRvIHBlcmZvcm0gd2hlbiBzY3JvbGwgb3V0c2lkZSBhbiBvcGVuZWQgb3ZlcmxheQogICAgICAgICAqIGhhcHBlbnMuIFBvc3NpYmxlIHZhbHVlczogbG9jayAtIGJsb2NrcyBzY3JvbGxpbmcgZnJvbSBoYXBwZW5pbmcsIHJlZml0IC0KICAgICAgICAgKiBjb21wdXRlcyB0aGUgbmV3IHBvc2l0aW9uIG9uIHRoZSBvdmVybGF5IGNhbmNlbCAtIGNhdXNlcyB0aGUgb3ZlcmxheSB0bwogICAgICAgICAqIGNsb3NlCiAgICAgICAgICovCiAgICAgICAgc2Nyb2xsQWN0aW9uOiB7CiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2hvcnRjdXQgdG8gYWNjZXNzIHRvIHRoZSBvdmVybGF5IG1hbmFnZXIuCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKiBAdHlwZSB7IUlyb25PdmVybGF5TWFuYWdlckNsYXNzfQogICAgICAgICAqLwogICAgICAgIF9tYW5hZ2VyOiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogSXJvbk92ZXJsYXlNYW5hZ2VyLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBub2RlIGJlaW5nIGZvY3VzZWQuCiAgICAgICAgICogQHR5cGUgez9Ob2RlfQogICAgICAgICAqLwogICAgICAgIF9mb2N1c2VkQ2hpbGQ6IHsKICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9CgogICAgICB9LAoKICAgICAgbGlzdGVuZXJzOiB7J2lyb24tcmVzaXplJzogJ19vbklyb25SZXNpemUnfSwKCiAgICAgIG9ic2VydmVyczogWydfX3VwZGF0ZVNjcm9sbE9ic2VydmVycyhpc0F0dGFjaGVkLCBvcGVuZWQsIHNjcm9sbEFjdGlvbiknXSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgYmFja2Ryb3AgZWxlbWVudC4KICAgICAgICogQHJldHVybiB7IUVsZW1lbnR9CiAgICAgICAqLwogICAgICBnZXQgYmFja2Ryb3BFbGVtZW50KCkgewogICAgICAgIHJldHVybiB0aGlzLl9tYW5hZ2VyLmJhY2tkcm9wRWxlbWVudDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRoZSBub2RlIHRvIGdpdmUgZm9jdXMgdG8uCiAgICAgICAqIEByZXR1cm4geyFOb2RlfQogICAgICAgKi8KICAgICAgZ2V0IF9mb2N1c05vZGUoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2ZvY3VzZWRDaGlsZCB8fCBkb20odGhpcykucXVlcnlTZWxlY3RvcignW2F1dG9mb2N1c10nKSB8fCB0aGlzOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEFycmF5IG9mIG5vZGVzIHRoYXQgY2FuIHJlY2VpdmUgZm9jdXMgKG92ZXJsYXkgaW5jbHVkZWQpLCBvcmRlcmVkIGJ5CiAgICAgICAqIGB0YWJpbmRleGAuIFRoaXMgaXMgdXNlZCB0byByZXRyaWV2ZSB3aGljaCBpcyB0aGUgZmlyc3QgYW5kIGxhc3QgZm9jdXNhYmxlCiAgICAgICAqIG5vZGVzIGluIG9yZGVyIHRvIHdyYXAgdGhlIGZvY3VzIGZvciBvdmVybGF5cyBgd2l0aC1iYWNrZHJvcGAuCiAgICAgICAqCiAgICAgICAqIElmIHlvdSBrbm93IHdoYXQgaXMgeW91ciBjb250ZW50IChzcGVjaWZpY2FsbHkgdGhlIGZpcnN0IGFuZCBsYXN0IGZvY3VzYWJsZQogICAgICAgKiBjaGlsZHJlbiksIHlvdSBjYW4gb3ZlcnJpZGUgdGhpcyBtZXRob2QgdG8gcmV0dXJuIG9ubHkgYFtmaXJzdEZvY3VzYWJsZSwKICAgICAgICogbGFzdEZvY3VzYWJsZV07YAogICAgICAgKiBAcmV0dXJuIHshQXJyYXk8IU5vZGU+fQogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBnZXQgX2ZvY3VzYWJsZU5vZGVzKCkgewogICAgICAgIHJldHVybiBJcm9uRm9jdXNhYmxlc0hlbHBlci5nZXRUYWJiYWJsZU5vZGVzKHRoaXMpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICByZWFkeTogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gVXNlZCB0byBza2lwIGNhbGxzIHRvIG5vdGlmeVJlc2l6ZSBhbmQgcmVmaXQgd2hpbGUgdGhlIG92ZXJsYXkgaXMKICAgICAgICAvLyBhbmltYXRpbmcuCiAgICAgICAgdGhpcy5fX2lzQW5pbWF0aW5nID0gZmFsc2U7CiAgICAgICAgLy8gd2l0aC1iYWNrZHJvcCBuZWVkcyB0YWJpbmRleCB0byBiZSBzZXQgaW4gb3JkZXIgdG8gdHJhcCB0aGUgZm9jdXMuCiAgICAgICAgLy8gSWYgaXQgaXMgbm90IHNldCwgSXJvbk92ZXJsYXlCZWhhdmlvciB3aWxsIHNldCBpdCwgYW5kIHJlbW92ZSBpdCBpZgogICAgICAgIC8vIHdpdGgtYmFja2Ryb3AgPSBmYWxzZS4KICAgICAgICB0aGlzLl9fc2hvdWxkUmVtb3ZlVGFiSW5kZXggPSBmYWxzZTsKICAgICAgICAvLyBVc2VkIGZvciB3cmFwcGluZyB0aGUgZm9jdXMgb24gVEFCIC8gU2hpZnQrVEFCLgogICAgICAgIHRoaXMuX19maXJzdEZvY3VzYWJsZU5vZGUgPSB0aGlzLl9fbGFzdEZvY3VzYWJsZU5vZGUgPSBudWxsOwogICAgICAgIC8vIFVzZWQgYnkgdG8ga2VlcCB0cmFjayBvZiB0aGUgUkFGIGNhbGxiYWNrcy4KICAgICAgICB0aGlzLl9fcmFmcyA9IHt9OwogICAgICAgIC8vIEZvY3VzZWQgbm9kZSBiZWZvcmUgb3ZlcmxheSBnZXRzIG9wZW5lZC4gQ2FuIGJlIHJlc3RvcmVkIG9uIGNsb3NlLgogICAgICAgIHRoaXMuX19yZXN0b3JlRm9jdXNOb2RlID0gbnVsbDsKICAgICAgICAvLyBTY3JvbGwgaW5mbyB0byBiZSByZXN0b3JlZC4KICAgICAgICB0aGlzLl9fc2Nyb2xsVG9wID0gdGhpcy5fX3Njcm9sbExlZnQgPSBudWxsOwogICAgICAgIHRoaXMuX19vbkNhcHR1cmVTY3JvbGwgPSB0aGlzLl9fb25DYXB0dXJlU2Nyb2xsLmJpbmQodGhpcyk7CiAgICAgICAgLy8gUm9vdCBub2RlcyBob3N0aW5nIHRoZSBvdmVybGF5LCB1c2VkIHRvIGxpc3RlbiBmb3Igc2Nyb2xsIGV2ZW50cyBvbiB0aGVtLgogICAgICAgIHRoaXMuX19yb290Tm9kZXMgPSBudWxsOwogICAgICAgIHRoaXMuX2Vuc3VyZVNldHVwKCk7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBDYWxsIF9vcGVuZWRDaGFuZ2VkIGhlcmUgc28gdGhhdCBwb3NpdGlvbiBjYW4gYmUgY29tcHV0ZWQgY29ycmVjdGx5LgogICAgICAgIGlmICh0aGlzLm9wZW5lZCkgewogICAgICAgICAgdGhpcy5fb3BlbmVkQ2hhbmdlZCh0aGlzLm9wZW5lZCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX29ic2VydmVyID0gZG9tKHRoaXMpLm9ic2VydmVOb2Rlcyh0aGlzLl9vbk5vZGVzQ2hhbmdlKTsKICAgICAgfSwKCiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgZGV0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFRPRE8oYmlja25lbGxyKTogUGVyIHNwZWMsIGNoZWNraW5nIGB0aGlzLl9vYnNlcnZlcmAgc2hvdWxkIG5ldmVyIGJlCiAgICAgICAgLy8gbmVjZXNzYXJ5IGJlY2F1c2UgYGNvbm5lY3RlZENhbGxiYWNrYCBhbmQgYGRpc2Nvbm5lY3RlZENhbGxiYWNrYCBzaG91bGQKICAgICAgICAvLyBhbHdheXMgYmUgY2FsbGVkIGluIGFsdGVybmF0aW5nIG9yZGVyLiBIb3dldmVyLCB0aGUgY3VzdG9tIGVsZW1lbnRzCiAgICAgICAgLy8gcG9seWZpbGwgZG9lc24ndCBpbXBsZW1lbnQgdGhlIHJlYWN0aW9ucyBzdGFjaywgc28gdGhpcyBjYW4gc29tZXRpbWVzCiAgICAgICAgLy8gaGFwcGVuLCBwYXJ0aWN1bGFybHkgaWYgU2hhZHlET00gaXMgaW4gbm9QYXRjaCBtb2RlIHdoZXJlIHRoZSBjdXN0b20KICAgICAgICAvLyBlbGVtZW50cyBwb2x5ZmlsbCBpcyBpbnN0YWxsZWQgYmVmb3JlIFNoYWR5RE9NLiBXZSBzaG91bGQgaW52ZXN0aWdhdGUKICAgICAgICAvLyB3aGV0aGVyIG9yIG5vdCB3ZSBjYW4gZWl0aGVyIGltcGxlbWVudCB0aGUgcmVhY3Rpb25zIHN0YWNrIHdpdGhvdXQgbWFqb3IKICAgICAgICAvLyBwZXJmb3JtYW5jZSBpbXBsaWNhdGlvbnMgb3IgcGF0Y2ggU2hhZHlET00ncyBmdW5jdGlvbnMgdG8gcmVzdG9yZSB0aGUKICAgICAgICAvLyB0eXBpY2FsIFNoYWR5RE9NLXRoZW4tY3VzdG9tLWVsZW1lbnRzIG9yZGVyIGFuZCByZW1vdmUgdGhpcyB3b3JrYXJvdW5kLgogICAgICAgIGlmICh0aGlzLl9vYnNlcnZlcikgewogICAgICAgICAgZG9tKHRoaXMpLnVub2JzZXJ2ZU5vZGVzKHRoaXMuX29ic2VydmVyKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fb2JzZXJ2ZXIgPSBudWxsOwogICAgICAgIGZvciAodmFyIGNiIGluIHRoaXMuX19yYWZzKSB7CiAgICAgICAgICBpZiAodGhpcy5fX3JhZnNbY2JdICE9PSBudWxsKSB7CiAgICAgICAgICAgIGNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX19yYWZzW2NiXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuX19yYWZzID0ge307CiAgICAgICAgdGhpcy5fbWFuYWdlci5yZW1vdmVPdmVybGF5KHRoaXMpOwoKICAgICAgICAvLyBXZSBnb3QgZGV0YWNoZWQgd2hpbGUgYW5pbWF0aW5nLCBlbnN1cmUgd2Ugc2hvdy9oaWRlIHRoZSBvdmVybGF5CiAgICAgICAgLy8gYW5kIGZpcmUgaXJvbi1vdmVybGF5LW9wZW5lZC9jbG9zZWQgZXZlbnQhCiAgICAgICAgaWYgKHRoaXMuX19pc0FuaW1hdGluZykgewogICAgICAgICAgaWYgKHRoaXMub3BlbmVkKSB7CiAgICAgICAgICAgIHRoaXMuX2ZpbmlzaFJlbmRlck9wZW5lZCgpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gUmVzdG9yZSB0aGUgZm9jdXMgaWYgbmVjZXNzYXJ5LgogICAgICAgICAgICB0aGlzLl9hcHBseUZvY3VzKCk7CiAgICAgICAgICAgIHRoaXMuX2ZpbmlzaFJlbmRlckNsb3NlZCgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUb2dnbGUgdGhlIG9wZW5lZCBzdGF0ZSBvZiB0aGUgb3ZlcmxheS4KICAgICAgICovCiAgICAgIHRvZ2dsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fc2V0Q2FuY2VsZWQoZmFsc2UpOwogICAgICAgIHRoaXMub3BlbmVkID0gIXRoaXMub3BlbmVkOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIE9wZW4gdGhlIG92ZXJsYXkuCiAgICAgICAqLwogICAgICBvcGVuOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9zZXRDYW5jZWxlZChmYWxzZSk7CiAgICAgICAgdGhpcy5vcGVuZWQgPSB0cnVlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENsb3NlIHRoZSBvdmVybGF5LgogICAgICAgKi8KICAgICAgY2xvc2U6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3NldENhbmNlbGVkKGZhbHNlKTsKICAgICAgICB0aGlzLm9wZW5lZCA9IGZhbHNlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbmNlbHMgdGhlIG92ZXJsYXkuCiAgICAgICAqIEBwYXJhbSB7RXZlbnQ9fSBldmVudCBUaGUgb3JpZ2luYWwgZXZlbnQKICAgICAgICovCiAgICAgIGNhbmNlbDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgY2FuY2VsRXZlbnQgPQogICAgICAgICAgICB0aGlzLmZpcmUoJ2lyb24tb3ZlcmxheS1jYW5jZWxlZCcsIGV2ZW50LCB7Y2FuY2VsYWJsZTogdHJ1ZX0pOwogICAgICAgIGlmIChjYW5jZWxFdmVudC5kZWZhdWx0UHJldmVudGVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9zZXRDYW5jZWxlZCh0cnVlKTsKICAgICAgICB0aGlzLm9wZW5lZCA9IGZhbHNlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEludmFsaWRhdGVzIHRoZSBjYWNoZWQgdGFiYmFibGUgbm9kZXMuIFRvIGJlIGNhbGxlZCB3aGVuIGFueSBvZiB0aGUKICAgICAgICogZm9jdXNhYmxlIGNvbnRlbnQgY2hhbmdlcyAoZS5nLiBhIGJ1dHRvbiBpcyBkaXNhYmxlZCkuCiAgICAgICAqLwogICAgICBpbnZhbGlkYXRlVGFiYmFibGVzOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9fZmlyc3RGb2N1c2FibGVOb2RlID0gdGhpcy5fX2xhc3RGb2N1c2FibGVOb2RlID0gbnVsbDsKICAgICAgfSwKCiAgICAgIF9lbnN1cmVTZXR1cDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX292ZXJsYXlTZXR1cCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB0aGlzLl9vdmVybGF5U2V0dXAgPSB0cnVlOwogICAgICAgIHRoaXMuc3R5bGUub3V0bGluZSA9ICdub25lJzsKICAgICAgICB0aGlzLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FsbGVkIHdoZW4gYG9wZW5lZGAgY2hhbmdlcy4KICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gb3BlbmVkCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9vcGVuZWRDaGFuZ2VkOiBmdW5jdGlvbihvcGVuZWQpIHsKICAgICAgICBpZiAob3BlbmVkKSB7CiAgICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnYXJpYS1oaWRkZW4nKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtaGlkZGVuJywgJ3RydWUnKTsKICAgICAgICB9CgogICAgICAgIC8vIERlZmVyIGFueSBhbmltYXRpb24tcmVsYXRlZCBjb2RlIG9uIGF0dGFjaGVkCiAgICAgICAgLy8gKF9vcGVuZWRDaGFuZ2VkIGdldHMgY2FsbGVkIGFnYWluIG9uIGF0dGFjaGVkKS4KICAgICAgICBpZiAoIXRoaXMuaXNBdHRhY2hlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fX2lzQW5pbWF0aW5nID0gdHJ1ZTsKCiAgICAgICAgLy8gRGVyYWYgZm9yIG5vbi1ibG9ja2luZyByZW5kZXJpbmcuCiAgICAgICAgdGhpcy5fX2RlcmFmKCdfX29wZW5lZENoYW5nZWQnLCB0aGlzLl9fb3BlbmVkQ2hhbmdlZCk7CiAgICAgIH0sCgogICAgICBfY2FuY2VsZWRDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmNsb3NpbmdSZWFzb24gPSB0aGlzLmNsb3NpbmdSZWFzb24gfHwge307CiAgICAgICAgdGhpcy5jbG9zaW5nUmVhc29uLmNhbmNlbGVkID0gdGhpcy5jYW5jZWxlZDsKICAgICAgfSwKCiAgICAgIF93aXRoQmFja2Ryb3BDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBJZiB0YWJpbmRleCBpcyBhbHJlYWR5IHNldCwgbm8gbmVlZCB0byBvdmVycmlkZSBpdC4KICAgICAgICBpZiAodGhpcy53aXRoQmFja2Ryb3AgJiYgIXRoaXMuaGFzQXR0cmlidXRlKCd0YWJpbmRleCcpKSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgndGFiaW5kZXgnLCAnLTEnKTsKICAgICAgICAgIHRoaXMuX19zaG91bGRSZW1vdmVUYWJJbmRleCA9IHRydWU7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl9fc2hvdWxkUmVtb3ZlVGFiSW5kZXgpIHsKICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCd0YWJpbmRleCcpOwogICAgICAgICAgdGhpcy5fX3Nob3VsZFJlbW92ZVRhYkluZGV4ID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLm9wZW5lZCAmJiB0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgIHRoaXMuX21hbmFnZXIudHJhY2tCYWNrZHJvcCgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiB0YXNrcyB3aGljaCBtdXN0IG9jY3VyIGJlZm9yZSBvcGVuaW5nOyBlLmcuIG1ha2luZyB0aGUgZWxlbWVudCB2aXNpYmxlLgogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfcHJlcGFyZVJlbmRlck9wZW5lZDogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gU3RvcmUgZm9jdXNlZCBub2RlLgogICAgICAgIHRoaXMuX19yZXN0b3JlRm9jdXNOb2RlID0gdGhpcy5fbWFuYWdlci5kZWVwQWN0aXZlRWxlbWVudDsKCiAgICAgICAgLy8gTmVlZGVkIHRvIGNhbGN1bGF0ZSB0aGUgc2l6ZSBvZiB0aGUgb3ZlcmxheSBzbyB0aGF0IHRyYW5zaXRpb25zIG9uIGl0cwogICAgICAgIC8vIHNpemUgd2lsbCBoYXZlIHRoZSBjb3JyZWN0IHN0YXJ0aW5nIHBvaW50cy4KICAgICAgICB0aGlzLl9wcmVwYXJlUG9zaXRpb25pbmcoKTsKICAgICAgICB0aGlzLnJlZml0KCk7CiAgICAgICAgdGhpcy5fZmluaXNoUG9zaXRpb25pbmcoKTsKCiAgICAgICAgLy8gU2FmYXJpIHdpbGwgYXBwbHkgdGhlIGZvY3VzIHRvIHRoZSBhdXRvZm9jdXMgZWxlbWVudCB3aGVuIGRpc3BsYXllZAogICAgICAgIC8vIGZvciB0aGUgZmlyc3QgdGltZSwgc28gd2UgbWFrZSBzdXJlIHRvIHJldHVybiB0aGUgZm9jdXMgd2hlcmUgaXQgd2FzLgogICAgICAgIGlmICh0aGlzLm5vQXV0b0ZvY3VzICYmIGRvY3VtZW50LmFjdGl2ZUVsZW1lbnQgPT09IHRoaXMuX2ZvY3VzTm9kZSkgewogICAgICAgICAgdGhpcy5fZm9jdXNOb2RlLmJsdXIoKTsKICAgICAgICAgIHRoaXMuX19yZXN0b3JlRm9jdXNOb2RlLmZvY3VzKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRhc2tzIHdoaWNoIGNhdXNlIHRoZSBvdmVybGF5IHRvIGFjdHVhbGx5IG9wZW47IHR5cGljYWxseSBwbGF5IGFuCiAgICAgICAqIGFuaW1hdGlvbi4KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX3JlbmRlck9wZW5lZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZmluaXNoUmVuZGVyT3BlbmVkKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGFza3Mgd2hpY2ggY2F1c2UgdGhlIG92ZXJsYXkgdG8gYWN0dWFsbHkgY2xvc2U7IHR5cGljYWxseSBwbGF5IGFuCiAgICAgICAqIGFuaW1hdGlvbi4KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX3JlbmRlckNsb3NlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZmluaXNoUmVuZGVyQ2xvc2VkKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGFza3MgdG8gYmUgcGVyZm9ybWVkIGF0IHRoZSBlbmQgb2Ygb3BlbiBhY3Rpb24uIFdpbGwgZmlyZQogICAgICAgKiBgaXJvbi1vdmVybGF5LW9wZW5lZGAuCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9maW5pc2hSZW5kZXJPcGVuZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgdGhpcy5fX2lzQW5pbWF0aW5nID0gZmFsc2U7CgogICAgICAgIHRoaXMuZmlyZSgnaXJvbi1vdmVybGF5LW9wZW5lZCcpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRhc2tzIHRvIGJlIHBlcmZvcm1lZCBhdCB0aGUgZW5kIG9mIGNsb3NlIGFjdGlvbi4gV2lsbCBmaXJlCiAgICAgICAqIGBpcm9uLW92ZXJsYXktY2xvc2VkYC4KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX2ZpbmlzaFJlbmRlckNsb3NlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gSGlkZSB0aGUgb3ZlcmxheS4KICAgICAgICB0aGlzLnN0eWxlLmRpc3BsYXkgPSAnbm9uZSc7CiAgICAgICAgLy8gUmVzZXQgei1pbmRleCBvbmx5IGF0IHRoZSBlbmQgb2YgdGhlIGFuaW1hdGlvbi4KICAgICAgICB0aGlzLnN0eWxlLnpJbmRleCA9ICcnOwogICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgdGhpcy5fX2lzQW5pbWF0aW5nID0gZmFsc2U7CiAgICAgICAgdGhpcy5maXJlKCdpcm9uLW92ZXJsYXktY2xvc2VkJywgdGhpcy5jbG9zaW5nUmVhc29uKTsKICAgICAgfSwKCiAgICAgIF9wcmVwYXJlUG9zaXRpb25pbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUudHJhbnNpdGlvbiA9IHRoaXMuc3R5bGUud2Via2l0VHJhbnNpdGlvbiA9ICdub25lJzsKICAgICAgICB0aGlzLnN0eWxlLnRyYW5zZm9ybSA9IHRoaXMuc3R5bGUud2Via2l0VHJhbnNmb3JtID0gJ25vbmUnOwogICAgICAgIHRoaXMuc3R5bGUuZGlzcGxheSA9ICcnOwogICAgICB9LAoKICAgICAgX2ZpbmlzaFBvc2l0aW9uaW5nOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBGaXJzdCwgbWFrZSBpdCBpbnZpc2libGUgJiByZWFjdGl2YXRlIGFuaW1hdGlvbnMuCiAgICAgICAgdGhpcy5zdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgIC8vIEZvcmNlIHJlZmxvdyBiZWZvcmUgcmUtZW5hYmxpbmcgYW5pbWF0aW9ucyBzbyB0aGF0IHRoZXkgZG9uJ3Qgc3RhcnQuCiAgICAgICAgLy8gU2V0IHNjcm9sbFRvcCB0byBpdHNlbGYgc28gdGhhdCBDbG9zdXJlIENvbXBpbGVyIGRvZXNuJ3QgcmVtb3ZlIHRoaXMuCiAgICAgICAgdGhpcy5zY3JvbGxUb3AgPSB0aGlzLnNjcm9sbFRvcDsKICAgICAgICB0aGlzLnN0eWxlLnRyYW5zaXRpb24gPSB0aGlzLnN0eWxlLndlYmtpdFRyYW5zaXRpb24gPSAnJzsKICAgICAgICB0aGlzLnN0eWxlLnRyYW5zZm9ybSA9IHRoaXMuc3R5bGUud2Via2l0VHJhbnNmb3JtID0gJyc7CiAgICAgICAgLy8gTm93IHRoYXQgYW5pbWF0aW9ucyBhcmUgZW5hYmxlZCwgbWFrZSBpdCB2aXNpYmxlIGFnYWluCiAgICAgICAgdGhpcy5zdHlsZS5kaXNwbGF5ID0gJyc7CiAgICAgICAgLy8gRm9yY2UgcmVmbG93LCBzbyB0aGF0IGZvbGxvd2luZyBhbmltYXRpb25zIGFyZSBwcm9wZXJseSBzdGFydGVkLgogICAgICAgIC8vIFNldCBzY3JvbGxUb3AgdG8gaXRzZWxmIHNvIHRoYXQgQ2xvc3VyZSBDb21waWxlciBkb2Vzbid0IHJlbW92ZSB0aGlzLgogICAgICAgIHRoaXMuc2Nyb2xsVG9wID0gdGhpcy5zY3JvbGxUb3A7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQXBwbGllcyBmb2N1cyBhY2NvcmRpbmcgdG8gdGhlIG9wZW5lZCBzdGF0ZS4KICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX2FwcGx5Rm9jdXM6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm9wZW5lZCkgewogICAgICAgICAgaWYgKCF0aGlzLm5vQXV0b0ZvY3VzKSB7CiAgICAgICAgICAgIHRoaXMuX2ZvY3VzTm9kZS5mb2N1cygpOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBSZXN0b3JlIGZvY3VzLgogICAgICAgICAgaWYgKHRoaXMucmVzdG9yZUZvY3VzT25DbG9zZSAmJiB0aGlzLl9fcmVzdG9yZUZvY3VzTm9kZSkgewogICAgICAgICAgICAvLyBJZiB0aGUgYWN0aXZlRWxlbWVudCBpcyBgPGJvZHk+YCBvciBpbnNpZGUgdGhlIG92ZXJsYXksCiAgICAgICAgICAgIC8vIHdlIGFyZSBhbGxvd2VkIHRvIHJlc3RvcmUgdGhlIGZvY3VzLiBJbiBhbGwgdGhlIG90aGVyCiAgICAgICAgICAgIC8vIGNhc2VzIGZvY3VzIG1pZ2h0IGhhdmUgYmVlbiBtb3ZlZCBlbHNld2hlcmUgYnkgYW5vdGhlcgogICAgICAgICAgICAvLyBjb21wb25lbnQgb3IgYnkgYW4gdXNlciBpbnRlcmFjdGlvbiAoZS5nLiBjbGljayBvbiBhCiAgICAgICAgICAgIC8vIGJ1dHRvbiBvdXRzaWRlIHRoZSBvdmVybGF5KS4KICAgICAgICAgICAgdmFyIGFjdGl2ZUVsZW1lbnQgPSB0aGlzLl9tYW5hZ2VyLmRlZXBBY3RpdmVFbGVtZW50OwogICAgICAgICAgICBpZiAoYWN0aXZlRWxlbWVudCA9PT0gZG9jdW1lbnQuYm9keSB8fAogICAgICAgICAgICAgICAgY29tcG9zZWRDb250YWlucyh0aGlzLCBhY3RpdmVFbGVtZW50KSkgewogICAgICAgICAgICAgIHRoaXMuX19yZXN0b3JlRm9jdXNOb2RlLmZvY3VzKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX19yZXN0b3JlRm9jdXNOb2RlID0gbnVsbDsKICAgICAgICAgIHRoaXMuX2ZvY3VzTm9kZS5ibHVyKCk7CiAgICAgICAgICB0aGlzLl9mb2N1c2VkQ2hpbGQgPSBudWxsOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDYW5jZWxzIChjbG9zZXMpIHRoZSBvdmVybGF5LiBDYWxsIHdoZW4gY2xpY2sgaGFwcGVucyBvdXRzaWRlIHRoZSBvdmVybGF5LgogICAgICAgKiBAcGFyYW0geyFFdmVudH0gZXZlbnQKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX29uQ2FwdHVyZUNsaWNrOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy5ub0NhbmNlbE9uT3V0c2lkZUNsaWNrKSB7CiAgICAgICAgICB0aGlzLmNhbmNlbChldmVudCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEtlZXBzIHRyYWNrIG9mIHRoZSBmb2N1c2VkIGNoaWxkLiBJZiB3aXRoQmFja2Ryb3AsIHRyYXBzIGZvY3VzIHdpdGhpbgogICAgICAgKiBvdmVybGF5LgogICAgICAgKiBAcGFyYW0geyFFdmVudH0gZXZlbnQKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgX29uQ2FwdHVyZUZvY3VzOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy53aXRoQmFja2Ryb3ApIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdmFyIHBhdGggPSBkb20oZXZlbnQpLnBhdGg7CiAgICAgICAgaWYgKHBhdGguaW5kZXhPZih0aGlzKSA9PT0gLTEpIHsKICAgICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgICAgdGhpcy5fYXBwbHlGb2N1cygpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9mb2N1c2VkQ2hpbGQgPSAvKiogQHR5cGUge05vZGV9ICovIChwYXRoWzBdKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSGFuZGxlcyB0aGUgRVNDIGtleSBldmVudCBhbmQgY2FuY2VscyAoY2xvc2VzKSB0aGUgb3ZlcmxheS4KICAgICAgICogQHBhcmFtIHshRXZlbnR9IGV2ZW50CiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9vbkNhcHR1cmVFc2M6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKCF0aGlzLm5vQ2FuY2VsT25Fc2NLZXkpIHsKICAgICAgICAgIHRoaXMuY2FuY2VsKGV2ZW50KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSGFuZGxlcyBUQUIga2V5IGV2ZW50cyB0byB0cmFjayBmb2N1cyBjaGFuZ2VzLgogICAgICAgKiBXaWxsIHdyYXAgZm9jdXMgZm9yIG92ZXJsYXlzIHdpdGhCYWNrZHJvcC4KICAgICAgICogQHBhcmFtIHshRXZlbnR9IGV2ZW50CiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9vbkNhcHR1cmVUYWI6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKCF0aGlzLndpdGhCYWNrZHJvcCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB0aGlzLl9fZW5zdXJlRmlyc3RMYXN0Rm9jdXNhYmxlcygpOwogICAgICAgIC8vIFRBQiB3cmFwcyBmcm9tIGxhc3QgdG8gZmlyc3QgZm9jdXNhYmxlLgogICAgICAgIC8vIFNoaWZ0ICsgVEFCIHdyYXBzIGZyb20gZmlyc3QgdG8gbGFzdCBmb2N1c2FibGUuCiAgICAgICAgdmFyIHNoaWZ0ID0gZXZlbnQuc2hpZnRLZXk7CiAgICAgICAgdmFyIG5vZGVUb0NoZWNrID0KICAgICAgICAgICAgc2hpZnQgPyB0aGlzLl9fZmlyc3RGb2N1c2FibGVOb2RlIDogdGhpcy5fX2xhc3RGb2N1c2FibGVOb2RlOwogICAgICAgIHZhciBub2RlVG9TZXQgPQogICAgICAgICAgICBzaGlmdCA/IHRoaXMuX19sYXN0Rm9jdXNhYmxlTm9kZSA6IHRoaXMuX19maXJzdEZvY3VzYWJsZU5vZGU7CiAgICAgICAgdmFyIHNob3VsZFdyYXAgPSBmYWxzZTsKICAgICAgICBpZiAobm9kZVRvQ2hlY2sgPT09IG5vZGVUb1NldCkgewogICAgICAgICAgLy8gSWYgbm9kZVRvQ2hlY2sgaXMgdGhlIHNhbWUgYXMgbm9kZVRvU2V0LCBpdCBtZWFucyB3ZSBoYXZlIGFuIG92ZXJsYXkKICAgICAgICAgIC8vIHdpdGggMCBvciAxIGZvY3VzYWJsZXM7IGluIGVpdGhlciBjYXNlIHdlIHN0aWxsIG5lZWQgdG8gdHJhcCB0aGUKICAgICAgICAgIC8vIGZvY3VzIHdpdGhpbiB0aGUgb3ZlcmxheS4KICAgICAgICAgIHNob3VsZFdyYXAgPSB0cnVlOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBJbiBkb209c2hhZG93LCB0aGUgbWFuYWdlciB3aWxsIHJlY2VpdmUgZm9jdXMgY2hhbmdlcyBvbiB0aGUgbWFpbgogICAgICAgICAgLy8gcm9vdCBidXQgbm90IHRoZSBvbmVzIHdpdGhpbiBvdGhlciBzaGFkb3cgcm9vdHMsIHNvIHdlIGNhbid0IHJlbHkgb24KICAgICAgICAgIC8vIF9mb2N1c2VkQ2hpbGQsIGJ1dCB3ZSBzaG91bGQgY2hlY2sgdGhlIGRlZXBlc3QgYWN0aXZlIGVsZW1lbnQuCiAgICAgICAgICB2YXIgZm9jdXNlZE5vZGUgPSB0aGlzLl9tYW5hZ2VyLmRlZXBBY3RpdmVFbGVtZW50OwogICAgICAgICAgLy8gSWYgdGhlIGFjdGl2ZSBlbGVtZW50IGlzIG5vdCB0aGUgbm9kZVRvQ2hlY2sgYnV0IHRoZSBvdmVybGF5IGl0c2VsZiwKICAgICAgICAgIC8vIGl0IG1lYW5zIHRoZSBmb2N1cyBpcyBhYm91dCB0byBnbyBvdXRzaWRlIHRoZSBvdmVybGF5LCBoZW5jZSB3ZQogICAgICAgICAgLy8gc2hvdWxkIHByZXZlbnQgdGhhdCAoZS5nLiB1c2VyIG9wZW5zIHRoZSBvdmVybGF5IGFuZCBoaXQgU2hpZnQrVEFCKS4KICAgICAgICAgIHNob3VsZFdyYXAgPSAoZm9jdXNlZE5vZGUgPT09IG5vZGVUb0NoZWNrIHx8IGZvY3VzZWROb2RlID09PSB0aGlzKTsKICAgICAgICB9CgogICAgICAgIGlmIChzaG91bGRXcmFwKSB7CiAgICAgICAgICAvLyBXaGVuIHRoZSBvdmVybGF5IGNvbnRhaW5zIHRoZSBsYXN0IGZvY3VzYWJsZSBlbGVtZW50IG9mIHRoZSBkb2N1bWVudAogICAgICAgICAgLy8gYW5kIGl0J3MgYWxyZWFkeSBmb2N1c2VkLCBwcmVzc2luZyBUQUIgd291bGQgbW92ZSB0aGUgZm9jdXMgb3V0c2lkZQogICAgICAgICAgLy8gdGhlIGRvY3VtZW50IChlLmcuIHRvIHRoZSBicm93c2VyIHNlYXJjaCBiYXIpLiBTaW1pbGFybHksIHdoZW4gdGhlCiAgICAgICAgICAvLyBvdmVybGF5IGNvbnRhaW5zIHRoZSBmaXJzdCBmb2N1c2FibGUgZWxlbWVudCBvZiB0aGUgZG9jdW1lbnQgYW5kIGl0J3MKICAgICAgICAgIC8vIGFscmVhZHkgZm9jdXNlZCwgcHJlc3NpbmcgU2hpZnQrVEFCIHdvdWxkIG1vdmUgdGhlIGZvY3VzIG91dHNpZGUgdGhlCiAgICAgICAgICAvLyBkb2N1bWVudCAoZS5nLiB0byB0aGUgYnJvd3NlciBzZWFyY2ggYmFyKS4KICAgICAgICAgIC8vIEluIGJvdGggY2FzZXMsIHdlIHdvdWxkIG5vdCByZWNlaXZlIGEgZm9jdXMgZXZlbnQsIGJ1dCBvbmx5IGEgYmx1ci4KICAgICAgICAgIC8vIEluIG9yZGVyIHRvIGFjaGlldmUgZm9jdXMgd3JhcHBpbmcsIHdlIHByZXZlbnQgdGhpcyBUQUIgZXZlbnQgYW5kCiAgICAgICAgICAvLyBmb3JjZSB0aGUgZm9jdXMuIFRoaXMgd2lsbCBhbHNvIHByZXZlbnQgdGhlIGZvY3VzIHRvIHRlbXBvcmFyaWx5IG1vdmUKICAgICAgICAgIC8vIG91dHNpZGUgdGhlIG92ZXJsYXksIHdoaWNoIG1pZ2h0IGNhdXNlIHNjcm9sbGluZy4KICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICB0aGlzLl9mb2N1c2VkQ2hpbGQgPSBub2RlVG9TZXQ7CiAgICAgICAgICB0aGlzLl9hcHBseUZvY3VzKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJlZml0cyBpZiB0aGUgb3ZlcmxheSBpcyBvcGVuZWQgYW5kIG5vdCBhbmltYXRpbmcuCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9vbklyb25SZXNpemU6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm9wZW5lZCAmJiAhdGhpcy5fX2lzQW5pbWF0aW5nKSB7CiAgICAgICAgICB0aGlzLl9fZGVyYWYoJ3JlZml0JywgdGhpcy5yZWZpdCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFdpbGwgY2FsbCBub3RpZnlSZXNpemUgaWYgb3ZlcmxheSBpcyBvcGVuZWQuCiAgICAgICAqIENhbiBiZSBvdmVycmlkZGVuIGluIG9yZGVyIHRvIGF2b2lkIG11bHRpcGxlIG9ic2VydmVycyBvbiB0aGUgc2FtZSBub2RlLgogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfb25Ob2Rlc0NoYW5nZTogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMub3BlbmVkICYmICF0aGlzLl9faXNBbmltYXRpbmcpIHsKICAgICAgICAgIC8vIEl0IG1pZ2h0IGhhdmUgYWRkZWQgZm9jdXNhYmxlIG5vZGVzLCBzbyBpbnZhbGlkYXRlIGNhY2hlZCB2YWx1ZXMuCiAgICAgICAgICB0aGlzLmludmFsaWRhdGVUYWJiYWJsZXMoKTsKICAgICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFVwZGF0ZXMgdGhlIHJlZmVyZW5jZXMgdG8gdGhlIGZpcnN0IGFuZCBsYXN0IGZvY3VzYWJsZSBub2Rlcy4KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fZW5zdXJlRmlyc3RMYXN0Rm9jdXNhYmxlczogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGZvY3VzYWJsZU5vZGVzID0gdGhpcy5fZm9jdXNhYmxlTm9kZXM7CiAgICAgICAgdGhpcy5fX2ZpcnN0Rm9jdXNhYmxlTm9kZSA9IGZvY3VzYWJsZU5vZGVzWzBdOwogICAgICAgIHRoaXMuX19sYXN0Rm9jdXNhYmxlTm9kZSA9IGZvY3VzYWJsZU5vZGVzW2ZvY3VzYWJsZU5vZGVzLmxlbmd0aCAtIDFdOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRhc2tzIGV4ZWN1dGVkIHdoZW4gb3BlbmVkIGNoYW5nZXM6IHByZXBhcmUgZm9yIHRoZSBvcGVuaW5nLCBtb3ZlIHRoZQogICAgICAgKiBmb2N1cywgdXBkYXRlIHRoZSBtYW5hZ2VyLCByZW5kZXIgb3BlbmVkL2Nsb3NlZC4KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fb3BlbmVkQ2hhbmdlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMub3BlbmVkKSB7CiAgICAgICAgICAvLyBNYWtlIG92ZXJsYXkgdmlzaWJsZSwgdGhlbiBhZGQgaXQgdG8gdGhlIG1hbmFnZXIuCiAgICAgICAgICB0aGlzLl9wcmVwYXJlUmVuZGVyT3BlbmVkKCk7CiAgICAgICAgICB0aGlzLl9tYW5hZ2VyLmFkZE92ZXJsYXkodGhpcyk7CiAgICAgICAgICAvLyBNb3ZlIHRoZSBmb2N1cyB0byB0aGUgY2hpbGQgbm9kZSB3aXRoIFthdXRvZm9jdXNdLgogICAgICAgICAgdGhpcy5fYXBwbHlGb2N1cygpOwoKICAgICAgICAgIHRoaXMuX3JlbmRlck9wZW5lZCgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBSZW1vdmUgb3ZlcmxheSwgdGhlbiByZXN0b3JlIHRoZSBmb2N1cyBiZWZvcmUgYWN0dWFsbHkgY2xvc2luZy4KICAgICAgICAgIHRoaXMuX21hbmFnZXIucmVtb3ZlT3ZlcmxheSh0aGlzKTsKICAgICAgICAgIHRoaXMuX2FwcGx5Rm9jdXMoKTsKCiAgICAgICAgICB0aGlzLl9yZW5kZXJDbG9zZWQoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRGVib3VuY2VzIHRoZSBleGVjdXRpb24gb2YgYSBjYWxsYmFjayB0byB0aGUgbmV4dCBhbmltYXRpb24gZnJhbWUuCiAgICAgICAqIEBwYXJhbSB7IXN0cmluZ30gam9ibmFtZQogICAgICAgKiBAcGFyYW0geyFGdW5jdGlvbn0gY2FsbGJhY2sgQWx3YXlzIGJvdW5kIHRvIGB0aGlzYAogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX19kZXJhZjogZnVuY3Rpb24oam9ibmFtZSwgY2FsbGJhY2spIHsKICAgICAgICB2YXIgcmFmcyA9IHRoaXMuX19yYWZzOwogICAgICAgIGlmIChyYWZzW2pvYm5hbWVdICE9PSBudWxsKSB7CiAgICAgICAgICBjYW5jZWxBbmltYXRpb25GcmFtZShyYWZzW2pvYm5hbWVdKTsKICAgICAgICB9CiAgICAgICAgcmFmc1tqb2JuYW1lXSA9IHJlcXVlc3RBbmltYXRpb25GcmFtZShmdW5jdGlvbiBuZXh0QW5pbWF0aW9uRnJhbWUoKSB7CiAgICAgICAgICByYWZzW2pvYm5hbWVdID0gbnVsbDsKICAgICAgICAgIGNhbGxiYWNrLmNhbGwodGhpcyk7CiAgICAgICAgfS5iaW5kKHRoaXMpKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IGlzQXR0YWNoZWQKICAgICAgICogQHBhcmFtIHtib29sZWFufSBvcGVuZWQKICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBzY3JvbGxBY3Rpb24KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fdXBkYXRlU2Nyb2xsT2JzZXJ2ZXJzOiBmdW5jdGlvbihpc0F0dGFjaGVkLCBvcGVuZWQsIHNjcm9sbEFjdGlvbikgewogICAgICAgIGlmICghaXNBdHRhY2hlZCB8fCAhb3BlbmVkIHx8ICF0aGlzLl9faXNWYWxpZFNjcm9sbEFjdGlvbihzY3JvbGxBY3Rpb24pKSB7CiAgICAgICAgICByZW1vdmVTY3JvbGxMb2NrKHRoaXMpOwogICAgICAgICAgdGhpcy5fX3JlbW92ZVNjcm9sbExpc3RlbmVycygpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAoc2Nyb2xsQWN0aW9uID09PSAnbG9jaycpIHsKICAgICAgICAgICAgdGhpcy5fX3NhdmVTY3JvbGxQb3NpdGlvbigpOwogICAgICAgICAgICBwdXNoU2Nyb2xsTG9jayh0aGlzKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX19hZGRTY3JvbGxMaXN0ZW5lcnMoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fYWRkU2Nyb2xsTGlzdGVuZXJzOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIXRoaXMuX19yb290Tm9kZXMpIHsKICAgICAgICAgIHRoaXMuX19yb290Tm9kZXMgPSBbXTsKICAgICAgICAgIC8vIExpc3RlbiBmb3Igc2Nyb2xsIGV2ZW50cyBpbiBhbGwgc2hhZG93Um9vdHMgaG9zdGluZyB0aGlzIG92ZXJsYXkgb25seQogICAgICAgICAgLy8gd2hlbiBpbiBuYXRpdmUgU2hhZG93RE9NLgogICAgICAgICAgaWYgKHVzZVNoYWRvdykgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXM7CiAgICAgICAgICAgIHdoaWxlIChub2RlKSB7CiAgICAgICAgICAgICAgaWYgKG5vZGUubm9kZVR5cGUgPT09IE5vZGUuRE9DVU1FTlRfRlJBR01FTlRfTk9ERSAmJiBub2RlLmhvc3QpIHsKICAgICAgICAgICAgICAgIHRoaXMuX19yb290Tm9kZXMucHVzaChub2RlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgbm9kZSA9IG5vZGUuaG9zdCB8fCBub2RlLmFzc2lnbmVkU2xvdCB8fCBub2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX19yb290Tm9kZXMucHVzaChkb2N1bWVudCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX19yb290Tm9kZXMuZm9yRWFjaChmdW5jdGlvbihlbCkgewogICAgICAgICAgZWwuYWRkRXZlbnRMaXN0ZW5lcignc2Nyb2xsJywgdGhpcy5fX29uQ2FwdHVyZVNjcm9sbCwgewogICAgICAgICAgICBjYXB0dXJlOiB0cnVlLAogICAgICAgICAgICBwYXNzaXZlOiB0cnVlLAogICAgICAgICAgfSk7CiAgICAgICAgfSwgdGhpcyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fcmVtb3ZlU2Nyb2xsTGlzdGVuZXJzOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fX3Jvb3ROb2RlcykgewogICAgICAgICAgdGhpcy5fX3Jvb3ROb2Rlcy5mb3JFYWNoKGZ1bmN0aW9uKGVsKSB7CiAgICAgICAgICAgIGVsLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3Njcm9sbCcsIHRoaXMuX19vbkNhcHR1cmVTY3JvbGwsIHsKICAgICAgICAgICAgICBjYXB0dXJlOiB0cnVlLAogICAgICAgICAgICAgIHBhc3NpdmU6IHRydWUsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgfSwgdGhpcyk7CiAgICAgICAgfQogICAgICAgIGlmICghdGhpcy5pc0F0dGFjaGVkKSB7CiAgICAgICAgICB0aGlzLl9fcm9vdE5vZGVzID0gbnVsbDsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHBhcmFtIHtzdHJpbmc9fSBzY3JvbGxBY3Rpb24KICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9faXNWYWxpZFNjcm9sbEFjdGlvbjogZnVuY3Rpb24oc2Nyb2xsQWN0aW9uKSB7CiAgICAgICAgcmV0dXJuIHNjcm9sbEFjdGlvbiA9PT0gJ2xvY2snIHx8IHNjcm9sbEFjdGlvbiA9PT0gJ3JlZml0JyB8fAogICAgICAgICAgICBzY3JvbGxBY3Rpb24gPT09ICdjYW5jZWwnOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfX29uQ2FwdHVyZVNjcm9sbDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAodGhpcy5fX2lzQW5pbWF0aW5nKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIC8vIENoZWNrIGlmIHNjcm9sbCBvdXRzaWRlIHRoZSBvdmVybGF5LgogICAgICAgIGlmIChkb20oZXZlbnQpLnBhdGguaW5kZXhPZih0aGlzKSA+PSAwKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHN3aXRjaCAodGhpcy5zY3JvbGxBY3Rpb24pIHsKICAgICAgICAgIGNhc2UgJ2xvY2snOgogICAgICAgICAgICAvLyBOT1RFOiBzY3JvbGxpbmcgbWlnaHQgaGFwcGVuIGlmIGEgc2Nyb2xsIGV2ZW50IGlzIG5vdCBjYW5jZWxsYWJsZSwgb3IKICAgICAgICAgICAgLy8gaWYgdXNlciBwcmVzc2VkIGtleXMgdGhhdCBjYXVzZSBzY3JvbGxpbmcgKHRoZXkncmUgbm90IHByZXZlbnRlZCBpbgogICAgICAgICAgICAvLyBvcmRlciBub3QgdG8gYnJlYWsgYTExeSBmZWF0dXJlcyBsaWtlIG5hdmlnYXRlIHdpdGggYXJyb3cga2V5cykuCiAgICAgICAgICAgIHRoaXMuX19yZXN0b3JlU2Nyb2xsUG9zaXRpb24oKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdyZWZpdCc6CiAgICAgICAgICAgIHRoaXMuX19kZXJhZigncmVmaXQnLCB0aGlzLnJlZml0KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdjYW5jZWwnOgogICAgICAgICAgICB0aGlzLmNhbmNlbChldmVudCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBNZW1vaXplcyB0aGUgc2Nyb2xsIHBvc2l0aW9uIG9mIHRoZSBvdXRzaWRlIHNjcm9sbGluZyBlbGVtZW50LgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX19zYXZlU2Nyb2xsUG9zaXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIGlmIChkb2N1bWVudC5zY3JvbGxpbmdFbGVtZW50KSB7CiAgICAgICAgICB0aGlzLl9fc2Nyb2xsVG9wID0gZG9jdW1lbnQuc2Nyb2xsaW5nRWxlbWVudC5zY3JvbGxUb3A7CiAgICAgICAgICB0aGlzLl9fc2Nyb2xsTGVmdCA9IGRvY3VtZW50LnNjcm9sbGluZ0VsZW1lbnQuc2Nyb2xsTGVmdDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gU2luY2Ugd2UgZG9uJ3Qga25vdyBpZiBpcyB0aGUgYm9keSBvciBodG1sLCBnZXQgbWF4LgogICAgICAgICAgdGhpcy5fX3Njcm9sbFRvcCA9CiAgICAgICAgICAgICAgTWF0aC5tYXgoZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LnNjcm9sbFRvcCwgZG9jdW1lbnQuYm9keS5zY3JvbGxUb3ApOwogICAgICAgICAgdGhpcy5fX3Njcm9sbExlZnQgPSBNYXRoLm1heCgKICAgICAgICAgICAgICBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuc2Nyb2xsTGVmdCwgZG9jdW1lbnQuYm9keS5zY3JvbGxMZWZ0KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVzZXRzIHRoZSBzY3JvbGwgcG9zaXRpb24gb2YgdGhlIG91dHNpZGUgc2Nyb2xsaW5nIGVsZW1lbnQuCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfX3Jlc3RvcmVTY3JvbGxQb3NpdGlvbjogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKGRvY3VtZW50LnNjcm9sbGluZ0VsZW1lbnQpIHsKICAgICAgICAgIGRvY3VtZW50LnNjcm9sbGluZ0VsZW1lbnQuc2Nyb2xsVG9wID0gdGhpcy5fX3Njcm9sbFRvcDsKICAgICAgICAgIGRvY3VtZW50LnNjcm9sbGluZ0VsZW1lbnQuc2Nyb2xsTGVmdCA9IHRoaXMuX19zY3JvbGxMZWZ0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBTaW5jZSB3ZSBkb24ndCBrbm93IGlmIGlzIHRoZSBib2R5IG9yIGh0bWwsIHNldCBib3RoLgogICAgICAgICAgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LnNjcm9sbFRvcCA9IGRvY3VtZW50LmJvZHkuc2Nyb2xsVG9wID0KICAgICAgICAgICAgICB0aGlzLl9fc2Nyb2xsVG9wOwogICAgICAgICAgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LnNjcm9sbExlZnQgPSBkb2N1bWVudC5ib2R5LnNjcm9sbExlZnQgPQogICAgICAgICAgICAgIHRoaXMuX19zY3JvbGxMZWZ0OwogICAgICAgIH0KICAgICAgfSwKCiAgICB9OwoKICAgIGNvbnN0IGNvbXBvc2VkUGFyZW50ID0gbm9kZSA9PgogICAgICAgIG5vZGUuYXNzaWduZWRTbG90IHx8IG5vZGUucGFyZW50Tm9kZSB8fCBub2RlLmhvc3Q7CgogICAgY29uc3QgY29tcG9zZWRDb250YWlucyA9IChhbmNlc3RvciwgZGVzY2VuZGFudCkgPT4gewogICAgICBmb3IgKGxldCBlbGVtZW50ID0gZGVzY2VuZGFudDsgZWxlbWVudDsgZWxlbWVudCA9IGNvbXBvc2VkUGFyZW50KGVsZW1lbnQpKSB7CiAgICAgICAgaWYgKGVsZW1lbnQgPT09IGFuY2VzdG9yKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfTsKCiAgICAvKioKICAgICAgVXNlIGBQb2x5bWVyLklyb25PdmVybGF5QmVoYXZpb3JgIHRvIGltcGxlbWVudCBhbiBlbGVtZW50IHRoYXQgY2FuIGJlIGhpZGRlbgogICAgICBvciBzaG93biwgYW5kIGRpc3BsYXlzIG9uIHRvcCBvZiBvdGhlciBjb250ZW50LiBJdCBpbmNsdWRlcyBhbiBvcHRpb25hbAogICAgICBiYWNrZHJvcCwgYW5kIGNhbiBiZSB1c2VkIHRvIGltcGxlbWVudCBhIHZhcmlldHkgb2YgVUkgY29udHJvbHMgaW5jbHVkaW5nCiAgICAgIGRpYWxvZ3MgYW5kIGRyb3AgZG93bnMuIE11bHRpcGxlIG92ZXJsYXlzIG1heSBiZSBkaXNwbGF5ZWQgYXQgb25jZS4KCiAgICAgIFNlZSB0aGUgW2RlbW8gc291cmNlCiAgICAgIGNvZGVdKGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyRWxlbWVudHMvaXJvbi1vdmVybGF5LWJlaGF2aW9yL2Jsb2IvbWFzdGVyL2RlbW8vc2ltcGxlLW92ZXJsYXkuaHRtbCkKICAgICAgZm9yIGFuIGV4YW1wbGUuCgogICAgICAjIyMgQ2xvc2luZyBhbmQgY2FuY2VsaW5nCgogICAgICBBbiBvdmVybGF5IG1heSBiZSBoaWRkZW4gYnkgY2xvc2luZyBvciBjYW5jZWxpbmcuIFRoZSBkaWZmZXJlbmNlIGJldHdlZW4gY2xvc2UKICAgICAgYW5kIGNhbmNlbCBpcyB1c2VyIGludGVudC4gQ2xvc2luZyBnZW5lcmFsbHkgaW1wbGllcyB0aGF0IHRoZSB1c2VyCiAgICAgIGFja25vd2xlZGdlZCB0aGUgY29udGVudCBvbiB0aGUgb3ZlcmxheS4gQnkgZGVmYXVsdCwgaXQgd2lsbCBjYW5jZWwgd2hlbmV2ZXIKICAgICAgdGhlIHVzZXIgdGFwcyBvdXRzaWRlIGl0IG9yIHByZXNzZXMgdGhlIGVzY2FwZSBrZXkuIFRoaXMgYmVoYXZpb3IgaXMKICAgICAgY29uZmlndXJhYmxlIHdpdGggdGhlIGBuby1jYW5jZWwtb24tZXNjLWtleWAgYW5kIHRoZQogICAgICBgbm8tY2FuY2VsLW9uLW91dHNpZGUtY2xpY2tgIHByb3BlcnRpZXMuIGBjbG9zZSgpYCBzaG91bGQgYmUgY2FsbGVkIGV4cGxpY2l0bHkKICAgICAgYnkgdGhlIGltcGxlbWVudGVyIHdoZW4gdGhlIHVzZXIgaW50ZXJhY3RzIHdpdGggYSBjb250cm9sIGluIHRoZSBvdmVybGF5CiAgICAgIGVsZW1lbnQuIFdoZW4gdGhlIGRpYWxvZyBpcyBjYW5jZWxlZCwgdGhlIG92ZXJsYXkgZmlyZXMgYW4KICAgICAgJ2lyb24tb3ZlcmxheS1jYW5jZWxlZCcgZXZlbnQuIENhbGwgYHByZXZlbnREZWZhdWx0YCBvbiB0aGlzIGV2ZW50IHRvIHByZXZlbnQKICAgICAgdGhlIG92ZXJsYXkgZnJvbSBjbG9zaW5nLgoKICAgICAgIyMjIFBvc2l0aW9uaW5nCgogICAgICBCeSBkZWZhdWx0IHRoZSBlbGVtZW50IGlzIHNpemVkIGFuZCBwb3NpdGlvbmVkIHRvIGZpdCBhbmQgY2VudGVyZWQgaW5zaWRlIHRoZQogICAgICB3aW5kb3cuIFlvdSBjYW4gcG9zaXRpb24gYW5kIHNpemUgaXQgbWFudWFsbHkgdXNpbmcgQ1NTLiBTZWUKICAgICAgYFBvbHltZXIuSXJvbkZpdEJlaGF2aW9yYC4KCiAgICAgICMjIyBCYWNrZHJvcAoKICAgICAgU2V0IHRoZSBgd2l0aC1iYWNrZHJvcGAgYXR0cmlidXRlIHRvIGRpc3BsYXkgYSBiYWNrZHJvcCBiZWhpbmQgdGhlIG92ZXJsYXkuCiAgICAgIFRoZSBiYWNrZHJvcCBpcyBhcHBlbmRlZCB0byBgPGJvZHk+YCBhbmQgaXMgb2YgdHlwZSBgPGlyb24tb3ZlcmxheS1iYWNrZHJvcD5gLgogICAgICBTZWUgaXRzIGRvYyBwYWdlIGZvciBzdHlsaW5nIG9wdGlvbnMuCgogICAgICBJbiBhZGRpdGlvbiwgYHdpdGgtYmFja2Ryb3BgIHdpbGwgd3JhcCB0aGUgZm9jdXMgd2l0aGluIHRoZSBjb250ZW50IGluIHRoZQogICAgICBsaWdodCBET00uIE92ZXJyaWRlIHRoZSBbYF9mb2N1c2FibGVOb2Rlc2AKICAgICAgZ2V0dGVyXSgjUG9seW1lci5Jcm9uT3ZlcmxheUJlaGF2aW9yOnByb3BlcnR5LV9mb2N1c2FibGVOb2RlcykgdG8gYWNoaWV2ZSBhCiAgICAgIGRpZmZlcmVudCBiZWhhdmlvci4KCiAgICAgICMjIyBMaW1pdGF0aW9ucwoKICAgICAgVGhlIGVsZW1lbnQgaXMgc3R5bGVkIHRvIGFwcGVhciBvbiB0b3Agb2Ygb3RoZXIgY29udGVudCBieSBzZXR0aW5nIGl0cwogICAgICBgei1pbmRleGAgcHJvcGVydHkuIFlvdSBtdXN0IGVuc3VyZSBubyBlbGVtZW50IGhhcyBhIHN0YWNraW5nIGNvbnRleHQgd2l0aCBhCiAgICAgIGhpZ2hlciBgei1pbmRleGAgdGhhbiBpdHMgcGFyZW50IHN0YWNraW5nIGNvbnRleHQuIFlvdSBzaG91bGQgcGxhY2UgdGhpcwogICAgICBlbGVtZW50IGFzIGEgY2hpbGQgb2YgYDxib2R5PmAgd2hlbmV2ZXIgcG9zc2libGUuCgogICAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAgQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uT3ZlcmxheUJlaGF2aW9yID0KICAgICAgICBbSXJvbkZpdEJlaGF2aW9yLCBJcm9uUmVzaXphYmxlQmVoYXZpb3IsIElyb25PdmVybGF5QmVoYXZpb3JJbXBsXTsKCiAgICAvKioKICAgICAqIEZpcmVkIGFmdGVyIHRoZSBvdmVybGF5IG9wZW5zLgogICAgICogQGV2ZW50IGlyb24tb3ZlcmxheS1vcGVuZWQKICAgICAqLwoKICAgIC8qKgogICAgICogRmlyZWQgd2hlbiB0aGUgb3ZlcmxheSBpcyBjYW5jZWxlZCwgYnV0IGJlZm9yZSBpdCBpcyBjbG9zZWQuCiAgICAgKiBAZXZlbnQgaXJvbi1vdmVybGF5LWNhbmNlbGVkCiAgICAgKiBAcGFyYW0ge0V2ZW50fSBldmVudCBUaGUgY2xvc2luZyBvZiB0aGUgb3ZlcmxheSBjYW4gYmUgcHJldmVudGVkCiAgICAgKiBieSBjYWxsaW5nIGBldmVudC5wcmV2ZW50RGVmYXVsdCgpYC4gVGhlIGBldmVudC5kZXRhaWxgIGlzIHRoZSBvcmlnaW5hbCBldmVudAogICAgICogdGhhdCBvcmlnaW5hdGVkIHRoZSBjYW5jZWxpbmcgKGUuZy4gRVNDIGtleWJvYXJkIGV2ZW50IG9yIGNsaWNrIGV2ZW50IG91dHNpZGUKICAgICAqIHRoZSBvdmVybGF5KS4KICAgICAqLwoKICAgIC8qKgogICAgICogRmlyZWQgYWZ0ZXIgdGhlIG92ZXJsYXkgY2xvc2VzLgogICAgICogQGV2ZW50IGlyb24tb3ZlcmxheS1jbG9zZWQKICAgICAqIEBwYXJhbSB7RXZlbnR9IGV2ZW50IFRoZSBgZXZlbnQuZGV0YWlsYCBpcyB0aGUgYGNsb3NpbmdSZWFzb25gIHByb3BlcnR5CiAgICAgKiAoY29udGFpbnMgYGNhbmNlbGVkYCwgd2hldGhlciB0aGUgb3ZlcmxheSB3YXMgY2FuY2VsZWQpLgogICAgICovCgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgIFVzZSBgUG9seW1lci5QYXBlckRpYWxvZ0JlaGF2aW9yYCBhbmQgYHBhcGVyLWRpYWxvZy1zaGFyZWQtc3R5bGVzLmh0bWxgIHRvCiAgICAgIGltcGxlbWVudCBhIE1hdGVyaWFsIERlc2lnbiBkaWFsb2cuCgogICAgICBGb3IgZXhhbXBsZSwgaWYgYDxwYXBlci1kaWFsb2ctaW1wbD5gIGltcGxlbWVudHMgdGhpcyBiZWhhdmlvcjoKCiAgICAgICAgICA8cGFwZXItZGlhbG9nLWltcGw+CiAgICAgICAgICAgICAgPGgyPkhlYWRlcjwvaDI+CiAgICAgICAgICAgICAgPGRpdj5EaWFsb2cgYm9keTwvZGl2PgogICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImJ1dHRvbnMiPgogICAgICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uIGRpYWxvZy1kaXNtaXNzPkNhbmNlbDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uIGRpYWxvZy1jb25maXJtPkFjY2VwdDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC9wYXBlci1kaWFsb2ctaW1wbD4KCiAgICAgIGBwYXBlci1kaWFsb2ctc2hhcmVkLXN0eWxlcy5odG1sYCBwcm92aWRlIHN0eWxlcyBmb3IgYSBoZWFkZXIsIGNvbnRlbnQgYXJlYSwKICAgICAgYW5kIGFuIGFjdGlvbiBhcmVhIGZvciBidXR0b25zLiBVc2UgdGhlIGA8aDI+YCB0YWcgZm9yIHRoZSBoZWFkZXIgYW5kIHRoZQogICAgICBgYnV0dG9uc2AgY2xhc3MgZm9yIHRoZSBhY3Rpb24gYXJlYS4gWW91IGNhbiB1c2UgdGhlIGBwYXBlci1kaWFsb2ctc2Nyb2xsYWJsZWAKICAgICAgZWxlbWVudCAoaW4gaXRzIG93biByZXBvc2l0b3J5KSBpZiB5b3UgbmVlZCBhIHNjcm9sbGluZyBjb250ZW50IGFyZWEuCgogICAgICBVc2UgdGhlIGBkaWFsb2ctZGlzbWlzc2AgYW5kIGBkaWFsb2ctY29uZmlybWAgYXR0cmlidXRlcyBvbiBpbnRlcmFjdGl2ZQogICAgICBjb250cm9scyB0byBjbG9zZSB0aGUgZGlhbG9nLiBJZiB0aGUgdXNlciBkaXNtaXNzZXMgdGhlIGRpYWxvZyB3aXRoCiAgICAgIGBkaWFsb2ctY29uZmlybWAsIHRoZSBgY2xvc2luZ1JlYXNvbmAgd2lsbCB1cGRhdGUgdG8gaW5jbHVkZSBgY29uZmlybWVkOgogICAgICB0cnVlYC4KCiAgICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgICBUaGlzIGVsZW1lbnQgaGFzIGByb2xlPSJkaWFsb2ciYCBieSBkZWZhdWx0LiBEZXBlbmRpbmcgb24gdGhlIGNvbnRleHQsIGl0IG1heQogICAgICBiZSBtb3JlIGFwcHJvcHJpYXRlIHRvIG92ZXJyaWRlIHRoaXMgYXR0cmlidXRlIHdpdGggYHJvbGU9ImFsZXJ0ZGlhbG9nImAuCgogICAgICBJZiBgbW9kYWxgIGlzIHNldCwgdGhlIGVsZW1lbnQgd2lsbCBwcmV2ZW50IHRoZSBmb2N1cyBmcm9tIGV4aXRpbmcgdGhlCiAgICAgIGVsZW1lbnQuIEl0IHdpbGwgYWxzbyBlbnN1cmUgdGhhdCBmb2N1cyByZW1haW5zIGluIHRoZSBkaWFsb2cuCgogICAgICBAaGVybyBoZXJvLnN2ZwogICAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAgQHBvbHltZXJCZWhhdmlvciBQYXBlckRpYWxvZ0JlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IFBhcGVyRGlhbG9nQmVoYXZpb3JJbXBsID0gewoKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHsncm9sZSc6ICdkaWFsb2cnLCAndGFiaW5kZXgnOiAnLTEnfSwKCiAgICAgIHByb3BlcnRpZXM6IHsKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgYG1vZGFsYCBpcyB0cnVlLCB0aGlzIGltcGxpZXMgYG5vLWNhbmNlbC1vbi1vdXRzaWRlLWNsaWNrYCwKICAgICAgICAgKiBgbm8tY2FuY2VsLW9uLWVzYy1rZXlgIGFuZCBgd2l0aC1iYWNrZHJvcGAuCiAgICAgICAgICovCiAgICAgICAgbW9kYWw6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICBfX3JlYWRpZWQ6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9CgogICAgICB9LAoKICAgICAgb2JzZXJ2ZXJzOiBbJ19tb2RhbENoYW5nZWQobW9kYWwsIF9fcmVhZGllZCknXSwKCiAgICAgIGxpc3RlbmVyczogeyd0YXAnOiAnX29uRGlhbG9nQ2xpY2snfSwKCiAgICAgIC8qKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgcmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIE9ubHkgbm93IHRoZXNlIHByb3BlcnRpZXMgY2FuIGJlIHJlYWQuCiAgICAgICAgdGhpcy5fX3ByZXZOb0NhbmNlbE9uT3V0c2lkZUNsaWNrID0gdGhpcy5ub0NhbmNlbE9uT3V0c2lkZUNsaWNrOwogICAgICAgIHRoaXMuX19wcmV2Tm9DYW5jZWxPbkVzY0tleSA9IHRoaXMubm9DYW5jZWxPbkVzY0tleTsKICAgICAgICB0aGlzLl9fcHJldldpdGhCYWNrZHJvcCA9IHRoaXMud2l0aEJhY2tkcm9wOwogICAgICAgIHRoaXMuX19yZWFkaWVkID0gdHJ1ZTsKICAgICAgfSwKCiAgICAgIF9tb2RhbENoYW5nZWQ6IGZ1bmN0aW9uKG1vZGFsLCByZWFkaWVkKSB7CiAgICAgICAgLy8gbW9kYWwgaW1wbGllcyBub0NhbmNlbE9uT3V0c2lkZUNsaWNrLCBub0NhbmNlbE9uRXNjS2V5IGFuZCB3aXRoQmFja2Ryb3AuCiAgICAgICAgLy8gV2UgbmVlZCB0byB3YWl0IGZvciB0aGUgZWxlbWVudCB0byBiZSByZWFkeSBiZWZvcmUgd2UgY2FuIHJlYWQgdGhlCiAgICAgICAgLy8gcHJvcGVydGllcyB2YWx1ZXMuCiAgICAgICAgaWYgKCFyZWFkaWVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBpZiAobW9kYWwpIHsKICAgICAgICAgIHRoaXMuX19wcmV2Tm9DYW5jZWxPbk91dHNpZGVDbGljayA9IHRoaXMubm9DYW5jZWxPbk91dHNpZGVDbGljazsKICAgICAgICAgIHRoaXMuX19wcmV2Tm9DYW5jZWxPbkVzY0tleSA9IHRoaXMubm9DYW5jZWxPbkVzY0tleTsKICAgICAgICAgIHRoaXMuX19wcmV2V2l0aEJhY2tkcm9wID0gdGhpcy53aXRoQmFja2Ryb3A7CiAgICAgICAgICB0aGlzLm5vQ2FuY2VsT25PdXRzaWRlQ2xpY2sgPSB0cnVlOwogICAgICAgICAgdGhpcy5ub0NhbmNlbE9uRXNjS2V5ID0gdHJ1ZTsKICAgICAgICAgIHRoaXMud2l0aEJhY2tkcm9wID0gdHJ1ZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gSWYgdGhlIHZhbHVlIHdhcyBjaGFuZ2VkIHRvIGZhbHNlLCBsZXQgaXQgZmFsc2UuCiAgICAgICAgICB0aGlzLm5vQ2FuY2VsT25PdXRzaWRlQ2xpY2sgPQogICAgICAgICAgICAgIHRoaXMubm9DYW5jZWxPbk91dHNpZGVDbGljayAmJiB0aGlzLl9fcHJldk5vQ2FuY2VsT25PdXRzaWRlQ2xpY2s7CiAgICAgICAgICB0aGlzLm5vQ2FuY2VsT25Fc2NLZXkgPQogICAgICAgICAgICAgIHRoaXMubm9DYW5jZWxPbkVzY0tleSAmJiB0aGlzLl9fcHJldk5vQ2FuY2VsT25Fc2NLZXk7CiAgICAgICAgICB0aGlzLndpdGhCYWNrZHJvcCA9IHRoaXMud2l0aEJhY2tkcm9wICYmIHRoaXMuX19wcmV2V2l0aEJhY2tkcm9wOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF91cGRhdGVDbG9zaW5nUmVhc29uQ29uZmlybWVkOiBmdW5jdGlvbihjb25maXJtZWQpIHsKICAgICAgICB0aGlzLmNsb3NpbmdSZWFzb24gPSB0aGlzLmNsb3NpbmdSZWFzb24gfHwge307CiAgICAgICAgdGhpcy5jbG9zaW5nUmVhc29uLmNvbmZpcm1lZCA9IGNvbmZpcm1lZDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBXaWxsIGRpc21pc3MgdGhlIGRpYWxvZyBpZiB1c2VyIGNsaWNrZWQgb24gYW4gZWxlbWVudCB3aXRoIGRpYWxvZy1kaXNtaXNzCiAgICAgICAqIG9yIGRpYWxvZy1jb25maXJtIGF0dHJpYnV0ZS4KICAgICAgICovCiAgICAgIF9vbkRpYWxvZ0NsaWNrOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIC8vIFNlYXJjaCBmb3IgdGhlIGVsZW1lbnQgd2l0aCBkaWFsb2ctY29uZmlybSBvciBkaWFsb2ctZGlzbWlzcywKICAgICAgICAvLyBmcm9tIHRoZSByb290IHRhcmdldCB1bnRpbCB0aGlzIChleGNsdWRlZCkuCiAgICAgICAgdmFyIHBhdGggPSBkb20oZXZlbnQpLnBhdGg7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBwYXRoLmluZGV4T2YodGhpcyk7IGkgPCBsOyBpKyspIHsKICAgICAgICAgIHZhciB0YXJnZXQgPSBwYXRoW2ldOwogICAgICAgICAgaWYgKHRhcmdldC5oYXNBdHRyaWJ1dGUgJiYKICAgICAgICAgICAgICAodGFyZ2V0Lmhhc0F0dHJpYnV0ZSgnZGlhbG9nLWRpc21pc3MnKSB8fAogICAgICAgICAgICAgICB0YXJnZXQuaGFzQXR0cmlidXRlKCdkaWFsb2ctY29uZmlybScpKSkgewogICAgICAgICAgICB0aGlzLl91cGRhdGVDbG9zaW5nUmVhc29uQ29uZmlybWVkKAogICAgICAgICAgICAgICAgdGFyZ2V0Lmhhc0F0dHJpYnV0ZSgnZGlhbG9nLWNvbmZpcm0nKSk7CiAgICAgICAgICAgIHRoaXMuY2xvc2UoKTsKICAgICAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVyRGlhbG9nQmVoYXZpb3IgPQogICAgICAgIFtJcm9uT3ZlcmxheUJlaGF2aW9yLCBQYXBlckRpYWxvZ0JlaGF2aW9ySW1wbF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbRGlhbG9nc10oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL2RpYWxvZ3MuaHRtbCkKCiAgICBgcGFwZXItZGlhbG9nLXNjcm9sbGFibGVgIGltcGxlbWVudHMgYSBzY3JvbGxpbmcgYXJlYSB1c2VkIGluIGEgTWF0ZXJpYWwgRGVzaWduCiAgICBkaWFsb2cuIEl0IHNob3dzIGEgZGl2aWRlciBhdCB0aGUgdG9wIGFuZC9vciBib3R0b20gaW5kaWNhdGluZyBtb3JlIGNvbnRlbnQsCiAgICBkZXBlbmRpbmcgb24gc2Nyb2xsIHBvc2l0aW9uLiBVc2UgdGhpcyB0b2dldGhlciB3aXRoIGVsZW1lbnRzIGltcGxlbWVudGluZwogICAgYFBvbHltZXIuUGFwZXJEaWFsb2dCZWhhdmlvcmAuCgogICAgICAgIDxwYXBlci1kaWFsb2ctaW1wbD4KICAgICAgICAgIDxoMj5IZWFkZXI8L2gyPgogICAgICAgICAgPHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlPgogICAgICAgICAgICBMb3JlbSBpcHN1bS4uLgogICAgICAgICAgPC9wYXBlci1kaWFsb2ctc2Nyb2xsYWJsZT4KICAgICAgICAgIDxkaXYgY2xhc3M9ImJ1dHRvbnMiPgogICAgICAgICAgICA8cGFwZXItYnV0dG9uPk9LPC9wYXBlci1idXR0b24+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3BhcGVyLWRpYWxvZy1pbXBsPgoKICAgIEl0IHNob3dzIGEgdG9wIGRpdmlkZXIgYWZ0ZXIgc2Nyb2xsaW5nIGlmIGl0IGlzIG5vdCB0aGUgZmlyc3QgY2hpbGQgaW4gaXRzCiAgICBwYXJlbnQgY29udGFpbmVyLCBpbmRpY2F0aW5nIHRoZXJlIGlzIG1vcmUgY29udGVudCBhYm92ZS4gSXQgc2hvd3MgYSBib3R0b20KICAgIGRpdmlkZXIgaWYgaXQgaXMgc2Nyb2xsYWJsZSBhbmQgaXQgaXMgbm90IHRoZSBsYXN0IGNoaWxkIGluIGl0cyBwYXJlbnQKICAgIGNvbnRhaW5lciwgaW5kaWNhdGluZyB0aGVyZSBpcyBtb3JlIGNvbnRlbnQgYmVsb3cuIFRoZSBib3R0b20gZGl2aWRlciBpcyBoaWRkZW4KICAgIGlmIGl0IGlzIHNjcm9sbGVkIHRvIHRoZSBib3R0b20uCgogICAgSWYgYHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlYCBpcyBub3QgYSBkaXJlY3QgY2hpbGQgb2YgdGhlIGVsZW1lbnQgaW1wbGVtZW50aW5nCiAgICBgUG9seW1lci5QYXBlckRpYWxvZ0JlaGF2aW9yYCwgcmVtZW1iZXIgdG8gc2V0IHRoZSBgZGlhbG9nRWxlbWVudGA6CgogICAgICAgIDxwYXBlci1kaWFsb2ctaW1wbCBpZD0ibXlEaWFsb2ciPgogICAgICAgICAgPGgyPkhlYWRlcjwvaDI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJteS1jb250ZW50LXdyYXBwZXIiPgogICAgICAgICAgICA8aDQ+U3ViLWhlYWRlcjwvaDQ+CiAgICAgICAgICAgIDxwYXBlci1kaWFsb2ctc2Nyb2xsYWJsZT4KICAgICAgICAgICAgICBMb3JlbSBpcHN1bS4uLgogICAgICAgICAgICA8L3BhcGVyLWRpYWxvZy1zY3JvbGxhYmxlPgogICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJidXR0b25zIj4KICAgICAgICAgICAgPHBhcGVyLWJ1dHRvbj5PSzwvcGFwZXItYnV0dG9uPgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC9wYXBlci1kaWFsb2ctaW1wbD4KCiAgICAgICAgPHNjcmlwdD4KICAgICAgICAgIHZhciBzY3JvbGxhYmxlID0KICAgIFBvbHltZXIuZG9tKG15RGlhbG9nKS5xdWVyeVNlbGVjdG9yKCdwYXBlci1kaWFsb2ctc2Nyb2xsYWJsZScpOwogICAgICAgICAgc2Nyb2xsYWJsZS5kaWFsb2dFbGVtZW50ID0gbXlEaWFsb2c7CiAgICAgICAgPC9KQVZBX1NDUklJSUlQVC8+CgogICAgIyMjIFN0eWxpbmcKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlYCB8IE1peGluIGZvciB0aGUgc2Nyb2xsYWJsZSBjb250ZW50IHwge30KCiAgICBAZ3JvdXAgUGFwZXIgRWxlbWVudHMKICAgIEBlbGVtZW50IHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgIEBoZXJvIGhlcm8uc3ZnCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KCiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgIDpob3N0KC5pcy1zY3JvbGxlZDpub3QoOmZpcnN0LWNoaWxkKSk6OmJlZm9yZSB7CiAgICAgICAgY29udGVudDogJyc7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHRvcDogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGhlaWdodDogMXB4OwogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLWRpdmlkZXItY29sb3IpOwogICAgICB9CgogICAgICA6aG9zdCguY2FuLXNjcm9sbDpub3QoLnNjcm9sbGVkLXRvLWJvdHRvbSk6bm90KDpsYXN0LWNoaWxkKSk6OmFmdGVyIHsKICAgICAgICBjb250ZW50OiAnJzsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgYm90dG9tOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgaGVpZ2h0OiAxcHg7CiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tZGl2aWRlci1jb2xvcik7CiAgICAgIH0KCiAgICAgIC5zY3JvbGxhYmxlIHsKICAgICAgICBwYWRkaW5nOiAwIDI0cHg7CgogICAgICAgIEBhcHBseSAtLWxheW91dC1zY3JvbGw7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZGlhbG9nLXNjcm9sbGFibGU7CiAgICAgIH0KCiAgICAgIC5maXQgewogICAgICAgIEBhcHBseSAtLWxheW91dC1maXQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPGRpdiBpZD0ic2Nyb2xsYWJsZSIgY2xhc3M9InNjcm9sbGFibGUiIG9uLXNjcm9sbD0idXBkYXRlU2Nyb2xsU3RhdGUiPgogICAgICA8c2xvdD48L3Nsb3Q+CiAgICA8L2Rpdj4KYCwKCiAgICAgIGlzOiAncGFwZXItZGlhbG9nLXNjcm9sbGFibGUnLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGlhbG9nIGVsZW1lbnQgdGhhdCBpbXBsZW1lbnRzIGBQb2x5bWVyLlBhcGVyRGlhbG9nQmVoYXZpb3JgCiAgICAgICAgICogY29udGFpbmluZyB0aGlzIGVsZW1lbnQuCiAgICAgICAgICogQHR5cGUgez9Ob2RlfQogICAgICAgICAqLwogICAgICAgIGRpYWxvZ0VsZW1lbnQ6IHt0eXBlOiBPYmplY3R9CgogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIHNjcm9sbGluZyBlbGVtZW50LgogICAgICAgKi8KICAgICAgZ2V0IHNjcm9sbFRhcmdldCgpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLnNjcm9sbGFibGU7CiAgICAgIH0sCgogICAgICByZWFkeTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZW5zdXJlVGFyZ2V0KCk7CiAgICAgICAgdGhpcy5jbGFzc0xpc3QuYWRkKCduby1wYWRkaW5nJyk7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZW5zdXJlVGFyZ2V0KCk7CiAgICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKHRoaXMudXBkYXRlU2Nyb2xsU3RhdGUuYmluZCh0aGlzKSk7CiAgICAgIH0sCgogICAgICB1cGRhdGVTY3JvbGxTdGF0ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy50b2dnbGVDbGFzcygnaXMtc2Nyb2xsZWQnLCB0aGlzLnNjcm9sbFRhcmdldC5zY3JvbGxUb3AgPiAwKTsKICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKAogICAgICAgICAgICAnY2FuLXNjcm9sbCcsCiAgICAgICAgICAgIHRoaXMuc2Nyb2xsVGFyZ2V0Lm9mZnNldEhlaWdodCA8IHRoaXMuc2Nyb2xsVGFyZ2V0LnNjcm9sbEhlaWdodCk7CiAgICAgICAgdGhpcy50b2dnbGVDbGFzcygKICAgICAgICAgICAgJ3Njcm9sbGVkLXRvLWJvdHRvbScsCiAgICAgICAgICAgIHRoaXMuc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCArIHRoaXMuc2Nyb2xsVGFyZ2V0Lm9mZnNldEhlaWdodCA+PQogICAgICAgICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsSGVpZ2h0KTsKICAgICAgfSwKCiAgICAgIF9lbnN1cmVUYXJnZXQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFJlYWQgcGFyZW50RWxlbWVudCBpbnN0ZWFkIG9mIHBhcmVudE5vZGUgaW4gb3JkZXIgdG8gc2tpcCBzaGFkb3dSb290cy4KICAgICAgICB0aGlzLmRpYWxvZ0VsZW1lbnQgPSB0aGlzLmRpYWxvZ0VsZW1lbnQgfHwgdGhpcy5wYXJlbnRFbGVtZW50OwogICAgICAgIC8vIENoZWNrIGlmIGRpYWxvZyBpbXBsZW1lbnRzIHBhcGVyLWRpYWxvZy1iZWhhdmlvci4gSWYgbm90LCBmaXQKICAgICAgICAvLyBzY3JvbGxUYXJnZXQgdG8gaG9zdC4KICAgICAgICBpZiAodGhpcy5kaWFsb2dFbGVtZW50ICYmIHRoaXMuZGlhbG9nRWxlbWVudC5iZWhhdmlvcnMgJiYKICAgICAgICAgICAgdGhpcy5kaWFsb2dFbGVtZW50LmJlaGF2aW9ycy5pbmRleE9mKFBhcGVyRGlhbG9nQmVoYXZpb3JJbXBsKSA+PSAwKSB7CiAgICAgICAgICB0aGlzLmRpYWxvZ0VsZW1lbnQuc2l6aW5nVGFyZ2V0ID0gdGhpcy5zY3JvbGxUYXJnZXQ7CiAgICAgICAgICB0aGlzLnNjcm9sbFRhcmdldC5jbGFzc0xpc3QucmVtb3ZlKCdmaXQnKTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuZGlhbG9nRWxlbWVudCkgewogICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuY2xhc3NMaXN0LmFkZCgnZml0Jyk7CiAgICAgICAgfQogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvLyBHaXZlIHRoZSB1c2VyIHRoZSBjaG9pY2UgdG8gb3B0IG91dCBvZiBmb250IGxvYWRpbmcuCiAgICBpZiAoIXdpbmRvdy5wb2x5bWVyU2tpcExvYWRpbmdGb250Um9ib3RvKSB7CiAgICAgIGNvbnN0IGxpbmsgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdsaW5rJyk7CiAgICAgIGxpbmsucmVsID0gJ3N0eWxlc2hlZXQnOwogICAgICBsaW5rLnR5cGUgPSAndGV4dC9jc3MnOwogICAgICBsaW5rLmNyb3NzT3JpZ2luID0gJ2Fub255bW91cyc7CiAgICAgIGxpbmsuaHJlZiA9CiAgICAgICAgICAnaHR0cHM6Ly9mb250cy5nb29nbGVhcGlzLmNvbS9jc3M/ZmFtaWx5PVJvYm90bytNb25vOjQwMCw3MDB8Um9ib3RvOjQwMCwzMDAsMzAwaXRhbGljLDQwMGl0YWxpYyw1MDAsNTAwaXRhbGljLDcwMCw3MDBpdGFsaWMnOwogICAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKGxpbmspOwogICAgfQoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgY29uc3QgdGVtcGxhdGUkYSA9IGh0bWxgPGN1c3RvbS1zdHlsZT4KICA8c3R5bGUgaXM9ImN1c3RvbS1zdHlsZSI+CiAgICBodG1sIHsKCiAgICAgIC8qIFNoYXJlZCBTdHlsZXMgKi8KICAgICAgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlOiB7CiAgICAgICAgZm9udC1mYW1pbHk6ICdSb2JvdG8nLCAnTm90bycsIHNhbnMtc2VyaWY7CiAgICAgICAgLXdlYmtpdC1mb250LXNtb290aGluZzogYW50aWFsaWFzZWQ7CiAgICAgIH07CgogICAgICAtLXBhcGVyLWZvbnQtY29tbW9uLWNvZGU6IHsKICAgICAgICBmb250LWZhbWlseTogJ1JvYm90byBNb25vJywgJ0NvbnNvbGFzJywgJ01lbmxvJywgbW9ub3NwYWNlOwogICAgICAgIC13ZWJraXQtZm9udC1zbW9vdGhpbmc6IGFudGlhbGlhc2VkOwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LWNvbW1vbi1leHBlbnNpdmUta2VybmluZzogewogICAgICAgIHRleHQtcmVuZGVyaW5nOiBvcHRpbWl6ZUxlZ2liaWxpdHk7CiAgICAgIH07CgogICAgICAtLXBhcGVyLWZvbnQtY29tbW9uLW5vd3JhcDogewogICAgICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgICB0ZXh0LW92ZXJmbG93OiBlbGxpcHNpczsKICAgICAgfTsKCiAgICAgIC8qIE1hdGVyaWFsIEZvbnQgU3R5bGVzICovCgogICAgICAtLXBhcGVyLWZvbnQtZGlzcGxheTQ6IHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLW5vd3JhcDsKCiAgICAgICAgZm9udC1zaXplOiAxMTJweDsKICAgICAgICBmb250LXdlaWdodDogMzAwOwogICAgICAgIGxldHRlci1zcGFjaW5nOiAtLjA0NGVtOwogICAgICAgIGxpbmUtaGVpZ2h0OiAxMjBweDsKICAgICAgfTsKCiAgICAgIC0tcGFwZXItZm9udC1kaXNwbGF5MzogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tbm93cmFwOwoKICAgICAgICBmb250LXNpemU6IDU2cHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IDQwMDsKICAgICAgICBsZXR0ZXItc3BhY2luZzogLS4wMjZlbTsKICAgICAgICBsaW5lLWhlaWdodDogNjBweDsKICAgICAgfTsKCiAgICAgIC0tcGFwZXItZm9udC1kaXNwbGF5MjogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CgogICAgICAgIGZvbnQtc2l6ZTogNDVweDsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICAgIGxldHRlci1zcGFjaW5nOiAtLjAxOGVtOwogICAgICAgIGxpbmUtaGVpZ2h0OiA0OHB4OwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LWRpc3BsYXkxOiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKCiAgICAgICAgZm9udC1zaXplOiAzNHB4OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgICAgbGV0dGVyLXNwYWNpbmc6IC0uMDFlbTsKICAgICAgICBsaW5lLWhlaWdodDogNDBweDsKICAgICAgfTsKCiAgICAgIC0tcGFwZXItZm9udC1oZWFkbGluZTogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CgogICAgICAgIGZvbnQtc2l6ZTogMjRweDsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICAgIGxldHRlci1zcGFjaW5nOiAtLjAxMmVtOwogICAgICAgIGxpbmUtaGVpZ2h0OiAzMnB4OwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LXRpdGxlOiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1ub3dyYXA7CgogICAgICAgIGZvbnQtc2l6ZTogMjBweDsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIGxpbmUtaGVpZ2h0OiAyOHB4OwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LXN1YmhlYWQ6IHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlOwoKICAgICAgICBmb250LXNpemU6IDE2cHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IDQwMDsKICAgICAgICBsaW5lLWhlaWdodDogMjRweDsKICAgICAgfTsKCiAgICAgIC0tcGFwZXItZm9udC1ib2R5MjogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CgogICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIGxpbmUtaGVpZ2h0OiAyNHB4OwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LWJvZHkxOiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKCiAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgICAgbGluZS1oZWlnaHQ6IDIwcHg7CiAgICAgIH07CgogICAgICAtLXBhcGVyLWZvbnQtY2FwdGlvbjogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tbm93cmFwOwoKICAgICAgICBmb250LXNpemU6IDEycHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IDQwMDsKICAgICAgICBsZXR0ZXItc3BhY2luZzogMC4wMTFlbTsKICAgICAgICBsaW5lLWhlaWdodDogMjBweDsKICAgICAgfTsKCiAgICAgIC0tcGFwZXItZm9udC1tZW51OiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1ub3dyYXA7CgogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIGxpbmUtaGVpZ2h0OiAyNHB4OwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LWJ1dHRvbjogewogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tbm93cmFwOwoKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IDUwMDsKICAgICAgICBsZXR0ZXItc3BhY2luZzogMC4wMThlbTsKICAgICAgICBsaW5lLWhlaWdodDogMjRweDsKICAgICAgICB0ZXh0LXRyYW5zZm9ybTogdXBwZXJjYXNlOwogICAgICB9OwoKICAgICAgLS1wYXBlci1mb250LWNvZGUyOiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tY29kZTsKCiAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIGZvbnQtd2VpZ2h0OiA3MDA7CiAgICAgICAgbGluZS1oZWlnaHQ6IDIwcHg7CiAgICAgIH07CgogICAgICAtLXBhcGVyLWZvbnQtY29kZTE6IHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1jb2RlOwoKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IDUwMDsKICAgICAgICBsaW5lLWhlaWdodDogMjBweDsKICAgICAgfTsKCiAgICB9CgogIDwvc3R5bGU+CjwvY3VzdG9tLXN0eWxlPmA7CiAgICB0ZW1wbGF0ZSRhLnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkYS5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIGNvbnN0ICRfZG9jdW1lbnRDb250YWluZXIgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwogICAgJF9kb2N1bWVudENvbnRhaW5lci5zZXRBdHRyaWJ1dGUoJ3N0eWxlJywgJ2Rpc3BsYXk6IG5vbmU7Jyk7CgogICAgJF9kb2N1bWVudENvbnRhaW5lci5pbm5lckhUTUwgPSBgPGRvbS1tb2R1bGUgaWQ9InBhcGVyLWRpYWxvZy1zaGFyZWQtc3R5bGVzIj4KICA8dGVtcGxhdGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBtYXJnaW46IDI0cHggNDBweDsKCiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tcGFwZXItZGlhbG9nLWJhY2tncm91bmQtY29sb3IsIHZhcigtLXByaW1hcnktYmFja2dyb3VuZC1jb2xvcikpOwogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1kaWFsb2ctY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWJvZHkxOwogICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tMTZkcDsKICAgICAgICBAYXBwbHkgLS1wYXBlci1kaWFsb2c7CiAgICAgIH0KCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKCopIHsKICAgICAgICBtYXJnaW4tdG9wOiAyMHB4OwogICAgICAgIHBhZGRpbmc6IDAgMjRweDsKICAgICAgfQoKICAgICAgOmhvc3QgPiA6OnNsb3R0ZWQoLm5vLXBhZGRpbmcpIHsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICB9CgogICAgICAKICAgICAgOmhvc3QgPiA6OnNsb3R0ZWQoKjpmaXJzdC1jaGlsZCkgewogICAgICAgIG1hcmdpbi10b3A6IDI0cHg7CiAgICAgIH0KCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKCo6bGFzdC1jaGlsZCkgewogICAgICAgIG1hcmdpbi1ib3R0b206IDI0cHg7CiAgICAgIH0KCiAgICAgIC8qIEluIDEueCwgdGhpcyBzZWxlY3RvciB3YXMgXGA6aG9zdCA+IDo6Y29udGVudCBoMlxgLiBJbiAyLnggPHNsb3Q+IGFsbG93cwogICAgICB0byBzZWxlY3QgZGlyZWN0IGNoaWxkcmVuIG9ubHksIHdoaWNoIGluY3JlYXNlcyB0aGUgd2VpZ2h0IG9mIHRoaXMKICAgICAgc2VsZWN0b3IsIHNvIHdlIGhhdmUgdG8gcmUtZGVmaW5lIGZpcnN0LWNoaWxkL2xhc3QtY2hpbGQgbWFyZ2lucyBiZWxvdy4gKi8KICAgICAgOmhvc3QgPiA6OnNsb3R0ZWQoaDIpIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgbWFyZ2luOiAwOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LXRpdGxlOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWRpYWxvZy10aXRsZTsKICAgICAgfQoKICAgICAgLyogQXBwbHkgbWl4aW4gYWdhaW4sIGluIGNhc2UgaXQgc2V0cyBtYXJnaW4tdG9wLiAqLwogICAgICA6aG9zdCA+IDo6c2xvdHRlZChoMjpmaXJzdC1jaGlsZCkgewogICAgICAgIG1hcmdpbi10b3A6IDI0cHg7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZGlhbG9nLXRpdGxlOwogICAgICB9CgogICAgICAvKiBBcHBseSBtaXhpbiBhZ2FpbiwgaW4gY2FzZSBpdCBzZXRzIG1hcmdpbi1ib3R0b20uICovCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKGgyOmxhc3QtY2hpbGQpIHsKICAgICAgICBtYXJnaW4tYm90dG9tOiAyNHB4OwogICAgICAgIEBhcHBseSAtLXBhcGVyLWRpYWxvZy10aXRsZTsKICAgICAgfQoKICAgICAgOmhvc3QgPiA6OnNsb3R0ZWQoLnBhcGVyLWRpYWxvZy1idXR0b25zKSwKICAgICAgOmhvc3QgPiA6OnNsb3R0ZWQoLmJ1dHRvbnMpIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgcGFkZGluZzogOHB4IDhweCA4cHggMjRweDsKICAgICAgICBtYXJnaW46IDA7CgogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1kaWFsb2ctYnV0dG9uLWNvbG9yLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CgogICAgICAgIEBhcHBseSAtLWxheW91dC1ob3Jpem9udGFsOwogICAgICAgIEBhcHBseSAtLWxheW91dC1lbmQtanVzdGlmaWVkOwogICAgICB9CiAgICA8L3N0eWxlPgogIDwvdGVtcGxhdGU+CjwvZG9tLW1vZHVsZT5gOwoKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoJF9kb2N1bWVudENvbnRhaW5lci5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIGBOZW9uQW5pbWF0YWJsZUJlaGF2aW9yYCBpcyBpbXBsZW1lbnRlZCBieSBlbGVtZW50cyBjb250YWluaW5nCiAgICAgKiBhbmltYXRpb25zIGZvciB1c2Ugd2l0aCBlbGVtZW50cyBpbXBsZW1lbnRpbmcKICAgICAqIGBOZW9uQW5pbWF0aW9uUnVubmVyQmVoYXZpb3JgLgogICAgICogQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBOZW9uQW5pbWF0YWJsZUJlaGF2aW9yID0gewoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBBbmltYXRpb24gY29uZmlndXJhdGlvbi4gU2VlIFJFQURNRSBmb3IgbW9yZSBpbmZvLgogICAgICAgICAqLwogICAgICAgIGFuaW1hdGlvbkNvbmZpZzoge3R5cGU6IE9iamVjdH0sCgogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlbmllbmNlIHByb3BlcnR5IGZvciBzZXR0aW5nIGFuICdlbnRyeScgYW5pbWF0aW9uLiBEbyBub3Qgc2V0CiAgICAgICAgICogYGFuaW1hdGlvbkNvbmZpZy5lbnRyeWAgbWFudWFsbHkgaWYgdXNpbmcgdGhpcy4gVGhlIGFuaW1hdGVkIG5vZGUgaXMgc2V0CiAgICAgICAgICogdG8gYHRoaXNgIGlmIHVzaW5nIHRoaXMgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgZW50cnlBbmltYXRpb246IHsKICAgICAgICAgIG9ic2VydmVyOiAnX2VudHJ5QW5pbWF0aW9uQ2hhbmdlZCcsCiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udmVuaWVuY2UgcHJvcGVydHkgZm9yIHNldHRpbmcgYW4gJ2V4aXQnIGFuaW1hdGlvbi4gRG8gbm90IHNldAogICAgICAgICAqIGBhbmltYXRpb25Db25maWcuZXhpdGAgbWFudWFsbHkgaWYgdXNpbmcgdGhpcy4gVGhlIGFuaW1hdGVkIG5vZGUgaXMgc2V0CiAgICAgICAgICogdG8gYHRoaXNgIGlmIHVzaW5nIHRoaXMgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgZXhpdEFuaW1hdGlvbjogewogICAgICAgICAgb2JzZXJ2ZXI6ICdfZXhpdEFuaW1hdGlvbkNoYW5nZWQnLAogICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0sCgogICAgICB9LAoKICAgICAgX2VudHJ5QW5pbWF0aW9uQ2hhbmdlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5hbmltYXRpb25Db25maWcgPSB0aGlzLmFuaW1hdGlvbkNvbmZpZyB8fCB7fTsKICAgICAgICB0aGlzLmFuaW1hdGlvbkNvbmZpZ1snZW50cnknXSA9IFt7bmFtZTogdGhpcy5lbnRyeUFuaW1hdGlvbiwgbm9kZTogdGhpc31dOwogICAgICB9LAoKICAgICAgX2V4aXRBbmltYXRpb25DaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmFuaW1hdGlvbkNvbmZpZyA9IHRoaXMuYW5pbWF0aW9uQ29uZmlnIHx8IHt9OwogICAgICAgIHRoaXMuYW5pbWF0aW9uQ29uZmlnWydleGl0J10gPSBbe25hbWU6IHRoaXMuZXhpdEFuaW1hdGlvbiwgbm9kZTogdGhpc31dOwogICAgICB9LAoKICAgICAgX2NvcHlQcm9wZXJ0aWVzOiBmdW5jdGlvbihjb25maWcxLCBjb25maWcyKSB7CiAgICAgICAgLy8gc2hhbGxvd2x5IGNvcHkgcHJvcGVydGllcyBmcm9tIGNvbmZpZzIgdG8gY29uZmlnMQogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIGNvbmZpZzIpIHsKICAgICAgICAgIGNvbmZpZzFbcHJvcGVydHldID0gY29uZmlnMltwcm9wZXJ0eV07CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2Nsb25lQ29uZmlnOiBmdW5jdGlvbihjb25maWcpIHsKICAgICAgICB2YXIgY2xvbmUgPSB7aXNDbG9uZTogdHJ1ZX07CiAgICAgICAgdGhpcy5fY29weVByb3BlcnRpZXMoY2xvbmUsIGNvbmZpZyk7CiAgICAgICAgcmV0dXJuIGNsb25lOwogICAgICB9LAoKICAgICAgX2dldEFuaW1hdGlvbkNvbmZpZ1JlY3Vyc2l2ZTogZnVuY3Rpb24odHlwZSwgbWFwLCBhbGxDb25maWdzKSB7CiAgICAgICAgaWYgKCF0aGlzLmFuaW1hdGlvbkNvbmZpZykgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuYW5pbWF0aW9uQ29uZmlnLnZhbHVlICYmCiAgICAgICAgICAgIHR5cGVvZiB0aGlzLmFuaW1hdGlvbkNvbmZpZy52YWx1ZSA9PT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgdGhpcy5fd2Fybih0aGlzLl9sb2dmKAogICAgICAgICAgICAgICdwbGF5QW5pbWF0aW9uJywKICAgICAgICAgICAgICAnUGxlYXNlIHB1dCBcJ2FuaW1hdGlvbkNvbmZpZ1wnIGluc2lkZSBvZiB5b3VyIGNvbXBvbmVudHMgXCdwcm9wZXJ0aWVzXCcgb2JqZWN0IGluc3RlYWQgb2Ygb3V0c2lkZSBvZiBpdC4nKSk7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyB0eXBlIGlzIG9wdGlvbmFsCiAgICAgICAgdmFyIHRoaXNDb25maWc7CiAgICAgICAgaWYgKHR5cGUpIHsKICAgICAgICAgIHRoaXNDb25maWcgPSB0aGlzLmFuaW1hdGlvbkNvbmZpZ1t0eXBlXTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpc0NvbmZpZyA9IHRoaXMuYW5pbWF0aW9uQ29uZmlnOwogICAgICAgIH0KCiAgICAgICAgaWYgKCFBcnJheS5pc0FycmF5KHRoaXNDb25maWcpKSB7CiAgICAgICAgICB0aGlzQ29uZmlnID0gW3RoaXNDb25maWddOwogICAgICAgIH0KCiAgICAgICAgLy8gaXRlcmF0ZSBhbmltYXRpb25zIGFuZCByZWN1cnNlIHRvIHByb2Nlc3MgY29uZmlndXJhdGlvbnMgZnJvbSBjaGlsZCBub2RlcwogICAgICAgIGlmICh0aGlzQ29uZmlnKSB7CiAgICAgICAgICBmb3IgKHZhciBjb25maWcsIGluZGV4ID0gMDsgY29uZmlnID0gdGhpc0NvbmZpZ1tpbmRleF07IGluZGV4KyspIHsKICAgICAgICAgICAgaWYgKGNvbmZpZy5hbmltYXRhYmxlKSB7CiAgICAgICAgICAgICAgY29uZmlnLmFuaW1hdGFibGUuX2dldEFuaW1hdGlvbkNvbmZpZ1JlY3Vyc2l2ZSgKICAgICAgICAgICAgICAgICAgY29uZmlnLnR5cGUgfHwgdHlwZSwgbWFwLCBhbGxDb25maWdzKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpZiAoY29uZmlnLmlkKSB7CiAgICAgICAgICAgICAgICB2YXIgY2FjaGVkQ29uZmlnID0gbWFwW2NvbmZpZy5pZF07CiAgICAgICAgICAgICAgICBpZiAoY2FjaGVkQ29uZmlnKSB7CiAgICAgICAgICAgICAgICAgIC8vIG1lcmdlIGNvbmZpZ3VyYXRpb25zIHdpdGggdGhlIHNhbWUgaWQsIG1ha2luZyBhIGNsb25lIGxhemlseQogICAgICAgICAgICAgICAgICBpZiAoIWNhY2hlZENvbmZpZy5pc0Nsb25lKSB7CiAgICAgICAgICAgICAgICAgICAgbWFwW2NvbmZpZy5pZF0gPSB0aGlzLl9jbG9uZUNvbmZpZyhjYWNoZWRDb25maWcpOwogICAgICAgICAgICAgICAgICAgIGNhY2hlZENvbmZpZyA9IG1hcFtjb25maWcuaWRdOwogICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgIHRoaXMuX2NvcHlQcm9wZXJ0aWVzKGNhY2hlZENvbmZpZywgY29uZmlnKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgIC8vIHB1dCBhbnkgY29uZmlncyB3aXRoIGFuIGlkIGludG8gYSBtYXAKICAgICAgICAgICAgICAgICAgbWFwW2NvbmZpZy5pZF0gPSBjb25maWc7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIGFsbENvbmZpZ3MucHVzaChjb25maWcpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBbiBlbGVtZW50IGltcGxlbWVudGluZyBgTmVvbkFuaW1hdGlvblJ1bm5lckJlaGF2aW9yYCBjYWxscyB0aGlzCiAgICAgICAqIG1ldGhvZCB0byBjb25maWd1cmUgYW4gYW5pbWF0aW9uIHdpdGggYW4gb3B0aW9uYWwgdHlwZS4gRWxlbWVudHMKICAgICAgICogaW1wbGVtZW50aW5nIGBOZW9uQW5pbWF0YWJsZUJlaGF2aW9yYCBzaG91bGQgZGVmaW5lIHRoZSBwcm9wZXJ0eQogICAgICAgKiBgYW5pbWF0aW9uQ29uZmlnYCwgd2hpY2ggaXMgZWl0aGVyIGEgY29uZmlndXJhdGlvbiBvYmplY3Qgb3IgYSBtYXAgb2YKICAgICAgICogYW5pbWF0aW9uIHR5cGUgdG8gYXJyYXkgb2YgY29uZmlndXJhdGlvbiBvYmplY3RzLgogICAgICAgKi8KICAgICAgZ2V0QW5pbWF0aW9uQ29uZmlnOiBmdW5jdGlvbih0eXBlKSB7CiAgICAgICAgdmFyIG1hcCA9IHt9OwogICAgICAgIHZhciBhbGxDb25maWdzID0gW107CiAgICAgICAgdGhpcy5fZ2V0QW5pbWF0aW9uQ29uZmlnUmVjdXJzaXZlKHR5cGUsIG1hcCwgYWxsQ29uZmlncyk7CiAgICAgICAgLy8gYXBwZW5kIHRoZSBjb25maWd1cmF0aW9ucyBzYXZlZCBpbiB0aGUgbWFwIHRvIHRoZSBhcnJheQogICAgICAgIGZvciAodmFyIGtleSBpbiBtYXApIHsKICAgICAgICAgIGFsbENvbmZpZ3MucHVzaChtYXBba2V5XSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBhbGxDb25maWdzOwogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIGBOZW9uQW5pbWF0aW9uUnVubmVyQmVoYXZpb3JgIGFkZHMgYSBtZXRob2QgdG8gcnVuIGFuaW1hdGlvbnMuCiAgICAgKgogICAgICogQHBvbHltZXJCZWhhdmlvciBOZW9uQW5pbWF0aW9uUnVubmVyQmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgTmVvbkFuaW1hdGlvblJ1bm5lckJlaGF2aW9ySW1wbCA9IHsKCiAgICAgIF9jb25maWd1cmVBbmltYXRpb25zOiBmdW5jdGlvbihjb25maWdzKSB7CiAgICAgICAgdmFyIHJlc3VsdHMgPSBbXTsKICAgICAgICB2YXIgcmVzdWx0c1RvUGxheSA9IFtdOwoKICAgICAgICBpZiAoY29uZmlncy5sZW5ndGggPiAwKSB7CiAgICAgICAgICBmb3IgKGxldCBjb25maWcsIGluZGV4ID0gMDsgY29uZmlnID0gY29uZmlnc1tpbmRleF07IGluZGV4KyspIHsKICAgICAgICAgICAgbGV0IG5lb25BbmltYXRpb24gPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KGNvbmZpZy5uYW1lKTsKICAgICAgICAgICAgLy8gaXMgdGhpcyBlbGVtZW50IGFjdHVhbGx5IGEgbmVvbiBhbmltYXRpb24/CiAgICAgICAgICAgIGlmIChuZW9uQW5pbWF0aW9uLmlzTmVvbkFuaW1hdGlvbikgewogICAgICAgICAgICAgIGxldCByZXN1bHQgPSBudWxsOwogICAgICAgICAgICAgIC8vIENsb3N1cmUgY29tcGlsZXIgZG9lcyBub3Qgd29yayB3ZWxsIHdpdGggYSB0cnkgLyBjYXRjaCBoZXJlLgogICAgICAgICAgICAgIC8vIC5jb25maWd1cmUgbmVlZHMgdG8gYmUgZXhwbGljaXRseSBkZWZpbmVkCiAgICAgICAgICAgICAgaWYgKCFuZW9uQW5pbWF0aW9uLmNvbmZpZ3VyZSkgewogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBAcGFyYW0ge09iamVjdH0gY29uZmlnCiAgICAgICAgICAgICAgICAgKiBAcmV0dXJuIHtBbmltYXRpb25FZmZlY3RSZWFkT25seX0KICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgbmVvbkFuaW1hdGlvbi5jb25maWd1cmUgPSBmdW5jdGlvbihjb25maWcpIHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgcmVzdWx0ID0gbmVvbkFuaW1hdGlvbi5jb25maWd1cmUoY29uZmlnKTsKICAgICAgICAgICAgICByZXN1bHRzVG9QbGF5LnB1c2goewogICAgICAgICAgICAgICAgcmVzdWx0OiByZXN1bHQsCiAgICAgICAgICAgICAgICBjb25maWc6IGNvbmZpZywKICAgICAgICAgICAgICAgIG5lb25BbmltYXRpb246IG5lb25BbmltYXRpb24sCiAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgY29uc29sZS53YXJuKHRoaXMuaXMgKyAnOicsIGNvbmZpZy5uYW1lLCAnbm90IGZvdW5kIScpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHJlc3VsdHNUb1BsYXkubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGxldCByZXN1bHQgPSByZXN1bHRzVG9QbGF5W2ldLnJlc3VsdDsKICAgICAgICAgIGxldCBjb25maWcgPSByZXN1bHRzVG9QbGF5W2ldLmNvbmZpZzsKICAgICAgICAgIGxldCBuZW9uQW5pbWF0aW9uID0gcmVzdWx0c1RvUGxheVtpXS5uZW9uQW5pbWF0aW9uOwogICAgICAgICAgLy8gY29uZmlndXJhdGlvbiBvciBwbGF5IGNvdWxkIGZhaWwgaWYgcG9seWZpbGxzIGFyZW4ndCBsb2FkZWQKICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgIC8vIENoZWNrIGlmIHdlIGhhdmUgYW4gRWZmZWN0IHJhdGhlciB0aGFuIGFuIEFuaW1hdGlvbgogICAgICAgICAgICBpZiAodHlwZW9mIHJlc3VsdC5jYW5jZWwgIT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICAgIHJlc3VsdCA9IGRvY3VtZW50LnRpbWVsaW5lLnBsYXkocmVzdWx0KTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgICByZXN1bHQgPSBudWxsOwogICAgICAgICAgICBjb25zb2xlLndhcm4oJ0NvdWxkbnQgcGxheScsICcoJywgY29uZmlnLm5hbWUsICcpLicsIGUpOwogICAgICAgICAgfQoKICAgICAgICAgIGlmIChyZXN1bHQpIHsKICAgICAgICAgICAgcmVzdWx0cy5wdXNoKHsKICAgICAgICAgICAgICBuZW9uQW5pbWF0aW9uOiBuZW9uQW5pbWF0aW9uLAogICAgICAgICAgICAgIGNvbmZpZzogY29uZmlnLAogICAgICAgICAgICAgIGFuaW1hdGlvbjogcmVzdWx0LAogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHJldHVybiByZXN1bHRzOwogICAgICB9LAoKICAgICAgX3Nob3VsZENvbXBsZXRlOiBmdW5jdGlvbihhY3RpdmVFbnRyaWVzKSB7CiAgICAgICAgdmFyIGZpbmlzaGVkID0gdHJ1ZTsKICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGFjdGl2ZUVudHJpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGlmIChhY3RpdmVFbnRyaWVzW2ldLmFuaW1hdGlvbi5wbGF5U3RhdGUgIT0gJ2ZpbmlzaGVkJykgewogICAgICAgICAgICBmaW5pc2hlZCA9IGZhbHNlOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGZpbmlzaGVkOwogICAgICB9LAoKICAgICAgX2NvbXBsZXRlOiBmdW5jdGlvbihhY3RpdmVFbnRyaWVzKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBhY3RpdmVFbnRyaWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBhY3RpdmVFbnRyaWVzW2ldLm5lb25BbmltYXRpb24uY29tcGxldGUoYWN0aXZlRW50cmllc1tpXS5jb25maWcpOwogICAgICAgIH0KICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGFjdGl2ZUVudHJpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgIGFjdGl2ZUVudHJpZXNbaV0uYW5pbWF0aW9uLmNhbmNlbCgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBQbGF5cyBhbiBhbmltYXRpb24gd2l0aCBhbiBvcHRpb25hbCBgdHlwZWAuCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nPX0gdHlwZQogICAgICAgKiBAcGFyYW0geyFPYmplY3Q9fSBjb29raWUKICAgICAgICovCiAgICAgIHBsYXlBbmltYXRpb246IGZ1bmN0aW9uKHR5cGUsIGNvb2tpZSkgewogICAgICAgIHZhciBjb25maWdzID0gdGhpcy5nZXRBbmltYXRpb25Db25maWcodHlwZSk7CiAgICAgICAgaWYgKCFjb25maWdzKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuX2FjdGl2ZSA9IHRoaXMuX2FjdGl2ZSB8fCB7fTsKICAgICAgICBpZiAodGhpcy5fYWN0aXZlW3R5cGVdKSB7CiAgICAgICAgICB0aGlzLl9jb21wbGV0ZSh0aGlzLl9hY3RpdmVbdHlwZV0pOwogICAgICAgICAgZGVsZXRlIHRoaXMuX2FjdGl2ZVt0eXBlXTsKICAgICAgICB9CgogICAgICAgIHZhciBhY3RpdmVFbnRyaWVzID0gdGhpcy5fY29uZmlndXJlQW5pbWF0aW9ucyhjb25maWdzKTsKCiAgICAgICAgaWYgKGFjdGl2ZUVudHJpZXMubGVuZ3RoID09IDApIHsKICAgICAgICAgIHRoaXMuZmlyZSgnbmVvbi1hbmltYXRpb24tZmluaXNoJywgY29va2llLCB7YnViYmxlczogZmFsc2V9KTsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2FjdGl2ZVt0eXBlXSA9IGFjdGl2ZUVudHJpZXM7CgogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgYWN0aXZlRW50cmllcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgYWN0aXZlRW50cmllc1tpXS5hbmltYXRpb24ub25maW5pc2ggPSBmdW5jdGlvbigpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX3Nob3VsZENvbXBsZXRlKGFjdGl2ZUVudHJpZXMpKSB7CiAgICAgICAgICAgICAgdGhpcy5fY29tcGxldGUoYWN0aXZlRW50cmllcyk7CiAgICAgICAgICAgICAgZGVsZXRlIHRoaXMuX2FjdGl2ZVt0eXBlXTsKICAgICAgICAgICAgICB0aGlzLmZpcmUoJ25lb24tYW5pbWF0aW9uLWZpbmlzaCcsIGNvb2tpZSwge2J1YmJsZXM6IGZhbHNlfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0uYmluZCh0aGlzKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FuY2VscyB0aGUgY3VycmVudGx5IHJ1bm5pbmcgYW5pbWF0aW9ucy4KICAgICAgICovCiAgICAgIGNhbmNlbEFuaW1hdGlvbjogZnVuY3Rpb24oKSB7CiAgICAgICAgZm9yICh2YXIgayBpbiB0aGlzLl9hY3RpdmUpIHsKICAgICAgICAgIHZhciBlbnRyaWVzID0gdGhpcy5fYWN0aXZlW2tdOwoKICAgICAgICAgICAgICAgICAgICAgICAgZm9yICh2YXIgaiBpbiBlbnRyaWVzKSB7CiAgICAgICAgICAgIGVudHJpZXNbal0uYW5pbWF0aW9uLmNhbmNlbCgpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5fYWN0aXZlID0ge307CiAgICAgIH0KICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IE5lb25BbmltYXRpb25SdW5uZXJCZWhhdmlvciA9CiAgICAgICAgW05lb25BbmltYXRhYmxlQmVoYXZpb3IsIE5lb25BbmltYXRpb25SdW5uZXJCZWhhdmlvckltcGxdOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgTWF0ZXJpYWwgZGVzaWduOgogICAgW0RpYWxvZ3NdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9kaWFsb2dzLmh0bWwpCgogICAgYDxwYXBlci1kaWFsb2c+YCBpcyBhIGRpYWxvZyB3aXRoIE1hdGVyaWFsIERlc2lnbiBzdHlsaW5nIGFuZCBvcHRpb25hbAogICAgYW5pbWF0aW9ucyB3aGVuIGl0IGlzIG9wZW5lZCBvciBjbG9zZWQuIEl0IHByb3ZpZGVzIHN0eWxlcyBmb3IgYSBoZWFkZXIsIGNvbnRlbnQKICAgIGFyZWEsIGFuZCBhbiBhY3Rpb24gYXJlYSBmb3IgYnV0dG9ucy4gWW91IGNhbiB1c2UgdGhlCiAgICBgPHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlPmAgZWxlbWVudCAoaW4gaXRzIG93biByZXBvc2l0b3J5KSBpZiB5b3UgbmVlZCBhCiAgICBzY3JvbGxpbmcgY29udGVudCBhcmVhLiBUbyBhdXRvZm9jdXMgYSBzcGVjaWZpYyBjaGlsZCBlbGVtZW50IGFmdGVyIG9wZW5pbmcgdGhlCiAgICBkaWFsb2csIGdpdmUgaXQgdGhlIGBhdXRvZm9jdXNgIGF0dHJpYnV0ZS4gU2VlIGBQb2x5bWVyLlBhcGVyRGlhbG9nQmVoYXZpb3JgIGFuZAogICAgYFBvbHltZXIuSXJvbk92ZXJsYXlCZWhhdmlvcmAgZm9yIHNwZWNpZmljcy4KCiAgICBGb3IgZXhhbXBsZSwgdGhlIGZvbGxvd2luZyBjb2RlIGltcGxlbWVudHMgYSBkaWFsb2cgd2l0aCBhIGhlYWRlciwgc2Nyb2xsaW5nCiAgICBjb250ZW50IGFyZWEgYW5kIGJ1dHRvbnMuIEZvY3VzIHdpbGwgYmUgZ2l2ZW4gdG8gdGhlIGBkaWFsb2ctY29uZmlybWAgYnV0dG9uCiAgICB3aGVuIHRoZSBkaWFsb2cgaXMgb3BlbmVkLgoKICAgICAgICA8cGFwZXItZGlhbG9nPgogICAgICAgICAgPGgyPkhlYWRlcjwvaDI+CiAgICAgICAgICA8cGFwZXItZGlhbG9nLXNjcm9sbGFibGU+CiAgICAgICAgICAgIExvcmVtIGlwc3VtLi4uCiAgICAgICAgICA8L3BhcGVyLWRpYWxvZy1zY3JvbGxhYmxlPgogICAgICAgICAgPGRpdiBjbGFzcz0iYnV0dG9ucyI+CiAgICAgICAgICAgIDxwYXBlci1idXR0b24gZGlhbG9nLWRpc21pc3M+Q2FuY2VsPC9wYXBlci1idXR0b24+CiAgICAgICAgICAgIDxwYXBlci1idXR0b24gZGlhbG9nLWNvbmZpcm0gYXV0b2ZvY3VzPkFjY2VwdDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC9wYXBlci1kaWFsb2c+CgogICAgIyMjIFN0eWxpbmcKCiAgICBTZWUgdGhlIGRvY3MgZm9yIGBQb2x5bWVyLlBhcGVyRGlhbG9nQmVoYXZpb3JgIGZvciB0aGUgY3VzdG9tIHByb3BlcnRpZXMKICAgIGF2YWlsYWJsZSBmb3Igc3R5bGluZyB0aGlzIGVsZW1lbnQuCgogICAgIyMjIEFuaW1hdGlvbnMKCiAgICBTZXQgdGhlIGBlbnRyeS1hbmltYXRpb25gIGFuZC9vciBgZXhpdC1hbmltYXRpb25gIGF0dHJpYnV0ZXMgdG8gYWRkIGFuIGFuaW1hdGlvbgogICAgd2hlbiB0aGUgZGlhbG9nIGlzIG9wZW5lZCBvciBjbG9zZWQuIFNlZSB0aGUgZG9jdW1lbnRhdGlvbiBpbgogICAgW1BvbHltZXJFbGVtZW50cy9uZW9uLWFuaW1hdGlvbl0oaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9uZW9uLWFuaW1hdGlvbikKICAgIGZvciBtb3JlIGluZm8uCgogICAgRm9yIGV4YW1wbGU6CgogICAgICAgIDxzY3JpcHQgdHlwZT0ibW9kdWxlIj4KICAgICAgICAgIGltcG9ydCAnQHBvbHltZXIvbmVvbi1hbmltYXRpb24vYW5pbWF0aW9ucy9mYWRlLW91dC1hbmltYXRpb24uanMnOwogICAgICAgICAgaW1wb3J0ICdAcG9seW1lci9uZW9uLWFuaW1hdGlvbi9hbmltYXRpb25zL3NjYWxlLXVwLWFuaW1hdGlvbi5qcyc7CiAgICAgICAgPC9KQVZBX1NDUklJSUlQVC8+CgogICAgICAgIDxwYXBlci1kaWFsb2cgZW50cnktYW5pbWF0aW9uPSJzY2FsZS11cC1hbmltYXRpb24iCiAgICAgICAgICAgICAgICAgICAgICBleGl0LWFuaW1hdGlvbj0iZmFkZS1vdXQtYW5pbWF0aW9uIj4KICAgICAgICAgIDxoMj5IZWFkZXI8L2gyPgogICAgICAgICAgPGRpdj5EaWFsb2cgYm9keTwvZGl2PgogICAgICAgIDwvcGFwZXItZGlhbG9nPgoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgU2VlIHRoZSBkb2NzIGZvciBgUG9seW1lci5QYXBlckRpYWxvZ0JlaGF2aW9yYCBmb3IgYWNjZXNzaWJpbGl0eSBmZWF0dXJlcwogICAgaW1wbGVtZW50ZWQgYnkgdGhpcyBlbGVtZW50LgoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItZGlhbG9nCiAgICBAaGVybyBoZXJvLnN2ZwogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZSBpbmNsdWRlPSJwYXBlci1kaWFsb2ctc2hhcmVkLXN0eWxlcyI+PC9zdHlsZT4KICAgIDxzbG90Pjwvc2xvdD4KYCwKCiAgICAgIGlzOiAncGFwZXItZGlhbG9nJywKICAgICAgYmVoYXZpb3JzOiBbUGFwZXJEaWFsb2dCZWhhdmlvciwgTmVvbkFuaW1hdGlvblJ1bm5lckJlaGF2aW9yXSwKICAgICAgbGlzdGVuZXJzOiB7J25lb24tYW5pbWF0aW9uLWZpbmlzaCc6ICdfb25OZW9uQW5pbWF0aW9uRmluaXNoJ30sCgogICAgICBfcmVuZGVyT3BlbmVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmNhbmNlbEFuaW1hdGlvbigpOwogICAgICAgIHRoaXMucGxheUFuaW1hdGlvbignZW50cnknKTsKICAgICAgfSwKCiAgICAgIF9yZW5kZXJDbG9zZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuY2FuY2VsQW5pbWF0aW9uKCk7CiAgICAgICAgdGhpcy5wbGF5QW5pbWF0aW9uKCdleGl0Jyk7CiAgICAgIH0sCgogICAgICBfb25OZW9uQW5pbWF0aW9uRmluaXNoOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5vcGVuZWQpIHsKICAgICAgICAgIHRoaXMuX2ZpbmlzaFJlbmRlck9wZW5lZCgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9maW5pc2hSZW5kZXJDbG9zZWQoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgYGlyb24tYTExeS1hbm5vdW5jZXJgIGlzIGEgc2luZ2xldG9uIGVsZW1lbnQgdGhhdCBpcyBpbnRlbmRlZCB0byBhZGQgYTExeQogICAgdG8gZmVhdHVyZXMgdGhhdCByZXF1aXJlIG9uLWRlbWFuZCBhbm5vdW5jZW1lbnQgZnJvbSBzY3JlZW4gcmVhZGVycy4gSW4KICAgIG9yZGVyIHRvIG1ha2UgdXNlIG9mIHRoZSBhbm5vdW5jZXIsIGl0IGlzIGJlc3QgdG8gcmVxdWVzdCBpdHMgYXZhaWxhYmlsaXR5CiAgICBpbiB0aGUgYW5ub3VuY2luZyBlbGVtZW50LgoKICAgIEV4YW1wbGU6CgogICAgICAgIFBvbHltZXIoewoKICAgICAgICAgIGlzOiAneC1jaGF0dHknLAoKICAgICAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgLy8gVGhpcyB3aWxsIGNyZWF0ZSB0aGUgc2luZ2xldG9uIGVsZW1lbnQgaWYgaXQgaGFzIG5vdAogICAgICAgICAgICAvLyBiZWVuIGNyZWF0ZWQgeWV0OgogICAgICAgICAgICBQb2x5bWVyLklyb25BMTF5QW5ub3VuY2VyLnJlcXVlc3RBdmFpbGFiaWxpdHkoKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICBBZnRlciB0aGUgYGlyb24tYTExeS1hbm5vdW5jZXJgIGhhcyBiZWVuIG1hZGUgYXZhaWxhYmxlLCBlbGVtZW50cyBjYW4KICAgIG1ha2UgYW5ub3VuY2VzIGJ5IGZpcmluZyBidWJibGluZyBgaXJvbi1hbm5vdW5jZWAgZXZlbnRzLgoKICAgIEV4YW1wbGU6CgogICAgICAgIHRoaXMuZmlyZSgnaXJvbi1hbm5vdW5jZScsIHsKICAgICAgICAgIHRleHQ6ICdUaGlzIGlzIGFuIGFubm91bmNlbWVudCEnCiAgICAgICAgfSwgeyBidWJibGVzOiB0cnVlIH0pOwoKICAgIE5vdGU6IGFubm91bmNlbWVudHMgYXJlIG9ubHkgYXVkaWJsZSBpZiB5b3UgaGF2ZSBhIHNjcmVlbiByZWFkZXIgZW5hYmxlZC4KCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBjb25zdCBJcm9uQTExeUFubm91bmNlciA9IFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICAgICAgY2xpcDogcmVjdCgwcHgsMHB4LDBweCwwcHgpOwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPGRpdiBhcmlhLWxpdmUkPSJbW21vZGVdXSI+W1tfdGV4dF1dPC9kaXY+CmAsCgogICAgICBpczogJ2lyb24tYTExeS1hbm5vdW5jZXInLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgdmFsdWUgb2YgbW9kZSBpcyB1c2VkIHRvIHNldCB0aGUgYGFyaWEtbGl2ZWAgYXR0cmlidXRlCiAgICAgICAgICogZm9yIHRoZSBlbGVtZW50IHRoYXQgd2lsbCBiZSBhbm5vdW5jZWQuIFZhbGlkIHZhbHVlcyBhcmU6IGBvZmZgLAogICAgICAgICAqIGBwb2xpdGVgIGFuZCBgYXNzZXJ0aXZlYC4KICAgICAgICAgKi8KICAgICAgICBtb2RlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ3BvbGl0ZSd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgdGltZW91dCBvbiByZWZyZXNoaW5nIHRoZSBhbm5vdW5jZW1lbnQgdGV4dC4gTGFyZ2VyIHRpbWVvdXRzIGFyZQogICAgICAgICAqIG5lZWRlZCBmb3IgY2VydGFpbiBzY3JlZW4gcmVhZGVycyB0byByZS1hbm5vdW5jZSB0aGUgc2FtZSBtZXNzYWdlLgogICAgICAgICAqLwogICAgICAgIHRpbWVvdXQ6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAxNTB9LAoKICAgICAgICBfdGV4dDoge3R5cGU6IFN0cmluZywgdmFsdWU6ICcnfSwKICAgICAgfSwKCiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgY3JlYXRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCFJcm9uQTExeUFubm91bmNlci5pbnN0YW5jZSkgewogICAgICAgICAgSXJvbkExMXlBbm5vdW5jZXIuaW5zdGFuY2UgPSB0aGlzOwogICAgICAgIH0KCiAgICAgICAgZG9jdW1lbnQuYWRkRXZlbnRMaXN0ZW5lcignaXJvbi1hbm5vdW5jZScsIHRoaXMuX29uSXJvbkFubm91bmNlLmJpbmQodGhpcykpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhdXNlIGEgdGV4dCBzdHJpbmcgdG8gYmUgYW5ub3VuY2VkIGJ5IHNjcmVlbiByZWFkZXJzLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGV4dCBUaGUgdGV4dCB0aGF0IHNob3VsZCBiZSBhbm5vdW5jZWQuCiAgICAgICAqLwogICAgICBhbm5vdW5jZTogZnVuY3Rpb24odGV4dCkgewogICAgICAgIHRoaXMuX3RleHQgPSAnJzsKICAgICAgICB0aGlzLmFzeW5jKGZ1bmN0aW9uKCkgewogICAgICAgICAgdGhpcy5fdGV4dCA9IHRleHQ7CiAgICAgICAgfSwgdGhpcy50aW1lb3V0KTsKICAgICAgfSwKCiAgICAgIF9vbklyb25Bbm5vdW5jZTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoZXZlbnQuZGV0YWlsICYmIGV2ZW50LmRldGFpbC50ZXh0KSB7CiAgICAgICAgICB0aGlzLmFubm91bmNlKGV2ZW50LmRldGFpbC50ZXh0KTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIElyb25BMTF5QW5ub3VuY2VyLmluc3RhbmNlID0gbnVsbDsKCiAgICBJcm9uQTExeUFubm91bmNlci5yZXF1ZXN0QXZhaWxhYmlsaXR5ID0gZnVuY3Rpb24oKSB7CiAgICAgIGlmICghSXJvbkExMXlBbm5vdW5jZXIuaW5zdGFuY2UpIHsKICAgICAgICBJcm9uQTExeUFubm91bmNlci5pbnN0YW5jZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2lyb24tYTExeS1hbm5vdW5jZXInKTsKICAgICAgfQoKICAgICAgaWYgKGRvY3VtZW50LmJvZHkpIHsKICAgICAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKElyb25BMTF5QW5ub3VuY2VyLmluc3RhbmNlKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBkb2N1bWVudC5hZGRFdmVudExpc3RlbmVyKCdsb2FkJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKElyb25BMTF5QW5ub3VuY2VyLmluc3RhbmNlKTsKICAgICAgICB9KTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgIGA8aXJvbi1pbnB1dD5gIGlzIGEgd3JhcHBlciB0byBhIG5hdGl2ZSBgPGlucHV0PmAgZWxlbWVudCwgdGhhdCBhZGRzIHR3by13YXkKICAgIGJpbmRpbmcgYW5kIHByZXZlbnRpb24gb2YgaW52YWxpZCBpbnB1dC4gVG8gdXNlIGl0LCB5b3UgbXVzdCBkaXN0cmlidXRlIGEgbmF0aXZlCiAgICBgPGlucHV0PmAgeW91cnNlbGYuIFlvdSBjYW4gY29udGludWUgdG8gdXNlIHRoZSBuYXRpdmUgYGlucHV0YCBhcyB5b3Ugd291bGQKICAgIG5vcm1hbGx5OgoKICAgICAgICA8aXJvbi1pbnB1dD4KICAgICAgICAgIDxpbnB1dD4KICAgICAgICA8L2lyb24taW5wdXQ+CgogICAgICAgIDxpcm9uLWlucHV0PgogICAgICAgICAgPGlucHV0IHR5cGU9ImVtYWlsIiBkaXNhYmxlZD4KICAgICAgICA8L2lyb24taW5wdXQ+CgogICAgIyMjIFR3by13YXkgYmluZGluZwoKICAgIEJ5IGRlZmF1bHQgeW91IGNhbiBvbmx5IGdldCBub3RpZmllZCBvZiBjaGFuZ2VzIHRvIGEgbmF0aXZlIGA8aW5wdXQ+YCdzIGB2YWx1ZWAKICAgIGR1ZSB0byB1c2VyIGlucHV0OgoKICAgICAgICA8aW5wdXQgdmFsdWU9Int7bXlWYWx1ZTo6aW5wdXR9fSI+CgogICAgVGhpcyBtZWFucyB0aGF0IGlmIHlvdSBpbXBlcmF0aXZlbHkgc2V0IHRoZSB2YWx1ZSAoaS5lLiBgc29tZU5hdGl2ZUlucHV0LnZhbHVlID0KICAgICdmb28nYCksIG5vIGV2ZW50cyB3aWxsIGJlIGZpcmVkIGFuZCB0aGlzIGNoYW5nZSBjYW5ub3QgYmUgb2JzZXJ2ZWQuCgogICAgYGlyb24taW5wdXRgIGFkZHMgdGhlIGBiaW5kLXZhbHVlYCBwcm9wZXJ0eSB0aGF0IG1pcnJvcnMgdGhlIG5hdGl2ZSBgaW5wdXRgJ3MKICAgICdgdmFsdWVgIHByb3BlcnR5OyB0aGlzIHByb3BlcnR5IGNhbiBiZSB1c2VkIGZvciB0d28td2F5IGRhdGEgYmluZGluZy4KICAgIGBiaW5kLXZhbHVlYCB3aWxsIG5vdGlmeSBpZiBpdCBpcyBjaGFuZ2VkIGVpdGhlciBieSB1c2VyIGlucHV0IG9yIGJ5IHNjcmlwdC4KCiAgICAgICAgPGlyb24taW5wdXQgYmluZC12YWx1ZT0ie3tteVZhbHVlfX0iPgogICAgICAgICAgPGlucHV0PgogICAgICAgIDwvaXJvbi1pbnB1dD4KCiAgICBOb3RlOiB0aGlzIG1lYW5zIHRoYXQgaWYgeW91IHdhbnQgdG8gaW1wZXJhdGl2ZWx5IHNldCB0aGUgbmF0aXZlIGBpbnB1dGAncywgeW91CiAgICBfbXVzdF8gc2V0IGBiaW5kLXZhbHVlYCBpbnN0ZWFkLCBzbyB0aGF0IHRoZSB3cmFwcGVyIGBpcm9uLWlucHV0YCBjYW4gYmUKICAgIG5vdGlmaWVkLgoKICAgICMjIyBWYWxpZGF0aW9uCgogICAgYGlyb24taW5wdXRgIHVzZXMgdGhlIG5hdGl2ZSBgaW5wdXRgJ3MgdmFsaWRhdGlvbi4gRm9yIHNpbXBsaWNpdHksIGBpcm9uLWlucHV0YAogICAgaGFzIGEgYHZhbGlkYXRlKClgIG1ldGhvZCAod2hpY2ggaW50ZXJuYWxseSBqdXN0IGNoZWNrcyB0aGUgZGlzdHJpYnV0ZWQKICAgIGBpbnB1dGAncyB2YWxpZGl0eSksIHdoaWNoIHNldHMgYW4gYGludmFsaWRgIGF0dHJpYnV0ZSB0aGF0IGNhbiBhbHNvIGJlIHVzZWQgZm9yCiAgICBzdHlsaW5nLgoKICAgIFRvIHZhbGlkYXRlIGF1dG9tYXRpY2FsbHkgYXMgeW91IHR5cGUsIHlvdSBjYW4gdXNlIHRoZSBgYXV0by12YWxpZGF0ZWAKICAgIGF0dHJpYnV0ZS4KCiAgICBgaXJvbi1pbnB1dGAgYWxzbyBmaXJlcyBhbiBgaXJvbi1pbnB1dC12YWxpZGF0ZWAgZXZlbnQgYWZ0ZXIgYHZhbGlkYXRlKClgIGlzCiAgICBjYWxsZWQuIFlvdSBjYW4gdXNlIGl0IHRvIGltcGxlbWVudCBhIGN1c3RvbSB2YWxpZGF0b3I6CgogICAgICAgIHZhciBDYXRzT25seVZhbGlkYXRvciA9IHsKICAgICAgICAgIHZhbGlkYXRlOiBmdW5jdGlvbihpcm9uSW5wdXQpIHsKICAgICAgICAgICAgdmFyIHZhbGlkID0gIWlyb25JbnB1dC5iaW5kVmFsdWUgfHwgaXJvbklucHV0LmJpbmRWYWx1ZSA9PT0gJ2NhdCc7CiAgICAgICAgICAgIGlyb25JbnB1dC5pbnZhbGlkID0gIXZhbGlkOwogICAgICAgICAgICByZXR1cm4gdmFsaWQ7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGlyb25JbnB1dC5hZGRFdmVudExpc3RlbmVyKCdpcm9uLWlucHV0LXZhbGlkYXRlJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICBDYXRzT25seS52YWxpZGF0ZShpbnB1dDIpOwogICAgICAgIH0pOwoKICAgIFlvdSBjYW4gYWxzbyB1c2UgYW4gZWxlbWVudCBpbXBsZW1lbnRpbmcgYW4KICAgIFtgSXJvblZhbGlkYXRvckJlaGF2aW9yYF0oL2VsZW1lbnQvUG9seW1lckVsZW1lbnRzL2lyb24tdmFsaWRhdGFibGUtYmVoYXZpb3IpLgogICAgVGhpcyBleGFtcGxlIGNhbiBhbHNvIGJlIGZvdW5kIGluIHRoZSBkZW1vIGZvciB0aGlzIGVsZW1lbnQ6CgogICAgICAgIDxpcm9uLWlucHV0IHZhbGlkYXRvcj0iY2F0cy1vbmx5Ij4KICAgICAgICAgIDxpbnB1dD4KICAgICAgICA8L2lyb24taW5wdXQ+CgogICAgIyMjIFByZXZlbnRpbmcgaW52YWxpZCBpbnB1dAoKICAgIEl0IG1heSBiZSBkZXNpcmFibGUgdG8gb25seSBhbGxvdyB1c2VycyB0byBlbnRlciBjZXJ0YWluIGNoYXJhY3RlcnMuIFlvdSBjYW4gdXNlCiAgICB0aGUgYGFsbG93ZWQtcGF0dGVybmAgYXR0cmlidXRlIHRvIGFjY29tcGxpc2ggdGhpcy4gVGhpcyBmZWF0dXJlIGlzIHNlcGFyYXRlCiAgICBmcm9tIHZhbGlkYXRpb24sIGFuZCBgYWxsb3dlZC1wYXR0ZXJuYCBkb2VzIG5vdCBhZmZlY3QgaG93IHRoZSBpbnB1dCBpcwogICAgdmFsaWRhdGVkLgoKICAgICAgICAvLyBPbmx5IGFsbG93IHR5cGluZyBkaWdpdHMsIGJ1dCBhIHZhbGlkIGlucHV0IGhhcyBleGFjdGx5IDUgZGlnaXRzLgogICAgICAgIDxpcm9uLWlucHV0IGFsbG93ZWQtcGF0dGVybj0iWzAtOV0iPgogICAgICAgICAgPGlucHV0IHBhdHRlcm49IlxkezV9Ij4KICAgICAgICA8L2lyb24taW5wdXQ+CgogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgfQogICAgPC9zdHlsZT4KICAgIDxzbG90IGlkPSJjb250ZW50Ij48L3Nsb3Q+CmAsCgogICAgICBpczogJ2lyb24taW5wdXQnLAogICAgICBiZWhhdmlvcnM6IFtJcm9uVmFsaWRhdGFibGVCZWhhdmlvcl0sCgogICAgICAvKioKICAgICAgICogRmlyZWQgd2hlbmV2ZXIgYHZhbGlkYXRlKClgIGlzIGNhbGxlZC4KICAgICAgICoKICAgICAgICogQGV2ZW50IGlyb24taW5wdXQtdmFsaWRhdGUKICAgICAgICovCgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIFVzZSB0aGlzIHByb3BlcnR5IGluc3RlYWQgb2YgYHZhbHVlYCBmb3IgdHdvLXdheSBkYXRhIGJpbmRpbmcsIG9yIHRvCiAgICAgICAgICogc2V0IGEgZGVmYXVsdCB2YWx1ZSBmb3IgdGhlIGlucHV0LiAqKkRvIG5vdCoqIHVzZSB0aGUgZGlzdHJpYnV0ZWQKICAgICAgICAgKiBpbnB1dCdzIGB2YWx1ZWAgcHJvcGVydHkgdG8gc2V0IGEgZGVmYXVsdCB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBiaW5kVmFsdWU6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIENvbXB1dGVkIHByb3BlcnR5IHRoYXQgZWNob2VzIGBiaW5kVmFsdWVgIChtb3N0bHkgdXNlZCBmb3IgUG9seW1lciAxLjAKICAgICAgICAgKiBiYWNrY29tcGF0aWJpbGl0eSwgaWYgeW91IHdlcmUgb25lLXdheSBiaW5kaW5nIHRvIHRoZSBQb2x5bWVyIDEuMAogICAgICAgICAqIGBpbnB1dCBpcz0iaXJvbi1pbnB1dCJgIHZhbHVlIGF0dHJpYnV0ZSkuCiAgICAgICAgICovCiAgICAgICAgdmFsdWU6IHt0eXBlOiBTdHJpbmcsIGNvbXB1dGVkOiAnX2NvbXB1dGVWYWx1ZShiaW5kVmFsdWUpJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2V4LWxpa2UgbGlzdCBvZiBjaGFyYWN0ZXJzIGFsbG93ZWQgYXMgaW5wdXQ7IGFsbCBjaGFyYWN0ZXJzIG5vdCBpbiB0aGUKICAgICAgICAgKiBsaXN0IHdpbGwgYmUgcmVqZWN0ZWQuIFRoZSByZWNvbW1lbmRlZCBmb3JtYXQgc2hvdWxkIGJlIGEgbGlzdCBvZiBhbGxvd2VkCiAgICAgICAgICogY2hhcmFjdGVycywgZm9yIGV4YW1wbGUsIGBbYS16QS1aMC05ListITs6XWAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIHBhdHRlcm4gcmVwcmVzZW50cyB0aGUgYWxsb3dlZCBjaGFyYWN0ZXJzIGZvciB0aGUgZmllbGQ7IGFzIHRoZSB1c2VyCiAgICAgICAgICogaW5wdXRzIHRleHQsIGVhY2ggaW5kaXZpZHVhbCBjaGFyYWN0ZXIgd2lsbCBiZSBjaGVja2VkIGFnYWluc3QgdGhlCiAgICAgICAgICogcGF0dGVybiAocmF0aGVyIHRoYW4gY2hlY2tpbmcgdGhlIGVudGlyZSB2YWx1ZSBhcyBhIHdob2xlKS4gSWYgYQogICAgICAgICAqIGNoYXJhY3RlciBpcyBub3QgYSBtYXRjaCwgaXQgd2lsbCBiZSByZWplY3RlZC4KICAgICAgICAgKgogICAgICAgICAqIFBhc3RlZCBpbnB1dCB3aWxsIGhhdmUgZWFjaCBjaGFyYWN0ZXIgY2hlY2tlZCBpbmRpdmlkdWFsbHk7IGlmIGFueQogICAgICAgICAqIGNoYXJhY3RlciBkb2Vzbid0IG1hdGNoIGBhbGxvd2VkUGF0dGVybmAsIHRoZSBlbnRpcmUgcGFzdGVkIHN0cmluZyB3aWxsCiAgICAgICAgICogYmUgcmVqZWN0ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlOiBpZiB5b3Ugd2VyZSB1c2luZyBgaXJvbi1pbnB1dGAgaW4gMS4wLCB5b3Ugd2VyZSBhbHNvIHJlcXVpcmVkIHRvCiAgICAgICAgICogc2V0IGBwcmV2ZW50LWludmFsaWQtaW5wdXRgLiBUaGlzIGlzIG5vIGxvbmdlciBuZWVkZWQgYXMgb2YgUG9seW1lciAyLjAsCiAgICAgICAgICogYW5kIHdpbGwgYmUgc2V0IGF1dG9tYXRpY2FsbHkgZm9yIHlvdSBpZiBhbiBgYWxsb3dlZFBhdHRlcm5gIGlzIHByb3ZpZGVkLgogICAgICAgICAqCiAgICAgICAgICovCiAgICAgICAgYWxsb3dlZFBhdHRlcm46IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBhdXRvLXZhbGlkYXRlIHRoZSBpbnB1dCB2YWx1ZSBhcyB5b3UgdHlwZS4KICAgICAgICAgKi8KICAgICAgICBhdXRvVmFsaWRhdGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbmF0aXZlIGlucHV0IGVsZW1lbnQuCiAgICAgICAgICovCiAgICAgICAgX2lucHV0RWxlbWVudDogT2JqZWN0LAogICAgICB9LAoKICAgICAgb2JzZXJ2ZXJzOiBbJ19iaW5kVmFsdWVDaGFuZ2VkKGJpbmRWYWx1ZSwgX2lucHV0RWxlbWVudCknXSwKICAgICAgbGlzdGVuZXJzOiB7J2lucHV0JzogJ19vbklucHV0JywgJ2tleXByZXNzJzogJ19vbktleXByZXNzJ30sCgogICAgICBjcmVhdGVkOiBmdW5jdGlvbigpIHsKICAgICAgICBJcm9uQTExeUFubm91bmNlci5yZXF1ZXN0QXZhaWxhYmlsaXR5KCk7CiAgICAgICAgdGhpcy5fcHJldmlvdXNWYWxpZElucHV0ID0gJyc7CiAgICAgICAgdGhpcy5fcGF0dGVybkFscmVhZHlDaGVja2VkID0gZmFsc2U7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gSWYgdGhlIGlucHV0IGlzIGFkZGVkIGF0IGEgbGF0ZXIgdGltZSwgdXBkYXRlIHRoZSBpbnRlcm5hbCByZWZlcmVuY2UuCiAgICAgICAgdGhpcy5fb2JzZXJ2ZXIgPSBkb20odGhpcykub2JzZXJ2ZU5vZGVzKGZ1bmN0aW9uKGluZm8pIHsKICAgICAgICAgIHRoaXMuX2luaXRTbG90dGVkSW5wdXQoKTsKICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICB9LAoKICAgICAgZGV0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9vYnNlcnZlcikgewogICAgICAgICAgZG9tKHRoaXMpLnVub2JzZXJ2ZU5vZGVzKHRoaXMuX29ic2VydmVyKTsKICAgICAgICAgIHRoaXMuX29ic2VydmVyID0gbnVsbDsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgZGlzdHJpYnV0ZWQgaW5wdXQgZWxlbWVudC4KICAgICAgICovCiAgICAgIGdldCBpbnB1dEVsZW1lbnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2lucHV0RWxlbWVudDsKICAgICAgfSwKCiAgICAgIF9pbml0U2xvdHRlZElucHV0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9pbnB1dEVsZW1lbnQgPSB0aGlzLmdldEVmZmVjdGl2ZUNoaWxkcmVuKClbMF07CgogICAgICAgIGlmICh0aGlzLmlucHV0RWxlbWVudCAmJiB0aGlzLmlucHV0RWxlbWVudC52YWx1ZSkgewogICAgICAgICAgdGhpcy5iaW5kVmFsdWUgPSB0aGlzLmlucHV0RWxlbWVudC52YWx1ZTsKICAgICAgICB9CgogICAgICAgIHRoaXMuZmlyZSgnaXJvbi1pbnB1dC1yZWFkeScpOwogICAgICB9LAoKICAgICAgZ2V0IF9wYXR0ZXJuUmVnRXhwKCkgewogICAgICAgIHZhciBwYXR0ZXJuOwogICAgICAgIGlmICh0aGlzLmFsbG93ZWRQYXR0ZXJuKSB7CiAgICAgICAgICBwYXR0ZXJuID0gbmV3IFJlZ0V4cCh0aGlzLmFsbG93ZWRQYXR0ZXJuKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgc3dpdGNoICh0aGlzLmlucHV0RWxlbWVudC50eXBlKSB7CiAgICAgICAgICAgIGNhc2UgJ251bWJlcic6CiAgICAgICAgICAgICAgcGF0dGVybiA9IC9bMC05LixlLV0vOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gcGF0dGVybjsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAc3VwcHJlc3Mge2NoZWNrVHlwZXN9CiAgICAgICAqLwogICAgICBfYmluZFZhbHVlQ2hhbmdlZDogZnVuY3Rpb24oYmluZFZhbHVlLCBpbnB1dEVsZW1lbnQpIHsKICAgICAgICAvLyBUaGUgb2JzZXJ2ZXIgY291bGQgaGF2ZSBydW4gYmVmb3JlIGF0dGFjaGVkKCkgd2hlbiB3ZSBoYXZlIGFjdHVhbGx5CiAgICAgICAgLy8gaW5pdGlhbGl6ZWQgdGhpcyBwcm9wZXJ0eS4KICAgICAgICBpZiAoIWlucHV0RWxlbWVudCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKGJpbmRWYWx1ZSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICBpbnB1dEVsZW1lbnQudmFsdWUgPSBudWxsOwogICAgICAgIH0gZWxzZSBpZiAoYmluZFZhbHVlICE9PSBpbnB1dEVsZW1lbnQudmFsdWUpIHsKICAgICAgICAgIHRoaXMuaW5wdXRFbGVtZW50LnZhbHVlID0gYmluZFZhbHVlOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuYXV0b1ZhbGlkYXRlKSB7CiAgICAgICAgICB0aGlzLnZhbGlkYXRlKCk7CiAgICAgICAgfQoKICAgICAgICAvLyBtYW51YWxseSBub3RpZnkgYmVjYXVzZSB3ZSBkb24ndCB3YW50IHRvIG5vdGlmeSB1bnRpbCBhZnRlciBzZXR0aW5nIHZhbHVlCiAgICAgICAgdGhpcy5maXJlKCdiaW5kLXZhbHVlLWNoYW5nZWQnLCB7dmFsdWU6IGJpbmRWYWx1ZX0pOwogICAgICB9LAoKICAgICAgX29uSW5wdXQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIE5lZWQgdG8gdmFsaWRhdGUgZWFjaCBvZiB0aGUgY2hhcmFjdGVycyBwYXN0ZWQgaWYgdGhleSBoYXZlbid0CiAgICAgICAgLy8gYmVlbiB2YWxpZGF0ZWQgaW5zaWRlIGBfb25LZXlwcmVzc2AgYWxyZWFkeS4KICAgICAgICBpZiAodGhpcy5hbGxvd2VkUGF0dGVybiAmJiAhdGhpcy5fcGF0dGVybkFscmVhZHlDaGVja2VkKSB7CiAgICAgICAgICB2YXIgdmFsaWQgPSB0aGlzLl9jaGVja1BhdHRlcm5WYWxpZGl0eSgpOwogICAgICAgICAgaWYgKCF2YWxpZCkgewogICAgICAgICAgICB0aGlzLl9hbm5vdW5jZUludmFsaWRDaGFyYWN0ZXIoCiAgICAgICAgICAgICAgICAnSW52YWxpZCBzdHJpbmcgb2YgY2hhcmFjdGVycyBub3QgZW50ZXJlZC4nKTsKICAgICAgICAgICAgdGhpcy5pbnB1dEVsZW1lbnQudmFsdWUgPSB0aGlzLl9wcmV2aW91c1ZhbGlkSW5wdXQ7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuYmluZFZhbHVlID0gdGhpcy5fcHJldmlvdXNWYWxpZElucHV0ID0gdGhpcy5pbnB1dEVsZW1lbnQudmFsdWU7CiAgICAgICAgdGhpcy5fcGF0dGVybkFscmVhZHlDaGVja2VkID0gZmFsc2U7CiAgICAgIH0sCgogICAgICBfaXNQcmludGFibGU6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgLy8gV2hhdCBhIGNvbnRyb2wvcHJpbnRhYmxlIGNoYXJhY3RlciBpcyB2YXJpZXMgd2lsZGx5IGJhc2VkIG9uIHRoZSBicm93c2VyLgogICAgICAgIC8vIC0gbW9zdCBjb250cm9sIGNoYXJhY3RlcnMgKGFycm93cywgYmFja3NwYWNlKSBkbyBub3Qgc2VuZCBhIGBrZXlwcmVzc2AKICAgICAgICAvLyBldmVudAogICAgICAgIC8vICAgaW4gQ2hyb21lLCBidXQgdGhlICpkbyogb24gRmlyZWZveAogICAgICAgIC8vIC0gaW4gRmlyZWZveCwgd2hlbiB0aGV5IGRvIHNlbmQgYSBga2V5cHJlc3NgIGV2ZW50LCBjb250cm9sIGNoYXJzIGhhdmUKICAgICAgICAvLyAgIGEgY2hhckNvZGUgPSAwLCBrZXlDb2RlID0geHggKGZvciBleC4gNDAgZm9yIGRvd24gYXJyb3cpCiAgICAgICAgLy8gLSBwcmludGFibGUgY2hhcmFjdGVycyBhbHdheXMgc2VuZCBhIGtleXByZXNzIGV2ZW50LgogICAgICAgIC8vIC0gaW4gRmlyZWZveCwgcHJpbnRhYmxlIGNoYXJzIGFsd2F5cyBoYXZlIGEga2V5Q29kZSA9IDAuIEluIENocm9tZSwgdGhlCiAgICAgICAgLy8ga2V5Q29kZQogICAgICAgIC8vICAgYWx3YXlzIG1hdGNoZXMgdGhlIGNoYXJDb2RlLgogICAgICAgIC8vIE5vbmUgb2YgdGhpcyBtYWtlcyBhbnkgc2Vuc2UuCgogICAgICAgIC8vIEZvciB0aGVzZSBrZXlzLCBBU0NJSSBjb2RlID09IGJyb3dzZXIga2V5Y29kZS4KICAgICAgICB2YXIgYW55Tm9uUHJpbnRhYmxlID0gKGV2ZW50LmtleUNvZGUgPT0gOCkgfHwgIC8vIGJhY2tzcGFjZQogICAgICAgICAgICAoZXZlbnQua2V5Q29kZSA9PSA5KSB8fCAgICAgICAgICAgICAgICAgICAgLy8gdGFiCiAgICAgICAgICAgIChldmVudC5rZXlDb2RlID09IDEzKSB8fCAgICAgICAgICAgICAgICAgICAvLyBlbnRlcgogICAgICAgICAgICAoZXZlbnQua2V5Q29kZSA9PSAyNyk7ICAgICAgICAgICAgICAgICAgICAgLy8gZXNjYXBlCgogICAgICAgIC8vIEZvciB0aGVzZSBrZXlzLCBtYWtlIHN1cmUgaXQncyBhIGJyb3dzZXIga2V5Y29kZSBhbmQgbm90IGFuIEFTQ0lJIGNvZGUuCiAgICAgICAgdmFyIG1vek5vblByaW50YWJsZSA9IChldmVudC5rZXlDb2RlID09IDE5KSB8fCAgLy8gcGF1c2UKICAgICAgICAgICAgKGV2ZW50LmtleUNvZGUgPT0gMjApIHx8ICAgICAgICAgICAgICAgICAgICAvLyBjYXBzIGxvY2sKICAgICAgICAgICAgKGV2ZW50LmtleUNvZGUgPT0gNDUpIHx8ICAgICAgICAgICAgICAgICAgICAvLyBpbnNlcnQKICAgICAgICAgICAgKGV2ZW50LmtleUNvZGUgPT0gNDYpIHx8ICAgICAgICAgICAgICAgICAgICAvLyBkZWxldGUKICAgICAgICAgICAgKGV2ZW50LmtleUNvZGUgPT0gMTQ0KSB8fCAgICAgICAgICAgICAgICAgICAvLyBudW0gbG9jawogICAgICAgICAgICAoZXZlbnQua2V5Q29kZSA9PSAxNDUpIHx8ICAgICAgICAgICAgICAgICAgIC8vIHNjcm9sbCBsb2NrCiAgICAgICAgICAgIChldmVudC5rZXlDb2RlID4gMzIgJiYKICAgICAgICAgICAgIGV2ZW50LmtleUNvZGUgPCA0MSkgfHwgIC8vIHBhZ2UgdXAvZG93biwgZW5kLCBob21lLCBhcnJvd3MKICAgICAgICAgICAgKGV2ZW50LmtleUNvZGUgPiAxMTEgJiYgZXZlbnQua2V5Q29kZSA8IDEyNCk7ICAvLyBmbiBrZXlzCgogICAgICAgIHJldHVybiAhYW55Tm9uUHJpbnRhYmxlICYmICEoZXZlbnQuY2hhckNvZGUgPT0gMCAmJiBtb3pOb25QcmludGFibGUpOwogICAgICB9LAoKICAgICAgX29uS2V5cHJlc3M6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKCF0aGlzLmFsbG93ZWRQYXR0ZXJuICYmIHRoaXMuaW5wdXRFbGVtZW50LnR5cGUgIT09ICdudW1iZXInKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHZhciByZWdleHAgPSB0aGlzLl9wYXR0ZXJuUmVnRXhwOwogICAgICAgIGlmICghcmVnZXhwKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBIYW5kbGUgc3BlY2lhbCBrZXlzIGFuZCBiYWNrc3BhY2UKICAgICAgICBpZiAoZXZlbnQubWV0YUtleSB8fCBldmVudC5jdHJsS2V5IHx8IGV2ZW50LmFsdEtleSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gQ2hlY2sgdGhlIHBhdHRlcm4gZWl0aGVyIGhlcmUgb3IgaW4gYF9vbklucHV0YCwgYnV0IG5vdCBpbiBib3RoLgogICAgICAgIHRoaXMuX3BhdHRlcm5BbHJlYWR5Q2hlY2tlZCA9IHRydWU7CgogICAgICAgIHZhciB0aGlzQ2hhciA9IFN0cmluZy5mcm9tQ2hhckNvZGUoZXZlbnQuY2hhckNvZGUpOwogICAgICAgIGlmICh0aGlzLl9pc1ByaW50YWJsZShldmVudCkgJiYgIXJlZ2V4cC50ZXN0KHRoaXNDaGFyKSkgewogICAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgIHRoaXMuX2Fubm91bmNlSW52YWxpZENoYXJhY3RlcigKICAgICAgICAgICAgICAnSW52YWxpZCBjaGFyYWN0ZXIgJyArIHRoaXNDaGFyICsgJyBub3QgZW50ZXJlZC4nKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfY2hlY2tQYXR0ZXJuVmFsaWRpdHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciByZWdleHAgPSB0aGlzLl9wYXR0ZXJuUmVnRXhwOwogICAgICAgIGlmICghcmVnZXhwKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLmlucHV0RWxlbWVudC52YWx1ZS5sZW5ndGg7IGkrKykgewogICAgICAgICAgaWYgKCFyZWdleHAudGVzdCh0aGlzLmlucHV0RWxlbWVudC52YWx1ZVtpXSkpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRydWUgaWYgYHZhbHVlYCBpcyB2YWxpZC4gVGhlIHZhbGlkYXRvciBwcm92aWRlZCBpbiBgdmFsaWRhdG9yYAogICAgICAgKiB3aWxsIGJlIHVzZWQgZmlyc3QsIHRoZW4gYW55IGNvbnN0cmFpbnRzLgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHRoZSB2YWx1ZSBpcyB2YWxpZC4KICAgICAgICovCiAgICAgIHZhbGlkYXRlOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIXRoaXMuaW5wdXRFbGVtZW50KSB7CiAgICAgICAgICB0aGlzLmludmFsaWQgPSBmYWxzZTsKICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLy8gVXNlIHRoZSBuZXN0ZWQgaW5wdXQncyBuYXRpdmUgdmFsaWRpdHkuCiAgICAgICAgdmFyIHZhbGlkID0gdGhpcy5pbnB1dEVsZW1lbnQuY2hlY2tWYWxpZGl0eSgpOwoKICAgICAgICAvLyBPbmx5IGRvIGV4dHJhIGNoZWNraW5nIGlmIHRoZSBicm93c2VyIHRob3VnaHQgdGhpcyB3YXMgdmFsaWQuCiAgICAgICAgaWYgKHZhbGlkKSB7CiAgICAgICAgICAvLyBFbXB0eSwgcmVxdWlyZWQgaW5wdXQgaXMgaW52YWxpZAogICAgICAgICAgaWYgKHRoaXMucmVxdWlyZWQgJiYgdGhpcy5iaW5kVmFsdWUgPT09ICcnKSB7CiAgICAgICAgICAgIHZhbGlkID0gZmFsc2U7CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuaGFzVmFsaWRhdG9yKCkpIHsKICAgICAgICAgICAgdmFsaWQgPSBJcm9uVmFsaWRhdGFibGVCZWhhdmlvci52YWxpZGF0ZS5jYWxsKHRoaXMsIHRoaXMuYmluZFZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHRoaXMuaW52YWxpZCA9ICF2YWxpZDsKICAgICAgICB0aGlzLmZpcmUoJ2lyb24taW5wdXQtdmFsaWRhdGUnKTsKICAgICAgICByZXR1cm4gdmFsaWQ7CiAgICAgIH0sCgogICAgICBfYW5ub3VuY2VJbnZhbGlkQ2hhcmFjdGVyOiBmdW5jdGlvbihtZXNzYWdlKSB7CiAgICAgICAgdGhpcy5maXJlKCdpcm9uLWFubm91bmNlJywge3RleHQ6IG1lc3NhZ2V9KTsKICAgICAgfSwKCiAgICAgIF9jb21wdXRlVmFsdWU6IGZ1bmN0aW9uKGJpbmRWYWx1ZSkgewogICAgICAgIHJldHVybiBiaW5kVmFsdWU7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgICogVXNlIGBQb2x5bWVyLlBhcGVySW5wdXRBZGRvbkJlaGF2aW9yYCB0byBpbXBsZW1lbnQgYW4gYWRkLW9uIGZvcgogICAgICogYDxwYXBlci1pbnB1dC1jb250YWluZXI+YC4gQSBhZGQtb24gYXBwZWFycyBiZWxvdyB0aGUgaW5wdXQsIGFuZCBtYXkgZGlzcGxheQogICAgICogaW5mb3JtYXRpb24gYmFzZWQgb24gdGhlIGlucHV0IHZhbHVlIGFuZCB2YWxpZGl0eSBzdWNoIGFzIGEgY2hhcmFjdGVyIGNvdW50ZXIKICAgICAqIG9yIGFuIGVycm9yIG1lc3NhZ2UuCiAgICAgKiBAcG9seW1lckJlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IFBhcGVySW5wdXRBZGRvbkJlaGF2aW9yID0gewogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5maXJlKCdhZGRvbi1hdHRhY2hlZCcpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBmdW5jdGlvbiBjYWxsZWQgYnkgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCB3aGVuIHRoZSBpbnB1dCB2YWx1ZSBvcgogICAgICAgKiB2YWxpZGl0eSBjaGFuZ2VzLgogICAgICAgKiBAcGFyYW0ge3sKICAgICAgICogICBpbnZhbGlkOiBib29sZWFuLAogICAgICAgKiAgIGlucHV0RWxlbWVudDogKEVsZW1lbnR8dW5kZWZpbmVkKSwKICAgICAgICogICB2YWx1ZTogKHN0cmluZ3x1bmRlZmluZWQpCiAgICAgICAqIH19IHN0YXRlIC0KICAgICAgICogICAgIGlucHV0RWxlbWVudDogVGhlIGlucHV0IGVsZW1lbnQuCiAgICAgICAqICAgICB2YWx1ZTogVGhlIGlucHV0IHZhbHVlLgogICAgICAgKiAgICAgaW52YWxpZDogVHJ1ZSBpZiB0aGUgaW5wdXQgdmFsdWUgaXMgaW52YWxpZC4KICAgICAgICovCiAgICAgIHVwZGF0ZTogZnVuY3Rpb24oc3RhdGUpIHt9CgogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKgogICAgYDxwYXBlci1pbnB1dC1jaGFyLWNvdW50ZXI+YCBpcyBhIGNoYXJhY3RlciBjb3VudGVyIGZvciB1c2Ugd2l0aAogICAgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YC4gSXQgc2hvd3MgdGhlIG51bWJlciBvZiBjaGFyYWN0ZXJzIGVudGVyZWQgaW4gdGhlCiAgICBpbnB1dCBhbmQgdGhlIG1heCBsZW5ndGggaWYgaXQgaXMgc3BlY2lmaWVkLgoKICAgICAgICA8cGFwZXItaW5wdXQtY29udGFpbmVyPgogICAgICAgICAgPGlucHV0IG1heGxlbmd0aD0iMjAiPgogICAgICAgICAgPHBhcGVyLWlucHV0LWNoYXItY291bnRlcj48L3BhcGVyLWlucHV0LWNoYXItY291bnRlcj4KICAgICAgICA8L3BhcGVyLWlucHV0LWNvbnRhaW5lcj4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgbWl4aW4gaXMgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLWlucHV0LWNoYXItY291bnRlcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBlbGVtZW50IHwgYHt9YAogICAgKi8KICAgIFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBmbG9hdDogcmlnaHQ7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY2FwdGlvbjsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jaGFyLWNvdW50ZXI7CiAgICAgIH0KCiAgICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICA6aG9zdCg6ZGlyKHJ0bCkpIHsKICAgICAgICBmbG9hdDogbGVmdDsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8c3Bhbj5bW19jaGFyQ291bnRlclN0cl1dPC9zcGFuPgpgLAoKICAgICAgaXM6ICdwYXBlci1pbnB1dC1jaGFyLWNvdW50ZXInLAogICAgICBiZWhhdmlvcnM6IFtQYXBlcklucHV0QWRkb25CZWhhdmlvcl0sCiAgICAgIHByb3BlcnRpZXM6IHtfY2hhckNvdW50ZXJTdHI6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnMCd9fSwKCiAgICAgIC8qKgogICAgICAgKiBUaGlzIG92ZXJyaWRlcyB0aGUgdXBkYXRlIGZ1bmN0aW9uIGluIFBhcGVySW5wdXRBZGRvbkJlaGF2aW9yLgogICAgICAgKiBAcGFyYW0ge3sKICAgICAgICogICBpbnB1dEVsZW1lbnQ6IChFbGVtZW50fHVuZGVmaW5lZCksCiAgICAgICAqICAgdmFsdWU6IChzdHJpbmd8dW5kZWZpbmVkKSwKICAgICAgICogICBpbnZhbGlkOiBib29sZWFuCiAgICAgICAqIH19IHN0YXRlIC0KICAgICAgICogICAgIGlucHV0RWxlbWVudDogVGhlIGlucHV0IGVsZW1lbnQuCiAgICAgICAqICAgICB2YWx1ZTogVGhlIGlucHV0IHZhbHVlLgogICAgICAgKiAgICAgaW52YWxpZDogVHJ1ZSBpZiB0aGUgaW5wdXQgdmFsdWUgaXMgaW52YWxpZC4KICAgICAgICovCiAgICAgIHVwZGF0ZTogZnVuY3Rpb24oc3RhdGUpIHsKICAgICAgICBpZiAoIXN0YXRlLmlucHV0RWxlbWVudCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgc3RhdGUudmFsdWUgPSBzdGF0ZS52YWx1ZSB8fCAnJzsKCiAgICAgICAgdmFyIGNvdW50ZXIgPSBzdGF0ZS52YWx1ZS50b1N0cmluZygpLmxlbmd0aC50b1N0cmluZygpOwoKICAgICAgICBpZiAoc3RhdGUuaW5wdXRFbGVtZW50Lmhhc0F0dHJpYnV0ZSgnbWF4bGVuZ3RoJykpIHsKICAgICAgICAgIGNvdW50ZXIgKz0gJy8nICsgc3RhdGUuaW5wdXRFbGVtZW50LmdldEF0dHJpYnV0ZSgnbWF4bGVuZ3RoJyk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9jaGFyQ291bnRlclN0ciA9IGNvdW50ZXI7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgY29uc3QgdGVtcGxhdGUkYiA9IGh0bWxgCjxjdXN0b20tc3R5bGU+CiAgPHN0eWxlIGlzPSJjdXN0b20tc3R5bGUiPgogICAgaHRtbCB7CiAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLXNoYXJlZC1pbnB1dC1zdHlsZTogewogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsgLyogdG8gbWFrZSBhIHN0YWNraW5nIGNvbnRleHQgKi8KICAgICAgICBvdXRsaW5lOiBub25lOwogICAgICAgIGJveC1zaGFkb3c6IG5vbmU7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgICBtYXJnaW46IDA7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgbWF4LXdpZHRoOiAxMDAlOwogICAgICAgIGJhY2tncm91bmQ6IHRyYW5zcGFyZW50OwogICAgICAgIGJvcmRlcjogbm9uZTsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgICAgICAtd2Via2l0LWFwcGVhcmFuY2U6IG5vbmU7CiAgICAgICAgdGV4dC1hbGlnbjogaW5oZXJpdDsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogdmFyKC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LWFsaWduLCBib3R0b20pOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LXN1YmhlYWQ7CiAgICAgIH07CiAgICB9CiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+CmA7CiAgICB0ZW1wbGF0ZSRiLnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkYi5jb250ZW50KTsKCiAgICAvKgogICAgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCBpcyBhIGNvbnRhaW5lciBmb3IgYSBgPGxhYmVsPmAsIGFuIGA8aXJvbi1pbnB1dD5gIG9yCiAgICBgPHRleHRhcmVhPmAgYW5kIG9wdGlvbmFsIGFkZC1vbiBlbGVtZW50cyBzdWNoIGFzIGFuIGVycm9yIG1lc3NhZ2Ugb3IgY2hhcmFjdGVyCiAgICBjb3VudGVyLCB1c2VkIHRvIGltcGxlbWVudCBNYXRlcmlhbCBEZXNpZ24gdGV4dCBmaWVsZHMuCgogICAgRm9yIGV4YW1wbGU6CgogICAgICAgIDxwYXBlci1pbnB1dC1jb250YWluZXI+CiAgICAgICAgICA8bGFiZWwgc2xvdD0ibGFiZWwiPllvdXIgbmFtZTwvbGFiZWw+CiAgICAgICAgICA8aXJvbi1pbnB1dCBzbG90PSJpbnB1dCI+CiAgICAgICAgICAgIDxpbnB1dD4KICAgICAgICAgIDwvaXJvbi1pbnB1dD4KICAgICAgICAgIC8vIEluIFBvbHltZXIgMS4wLCB5b3Ugd291bGQgdXNlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiIHNsb3Q9ImlucHV0Ij5gCiAgICBpbnN0ZWFkIG9mIHRoZSBhYm92ZS4KICAgICAgICA8L3BhcGVyLWlucHV0LWNvbnRhaW5lcj4KCiAgICBZb3UgY2FuIHN0eWxlIHRoZSBuZXN0ZWQgYDxpbnB1dD5gIGhvd2V2ZXIgeW91IHdhbnQ7IGlmIHlvdSB3YW50IGl0IHRvIGxvb2sgbGlrZQogICAgYSBNYXRlcmlhbCBEZXNpZ24gaW5wdXQsIHlvdSBjYW4gc3R5bGUgaXQgd2l0aCB0aGUKICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLXNoYXJlZC1pbnB1dC1zdHlsZSBtaXhpbi4KCiAgICBEbyBub3Qgd3JhcCBgPHBhcGVyLWlucHV0LWNvbnRhaW5lcj5gIGFyb3VuZCBlbGVtZW50cyB0aGF0IGFscmVhZHkgaW5jbHVkZSBpdCwKICAgIHN1Y2ggYXMgYDxwYXBlci1pbnB1dD5gLiBEb2luZyBzbyBtYXkgY2F1c2UgZXZlbnRzIHRvIGJvdW5jZSBpbmZpbml0ZWx5IGJldHdlZW4KICAgIHRoZSBjb250YWluZXIgYW5kIGl0cyBjb250YWluZWQgZWxlbWVudC4KCiAgICAjIyMgTGlzdGVuaW5nIGZvciBpbnB1dCBjaGFuZ2VzCgogICAgQnkgZGVmYXVsdCwgaXQgbGlzdGVucyBmb3IgY2hhbmdlcyBvbiB0aGUgYGJpbmQtdmFsdWVgIGF0dHJpYnV0ZSBvbiBpdHMgY2hpbGRyZW4KICAgIG5vZGVzIGFuZCBwZXJmb3JtIHRhc2tzIHN1Y2ggYXMgYXV0by12YWxpZGF0aW5nIGFuZCBsYWJlbCBzdHlsaW5nIHdoZW4gdGhlCiAgICBgYmluZC12YWx1ZWAgY2hhbmdlcy4gWW91IGNhbiBjb25maWd1cmUgdGhlIGF0dHJpYnV0ZSBpdCBsaXN0ZW5zIHRvIHdpdGggdGhlCiAgICBgYXR0ci1mb3ItdmFsdWVgIGF0dHJpYnV0ZS4KCiAgICAjIyMgVXNpbmcgYSBjdXN0b20gaW5wdXQgZWxlbWVudAoKICAgIFlvdSBjYW4gdXNlIGEgY3VzdG9tIGlucHV0IGVsZW1lbnQgaW4gYSBgPHBhcGVyLWlucHV0LWNvbnRhaW5lcj5gLCBmb3IgZXhhbXBsZQogICAgdG8gaW1wbGVtZW50IGEgY29tcG91bmQgaW5wdXQgZmllbGQgbGlrZSBhIHNvY2lhbCBzZWN1cml0eSBudW1iZXIgaW5wdXQuIFRoZQogICAgY3VzdG9tIGlucHV0IGVsZW1lbnQgc2hvdWxkIGhhdmUgdGhlIGBwYXBlci1pbnB1dC1pbnB1dGAgY2xhc3MsIGhhdmUgYQogICAgYG5vdGlmeTp0cnVlYCB2YWx1ZSBwcm9wZXJ0eSBhbmQgb3B0aW9uYWxseSBpbXBsZW1lbnRzCiAgICBgUG9seW1lci5Jcm9uVmFsaWRhdGFibGVCZWhhdmlvcmAgaWYgaXQgaXMgdmFsaWRhdGFibGUuCgogICAgICAgIDxwYXBlci1pbnB1dC1jb250YWluZXIgYXR0ci1mb3ItdmFsdWU9InNzbi12YWx1ZSI+CiAgICAgICAgICA8bGFiZWwgc2xvdD0ibGFiZWwiPlNvY2lhbCBzZWN1cml0eSBudW1iZXI8L2xhYmVsPgogICAgICAgICAgPHNzbi1pbnB1dCBzbG90PSJpbnB1dCIgY2xhc3M9InBhcGVyLWlucHV0LWlucHV0Ij48L3Nzbi1pbnB1dD4KICAgICAgICA8L3BhcGVyLWlucHV0LWNvbnRhaW5lcj4KCgogICAgSWYgeW91J3JlIHVzaW5nIGEgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCBpbXBlcmF0aXZlbHksIGl0J3MgaW1wb3J0YW50IHRvIG1ha2UKICAgIHN1cmUgdGhhdCB5b3UgYXR0YWNoIGl0cyBjaGlsZHJlbiAodGhlIGBpcm9uLWlucHV0YCBhbmQgdGhlIG9wdGlvbmFsIGBsYWJlbGApCiAgICBiZWZvcmUgeW91IGF0dGFjaCB0aGUgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCBpdHNlbGYsIHNvIHRoYXQgaXQgY2FuIGJlIHNldCB1cAogICAgY29ycmVjdGx5LgoKICAgICMjIyBWYWxpZGF0aW9uCgogICAgSWYgdGhlIGBhdXRvLXZhbGlkYXRlYCBhdHRyaWJ1dGUgaXMgc2V0LCB0aGUgaW5wdXQgY29udGFpbmVyIHdpbGwgdmFsaWRhdGUgdGhlCiAgICBpbnB1dCBhbmQgdXBkYXRlIHRoZSBjb250YWluZXIgc3R5bGluZyB3aGVuIHRoZSBpbnB1dCB2YWx1ZSBjaGFuZ2VzLgoKICAgICMjIyBBZGQtb25zCgogICAgQWRkLW9ucyBhcmUgY2hpbGQgZWxlbWVudHMgb2YgYSBgPHBhcGVyLWlucHV0LWNvbnRhaW5lcj5gIHdpdGggdGhlIGBhZGQtb25gCiAgICBhdHRyaWJ1dGUgYW5kIGltcGxlbWVudHMgdGhlIGBQb2x5bWVyLlBhcGVySW5wdXRBZGRvbkJlaGF2aW9yYCBiZWhhdmlvci4gVGhleQogICAgYXJlIG5vdGlmaWVkIHdoZW4gdGhlIGlucHV0IHZhbHVlIG9yIHZhbGlkaXR5IGNoYW5nZXMsIGFuZCBtYXkgaW1wbGVtZW50CiAgICBmdW5jdGlvbmFsaXR5IHN1Y2ggYXMgZXJyb3IgbWVzc2FnZXMgb3IgY2hhcmFjdGVyIGNvdW50ZXJzLiBUaGV5IGFwcGVhciBhdCB0aGUKICAgIGJvdHRvbSBvZiB0aGUgaW5wdXQuCgogICAgIyMjIFByZWZpeGVzIGFuZCBzdWZmaXhlcwogICAgVGhlc2UgYXJlIGNoaWxkIGVsZW1lbnRzIG9mIGEgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCB3aXRoIHRoZSBgcHJlZml4YAogICAgb3IgYHN1ZmZpeGAgYXR0cmlidXRlLCBhbmQgYXJlIGRpc3BsYXllZCBpbmxpbmUgd2l0aCB0aGUgaW5wdXQsIGJlZm9yZSBvciBhZnRlci4KCiAgICAgICAgPHBhcGVyLWlucHV0LWNvbnRhaW5lcj4KICAgICAgICAgIDxkaXYgc2xvdD0icHJlZml4Ij4kPC9kaXY+CiAgICAgICAgICA8bGFiZWwgc2xvdD0ibGFiZWwiPlRvdGFsPC9sYWJlbD4KICAgICAgICAgIDxpcm9uLWlucHV0IHNsb3Q9ImlucHV0Ij4KICAgICAgICAgICAgPGlucHV0PgogICAgICAgICAgPC9pcm9uLWlucHV0PgogICAgICAgICAgLy8gSW4gUG9seW1lciAxLjAsIHlvdSB3b3VsZCB1c2UgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCIgc2xvdD0iaW5wdXQiPmAKICAgIGluc3RlYWQgb2YgdGhlIGFib3ZlLiA8cGFwZXItaWNvbi1idXR0b24gc2xvdD0ic3VmZml4IgogICAgaWNvbj0iY2xlYXIiPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICAgICAgPC9wYXBlci1pbnB1dC1jb250YWluZXI+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItY29sb3JgIHwgTGFiZWwgYW5kIHVuZGVybGluZSBjb2xvciB3aGVuIHRoZSBpbnB1dCBpcyBub3QgZm9jdXNlZCB8IGAtLXNlY29uZGFyeS10ZXh0LWNvbG9yYAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWZvY3VzLWNvbG9yYCB8IExhYmVsIGFuZCB1bmRlcmxpbmUgY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgZm9jdXNlZCB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvcmAgfCBMYWJlbCBhbmQgdW5kZXJsaW5lIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGlzIGludmFsaWQgfCBgLS1lcnJvci1jb2xvcmAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC1jb2xvcmAgfCBJbnB1dCBmb3JlZ3JvdW5kIGNvbG9yIHwgYC0tcHJpbWFyeS10ZXh0LWNvbG9yYAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGNvbnRhaW5lciB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1kaXNhYmxlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBjb250YWluZXIgd2hlbiBpdCdzIGRpc2FibGVkIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGxhYmVsIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsLWZvY3VzYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGxhYmVsIHdoZW4gdGhlIGlucHV0IGlzIGZvY3VzZWQgfCBge31gCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItbGFiZWwtZmxvYXRpbmdgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgbGFiZWwgd2hlbiBmbG9hdGluZyB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBpbnB1dCB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC1hbGlnbmAgfCBUaGUgdmVydGljYWwtYWxpZ24gcHJvcGVydHkgb2YgdGhlIGlucHV0IHwgYGJvdHRvbWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC1kaXNhYmxlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBpbnB1dCB3aGVuIHRoZSBjb21wb25lbnQgaXMgZGlzYWJsZWQgfCBge31gCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQtZm9jdXNgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgaW5wdXQgd2hlbiBmb2N1c2VkIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LWludmFsaWRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgaW5wdXQgd2hlbiBpbnZhbGlkIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LXdlYmtpdC1zcGlubmVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHdlYmtpdCBzcGlubmVyIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LXdlYmtpdC1jbGVhcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB3ZWJraXQgY2xlYXIgYnV0dG9uIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LXdlYmtpdC1jYWxlbmRhci1waWNrZXItaW5kaWNhdG9yYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHdlYmtpdCBjYWxlbmRhciBwaWNrZXIgaW5kaWNhdG9yIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLW1zLWNsZWFyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIEludGVybmV0IEV4cGxvcmVyIGNsZWFyIGJ1dHRvbiB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci11bmRlcmxpbmVgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdW5kZXJsaW5lIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtY29udGFpbmVyLXVuZGVybGluZS1mb2N1c2AgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB1bmRlcmxpbmUgd2hlbiB0aGUgaW5wdXQgaXMgZm9jdXNlZCB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci11bmRlcmxpbmUtZGlzYWJsZWRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdW5kZXJsaW5lIHdoZW4gdGhlIGlucHV0IGlzIGRpc2FibGVkIHwgYHt9YAogICAgYC0tcGFwZXItaW5wdXQtcHJlZml4YCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGlucHV0IHByZWZpeCB8IGB7fWAKICAgIGAtLXBhcGVyLWlucHV0LXN1ZmZpeGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBpbnB1dCBzdWZmaXggfCBge31gCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItbGFiZWwtYmVmb3JlYCB8IE1peGluIGFwcGxpZWQgdG8gbGFiZWwgYmVmb3JlIHBzZXVkbyBlbGVtZW50IHwge30KICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1sYWJlbC1hZnRlcmAgfCBNaXhpbiBhcHBsaWVkIHRvIGxhYmVsIGFmdGVyIHBzZXVkbyBlbGVtZW50ICh1c2VmdWwgZm9yIHJlcXVpcmVkIGFzdGVyaXNrKSB8IHt9CgogICAgVGhpcyBlbGVtZW50IGlzIGBkaXNwbGF5OmJsb2NrYCBieSBkZWZhdWx0LCBidXQgeW91IGNhbiBzZXQgdGhlIGBpbmxpbmVgCiAgICBhdHRyaWJ1dGUgdG8gbWFrZSBpdCBgZGlzcGxheTppbmxpbmUtYmxvY2tgLgogICAgKi8KICAgIFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHBhZGRpbmc6IDhweCAwOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lcjsKICAgICAgfQoKICAgICAgOmhvc3QoW2lubGluZV0pIHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgIH0KCiAgICAgIDpob3N0KFtkaXNhYmxlZF0pIHsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgICBvcGFjaXR5OiAwLjMzOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItZGlzYWJsZWQ7CiAgICAgIH0KCiAgICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICBbaGlkZGVuXSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICAuZmxvYXRlZC1sYWJlbC1wbGFjZWhvbGRlciB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jYXB0aW9uOwogICAgICB9CgogICAgICAudW5kZXJsaW5lIHsKICAgICAgICBoZWlnaHQ6IDJweDsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgIC5mb2N1c2VkLWxpbmUgewogICAgICAgIEBhcHBseSAtLWxheW91dC1maXQ7CiAgICAgICAgYm9yZGVyLWJvdHRvbTogMnB4IHNvbGlkIHZhcigtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1mb2N1cy1jb2xvciwgdmFyKC0tcHJpbWFyeS1jb2xvcikpOwoKICAgICAgICAtd2Via2l0LXRyYW5zZm9ybS1vcmlnaW46IGNlbnRlciBjZW50ZXI7CiAgICAgICAgdHJhbnNmb3JtLW9yaWdpbjogY2VudGVyIGNlbnRlcjsKICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGUzZCgwLDEsMSk7CiAgICAgICAgdHJhbnNmb3JtOiBzY2FsZTNkKDAsMSwxKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLXVuZGVybGluZS1mb2N1czsKICAgICAgfQoKICAgICAgLnVuZGVybGluZS5pcy1oaWdobGlnaHRlZCAuZm9jdXNlZC1saW5lIHsKICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogbm9uZTsKICAgICAgICB0cmFuc2Zvcm06IG5vbmU7CiAgICAgICAgLXdlYmtpdC10cmFuc2l0aW9uOiAtd2Via2l0LXRyYW5zZm9ybSAwLjI1czsKICAgICAgICB0cmFuc2l0aW9uOiB0cmFuc2Zvcm0gMC4yNXM7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRyYW5zaXRpb24tZWFzaW5nOwogICAgICB9CgogICAgICAudW5kZXJsaW5lLmlzLWludmFsaWQgLmZvY3VzZWQtbGluZSB7CiAgICAgICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvciwgdmFyKC0tZXJyb3ItY29sb3IpKTsKICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogbm9uZTsKICAgICAgICB0cmFuc2Zvcm06IG5vbmU7CiAgICAgICAgLXdlYmtpdC10cmFuc2l0aW9uOiAtd2Via2l0LXRyYW5zZm9ybSAwLjI1czsKICAgICAgICB0cmFuc2l0aW9uOiB0cmFuc2Zvcm0gMC4yNXM7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRyYW5zaXRpb24tZWFzaW5nOwogICAgICB9CgogICAgICAudW5mb2N1c2VkLWxpbmUgewogICAgICAgIEBhcHBseSAtLWxheW91dC1maXQ7CiAgICAgICAgYm9yZGVyLWJvdHRvbTogMXB4IHNvbGlkIHZhcigtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1jb2xvciwgdmFyKC0tc2Vjb25kYXJ5LXRleHQtY29sb3IpKTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItdW5kZXJsaW5lOwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSAudW5mb2N1c2VkLWxpbmUgewogICAgICAgIGJvcmRlci1ib3R0b206IDFweCBkYXNoZWQ7CiAgICAgICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItY29sb3IsIHZhcigtLXNlY29uZGFyeS10ZXh0LWNvbG9yKSk7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLXVuZGVybGluZS1kaXNhYmxlZDsKICAgICAgfQoKICAgICAgLmlucHV0LXdyYXBwZXIgewogICAgICAgIEBhcHBseSAtLWxheW91dC1ob3Jpem9udGFsOwogICAgICAgIEBhcHBseSAtLWxheW91dC1jZW50ZXI7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudCB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtcmVsYXRpdmU7CiAgICAgICAgbWF4LXdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudCA6OnNsb3R0ZWQobGFiZWwpLAogICAgICAuaW5wdXQtY29udGVudCA6OnNsb3R0ZWQoLnBhcGVyLWlucHV0LWxhYmVsKSB7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHRvcDogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGZvbnQ6IGluaGVyaXQ7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1jb2xvciwgdmFyKC0tc2Vjb25kYXJ5LXRleHQtY29sb3IpKTsKICAgICAgICAtd2Via2l0LXRyYW5zaXRpb246IC13ZWJraXQtdHJhbnNmb3JtIDAuMjVzLCB3aWR0aCAwLjI1czsKICAgICAgICB0cmFuc2l0aW9uOiB0cmFuc2Zvcm0gMC4yNXMsIHdpZHRoIDAuMjVzOwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogbGVmdCB0b3A7CiAgICAgICAgdHJhbnNmb3JtLW9yaWdpbjogbGVmdCB0b3A7CiAgICAgICAgLyogRml4IGZvciBzYWZhcmkgbm90IGZvY3VzaW5nIDAtaGVpZ2h0IGRhdGUvdGltZSBpbnB1dHMgd2l0aCAtd2Via2l0LWFwcGVyYW5jZTogbm9uZTsgKi8KICAgICAgICBtaW4taGVpZ2h0OiAxcHg7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLW5vd3JhcDsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LXN1YmhlYWQ7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRyYW5zaXRpb24tZWFzaW5nOwogICAgICB9CgoKICAgICAgLmlucHV0LWNvbnRlbnQgOjpzbG90dGVkKGxhYmVsKTpiZWZvcmUsCiAgICAgIC5pbnB1dC1jb250ZW50IDo6c2xvdHRlZCgucGFwZXItaW5wdXQtbGFiZWwpOmJlZm9yZSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsLWJlZm9yZTsKICAgICAgfQoKICAgICAgLmlucHV0LWNvbnRlbnQgOjpzbG90dGVkKGxhYmVsKTphZnRlciwKICAgICAgLmlucHV0LWNvbnRlbnQgOjpzbG90dGVkKC5wYXBlci1pbnB1dC1sYWJlbCk6YWZ0ZXIgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1sYWJlbC1hZnRlcjsKICAgICAgfQoKICAgICAgLmlucHV0LWNvbnRlbnQubGFiZWwtaXMtZmxvYXRpbmcgOjpzbG90dGVkKGxhYmVsKSwKICAgICAgLmlucHV0LWNvbnRlbnQubGFiZWwtaXMtZmxvYXRpbmcgOjpzbG90dGVkKC5wYXBlci1pbnB1dC1sYWJlbCkgewogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC03NSUpIHNjYWxlKDAuNzUpOwogICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgtNzUlKSBzY2FsZSgwLjc1KTsKCiAgICAgICAgLyogU2luY2Ugd2Ugc2NhbGUgdG8gNzUvMTAwIG9mIHRoZSBzaXplLCB3ZSBhY3R1YWxseSBoYXZlIDEwMC83NSBvZiB0aGUKICAgICAgICBvcmlnaW5hbCBzcGFjZSBub3cgYXZhaWxhYmxlICovCiAgICAgICAgd2lkdGg6IDEzMyU7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1sYWJlbC1mbG9hdGluZzsKICAgICAgfQoKICAgICAgOmhvc3QoOmRpcihydGwpKSAuaW5wdXQtY29udGVudC5sYWJlbC1pcy1mbG9hdGluZyA6OnNsb3R0ZWQobGFiZWwpLAogICAgICA6aG9zdCg6ZGlyKHJ0bCkpIC5pbnB1dC1jb250ZW50LmxhYmVsLWlzLWZsb2F0aW5nIDo6c2xvdHRlZCgucGFwZXItaW5wdXQtbGFiZWwpIHsKICAgICAgICByaWdodDogMDsKICAgICAgICBsZWZ0OiBhdXRvOwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogcmlnaHQgdG9wOwogICAgICAgIHRyYW5zZm9ybS1vcmlnaW46IHJpZ2h0IHRvcDsKICAgICAgfQoKICAgICAgLmlucHV0LWNvbnRlbnQubGFiZWwtaXMtaGlnaGxpZ2h0ZWQgOjpzbG90dGVkKGxhYmVsKSwKICAgICAgLmlucHV0LWNvbnRlbnQubGFiZWwtaXMtaGlnaGxpZ2h0ZWQgOjpzbG90dGVkKC5wYXBlci1pbnB1dC1sYWJlbCkgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItZm9jdXMtY29sb3IsIHZhcigtLXByaW1hcnktY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsLWZvY3VzOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudC5pcy1pbnZhbGlkIDo6c2xvdHRlZChsYWJlbCksCiAgICAgIC5pbnB1dC1jb250ZW50LmlzLWludmFsaWQgOjpzbG90dGVkKC5wYXBlci1pbnB1dC1sYWJlbCkgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvciwgdmFyKC0tZXJyb3ItY29sb3IpKTsKICAgICAgfQoKICAgICAgLmlucHV0LWNvbnRlbnQubGFiZWwtaXMtaGlkZGVuIDo6c2xvdHRlZChsYWJlbCksCiAgICAgIC5pbnB1dC1jb250ZW50LmxhYmVsLWlzLWhpZGRlbiA6OnNsb3R0ZWQoLnBhcGVyLWlucHV0LWxhYmVsKSB7CiAgICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudCA6OnNsb3R0ZWQoaW5wdXQpLAogICAgICAuaW5wdXQtY29udGVudCA6OnNsb3R0ZWQoaXJvbi1pbnB1dCksCiAgICAgIC5pbnB1dC1jb250ZW50IDo6c2xvdHRlZCh0ZXh0YXJlYSksCiAgICAgIC5pbnB1dC1jb250ZW50IDo6c2xvdHRlZChpcm9uLWF1dG9ncm93LXRleHRhcmVhKSwKICAgICAgLmlucHV0LWNvbnRlbnQgOjpzbG90dGVkKC5wYXBlci1pbnB1dC1pbnB1dCkgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1zaGFyZWQtaW5wdXQtc3R5bGU7CiAgICAgICAgLyogVGhlIGFwcGx5IHNoaW0gZG9lc24ndCBhcHBseSB0aGUgbmVzdGVkIGNvbG9yIGN1c3RvbSBwcm9wZXJ0eSwKICAgICAgICAgIHNvIHdlIGhhdmUgdG8gcmUtYXBwbHkgaXQgaGVyZS4gKi8KICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQ7CiAgICAgIH0KCiAgICAgIC5pbnB1dC1jb250ZW50IDo6c2xvdHRlZChpbnB1dCk6Oi13ZWJraXQtb3V0ZXItc3Bpbi1idXR0b24sCiAgICAgIC5pbnB1dC1jb250ZW50IDo6c2xvdHRlZChpbnB1dCk6Oi13ZWJraXQtaW5uZXItc3Bpbi1idXR0b24gewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC13ZWJraXQtc3Bpbm5lcjsKICAgICAgfQoKICAgICAgLmlucHV0LWNvbnRlbnQuZm9jdXNlZCA6OnNsb3R0ZWQoaW5wdXQpLAogICAgICAuaW5wdXQtY29udGVudC5mb2N1c2VkIDo6c2xvdHRlZChpcm9uLWlucHV0KSwKICAgICAgLmlucHV0LWNvbnRlbnQuZm9jdXNlZCA6OnNsb3R0ZWQodGV4dGFyZWEpLAogICAgICAuaW5wdXQtY29udGVudC5mb2N1c2VkIDo6c2xvdHRlZChpcm9uLWF1dG9ncm93LXRleHRhcmVhKSwKICAgICAgLmlucHV0LWNvbnRlbnQuZm9jdXNlZCA6OnNsb3R0ZWQoLnBhcGVyLWlucHV0LWlucHV0KSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LWZvY3VzOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudC5pcy1pbnZhbGlkIDo6c2xvdHRlZChpbnB1dCksCiAgICAgIC5pbnB1dC1jb250ZW50LmlzLWludmFsaWQgOjpzbG90dGVkKGlyb24taW5wdXQpLAogICAgICAuaW5wdXQtY29udGVudC5pcy1pbnZhbGlkIDo6c2xvdHRlZCh0ZXh0YXJlYSksCiAgICAgIC5pbnB1dC1jb250ZW50LmlzLWludmFsaWQgOjpzbG90dGVkKGlyb24tYXV0b2dyb3ctdGV4dGFyZWEpLAogICAgICAuaW5wdXQtY29udGVudC5pcy1pbnZhbGlkIDo6c2xvdHRlZCgucGFwZXItaW5wdXQtaW5wdXQpIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQtaW52YWxpZDsKICAgICAgfQoKICAgICAgLnByZWZpeCA6OnNsb3R0ZWQoKikgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LXN1YmhlYWQ7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtbm9uZTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1wcmVmaXg7CiAgICAgIH0KCiAgICAgIC5zdWZmaXggOjpzbG90dGVkKCopIHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1zdWJoZWFkOwogICAgICAgIEBhcHBseSAtLWxheW91dC1mbGV4LW5vbmU7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LXN1ZmZpeDsKICAgICAgfQoKICAgICAgLyogRmlyZWZveCBzZXRzIGEgbWluLXdpZHRoIG9uIHRoZSBpbnB1dCwgd2hpY2ggY2FuIGNhdXNlIGxheW91dCBpc3N1ZXMgKi8KICAgICAgLmlucHV0LWNvbnRlbnQgOjpzbG90dGVkKGlucHV0KSB7CiAgICAgICAgbWluLXdpZHRoOiAwOwogICAgICB9CgogICAgICAuaW5wdXQtY29udGVudCA6OnNsb3R0ZWQodGV4dGFyZWEpIHsKICAgICAgICByZXNpemU6IG5vbmU7CiAgICAgIH0KCiAgICAgIC5hZGQtb24tY29udGVudCB7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CgogICAgICAuYWRkLW9uLWNvbnRlbnQuaXMtaW52YWxpZCA6OnNsb3R0ZWQoKikgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvciwgdmFyKC0tZXJyb3ItY29sb3IpKTsKICAgICAgfQoKICAgICAgLmFkZC1vbi1jb250ZW50LmlzLWhpZ2hsaWdodGVkIDo6c2xvdHRlZCgqKSB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1mb2N1cy1jb2xvciwgdmFyKC0tcHJpbWFyeS1jb2xvcikpOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxkaXYgY2xhc3M9ImZsb2F0ZWQtbGFiZWwtcGxhY2Vob2xkZXIiIGFyaWEtaGlkZGVuPSJ0cnVlIiBoaWRkZW49Iltbbm9MYWJlbEZsb2F0XV0iPiZuYnNwOzwvZGl2PgoKICAgIDxkaXYgY2xhc3M9ImlucHV0LXdyYXBwZXIiPgogICAgICA8c3BhbiBjbGFzcz0icHJlZml4Ij48c2xvdCBuYW1lPSJwcmVmaXgiPjwvc2xvdD48L3NwYW4+CgogICAgICA8ZGl2IGNsYXNzJD0iW1tfY29tcHV0ZUlucHV0Q29udGVudENsYXNzKG5vTGFiZWxGbG9hdCxhbHdheXNGbG9hdExhYmVsLGZvY3VzZWQsaW52YWxpZCxfaW5wdXRIYXNDb250ZW50KV1dIiBpZD0ibGFiZWxBbmRJbnB1dENvbnRhaW5lciI+CiAgICAgICAgPHNsb3QgbmFtZT0ibGFiZWwiPjwvc2xvdD4KICAgICAgICA8c2xvdCBuYW1lPSJpbnB1dCI+PC9zbG90PgogICAgICA8L2Rpdj4KCiAgICAgIDxzcGFuIGNsYXNzPSJzdWZmaXgiPjxzbG90IG5hbWU9InN1ZmZpeCI+PC9zbG90Pjwvc3Bhbj4KICAgIDwvZGl2PgoKICAgIDxkaXYgY2xhc3MkPSJbW19jb21wdXRlVW5kZXJsaW5lQ2xhc3MoZm9jdXNlZCxpbnZhbGlkKV1dIj4KICAgICAgPGRpdiBjbGFzcz0idW5mb2N1c2VkLWxpbmUiPjwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJmb2N1c2VkLWxpbmUiPjwvZGl2PgogICAgPC9kaXY+CgogICAgPGRpdiBjbGFzcyQ9IltbX2NvbXB1dGVBZGRPbkNvbnRlbnRDbGFzcyhmb2N1c2VkLGludmFsaWQpXV0iPgogICAgICA8c2xvdCBuYW1lPSJhZGQtb24iPjwvc2xvdD4KICAgIDwvZGl2PgpgLAoKICAgICAgaXM6ICdwYXBlci1pbnB1dC1jb250YWluZXInLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGRpc2FibGUgdGhlIGZsb2F0aW5nIGxhYmVsLiBUaGUgbGFiZWwgZGlzYXBwZWFycyB3aGVuIHRoZQogICAgICAgICAqIGlucHV0IHZhbHVlIGlzIG5vdCBudWxsLgogICAgICAgICAqLwogICAgICAgIG5vTGFiZWxGbG9hdDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGFsd2F5cyBmbG9hdCB0aGUgZmxvYXRpbmcgbGFiZWwuCiAgICAgICAgICovCiAgICAgICAgYWx3YXlzRmxvYXRMYWJlbDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBhdHRyaWJ1dGUgdG8gbGlzdGVuIGZvciB2YWx1ZSBjaGFuZ2VzIG9uLgogICAgICAgICAqLwogICAgICAgIGF0dHJGb3JWYWx1ZToge3R5cGU6IFN0cmluZywgdmFsdWU6ICdiaW5kLXZhbHVlJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGF1dG8tdmFsaWRhdGUgdGhlIGlucHV0IHZhbHVlIHdoZW4gaXQgY2hhbmdlcy4KICAgICAgICAgKi8KICAgICAgICBhdXRvVmFsaWRhdGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBpbnB1dCBpcyBpbnZhbGlkLiBUaGlzIHByb3BlcnR5IGlzIHNldCBhdXRvbWF0aWNhbGx5IHdoZW4gdGhlCiAgICAgICAgICogaW5wdXQgdmFsdWUgY2hhbmdlcyBpZiBhdXRvLXZhbGlkYXRpbmcsIG9yIHdoZW4gdGhlIGBpcm9uLWlucHV0LXZhbGlkYXRlYAogICAgICAgICAqIGV2ZW50IGlzIGhlYXJkIGZyb20gYSBjaGlsZC4KICAgICAgICAgKi8KICAgICAgICBpbnZhbGlkOiB7b2JzZXJ2ZXI6ICdfaW52YWxpZENoYW5nZWQnLCB0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBpbnB1dCBoYXMgZm9jdXMuCiAgICAgICAgICovCiAgICAgICAgZm9jdXNlZDoge3JlYWRPbmx5OiB0cnVlLCB0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgIF9hZGRvbnM6IHsKICAgICAgICAgIHR5cGU6IEFycmF5CiAgICAgICAgICAvLyBkbyBub3Qgc2V0IGEgZGVmYXVsdCB2YWx1ZSBoZXJlIGludGVudGlvbmFsbHkgLSBpdCB3aWxsIGJlIGluaXRpYWxpemVkCiAgICAgICAgICAvLyBsYXppbHkgd2hlbiBhIGRpc3RyaWJ1dGVkIGNoaWxkIGlzIGF0dGFjaGVkLCB3aGljaCBtYXkgb2NjdXIgYmVmb3JlCiAgICAgICAgICAvLyBjb25maWd1cmF0aW9uIGZvciB0aGlzIGVsZW1lbnQgaW4gcG9seWZpbGwuCiAgICAgICAgfSwKCiAgICAgICAgX2lucHV0SGFzQ29udGVudDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIF9pbnB1dFNlbGVjdG9yOgogICAgICAgICAgICB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ2lucHV0LGlyb24taW5wdXQsdGV4dGFyZWEsLnBhcGVyLWlucHV0LWlucHV0J30sCgogICAgICAgIF9ib3VuZE9uRm9jdXM6IHsKICAgICAgICAgIHR5cGU6IEZ1bmN0aW9uLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fb25Gb2N1cy5iaW5kKHRoaXMpOwogICAgICAgICAgfQogICAgICAgIH0sCgogICAgICAgIF9ib3VuZE9uQmx1cjogewogICAgICAgICAgdHlwZTogRnVuY3Rpb24sCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9vbkJsdXIuYmluZCh0aGlzKTsKICAgICAgICAgIH0KICAgICAgICB9LAoKICAgICAgICBfYm91bmRPbklucHV0OiB7CiAgICAgICAgICB0eXBlOiBGdW5jdGlvbiwKICAgICAgICAgIHZhbHVlOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX29uSW5wdXQuYmluZCh0aGlzKTsKICAgICAgICAgIH0KICAgICAgICB9LAoKICAgICAgICBfYm91bmRWYWx1ZUNoYW5nZWQ6IHsKICAgICAgICAgIHR5cGU6IEZ1bmN0aW9uLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fb25WYWx1ZUNoYW5nZWQuYmluZCh0aGlzKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsKICAgICAgICAnYWRkb24tYXR0YWNoZWQnOiAnX29uQWRkb25BdHRhY2hlZCcsCiAgICAgICAgJ2lyb24taW5wdXQtdmFsaWRhdGUnOiAnX29uSXJvbklucHV0VmFsaWRhdGUnCiAgICAgIH0sCgogICAgICBnZXQgX3ZhbHVlQ2hhbmdlZEV2ZW50KCkgewogICAgICAgIHJldHVybiB0aGlzLmF0dHJGb3JWYWx1ZSArICctY2hhbmdlZCc7CiAgICAgIH0sCgogICAgICBnZXQgX3Byb3BlcnR5Rm9yVmFsdWUoKSB7CiAgICAgICAgcmV0dXJuIGRhc2hUb0NhbWVsQ2FzZSh0aGlzLmF0dHJGb3JWYWx1ZSk7CiAgICAgIH0sCgogICAgICBnZXQgX2lucHV0RWxlbWVudCgpIHsKICAgICAgICByZXR1cm4gZG9tKHRoaXMpLnF1ZXJ5U2VsZWN0b3IodGhpcy5faW5wdXRTZWxlY3Rvcik7CiAgICAgIH0sCgogICAgICBnZXQgX2lucHV0RWxlbWVudFZhbHVlKCkgewogICAgICAgIHJldHVybiB0aGlzLl9pbnB1dEVsZW1lbnRbdGhpcy5fcHJvcGVydHlGb3JWYWx1ZV0gfHwKICAgICAgICAgICAgdGhpcy5faW5wdXRFbGVtZW50LnZhbHVlOwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICByZWFkeTogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gUGFwZXItaW5wdXQgdHJlYXRzIGEgdmFsdWUgb2YgdW5kZWZpbmVkIGRpZmZlcmVudGx5IGF0IHN0YXJ0dXAgdGhhbgogICAgICAgIC8vIHRoZSByZXN0IG9mIHRoZSB0aW1lIChzcGVjaWZpY2FsbHk6IGl0IGRvZXMgbm90IHZhbGlkYXRlIGl0IGF0IHN0YXJ0dXAsCiAgICAgICAgLy8gYnV0IGl0IGRvZXMgYWZ0ZXIgdGhhdC4gV2UgbmVlZCB0byB0cmFjayB3aGV0aGVyIHRoZSBmaXJzdCB0aW1lIHdlCiAgICAgICAgLy8gZW5jb3VudGVyIHRoZSB2YWx1ZSBpcyBiYXNpY2FsbHkgdGhpcyBmaXJzdCB0aW1lLCBzbyB0aGF0IHdlIGNhbiB2YWxpZGF0ZQogICAgICAgIC8vIGl0IGNvcnJlY3RseSB0aGUgcmVzdCBvZiB0aGUgdGltZS4gU2VlCiAgICAgICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9wYXBlci1pbnB1dC9pc3N1ZXMvNjA1CiAgICAgICAgdGhpcy5fX2lzRmlyc3RWYWx1ZVVwZGF0ZSA9IHRydWU7CiAgICAgICAgaWYgKCF0aGlzLl9hZGRvbnMpIHsKICAgICAgICAgIHRoaXMuX2FkZG9ucyA9IFtdOwogICAgICAgIH0KICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3VzJywgdGhpcy5fYm91bmRPbkZvY3VzLCB0cnVlKTsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2JsdXInLCB0aGlzLl9ib3VuZE9uQmx1ciwgdHJ1ZSk7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5hdHRyRm9yVmFsdWUpIHsKICAgICAgICAgIHRoaXMuX2lucHV0RWxlbWVudC5hZGRFdmVudExpc3RlbmVyKAogICAgICAgICAgICAgIHRoaXMuX3ZhbHVlQ2hhbmdlZEV2ZW50LCB0aGlzLl9ib3VuZFZhbHVlQ2hhbmdlZCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignaW5wdXQnLCB0aGlzLl9vbklucHV0KTsKICAgICAgICB9CgogICAgICAgIC8vIE9ubHkgdmFsaWRhdGUgd2hlbiBhdHRhY2hlZCBpZiB0aGUgaW5wdXQgYWxyZWFkeSBoYXMgYSB2YWx1ZS4KICAgICAgICBpZiAodGhpcy5faW5wdXRFbGVtZW50VmFsdWUgJiYgdGhpcy5faW5wdXRFbGVtZW50VmFsdWUgIT0gJycpIHsKICAgICAgICAgIHRoaXMuX2hhbmRsZVZhbHVlQW5kQXV0b1ZhbGlkYXRlKHRoaXMuX2lucHV0RWxlbWVudCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX2hhbmRsZVZhbHVlKHRoaXMuX2lucHV0RWxlbWVudCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9vbkFkZG9uQXR0YWNoZWQ6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKCF0aGlzLl9hZGRvbnMpIHsKICAgICAgICAgIHRoaXMuX2FkZG9ucyA9IFtdOwogICAgICAgIH0KICAgICAgICB2YXIgdGFyZ2V0ID0gZXZlbnQudGFyZ2V0OwogICAgICAgIGlmICh0aGlzLl9hZGRvbnMuaW5kZXhPZih0YXJnZXQpID09PSAtMSkgewogICAgICAgICAgdGhpcy5fYWRkb25zLnB1c2godGFyZ2V0KTsKICAgICAgICAgIGlmICh0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgICAgdGhpcy5faGFuZGxlVmFsdWUodGhpcy5faW5wdXRFbGVtZW50KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgX29uRm9jdXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3NldEZvY3VzZWQodHJ1ZSk7CiAgICAgIH0sCgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgX29uQmx1cjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fc2V0Rm9jdXNlZChmYWxzZSk7CiAgICAgICAgdGhpcy5faGFuZGxlVmFsdWVBbmRBdXRvVmFsaWRhdGUodGhpcy5faW5wdXRFbGVtZW50KTsKICAgICAgfSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfb25JbnB1dDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLl9oYW5kbGVWYWx1ZUFuZEF1dG9WYWxpZGF0ZShldmVudC50YXJnZXQpOwogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9vblZhbHVlQ2hhbmdlZDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgaW5wdXQgPSBldmVudC50YXJnZXQ7CgogICAgICAgIC8vIFBhcGVyLWlucHV0IHRyZWF0cyBhIHZhbHVlIG9mIHVuZGVmaW5lZCBkaWZmZXJlbnRseSBhdCBzdGFydHVwIHRoYW4KICAgICAgICAvLyB0aGUgcmVzdCBvZiB0aGUgdGltZSAoc3BlY2lmaWNhbGx5OiBpdCBkb2VzIG5vdCB2YWxpZGF0ZSBpdCBhdCBzdGFydHVwLAogICAgICAgIC8vIGJ1dCBpdCBkb2VzIGFmdGVyIHRoYXQuIElmIHRoaXMgaXMgaW4gZmFjdCB0aGUgYm9vdHVwIGNhc2UsIGlnbm9yZQogICAgICAgIC8vIHZhbGlkYXRpb24sIGp1c3QgdGhpcyBvbmNlLgogICAgICAgIGlmICh0aGlzLl9faXNGaXJzdFZhbHVlVXBkYXRlKSB7CiAgICAgICAgICB0aGlzLl9faXNGaXJzdFZhbHVlVXBkYXRlID0gZmFsc2U7CiAgICAgICAgICBpZiAoaW5wdXQudmFsdWUgPT09IHVuZGVmaW5lZCB8fCBpbnB1dC52YWx1ZSA9PT0gJycpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5faGFuZGxlVmFsdWVBbmRBdXRvVmFsaWRhdGUoZXZlbnQudGFyZ2V0KTsKICAgICAgfSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfaGFuZGxlVmFsdWU6IGZ1bmN0aW9uKGlucHV0RWxlbWVudCkgewogICAgICAgIHZhciB2YWx1ZSA9IHRoaXMuX2lucHV0RWxlbWVudFZhbHVlOwoKICAgICAgICAvLyB0eXBlPSJudW1iZXIiIGhhY2sgbmVlZGVkIGJlY2F1c2UgdGhpcy52YWx1ZSBpcyBlbXB0eSB1bnRpbCBpdCdzIHZhbGlkCiAgICAgICAgaWYgKHZhbHVlIHx8IHZhbHVlID09PSAwIHx8CiAgICAgICAgICAgIChpbnB1dEVsZW1lbnQudHlwZSA9PT0gJ251bWJlcicgJiYgIWlucHV0RWxlbWVudC5jaGVja1ZhbGlkaXR5KCkpKSB7CiAgICAgICAgICB0aGlzLl9pbnB1dEhhc0NvbnRlbnQgPSB0cnVlOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9pbnB1dEhhc0NvbnRlbnQgPSBmYWxzZTsKICAgICAgICB9CgogICAgICAgIHRoaXMudXBkYXRlQWRkb25zKAogICAgICAgICAgICB7aW5wdXRFbGVtZW50OiBpbnB1dEVsZW1lbnQsIHZhbHVlOiB2YWx1ZSwgaW52YWxpZDogdGhpcy5pbnZhbGlkfSk7CiAgICAgIH0sCgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgX2hhbmRsZVZhbHVlQW5kQXV0b1ZhbGlkYXRlOiBmdW5jdGlvbihpbnB1dEVsZW1lbnQpIHsKICAgICAgICBpZiAodGhpcy5hdXRvVmFsaWRhdGUgJiYgaW5wdXRFbGVtZW50KSB7CiAgICAgICAgICB2YXIgdmFsaWQ7CgogICAgICAgICAgaWYgKGlucHV0RWxlbWVudC52YWxpZGF0ZSkgewogICAgICAgICAgICB2YWxpZCA9IGlucHV0RWxlbWVudC52YWxpZGF0ZSh0aGlzLl9pbnB1dEVsZW1lbnRWYWx1ZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB2YWxpZCA9IGlucHV0RWxlbWVudC5jaGVja1ZhbGlkaXR5KCk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLmludmFsaWQgPSAhdmFsaWQ7CiAgICAgICAgfQoKICAgICAgICAvLyBDYWxsIHRoaXMgbGFzdCB0byBub3RpZnkgdGhlIGFkZC1vbnMuCiAgICAgICAgdGhpcy5faGFuZGxlVmFsdWUoaW5wdXRFbGVtZW50KTsKICAgICAgfSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfb25Jcm9uSW5wdXRWYWxpZGF0ZTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLmludmFsaWQgPSB0aGlzLl9pbnB1dEVsZW1lbnQuaW52YWxpZDsKICAgICAgfSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfaW52YWxpZENoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9hZGRvbnMpIHsKICAgICAgICAgIHRoaXMudXBkYXRlQWRkb25zKHtpbnZhbGlkOiB0aGlzLmludmFsaWR9KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FsbCB0aGlzIHRvIHVwZGF0ZSB0aGUgc3RhdGUgb2YgYWRkLW9ucy4KICAgICAgICogQHBhcmFtIHtPYmplY3R9IHN0YXRlIEFkZC1vbiBzdGF0ZS4KICAgICAgICovCiAgICAgIHVwZGF0ZUFkZG9uczogZnVuY3Rpb24oc3RhdGUpIHsKICAgICAgICBmb3IgKHZhciBhZGRvbiwgaW5kZXggPSAwOyBhZGRvbiA9IHRoaXMuX2FkZG9uc1tpbmRleF07IGluZGV4KyspIHsKICAgICAgICAgIGFkZG9uLnVwZGF0ZShzdGF0ZSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9jb21wdXRlSW5wdXRDb250ZW50Q2xhc3M6IGZ1bmN0aW9uKAogICAgICAgICAgbm9MYWJlbEZsb2F0LCBhbHdheXNGbG9hdExhYmVsLCBmb2N1c2VkLCBpbnZhbGlkLCBfaW5wdXRIYXNDb250ZW50KSB7CiAgICAgICAgdmFyIGNscyA9ICdpbnB1dC1jb250ZW50JzsKICAgICAgICBpZiAoIW5vTGFiZWxGbG9hdCkgewogICAgICAgICAgdmFyIGxhYmVsID0gdGhpcy5xdWVyeVNlbGVjdG9yKCdsYWJlbCcpOwoKICAgICAgICAgIGlmIChhbHdheXNGbG9hdExhYmVsIHx8IF9pbnB1dEhhc0NvbnRlbnQpIHsKICAgICAgICAgICAgY2xzICs9ICcgbGFiZWwtaXMtZmxvYXRpbmcnOwogICAgICAgICAgICAvLyBJZiB0aGUgbGFiZWwgaXMgZmxvYXRpbmcsIGlnbm9yZSBhbnkgb2Zmc2V0cyB0aGF0IG1heSBoYXZlIGJlZW4KICAgICAgICAgICAgLy8gYXBwbGllZCBmcm9tIGEgcHJlZml4IGVsZW1lbnQuCiAgICAgICAgICAgIHRoaXMuJC5sYWJlbEFuZElucHV0Q29udGFpbmVyLnN0eWxlLnBvc2l0aW9uID0gJ3N0YXRpYyc7CgogICAgICAgICAgICBpZiAoaW52YWxpZCkgewogICAgICAgICAgICAgIGNscyArPSAnIGlzLWludmFsaWQnOwogICAgICAgICAgICB9IGVsc2UgaWYgKGZvY3VzZWQpIHsKICAgICAgICAgICAgICBjbHMgKz0gJyBsYWJlbC1pcy1oaWdobGlnaHRlZCc7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIFdoZW4gdGhlIGxhYmVsIGlzIG5vdCBmbG9hdGluZywgaXQgc2hvdWxkIG92ZXJsYXAgdGhlIGlucHV0IGVsZW1lbnQuCiAgICAgICAgICAgIGlmIChsYWJlbCkgewogICAgICAgICAgICAgIHRoaXMuJC5sYWJlbEFuZElucHV0Q29udGFpbmVyLnN0eWxlLnBvc2l0aW9uID0gJ3JlbGF0aXZlJzsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaW52YWxpZCkgewogICAgICAgICAgICAgIGNscyArPSAnIGlzLWludmFsaWQnOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChfaW5wdXRIYXNDb250ZW50KSB7CiAgICAgICAgICAgIGNscyArPSAnIGxhYmVsLWlzLWhpZGRlbic7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaW52YWxpZCkgewogICAgICAgICAgICBjbHMgKz0gJyBpcy1pbnZhbGlkJzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKGZvY3VzZWQpIHsKICAgICAgICAgIGNscyArPSAnIGZvY3VzZWQnOwogICAgICAgIH0KICAgICAgICByZXR1cm4gY2xzOwogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9jb21wdXRlVW5kZXJsaW5lQ2xhc3M6IGZ1bmN0aW9uKGZvY3VzZWQsIGludmFsaWQpIHsKICAgICAgICB2YXIgY2xzID0gJ3VuZGVybGluZSc7CiAgICAgICAgaWYgKGludmFsaWQpIHsKICAgICAgICAgIGNscyArPSAnIGlzLWludmFsaWQnOwogICAgICAgIH0gZWxzZSBpZiAoZm9jdXNlZCkgewogICAgICAgICAgY2xzICs9ICcgaXMtaGlnaGxpZ2h0ZWQnOwogICAgICAgIH0KICAgICAgICByZXR1cm4gY2xzOwogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9jb21wdXRlQWRkT25Db250ZW50Q2xhc3M6IGZ1bmN0aW9uKGZvY3VzZWQsIGludmFsaWQpIHsKICAgICAgICB2YXIgY2xzID0gJ2FkZC1vbi1jb250ZW50JzsKICAgICAgICBpZiAoaW52YWxpZCkgewogICAgICAgICAgY2xzICs9ICcgaXMtaW52YWxpZCc7CiAgICAgICAgfSBlbHNlIGlmIChmb2N1c2VkKSB7CiAgICAgICAgICBjbHMgKz0gJyBpcy1oaWdobGlnaHRlZCc7CiAgICAgICAgfQogICAgICAgIHJldHVybiBjbHM7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qCiAgICBgPHBhcGVyLWlucHV0LWVycm9yPmAgaXMgYW4gZXJyb3IgbWVzc2FnZSBmb3IgdXNlIHdpdGgKICAgIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAuIFRoZSBlcnJvciBpcyBkaXNwbGF5ZWQgd2hlbiB0aGUKICAgIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAgaXMgYGludmFsaWRgLgoKICAgICAgICA8cGFwZXItaW5wdXQtY29udGFpbmVyPgogICAgICAgICAgPGlucHV0IHBhdHRlcm49IlswLTldKiI+CiAgICAgICAgICA8cGFwZXItaW5wdXQtZXJyb3Igc2xvdD0iYWRkLW9uIj5Pbmx5IG51bWJlcnMgYXJlCiAgICBhbGxvd2VkITwvcGFwZXItaW5wdXQtZXJyb3I+CiAgICAgICAgPC9wYXBlci1pbnB1dC1jb250YWluZXI+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvcmAgfCBUaGUgZm9yZWdyb3VuZCBjb2xvciBvZiB0aGUgZXJyb3IgfCBgLS1lcnJvci1jb2xvcmAKICAgIGAtLXBhcGVyLWlucHV0LWVycm9yYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGVycm9yIHwgYHt9YAogICAgKi8KICAgIFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICB2aXNpYmlsaXR5OiBoaWRkZW47CgogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItaW52YWxpZC1jb2xvciwgdmFyKC0tZXJyb3ItY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jYXB0aW9uOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWVycm9yOwogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICBsZWZ0OjA7CiAgICAgICAgcmlnaHQ6MDsKICAgICAgfQoKICAgICAgOmhvc3QoW2ludmFsaWRdKSB7CiAgICAgICAgdmlzaWJpbGl0eTogdmlzaWJsZTsKICAgICAgfQoKICAgICAgI2ExMXlXcmFwcGVyIHsKICAgICAgICB2aXNpYmlsaXR5OiBoaWRkZW47CiAgICAgIH0KCiAgICAgIDpob3N0KFtpbnZhbGlkXSkgI2ExMXlXcmFwcGVyIHsKICAgICAgICB2aXNpYmlsaXR5OiB2aXNpYmxlOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDwhLS0KICAgIElmIHRoZSBwYXBlci1pbnB1dC1lcnJvciBlbGVtZW50IGlzIGRpcmVjdGx5IHJlZmVyZW5jZWQgYnkgYW4KICAgIFxgYXJpYS1kZXNjcmliZWRieVxgIGF0dHJpYnV0ZSwgc3VjaCBhcyB3aGVuIHVzZWQgYXMgYSBwYXBlci1pbnB1dCBhZGQtb24sCiAgICB0aGVuIGFwcGx5aW5nIFxgdmlzaWJpbGl0eTogaGlkZGVuO1xgIHRvIHRoZSBwYXBlci1pbnB1dC1lcnJvciBlbGVtZW50IGl0c2VsZgogICAgZG9lcyBub3QgaGlkZSB0aGUgZXJyb3IuCgogICAgRm9yIG1vcmUgaW5mb3JtYXRpb24sIHNlZToKICAgIGh0dHBzOi8vd3d3LnczLm9yZy9UUi9hY2NuYW1lLTEuMS8jbWFwcGluZ19hZGRpdGlvbmFsX25kX2Rlc2NyaXB0aW9uCiAgICAtLT4KICAgIDxkaXYgaWQ9ImExMXlXcmFwcGVyIj4KICAgICAgPHNsb3Q+PC9zbG90PgogICAgPC9kaXY+CmAsCgogICAgICBpczogJ3BhcGVyLWlucHV0LWVycm9yJywKICAgICAgYmVoYXZpb3JzOiBbUGFwZXJJbnB1dEFkZG9uQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIFRydWUgaWYgdGhlIGVycm9yIGlzIHNob3dpbmcuCiAgICAgICAgICovCiAgICAgICAgaW52YWxpZDoge3JlYWRPbmx5OiB0cnVlLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWUsIHR5cGU6IEJvb2xlYW59CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhpcyBvdmVycmlkZXMgdGhlIHVwZGF0ZSBmdW5jdGlvbiBpbiBQYXBlcklucHV0QWRkb25CZWhhdmlvci4KICAgICAgICogQHBhcmFtIHt7CiAgICAgICAqICAgaW5wdXRFbGVtZW50OiAoRWxlbWVudHx1bmRlZmluZWQpLAogICAgICAgKiAgIHZhbHVlOiAoc3RyaW5nfHVuZGVmaW5lZCksCiAgICAgICAqICAgaW52YWxpZDogYm9vbGVhbgogICAgICAgKiB9fSBzdGF0ZSAtCiAgICAgICAqICAgICBpbnB1dEVsZW1lbnQ6IFRoZSBpbnB1dCBlbGVtZW50LgogICAgICAgKiAgICAgdmFsdWU6IFRoZSBpbnB1dCB2YWx1ZS4KICAgICAgICogICAgIGludmFsaWQ6IFRydWUgaWYgdGhlIGlucHV0IHZhbHVlIGlzIGludmFsaWQuCiAgICAgICAqLwogICAgICB1cGRhdGU6IGZ1bmN0aW9uKHN0YXRlKSB7CiAgICAgICAgdGhpcy5fc2V0SW52YWxpZChzdGF0ZS5pbnZhbGlkKTsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLy8gR2VuZXJhdGUgdW5pcXVlLCBtb25vdG9uaWNhbGx5IGluY3JlYXNpbmcgSURzIGZvciBsYWJlbHMgKG5lZWRlZCBieQogICAgLy8gYXJpYS1sYWJlbGxlZGJ5KSBhbmQgYWRkLW9ucy4KICAgIGNvbnN0IFBhcGVySW5wdXRIZWxwZXIgPSB7fTsKCiAgICBQYXBlcklucHV0SGVscGVyLk5leHRMYWJlbElEID0gMTsKICAgIFBhcGVySW5wdXRIZWxwZXIuTmV4dEFkZG9uSUQgPSAxOwogICAgUGFwZXJJbnB1dEhlbHBlci5OZXh0SW5wdXRJRCA9IDE7CgogICAgLyoqCiAgICAgKiBVc2UgYFBhcGVySW5wdXRCZWhhdmlvcmAgdG8gaW1wbGVtZW50IGlucHV0cyB3aXRoIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAuCiAgICAgKiBUaGlzIGJlaGF2aW9yIGlzIGltcGxlbWVudGVkIGJ5IGA8cGFwZXItaW5wdXQ+YC4gSXQgZXhwb3NlcyBhIG51bWJlciBvZgogICAgICogcHJvcGVydGllcyBmcm9tIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAgYW5kIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAgYW5kCiAgICAgKiB0aGV5IHNob3VsZCBiZSBib3VuZCBpbiB5b3VyIHRlbXBsYXRlLgogICAgICoKICAgICAqIFRoZSBpbnB1dCBlbGVtZW50IGNhbiBiZSBhY2Nlc3NlZCBieSB0aGUgYGlucHV0RWxlbWVudGAgcHJvcGVydHkgaWYgeW91IG5lZWQKICAgICAqIHRvIGFjY2VzcyBwcm9wZXJ0aWVzIG9yIG1ldGhvZHMgdGhhdCBhcmUgbm90IGV4cG9zZWQuCiAgICAgKiBAcG9seW1lckJlaGF2aW9yIFBhcGVySW5wdXRCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBQYXBlcklucHV0QmVoYXZpb3JJbXBsID0gewoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIEZpcmVkIHdoZW4gdGhlIGlucHV0IGNoYW5nZXMgZHVlIHRvIHVzZXIgaW50ZXJhY3Rpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAZXZlbnQgY2hhbmdlCiAgICAgICAgICovCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBsYWJlbCBmb3IgdGhpcyBpbnB1dC4gSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0bwogICAgICAgICAqIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlIGVsZW1lbnQsIGJpbmQgdGhpcyB0bwogICAgICAgICAqIGA8bGFiZWw+YCdzIGNvbnRlbnQgYW5kIGBoaWRkZW5gIHByb3BlcnR5LCBlLmcuCiAgICAgICAgICogYDxsYWJlbCBoaWRkZW4kPSJbWyFsYWJlbF1dIj5bW2xhYmVsXV08L2xhYmVsPmAgaW4geW91ciBgdGVtcGxhdGVgCiAgICAgICAgICovCiAgICAgICAgbGFiZWw6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgdmFsdWUgZm9yIHRoaXMgaW5wdXQuIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8KICAgICAgICAgKiBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kIHRoaXMgdG8KICAgICAgICAgKiB0aGUgYDxpcm9uLWlucHV0PmAncyBgYmluZFZhbHVlYAogICAgICAgICAqIHByb3BlcnR5LCBvciB0aGUgdmFsdWUgcHJvcGVydHkgb2YgeW91ciBpbnB1dCB0aGF0IGlzIGBub3RpZnk6dHJ1ZWAuCiAgICAgICAgICogQHR5cGUgeyp9CiAgICAgICAgICovCiAgICAgICAgdmFsdWU6IHtub3RpZnk6IHRydWUsIHR5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGRpc2FibGUgdGhpcyBpbnB1dC4gSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0bwogICAgICAgICAqIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlIGVsZW1lbnQsIGJpbmQgdGhpcyB0bwogICAgICAgICAqIGJvdGggdGhlIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAncyBhbmQgdGhlIGlucHV0J3MgYGRpc2FibGVkYCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBkaXNhYmxlZDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgdmFsdWUgaXMgaW52YWxpZC4gSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvcgogICAgICAgICAqIHRvIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlIGVsZW1lbnQsIGJpbmQgdGhpcyB0byBib3RoIHRoZQogICAgICAgICAqIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAncyBhbmQgdGhlIGlucHV0J3MgYGludmFsaWRgIHByb3BlcnR5LgogICAgICAgICAqCiAgICAgICAgICogSWYgYGF1dG9WYWxpZGF0ZWAgaXMgdHJ1ZSwgdGhlIGBpbnZhbGlkYCBhdHRyaWJ1dGUgaXMgbWFuYWdlZAogICAgICAgICAqIGF1dG9tYXRpY2FsbHksIHdoaWNoIGNhbiBjbG9iYmVyIGF0dGVtcHRzIHRvIG1hbmFnZSBpdCBtYW51YWxseS4KICAgICAgICAgKi8KICAgICAgICBpbnZhbGlkOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlLCBub3RpZnk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdGhpcyB0byBzcGVjaWZ5IHRoZSBwYXR0ZXJuIGFsbG93ZWQgYnkgYHByZXZlbnRJbnZhbGlkSW5wdXRgLiBJZgogICAgICAgICAqIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgYWxsb3dlZFBhdHRlcm5gCiAgICAgICAgICogcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgYWxsb3dlZFBhdHRlcm46IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgdHlwZSBvZiB0aGUgaW5wdXQuIFRoZSBzdXBwb3J0ZWQgdHlwZXMgYXJlIHRoZQogICAgICAgICAqIFtuYXRpdmUgaW5wdXQncwogICAgICAgICAqIHR5cGVzXShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9IVE1ML0VsZW1lbnQvaW5wdXQjRm9ybV88aW5wdXQ+X3R5cGVzKS4KICAgICAgICAgKiBJZiB5b3UncmUgdXNpbmcgUGFwZXJJbnB1dEJlaGF2aW9yIHRvIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlCiAgICAgICAgICogZWxlbWVudCwgYmluZCB0aGlzIHRvIHRoZSAoUG9seW1lciAxKSBgPGlucHV0IGlzPSJpcm9uLWlucHV0Ij5gJ3Mgb3IKICAgICAgICAgKiAoUG9seW1lciAyKQogICAgICAgICAqIGA8aXJvbi1pbnB1dD5gJ3MgYHR5cGVgIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIHR5cGU6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGF0YWxpc3Qgb2YgdGhlIGlucHV0IChpZiBhbnkpLiBUaGlzIHNob3VsZCBtYXRjaCB0aGUgaWQgb2YgYW4KICAgICAgICAgKiBleGlzdGluZyBgPGRhdGFsaXN0PmAuIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50CiAgICAgICAgICogeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQKICAgICAgICAgKiBpcz0iaXJvbi1pbnB1dCI+YCdzIGBsaXN0YCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBsaXN0OiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQSBwYXR0ZXJuIHRvIHZhbGlkYXRlIHRoZSBgaW5wdXRgIHdpdGguIElmIHlvdSdyZSB1c2luZwogICAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kCiAgICAgICAgICogdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBwYXR0ZXJuYCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBwYXR0ZXJuOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gbWFyayB0aGUgaW5wdXQgYXMgcmVxdWlyZWQuIElmIHlvdSdyZSB1c2luZwogICAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kCiAgICAgICAgICogdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGByZXF1aXJlZGAgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgcmVxdWlyZWQ6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZXJyb3IgbWVzc2FnZSB0byBkaXNwbGF5IHdoZW4gdGhlIGlucHV0IGlzIGludmFsaWQuIElmIHlvdSdyZSB1c2luZwogICAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LAogICAgICAgICAqIGJpbmQgdGhpcyB0byB0aGUgYDxwYXBlci1pbnB1dC1lcnJvcj5gJ3MgY29udGVudCwgaWYgdXNpbmcuCiAgICAgICAgICovCiAgICAgICAgZXJyb3JNZXNzYWdlOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gc2hvdyBhIGNoYXJhY3RlciBjb3VudGVyLgogICAgICAgICAqLwogICAgICAgIGNoYXJDb3VudGVyOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gZGlzYWJsZSB0aGUgZmxvYXRpbmcgbGFiZWwuIElmIHlvdSdyZSB1c2luZwogICAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kCiAgICAgICAgICogdGhpcyB0byB0aGUgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCdzIGBub0xhYmVsRmxvYXRgIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIG5vTGFiZWxGbG9hdDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGFsd2F5cyBmbG9hdCB0aGUgbGFiZWwuIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IKICAgICAgICAgKiB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlCiAgICAgICAgICogYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCdzIGBhbHdheXNGbG9hdExhYmVsYCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBhbHdheXNGbG9hdExhYmVsOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gYXV0by12YWxpZGF0ZSB0aGUgaW5wdXQgdmFsdWUuIElmIHlvdSdyZSB1c2luZwogICAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kCiAgICAgICAgICogdGhpcyB0byB0aGUgYDxwYXBlci1pbnB1dC1jb250YWluZXI+YCdzIGBhdXRvVmFsaWRhdGVgIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIGF1dG9WYWxpZGF0ZToge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIE5hbWUgb2YgdGhlIHZhbGlkYXRvciB0byB1c2UuIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8KICAgICAgICAgKiBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZSBlbGVtZW50LCBiaW5kIHRoaXMgdG8KICAgICAgICAgKiB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGB2YWxpZGF0b3JgIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIHZhbGlkYXRvcjoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8vIEhUTUxJbnB1dEVsZW1lbnQgYXR0cmlidXRlcyBmb3IgYmluZGluZyBpZiBuZWVkZWQKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBhdXRvY29tcGxldGVgCiAgICAgICAgICogcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgYXV0b2NvbXBsZXRlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ29mZid9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB5b3UncmUgdXNpbmcgUGFwZXJJbnB1dEJlaGF2aW9yIHRvIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlCiAgICAgICAgICogZWxlbWVudCwgYmluZCB0aGlzIHRvIHRoZSBgPGlucHV0IGlzPSJpcm9uLWlucHV0Ij5gJ3MgYGF1dG9mb2N1c2AKICAgICAgICAgKiBwcm9wZXJ0eS4KICAgICAgICAgKgogICAgICAgICAqIEB0eXBlIHshYm9vbGVhbn0KICAgICAgICAgKi8KICAgICAgICBhdXRvZm9jdXM6IHt0eXBlOiBCb29sZWFuLCBvYnNlcnZlcjogJ19hdXRvZm9jdXNDaGFuZ2VkJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgaW5wdXRtb2RlYAogICAgICAgICAqIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIGlucHV0bW9kZToge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBtaW5pbXVtIGxlbmd0aCBvZiB0aGUgaW5wdXQgdmFsdWUuCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBtaW5sZW5ndGhgCiAgICAgICAgICogcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgbWlubGVuZ3RoOiB7dHlwZTogTnVtYmVyfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG1heGltdW0gbGVuZ3RoIG9mIHRoZSBpbnB1dCB2YWx1ZS4KICAgICAgICAgKiBJZiB5b3UncmUgdXNpbmcgUGFwZXJJbnB1dEJlaGF2aW9yIHRvIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlCiAgICAgICAgICogZWxlbWVudCwgYmluZCB0aGlzIHRvIHRoZSBgPGlucHV0IGlzPSJpcm9uLWlucHV0Ij5gJ3MgYG1heGxlbmd0aGAKICAgICAgICAgKiBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBtYXhsZW5ndGg6IHt0eXBlOiBOdW1iZXJ9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbWluaW11bSAobnVtZXJpYyBvciBkYXRlLXRpbWUpIGlucHV0IHZhbHVlLgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgbWluYCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBtaW46IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbWF4aW11bSAobnVtZXJpYyBvciBkYXRlLXRpbWUpIGlucHV0IHZhbHVlLgogICAgICAgICAqIENhbiBiZSBhIFN0cmluZyAoZS5nLiBgIjIwMDAtMDEtMDEiYCkgb3IgYSBOdW1iZXIgKGUuZy4gYDJgKS4KICAgICAgICAgKiBJZiB5b3UncmUgdXNpbmcgUGFwZXJJbnB1dEJlaGF2aW9yIHRvIGltcGxlbWVudCB5b3VyIG93biBwYXBlci1pbnB1dC1saWtlCiAgICAgICAgICogZWxlbWVudCwgYmluZCB0aGlzIHRvIHRoZSBgPGlucHV0IGlzPSJpcm9uLWlucHV0Ij5gJ3MgYG1heGAgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgbWF4OiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogTGltaXRzIHRoZSBudW1lcmljIG9yIGRhdGUtdGltZSBpbmNyZW1lbnRzLgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgc3RlcGAgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgc3RlcDoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgbmFtZWAgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgbmFtZToge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIEEgcGxhY2Vob2xkZXIgc3RyaW5nIGluIGFkZGl0aW9uIHRvIHRoZSBsYWJlbC4gSWYgdGhpcyBpcyBzZXQsIHRoZSBsYWJlbAogICAgICAgICAqIHdpbGwgYWx3YXlzIGZsb2F0LgogICAgICAgICAqLwogICAgICAgIHBsYWNlaG9sZGVyOiB7CiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAvLyBuZWVkIHRvIHNldCBhIGRlZmF1bHQgc28gX2NvbXB1dGVBbHdheXNGbG9hdExhYmVsIGlzIHJ1bgogICAgICAgICAgdmFsdWU6ICcnCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGByZWFkb25seWAKICAgICAgICAgKiBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICByZWFkb25seToge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgc2l6ZWAgcHJvcGVydHkuCiAgICAgICAgICovCiAgICAgICAgc2l6ZToge3R5cGU6IE51bWJlcn0sCgogICAgICAgIC8vIE5vbnN0YW5kYXJkIGF0dHJpYnV0ZXMgZm9yIGJpbmRpbmcgaWYgbmVlZGVkCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgYXV0b2NhcGl0YWxpemVgCiAgICAgICAgICogcHJvcGVydHkuCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSB7c3RyaW5nfQogICAgICAgICAqLwogICAgICAgIGF1dG9jYXBpdGFsaXplOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ25vbmUnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBhdXRvY29ycmVjdGAKICAgICAgICAgKiBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBhdXRvY29ycmVjdDoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdvZmYnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBhdXRvc2F2ZWAKICAgICAgICAgKiBwcm9wZXJ0eSwgdXNlZCB3aXRoIHR5cGU9c2VhcmNoLgogICAgICAgICAqLwogICAgICAgIGF1dG9zYXZlOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgeW91J3JlIHVzaW5nIFBhcGVySW5wdXRCZWhhdmlvciB0byBpbXBsZW1lbnQgeW91ciBvd24gcGFwZXItaW5wdXQtbGlrZQogICAgICAgICAqIGVsZW1lbnQsIGJpbmQgdGhpcyB0byB0aGUgYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGByZXN1bHRzYCBwcm9wZXJ0eSwKICAgICAgICAgKiB1c2VkIHdpdGggdHlwZT1zZWFyY2guCiAgICAgICAgICovCiAgICAgICAgcmVzdWx0czoge3R5cGU6IE51bWJlcn0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlIGA8aW5wdXQgaXM9Imlyb24taW5wdXQiPmAncyBgYWNjZXB0YCBwcm9wZXJ0eSwKICAgICAgICAgKiB1c2VkIHdpdGggdHlwZT1maWxlLgogICAgICAgICAqLwogICAgICAgIGFjY2VwdDoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHlvdSdyZSB1c2luZyBQYXBlcklucHV0QmVoYXZpb3IgdG8gaW1wbGVtZW50IHlvdXIgb3duIHBhcGVyLWlucHV0LWxpa2UKICAgICAgICAgKiBlbGVtZW50LCBiaW5kIHRoaXMgdG8gdGhlYDxpbnB1dCBpcz0iaXJvbi1pbnB1dCI+YCdzIGBtdWx0aXBsZWAgcHJvcGVydHksCiAgICAgICAgICogdXNlZCB3aXRoIHR5cGU9ZmlsZS4KICAgICAgICAgKi8KICAgICAgICBtdWx0aXBsZToge3R5cGU6IEJvb2xlYW59LAoKICAgICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgICBfYXJpYURlc2NyaWJlZEJ5OiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJyd9LAoKICAgICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgICBfYXJpYUxhYmVsbGVkQnk6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnJ30sCgogICAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICAgIF9pbnB1dElkOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJyd9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsKICAgICAgICAnYWRkb24tYXR0YWNoZWQnOiAnX29uQWRkb25BdHRhY2hlZCcsCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHR5cGUgeyFPYmplY3R9CiAgICAgICAqLwogICAgICBrZXlCaW5kaW5nczogeydzaGlmdCt0YWI6a2V5ZG93bic6ICdfb25TaGlmdFRhYkRvd24nfSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBob3N0QXR0cmlidXRlczoge3RhYmluZGV4OiAwfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGEgcmVmZXJlbmNlIHRvIHRoZSBpbnB1dCBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshSFRNTEVsZW1lbnR9CiAgICAgICAqLwogICAgICBnZXQgaW5wdXRFbGVtZW50KCkgewogICAgICAgIC8vIENocm9tZSBnZW5lcmF0ZXMgYXVkaXQgZXJyb3JzIGlmIGFuIDxpbnB1dCB0eXBlPSJwYXNzd29yZCI+IGhhcyBhCiAgICAgICAgLy8gZHVwbGljYXRlIElELCB3aGljaCBpcyBhbG1vc3QgYWx3YXlzIHRydWUgaW4gU2hhZHkgRE9NLiBHZW5lcmF0ZQogICAgICAgIC8vIGEgdW5pcXVlIElEIGluc3RlYWQuCiAgICAgICAgaWYgKCF0aGlzLiQpIHsKICAgICAgICAgIHRoaXMuJCA9IHt9OwogICAgICAgIH0KICAgICAgICBpZiAoIXRoaXMuJC5pbnB1dCkgewogICAgICAgICAgdGhpcy5fZ2VuZXJhdGVJbnB1dElkKCk7CiAgICAgICAgICB0aGlzLiQuaW5wdXQgPSB0aGlzLiQkKCcjJyArIHRoaXMuX2lucHV0SWQpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy4kLmlucHV0OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgYSByZWZlcmVuY2UgdG8gdGhlIGZvY3VzYWJsZSBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshSFRNTEVsZW1lbnR9CiAgICAgICAqLwogICAgICBnZXQgX2ZvY3VzYWJsZUVsZW1lbnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaW5wdXRFbGVtZW50OwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBjcmVhdGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBUaGVzZSB0eXBlcyBoYXZlIHNvbWUgZGVmYXVsdCBwbGFjZWhvbGRlciB0ZXh0OyBvdmVybGFwcGluZwogICAgICAgIC8vIHRoZSBsYWJlbCBvbiB0b3Agb2YgaXQgbG9va3MgdGVycmlibGUuIEF1dG8tZmxvYXQgdGhlIGxhYmVsIGluIHRoaXMgY2FzZS4KICAgICAgICB0aGlzLl90eXBlc1RoYXRIYXZlVGV4dCA9CiAgICAgICAgICAgIFsnZGF0ZScsICdkYXRldGltZScsICdkYXRldGltZS1sb2NhbCcsICdtb250aCcsICd0aW1lJywgJ3dlZWsnLCAnZmlsZSddOwogICAgICB9LAoKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fdXBkYXRlQXJpYUxhYmVsbGVkQnkoKTsKCiAgICAgICAgLy8gSW4gdGhlIDIuMCB2ZXJzaW9uIG9mIHRoZSBlbGVtZW50LCB0aGlzIGlzIGhhbmRsZWQgaW4gYG9uSXJvbklucHV0UmVhZHlgLAogICAgICAgIC8vIGkuZS4gYWZ0ZXIgdGhlIG5hdGl2ZSBpbnB1dCBoYXMgZmluaXNoZWQgZGlzdHJpYnV0aW5nLiBJbiB0aGUgMS4wCiAgICAgICAgLy8gdmVyc2lvbiwgdGhlIGlucHV0IGlzIGluIHRoZSBzaGFkb3cgdHJlZSwgc28gaXQncyBhbHJlYWR5IGF2YWlsYWJsZS4KICAgICAgICBpZiAoIVBvbHltZXJFbGVtZW50ICYmIHRoaXMuaW5wdXRFbGVtZW50ICYmCiAgICAgICAgICAgIHRoaXMuX3R5cGVzVGhhdEhhdmVUZXh0LmluZGV4T2YodGhpcy5pbnB1dEVsZW1lbnQudHlwZSkgIT09IC0xKSB7CiAgICAgICAgICB0aGlzLmFsd2F5c0Zsb2F0TGFiZWwgPSB0cnVlOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9hcHBlbmRTdHJpbmdXaXRoU3BhY2U6IGZ1bmN0aW9uKHN0ciwgbW9yZSkgewogICAgICAgIGlmIChzdHIpIHsKICAgICAgICAgIHN0ciA9IHN0ciArICcgJyArIG1vcmU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHN0ciA9IG1vcmU7CiAgICAgICAgfQogICAgICAgIHJldHVybiBzdHI7CiAgICAgIH0sCgogICAgICBfb25BZGRvbkF0dGFjaGVkOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciB0YXJnZXQgPSBkb20oZXZlbnQpLnJvb3RUYXJnZXQ7CiAgICAgICAgaWYgKHRhcmdldC5pZCkgewogICAgICAgICAgdGhpcy5fYXJpYURlc2NyaWJlZEJ5ID0KICAgICAgICAgICAgICB0aGlzLl9hcHBlbmRTdHJpbmdXaXRoU3BhY2UodGhpcy5fYXJpYURlc2NyaWJlZEJ5LCB0YXJnZXQuaWQpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB2YXIgaWQgPSAncGFwZXItaW5wdXQtYWRkLW9uLScgKyBQYXBlcklucHV0SGVscGVyLk5leHRBZGRvbklEKys7CiAgICAgICAgICB0YXJnZXQuaWQgPSBpZDsKICAgICAgICAgIHRoaXMuX2FyaWFEZXNjcmliZWRCeSA9CiAgICAgICAgICAgICAgdGhpcy5fYXBwZW5kU3RyaW5nV2l0aFNwYWNlKHRoaXMuX2FyaWFEZXNjcmliZWRCeSwgaWQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBWYWxpZGF0ZXMgdGhlIGlucHV0IGVsZW1lbnQgYW5kIHNldHMgYW4gZXJyb3Igc3R5bGUgaWYgbmVlZGVkLgogICAgICAgKgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufQogICAgICAgKi8KICAgICAgdmFsaWRhdGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLmlucHV0RWxlbWVudC52YWxpZGF0ZSgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEZvcndhcmQgZm9jdXMgdG8gaW5wdXRFbGVtZW50LiBPdmVycmlkZW4gZnJvbSBJcm9uQ29udHJvbFN0YXRlLgogICAgICAgKi8KICAgICAgX2ZvY3VzQmx1ckhhbmRsZXI6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgSXJvbkNvbnRyb2xTdGF0ZS5fZm9jdXNCbHVySGFuZGxlci5jYWxsKHRoaXMsIGV2ZW50KTsKCiAgICAgICAgLy8gRm9yd2FyZCB0aGUgZm9jdXMgdG8gdGhlIG5lc3RlZCBpbnB1dC4KICAgICAgICBpZiAodGhpcy5mb2N1c2VkICYmICF0aGlzLl9zaGlmdFRhYlByZXNzZWQgJiYgdGhpcy5fZm9jdXNhYmxlRWxlbWVudCkgewogICAgICAgICAgdGhpcy5fZm9jdXNhYmxlRWxlbWVudC5mb2N1cygpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIYW5kbGVyIHRoYXQgaXMgY2FsbGVkIHdoZW4gYSBzaGlmdCt0YWIga2V5cHJlc3MgaXMgZGV0ZWN0ZWQgYnkgdGhlIG1lbnUuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Q3VzdG9tRXZlbnR9IGV2ZW50IEEga2V5IGNvbWJpbmF0aW9uIGV2ZW50LgogICAgICAgKi8KICAgICAgX29uU2hpZnRUYWJEb3duOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciBvbGRUYWJJbmRleCA9IHRoaXMuZ2V0QXR0cmlidXRlKCd0YWJpbmRleCcpOwogICAgICAgIHRoaXMuX3NoaWZ0VGFiUHJlc3NlZCA9IHRydWU7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgJy0xJyk7CiAgICAgICAgdGhpcy5hc3luYyhmdW5jdGlvbigpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCd0YWJpbmRleCcsIG9sZFRhYkluZGV4KTsKICAgICAgICAgIHRoaXMuX3NoaWZ0VGFiUHJlc3NlZCA9IGZhbHNlOwogICAgICAgIH0sIDEpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIElmIGBhdXRvVmFsaWRhdGVgIGlzIHRydWUsIHRoZW4gdmFsaWRhdGVzIHRoZSBlbGVtZW50LgogICAgICAgKi8KICAgICAgX2hhbmRsZUF1dG9WYWxpZGF0ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuYXV0b1ZhbGlkYXRlKQogICAgICAgICAgdGhpcy52YWxpZGF0ZSgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJlc3RvcmVzIHRoZSBjdXJzb3IgdG8gaXRzIG9yaWdpbmFsIHBvc2l0aW9uIGFmdGVyIHVwZGF0aW5nIHRoZSB2YWx1ZS4KICAgICAgICogQHBhcmFtIHtzdHJpbmd9IG5ld1ZhbHVlIFRoZSB2YWx1ZSB0aGF0IHNob3VsZCBiZSBzYXZlZC4KICAgICAgICovCiAgICAgIHVwZGF0ZVZhbHVlQW5kUHJlc2VydmVDYXJldDogZnVuY3Rpb24obmV3VmFsdWUpIHsKICAgICAgICAvLyBOb3QgYWxsIGVsZW1lbnRzIG1pZ2h0IGhhdmUgc2VsZWN0aW9uLCBhbmQgZXZlbiBpZiB0aGV5IGhhdmUgdGhlCiAgICAgICAgLy8gcmlnaHQgcHJvcGVydGllcywgYWNjZXNzaW5nIHRoZW0gbWlnaHQgdGhyb3cgYW4gZXhjZXB0aW9uIChsaWtlIGZvcgogICAgICAgIC8vIDxpbnB1dCB0eXBlPW51bWJlcj4pCiAgICAgICAgdHJ5IHsKICAgICAgICAgIHZhciBzdGFydCA9IHRoaXMuaW5wdXRFbGVtZW50LnNlbGVjdGlvblN0YXJ0OwogICAgICAgICAgdGhpcy52YWx1ZSA9IG5ld1ZhbHVlOwoKICAgICAgICAgIC8vIFRoZSBjdXJzb3IgYXV0b21hdGljYWxseSBqdW1wcyB0byB0aGUgZW5kIGFmdGVyIHJlLXNldHRpbmcgdGhlIHZhbHVlLAogICAgICAgICAgLy8gc28gcmVzdG9yZSBpdCB0byBpdHMgb3JpZ2luYWwgcG9zaXRpb24uCiAgICAgICAgICB0aGlzLmlucHV0RWxlbWVudC5zZWxlY3Rpb25TdGFydCA9IHN0YXJ0OwogICAgICAgICAgdGhpcy5pbnB1dEVsZW1lbnQuc2VsZWN0aW9uRW5kID0gc3RhcnQ7CiAgICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgICAgLy8gSnVzdCBzZXQgdGhlIHZhbHVlIGFuZCBnaXZlIHVwIG9uIHRoZSBjYXJldC4KICAgICAgICAgIHRoaXMudmFsdWUgPSBuZXdWYWx1ZTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfY29tcHV0ZUFsd2F5c0Zsb2F0TGFiZWw6IGZ1bmN0aW9uKGFsd2F5c0Zsb2F0TGFiZWwsIHBsYWNlaG9sZGVyKSB7CiAgICAgICAgcmV0dXJuIHBsYWNlaG9sZGVyIHx8IGFsd2F5c0Zsb2F0TGFiZWw7CiAgICAgIH0sCgogICAgICBfdXBkYXRlQXJpYUxhYmVsbGVkQnk6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBsYWJlbCA9IGRvbSh0aGlzLnJvb3QpLnF1ZXJ5U2VsZWN0b3IoJ2xhYmVsJyk7CiAgICAgICAgaWYgKCFsYWJlbCkgewogICAgICAgICAgdGhpcy5fYXJpYUxhYmVsbGVkQnkgPSAnJzsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdmFyIGxhYmVsbGVkQnk7CiAgICAgICAgaWYgKGxhYmVsLmlkKSB7CiAgICAgICAgICBsYWJlbGxlZEJ5ID0gbGFiZWwuaWQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGxhYmVsbGVkQnkgPSAncGFwZXItaW5wdXQtbGFiZWwtJyArIFBhcGVySW5wdXRIZWxwZXIuTmV4dExhYmVsSUQrKzsKICAgICAgICAgIGxhYmVsLmlkID0gbGFiZWxsZWRCeTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fYXJpYUxhYmVsbGVkQnkgPSBsYWJlbGxlZEJ5OwogICAgICB9LAoKICAgICAgX2dlbmVyYXRlSW5wdXRJZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLl9pbnB1dElkIHx8IHRoaXMuX2lucHV0SWQgPT09ICcnKSB7CiAgICAgICAgICB0aGlzLl9pbnB1dElkID0gJ2lucHV0LScgKyBQYXBlcklucHV0SGVscGVyLk5leHRJbnB1dElEKys7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX29uQ2hhbmdlOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIC8vIEluIHRoZSBTaGFkb3cgRE9NLCB0aGUgYGNoYW5nZWAgZXZlbnQgaXMgbm90IGxlYWtlZCBpbnRvIHRoZQogICAgICAgIC8vIGFuY2VzdG9yIHRyZWUsIHNvIHdlIG11c3QgZG8gdGhpcyBtYW51YWxseS4KICAgICAgICAvLyBTZWUKICAgICAgICAvLyBodHRwczovL3czYy5naXRodWIuaW8vd2ViY29tcG9uZW50cy9zcGVjL3NoYWRvdy8jZXZlbnRzLXRoYXQtYXJlLW5vdC1sZWFrZWQtaW50by1hbmNlc3Rvci10cmVlcy4KICAgICAgICBpZiAodGhpcy5zaGFkb3dSb290KSB7CiAgICAgICAgICB0aGlzLmZpcmUoCiAgICAgICAgICAgICAgZXZlbnQudHlwZSwKICAgICAgICAgICAgICB7c291cmNlRXZlbnQ6IGV2ZW50fSwKICAgICAgICAgICAgICB7bm9kZTogdGhpcywgYnViYmxlczogZXZlbnQuYnViYmxlcywgY2FuY2VsYWJsZTogZXZlbnQuY2FuY2VsYWJsZX0pOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9hdXRvZm9jdXNDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBGaXJlZm94IGRvZXNuJ3QgcmVzcGVjdCB0aGUgYXV0b2ZvY3VzIGF0dHJpYnV0ZSBpZiBpdCdzIGFwcGxpZWQgYWZ0ZXIKICAgICAgICAvLyB0aGUgcGFnZSBpcyBsb2FkZWQgKENocm9tZS9XZWJLaXQgZG8gcmVzcGVjdCBpdCksIHByZXZlbnRpbmcgYW4KICAgICAgICAvLyBhdXRvZm9jdXMgYXR0cmlidXRlIHNwZWNpZmllZCBpbiBtYXJrdXAgZnJvbSB0YWtpbmcgZWZmZWN0IHdoZW4gdGhlCiAgICAgICAgLy8gZWxlbWVudCBpcyB1cGdyYWRlZC4gQXMgYSB3b3JrYXJvdW5kLCBpZiB0aGUgYXV0b2ZvY3VzIHByb3BlcnR5IGlzIHNldCwKICAgICAgICAvLyBhbmQgdGhlIGZvY3VzIGhhc24ndCBhbHJlYWR5IGJlZW4gbW92ZWQgZWxzZXdoZXJlLCB3ZSB0YWtlIGZvY3VzLgogICAgICAgIGlmICh0aGlzLmF1dG9mb2N1cyAmJiB0aGlzLl9mb2N1c2FibGVFbGVtZW50KSB7CiAgICAgICAgICAvLyBJbiBJRSAxMSwgdGhlIGRlZmF1bHQgZG9jdW1lbnQuYWN0aXZlRWxlbWVudCBjYW4gYmUgdGhlIHBhZ2UncwogICAgICAgICAgLy8gb3V0ZXJtb3N0IGh0bWwgZWxlbWVudCwgYnV0IHRoZXJlIGFyZSBhbHNvIGNhc2VzICh1bmRlciB0aGUKICAgICAgICAgIC8vIHBvbHlmaWxsPykgaW4gd2hpY2ggdGhlIGFjdGl2ZUVsZW1lbnQgaXMgbm90IGEgcmVhbCBIVE1MRWxlbWVudCwgYnV0CiAgICAgICAgICAvLyBqdXN0IGEgcGxhaW4gb2JqZWN0LiBXZSBpZGVudGlmeSB0aGUgbGF0dGVyIGNhc2UgYXMgaGF2aW5nIG5vIHZhbGlkCiAgICAgICAgICAvLyBhY3RpdmVFbGVtZW50LgogICAgICAgICAgdmFyIGFjdGl2ZUVsZW1lbnQgPSBkb2N1bWVudC5hY3RpdmVFbGVtZW50OwogICAgICAgICAgdmFyIGlzQWN0aXZlRWxlbWVudFZhbGlkID0gYWN0aXZlRWxlbWVudCBpbnN0YW5jZW9mIEhUTUxFbGVtZW50OwoKICAgICAgICAgIC8vIEhhcyBzb21lIG90aGVyIGVsZW1lbnQgaGFzIGFscmVhZHkgdGFrZW4gdGhlIGZvY3VzPwogICAgICAgICAgdmFyIGlzU29tZUVsZW1lbnRBY3RpdmUgPSBpc0FjdGl2ZUVsZW1lbnRWYWxpZCAmJgogICAgICAgICAgICAgIGFjdGl2ZUVsZW1lbnQgIT09IGRvY3VtZW50LmJvZHkgJiYKICAgICAgICAgICAgICBhY3RpdmVFbGVtZW50ICE9PSBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQ7IC8qIElFIDExICovCiAgICAgICAgICBpZiAoIWlzU29tZUVsZW1lbnRBY3RpdmUpIHsKICAgICAgICAgICAgLy8gTm8gc3BlY2lmaWMgZWxlbWVudCBoYXMgdGFrZW4gdGhlIGZvY3VzIHlldCwgc28gd2UgY2FuIHRha2UgaXQuCiAgICAgICAgICAgIHRoaXMuX2ZvY3VzYWJsZUVsZW1lbnQuZm9jdXMoKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IFBhcGVySW5wdXRCZWhhdmlvciA9CiAgICAgICAgW0lyb25Db250cm9sU3RhdGUsIElyb25BMTF5S2V5c0JlaGF2aW9yLCBQYXBlcklucHV0QmVoYXZpb3JJbXBsXTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgIE1hdGVyaWFsIGRlc2lnbjogW1RleHQKICAgIGZpZWxkc10oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3RleHQtZmllbGRzLmh0bWwpCgogICAgYDxwYXBlci1pbnB1dD5gIGlzIGEgc2luZ2xlLWxpbmUgdGV4dCBmaWVsZCB3aXRoIE1hdGVyaWFsIERlc2lnbiBzdHlsaW5nLgoKICAgICAgICA8cGFwZXItaW5wdXQgbGFiZWw9IklucHV0IGxhYmVsIj48L3BhcGVyLWlucHV0PgoKICAgIEl0IG1heSBpbmNsdWRlIGFuIG9wdGlvbmFsIGVycm9yIG1lc3NhZ2Ugb3IgY2hhcmFjdGVyIGNvdW50ZXIuCgogICAgICAgIDxwYXBlci1pbnB1dCBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0ISIgbGFiZWw9IklucHV0CiAgICAgICAgbGFiZWwiPjwvcGFwZXItaW5wdXQ+IDxwYXBlci1pbnB1dCBjaGFyLWNvdW50ZXIgbGFiZWw9IklucHV0CiAgICAgICAgbGFiZWwiPjwvcGFwZXItaW5wdXQ+CgogICAgSXQgY2FuIGFsc28gaW5jbHVkZSBjdXN0b20gcHJlZml4IG9yIHN1ZmZpeCBlbGVtZW50cywgd2hpY2ggYXJlIGRpc3BsYXllZAogICAgYmVmb3JlIG9yIGFmdGVyIHRoZSB0ZXh0IGlucHV0IGl0c2VsZi4gSW4gb3JkZXIgZm9yIGFuIGVsZW1lbnQgdG8gYmUKICAgIGNvbnNpZGVyZWQgYXMgYSBwcmVmaXgsIGl0IG11c3QgaGF2ZSB0aGUgYHByZWZpeGAgYXR0cmlidXRlIChhbmQgc2ltaWxhcmx5CiAgICBmb3IgYHN1ZmZpeGApLgoKICAgICAgICA8cGFwZXItaW5wdXQgbGFiZWw9InRvdGFsIj4KICAgICAgICAgIDxkaXYgcHJlZml4PiQ8L2Rpdj4KICAgICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbiBzbG90PSJzdWZmaXgiIGljb249ImNsZWFyIj48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgIDwvcGFwZXItaW5wdXQ+CgogICAgQSBgcGFwZXItaW5wdXRgIGNhbiB1c2UgdGhlIG5hdGl2ZSBgdHlwZT1zZWFyY2hgIG9yIGB0eXBlPWZpbGVgIGZlYXR1cmVzLgogICAgSG93ZXZlciwgc2luY2Ugd2UgY2FuJ3QgY29udHJvbCB0aGUgbmF0aXZlIHN0eWxpbmcgb2YgdGhlIGlucHV0IChzZWFyY2ggaWNvbiwKICAgIGZpbGUgYnV0dG9uLCBkYXRlIHBsYWNlaG9sZGVyLCBldGMuKSwgaW4gdGhlc2UgY2FzZXMgdGhlIGxhYmVsIHdpbGwgYmUKICAgIGF1dG9tYXRpY2FsbHkgZmxvYXRlZC4gVGhlIGBwbGFjZWhvbGRlcmAgYXR0cmlidXRlIGNhbiBzdGlsbCBiZSB1c2VkIGZvcgogICAgYWRkaXRpb25hbCBpbmZvcm1hdGlvbmFsIHRleHQuCgogICAgICAgIDxwYXBlci1pbnB1dCBsYWJlbD0ic2VhcmNoISIgdHlwZT0ic2VhcmNoIgogICAgICAgICAgICBwbGFjZWhvbGRlcj0ic2VhcmNoIGZvciBjYXRzIiBhdXRvc2F2ZT0idGVzdCIgcmVzdWx0cz0iNSI+CiAgICAgICAgPC9wYXBlci1pbnB1dD4KCiAgICBTZWUgYFBvbHltZXIuUGFwZXJJbnB1dEJlaGF2aW9yYCBmb3IgbW9yZSBBUEkgZG9jcy4KCiAgICAjIyMgRm9jdXMKCiAgICBUbyBmb2N1cyBhIHBhcGVyLWlucHV0LCB5b3UgY2FuIGNhbGwgdGhlIG5hdGl2ZSBgZm9jdXMoKWAgbWV0aG9kIGFzIGxvbmcgYXMgdGhlCiAgICBwYXBlciBpbnB1dCBoYXMgYSB0YWIgaW5kZXguIFNpbWlsYXJseSwgYGJsdXIoKWAgd2lsbCBibHVyIHRoZSBlbGVtZW50LgoKICAgICMjIyBTdHlsaW5nCgogICAgU2VlIGBQb2x5bWVyLlBhcGVySW5wdXRDb250YWluZXJgIGZvciBhIGxpc3Qgb2YgY3VzdG9tIHByb3BlcnRpZXMgdXNlZCB0bwogICAgc3R5bGUgdGhpcyBlbGVtZW50LgoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1tcy1jbGVhcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBJbnRlcm5ldCBFeHBsb3JlciByZXZlYWwgYnV0dG9uICh0aGUgZXllYmFsbCkgfCB7fQoKICAgIEBlbGVtZW50IHBhcGVyLWlucHV0CiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgaXM6ICdwYXBlci1pbnB1dCcsCiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KCiAgICAgIDpob3N0KFtmb2N1c2VkXSkgewogICAgICAgIG91dGxpbmU6IG5vbmU7CiAgICAgIH0KCiAgICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICBpbnB1dCB7CiAgICAgICAgLyogRmlyZWZveCBzZXRzIGEgbWluLXdpZHRoIG9uIHRoZSBpbnB1dCwgd2hpY2ggY2FuIGNhdXNlIGxheW91dCBpc3N1ZXMgKi8KICAgICAgICBtaW4td2lkdGg6IDA7CiAgICAgIH0KCiAgICAgIC8qIEluIDEueCwgdGhlIDxpbnB1dD4gaXMgZGlzdHJpYnV0ZWQgdG8gcGFwZXItaW5wdXQtY29udGFpbmVyLCB3aGljaCBzdHlsZXMgaXQuCiAgICAgIEluIDIueCB0aGUgPGlyb24taW5wdXQ+IGlzIGRpc3RyaWJ1dGVkIHRvIHBhcGVyLWlucHV0LWNvbnRhaW5lciwgd2hpY2ggc3R5bGVzCiAgICAgIGl0LCBidXQgaW4gb3JkZXIgZm9yIHRoaXMgdG8gd29yayBjb3JyZWN0bHksIHdlIG5lZWQgdG8gcmVzZXQgc29tZQogICAgICBvZiB0aGUgbmF0aXZlIGlucHV0J3MgcHJvcGVydGllcyB0byBpbmhlcml0IChmcm9tIHRoZSBpcm9uLWlucHV0KSAqLwogICAgICBpcm9uLWlucHV0ID4gaW5wdXQgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1zaGFyZWQtaW5wdXQtc3R5bGU7CiAgICAgICAgZm9udC1mYW1pbHk6IGluaGVyaXQ7CiAgICAgICAgZm9udC13ZWlnaHQ6IGluaGVyaXQ7CiAgICAgICAgZm9udC1zaXplOiBpbmhlcml0OwogICAgICAgIGxldHRlci1zcGFjaW5nOiBpbmhlcml0OwogICAgICAgIHdvcmQtc3BhY2luZzogaW5oZXJpdDsKICAgICAgICBsaW5lLWhlaWdodDogaW5oZXJpdDsKICAgICAgICB0ZXh0LXNoYWRvdzogaW5oZXJpdDsKICAgICAgICBjb2xvcjogaW5oZXJpdDsKICAgICAgICBjdXJzb3I6IGluaGVyaXQ7CiAgICAgIH0KCiAgICAgIGlucHV0OmRpc2FibGVkIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQtZGlzYWJsZWQ7CiAgICAgIH0KCiAgICAgIGlucHV0Ojotd2Via2l0LW91dGVyLXNwaW4tYnV0dG9uLAogICAgICBpbnB1dDo6LXdlYmtpdC1pbm5lci1zcGluLWJ1dHRvbiB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0LXdlYmtpdC1zcGlubmVyOwogICAgICB9CgogICAgICBpbnB1dDo6LXdlYmtpdC1jbGVhci1idXR0b24gewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC13ZWJraXQtY2xlYXI7CiAgICAgIH0KCiAgICAgIGlucHV0Ojotd2Via2l0LWNhbGVuZGFyLXBpY2tlci1pbmRpY2F0b3IgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dC13ZWJraXQtY2FsZW5kYXItcGlja2VyLWluZGljYXRvcjsKICAgICAgfQoKICAgICAgaW5wdXQ6Oi13ZWJraXQtaW5wdXQtcGxhY2Vob2xkZXIgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItY29sb3IsIHZhcigtLXNlY29uZGFyeS10ZXh0LWNvbG9yKSk7CiAgICAgIH0KCiAgICAgIGlucHV0Oi1tb3otcGxhY2Vob2xkZXIgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItY29sb3IsIHZhcigtLXNlY29uZGFyeS10ZXh0LWNvbG9yKSk7CiAgICAgIH0KCiAgICAgIGlucHV0OjotbW96LXBsYWNlaG9sZGVyIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWNvbG9yLCB2YXIoLS1zZWNvbmRhcnktdGV4dC1jb2xvcikpOwogICAgICB9CgogICAgICBpbnB1dDo6LW1zLWNsZWFyIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItbXMtY2xlYXI7CiAgICAgIH0KCiAgICAgIGlucHV0OjotbXMtcmV2ZWFsIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pbnB1dC1jb250YWluZXItbXMtcmV2ZWFsOwogICAgICB9CgogICAgICBpbnB1dDotbXMtaW5wdXQtcGxhY2Vob2xkZXIgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pbnB1dC1jb250YWluZXItY29sb3IsIHZhcigtLXNlY29uZGFyeS10ZXh0LWNvbG9yKSk7CiAgICAgIH0KCiAgICAgIGxhYmVsIHsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8cGFwZXItaW5wdXQtY29udGFpbmVyIGlkPSJjb250YWluZXIiIG5vLWxhYmVsLWZsb2F0PSJbW25vTGFiZWxGbG9hdF1dIiBhbHdheXMtZmxvYXQtbGFiZWw9IltbX2NvbXB1dGVBbHdheXNGbG9hdExhYmVsKGFsd2F5c0Zsb2F0TGFiZWwscGxhY2Vob2xkZXIpXV0iIGF1dG8tdmFsaWRhdGUkPSJbW2F1dG9WYWxpZGF0ZV1dIiBkaXNhYmxlZCQ9IltbZGlzYWJsZWRdXSIgaW52YWxpZD0iW1tpbnZhbGlkXV0iPgoKICAgICAgPHNsb3QgbmFtZT0icHJlZml4IiBzbG90PSJwcmVmaXgiPjwvc2xvdD4KCiAgICAgIDxsYWJlbCBoaWRkZW4kPSJbWyFsYWJlbF1dIiBhcmlhLWhpZGRlbj0idHJ1ZSIgZm9yJD0iW1tfaW5wdXRJZF1dIiBzbG90PSJsYWJlbCI+W1tsYWJlbF1dPC9sYWJlbD4KCiAgICAgIDwhLS0gTmVlZCB0byBiaW5kIG1heGxlbmd0aCBzbyB0aGF0IHRoZSBwYXBlci1pbnB1dC1jaGFyLWNvdW50ZXIgd29ya3MgY29ycmVjdGx5IC0tPgogICAgICA8aXJvbi1pbnB1dCBiaW5kLXZhbHVlPSJ7e3ZhbHVlfX0iIHNsb3Q9ImlucHV0IiBjbGFzcz0iaW5wdXQtZWxlbWVudCIgaWQkPSJbW19pbnB1dElkXV0iIG1heGxlbmd0aCQ9IltbbWF4bGVuZ3RoXV0iIGFsbG93ZWQtcGF0dGVybj0iW1thbGxvd2VkUGF0dGVybl1dIiBpbnZhbGlkPSJ7e2ludmFsaWR9fSIgdmFsaWRhdG9yPSJbW3ZhbGlkYXRvcl1dIj4KICAgICAgICA8aW5wdXQgYXJpYS1sYWJlbGxlZGJ5JD0iW1tfYXJpYUxhYmVsbGVkQnldXSIgYXJpYS1kZXNjcmliZWRieSQ9IltbX2FyaWFEZXNjcmliZWRCeV1dIiBkaXNhYmxlZCQ9IltbZGlzYWJsZWRdXSIgdGl0bGUkPSJbW3RpdGxlXV0iIHR5cGUkPSJbW3R5cGVdXSIgcGF0dGVybiQ9IltbcGF0dGVybl1dIiByZXF1aXJlZCQ9IltbcmVxdWlyZWRdXSIgYXV0b2NvbXBsZXRlJD0iW1thdXRvY29tcGxldGVdXSIgYXV0b2ZvY3VzJD0iW1thdXRvZm9jdXNdXSIgaW5wdXRtb2RlJD0iW1tpbnB1dG1vZGVdXSIgbWlubGVuZ3RoJD0iW1ttaW5sZW5ndGhdXSIgbWF4bGVuZ3RoJD0iW1ttYXhsZW5ndGhdXSIgbWluJD0iW1ttaW5dXSIgbWF4JD0iW1ttYXhdXSIgc3RlcCQ9Iltbc3RlcF1dIiBuYW1lJD0iW1tuYW1lXV0iIHBsYWNlaG9sZGVyJD0iW1twbGFjZWhvbGRlcl1dIiByZWFkb25seSQ9IltbcmVhZG9ubHldXSIgbGlzdCQ9IltbbGlzdF1dIiBzaXplJD0iW1tzaXplXV0iIGF1dG9jYXBpdGFsaXplJD0iW1thdXRvY2FwaXRhbGl6ZV1dIiBhdXRvY29ycmVjdCQ9IltbYXV0b2NvcnJlY3RdXSIgb24tY2hhbmdlPSJfb25DaGFuZ2UiIHRhYmluZGV4JD0iW1t0YWJJbmRleF1dIiBhdXRvc2F2ZSQ9IltbYXV0b3NhdmVdXSIgcmVzdWx0cyQ9IltbcmVzdWx0c11dIiBhY2NlcHQkPSJbW2FjY2VwdF1dIiBtdWx0aXBsZSQ9IltbbXVsdGlwbGVdXSIgcm9sZSQ9IltbaW5wdXRSb2xlXV0iIGFyaWEtaGFzcG9wdXAkPSJbW2lucHV0QXJpYUhhc3BvcHVwXV0iPgogICAgICA8L2lyb24taW5wdXQ+CgogICAgICA8c2xvdCBuYW1lPSJzdWZmaXgiIHNsb3Q9InN1ZmZpeCI+PC9zbG90PgoKICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW2Vycm9yTWVzc2FnZV1dIj4KICAgICAgICA8cGFwZXItaW5wdXQtZXJyb3IgYXJpYS1saXZlPSJhc3NlcnRpdmUiIHNsb3Q9ImFkZC1vbiI+W1tlcnJvck1lc3NhZ2VdXTwvcGFwZXItaW5wdXQtZXJyb3I+CiAgICAgIDwvdGVtcGxhdGU+CgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbY2hhckNvdW50ZXJdXSI+CiAgICAgICAgPHBhcGVyLWlucHV0LWNoYXItY291bnRlciBzbG90PSJhZGQtb24iPjwvcGFwZXItaW5wdXQtY2hhci1jb3VudGVyPgogICAgICA8L3RlbXBsYXRlPgoKICAgIDwvcGFwZXItaW5wdXQtY29udGFpbmVyPgogIGAsCgogICAgICBiZWhhdmlvcnM6IFtQYXBlcklucHV0QmVoYXZpb3IsIElyb25Gb3JtRWxlbWVudEJlaGF2aW9yXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICB2YWx1ZTogewogICAgICAgICAgLy8gUmVxdWlyZWQgZm9yIHRoZSBjb3JyZWN0IFR5cGVTY3JpcHQgdHlwZS1nZW5lcmF0aW9uCiAgICAgICAgICB0eXBlOiBTdHJpbmcKICAgICAgICB9LAoKICAgICAgICBpbnB1dFJvbGU6IHsKICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgIHZhbHVlOiB1bmRlZmluZWQsCiAgICAgICAgfSwKCiAgICAgICAgaW5wdXRBcmlhSGFzcG9wdXA6IHsKICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgIHZhbHVlOiB1bmRlZmluZWQsCiAgICAgICAgfSwKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGEgcmVmZXJlbmNlIHRvIHRoZSBmb2N1c2FibGUgZWxlbWVudC4gT3ZlcnJpZGRlbiBmcm9tCiAgICAgICAqIFBhcGVySW5wdXRCZWhhdmlvciB0byBjb3JyZWN0bHkgZm9jdXMgdGhlIG5hdGl2ZSBpbnB1dC4KICAgICAgICoKICAgICAgICogQHJldHVybiB7IUhUTUxFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2V0IF9mb2N1c2FibGVFbGVtZW50KCkgewogICAgICAgIHJldHVybiB0aGlzLmlucHV0RWxlbWVudC5faW5wdXRFbGVtZW50OwogICAgICB9LAoKICAgICAgLy8gTm90ZTogVGhpcyBldmVudCBpcyBvbmx5IGF2YWlsYWJsZSBpbiB0aGUgMS4wIHZlcnNpb24gb2YgdGhpcyBlbGVtZW50LgogICAgICAvLyBJbiAyLjAsIHRoZSBmdW5jdGlvbmFsaXR5IG9mIGBfb25Jcm9uSW5wdXRSZWFkeWAgaXMgZG9uZSBpbgogICAgICAvLyBQYXBlcklucHV0QmVoYXZpb3I6OmF0dGFjaGVkLgogICAgICBsaXN0ZW5lcnM6IHsnaXJvbi1pbnB1dC1yZWFkeSc6ICdfb25Jcm9uSW5wdXRSZWFkeSd9LAoKICAgICAgX29uSXJvbklucHV0UmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIEV2ZW4gdGhvdWdoIHRoaXMgaXMgb25seSB1c2VkIGluIHRoZSBuZXh0IGxpbmUsIHNhdmUgdGhpcyBmb3IKICAgICAgICAvLyBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eSwgc2luY2UgdGhlIG5hdGl2ZSBpbnB1dCBoYWQgdGhpcyBJRCB1bnRpbCAyLjAuNS4KICAgICAgICBpZiAoIXRoaXMuJC5uYXRpdmVJbnB1dCkgewogICAgICAgICAgdGhpcy4kLm5hdGl2ZUlucHV0ID0gLyoqIEB0eXBlIHshRWxlbWVudH0gKi8gKHRoaXMuJCQoJ2lucHV0JykpOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5pbnB1dEVsZW1lbnQgJiYKICAgICAgICAgICAgdGhpcy5fdHlwZXNUaGF0SGF2ZVRleHQuaW5kZXhPZih0aGlzLiQubmF0aXZlSW5wdXQudHlwZSkgIT09IC0xKSB7CiAgICAgICAgICB0aGlzLmFsd2F5c0Zsb2F0TGFiZWwgPSB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLy8gT25seSB2YWxpZGF0ZSB3aGVuIGF0dGFjaGVkIGlmIHRoZSBpbnB1dCBhbHJlYWR5IGhhcyBhIHZhbHVlLgogICAgICAgIGlmICghIXRoaXMuaW5wdXRFbGVtZW50LmJpbmRWYWx1ZSkgewogICAgICAgICAgdGhpcy4kLmNvbnRhaW5lci5faGFuZGxlVmFsdWVBbmRBdXRvVmFsaWRhdGUodGhpcy5pbnB1dEVsZW1lbnQpOwogICAgICAgIH0KICAgICAgfSwKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgYDxpcm9uLWRyb3Bkb3duPmAgaXMgYSBnZW5lcmFsaXplZCBlbGVtZW50IHRoYXQgaXMgdXNlZnVsIHdoZW4geW91IGhhdmUKICAgIGhpZGRlbiBjb250ZW50IChgZHJvcGRvd24tY29udGVudGApIHRoYXQgaXMgcmV2ZWFsZWQgZHVlIHRvIHNvbWUgY2hhbmdlIGluCiAgICBzdGF0ZSB0aGF0IHNob3VsZCBjYXVzZSBpdCB0byBkbyBzby4KCiAgICBOb3RlIHRoYXQgdGhpcyBpcyBhIGxvdy1sZXZlbCBlbGVtZW50IGludGVuZGVkIHRvIGJlIHVzZWQgYXMgcGFydCBvZiBvdGhlcgogICAgY29tcG9zaXRlIGVsZW1lbnRzIHRoYXQgY2F1c2UgZHJvcGRvd25zIHRvIGJlIHJldmVhbGVkLgoKICAgIEV4YW1wbGVzIG9mIGVsZW1lbnRzIHRoYXQgbWlnaHQgYmUgaW1wbGVtZW50ZWQgdXNpbmcgYW4gYGlyb24tZHJvcGRvd25gCiAgICBpbmNsdWRlIGNvbWJvYm94ZXMsIG1lbnVidXR0b25zLCBzZWxlY3RzLiBUaGUgbGlzdCBnb2VzIG9uLgoKICAgIFRoZSBgPGlyb24tZHJvcGRvd24+YCBlbGVtZW50IGV4cG9zZXMgYXR0cmlidXRlcyB0aGF0IGFsbG93IHRoZSBwb3NpdGlvbgogICAgb2YgdGhlIGBkcm9wZG93bi1jb250ZW50YCByZWxhdGl2ZSB0byB0aGUgYGRyb3Bkb3duLXRyaWdnZXJgIHRvIGJlCiAgICBjb25maWd1cmVkLgoKICAgICAgICA8aXJvbi1kcm9wZG93biBob3Jpem9udGFsLWFsaWduPSJyaWdodCIgdmVydGljYWwtYWxpZ249InRvcCI+CiAgICAgICAgICA8ZGl2IHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiPkhlbGxvITwvZGl2PgogICAgICAgIDwvaXJvbi1kcm9wZG93bj4KCiAgICBJbiB0aGUgYWJvdmUgZXhhbXBsZSwgdGhlIGA8ZGl2PmAgYXNzaWduZWQgdG8gdGhlIGBkcm9wZG93bi1jb250ZW50YCBzbG90IHdpbGwKICAgIGJlIGhpZGRlbiB1bnRpbCB0aGUgZHJvcGRvd24gZWxlbWVudCBoYXMgYG9wZW5lZGAgc2V0IHRvIHRydWUsIG9yIHdoZW4gdGhlCiAgICBgb3BlbmAgbWV0aG9kIGlzIGNhbGxlZCBvbiB0aGUgZWxlbWVudC4KCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgcG9zaXRpb246IGZpeGVkOwogICAgICB9CgogICAgICAjY29udGVudFdyYXBwZXIgOjpzbG90dGVkKCopIHsKICAgICAgICBvdmVyZmxvdzogYXV0bzsKICAgICAgfQoKICAgICAgI2NvbnRlbnRXcmFwcGVyLmFuaW1hdGluZyA6OnNsb3R0ZWQoKikgewogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPGRpdiBpZD0iY29udGVudFdyYXBwZXIiPgogICAgICA8c2xvdCBpZD0iY29udGVudCIgbmFtZT0iZHJvcGRvd24tY29udGVudCI+PC9zbG90PgogICAgPC9kaXY+CmAsCgogICAgICBpczogJ2lyb24tZHJvcGRvd24nLAoKICAgICAgYmVoYXZpb3JzOiBbCiAgICAgICAgSXJvbkNvbnRyb2xTdGF0ZSwKICAgICAgICBJcm9uQTExeUtleXNCZWhhdmlvciwKICAgICAgICBJcm9uT3ZlcmxheUJlaGF2aW9yLAogICAgICAgIE5lb25BbmltYXRpb25SdW5uZXJCZWhhdmlvcgogICAgICBdLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBvcmllbnRhdGlvbiBhZ2FpbnN0IHdoaWNoIHRvIGFsaWduIHRoZSBkcm9wZG93biBjb250ZW50CiAgICAgICAgICogaG9yaXpvbnRhbGx5IHJlbGF0aXZlIHRvIHRoZSBkcm9wZG93biB0cmlnZ2VyLgogICAgICAgICAqIE92ZXJyaWRkZW4gZnJvbSBgUG9seW1lci5Jcm9uRml0QmVoYXZpb3JgLgogICAgICAgICAqLwogICAgICAgIGhvcml6b250YWxBbGlnbjoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdsZWZ0JywgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG9yaWVudGF0aW9uIGFnYWluc3Qgd2hpY2ggdG8gYWxpZ24gdGhlIGRyb3Bkb3duIGNvbnRlbnQKICAgICAgICAgKiB2ZXJ0aWNhbGx5IHJlbGF0aXZlIHRvIHRoZSBkcm9wZG93biB0cmlnZ2VyLgogICAgICAgICAqIE92ZXJyaWRkZW4gZnJvbSBgUG9seW1lci5Jcm9uRml0QmVoYXZpb3JgLgogICAgICAgICAqLwogICAgICAgIHZlcnRpY2FsQWxpZ246IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAndG9wJywgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQW4gYW5pbWF0aW9uIGNvbmZpZy4gSWYgcHJvdmlkZWQsIHRoaXMgd2lsbCBiZSB1c2VkIHRvIGFuaW1hdGUgdGhlCiAgICAgICAgICogb3BlbmluZyBvZiB0aGUgZHJvcGRvd24uIFBhc3MgYW4gQXJyYXkgZm9yIG11bHRpcGxlIGFuaW1hdGlvbnMuCiAgICAgICAgICogU2VlIGBuZW9uLWFuaW1hdGlvbmAgZG9jdW1lbnRhdGlvbiBmb3IgbW9yZSBhbmltYXRpb24gY29uZmlndXJhdGlvbgogICAgICAgICAqIGRldGFpbHMuCiAgICAgICAgICovCiAgICAgICAgb3BlbkFuaW1hdGlvbkNvbmZpZzoge3R5cGU6IE9iamVjdH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEFuIGFuaW1hdGlvbiBjb25maWcuIElmIHByb3ZpZGVkLCB0aGlzIHdpbGwgYmUgdXNlZCB0byBhbmltYXRlIHRoZQogICAgICAgICAqIGNsb3Npbmcgb2YgdGhlIGRyb3Bkb3duLiBQYXNzIGFuIEFycmF5IGZvciBtdWx0aXBsZSBhbmltYXRpb25zLgogICAgICAgICAqIFNlZSBgbmVvbi1hbmltYXRpb25gIGRvY3VtZW50YXRpb24gZm9yIG1vcmUgYW5pbWF0aW9uIGNvbmZpZ3VyYXRpb24KICAgICAgICAgKiBkZXRhaWxzLgogICAgICAgICAqLwogICAgICAgIGNsb3NlQW5pbWF0aW9uQ29uZmlnOiB7dHlwZTogT2JqZWN0fSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgcHJvdmlkZWQsIHRoaXMgd2lsbCBiZSB0aGUgZWxlbWVudCB0aGF0IHdpbGwgYmUgZm9jdXNlZCB3aGVuCiAgICAgICAgICogdGhlIGRyb3Bkb3duIG9wZW5zLgogICAgICAgICAqLwogICAgICAgIGZvY3VzVGFyZ2V0OiB7dHlwZTogT2JqZWN0fSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gZGlzYWJsZSBhbmltYXRpb25zIHdoZW4gb3BlbmluZyBhbmQgY2xvc2luZyB0aGUKICAgICAgICAgKiBkcm9wZG93bi4KICAgICAgICAgKi8KICAgICAgICBub0FuaW1hdGlvbnM6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCeSBkZWZhdWx0LCB0aGUgZHJvcGRvd24gd2lsbCBjb25zdHJhaW4gc2Nyb2xsaW5nIG9uIHRoZSBwYWdlCiAgICAgICAgICogdG8gaXRzZWxmIHdoZW4gb3BlbmVkLgogICAgICAgICAqIFNldCB0byB0cnVlIGluIG9yZGVyIHRvIHByZXZlbnQgc2Nyb2xsIGZyb20gYmVpbmcgY29uc3RyYWluZWQKICAgICAgICAgKiB0byB0aGUgZHJvcGRvd24gd2hlbiBpdCBvcGVucy4KICAgICAgICAgKiBUaGlzIHByb3BlcnR5IGlzIGEgc2hvcnRjdXQgdG8gc2V0IGBzY3JvbGxBY3Rpb25gIHRvIGxvY2sgb3IgcmVmaXQuCiAgICAgICAgICogUHJlZmVyIGRpcmVjdGx5IHNldHRpbmcgdGhlIGBzY3JvbGxBY3Rpb25gIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIGFsbG93T3V0c2lkZVNjcm9sbDoKICAgICAgICAgICAge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZSwgb2JzZXJ2ZXI6ICdfYWxsb3dPdXRzaWRlU2Nyb2xsQ2hhbmdlZCd9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsnbmVvbi1hbmltYXRpb24tZmluaXNoJzogJ19vbk5lb25BbmltYXRpb25GaW5pc2gnfSwKCiAgICAgIG9ic2VydmVyczogWwogICAgICAgICdfdXBkYXRlT3ZlcmxheVBvc2l0aW9uKHBvc2l0aW9uVGFyZ2V0LCB2ZXJ0aWNhbEFsaWduLCBob3Jpem9udGFsQWxpZ24sIHZlcnRpY2FsT2Zmc2V0LCBob3Jpem9udGFsT2Zmc2V0KScKICAgICAgXSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgZWxlbWVudCB0aGF0IGlzIGNvbnRhaW5lZCBieSB0aGUgZHJvcGRvd24sIGlmIGFueS4KICAgICAgICovCiAgICAgIGdldCBjb250YWluZWRFbGVtZW50KCkgewogICAgICAgIC8vIFBvbHltZXIgMi54IHJldHVybnMgc2xvdC5hc3NpZ25lZE5vZGVzIHdoaWNoIGNhbiBjb250YWluIHRleHQgbm9kZXMuCiAgICAgICAgdmFyIG5vZGVzID0gZG9tKHRoaXMuJC5jb250ZW50KS5nZXREaXN0cmlidXRlZE5vZGVzKCk7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBub2Rlcy5sZW5ndGg7IGkgPCBsOyBpKyspIHsKICAgICAgICAgIGlmIChub2Rlc1tpXS5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpIHsKICAgICAgICAgICAgcmV0dXJuIG5vZGVzW2ldOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIHJlYWR5OiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBFbnN1cmUgc2Nyb2xsQWN0aW9uIGlzIHNldC4KICAgICAgICBpZiAoIXRoaXMuc2Nyb2xsQWN0aW9uKSB7CiAgICAgICAgICB0aGlzLnNjcm9sbEFjdGlvbiA9IHRoaXMuYWxsb3dPdXRzaWRlU2Nyb2xsID8gJ3JlZml0JyA6ICdsb2NrJzsKICAgICAgICB9CiAgICAgICAgdGhpcy5fcmVhZGllZCA9IHRydWU7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLnNpemluZ1RhcmdldCB8fCB0aGlzLnNpemluZ1RhcmdldCA9PT0gdGhpcykgewogICAgICAgICAgdGhpcy5zaXppbmdUYXJnZXQgPSB0aGlzLmNvbnRhaW5lZEVsZW1lbnQgfHwgdGhpczsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5jYW5jZWxBbmltYXRpb24oKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDYWxsZWQgd2hlbiB0aGUgdmFsdWUgb2YgYG9wZW5lZGAgY2hhbmdlcy4KICAgICAgICogT3ZlcnJpZGRlbiBmcm9tIGBJcm9uT3ZlcmxheUJlaGF2aW9yYAogICAgICAgKi8KICAgICAgX29wZW5lZENoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm9wZW5lZCAmJiB0aGlzLmRpc2FibGVkKSB7CiAgICAgICAgICB0aGlzLmNhbmNlbCgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLmNhbmNlbEFuaW1hdGlvbigpOwogICAgICAgICAgdGhpcy5fdXBkYXRlQW5pbWF0aW9uQ29uZmlnKCk7CiAgICAgICAgICBJcm9uT3ZlcmxheUJlaGF2aW9ySW1wbC5fb3BlbmVkQ2hhbmdlZC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKi8KICAgICAgX3JlbmRlck9wZW5lZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLm5vQW5pbWF0aW9ucyAmJiB0aGlzLmFuaW1hdGlvbkNvbmZpZy5vcGVuKSB7CiAgICAgICAgICB0aGlzLiQuY29udGVudFdyYXBwZXIuY2xhc3NMaXN0LmFkZCgnYW5pbWF0aW5nJyk7CiAgICAgICAgICB0aGlzLnBsYXlBbmltYXRpb24oJ29wZW4nKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgSXJvbk92ZXJsYXlCZWhhdmlvckltcGwuX3JlbmRlck9wZW5lZC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKi8KICAgICAgX3JlbmRlckNsb3NlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLm5vQW5pbWF0aW9ucyAmJiB0aGlzLmFuaW1hdGlvbkNvbmZpZy5jbG9zZSkgewogICAgICAgICAgdGhpcy4kLmNvbnRlbnRXcmFwcGVyLmNsYXNzTGlzdC5hZGQoJ2FuaW1hdGluZycpOwogICAgICAgICAgdGhpcy5wbGF5QW5pbWF0aW9uKCdjbG9zZScpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBJcm9uT3ZlcmxheUJlaGF2aW9ySW1wbC5fcmVuZGVyQ2xvc2VkLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbGxlZCB3aGVuIGFuaW1hdGlvbiBmaW5pc2hlcyBvbiB0aGUgZHJvcGRvd24gKHdoZW4gb3BlbmluZyBvcgogICAgICAgKiBjbG9zaW5nKS4gUmVzcG9uc2libGUgZm9yICJjb21wbGV0aW5nIiB0aGUgcHJvY2VzcyBvZiBvcGVuaW5nIG9yCiAgICAgICAqIGNsb3NpbmcgdGhlIGRyb3Bkb3duIGJ5IHBvc2l0aW9uaW5nIGl0IG9yIHNldHRpbmcgaXRzIGRpc3BsYXkgdG8KICAgICAgICogbm9uZS4KICAgICAgICovCiAgICAgIF9vbk5lb25BbmltYXRpb25GaW5pc2g6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuJC5jb250ZW50V3JhcHBlci5jbGFzc0xpc3QucmVtb3ZlKCdhbmltYXRpbmcnKTsKICAgICAgICBpZiAodGhpcy5vcGVuZWQpIHsKICAgICAgICAgIHRoaXMuX2ZpbmlzaFJlbmRlck9wZW5lZCgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9maW5pc2hSZW5kZXJDbG9zZWQoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ29uc3RydWN0cyB0aGUgZmluYWwgYW5pbWF0aW9uIGNvbmZpZyBmcm9tIGRpZmZlcmVudCBwcm9wZXJ0aWVzIHVzZWQKICAgICAgICogdG8gY29uZmlndXJlIHNwZWNpZmljIHBhcnRzIG9mIHRoZSBvcGVuaW5nIGFuZCBjbG9zaW5nIGFuaW1hdGlvbnMuCiAgICAgICAqLwogICAgICBfdXBkYXRlQW5pbWF0aW9uQ29uZmlnOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBVcGRhdGUgdGhlIGFuaW1hdGlvbiBub2RlIHRvIGJlIHRoZSBjb250YWluZWRFbGVtZW50LgogICAgICAgIHZhciBhbmltYXRpb25Ob2RlID0gdGhpcy5jb250YWluZWRFbGVtZW50OwogICAgICAgIHZhciBhbmltYXRpb25zID0gW10uY29uY2F0KHRoaXMub3BlbkFuaW1hdGlvbkNvbmZpZyB8fCBbXSkKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAuY29uY2F0KHRoaXMuY2xvc2VBbmltYXRpb25Db25maWcgfHwgW10pOwogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgYW5pbWF0aW9ucy5sZW5ndGg7IGkrKykgewogICAgICAgICAgYW5pbWF0aW9uc1tpXS5ub2RlID0gYW5pbWF0aW9uTm9kZTsKICAgICAgICB9CiAgICAgICAgdGhpcy5hbmltYXRpb25Db25maWcgPSB7CiAgICAgICAgICBvcGVuOiB0aGlzLm9wZW5BbmltYXRpb25Db25maWcsCiAgICAgICAgICBjbG9zZTogdGhpcy5jbG9zZUFuaW1hdGlvbkNvbmZpZwogICAgICAgIH07CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXBkYXRlcyB0aGUgb3ZlcmxheSBwb3NpdGlvbiBiYXNlZCBvbiBjb25maWd1cmVkIGhvcml6b250YWwKICAgICAgICogYW5kIHZlcnRpY2FsIGFsaWdubWVudC4KICAgICAgICovCiAgICAgIF91cGRhdGVPdmVybGF5UG9zaXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLmlzQXR0YWNoZWQpIHsKICAgICAgICAgIC8vIFRoaXMgdHJpZ2dlcnMgaXJvbi1yZXNpemUsIGFuZCBpcm9uLW92ZXJsYXktYmVoYXZpb3Igd2lsbCBjYWxsIHJlZml0IGlmCiAgICAgICAgICAvLyBuZWVkZWQuCiAgICAgICAgICB0aGlzLm5vdGlmeVJlc2l6ZSgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZXRzIHNjcm9sbEFjdGlvbiBhY2NvcmRpbmcgdG8gdGhlIHZhbHVlIG9mIGFsbG93T3V0c2lkZVNjcm9sbC4KICAgICAgICogUHJlZmVyIHNldHRpbmcgZGlyZWN0bHkgc2Nyb2xsQWN0aW9uLgogICAgICAgKi8KICAgICAgX2FsbG93T3V0c2lkZVNjcm9sbENoYW5nZWQ6IGZ1bmN0aW9uKGFsbG93T3V0c2lkZVNjcm9sbCkgewogICAgICAgIC8vIFdhaXQgdW50aWwgaW5pdGlhbCB2YWx1ZXMgYXJlIGFsbCBzZXQuCiAgICAgICAgaWYgKCF0aGlzLl9yZWFkaWVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlmICghYWxsb3dPdXRzaWRlU2Nyb2xsKSB7CiAgICAgICAgICB0aGlzLnNjcm9sbEFjdGlvbiA9ICdsb2NrJzsKICAgICAgICB9IGVsc2UgaWYgKCF0aGlzLnNjcm9sbEFjdGlvbiB8fCB0aGlzLnNjcm9sbEFjdGlvbiA9PT0gJ2xvY2snKSB7CiAgICAgICAgICB0aGlzLnNjcm9sbEFjdGlvbiA9ICdyZWZpdCc7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEFwcGx5IGZvY3VzIHRvIGZvY3VzVGFyZ2V0IG9yIGNvbnRhaW5lZEVsZW1lbnQKICAgICAgICovCiAgICAgIF9hcHBseUZvY3VzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZm9jdXNUYXJnZXQgPSB0aGlzLmZvY3VzVGFyZ2V0IHx8IHRoaXMuY29udGFpbmVkRWxlbWVudDsKICAgICAgICBpZiAoZm9jdXNUYXJnZXQgJiYgdGhpcy5vcGVuZWQgJiYgIXRoaXMubm9BdXRvRm9jdXMpIHsKICAgICAgICAgIGZvY3VzVGFyZ2V0LmZvY3VzKCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIElyb25PdmVybGF5QmVoYXZpb3JJbXBsLl9hcHBseUZvY3VzLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgfQogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIFVzZSBgTmVvbkFuaW1hdGlvbkJlaGF2aW9yYCB0byBpbXBsZW1lbnQgYW4gYW5pbWF0aW9uLgogICAgICogQHBvbHltZXJCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBOZW9uQW5pbWF0aW9uQmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIERlZmluZXMgdGhlIGFuaW1hdGlvbiB0aW1pbmcuCiAgICAgICAgICovCiAgICAgICAgYW5pbWF0aW9uVGltaW5nOiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgZHVyYXRpb246IDUwMCwgZWFzaW5nOiAnY3ViaWMtYmV6aWVyKDAuNCwgMCwgMC4yLCAxKScsIGZpbGw6ICdib3RoJwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDYW4gYmUgdXNlZCB0byBkZXRlcm1pbmUgdGhhdCBlbGVtZW50cyBpbXBsZW1lbnQgdGhpcyBiZWhhdmlvci4KICAgICAgICovCiAgICAgIGlzTmVvbkFuaW1hdGlvbjogdHJ1ZSwKCiAgICAgIC8qKgogICAgICAgKiBEbyBhbnkgYW5pbWF0aW9uIGNvbmZpZ3VyYXRpb24gaGVyZS4KICAgICAgICovCiAgICAgIC8vIGNvbmZpZ3VyZTogZnVuY3Rpb24oY29uZmlnKSB7CiAgICAgIC8vIH0sCgogICAgICBjcmVhdGVkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAoIWRvY3VtZW50LmJvZHkuYW5pbWF0ZSkgewogICAgICAgICAgY29uc29sZS53YXJuKAogICAgICAgICAgICAgICdObyB3ZWIgYW5pbWF0aW9ucyBkZXRlY3RlZC4gVGhpcyBlbGVtZW50IHdpbGwgbm90JyArCiAgICAgICAgICAgICAgJyBmdW5jdGlvbiB3aXRob3V0IGEgd2ViIGFuaW1hdGlvbnMgcG9seWZpbGwuJyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIGFuaW1hdGlvbiB0aW1pbmcgYnkgbWl4aW5nIGluIHByb3BlcnRpZXMgZnJvbSBgY29uZmlnYCB0byB0aGUKICAgICAgICogZGVmYXVsdHMgZGVmaW5lZCBieSB0aGUgYW5pbWF0aW9uLgogICAgICAgKi8KICAgICAgdGltaW5nRnJvbUNvbmZpZzogZnVuY3Rpb24oY29uZmlnKSB7CiAgICAgICAgaWYgKGNvbmZpZy50aW1pbmcpIHsKICAgICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIGNvbmZpZy50aW1pbmcpIHsKICAgICAgICAgICAgdGhpcy5hbmltYXRpb25UaW1pbmdbcHJvcGVydHldID0gY29uZmlnLnRpbWluZ1twcm9wZXJ0eV07CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLmFuaW1hdGlvblRpbWluZzsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZXRzIGB0cmFuc2Zvcm1gIGFuZCBgdHJhbnNmb3JtT3JpZ2luYCBwcm9wZXJ0aWVzIGFsb25nIHdpdGggdGhlIHByZWZpeGVkCiAgICAgICAqIHZlcnNpb25zLgogICAgICAgKi8KICAgICAgc2V0UHJlZml4ZWRQcm9wZXJ0eTogZnVuY3Rpb24obm9kZSwgcHJvcGVydHksIHZhbHVlKSB7CiAgICAgICAgdmFyIG1hcCA9IHsKICAgICAgICAgICd0cmFuc2Zvcm0nOiBbJ3dlYmtpdFRyYW5zZm9ybSddLAogICAgICAgICAgJ3RyYW5zZm9ybU9yaWdpbic6IFsnbW96VHJhbnNmb3JtT3JpZ2luJywgJ3dlYmtpdFRyYW5zZm9ybU9yaWdpbiddCiAgICAgICAgfTsKICAgICAgICB2YXIgcHJlZml4ZXMgPSBtYXBbcHJvcGVydHldOwogICAgICAgIGZvciAodmFyIHByZWZpeCwgaW5kZXggPSAwOyBwcmVmaXggPSBwcmVmaXhlc1tpbmRleF07IGluZGV4KyspIHsKICAgICAgICAgIG5vZGUuc3R5bGVbcHJlZml4XSA9IHZhbHVlOwogICAgICAgIH0KICAgICAgICBub2RlLnN0eWxlW3Byb3BlcnR5XSA9IHZhbHVlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbGxlZCB3aGVuIHRoZSBhbmltYXRpb24gZmluaXNoZXMuCiAgICAgICAqLwogICAgICBjb21wbGV0ZTogZnVuY3Rpb24oY29uZmlnKSB7fQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICAvKgogICAgYDxmYWRlLWluLWFuaW1hdGlvbj5gIGFuaW1hdGVzIHRoZSBvcGFjaXR5IG9mIGFuIGVsZW1lbnQgZnJvbSAwIHRvIDEuCgogICAgQ29uZmlndXJhdGlvbjoKICAgIGBgYAogICAgewogICAgICBuYW1lOiAnZmFkZS1pbi1hbmltYXRpb24nLAogICAgICBub2RlOiA8bm9kZT4KICAgICAgdGltaW5nOiA8YW5pbWF0aW9uLXRpbWluZz4KICAgIH0KICAgIGBgYAogICAgKi8KICAgIFBvbHltZXIoewoKICAgICAgaXM6ICdmYWRlLWluLWFuaW1hdGlvbicsCgogICAgICBiZWhhdmlvcnM6IFtOZW9uQW5pbWF0aW9uQmVoYXZpb3JdLAoKICAgICAgY29uZmlndXJlOiBmdW5jdGlvbihjb25maWcpIHsKICAgICAgICB2YXIgbm9kZSA9IGNvbmZpZy5ub2RlOwogICAgICAgIHRoaXMuX2VmZmVjdCA9IG5ldyBLZXlmcmFtZUVmZmVjdCgKICAgICAgICAgICAgbm9kZSwKICAgICAgICAgICAgW3snb3BhY2l0eSc6ICcwJ30sIHsnb3BhY2l0eSc6ICcxJ31dLAogICAgICAgICAgICB0aGlzLnRpbWluZ0Zyb21Db25maWcoY29uZmlnKSk7CiAgICAgICAgcmV0dXJuIHRoaXMuX2VmZmVjdDsKICAgICAgfQoKICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgLyoKICAgIGA8ZmFkZS1vdXQtYW5pbWF0aW9uPmAgYW5pbWF0ZXMgdGhlIG9wYWNpdHkgb2YgYW4gZWxlbWVudCBmcm9tIDEgdG8gMC4KCiAgICBDb25maWd1cmF0aW9uOgogICAgYGBgCiAgICB7CiAgICAgIG5hbWU6ICdmYWRlLW91dC1hbmltYXRpb24nLAogICAgICBub2RlOiA8bm9kZT4KICAgICAgdGltaW5nOiA8YW5pbWF0aW9uLXRpbWluZz4KICAgIH0KICAgIGBgYAogICAgKi8KICAgIFBvbHltZXIoewoKICAgICAgaXM6ICdmYWRlLW91dC1hbmltYXRpb24nLAoKICAgICAgYmVoYXZpb3JzOiBbTmVvbkFuaW1hdGlvbkJlaGF2aW9yXSwKCiAgICAgIGNvbmZpZ3VyZTogZnVuY3Rpb24oY29uZmlnKSB7CiAgICAgICAgdmFyIG5vZGUgPSBjb25maWcubm9kZTsKICAgICAgICB0aGlzLl9lZmZlY3QgPSBuZXcgS2V5ZnJhbWVFZmZlY3QoCiAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgIFsKICAgICAgICAgICAgICB7J29wYWNpdHknOiAnMSd9LAogICAgICAgICAgICAgIHsnb3BhY2l0eSc6ICcwJ30sCiAgICAgICAgICAgIF0sCiAgICAgICAgICAgIHRoaXMudGltaW5nRnJvbUNvbmZpZyhjb25maWcpKTsKICAgICAgICByZXR1cm4gdGhpcy5fZWZmZWN0OwogICAgICB9CgogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgaXM6ICdwYXBlci1tZW51LWdyb3ctaGVpZ2h0LWFuaW1hdGlvbicsCgogICAgICBiZWhhdmlvcnM6IFtOZW9uQW5pbWF0aW9uQmVoYXZpb3JdLAoKICAgICAgY29uZmlndXJlOiBmdW5jdGlvbihjb25maWcpIHsKICAgICAgICB2YXIgbm9kZSA9IGNvbmZpZy5ub2RlOwogICAgICAgIHZhciByZWN0ID0gbm9kZS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICB2YXIgaGVpZ2h0ID0gcmVjdC5oZWlnaHQ7CgogICAgICAgIHRoaXMuX2VmZmVjdCA9IG5ldyBLZXlmcmFtZUVmZmVjdCgKICAgICAgICAgICAgbm9kZSwKICAgICAgICAgICAgW3toZWlnaHQ6IChoZWlnaHQgLyAyKSArICdweCd9LCB7aGVpZ2h0OiBoZWlnaHQgKyAncHgnfV0sCiAgICAgICAgICAgIHRoaXMudGltaW5nRnJvbUNvbmZpZyhjb25maWcpKTsKCiAgICAgICAgcmV0dXJuIHRoaXMuX2VmZmVjdDsKICAgICAgfQogICAgfSk7CgogICAgUG9seW1lcih7CiAgICAgIGlzOiAncGFwZXItbWVudS1ncm93LXdpZHRoLWFuaW1hdGlvbicsCgogICAgICBiZWhhdmlvcnM6IFtOZW9uQW5pbWF0aW9uQmVoYXZpb3JdLAoKICAgICAgY29uZmlndXJlOiBmdW5jdGlvbihjb25maWcpIHsKICAgICAgICB2YXIgbm9kZSA9IGNvbmZpZy5ub2RlOwogICAgICAgIHZhciByZWN0ID0gbm9kZS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICB2YXIgd2lkdGggPSByZWN0LndpZHRoOwoKICAgICAgICB0aGlzLl9lZmZlY3QgPSBuZXcgS2V5ZnJhbWVFZmZlY3QoCiAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgIFt7d2lkdGg6ICh3aWR0aCAvIDIpICsgJ3B4J30sIHt3aWR0aDogd2lkdGggKyAncHgnfV0sCiAgICAgICAgICAgIHRoaXMudGltaW5nRnJvbUNvbmZpZyhjb25maWcpKTsKCiAgICAgICAgcmV0dXJuIHRoaXMuX2VmZmVjdDsKICAgICAgfQogICAgfSk7CgogICAgUG9seW1lcih7CiAgICAgIGlzOiAncGFwZXItbWVudS1zaHJpbmstd2lkdGgtYW5pbWF0aW9uJywKCiAgICAgIGJlaGF2aW9yczogW05lb25BbmltYXRpb25CZWhhdmlvcl0sCgogICAgICBjb25maWd1cmU6IGZ1bmN0aW9uKGNvbmZpZykgewogICAgICAgIHZhciBub2RlID0gY29uZmlnLm5vZGU7CiAgICAgICAgdmFyIHJlY3QgPSBub2RlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciB3aWR0aCA9IHJlY3Qud2lkdGg7CgogICAgICAgIHRoaXMuX2VmZmVjdCA9IG5ldyBLZXlmcmFtZUVmZmVjdCgKICAgICAgICAgICAgbm9kZSwKICAgICAgICAgICAgW3t3aWR0aDogd2lkdGggKyAncHgnfSwge3dpZHRoOiB3aWR0aCAtICh3aWR0aCAvIDIwKSArICdweCd9XSwKICAgICAgICAgICAgdGhpcy50aW1pbmdGcm9tQ29uZmlnKGNvbmZpZykpOwoKICAgICAgICByZXR1cm4gdGhpcy5fZWZmZWN0OwogICAgICB9CiAgICB9KTsKCiAgICBQb2x5bWVyKHsKICAgICAgaXM6ICdwYXBlci1tZW51LXNocmluay1oZWlnaHQtYW5pbWF0aW9uJywKCiAgICAgIGJlaGF2aW9yczogW05lb25BbmltYXRpb25CZWhhdmlvcl0sCgogICAgICBjb25maWd1cmU6IGZ1bmN0aW9uKGNvbmZpZykgewogICAgICAgIHZhciBub2RlID0gY29uZmlnLm5vZGU7CiAgICAgICAgdmFyIHJlY3QgPSBub2RlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciBoZWlnaHQgPSByZWN0LmhlaWdodDsKCiAgICAgICAgdGhpcy5zZXRQcmVmaXhlZFByb3BlcnR5KG5vZGUsICd0cmFuc2Zvcm1PcmlnaW4nLCAnMCAwJyk7CgogICAgICAgIHRoaXMuX2VmZmVjdCA9IG5ldyBLZXlmcmFtZUVmZmVjdCgKICAgICAgICAgICAgbm9kZSwKICAgICAgICAgICAgWwogICAgICAgICAgICAgIHtoZWlnaHQ6IGhlaWdodCArICdweCcsIHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVkoMCknfSwKICAgICAgICAgICAgICB7aGVpZ2h0OiBoZWlnaHQgLyAyICsgJ3B4JywgdHJhbnNmb3JtOiAndHJhbnNsYXRlWSgtMjBweCknfQogICAgICAgICAgICBdLAogICAgICAgICAgICB0aGlzLnRpbWluZ0Zyb21Db25maWcoY29uZmlnKSk7CgogICAgICAgIHJldHVybiB0aGlzLl9lZmZlY3Q7CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIHZhciBjb25maWcgPSB7CiAgICAgIEFOSU1BVElPTl9DVUJJQ19CRVpJRVI6ICdjdWJpYy1iZXppZXIoLjMsLjk1LC41LDEpJywKICAgICAgTUFYX0FOSU1BVElPTl9USU1FX01TOiA0MDAKICAgIH07CgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246IFtEcm9wZG93bgogICAgYnV0dG9uc10oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL2J1dHRvbnMuaHRtbCNidXR0b25zLWRyb3Bkb3duLWJ1dHRvbnMpCgogICAgYHBhcGVyLW1lbnUtYnV0dG9uYCBhbGxvd3Mgb25lIHRvIGNvbXBvc2UgYSBkZXNpZ25hdGVkICJ0cmlnZ2VyIiBlbGVtZW50IHdpdGgKICAgIGFub3RoZXIgZWxlbWVudCB0aGF0IHJlcHJlc2VudHMgImNvbnRlbnQiLCB0byBjcmVhdGUgYSBkcm9wZG93biBtZW51IHRoYXQKICAgIGRpc3BsYXlzIHRoZSAiY29udGVudCIgd2hlbiB0aGUgInRyaWdnZXIiIGlzIGNsaWNrZWQuCgogICAgVGhlIGNoaWxkIGVsZW1lbnQgYXNzaWduZWQgdG8gdGhlIGBkcm9wZG93bi10cmlnZ2VyYCBzbG90IHdpbGwgYmUgdXNlZCBhcyB0aGUKICAgICJ0cmlnZ2VyIiBlbGVtZW50LiBUaGUgY2hpbGQgZWxlbWVudCBhc3NpZ25lZCB0byB0aGUgYGRyb3Bkb3duLWNvbnRlbnRgIHNsb3QKICAgIHdpbGwgYmUgdXNlZCBhcyB0aGUgImNvbnRlbnQiIGVsZW1lbnQuCgogICAgVGhlIGBwYXBlci1tZW51LWJ1dHRvbmAgaXMgc2Vuc2l0aXZlIHRvIGl0cyBjb250ZW50J3MgYGlyb24tc2VsZWN0YCBldmVudHMuIElmCiAgICB0aGUgImNvbnRlbnQiIGVsZW1lbnQgdHJpZ2dlcnMgYW4gYGlyb24tc2VsZWN0YCBldmVudCwgdGhlIGBwYXBlci1tZW51LWJ1dHRvbmAKICAgIHdpbGwgY2xvc2UgYXV0b21hdGljYWxseS4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItbWVudS1idXR0b24+CiAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24gaWNvbj0ibWVudSIKICAgIHNsb3Q9ImRyb3Bkb3duLXRyaWdnZXIiPjwvcGFwZXItaWNvbi1idXR0b24+IDxwYXBlci1saXN0Ym94CiAgICBzbG90PSJkcm9wZG93bi1jb250ZW50Ij4gPHBhcGVyLWl0ZW0+U2hhcmU8L3BhcGVyLWl0ZW0+CiAgICAgICAgICAgIDxwYXBlci1pdGVtPlNldHRpbmdzPC9wYXBlci1pdGVtPgogICAgICAgICAgICA8cGFwZXItaXRlbT5IZWxwPC9wYXBlci1pdGVtPgogICAgICAgICAgPC9wYXBlci1saXN0Ym94PgogICAgICAgIDwvcGFwZXItbWVudS1idXR0b24+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGFsc28gYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLW1lbnUtYnV0dG9uLWRyb3Bkb3duLWJhY2tncm91bmRgIHwgQmFja2dyb3VuZCBjb2xvciBvZiB0aGUgcGFwZXItbWVudS1idXR0b24gZHJvcGRvd24gfCBgLS1wcmltYXJ5LWJhY2tncm91bmQtY29sb3JgCiAgICBgLS1wYXBlci1tZW51LWJ1dHRvbmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBwYXBlci1tZW51LWJ1dHRvbiB8IGB7fWAKICAgIGAtLXBhcGVyLW1lbnUtYnV0dG9uLWRpc2FibGVkYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHBhcGVyLW1lbnUtYnV0dG9uIHdoZW4gZGlzYWJsZWQgfCBge31gCiAgICBgLS1wYXBlci1tZW51LWJ1dHRvbi1kcm9wZG93bmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBwYXBlci1tZW51LWJ1dHRvbiBkcm9wZG93biB8IGB7fWAKICAgIGAtLXBhcGVyLW1lbnUtYnV0dG9uLWNvbnRlbnRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgcGFwZXItbWVudS1idXR0b24gY29udGVudCB8IGB7fWAKCiAgICBAaGVybyBoZXJvLnN2ZwogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgY29uc3QgUGFwZXJNZW51QnV0dG9uID0gUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgcGFkZGluZzogOHB4OwogICAgICAgIG91dGxpbmU6IG5vbmU7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLW1lbnUtYnV0dG9uOwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSB7CiAgICAgICAgY3Vyc29yOiBhdXRvOwogICAgICAgIGNvbG9yOiB2YXIoLS1kaXNhYmxlZC10ZXh0LWNvbG9yKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWVudS1idXR0b24tZGlzYWJsZWQ7CiAgICAgIH0KCiAgICAgIGlyb24tZHJvcGRvd24gewogICAgICAgIEBhcHBseSAtLXBhcGVyLW1lbnUtYnV0dG9uLWRyb3Bkb3duOwogICAgICB9CgogICAgICAuZHJvcGRvd24tY29udGVudCB7CiAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi0yZHA7CgogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBib3JkZXItcmFkaXVzOiAycHg7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItbWVudS1idXR0b24tZHJvcGRvd24tYmFja2dyb3VuZCwgdmFyKC0tcHJpbWFyeS1iYWNrZ3JvdW5kLWNvbG9yKSk7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLW1lbnUtYnV0dG9uLWNvbnRlbnQ7CiAgICAgIH0KCiAgICAgIDpob3N0KFt2ZXJ0aWNhbC1hbGlnbj0idG9wIl0pIC5kcm9wZG93bi1jb250ZW50IHsKICAgICAgICBtYXJnaW4tYm90dG9tOiAyMHB4OwogICAgICAgIG1hcmdpbi10b3A6IC0xMHB4OwogICAgICAgIHRvcDogMTBweDsKICAgICAgfQoKICAgICAgOmhvc3QoW3ZlcnRpY2FsLWFsaWduPSJib3R0b20iXSkgLmRyb3Bkb3duLWNvbnRlbnQgewogICAgICAgIGJvdHRvbTogMTBweDsKICAgICAgICBtYXJnaW4tYm90dG9tOiAtMTBweDsKICAgICAgICBtYXJnaW4tdG9wOiAyMHB4OwogICAgICB9CgogICAgICAjdHJpZ2dlciB7CiAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxkaXYgaWQ9InRyaWdnZXIiIG9uLXRhcD0idG9nZ2xlIj4KICAgICAgPHNsb3QgbmFtZT0iZHJvcGRvd24tdHJpZ2dlciI+PC9zbG90PgogICAgPC9kaXY+CgogICAgPGlyb24tZHJvcGRvd24gaWQ9ImRyb3Bkb3duIiBvcGVuZWQ9Int7b3BlbmVkfX0iIGhvcml6b250YWwtYWxpZ249IltbaG9yaXpvbnRhbEFsaWduXV0iIHZlcnRpY2FsLWFsaWduPSJbW3ZlcnRpY2FsQWxpZ25dXSIgZHluYW1pYy1hbGlnbj0iW1tkeW5hbWljQWxpZ25dXSIgaG9yaXpvbnRhbC1vZmZzZXQ9IltbaG9yaXpvbnRhbE9mZnNldF1dIiB2ZXJ0aWNhbC1vZmZzZXQ9IltbdmVydGljYWxPZmZzZXRdXSIgbm8tb3ZlcmxhcD0iW1tub092ZXJsYXBdXSIgb3Blbi1hbmltYXRpb24tY29uZmlnPSJbW29wZW5BbmltYXRpb25Db25maWddXSIgY2xvc2UtYW5pbWF0aW9uLWNvbmZpZz0iW1tjbG9zZUFuaW1hdGlvbkNvbmZpZ11dIiBuby1hbmltYXRpb25zPSJbW25vQW5pbWF0aW9uc11dIiBmb2N1cy10YXJnZXQ9IltbX2Ryb3Bkb3duQ29udGVudF1dIiBhbGxvdy1vdXRzaWRlLXNjcm9sbD0iW1thbGxvd091dHNpZGVTY3JvbGxdXSIgcmVzdG9yZS1mb2N1cy1vbi1jbG9zZT0iW1tyZXN0b3JlRm9jdXNPbkNsb3NlXV0iIG9uLWlyb24tb3ZlcmxheS1jYW5jZWxlZD0iX19vbklyb25PdmVybGF5Q2FuY2VsZWQiPgogICAgICA8ZGl2IHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiIGNsYXNzPSJkcm9wZG93bi1jb250ZW50Ij4KICAgICAgICA8c2xvdCBpZD0iY29udGVudCIgbmFtZT0iZHJvcGRvd24tY29udGVudCI+PC9zbG90PgogICAgICA8L2Rpdj4KICAgIDwvaXJvbi1kcm9wZG93bj4KYCwKCiAgICAgIGlzOiAncGFwZXItbWVudS1idXR0b24nLAoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gdGhlIGRyb3Bkb3duIG9wZW5zLgogICAgICAgKgogICAgICAgKiBAZXZlbnQgcGFwZXItZHJvcGRvd24tb3BlbgogICAgICAgKi8KCiAgICAgIC8qKgogICAgICAgKiBGaXJlZCB3aGVuIHRoZSBkcm9wZG93biBjbG9zZXMuCiAgICAgICAqCiAgICAgICAqIEBldmVudCBwYXBlci1kcm9wZG93bi1jbG9zZQogICAgICAgKi8KCiAgICAgIGJlaGF2aW9yczogW0lyb25BMTF5S2V5c0JlaGF2aW9yLCBJcm9uQ29udHJvbFN0YXRlXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBjb250ZW50IGlzIGN1cnJlbnRseSBkaXNwbGF5ZWQuCiAgICAgICAgICovCiAgICAgICAgb3BlbmVkOgogICAgICAgICAgICB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlLCBub3RpZnk6IHRydWUsIG9ic2VydmVyOiAnX29wZW5lZENoYW5nZWQnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG9yaWVudGF0aW9uIGFnYWluc3Qgd2hpY2ggdG8gYWxpZ24gdGhlIG1lbnUgZHJvcGRvd24KICAgICAgICAgKiBob3Jpem9udGFsbHkgcmVsYXRpdmUgdG8gdGhlIGRyb3Bkb3duIHRyaWdnZXIuCiAgICAgICAgICovCiAgICAgICAgaG9yaXpvbnRhbEFsaWduOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ2xlZnQnLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3JpZW50YXRpb24gYWdhaW5zdCB3aGljaCB0byBhbGlnbiB0aGUgbWVudSBkcm9wZG93bgogICAgICAgICAqIHZlcnRpY2FsbHkgcmVsYXRpdmUgdG8gdGhlIGRyb3Bkb3duIHRyaWdnZXIuCiAgICAgICAgICovCiAgICAgICAgdmVydGljYWxBbGlnbjoge3R5cGU6IFN0cmluZywgdmFsdWU6ICd0b3AnLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgYGhvcml6b250YWxBbGlnbmAgYW5kIGB2ZXJ0aWNhbEFsaWduYCBwcm9wZXJ0aWVzIHdpbGwKICAgICAgICAgKiBiZSBjb25zaWRlcmVkIHByZWZlcmVuY2VzIGluc3RlYWQgb2Ygc3RyaWN0IHJlcXVpcmVtZW50cyB3aGVuCiAgICAgICAgICogcG9zaXRpb25pbmcgdGhlIGRyb3Bkb3duIGFuZCBtYXkgYmUgY2hhbmdlZCBpZiBkb2luZyBzbyByZWR1Y2VzCiAgICAgICAgICogdGhlIGFyZWEgb2YgdGhlIGRyb3Bkb3duIGZhbGxpbmcgb3V0c2lkZSBvZiBgZml0SW50b2AuCiAgICAgICAgICovCiAgICAgICAgZHluYW1pY0FsaWduOiB7dHlwZTogQm9vbGVhbn0sCgogICAgICAgIC8qKgogICAgICAgICAqIEEgcGl4ZWwgdmFsdWUgdGhhdCB3aWxsIGJlIGFkZGVkIHRvIHRoZSBwb3NpdGlvbiBjYWxjdWxhdGVkIGZvciB0aGUKICAgICAgICAgKiBnaXZlbiBgaG9yaXpvbnRhbEFsaWduYC4gVXNlIGEgbmVnYXRpdmUgdmFsdWUgdG8gb2Zmc2V0IHRvIHRoZQogICAgICAgICAqIGxlZnQsIG9yIGEgcG9zaXRpdmUgdmFsdWUgdG8gb2Zmc2V0IHRvIHRoZSByaWdodC4KICAgICAgICAgKi8KICAgICAgICBob3Jpem9udGFsT2Zmc2V0OiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMCwgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQSBwaXhlbCB2YWx1ZSB0aGF0IHdpbGwgYmUgYWRkZWQgdG8gdGhlIHBvc2l0aW9uIGNhbGN1bGF0ZWQgZm9yIHRoZQogICAgICAgICAqIGdpdmVuIGB2ZXJ0aWNhbEFsaWduYC4gVXNlIGEgbmVnYXRpdmUgdmFsdWUgdG8gb2Zmc2V0IHRvd2FyZHMgdGhlCiAgICAgICAgICogdG9wLCBvciBhIHBvc2l0aXZlIHZhbHVlIHRvIG9mZnNldCB0b3dhcmRzIHRoZSBib3R0b20uCiAgICAgICAgICovCiAgICAgICAgdmVydGljYWxPZmZzZXQ6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAwLCBub3RpZnk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgZHJvcGRvd24gd2lsbCBiZSBwb3NpdGlvbmVkIHNvIHRoYXQgaXQgZG9lc24ndCBvdmVybGFwCiAgICAgICAgICogdGhlIGJ1dHRvbi4KICAgICAgICAgKi8KICAgICAgICBub092ZXJsYXA6IHt0eXBlOiBCb29sZWFufSwKCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRvIHRydWUgdG8gZGlzYWJsZSBhbmltYXRpb25zIHdoZW4gb3BlbmluZyBhbmQgY2xvc2luZyB0aGUKICAgICAgICAgKiBkcm9wZG93bi4KICAgICAgICAgKi8KICAgICAgICBub0FuaW1hdGlvbnM6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNhYmxlIGF1dG9tYXRpY2FsbHkgY2xvc2luZyB0aGUgZHJvcGRvd24gYWZ0ZXIKICAgICAgICAgKiBhIHNlbGVjdGlvbiBoYXMgYmVlbiBtYWRlLgogICAgICAgICAqLwogICAgICAgIGlnbm9yZVNlbGVjdDoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGVuYWJsZSBhdXRvbWF0aWNhbGx5IGNsb3NpbmcgdGhlIGRyb3Bkb3duIGFmdGVyIGFuCiAgICAgICAgICogaXRlbSBoYXMgYmVlbiBhY3RpdmF0ZWQsIGV2ZW4gaWYgdGhlIHNlbGVjdGlvbiBkaWQgbm90IGNoYW5nZS4KICAgICAgICAgKi8KICAgICAgICBjbG9zZU9uQWN0aXZhdGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBBbiBhbmltYXRpb24gY29uZmlnLiBJZiBwcm92aWRlZCwgdGhpcyB3aWxsIGJlIHVzZWQgdG8gYW5pbWF0ZSB0aGUKICAgICAgICAgKiBvcGVuaW5nIG9mIHRoZSBkcm9wZG93bi4KICAgICAgICAgKi8KICAgICAgICBvcGVuQW5pbWF0aW9uQ29uZmlnOiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgICAge25hbWU6ICdmYWRlLWluLWFuaW1hdGlvbicsIHRpbWluZzoge2RlbGF5OiAxMDAsIGR1cmF0aW9uOiAyMDB9fSwKICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBuYW1lOiAncGFwZXItbWVudS1ncm93LXdpZHRoLWFuaW1hdGlvbicsCiAgICAgICAgICAgICAgICB0aW1pbmc6IHsKICAgICAgICAgICAgICAgICAgZGVsYXk6IDEwMCwKICAgICAgICAgICAgICAgICAgZHVyYXRpb246IDE1MCwKICAgICAgICAgICAgICAgICAgZWFzaW5nOiBjb25maWcuQU5JTUFUSU9OX0NVQklDX0JFWklFUgogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgbmFtZTogJ3BhcGVyLW1lbnUtZ3Jvdy1oZWlnaHQtYW5pbWF0aW9uJywKICAgICAgICAgICAgICAgIHRpbWluZzogewogICAgICAgICAgICAgICAgICBkZWxheTogMTAwLAogICAgICAgICAgICAgICAgICBkdXJhdGlvbjogMjc1LAogICAgICAgICAgICAgICAgICBlYXNpbmc6IGNvbmZpZy5BTklNQVRJT05fQ1VCSUNfQkVaSUVSCiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICBdOwogICAgICAgICAgfQogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIEFuIGFuaW1hdGlvbiBjb25maWcuIElmIHByb3ZpZGVkLCB0aGlzIHdpbGwgYmUgdXNlZCB0byBhbmltYXRlIHRoZQogICAgICAgICAqIGNsb3Npbmcgb2YgdGhlIGRyb3Bkb3duLgogICAgICAgICAqLwogICAgICAgIGNsb3NlQW5pbWF0aW9uQ29uZmlnOiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgICAge25hbWU6ICdmYWRlLW91dC1hbmltYXRpb24nLCB0aW1pbmc6IHtkdXJhdGlvbjogMTUwfX0sCiAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgbmFtZTogJ3BhcGVyLW1lbnUtc2hyaW5rLXdpZHRoLWFuaW1hdGlvbicsCiAgICAgICAgICAgICAgICB0aW1pbmc6IHsKICAgICAgICAgICAgICAgICAgZGVsYXk6IDEwMCwKICAgICAgICAgICAgICAgICAgZHVyYXRpb246IDUwLAogICAgICAgICAgICAgICAgICBlYXNpbmc6IGNvbmZpZy5BTklNQVRJT05fQ1VCSUNfQkVaSUVSCiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBuYW1lOiAncGFwZXItbWVudS1zaHJpbmstaGVpZ2h0LWFuaW1hdGlvbicsCiAgICAgICAgICAgICAgICB0aW1pbmc6IHtkdXJhdGlvbjogMjAwLCBlYXNpbmc6ICdlYXNlLWluJ30KICAgICAgICAgICAgICB9CiAgICAgICAgICAgIF07CiAgICAgICAgICB9CiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQnkgZGVmYXVsdCwgdGhlIGRyb3Bkb3duIHdpbGwgY29uc3RyYWluIHNjcm9sbGluZyBvbiB0aGUgcGFnZQogICAgICAgICAqIHRvIGl0c2VsZiB3aGVuIG9wZW5lZC4KICAgICAgICAgKiBTZXQgdG8gdHJ1ZSBpbiBvcmRlciB0byBwcmV2ZW50IHNjcm9sbCBmcm9tIGJlaW5nIGNvbnN0cmFpbmVkCiAgICAgICAgICogdG8gdGhlIGRyb3Bkb3duIHdoZW4gaXQgb3BlbnMuCiAgICAgICAgICovCiAgICAgICAgYWxsb3dPdXRzaWRlU2Nyb2xsOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogV2hldGhlciBmb2N1cyBzaG91bGQgYmUgcmVzdG9yZWQgdG8gdGhlIGJ1dHRvbiB3aGVuIHRoZSBtZW51IGNsb3Nlcy4KICAgICAgICAgKi8KICAgICAgICByZXN0b3JlRm9jdXNPbkNsb3NlOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIGlzIHRoZSBlbGVtZW50IGludGVuZGVkIHRvIGJlIGJvdW5kIGFzIHRoZSBmb2N1cyB0YXJnZXQKICAgICAgICAgKiBmb3IgdGhlIGBpcm9uLWRyb3Bkb3duYCBjb250YWluZWQgYnkgYHBhcGVyLW1lbnUtYnV0dG9uYC4KICAgICAgICAgKi8KICAgICAgICBfZHJvcGRvd25Db250ZW50OiB7dHlwZTogT2JqZWN0fQogICAgICB9LAoKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHtyb2xlOiAnZ3JvdXAnLCAnYXJpYS1oYXNwb3B1cCc6ICd0cnVlJ30sCgogICAgICBsaXN0ZW5lcnM6CiAgICAgICAgICB7J2lyb24tYWN0aXZhdGUnOiAnX29uSXJvbkFjdGl2YXRlJywgJ2lyb24tc2VsZWN0JzogJ19vbklyb25TZWxlY3QnfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgY29udGVudCBlbGVtZW50IHRoYXQgaXMgY29udGFpbmVkIGJ5IHRoZSBtZW51IGJ1dHRvbiwgaWYgYW55LgogICAgICAgKi8KICAgICAgZ2V0IGNvbnRlbnRFbGVtZW50KCkgewogICAgICAgIC8vIFBvbHltZXIgMi54IHJldHVybnMgc2xvdC5hc3NpZ25lZE5vZGVzIHdoaWNoIGNhbiBjb250YWluIHRleHQgbm9kZXMuCiAgICAgICAgdmFyIG5vZGVzID0gZG9tKHRoaXMuJC5jb250ZW50KS5nZXREaXN0cmlidXRlZE5vZGVzKCk7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBub2Rlcy5sZW5ndGg7IGkgPCBsOyBpKyspIHsKICAgICAgICAgIGlmIChub2Rlc1tpXS5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpIHsKICAgICAgICAgICAgcmV0dXJuIG5vZGVzW2ldOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUb2dnbGVzIHRoZSBkcm9wZG93biBjb250ZW50IGJldHdlZW4gb3BlbmVkIGFuZCBjbG9zZWQuCiAgICAgICAqLwogICAgICB0b2dnbGU6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm9wZW5lZCkgewogICAgICAgICAgdGhpcy5jbG9zZSgpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLm9wZW4oKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogTWFrZSB0aGUgZHJvcGRvd24gY29udGVudCBhcHBlYXIgYXMgYW4gb3ZlcmxheSBwb3NpdGlvbmVkIHJlbGF0aXZlCiAgICAgICAqIHRvIHRoZSBkcm9wZG93biB0cmlnZ2VyLgogICAgICAgKi8KICAgICAgb3BlbjogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRoaXMuJC5kcm9wZG93bi5vcGVuKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSGlkZSB0aGUgZHJvcGRvd24gY29udGVudC4KICAgICAgICovCiAgICAgIGNsb3NlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLiQuZHJvcGRvd24uY2xvc2UoKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBXaGVuIGFuIGBpcm9uLXNlbGVjdGAgZXZlbnQgaXMgcmVjZWl2ZWQsIHRoZSBkcm9wZG93biBzaG91bGQKICAgICAgICogYXV0b21hdGljYWxseSBjbG9zZSBvbiB0aGUgYXNzdW1wdGlvbiB0aGF0IGEgdmFsdWUgaGFzIGJlZW4gY2hvc2VuLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBIEN1c3RvbUV2ZW50IGluc3RhbmNlIHdpdGggdHlwZQogICAgICAgKiBzZXQgdG8gYCJpcm9uLXNlbGVjdCJgLgogICAgICAgKi8KICAgICAgX29uSXJvblNlbGVjdDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoIXRoaXMuaWdub3JlU2VsZWN0KSB7CiAgICAgICAgICB0aGlzLmNsb3NlKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENsb3NlcyB0aGUgZHJvcGRvd24gd2hlbiBhbiBgaXJvbi1hY3RpdmF0ZWAgZXZlbnQgaXMgcmVjZWl2ZWQgaWYKICAgICAgICogYGNsb3NlT25BY3RpdmF0ZWAgaXMgdHJ1ZS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtDdXN0b21FdmVudH0gZXZlbnQgQSBDdXN0b21FdmVudCBvZiB0eXBlICdpcm9uLWFjdGl2YXRlJy4KICAgICAgICovCiAgICAgIF9vbklyb25BY3RpdmF0ZTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAodGhpcy5jbG9zZU9uQWN0aXZhdGUpIHsKICAgICAgICAgIHRoaXMuY2xvc2UoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogV2hlbiB0aGUgZHJvcGRvd24gb3BlbnMsIHRoZSBgcGFwZXItbWVudS1idXR0b25gIGZpcmVzIGBwYXBlci1vcGVuYC4KICAgICAgICogV2hlbiB0aGUgZHJvcGRvd24gY2xvc2VzLCB0aGUgYHBhcGVyLW1lbnUtYnV0dG9uYCBmaXJlcyBgcGFwZXItY2xvc2VgLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IG9wZW5lZCBUcnVlIGlmIHRoZSBkcm9wZG93biBpcyBvcGVuZWQsIG90aGVyd2lzZSBmYWxzZS4KICAgICAgICogQHBhcmFtIHtib29sZWFufSBvbGRPcGVuZWQgVGhlIHByZXZpb3VzIHZhbHVlIG9mIGBvcGVuZWRgLgogICAgICAgKi8KICAgICAgX29wZW5lZENoYW5nZWQ6IGZ1bmN0aW9uKG9wZW5lZCwgb2xkT3BlbmVkKSB7CiAgICAgICAgaWYgKG9wZW5lZCkgewogICAgICAgICAgLy8gVE9ETyhjZGF0YSk6IFVwZGF0ZSB0aGlzIHdoZW4gd2UgY2FuIG1lYXN1cmUgY2hhbmdlcyBpbiBkaXN0cmlidXRlZAogICAgICAgICAgLy8gY2hpbGRyZW4gaW4gYW4gaWRpb21hdGljIHdheS4KICAgICAgICAgIC8vIFdlIHBva2UgdGhpcyBwcm9wZXJ0eSBpbiBjYXNlIHRoZSBlbGVtZW50IGhhcyBjaGFuZ2VkLiBUaGlzIHdpbGwKICAgICAgICAgIC8vIGNhdXNlIHRoZSBmb2N1cyB0YXJnZXQgZm9yIHRoZSBgaXJvbi1kcm9wZG93bmAgdG8gYmUgdXBkYXRlZCBhcwogICAgICAgICAgLy8gbmVjZXNzYXJ5OgogICAgICAgICAgdGhpcy5fZHJvcGRvd25Db250ZW50ID0gdGhpcy5jb250ZW50RWxlbWVudDsKICAgICAgICAgIHRoaXMuZmlyZSgncGFwZXItZHJvcGRvd24tb3BlbicpOwogICAgICAgIH0gZWxzZSBpZiAob2xkT3BlbmVkICE9IG51bGwpIHsKICAgICAgICAgIHRoaXMuZmlyZSgncGFwZXItZHJvcGRvd24tY2xvc2UnKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSWYgdGhlIGRyb3Bkb3duIGlzIG9wZW4gd2hlbiBkaXNhYmxlZCBiZWNvbWVzIHRydWUsIGNsb3NlIHRoZQogICAgICAgKiBkcm9wZG93bi4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtib29sZWFufSBkaXNhYmxlZCBUcnVlIGlmIGRpc2FibGVkLCBvdGhlcndpc2UgZmFsc2UuCiAgICAgICAqLwogICAgICBfZGlzYWJsZWRDaGFuZ2VkOiBmdW5jdGlvbihkaXNhYmxlZCkgewogICAgICAgIElyb25Db250cm9sU3RhdGUuX2Rpc2FibGVkQ2hhbmdlZC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChkaXNhYmxlZCAmJiB0aGlzLm9wZW5lZCkgewogICAgICAgICAgdGhpcy5jbG9zZSgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9fb25Jcm9uT3ZlcmxheUNhbmNlbGVkOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciB1aUV2ZW50ID0gZXZlbnQuZGV0YWlsOwogICAgICAgIHZhciB0cmlnZ2VyID0gdGhpcy4kLnRyaWdnZXI7CiAgICAgICAgdmFyIHBhdGggPSBkb20odWlFdmVudCkucGF0aDsKCiAgICAgICAgaWYgKHBhdGguaW5kZXhPZih0cmlnZ2VyKSA+IC0xKSB7CiAgICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgIH0KICAgICAgfQogICAgfSk7CgogICAgT2JqZWN0LmtleXMoY29uZmlnKS5mb3JFYWNoKGZ1bmN0aW9uKGtleSkgewogICAgICBQYXBlck1lbnVCdXR0b25ba2V5XSA9IGNvbmZpZ1trZXldOwogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE2IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICBjb25zdCAkX2RvY3VtZW50Q29udGFpbmVyJDEgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwogICAgJF9kb2N1bWVudENvbnRhaW5lciQxLnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKCiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDEuaW5uZXJIVE1MID0KICAgICAgICBgPGlyb24taWNvbnNldC1zdmcgbmFtZT0icGFwZXItZHJvcGRvd24tbWVudSIgc2l6ZT0iMjQiPgo8c3ZnPjxkZWZzPgo8ZyBpZD0iYXJyb3ctZHJvcC1kb3duIj48cGF0aCBkPSJNNyAxMGw1IDUgNS01eiI+PC9wYXRoPjwvZz4KPC9kZWZzPjwvc3ZnPgo8L2lyb24taWNvbnNldC1zdmc+YDsKCiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKCRfZG9jdW1lbnRDb250YWluZXIkMS5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTYgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIGNvbnN0ICRfZG9jdW1lbnRDb250YWluZXIkMiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RlbXBsYXRlJyk7CiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDIuc2V0QXR0cmlidXRlKCdzdHlsZScsICdkaXNwbGF5OiBub25lOycpOwoKICAgICRfZG9jdW1lbnRDb250YWluZXIkMi5pbm5lckhUTUwgPQogICAgICAgIGA8ZG9tLW1vZHVsZSBpZD0icGFwZXItZHJvcGRvd24tbWVudS1zaGFyZWQtc3R5bGVzIj4KICA8dGVtcGxhdGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIHRleHQtYWxpZ246IGxlZnQ7CgogICAgICAgIC8qIE5PVEUoY2RhdGEpOiBCb3RoIHZhbHVlcyBhcmUgbmVlZGVkLCBzaW5jZSBzb21lIHBob25lcyByZXF1aXJlIHRoZQogICAgICAgICAqIHZhbHVlIHRvIGJlIFxgdHJhbnNwYXJlbnRcYC4KICAgICAgICAgKi8KICAgICAgICAtd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3I6IHJnYmEoMCwwLDAsMCk7CiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKCiAgICAgICAgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQ6IHsKICAgICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICAgICAgdGV4dC1vdmVyZmxvdzogZWxsaXBzaXM7CiAgICAgICAgICBtYXgtd2lkdGg6IDEwMCU7CiAgICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICAgIH07CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWRyb3Bkb3duLW1lbnU7CiAgICAgIH0KCiAgICAgIC8qIHBhcGVyLWRyb3Bkb3duLW1lbnUgYW5kIHBhcGVyLWRyb3Bkb3duLW1lbnUtbGlnaHQgYm90aCBkZWxlZ2F0ZSBmb2N1cwogICAgICAgKiB0byBvdGhlciBpbnRlcm5hbCBlbGVtZW50cyB3aGljaCBtYW5hZ2UgZm9jdXMgc3R5bGluZy4gKi8KICAgICAgOmhvc3QoOmZvY3VzKSB7CiAgICAgICAgb3V0bGluZTogbm9uZTsKICAgICAgfQoKICAgICAgOmhvc3QoOmRpcihydGwpKSB7CiAgICAgICAgdGV4dC1hbGlnbjogcmlnaHQ7CgogICAgICAgIEBhcHBseSgtLXBhcGVyLWRyb3Bkb3duLW1lbnUpOwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZHJvcGRvd24tbWVudS1kaXNhYmxlZDsKICAgICAgfQoKICAgICAgOmhvc3QoW25vaW5rXSkgcGFwZXItcmlwcGxlIHsKICAgICAgICBkaXNwbGF5OiBub25lOwogICAgICB9CgogICAgICA6aG9zdChbbm8tbGFiZWwtZmxvYXRdKSBwYXBlci1yaXBwbGUgewogICAgICAgIHRvcDogOHB4OwogICAgICB9CgogICAgICBwYXBlci1yaXBwbGUgewogICAgICAgIHRvcDogMTJweDsKICAgICAgICBsZWZ0OiAwcHg7CiAgICAgICAgYm90dG9tOiA4cHg7CiAgICAgICAgcmlnaHQ6IDBweDsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItZHJvcGRvd24tbWVudS1yaXBwbGU7CiAgICAgIH0KCiAgICAgIHBhcGVyLW1lbnUtYnV0dG9uIHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBwYWRkaW5nOiAwOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1kcm9wZG93bi1tZW51LWJ1dHRvbjsKICAgICAgfQoKICAgICAgcGFwZXItaW5wdXQgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWRyb3Bkb3duLW1lbnUtaW5wdXQ7CiAgICAgIH0KCiAgICAgIGlyb24taWNvbiB7CiAgICAgICAgY29sb3I6IHZhcigtLWRpc2FibGVkLXRleHQtY29sb3IpOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1kcm9wZG93bi1tZW51LWljb247CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJDIuY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLy8gTGVnYWN5RWxlbWVudE1peGluIGRlZHVwZXMgYW5kIHRoaXMgaXMgdGhlIGJhc2UgY2xhc3MgZm9yIGVsZW1lbnRzIGNyZWF0ZWQKICAgIC8vIHdpdGggdGhlIGBQb2x5bWVyYCBmdW5jdGlvbiwgc28gdGhpcyBpcyBvbmx5IGEgY2FjaGUgbG9va3VwLgogICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXIvcG9seW1lci9ibG9iLzY0MGJjODBhYzcxNzdiNzYxZDQ2YjJmYTljNDU1YzMxOGYyYjg1YzYvbGliL2xlZ2FjeS9jbGFzcy5qcyNMNTMzLUw1MzQKICAgIGNvbnN0IExlZ2FjeVBvbHltZXJFbGVtZW50QmFzZSA9IExlZ2FjeUVsZW1lbnRNaXhpbihIVE1MRWxlbWVudCk7CgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246IFtEcm9wZG93bgogICAgbWVudXNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9idXR0b25zLmh0bWwjYnV0dG9ucy1kcm9wZG93bi1idXR0b25zKQoKICAgIGBwYXBlci1kcm9wZG93bi1tZW51YCBpcyBzaW1pbGFyIHRvIGEgbmF0aXZlIGJyb3dzZXIgc2VsZWN0IGVsZW1lbnQuCiAgICBgcGFwZXItZHJvcGRvd24tbWVudWAgd29ya3Mgd2l0aCBzZWxlY3RhYmxlIGNvbnRlbnQuIFRoZSBjdXJyZW50bHkgc2VsZWN0ZWQKICAgIGl0ZW0gaXMgZGlzcGxheWVkIGluIHRoZSBjb250cm9sLiBJZiBubyBpdGVtIGlzIHNlbGVjdGVkLCB0aGUgYGxhYmVsYCBpcwogICAgZGlzcGxheWVkIGluc3RlYWQuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLWRyb3Bkb3duLW1lbnUgbGFiZWw9IllvdXIgZmF2b3VyaXRlIHBhc3RyeSI+CiAgICAgICAgICA8cGFwZXItbGlzdGJveCBzbG90PSJkcm9wZG93bi1jb250ZW50Ij4KICAgICAgICAgICAgPHBhcGVyLWl0ZW0+Q3JvaXNzYW50PC9wYXBlci1pdGVtPgogICAgICAgICAgICA8cGFwZXItaXRlbT5Eb251dDwvcGFwZXItaXRlbT4KICAgICAgICAgICAgPHBhcGVyLWl0ZW0+RmluYW5jaWVyPC9wYXBlci1pdGVtPgogICAgICAgICAgICA8cGFwZXItaXRlbT5NYWRlbGVpbmU8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgoKICAgIFRoaXMgZXhhbXBsZSByZW5kZXJzIGEgZHJvcGRvd24gbWVudSB3aXRoIDQgb3B0aW9ucy4KCiAgICBUaGUgY2hpbGQgZWxlbWVudCB3aXRoIHRoZSBzbG90IGBkcm9wZG93bi1jb250ZW50YCBpcyB1c2VkIGFzIHRoZSBkcm9wZG93bgogICAgbWVudS4gVGhpcyBjYW4gYmUgYSBbYHBhcGVyLWxpc3Rib3hgXShwYXBlci1saXN0Ym94KSwgb3IgYW55IG90aGVyIG9yCiAgICBlbGVtZW50IHRoYXQgYWN0cyBsaWtlIGFuIFtgaXJvbi1zZWxlY3RvcmBdKGlyb24tc2VsZWN0b3IpLgoKICAgIFNwZWNpZmljYWxseSwgdGhlIG1lbnUgY2hpbGQgbXVzdCBmaXJlIGFuCiAgICBbYGlyb24tc2VsZWN0YF0oaXJvbi1zZWxlY3RvciNldmVudC1pcm9uLXNlbGVjdCkgZXZlbnQgd2hlbiBvbmUgb2YgaXRzCiAgICBjaGlsZHJlbiBpcyBzZWxlY3RlZCwgYW5kIGFuCiAgICBbYGlyb24tZGVzZWxlY3RgXShpcm9uLXNlbGVjdG9yI2V2ZW50LWlyb24tZGVzZWxlY3QpIGV2ZW50IHdoZW4gYSBjaGlsZCBpcwogICAgZGVzZWxlY3RlZC4gVGhlIHNlbGVjdGVkIG9yIGRlc2VsZWN0ZWQgaXRlbSBtdXN0IGJlIHBhc3NlZCBhcyB0aGUgZXZlbnQncwogICAgYGRldGFpbC5pdGVtYCBwcm9wZXJ0eS4KCiAgICBBcHBsaWNhdGlvbnMgY2FuIGxpc3RlbiBmb3IgdGhlIGBpcm9uLXNlbGVjdGAgYW5kIGBpcm9uLWRlc2VsZWN0YCBldmVudHMKICAgIHRvIHJlYWN0IHdoZW4gb3B0aW9ucyBhcmUgc2VsZWN0ZWQgYW5kIGRlc2VsZWN0ZWQuCgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGFsc28gYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLWRyb3Bkb3duLW1lbnVgIHwgQSBtaXhpbiB0aGF0IGlzIGFwcGxpZWQgdG8gdGhlIGVsZW1lbnQgaG9zdCB8IGB7fWAKICAgIGAtLXBhcGVyLWRyb3Bkb3duLW1lbnUtZGlzYWJsZWRgIHwgQSBtaXhpbiB0aGF0IGlzIGFwcGxpZWQgdG8gdGhlIGVsZW1lbnQgaG9zdCB3aGVuIGRpc2FibGVkIHwgYHt9YAogICAgYC0tcGFwZXItZHJvcGRvd24tbWVudS1yaXBwbGVgIHwgQSBtaXhpbiB0aGF0IGlzIGFwcGxpZWQgdG8gdGhlIGludGVybmFsIHJpcHBsZSB8IGB7fWAKICAgIGAtLXBhcGVyLWRyb3Bkb3duLW1lbnUtYnV0dG9uYCB8IEEgbWl4aW4gdGhhdCBpcyBhcHBsaWVkIHRvIHRoZSBpbnRlcm5hbCBtZW51IGJ1dHRvbiB8IGB7fWAKICAgIGAtLXBhcGVyLWRyb3Bkb3duLW1lbnUtaW5wdXRgIHwgQSBtaXhpbiB0aGF0IGlzIGFwcGxpZWQgdG8gdGhlIGludGVybmFsIHBhcGVyIGlucHV0IHwgYHt9YAogICAgYC0tcGFwZXItZHJvcGRvd24tbWVudS1pY29uYCB8IEEgbWl4aW4gdGhhdCBpcyBhcHBsaWVkIHRvIHRoZSBpbnRlcm5hbCBpY29uIHwgYHt9YAoKICAgIFlvdSBjYW4gYWxzbyB1c2UgYW55IG9mIHRoZSBgcGFwZXItaW5wdXQtY29udGFpbmVyYCBhbmQgYHBhcGVyLW1lbnUtYnV0dG9uYAogICAgc3R5bGUgbWl4aW5zIGFuZCBjdXN0b20gcHJvcGVydGllcyB0byBzdHlsZSB0aGUgaW50ZXJuYWwgaW5wdXQgYW5kIG1lbnUgYnV0dG9uCiAgICByZXNwZWN0aXZlbHkuCgogICAgQGVsZW1lbnQgcGFwZXItZHJvcGRvd24tbWVudQogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlIGluY2x1ZGU9InBhcGVyLWRyb3Bkb3duLW1lbnUtc2hhcmVkLXN0eWxlcyI+PC9zdHlsZT4KCiAgICA8cGFwZXItbWVudS1idXR0b24gaWQ9Im1lbnVCdXR0b24iIHZlcnRpY2FsLWFsaWduPSJbW3ZlcnRpY2FsQWxpZ25dXSIgaG9yaXpvbnRhbC1hbGlnbj0iW1tob3Jpem9udGFsQWxpZ25dXSIgZHluYW1pYy1hbGlnbj0iW1tkeW5hbWljQWxpZ25dXSIgdmVydGljYWwtb2Zmc2V0PSJbW19jb21wdXRlTWVudVZlcnRpY2FsT2Zmc2V0KG5vTGFiZWxGbG9hdCwgdmVydGljYWxPZmZzZXQpXV0iIGRpc2FibGVkPSJbW2Rpc2FibGVkXV0iIG5vLWFuaW1hdGlvbnM9Iltbbm9BbmltYXRpb25zXV0iIG9uLWlyb24tc2VsZWN0PSJfb25Jcm9uU2VsZWN0IiBvbi1pcm9uLWRlc2VsZWN0PSJfb25Jcm9uRGVzZWxlY3QiIG9wZW5lZD0ie3tvcGVuZWR9fSIgY2xvc2Utb24tYWN0aXZhdGUgYWxsb3ctb3V0c2lkZS1zY3JvbGw9IltbYWxsb3dPdXRzaWRlU2Nyb2xsXV0iIHJlc3RvcmUtZm9jdXMtb24tY2xvc2U9IltbcmVzdG9yZUZvY3VzT25DbG9zZV1dIj4KICAgICAgPCEtLSBzdXBwb3J0IGh5YnJpZCBtb2RlOiB1c2VyIG1pZ2h0IGJlIHVzaW5nIHBhcGVyLW1lbnUtYnV0dG9uIDEueCB3aGljaCBkaXN0cmlidXRlcyB2aWEgPGNvbnRlbnQ+IC0tPgogICAgICA8ZGl2IGNsYXNzPSJkcm9wZG93bi10cmlnZ2VyIiBzbG90PSJkcm9wZG93bi10cmlnZ2VyIj4KICAgICAgICA8cGFwZXItcmlwcGxlPjwvcGFwZXItcmlwcGxlPgogICAgICAgIDwhLS0gcGFwZXItaW5wdXQgaGFzIHR5cGU9InRleHQiIGZvciBhMTF5LCBkbyBub3QgcmVtb3ZlIC0tPgogICAgICAgIDxwYXBlci1pbnB1dCBpZD0iaW5wdXQiIHR5cGU9InRleHQiIGludmFsaWQ9IltbaW52YWxpZF1dIiByZWFkb25seSBkaXNhYmxlZD0iW1tkaXNhYmxlZF1dIiB2YWx1ZT0iW1t2YWx1ZV1dIiBwbGFjZWhvbGRlcj0iW1twbGFjZWhvbGRlcl1dIiBlcnJvci1tZXNzYWdlPSJbW2Vycm9yTWVzc2FnZV1dIiBhbHdheXMtZmxvYXQtbGFiZWw9IltbYWx3YXlzRmxvYXRMYWJlbF1dIiBuby1sYWJlbC1mbG9hdD0iW1tub0xhYmVsRmxvYXRdXSIgbGFiZWw9IltbbGFiZWxdXSIgaW5wdXQtcm9sZT0iYnV0dG9uIiBpbnB1dC1hcmlhLWhhc3BvcHVwPSJsaXN0Ym94IiBhdXRvY29tcGxldGU9Im9mZiI+CiAgICAgICAgICA8IS0tIHN1cHBvcnQgaHlicmlkIG1vZGU6IHVzZXIgbWlnaHQgYmUgdXNpbmcgcGFwZXItaW5wdXQgMS54IHdoaWNoIGRpc3RyaWJ1dGVzIHZpYSA8Y29udGVudD4gLS0+CiAgICAgICAgICA8aXJvbi1pY29uIGljb249InBhcGVyLWRyb3Bkb3duLW1lbnU6YXJyb3ctZHJvcC1kb3duIiBzdWZmaXggc2xvdD0ic3VmZml4Ij48L2lyb24taWNvbj4KICAgICAgICA8L3BhcGVyLWlucHV0PgogICAgICA8L2Rpdj4KICAgICAgPHNsb3QgaWQ9ImNvbnRlbnQiIG5hbWU9ImRyb3Bkb3duLWNvbnRlbnQiIHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiPjwvc2xvdD4KICAgIDwvcGFwZXItbWVudS1idXR0b24+CmAsCgogICAgICBpczogJ3BhcGVyLWRyb3Bkb3duLW1lbnUnLAoKICAgICAgYmVoYXZpb3JzOiBbCiAgICAgICAgSXJvbkJ1dHRvblN0YXRlLAogICAgICAgIElyb25Db250cm9sU3RhdGUsCiAgICAgICAgSXJvbkZvcm1FbGVtZW50QmVoYXZpb3IsCiAgICAgICAgSXJvblZhbGlkYXRhYmxlQmVoYXZpb3IKICAgICAgXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGVyaXZlZCAibGFiZWwiIG9mIHRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbS4gVGhpcyB2YWx1ZQogICAgICAgICAqIGlzIHRoZSBgbGFiZWxgIHByb3BlcnR5IG9uIHRoZSBzZWxlY3RlZCBpdGVtIGlmIHNldCwgb3IgZWxzZSB0aGUKICAgICAgICAgKiB0cmltbWVkIHRleHQgY29udGVudCBvZiB0aGUgc2VsZWN0ZWQgaXRlbS4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZEl0ZW1MYWJlbDoge3R5cGU6IFN0cmluZywgbm90aWZ5OiB0cnVlLCByZWFkT25seTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBsYXN0IHNlbGVjdGVkIGl0ZW0uIEFuIGl0ZW0gaXMgc2VsZWN0ZWQgaWYgdGhlIGRyb3Bkb3duIG1lbnUgaGFzCiAgICAgICAgICogYSBjaGlsZCB3aXRoIHNsb3QgYGRyb3Bkb3duLWNvbnRlbnRgLCBhbmQgdGhhdCBjaGlsZCB0cmlnZ2VycyBhbgogICAgICAgICAqIGBpcm9uLXNlbGVjdGAgZXZlbnQgd2l0aCB0aGUgc2VsZWN0ZWQgYGl0ZW1gIGluIHRoZSBgZGV0YWlsYC4KICAgICAgICAgKgogICAgICAgICAqIEB0eXBlIHs/T2JqZWN0fQogICAgICAgICAqLwogICAgICAgIHNlbGVjdGVkSXRlbToge3R5cGU6IE9iamVjdCwgbm90aWZ5OiB0cnVlLCByZWFkT25seTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSB2YWx1ZSBmb3IgdGhpcyBlbGVtZW50IHRoYXQgd2lsbCBiZSB1c2VkIHdoZW4gc3VibWl0dGluZyBpbgogICAgICAgICAqIGEgZm9ybS4gSXQgcmVmbGVjdHMgdGhlIHZhbHVlIG9mIGBzZWxlY3RlZEl0ZW1MYWJlbGAuIElmIHNldCBkaXJlY3RseSwKICAgICAgICAgKiBpdCB3aWxsIG5vdCB1cGRhdGUgdGhlIGBzZWxlY3RlZEl0ZW1MYWJlbGAgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgdmFsdWU6IHsKICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbGFiZWwgZm9yIHRoZSBkcm9wZG93bi4KICAgICAgICAgKi8KICAgICAgICBsYWJlbDoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBwbGFjZWhvbGRlciBmb3IgdGhlIGRyb3Bkb3duLgogICAgICAgICAqLwogICAgICAgIHBsYWNlaG9sZGVyOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGVycm9yIG1lc3NhZ2UgdG8gZGlzcGxheSB3aGVuIGludmFsaWQuCiAgICAgICAgICovCiAgICAgICAgZXJyb3JNZXNzYWdlOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVHJ1ZSBpZiB0aGUgZHJvcGRvd24gaXMgb3Blbi4gT3RoZXJ3aXNlLCBmYWxzZS4KICAgICAgICAgKi8KICAgICAgICBvcGVuZWQ6CiAgICAgICAgICAgIHt0eXBlOiBCb29sZWFuLCBub3RpZnk6IHRydWUsIHZhbHVlOiBmYWxzZSwgb2JzZXJ2ZXI6ICdfb3BlbmVkQ2hhbmdlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCeSBkZWZhdWx0LCB0aGUgZHJvcGRvd24gd2lsbCBjb25zdHJhaW4gc2Nyb2xsaW5nIG9uIHRoZSBwYWdlCiAgICAgICAgICogdG8gaXRzZWxmIHdoZW4gb3BlbmVkLgogICAgICAgICAqIFNldCB0byB0cnVlIGluIG9yZGVyIHRvIHByZXZlbnQgc2Nyb2xsIGZyb20gYmVpbmcgY29uc3RyYWluZWQKICAgICAgICAgKiB0byB0aGUgZHJvcGRvd24gd2hlbiBpdCBvcGVucy4KICAgICAgICAgKi8KICAgICAgICBhbGxvd091dHNpZGVTY3JvbGw6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNhYmxlIHRoZSBmbG9hdGluZyBsYWJlbC4gQmluZCB0aGlzIHRvIHRoZQogICAgICAgICAqIGA8cGFwZXItaW5wdXQtY29udGFpbmVyPmAncyBgbm9MYWJlbEZsb2F0YCBwcm9wZXJ0eS4KICAgICAgICAgKi8KICAgICAgICBub0xhYmVsRmxvYXQ6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGFsd2F5cyBmbG9hdCB0aGUgbGFiZWwuIEJpbmQgdGhpcyB0byB0aGUKICAgICAgICAgKiBgPHBhcGVyLWlucHV0LWNvbnRhaW5lcj5gJ3MgYGFsd2F5c0Zsb2F0TGFiZWxgIHByb3BlcnR5LgogICAgICAgICAqLwogICAgICAgIGFsd2F5c0Zsb2F0TGFiZWw6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBkaXNhYmxlIGFuaW1hdGlvbnMgd2hlbiBvcGVuaW5nIGFuZCBjbG9zaW5nIHRoZQogICAgICAgICAqIGRyb3Bkb3duLgogICAgICAgICAqLwogICAgICAgIG5vQW5pbWF0aW9uczoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBvcmllbnRhdGlvbiBhZ2FpbnN0IHdoaWNoIHRvIGFsaWduIHRoZSBtZW51IGRyb3Bkb3duCiAgICAgICAgICogaG9yaXpvbnRhbGx5IHJlbGF0aXZlIHRvIHRoZSBkcm9wZG93biB0cmlnZ2VyLgogICAgICAgICAqLwogICAgICAgIGhvcml6b250YWxBbGlnbjoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdyaWdodCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3JpZW50YXRpb24gYWdhaW5zdCB3aGljaCB0byBhbGlnbiB0aGUgbWVudSBkcm9wZG93bgogICAgICAgICAqIHZlcnRpY2FsbHkgcmVsYXRpdmUgdG8gdGhlIGRyb3Bkb3duIHRyaWdnZXIuCiAgICAgICAgICovCiAgICAgICAgdmVydGljYWxBbGlnbjoge3R5cGU6IFN0cmluZywgdmFsdWU6ICd0b3AnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVzIHRoZSB2ZXJ0aWNhbCBvZmZzZXQgY29tcHV0ZWQgaW4KICAgICAgICAgKiBfY29tcHV0ZU1lbnVWZXJ0aWNhbE9mZnNldC4KICAgICAgICAgKi8KICAgICAgICB2ZXJ0aWNhbE9mZnNldDogTnVtYmVyLAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgYGhvcml6b250YWxBbGlnbmAgYW5kIGB2ZXJ0aWNhbEFsaWduYCBwcm9wZXJ0aWVzIHdpbGwKICAgICAgICAgKiBiZSBjb25zaWRlcmVkIHByZWZlcmVuY2VzIGluc3RlYWQgb2Ygc3RyaWN0IHJlcXVpcmVtZW50cyB3aGVuCiAgICAgICAgICogcG9zaXRpb25pbmcgdGhlIGRyb3Bkb3duIGFuZCBtYXkgYmUgY2hhbmdlZCBpZiBkb2luZyBzbyByZWR1Y2VzCiAgICAgICAgICogdGhlIGFyZWEgb2YgdGhlIGRyb3Bkb3duIGZhbGxpbmcgb3V0c2lkZSBvZiBgZml0SW50b2AuCiAgICAgICAgICovCiAgICAgICAgZHluYW1pY0FsaWduOiB7dHlwZTogQm9vbGVhbn0sCgogICAgICAgIC8qKgogICAgICAgICAqIFdoZXRoZXIgZm9jdXMgc2hvdWxkIGJlIHJlc3RvcmVkIHRvIHRoZSBkcm9wZG93biB3aGVuIHRoZSBtZW51IGNsb3Nlcy4KICAgICAgICAgKi8KICAgICAgICByZXN0b3JlRm9jdXNPbkNsb3NlOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IHRydWV9LAogICAgICB9LAoKICAgICAgbGlzdGVuZXJzOiB7J3RhcCc6ICdfb25UYXAnfSwKCiAgICAgIC8qKgogICAgICAgKiBAdHlwZSB7IU9iamVjdH0KICAgICAgICovCiAgICAgIGtleUJpbmRpbmdzOiB7J3VwIGRvd24nOiAnb3BlbicsICdlc2MnOiAnY2xvc2UnfSwKCiAgICAgIG9ic2VydmVyczogWydfc2VsZWN0ZWRJdGVtQ2hhbmdlZChzZWxlY3RlZEl0ZW0pJ10sCgogICAgICAvKioKICAgICAgICogT3ZlcnJpZGUgYF9hdHRhY2hEb21gIHNvIHRoYXQgd2UgY2FuIHBhc3MgYGRlbGVnYXRlc0ZvY3VzYC4gVGhlIG92ZXJyaWRkZW4KICAgICAgICogaW1wbGVtZW50YXRpb24gb2YgYF9hdHRhY2hEb21gIHNwZWNpZmljYWxseSBza2lwcyB0aGUgc3RlcHMgcGVyZm9ybWVkIGhlcmUKICAgICAgICogaWYgdGhlIG5vZGUgYWxyZWFkeSBob3N0cyBhIHNoYWRvdyByb290OgogICAgICAgKiBodHRwczovL2dpdGh1Yi5jb20vUG9seW1lci9wb2x5bWVyL2Jsb2IvNjQwYmM4MGFjNzE3N2I3NjFkNDZiMmZhOWM0NTVjMzE4ZjJiODVjNi9saWIvbWl4aW5zL2VsZW1lbnQtbWl4aW4uanMjTDY5MS1MNjk0CiAgICAgICAqIEBvdmVycmlkZQogICAgICAgKi8KICAgICAgX2F0dGFjaERvbShkb20pIHsKICAgICAgICBjb25zdCB3cmFwcGVkVGhpcyA9IHdyYXAodGhpcyk7CiAgICAgICAgd3JhcHBlZFRoaXMuYXR0YWNoU2hhZG93KHsKICAgICAgICAgIG1vZGU6ICdvcGVuJywKICAgICAgICAgIGRlbGVnYXRlc0ZvY3VzOiB0cnVlLAogICAgICAgICAgc2hhZHlVcGdyYWRlRnJhZ21lbnQ6IGRvbSwKICAgICAgICB9KTsKICAgICAgICB3cmFwcGVkVGhpcy5zaGFkb3dSb290LmFwcGVuZENoaWxkKGRvbSk7CiAgICAgICAgcmV0dXJuIExlZ2FjeVBvbHltZXJFbGVtZW50QmFzZS5wcm90b3R5cGUuX2F0dGFjaERvbS5jYWxsKHRoaXMsIGRvbSk7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGZvY3VzKCkgewogICAgICAgIC8vIFdoZW4gdXNpbmcgU2hhZHkgRE9NIGFuZCBpbiBicm93c2VycyB0aGF0IGRvbid0IHN1cHBvcnQKICAgICAgICAvLyBgZGVsZWdhdGVzRm9jdXNgLCBhdHRlbXB0aW5nIHRvIGZvY3VzIHRoaXMgZWxlbWVudCB3aXRoIHRoZSBicm93c2VyJ3MKICAgICAgICAvLyBuYXRpdmUgYEhUTUxFbGVtZW50I2ZvY3VzYCB3aWxsIGNhdXNlIGZvY3VzIHRvIGJlIGxvc3QgYmVjYXVzZSB0aGlzCiAgICAgICAgLy8gZWxlbWVudCBpc24ndCBmb2N1c2FibGUgaW4gdGhvc2Ugc2l0dWF0aW9ucy4gVG8gd29yayBhcm91bmQgdGhpcywgdGhlCiAgICAgICAgLy8gZWxlbWVudCBpbiB0aGUgc2hhZG93IHJvb3QgdGhhdCB0aGlzIGVsZW1lbnQgaW50ZW5kcyB0byBkZWxlZ2F0ZSBmb2N1cwogICAgICAgIC8vIHRvIGlzIG1hbnVhbGx5IGZvY3VzZWQgaW5zdGVhZC4KICAgICAgICB0aGlzLiQuaW5wdXQuX2ZvY3VzYWJsZUVsZW1lbnQuZm9jdXMoKTsKICAgICAgfSwKCiAgICAgIC8qKiBAb3ZlcnJpZGUgKi8KICAgICAgYXR0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIE5PVEUoY2RhdGEpOiBEdWUgdG8gdGltaW5nLCBhIHByZXNlbGVjdGVkIHZhbHVlIGluIGEgYElyb25TZWxlY3RhYmxlYAogICAgICAgIC8vIGNoaWxkIHdpbGwgY2F1c2UgYW4gYGlyb24tc2VsZWN0YCBldmVudCB0byBmaXJlIHdoaWxlIHRoZSBlbGVtZW50IGlzCiAgICAgICAgLy8gc3RpbGwgaW4gYSBgRG9jdW1lbnRGcmFnbWVudGAuIFRoaXMgaGFzIHRoZSBlZmZlY3Qgb2YgY2F1c2luZwogICAgICAgIC8vIGhhbmRsZXJzIG5vdCB0byBmaXJlLiBTbywgd2UgZG91YmxlIGNoZWNrIHRoaXMgdmFsdWUgb24gYXR0YWNoZWQ6CiAgICAgICAgdmFyIGNvbnRlbnRFbGVtZW50ID0gdGhpcy5jb250ZW50RWxlbWVudDsKICAgICAgICBpZiAoY29udGVudEVsZW1lbnQgJiYgY29udGVudEVsZW1lbnQuc2VsZWN0ZWRJdGVtKSB7CiAgICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW0oY29udGVudEVsZW1lbnQuc2VsZWN0ZWRJdGVtKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIGNvbnRlbnQgZWxlbWVudCB0aGF0IGlzIGNvbnRhaW5lZCBieSB0aGUgZHJvcGRvd24gbWVudSwgaWYgYW55LgogICAgICAgKi8KICAgICAgZ2V0IGNvbnRlbnRFbGVtZW50KCkgewogICAgICAgIC8vIFBvbHltZXIgMi54IHJldHVybnMgc2xvdC5hc3NpZ25lZE5vZGVzIHdoaWNoIGNhbiBjb250YWluIHRleHQgbm9kZXMuCiAgICAgICAgdmFyIG5vZGVzID0gZG9tKHRoaXMuJC5jb250ZW50KS5nZXREaXN0cmlidXRlZE5vZGVzKCk7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBub2Rlcy5sZW5ndGg7IGkgPCBsOyBpKyspIHsKICAgICAgICAgIGlmIChub2Rlc1tpXS5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUpIHsKICAgICAgICAgICAgcmV0dXJuIG5vZGVzW2ldOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTaG93IHRoZSBkcm9wZG93biBjb250ZW50LgogICAgICAgKi8KICAgICAgb3BlbjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy4kLm1lbnVCdXR0b24ub3BlbigpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEhpZGUgdGhlIGRyb3Bkb3duIGNvbnRlbnQuCiAgICAgICAqLwogICAgICBjbG9zZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy4kLm1lbnVCdXR0b24uY2xvc2UoKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBIGhhbmRsZXIgdGhhdCBpcyBjYWxsZWQgd2hlbiBgaXJvbi1zZWxlY3RgIGlzIGZpcmVkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBbiBgaXJvbi1zZWxlY3RgIGV2ZW50LgogICAgICAgKi8KICAgICAgX29uSXJvblNlbGVjdDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW0oZXZlbnQuZGV0YWlsLml0ZW0pOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEEgaGFuZGxlciB0aGF0IGlzIGNhbGxlZCB3aGVuIGBpcm9uLWRlc2VsZWN0YCBpcyBmaXJlZC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtDdXN0b21FdmVudH0gZXZlbnQgQW4gYGlyb24tZGVzZWxlY3RgIGV2ZW50LgogICAgICAgKi8KICAgICAgX29uSXJvbkRlc2VsZWN0OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuX3NldFNlbGVjdGVkSXRlbShudWxsKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBIGhhbmRsZXIgdGhhdCBpcyBjYWxsZWQgd2hlbiB0aGUgZHJvcGRvd24gaXMgdGFwcGVkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBIHRhcCBldmVudC4KICAgICAgICovCiAgICAgIF9vblRhcDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoZmluZE9yaWdpbmFsVGFyZ2V0KGV2ZW50KSA9PT0gdGhpcykgewogICAgICAgICAgdGhpcy5vcGVuKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENvbXB1dGUgdGhlIGxhYmVsIGZvciB0aGUgZHJvcGRvd24gZ2l2ZW4gYSBzZWxlY3RlZCBpdGVtLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IHNlbGVjdGVkSXRlbSBBIHNlbGVjdGVkIEVsZW1lbnQgaXRlbSwgd2l0aCBhbgogICAgICAgKiBvcHRpb25hbCBgbGFiZWxgIHByb3BlcnR5LgogICAgICAgKi8KICAgICAgX3NlbGVjdGVkSXRlbUNoYW5nZWQ6IGZ1bmN0aW9uKHNlbGVjdGVkSXRlbSkgewogICAgICAgIHZhciB2YWx1ZSA9ICcnOwogICAgICAgIGlmICghc2VsZWN0ZWRJdGVtKSB7CiAgICAgICAgICB2YWx1ZSA9ICcnOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB2YWx1ZSA9IHNlbGVjdGVkSXRlbS5sYWJlbCB8fCBzZWxlY3RlZEl0ZW0uZ2V0QXR0cmlidXRlKCdsYWJlbCcpIHx8CiAgICAgICAgICAgICAgc2VsZWN0ZWRJdGVtLnRleHRDb250ZW50LnRyaW0oKTsKICAgICAgICB9CgogICAgICAgIHRoaXMudmFsdWUgPSB2YWx1ZTsKICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW1MYWJlbCh2YWx1ZSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ29tcHV0ZSB0aGUgdmVydGljYWwgb2Zmc2V0IG9mIHRoZSBtZW51IGJhc2VkIG9uIHRoZSB2YWx1ZSBvZgogICAgICAgKiBgbm9MYWJlbEZsb2F0YC4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtib29sZWFufSBub0xhYmVsRmxvYXQgVHJ1ZSBpZiB0aGUgbGFiZWwgc2hvdWxkIG5vdCBmbG9hdAogICAgICAgKiBAcGFyYW0ge251bWJlcj19IG9wdF92ZXJ0aWNhbE9mZnNldCBPcHRpb25hbCBvZmZzZXQgZnJvbSB0aGUgdXNlcgogICAgICAgKiBhYm92ZSB0aGUgaW5wdXQsIG90aGVyd2lzZSBmYWxzZS4KICAgICAgICovCiAgICAgIF9jb21wdXRlTWVudVZlcnRpY2FsT2Zmc2V0OiBmdW5jdGlvbihub0xhYmVsRmxvYXQsIG9wdF92ZXJ0aWNhbE9mZnNldCkgewogICAgICAgIC8vIE92ZXJyaWRlIG9mZnNldCBpZiBpdCdzIHBhc3NlZCBmcm9tIHRoZSB1c2VyLgogICAgICAgIGlmIChvcHRfdmVydGljYWxPZmZzZXQpIHsKICAgICAgICAgIHJldHVybiBvcHRfdmVydGljYWxPZmZzZXQ7CiAgICAgICAgfQoKICAgICAgICAvLyBOT1RFKGNkYXRhKTogVGhlc2UgbnVtYmVycyBhcmUgc29tZXdoYXQgbWFnaWNhbCBiZWNhdXNlIHRoZXkgYXJlCiAgICAgICAgLy8gZGVyaXZlZCBmcm9tIHRoZSBtZXRyaWNzIG9mIGVsZW1lbnRzIGludGVybmFsIHRvIGBwYXBlci1pbnB1dGAncwogICAgICAgIC8vIHRlbXBsYXRlLiBUaGUgbWV0cmljcyB3aWxsIGNoYW5nZSBkZXBlbmRpbmcgb24gd2hldGhlciBvciBub3QgdGhlCiAgICAgICAgLy8gaW5wdXQgaGFzIGEgZmxvYXRpbmcgbGFiZWwuCiAgICAgICAgcmV0dXJuIG5vTGFiZWxGbG9hdCA/IC00IDogODsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGZhbHNlIGlmIHRoZSBlbGVtZW50IGlzIHJlcXVpcmVkIGFuZCBkb2VzIG5vdCBoYXZlIGEgc2VsZWN0aW9uLAogICAgICAgKiBhbmQgdHJ1ZSBvdGhlcndpc2UuCiAgICAgICAqIEBwYXJhbSB7Kj19IF92YWx1ZSBJZ25vcmVkLgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSB0cnVlIGlmIGByZXF1aXJlZGAgaXMgZmFsc2UsIG9yIGlmIGByZXF1aXJlZGAgaXMgdHJ1ZQogICAgICAgKiBhbmQgdGhlIGVsZW1lbnQgaGFzIGEgdmFsaWQgc2VsZWN0aW9uLgogICAgICAgKi8KICAgICAgX2dldFZhbGlkaXR5OiBmdW5jdGlvbihfdmFsdWUpIHsKICAgICAgICByZXR1cm4gdGhpcy5kaXNhYmxlZCB8fCAhdGhpcy5yZXF1aXJlZCB8fCAodGhpcy5yZXF1aXJlZCAmJiAhIXRoaXMudmFsdWUpOwogICAgICB9LAoKICAgICAgX29wZW5lZENoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBvcGVuU3RhdGUgPSB0aGlzLm9wZW5lZCA/ICd0cnVlJyA6ICdmYWxzZSc7CiAgICAgICAgdmFyIGUgPSB0aGlzLmNvbnRlbnRFbGVtZW50OwogICAgICAgIGlmIChlKSB7CiAgICAgICAgICBlLnNldEF0dHJpYnV0ZSgnYXJpYS1leHBhbmRlZCcsIG9wZW5TdGF0ZSk7CiAgICAgICAgfQogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICB2YXIgU0hBRE9XX1dIRU5fU0NST0xMSU5HID0gMTsKICAgIHZhciBTSEFET1dfQUxXQVlTID0gMjsKICAgIHZhciBNT0RFX0NPTkZJR1MgPSB7CiAgICAgIG91dGVyU2Nyb2xsOiB7J3Njcm9sbCc6IHRydWV9LAoKICAgICAgc2hhZG93TW9kZTogewogICAgICAgICdzdGFuZGFyZCc6IFNIQURPV19BTFdBWVMsCiAgICAgICAgJ3dhdGVyZmFsbCc6IFNIQURPV19XSEVOX1NDUk9MTElORywKICAgICAgICAnd2F0ZXJmYWxsLXRhbGwnOiBTSEFET1dfV0hFTl9TQ1JPTExJTkcKICAgICAgfSwKCiAgICAgIHRhbGxNb2RlOiB7J3dhdGVyZmFsbC10YWxsJzogdHJ1ZX0KICAgIH07CgogICAgLyoqCiAgICAqKlRoaXMgZWxlbWVudCBoYXMgYmVlbiBkZXByZWNhdGVkIGluIGZhdm9yIG9mCiAgICBbYXBwLWxheW91dF0oaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9hcHAtbGF5b3V0KS4qKgoKICAgIGBwYXBlci1oZWFkZXItcGFuZWxgIGNvbnRhaW5zIGEgaGVhZGVyIHNlY3Rpb24gYW5kIGEgY29udGVudCBwYW5lbCBzZWN0aW9uLgoKICAgIF9fSW1wb3J0YW50Ol9fIFRoZSBgcGFwZXItaGVhZGVyLXBhbmVsYCB3aWxsIG5vdCBkaXNwbGF5IGlmIGl0cyBwYXJlbnQgZG9lcyBub3QKICAgIGhhdmUgYSBoZWlnaHQuCgogICAgVXNpbmcgbGF5b3V0IGNsYXNzZXMsIHlvdSBjYW4gbWFrZSB0aGUgYHBhcGVyLWhlYWRlci1wYW5lbGAgZmlsbCB0aGUgc2NyZWVuCgogICAgICAgIDxib2R5IGNsYXNzPSJmdWxsYmxlZWQgbGF5b3V0IHZlcnRpY2FsIj4KICAgICAgICAgIDxwYXBlci1oZWFkZXItcGFuZWwgY2xhc3M9ImZsZXgiPgogICAgICAgICAgICA8cGFwZXItdG9vbGJhciBzbG90PSJoZWFkZXIiPgogICAgICAgICAgICAgIDxkaXY+SGVsbG8gV29ybGQhPC9kaXY+CiAgICAgICAgICAgIDwvcGFwZXItdG9vbGJhcj4KICAgICAgICAgIDwvcGFwZXItaGVhZGVyLXBhbmVsPgogICAgICAgIDwvYm9keT4KCiAgICBTcGVjaWFsIHN1cHBvcnQgaXMgcHJvdmlkZWQgZm9yIHNjcm9sbGluZyBtb2RlcyB3aGVuIG9uZSB1c2VzIGEgcGFwZXItdG9vbGJhciBvcgogICAgZXF1aXZhbGVudCBmb3IgdGhlIGhlYWRlciBzZWN0aW9uLgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1oZWFkZXItcGFuZWw+CiAgICAgICAgICA8cGFwZXItdG9vbGJhciBzbG90PSJoZWFkZXIiPkhlYWRlcjwvcGFwZXItdG9vbGJhcj4KICAgICAgICAgIDxkaXY+Q29udGVudCBnb2VzIGhlcmUuLi48L2Rpdj4KICAgICAgICA8L3BhcGVyLWhlYWRlci1wYW5lbD4KCiAgICBUbyBoYXZlIHRoZSBjb250ZW50IGZpdCB0byB0aGUgbWFpbiBhcmVhLCB1c2UgdGhlIGBmaXRgIGNsYXNzLgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1oZWFkZXItcGFuZWw+CiAgICAgICAgICA8ZGl2IHNsb3Q9ImhlYWRlciI+c3RhbmRhcmQ8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImZpdCI+Y29udGVudCBmaXRzIDEwMCUgYmVsb3cgdGhlIGhlYWRlcjwvZGl2PgogICAgICAgIDwvcGFwZXItaGVhZGVyLXBhbmVsPgoKICAgICMjIyBNb2RlcwoKICAgIENvbnRyb2xzIGhlYWRlciBhbmQgc2Nyb2xsaW5nIGJlaGF2aW9yLiBPcHRpb25zIGFyZSBgc3RhbmRhcmRgLCBgc2VhbWVkYCwKICAgIGB3YXRlcmZhbGxgLCBgd2F0ZXJmYWxsLXRhbGxgLCBgc2Nyb2xsYCBhbmQgYGNvdmVyYC4gRGVmYXVsdCBpcyBgc3RhbmRhcmRgLgoKICAgIE1vZGUgfCBEZXNjcmlwdGlvbgogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tCiAgICBgc3RhbmRhcmRgIHwgVGhlIGhlYWRlciBpcyBhIHN0ZXAgYWJvdmUgdGhlIHBhbmVsLiBUaGUgaGVhZGVyIHdpbGwgY29uc3VtZSB0aGUgcGFuZWwgYXQgdGhlIHBvaW50IG9mIGVudHJ5LCBwcmV2ZW50aW5nIGl0IGZyb20gcGFzc2luZyB0aHJvdWdoIHRvIHRoZSBvcHBvc2l0ZSBzaWRlLgogICAgYHNlYW1lZGAgfCBUaGUgaGVhZGVyIGlzIHByZXNlbnRlZCBhcyBzZWFtZWQgd2l0aCB0aGUgcGFuZWwuCiAgICBgd2F0ZXJmYWxsYCB8IFNpbWlsYXIgdG8gc3RhbmRhcmQgbW9kZSwgYnV0IGhlYWRlciBpcyBpbml0aWFsbHkgcHJlc2VudGVkIGFzIHNlYW1lZCB3aXRoIHBhbmVsLCBidXQgdGhlbiBzZXBhcmF0ZXMgdG8gZm9ybSB0aGUgc3RlcC4KICAgIGB3YXRlcmZhbGwtdGFsbGAgfCBUaGUgaGVhZGVyIGlzIGluaXRpYWxseSB0YWxsZXIgKGB0YWxsYCBjbGFzcyBpcyBhZGRlZCB0byB0aGUgaGVhZGVyKS4gQXMgdGhlIHVzZXIgc2Nyb2xscywgdGhlIGhlYWRlciBzZXBhcmF0ZXMgKGZvcm1pbmcgYW4gZWRnZSkgd2hpbGUgY29uZGVuc2luZyAoYHRhbGxgIGNsYXNzIGlzIHJlbW92ZWQgZnJvbSB0aGUgaGVhZGVyKS4KICAgIGBzY3JvbGxgIHwgVGhlIGhlYWRlciBrZWVwcyBpdHMgc2VhbSB3aXRoIHRoZSBwYW5lbCwgYW5kIGlzIHB1c2hlZCBvZmYgc2NyZWVuLgogICAgYGNvdmVyYCB8IFRoZSBwYW5lbCBjb3ZlcnMgdGhlIHdob2xlIGBwYXBlci1oZWFkZXItcGFuZWxgIGluY2x1ZGluZyB0aGUgaGVhZGVyLiBUaGlzIGFsbG93cyB1c2VyIHRvIHN0eWxlIHRoZSBwYW5lbCBpbiBzdWNoIGEgd2F5IHRoYXQgdGhlIHBhbmVsIGlzIHBhcnRpYWxseSBjb3ZlcmluZyB0aGUgaGVhZGVyLgoKICAgICMjIyBTdHlsaW5nCgogICAgVG8gY2hhbmdlIHRoZSBzaGFkb3cgdGhhdCBzaG93cyB1cCB1bmRlcm5lYXRoIHRoZSBoZWFkZXI6CgogICAgICAgIHBhcGVyLWhlYWRlci1wYW5lbCB7CiAgICAgICAgICAtLXBhcGVyLWhlYWRlci1wYW5lbC1zaGFkb3c6IHsKICAgICAgICAgICAgICBoZWlnaHQ6IDZweDsKICAgICAgICAgICAgICBib3R0b206IC02cHg7CiAgICAgICAgICAgICAgYm94LXNoYWRvdzogaW5zZXQgMHB4IDVweCA2cHggLTNweCByZ2JhKDAsIDAsIDAsIDAuNCk7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICBUbyBjaGFuZ2UgdGhlIHBhbmVsIGNvbnRhaW5lcjoKCiAgICAgICAgcGFwZXItaGVhZGVyLXBhbmVsIHsKICAgICAgICAgIC0tcGFwZXItaGVhZGVyLXBhbmVsLWNvbnRhaW5lcjogewogICAgICAgICAgICBib3JkZXI6IDFweCBzb2xpZCBncmF5OwogICAgICAgICAgfTsKCiAgICBUbyBjaGFuZ2UgdGhlIHBhbmVsIGNvbnRhaW5lciBpbiBkaWZmZXJlbnQgbW9kZXM6CgogICAgICAgIHBhcGVyLWhlYWRlci1wYW5lbCB7CiAgICAgICAgICAtLXBhcGVyLWhlYWRlci1wYW5lbC1zdGFuZGFyZC1jb250YWluZXI6IHsKICAgICAgICAgICAgYm9yZGVyOiAxcHggc29saWQgZ3JheTsKICAgICAgICAgIH07CgogICAgICAgICAgLS1wYXBlci1oZWFkZXItcGFuZWwtc2VhbWVkLWNvbnRhaW5lcjogewogICAgICAgICAgICBib3JkZXI6IDFweCBzb2xpZCBncmF5OwogICAgICAgICAgfTsKCiAgICAgICAgICAtLXBhcGVyLWhlYWRlci1wYW5lbC13YXRlcmZhbGwtY29udGFpbmVyOiB7CiAgICAgICAgICAgIGJvcmRlcjogMXB4IHNvbGlkIGdyYXk7CiAgICAgICAgICB9OwoKICAgICAgICAgIC0tcGFwZXItaGVhZGVyLXBhbmVsLXdhdGVyZmFsbC10YWxsLWNvbnRhaW5lcjogewogICAgICAgICAgICBib3JkZXI6IDFweCBzb2xpZCBncmF5OwogICAgICAgICAgfTsKCiAgICAgICAgICAtLXBhcGVyLWhlYWRlci1wYW5lbC1zY3JvbGwtY29udGFpbmVyOiB7CiAgICAgICAgICAgIGJvcmRlcjogMXB4IHNvbGlkIGdyYXk7CiAgICAgICAgICB9OwoKICAgICAgICAgIC0tcGFwZXItaGVhZGVyLXBhbmVsLWNvdmVyLWNvbnRhaW5lcjogewogICAgICAgICAgICBib3JkZXI6IDFweCBzb2xpZCBncmF5OwogICAgICAgICAgfTsKICAgICAgICB9CgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItaGVhZGVyLXBhbmVsYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGVsZW1lbnQgfCBge31gCiAgICBgLS1wYXBlci1oZWFkZXItcGFuZWwtYm9keWAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBlbGVtZW50J3MgYm9keSAoaS5lLiBldmVyeXRoaW5nIGJlbG93IHRoZSB0b29sYmFyKSB8IGB7fWAKICAgIGAtLXBhcGVyLWhlYWRlci1wYW5lbC1jb250YWluZXJgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgY29udGFpbmVyIGluIGFueSBtb2RlIHwgYHt9YAogICAgYC0tcGFwZXItaGVhZGVyLXBhbmVsLXNjcm9sbC1jb250YWluZXJgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgY29udGFpbmVyIHdoZW4gaW4gc2Nyb2xsIG1vZGUgfCBge31gCiAgICBgLS1wYXBlci1oZWFkZXItcGFuZWwtY292ZXItY29udGFpbmVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGNvbnRhaW5lciB3aGVuIGluIGNvdmVyIG1vZGUgfCBge31gCiAgICBgLS1wYXBlci1oZWFkZXItcGFuZWwtc3RhbmRhcmQtY29udGFpbmVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGNvbnRhaW5lciB3aGVuIGluIHN0YW5kYXJkIG1vZGUgfCBge31gCiAgICBgLS1wYXBlci1oZWFkZXItcGFuZWwtc2VhbWVkLWNvbnRhaW5lcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBjb250YWluZXIgd2hlbiBpbiBzZWFtZWQgbW9kZSB8IGB7fWAKICAgIGAtLXBhcGVyLWhlYWRlci1wYW5lbC13YXRlcmZhbGwtY29udGFpbmVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGNvbnRhaW5lciB3aGVuIGluIHdhdGVyZmFsbCBtb2RlIHwgYHt9YAogICAgYC0tcGFwZXItaGVhZGVyLXBhbmVsLXdhdGVyZmFsbC10YWxsLWNvbnRhaW5lcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBjb250YWluZXIgd2hlbiBpbiB0YWxsIHdhdGVyZmFsbCBtb2RlIHwgYHt9YAogICAgYC0tcGFwZXItaGVhZGVyLXBhbmVsLXNoYWRvd2AgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB3YXRlcmZhbGwgc2hhZG93IHwgYHt9YAoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItaGVhZGVyLXBhbmVsCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgIEBoZXJvIGhlcm8uc3ZnCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIEBhcHBseSAtLWxheW91dC12ZXJ0aWNhbDsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWhlYWRlci1wYW5lbDsKICAgICAgfQoKICAgICAgI21haW5Db250YWluZXIgewogICAgICAgIEBhcHBseSAtLWxheW91dC1mbGV4OwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBvdmVyZmxvdy15OiBhdXRvOwogICAgICAgIG92ZXJmbG93LXg6IGhpZGRlbjsKICAgICAgICAtd2Via2l0LW92ZXJmbG93LXNjcm9sbGluZzogdG91Y2g7CiAgICAgIH0KCiAgICAgICNtYWluUGFuZWwgewogICAgICAgIEBhcHBseSAtLWxheW91dC12ZXJ0aWNhbDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtZmxleDsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgbWluLWhlaWdodDogMDsKICAgICAgICBAYXBwbHkgLS1wYXBlci1oZWFkZXItcGFuZWwtYm9keTsKICAgICAgfQoKICAgICAgI21haW5Db250YWluZXIgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWhlYWRlci1wYW5lbC1jb250YWluZXI7CiAgICAgIH0KCiAgICAgIC8qCiAgICAgICAqIG1vZGU6IHNjcm9sbAogICAgICAgKi8KICAgICAgOmhvc3QoW21vZGU9c2Nyb2xsXSkgI21haW5Db250YWluZXIgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWhlYWRlci1wYW5lbC1zY3JvbGwtY29udGFpbmVyOwogICAgICAgIG92ZXJmbG93OiB2aXNpYmxlOwogICAgICB9CgogICAgICA6aG9zdChbbW9kZT1zY3JvbGxdKSB7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgLXdlYmtpdC1vdmVyZmxvdy1zY3JvbGxpbmc6IHRvdWNoOwogICAgICB9CgogICAgICAvKgogICAgICAgKiBtb2RlOiBjb3ZlcgogICAgICAgKi8KICAgICAgOmhvc3QoW21vZGU9Y292ZXJdKSAjbWFpbkNvbnRhaW5lciB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaGVhZGVyLXBhbmVsLWNvdmVyLWNvbnRhaW5lcjsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICB9CgogICAgICA6aG9zdChbbW9kZT1jb3Zlcl0pICNtYWluUGFuZWwgewogICAgICAgIHBvc2l0aW9uOiBzdGF0aWM7CiAgICAgIH0KCiAgICAgIC8qCiAgICAgICAqIG1vZGU6IHN0YW5kYXJkCiAgICAgICAqLwogICAgICA6aG9zdChbbW9kZT1zdGFuZGFyZF0pICNtYWluQ29udGFpbmVyIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1oZWFkZXItcGFuZWwtc3RhbmRhcmQtY29udGFpbmVyOwogICAgICB9CgogICAgICAvKgogICAgICAgKiBtb2RlOiBzZWFtZWQKICAgICAgICovCiAgICAgIDpob3N0KFttb2RlPXNlYW1lZF0pICNtYWluQ29udGFpbmVyIHsKICAgICAgICBAYXBwbHkgLS1wYXBlci1oZWFkZXItcGFuZWwtc2VhbWVkLWNvbnRhaW5lcjsKICAgICAgfQoKCiAgICAgIC8qCiAgICAgICAqIG1vZGU6IHdhdGVyZmFsbAogICAgICAgKi8KICAgICAgOmhvc3QoW21vZGU9d2F0ZXJmYWxsXSkgI21haW5Db250YWluZXIgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWhlYWRlci1wYW5lbC13YXRlcmZhbGwtY29udGFpbmVyOwogICAgICB9CgogICAgICAvKgogICAgICAgKiBtb2RlOiB3YXRlcmZhbGwtdGFsbAogICAgICAgKi8KICAgICAgOmhvc3QoW21vZGU9d2F0ZXJmYWxsLXRhbGxdKSAjbWFpbkNvbnRhaW5lciB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItaGVhZGVyLXBhbmVsLXdhdGVyZmFsbC10YWxsLWNvbnRhaW5lcjsKICAgICAgfQoKICAgICAgI2Ryb3BTaGFkb3cgewogICAgICAgIHRyYW5zaXRpb246IG9wYWNpdHkgMC41czsKICAgICAgICBoZWlnaHQ6IDZweDsKICAgICAgICBib3gtc2hhZG93OiBpbnNldCAwcHggNXB4IDZweCAtM3B4IHJnYmEoMCwgMCwgMCwgMC40KTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1oZWFkZXItcGFuZWwtc2hhZG93OwogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgICByaWdodDogMDsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICB9CgogICAgICAjZHJvcFNoYWRvdy5oYXMtc2hhZG93IHsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICB9CgogICAgICAjbWFpbkNvbnRhaW5lciA+IDo6c2xvdHRlZCguZml0KSB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZpdDsKICAgICAgfQoKICAgIDwvc3R5bGU+CgogICAgPHNsb3QgaWQ9ImhlYWRlclNsb3QiIG5hbWU9ImhlYWRlciI+PC9zbG90PgoKICAgIDxkaXYgaWQ9Im1haW5QYW5lbCI+CiAgICAgIDxkaXYgaWQ9Im1haW5Db250YWluZXIiIGNsYXNzXCQ9IltbX2NvbXB1dGVNYWluQ29udGFpbmVyQ2xhc3MobW9kZSldXSI+CiAgICAgICAgPHNsb3Q+PC9zbG90PgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBpZD0iZHJvcFNoYWRvdyI+PC9kaXY+CiAgICA8L2Rpdj4KYCwKCiAgICAgIGlzOiAncGFwZXItaGVhZGVyLXBhbmVsJywKCiAgICAgIC8qKgogICAgICAgKiBGaXJlZCB3aGVuIHRoZSBjb250ZW50IGhhcyBiZWVuIHNjcm9sbGVkLiBgZXZlbnQuZGV0YWlsLnRhcmdldGAgcmV0dXJucwogICAgICAgKiB0aGUgc2Nyb2xsYWJsZSBlbGVtZW50IHdoaWNoIHlvdSBjYW4gdXNlIHRvIGFjY2VzcyBzY3JvbGwgaW5mbyBzdWNoIGFzCiAgICAgICAqIGBzY3JvbGxUb3BgLgogICAgICAgKgogICAgICAgKiAgICAgPHBhcGVyLWhlYWRlci1wYW5lbCBvbi1jb250ZW50LXNjcm9sbD0ic2Nyb2xsSGFuZGxlciI+CiAgICAgICAqICAgICAgIC4uLgogICAgICAgKiAgICAgPC9wYXBlci1oZWFkZXItcGFuZWw+CiAgICAgICAqCiAgICAgICAqCiAgICAgICAqICAgICBzY3JvbGxIYW5kbGVyOiBmdW5jdGlvbihldmVudCkgewogICAgICAgKiAgICAgICB2YXIgc2Nyb2xsZXIgPSBldmVudC5kZXRhaWwudGFyZ2V0OwogICAgICAgKiAgICAgICBjb25zb2xlLmxvZyhzY3JvbGxlci5zY3JvbGxUb3ApOwogICAgICAgKiAgICAgfQogICAgICAgKgogICAgICAgKiBAZXZlbnQgY29udGVudC1zY3JvbGwKICAgICAgICovCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29udHJvbHMgaGVhZGVyIGFuZCBzY3JvbGxpbmcgYmVoYXZpb3IuIE9wdGlvbnMgYXJlCiAgICAgICAgICogYHN0YW5kYXJkYCwgYHNlYW1lZGAsIGB3YXRlcmZhbGxgLCBgd2F0ZXJmYWxsLXRhbGxgLCBgc2Nyb2xsYCBhbmQKICAgICAgICAgKiBgY292ZXJgLiBEZWZhdWx0IGlzIGBzdGFuZGFyZGAuCiAgICAgICAgICoKICAgICAgICAgKiBgc3RhbmRhcmRgOiBUaGUgaGVhZGVyIGlzIGEgc3RlcCBhYm92ZSB0aGUgcGFuZWwuIFRoZSBoZWFkZXIgd2lsbCBjb25zdW1lCiAgICAgICAgICogdGhlIHBhbmVsIGF0IHRoZSBwb2ludCBvZiBlbnRyeSwgcHJldmVudGluZyBpdCBmcm9tIHBhc3NpbmcgdGhyb3VnaCB0bwogICAgICAgICAqIHRoZSBvcHBvc2l0ZSBzaWRlLgogICAgICAgICAqCiAgICAgICAgICogYHNlYW1lZGA6IFRoZSBoZWFkZXIgaXMgcHJlc2VudGVkIGFzIHNlYW1lZCB3aXRoIHRoZSBwYW5lbC4KICAgICAgICAgKgogICAgICAgICAqIGB3YXRlcmZhbGxgOiBTaW1pbGFyIHRvIHN0YW5kYXJkIG1vZGUsIGJ1dCBoZWFkZXIgaXMgaW5pdGlhbGx5IHByZXNlbnRlZAogICAgICAgICAqIGFzIHNlYW1lZCB3aXRoIHBhbmVsLCBidXQgdGhlbiBzZXBhcmF0ZXMgdG8gZm9ybSB0aGUgc3RlcC4KICAgICAgICAgKgogICAgICAgICAqIGB3YXRlcmZhbGwtdGFsbGA6IFRoZSBoZWFkZXIgaXMgaW5pdGlhbGx5IHRhbGxlciAoYHRhbGxgIGNsYXNzIGlzIGFkZGVkCiAgICAgICAgICogdG8gdGhlIGhlYWRlcikuICBBcyB0aGUgdXNlciBzY3JvbGxzLCB0aGUgaGVhZGVyIHNlcGFyYXRlcyAoZm9ybWluZyBhbgogICAgICAgICAqIGVkZ2UpIHdoaWxlIGNvbmRlbnNpbmcgKGB0YWxsYCBjbGFzcyBpcyByZW1vdmVkIGZyb20gdGhlIGhlYWRlcikuCiAgICAgICAgICoKICAgICAgICAgKiBgc2Nyb2xsYDogVGhlIGhlYWRlciBrZWVwcyBpdHMgc2VhbSB3aXRoIHRoZSBwYW5lbCwgYW5kIGlzIHB1c2hlZCBvZmYKICAgICAgICAgKiBzY3JlZW4uCiAgICAgICAgICoKICAgICAgICAgKiBgY292ZXJgOiBUaGUgcGFuZWwgY292ZXJzIHRoZSB3aG9sZSBgcGFwZXItaGVhZGVyLXBhbmVsYCBpbmNsdWRpbmcgdGhlCiAgICAgICAgICogaGVhZGVyLiBUaGlzIGFsbG93cyB1c2VyIHRvIHN0eWxlIHRoZSBwYW5lbCBpbiBzdWNoIGEgd2F5IHRoYXQgdGhlIHBhbmVsCiAgICAgICAgICogaXMgcGFydGlhbGx5IGNvdmVyaW5nIHRoZSBoZWFkZXIuCiAgICAgICAgICoKICAgICAgICAgKiAgICAgPHBhcGVyLWhlYWRlci1wYW5lbCBtb2RlPSJjb3ZlciI+CiAgICAgICAgICogICAgICAgPHBhcGVyLXRvb2xiYXIgc2xvdD0iaGVhZGVyIiBjbGFzcz0idGFsbCI+CiAgICAgICAgICogICAgICAgICA8cGFwZXItaWNvbi1idXR0b24gaWNvbj0ibWVudSI+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgKiAgICAgICA8L3BhcGVyLXRvb2xiYXI+CiAgICAgICAgICogICAgICAgPGRpdj48L2Rpdj4KICAgICAgICAgKiAgICAgPC9wYXBlci1oZWFkZXItcGFuZWw+CiAgICAgICAgICovCiAgICAgICAgbW9kZTogewogICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgdmFsdWU6ICdzdGFuZGFyZCcsCiAgICAgICAgICBvYnNlcnZlcjogJ19tb2RlQ2hhbmdlZCcsCiAgICAgICAgICByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWUKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgZHJvcC1zaGFkb3cgaXMgYWx3YXlzIHNob3duIG5vIG1hdHRlciB3aGF0IG1vZGUgaXMgc2V0IHRvLgogICAgICAgICAqLwogICAgICAgIHNoYWRvdzoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjbGFzcyB1c2VkIGluIHdhdGVyZmFsbC10YWxsIG1vZGUuICBDaGFuZ2UgdGhpcyBpZiB0aGUgaGVhZGVyCiAgICAgICAgICogYWNjZXB0cyBhIGRpZmZlcmVudCBjbGFzcyBmb3IgdG9nZ2xpbmcgaGVpZ2h0LCBlLmcuICJtZWRpdW0tdGFsbCIKICAgICAgICAgKi8KICAgICAgICB0YWxsQ2xhc3M6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAndGFsbCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgc2Nyb2xsZXIgaXMgYXQgdGhlIHRvcAogICAgICAgICAqLwogICAgICAgIGF0VG9wOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgdmFsdWU6IHRydWUsCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICByZWFkT25seTogdHJ1ZSwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWydfY29tcHV0ZURyb3BTaGFkb3dIaWRkZW4oYXRUb3AsIG1vZGUsIHNoYWRvdyknXSwKCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9hZGRMaXN0ZW5lcigpOwogICAgICAgIC8vIFJ1biBgc2Nyb2xsYCBsb2dpYyBvbmNlIHRvIGluaXRpYWxpemUgY2xhc3MgbmFtZXMsIGV0Yy4KICAgICAgICB0aGlzLl9rZWVwU2Nyb2xsaW5nU3RhdGUoKTsKICAgICAgfSwKCiAgICAgIGRldGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9yZW1vdmVMaXN0ZW5lcigpOwogICAgICB9LAoKICAgICAgcmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc2Nyb2xsSGFuZGxlciA9IHRoaXMuX3Njcm9sbC5iaW5kKHRoaXMpOwogICAgICAgIGNvbnNvbGUud2Fybih0aGlzLmlzLCAnaXMgZGVwcmVjYXRlZC4gUGxlYXNlIHVzZSBhcHAtbGF5b3V0IGluc3RlYWQhJyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgaGVhZGVyIGVsZW1lbnQKICAgICAgICogQHJldHVybiB7IUVsZW1lbnR8dW5kZWZpbmVkfQogICAgICAgKi8KICAgICAgZ2V0IGhlYWRlcigpIHsKICAgICAgICByZXR1cm4gZG9tKHRoaXMuJC5oZWFkZXJTbG90KS5nZXREaXN0cmlidXRlZE5vZGVzKClbMF07CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgc2Nyb2xsYWJsZSBlbGVtZW50LgogICAgICAgKiBAcmV0dXJuIHshSFRNTEVsZW1lbnR9CiAgICAgICAqLwogICAgICBnZXQgc2Nyb2xsZXIoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2dldFNjcm9sbGVyRm9yTW9kZSh0aGlzLm1vZGUpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgc2Nyb2xsZXIgaGFzIGEgdmlzaWJsZSBzaGFkb3cuCiAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59CiAgICAgICAqLwogICAgICBnZXQgdmlzaWJsZVNoYWRvdygpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLmRyb3BTaGFkb3cuY2xhc3NMaXN0LmNvbnRhaW5zKCdoYXMtc2hhZG93Jyk7CiAgICAgIH0sCgogICAgICBfY29tcHV0ZURyb3BTaGFkb3dIaWRkZW46IGZ1bmN0aW9uKGF0VG9wLCBtb2RlLCBzaGFkb3cpIHsKICAgICAgICB2YXIgc2hhZG93TW9kZSA9IE1PREVfQ09ORklHUy5zaGFkb3dNb2RlW21vZGVdOwoKICAgICAgICBpZiAodGhpcy5zaGFkb3cpIHsKICAgICAgICAgIHRoaXMudG9nZ2xlQ2xhc3MoJ2hhcy1zaGFkb3cnLCB0cnVlLCB0aGlzLiQuZHJvcFNoYWRvdyk7CiAgICAgICAgfSBlbHNlIGlmIChzaGFkb3dNb2RlID09PSBTSEFET1dfQUxXQVlTKSB7CiAgICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdoYXMtc2hhZG93JywgdHJ1ZSwgdGhpcy4kLmRyb3BTaGFkb3cpOwogICAgICAgIH0gZWxzZSBpZiAoc2hhZG93TW9kZSA9PT0gU0hBRE9XX1dIRU5fU0NST0xMSU5HICYmICFhdFRvcCkgewogICAgICAgICAgdGhpcy50b2dnbGVDbGFzcygnaGFzLXNoYWRvdycsIHRydWUsIHRoaXMuJC5kcm9wU2hhZG93KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy50b2dnbGVDbGFzcygnaGFzLXNoYWRvdycsIGZhbHNlLCB0aGlzLiQuZHJvcFNoYWRvdyk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2NvbXB1dGVNYWluQ29udGFpbmVyQ2xhc3M6IGZ1bmN0aW9uKG1vZGUpIHsKICAgICAgICAvLyBUT0RPOiAgSXQgd2lsbCBiZSB1c2VmdWwgdG8gaGF2ZSBhIHV0aWxpdHkgZm9yIGNsYXNzZXMKICAgICAgICAvLyBlLmcuIFBvbHltZXIuVXRpbHMuY2xhc3Nlcyh7IGZvbzogdHJ1ZSB9KTsKCiAgICAgICAgdmFyIGNsYXNzZXMgPSB7fTsKCiAgICAgICAgY2xhc3Nlc1snZmxleCddID0gbW9kZSAhPT0gJ2NvdmVyJzsKCiAgICAgICAgcmV0dXJuIE9iamVjdC5rZXlzKGNsYXNzZXMpCiAgICAgICAgICAgIC5maWx0ZXIoZnVuY3Rpb24oY2xhc3NOYW1lKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGNsYXNzZXNbY2xhc3NOYW1lXTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgLmpvaW4oJyAnKTsKICAgICAgfSwKCiAgICAgIF9hZGRMaXN0ZW5lcjogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zY3JvbGxlci5hZGRFdmVudExpc3RlbmVyKCdzY3JvbGwnLCB0aGlzLnNjcm9sbEhhbmRsZXIpOwogICAgICB9LAoKICAgICAgX3JlbW92ZUxpc3RlbmVyOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNjcm9sbGVyLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3Njcm9sbCcsIHRoaXMuc2Nyb2xsSGFuZGxlcik7CiAgICAgIH0sCgogICAgICBfbW9kZUNoYW5nZWQ6IGZ1bmN0aW9uKG5ld01vZGUsIG9sZE1vZGUpIHsKICAgICAgICB2YXIgY29uZmlncyA9IE1PREVfQ09ORklHUzsKICAgICAgICB2YXIgaGVhZGVyID0gdGhpcy5oZWFkZXI7CiAgICAgICAgdmFyIGFuaW1hdGVEdXJhdGlvbiA9IDIwMDsKCiAgICAgICAgaWYgKGhlYWRlcikgewogICAgICAgICAgLy8gaW4gdGFsbE1vZGUgaXQgbWF5IGFkZCB0YWxsQ2xhc3MgdG8gdGhlIGhlYWRlcjsgc28gZG8gdGhlIGNsZWFudXAKICAgICAgICAgIC8vIHdoZW4gbW9kZSBpcyBjaGFuZ2VkIGZyb20gdGFsbE1vZGUgdG8gbm90IHRhbGxNb2RlCiAgICAgICAgICBpZiAoY29uZmlncy50YWxsTW9kZVtvbGRNb2RlXSAmJiAhY29uZmlncy50YWxsTW9kZVtuZXdNb2RlXSkgewogICAgICAgICAgICBoZWFkZXIuY2xhc3NMaXN0LnJlbW92ZSh0aGlzLnRhbGxDbGFzcyk7CiAgICAgICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgaGVhZGVyLmNsYXNzTGlzdC5yZW1vdmUoJ2FuaW1hdGUnKTsKICAgICAgICAgICAgfSwgYW5pbWF0ZUR1cmF0aW9uKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRoaXMudG9nZ2xlQ2xhc3MoJ2FuaW1hdGUnLCBjb25maWdzLnRhbGxNb2RlW25ld01vZGVdLCBoZWFkZXIpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0aGlzLl9rZWVwU2Nyb2xsaW5nU3RhdGUoKTsKICAgICAgfSwKCiAgICAgIF9rZWVwU2Nyb2xsaW5nU3RhdGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBtYWluID0gdGhpcy5zY3JvbGxlcjsKICAgICAgICB2YXIgaGVhZGVyID0gdGhpcy5oZWFkZXI7CgogICAgICAgIHRoaXMuX3NldEF0VG9wKG1haW4uc2Nyb2xsVG9wID09PSAwKTsKCiAgICAgICAgaWYgKGhlYWRlciAmJiB0aGlzLnRhbGxDbGFzcyAmJiBNT0RFX0NPTkZJR1MudGFsbE1vZGVbdGhpcy5tb2RlXSkgewogICAgICAgICAgdGhpcy50b2dnbGVDbGFzcygKICAgICAgICAgICAgICB0aGlzLnRhbGxDbGFzcywKICAgICAgICAgICAgICB0aGlzLmF0VG9wIHx8CiAgICAgICAgICAgICAgICAgIGhlYWRlci5jbGFzc0xpc3QuY29udGFpbnModGhpcy50YWxsQ2xhc3MpICYmCiAgICAgICAgICAgICAgICAgICAgICBtYWluLnNjcm9sbEhlaWdodCA8IHRoaXMub2Zmc2V0SGVpZ2h0LAogICAgICAgICAgICAgIGhlYWRlcik7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3Njcm9sbDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fa2VlcFNjcm9sbGluZ1N0YXRlKCk7CiAgICAgICAgdGhpcy5maXJlKCdjb250ZW50LXNjcm9sbCcsIHt0YXJnZXQ6IHRoaXMuc2Nyb2xsZXJ9LCB7YnViYmxlczogZmFsc2V9KTsKICAgICAgfSwKCiAgICAgIF9nZXRTY3JvbGxlckZvck1vZGU6IGZ1bmN0aW9uKG1vZGUpIHsKICAgICAgICByZXR1cm4gTU9ERV9DT05GSUdTLm91dGVyU2Nyb2xsW21vZGVdID8gdGhpcyA6IHRoaXMuJC5tYWluQ29udGFpbmVyOwogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgIE1hdGVyaWFsIGRlc2lnbjogW0ljb24KICAgIHRvZ2dsZXNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9idXR0b25zLmh0bWwjYnV0dG9ucy10b2dnbGUtYnV0dG9ucykKCiAgICBgcGFwZXItaWNvbi1idXR0b25gIGlzIGEgYnV0dG9uIHdpdGggYW4gaW1hZ2UgcGxhY2VkIGF0IHRoZSBjZW50ZXIuIFdoZW4gdGhlCiAgICB1c2VyIHRvdWNoZXMgdGhlIGJ1dHRvbiwgYSByaXBwbGUgZWZmZWN0IGVtYW5hdGVzIGZyb20gdGhlIGNlbnRlciBvZiB0aGUgYnV0dG9uLgoKICAgIGBwYXBlci1pY29uLWJ1dHRvbmAgZG9lcyBub3QgaW5jbHVkZSBhIGRlZmF1bHQgaWNvbiBzZXQuIFRvIHVzZSBpY29ucyBmcm9tIHRoZQogICAgZGVmYXVsdCBzZXQsIGluY2x1ZGUgYFBvbHltZXJFbGVtZW50cy9pcm9uLWljb25zL2lyb24taWNvbnMuaHRtbGAsIGFuZCB1c2UgdGhlCiAgICBgaWNvbmAgYXR0cmlidXRlIHRvIHNwZWNpZnkgd2hpY2ggaWNvbiBmcm9tIHRoZSBpY29uIHNldCB0byB1c2UuCgogICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbiBpY29uPSJtZW51Ij48L3BhcGVyLWljb24tYnV0dG9uPgoKICAgIFNlZSBbYGlyb24taWNvbnNldGBdKGlyb24taWNvbnNldCkgZm9yIG1vcmUgaW5mb3JtYXRpb24gYWJvdXQKICAgIGhvdyB0byB1c2UgYSBjdXN0b20gaWNvbiBzZXQuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHNjcmlwdCB0eXBlPSJtb2R1bGUiPgogICAgICAgICAgaW1wb3J0ICdAcG9seW1lci9pcm9uLWljb25zL2lyb24taWNvbnMuanMnOwogICAgICAgIDwvSkFWQV9TQ1JJSUlJUFQvPgoKICAgICAgICA8cGFwZXItaWNvbi1idXR0b24gaWNvbj0iZmF2b3JpdGUiPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICAgICAgPHBhcGVyLWljb24tYnV0dG9uIHNyYz0ic3Rhci5wbmciPjwvcGFwZXItaWNvbi1idXR0b24+CgogICAgVG8gdXNlIGBwYXBlci1pY29uLWJ1dHRvbmAgYXMgYSBsaW5rLCB3cmFwIGl0IGluIGFuIGFuY2hvciB0YWcuIFNpbmNlCiAgICBgcGFwZXItaWNvbi1idXR0b25gIHdpbGwgYWxyZWFkeSByZWNlaXZlIGZvY3VzLCB5b3UgbWF5IHdhbnQgdG8gcHJldmVudCB0aGUKICAgIGFuY2hvciB0YWcgZnJvbSByZWNlaXZpbmcgZm9jdXMgYXMgd2VsbCBieSBzZXR0aW5nIGl0cyB0YWJpbmRleCB0byAtMS4KCiAgICAgICAgPGEgaHJlZj0iaHR0cHM6Ly93d3cucG9seW1lci1wcm9qZWN0Lm9yZyIgdGFiaW5kZXg9Ii0xIj4KICAgICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbiBpY29uPSJwb2x5bWVyIj48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgIDwvYT4KCiAgICAjIyMgU3R5bGluZwoKICAgIFN0eWxlIHRoZSBidXR0b24gd2l0aCBDU1MgYXMgeW91IHdvdWxkIGEgbm9ybWFsIERPTSBlbGVtZW50LiBJZiB5b3UgYXJlIHVzaW5nCiAgICB0aGUgaWNvbnMgcHJvdmlkZWQgYnkgYGlyb24taWNvbnNgLCB0aGV5IHdpbGwgaW5oZXJpdCB0aGUgZm9yZWdyb3VuZCBjb2xvciBvZgogICAgdGhlIGJ1dHRvbi4KCiAgICAgICAgLyogbWFrZSBhIHJlZCAiZmF2b3JpdGUiIGJ1dHRvbiAqXC8KICAgICAgICA8cGFwZXItaWNvbi1idXR0b24gaWNvbj0iZmF2b3JpdGUiIHN0eWxlPSJjb2xvcjogcmVkOyI+PC9wYXBlci1pY29uLWJ1dHRvbj4KCiAgICBCeSBkZWZhdWx0LCB0aGUgcmlwcGxlIGlzIHRoZSBzYW1lIGNvbG9yIGFzIHRoZSBmb3JlZ3JvdW5kIGF0IDI1JSBvcGFjaXR5LiBZb3UKICAgIG1heSBjdXN0b21pemUgdGhlIGNvbG9yIHVzaW5nIHRoZSBgLS1wYXBlci1pY29uLWJ1dHRvbi1pbmstY29sb3JgIGN1c3RvbQogICAgcHJvcGVydHkuCgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItaWNvbi1idXR0b24tZGlzYWJsZWQtdGV4dGAgfCBUaGUgY29sb3Igb2YgdGhlIGRpc2FibGVkIGJ1dHRvbiB8IGAtLWRpc2FibGVkLXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1pY29uLWJ1dHRvbi1pbmstY29sb3JgIHwgU2VsZWN0ZWQvZm9jdXMgcmlwcGxlIGNvbG9yIHwgYC0tcHJpbWFyeS10ZXh0LWNvbG9yYAogICAgYC0tcGFwZXItaWNvbi1idXR0b25gIHwgTWl4aW4gZm9yIGEgYnV0dG9uIHwgYHt9YAogICAgYC0tcGFwZXItaWNvbi1idXR0b24tZGlzYWJsZWRgIHwgTWl4aW4gZm9yIGEgZGlzYWJsZWQgYnV0dG9uIHwgYHt9YAogICAgYC0tcGFwZXItaWNvbi1idXR0b24taG92ZXJgIHwgTWl4aW4gZm9yIGJ1dHRvbiBvbiBob3ZlciB8IGB7fWAKCiAgICBAZ3JvdXAgUGFwZXIgRWxlbWVudHMKICAgIEBlbGVtZW50IHBhcGVyLWljb24tYnV0dG9uCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgaXM6ICdwYXBlci1pY29uLWJ1dHRvbicsCgogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIHBhZGRpbmc6IDhweDsKICAgICAgICBvdXRsaW5lOiBub25lOwogICAgICAgIC13ZWJraXQtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLW1vei11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICAgIHotaW5kZXg6IDA7CiAgICAgICAgbGluZS1oZWlnaHQ6IDE7CgogICAgICAgIHdpZHRoOiA0MHB4OwogICAgICAgIGhlaWdodDogNDBweDsKCiAgICAgICAgLyoKICAgICAgICAgIE5PVEU6IEJvdGggdmFsdWVzIGFyZSBuZWVkZWQsIHNpbmNlIHNvbWUgcGhvbmVzIHJlcXVpcmUgdGhlIHZhbHVlIHRvCiAgICAgICAgICBiZSBcYHRyYW5zcGFyZW50XGAuCiAgICAgICAgKi8KICAgICAgICAtd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3I6IHJnYmEoMCwgMCwgMCwgMCk7CiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKCiAgICAgICAgLyogQmVjYXVzZSBvZiBwb2x5bWVyLzI1NTgsIHRoaXMgc3R5bGUgaGFzIGxvd2VyIHNwZWNpZmljaXR5IHRoYW4gKiAqLwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3ggIWltcG9ydGFudDsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaWNvbi1idXR0b247CiAgICAgIH0KCiAgICAgIDpob3N0ICNpbmsgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pY29uLWJ1dHRvbi1pbmstY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwogICAgICAgIG9wYWNpdHk6IDAuNjsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1pY29uLWJ1dHRvbi1kaXNhYmxlZC10ZXh0LCB2YXIoLS1kaXNhYmxlZC10ZXh0LWNvbG9yKSk7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgICAgY3Vyc29yOiBhdXRvOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1pY29uLWJ1dHRvbi1kaXNhYmxlZDsKICAgICAgfQoKICAgICAgOmhvc3QoW2hpZGRlbl0pIHsKICAgICAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIDpob3N0KDpob3ZlcikgewogICAgICAgIEBhcHBseSAtLXBhcGVyLWljb24tYnV0dG9uLWhvdmVyOwogICAgICB9CgogICAgICBpcm9uLWljb24gewogICAgICAgIC0taXJvbi1pY29uLXdpZHRoOiAxMDAlOwogICAgICAgIC0taXJvbi1pY29uLWhlaWdodDogMTAwJTsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8aXJvbi1pY29uIGlkPSJpY29uIiBzcmM9Iltbc3JjXV0iIGljb249IltbaWNvbl1dIgogICAgICAgICAgICAgICBhbHQkPSJbW2FsdF1dIj48L2lyb24taWNvbj4KICBgLAoKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHtyb2xlOiAnYnV0dG9uJywgdGFiaW5kZXg6ICcwJ30sCgogICAgICBiZWhhdmlvcnM6IFtQYXBlcklua3lGb2N1c0JlaGF2aW9yXSwKCiAgICAgIHJlZ2lzdGVyZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3RlbXBsYXRlLnNldEF0dHJpYnV0ZSgnc3RyaXAtd2hpdGVzcGFjZScsICcnKTsKICAgICAgfSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgVVJMIG9mIGFuIGltYWdlIGZvciB0aGUgaWNvbi4gSWYgdGhlIHNyYyBwcm9wZXJ0eSBpcyBzcGVjaWZpZWQsCiAgICAgICAgICogdGhlIGljb24gcHJvcGVydHkgc2hvdWxkIG5vdCBiZS4KICAgICAgICAgKi8KICAgICAgICBzcmM6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTcGVjaWZpZXMgdGhlIGljb24gbmFtZSBvciBpbmRleCBpbiB0aGUgc2V0IG9mIGljb25zIGF2YWlsYWJsZSBpbgogICAgICAgICAqIHRoZSBpY29uJ3MgaWNvbiBzZXQuIElmIHRoZSBpY29uIHByb3BlcnR5IGlzIHNwZWNpZmllZCwKICAgICAgICAgKiB0aGUgc3JjIHByb3BlcnR5IHNob3VsZCBub3QgYmUuCiAgICAgICAgICovCiAgICAgICAgaWNvbjoge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFNwZWNpZmllcyB0aGUgYWx0ZXJuYXRlIHRleHQgZm9yIHRoZSBidXR0b24sIGZvciBhY2Nlc3NpYmlsaXR5LgogICAgICAgICAqLwogICAgICAgIGFsdDoge3R5cGU6IFN0cmluZywgb2JzZXJ2ZXI6ICdfYWx0Q2hhbmdlZCd9CiAgICAgIH0sCgogICAgICBfYWx0Q2hhbmdlZDogZnVuY3Rpb24obmV3VmFsdWUsIG9sZFZhbHVlKSB7CiAgICAgICAgdmFyIGxhYmVsID0gdGhpcy5nZXRBdHRyaWJ1dGUoJ2FyaWEtbGFiZWwnKTsKCiAgICAgICAgLy8gRG9uJ3Qgc3RvbXAgb3ZlciBhIHVzZXItc2V0IGFyaWEtbGFiZWwuCiAgICAgICAgaWYgKCFsYWJlbCB8fCBvbGRWYWx1ZSA9PSBsYWJlbCkgewogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtbGFiZWwnLCBuZXdWYWx1ZSk7CiAgICAgICAgfQogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgIGBpcm9uLWF1dG9ncm93LXRleHRhcmVhYCBpcyBhbiBlbGVtZW50IGNvbnRhaW5pbmcgYSB0ZXh0YXJlYSB0aGF0IGdyb3dzIGluCiAgICBoZWlnaHQgYXMgbW9yZSBsaW5lcyBvZiBpbnB1dCBhcmUgZW50ZXJlZC4gVW5sZXNzIGFuIGV4cGxpY2l0IGhlaWdodCBvciB0aGUKICAgIGBtYXhSb3dzYCBwcm9wZXJ0eSBpcyBzZXQsIGl0IHdpbGwgbmV2ZXIgc2Nyb2xsLgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxpcm9uLWF1dG9ncm93LXRleHRhcmVhPjwvaXJvbi1hdXRvZ3Jvdy10ZXh0YXJlYT4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLWlyb24tYXV0b2dyb3ctdGV4dGFyZWFgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdGV4dGFyZWEgfCBge31gCiAgICBgLS1pcm9uLWF1dG9ncm93LXRleHRhcmVhLXBsYWNlaG9sZGVyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHRleHRhcmVhIHBsYWNlaG9sZGVyIHwgYHt9YAoKICAgIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgKi8KICAgIFBvbHltZXIoewogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgd2lkdGg6IDQwMHB4OwogICAgICAgIGJvcmRlcjogMXB4IHNvbGlkOwogICAgICAgIHBhZGRpbmc6IDJweDsKICAgICAgICAtbW96LWFwcGVhcmFuY2U6IHRleHRhcmVhOwogICAgICAgIC13ZWJraXQtYXBwZWFyYW5jZTogdGV4dGFyZWE7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgfQoKICAgICAgLm1pcnJvci10ZXh0IHsKICAgICAgICB2aXNpYmlsaXR5OiBoaWRkZW47CiAgICAgICAgd29yZC13cmFwOiBicmVhay13b3JkOwogICAgICAgIEBhcHBseSAtLWlyb24tYXV0b2dyb3ctdGV4dGFyZWE7CiAgICAgIH0KCiAgICAgIC5maXQgewogICAgICAgIEBhcHBseSAtLWxheW91dC1maXQ7CiAgICAgIH0KCiAgICAgIHRleHRhcmVhIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgb3V0bGluZTogbm9uZTsKICAgICAgICBib3JkZXI6IG5vbmU7CiAgICAgICAgcmVzaXplOiBub25lOwogICAgICAgIGJhY2tncm91bmQ6IGluaGVyaXQ7CiAgICAgICAgY29sb3I6IGluaGVyaXQ7CiAgICAgICAgLyogc2VlIGNvbW1lbnRzIGluIHRlbXBsYXRlICovCiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIGZvbnQtc2l6ZTogaW5oZXJpdDsKICAgICAgICBmb250LWZhbWlseTogaW5oZXJpdDsKICAgICAgICBsaW5lLWhlaWdodDogaW5oZXJpdDsKICAgICAgICB0ZXh0LWFsaWduOiBpbmhlcml0OwogICAgICAgIEBhcHBseSAtLWlyb24tYXV0b2dyb3ctdGV4dGFyZWE7CiAgICAgIH0KCiAgICAgIHRleHRhcmVhOjotd2Via2l0LWlucHV0LXBsYWNlaG9sZGVyIHsKICAgICAgICBAYXBwbHkgLS1pcm9uLWF1dG9ncm93LXRleHRhcmVhLXBsYWNlaG9sZGVyOwogICAgICB9CgogICAgICB0ZXh0YXJlYTotbW96LXBsYWNlaG9sZGVyIHsKICAgICAgICBAYXBwbHkgLS1pcm9uLWF1dG9ncm93LXRleHRhcmVhLXBsYWNlaG9sZGVyOwogICAgICB9CgogICAgICB0ZXh0YXJlYTo6LW1vei1wbGFjZWhvbGRlciB7CiAgICAgICAgQGFwcGx5IC0taXJvbi1hdXRvZ3Jvdy10ZXh0YXJlYS1wbGFjZWhvbGRlcjsKICAgICAgfQoKICAgICAgdGV4dGFyZWE6LW1zLWlucHV0LXBsYWNlaG9sZGVyIHsKICAgICAgICBAYXBwbHkgLS1pcm9uLWF1dG9ncm93LXRleHRhcmVhLXBsYWNlaG9sZGVyOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDwhLS0gdGhlIG1pcnJvciBzaXplcyB0aGUgaW5wdXQvdGV4dGFyZWEgc28gaXQgZ3Jvd3Mgd2l0aCB0eXBpbmcgLS0+CiAgICA8IS0tIHVzZSAmIzE2MDsgaW5zdGVhZCAmbmJzcDsgb2YgdG8gYWxsb3cgdGhpcyBlbGVtZW50IHRvIGJlIHVzZWQgaW4gWEhUTUwgLS0+CiAgICA8ZGl2IGlkPSJtaXJyb3IiIGNsYXNzPSJtaXJyb3ItdGV4dCIgYXJpYS1oaWRkZW49InRydWUiPiZuYnNwOzwvZGl2PgoKICAgIDwhLS0gc2l6ZSB0aGUgaW5wdXQvdGV4dGFyZWEgd2l0aCBhIGRpdiwgYmVjYXVzZSB0aGUgdGV4dGFyZWEgaGFzIGludHJpbnNpYyBzaXplIGluIGZmIC0tPgogICAgPGRpdiBjbGFzcz0idGV4dGFyZWEtY29udGFpbmVyIGZpdCI+CiAgICAgIDx0ZXh0YXJlYSBpZD0idGV4dGFyZWEiIG5hbWUkPSJbW25hbWVdXSIgYXJpYS1sYWJlbCQ9IltbbGFiZWxdXSIgYXV0b2NvbXBsZXRlJD0iW1thdXRvY29tcGxldGVdXSIgYXV0b2ZvY3VzJD0iW1thdXRvZm9jdXNdXSIgYXV0b2NhcGl0YWxpemUkPSJbW2F1dG9jYXBpdGFsaXplXV0iIGlucHV0bW9kZSQ9IltbaW5wdXRtb2RlXV0iIHBsYWNlaG9sZGVyJD0iW1twbGFjZWhvbGRlcl1dIiByZWFkb25seSQ9IltbcmVhZG9ubHldXSIgcmVxdWlyZWQkPSJbW3JlcXVpcmVkXV0iIGRpc2FibGVkJD0iW1tkaXNhYmxlZF1dIiByb3dzJD0iW1tyb3dzXV0iIG1pbmxlbmd0aCQ9IltbbWlubGVuZ3RoXV0iIG1heGxlbmd0aCQ9IltbbWF4bGVuZ3RoXV0iPjwvdGV4dGFyZWE+CiAgICA8L2Rpdj4KYCwKCiAgICAgIGlzOiAnaXJvbi1hdXRvZ3Jvdy10ZXh0YXJlYScsCiAgICAgIGJlaGF2aW9yczogW0lyb25WYWxpZGF0YWJsZUJlaGF2aW9yLCBJcm9uQ29udHJvbFN0YXRlXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBVc2UgdGhpcyBwcm9wZXJ0eSBpbnN0ZWFkIG9mIGBiaW5kLXZhbHVlYCBmb3IgdHdvLXdheSBkYXRhIGJpbmRpbmcuCiAgICAgICAgICogQHR5cGUge3N0cmluZ3xudW1iZXJ9CiAgICAgICAgICovCiAgICAgICAgdmFsdWU6IHtvYnNlcnZlcjogJ192YWx1ZUNoYW5nZWQnLCB0eXBlOiBTdHJpbmcsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgcHJvcGVydHkgaXMgZGVwcmVjYXRlZCwgYW5kIGp1c3QgbWlycm9ycyBgdmFsdWVgLiBVc2UgYHZhbHVlYAogICAgICAgICAqIGluc3RlYWQuCiAgICAgICAgICogQHR5cGUge3N0cmluZ3xudW1iZXJ9CiAgICAgICAgICovCiAgICAgICAgYmluZFZhbHVlOiB7b2JzZXJ2ZXI6ICdfYmluZFZhbHVlQ2hhbmdlZCcsIHR5cGU6IFN0cmluZywgbm90aWZ5OiB0cnVlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGluaXRpYWwgbnVtYmVyIG9mIHJvd3MuCiAgICAgICAgICoKICAgICAgICAgKiBAYXR0cmlidXRlIHJvd3MKICAgICAgICAgKiBAdHlwZSBudW1iZXIKICAgICAgICAgKiBAZGVmYXVsdCAxCiAgICAgICAgICovCiAgICAgICAgcm93czoge3R5cGU6IE51bWJlciwgdmFsdWU6IDEsIG9ic2VydmVyOiAnX3VwZGF0ZUNhY2hlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbWF4aW11bSBudW1iZXIgb2Ygcm93cyB0aGlzIGVsZW1lbnQgY2FuIGdyb3cgdG8gdW50aWwgaXQKICAgICAgICAgKiBzY3JvbGxzLiAwIG1lYW5zIG5vIG1heGltdW0uCiAgICAgICAgICoKICAgICAgICAgKiBAYXR0cmlidXRlIG1heFJvd3MKICAgICAgICAgKiBAdHlwZSBudW1iZXIKICAgICAgICAgKiBAZGVmYXVsdCAwCiAgICAgICAgICovCiAgICAgICAgbWF4Um93czoge3R5cGU6IE51bWJlciwgdmFsdWU6IDAsIG9ic2VydmVyOiAnX3VwZGF0ZUNhY2hlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCb3VuZCB0byB0aGUgdGV4dGFyZWEncyBgYXV0b2NvbXBsZXRlYCBhdHRyaWJ1dGUuCiAgICAgICAgICovCiAgICAgICAgYXV0b2NvbXBsZXRlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ29mZid9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCb3VuZCB0byB0aGUgdGV4dGFyZWEncyBgYXV0b2ZvY3VzYCBhdHRyaWJ1dGUuCiAgICAgICAgICoKICAgICAgICAgKiBAdHlwZSB7IWJvb2xlYW59CiAgICAgICAgICovCiAgICAgICAgYXV0b2ZvY3VzOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQm91bmQgdG8gdGhlIHRleHRhcmVhJ3MgYGF1dG9jYXBpdGFsaXplYCBhdHRyaWJ1dGUuCiAgICAgICAgICovCiAgICAgICAgYXV0b2NhcGl0YWxpemU6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnbm9uZSd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCb3VuZCB0byB0aGUgdGV4dGFyZWEncyBgaW5wdXRtb2RlYCBhdHRyaWJ1dGUuCiAgICAgICAgICovCiAgICAgICAgaW5wdXRtb2RlOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQm91bmQgdG8gdGhlIHRleHRhcmVhJ3MgYHBsYWNlaG9sZGVyYCBhdHRyaWJ1dGUuCiAgICAgICAgICovCiAgICAgICAgcGxhY2Vob2xkZXI6IHt0eXBlOiBTdHJpbmd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCb3VuZCB0byB0aGUgdGV4dGFyZWEncyBgcmVhZG9ubHlgIGF0dHJpYnV0ZS4KICAgICAgICAgKi8KICAgICAgICByZWFkb25seToge3R5cGU6IFN0cmluZ30sCgogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIG1hcmsgdGhlIHRleHRhcmVhIGFzIHJlcXVpcmVkLgogICAgICAgICAqLwogICAgICAgIHJlcXVpcmVkOiB7dHlwZTogQm9vbGVhbn0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBtaW5pbXVtIGxlbmd0aCBvZiB0aGUgaW5wdXQgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgbWlubGVuZ3RoOiB7dHlwZTogTnVtYmVyfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG1heGltdW0gbGVuZ3RoIG9mIHRoZSBpbnB1dCB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBtYXhsZW5ndGg6IHt0eXBlOiBOdW1iZXJ9LAoKICAgICAgICAvKioKICAgICAgICAgKiBCb3VuZCB0byB0aGUgdGV4dGFyZWEncyBgYXJpYS1sYWJlbGAgYXR0cmlidXRlLgogICAgICAgICAqLwogICAgICAgIGxhYmVsOiB7dHlwZTogU3RyaW5nfQoKICAgICAgfSwKCiAgICAgIGxpc3RlbmVyczogeydpbnB1dCc6ICdfb25JbnB1dCd9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIHVuZGVybHlpbmcgdGV4dGFyZWEuCiAgICAgICAqIEByZXR1cm4geyFIVE1MVGV4dEFyZWFFbGVtZW50fQogICAgICAgKi8KICAgICAgZ2V0IHRleHRhcmVhKCkgewogICAgICAgIHJldHVybiAvKiogQHR5cGUgeyFIVE1MVGV4dEFyZWFFbGVtZW50fSAqLyAodGhpcy4kLnRleHRhcmVhKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRleHRhcmVhJ3Mgc2VsZWN0aW9uIHN0YXJ0LgogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9CiAgICAgICAqLwogICAgICBnZXQgc2VsZWN0aW9uU3RhcnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuJC50ZXh0YXJlYS5zZWxlY3Rpb25TdGFydDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIHRleHRhcmVhJ3Mgc2VsZWN0aW9uIGVuZC4KICAgICAgICogQHJldHVybiB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IHNlbGVjdGlvbkVuZCgpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLnRleHRhcmVhLnNlbGVjdGlvbkVuZDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZXRzIHRoZSB0ZXh0YXJlYSdzIHNlbGVjdGlvbiBzdGFydC4KICAgICAgICovCiAgICAgIHNldCBzZWxlY3Rpb25TdGFydCh2YWx1ZSkgewogICAgICAgIHRoaXMuJC50ZXh0YXJlYS5zZWxlY3Rpb25TdGFydCA9IHZhbHVlOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNldHMgdGhlIHRleHRhcmVhJ3Mgc2VsZWN0aW9uIGVuZC4KICAgICAgICovCiAgICAgIHNldCBzZWxlY3Rpb25FbmQodmFsdWUpIHsKICAgICAgICB0aGlzLiQudGV4dGFyZWEuc2VsZWN0aW9uRW5kID0gdmFsdWU7CiAgICAgIH0sCgogICAgICAvKiogQG92ZXJyaWRlICovCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAvKiBpT1MgaGFzIGFuIGFyYml0cmFyeSBsZWZ0IG1hcmdpbiBvZiAzcHggdGhhdCBpc24ndCBwcmVzZW50CiAgICAgICAgICogaW4gYW55IG90aGVyIGJyb3dzZXIsIGFuZCBtZWFucyB0aGF0IHRoZSBwYXBlci10ZXh0YXJlYSdzIGN1cnNvcgogICAgICAgICAqIG92ZXJsYXBzIHRoZSBsYWJlbC4KICAgICAgICAgKiBTZWUgaHR0cHM6Ly9naXRodWIuY29tL1BvbHltZXJFbGVtZW50cy9wYXBlci1pbnB1dC9pc3N1ZXMvNDY4LgogICAgICAgICAqLwogICAgICAgIHZhciBJU19JT1MgPSBuYXZpZ2F0b3IudXNlckFnZW50Lm1hdGNoKC9pUCg/OltvYV1kfGhvbmUpLykgJiYKICAgICAgICAgICAgIW5hdmlnYXRvci51c2VyQWdlbnQubWF0Y2goL09TIDFbMzQ1Njc4OV0vKTsKICAgICAgICBpZiAoSVNfSU9TKSB7CiAgICAgICAgICB0aGlzLiQudGV4dGFyZWEuc3R5bGUubWFyZ2luTGVmdCA9ICctM3B4JzsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0cnVlIGlmIGB2YWx1ZWAgaXMgdmFsaWQuIFRoZSB2YWxpZGF0b3IgcHJvdmlkZWQgaW4gYHZhbGlkYXRvcmAKICAgICAgICogd2lsbCBiZSB1c2VkIGZpcnN0LCBpZiBpdCBleGlzdHM7IG90aGVyd2lzZSwgdGhlIGB0ZXh0YXJlYWAncyB2YWxpZGl0eQogICAgICAgKiBpcyB1c2VkLgogICAgICAgKiBAcmV0dXJuIHtib29sZWFufSBUcnVlIGlmIHRoZSB2YWx1ZSBpcyB2YWxpZC4KICAgICAgICovCiAgICAgIHZhbGlkYXRlOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBVc2UgdGhlIG5lc3RlZCBpbnB1dCdzIG5hdGl2ZSB2YWxpZGl0eS4KICAgICAgICB2YXIgdmFsaWQgPSB0aGlzLiQudGV4dGFyZWEudmFsaWRpdHkudmFsaWQ7CgogICAgICAgIC8vIE9ubHkgZG8gZXh0cmEgY2hlY2tpbmcgaWYgdGhlIGJyb3dzZXIgdGhvdWdodCB0aGlzIHdhcyB2YWxpZC4KICAgICAgICBpZiAodmFsaWQpIHsKICAgICAgICAgIC8vIEVtcHR5LCByZXF1aXJlZCBpbnB1dCBpcyBpbnZhbGlkCiAgICAgICAgICBpZiAodGhpcy5yZXF1aXJlZCAmJiB0aGlzLnZhbHVlID09PSAnJykgewogICAgICAgICAgICB2YWxpZCA9IGZhbHNlOwogICAgICAgICAgfSBlbHNlIGlmICh0aGlzLmhhc1ZhbGlkYXRvcigpKSB7CiAgICAgICAgICAgIHZhbGlkID0gSXJvblZhbGlkYXRhYmxlQmVoYXZpb3IudmFsaWRhdGUuY2FsbCh0aGlzLCB0aGlzLnZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHRoaXMuaW52YWxpZCA9ICF2YWxpZDsKICAgICAgICB0aGlzLmZpcmUoJ2lyb24taW5wdXQtdmFsaWRhdGUnKTsKICAgICAgICByZXR1cm4gdmFsaWQ7CiAgICAgIH0sCgogICAgICBfYmluZFZhbHVlQ2hhbmdlZDogZnVuY3Rpb24oYmluZFZhbHVlKSB7CiAgICAgICAgdGhpcy52YWx1ZSA9IGJpbmRWYWx1ZTsKICAgICAgfSwKCiAgICAgIF92YWx1ZUNoYW5nZWQ6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgdmFyIHRleHRhcmVhID0gdGhpcy50ZXh0YXJlYTsKICAgICAgICBpZiAoIXRleHRhcmVhKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBJZiB0aGUgYmluZFZhbHVlIGNoYW5nZWQgbWFudWFsbHksIHRoZW4gd2UgbmVlZCB0byBhbHNvIHVwZGF0ZQogICAgICAgIC8vIHRoZSB1bmRlcmx5aW5nIHRleHRhcmVhJ3MgdmFsdWUuIE90aGVyd2lzZSB0aGlzIGNoYW5nZSB3YXMgcHJvYmFibHkKICAgICAgICAvLyBnZW5lcmF0ZWQgZnJvbSB0aGUgX29uSW5wdXQgaGFuZGxlciwgYW5kIHRoZSB0d28gdmFsdWVzIGFyZSBhbHJlYWR5CiAgICAgICAgLy8gdGhlIHNhbWUuCiAgICAgICAgaWYgKHRleHRhcmVhLnZhbHVlICE9PSB2YWx1ZSkgewogICAgICAgICAgdGV4dGFyZWEudmFsdWUgPSAhKHZhbHVlIHx8IHZhbHVlID09PSAwKSA/ICcnIDogdmFsdWU7CiAgICAgICAgfQoKICAgICAgICB0aGlzLmJpbmRWYWx1ZSA9IHZhbHVlOwogICAgICAgIHRoaXMuJC5taXJyb3IuaW5uZXJIVE1MID0gdGhpcy5fdmFsdWVGb3JNaXJyb3IoKTsKCiAgICAgICAgLy8gTWFudWFsbHkgbm90aWZ5IGJlY2F1c2Ugd2UgZG9uJ3Qgd2FudCB0byBub3RpZnkgdW50aWwgYWZ0ZXIgc2V0dGluZwogICAgICAgIC8vIHZhbHVlLgogICAgICAgIHRoaXMuZmlyZSgnYmluZC12YWx1ZS1jaGFuZ2VkJywge3ZhbHVlOiB0aGlzLmJpbmRWYWx1ZX0pOwogICAgICB9LAoKICAgICAgX29uSW5wdXQ6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdmFyIGV2ZW50UGF0aCA9IGRvbShldmVudCkucGF0aDsKICAgICAgICB0aGlzLnZhbHVlID0gZXZlbnRQYXRoID8gZXZlbnRQYXRoWzBdLnZhbHVlIDogZXZlbnQudGFyZ2V0LnZhbHVlOwogICAgICB9LAoKICAgICAgX2NvbnN0cmFpbjogZnVuY3Rpb24odG9rZW5zKSB7CiAgICAgICAgdmFyIF90b2tlbnM7CiAgICAgICAgdG9rZW5zID0gdG9rZW5zIHx8IFsnJ107CiAgICAgICAgLy8gRW5mb3JjZSB0aGUgbWluIGFuZCBtYXggaGVpZ2h0cyBmb3IgYSBtdWx0aWxpbmUgaW5wdXQgdG8gYXZvaWQKICAgICAgICAvLyBtZWFzdXJlbWVudAogICAgICAgIGlmICh0aGlzLm1heFJvd3MgPiAwICYmIHRva2Vucy5sZW5ndGggPiB0aGlzLm1heFJvd3MpIHsKICAgICAgICAgIF90b2tlbnMgPSB0b2tlbnMuc2xpY2UoMCwgdGhpcy5tYXhSb3dzKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgX3Rva2VucyA9IHRva2Vucy5zbGljZSgwKTsKICAgICAgICB9CiAgICAgICAgd2hpbGUgKHRoaXMucm93cyA+IDAgJiYgX3Rva2Vucy5sZW5ndGggPCB0aGlzLnJvd3MpIHsKICAgICAgICAgIF90b2tlbnMucHVzaCgnJyk7CiAgICAgICAgfQogICAgICAgIC8vIFVzZSAmIzE2MDsgaW5zdGVhZCAmbmJzcDsgb2YgdG8gYWxsb3cgdGhpcyBlbGVtZW50IHRvIGJlIHVzZWQgaW4gWEhUTUwuCiAgICAgICAgcmV0dXJuIF90b2tlbnMuam9pbignPGJyLz4nKSArICcmIzE2MDsnOwogICAgICB9LAoKICAgICAgX3ZhbHVlRm9yTWlycm9yOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaW5wdXQgPSB0aGlzLnRleHRhcmVhOwogICAgICAgIGlmICghaW5wdXQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpcy50b2tlbnMgPSAoaW5wdXQgJiYgaW5wdXQudmFsdWUpID8gaW5wdXQudmFsdWUucmVwbGFjZSgvJi9nbSwgJyZhbXA7JykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoLyIvZ20sICcmcXVvdDsnKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAucmVwbGFjZSgvJy9nbSwgJyYjMzk7JykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoLzwvZ20sICcmbHQ7JykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoLz4vZ20sICcmZ3Q7JykKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLnNwbGl0KCdcbicpIDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBbJyddOwogICAgICAgIHJldHVybiB0aGlzLl9jb25zdHJhaW4odGhpcy50b2tlbnMpOwogICAgICB9LAoKICAgICAgX3VwZGF0ZUNhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy4kLm1pcnJvci5pbm5lckhUTUwgPSB0aGlzLl9jb25zdHJhaW4odGhpcy50b2tlbnMpOwogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKgogICAgYDxwYXBlci10ZXh0YXJlYT5gIGlzIGEgbXVsdGktbGluZSB0ZXh0IGZpZWxkIHdpdGggTWF0ZXJpYWwgRGVzaWduIHN0eWxpbmcuCgogICAgICAgIDxwYXBlci10ZXh0YXJlYSBsYWJlbD0iVGV4dGFyZWEgbGFiZWwiPjwvcGFwZXItdGV4dGFyZWE+CgogICAgU2VlIGBQb2x5bWVyLlBhcGVySW5wdXRCZWhhdmlvcmAgZm9yIG1vcmUgQVBJIGRvY3MuCgogICAgIyMjIFZhbGlkYXRpb24KCiAgICBDdXJyZW50bHkgb25seSBgcmVxdWlyZWRgIGFuZCBgbWF4bGVuZ3RoYCB2YWxpZGF0aW9uIGlzIHN1cHBvcnRlZC4KCiAgICAjIyMgU3R5bGluZwoKICAgIFNlZSBgUG9seW1lci5QYXBlcklucHV0Q29udGFpbmVyYCBmb3IgYSBsaXN0IG9mIGN1c3RvbSBwcm9wZXJ0aWVzIHVzZWQgdG8KICAgIHN0eWxlIHRoaXMgZWxlbWVudC4KICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgLyoqIEBvdmVycmlkZSAqLwogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQoKICAgICAgOmhvc3QoW2hpZGRlbl0pIHsKICAgICAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIGxhYmVsIHsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8cGFwZXItaW5wdXQtY29udGFpbmVyIG5vLWxhYmVsLWZsb2F0JD0iW1tub0xhYmVsRmxvYXRdXSIgYWx3YXlzLWZsb2F0LWxhYmVsPSJbW19jb21wdXRlQWx3YXlzRmxvYXRMYWJlbChhbHdheXNGbG9hdExhYmVsLHBsYWNlaG9sZGVyKV1dIiBhdXRvLXZhbGlkYXRlJD0iW1thdXRvVmFsaWRhdGVdXSIgZGlzYWJsZWQkPSJbW2Rpc2FibGVkXV0iIGludmFsaWQ9IltbaW52YWxpZF1dIj4KCiAgICAgIDxsYWJlbCBoaWRkZW4kPSJbWyFsYWJlbF1dIiBhcmlhLWhpZGRlbj0idHJ1ZSIgZm9yJD0iW1tfaW5wdXRJZF1dIiBzbG90PSJsYWJlbCI+W1tsYWJlbF1dPC9sYWJlbD4KCiAgICAgIDxpcm9uLWF1dG9ncm93LXRleHRhcmVhIGNsYXNzPSJwYXBlci1pbnB1dC1pbnB1dCIgc2xvdD0iaW5wdXQiIGlkJD0iW1tfaW5wdXRJZF1dIiBhcmlhLWxhYmVsbGVkYnkkPSJbW19hcmlhTGFiZWxsZWRCeV1dIiBhcmlhLWRlc2NyaWJlZGJ5JD0iW1tfYXJpYURlc2NyaWJlZEJ5XV0iIGJpbmQtdmFsdWU9Int7dmFsdWV9fSIgaW52YWxpZD0ie3tpbnZhbGlkfX0iIHZhbGlkYXRvciQ9IltbdmFsaWRhdG9yXV0iIGRpc2FibGVkJD0iW1tkaXNhYmxlZF1dIiBhdXRvY29tcGxldGUkPSJbW2F1dG9jb21wbGV0ZV1dIiBhdXRvZm9jdXMkPSJbW2F1dG9mb2N1c11dIiBpbnB1dG1vZGUkPSJbW2lucHV0bW9kZV1dIiBuYW1lJD0iW1tuYW1lXV0iIHBsYWNlaG9sZGVyJD0iW1twbGFjZWhvbGRlcl1dIiByZWFkb25seSQ9IltbcmVhZG9ubHldXSIgcmVxdWlyZWQkPSJbW3JlcXVpcmVkXV0iIG1pbmxlbmd0aCQ9IltbbWlubGVuZ3RoXV0iIG1heGxlbmd0aCQ9IltbbWF4bGVuZ3RoXV0iIGF1dG9jYXBpdGFsaXplJD0iW1thdXRvY2FwaXRhbGl6ZV1dIiByb3dzJD0iW1tyb3dzXV0iIG1heC1yb3dzJD0iW1ttYXhSb3dzXV0iIG9uLWNoYW5nZT0iX29uQ2hhbmdlIj48L2lyb24tYXV0b2dyb3ctdGV4dGFyZWE+CgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbZXJyb3JNZXNzYWdlXV0iPgogICAgICAgIDxwYXBlci1pbnB1dC1lcnJvciBhcmlhLWxpdmU9ImFzc2VydGl2ZSIgc2xvdD0iYWRkLW9uIj5bW2Vycm9yTWVzc2FnZV1dPC9wYXBlci1pbnB1dC1lcnJvcj4KICAgICAgPC90ZW1wbGF0ZT4KCiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tjaGFyQ291bnRlcl1dIj4KICAgICAgICA8cGFwZXItaW5wdXQtY2hhci1jb3VudGVyIHNsb3Q9ImFkZC1vbiI+PC9wYXBlci1pbnB1dC1jaGFyLWNvdW50ZXI+CiAgICAgIDwvdGVtcGxhdGU+CgogICAgPC9wYXBlci1pbnB1dC1jb250YWluZXI+CmAsCgogICAgICBpczogJ3BhcGVyLXRleHRhcmVhJywKCiAgICAgIGJlaGF2aW9yczogWwogICAgICAgIFBhcGVySW5wdXRCZWhhdmlvciwKICAgICAgICBJcm9uRm9ybUVsZW1lbnRCZWhhdmlvciwKICAgICAgXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICBfYXJpYUxhYmVsbGVkQnk6IHsKICAgICAgICAgIG9ic2VydmVyOiAnX2FyaWFMYWJlbGxlZEJ5Q2hhbmdlZCcsCiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSwKCiAgICAgICAgX2FyaWFEZXNjcmliZWRCeTogewogICAgICAgICAgb2JzZXJ2ZXI6ICdfYXJpYURlc2NyaWJlZEJ5Q2hhbmdlZCcsCiAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSwKCiAgICAgICAgdmFsdWU6IHsKICAgICAgICAgIC8vIFJlcXVpcmVkIGZvciB0aGUgY29ycmVjdCBUeXBlU2NyaXB0IHR5cGUtZ2VuZXJhdGlvbgogICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBpbml0aWFsIG51bWJlciBvZiByb3dzLgogICAgICAgICAqIEB0eXBlIHtudW1iZXJ9CiAgICAgICAgICogQGRlZmF1bHQgMQogICAgICAgICAqLwogICAgICAgIHJvd3M6IHsKICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgIHZhbHVlOiAxLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBtYXhpbXVtIG51bWJlciBvZiByb3dzIHRoaXMgZWxlbWVudCBjYW4gZ3JvdyB0byB1bnRpbCBpdAogICAgICAgICAqIHNjcm9sbHMuIDAgbWVhbnMgbm8gbWF4aW11bS4KICAgICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgICAqIEBkZWZhdWx0IDAKICAgICAgICAgKi8KICAgICAgICBtYXhSb3dzOiB7CiAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICB2YWx1ZTogMCwKICAgICAgICB9LAogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge251bWJlcn0KICAgICAgICovCiAgICAgIGdldCBzZWxlY3Rpb25TdGFydCgpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLmlucHV0LnRleHRhcmVhLnNlbGVjdGlvblN0YXJ0OwogICAgICB9LAoKICAgICAgc2V0IHNlbGVjdGlvblN0YXJ0KHN0YXJ0KSB7CiAgICAgICAgdGhpcy4kLmlucHV0LnRleHRhcmVhLnNlbGVjdGlvblN0YXJ0ID0gc3RhcnQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHJldHVybiB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IHNlbGVjdGlvbkVuZCgpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLmlucHV0LnRleHRhcmVhLnNlbGVjdGlvbkVuZDsKICAgICAgfSwKCiAgICAgIHNldCBzZWxlY3Rpb25FbmQoZW5kKSB7CiAgICAgICAgdGhpcy4kLmlucHV0LnRleHRhcmVhLnNlbGVjdGlvbkVuZCA9IGVuZDsKICAgICAgfSwKCiAgICAgIF9hcmlhTGFiZWxsZWRCeUNoYW5nZWQ6IGZ1bmN0aW9uKGFyaWFMYWJlbGxlZEJ5KSB7CiAgICAgICAgdGhpcy5fZm9jdXNhYmxlRWxlbWVudC5zZXRBdHRyaWJ1dGUoJ2FyaWEtbGFiZWxsZWRieScsIGFyaWFMYWJlbGxlZEJ5KTsKICAgICAgfSwKCiAgICAgIF9hcmlhRGVzY3JpYmVkQnlDaGFuZ2VkOiBmdW5jdGlvbihhcmlhRGVzY3JpYmVkQnkpIHsKICAgICAgICB0aGlzLl9mb2N1c2FibGVFbGVtZW50LnNldEF0dHJpYnV0ZSgnYXJpYS1kZXNjcmliZWRieScsIGFyaWFEZXNjcmliZWRCeSk7CiAgICAgIH0sCgogICAgICBnZXQgX2ZvY3VzYWJsZUVsZW1lbnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaW5wdXRFbGVtZW50LnRleHRhcmVhOwogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIGNvbnN0ICRfZG9jdW1lbnRDb250YWluZXIkMyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RlbXBsYXRlJyk7CiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDMuc2V0QXR0cmlidXRlKCdzdHlsZScsICdkaXNwbGF5OiBub25lOycpOwoKICAgICRfZG9jdW1lbnRDb250YWluZXIkMy5pbm5lckhUTUwgPSBgPGRvbS1tb2R1bGUgaWQ9InBhcGVyLWl0ZW0tc2hhcmVkLXN0eWxlcyI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICA6aG9zdCwgLnBhcGVyLWl0ZW0gewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBtaW4taGVpZ2h0OiB2YXIoLS1wYXBlci1pdGVtLW1pbi1oZWlnaHQsIDQ4cHgpOwogICAgICAgIHBhZGRpbmc6IDBweCAxNnB4OwogICAgICB9CgogICAgICAucGFwZXItaXRlbSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1zdWJoZWFkOwogICAgICAgIGJvcmRlcjpub25lOwogICAgICAgIG91dGxpbmU6IG5vbmU7CiAgICAgICAgYmFja2dyb3VuZDogd2hpdGU7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgdGV4dC1hbGlnbjogbGVmdDsKICAgICAgfQoKICAgICAgOmhvc3QoW2hpZGRlbl0pLCAucGFwZXItaXRlbVtoaWRkZW5dIHsKICAgICAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIDpob3N0KC5pcm9uLXNlbGVjdGVkKSwgLnBhcGVyLWl0ZW0uaXJvbi1zZWxlY3RlZCB7CiAgICAgICAgZm9udC13ZWlnaHQ6IHZhcigtLXBhcGVyLWl0ZW0tc2VsZWN0ZWQtd2VpZ2h0LCBib2xkKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaXRlbS1zZWxlY3RlZDsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSksIC5wYXBlci1pdGVtW2Rpc2FibGVkXSB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWl0ZW0tZGlzYWJsZWQtY29sb3IsIHZhcigtLWRpc2FibGVkLXRleHQtY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaXRlbS1kaXNhYmxlZDsKICAgICAgfQoKICAgICAgOmhvc3QoOmZvY3VzKSwgLnBhcGVyLWl0ZW06Zm9jdXMgewogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBvdXRsaW5lOiAwOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1pdGVtLWZvY3VzZWQ7CiAgICAgIH0KCiAgICAgIDpob3N0KDpmb2N1cyk6YmVmb3JlLCAucGFwZXItaXRlbTpmb2N1czpiZWZvcmUgewogICAgICAgIEBhcHBseSAtLWxheW91dC1maXQ7CgogICAgICAgIGJhY2tncm91bmQ6IGN1cnJlbnRDb2xvcjsKICAgICAgICBjb250ZW50OiAnJzsKICAgICAgICBvcGFjaXR5OiB2YXIoLS1kYXJrLWRpdmlkZXItb3BhY2l0eSk7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWl0ZW0tZm9jdXNlZC1iZWZvcmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJDMuY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoKICAgIGBQYXBlckl0ZW1CZWhhdmlvcmAgaXMgYSBjb252ZW5pZW5jZSBiZWhhdmlvciBzaGFyZWQgYnkgPHBhcGVyLWl0ZW0+IGFuZAogICAgPHBhcGVyLWljb24taXRlbT4gdGhhdCBtYW5hZ2VzIHRoZSBzaGFyZWQgY29udHJvbCBzdGF0ZXMgYW5kIGF0dHJpYnV0ZXMgb2YKICAgIHRoZSBpdGVtcy4KICAgICovCiAgICAvKiogQHBvbHltZXJCZWhhdmlvciBQYXBlckl0ZW1CZWhhdmlvciAqLwogICAgY29uc3QgUGFwZXJJdGVtQmVoYXZpb3JJbXBsID0gewogICAgICBob3N0QXR0cmlidXRlczoge3JvbGU6ICdvcHRpb24nLCB0YWJpbmRleDogJzAnfQogICAgfTsKCiAgICAvKiogQHBvbHltZXJCZWhhdmlvciAqLwogICAgY29uc3QgUGFwZXJJdGVtQmVoYXZpb3IgPQogICAgICAgIFtJcm9uQnV0dG9uU3RhdGUsIElyb25Db250cm9sU3RhdGUsIFBhcGVySXRlbUJlaGF2aW9ySW1wbF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbTGlzdHNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9saXN0cy5odG1sKQoKICAgIGA8cGFwZXItaXRlbT5gIGlzIGFuIGludGVyYWN0aXZlIGxpc3QgaXRlbS4gQnkgZGVmYXVsdCwgaXQgaXMgYSBob3Jpem9udGFsCiAgICBmbGV4Ym94LgoKICAgICAgICA8cGFwZXItaXRlbT5JdGVtPC9wYXBlci1pdGVtPgoKICAgIFVzZSB0aGlzIGVsZW1lbnQgd2l0aCBgPHBhcGVyLWl0ZW0tYm9keT5gIHRvIG1ha2UgTWF0ZXJpYWwgRGVzaWduIHN0eWxlZAogICAgdHdvLWxpbmUgYW5kIHRocmVlLWxpbmUgaXRlbXMuCgogICAgICAgIDxwYXBlci1pdGVtPgogICAgICAgICAgPHBhcGVyLWl0ZW0tYm9keSB0d28tbGluZT4KICAgICAgICAgICAgPGRpdj5TaG93IHlvdXIgc3RhdHVzPC9kaXY+CiAgICAgICAgICAgIDxkaXYgc2Vjb25kYXJ5PllvdXIgc3RhdHVzIGlzIHZpc2libGUgdG8gZXZlcnlvbmU8L2Rpdj4KICAgICAgICAgIDwvcGFwZXItaXRlbS1ib2R5PgogICAgICAgICAgPGlyb24taWNvbiBpY29uPSJ3YXJuaW5nIj48L2lyb24taWNvbj4KICAgICAgICA8L3BhcGVyLWl0ZW0+CgogICAgVG8gdXNlIGBwYXBlci1pdGVtYCBhcyBhIGxpbmssIHdyYXAgaXQgaW4gYW4gYW5jaG9yIHRhZy4gU2luY2UgYHBhcGVyLWl0ZW1gIHdpbGwKICAgIGFscmVhZHkgcmVjZWl2ZSBmb2N1cywgeW91IG1heSB3YW50IHRvIHByZXZlbnQgdGhlIGFuY2hvciB0YWcgZnJvbSByZWNlaXZpbmcKICAgIGZvY3VzIGFzIHdlbGwgYnkgc2V0dGluZyBpdHMgdGFiaW5kZXggdG8gLTEuCgogICAgICAgIDxhIGhyZWY9Imh0dHBzOi8vd3d3LnBvbHltZXItcHJvamVjdC5vcmcvIiB0YWJpbmRleD0iLTEiPgogICAgICAgICAgPHBhcGVyLWl0ZW0gcmFpc2VkPlBvbHltZXIgUHJvamVjdDwvcGFwZXItaXRlbT4KICAgICAgICA8L2E+CgogICAgSWYgeW91IGFyZSBjb25jZXJuZWQgYWJvdXQgcGVyZm9ybWFuY2UgYW5kIHdhbnQgdG8gdXNlIGBwYXBlci1pdGVtYCBpbiBhCiAgICBgcGFwZXItbGlzdGJveGAgd2l0aCBtYW55IGl0ZW1zLCB5b3UgY2FuIGp1c3QgdXNlIGEgbmF0aXZlIGBidXR0b25gIHdpdGggdGhlCiAgICBgcGFwZXItaXRlbWAgY2xhc3MgYXBwbGllZCAocHJvdmlkZWQgeW91IGhhdmUgY29ycmVjdGx5IGluY2x1ZGVkIHRoZSBzaGFyZWQKICAgIHN0eWxlcyk6CgogICAgICAgIDxzdHlsZSBpcz0iY3VzdG9tLXN0eWxlIiBpbmNsdWRlPSJwYXBlci1pdGVtLXNoYXJlZC1zdHlsZXMiPjwvc3R5bGU+CgogICAgICAgIDxwYXBlci1saXN0Ym94PgogICAgICAgICAgPGJ1dHRvbiBjbGFzcz0icGFwZXItaXRlbSIgcm9sZT0ib3B0aW9uIj5JbmJveDwvYnV0dG9uPgogICAgICAgICAgPGJ1dHRvbiBjbGFzcz0icGFwZXItaXRlbSIgcm9sZT0ib3B0aW9uIj5TdGFycmVkPC9idXR0b24+CiAgICAgICAgICA8YnV0dG9uIGNsYXNzPSJwYXBlci1pdGVtIiByb2xlPSJvcHRpb24iPlNlbnQgbWFpbDwvYnV0dG9uPgogICAgICAgIDwvcGFwZXItbGlzdGJveD4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLWl0ZW0tbWluLWhlaWdodGAgfCBNaW5pbXVtIGhlaWdodCBvZiB0aGUgaXRlbSB8IGA0OHB4YAogICAgYC0tcGFwZXItaXRlbWAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBpdGVtIHwgYHt9YAogICAgYC0tcGFwZXItaXRlbS1zZWxlY3RlZC13ZWlnaHRgIHwgVGhlIGZvbnQgd2VpZ2h0IG9mIGEgc2VsZWN0ZWQgaXRlbSB8IGBib2xkYAogICAgYC0tcGFwZXItaXRlbS1zZWxlY3RlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHNlbGVjdGVkIHBhcGVyLWl0ZW1zIHwgYHt9YAogICAgYC0tcGFwZXItaXRlbS1kaXNhYmxlZC1jb2xvcmAgfCBUaGUgY29sb3IgZm9yIGRpc2FibGVkIHBhcGVyLWl0ZW1zIHwgYC0tZGlzYWJsZWQtdGV4dC1jb2xvcmAKICAgIGAtLXBhcGVyLWl0ZW0tZGlzYWJsZWRgIHwgTWl4aW4gYXBwbGllZCB0byBkaXNhYmxlZCBwYXBlci1pdGVtcyB8IGB7fWAKICAgIGAtLXBhcGVyLWl0ZW0tZm9jdXNlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIGZvY3VzZWQgcGFwZXItaXRlbXMgfCBge31gCiAgICBgLS1wYXBlci1pdGVtLWZvY3VzZWQtYmVmb3JlYCB8IE1peGluIGFwcGxpZWQgdG8gOmJlZm9yZSBmb2N1c2VkIHBhcGVyLWl0ZW1zIHwgYHt9YAoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgVGhpcyBlbGVtZW50IGhhcyBgcm9sZT0ibGlzdGl0ZW0iYCBieSBkZWZhdWx0LiBEZXBlbmRpbmcgb24gdXNhZ2UsIGl0IG1heSBiZQogICAgbW9yZSBhcHByb3ByaWF0ZSB0byBzZXQgYHJvbGU9Im1lbnVpdGVtImAsIGByb2xlPSJtZW51aXRlbWNoZWNrYm94ImAgb3IKICAgIGByb2xlPSJtZW51aXRlbXJhZGlvImAuCgogICAgICAgIDxwYXBlci1pdGVtIHJvbGU9Im1lbnVpdGVtY2hlY2tib3giPgogICAgICAgICAgPHBhcGVyLWl0ZW0tYm9keT4KICAgICAgICAgICAgU2hvdyB5b3VyIHN0YXR1cwogICAgICAgICAgPC9wYXBlci1pdGVtLWJvZHk+CiAgICAgICAgICA8cGFwZXItY2hlY2tib3g+PC9wYXBlci1jaGVja2JveD4KICAgICAgICA8L3BhcGVyLWl0ZW0+CgogICAgQGdyb3VwIFBhcGVyIEVsZW1lbnRzCiAgICBAZWxlbWVudCBwYXBlci1pdGVtCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlIGluY2x1ZGU9InBhcGVyLWl0ZW0tc2hhcmVkLXN0eWxlcyI+CiAgICAgIDpob3N0IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtc3ViaGVhZDsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaXRlbTsKICAgICAgfQogICAgPC9zdHlsZT4KICAgIDxzbG90Pjwvc2xvdD4KYCwKCiAgICAgIGlzOiAncGFwZXItaXRlbScsCiAgICAgIGJlaGF2aW9yczogW1BhcGVySXRlbUJlaGF2aW9yXQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoKICAgIFVzZSBgPHBhcGVyLWl0ZW0tYm9keT5gIGluIGEgYDxwYXBlci1pdGVtPmAgb3IgYDxwYXBlci1pY29uLWl0ZW0+YCB0byBtYWtlIHR3by0KICAgIG9yIHRocmVlLSBsaW5lIGl0ZW1zLiBJdCBpcyBhIGZsZXggaXRlbSB0aGF0IGlzIGEgdmVydGljYWwgZmxleGJveC4KCiAgICAgICAgPHBhcGVyLWl0ZW0+CiAgICAgICAgICA8cGFwZXItaXRlbS1ib2R5IHR3by1saW5lPgogICAgICAgICAgICA8ZGl2PlNob3cgeW91ciBzdGF0dXM8L2Rpdj4KICAgICAgICAgICAgPGRpdiBzZWNvbmRhcnk+WW91ciBzdGF0dXMgaXMgdmlzaWJsZSB0byBldmVyeW9uZTwvZGl2PgogICAgICAgICAgPC9wYXBlci1pdGVtLWJvZHk+CiAgICAgICAgPC9wYXBlci1pdGVtPgoKICAgIFRoZSBjaGlsZCBlbGVtZW50cyB3aXRoIHRoZSBgc2Vjb25kYXJ5YCBhdHRyaWJ1dGUgaXMgZ2l2ZW4gc2Vjb25kYXJ5IHRleHQKICAgIHN0eWxpbmcuCgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1pdGVtLWJvZHktdHdvLWxpbmUtbWluLWhlaWdodGAgfCBNaW5pbXVtIGhlaWdodCBvZiBhIHR3by1saW5lIGl0ZW0gfCBgNzJweGAKICAgIGAtLXBhcGVyLWl0ZW0tYm9keS10aHJlZS1saW5lLW1pbi1oZWlnaHRgIHwgTWluaW11bSBoZWlnaHQgb2YgYSB0aHJlZS1saW5lIGl0ZW0gfCBgODhweGAKICAgIGAtLXBhcGVyLWl0ZW0tYm9keS1zZWNvbmRhcnktY29sb3JgIHwgRm9yZWdyb3VuZCBjb2xvciBmb3IgdGhlIGBzZWNvbmRhcnlgIGFyZWEgfCBgLS1zZWNvbmRhcnktdGV4dC1jb2xvcmAKICAgIGAtLXBhcGVyLWl0ZW0tYm9keS1zZWNvbmRhcnlgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgYHNlY29uZGFyeWAgYXJlYSB8IGB7fWAKCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIG92ZXJmbG93OiBoaWRkZW47IC8qIG5lZWRlZCBmb3IgdGV4dC1vdmVyZmxvdzogZWxsaXBzaXMgdG8gd29yayBvbiBmZiAqLwogICAgICAgIEBhcHBseSAtLWxheW91dC12ZXJ0aWNhbDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyLWp1c3RpZmllZDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtZmxleDsKICAgICAgfQoKICAgICAgOmhvc3QoW3R3by1saW5lXSkgewogICAgICAgIG1pbi1oZWlnaHQ6IHZhcigtLXBhcGVyLWl0ZW0tYm9keS10d28tbGluZS1taW4taGVpZ2h0LCA3MnB4KTsKICAgICAgfQoKICAgICAgOmhvc3QoW3RocmVlLWxpbmVdKSB7CiAgICAgICAgbWluLWhlaWdodDogdmFyKC0tcGFwZXItaXRlbS1ib2R5LXRocmVlLWxpbmUtbWluLWhlaWdodCwgODhweCk7CiAgICAgIH0KCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKCopIHsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICAgIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzOwogICAgICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7CiAgICAgIH0KCiAgICAgIDpob3N0ID4gOjpzbG90dGVkKFtzZWNvbmRhcnldKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1ib2R5MTsKCiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWl0ZW0tYm9keS1zZWNvbmRhcnktY29sb3IsIHZhcigtLXNlY29uZGFyeS10ZXh0LWNvbG9yKSk7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLWl0ZW0tYm9keS1zZWNvbmRhcnk7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgLAoKICAgICAgaXM6ICdwYXBlci1pdGVtLWJvZHknCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKgogICAgYDxwYXBlci1pY29uLWl0ZW0+YCBpcyBhIGNvbnZlbmllbmNlIGVsZW1lbnQgdG8gbWFrZSBhbiBpdGVtIHdpdGggaWNvbi4gSXQgaXMgYW4KICAgIGludGVyYWN0aXZlIGxpc3QgaXRlbSB3aXRoIGEgZml4ZWQtd2lkdGggaWNvbiBhcmVhLCBhY2NvcmRpbmcgdG8gTWF0ZXJpYWwKICAgIERlc2lnbi4gVGhpcyBpcyB1c2VmdWwgaWYgdGhlIGljb25zIGFyZSBvZiB2YXJ5aW5nIHdpZHRocywgYnV0IHlvdSB3YW50IHRoZSBpdGVtCiAgICBib2RpZXMgdG8gbGluZSB1cC4gVXNlIHRoaXMgbGlrZSBhIGA8cGFwZXItaXRlbT5gLiBUaGUgY2hpbGQgbm9kZSB3aXRoIHRoZSBzbG90CiAgICBuYW1lIGBpdGVtLWljb25gIGlzIHBsYWNlZCBpbiB0aGUgaWNvbiBhcmVhLgoKICAgICAgICA8cGFwZXItaWNvbi1pdGVtPgogICAgICAgICAgPGlyb24taWNvbiBpY29uPSJmYXZvcml0ZSIgc2xvdD0iaXRlbS1pY29uIj48L2lyb24taWNvbj4KICAgICAgICAgIEZhdm9yaXRlCiAgICAgICAgPC9wYXBlci1pY29uLWl0ZW0+CiAgICAgICAgPHBhcGVyLWljb24taXRlbT4KICAgICAgICAgIDxkaXYgY2xhc3M9ImF2YXRhciIgc2xvdD0iaXRlbS1pY29uIj48L2Rpdj4KICAgICAgICAgIEF2YXRhcgogICAgICAgIDwvcGFwZXItaWNvbi1pdGVtPgoKICAgICMjIyBTdHlsaW5nCgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItaXRlbS1pY29uLXdpZHRoYCB8IFdpZHRoIG9mIHRoZSBpY29uIGFyZWEgfCBgNTZweGAKICAgIGAtLXBhcGVyLWl0ZW0taWNvbmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBpY29uIGFyZWEgfCBge31gCiAgICBgLS1wYXBlci1pY29uLWl0ZW1gIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgaXRlbSB8IGB7fWAKICAgIGAtLXBhcGVyLWl0ZW0tc2VsZWN0ZWQtd2VpZ2h0YCB8IFRoZSBmb250IHdlaWdodCBvZiBhIHNlbGVjdGVkIGl0ZW0gfCBgYm9sZGAKICAgIGAtLXBhcGVyLWl0ZW0tc2VsZWN0ZWRgIHwgTWl4aW4gYXBwbGllZCB0byBzZWxlY3RlZCBwYXBlci1pdGVtcyB8IGB7fWAKICAgIGAtLXBhcGVyLWl0ZW0tZGlzYWJsZWQtY29sb3JgIHwgVGhlIGNvbG9yIGZvciBkaXNhYmxlZCBwYXBlci1pdGVtcyB8IGAtLWRpc2FibGVkLXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1pdGVtLWRpc2FibGVkYCB8IE1peGluIGFwcGxpZWQgdG8gZGlzYWJsZWQgcGFwZXItaXRlbXMgfCBge31gCiAgICBgLS1wYXBlci1pdGVtLWZvY3VzZWRgIHwgTWl4aW4gYXBwbGllZCB0byBmb2N1c2VkIHBhcGVyLWl0ZW1zIHwgYHt9YAogICAgYC0tcGFwZXItaXRlbS1mb2N1c2VkLWJlZm9yZWAgfCBNaXhpbiBhcHBsaWVkIHRvIDpiZWZvcmUgZm9jdXNlZCBwYXBlci1pdGVtcyB8IGB7fWAKCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZSBpbmNsdWRlPSJwYXBlci1pdGVtLXNoYXJlZC1zdHlsZXMiPjwvc3R5bGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtc3ViaGVhZDsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItaXRlbTsKICAgICAgICBAYXBwbHkgLS1wYXBlci1pY29uLWl0ZW07CiAgICAgIH0KCiAgICAgIC5jb250ZW50LWljb24gewogICAgICAgIEBhcHBseSAtLWxheW91dC1ob3Jpem9udGFsOwogICAgICAgIEBhcHBseSAtLWxheW91dC1jZW50ZXI7CgogICAgICAgIHdpZHRoOiB2YXIoLS1wYXBlci1pdGVtLWljb24td2lkdGgsIDU2cHgpOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWl0ZW0taWNvbjsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8ZGl2IGlkPSJjb250ZW50SWNvbiIgY2xhc3M9ImNvbnRlbnQtaWNvbiI+CiAgICAgIDxzbG90IG5hbWU9Iml0ZW0taWNvbiI+PC9zbG90PgogICAgPC9kaXY+CiAgICA8c2xvdD48L3Nsb3Q+CmAsCgogICAgICBpczogJ3BhcGVyLWljb24taXRlbScsCiAgICAgIGJlaGF2aW9yczogW1BhcGVySXRlbUJlaGF2aW9yXQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lckJlaGF2aW9yIElyb25NdWx0aVNlbGVjdGFibGVCZWhhdmlvcgogICAgICovCiAgICBjb25zdCBJcm9uTXVsdGlTZWxlY3RhYmxlQmVoYXZpb3JJbXBsID0gewogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIG11bHRpcGxlIHNlbGVjdGlvbnMgYXJlIGFsbG93ZWQuCiAgICAgICAgICovCiAgICAgICAgbXVsdGk6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2UsIG9ic2VydmVyOiAnbXVsdGlDaGFuZ2VkJ30sCgogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgb3Igc2V0cyB0aGUgc2VsZWN0ZWQgZWxlbWVudHMuIFRoaXMgaXMgdXNlZCBpbnN0ZWFkIG9mIGBzZWxlY3RlZGAKICAgICAgICAgKiB3aGVuIGBtdWx0aWAgaXMgdHJ1ZS4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZFZhbHVlczogewogICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgIH0KICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGFuIGFycmF5IG9mIGN1cnJlbnRseSBzZWxlY3RlZCBpdGVtcy4KICAgICAgICAgKi8KICAgICAgICBzZWxlY3RlZEl0ZW1zOiB7CiAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICB9CiAgICAgICAgfSwKCiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6IFsnX3VwZGF0ZVNlbGVjdGVkKHNlbGVjdGVkVmFsdWVzLnNwbGljZXMpJ10sCgogICAgICAvKioKICAgICAgICogU2VsZWN0cyB0aGUgZ2l2ZW4gdmFsdWUuIElmIHRoZSBgbXVsdGlgIHByb3BlcnR5IGlzIHRydWUsIHRoZW4gdGhlIHNlbGVjdGVkCiAgICAgICAqIHN0YXRlIG9mIHRoZSBgdmFsdWVgIHdpbGwgYmUgdG9nZ2xlZDsgb3RoZXJ3aXNlIHRoZSBgdmFsdWVgIHdpbGwgYmUKICAgICAgICogc2VsZWN0ZWQuCiAgICAgICAqCiAgICAgICAqIEBtZXRob2Qgc2VsZWN0CiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfG51bWJlcn0gdmFsdWUgdGhlIHZhbHVlIHRvIHNlbGVjdC4KICAgICAgICovCiAgICAgIHNlbGVjdDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICBpZiAodGhpcy5tdWx0aSkgewogICAgICAgICAgdGhpcy5fdG9nZ2xlU2VsZWN0ZWQodmFsdWUpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnNlbGVjdGVkID0gdmFsdWU7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgbXVsdGlDaGFuZ2VkOiBmdW5jdGlvbihtdWx0aSkgewogICAgICAgIHRoaXMuX3NlbGVjdGlvbi5tdWx0aSA9IG11bHRpOwogICAgICAgIHRoaXMuX3VwZGF0ZVNlbGVjdGVkKCk7CiAgICAgIH0sCgogICAgICAvLyBVTlVTRUQsIEZPUiBBUEkgQ09NUEFUSUJJTElUWQogICAgICBnZXQgX3Nob3VsZFVwZGF0ZVNlbGVjdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5zZWxlY3RlZCAhPSBudWxsIHx8CiAgICAgICAgICAgICh0aGlzLnNlbGVjdGVkVmFsdWVzICE9IG51bGwgJiYgdGhpcy5zZWxlY3RlZFZhbHVlcy5sZW5ndGgpOwogICAgICB9LAoKICAgICAgX3VwZGF0ZUF0dHJGb3JTZWxlY3RlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLm11bHRpKSB7CiAgICAgICAgICBJcm9uU2VsZWN0YWJsZUJlaGF2aW9yLl91cGRhdGVBdHRyRm9yU2VsZWN0ZWQuYXBwbHkodGhpcyk7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLnNlbGVjdGVkSXRlbXMgJiYgdGhpcy5zZWxlY3RlZEl0ZW1zLmxlbmd0aCA+IDApIHsKICAgICAgICAgIHRoaXMuc2VsZWN0ZWRWYWx1ZXMgPQogICAgICAgICAgICAgIHRoaXMuc2VsZWN0ZWRJdGVtcwogICAgICAgICAgICAgICAgICAubWFwKAogICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oc2VsZWN0ZWRJdGVtKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9pbmRleFRvVmFsdWUodGhpcy5pbmRleE9mKHNlbGVjdGVkSXRlbSkpOwogICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICAgIHRoaXMpCiAgICAgICAgICAgICAgICAgIC5maWx0ZXIoZnVuY3Rpb24odW5maWx0ZXJlZFZhbHVlKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHVuZmlsdGVyZWRWYWx1ZSAhPSBudWxsOwogICAgICAgICAgICAgICAgICB9LCB0aGlzKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfdXBkYXRlU2VsZWN0ZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm11bHRpKSB7CiAgICAgICAgICB0aGlzLl9zZWxlY3RNdWx0aSh0aGlzLnNlbGVjdGVkVmFsdWVzKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fc2VsZWN0U2VsZWN0ZWQodGhpcy5zZWxlY3RlZCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3NlbGVjdE11bHRpOiBmdW5jdGlvbih2YWx1ZXMpIHsKICAgICAgICB2YWx1ZXMgPSB2YWx1ZXMgfHwgW107CgogICAgICAgIHZhciBzZWxlY3RlZEl0ZW1zID0KICAgICAgICAgICAgKHRoaXMuX3ZhbHVlc1RvSXRlbXModmFsdWVzKSB8fCBbXSkuZmlsdGVyKGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICAgICAgICByZXR1cm4gaXRlbSAhPT0gbnVsbCAmJiBpdGVtICE9PSB1bmRlZmluZWQ7CiAgICAgICAgICAgIH0pOwoKICAgICAgICAvLyBjbGVhciBhbGwgYnV0IHRoZSBjdXJyZW50IHNlbGVjdGVkIGl0ZW1zCiAgICAgICAgdGhpcy5fc2VsZWN0aW9uLmNsZWFyKHNlbGVjdGVkSXRlbXMpOwoKICAgICAgICAvLyBzZWxlY3Qgb25seSB0aG9zZSBub3Qgc2VsZWN0ZWQgeWV0CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBzZWxlY3RlZEl0ZW1zLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICB0aGlzLl9zZWxlY3Rpb24uc2V0SXRlbVNlbGVjdGVkKHNlbGVjdGVkSXRlbXNbaV0sIHRydWUpOwogICAgICAgIH0KCiAgICAgICAgLy8gQ2hlY2sgZm9yIGl0ZW1zLCBzaW5jZSB0aGlzIGFycmF5IGlzIHBvcHVsYXRlZCBvbmx5IHdoZW4gYXR0YWNoZWQKICAgICAgICBpZiAodGhpcy5mYWxsYmFja1NlbGVjdGlvbiAmJiAhdGhpcy5fc2VsZWN0aW9uLmdldCgpLmxlbmd0aCkgewogICAgICAgICAgdmFyIGZhbGxiYWNrID0gdGhpcy5fdmFsdWVUb0l0ZW0odGhpcy5mYWxsYmFja1NlbGVjdGlvbik7CiAgICAgICAgICBpZiAoZmFsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5zZWxlY3QodGhpcy5mYWxsYmFja1NlbGVjdGlvbik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3NlbGVjdGlvbkNoYW5nZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHMgPSB0aGlzLl9zZWxlY3Rpb24uZ2V0KCk7CiAgICAgICAgaWYgKHRoaXMubXVsdGkpIHsKICAgICAgICAgIHRoaXMuX3NldFNlbGVjdGVkSXRlbXMocyk7CiAgICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW0ocy5sZW5ndGggPyBzWzBdIDogbnVsbCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChzICE9PSBudWxsICYmIHMgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW1zKFtzXSk7CiAgICAgICAgICAgIHRoaXMuX3NldFNlbGVjdGVkSXRlbShzKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRoaXMuX3NldFNlbGVjdGVkSXRlbXMoW10pOwogICAgICAgICAgICB0aGlzLl9zZXRTZWxlY3RlZEl0ZW0obnVsbCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3RvZ2dsZVNlbGVjdGVkOiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgIHZhciBpID0gdGhpcy5zZWxlY3RlZFZhbHVlcy5pbmRleE9mKHZhbHVlKTsKICAgICAgICB2YXIgdW5zZWxlY3RlZCA9IGkgPCAwOwogICAgICAgIGlmICh1bnNlbGVjdGVkKSB7CiAgICAgICAgICB0aGlzLnB1c2goJ3NlbGVjdGVkVmFsdWVzJywgdmFsdWUpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnNwbGljZSgnc2VsZWN0ZWRWYWx1ZXMnLCBpLCAxKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfdmFsdWVzVG9JdGVtczogZnVuY3Rpb24odmFsdWVzKSB7CiAgICAgICAgcmV0dXJuICh2YWx1ZXMgPT0gbnVsbCkgPyBudWxsIDogdmFsdWVzLm1hcChmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX3ZhbHVlVG9JdGVtKHZhbHVlKTsKICAgICAgICB9LCB0aGlzKTsKICAgICAgfQogICAgfTsKCiAgICAvKiogQHBvbHltZXJCZWhhdmlvciAqLwogICAgY29uc3QgSXJvbk11bHRpU2VsZWN0YWJsZUJlaGF2aW9yID0KICAgICAgICBbSXJvblNlbGVjdGFibGVCZWhhdmlvciwgSXJvbk11bHRpU2VsZWN0YWJsZUJlaGF2aW9ySW1wbF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBgSXJvbk1lbnVCZWhhdmlvcmAgaW1wbGVtZW50cyBhY2Nlc3NpYmxlIG1lbnUgYmVoYXZpb3IuCiAgICAgKgogICAgICogQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAgKiBAcG9seW1lckJlaGF2aW9yIElyb25NZW51QmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgSXJvbk1lbnVCZWhhdmlvckltcGwgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIGN1cnJlbnRseSBmb2N1c2VkIGl0ZW0uCiAgICAgICAgICogQHR5cGUgez9PYmplY3R9CiAgICAgICAgICovCiAgICAgICAgZm9jdXNlZEl0ZW06CiAgICAgICAgICAgIHtvYnNlcnZlcjogJ19mb2N1c2VkSXRlbUNoYW5nZWQnLCByZWFkT25seTogdHJ1ZSwgdHlwZTogT2JqZWN0fSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGF0dHJpYnV0ZSB0byB1c2Ugb24gbWVudSBpdGVtcyB0byBsb29rIHVwIHRoZSBpdGVtIHRpdGxlLiBUeXBpbmcgdGhlCiAgICAgICAgICogZmlyc3QgbGV0dGVyIG9mIGFuIGl0ZW0gd2hlbiB0aGUgbWVudSBpcyBvcGVuIGZvY3VzZXMgdGhhdCBpdGVtLiBJZgogICAgICAgICAqIHVuc2V0LCBgdGV4dENvbnRlbnRgIHdpbGwgYmUgdXNlZC4KICAgICAgICAgKi8KICAgICAgICBhdHRyRm9ySXRlbVRpdGxlOiB7dHlwZTogU3RyaW5nfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQHR5cGUge2Jvb2xlYW59CiAgICAgICAgICovCiAgICAgICAgZGlzYWJsZWQ6IHsKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICBvYnNlcnZlcjogJ19kaXNhYmxlZENoYW5nZWQnLAogICAgICAgIH0sCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIGxpc3Qgb2Yga2V5cyBoYXMgYmVlbiB0YWtlbiBmcm9tCiAgICAgICAqIGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9LZXlib2FyZEV2ZW50L2dldE1vZGlmaWVyU3RhdGUKICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9NT0RJRklFUl9LRVlTOiBbCiAgICAgICAgJ0FsdCcsCiAgICAgICAgJ0FsdEdyYXBoJywKICAgICAgICAnQ2Fwc0xvY2snLAogICAgICAgICdDb250cm9sJywKICAgICAgICAnRm4nLAogICAgICAgICdGbkxvY2snLAogICAgICAgICdIeXBlcicsCiAgICAgICAgJ01ldGEnLAogICAgICAgICdOdW1Mb2NrJywKICAgICAgICAnT1MnLAogICAgICAgICdTY3JvbGxMb2NrJywKICAgICAgICAnU2hpZnQnLAogICAgICAgICdTdXBlcicsCiAgICAgICAgJ1N5bWJvbCcsCiAgICAgICAgJ1N5bWJvbExvY2snCiAgICAgIF0sCgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgX1NFQVJDSF9SRVNFVF9USU1FT1VUX01TOiAxMDAwLAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIF9wcmV2aW91c1RhYkluZGV4OiAwLAoKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHsKICAgICAgICAncm9sZSc6ICdtZW51JywKICAgICAgfSwKCiAgICAgIG9ic2VydmVyczogWydfdXBkYXRlTXVsdGlzZWxlY3RhYmxlKG11bHRpKSddLAoKICAgICAgbGlzdGVuZXJzOiB7CiAgICAgICAgJ2ZvY3VzJzogJ19vbkZvY3VzJywKICAgICAgICAna2V5ZG93bic6ICdfb25LZXlkb3duJywKICAgICAgICAnaXJvbi1pdGVtcy1jaGFuZ2VkJzogJ19vbklyb25JdGVtc0NoYW5nZWQnCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQHR5cGUgeyFPYmplY3R9CiAgICAgICAqLwogICAgICBrZXlCaW5kaW5nczogewogICAgICAgICd1cCc6ICdfb25VcEtleScsCiAgICAgICAgJ2Rvd24nOiAnX29uRG93bktleScsCiAgICAgICAgJ2VzYyc6ICdfb25Fc2NLZXknLAogICAgICAgICdzaGlmdCt0YWI6a2V5ZG93bic6ICdfb25TaGlmdFRhYkRvd24nCiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcmVzZXRUYWJpbmRpY2VzKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2VsZWN0cyB0aGUgZ2l2ZW4gdmFsdWUuIElmIHRoZSBgbXVsdGlgIHByb3BlcnR5IGlzIHRydWUsIHRoZW4gdGhlIHNlbGVjdGVkCiAgICAgICAqIHN0YXRlIG9mIHRoZSBgdmFsdWVgIHdpbGwgYmUgdG9nZ2xlZDsgb3RoZXJ3aXNlIHRoZSBgdmFsdWVgIHdpbGwgYmUKICAgICAgICogc2VsZWN0ZWQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfG51bWJlcn0gdmFsdWUgdGhlIHZhbHVlIHRvIHNlbGVjdC4KICAgICAgICovCiAgICAgIHNlbGVjdDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAvLyBDYW5jZWwgYXV0b21hdGljYWxseSBmb2N1c2luZyBhIGRlZmF1bHQgaXRlbSBpZiB0aGUgbWVudSByZWNlaXZlZCBmb2N1cwogICAgICAgIC8vIHRocm91Z2ggYSB1c2VyIGFjdGlvbiBzZWxlY3RpbmcgYSBwYXJ0aWN1bGFyIGl0ZW0uCiAgICAgICAgaWYgKHRoaXMuX2RlZmF1bHRGb2N1c0FzeW5jKSB7CiAgICAgICAgICB0aGlzLmNhbmNlbEFzeW5jKHRoaXMuX2RlZmF1bHRGb2N1c0FzeW5jKTsKICAgICAgICAgIHRoaXMuX2RlZmF1bHRGb2N1c0FzeW5jID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgdmFyIGl0ZW0gPSB0aGlzLl92YWx1ZVRvSXRlbSh2YWx1ZSk7CiAgICAgICAgaWYgKGl0ZW0gJiYgaXRlbS5oYXNBdHRyaWJ1dGUoJ2Rpc2FibGVkJykpCiAgICAgICAgICByZXR1cm47CiAgICAgICAgdGhpcy5fc2V0Rm9jdXNlZEl0ZW0oaXRlbSk7CiAgICAgICAgSXJvbk11bHRpU2VsZWN0YWJsZUJlaGF2aW9ySW1wbC5zZWxlY3QuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXNldHMgYWxsIHRhYmluZGV4IGF0dHJpYnV0ZXMgdG8gdGhlIGFwcHJvcHJpYXRlIHZhbHVlIGJhc2VkIG9uIHRoZQogICAgICAgKiBjdXJyZW50IHNlbGVjdGlvbiBzdGF0ZS4gVGhlIGFwcHJvcHJpYXRlIHZhbHVlIGlzIGAwYCAoZm9jdXNhYmxlKSBmb3IKICAgICAgICogdGhlIGRlZmF1bHQgc2VsZWN0ZWQgaXRlbSwgYW5kIGAtMWAgKG5vdCBrZXlib2FyZCBmb2N1c2FibGUpIGZvciBhbGwKICAgICAgICogb3RoZXIgaXRlbXMuIEFsc28gc2V0cyB0aGUgY29ycmVjdCBpbml0aWFsIHZhbHVlcyBmb3IgYXJpYS1zZWxlY3RlZAogICAgICAgKiBhdHRyaWJ1dGUsIHRydWUgZm9yIGRlZmF1bHQgc2VsZWN0ZWQgaXRlbSBhbmQgZmFsc2UgZm9yIG90aGVycy4KICAgICAgICovCiAgICAgIF9yZXNldFRhYmluZGljZXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBmaXJzdFNlbGVjdGVkSXRlbSA9IHRoaXMubXVsdGkgPwogICAgICAgICAgICAodGhpcy5zZWxlY3RlZEl0ZW1zICYmIHRoaXMuc2VsZWN0ZWRJdGVtc1swXSkgOgogICAgICAgICAgICB0aGlzLnNlbGVjdGVkSXRlbTsKCiAgICAgICAgdGhpcy5pdGVtcy5mb3JFYWNoKGZ1bmN0aW9uKGl0ZW0pIHsKICAgICAgICAgIGl0ZW0uc2V0QXR0cmlidXRlKCd0YWJpbmRleCcsIGl0ZW0gPT09IGZpcnN0U2VsZWN0ZWRJdGVtID8gJzAnIDogJy0xJyk7CiAgICAgICAgICBpdGVtLnNldEF0dHJpYnV0ZSgnYXJpYS1zZWxlY3RlZCcsIHRoaXMuX3NlbGVjdGlvbi5pc1NlbGVjdGVkKGl0ZW0pKTsKICAgICAgICB9LCB0aGlzKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZXRzIGFwcHJvcHJpYXRlIEFSSUEgYmFzZWQgb24gd2hldGhlciBvciBub3QgdGhlIG1lbnUgaXMgbWVhbnQgdG8gYmUKICAgICAgICogbXVsdGktc2VsZWN0YWJsZS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtib29sZWFufSBtdWx0aSBUcnVlIGlmIHRoZSBtZW51IHNob3VsZCBiZSBtdWx0aS1zZWxlY3RhYmxlLgogICAgICAgKi8KICAgICAgX3VwZGF0ZU11bHRpc2VsZWN0YWJsZTogZnVuY3Rpb24obXVsdGkpIHsKICAgICAgICBpZiAobXVsdGkpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdhcmlhLW11bHRpc2VsZWN0YWJsZScsICd0cnVlJyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhcmlhLW11bHRpc2VsZWN0YWJsZScpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBHaXZlbiBhIEtleWJvYXJkRXZlbnQsIHRoaXMgbWV0aG9kIHdpbGwgZm9jdXMgdGhlIGFwcHJvcHJpYXRlIGl0ZW0gaW4gdGhlCiAgICAgICAqIG1lbnUgKGlmIHRoZXJlIGlzIGEgcmVsZXZhbnQgaXRlbSwgYW5kIGl0IGlzIHBvc3NpYmxlIHRvIGZvY3VzIGl0KS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtLZXlib2FyZEV2ZW50fSBldmVudCBBIEtleWJvYXJkRXZlbnQuCiAgICAgICAqLwogICAgICBfZm9jdXNXaXRoS2V5Ym9hcmRFdmVudDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICAvLyBNYWtlIHN1cmUgdGhhdCB0aGUga2V5IHByZXNzZWQgaXMgbm90IGEgbW9kaWZpZXIga2V5LgogICAgICAgIC8vIGdldE1vZGlmaWVyU3RhdGUgaXMgbm90IGJlaW5nIHVzZWQsIGFzIGl0IGlzIG5vdCBhdmFpbGFibGUgaW4gU2FmYXJpCiAgICAgICAgLy8gZWFybGllciB0aGFuIDEwLjAuMiAoaHR0cHM6Ly90cmFjLndlYmtpdC5vcmcvY2hhbmdlc2V0LzIwNjcyNS93ZWJraXQpCiAgICAgICAgaWYgKHRoaXMuX01PRElGSUVSX0tFWVMuaW5kZXhPZihldmVudC5rZXkpICE9PSAtMSkKICAgICAgICAgIHJldHVybjsKCiAgICAgICAgdGhpcy5jYW5jZWxEZWJvdW5jZXIoJ19jbGVhclNlYXJjaFRleHQnKTsKCiAgICAgICAgdmFyIHNlYXJjaFRleHQgPSB0aGlzLl9zZWFyY2hUZXh0IHx8ICcnOwogICAgICAgIHZhciBrZXkgPSBldmVudC5rZXkgJiYgZXZlbnQua2V5Lmxlbmd0aCA9PSAxID8KICAgICAgICAgICAgZXZlbnQua2V5IDoKICAgICAgICAgICAgU3RyaW5nLmZyb21DaGFyQ29kZShldmVudC5rZXlDb2RlKTsKICAgICAgICBzZWFyY2hUZXh0ICs9IGtleS50b0xvY2FsZUxvd2VyQ2FzZSgpOwoKICAgICAgICB2YXIgc2VhcmNoTGVuZ3RoID0gc2VhcmNoVGV4dC5sZW5ndGg7CgogICAgICAgIGZvciAodmFyIGkgPSAwLCBpdGVtOyBpdGVtID0gdGhpcy5pdGVtc1tpXTsgaSsrKSB7CiAgICAgICAgICBpZiAoaXRlbS5oYXNBdHRyaWJ1dGUoJ2Rpc2FibGVkJykpIHsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICB9CgogICAgICAgICAgdmFyIGF0dHIgPSB0aGlzLmF0dHJGb3JJdGVtVGl0bGUgfHwgJ3RleHRDb250ZW50JzsKICAgICAgICAgIHZhciB0aXRsZSA9IChpdGVtW2F0dHJdIHx8IGl0ZW0uZ2V0QXR0cmlidXRlKGF0dHIpIHx8ICcnKS50cmltKCk7CgogICAgICAgICAgaWYgKHRpdGxlLmxlbmd0aCA8IHNlYXJjaExlbmd0aCkgewogICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAodGl0bGUuc2xpY2UoMCwgc2VhcmNoTGVuZ3RoKS50b0xvY2FsZUxvd2VyQ2FzZSgpID09IHNlYXJjaFRleHQpIHsKICAgICAgICAgICAgdGhpcy5fc2V0Rm9jdXNlZEl0ZW0oaXRlbSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5fc2VhcmNoVGV4dCA9IHNlYXJjaFRleHQ7CiAgICAgICAgdGhpcy5kZWJvdW5jZSgKICAgICAgICAgICAgJ19jbGVhclNlYXJjaFRleHQnLAogICAgICAgICAgICB0aGlzLl9jbGVhclNlYXJjaFRleHQsCiAgICAgICAgICAgIHRoaXMuX1NFQVJDSF9SRVNFVF9USU1FT1VUX01TKTsKICAgICAgfSwKCiAgICAgIF9jbGVhclNlYXJjaFRleHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3NlYXJjaFRleHQgPSAnJzsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBGb2N1c2VzIHRoZSBwcmV2aW91cyBpdGVtIChyZWxhdGl2ZSB0byB0aGUgY3VycmVudGx5IGZvY3VzZWQgaXRlbSkgaW4gdGhlCiAgICAgICAqIG1lbnUsIGRpc2FibGVkIGl0ZW1zIHdpbGwgYmUgc2tpcHBlZC4KICAgICAgICogTG9vcCB1bnRpbCBsZW5ndGggKyAxIHRvIGhhbmRsZSBjYXNlIG9mIHNpbmdsZSBpdGVtIGluIG1lbnUuCiAgICAgICAqLwogICAgICBfZm9jdXNQcmV2aW91czogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGxlbmd0aCA9IHRoaXMuaXRlbXMubGVuZ3RoOwogICAgICAgIHZhciBjdXJGb2N1c0luZGV4ID0gTnVtYmVyKHRoaXMuaW5kZXhPZih0aGlzLmZvY3VzZWRJdGVtKSk7CgogICAgICAgIGZvciAodmFyIGkgPSAxOyBpIDwgbGVuZ3RoICsgMTsgaSsrKSB7CiAgICAgICAgICB2YXIgaXRlbSA9IHRoaXMuaXRlbXNbKGN1ckZvY3VzSW5kZXggLSBpICsgbGVuZ3RoKSAlIGxlbmd0aF07CiAgICAgICAgICBpZiAoIWl0ZW0uaGFzQXR0cmlidXRlKCdkaXNhYmxlZCcpKSB7CiAgICAgICAgICAgIHZhciBvd25lciA9IGRvbShpdGVtKS5nZXRPd25lclJvb3QoKSB8fCBkb2N1bWVudDsKICAgICAgICAgICAgdGhpcy5fc2V0Rm9jdXNlZEl0ZW0oaXRlbSk7CgogICAgICAgICAgICAvLyBGb2N1cyBtaWdodCBub3QgaGF2ZSB3b3JrZWQsIGlmIHRoZSBlbGVtZW50IHdhcyBoaWRkZW4gb3Igbm90CiAgICAgICAgICAgIC8vIGZvY3VzYWJsZS4gSW4gdGhhdCBjYXNlLCB0cnkgYWdhaW4uCiAgICAgICAgICAgIGlmIChkb20ob3duZXIpLmFjdGl2ZUVsZW1lbnQgPT0gaXRlbSkgewogICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBGb2N1c2VzIHRoZSBuZXh0IGl0ZW0gKHJlbGF0aXZlIHRvIHRoZSBjdXJyZW50bHkgZm9jdXNlZCBpdGVtKSBpbiB0aGUKICAgICAgICogbWVudSwgZGlzYWJsZWQgaXRlbXMgd2lsbCBiZSBza2lwcGVkLgogICAgICAgKiBMb29wIHVudGlsIGxlbmd0aCArIDEgdG8gaGFuZGxlIGNhc2Ugb2Ygc2luZ2xlIGl0ZW0gaW4gbWVudS4KICAgICAgICovCiAgICAgIF9mb2N1c05leHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBsZW5ndGggPSB0aGlzLml0ZW1zLmxlbmd0aDsKICAgICAgICB2YXIgY3VyRm9jdXNJbmRleCA9IE51bWJlcih0aGlzLmluZGV4T2YodGhpcy5mb2N1c2VkSXRlbSkpOwoKICAgICAgICBmb3IgKHZhciBpID0gMTsgaSA8IGxlbmd0aCArIDE7IGkrKykgewogICAgICAgICAgdmFyIGl0ZW0gPSB0aGlzLml0ZW1zWyhjdXJGb2N1c0luZGV4ICsgaSkgJSBsZW5ndGhdOwogICAgICAgICAgaWYgKCFpdGVtLmhhc0F0dHJpYnV0ZSgnZGlzYWJsZWQnKSkgewogICAgICAgICAgICB2YXIgb3duZXIgPSBkb20oaXRlbSkuZ2V0T3duZXJSb290KCkgfHwgZG9jdW1lbnQ7CiAgICAgICAgICAgIHRoaXMuX3NldEZvY3VzZWRJdGVtKGl0ZW0pOwoKICAgICAgICAgICAgLy8gRm9jdXMgbWlnaHQgbm90IGhhdmUgd29ya2VkLCBpZiB0aGUgZWxlbWVudCB3YXMgaGlkZGVuIG9yIG5vdAogICAgICAgICAgICAvLyBmb2N1c2FibGUuIEluIHRoYXQgY2FzZSwgdHJ5IGFnYWluLgogICAgICAgICAgICBpZiAoZG9tKG93bmVyKS5hY3RpdmVFbGVtZW50ID09IGl0ZW0pIHsKICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogTXV0YXRlcyBpdGVtcyBpbiB0aGUgbWVudSBiYXNlZCBvbiBwcm92aWRlZCBzZWxlY3Rpb24gZGV0YWlscywgc28gdGhhdAogICAgICAgKiBhbGwgaXRlbXMgY29ycmVjdGx5IHJlZmxlY3Qgc2VsZWN0aW9uIHN0YXRlLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0VsZW1lbnR9IGl0ZW0gQW4gaXRlbSBpbiB0aGUgbWVudS4KICAgICAgICogQHBhcmFtIHtib29sZWFufSBpc1NlbGVjdGVkIFRydWUgaWYgdGhlIGl0ZW0gc2hvdWxkIGJlIHNob3duIGluIGEKICAgICAgICogc2VsZWN0ZWQgc3RhdGUsIG90aGVyd2lzZSBmYWxzZS4KICAgICAgICovCiAgICAgIF9hcHBseVNlbGVjdGlvbjogZnVuY3Rpb24oaXRlbSwgaXNTZWxlY3RlZCkgewogICAgICAgIGlmIChpc1NlbGVjdGVkKSB7CiAgICAgICAgICBpdGVtLnNldEF0dHJpYnV0ZSgnYXJpYS1zZWxlY3RlZCcsICd0cnVlJyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGl0ZW0uc2V0QXR0cmlidXRlKCdhcmlhLXNlbGVjdGVkJywgJ2ZhbHNlJyk7CiAgICAgICAgfQogICAgICAgIElyb25TZWxlY3RhYmxlQmVoYXZpb3IuX2FwcGx5U2VsZWN0aW9uLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogRGlzY3JldGVseSB1cGRhdGVzIHRhYmluZGV4IHZhbHVlcyBhbW9uZyBtZW51IGl0ZW1zIGFzIHRoZSBmb2N1c2VkIGl0ZW0KICAgICAgICogY2hhbmdlcy4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBmb2N1c2VkSXRlbSBUaGUgZWxlbWVudCB0aGF0IGlzIGN1cnJlbnRseSBmb2N1c2VkLgogICAgICAgKiBAcGFyYW0gez9FbGVtZW50fSBvbGQgVGhlIGxhc3QgZWxlbWVudCB0aGF0IHdhcyBjb25zaWRlcmVkIGZvY3VzZWQsIGlmCiAgICAgICAqIGFwcGxpY2FibGUuCiAgICAgICAqLwogICAgICBfZm9jdXNlZEl0ZW1DaGFuZ2VkOiBmdW5jdGlvbihmb2N1c2VkSXRlbSwgb2xkKSB7CiAgICAgICAgb2xkICYmIG9sZC5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgJy0xJyk7CiAgICAgICAgaWYgKGZvY3VzZWRJdGVtICYmICFmb2N1c2VkSXRlbS5oYXNBdHRyaWJ1dGUoJ2Rpc2FibGVkJykgJiYKICAgICAgICAgICAgIXRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgIGZvY3VzZWRJdGVtLnNldEF0dHJpYnV0ZSgndGFiaW5kZXgnLCAnMCcpOwogICAgICAgICAgZm9jdXNlZEl0ZW0uZm9jdXMoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQSBoYW5kbGVyIHRoYXQgcmVzcG9uZHMgdG8gbXV0YXRpb24gY2hhbmdlcyByZWxhdGVkIHRvIHRoZSBsaXN0IG9mIGl0ZW1zCiAgICAgICAqIGluIHRoZSBtZW51LgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBbiBldmVudCBjb250YWluaW5nIG11dGF0aW9uIHJlY29yZHMgYXMgaXRzCiAgICAgICAqIGRldGFpbC4KICAgICAgICovCiAgICAgIF9vbklyb25JdGVtc0NoYW5nZWQ6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKGV2ZW50LmRldGFpbC5hZGRlZE5vZGVzLmxlbmd0aCkgewogICAgICAgICAgdGhpcy5fcmVzZXRUYWJpbmRpY2VzKCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEhhbmRsZXIgdGhhdCBpcyBjYWxsZWQgd2hlbiBhIHNoaWZ0K3RhYiBrZXlwcmVzcyBpcyBkZXRlY3RlZCBieSB0aGUgbWVudS4KICAgICAgICoKICAgICAgICogQHBhcmFtIHtDdXN0b21FdmVudH0gZXZlbnQgQSBrZXkgY29tYmluYXRpb24gZXZlbnQuCiAgICAgICAqLwogICAgICBfb25TaGlmdFRhYkRvd246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdmFyIG9sZFRhYkluZGV4ID0gdGhpcy5nZXRBdHRyaWJ1dGUoJ3RhYmluZGV4Jyk7CgogICAgICAgIElyb25NZW51QmVoYXZpb3JJbXBsLl9zaGlmdFRhYlByZXNzZWQgPSB0cnVlOwoKICAgICAgICB0aGlzLl9zZXRGb2N1c2VkSXRlbShudWxsKTsKCiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgJy0xJyk7CgogICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgndGFiaW5kZXgnLCBvbGRUYWJJbmRleCk7CiAgICAgICAgICBJcm9uTWVudUJlaGF2aW9ySW1wbC5fc2hpZnRUYWJQcmVzc2VkID0gZmFsc2U7CiAgICAgICAgICAvLyBOT1RFKGNkYXRhKTogcG9seW1lci9wb2x5bWVyIzEzMDUKICAgICAgICB9LCAxKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIYW5kbGVyIHRoYXQgaXMgY2FsbGVkIHdoZW4gdGhlIG1lbnUgcmVjZWl2ZXMgZm9jdXMuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Rm9jdXNFdmVudH0gZXZlbnQgQSBmb2N1cyBldmVudC4KICAgICAgICovCiAgICAgIF9vbkZvY3VzOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmIChJcm9uTWVudUJlaGF2aW9ySW1wbC5fc2hpZnRUYWJQcmVzc2VkKSB7CiAgICAgICAgICAvLyBkbyBub3QgZm9jdXMgdGhlIG1lbnUgaXRzZWxmCiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBEbyBub3QgZm9jdXMgdGhlIHNlbGVjdGVkIHRhYiBpZiB0aGUgZGVlcGVzdCB0YXJnZXQgaXMgcGFydCBvZiB0aGUKICAgICAgICAvLyBtZW51IGVsZW1lbnQncyBsb2NhbCBET00gYW5kIGlzIGZvY3VzYWJsZS4KICAgICAgICB2YXIgcm9vdFRhcmdldCA9CiAgICAgICAgICAgIC8qKiBAdHlwZSB7P0hUTUxFbGVtZW50fSAqLyAoZG9tKGV2ZW50KS5yb290VGFyZ2V0KTsKICAgICAgICBpZiAocm9vdFRhcmdldCAhPT0gdGhpcyAmJiB0eXBlb2Ygcm9vdFRhcmdldC50YWJJbmRleCAhPT0gJ3VuZGVmaW5lZCcgJiYKICAgICAgICAgICAgIXRoaXMuaXNMaWdodERlc2NlbmRhbnQocm9vdFRhcmdldCkpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIGNsZWFyIHRoZSBjYWNoZWQgZm9jdXMgaXRlbQogICAgICAgIHRoaXMuX2RlZmF1bHRGb2N1c0FzeW5jID0gdGhpcy5hc3luYyhmdW5jdGlvbigpIHsKICAgICAgICAgIC8vIGZvY3VzIHRoZSBzZWxlY3RlZCBpdGVtIHdoZW4gdGhlIG1lbnUgcmVjZWl2ZXMgZm9jdXMsIG9yIHRoZSBmaXJzdCBpdGVtCiAgICAgICAgICAvLyBpZiBubyBpdGVtIGlzIHNlbGVjdGVkCiAgICAgICAgICB2YXIgZmlyc3RTZWxlY3RlZEl0ZW0gPSB0aGlzLm11bHRpID8KICAgICAgICAgICAgICAodGhpcy5zZWxlY3RlZEl0ZW1zICYmIHRoaXMuc2VsZWN0ZWRJdGVtc1swXSkgOgogICAgICAgICAgICAgIHRoaXMuc2VsZWN0ZWRJdGVtOwoKICAgICAgICAgIHRoaXMuX3NldEZvY3VzZWRJdGVtKG51bGwpOwoKICAgICAgICAgIGlmIChmaXJzdFNlbGVjdGVkSXRlbSkgewogICAgICAgICAgICB0aGlzLl9zZXRGb2N1c2VkSXRlbShmaXJzdFNlbGVjdGVkSXRlbSk7CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuaXRlbXNbMF0pIHsKICAgICAgICAgICAgLy8gV2UgZmluZCB0aGUgZmlyc3Qgbm9uZS1kaXNhYmxlZCBpdGVtIChpZiBvbmUgZXhpc3RzKQogICAgICAgICAgICB0aGlzLl9mb2N1c05leHQoKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIYW5kbGVyIHRoYXQgaXMgY2FsbGVkIHdoZW4gdGhlIHVwIGtleSBpcyBwcmVzc2VkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBIGtleSBjb21iaW5hdGlvbiBldmVudC4KICAgICAgICovCiAgICAgIF9vblVwS2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIC8vIHVwIGFuZCBkb3duIGFycm93cyBtb3ZlcyB0aGUgZm9jdXMKICAgICAgICB0aGlzLl9mb2N1c1ByZXZpb3VzKCk7CiAgICAgICAgZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIYW5kbGVyIHRoYXQgaXMgY2FsbGVkIHdoZW4gdGhlIGRvd24ga2V5IGlzIHByZXNzZWQuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7Q3VzdG9tRXZlbnR9IGV2ZW50IEEga2V5IGNvbWJpbmF0aW9uIGV2ZW50LgogICAgICAgKi8KICAgICAgX29uRG93bktleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLl9mb2N1c05leHQoKTsKICAgICAgICBldmVudC5kZXRhaWwua2V5Ym9hcmRFdmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEhhbmRsZXIgdGhhdCBpcyBjYWxsZWQgd2hlbiB0aGUgZXNjIGtleSBpcyBwcmVzc2VkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0N1c3RvbUV2ZW50fSBldmVudCBBIGtleSBjb21iaW5hdGlvbiBldmVudC4KICAgICAgICovCiAgICAgIF9vbkVzY0tleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgZm9jdXNlZEl0ZW0gPSB0aGlzLmZvY3VzZWRJdGVtOwogICAgICAgIGlmIChmb2N1c2VkSXRlbSkgewogICAgICAgICAgZm9jdXNlZEl0ZW0uYmx1cigpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIYW5kbGVyIHRoYXQgaXMgY2FsbGVkIHdoZW4gYSBrZXlkb3duIGV2ZW50IGlzIGRldGVjdGVkLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge0tleWJvYXJkRXZlbnR9IGV2ZW50IEEga2V5Ym9hcmQgZXZlbnQuCiAgICAgICAqLwogICAgICBfb25LZXlkb3duOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy5rZXlib2FyZEV2ZW50TWF0Y2hlc0tleXMoZXZlbnQsICd1cCBkb3duIGVzYycpKSB7CiAgICAgICAgICAvLyBhbGwgb3RoZXIga2V5cyBmb2N1cyB0aGUgbWVudSBpdGVtIHN0YXJ0aW5nIHdpdGggdGhhdCBjaGFyYWN0ZXIKICAgICAgICAgIHRoaXMuX2ZvY3VzV2l0aEtleWJvYXJkRXZlbnQoZXZlbnQpOwogICAgICAgIH0KICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgfSwKCiAgICAgIC8vIG92ZXJyaWRlIF9hY3RpdmF0ZUhhbmRsZXIKICAgICAgX2FjdGl2YXRlSGFuZGxlcjogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBJcm9uU2VsZWN0YWJsZUJlaGF2aW9yLl9hY3RpdmF0ZUhhbmRsZXIuY2FsbCh0aGlzLCBldmVudCk7CiAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXBkYXRlcyB0aGlzIGVsZW1lbnQncyB0YWIgaW5kZXggd2hlbiBpdCdzIGVuYWJsZWQvZGlzYWJsZWQuCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gZGlzYWJsZWQKICAgICAgICovCiAgICAgIF9kaXNhYmxlZENoYW5nZWQ6IGZ1bmN0aW9uKGRpc2FibGVkKSB7CiAgICAgICAgaWYgKGRpc2FibGVkKSB7CiAgICAgICAgICB0aGlzLl9wcmV2aW91c1RhYkluZGV4ID0KICAgICAgICAgICAgICB0aGlzLmhhc0F0dHJpYnV0ZSgndGFiaW5kZXgnKSA/IHRoaXMudGFiSW5kZXggOiAwOwogICAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoCiAgICAgICAgICAgICAgJ3RhYmluZGV4Jyk7ICAvLyBObyB0YWJpbmRleCBtZWFucyBub3QgdGFiLWFibGUgb3Igc2VsZWN0LWFibGUuCiAgICAgICAgfSBlbHNlIGlmICghdGhpcy5oYXNBdHRyaWJ1dGUoJ3RhYmluZGV4JykpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCd0YWJpbmRleCcsIHRoaXMuX3ByZXZpb3VzVGFiSW5kZXgpOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICBJcm9uTWVudUJlaGF2aW9ySW1wbC5fc2hpZnRUYWJQcmVzc2VkID0gZmFsc2U7CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IElyb25NZW51QmVoYXZpb3IgPQogICAgICAgIFtJcm9uTXVsdGlTZWxlY3RhYmxlQmVoYXZpb3IsIElyb25BMTF5S2V5c0JlaGF2aW9yLCBJcm9uTWVudUJlaGF2aW9ySW1wbF07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbTWVudXNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9tZW51cy5odG1sKQoKICAgIGA8cGFwZXItbGlzdGJveD5gIGltcGxlbWVudHMgYW4gYWNjZXNzaWJsZSBsaXN0Ym94IGNvbnRyb2wgd2l0aCBNYXRlcmlhbCBEZXNpZ24KICAgIHN0eWxpbmcuIFRoZSBmb2N1c2VkIGl0ZW0gaXMgaGlnaGxpZ2h0ZWQsIGFuZCB0aGUgc2VsZWN0ZWQgaXRlbSBoYXMgYm9sZGVkIHRleHQuCgogICAgICAgIDxwYXBlci1saXN0Ym94PgogICAgICAgICAgPHBhcGVyLWl0ZW0+SXRlbSAxPC9wYXBlci1pdGVtPgogICAgICAgICAgPHBhcGVyLWl0ZW0+SXRlbSAyPC9wYXBlci1pdGVtPgogICAgICAgIDwvcGFwZXItbGlzdGJveD4KCiAgICBBbiBpbml0aWFsIHNlbGVjdGlvbiBjYW4gYmUgc3BlY2lmaWVkIHdpdGggdGhlIGBzZWxlY3RlZGAgYXR0cmlidXRlLgoKICAgICAgICA8cGFwZXItbGlzdGJveCBzZWxlY3RlZD0iMCI+CiAgICAgICAgICA8cGFwZXItaXRlbT5JdGVtIDE8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8cGFwZXItaXRlbT5JdGVtIDI8L3BhcGVyLWl0ZW0+CiAgICAgICAgPC9wYXBlci1saXN0Ym94PgoKICAgIE1ha2UgYSBtdWx0aS1zZWxlY3QgbGlzdGJveCB3aXRoIHRoZSBgbXVsdGlgIGF0dHJpYnV0ZS4gSXRlbXMgaW4gYSBtdWx0aS1zZWxlY3QKICAgIGxpc3Rib3ggY2FuIGJlIGRlc2VsZWN0ZWQsIGFuZCBtdWx0aXBsZSBpdGVtIGNhbiBiZSBzZWxlY3RlZC4KCiAgICAgICAgPHBhcGVyLWxpc3Rib3ggbXVsdGk+CiAgICAgICAgICA8cGFwZXItaXRlbT5JdGVtIDE8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8cGFwZXItaXRlbT5JdGVtIDI8L3BhcGVyLWl0ZW0+CiAgICAgICAgPC9wYXBlci1saXN0Ym94PgoKICAgICMjIyBTdHlsaW5nCgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItbGlzdGJveC1iYWNrZ3JvdW5kLWNvbG9yYCAgIHwgTWVudSBiYWNrZ3JvdW5kIGNvbG9yIHwKICAgIGAtLXByaW1hcnktYmFja2dyb3VuZC1jb2xvcmAKICAgIGAtLXBhcGVyLWxpc3Rib3gtY29sb3JgICAgICAgICAgICAgICB8IE1lbnUgZm9yZWdyb3VuZCBjb2xvciB8CiAgICBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1saXN0Ym94YCAgICAgICAgICAgICAgICAgICAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBsaXN0Ym94IHwgYHt9YAoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgYDxwYXBlci1saXN0Ym94PmAgaGFzIGByb2xlPSJsaXN0Ym94ImAgYnkgZGVmYXVsdC4gQSBtdWx0aS1zZWxlY3QgbGlzdGJveCB3aWxsCiAgICBhbHNvIGhhdmUgYGFyaWEtbXVsdGlzZWxlY3RhYmxlYCBzZXQuIEl0IGltcGxlbWVudHMga2V5IGJpbmRpbmdzIHRvIG5hdmlnYXRlCiAgICB0aHJvdWdoIHRoZSBsaXN0Ym94IHdpdGggdGhlIHVwIGFuZCBkb3duIGFycm93IGtleXMsIGVzYyB0byBleGl0IHRoZSBsaXN0Ym94LAogICAgYW5kIGVudGVyIHRvIGFjdGl2YXRlIGEgbGlzdGJveCBpdGVtLiBUeXBpbmcgdGhlIGZpcnN0IGxldHRlciBvZiBhIGxpc3Rib3ggaXRlbQogICAgd2lsbCBhbHNvIGZvY3VzIGl0LgoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItbGlzdGJveAogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHBhZGRpbmc6IDhweCAwOwoKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS1wYXBlci1saXN0Ym94LWJhY2tncm91bmQtY29sb3IsIHZhcigtLXByaW1hcnktYmFja2dyb3VuZC1jb2xvcikpOwogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1saXN0Ym94LWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItbGlzdGJveDsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8c2xvdD48L3Nsb3Q+CmAsCgogICAgICBpczogJ3BhcGVyLWxpc3Rib3gnLAogICAgICBiZWhhdmlvcnM6IFtJcm9uTWVudUJlaGF2aW9yXSwKCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBob3N0QXR0cmlidXRlczoge3JvbGU6ICdsaXN0Ym94J30KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwogICAgY29uc3QgdGVtcGxhdGUkYyA9IGh0bWxgCjxkb20tbW9kdWxlIGlkPSJwYXBlci1tYXRlcmlhbC1zaGFyZWQtc3R5bGVzIj4KICA8dGVtcGxhdGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgIDpob3N0KFtlbGV2YXRpb249IjEiXSkgewogICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tMmRwOwogICAgICB9CgogICAgICA6aG9zdChbZWxldmF0aW9uPSIyIl0pIHsKICAgICAgICBAYXBwbHkgLS1zaGFkb3ctZWxldmF0aW9uLTRkcDsKICAgICAgfQoKICAgICAgOmhvc3QoW2VsZXZhdGlvbj0iMyJdKSB7CiAgICAgICAgQGFwcGx5IC0tc2hhZG93LWVsZXZhdGlvbi02ZHA7CiAgICAgIH0KCiAgICAgIDpob3N0KFtlbGV2YXRpb249IjQiXSkgewogICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tOGRwOwogICAgICB9CgogICAgICA6aG9zdChbZWxldmF0aW9uPSI1Il0pIHsKICAgICAgICBAYXBwbHkgLS1zaGFkb3ctZWxldmF0aW9uLTE2ZHA7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPgpgOwogICAgdGVtcGxhdGUkYy5zZXRBdHRyaWJ1dGUoJ3N0eWxlJywgJ2Rpc3BsYXk6IG5vbmU7Jyk7CiAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKHRlbXBsYXRlJGMuY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbQ2FyZHNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9jYXJkcy5odG1sKQoKICAgIGBwYXBlci1tYXRlcmlhbGAgaXMgYSBjb250YWluZXIgdGhhdCByZW5kZXJzIHR3byBzaGFkb3dzIG9uIHRvcCBvZiBlYWNoIG90aGVyIHRvCiAgICBjcmVhdGUgdGhlIGVmZmVjdCBvZiBhIGxpZnRlZCBwaWVjZSBvZiBwYXBlci4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItbWF0ZXJpYWwgZWxldmF0aW9uPSIxIj4KICAgICAgICAgIC4uLiBjb250ZW50IC4uLgogICAgICAgIDwvcGFwZXItbWF0ZXJpYWw+CgogICAgQGdyb3VwIFBhcGVyIEVsZW1lbnRzCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlIGluY2x1ZGU9InBhcGVyLW1hdGVyaWFsLXNoYXJlZC1zdHlsZXMiPjwvc3R5bGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0KFthbmltYXRlZF0pIHsKICAgICAgICBAYXBwbHkgLS1zaGFkb3ctdHJhbnNpdGlvbjsKICAgICAgfQogICAgICA6aG9zdCB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItbWF0ZXJpYWw7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgLAoKICAgICAgaXM6ICdwYXBlci1tYXRlcmlhbCcsCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIHotZGVwdGggb2YgdGhpcyBlbGVtZW50LCBmcm9tIDAtNS4gU2V0dGluZyB0byAwIHdpbGwgcmVtb3ZlIHRoZQogICAgICAgICAqIHNoYWRvdywgYW5kIGVhY2ggaW5jcmVhc2luZyBudW1iZXIgZ3JlYXRlciB0aGFuIDAgd2lsbCBiZSAiZGVlcGVyIgogICAgICAgICAqIHRoYW4gdGhlIGxhc3QuCiAgICAgICAgICoKICAgICAgICAgKiBAYXR0cmlidXRlIGVsZXZhdGlvbgogICAgICAgICAqIEB0eXBlIG51bWJlcgogICAgICAgICAqIEBkZWZhdWx0IDEKICAgICAgICAgKi8KICAgICAgICBlbGV2YXRpb246IHt0eXBlOiBOdW1iZXIsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwgdmFsdWU6IDF9LAoKICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdGhpcyB0byB0cnVlIHRvIGFuaW1hdGUgdGhlIHNoYWRvdyB3aGVuIHNldHRpbmcgYSBuZXcKICAgICAgICAgKiBgZWxldmF0aW9uYCB2YWx1ZS4KICAgICAgICAgKgogICAgICAgICAqIEBhdHRyaWJ1dGUgYW5pbWF0ZWQKICAgICAgICAgKiBAdHlwZSBib29sZWFuCiAgICAgICAgICogQGRlZmF1bHQgZmFsc2UKICAgICAgICAgKi8KICAgICAgICBhbmltYXRlZDoge3R5cGU6IEJvb2xlYW4sIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwgdmFsdWU6IGZhbHNlfQogICAgICB9CiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICAqIGBpcm9uLXJhbmdlLWJlaGF2aW9yYCBwcm92aWRlcyB0aGUgYmVoYXZpb3IgZm9yIHNvbWV0aGluZyB3aXRoIGEgbWluaW11bSB0bwogICAgICogbWF4aW11bSByYW5nZS4KICAgICAqCiAgICAgKiBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICAqIEBwb2x5bWVyQmVoYXZpb3IKICAgICAqLwogICAgY29uc3QgSXJvblJhbmdlQmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBudW1iZXIgdGhhdCByZXByZXNlbnRzIHRoZSBjdXJyZW50IHZhbHVlLgogICAgICAgICAqLwogICAgICAgIHZhbHVlOiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMCwgbm90aWZ5OiB0cnVlLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbnVtYmVyIHRoYXQgaW5kaWNhdGVzIHRoZSBtaW5pbXVtIHZhbHVlIG9mIHRoZSByYW5nZS4KICAgICAgICAgKi8KICAgICAgICBtaW46IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAwLCBub3RpZnk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbnVtYmVyIHRoYXQgaW5kaWNhdGVzIHRoZSBtYXhpbXVtIHZhbHVlIG9mIHRoZSByYW5nZS4KICAgICAgICAgKi8KICAgICAgICBtYXg6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAxMDAsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFNwZWNpZmllcyB0aGUgdmFsdWUgZ3JhbnVsYXJpdHkgb2YgdGhlIHJhbmdlJ3MgdmFsdWUuCiAgICAgICAgICovCiAgICAgICAgc3RlcDoge3R5cGU6IE51bWJlciwgdmFsdWU6IDEsIG5vdGlmeTogdHJ1ZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIHJhdGlvIG9mIHRoZSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICByYXRpbzoge3R5cGU6IE51bWJlciwgdmFsdWU6IDAsIHJlYWRPbmx5OiB0cnVlLCBub3RpZnk6IHRydWV9LAogICAgICB9LAoKICAgICAgb2JzZXJ2ZXJzOiBbJ191cGRhdGUodmFsdWUsIG1pbiwgbWF4LCBzdGVwKSddLAoKICAgICAgX2NhbGNSYXRpbzogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICByZXR1cm4gKHRoaXMuX2NsYW1wVmFsdWUodmFsdWUpIC0gdGhpcy5taW4pIC8gKHRoaXMubWF4IC0gdGhpcy5taW4pOwogICAgICB9LAoKICAgICAgX2NsYW1wVmFsdWU6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgcmV0dXJuIE1hdGgubWluKHRoaXMubWF4LCBNYXRoLm1heCh0aGlzLm1pbiwgdGhpcy5fY2FsY1N0ZXAodmFsdWUpKSk7CiAgICAgIH0sCgogICAgICBfY2FsY1N0ZXA6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgLy8gcG9seW1lci9pc3N1ZXMvMjQ5MwogICAgICAgIHZhbHVlID0gcGFyc2VGbG9hdCh2YWx1ZSk7CgogICAgICAgIGlmICghdGhpcy5zdGVwKSB7CiAgICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgICAgfQoKICAgICAgICB2YXIgbnVtU3RlcHMgPSBNYXRoLnJvdW5kKCh2YWx1ZSAtIHRoaXMubWluKSAvIHRoaXMuc3RlcCk7CiAgICAgICAgaWYgKHRoaXMuc3RlcCA8IDEpIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogRm9yIHNtYWxsIHZhbHVlcyBvZiB0aGlzLnN0ZXAsIGlmIHdlIGNhbGN1bGF0ZSB0aGUgc3RlcCB1c2luZwogICAgICAgICAgICogYE1hdGgucm91bmQodmFsdWUgLyBzdGVwKSAqIHN0ZXBgIHdlIG1heSBoaXQgYSBwcmVjaXNpb24gcG9pbnQgaXNzdWUKICAgICAgICAgICAqIGVnLiAwLjEgKiAwLjIgPSAgMC4wMjAwMDAwMDAwMDAwMDAwMDQKICAgICAgICAgICAqIGh0dHA6Ly9kb2NzLm9yYWNsZS5jb20vY2QvRTE5OTU3LTAxLzgwNi0zNTY4L25jZ19nb2xkYmVyZy5odG1sCiAgICAgICAgICAgKgogICAgICAgICAgICogYXMgYSB3b3JrIGFyb3VuZCB3ZSBjYW4gZGl2aWRlIGJ5IHRoZSByZWNpcHJvY2FsIG9mIGBzdGVwYAogICAgICAgICAgICovCiAgICAgICAgICByZXR1cm4gbnVtU3RlcHMgLyAoMSAvIHRoaXMuc3RlcCkgKyB0aGlzLm1pbjsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIG51bVN0ZXBzICogdGhpcy5zdGVwICsgdGhpcy5taW47CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3ZhbGlkYXRlVmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdGhpcy5fY2xhbXBWYWx1ZSh0aGlzLnZhbHVlKTsKICAgICAgICB0aGlzLnZhbHVlID0gdGhpcy5vbGRWYWx1ZSA9IGlzTmFOKHYpID8gdGhpcy5vbGRWYWx1ZSA6IHY7CiAgICAgICAgcmV0dXJuIHRoaXMudmFsdWUgIT09IHY7CiAgICAgIH0sCgogICAgICBfdXBkYXRlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl92YWxpZGF0ZVZhbHVlKCk7CiAgICAgICAgdGhpcy5fc2V0UmF0aW8odGhpcy5fY2FsY1JhdGlvKHRoaXMudmFsdWUpICogMTAwKTsKICAgICAgfQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246IFtQcm9ncmVzcyAmCiAgICBhY3Rpdml0eV0oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3Byb2dyZXNzLWFjdGl2aXR5Lmh0bWwpCgogICAgVGhlIHByb2dyZXNzIGJhcnMgYXJlIGZvciBzaXR1YXRpb25zIHdoZXJlIHRoZSBwZXJjZW50YWdlIGNvbXBsZXRlZCBjYW4gYmUKICAgIGRldGVybWluZWQuIFRoZXkgZ2l2ZSB1c2VycyBhIHF1aWNrIHNlbnNlIG9mIGhvdyBtdWNoIGxvbmdlciBhbiBvcGVyYXRpb24KICAgIHdpbGwgdGFrZS4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItcHJvZ3Jlc3MgdmFsdWU9IjEwIj48L3BhcGVyLXByb2dyZXNzPgoKICAgIFRoZXJlIGlzIGFsc28gYSBzZWNvbmRhcnkgcHJvZ3Jlc3Mgd2hpY2ggaXMgdXNlZnVsIGZvciBkaXNwbGF5aW5nIGludGVybWVkaWF0ZQogICAgcHJvZ3Jlc3MsIHN1Y2ggYXMgdGhlIGJ1ZmZlciBsZXZlbCBkdXJpbmcgYSBzdHJlYW1pbmcgcGxheWJhY2sgcHJvZ3Jlc3MgYmFyLgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1wcm9ncmVzcyB2YWx1ZT0iMTAiIHNlY29uZGFyeS1wcm9ncmVzcz0iMzAiPjwvcGFwZXItcHJvZ3Jlc3M+CgogICAgIyMjIFN0eWxpbmcgcHJvZ3Jlc3MgYmFyOgoKICAgIFRvIGNoYW5nZSB0aGUgYWN0aXZlIHByb2dyZXNzIGJhciBjb2xvcjoKCiAgICAgICAgcGFwZXItcHJvZ3Jlc3MgewogICAgICAgICAgIC0tcGFwZXItcHJvZ3Jlc3MtYWN0aXZlLWNvbG9yOiAjZTkxZTYzOwogICAgICAgIH0KCiAgICBUbyBjaGFuZ2UgdGhlIHNlY29uZGFyeSBwcm9ncmVzcyBiYXIgY29sb3I6CgogICAgICAgIHBhcGVyLXByb2dyZXNzIHsKICAgICAgICAgIC0tcGFwZXItcHJvZ3Jlc3Mtc2Vjb25kYXJ5LWNvbG9yOiAjZjhiYmQwOwogICAgICAgIH0KCiAgICBUbyBjaGFuZ2UgdGhlIHByb2dyZXNzIGJhciBiYWNrZ3JvdW5kIGNvbG9yOgoKICAgICAgICBwYXBlci1wcm9ncmVzcyB7CiAgICAgICAgICAtLXBhcGVyLXByb2dyZXNzLWNvbnRhaW5lci1jb2xvcjogIzY0ZmZkYTsKICAgICAgICB9CgogICAgQWRkIHRoZSBjbGFzcyBgdHJhbnNpdGluZ2AgdG8gYSBwYXBlci1wcm9ncmVzcyB0byBhbmltYXRlIHRoZSBwcm9ncmVzcyBiYXIgd2hlbgogICAgdGhlIHZhbHVlIGNoYW5nZWQuIFlvdSBjYW4gYWxzbyBjdXN0b21pemUgdGhlIHRyYW5zaXRpb246CgogICAgICAgIHBhcGVyLXByb2dyZXNzIHsKICAgICAgICAgIC0tcGFwZXItcHJvZ3Jlc3MtdHJhbnNpdGlvbi1kdXJhdGlvbjogMC4wOHM7CiAgICAgICAgICAtLXBhcGVyLXByb2dyZXNzLXRyYW5zaXRpb24tdGltaW5nLWZ1bmN0aW9uOiBlYXNlOwogICAgICAgICAgLS1wYXBlci1wcm9ncmVzcy10cmFuc2l0aW9uLWRlbGF5OiAwczsKICAgICAgICB9CgogICAgVG8gY2hhbmdlIHRoZSBkdXJhdGlvbiBvZiB0aGUgaW5kZXRlcm1pbmF0ZSBjeWNsZToKCiAgICAgICAgcGFwZXItcHJvZ3Jlc3MgewogICAgICAgICAgLS1wYXBlci1wcm9ncmVzcy1pbmRldGVybWluYXRlLWN5Y2xlLWR1cmF0aW9uOiAyczsKICAgICAgICB9CgogICAgVGhlIGZvbGxvd2luZyBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0KICAgIGAtLXBhcGVyLXByb2dyZXNzLWNvbnRhaW5lcmAgfCBNaXhpbiBhcHBsaWVkIHRvIGNvbnRhaW5lciB8IGB7fWAKICAgIGAtLXBhcGVyLXByb2dyZXNzLXRyYW5zaXRpb24tZHVyYXRpb25gIHwgRHVyYXRpb24gb2YgdGhlIHRyYW5zaXRpb24gfCBgMC4wOHNgCiAgICBgLS1wYXBlci1wcm9ncmVzcy10cmFuc2l0aW9uLXRpbWluZy1mdW5jdGlvbmAgfCBUaGUgdGltaW5nIGZ1bmN0aW9uIGZvciB0aGUgdHJhbnNpdGlvbiB8IGBlYXNlYAogICAgYC0tcGFwZXItcHJvZ3Jlc3MtdHJhbnNpdGlvbi1kZWxheWAgfCBkZWxheSBmb3IgdGhlIHRyYW5zaXRpb24gfCBgMHNgCiAgICBgLS1wYXBlci1wcm9ncmVzcy1jb250YWluZXItY29sb3JgIHwgQ29sb3Igb2YgdGhlIGNvbnRhaW5lciB8IGAtLWdvb2dsZS1ncmV5LTMwMGAKICAgIGAtLXBhcGVyLXByb2dyZXNzLWFjdGl2ZS1jb2xvcmAgfCBUaGUgY29sb3Igb2YgdGhlIGFjdGl2ZSBiYXIgfCBgLS1nb29nbGUtZ3JlZW4tNTAwYAogICAgYC0tcGFwZXItcHJvZ3Jlc3Mtc2Vjb25kYXJ5LWNvbG9yYCB8IFRoZSBjb2xvciBvZiB0aGUgc2Vjb25kYXJ5IGJhciB8IGAtLWdvb2dsZS1ncmVlbi0xMDBgCiAgICBgLS1wYXBlci1wcm9ncmVzcy1kaXNhYmxlZC1hY3RpdmUtY29sb3JgIHwgVGhlIGNvbG9yIG9mIHRoZSBhY3RpdmUgYmFyIGlmIGRpc2FibGVkIHwgYC0tZ29vZ2xlLWdyZXktNTAwYAogICAgYC0tcGFwZXItcHJvZ3Jlc3MtZGlzYWJsZWQtc2Vjb25kYXJ5LWNvbG9yYCB8IFRoZSBjb2xvciBvZiB0aGUgc2Vjb25kYXJ5IGJhciBpZiBkaXNhYmxlZCAgfCBgLS1nb29nbGUtZ3JleS0zMDBgCiAgICBgLS1wYXBlci1wcm9ncmVzcy1oZWlnaHRgIHwgVGhlIGhlaWdodCBvZiB0aGUgcHJvZ3Jlc3MgYmFyIHwgYDRweGAKICAgIGAtLXBhcGVyLXByb2dyZXNzLWluZGV0ZXJtaW5hdGUtY3ljbGUtZHVyYXRpb25gIHwgRHVyYXRpb24gb2YgYW4gaW5kZXRlcm1pbmF0ZSBjeWNsZSB8IGAyc2AKCiAgICBAZ3JvdXAgUGFwZXIgRWxlbWVudHMKICAgIEBlbGVtZW50IHBhcGVyLXByb2dyZXNzCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgd2lkdGg6IDIwMHB4OwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICB9CgogICAgICA6aG9zdChbaGlkZGVuXSksIFtoaWRkZW5dIHsKICAgICAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgICNwcm9ncmVzc0NvbnRhaW5lciB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItcHJvZ3Jlc3MtY29udGFpbmVyOwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgfQoKICAgICAgI3Byb2dyZXNzQ29udGFpbmVyLAogICAgICAvKiB0aGUgc3RyaXBlIGZvciB0aGUgaW5kZXRlcm1pbmF0ZSBhbmltYXRpb24qLwogICAgICAuaW5kZXRlcm1pbmF0ZTo6YWZ0ZXIgewogICAgICAgIGhlaWdodDogdmFyKC0tcGFwZXItcHJvZ3Jlc3MtaGVpZ2h0LCA0cHgpOwogICAgICB9CgogICAgICAjcHJpbWFyeVByb2dyZXNzLAogICAgICAjc2Vjb25kYXJ5UHJvZ3Jlc3MsCiAgICAgIC5pbmRldGVybWluYXRlOjphZnRlciB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZpdDsKICAgICAgfQoKICAgICAgI3Byb2dyZXNzQ29udGFpbmVyLAogICAgICAuaW5kZXRlcm1pbmF0ZTo6YWZ0ZXIgewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXBhcGVyLXByb2dyZXNzLWNvbnRhaW5lci1jb2xvciwgdmFyKC0tZ29vZ2xlLWdyZXktMzAwKSk7CiAgICAgIH0KCiAgICAgIDpob3N0KC50cmFuc2l0aW5nKSAjcHJpbWFyeVByb2dyZXNzLAogICAgICA6aG9zdCgudHJhbnNpdGluZykgI3NlY29uZGFyeVByb2dyZXNzIHsKICAgICAgICAtd2Via2l0LXRyYW5zaXRpb24tcHJvcGVydHk6IC13ZWJraXQtdHJhbnNmb3JtOwogICAgICAgIHRyYW5zaXRpb24tcHJvcGVydHk6IHRyYW5zZm9ybTsKCiAgICAgICAgLyogRHVyYXRpb24gKi8KICAgICAgICAtd2Via2l0LXRyYW5zaXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLXByb2dyZXNzLXRyYW5zaXRpb24tZHVyYXRpb24sIDAuMDhzKTsKICAgICAgICB0cmFuc2l0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci1wcm9ncmVzcy10cmFuc2l0aW9uLWR1cmF0aW9uLCAwLjA4cyk7CgogICAgICAgIC8qIFRpbWluZyBmdW5jdGlvbiAqLwogICAgICAgIC13ZWJraXQtdHJhbnNpdGlvbi10aW1pbmctZnVuY3Rpb246IHZhcigtLXBhcGVyLXByb2dyZXNzLXRyYW5zaXRpb24tdGltaW5nLWZ1bmN0aW9uLCBlYXNlKTsKICAgICAgICB0cmFuc2l0aW9uLXRpbWluZy1mdW5jdGlvbjogdmFyKC0tcGFwZXItcHJvZ3Jlc3MtdHJhbnNpdGlvbi10aW1pbmctZnVuY3Rpb24sIGVhc2UpOwoKICAgICAgICAvKiBEZWxheSAqLwogICAgICAgIC13ZWJraXQtdHJhbnNpdGlvbi1kZWxheTogdmFyKC0tcGFwZXItcHJvZ3Jlc3MtdHJhbnNpdGlvbi1kZWxheSwgMHMpOwogICAgICAgIHRyYW5zaXRpb24tZGVsYXk6IHZhcigtLXBhcGVyLXByb2dyZXNzLXRyYW5zaXRpb24tZGVsYXksIDBzKTsKICAgICAgfQoKICAgICAgI3ByaW1hcnlQcm9ncmVzcywKICAgICAgI3NlY29uZGFyeVByb2dyZXNzIHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtZml0OwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogbGVmdCBjZW50ZXI7CiAgICAgICAgdHJhbnNmb3JtLW9yaWdpbjogbGVmdCBjZW50ZXI7CiAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlWCgwKTsKICAgICAgICB0cmFuc2Zvcm06IHNjYWxlWCgwKTsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CgogICAgICAjcHJpbWFyeVByb2dyZXNzIHsKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS1wYXBlci1wcm9ncmVzcy1hY3RpdmUtY29sb3IsIHZhcigtLWdvb2dsZS1ncmVlbi01MDApKTsKICAgICAgfQoKICAgICAgI3NlY29uZGFyeVByb2dyZXNzIHsKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS1wYXBlci1wcm9ncmVzcy1zZWNvbmRhcnktY29sb3IsIHZhcigtLWdvb2dsZS1ncmVlbi0xMDApKTsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgI3ByaW1hcnlQcm9ncmVzcyB7CiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tcGFwZXItcHJvZ3Jlc3MtZGlzYWJsZWQtYWN0aXZlLWNvbG9yLCB2YXIoLS1nb29nbGUtZ3JleS01MDApKTsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgI3NlY29uZGFyeVByb2dyZXNzIHsKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS1wYXBlci1wcm9ncmVzcy1kaXNhYmxlZC1zZWNvbmRhcnktY29sb3IsIHZhcigtLWdvb2dsZS1ncmV5LTMwMCkpOwogICAgICB9CgogICAgICA6aG9zdCg6bm90KFtkaXNhYmxlZF0pKSAjcHJpbWFyeVByb2dyZXNzLmluZGV0ZXJtaW5hdGUgewogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogcmlnaHQgY2VudGVyOwogICAgICAgIHRyYW5zZm9ybS1vcmlnaW46IHJpZ2h0IGNlbnRlcjsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbjogaW5kZXRlcm1pbmF0ZS1iYXIgdmFyKC0tcGFwZXItcHJvZ3Jlc3MtaW5kZXRlcm1pbmF0ZS1jeWNsZS1kdXJhdGlvbiwgMnMpIGxpbmVhciBpbmZpbml0ZTsKICAgICAgICBhbmltYXRpb246IGluZGV0ZXJtaW5hdGUtYmFyIHZhcigtLXBhcGVyLXByb2dyZXNzLWluZGV0ZXJtaW5hdGUtY3ljbGUtZHVyYXRpb24sIDJzKSBsaW5lYXIgaW5maW5pdGU7CiAgICAgIH0KCiAgICAgIDpob3N0KDpub3QoW2Rpc2FibGVkXSkpICNwcmltYXJ5UHJvZ3Jlc3MuaW5kZXRlcm1pbmF0ZTo6YWZ0ZXIgewogICAgICAgIGNvbnRlbnQ6ICIiOwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtLW9yaWdpbjogY2VudGVyIGNlbnRlcjsKICAgICAgICB0cmFuc2Zvcm0tb3JpZ2luOiBjZW50ZXIgY2VudGVyOwoKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbjogaW5kZXRlcm1pbmF0ZS1zcGxpdHRlciB2YXIoLS1wYXBlci1wcm9ncmVzcy1pbmRldGVybWluYXRlLWN5Y2xlLWR1cmF0aW9uLCAycykgbGluZWFyIGluZmluaXRlOwogICAgICAgIGFuaW1hdGlvbjogaW5kZXRlcm1pbmF0ZS1zcGxpdHRlciB2YXIoLS1wYXBlci1wcm9ncmVzcy1pbmRldGVybWluYXRlLWN5Y2xlLWR1cmF0aW9uLCAycykgbGluZWFyIGluZmluaXRlOwogICAgICB9CgogICAgICBALXdlYmtpdC1rZXlmcmFtZXMgaW5kZXRlcm1pbmF0ZS1iYXIgewogICAgICAgIDAlIHsKICAgICAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZVgoMSkgdHJhbnNsYXRlWCgtMTAwJSk7CiAgICAgICAgfQogICAgICAgIDUwJSB7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGVYKDEpIHRyYW5zbGF0ZVgoMCUpOwogICAgICAgIH0KICAgICAgICA3NSUgewogICAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlWCgxKSB0cmFuc2xhdGVYKDAlKTsKICAgICAgICAgIC13ZWJraXQtYW5pbWF0aW9uLXRpbWluZy1mdW5jdGlvbjogY3ViaWMtYmV6aWVyKC4yOCwuNjIsLjM3LC45MSk7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlWCgwKSB0cmFuc2xhdGVYKDAlKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIEAtd2Via2l0LWtleWZyYW1lcyBpbmRldGVybWluYXRlLXNwbGl0dGVyIHsKICAgICAgICAwJSB7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGVYKC43NSkgdHJhbnNsYXRlWCgtMTI1JSk7CiAgICAgICAgfQogICAgICAgIDMwJSB7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGVYKC43NSkgdHJhbnNsYXRlWCgtMTI1JSk7CiAgICAgICAgICAtd2Via2l0LWFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllciguNDIsMCwuNiwuOCk7CiAgICAgICAgfQogICAgICAgIDkwJSB7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGVYKC43NSkgdHJhbnNsYXRlWCgxMjUlKTsKICAgICAgICB9CiAgICAgICAgMTAwJSB7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGVYKC43NSkgdHJhbnNsYXRlWCgxMjUlKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIEBrZXlmcmFtZXMgaW5kZXRlcm1pbmF0ZS1iYXIgewogICAgICAgIDAlIHsKICAgICAgICAgIHRyYW5zZm9ybTogc2NhbGVYKDEpIHRyYW5zbGF0ZVgoLTEwMCUpOwogICAgICAgIH0KICAgICAgICA1MCUgewogICAgICAgICAgdHJhbnNmb3JtOiBzY2FsZVgoMSkgdHJhbnNsYXRlWCgwJSk7CiAgICAgICAgfQogICAgICAgIDc1JSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHNjYWxlWCgxKSB0cmFuc2xhdGVYKDAlKTsKICAgICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllciguMjgsLjYyLC4zNywuOTEpOwogICAgICAgIH0KICAgICAgICAxMDAlIHsKICAgICAgICAgIHRyYW5zZm9ybTogc2NhbGVYKDApIHRyYW5zbGF0ZVgoMCUpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBpbmRldGVybWluYXRlLXNwbGl0dGVyIHsKICAgICAgICAwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHNjYWxlWCguNzUpIHRyYW5zbGF0ZVgoLTEyNSUpOwogICAgICAgIH0KICAgICAgICAzMCUgewogICAgICAgICAgdHJhbnNmb3JtOiBzY2FsZVgoLjc1KSB0cmFuc2xhdGVYKC0xMjUlKTsKICAgICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllciguNDIsMCwuNiwuOCk7CiAgICAgICAgfQogICAgICAgIDkwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHNjYWxlWCguNzUpIHRyYW5zbGF0ZVgoMTI1JSk7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgdHJhbnNmb3JtOiBzY2FsZVgoLjc1KSB0cmFuc2xhdGVYKDEyNSUpOwogICAgICAgIH0KICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8ZGl2IGlkPSJwcm9ncmVzc0NvbnRhaW5lciI+CiAgICAgIDxkaXYgaWQ9InNlY29uZGFyeVByb2dyZXNzIiBoaWRkZW5cJD0iW1tfaGlkZVNlY29uZGFyeVByb2dyZXNzKHNlY29uZGFyeVJhdGlvKV1dIj48L2Rpdj4KICAgICAgPGRpdiBpZD0icHJpbWFyeVByb2dyZXNzIj48L2Rpdj4KICAgIDwvZGl2PgpgLAoKICAgICAgaXM6ICdwYXBlci1wcm9ncmVzcycsCiAgICAgIGJlaGF2aW9yczogW0lyb25SYW5nZUJlaGF2aW9yXSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbnVtYmVyIHRoYXQgcmVwcmVzZW50cyB0aGUgY3VycmVudCBzZWNvbmRhcnkgcHJvZ3Jlc3MuCiAgICAgICAgICovCiAgICAgICAgc2Vjb25kYXJ5UHJvZ3Jlc3M6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAwfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIHNlY29uZGFyeSByYXRpbwogICAgICAgICAqLwogICAgICAgIHNlY29uZGFyeVJhdGlvOiB7dHlwZTogTnVtYmVyLCB2YWx1ZTogMCwgcmVhZE9ubHk6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBVc2UgYW4gaW5kZXRlcm1pbmF0ZSBwcm9ncmVzcyBpbmRpY2F0b3IuCiAgICAgICAgICovCiAgICAgICAgaW5kZXRlcm1pbmF0ZToKICAgICAgICAgICAge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZSwgb2JzZXJ2ZXI6ICdfdG9nZ2xlSW5kZXRlcm1pbmF0ZSd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIGlmIHRoZSBwcm9ncmVzcyBpcyBkaXNhYmxlZC4KICAgICAgICAgKi8KICAgICAgICBkaXNhYmxlZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgIG9ic2VydmVyOiAnX2Rpc2FibGVkQ2hhbmdlZCcKICAgICAgICB9CiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6CiAgICAgICAgICBbJ19wcm9ncmVzc0NoYW5nZWQoc2Vjb25kYXJ5UHJvZ3Jlc3MsIHZhbHVlLCBtaW4sIG1heCwgaW5kZXRlcm1pbmF0ZSknXSwKCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ3Byb2dyZXNzYmFyJ30sCgogICAgICBfdG9nZ2xlSW5kZXRlcm1pbmF0ZTogZnVuY3Rpb24oaW5kZXRlcm1pbmF0ZSkgewogICAgICAgIC8vIElmIHdlIHVzZSBhdHRyaWJ1dGUvY2xhc3MgYmluZGluZywgdGhlIGFuaW1hdGlvbiBzb21ldGltZXMgZG9lc24ndAogICAgICAgIC8vIHRyYW5zbGF0ZSBwcm9wZXJseSBvbiBTYWZhcmkgNy4xLiBTbyBpbnN0ZWFkLCB3ZSB0b2dnbGUgdGhlIGNsYXNzIGhlcmUgaW4KICAgICAgICAvLyB0aGUgdXBkYXRlIG1ldGhvZC4KICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdpbmRldGVybWluYXRlJywgaW5kZXRlcm1pbmF0ZSwgdGhpcy4kLnByaW1hcnlQcm9ncmVzcyk7CiAgICAgIH0sCgogICAgICBfdHJhbnNmb3JtUHJvZ3Jlc3M6IGZ1bmN0aW9uKHByb2dyZXNzLCByYXRpbykgewogICAgICAgIHZhciB0cmFuc2Zvcm0gPSAnc2NhbGVYKCcgKyAocmF0aW8gLyAxMDApICsgJyknOwogICAgICAgIHByb2dyZXNzLnN0eWxlLnRyYW5zZm9ybSA9IHByb2dyZXNzLnN0eWxlLndlYmtpdFRyYW5zZm9ybSA9IHRyYW5zZm9ybTsKICAgICAgfSwKCiAgICAgIF9tYWluUmF0aW9DaGFuZ2VkOiBmdW5jdGlvbihyYXRpbykgewogICAgICAgIHRoaXMuX3RyYW5zZm9ybVByb2dyZXNzKHRoaXMuJC5wcmltYXJ5UHJvZ3Jlc3MsIHJhdGlvKTsKICAgICAgfSwKCiAgICAgIF9wcm9ncmVzc0NoYW5nZWQ6IGZ1bmN0aW9uKAogICAgICAgICAgc2Vjb25kYXJ5UHJvZ3Jlc3MsIHZhbHVlLCBtaW4sIG1heCwgaW5kZXRlcm1pbmF0ZSkgewogICAgICAgIHNlY29uZGFyeVByb2dyZXNzID0gdGhpcy5fY2xhbXBWYWx1ZShzZWNvbmRhcnlQcm9ncmVzcyk7CiAgICAgICAgdmFsdWUgPSB0aGlzLl9jbGFtcFZhbHVlKHZhbHVlKTsKCiAgICAgICAgdmFyIHNlY29uZGFyeVJhdGlvID0gdGhpcy5fY2FsY1JhdGlvKHNlY29uZGFyeVByb2dyZXNzKSAqIDEwMDsKICAgICAgICB2YXIgbWFpblJhdGlvID0gdGhpcy5fY2FsY1JhdGlvKHZhbHVlKSAqIDEwMDsKCiAgICAgICAgdGhpcy5fc2V0U2Vjb25kYXJ5UmF0aW8oc2Vjb25kYXJ5UmF0aW8pOwogICAgICAgIHRoaXMuX3RyYW5zZm9ybVByb2dyZXNzKHRoaXMuJC5zZWNvbmRhcnlQcm9ncmVzcywgc2Vjb25kYXJ5UmF0aW8pOwogICAgICAgIHRoaXMuX3RyYW5zZm9ybVByb2dyZXNzKHRoaXMuJC5wcmltYXJ5UHJvZ3Jlc3MsIG1haW5SYXRpbyk7CgogICAgICAgIHRoaXMuc2Vjb25kYXJ5UHJvZ3Jlc3MgPSBzZWNvbmRhcnlQcm9ncmVzczsKCiAgICAgICAgaWYgKGluZGV0ZXJtaW5hdGUpIHsKICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhcmlhLXZhbHVlbm93Jyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdhcmlhLXZhbHVlbm93JywgdmFsdWUpOwogICAgICAgIH0KICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS12YWx1ZW1pbicsIG1pbik7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtdmFsdWVtYXgnLCBtYXgpOwogICAgICB9LAoKICAgICAgX2Rpc2FibGVkQ2hhbmdlZDogZnVuY3Rpb24oZGlzYWJsZWQpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1kaXNhYmxlZCcsIGRpc2FibGVkID8gJ3RydWUnIDogJ2ZhbHNlJyk7CiAgICAgIH0sCgogICAgICBfaGlkZVNlY29uZGFyeVByb2dyZXNzOiBmdW5jdGlvbihzZWNvbmRhcnlSYXRpbykgewogICAgICAgIHJldHVybiBzZWNvbmRhcnlSYXRpbyA9PT0gMDsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCB0ZW1wbGF0ZSRkID0gaHRtbGAKPHN0eWxlPgogIDpob3N0IHsKICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgIGxpbmUtaGVpZ2h0OiAwOwogICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgIGN1cnNvcjogcG9pbnRlcjsKICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAtLWNhbGN1bGF0ZWQtcGFwZXItcmFkaW8tYnV0dG9uLXNpemU6IHZhcigtLXBhcGVyLXJhZGlvLWJ1dHRvbi1zaXplLCAxNnB4KTsKICAgIC8qIC0xcHggaXMgYSBzZW50aW5lbCBmb3IgdGhlIGRlZmF1bHQgYW5kIGlzIHJlcGxhY2UgaW4gXGBhdHRhY2hlZFxgLiAqLwogICAgLS1jYWxjdWxhdGVkLXBhcGVyLXJhZGlvLWJ1dHRvbi1pbmstc2l6ZTogdmFyKC0tcGFwZXItcmFkaW8tYnV0dG9uLWluay1zaXplLCAtMXB4KTsKICB9CgogIDpob3N0KDpmb2N1cykgewogICAgb3V0bGluZTogbm9uZTsKICB9CgogICNyYWRpb0NvbnRhaW5lciB7CiAgICBAYXBwbHkgLS1sYXlvdXQtaW5saW5lOwogICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlci1jZW50ZXI7CiAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICB3aWR0aDogdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1yYWRpby1idXR0b24tc2l6ZSk7CiAgICBoZWlnaHQ6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItcmFkaW8tYnV0dG9uLXNpemUpOwogICAgdmVydGljYWwtYWxpZ246IG1pZGRsZTsKCiAgICBAYXBwbHkgLS1wYXBlci1yYWRpby1idXR0b24tcmFkaW8tY29udGFpbmVyOwogIH0KCiAgI2luayB7CiAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICB0b3A6IDUwJTsKICAgIGxlZnQ6IDUwJTsKICAgIHJpZ2h0OiBhdXRvOwogICAgd2lkdGg6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItcmFkaW8tYnV0dG9uLWluay1zaXplKTsKICAgIGhlaWdodDogdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1yYWRpby1idXR0b24taW5rLXNpemUpOwogICAgY29sb3I6IHZhcigtLXBhcGVyLXJhZGlvLWJ1dHRvbi11bmNoZWNrZWQtaW5rLWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgIG9wYWNpdHk6IDAuNjsKICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgLXdlYmtpdC10cmFuc2Zvcm06IHRyYW5zbGF0ZSgtNTAlLCAtNTAlKTsKICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlKC01MCUsIC01MCUpOwogIH0KCiAgI2lua1tjaGVja2VkXSB7CiAgICBjb2xvcjogdmFyKC0tcGFwZXItcmFkaW8tYnV0dG9uLWNoZWNrZWQtaW5rLWNvbG9yLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CiAgfQoKICAjb2ZmUmFkaW8sICNvblJhZGlvIHsKICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICB0b3A6IDA7CiAgICBsZWZ0OiAwOwogICAgd2lkdGg6IDEwMCU7CiAgICBoZWlnaHQ6IDEwMCU7CiAgICBib3JkZXItcmFkaXVzOiA1MCU7CiAgfQoKICAjb2ZmUmFkaW8gewogICAgYm9yZGVyOiAycHggc29saWQgdmFyKC0tcGFwZXItcmFkaW8tYnV0dG9uLXVuY2hlY2tlZC1jb2xvciwgdmFyKC0tcHJpbWFyeS10ZXh0LWNvbG9yKSk7CiAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1yYWRpby1idXR0b24tdW5jaGVja2VkLWJhY2tncm91bmQtY29sb3IsIHRyYW5zcGFyZW50KTsKICAgIHRyYW5zaXRpb246IGJvcmRlci1jb2xvciAwLjI4czsKICB9CgogICNvblJhZGlvIHsKICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXJhZGlvLWJ1dHRvbi1jaGVja2VkLWNvbG9yLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CiAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGUoMCk7CiAgICB0cmFuc2Zvcm06IHNjYWxlKDApOwogICAgdHJhbnNpdGlvbjogLXdlYmtpdC10cmFuc2Zvcm0gZWFzZSAwLjI4czsKICAgIHRyYW5zaXRpb246IHRyYW5zZm9ybSBlYXNlIDAuMjhzOwogICAgd2lsbC1jaGFuZ2U6IHRyYW5zZm9ybTsKICB9CgogIDpob3N0KFtjaGVja2VkXSkgI29mZlJhZGlvIHsKICAgIGJvcmRlci1jb2xvcjogdmFyKC0tcGFwZXItcmFkaW8tYnV0dG9uLWNoZWNrZWQtY29sb3IsIHZhcigtLXByaW1hcnktY29sb3IpKTsKICB9CgogIDpob3N0KFtjaGVja2VkXSkgI29uUmFkaW8gewogICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlKDAuNSk7CiAgICB0cmFuc2Zvcm06IHNjYWxlKDAuNSk7CiAgfQoKICAjcmFkaW9MYWJlbCB7CiAgICBsaW5lLWhlaWdodDogbm9ybWFsOwogICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgdmVydGljYWwtYWxpZ246IG1pZGRsZTsKICAgIG1hcmdpbi1sZWZ0OiB2YXIoLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtc3BhY2luZywgMTBweCk7CiAgICB3aGl0ZS1zcGFjZTogbm9ybWFsOwogICAgY29sb3I6IHZhcigtLXBhcGVyLXJhZGlvLWJ1dHRvbi1sYWJlbC1jb2xvciwgdmFyKC0tcHJpbWFyeS10ZXh0LWNvbG9yKSk7CgogICAgQGFwcGx5IC0tcGFwZXItcmFkaW8tYnV0dG9uLWxhYmVsOwogIH0KCiAgOmhvc3QoW2NoZWNrZWRdKSAjcmFkaW9MYWJlbCB7CiAgICBAYXBwbHkgLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtY2hlY2tlZDsKICB9CgogICNyYWRpb0xhYmVsOmRpcihydGwpIHsKICAgIG1hcmdpbi1sZWZ0OiAwOwogICAgbWFyZ2luLXJpZ2h0OiB2YXIoLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtc3BhY2luZywgMTBweCk7CiAgfQoKICAjcmFkaW9MYWJlbFtoaWRkZW5dIHsKICAgIGRpc3BsYXk6IG5vbmU7CiAgfQoKICAvKiBkaXNhYmxlZCBzdGF0ZSAqLwoKICA6aG9zdChbZGlzYWJsZWRdKSAjb2ZmUmFkaW8gewogICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1wYXBlci1yYWRpby1idXR0b24tdW5jaGVja2VkLWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgIG9wYWNpdHk6IDAuNTsKICB9CgogIDpob3N0KFtkaXNhYmxlZF1bY2hlY2tlZF0pICNvblJhZGlvIHsKICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXJhZGlvLWJ1dHRvbi11bmNoZWNrZWQtY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwogICAgb3BhY2l0eTogMC41OwogIH0KCiAgOmhvc3QoW2Rpc2FibGVkXSkgI3JhZGlvTGFiZWwgewogICAgLyogc2xpZ2h0bHkgZGFya2VyIHRoYW4gdGhlIGJ1dHRvbiwgc28gdGhhdCBpdCdzIHJlYWRhYmxlICovCiAgICBvcGFjaXR5OiAwLjY1OwogIH0KPC9zdHlsZT4KCjxkaXYgaWQ9InJhZGlvQ29udGFpbmVyIj4KICA8ZGl2IGlkPSJvZmZSYWRpbyI+PC9kaXY+CiAgPGRpdiBpZD0ib25SYWRpbyI+PC9kaXY+CjwvZGl2PgoKPGRpdiBpZD0icmFkaW9MYWJlbCI+PHNsb3Q+PC9zbG90PjwvZGl2PmA7CiAgICB0ZW1wbGF0ZSRkLnNldEF0dHJpYnV0ZSgnc3RyaXAtd2hpdGVzcGFjZScsICcnKTsKCiAgICAvKioKICAgIE1hdGVyaWFsIGRlc2lnbjogW1JhZGlvIGJ1dHRvbl0oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3NlbGVjdGlvbi1jb250cm9scy5odG1sI3NlbGVjdGlvbi1jb250cm9scy1yYWRpby1idXR0b24pCgogICAgYHBhcGVyLXJhZGlvLWJ1dHRvbmAgaXMgYSBidXR0b24gdGhhdCBjYW4gYmUgZWl0aGVyIGNoZWNrZWQgb3IgdW5jaGVja2VkLiBUaGUKICAgIHVzZXIgY2FuIHRhcCB0aGUgcmFkaW8gYnV0dG9uIHRvIGNoZWNrIG9yIHVuY2hlY2sgaXQuCgogICAgVXNlIGEgYDxwYXBlci1yYWRpby1ncm91cD5gIHRvIGdyb3VwIGEgc2V0IG9mIHJhZGlvIGJ1dHRvbnMuIFdoZW4gcmFkaW8gYnV0dG9ucwogICAgYXJlIGluc2lkZSBhIHJhZGlvIGdyb3VwLCBleGFjdGx5IG9uZSByYWRpbyBidXR0b24gaW4gdGhlIGdyb3VwIGNhbiBiZSBjaGVja2VkCiAgICBhdCBhbnkgdGltZS4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uPjwvcGFwZXItcmFkaW8tYnV0dG9uPgogICAgICAgIDxwYXBlci1yYWRpby1idXR0b24+SXRlbSBsYWJlbDwvcGFwZXItcmFkaW8tYnV0dG9uPgoKICAgICMjIyBTdHlsaW5nCgogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItcmFkaW8tYnV0dG9uLXVuY2hlY2tlZC1iYWNrZ3JvdW5kLWNvbG9yYCB8IFJhZGlvIGJ1dHRvbiBiYWNrZ3JvdW5kIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIG5vdCBjaGVja2VkIHwgYHRyYW5zcGFyZW50YAogICAgYC0tcGFwZXItcmFkaW8tYnV0dG9uLXVuY2hlY2tlZC1jb2xvcmAgfCBSYWRpbyBidXR0b24gY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tdW5jaGVja2VkLWluay1jb2xvcmAgfCBTZWxlY3RlZC9mb2N1cyByaXBwbGUgY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tY2hlY2tlZC1jb2xvcmAgfCBSYWRpbyBidXR0b24gY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgY2hlY2tlZCB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tY2hlY2tlZC1pbmstY29sb3JgIHwgU2VsZWN0ZWQvZm9jdXMgcmlwcGxlIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGNoZWNrZWQgfCBgLS1wcmltYXJ5LWNvbG9yYAogICAgYC0tcGFwZXItcmFkaW8tYnV0dG9uLXNpemVgIHwgU2l6ZSBvZiB0aGUgcmFkaW8gYnV0dG9uIHwgYDE2cHhgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24taW5rLXNpemVgIHwgU2l6ZSBvZiB0aGUgcmlwcGxlIHwgYDQ4cHhgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtY29sb3JgIHwgTGFiZWwgY29sb3IgfCBgLS1wcmltYXJ5LXRleHQtY29sb3JgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtc3BhY2luZ2AgfCBTcGFjaW5nIGJldHdlZW4gdGhlIGxhYmVsIGFuZCB0aGUgYnV0dG9uIHwgYDEwcHhgCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tcmFkaW8tY29udGFpbmVyYCB8IEEgbWl4aW4gYXBwbGllZCB0byB0aGUgaW50ZXJuYWwgcmFkaW8gY29udGFpbmVyIHwgYHt9YAogICAgYC0tcGFwZXItcmFkaW8tYnV0dG9uLWxhYmVsYCB8IEEgbWl4aW4gYXBwbGllZCB0byB0aGUgaW50ZXJuYWwgbGFiZWwgfCBge31gCiAgICBgLS1wYXBlci1yYWRpby1idXR0b24tbGFiZWwtY2hlY2tlZGAgfCBBIG1peGluIGFwcGxpZWQgdG8gdGhlIGludGVybmFsIGxhYmVsIHdoZW4gdGhlIHJhZGlvIGJ1dHRvbiBpcyBjaGVja2VkIHwgYHt9YAoKICAgIFRoaXMgZWxlbWVudCBhcHBsaWVzIHRoZSBtaXhpbiBgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlYCBidXQgZG9lcyBub3QgaW1wb3J0CiAgICBgcGFwZXItc3R5bGVzL3R5cG9ncmFwaHkuaHRtbGAuIEluIG9yZGVyIHRvIGFwcGx5IHRoZSBgUm9ib3RvYCBmb250IHRvIHRoaXMKICAgIGVsZW1lbnQsIG1ha2Ugc3VyZSB5b3UndmUgaW1wb3J0ZWQgYHBhcGVyLXN0eWxlcy90eXBvZ3JhcGh5Lmh0bWxgLgoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItcmFkaW8tYnV0dG9uCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiB0ZW1wbGF0ZSRkLAoKICAgICAgaXM6ICdwYXBlci1yYWRpby1idXR0b24nLAoKICAgICAgYmVoYXZpb3JzOiBbUGFwZXJDaGVja2VkRWxlbWVudEJlaGF2aW9yXSwKCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ3JhZGlvJywgJ2FyaWEtY2hlY2tlZCc6IGZhbHNlLCB0YWJpbmRleDogMH0sCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogRmlyZWQgd2hlbiB0aGUgY2hlY2tlZCBzdGF0ZSBjaGFuZ2VzIGR1ZSB0byB1c2VyIGludGVyYWN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQGV2ZW50IGNoYW5nZQogICAgICAgICAqLwoKICAgICAgICAvKioKICAgICAgICAgKiBGaXJlZCB3aGVuIHRoZSBjaGVja2VkIHN0YXRlIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAZXZlbnQgaXJvbi1jaGFuZ2UKICAgICAgICAgKi8KCiAgICAgICAgYXJpYUFjdGl2ZUF0dHJpYnV0ZToge3R5cGU6IFN0cmluZywgdmFsdWU6ICdhcmlhLWNoZWNrZWQnfQogICAgICB9LAoKICAgICAgcmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3JpcHBsZUNvbnRhaW5lciA9IHRoaXMuJC5yYWRpb0NvbnRhaW5lcjsKICAgICAgfSwKCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICAvLyBXYWl0IHVudGlsIHN0eWxlcyBoYXZlIHJlc29sdmVkIHRvIGNoZWNrIGZvciB0aGUgZGVmYXVsdCBzZW50aW5lbC4KICAgICAgICAvLyBTZWUgcG9seW1lciM0MDA5IGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgYWZ0ZXJOZXh0UmVuZGVyKHRoaXMsIGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIGlua1NpemUgPQogICAgICAgICAgICAgIHRoaXMuZ2V0Q29tcHV0ZWRTdHlsZVZhbHVlKCctLWNhbGN1bGF0ZWQtcGFwZXItcmFkaW8tYnV0dG9uLWluay1zaXplJykKICAgICAgICAgICAgICAgICAgLnRyaW0oKTsKICAgICAgICAgIC8vIElmIHVuc2V0LCBjb21wdXRlIGFuZCBzZXQgdGhlIGRlZmF1bHQgYC0tcGFwZXItcmFkaW8tYnV0dG9uLWluay1zaXplYC4KICAgICAgICAgIGlmIChpbmtTaXplID09PSAnLTFweCcpIHsKICAgICAgICAgICAgdmFyIHNpemUgPSBwYXJzZUZsb2F0KAogICAgICAgICAgICAgICAgdGhpcy5nZXRDb21wdXRlZFN0eWxlVmFsdWUoJy0tY2FsY3VsYXRlZC1wYXBlci1yYWRpby1idXR0b24tc2l6ZScpCiAgICAgICAgICAgICAgICAgICAgLnRyaW0oKSk7CiAgICAgICAgICAgIHZhciBkZWZhdWx0SW5rU2l6ZSA9IE1hdGguZmxvb3IoMyAqIHNpemUpOwoKICAgICAgICAgICAgLy8gVGhlIGJ1dHRvbiBhbmQgcmlwcGxlIG5lZWQgdG8gaGF2ZSB0aGUgc2FtZSBwYXJpdHkgc28gdGhhdCB0aGVpcgogICAgICAgICAgICAvLyBjZW50ZXJzIGFsaWduLgogICAgICAgICAgICBpZiAoZGVmYXVsdElua1NpemUgJSAyICE9PSBzaXplICUgMikgewogICAgICAgICAgICAgIGRlZmF1bHRJbmtTaXplKys7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIHRoaXMudXBkYXRlU3R5bGVzKHsKICAgICAgICAgICAgICAnLS1wYXBlci1yYWRpby1idXR0b24taW5rLXNpemUnOiBkZWZhdWx0SW5rU2l6ZSArICdweCcsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9LAogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICAgKiBgSXJvbk1lbnViYXJCZWhhdmlvcmAgaW1wbGVtZW50cyBhY2Nlc3NpYmxlIG1lbnViYXIgYmVoYXZpb3IuCiAgICAgKgogICAgICogQHBvbHltZXJCZWhhdmlvciBJcm9uTWVudWJhckJlaGF2aW9yCiAgICAgKi8KICAgIGNvbnN0IElyb25NZW51YmFyQmVoYXZpb3JJbXBsID0gewoKICAgICAgaG9zdEF0dHJpYnV0ZXM6IHsncm9sZSc6ICdtZW51YmFyJ30sCgogICAgICAvKioKICAgICAgICogQHR5cGUgeyFPYmplY3R9CiAgICAgICAqLwogICAgICBrZXlCaW5kaW5nczogeydsZWZ0JzogJ19vbkxlZnRLZXknLCAncmlnaHQnOiAnX29uUmlnaHRLZXknfSwKCiAgICAgIF9vblVwS2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuZm9jdXNlZEl0ZW0uY2xpY2soKTsKICAgICAgICBldmVudC5kZXRhaWwua2V5Ym9hcmRFdmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICB9LAoKICAgICAgX29uRG93bktleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLmZvY3VzZWRJdGVtLmNsaWNrKCk7CiAgICAgICAgZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgfSwKCiAgICAgIGdldCBfaXNSVEwoKSB7CiAgICAgICAgcmV0dXJuIHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKHRoaXMpWydkaXJlY3Rpb24nXSA9PT0gJ3J0bCc7CiAgICAgIH0sCgogICAgICBfb25MZWZ0S2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICh0aGlzLl9pc1JUTCkgewogICAgICAgICAgdGhpcy5fZm9jdXNOZXh0KCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX2ZvY3VzUHJldmlvdXMoKTsKICAgICAgICB9CiAgICAgICAgZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgfSwKCiAgICAgIF9vblJpZ2h0S2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICh0aGlzLl9pc1JUTCkgewogICAgICAgICAgdGhpcy5fZm9jdXNQcmV2aW91cygpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl9mb2N1c05leHQoKTsKICAgICAgICB9CiAgICAgICAgZXZlbnQuZGV0YWlsLmtleWJvYXJkRXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgfSwKCiAgICAgIF9vbktleWRvd246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMua2V5Ym9hcmRFdmVudE1hdGNoZXNLZXlzKGV2ZW50LCAndXAgZG93biBsZWZ0IHJpZ2h0IGVzYycpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBhbGwgb3RoZXIga2V5cyBmb2N1cyB0aGUgbWVudSBpdGVtIHN0YXJ0aW5nIHdpdGggdGhhdCBjaGFyYWN0ZXIKICAgICAgICB0aGlzLl9mb2N1c1dpdGhLZXlib2FyZEV2ZW50KGV2ZW50KTsKICAgICAgfQoKICAgIH07CgogICAgLyoqIEBwb2x5bWVyQmVoYXZpb3IgKi8KICAgIGNvbnN0IElyb25NZW51YmFyQmVoYXZpb3IgPSBbSXJvbk1lbnVCZWhhdmlvciwgSXJvbk1lbnViYXJCZWhhdmlvckltcGxdOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qKgogICAgTWF0ZXJpYWwgZGVzaWduOiBbUmFkaW8KICAgIGJ1dHRvbl0oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3NlbGVjdGlvbi1jb250cm9scy5odG1sI3NlbGVjdGlvbi1jb250cm9scy1yYWRpby1idXR0b24pCgogICAgYHBhcGVyLXJhZGlvLWdyb3VwYCBhbGxvd3MgdXNlciB0byBzZWxlY3QgYXQgbW9zdCBvbmUgcmFkaW8gYnV0dG9uIGZyb20gYSBzZXQuCiAgICBDaGVja2luZyBvbmUgcmFkaW8gYnV0dG9uIHRoYXQgYmVsb25ncyB0byBhIHJhZGlvIGdyb3VwIHVuY2hlY2tzIGFueQogICAgcHJldmlvdXNseSBjaGVja2VkIHJhZGlvIGJ1dHRvbiB3aXRoaW4gdGhlIHNhbWUgZ3JvdXAuIFVzZQogICAgYHNlbGVjdGVkYCB0byBnZXQgb3Igc2V0IHRoZSBzZWxlY3RlZCByYWRpbyBidXR0b24uCgogICAgVGhlIDxwYXBlci1yYWRpby1idXR0b25zPiBpbnNpZGUgdGhlIGdyb3VwIG11c3QgaGF2ZSB0aGUgYG5hbWVgIGF0dHJpYnV0ZQogICAgc2V0LgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1yYWRpby1ncm91cCBzZWxlY3RlZD0ic21hbGwiPgogICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbiBuYW1lPSJzbWFsbCI+U21hbGw8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24gbmFtZT0ibWVkaXVtIj5NZWRpdW08L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24gbmFtZT0ibGFyZ2UiPkxhcmdlPC9wYXBlci1yYWRpby1idXR0b24+CiAgICAgICAgPC9wYXBlci1yYWRpby1ncm91cD4KCiAgICBSYWRpby1idXR0b24tZ3JvdXBzIGNhbiBiZSBtYWRlIG9wdGlvbmFsLCBhbmQgYWxsb3cgemVybyBidXR0b25zIHRvIGJlIHNlbGVjdGVkOgoKICAgICAgICA8cGFwZXItcmFkaW8tZ3JvdXAgc2VsZWN0ZWQ9InNtYWxsIiBhbGxvdy1lbXB0eS1zZWxlY3Rpb24+CiAgICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uIG5hbWU9InNtYWxsIj5TbWFsbDwvcGFwZXItcmFkaW8tYnV0dG9uPgogICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbiBuYW1lPSJtZWRpdW0iPk1lZGl1bTwvcGFwZXItcmFkaW8tYnV0dG9uPgogICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbiBuYW1lPSJsYXJnZSI+TGFyZ2U8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICA8L3BhcGVyLXJhZGlvLWdyb3VwPgoKICAgIFNlZSA8YSBocmVmPSJwYXBlci1yYWRpby1idXR0b24iPnBhcGVyLXJhZGlvLWJ1dHRvbjwvYT4gZm9yIG1vcmUKICAgIGluZm9ybWF0aW9uIGFib3V0IGBwYXBlci1yYWRpby1idXR0b25gLgoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1yYWRpby1ncm91cC1pdGVtLXBhZGRpbmdgIHwgVGhlIHBhZGRpbmcgb2YgdGhlIGl0ZW0gfCBgMTJweGAKCiAgICBAZ3JvdXAgUGFwZXIgRWxlbWVudHMKICAgIEBlbGVtZW50IHBhcGVyLXJhZGlvLWdyb3VwCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICB9CgogICAgICA6aG9zdCA6OnNsb3R0ZWQoKikgewogICAgICAgIHBhZGRpbmc6IHZhcigtLXBhcGVyLXJhZGlvLWdyb3VwLWl0ZW0tcGFkZGluZywgMTJweCk7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgLAoKICAgICAgaXM6ICdwYXBlci1yYWRpby1ncm91cCcsCiAgICAgIGJlaGF2aW9yczogW0lyb25NZW51YmFyQmVoYXZpb3JdLAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7CiAgICAgICAgcm9sZTogJ3JhZGlvZ3JvdXAnLAogICAgICB9LAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIEZpcmVkIHdoZW4gdGhlIHJhZGlvIGdyb3VwIHNlbGVjdGlvbiBjaGFuZ2VzLgogICAgICAgICAqCiAgICAgICAgICogQGV2ZW50IHBhcGVyLXJhZGlvLWdyb3VwLWNoYW5nZWQKICAgICAgICAgKi8KCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVuIGZyb20gUG9seW1lci5Jcm9uU2VsZWN0YWJsZUJlaGF2aW9yCiAgICAgICAgICovCiAgICAgICAgYXR0ckZvclNlbGVjdGVkOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ25hbWUnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogT3ZlcnJpZGVuIGZyb20gUG9seW1lci5Jcm9uU2VsZWN0YWJsZUJlaGF2aW9yCiAgICAgICAgICovCiAgICAgICAgc2VsZWN0ZWRBdHRyaWJ1dGU6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnY2hlY2tlZCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZW4gZnJvbSBQb2x5bWVyLklyb25TZWxlY3RhYmxlQmVoYXZpb3IKICAgICAgICAgKi8KICAgICAgICBzZWxlY3RhYmxlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ3BhcGVyLXJhZGlvLWJ1dHRvbid9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCByYWRpby1idXR0b25zIGNhbiBiZSBkZXNlbGVjdGVkCiAgICAgICAgICovCiAgICAgICAgYWxsb3dFbXB0eVNlbGVjdGlvbjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3RzIHRoZSBnaXZlbiB2YWx1ZS4KICAgICAgICovCiAgICAgIHNlbGVjdDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICB2YXIgbmV3SXRlbSA9IHRoaXMuX3ZhbHVlVG9JdGVtKHZhbHVlKTsKICAgICAgICBpZiAobmV3SXRlbSAmJiBuZXdJdGVtLmhhc0F0dHJpYnV0ZSgnZGlzYWJsZWQnKSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuc2VsZWN0ZWQpIHsKICAgICAgICAgIHZhciBvbGRJdGVtID0gdGhpcy5fdmFsdWVUb0l0ZW0odGhpcy5zZWxlY3RlZCk7CgogICAgICAgICAgaWYgKHRoaXMuc2VsZWN0ZWQgPT0gdmFsdWUpIHsKICAgICAgICAgICAgLy8gSWYgZGVzZWxlY3RpbmcgaXMgYWxsb3dlZCB3ZSdsbCBoYXZlIHRvIGFwcGx5IGFuIGVtcHR5IHNlbGVjdGlvbi4KICAgICAgICAgICAgLy8gT3RoZXJ3aXNlLCB3ZSBzaG91bGQgZm9yY2UgdGhlIHNlbGVjdGlvbiB0byBzdGF5IGFuZCBtYWtlIHRoaXMKICAgICAgICAgICAgLy8gYWN0aW9uIGEgbm8tb3AuCiAgICAgICAgICAgIGlmICh0aGlzLmFsbG93RW1wdHlTZWxlY3Rpb24pIHsKICAgICAgICAgICAgICB2YWx1ZSA9ICcnOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGlmIChvbGRJdGVtKQogICAgICAgICAgICAgICAgb2xkSXRlbS5jaGVja2VkID0gdHJ1ZTsKICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICBpZiAob2xkSXRlbSkKICAgICAgICAgICAgb2xkSXRlbS5jaGVja2VkID0gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICBJcm9uU2VsZWN0YWJsZUJlaGF2aW9yLnNlbGVjdC5hcHBseSh0aGlzLCBbdmFsdWVdKTsKICAgICAgICB0aGlzLmZpcmUoJ3BhcGVyLXJhZGlvLWdyb3VwLWNoYW5nZWQnKTsKICAgICAgfSwKCiAgICAgIF9hY3RpdmF0ZUZvY3VzZWRJdGVtOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9pdGVtQWN0aXZhdGUodGhpcy5fdmFsdWVGb3JJdGVtKHRoaXMuZm9jdXNlZEl0ZW0pLCB0aGlzLmZvY3VzZWRJdGVtKTsKICAgICAgfSwKCiAgICAgIF9vblVwS2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuX2ZvY3VzUHJldmlvdXMoKTsKICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgIHRoaXMuX2FjdGl2YXRlRm9jdXNlZEl0ZW0oKTsKICAgICAgfSwKCiAgICAgIF9vbkRvd25LZXk6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdGhpcy5fZm9jdXNOZXh0KCk7CiAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgICB0aGlzLl9hY3RpdmF0ZUZvY3VzZWRJdGVtKCk7CiAgICAgIH0sCgogICAgICBfb25MZWZ0S2V5OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIElyb25NZW51YmFyQmVoYXZpb3JJbXBsLl9vbkxlZnRLZXkuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLl9hY3RpdmF0ZUZvY3VzZWRJdGVtKCk7CiAgICAgIH0sCgogICAgICBfb25SaWdodEtleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBJcm9uTWVudWJhckJlaGF2aW9ySW1wbC5fb25SaWdodEtleS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHRoaXMuX2FjdGl2YXRlRm9jdXNlZEl0ZW0oKTsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgdGVtcGxhdGUkZSA9IGh0bWxgCiAgPHN0eWxlPgogICAgOmhvc3QgewogICAgICBAYXBwbHkgLS1sYXlvdXQ7CiAgICAgIEBhcHBseSAtLWxheW91dC1qdXN0aWZpZWQ7CiAgICAgIEBhcHBseSAtLWxheW91dC1jZW50ZXI7CiAgICAgIHdpZHRoOiAyMDBweDsKICAgICAgY3Vyc29yOiBkZWZhdWx0OwogICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgIHVzZXItc2VsZWN0OiBub25lOwogICAgICAtd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3I6IHJnYmEoMCwgMCwgMCwgMCk7CiAgICAgIC0tcGFwZXItcHJvZ3Jlc3MtYWN0aXZlLWNvbG9yOiB2YXIoLS1wYXBlci1zbGlkZXItYWN0aXZlLWNvbG9yLCB2YXIoLS1nb29nbGUtYmx1ZS03MDApKTsKICAgICAgLS1wYXBlci1wcm9ncmVzcy1zZWNvbmRhcnktY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1zZWNvbmRhcnktY29sb3IsIHZhcigtLWdvb2dsZS1ibHVlLTMwMCkpOwogICAgICAtLXBhcGVyLXByb2dyZXNzLWRpc2FibGVkLWFjdGl2ZS1jb2xvcjogdmFyKC0tcGFwZXItc2xpZGVyLWRpc2FibGVkLWFjdGl2ZS1jb2xvciwgdmFyKC0tcGFwZXItZ3JleS00MDApKTsKICAgICAgLS1wYXBlci1wcm9ncmVzcy1kaXNhYmxlZC1zZWNvbmRhcnktY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1kaXNhYmxlZC1zZWNvbmRhcnktY29sb3IsIHZhcigtLXBhcGVyLWdyZXktNDAwKSk7CiAgICAgIC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0OiB2YXIoLS1wYXBlci1zbGlkZXItaGVpZ2h0LCAycHgpOwogICAgfQoKICAgIC8qIGZvY3VzIHNob3dzIHRoZSByaXBwbGUgKi8KICAgIDpob3N0KDpmb2N1cykgewogICAgICBvdXRsaW5lOiBub25lOwogICAgfQoKICAgIC8qKgogICAgICAqIE5PVEUoa2VhbnVsZWUpOiBUaG91Z2ggOmhvc3QtY29udGV4dCBpcyBub3QgdW5pdmVyc2FsbHkgc3VwcG9ydGVkLCBzb21lIHBhZ2VzCiAgICAgICogc3RpbGwgcmVseSBvbiBwYXBlci1zbGlkZXIgYmVpbmcgZmxpcHBlZCB3aGVuIGRpcj0icnRsIiBpcyBzZXQgb24gYm9keS4gRm9yIGZ1bGwKICAgICAgKiBjb21wYXRpYmlsaXR5LCBkaXI9InJ0bCIgbXVzdCBiZSBleHBsaWNpdGx5IHNldCBvbiBwYXBlci1zbGlkZXIuCiAgICAgICovCiAgICA6ZGlyKHJ0bCkgI3NsaWRlckNvbnRhaW5lciB7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZVgoLTEpOwogICAgICB0cmFuc2Zvcm06IHNjYWxlWCgtMSk7CiAgICB9CgogICAgLyoqCiAgICAgICogTk9URShrZWFudWxlZSk6IFRoaXMgaXMgc2VwYXJhdGUgZnJvbSB0aGUgcnVsZSBhYm92ZSBiZWNhdXNlIDpob3N0LWNvbnRleHQgbWF5CiAgICAgICogbm90IGJlIHJlY29nbml6ZWQuCiAgICAgICovCiAgICA6aG9zdChbZGlyPSJydGwiXSkgI3NsaWRlckNvbnRhaW5lciB7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZVgoLTEpOwogICAgICB0cmFuc2Zvcm06IHNjYWxlWCgtMSk7CiAgICB9CgogICAgLyoqCiAgICAgICogTk9URShrZWFudWxlZSk6IE5lZWRlZCB0byBvdmVycmlkZSB0aGUgOmhvc3QtY29udGV4dCBydWxlICh3aGVyZSBzdXBwb3J0ZWQpCiAgICAgICogdG8gc3VwcG9ydCBMVFIgc2xpZGVycyBpbiBSVEwgcGFnZXMuCiAgICAgICovCiAgICA6aG9zdChbZGlyPSJsdHIiXSkgI3NsaWRlckNvbnRhaW5lciB7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZVgoMSk7CiAgICAgIHRyYW5zZm9ybTogc2NhbGVYKDEpOwogICAgfQoKICAgICNzbGlkZXJDb250YWluZXIgewogICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgICBoZWlnaHQ6IGNhbGMoMzBweCArIHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItc2xpZGVyLWhlaWdodCkpOwogICAgICBtYXJnaW4tbGVmdDogY2FsYygxNXB4ICsgdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0KS8yKTsKICAgICAgbWFyZ2luLXJpZ2h0OiBjYWxjKDE1cHggKyB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLXNsaWRlci1oZWlnaHQpLzIpOwogICAgfQoKICAgICNzbGlkZXJDb250YWluZXI6Zm9jdXMgewogICAgICBvdXRsaW5lOiAwOwogICAgfQoKICAgICNzbGlkZXJDb250YWluZXIuZWRpdGFibGUgewogICAgICBtYXJnaW4tdG9wOiAxMnB4OwogICAgICBtYXJnaW4tYm90dG9tOiAxMnB4OwogICAgfQoKICAgIC5iYXItY29udGFpbmVyIHsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICB0b3A6IDA7CiAgICAgIGJvdHRvbTogMDsKICAgICAgbGVmdDogMDsKICAgICAgcmlnaHQ6IDA7CiAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICB9CgogICAgLnJpbmcgPiAuYmFyLWNvbnRhaW5lciB7CiAgICAgIGxlZnQ6IGNhbGMoNXB4ICsgdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0KS8yKTsKICAgICAgdHJhbnNpdGlvbjogbGVmdCAwLjE4cyBlYXNlOwogICAgfQoKICAgIC5yaW5nLmV4cGFuZC5kcmFnZ2luZyA+IC5iYXItY29udGFpbmVyIHsKICAgICAgdHJhbnNpdGlvbjogbm9uZTsKICAgIH0KCiAgICAucmluZy5leHBhbmQ6bm90KC5waW4pID4gLmJhci1jb250YWluZXIgewogICAgICBsZWZ0OiBjYWxjKDhweCArIHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItc2xpZGVyLWhlaWdodCkvMik7CiAgICB9CgogICAgI3NsaWRlckJhciB7CiAgICAgIHBhZGRpbmc6IDE1cHggMDsKICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1iYXItY29sb3IsIHRyYW5zcGFyZW50KTsKICAgICAgLS1wYXBlci1wcm9ncmVzcy1jb250YWluZXItY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1jb250YWluZXItY29sb3IsIHZhcigtLXBhcGVyLWdyZXktNDAwKSk7CiAgICAgIC0tcGFwZXItcHJvZ3Jlc3MtaGVpZ2h0OiB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLXNsaWRlci1oZWlnaHQpOwogICAgfQoKICAgIC5zbGlkZXItbWFya2VycyB7CiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgLyogc2xpZGVyLWtub2IgaXMgMzBweCArIHRoZSBzbGlkZXItaGVpZ2h0IHNvIHRoYXQgdGhlIG1hcmtlcnMgc2hvdWxkIHN0YXJ0IGF0IGEgb2Zmc2V0IG9mIDE1cHgqLwogICAgICB0b3A6IDE1cHg7CiAgICAgIGhlaWdodDogdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0KTsKICAgICAgbGVmdDogMDsKICAgICAgcmlnaHQ6IC0xcHg7CiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgIH0KCiAgICAuc2xpZGVyLW1hcmtlciB7CiAgICAgIEBhcHBseSAtLWxheW91dC1mbGV4OwogICAgfQogICAgLnNsaWRlci1tYXJrZXJzOjphZnRlciwKICAgIC5zbGlkZXItbWFya2VyOjphZnRlciB7CiAgICAgIGNvbnRlbnQ6ICIiOwogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgbWFyZ2luLWxlZnQ6IC0xcHg7CiAgICAgIHdpZHRoOiAycHg7CiAgICAgIGhlaWdodDogdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0KTsKICAgICAgYm9yZGVyLXJhZGl1czogNTAlOwogICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1zbGlkZXItbWFya2Vycy1jb2xvciwgIzAwMCk7CiAgICB9CgogICAgLnNsaWRlci1rbm9iIHsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICBsZWZ0OiAwOwogICAgICB0b3A6IDA7CiAgICAgIG1hcmdpbi1sZWZ0OiBjYWxjKC0xNXB4IC0gdmFyKC0tY2FsY3VsYXRlZC1wYXBlci1zbGlkZXItaGVpZ2h0KS8yKTsKICAgICAgd2lkdGg6IGNhbGMoMzBweCArIHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItc2xpZGVyLWhlaWdodCkpOwogICAgICBoZWlnaHQ6IGNhbGMoMzBweCArIHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItc2xpZGVyLWhlaWdodCkpOwogICAgfQoKICAgIC50cmFuc2l0aW5nID4gLnNsaWRlci1rbm9iIHsKICAgICAgdHJhbnNpdGlvbjogbGVmdCAwLjA4cyBlYXNlOwogICAgfQoKICAgIC5zbGlkZXIta25vYjpmb2N1cyB7CiAgICAgIG91dGxpbmU6IG5vbmU7CiAgICB9CgogICAgLnNsaWRlci1rbm9iLmRyYWdnaW5nIHsKICAgICAgdHJhbnNpdGlvbjogbm9uZTsKICAgIH0KCiAgICAuc25hcHMgPiAuc2xpZGVyLWtub2IuZHJhZ2dpbmcgewogICAgICB0cmFuc2l0aW9uOiAtd2Via2l0LXRyYW5zZm9ybSAwLjA4cyBlYXNlOwogICAgICB0cmFuc2l0aW9uOiB0cmFuc2Zvcm0gMC4wOHMgZWFzZTsKICAgIH0KCiAgICAuc2xpZGVyLWtub2ItaW5uZXIgewogICAgICBtYXJnaW46IDEwcHg7CiAgICAgIHdpZHRoOiBjYWxjKDEwMCUgLSAyMHB4KTsKICAgICAgaGVpZ2h0OiBjYWxjKDEwMCUgLSAyMHB4KTsKICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItc2xpZGVyLWtub2ItY29sb3IsIHZhcigtLWdvb2dsZS1ibHVlLTcwMCkpOwogICAgICBib3JkZXI6IDJweCBzb2xpZCB2YXIoLS1wYXBlci1zbGlkZXIta25vYi1jb2xvciwgdmFyKC0tZ29vZ2xlLWJsdWUtNzAwKSk7CiAgICAgIGJvcmRlci1yYWRpdXM6IDUwJTsKCiAgICAgIC1tb3otYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKCiAgICAgIHRyYW5zaXRpb24tcHJvcGVydHk6IC13ZWJraXQtdHJhbnNmb3JtLCBiYWNrZ3JvdW5kLWNvbG9yLCBib3JkZXI7CiAgICAgIHRyYW5zaXRpb24tcHJvcGVydHk6IHRyYW5zZm9ybSwgYmFja2dyb3VuZC1jb2xvciwgYm9yZGVyOwogICAgICB0cmFuc2l0aW9uLWR1cmF0aW9uOiAwLjE4czsKICAgICAgdHJhbnNpdGlvbi10aW1pbmctZnVuY3Rpb246IGVhc2U7CiAgICB9CgogICAgLmV4cGFuZDpub3QoLnBpbikgPiAuc2xpZGVyLWtub2IgPiAuc2xpZGVyLWtub2ItaW5uZXIgewogICAgICAtd2Via2l0LXRyYW5zZm9ybTogc2NhbGUoMS41KTsKICAgICAgdHJhbnNmb3JtOiBzY2FsZSgxLjUpOwogICAgfQoKICAgIC5yaW5nID4gLnNsaWRlci1rbm9iID4gLnNsaWRlci1rbm9iLWlubmVyIHsKICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtY29sb3IsIHRyYW5zcGFyZW50KTsKICAgICAgYm9yZGVyOiAycHggc29saWQgdmFyKC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtYm9yZGVyLWNvbG9yLCB2YXIoLS1wYXBlci1ncmV5LTQwMCkpOwogICAgfQoKICAgIC5zbGlkZXIta25vYi1pbm5lcjo6YmVmb3JlIHsKICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItc2xpZGVyLXBpbi1jb2xvciwgdmFyKC0tZ29vZ2xlLWJsdWUtNzAwKSk7CiAgICB9CgogICAgLnBpbiA+IC5zbGlkZXIta25vYiA+IC5zbGlkZXIta25vYi1pbm5lcjo6YmVmb3JlIHsKICAgICAgY29udGVudDogIiI7CiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgdG9wOiAwOwogICAgICBsZWZ0OiA1MCU7CiAgICAgIG1hcmdpbi1sZWZ0OiAtMTNweDsKICAgICAgd2lkdGg6IDI2cHg7CiAgICAgIGhlaWdodDogMjZweDsKICAgICAgYm9yZGVyLXJhZGl1czogNTAlIDUwJSA1MCUgMDsKCiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiByb3RhdGUoLTQ1ZGVnKSBzY2FsZSgwKSB0cmFuc2xhdGUoMCk7CiAgICAgIHRyYW5zZm9ybTogcm90YXRlKC00NWRlZykgc2NhbGUoMCkgdHJhbnNsYXRlKDApOwogICAgfQoKICAgIC5zbGlkZXIta25vYi1pbm5lcjo6YmVmb3JlLAogICAgLnNsaWRlci1rbm9iLWlubmVyOjphZnRlciB7CiAgICAgIHRyYW5zaXRpb246IC13ZWJraXQtdHJhbnNmb3JtIC4xOHMgZWFzZSwgYmFja2dyb3VuZC1jb2xvciAuMThzIGVhc2U7CiAgICAgIHRyYW5zaXRpb246IHRyYW5zZm9ybSAuMThzIGVhc2UsIGJhY2tncm91bmQtY29sb3IgLjE4cyBlYXNlOwogICAgfQoKICAgIC5waW4ucmluZyA+IC5zbGlkZXIta25vYiA+IC5zbGlkZXIta25vYi1pbm5lcjo6YmVmb3JlIHsKICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItc2xpZGVyLXBpbi1zdGFydC1jb2xvciwgdmFyKC0tcGFwZXItZ3JleS00MDApKTsKICAgIH0KCiAgICAucGluLmV4cGFuZCA+IC5zbGlkZXIta25vYiA+IC5zbGlkZXIta25vYi1pbm5lcjo6YmVmb3JlIHsKICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgtNDVkZWcpIHNjYWxlKDEpIHRyYW5zbGF0ZSgxN3B4LCAtMTdweCk7CiAgICAgIHRyYW5zZm9ybTogcm90YXRlKC00NWRlZykgc2NhbGUoMSkgdHJhbnNsYXRlKDE3cHgsIC0xN3B4KTsKICAgIH0KCiAgICAucGluID4gLnNsaWRlci1rbm9iID4gLnNsaWRlci1rbm9iLWlubmVyOjphZnRlciB7CiAgICAgIGNvbnRlbnQ6IGF0dHIodmFsdWUpOwogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgIHRvcDogMDsKICAgICAgbGVmdDogNTAlOwogICAgICBtYXJnaW4tbGVmdDogLTE2cHg7CiAgICAgIHdpZHRoOiAzMnB4OwogICAgICBoZWlnaHQ6IDI2cHg7CiAgICAgIHRleHQtYWxpZ246IGNlbnRlcjsKICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1mb250LWNvbG9yLCAjZmZmKTsKICAgICAgZm9udC1zaXplOiAxMHB4OwoKICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlKDApIHRyYW5zbGF0ZSgwKTsKICAgICAgdHJhbnNmb3JtOiBzY2FsZSgwKSB0cmFuc2xhdGUoMCk7CiAgICB9CgogICAgLnBpbi5leHBhbmQgPiAuc2xpZGVyLWtub2IgPiAuc2xpZGVyLWtub2ItaW5uZXI6OmFmdGVyIHsKICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlKDEpIHRyYW5zbGF0ZSgwLCAtMTdweCk7CiAgICAgIHRyYW5zZm9ybTogc2NhbGUoMSkgdHJhbnNsYXRlKDAsIC0xN3B4KTsKICAgIH0KCiAgICAvKiBwYXBlci1pbnB1dCAqLwogICAgLnNsaWRlci1pbnB1dCB7CiAgICAgIHdpZHRoOiA1MHB4OwogICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dDogewogICAgICAgIHRleHQtYWxpZ246IGNlbnRlcjsKICAgICAgICBAYXBwbHkgLS1wYXBlci1zbGlkZXItaW5wdXQtY29udGFpbmVyLWlucHV0OwogICAgICB9OwogICAgICBAYXBwbHkgLS1wYXBlci1zbGlkZXItaW5wdXQ7CiAgICB9CgogICAgLyogZGlzYWJsZWQgc3RhdGUgKi8KICAgICNzbGlkZXJDb250YWluZXIuZGlzYWJsZWQgewogICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgIH0KCiAgICAuZGlzYWJsZWQgPiAuc2xpZGVyLWtub2IgPiAuc2xpZGVyLWtub2ItaW5uZXIgewogICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1zbGlkZXItZGlzYWJsZWQta25vYi1jb2xvciwgdmFyKC0tcGFwZXItZ3JleS00MDApKTsKICAgICAgYm9yZGVyOiAycHggc29saWQgdmFyKC0tcGFwZXItc2xpZGVyLWRpc2FibGVkLWtub2ItY29sb3IsIHZhcigtLXBhcGVyLWdyZXktNDAwKSk7CiAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiBzY2FsZTNkKDAuNzUsIDAuNzUsIDEpOwogICAgICB0cmFuc2Zvcm06IHNjYWxlM2QoMC43NSwgMC43NSwgMSk7CiAgICB9CgogICAgLmRpc2FibGVkLnJpbmcgPiAuc2xpZGVyLWtub2IgPiAuc2xpZGVyLWtub2ItaW5uZXIgewogICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1zbGlkZXIta25vYi1zdGFydC1jb2xvciwgdHJhbnNwYXJlbnQpOwogICAgICBib3JkZXI6IDJweCBzb2xpZCB2YXIoLS1wYXBlci1zbGlkZXIta25vYi1zdGFydC1ib3JkZXItY29sb3IsIHZhcigtLXBhcGVyLWdyZXktNDAwKSk7CiAgICB9CgogICAgcGFwZXItcmlwcGxlIHsKICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXNsaWRlci1rbm9iLWNvbG9yLCB2YXIoLS1nb29nbGUtYmx1ZS03MDApKTsKICAgIH0KICA8L3N0eWxlPgoKICA8ZGl2IGlkPSJzbGlkZXJDb250YWluZXIiIGNsYXNzXCQ9IltbX2dldENsYXNzTmFtZXMoZGlzYWJsZWQsIHBpbiwgc25hcHMsIGltbWVkaWF0ZVZhbHVlLCBtaW4sIGV4cGFuZCwgZHJhZ2dpbmcsIHRyYW5zaXRpbmcsIGVkaXRhYmxlKV1dIj4KICAgIDxkaXYgY2xhc3M9ImJhci1jb250YWluZXIiPgogICAgICA8cGFwZXItcHJvZ3Jlc3MgZGlzYWJsZWRcJD0iW1tkaXNhYmxlZF1dIiBpZD0ic2xpZGVyQmFyIiBhcmlhLWhpZGRlbj0idHJ1ZSIgbWluPSJbW21pbl1dIiBtYXg9IltbbWF4XV0iIHN0ZXA9Iltbc3RlcF1dIiB2YWx1ZT0iW1tpbW1lZGlhdGVWYWx1ZV1dIiBzZWNvbmRhcnktcHJvZ3Jlc3M9Iltbc2Vjb25kYXJ5UHJvZ3Jlc3NdXSIgb24tZG93bj0iX2JhcmRvd24iIG9uLXVwPSJfcmVzZXRLbm9iIiBvbi10cmFjaz0iX2JhcnRyYWNrIiBvbi10YXA9Il9iYXJjbGljayI+CiAgICAgIDwvcGFwZXItcHJvZ3Jlc3M+CiAgICA8L2Rpdj4KCiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9Iltbc25hcHNdXSI+CiAgICAgIDxkaXYgY2xhc3M9InNsaWRlci1tYXJrZXJzIj4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW21hcmtlcnNdXSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJzbGlkZXItbWFya2VyIj48L2Rpdj4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICA8L2Rpdj4KICAgIDwvdGVtcGxhdGU+CgogICAgPGRpdiBpZD0ic2xpZGVyS25vYiIgY2xhc3M9InNsaWRlci1rbm9iIiBvbi1kb3duPSJfa25vYmRvd24iIG9uLXVwPSJfcmVzZXRLbm9iIiBvbi10cmFjaz0iX29uVHJhY2siIG9uLXRyYW5zaXRpb25lbmQ9Il9rbm9iVHJhbnNpdGlvbkVuZCI+CiAgICAgICAgPGRpdiBjbGFzcz0ic2xpZGVyLWtub2ItaW5uZXIiIHZhbHVlXCQ9IltbaW1tZWRpYXRlVmFsdWVdXSI+PC9kaXY+CiAgICA8L2Rpdj4KICA8L2Rpdj4KCiAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW2VkaXRhYmxlXV0iPgogICAgPHBhcGVyLWlucHV0IGlkPSJpbnB1dCIgdHlwZT0ibnVtYmVyIiBzdGVwPSJbW3N0ZXBdXSIgbWluPSJbW21pbl1dIiBtYXg9IltbbWF4XV0iIGNsYXNzPSJzbGlkZXItaW5wdXQiIGRpc2FibGVkXCQ9IltbZGlzYWJsZWRdXSIgdmFsdWU9IltbaW1tZWRpYXRlVmFsdWVdXSIgb24tY2hhbmdlPSJfY2hhbmdlVmFsdWUiIG9uLWtleWRvd249Il9pbnB1dEtleURvd24iIG5vLWxhYmVsLWZsb2F0PgogICAgPC9wYXBlci1pbnB1dD4KICA8L3RlbXBsYXRlPgpgOwogICAgdGVtcGxhdGUkZS5zZXRBdHRyaWJ1dGUoJ3N0cmlwLXdoaXRlc3BhY2UnLCAnJyk7CgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbU2xpZGVyc10oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3NsaWRlcnMuaHRtbCkKCiAgICBgcGFwZXItc2xpZGVyYCBhbGxvd3MgdXNlciB0byBzZWxlY3QgYSB2YWx1ZSBmcm9tIGEgcmFuZ2Ugb2YgdmFsdWVzIGJ5CiAgICBtb3ZpbmcgdGhlIHNsaWRlciB0aHVtYi4gIFRoZSBpbnRlcmFjdGl2ZSBuYXR1cmUgb2YgdGhlIHNsaWRlciBtYWtlcyBpdCBhCiAgICBncmVhdCBjaG9pY2UgZm9yIHNldHRpbmdzIHRoYXQgcmVmbGVjdCBpbnRlbnNpdHkgbGV2ZWxzLCBzdWNoIGFzIHZvbHVtZSwKICAgIGJyaWdodG5lc3MsIG9yIGNvbG9yIHNhdHVyYXRpb24uCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLXNsaWRlcj48L3BhcGVyLXNsaWRlcj4KCiAgICBVc2UgYG1pbmAgYW5kIGBtYXhgIHRvIHNwZWNpZnkgdGhlIHNsaWRlciByYW5nZS4gIERlZmF1bHQgaXMgMCB0byAxMDAuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLXNsaWRlciBtaW49IjEwIiBtYXg9IjIwMCIgdmFsdWU9IjExMCI+PC9wYXBlci1zbGlkZXI+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1zbGlkZXItY29udGFpbmVyLWNvbG9yYCB8IFRoZSBiYWNrZ3JvdW5kIGNvbG9yIG9mIHRoZSBiYXIgfCBgLS1wYXBlci1ncmV5LTQwMGAKICAgIGAtLXBhcGVyLXNsaWRlci1iYXItY29sb3JgIHwgVGhlIGJhY2tncm91bmQgY29sb3Igb2YgdGhlIHNsaWRlciB8IGB0cmFuc3BhcmVudGAKICAgIGAtLXBhcGVyLXNsaWRlci1hY3RpdmUtY29sb3JgIHwgVGhlIHByb2dyZXNzIGJhciBjb2xvciB8IGAtLWdvb2dsZS1ibHVlLTcwMGAKICAgIGAtLXBhcGVyLXNsaWRlci1zZWNvbmRhcnktY29sb3JgIHwgVGhlIHNlY29uZGFyeSBwcm9ncmVzcyBiYXIgY29sb3IgfCBgLS1nb29nbGUtYmx1ZS0zMDBgCiAgICBgLS1wYXBlci1zbGlkZXIta25vYi1jb2xvcmAgfCBUaGUga25vYiBjb2xvciB8IGAtLWdvb2dsZS1ibHVlLTcwMGAKICAgIGAtLXBhcGVyLXNsaWRlci1kaXNhYmxlZC1rbm9iLWNvbG9yYCB8IFRoZSBkaXNhYmxlZCBrbm9iIGNvbG9yIHwgYC0tcGFwZXItZ3JleS00MDBgCiAgICBgLS1wYXBlci1zbGlkZXItcGluLWNvbG9yYCB8IFRoZSBwaW4gY29sb3IgfCBgLS1nb29nbGUtYmx1ZS03MDBgCiAgICBgLS1wYXBlci1zbGlkZXItZm9udC1jb2xvcmAgfCBUaGUgcGluJ3MgdGV4dCBjb2xvciB8IGAjZmZmYAogICAgYC0tcGFwZXItc2xpZGVyLW1hcmtlcnMtY29sb3JgIHwgVGhlIHNuYXBzIG1hcmtlcnMgY29sb3IgfCBgIzAwMGAKICAgIGAtLXBhcGVyLXNsaWRlci1kaXNhYmxlZC1hY3RpdmUtY29sb3JgIHwgVGhlIGRpc2FibGVkIHByb2dyZXNzIGJhciBjb2xvciB8IGAtLXBhcGVyLWdyZXktNDAwYAogICAgYC0tcGFwZXItc2xpZGVyLWRpc2FibGVkLXNlY29uZGFyeS1jb2xvcmAgfCBUaGUgZGlzYWJsZWQgc2Vjb25kYXJ5IHByb2dyZXNzIGJhciBjb2xvciB8IGAtLXBhcGVyLWdyZXktNDAwYAogICAgYC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtY29sb3JgIHwgVGhlIGZpbGwgY29sb3Igb2YgdGhlIGtub2IgYXQgdGhlIGZhciBsZWZ0IHwgYHRyYW5zcGFyZW50YAogICAgYC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtYm9yZGVyLWNvbG9yYCB8IFRoZSBib3JkZXIgY29sb3Igb2YgdGhlIGtub2IgYXQgdGhlIGZhciBsZWZ0IHwgYC0tcGFwZXItZ3JleS00MDBgCiAgICBgLS1wYXBlci1zbGlkZXItcGluLXN0YXJ0LWNvbG9yYCB8IFRoZSBjb2xvciBvZiB0aGUgcGluIGF0IHRoZSBmYXIgbGVmdCB8IGAtLXBhcGVyLWdyZXktNDAwYAogICAgYC0tcGFwZXItc2xpZGVyLWhlaWdodGAgfCBIZWlnaHQgb2YgdGhlIHByb2dyZXNzIGJhciB8IGAycHhgCiAgICBgLS1wYXBlci1zbGlkZXItaW5wdXRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgaW5wdXQgaW4gZWRpdGFibGUgbW9kZSB8IGB7fWAKICAgIGAtLXBhcGVyLXNsaWRlci1pbnB1dC1jb250YWluZXItaW5wdXRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0IGluIGVkaXRhYmxlIG1vZGUgfCBge31gCgogICAgQGdyb3VwIFBhcGVyIEVsZW1lbnRzCiAgICBAZWxlbWVudCBwYXBlci1zbGlkZXIKICAgIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IHRlbXBsYXRlJGUsCgogICAgICBpczogJ3BhcGVyLXNsaWRlcicsCgogICAgICBiZWhhdmlvcnM6IFsKICAgICAgICBJcm9uQTExeUtleXNCZWhhdmlvciwKICAgICAgICBJcm9uRm9ybUVsZW1lbnRCZWhhdmlvciwKICAgICAgICBQYXBlcklua3lGb2N1c0JlaGF2aW9yLAogICAgICAgIElyb25SYW5nZUJlaGF2aW9yCiAgICAgIF0sCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgdmFsdWU6IHsKICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgIHZhbHVlOiAwLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHRoZSBzbGlkZXIgdGh1bWIgc25hcHMgdG8gdGljayBtYXJrcyBldmVubHkgc3BhY2VkIGJhc2VkCiAgICAgICAgICogb24gdGhlIGBzdGVwYCBwcm9wZXJ0eSB2YWx1ZS4KICAgICAgICAgKi8KICAgICAgICBzbmFwczogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCBhIHBpbiB3aXRoIG51bWVyaWMgdmFsdWUgbGFiZWwgaXMgc2hvd24gd2hlbiB0aGUgc2xpZGVyIHRodW1iCiAgICAgICAgICogaXMgcHJlc3NlZC4gVXNlIGZvciBzZXR0aW5ncyBmb3Igd2hpY2ggdXNlcnMgbmVlZCB0byBrbm93IHRoZSBleGFjdAogICAgICAgICAqIHZhbHVlIG9mIHRoZSBzZXR0aW5nLgogICAgICAgICAqLwogICAgICAgIHBpbjogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgbnVtYmVyIHRoYXQgcmVwcmVzZW50cyB0aGUgY3VycmVudCBzZWNvbmRhcnkgcHJvZ3Jlc3MuCiAgICAgICAgICovCiAgICAgICAgc2Vjb25kYXJ5UHJvZ3Jlc3M6IHsKICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgIHZhbHVlOiAwLAogICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgb2JzZXJ2ZXI6ICdfc2Vjb25kYXJ5UHJvZ3Jlc3NDaGFuZ2VkJywKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCBhbiBpbnB1dCBpcyBzaG93biBhbmQgdXNlciBjYW4gdXNlIGl0IHRvIHNldCB0aGUgc2xpZGVyIHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGVkaXRhYmxlOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBpbW1lZGlhdGUgdmFsdWUgb2YgdGhlIHNsaWRlci4gIFRoaXMgdmFsdWUgaXMgdXBkYXRlZCB3aGlsZSB0aGUgdXNlcgogICAgICAgICAqIGlzIGRyYWdnaW5nIHRoZSBzbGlkZXIuCiAgICAgICAgICovCiAgICAgICAgaW1tZWRpYXRlVmFsdWU6IHsKICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgIHZhbHVlOiAwLAogICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG1heGltdW0gbnVtYmVyIG9mIG1hcmtlcnMKICAgICAgICAgKi8KICAgICAgICBtYXhNYXJrZXJzOiB7CiAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICB2YWx1ZTogMCwKICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUga25vYiBpcyBleHBhbmRlZAogICAgICAgICAqLwogICAgICAgIGV4cGFuZDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgIH0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIGEgdG91Y2htb3ZlIG9uIHRoZSBzbGlkZXIgYmFyIGRvZXNuJ3QgZHJhZyB0aGUgc2xpZGVyIHRodW5iLgogICAgICAgICAqIFRhcHBpbmcgb24gdGhlIHNsaWRlciBiYXIgc3RpbGwgdXBkYXRlcyB0aGUgc2xpZGVyJ3MgcG9zaXRpb24KICAgICAgICAgKi8KICAgICAgICBpZ25vcmVCYXJUb3VjaDogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUcnVlIHdoZW4gdGhlIHVzZXIgaXMgZHJhZ2dpbmcgdGhlIHNsaWRlci4KICAgICAgICAgKi8KICAgICAgICBkcmFnZ2luZzogewogICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgIHZhbHVlOiBmYWxzZSwKICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0sCgogICAgICAgIHRyYW5zaXRpbmc6IHsKICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICByZWFkT25seTogdHJ1ZSwKICAgICAgICB9LAoKICAgICAgICBtYXJrZXJzOiB7CiAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICB9LAogICAgICAgIH0sCiAgICAgIH0sCgogICAgICBvYnNlcnZlcnM6IFsKICAgICAgICAnX3VwZGF0ZUtub2IodmFsdWUsIG1pbiwgbWF4LCBzbmFwcywgc3RlcCknLAogICAgICAgICdfdmFsdWVDaGFuZ2VkKHZhbHVlKScsCiAgICAgICAgJ19pbW1lZGlhdGVWYWx1ZUNoYW5nZWQoaW1tZWRpYXRlVmFsdWUpJywKICAgICAgICAnX3VwZGF0ZU1hcmtlcnMobWF4TWFya2VycywgbWluLCBtYXgsIHNuYXBzKScsCiAgICAgIF0sCgogICAgICBob3N0QXR0cmlidXRlczogewogICAgICAgIHJvbGU6ICdzbGlkZXInLAogICAgICAgIHRhYmluZGV4OiAwLAogICAgICB9LAoKICAgICAgLyoqIEB0eXBlIHshT2JqZWN0fSAqLwogICAgICBrZXlCaW5kaW5nczogewogICAgICAgICdsZWZ0JzogJ19sZWZ0S2V5JywKICAgICAgICAncmlnaHQnOiAnX3JpZ2h0S2V5JywKICAgICAgICAnZG93biBwYWdlZG93biBob21lJzogJ19kZWNyZW1lbnRLZXknLAogICAgICAgICd1cCBwYWdldXAgZW5kJzogJ19pbmNyZW1lbnRLZXknLAogICAgICB9LAoKICAgICAgcmVhZHk6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLmlnbm9yZUJhclRvdWNoKSB7CiAgICAgICAgICBzZXRUb3VjaEFjdGlvbih0aGlzLiQuc2xpZGVyQmFyLCAnYXV0bycpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBJbmNyZWFzZXMgdmFsdWUgYnkgYHN0ZXBgIGJ1dCBub3QgYWJvdmUgYG1heGAuCiAgICAgICAqIEBtZXRob2QgaW5jcmVtZW50CiAgICAgICAqLwogICAgICBpbmNyZW1lbnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudmFsdWUgPSB0aGlzLl9jbGFtcFZhbHVlKHRoaXMudmFsdWUgKyB0aGlzLnN0ZXApOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIERlY3JlYXNlcyB2YWx1ZSBieSBgc3RlcGAgYnV0IG5vdCBiZWxvdyBgbWluYC4KICAgICAgICogQG1ldGhvZCBkZWNyZW1lbnQKICAgICAgICovCiAgICAgIGRlY3JlbWVudDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy52YWx1ZSA9IHRoaXMuX2NsYW1wVmFsdWUodGhpcy52YWx1ZSAtIHRoaXMuc3RlcCk7CiAgICAgIH0sCgogICAgICBfdXBkYXRlS25vYjogZnVuY3Rpb24odmFsdWUsIG1pbiwgbWF4LCBzbmFwcywgc3RlcCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdhcmlhLXZhbHVlbWluJywgbWluKTsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS12YWx1ZW1heCcsIG1heCk7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtdmFsdWVub3cnLCB2YWx1ZSk7CgogICAgICAgIHRoaXMuX3Bvc2l0aW9uS25vYih0aGlzLl9jYWxjUmF0aW8odmFsdWUpICogMTAwKTsKICAgICAgfSwKCiAgICAgIF92YWx1ZUNoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuZmlyZSgndmFsdWUtY2hhbmdlJywge2NvbXBvc2VkOiB0cnVlfSk7CiAgICAgIH0sCgogICAgICBfaW1tZWRpYXRlVmFsdWVDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5kcmFnZ2luZykgewogICAgICAgICAgdGhpcy5maXJlKCdpbW1lZGlhdGUtdmFsdWUtY2hhbmdlJywge2NvbXBvc2VkOiB0cnVlfSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMudmFsdWUgPSB0aGlzLmltbWVkaWF0ZVZhbHVlOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9zZWNvbmRhcnlQcm9ncmVzc0NoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc2Vjb25kYXJ5UHJvZ3Jlc3MgPSB0aGlzLl9jbGFtcFZhbHVlKHRoaXMuc2Vjb25kYXJ5UHJvZ3Jlc3MpOwogICAgICB9LAoKICAgICAgX2V4cGFuZEtub2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3NldEV4cGFuZCh0cnVlKTsKICAgICAgfSwKCiAgICAgIF9yZXNldEtub2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuY2FuY2VsRGVib3VuY2VyKCdleHBhbmRLbm9iJyk7CiAgICAgICAgdGhpcy5fc2V0RXhwYW5kKGZhbHNlKTsKICAgICAgfSwKCiAgICAgIF9wb3NpdGlvbktub2I6IGZ1bmN0aW9uKHJhdGlvKSB7CiAgICAgICAgdGhpcy5fc2V0SW1tZWRpYXRlVmFsdWUodGhpcy5fY2FsY1N0ZXAodGhpcy5fY2FsY0tub2JQb3NpdGlvbihyYXRpbykpKTsKICAgICAgICB0aGlzLl9zZXRSYXRpbyh0aGlzLl9jYWxjUmF0aW8odGhpcy5pbW1lZGlhdGVWYWx1ZSkgKiAxMDApOwoKICAgICAgICB0aGlzLiQuc2xpZGVyS25vYi5zdHlsZS5sZWZ0ID0gdGhpcy5yYXRpbyArICclJzsKICAgICAgICBpZiAodGhpcy5kcmFnZ2luZykgewogICAgICAgICAgdGhpcy5fa25vYnN0YXJ0eCA9ICh0aGlzLnJhdGlvICogdGhpcy5fdykgLyAxMDA7CiAgICAgICAgICB0aGlzLnRyYW5zbGF0ZTNkKDAsIDAsIDAsIHRoaXMuJC5zbGlkZXJLbm9iKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfY2FsY0tub2JQb3NpdGlvbjogZnVuY3Rpb24ocmF0aW8pIHsKICAgICAgICByZXR1cm4gKHRoaXMubWF4IC0gdGhpcy5taW4pICogcmF0aW8gLyAxMDAgKyB0aGlzLm1pbjsKICAgICAgfSwKCiAgICAgIF9vblRyYWNrOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgIHN3aXRjaCAoZXZlbnQuZGV0YWlsLnN0YXRlKSB7CiAgICAgICAgICBjYXNlICdzdGFydCc6CiAgICAgICAgICAgIHRoaXMuX3RyYWNrU3RhcnQoZXZlbnQpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgJ3RyYWNrJzoKICAgICAgICAgICAgdGhpcy5fdHJhY2tYKGV2ZW50KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdlbmQnOgogICAgICAgICAgICB0aGlzLl90cmFja0VuZCgpOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfdHJhY2tTdGFydDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLl9zZXRUcmFuc2l0aW5nKGZhbHNlKTsKICAgICAgICB0aGlzLl93ID0gdGhpcy4kLnNsaWRlckJhci5vZmZzZXRXaWR0aDsKICAgICAgICB0aGlzLl94ID0gdGhpcy5yYXRpbyAqIHRoaXMuX3cgLyAxMDA7CiAgICAgICAgdGhpcy5fc3RhcnR4ID0gdGhpcy5feDsKICAgICAgICB0aGlzLl9rbm9ic3RhcnR4ID0gdGhpcy5fc3RhcnR4OwogICAgICAgIHRoaXMuX21pbnggPSAtdGhpcy5fc3RhcnR4OwogICAgICAgIHRoaXMuX21heHggPSB0aGlzLl93IC0gdGhpcy5fc3RhcnR4OwogICAgICAgIHRoaXMuJC5zbGlkZXJLbm9iLmNsYXNzTGlzdC5hZGQoJ2RyYWdnaW5nJyk7CiAgICAgICAgdGhpcy5fc2V0RHJhZ2dpbmcodHJ1ZSk7CiAgICAgIH0sCgogICAgICBfdHJhY2tYOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICghdGhpcy5kcmFnZ2luZykgewogICAgICAgICAgdGhpcy5fdHJhY2tTdGFydChldmVudCk7CiAgICAgICAgfQoKICAgICAgICB2YXIgZGlyZWN0aW9uID0gdGhpcy5faXNSVEwgPyAtMSA6IDE7CiAgICAgICAgdmFyIGR4ID0KICAgICAgICAgICAgTWF0aC5taW4odGhpcy5fbWF4eCwgTWF0aC5tYXgodGhpcy5fbWlueCwgZXZlbnQuZGV0YWlsLmR4ICogZGlyZWN0aW9uKSk7CiAgICAgICAgdGhpcy5feCA9IHRoaXMuX3N0YXJ0eCArIGR4OwoKICAgICAgICB2YXIgaW1tZWRpYXRlVmFsdWUgPQogICAgICAgICAgICB0aGlzLl9jYWxjU3RlcCh0aGlzLl9jYWxjS25vYlBvc2l0aW9uKHRoaXMuX3ggLyB0aGlzLl93ICogMTAwKSk7CiAgICAgICAgdGhpcy5fc2V0SW1tZWRpYXRlVmFsdWUoaW1tZWRpYXRlVmFsdWUpOwoKICAgICAgICAvLyB1cGRhdGUga25vYidzIHBvc2l0aW9uCiAgICAgICAgdmFyIHRyYW5zbGF0ZVggPQogICAgICAgICAgICAoKHRoaXMuX2NhbGNSYXRpbyh0aGlzLmltbWVkaWF0ZVZhbHVlKSAqIHRoaXMuX3cpIC0gdGhpcy5fa25vYnN0YXJ0eCk7CiAgICAgICAgdGhpcy50cmFuc2xhdGUzZCh0cmFuc2xhdGVYICsgJ3B4JywgMCwgMCwgdGhpcy4kLnNsaWRlcktub2IpOwogICAgICB9LAoKICAgICAgX3RyYWNrRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgcyA9IHRoaXMuJC5zbGlkZXJLbm9iLnN0eWxlOwoKICAgICAgICB0aGlzLiQuc2xpZGVyS25vYi5jbGFzc0xpc3QucmVtb3ZlKCdkcmFnZ2luZycpOwogICAgICAgIHRoaXMuX3NldERyYWdnaW5nKGZhbHNlKTsKICAgICAgICB0aGlzLl9yZXNldEtub2IoKTsKICAgICAgICB0aGlzLnZhbHVlID0gdGhpcy5pbW1lZGlhdGVWYWx1ZTsKCiAgICAgICAgcy50cmFuc2Zvcm0gPSBzLndlYmtpdFRyYW5zZm9ybSA9ICcnOwoKICAgICAgICB0aGlzLmZpcmUoJ2NoYW5nZScsIHtjb21wb3NlZDogdHJ1ZX0pOwogICAgICB9LAoKICAgICAgX2tub2Jkb3duOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuX2V4cGFuZEtub2IoKTsKCiAgICAgICAgLy8gY2FuY2VsIHNlbGVjdGlvbgogICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CgogICAgICAgIC8vIHNldCB0aGUgZm9jdXMgbWFudWFsbHkgYmVjYXVzZSB3ZSB3aWxsIGNhbGxlZCBwcmV2ZW50IGRlZmF1bHQKICAgICAgICB0aGlzLmZvY3VzKCk7CiAgICAgIH0sCgogICAgICBfYmFydHJhY2s6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMuX2FsbG93QmFyRXZlbnQoZXZlbnQpKSB7CiAgICAgICAgICB0aGlzLl9vblRyYWNrKGV2ZW50KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfYmFyY2xpY2s6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdGhpcy5fdyA9IHRoaXMuJC5zbGlkZXJCYXIub2Zmc2V0V2lkdGg7CiAgICAgICAgdmFyIHJlY3QgPSB0aGlzLiQuc2xpZGVyQmFyLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciByYXRpbyA9IChldmVudC5kZXRhaWwueCAtIHJlY3QubGVmdCkgLyB0aGlzLl93ICogMTAwOwogICAgICAgIGlmICh0aGlzLl9pc1JUTCkgewogICAgICAgICAgcmF0aW8gPSAxMDAgLSByYXRpbzsKICAgICAgICB9CiAgICAgICAgdmFyIHByZXZSYXRpbyA9IHRoaXMucmF0aW87CgogICAgICAgIHRoaXMuX3NldFRyYW5zaXRpbmcodHJ1ZSk7CiAgICAgICAgdGhpcy5fcG9zaXRpb25Lbm9iKHJhdGlvKTsKCiAgICAgICAgLy8gaWYgdGhlIHJhdGlvIGRvZXNuJ3QgY2hhbmdlLCBzbGlkZXJLbm9iJ3MgYW5pbWF0aW9uIHdvbid0IHN0YXJ0CiAgICAgICAgLy8gYW5kIGBfa25vYlRyYW5zaXRpb25FbmRgIHdvbid0IGJlIGNhbGxlZAogICAgICAgIC8vIFRoZXJlZm9yZSwgd2UgbmVlZCB0byBtYW51YWxseSB1cGRhdGUgdGhlIGB0cmFuc2l0aW5nYCBzdGF0ZQogICAgICAgIGlmIChwcmV2UmF0aW8gPT09IHRoaXMucmF0aW8pIHsKICAgICAgICAgIHRoaXMuX3NldFRyYW5zaXRpbmcoZmFsc2UpOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5hc3luYyhmdW5jdGlvbigpIHsKICAgICAgICAgIHRoaXMuZmlyZSgnY2hhbmdlJywge2NvbXBvc2VkOiB0cnVlfSk7CiAgICAgICAgfSk7CgogICAgICAgIC8vIGNhbmNlbCBzZWxlY3Rpb24KICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpOwoKICAgICAgICAvLyBzZXQgdGhlIGZvY3VzIG1hbnVhbGx5IGJlY2F1c2Ugd2Ugd2lsbCBjYWxsZWQgcHJldmVudCBkZWZhdWx0CiAgICAgICAgdGhpcy5mb2N1cygpOwogICAgICB9LAoKICAgICAgX2JhcmRvd246IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMuX2FsbG93QmFyRXZlbnQoZXZlbnQpKSB7CiAgICAgICAgICB0aGlzLmRlYm91bmNlKCdleHBhbmRLbm9iJywgdGhpcy5fZXhwYW5kS25vYiwgNjApOwogICAgICAgICAgdGhpcy5fYmFyY2xpY2soZXZlbnQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9rbm9iVHJhbnNpdGlvbkVuZDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoZXZlbnQudGFyZ2V0ID09PSB0aGlzLiQuc2xpZGVyS25vYikgewogICAgICAgICAgdGhpcy5fc2V0VHJhbnNpdGluZyhmYWxzZSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3VwZGF0ZU1hcmtlcnM6IGZ1bmN0aW9uKG1heE1hcmtlcnMsIG1pbiwgbWF4LCBzbmFwcykgewogICAgICAgIGlmICghc25hcHMpIHsKICAgICAgICAgIHRoaXMuX3NldE1hcmtlcnMoW10pOwogICAgICAgIH0KICAgICAgICB2YXIgc3RlcHMgPSBNYXRoLnJvdW5kKChtYXggLSBtaW4pIC8gdGhpcy5zdGVwKTsKICAgICAgICBpZiAoc3RlcHMgPiBtYXhNYXJrZXJzKSB7CiAgICAgICAgICBzdGVwcyA9IG1heE1hcmtlcnM7CiAgICAgICAgfQogICAgICAgIGlmIChzdGVwcyA8IDAgfHwgIWlzRmluaXRlKHN0ZXBzKSkgewogICAgICAgICAgc3RlcHMgPSAwOwogICAgICAgIH0KICAgICAgICB0aGlzLl9zZXRNYXJrZXJzKG5ldyBBcnJheShzdGVwcykpOwogICAgICB9LAoKICAgICAgX21lcmdlQ2xhc3NlczogZnVuY3Rpb24oY2xhc3NlcykgewogICAgICAgIHJldHVybiBPYmplY3Qua2V5cyhjbGFzc2VzKQogICAgICAgICAgICAuZmlsdGVyKGZ1bmN0aW9uKGNsYXNzTmFtZSkgewogICAgICAgICAgICAgIHJldHVybiBjbGFzc2VzW2NsYXNzTmFtZV07CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgIC5qb2luKCcgJyk7CiAgICAgIH0sCgogICAgICBfZ2V0Q2xhc3NOYW1lczogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX21lcmdlQ2xhc3Nlcyh7CiAgICAgICAgICBkaXNhYmxlZDogdGhpcy5kaXNhYmxlZCwKICAgICAgICAgIHBpbjogdGhpcy5waW4sCiAgICAgICAgICBzbmFwczogdGhpcy5zbmFwcywKICAgICAgICAgIHJpbmc6IHRoaXMuaW1tZWRpYXRlVmFsdWUgPD0gdGhpcy5taW4sCiAgICAgICAgICBleHBhbmQ6IHRoaXMuZXhwYW5kLAogICAgICAgICAgZHJhZ2dpbmc6IHRoaXMuZHJhZ2dpbmcsCiAgICAgICAgICB0cmFuc2l0aW5nOiB0aGlzLnRyYW5zaXRpbmcsCiAgICAgICAgICBlZGl0YWJsZTogdGhpcy5lZGl0YWJsZQogICAgICAgIH0pOwogICAgICB9LAoKICAgICAgX2FsbG93QmFyRXZlbnQ6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgcmV0dXJuICgKICAgICAgICAgICAgIXRoaXMuaWdub3JlQmFyVG91Y2ggfHwKICAgICAgICAgICAgKGV2ZW50LmRldGFpbC5zb3VyY2VFdmVudCBpbnN0YW5jZW9mIE1vdXNlRXZlbnQpKQogICAgICB9LAoKICAgICAgZ2V0IF9pc1JUTCgpIHsKICAgICAgICBpZiAodGhpcy5fX2lzUlRMID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgIHRoaXMuX19pc1JUTCA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKHRoaXMpWydkaXJlY3Rpb24nXSA9PT0gJ3J0bCc7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLl9faXNSVEw7CiAgICAgIH0sCgogICAgICBfbGVmdEtleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAodGhpcy5faXNSVEwpCiAgICAgICAgICB0aGlzLl9pbmNyZW1lbnRLZXkoZXZlbnQpOwogICAgICAgIGVsc2UKICAgICAgICAgIHRoaXMuX2RlY3JlbWVudEtleShldmVudCk7CiAgICAgIH0sCgogICAgICBfcmlnaHRLZXk6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgaWYgKHRoaXMuX2lzUlRMKQogICAgICAgICAgdGhpcy5fZGVjcmVtZW50S2V5KGV2ZW50KTsKICAgICAgICBlbHNlCiAgICAgICAgICB0aGlzLl9pbmNyZW1lbnRLZXkoZXZlbnQpOwogICAgICB9LAoKICAgICAgX2luY3JlbWVudEtleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoIXRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgIGlmIChldmVudC5kZXRhaWwua2V5ID09PSAnZW5kJykgewogICAgICAgICAgICB0aGlzLnZhbHVlID0gdGhpcy5tYXg7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLmluY3JlbWVudCgpOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5maXJlKCdjaGFuZ2UnKTsKICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX2RlY3JlbWVudEtleTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAoIXRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgIGlmIChldmVudC5kZXRhaWwua2V5ID09PSAnaG9tZScpIHsKICAgICAgICAgICAgdGhpcy52YWx1ZSA9IHRoaXMubWluOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5kZWNyZW1lbnQoKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuZmlyZSgnY2hhbmdlJyk7CiAgICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9jaGFuZ2VWYWx1ZTogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB0aGlzLnZhbHVlID0gZXZlbnQudGFyZ2V0LnZhbHVlOwogICAgICAgIHRoaXMuZmlyZSgnY2hhbmdlJywge2NvbXBvc2VkOiB0cnVlfSk7CiAgICAgIH0sCgogICAgICBfaW5wdXRLZXlEb3duOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICB9LAoKICAgICAgLy8gY3JlYXRlIHRoZSBlbGVtZW50IHJpcHBsZSBpbnNpZGUgdGhlIGBzbGlkZXJLbm9iYAogICAgICBfY3JlYXRlUmlwcGxlOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9yaXBwbGVDb250YWluZXIgPSB0aGlzLiQuc2xpZGVyS25vYjsKICAgICAgICByZXR1cm4gUGFwZXJJbmt5Rm9jdXNCZWhhdmlvckltcGwuX2NyZWF0ZVJpcHBsZS5jYWxsKHRoaXMpOwogICAgICB9LAoKICAgICAgLy8gSGlkZSB0aGUgcmlwcGxlIHdoZW4gdXNlciBpcyBub3QgaW50ZXJhY3Rpbmcgd2l0aCBrZXlib2FyZC4KICAgICAgLy8gVGhpcyBiZWhhdmlvciBpcyBkaWZmZXJlbnQgZnJvbSBvdGhlciByaXBwbGUteSBjb250cm9scywgYnV0IGlzCiAgICAgIC8vIGFjY29yZGluZyB0byBzcGVjOgogICAgICAvLyBodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2NvbXBvbmVudHMvc2xpZGVycy5odG1sCiAgICAgIF9mb2N1c2VkQ2hhbmdlZDogZnVuY3Rpb24ocmVjZWl2ZWRGb2N1c0Zyb21LZXlib2FyZCkgewogICAgICAgIGlmIChyZWNlaXZlZEZvY3VzRnJvbUtleWJvYXJkKSB7CiAgICAgICAgICB0aGlzLmVuc3VyZVJpcHBsZSgpOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5oYXNSaXBwbGUoKSkgewogICAgICAgICAgLy8gbm90ZSwgcmlwcGxlIG11c3QgYmUgdW4taGlkZGVuIHByaW9yIHRvIHNldHRpbmcgYGhvbGREb3duYAogICAgICAgICAgaWYgKHJlY2VpdmVkRm9jdXNGcm9tS2V5Ym9hcmQpIHsKICAgICAgICAgICAgdGhpcy5fcmlwcGxlLnN0eWxlLmRpc3BsYXkgPSAnJzsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRoaXMuX3JpcHBsZS5zdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fcmlwcGxlLmhvbGREb3duID0gcmVjZWl2ZWRGb2N1c0Zyb21LZXlib2FyZDsKICAgICAgICB9CiAgICAgIH0KICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gdGhlIHNsaWRlcidzIHZhbHVlIGNoYW5nZXMuCiAgICAgICAqCiAgICAgICAqIEBldmVudCB2YWx1ZS1jaGFuZ2UKICAgICAgICovCgogICAgICAvKioKICAgICAgICogRmlyZWQgd2hlbiB0aGUgc2xpZGVyJ3MgaW1tZWRpYXRlVmFsdWUgY2hhbmdlcy4gT25seSBvY2N1cnMgd2hpbGUgdGhlCiAgICAgICAqIHVzZXIgaXMgZHJhZ2dpbmcuCiAgICAgICAqCiAgICAgICAqIFRvIGRldGVjdCBjaGFuZ2VzIHRvIGltbWVkaWF0ZVZhbHVlIHRoYXQgaGFwcGVuIGZvciBhbnkgaW5wdXQgKGkuZS4KICAgICAgICogZHJhZ2dpbmcsIHRhcHBpbmcsIGNsaWNraW5nLCBldGMuKSBsaXN0ZW4gZm9yIGltbWVkaWF0ZS12YWx1ZS1jaGFuZ2VkCiAgICAgICAqIGluc3RlYWQuCiAgICAgICAqCiAgICAgICAqIEBldmVudCBpbW1lZGlhdGUtdmFsdWUtY2hhbmdlCiAgICAgICAqLwoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gdGhlIHNsaWRlcidzIHZhbHVlIGNoYW5nZXMgZHVlIHRvIHVzZXIgaW50ZXJhY3Rpb24uCiAgICAgICAqCiAgICAgICAqIENoYW5nZXMgdG8gdGhlIHNsaWRlcidzIHZhbHVlIGR1ZSB0byBjaGFuZ2VzIGluIGFuIHVuZGVybHlpbmcKICAgICAgICogYm91bmQgdmFyaWFibGUgd2lsbCBub3QgdHJpZ2dlciB0aGlzIGV2ZW50LgogICAgICAgKgogICAgICAgKiBAZXZlbnQgY2hhbmdlCiAgICAgICAqLwogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCiAgICBjb25zdCAkX2RvY3VtZW50Q29udGFpbmVyJDQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwogICAgJF9kb2N1bWVudENvbnRhaW5lciQ0LnNldEF0dHJpYnV0ZSgnc3R5bGUnLCAnZGlzcGxheTogbm9uZTsnKTsKCiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDQuaW5uZXJIVE1MID0gYDxkb20tbW9kdWxlIGlkPSJwYXBlci1zcGlubmVyLXN0eWxlcyI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICAvKgogICAgICAvKioqKioqKioqKioqKioqKioqKioqKioqKiovCiAgICAgIC8qIFNUWUxFUyBGT1IgVEhFIFNQSU5ORVIgKi8KICAgICAgLyoqKioqKioqKioqKioqKioqKioqKioqKioqLwoKICAgICAgLyoKICAgICAgICogQ29uc3RhbnRzOgogICAgICAgKiAgICAgIEFSQ1NJWkUgICAgID0gMjcwIGRlZ3JlZXMgKGFtb3VudCBvZiBjaXJjbGUgdGhlIGFyYyB0YWtlcyB1cCkKICAgICAgICogICAgICBBUkNUSU1FICAgICA9IDEzMzNtcyAodGltZSBpdCB0YWtlcyB0byBleHBhbmQgYW5kIGNvbnRyYWN0IGFyYykKICAgICAgICogICAgICBBUkNTVEFSVFJPVCA9IDIxNiBkZWdyZWVzIChob3cgbXVjaCB0aGUgc3RhcnQgbG9jYXRpb24gb2YgdGhlIGFyYwogICAgICAgKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2hvdWxkIHJvdGF0ZSBlYWNoIHRpbWUsIDIxNiBnaXZlcyB1cyBhCiAgICAgICAqICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICA1IHBvaW50ZWQgc3RhciBzaGFwZSAoaXQncyAzNjAvNSAqIDMpLgogICAgICAgKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgRm9yIGEgNyBwb2ludGVkIHN0YXIsIHdlIG1pZ2h0IGRvCiAgICAgICAqICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAzNjAvNyAqIDMgPSAxNTQuMjg2KQogICAgICAgKiAgICAgIFNIUklOS19USU1FID0gNDAwbXMKICAgICAgICovCgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICB3aWR0aDogMjhweDsKICAgICAgICBoZWlnaHQ6IDI4cHg7CgogICAgICAgIC8qIDM2MCAqIEFSQ1RJTUUgLyAoQVJDU1RBUlRST1QgKyAoMzYwLUFSQ1NJWkUpKSAqLwogICAgICAgIC0tcGFwZXItc3Bpbm5lci1jb250YWluZXItcm90YXRpb24tZHVyYXRpb246IDE1NjhtczsKCiAgICAgICAgLyogQVJDVElNRSAqLwogICAgICAgIC0tcGFwZXItc3Bpbm5lci1leHBhbmQtY29udHJhY3QtZHVyYXRpb246IDEzMzNtczsKCiAgICAgICAgLyogNCAqIEFSQ1RJTUUgKi8KICAgICAgICAtLXBhcGVyLXNwaW5uZXItZnVsbC1jeWNsZS1kdXJhdGlvbjogNTMzMm1zOwoKICAgICAgICAvKiBTSFJJTktfVElNRSAqLwogICAgICAgIC0tcGFwZXItc3Bpbm5lci1jb29sZG93bi1kdXJhdGlvbjogNDAwbXM7CiAgICAgIH0KCiAgICAgICNzcGlubmVyQ29udGFpbmVyIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CgogICAgICAgIC8qIFRoZSBzcGlubmVyIGRvZXMgbm90IGhhdmUgYW55IGNvbnRlbnRzIHRoYXQgd291bGQgaGF2ZSB0byBiZQogICAgICAgICAqIGZsaXBwZWQgaWYgdGhlIGRpcmVjdGlvbiBjaGFuZ2VzLiBBbHdheXMgdXNlIGx0ciBzbyB0aGF0IHRoZQogICAgICAgICAqIHN0eWxlIHdvcmtzIG91dCBjb3JyZWN0bHkgaW4gYm90aCBjYXNlcy4gKi8KICAgICAgICBkaXJlY3Rpb246IGx0cjsKICAgICAgfQoKICAgICAgI3NwaW5uZXJDb250YWluZXIuYWN0aXZlIHsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbjogY29udGFpbmVyLXJvdGF0ZSB2YXIoLS1wYXBlci1zcGlubmVyLWNvbnRhaW5lci1yb3RhdGlvbi1kdXJhdGlvbikgbGluZWFyIGluZmluaXRlOwogICAgICAgIGFuaW1hdGlvbjogY29udGFpbmVyLXJvdGF0ZSB2YXIoLS1wYXBlci1zcGlubmVyLWNvbnRhaW5lci1yb3RhdGlvbi1kdXJhdGlvbikgbGluZWFyIGluZmluaXRlOwogICAgICB9CgogICAgICBALXdlYmtpdC1rZXlmcmFtZXMgY29udGFpbmVyLXJvdGF0ZSB7CiAgICAgICAgdG8geyAtd2Via2l0LXRyYW5zZm9ybTogcm90YXRlKDM2MGRlZykgfQogICAgICB9CgogICAgICBAa2V5ZnJhbWVzIGNvbnRhaW5lci1yb3RhdGUgewogICAgICAgIHRvIHsgdHJhbnNmb3JtOiByb3RhdGUoMzYwZGVnKSB9CiAgICAgIH0KCiAgICAgIC5zcGlubmVyLWxheWVyIHsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItc3Bpbm5lci1jb2xvciwgdmFyKC0tZ29vZ2xlLWJsdWUtNTAwKSk7CiAgICAgIH0KCiAgICAgIC5sYXllci0xIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItc3Bpbm5lci1sYXllci0xLWNvbG9yLCB2YXIoLS1nb29nbGUtYmx1ZS01MDApKTsKICAgICAgfQoKICAgICAgLmxheWVyLTIgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1zcGlubmVyLWxheWVyLTItY29sb3IsIHZhcigtLWdvb2dsZS1yZWQtNTAwKSk7CiAgICAgIH0KCiAgICAgIC5sYXllci0zIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItc3Bpbm5lci1sYXllci0zLWNvbG9yLCB2YXIoLS1nb29nbGUteWVsbG93LTUwMCkpOwogICAgICB9CgogICAgICAubGF5ZXItNCB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXNwaW5uZXItbGF5ZXItNC1jb2xvciwgdmFyKC0tZ29vZ2xlLWdyZWVuLTUwMCkpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogSU1QT1JUQU5UIE5PVEUgQUJPVVQgQ1NTIEFOSU1BVElPTiBQUk9QRVJUSUVTIChrZWFudWxlZSk6CiAgICAgICAqCiAgICAgICAqIGlPUyBTYWZhcmkgKHRlc3RlZCBvbiBpT1MgOC4xKSBkb2VzIG5vdCBoYW5kbGUgYW5pbWF0aW9uLWRlbGF5IHZlcnkgd2VsbCAtIGl0IGRvZXNuJ3QKICAgICAgICogZ3VhcmFudGVlIHRoYXQgdGhlIGFuaW1hdGlvbiB3aWxsIHN0YXJ0IF9leGFjdGx5XyBhZnRlciB0aGF0IHZhbHVlLiBTbyB3ZSBhdm9pZCB1c2luZwogICAgICAgKiBhbmltYXRpb24tZGVsYXkgYW5kIGluc3RlYWQgc2V0IGN1c3RvbSBrZXlmcmFtZXMgZm9yIGVhY2ggY29sb3IgKGFzIGxheWVyLTJ1bmRhbnQgYXMgaXQKICAgICAgICogc2VlbXMpLgogICAgICAgKi8KICAgICAgLmFjdGl2ZSAuc3Bpbm5lci1sYXllciB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogZmlsbC11bmZpbGwtcm90YXRlOwogICAgICAgIC13ZWJraXQtYW5pbWF0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci1zcGlubmVyLWZ1bGwtY3ljbGUtZHVyYXRpb24pOwogICAgICAgIC13ZWJraXQtYW5pbWF0aW9uLXRpbWluZy1mdW5jdGlvbjogY3ViaWMtYmV6aWVyKDAuNCwgMC4wLCAwLjIsIDEpOwogICAgICAgIC13ZWJraXQtYW5pbWF0aW9uLWl0ZXJhdGlvbi1jb3VudDogaW5maW5pdGU7CiAgICAgICAgYW5pbWF0aW9uLW5hbWU6IGZpbGwtdW5maWxsLXJvdGF0ZTsKICAgICAgICBhbmltYXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLXNwaW5uZXItZnVsbC1jeWNsZS1kdXJhdGlvbik7CiAgICAgICAgYW5pbWF0aW9uLXRpbWluZy1mdW5jdGlvbjogY3ViaWMtYmV6aWVyKDAuNCwgMC4wLCAwLjIsIDEpOwogICAgICAgIGFuaW1hdGlvbi1pdGVyYXRpb24tY291bnQ6IGluZmluaXRlOwogICAgICAgIG9wYWNpdHk6IDE7CiAgICAgIH0KCiAgICAgIC5hY3RpdmUgLnNwaW5uZXItbGF5ZXIubGF5ZXItMSB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogZmlsbC11bmZpbGwtcm90YXRlLCBsYXllci0xLWZhZGUtaW4tb3V0OwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBmaWxsLXVuZmlsbC1yb3RhdGUsIGxheWVyLTEtZmFkZS1pbi1vdXQ7CiAgICAgIH0KCiAgICAgIC5hY3RpdmUgLnNwaW5uZXItbGF5ZXIubGF5ZXItMiB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogZmlsbC11bmZpbGwtcm90YXRlLCBsYXllci0yLWZhZGUtaW4tb3V0OwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBmaWxsLXVuZmlsbC1yb3RhdGUsIGxheWVyLTItZmFkZS1pbi1vdXQ7CiAgICAgIH0KCiAgICAgIC5hY3RpdmUgLnNwaW5uZXItbGF5ZXIubGF5ZXItMyB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogZmlsbC11bmZpbGwtcm90YXRlLCBsYXllci0zLWZhZGUtaW4tb3V0OwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBmaWxsLXVuZmlsbC1yb3RhdGUsIGxheWVyLTMtZmFkZS1pbi1vdXQ7CiAgICAgIH0KCiAgICAgIC5hY3RpdmUgLnNwaW5uZXItbGF5ZXIubGF5ZXItNCB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogZmlsbC11bmZpbGwtcm90YXRlLCBsYXllci00LWZhZGUtaW4tb3V0OwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBmaWxsLXVuZmlsbC1yb3RhdGUsIGxheWVyLTQtZmFkZS1pbi1vdXQ7CiAgICAgIH0KCiAgICAgIEAtd2Via2l0LWtleWZyYW1lcyBmaWxsLXVuZmlsbC1yb3RhdGUgewogICAgICAgIDEyLjUlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgxMzVkZWcpIH0gLyogMC41ICogQVJDU0laRSAqLwogICAgICAgIDI1JSAgIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgyNzBkZWcpIH0gLyogMSAgICogQVJDU0laRSAqLwogICAgICAgIDM3LjUlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg0MDVkZWcpIH0gLyogMS41ICogQVJDU0laRSAqLwogICAgICAgIDUwJSAgIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg1NDBkZWcpIH0gLyogMiAgICogQVJDU0laRSAqLwogICAgICAgIDYyLjUlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg2NzVkZWcpIH0gLyogMi41ICogQVJDU0laRSAqLwogICAgICAgIDc1JSAgIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg4MTBkZWcpIH0gLyogMyAgICogQVJDU0laRSAqLwogICAgICAgIDg3LjUlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg5NDVkZWcpIH0gLyogMy41ICogQVJDU0laRSAqLwogICAgICAgIHRvICAgIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgxMDgwZGVnKSB9IC8qIDQgICAqIEFSQ1NJWkUgKi8KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBmaWxsLXVuZmlsbC1yb3RhdGUgewogICAgICAgIDEyLjUlIHsgdHJhbnNmb3JtOiByb3RhdGUoMTM1ZGVnKSB9IC8qIDAuNSAqIEFSQ1NJWkUgKi8KICAgICAgICAyNSUgICB7IHRyYW5zZm9ybTogcm90YXRlKDI3MGRlZykgfSAvKiAxICAgKiBBUkNTSVpFICovCiAgICAgICAgMzcuNSUgeyB0cmFuc2Zvcm06IHJvdGF0ZSg0MDVkZWcpIH0gLyogMS41ICogQVJDU0laRSAqLwogICAgICAgIDUwJSAgIHsgdHJhbnNmb3JtOiByb3RhdGUoNTQwZGVnKSB9IC8qIDIgICAqIEFSQ1NJWkUgKi8KICAgICAgICA2Mi41JSB7IHRyYW5zZm9ybTogcm90YXRlKDY3NWRlZykgfSAvKiAyLjUgKiBBUkNTSVpFICovCiAgICAgICAgNzUlICAgeyB0cmFuc2Zvcm06IHJvdGF0ZSg4MTBkZWcpIH0gLyogMyAgICogQVJDU0laRSAqLwogICAgICAgIDg3LjUlIHsgdHJhbnNmb3JtOiByb3RhdGUoOTQ1ZGVnKSB9IC8qIDMuNSAqIEFSQ1NJWkUgKi8KICAgICAgICB0byAgICB7IHRyYW5zZm9ybTogcm90YXRlKDEwODBkZWcpIH0gLyogNCAgICogQVJDU0laRSAqLwogICAgICB9CgogICAgICBALXdlYmtpdC1rZXlmcmFtZXMgbGF5ZXItMS1mYWRlLWluLW91dCB7CiAgICAgICAgMCUgeyBvcGFjaXR5OiAxIH0KICAgICAgICAyNSUgeyBvcGFjaXR5OiAxIH0KICAgICAgICAyNiUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA4OSUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA5MCUgeyBvcGFjaXR5OiAxIH0KICAgICAgICB0byB7IG9wYWNpdHk6IDEgfQogICAgICB9CgogICAgICBAa2V5ZnJhbWVzIGxheWVyLTEtZmFkZS1pbi1vdXQgewogICAgICAgIDAlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgMjUlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgMjYlIHsgb3BhY2l0eTogMCB9CiAgICAgICAgODklIHsgb3BhY2l0eTogMCB9CiAgICAgICAgOTAlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgdG8geyBvcGFjaXR5OiAxIH0KICAgICAgfQoKICAgICAgQC13ZWJraXQta2V5ZnJhbWVzIGxheWVyLTItZmFkZS1pbi1vdXQgewogICAgICAgIDAlIHsgb3BhY2l0eTogMCB9CiAgICAgICAgMTUlIHsgb3BhY2l0eTogMCB9CiAgICAgICAgMjUlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgNTAlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgNTElIHsgb3BhY2l0eTogMCB9CiAgICAgICAgdG8geyBvcGFjaXR5OiAwIH0KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBsYXllci0yLWZhZGUtaW4tb3V0IHsKICAgICAgICAwJSB7IG9wYWNpdHk6IDAgfQogICAgICAgIDE1JSB7IG9wYWNpdHk6IDAgfQogICAgICAgIDI1JSB7IG9wYWNpdHk6IDEgfQogICAgICAgIDUwJSB7IG9wYWNpdHk6IDEgfQogICAgICAgIDUxJSB7IG9wYWNpdHk6IDAgfQogICAgICAgIHRvIHsgb3BhY2l0eTogMCB9CiAgICAgIH0KCiAgICAgIEAtd2Via2l0LWtleWZyYW1lcyBsYXllci0zLWZhZGUtaW4tb3V0IHsKICAgICAgICAwJSB7IG9wYWNpdHk6IDAgfQogICAgICAgIDQwJSB7IG9wYWNpdHk6IDAgfQogICAgICAgIDUwJSB7IG9wYWNpdHk6IDEgfQogICAgICAgIDc1JSB7IG9wYWNpdHk6IDEgfQogICAgICAgIDc2JSB7IG9wYWNpdHk6IDAgfQogICAgICAgIHRvIHsgb3BhY2l0eTogMCB9CiAgICAgIH0KCiAgICAgIEBrZXlmcmFtZXMgbGF5ZXItMy1mYWRlLWluLW91dCB7CiAgICAgICAgMCUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA0MCUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA1MCUgeyBvcGFjaXR5OiAxIH0KICAgICAgICA3NSUgeyBvcGFjaXR5OiAxIH0KICAgICAgICA3NiUgeyBvcGFjaXR5OiAwIH0KICAgICAgICB0byB7IG9wYWNpdHk6IDAgfQogICAgICB9CgogICAgICBALXdlYmtpdC1rZXlmcmFtZXMgbGF5ZXItNC1mYWRlLWluLW91dCB7CiAgICAgICAgMCUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA2NSUgeyBvcGFjaXR5OiAwIH0KICAgICAgICA3NSUgeyBvcGFjaXR5OiAxIH0KICAgICAgICA5MCUgeyBvcGFjaXR5OiAxIH0KICAgICAgICB0byB7IG9wYWNpdHk6IDAgfQogICAgICB9CgogICAgICBAa2V5ZnJhbWVzIGxheWVyLTQtZmFkZS1pbi1vdXQgewogICAgICAgIDAlIHsgb3BhY2l0eTogMCB9CiAgICAgICAgNjUlIHsgb3BhY2l0eTogMCB9CiAgICAgICAgNzUlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgOTAlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgdG8geyBvcGFjaXR5OiAwIH0KICAgICAgfQoKICAgICAgLmNpcmNsZS1jbGlwcGVyIHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIHdpZHRoOiA1MCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBQYXRjaCB0aGUgZ2FwIHRoYXQgYXBwZWFyIGJldHdlZW4gdGhlIHR3byBhZGphY2VudCBkaXYuY2lyY2xlLWNsaXBwZXIgd2hpbGUgdGhlCiAgICAgICAqIHNwaW5uZXIgaXMgcm90YXRpbmcgKGFwcGVhcnMgb24gQ2hyb21lIDUwLCBTYWZhcmkgOS4xLjEsIGFuZCBFZGdlKS4KICAgICAgICovCiAgICAgIC5zcGlubmVyLWxheWVyOjphZnRlciB7CiAgICAgICAgY29udGVudDogJyc7CiAgICAgICAgbGVmdDogNDUlOwogICAgICAgIHdpZHRoOiAxMCU7CiAgICAgICAgYm9yZGVyLXRvcC1zdHlsZTogc29saWQ7CiAgICAgIH0KCiAgICAgIC5zcGlubmVyLWxheWVyOjphZnRlciwKICAgICAgLmNpcmNsZS1jbGlwcGVyIC5jaXJjbGUgewogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHRvcDogMDsKICAgICAgICBib3JkZXItd2lkdGg6IHZhcigtLXBhcGVyLXNwaW5uZXItc3Ryb2tlLXdpZHRoLCAzcHgpOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDUwJTsKICAgICAgfQoKICAgICAgLmNpcmNsZS1jbGlwcGVyIC5jaXJjbGUgewogICAgICAgIGJvdHRvbTogMDsKICAgICAgICB3aWR0aDogMjAwJTsKICAgICAgICBib3JkZXItc3R5bGU6IHNvbGlkOwogICAgICAgIGJvcmRlci1ib3R0b20tY29sb3I6IHRyYW5zcGFyZW50ICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC5jaXJjbGUtY2xpcHBlci5sZWZ0IC5jaXJjbGUgewogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgYm9yZGVyLXJpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudCAhaW1wb3J0YW50OwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiByb3RhdGUoMTI5ZGVnKTsKICAgICAgICB0cmFuc2Zvcm06IHJvdGF0ZSgxMjlkZWcpOwogICAgICB9CgogICAgICAuY2lyY2xlLWNsaXBwZXIucmlnaHQgLmNpcmNsZSB7CiAgICAgICAgbGVmdDogLTEwMCU7CiAgICAgICAgYm9yZGVyLWxlZnQtY29sb3I6IHRyYW5zcGFyZW50ICFpbXBvcnRhbnQ7CiAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgtMTI5ZGVnKTsKICAgICAgICB0cmFuc2Zvcm06IHJvdGF0ZSgtMTI5ZGVnKTsKICAgICAgfQoKICAgICAgLmFjdGl2ZSAuZ2FwLXBhdGNoOjphZnRlciwKICAgICAgLmFjdGl2ZSAuY2lyY2xlLWNsaXBwZXIgLmNpcmNsZSB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLXNwaW5uZXItZXhwYW5kLWNvbnRyYWN0LWR1cmF0aW9uKTsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllcigwLjQsIDAuMCwgMC4yLCAxKTsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbi1pdGVyYXRpb24tY291bnQ6IGluZmluaXRlOwogICAgICAgIGFuaW1hdGlvbi1kdXJhdGlvbjogdmFyKC0tcGFwZXItc3Bpbm5lci1leHBhbmQtY29udHJhY3QtZHVyYXRpb24pOwogICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllcigwLjQsIDAuMCwgMC4yLCAxKTsKICAgICAgICBhbmltYXRpb24taXRlcmF0aW9uLWNvdW50OiBpbmZpbml0ZTsKICAgICAgfQoKICAgICAgLmFjdGl2ZSAuY2lyY2xlLWNsaXBwZXIubGVmdCAuY2lyY2xlIHsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbi1uYW1lOiBsZWZ0LXNwaW47CiAgICAgICAgYW5pbWF0aW9uLW5hbWU6IGxlZnQtc3BpbjsKICAgICAgfQoKICAgICAgLmFjdGl2ZSAuY2lyY2xlLWNsaXBwZXIucmlnaHQgLmNpcmNsZSB7CiAgICAgICAgLXdlYmtpdC1hbmltYXRpb24tbmFtZTogcmlnaHQtc3BpbjsKICAgICAgICBhbmltYXRpb24tbmFtZTogcmlnaHQtc3BpbjsKICAgICAgfQoKICAgICAgQC13ZWJraXQta2V5ZnJhbWVzIGxlZnQtc3BpbiB7CiAgICAgICAgMCUgeyAtd2Via2l0LXRyYW5zZm9ybTogcm90YXRlKDEzMGRlZykgfQogICAgICAgIDUwJSB7IC13ZWJraXQtdHJhbnNmb3JtOiByb3RhdGUoLTVkZWcpIH0KICAgICAgICB0byB7IC13ZWJraXQtdHJhbnNmb3JtOiByb3RhdGUoMTMwZGVnKSB9CiAgICAgIH0KCiAgICAgIEBrZXlmcmFtZXMgbGVmdC1zcGluIHsKICAgICAgICAwJSB7IHRyYW5zZm9ybTogcm90YXRlKDEzMGRlZykgfQogICAgICAgIDUwJSB7IHRyYW5zZm9ybTogcm90YXRlKC01ZGVnKSB9CiAgICAgICAgdG8geyB0cmFuc2Zvcm06IHJvdGF0ZSgxMzBkZWcpIH0KICAgICAgfQoKICAgICAgQC13ZWJraXQta2V5ZnJhbWVzIHJpZ2h0LXNwaW4gewogICAgICAgIDAlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSgtMTMwZGVnKSB9CiAgICAgICAgNTAlIHsgLXdlYmtpdC10cmFuc2Zvcm06IHJvdGF0ZSg1ZGVnKSB9CiAgICAgICAgdG8geyAtd2Via2l0LXRyYW5zZm9ybTogcm90YXRlKC0xMzBkZWcpIH0KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyByaWdodC1zcGluIHsKICAgICAgICAwJSB7IHRyYW5zZm9ybTogcm90YXRlKC0xMzBkZWcpIH0KICAgICAgICA1MCUgeyB0cmFuc2Zvcm06IHJvdGF0ZSg1ZGVnKSB9CiAgICAgICAgdG8geyB0cmFuc2Zvcm06IHJvdGF0ZSgtMTMwZGVnKSB9CiAgICAgIH0KCiAgICAgICNzcGlubmVyQ29udGFpbmVyLmNvb2xkb3duIHsKICAgICAgICAtd2Via2l0LWFuaW1hdGlvbjogY29udGFpbmVyLXJvdGF0ZSB2YXIoLS1wYXBlci1zcGlubmVyLWNvbnRhaW5lci1yb3RhdGlvbi1kdXJhdGlvbikgbGluZWFyIGluZmluaXRlLCBmYWRlLW91dCB2YXIoLS1wYXBlci1zcGlubmVyLWNvb2xkb3duLWR1cmF0aW9uKSBjdWJpYy1iZXppZXIoMC40LCAwLjAsIDAuMiwgMSk7CiAgICAgICAgYW5pbWF0aW9uOiBjb250YWluZXItcm90YXRlIHZhcigtLXBhcGVyLXNwaW5uZXItY29udGFpbmVyLXJvdGF0aW9uLWR1cmF0aW9uKSBsaW5lYXIgaW5maW5pdGUsIGZhZGUtb3V0IHZhcigtLXBhcGVyLXNwaW5uZXItY29vbGRvd24tZHVyYXRpb24pIGN1YmljLWJlemllcigwLjQsIDAuMCwgMC4yLCAxKTsKICAgICAgfQoKICAgICAgQC13ZWJraXQta2V5ZnJhbWVzIGZhZGUtb3V0IHsKICAgICAgICAwJSB7IG9wYWNpdHk6IDEgfQogICAgICAgIHRvIHsgb3BhY2l0eTogMCB9CiAgICAgIH0KCiAgICAgIEBrZXlmcmFtZXMgZmFkZS1vdXQgewogICAgICAgIDAlIHsgb3BhY2l0eTogMSB9CiAgICAgICAgdG8geyBvcGFjaXR5OiAwIH0KICAgICAgfQogICAgPC9zdHlsZT4KICA8L3RlbXBsYXRlPgo8L2RvbS1tb2R1bGU+YDsKCiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKCRfZG9jdW1lbnRDb250YWluZXIkNC5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKiogQHBvbHltZXJCZWhhdmlvciAqLwogICAgY29uc3QgUGFwZXJTcGlubmVyQmVoYXZpb3IgPSB7CgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogRGlzcGxheXMgdGhlIHNwaW5uZXIuCiAgICAgICAgICovCiAgICAgICAgYWN0aXZlOiB7CiAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgdmFsdWU6IGZhbHNlLAogICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgICAgb2JzZXJ2ZXI6ICdfX2FjdGl2ZUNoYW5nZWQnCiAgICAgICAgfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQWx0ZXJuYXRpdmUgdGV4dCBjb250ZW50IGZvciBhY2Nlc3NpYmlsaXR5IHN1cHBvcnQuCiAgICAgICAgICogSWYgYWx0IGlzIHByZXNlbnQsIGl0IHdpbGwgYWRkIGFuIGFyaWEtbGFiZWwgd2hvc2UgY29udGVudCBtYXRjaGVzIGFsdAogICAgICAgICAqIHdoZW4gYWN0aXZlLiBJZiBhbHQgaXMgbm90IHByZXNlbnQsIGl0IHdpbGwgZGVmYXVsdCB0byAnbG9hZGluZycgYXMgdGhlCiAgICAgICAgICogYWx0IHZhbHVlLgogICAgICAgICAqLwogICAgICAgIGFsdDoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdsb2FkaW5nJywgb2JzZXJ2ZXI6ICdfX2FsdENoYW5nZWQnfSwKCiAgICAgICAgX19jb29saW5nRG93bjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0KICAgICAgfSwKCiAgICAgIF9fY29tcHV0ZUNvbnRhaW5lckNsYXNzZXM6IGZ1bmN0aW9uKGFjdGl2ZSwgY29vbGluZ0Rvd24pIHsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgYWN0aXZlIHx8IGNvb2xpbmdEb3duID8gJ2FjdGl2ZScgOiAnJywKICAgICAgICAgIGNvb2xpbmdEb3duID8gJ2Nvb2xkb3duJyA6ICcnCiAgICAgICAgXS5qb2luKCcgJyk7CiAgICAgIH0sCgogICAgICBfX2FjdGl2ZUNoYW5nZWQ6IGZ1bmN0aW9uKGFjdGl2ZSwgb2xkKSB7CiAgICAgICAgdGhpcy5fX3NldEFyaWFIaWRkZW4oIWFjdGl2ZSk7CiAgICAgICAgdGhpcy5fX2Nvb2xpbmdEb3duID0gIWFjdGl2ZSAmJiBvbGQ7CiAgICAgIH0sCgogICAgICBfX2FsdENoYW5nZWQ6IGZ1bmN0aW9uKGFsdCkgewogICAgICAgIC8vIHVzZXItcHJvdmlkZWQgYGFyaWEtbGFiZWxgIHRha2VzIHByZWNlZGVuY2Ugb3ZlciBwcm90b3R5cGUgZGVmYXVsdAogICAgICAgIGlmIChhbHQgPT09ICdsb2FkaW5nJykgewogICAgICAgICAgdGhpcy5hbHQgPSB0aGlzLmdldEF0dHJpYnV0ZSgnYXJpYS1sYWJlbCcpIHx8IGFsdDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fX3NldEFyaWFIaWRkZW4oYWx0ID09PSAnJyk7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1sYWJlbCcsIGFsdCk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX19zZXRBcmlhSGlkZGVuOiBmdW5jdGlvbihoaWRkZW4pIHsKICAgICAgICB2YXIgYXR0ciA9ICdhcmlhLWhpZGRlbic7CiAgICAgICAgaWYgKGhpZGRlbikgewogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoYXR0ciwgJ3RydWUnKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoYXR0cik7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX19yZXNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5hY3RpdmUgPSBmYWxzZTsKICAgICAgICB0aGlzLl9fY29vbGluZ0Rvd24gPSBmYWxzZTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICBjb25zdCB0ZW1wbGF0ZSRmID0gaHRtbGAKICA8c3R5bGUgaW5jbHVkZT0icGFwZXItc3Bpbm5lci1zdHlsZXMiPjwvc3R5bGU+CgogIDxkaXYgaWQ9InNwaW5uZXJDb250YWluZXIiIGNsYXNzLW5hbWU9IltbX19jb21wdXRlQ29udGFpbmVyQ2xhc3NlcyhhY3RpdmUsIF9fY29vbGluZ0Rvd24pXV0iIG9uLWFuaW1hdGlvbmVuZD0iX19yZXNldCIgb24td2Via2l0LWFuaW1hdGlvbi1lbmQ9Il9fcmVzZXQiPgogICAgPGRpdiBjbGFzcz0ic3Bpbm5lci1sYXllciI+CiAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZS1jbGlwcGVyIGxlZnQiPgogICAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZSI+PC9kaXY+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUtY2xpcHBlciByaWdodCI+CiAgICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlIj48L2Rpdj4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICA8L2Rpdj4KYDsKICAgIHRlbXBsYXRlJGYuc2V0QXR0cmlidXRlKCdzdHJpcC13aGl0ZXNwYWNlJywgJycpOwoKICAgIC8qKgogICAgTWF0ZXJpYWwgZGVzaWduOiBbUHJvZ3Jlc3MgJgogICAgYWN0aXZpdHldKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9wcm9ncmVzcy1hY3Rpdml0eS5odG1sKQoKICAgIEVsZW1lbnQgcHJvdmlkaW5nIGEgc2luZ2xlIGNvbG9yIG1hdGVyaWFsIGRlc2lnbiBjaXJjdWxhciBzcGlubmVyLgoKICAgICAgICA8cGFwZXItc3Bpbm5lci1saXRlIGFjdGl2ZT48L3BhcGVyLXNwaW5uZXItbGl0ZT4KCiAgICBUaGUgZGVmYXVsdCBzcGlubmVyIGlzIGJsdWUuIEl0IGNhbiBiZSBjdXN0b21pemVkIHRvIGJlIGEgZGlmZmVyZW50IGNvbG9yLgoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgQWx0IGF0dHJpYnV0ZSBzaG91bGQgYmUgc2V0IHRvIHByb3ZpZGUgYWRlcXVhdGUgY29udGV4dCBmb3IgYWNjZXNzaWJpbGl0eS4gSWYKICAgIG5vdCBwcm92aWRlZCwgaXQgZGVmYXVsdHMgdG8gJ2xvYWRpbmcnLiBFbXB0eSBhbHQgY2FuIGJlIHByb3ZpZGVkIHRvIG1hcmsgdGhlCiAgICBlbGVtZW50IGFzIGRlY29yYXRpdmUgaWYgYWx0ZXJuYXRpdmUgY29udGVudCBpcyBwcm92aWRlZCBpbiBhbm90aGVyIGZvcm0gKGUuZy4gYQogICAgdGV4dCBibG9jayBmb2xsb3dpbmcgdGhlIHNwaW5uZXIpLgoKICAgICAgICA8cGFwZXItc3Bpbm5lci1saXRlIGFsdD0iTG9hZGluZyBjb250YWN0cyBsaXN0IiBhY3RpdmU+PC9wYXBlci1zcGlubmVyLWxpdGU+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1zcGlubmVyLWNvbG9yYCB8IENvbG9yIG9mIHRoZSBzcGlubmVyIHwgYC0tZ29vZ2xlLWJsdWUtNTAwYAogICAgYC0tcGFwZXItc3Bpbm5lci1zdHJva2Utd2lkdGhgIHwgVGhlIHdpZHRoIG9mIHRoZSBzcGlubmVyIHN0cm9rZSB8IDNweAoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItc3Bpbm5lci1saXRlCiAgICBAaGVybyBoZXJvLnN2ZwogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogdGVtcGxhdGUkZiwKCiAgICAgIGlzOiAncGFwZXItc3Bpbm5lci1saXRlJywKCiAgICAgIGJlaGF2aW9yczogW1BhcGVyU3Bpbm5lckJlaGF2aW9yXQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgdGVtcGxhdGUkZyA9IGh0bWxgCiAgPHN0eWxlIGluY2x1ZGU9InBhcGVyLXNwaW5uZXItc3R5bGVzIj48L3N0eWxlPgoKICA8ZGl2IGlkPSJzcGlubmVyQ29udGFpbmVyIiBjbGFzcy1uYW1lPSJbW19fY29tcHV0ZUNvbnRhaW5lckNsYXNzZXMoYWN0aXZlLCBfX2Nvb2xpbmdEb3duKV1dIiBvbi1hbmltYXRpb25lbmQ9Il9fcmVzZXQiIG9uLXdlYmtpdC1hbmltYXRpb24tZW5kPSJfX3Jlc2V0Ij4KICAgIDxkaXYgY2xhc3M9InNwaW5uZXItbGF5ZXIgbGF5ZXItMSI+CiAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZS1jbGlwcGVyIGxlZnQiPgogICAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZSI+PC9kaXY+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUtY2xpcHBlciByaWdodCI+CiAgICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlIj48L2Rpdj4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KCiAgICA8ZGl2IGNsYXNzPSJzcGlubmVyLWxheWVyIGxheWVyLTIiPgogICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUtY2xpcHBlciBsZWZ0Ij4KICAgICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUiPjwvZGl2PgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlLWNsaXBwZXIgcmlnaHQiPgogICAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZSI+PC9kaXY+CiAgICAgIDwvZGl2PgogICAgPC9kaXY+CgogICAgPGRpdiBjbGFzcz0ic3Bpbm5lci1sYXllciBsYXllci0zIj4KICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlLWNsaXBwZXIgbGVmdCI+CiAgICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlIj48L2Rpdj4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZS1jbGlwcGVyIHJpZ2h0Ij4KICAgICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUiPjwvZGl2PgogICAgICA8L2Rpdj4KICAgIDwvZGl2PgoKICAgIDxkaXYgY2xhc3M9InNwaW5uZXItbGF5ZXIgbGF5ZXItNCI+CiAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZS1jbGlwcGVyIGxlZnQiPgogICAgICAgIDxkaXYgY2xhc3M9ImNpcmNsZSI+PC9kaXY+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJjaXJjbGUtY2xpcHBlciByaWdodCI+CiAgICAgICAgPGRpdiBjbGFzcz0iY2lyY2xlIj48L2Rpdj4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICA8L2Rpdj4KYDsKICAgIHRlbXBsYXRlJGcuc2V0QXR0cmlidXRlKCdzdHJpcC13aGl0ZXNwYWNlJywgJycpOwoKICAgIC8qKgogICAgTWF0ZXJpYWwgZGVzaWduOiBbUHJvZ3Jlc3MgJgogICAgYWN0aXZpdHldKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy9wcm9ncmVzcy1hY3Rpdml0eS5odG1sKQoKICAgIEVsZW1lbnQgcHJvdmlkaW5nIGEgbXVsdGlwbGUgY29sb3IgbWF0ZXJpYWwgZGVzaWduIGNpcmN1bGFyIHNwaW5uZXIuCgogICAgICAgIDxwYXBlci1zcGlubmVyIGFjdGl2ZT48L3BhcGVyLXNwaW5uZXI+CgogICAgVGhlIGRlZmF1bHQgc3Bpbm5lciBjeWNsZXMgYmV0d2VlbiBmb3VyIGxheWVycyBvZiBjb2xvcnM7IGJ5IGRlZmF1bHQgdGhleSBhcmUKICAgIGJsdWUsIHJlZCwgeWVsbG93IGFuZCBncmVlbi4gSXQgY2FuIGJlIGN1c3RvbWl6ZWQgdG8gY3ljbGUgYmV0d2VlbiBmb3VyCiAgICBkaWZmZXJlbnQgY29sb3JzLiBVc2UgPHBhcGVyLXNwaW5uZXItbGl0ZT4gZm9yIHNpbmdsZSBjb2xvciBzcGlubmVycy4KCiAgICAjIyMgQWNjZXNzaWJpbGl0eQoKICAgIEFsdCBhdHRyaWJ1dGUgc2hvdWxkIGJlIHNldCB0byBwcm92aWRlIGFkZXF1YXRlIGNvbnRleHQgZm9yIGFjY2Vzc2liaWxpdHkuIElmCiAgICBub3QgcHJvdmlkZWQsIGl0IGRlZmF1bHRzIHRvICdsb2FkaW5nJy4gRW1wdHkgYWx0IGNhbiBiZSBwcm92aWRlZCB0byBtYXJrIHRoZQogICAgZWxlbWVudCBhcyBkZWNvcmF0aXZlIGlmIGFsdGVybmF0aXZlIGNvbnRlbnQgaXMgcHJvdmlkZWQgaW4gYW5vdGhlciBmb3JtIChlLmcuIGEKICAgIHRleHQgYmxvY2sgZm9sbG93aW5nIHRoZSBzcGlubmVyKS4KCiAgICAgICAgPHBhcGVyLXNwaW5uZXIgYWx0PSJMb2FkaW5nIGNvbnRhY3RzIGxpc3QiIGFjdGl2ZT48L3BhcGVyLXNwaW5uZXI+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci1zcGlubmVyLWxheWVyLTEtY29sb3JgIHwgQ29sb3Igb2YgdGhlIGZpcnN0IHNwaW5uZXIgcm90YXRpb24gfCBgLS1nb29nbGUtYmx1ZS01MDBgCiAgICBgLS1wYXBlci1zcGlubmVyLWxheWVyLTItY29sb3JgIHwgQ29sb3Igb2YgdGhlIHNlY29uZCBzcGlubmVyIHJvdGF0aW9uIHwgYC0tZ29vZ2xlLXJlZC01MDBgCiAgICBgLS1wYXBlci1zcGlubmVyLWxheWVyLTMtY29sb3JgIHwgQ29sb3Igb2YgdGhlIHRoaXJkIHNwaW5uZXIgcm90YXRpb24gfCBgLS1nb29nbGUteWVsbG93LTUwMGAKICAgIGAtLXBhcGVyLXNwaW5uZXItbGF5ZXItNC1jb2xvcmAgfCBDb2xvciBvZiB0aGUgZm91cnRoIHNwaW5uZXIgcm90YXRpb24gfCBgLS1nb29nbGUtZ3JlZW4tNTAwYAogICAgYC0tcGFwZXItc3Bpbm5lci1zdHJva2Utd2lkdGhgIHwgVGhlIHdpZHRoIG9mIHRoZSBzcGlubmVyIHN0cm9rZSB8IDNweAoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItc3Bpbm5lcgogICAgQGhlcm8gaGVyby5zdmcKICAgIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IHRlbXBsYXRlJGcsCgogICAgICBpczogJ3BhcGVyLXNwaW5uZXInLAoKICAgICAgYmVoYXZpb3JzOiBbUGFwZXJTcGlubmVyQmVoYXZpb3JdCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIGNvbnN0IHRlbXBsYXRlJGggPSBodG1sYDxpcm9uLWljb25zZXQtc3ZnIG5hbWU9InBhcGVyLXRhYnMiIHNpemU9IjI0Ij4KPHN2Zz48ZGVmcz4KPGcgaWQ9ImNoZXZyb24tbGVmdCI+PHBhdGggZD0iTTE1LjQxIDcuNDFMMTQgNmwtNiA2IDYgNiAxLjQxLTEuNDFMMTAuODMgMTJ6Ij48L3BhdGg+PC9nPgo8ZyBpZD0iY2hldnJvbi1yaWdodCI+PHBhdGggZD0iTTEwIDZMOC41OSA3LjQxIDEzLjE3IDEybC00LjU4IDQuNTlMMTAgMThsNi02eiI+PC9wYXRoPjwvZz4KPC9kZWZzPjwvc3ZnPgo8L2lyb24taWNvbnNldC1zdmc+YDsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQodGVtcGxhdGUkaC5jb250ZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dAogICAgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28KICAgIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8qCiAgICBgcGFwZXItdGFiYCBpcyBzdHlsZWQgdG8gbG9vayBsaWtlIGEgdGFiLiBJdCBzaG91bGQgYmUgdXNlZCBpbiBjb25qdW5jdGlvbiB3aXRoCiAgICBgcGFwZXItdGFic2AuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLXRhYnMgc2VsZWN0ZWQ9IjAiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMTwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMjwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMzwvcGFwZXItdGFiPgogICAgICAgIDwvcGFwZXItdGFicz4KCiAgICAjIyMgU3R5bGluZwoKICAgIFRoZSBmb2xsb3dpbmcgY3VzdG9tIHByb3BlcnRpZXMgYW5kIG1peGlucyBhcmUgYXZhaWxhYmxlIGZvciBzdHlsaW5nOgoKICAgIEN1c3RvbSBwcm9wZXJ0eSB8IERlc2NyaXB0aW9uIHwgRGVmYXVsdAogICAgLS0tLS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0KICAgIGAtLXBhcGVyLXRhYi1pbmtgIHwgSW5rIGNvbG9yIHwgYC0tcGFwZXIteWVsbG93LWExMDBgCiAgICBgLS1wYXBlci10YWJgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdGFiIHwgYHt9YAogICAgYC0tcGFwZXItdGFiLWNvbnRlbnRgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdGFiIGNvbnRlbnQgfCBge31gCiAgICBgLS1wYXBlci10YWItY29udGVudC1mb2N1c2VkYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHRhYiBjb250ZW50IHdoZW4gdGhlIHRhYiBpcyBmb2N1c2VkIHwgYHt9YAogICAgYC0tcGFwZXItdGFiLWNvbnRlbnQtdW5zZWxlY3RlZGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB0YWIgY29udGVudCB3aGVuIHRoZSB0YWIgaXMgbm90IHNlbGVjdGVkIHwgYHt9YAoKICAgIFRoaXMgZWxlbWVudCBhcHBsaWVzIHRoZSBtaXhpbiBgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlYCBidXQgZG9lcyBub3QgaW1wb3J0CiAgICBgcGFwZXItc3R5bGVzL3R5cG9ncmFwaHkuaHRtbGAuIEluIG9yZGVyIHRvIGFwcGx5IHRoZSBgUm9ib3RvYCBmb250IHRvIHRoaXMKICAgIGVsZW1lbnQsIG1ha2Ugc3VyZSB5b3UndmUgaW1wb3J0ZWQgYHBhcGVyLXN0eWxlcy90eXBvZ3JhcGh5Lmh0bWxgLgogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaW5saW5lOwogICAgICAgIEBhcHBseSAtLWxheW91dC1jZW50ZXI7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlci1qdXN0aWZpZWQ7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKCiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIHBhZGRpbmc6IDAgMTJweDsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICAgIGN1cnNvcjogcG9pbnRlcjsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci1mb250LWNvbW1vbi1iYXNlOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRhYjsKICAgICAgfQoKICAgICAgOmhvc3QoOmZvY3VzKSB7CiAgICAgICAgb3V0bGluZTogbm9uZTsKICAgICAgfQoKICAgICAgOmhvc3QoW2xpbmtdKSB7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgfQoKICAgICAgLnRhYi1jb250ZW50IHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVaKDApOwogICAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHRyYW5zbGF0ZVooMCk7CiAgICAgICAgdHJhbnNpdGlvbjogb3BhY2l0eSAwLjFzIGN1YmljLWJlemllcigwLjQsIDAuMCwgMSwgMSk7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWhvcml6b250YWw7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlci1jZW50ZXI7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKICAgICAgICBAYXBwbHkgLS1wYXBlci10YWItY29udGVudDsKICAgICAgfQoKICAgICAgOmhvc3QoOm5vdCguaXJvbi1zZWxlY3RlZCkpID4gLnRhYi1jb250ZW50IHsKICAgICAgICBvcGFjaXR5OiAwLjg7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRhYi1jb250ZW50LXVuc2VsZWN0ZWQ7CiAgICAgIH0KCiAgICAgIDpob3N0KDpmb2N1cykgLnRhYi1jb250ZW50IHsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICAgIGZvbnQtd2VpZ2h0OiA3MDA7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRhYi1jb250ZW50LWZvY3VzZWQ7CiAgICAgIH0KCiAgICAgIHBhcGVyLXJpcHBsZSB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXRhYi1pbmssIHZhcigtLXBhcGVyLXllbGxvdy1hMTAwKSk7CiAgICAgIH0KCiAgICAgIC50YWItY29udGVudCA+IDo6c2xvdHRlZChhKSB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKCiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxkaXYgY2xhc3M9InRhYi1jb250ZW50Ij4KICAgICAgPHNsb3Q+PC9zbG90PgogICAgPC9kaXY+CmAsCgogICAgICBpczogJ3BhcGVyLXRhYicsCgogICAgICBiZWhhdmlvcnM6IFtJcm9uQ29udHJvbFN0YXRlLCBJcm9uQnV0dG9uU3RhdGUsIFBhcGVyUmlwcGxlQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0aGUgdGFiIHdpbGwgZm9yd2FyZCBrZXlib2FyZCBjbGlja3MgKGVudGVyL3NwYWNlKSB0bwogICAgICAgICAqIHRoZSBmaXJzdCBhbmNob3IgZWxlbWVudCBmb3VuZCBpbiBpdHMgZGVzY2VuZGFudHMKICAgICAgICAgKi8KICAgICAgICBsaW5rOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlLCByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWV9CgogICAgICB9LAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ3RhYid9LAoKICAgICAgbGlzdGVuZXJzOiB7ZG93bjogJ191cGRhdGVOb2luaycsIHRhcDogJ19vblRhcCd9LAoKICAgICAgYXR0YWNoZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3VwZGF0ZU5vaW5rKCk7CiAgICAgIH0sCgogICAgICBnZXQgX3BhcmVudE5vaW5rKCkgewogICAgICAgIHZhciBwYXJlbnQgPSBkb20odGhpcykucGFyZW50Tm9kZTsKICAgICAgICByZXR1cm4gISFwYXJlbnQgJiYgISFwYXJlbnQubm9pbms7CiAgICAgIH0sCgogICAgICBfdXBkYXRlTm9pbms6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMubm9pbmsgPSAhIXRoaXMubm9pbmsgfHwgISF0aGlzLl9wYXJlbnROb2luazsKICAgICAgfSwKCiAgICAgIF9vblRhcDogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICBpZiAodGhpcy5saW5rKSB7CiAgICAgICAgICB2YXIgYW5jaG9yID0gdGhpcy5xdWVyeUVmZmVjdGl2ZUNoaWxkcmVuKCdhJyk7CgogICAgICAgICAgaWYgKCFhbmNob3IpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIERvbid0IGdldCBzdHVjayBpbiBhIGxvb3AgZGVsZWdhdGluZwogICAgICAgICAgLy8gdGhlIGxpc3RlbmVyIGZyb20gdGhlIGNoaWxkIGFuY2hvcgogICAgICAgICAgaWYgKGV2ZW50LnRhcmdldCA9PT0gYW5jaG9yKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICBhbmNob3IuY2xpY2soKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246IFtUYWJzXShodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2NvbXBvbmVudHMvdGFicy5odG1sKQoKICAgIGBwYXBlci10YWJzYCBtYWtlcyBpdCBlYXN5IHRvIGV4cGxvcmUgYW5kIHN3aXRjaCBiZXR3ZWVuIGRpZmZlcmVudCB2aWV3cyBvcgogICAgZnVuY3Rpb25hbCBhc3BlY3RzIG9mIGFuIGFwcCwgb3IgdG8gYnJvd3NlIGNhdGVnb3JpemVkIGRhdGEgc2V0cy4KCiAgICBVc2UgYHNlbGVjdGVkYCBwcm9wZXJ0eSB0byBnZXQgb3Igc2V0IHRoZSBzZWxlY3RlZCB0YWIuCgogICAgRXhhbXBsZToKCiAgICAgICAgPHBhcGVyLXRhYnMgc2VsZWN0ZWQ9IjAiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMTwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMjwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UQUIgMzwvcGFwZXItdGFiPgogICAgICAgIDwvcGFwZXItdGFicz4KCiAgICBTZWUgPGEgaHJlZj0iP2FjdGl2ZT1wYXBlci10YWIiPnBhcGVyLXRhYjwvYT4gZm9yIG1vcmUgaW5mb3JtYXRpb24gYWJvdXQKICAgIGBwYXBlci10YWJgLgoKICAgIEEgY29tbW9uIHVzYWdlIGZvciBgcGFwZXItdGFic2AgaXMgdG8gdXNlIGl0IGFsb25nIHdpdGggYGlyb24tcGFnZXNgIHRvIHN3aXRjaAogICAgYmV0d2VlbiBkaWZmZXJlbnQgdmlld3MuCgogICAgICAgIDxwYXBlci10YWJzIHNlbGVjdGVkPSJ7e3NlbGVjdGVkfX0iPgogICAgICAgICAgPHBhcGVyLXRhYj5UYWIgMTwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UYWIgMjwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYj5UYWIgMzwvcGFwZXItdGFiPgogICAgICAgIDwvcGFwZXItdGFicz4KCiAgICAgICAgPGlyb24tcGFnZXMgc2VsZWN0ZWQ9Int7c2VsZWN0ZWR9fSI+CiAgICAgICAgICA8ZGl2PlBhZ2UgMTwvZGl2PgogICAgICAgICAgPGRpdj5QYWdlIDI8L2Rpdj4KICAgICAgICAgIDxkaXY+UGFnZSAzPC9kaXY+CiAgICAgICAgPC9pcm9uLXBhZ2VzPgoKICAgIFRvIHVzZSBsaW5rcyBpbiB0YWJzLCBhZGQgYGxpbmtgIGF0dHJpYnV0ZSB0byBgcGFwZXItdGFiYCBhbmQgcHV0IGFuIGA8YT5gCiAgICBlbGVtZW50IGluIGBwYXBlci10YWJgIHdpdGggYSBgdGFiaW5kZXhgIG9mIC0xLgoKICAgIEV4YW1wbGU6CgogICAgPHByZT48Y29kZT4KICAgICZsdDtzdHlsZSBpcz0iY3VzdG9tLXN0eWxlIj4KICAgICAgLmxpbmsgewogICAgICAgICYjNjQ7YXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgICAgICAmIzY0O2FwcGx5IC0tbGF5b3V0LWNlbnRlci1jZW50ZXI7CiAgICAgIH0KICAgICZsdDsvc3R5bGU+CgogICAgJmx0O3BhcGVyLXRhYnMgc2VsZWN0ZWQ9IjAiPgogICAgICAmbHQ7cGFwZXItdGFiIGxpbms+CiAgICAgICAgJmx0O2EgaHJlZj0iI2xpbmsxIiBjbGFzcz0ibGluayIgdGFiaW5kZXg9Ii0xIj5UQUIgT05FJmx0Oy9hPgogICAgICAmbHQ7L3BhcGVyLXRhYj4KICAgICAgJmx0O3BhcGVyLXRhYiBsaW5rPgogICAgICAgICZsdDthIGhyZWY9IiNsaW5rMiIgY2xhc3M9ImxpbmsiIHRhYmluZGV4PSItMSI+VEFCIFRXTyZsdDsvYT4KICAgICAgJmx0Oy9wYXBlci10YWI+CiAgICAgICZsdDtwYXBlci10YWIgbGluaz4KICAgICAgICAmbHQ7YSBocmVmPSIjbGluazMiIGNsYXNzPSJsaW5rIiB0YWJpbmRleD0iLTEiPlRBQiBUSFJFRSZsdDsvYT4KICAgICAgJmx0Oy9wYXBlci10YWI+CiAgICAmbHQ7L3BhcGVyLXRhYnM+CiAgICA8L2NvZGU+PC9wcmU+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci10YWJzLXNlbGVjdGlvbi1iYXItY29sb3JgIHwgQ29sb3IgZm9yIHRoZSBzZWxlY3Rpb24gYmFyIHwgYC0tcGFwZXIteWVsbG93LWExMDBgCiAgICBgLS1wYXBlci10YWJzLXNlbGVjdGlvbi1iYXJgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgc2VsZWN0aW9uIGJhciB8IGB7fWAKICAgIGAtLXBhcGVyLXRhYnNgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdGFicyB8IGB7fWAKICAgIGAtLXBhcGVyLXRhYnMtY29udGVudGAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBjb250ZW50IGNvbnRhaW5lciBvZiB0YWJzIHwgYHt9YAogICAgYC0tcGFwZXItdGFicy1jb250YWluZXJgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgbGF5b3V0IGNvbnRhaW5lciBvZiB0YWJzIHwgYHt9YAoKICAgIEBkZW1vIGRlbW8vaW5kZXguaHRtbAogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQ7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWNlbnRlcjsKCiAgICAgICAgaGVpZ2h0OiA0OHB4OwogICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgLW1vei11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICB1c2VyLXNlbGVjdDogbm9uZTsKCiAgICAgICAgLyogTk9URTogQm90aCB2YWx1ZXMgYXJlIG5lZWRlZCwgc2luY2Ugc29tZSBwaG9uZXMgcmVxdWlyZSB0aGUgdmFsdWUgdG8gYmUgXGB0cmFuc3BhcmVudFxgLiAqLwogICAgICAgIC13ZWJraXQtdGFwLWhpZ2hsaWdodC1jb2xvcjogcmdiYSgwLCAwLCAwLCAwKTsKICAgICAgICAtd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3I6IHRyYW5zcGFyZW50OwoKICAgICAgICBAYXBwbHkgLS1wYXBlci10YWJzOwogICAgICB9CgogICAgICA6aG9zdCg6ZGlyKHJ0bCkpIHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbC1yZXZlcnNlOwogICAgICB9CgogICAgICAjdGFic0NvbnRhaW5lciB7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKICAgICAgICBAYXBwbHkgLS1wYXBlci10YWJzLWNvbnRhaW5lcjsKICAgICAgfQoKICAgICAgI3RhYnNDb250ZW50IHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgLW1vei1mbGV4LWJhc2lzOiBhdXRvOwogICAgICAgIC1tcy1mbGV4LWJhc2lzOiBhdXRvOwogICAgICAgIGZsZXgtYmFzaXM6IGF1dG87CiAgICAgICAgQGFwcGx5IC0tcGFwZXItdGFicy1jb250ZW50OwogICAgICB9CgogICAgICAjdGFic0NvbnRlbnQuc2Nyb2xsYWJsZSB7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7CiAgICAgIH0KCiAgICAgICN0YWJzQ29udGVudDpub3QoLnNjcm9sbGFibGUpLAogICAgICAjdGFic0NvbnRlbnQuc2Nyb2xsYWJsZS5maXQtY29udGFpbmVyIHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgICAgfQoKICAgICAgI3RhYnNDb250ZW50LnNjcm9sbGFibGUuZml0LWNvbnRhaW5lciB7CiAgICAgICAgbWluLXdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAjdGFic0NvbnRlbnQuc2Nyb2xsYWJsZS5maXQtY29udGFpbmVyID4gOjpzbG90dGVkKCopIHsKICAgICAgICAvKiBJRSAtIHByZXZlbnQgdGFicyBmcm9tIGNvbXByZXNzaW5nIHdoZW4gdGhleSBzaG91bGQgc2Nyb2xsLiAqLwogICAgICAgIC1tcy1mbGV4OiAxIDAgYXV0bzsKICAgICAgICAtd2Via2l0LWZsZXg6IDEgMCBhdXRvOwogICAgICAgIGZsZXg6IDEgMCBhdXRvOwogICAgICB9CgogICAgICAuaGlkZGVuIHsKICAgICAgICBkaXNwbGF5OiBub25lOwogICAgICB9CgogICAgICAubm90LXZpc2libGUgewogICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgY3Vyc29yOiBkZWZhdWx0OwogICAgICB9CgogICAgICBwYXBlci1pY29uLWJ1dHRvbiB7CiAgICAgICAgd2lkdGg6IDQ4cHg7CiAgICAgICAgaGVpZ2h0OiA0OHB4OwogICAgICAgIHBhZGRpbmc6IDEycHg7CiAgICAgICAgbWFyZ2luOiAwIDRweDsKICAgICAgfQoKICAgICAgI3NlbGVjdGlvbkJhciB7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIGhlaWdodDogMDsKICAgICAgICBib3R0b206IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgICByaWdodDogMDsKICAgICAgICBib3JkZXItYm90dG9tOiAycHggc29saWQgdmFyKC0tcGFwZXItdGFicy1zZWxlY3Rpb24tYmFyLWNvbG9yLCB2YXIoLS1wYXBlci15ZWxsb3ctYTEwMCkpOwogICAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHNjYWxlKDApOwogICAgICAgIHRyYW5zZm9ybTogc2NhbGUoMCk7CiAgICAgICAgICAtd2Via2l0LXRyYW5zZm9ybS1vcmlnaW46IGxlZnQgY2VudGVyOwogICAgICAgIHRyYW5zZm9ybS1vcmlnaW46IGxlZnQgY2VudGVyOwogICAgICAgICAgdHJhbnNpdGlvbjogLXdlYmtpdC10cmFuc2Zvcm07CiAgICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci10YWJzLXNlbGVjdGlvbi1iYXI7CiAgICAgIH0KCiAgICAgICNzZWxlY3Rpb25CYXIuYWxpZ24tYm90dG9tIHsKICAgICAgICB0b3A6IDA7CiAgICAgICAgYm90dG9tOiBhdXRvOwogICAgICB9CgogICAgICAjc2VsZWN0aW9uQmFyLmV4cGFuZCB7CiAgICAgICAgdHJhbnNpdGlvbi1kdXJhdGlvbjogMC4xNXM7CiAgICAgICAgdHJhbnNpdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllcigwLjQsIDAuMCwgMSwgMSk7CiAgICAgIH0KCiAgICAgICNzZWxlY3Rpb25CYXIuY29udHJhY3QgewogICAgICAgIHRyYW5zaXRpb24tZHVyYXRpb246IDAuMThzOwogICAgICAgIHRyYW5zaXRpb24tdGltaW5nLWZ1bmN0aW9uOiBjdWJpYy1iZXppZXIoMC4wLCAwLjAsIDAuMiwgMSk7CiAgICAgIH0KCiAgICAgICN0YWJzQ29udGVudCA+IDo6c2xvdHRlZCg6bm90KCNzZWxlY3Rpb25CYXIpKSB7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxwYXBlci1pY29uLWJ1dHRvbiBpY29uPSJwYXBlci10YWJzOmNoZXZyb24tbGVmdCIgY2xhc3MkPSJbW19jb21wdXRlU2Nyb2xsQnV0dG9uQ2xhc3MoX2xlZnRIaWRkZW4sIHNjcm9sbGFibGUsIGhpZGVTY3JvbGxCdXR0b25zKV1dIiBvbi11cD0iX29uU2Nyb2xsQnV0dG9uVXAiIG9uLWRvd249Il9vbkxlZnRTY3JvbGxCdXR0b25Eb3duIiB0YWJpbmRleD0iLTEiPjwvcGFwZXItaWNvbi1idXR0b24+CgogICAgPGRpdiBpZD0idGFic0NvbnRhaW5lciIgb24tdHJhY2s9Il9zY3JvbGwiIG9uLWRvd249Il9kb3duIj4KICAgICAgPGRpdiBpZD0idGFic0NvbnRlbnQiIGNsYXNzJD0iW1tfY29tcHV0ZVRhYnNDb250ZW50Q2xhc3Moc2Nyb2xsYWJsZSwgZml0Q29udGFpbmVyKV1dIj4KICAgICAgICA8ZGl2IGlkPSJzZWxlY3Rpb25CYXIiIGNsYXNzJD0iW1tfY29tcHV0ZVNlbGVjdGlvbkJhckNsYXNzKG5vQmFyLCBhbGlnbkJvdHRvbSldXSIgb24tdHJhbnNpdGlvbmVuZD0iX29uQmFyVHJhbnNpdGlvbkVuZCI+PC9kaXY+CiAgICAgICAgPHNsb3Q+PC9zbG90PgogICAgICA8L2Rpdj4KICAgIDwvZGl2PgoKICAgIDxwYXBlci1pY29uLWJ1dHRvbiBpY29uPSJwYXBlci10YWJzOmNoZXZyb24tcmlnaHQiIGNsYXNzJD0iW1tfY29tcHV0ZVNjcm9sbEJ1dHRvbkNsYXNzKF9yaWdodEhpZGRlbiwgc2Nyb2xsYWJsZSwgaGlkZVNjcm9sbEJ1dHRvbnMpXV0iIG9uLXVwPSJfb25TY3JvbGxCdXR0b25VcCIgb24tZG93bj0iX29uUmlnaHRTY3JvbGxCdXR0b25Eb3duIiB0YWJpbmRleD0iLTEiPjwvcGFwZXItaWNvbi1idXR0b24+CmAsCgogICAgICBpczogJ3BhcGVyLXRhYnMnLAogICAgICBiZWhhdmlvcnM6IFtJcm9uUmVzaXphYmxlQmVoYXZpb3IsIElyb25NZW51YmFyQmVoYXZpb3JdLAoKICAgICAgcHJvcGVydGllczogewogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIGluayByaXBwbGUgZWZmZWN0IGlzIGRpc2FibGVkLiBXaGVuIHRoaXMgcHJvcGVydHkgaXMgY2hhbmdlZCwKICAgICAgICAgKiBhbGwgZGVzY2VuZGFudCBgPHBhcGVyLXRhYj5gIGVsZW1lbnRzIGhhdmUgdGhlaXIgYG5vaW5rYCBwcm9wZXJ0eQogICAgICAgICAqIGNoYW5nZWQgdG8gdGhlIG5ldyB2YWx1ZSBhcyB3ZWxsLgogICAgICAgICAqLwogICAgICAgIG5vaW5rOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlLCBvYnNlcnZlcjogJ19ub2lua0NoYW5nZWQnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIGJvdHRvbSBiYXIgdG8gaW5kaWNhdGUgdGhlIHNlbGVjdGVkIHRhYiB3aWxsIG5vdCBiZSBzaG93bi4KICAgICAgICAgKi8KICAgICAgICBub0Jhcjoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCgogICAgICAgIC8qKgogICAgICAgICAqIElmIHRydWUsIHRoZSBzbGlkZSBlZmZlY3QgZm9yIHRoZSBib3R0b20gYmFyIGlzIGRpc2FibGVkLgogICAgICAgICAqLwogICAgICAgIG5vU2xpZGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0YWJzIGFyZSBzY3JvbGxhYmxlIGFuZCB0aGUgdGFiIHdpZHRoIGlzIGJhc2VkIG9uIHRoZSBsYWJlbAogICAgICAgICAqIHdpZHRoLgogICAgICAgICAqLwogICAgICAgIHNjcm9sbGFibGU6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0YWJzIGV4cGFuZCB0byBmaXQgdGhlaXIgY29udGFpbmVyLiBUaGlzIGN1cnJlbnRseSBvbmx5IGFwcGxpZXMKICAgICAgICAgKiB3aGVuIHNjcm9sbGFibGUgaXMgdHJ1ZS4KICAgICAgICAgKi8KICAgICAgICBmaXRDb250YWluZXI6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCBkcmFnZ2luZyBvbiB0aGUgdGFicyB0byBzY3JvbGwgaXMgZGlzYWJsZWQuCiAgICAgICAgICovCiAgICAgICAgZGlzYWJsZURyYWc6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCBzY3JvbGwgYnV0dG9ucyAobGVmdC9yaWdodCBhcnJvdykgd2lsbCBiZSBoaWRkZW4gZm9yIHNjcm9sbGFibGUKICAgICAgICAgKiB0YWJzLgogICAgICAgICAqLwogICAgICAgIGhpZGVTY3JvbGxCdXR0b25zOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogSWYgdHJ1ZSwgdGhlIHRhYnMgYXJlIGFsaWduZWQgdG8gYm90dG9tICh0aGUgc2VsZWN0aW9uIGJhciBhcHBlYXJzIGF0IHRoZQogICAgICAgICAqIHRvcCkuCiAgICAgICAgICovCiAgICAgICAgYWxpZ25Cb3R0b206IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICBzZWxlY3RhYmxlOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ3BhcGVyLXRhYid9LAoKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCB0YWJzIGFyZSBhdXRvbWF0aWNhbGx5IHNlbGVjdGVkIHdoZW4gZm9jdXNlZCB1c2luZyB0aGUKICAgICAgICAgKiBrZXlib2FyZC4KICAgICAgICAgKi8KICAgICAgICBhdXRvc2VsZWN0OiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IGZhbHNlfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGRlbGF5IChpbiBtaWxsaXNlY29uZHMpIGJldHdlZW4gd2hlbiB0aGUgdXNlciBzdG9wcyBpbnRlcmFjdGluZwogICAgICAgICAqIHdpdGggdGhlIHRhYnMgdGhyb3VnaCB0aGUga2V5Ym9hcmQgYW5kIHdoZW4gdGhlIGZvY3VzZWQgaXRlbSBpcwogICAgICAgICAqIGF1dG9tYXRpY2FsbHkgc2VsZWN0ZWQgKGlmIGBhdXRvc2VsZWN0YCBpcyB0cnVlKS4KICAgICAgICAgKi8KICAgICAgICBhdXRvc2VsZWN0RGVsYXk6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAwfSwKCiAgICAgICAgX3N0ZXA6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAxMH0sCgogICAgICAgIF9ob2xkRGVsYXk6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiAxfSwKCiAgICAgICAgX2xlZnRIaWRkZW46IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICBfcmlnaHRIaWRkZW46IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9LAoKICAgICAgICBfcHJldmlvdXNUYWI6IHt0eXBlOiBPYmplY3R9CiAgICAgIH0sCgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgaG9zdEF0dHJpYnV0ZXM6IHtyb2xlOiAndGFibGlzdCd9LAoKICAgICAgbGlzdGVuZXJzOiB7CiAgICAgICAgJ2lyb24tcmVzaXplJzogJ19vblRhYlNpemluZ0NoYW5nZWQnLAogICAgICAgICdpcm9uLWl0ZW1zLWNoYW5nZWQnOiAnX29uVGFiU2l6aW5nQ2hhbmdlZCcsCiAgICAgICAgJ2lyb24tc2VsZWN0JzogJ19vbklyb25TZWxlY3QnLAogICAgICAgICdpcm9uLWRlc2VsZWN0JzogJ19vbklyb25EZXNlbGVjdCcKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAdHlwZSB7IU9iamVjdH0KICAgICAgICovCiAgICAgIGtleUJpbmRpbmdzOiB7J2xlZnQ6a2V5dXAgcmlnaHQ6a2V5dXAnOiAnX29uQXJyb3dLZXl1cCd9LAoKICAgICAgY3JlYXRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5faG9sZEpvYiA9IG51bGw7CiAgICAgICAgdGhpcy5fcGVuZGluZ0FjdGl2YXRpb25JdGVtID0gdW5kZWZpbmVkOwogICAgICAgIHRoaXMuX3BlbmRpbmdBY3RpdmF0aW9uVGltZW91dCA9IHVuZGVmaW5lZDsKICAgICAgICB0aGlzLl9iaW5kRGVsYXllZEFjdGl2YXRpb25IYW5kbGVyID0KICAgICAgICAgICAgdGhpcy5fZGVsYXllZEFjdGl2YXRpb25IYW5kbGVyLmJpbmQodGhpcyk7CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdibHVyJywgdGhpcy5fb25CbHVyQ2FwdHVyZS5iaW5kKHRoaXMpLCB0cnVlKTsKICAgICAgfSwKCiAgICAgIHJlYWR5OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNldFNjcm9sbERpcmVjdGlvbigneScsIHRoaXMuJC50YWJzQ29udGFpbmVyKTsKICAgICAgfSwKCiAgICAgIGRldGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9jYW5jZWxQZW5kaW5nQWN0aXZhdGlvbigpOwogICAgICB9LAoKICAgICAgX25vaW5rQ2hhbmdlZDogZnVuY3Rpb24obm9pbmspIHsKICAgICAgICB2YXIgY2hpbGRUYWJzID0gZG9tKHRoaXMpLnF1ZXJ5U2VsZWN0b3JBbGwoJ3BhcGVyLXRhYicpOwogICAgICAgIGNoaWxkVGFicy5mb3JFYWNoKAogICAgICAgICAgICBub2luayA/IHRoaXMuX3NldE5vaW5rQXR0cmlidXRlIDogdGhpcy5fcmVtb3ZlTm9pbmtBdHRyaWJ1dGUpOwogICAgICB9LAoKICAgICAgX3NldE5vaW5rQXR0cmlidXRlOiBmdW5jdGlvbihlbGVtZW50KSB7CiAgICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoJ25vaW5rJywgJycpOwogICAgICB9LAoKICAgICAgX3JlbW92ZU5vaW5rQXR0cmlidXRlOiBmdW5jdGlvbihlbGVtZW50KSB7CiAgICAgICAgZWxlbWVudC5yZW1vdmVBdHRyaWJ1dGUoJ25vaW5rJyk7CiAgICAgIH0sCgogICAgICBfY29tcHV0ZVNjcm9sbEJ1dHRvbkNsYXNzOiBmdW5jdGlvbigKICAgICAgICAgIGhpZGVUaGlzQnV0dG9uLCBzY3JvbGxhYmxlLCBoaWRlU2Nyb2xsQnV0dG9ucykgewogICAgICAgIGlmICghc2Nyb2xsYWJsZSB8fCBoaWRlU2Nyb2xsQnV0dG9ucykgewogICAgICAgICAgcmV0dXJuICdoaWRkZW4nOwogICAgICAgIH0KCiAgICAgICAgaWYgKGhpZGVUaGlzQnV0dG9uKSB7CiAgICAgICAgICByZXR1cm4gJ25vdC12aXNpYmxlJzsKICAgICAgICB9CgogICAgICAgIHJldHVybiAnJzsKICAgICAgfSwKCiAgICAgIF9jb21wdXRlVGFic0NvbnRlbnRDbGFzczogZnVuY3Rpb24oc2Nyb2xsYWJsZSwgZml0Q29udGFpbmVyKSB7CiAgICAgICAgcmV0dXJuIHNjcm9sbGFibGUgPyAnc2Nyb2xsYWJsZScgKyAoZml0Q29udGFpbmVyID8gJyBmaXQtY29udGFpbmVyJyA6ICcnKSA6CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAnIGZpdC1jb250YWluZXInOwogICAgICB9LAoKICAgICAgX2NvbXB1dGVTZWxlY3Rpb25CYXJDbGFzczogZnVuY3Rpb24obm9CYXIsIGFsaWduQm90dG9tKSB7CiAgICAgICAgaWYgKG5vQmFyKSB7CiAgICAgICAgICByZXR1cm4gJ2hpZGRlbic7CiAgICAgICAgfSBlbHNlIGlmIChhbGlnbkJvdHRvbSkgewogICAgICAgICAgcmV0dXJuICdhbGlnbi1ib3R0b20nOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuICcnOwogICAgICB9LAoKICAgICAgLy8gVE9ETyhjZGF0YSk6IEFkZCBgdHJhY2tgIHJlc3BvbnNlIGJhY2sgaW4gd2hlbiBnZXN0dXJlIGxhbmRzLgoKICAgICAgX29uVGFiU2l6aW5nQ2hhbmdlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5kZWJvdW5jZSgnX29uVGFiU2l6aW5nQ2hhbmdlZCcsIGZ1bmN0aW9uKCkgewogICAgICAgICAgdGhpcy5fc2Nyb2xsKCk7CiAgICAgICAgICB0aGlzLl90YWJDaGFuZ2VkKHRoaXMuc2VsZWN0ZWRJdGVtKTsKICAgICAgICB9LCAxMCk7CiAgICAgIH0sCgogICAgICBfb25Jcm9uU2VsZWN0OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuX3RhYkNoYW5nZWQoZXZlbnQuZGV0YWlsLml0ZW0sIHRoaXMuX3ByZXZpb3VzVGFiKTsKICAgICAgICB0aGlzLl9wcmV2aW91c1RhYiA9IGV2ZW50LmRldGFpbC5pdGVtOwogICAgICAgIHRoaXMuY2FuY2VsRGVib3VuY2VyKCd0YWItY2hhbmdlZCcpOwogICAgICB9LAoKICAgICAgX29uSXJvbkRlc2VsZWN0OiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHRoaXMuZGVib3VuY2UoJ3RhYi1jaGFuZ2VkJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLl90YWJDaGFuZ2VkKG51bGwsIHRoaXMuX3ByZXZpb3VzVGFiKTsKICAgICAgICAgIHRoaXMuX3ByZXZpb3VzVGFiID0gbnVsbDsKICAgICAgICAgIC8vIFNlZSBwb2x5bWVyL3BvbHltZXIjMTMwNQogICAgICAgIH0sIDEpOwogICAgICB9LAoKICAgICAgX2FjdGl2YXRlSGFuZGxlcjogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gQ2FuY2VsIGl0ZW0gYWN0aXZhdGlvbnMgc2NoZWR1bGVkIGJ5IGtleWJvYXJkIGV2ZW50cyB3aGVuIGFueSBvdGhlcgogICAgICAgIC8vIGFjdGlvbiBjYXVzZXMgYW4gaXRlbSB0byBiZSBhY3RpdmF0ZWQgKGUuZy4gY2xpY2tzKS4KICAgICAgICB0aGlzLl9jYW5jZWxQZW5kaW5nQWN0aXZhdGlvbigpOwoKICAgICAgICBJcm9uTWVudUJlaGF2aW9ySW1wbC5fYWN0aXZhdGVIYW5kbGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQWN0aXZhdGVzIGFuIGl0ZW0gYWZ0ZXIgYSBkZWxheSAoaW4gbWlsbGlzZWNvbmRzKS4KICAgICAgICovCiAgICAgIF9zY2hlZHVsZUFjdGl2YXRpb246IGZ1bmN0aW9uKGl0ZW0sIGRlbGF5KSB7CiAgICAgICAgdGhpcy5fcGVuZGluZ0FjdGl2YXRpb25JdGVtID0gaXRlbTsKICAgICAgICB0aGlzLl9wZW5kaW5nQWN0aXZhdGlvblRpbWVvdXQgPQogICAgICAgICAgICB0aGlzLmFzeW5jKHRoaXMuX2JpbmREZWxheWVkQWN0aXZhdGlvbkhhbmRsZXIsIGRlbGF5KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBBY3RpdmF0ZXMgdGhlIGxhc3QgaXRlbSBnaXZlbiB0byBgX3NjaGVkdWxlQWN0aXZhdGlvbmAuCiAgICAgICAqLwogICAgICBfZGVsYXllZEFjdGl2YXRpb25IYW5kbGVyOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaXRlbSA9IHRoaXMuX3BlbmRpbmdBY3RpdmF0aW9uSXRlbTsKICAgICAgICB0aGlzLl9wZW5kaW5nQWN0aXZhdGlvbkl0ZW0gPSB1bmRlZmluZWQ7CiAgICAgICAgdGhpcy5fcGVuZGluZ0FjdGl2YXRpb25UaW1lb3V0ID0gdW5kZWZpbmVkOwogICAgICAgIGl0ZW0uZmlyZSh0aGlzLmFjdGl2YXRlRXZlbnQsIG51bGwsIHtidWJibGVzOiB0cnVlLCBjYW5jZWxhYmxlOiB0cnVlfSk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQ2FuY2VscyBhIHByZXZpb3VzbHkgc2NoZWR1bGVkIGl0ZW0gYWN0aXZhdGlvbiBtYWRlIHdpdGgKICAgICAgICogYF9zY2hlZHVsZUFjdGl2YXRpb25gLgogICAgICAgKi8KICAgICAgX2NhbmNlbFBlbmRpbmdBY3RpdmF0aW9uOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fcGVuZGluZ0FjdGl2YXRpb25UaW1lb3V0ICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgIHRoaXMuY2FuY2VsQXN5bmModGhpcy5fcGVuZGluZ0FjdGl2YXRpb25UaW1lb3V0KTsKICAgICAgICAgIHRoaXMuX3BlbmRpbmdBY3RpdmF0aW9uSXRlbSA9IHVuZGVmaW5lZDsKICAgICAgICAgIHRoaXMuX3BlbmRpbmdBY3RpdmF0aW9uVGltZW91dCA9IHVuZGVmaW5lZDsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfb25BcnJvd0tleXVwOiBmdW5jdGlvbihldmVudCkgewogICAgICAgIGlmICh0aGlzLmF1dG9zZWxlY3QpIHsKICAgICAgICAgIHRoaXMuX3NjaGVkdWxlQWN0aXZhdGlvbih0aGlzLmZvY3VzZWRJdGVtLCB0aGlzLmF1dG9zZWxlY3REZWxheSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX29uQmx1ckNhcHR1cmU6IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgLy8gQ2FuY2VsIGEgc2NoZWR1bGVkIGl0ZW0gYWN0aXZhdGlvbiAoaWYgYW55KSB3aGVuIHRoYXQgaXRlbSBpcwogICAgICAgIC8vIGJsdXJyZWQuCiAgICAgICAgaWYgKGV2ZW50LnRhcmdldCA9PT0gdGhpcy5fcGVuZGluZ0FjdGl2YXRpb25JdGVtKSB7CiAgICAgICAgICB0aGlzLl9jYW5jZWxQZW5kaW5nQWN0aXZhdGlvbigpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIGdldCBfdGFiQ29udGFpbmVyU2Nyb2xsU2l6ZSgpIHsKICAgICAgICByZXR1cm4gTWF0aC5tYXgoCiAgICAgICAgICAgIDAsIHRoaXMuJC50YWJzQ29udGFpbmVyLnNjcm9sbFdpZHRoIC0gdGhpcy4kLnRhYnNDb250YWluZXIub2Zmc2V0V2lkdGgpOwogICAgICB9LAoKICAgICAgX3Njcm9sbDogZnVuY3Rpb24oZSwgZGV0YWlsKSB7CiAgICAgICAgaWYgKCF0aGlzLnNjcm9sbGFibGUpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHZhciBkZHggPSAoZGV0YWlsICYmIC1kZXRhaWwuZGR4KSB8fCAwOwogICAgICAgIHRoaXMuX2FmZmVjdFNjcm9sbChkZHgpOwogICAgICB9LAoKICAgICAgX2Rvd246IGZ1bmN0aW9uKGUpIHsKICAgICAgICAvLyBnbyBvbmUgYmVhdCBhc3luYyB0byBkZWZlYXQgSXJvbk1lbnVCZWhhdmlvcgogICAgICAgIC8vIGF1dG9yZWZvY3VzLW9uLW5vLXNlbGVjdGlvbiB0aW1lb3V0CiAgICAgICAgdGhpcy5hc3luYyhmdW5jdGlvbigpIHsKICAgICAgICAgIGlmICh0aGlzLl9kZWZhdWx0Rm9jdXNBc3luYykgewogICAgICAgICAgICB0aGlzLmNhbmNlbEFzeW5jKHRoaXMuX2RlZmF1bHRGb2N1c0FzeW5jKTsKICAgICAgICAgICAgdGhpcy5fZGVmYXVsdEZvY3VzQXN5bmMgPSBudWxsOwogICAgICAgICAgfQogICAgICAgIH0sIDEpOwogICAgICB9LAoKICAgICAgX2FmZmVjdFNjcm9sbDogZnVuY3Rpb24oZHgpIHsKICAgICAgICB0aGlzLiQudGFic0NvbnRhaW5lci5zY3JvbGxMZWZ0ICs9IGR4OwoKICAgICAgICB2YXIgc2Nyb2xsTGVmdCA9IHRoaXMuJC50YWJzQ29udGFpbmVyLnNjcm9sbExlZnQ7CgogICAgICAgIHRoaXMuX2xlZnRIaWRkZW4gPSBzY3JvbGxMZWZ0ID09PSAwOwogICAgICAgIHRoaXMuX3JpZ2h0SGlkZGVuID0gc2Nyb2xsTGVmdCA9PT0gdGhpcy5fdGFiQ29udGFpbmVyU2Nyb2xsU2l6ZTsKICAgICAgfSwKCiAgICAgIF9vbkxlZnRTY3JvbGxCdXR0b25Eb3duOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9zY3JvbGxUb0xlZnQoKTsKICAgICAgICB0aGlzLl9ob2xkSm9iID0gc2V0SW50ZXJ2YWwodGhpcy5fc2Nyb2xsVG9MZWZ0LmJpbmQodGhpcyksIHRoaXMuX2hvbGREZWxheSk7CiAgICAgIH0sCgogICAgICBfb25SaWdodFNjcm9sbEJ1dHRvbkRvd246IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3Njcm9sbFRvUmlnaHQoKTsKICAgICAgICB0aGlzLl9ob2xkSm9iID0KICAgICAgICAgICAgc2V0SW50ZXJ2YWwodGhpcy5fc2Nyb2xsVG9SaWdodC5iaW5kKHRoaXMpLCB0aGlzLl9ob2xkRGVsYXkpOwogICAgICB9LAoKICAgICAgX29uU2Nyb2xsQnV0dG9uVXA6IGZ1bmN0aW9uKCkgewogICAgICAgIGNsZWFySW50ZXJ2YWwodGhpcy5faG9sZEpvYik7CiAgICAgICAgdGhpcy5faG9sZEpvYiA9IG51bGw7CiAgICAgIH0sCgogICAgICBfc2Nyb2xsVG9MZWZ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9hZmZlY3RTY3JvbGwoLXRoaXMuX3N0ZXApOwogICAgICB9LAoKICAgICAgX3Njcm9sbFRvUmlnaHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2FmZmVjdFNjcm9sbCh0aGlzLl9zdGVwKTsKICAgICAgfSwKCiAgICAgIF90YWJDaGFuZ2VkOiBmdW5jdGlvbih0YWIsIG9sZCkgewogICAgICAgIGlmICghdGFiKSB7CiAgICAgICAgICAvLyBSZW1vdmUgdGhlIGJhciB3aXRob3V0IGFuaW1hdGlvbi4KICAgICAgICAgIHRoaXMuJC5zZWxlY3Rpb25CYXIuY2xhc3NMaXN0LnJlbW92ZSgnZXhwYW5kJyk7CiAgICAgICAgICB0aGlzLiQuc2VsZWN0aW9uQmFyLmNsYXNzTGlzdC5yZW1vdmUoJ2NvbnRyYWN0Jyk7CiAgICAgICAgICB0aGlzLl9wb3NpdGlvbkJhcigwLCAwKTsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHZhciByID0gdGhpcy4kLnRhYnNDb250ZW50LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciB3ID0gci53aWR0aDsKICAgICAgICB2YXIgdGFiUmVjdCA9IHRhYi5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICB2YXIgdGFiT2Zmc2V0TGVmdCA9IHRhYlJlY3QubGVmdCAtIHIubGVmdDsKCiAgICAgICAgdGhpcy5fcG9zID0gewogICAgICAgICAgd2lkdGg6IHRoaXMuX2NhbGNQZXJjZW50KHRhYlJlY3Qud2lkdGgsIHcpLAogICAgICAgICAgbGVmdDogdGhpcy5fY2FsY1BlcmNlbnQodGFiT2Zmc2V0TGVmdCwgdykKICAgICAgICB9OwoKICAgICAgICBpZiAodGhpcy5ub1NsaWRlIHx8IG9sZCA9PSBudWxsKSB7CiAgICAgICAgICAvLyBQb3NpdGlvbiB0aGUgYmFyIHdpdGhvdXQgYW5pbWF0aW9uLgogICAgICAgICAgdGhpcy4kLnNlbGVjdGlvbkJhci5jbGFzc0xpc3QucmVtb3ZlKCdleHBhbmQnKTsKICAgICAgICAgIHRoaXMuJC5zZWxlY3Rpb25CYXIuY2xhc3NMaXN0LnJlbW92ZSgnY29udHJhY3QnKTsKICAgICAgICAgIHRoaXMuX3Bvc2l0aW9uQmFyKHRoaXMuX3Bvcy53aWR0aCwgdGhpcy5fcG9zLmxlZnQpOwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdmFyIG9sZFJlY3QgPSBvbGQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgdmFyIG9sZEluZGV4ID0gdGhpcy5pdGVtcy5pbmRleE9mKG9sZCk7CiAgICAgICAgdmFyIGluZGV4ID0gdGhpcy5pdGVtcy5pbmRleE9mKHRhYik7CiAgICAgICAgdmFyIG0gPSA1OwoKICAgICAgICAvLyBiYXIgYW5pbWF0aW9uOiBleHBhbmQKICAgICAgICB0aGlzLiQuc2VsZWN0aW9uQmFyLmNsYXNzTGlzdC5hZGQoJ2V4cGFuZCcpOwoKICAgICAgICB2YXIgbW92ZVJpZ2h0ID0gb2xkSW5kZXggPCBpbmRleDsKICAgICAgICB2YXIgaXNSVEwgPSB0aGlzLl9pc1JUTDsKICAgICAgICBpZiAoaXNSVEwpIHsKICAgICAgICAgIG1vdmVSaWdodCA9ICFtb3ZlUmlnaHQ7CiAgICAgICAgfQoKICAgICAgICBpZiAobW92ZVJpZ2h0KSB7CiAgICAgICAgICB0aGlzLl9wb3NpdGlvbkJhcigKICAgICAgICAgICAgICB0aGlzLl9jYWxjUGVyY2VudCh0YWJSZWN0LmxlZnQgKyB0YWJSZWN0LndpZHRoIC0gb2xkUmVjdC5sZWZ0LCB3KSAtIG0sCiAgICAgICAgICAgICAgdGhpcy5fbGVmdCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX3Bvc2l0aW9uQmFyKAogICAgICAgICAgICAgIHRoaXMuX2NhbGNQZXJjZW50KG9sZFJlY3QubGVmdCArIG9sZFJlY3Qud2lkdGggLSB0YWJSZWN0LmxlZnQsIHcpIC0gbSwKICAgICAgICAgICAgICB0aGlzLl9jYWxjUGVyY2VudCh0YWJPZmZzZXRMZWZ0LCB3KSArIG0pOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuc2Nyb2xsYWJsZSkgewogICAgICAgICAgdGhpcy5fc2Nyb2xsVG9TZWxlY3RlZElmTmVlZGVkKHRhYlJlY3Qud2lkdGgsIHRhYk9mZnNldExlZnQpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9zY3JvbGxUb1NlbGVjdGVkSWZOZWVkZWQ6IGZ1bmN0aW9uKHRhYldpZHRoLCB0YWJPZmZzZXRMZWZ0KSB7CiAgICAgICAgdmFyIGwgPSB0YWJPZmZzZXRMZWZ0IC0gdGhpcy4kLnRhYnNDb250YWluZXIuc2Nyb2xsTGVmdDsKICAgICAgICBpZiAobCA8IDApIHsKICAgICAgICAgIHRoaXMuJC50YWJzQ29udGFpbmVyLnNjcm9sbExlZnQgKz0gbDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgbCArPSAodGFiV2lkdGggLSB0aGlzLiQudGFic0NvbnRhaW5lci5vZmZzZXRXaWR0aCk7CiAgICAgICAgICBpZiAobCA+IDApIHsKICAgICAgICAgICAgdGhpcy4kLnRhYnNDb250YWluZXIuc2Nyb2xsTGVmdCArPSBsOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9jYWxjUGVyY2VudDogZnVuY3Rpb24odywgdzApIHsKICAgICAgICByZXR1cm4gMTAwICogdyAvIHcwOwogICAgICB9LAoKICAgICAgX3Bvc2l0aW9uQmFyOiBmdW5jdGlvbih3aWR0aCwgbGVmdCkgewogICAgICAgIHdpZHRoID0gd2lkdGggfHwgMDsKICAgICAgICBsZWZ0ID0gbGVmdCB8fCAwOwoKICAgICAgICB0aGlzLl93aWR0aCA9IHdpZHRoOwogICAgICAgIHRoaXMuX2xlZnQgPSBsZWZ0OwogICAgICAgIHRoaXMudHJhbnNmb3JtKAogICAgICAgICAgICAndHJhbnNsYXRlWCgnICsgbGVmdCArICclKSBzY2FsZVgoJyArICh3aWR0aCAvIDEwMCkgKyAnKScsCiAgICAgICAgICAgIHRoaXMuJC5zZWxlY3Rpb25CYXIpOwogICAgICB9LAoKICAgICAgX29uQmFyVHJhbnNpdGlvbkVuZDogZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBjbCA9IHRoaXMuJC5zZWxlY3Rpb25CYXIuY2xhc3NMaXN0OwogICAgICAgIC8vIGJhciBhbmltYXRpb246IGV4cGFuZCAtPiBjb250cmFjdAogICAgICAgIGlmIChjbC5jb250YWlucygnZXhwYW5kJykpIHsKICAgICAgICAgIGNsLnJlbW92ZSgnZXhwYW5kJyk7CiAgICAgICAgICBjbC5hZGQoJ2NvbnRyYWN0Jyk7CiAgICAgICAgICB0aGlzLl9wb3NpdGlvbkJhcih0aGlzLl9wb3Mud2lkdGgsIHRoaXMuX3Bvcy5sZWZ0KTsKICAgICAgICAgIC8vIGJhciBhbmltYXRpb24gZG9uZQogICAgICAgIH0gZWxzZSBpZiAoY2wuY29udGFpbnMoJ2NvbnRyYWN0JykpIHsKICAgICAgICAgIGNsLnJlbW92ZSgnY29udHJhY3QnKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9MSUNFTlNFLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQVVUSE9SUy50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlCiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vQ09OVFJJQlVUT1JTLnR4dCBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcwogICAgcGFydCBvZiB0aGUgcG9seW1lciBwcm9qZWN0IGlzIGFsc28gc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudAogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL1BBVEVOVFMudHh0CiAgICAqLwoKICAgIC8vIEtlZXBzIHRyYWNrIG9mIHRoZSB0b2FzdCBjdXJyZW50bHkgb3BlbmVkLgogICAgdmFyIGN1cnJlbnRUb2FzdCA9IG51bGw7CgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246IFtTbmFja2JhcnMgJgogICAgdG9hc3RzXShodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2NvbXBvbmVudHMvc25hY2tiYXJzLXRvYXN0cy5odG1sKQoKICAgIGBwYXBlci10b2FzdGAgcHJvdmlkZXMgYSBzdWJ0bGUgbm90aWZpY2F0aW9uIHRvYXN0LiBPbmx5IG9uZSBgcGFwZXItdG9hc3RgIHdpbGwKICAgIGJlIHZpc2libGUgb24gc2NyZWVuLgoKICAgIFVzZSBgb3BlbmVkYCB0byBzaG93IHRoZSB0b2FzdDoKCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItdG9hc3QgdGV4dD0iSGVsbG8gd29ybGQhIiBvcGVuZWQ+PC9wYXBlci10b2FzdD4KCiAgICBBbHNvIGBvcGVuKClgIG9yIGBzaG93KClgIGNhbiBiZSB1c2VkIHRvIHNob3cgdGhlIHRvYXN0OgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci1idXR0b24gb24tY2xpY2s9Im9wZW5Ub2FzdCI+T3BlbiBUb2FzdDwvcGFwZXItYnV0dG9uPgogICAgICAgIDxwYXBlci10b2FzdCBpZD0idG9hc3QiIHRleHQ9IkhlbGxvIHdvcmxkISI+PC9wYXBlci10b2FzdD4KCiAgICAgICAgLi4uCgogICAgICAgIG9wZW5Ub2FzdDogZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLiQudG9hc3Qub3BlbigpOwogICAgICAgIH0KCiAgICBTZXQgYGR1cmF0aW9uYCB0byAwLCBhIG5lZ2F0aXZlIG51bWJlciBvciBJbmZpbml0eSB0byBwZXJzaXN0IHRoZSB0b2FzdCBvbgogICAgc2NyZWVuOgoKICAgIEV4YW1wbGU6CgogICAgICAgIDxwYXBlci10b2FzdCB0ZXh0PSJUZXJtcyBhbmQgY29uZGl0aW9ucyIgb3BlbmVkIGR1cmF0aW9uPSIwIj4KICAgICAgICAgIDxhIGhyZWY9IiMiPlNob3cgbW9yZTwvYT4KICAgICAgICA8L3BhcGVyLXRvYXN0PgoKCiAgICAjIyMgU3R5bGluZwogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CgogICAgQ3VzdG9tIHByb3BlcnR5IHwgRGVzY3JpcHRpb24gfCBEZWZhdWx0CiAgICAtLS0tLS0tLS0tLS0tLS0tfC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLQogICAgYC0tcGFwZXItdG9hc3QtYmFja2dyb3VuZC1jb2xvcmAgfCBUaGUgcGFwZXItdG9hc3QgYmFja2dyb3VuZC1jb2xvciB8IGAjMzIzMjMyYAogICAgYC0tcGFwZXItdG9hc3QtY29sb3JgIHwgVGhlIHBhcGVyLXRvYXN0IGNvbG9yIHwgYCNmMWYxZjFgCgogICAgVGhpcyBlbGVtZW50IGFwcGxpZXMgdGhlIG1peGluIGAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2VgIGJ1dCBkb2VzIG5vdCBpbXBvcnQKICAgIGBwYXBlci1zdHlsZXMvdHlwb2dyYXBoeS5odG1sYC4gSW4gb3JkZXIgdG8gYXBwbHkgdGhlIGBSb2JvdG9gIGZvbnQgdG8gdGhpcwogICAgZWxlbWVudCwgbWFrZSBzdXJlIHlvdSd2ZSBpbXBvcnRlZCBgcGFwZXItc3R5bGVzL3R5cG9ncmFwaHkuaHRtbGAuCgogICAgQGdyb3VwIFBhcGVyIEVsZW1lbnRzCiAgICBAZWxlbWVudCBwYXBlci10b2FzdAogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICBAaGVybyBoZXJvLnN2ZwogICAgKi8KICAgIFBvbHltZXIoewogICAgICBfdGVtcGxhdGU6IGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItdG9hc3QtYmFja2dyb3VuZC1jb2xvciwgIzMyMzIzMik7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXRvYXN0LWNvbG9yLCAjZjFmMWYxKTsKICAgICAgICBtaW4taGVpZ2h0OiA0OHB4OwogICAgICAgIG1pbi13aWR0aDogMjg4cHg7CiAgICAgICAgcGFkZGluZzogMTZweCAyNHB4OwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgYm94LXNoYWRvdzogMCAycHggNXB4IDAgcmdiYSgwLCAwLCAwLCAwLjI2KTsKICAgICAgICBib3JkZXItcmFkaXVzOiAycHg7CiAgICAgICAgbWFyZ2luOiAxMnB4OwogICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICBjdXJzb3I6IGRlZmF1bHQ7CiAgICAgICAgLXdlYmtpdC10cmFuc2l0aW9uOiAtd2Via2l0LXRyYW5zZm9ybSAwLjNzLCBvcGFjaXR5IDAuM3M7CiAgICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtIDAuM3MsIG9wYWNpdHkgMC4zczsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICAgIC13ZWJraXQtdHJhbnNmb3JtOiB0cmFuc2xhdGVZKDEwMHB4KTsKICAgICAgICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoMTAwcHgpOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgIH0KCiAgICAgIDpob3N0KC5jYXBzdWxlKSB7CiAgICAgICAgYm9yZGVyLXJhZGl1czogMjRweDsKICAgICAgfQoKICAgICAgOmhvc3QoLmZpdC1ib3R0b20pIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBtaW4td2lkdGg6IDA7CiAgICAgICAgYm9yZGVyLXJhZGl1czogMDsKICAgICAgICBtYXJnaW46IDA7CiAgICAgIH0KCiAgICAgIDpob3N0KC5wYXBlci10b2FzdC1vcGVuKSB7CiAgICAgICAgb3BhY2l0eTogMTsKICAgICAgICAtd2Via2l0LXRyYW5zZm9ybTogdHJhbnNsYXRlWSgwcHgpOwogICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgwcHgpOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxzcGFuIGlkPSJsYWJlbCI+e3t0ZXh0fX08L3NwYW4+CiAgICA8c2xvdD48L3Nsb3Q+CmAsCgogICAgICBpczogJ3BhcGVyLXRvYXN0JywKICAgICAgYmVoYXZpb3JzOiBbSXJvbk92ZXJsYXlCZWhhdmlvcl0sCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGVsZW1lbnQgdG8gZml0IGB0aGlzYCBpbnRvLgogICAgICAgICAqIE92ZXJyaWRkZW4gZnJvbSBgUG9seW1lci5Jcm9uRml0QmVoYXZpb3JgLgogICAgICAgICAqLwogICAgICAgIGZpdEludG86IHt0eXBlOiBPYmplY3QsIHZhbHVlOiB3aW5kb3csIG9ic2VydmVyOiAnX29uRml0SW50b0NoYW5nZWQnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG9yaWVudGF0aW9uIGFnYWluc3Qgd2hpY2ggdG8gYWxpZ24gdGhlIGRyb3Bkb3duIGNvbnRlbnQKICAgICAgICAgKiBob3Jpem9udGFsbHkgcmVsYXRpdmUgdG8gYHBvc2l0aW9uVGFyZ2V0YC4KICAgICAgICAgKiBPdmVycmlkZGVuIGZyb20gYFBvbHltZXIuSXJvbkZpdEJlaGF2aW9yYC4KICAgICAgICAgKi8KICAgICAgICBob3Jpem9udGFsQWxpZ246IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnbGVmdCd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgb3JpZW50YXRpb24gYWdhaW5zdCB3aGljaCB0byBhbGlnbiB0aGUgZHJvcGRvd24gY29udGVudAogICAgICAgICAqIHZlcnRpY2FsbHkgcmVsYXRpdmUgdG8gYHBvc2l0aW9uVGFyZ2V0YC4KICAgICAgICAgKiBPdmVycmlkZGVuIGZyb20gYFBvbHltZXIuSXJvbkZpdEJlaGF2aW9yYC4KICAgICAgICAgKi8KICAgICAgICB2ZXJ0aWNhbEFsaWduOiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJ2JvdHRvbSd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZHVyYXRpb24gaW4gbWlsbGlzZWNvbmRzIHRvIHNob3cgdGhlIHRvYXN0LgogICAgICAgICAqIFNldCB0byBgMGAsIGEgbmVnYXRpdmUgbnVtYmVyLCBvciBgSW5maW5pdHlgLCB0byBkaXNhYmxlIHRoZQogICAgICAgICAqIHRvYXN0IGF1dG8tY2xvc2luZy4KICAgICAgICAgKi8KICAgICAgICBkdXJhdGlvbjoge3R5cGU6IE51bWJlciwgdmFsdWU6IDMwMDB9LAoKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgdGV4dCB0byBkaXNwbGF5IGluIHRoZSB0b2FzdC4KICAgICAgICAgKi8KICAgICAgICB0ZXh0OiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJyd9LAoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgICAqIFNldCB0byBmYWxzZSB0byBlbmFibGUgY2xvc2luZyBvZiB0aGUgdG9hc3QgYnkgY2xpY2tpbmcgb3V0c2lkZSBpdC4KICAgICAgICAgKi8KICAgICAgICBub0NhbmNlbE9uT3V0c2lkZUNsaWNrOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IHRydWV9LAoKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgICAqIFNldCB0byB0cnVlIHRvIGRpc2FibGUgYXV0by1mb2N1c2luZyB0aGUgdG9hc3Qgb3IgY2hpbGQgbm9kZXMgd2l0aAogICAgICAgICAqIHRoZSBgYXV0b2ZvY3VzYCBhdHRyaWJ1dGVgIHdoZW4gdGhlIG92ZXJsYXkgaXMgb3BlbmVkLgogICAgICAgICAqLwogICAgICAgIG5vQXV0b0ZvY3VzOiB7dHlwZTogQm9vbGVhbiwgdmFsdWU6IHRydWV9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsndHJhbnNpdGlvbmVuZCc6ICdfX29uVHJhbnNpdGlvbkVuZCd9LAoKICAgICAgLyoqCiAgICAgICAqIFJlYWQtb25seS4gRGVwcmVjYXRlZC4gVXNlIGBvcGVuZWRgIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKiBAcHJvcGVydHkgdmlzaWJsZQogICAgICAgKiBAZGVwcmVjYXRlZAogICAgICAgKi8KICAgICAgZ2V0IHZpc2libGUoKSB7CiAgICAgICAgQmFzZS5fd2FybignYHZpc2libGVgIGlzIGRlcHJlY2F0ZWQsIHVzZSBgb3BlbmVkYCBpbnN0ZWFkJyk7CiAgICAgICAgcmV0dXJuIHRoaXMub3BlbmVkOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJlYWQtb25seS4gQ2FuIGF1dG8tY2xvc2UgaWYgZHVyYXRpb24gaXMgYSBwb3NpdGl2ZSBmaW5pdGUgbnVtYmVyLgogICAgICAgKiBAcHJvcGVydHkgX2NhbkF1dG9DbG9zZQogICAgICAgKi8KICAgICAgZ2V0IF9jYW5BdXRvQ2xvc2UoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZHVyYXRpb24gPiAwICYmIHRoaXMuZHVyYXRpb24gIT09IEluZmluaXR5OwogICAgICB9LAoKICAgICAgY3JlYXRlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fYXV0b0Nsb3NlID0gbnVsbDsKICAgICAgICBJcm9uQTExeUFubm91bmNlci5yZXF1ZXN0QXZhaWxhYmlsaXR5KCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2hvdyB0aGUgdG9hc3QuIFdpdGhvdXQgYXJndW1lbnRzLCB0aGlzIGlzIHRoZSBzYW1lIGFzIGBvcGVuKClgIGZyb20KICAgICAgICogYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKiBAcGFyYW0geyhPYmplY3R8c3RyaW5nKT19IHByb3BlcnRpZXMgUHJvcGVydGllcyB0byBiZSBzZXQgYmVmb3JlIG9wZW5pbmcgdGhlIHRvYXN0LgogICAgICAgKiBlLmcuIGB0b2FzdC5zaG93KCdoZWxsbycpYCBvciBgdG9hc3Quc2hvdyh7dGV4dDogJ2hlbGxvJywgZHVyYXRpb246IDMwMDB9KWAKICAgICAgICovCiAgICAgIHNob3c6IGZ1bmN0aW9uKHByb3BlcnRpZXMpIHsKICAgICAgICBpZiAodHlwZW9mIHByb3BlcnRpZXMgPT0gJ3N0cmluZycpIHsKICAgICAgICAgIHByb3BlcnRpZXMgPSB7dGV4dDogcHJvcGVydGllc307CiAgICAgICAgfQogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHByb3BlcnRpZXMpIHsKICAgICAgICAgIGlmIChwcm9wZXJ0eS5pbmRleE9mKCdfJykgPT09IDApIHsKICAgICAgICAgICAgQmFzZS5fd2FybigKICAgICAgICAgICAgICAgICdUaGUgcHJvcGVydHkgIicgKyBwcm9wZXJ0eSArICciIGlzIHByaXZhdGUgYW5kIHdhcyBub3Qgc2V0LicpOwogICAgICAgICAgfSBlbHNlIGlmIChwcm9wZXJ0eSBpbiB0aGlzKSB7CiAgICAgICAgICAgIHRoaXNbcHJvcGVydHldID0gcHJvcGVydGllc1twcm9wZXJ0eV07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBCYXNlLl93YXJuKCdUaGUgcHJvcGVydHkgIicgKyBwcm9wZXJ0eSArICciIGlzIG5vdCB2YWxpZC4nKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdGhpcy5vcGVuKCk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogSGlkZSB0aGUgdG9hc3QuIFNhbWUgYXMgYGNsb3NlKClgIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKi8KICAgICAgaGlkZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5jbG9zZSgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbGxlZCBvbiB0cmFuc2l0aW9ucyBvZiB0aGUgdG9hc3QsIGluZGljYXRpbmcgYSBmaW5pc2hlZCBhbmltYXRpb24KICAgICAgICogQHByaXZhdGUKICAgICAgICovCiAgICAgIF9fb25UcmFuc2l0aW9uRW5kOiBmdW5jdGlvbihlKSB7CiAgICAgICAgLy8gdGhlcmUgYXJlIGRpZmZlcmVudCB0cmFuc2l0aW9ucyB0aGF0IGFyZSBoYXBwZW5pbmcgd2hlbiBvcGVuaW5nIGFuZAogICAgICAgIC8vIGNsb3NpbmcgdGhlIHRvYXN0LiBUaGUgbGFzdCBvbmUgc28gZmFyIGlzIGZvciBgb3BhY2l0eWAuCiAgICAgICAgLy8gVGhpcyBtYXJrcyB0aGUgZW5kIG9mIHRoZSB0cmFuc2l0aW9uLCBzbyB3ZSBjaGVjayBmb3IgdGhpcyB0byBkZXRlcm1pbmUKICAgICAgICAvLyBpZiB0aGlzIGlzIHRoZSBjb3JyZWN0IGV2ZW50LgogICAgICAgIGlmIChlICYmIGUudGFyZ2V0ID09PSB0aGlzICYmIGUucHJvcGVydHlOYW1lID09PSAnb3BhY2l0eScpIHsKICAgICAgICAgIGlmICh0aGlzLm9wZW5lZCkgewogICAgICAgICAgICB0aGlzLl9maW5pc2hSZW5kZXJPcGVuZWQoKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHRoaXMuX2ZpbmlzaFJlbmRlckNsb3NlZCgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKiBDYWxsZWQgd2hlbiB0aGUgdmFsdWUgb2YgYG9wZW5lZGAgY2hhbmdlcy4KICAgICAgICovCiAgICAgIF9vcGVuZWRDaGFuZ2VkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fYXV0b0Nsb3NlICE9PSBudWxsKSB7CiAgICAgICAgICB0aGlzLmNhbmNlbEFzeW5jKHRoaXMuX2F1dG9DbG9zZSk7CiAgICAgICAgICB0aGlzLl9hdXRvQ2xvc2UgPSBudWxsOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5vcGVuZWQpIHsKICAgICAgICAgIGlmIChjdXJyZW50VG9hc3QgJiYgY3VycmVudFRvYXN0ICE9PSB0aGlzKSB7CiAgICAgICAgICAgIGN1cnJlbnRUb2FzdC5jbG9zZSgpOwogICAgICAgICAgfQogICAgICAgICAgY3VycmVudFRvYXN0ID0gdGhpczsKICAgICAgICAgIHRoaXMuZmlyZSgnaXJvbi1hbm5vdW5jZScsIHt0ZXh0OiB0aGlzLnRleHR9KTsKICAgICAgICAgIGlmICh0aGlzLl9jYW5BdXRvQ2xvc2UpIHsKICAgICAgICAgICAgdGhpcy5fYXV0b0Nsb3NlID0gdGhpcy5hc3luYyh0aGlzLmNsb3NlLCB0aGlzLmR1cmF0aW9uKTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgaWYgKGN1cnJlbnRUb2FzdCA9PT0gdGhpcykgewogICAgICAgICAgY3VycmVudFRvYXN0ID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgSXJvbk92ZXJsYXlCZWhhdmlvckltcGwuX29wZW5lZENoYW5nZWQuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBPdmVycmlkZGVuIGZyb20gYElyb25PdmVybGF5QmVoYXZpb3JgLgogICAgICAgKi8KICAgICAgX3JlbmRlck9wZW5lZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5jbGFzc0xpc3QuYWRkKCdwYXBlci10b2FzdC1vcGVuJyk7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogT3ZlcnJpZGRlbiBmcm9tIGBJcm9uT3ZlcmxheUJlaGF2aW9yYC4KICAgICAgICovCiAgICAgIF9yZW5kZXJDbG9zZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuY2xhc3NMaXN0LnJlbW92ZSgncGFwZXItdG9hc3Qtb3BlbicpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfb25GaXRJbnRvQ2hhbmdlZDogZnVuY3Rpb24oZml0SW50bykgewogICAgICAgIHRoaXMucG9zaXRpb25UYXJnZXQgPSBmaXRJbnRvOwogICAgICB9CgogICAgICAvKioKICAgICAgICogRmlyZWQgd2hlbiBgcGFwZXItdG9hc3RgIGlzIG9wZW5lZC4KICAgICAgICoKICAgICAgICogQGV2ZW50ICdpcm9uLWFubm91bmNlJwogICAgICAgKiBAcGFyYW0ge3t0ZXh0OiBzdHJpbmd9fSBkZXRhaWwgQ29udGFpbnMgdGV4dCB0aGF0IHdpbGwgYmUgYW5ub3VuY2VkLgogICAgICAgKi8KICAgIH0pOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNSBUaGUgUG9seW1lciBQcm9qZWN0IEF1dGhvcnMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICBUaGlzIGNvZGUgbWF5IG9ubHkgYmUgdXNlZCB1bmRlciB0aGUgQlNEIHN0eWxlIGxpY2Vuc2UgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGF1dGhvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dAogICAgVGhlIGNvbXBsZXRlIHNldCBvZiBjb250cmlidXRvcnMgbWF5IGJlIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0CiAgICBDb2RlIGRpc3RyaWJ1dGVkIGJ5IEdvb2dsZSBhcyBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbwogICAgc3ViamVjdCB0byBhbiBhZGRpdGlvbmFsIElQIHJpZ2h0cyBncmFudCBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgY29uc3QgdGVtcGxhdGUkaSA9IGh0bWxgCgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIEBhcHBseSAtLWxheW91dC1ob3Jpem9udGFsOwogICAgICAgIEBhcHBseSAtLWxheW91dC1jZW50ZXI7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgewogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICB9CgogICAgICA6aG9zdCg6Zm9jdXMpIHsKICAgICAgICBvdXRsaW5lOm5vbmU7CiAgICAgIH0KCiAgICAgIC50b2dnbGUtYmFyIHsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDhweDsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgICBvcGFjaXR5OiAwLjQ7CiAgICAgICAgdHJhbnNpdGlvbjogYmFja2dyb3VuZC1jb2xvciBsaW5lYXIgLjA4czsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1iYXItY29sb3IsICMwMDAwMDApOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1iYXI7CiAgICAgIH0KCiAgICAgIC50b2dnbGUtYnV0dG9uIHsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAtM3B4OwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgaGVpZ2h0OiAyMHB4OwogICAgICAgIHdpZHRoOiAyMHB4OwogICAgICAgIGJvcmRlci1yYWRpdXM6IDUwJTsKICAgICAgICBib3gtc2hhZG93OiAwIDFweCA1cHggMCByZ2JhKDAsIDAsIDAsIDAuNik7CiAgICAgICAgdHJhbnNpdGlvbjogLXdlYmtpdC10cmFuc2Zvcm0gbGluZWFyIC4wOHMsIGJhY2tncm91bmQtY29sb3IgbGluZWFyIC4wOHM7CiAgICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtIGxpbmVhciAuMDhzLCBiYWNrZ3JvdW5kLWNvbG9yIGxpbmVhciAuMDhzOwogICAgICAgIHdpbGwtY2hhbmdlOiB0cmFuc2Zvcm07CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi11bmNoZWNrZWQtYnV0dG9uLWNvbG9yLCB2YXIoLS1wYXBlci1ncmV5LTUwKSk7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvZ2dsZS1idXR0b24tdW5jaGVja2VkLWJ1dHRvbjsKICAgICAgfQoKICAgICAgLnRvZ2dsZS1idXR0b24uZHJhZ2dpbmcgewogICAgICAgIC13ZWJraXQtdHJhbnNpdGlvbjogbm9uZTsKICAgICAgICB0cmFuc2l0aW9uOiBub25lOwogICAgICB9CgogICAgICA6aG9zdChbY2hlY2tlZF06bm90KFtkaXNhYmxlZF0pKSAudG9nZ2xlLWJhciB7CiAgICAgICAgb3BhY2l0eTogMC41OwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXRvZ2dsZS1idXR0b24tY2hlY2tlZC1iYXItY29sb3IsIHZhcigtLXByaW1hcnktY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1jaGVja2VkLWJhcjsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgLnRvZ2dsZS1iYXIgewogICAgICAgIGJhY2tncm91bmQtY29sb3I6ICMwMDA7CiAgICAgICAgb3BhY2l0eTogMC4xMjsKICAgICAgfQoKICAgICAgOmhvc3QoW2NoZWNrZWRdKSAudG9nZ2xlLWJ1dHRvbiB7CiAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHRyYW5zbGF0ZSgxNnB4LCAwKTsKICAgICAgICB0cmFuc2Zvcm06IHRyYW5zbGF0ZSgxNnB4LCAwKTsKICAgICAgfQoKICAgICAgOmhvc3QoW2NoZWNrZWRdOm5vdChbZGlzYWJsZWRdKSkgLnRvZ2dsZS1idXR0b24gewogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXRvZ2dsZS1idXR0b24tY2hlY2tlZC1idXR0b24tY29sb3IsIHZhcigtLXByaW1hcnktY29sb3IpKTsKCiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1jaGVja2VkLWJ1dHRvbjsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgLnRvZ2dsZS1idXR0b24gewogICAgICAgIGJhY2tncm91bmQtY29sb3I6ICNiZGJkYmQ7CiAgICAgICAgb3BhY2l0eTogMTsKICAgICAgfQoKICAgICAgLnRvZ2dsZS1pbmsgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IC0xNHB4OwogICAgICAgIGxlZnQ6IC0xNHB4OwogICAgICAgIHJpZ2h0OiBhdXRvOwogICAgICAgIGJvdHRvbTogYXV0bzsKICAgICAgICB3aWR0aDogNDhweDsKICAgICAgICBoZWlnaHQ6IDQ4cHg7CiAgICAgICAgb3BhY2l0eTogMC41OwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1pbmstY29sb3IsIHZhcigtLXByaW1hcnktdGV4dC1jb2xvcikpOwoKICAgICAgICBAYXBwbHkgLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1pbms7CiAgICAgIH0KCiAgICAgIDpob3N0KFtjaGVja2VkXSkgLnRvZ2dsZS1pbmsgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLWNoZWNrZWQtaW5rLWNvbG9yLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CgogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvZ2dsZS1idXR0b24tY2hlY2tlZC1pbms7CiAgICAgIH0KCiAgICAgIC50b2dnbGUtY29udGFpbmVyIHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIHdpZHRoOiAzNnB4OwogICAgICAgIGhlaWdodDogMTRweDsKICAgICAgICAvKiBUaGUgdG9nZ2xlIGJ1dHRvbiBoYXMgYW4gYWJzb2x1dGUgcG9zaXRpb24gb2YgLTNweDsgVGhlIGV4dHJhIDFweAogICAgICAgIC8qIGFjY291bnRzIGZvciB0aGUgdG9nZ2xlIGJ1dHRvbiBzaGFkb3cgYm94LiAqLwogICAgICAgIG1hcmdpbjogNHB4IDFweDsKICAgICAgfQoKICAgICAgLnRvZ2dsZS1sYWJlbCB7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwogICAgICAgIHBhZGRpbmctbGVmdDogdmFyKC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1sYWJlbC1zcGFjaW5nLCA4cHgpOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLWxhYmVsLWNvbG9yLCB2YXIoLS1wcmltYXJ5LXRleHQtY29sb3IpKTsKICAgICAgfQoKICAgICAgLyogaW52YWxpZCBzdGF0ZSAqLwogICAgICA6aG9zdChbaW52YWxpZF0pIC50b2dnbGUtYmFyIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLWludmFsaWQtYmFyLWNvbG9yLCB2YXIoLS1lcnJvci1jb2xvcikpOwogICAgICB9CgogICAgICA6aG9zdChbaW52YWxpZF0pIC50b2dnbGUtYnV0dG9uIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci10b2dnbGUtYnV0dG9uLWludmFsaWQtYnV0dG9uLWNvbG9yLCB2YXIoLS1lcnJvci1jb2xvcikpOwogICAgICB9CgogICAgICA6aG9zdChbaW52YWxpZF0pIC50b2dnbGUtaW5rIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1pbnZhbGlkLWluay1jb2xvciwgdmFyKC0tZXJyb3ItY29sb3IpKTsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8ZGl2IGNsYXNzPSJ0b2dnbGUtY29udGFpbmVyIj4KICAgICAgPGRpdiBpZD0idG9nZ2xlQmFyIiBjbGFzcz0idG9nZ2xlLWJhciI+PC9kaXY+CiAgICAgIDxkaXYgaWQ9InRvZ2dsZUJ1dHRvbiIgY2xhc3M9InRvZ2dsZS1idXR0b24iPjwvZGl2PgogICAgPC9kaXY+CgogICAgPGRpdiBjbGFzcz0idG9nZ2xlLWxhYmVsIj48c2xvdD48L3Nsb3Q+PC9kaXY+CgogIGA7CiAgICB0ZW1wbGF0ZSRpLnNldEF0dHJpYnV0ZSgnc3RyaXAtd2hpdGVzcGFjZScsICcnKTsKCiAgICAvKioKICAgIE1hdGVyaWFsIGRlc2lnbjogW1N3aXRjaF0oaHR0cHM6Ly93d3cuZ29vZ2xlLmNvbS9kZXNpZ24vc3BlYy9jb21wb25lbnRzL3NlbGVjdGlvbi1jb250cm9scy5odG1sI3NlbGVjdGlvbi1jb250cm9scy1zd2l0Y2gpCgogICAgYHBhcGVyLXRvZ2dsZS1idXR0b25gIHByb3ZpZGVzIGEgT04vT0ZGIHN3aXRjaCB0aGF0IHVzZXIgY2FuIHRvZ2dsZSB0aGUgc3RhdGUKICAgIGJ5IHRhcHBpbmcgb3IgYnkgZHJhZ2dpbmcgdGhlIHN3aXRjaC4KCiAgICBFeGFtcGxlOgoKICAgICAgICA8cGFwZXItdG9nZ2xlLWJ1dHRvbj48L3BhcGVyLXRvZ2dsZS1idXR0b24+CgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1iYXItY29sb3JgIHwgU2xpZGVyIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIG5vdCBjaGVja2VkIHwgYCMwMDAwMDBgCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1idXR0b24tY29sb3JgIHwgQnV0dG9uIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIG5vdCBjaGVja2VkIHwgYC0tcGFwZXItZ3JleS01MGAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24tdW5jaGVja2VkLWluay1jb2xvcmAgfCBTZWxlY3RlZC9mb2N1cyByaXBwbGUgY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBgLS1kYXJrLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLWNoZWNrZWQtYmFyLWNvbG9yYCB8IFNsaWRlciBidXR0b24gY29sb3Igd2hlbiB0aGUgaW5wdXQgaXMgY2hlY2tlZCB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLWNoZWNrZWQtYnV0dG9uLWNvbG9yYCB8IEJ1dHRvbiBjb2xvciB3aGVuIHRoZSBpbnB1dCBpcyBjaGVja2VkIHwgYC0tcHJpbWFyeS1jb2xvcmAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24tY2hlY2tlZC1pbmstY29sb3JgIHwgU2VsZWN0ZWQvZm9jdXMgcmlwcGxlIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGNoZWNrZWQgfCBgLS1wcmltYXJ5LWNvbG9yYAogICAgYC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1pbnZhbGlkLWJhci1jb2xvcmAgfCBTbGlkZXIgYnV0dG9uIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGludmFsaWQgfCBgLS1lcnJvci1jb2xvcmAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24taW52YWxpZC1idXR0b24tY29sb3JgIHwgQnV0dG9uIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGludmFsaWQgfCBgLS1lcnJvci1jb2xvcmAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24taW52YWxpZC1pbmstY29sb3JgIHwgU2VsZWN0ZWQvZm9jdXMgcmlwcGxlIGNvbG9yIHdoZW4gdGhlIGlucHV0IGlzIGludmFsaWQgfCBgLS1lcnJvci1jb2xvcmAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24tdW5jaGVja2VkLWJhcmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBzbGlkZXIgd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBge31gCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLXVuY2hlY2tlZC1idXR0b25gIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgc2xpZGVyIGJ1dHRvbiB3aGVuIHRoZSBpbnB1dCBpcyBub3QgY2hlY2tlZCB8IGB7fWAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24tdW5jaGVja2VkLWlua2AgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSByaXBwbGUgd2hlbiB0aGUgaW5wdXQgaXMgbm90IGNoZWNrZWQgfCBge31gCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLWNoZWNrZWQtYmFyYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHNsaWRlciB3aGVuIHRoZSBpbnB1dCBpcyBjaGVja2VkIHwgYHt9YAogICAgYC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1jaGVja2VkLWJ1dHRvbmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSBzbGlkZXIgYnV0dG9uIHdoZW4gdGhlIGlucHV0IGlzIGNoZWNrZWQgfCBge31gCiAgICBgLS1wYXBlci10b2dnbGUtYnV0dG9uLWNoZWNrZWQtaW5rYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHJpcHBsZSB3aGVuIHRoZSBpbnB1dCBpcyBjaGVja2VkIHwgYHt9YAogICAgYC0tcGFwZXItdG9nZ2xlLWJ1dHRvbi1sYWJlbC1jb2xvcmAgfCBMYWJlbCBjb2xvciB8IGAtLXByaW1hcnktdGV4dC1jb2xvcmAKICAgIGAtLXBhcGVyLXRvZ2dsZS1idXR0b24tbGFiZWwtc3BhY2luZ2AgfCBTcGFjaW5nIGJldHdlZW4gdGhlIGxhYmVsIGFuZCB0aGUgYnV0dG9uIHwgYDhweGAKCiAgICBUaGlzIGVsZW1lbnQgYXBwbGllcyB0aGUgbWl4aW4gYC0tcGFwZXItZm9udC1jb21tb24tYmFzZWAgYnV0IGRvZXMgbm90IGltcG9ydCBgcGFwZXItc3R5bGVzL3R5cG9ncmFwaHkuaHRtbGAuCiAgICBJbiBvcmRlciB0byBhcHBseSB0aGUgYFJvYm90b2AgZm9udCB0byB0aGlzIGVsZW1lbnQsIG1ha2Ugc3VyZSB5b3UndmUgaW1wb3J0ZWQgYHBhcGVyLXN0eWxlcy90eXBvZ3JhcGh5Lmh0bWxgLgoKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItdG9nZ2xlLWJ1dHRvbgogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogdGVtcGxhdGUkaSwKCiAgICAgIGlzOiAncGFwZXItdG9nZ2xlLWJ1dHRvbicsCgogICAgICBiZWhhdmlvcnM6IFtQYXBlckNoZWNrZWRFbGVtZW50QmVoYXZpb3JdLAoKICAgICAgLyoqIEBwcml2YXRlICovCiAgICAgIGhvc3RBdHRyaWJ1dGVzOiB7cm9sZTogJ2J1dHRvbicsICdhcmlhLXByZXNzZWQnOiAnZmFsc2UnLCB0YWJpbmRleDogMH0sCgogICAgICBwcm9wZXJ0aWVzOiB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEZpcmVkIHdoZW4gdGhlIGNoZWNrZWQgc3RhdGUgY2hhbmdlcyBkdWUgdG8gdXNlciBpbnRlcmFjdGlvbi4KICAgICAgICAgICAqCiAgICAgICAgICAgKiBAZXZlbnQgY2hhbmdlCiAgICAgICAgICAgKi8KICAgICAgICAgIC8qKgogICAgICAgICAgICogRmlyZWQgd2hlbiB0aGUgY2hlY2tlZCBzdGF0ZSBjaGFuZ2VzLgogICAgICAgICAgICoKICAgICAgICAgICAqIEBldmVudCBpcm9uLWNoYW5nZQogICAgICAgICAgICovCiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHt0cmFjazogJ19vbnRyYWNrJ30sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgYWZ0ZXJOZXh0UmVuZGVyKHRoaXMsIGZ1bmN0aW9uKCkgewogICAgICAgICAgc2V0VG91Y2hBY3Rpb24odGhpcywgJ3Bhbi15Jyk7CiAgICAgICAgfSk7CiAgICAgIH0sCgogICAgICBfb250cmFjazogZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgdHJhY2sgPSBldmVudC5kZXRhaWw7CiAgICAgICAgaWYgKHRyYWNrLnN0YXRlID09PSAnc3RhcnQnKSB7CiAgICAgICAgICB0aGlzLl90cmFja1N0YXJ0KHRyYWNrKTsKICAgICAgICB9IGVsc2UgaWYgKHRyYWNrLnN0YXRlID09PSAndHJhY2snKSB7CiAgICAgICAgICB0aGlzLl90cmFja01vdmUodHJhY2spOwogICAgICAgIH0gZWxzZSBpZiAodHJhY2suc3RhdGUgPT09ICdlbmQnKSB7CiAgICAgICAgICB0aGlzLl90cmFja0VuZCh0cmFjayk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgX3RyYWNrU3RhcnQ6IGZ1bmN0aW9uKHRyYWNrKSB7CiAgICAgICAgdGhpcy5fd2lkdGggPSB0aGlzLiQudG9nZ2xlQmFyLm9mZnNldFdpZHRoIC8gMjsKICAgICAgICAvKgogICAgICAgICAqIGtlZXAgYW4gdHJhY2stb25seSBjaGVjayBzdGF0ZSB0byBrZWVwIHRoZSBkcmFnZ2luZyBiZWhhdmlvciBzbW9vdGgKICAgICAgICAgKiB3aGlsZSB0b2dnbGluZyBhY3RpdmF0aW9ucwogICAgICAgICAqLwogICAgICAgIHRoaXMuX3RyYWNrQ2hlY2tlZCA9IHRoaXMuY2hlY2tlZDsKICAgICAgICB0aGlzLiQudG9nZ2xlQnV0dG9uLmNsYXNzTGlzdC5hZGQoJ2RyYWdnaW5nJyk7CiAgICAgIH0sCgogICAgICBfdHJhY2tNb3ZlOiBmdW5jdGlvbih0cmFjaykgewogICAgICAgIHZhciBkeCA9IHRyYWNrLmR4OwogICAgICAgIHRoaXMuX3ggPSBNYXRoLm1pbigKICAgICAgICAgICAgdGhpcy5fd2lkdGgsIE1hdGgubWF4KDAsIHRoaXMuX3RyYWNrQ2hlY2tlZCA/IHRoaXMuX3dpZHRoICsgZHggOiBkeCkpOwogICAgICAgIHRoaXMudHJhbnNsYXRlM2QodGhpcy5feCArICdweCcsIDAsIDAsIHRoaXMuJC50b2dnbGVCdXR0b24pOwogICAgICAgIHRoaXMuX3VzZXJBY3RpdmF0ZSh0aGlzLl94ID4gKHRoaXMuX3dpZHRoIC8gMikpOwogICAgICB9LAoKICAgICAgX3RyYWNrRW5kOiBmdW5jdGlvbih0cmFjaykgewogICAgICAgIHRoaXMuJC50b2dnbGVCdXR0b24uY2xhc3NMaXN0LnJlbW92ZSgnZHJhZ2dpbmcnKTsKICAgICAgICB0aGlzLnRyYW5zZm9ybSgnJywgdGhpcy4kLnRvZ2dsZUJ1dHRvbik7CiAgICAgIH0sCgogICAgICAvLyBjdXN0b21pemUgdGhlIGVsZW1lbnQncyByaXBwbGUKICAgICAgX2NyZWF0ZVJpcHBsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcmlwcGxlQ29udGFpbmVyID0gdGhpcy4kLnRvZ2dsZUJ1dHRvbjsKICAgICAgICB2YXIgcmlwcGxlID0gUGFwZXJSaXBwbGVCZWhhdmlvci5fY3JlYXRlUmlwcGxlKCk7CiAgICAgICAgcmlwcGxlLmlkID0gJ2luayc7CiAgICAgICAgcmlwcGxlLnNldEF0dHJpYnV0ZSgncmVjZW50ZXJzJywgJycpOwogICAgICAgIHJpcHBsZS5jbGFzc0xpc3QuYWRkKCdjaXJjbGUnLCAndG9nZ2xlLWluaycpOwogICAgICAgIHJldHVybiByaXBwbGU7CiAgICAgIH0KCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTUgVGhlIFBvbHltZXIgUHJvamVjdCBBdXRob3JzLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgVGhpcyBjb2RlIG1heSBvbmx5IGJlIHVzZWQgdW5kZXIgdGhlIEJTRCBzdHlsZSBsaWNlbnNlIGZvdW5kIGF0CiAgICBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQgVGhlIGNvbXBsZXRlIHNldCBvZiBhdXRob3JzIG1heSBiZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgY29udHJpYnV0b3JzIG1heSBiZQogICAgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQgQ29kZSBkaXN0cmlidXRlZCBieSBHb29nbGUgYXMKICAgIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvIHN1YmplY3QgdG8gYW4gYWRkaXRpb25hbCBJUCByaWdodHMgZ3JhbnQKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KCiAgICAvKioKICAgICoqVGhpcyBlbGVtZW50IGhhcyBiZWVuIGRlcHJlY2F0ZWQgaW4gZmF2b3Igb2YKICAgIFthcHAtbGF5b3V0XShodHRwczovL2dpdGh1Yi5jb20vUG9seW1lckVsZW1lbnRzL2FwcC1sYXlvdXQpLioqCgogICAgTWF0ZXJpYWwgZGVzaWduOgogICAgW1Rvb2xiYXJzXShodHRwczovL3d3dy5nb29nbGUuY29tL2Rlc2lnbi9zcGVjL2NvbXBvbmVudHMvdG9vbGJhcnMuaHRtbCkKCiAgICBgcGFwZXItdG9vbGJhcmAgaXMgYSBob3Jpem9udGFsIGJhciBjb250YWluaW5nIGl0ZW1zIHRoYXQgY2FuIGJlIHVzZWQgZm9yCiAgICBsYWJlbCwgbmF2aWdhdGlvbiwgc2VhcmNoIGFuZCBhY3Rpb25zLiAgVGhlIGl0ZW1zIHBsYWNlZCBpbnNpZGUgdGhlCiAgICBgcGFwZXItdG9vbGJhcmAgYXJlIHByb2plY3RlZCBpbnRvIGEgYGNsYXNzPSJob3Jpem9udGFsIGNlbnRlciBsYXlvdXQiYAogICAgY29udGFpbmVyIGluc2lkZSBvZiBgcGFwZXItdG9vbGJhcmAncyBTaGFkb3cgRE9NLiAgWW91IGNhbiB1c2UgZmxleCBhdHRyaWJ1dGVzCiAgICB0byBjb250cm9sIHRoZSBpdGVtcycgc2l6aW5nLgoKICAgIEV4YW1wbGU6CgogICAgYGBgaHRtbAogICAgPHBhcGVyLXRvb2xiYXI+CiAgICAgIDxwYXBlci1pY29uLWJ1dHRvbiBzbG90PSJ0b3AiIGljb249Im1lbnUiCiAgICBvbi10YXA9Im1lbnVBY3Rpb24iPjwvcGFwZXItaWNvbi1idXR0b24+IDxkaXYgc2xvdD0idG9wIgogICAgY2xhc3M9InRpdGxlIj5UaXRsZTwvZGl2PiA8cGFwZXItaWNvbi1idXR0b24gc2xvdD0idG9wIiBpY29uPSJtb3JlLXZlcnQiCiAgICBvbi10YXA9Im1vcmVBY3Rpb24iPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICA8L3BhcGVyLXRvb2xiYXI+CiAgICBgYGAKCiAgICBgcGFwZXItdG9vbGJhcmAgaGFzIGEgc3RhbmRhcmQgaGVpZ2h0LCBidXQgY2FuIG1hZGUgYmUgdGFsbGVyIGJ5IHNldHRpbmcgYHRhbGxgCiAgICBjbGFzcyBvbiB0aGUgYHBhcGVyLXRvb2xiYXJgLiBUaGlzIHdpbGwgbWFrZSB0aGUgdG9vbGJhciAzeCB0aGUgbm9ybWFsIGhlaWdodC4KCiAgICBgYGBodG1sCiAgICA8cGFwZXItdG9vbGJhciBjbGFzcz0idGFsbCI+CiAgICAgIDxwYXBlci1pY29uLWJ1dHRvbiBzbG90PSJ0b3AiIGljb249Im1lbnUiPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICA8L3BhcGVyLXRvb2xiYXI+CiAgICBgYGAKCiAgICBBcHBseSBgbWVkaXVtLXRhbGxgIGNsYXNzIHRvIG1ha2UgdGhlIHRvb2xiYXIgbWVkaXVtIHRhbGwuICBUaGlzIHdpbGwgbWFrZSB0aGUKICAgIHRvb2xiYXIgMnggdGhlIG5vcm1hbCBoZWlnaHQuCgogICAgYGBgaHRtbAogICAgPHBhcGVyLXRvb2xiYXIgY2xhc3M9Im1lZGl1bS10YWxsIj4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uIHNsb3Q9InRvcCIgaWNvbj0ibWVudSI+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgIDwvcGFwZXItdG9vbGJhcj4KICAgIGBgYAoKICAgIFdoZW4gYHRhbGxgLCBpdGVtcyBjYW4gcGluIHRvIGVpdGhlciB0aGUgdG9wIChkZWZhdWx0KSwgbWlkZGxlIG9yIGJvdHRvbS4gVXNlCiAgICBgbWlkZGxlYCBzbG90IGZvciBtaWRkbGUgY29udGVudCBhbmQgYGJvdHRvbWAgc2xvdCBmb3IgYm90dG9tIGNvbnRlbnQuCgogICAgYGBgaHRtbAogICAgPHBhcGVyLXRvb2xiYXIgY2xhc3M9InRhbGwiPgogICAgICA8cGFwZXItaWNvbi1idXR0b24gc2xvdD0idG9wIiBpY29uPSJtZW51Ij48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICA8ZGl2IHNsb3Q9Im1pZGRsZSIgY2xhc3M9InRpdGxlIj5NaWRkbGUgVGl0bGU8L2Rpdj4KICAgICAgPGRpdiBzbG90PSJib3R0b20iIGNsYXNzPSJ0aXRsZSI+Qm90dG9tIFRpdGxlPC9kaXY+CiAgICA8L3BhcGVyLXRvb2xiYXI+CiAgICBgYGAKCiAgICBGb3IgYG1lZGl1bS10YWxsYCB0b29sYmFyLCB0aGUgbWlkZGxlIGFuZCBib3R0b20gY29udGVudHMgb3ZlcmxhcCBhbmQgYXJlCiAgICBwaW5uZWQgdG8gdGhlIGJvdHRvbS4gQnV0IGBtaWRkbGVKdXN0aWZ5YCBhbmQgYGJvdHRvbUp1c3RpZnlgIGF0dHJpYnV0ZXMgYXJlCiAgICBzdGlsbCBob25vcmVkIHNlcGFyYXRlbHkuCgogICAgVG8gbWFrZSBhbiBlbGVtZW50IGNvbXBsZXRlbHkgZml0IGF0IHRoZSBib3R0b20gb2YgdGhlIHRvb2xiYXIsIHVzZSBgZml0YCBhbG9uZwogICAgd2l0aCBgYm90dG9tYC4KCiAgICBgYGBodG1sCiAgICA8cGFwZXItdG9vbGJhciBjbGFzcz0idGFsbCI+CiAgICAgIDxkaXYgaWQ9InByb2dyZXNzQmFyIiBzbG90PSJib3R0b20iIGNsYXNzPSJmaXQiPjwvZGl2PgogICAgPC9wYXBlci10b29sYmFyPgogICAgYGBgCgogICAgV2hlbiBpbnNpZGUgYSBgcGFwZXItaGVhZGVyLXBhbmVsYCBlbGVtZW50IHdpdGggYG1vZGU9IndhdGVyZmFsbC10YWxsImAsCiAgICB0aGUgY2xhc3MgYC5hbmltYXRlYCBpcyB0b2dnbGVkIHRvIGFuaW1hdGUgdGhlIGhlaWdodCBjaGFuZ2UgaW4gdGhlIHRvb2xiYXIuCgogICAgIyMjIFN0eWxpbmcKCiAgICBUaGUgZm9sbG93aW5nIGN1c3RvbSBwcm9wZXJ0aWVzIGFuZCBtaXhpbnMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKCiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci10b29sYmFyLXRpdGxlYCAgICAgIHwgTWl4aW4gYXBwbGllZCB0byB0aGUgdGl0bGUgb2YgdGhlIHRvb2xiYXIgfCBge31gCiAgICBgLS1wYXBlci10b29sYmFyLWJhY2tncm91bmRgIHwgVG9vbGJhciBiYWNrZ3JvdW5kIGNvbG9yICAgICB8IGAtLXByaW1hcnktY29sb3JgCiAgICBgLS1wYXBlci10b29sYmFyLWNvbG9yYCAgICAgIHwgVG9vbGJhciBmb3JlZ3JvdW5kIGNvbG9yICAgICB8IGAtLWRhcmstdGhlbWUtdGV4dC1jb2xvcmAKICAgIGAtLXBhcGVyLXRvb2xiYXItaGVpZ2h0YCAgICAgfCBDdXN0b20gaGVpZ2h0IGZvciB0b29sYmFyICAgIHwgYDY0cHhgCiAgICBgLS1wYXBlci10b29sYmFyLXNtLWhlaWdodGAgIHwgQ3VzdG9tIGhlaWdodCBmb3Igc21hbGwgc2NyZWVuIHRvb2xiYXIgfCBgNTZweGAKICAgIGAtLXBhcGVyLXRvb2xiYXJgICAgICAgICAgICAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB0b29sYmFyIHwgYHt9YAogICAgYC0tcGFwZXItdG9vbGJhci1jb250ZW50YCAgICB8IE1peGluIGFwcGxpZWQgdG8gdGhlIGNvbnRlbnQgc2VjdGlvbiBvZiB0aGUgdG9vbGJhciB8IGB7fWAKICAgIGAtLXBhcGVyLXRvb2xiYXItbWVkaXVtYCAgICAgfCBNaXhpbiBhcHBsaWVkIHRvIG1lZGl1bSBoZWlnaHQgdG9vbGJhciB8IGB7fWAKICAgIGAtLXBhcGVyLXRvb2xiYXItdGFsbGAgICAgICAgfCBNaXhpbiBhcHBsaWVkIHRvIHRhbGwgaGVpZ2h0IHRvb2xiYXIgfCBge31gCiAgICBgLS1wYXBlci10b29sYmFyLXRyYW5zaXRpb25gIHwgVHJhbnNpdGlvbiBhcHBsaWVkIHRvIHRoZSBgLmFuaW1hdGVgIGNsYXNzIHwgYGhlaWdodCAwLjE4cyBlYXNlLWluYAoKICAgICMjIyBBY2Nlc3NpYmlsaXR5CgogICAgYDxwYXBlci10b29sYmFyPmAgaGFzIGByb2xlPSJ0b29sYmFyImAgYnkgZGVmYXVsdC4gQW55IGVsZW1lbnRzIHdpdGggdGhlIGNsYXNzCiAgICBgdGl0bGVgIHdpbGwgYmUgdXNlZCBhcyB0aGUgbGFiZWwgb2YgdGhlIHRvb2xiYXIgdmlhIGBhcmlhLWxhYmVsbGVkYnlgLgoKICAgICMjIyBCcmVha2luZyBjaGFuZ2UgaW4gMi4wCgogICAgKiBJbiBQb2x5bWVyIDEueCwgZGVmYXVsdCBjb250ZW50IHVzZWQgdG8gYmUgZGlzdHJpYnVpdGVkIGF1dG9tYXRpY2FsbHkgdG8gdGhlCiAgICB0b3AgdG9vbGJhci4gSW4gdjIsIHRoZSB5b3UgbXVzdCBzZXQgYHNsb3Q9InRvcCJgIG9uIHRoZSBkZWZhdWx0IGNvbnRlbnQgdG8KICAgIGRpc3RyaWJ1aXRlIHRoZSBjb250ZW50IHRvIHRoZSB0b3AgdG9vbGJhci4KCiAgICBAZGVtbyBkZW1vL2luZGV4Lmh0bWwKICAgICovCiAgICBQb2x5bWVyKHsKICAgICAgX3RlbXBsYXRlOiBodG1sYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgLS1jYWxjdWxhdGVkLXBhcGVyLXRvb2xiYXItaGVpZ2h0OiB2YXIoLS1wYXBlci10b29sYmFyLWhlaWdodCwgNjRweCk7CiAgICAgICAgLS1jYWxjdWxhdGVkLXBhcGVyLXRvb2xiYXItc20taGVpZ2h0OiB2YXIoLS1wYXBlci10b29sYmFyLXNtLWhlaWdodCwgNTZweCk7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgLW1vei1ib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgIGhlaWdodDogdmFyKC0tY2FsY3VsYXRlZC1wYXBlci10b29sYmFyLWhlaWdodCk7CiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tcGFwZXItdG9vbGJhci1iYWNrZ3JvdW5kLCB2YXIoLS1wcmltYXJ5LWNvbG9yKSk7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXRvb2xiYXItY29sb3IsIHZhcigtLWRhcmstdGhlbWUtdGV4dC1jb2xvcikpOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2xiYXI7CiAgICAgIH0KCiAgICAgIDpob3N0KC5hbmltYXRlKSB7CiAgICAgICAgdHJhbnNpdGlvbjogdmFyKC0tcGFwZXItdG9vbGJhci10cmFuc2l0aW9uLCBoZWlnaHQgMC4xOHMgZWFzZS1pbik7CiAgICAgIH0KCiAgICAgIDpob3N0KC5tZWRpdW0tdGFsbCkgewogICAgICAgIGhlaWdodDogY2FsYyh2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLXRvb2xiYXItaGVpZ2h0KSAqIDIpOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2xiYXItbWVkaXVtOwogICAgICB9CgogICAgICA6aG9zdCgudGFsbCkgewogICAgICAgIGhlaWdodDogY2FsYyh2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLXRvb2xiYXItaGVpZ2h0KSAqIDMpOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2xiYXItdGFsbDsKICAgICAgfQoKICAgICAgLnRvb2xiYXItdG9vbHMgewogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBoZWlnaHQ6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItdG9vbGJhci1oZWlnaHQpOwogICAgICAgIHBhZGRpbmc6IDAgMTZweDsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtaG9yaXpvbnRhbDsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2xiYXItY29udGVudDsKICAgICAgfQoKICAgICAgLyoKICAgICAgICogVE9ETzogV2hlcmUgc2hvdWxkIG1lZGlhIHF1ZXJ5IGJyZWFrcG9pbnRzIGxpdmUgc28gdGhleSBjYW4gYmUgc2hhcmVkIGJldHdlZW4gZWxlbWVudHM/CiAgICAgICAqLwoKICAgICAgQG1lZGlhIChtYXgtd2lkdGg6IDYwMHB4KSB7CiAgICAgICAgOmhvc3QgewogICAgICAgICAgaGVpZ2h0OiB2YXIoLS1jYWxjdWxhdGVkLXBhcGVyLXRvb2xiYXItc20taGVpZ2h0KTsKICAgICAgICB9CgogICAgICAgIDpob3N0KC5tZWRpdW0tdGFsbCkgewogICAgICAgICAgaGVpZ2h0OiBjYWxjKHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItdG9vbGJhci1zbS1oZWlnaHQpICogMik7CiAgICAgICAgfQoKICAgICAgICA6aG9zdCgudGFsbCkgewogICAgICAgICAgaGVpZ2h0OiBjYWxjKHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItdG9vbGJhci1zbS1oZWlnaHQpICogMyk7CiAgICAgICAgfQoKICAgICAgICAudG9vbGJhci10b29scyB7CiAgICAgICAgICBoZWlnaHQ6IHZhcigtLWNhbGN1bGF0ZWQtcGFwZXItdG9vbGJhci1zbS1oZWlnaHQpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgI3RvcEJhciB7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CgogICAgICAvKiBtaWRkbGUgYmFyICovCiAgICAgICNtaWRkbGVCYXIgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgfQoKICAgICAgOmhvc3QoLnRhbGwpICNtaWRkbGVCYXIsCiAgICAgIDpob3N0KC5tZWRpdW0tdGFsbCkgI21pZGRsZUJhciB7CiAgICAgICAgLXdlYmtpdC10cmFuc2Zvcm06IHRyYW5zbGF0ZVkoMTAwJSk7CiAgICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKDEwMCUpOwogICAgICB9CgogICAgICAvKiBib3R0b20gYmFyICovCiAgICAgICNib3R0b21CYXIgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICByaWdodDogMDsKICAgICAgICBib3R0b206IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgfQoKICAgICAgLyoKICAgICAgICogbWFrZSBlbGVtZW50cyAoZS5nLiBidXR0b25zKSByZXNwb25kIHRvIG1vdXNlL3RvdWNoIGV2ZW50cwogICAgICAgKgogICAgICAgKiBcYC50b29sYmFyLXRvb2xzXGAgZGlzYWJsZXMgdG91Y2ggZXZlbnRzIHNvIG11bHRpcGxlIHRvb2xiYXJzIGNhbiBzdGFjayBhbmQgbm90CiAgICAgICAqIGFic29yYiBldmVudHMuIEFsbCBjaGlsZHJlbiBtdXN0IGhhdmUgcG9pbnRlciBldmVudHMgcmUtZW5hYmxlZCB0byB3b3JrIGFzCiAgICAgICAqIGV4cGVjdGVkLgogICAgICAgKi8KICAgICAgLnRvb2xiYXItdG9vbHMgPiA6OnNsb3R0ZWQoKjpub3QoW2Rpc2FibGVkXSkpIHsKICAgICAgICBwb2ludGVyLWV2ZW50czogYXV0bzsKICAgICAgfQoKICAgICAgLnRvb2xiYXItdG9vbHMgPiA6OnNsb3R0ZWQoLnRpdGxlKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItZm9udC1jb21tb24tYmFzZTsKICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgdGV4dC1vdmVyZmxvdzogZWxsaXBzaXM7CiAgICAgICAgZm9udC1zaXplOiAyMHB4OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgICAgbGluZS1oZWlnaHQ6IDE7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXg7CiAgICAgIH0KCiAgICAgIC50b29sYmFyLXRvb2xzID4gOjpzbG90dGVkKC50aXRsZSkgewogICAgICAgIG1hcmdpbi1sZWZ0OiA1NnB4OwogICAgICB9CgogICAgICAudG9vbGJhci10b29scyA+IDo6c2xvdHRlZChwYXBlci1pY29uLWJ1dHRvbiArIC50aXRsZSkgewogICAgICAgIG1hcmdpbi1sZWZ0OiAwOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVGhlIC0tcGFwZXItdG9vbGJhci10aXRsZSBtaXhpbiBpcyBhcHBsaWVkIGhlcmUgaW5zdGVhZCBvZiBhYm92ZSB0bwogICAgICAgKiBmaXggdGhlIGlzc3VlIHdpdGggbWFyZ2luLWxlZnQgYmVpbmcgaWdub3JlZCBkdWUgdG8gY3NzIG9yZGVyaW5nLgogICAgICAgKi8KICAgICAgLnRvb2xiYXItdG9vbHMgPiA6OnNsb3R0ZWQoLnRpdGxlKSB7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9vbGJhci10aXRsZTsKICAgICAgfQoKICAgICAgLnRvb2xiYXItdG9vbHMgPiA6OnNsb3R0ZWQocGFwZXItaWNvbi1idXR0b25baWNvbj1tZW51XSkgewogICAgICAgIG1hcmdpbi1yaWdodDogMjRweDsKICAgICAgfQoKICAgICAgLnRvb2xiYXItdG9vbHMgPiA6OnNsb3R0ZWQoLmZpdCkgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IGF1dG87CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgYm90dG9tOiAwOwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgd2lkdGg6IGF1dG87CiAgICAgICAgbWFyZ2luOiAwOwogICAgICB9CgogICAgICAvKiBUT0RPKG5vbXMpOiBVbnRpbCB3ZSBoYXZlIGEgYmV0dGVyIHNvbHV0aW9uIGZvciBjbGFzc2VzIHRoYXQgZG9uJ3QgdXNlCiAgICAgICAqIC9kZWVwLyBjcmVhdGUgb3VyIG93bi4KICAgICAgICovCiAgICAgIC5zdGFydC1qdXN0aWZpZWQgewogICAgICAgIEBhcHBseSAtLWxheW91dC1zdGFydC1qdXN0aWZpZWQ7CiAgICAgIH0KCiAgICAgIC5jZW50ZXItanVzdGlmaWVkIHsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtY2VudGVyLWp1c3RpZmllZDsKICAgICAgfQoKICAgICAgLmVuZC1qdXN0aWZpZWQgewogICAgICAgIEBhcHBseSAtLWxheW91dC1lbmQtanVzdGlmaWVkOwogICAgICB9CgogICAgICAuYXJvdW5kLWp1c3RpZmllZCB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWFyb3VuZC1qdXN0aWZpZWQ7CiAgICAgIH0KCiAgICAgIC5qdXN0aWZpZWQgewogICAgICAgIEBhcHBseSAtLWxheW91dC1qdXN0aWZpZWQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPGRpdiBpZD0idG9wQmFyIiBjbGFzc1wkPSJ0b29sYmFyLXRvb2xzIFtbX2NvbXB1dGVCYXJFeHRyYUNsYXNzZXMoanVzdGlmeSldXSI+CiAgICAgIDxzbG90IG5hbWU9InRvcCI+PC9zbG90PgogICAgPC9kaXY+CgogICAgPGRpdiBpZD0ibWlkZGxlQmFyIiBjbGFzc1wkPSJ0b29sYmFyLXRvb2xzIFtbX2NvbXB1dGVCYXJFeHRyYUNsYXNzZXMobWlkZGxlSnVzdGlmeSldXSI+CiAgICAgIDxzbG90IG5hbWU9Im1pZGRsZSI+PC9zbG90PgogICAgPC9kaXY+CgogICAgPGRpdiBpZD0iYm90dG9tQmFyIiBjbGFzc1wkPSJ0b29sYmFyLXRvb2xzIFtbX2NvbXB1dGVCYXJFeHRyYUNsYXNzZXMoYm90dG9tSnVzdGlmeSldXSI+CiAgICAgIDxzbG90IG5hbWU9ImJvdHRvbSI+PC9zbG90PgogICAgPC9kaXY+CmAsCgogICAgICBpczogJ3BhcGVyLXRvb2xiYXInLAogICAgICBob3N0QXR0cmlidXRlczogeydyb2xlJzogJ3Rvb2xiYXInfSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBDb250cm9scyBob3cgdGhlIGl0ZW1zIGFyZSBhbGlnbmVkIGhvcml6b250YWxseSB3aGVuIHRoZXkgYXJlIHBsYWNlZAogICAgICAgICAqIGF0IHRoZSBib3R0b20uCiAgICAgICAgICogT3B0aW9ucyBhcmUgYHN0YXJ0YCwgYGNlbnRlcmAsIGBlbmRgLCBganVzdGlmaWVkYCBhbmQgYGFyb3VuZGAuCiAgICAgICAgICovCiAgICAgICAgYm90dG9tSnVzdGlmeToge3R5cGU6IFN0cmluZywgdmFsdWU6ICcnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udHJvbHMgaG93IHRoZSBpdGVtcyBhcmUgYWxpZ25lZCBob3Jpem9udGFsbHkuCiAgICAgICAgICogT3B0aW9ucyBhcmUgYHN0YXJ0YCwgYGNlbnRlcmAsIGBlbmRgLCBganVzdGlmaWVkYCBhbmQgYGFyb3VuZGAuCiAgICAgICAgICovCiAgICAgICAganVzdGlmeToge3R5cGU6IFN0cmluZywgdmFsdWU6ICcnfSwKCiAgICAgICAgLyoqCiAgICAgICAgICogQ29udHJvbHMgaG93IHRoZSBpdGVtcyBhcmUgYWxpZ25lZCBob3Jpem9udGFsbHkgd2hlbiB0aGV5IGFyZSBwbGFjZWQKICAgICAgICAgKiBpbiB0aGUgbWlkZGxlLgogICAgICAgICAqIE9wdGlvbnMgYXJlIGBzdGFydGAsIGBjZW50ZXJgLCBgZW5kYCwgYGp1c3RpZmllZGAgYW5kIGBhcm91bmRgLgogICAgICAgICAqLwogICAgICAgIG1pZGRsZUp1c3RpZnk6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnJ30KCiAgICAgIH0sCgogICAgICByZWFkeTogZnVuY3Rpb24oKSB7CiAgICAgICAgY29uc29sZS53YXJuKHRoaXMuaXMsICdpcyBkZXByZWNhdGVkLiBQbGVhc2UgdXNlIGFwcC1sYXlvdXQgaW5zdGVhZCEnKTsKICAgICAgfSwKCiAgICAgIGF0dGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9vYnNlcnZlciA9IHRoaXMuX29ic2VydmUodGhpcyk7CiAgICAgICAgdGhpcy5fdXBkYXRlQXJpYUxhYmVsbGVkQnkoKTsKICAgICAgfSwKCiAgICAgIGRldGFjaGVkOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fb2JzZXJ2ZXIpIHsKICAgICAgICAgIHRoaXMuX29ic2VydmVyLmRpc2Nvbm5lY3QoKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfb2JzZXJ2ZTogZnVuY3Rpb24obm9kZSkgewogICAgICAgIHZhciBvYnNlcnZlciA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKGZ1bmN0aW9uKCkgewogICAgICAgICAgdGhpcy5fdXBkYXRlQXJpYUxhYmVsbGVkQnkoKTsKICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICAgIG9ic2VydmVyLm9ic2VydmUobm9kZSwge2NoaWxkTGlzdDogdHJ1ZSwgc3VidHJlZTogdHJ1ZX0pOwogICAgICAgIHJldHVybiBvYnNlcnZlcjsKICAgICAgfSwKCiAgICAgIF91cGRhdGVBcmlhTGFiZWxsZWRCeTogZnVuY3Rpb24oKSB7CiAgICAgICAgZmx1c2goKTsKICAgICAgICB2YXIgbGFiZWxsZWRCeSA9IFtdOwogICAgICAgIHZhciBjb250ZW50cyA9CiAgICAgICAgICAgIEFycmF5LnByb3RvdHlwZS5zbGljZS5jYWxsKGRvbSh0aGlzLnJvb3QpLnF1ZXJ5U2VsZWN0b3JBbGwoJ3Nsb3QnKSkKICAgICAgICAgICAgICAgIC5jb25jYXQoQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwoCiAgICAgICAgICAgICAgICAgICAgZG9tKHRoaXMucm9vdCkucXVlcnlTZWxlY3RvckFsbCgnY29udGVudCcpKSk7CgogICAgICAgIGZvciAodmFyIGNvbnRlbnQsIGluZGV4ID0gMDsgY29udGVudCA9IGNvbnRlbnRzW2luZGV4XTsgaW5kZXgrKykgewogICAgICAgICAgdmFyIG5vZGVzID0gZG9tKGNvbnRlbnQpLmdldERpc3RyaWJ1dGVkTm9kZXMoKTsKICAgICAgICAgIGZvciAodmFyIG5vZGUsIGpuZGV4ID0gMDsgbm9kZSA9IG5vZGVzW2puZGV4XTsgam5kZXgrKykgewogICAgICAgICAgICBpZiAobm9kZS5jbGFzc0xpc3QgJiYgbm9kZS5jbGFzc0xpc3QuY29udGFpbnMoJ3RpdGxlJykpIHsKICAgICAgICAgICAgICBpZiAobm9kZS5pZCkgewogICAgICAgICAgICAgICAgbGFiZWxsZWRCeS5wdXNoKG5vZGUuaWQpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICB2YXIgaWQgPSAncGFwZXItdG9vbGJhci1sYWJlbC0nICsgTWF0aC5mbG9vcihNYXRoLnJhbmRvbSgpICogMTAwMDApOwogICAgICAgICAgICAgICAgbm9kZS5pZCA9IGlkOwogICAgICAgICAgICAgICAgbGFiZWxsZWRCeS5wdXNoKGlkKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKGxhYmVsbGVkQnkubGVuZ3RoID4gMCkgewogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtbGFiZWxsZWRieScsIGxhYmVsbGVkQnkuam9pbignICcpKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfY29tcHV0ZUJhckV4dHJhQ2xhc3NlczogZnVuY3Rpb24oYmFySnVzdGlmeSkgewogICAgICAgIGlmICghYmFySnVzdGlmeSkKICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICByZXR1cm4gYmFySnVzdGlmeSArIChiYXJKdXN0aWZ5ID09PSAnanVzdGlmaWVkJyA/ICcnIDogJy1qdXN0aWZpZWQnKTsKICAgICAgfQogICAgfSk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE1IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdAogICAgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0xJQ0VOU0UudHh0IFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQKICAgIGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9BVVRIT1JTLnR4dCBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUKICAgIGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9DT05UUklCVVRPUlMudHh0IENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzCiAgICBwYXJ0IG9mIHRoZSBwb2x5bWVyIHByb2plY3QgaXMgYWxzbyBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50CiAgICBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vUEFURU5UUy50eHQKICAgICovCgogICAgLyoqCiAgICBNYXRlcmlhbCBkZXNpZ246CiAgICBbVG9vbHRpcHNdKGh0dHBzOi8vd3d3Lmdvb2dsZS5jb20vZGVzaWduL3NwZWMvY29tcG9uZW50cy90b29sdGlwcy5odG1sKQogICAgYDxwYXBlci10b29sdGlwPmAgaXMgYSBsYWJlbCB0aGF0IGFwcGVhcnMgb24gaG92ZXIgYW5kIGZvY3VzIHdoZW4gdGhlIHVzZXIKICAgIGhvdmVycyBvdmVyIGFuIGVsZW1lbnQgd2l0aCB0aGUgY3Vyc29yIG9yIHdpdGggdGhlIGtleWJvYXJkLiBJdCB3aWxsIGJlIGNlbnRlcmVkCiAgICB0byBhbiBhbmNob3IgZWxlbWVudCBzcGVjaWZpZWQgaW4gdGhlIGBmb3JgIGF0dHJpYnV0ZSwgb3IsIGlmIHRoYXQgZG9lc24ndAogICAgZXhpc3QsIGNlbnRlcmVkIHRvIHRoZSBwYXJlbnQgbm9kZSBjb250YWluaW5nIGl0LgogICAgRXhhbXBsZToKICAgICAgICA8ZGl2IHN0eWxlPSJkaXNwbGF5OmlubGluZS1ibG9jayI+CiAgICAgICAgICA8YnV0dG9uPkNsaWNrIG1lITwvYnV0dG9uPgogICAgICAgICAgPHBhcGVyLXRvb2x0aXA+VG9vbHRpcCB0ZXh0PC9wYXBlci10b29sdGlwPgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXY+CiAgICAgICAgICA8YnV0dG9uIGlkPSJidG4iPkNsaWNrIG1lITwvYnV0dG9uPgogICAgICAgICAgPHBhcGVyLXRvb2x0aXAgZm9yPSJidG4iPlRvb2x0aXAgdGV4dDwvcGFwZXItdG9vbHRpcD4KICAgICAgICA8L2Rpdj4KICAgIFRoZSB0b29sdGlwIGNhbiBiZSBwb3NpdGlvbmVkIG9uIHRoZSB0b3B8Ym90dG9tfGxlZnR8cmlnaHQgb2YgdGhlIGFuY2hvciB1c2luZwogICAgdGhlIGBwb3NpdGlvbmAgYXR0cmlidXRlLiBUaGUgZGVmYXVsdCBwb3NpdGlvbiBpcyBib3R0b20uCiAgICAgICAgPHBhcGVyLXRvb2x0aXAgZm9yPSJidG4iIHBvc2l0aW9uPSJsZWZ0Ij5Ub29sdGlwIHRleHQ8L3BhcGVyLXRvb2x0aXA+CiAgICAgICAgPHBhcGVyLXRvb2x0aXAgZm9yPSJidG4iIHBvc2l0aW9uPSJ0b3AiPlRvb2x0aXAgdGV4dDwvcGFwZXItdG9vbHRpcD4KCiAgICAjIyMgU3R5bGluZwogICAgVGhlIGZvbGxvd2luZyBjdXN0b20gcHJvcGVydGllcyBhbmQgbWl4aW5zIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CiAgICBDdXN0b20gcHJvcGVydHkgfCBEZXNjcmlwdGlvbiB8IERlZmF1bHQKICAgIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tCiAgICBgLS1wYXBlci10b29sdGlwLWJhY2tncm91bmRgIHwgVGhlIGJhY2tncm91bmQgY29sb3Igb2YgdGhlIHRvb2x0aXAgfCBgIzYxNjE2MWAKICAgIGAtLXBhcGVyLXRvb2x0aXAtb3BhY2l0eWAgfCBUaGUgb3BhY2l0eSBvZiB0aGUgdG9vbHRpcCB8IGAwLjlgCiAgICBgLS1wYXBlci10b29sdGlwLXRleHQtY29sb3JgIHwgVGhlIHRleHQgY29sb3Igb2YgdGhlIHRvb2x0aXAgfCBgd2hpdGVgCiAgICBgLS1wYXBlci10b29sdGlwYCB8IE1peGluIGFwcGxpZWQgdG8gdGhlIHRvb2x0aXAgfCBge31gCiAgICBgLS1wYXBlci10b29sdGlwLWRlbGF5LWluYCB8IERlbGF5IGJlZm9yZSB0b29sdGlwIHN0YXJ0cyB0byBmYWRlIGluIHwgYDUwMGAKICAgIGAtLXBhcGVyLXRvb2x0aXAtZGVsYXktb3V0YCB8IERlbGF5IGJlZm9yZSB0b29sdGlwIHN0YXJ0cyB0byBmYWRlIG91dCB8IGAwYAogICAgYC0tcGFwZXItdG9vbHRpcC1kdXJhdGlvbi1pbmAgfCBUaW1pbmcgZm9yIGFuaW1hdGlvbiB3aGVuIHNob3dpbmcgdG9vbHRpcCB8IGA1MDBgCiAgICBgLS1wYXBlci10b29sdGlwLWR1cmF0aW9uLW91dGAgfCBUaW1pbmcgZm9yIGFuaW1hdGlvbiB3aGVuIGhpZGluZyB0b29sdGlwIHwgYDBgCiAgICBgLS1wYXBlci10b29sdGlwLWFuaW1hdGlvbmAgfCBNaXhpbiBhcHBsaWVkIHRvIHRoZSB0b29sdGlwIGFuaW1hdGlvbiB8IGB7fWAKICAgIEBncm91cCBQYXBlciBFbGVtZW50cwogICAgQGVsZW1lbnQgcGFwZXItdG9vbHRpcAogICAgQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAqLwogICAgUG9seW1lcih7CiAgICAgIF90ZW1wbGF0ZTogaHRtbGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICBvdXRsaW5lOiBub25lOwogICAgICAgIHotaW5kZXg6IDEwMDI7CiAgICAgICAgLW1vei11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICB1c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICBjdXJzb3I6IGRlZmF1bHQ7CiAgICAgIH0KCiAgICAgICN0b29sdGlwIHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBvdXRsaW5lOiBub25lOwogICAgICAgIEBhcHBseSAtLXBhcGVyLWZvbnQtY29tbW9uLWJhc2U7CiAgICAgICAgZm9udC1zaXplOiAxMHB4OwogICAgICAgIGxpbmUtaGVpZ2h0OiAxOwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXBhcGVyLXRvb2x0aXAtYmFja2dyb3VuZCwgIzYxNjE2MSk7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLXRvb2x0aXAtdGV4dC1jb2xvciwgd2hpdGUpOwogICAgICAgIHBhZGRpbmc6IDhweDsKICAgICAgICBib3JkZXItcmFkaXVzOiAycHg7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9vbHRpcDsKICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBrZXlGcmFtZVNjYWxlVXAgewogICAgICAgIDAlIHsKICAgICAgICAgIHRyYW5zZm9ybTogc2NhbGUoMC4wKTsKICAgICAgICB9CiAgICAgICAgMTAwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHNjYWxlKDEuMCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBAa2V5ZnJhbWVzIGtleUZyYW1lU2NhbGVEb3duIHsKICAgICAgICAwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHNjYWxlKDEuMCk7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgdHJhbnNmb3JtOiBzY2FsZSgwLjApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBrZXlGcmFtZUZhZGVJbk9wYWNpdHkgewogICAgICAgIDAlIHsKICAgICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgb3BhY2l0eTogdmFyKC0tcGFwZXItdG9vbHRpcC1vcGFjaXR5LCAwLjkpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgQGtleWZyYW1lcyBrZXlGcmFtZUZhZGVPdXRPcGFjaXR5IHsKICAgICAgICAwJSB7CiAgICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIEBrZXlmcmFtZXMga2V5RnJhbWVTbGlkZURvd25JbiB7CiAgICAgICAgMCUgewogICAgICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC0yMDAwcHgpOwogICAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICB9CiAgICAgICAgMTAlIHsKICAgICAgICAgIG9wYWNpdHk6IDAuMjsKICAgICAgICB9CiAgICAgICAgMTAwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoMCk7CiAgICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBAa2V5ZnJhbWVzIGtleUZyYW1lU2xpZGVEb3duT3V0IHsKICAgICAgICAwJSB7CiAgICAgICAgICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoMCk7CiAgICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgfQogICAgICAgIDEwJSB7CiAgICAgICAgICBvcGFjaXR5OiAwLjI7CiAgICAgICAgfQogICAgICAgIDEwMCUgewogICAgICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC0yMDAwcHgpOwogICAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC5mYWRlLWluLWFuaW1hdGlvbiB7CiAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICBhbmltYXRpb24tZGVsYXk6IHZhcigtLXBhcGVyLXRvb2x0aXAtZGVsYXktaW4sIDUwMG1zKTsKICAgICAgICBhbmltYXRpb24tbmFtZToga2V5RnJhbWVGYWRlSW5PcGFjaXR5OwogICAgICAgIGFuaW1hdGlvbi1pdGVyYXRpb24tY291bnQ6IDE7CiAgICAgICAgYW5pbWF0aW9uLXRpbWluZy1mdW5jdGlvbjogZWFzZS1pbjsKICAgICAgICBhbmltYXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLXRvb2x0aXAtZHVyYXRpb24taW4sIDUwMG1zKTsKICAgICAgICBhbmltYXRpb24tZmlsbC1tb2RlOiBmb3J3YXJkczsKICAgICAgICBAYXBwbHkgLS1wYXBlci10b29sdGlwLWFuaW1hdGlvbjsKICAgICAgfQoKICAgICAgLmZhZGUtb3V0LWFuaW1hdGlvbiB7CiAgICAgICAgb3BhY2l0eTogdmFyKC0tcGFwZXItdG9vbHRpcC1vcGFjaXR5LCAwLjkpOwogICAgICAgIGFuaW1hdGlvbi1kZWxheTogdmFyKC0tcGFwZXItdG9vbHRpcC1kZWxheS1vdXQsIDBtcyk7CiAgICAgICAgYW5pbWF0aW9uLW5hbWU6IGtleUZyYW1lRmFkZU91dE9wYWNpdHk7CiAgICAgICAgYW5pbWF0aW9uLWl0ZXJhdGlvbi1jb3VudDogMTsKICAgICAgICBhbmltYXRpb24tdGltaW5nLWZ1bmN0aW9uOiBlYXNlLWluOwogICAgICAgIGFuaW1hdGlvbi1kdXJhdGlvbjogdmFyKC0tcGFwZXItdG9vbHRpcC1kdXJhdGlvbi1vdXQsIDUwMG1zKTsKICAgICAgICBhbmltYXRpb24tZmlsbC1tb2RlOiBmb3J3YXJkczsKICAgICAgICBAYXBwbHkgLS1wYXBlci10b29sdGlwLWFuaW1hdGlvbjsKICAgICAgfQoKICAgICAgLnNjYWxlLXVwLWFuaW1hdGlvbiB7CiAgICAgICAgdHJhbnNmb3JtOiBzY2FsZSgwKTsKICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiB2YXIoLS1wYXBlci10b29sdGlwLWRlbGF5LWluLCA1MDBtcyk7CiAgICAgICAgYW5pbWF0aW9uLW5hbWU6IGtleUZyYW1lU2NhbGVVcDsKICAgICAgICBhbmltYXRpb24taXRlcmF0aW9uLWNvdW50OiAxOwogICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGVhc2UtaW47CiAgICAgICAgYW5pbWF0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci10b29sdGlwLWR1cmF0aW9uLWluLCA1MDBtcyk7CiAgICAgICAgYW5pbWF0aW9uLWZpbGwtbW9kZTogZm9yd2FyZHM7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9vbHRpcC1hbmltYXRpb247CiAgICAgIH0KCiAgICAgIC5zY2FsZS1kb3duLWFuaW1hdGlvbiB7CiAgICAgICAgdHJhbnNmb3JtOiBzY2FsZSgxKTsKICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiB2YXIoLS1wYXBlci10b29sdGlwLWRlbGF5LW91dCwgNTAwbXMpOwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBrZXlGcmFtZVNjYWxlRG93bjsKICAgICAgICBhbmltYXRpb24taXRlcmF0aW9uLWNvdW50OiAxOwogICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGVhc2UtaW47CiAgICAgICAgYW5pbWF0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci10b29sdGlwLWR1cmF0aW9uLW91dCwgNTAwbXMpOwogICAgICAgIGFuaW1hdGlvbi1maWxsLW1vZGU6IGZvcndhcmRzOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2x0aXAtYW5pbWF0aW9uOwogICAgICB9CgogICAgICAuc2xpZGUtZG93bi1hbmltYXRpb24gewogICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgtMjAwMHB4KTsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICAgIGFuaW1hdGlvbi1kZWxheTogdmFyKC0tcGFwZXItdG9vbHRpcC1kZWxheS1vdXQsIDUwMG1zKTsKICAgICAgICBhbmltYXRpb24tbmFtZToga2V5RnJhbWVTbGlkZURvd25JbjsKICAgICAgICBhbmltYXRpb24taXRlcmF0aW9uLWNvdW50OiAxOwogICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllcigwLjAsIDAuMCwgMC4yLCAxKTsKICAgICAgICBhbmltYXRpb24tZHVyYXRpb246IHZhcigtLXBhcGVyLXRvb2x0aXAtZHVyYXRpb24tb3V0LCA1MDBtcyk7CiAgICAgICAgYW5pbWF0aW9uLWZpbGwtbW9kZTogZm9yd2FyZHM7CiAgICAgICAgQGFwcGx5IC0tcGFwZXItdG9vbHRpcC1hbmltYXRpb247CiAgICAgIH0KCiAgICAgIC5zbGlkZS1kb3duLWFuaW1hdGlvbi1vdXQgewogICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgwKTsKICAgICAgICBvcGFjaXR5OiB2YXIoLS1wYXBlci10b29sdGlwLW9wYWNpdHksIDAuOSk7CiAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiB2YXIoLS1wYXBlci10b29sdGlwLWRlbGF5LW91dCwgNTAwbXMpOwogICAgICAgIGFuaW1hdGlvbi1uYW1lOiBrZXlGcmFtZVNsaWRlRG93bk91dDsKICAgICAgICBhbmltYXRpb24taXRlcmF0aW9uLWNvdW50OiAxOwogICAgICAgIGFuaW1hdGlvbi10aW1pbmctZnVuY3Rpb246IGN1YmljLWJlemllcigwLjQsIDAuMCwgMSwgMSk7CiAgICAgICAgYW5pbWF0aW9uLWR1cmF0aW9uOiB2YXIoLS1wYXBlci10b29sdGlwLWR1cmF0aW9uLW91dCwgNTAwbXMpOwogICAgICAgIGFuaW1hdGlvbi1maWxsLW1vZGU6IGZvcndhcmRzOwogICAgICAgIEBhcHBseSAtLXBhcGVyLXRvb2x0aXAtYW5pbWF0aW9uOwogICAgICB9CgogICAgICAuY2FuY2VsLWFuaW1hdGlvbiB7CiAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiAtMzBzICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC8qIFRoYW5rcyBJRSAxMC4gKi8KCiAgICAgIC5oaWRkZW4gewogICAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8ZGl2IGlkPSJ0b29sdGlwIiBjbGFzcz0iaGlkZGVuIj4KICAgICAgPHNsb3Q+PC9zbG90PgogICAgPC9kaXY+CmAsCgogICAgICBpczogJ3BhcGVyLXRvb2x0aXAnLAogICAgICBob3N0QXR0cmlidXRlczoge3JvbGU6ICd0b29sdGlwJywgdGFiaW5kZXg6IC0xfSwKCiAgICAgIHByb3BlcnRpZXM6IHsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgaWQgb2YgdGhlIGVsZW1lbnQgdGhhdCB0aGUgdG9vbHRpcCBpcyBhbmNob3JlZCB0by4gVGhpcyBlbGVtZW50CiAgICAgICAgICogbXVzdCBiZSBhIHNpYmxpbmcgb2YgdGhlIHRvb2x0aXAuIElmIHRoaXMgcHJvcGVydHkgaXMgbm90IHNldCwKICAgICAgICAgKiB0aGVuIHRoZSB0b29sdGlwIHdpbGwgYmUgY2VudGVyZWQgdG8gdGhlIHBhcmVudCBub2RlIGNvbnRhaW5pbmcgaXQuCiAgICAgICAgICovCiAgICAgICAgZm9yOiB7dHlwZTogU3RyaW5nLCBvYnNlcnZlcjogJ19maW5kVGFyZ2V0J30sCiAgICAgICAgLyoqCiAgICAgICAgICogU2V0IHRoaXMgdG8gdHJ1ZSBpZiB5b3Ugd2FudCB0byBtYW51YWxseSBjb250cm9sIHdoZW4gdGhlIHRvb2x0aXAKICAgICAgICAgKiBpcyBzaG93biBvciBoaWRkZW4uCiAgICAgICAgICovCiAgICAgICAgbWFudWFsTW9kZToge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZSwgb2JzZXJ2ZXI6ICdfbWFudWFsTW9kZUNoYW5nZWQnfSwKICAgICAgICAvKioKICAgICAgICAgKiBQb3NpdGlvbnMgdGhlIHRvb2x0aXAgdG8gdGhlIHRvcCwgcmlnaHQsIGJvdHRvbSwgbGVmdCBvZiBpdHMgY29udGVudC4KICAgICAgICAgKi8KICAgICAgICBwb3NpdGlvbjoge3R5cGU6IFN0cmluZywgdmFsdWU6ICdib3R0b20nfSwKICAgICAgICAvKioKICAgICAgICAgKiBJZiB0cnVlLCBubyBwYXJ0cyBvZiB0aGUgdG9vbHRpcCB3aWxsIGV2ZXIgYmUgc2hvd24gb2Zmc2NyZWVuLgogICAgICAgICAqLwogICAgICAgIGZpdFRvVmlzaWJsZUJvdW5kczoge3R5cGU6IEJvb2xlYW4sIHZhbHVlOiBmYWxzZX0sCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIHNwYWNpbmcgYmV0d2VlbiB0aGUgdG9wIG9mIHRoZSB0b29sdGlwIGFuZCB0aGUgZWxlbWVudCBpdCBpcwogICAgICAgICAqIGFuY2hvcmVkIHRvLgogICAgICAgICAqLwogICAgICAgIG9mZnNldDoge3R5cGU6IE51bWJlciwgdmFsdWU6IDE0fSwKICAgICAgICAvKioKICAgICAgICAgKiBUaGlzIHByb3BlcnR5IGlzIGRlcHJlY2F0ZWQsIGJ1dCBsZWZ0IG92ZXIgc28gdGhhdCBpdCBkb2Vzbid0CiAgICAgICAgICogYnJlYWsgZXhpdGluZyBjb2RlLiBQbGVhc2UgdXNlIGBvZmZzZXRgIGluc3RlYWQuIElmIGJvdGggYG9mZnNldGAgYW5kCiAgICAgICAgICogYG1hcmdpblRvcGAgYXJlIHByb3ZpZGVkLCBgbWFyZ2luVG9wYCB3aWxsIGJlIGlnbm9yZWQuCiAgICAgICAgICogQGRlcHJlY2F0ZWQgc2luY2UgdmVyc2lvbiAxLjAuMwogICAgICAgICAqLwogICAgICAgIG1hcmdpblRvcDoge3R5cGU6IE51bWJlciwgdmFsdWU6IDE0fSwKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGVsYXkgdGhhdCB3aWxsIGJlIGFwcGxpZWQgYmVmb3JlIHRoZSBgZW50cnlgIGFuaW1hdGlvbiBpcwogICAgICAgICAqIHBsYXllZCB3aGVuIHNob3dpbmcgdGhlIHRvb2x0aXAuCiAgICAgICAgICovCiAgICAgICAgYW5pbWF0aW9uRGVsYXk6IHt0eXBlOiBOdW1iZXIsIHZhbHVlOiA1MDAsIG9ic2VydmVyOiAnX2RlbGF5Q2hhbmdlJ30sCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGFuaW1hdGlvbiB0aGF0IHdpbGwgYmUgcGxheWVkIG9uIGVudHJ5LiAgVGhpcyByZXBsYWNlcyB0aGUKICAgICAgICAgKiBkZXByZWNhdGVkIGFuaW1hdGlvbkNvbmZpZy4gIEVudHJpZXMgaGVyZSB3aWxsIG92ZXJyaWRlIHRoZQogICAgICAgICAqIGFuaW1hdGlvbkNvbmZpZyBzZXR0aW5ncy4gIFlvdSBjYW4gZW50ZXIgeW91ciBvd24gYW5pbWF0aW9uCiAgICAgICAgICogYnkgc2V0dGluZyBpdCB0byB0aGUgY3NzIGNsYXNzIG5hbWUuCiAgICAgICAgICovCiAgICAgICAgYW5pbWF0aW9uRW50cnk6IHt0eXBlOiBTdHJpbmcsIHZhbHVlOiAnJ30sCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGFuaW1hdGlvbiB0aGF0IHdpbGwgYmUgcGxheWVkIG9uIGV4aXQuICBUaGlzIHJlcGxhY2VzIHRoZQogICAgICAgICAqIGRlcHJlY2F0ZWQgYW5pbWF0aW9uQ29uZmlnLiAgRW50cmllcyBoZXJlIHdpbGwgb3ZlcnJpZGUgdGhlCiAgICAgICAgICogYW5pbWF0aW9uQ29uZmlnIHNldHRpbmdzLiAgWW91IGNhbiBlbnRlciB5b3VyIG93biBhbmltYXRpb24KICAgICAgICAgKiBieSBzZXR0aW5nIGl0IHRvIHRoZSBjc3MgY2xhc3MgbmFtZS4KICAgICAgICAgKi8KICAgICAgICBhbmltYXRpb25FeGl0OiB7dHlwZTogU3RyaW5nLCB2YWx1ZTogJyd9LAogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgcHJvcGVydHkgaXMgZGVwcmVjYXRlZC4gIFVzZSAtLXBhcGVyLXRvb2x0aXAtYW5pbWF0aW9uIHRvIGNoYW5nZSB0aGUKICAgICAgICAgKiBhbmltYXRpb24uIFRoZSBlbnRyeSBhbmQgZXhpdCBhbmltYXRpb25zIHRoYXQgd2lsbCBiZSBwbGF5ZWQgd2hlbiBzaG93aW5nCiAgICAgICAgICogYW5kIGhpZGluZyB0aGUgdG9vbHRpcC4gSWYgeW91IHdhbnQgdG8gb3ZlcnJpZGUgdGhpcywgeW91IG11c3QgZW5zdXJlCiAgICAgICAgICogdGhhdCB5b3VyIGFuaW1hdGlvbkNvbmZpZyBoYXMgdGhlIGV4YWN0IGZvcm1hdCBiZWxvdy4KICAgICAgICAgKiBAZGVwcmVjYXRlZCBzaW5jZSB2ZXJzaW9uCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgZW50cnkgYW5kIGV4aXQgYW5pbWF0aW9ucyB0aGF0IHdpbGwgYmUgcGxheWVkIHdoZW4gc2hvd2luZyBhbmQKICAgICAgICAgKiBoaWRpbmcgdGhlIHRvb2x0aXAuIElmIHlvdSB3YW50IHRvIG92ZXJyaWRlIHRoaXMsIHlvdSBtdXN0IGVuc3VyZQogICAgICAgICAqIHRoYXQgeW91ciBhbmltYXRpb25Db25maWcgaGFzIHRoZSBleGFjdCBmb3JtYXQgYmVsb3cuCiAgICAgICAgICovCiAgICAgICAgYW5pbWF0aW9uQ29uZmlnOiB7CiAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgJ2VudHJ5JzoKICAgICAgICAgICAgICAgICAgW3tuYW1lOiAnZmFkZS1pbi1hbmltYXRpb24nLCBub2RlOiB0aGlzLCB0aW1pbmc6IHtkZWxheTogMH19XSwKICAgICAgICAgICAgICAgICAgJ2V4aXQnOiBbe25hbWU6ICdmYWRlLW91dC1hbmltYXRpb24nLCBub2RlOiB0aGlzfV0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0sCiAgICAgICAgX3Nob3dpbmc6IHt0eXBlOiBCb29sZWFuLCB2YWx1ZTogZmFsc2V9CiAgICAgIH0sCgogICAgICBsaXN0ZW5lcnM6IHsKICAgICAgICAnd2Via2l0QW5pbWF0aW9uRW5kJzogJ19vbkFuaW1hdGlvbkVuZCcsCiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmV0dXJucyB0aGUgdGFyZ2V0IGVsZW1lbnQgdGhhdCB0aGlzIHRvb2x0aXAgaXMgYW5jaG9yZWQgdG8uIEl0IGlzCiAgICAgICAqIGVpdGhlciB0aGUgZWxlbWVudCBnaXZlbiBieSB0aGUgYGZvcmAgYXR0cmlidXRlLCBvciB0aGUgaW1tZWRpYXRlIHBhcmVudAogICAgICAgKiBvZiB0aGUgdG9vbHRpcC4KICAgICAgICoKICAgICAgICogQHR5cGUge05vZGV9CiAgICAgICAqLwogICAgICBnZXQgdGFyZ2V0KCkgewogICAgICAgIHZhciBwYXJlbnROb2RlID0gZG9tKHRoaXMpLnBhcmVudE5vZGU7CiAgICAgICAgLy8gSWYgdGhlIHBhcmVudE5vZGUgaXMgYSBkb2N1bWVudCBmcmFnbWVudCwgdGhlbiB3ZSBuZWVkIHRvIHVzZSB0aGUgaG9zdC4KICAgICAgICB2YXIgb3duZXJSb290ID0gZG9tKHRoaXMpLmdldE93bmVyUm9vdCgpOwogICAgICAgIHZhciB0YXJnZXQ7CiAgICAgICAgaWYgKHRoaXMuZm9yKSB7CiAgICAgICAgICB0YXJnZXQgPSBkb20ob3duZXJSb290KS5xdWVyeVNlbGVjdG9yKCcjJyArIHRoaXMuZm9yKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGFyZ2V0ID0gcGFyZW50Tm9kZS5ub2RlVHlwZSA9PSBOb2RlLkRPQ1VNRU5UX0ZSQUdNRU5UX05PREUgPwogICAgICAgICAgICAgIG93bmVyUm9vdC5ob3N0IDoKICAgICAgICAgICAgICBwYXJlbnROb2RlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGFyZ2V0OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZmluZFRhcmdldCgpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEByZXR1cm4ge3ZvaWR9CiAgICAgICAqLwogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLm1hbnVhbE1vZGUpCiAgICAgICAgICB0aGlzLl9yZW1vdmVMaXN0ZW5lcnMoKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXBsYWNlcyBOZW9uLUFuaW1hdGlvbiBwbGF5QW5pbWF0aW9uIC0ganVzdCBjYWxscyBzaG93IGFuZCBoaWRlLgogICAgICAgKiBAZGVwcmVjYXRlZCBVc2Ugc2hvdyBhbmQgaGlkZSBpbnN0ZWFkLgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdHlwZSBFaXRoZXIgYGVudHJ5YCBvciBgZXhpdGAKICAgICAgICovCiAgICAgIHBsYXlBbmltYXRpb246IGZ1bmN0aW9uKHR5cGUpIHsKICAgICAgICBpZiAodHlwZSA9PT0gJ2VudHJ5JykgewogICAgICAgICAgdGhpcy5zaG93KCk7CiAgICAgICAgfSBlbHNlIGlmICh0eXBlID09PSAnZXhpdCcpIHsKICAgICAgICAgIHRoaXMuaGlkZSgpOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBDYW5jZWxzIHRoZSBhbmltYXRpb24gYW5kIGVpdGhlciBmdWxseSBzaG93cyBvciBmdWxseSBoaWRlcyB0b29sdGlwCiAgICAgICAqLwogICAgICBjYW5jZWxBbmltYXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFNob3J0LWN1dCBhbmQgY2FuY2VsIGFsbCBhbmltYXRpb25zIGFuZCBoaWRlCiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LmFkZCgnY2FuY2VsLWFuaW1hdGlvbicpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNob3dzIHRoZSB0b29sdGlwIHByb2dyYW1hdGljYWxseQogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgc2hvdzogZnVuY3Rpb24oKSB7CiAgICAgICAgLy8gSWYgdGhlIHRvb2x0aXAgaXMgYWxyZWFkeSBzaG93aW5nLCB0aGVyZSdzIG5vdGhpbmcgdG8gZG8uCiAgICAgICAgaWYgKHRoaXMuX3Nob3dpbmcpCiAgICAgICAgICByZXR1cm47CgogICAgICAgIGlmIChkb20odGhpcykudGV4dENvbnRlbnQudHJpbSgpID09PSAnJykgewogICAgICAgICAgLy8gQ2hlY2sgaWYgZWZmZWN0aXZlIGNoaWxkcmVuIGFyZSBhbHNvIGVtcHR5CiAgICAgICAgICB2YXIgYWxsQ2hpbGRyZW5FbXB0eSA9IHRydWU7CiAgICAgICAgICB2YXIgZWZmZWN0aXZlQ2hpbGRyZW4gPSBkb20odGhpcykuZ2V0RWZmZWN0aXZlQ2hpbGROb2RlcygpOwogICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBlZmZlY3RpdmVDaGlsZHJlbi5sZW5ndGg7IGkrKykgewogICAgICAgICAgICBpZiAoZWZmZWN0aXZlQ2hpbGRyZW5baV0udGV4dENvbnRlbnQudHJpbSgpICE9PSAnJykgewogICAgICAgICAgICAgIGFsbENoaWxkcmVuRW1wdHkgPSBmYWxzZTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGFsbENoaWxkcmVuRW1wdHkpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5fc2hvd2luZyA9IHRydWU7CiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LnJlbW92ZSgnaGlkZGVuJyk7CiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LnJlbW92ZSgnY2FuY2VsLWFuaW1hdGlvbicpOwogICAgICAgIHRoaXMuJC50b29sdGlwLmNsYXNzTGlzdC5yZW1vdmUodGhpcy5fZ2V0QW5pbWF0aW9uVHlwZSgnZXhpdCcpKTsKICAgICAgICB0aGlzLnVwZGF0ZVBvc2l0aW9uKCk7CiAgICAgICAgdGhpcy5fYW5pbWF0aW9uUGxheWluZyA9IHRydWU7CiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LmFkZCh0aGlzLl9nZXRBbmltYXRpb25UeXBlKCdlbnRyeScpKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBIaWRlcyB0aGUgdG9vbHRpcCBwcm9ncmFtYXRpY2FsbHkKICAgICAgICogQHJldHVybiB7dm9pZH0KICAgICAgICovCiAgICAgIGhpZGU6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIElmIHRoZSB0b29sdGlwIGlzIGFscmVhZHkgaGlkZGVuLCB0aGVyZSdzIG5vdGhpbmcgdG8gZG8uCiAgICAgICAgaWYgKCF0aGlzLl9zaG93aW5nKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBJZiB0aGUgZW50cnkgYW5pbWF0aW9uIGlzIHN0aWxsIHBsYXlpbmcsIGRvbid0IHRyeSB0byBwbGF5IHRoZSBleGl0CiAgICAgICAgLy8gYW5pbWF0aW9uIHNpbmNlIHRoaXMgd2lsbCByZXNldCB0aGUgb3BhY2l0eSB0byAxLiBKdXN0IGVuZCB0aGUgYW5pbWF0aW9uLgogICAgICAgIGlmICh0aGlzLl9hbmltYXRpb25QbGF5aW5nKSB7CiAgICAgICAgICB0aGlzLl9zaG93aW5nID0gZmFsc2U7CiAgICAgICAgICB0aGlzLl9jYW5jZWxBbmltYXRpb24oKTsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgLy8gUGxheSBFeGl0IEFuaW1hdGlvbgogICAgICAgICAgdGhpcy5fb25BbmltYXRpb25GaW5pc2goKTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX3Nob3dpbmcgPSBmYWxzZTsKICAgICAgICB0aGlzLl9hbmltYXRpb25QbGF5aW5nID0gdHJ1ZTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBAcmV0dXJuIHt2b2lkfQogICAgICAgKi8KICAgICAgdXBkYXRlUG9zaXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICghdGhpcy5fdGFyZ2V0IHx8ICF0aGlzLm9mZnNldFBhcmVudCkKICAgICAgICAgIHJldHVybjsKICAgICAgICB2YXIgb2Zmc2V0ID0gdGhpcy5vZmZzZXQ7CiAgICAgICAgLy8gSWYgYSBtYXJnaW5Ub3AgaGFzIGJlZW4gcHJvdmlkZWQgYnkgdGhlIHVzZXIgKHByZSAxLjAuMyksIHVzZSBpdC4KICAgICAgICBpZiAodGhpcy5tYXJnaW5Ub3AgIT0gMTQgJiYgdGhpcy5vZmZzZXQgPT0gMTQpCiAgICAgICAgICBvZmZzZXQgPSB0aGlzLm1hcmdpblRvcDsKICAgICAgICB2YXIgcGFyZW50UmVjdCA9IHRoaXMub2Zmc2V0UGFyZW50LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciB0YXJnZXRSZWN0ID0gdGhpcy5fdGFyZ2V0LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIHZhciB0aGlzUmVjdCA9IHRoaXMuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgdmFyIGhvcml6b250YWxDZW50ZXJPZmZzZXQgPSAodGFyZ2V0UmVjdC53aWR0aCAtIHRoaXNSZWN0LndpZHRoKSAvIDI7CiAgICAgICAgdmFyIHZlcnRpY2FsQ2VudGVyT2Zmc2V0ID0gKHRhcmdldFJlY3QuaGVpZ2h0IC0gdGhpc1JlY3QuaGVpZ2h0KSAvIDI7CiAgICAgICAgdmFyIHRhcmdldExlZnQgPSB0YXJnZXRSZWN0LmxlZnQgLSBwYXJlbnRSZWN0LmxlZnQ7CiAgICAgICAgdmFyIHRhcmdldFRvcCA9IHRhcmdldFJlY3QudG9wIC0gcGFyZW50UmVjdC50b3A7CiAgICAgICAgdmFyIHRvb2x0aXBMZWZ0LCB0b29sdGlwVG9wOwogICAgICAgIHN3aXRjaCAodGhpcy5wb3NpdGlvbikgewogICAgICAgICAgY2FzZSAndG9wJzoKICAgICAgICAgICAgdG9vbHRpcExlZnQgPSB0YXJnZXRMZWZ0ICsgaG9yaXpvbnRhbENlbnRlck9mZnNldDsKICAgICAgICAgICAgdG9vbHRpcFRvcCA9IHRhcmdldFRvcCAtIHRoaXNSZWN0LmhlaWdodCAtIG9mZnNldDsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdib3R0b20nOgogICAgICAgICAgICB0b29sdGlwTGVmdCA9IHRhcmdldExlZnQgKyBob3Jpem9udGFsQ2VudGVyT2Zmc2V0OwogICAgICAgICAgICB0b29sdGlwVG9wID0gdGFyZ2V0VG9wICsgdGFyZ2V0UmVjdC5oZWlnaHQgKyBvZmZzZXQ7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnbGVmdCc6CiAgICAgICAgICAgIHRvb2x0aXBMZWZ0ID0gdGFyZ2V0TGVmdCAtIHRoaXNSZWN0LndpZHRoIC0gb2Zmc2V0OwogICAgICAgICAgICB0b29sdGlwVG9wID0gdGFyZ2V0VG9wICsgdmVydGljYWxDZW50ZXJPZmZzZXQ7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAncmlnaHQnOgogICAgICAgICAgICB0b29sdGlwTGVmdCA9IHRhcmdldExlZnQgKyB0YXJnZXRSZWN0LndpZHRoICsgb2Zmc2V0OwogICAgICAgICAgICB0b29sdGlwVG9wID0gdGFyZ2V0VG9wICsgdmVydGljYWxDZW50ZXJPZmZzZXQ7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgICAvLyBUT0RPKG5vbXMpOiBUaGlzIHNob3VsZCB1c2UgSXJvbkZpdEJlaGF2aW9yIGlmIHBvc3NpYmxlLgogICAgICAgIGlmICh0aGlzLmZpdFRvVmlzaWJsZUJvdW5kcykgewogICAgICAgICAgLy8gQ2xpcCB0aGUgbGVmdC9yaWdodCBzaWRlCiAgICAgICAgICBpZiAocGFyZW50UmVjdC5sZWZ0ICsgdG9vbHRpcExlZnQgKyB0aGlzUmVjdC53aWR0aCA+IHdpbmRvdy5pbm5lcldpZHRoKSB7CiAgICAgICAgICAgIHRoaXMuc3R5bGUucmlnaHQgPSAnMHB4JzsKICAgICAgICAgICAgdGhpcy5zdHlsZS5sZWZ0ID0gJ2F1dG8nOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5zdHlsZS5sZWZ0ID0gTWF0aC5tYXgoMCwgdG9vbHRpcExlZnQpICsgJ3B4JzsKICAgICAgICAgICAgdGhpcy5zdHlsZS5yaWdodCA9ICdhdXRvJzsKICAgICAgICAgIH0KICAgICAgICAgIC8vIENsaXAgdGhlIHRvcC9ib3R0b20gc2lkZS4KICAgICAgICAgIGlmIChwYXJlbnRSZWN0LnRvcCArIHRvb2x0aXBUb3AgKyB0aGlzUmVjdC5oZWlnaHQgPiB3aW5kb3cuaW5uZXJIZWlnaHQpIHsKICAgICAgICAgICAgdGhpcy5zdHlsZS5ib3R0b20gPSAocGFyZW50UmVjdC5oZWlnaHQgLSB0YXJnZXRUb3AgKyBvZmZzZXQpICsgJ3B4JzsKICAgICAgICAgICAgdGhpcy5zdHlsZS50b3AgPSAnYXV0byc7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLnN0eWxlLnRvcCA9IE1hdGgubWF4KC1wYXJlbnRSZWN0LnRvcCwgdG9vbHRpcFRvcCkgKyAncHgnOwogICAgICAgICAgICB0aGlzLnN0eWxlLmJvdHRvbSA9ICdhdXRvJzsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5zdHlsZS5sZWZ0ID0gdG9vbHRpcExlZnQgKyAncHgnOwogICAgICAgICAgdGhpcy5zdHlsZS50b3AgPSB0b29sdGlwVG9wICsgJ3B4JzsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfYWRkTGlzdGVuZXJzOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fdGFyZ2V0KSB7CiAgICAgICAgICB0aGlzLmxpc3Rlbih0aGlzLl90YXJnZXQsICdtb3VzZWVudGVyJywgJ3Nob3cnKTsKICAgICAgICAgIHRoaXMubGlzdGVuKHRoaXMuX3RhcmdldCwgJ2ZvY3VzJywgJ3Nob3cnKTsKICAgICAgICAgIHRoaXMubGlzdGVuKHRoaXMuX3RhcmdldCwgJ21vdXNlbGVhdmUnLCAnaGlkZScpOwogICAgICAgICAgdGhpcy5saXN0ZW4odGhpcy5fdGFyZ2V0LCAnYmx1cicsICdoaWRlJyk7CiAgICAgICAgICB0aGlzLmxpc3Rlbih0aGlzLl90YXJnZXQsICd0YXAnLCAnaGlkZScpOwogICAgICAgIH0KICAgICAgICB0aGlzLmxpc3Rlbih0aGlzLiQudG9vbHRpcCwgJ2FuaW1hdGlvbmVuZCcsICdfb25BbmltYXRpb25FbmQnKTsKICAgICAgICB0aGlzLmxpc3Rlbih0aGlzLCAnbW91c2VlbnRlcicsICdoaWRlJyk7CiAgICAgIH0sCgogICAgICBfZmluZFRhcmdldDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKCF0aGlzLm1hbnVhbE1vZGUpCiAgICAgICAgICB0aGlzLl9yZW1vdmVMaXN0ZW5lcnMoKTsKICAgICAgICB0aGlzLl90YXJnZXQgPSB0aGlzLnRhcmdldDsKICAgICAgICBpZiAoIXRoaXMubWFudWFsTW9kZSkKICAgICAgICAgIHRoaXMuX2FkZExpc3RlbmVycygpOwogICAgICB9LAoKICAgICAgX2RlbGF5Q2hhbmdlOiBmdW5jdGlvbihuZXdWYWx1ZSkgewogICAgICAgIC8vIE9ubHkgVXBkYXRlIGRlbGF5IGlmIGRpZmZlcmVudCB2YWx1ZSBzZXQKICAgICAgICBpZiAobmV3VmFsdWUgIT09IDUwMCkgewogICAgICAgICAgdGhpcy51cGRhdGVTdHlsZXMoeyctLXBhcGVyLXRvb2x0aXAtZGVsYXktaW4nOiBuZXdWYWx1ZSArICdtcyd9KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfbWFudWFsTW9kZUNoYW5nZWQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLm1hbnVhbE1vZGUpCiAgICAgICAgICB0aGlzLl9yZW1vdmVMaXN0ZW5lcnMoKTsKICAgICAgICBlbHNlCiAgICAgICAgICB0aGlzLl9hZGRMaXN0ZW5lcnMoKTsKICAgICAgfSwKCiAgICAgIF9jYW5jZWxBbmltYXRpb246IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIFNob3J0LWN1dCBhbmQgY2FuY2VsIGFsbCBhbmltYXRpb25zIGFuZCBoaWRlCiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LnJlbW92ZSh0aGlzLl9nZXRBbmltYXRpb25UeXBlKCdlbnRyeScpKTsKICAgICAgICB0aGlzLiQudG9vbHRpcC5jbGFzc0xpc3QucmVtb3ZlKHRoaXMuX2dldEFuaW1hdGlvblR5cGUoJ2V4aXQnKSk7CiAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LnJlbW92ZSgnY2FuY2VsLWFuaW1hdGlvbicpOwogICAgICAgIHRoaXMuJC50b29sdGlwLmNsYXNzTGlzdC5hZGQoJ2hpZGRlbicpOwogICAgICB9LAoKICAgICAgX29uQW5pbWF0aW9uRmluaXNoOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fc2hvd2luZykgewogICAgICAgICAgdGhpcy4kLnRvb2x0aXAuY2xhc3NMaXN0LnJlbW92ZSh0aGlzLl9nZXRBbmltYXRpb25UeXBlKCdlbnRyeScpKTsKICAgICAgICAgIHRoaXMuJC50b29sdGlwLmNsYXNzTGlzdC5yZW1vdmUoJ2NhbmNlbC1hbmltYXRpb24nKTsKICAgICAgICAgIHRoaXMuJC50b29sdGlwLmNsYXNzTGlzdC5hZGQodGhpcy5fZ2V0QW5pbWF0aW9uVHlwZSgnZXhpdCcpKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfb25BbmltYXRpb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIC8vIElmIG5vIGxvbmdlciBzaG93aW5nIGFkZCBjbGFzcyBoaWRkZW4gdG8gY29tcGxldGVseSBoaWRlIHRvb2x0aXAKICAgICAgICB0aGlzLl9hbmltYXRpb25QbGF5aW5nID0gZmFsc2U7CiAgICAgICAgaWYgKCF0aGlzLl9zaG93aW5nKSB7CiAgICAgICAgICB0aGlzLiQudG9vbHRpcC5jbGFzc0xpc3QucmVtb3ZlKHRoaXMuX2dldEFuaW1hdGlvblR5cGUoJ2V4aXQnKSk7CiAgICAgICAgICB0aGlzLiQudG9vbHRpcC5jbGFzc0xpc3QuYWRkKCdoaWRkZW4nKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICBfZ2V0QW5pbWF0aW9uVHlwZTogZnVuY3Rpb24odHlwZSkgewogICAgICAgIC8vIFRoZXNlIHByb3BlcnRpZXMgaGF2ZSBwcmlvcml0eSBvdmVyIGFuaW1hdGlvbkNvbmZpZyB2YWx1ZXMKICAgICAgICBpZiAoKHR5cGUgPT09ICdlbnRyeScpICYmICh0aGlzLmFuaW1hdGlvbkVudHJ5ICE9PSAnJykpIHsKICAgICAgICAgIHJldHVybiB0aGlzLmFuaW1hdGlvbkVudHJ5OwogICAgICAgIH0KICAgICAgICBpZiAoKHR5cGUgPT09ICdleGl0JykgJiYgKHRoaXMuYW5pbWF0aW9uRXhpdCAhPT0gJycpKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5hbmltYXRpb25FeGl0OwogICAgICAgIH0KICAgICAgICAvLyBJZiBubyByZXN1bHRzIHRoZW4gcmV0dXJuIHRoZSBsZWdhY3kgdmFsdWUgZnJvbSBhbmltYXRpb25Db25maWcKICAgICAgICBpZiAodGhpcy5hbmltYXRpb25Db25maWdbdHlwZV0gJiYKICAgICAgICAgICAgdHlwZW9mIHRoaXMuYW5pbWF0aW9uQ29uZmlnW3R5cGVdWzBdLm5hbWUgPT09ICdzdHJpbmcnKSB7CiAgICAgICAgICAvLyBDaGVja2luZyBUaW1pbmcgYW5kIFVwZGF0ZSBpZiBuZWNlc3NhcnkgLSBMZWdhY3kgZm9yIGFuaW1hdGlvbkNvbmZpZwogICAgICAgICAgaWYgKHRoaXMuYW5pbWF0aW9uQ29uZmlnW3R5cGVdWzBdLnRpbWluZyAmJgogICAgICAgICAgICAgIHRoaXMuYW5pbWF0aW9uQ29uZmlnW3R5cGVdWzBdLnRpbWluZy5kZWxheSAmJgogICAgICAgICAgICAgIHRoaXMuYW5pbWF0aW9uQ29uZmlnW3R5cGVdWzBdLnRpbWluZy5kZWxheSAhPT0gMCkgewogICAgICAgICAgICB2YXIgdGltaW5nRGVsYXkgPSB0aGlzLmFuaW1hdGlvbkNvbmZpZ1t0eXBlXVswXS50aW1pbmcuZGVsYXk7CiAgICAgICAgICAgIC8vIEhhcyBUaW1pbmcgQ2hhbmdlIC0gVXBkYXRlIENTUwogICAgICAgICAgICBpZiAodHlwZSA9PT0gJ2VudHJ5JykgewogICAgICAgICAgICAgIHRoaXMudXBkYXRlU3R5bGVzKHsnLS1wYXBlci10b29sdGlwLWRlbGF5LWluJzogdGltaW5nRGVsYXkgKyAnbXMnfSk7CiAgICAgICAgICAgIH0gZWxzZSBpZiAodHlwZSA9PT0gJ2V4aXQnKSB7CiAgICAgICAgICAgICAgdGhpcy51cGRhdGVTdHlsZXMoeyctLXBhcGVyLXRvb2x0aXAtZGVsYXktb3V0JzogdGltaW5nRGVsYXkgKyAnbXMnfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0aGlzLmFuaW1hdGlvbkNvbmZpZ1t0eXBlXVswXS5uYW1lOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIF9yZW1vdmVMaXN0ZW5lcnM6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl90YXJnZXQpIHsKICAgICAgICAgIHRoaXMudW5saXN0ZW4odGhpcy5fdGFyZ2V0LCAnbW91c2VlbnRlcicsICdzaG93Jyk7CiAgICAgICAgICB0aGlzLnVubGlzdGVuKHRoaXMuX3RhcmdldCwgJ2ZvY3VzJywgJ3Nob3cnKTsKICAgICAgICAgIHRoaXMudW5saXN0ZW4odGhpcy5fdGFyZ2V0LCAnbW91c2VsZWF2ZScsICdoaWRlJyk7CiAgICAgICAgICB0aGlzLnVubGlzdGVuKHRoaXMuX3RhcmdldCwgJ2JsdXInLCAnaGlkZScpOwogICAgICAgICAgdGhpcy51bmxpc3Rlbih0aGlzLl90YXJnZXQsICd0YXAnLCAnaGlkZScpOwogICAgICAgIH0KICAgICAgICB0aGlzLnVubGlzdGVuKHRoaXMuJC50b29sdGlwLCAnYW5pbWF0aW9uZW5kJywgJ19vbkFuaW1hdGlvbkVuZCcpOwogICAgICAgIHRoaXMudW5saXN0ZW4odGhpcywgJ21vdXNlZW50ZXInLCAnaGlkZScpOwogICAgICB9CiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxOCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNsYXNzIExpc3RlbktleSB7CiAgICAgICAgY29uc3RydWN0b3IobGlzdGVuZXIpIHsKICAgICAgICAgICAgdGhpcy5saXN0ZW5lciA9IGxpc3RlbmVyOwogICAgICAgIH0KICAgIH0KICAgIGNvbnN0IGhhc2hMaXN0ZW5lcnMgPSBuZXcgU2V0KCk7CiAgICBjb25zdCBzdG9yYWdlTGlzdGVuZXJzID0gbmV3IFNldCgpOwogICAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ2hhc2hjaGFuZ2UnLCAoKSA9PiB7CiAgICAgICAgaGFzaExpc3RlbmVycy5mb3JFYWNoKChsaXN0ZW5LZXkpID0+IGxpc3RlbktleS5saXN0ZW5lcigpKTsKICAgIH0pOwogICAgLy8gWzFdOiBUaGUgZXZlbnQgb25seSB0cmlnZ2VycyB3aGVuIGFub3RoZXIgdGFiIGVkaXRzIHRoZSBzdG9yYWdlLiBDaGFuZ2luZyBhCiAgICAvLyB2YWx1ZSBpbiBjdXJyZW50IGJyb3dzZXIgdGFiIHdpbGwgTk9UIHRyaWdnZXIgYmVsb3cgZXZlbnQuCiAgICB3aW5kb3cuYWRkRXZlbnRMaXN0ZW5lcignc3RvcmFnZScsICgpID0+IHsKICAgICAgICBzdG9yYWdlTGlzdGVuZXJzLmZvckVhY2goKGxpc3RlbktleSkgPT4gbGlzdGVuS2V5Lmxpc3RlbmVyKCkpOwogICAgfSk7CiAgICBmdW5jdGlvbiBhZGRIYXNoTGlzdGVuZXIoZm4pIHsKICAgICAgICBjb25zdCBrZXkgPSBuZXcgTGlzdGVuS2V5KGZuKTsKICAgICAgICBoYXNoTGlzdGVuZXJzLmFkZChrZXkpOwogICAgICAgIHJldHVybiBrZXk7CiAgICB9CiAgICBmdW5jdGlvbiBhZGRTdG9yYWdlTGlzdGVuZXIoZm4pIHsKICAgICAgICBjb25zdCBrZXkgPSBuZXcgTGlzdGVuS2V5KGZuKTsKICAgICAgICBzdG9yYWdlTGlzdGVuZXJzLmFkZChrZXkpOwogICAgICAgIHJldHVybiBrZXk7CiAgICB9CiAgICBmdW5jdGlvbiBmaXJlU3RvcmFnZUNoYW5nZWQoKSB7CiAgICAgICAgc3RvcmFnZUxpc3RlbmVycy5mb3JFYWNoKChsaXN0ZW5LZXkpID0+IGxpc3RlbktleS5saXN0ZW5lcigpKTsKICAgIH0KICAgIGZ1bmN0aW9uIHJlbW92ZUhhc2hMaXN0ZW5lckJ5S2V5KGtleSkgewogICAgICAgIGhhc2hMaXN0ZW5lcnMuZGVsZXRlKGtleSk7CiAgICB9CiAgICBmdW5jdGlvbiByZW1vdmVTdG9yYWdlTGlzdGVuZXJCeUtleShrZXkpIHsKICAgICAgICBzdG9yYWdlTGlzdGVuZXJzLmRlbGV0ZShrZXkpOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE2IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gSWYgdHJ1ZSwgVGVuc29yQm9hcmQgc3RvcmVzIGl0cyBoYXNoIGluIHRoZSBVUkkgc3RhdGUuCiAgICAvLyBJZiBmYWxzZSwgdGFiIHN3aXRjaGluZyBpbiBUZW5zb3JCb2FyZCB3aWxsIG5vdCB1cGRhdGUgbG9jYXRpb24gaGFzaCwKICAgIC8vIGJlY2F1c2UgaGFzaCB1cGRhdGVzIGludGVyZmVyZSB3aXRoIHdjdF90ZXN0cy4KICAgIGxldCBfdXNlSGFzaCA9IGZhbHNlOwogICAgZnVuY3Rpb24gc2V0VXNlSGFzaChzaG91bGRVc2VIYXNoKSB7CiAgICAgICAgX3VzZUhhc2ggPSBzaG91bGRVc2VIYXNoOwogICAgfQogICAgZnVuY3Rpb24gdXNlSGFzaCgpIHsKICAgICAgICByZXR1cm4gX3VzZUhhc2g7CiAgICB9CiAgICBsZXQgX2Zha2VIYXNoID0gJyc7CiAgICBmdW5jdGlvbiBzZXRGYWtlSGFzaChoKSB7CiAgICAgICAgX2Zha2VIYXNoID0gaDsKICAgIH0KICAgIGZ1bmN0aW9uIGdldEZha2VIYXNoKCkgewogICAgICAgIHJldHVybiBfZmFrZUhhc2g7CiAgICB9CgogICAgdmFyIHRmX2dsb2JhbHMgPSAvKiNfX1BVUkVfXyovT2JqZWN0LmZyZWV6ZSh7CiAgICAgICAgX19wcm90b19fOiBudWxsLAogICAgICAgIHNldFVzZUhhc2g6IHNldFVzZUhhc2gsCiAgICAgICAgdXNlSGFzaDogdXNlSGFzaCwKICAgICAgICBzZXRGYWtlSGFzaDogc2V0RmFrZUhhc2gsCiAgICAgICAgZ2V0RmFrZUhhc2g6IGdldEZha2VIYXNoCiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogQSBrZXl3b3JkIHRoYXQgdXNlcnMgY2Fubm90IHVzZSwgc2luY2UgVGVuc29yQm9hcmQgdXNlcyB0aGlzIHRvIHN0b3JlIGluZm8KICAgICAqIGFib3V0IHRoZSBhY3RpdmUgdGFiLgogICAgICovCiAgICBjb25zdCBUQUIgPSAnX190YWJfXyc7CiAgICAvKioKICAgICAqIFRoZSBuYW1lIG9mIHRoZSBwcm9wZXJ0eSBmb3IgdXNlcnMgdG8gc2V0IG9uIGEgUG9seW1lciBjb21wb25lbnQKICAgICAqIGluIG9yZGVyIGZvciBpdHMgc3RvcmVkIHByb3BlcnRpZXMgdG8gYmUgc3RvcmVkIGluIHRoZSBVUkkgdW5hbWJpZ3VvdXNseS4KICAgICAqIChObyBuZWVkIHRvIHNldCB0aGlzIGlmIHlvdSB3YW50IG11bHRpcGxlIGluc3RhbmNlcyBvZiB0aGUgY29tcG9uZW50IHRvCiAgICAgKiBzaGFyZSBVUkkgc3RhdGUpCiAgICAgKgogICAgICogRXhhbXBsZToKICAgICAqIDxteS1jb21wb25lbnQgZGlzYW1iaWd1YXRvcj0iMCI+PC9teS1jb21wb25lbnQ+CiAgICAgKgogICAgICogVGhlIGRpc2FtYmlndWF0b3Igc2hvdWxkIGJlIHNldCB0byBhbnkgdW5pcXVlIHZhbHVlIHNvIHRoYXQgbXVsdGlwbGUKICAgICAqIGluc3RhbmNlcyBvZiB0aGUgY29tcG9uZW50IGNhbiBzdG9yZSBwcm9wZXJ0aWVzIGluIFVSSSBzdG9yYWdlLgogICAgICoKICAgICAqIEJlY2F1c2UgaXQncyBoYXJkIHRvIGRlcmVmZXJlbmNlIHRoaXMgdmFyaWFibGUgaW4gSFRNTCBwcm9wZXJ0eSBiaW5kaW5ncywKICAgICAqIGl0IGlzIE5PVCBzYWZlIHRvIGNoYW5nZSB0aGUgZGlzYW1iaWd1YXRvciBzdHJpbmcgd2l0aG91dCBmaW5kK3JlcGxhY2UKICAgICAqIGFjcm9zcyB0aGUgY29kZWJhc2UuCiAgICAgKi8KICAgIGNvbnN0IERJU0FNQklHVUFUT1IgPSAnZGlzYW1iaWd1YXRvcic7CiAgICAvLyBLZWVwIGFuIHVwLXRvLWRhdGUgc3RvcmUgb2YgVVJMIHBhcmFtcywgd2hpY2ggaWZyYW1lZCBwbHVnaW5zIGNhbiByZXF1ZXN0LgogICAgbGV0IHVybERpY3QgPSB7fTsKICAgIGZ1bmN0aW9uIGdldFVybERpY3QoKSB7CiAgICAgICAgcmV0dXJuIHVybERpY3Q7CiAgICB9CiAgICBhZGRIYXNoTGlzdGVuZXIoKCkgPT4gewogICAgICAgIHVybERpY3QgPSBjb21wb25lbnRUb0RpY3QocmVhZENvbXBvbmVudCgpKTsKICAgIH0pOwogICAgY29uc3QgeyBnZXQ6IGdldFN0cmluZywgc2V0OiBzZXRTdHJpbmcsIGdldEluaXRpYWxpemVyOiBnZXRTdHJpbmdJbml0aWFsaXplciwgZ2V0T2JzZXJ2ZXI6IGdldFN0cmluZ09ic2VydmVyLCBkaXNwb3NlQmluZGluZzogZGlzcG9zZVN0cmluZ0JpbmRpbmcsIH0gPSBtYWtlQmluZGluZ3MoKHgpID0+IHgsICh4KSA9PiB4KTsKICAgIGNvbnN0IHsgZ2V0OiBnZXRCb29sZWFuLCBzZXQ6IHNldEJvb2xlYW4sIGdldEluaXRpYWxpemVyOiBnZXRCb29sZWFuSW5pdGlhbGl6ZXIsIGdldE9ic2VydmVyOiBnZXRCb29sZWFuT2JzZXJ2ZXIsIGRpc3Bvc2VCaW5kaW5nOiBkaXNwb3NlQm9vbGVhbkJpbmRpbmcsIH0gPSBtYWtlQmluZGluZ3MoKHMpID0+IChzID09PSAndHJ1ZScgPyB0cnVlIDogcyA9PT0gJ2ZhbHNlJyA/IGZhbHNlIDogdW5kZWZpbmVkKSwgKGIpID0+IGIudG9TdHJpbmcoKSk7CiAgICBjb25zdCB7IGdldDogZ2V0TnVtYmVyLCBzZXQ6IHNldE51bWJlciwgZ2V0SW5pdGlhbGl6ZXI6IGdldE51bWJlckluaXRpYWxpemVyLCBnZXRPYnNlcnZlcjogZ2V0TnVtYmVyT2JzZXJ2ZXIsIGRpc3Bvc2VCaW5kaW5nOiBkaXNwb3NlTnVtYmVyQmluZGluZywgfSA9IG1ha2VCaW5kaW5ncygocykgPT4gK3MsIChuKSA9PiBuLnRvU3RyaW5nKCkpOwogICAgY29uc3QgeyBnZXQ6IGdldE9iamVjdCwgc2V0OiBzZXRPYmplY3QsIGdldEluaXRpYWxpemVyOiBnZXRPYmplY3RJbml0aWFsaXplciwgZ2V0T2JzZXJ2ZXI6IGdldE9iamVjdE9ic2VydmVyLCBkaXNwb3NlQmluZGluZzogZGlzcG9zZU9iamVjdEJpbmRpbmcsIH0gPSBtYWtlQmluZGluZ3MoKHMpID0+IEpTT04ucGFyc2UoYXRvYihzKSksIChvKSA9PiBidG9hKEpTT04uc3RyaW5naWZ5KG8pKSk7CiAgICBmdW5jdGlvbiBtYWtlQmluZGluZ3MoZnJvbVN0cmluZywgdG9TdHJpbmcpIHsKICAgICAgICBjb25zdCBoYXNoTGlzdGVuZXJzID0gW107CiAgICAgICAgY29uc3Qgc3RvcmFnZUxpc3RlbmVycyA9IFtdOwogICAgICAgIGZ1bmN0aW9uIGdldChrZXksIG9wdGlvbnMgPSB7fSkgewogICAgICAgICAgICBjb25zdCB7IGRlZmF1bHRWYWx1ZSwgdXNlTG9jYWxTdG9yYWdlID0gZmFsc2UgfSA9IG9wdGlvbnM7CiAgICAgICAgICAgIGNvbnN0IHZhbHVlID0gdXNlTG9jYWxTdG9yYWdlCiAgICAgICAgICAgICAgICA/IHdpbmRvdy5sb2NhbFN0b3JhZ2UuZ2V0SXRlbShrZXkpCiAgICAgICAgICAgICAgICA6IGNvbXBvbmVudFRvRGljdChyZWFkQ29tcG9uZW50KCkpW2tleV07CiAgICAgICAgICAgIHJldHVybiB2YWx1ZSA9PSB1bmRlZmluZWQgPyBsb2Rhc2guY2xvbmVEZWVwKGRlZmF1bHRWYWx1ZSkgOiBmcm9tU3RyaW5nKHZhbHVlKTsKICAgICAgICB9CiAgICAgICAgZnVuY3Rpb24gc2V0KGtleSwgdmFsdWUsIG9wdGlvbnMgPSB7fSkgewogICAgICAgICAgICBjb25zdCB7IGRlZmF1bHRWYWx1ZSwgdXNlTG9jYWxTdG9yYWdlID0gZmFsc2UsIHVzZUxvY2F0aW9uUmVwbGFjZSA9IGZhbHNlLCB9ID0gb3B0aW9uczsKICAgICAgICAgICAgY29uc3Qgc3RyaW5nVmFsdWUgPSB0b1N0cmluZyh2YWx1ZSk7CiAgICAgICAgICAgIGlmICh1c2VMb2NhbFN0b3JhZ2UpIHsKICAgICAgICAgICAgICAgIHdpbmRvdy5sb2NhbFN0b3JhZ2Uuc2V0SXRlbShrZXksIHN0cmluZ1ZhbHVlKTsKICAgICAgICAgICAgICAgIC8vIEJlY2F1c2Ugb2YgbGlzdGVuZXJzLnRzOlsxXSwgd2UgbmVlZCB0byBtYW51YWxseSBub3RpZnkgYWxsIFVJIGVsZW1lbnRzCiAgICAgICAgICAgICAgICAvLyBsaXN0ZW5pbmcgdG8gc3RvcmFnZSB3aXRoaW4gdGhlIHRhYiBvZiBhIGNoYW5nZS4KICAgICAgICAgICAgICAgIGZpcmVTdG9yYWdlQ2hhbmdlZCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKCFsb2Rhc2guaXNFcXVhbCh2YWx1ZSwgZ2V0KGtleSwgeyB1c2VMb2NhbFN0b3JhZ2UgfSkpKSB7CiAgICAgICAgICAgICAgICBpZiAobG9kYXNoLmlzRXF1YWwodmFsdWUsIGRlZmF1bHRWYWx1ZSkpIHsKICAgICAgICAgICAgICAgICAgICB1bnNldEZyb21VUkkoa2V5KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGNvbnN0IGl0ZW1zID0gY29tcG9uZW50VG9EaWN0KHJlYWRDb21wb25lbnQoKSk7CiAgICAgICAgICAgICAgICAgICAgaXRlbXNba2V5XSA9IHN0cmluZ1ZhbHVlOwogICAgICAgICAgICAgICAgICAgIHdyaXRlQ29tcG9uZW50KGRpY3RUb0NvbXBvbmVudChpdGVtcyksIHVzZUxvY2F0aW9uUmVwbGFjZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBhIGZ1bmN0aW9uIHRoYXQgY2FuIGJlIHVzZWQgb24gYSBgdmFsdWVgIGRlY2xhcmF0aW9uIHRvIGEgUG9seW1lcgogICAgICAgICAqIHByb3BlcnR5LiBJdCB1cGRhdGVzIHRoZSBgcG9seW1lclByb3BlcnR5YCB3aGVuIHN0b3JhZ2UgY2hhbmdlcyAtLSBpLmUuLAogICAgICAgICAqIHdoZW4gYHVzZUxvY2FsU3RvcmFnZWAsIGl0IGxpc3RlbnMgdG8gc3RvcmFnZSBjaGFuZ2UgZnJvbSBhbm90aGVyIHRhYiBhbmQKICAgICAgICAgKiB3aGVuIGB1c2VMb2NhbFN0b3JhZ2U9ZmFsc2VgLCBpdCBsaXN0ZW5zIHRvIGhhc2hjaGFuZ2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gZ2V0SW5pdGlhbGl6ZXIoa2V5LCBvcHRpb25zKSB7CiAgICAgICAgICAgIGNvbnN0IGZ1bGxPcHRpb25zID0gT2JqZWN0LmFzc2lnbih7IGRlZmF1bHRWYWx1ZTogb3B0aW9ucy5kZWZhdWx0VmFsdWUsIHBvbHltZXJQcm9wZXJ0eToga2V5LCB1c2VMb2NhbFN0b3JhZ2U6IGZhbHNlIH0sIG9wdGlvbnMpOwogICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgY29uc3QgdXJpU3RvcmFnZU5hbWUgPSBnZXRVUklTdG9yYWdlTmFtZSh0aGlzLCBrZXkpOwogICAgICAgICAgICAgICAgLy8gc2V0Q29tcG9uZW50VmFsdWUgd2lsbCBiZSBjYWxsZWQgZXZlcnkgdGltZSB0aGUgdW5kZXJseWluZyBzdG9yYWdlCiAgICAgICAgICAgICAgICAvLyBjaGFuZ2VzIGFuZCBpcyByZXNwb25zaWJsZSBmb3IgZW5zdXJpbmcgdGhhdCBuZXcgc3RhdGUgd2lsbCBwcm9wYWdhdGUKICAgICAgICAgICAgICAgIC8vIHRvIHRoZSBjb21wb25lbnQgd2l0aCBzcGVjaWZpZWQgcHJvcGVydHkuIEl0IGlzIGltcG9ydGFudCB0aGF0IHRoaXMKICAgICAgICAgICAgICAgIC8vIGZ1bmN0aW9uIGRvZXMgbm90IHJlLWFzc2lnbiBuZWVkbGVzc2x5LCB0byBhdm9pZCBQb2x5bWVyIG9ic2VydmVyCiAgICAgICAgICAgICAgICAvLyBjaHVybi4KICAgICAgICAgICAgICAgIGNvbnN0IHNldENvbXBvbmVudFZhbHVlID0gKCkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IHN0b3JlZFZhbHVlID0gZ2V0KHVyaVN0b3JhZ2VOYW1lLCBmdWxsT3B0aW9ucyk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgY3VycmVudFZhbHVlID0gdGhpc1tmdWxsT3B0aW9ucy5wb2x5bWVyUHJvcGVydHldOwogICAgICAgICAgICAgICAgICAgIGlmICghbG9kYXNoLmlzRXF1YWwoc3RvcmVkVmFsdWUsIGN1cnJlbnRWYWx1ZSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpc1tmdWxsT3B0aW9ucy5wb2x5bWVyUHJvcGVydHldID0gc3RvcmVkVmFsdWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGNvbnN0IGFkZExpc3RlbmVyID0gZnVsbE9wdGlvbnMudXNlTG9jYWxTdG9yYWdlCiAgICAgICAgICAgICAgICAgICAgPyBhZGRTdG9yYWdlTGlzdGVuZXIKICAgICAgICAgICAgICAgICAgICA6IGFkZEhhc2hMaXN0ZW5lcjsKICAgICAgICAgICAgICAgIC8vIFRPRE8oc3RlcGhhbndsZWUpOiBXaGVuIHVzaW5nIGZha2VIYXNoLCBpdCBfc2hvdWxkIG5vdF8gbGlzdGVuIHRvIHRoZQogICAgICAgICAgICAgICAgLy8gICAgICAgICAgICAgICAgICAgIHdpbmRvdy5oYXNoY2hhbmdlLgogICAgICAgICAgICAgICAgY29uc3QgbGlzdGVuS2V5ID0gYWRkTGlzdGVuZXIoKCkgPT4gc2V0Q29tcG9uZW50VmFsdWUoKSk7CiAgICAgICAgICAgICAgICBpZiAoZnVsbE9wdGlvbnMudXNlTG9jYWxTdG9yYWdlKSB7CiAgICAgICAgICAgICAgICAgICAgc3RvcmFnZUxpc3RlbmVycy5wdXNoKGxpc3RlbktleSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBoYXNoTGlzdGVuZXJzLnB1c2gobGlzdGVuS2V5KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFNldCB0aGUgdmFsdWUgb24gdGhlIHByb3BlcnR5LgogICAgICAgICAgICAgICAgc2V0Q29tcG9uZW50VmFsdWUoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzW2Z1bGxPcHRpb25zLnBvbHltZXJQcm9wZXJ0eV07CiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIGZ1bmN0aW9uIGRpc3Bvc2VCaW5kaW5nKCkgewogICAgICAgICAgICBoYXNoTGlzdGVuZXJzLmZvckVhY2goKGtleSkgPT4gcmVtb3ZlSGFzaExpc3RlbmVyQnlLZXkoa2V5KSk7CiAgICAgICAgICAgIHN0b3JhZ2VMaXN0ZW5lcnMuZm9yRWFjaCgoa2V5KSA9PiByZW1vdmVTdG9yYWdlTGlzdGVuZXJCeUtleShrZXkpKTsKICAgICAgICB9CiAgICAgICAgZnVuY3Rpb24gZ2V0T2JzZXJ2ZXIoa2V5LCBvcHRpb25zKSB7CiAgICAgICAgICAgIGNvbnN0IGZ1bGxPcHRpb25zID0gT2JqZWN0LmFzc2lnbih7IGRlZmF1bHRWYWx1ZTogb3B0aW9ucy5kZWZhdWx0VmFsdWUsIHBvbHltZXJQcm9wZXJ0eToga2V5LCB1c2VMb2NhbFN0b3JhZ2U6IGZhbHNlIH0sIG9wdGlvbnMpOwogICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgY29uc3QgdXJpU3RvcmFnZU5hbWUgPSBnZXRVUklTdG9yYWdlTmFtZSh0aGlzLCBrZXkpOwogICAgICAgICAgICAgICAgY29uc3QgbmV3VmFsID0gdGhpc1tmdWxsT3B0aW9ucy5wb2x5bWVyUHJvcGVydHldOwogICAgICAgICAgICAgICAgc2V0KHVyaVN0b3JhZ2VOYW1lLCBuZXdWYWwsIGZ1bGxPcHRpb25zKTsKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHsgZ2V0LCBzZXQsIGdldEluaXRpYWxpemVyLCBnZXRPYnNlcnZlciwgZGlzcG9zZUJpbmRpbmcgfTsKICAgIH0KICAgIGZ1bmN0aW9uIG1pZ3JhdGVMZWdhY3lVUkxTY2hlbWUoKSB7CiAgICAgICAgLyoqCiAgICAgICAgICogVE9ETyhwc3lidXp6KTogbW92ZSB0byBzb21lIGNvbXBhdGliaWxpdHkgZmlsZS4KICAgICAgICAgKiBGb3IgZWFjaCBXSVQgVVJMIHBhcmFtIGluIHRoZSBsZWdhY3kgc2NoZW1lLCBjcmVhdGUgYW5vdGhlciBVUkwgcGFyYW0KICAgICAgICAgKiBpbiB0aGUgbmV3IHNjaGVtZS4gT25jZSBXSVQgbWlncmF0ZXMgdG8gdXNpbmcgdGhlIG5ldyBwbHVnaW4gQVBJCiAgICAgICAgICogYGdldFVSTFBsdWdpbkRhdGEoKWAsIHdlIGNhbiB1cGRhdGUgdGhpcyBtZXRob2QgdG8gZGVsZXRlIHRoZSBsZWdhY3kKICAgICAgICAgKiBzY2hlbWUgcGFyYW1zLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBsaXN0IG9mIHBhcmFtcyB3YXMgdGFrZW4gb24gMS8xNi8yMDIwLiBMdWNraWx5LCBXSVQgb25seSBzdG9yZWQKICAgICAgICAgKiBzdHJpbmdzLCBib29sZWFucy4KICAgICAgICAgKi8KICAgICAgICBjb25zdCB3aXRVcmxDb21wYXRpYmlsaXR5U2V0ID0gbmV3IFNldChbCiAgICAgICAgICAgICdleGFtcGxlc1BhdGgnLAogICAgICAgICAgICAnaGlkZU1vZGVsUGFuZTInLAogICAgICAgICAgICAnbW9kZWxOYW1lMScsCiAgICAgICAgICAgICdtb2RlbE5hbWUyJywKICAgICAgICAgICAgJ2luZmVyZW5jZUFkZHJlc3MxJywKICAgICAgICAgICAgJ2luZmVyZW5jZUFkZHJlc3MyJywKICAgICAgICAgICAgJ21vZGVsVHlwZScsCiAgICAgICAgICAgICdtb2RlbFZlcnNpb24xJywKICAgICAgICAgICAgJ21vZGVsVmVyc2lvbjInLAogICAgICAgICAgICAnbW9kZWxTaWduYXR1cmUxJywKICAgICAgICAgICAgJ21vZGVsU2lnbmF0dXJlMicsCiAgICAgICAgICAgICdtYXhFeGFtcGxlcycsCiAgICAgICAgICAgICdsYWJlbFZvY2FiUGF0aCcsCiAgICAgICAgICAgICdtdWx0aUNsYXNzJywKICAgICAgICAgICAgJ3NlcXVlbmNlRXhhbXBsZXMnLAogICAgICAgICAgICAnbWF4Q2xhc3Nlc1RvRGlzcGxheScsCiAgICAgICAgICAgICdzYW1wbGluZ09kZHMnLAogICAgICAgICAgICAndXNlUHJlZGljdEFwaScsCiAgICAgICAgICAgICdwcmVkaWN0SW5wdXRUZW5zb3InLAogICAgICAgICAgICAncHJlZGljdE91dHB1dFRlbnNvcicsCiAgICAgICAgXSk7CiAgICAgICAgY29uc3QgaXRlbXMgPSBjb21wb25lbnRUb0RpY3QocmVhZENvbXBvbmVudCgpKTsKICAgICAgICBpZiAoaXRlbXNbVEFCXSA9PT0gJ3doYXRpZicpIHsKICAgICAgICAgICAgZm9yIChsZXQgb2xkTmFtZSBvZiB3aXRVcmxDb21wYXRpYmlsaXR5U2V0KSB7CiAgICAgICAgICAgICAgICBpZiAob2xkTmFtZSBpbiBpdGVtcykgewogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9sZFZhbHVlID0gaXRlbXNbb2xkTmFtZV07CiAgICAgICAgICAgICAgICAgICAgaXRlbXNbYHAud2hhdGlmLiR7b2xkTmFtZX1gXSA9IG9sZFZhbHVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHdyaXRlQ29tcG9uZW50KGRpY3RUb0NvbXBvbmVudChpdGVtcykpOwogICAgICAgIHVybERpY3QgPSBpdGVtczsKICAgIH0KICAgIC8qKgogICAgICogR2V0IGEgdW5pcXVlIHN0b3JhZ2UgbmFtZSBmb3IgYSAoUG9seW1lciBjb21wb25lbnQsIHByb3BlcnR5TmFtZSkgdHVwbGUuCiAgICAgKgogICAgICogRElTQU1CSUdVQVRPUiBtdXN0IGJlIHNldCBvbiB0aGUgY29tcG9uZW50LCBpZiBvdGhlciBjb21wb25lbnRzIHVzZSB0aGUKICAgICAqIHNhbWUgcHJvcGVydHlOYW1lLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRVUklTdG9yYWdlTmFtZShjb21wb25lbnQsIHByb3BlcnR5TmFtZSkgewogICAgICAgIGNvbnN0IGQgPSBjb21wb25lbnRbRElTQU1CSUdVQVRPUl07CiAgICAgICAgY29uc3QgY29tcG9uZW50cyA9IGQgPT0gbnVsbCA/IFtwcm9wZXJ0eU5hbWVdIDogW2QsIHByb3BlcnR5TmFtZV07CiAgICAgICAgcmV0dXJuIGNvbXBvbmVudHMuam9pbignLicpOwogICAgfQogICAgLyoqCiAgICAgKiBSZWFkIGNvbXBvbmVudCBmcm9tIFVSSSAoZS5nLiByZXR1cm5zICJldmVudHMmcnVuUHJlZml4PXRyYWluKiIpLgogICAgICovCiAgICBmdW5jdGlvbiByZWFkQ29tcG9uZW50KCkgewogICAgICAgIHJldHVybiB1c2VIYXNoKCkgPyB3aW5kb3cubG9jYXRpb24uaGFzaC5zbGljZSgxKSA6IGdldEZha2VIYXNoKCk7CiAgICB9CiAgICAvKioKICAgICAqIFdyaXRlIGNvbXBvbmVudCB0byBVUkkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHdyaXRlQ29tcG9uZW50KGNvbXBvbmVudCwgdXNlTG9jYXRpb25SZXBsYWNlID0gZmFsc2UpIHsKICAgICAgICBpZiAodXNlSGFzaCgpKSB7CiAgICAgICAgICAgIGlmICh1c2VMb2NhdGlvblJlcGxhY2UpIHsKICAgICAgICAgICAgICAgIGNvbnN0IHVybCA9IG5ldyBVUkwod2luZG93LmxvY2F0aW9uLmhyZWYpOwogICAgICAgICAgICAgICAgdXJsLmhhc2ggPSBjb21wb25lbnQ7CiAgICAgICAgICAgICAgICB3aW5kb3cuaGlzdG9yeS5yZXBsYWNlU3RhdGUobnVsbCwgJycsIHVybC50b1N0cmluZygpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHdpbmRvdy5sb2NhdGlvbi5oYXNoID0gY29tcG9uZW50OwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBzZXRGYWtlSGFzaChjb21wb25lbnQpOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQ29udmVydCBkaWN0aW9uYXJ5IG9mIHN0cmluZ3MgaW50byBhIFVSSSBDb21wb25lbnQuCiAgICAgKiBBbGwga2V5IHZhbHVlIGVudHJpZXMgZ2V0IGFkZGVkIGFzIGtleSB2YWx1ZSBwYWlycyBpbiB0aGUgY29tcG9uZW50LAogICAgICogd2l0aCB0aGUgZXhjZXB0aW9uIG9mIGEga2V5IHdpdGggdGhlIFRBQiB2YWx1ZSwgd2hpY2ggaWYgcHJlc2VudAogICAgICogZ2V0cyBwcmVwZW5kZWQgdG8gdGhlIFVSSSBDb21wb25lbnQgc3RyaW5nIGZvciBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eQogICAgICogcmVhc29ucy4KICAgICAqLwogICAgZnVuY3Rpb24gZGljdFRvQ29tcG9uZW50KGl0ZW1zKSB7CiAgICAgICAgbGV0IGNvbXBvbmVudCA9ICcnOwogICAgICAgIC8vIEFkZCB0aGUgdGFiIG5hbWUgZS5nLiAnZXZlbnRzJywgJ2ltYWdlcycsICdoaXN0b2dyYW1zJyBhcyBhIHByZWZpeAogICAgICAgIC8vIGZvciBiYWNrd2FyZHMgY29tcGF0YmlsaXR5LgogICAgICAgIGlmIChpdGVtc1tUQUJdICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgY29tcG9uZW50ICs9IGl0ZW1zW1RBQl07CiAgICAgICAgfQogICAgICAgIC8vIEpvaW4gb3RoZXIgc3RyaW5ncyB3aXRoICZrZXk9dmFsdWUgbm90YXRpb24KICAgICAgICBjb25zdCBub25UYWIgPSBPYmplY3Qua2V5cyhpdGVtcykKICAgICAgICAgICAgLm1hcCgoa2V5KSA9PiBba2V5LCBpdGVtc1trZXldXSkKICAgICAgICAgICAgLmZpbHRlcigocGFpcikgPT4gcGFpclswXSAhPT0gVEFCKQogICAgICAgICAgICAubWFwKChwYWlyKSA9PiB7CiAgICAgICAgICAgIHJldHVybiBlbmNvZGVVUklDb21wb25lbnQocGFpclswXSkgKyAnPScgKyBlbmNvZGVVUklDb21wb25lbnQocGFpclsxXSk7CiAgICAgICAgfSkKICAgICAgICAgICAgLmpvaW4oJyYnKTsKICAgICAgICByZXR1cm4gbm9uVGFiLmxlbmd0aCA+IDAgPyBjb21wb25lbnQgKyAnJicgKyBub25UYWIgOiBjb21wb25lbnQ7CiAgICB9CiAgICAvKioKICAgICAqIENvbnZlcnQgYSBVUkkgQ29tcG9uZW50IGludG8gYSBkaWN0aW9uYXJ5IG9mIHN0cmluZ3MuCiAgICAgKiBDb21wb25lbnQgc2hvdWxkIGNvbnNpc3Qgb2Yga2V5LXZhbHVlIHBhaXJzIGpvaW5lZCBieSBhIGRlbGltaXRlcgogICAgICogd2l0aCB0aGUgZXhjZXB0aW9uIG9mIHRoZSB0YWJOYW1lLgogICAgICogUmV0dXJucyBkaWN0IGNvbnNpc3Rpbmcgb2YgYWxsIGtleS12YWx1ZSBwYWlycyBhbmQKICAgICAqIGRpY3RbVEFCXSA9IHRhYk5hbWUKICAgICAqLwogICAgZnVuY3Rpb24gY29tcG9uZW50VG9EaWN0KGNvbXBvbmVudCkgewogICAgICAgIGNvbnN0IGl0ZW1zID0ge307CiAgICAgICAgY29uc3QgdG9rZW5zID0gY29tcG9uZW50LnNwbGl0KCcmJyk7CiAgICAgICAgdG9rZW5zLmZvckVhY2goKHRva2VuKSA9PiB7CiAgICAgICAgICAgIGNvbnN0IGt2ID0gdG9rZW4uc3BsaXQoJz0nKTsKICAgICAgICAgICAgLy8gU3BlY2lhbCBiYWNrd2FyZHMgY29tcGF0aWJpbGl0eSBmb3IgVVJJIGNvbXBvbmVudHMgbGlrZSAjc2NhbGFycy4KICAgICAgICAgICAgaWYgKGt2Lmxlbmd0aCA9PT0gMSkgewogICAgICAgICAgICAgICAgaXRlbXNbVEFCXSA9IGt2WzBdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGt2Lmxlbmd0aCA9PT0gMikgewogICAgICAgICAgICAgICAgaXRlbXNbZGVjb2RlVVJJQ29tcG9uZW50KGt2WzBdKV0gPSBkZWNvZGVVUklDb21wb25lbnQoa3ZbMV0pOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGl0ZW1zOwogICAgfQogICAgLyoqCiAgICAgKiBEZWxldGUgYSBrZXkgZnJvbSB0aGUgVVJJLgogICAgICovCiAgICBmdW5jdGlvbiB1bnNldEZyb21VUkkoa2V5KSB7CiAgICAgICAgY29uc3QgaXRlbXMgPSBjb21wb25lbnRUb0RpY3QocmVhZENvbXBvbmVudCgpKTsKICAgICAgICBkZWxldGUgaXRlbXNba2V5XTsKICAgICAgICB3cml0ZUNvbXBvbmVudChkaWN0VG9Db21wb25lbnQoaXRlbXMpKTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBUZlRhZ0ZpbHRlcmVyID0gY2xhc3MgVGZUYWdGaWx0ZXJlciBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fdGFnRmlsdGVyID0gZ2V0U3RyaW5nSW5pdGlhbGl6ZXIoJ3RhZ0ZpbHRlcicsIHsKICAgICAgICAgICAgICAgIGRlZmF1bHRWYWx1ZTogJycsCiAgICAgICAgICAgICAgICB1c2VMb2NhbFN0b3JhZ2U6IGZhbHNlLAogICAgICAgICAgICAgICAgcG9seW1lclByb3BlcnR5OiAnX3RhZ0ZpbHRlcicsCiAgICAgICAgICAgIH0pLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3RhZ0ZpbHRlck9ic2VydmVyID0gZ2V0U3RyaW5nT2JzZXJ2ZXIoJ3RhZ0ZpbHRlcicsIHsKICAgICAgICAgICAgICAgIGRlZmF1bHRWYWx1ZTogJycsCiAgICAgICAgICAgICAgICB1c2VMb2NhbFN0b3JhZ2U6IGZhbHNlLAogICAgICAgICAgICAgICAgcG9seW1lclByb3BlcnR5OiAnX3RhZ0ZpbHRlcicsCiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfY29tcHV0ZVRhZ0ZpbHRlcigpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3RhZ0ZpbHRlcjsKICAgICAgICB9CiAgICB9OwogICAgVGZUYWdGaWx0ZXJlci50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHBhcGVyLWlucHV0CiAgICAgIG5vLWxhYmVsLWZsb2F0PSIiCiAgICAgIGxhYmVsPSJGaWx0ZXIgdGFncyAocmVndWxhciBleHByZXNzaW9ucyBzdXBwb3J0ZWQpIgogICAgICB2YWx1ZT0ie3tfdGFnRmlsdGVyfX0iCiAgICAgIGNsYXNzPSJzZWFyY2gtaW5wdXQiCiAgICA+CiAgICAgIDxpcm9uLWljb24gcHJlZml4PSIiIGljb249InNlYXJjaCIgc2xvdD0icHJlZml4Ij48L2lyb24taWNvbj4KICAgIDwvcGFwZXItaW5wdXQ+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBtYXJnaW46IDEwcHggNXB4IDEwcHggMTBweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgY29tcHV0ZWQ6ICdfY29tcHV0ZVRhZ0ZpbHRlcihfdGFnRmlsdGVyKScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZlRhZ0ZpbHRlcmVyLnByb3RvdHlwZSwgInRhZ0ZpbHRlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfdGFnRmlsdGVyT2JzZXJ2ZXInLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZUYWdGaWx0ZXJlci5wcm90b3R5cGUsICJfdGFnRmlsdGVyIiwgdm9pZCAwKTsKICAgIFRmVGFnRmlsdGVyZXIgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi10YWctZmlsdGVyZXInKQogICAgXSwgVGZUYWdGaWx0ZXJlcik7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIEludGVyb3AgZm9yIFBvbHltZXIgMyBzdHlsaW5nCiAgICAgKgogICAgICogRnJvbSBodHRwczovL3BvbHltZXItbGlicmFyeS5wb2x5bWVyLXByb2plY3Qub3JnLzMuMC9kb2NzL2Rldmd1aWRlL3N0eWxlLXNoYWRvdy1kb206CiAgICAgKiAgIFRoZSBmb2xsb3dpbmcgcHJvY2VzcyBpcyBhIHdvcmthcm91bmQuIFdoaWxlIFBvbHltZXIgMy4wIGRvZXMgbm90IHVzZQogICAgICogICA8ZG9tLW1vZHVsZT4gZWxlbWVudHMgZm9yIHRlbXBsYXRpbmcsIHN0eWxlIG1vZHVsZXMgZG8uIFRoZSBmb2xsb3dpbmcgcHJvY2VzcwogICAgICogICBpcyBhIHdvcmthcm91bmQgZm9yIHRoaXMgZmFjdC4gVGhpcyBwcm9jZXNzIG1heSBiZSB1cGRhdGVkIGFzIHJlcXVpcmVkLgogICAgICovCiAgICBmdW5jdGlvbiByZWdpc3RlclN0eWxlRG9tTW9kdWxlKGFyZ3MpIHsKICAgICAgICBjb25zdCB7IG1vZHVsZU5hbWUsIHN0eWxlQ29udGVudCB9ID0gYXJnczsKICAgICAgICBjb25zdCBkb21Nb2R1bGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkb20tbW9kdWxlJyk7CiAgICAgICAgY29uc3QgdGVtcGxhdGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwogICAgICAgIGNvbnN0IHN0eWxlSW5jbHVkZXMgPSBbXTsKICAgICAgICBpZiAoYXJncy5zdHlsZURlcGVuZGVuY2llcykgewogICAgICAgICAgICBhcmdzLnN0eWxlRGVwZW5kZW5jaWVzLmZvckVhY2goKGRlcCkgPT4gewogICAgICAgICAgICAgICAgY29uc3Qgc3R5bGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzdHlsZScpOwogICAgICAgICAgICAgICAgc3R5bGUuc2V0QXR0cmlidXRlKCdpbmNsdWRlJywgZGVwKTsKICAgICAgICAgICAgICAgIHN0eWxlSW5jbHVkZXMucHVzaChzdHlsZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBjb25zdCBzdHlsZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3N0eWxlJyk7CiAgICAgICAgT2JqZWN0LmFzc2lnbihzdHlsZSwgeyB0ZXh0Q29udGVudDogc3R5bGVDb250ZW50IH0pOwogICAgICAgIHN0eWxlSW5jbHVkZXMuZm9yRWFjaCgoc3R5bGVFbGVtZW50KSA9PiB7CiAgICAgICAgICAgIHRlbXBsYXRlLmNvbnRlbnQuYXBwZW5kQ2hpbGQoc3R5bGVFbGVtZW50KTsKICAgICAgICB9KTsKICAgICAgICB0ZW1wbGF0ZS5jb250ZW50LmFwcGVuZENoaWxkKHN0eWxlKTsKICAgICAgICBkb21Nb2R1bGUuYXBwZW5kQ2hpbGQodGVtcGxhdGUpOwogICAgICAgIGRvbU1vZHVsZS5yZWdpc3Rlcihtb2R1bGVOYW1lKTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHJlZ2lzdGVyU3R5bGVEb21Nb2R1bGUoewogICAgICAgIG1vZHVsZU5hbWU6ICdkYXNoYm9hcmQtc3R5bGUnLAogICAgICAgIHN0eWxlRGVwZW5kZW5jaWVzOiBbJ2lyb24tZmxleCddLAogICAgICAgIHN0eWxlQ29udGVudDogYAogICAgICA6aG9zdCB7CiAgICAgICAgLS1zaWRlYmFyLXZlcnRpY2FsLXBhZGRpbmc6IDE1cHg7CiAgICAgICAgLS1zaWRlYmFyLWxlZnQtcGFkZGluZzogMzBweDsKICAgICAgfQoKICAgICAgW3Nsb3Q9J3NpZGViYXInXSB7CiAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIG1hcmdpbi1yaWdodDogMTBweDsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgcGFkZGluZzogNXB4IDA7CiAgICAgICAgdGV4dC1vdmVyZmxvdzogZWxsaXBzaXM7CiAgICAgIH0KCiAgICAgIC5zZXR0aW5ncyB7CiAgICAgICAgbWluLWhlaWdodDogNTBweDsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CgogICAgICAucnVucy1zZWxlY3RvciB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgbWluLWhlaWdodDogMjAwcHg7CiAgICAgIH0KCiAgICAgIHRmLXJ1bnMtc2VsZWN0b3IgewogICAgICAgIGZsZXgtZ3JvdzogMTsKICAgICAgICBmbGV4LXNocmluazogMTsKICAgICAgICBsZWZ0OiB2YXIoLS1zaWRlYmFyLWxlZnQtcGFkZGluZyk7CiAgICAgICAgbWF4LWhlaWdodDogY2FsYygxMDAlIC0gdmFyKC0tc2lkZWJhci12ZXJ0aWNhbC1wYWRkaW5nKSAqIDIpOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHJpZ2h0OiAwOwogICAgICB9CgogICAgICAuc2VhcmNoLWlucHV0IHsKICAgICAgICBtYXJnaW46IDEwcHggNXB4IDAgMTBweDsKICAgICAgfQoKICAgICAgLnNpZGViYXItc2VjdGlvbiB7CiAgICAgICAgYm9yZGVyLXRvcDogc29saWQgMXB4IHJnYmEoMCwgMCwgMCwgMC4xMik7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiAxMHB4OwogICAgICAgIHBhZGRpbmc6IHZhcigtLXNpZGViYXItdmVydGljYWwtcGFkZGluZykgMAogICAgICAgICAgdmFyKC0tc2lkZWJhci12ZXJ0aWNhbC1wYWRkaW5nKSB2YXIoLS1zaWRlYmFyLWxlZnQtcGFkZGluZyk7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyLXNlY3Rpb246Zmlyc3Qtb2YtdHlwZSB7CiAgICAgICAgYm9yZGVyOiBub25lOwogICAgICB9CgogICAgICAuc2lkZWJhci1zZWN0aW9uIHBhcGVyLWJ1dHRvbiB7CiAgICAgICAgbWFyZ2luOiA1cHg7CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyLXNlY3Rpb24gcGFwZXItYnV0dG9uOmZpcnN0LW9mLXR5cGUgewogICAgICAgIG1hcmdpbi1sZWZ0OiAwICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyLXNlY3Rpb24gcGFwZXItYnV0dG9uOmxhc3Qtb2YtdHlwZSB7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiAwICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyLXNlY3Rpb24gPiA6Zmlyc3QtY2hpbGQgewogICAgICAgIG1hcmdpbi10b3A6IDA7CiAgICAgICAgcGFkZGluZy10b3A6IDA7CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyLXNlY3Rpb24gPiA6bGFzdC1jaGlsZCB7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMDsKICAgICAgICBwYWRkaW5nLWJvdHRvbTogMDsKICAgICAgfQoKICAgICAgLnNpZGViYXItc2VjdGlvbiBoMyB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWdyZXktODAwKTsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgZm9udC13ZWlnaHQ6IG5vcm1hbDsKICAgICAgICBtYXJnaW46IDEwcHggMCA1cHg7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgIH0KCiAgICAgIHBhcGVyLWNoZWNrYm94IHsKICAgICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3I6IHZhcigtLXRiLXVpLWRhcmstYWNjZW50KTsKICAgICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tdGItdWktZGFyay1hY2NlbnQpOwogICAgICAgIGZvbnQtc2l6ZTogMTVweDsKICAgICAgICBtYXJnaW4tdG9wOiA1cHg7CiAgICAgIH0KICBgLAogICAgfSk7CgogICAgLyogQ29weXJpZ2h0IDIwMTYgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjb25zdCBzdHlsZSQxID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKTsKICAgIHN0eWxlJDEuc2V0QXR0cmlidXRlKCdpcycsICdjdXN0b20tc3R5bGUnKTsKICAgIHN0eWxlJDEudGV4dENvbnRlbnQgPSBgCiAgOnJvb3QgewogICAgLS10Yi1vcmFuZ2Utd2VhazogI2ZmYTcyNjsKICAgIC0tdGItb3JhbmdlLXN0cm9uZzogI2Y1N2MwMDsKICAgIC0tdGItb3JhbmdlLWRhcms6ICNkYzczMjA7CiAgICAtLXRiLWdyZXktZGFya2VyOiAjZTJlMmUyOwogICAgLS10Yi1ncmV5LWxpZ2h0ZXI6ICNmM2YzZjM7CiAgICAtLXRiLXVpLWRhcmstYWNjZW50OiAjNzU3NTc1OwogICAgLS10Yi11aS1saWdodC1hY2NlbnQ6ICNlMGUwZTA7CiAgICAtLXRiLWdyYXBoLWZhZGVkOiAjZTBkNGIzOwogIH0KYDsKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoc3R5bGUkMSk7CgogICAgLyogQ29weXJpZ2h0IDIwMTYgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICByZWdpc3RlclN0eWxlRG9tTW9kdWxlKHsKICAgICAgICBtb2R1bGVOYW1lOiAnc2Nyb2xsYmFyLXN0eWxlJywKICAgICAgICBzdHlsZUNvbnRlbnQ6IGAKICAgIC5zY3JvbGxiYXI6Oi13ZWJraXQtc2Nyb2xsYmFyLXRyYWNrIHsKICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgfQoKICAgIC5zY3JvbGxiYXI6Oi13ZWJraXQtc2Nyb2xsYmFyIHsKICAgICAgd2lkdGg6IDEwcHg7CiAgICB9CgogICAgLnNjcm9sbGJhcjo6LXdlYmtpdC1zY3JvbGxiYXItdGh1bWIgewogICAgICBib3JkZXItcmFkaXVzOiAxMHB4OwogICAgICAtd2Via2l0LWJveC1zaGFkb3c6IGluc2V0IDAgMCAycHggcmdiYSgwLCAwLCAwLCAwLjMpOwogICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1wYXBlci1ncmV5LTUwMCk7CiAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1ncmV5LTkwMCk7CiAgICB9CiAgICAuc2Nyb2xsYmFyIHsKICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgIH0KICBgLAogICAgfSk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZEYXNoYm9hcmRMYXlvdXQgPSBjbGFzcyBUZkRhc2hib2FyZExheW91dCBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgIH07CiAgICBUZkRhc2hib2FyZExheW91dC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPGRpdiBpZD0ic2lkZWJhciI+CiAgICAgIDxzbG90IG5hbWU9InNpZGViYXIiPjwvc2xvdD4KICAgIDwvZGl2PgoKICAgIDxkaXYgaWQ9ImNlbnRlciI+CiAgICAgIDxzbG90IG5hbWU9ImNlbnRlciIgY2xhc3M9InNjb2xsYmFyIj48L3Nsb3Q+CiAgICA8L2Rpdj4KICAgIDxzdHlsZSBpbmNsdWRlPSJzY3JvbGxiYXItc3R5bGUiPjwvc3R5bGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiByb3c7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CgogICAgICAjc2lkZWJhciB7CiAgICAgICAgZmxleDogMCAwIHZhcigtLXRmLWRhc2hib2FyZC1sYXlvdXQtc2lkZWJhci1iYXNpcywgMjUlKTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgbWF4LXdpZHRoOiB2YXIoLS10Zi1kYXNoYm9hcmQtbGF5b3V0LXNpZGViYXItbWF4LXdpZHRoLCAzNTBweCk7CiAgICAgICAgbWluLXdpZHRoOiB2YXIoLS10Zi1kYXNoYm9hcmQtbGF5b3V0LXNpZGViYXItbWluLXdpZHRoLCAyNzBweCk7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICB0ZXh0LW92ZXJmbG93OiBlbGxpcHNpczsKICAgICAgfQoKICAgICAgI2NlbnRlciB7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICAgIGZsZXgtc2hyaW5rOiAxOwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICB9CgogICAgICA6OnNsb3R0ZWQoW3Nsb3Q9J2NlbnRlciddKSB7CiAgICAgICAgY29udGFpbjogc3RyaWN0OwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CgogICAgICAudGYtZ3JhcGgtZGFzaGJvYXJkICNjZW50ZXIgewogICAgICAgIGJhY2tncm91bmQ6ICNmZmY7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIFRmRGFzaGJvYXJkTGF5b3V0ID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZGFzaGJvYXJkLWxheW91dCcpCiAgICBdLCBUZkRhc2hib2FyZExheW91dCk7CgogICAgLyogQ29weXJpZ2h0IDIwMTcgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjb25zdCBMSU1JVF9MT0NBTF9TVE9SQUdFX0tFWSA9ICdURi5UZW5zb3JCb2FyZC5QYWdpbmF0ZWRWaWV3LmxpbWl0JzsKICAgIGNvbnN0IERFRkFVTFRfTElNSVQgPSAxMjsgLy8gcmVhc29uYWJseSBzbWFsbCBhbmQgaGFzIGxvdHMgb2YgZmFjdG9ycwogICAgbGV0IF9saW1pdCA9IG51bGw7IC8vIGNhY2hlZCBsb2NhbFN0b3JhZ2UgdmFsdWUKICAgIGNvbnN0IGxpc3RlbmVycyA9IG5ldyBTZXQoKTsKICAgIC8qKgogICAgICogUmVnaXN0ZXIgYSBsaXN0ZW5lciAobnVsbGFyeSBmdW5jdGlvbikgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIHBhZ2UKICAgICAqIGxpbWl0IGNoYW5nZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFkZExpbWl0TGlzdGVuZXIobGlzdGVuZXIpIHsKICAgICAgICBsaXN0ZW5lcnMuYWRkKGxpc3RlbmVyKTsKICAgIH0KICAgIC8qKgogICAgICogUmVtb3ZlIGEgbGlzdGVuZXIgcmVnaXN0ZXJlZCB3aXRoIGBhZGRMaW1pdExpc3RlbmVyYC4KICAgICAqLwogICAgZnVuY3Rpb24gcmVtb3ZlTGltaXRMaXN0ZW5lcihsaXN0ZW5lcikgewogICAgICAgIGxpc3RlbmVycy5kZWxldGUobGlzdGVuZXIpOwogICAgfQogICAgZnVuY3Rpb24gZ2V0TGltaXQoKSB7CiAgICAgICAgaWYgKF9saW1pdCA9PSBudWxsKSB7CiAgICAgICAgICAgIF9saW1pdCA9IGdldE51bWJlcihMSU1JVF9MT0NBTF9TVE9SQUdFX0tFWSwgewogICAgICAgICAgICAgICAgdXNlTG9jYWxTdG9yYWdlOiB0cnVlLAogICAgICAgICAgICB9KTsKICAgICAgICAgICAgaWYgKF9saW1pdCA9PSBudWxsIHx8ICFpc0Zpbml0ZShfbGltaXQpIHx8IF9saW1pdCA8PSAwKSB7CiAgICAgICAgICAgICAgICBfbGltaXQgPSBERUZBVUxUX0xJTUlUOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBfbGltaXQ7CiAgICB9CiAgICBmdW5jdGlvbiBzZXRMaW1pdChsaW1pdCkgewogICAgICAgIGlmIChsaW1pdCAhPT0gTWF0aC5mbG9vcihsaW1pdCkpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBsaW1pdCBtdXN0IGJlIGFuIGludGVnZXIsIGJ1dCBnb3Q6ICR7bGltaXR9YCk7CiAgICAgICAgfQogICAgICAgIGlmIChsaW1pdCA8PSAwKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihgbGltaXQgbXVzdCBiZSBwb3NpdGl2ZSwgYnV0IGdvdDogJHtsaW1pdH1gKTsKICAgICAgICB9CiAgICAgICAgaWYgKGxpbWl0ID09PSBfbGltaXQpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBfbGltaXQgPSBsaW1pdDsKICAgICAgICBzZXROdW1iZXIoTElNSVRfTE9DQUxfU1RPUkFHRV9LRVksIF9saW1pdCwgewogICAgICAgICAgICB1c2VMb2NhbFN0b3JhZ2U6IHRydWUsCiAgICAgICAgfSk7CiAgICAgICAgbGlzdGVuZXJzLmZvckVhY2goKGxpc3RlbmVyKSA9PiB7CiAgICAgICAgICAgIGxpc3RlbmVyKCk7CiAgICAgICAgfSk7CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjbGFzcyBBcnJheVVwZGF0ZUhlbHBlciBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAgICB1cGRhdGVBcnJheVByb3AocHJvcCwgdmFsdWUsIGdldEtleSkgewogICAgICAgICAgICBsZXQgb3JpZyA9IHRoaXMuZ2V0KHByb3ApOwogICAgICAgICAgICBjb25zdCBuZXdWYWwgPSB2YWx1ZTsKICAgICAgICAgICAgaWYgKCFBcnJheS5pc0FycmF5KG5ld1ZhbCkpIHsKICAgICAgICAgICAgICAgIHRocm93IFJhbmdlRXJyb3IoYEV4cGVjdGVkIG5ldyB2YWx1ZSB0byAnJHtwcm9wfScgdG8gYmUgYW4gYXJyYXkuYCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gSW4gY2FzZSB1c2luZyBDb21wbGV4T2JzZXJ2ZXIsIHRoZSBtZXRob2QgY2FuIGJlIGludm9rZWQgYmVmb3JlIHRoZSBwcm9wCiAgICAgICAgICAgIC8vIGhhZCBhIGNoYW5jZSB0byBpbml0aWFsaXplIHByb3Blcmx5LgogICAgICAgICAgICBpZiAoIUFycmF5LmlzQXJyYXkob3JpZykpIHsKICAgICAgICAgICAgICAgIG9yaWcgPSBbXTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KHByb3AsIG9yaWcpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGxvb2t1cCA9IG5ldyBTZXQobmV3VmFsLm1hcCgoaXRlbSwgaSkgPT4gZ2V0S2V5KGl0ZW0sIGkpKSk7CiAgICAgICAgICAgIGxldCBvcmlnSW5kID0gMDsKICAgICAgICAgICAgbGV0IG5ld1ZhbEluZCA9IDA7CiAgICAgICAgICAgIHdoaWxlIChvcmlnSW5kIDwgb3JpZy5sZW5ndGggJiYgbmV3VmFsSW5kIDwgbmV3VmFsLmxlbmd0aCkgewogICAgICAgICAgICAgICAgaWYgKCFsb29rdXAuaGFzKGdldEtleShvcmlnW29yaWdJbmRdLCBvcmlnSW5kKSkpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnNwbGljZShwcm9wLCBvcmlnSW5kLCAxKTsKICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGdldEtleShvcmlnW29yaWdJbmRdLCBvcmlnSW5kKSA9PSBnZXRLZXkobmV3VmFsW25ld1ZhbEluZF0sIG5ld1ZhbEluZCkpIHsKICAgICAgICAgICAgICAgICAgICAvLyB1cGRhdGUgdGhlIGVsZW1lbnQuCiAgICAgICAgICAgICAgICAgICAgLy8gVE9ETyhzdGVwaGFud2xlZSk6IFdlIG1heSBiZSBhYmxlIHRvIHVwZGF0ZSB0aGUgb3JpZ2luYWwgcmVmZXJlbmNlIG9mCiAgICAgICAgICAgICAgICAgICAgLy8gdGhlIGB2YWx1ZWAgYnkgZGVlcC1jb3B5aW5nIHRoZSBuZXcgdmFsdWUgb3Zlci4KICAgICAgICAgICAgICAgICAgICB0aGlzLnNldChgJHtwcm9wfS4ke29yaWdJbmR9YCwgbmV3VmFsW25ld1ZhbEluZF0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5zcGxpY2UocHJvcCwgb3JpZ0luZCwgMCwgbmV3VmFsW25ld1ZhbEluZF0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbmV3VmFsSW5kKys7CiAgICAgICAgICAgICAgICBvcmlnSW5kKys7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG9yaWdJbmQgPCBvcmlnLmxlbmd0aCkgewogICAgICAgICAgICAgICAgdGhpcy5zcGxpY2UocHJvcCwgb3JpZ0luZCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG5ld1ZhbEluZCA8IG5ld1ZhbC5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIHRoaXMucHVzaChwcm9wLCAuLi5uZXdWYWwuc2xpY2UobmV3VmFsSW5kKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICB9CgogICAgLyoqCiAgICAgKiBUaGUgVGZEb21SZXBlYXRCZWhhdmlvciByZS1pbXBsZW1lbnRzIHBhcnQgb2YgdGhlIGRvbS1yZXBlYXQgdGVtcGxhdGUuCiAgICAgKiBJdCBjYW4gYmUgYXBwbGllZCB0byBhbnkgUG9seW1lciBjb21wb25lbnRzIHRvIG1ha2UgaXQgZG9tLXJlcGVhdC1saWtlLgogICAgICogVGhlIG1ham9yIGRpc2NyZXBlbmN5IGlzIGluIHN5bnRheCB3aGVuIHVzaW5nOgogICAgICoKICAgICAqICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0Ij4KICAgICAqICAgICAuLi4KICAgICAqICAgPC90ZW1wbGF0ZT4KICAgICAqICAgLy8gdmVyc3VzCiAgICAgKiAgIDxmb28tY29tcD4KICAgICAqICAgICA8dGVtcGxhdGU+CiAgICAgKiAgICAgICAuLi4KICAgICAqICAgICA8L3RlbXBsYXRlPgogICAgICogICA8L2Zvby1jb21wPgogICAgICoKICAgICAqIFdoZW4gaW1wbGVtZW50aW5nIHRoZSBiZWhhdmlvciwgdGhlIFBvbHltZXIgY29tcG9uZW50IGhhcyB0byBpbnZva2UKICAgICAqIGB0aGlzLnVwZGF0ZURvbShuZXdJdGVtcylgLiBPdGhlciBwcm90ZWN0ZWQgQVBJcyBhcmUgYHNldEdldEl0ZW1LZXlgIGFuZAogICAgICogYHNldENhY2hlU2l6ZWAgKHBsZWFzZSBzZWUgcmVzcGVjdGl2ZSBkb2MgZm9yIGRldGFpbHMpLgogICAgICovCiAgICBjbGFzcyBUZkRvbVJlcGVhdCBleHRlbmRzIEFycmF5VXBkYXRlSGVscGVyIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5hcyA9ICdpdGVtJzsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdoZXRoZXIgYWxsIHN0YW1wZWQgaXRlbXMgYXJlIGFjdGl2ZSBvciBub3QuCiAgICAgICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMuX2NvbnRlbnRBY3RpdmUgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9kb21Cb290c3RyYXBwZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fY3RvciA9IG51bGw7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBBIGxpc3Qgb2YgcmVuZGVyZWQgYW5kIG1vdW50ZWQgaXRlbXMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9yZW5kZXJlZEl0ZW1zID0gW107CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBBIG1hcCBvZiBzdGFtcGVkIGNoaWxkIGNvbXBvbmVudHMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9yZW5kZXJlZFRlbXBsYXRlSW5zdCA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdoZW4gaXRlbSBpcyByZW1vdmVkLCBpdCBpcyBwbGFjZWQgaW4gYSBjYWNoZSBhbmQgdGhlIG9sZGVzdCBpdGVtIGdldHMKICAgICAgICAgICAgICogcmVtb3ZlZCB3aGVuIExSVSBncm93cyBtb3JlIHRoYW4gc2l6ZSBvZiB0aGUgMnhfbGltaXQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9scnVDYWNoZWRJdGVtcyA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgdGhpcy5fY2FjaGVTaXplID0gMTA7CiAgICAgICAgICAgIHRoaXMuX2dldEl0ZW1LZXkgPSAoaXRlbSkgPT4gSlNPTi5zdHJpbmdpZnkoaXRlbSk7CiAgICAgICAgICAgIHRoaXMuX2lzQ29ubmVjdGVkID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICAgICB0aGlzLl9pc0Nvbm5lY3RlZCA9IHRydWU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIHNpemUgb2YgdGhlIERPTSBjYWNoZSB1c2VkIGZvciBvcHRpbWl6aW5nIHBlcmZvcm1hbmNlLiBUaGUKICAgICAgICAgKiBkZWZhdWx0IGNhY2hlIHNpemUgaXMgMTAuCiAgICAgICAgICovCiAgICAgICAgc2V0Q2FjaGVTaXplKHNpemUpIHsKICAgICAgICAgICAgdGhpcy5fY2FjaGVTaXplID0gc2l6ZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyBnZXRJdGVtS2V5LCBhIGZ1bmN0aW9uIHRoYXQgcmVxdWlyZXMgYSB1bmlxdWUgaWRlbnRpZmllciBmb3IgYW4KICAgICAgICAgKiBpdGVtLiBJdCBpcyB1c2VkIHRvIG9wdGltaXplIHBlcmZvcm1hbmNlIG9mIHJlZHJhd3MuIFRoZSBkZWZhdWx0IGlzCiAgICAgICAgICogSlNPTi5zdHJpbmdpZnkoaXRlbSkuCiAgICAgICAgICovCiAgICAgICAgc2V0R2V0SXRlbUtleShnZXRJdGVtS2V5KSB7CiAgICAgICAgICAgIHRoaXMuX2dldEl0ZW1LZXkgPSBnZXRJdGVtS2V5OwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBVcGRhdGVzIERPTSB0byByZWZsZWN0IGNoYW5nZXMgaW4gYGl0ZW1zYC4KICAgICAgICAgKi8KICAgICAgICB1cGRhdGVEb20oaXRlbXMpIHsKICAgICAgICAgICAgdGhpcy51cGRhdGVBcnJheVByb3AoJ19yZW5kZXJlZEl0ZW1zJywgaXRlbXMsIHRoaXMuX2dldEl0ZW1LZXkpOwogICAgICAgIH0KICAgICAgICBfZW5zdXJlVGVtcGxhdGl6ZWQoKSB7CiAgICAgICAgICAgIC8vIFBvbHltZXIgaXMgbm90IHJlYWR5IChhbmQgcHJvcHMvRE9NIGZvciB0aGUgY29tcG9uZW50cyBhcmUgbm90CiAgICAgICAgICAgIC8vIHBvcHVsYXRlZCkKICAgICAgICAgICAgaWYgKCF0aGlzLmlzQ29ubmVjdGVkKQogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICBpZiAoIXRoaXMuX2N0b3IpIHsKICAgICAgICAgICAgICAgIGNvbnN0IHRlbXBsYXRlTm9kZSA9IHRoaXMucXVlcnlTZWxlY3RvcigndGVtcGxhdGUnKTsKICAgICAgICAgICAgICAgIHRoaXMuX2N0b3IgPSB0ZW1wbGF0aXplKHRlbXBsYXRlTm9kZSwgdGhpcywgewogICAgICAgICAgICAgICAgICAgIHBhcmVudE1vZGVsOiB0cnVlLAogICAgICAgICAgICAgICAgICAgIGluc3RhbmNlUHJvcHM6IHsKICAgICAgICAgICAgICAgICAgICAgICAgW3RoaXMuYXNdOiB0cnVlLAogICAgICAgICAgICAgICAgICAgICAgICBhY3RpdmU6IHRoaXMuX2NvbnRlbnRBY3RpdmUsCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICBmb3J3YXJkSG9zdFByb3A6IGZ1bmN0aW9uIChwcm9wLCB2YWx1ZSkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9yZW5kZXJlZFRlbXBsYXRlSW5zdC5mb3JFYWNoKChpbnN0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbnN0LmZvcndhcmRIb3N0UHJvcChwcm9wLCB2YWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgX2Jvb3RzdHJhcERvbSgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9lbnN1cmVUZW1wbGF0aXplZCgpIHx8IHRoaXMuX2RvbUJvb3RzdHJhcHBlZCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IG9ic2VydmVyID0gbmV3IE11dGF0aW9uT2JzZXJ2ZXIoKG11dGF0aW9uc0xpc3QpID0+IHsKICAgICAgICAgICAgICAgIGZvciAoY29uc3QgbXV0YXRpb24gb2YgbXV0YXRpb25zTGlzdCkgewogICAgICAgICAgICAgICAgICAgIGlmIChtdXRhdGlvbi50eXBlID09PSAnY2hpbGRMaXN0JykgewogICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGNvbnN0IG5vZGUgb2YgQXJyYXkuZnJvbShtdXRhdGlvbi5hZGRlZE5vZGVzKSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG5vZGUgaW5zdGFuY2VvZiBFbGVtZW50KSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbm9kZS5zZXRBdHRyaWJ1dGUoJ3Nsb3QnLCAnaXRlbXMnKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIG9ic2VydmVyLm9ic2VydmUodGhpcywgeyBjaGlsZExpc3Q6IHRydWUgfSk7CiAgICAgICAgICAgIEFycmF5LmZyb20odGhpcy5jaGlsZHJlbikuZm9yRWFjaCgoY2hpbGQpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMucmVtb3ZlQ2hpbGQoY2hpbGQpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fbHJ1Q2FjaGVkSXRlbXMuY2xlYXIoKTsKICAgICAgICAgICAgdGhpcy5fcmVuZGVyZWRJdGVtcy5mb3JFYWNoKChpdGVtLCBpbmRleCkgPT4gdGhpcy5faW5zZXJ0SXRlbShpdGVtLCBpbmRleCkpOwogICAgICAgICAgICB0aGlzLl9kb21Cb290c3RyYXBwZWQgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBfdXBkYXRlQWN0aXZlKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX2RvbUJvb3RzdHJhcHBlZCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgQXJyYXkuZnJvbSh0aGlzLl9yZW5kZXJlZFRlbXBsYXRlSW5zdC52YWx1ZXMoKSkuZm9yRWFjaCgoaW5zdCkgPT4gewogICAgICAgICAgICAgICAgaW5zdC5ub3RpZnlQYXRoKCdhY3RpdmUnLCB0aGlzLl9jb250ZW50QWN0aXZlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVEb20oZXZlbnQgLy8gUG9seW1lckRlZXBQcm9wZXJ0eUNoYW5nZTxULCBQb2x5bWVyU3BsaWNlQ2hhbmdlPFRbXT4+CiAgICAgICAgKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fZG9tQm9vdHN0cmFwcGVkKQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAvLyBUaGVzZSBhcmUgdW5pbnRlcmVzdGluZy4KICAgICAgICAgICAgaWYgKGV2ZW50LnBhdGggPT0gJ19yZW5kZXJlZEl0ZW1zJyB8fAogICAgICAgICAgICAgICAgZXZlbnQucGF0aCA9PSAnX3JlbmRlcmVkSXRlbXMubGVuZ3RoJykgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChldmVudC5wYXRoID09PSAnX3JlbmRlcmVkSXRlbXMuc3BsaWNlcycpIHsKICAgICAgICAgICAgICAgIGNvbnN0IHZhbHVlID0gZXZlbnQudmFsdWU7IC8vIFBvbHltZXJTcGxpY2VDaGFuZ2U8VFtdPjsKICAgICAgICAgICAgICAgIHZhbHVlLmluZGV4U3BsaWNlcy5mb3JFYWNoKChzcGxpY2UpID0+IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCB7IGluZGV4LCBhZGRlZENvdW50LCBvYmplY3QsIHJlbW92ZWQgfSA9IHNwbGljZTsKICAgICAgICAgICAgICAgICAgICByZW1vdmVkLmZvckVhY2goKGl0ZW0pID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fcmVtb3ZlSXRlbShpdGVtLCB0aGlzLmNoaWxkcmVuW2luZGV4XSk7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgb2JqZWN0CiAgICAgICAgICAgICAgICAgICAgICAgIC5zbGljZShpbmRleCwgaW5kZXggKyBhZGRlZENvdW50KQogICAgICAgICAgICAgICAgICAgICAgICAuZm9yRWFjaCgoaXRlbSwgaW5kKSA9PiB0aGlzLl9pbnNlcnRJdGVtKGl0ZW0sIGluZGV4ICsgaW5kKSk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fdHJpbUNhY2hlKCk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgc3RhbXBlZCBhbmQgbW91bnRlZCBET00gbW9kZWwgYnkgbm90aWZ5aW5nLgogICAgICAgICAgICAgICAgY29uc3Qga2V5ID0gdGhpcy5fZ2V0SXRlbUtleShldmVudC52YWx1ZSk7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fcmVuZGVyZWRUZW1wbGF0ZUluc3QuaGFzKGtleSkpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9yZW5kZXJlZFRlbXBsYXRlSW5zdC5nZXQoa2V5KS5ub3RpZnlQYXRoKHRoaXMuYXMsIGV2ZW50LnZhbHVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGNvbnNvbGUud2FybihgRXhwZWN0ZWQgJyR7a2V5fScgdG8gZXhpc3QgaW4gdGhlIERPTSBidXQgYCArIGBjb3VsZCBub3QgZmluZCBvbmUuYCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgX2luc2VydEl0ZW0oaXRlbSwgYXRJbmRleCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX2Vuc3VyZVRlbXBsYXRpemVkKCkpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcignRXhwZWN0ZWQgdGVtcGxhdGl6ZWQgYmVmb3JlIGluc2VydGluZyBhbiBpdGVtJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IGZyYWdPckVsOwogICAgICAgICAgICBjb25zdCBrZXkgPSB0aGlzLl9nZXRJdGVtS2V5KGl0ZW0pOwogICAgICAgICAgICBpZiAodGhpcy5fbHJ1Q2FjaGVkSXRlbXMuaGFzKGtleSkpIHsKICAgICAgICAgICAgICAgIGZyYWdPckVsID0gdGhpcy5fbHJ1Q2FjaGVkSXRlbXMuZ2V0KGtleSk7CiAgICAgICAgICAgICAgICB0aGlzLl9scnVDYWNoZWRJdGVtcy5kZWxldGUoa2V5KTsKICAgICAgICAgICAgICAgIHRoaXMuX3JlbmRlcmVkVGVtcGxhdGVJbnN0CiAgICAgICAgICAgICAgICAgICAgLmdldChrZXkpCiAgICAgICAgICAgICAgICAgICAgLm5vdGlmeVBhdGgoJ2FjdGl2ZScsIHRoaXMuX2NvbnRlbnRBY3RpdmUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgY29uc3QgcHJvcCA9IHsgW3RoaXMuYXNdOiBpdGVtLCBhY3RpdmU6IHRoaXMuX2NvbnRlbnRBY3RpdmUgfTsKICAgICAgICAgICAgICAgIGNvbnN0IGluc3QgPSBuZXcgdGhpcy5fY3Rvcihwcm9wKTsKICAgICAgICAgICAgICAgIGZyYWdPckVsID0gaW5zdC5yb290OwogICAgICAgICAgICAgICAgdGhpcy5fcmVuZGVyZWRUZW1wbGF0ZUluc3Quc2V0KGtleSwgaW5zdCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuY2hpbGRyZW5bYXRJbmRleF0pIHsKICAgICAgICAgICAgICAgIHRoaXMuaW5zZXJ0QmVmb3JlKGZyYWdPckVsLCB0aGlzLmNoaWxkcmVuW2F0SW5kZXhdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGNvbnN0IGVscyA9IGZyYWdPckVsLm5vZGVUeXBlID09IE5vZGUuRE9DVU1FTlRfRlJBR01FTlRfTk9ERQogICAgICAgICAgICAgICAgICAgID8gQXJyYXkuZnJvbShmcmFnT3JFbC5jaGlsZHJlbikKICAgICAgICAgICAgICAgICAgICA6IFtmcmFnT3JFbF07CiAgICAgICAgICAgICAgICBlbHMuZm9yRWFjaCgoZWwpID0+IGVsLnNldEF0dHJpYnV0ZSgnc2xvdCcsICdpdGVtcycpKTsKICAgICAgICAgICAgICAgIHRoaXMuYXBwZW5kQ2hpbGQoZnJhZ09yRWwpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9yZW1vdmVJdGVtKGl0ZW0sIG5vZGUpIHsKICAgICAgICAgICAgaWYgKG5vZGUucGFyZW50Tm9kZSkKICAgICAgICAgICAgICAgIG5vZGUucGFyZW50Tm9kZS5yZW1vdmVDaGlsZChub2RlKTsKICAgICAgICAgICAgY29uc3Qga2V5ID0gdGhpcy5fZ2V0SXRlbUtleShpdGVtKTsKICAgICAgICAgICAgdGhpcy5fbHJ1Q2FjaGVkSXRlbXMuc2V0KGtleSwgbm9kZSk7CiAgICAgICAgICAgIHRoaXMuX3JlbmRlcmVkVGVtcGxhdGVJbnN0LmdldChrZXkpLm5vdGlmeVBhdGgoJ2FjdGl2ZScsIGZhbHNlKTsKICAgICAgICB9CiAgICAgICAgX3RyaW1DYWNoZSgpIHsKICAgICAgICAgICAgd2hpbGUgKHRoaXMuX2xydUNhY2hlZEl0ZW1zLnNpemUgPiB0aGlzLl9jYWNoZVNpemUpIHsKICAgICAgICAgICAgICAgIGNvbnN0IFtmaXJzdEtleV0gPSB0aGlzLl9scnVDYWNoZWRJdGVtcy5rZXlzKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9scnVDYWNoZWRJdGVtcy5kZWxldGUoZmlyc3RLZXkpOwogICAgICAgICAgICAgICAgdGhpcy5fcmVuZGVyZWRUZW1wbGF0ZUluc3QuZGVsZXRlKGZpcnN0S2V5KTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZEb21SZXBlYXQucHJvdG90eXBlLCAiYXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZEb21SZXBlYXQucHJvdG90eXBlLCAiaXRlbXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmRG9tUmVwZWF0LnByb3RvdHlwZSwgIl9jb250ZW50QWN0aXZlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmRG9tUmVwZWF0LnByb3RvdHlwZSwgIl9kb21Cb290c3RyYXBwZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfY3RvciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfcmVuZGVyZWRJdGVtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmRG9tUmVwZWF0LnByb3RvdHlwZSwgIl9yZW5kZXJlZFRlbXBsYXRlSW5zdCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmRG9tUmVwZWF0LnByb3RvdHlwZSwgIl9scnVDYWNoZWRJdGVtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmRG9tUmVwZWF0LnByb3RvdHlwZSwgIl9jYWNoZVNpemUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfZ2V0SXRlbUtleSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfaXNDb25uZWN0ZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX2lzQ29ubmVjdGVkJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfYm9vdHN0cmFwRG9tIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdfY29udGVudEFjdGl2ZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZEb21SZXBlYXQucHJvdG90eXBlLCAiX3VwZGF0ZUFjdGl2ZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX3JlbmRlcmVkSXRlbXMuKicsICdfZG9tQm9vdHN0cmFwcGVkJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbT2JqZWN0XSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfdXBkYXRlRG9tIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdfY2FjaGVTaXplJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkRvbVJlcGVhdC5wcm90b3R5cGUsICJfdHJpbUNhY2hlIiwgbnVsbCk7CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcgPSBjbGFzcyBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldyBleHRlbmRzIFRmRG9tUmVwZWF0IHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5kaXNhYmxlUGFnaW5hdGlvbiA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLmdldENhdGVnb3J5SXRlbUtleSA9IChpdGVtKSA9PiBKU09OLnN0cmluZ2lmeShpdGVtKTsKICAgICAgICAgICAgdGhpcy5fbGltaXQgPSAxMjsKICAgICAgICAgICAgdGhpcy5fYWN0aXZlSW5kZXggPSAwOwogICAgICAgICAgICB0aGlzLl9wYWdlSW5wdXRSYXdWYWx1ZSA9ICcnOwogICAgICAgICAgICB0aGlzLl9wYWdlSW5wdXRGb2N1c2VkID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlQ291bnQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmNhdGVnb3J5Lml0ZW1zLmxlbmd0aDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9oYXNNdWx0aXBsZSgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvdW50ID4gMTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZVBhbmUoKSB7CiAgICAgICAgICAgIHRoaXMub3BlbmVkID0gIXRoaXMub3BlbmVkOwogICAgICAgIH0KICAgICAgICBfY2hhbmdlQ29udGVudEFjdGl2ZShvcGVuZWQpIHsKICAgICAgICAgICAgdGhpcy5fY29udGVudEFjdGl2ZSA9IG9wZW5lZDsKICAgICAgICB9CiAgICAgICAgX29uUGFuZVJlbmRlcmVkQ2hhbmdlZChuZXdSZW5kZXJlZCwgb2xkUmVuZGVyZWQpIHsKICAgICAgICAgICAgaWYgKG5ld1JlbmRlcmVkICYmIG5ld1JlbmRlcmVkICE9PSBvbGRSZW5kZXJlZCkgewogICAgICAgICAgICAgICAgLy8gRm9yY2UgZG9tLWlmIHJlbmRlciB3aXRob3V0IHdhaXRpbmcgZm9yIG9uZSByQUYuCiAgICAgICAgICAgICAgICB0aGlzLiQuaWZSZW5kZXJlZC5yZW5kZXIoKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfY29tcHV0ZVBhbmVSZW5kZXJlZChjYXRlZ29yeSkgewogICAgICAgICAgICAvLyBTaG93IGEgY2F0ZWdvcnkgdW5sZXNzIGl0J3MgYSBzZWFyY2ggcmVzdWx0cyBjYXRlZ29yeSB3aGVyZQogICAgICAgICAgICAvLyB0aGVyZSB3YXNuJ3QgYWN0dWFsbHkgYSBzZWFyY2ggcXVlcnkuCiAgICAgICAgICAgIHJldHVybiAhKGNhdGVnb3J5Lm1ldGFkYXRhLnR5cGUgPT09IENhdGVnb3J5VHlwZS5TRUFSQ0hfUkVTVUxUUyAmJgogICAgICAgICAgICAgICAgY2F0ZWdvcnkubmFtZSA9PT0gJycpOwogICAgICAgIH0KICAgICAgICBnZXQgX2l0ZW1zUmVuZGVyZWQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9wYW5lUmVuZGVyZWQgJiYgdGhpcy5vcGVuZWQ7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlSXNTZWFyY2hSZXN1bHRzKHR5cGUpIHsKICAgICAgICAgICAgcmV0dXJuIHR5cGUgPT09IENhdGVnb3J5VHlwZS5TRUFSQ0hfUkVTVUxUUzsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVJc0ludmFsaWRTZWFyY2hSZXN1bHRzKG1ldGFkYXRhKSB7CiAgICAgICAgICAgIHJldHVybiAobWV0YWRhdGEudHlwZSA9PT0gQ2F0ZWdvcnlUeXBlLlNFQVJDSF9SRVNVTFRTICYmICFtZXRhZGF0YS52YWxpZFJlZ2V4KTsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVJc1VuaXZlcnNhbFNlYXJjaFF1ZXJ5KG1ldGFkYXRhKSB7CiAgICAgICAgICAgIHJldHVybiAobWV0YWRhdGEudHlwZSA9PT0gQ2F0ZWdvcnlUeXBlLlNFQVJDSF9SRVNVTFRTICYmIG1ldGFkYXRhLnVuaXZlcnNhbFJlZ2V4KTsKICAgICAgICB9CiAgICAgICAgX2lzQ29tcG9zaXRlU2VhcmNoKCkgewogICAgICAgICAgICBjb25zdCB7IHR5cGUsIGNvbXBvc2l0ZVNlYXJjaCB9ID0gdGhpcy5jYXRlZ29yeS5tZXRhZGF0YTsKICAgICAgICAgICAgcmV0dXJuIGNvbXBvc2l0ZVNlYXJjaCAmJiB0eXBlID09PSBDYXRlZ29yeVR5cGUuU0VBUkNIX1JFU1VMVFM7CiAgICAgICAgfQogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgICBzdXBlci5yZWFkeSgpOwogICAgICAgICAgICB0aGlzLm9wZW5lZCA9IHRoaXMuaW5pdGlhbE9wZW5lZCA9PSBudWxsID8gdHJ1ZSA6IHRoaXMuaW5pdGlhbE9wZW5lZDsKICAgICAgICAgICAgdGhpcy5fbGltaXRMaXN0ZW5lciA9ICgpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfbGltaXQnLCBnZXRMaW1pdCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgYWRkTGltaXRMaXN0ZW5lcih0aGlzLl9saW1pdExpc3RlbmVyKTsKICAgICAgICAgICAgdGhpcy5fbGltaXRMaXN0ZW5lcigpOwogICAgICAgIH0KICAgICAgICBkZXRhY2hlZCgpIHsKICAgICAgICAgICAgcmVtb3ZlTGltaXRMaXN0ZW5lcih0aGlzLl9saW1pdExpc3RlbmVyKTsKICAgICAgICB9CiAgICAgICAgX3VwZGF0ZVJlbmRlcmVkSXRlbXMoKSB7CiAgICAgICAgICAgIHZhciBpdGVtc1JlbmRlcmVkID0gdGhpcy5faXRlbXNSZW5kZXJlZDsKICAgICAgICAgICAgdmFyIGxpbWl0ID0gdGhpcy5fbGltaXQ7CiAgICAgICAgICAgIHZhciBhY3RpdmVJbmRleCA9IHRoaXMuX2FjdGl2ZUluZGV4OwogICAgICAgICAgICB2YXIgZGlzYWJsZVBhZ2luYXRpb24gPSB0aGlzLmRpc2FibGVQYWdpbmF0aW9uOwogICAgICAgICAgICBpZiAoIWl0ZW1zUmVuZGVyZWQpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIGNvbnN0IGFjdGl2ZVBhZ2VJbmRleCA9IE1hdGguZmxvb3IoYWN0aXZlSW5kZXggLyBsaW1pdCk7CiAgICAgICAgICAgIGNvbnN0IGl0ZW1zID0gdGhpcy5jYXRlZ29yeS5pdGVtcyB8fCBbXTsKICAgICAgICAgICAgY29uc3QgZG9tSXRlbXMgPSBkaXNhYmxlUGFnaW5hdGlvbgogICAgICAgICAgICAgICAgPyBpdGVtcwogICAgICAgICAgICAgICAgOiBpdGVtcy5zbGljZShhY3RpdmVQYWdlSW5kZXggKiBsaW1pdCwgKGFjdGl2ZVBhZ2VJbmRleCArIDEpICogbGltaXQpOwogICAgICAgICAgICB0aGlzLnVwZGF0ZURvbShkb21JdGVtcyk7CiAgICAgICAgfQogICAgICAgIF9saW1pdENoYW5nZWQobGltaXQpIHsKICAgICAgICAgICAgdGhpcy5zZXRDYWNoZVNpemUobGltaXQgKiAyKTsKICAgICAgICB9CiAgICAgICAgX2dldENhdGVnb3J5SXRlbUtleUNoYW5nZWQoKSB7CiAgICAgICAgICAgIHRoaXMuc2V0R2V0SXRlbUtleSh0aGlzLmdldENhdGVnb3J5SXRlbUtleSk7CiAgICAgICAgfQogICAgICAgIGdldCBfY3VycmVudFBhZ2UoKSB7CiAgICAgICAgICAgIHZhciBsaW1pdCA9IHRoaXMuX2xpbWl0OwogICAgICAgICAgICB2YXIgYWN0aXZlSW5kZXggPSB0aGlzLl9hY3RpdmVJbmRleDsKICAgICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IoYWN0aXZlSW5kZXggLyBsaW1pdCkgKyAxOwogICAgICAgIH0KICAgICAgICBfY29tcHV0ZVBhZ2VDb3VudChfLCBsaW1pdCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5jYXRlZ29yeSA/IE1hdGguY2VpbCh0aGlzLmNhdGVnb3J5Lml0ZW1zLmxlbmd0aCAvIGxpbWl0KSA6IDA7CiAgICAgICAgfQogICAgICAgIGdldCBfbXVsdGlwbGVQYWdlc0V4aXN0KCkgewogICAgICAgICAgICB2YXIgcGFnZUNvdW50ID0gdGhpcy5fcGFnZUNvdW50OwogICAgICAgICAgICB2YXIgZGlzYWJsZVBhZ2luYXRpb24gPSB0aGlzLmRpc2FibGVQYWdpbmF0aW9uOwogICAgICAgICAgICByZXR1cm4gIWRpc2FibGVQYWdpbmF0aW9uICYmIHBhZ2VDb3VudCA+IDE7CiAgICAgICAgfQogICAgICAgIGdldCBfaGFzUHJldmlvdXNQYWdlKCkgewogICAgICAgICAgICB2YXIgY3VycmVudFBhZ2UgPSB0aGlzLl9jdXJyZW50UGFnZTsKICAgICAgICAgICAgcmV0dXJuIGN1cnJlbnRQYWdlID4gMTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9oYXNOZXh0UGFnZSgpIHsKICAgICAgICAgICAgdmFyIGN1cnJlbnRQYWdlID0gdGhpcy5fY3VycmVudFBhZ2U7CiAgICAgICAgICAgIHZhciBwYWdlQ291bnQgPSB0aGlzLl9wYWdlQ291bnQ7CiAgICAgICAgICAgIHJldHVybiBjdXJyZW50UGFnZSA8IHBhZ2VDb3VudDsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVJbnB1dFdpZHRoKHBhZ2VDb3VudCkgewogICAgICAgICAgICAvLyBBZGQgMjBweCBmb3IgdGhlICsvLSBhcnJvd3MgYWRkZWQgYnkgYnJvd3NlcnMuCiAgICAgICAgICAgIHJldHVybiBgY2FsYygke3BhZ2VDb3VudC50b1N0cmluZygpLmxlbmd0aH1lbSArIDIwcHgpYDsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogVXBkYXRlIF9hY3RpdmVJbmRleCwgbWFpbnRhaW5pbmcgaXRzIHJhbmdlIGludmFyaWFudC4KICAgICAgICAgKi8KICAgICAgICBfc2V0QWN0aXZlSW5kZXgoaW5kZXgpIHsKICAgICAgICAgICAgY29uc3QgbWF4SW5kZXggPSAodGhpcy5jYXRlZ29yeS5pdGVtcyB8fCBbXSkubGVuZ3RoIC0gMTsKICAgICAgICAgICAgaWYgKGluZGV4ID4gbWF4SW5kZXgpIHsKICAgICAgICAgICAgICAgIGluZGV4ID0gbWF4SW5kZXg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGluZGV4IDwgMCkgewogICAgICAgICAgICAgICAgaW5kZXggPSAwOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuc2V0KCdfYWN0aXZlSW5kZXgnLCBpbmRleCk7CiAgICAgICAgfQogICAgICAgIF9jbGFtcEFjdGl2ZUluZGV4KCkgewogICAgICAgICAgICB0aGlzLl9zZXRBY3RpdmVJbmRleCh0aGlzLl9hY3RpdmVJbmRleCk7CiAgICAgICAgfQogICAgICAgIF9wZXJmb3JtUHJldmlvdXNQYWdlKCkgewogICAgICAgICAgICB0aGlzLl9zZXRBY3RpdmVJbmRleCh0aGlzLl9hY3RpdmVJbmRleCAtIHRoaXMuX2xpbWl0KTsKICAgICAgICB9CiAgICAgICAgX3BlcmZvcm1OZXh0UGFnZSgpIHsKICAgICAgICAgICAgdGhpcy5fc2V0QWN0aXZlSW5kZXgodGhpcy5fYWN0aXZlSW5kZXggKyB0aGlzLl9saW1pdCk7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlUGFnZUlucHV0VmFsdWUoZm9jdXNlZCwgcmF3VmFsdWUsIGN1cnJlbnRQYWdlKSB7CiAgICAgICAgICAgIHJldHVybiBmb2N1c2VkID8gcmF3VmFsdWUgOiBjdXJyZW50UGFnZS50b1N0cmluZygpOwogICAgICAgIH0KICAgICAgICBfaGFuZGxlUGFnZUlucHV0RXZlbnQoZSkgewogICAgICAgICAgICB0aGlzLnNldCgnX3BhZ2VJbnB1dFJhd1ZhbHVlJywgZS50YXJnZXQudmFsdWUpOwogICAgICAgICAgICBjb25zdCBvbmVJbmRleGVkUGFnZSA9IE51bWJlcihlLnRhcmdldC52YWx1ZSB8fCBOYU4pOwogICAgICAgICAgICBpZiAoaXNOYU4ob25lSW5kZXhlZFBhZ2UpKQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICBjb25zdCBwYWdlID0gTWF0aC5tYXgoMSwgTWF0aC5taW4ob25lSW5kZXhlZFBhZ2UsIHRoaXMuX3BhZ2VDb3VudCkpIC0gMTsKICAgICAgICAgICAgdGhpcy5fc2V0QWN0aXZlSW5kZXgodGhpcy5fbGltaXQgKiBwYWdlKTsKICAgICAgICB9CiAgICAgICAgX2hhbmRsZVBhZ2VDaGFuZ2VFdmVudCgpIHsKICAgICAgICAgICAgLy8gT2NjdXJzIG9uIEVudGVyLCBldGMuIENvbW1pdCB0aGUgdHJ1ZSBzdGF0ZS4KICAgICAgICAgICAgdGhpcy5zZXQoJ19wYWdlSW5wdXRSYXdWYWx1ZScsIHRoaXMuX2N1cnJlbnRQYWdlLnRvU3RyaW5nKCkpOwogICAgICAgIH0KICAgICAgICBfaGFuZGxlUGFnZUZvY3VzRXZlbnQoKSB7CiAgICAgICAgICAgIC8vIERpc2NhcmQgYW55IG9sZCAob3IgdW5pbml0aWFsaXplZCkgc3RhdGUgYmVmb3JlIHdlIGdyYW50IGZvY3VzLgogICAgICAgICAgICB0aGlzLnNldCgnX3BhZ2VJbnB1dFJhd1ZhbHVlJywgdGhpcy5fcGFnZUlucHV0VmFsdWUpOwogICAgICAgICAgICB0aGlzLnNldCgnX3BhZ2VJbnB1dEZvY3VzZWQnLCB0cnVlKTsKICAgICAgICB9CiAgICAgICAgX2hhbmRsZVBhZ2VCbHVyRXZlbnQoKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfcGFnZUlucHV0Rm9jdXNlZCcsIGZhbHNlKTsKICAgICAgICB9CiAgICAgICAgX3VwZGF0ZVBhZ2VJbnB1dFZhbHVlKG5ld1ZhbHVlKSB7CiAgICAgICAgICAgIC8vIEZvcmNlIHR3by13YXkgYmluZGluZy4KICAgICAgICAgICAgY29uc3QgcGFnZUlucHV0ID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3IoJyNwYWdlLWlucHV0IGlucHV0Jyk7CiAgICAgICAgICAgIGlmIChwYWdlSW5wdXQpIHsKICAgICAgICAgICAgICAgIHBhZ2VJbnB1dC52YWx1ZSA9IG5ld1ZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF91cGRhdGVJbnB1dFdpZHRoKCkgewogICAgICAgICAgICB0aGlzLnVwZGF0ZVN0eWxlcyh7CiAgICAgICAgICAgICAgICAnLS10Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldy1wYWdlLWlucHV0LXdpZHRoJzogdGhpcy5faW5wdXRXaWR0aCwKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgfTsKICAgIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnRlbXBsYXRlID0gaHRtbCBgCiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX3BhbmVSZW5kZXJlZF1dIiBpZD0iaWZSZW5kZXJlZCI+CiAgICAgIDxidXR0b24gY2xhc3M9ImhlYWRpbmciIG9uLXRhcD0iX3RvZ2dsZVBhbmUiIG9wZW4tYnV0dG9uJD0iW1tvcGVuZWRdXSI+CiAgICAgICAgPHNwYW4gY2xhc3M9Im5hbWUiPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19pc1NlYXJjaFJlc3VsdHNdXSI+CiAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaXNDb21wb3NpdGVTZWFyY2goY2F0ZWdvcnkpXV0iPgogICAgICAgICAgICAgIDxzcGFuPlRhZ3MgbWF0Y2hpbmcgbXVsdGlwbGUgZXhwZXJpbWVudHM8L3NwYW4+CiAgICAgICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19pc0ludmFsaWRTZWFyY2hSZXN1bHRzXV0iPgogICAgICAgICAgICAgICAgPHNwYW4KICAgICAgICAgICAgICAgICAgPiZuYnNwOzxzdHJvbmc+KG1hbGZvcm1lZCByZWd1bGFyIGV4cHJlc3Npb24pPC9zdHJvbmc+PC9zcGFuCiAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbWyFfaXNDb21wb3NpdGVTZWFyY2goY2F0ZWdvcnkpXV0iPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJsaWdodCI+VGFncyBtYXRjaGluZyAvPC9zcGFuPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjYXRlZ29yeS1uYW1lIiB0aXRsZSQ9IltbY2F0ZWdvcnkubmFtZV1dIgogICAgICAgICAgICAgICAgPltbY2F0ZWdvcnkubmFtZV1dPC9zcGFuCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJsaWdodCI+Lzwvc3Bhbj4KICAgICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2lzVW5pdmVyc2FsU2VhcmNoUXVlcnldXSI+CiAgICAgICAgICAgICAgICA8c3Bhbj4gKGFsbCB0YWdzKTwvc3Bhbj4KICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaXNJbnZhbGlkU2VhcmNoUmVzdWx0c11dIj4KICAgICAgICAgICAgICAgIDxzcGFuPiA8c3Ryb25nPihtYWxmb3JtZWQgcmVndWxhciBleHByZXNzaW9uKTwvc3Ryb25nPjwvc3Bhbj4KICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shX2lzU2VhcmNoUmVzdWx0c11dIj4KICAgICAgICAgICAgPHNwYW4gY2xhc3M9ImNhdGVnb3J5LW5hbWUiIHRpdGxlJD0iW1tjYXRlZ29yeS5uYW1lXV0iCiAgICAgICAgICAgICAgPltbY2F0ZWdvcnkubmFtZV1dPC9zcGFuCiAgICAgICAgICAgID4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC9zcGFuPgogICAgICAgIDxzcGFuIGNsYXNzPSJjb3VudCI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc011bHRpcGxlXV0iPgogICAgICAgICAgICA8c3Bhbj5bW19jb3VudF1dPC9zcGFuPgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDxpcm9uLWljb24gaWNvbj0iZXhwYW5kLW1vcmUiIGNsYXNzPSJleHBhbmQtYXJyb3ciPjwvaXJvbi1pY29uPgogICAgICAgIDwvc3Bhbj4KICAgICAgPC9idXR0b24+CiAgICAgIDwhLS0gVE9ETyhzdGVwaGFud2xlZSk6IGludmVzdGlnYXRlIGZ1cnRoZXIuIEZvciBzb21lIHJlYXNvbiwKICAgICAgICB0cmFuc2l0aW9uZW5kIHRoYXQgdGhlIGlyb24tY29sbGFwc2UgcmVsaWVzIG9uIHNvbWV0aW1lcyBkb2VzIG5vdAogICAgICAgIHRyaWdnZXIgd2hlbiByZW5kZXJpbmcgYSBjaGFydCB3aXRoIGEgc3Bpbm5lci4gQSB0b3kgZXhhbXBsZSBjYW5ub3QKICAgICAgICByZXByb2R1Y2UgdGhpcyBidWcuIC0tPgogICAgICA8aXJvbi1jb2xsYXBzZSBvcGVuZWQ9Iltbb3BlbmVkXV0iIG5vLWFuaW1hdGlvbj0iIj4KICAgICAgICA8ZGl2IGNsYXNzPSJjb250ZW50Ij4KICAgICAgICAgIDxzcGFuIGlkPSJ0b3Atb2YtY29udGFpbmVyIj48L3NwYW4+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX211bHRpcGxlUGFnZXNFeGlzdF1dIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iYmlnLXBhZ2UtYnV0dG9ucyIgc3R5bGU9Im1hcmdpbi1ib3R0b206IDEwcHg7Ij4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgICBvbi10YXA9Il9wZXJmb3JtUHJldmlvdXNQYWdlIgogICAgICAgICAgICAgICAgZGlzYWJsZWQkPSJbWyFfaGFzUHJldmlvdXNQYWdlXV0iCiAgICAgICAgICAgICAgICA+UHJldmlvdXMgcGFnZTwvcGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24KICAgICAgICAgICAgICAgIG9uLXRhcD0iX3BlcmZvcm1OZXh0UGFnZSIKICAgICAgICAgICAgICAgIGRpc2FibGVkJD0iW1shX2hhc05leHRQYWdlXV0iCiAgICAgICAgICAgICAgICA+TmV4dCBwYWdlPC9wYXBlci1idXR0b24KICAgICAgICAgICAgICA+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KCiAgICAgICAgICA8ZGl2IGlkPSJpdGVtcyI+CiAgICAgICAgICAgIDxzbG90IG5hbWU9Iml0ZW1zIj48L3Nsb3Q+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfbXVsdGlwbGVQYWdlc0V4aXN0XV0iPgogICAgICAgICAgICA8ZGl2IGlkPSJjb250cm9scy1jb250YWluZXIiPgogICAgICAgICAgICAgIDxkaXYgc3R5bGU9ImRpc3BsYXk6IGlubGluZS1ibG9jazsgcGFkZGluZzogMCA1cHgiPgogICAgICAgICAgICAgICAgUGFnZQogICAgICAgICAgICAgICAgPHBhcGVyLWlucHV0CiAgICAgICAgICAgICAgICAgIGlkPSJwYWdlLWlucHV0IgogICAgICAgICAgICAgICAgICB0eXBlPSJudW1iZXIiCiAgICAgICAgICAgICAgICAgIG5vLWxhYmVsLWZsb2F0PSIiCiAgICAgICAgICAgICAgICAgIG1pbj0iMSIKICAgICAgICAgICAgICAgICAgbWF4PSJbW19wYWdlQ291bnRdXSIKICAgICAgICAgICAgICAgICAgdmFsdWU9IltbX3BhZ2VJbnB1dFZhbHVlXV0iCiAgICAgICAgICAgICAgICAgIG9uLWlucHV0PSJfaGFuZGxlUGFnZUlucHV0RXZlbnQiCiAgICAgICAgICAgICAgICAgIG9uLWNoYW5nZT0iX2hhbmRsZVBhZ2VDaGFuZ2VFdmVudCIKICAgICAgICAgICAgICAgICAgb24tZm9jdXM9Il9oYW5kbGVQYWdlRm9jdXNFdmVudCIKICAgICAgICAgICAgICAgICAgb24tYmx1cj0iX2hhbmRsZVBhZ2VCbHVyRXZlbnQiCiAgICAgICAgICAgICAgICA+PC9wYXBlci1pbnB1dD4KICAgICAgICAgICAgICAgIG9mIFtbX3BhZ2VDb3VudF1dCiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvZGl2PgoKICAgICAgICAgICAgPGRpdiBjbGFzcz0iYmlnLXBhZ2UtYnV0dG9ucyIgc3R5bGU9Im1hcmdpbi10b3A6IDEwcHg7Ij4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgICBvbi10YXA9Il9wZXJmb3JtUHJldmlvdXNQYWdlIgogICAgICAgICAgICAgICAgZGlzYWJsZWQkPSJbWyFfaGFzUHJldmlvdXNQYWdlXV0iCiAgICAgICAgICAgICAgICA+UHJldmlvdXMgcGFnZTwvcGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24KICAgICAgICAgICAgICAgIG9uLXRhcD0iX3BlcmZvcm1OZXh0UGFnZSIKICAgICAgICAgICAgICAgIGRpc2FibGVkJD0iW1shX2hhc05leHRQYWdlXV0iCiAgICAgICAgICAgICAgICA+TmV4dCBwYWdlPC9wYXBlci1idXR0b24KICAgICAgICAgICAgICA+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8L2Rpdj4KICAgICAgPC9pcm9uLWNvbGxhcHNlPgogICAgPC90ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIG1hcmdpbjogMCA1cHggMXB4IDEwcHg7CiAgICAgIH0KCiAgICAgIDpob3N0KDpmaXJzdC1vZi10eXBlKSB7CiAgICAgICAgbWFyZ2luLXRvcDogMTBweDsKICAgICAgfQoKICAgICAgOmhvc3QoOmxhc3Qtb2YtdHlwZSkgewogICAgICAgIG1hcmdpbi1ib3R0b206IDIwcHg7CiAgICAgIH0KCiAgICAgIC5oZWFkaW5nIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB3aGl0ZTsKICAgICAgICBib3JkZXI6IG5vbmU7CiAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGZvbnQtc2l6ZTogMTVweDsKICAgICAgICBsaW5lLWhlaWdodDogMTsKICAgICAgICBib3gtc2hhZG93OiAwIDFweCA1cHggcmdiYSgwLCAwLCAwLCAwLjIpOwogICAgICAgIHBhZGRpbmc6IDEwcHggMTVweDsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgICAgICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1iZXR3ZWVuOwogICAgICB9CgogICAgICAuaGVhZGluZzo6LW1vei1mb2N1cy1pbm5lciB7CiAgICAgICAgcGFkZGluZzogMTBweCAxNXB4OwogICAgICB9CgogICAgICBbb3Blbi1idXR0b25dIHsKICAgICAgICBib3JkZXItYm90dG9tLWxlZnQtcmFkaXVzOiAwICFpbXBvcnRhbnQ7CiAgICAgICAgYm9yZGVyLWJvdHRvbS1yaWdodC1yYWRpdXM6IDAgIWltcG9ydGFudDsKICAgICAgfQoKICAgICAgW29wZW4tYnV0dG9uXSAuZXhwYW5kLWFycm93IHsKICAgICAgICB0cmFuc2Zvcm06IHJvdGF0ZVooMTgwZGVnKTsKICAgICAgfQoKICAgICAgLm5hbWUgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1mbGV4OwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KCiAgICAgIC5saWdodCB7CiAgICAgICAgY29sb3I6IHZhcigtLXBhcGVyLWdyZXktNTAwKTsKICAgICAgfQoKICAgICAgLmNhdGVnb3J5LW5hbWUgewogICAgICAgIHdoaXRlLXNwYWNlOiBwcmU7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgICB0ZXh0LW92ZXJmbG93OiBlbGxpcHNpczsKICAgICAgICBwYWRkaW5nOiAycHggMDsKICAgICAgfQoKICAgICAgLmNvdW50IHsKICAgICAgICBtYXJnaW46IDAgNXB4OwogICAgICAgIGZvbnQtc2l6ZTogMTJweDsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItZ3JleS01MDApOwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICBmbGV4OiBub25lOwogICAgICB9CgogICAgICAuaGVhZGluZzo6LW1vei1mb2N1cy1pbm5lciB7CiAgICAgICAgcGFkZGluZzogMTBweCAxNXB4OwogICAgICB9CgogICAgICAuY29udGVudCB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogICAgICAgIGJhY2tncm91bmQ6IHdoaXRlOwogICAgICAgIGJvcmRlci1ib3R0b20tbGVmdC1yYWRpdXM6IDJweDsKICAgICAgICBib3JkZXItYm90dG9tLXJpZ2h0LXJhZGl1czogMnB4OwogICAgICAgIGJvcmRlci10b3A6IG5vbmU7CiAgICAgICAgYm9yZGVyOiAxcHggc29saWQgI2RlZGVkZTsKICAgICAgICBwYWRkaW5nOiAxNXB4OwogICAgICB9CgogICAgICAubGlnaHQgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1ncmV5LTUwMCk7CiAgICAgIH0KCiAgICAgICNjb250cm9scy1jb250YWluZXIgewogICAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyOwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgICBmbGV4LWdyb3c6IDA7CiAgICAgICAgZmxleC1zaHJpbms6IDA7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIH0KCiAgICAgICNjb250cm9scy1jb250YWluZXIgcGFwZXItYnV0dG9uIHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgIH0KCiAgICAgIC5iaWctcGFnZS1idXR0b25zIHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICB9CgogICAgICAuYmlnLXBhZ2UtYnV0dG9ucyBwYXBlci1idXR0b24gewogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLXRiLXVpLWxpZ2h0LWFjY2VudCk7CiAgICAgICAgY29sb3I6IHZhcigtLXRiLXVpLWRhcmstYWNjZW50KTsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgZmxleC1iYXNpczogMDsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgZm9udC1zaXplOiAxM3B4OwogICAgICB9CgogICAgICAuYmlnLXBhZ2UtYnV0dG9ucyBwYXBlci1idXR0b25bZGlzYWJsZWRdIHsKICAgICAgICBiYWNrZ3JvdW5kOiBub25lOwogICAgICB9CgogICAgICBzbG90IHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiByb3c7CiAgICAgICAgZmxleC13cmFwOiB3cmFwOwogICAgICB9CgogICAgICA6OnNsb3R0ZWQoW3Nsb3Q9J2l0ZW1zJ10pIHsKICAgICAgICAvKiBUb29sdGlwIGZvciBkZXNjcmlwdGlvbnMgYW5kIG90aGVycyBicmVhayB3aXRoIG1vcmUgc3RyaWN0IG9uZXMuICovCiAgICAgICAgY29udGFpbjogc3R5bGU7CiAgICAgIH0KCiAgICAgICNwYWdlLWlucHV0IHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgICAgd2lkdGg6IHZhcigtLXRmLWNhdGVnb3J5LXBhZ2luYXRlZC12aWV3LXBhZ2UtaW5wdXQtd2lkdGgsIDEwMCUpOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnByb3RvdHlwZSwgImNhdGVnb3J5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJpbml0aWFsT3BlbmVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnByb3RvdHlwZSwgIm9wZW5lZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiZGlzYWJsZVBhZ2luYXRpb24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVDb3VudChjYXRlZ29yeS5pdGVtcy4qKScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfY291bnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBjb21wdXRlZDogJ19jb21wdXRlUGFuZVJlbmRlcmVkKGNhdGVnb3J5KScsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX29uUGFuZVJlbmRlcmVkQ2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX3BhbmVSZW5kZXJlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVJc1NlYXJjaFJlc3VsdHMoY2F0ZWdvcnkubWV0YWRhdGEudHlwZSknLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnByb3RvdHlwZSwgIl9pc1NlYXJjaFJlc3VsdHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBjb21wdXRlZDogJ19jb21wdXRlSXNJbnZhbGlkU2VhcmNoUmVzdWx0cyhjYXRlZ29yeS5tZXRhZGF0YSknLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnByb3RvdHlwZSwgIl9pc0ludmFsaWRTZWFyY2hSZXN1bHRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgY29tcHV0ZWQ6ICdfY29tcHV0ZUlzVW5pdmVyc2FsU2VhcmNoUXVlcnkoY2F0ZWdvcnkubWV0YWRhdGEpJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfaXNVbml2ZXJzYWxTZWFyY2hRdWVyeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZ2V0Q2F0ZWdvcnlJdGVtS2V5Q2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJnZXRDYXRlZ29yeUl0ZW1LZXkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX2xpbWl0Q2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfbGltaXQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfYWN0aXZlSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVQYWdlQ291bnQoY2F0ZWdvcnkuaXRlbXMuKiwgX2xpbWl0KScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfcGFnZUNvdW50Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBjb21wdXRlZDogJ19jb21wdXRlSW5wdXRXaWR0aChfcGFnZUNvdW50KScsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX3VwZGF0ZUlucHV0V2lkdGgnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX2lucHV0V2lkdGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVQYWdlSW5wdXRWYWx1ZShfcGFnZUlucHV0Rm9jdXNlZCwgX3BhZ2VJbnB1dFJhd1ZhbHVlLCBfY3VycmVudFBhZ2UpJywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfdXBkYXRlUGFnZUlucHV0VmFsdWUnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX3BhZ2VJbnB1dFZhbHVlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX3BhZ2VJbnB1dFJhd1ZhbHVlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfcGFnZUlucHV0Rm9jdXNlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX2NvdW50JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX2hhc011bHRpcGxlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdvcGVuZWQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtCb29sZWFuXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfY2hhbmdlQ29udGVudEFjdGl2ZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ29wZW5lZCcsICdfcGFuZVJlbmRlcmVkJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX2l0ZW1zUmVuZGVyZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ19pdGVtc1JlbmRlcmVkJywgJ2NhdGVnb3J5Lml0ZW1zLionLCAnX2xpbWl0JywgJ19hY3RpdmVJbmRleCcsICdfcGFnZUNvdW50JywgJ2Rpc2FibGVQYWdpbmF0aW9uJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfdXBkYXRlUmVuZGVyZWRJdGVtcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19saW1pdCcsICdfYWN0aXZlSW5kZXgnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlciksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmQ2F0ZWdvcnlQYWdpbmF0ZWRWaWV3LnByb3RvdHlwZSwgIl9jdXJyZW50UGFnZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19wYWdlQ291bnQnLCAnZGlzYWJsZVBhZ2luYXRpb24nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfbXVsdGlwbGVQYWdlc0V4aXN0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX2N1cnJlbnRQYWdlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX2hhc1ByZXZpb3VzUGFnZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19jdXJyZW50UGFnZScsICdfcGFnZUNvdW50JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcucHJvdG90eXBlLCAiX2hhc05leHRQYWdlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdjYXRlZ29yeS5pdGVtcy4qJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldy5wcm90b3R5cGUsICJfY2xhbXBBY3RpdmVJbmRleCIsIG51bGwpOwogICAgVGZDYXRlZ29yeVBhZ2luYXRlZFZpZXcgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldycpCiAgICBdLCBUZkNhdGVnb3J5UGFnaW5hdGVkVmlldyk7CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KICAgICsKICAgICtMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgICt5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICArWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CiAgICArCiAgICArICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAogICAgKwogICAgK1VubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgICtkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgK1dJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgK1NlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgICtsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgICs9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gQSB1bmlxdWUgcmVmZXJlbmNlIHRvIGEgbGlzdGVuZXIgZm9yIGFuIGVhc2llciBkZXJlZmVyZW5jaW5nLgogICAgY2xhc3MgTGlzdGVuS2V5JDEgewogICAgICAgIGNvbnN0cnVjdG9yKGxpc3RlbmVyKSB7CiAgICAgICAgICAgIHRoaXMubGlzdGVuZXIgPSBsaXN0ZW5lcjsKICAgICAgICB9CiAgICB9CiAgICBjbGFzcyBCYXNlU3RvcmUgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICB0aGlzLnJlcXVlc3RNYW5hZ2VyID0gbmV3IFJlcXVlc3RNYW5hZ2VyKDEgLyogc2ltdWx0YW5lb3VzIHJlcXVlc3QgKi8pOwogICAgICAgICAgICB0aGlzLl9saXN0ZW5lcnMgPSBuZXcgU2V0KCk7CiAgICAgICAgICAgIHRoaXMuaW5pdGlhbGl6ZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgcmVmcmVzaCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMubG9hZCgpLnRoZW4oKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5pbml0aWFsaXplZCA9IHRydWU7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZWdpc3RlciBhIGxpc3RlbmVyIChudWxsYXJ5IGZ1bmN0aW9uKSB0byBiZSBjYWxsZWQgd2hlbiBuZXcgcnVucyBhcmUKICAgICAgICAgKiBhdmFpbGFibGUuCiAgICAgICAgICovCiAgICAgICAgYWRkTGlzdGVuZXIobGlzdGVuZXIpIHsKICAgICAgICAgICAgY29uc3Qga2V5ID0gbmV3IExpc3RlbktleSQxKGxpc3RlbmVyKTsKICAgICAgICAgICAgdGhpcy5fbGlzdGVuZXJzLmFkZChrZXkpOwogICAgICAgICAgICByZXR1cm4ga2V5OwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmUgYSBsaXN0ZW5lciByZWdpc3RlcmVkIHdpdGggYGFkZExpc3RlbmVyYC4KICAgICAgICAgKi8KICAgICAgICByZW1vdmVMaXN0ZW5lckJ5S2V5KGxpc3RlbktleSkgewogICAgICAgICAgICB0aGlzLl9saXN0ZW5lcnMuZGVsZXRlKGxpc3RlbktleSk7CiAgICAgICAgfQogICAgICAgIGVtaXRDaGFuZ2UoKSB7CiAgICAgICAgICAgIHRoaXMuX2xpc3RlbmVycy5mb3JFYWNoKChsaXN0ZW5LZXkpID0+IHsKICAgICAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgICAgICAgbGlzdGVuS2V5Lmxpc3RlbmVyKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXRjaCAoZSkgewogICAgICAgICAgICAgICAgICAgIC8vIGlnbm9yZSBleGNlcHRpb25zIG9uIHRoZSBsaXN0ZW5lciBzaWRlLgogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjbGFzcyBFbnZpcm9ubWVudFN0b3JlIGV4dGVuZHMgQmFzZVN0b3JlIHsKICAgICAgICBsb2FkKCkgewogICAgICAgICAgICBjb25zdCB1cmwgPSBnZXRSb3V0ZXIoKS5lbnZpcm9ubWVudCgpOwogICAgICAgICAgICByZXR1cm4gdGhpcy5yZXF1ZXN0TWFuYWdlci5yZXF1ZXN0KHVybCkudGhlbigocmVzdWx0KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBlbnZpcm9ubWVudCA9IHsKICAgICAgICAgICAgICAgICAgICBkYXRhTG9jYXRpb246IHJlc3VsdC5kYXRhX2xvY2F0aW9uLAogICAgICAgICAgICAgICAgICAgIHdpbmRvd1RpdGxlOiByZXN1bHQud2luZG93X3RpdGxlLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGlmIChyZXN1bHQuZXhwZXJpbWVudF9uYW1lICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgICAgICBlbnZpcm9ubWVudC5leHBlcmltZW50TmFtZSA9IHJlc3VsdC5leHBlcmltZW50X25hbWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAocmVzdWx0LmV4cGVyaW1lbnRfZGVzY3JpcHRpb24gIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgICAgIGVudmlyb25tZW50LmV4cGVyaW1lbnREZXNjcmlwdGlvbiA9IHJlc3VsdC5leHBlcmltZW50X2Rlc2NyaXB0aW9uOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKHJlc3VsdC5jcmVhdGlvbl90aW1lICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgICAgICBlbnZpcm9ubWVudC5jcmVhdGlvblRpbWUgPSByZXN1bHQuY3JlYXRpb25fdGltZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNFcXVhbCh0aGlzLmVudmlyb25tZW50LCBlbnZpcm9ubWVudCkpCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgdGhpcy5lbnZpcm9ubWVudCA9IGVudmlyb25tZW50OwogICAgICAgICAgICAgICAgdGhpcy5lbWl0Q2hhbmdlKCk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBnZXREYXRhTG9jYXRpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmVudmlyb25tZW50ID8gdGhpcy5lbnZpcm9ubWVudC5kYXRhTG9jYXRpb24gOiAnJzsKICAgICAgICB9CiAgICAgICAgZ2V0V2luZG93VGl0bGUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmVudmlyb25tZW50ID8gdGhpcy5lbnZpcm9ubWVudC53aW5kb3dUaXRsZSA6ICcnOwogICAgICAgIH0KICAgICAgICBnZXRFeHBlcmltZW50TmFtZSgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuZW52aXJvbm1lbnQgPyB0aGlzLmVudmlyb25tZW50LmV4cGVyaW1lbnROYW1lIDogJyc7CiAgICAgICAgfQogICAgICAgIGdldEV4cGVyaW1lbnREZXNjcmlwdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuZW52aXJvbm1lbnQgPyB0aGlzLmVudmlyb25tZW50LmV4cGVyaW1lbnREZXNjcmlwdGlvbiA6ICcnOwogICAgICAgIH0KICAgICAgICBnZXRDcmVhdGlvblRpbWUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmVudmlyb25tZW50ID8gdGhpcy5lbnZpcm9ubWVudC5jcmVhdGlvblRpbWUgOiBudWxsOwogICAgICAgIH0KICAgIH0KICAgIGNvbnN0IGVudmlyb25tZW50U3RvcmUgPSBuZXcgRW52aXJvbm1lbnRTdG9yZSgpOwoKICAgIC8qIENvcHlyaWdodCAyMDE3IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY2xhc3MgUnVuc1N0b3JlIGV4dGVuZHMgQmFzZVN0b3JlIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fcnVucyA9IFtdOwogICAgICAgIH0KICAgICAgICBsb2FkKCkgewogICAgICAgICAgICBjb25zdCB1cmwgPSBnZXRSb3V0ZXIoKS5ydW5zKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJlcXVlc3RNYW5hZ2VyLnJlcXVlc3QodXJsKS50aGVuKChuZXdSdW5zKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAoIWxvZGFzaC5pc0VxdWFsKHRoaXMuX3J1bnMsIG5ld1J1bnMpKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fcnVucyA9IG5ld1J1bnM7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5lbWl0Q2hhbmdlKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHZXQgdGhlIGN1cnJlbnQgbGlzdCBvZiBydW5zLiBJZiBubyBkYXRhIGlzIGF2YWlsYWJsZSwgdGhpcyB3aWxsIGJlCiAgICAgICAgICogYW4gZW1wdHkgYXJyYXkgKGkuZS4sIHRoZXJlIGlzIG5vIGRpc3RpbmN0aW9uIGJldHdlZW4gIm5vIHJ1bnMiIGFuZAogICAgICAgICAqICJubyBydW5zIHlldCIpLgogICAgICAgICAqLwogICAgICAgIGdldFJ1bnMoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9ydW5zLnNsaWNlKCk7CiAgICAgICAgfQogICAgfQogICAgY29uc3QgcnVuc1N0b3JlID0gbmV3IFJ1bnNTdG9yZSgpOwoKICAgIHZhciB2ZXJzaW9uJDEgPSAiNS43LjAiOwoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyhhLCBiKSB7CiAgICAgIHJldHVybiBhIDwgYiA/IC0xIDogYSA+IGIgPyAxIDogYSA+PSBiID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBiaXNlY3Rvcihjb21wYXJlKSB7CiAgICAgIGlmIChjb21wYXJlLmxlbmd0aCA9PT0gMSkgY29tcGFyZSA9IGFzY2VuZGluZ0NvbXBhcmF0b3IoY29tcGFyZSk7CiAgICAgIHJldHVybiB7CiAgICAgICAgbGVmdDogZnVuY3Rpb24oYSwgeCwgbG8sIGhpKSB7CiAgICAgICAgICBpZiAobG8gPT0gbnVsbCkgbG8gPSAwOwogICAgICAgICAgaWYgKGhpID09IG51bGwpIGhpID0gYS5sZW5ndGg7CiAgICAgICAgICB3aGlsZSAobG8gPCBoaSkgewogICAgICAgICAgICB2YXIgbWlkID0gbG8gKyBoaSA+Pj4gMTsKICAgICAgICAgICAgaWYgKGNvbXBhcmUoYVttaWRdLCB4KSA8IDApIGxvID0gbWlkICsgMTsKICAgICAgICAgICAgZWxzZSBoaSA9IG1pZDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBsbzsKICAgICAgICB9LAogICAgICAgIHJpZ2h0OiBmdW5jdGlvbihhLCB4LCBsbywgaGkpIHsKICAgICAgICAgIGlmIChsbyA9PSBudWxsKSBsbyA9IDA7CiAgICAgICAgICBpZiAoaGkgPT0gbnVsbCkgaGkgPSBhLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChsbyA8IGhpKSB7CiAgICAgICAgICAgIHZhciBtaWQgPSBsbyArIGhpID4+PiAxOwogICAgICAgICAgICBpZiAoY29tcGFyZShhW21pZF0sIHgpID4gMCkgaGkgPSBtaWQ7CiAgICAgICAgICAgIGVsc2UgbG8gPSBtaWQgKyAxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGxvOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2NlbmRpbmdDb21wYXJhdG9yKGYpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQsIHgpIHsKICAgICAgICByZXR1cm4gYXNjZW5kaW5nKGYoZCksIHgpOwogICAgICB9OwogICAgfQoKICAgIHZhciBhc2NlbmRpbmdCaXNlY3QgPSBiaXNlY3Rvcihhc2NlbmRpbmcpOwogICAgdmFyIGJpc2VjdFJpZ2h0ID0gYXNjZW5kaW5nQmlzZWN0LnJpZ2h0OwogICAgdmFyIGJpc2VjdExlZnQgPSBhc2NlbmRpbmdCaXNlY3QubGVmdDsKCiAgICBmdW5jdGlvbiBwYWlycyhhcnJheSwgZikgewogICAgICBpZiAoZiA9PSBudWxsKSBmID0gcGFpcjsKICAgICAgdmFyIGkgPSAwLCBuID0gYXJyYXkubGVuZ3RoIC0gMSwgcCA9IGFycmF5WzBdLCBwYWlycyA9IG5ldyBBcnJheShuIDwgMCA/IDAgOiBuKTsKICAgICAgd2hpbGUgKGkgPCBuKSBwYWlyc1tpXSA9IGYocCwgcCA9IGFycmF5WysraV0pOwogICAgICByZXR1cm4gcGFpcnM7CiAgICB9CgogICAgZnVuY3Rpb24gcGFpcihhLCBiKSB7CiAgICAgIHJldHVybiBbYSwgYl07CiAgICB9CgogICAgZnVuY3Rpb24gY3Jvc3ModmFsdWVzMCwgdmFsdWVzMSwgcmVkdWNlKSB7CiAgICAgIHZhciBuMCA9IHZhbHVlczAubGVuZ3RoLAogICAgICAgICAgbjEgPSB2YWx1ZXMxLmxlbmd0aCwKICAgICAgICAgIHZhbHVlcyA9IG5ldyBBcnJheShuMCAqIG4xKSwKICAgICAgICAgIGkwLAogICAgICAgICAgaTEsCiAgICAgICAgICBpLAogICAgICAgICAgdmFsdWUwOwoKICAgICAgaWYgKHJlZHVjZSA9PSBudWxsKSByZWR1Y2UgPSBwYWlyOwoKICAgICAgZm9yIChpMCA9IGkgPSAwOyBpMCA8IG4wOyArK2kwKSB7CiAgICAgICAgZm9yICh2YWx1ZTAgPSB2YWx1ZXMwW2kwXSwgaTEgPSAwOyBpMSA8IG4xOyArK2kxLCArK2kpIHsKICAgICAgICAgIHZhbHVlc1tpXSA9IHJlZHVjZSh2YWx1ZTAsIHZhbHVlczFbaTFdKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB2YWx1ZXM7CiAgICB9CgogICAgZnVuY3Rpb24gZGVzY2VuZGluZyhhLCBiKSB7CiAgICAgIHJldHVybiBiIDwgYSA/IC0xIDogYiA+IGEgPyAxIDogYiA+PSBhID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBudW1iZXIoeCkgewogICAgICByZXR1cm4geCA9PT0gbnVsbCA/IE5hTiA6ICt4OwogICAgfQoKICAgIGZ1bmN0aW9uIHZhcmlhbmNlKHZhbHVlcywgdmFsdWVvZikgewogICAgICB2YXIgbiA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBtID0gMCwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIG1lYW4gPSAwLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBkZWx0YSwKICAgICAgICAgIHN1bSA9IDA7CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICghaXNOYU4odmFsdWUgPSBudW1iZXIodmFsdWVzW2ldKSkpIHsKICAgICAgICAgICAgZGVsdGEgPSB2YWx1ZSAtIG1lYW47CiAgICAgICAgICAgIG1lYW4gKz0gZGVsdGEgLyArK207CiAgICAgICAgICAgIHN1bSArPSBkZWx0YSAqICh2YWx1ZSAtIG1lYW4pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZWxzZSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICghaXNOYU4odmFsdWUgPSBudW1iZXIodmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpKSkgewogICAgICAgICAgICBkZWx0YSA9IHZhbHVlIC0gbWVhbjsKICAgICAgICAgICAgbWVhbiArPSBkZWx0YSAvICsrbTsKICAgICAgICAgICAgc3VtICs9IGRlbHRhICogKHZhbHVlIC0gbWVhbik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBpZiAobSA+IDEpIHJldHVybiBzdW0gLyAobSAtIDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRldmlhdGlvbihhcnJheSwgZikgewogICAgICB2YXIgdiA9IHZhcmlhbmNlKGFycmF5LCBmKTsKICAgICAgcmV0dXJuIHYgPyBNYXRoLnNxcnQodikgOiB2OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVudCh2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBtaW4sCiAgICAgICAgICBtYXg7CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gRmluZCB0aGUgZmlyc3QgY29tcGFyYWJsZSB2YWx1ZS4KICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZXNbaV0pICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWluID0gbWF4ID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgaWYgKG1pbiA+IHZhbHVlKSBtaW4gPSB2YWx1ZTsKICAgICAgICAgICAgICAgIGlmIChtYXggPCB2YWx1ZSkgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBlbHNlIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsICYmIHZhbHVlID49IHZhbHVlKSB7CiAgICAgICAgICAgIG1pbiA9IG1heCA9IHZhbHVlOwogICAgICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBDb21wYXJlIHRoZSByZW1haW5pbmcgdmFsdWVzLgogICAgICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgaWYgKG1pbiA+IHZhbHVlKSBtaW4gPSB2YWx1ZTsKICAgICAgICAgICAgICAgIGlmIChtYXggPCB2YWx1ZSkgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gW21pbiwgbWF4XTsKICAgIH0KCiAgICB2YXIgYXJyYXkgPSBBcnJheS5wcm90b3R5cGU7CgogICAgdmFyIHNsaWNlID0gYXJyYXkuc2xpY2U7CiAgICB2YXIgbWFwID0gYXJyYXkubWFwOwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50KHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5KHgpIHsKICAgICAgcmV0dXJuIHg7CiAgICB9CgogICAgZnVuY3Rpb24gc2VxdWVuY2Uoc3RhcnQsIHN0b3AsIHN0ZXApIHsKICAgICAgc3RhcnQgPSArc3RhcnQsIHN0b3AgPSArc3RvcCwgc3RlcCA9IChuID0gYXJndW1lbnRzLmxlbmd0aCkgPCAyID8gKHN0b3AgPSBzdGFydCwgc3RhcnQgPSAwLCAxKSA6IG4gPCAzID8gMSA6ICtzdGVwOwoKICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgIG4gPSBNYXRoLm1heCgwLCBNYXRoLmNlaWwoKHN0b3AgLSBzdGFydCkgLyBzdGVwKSkgfCAwLAogICAgICAgICAgcmFuZ2UgPSBuZXcgQXJyYXkobik7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIHJhbmdlW2ldID0gc3RhcnQgKyBpICogc3RlcDsKICAgICAgfQoKICAgICAgcmV0dXJuIHJhbmdlOwogICAgfQoKICAgIHZhciBlMTAgPSBNYXRoLnNxcnQoNTApLAogICAgICAgIGU1ID0gTWF0aC5zcXJ0KDEwKSwKICAgICAgICBlMiA9IE1hdGguc3FydCgyKTsKCiAgICBmdW5jdGlvbiB0aWNrcyhzdGFydCwgc3RvcCwgY291bnQpIHsKICAgICAgdmFyIHJldmVyc2UsCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICBuLAogICAgICAgICAgdGlja3MsCiAgICAgICAgICBzdGVwOwoKICAgICAgc3RvcCA9ICtzdG9wLCBzdGFydCA9ICtzdGFydCwgY291bnQgPSArY291bnQ7CiAgICAgIGlmIChzdGFydCA9PT0gc3RvcCAmJiBjb3VudCA+IDApIHJldHVybiBbc3RhcnRdOwogICAgICBpZiAocmV2ZXJzZSA9IHN0b3AgPCBzdGFydCkgbiA9IHN0YXJ0LCBzdGFydCA9IHN0b3AsIHN0b3AgPSBuOwogICAgICBpZiAoKHN0ZXAgPSB0aWNrSW5jcmVtZW50KHN0YXJ0LCBzdG9wLCBjb3VudCkpID09PSAwIHx8ICFpc0Zpbml0ZShzdGVwKSkgcmV0dXJuIFtdOwoKICAgICAgaWYgKHN0ZXAgPiAwKSB7CiAgICAgICAgc3RhcnQgPSBNYXRoLmNlaWwoc3RhcnQgLyBzdGVwKTsKICAgICAgICBzdG9wID0gTWF0aC5mbG9vcihzdG9wIC8gc3RlcCk7CiAgICAgICAgdGlja3MgPSBuZXcgQXJyYXkobiA9IE1hdGguY2VpbChzdG9wIC0gc3RhcnQgKyAxKSk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHRpY2tzW2ldID0gKHN0YXJ0ICsgaSkgKiBzdGVwOwogICAgICB9IGVsc2UgewogICAgICAgIHN0YXJ0ID0gTWF0aC5mbG9vcihzdGFydCAqIHN0ZXApOwogICAgICAgIHN0b3AgPSBNYXRoLmNlaWwoc3RvcCAqIHN0ZXApOwogICAgICAgIHRpY2tzID0gbmV3IEFycmF5KG4gPSBNYXRoLmNlaWwoc3RhcnQgLSBzdG9wICsgMSkpOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSB0aWNrc1tpXSA9IChzdGFydCAtIGkpIC8gc3RlcDsKICAgICAgfQoKICAgICAgaWYgKHJldmVyc2UpIHRpY2tzLnJldmVyc2UoKTsKCiAgICAgIHJldHVybiB0aWNrczsKICAgIH0KCiAgICBmdW5jdGlvbiB0aWNrSW5jcmVtZW50KHN0YXJ0LCBzdG9wLCBjb3VudCkgewogICAgICB2YXIgc3RlcCA9IChzdG9wIC0gc3RhcnQpIC8gTWF0aC5tYXgoMCwgY291bnQpLAogICAgICAgICAgcG93ZXIgPSBNYXRoLmZsb29yKE1hdGgubG9nKHN0ZXApIC8gTWF0aC5MTjEwKSwKICAgICAgICAgIGVycm9yID0gc3RlcCAvIE1hdGgucG93KDEwLCBwb3dlcik7CiAgICAgIHJldHVybiBwb3dlciA+PSAwCiAgICAgICAgICA/IChlcnJvciA+PSBlMTAgPyAxMCA6IGVycm9yID49IGU1ID8gNSA6IGVycm9yID49IGUyID8gMiA6IDEpICogTWF0aC5wb3coMTAsIHBvd2VyKQogICAgICAgICAgOiAtTWF0aC5wb3coMTAsIC1wb3dlcikgLyAoZXJyb3IgPj0gZTEwID8gMTAgOiBlcnJvciA+PSBlNSA/IDUgOiBlcnJvciA+PSBlMiA/IDIgOiAxKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aWNrU3RlcChzdGFydCwgc3RvcCwgY291bnQpIHsKICAgICAgdmFyIHN0ZXAwID0gTWF0aC5hYnMoc3RvcCAtIHN0YXJ0KSAvIE1hdGgubWF4KDAsIGNvdW50KSwKICAgICAgICAgIHN0ZXAxID0gTWF0aC5wb3coMTAsIE1hdGguZmxvb3IoTWF0aC5sb2coc3RlcDApIC8gTWF0aC5MTjEwKSksCiAgICAgICAgICBlcnJvciA9IHN0ZXAwIC8gc3RlcDE7CiAgICAgIGlmIChlcnJvciA+PSBlMTApIHN0ZXAxICo9IDEwOwogICAgICBlbHNlIGlmIChlcnJvciA+PSBlNSkgc3RlcDEgKj0gNTsKICAgICAgZWxzZSBpZiAoZXJyb3IgPj0gZTIpIHN0ZXAxICo9IDI7CiAgICAgIHJldHVybiBzdG9wIDwgc3RhcnQgPyAtc3RlcDEgOiBzdGVwMTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aHJlc2hvbGRTdHVyZ2VzKHZhbHVlcykgewogICAgICByZXR1cm4gTWF0aC5jZWlsKE1hdGgubG9nKHZhbHVlcy5sZW5ndGgpIC8gTWF0aC5MTjIpICsgMTsKICAgIH0KCiAgICBmdW5jdGlvbiBoaXN0b2dyYW0oKSB7CiAgICAgIHZhciB2YWx1ZSA9IGlkZW50aXR5LAogICAgICAgICAgZG9tYWluID0gZXh0ZW50LAogICAgICAgICAgdGhyZXNob2xkID0gdGhyZXNob2xkU3R1cmdlczsKCiAgICAgIGZ1bmN0aW9uIGhpc3RvZ3JhbShkYXRhKSB7CiAgICAgICAgdmFyIGksCiAgICAgICAgICAgIG4gPSBkYXRhLmxlbmd0aCwKICAgICAgICAgICAgeCwKICAgICAgICAgICAgdmFsdWVzID0gbmV3IEFycmF5KG4pOwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB2YWx1ZXNbaV0gPSB2YWx1ZShkYXRhW2ldLCBpLCBkYXRhKTsKICAgICAgICB9CgogICAgICAgIHZhciB4eiA9IGRvbWFpbih2YWx1ZXMpLAogICAgICAgICAgICB4MCA9IHh6WzBdLAogICAgICAgICAgICB4MSA9IHh6WzFdLAogICAgICAgICAgICB0eiA9IHRocmVzaG9sZCh2YWx1ZXMsIHgwLCB4MSk7CgogICAgICAgIC8vIENvbnZlcnQgbnVtYmVyIG9mIHRocmVzaG9sZHMgaW50byB1bmlmb3JtIHRocmVzaG9sZHMuCiAgICAgICAgaWYgKCFBcnJheS5pc0FycmF5KHR6KSkgewogICAgICAgICAgdHogPSB0aWNrU3RlcCh4MCwgeDEsIHR6KTsKICAgICAgICAgIHR6ID0gc2VxdWVuY2UoTWF0aC5jZWlsKHgwIC8gdHopICogdHosIHgxLCB0eik7IC8vIGV4Y2x1c2l2ZQogICAgICAgIH0KCiAgICAgICAgLy8gUmVtb3ZlIGFueSB0aHJlc2hvbGRzIG91dHNpZGUgdGhlIGRvbWFpbi4KICAgICAgICB2YXIgbSA9IHR6Lmxlbmd0aDsKICAgICAgICB3aGlsZSAodHpbMF0gPD0geDApIHR6LnNoaWZ0KCksIC0tbTsKICAgICAgICB3aGlsZSAodHpbbSAtIDFdID4geDEpIHR6LnBvcCgpLCAtLW07CgogICAgICAgIHZhciBiaW5zID0gbmV3IEFycmF5KG0gKyAxKSwKICAgICAgICAgICAgYmluOwoKICAgICAgICAvLyBJbml0aWFsaXplIGJpbnMuCiAgICAgICAgZm9yIChpID0gMDsgaSA8PSBtOyArK2kpIHsKICAgICAgICAgIGJpbiA9IGJpbnNbaV0gPSBbXTsKICAgICAgICAgIGJpbi54MCA9IGkgPiAwID8gdHpbaSAtIDFdIDogeDA7CiAgICAgICAgICBiaW4ueDEgPSBpIDwgbSA/IHR6W2ldIDogeDE7CiAgICAgICAgfQoKICAgICAgICAvLyBBc3NpZ24gZGF0YSB0byBiaW5zIGJ5IHZhbHVlLCBpZ25vcmluZyBhbnkgb3V0c2lkZSB0aGUgZG9tYWluLgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHggPSB2YWx1ZXNbaV07CiAgICAgICAgICBpZiAoeDAgPD0geCAmJiB4IDw9IHgxKSB7CiAgICAgICAgICAgIGJpbnNbYmlzZWN0UmlnaHQodHosIHgsIDAsIG0pXS5wdXNoKGRhdGFbaV0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIGJpbnM7CiAgICAgIH0KCiAgICAgIGhpc3RvZ3JhbS52YWx1ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh2YWx1ZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50KF8pLCBoaXN0b2dyYW0pIDogdmFsdWU7CiAgICAgIH07CgogICAgICBoaXN0b2dyYW0uZG9tYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRvbWFpbiA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50KFtfWzBdLCBfWzFdXSksIGhpc3RvZ3JhbSkgOiBkb21haW47CiAgICAgIH07CgogICAgICBoaXN0b2dyYW0udGhyZXNob2xkcyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aHJlc2hvbGQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBBcnJheS5pc0FycmF5KF8pID8gY29uc3RhbnQoc2xpY2UuY2FsbChfKSkgOiBjb25zdGFudChfKSwgaGlzdG9ncmFtKSA6IHRocmVzaG9sZDsKICAgICAgfTsKCiAgICAgIHJldHVybiBoaXN0b2dyYW07CiAgICB9CgogICAgZnVuY3Rpb24gdGhyZXNob2xkKHZhbHVlcywgcCwgdmFsdWVvZikgewogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB2YWx1ZW9mID0gbnVtYmVyOwogICAgICBpZiAoIShuID0gdmFsdWVzLmxlbmd0aCkpIHJldHVybjsKICAgICAgaWYgKChwID0gK3ApIDw9IDAgfHwgbiA8IDIpIHJldHVybiArdmFsdWVvZih2YWx1ZXNbMF0sIDAsIHZhbHVlcyk7CiAgICAgIGlmIChwID49IDEpIHJldHVybiArdmFsdWVvZih2YWx1ZXNbbiAtIDFdLCBuIC0gMSwgdmFsdWVzKTsKICAgICAgdmFyIG4sCiAgICAgICAgICBpID0gKG4gLSAxKSAqIHAsCiAgICAgICAgICBpMCA9IE1hdGguZmxvb3IoaSksCiAgICAgICAgICB2YWx1ZTAgPSArdmFsdWVvZih2YWx1ZXNbaTBdLCBpMCwgdmFsdWVzKSwKICAgICAgICAgIHZhbHVlMSA9ICt2YWx1ZW9mKHZhbHVlc1tpMCArIDFdLCBpMCArIDEsIHZhbHVlcyk7CiAgICAgIHJldHVybiB2YWx1ZTAgKyAodmFsdWUxIC0gdmFsdWUwKSAqIChpIC0gaTApOwogICAgfQoKICAgIGZ1bmN0aW9uIGZyZWVkbWFuRGlhY29uaXModmFsdWVzLCBtaW4sIG1heCkgewogICAgICB2YWx1ZXMgPSBtYXAuY2FsbCh2YWx1ZXMsIG51bWJlcikuc29ydChhc2NlbmRpbmcpOwogICAgICByZXR1cm4gTWF0aC5jZWlsKChtYXggLSBtaW4pIC8gKDIgKiAodGhyZXNob2xkKHZhbHVlcywgMC43NSkgLSB0aHJlc2hvbGQodmFsdWVzLCAwLjI1KSkgKiBNYXRoLnBvdyh2YWx1ZXMubGVuZ3RoLCAtMSAvIDMpKSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2NvdHQodmFsdWVzLCBtaW4sIG1heCkgewogICAgICByZXR1cm4gTWF0aC5jZWlsKChtYXggLSBtaW4pIC8gKDMuNSAqIGRldmlhdGlvbih2YWx1ZXMpICogTWF0aC5wb3codmFsdWVzLmxlbmd0aCwgLTEgLyAzKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1heCh2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBtYXg7CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gRmluZCB0aGUgZmlyc3QgY29tcGFyYWJsZSB2YWx1ZS4KICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZXNbaV0pICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCAmJiB2YWx1ZSA+IG1heCkgewogICAgICAgICAgICAgICAgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBlbHNlIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsICYmIHZhbHVlID49IHZhbHVlKSB7CiAgICAgICAgICAgIG1heCA9IHZhbHVlOwogICAgICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBDb21wYXJlIHRoZSByZW1haW5pbmcgdmFsdWVzLgogICAgICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkgIT0gbnVsbCAmJiB2YWx1ZSA+IG1heCkgewogICAgICAgICAgICAgICAgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbWF4OwogICAgfQoKICAgIGZ1bmN0aW9uIG1lYW4odmFsdWVzLCB2YWx1ZW9mKSB7CiAgICAgIHZhciBuID0gdmFsdWVzLmxlbmd0aCwKICAgICAgICAgIG0gPSBuLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBzdW0gPSAwOwoKICAgICAgaWYgKHZhbHVlb2YgPT0gbnVsbCkgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyKHZhbHVlc1tpXSkpKSBzdW0gKz0gdmFsdWU7CiAgICAgICAgICBlbHNlIC0tbTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyKHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSkpIHN1bSArPSB2YWx1ZTsKICAgICAgICAgIGVsc2UgLS1tOwogICAgICAgIH0KICAgICAgfQoKICAgICAgaWYgKG0pIHJldHVybiBzdW0gLyBtOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lZGlhbih2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBudW1iZXJzID0gW107CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICghaXNOYU4odmFsdWUgPSBudW1iZXIodmFsdWVzW2ldKSkpIHsKICAgICAgICAgICAgbnVtYmVycy5wdXNoKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyKHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSkpIHsKICAgICAgICAgICAgbnVtYmVycy5wdXNoKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB0aHJlc2hvbGQobnVtYmVycy5zb3J0KGFzY2VuZGluZyksIDAuNSk7CiAgICB9CgogICAgZnVuY3Rpb24gbWVyZ2UoYXJyYXlzKSB7CiAgICAgIHZhciBuID0gYXJyYXlzLmxlbmd0aCwKICAgICAgICAgIG0sCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICBqID0gMCwKICAgICAgICAgIG1lcmdlZCwKICAgICAgICAgIGFycmF5OwoKICAgICAgd2hpbGUgKCsraSA8IG4pIGogKz0gYXJyYXlzW2ldLmxlbmd0aDsKICAgICAgbWVyZ2VkID0gbmV3IEFycmF5KGopOwoKICAgICAgd2hpbGUgKC0tbiA+PSAwKSB7CiAgICAgICAgYXJyYXkgPSBhcnJheXNbbl07CiAgICAgICAgbSA9IGFycmF5Lmxlbmd0aDsKICAgICAgICB3aGlsZSAoLS1tID49IDApIHsKICAgICAgICAgIG1lcmdlZFstLWpdID0gYXJyYXlbbV07CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbWVyZ2VkOwogICAgfQoKICAgIGZ1bmN0aW9uIG1pbih2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBtaW47CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gRmluZCB0aGUgZmlyc3QgY29tcGFyYWJsZSB2YWx1ZS4KICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZXNbaV0pICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCAmJiBtaW4gPiB2YWx1ZSkgewogICAgICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBlbHNlIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsICYmIHZhbHVlID49IHZhbHVlKSB7CiAgICAgICAgICAgIG1pbiA9IHZhbHVlOwogICAgICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBDb21wYXJlIHRoZSByZW1haW5pbmcgdmFsdWVzLgogICAgICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkgIT0gbnVsbCAmJiBtaW4gPiB2YWx1ZSkgewogICAgICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbWluOwogICAgfQoKICAgIGZ1bmN0aW9uIHBlcm11dGUoYXJyYXksIGluZGV4ZXMpIHsKICAgICAgdmFyIGkgPSBpbmRleGVzLmxlbmd0aCwgcGVybXV0ZXMgPSBuZXcgQXJyYXkoaSk7CiAgICAgIHdoaWxlIChpLS0pIHBlcm11dGVzW2ldID0gYXJyYXlbaW5kZXhlc1tpXV07CiAgICAgIHJldHVybiBwZXJtdXRlczsKICAgIH0KCiAgICBmdW5jdGlvbiBzY2FuKHZhbHVlcywgY29tcGFyZSkgewogICAgICBpZiAoIShuID0gdmFsdWVzLmxlbmd0aCkpIHJldHVybjsKICAgICAgdmFyIG4sCiAgICAgICAgICBpID0gMCwKICAgICAgICAgIGogPSAwLAogICAgICAgICAgeGksCiAgICAgICAgICB4aiA9IHZhbHVlc1tqXTsKCiAgICAgIGlmIChjb21wYXJlID09IG51bGwpIGNvbXBhcmUgPSBhc2NlbmRpbmc7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIGlmIChjb21wYXJlKHhpID0gdmFsdWVzW2ldLCB4aikgPCAwIHx8IGNvbXBhcmUoeGosIHhqKSAhPT0gMCkgewogICAgICAgICAgeGogPSB4aSwgaiA9IGk7CiAgICAgICAgfQogICAgICB9CgogICAgICBpZiAoY29tcGFyZSh4aiwgeGopID09PSAwKSByZXR1cm4gajsKICAgIH0KCiAgICBmdW5jdGlvbiBzaHVmZmxlKGFycmF5LCBpMCwgaTEpIHsKICAgICAgdmFyIG0gPSAoaTEgPT0gbnVsbCA/IGFycmF5Lmxlbmd0aCA6IGkxKSAtIChpMCA9IGkwID09IG51bGwgPyAwIDogK2kwKSwKICAgICAgICAgIHQsCiAgICAgICAgICBpOwoKICAgICAgd2hpbGUgKG0pIHsKICAgICAgICBpID0gTWF0aC5yYW5kb20oKSAqIG0tLSB8IDA7CiAgICAgICAgdCA9IGFycmF5W20gKyBpMF07CiAgICAgICAgYXJyYXlbbSArIGkwXSA9IGFycmF5W2kgKyBpMF07CiAgICAgICAgYXJyYXlbaSArIGkwXSA9IHQ7CiAgICAgIH0KCiAgICAgIHJldHVybiBhcnJheTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdW0odmFsdWVzLCB2YWx1ZW9mKSB7CiAgICAgIHZhciBuID0gdmFsdWVzLmxlbmd0aCwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIHZhbHVlLAogICAgICAgICAgc3VtID0gMDsKCiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaWYgKHZhbHVlID0gK3ZhbHVlc1tpXSkgc3VtICs9IHZhbHVlOyAvLyBOb3RlOiB6ZXJvIGFuZCBudWxsIGFyZSBlcXVpdmFsZW50LgogICAgICAgIH0KICAgICAgfQoKICAgICAgZWxzZSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICh2YWx1ZSA9ICt2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkgc3VtICs9IHZhbHVlOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHN1bTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc3Bvc2UobWF0cml4KSB7CiAgICAgIGlmICghKG4gPSBtYXRyaXgubGVuZ3RoKSkgcmV0dXJuIFtdOwogICAgICBmb3IgKHZhciBpID0gLTEsIG0gPSBtaW4obWF0cml4LCBsZW5ndGgpLCB0cmFuc3Bvc2UgPSBuZXcgQXJyYXkobSk7ICsraSA8IG07KSB7CiAgICAgICAgZm9yICh2YXIgaiA9IC0xLCBuLCByb3cgPSB0cmFuc3Bvc2VbaV0gPSBuZXcgQXJyYXkobik7ICsraiA8IG47KSB7CiAgICAgICAgICByb3dbal0gPSBtYXRyaXhbal1baV07CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0cmFuc3Bvc2U7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoKGQpIHsKICAgICAgcmV0dXJuIGQubGVuZ3RoOwogICAgfQoKICAgIGZ1bmN0aW9uIHppcCgpIHsKICAgICAgcmV0dXJuIHRyYW5zcG9zZShhcmd1bWVudHMpOwogICAgfQoKICAgIHZhciBzbGljZSQxID0gQXJyYXkucHJvdG90eXBlLnNsaWNlOwoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JDEoeCkgewogICAgICByZXR1cm4geDsKICAgIH0KCiAgICB2YXIgdG9wID0gMSwKICAgICAgICByaWdodCA9IDIsCiAgICAgICAgYm90dG9tID0gMywKICAgICAgICBsZWZ0ID0gNCwKICAgICAgICBlcHNpbG9uID0gMWUtNjsKCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVYKHgpIHsKICAgICAgcmV0dXJuICJ0cmFuc2xhdGUoIiArICh4ICsgMC41KSArICIsMCkiOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zbGF0ZVkoeSkgewogICAgICByZXR1cm4gInRyYW5zbGF0ZSgwLCIgKyAoeSArIDAuNSkgKyAiKSI7CiAgICB9CgogICAgZnVuY3Rpb24gbnVtYmVyJDEoc2NhbGUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQpIHsKICAgICAgICByZXR1cm4gK3NjYWxlKGQpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRlcihzY2FsZSkgewogICAgICB2YXIgb2Zmc2V0ID0gTWF0aC5tYXgoMCwgc2NhbGUuYmFuZHdpZHRoKCkgLSAxKSAvIDI7IC8vIEFkanVzdCBmb3IgMC41cHggb2Zmc2V0LgogICAgICBpZiAoc2NhbGUucm91bmQoKSkgb2Zmc2V0ID0gTWF0aC5yb3VuZChvZmZzZXQpOwogICAgICByZXR1cm4gZnVuY3Rpb24oZCkgewogICAgICAgIHJldHVybiArc2NhbGUoZCkgKyBvZmZzZXQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZW50ZXJpbmcoKSB7CiAgICAgIHJldHVybiAhdGhpcy5fX2F4aXM7CiAgICB9CgogICAgZnVuY3Rpb24gYXhpcyhvcmllbnQsIHNjYWxlKSB7CiAgICAgIHZhciB0aWNrQXJndW1lbnRzID0gW10sCiAgICAgICAgICB0aWNrVmFsdWVzID0gbnVsbCwKICAgICAgICAgIHRpY2tGb3JtYXQgPSBudWxsLAogICAgICAgICAgdGlja1NpemVJbm5lciA9IDYsCiAgICAgICAgICB0aWNrU2l6ZU91dGVyID0gNiwKICAgICAgICAgIHRpY2tQYWRkaW5nID0gMywKICAgICAgICAgIGsgPSBvcmllbnQgPT09IHRvcCB8fCBvcmllbnQgPT09IGxlZnQgPyAtMSA6IDEsCiAgICAgICAgICB4ID0gb3JpZW50ID09PSBsZWZ0IHx8IG9yaWVudCA9PT0gcmlnaHQgPyAieCIgOiAieSIsCiAgICAgICAgICB0cmFuc2Zvcm0gPSBvcmllbnQgPT09IHRvcCB8fCBvcmllbnQgPT09IGJvdHRvbSA/IHRyYW5zbGF0ZVggOiB0cmFuc2xhdGVZOwoKICAgICAgZnVuY3Rpb24gYXhpcyhjb250ZXh0KSB7CiAgICAgICAgdmFyIHZhbHVlcyA9IHRpY2tWYWx1ZXMgPT0gbnVsbCA/IChzY2FsZS50aWNrcyA/IHNjYWxlLnRpY2tzLmFwcGx5KHNjYWxlLCB0aWNrQXJndW1lbnRzKSA6IHNjYWxlLmRvbWFpbigpKSA6IHRpY2tWYWx1ZXMsCiAgICAgICAgICAgIGZvcm1hdCA9IHRpY2tGb3JtYXQgPT0gbnVsbCA/IChzY2FsZS50aWNrRm9ybWF0ID8gc2NhbGUudGlja0Zvcm1hdC5hcHBseShzY2FsZSwgdGlja0FyZ3VtZW50cykgOiBpZGVudGl0eSQxKSA6IHRpY2tGb3JtYXQsCiAgICAgICAgICAgIHNwYWNpbmcgPSBNYXRoLm1heCh0aWNrU2l6ZUlubmVyLCAwKSArIHRpY2tQYWRkaW5nLAogICAgICAgICAgICByYW5nZSA9IHNjYWxlLnJhbmdlKCksCiAgICAgICAgICAgIHJhbmdlMCA9ICtyYW5nZVswXSArIDAuNSwKICAgICAgICAgICAgcmFuZ2UxID0gK3JhbmdlW3JhbmdlLmxlbmd0aCAtIDFdICsgMC41LAogICAgICAgICAgICBwb3NpdGlvbiA9IChzY2FsZS5iYW5kd2lkdGggPyBjZW50ZXIgOiBudW1iZXIkMSkoc2NhbGUuY29weSgpKSwKICAgICAgICAgICAgc2VsZWN0aW9uID0gY29udGV4dC5zZWxlY3Rpb24gPyBjb250ZXh0LnNlbGVjdGlvbigpIDogY29udGV4dCwKICAgICAgICAgICAgcGF0aCA9IHNlbGVjdGlvbi5zZWxlY3RBbGwoIi5kb21haW4iKS5kYXRhKFtudWxsXSksCiAgICAgICAgICAgIHRpY2sgPSBzZWxlY3Rpb24uc2VsZWN0QWxsKCIudGljayIpLmRhdGEodmFsdWVzLCBzY2FsZSkub3JkZXIoKSwKICAgICAgICAgICAgdGlja0V4aXQgPSB0aWNrLmV4aXQoKSwKICAgICAgICAgICAgdGlja0VudGVyID0gdGljay5lbnRlcigpLmFwcGVuZCgiZyIpLmF0dHIoImNsYXNzIiwgInRpY2siKSwKICAgICAgICAgICAgbGluZSA9IHRpY2suc2VsZWN0KCJsaW5lIiksCiAgICAgICAgICAgIHRleHQgPSB0aWNrLnNlbGVjdCgidGV4dCIpOwoKICAgICAgICBwYXRoID0gcGF0aC5tZXJnZShwYXRoLmVudGVyKCkuaW5zZXJ0KCJwYXRoIiwgIi50aWNrIikKICAgICAgICAgICAgLmF0dHIoImNsYXNzIiwgImRvbWFpbiIpCiAgICAgICAgICAgIC5hdHRyKCJzdHJva2UiLCAiY3VycmVudENvbG9yIikpOwoKICAgICAgICB0aWNrID0gdGljay5tZXJnZSh0aWNrRW50ZXIpOwoKICAgICAgICBsaW5lID0gbGluZS5tZXJnZSh0aWNrRW50ZXIuYXBwZW5kKCJsaW5lIikKICAgICAgICAgICAgLmF0dHIoInN0cm9rZSIsICJjdXJyZW50Q29sb3IiKQogICAgICAgICAgICAuYXR0cih4ICsgIjIiLCBrICogdGlja1NpemVJbm5lcikpOwoKICAgICAgICB0ZXh0ID0gdGV4dC5tZXJnZSh0aWNrRW50ZXIuYXBwZW5kKCJ0ZXh0IikKICAgICAgICAgICAgLmF0dHIoImZpbGwiLCAiY3VycmVudENvbG9yIikKICAgICAgICAgICAgLmF0dHIoeCwgayAqIHNwYWNpbmcpCiAgICAgICAgICAgIC5hdHRyKCJkeSIsIG9yaWVudCA9PT0gdG9wID8gIjBlbSIgOiBvcmllbnQgPT09IGJvdHRvbSA/ICIwLjcxZW0iIDogIjAuMzJlbSIpKTsKCiAgICAgICAgaWYgKGNvbnRleHQgIT09IHNlbGVjdGlvbikgewogICAgICAgICAgcGF0aCA9IHBhdGgudHJhbnNpdGlvbihjb250ZXh0KTsKICAgICAgICAgIHRpY2sgPSB0aWNrLnRyYW5zaXRpb24oY29udGV4dCk7CiAgICAgICAgICBsaW5lID0gbGluZS50cmFuc2l0aW9uKGNvbnRleHQpOwogICAgICAgICAgdGV4dCA9IHRleHQudHJhbnNpdGlvbihjb250ZXh0KTsKCiAgICAgICAgICB0aWNrRXhpdCA9IHRpY2tFeGl0LnRyYW5zaXRpb24oY29udGV4dCkKICAgICAgICAgICAgICAuYXR0cigib3BhY2l0eSIsIGVwc2lsb24pCiAgICAgICAgICAgICAgLmF0dHIoInRyYW5zZm9ybSIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGlzRmluaXRlKGQgPSBwb3NpdGlvbihkKSkgPyB0cmFuc2Zvcm0oZCkgOiB0aGlzLmdldEF0dHJpYnV0ZSgidHJhbnNmb3JtIik7IH0pOwoKICAgICAgICAgIHRpY2tFbnRlcgogICAgICAgICAgICAgIC5hdHRyKCJvcGFjaXR5IiwgZXBzaWxvbikKICAgICAgICAgICAgICAuYXR0cigidHJhbnNmb3JtIiwgZnVuY3Rpb24oZCkgeyB2YXIgcCA9IHRoaXMucGFyZW50Tm9kZS5fX2F4aXM7IHJldHVybiB0cmFuc2Zvcm0ocCAmJiBpc0Zpbml0ZShwID0gcChkKSkgPyBwIDogcG9zaXRpb24oZCkpOyB9KTsKICAgICAgICB9CgogICAgICAgIHRpY2tFeGl0LnJlbW92ZSgpOwoKICAgICAgICBwYXRoCiAgICAgICAgICAgIC5hdHRyKCJkIiwgb3JpZW50ID09PSBsZWZ0IHx8IG9yaWVudCA9PSByaWdodAogICAgICAgICAgICAgICAgPyAodGlja1NpemVPdXRlciA/ICJNIiArIGsgKiB0aWNrU2l6ZU91dGVyICsgIiwiICsgcmFuZ2UwICsgIkgwLjVWIiArIHJhbmdlMSArICJIIiArIGsgKiB0aWNrU2l6ZU91dGVyIDogIk0wLjUsIiArIHJhbmdlMCArICJWIiArIHJhbmdlMSkKICAgICAgICAgICAgICAgIDogKHRpY2tTaXplT3V0ZXIgPyAiTSIgKyByYW5nZTAgKyAiLCIgKyBrICogdGlja1NpemVPdXRlciArICJWMC41SCIgKyByYW5nZTEgKyAiViIgKyBrICogdGlja1NpemVPdXRlciA6ICJNIiArIHJhbmdlMCArICIsMC41SCIgKyByYW5nZTEpKTsKCiAgICAgICAgdGljawogICAgICAgICAgICAuYXR0cigib3BhY2l0eSIsIDEpCiAgICAgICAgICAgIC5hdHRyKCJ0cmFuc2Zvcm0iLCBmdW5jdGlvbihkKSB7IHJldHVybiB0cmFuc2Zvcm0ocG9zaXRpb24oZCkpOyB9KTsKCiAgICAgICAgbGluZQogICAgICAgICAgICAuYXR0cih4ICsgIjIiLCBrICogdGlja1NpemVJbm5lcik7CgogICAgICAgIHRleHQKICAgICAgICAgICAgLmF0dHIoeCwgayAqIHNwYWNpbmcpCiAgICAgICAgICAgIC50ZXh0KGZvcm1hdCk7CgogICAgICAgIHNlbGVjdGlvbi5maWx0ZXIoZW50ZXJpbmcpCiAgICAgICAgICAgIC5hdHRyKCJmaWxsIiwgIm5vbmUiKQogICAgICAgICAgICAuYXR0cigiZm9udC1zaXplIiwgMTApCiAgICAgICAgICAgIC5hdHRyKCJmb250LWZhbWlseSIsICJzYW5zLXNlcmlmIikKICAgICAgICAgICAgLmF0dHIoInRleHQtYW5jaG9yIiwgb3JpZW50ID09PSByaWdodCA/ICJzdGFydCIgOiBvcmllbnQgPT09IGxlZnQgPyAiZW5kIiA6ICJtaWRkbGUiKTsKCiAgICAgICAgc2VsZWN0aW9uCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uKCkgeyB0aGlzLl9fYXhpcyA9IHBvc2l0aW9uOyB9KTsKICAgICAgfQoKICAgICAgYXhpcy5zY2FsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzY2FsZSA9IF8sIGF4aXMpIDogc2NhbGU7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tzID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRpY2tBcmd1bWVudHMgPSBzbGljZSQxLmNhbGwoYXJndW1lbnRzKSwgYXhpczsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja0FyZ3VtZW50cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrQXJndW1lbnRzID0gXyA9PSBudWxsID8gW10gOiBzbGljZSQxLmNhbGwoXyksIGF4aXMpIDogdGlja0FyZ3VtZW50cy5zbGljZSgpOwogICAgICB9OwoKICAgICAgYXhpcy50aWNrVmFsdWVzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRpY2tWYWx1ZXMgPSBfID09IG51bGwgPyBudWxsIDogc2xpY2UkMS5jYWxsKF8pLCBheGlzKSA6IHRpY2tWYWx1ZXMgJiYgdGlja1ZhbHVlcy5zbGljZSgpOwogICAgICB9OwoKICAgICAgYXhpcy50aWNrRm9ybWF0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRpY2tGb3JtYXQgPSBfLCBheGlzKSA6IHRpY2tGb3JtYXQ7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tTaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRpY2tTaXplSW5uZXIgPSB0aWNrU2l6ZU91dGVyID0gK18sIGF4aXMpIDogdGlja1NpemVJbm5lcjsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja1NpemVJbm5lciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrU2l6ZUlubmVyID0gK18sIGF4aXMpIDogdGlja1NpemVJbm5lcjsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja1NpemVPdXRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrU2l6ZU91dGVyID0gK18sIGF4aXMpIDogdGlja1NpemVPdXRlcjsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja1BhZGRpbmcgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGlja1BhZGRpbmcgPSArXywgYXhpcykgOiB0aWNrUGFkZGluZzsKICAgICAgfTsKCiAgICAgIHJldHVybiBheGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGF4aXNUb3Aoc2NhbGUpIHsKICAgICAgcmV0dXJuIGF4aXModG9wLCBzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXhpc1JpZ2h0KHNjYWxlKSB7CiAgICAgIHJldHVybiBheGlzKHJpZ2h0LCBzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXhpc0JvdHRvbShzY2FsZSkgewogICAgICByZXR1cm4gYXhpcyhib3R0b20sIHNjYWxlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBheGlzTGVmdChzY2FsZSkgewogICAgICByZXR1cm4gYXhpcyhsZWZ0LCBzY2FsZSk7CiAgICB9CgogICAgdmFyIG5vb3AgPSB7dmFsdWU6IGZ1bmN0aW9uKCkge319OwoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoKCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGFyZ3VtZW50cy5sZW5ndGgsIF8gPSB7fSwgdDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICghKHQgPSBhcmd1bWVudHNbaV0gKyAiIikgfHwgKHQgaW4gXykgfHwgL1tccy5dLy50ZXN0KHQpKSB0aHJvdyBuZXcgRXJyb3IoImlsbGVnYWwgdHlwZTogIiArIHQpOwogICAgICAgIF9bdF0gPSBbXTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERpc3BhdGNoKF8pOwogICAgfQoKICAgIGZ1bmN0aW9uIERpc3BhdGNoKF8pIHsKICAgICAgdGhpcy5fID0gXzsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVR5cGVuYW1lcyh0eXBlbmFtZXMsIHR5cGVzKSB7CiAgICAgIHJldHVybiB0eXBlbmFtZXMudHJpbSgpLnNwbGl0KC9efFxzKy8pLm1hcChmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIG5hbWUgPSAiIiwgaSA9IHQuaW5kZXhPZigiLiIpOwogICAgICAgIGlmIChpID49IDApIG5hbWUgPSB0LnNsaWNlKGkgKyAxKSwgdCA9IHQuc2xpY2UoMCwgaSk7CiAgICAgICAgaWYgKHQgJiYgIXR5cGVzLmhhc093blByb3BlcnR5KHQpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHQpOwogICAgICAgIHJldHVybiB7dHlwZTogdCwgbmFtZTogbmFtZX07CiAgICAgIH0pOwogICAgfQoKICAgIERpc3BhdGNoLnByb3RvdHlwZSA9IGRpc3BhdGNoLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IERpc3BhdGNoLAogICAgICBvbjogZnVuY3Rpb24odHlwZW5hbWUsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIF8gPSB0aGlzLl8sCiAgICAgICAgICAgIFQgPSBwYXJzZVR5cGVuYW1lcyh0eXBlbmFtZSArICIiLCBfKSwKICAgICAgICAgICAgdCwKICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICBuID0gVC5sZW5ndGg7CgogICAgICAgIC8vIElmIG5vIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJldHVybiB0aGUgY2FsbGJhY2sgb2YgdGhlIGdpdmVuIHR5cGUgYW5kIG5hbWUuCiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKCh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgJiYgKHQgPSBnZXQkMShfW3RdLCB0eXBlbmFtZS5uYW1lKSkpIHJldHVybiB0OwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gSWYgYSB0eXBlIHdhcyBzcGVjaWZpZWQsIHNldCB0aGUgY2FsbGJhY2sgZm9yIHRoZSBnaXZlbiB0eXBlIGFuZCBuYW1lLgogICAgICAgIC8vIE90aGVyd2lzZSwgaWYgYSBudWxsIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJlbW92ZSBjYWxsYmFja3Mgb2YgdGhlIGdpdmVuIG5hbWUuCiAgICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwgJiYgdHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2FsbGJhY2s6ICIgKyBjYWxsYmFjayk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgX1t0XSA9IHNldCQxKF9bdF0sIHR5cGVuYW1lLm5hbWUsIGNhbGxiYWNrKTsKICAgICAgICAgIGVsc2UgaWYgKGNhbGxiYWNrID09IG51bGwpIGZvciAodCBpbiBfKSBfW3RdID0gc2V0JDEoX1t0XSwgdHlwZW5hbWUubmFtZSwgbnVsbCk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgY29weTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGNvcHkgPSB7fSwgXyA9IHRoaXMuXzsKICAgICAgICBmb3IgKHZhciB0IGluIF8pIGNvcHlbdF0gPSBfW3RdLnNsaWNlKCk7CiAgICAgICAgcmV0dXJuIG5ldyBEaXNwYXRjaChjb3B5KTsKICAgICAgfSwKICAgICAgY2FsbDogZnVuY3Rpb24odHlwZSwgdGhhdCkgewogICAgICAgIGlmICgobiA9IGFyZ3VtZW50cy5sZW5ndGggLSAyKSA+IDApIGZvciAodmFyIGFyZ3MgPSBuZXcgQXJyYXkobiksIGkgPSAwLCBuLCB0OyBpIDwgbjsgKytpKSBhcmdzW2ldID0gYXJndW1lbnRzW2kgKyAyXTsKICAgICAgICBpZiAoIXRoaXMuXy5oYXNPd25Qcm9wZXJ0eSh0eXBlKSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0eXBlKTsKICAgICAgICBmb3IgKHQgPSB0aGlzLl9bdHlwZV0sIGkgPSAwLCBuID0gdC5sZW5ndGg7IGkgPCBuOyArK2kpIHRbaV0udmFsdWUuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0sCiAgICAgIGFwcGx5OiBmdW5jdGlvbih0eXBlLCB0aGF0LCBhcmdzKSB7CiAgICAgICAgaWYgKCF0aGlzLl8uaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdHlwZSk7CiAgICAgICAgZm9yICh2YXIgdCA9IHRoaXMuX1t0eXBlXSwgaSA9IDAsIG4gPSB0Lmxlbmd0aDsgaSA8IG47ICsraSkgdFtpXS52YWx1ZS5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBnZXQkMSh0eXBlLCBuYW1lKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHlwZS5sZW5ndGgsIGM7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoKGMgPSB0eXBlW2ldKS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICByZXR1cm4gYy52YWx1ZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZXQkMSh0eXBlLCBuYW1lLCBjYWxsYmFjaykgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR5cGUubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKHR5cGVbaV0ubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgdHlwZVtpXSA9IG5vb3AsIHR5cGUgPSB0eXBlLnNsaWNlKDAsIGkpLmNvbmNhdCh0eXBlLnNsaWNlKGkgKyAxKSk7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwpIHR5cGUucHVzaCh7bmFtZTogbmFtZSwgdmFsdWU6IGNhbGxiYWNrfSk7CiAgICAgIHJldHVybiB0eXBlOwogICAgfQoKICAgIHZhciB4aHRtbCA9ICJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sIjsKCiAgICB2YXIgbmFtZXNwYWNlcyA9IHsKICAgICAgc3ZnOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciLAogICAgICB4aHRtbDogeGh0bWwsCiAgICAgIHhsaW5rOiAiaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIsCiAgICAgIHhtbDogImh0dHA6Ly93d3cudzMub3JnL1hNTC8xOTk4L25hbWVzcGFjZSIsCiAgICAgIHhtbG5zOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC94bWxucy8iCiAgICB9OwoKICAgIGZ1bmN0aW9uIG5hbWVzcGFjZShuYW1lKSB7CiAgICAgIHZhciBwcmVmaXggPSBuYW1lICs9ICIiLCBpID0gcHJlZml4LmluZGV4T2YoIjoiKTsKICAgICAgaWYgKGkgPj0gMCAmJiAocHJlZml4ID0gbmFtZS5zbGljZSgwLCBpKSkgIT09ICJ4bWxucyIpIG5hbWUgPSBuYW1lLnNsaWNlKGkgKyAxKTsKICAgICAgcmV0dXJuIG5hbWVzcGFjZXMuaGFzT3duUHJvcGVydHkocHJlZml4KSA/IHtzcGFjZTogbmFtZXNwYWNlc1twcmVmaXhdLCBsb2NhbDogbmFtZX0gOiBuYW1lOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3JJbmhlcml0KG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBkb2N1bWVudCA9IHRoaXMub3duZXJEb2N1bWVudCwKICAgICAgICAgICAgdXJpID0gdGhpcy5uYW1lc3BhY2VVUkk7CiAgICAgICAgcmV0dXJuIHVyaSA9PT0geGh0bWwgJiYgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50Lm5hbWVzcGFjZVVSSSA9PT0geGh0bWwKICAgICAgICAgICAgPyBkb2N1bWVudC5jcmVhdGVFbGVtZW50KG5hbWUpCiAgICAgICAgICAgIDogZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKHVyaSwgbmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvckZpeGVkKGZ1bGxuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5vd25lckRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3IobmFtZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UobmFtZSk7CiAgICAgIHJldHVybiAoZnVsbG5hbWUubG9jYWwKICAgICAgICAgID8gY3JlYXRvckZpeGVkCiAgICAgICAgICA6IGNyZWF0b3JJbmhlcml0KShmdWxsbmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9uZSgpIHt9CgogICAgZnVuY3Rpb24gc2VsZWN0b3Ioc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHNlbGVjdG9yID09IG51bGwgPyBub25lIDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucXVlcnlTZWxlY3RvcihzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NlbGVjdChzZWxlY3QpIHsKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yKHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBzdWJub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChzdWJub2RlID0gc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSkgewogICAgICAgICAgICBpZiAoIl9fZGF0YV9fIiBpbiBub2RlKSBzdWJub2RlLl9fZGF0YV9fID0gbm9kZS5fX2RhdGFfXzsKICAgICAgICAgICAgc3ViZ3JvdXBbaV0gPSBzdWJub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24oc3ViZ3JvdXBzLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbXB0eSgpIHsKICAgICAgcmV0dXJuIFtdOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdG9yQWxsKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBzZWxlY3RvciA9PSBudWxsID8gZW1wdHkgOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5xdWVyeVNlbGVjdG9yQWxsKHNlbGVjdG9yKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2VsZWN0QWxsKHNlbGVjdCkgewogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3JBbGwoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IFtdLCBwYXJlbnRzID0gW10sIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHN1Ymdyb3Vwcy5wdXNoKHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSk7CiAgICAgICAgICAgIHBhcmVudHMucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uKHN1Ymdyb3VwcywgcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gbWF0Y2hlcihzZWxlY3RvcikgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubWF0Y2hlcyhzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2ZpbHRlcihtYXRjaCkgewogICAgICBpZiAodHlwZW9mIG1hdGNoICE9PSAiZnVuY3Rpb24iKSBtYXRjaCA9IG1hdGNoZXIobWF0Y2gpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IFtdLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIG1hdGNoLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSB7CiAgICAgICAgICAgIHN1Ymdyb3VwLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbihzdWJncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNwYXJzZSh1cGRhdGUpIHsKICAgICAgcmV0dXJuIG5ldyBBcnJheSh1cGRhdGUubGVuZ3RoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZW50ZXIoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uKHRoaXMuX2VudGVyIHx8IHRoaXMuX2dyb3Vwcy5tYXAoc3BhcnNlKSwgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gRW50ZXJOb2RlKHBhcmVudCwgZGF0dW0pIHsKICAgICAgdGhpcy5vd25lckRvY3VtZW50ID0gcGFyZW50Lm93bmVyRG9jdW1lbnQ7CiAgICAgIHRoaXMubmFtZXNwYWNlVVJJID0gcGFyZW50Lm5hbWVzcGFjZVVSSTsKICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICAgIHRoaXMuX3BhcmVudCA9IHBhcmVudDsKICAgICAgdGhpcy5fX2RhdGFfXyA9IGRhdHVtOwogICAgfQoKICAgIEVudGVyTm9kZS5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBFbnRlck5vZGUsCiAgICAgIGFwcGVuZENoaWxkOiBmdW5jdGlvbihjaGlsZCkgeyByZXR1cm4gdGhpcy5fcGFyZW50Lmluc2VydEJlZm9yZShjaGlsZCwgdGhpcy5fbmV4dCk7IH0sCiAgICAgIGluc2VydEJlZm9yZTogZnVuY3Rpb24oY2hpbGQsIG5leHQpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5pbnNlcnRCZWZvcmUoY2hpbGQsIG5leHQpOyB9LAogICAgICBxdWVyeVNlbGVjdG9yOiBmdW5jdGlvbihzZWxlY3RvcikgeyByZXR1cm4gdGhpcy5fcGFyZW50LnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpOyB9LAogICAgICBxdWVyeVNlbGVjdG9yQWxsOiBmdW5jdGlvbihzZWxlY3RvcikgeyByZXR1cm4gdGhpcy5fcGFyZW50LnF1ZXJ5U2VsZWN0b3JBbGwoc2VsZWN0b3IpOyB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JDEoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGtleVByZWZpeCA9ICIkIjsgLy8gUHJvdGVjdCBhZ2FpbnN0IGtleXMgbGlrZSDigJxfX3Byb3RvX1/igJ0uCgogICAgZnVuY3Rpb24gYmluZEluZGV4KHBhcmVudCwgZ3JvdXAsIGVudGVyLCB1cGRhdGUsIGV4aXQsIGRhdGEpIHsKICAgICAgdmFyIGkgPSAwLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoOwoKICAgICAgLy8gUHV0IGFueSBub24tbnVsbCBub2RlcyB0aGF0IGZpdCBpbnRvIHVwZGF0ZS4KICAgICAgLy8gUHV0IGFueSBudWxsIG5vZGVzIGludG8gZW50ZXIuCiAgICAgIC8vIFB1dCBhbnkgcmVtYWluaW5nIGRhdGEgaW50byBlbnRlci4KICAgICAgZm9yICg7IGkgPCBkYXRhTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBub2RlLl9fZGF0YV9fID0gZGF0YVtpXTsKICAgICAgICAgIHVwZGF0ZVtpXSA9IG5vZGU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVudGVyW2ldID0gbmV3IEVudGVyTm9kZShwYXJlbnQsIGRhdGFbaV0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gUHV0IGFueSBub24tbnVsbCBub2RlcyB0aGF0IGRvbuKAmXQgZml0IGludG8gZXhpdC4KICAgICAgZm9yICg7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgZXhpdFtpXSA9IG5vZGU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gYmluZEtleShwYXJlbnQsIGdyb3VwLCBlbnRlciwgdXBkYXRlLCBleGl0LCBkYXRhLCBrZXkpIHsKICAgICAgdmFyIGksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZUJ5S2V5VmFsdWUgPSB7fSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoLAogICAgICAgICAga2V5VmFsdWVzID0gbmV3IEFycmF5KGdyb3VwTGVuZ3RoKSwKICAgICAgICAgIGtleVZhbHVlOwoKICAgICAgLy8gQ29tcHV0ZSB0aGUga2V5IGZvciBlYWNoIG5vZGUuCiAgICAgIC8vIElmIG11bHRpcGxlIG5vZGVzIGhhdmUgdGhlIHNhbWUga2V5LCB0aGUgZHVwbGljYXRlcyBhcmUgYWRkZWQgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBrZXlWYWx1ZXNbaV0gPSBrZXlWYWx1ZSA9IGtleVByZWZpeCArIGtleS5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKTsKICAgICAgICAgIGlmIChrZXlWYWx1ZSBpbiBub2RlQnlLZXlWYWx1ZSkgewogICAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBDb21wdXRlIHRoZSBrZXkgZm9yIGVhY2ggZGF0dW0uCiAgICAgIC8vIElmIHRoZXJlIGEgbm9kZSBhc3NvY2lhdGVkIHdpdGggdGhpcyBrZXksIGpvaW4gYW5kIGFkZCBpdCB0byB1cGRhdGUuCiAgICAgIC8vIElmIHRoZXJlIGlzIG5vdCAob3IgdGhlIGtleSBpcyBhIGR1cGxpY2F0ZSksIGFkZCBpdCB0byBlbnRlci4KICAgICAgZm9yIChpID0gMDsgaSA8IGRhdGFMZW5ndGg7ICsraSkgewogICAgICAgIGtleVZhbHVlID0ga2V5UHJlZml4ICsga2V5LmNhbGwocGFyZW50LCBkYXRhW2ldLCBpLCBkYXRhKTsKICAgICAgICBpZiAobm9kZSA9IG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSkgewogICAgICAgICAgdXBkYXRlW2ldID0gbm9kZTsKICAgICAgICAgIG5vZGUuX19kYXRhX18gPSBkYXRhW2ldOwogICAgICAgICAgbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdID0gbnVsbDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZW50ZXJbaV0gPSBuZXcgRW50ZXJOb2RlKHBhcmVudCwgZGF0YVtpXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBBZGQgYW55IHJlbWFpbmluZyBub2RlcyB0aGF0IHdlcmUgbm90IGJvdW5kIHRvIGRhdGEgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKG5vZGVCeUtleVZhbHVlW2tleVZhbHVlc1tpXV0gPT09IG5vZGUpKSB7CiAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGF0YSh2YWx1ZSwga2V5KSB7CiAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICBkYXRhID0gbmV3IEFycmF5KHRoaXMuc2l6ZSgpKSwgaiA9IC0xOwogICAgICAgIHRoaXMuZWFjaChmdW5jdGlvbihkKSB7IGRhdGFbKytqXSA9IGQ7IH0pOwogICAgICAgIHJldHVybiBkYXRhOwogICAgICB9CgogICAgICB2YXIgYmluZCA9IGtleSA/IGJpbmRLZXkgOiBiaW5kSW5kZXgsCiAgICAgICAgICBwYXJlbnRzID0gdGhpcy5fcGFyZW50cywKICAgICAgICAgIGdyb3VwcyA9IHRoaXMuX2dyb3VwczsKCiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHZhbHVlID0gY29uc3RhbnQkMSh2YWx1ZSk7CgogICAgICBmb3IgKHZhciBtID0gZ3JvdXBzLmxlbmd0aCwgdXBkYXRlID0gbmV3IEFycmF5KG0pLCBlbnRlciA9IG5ldyBBcnJheShtKSwgZXhpdCA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICB2YXIgcGFyZW50ID0gcGFyZW50c1tqXSwKICAgICAgICAgICAgZ3JvdXAgPSBncm91cHNbal0sCiAgICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgICBkYXRhID0gdmFsdWUuY2FsbChwYXJlbnQsIHBhcmVudCAmJiBwYXJlbnQuX19kYXRhX18sIGosIHBhcmVudHMpLAogICAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIGVudGVyR3JvdXAgPSBlbnRlcltqXSA9IG5ldyBBcnJheShkYXRhTGVuZ3RoKSwKICAgICAgICAgICAgdXBkYXRlR3JvdXAgPSB1cGRhdGVbal0gPSBuZXcgQXJyYXkoZGF0YUxlbmd0aCksCiAgICAgICAgICAgIGV4aXRHcm91cCA9IGV4aXRbal0gPSBuZXcgQXJyYXkoZ3JvdXBMZW5ndGgpOwoKICAgICAgICBiaW5kKHBhcmVudCwgZ3JvdXAsIGVudGVyR3JvdXAsIHVwZGF0ZUdyb3VwLCBleGl0R3JvdXAsIGRhdGEsIGtleSk7CgogICAgICAgIC8vIE5vdyBjb25uZWN0IHRoZSBlbnRlciBub2RlcyB0byB0aGVpciBmb2xsb3dpbmcgdXBkYXRlIG5vZGUsIHN1Y2ggdGhhdAogICAgICAgIC8vIGFwcGVuZENoaWxkIGNhbiBpbnNlcnQgdGhlIG1hdGVyaWFsaXplZCBlbnRlciBub2RlIGJlZm9yZSB0aGlzIG5vZGUsCiAgICAgICAgLy8gcmF0aGVyIHRoYW4gYXQgdGhlIGVuZCBvZiB0aGUgcGFyZW50IG5vZGUuCiAgICAgICAgZm9yICh2YXIgaTAgPSAwLCBpMSA9IDAsIHByZXZpb3VzLCBuZXh0OyBpMCA8IGRhdGFMZW5ndGg7ICsraTApIHsKICAgICAgICAgIGlmIChwcmV2aW91cyA9IGVudGVyR3JvdXBbaTBdKSB7CiAgICAgICAgICAgIGlmIChpMCA+PSBpMSkgaTEgPSBpMCArIDE7CiAgICAgICAgICAgIHdoaWxlICghKG5leHQgPSB1cGRhdGVHcm91cFtpMV0pICYmICsraTEgPCBkYXRhTGVuZ3RoKTsKICAgICAgICAgICAgcHJldmlvdXMuX25leHQgPSBuZXh0IHx8IG51bGw7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICB1cGRhdGUgPSBuZXcgU2VsZWN0aW9uKHVwZGF0ZSwgcGFyZW50cyk7CiAgICAgIHVwZGF0ZS5fZW50ZXIgPSBlbnRlcjsKICAgICAgdXBkYXRlLl9leGl0ID0gZXhpdDsKICAgICAgcmV0dXJuIHVwZGF0ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZXhpdCgpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24odGhpcy5fZXhpdCB8fCB0aGlzLl9ncm91cHMubWFwKHNwYXJzZSksIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9qb2luKG9uZW50ZXIsIG9udXBkYXRlLCBvbmV4aXQpIHsKICAgICAgdmFyIGVudGVyID0gdGhpcy5lbnRlcigpLCB1cGRhdGUgPSB0aGlzLCBleGl0ID0gdGhpcy5leGl0KCk7CiAgICAgIGVudGVyID0gdHlwZW9mIG9uZW50ZXIgPT09ICJmdW5jdGlvbiIgPyBvbmVudGVyKGVudGVyKSA6IGVudGVyLmFwcGVuZChvbmVudGVyICsgIiIpOwogICAgICBpZiAob251cGRhdGUgIT0gbnVsbCkgdXBkYXRlID0gb251cGRhdGUodXBkYXRlKTsKICAgICAgaWYgKG9uZXhpdCA9PSBudWxsKSBleGl0LnJlbW92ZSgpOyBlbHNlIG9uZXhpdChleGl0KTsKICAgICAgcmV0dXJuIGVudGVyICYmIHVwZGF0ZSA/IGVudGVyLm1lcmdlKHVwZGF0ZSkub3JkZXIoKSA6IHVwZGF0ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbWVyZ2Uoc2VsZWN0aW9uKSB7CgogICAgICBmb3IgKHZhciBncm91cHMwID0gdGhpcy5fZ3JvdXBzLCBncm91cHMxID0gc2VsZWN0aW9uLl9ncm91cHMsIG0wID0gZ3JvdXBzMC5sZW5ndGgsIG0xID0gZ3JvdXBzMS5sZW5ndGgsIG0gPSBNYXRoLm1pbihtMCwgbTEpLCBtZXJnZXMgPSBuZXcgQXJyYXkobTApLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwMCA9IGdyb3VwczBbal0sIGdyb3VwMSA9IGdyb3VwczFbal0sIG4gPSBncm91cDAubGVuZ3RoLCBtZXJnZSA9IG1lcmdlc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXAwW2ldIHx8IGdyb3VwMVtpXSkgewogICAgICAgICAgICBtZXJnZVtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3IgKDsgaiA8IG0wOyArK2opIHsKICAgICAgICBtZXJnZXNbal0gPSBncm91cHMwW2pdOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbihtZXJnZXMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9vcmRlcigpIHsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgaiA9IC0xLCBtID0gZ3JvdXBzLmxlbmd0aDsgKytqIDwgbTspIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IGdyb3VwLmxlbmd0aCAtIDEsIG5leHQgPSBncm91cFtpXSwgbm9kZTsgLS1pID49IDA7KSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIGlmIChuZXh0ICYmIG5vZGUuY29tcGFyZURvY3VtZW50UG9zaXRpb24obmV4dCkgXiA0KSBuZXh0LnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKG5vZGUsIG5leHQpOwogICAgICAgICAgICBuZXh0ID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zb3J0KGNvbXBhcmUpIHsKICAgICAgaWYgKCFjb21wYXJlKSBjb21wYXJlID0gYXNjZW5kaW5nJDE7CgogICAgICBmdW5jdGlvbiBjb21wYXJlTm9kZShhLCBiKSB7CiAgICAgICAgcmV0dXJuIGEgJiYgYiA/IGNvbXBhcmUoYS5fX2RhdGFfXywgYi5fX2RhdGFfXykgOiAhYSAtICFiOwogICAgICB9CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzb3J0Z3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzb3J0Z3JvdXAgPSBzb3J0Z3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBzb3J0Z3JvdXBbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBzb3J0Z3JvdXAuc29ydChjb21wYXJlTm9kZSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uKHNvcnRncm91cHMsIHRoaXMuX3BhcmVudHMpLm9yZGVyKCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nJDEoYSwgYikgewogICAgICByZXR1cm4gYSA8IGIgPyAtMSA6IGEgPiBiID8gMSA6IGEgPj0gYiA/IDAgOiBOYU47CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2NhbGwoKSB7CiAgICAgIHZhciBjYWxsYmFjayA9IGFyZ3VtZW50c1swXTsKICAgICAgYXJndW1lbnRzWzBdID0gdGhpczsKICAgICAgY2FsbGJhY2suYXBwbHkobnVsbCwgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX25vZGVzKCkgewogICAgICB2YXIgbm9kZXMgPSBuZXcgQXJyYXkodGhpcy5zaXplKCkpLCBpID0gLTE7CiAgICAgIHRoaXMuZWFjaChmdW5jdGlvbigpIHsgbm9kZXNbKytpXSA9IHRoaXM7IH0pOwogICAgICByZXR1cm4gbm9kZXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX25vZGUoKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgdmFyIG5vZGUgPSBncm91cFtpXTsKICAgICAgICAgIGlmIChub2RlKSByZXR1cm4gbm9kZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zaXplKCkgewogICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgIHRoaXMuZWFjaChmdW5jdGlvbigpIHsgKytzaXplOyB9KTsKICAgICAgcmV0dXJuIHNpemU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VtcHR5KCkgewogICAgICByZXR1cm4gIXRoaXMubm9kZSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9lYWNoKGNhbGxiYWNrKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZTsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgY2FsbGJhY2suY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJSZW1vdmVOUyhmdWxsbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgdmFsdWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudE5TKGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwsIHZhbHVlKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb24obmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICBlbHNlIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIHYpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbk5TKGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBlbHNlIHRoaXMuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCB2KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fYXR0cihuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UobmFtZSk7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgbm9kZSA9IHRoaXMubm9kZSgpOwogICAgICAgIHJldHVybiBmdWxsbmFtZS5sb2NhbAogICAgICAgICAgICA/IG5vZGUuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKQogICAgICAgICAgICA6IG5vZGUuZ2V0QXR0cmlidXRlKGZ1bGxuYW1lKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyUmVtb3ZlTlMgOiBhdHRyUmVtb3ZlKSA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckZ1bmN0aW9uTlMgOiBhdHRyRnVuY3Rpb24pCiAgICAgICAgICA6IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJDb25zdGFudE5TIDogYXR0ckNvbnN0YW50KSkpKGZ1bGxuYW1lLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRWaWV3KG5vZGUpIHsKICAgICAgcmV0dXJuIChub2RlLm93bmVyRG9jdW1lbnQgJiYgbm9kZS5vd25lckRvY3VtZW50LmRlZmF1bHRWaWV3KSAvLyBub2RlIGlzIGEgTm9kZQogICAgICAgICAgfHwgKG5vZGUuZG9jdW1lbnQgJiYgbm9kZSkgLy8gbm9kZSBpcyBhIFdpbmRvdwogICAgICAgICAgfHwgbm9kZS5kZWZhdWx0VmlldzsgLy8gbm9kZSBpcyBhIERvY3VtZW50CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVSZW1vdmUobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUNvbnN0YW50KG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5zZXRQcm9wZXJ0eShuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlRnVuY3Rpb24obmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgICBlbHNlIHRoaXMuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgdiwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zdHlsZShuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPiAxCiAgICAgICAgICA/IHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgICAgPyBzdHlsZVJlbW92ZSA6IHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgICAgPyBzdHlsZUZ1bmN0aW9uCiAgICAgICAgICAgICAgICA6IHN0eWxlQ29uc3RhbnQpKG5hbWUsIHZhbHVlLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSkpCiAgICAgICAgICA6IHN0eWxlVmFsdWUodGhpcy5ub2RlKCksIG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlVmFsdWUobm9kZSwgbmFtZSkgewogICAgICByZXR1cm4gbm9kZS5zdHlsZS5nZXRQcm9wZXJ0eVZhbHVlKG5hbWUpCiAgICAgICAgICB8fCBkZWZhdWx0Vmlldyhub2RlKS5nZXRDb21wdXRlZFN0eWxlKG5vZGUsIG51bGwpLmdldFByb3BlcnR5VmFsdWUobmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlSZW1vdmUobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgZGVsZXRlIHRoaXNbbmFtZV07CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlDb25zdGFudChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpc1tuYW1lXSA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5RnVuY3Rpb24obmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSBkZWxldGUgdGhpc1tuYW1lXTsKICAgICAgICBlbHNlIHRoaXNbbmFtZV0gPSB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9wcm9wZXJ0eShuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA+IDEKICAgICAgICAgID8gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyBwcm9wZXJ0eVJlbW92ZSA6IHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gcHJvcGVydHlGdW5jdGlvbgogICAgICAgICAgICAgIDogcHJvcGVydHlDb25zdGFudCkobmFtZSwgdmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKVtuYW1lXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc0FycmF5KHN0cmluZykgewogICAgICByZXR1cm4gc3RyaW5nLnRyaW0oKS5zcGxpdCgvXnxccysvKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc0xpc3Qobm9kZSkgewogICAgICByZXR1cm4gbm9kZS5jbGFzc0xpc3QgfHwgbmV3IENsYXNzTGlzdChub2RlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBDbGFzc0xpc3Qobm9kZSkgewogICAgICB0aGlzLl9ub2RlID0gbm9kZTsKICAgICAgdGhpcy5fbmFtZXMgPSBjbGFzc0FycmF5KG5vZGUuZ2V0QXR0cmlidXRlKCJjbGFzcyIpIHx8ICIiKTsKICAgIH0KCiAgICBDbGFzc0xpc3QucHJvdG90eXBlID0gewogICAgICBhZGQ6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICB2YXIgaSA9IHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSk7CiAgICAgICAgaWYgKGkgPCAwKSB7CiAgICAgICAgICB0aGlzLl9uYW1lcy5wdXNoKG5hbWUpOwogICAgICAgICAgdGhpcy5fbm9kZS5zZXRBdHRyaWJ1dGUoImNsYXNzIiwgdGhpcy5fbmFtZXMuam9pbigiICIpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIHJlbW92ZTogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHZhciBpID0gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKTsKICAgICAgICBpZiAoaSA+PSAwKSB7CiAgICAgICAgICB0aGlzLl9uYW1lcy5zcGxpY2UoaSwgMSk7CiAgICAgICAgICB0aGlzLl9ub2RlLnNldEF0dHJpYnV0ZSgiY2xhc3MiLCB0aGlzLl9uYW1lcy5qb2luKCIgIikpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgY29udGFpbnM6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICByZXR1cm4gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKSA+PSAwOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNsYXNzZWRBZGQobm9kZSwgbmFtZXMpIHsKICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3Qobm9kZSksIGkgPSAtMSwgbiA9IG5hbWVzLmxlbmd0aDsKICAgICAgd2hpbGUgKCsraSA8IG4pIGxpc3QuYWRkKG5hbWVzW2ldKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkUmVtb3ZlKG5vZGUsIG5hbWVzKSB7CiAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0KG5vZGUpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBsaXN0LnJlbW92ZShuYW1lc1tpXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZFRydWUobmFtZXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGNsYXNzZWRBZGQodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRGYWxzZShuYW1lcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgY2xhc3NlZFJlbW92ZSh0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZEZ1bmN0aW9uKG5hbWVzLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgKHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgPyBjbGFzc2VkQWRkIDogY2xhc3NlZFJlbW92ZSkodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbGFzc2VkKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBuYW1lcyA9IGNsYXNzQXJyYXkobmFtZSArICIiKTsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0KHRoaXMubm9kZSgpKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoIWxpc3QuY29udGFpbnMobmFtZXNbaV0pKSByZXR1cm4gZmFsc2U7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyBjbGFzc2VkRnVuY3Rpb24gOiB2YWx1ZQogICAgICAgICAgPyBjbGFzc2VkVHJ1ZQogICAgICAgICAgOiBjbGFzc2VkRmFsc2UpKG5hbWVzLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRSZW1vdmUoKSB7CiAgICAgIHRoaXMudGV4dENvbnRlbnQgPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0Q29uc3RhbnQodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0RnVuY3Rpb24odmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdiA9PSBudWxsID8gIiIgOiB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl90ZXh0KHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyB0ZXh0UmVtb3ZlIDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gdGV4dEZ1bmN0aW9uCiAgICAgICAgICAgICAgOiB0ZXh0Q29uc3RhbnQpKHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKCkudGV4dENvbnRlbnQ7CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbFJlbW92ZSgpIHsKICAgICAgdGhpcy5pbm5lckhUTUwgPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sQ29uc3RhbnQodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuaW5uZXJIVE1MID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbEZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgdGhpcy5pbm5lckhUTUwgPSB2ID09IG51bGwgPyAiIiA6IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2h0bWwodmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IGh0bWxSZW1vdmUgOiAodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBodG1sRnVuY3Rpb24KICAgICAgICAgICAgICA6IGh0bWxDb25zdGFudCkodmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS5pbm5lckhUTUw7CiAgICB9CgogICAgZnVuY3Rpb24gcmFpc2UoKSB7CiAgICAgIGlmICh0aGlzLm5leHRTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuYXBwZW5kQ2hpbGQodGhpcyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3JhaXNlKCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKHJhaXNlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsb3dlcigpIHsKICAgICAgaWYgKHRoaXMucHJldmlvdXNTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKHRoaXMsIHRoaXMucGFyZW50Tm9kZS5maXJzdENoaWxkKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbG93ZXIoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2gobG93ZXIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9hcHBlbmQobmFtZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvcihuYW1lKTsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLmFwcGVuZENoaWxkKGNyZWF0ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnROdWxsKCkgewogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25faW5zZXJ0KG5hbWUsIGJlZm9yZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvcihuYW1lKSwKICAgICAgICAgIHNlbGVjdCA9IGJlZm9yZSA9PSBudWxsID8gY29uc3RhbnROdWxsIDogdHlwZW9mIGJlZm9yZSA9PT0gImZ1bmN0aW9uIiA/IGJlZm9yZSA6IHNlbGVjdG9yKGJlZm9yZSk7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5pbnNlcnRCZWZvcmUoY3JlYXRlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksIHNlbGVjdC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIHx8IG51bGwpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmUoKSB7CiAgICAgIHZhciBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIGlmIChwYXJlbnQpIHBhcmVudC5yZW1vdmVDaGlsZCh0aGlzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fcmVtb3ZlKCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKHJlbW92ZSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Nsb25lU2hhbGxvdygpIHsKICAgICAgdmFyIGNsb25lID0gdGhpcy5jbG9uZU5vZGUoZmFsc2UpLCBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIHJldHVybiBwYXJlbnQgPyBwYXJlbnQuaW5zZXJ0QmVmb3JlKGNsb25lLCB0aGlzLm5leHRTaWJsaW5nKSA6IGNsb25lOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZURlZXAoKSB7CiAgICAgIHZhciBjbG9uZSA9IHRoaXMuY2xvbmVOb2RlKHRydWUpLCBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIHJldHVybiBwYXJlbnQgPyBwYXJlbnQuaW5zZXJ0QmVmb3JlKGNsb25lLCB0aGlzLm5leHRTaWJsaW5nKSA6IGNsb25lOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZShkZWVwKSB7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChkZWVwID8gc2VsZWN0aW9uX2Nsb25lRGVlcCA6IHNlbGVjdGlvbl9jbG9uZVNoYWxsb3cpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kYXR1bSh2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLnByb3BlcnR5KCJfX2RhdGFfXyIsIHZhbHVlKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS5fX2RhdGFfXzsKICAgIH0KCiAgICB2YXIgZmlsdGVyRXZlbnRzID0ge307CgogICAgdmFyIGV2ZW50ID0gbnVsbDsKCiAgICBpZiAodHlwZW9mIGRvY3VtZW50ICE9PSAidW5kZWZpbmVkIikgewogICAgICB2YXIgZWxlbWVudCA9IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudDsKICAgICAgaWYgKCEoIm9ubW91c2VlbnRlciIgaW4gZWxlbWVudCkpIHsKICAgICAgICBmaWx0ZXJFdmVudHMgPSB7bW91c2VlbnRlcjogIm1vdXNlb3ZlciIsIG1vdXNlbGVhdmU6ICJtb3VzZW91dCJ9OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZmlsdGVyQ29udGV4dExpc3RlbmVyKGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApIHsKICAgICAgbGlzdGVuZXIgPSBjb250ZXh0TGlzdGVuZXIobGlzdGVuZXIsIGluZGV4LCBncm91cCk7CiAgICAgIHJldHVybiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciByZWxhdGVkID0gZXZlbnQucmVsYXRlZFRhcmdldDsKICAgICAgICBpZiAoIXJlbGF0ZWQgfHwgKHJlbGF0ZWQgIT09IHRoaXMgJiYgIShyZWxhdGVkLmNvbXBhcmVEb2N1bWVudFBvc2l0aW9uKHRoaXMpICYgOCkpKSB7CiAgICAgICAgICBsaXN0ZW5lci5jYWxsKHRoaXMsIGV2ZW50KTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY29udGV4dExpc3RlbmVyKGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGV2ZW50MSkgewogICAgICAgIHZhciBldmVudDAgPSBldmVudDsgLy8gRXZlbnRzIGNhbiBiZSByZWVudHJhbnQgKGUuZy4sIGZvY3VzKS4KICAgICAgICBldmVudCA9IGV2ZW50MTsKICAgICAgICB0cnkgewogICAgICAgICAgbGlzdGVuZXIuY2FsbCh0aGlzLCB0aGlzLl9fZGF0YV9fLCBpbmRleCwgZ3JvdXApOwogICAgICAgIH0gZmluYWxseSB7CiAgICAgICAgICBldmVudCA9IGV2ZW50MDsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VUeXBlbmFtZXMkMSh0eXBlbmFtZXMpIHsKICAgICAgcmV0dXJuIHR5cGVuYW1lcy50cmltKCkuc3BsaXQoL158XHMrLykubWFwKGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgbmFtZSA9ICIiLCBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgbmFtZSA9IHQuc2xpY2UoaSArIDEpLCB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICByZXR1cm4ge3R5cGU6IHQsIG5hbWU6IG5hbWV9OwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBvblJlbW92ZSh0eXBlbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIG9uID0gdGhpcy5fX29uOwogICAgICAgIGlmICghb24pIHJldHVybjsKICAgICAgICBmb3IgKHZhciBqID0gMCwgaSA9IC0xLCBtID0gb24ubGVuZ3RoLCBvOyBqIDwgbTsgKytqKSB7CiAgICAgICAgICBpZiAobyA9IG9uW2pdLCAoIXR5cGVuYW1lLnR5cGUgfHwgby50eXBlID09PSB0eXBlbmFtZS50eXBlKSAmJiBvLm5hbWUgPT09IHR5cGVuYW1lLm5hbWUpIHsKICAgICAgICAgICAgdGhpcy5yZW1vdmVFdmVudExpc3RlbmVyKG8udHlwZSwgby5saXN0ZW5lciwgby5jYXB0dXJlKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG9uWysraV0gPSBvOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoKytpKSBvbi5sZW5ndGggPSBpOwogICAgICAgIGVsc2UgZGVsZXRlIHRoaXMuX19vbjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBvbkFkZCh0eXBlbmFtZSwgdmFsdWUsIGNhcHR1cmUpIHsKICAgICAgdmFyIHdyYXAgPSBmaWx0ZXJFdmVudHMuaGFzT3duUHJvcGVydHkodHlwZW5hbWUudHlwZSkgPyBmaWx0ZXJDb250ZXh0TGlzdGVuZXIgOiBjb250ZXh0TGlzdGVuZXI7CiAgICAgIHJldHVybiBmdW5jdGlvbihkLCBpLCBncm91cCkgewogICAgICAgIHZhciBvbiA9IHRoaXMuX19vbiwgbywgbGlzdGVuZXIgPSB3cmFwKHZhbHVlLCBpLCBncm91cCk7CiAgICAgICAgaWYgKG9uKSBmb3IgKHZhciBqID0gMCwgbSA9IG9uLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgICAgaWYgKChvID0gb25bal0pLnR5cGUgPT09IHR5cGVuYW1lLnR5cGUgJiYgby5uYW1lID09PSB0eXBlbmFtZS5uYW1lKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIsIG8uY2FwdHVyZSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIgPSBsaXN0ZW5lciwgby5jYXB0dXJlID0gY2FwdHVyZSk7CiAgICAgICAgICAgIG8udmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIodHlwZW5hbWUudHlwZSwgbGlzdGVuZXIsIGNhcHR1cmUpOwogICAgICAgIG8gPSB7dHlwZTogdHlwZW5hbWUudHlwZSwgbmFtZTogdHlwZW5hbWUubmFtZSwgdmFsdWU6IHZhbHVlLCBsaXN0ZW5lcjogbGlzdGVuZXIsIGNhcHR1cmU6IGNhcHR1cmV9OwogICAgICAgIGlmICghb24pIHRoaXMuX19vbiA9IFtvXTsKICAgICAgICBlbHNlIG9uLnB1c2gobyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX29uKHR5cGVuYW1lLCB2YWx1ZSwgY2FwdHVyZSkgewogICAgICB2YXIgdHlwZW5hbWVzID0gcGFyc2VUeXBlbmFtZXMkMSh0eXBlbmFtZSArICIiKSwgaSwgbiA9IHR5cGVuYW1lcy5sZW5ndGgsIHQ7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgb24gPSB0aGlzLm5vZGUoKS5fX29uOwogICAgICAgIGlmIChvbikgZm9yICh2YXIgaiA9IDAsIG0gPSBvbi5sZW5ndGgsIG87IGogPCBtOyArK2opIHsKICAgICAgICAgIGZvciAoaSA9IDAsIG8gPSBvbltqXTsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAoKHQgPSB0eXBlbmFtZXNbaV0pLnR5cGUgPT09IG8udHlwZSAmJiB0Lm5hbWUgPT09IG8ubmFtZSkgewogICAgICAgICAgICAgIHJldHVybiBvLnZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgb24gPSB2YWx1ZSA/IG9uQWRkIDogb25SZW1vdmU7CiAgICAgIGlmIChjYXB0dXJlID09IG51bGwpIGNhcHR1cmUgPSBmYWxzZTsKICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgdGhpcy5lYWNoKG9uKHR5cGVuYW1lc1tpXSwgdmFsdWUsIGNhcHR1cmUpKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gY3VzdG9tRXZlbnQoZXZlbnQxLCBsaXN0ZW5lciwgdGhhdCwgYXJncykgewogICAgICB2YXIgZXZlbnQwID0gZXZlbnQ7CiAgICAgIGV2ZW50MS5zb3VyY2VFdmVudCA9IGV2ZW50OwogICAgICBldmVudCA9IGV2ZW50MTsKICAgICAgdHJ5IHsKICAgICAgICByZXR1cm4gbGlzdGVuZXIuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0gZmluYWxseSB7CiAgICAgICAgZXZlbnQgPSBldmVudDA7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBkaXNwYXRjaEV2ZW50KG5vZGUsIHR5cGUsIHBhcmFtcykgewogICAgICB2YXIgd2luZG93ID0gZGVmYXVsdFZpZXcobm9kZSksCiAgICAgICAgICBldmVudCA9IHdpbmRvdy5DdXN0b21FdmVudDsKCiAgICAgIGlmICh0eXBlb2YgZXZlbnQgPT09ICJmdW5jdGlvbiIpIHsKICAgICAgICBldmVudCA9IG5ldyBldmVudCh0eXBlLCBwYXJhbXMpOwogICAgICB9IGVsc2UgewogICAgICAgIGV2ZW50ID0gd2luZG93LmRvY3VtZW50LmNyZWF0ZUV2ZW50KCJFdmVudCIpOwogICAgICAgIGlmIChwYXJhbXMpIGV2ZW50LmluaXRFdmVudCh0eXBlLCBwYXJhbXMuYnViYmxlcywgcGFyYW1zLmNhbmNlbGFibGUpLCBldmVudC5kZXRhaWwgPSBwYXJhbXMuZGV0YWlsOwogICAgICAgIGVsc2UgZXZlbnQuaW5pdEV2ZW50KHR5cGUsIGZhbHNlLCBmYWxzZSk7CiAgICAgIH0KCiAgICAgIG5vZGUuZGlzcGF0Y2hFdmVudChldmVudCk7CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hDb25zdGFudCh0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkaXNwYXRjaEV2ZW50KHRoaXMsIHR5cGUsIHBhcmFtcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hGdW5jdGlvbih0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkaXNwYXRjaEV2ZW50KHRoaXMsIHR5cGUsIHBhcmFtcy5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGlzcGF0Y2godHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiBwYXJhbXMgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gZGlzcGF0Y2hGdW5jdGlvbgogICAgICAgICAgOiBkaXNwYXRjaENvbnN0YW50KSh0eXBlLCBwYXJhbXMpKTsKICAgIH0KCiAgICB2YXIgcm9vdCQxID0gW251bGxdOwoKICAgIGZ1bmN0aW9uIFNlbGVjdGlvbihncm91cHMsIHBhcmVudHMpIHsKICAgICAgdGhpcy5fZ3JvdXBzID0gZ3JvdXBzOwogICAgICB0aGlzLl9wYXJlbnRzID0gcGFyZW50czsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb24oKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uKFtbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XV0sIHJvb3QkMSk7CiAgICB9CgogICAgU2VsZWN0aW9uLnByb3RvdHlwZSA9IHNlbGVjdGlvbi5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBTZWxlY3Rpb24sCiAgICAgIHNlbGVjdDogc2VsZWN0aW9uX3NlbGVjdCwKICAgICAgc2VsZWN0QWxsOiBzZWxlY3Rpb25fc2VsZWN0QWxsLAogICAgICBmaWx0ZXI6IHNlbGVjdGlvbl9maWx0ZXIsCiAgICAgIGRhdGE6IHNlbGVjdGlvbl9kYXRhLAogICAgICBlbnRlcjogc2VsZWN0aW9uX2VudGVyLAogICAgICBleGl0OiBzZWxlY3Rpb25fZXhpdCwKICAgICAgam9pbjogc2VsZWN0aW9uX2pvaW4sCiAgICAgIG1lcmdlOiBzZWxlY3Rpb25fbWVyZ2UsCiAgICAgIG9yZGVyOiBzZWxlY3Rpb25fb3JkZXIsCiAgICAgIHNvcnQ6IHNlbGVjdGlvbl9zb3J0LAogICAgICBjYWxsOiBzZWxlY3Rpb25fY2FsbCwKICAgICAgbm9kZXM6IHNlbGVjdGlvbl9ub2RlcywKICAgICAgbm9kZTogc2VsZWN0aW9uX25vZGUsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9zaXplLAogICAgICBlbXB0eTogc2VsZWN0aW9uX2VtcHR5LAogICAgICBlYWNoOiBzZWxlY3Rpb25fZWFjaCwKICAgICAgYXR0cjogc2VsZWN0aW9uX2F0dHIsCiAgICAgIHN0eWxlOiBzZWxlY3Rpb25fc3R5bGUsCiAgICAgIHByb3BlcnR5OiBzZWxlY3Rpb25fcHJvcGVydHksCiAgICAgIGNsYXNzZWQ6IHNlbGVjdGlvbl9jbGFzc2VkLAogICAgICB0ZXh0OiBzZWxlY3Rpb25fdGV4dCwKICAgICAgaHRtbDogc2VsZWN0aW9uX2h0bWwsCiAgICAgIHJhaXNlOiBzZWxlY3Rpb25fcmFpc2UsCiAgICAgIGxvd2VyOiBzZWxlY3Rpb25fbG93ZXIsCiAgICAgIGFwcGVuZDogc2VsZWN0aW9uX2FwcGVuZCwKICAgICAgaW5zZXJ0OiBzZWxlY3Rpb25faW5zZXJ0LAogICAgICByZW1vdmU6IHNlbGVjdGlvbl9yZW1vdmUsCiAgICAgIGNsb25lOiBzZWxlY3Rpb25fY2xvbmUsCiAgICAgIGRhdHVtOiBzZWxlY3Rpb25fZGF0dW0sCiAgICAgIG9uOiBzZWxlY3Rpb25fb24sCiAgICAgIGRpc3BhdGNoOiBzZWxlY3Rpb25fZGlzcGF0Y2gKICAgIH07CgogICAgZnVuY3Rpb24gc2VsZWN0KHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiB0eXBlb2Ygc2VsZWN0b3IgPT09ICJzdHJpbmciCiAgICAgICAgICA/IG5ldyBTZWxlY3Rpb24oW1tkb2N1bWVudC5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKV1dLCBbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XSkKICAgICAgICAgIDogbmV3IFNlbGVjdGlvbihbW3NlbGVjdG9yXV0sIHJvb3QkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlKG5hbWUpIHsKICAgICAgcmV0dXJuIHNlbGVjdChjcmVhdG9yKG5hbWUpLmNhbGwoZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50KSk7CiAgICB9CgogICAgdmFyIG5leHRJZCA9IDA7CgogICAgZnVuY3Rpb24gbG9jYWwoKSB7CiAgICAgIHJldHVybiBuZXcgTG9jYWw7CiAgICB9CgogICAgZnVuY3Rpb24gTG9jYWwoKSB7CiAgICAgIHRoaXMuXyA9ICJAIiArICgrK25leHRJZCkudG9TdHJpbmcoMzYpOwogICAgfQoKICAgIExvY2FsLnByb3RvdHlwZSA9IGxvY2FsLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IExvY2FsLAogICAgICBnZXQ6IGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICB2YXIgaWQgPSB0aGlzLl87CiAgICAgICAgd2hpbGUgKCEoaWQgaW4gbm9kZSkpIGlmICghKG5vZGUgPSBub2RlLnBhcmVudE5vZGUpKSByZXR1cm47CiAgICAgICAgcmV0dXJuIG5vZGVbaWRdOwogICAgICB9LAogICAgICBzZXQ6IGZ1bmN0aW9uKG5vZGUsIHZhbHVlKSB7CiAgICAgICAgcmV0dXJuIG5vZGVbdGhpcy5fXSA9IHZhbHVlOwogICAgICB9LAogICAgICByZW1vdmU6IGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICByZXR1cm4gdGhpcy5fIGluIG5vZGUgJiYgZGVsZXRlIG5vZGVbdGhpcy5fXTsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl87CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gc291cmNlRXZlbnQoKSB7CiAgICAgIHZhciBjdXJyZW50ID0gZXZlbnQsIHNvdXJjZTsKICAgICAgd2hpbGUgKHNvdXJjZSA9IGN1cnJlbnQuc291cmNlRXZlbnQpIGN1cnJlbnQgPSBzb3VyY2U7CiAgICAgIHJldHVybiBjdXJyZW50OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50KG5vZGUsIGV2ZW50KSB7CiAgICAgIHZhciBzdmcgPSBub2RlLm93bmVyU1ZHRWxlbWVudCB8fCBub2RlOwoKICAgICAgaWYgKHN2Zy5jcmVhdGVTVkdQb2ludCkgewogICAgICAgIHZhciBwb2ludCA9IHN2Zy5jcmVhdGVTVkdQb2ludCgpOwogICAgICAgIHBvaW50LnggPSBldmVudC5jbGllbnRYLCBwb2ludC55ID0gZXZlbnQuY2xpZW50WTsKICAgICAgICBwb2ludCA9IHBvaW50Lm1hdHJpeFRyYW5zZm9ybShub2RlLmdldFNjcmVlbkNUTSgpLmludmVyc2UoKSk7CiAgICAgICAgcmV0dXJuIFtwb2ludC54LCBwb2ludC55XTsKICAgICAgfQoKICAgICAgdmFyIHJlY3QgPSBub2RlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICByZXR1cm4gW2V2ZW50LmNsaWVudFggLSByZWN0LmxlZnQgLSBub2RlLmNsaWVudExlZnQsIGV2ZW50LmNsaWVudFkgLSByZWN0LnRvcCAtIG5vZGUuY2xpZW50VG9wXTsKICAgIH0KCiAgICBmdW5jdGlvbiBtb3VzZShub2RlKSB7CiAgICAgIHZhciBldmVudCA9IHNvdXJjZUV2ZW50KCk7CiAgICAgIGlmIChldmVudC5jaGFuZ2VkVG91Y2hlcykgZXZlbnQgPSBldmVudC5jaGFuZ2VkVG91Y2hlc1swXTsKICAgICAgcmV0dXJuIHBvaW50KG5vZGUsIGV2ZW50KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3RBbGwoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHR5cGVvZiBzZWxlY3RvciA9PT0gInN0cmluZyIKICAgICAgICAgID8gbmV3IFNlbGVjdGlvbihbZG9jdW1lbnQucXVlcnlTZWxlY3RvckFsbChzZWxlY3RvcildLCBbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XSkKICAgICAgICAgIDogbmV3IFNlbGVjdGlvbihbc2VsZWN0b3IgPT0gbnVsbCA/IFtdIDogc2VsZWN0b3JdLCByb290JDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRvdWNoKG5vZGUsIHRvdWNoZXMsIGlkZW50aWZpZXIpIHsKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAzKSBpZGVudGlmaWVyID0gdG91Y2hlcywgdG91Y2hlcyA9IHNvdXJjZUV2ZW50KCkuY2hhbmdlZFRvdWNoZXM7CgogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHRvdWNoZXMgPyB0b3VjaGVzLmxlbmd0aCA6IDAsIHRvdWNoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKCh0b3VjaCA9IHRvdWNoZXNbaV0pLmlkZW50aWZpZXIgPT09IGlkZW50aWZpZXIpIHsKICAgICAgICAgIHJldHVybiBwb2ludChub2RlLCB0b3VjaCk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiB0b3VjaGVzKG5vZGUsIHRvdWNoZXMpIHsKICAgICAgaWYgKHRvdWNoZXMgPT0gbnVsbCkgdG91Y2hlcyA9IHNvdXJjZUV2ZW50KCkudG91Y2hlczsKCiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdG91Y2hlcyA/IHRvdWNoZXMubGVuZ3RoIDogMCwgcG9pbnRzID0gbmV3IEFycmF5KG4pOyBpIDwgbjsgKytpKSB7CiAgICAgICAgcG9pbnRzW2ldID0gcG9pbnQobm9kZSwgdG91Y2hlc1tpXSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBwb2ludHM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9wcm9wYWdhdGlvbigpIHsKICAgICAgZXZlbnQuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9ldmVudCgpIHsKICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgZXZlbnQuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgZnVuY3Rpb24gZHJhZ0Rpc2FibGUodmlldykgewogICAgICB2YXIgcm9vdCA9IHZpZXcuZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LAogICAgICAgICAgc2VsZWN0aW9uID0gc2VsZWN0KHZpZXcpLm9uKCJkcmFnc3RhcnQuZHJhZyIsIG5vZXZlbnQsIHRydWUpOwogICAgICBpZiAoIm9uc2VsZWN0c3RhcnQiIGluIHJvb3QpIHsKICAgICAgICBzZWxlY3Rpb24ub24oInNlbGVjdHN0YXJ0LmRyYWciLCBub2V2ZW50LCB0cnVlKTsKICAgICAgfSBlbHNlIHsKICAgICAgICByb290Ll9fbm9zZWxlY3QgPSByb290LnN0eWxlLk1velVzZXJTZWxlY3Q7CiAgICAgICAgcm9vdC5zdHlsZS5Nb3pVc2VyU2VsZWN0ID0gIm5vbmUiOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24geWVzZHJhZyh2aWV3LCBub2NsaWNrKSB7CiAgICAgIHZhciByb290ID0gdmlldy5kb2N1bWVudC5kb2N1bWVudEVsZW1lbnQsCiAgICAgICAgICBzZWxlY3Rpb24gPSBzZWxlY3Qodmlldykub24oImRyYWdzdGFydC5kcmFnIiwgbnVsbCk7CiAgICAgIGlmIChub2NsaWNrKSB7CiAgICAgICAgc2VsZWN0aW9uLm9uKCJjbGljay5kcmFnIiwgbm9ldmVudCwgdHJ1ZSk7CiAgICAgICAgc2V0VGltZW91dChmdW5jdGlvbigpIHsgc2VsZWN0aW9uLm9uKCJjbGljay5kcmFnIiwgbnVsbCk7IH0sIDApOwogICAgICB9CiAgICAgIGlmICgib25zZWxlY3RzdGFydCIgaW4gcm9vdCkgewogICAgICAgIHNlbGVjdGlvbi5vbigic2VsZWN0c3RhcnQuZHJhZyIsIG51bGwpOwogICAgICB9IGVsc2UgewogICAgICAgIHJvb3Quc3R5bGUuTW96VXNlclNlbGVjdCA9IHJvb3QuX19ub3NlbGVjdDsKICAgICAgICBkZWxldGUgcm9vdC5fX25vc2VsZWN0OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkMih4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBEcmFnRXZlbnQodGFyZ2V0LCB0eXBlLCBzdWJqZWN0LCBpZCwgYWN0aXZlLCB4LCB5LCBkeCwgZHksIGRpc3BhdGNoKSB7CiAgICAgIHRoaXMudGFyZ2V0ID0gdGFyZ2V0OwogICAgICB0aGlzLnR5cGUgPSB0eXBlOwogICAgICB0aGlzLnN1YmplY3QgPSBzdWJqZWN0OwogICAgICB0aGlzLmlkZW50aWZpZXIgPSBpZDsKICAgICAgdGhpcy5hY3RpdmUgPSBhY3RpdmU7CiAgICAgIHRoaXMueCA9IHg7CiAgICAgIHRoaXMueSA9IHk7CiAgICAgIHRoaXMuZHggPSBkeDsKICAgICAgdGhpcy5keSA9IGR5OwogICAgICB0aGlzLl8gPSBkaXNwYXRjaDsKICAgIH0KCiAgICBEcmFnRXZlbnQucHJvdG90eXBlLm9uID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciB2YWx1ZSA9IHRoaXMuXy5vbi5hcHBseSh0aGlzLl8sIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiB2YWx1ZSA9PT0gdGhpcy5fID8gdGhpcyA6IHZhbHVlOwogICAgfTsKCiAgICAvLyBJZ25vcmUgcmlnaHQtY2xpY2ssIHNpbmNlIHRoYXQgc2hvdWxkIG9wZW4gdGhlIGNvbnRleHQgbWVudS4KICAgIGZ1bmN0aW9uIGRlZmF1bHRGaWx0ZXIoKSB7CiAgICAgIHJldHVybiAhZXZlbnQuY3RybEtleSAmJiAhZXZlbnQuYnV0dG9uOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRDb250YWluZXIoKSB7CiAgICAgIHJldHVybiB0aGlzLnBhcmVudE5vZGU7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFN1YmplY3QoZCkgewogICAgICByZXR1cm4gZCA9PSBudWxsID8ge3g6IGV2ZW50LngsIHk6IGV2ZW50Lnl9IDogZDsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0VG91Y2hhYmxlKCkgewogICAgICByZXR1cm4gbmF2aWdhdG9yLm1heFRvdWNoUG9pbnRzIHx8ICgib250b3VjaHN0YXJ0IiBpbiB0aGlzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkcmFnKCkgewogICAgICB2YXIgZmlsdGVyID0gZGVmYXVsdEZpbHRlciwKICAgICAgICAgIGNvbnRhaW5lciA9IGRlZmF1bHRDb250YWluZXIsCiAgICAgICAgICBzdWJqZWN0ID0gZGVmYXVsdFN1YmplY3QsCiAgICAgICAgICB0b3VjaGFibGUgPSBkZWZhdWx0VG91Y2hhYmxlLAogICAgICAgICAgZ2VzdHVyZXMgPSB7fSwKICAgICAgICAgIGxpc3RlbmVycyA9IGRpc3BhdGNoKCJzdGFydCIsICJkcmFnIiwgImVuZCIpLAogICAgICAgICAgYWN0aXZlID0gMCwKICAgICAgICAgIG1vdXNlZG93bngsCiAgICAgICAgICBtb3VzZWRvd255LAogICAgICAgICAgbW91c2Vtb3ZpbmcsCiAgICAgICAgICB0b3VjaGVuZGluZywKICAgICAgICAgIGNsaWNrRGlzdGFuY2UyID0gMDsKCiAgICAgIGZ1bmN0aW9uIGRyYWcoc2VsZWN0aW9uKSB7CiAgICAgICAgc2VsZWN0aW9uCiAgICAgICAgICAgIC5vbigibW91c2Vkb3duLmRyYWciLCBtb3VzZWRvd25lZCkKICAgICAgICAgIC5maWx0ZXIodG91Y2hhYmxlKQogICAgICAgICAgICAub24oInRvdWNoc3RhcnQuZHJhZyIsIHRvdWNoc3RhcnRlZCkKICAgICAgICAgICAgLm9uKCJ0b3VjaG1vdmUuZHJhZyIsIHRvdWNobW92ZWQpCiAgICAgICAgICAgIC5vbigidG91Y2hlbmQuZHJhZyB0b3VjaGNhbmNlbC5kcmFnIiwgdG91Y2hlbmRlZCkKICAgICAgICAgICAgLnN0eWxlKCJ0b3VjaC1hY3Rpb24iLCAibm9uZSIpCiAgICAgICAgICAgIC5zdHlsZSgiLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yIiwgInJnYmEoMCwwLDAsMCkiKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gbW91c2Vkb3duZWQoKSB7CiAgICAgICAgaWYgKHRvdWNoZW5kaW5nIHx8ICFmaWx0ZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgcmV0dXJuOwogICAgICAgIHZhciBnZXN0dXJlID0gYmVmb3Jlc3RhcnQoIm1vdXNlIiwgY29udGFpbmVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksIG1vdXNlLCB0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICghZ2VzdHVyZSkgcmV0dXJuOwogICAgICAgIHNlbGVjdChldmVudC52aWV3KS5vbigibW91c2Vtb3ZlLmRyYWciLCBtb3VzZW1vdmVkLCB0cnVlKS5vbigibW91c2V1cC5kcmFnIiwgbW91c2V1cHBlZCwgdHJ1ZSk7CiAgICAgICAgZHJhZ0Rpc2FibGUoZXZlbnQudmlldyk7CiAgICAgICAgbm9wcm9wYWdhdGlvbigpOwogICAgICAgIG1vdXNlbW92aW5nID0gZmFsc2U7CiAgICAgICAgbW91c2Vkb3dueCA9IGV2ZW50LmNsaWVudFg7CiAgICAgICAgbW91c2Vkb3dueSA9IGV2ZW50LmNsaWVudFk7CiAgICAgICAgZ2VzdHVyZSgic3RhcnQiKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gbW91c2Vtb3ZlZCgpIHsKICAgICAgICBub2V2ZW50KCk7CiAgICAgICAgaWYgKCFtb3VzZW1vdmluZykgewogICAgICAgICAgdmFyIGR4ID0gZXZlbnQuY2xpZW50WCAtIG1vdXNlZG93bngsIGR5ID0gZXZlbnQuY2xpZW50WSAtIG1vdXNlZG93bnk7CiAgICAgICAgICBtb3VzZW1vdmluZyA9IGR4ICogZHggKyBkeSAqIGR5ID4gY2xpY2tEaXN0YW5jZTI7CiAgICAgICAgfQogICAgICAgIGdlc3R1cmVzLm1vdXNlKCJkcmFnIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIG1vdXNldXBwZWQoKSB7CiAgICAgICAgc2VsZWN0KGV2ZW50LnZpZXcpLm9uKCJtb3VzZW1vdmUuZHJhZyBtb3VzZXVwLmRyYWciLCBudWxsKTsKICAgICAgICB5ZXNkcmFnKGV2ZW50LnZpZXcsIG1vdXNlbW92aW5nKTsKICAgICAgICBub2V2ZW50KCk7CiAgICAgICAgZ2VzdHVyZXMubW91c2UoImVuZCIpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0b3VjaHN0YXJ0ZWQoKSB7CiAgICAgICAgaWYgKCFmaWx0ZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgcmV0dXJuOwogICAgICAgIHZhciB0b3VjaGVzID0gZXZlbnQuY2hhbmdlZFRvdWNoZXMsCiAgICAgICAgICAgIGMgPSBjb250YWluZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgbiA9IHRvdWNoZXMubGVuZ3RoLCBpLCBnZXN0dXJlOwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoZ2VzdHVyZSA9IGJlZm9yZXN0YXJ0KHRvdWNoZXNbaV0uaWRlbnRpZmllciwgYywgdG91Y2gsIHRoaXMsIGFyZ3VtZW50cykpIHsKICAgICAgICAgICAgbm9wcm9wYWdhdGlvbigpOwogICAgICAgICAgICBnZXN0dXJlKCJzdGFydCIpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gdG91Y2htb3ZlZCgpIHsKICAgICAgICB2YXIgdG91Y2hlcyA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBuID0gdG91Y2hlcy5sZW5ndGgsIGksIGdlc3R1cmU7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChnZXN0dXJlID0gZ2VzdHVyZXNbdG91Y2hlc1tpXS5pZGVudGlmaWVyXSkgewogICAgICAgICAgICBub2V2ZW50KCk7CiAgICAgICAgICAgIGdlc3R1cmUoImRyYWciKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNoZW5kZWQoKSB7CiAgICAgICAgdmFyIHRvdWNoZXMgPSBldmVudC5jaGFuZ2VkVG91Y2hlcywKICAgICAgICAgICAgbiA9IHRvdWNoZXMubGVuZ3RoLCBpLCBnZXN0dXJlOwoKICAgICAgICBpZiAodG91Y2hlbmRpbmcpIGNsZWFyVGltZW91dCh0b3VjaGVuZGluZyk7CiAgICAgICAgdG91Y2hlbmRpbmcgPSBzZXRUaW1lb3V0KGZ1bmN0aW9uKCkgeyB0b3VjaGVuZGluZyA9IG51bGw7IH0sIDUwMCk7IC8vIEdob3N0IGNsaWNrcyBhcmUgZGVsYXllZCEKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoZ2VzdHVyZSA9IGdlc3R1cmVzW3RvdWNoZXNbaV0uaWRlbnRpZmllcl0pIHsKICAgICAgICAgICAgbm9wcm9wYWdhdGlvbigpOwogICAgICAgICAgICBnZXN0dXJlKCJlbmQiKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGJlZm9yZXN0YXJ0KGlkLCBjb250YWluZXIsIHBvaW50LCB0aGF0LCBhcmdzKSB7CiAgICAgICAgdmFyIHAgPSBwb2ludChjb250YWluZXIsIGlkKSwgcywgZHgsIGR5LAogICAgICAgICAgICBzdWJsaXN0ZW5lcnMgPSBsaXN0ZW5lcnMuY29weSgpOwoKICAgICAgICBpZiAoIWN1c3RvbUV2ZW50KG5ldyBEcmFnRXZlbnQoZHJhZywgImJlZm9yZXN0YXJ0IiwgcywgaWQsIGFjdGl2ZSwgcFswXSwgcFsxXSwgMCwgMCwgc3VibGlzdGVuZXJzKSwgZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoKGV2ZW50LnN1YmplY3QgPSBzID0gc3ViamVjdC5hcHBseSh0aGF0LCBhcmdzKSkgPT0gbnVsbCkgcmV0dXJuIGZhbHNlOwogICAgICAgICAgZHggPSBzLnggLSBwWzBdIHx8IDA7CiAgICAgICAgICBkeSA9IHMueSAtIHBbMV0gfHwgMDsKICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0pKSByZXR1cm47CgogICAgICAgIHJldHVybiBmdW5jdGlvbiBnZXN0dXJlKHR5cGUpIHsKICAgICAgICAgIHZhciBwMCA9IHAsIG47CiAgICAgICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICAgICAgY2FzZSAic3RhcnQiOiBnZXN0dXJlc1tpZF0gPSBnZXN0dXJlLCBuID0gYWN0aXZlKys7IGJyZWFrOwogICAgICAgICAgICBjYXNlICJlbmQiOiBkZWxldGUgZ2VzdHVyZXNbaWRdLCAtLWFjdGl2ZTsgLy8gbm9icmVhawogICAgICAgICAgICBjYXNlICJkcmFnIjogcCA9IHBvaW50KGNvbnRhaW5lciwgaWQpLCBuID0gYWN0aXZlOyBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGN1c3RvbUV2ZW50KG5ldyBEcmFnRXZlbnQoZHJhZywgdHlwZSwgcywgaWQsIG4sIHBbMF0gKyBkeCwgcFsxXSArIGR5LCBwWzBdIC0gcDBbMF0sIHBbMV0gLSBwMFsxXSwgc3VibGlzdGVuZXJzKSwgc3VibGlzdGVuZXJzLmFwcGx5LCBzdWJsaXN0ZW5lcnMsIFt0eXBlLCB0aGF0LCBhcmdzXSk7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgZHJhZy5maWx0ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZmlsdGVyID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkMighIV8pLCBkcmFnKSA6IGZpbHRlcjsKICAgICAgfTsKCiAgICAgIGRyYWcuY29udGFpbmVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNvbnRhaW5lciA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDIoXyksIGRyYWcpIDogY29udGFpbmVyOwogICAgICB9OwoKICAgICAgZHJhZy5zdWJqZWN0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN1YmplY3QgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQyKF8pLCBkcmFnKSA6IHN1YmplY3Q7CiAgICAgIH07CgogICAgICBkcmFnLnRvdWNoYWJsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0b3VjaGFibGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQyKCEhXyksIGRyYWcpIDogdG91Y2hhYmxlOwogICAgICB9OwoKICAgICAgZHJhZy5vbiA9IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZSA9IGxpc3RlbmVycy5vbi5hcHBseShsaXN0ZW5lcnMsIGFyZ3VtZW50cyk7CiAgICAgICAgcmV0dXJuIHZhbHVlID09PSBsaXN0ZW5lcnMgPyBkcmFnIDogdmFsdWU7CiAgICAgIH07CgogICAgICBkcmFnLmNsaWNrRGlzdGFuY2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY2xpY2tEaXN0YW5jZTIgPSAoXyA9ICtfKSAqIF8sIGRyYWcpIDogTWF0aC5zcXJ0KGNsaWNrRGlzdGFuY2UyKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBkcmFnOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmluZShjb25zdHJ1Y3RvciwgZmFjdG9yeSwgcHJvdG90eXBlKSB7CiAgICAgIGNvbnN0cnVjdG9yLnByb3RvdHlwZSA9IGZhY3RvcnkucHJvdG90eXBlID0gcHJvdG90eXBlOwogICAgICBwcm90b3R5cGUuY29uc3RydWN0b3IgPSBjb25zdHJ1Y3RvcjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHRlbmQocGFyZW50LCBkZWZpbml0aW9uKSB7CiAgICAgIHZhciBwcm90b3R5cGUgPSBPYmplY3QuY3JlYXRlKHBhcmVudC5wcm90b3R5cGUpOwogICAgICBmb3IgKHZhciBrZXkgaW4gZGVmaW5pdGlvbikgcHJvdG90eXBlW2tleV0gPSBkZWZpbml0aW9uW2tleV07CiAgICAgIHJldHVybiBwcm90b3R5cGU7CiAgICB9CgogICAgZnVuY3Rpb24gQ29sb3IoKSB7fQoKICAgIHZhciBkYXJrZXIgPSAwLjc7CiAgICB2YXIgYnJpZ2h0ZXIgPSAxIC8gZGFya2VyOwoKICAgIHZhciByZUkgPSAiXFxzKihbKy1dP1xcZCspXFxzKiIsCiAgICAgICAgcmVOID0gIlxccyooWystXT9cXGQqXFwuP1xcZCsoPzpbZUVdWystXT9cXGQrKT8pXFxzKiIsCiAgICAgICAgcmVQID0gIlxccyooWystXT9cXGQqXFwuP1xcZCsoPzpbZUVdWystXT9cXGQrKT8pJVxccyoiLAogICAgICAgIHJlSGV4ID0gL14jKFswLTlhLWZdezMsOH0pJC8sCiAgICAgICAgcmVSZ2JJbnRlZ2VyID0gbmV3IFJlZ0V4cCgiXnJnYlxcKCIgKyBbcmVJLCByZUksIHJlSV0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiUGVyY2VudCA9IG5ldyBSZWdFeHAoIl5yZ2JcXCgiICsgW3JlUCwgcmVQLCByZVBdICsgIlxcKSQiKSwKICAgICAgICByZVJnYmFJbnRlZ2VyID0gbmV3IFJlZ0V4cCgiXnJnYmFcXCgiICsgW3JlSSwgcmVJLCByZUksIHJlTl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiYVBlcmNlbnQgPSBuZXcgUmVnRXhwKCJecmdiYVxcKCIgKyBbcmVQLCByZVAsIHJlUCwgcmVOXSArICJcXCkkIiksCiAgICAgICAgcmVIc2xQZXJjZW50ID0gbmV3IFJlZ0V4cCgiXmhzbFxcKCIgKyBbcmVOLCByZVAsIHJlUF0gKyAiXFwpJCIpLAogICAgICAgIHJlSHNsYVBlcmNlbnQgPSBuZXcgUmVnRXhwKCJeaHNsYVxcKCIgKyBbcmVOLCByZVAsIHJlUCwgcmVOXSArICJcXCkkIik7CgogICAgdmFyIG5hbWVkID0gewogICAgICBhbGljZWJsdWU6IDB4ZjBmOGZmLAogICAgICBhbnRpcXVld2hpdGU6IDB4ZmFlYmQ3LAogICAgICBhcXVhOiAweDAwZmZmZiwKICAgICAgYXF1YW1hcmluZTogMHg3ZmZmZDQsCiAgICAgIGF6dXJlOiAweGYwZmZmZiwKICAgICAgYmVpZ2U6IDB4ZjVmNWRjLAogICAgICBiaXNxdWU6IDB4ZmZlNGM0LAogICAgICBibGFjazogMHgwMDAwMDAsCiAgICAgIGJsYW5jaGVkYWxtb25kOiAweGZmZWJjZCwKICAgICAgYmx1ZTogMHgwMDAwZmYsCiAgICAgIGJsdWV2aW9sZXQ6IDB4OGEyYmUyLAogICAgICBicm93bjogMHhhNTJhMmEsCiAgICAgIGJ1cmx5d29vZDogMHhkZWI4ODcsCiAgICAgIGNhZGV0Ymx1ZTogMHg1ZjllYTAsCiAgICAgIGNoYXJ0cmV1c2U6IDB4N2ZmZjAwLAogICAgICBjaG9jb2xhdGU6IDB4ZDI2OTFlLAogICAgICBjb3JhbDogMHhmZjdmNTAsCiAgICAgIGNvcm5mbG93ZXJibHVlOiAweDY0OTVlZCwKICAgICAgY29ybnNpbGs6IDB4ZmZmOGRjLAogICAgICBjcmltc29uOiAweGRjMTQzYywKICAgICAgY3lhbjogMHgwMGZmZmYsCiAgICAgIGRhcmtibHVlOiAweDAwMDA4YiwKICAgICAgZGFya2N5YW46IDB4MDA4YjhiLAogICAgICBkYXJrZ29sZGVucm9kOiAweGI4ODYwYiwKICAgICAgZGFya2dyYXk6IDB4YTlhOWE5LAogICAgICBkYXJrZ3JlZW46IDB4MDA2NDAwLAogICAgICBkYXJrZ3JleTogMHhhOWE5YTksCiAgICAgIGRhcmtraGFraTogMHhiZGI3NmIsCiAgICAgIGRhcmttYWdlbnRhOiAweDhiMDA4YiwKICAgICAgZGFya29saXZlZ3JlZW46IDB4NTU2YjJmLAogICAgICBkYXJrb3JhbmdlOiAweGZmOGMwMCwKICAgICAgZGFya29yY2hpZDogMHg5OTMyY2MsCiAgICAgIGRhcmtyZWQ6IDB4OGIwMDAwLAogICAgICBkYXJrc2FsbW9uOiAweGU5OTY3YSwKICAgICAgZGFya3NlYWdyZWVuOiAweDhmYmM4ZiwKICAgICAgZGFya3NsYXRlYmx1ZTogMHg0ODNkOGIsCiAgICAgIGRhcmtzbGF0ZWdyYXk6IDB4MmY0ZjRmLAogICAgICBkYXJrc2xhdGVncmV5OiAweDJmNGY0ZiwKICAgICAgZGFya3R1cnF1b2lzZTogMHgwMGNlZDEsCiAgICAgIGRhcmt2aW9sZXQ6IDB4OTQwMGQzLAogICAgICBkZWVwcGluazogMHhmZjE0OTMsCiAgICAgIGRlZXBza3libHVlOiAweDAwYmZmZiwKICAgICAgZGltZ3JheTogMHg2OTY5NjksCiAgICAgIGRpbWdyZXk6IDB4Njk2OTY5LAogICAgICBkb2RnZXJibHVlOiAweDFlOTBmZiwKICAgICAgZmlyZWJyaWNrOiAweGIyMjIyMiwKICAgICAgZmxvcmFsd2hpdGU6IDB4ZmZmYWYwLAogICAgICBmb3Jlc3RncmVlbjogMHgyMjhiMjIsCiAgICAgIGZ1Y2hzaWE6IDB4ZmYwMGZmLAogICAgICBnYWluc2Jvcm86IDB4ZGNkY2RjLAogICAgICBnaG9zdHdoaXRlOiAweGY4ZjhmZiwKICAgICAgZ29sZDogMHhmZmQ3MDAsCiAgICAgIGdvbGRlbnJvZDogMHhkYWE1MjAsCiAgICAgIGdyYXk6IDB4ODA4MDgwLAogICAgICBncmVlbjogMHgwMDgwMDAsCiAgICAgIGdyZWVueWVsbG93OiAweGFkZmYyZiwKICAgICAgZ3JleTogMHg4MDgwODAsCiAgICAgIGhvbmV5ZGV3OiAweGYwZmZmMCwKICAgICAgaG90cGluazogMHhmZjY5YjQsCiAgICAgIGluZGlhbnJlZDogMHhjZDVjNWMsCiAgICAgIGluZGlnbzogMHg0YjAwODIsCiAgICAgIGl2b3J5OiAweGZmZmZmMCwKICAgICAga2hha2k6IDB4ZjBlNjhjLAogICAgICBsYXZlbmRlcjogMHhlNmU2ZmEsCiAgICAgIGxhdmVuZGVyYmx1c2g6IDB4ZmZmMGY1LAogICAgICBsYXduZ3JlZW46IDB4N2NmYzAwLAogICAgICBsZW1vbmNoaWZmb246IDB4ZmZmYWNkLAogICAgICBsaWdodGJsdWU6IDB4YWRkOGU2LAogICAgICBsaWdodGNvcmFsOiAweGYwODA4MCwKICAgICAgbGlnaHRjeWFuOiAweGUwZmZmZiwKICAgICAgbGlnaHRnb2xkZW5yb2R5ZWxsb3c6IDB4ZmFmYWQyLAogICAgICBsaWdodGdyYXk6IDB4ZDNkM2QzLAogICAgICBsaWdodGdyZWVuOiAweDkwZWU5MCwKICAgICAgbGlnaHRncmV5OiAweGQzZDNkMywKICAgICAgbGlnaHRwaW5rOiAweGZmYjZjMSwKICAgICAgbGlnaHRzYWxtb246IDB4ZmZhMDdhLAogICAgICBsaWdodHNlYWdyZWVuOiAweDIwYjJhYSwKICAgICAgbGlnaHRza3libHVlOiAweDg3Y2VmYSwKICAgICAgbGlnaHRzbGF0ZWdyYXk6IDB4Nzc4ODk5LAogICAgICBsaWdodHNsYXRlZ3JleTogMHg3Nzg4OTksCiAgICAgIGxpZ2h0c3RlZWxibHVlOiAweGIwYzRkZSwKICAgICAgbGlnaHR5ZWxsb3c6IDB4ZmZmZmUwLAogICAgICBsaW1lOiAweDAwZmYwMCwKICAgICAgbGltZWdyZWVuOiAweDMyY2QzMiwKICAgICAgbGluZW46IDB4ZmFmMGU2LAogICAgICBtYWdlbnRhOiAweGZmMDBmZiwKICAgICAgbWFyb29uOiAweDgwMDAwMCwKICAgICAgbWVkaXVtYXF1YW1hcmluZTogMHg2NmNkYWEsCiAgICAgIG1lZGl1bWJsdWU6IDB4MDAwMGNkLAogICAgICBtZWRpdW1vcmNoaWQ6IDB4YmE1NWQzLAogICAgICBtZWRpdW1wdXJwbGU6IDB4OTM3MGRiLAogICAgICBtZWRpdW1zZWFncmVlbjogMHgzY2IzNzEsCiAgICAgIG1lZGl1bXNsYXRlYmx1ZTogMHg3YjY4ZWUsCiAgICAgIG1lZGl1bXNwcmluZ2dyZWVuOiAweDAwZmE5YSwKICAgICAgbWVkaXVtdHVycXVvaXNlOiAweDQ4ZDFjYywKICAgICAgbWVkaXVtdmlvbGV0cmVkOiAweGM3MTU4NSwKICAgICAgbWlkbmlnaHRibHVlOiAweDE5MTk3MCwKICAgICAgbWludGNyZWFtOiAweGY1ZmZmYSwKICAgICAgbWlzdHlyb3NlOiAweGZmZTRlMSwKICAgICAgbW9jY2FzaW46IDB4ZmZlNGI1LAogICAgICBuYXZham93aGl0ZTogMHhmZmRlYWQsCiAgICAgIG5hdnk6IDB4MDAwMDgwLAogICAgICBvbGRsYWNlOiAweGZkZjVlNiwKICAgICAgb2xpdmU6IDB4ODA4MDAwLAogICAgICBvbGl2ZWRyYWI6IDB4NmI4ZTIzLAogICAgICBvcmFuZ2U6IDB4ZmZhNTAwLAogICAgICBvcmFuZ2VyZWQ6IDB4ZmY0NTAwLAogICAgICBvcmNoaWQ6IDB4ZGE3MGQ2LAogICAgICBwYWxlZ29sZGVucm9kOiAweGVlZThhYSwKICAgICAgcGFsZWdyZWVuOiAweDk4ZmI5OCwKICAgICAgcGFsZXR1cnF1b2lzZTogMHhhZmVlZWUsCiAgICAgIHBhbGV2aW9sZXRyZWQ6IDB4ZGI3MDkzLAogICAgICBwYXBheWF3aGlwOiAweGZmZWZkNSwKICAgICAgcGVhY2hwdWZmOiAweGZmZGFiOSwKICAgICAgcGVydTogMHhjZDg1M2YsCiAgICAgIHBpbms6IDB4ZmZjMGNiLAogICAgICBwbHVtOiAweGRkYTBkZCwKICAgICAgcG93ZGVyYmx1ZTogMHhiMGUwZTYsCiAgICAgIHB1cnBsZTogMHg4MDAwODAsCiAgICAgIHJlYmVjY2FwdXJwbGU6IDB4NjYzMzk5LAogICAgICByZWQ6IDB4ZmYwMDAwLAogICAgICByb3N5YnJvd246IDB4YmM4ZjhmLAogICAgICByb3lhbGJsdWU6IDB4NDE2OWUxLAogICAgICBzYWRkbGVicm93bjogMHg4YjQ1MTMsCiAgICAgIHNhbG1vbjogMHhmYTgwNzIsCiAgICAgIHNhbmR5YnJvd246IDB4ZjRhNDYwLAogICAgICBzZWFncmVlbjogMHgyZThiNTcsCiAgICAgIHNlYXNoZWxsOiAweGZmZjVlZSwKICAgICAgc2llbm5hOiAweGEwNTIyZCwKICAgICAgc2lsdmVyOiAweGMwYzBjMCwKICAgICAgc2t5Ymx1ZTogMHg4N2NlZWIsCiAgICAgIHNsYXRlYmx1ZTogMHg2YTVhY2QsCiAgICAgIHNsYXRlZ3JheTogMHg3MDgwOTAsCiAgICAgIHNsYXRlZ3JleTogMHg3MDgwOTAsCiAgICAgIHNub3c6IDB4ZmZmYWZhLAogICAgICBzcHJpbmdncmVlbjogMHgwMGZmN2YsCiAgICAgIHN0ZWVsYmx1ZTogMHg0NjgyYjQsCiAgICAgIHRhbjogMHhkMmI0OGMsCiAgICAgIHRlYWw6IDB4MDA4MDgwLAogICAgICB0aGlzdGxlOiAweGQ4YmZkOCwKICAgICAgdG9tYXRvOiAweGZmNjM0NywKICAgICAgdHVycXVvaXNlOiAweDQwZTBkMCwKICAgICAgdmlvbGV0OiAweGVlODJlZSwKICAgICAgd2hlYXQ6IDB4ZjVkZWIzLAogICAgICB3aGl0ZTogMHhmZmZmZmYsCiAgICAgIHdoaXRlc21va2U6IDB4ZjVmNWY1LAogICAgICB5ZWxsb3c6IDB4ZmZmZjAwLAogICAgICB5ZWxsb3dncmVlbjogMHg5YWNkMzIKICAgIH07CgogICAgZGVmaW5lKENvbG9yLCBjb2xvciwgewogICAgICBjb3B5OiBmdW5jdGlvbihjaGFubmVscykgewogICAgICAgIHJldHVybiBPYmplY3QuYXNzaWduKG5ldyB0aGlzLmNvbnN0cnVjdG9yLCB0aGlzLCBjaGFubmVscyk7CiAgICAgIH0sCiAgICAgIGRpc3BsYXlhYmxlOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5yZ2IoKS5kaXNwbGF5YWJsZSgpOwogICAgICB9LAogICAgICBoZXg6IGNvbG9yX2Zvcm1hdEhleCwgLy8gRGVwcmVjYXRlZCEgVXNlIGNvbG9yLmZvcm1hdEhleC4KICAgICAgZm9ybWF0SGV4OiBjb2xvcl9mb3JtYXRIZXgsCiAgICAgIGZvcm1hdEhzbDogY29sb3JfZm9ybWF0SHNsLAogICAgICBmb3JtYXRSZ2I6IGNvbG9yX2Zvcm1hdFJnYiwKICAgICAgdG9TdHJpbmc6IGNvbG9yX2Zvcm1hdFJnYgogICAgfSk7CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0SGV4KCkgewogICAgICByZXR1cm4gdGhpcy5yZ2IoKS5mb3JtYXRIZXgoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvcl9mb3JtYXRIc2woKSB7CiAgICAgIHJldHVybiBoc2xDb252ZXJ0KHRoaXMpLmZvcm1hdEhzbCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdFJnYigpIHsKICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZm9ybWF0UmdiKCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3IoZm9ybWF0KSB7CiAgICAgIHZhciBtLCBsOwogICAgICBmb3JtYXQgPSAoZm9ybWF0ICsgIiIpLnRyaW0oKS50b0xvd2VyQ2FzZSgpOwogICAgICByZXR1cm4gKG0gPSByZUhleC5leGVjKGZvcm1hdCkpID8gKGwgPSBtWzFdLmxlbmd0aCwgbSA9IHBhcnNlSW50KG1bMV0sIDE2KSwgbCA9PT0gNiA/IHJnYm4obSkgLy8gI2ZmMDAwMAogICAgICAgICAgOiBsID09PSAzID8gbmV3IFJnYigobSA+PiA4ICYgMHhmKSB8IChtID4+IDQgJiAweGYwKSwgKG0gPj4gNCAmIDB4ZikgfCAobSAmIDB4ZjApLCAoKG0gJiAweGYpIDw8IDQpIHwgKG0gJiAweGYpLCAxKSAvLyAjZjAwCiAgICAgICAgICA6IGwgPT09IDggPyByZ2JhKG0gPj4gMjQgJiAweGZmLCBtID4+IDE2ICYgMHhmZiwgbSA+PiA4ICYgMHhmZiwgKG0gJiAweGZmKSAvIDB4ZmYpIC8vICNmZjAwMDAwMAogICAgICAgICAgOiBsID09PSA0ID8gcmdiYSgobSA+PiAxMiAmIDB4ZikgfCAobSA+PiA4ICYgMHhmMCksIChtID4+IDggJiAweGYpIHwgKG0gPj4gNCAmIDB4ZjApLCAobSA+PiA0ICYgMHhmKSB8IChtICYgMHhmMCksICgoKG0gJiAweGYpIDw8IDQpIHwgKG0gJiAweGYpKSAvIDB4ZmYpIC8vICNmMDAwCiAgICAgICAgICA6IG51bGwpIC8vIGludmFsaWQgaGV4CiAgICAgICAgICA6IChtID0gcmVSZ2JJbnRlZ2VyLmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiKG1bMV0sIG1bMl0sIG1bM10sIDEpIC8vIHJnYigyNTUsIDAsIDApCiAgICAgICAgICA6IChtID0gcmVSZ2JQZXJjZW50LmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiKG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIDEpIC8vIHJnYigxMDAlLCAwJSwgMCUpCiAgICAgICAgICA6IChtID0gcmVSZ2JhSW50ZWdlci5leGVjKGZvcm1hdCkpID8gcmdiYShtWzFdLCBtWzJdLCBtWzNdLCBtWzRdKSAvLyByZ2JhKDI1NSwgMCwgMCwgMSkKICAgICAgICAgIDogKG0gPSByZVJnYmFQZXJjZW50LmV4ZWMoZm9ybWF0KSkgPyByZ2JhKG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIG1bNF0pIC8vIHJnYigxMDAlLCAwJSwgMCUsIDEpCiAgICAgICAgICA6IChtID0gcmVIc2xQZXJjZW50LmV4ZWMoZm9ybWF0KSkgPyBoc2xhKG1bMV0sIG1bMl0gLyAxMDAsIG1bM10gLyAxMDAsIDEpIC8vIGhzbCgxMjAsIDUwJSwgNTAlKQogICAgICAgICAgOiAobSA9IHJlSHNsYVBlcmNlbnQuZXhlYyhmb3JtYXQpKSA/IGhzbGEobVsxXSwgbVsyXSAvIDEwMCwgbVszXSAvIDEwMCwgbVs0XSkgLy8gaHNsYSgxMjAsIDUwJSwgNTAlLCAxKQogICAgICAgICAgOiBuYW1lZC5oYXNPd25Qcm9wZXJ0eShmb3JtYXQpID8gcmdibihuYW1lZFtmb3JtYXRdKSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXByb3RvdHlwZS1idWlsdGlucwogICAgICAgICAgOiBmb3JtYXQgPT09ICJ0cmFuc3BhcmVudCIgPyBuZXcgUmdiKE5hTiwgTmFOLCBOYU4sIDApCiAgICAgICAgICA6IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gcmdibihuKSB7CiAgICAgIHJldHVybiBuZXcgUmdiKG4gPj4gMTYgJiAweGZmLCBuID4+IDggJiAweGZmLCBuICYgMHhmZiwgMSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiYShyLCBnLCBiLCBhKSB7CiAgICAgIGlmIChhIDw9IDApIHIgPSBnID0gYiA9IE5hTjsKICAgICAgcmV0dXJuIG5ldyBSZ2IociwgZywgYiwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiQ29udmVydChvKSB7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvcikpIG8gPSBjb2xvcihvKTsKICAgICAgaWYgKCFvKSByZXR1cm4gbmV3IFJnYjsKICAgICAgbyA9IG8ucmdiKCk7CiAgICAgIHJldHVybiBuZXcgUmdiKG8uciwgby5nLCBvLmIsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiKHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyByZ2JDb252ZXJ0KHIpIDogbmV3IFJnYihyLCBnLCBiLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gUmdiKHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5yID0gK3I7CiAgICAgIHRoaXMuZyA9ICtnOwogICAgICB0aGlzLmIgPSArYjsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lKFJnYiwgcmdiLCBleHRlbmQoQ29sb3IsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIgOiBNYXRoLnBvdyhicmlnaHRlciwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciA6IE1hdGgucG93KGRhcmtlciwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoLTAuNSA8PSB0aGlzLnIgJiYgdGhpcy5yIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgtMC41IDw9IHRoaXMuZyAmJiB0aGlzLmcgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKC0wLjUgPD0gdGhpcy5iICYmIHRoaXMuYiA8IDI1NS41KQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9LAogICAgICBoZXg6IHJnYl9mb3JtYXRIZXgsIC8vIERlcHJlY2F0ZWQhIFVzZSBjb2xvci5mb3JtYXRIZXguCiAgICAgIGZvcm1hdEhleDogcmdiX2Zvcm1hdEhleCwKICAgICAgZm9ybWF0UmdiOiByZ2JfZm9ybWF0UmdiLAogICAgICB0b1N0cmluZzogcmdiX2Zvcm1hdFJnYgogICAgfSkpOwoKICAgIGZ1bmN0aW9uIHJnYl9mb3JtYXRIZXgoKSB7CiAgICAgIHJldHVybiAiIyIgKyBoZXgodGhpcy5yKSArIGhleCh0aGlzLmcpICsgaGV4KHRoaXMuYik7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiX2Zvcm1hdFJnYigpIHsKICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgIHJldHVybiAoYSA9PT0gMSA/ICJyZ2IoIiA6ICJyZ2JhKCIpCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLnIpIHx8IDApKSArICIsICIKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuZykgfHwgMCkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5iKSB8fCAwKSkKICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICB9CgogICAgZnVuY3Rpb24gaGV4KHZhbHVlKSB7CiAgICAgIHZhbHVlID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHZhbHVlKSB8fCAwKSk7CiAgICAgIHJldHVybiAodmFsdWUgPCAxNiA/ICIwIiA6ICIiKSArIHZhbHVlLnRvU3RyaW5nKDE2KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xhKGgsIHMsIGwsIGEpIHsKICAgICAgaWYgKGEgPD0gMCkgaCA9IHMgPSBsID0gTmFOOwogICAgICBlbHNlIGlmIChsIDw9IDAgfHwgbCA+PSAxKSBoID0gcyA9IE5hTjsKICAgICAgZWxzZSBpZiAocyA8PSAwKSBoID0gTmFOOwogICAgICByZXR1cm4gbmV3IEhzbChoLCBzLCBsLCBhKTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xDb252ZXJ0KG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wpIHJldHVybiBuZXcgSHNsKG8uaCwgby5zLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvcikpIG8gPSBjb2xvcihvKTsKICAgICAgaWYgKCFvKSByZXR1cm4gbmV3IEhzbDsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wpIHJldHVybiBvOwogICAgICBvID0gby5yZ2IoKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIG1pbiA9IE1hdGgubWluKHIsIGcsIGIpLAogICAgICAgICAgbWF4ID0gTWF0aC5tYXgociwgZywgYiksCiAgICAgICAgICBoID0gTmFOLAogICAgICAgICAgcyA9IG1heCAtIG1pbiwKICAgICAgICAgIGwgPSAobWF4ICsgbWluKSAvIDI7CiAgICAgIGlmIChzKSB7CiAgICAgICAgaWYgKHIgPT09IG1heCkgaCA9IChnIC0gYikgLyBzICsgKGcgPCBiKSAqIDY7CiAgICAgICAgZWxzZSBpZiAoZyA9PT0gbWF4KSBoID0gKGIgLSByKSAvIHMgKyAyOwogICAgICAgIGVsc2UgaCA9IChyIC0gZykgLyBzICsgNDsKICAgICAgICBzIC89IGwgPCAwLjUgPyBtYXggKyBtaW4gOiAyIC0gbWF4IC0gbWluOwogICAgICAgIGggKj0gNjA7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcyA9IGwgPiAwICYmIGwgPCAxID8gMCA6IGg7CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBIc2woaCwgcywgbCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2woaCwgcywgbCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGhzbENvbnZlcnQoaCkgOiBuZXcgSHNsKGgsIHMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBIc2woaCwgcywgbCwgb3BhY2l0eSkgewogICAgICB0aGlzLmggPSAraDsKICAgICAgdGhpcy5zID0gK3M7CiAgICAgIHRoaXMubCA9ICtsOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUoSHNsLCBoc2wsIGV4dGVuZChDb2xvciwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBicmlnaHRlciA6IE1hdGgucG93KGJyaWdodGVyLCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCh0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciA6IE1hdGgucG93KGRhcmtlciwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBIc2wodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIHJnYjogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGggPSB0aGlzLmggJSAzNjAgKyAodGhpcy5oIDwgMCkgKiAzNjAsCiAgICAgICAgICAgIHMgPSBpc05hTihoKSB8fCBpc05hTih0aGlzLnMpID8gMCA6IHRoaXMucywKICAgICAgICAgICAgbCA9IHRoaXMubCwKICAgICAgICAgICAgbTIgPSBsICsgKGwgPCAwLjUgPyBsIDogMSAtIGwpICogcywKICAgICAgICAgICAgbTEgPSAyICogbCAtIG0yOwogICAgICAgIHJldHVybiBuZXcgUmdiKAogICAgICAgICAgaHNsMnJnYihoID49IDI0MCA/IGggLSAyNDAgOiBoICsgMTIwLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYihoLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYihoIDwgMTIwID8gaCArIDI0MCA6IGggLSAxMjAsIG0xLCBtMiksCiAgICAgICAgICB0aGlzLm9wYWNpdHkKICAgICAgICApOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuICgwIDw9IHRoaXMucyAmJiB0aGlzLnMgPD0gMSB8fCBpc05hTih0aGlzLnMpKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLmwgJiYgdGhpcy5sIDw9IDEpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMub3BhY2l0eSAmJiB0aGlzLm9wYWNpdHkgPD0gMSk7CiAgICAgIH0sCiAgICAgIGZvcm1hdEhzbDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgICAgcmV0dXJuIChhID09PSAxID8gImhzbCgiIDogImhzbGEoIikKICAgICAgICAgICAgKyAodGhpcy5oIHx8IDApICsgIiwgIgogICAgICAgICAgICArICh0aGlzLnMgfHwgMCkgKiAxMDAgKyAiJSwgIgogICAgICAgICAgICArICh0aGlzLmwgfHwgMCkgKiAxMDAgKyAiJSIKICAgICAgICAgICAgKyAoYSA9PT0gMSA/ICIpIiA6ICIsICIgKyBhICsgIikiKTsKICAgICAgfQogICAgfSkpOwoKICAgIC8qIEZyb20gRnZEIDEzLjM3LCBDU1MgQ29sb3IgTW9kdWxlIExldmVsIDMgKi8KICAgIGZ1bmN0aW9uIGhzbDJyZ2IoaCwgbTEsIG0yKSB7CiAgICAgIHJldHVybiAoaCA8IDYwID8gbTEgKyAobTIgLSBtMSkgKiBoIC8gNjAKICAgICAgICAgIDogaCA8IDE4MCA/IG0yCiAgICAgICAgICA6IGggPCAyNDAgPyBtMSArIChtMiAtIG0xKSAqICgyNDAgLSBoKSAvIDYwCiAgICAgICAgICA6IG0xKSAqIDI1NTsKICAgIH0KCiAgICB2YXIgZGVnMnJhZCA9IE1hdGguUEkgLyAxODA7CiAgICB2YXIgcmFkMmRlZyA9IDE4MCAvIE1hdGguUEk7CgogICAgLy8gaHR0cHM6Ly9vYnNlcnZhYmxlaHEuY29tL0BtYm9zdG9jay9sYWItYW5kLXJnYgogICAgdmFyIEsgPSAxOCwKICAgICAgICBYbiA9IDAuOTY0MjIsCiAgICAgICAgWW4gPSAxLAogICAgICAgIFpuID0gMC44MjUyMSwKICAgICAgICB0MCA9IDQgLyAyOSwKICAgICAgICB0MSA9IDYgLyAyOSwKICAgICAgICB0MiA9IDMgKiB0MSAqIHQxLAogICAgICAgIHQzID0gdDEgKiB0MSAqIHQxOwoKICAgIGZ1bmN0aW9uIGxhYkNvbnZlcnQobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIExhYikgcmV0dXJuIG5ldyBMYWIoby5sLCBvLmEsIG8uYiwgby5vcGFjaXR5KTsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIY2wpIHJldHVybiBoY2wybGFiKG8pOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgUmdiKSkgbyA9IHJnYkNvbnZlcnQobyk7CiAgICAgIHZhciByID0gcmdiMmxyZ2Ioby5yKSwKICAgICAgICAgIGcgPSByZ2IybHJnYihvLmcpLAogICAgICAgICAgYiA9IHJnYjJscmdiKG8uYiksCiAgICAgICAgICB5ID0geHl6MmxhYigoMC4yMjI1MDQ1ICogciArIDAuNzE2ODc4NiAqIGcgKyAwLjA2MDYxNjkgKiBiKSAvIFluKSwgeCwgejsKICAgICAgaWYgKHIgPT09IGcgJiYgZyA9PT0gYikgeCA9IHogPSB5OyBlbHNlIHsKICAgICAgICB4ID0geHl6MmxhYigoMC40MzYwNzQ3ICogciArIDAuMzg1MDY0OSAqIGcgKyAwLjE0MzA4MDQgKiBiKSAvIFhuKTsKICAgICAgICB6ID0geHl6MmxhYigoMC4wMTM5MzIyICogciArIDAuMDk3MTA0NSAqIGcgKyAwLjcxNDE3MzMgKiBiKSAvIFpuKTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IExhYigxMTYgKiB5IC0gMTYsIDUwMCAqICh4IC0geSksIDIwMCAqICh5IC0geiksIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gZ3JheShsLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBuZXcgTGFiKGwsIDAsIDAsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBsYWIobCwgYSwgYiwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGxhYkNvbnZlcnQobCkgOiBuZXcgTGFiKGwsIGEsIGIsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBMYWIobCwgYSwgYiwgb3BhY2l0eSkgewogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5hID0gK2E7CiAgICAgIHRoaXMuYiA9ICtiOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUoTGFiLCBsYWIsIGV4dGVuZChDb2xvciwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIHJldHVybiBuZXcgTGFiKHRoaXMubCArIEsgKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLmEsIHRoaXMuYiwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBMYWIodGhpcy5sIC0gSyAqIChrID09IG51bGwgPyAxIDogayksIHRoaXMuYSwgdGhpcy5iLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB5ID0gKHRoaXMubCArIDE2KSAvIDExNiwKICAgICAgICAgICAgeCA9IGlzTmFOKHRoaXMuYSkgPyB5IDogeSArIHRoaXMuYSAvIDUwMCwKICAgICAgICAgICAgeiA9IGlzTmFOKHRoaXMuYikgPyB5IDogeSAtIHRoaXMuYiAvIDIwMDsKICAgICAgICB4ID0gWG4gKiBsYWIyeHl6KHgpOwogICAgICAgIHkgPSBZbiAqIGxhYjJ4eXooeSk7CiAgICAgICAgeiA9IFpuICogbGFiMnh5eih6KTsKICAgICAgICByZXR1cm4gbmV3IFJnYigKICAgICAgICAgIGxyZ2IycmdiKCAzLjEzMzg1NjEgKiB4IC0gMS42MTY4NjY3ICogeSAtIDAuNDkwNjE0NiAqIHopLAogICAgICAgICAgbHJnYjJyZ2IoLTAuOTc4NzY4NCAqIHggKyAxLjkxNjE0MTUgKiB5ICsgMC4wMzM0NTQwICogeiksCiAgICAgICAgICBscmdiMnJnYiggMC4wNzE5NDUzICogeCAtIDAuMjI4OTkxNCAqIHkgKyAxLjQwNTI0MjcgKiB6KSwKICAgICAgICAgIHRoaXMub3BhY2l0eQogICAgICAgICk7CiAgICAgIH0KICAgIH0pKTsKCiAgICBmdW5jdGlvbiB4eXoybGFiKHQpIHsKICAgICAgcmV0dXJuIHQgPiB0MyA/IE1hdGgucG93KHQsIDEgLyAzKSA6IHQgLyB0MiArIHQwOwogICAgfQoKICAgIGZ1bmN0aW9uIGxhYjJ4eXoodCkgewogICAgICByZXR1cm4gdCA+IHQxID8gdCAqIHQgKiB0IDogdDIgKiAodCAtIHQwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBscmdiMnJnYih4KSB7CiAgICAgIHJldHVybiAyNTUgKiAoeCA8PSAwLjAwMzEzMDggPyAxMi45MiAqIHggOiAxLjA1NSAqIE1hdGgucG93KHgsIDEgLyAyLjQpIC0gMC4wNTUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYjJscmdiKHgpIHsKICAgICAgcmV0dXJuICh4IC89IDI1NSkgPD0gMC4wNDA0NSA/IHggLyAxMi45MiA6IE1hdGgucG93KCh4ICsgMC4wNTUpIC8gMS4wNTUsIDIuNCk7CiAgICB9CgogICAgZnVuY3Rpb24gaGNsQ29udmVydChvKSB7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgSGNsKSByZXR1cm4gbmV3IEhjbChvLmgsIG8uYywgby5sLCBvLm9wYWNpdHkpOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgTGFiKSkgbyA9IGxhYkNvbnZlcnQobyk7CiAgICAgIGlmIChvLmEgPT09IDAgJiYgby5iID09PSAwKSByZXR1cm4gbmV3IEhjbChOYU4sIDAgPCBvLmwgJiYgby5sIDwgMTAwID8gMCA6IE5hTiwgby5sLCBvLm9wYWNpdHkpOwogICAgICB2YXIgaCA9IE1hdGguYXRhbjIoby5iLCBvLmEpICogcmFkMmRlZzsKICAgICAgcmV0dXJuIG5ldyBIY2woaCA8IDAgPyBoICsgMzYwIDogaCwgTWF0aC5zcXJ0KG8uYSAqIG8uYSArIG8uYiAqIG8uYiksIG8ubCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBsY2gobCwgYywgaCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGhjbENvbnZlcnQobCkgOiBuZXcgSGNsKGgsIGMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2woaCwgYywgbCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGhjbENvbnZlcnQoaCkgOiBuZXcgSGNsKGgsIGMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBIY2woaCwgYywgbCwgb3BhY2l0eSkgewogICAgICB0aGlzLmggPSAraDsKICAgICAgdGhpcy5jID0gK2M7CiAgICAgIHRoaXMubCA9ICtsOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2wybGFiKG8pIHsKICAgICAgaWYgKGlzTmFOKG8uaCkpIHJldHVybiBuZXcgTGFiKG8ubCwgMCwgMCwgby5vcGFjaXR5KTsKICAgICAgdmFyIGggPSBvLmggKiBkZWcycmFkOwogICAgICByZXR1cm4gbmV3IExhYihvLmwsIE1hdGguY29zKGgpICogby5jLCBNYXRoLnNpbihoKSAqIG8uYywgby5vcGFjaXR5KTsKICAgIH0KCiAgICBkZWZpbmUoSGNsLCBoY2wsIGV4dGVuZChDb2xvciwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIHJldHVybiBuZXcgSGNsKHRoaXMuaCwgdGhpcy5jLCB0aGlzLmwgKyBLICogKGsgPT0gbnVsbCA/IDEgOiBrKSwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBIY2wodGhpcy5oLCB0aGlzLmMsIHRoaXMubCAtIEsgKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBoY2wybGFiKHRoaXMpLnJnYigpOwogICAgICB9CiAgICB9KSk7CgogICAgdmFyIEEgPSAtMC4xNDg2MSwKICAgICAgICBCID0gKzEuNzgyNzcsCiAgICAgICAgQyA9IC0wLjI5MjI3LAogICAgICAgIEQgPSAtMC45MDY0OSwKICAgICAgICBFID0gKzEuOTcyOTQsCiAgICAgICAgRUQgPSBFICogRCwKICAgICAgICBFQiA9IEUgKiBCLAogICAgICAgIEJDX0RBID0gQiAqIEMgLSBEICogQTsKCiAgICBmdW5jdGlvbiBjdWJlaGVsaXhDb252ZXJ0KG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBDdWJlaGVsaXgpIHJldHVybiBuZXcgQ3ViZWhlbGl4KG8uaCwgby5zLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBSZ2IpKSBvID0gcmdiQ29udmVydChvKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIGwgPSAoQkNfREEgKiBiICsgRUQgKiByIC0gRUIgKiBnKSAvIChCQ19EQSArIEVEIC0gRUIpLAogICAgICAgICAgYmwgPSBiIC0gbCwKICAgICAgICAgIGsgPSAoRSAqIChnIC0gbCkgLSBDICogYmwpIC8gRCwKICAgICAgICAgIHMgPSBNYXRoLnNxcnQoayAqIGsgKyBibCAqIGJsKSAvIChFICogbCAqICgxIC0gbCkpLCAvLyBOYU4gaWYgbD0wIG9yIGw9MQogICAgICAgICAgaCA9IHMgPyBNYXRoLmF0YW4yKGssIGJsKSAqIHJhZDJkZWcgLSAxMjAgOiBOYU47CiAgICAgIHJldHVybiBuZXcgQ3ViZWhlbGl4KGggPCAwID8gaCArIDM2MCA6IGgsIHMsIGwsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3ViZWhlbGl4KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBjdWJlaGVsaXhDb252ZXJ0KGgpIDogbmV3IEN1YmVoZWxpeChoLCBzLCBsLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gQ3ViZWhlbGl4KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5oID0gK2g7CiAgICAgIHRoaXMucyA9ICtzOwogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lKEN1YmVoZWxpeCwgY3ViZWhlbGl4LCBleHRlbmQoQ29sb3IsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIgOiBNYXRoLnBvdyhicmlnaHRlciwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBDdWJlaGVsaXgodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIgOiBNYXRoLnBvdyhkYXJrZXIsIGspOwogICAgICAgIHJldHVybiBuZXcgQ3ViZWhlbGl4KHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBoID0gaXNOYU4odGhpcy5oKSA/IDAgOiAodGhpcy5oICsgMTIwKSAqIGRlZzJyYWQsCiAgICAgICAgICAgIGwgPSArdGhpcy5sLAogICAgICAgICAgICBhID0gaXNOYU4odGhpcy5zKSA/IDAgOiB0aGlzLnMgKiBsICogKDEgLSBsKSwKICAgICAgICAgICAgY29zaCA9IE1hdGguY29zKGgpLAogICAgICAgICAgICBzaW5oID0gTWF0aC5zaW4oaCk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IoCiAgICAgICAgICAyNTUgKiAobCArIGEgKiAoQSAqIGNvc2ggKyBCICogc2luaCkpLAogICAgICAgICAgMjU1ICogKGwgKyBhICogKEMgKiBjb3NoICsgRCAqIHNpbmgpKSwKICAgICAgICAgIDI1NSAqIChsICsgYSAqIChFICogY29zaCkpLAogICAgICAgICAgdGhpcy5vcGFjaXR5CiAgICAgICAgKTsKICAgICAgfQogICAgfSkpOwoKICAgIGZ1bmN0aW9uIGJhc2lzKHQxLCB2MCwgdjEsIHYyLCB2MykgewogICAgICB2YXIgdDIgPSB0MSAqIHQxLCB0MyA9IHQyICogdDE7CiAgICAgIHJldHVybiAoKDEgLSAzICogdDEgKyAzICogdDIgLSB0MykgKiB2MAogICAgICAgICAgKyAoNCAtIDYgKiB0MiArIDMgKiB0MykgKiB2MQogICAgICAgICAgKyAoMSArIDMgKiB0MSArIDMgKiB0MiAtIDMgKiB0MykgKiB2MgogICAgICAgICAgKyB0MyAqIHYzKSAvIDY7CiAgICB9CgogICAgZnVuY3Rpb24gYmFzaXMkMSh2YWx1ZXMpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoIC0gMTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgaSA9IHQgPD0gMCA/ICh0ID0gMCkgOiB0ID49IDEgPyAodCA9IDEsIG4gLSAxKSA6IE1hdGguZmxvb3IodCAqIG4pLAogICAgICAgICAgICB2MSA9IHZhbHVlc1tpXSwKICAgICAgICAgICAgdjIgPSB2YWx1ZXNbaSArIDFdLAogICAgICAgICAgICB2MCA9IGkgPiAwID8gdmFsdWVzW2kgLSAxXSA6IDIgKiB2MSAtIHYyLAogICAgICAgICAgICB2MyA9IGkgPCBuIC0gMSA/IHZhbHVlc1tpICsgMl0gOiAyICogdjIgLSB2MTsKICAgICAgICByZXR1cm4gYmFzaXMoKHQgLSBpIC8gbikgKiBuLCB2MCwgdjEsIHYyLCB2Myk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYmFzaXNDbG9zZWQodmFsdWVzKSB7CiAgICAgIHZhciBuID0gdmFsdWVzLmxlbmd0aDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgaSA9IE1hdGguZmxvb3IoKCh0ICU9IDEpIDwgMCA/ICsrdCA6IHQpICogbiksCiAgICAgICAgICAgIHYwID0gdmFsdWVzWyhpICsgbiAtIDEpICUgbl0sCiAgICAgICAgICAgIHYxID0gdmFsdWVzW2kgJSBuXSwKICAgICAgICAgICAgdjIgPSB2YWx1ZXNbKGkgKyAxKSAlIG5dLAogICAgICAgICAgICB2MyA9IHZhbHVlc1soaSArIDIpICUgbl07CiAgICAgICAgcmV0dXJuIGJhc2lzKCh0IC0gaSAvIG4pICogbiwgdjAsIHYxLCB2MiwgdjMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JDMoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbGluZWFyKGEsIGQpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICByZXR1cm4gYSArIHQgKiBkOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4cG9uZW50aWFsKGEsIGIsIHkpIHsKICAgICAgcmV0dXJuIGEgPSBNYXRoLnBvdyhhLCB5KSwgYiA9IE1hdGgucG93KGIsIHkpIC0gYSwgeSA9IDEgLyB5LCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIE1hdGgucG93KGEgKyB0ICogYiwgeSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaHVlKGEsIGIpIHsKICAgICAgdmFyIGQgPSBiIC0gYTsKICAgICAgcmV0dXJuIGQgPyBsaW5lYXIoYSwgZCA+IDE4MCB8fCBkIDwgLTE4MCA/IGQgLSAzNjAgKiBNYXRoLnJvdW5kKGQgLyAzNjApIDogZCkgOiBjb25zdGFudCQzKGlzTmFOKGEpID8gYiA6IGEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGdhbW1hKHkpIHsKICAgICAgcmV0dXJuICh5ID0gK3kpID09PSAxID8gbm9nYW1tYSA6IGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICByZXR1cm4gYiAtIGEgPyBleHBvbmVudGlhbChhLCBiLCB5KSA6IGNvbnN0YW50JDMoaXNOYU4oYSkgPyBiIDogYSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbm9nYW1tYShhLCBiKSB7CiAgICAgIHZhciBkID0gYiAtIGE7CiAgICAgIHJldHVybiBkID8gbGluZWFyKGEsIGQpIDogY29uc3RhbnQkMyhpc05hTihhKSA/IGIgOiBhKTsKICAgIH0KCiAgICB2YXIgaW50ZXJwb2xhdGVSZ2IgPSAoZnVuY3Rpb24gcmdiR2FtbWEoeSkgewogICAgICB2YXIgY29sb3IgPSBnYW1tYSh5KTsKCiAgICAgIGZ1bmN0aW9uIHJnYiQxKHN0YXJ0LCBlbmQpIHsKICAgICAgICB2YXIgciA9IGNvbG9yKChzdGFydCA9IHJnYihzdGFydCkpLnIsIChlbmQgPSByZ2IoZW5kKSkuciksCiAgICAgICAgICAgIGcgPSBjb2xvcihzdGFydC5nLCBlbmQuZyksCiAgICAgICAgICAgIGIgPSBjb2xvcihzdGFydC5iLCBlbmQuYiksCiAgICAgICAgICAgIG9wYWNpdHkgPSBub2dhbW1hKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgc3RhcnQuciA9IHIodCk7CiAgICAgICAgICBzdGFydC5nID0gZyh0KTsKICAgICAgICAgIHN0YXJ0LmIgPSBiKHQpOwogICAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICB9OwogICAgICB9CgogICAgICByZ2IkMS5nYW1tYSA9IHJnYkdhbW1hOwoKICAgICAgcmV0dXJuIHJnYiQxOwogICAgfSkoMSk7CgogICAgZnVuY3Rpb24gcmdiU3BsaW5lKHNwbGluZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oY29sb3JzKSB7CiAgICAgICAgdmFyIG4gPSBjb2xvcnMubGVuZ3RoLAogICAgICAgICAgICByID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBnID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBiID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBpLCBjb2xvcjsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBjb2xvciA9IHJnYihjb2xvcnNbaV0pOwogICAgICAgICAgcltpXSA9IGNvbG9yLnIgfHwgMDsKICAgICAgICAgIGdbaV0gPSBjb2xvci5nIHx8IDA7CiAgICAgICAgICBiW2ldID0gY29sb3IuYiB8fCAwOwogICAgICAgIH0KICAgICAgICByID0gc3BsaW5lKHIpOwogICAgICAgIGcgPSBzcGxpbmUoZyk7CiAgICAgICAgYiA9IHNwbGluZShiKTsKICAgICAgICBjb2xvci5vcGFjaXR5ID0gMTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgY29sb3IuciA9IHIodCk7CiAgICAgICAgICBjb2xvci5nID0gZyh0KTsKICAgICAgICAgIGNvbG9yLmIgPSBiKHQpOwogICAgICAgICAgcmV0dXJuIGNvbG9yICsgIiI7CiAgICAgICAgfTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcmdiQmFzaXMgPSByZ2JTcGxpbmUoYmFzaXMkMSk7CiAgICB2YXIgcmdiQmFzaXNDbG9zZWQgPSByZ2JTcGxpbmUoYmFzaXNDbG9zZWQpOwoKICAgIGZ1bmN0aW9uIG51bWJlckFycmF5KGEsIGIpIHsKICAgICAgaWYgKCFiKSBiID0gW107CiAgICAgIHZhciBuID0gYSA/IE1hdGgubWluKGIubGVuZ3RoLCBhLmxlbmd0aCkgOiAwLAogICAgICAgICAgYyA9IGIuc2xpY2UoKSwKICAgICAgICAgIGk7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgY1tpXSA9IGFbaV0gKiAoMSAtIHQpICsgYltpXSAqIHQ7CiAgICAgICAgcmV0dXJuIGM7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaXNOdW1iZXJBcnJheSh4KSB7CiAgICAgIHJldHVybiBBcnJheUJ1ZmZlci5pc1ZpZXcoeCkgJiYgISh4IGluc3RhbmNlb2YgRGF0YVZpZXcpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFycmF5JDEoYSwgYikgewogICAgICByZXR1cm4gKGlzTnVtYmVyQXJyYXkoYikgPyBudW1iZXJBcnJheSA6IGdlbmVyaWNBcnJheSkoYSwgYik7CiAgICB9CgogICAgZnVuY3Rpb24gZ2VuZXJpY0FycmF5KGEsIGIpIHsKICAgICAgdmFyIG5iID0gYiA/IGIubGVuZ3RoIDogMCwKICAgICAgICAgIG5hID0gYSA/IE1hdGgubWluKG5iLCBhLmxlbmd0aCkgOiAwLAogICAgICAgICAgeCA9IG5ldyBBcnJheShuYSksCiAgICAgICAgICBjID0gbmV3IEFycmF5KG5iKSwKICAgICAgICAgIGk7CgogICAgICBmb3IgKGkgPSAwOyBpIDwgbmE7ICsraSkgeFtpXSA9IGludGVycG9sYXRlVmFsdWUoYVtpXSwgYltpXSk7CiAgICAgIGZvciAoOyBpIDwgbmI7ICsraSkgY1tpXSA9IGJbaV07CgogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuYTsgKytpKSBjW2ldID0geFtpXSh0KTsKICAgICAgICByZXR1cm4gYzsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkYXRlKGEsIGIpIHsKICAgICAgdmFyIGQgPSBuZXcgRGF0ZTsKICAgICAgcmV0dXJuIGEgPSArYSwgYiA9ICtiLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGQuc2V0VGltZShhICogKDEgLSB0KSArIGIgKiB0KSwgZDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZU51bWJlcihhLCBiKSB7CiAgICAgIHJldHVybiBhID0gK2EsIGIgPSArYiwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICogKDEgLSB0KSArIGIgKiB0OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9iamVjdChhLCBiKSB7CiAgICAgIHZhciBpID0ge30sCiAgICAgICAgICBjID0ge30sCiAgICAgICAgICBrOwoKICAgICAgaWYgKGEgPT09IG51bGwgfHwgdHlwZW9mIGEgIT09ICJvYmplY3QiKSBhID0ge307CiAgICAgIGlmIChiID09PSBudWxsIHx8IHR5cGVvZiBiICE9PSAib2JqZWN0IikgYiA9IHt9OwoKICAgICAgZm9yIChrIGluIGIpIHsKICAgICAgICBpZiAoayBpbiBhKSB7CiAgICAgICAgICBpW2tdID0gaW50ZXJwb2xhdGVWYWx1ZShhW2tdLCBiW2tdKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY1trXSA9IGJba107CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIGZvciAoayBpbiBpKSBjW2tdID0gaVtrXSh0KTsKICAgICAgICByZXR1cm4gYzsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcmVBID0gL1stK10/KD86XGQrXC4/XGQqfFwuP1xkKykoPzpbZUVdWy0rXT9cZCspPy9nLAogICAgICAgIHJlQiA9IG5ldyBSZWdFeHAocmVBLnNvdXJjZSwgImciKTsKCiAgICBmdW5jdGlvbiB6ZXJvKGIpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBiOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9uZShiKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGIodCkgKyAiIjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZVN0cmluZyhhLCBiKSB7CiAgICAgIHZhciBiaSA9IHJlQS5sYXN0SW5kZXggPSByZUIubGFzdEluZGV4ID0gMCwgLy8gc2NhbiBpbmRleCBmb3IgbmV4dCBudW1iZXIgaW4gYgogICAgICAgICAgYW0sIC8vIGN1cnJlbnQgbWF0Y2ggaW4gYQogICAgICAgICAgYm0sIC8vIGN1cnJlbnQgbWF0Y2ggaW4gYgogICAgICAgICAgYnMsIC8vIHN0cmluZyBwcmVjZWRpbmcgY3VycmVudCBudW1iZXIgaW4gYiwgaWYgYW55CiAgICAgICAgICBpID0gLTEsIC8vIGluZGV4IGluIHMKICAgICAgICAgIHMgPSBbXSwgLy8gc3RyaW5nIGNvbnN0YW50cyBhbmQgcGxhY2Vob2xkZXJzCiAgICAgICAgICBxID0gW107IC8vIG51bWJlciBpbnRlcnBvbGF0b3JzCgogICAgICAvLyBDb2VyY2UgaW5wdXRzIHRvIHN0cmluZ3MuCiAgICAgIGEgPSBhICsgIiIsIGIgPSBiICsgIiI7CgogICAgICAvLyBJbnRlcnBvbGF0ZSBwYWlycyBvZiBudW1iZXJzIGluIGEgJiBiLgogICAgICB3aGlsZSAoKGFtID0gcmVBLmV4ZWMoYSkpCiAgICAgICAgICAmJiAoYm0gPSByZUIuZXhlYyhiKSkpIHsKICAgICAgICBpZiAoKGJzID0gYm0uaW5kZXgpID4gYmkpIHsgLy8gYSBzdHJpbmcgcHJlY2VkZXMgdGhlIG5leHQgbnVtYmVyIGluIGIKICAgICAgICAgIGJzID0gYi5zbGljZShiaSwgYnMpOwogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICAgIH0KICAgICAgICBpZiAoKGFtID0gYW1bMF0pID09PSAoYm0gPSBibVswXSkpIHsgLy8gbnVtYmVycyBpbiBhICYgYiBtYXRjaAogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYm07IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJtOwogICAgICAgIH0gZWxzZSB7IC8vIGludGVycG9sYXRlIG5vbi1tYXRjaGluZyBudW1iZXJzCiAgICAgICAgICBzWysraV0gPSBudWxsOwogICAgICAgICAgcS5wdXNoKHtpOiBpLCB4OiBpbnRlcnBvbGF0ZU51bWJlcihhbSwgYm0pfSk7CiAgICAgICAgfQogICAgICAgIGJpID0gcmVCLmxhc3RJbmRleDsKICAgICAgfQoKICAgICAgLy8gQWRkIHJlbWFpbnMgb2YgYi4KICAgICAgaWYgKGJpIDwgYi5sZW5ndGgpIHsKICAgICAgICBicyA9IGIuc2xpY2UoYmkpOwogICAgICAgIGlmIChzW2ldKSBzW2ldICs9IGJzOyAvLyBjb2FsZXNjZSB3aXRoIHByZXZpb3VzIHN0cmluZwogICAgICAgIGVsc2Ugc1srK2ldID0gYnM7CiAgICAgIH0KCiAgICAgIC8vIFNwZWNpYWwgb3B0aW1pemF0aW9uIGZvciBvbmx5IGEgc2luZ2xlIG1hdGNoLgogICAgICAvLyBPdGhlcndpc2UsIGludGVycG9sYXRlIGVhY2ggb2YgdGhlIG51bWJlcnMgYW5kIHJlam9pbiB0aGUgc3RyaW5nLgogICAgICByZXR1cm4gcy5sZW5ndGggPCAyID8gKHFbMF0KICAgICAgICAgID8gb25lKHFbMF0ueCkKICAgICAgICAgIDogemVybyhiKSkKICAgICAgICAgIDogKGIgPSBxLmxlbmd0aCwgZnVuY3Rpb24odCkgewogICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBvOyBpIDwgYjsgKytpKSBzWyhvID0gcVtpXSkuaV0gPSBvLngodCk7CiAgICAgICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlVmFsdWUoYSwgYikgewogICAgICB2YXIgdCA9IHR5cGVvZiBiLCBjOwogICAgICByZXR1cm4gYiA9PSBudWxsIHx8IHQgPT09ICJib29sZWFuIiA/IGNvbnN0YW50JDMoYikKICAgICAgICAgIDogKHQgPT09ICJudW1iZXIiID8gaW50ZXJwb2xhdGVOdW1iZXIKICAgICAgICAgIDogdCA9PT0gInN0cmluZyIgPyAoKGMgPSBjb2xvcihiKSkgPyAoYiA9IGMsIGludGVycG9sYXRlUmdiKSA6IGludGVycG9sYXRlU3RyaW5nKQogICAgICAgICAgOiBiIGluc3RhbmNlb2YgY29sb3IgPyBpbnRlcnBvbGF0ZVJnYgogICAgICAgICAgOiBiIGluc3RhbmNlb2YgRGF0ZSA/IGRhdGUKICAgICAgICAgIDogaXNOdW1iZXJBcnJheShiKSA/IG51bWJlckFycmF5CiAgICAgICAgICA6IEFycmF5LmlzQXJyYXkoYikgPyBnZW5lcmljQXJyYXkKICAgICAgICAgIDogdHlwZW9mIGIudmFsdWVPZiAhPT0gImZ1bmN0aW9uIiAmJiB0eXBlb2YgYi50b1N0cmluZyAhPT0gImZ1bmN0aW9uIiB8fCBpc05hTihiKSA/IG9iamVjdAogICAgICAgICAgOiBpbnRlcnBvbGF0ZU51bWJlcikoYSwgYik7CiAgICB9CgogICAgZnVuY3Rpb24gZGlzY3JldGUocmFuZ2UpIHsKICAgICAgdmFyIG4gPSByYW5nZS5sZW5ndGg7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIHJhbmdlW01hdGgubWF4KDAsIE1hdGgubWluKG4gLSAxLCBNYXRoLmZsb29yKHQgKiBuKSkpXTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBodWUkMShhLCBiKSB7CiAgICAgIHZhciBpID0gaHVlKCthLCArYik7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIHggPSBpKHQpOwogICAgICAgIHJldHVybiB4IC0gMzYwICogTWF0aC5mbG9vcih4IC8gMzYwKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZVJvdW5kKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPSArYSwgYiA9ICtiLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIE1hdGgucm91bmQoYSAqICgxIC0gdCkgKyBiICogdCk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGRlZ3JlZXMgPSAxODAgLyBNYXRoLlBJOwoKICAgIHZhciBpZGVudGl0eSQyID0gewogICAgICB0cmFuc2xhdGVYOiAwLAogICAgICB0cmFuc2xhdGVZOiAwLAogICAgICByb3RhdGU6IDAsCiAgICAgIHNrZXdYOiAwLAogICAgICBzY2FsZVg6IDEsCiAgICAgIHNjYWxlWTogMQogICAgfTsKCiAgICBmdW5jdGlvbiBkZWNvbXBvc2UoYSwgYiwgYywgZCwgZSwgZikgewogICAgICB2YXIgc2NhbGVYLCBzY2FsZVksIHNrZXdYOwogICAgICBpZiAoc2NhbGVYID0gTWF0aC5zcXJ0KGEgKiBhICsgYiAqIGIpKSBhIC89IHNjYWxlWCwgYiAvPSBzY2FsZVg7CiAgICAgIGlmIChza2V3WCA9IGEgKiBjICsgYiAqIGQpIGMgLT0gYSAqIHNrZXdYLCBkIC09IGIgKiBza2V3WDsKICAgICAgaWYgKHNjYWxlWSA9IE1hdGguc3FydChjICogYyArIGQgKiBkKSkgYyAvPSBzY2FsZVksIGQgLz0gc2NhbGVZLCBza2V3WCAvPSBzY2FsZVk7CiAgICAgIGlmIChhICogZCA8IGIgKiBjKSBhID0gLWEsIGIgPSAtYiwgc2tld1ggPSAtc2tld1gsIHNjYWxlWCA9IC1zY2FsZVg7CiAgICAgIHJldHVybiB7CiAgICAgICAgdHJhbnNsYXRlWDogZSwKICAgICAgICB0cmFuc2xhdGVZOiBmLAogICAgICAgIHJvdGF0ZTogTWF0aC5hdGFuMihiLCBhKSAqIGRlZ3JlZXMsCiAgICAgICAgc2tld1g6IE1hdGguYXRhbihza2V3WCkgKiBkZWdyZWVzLAogICAgICAgIHNjYWxlWDogc2NhbGVYLAogICAgICAgIHNjYWxlWTogc2NhbGVZCiAgICAgIH07CiAgICB9CgogICAgdmFyIGNzc05vZGUsCiAgICAgICAgY3NzUm9vdCwKICAgICAgICBjc3NWaWV3LAogICAgICAgIHN2Z05vZGU7CgogICAgZnVuY3Rpb24gcGFyc2VDc3MkMSh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgPT09ICJub25lIikgcmV0dXJuIGlkZW50aXR5JDI7CiAgICAgIGlmICghY3NzTm9kZSkgY3NzTm9kZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoIkRJViIpLCBjc3NSb290ID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LCBjc3NWaWV3ID0gZG9jdW1lbnQuZGVmYXVsdFZpZXc7CiAgICAgIGNzc05vZGUuc3R5bGUudHJhbnNmb3JtID0gdmFsdWU7CiAgICAgIHZhbHVlID0gY3NzVmlldy5nZXRDb21wdXRlZFN0eWxlKGNzc1Jvb3QuYXBwZW5kQ2hpbGQoY3NzTm9kZSksIG51bGwpLmdldFByb3BlcnR5VmFsdWUoInRyYW5zZm9ybSIpOwogICAgICBjc3NSb290LnJlbW92ZUNoaWxkKGNzc05vZGUpOwogICAgICB2YWx1ZSA9IHZhbHVlLnNsaWNlKDcsIC0xKS5zcGxpdCgiLCIpOwogICAgICByZXR1cm4gZGVjb21wb3NlKCt2YWx1ZVswXSwgK3ZhbHVlWzFdLCArdmFsdWVbMl0sICt2YWx1ZVszXSwgK3ZhbHVlWzRdLCArdmFsdWVbNV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlU3ZnKHZhbHVlKSB7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gaWRlbnRpdHkkMjsKICAgICAgaWYgKCFzdmdOb2RlKSBzdmdOb2RlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIsICJnIik7CiAgICAgIHN2Z05vZGUuc2V0QXR0cmlidXRlKCJ0cmFuc2Zvcm0iLCB2YWx1ZSk7CiAgICAgIGlmICghKHZhbHVlID0gc3ZnTm9kZS50cmFuc2Zvcm0uYmFzZVZhbC5jb25zb2xpZGF0ZSgpKSkgcmV0dXJuIGlkZW50aXR5JDI7CiAgICAgIHZhbHVlID0gdmFsdWUubWF0cml4OwogICAgICByZXR1cm4gZGVjb21wb3NlKHZhbHVlLmEsIHZhbHVlLmIsIHZhbHVlLmMsIHZhbHVlLmQsIHZhbHVlLmUsIHZhbHVlLmYpOwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlVHJhbnNmb3JtKHBhcnNlLCBweENvbW1hLCBweFBhcmVuLCBkZWdQYXJlbikgewoKICAgICAgZnVuY3Rpb24gcG9wKHMpIHsKICAgICAgICByZXR1cm4gcy5sZW5ndGggPyBzLnBvcCgpICsgIiAiIDogIiI7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRyYW5zbGF0ZSh4YSwgeWEsIHhiLCB5YiwgcywgcSkgewogICAgICAgIGlmICh4YSAhPT0geGIgfHwgeWEgIT09IHliKSB7CiAgICAgICAgICB2YXIgaSA9IHMucHVzaCgidHJhbnNsYXRlKCIsIG51bGwsIHB4Q29tbWEsIG51bGwsIHB4UGFyZW4pOwogICAgICAgICAgcS5wdXNoKHtpOiBpIC0gNCwgeDogaW50ZXJwb2xhdGVOdW1iZXIoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIoeWEsIHliKX0pOwogICAgICAgIH0gZWxzZSBpZiAoeGIgfHwgeWIpIHsKICAgICAgICAgIHMucHVzaCgidHJhbnNsYXRlKCIgKyB4YiArIHB4Q29tbWEgKyB5YiArIHB4UGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gcm90YXRlKGEsIGIsIHMsIHEpIHsKICAgICAgICBpZiAoYSAhPT0gYikgewogICAgICAgICAgaWYgKGEgLSBiID4gMTgwKSBiICs9IDM2MDsgZWxzZSBpZiAoYiAtIGEgPiAxODApIGEgKz0gMzYwOyAvLyBzaG9ydGVzdCBwYXRoCiAgICAgICAgICBxLnB1c2goe2k6IHMucHVzaChwb3AocykgKyAicm90YXRlKCIsIG51bGwsIGRlZ1BhcmVuKSAtIDIsIHg6IGludGVycG9sYXRlTnVtYmVyKGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInJvdGF0ZSgiICsgYiArIGRlZ1BhcmVuKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNrZXdYKGEsIGIsIHMsIHEpIHsKICAgICAgICBpZiAoYSAhPT0gYikgewogICAgICAgICAgcS5wdXNoKHtpOiBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIsIG51bGwsIGRlZ1BhcmVuKSAtIDIsIHg6IGludGVycG9sYXRlTnVtYmVyKGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIgKyBiICsgZGVnUGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIsIG51bGwsICIsIiwgbnVsbCwgIikiKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IGludGVycG9sYXRlTnVtYmVyKHhhLCB4Yil9LCB7aTogaSAtIDIsIHg6IGludGVycG9sYXRlTnVtYmVyKHlhLCB5Yil9KTsKICAgICAgICB9IGVsc2UgaWYgKHhiICE9PSAxIHx8IHliICE9PSAxKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIgKyB4YiArICIsIiArIHliICsgIikiKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgdmFyIHMgPSBbXSwgLy8gc3RyaW5nIGNvbnN0YW50cyBhbmQgcGxhY2Vob2xkZXJzCiAgICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKICAgICAgICBhID0gcGFyc2UoYSksIGIgPSBwYXJzZShiKTsKICAgICAgICB0cmFuc2xhdGUoYS50cmFuc2xhdGVYLCBhLnRyYW5zbGF0ZVksIGIudHJhbnNsYXRlWCwgYi50cmFuc2xhdGVZLCBzLCBxKTsKICAgICAgICByb3RhdGUoYS5yb3RhdGUsIGIucm90YXRlLCBzLCBxKTsKICAgICAgICBza2V3WChhLnNrZXdYLCBiLnNrZXdYLCBzLCBxKTsKICAgICAgICBzY2FsZShhLnNjYWxlWCwgYS5zY2FsZVksIGIuc2NhbGVYLCBiLnNjYWxlWSwgcywgcSk7CiAgICAgICAgYSA9IGIgPSBudWxsOyAvLyBnYwogICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICB2YXIgaSA9IC0xLCBuID0gcS5sZW5ndGgsIG87CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgc1sobyA9IHFbaV0pLmldID0gby54KHQpOwogICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgaW50ZXJwb2xhdGVUcmFuc2Zvcm1Dc3MgPSBpbnRlcnBvbGF0ZVRyYW5zZm9ybShwYXJzZUNzcyQxLCAicHgsICIsICJweCkiLCAiZGVnKSIpOwogICAgdmFyIGludGVycG9sYXRlVHJhbnNmb3JtU3ZnID0gaW50ZXJwb2xhdGVUcmFuc2Zvcm0ocGFyc2VTdmcsICIsICIsICIpIiwgIikiKTsKCiAgICB2YXIgcmhvID0gTWF0aC5TUVJUMiwKICAgICAgICByaG8yID0gMiwKICAgICAgICByaG80ID0gNCwKICAgICAgICBlcHNpbG9uMiA9IDFlLTEyOwoKICAgIGZ1bmN0aW9uIGNvc2goeCkgewogICAgICByZXR1cm4gKCh4ID0gTWF0aC5leHAoeCkpICsgMSAvIHgpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBzaW5oKHgpIHsKICAgICAgcmV0dXJuICgoeCA9IE1hdGguZXhwKHgpKSAtIDEgLyB4KSAvIDI7CiAgICB9CgogICAgZnVuY3Rpb24gdGFuaCh4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCgyICogeCkpIC0gMSkgLyAoeCArIDEpOwogICAgfQoKICAgIC8vIHAwID0gW3V4MCwgdXkwLCB3MF0KICAgIC8vIHAxID0gW3V4MSwgdXkxLCB3MV0KICAgIGZ1bmN0aW9uIGludGVycG9sYXRlWm9vbShwMCwgcDEpIHsKICAgICAgdmFyIHV4MCA9IHAwWzBdLCB1eTAgPSBwMFsxXSwgdzAgPSBwMFsyXSwKICAgICAgICAgIHV4MSA9IHAxWzBdLCB1eTEgPSBwMVsxXSwgdzEgPSBwMVsyXSwKICAgICAgICAgIGR4ID0gdXgxIC0gdXgwLAogICAgICAgICAgZHkgPSB1eTEgLSB1eTAsCiAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5LAogICAgICAgICAgaSwKICAgICAgICAgIFM7CgogICAgICAvLyBTcGVjaWFsIGNhc2UgZm9yIHUwIOKJhSB1MS4KICAgICAgaWYgKGQyIDwgZXBzaWxvbjIpIHsKICAgICAgICBTID0gTWF0aC5sb2codzEgLyB3MCkgLyByaG87CiAgICAgICAgaSA9IGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgIHV4MCArIHQgKiBkeCwKICAgICAgICAgICAgdXkwICsgdCAqIGR5LAogICAgICAgICAgICB3MCAqIE1hdGguZXhwKHJobyAqIHQgKiBTKQogICAgICAgICAgXTsKICAgICAgICB9OwogICAgICB9CgogICAgICAvLyBHZW5lcmFsIGNhc2UuCiAgICAgIGVsc2UgewogICAgICAgIHZhciBkMSA9IE1hdGguc3FydChkMiksCiAgICAgICAgICAgIGIwID0gKHcxICogdzEgLSB3MCAqIHcwICsgcmhvNCAqIGQyKSAvICgyICogdzAgKiByaG8yICogZDEpLAogICAgICAgICAgICBiMSA9ICh3MSAqIHcxIC0gdzAgKiB3MCAtIHJobzQgKiBkMikgLyAoMiAqIHcxICogcmhvMiAqIGQxKSwKICAgICAgICAgICAgcjAgPSBNYXRoLmxvZyhNYXRoLnNxcnQoYjAgKiBiMCArIDEpIC0gYjApLAogICAgICAgICAgICByMSA9IE1hdGgubG9nKE1hdGguc3FydChiMSAqIGIxICsgMSkgLSBiMSk7CiAgICAgICAgUyA9IChyMSAtIHIwKSAvIHJobzsKICAgICAgICBpID0gZnVuY3Rpb24odCkgewogICAgICAgICAgdmFyIHMgPSB0ICogUywKICAgICAgICAgICAgICBjb3NocjAgPSBjb3NoKHIwKSwKICAgICAgICAgICAgICB1ID0gdzAgLyAocmhvMiAqIGQxKSAqIChjb3NocjAgKiB0YW5oKHJobyAqIHMgKyByMCkgLSBzaW5oKHIwKSk7CiAgICAgICAgICByZXR1cm4gWwogICAgICAgICAgICB1eDAgKyB1ICogZHgsCiAgICAgICAgICAgIHV5MCArIHUgKiBkeSwKICAgICAgICAgICAgdzAgKiBjb3NocjAgLyBjb3NoKHJobyAqIHMgKyByMCkKICAgICAgICAgIF07CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgaS5kdXJhdGlvbiA9IFMgKiAxMDAwOwoKICAgICAgcmV0dXJuIGk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsJDEoaHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgdmFyIGggPSBodWUoKHN0YXJ0ID0gaHNsKHN0YXJ0KSkuaCwgKGVuZCA9IGhzbChlbmQpKS5oKSwKICAgICAgICAgICAgcyA9IG5vZ2FtbWEoc3RhcnQucywgZW5kLnMpLAogICAgICAgICAgICBsID0gbm9nYW1tYShzdGFydC5sLCBlbmQubCksCiAgICAgICAgICAgIG9wYWNpdHkgPSBub2dhbW1hKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgc3RhcnQuaCA9IGgodCk7CiAgICAgICAgICBzdGFydC5zID0gcyh0KTsKICAgICAgICAgIHN0YXJ0LmwgPSBsKHQpOwogICAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICB9OwogICAgICB9CiAgICB9CgogICAgdmFyIGhzbCQyID0gaHNsJDEoaHVlKTsKICAgIHZhciBoc2xMb25nID0gaHNsJDEobm9nYW1tYSk7CgogICAgZnVuY3Rpb24gbGFiJDEoc3RhcnQsIGVuZCkgewogICAgICB2YXIgbCA9IG5vZ2FtbWEoKHN0YXJ0ID0gbGFiKHN0YXJ0KSkubCwgKGVuZCA9IGxhYihlbmQpKS5sKSwKICAgICAgICAgIGEgPSBub2dhbW1hKHN0YXJ0LmEsIGVuZC5hKSwKICAgICAgICAgIGIgPSBub2dhbW1hKHN0YXJ0LmIsIGVuZC5iKSwKICAgICAgICAgIG9wYWNpdHkgPSBub2dhbW1hKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICBzdGFydC5sID0gbCh0KTsKICAgICAgICBzdGFydC5hID0gYSh0KTsKICAgICAgICBzdGFydC5iID0gYih0KTsKICAgICAgICBzdGFydC5vcGFjaXR5ID0gb3BhY2l0eSh0KTsKICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2wkMShodWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICB2YXIgaCA9IGh1ZSgoc3RhcnQgPSBoY2woc3RhcnQpKS5oLCAoZW5kID0gaGNsKGVuZCkpLmgpLAogICAgICAgICAgICBjID0gbm9nYW1tYShzdGFydC5jLCBlbmQuYyksCiAgICAgICAgICAgIGwgPSBub2dhbW1hKHN0YXJ0LmwsIGVuZC5sKSwKICAgICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEoc3RhcnQub3BhY2l0eSwgZW5kLm9wYWNpdHkpOwogICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICBzdGFydC5oID0gaCh0KTsKICAgICAgICAgIHN0YXJ0LmMgPSBjKHQpOwogICAgICAgICAgc3RhcnQubCA9IGwodCk7CiAgICAgICAgICBzdGFydC5vcGFjaXR5ID0gb3BhY2l0eSh0KTsKICAgICAgICAgIHJldHVybiBzdGFydCArICIiOwogICAgICAgIH07CiAgICAgIH0KICAgIH0KCiAgICB2YXIgaGNsJDIgPSBoY2wkMShodWUpOwogICAgdmFyIGhjbExvbmcgPSBoY2wkMShub2dhbW1hKTsKCiAgICBmdW5jdGlvbiBjdWJlaGVsaXgkMShodWUpIHsKICAgICAgcmV0dXJuIChmdW5jdGlvbiBjdWJlaGVsaXhHYW1tYSh5KSB7CiAgICAgICAgeSA9ICt5OwoKICAgICAgICBmdW5jdGlvbiBjdWJlaGVsaXgkMShzdGFydCwgZW5kKSB7CiAgICAgICAgICB2YXIgaCA9IGh1ZSgoc3RhcnQgPSBjdWJlaGVsaXgoc3RhcnQpKS5oLCAoZW5kID0gY3ViZWhlbGl4KGVuZCkpLmgpLAogICAgICAgICAgICAgIHMgPSBub2dhbW1hKHN0YXJ0LnMsIGVuZC5zKSwKICAgICAgICAgICAgICBsID0gbm9nYW1tYShzdGFydC5sLCBlbmQubCksCiAgICAgICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEoc3RhcnQub3BhY2l0eSwgZW5kLm9wYWNpdHkpOwogICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgICAgc3RhcnQuaCA9IGgodCk7CiAgICAgICAgICAgIHN0YXJ0LnMgPSBzKHQpOwogICAgICAgICAgICBzdGFydC5sID0gbChNYXRoLnBvdyh0LCB5KSk7CiAgICAgICAgICAgIHN0YXJ0Lm9wYWNpdHkgPSBvcGFjaXR5KHQpOwogICAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICBjdWJlaGVsaXgkMS5nYW1tYSA9IGN1YmVoZWxpeEdhbW1hOwoKICAgICAgICByZXR1cm4gY3ViZWhlbGl4JDE7CiAgICAgIH0pKDEpOwogICAgfQoKICAgIHZhciBjdWJlaGVsaXgkMiA9IGN1YmVoZWxpeCQxKGh1ZSk7CiAgICB2YXIgY3ViZWhlbGl4TG9uZyA9IGN1YmVoZWxpeCQxKG5vZ2FtbWEpOwoKICAgIGZ1bmN0aW9uIHBpZWNld2lzZShpbnRlcnBvbGF0ZSwgdmFsdWVzKSB7CiAgICAgIHZhciBpID0gMCwgbiA9IHZhbHVlcy5sZW5ndGggLSAxLCB2ID0gdmFsdWVzWzBdLCBJID0gbmV3IEFycmF5KG4gPCAwID8gMCA6IG4pOwogICAgICB3aGlsZSAoaSA8IG4pIElbaV0gPSBpbnRlcnBvbGF0ZSh2LCB2ID0gdmFsdWVzWysraV0pOwogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHZhciBpID0gTWF0aC5tYXgoMCwgTWF0aC5taW4obiAtIDEsIE1hdGguZmxvb3IodCAqPSBuKSkpOwogICAgICAgIHJldHVybiBJW2ldKHQgLSBpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBxdWFudGl6ZShpbnRlcnBvbGF0b3IsIG4pIHsKICAgICAgdmFyIHNhbXBsZXMgPSBuZXcgQXJyYXkobik7CiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbjsgKytpKSBzYW1wbGVzW2ldID0gaW50ZXJwb2xhdG9yKGkgLyAobiAtIDEpKTsKICAgICAgcmV0dXJuIHNhbXBsZXM7CiAgICB9CgogICAgdmFyIGZyYW1lID0gMCwgLy8gaXMgYW4gYW5pbWF0aW9uIGZyYW1lIHBlbmRpbmc/CiAgICAgICAgdGltZW91dCA9IDAsIC8vIGlzIGEgdGltZW91dCBwZW5kaW5nPwogICAgICAgIGludGVydmFsID0gMCwgLy8gYXJlIGFueSB0aW1lcnMgYWN0aXZlPwogICAgICAgIHBva2VEZWxheSA9IDEwMDAsIC8vIGhvdyBmcmVxdWVudGx5IHdlIGNoZWNrIGZvciBjbG9jayBza2V3CiAgICAgICAgdGFza0hlYWQsCiAgICAgICAgdGFza1RhaWwsCiAgICAgICAgY2xvY2tMYXN0ID0gMCwKICAgICAgICBjbG9ja05vdyA9IDAsCiAgICAgICAgY2xvY2tTa2V3ID0gMCwKICAgICAgICBjbG9jayA9IHR5cGVvZiBwZXJmb3JtYW5jZSA9PT0gIm9iamVjdCIgJiYgcGVyZm9ybWFuY2Uubm93ID8gcGVyZm9ybWFuY2UgOiBEYXRlLAogICAgICAgIHNldEZyYW1lID0gdHlwZW9mIHdpbmRvdyA9PT0gIm9iamVjdCIgJiYgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSA/IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUuYmluZCh3aW5kb3cpIDogZnVuY3Rpb24oZikgeyBzZXRUaW1lb3V0KGYsIDE3KTsgfTsKCiAgICBmdW5jdGlvbiBub3coKSB7CiAgICAgIHJldHVybiBjbG9ja05vdyB8fCAoc2V0RnJhbWUoY2xlYXJOb3cpLCBjbG9ja05vdyA9IGNsb2NrLm5vdygpICsgY2xvY2tTa2V3KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGVhck5vdygpIHsKICAgICAgY2xvY2tOb3cgPSAwOwogICAgfQoKICAgIGZ1bmN0aW9uIFRpbWVyKCkgewogICAgICB0aGlzLl9jYWxsID0KICAgICAgdGhpcy5fdGltZSA9CiAgICAgIHRoaXMuX25leHQgPSBudWxsOwogICAgfQoKICAgIFRpbWVyLnByb3RvdHlwZSA9IHRpbWVyLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRpbWVyLAogICAgICByZXN0YXJ0OiBmdW5jdGlvbihjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgICBpZiAodHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgVHlwZUVycm9yKCJjYWxsYmFjayBpcyBub3QgYSBmdW5jdGlvbiIpOwogICAgICAgIHRpbWUgPSAodGltZSA9PSBudWxsID8gbm93KCkgOiArdGltZSkgKyAoZGVsYXkgPT0gbnVsbCA/IDAgOiArZGVsYXkpOwogICAgICAgIGlmICghdGhpcy5fbmV4dCAmJiB0YXNrVGFpbCAhPT0gdGhpcykgewogICAgICAgICAgaWYgKHRhc2tUYWlsKSB0YXNrVGFpbC5fbmV4dCA9IHRoaXM7CiAgICAgICAgICBlbHNlIHRhc2tIZWFkID0gdGhpczsKICAgICAgICAgIHRhc2tUYWlsID0gdGhpczsKICAgICAgICB9CiAgICAgICAgdGhpcy5fY2FsbCA9IGNhbGxiYWNrOwogICAgICAgIHRoaXMuX3RpbWUgPSB0aW1lOwogICAgICAgIHNsZWVwKCk7CiAgICAgIH0sCiAgICAgIHN0b3A6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9jYWxsKSB7CiAgICAgICAgICB0aGlzLl9jYWxsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX3RpbWUgPSBJbmZpbml0eTsKICAgICAgICAgIHNsZWVwKCk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHRpbWVyKGNhbGxiYWNrLCBkZWxheSwgdGltZSkgewogICAgICB2YXIgdCA9IG5ldyBUaW1lcjsKICAgICAgdC5yZXN0YXJ0KGNhbGxiYWNrLCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVyRmx1c2goKSB7CiAgICAgIG5vdygpOyAvLyBHZXQgdGhlIGN1cnJlbnQgdGltZSwgaWYgbm90IGFscmVhZHkgc2V0LgogICAgICArK2ZyYW1lOyAvLyBQcmV0ZW5kIHdl4oCZdmUgc2V0IGFuIGFsYXJtLCBpZiB3ZSBoYXZlbuKAmXQgYWxyZWFkeS4KICAgICAgdmFyIHQgPSB0YXNrSGVhZCwgZTsKICAgICAgd2hpbGUgKHQpIHsKICAgICAgICBpZiAoKGUgPSBjbG9ja05vdyAtIHQuX3RpbWUpID49IDApIHQuX2NhbGwuY2FsbChudWxsLCBlKTsKICAgICAgICB0ID0gdC5fbmV4dDsKICAgICAgfQogICAgICAtLWZyYW1lOwogICAgfQoKICAgIGZ1bmN0aW9uIHdha2UoKSB7CiAgICAgIGNsb2NrTm93ID0gKGNsb2NrTGFzdCA9IGNsb2NrLm5vdygpKSArIGNsb2NrU2tldzsKICAgICAgZnJhbWUgPSB0aW1lb3V0ID0gMDsKICAgICAgdHJ5IHsKICAgICAgICB0aW1lckZsdXNoKCk7CiAgICAgIH0gZmluYWxseSB7CiAgICAgICAgZnJhbWUgPSAwOwogICAgICAgIG5hcCgpOwogICAgICAgIGNsb2NrTm93ID0gMDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHBva2UoKSB7CiAgICAgIHZhciBub3cgPSBjbG9jay5ub3coKSwgZGVsYXkgPSBub3cgLSBjbG9ja0xhc3Q7CiAgICAgIGlmIChkZWxheSA+IHBva2VEZWxheSkgY2xvY2tTa2V3IC09IGRlbGF5LCBjbG9ja0xhc3QgPSBub3c7CiAgICB9CgogICAgZnVuY3Rpb24gbmFwKCkgewogICAgICB2YXIgdDAsIHQxID0gdGFza0hlYWQsIHQyLCB0aW1lID0gSW5maW5pdHk7CiAgICAgIHdoaWxlICh0MSkgewogICAgICAgIGlmICh0MS5fY2FsbCkgewogICAgICAgICAgaWYgKHRpbWUgPiB0MS5fdGltZSkgdGltZSA9IHQxLl90aW1lOwogICAgICAgICAgdDAgPSB0MSwgdDEgPSB0MS5fbmV4dDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdDIgPSB0MS5fbmV4dCwgdDEuX25leHQgPSBudWxsOwogICAgICAgICAgdDEgPSB0MCA/IHQwLl9uZXh0ID0gdDIgOiB0YXNrSGVhZCA9IHQyOwogICAgICAgIH0KICAgICAgfQogICAgICB0YXNrVGFpbCA9IHQwOwogICAgICBzbGVlcCh0aW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzbGVlcCh0aW1lKSB7CiAgICAgIGlmIChmcmFtZSkgcmV0dXJuOyAvLyBTb29uZXN0IGFsYXJtIGFscmVhZHkgc2V0LCBvciB3aWxsIGJlLgogICAgICBpZiAodGltZW91dCkgdGltZW91dCA9IGNsZWFyVGltZW91dCh0aW1lb3V0KTsKICAgICAgdmFyIGRlbGF5ID0gdGltZSAtIGNsb2NrTm93OyAvLyBTdHJpY3RseSBsZXNzIHRoYW4gaWYgd2UgcmVjb21wdXRlZCBjbG9ja05vdy4KICAgICAgaWYgKGRlbGF5ID4gMjQpIHsKICAgICAgICBpZiAodGltZSA8IEluZmluaXR5KSB0aW1lb3V0ID0gc2V0VGltZW91dCh3YWtlLCB0aW1lIC0gY2xvY2subm93KCkgLSBjbG9ja1NrZXcpOwogICAgICAgIGlmIChpbnRlcnZhbCkgaW50ZXJ2YWwgPSBjbGVhckludGVydmFsKGludGVydmFsKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBpZiAoIWludGVydmFsKSBjbG9ja0xhc3QgPSBjbG9jay5ub3coKSwgaW50ZXJ2YWwgPSBzZXRJbnRlcnZhbChwb2tlLCBwb2tlRGVsYXkpOwogICAgICAgIGZyYW1lID0gMSwgc2V0RnJhbWUod2FrZSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiB0aW1lb3V0JDEoY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgIHZhciB0ID0gbmV3IFRpbWVyOwogICAgICBkZWxheSA9IGRlbGF5ID09IG51bGwgPyAwIDogK2RlbGF5OwogICAgICB0LnJlc3RhcnQoZnVuY3Rpb24oZWxhcHNlZCkgewogICAgICAgIHQuc3RvcCgpOwogICAgICAgIGNhbGxiYWNrKGVsYXBzZWQgKyBkZWxheSk7CiAgICAgIH0sIGRlbGF5LCB0aW1lKTsKICAgICAgcmV0dXJuIHQ7CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJ2YWwkMShjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIsIHRvdGFsID0gZGVsYXk7CiAgICAgIGlmIChkZWxheSA9PSBudWxsKSByZXR1cm4gdC5yZXN0YXJ0KGNhbGxiYWNrLCBkZWxheSwgdGltZSksIHQ7CiAgICAgIGRlbGF5ID0gK2RlbGF5LCB0aW1lID0gdGltZSA9PSBudWxsID8gbm93KCkgOiArdGltZTsKICAgICAgdC5yZXN0YXJ0KGZ1bmN0aW9uIHRpY2soZWxhcHNlZCkgewogICAgICAgIGVsYXBzZWQgKz0gdG90YWw7CiAgICAgICAgdC5yZXN0YXJ0KHRpY2ssIHRvdGFsICs9IGRlbGF5LCB0aW1lKTsKICAgICAgICBjYWxsYmFjayhlbGFwc2VkKTsKICAgICAgfSwgZGVsYXksIHRpbWUpOwogICAgICByZXR1cm4gdDsKICAgIH0KCiAgICB2YXIgZW1wdHlPbiA9IGRpc3BhdGNoKCJzdGFydCIsICJlbmQiLCAiY2FuY2VsIiwgImludGVycnVwdCIpOwogICAgdmFyIGVtcHR5VHdlZW4gPSBbXTsKCiAgICB2YXIgQ1JFQVRFRCA9IDA7CiAgICB2YXIgU0NIRURVTEVEID0gMTsKICAgIHZhciBTVEFSVElORyA9IDI7CiAgICB2YXIgU1RBUlRFRCA9IDM7CiAgICB2YXIgUlVOTklORyA9IDQ7CiAgICB2YXIgRU5ESU5HID0gNTsKICAgIHZhciBFTkRFRCA9IDY7CgogICAgZnVuY3Rpb24gc2NoZWR1bGUkMShub2RlLCBuYW1lLCBpZCwgaW5kZXgsIGdyb3VwLCB0aW1pbmcpIHsKICAgICAgdmFyIHNjaGVkdWxlcyA9IG5vZGUuX190cmFuc2l0aW9uOwogICAgICBpZiAoIXNjaGVkdWxlcykgbm9kZS5fX3RyYW5zaXRpb24gPSB7fTsKICAgICAgZWxzZSBpZiAoaWQgaW4gc2NoZWR1bGVzKSByZXR1cm47CiAgICAgIGNyZWF0ZSQxKG5vZGUsIGlkLCB7CiAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICBpbmRleDogaW5kZXgsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBncm91cDogZ3JvdXAsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBvbjogZW1wdHlPbiwKICAgICAgICB0d2VlbjogZW1wdHlUd2VlbiwKICAgICAgICB0aW1lOiB0aW1pbmcudGltZSwKICAgICAgICBkZWxheTogdGltaW5nLmRlbGF5LAogICAgICAgIGR1cmF0aW9uOiB0aW1pbmcuZHVyYXRpb24sCiAgICAgICAgZWFzZTogdGltaW5nLmVhc2UsCiAgICAgICAgdGltZXI6IG51bGwsCiAgICAgICAgc3RhdGU6IENSRUFURUQKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gaW5pdChub2RlLCBpZCkgewogICAgICB2YXIgc2NoZWR1bGUgPSBnZXQkMihub2RlLCBpZCk7CiAgICAgIGlmIChzY2hlZHVsZS5zdGF0ZSA+IENSRUFURUQpIHRocm93IG5ldyBFcnJvcigidG9vIGxhdGU7IGFscmVhZHkgc2NoZWR1bGVkIik7CiAgICAgIHJldHVybiBzY2hlZHVsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZXQkMihub2RlLCBpZCkgewogICAgICB2YXIgc2NoZWR1bGUgPSBnZXQkMihub2RlLCBpZCk7CiAgICAgIGlmIChzY2hlZHVsZS5zdGF0ZSA+IFNUQVJURUQpIHRocm93IG5ldyBFcnJvcigidG9vIGxhdGU7IGFscmVhZHkgcnVubmluZyIpOwogICAgICByZXR1cm4gc2NoZWR1bGU7CiAgICB9CgogICAgZnVuY3Rpb24gZ2V0JDIobm9kZSwgaWQpIHsKICAgICAgdmFyIHNjaGVkdWxlID0gbm9kZS5fX3RyYW5zaXRpb247CiAgICAgIGlmICghc2NoZWR1bGUgfHwgIShzY2hlZHVsZSA9IHNjaGVkdWxlW2lkXSkpIHRocm93IG5ldyBFcnJvcigidHJhbnNpdGlvbiBub3QgZm91bmQiKTsKICAgICAgcmV0dXJuIHNjaGVkdWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZSQxKG5vZGUsIGlkLCBzZWxmKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbiwKICAgICAgICAgIHR3ZWVuOwoKICAgICAgLy8gSW5pdGlhbGl6ZSB0aGUgc2VsZiB0aW1lciB3aGVuIHRoZSB0cmFuc2l0aW9uIGlzIGNyZWF0ZWQuCiAgICAgIC8vIE5vdGUgdGhlIGFjdHVhbCBkZWxheSBpcyBub3Qga25vd24gdW50aWwgdGhlIGZpcnN0IGNhbGxiYWNrIQogICAgICBzY2hlZHVsZXNbaWRdID0gc2VsZjsKICAgICAgc2VsZi50aW1lciA9IHRpbWVyKHNjaGVkdWxlLCAwLCBzZWxmLnRpbWUpOwoKICAgICAgZnVuY3Rpb24gc2NoZWR1bGUoZWxhcHNlZCkgewogICAgICAgIHNlbGYuc3RhdGUgPSBTQ0hFRFVMRUQ7CiAgICAgICAgc2VsZi50aW1lci5yZXN0YXJ0KHN0YXJ0LCBzZWxmLmRlbGF5LCBzZWxmLnRpbWUpOwoKICAgICAgICAvLyBJZiB0aGUgZWxhcHNlZCBkZWxheSBpcyBsZXNzIHRoYW4gb3VyIGZpcnN0IHNsZWVwLCBzdGFydCBpbW1lZGlhdGVseS4KICAgICAgICBpZiAoc2VsZi5kZWxheSA8PSBlbGFwc2VkKSBzdGFydChlbGFwc2VkIC0gc2VsZi5kZWxheSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHN0YXJ0KGVsYXBzZWQpIHsKICAgICAgICB2YXIgaSwgaiwgbiwgbzsKCiAgICAgICAgLy8gSWYgdGhlIHN0YXRlIGlzIG5vdCBTQ0hFRFVMRUQsIHRoZW4gd2UgcHJldmlvdXNseSBlcnJvcmVkIG9uIHN0YXJ0LgogICAgICAgIGlmIChzZWxmLnN0YXRlICE9PSBTQ0hFRFVMRUQpIHJldHVybiBzdG9wKCk7CgogICAgICAgIGZvciAoaSBpbiBzY2hlZHVsZXMpIHsKICAgICAgICAgIG8gPSBzY2hlZHVsZXNbaV07CiAgICAgICAgICBpZiAoby5uYW1lICE9PSBzZWxmLm5hbWUpIGNvbnRpbnVlOwoKICAgICAgICAgIC8vIFdoaWxlIHRoaXMgZWxlbWVudCBhbHJlYWR5IGhhcyBhIHN0YXJ0aW5nIHRyYW5zaXRpb24gZHVyaW5nIHRoaXMgZnJhbWUsCiAgICAgICAgICAvLyBkZWZlciBzdGFydGluZyBhbiBpbnRlcnJ1cHRpbmcgdHJhbnNpdGlvbiB1bnRpbCB0aGF0IHRyYW5zaXRpb24gaGFzIGEKICAgICAgICAgIC8vIGNoYW5jZSB0byB0aWNrIChhbmQgcG9zc2libHkgZW5kKTsgc2VlIGQzL2QzLXRyYW5zaXRpb24jNTQhCiAgICAgICAgICBpZiAoby5zdGF0ZSA9PT0gU1RBUlRFRCkgcmV0dXJuIHRpbWVvdXQkMShzdGFydCk7CgogICAgICAgICAgLy8gSW50ZXJydXB0IHRoZSBhY3RpdmUgdHJhbnNpdGlvbiwgaWYgYW55LgogICAgICAgICAgaWYgKG8uc3RhdGUgPT09IFJVTk5JTkcpIHsKICAgICAgICAgICAgby5zdGF0ZSA9IEVOREVEOwogICAgICAgICAgICBvLnRpbWVyLnN0b3AoKTsKICAgICAgICAgICAgby5vbi5jYWxsKCJpbnRlcnJ1cHQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBvLmluZGV4LCBvLmdyb3VwKTsKICAgICAgICAgICAgZGVsZXRlIHNjaGVkdWxlc1tpXTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBDYW5jZWwgYW55IHByZS1lbXB0ZWQgdHJhbnNpdGlvbnMuCiAgICAgICAgICBlbHNlIGlmICgraSA8IGlkKSB7CiAgICAgICAgICAgIG8uc3RhdGUgPSBFTkRFRDsKICAgICAgICAgICAgby50aW1lci5zdG9wKCk7CiAgICAgICAgICAgIG8ub24uY2FsbCgiY2FuY2VsIiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgby5pbmRleCwgby5ncm91cCk7CiAgICAgICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBEZWZlciB0aGUgZmlyc3QgdGljayB0byBlbmQgb2YgdGhlIGN1cnJlbnQgZnJhbWU7IHNlZSBkMy9kMyMxNTc2LgogICAgICAgIC8vIE5vdGUgdGhlIHRyYW5zaXRpb24gbWF5IGJlIGNhbmNlbGVkIGFmdGVyIHN0YXJ0IGFuZCBiZWZvcmUgdGhlIGZpcnN0IHRpY2shCiAgICAgICAgLy8gTm90ZSB0aGlzIG11c3QgYmUgc2NoZWR1bGVkIGJlZm9yZSB0aGUgc3RhcnQgZXZlbnQ7IHNlZSBkMy9kMy10cmFuc2l0aW9uIzE2IQogICAgICAgIC8vIEFzc3VtaW5nIHRoaXMgaXMgc3VjY2Vzc2Z1bCwgc3Vic2VxdWVudCBjYWxsYmFja3MgZ28gc3RyYWlnaHQgdG8gdGljay4KICAgICAgICB0aW1lb3V0JDEoZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoc2VsZi5zdGF0ZSA9PT0gU1RBUlRFRCkgewogICAgICAgICAgICBzZWxmLnN0YXRlID0gUlVOTklORzsKICAgICAgICAgICAgc2VsZi50aW1lci5yZXN0YXJ0KHRpY2ssIHNlbGYuZGVsYXksIHNlbGYudGltZSk7CiAgICAgICAgICAgIHRpY2soZWxhcHNlZCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8vIERpc3BhdGNoIHRoZSBzdGFydCBldmVudC4KICAgICAgICAvLyBOb3RlIHRoaXMgbXVzdCBiZSBkb25lIGJlZm9yZSB0aGUgdHdlZW4gYXJlIGluaXRpYWxpemVkLgogICAgICAgIHNlbGYuc3RhdGUgPSBTVEFSVElORzsKICAgICAgICBzZWxmLm9uLmNhbGwoInN0YXJ0Iiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgc2VsZi5pbmRleCwgc2VsZi5ncm91cCk7CiAgICAgICAgaWYgKHNlbGYuc3RhdGUgIT09IFNUQVJUSU5HKSByZXR1cm47IC8vIGludGVycnVwdGVkCiAgICAgICAgc2VsZi5zdGF0ZSA9IFNUQVJURUQ7CgogICAgICAgIC8vIEluaXRpYWxpemUgdGhlIHR3ZWVuLCBkZWxldGluZyBudWxsIHR3ZWVuLgogICAgICAgIHR3ZWVuID0gbmV3IEFycmF5KG4gPSBzZWxmLnR3ZWVuLmxlbmd0aCk7CiAgICAgICAgZm9yIChpID0gMCwgaiA9IC0xOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobyA9IHNlbGYudHdlZW5baV0udmFsdWUuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKSkgewogICAgICAgICAgICB0d2VlblsrK2pdID0gbzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdHdlZW4ubGVuZ3RoID0gaiArIDE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRpY2soZWxhcHNlZCkgewogICAgICAgIHZhciB0ID0gZWxhcHNlZCA8IHNlbGYuZHVyYXRpb24gPyBzZWxmLmVhc2UuY2FsbChudWxsLCBlbGFwc2VkIC8gc2VsZi5kdXJhdGlvbikgOiAoc2VsZi50aW1lci5yZXN0YXJ0KHN0b3ApLCBzZWxmLnN0YXRlID0gRU5ESU5HLCAxKSwKICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICBuID0gdHdlZW4ubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgdHdlZW5baV0uY2FsbChub2RlLCB0KTsKICAgICAgICB9CgogICAgICAgIC8vIERpc3BhdGNoIHRoZSBlbmQgZXZlbnQuCiAgICAgICAgaWYgKHNlbGYuc3RhdGUgPT09IEVORElORykgewogICAgICAgICAgc2VsZi5vbi5jYWxsKCJlbmQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKTsKICAgICAgICAgIHN0b3AoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHN0b3AoKSB7CiAgICAgICAgc2VsZi5zdGF0ZSA9IEVOREVEOwogICAgICAgIHNlbGYudGltZXIuc3RvcCgpOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaWRdOwogICAgICAgIGZvciAodmFyIGkgaW4gc2NoZWR1bGVzKSByZXR1cm47IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKICAgICAgICBkZWxldGUgbm9kZS5fX3RyYW5zaXRpb247CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnJ1cHQobm9kZSwgbmFtZSkgewogICAgICB2YXIgc2NoZWR1bGVzID0gbm9kZS5fX3RyYW5zaXRpb24sCiAgICAgICAgICBzY2hlZHVsZSwKICAgICAgICAgIGFjdGl2ZSwKICAgICAgICAgIGVtcHR5ID0gdHJ1ZSwKICAgICAgICAgIGk7CgogICAgICBpZiAoIXNjaGVkdWxlcykgcmV0dXJuOwoKICAgICAgbmFtZSA9IG5hbWUgPT0gbnVsbCA/IG51bGwgOiBuYW1lICsgIiI7CgogICAgICBmb3IgKGkgaW4gc2NoZWR1bGVzKSB7CiAgICAgICAgaWYgKChzY2hlZHVsZSA9IHNjaGVkdWxlc1tpXSkubmFtZSAhPT0gbmFtZSkgeyBlbXB0eSA9IGZhbHNlOyBjb250aW51ZTsgfQogICAgICAgIGFjdGl2ZSA9IHNjaGVkdWxlLnN0YXRlID4gU1RBUlRJTkcgJiYgc2NoZWR1bGUuc3RhdGUgPCBFTkRJTkc7CiAgICAgICAgc2NoZWR1bGUuc3RhdGUgPSBFTkRFRDsKICAgICAgICBzY2hlZHVsZS50aW1lci5zdG9wKCk7CiAgICAgICAgc2NoZWR1bGUub24uY2FsbChhY3RpdmUgPyAiaW50ZXJydXB0IiA6ICJjYW5jZWwiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzY2hlZHVsZS5pbmRleCwgc2NoZWR1bGUuZ3JvdXApOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgIH0KCiAgICAgIGlmIChlbXB0eSkgZGVsZXRlIG5vZGUuX190cmFuc2l0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9pbnRlcnJ1cHQobmFtZSkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKGZ1bmN0aW9uKCkgewogICAgICAgIGludGVycnVwdCh0aGlzLCBuYW1lKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHdlZW5SZW1vdmUoaWQsIG5hbWUpIHsKICAgICAgdmFyIHR3ZWVuMCwgdHdlZW4xOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JDIodGhpcywgaWQpLAogICAgICAgICAgICB0d2VlbiA9IHNjaGVkdWxlLnR3ZWVuOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIHR3ZWVuIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIHR3ZWVuIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmICh0d2VlbiAhPT0gdHdlZW4wKSB7CiAgICAgICAgICB0d2VlbjEgPSB0d2VlbjAgPSB0d2VlbjsKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHdlZW4xLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAodHdlZW4xW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgICB0d2VlbjEgPSB0d2VlbjEuc2xpY2UoKTsKICAgICAgICAgICAgICB0d2VlbjEuc3BsaWNlKGksIDEpOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBzY2hlZHVsZS50d2VlbiA9IHR3ZWVuMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0d2VlbkZ1bmN0aW9uKGlkLCBuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgdHdlZW4wLCB0d2VlbjE7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCQyKHRoaXMsIGlkKSwKICAgICAgICAgICAgdHdlZW4gPSBzY2hlZHVsZS50d2VlbjsKCiAgICAgICAgLy8gSWYgdGhpcyBub2RlIHNoYXJlZCB0d2VlbiB3aXRoIHRoZSBwcmV2aW91cyBub2RlLAogICAgICAgIC8vIGp1c3QgYXNzaWduIHRoZSB1cGRhdGVkIHNoYXJlZCB0d2VlbiBhbmQgd2XigJlyZSBkb25lIQogICAgICAgIC8vIE90aGVyd2lzZSwgY29weS1vbi13cml0ZS4KICAgICAgICBpZiAodHdlZW4gIT09IHR3ZWVuMCkgewogICAgICAgICAgdHdlZW4xID0gKHR3ZWVuMCA9IHR3ZWVuKS5zbGljZSgpOwogICAgICAgICAgZm9yICh2YXIgdCA9IHtuYW1lOiBuYW1lLCB2YWx1ZTogdmFsdWV9LCBpID0gMCwgbiA9IHR3ZWVuMS5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgaWYgKHR3ZWVuMVtpXS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICAgICAgdHdlZW4xW2ldID0gdDsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGkgPT09IG4pIHR3ZWVuMS5wdXNoKHQpOwogICAgICAgIH0KCiAgICAgICAgc2NoZWR1bGUudHdlZW4gPSB0d2VlbjE7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl90d2VlbihuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIG5hbWUgKz0gIiI7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgdHdlZW4gPSBnZXQkMih0aGlzLm5vZGUoKSwgaWQpLnR3ZWVuOwogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHdlZW4ubGVuZ3RoLCB0OyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKHQgPSB0d2VlbltpXSkubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgICByZXR1cm4gdC52YWx1ZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHZhbHVlID09IG51bGwgPyB0d2VlblJlbW92ZSA6IHR3ZWVuRnVuY3Rpb24pKGlkLCBuYW1lLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHR3ZWVuVmFsdWUodHJhbnNpdGlvbiwgbmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGlkID0gdHJhbnNpdGlvbi5faWQ7CgogICAgICB0cmFuc2l0aW9uLmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JDIodGhpcywgaWQpOwogICAgICAgIChzY2hlZHVsZS52YWx1ZSB8fCAoc2NoZWR1bGUudmFsdWUgPSB7fSkpW25hbWVdID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfSk7CgogICAgICByZXR1cm4gZnVuY3Rpb24obm9kZSkgewogICAgICAgIHJldHVybiBnZXQkMihub2RlLCBpZCkudmFsdWVbbmFtZV07CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGUoYSwgYikgewogICAgICB2YXIgYzsKICAgICAgcmV0dXJuICh0eXBlb2YgYiA9PT0gIm51bWJlciIgPyBpbnRlcnBvbGF0ZU51bWJlcgogICAgICAgICAgOiBiIGluc3RhbmNlb2YgY29sb3IgPyBpbnRlcnBvbGF0ZVJnYgogICAgICAgICAgOiAoYyA9IGNvbG9yKGIpKSA/IChiID0gYywgaW50ZXJwb2xhdGVSZ2IpCiAgICAgICAgICA6IGludGVycG9sYXRlU3RyaW5nKShhLCBiKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlJDEobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZU5TJDEoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnQkMShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUxKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIiwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckNvbnN0YW50TlMkMShmdWxsbmFtZSwgaW50ZXJwb2xhdGUsIHZhbHVlMSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiIsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCA9IHRoaXMuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgdmFsdWUxKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb24kMShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCwgdmFsdWUxID0gdmFsdWUodGhpcyksIHN0cmluZzE7CiAgICAgICAgaWYgKHZhbHVlMSA9PSBudWxsKSByZXR1cm4gdm9pZCB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgc3RyaW5nMSA9IHZhbHVlMSArICIiOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwICYmIHN0cmluZzEgPT09IHN0cmluZzEwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogKHN0cmluZzEwID0gc3RyaW5nMSwgaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCB2YWx1ZTEpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb25OUyQxKGZ1bGxuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCwgdmFsdWUxID0gdmFsdWUodGhpcyksIHN0cmluZzE7CiAgICAgICAgaWYgKHZhbHVlMSA9PSBudWxsKSByZXR1cm4gdm9pZCB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgICAgc3RyaW5nMCA9IHRoaXMuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiI7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgJiYgc3RyaW5nMSA9PT0gc3RyaW5nMTAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiAoc3RyaW5nMTAgPSBzdHJpbmcxLCBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0cihuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UobmFtZSksIGkgPSBmdWxsbmFtZSA9PT0gInRyYW5zZm9ybSIgPyBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZyA6IGludGVycG9sYXRlOwogICAgICByZXR1cm4gdGhpcy5hdHRyVHdlZW4obmFtZSwgdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJGdW5jdGlvbk5TJDEgOiBhdHRyRnVuY3Rpb24kMSkoZnVsbG5hbWUsIGksIHR3ZWVuVmFsdWUodGhpcywgImF0dHIuIiArIG5hbWUsIHZhbHVlKSkKICAgICAgICAgIDogdmFsdWUgPT0gbnVsbCA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJSZW1vdmVOUyQxIDogYXR0clJlbW92ZSQxKShmdWxsbmFtZSkKICAgICAgICAgIDogKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckNvbnN0YW50TlMkMSA6IGF0dHJDb25zdGFudCQxKShmdWxsbmFtZSwgaSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRySW50ZXJwb2xhdGUobmFtZSwgaSkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIGkuY2FsbCh0aGlzLCB0KSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckludGVycG9sYXRlTlMoZnVsbG5hbWUsIGkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCwgaS5jYWxsKHRoaXMsIHQpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyVHdlZW5OUyhmdWxsbmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIHQwLCBpMDsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChpICE9PSBpMCkgdDAgPSAoaTAgPSBpKSAmJiBhdHRySW50ZXJwb2xhdGVOUyhmdWxsbmFtZSwgaSk7CiAgICAgICAgcmV0dXJuIHQwOwogICAgICB9CiAgICAgIHR3ZWVuLl92YWx1ZSA9IHZhbHVlOwogICAgICByZXR1cm4gdHdlZW47CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clR3ZWVuKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciB0MCwgaTA7CiAgICAgIGZ1bmN0aW9uIHR3ZWVuKCkgewogICAgICAgIHZhciBpID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAoaSAhPT0gaTApIHQwID0gKGkwID0gaSkgJiYgYXR0ckludGVycG9sYXRlKG5hbWUsIGkpOwogICAgICAgIHJldHVybiB0MDsKICAgICAgfQogICAgICB0d2Vlbi5fdmFsdWUgPSB2YWx1ZTsKICAgICAgcmV0dXJuIHR3ZWVuOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0clR3ZWVuKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBrZXkgPSAiYXR0ci4iICsgbmFtZTsKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSByZXR1cm4gKGtleSA9IHRoaXMudHdlZW4oa2V5KSkgJiYga2V5Ll92YWx1ZTsKICAgICAgaWYgKHZhbHVlID09IG51bGwpIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgbnVsbCk7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlKG5hbWUpOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIChmdWxsbmFtZS5sb2NhbCA/IGF0dHJUd2Vlbk5TIDogYXR0clR3ZWVuKShmdWxsbmFtZSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWxheUZ1bmN0aW9uKGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgaW5pdCh0aGlzLCBpZCkuZGVsYXkgPSArdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWxheUNvbnN0YW50KGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPSArdmFsdWUsIGZ1bmN0aW9uKCkgewogICAgICAgIGluaXQodGhpcywgaWQpLmRlbGF5ID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9kZWxheSh2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCgodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBkZWxheUZ1bmN0aW9uCiAgICAgICAgICAgICAgOiBkZWxheUNvbnN0YW50KShpZCwgdmFsdWUpKQogICAgICAgICAgOiBnZXQkMih0aGlzLm5vZGUoKSwgaWQpLmRlbGF5OwogICAgfQoKICAgIGZ1bmN0aW9uIGR1cmF0aW9uRnVuY3Rpb24oaWQsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBzZXQkMih0aGlzLCBpZCkuZHVyYXRpb24gPSArdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkdXJhdGlvbkNvbnN0YW50KGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPSArdmFsdWUsIGZ1bmN0aW9uKCkgewogICAgICAgIHNldCQyKHRoaXMsIGlkKS5kdXJhdGlvbiA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZHVyYXRpb24odmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gZHVyYXRpb25GdW5jdGlvbgogICAgICAgICAgICAgIDogZHVyYXRpb25Db25zdGFudCkoaWQsIHZhbHVlKSkKICAgICAgICAgIDogZ2V0JDIodGhpcy5ub2RlKCksIGlkKS5kdXJhdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBlYXNlQ29uc3RhbnQoaWQsIHZhbHVlKSB7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHNldCQyKHRoaXMsIGlkKS5lYXNlID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9lYXNlKHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRoaXMuX2lkOwoKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKGVhc2VDb25zdGFudChpZCwgdmFsdWUpKQogICAgICAgICAgOiBnZXQkMih0aGlzLm5vZGUoKSwgaWQpLmVhc2U7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9maWx0ZXIobWF0Y2gpIHsKICAgICAgaWYgKHR5cGVvZiBtYXRjaCAhPT0gImZ1bmN0aW9uIikgbWF0Y2ggPSBtYXRjaGVyKG1hdGNoKTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBbXSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiBtYXRjaC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkgewogICAgICAgICAgICBzdWJncm91cC5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uKHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cywgdGhpcy5fbmFtZSwgdGhpcy5faWQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fbWVyZ2UodHJhbnNpdGlvbikgewogICAgICBpZiAodHJhbnNpdGlvbi5faWQgIT09IHRoaXMuX2lkKSB0aHJvdyBuZXcgRXJyb3I7CgogICAgICBmb3IgKHZhciBncm91cHMwID0gdGhpcy5fZ3JvdXBzLCBncm91cHMxID0gdHJhbnNpdGlvbi5fZ3JvdXBzLCBtMCA9IGdyb3VwczAubGVuZ3RoLCBtMSA9IGdyb3VwczEubGVuZ3RoLCBtID0gTWF0aC5taW4obTAsIG0xKSwgbWVyZ2VzID0gbmV3IEFycmF5KG0wKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cDAgPSBncm91cHMwW2pdLCBncm91cDEgPSBncm91cHMxW2pdLCBuID0gZ3JvdXAwLmxlbmd0aCwgbWVyZ2UgPSBtZXJnZXNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwMFtpXSB8fCBncm91cDFbaV0pIHsKICAgICAgICAgICAgbWVyZ2VbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yICg7IGogPCBtMDsgKytqKSB7CiAgICAgICAgbWVyZ2VzW2pdID0gZ3JvdXBzMFtqXTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uKG1lcmdlcywgdGhpcy5fcGFyZW50cywgdGhpcy5fbmFtZSwgdGhpcy5faWQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0YXJ0KG5hbWUpIHsKICAgICAgcmV0dXJuIChuYW1lICsgIiIpLnRyaW0oKS5zcGxpdCgvXnxccysvKS5ldmVyeShmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICByZXR1cm4gIXQgfHwgdCA9PT0gInN0YXJ0IjsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gb25GdW5jdGlvbihpZCwgbmFtZSwgbGlzdGVuZXIpIHsKICAgICAgdmFyIG9uMCwgb24xLCBzaXQgPSBzdGFydChuYW1lKSA/IGluaXQgOiBzZXQkMjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNpdCh0aGlzLCBpZCksCiAgICAgICAgICAgIG9uID0gc2NoZWR1bGUub247CgogICAgICAgIC8vIElmIHRoaXMgbm9kZSBzaGFyZWQgYSBkaXNwYXRjaCB3aXRoIHRoZSBwcmV2aW91cyBub2RlLAogICAgICAgIC8vIGp1c3QgYXNzaWduIHRoZSB1cGRhdGVkIHNoYXJlZCBkaXNwYXRjaCBhbmQgd2XigJlyZSBkb25lIQogICAgICAgIC8vIE90aGVyd2lzZSwgY29weS1vbi13cml0ZS4KICAgICAgICBpZiAob24gIT09IG9uMCkgKG9uMSA9IChvbjAgPSBvbikuY29weSgpKS5vbihuYW1lLCBsaXN0ZW5lcik7CgogICAgICAgIHNjaGVkdWxlLm9uID0gb24xOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fb24obmFtZSwgbGlzdGVuZXIpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA8IDIKICAgICAgICAgID8gZ2V0JDIodGhpcy5ub2RlKCksIGlkKS5vbi5vbihuYW1lKQogICAgICAgICAgOiB0aGlzLmVhY2gob25GdW5jdGlvbihpZCwgbmFtZSwgbGlzdGVuZXIpKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVGdW5jdGlvbihpZCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgICBmb3IgKHZhciBpIGluIHRoaXMuX190cmFuc2l0aW9uKSBpZiAoK2kgIT09IGlkKSByZXR1cm47CiAgICAgICAgaWYgKHBhcmVudCkgcGFyZW50LnJlbW92ZUNoaWxkKHRoaXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fcmVtb3ZlKCkgewogICAgICByZXR1cm4gdGhpcy5vbigiZW5kLnJlbW92ZSIsIHJlbW92ZUZ1bmN0aW9uKHRoaXMuX2lkKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zZWxlY3Qoc2VsZWN0KSB7CiAgICAgIHZhciBuYW1lID0gdGhpcy5fbmFtZSwKICAgICAgICAgIGlkID0gdGhpcy5faWQ7CgogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3Ioc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIHN1Ym5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKHN1Ym5vZGUgPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpKSB7CiAgICAgICAgICAgIGlmICgiX19kYXRhX18iIGluIG5vZGUpIHN1Ym5vZGUuX19kYXRhX18gPSBub2RlLl9fZGF0YV9fOwogICAgICAgICAgICBzdWJncm91cFtpXSA9IHN1Ym5vZGU7CiAgICAgICAgICAgIHNjaGVkdWxlJDEoc3ViZ3JvdXBbaV0sIG5hbWUsIGlkLCBpLCBzdWJncm91cCwgZ2V0JDIobm9kZSwgaWQpKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbihzdWJncm91cHMsIHRoaXMuX3BhcmVudHMsIG5hbWUsIGlkKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3NlbGVjdEFsbChzZWxlY3QpIHsKICAgICAgdmFyIG5hbWUgPSB0aGlzLl9uYW1lLAogICAgICAgICAgaWQgPSB0aGlzLl9pZDsKCiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvckFsbChzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gW10sIHBhcmVudHMgPSBbXSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgZm9yICh2YXIgY2hpbGRyZW4gPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCksIGNoaWxkLCBpbmhlcml0ID0gZ2V0JDIobm9kZSwgaWQpLCBrID0gMCwgbCA9IGNoaWxkcmVuLmxlbmd0aDsgayA8IGw7ICsraykgewogICAgICAgICAgICAgIGlmIChjaGlsZCA9IGNoaWxkcmVuW2tdKSB7CiAgICAgICAgICAgICAgICBzY2hlZHVsZSQxKGNoaWxkLCBuYW1lLCBpZCwgaywgY2hpbGRyZW4sIGluaGVyaXQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBzdWJncm91cHMucHVzaChjaGlsZHJlbik7CiAgICAgICAgICAgIHBhcmVudHMucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbihzdWJncm91cHMsIHBhcmVudHMsIG5hbWUsIGlkKTsKICAgIH0KCiAgICB2YXIgU2VsZWN0aW9uJDEgPSBzZWxlY3Rpb24ucHJvdG90eXBlLmNvbnN0cnVjdG9yOwoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc2VsZWN0aW9uKCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQxKHRoaXMuX2dyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVOdWxsKG5hbWUsIGludGVycG9sYXRlKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEwLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHN0cmluZzAgPSBzdHlsZVZhbHVlKHRoaXMsIG5hbWUpLAogICAgICAgICAgICBzdHJpbmcxID0gKHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSksIHN0eWxlVmFsdWUodGhpcywgbmFtZSkpOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwICYmIHN0cmluZzEgPT09IHN0cmluZzEwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCBzdHJpbmcxMCA9IHN0cmluZzEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlUmVtb3ZlJDEobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUNvbnN0YW50JDEobmFtZSwgaW50ZXJwb2xhdGUsIHZhbHVlMSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiIsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCA9IHN0eWxlVmFsdWUodGhpcywgbmFtZSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVGdW5jdGlvbiQxKG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gc3R5bGVWYWx1ZSh0aGlzLCBuYW1lKSwKICAgICAgICAgICAgdmFsdWUxID0gdmFsdWUodGhpcyksCiAgICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIjsKICAgICAgICBpZiAodmFsdWUxID09IG51bGwpIHN0cmluZzEgPSB2YWx1ZTEgPSAodGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKSwgc3R5bGVWYWx1ZSh0aGlzLCBuYW1lKSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgJiYgc3RyaW5nMSA9PT0gc3RyaW5nMTAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiAoc3RyaW5nMTAgPSBzdHJpbmcxLCBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlTWF5YmVSZW1vdmUoaWQsIG5hbWUpIHsKICAgICAgdmFyIG9uMCwgb24xLCBsaXN0ZW5lcjAsIGtleSA9ICJzdHlsZS4iICsgbmFtZSwgZXZlbnQgPSAiZW5kLiIgKyBrZXksIHJlbW92ZTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCQyKHRoaXMsIGlkKSwKICAgICAgICAgICAgb24gPSBzY2hlZHVsZS5vbiwKICAgICAgICAgICAgbGlzdGVuZXIgPSBzY2hlZHVsZS52YWx1ZVtrZXldID09IG51bGwgPyByZW1vdmUgfHwgKHJlbW92ZSA9IHN0eWxlUmVtb3ZlJDEobmFtZSkpIDogdW5kZWZpbmVkOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIGEgZGlzcGF0Y2ggd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAvLyBqdXN0IGFzc2lnbiB0aGUgdXBkYXRlZCBzaGFyZWQgZGlzcGF0Y2ggYW5kIHdl4oCZcmUgZG9uZSEKICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgaWYgKG9uICE9PSBvbjAgfHwgbGlzdGVuZXIwICE9PSBsaXN0ZW5lcikgKG9uMSA9IChvbjAgPSBvbikuY29weSgpKS5vbihldmVudCwgbGlzdGVuZXIwID0gbGlzdGVuZXIpOwoKICAgICAgICBzY2hlZHVsZS5vbiA9IG9uMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3N0eWxlKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICB2YXIgaSA9IChuYW1lICs9ICIiKSA9PT0gInRyYW5zZm9ybSIgPyBpbnRlcnBvbGF0ZVRyYW5zZm9ybUNzcyA6IGludGVycG9sYXRlOwogICAgICByZXR1cm4gdmFsdWUgPT0gbnVsbCA/IHRoaXMKICAgICAgICAgIC5zdHlsZVR3ZWVuKG5hbWUsIHN0eWxlTnVsbChuYW1lLCBpKSkKICAgICAgICAgIC5vbigiZW5kLnN0eWxlLiIgKyBuYW1lLCBzdHlsZVJlbW92ZSQxKG5hbWUpKQogICAgICAgIDogdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iID8gdGhpcwogICAgICAgICAgLnN0eWxlVHdlZW4obmFtZSwgc3R5bGVGdW5jdGlvbiQxKG5hbWUsIGksIHR3ZWVuVmFsdWUodGhpcywgInN0eWxlLiIgKyBuYW1lLCB2YWx1ZSkpKQogICAgICAgICAgLmVhY2goc3R5bGVNYXliZVJlbW92ZSh0aGlzLl9pZCwgbmFtZSkpCiAgICAgICAgOiB0aGlzCiAgICAgICAgICAuc3R5bGVUd2VlbihuYW1lLCBzdHlsZUNvbnN0YW50JDEobmFtZSwgaSwgdmFsdWUpLCBwcmlvcml0eSkKICAgICAgICAgIC5vbigiZW5kLnN0eWxlLiIgKyBuYW1lLCBudWxsKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUludGVycG9sYXRlKG5hbWUsIGksIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdGhpcy5zdHlsZS5zZXRQcm9wZXJ0eShuYW1lLCBpLmNhbGwodGhpcywgdCksIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVR3ZWVuKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICB2YXIgdCwgaTA7CiAgICAgIGZ1bmN0aW9uIHR3ZWVuKCkgewogICAgICAgIHZhciBpID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAoaSAhPT0gaTApIHQgPSAoaTAgPSBpKSAmJiBzdHlsZUludGVycG9sYXRlKG5hbWUsIGksIHByaW9yaXR5KTsKICAgICAgICByZXR1cm4gdDsKICAgICAgfQogICAgICB0d2Vlbi5fdmFsdWUgPSB2YWx1ZTsKICAgICAgcmV0dXJuIHR3ZWVuOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc3R5bGVUd2VlbihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIGtleSA9ICJzdHlsZS4iICsgKG5hbWUgKz0gIiIpOwogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHJldHVybiAoa2V5ID0gdGhpcy50d2VlbihrZXkpKSAmJiBrZXkuX3ZhbHVlOwogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCBudWxsKTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIHN0eWxlVHdlZW4obmFtZSwgdmFsdWUsIHByaW9yaXR5ID09IG51bGwgPyAiIiA6IHByaW9yaXR5KSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dENvbnN0YW50JDEodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0RnVuY3Rpb24kMSh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHZhbHVlMSA9IHZhbHVlKHRoaXMpOwogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2YWx1ZTEgPT0gbnVsbCA/ICIiIDogdmFsdWUxOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fdGV4dCh2YWx1ZSkgewogICAgICByZXR1cm4gdGhpcy50d2VlbigidGV4dCIsIHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyB0ZXh0RnVuY3Rpb24kMSh0d2VlblZhbHVlKHRoaXMsICJ0ZXh0IiwgdmFsdWUpKQogICAgICAgICAgOiB0ZXh0Q29uc3RhbnQkMSh2YWx1ZSA9PSBudWxsID8gIiIgOiB2YWx1ZSArICIiKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dEludGVycG9sYXRlKGkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gaS5jYWxsKHRoaXMsIHQpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRUd2Vlbih2YWx1ZSkgewogICAgICB2YXIgdDAsIGkwOwogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgaSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKGkgIT09IGkwKSB0MCA9IChpMCA9IGkpICYmIHRleHRJbnRlcnBvbGF0ZShpKTsKICAgICAgICByZXR1cm4gdDA7CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3RleHRUd2Vlbih2YWx1ZSkgewogICAgICB2YXIga2V5ID0gInRleHQiOwogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDEpIHJldHVybiAoa2V5ID0gdGhpcy50d2VlbihrZXkpKSAmJiBrZXkuX3ZhbHVlOwogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCBudWxsKTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIHRleHRUd2Vlbih2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fdHJhbnNpdGlvbigpIHsKICAgICAgdmFyIG5hbWUgPSB0aGlzLl9uYW1lLAogICAgICAgICAgaWQwID0gdGhpcy5faWQsCiAgICAgICAgICBpZDEgPSBuZXdJZCgpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgdmFyIGluaGVyaXQgPSBnZXQkMihub2RlLCBpZDApOwogICAgICAgICAgICBzY2hlZHVsZSQxKG5vZGUsIG5hbWUsIGlkMSwgaSwgZ3JvdXAsIHsKICAgICAgICAgICAgICB0aW1lOiBpbmhlcml0LnRpbWUgKyBpbmhlcml0LmRlbGF5ICsgaW5oZXJpdC5kdXJhdGlvbiwKICAgICAgICAgICAgICBkZWxheTogMCwKICAgICAgICAgICAgICBkdXJhdGlvbjogaW5oZXJpdC5kdXJhdGlvbiwKICAgICAgICAgICAgICBlYXNlOiBpbmhlcml0LmVhc2UKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24oZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCBuYW1lLCBpZDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZW5kKCkgewogICAgICB2YXIgb24wLCBvbjEsIHRoYXQgPSB0aGlzLCBpZCA9IHRoYXQuX2lkLCBzaXplID0gdGhhdC5zaXplKCk7CiAgICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgICB2YXIgY2FuY2VsID0ge3ZhbHVlOiByZWplY3R9LAogICAgICAgICAgICBlbmQgPSB7dmFsdWU6IGZ1bmN0aW9uKCkgeyBpZiAoLS1zaXplID09PSAwKSByZXNvbHZlKCk7IH19OwoKICAgICAgICB0aGF0LmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgc2NoZWR1bGUgPSBzZXQkMih0aGlzLCBpZCksCiAgICAgICAgICAgICAgb24gPSBzY2hlZHVsZS5vbjsKCiAgICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIGEgZGlzcGF0Y2ggd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAgIC8vIGp1c3QgYXNzaWduIHRoZSB1cGRhdGVkIHNoYXJlZCBkaXNwYXRjaCBhbmQgd2XigJlyZSBkb25lIQogICAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgICAgaWYgKG9uICE9PSBvbjApIHsKICAgICAgICAgICAgb24xID0gKG9uMCA9IG9uKS5jb3B5KCk7CiAgICAgICAgICAgIG9uMS5fLmNhbmNlbC5wdXNoKGNhbmNlbCk7CiAgICAgICAgICAgIG9uMS5fLmludGVycnVwdC5wdXNoKGNhbmNlbCk7CiAgICAgICAgICAgIG9uMS5fLmVuZC5wdXNoKGVuZCk7CiAgICAgICAgICB9CgogICAgICAgICAgc2NoZWR1bGUub24gPSBvbjE7CiAgICAgICAgfSk7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBpZCA9IDA7CgogICAgZnVuY3Rpb24gVHJhbnNpdGlvbihncm91cHMsIHBhcmVudHMsIG5hbWUsIGlkKSB7CiAgICAgIHRoaXMuX2dyb3VwcyA9IGdyb3VwczsKICAgICAgdGhpcy5fcGFyZW50cyA9IHBhcmVudHM7CiAgICAgIHRoaXMuX25hbWUgPSBuYW1lOwogICAgICB0aGlzLl9pZCA9IGlkOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb24obmFtZSkgewogICAgICByZXR1cm4gc2VsZWN0aW9uKCkudHJhbnNpdGlvbihuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBuZXdJZCgpIHsKICAgICAgcmV0dXJuICsraWQ7CiAgICB9CgogICAgdmFyIHNlbGVjdGlvbl9wcm90b3R5cGUgPSBzZWxlY3Rpb24ucHJvdG90eXBlOwoKICAgIFRyYW5zaXRpb24ucHJvdG90eXBlID0gdHJhbnNpdGlvbi5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBUcmFuc2l0aW9uLAogICAgICBzZWxlY3Q6IHRyYW5zaXRpb25fc2VsZWN0LAogICAgICBzZWxlY3RBbGw6IHRyYW5zaXRpb25fc2VsZWN0QWxsLAogICAgICBmaWx0ZXI6IHRyYW5zaXRpb25fZmlsdGVyLAogICAgICBtZXJnZTogdHJhbnNpdGlvbl9tZXJnZSwKICAgICAgc2VsZWN0aW9uOiB0cmFuc2l0aW9uX3NlbGVjdGlvbiwKICAgICAgdHJhbnNpdGlvbjogdHJhbnNpdGlvbl90cmFuc2l0aW9uLAogICAgICBjYWxsOiBzZWxlY3Rpb25fcHJvdG90eXBlLmNhbGwsCiAgICAgIG5vZGVzOiBzZWxlY3Rpb25fcHJvdG90eXBlLm5vZGVzLAogICAgICBub2RlOiBzZWxlY3Rpb25fcHJvdG90eXBlLm5vZGUsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9wcm90b3R5cGUuc2l6ZSwKICAgICAgZW1wdHk6IHNlbGVjdGlvbl9wcm90b3R5cGUuZW1wdHksCiAgICAgIGVhY2g6IHNlbGVjdGlvbl9wcm90b3R5cGUuZWFjaCwKICAgICAgb246IHRyYW5zaXRpb25fb24sCiAgICAgIGF0dHI6IHRyYW5zaXRpb25fYXR0ciwKICAgICAgYXR0clR3ZWVuOiB0cmFuc2l0aW9uX2F0dHJUd2VlbiwKICAgICAgc3R5bGU6IHRyYW5zaXRpb25fc3R5bGUsCiAgICAgIHN0eWxlVHdlZW46IHRyYW5zaXRpb25fc3R5bGVUd2VlbiwKICAgICAgdGV4dDogdHJhbnNpdGlvbl90ZXh0LAogICAgICB0ZXh0VHdlZW46IHRyYW5zaXRpb25fdGV4dFR3ZWVuLAogICAgICByZW1vdmU6IHRyYW5zaXRpb25fcmVtb3ZlLAogICAgICB0d2VlbjogdHJhbnNpdGlvbl90d2VlbiwKICAgICAgZGVsYXk6IHRyYW5zaXRpb25fZGVsYXksCiAgICAgIGR1cmF0aW9uOiB0cmFuc2l0aW9uX2R1cmF0aW9uLAogICAgICBlYXNlOiB0cmFuc2l0aW9uX2Vhc2UsCiAgICAgIGVuZDogdHJhbnNpdGlvbl9lbmQKICAgIH07CgogICAgZnVuY3Rpb24gbGluZWFyJDEodCkgewogICAgICByZXR1cm4gK3Q7CiAgICB9CgogICAgZnVuY3Rpb24gcXVhZEluKHQpIHsKICAgICAgcmV0dXJuIHQgKiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YWRPdXQodCkgewogICAgICByZXR1cm4gdCAqICgyIC0gdCk7CiAgICB9CgogICAgZnVuY3Rpb24gcXVhZEluT3V0KHQpIHsKICAgICAgcmV0dXJuICgodCAqPSAyKSA8PSAxID8gdCAqIHQgOiAtLXQgKiAoMiAtIHQpICsgMSkgLyAyOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmljSW4odCkgewogICAgICByZXR1cm4gdCAqIHQgKiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmljT3V0KHQpIHsKICAgICAgcmV0dXJuIC0tdCAqIHQgKiB0ICsgMTsKICAgIH0KCiAgICBmdW5jdGlvbiBjdWJpY0luT3V0KHQpIHsKICAgICAgcmV0dXJuICgodCAqPSAyKSA8PSAxID8gdCAqIHQgKiB0IDogKHQgLT0gMikgKiB0ICogdCArIDIpIC8gMjsKICAgIH0KCiAgICB2YXIgZXhwb25lbnQgPSAzOwoKICAgIHZhciBwb2x5SW4gPSAoZnVuY3Rpb24gY3VzdG9tKGUpIHsKICAgICAgZSA9ICtlOwoKICAgICAgZnVuY3Rpb24gcG9seUluKHQpIHsKICAgICAgICByZXR1cm4gTWF0aC5wb3codCwgZSk7CiAgICAgIH0KCiAgICAgIHBvbHlJbi5leHBvbmVudCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBwb2x5SW47CiAgICB9KShleHBvbmVudCk7CgogICAgdmFyIHBvbHlPdXQgPSAoZnVuY3Rpb24gY3VzdG9tKGUpIHsKICAgICAgZSA9ICtlOwoKICAgICAgZnVuY3Rpb24gcG9seU91dCh0KSB7CiAgICAgICAgcmV0dXJuIDEgLSBNYXRoLnBvdygxIC0gdCwgZSk7CiAgICAgIH0KCiAgICAgIHBvbHlPdXQuZXhwb25lbnQgPSBjdXN0b207CgogICAgICByZXR1cm4gcG9seU91dDsKICAgIH0pKGV4cG9uZW50KTsKCiAgICB2YXIgcG9seUluT3V0ID0gKGZ1bmN0aW9uIGN1c3RvbShlKSB7CiAgICAgIGUgPSArZTsKCiAgICAgIGZ1bmN0aW9uIHBvbHlJbk91dCh0KSB7CiAgICAgICAgcmV0dXJuICgodCAqPSAyKSA8PSAxID8gTWF0aC5wb3codCwgZSkgOiAyIC0gTWF0aC5wb3coMiAtIHQsIGUpKSAvIDI7CiAgICAgIH0KCiAgICAgIHBvbHlJbk91dC5leHBvbmVudCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBwb2x5SW5PdXQ7CiAgICB9KShleHBvbmVudCk7CgogICAgdmFyIHBpID0gTWF0aC5QSSwKICAgICAgICBoYWxmUGkgPSBwaSAvIDI7CgogICAgZnVuY3Rpb24gc2luSW4odCkgewogICAgICByZXR1cm4gMSAtIE1hdGguY29zKHQgKiBoYWxmUGkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNpbk91dCh0KSB7CiAgICAgIHJldHVybiBNYXRoLnNpbih0ICogaGFsZlBpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzaW5Jbk91dCh0KSB7CiAgICAgIHJldHVybiAoMSAtIE1hdGguY29zKHBpICogdCkpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBJbih0KSB7CiAgICAgIHJldHVybiBNYXRoLnBvdygyLCAxMCAqIHQgLSAxMCk7CiAgICB9CgogICAgZnVuY3Rpb24gZXhwT3V0KHQpIHsKICAgICAgcmV0dXJuIDEgLSBNYXRoLnBvdygyLCAtMTAgKiB0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBJbk91dCh0KSB7CiAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IE1hdGgucG93KDIsIDEwICogdCAtIDEwKSA6IDIgLSBNYXRoLnBvdygyLCAxMCAtIDEwICogdCkpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjaXJjbGVJbih0KSB7CiAgICAgIHJldHVybiAxIC0gTWF0aC5zcXJ0KDEgLSB0ICogdCk7CiAgICB9CgogICAgZnVuY3Rpb24gY2lyY2xlT3V0KHQpIHsKICAgICAgcmV0dXJuIE1hdGguc3FydCgxIC0gLS10ICogdCk7CiAgICB9CgogICAgZnVuY3Rpb24gY2lyY2xlSW5PdXQodCkgewogICAgICByZXR1cm4gKCh0ICo9IDIpIDw9IDEgPyAxIC0gTWF0aC5zcXJ0KDEgLSB0ICogdCkgOiBNYXRoLnNxcnQoMSAtICh0IC09IDIpICogdCkgKyAxKSAvIDI7CiAgICB9CgogICAgdmFyIGIxID0gNCAvIDExLAogICAgICAgIGIyID0gNiAvIDExLAogICAgICAgIGIzID0gOCAvIDExLAogICAgICAgIGI0ID0gMyAvIDQsCiAgICAgICAgYjUgPSA5IC8gMTEsCiAgICAgICAgYjYgPSAxMCAvIDExLAogICAgICAgIGI3ID0gMTUgLyAxNiwKICAgICAgICBiOCA9IDIxIC8gMjIsCiAgICAgICAgYjkgPSA2MyAvIDY0LAogICAgICAgIGIwID0gMSAvIGIxIC8gYjE7CgogICAgZnVuY3Rpb24gYm91bmNlSW4odCkgewogICAgICByZXR1cm4gMSAtIGJvdW5jZU91dCgxIC0gdCk7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmNlT3V0KHQpIHsKICAgICAgcmV0dXJuICh0ID0gK3QpIDwgYjEgPyBiMCAqIHQgKiB0IDogdCA8IGIzID8gYjAgKiAodCAtPSBiMikgKiB0ICsgYjQgOiB0IDwgYjYgPyBiMCAqICh0IC09IGI1KSAqIHQgKyBiNyA6IGIwICogKHQgLT0gYjgpICogdCArIGI5OwogICAgfQoKICAgIGZ1bmN0aW9uIGJvdW5jZUluT3V0KHQpIHsKICAgICAgcmV0dXJuICgodCAqPSAyKSA8PSAxID8gMSAtIGJvdW5jZU91dCgxIC0gdCkgOiBib3VuY2VPdXQodCAtIDEpICsgMSkgLyAyOwogICAgfQoKICAgIHZhciBvdmVyc2hvb3QgPSAxLjcwMTU4OwoKICAgIHZhciBiYWNrSW4gPSAoZnVuY3Rpb24gY3VzdG9tKHMpIHsKICAgICAgcyA9ICtzOwoKICAgICAgZnVuY3Rpb24gYmFja0luKHQpIHsKICAgICAgICByZXR1cm4gdCAqIHQgKiAoKHMgKyAxKSAqIHQgLSBzKTsKICAgICAgfQoKICAgICAgYmFja0luLm92ZXJzaG9vdCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBiYWNrSW47CiAgICB9KShvdmVyc2hvb3QpOwoKICAgIHZhciBiYWNrT3V0ID0gKGZ1bmN0aW9uIGN1c3RvbShzKSB7CiAgICAgIHMgPSArczsKCiAgICAgIGZ1bmN0aW9uIGJhY2tPdXQodCkgewogICAgICAgIHJldHVybiAtLXQgKiB0ICogKChzICsgMSkgKiB0ICsgcykgKyAxOwogICAgICB9CgogICAgICBiYWNrT3V0Lm92ZXJzaG9vdCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBiYWNrT3V0OwogICAgfSkob3ZlcnNob290KTsKCiAgICB2YXIgYmFja0luT3V0ID0gKGZ1bmN0aW9uIGN1c3RvbShzKSB7CiAgICAgIHMgPSArczsKCiAgICAgIGZ1bmN0aW9uIGJhY2tJbk91dCh0KSB7CiAgICAgICAgcmV0dXJuICgodCAqPSAyKSA8IDEgPyB0ICogdCAqICgocyArIDEpICogdCAtIHMpIDogKHQgLT0gMikgKiB0ICogKChzICsgMSkgKiB0ICsgcykgKyAyKSAvIDI7CiAgICAgIH0KCiAgICAgIGJhY2tJbk91dC5vdmVyc2hvb3QgPSBjdXN0b207CgogICAgICByZXR1cm4gYmFja0luT3V0OwogICAgfSkob3ZlcnNob290KTsKCiAgICB2YXIgdGF1ID0gMiAqIE1hdGguUEksCiAgICAgICAgYW1wbGl0dWRlID0gMSwKICAgICAgICBwZXJpb2QgPSAwLjM7CgogICAgdmFyIGVsYXN0aWNJbiA9IChmdW5jdGlvbiBjdXN0b20oYSwgcCkgewogICAgICB2YXIgcyA9IE1hdGguYXNpbigxIC8gKGEgPSBNYXRoLm1heCgxLCBhKSkpICogKHAgLz0gdGF1KTsKCiAgICAgIGZ1bmN0aW9uIGVsYXN0aWNJbih0KSB7CiAgICAgICAgcmV0dXJuIGEgKiBNYXRoLnBvdygyLCAxMCAqIC0tdCkgKiBNYXRoLnNpbigocyAtIHQpIC8gcCk7CiAgICAgIH0KCiAgICAgIGVsYXN0aWNJbi5hbXBsaXR1ZGUgPSBmdW5jdGlvbihhKSB7IHJldHVybiBjdXN0b20oYSwgcCAqIHRhdSk7IH07CiAgICAgIGVsYXN0aWNJbi5wZXJpb2QgPSBmdW5jdGlvbihwKSB7IHJldHVybiBjdXN0b20oYSwgcCk7IH07CgogICAgICByZXR1cm4gZWxhc3RpY0luOwogICAgfSkoYW1wbGl0dWRlLCBwZXJpb2QpOwoKICAgIHZhciBlbGFzdGljT3V0ID0gKGZ1bmN0aW9uIGN1c3RvbShhLCBwKSB7CiAgICAgIHZhciBzID0gTWF0aC5hc2luKDEgLyAoYSA9IE1hdGgubWF4KDEsIGEpKSkgKiAocCAvPSB0YXUpOwoKICAgICAgZnVuY3Rpb24gZWxhc3RpY091dCh0KSB7CiAgICAgICAgcmV0dXJuIDEgLSBhICogTWF0aC5wb3coMiwgLTEwICogKHQgPSArdCkpICogTWF0aC5zaW4oKHQgKyBzKSAvIHApOwogICAgICB9CgogICAgICBlbGFzdGljT3V0LmFtcGxpdHVkZSA9IGZ1bmN0aW9uKGEpIHsgcmV0dXJuIGN1c3RvbShhLCBwICogdGF1KTsgfTsKICAgICAgZWxhc3RpY091dC5wZXJpb2QgPSBmdW5jdGlvbihwKSB7IHJldHVybiBjdXN0b20oYSwgcCk7IH07CgogICAgICByZXR1cm4gZWxhc3RpY091dDsKICAgIH0pKGFtcGxpdHVkZSwgcGVyaW9kKTsKCiAgICB2YXIgZWxhc3RpY0luT3V0ID0gKGZ1bmN0aW9uIGN1c3RvbShhLCBwKSB7CiAgICAgIHZhciBzID0gTWF0aC5hc2luKDEgLyAoYSA9IE1hdGgubWF4KDEsIGEpKSkgKiAocCAvPSB0YXUpOwoKICAgICAgZnVuY3Rpb24gZWxhc3RpY0luT3V0KHQpIHsKICAgICAgICByZXR1cm4gKCh0ID0gdCAqIDIgLSAxKSA8IDAKICAgICAgICAgICAgPyBhICogTWF0aC5wb3coMiwgMTAgKiB0KSAqIE1hdGguc2luKChzIC0gdCkgLyBwKQogICAgICAgICAgICA6IDIgLSBhICogTWF0aC5wb3coMiwgLTEwICogdCkgKiBNYXRoLnNpbigocyArIHQpIC8gcCkpIC8gMjsKICAgICAgfQoKICAgICAgZWxhc3RpY0luT3V0LmFtcGxpdHVkZSA9IGZ1bmN0aW9uKGEpIHsgcmV0dXJuIGN1c3RvbShhLCBwICogdGF1KTsgfTsKICAgICAgZWxhc3RpY0luT3V0LnBlcmlvZCA9IGZ1bmN0aW9uKHApIHsgcmV0dXJuIGN1c3RvbShhLCBwKTsgfTsKCiAgICAgIHJldHVybiBlbGFzdGljSW5PdXQ7CiAgICB9KShhbXBsaXR1ZGUsIHBlcmlvZCk7CgogICAgdmFyIHNyYyA9IC8qI19fUFVSRV9fKi9PYmplY3QuZnJlZXplKHsKICAgICAgICBfX3Byb3RvX186IG51bGwsCiAgICAgICAgZWFzZUxpbmVhcjogbGluZWFyJDEsCiAgICAgICAgZWFzZVF1YWQ6IHF1YWRJbk91dCwKICAgICAgICBlYXNlUXVhZEluOiBxdWFkSW4sCiAgICAgICAgZWFzZVF1YWRPdXQ6IHF1YWRPdXQsCiAgICAgICAgZWFzZVF1YWRJbk91dDogcXVhZEluT3V0LAogICAgICAgIGVhc2VDdWJpYzogY3ViaWNJbk91dCwKICAgICAgICBlYXNlQ3ViaWNJbjogY3ViaWNJbiwKICAgICAgICBlYXNlQ3ViaWNPdXQ6IGN1YmljT3V0LAogICAgICAgIGVhc2VDdWJpY0luT3V0OiBjdWJpY0luT3V0LAogICAgICAgIGVhc2VQb2x5OiBwb2x5SW5PdXQsCiAgICAgICAgZWFzZVBvbHlJbjogcG9seUluLAogICAgICAgIGVhc2VQb2x5T3V0OiBwb2x5T3V0LAogICAgICAgIGVhc2VQb2x5SW5PdXQ6IHBvbHlJbk91dCwKICAgICAgICBlYXNlU2luOiBzaW5Jbk91dCwKICAgICAgICBlYXNlU2luSW46IHNpbkluLAogICAgICAgIGVhc2VTaW5PdXQ6IHNpbk91dCwKICAgICAgICBlYXNlU2luSW5PdXQ6IHNpbkluT3V0LAogICAgICAgIGVhc2VFeHA6IGV4cEluT3V0LAogICAgICAgIGVhc2VFeHBJbjogZXhwSW4sCiAgICAgICAgZWFzZUV4cE91dDogZXhwT3V0LAogICAgICAgIGVhc2VFeHBJbk91dDogZXhwSW5PdXQsCiAgICAgICAgZWFzZUNpcmNsZTogY2lyY2xlSW5PdXQsCiAgICAgICAgZWFzZUNpcmNsZUluOiBjaXJjbGVJbiwKICAgICAgICBlYXNlQ2lyY2xlT3V0OiBjaXJjbGVPdXQsCiAgICAgICAgZWFzZUNpcmNsZUluT3V0OiBjaXJjbGVJbk91dCwKICAgICAgICBlYXNlQm91bmNlOiBib3VuY2VPdXQsCiAgICAgICAgZWFzZUJvdW5jZUluOiBib3VuY2VJbiwKICAgICAgICBlYXNlQm91bmNlT3V0OiBib3VuY2VPdXQsCiAgICAgICAgZWFzZUJvdW5jZUluT3V0OiBib3VuY2VJbk91dCwKICAgICAgICBlYXNlQmFjazogYmFja0luT3V0LAogICAgICAgIGVhc2VCYWNrSW46IGJhY2tJbiwKICAgICAgICBlYXNlQmFja091dDogYmFja091dCwKICAgICAgICBlYXNlQmFja0luT3V0OiBiYWNrSW5PdXQsCiAgICAgICAgZWFzZUVsYXN0aWM6IGVsYXN0aWNPdXQsCiAgICAgICAgZWFzZUVsYXN0aWNJbjogZWxhc3RpY0luLAogICAgICAgIGVhc2VFbGFzdGljT3V0OiBlbGFzdGljT3V0LAogICAgICAgIGVhc2VFbGFzdGljSW5PdXQ6IGVsYXN0aWNJbk91dAogICAgfSk7CgogICAgdmFyIGRlZmF1bHRUaW1pbmcgPSB7CiAgICAgIHRpbWU6IG51bGwsIC8vIFNldCBvbiB1c2UuCiAgICAgIGRlbGF5OiAwLAogICAgICBkdXJhdGlvbjogMjUwLAogICAgICBlYXNlOiBjdWJpY0luT3V0CiAgICB9OwoKICAgIGZ1bmN0aW9uIGluaGVyaXQobm9kZSwgaWQpIHsKICAgICAgdmFyIHRpbWluZzsKICAgICAgd2hpbGUgKCEodGltaW5nID0gbm9kZS5fX3RyYW5zaXRpb24pIHx8ICEodGltaW5nID0gdGltaW5nW2lkXSkpIHsKICAgICAgICBpZiAoIShub2RlID0gbm9kZS5wYXJlbnROb2RlKSkgewogICAgICAgICAgcmV0dXJuIGRlZmF1bHRUaW1pbmcudGltZSA9IG5vdygpLCBkZWZhdWx0VGltaW5nOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGltaW5nOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl90cmFuc2l0aW9uKG5hbWUpIHsKICAgICAgdmFyIGlkLAogICAgICAgICAgdGltaW5nOwoKICAgICAgaWYgKG5hbWUgaW5zdGFuY2VvZiBUcmFuc2l0aW9uKSB7CiAgICAgICAgaWQgPSBuYW1lLl9pZCwgbmFtZSA9IG5hbWUuX25hbWU7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgaWQgPSBuZXdJZCgpLCAodGltaW5nID0gZGVmYXVsdFRpbWluZykudGltZSA9IG5vdygpLCBuYW1lID0gbmFtZSA9PSBudWxsID8gbnVsbCA6IG5hbWUgKyAiIjsKICAgICAgfQoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc2NoZWR1bGUkMShub2RlLCBuYW1lLCBpZCwgaSwgZ3JvdXAsIHRpbWluZyB8fCBpbmhlcml0KG5vZGUsIGlkKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24oZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCBuYW1lLCBpZCk7CiAgICB9CgogICAgc2VsZWN0aW9uLnByb3RvdHlwZS5pbnRlcnJ1cHQgPSBzZWxlY3Rpb25faW50ZXJydXB0OwogICAgc2VsZWN0aW9uLnByb3RvdHlwZS50cmFuc2l0aW9uID0gc2VsZWN0aW9uX3RyYW5zaXRpb247CgogICAgdmFyIHJvb3QkMiA9IFtudWxsXTsKCiAgICBmdW5jdGlvbiBhY3RpdmUobm9kZSwgbmFtZSkgewogICAgICB2YXIgc2NoZWR1bGVzID0gbm9kZS5fX3RyYW5zaXRpb24sCiAgICAgICAgICBzY2hlZHVsZSwKICAgICAgICAgIGk7CgogICAgICBpZiAoc2NoZWR1bGVzKSB7CiAgICAgICAgbmFtZSA9IG5hbWUgPT0gbnVsbCA/IG51bGwgOiBuYW1lICsgIiI7CiAgICAgICAgZm9yIChpIGluIHNjaGVkdWxlcykgewogICAgICAgICAgaWYgKChzY2hlZHVsZSA9IHNjaGVkdWxlc1tpXSkuc3RhdGUgPiBTQ0hFRFVMRUQgJiYgc2NoZWR1bGUubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24oW1tub2RlXV0sIHJvb3QkMiwgbmFtZSwgK2kpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkNCh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBCcnVzaEV2ZW50KHRhcmdldCwgdHlwZSwgc2VsZWN0aW9uKSB7CiAgICAgIHRoaXMudGFyZ2V0ID0gdGFyZ2V0OwogICAgICB0aGlzLnR5cGUgPSB0eXBlOwogICAgICB0aGlzLnNlbGVjdGlvbiA9IHNlbGVjdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBub3Byb3BhZ2F0aW9uJDEoKSB7CiAgICAgIGV2ZW50LnN0b3BJbW1lZGlhdGVQcm9wYWdhdGlvbigpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZXZlbnQkMSgpIHsKICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTsKICAgICAgZXZlbnQuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgdmFyIE1PREVfRFJBRyA9IHtuYW1lOiAiZHJhZyJ9LAogICAgICAgIE1PREVfU1BBQ0UgPSB7bmFtZTogInNwYWNlIn0sCiAgICAgICAgTU9ERV9IQU5ETEUgPSB7bmFtZTogImhhbmRsZSJ9LAogICAgICAgIE1PREVfQ0VOVEVSID0ge25hbWU6ICJjZW50ZXIifTsKCiAgICBmdW5jdGlvbiBudW1iZXIxKGUpIHsKICAgICAgcmV0dXJuIFsrZVswXSwgK2VbMV1dOwogICAgfQoKICAgIGZ1bmN0aW9uIG51bWJlcjIoZSkgewogICAgICByZXR1cm4gW251bWJlcjEoZVswXSksIG51bWJlcjEoZVsxXSldOwogICAgfQoKICAgIGZ1bmN0aW9uIHRvdWNoZXIoaWRlbnRpZmllcikgewogICAgICByZXR1cm4gZnVuY3Rpb24odGFyZ2V0KSB7CiAgICAgICAgcmV0dXJuIHRvdWNoKHRhcmdldCwgZXZlbnQudG91Y2hlcywgaWRlbnRpZmllcik7CiAgICAgIH07CiAgICB9CgogICAgdmFyIFggPSB7CiAgICAgIG5hbWU6ICJ4IiwKICAgICAgaGFuZGxlczogWyJ3IiwgImUiXS5tYXAodHlwZSksCiAgICAgIGlucHV0OiBmdW5jdGlvbih4LCBlKSB7IHJldHVybiB4ID09IG51bGwgPyBudWxsIDogW1sreFswXSwgZVswXVsxXV0sIFsreFsxXSwgZVsxXVsxXV1dOyB9LAogICAgICBvdXRwdXQ6IGZ1bmN0aW9uKHh5KSB7IHJldHVybiB4eSAmJiBbeHlbMF1bMF0sIHh5WzFdWzBdXTsgfQogICAgfTsKCiAgICB2YXIgWSA9IHsKICAgICAgbmFtZTogInkiLAogICAgICBoYW5kbGVzOiBbIm4iLCAicyJdLm1hcCh0eXBlKSwKICAgICAgaW5wdXQ6IGZ1bmN0aW9uKHksIGUpIHsgcmV0dXJuIHkgPT0gbnVsbCA/IG51bGwgOiBbW2VbMF1bMF0sICt5WzBdXSwgW2VbMV1bMF0sICt5WzFdXV07IH0sCiAgICAgIG91dHB1dDogZnVuY3Rpb24oeHkpIHsgcmV0dXJuIHh5ICYmIFt4eVswXVsxXSwgeHlbMV1bMV1dOyB9CiAgICB9OwoKICAgIHZhciBYWSA9IHsKICAgICAgbmFtZTogInh5IiwKICAgICAgaGFuZGxlczogWyJuIiwgInciLCAiZSIsICJzIiwgIm53IiwgIm5lIiwgInN3IiwgInNlIl0ubWFwKHR5cGUpLAogICAgICBpbnB1dDogZnVuY3Rpb24oeHkpIHsgcmV0dXJuIHh5ID09IG51bGwgPyBudWxsIDogbnVtYmVyMih4eSk7IH0sCiAgICAgIG91dHB1dDogZnVuY3Rpb24oeHkpIHsgcmV0dXJuIHh5OyB9CiAgICB9OwoKICAgIHZhciBjdXJzb3JzID0gewogICAgICBvdmVybGF5OiAiY3Jvc3NoYWlyIiwKICAgICAgc2VsZWN0aW9uOiAibW92ZSIsCiAgICAgIG46ICJucy1yZXNpemUiLAogICAgICBlOiAiZXctcmVzaXplIiwKICAgICAgczogIm5zLXJlc2l6ZSIsCiAgICAgIHc6ICJldy1yZXNpemUiLAogICAgICBudzogIm53c2UtcmVzaXplIiwKICAgICAgbmU6ICJuZXN3LXJlc2l6ZSIsCiAgICAgIHNlOiAibndzZS1yZXNpemUiLAogICAgICBzdzogIm5lc3ctcmVzaXplIgogICAgfTsKCiAgICB2YXIgZmxpcFggPSB7CiAgICAgIGU6ICJ3IiwKICAgICAgdzogImUiLAogICAgICBudzogIm5lIiwKICAgICAgbmU6ICJudyIsCiAgICAgIHNlOiAic3ciLAogICAgICBzdzogInNlIgogICAgfTsKCiAgICB2YXIgZmxpcFkgPSB7CiAgICAgIG46ICJzIiwKICAgICAgczogIm4iLAogICAgICBudzogInN3IiwKICAgICAgbmU6ICJzZSIsCiAgICAgIHNlOiAibmUiLAogICAgICBzdzogIm53IgogICAgfTsKCiAgICB2YXIgc2lnbnNYID0gewogICAgICBvdmVybGF5OiArMSwKICAgICAgc2VsZWN0aW9uOiArMSwKICAgICAgbjogbnVsbCwKICAgICAgZTogKzEsCiAgICAgIHM6IG51bGwsCiAgICAgIHc6IC0xLAogICAgICBudzogLTEsCiAgICAgIG5lOiArMSwKICAgICAgc2U6ICsxLAogICAgICBzdzogLTEKICAgIH07CgogICAgdmFyIHNpZ25zWSA9IHsKICAgICAgb3ZlcmxheTogKzEsCiAgICAgIHNlbGVjdGlvbjogKzEsCiAgICAgIG46IC0xLAogICAgICBlOiBudWxsLAogICAgICBzOiArMSwKICAgICAgdzogbnVsbCwKICAgICAgbnc6IC0xLAogICAgICBuZTogLTEsCiAgICAgIHNlOiArMSwKICAgICAgc3c6ICsxCiAgICB9OwoKICAgIGZ1bmN0aW9uIHR5cGUodCkgewogICAgICByZXR1cm4ge3R5cGU6IHR9OwogICAgfQoKICAgIC8vIElnbm9yZSByaWdodC1jbGljaywgc2luY2UgdGhhdCBzaG91bGQgb3BlbiB0aGUgY29udGV4dCBtZW51LgogICAgZnVuY3Rpb24gZGVmYXVsdEZpbHRlciQxKCkgewogICAgICByZXR1cm4gIWV2ZW50LmN0cmxLZXkgJiYgIWV2ZW50LmJ1dHRvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0RXh0ZW50KCkgewogICAgICB2YXIgc3ZnID0gdGhpcy5vd25lclNWR0VsZW1lbnQgfHwgdGhpczsKICAgICAgaWYgKHN2Zy5oYXNBdHRyaWJ1dGUoInZpZXdCb3giKSkgewogICAgICAgIHN2ZyA9IHN2Zy52aWV3Qm94LmJhc2VWYWw7CiAgICAgICAgcmV0dXJuIFtbc3ZnLngsIHN2Zy55XSwgW3N2Zy54ICsgc3ZnLndpZHRoLCBzdmcueSArIHN2Zy5oZWlnaHRdXTsKICAgICAgfQogICAgICByZXR1cm4gW1swLCAwXSwgW3N2Zy53aWR0aC5iYXNlVmFsLnZhbHVlLCBzdmcuaGVpZ2h0LmJhc2VWYWwudmFsdWVdXTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0VG91Y2hhYmxlJDEoKSB7CiAgICAgIHJldHVybiBuYXZpZ2F0b3IubWF4VG91Y2hQb2ludHMgfHwgKCJvbnRvdWNoc3RhcnQiIGluIHRoaXMpOwogICAgfQoKICAgIC8vIExpa2UgZDMubG9jYWwsIGJ1dCB3aXRoIHRoZSBuYW1lIOKAnF9fYnJ1c2jigJ0gcmF0aGVyIHRoYW4gYXV0by1nZW5lcmF0ZWQuCiAgICBmdW5jdGlvbiBsb2NhbCQxKG5vZGUpIHsKICAgICAgd2hpbGUgKCFub2RlLl9fYnJ1c2gpIGlmICghKG5vZGUgPSBub2RlLnBhcmVudE5vZGUpKSByZXR1cm47CiAgICAgIHJldHVybiBub2RlLl9fYnJ1c2g7CiAgICB9CgogICAgZnVuY3Rpb24gZW1wdHkkMShleHRlbnQpIHsKICAgICAgcmV0dXJuIGV4dGVudFswXVswXSA9PT0gZXh0ZW50WzFdWzBdCiAgICAgICAgICB8fCBleHRlbnRbMF1bMV0gPT09IGV4dGVudFsxXVsxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBicnVzaFNlbGVjdGlvbihub2RlKSB7CiAgICAgIHZhciBzdGF0ZSA9IG5vZGUuX19icnVzaDsKICAgICAgcmV0dXJuIHN0YXRlID8gc3RhdGUuZGltLm91dHB1dChzdGF0ZS5zZWxlY3Rpb24pIDogbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBicnVzaFgoKSB7CiAgICAgIHJldHVybiBicnVzaCQxKFgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJydXNoWSgpIHsKICAgICAgcmV0dXJuIGJydXNoJDEoWSk7CiAgICB9CgogICAgZnVuY3Rpb24gYnJ1c2goKSB7CiAgICAgIHJldHVybiBicnVzaCQxKFhZKTsKICAgIH0KCiAgICBmdW5jdGlvbiBicnVzaCQxKGRpbSkgewogICAgICB2YXIgZXh0ZW50ID0gZGVmYXVsdEV4dGVudCwKICAgICAgICAgIGZpbHRlciA9IGRlZmF1bHRGaWx0ZXIkMSwKICAgICAgICAgIHRvdWNoYWJsZSA9IGRlZmF1bHRUb3VjaGFibGUkMSwKICAgICAgICAgIGtleXMgPSB0cnVlLAogICAgICAgICAgbGlzdGVuZXJzID0gZGlzcGF0Y2goInN0YXJ0IiwgImJydXNoIiwgImVuZCIpLAogICAgICAgICAgaGFuZGxlU2l6ZSA9IDYsCiAgICAgICAgICB0b3VjaGVuZGluZzsKCiAgICAgIGZ1bmN0aW9uIGJydXNoKGdyb3VwKSB7CiAgICAgICAgdmFyIG92ZXJsYXkgPSBncm91cAogICAgICAgICAgICAucHJvcGVydHkoIl9fYnJ1c2giLCBpbml0aWFsaXplKQogICAgICAgICAgLnNlbGVjdEFsbCgiLm92ZXJsYXkiKQogICAgICAgICAgLmRhdGEoW3R5cGUoIm92ZXJsYXkiKV0pOwoKICAgICAgICBvdmVybGF5LmVudGVyKCkuYXBwZW5kKCJyZWN0IikKICAgICAgICAgICAgLmF0dHIoImNsYXNzIiwgIm92ZXJsYXkiKQogICAgICAgICAgICAuYXR0cigicG9pbnRlci1ldmVudHMiLCAiYWxsIikKICAgICAgICAgICAgLmF0dHIoImN1cnNvciIsIGN1cnNvcnMub3ZlcmxheSkKICAgICAgICAgIC5tZXJnZShvdmVybGF5KQogICAgICAgICAgICAuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICAgICAgICB2YXIgZXh0ZW50ID0gbG9jYWwkMSh0aGlzKS5leHRlbnQ7CiAgICAgICAgICAgICAgc2VsZWN0KHRoaXMpCiAgICAgICAgICAgICAgICAgIC5hdHRyKCJ4IiwgZXh0ZW50WzBdWzBdKQogICAgICAgICAgICAgICAgICAuYXR0cigieSIsIGV4dGVudFswXVsxXSkKICAgICAgICAgICAgICAgICAgLmF0dHIoIndpZHRoIiwgZXh0ZW50WzFdWzBdIC0gZXh0ZW50WzBdWzBdKQogICAgICAgICAgICAgICAgICAuYXR0cigiaGVpZ2h0IiwgZXh0ZW50WzFdWzFdIC0gZXh0ZW50WzBdWzFdKTsKICAgICAgICAgICAgfSk7CgogICAgICAgIGdyb3VwLnNlbGVjdEFsbCgiLnNlbGVjdGlvbiIpCiAgICAgICAgICAuZGF0YShbdHlwZSgic2VsZWN0aW9uIildKQogICAgICAgICAgLmVudGVyKCkuYXBwZW5kKCJyZWN0IikKICAgICAgICAgICAgLmF0dHIoImNsYXNzIiwgInNlbGVjdGlvbiIpCiAgICAgICAgICAgIC5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzLnNlbGVjdGlvbikKICAgICAgICAgICAgLmF0dHIoImZpbGwiLCAiIzc3NyIpCiAgICAgICAgICAgIC5hdHRyKCJmaWxsLW9wYWNpdHkiLCAwLjMpCiAgICAgICAgICAgIC5hdHRyKCJzdHJva2UiLCAiI2ZmZiIpCiAgICAgICAgICAgIC5hdHRyKCJzaGFwZS1yZW5kZXJpbmciLCAiY3Jpc3BFZGdlcyIpOwoKICAgICAgICB2YXIgaGFuZGxlID0gZ3JvdXAuc2VsZWN0QWxsKCIuaGFuZGxlIikKICAgICAgICAgIC5kYXRhKGRpbS5oYW5kbGVzLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGU7IH0pOwoKICAgICAgICBoYW5kbGUuZXhpdCgpLnJlbW92ZSgpOwoKICAgICAgICBoYW5kbGUuZW50ZXIoKS5hcHBlbmQoInJlY3QiKQogICAgICAgICAgICAuYXR0cigiY2xhc3MiLCBmdW5jdGlvbihkKSB7IHJldHVybiAiaGFuZGxlIGhhbmRsZS0tIiArIGQudHlwZTsgfSkKICAgICAgICAgICAgLmF0dHIoImN1cnNvciIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGN1cnNvcnNbZC50eXBlXTsgfSk7CgogICAgICAgIGdyb3VwCiAgICAgICAgICAgIC5lYWNoKHJlZHJhdykKICAgICAgICAgICAgLmF0dHIoImZpbGwiLCAibm9uZSIpCiAgICAgICAgICAgIC5hdHRyKCJwb2ludGVyLWV2ZW50cyIsICJhbGwiKQogICAgICAgICAgICAub24oIm1vdXNlZG93bi5icnVzaCIsIHN0YXJ0ZWQpCiAgICAgICAgICAuZmlsdGVyKHRvdWNoYWJsZSkKICAgICAgICAgICAgLm9uKCJ0b3VjaHN0YXJ0LmJydXNoIiwgc3RhcnRlZCkKICAgICAgICAgICAgLm9uKCJ0b3VjaG1vdmUuYnJ1c2giLCB0b3VjaG1vdmVkKQogICAgICAgICAgICAub24oInRvdWNoZW5kLmJydXNoIHRvdWNoY2FuY2VsLmJydXNoIiwgdG91Y2hlbmRlZCkKICAgICAgICAgICAgLnN0eWxlKCJ0b3VjaC1hY3Rpb24iLCAibm9uZSIpCiAgICAgICAgICAgIC5zdHlsZSgiLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yIiwgInJnYmEoMCwwLDAsMCkiKTsKICAgICAgfQoKICAgICAgYnJ1c2gubW92ZSA9IGZ1bmN0aW9uKGdyb3VwLCBzZWxlY3Rpb24pIHsKICAgICAgICBpZiAoZ3JvdXAuc2VsZWN0aW9uKSB7CiAgICAgICAgICBncm91cAogICAgICAgICAgICAgIC5vbigic3RhcnQuYnJ1c2giLCBmdW5jdGlvbigpIHsgZW1pdHRlcih0aGlzLCBhcmd1bWVudHMpLmJlZm9yZXN0YXJ0KCkuc3RhcnQoKTsgfSkKICAgICAgICAgICAgICAub24oImludGVycnVwdC5icnVzaCBlbmQuYnJ1c2giLCBmdW5jdGlvbigpIHsgZW1pdHRlcih0aGlzLCBhcmd1bWVudHMpLmVuZCgpOyB9KQogICAgICAgICAgICAgIC50d2VlbigiYnJ1c2giLCBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICAgIHZhciB0aGF0ID0gdGhpcywKICAgICAgICAgICAgICAgICAgICBzdGF0ZSA9IHRoYXQuX19icnVzaCwKICAgICAgICAgICAgICAgICAgICBlbWl0ID0gZW1pdHRlcih0aGF0LCBhcmd1bWVudHMpLAogICAgICAgICAgICAgICAgICAgIHNlbGVjdGlvbjAgPSBzdGF0ZS5zZWxlY3Rpb24sCiAgICAgICAgICAgICAgICAgICAgc2VsZWN0aW9uMSA9IGRpbS5pbnB1dCh0eXBlb2Ygc2VsZWN0aW9uID09PSAiZnVuY3Rpb24iID8gc2VsZWN0aW9uLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiBzZWxlY3Rpb24sIHN0YXRlLmV4dGVudCksCiAgICAgICAgICAgICAgICAgICAgaSA9IGludGVycG9sYXRlVmFsdWUoc2VsZWN0aW9uMCwgc2VsZWN0aW9uMSk7CgogICAgICAgICAgICAgICAgZnVuY3Rpb24gdHdlZW4odCkgewogICAgICAgICAgICAgICAgICBzdGF0ZS5zZWxlY3Rpb24gPSB0ID09PSAxICYmIHNlbGVjdGlvbjEgPT09IG51bGwgPyBudWxsIDogaSh0KTsKICAgICAgICAgICAgICAgICAgcmVkcmF3LmNhbGwodGhhdCk7CiAgICAgICAgICAgICAgICAgIGVtaXQuYnJ1c2goKTsKICAgICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgICByZXR1cm4gc2VsZWN0aW9uMCAhPT0gbnVsbCAmJiBzZWxlY3Rpb24xICE9PSBudWxsID8gdHdlZW4gOiB0d2VlbigxKTsKICAgICAgICAgICAgICB9KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZ3JvdXAKICAgICAgICAgICAgICAuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICAgICAgICAgIHZhciB0aGF0ID0gdGhpcywKICAgICAgICAgICAgICAgICAgICBhcmdzID0gYXJndW1lbnRzLAogICAgICAgICAgICAgICAgICAgIHN0YXRlID0gdGhhdC5fX2JydXNoLAogICAgICAgICAgICAgICAgICAgIHNlbGVjdGlvbjEgPSBkaW0uaW5wdXQodHlwZW9mIHNlbGVjdGlvbiA9PT0gImZ1bmN0aW9uIiA/IHNlbGVjdGlvbi5hcHBseSh0aGF0LCBhcmdzKSA6IHNlbGVjdGlvbiwgc3RhdGUuZXh0ZW50KSwKICAgICAgICAgICAgICAgICAgICBlbWl0ID0gZW1pdHRlcih0aGF0LCBhcmdzKS5iZWZvcmVzdGFydCgpOwoKICAgICAgICAgICAgICAgIGludGVycnVwdCh0aGF0KTsKICAgICAgICAgICAgICAgIHN0YXRlLnNlbGVjdGlvbiA9IHNlbGVjdGlvbjEgPT09IG51bGwgPyBudWxsIDogc2VsZWN0aW9uMTsKICAgICAgICAgICAgICAgIHJlZHJhdy5jYWxsKHRoYXQpOwogICAgICAgICAgICAgICAgZW1pdC5zdGFydCgpLmJydXNoKCkuZW5kKCk7CiAgICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9OwoKICAgICAgYnJ1c2guY2xlYXIgPSBmdW5jdGlvbihncm91cCkgewogICAgICAgIGJydXNoLm1vdmUoZ3JvdXAsIG51bGwpOwogICAgICB9OwoKICAgICAgZnVuY3Rpb24gcmVkcmF3KCkgewogICAgICAgIHZhciBncm91cCA9IHNlbGVjdCh0aGlzKSwKICAgICAgICAgICAgc2VsZWN0aW9uID0gbG9jYWwkMSh0aGlzKS5zZWxlY3Rpb247CgogICAgICAgIGlmIChzZWxlY3Rpb24pIHsKICAgICAgICAgIGdyb3VwLnNlbGVjdEFsbCgiLnNlbGVjdGlvbiIpCiAgICAgICAgICAgICAgLnN0eWxlKCJkaXNwbGF5IiwgbnVsbCkKICAgICAgICAgICAgICAuYXR0cigieCIsIHNlbGVjdGlvblswXVswXSkKICAgICAgICAgICAgICAuYXR0cigieSIsIHNlbGVjdGlvblswXVsxXSkKICAgICAgICAgICAgICAuYXR0cigid2lkdGgiLCBzZWxlY3Rpb25bMV1bMF0gLSBzZWxlY3Rpb25bMF1bMF0pCiAgICAgICAgICAgICAgLmF0dHIoImhlaWdodCIsIHNlbGVjdGlvblsxXVsxXSAtIHNlbGVjdGlvblswXVsxXSk7CgogICAgICAgICAgZ3JvdXAuc2VsZWN0QWxsKCIuaGFuZGxlIikKICAgICAgICAgICAgICAuc3R5bGUoImRpc3BsYXkiLCBudWxsKQogICAgICAgICAgICAgIC5hdHRyKCJ4IiwgZnVuY3Rpb24oZCkgeyByZXR1cm4gZC50eXBlW2QudHlwZS5sZW5ndGggLSAxXSA9PT0gImUiID8gc2VsZWN0aW9uWzFdWzBdIC0gaGFuZGxlU2l6ZSAvIDIgOiBzZWxlY3Rpb25bMF1bMF0gLSBoYW5kbGVTaXplIC8gMjsgfSkKICAgICAgICAgICAgICAuYXR0cigieSIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGQudHlwZVswXSA9PT0gInMiID8gc2VsZWN0aW9uWzFdWzFdIC0gaGFuZGxlU2l6ZSAvIDIgOiBzZWxlY3Rpb25bMF1bMV0gLSBoYW5kbGVTaXplIC8gMjsgfSkKICAgICAgICAgICAgICAuYXR0cigid2lkdGgiLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGUgPT09ICJuIiB8fCBkLnR5cGUgPT09ICJzIiA/IHNlbGVjdGlvblsxXVswXSAtIHNlbGVjdGlvblswXVswXSArIGhhbmRsZVNpemUgOiBoYW5kbGVTaXplOyB9KQogICAgICAgICAgICAgIC5hdHRyKCJoZWlnaHQiLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGUgPT09ICJlIiB8fCBkLnR5cGUgPT09ICJ3IiA/IHNlbGVjdGlvblsxXVsxXSAtIHNlbGVjdGlvblswXVsxXSArIGhhbmRsZVNpemUgOiBoYW5kbGVTaXplOyB9KTsKICAgICAgICB9CgogICAgICAgIGVsc2UgewogICAgICAgICAgZ3JvdXAuc2VsZWN0QWxsKCIuc2VsZWN0aW9uLC5oYW5kbGUiKQogICAgICAgICAgICAgIC5zdHlsZSgiZGlzcGxheSIsICJub25lIikKICAgICAgICAgICAgICAuYXR0cigieCIsIG51bGwpCiAgICAgICAgICAgICAgLmF0dHIoInkiLCBudWxsKQogICAgICAgICAgICAgIC5hdHRyKCJ3aWR0aCIsIG51bGwpCiAgICAgICAgICAgICAgLmF0dHIoImhlaWdodCIsIG51bGwpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gZW1pdHRlcih0aGF0LCBhcmdzLCBjbGVhbikgewogICAgICAgIHJldHVybiAoIWNsZWFuICYmIHRoYXQuX19icnVzaC5lbWl0dGVyKSB8fCBuZXcgRW1pdHRlcih0aGF0LCBhcmdzKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gRW1pdHRlcih0aGF0LCBhcmdzKSB7CiAgICAgICAgdGhpcy50aGF0ID0gdGhhdDsKICAgICAgICB0aGlzLmFyZ3MgPSBhcmdzOwogICAgICAgIHRoaXMuc3RhdGUgPSB0aGF0Ll9fYnJ1c2g7CiAgICAgICAgdGhpcy5hY3RpdmUgPSAwOwogICAgICB9CgogICAgICBFbWl0dGVyLnByb3RvdHlwZSA9IHsKICAgICAgICBiZWZvcmVzdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoKyt0aGlzLmFjdGl2ZSA9PT0gMSkgdGhpcy5zdGF0ZS5lbWl0dGVyID0gdGhpcywgdGhpcy5zdGFydGluZyA9IHRydWU7CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIHN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIGlmICh0aGlzLnN0YXJ0aW5nKSB0aGlzLnN0YXJ0aW5nID0gZmFsc2UsIHRoaXMuZW1pdCgic3RhcnQiKTsKICAgICAgICAgIGVsc2UgdGhpcy5lbWl0KCJicnVzaCIpOwogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfSwKICAgICAgICBicnVzaDogZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLmVtaXQoImJydXNoIik7CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIGVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoLS10aGlzLmFjdGl2ZSA9PT0gMCkgZGVsZXRlIHRoaXMuc3RhdGUuZW1pdHRlciwgdGhpcy5lbWl0KCJlbmQiKTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0sCiAgICAgICAgZW1pdDogZnVuY3Rpb24odHlwZSkgewogICAgICAgICAgY3VzdG9tRXZlbnQobmV3IEJydXNoRXZlbnQoYnJ1c2gsIHR5cGUsIGRpbS5vdXRwdXQodGhpcy5zdGF0ZS5zZWxlY3Rpb24pKSwgbGlzdGVuZXJzLmFwcGx5LCBsaXN0ZW5lcnMsIFt0eXBlLCB0aGlzLnRoYXQsIHRoaXMuYXJnc10pOwogICAgICAgIH0KICAgICAgfTsKCiAgICAgIGZ1bmN0aW9uIHN0YXJ0ZWQoKSB7CiAgICAgICAgaWYgKHRvdWNoZW5kaW5nICYmICFldmVudC50b3VjaGVzKSByZXR1cm47CiAgICAgICAgaWYgKCFmaWx0ZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgcmV0dXJuOwoKICAgICAgICB2YXIgdGhhdCA9IHRoaXMsCiAgICAgICAgICAgIHR5cGUgPSBldmVudC50YXJnZXQuX19kYXRhX18udHlwZSwKICAgICAgICAgICAgbW9kZSA9IChrZXlzICYmIGV2ZW50Lm1ldGFLZXkgPyB0eXBlID0gIm92ZXJsYXkiIDogdHlwZSkgPT09ICJzZWxlY3Rpb24iID8gTU9ERV9EUkFHIDogKGtleXMgJiYgZXZlbnQuYWx0S2V5ID8gTU9ERV9DRU5URVIgOiBNT0RFX0hBTkRMRSksCiAgICAgICAgICAgIHNpZ25YID0gZGltID09PSBZID8gbnVsbCA6IHNpZ25zWFt0eXBlXSwKICAgICAgICAgICAgc2lnblkgPSBkaW0gPT09IFggPyBudWxsIDogc2lnbnNZW3R5cGVdLAogICAgICAgICAgICBzdGF0ZSA9IGxvY2FsJDEodGhhdCksCiAgICAgICAgICAgIGV4dGVudCA9IHN0YXRlLmV4dGVudCwKICAgICAgICAgICAgc2VsZWN0aW9uID0gc3RhdGUuc2VsZWN0aW9uLAogICAgICAgICAgICBXID0gZXh0ZW50WzBdWzBdLCB3MCwgdzEsCiAgICAgICAgICAgIE4gPSBleHRlbnRbMF1bMV0sIG4wLCBuMSwKICAgICAgICAgICAgRSA9IGV4dGVudFsxXVswXSwgZTAsIGUxLAogICAgICAgICAgICBTID0gZXh0ZW50WzFdWzFdLCBzMCwgczEsCiAgICAgICAgICAgIGR4ID0gMCwKICAgICAgICAgICAgZHkgPSAwLAogICAgICAgICAgICBtb3ZpbmcsCiAgICAgICAgICAgIHNoaWZ0aW5nID0gc2lnblggJiYgc2lnblkgJiYga2V5cyAmJiBldmVudC5zaGlmdEtleSwKICAgICAgICAgICAgbG9ja1gsCiAgICAgICAgICAgIGxvY2tZLAogICAgICAgICAgICBwb2ludGVyID0gZXZlbnQudG91Y2hlcyA/IHRvdWNoZXIoZXZlbnQuY2hhbmdlZFRvdWNoZXNbMF0uaWRlbnRpZmllcikgOiBtb3VzZSwKICAgICAgICAgICAgcG9pbnQwID0gcG9pbnRlcih0aGF0KSwKICAgICAgICAgICAgcG9pbnQgPSBwb2ludDAsCiAgICAgICAgICAgIGVtaXQgPSBlbWl0dGVyKHRoYXQsIGFyZ3VtZW50cywgdHJ1ZSkuYmVmb3Jlc3RhcnQoKTsKCiAgICAgICAgaWYgKHR5cGUgPT09ICJvdmVybGF5IikgewogICAgICAgICAgaWYgKHNlbGVjdGlvbikgbW92aW5nID0gdHJ1ZTsKICAgICAgICAgIHN0YXRlLnNlbGVjdGlvbiA9IHNlbGVjdGlvbiA9IFsKICAgICAgICAgICAgW3cwID0gZGltID09PSBZID8gVyA6IHBvaW50MFswXSwgbjAgPSBkaW0gPT09IFggPyBOIDogcG9pbnQwWzFdXSwKICAgICAgICAgICAgW2UwID0gZGltID09PSBZID8gRSA6IHcwLCBzMCA9IGRpbSA9PT0gWCA/IFMgOiBuMF0KICAgICAgICAgIF07CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHcwID0gc2VsZWN0aW9uWzBdWzBdOwogICAgICAgICAgbjAgPSBzZWxlY3Rpb25bMF1bMV07CiAgICAgICAgICBlMCA9IHNlbGVjdGlvblsxXVswXTsKICAgICAgICAgIHMwID0gc2VsZWN0aW9uWzFdWzFdOwogICAgICAgIH0KCiAgICAgICAgdzEgPSB3MDsKICAgICAgICBuMSA9IG4wOwogICAgICAgIGUxID0gZTA7CiAgICAgICAgczEgPSBzMDsKCiAgICAgICAgdmFyIGdyb3VwID0gc2VsZWN0KHRoYXQpCiAgICAgICAgICAgIC5hdHRyKCJwb2ludGVyLWV2ZW50cyIsICJub25lIik7CgogICAgICAgIHZhciBvdmVybGF5ID0gZ3JvdXAuc2VsZWN0QWxsKCIub3ZlcmxheSIpCiAgICAgICAgICAgIC5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzW3R5cGVdKTsKCiAgICAgICAgaWYgKGV2ZW50LnRvdWNoZXMpIHsKICAgICAgICAgIGVtaXQubW92ZWQgPSBtb3ZlZDsKICAgICAgICAgIGVtaXQuZW5kZWQgPSBlbmRlZDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFyIHZpZXcgPSBzZWxlY3QoZXZlbnQudmlldykKICAgICAgICAgICAgICAub24oIm1vdXNlbW92ZS5icnVzaCIsIG1vdmVkLCB0cnVlKQogICAgICAgICAgICAgIC5vbigibW91c2V1cC5icnVzaCIsIGVuZGVkLCB0cnVlKTsKICAgICAgICAgIGlmIChrZXlzKSB2aWV3CiAgICAgICAgICAgICAgLm9uKCJrZXlkb3duLmJydXNoIiwga2V5ZG93bmVkLCB0cnVlKQogICAgICAgICAgICAgIC5vbigia2V5dXAuYnJ1c2giLCBrZXl1cHBlZCwgdHJ1ZSk7CgogICAgICAgICAgZHJhZ0Rpc2FibGUoZXZlbnQudmlldyk7CiAgICAgICAgfQoKICAgICAgICBub3Byb3BhZ2F0aW9uJDEoKTsKICAgICAgICBpbnRlcnJ1cHQodGhhdCk7CiAgICAgICAgcmVkcmF3LmNhbGwodGhhdCk7CiAgICAgICAgZW1pdC5zdGFydCgpOwoKICAgICAgICBmdW5jdGlvbiBtb3ZlZCgpIHsKICAgICAgICAgIHZhciBwb2ludDEgPSBwb2ludGVyKHRoYXQpOwogICAgICAgICAgaWYgKHNoaWZ0aW5nICYmICFsb2NrWCAmJiAhbG9ja1kpIHsKICAgICAgICAgICAgaWYgKE1hdGguYWJzKHBvaW50MVswXSAtIHBvaW50WzBdKSA+IE1hdGguYWJzKHBvaW50MVsxXSAtIHBvaW50WzFdKSkgbG9ja1kgPSB0cnVlOwogICAgICAgICAgICBlbHNlIGxvY2tYID0gdHJ1ZTsKICAgICAgICAgIH0KICAgICAgICAgIHBvaW50ID0gcG9pbnQxOwogICAgICAgICAgbW92aW5nID0gdHJ1ZTsKICAgICAgICAgIG5vZXZlbnQkMSgpOwogICAgICAgICAgbW92ZSgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbW92ZSgpIHsKICAgICAgICAgIHZhciB0OwoKICAgICAgICAgIGR4ID0gcG9pbnRbMF0gLSBwb2ludDBbMF07CiAgICAgICAgICBkeSA9IHBvaW50WzFdIC0gcG9pbnQwWzFdOwoKICAgICAgICAgIHN3aXRjaCAobW9kZSkgewogICAgICAgICAgICBjYXNlIE1PREVfU1BBQ0U6CiAgICAgICAgICAgIGNhc2UgTU9ERV9EUkFHOiB7CiAgICAgICAgICAgICAgaWYgKHNpZ25YKSBkeCA9IE1hdGgubWF4KFcgLSB3MCwgTWF0aC5taW4oRSAtIGUwLCBkeCkpLCB3MSA9IHcwICsgZHgsIGUxID0gZTAgKyBkeDsKICAgICAgICAgICAgICBpZiAoc2lnblkpIGR5ID0gTWF0aC5tYXgoTiAtIG4wLCBNYXRoLm1pbihTIC0gczAsIGR5KSksIG4xID0gbjAgKyBkeSwgczEgPSBzMCArIGR5OwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgTU9ERV9IQU5ETEU6IHsKICAgICAgICAgICAgICBpZiAoc2lnblggPCAwKSBkeCA9IE1hdGgubWF4KFcgLSB3MCwgTWF0aC5taW4oRSAtIHcwLCBkeCkpLCB3MSA9IHcwICsgZHgsIGUxID0gZTA7CiAgICAgICAgICAgICAgZWxzZSBpZiAoc2lnblggPiAwKSBkeCA9IE1hdGgubWF4KFcgLSBlMCwgTWF0aC5taW4oRSAtIGUwLCBkeCkpLCB3MSA9IHcwLCBlMSA9IGUwICsgZHg7CiAgICAgICAgICAgICAgaWYgKHNpZ25ZIDwgMCkgZHkgPSBNYXRoLm1heChOIC0gbjAsIE1hdGgubWluKFMgLSBuMCwgZHkpKSwgbjEgPSBuMCArIGR5LCBzMSA9IHMwOwogICAgICAgICAgICAgIGVsc2UgaWYgKHNpZ25ZID4gMCkgZHkgPSBNYXRoLm1heChOIC0gczAsIE1hdGgubWluKFMgLSBzMCwgZHkpKSwgbjEgPSBuMCwgczEgPSBzMCArIGR5OwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgTU9ERV9DRU5URVI6IHsKICAgICAgICAgICAgICBpZiAoc2lnblgpIHcxID0gTWF0aC5tYXgoVywgTWF0aC5taW4oRSwgdzAgLSBkeCAqIHNpZ25YKSksIGUxID0gTWF0aC5tYXgoVywgTWF0aC5taW4oRSwgZTAgKyBkeCAqIHNpZ25YKSk7CiAgICAgICAgICAgICAgaWYgKHNpZ25ZKSBuMSA9IE1hdGgubWF4KE4sIE1hdGgubWluKFMsIG4wIC0gZHkgKiBzaWduWSkpLCBzMSA9IE1hdGgubWF4KE4sIE1hdGgubWluKFMsIHMwICsgZHkgKiBzaWduWSkpOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKGUxIDwgdzEpIHsKICAgICAgICAgICAgc2lnblggKj0gLTE7CiAgICAgICAgICAgIHQgPSB3MCwgdzAgPSBlMCwgZTAgPSB0OwogICAgICAgICAgICB0ID0gdzEsIHcxID0gZTEsIGUxID0gdDsKICAgICAgICAgICAgaWYgKHR5cGUgaW4gZmxpcFgpIG92ZXJsYXkuYXR0cigiY3Vyc29yIiwgY3Vyc29yc1t0eXBlID0gZmxpcFhbdHlwZV1dKTsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAoczEgPCBuMSkgewogICAgICAgICAgICBzaWduWSAqPSAtMTsKICAgICAgICAgICAgdCA9IG4wLCBuMCA9IHMwLCBzMCA9IHQ7CiAgICAgICAgICAgIHQgPSBuMSwgbjEgPSBzMSwgczEgPSB0OwogICAgICAgICAgICBpZiAodHlwZSBpbiBmbGlwWSkgb3ZlcmxheS5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzW3R5cGUgPSBmbGlwWVt0eXBlXV0pOwogICAgICAgICAgfQoKICAgICAgICAgIGlmIChzdGF0ZS5zZWxlY3Rpb24pIHNlbGVjdGlvbiA9IHN0YXRlLnNlbGVjdGlvbjsgLy8gTWF5IGJlIHNldCBieSBicnVzaC5tb3ZlIQogICAgICAgICAgaWYgKGxvY2tYKSB3MSA9IHNlbGVjdGlvblswXVswXSwgZTEgPSBzZWxlY3Rpb25bMV1bMF07CiAgICAgICAgICBpZiAobG9ja1kpIG4xID0gc2VsZWN0aW9uWzBdWzFdLCBzMSA9IHNlbGVjdGlvblsxXVsxXTsKCiAgICAgICAgICBpZiAoc2VsZWN0aW9uWzBdWzBdICE9PSB3MQogICAgICAgICAgICAgIHx8IHNlbGVjdGlvblswXVsxXSAhPT0gbjEKICAgICAgICAgICAgICB8fCBzZWxlY3Rpb25bMV1bMF0gIT09IGUxCiAgICAgICAgICAgICAgfHwgc2VsZWN0aW9uWzFdWzFdICE9PSBzMSkgewogICAgICAgICAgICBzdGF0ZS5zZWxlY3Rpb24gPSBbW3cxLCBuMV0sIFtlMSwgczFdXTsKICAgICAgICAgICAgcmVkcmF3LmNhbGwodGhhdCk7CiAgICAgICAgICAgIGVtaXQuYnJ1c2goKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGVuZGVkKCkgewogICAgICAgICAgbm9wcm9wYWdhdGlvbiQxKCk7CiAgICAgICAgICBpZiAoZXZlbnQudG91Y2hlcykgewogICAgICAgICAgICBpZiAoZXZlbnQudG91Y2hlcy5sZW5ndGgpIHJldHVybjsKICAgICAgICAgICAgaWYgKHRvdWNoZW5kaW5nKSBjbGVhclRpbWVvdXQodG91Y2hlbmRpbmcpOwogICAgICAgICAgICB0b3VjaGVuZGluZyA9IHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHRvdWNoZW5kaW5nID0gbnVsbDsgfSwgNTAwKTsgLy8gR2hvc3QgY2xpY2tzIGFyZSBkZWxheWVkIQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgeWVzZHJhZyhldmVudC52aWV3LCBtb3ZpbmcpOwogICAgICAgICAgICB2aWV3Lm9uKCJrZXlkb3duLmJydXNoIGtleXVwLmJydXNoIG1vdXNlbW92ZS5icnVzaCBtb3VzZXVwLmJydXNoIiwgbnVsbCk7CiAgICAgICAgICB9CiAgICAgICAgICBncm91cC5hdHRyKCJwb2ludGVyLWV2ZW50cyIsICJhbGwiKTsKICAgICAgICAgIG92ZXJsYXkuYXR0cigiY3Vyc29yIiwgY3Vyc29ycy5vdmVybGF5KTsKICAgICAgICAgIGlmIChzdGF0ZS5zZWxlY3Rpb24pIHNlbGVjdGlvbiA9IHN0YXRlLnNlbGVjdGlvbjsgLy8gTWF5IGJlIHNldCBieSBicnVzaC5tb3ZlIChvbiBzdGFydCkhCiAgICAgICAgICBpZiAoZW1wdHkkMShzZWxlY3Rpb24pKSBzdGF0ZS5zZWxlY3Rpb24gPSBudWxsLCByZWRyYXcuY2FsbCh0aGF0KTsKICAgICAgICAgIGVtaXQuZW5kKCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBrZXlkb3duZWQoKSB7CiAgICAgICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHsKICAgICAgICAgICAgY2FzZSAxNjogeyAvLyBTSElGVAogICAgICAgICAgICAgIHNoaWZ0aW5nID0gc2lnblggJiYgc2lnblk7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSAxODogeyAvLyBBTFQKICAgICAgICAgICAgICBpZiAobW9kZSA9PT0gTU9ERV9IQU5ETEUpIHsKICAgICAgICAgICAgICAgIGlmIChzaWduWCkgZTAgPSBlMSAtIGR4ICogc2lnblgsIHcwID0gdzEgKyBkeCAqIHNpZ25YOwogICAgICAgICAgICAgICAgaWYgKHNpZ25ZKSBzMCA9IHMxIC0gZHkgKiBzaWduWSwgbjAgPSBuMSArIGR5ICogc2lnblk7CiAgICAgICAgICAgICAgICBtb2RlID0gTU9ERV9DRU5URVI7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgMzI6IHsgLy8gU1BBQ0U7IHRha2VzIHByaW9yaXR5IG92ZXIgQUxUCiAgICAgICAgICAgICAgaWYgKG1vZGUgPT09IE1PREVfSEFORExFIHx8IG1vZGUgPT09IE1PREVfQ0VOVEVSKSB7CiAgICAgICAgICAgICAgICBpZiAoc2lnblggPCAwKSBlMCA9IGUxIC0gZHg7IGVsc2UgaWYgKHNpZ25YID4gMCkgdzAgPSB3MSAtIGR4OwogICAgICAgICAgICAgICAgaWYgKHNpZ25ZIDwgMCkgczAgPSBzMSAtIGR5OyBlbHNlIGlmIChzaWduWSA+IDApIG4wID0gbjEgLSBkeTsKICAgICAgICAgICAgICAgIG1vZGUgPSBNT0RFX1NQQUNFOwogICAgICAgICAgICAgICAgb3ZlcmxheS5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzLnNlbGVjdGlvbik7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGRlZmF1bHQ6IHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIG5vZXZlbnQkMSgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24ga2V5dXBwZWQoKSB7CiAgICAgICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHsKICAgICAgICAgICAgY2FzZSAxNjogeyAvLyBTSElGVAogICAgICAgICAgICAgIGlmIChzaGlmdGluZykgewogICAgICAgICAgICAgICAgbG9ja1ggPSBsb2NrWSA9IHNoaWZ0aW5nID0gZmFsc2U7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgMTg6IHsgLy8gQUxUCiAgICAgICAgICAgICAgaWYgKG1vZGUgPT09IE1PREVfQ0VOVEVSKSB7CiAgICAgICAgICAgICAgICBpZiAoc2lnblggPCAwKSBlMCA9IGUxOyBlbHNlIGlmIChzaWduWCA+IDApIHcwID0gdzE7CiAgICAgICAgICAgICAgICBpZiAoc2lnblkgPCAwKSBzMCA9IHMxOyBlbHNlIGlmIChzaWduWSA+IDApIG4wID0gbjE7CiAgICAgICAgICAgICAgICBtb2RlID0gTU9ERV9IQU5ETEU7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgMzI6IHsgLy8gU1BBQ0UKICAgICAgICAgICAgICBpZiAobW9kZSA9PT0gTU9ERV9TUEFDRSkgewogICAgICAgICAgICAgICAgaWYgKGV2ZW50LmFsdEtleSkgewogICAgICAgICAgICAgICAgICBpZiAoc2lnblgpIGUwID0gZTEgLSBkeCAqIHNpZ25YLCB3MCA9IHcxICsgZHggKiBzaWduWDsKICAgICAgICAgICAgICAgICAgaWYgKHNpZ25ZKSBzMCA9IHMxIC0gZHkgKiBzaWduWSwgbjAgPSBuMSArIGR5ICogc2lnblk7CiAgICAgICAgICAgICAgICAgIG1vZGUgPSBNT0RFX0NFTlRFUjsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgIGlmIChzaWduWCA8IDApIGUwID0gZTE7IGVsc2UgaWYgKHNpZ25YID4gMCkgdzAgPSB3MTsKICAgICAgICAgICAgICAgICAgaWYgKHNpZ25ZIDwgMCkgczAgPSBzMTsgZWxzZSBpZiAoc2lnblkgPiAwKSBuMCA9IG4xOwogICAgICAgICAgICAgICAgICBtb2RlID0gTU9ERV9IQU5ETEU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBvdmVybGF5LmF0dHIoImN1cnNvciIsIGN1cnNvcnNbdHlwZV0pOwogICAgICAgICAgICAgICAgbW92ZSgpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBkZWZhdWx0OiByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBub2V2ZW50JDEoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNobW92ZWQoKSB7CiAgICAgICAgZW1pdHRlcih0aGlzLCBhcmd1bWVudHMpLm1vdmVkKCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNoZW5kZWQoKSB7CiAgICAgICAgZW1pdHRlcih0aGlzLCBhcmd1bWVudHMpLmVuZGVkKCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgdmFyIHN0YXRlID0gdGhpcy5fX2JydXNoIHx8IHtzZWxlY3Rpb246IG51bGx9OwogICAgICAgIHN0YXRlLmV4dGVudCA9IG51bWJlcjIoZXh0ZW50LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpOwogICAgICAgIHN0YXRlLmRpbSA9IGRpbTsKICAgICAgICByZXR1cm4gc3RhdGU7CiAgICAgIH0KCiAgICAgIGJydXNoLmV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChleHRlbnQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ0KG51bWJlcjIoXykpLCBicnVzaCkgOiBleHRlbnQ7CiAgICAgIH07CgogICAgICBicnVzaC5maWx0ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZmlsdGVyID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkNCghIV8pLCBicnVzaCkgOiBmaWx0ZXI7CiAgICAgIH07CgogICAgICBicnVzaC50b3VjaGFibGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodG91Y2hhYmxlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkNCghIV8pLCBicnVzaCkgOiB0b3VjaGFibGU7CiAgICAgIH07CgogICAgICBicnVzaC5oYW5kbGVTaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGhhbmRsZVNpemUgPSArXywgYnJ1c2gpIDogaGFuZGxlU2l6ZTsKICAgICAgfTsKCiAgICAgIGJydXNoLmtleU1vZGlmaWVycyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChrZXlzID0gISFfLCBicnVzaCkgOiBrZXlzOwogICAgICB9OwoKICAgICAgYnJ1c2gub24gPSBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUgPSBsaXN0ZW5lcnMub24uYXBwbHkobGlzdGVuZXJzLCBhcmd1bWVudHMpOwogICAgICAgIHJldHVybiB2YWx1ZSA9PT0gbGlzdGVuZXJzID8gYnJ1c2ggOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIHJldHVybiBicnVzaDsKICAgIH0KCiAgICB2YXIgY29zID0gTWF0aC5jb3M7CiAgICB2YXIgc2luID0gTWF0aC5zaW47CiAgICB2YXIgcGkkMSA9IE1hdGguUEk7CiAgICB2YXIgaGFsZlBpJDEgPSBwaSQxIC8gMjsKICAgIHZhciB0YXUkMSA9IHBpJDEgKiAyOwogICAgdmFyIG1heCQxID0gTWF0aC5tYXg7CgogICAgZnVuY3Rpb24gY29tcGFyZVZhbHVlKGNvbXBhcmUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICByZXR1cm4gY29tcGFyZSgKICAgICAgICAgIGEuc291cmNlLnZhbHVlICsgYS50YXJnZXQudmFsdWUsCiAgICAgICAgICBiLnNvdXJjZS52YWx1ZSArIGIudGFyZ2V0LnZhbHVlCiAgICAgICAgKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjaG9yZCgpIHsKICAgICAgdmFyIHBhZEFuZ2xlID0gMCwKICAgICAgICAgIHNvcnRHcm91cHMgPSBudWxsLAogICAgICAgICAgc29ydFN1Ymdyb3VwcyA9IG51bGwsCiAgICAgICAgICBzb3J0Q2hvcmRzID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIGNob3JkKG1hdHJpeCkgewogICAgICAgIHZhciBuID0gbWF0cml4Lmxlbmd0aCwKICAgICAgICAgICAgZ3JvdXBTdW1zID0gW10sCiAgICAgICAgICAgIGdyb3VwSW5kZXggPSBzZXF1ZW5jZShuKSwKICAgICAgICAgICAgc3ViZ3JvdXBJbmRleCA9IFtdLAogICAgICAgICAgICBjaG9yZHMgPSBbXSwKICAgICAgICAgICAgZ3JvdXBzID0gY2hvcmRzLmdyb3VwcyA9IG5ldyBBcnJheShuKSwKICAgICAgICAgICAgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG4gKiBuKSwKICAgICAgICAgICAgaywKICAgICAgICAgICAgeCwKICAgICAgICAgICAgeDAsCiAgICAgICAgICAgIGR4LAogICAgICAgICAgICBpLAogICAgICAgICAgICBqOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBzdW0uCiAgICAgICAgayA9IDAsIGkgPSAtMTsgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIHggPSAwLCBqID0gLTE7IHdoaWxlICgrK2ogPCBuKSB7CiAgICAgICAgICAgIHggKz0gbWF0cml4W2ldW2pdOwogICAgICAgICAgfQogICAgICAgICAgZ3JvdXBTdW1zLnB1c2goeCk7CiAgICAgICAgICBzdWJncm91cEluZGV4LnB1c2goc2VxdWVuY2UobikpOwogICAgICAgICAgayArPSB4OwogICAgICAgIH0KCiAgICAgICAgLy8gU29ydCBncm91cHPigKYKICAgICAgICBpZiAoc29ydEdyb3VwcykgZ3JvdXBJbmRleC5zb3J0KGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICAgIHJldHVybiBzb3J0R3JvdXBzKGdyb3VwU3Vtc1thXSwgZ3JvdXBTdW1zW2JdKTsKICAgICAgICB9KTsKCiAgICAgICAgLy8gU29ydCBzdWJncm91cHPigKYKICAgICAgICBpZiAoc29ydFN1Ymdyb3Vwcykgc3ViZ3JvdXBJbmRleC5mb3JFYWNoKGZ1bmN0aW9uKGQsIGkpIHsKICAgICAgICAgIGQuc29ydChmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgICAgIHJldHVybiBzb3J0U3ViZ3JvdXBzKG1hdHJpeFtpXVthXSwgbWF0cml4W2ldW2JdKTsKICAgICAgICAgIH0pOwogICAgICAgIH0pOwoKICAgICAgICAvLyBDb252ZXJ0IHRoZSBzdW0gdG8gc2NhbGluZyBmYWN0b3IgZm9yIFswLCAycGldLgogICAgICAgIC8vIFRPRE8gQWxsb3cgc3RhcnQgYW5kIGVuZCBhbmdsZSB0byBiZSBzcGVjaWZpZWQ/CiAgICAgICAgLy8gVE9ETyBBbGxvdyBwYWRkaW5nIHRvIGJlIHNwZWNpZmllZCBhcyBwZXJjZW50YWdlPwogICAgICAgIGsgPSBtYXgkMSgwLCB0YXUkMSAtIHBhZEFuZ2xlICogbikgLyBrOwogICAgICAgIGR4ID0gayA/IHBhZEFuZ2xlIDogdGF1JDEgLyBuOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBzdGFydCBhbmQgZW5kIGFuZ2xlIGZvciBlYWNoIGdyb3VwIGFuZCBzdWJncm91cC4KICAgICAgICAvLyBOb3RlOiBPcGVyYSBoYXMgYSBidWcgcmVvcmRlcmluZyBvYmplY3QgbGl0ZXJhbCBwcm9wZXJ0aWVzIQogICAgICAgIHggPSAwLCBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICB4MCA9IHgsIGogPSAtMTsgd2hpbGUgKCsraiA8IG4pIHsKICAgICAgICAgICAgdmFyIGRpID0gZ3JvdXBJbmRleFtpXSwKICAgICAgICAgICAgICAgIGRqID0gc3ViZ3JvdXBJbmRleFtkaV1bal0sCiAgICAgICAgICAgICAgICB2ID0gbWF0cml4W2RpXVtkal0sCiAgICAgICAgICAgICAgICBhMCA9IHgsCiAgICAgICAgICAgICAgICBhMSA9IHggKz0gdiAqIGs7CiAgICAgICAgICAgIHN1Ymdyb3Vwc1tkaiAqIG4gKyBkaV0gPSB7CiAgICAgICAgICAgICAgaW5kZXg6IGRpLAogICAgICAgICAgICAgIHN1YmluZGV4OiBkaiwKICAgICAgICAgICAgICBzdGFydEFuZ2xlOiBhMCwKICAgICAgICAgICAgICBlbmRBbmdsZTogYTEsCiAgICAgICAgICAgICAgdmFsdWU6IHYKICAgICAgICAgICAgfTsKICAgICAgICAgIH0KICAgICAgICAgIGdyb3Vwc1tkaV0gPSB7CiAgICAgICAgICAgIGluZGV4OiBkaSwKICAgICAgICAgICAgc3RhcnRBbmdsZTogeDAsCiAgICAgICAgICAgIGVuZEFuZ2xlOiB4LAogICAgICAgICAgICB2YWx1ZTogZ3JvdXBTdW1zW2RpXQogICAgICAgICAgfTsKICAgICAgICAgIHggKz0gZHg7CiAgICAgICAgfQoKICAgICAgICAvLyBHZW5lcmF0ZSBjaG9yZHMgZm9yIGVhY2ggKG5vbi1lbXB0eSkgc3ViZ3JvdXAtc3ViZ3JvdXAgbGluay4KICAgICAgICBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBqID0gaSAtIDE7IHdoaWxlICgrK2ogPCBuKSB7CiAgICAgICAgICAgIHZhciBzb3VyY2UgPSBzdWJncm91cHNbaiAqIG4gKyBpXSwKICAgICAgICAgICAgICAgIHRhcmdldCA9IHN1Ymdyb3Vwc1tpICogbiArIGpdOwogICAgICAgICAgICBpZiAoc291cmNlLnZhbHVlIHx8IHRhcmdldC52YWx1ZSkgewogICAgICAgICAgICAgIGNob3Jkcy5wdXNoKHNvdXJjZS52YWx1ZSA8IHRhcmdldC52YWx1ZQogICAgICAgICAgICAgICAgICA/IHtzb3VyY2U6IHRhcmdldCwgdGFyZ2V0OiBzb3VyY2V9CiAgICAgICAgICAgICAgICAgIDoge3NvdXJjZTogc291cmNlLCB0YXJnZXQ6IHRhcmdldH0pOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gc29ydENob3JkcyA/IGNob3Jkcy5zb3J0KHNvcnRDaG9yZHMpIDogY2hvcmRzOwogICAgICB9CgogICAgICBjaG9yZC5wYWRBbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRBbmdsZSA9IG1heCQxKDAsIF8pLCBjaG9yZCkgOiBwYWRBbmdsZTsKICAgICAgfTsKCiAgICAgIGNob3JkLnNvcnRHcm91cHMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc29ydEdyb3VwcyA9IF8sIGNob3JkKSA6IHNvcnRHcm91cHM7CiAgICAgIH07CgogICAgICBjaG9yZC5zb3J0U3ViZ3JvdXBzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNvcnRTdWJncm91cHMgPSBfLCBjaG9yZCkgOiBzb3J0U3ViZ3JvdXBzOwogICAgICB9OwoKICAgICAgY2hvcmQuc29ydENob3JkcyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChfID09IG51bGwgPyBzb3J0Q2hvcmRzID0gbnVsbCA6IChzb3J0Q2hvcmRzID0gY29tcGFyZVZhbHVlKF8pKS5fID0gXywgY2hvcmQpIDogc29ydENob3JkcyAmJiBzb3J0Q2hvcmRzLl87CiAgICAgIH07CgogICAgICByZXR1cm4gY2hvcmQ7CiAgICB9CgogICAgdmFyIHNsaWNlJDIgPSBBcnJheS5wcm90b3R5cGUuc2xpY2U7CgogICAgZnVuY3Rpb24gY29uc3RhbnQkNSh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcGkkMiA9IE1hdGguUEksCiAgICAgICAgdGF1JDIgPSAyICogcGkkMiwKICAgICAgICBlcHNpbG9uJDEgPSAxZS02LAogICAgICAgIHRhdUVwc2lsb24gPSB0YXUkMiAtIGVwc2lsb24kMTsKCiAgICBmdW5jdGlvbiBQYXRoKCkgewogICAgICB0aGlzLl94MCA9IHRoaXMuX3kwID0gLy8gc3RhcnQgb2YgY3VycmVudCBzdWJwYXRoCiAgICAgIHRoaXMuX3gxID0gdGhpcy5feTEgPSBudWxsOyAvLyBlbmQgb2YgY3VycmVudCBzdWJwYXRoCiAgICAgIHRoaXMuXyA9ICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhdGgoKSB7CiAgICAgIHJldHVybiBuZXcgUGF0aDsKICAgIH0KCiAgICBQYXRoLnByb3RvdHlwZSA9IHBhdGgucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogUGF0aCwKICAgICAgbW92ZVRvOiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJNIiArICh0aGlzLl94MCA9IHRoaXMuX3gxID0gK3gpICsgIiwiICsgKHRoaXMuX3kwID0gdGhpcy5feTEgPSAreSk7CiAgICAgIH0sCiAgICAgIGNsb3NlUGF0aDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX3gxICE9PSBudWxsKSB7CiAgICAgICAgICB0aGlzLl94MSA9IHRoaXMuX3gwLCB0aGlzLl95MSA9IHRoaXMuX3kwOwogICAgICAgICAgdGhpcy5fICs9ICJaIjsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGxpbmVUbzogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHRoaXMuXyArPSAiTCIgKyAodGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTEgPSAreSk7CiAgICAgIH0sCiAgICAgIHF1YWRyYXRpY0N1cnZlVG86IGZ1bmN0aW9uKHgxLCB5MSwgeCwgeSkgewogICAgICAgIHRoaXMuXyArPSAiUSIgKyAoK3gxKSArICIsIiArICgreTEpICsgIiwiICsgKHRoaXMuX3gxID0gK3gpICsgIiwiICsgKHRoaXMuX3kxID0gK3kpOwogICAgICB9LAogICAgICBiZXppZXJDdXJ2ZVRvOiBmdW5jdGlvbih4MSwgeTEsIHgyLCB5MiwgeCwgeSkgewogICAgICAgIHRoaXMuXyArPSAiQyIgKyAoK3gxKSArICIsIiArICgreTEpICsgIiwiICsgKCt4MikgKyAiLCIgKyAoK3kyKSArICIsIiArICh0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgYXJjVG86IGZ1bmN0aW9uKHgxLCB5MSwgeDIsIHkyLCByKSB7CiAgICAgICAgeDEgPSAreDEsIHkxID0gK3kxLCB4MiA9ICt4MiwgeTIgPSAreTIsIHIgPSArcjsKICAgICAgICB2YXIgeDAgPSB0aGlzLl94MSwKICAgICAgICAgICAgeTAgPSB0aGlzLl95MSwKICAgICAgICAgICAgeDIxID0geDIgLSB4MSwKICAgICAgICAgICAgeTIxID0geTIgLSB5MSwKICAgICAgICAgICAgeDAxID0geDAgLSB4MSwKICAgICAgICAgICAgeTAxID0geTAgLSB5MSwKICAgICAgICAgICAgbDAxXzIgPSB4MDEgKiB4MDEgKyB5MDEgKiB5MDE7CgogICAgICAgIC8vIElzIHRoZSByYWRpdXMgbmVnYXRpdmU/IEVycm9yLgogICAgICAgIGlmIChyIDwgMCkgdGhyb3cgbmV3IEVycm9yKCJuZWdhdGl2ZSByYWRpdXM6ICIgKyByKTsKCiAgICAgICAgLy8gSXMgdGhpcyBwYXRoIGVtcHR5PyBNb3ZlIHRvICh4MSx5MSkuCiAgICAgICAgaWYgKHRoaXMuX3gxID09PSBudWxsKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIk0iICsgKHRoaXMuX3gxID0geDEpICsgIiwiICsgKHRoaXMuX3kxID0geTEpOwogICAgICAgIH0KCiAgICAgICAgLy8gT3IsIGlzICh4MSx5MSkgY29pbmNpZGVudCB3aXRoICh4MCx5MCk/IERvIG5vdGhpbmcuCiAgICAgICAgZWxzZSBpZiAoIShsMDFfMiA+IGVwc2lsb24kMSkpOwoKICAgICAgICAvLyBPciwgYXJlICh4MCx5MCksICh4MSx5MSkgYW5kICh4Mix5MikgY29sbGluZWFyPwogICAgICAgIC8vIEVxdWl2YWxlbnRseSwgaXMgKHgxLHkxKSBjb2luY2lkZW50IHdpdGggKHgyLHkyKT8KICAgICAgICAvLyBPciwgaXMgdGhlIHJhZGl1cyB6ZXJvPyBMaW5lIHRvICh4MSx5MSkuCiAgICAgICAgZWxzZSBpZiAoIShNYXRoLmFicyh5MDEgKiB4MjEgLSB5MjEgKiB4MDEpID4gZXBzaWxvbiQxKSB8fCAhcikgewogICAgICAgICAgdGhpcy5fICs9ICJMIiArICh0aGlzLl94MSA9IHgxKSArICIsIiArICh0aGlzLl95MSA9IHkxKTsKICAgICAgICB9CgogICAgICAgIC8vIE90aGVyd2lzZSwgZHJhdyBhbiBhcmMhCiAgICAgICAgZWxzZSB7CiAgICAgICAgICB2YXIgeDIwID0geDIgLSB4MCwKICAgICAgICAgICAgICB5MjAgPSB5MiAtIHkwLAogICAgICAgICAgICAgIGwyMV8yID0geDIxICogeDIxICsgeTIxICogeTIxLAogICAgICAgICAgICAgIGwyMF8yID0geDIwICogeDIwICsgeTIwICogeTIwLAogICAgICAgICAgICAgIGwyMSA9IE1hdGguc3FydChsMjFfMiksCiAgICAgICAgICAgICAgbDAxID0gTWF0aC5zcXJ0KGwwMV8yKSwKICAgICAgICAgICAgICBsID0gciAqIE1hdGgudGFuKChwaSQyIC0gTWF0aC5hY29zKChsMjFfMiArIGwwMV8yIC0gbDIwXzIpIC8gKDIgKiBsMjEgKiBsMDEpKSkgLyAyKSwKICAgICAgICAgICAgICB0MDEgPSBsIC8gbDAxLAogICAgICAgICAgICAgIHQyMSA9IGwgLyBsMjE7CgogICAgICAgICAgLy8gSWYgdGhlIHN0YXJ0IHRhbmdlbnQgaXMgbm90IGNvaW5jaWRlbnQgd2l0aCAoeDAseTApLCBsaW5lIHRvLgogICAgICAgICAgaWYgKE1hdGguYWJzKHQwMSAtIDEpID4gZXBzaWxvbiQxKSB7CiAgICAgICAgICAgIHRoaXMuXyArPSAiTCIgKyAoeDEgKyB0MDEgKiB4MDEpICsgIiwiICsgKHkxICsgdDAxICogeTAxKTsKICAgICAgICAgIH0KCiAgICAgICAgICB0aGlzLl8gKz0gIkEiICsgciArICIsIiArIHIgKyAiLDAsMCwiICsgKCsoeTAxICogeDIwID4geDAxICogeTIwKSkgKyAiLCIgKyAodGhpcy5feDEgPSB4MSArIHQyMSAqIHgyMSkgKyAiLCIgKyAodGhpcy5feTEgPSB5MSArIHQyMSAqIHkyMSk7CiAgICAgICAgfQogICAgICB9LAogICAgICBhcmM6IGZ1bmN0aW9uKHgsIHksIHIsIGEwLCBhMSwgY2N3KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3ksIHIgPSArciwgY2N3ID0gISFjY3c7CiAgICAgICAgdmFyIGR4ID0gciAqIE1hdGguY29zKGEwKSwKICAgICAgICAgICAgZHkgPSByICogTWF0aC5zaW4oYTApLAogICAgICAgICAgICB4MCA9IHggKyBkeCwKICAgICAgICAgICAgeTAgPSB5ICsgZHksCiAgICAgICAgICAgIGN3ID0gMSBeIGNjdywKICAgICAgICAgICAgZGEgPSBjY3cgPyBhMCAtIGExIDogYTEgLSBhMDsKCiAgICAgICAgLy8gSXMgdGhlIHJhZGl1cyBuZWdhdGl2ZT8gRXJyb3IuCiAgICAgICAgaWYgKHIgPCAwKSB0aHJvdyBuZXcgRXJyb3IoIm5lZ2F0aXZlIHJhZGl1czogIiArIHIpOwoKICAgICAgICAvLyBJcyB0aGlzIHBhdGggZW1wdHk/IE1vdmUgdG8gKHgwLHkwKS4KICAgICAgICBpZiAodGhpcy5feDEgPT09IG51bGwpIHsKICAgICAgICAgIHRoaXMuXyArPSAiTSIgKyB4MCArICIsIiArIHkwOwogICAgICAgIH0KCiAgICAgICAgLy8gT3IsIGlzICh4MCx5MCkgbm90IGNvaW5jaWRlbnQgd2l0aCB0aGUgcHJldmlvdXMgcG9pbnQ/IExpbmUgdG8gKHgwLHkwKS4KICAgICAgICBlbHNlIGlmIChNYXRoLmFicyh0aGlzLl94MSAtIHgwKSA+IGVwc2lsb24kMSB8fCBNYXRoLmFicyh0aGlzLl95MSAtIHkwKSA+IGVwc2lsb24kMSkgewogICAgICAgICAgdGhpcy5fICs9ICJMIiArIHgwICsgIiwiICsgeTA7CiAgICAgICAgfQoKICAgICAgICAvLyBJcyB0aGlzIGFyYyBlbXB0eT8gV2XigJlyZSBkb25lLgogICAgICAgIGlmICghcikgcmV0dXJuOwoKICAgICAgICAvLyBEb2VzIHRoZSBhbmdsZSBnbyB0aGUgd3Jvbmcgd2F5PyBGbGlwIHRoZSBkaXJlY3Rpb24uCiAgICAgICAgaWYgKGRhIDwgMCkgZGEgPSBkYSAlIHRhdSQyICsgdGF1JDI7CgogICAgICAgIC8vIElzIHRoaXMgYSBjb21wbGV0ZSBjaXJjbGU/IERyYXcgdHdvIGFyY3MgdG8gY29tcGxldGUgdGhlIGNpcmNsZS4KICAgICAgICBpZiAoZGEgPiB0YXVFcHNpbG9uKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkEiICsgciArICIsIiArIHIgKyAiLDAsMSwiICsgY3cgKyAiLCIgKyAoeCAtIGR4KSArICIsIiArICh5IC0gZHkpICsgIkEiICsgciArICIsIiArIHIgKyAiLDAsMSwiICsgY3cgKyAiLCIgKyAodGhpcy5feDEgPSB4MCkgKyAiLCIgKyAodGhpcy5feTEgPSB5MCk7CiAgICAgICAgfQoKICAgICAgICAvLyBJcyB0aGlzIGFyYyBub24tZW1wdHk/IERyYXcgYW4gYXJjIQogICAgICAgIGVsc2UgaWYgKGRhID4gZXBzaWxvbiQxKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkEiICsgciArICIsIiArIHIgKyAiLDAsIiArICgrKGRhID49IHBpJDIpKSArICIsIiArIGN3ICsgIiwiICsgKHRoaXMuX3gxID0geCArIHIgKiBNYXRoLmNvcyhhMSkpICsgIiwiICsgKHRoaXMuX3kxID0geSArIHIgKiBNYXRoLnNpbihhMSkpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgcmVjdDogZnVuY3Rpb24oeCwgeSwgdywgaCkgewogICAgICAgIHRoaXMuXyArPSAiTSIgKyAodGhpcy5feDAgPSB0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MCA9IHRoaXMuX3kxID0gK3kpICsgImgiICsgKCt3KSArICJ2IiArICgraCkgKyAiaCIgKyAoLXcpICsgIloiOwogICAgICB9LAogICAgICB0b1N0cmluZzogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuXzsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBkZWZhdWx0U291cmNlKGQpIHsKICAgICAgcmV0dXJuIGQuc291cmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRUYXJnZXQoZCkgewogICAgICByZXR1cm4gZC50YXJnZXQ7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFJhZGl1cyhkKSB7CiAgICAgIHJldHVybiBkLnJhZGl1czsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0U3RhcnRBbmdsZShkKSB7CiAgICAgIHJldHVybiBkLnN0YXJ0QW5nbGU7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdEVuZEFuZ2xlKGQpIHsKICAgICAgcmV0dXJuIGQuZW5kQW5nbGU7CiAgICB9CgogICAgZnVuY3Rpb24gcmliYm9uKCkgewogICAgICB2YXIgc291cmNlID0gZGVmYXVsdFNvdXJjZSwKICAgICAgICAgIHRhcmdldCA9IGRlZmF1bHRUYXJnZXQsCiAgICAgICAgICByYWRpdXMgPSBkZWZhdWx0UmFkaXVzLAogICAgICAgICAgc3RhcnRBbmdsZSA9IGRlZmF1bHRTdGFydEFuZ2xlLAogICAgICAgICAgZW5kQW5nbGUgPSBkZWZhdWx0RW5kQW5nbGUsCiAgICAgICAgICBjb250ZXh0ID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIHJpYmJvbigpIHsKICAgICAgICB2YXIgYnVmZmVyLAogICAgICAgICAgICBhcmd2ID0gc2xpY2UkMi5jYWxsKGFyZ3VtZW50cyksCiAgICAgICAgICAgIHMgPSBzb3VyY2UuYXBwbHkodGhpcywgYXJndiksCiAgICAgICAgICAgIHQgPSB0YXJnZXQuYXBwbHkodGhpcywgYXJndiksCiAgICAgICAgICAgIHNyID0gK3JhZGl1cy5hcHBseSh0aGlzLCAoYXJndlswXSA9IHMsIGFyZ3YpKSwKICAgICAgICAgICAgc2EwID0gc3RhcnRBbmdsZS5hcHBseSh0aGlzLCBhcmd2KSAtIGhhbGZQaSQxLAogICAgICAgICAgICBzYTEgPSBlbmRBbmdsZS5hcHBseSh0aGlzLCBhcmd2KSAtIGhhbGZQaSQxLAogICAgICAgICAgICBzeDAgPSBzciAqIGNvcyhzYTApLAogICAgICAgICAgICBzeTAgPSBzciAqIHNpbihzYTApLAogICAgICAgICAgICB0ciA9ICtyYWRpdXMuYXBwbHkodGhpcywgKGFyZ3ZbMF0gPSB0LCBhcmd2KSksCiAgICAgICAgICAgIHRhMCA9IHN0YXJ0QW5nbGUuYXBwbHkodGhpcywgYXJndikgLSBoYWxmUGkkMSwKICAgICAgICAgICAgdGExID0gZW5kQW5nbGUuYXBwbHkodGhpcywgYXJndikgLSBoYWxmUGkkMTsKCiAgICAgICAgaWYgKCFjb250ZXh0KSBjb250ZXh0ID0gYnVmZmVyID0gcGF0aCgpOwoKICAgICAgICBjb250ZXh0Lm1vdmVUbyhzeDAsIHN5MCk7CiAgICAgICAgY29udGV4dC5hcmMoMCwgMCwgc3IsIHNhMCwgc2ExKTsKICAgICAgICBpZiAoc2EwICE9PSB0YTAgfHwgc2ExICE9PSB0YTEpIHsgLy8gVE9ETyBzciAhPT0gdHI/CiAgICAgICAgICBjb250ZXh0LnF1YWRyYXRpY0N1cnZlVG8oMCwgMCwgdHIgKiBjb3ModGEwKSwgdHIgKiBzaW4odGEwKSk7CiAgICAgICAgICBjb250ZXh0LmFyYygwLCAwLCB0ciwgdGEwLCB0YTEpOwogICAgICAgIH0KICAgICAgICBjb250ZXh0LnF1YWRyYXRpY0N1cnZlVG8oMCwgMCwgc3gwLCBzeTApOwogICAgICAgIGNvbnRleHQuY2xvc2VQYXRoKCk7CgogICAgICAgIGlmIChidWZmZXIpIHJldHVybiBjb250ZXh0ID0gbnVsbCwgYnVmZmVyICsgIiIgfHwgbnVsbDsKICAgICAgfQoKICAgICAgcmliYm9uLnJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ1KCtfKSwgcmliYm9uKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIHJpYmJvbi5zdGFydEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN0YXJ0QW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ1KCtfKSwgcmliYm9uKSA6IHN0YXJ0QW5nbGU7CiAgICAgIH07CgogICAgICByaWJib24uZW5kQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZW5kQW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ1KCtfKSwgcmliYm9uKSA6IGVuZEFuZ2xlOwogICAgICB9OwoKICAgICAgcmliYm9uLnNvdXJjZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzb3VyY2UgPSBfLCByaWJib24pIDogc291cmNlOwogICAgICB9OwoKICAgICAgcmliYm9uLnRhcmdldCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0YXJnZXQgPSBfLCByaWJib24pIDogdGFyZ2V0OwogICAgICB9OwoKICAgICAgcmliYm9uLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoKGNvbnRleHQgPSBfID09IG51bGwgPyBudWxsIDogXyksIHJpYmJvbikgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIHJpYmJvbjsKICAgIH0KCiAgICB2YXIgcHJlZml4ID0gIiQiOwoKICAgIGZ1bmN0aW9uIE1hcCQxKCkge30KCiAgICBNYXAkMS5wcm90b3R5cGUgPSBtYXAkMS5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBNYXAkMSwKICAgICAgaGFzOiBmdW5jdGlvbihrZXkpIHsKICAgICAgICByZXR1cm4gKHByZWZpeCArIGtleSkgaW4gdGhpczsKICAgICAgfSwKICAgICAgZ2V0OiBmdW5jdGlvbihrZXkpIHsKICAgICAgICByZXR1cm4gdGhpc1twcmVmaXggKyBrZXldOwogICAgICB9LAogICAgICBzZXQ6IGZ1bmN0aW9uKGtleSwgdmFsdWUpIHsKICAgICAgICB0aGlzW3ByZWZpeCArIGtleV0gPSB2YWx1ZTsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgcmVtb3ZlOiBmdW5jdGlvbihrZXkpIHsKICAgICAgICB2YXIgcHJvcGVydHkgPSBwcmVmaXggKyBrZXk7CiAgICAgICAgcmV0dXJuIHByb3BlcnR5IGluIHRoaXMgJiYgZGVsZXRlIHRoaXNbcHJvcGVydHldOwogICAgICB9LAogICAgICBjbGVhcjogZnVuY3Rpb24oKSB7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgpIGRlbGV0ZSB0aGlzW3Byb3BlcnR5XTsKICAgICAgfSwKICAgICAga2V5czogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGtleXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCkga2V5cy5wdXNoKHByb3BlcnR5LnNsaWNlKDEpKTsKICAgICAgICByZXR1cm4ga2V5czsKICAgICAgfSwKICAgICAgdmFsdWVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWVzID0gW107CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgpIHZhbHVlcy5wdXNoKHRoaXNbcHJvcGVydHldKTsKICAgICAgICByZXR1cm4gdmFsdWVzOwogICAgICB9LAogICAgICBlbnRyaWVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZW50cmllcyA9IFtdOwogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4KSBlbnRyaWVzLnB1c2goe2tleTogcHJvcGVydHkuc2xpY2UoMSksIHZhbHVlOiB0aGlzW3Byb3BlcnR5XX0pOwogICAgICAgIHJldHVybiBlbnRyaWVzOwogICAgICB9LAogICAgICBzaXplOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgpICsrc2l6ZTsKICAgICAgICByZXR1cm4gc2l6ZTsKICAgICAgfSwKICAgICAgZW1wdHk6IGZ1bmN0aW9uKCkgewogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4KSByZXR1cm4gZmFsc2U7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0sCiAgICAgIGVhY2g6IGZ1bmN0aW9uKGYpIHsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCkgZih0aGlzW3Byb3BlcnR5XSwgcHJvcGVydHkuc2xpY2UoMSksIHRoaXMpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIG1hcCQxKG9iamVjdCwgZikgewogICAgICB2YXIgbWFwID0gbmV3IE1hcCQxOwoKICAgICAgLy8gQ29weSBjb25zdHJ1Y3Rvci4KICAgICAgaWYgKG9iamVjdCBpbnN0YW5jZW9mIE1hcCQxKSBvYmplY3QuZWFjaChmdW5jdGlvbih2YWx1ZSwga2V5KSB7IG1hcC5zZXQoa2V5LCB2YWx1ZSk7IH0pOwoKICAgICAgLy8gSW5kZXggYXJyYXkgYnkgbnVtZXJpYyBpbmRleCBvciBzcGVjaWZpZWQga2V5IGZ1bmN0aW9uLgogICAgICBlbHNlIGlmIChBcnJheS5pc0FycmF5KG9iamVjdCkpIHsKICAgICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgICBuID0gb2JqZWN0Lmxlbmd0aCwKICAgICAgICAgICAgbzsKCiAgICAgICAgaWYgKGYgPT0gbnVsbCkgd2hpbGUgKCsraSA8IG4pIG1hcC5zZXQoaSwgb2JqZWN0W2ldKTsKICAgICAgICBlbHNlIHdoaWxlICgrK2kgPCBuKSBtYXAuc2V0KGYobyA9IG9iamVjdFtpXSwgaSwgb2JqZWN0KSwgbyk7CiAgICAgIH0KCiAgICAgIC8vIENvbnZlcnQgb2JqZWN0IHRvIG1hcC4KICAgICAgZWxzZSBpZiAob2JqZWN0KSBmb3IgKHZhciBrZXkgaW4gb2JqZWN0KSBtYXAuc2V0KGtleSwgb2JqZWN0W2tleV0pOwoKICAgICAgcmV0dXJuIG1hcDsKICAgIH0KCiAgICBmdW5jdGlvbiBuZXN0KCkgewogICAgICB2YXIga2V5cyA9IFtdLAogICAgICAgICAgc29ydEtleXMgPSBbXSwKICAgICAgICAgIHNvcnRWYWx1ZXMsCiAgICAgICAgICByb2xsdXAsCiAgICAgICAgICBuZXN0OwoKICAgICAgZnVuY3Rpb24gYXBwbHkoYXJyYXksIGRlcHRoLCBjcmVhdGVSZXN1bHQsIHNldFJlc3VsdCkgewogICAgICAgIGlmIChkZXB0aCA+PSBrZXlzLmxlbmd0aCkgewogICAgICAgICAgaWYgKHNvcnRWYWx1ZXMgIT0gbnVsbCkgYXJyYXkuc29ydChzb3J0VmFsdWVzKTsKICAgICAgICAgIHJldHVybiByb2xsdXAgIT0gbnVsbCA/IHJvbGx1cChhcnJheSkgOiBhcnJheTsKICAgICAgICB9CgogICAgICAgIHZhciBpID0gLTEsCiAgICAgICAgICAgIG4gPSBhcnJheS5sZW5ndGgsCiAgICAgICAgICAgIGtleSA9IGtleXNbZGVwdGgrK10sCiAgICAgICAgICAgIGtleVZhbHVlLAogICAgICAgICAgICB2YWx1ZSwKICAgICAgICAgICAgdmFsdWVzQnlLZXkgPSBtYXAkMSgpLAogICAgICAgICAgICB2YWx1ZXMsCiAgICAgICAgICAgIHJlc3VsdCA9IGNyZWF0ZVJlc3VsdCgpOwoKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaWYgKHZhbHVlcyA9IHZhbHVlc0J5S2V5LmdldChrZXlWYWx1ZSA9IGtleSh2YWx1ZSA9IGFycmF5W2ldKSArICIiKSkgewogICAgICAgICAgICB2YWx1ZXMucHVzaCh2YWx1ZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB2YWx1ZXNCeUtleS5zZXQoa2V5VmFsdWUsIFt2YWx1ZV0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdmFsdWVzQnlLZXkuZWFjaChmdW5jdGlvbih2YWx1ZXMsIGtleSkgewogICAgICAgICAgc2V0UmVzdWx0KHJlc3VsdCwga2V5LCBhcHBseSh2YWx1ZXMsIGRlcHRoLCBjcmVhdGVSZXN1bHQsIHNldFJlc3VsdCkpOwogICAgICAgIH0pOwoKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICBmdW5jdGlvbiBlbnRyaWVzKG1hcCwgZGVwdGgpIHsKICAgICAgICBpZiAoKytkZXB0aCA+IGtleXMubGVuZ3RoKSByZXR1cm4gbWFwOwogICAgICAgIHZhciBhcnJheSwgc29ydEtleSA9IHNvcnRLZXlzW2RlcHRoIC0gMV07CiAgICAgICAgaWYgKHJvbGx1cCAhPSBudWxsICYmIGRlcHRoID49IGtleXMubGVuZ3RoKSBhcnJheSA9IG1hcC5lbnRyaWVzKCk7CiAgICAgICAgZWxzZSBhcnJheSA9IFtdLCBtYXAuZWFjaChmdW5jdGlvbih2LCBrKSB7IGFycmF5LnB1c2goe2tleTogaywgdmFsdWVzOiBlbnRyaWVzKHYsIGRlcHRoKX0pOyB9KTsKICAgICAgICByZXR1cm4gc29ydEtleSAhPSBudWxsID8gYXJyYXkuc29ydChmdW5jdGlvbihhLCBiKSB7IHJldHVybiBzb3J0S2V5KGEua2V5LCBiLmtleSk7IH0pIDogYXJyYXk7CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXN0ID0gewogICAgICAgIG9iamVjdDogZnVuY3Rpb24oYXJyYXkpIHsgcmV0dXJuIGFwcGx5KGFycmF5LCAwLCBjcmVhdGVPYmplY3QsIHNldE9iamVjdCQxKTsgfSwKICAgICAgICBtYXA6IGZ1bmN0aW9uKGFycmF5KSB7IHJldHVybiBhcHBseShhcnJheSwgMCwgY3JlYXRlTWFwLCBzZXRNYXApOyB9LAogICAgICAgIGVudHJpZXM6IGZ1bmN0aW9uKGFycmF5KSB7IHJldHVybiBlbnRyaWVzKGFwcGx5KGFycmF5LCAwLCBjcmVhdGVNYXAsIHNldE1hcCksIDApOyB9LAogICAgICAgIGtleTogZnVuY3Rpb24oZCkgeyBrZXlzLnB1c2goZCk7IHJldHVybiBuZXN0OyB9LAogICAgICAgIHNvcnRLZXlzOiBmdW5jdGlvbihvcmRlcikgeyBzb3J0S2V5c1trZXlzLmxlbmd0aCAtIDFdID0gb3JkZXI7IHJldHVybiBuZXN0OyB9LAogICAgICAgIHNvcnRWYWx1ZXM6IGZ1bmN0aW9uKG9yZGVyKSB7IHNvcnRWYWx1ZXMgPSBvcmRlcjsgcmV0dXJuIG5lc3Q7IH0sCiAgICAgICAgcm9sbHVwOiBmdW5jdGlvbihmKSB7IHJvbGx1cCA9IGY7IHJldHVybiBuZXN0OyB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlT2JqZWN0KCkgewogICAgICByZXR1cm4ge307CiAgICB9CgogICAgZnVuY3Rpb24gc2V0T2JqZWN0JDEob2JqZWN0LCBrZXksIHZhbHVlKSB7CiAgICAgIG9iamVjdFtrZXldID0gdmFsdWU7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlTWFwKCkgewogICAgICByZXR1cm4gbWFwJDEoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZXRNYXAobWFwLCBrZXksIHZhbHVlKSB7CiAgICAgIG1hcC5zZXQoa2V5LCB2YWx1ZSk7CiAgICB9CgogICAgZnVuY3Rpb24gU2V0JDEoKSB7fQoKICAgIHZhciBwcm90byQxID0gbWFwJDEucHJvdG90eXBlOwoKICAgIFNldCQxLnByb3RvdHlwZSA9IHNldCQzLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFNldCQxLAogICAgICBoYXM6IHByb3RvJDEuaGFzLAogICAgICBhZGQ6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgdmFsdWUgKz0gIiI7CiAgICAgICAgdGhpc1twcmVmaXggKyB2YWx1ZV0gPSB2YWx1ZTsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgcmVtb3ZlOiBwcm90byQxLnJlbW92ZSwKICAgICAgY2xlYXI6IHByb3RvJDEuY2xlYXIsCiAgICAgIHZhbHVlczogcHJvdG8kMS5rZXlzLAogICAgICBzaXplOiBwcm90byQxLnNpemUsCiAgICAgIGVtcHR5OiBwcm90byQxLmVtcHR5LAogICAgICBlYWNoOiBwcm90byQxLmVhY2gKICAgIH07CgogICAgZnVuY3Rpb24gc2V0JDMob2JqZWN0LCBmKSB7CiAgICAgIHZhciBzZXQgPSBuZXcgU2V0JDE7CgogICAgICAvLyBDb3B5IGNvbnN0cnVjdG9yLgogICAgICBpZiAob2JqZWN0IGluc3RhbmNlb2YgU2V0JDEpIG9iamVjdC5lYWNoKGZ1bmN0aW9uKHZhbHVlKSB7IHNldC5hZGQodmFsdWUpOyB9KTsKCiAgICAgIC8vIE90aGVyd2lzZSwgYXNzdW1lIGl04oCZcyBhbiBhcnJheS4KICAgICAgZWxzZSBpZiAob2JqZWN0KSB7CiAgICAgICAgdmFyIGkgPSAtMSwgbiA9IG9iamVjdC5sZW5ndGg7CiAgICAgICAgaWYgKGYgPT0gbnVsbCkgd2hpbGUgKCsraSA8IG4pIHNldC5hZGQob2JqZWN0W2ldKTsKICAgICAgICBlbHNlIHdoaWxlICgrK2kgPCBuKSBzZXQuYWRkKGYob2JqZWN0W2ldLCBpLCBvYmplY3QpKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHNldDsKICAgIH0KCiAgICBmdW5jdGlvbiBrZXlzKG1hcCkgewogICAgICB2YXIga2V5cyA9IFtdOwogICAgICBmb3IgKHZhciBrZXkgaW4gbWFwKSBrZXlzLnB1c2goa2V5KTsKICAgICAgcmV0dXJuIGtleXM7CiAgICB9CgogICAgZnVuY3Rpb24gdmFsdWVzKG1hcCkgewogICAgICB2YXIgdmFsdWVzID0gW107CiAgICAgIGZvciAodmFyIGtleSBpbiBtYXApIHZhbHVlcy5wdXNoKG1hcFtrZXldKTsKICAgICAgcmV0dXJuIHZhbHVlczsKICAgIH0KCiAgICBmdW5jdGlvbiBlbnRyaWVzKG1hcCkgewogICAgICB2YXIgZW50cmllcyA9IFtdOwogICAgICBmb3IgKHZhciBrZXkgaW4gbWFwKSBlbnRyaWVzLnB1c2goe2tleToga2V5LCB2YWx1ZTogbWFwW2tleV19KTsKICAgICAgcmV0dXJuIGVudHJpZXM7CiAgICB9CgogICAgdmFyIGFycmF5JDIgPSBBcnJheS5wcm90b3R5cGU7CgogICAgdmFyIHNsaWNlJDMgPSBhcnJheSQyLnNsaWNlOwoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyQyKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgLSBiOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWEocmluZykgewogICAgICB2YXIgaSA9IDAsIG4gPSByaW5nLmxlbmd0aCwgYXJlYSA9IHJpbmdbbiAtIDFdWzFdICogcmluZ1swXVswXSAtIHJpbmdbbiAtIDFdWzBdICogcmluZ1swXVsxXTsKICAgICAgd2hpbGUgKCsraSA8IG4pIGFyZWEgKz0gcmluZ1tpIC0gMV1bMV0gKiByaW5nW2ldWzBdIC0gcmluZ1tpIC0gMV1bMF0gKiByaW5nW2ldWzFdOwogICAgICByZXR1cm4gYXJlYTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudCQ2KHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRhaW5zKHJpbmcsIGhvbGUpIHsKICAgICAgdmFyIGkgPSAtMSwgbiA9IGhvbGUubGVuZ3RoLCBjOwogICAgICB3aGlsZSAoKytpIDwgbikgaWYgKGMgPSByaW5nQ29udGFpbnMocmluZywgaG9sZVtpXSkpIHJldHVybiBjOwogICAgICByZXR1cm4gMDsKICAgIH0KCiAgICBmdW5jdGlvbiByaW5nQ29udGFpbnMocmluZywgcG9pbnQpIHsKICAgICAgdmFyIHggPSBwb2ludFswXSwgeSA9IHBvaW50WzFdLCBjb250YWlucyA9IC0xOwogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHJpbmcubGVuZ3RoLCBqID0gbiAtIDE7IGkgPCBuOyBqID0gaSsrKSB7CiAgICAgICAgdmFyIHBpID0gcmluZ1tpXSwgeGkgPSBwaVswXSwgeWkgPSBwaVsxXSwgcGogPSByaW5nW2pdLCB4aiA9IHBqWzBdLCB5aiA9IHBqWzFdOwogICAgICAgIGlmIChzZWdtZW50Q29udGFpbnMocGksIHBqLCBwb2ludCkpIHJldHVybiAwOwogICAgICAgIGlmICgoKHlpID4geSkgIT09ICh5aiA+IHkpKSAmJiAoKHggPCAoeGogLSB4aSkgKiAoeSAtIHlpKSAvICh5aiAtIHlpKSArIHhpKSkpIGNvbnRhaW5zID0gLWNvbnRhaW5zOwogICAgICB9CiAgICAgIHJldHVybiBjb250YWluczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWdtZW50Q29udGFpbnMoYSwgYiwgYykgewogICAgICB2YXIgaTsgcmV0dXJuIGNvbGxpbmVhcihhLCBiLCBjKSAmJiB3aXRoaW4oYVtpID0gKyhhWzBdID09PSBiWzBdKV0sIGNbaV0sIGJbaV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbGxpbmVhcihhLCBiLCBjKSB7CiAgICAgIHJldHVybiAoYlswXSAtIGFbMF0pICogKGNbMV0gLSBhWzFdKSA9PT0gKGNbMF0gLSBhWzBdKSAqIChiWzFdIC0gYVsxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gd2l0aGluKHAsIHEsIHIpIHsKICAgICAgcmV0dXJuIHAgPD0gcSAmJiBxIDw9IHIgfHwgciA8PSBxICYmIHEgPD0gcDsKICAgIH0KCiAgICBmdW5jdGlvbiBub29wJDEoKSB7fQoKICAgIHZhciBjYXNlcyA9IFsKICAgICAgW10sCiAgICAgIFtbWzEuMCwgMS41XSwgWzAuNSwgMS4wXV1dLAogICAgICBbW1sxLjUsIDEuMF0sIFsxLjAsIDEuNV1dXSwKICAgICAgW1tbMS41LCAxLjBdLCBbMC41LCAxLjBdXV0sCiAgICAgIFtbWzEuMCwgMC41XSwgWzEuNSwgMS4wXV1dLAogICAgICBbW1sxLjAsIDEuNV0sIFswLjUsIDEuMF1dLCBbWzEuMCwgMC41XSwgWzEuNSwgMS4wXV1dLAogICAgICBbW1sxLjAsIDAuNV0sIFsxLjAsIDEuNV1dXSwKICAgICAgW1tbMS4wLCAwLjVdLCBbMC41LCAxLjBdXV0sCiAgICAgIFtbWzAuNSwgMS4wXSwgWzEuMCwgMC41XV1dLAogICAgICBbW1sxLjAsIDEuNV0sIFsxLjAsIDAuNV1dXSwKICAgICAgW1tbMC41LCAxLjBdLCBbMS4wLCAwLjVdXSwgW1sxLjUsIDEuMF0sIFsxLjAsIDEuNV1dXSwKICAgICAgW1tbMS41LCAxLjBdLCBbMS4wLCAwLjVdXV0sCiAgICAgIFtbWzAuNSwgMS4wXSwgWzEuNSwgMS4wXV1dLAogICAgICBbW1sxLjAsIDEuNV0sIFsxLjUsIDEuMF1dXSwKICAgICAgW1tbMC41LCAxLjBdLCBbMS4wLCAxLjVdXV0sCiAgICAgIFtdCiAgICBdOwoKICAgIGZ1bmN0aW9uIGNvbnRvdXJzKCkgewogICAgICB2YXIgZHggPSAxLAogICAgICAgICAgZHkgPSAxLAogICAgICAgICAgdGhyZXNob2xkID0gdGhyZXNob2xkU3R1cmdlcywKICAgICAgICAgIHNtb290aCA9IHNtb290aExpbmVhcjsKCiAgICAgIGZ1bmN0aW9uIGNvbnRvdXJzKHZhbHVlcykgewogICAgICAgIHZhciB0eiA9IHRocmVzaG9sZCh2YWx1ZXMpOwoKICAgICAgICAvLyBDb252ZXJ0IG51bWJlciBvZiB0aHJlc2hvbGRzIGludG8gdW5pZm9ybSB0aHJlc2hvbGRzLgogICAgICAgIGlmICghQXJyYXkuaXNBcnJheSh0eikpIHsKICAgICAgICAgIHZhciBkb21haW4gPSBleHRlbnQodmFsdWVzKSwgc3RhcnQgPSBkb21haW5bMF0sIHN0b3AgPSBkb21haW5bMV07CiAgICAgICAgICB0eiA9IHRpY2tTdGVwKHN0YXJ0LCBzdG9wLCB0eik7CiAgICAgICAgICB0eiA9IHNlcXVlbmNlKE1hdGguZmxvb3Ioc3RhcnQgLyB0eikgKiB0eiwgTWF0aC5mbG9vcihzdG9wIC8gdHopICogdHosIHR6KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdHogPSB0ei5zbGljZSgpLnNvcnQoYXNjZW5kaW5nJDIpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHR6Lm1hcChmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGNvbnRvdXIodmFsdWVzLCB2YWx1ZSk7CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIC8vIEFjY3VtdWxhdGUsIHNtb290aCBjb250b3VyIHJpbmdzLCBhc3NpZ24gaG9sZXMgdG8gZXh0ZXJpb3IgcmluZ3MuCiAgICAgIC8vIEJhc2VkIG9uIGh0dHBzOi8vZ2l0aHViLmNvbS9tYm9zdG9jay9zaGFwZWZpbGUvYmxvYi92MC42LjIvc2hwL3BvbHlnb24uanMKICAgICAgZnVuY3Rpb24gY29udG91cih2YWx1ZXMsIHZhbHVlKSB7CiAgICAgICAgdmFyIHBvbHlnb25zID0gW10sCiAgICAgICAgICAgIGhvbGVzID0gW107CgogICAgICAgIGlzb3JpbmdzKHZhbHVlcywgdmFsdWUsIGZ1bmN0aW9uKHJpbmcpIHsKICAgICAgICAgIHNtb290aChyaW5nLCB2YWx1ZXMsIHZhbHVlKTsKICAgICAgICAgIGlmIChhcmVhKHJpbmcpID4gMCkgcG9seWdvbnMucHVzaChbcmluZ10pOwogICAgICAgICAgZWxzZSBob2xlcy5wdXNoKHJpbmcpOwogICAgICAgIH0pOwoKICAgICAgICBob2xlcy5mb3JFYWNoKGZ1bmN0aW9uKGhvbGUpIHsKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gcG9seWdvbnMubGVuZ3RoLCBwb2x5Z29uOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGlmIChjb250YWlucygocG9seWdvbiA9IHBvbHlnb25zW2ldKVswXSwgaG9sZSkgIT09IC0xKSB7CiAgICAgICAgICAgICAgcG9seWdvbi5wdXNoKGhvbGUpOwogICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICByZXR1cm4gewogICAgICAgICAgdHlwZTogIk11bHRpUG9seWdvbiIsCiAgICAgICAgICB2YWx1ZTogdmFsdWUsCiAgICAgICAgICBjb29yZGluYXRlczogcG9seWdvbnMKICAgICAgICB9OwogICAgICB9CgogICAgICAvLyBNYXJjaGluZyBzcXVhcmVzIHdpdGggaXNvbGluZXMgc3RpdGNoZWQgaW50byByaW5ncy4KICAgICAgLy8gQmFzZWQgb24gaHR0cHM6Ly9naXRodWIuY29tL3RvcG9qc29uL3RvcG9qc29uLWNsaWVudC9ibG9iL3YzLjAuMC9zcmMvc3RpdGNoLmpzCiAgICAgIGZ1bmN0aW9uIGlzb3JpbmdzKHZhbHVlcywgdmFsdWUsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIGZyYWdtZW50QnlTdGFydCA9IG5ldyBBcnJheSwKICAgICAgICAgICAgZnJhZ21lbnRCeUVuZCA9IG5ldyBBcnJheSwKICAgICAgICAgICAgeCwgeSwgdDAsIHQxLCB0MiwgdDM7CgogICAgICAgIC8vIFNwZWNpYWwgY2FzZSBmb3IgdGhlIGZpcnN0IHJvdyAoeSA9IC0xLCB0MiA9IHQzID0gMCkuCiAgICAgICAgeCA9IHkgPSAtMTsKICAgICAgICB0MSA9IHZhbHVlc1swXSA+PSB2YWx1ZTsKICAgICAgICBjYXNlc1t0MSA8PCAxXS5mb3JFYWNoKHN0aXRjaCk7CiAgICAgICAgd2hpbGUgKCsreCA8IGR4IC0gMSkgewogICAgICAgICAgdDAgPSB0MSwgdDEgPSB2YWx1ZXNbeCArIDFdID49IHZhbHVlOwogICAgICAgICAgY2FzZXNbdDAgfCB0MSA8PCAxXS5mb3JFYWNoKHN0aXRjaCk7CiAgICAgICAgfQogICAgICAgIGNhc2VzW3QxIDw8IDBdLmZvckVhY2goc3RpdGNoKTsKCiAgICAgICAgLy8gR2VuZXJhbCBjYXNlIGZvciB0aGUgaW50ZXJtZWRpYXRlIHJvd3MuCiAgICAgICAgd2hpbGUgKCsreSA8IGR5IC0gMSkgewogICAgICAgICAgeCA9IC0xOwogICAgICAgICAgdDEgPSB2YWx1ZXNbeSAqIGR4ICsgZHhdID49IHZhbHVlOwogICAgICAgICAgdDIgPSB2YWx1ZXNbeSAqIGR4XSA+PSB2YWx1ZTsKICAgICAgICAgIGNhc2VzW3QxIDw8IDEgfCB0MiA8PCAyXS5mb3JFYWNoKHN0aXRjaCk7CiAgICAgICAgICB3aGlsZSAoKyt4IDwgZHggLSAxKSB7CiAgICAgICAgICAgIHQwID0gdDEsIHQxID0gdmFsdWVzW3kgKiBkeCArIGR4ICsgeCArIDFdID49IHZhbHVlOwogICAgICAgICAgICB0MyA9IHQyLCB0MiA9IHZhbHVlc1t5ICogZHggKyB4ICsgMV0gPj0gdmFsdWU7CiAgICAgICAgICAgIGNhc2VzW3QwIHwgdDEgPDwgMSB8IHQyIDw8IDIgfCB0MyA8PCAzXS5mb3JFYWNoKHN0aXRjaCk7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlc1t0MSB8IHQyIDw8IDNdLmZvckVhY2goc3RpdGNoKTsKICAgICAgICB9CgogICAgICAgIC8vIFNwZWNpYWwgY2FzZSBmb3IgdGhlIGxhc3Qgcm93ICh5ID0gZHkgLSAxLCB0MCA9IHQxID0gMCkuCiAgICAgICAgeCA9IC0xOwogICAgICAgIHQyID0gdmFsdWVzW3kgKiBkeF0gPj0gdmFsdWU7CiAgICAgICAgY2FzZXNbdDIgPDwgMl0uZm9yRWFjaChzdGl0Y2gpOwogICAgICAgIHdoaWxlICgrK3ggPCBkeCAtIDEpIHsKICAgICAgICAgIHQzID0gdDIsIHQyID0gdmFsdWVzW3kgKiBkeCArIHggKyAxXSA+PSB2YWx1ZTsKICAgICAgICAgIGNhc2VzW3QyIDw8IDIgfCB0MyA8PCAzXS5mb3JFYWNoKHN0aXRjaCk7CiAgICAgICAgfQogICAgICAgIGNhc2VzW3QyIDw8IDNdLmZvckVhY2goc3RpdGNoKTsKCiAgICAgICAgZnVuY3Rpb24gc3RpdGNoKGxpbmUpIHsKICAgICAgICAgIHZhciBzdGFydCA9IFtsaW5lWzBdWzBdICsgeCwgbGluZVswXVsxXSArIHldLAogICAgICAgICAgICAgIGVuZCA9IFtsaW5lWzFdWzBdICsgeCwgbGluZVsxXVsxXSArIHldLAogICAgICAgICAgICAgIHN0YXJ0SW5kZXggPSBpbmRleChzdGFydCksCiAgICAgICAgICAgICAgZW5kSW5kZXggPSBpbmRleChlbmQpLAogICAgICAgICAgICAgIGYsIGc7CiAgICAgICAgICBpZiAoZiA9IGZyYWdtZW50QnlFbmRbc3RhcnRJbmRleF0pIHsKICAgICAgICAgICAgaWYgKGcgPSBmcmFnbWVudEJ5U3RhcnRbZW5kSW5kZXhdKSB7CiAgICAgICAgICAgICAgZGVsZXRlIGZyYWdtZW50QnlFbmRbZi5lbmRdOwogICAgICAgICAgICAgIGRlbGV0ZSBmcmFnbWVudEJ5U3RhcnRbZy5zdGFydF07CiAgICAgICAgICAgICAgaWYgKGYgPT09IGcpIHsKICAgICAgICAgICAgICAgIGYucmluZy5wdXNoKGVuZCk7CiAgICAgICAgICAgICAgICBjYWxsYmFjayhmLnJpbmcpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBmcmFnbWVudEJ5U3RhcnRbZi5zdGFydF0gPSBmcmFnbWVudEJ5RW5kW2cuZW5kXSA9IHtzdGFydDogZi5zdGFydCwgZW5kOiBnLmVuZCwgcmluZzogZi5yaW5nLmNvbmNhdChnLnJpbmcpfTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgZGVsZXRlIGZyYWdtZW50QnlFbmRbZi5lbmRdOwogICAgICAgICAgICAgIGYucmluZy5wdXNoKGVuZCk7CiAgICAgICAgICAgICAgZnJhZ21lbnRCeUVuZFtmLmVuZCA9IGVuZEluZGV4XSA9IGY7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAoZiA9IGZyYWdtZW50QnlTdGFydFtlbmRJbmRleF0pIHsKICAgICAgICAgICAgaWYgKGcgPSBmcmFnbWVudEJ5RW5kW3N0YXJ0SW5kZXhdKSB7CiAgICAgICAgICAgICAgZGVsZXRlIGZyYWdtZW50QnlTdGFydFtmLnN0YXJ0XTsKICAgICAgICAgICAgICBkZWxldGUgZnJhZ21lbnRCeUVuZFtnLmVuZF07CiAgICAgICAgICAgICAgaWYgKGYgPT09IGcpIHsKICAgICAgICAgICAgICAgIGYucmluZy5wdXNoKGVuZCk7CiAgICAgICAgICAgICAgICBjYWxsYmFjayhmLnJpbmcpOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBmcmFnbWVudEJ5U3RhcnRbZy5zdGFydF0gPSBmcmFnbWVudEJ5RW5kW2YuZW5kXSA9IHtzdGFydDogZy5zdGFydCwgZW5kOiBmLmVuZCwgcmluZzogZy5yaW5nLmNvbmNhdChmLnJpbmcpfTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgZGVsZXRlIGZyYWdtZW50QnlTdGFydFtmLnN0YXJ0XTsKICAgICAgICAgICAgICBmLnJpbmcudW5zaGlmdChzdGFydCk7CiAgICAgICAgICAgICAgZnJhZ21lbnRCeVN0YXJ0W2Yuc3RhcnQgPSBzdGFydEluZGV4XSA9IGY7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGZyYWdtZW50QnlTdGFydFtzdGFydEluZGV4XSA9IGZyYWdtZW50QnlFbmRbZW5kSW5kZXhdID0ge3N0YXJ0OiBzdGFydEluZGV4LCBlbmQ6IGVuZEluZGV4LCByaW5nOiBbc3RhcnQsIGVuZF19OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5kZXgocG9pbnQpIHsKICAgICAgICByZXR1cm4gcG9pbnRbMF0gKiAyICsgcG9pbnRbMV0gKiAoZHggKyAxKSAqIDQ7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNtb290aExpbmVhcihyaW5nLCB2YWx1ZXMsIHZhbHVlKSB7CiAgICAgICAgcmluZy5mb3JFYWNoKGZ1bmN0aW9uKHBvaW50KSB7CiAgICAgICAgICB2YXIgeCA9IHBvaW50WzBdLAogICAgICAgICAgICAgIHkgPSBwb2ludFsxXSwKICAgICAgICAgICAgICB4dCA9IHggfCAwLAogICAgICAgICAgICAgIHl0ID0geSB8IDAsCiAgICAgICAgICAgICAgdjAsCiAgICAgICAgICAgICAgdjEgPSB2YWx1ZXNbeXQgKiBkeCArIHh0XTsKICAgICAgICAgIGlmICh4ID4gMCAmJiB4IDwgZHggJiYgeHQgPT09IHgpIHsKICAgICAgICAgICAgdjAgPSB2YWx1ZXNbeXQgKiBkeCArIHh0IC0gMV07CiAgICAgICAgICAgIHBvaW50WzBdID0geCArICh2YWx1ZSAtIHYwKSAvICh2MSAtIHYwKSAtIDAuNTsKICAgICAgICAgIH0KICAgICAgICAgIGlmICh5ID4gMCAmJiB5IDwgZHkgJiYgeXQgPT09IHkpIHsKICAgICAgICAgICAgdjAgPSB2YWx1ZXNbKHl0IC0gMSkgKiBkeCArIHh0XTsKICAgICAgICAgICAgcG9pbnRbMV0gPSB5ICsgKHZhbHVlIC0gdjApIC8gKHYxIC0gdjApIC0gMC41OwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CgogICAgICBjb250b3Vycy5jb250b3VyID0gY29udG91cjsKCiAgICAgIGNvbnRvdXJzLnNpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW2R4LCBkeV07CiAgICAgICAgdmFyIF8wID0gTWF0aC5jZWlsKF9bMF0pLCBfMSA9IE1hdGguY2VpbChfWzFdKTsKICAgICAgICBpZiAoIShfMCA+IDApIHx8ICEoXzEgPiAwKSkgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIHNpemUiKTsKICAgICAgICByZXR1cm4gZHggPSBfMCwgZHkgPSBfMSwgY29udG91cnM7CiAgICAgIH07CgogICAgICBjb250b3Vycy50aHJlc2hvbGRzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRocmVzaG9sZCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IEFycmF5LmlzQXJyYXkoXykgPyBjb25zdGFudCQ2KHNsaWNlJDMuY2FsbChfKSkgOiBjb25zdGFudCQ2KF8pLCBjb250b3VycykgOiB0aHJlc2hvbGQ7CiAgICAgIH07CgogICAgICBjb250b3Vycy5zbW9vdGggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc21vb3RoID0gXyA/IHNtb290aExpbmVhciA6IG5vb3AkMSwgY29udG91cnMpIDogc21vb3RoID09PSBzbW9vdGhMaW5lYXI7CiAgICAgIH07CgogICAgICByZXR1cm4gY29udG91cnM7CiAgICB9CgogICAgLy8gVE9ETyBPcHRpbWl6ZSBlZGdlIGNhc2VzLgogICAgLy8gVE9ETyBPcHRpbWl6ZSBpbmRleCBjYWxjdWxhdGlvbi4KICAgIC8vIFRPRE8gT3B0aW1pemUgYXJndW1lbnRzLgogICAgZnVuY3Rpb24gYmx1clgoc291cmNlLCB0YXJnZXQsIHIpIHsKICAgICAgdmFyIG4gPSBzb3VyY2Uud2lkdGgsCiAgICAgICAgICBtID0gc291cmNlLmhlaWdodCwKICAgICAgICAgIHcgPSAociA8PCAxKSArIDE7CiAgICAgIGZvciAodmFyIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIHNyID0gMDsgaSA8IG4gKyByOyArK2kpIHsKICAgICAgICAgIGlmIChpIDwgbikgewogICAgICAgICAgICBzciArPSBzb3VyY2UuZGF0YVtpICsgaiAqIG5dOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGkgPj0gcikgewogICAgICAgICAgICBpZiAoaSA+PSB3KSB7CiAgICAgICAgICAgICAgc3IgLT0gc291cmNlLmRhdGFbaSAtIHcgKyBqICogbl07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGFyZ2V0LmRhdGFbaSAtIHIgKyBqICogbl0gPSBzciAvIE1hdGgubWluKGkgKyAxLCBuIC0gMSArIHcgLSBpLCB3KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICAvLyBUT0RPIE9wdGltaXplIGVkZ2UgY2FzZXMuCiAgICAvLyBUT0RPIE9wdGltaXplIGluZGV4IGNhbGN1bGF0aW9uLgogICAgLy8gVE9ETyBPcHRpbWl6ZSBhcmd1bWVudHMuCiAgICBmdW5jdGlvbiBibHVyWShzb3VyY2UsIHRhcmdldCwgcikgewogICAgICB2YXIgbiA9IHNvdXJjZS53aWR0aCwKICAgICAgICAgIG0gPSBzb3VyY2UuaGVpZ2h0LAogICAgICAgICAgdyA9IChyIDw8IDEpICsgMTsKICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBmb3IgKHZhciBqID0gMCwgc3IgPSAwOyBqIDwgbSArIHI7ICsraikgewogICAgICAgICAgaWYgKGogPCBtKSB7CiAgICAgICAgICAgIHNyICs9IHNvdXJjZS5kYXRhW2kgKyBqICogbl07CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaiA+PSByKSB7CiAgICAgICAgICAgIGlmIChqID49IHcpIHsKICAgICAgICAgICAgICBzciAtPSBzb3VyY2UuZGF0YVtpICsgKGogLSB3KSAqIG5dOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRhcmdldC5kYXRhW2kgKyAoaiAtIHIpICogbl0gPSBzciAvIE1hdGgubWluKGogKyAxLCBtIC0gMSArIHcgLSBqLCB3KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0WChkKSB7CiAgICAgIHJldHVybiBkWzBdOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRZKGQpIHsKICAgICAgcmV0dXJuIGRbMV07CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFdlaWdodCgpIHsKICAgICAgcmV0dXJuIDE7CiAgICB9CgogICAgZnVuY3Rpb24gZGVuc2l0eSgpIHsKICAgICAgdmFyIHggPSBkZWZhdWx0WCwKICAgICAgICAgIHkgPSBkZWZhdWx0WSwKICAgICAgICAgIHdlaWdodCA9IGRlZmF1bHRXZWlnaHQsCiAgICAgICAgICBkeCA9IDk2MCwKICAgICAgICAgIGR5ID0gNTAwLAogICAgICAgICAgciA9IDIwLCAvLyBibHVyIHJhZGl1cwogICAgICAgICAgayA9IDIsIC8vIGxvZzIoZ3JpZCBjZWxsIHNpemUpCiAgICAgICAgICBvID0gciAqIDMsIC8vIGdyaWQgb2Zmc2V0LCB0byBwYWQgZm9yIGJsdXIKICAgICAgICAgIG4gPSAoZHggKyBvICogMikgPj4gaywgLy8gZ3JpZCB3aWR0aAogICAgICAgICAgbSA9IChkeSArIG8gKiAyKSA+PiBrLCAvLyBncmlkIGhlaWdodAogICAgICAgICAgdGhyZXNob2xkID0gY29uc3RhbnQkNigyMCk7CgogICAgICBmdW5jdGlvbiBkZW5zaXR5KGRhdGEpIHsKICAgICAgICB2YXIgdmFsdWVzMCA9IG5ldyBGbG9hdDMyQXJyYXkobiAqIG0pLAogICAgICAgICAgICB2YWx1ZXMxID0gbmV3IEZsb2F0MzJBcnJheShuICogbSk7CgogICAgICAgIGRhdGEuZm9yRWFjaChmdW5jdGlvbihkLCBpLCBkYXRhKSB7CiAgICAgICAgICB2YXIgeGkgPSAoK3goZCwgaSwgZGF0YSkgKyBvKSA+PiBrLAogICAgICAgICAgICAgIHlpID0gKCt5KGQsIGksIGRhdGEpICsgbykgPj4gaywKICAgICAgICAgICAgICB3aSA9ICt3ZWlnaHQoZCwgaSwgZGF0YSk7CiAgICAgICAgICBpZiAoeGkgPj0gMCAmJiB4aSA8IG4gJiYgeWkgPj0gMCAmJiB5aSA8IG0pIHsKICAgICAgICAgICAgdmFsdWVzMFt4aSArIHlpICogbl0gKz0gd2k7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8vIFRPRE8gT3B0aW1pemUuCiAgICAgICAgYmx1clgoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczB9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMX0sIHIgPj4gayk7CiAgICAgICAgYmx1clkoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczF9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMH0sIHIgPj4gayk7CiAgICAgICAgYmx1clgoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczB9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMX0sIHIgPj4gayk7CiAgICAgICAgYmx1clkoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczF9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMH0sIHIgPj4gayk7CiAgICAgICAgYmx1clgoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczB9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMX0sIHIgPj4gayk7CiAgICAgICAgYmx1clkoe3dpZHRoOiBuLCBoZWlnaHQ6IG0sIGRhdGE6IHZhbHVlczF9LCB7d2lkdGg6IG4sIGhlaWdodDogbSwgZGF0YTogdmFsdWVzMH0sIHIgPj4gayk7CgogICAgICAgIHZhciB0eiA9IHRocmVzaG9sZCh2YWx1ZXMwKTsKCiAgICAgICAgLy8gQ29udmVydCBudW1iZXIgb2YgdGhyZXNob2xkcyBpbnRvIHVuaWZvcm0gdGhyZXNob2xkcy4KICAgICAgICBpZiAoIUFycmF5LmlzQXJyYXkodHopKSB7CiAgICAgICAgICB2YXIgc3RvcCA9IG1heCh2YWx1ZXMwKTsKICAgICAgICAgIHR6ID0gdGlja1N0ZXAoMCwgc3RvcCwgdHopOwogICAgICAgICAgdHogPSBzZXF1ZW5jZSgwLCBNYXRoLmZsb29yKHN0b3AgLyB0eikgKiB0eiwgdHopOwogICAgICAgICAgdHouc2hpZnQoKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBjb250b3VycygpCiAgICAgICAgICAgIC50aHJlc2hvbGRzKHR6KQogICAgICAgICAgICAuc2l6ZShbbiwgbV0pCiAgICAgICAgICAodmFsdWVzMCkKICAgICAgICAgICAgLm1hcCh0cmFuc2Zvcm0pOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2Zvcm0oZ2VvbWV0cnkpIHsKICAgICAgICBnZW9tZXRyeS52YWx1ZSAqPSBNYXRoLnBvdygyLCAtMiAqIGspOyAvLyBEZW5zaXR5IGluIHBvaW50cyBwZXIgc3F1YXJlIHBpeGVsLgogICAgICAgIGdlb21ldHJ5LmNvb3JkaW5hdGVzLmZvckVhY2godHJhbnNmb3JtUG9seWdvbik7CiAgICAgICAgcmV0dXJuIGdlb21ldHJ5OwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2Zvcm1Qb2x5Z29uKGNvb3JkaW5hdGVzKSB7CiAgICAgICAgY29vcmRpbmF0ZXMuZm9yRWFjaCh0cmFuc2Zvcm1SaW5nKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gdHJhbnNmb3JtUmluZyhjb29yZGluYXRlcykgewogICAgICAgIGNvb3JkaW5hdGVzLmZvckVhY2godHJhbnNmb3JtUG9pbnQpOwogICAgICB9CgogICAgICAvLyBUT0RPIE9wdGltaXplLgogICAgICBmdW5jdGlvbiB0cmFuc2Zvcm1Qb2ludChjb29yZGluYXRlcykgewogICAgICAgIGNvb3JkaW5hdGVzWzBdID0gY29vcmRpbmF0ZXNbMF0gKiBNYXRoLnBvdygyLCBrKSAtIG87CiAgICAgICAgY29vcmRpbmF0ZXNbMV0gPSBjb29yZGluYXRlc1sxXSAqIE1hdGgucG93KDIsIGspIC0gbzsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcmVzaXplKCkgewogICAgICAgIG8gPSByICogMzsKICAgICAgICBuID0gKGR4ICsgbyAqIDIpID4+IGs7CiAgICAgICAgbSA9IChkeSArIG8gKiAyKSA+PiBrOwogICAgICAgIHJldHVybiBkZW5zaXR5OwogICAgICB9CgogICAgICBkZW5zaXR5LnggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDYoK18pLCBkZW5zaXR5KSA6IHg7CiAgICAgIH07CgogICAgICBkZW5zaXR5LnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDYoK18pLCBkZW5zaXR5KSA6IHk7CiAgICAgIH07CgogICAgICBkZW5zaXR5LndlaWdodCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh3ZWlnaHQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ2KCtfKSwgZGVuc2l0eSkgOiB3ZWlnaHQ7CiAgICAgIH07CgogICAgICBkZW5zaXR5LnNpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW2R4LCBkeV07CiAgICAgICAgdmFyIF8wID0gTWF0aC5jZWlsKF9bMF0pLCBfMSA9IE1hdGguY2VpbChfWzFdKTsKICAgICAgICBpZiAoIShfMCA+PSAwKSAmJiAhKF8wID49IDApKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgc2l6ZSIpOwogICAgICAgIHJldHVybiBkeCA9IF8wLCBkeSA9IF8xLCByZXNpemUoKTsKICAgICAgfTsKCiAgICAgIGRlbnNpdHkuY2VsbFNpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gMSA8PCBrOwogICAgICAgIGlmICghKChfID0gK18pID49IDEpKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2VsbCBzaXplIik7CiAgICAgICAgcmV0dXJuIGsgPSBNYXRoLmZsb29yKE1hdGgubG9nKF8pIC8gTWF0aC5MTjIpLCByZXNpemUoKTsKICAgICAgfTsKCiAgICAgIGRlbnNpdHkudGhyZXNob2xkcyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aHJlc2hvbGQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBBcnJheS5pc0FycmF5KF8pID8gY29uc3RhbnQkNihzbGljZSQzLmNhbGwoXykpIDogY29uc3RhbnQkNihfKSwgZGVuc2l0eSkgOiB0aHJlc2hvbGQ7CiAgICAgIH07CgogICAgICBkZW5zaXR5LmJhbmR3aWR0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBNYXRoLnNxcnQociAqIChyICsgMSkpOwogICAgICAgIGlmICghKChfID0gK18pID49IDApKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgYmFuZHdpZHRoIik7CiAgICAgICAgcmV0dXJuIHIgPSBNYXRoLnJvdW5kKChNYXRoLnNxcnQoNCAqIF8gKiBfICsgMSkgLSAxKSAvIDIpLCByZXNpemUoKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBkZW5zaXR5OwogICAgfQoKICAgIHZhciBFT0wgPSB7fSwKICAgICAgICBFT0YgPSB7fSwKICAgICAgICBRVU9URSA9IDM0LAogICAgICAgIE5FV0xJTkUgPSAxMCwKICAgICAgICBSRVRVUk4gPSAxMzsKCiAgICBmdW5jdGlvbiBvYmplY3RDb252ZXJ0ZXIoY29sdW1ucykgewogICAgICByZXR1cm4gbmV3IEZ1bmN0aW9uKCJkIiwgInJldHVybiB7IiArIGNvbHVtbnMubWFwKGZ1bmN0aW9uKG5hbWUsIGkpIHsKICAgICAgICByZXR1cm4gSlNPTi5zdHJpbmdpZnkobmFtZSkgKyAiOiBkWyIgKyBpICsgIl0gfHwgXCJcIiI7CiAgICAgIH0pLmpvaW4oIiwiKSArICJ9Iik7CiAgICB9CgogICAgZnVuY3Rpb24gY3VzdG9tQ29udmVydGVyKGNvbHVtbnMsIGYpIHsKICAgICAgdmFyIG9iamVjdCA9IG9iamVjdENvbnZlcnRlcihjb2x1bW5zKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHJvdywgaSkgewogICAgICAgIHJldHVybiBmKG9iamVjdChyb3cpLCBpLCBjb2x1bW5zKTsKICAgICAgfTsKICAgIH0KCiAgICAvLyBDb21wdXRlIHVuaXF1ZSBjb2x1bW5zIGluIG9yZGVyIG9mIGRpc2NvdmVyeS4KICAgIGZ1bmN0aW9uIGluZmVyQ29sdW1ucyhyb3dzKSB7CiAgICAgIHZhciBjb2x1bW5TZXQgPSBPYmplY3QuY3JlYXRlKG51bGwpLAogICAgICAgICAgY29sdW1ucyA9IFtdOwoKICAgICAgcm93cy5mb3JFYWNoKGZ1bmN0aW9uKHJvdykgewogICAgICAgIGZvciAodmFyIGNvbHVtbiBpbiByb3cpIHsKICAgICAgICAgIGlmICghKGNvbHVtbiBpbiBjb2x1bW5TZXQpKSB7CiAgICAgICAgICAgIGNvbHVtbnMucHVzaChjb2x1bW5TZXRbY29sdW1uXSA9IGNvbHVtbik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9KTsKCiAgICAgIHJldHVybiBjb2x1bW5zOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhZCh2YWx1ZSwgd2lkdGgpIHsKICAgICAgdmFyIHMgPSB2YWx1ZSArICIiLCBsZW5ndGggPSBzLmxlbmd0aDsKICAgICAgcmV0dXJuIGxlbmd0aCA8IHdpZHRoID8gbmV3IEFycmF5KHdpZHRoIC0gbGVuZ3RoICsgMSkuam9pbigwKSArIHMgOiBzOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFllYXIoeWVhcikgewogICAgICByZXR1cm4geWVhciA8IDAgPyAiLSIgKyBwYWQoLXllYXIsIDYpCiAgICAgICAgOiB5ZWFyID4gOTk5OSA/ICIrIiArIHBhZCh5ZWFyLCA2KQogICAgICAgIDogcGFkKHllYXIsIDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdERhdGUoZGF0ZSkgewogICAgICB2YXIgaG91cnMgPSBkYXRlLmdldFVUQ0hvdXJzKCksCiAgICAgICAgICBtaW51dGVzID0gZGF0ZS5nZXRVVENNaW51dGVzKCksCiAgICAgICAgICBzZWNvbmRzID0gZGF0ZS5nZXRVVENTZWNvbmRzKCksCiAgICAgICAgICBtaWxsaXNlY29uZHMgPSBkYXRlLmdldFVUQ01pbGxpc2Vjb25kcygpOwogICAgICByZXR1cm4gaXNOYU4oZGF0ZSkgPyAiSW52YWxpZCBEYXRlIgogICAgICAgICAgOiBmb3JtYXRZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSkgKyAiLSIgKyBwYWQoZGF0ZS5nZXRVVENNb250aCgpICsgMSwgMikgKyAiLSIgKyBwYWQoZGF0ZS5nZXRVVENEYXRlKCksIDIpCiAgICAgICAgICArIChtaWxsaXNlY29uZHMgPyAiVCIgKyBwYWQoaG91cnMsIDIpICsgIjoiICsgcGFkKG1pbnV0ZXMsIDIpICsgIjoiICsgcGFkKHNlY29uZHMsIDIpICsgIi4iICsgcGFkKG1pbGxpc2Vjb25kcywgMykgKyAiWiIKICAgICAgICAgIDogc2Vjb25kcyA/ICJUIiArIHBhZChob3VycywgMikgKyAiOiIgKyBwYWQobWludXRlcywgMikgKyAiOiIgKyBwYWQoc2Vjb25kcywgMikgKyAiWiIKICAgICAgICAgIDogbWludXRlcyB8fCBob3VycyA/ICJUIiArIHBhZChob3VycywgMikgKyAiOiIgKyBwYWQobWludXRlcywgMikgKyAiWiIKICAgICAgICAgIDogIiIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRzdkZvcm1hdChkZWxpbWl0ZXIpIHsKICAgICAgdmFyIHJlRm9ybWF0ID0gbmV3IFJlZ0V4cCgiW1wiIiArIGRlbGltaXRlciArICJcblxyXSIpLAogICAgICAgICAgREVMSU1JVEVSID0gZGVsaW1pdGVyLmNoYXJDb2RlQXQoMCk7CgogICAgICBmdW5jdGlvbiBwYXJzZSh0ZXh0LCBmKSB7CiAgICAgICAgdmFyIGNvbnZlcnQsIGNvbHVtbnMsIHJvd3MgPSBwYXJzZVJvd3ModGV4dCwgZnVuY3Rpb24ocm93LCBpKSB7CiAgICAgICAgICBpZiAoY29udmVydCkgcmV0dXJuIGNvbnZlcnQocm93LCBpIC0gMSk7CiAgICAgICAgICBjb2x1bW5zID0gcm93LCBjb252ZXJ0ID0gZiA/IGN1c3RvbUNvbnZlcnRlcihyb3csIGYpIDogb2JqZWN0Q29udmVydGVyKHJvdyk7CiAgICAgICAgfSk7CiAgICAgICAgcm93cy5jb2x1bW5zID0gY29sdW1ucyB8fCBbXTsKICAgICAgICByZXR1cm4gcm93czsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VSb3dzKHRleHQsIGYpIHsKICAgICAgICB2YXIgcm93cyA9IFtdLCAvLyBvdXRwdXQgcm93cwogICAgICAgICAgICBOID0gdGV4dC5sZW5ndGgsCiAgICAgICAgICAgIEkgPSAwLCAvLyBjdXJyZW50IGNoYXJhY3RlciBpbmRleAogICAgICAgICAgICBuID0gMCwgLy8gY3VycmVudCBsaW5lIG51bWJlcgogICAgICAgICAgICB0LCAvLyBjdXJyZW50IHRva2VuCiAgICAgICAgICAgIGVvZiA9IE4gPD0gMCwgLy8gY3VycmVudCB0b2tlbiBmb2xsb3dlZCBieSBFT0Y/CiAgICAgICAgICAgIGVvbCA9IGZhbHNlOyAvLyBjdXJyZW50IHRva2VuIGZvbGxvd2VkIGJ5IEVPTD8KCiAgICAgICAgLy8gU3RyaXAgdGhlIHRyYWlsaW5nIG5ld2xpbmUuCiAgICAgICAgaWYgKHRleHQuY2hhckNvZGVBdChOIC0gMSkgPT09IE5FV0xJTkUpIC0tTjsKICAgICAgICBpZiAodGV4dC5jaGFyQ29kZUF0KE4gLSAxKSA9PT0gUkVUVVJOKSAtLU47CgogICAgICAgIGZ1bmN0aW9uIHRva2VuKCkgewogICAgICAgICAgaWYgKGVvZikgcmV0dXJuIEVPRjsKICAgICAgICAgIGlmIChlb2wpIHJldHVybiBlb2wgPSBmYWxzZSwgRU9MOwoKICAgICAgICAgIC8vIFVuZXNjYXBlIHF1b3Rlcy4KICAgICAgICAgIHZhciBpLCBqID0gSSwgYzsKICAgICAgICAgIGlmICh0ZXh0LmNoYXJDb2RlQXQoaikgPT09IFFVT1RFKSB7CiAgICAgICAgICAgIHdoaWxlIChJKysgPCBOICYmIHRleHQuY2hhckNvZGVBdChJKSAhPT0gUVVPVEUgfHwgdGV4dC5jaGFyQ29kZUF0KCsrSSkgPT09IFFVT1RFKTsKICAgICAgICAgICAgaWYgKChpID0gSSkgPj0gTikgZW9mID0gdHJ1ZTsKICAgICAgICAgICAgZWxzZSBpZiAoKGMgPSB0ZXh0LmNoYXJDb2RlQXQoSSsrKSkgPT09IE5FV0xJTkUpIGVvbCA9IHRydWU7CiAgICAgICAgICAgIGVsc2UgaWYgKGMgPT09IFJFVFVSTikgeyBlb2wgPSB0cnVlOyBpZiAodGV4dC5jaGFyQ29kZUF0KEkpID09PSBORVdMSU5FKSArK0k7IH0KICAgICAgICAgICAgcmV0dXJuIHRleHQuc2xpY2UoaiArIDEsIGkgLSAxKS5yZXBsYWNlKC8iIi9nLCAiXCIiKTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBGaW5kIG5leHQgZGVsaW1pdGVyIG9yIG5ld2xpbmUuCiAgICAgICAgICB3aGlsZSAoSSA8IE4pIHsKICAgICAgICAgICAgaWYgKChjID0gdGV4dC5jaGFyQ29kZUF0KGkgPSBJKyspKSA9PT0gTkVXTElORSkgZW9sID0gdHJ1ZTsKICAgICAgICAgICAgZWxzZSBpZiAoYyA9PT0gUkVUVVJOKSB7IGVvbCA9IHRydWU7IGlmICh0ZXh0LmNoYXJDb2RlQXQoSSkgPT09IE5FV0xJTkUpICsrSTsgfQogICAgICAgICAgICBlbHNlIGlmIChjICE9PSBERUxJTUlURVIpIGNvbnRpbnVlOwogICAgICAgICAgICByZXR1cm4gdGV4dC5zbGljZShqLCBpKTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBSZXR1cm4gbGFzdCB0b2tlbiBiZWZvcmUgRU9GLgogICAgICAgICAgcmV0dXJuIGVvZiA9IHRydWUsIHRleHQuc2xpY2UoaiwgTik7CiAgICAgICAgfQoKICAgICAgICB3aGlsZSAoKHQgPSB0b2tlbigpKSAhPT0gRU9GKSB7CiAgICAgICAgICB2YXIgcm93ID0gW107CiAgICAgICAgICB3aGlsZSAodCAhPT0gRU9MICYmIHQgIT09IEVPRikgcm93LnB1c2godCksIHQgPSB0b2tlbigpOwogICAgICAgICAgaWYgKGYgJiYgKHJvdyA9IGYocm93LCBuKyspKSA9PSBudWxsKSBjb250aW51ZTsKICAgICAgICAgIHJvd3MucHVzaChyb3cpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHJvd3M7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHByZWZvcm1hdEJvZHkocm93cywgY29sdW1ucykgewogICAgICAgIHJldHVybiByb3dzLm1hcChmdW5jdGlvbihyb3cpIHsKICAgICAgICAgIHJldHVybiBjb2x1bW5zLm1hcChmdW5jdGlvbihjb2x1bW4pIHsKICAgICAgICAgICAgcmV0dXJuIGZvcm1hdFZhbHVlKHJvd1tjb2x1bW5dKTsKICAgICAgICAgIH0pLmpvaW4oZGVsaW1pdGVyKTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0KHJvd3MsIGNvbHVtbnMpIHsKICAgICAgICBpZiAoY29sdW1ucyA9PSBudWxsKSBjb2x1bW5zID0gaW5mZXJDb2x1bW5zKHJvd3MpOwogICAgICAgIHJldHVybiBbY29sdW1ucy5tYXAoZm9ybWF0VmFsdWUpLmpvaW4oZGVsaW1pdGVyKV0uY29uY2F0KHByZWZvcm1hdEJvZHkocm93cywgY29sdW1ucykpLmpvaW4oIlxuIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdEJvZHkocm93cywgY29sdW1ucykgewogICAgICAgIGlmIChjb2x1bW5zID09IG51bGwpIGNvbHVtbnMgPSBpbmZlckNvbHVtbnMocm93cyk7CiAgICAgICAgcmV0dXJuIHByZWZvcm1hdEJvZHkocm93cywgY29sdW1ucykuam9pbigiXG4iKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0Um93cyhyb3dzKSB7CiAgICAgICAgcmV0dXJuIHJvd3MubWFwKGZvcm1hdFJvdykuam9pbigiXG4iKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0Um93KHJvdykgewogICAgICAgIHJldHVybiByb3cubWFwKGZvcm1hdFZhbHVlKS5qb2luKGRlbGltaXRlcik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFZhbHVlKHZhbHVlKSB7CiAgICAgICAgcmV0dXJuIHZhbHVlID09IG51bGwgPyAiIgogICAgICAgICAgICA6IHZhbHVlIGluc3RhbmNlb2YgRGF0ZSA/IGZvcm1hdERhdGUodmFsdWUpCiAgICAgICAgICAgIDogcmVGb3JtYXQudGVzdCh2YWx1ZSArPSAiIikgPyAiXCIiICsgdmFsdWUucmVwbGFjZSgvIi9nLCAiXCJcIiIpICsgIlwiIgogICAgICAgICAgICA6IHZhbHVlOwogICAgICB9CgogICAgICByZXR1cm4gewogICAgICAgIHBhcnNlOiBwYXJzZSwKICAgICAgICBwYXJzZVJvd3M6IHBhcnNlUm93cywKICAgICAgICBmb3JtYXQ6IGZvcm1hdCwKICAgICAgICBmb3JtYXRCb2R5OiBmb3JtYXRCb2R5LAogICAgICAgIGZvcm1hdFJvd3M6IGZvcm1hdFJvd3MsCiAgICAgICAgZm9ybWF0Um93OiBmb3JtYXRSb3csCiAgICAgICAgZm9ybWF0VmFsdWU6IGZvcm1hdFZhbHVlCiAgICAgIH07CiAgICB9CgogICAgdmFyIGNzdiA9IGRzdkZvcm1hdCgiLCIpOwoKICAgIHZhciBjc3ZQYXJzZSA9IGNzdi5wYXJzZTsKICAgIHZhciBjc3ZQYXJzZVJvd3MgPSBjc3YucGFyc2VSb3dzOwogICAgdmFyIGNzdkZvcm1hdCA9IGNzdi5mb3JtYXQ7CiAgICB2YXIgY3N2Rm9ybWF0Qm9keSA9IGNzdi5mb3JtYXRCb2R5OwogICAgdmFyIGNzdkZvcm1hdFJvd3MgPSBjc3YuZm9ybWF0Um93czsKICAgIHZhciBjc3ZGb3JtYXRSb3cgPSBjc3YuZm9ybWF0Um93OwogICAgdmFyIGNzdkZvcm1hdFZhbHVlID0gY3N2LmZvcm1hdFZhbHVlOwoKICAgIHZhciB0c3YgPSBkc3ZGb3JtYXQoIlx0Iik7CgogICAgdmFyIHRzdlBhcnNlID0gdHN2LnBhcnNlOwogICAgdmFyIHRzdlBhcnNlUm93cyA9IHRzdi5wYXJzZVJvd3M7CiAgICB2YXIgdHN2Rm9ybWF0ID0gdHN2LmZvcm1hdDsKICAgIHZhciB0c3ZGb3JtYXRCb2R5ID0gdHN2LmZvcm1hdEJvZHk7CiAgICB2YXIgdHN2Rm9ybWF0Um93cyA9IHRzdi5mb3JtYXRSb3dzOwogICAgdmFyIHRzdkZvcm1hdFJvdyA9IHRzdi5mb3JtYXRSb3c7CiAgICB2YXIgdHN2Rm9ybWF0VmFsdWUgPSB0c3YuZm9ybWF0VmFsdWU7CgogICAgZnVuY3Rpb24gYXV0b1R5cGUob2JqZWN0KSB7CiAgICAgIGZvciAodmFyIGtleSBpbiBvYmplY3QpIHsKICAgICAgICB2YXIgdmFsdWUgPSBvYmplY3Rba2V5XS50cmltKCksIG51bWJlciwgbTsKICAgICAgICBpZiAoIXZhbHVlKSB2YWx1ZSA9IG51bGw7CiAgICAgICAgZWxzZSBpZiAodmFsdWUgPT09ICJ0cnVlIikgdmFsdWUgPSB0cnVlOwogICAgICAgIGVsc2UgaWYgKHZhbHVlID09PSAiZmFsc2UiKSB2YWx1ZSA9IGZhbHNlOwogICAgICAgIGVsc2UgaWYgKHZhbHVlID09PSAiTmFOIikgdmFsdWUgPSBOYU47CiAgICAgICAgZWxzZSBpZiAoIWlzTmFOKG51bWJlciA9ICt2YWx1ZSkpIHZhbHVlID0gbnVtYmVyOwogICAgICAgIGVsc2UgaWYgKG0gPSB2YWx1ZS5tYXRjaCgvXihbLStdXGR7Mn0pP1xkezR9KC1cZHsyfSgtXGR7Mn0pPyk/KFRcZHsyfTpcZHsyfSg6XGR7Mn0oXC5cZHszfSk/KT8oWnxbLStdXGR7Mn06XGR7Mn0pPyk/JC8pKSB7CiAgICAgICAgICBpZiAoZml4dHogJiYgISFtWzRdICYmICFtWzddKSB2YWx1ZSA9IHZhbHVlLnJlcGxhY2UoLy0vZywgIi8iKS5yZXBsYWNlKC9ULywgIiAiKTsKICAgICAgICAgIHZhbHVlID0gbmV3IERhdGUodmFsdWUpOwogICAgICAgIH0KICAgICAgICBlbHNlIGNvbnRpbnVlOwogICAgICAgIG9iamVjdFtrZXldID0gdmFsdWU7CiAgICAgIH0KICAgICAgcmV0dXJuIG9iamVjdDsKICAgIH0KCiAgICAvLyBodHRwczovL2dpdGh1Yi5jb20vZDMvZDMtZHN2L2lzc3Vlcy80NQogICAgdmFyIGZpeHR6ID0gbmV3IERhdGUoIjIwMTktMDEtMDFUMDA6MDAiKS5nZXRIb3VycygpIHx8IG5ldyBEYXRlKCIyMDE5LTA3LTAxVDAwOjAwIikuZ2V0SG91cnMoKTsKCiAgICBmdW5jdGlvbiByZXNwb25zZUJsb2IocmVzcG9uc2UpIHsKICAgICAgaWYgKCFyZXNwb25zZS5vaykgdGhyb3cgbmV3IEVycm9yKHJlc3BvbnNlLnN0YXR1cyArICIgIiArIHJlc3BvbnNlLnN0YXR1c1RleHQpOwogICAgICByZXR1cm4gcmVzcG9uc2UuYmxvYigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJsb2IoaW5wdXQsIGluaXQpIHsKICAgICAgcmV0dXJuIGZldGNoKGlucHV0LCBpbml0KS50aGVuKHJlc3BvbnNlQmxvYik7CiAgICB9CgogICAgZnVuY3Rpb24gcmVzcG9uc2VBcnJheUJ1ZmZlcihyZXNwb25zZSkgewogICAgICBpZiAoIXJlc3BvbnNlLm9rKSB0aHJvdyBuZXcgRXJyb3IocmVzcG9uc2Uuc3RhdHVzICsgIiAiICsgcmVzcG9uc2Uuc3RhdHVzVGV4dCk7CiAgICAgIHJldHVybiByZXNwb25zZS5hcnJheUJ1ZmZlcigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJ1ZmZlcihpbnB1dCwgaW5pdCkgewogICAgICByZXR1cm4gZmV0Y2goaW5wdXQsIGluaXQpLnRoZW4ocmVzcG9uc2VBcnJheUJ1ZmZlcik7CiAgICB9CgogICAgZnVuY3Rpb24gcmVzcG9uc2VUZXh0KHJlc3BvbnNlKSB7CiAgICAgIGlmICghcmVzcG9uc2Uub2spIHRocm93IG5ldyBFcnJvcihyZXNwb25zZS5zdGF0dXMgKyAiICIgKyByZXNwb25zZS5zdGF0dXNUZXh0KTsKICAgICAgcmV0dXJuIHJlc3BvbnNlLnRleHQoKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0KGlucHV0LCBpbml0KSB7CiAgICAgIHJldHVybiBmZXRjaChpbnB1dCwgaW5pdCkudGhlbihyZXNwb25zZVRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRzdlBhcnNlKHBhcnNlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihpbnB1dCwgaW5pdCwgcm93KSB7CiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDIgJiYgdHlwZW9mIGluaXQgPT09ICJmdW5jdGlvbiIpIHJvdyA9IGluaXQsIGluaXQgPSB1bmRlZmluZWQ7CiAgICAgICAgcmV0dXJuIHRleHQoaW5wdXQsIGluaXQpLnRoZW4oZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICAgIHJldHVybiBwYXJzZShyZXNwb25zZSwgcm93KTsKICAgICAgICB9KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkc3YoZGVsaW1pdGVyLCBpbnB1dCwgaW5pdCwgcm93KSB7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID09PSAzICYmIHR5cGVvZiBpbml0ID09PSAiZnVuY3Rpb24iKSByb3cgPSBpbml0LCBpbml0ID0gdW5kZWZpbmVkOwogICAgICB2YXIgZm9ybWF0ID0gZHN2Rm9ybWF0KGRlbGltaXRlcik7CiAgICAgIHJldHVybiB0ZXh0KGlucHV0LCBpbml0KS50aGVuKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgcmV0dXJuIGZvcm1hdC5wYXJzZShyZXNwb25zZSwgcm93KTsKICAgICAgfSk7CiAgICB9CgogICAgdmFyIGNzdiQxID0gZHN2UGFyc2UoY3N2UGFyc2UpOwogICAgdmFyIHRzdiQxID0gZHN2UGFyc2UodHN2UGFyc2UpOwoKICAgIGZ1bmN0aW9uIGltYWdlKGlucHV0LCBpbml0KSB7CiAgICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgICB2YXIgaW1hZ2UgPSBuZXcgSW1hZ2U7CiAgICAgICAgZm9yICh2YXIga2V5IGluIGluaXQpIGltYWdlW2tleV0gPSBpbml0W2tleV07CiAgICAgICAgaW1hZ2Uub25lcnJvciA9IHJlamVjdDsKICAgICAgICBpbWFnZS5vbmxvYWQgPSBmdW5jdGlvbigpIHsgcmVzb2x2ZShpbWFnZSk7IH07CiAgICAgICAgaW1hZ2Uuc3JjID0gaW5wdXQ7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHJlc3BvbnNlSnNvbihyZXNwb25zZSkgewogICAgICBpZiAoIXJlc3BvbnNlLm9rKSB0aHJvdyBuZXcgRXJyb3IocmVzcG9uc2Uuc3RhdHVzICsgIiAiICsgcmVzcG9uc2Uuc3RhdHVzVGV4dCk7CiAgICAgIGlmIChyZXNwb25zZS5zdGF0dXMgPT09IDIwNCB8fCByZXNwb25zZS5zdGF0dXMgPT09IDIwNSkgcmV0dXJuOwogICAgICByZXR1cm4gcmVzcG9uc2UuanNvbigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGpzb24oaW5wdXQsIGluaXQpIHsKICAgICAgcmV0dXJuIGZldGNoKGlucHV0LCBpbml0KS50aGVuKHJlc3BvbnNlSnNvbik7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VyKHR5cGUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGlucHV0LCBpbml0KSAgewogICAgICAgIHJldHVybiB0ZXh0KGlucHV0LCBpbml0KS50aGVuKGZ1bmN0aW9uKHRleHQpIHsKICAgICAgICAgIHJldHVybiAobmV3IERPTVBhcnNlcikucGFyc2VGcm9tU3RyaW5nKHRleHQsIHR5cGUpOwogICAgICAgIH0pOwogICAgICB9OwogICAgfQoKICAgIHZhciB4bWwgPSBwYXJzZXIoImFwcGxpY2F0aW9uL3htbCIpOwoKICAgIHZhciBodG1sJDEgPSBwYXJzZXIoInRleHQvaHRtbCIpOwoKICAgIHZhciBzdmcgPSBwYXJzZXIoImltYWdlL3N2Zyt4bWwiKTsKCiAgICBmdW5jdGlvbiBjZW50ZXIkMSh4LCB5KSB7CiAgICAgIHZhciBub2RlczsKCiAgICAgIGlmICh4ID09IG51bGwpIHggPSAwOwogICAgICBpZiAoeSA9PSBudWxsKSB5ID0gMDsKCiAgICAgIGZ1bmN0aW9uIGZvcmNlKCkgewogICAgICAgIHZhciBpLAogICAgICAgICAgICBuID0gbm9kZXMubGVuZ3RoLAogICAgICAgICAgICBub2RlLAogICAgICAgICAgICBzeCA9IDAsCiAgICAgICAgICAgIHN5ID0gMDsKCiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgbm9kZSA9IG5vZGVzW2ldLCBzeCArPSBub2RlLngsIHN5ICs9IG5vZGUueTsKICAgICAgICB9CgogICAgICAgIGZvciAoc3ggPSBzeCAvIG4gLSB4LCBzeSA9IHN5IC8gbiAtIHksIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUueCAtPSBzeCwgbm9kZS55IC09IHN5OwogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yY2UuaW5pdGlhbGl6ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBub2RlcyA9IF87CiAgICAgIH07CgogICAgICBmb3JjZS54ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHggPSArXywgZm9yY2UpIDogeDsKICAgICAgfTsKCiAgICAgIGZvcmNlLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeSA9ICtfLCBmb3JjZSkgOiB5OwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JDcoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gamlnZ2xlKCkgewogICAgICByZXR1cm4gKE1hdGgucmFuZG9tKCkgLSAwLjUpICogMWUtNjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX2FkZChkKSB7CiAgICAgIHZhciB4ID0gK3RoaXMuX3guY2FsbChudWxsLCBkKSwKICAgICAgICAgIHkgPSArdGhpcy5feS5jYWxsKG51bGwsIGQpOwogICAgICByZXR1cm4gYWRkKHRoaXMuY292ZXIoeCwgeSksIHgsIHksIGQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFkZCh0cmVlLCB4LCB5LCBkKSB7CiAgICAgIGlmIChpc05hTih4KSB8fCBpc05hTih5KSkgcmV0dXJuIHRyZWU7IC8vIGlnbm9yZSBpbnZhbGlkIHBvaW50cwoKICAgICAgdmFyIHBhcmVudCwKICAgICAgICAgIG5vZGUgPSB0cmVlLl9yb290LAogICAgICAgICAgbGVhZiA9IHtkYXRhOiBkfSwKICAgICAgICAgIHgwID0gdHJlZS5feDAsCiAgICAgICAgICB5MCA9IHRyZWUuX3kwLAogICAgICAgICAgeDEgPSB0cmVlLl94MSwKICAgICAgICAgIHkxID0gdHJlZS5feTEsCiAgICAgICAgICB4bSwKICAgICAgICAgIHltLAogICAgICAgICAgeHAsCiAgICAgICAgICB5cCwKICAgICAgICAgIHJpZ2h0LAogICAgICAgICAgYm90dG9tLAogICAgICAgICAgaSwKICAgICAgICAgIGo7CgogICAgICAvLyBJZiB0aGUgdHJlZSBpcyBlbXB0eSwgaW5pdGlhbGl6ZSB0aGUgcm9vdCBhcyBhIGxlYWYuCiAgICAgIGlmICghbm9kZSkgcmV0dXJuIHRyZWUuX3Jvb3QgPSBsZWFmLCB0cmVlOwoKICAgICAgLy8gRmluZCB0aGUgZXhpc3RpbmcgbGVhZiBmb3IgdGhlIG5ldyBwb2ludCwgb3IgYWRkIGl0LgogICAgICB3aGlsZSAobm9kZS5sZW5ndGgpIHsKICAgICAgICBpZiAocmlnaHQgPSB4ID49ICh4bSA9ICh4MCArIHgxKSAvIDIpKSB4MCA9IHhtOyBlbHNlIHgxID0geG07CiAgICAgICAgaWYgKGJvdHRvbSA9IHkgPj0gKHltID0gKHkwICsgeTEpIC8gMikpIHkwID0geW07IGVsc2UgeTEgPSB5bTsKICAgICAgICBpZiAocGFyZW50ID0gbm9kZSwgIShub2RlID0gbm9kZVtpID0gYm90dG9tIDw8IDEgfCByaWdodF0pKSByZXR1cm4gcGFyZW50W2ldID0gbGVhZiwgdHJlZTsKICAgICAgfQoKICAgICAgLy8gSXMgdGhlIG5ldyBwb2ludCBpcyBleGFjdGx5IGNvaW5jaWRlbnQgd2l0aCB0aGUgZXhpc3RpbmcgcG9pbnQ/CiAgICAgIHhwID0gK3RyZWUuX3guY2FsbChudWxsLCBub2RlLmRhdGEpOwogICAgICB5cCA9ICt0cmVlLl95LmNhbGwobnVsbCwgbm9kZS5kYXRhKTsKICAgICAgaWYgKHggPT09IHhwICYmIHkgPT09IHlwKSByZXR1cm4gbGVhZi5uZXh0ID0gbm9kZSwgcGFyZW50ID8gcGFyZW50W2ldID0gbGVhZiA6IHRyZWUuX3Jvb3QgPSBsZWFmLCB0cmVlOwoKICAgICAgLy8gT3RoZXJ3aXNlLCBzcGxpdCB0aGUgbGVhZiBub2RlIHVudGlsIHRoZSBvbGQgYW5kIG5ldyBwb2ludCBhcmUgc2VwYXJhdGVkLgogICAgICBkbyB7CiAgICAgICAgcGFyZW50ID0gcGFyZW50ID8gcGFyZW50W2ldID0gbmV3IEFycmF5KDQpIDogdHJlZS5fcm9vdCA9IG5ldyBBcnJheSg0KTsKICAgICAgICBpZiAocmlnaHQgPSB4ID49ICh4bSA9ICh4MCArIHgxKSAvIDIpKSB4MCA9IHhtOyBlbHNlIHgxID0geG07CiAgICAgICAgaWYgKGJvdHRvbSA9IHkgPj0gKHltID0gKHkwICsgeTEpIC8gMikpIHkwID0geW07IGVsc2UgeTEgPSB5bTsKICAgICAgfSB3aGlsZSAoKGkgPSBib3R0b20gPDwgMSB8IHJpZ2h0KSA9PT0gKGogPSAoeXAgPj0geW0pIDw8IDEgfCAoeHAgPj0geG0pKSk7CiAgICAgIHJldHVybiBwYXJlbnRbal0gPSBub2RlLCBwYXJlbnRbaV0gPSBsZWFmLCB0cmVlOwogICAgfQoKICAgIGZ1bmN0aW9uIGFkZEFsbChkYXRhKSB7CiAgICAgIHZhciBkLCBpLCBuID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICB4LAogICAgICAgICAgeSwKICAgICAgICAgIHh6ID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgeXogPSBuZXcgQXJyYXkobiksCiAgICAgICAgICB4MCA9IEluZmluaXR5LAogICAgICAgICAgeTAgPSBJbmZpbml0eSwKICAgICAgICAgIHgxID0gLUluZmluaXR5LAogICAgICAgICAgeTEgPSAtSW5maW5pdHk7CgogICAgICAvLyBDb21wdXRlIHRoZSBwb2ludHMgYW5kIHRoZWlyIGV4dGVudC4KICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgIGlmIChpc05hTih4ID0gK3RoaXMuX3guY2FsbChudWxsLCBkID0gZGF0YVtpXSkpIHx8IGlzTmFOKHkgPSArdGhpcy5feS5jYWxsKG51bGwsIGQpKSkgY29udGludWU7CiAgICAgICAgeHpbaV0gPSB4OwogICAgICAgIHl6W2ldID0geTsKICAgICAgICBpZiAoeCA8IHgwKSB4MCA9IHg7CiAgICAgICAgaWYgKHggPiB4MSkgeDEgPSB4OwogICAgICAgIGlmICh5IDwgeTApIHkwID0geTsKICAgICAgICBpZiAoeSA+IHkxKSB5MSA9IHk7CiAgICAgIH0KCiAgICAgIC8vIElmIHRoZXJlIHdlcmUgbm8gKHZhbGlkKSBwb2ludHMsIGFib3J0LgogICAgICBpZiAoeDAgPiB4MSB8fCB5MCA+IHkxKSByZXR1cm4gdGhpczsKCiAgICAgIC8vIEV4cGFuZCB0aGUgdHJlZSB0byBjb3ZlciB0aGUgbmV3IHBvaW50cy4KICAgICAgdGhpcy5jb3Zlcih4MCwgeTApLmNvdmVyKHgxLCB5MSk7CgogICAgICAvLyBBZGQgdGhlIG5ldyBwb2ludHMuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBhZGQodGhpcywgeHpbaV0sIHl6W2ldLCBkYXRhW2ldKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9jb3Zlcih4LCB5KSB7CiAgICAgIGlmIChpc05hTih4ID0gK3gpIHx8IGlzTmFOKHkgPSAreSkpIHJldHVybiB0aGlzOyAvLyBpZ25vcmUgaW52YWxpZCBwb2ludHMKCiAgICAgIHZhciB4MCA9IHRoaXMuX3gwLAogICAgICAgICAgeTAgPSB0aGlzLl95MCwKICAgICAgICAgIHgxID0gdGhpcy5feDEsCiAgICAgICAgICB5MSA9IHRoaXMuX3kxOwoKICAgICAgLy8gSWYgdGhlIHF1YWR0cmVlIGhhcyBubyBleHRlbnQsIGluaXRpYWxpemUgdGhlbS4KICAgICAgLy8gSW50ZWdlciBleHRlbnQgYXJlIG5lY2Vzc2FyeSBzbyB0aGF0IGlmIHdlIGxhdGVyIGRvdWJsZSB0aGUgZXh0ZW50LAogICAgICAvLyB0aGUgZXhpc3RpbmcgcXVhZHJhbnQgYm91bmRhcmllcyBkb27igJl0IGNoYW5nZSBkdWUgdG8gZmxvYXRpbmcgcG9pbnQgZXJyb3IhCiAgICAgIGlmIChpc05hTih4MCkpIHsKICAgICAgICB4MSA9ICh4MCA9IE1hdGguZmxvb3IoeCkpICsgMTsKICAgICAgICB5MSA9ICh5MCA9IE1hdGguZmxvb3IoeSkpICsgMTsKICAgICAgfQoKICAgICAgLy8gT3RoZXJ3aXNlLCBkb3VibGUgcmVwZWF0ZWRseSB0byBjb3Zlci4KICAgICAgZWxzZSB7CiAgICAgICAgdmFyIHogPSB4MSAtIHgwLAogICAgICAgICAgICBub2RlID0gdGhpcy5fcm9vdCwKICAgICAgICAgICAgcGFyZW50LAogICAgICAgICAgICBpOwoKICAgICAgICB3aGlsZSAoeDAgPiB4IHx8IHggPj0geDEgfHwgeTAgPiB5IHx8IHkgPj0geTEpIHsKICAgICAgICAgIGkgPSAoeSA8IHkwKSA8PCAxIHwgKHggPCB4MCk7CiAgICAgICAgICBwYXJlbnQgPSBuZXcgQXJyYXkoNCksIHBhcmVudFtpXSA9IG5vZGUsIG5vZGUgPSBwYXJlbnQsIHogKj0gMjsKICAgICAgICAgIHN3aXRjaCAoaSkgewogICAgICAgICAgICBjYXNlIDA6IHgxID0geDAgKyB6LCB5MSA9IHkwICsgejsgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgMTogeDAgPSB4MSAtIHosIHkxID0geTAgKyB6OyBicmVhazsKICAgICAgICAgICAgY2FzZSAyOiB4MSA9IHgwICsgeiwgeTAgPSB5MSAtIHo7IGJyZWFrOwogICAgICAgICAgICBjYXNlIDM6IHgwID0geDEgLSB6LCB5MCA9IHkxIC0gejsgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy5fcm9vdCAmJiB0aGlzLl9yb290Lmxlbmd0aCkgdGhpcy5fcm9vdCA9IG5vZGU7CiAgICAgIH0KCiAgICAgIHRoaXMuX3gwID0geDA7CiAgICAgIHRoaXMuX3kwID0geTA7CiAgICAgIHRoaXMuX3gxID0geDE7CiAgICAgIHRoaXMuX3kxID0geTE7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfZGF0YSgpIHsKICAgICAgdmFyIGRhdGEgPSBbXTsKICAgICAgdGhpcy52aXNpdChmdW5jdGlvbihub2RlKSB7CiAgICAgICAgaWYgKCFub2RlLmxlbmd0aCkgZG8gZGF0YS5wdXNoKG5vZGUuZGF0YSk7IHdoaWxlIChub2RlID0gbm9kZS5uZXh0KQogICAgICB9KTsKICAgICAgcmV0dXJuIGRhdGE7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9leHRlbnQoXykgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmNvdmVyKCtfWzBdWzBdLCArX1swXVsxXSkuY292ZXIoK19bMV1bMF0sICtfWzFdWzFdKQogICAgICAgICAgOiBpc05hTih0aGlzLl94MCkgPyB1bmRlZmluZWQgOiBbW3RoaXMuX3gwLCB0aGlzLl95MF0sIFt0aGlzLl94MSwgdGhpcy5feTFdXTsKICAgIH0KCiAgICBmdW5jdGlvbiBRdWFkKG5vZGUsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIHRoaXMubm9kZSA9IG5vZGU7CiAgICAgIHRoaXMueDAgPSB4MDsKICAgICAgdGhpcy55MCA9IHkwOwogICAgICB0aGlzLngxID0geDE7CiAgICAgIHRoaXMueTEgPSB5MTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX2ZpbmQoeCwgeSwgcmFkaXVzKSB7CiAgICAgIHZhciBkYXRhLAogICAgICAgICAgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSwKICAgICAgICAgIHkxLAogICAgICAgICAgeDIsCiAgICAgICAgICB5MiwKICAgICAgICAgIHgzID0gdGhpcy5feDEsCiAgICAgICAgICB5MyA9IHRoaXMuX3kxLAogICAgICAgICAgcXVhZHMgPSBbXSwKICAgICAgICAgIG5vZGUgPSB0aGlzLl9yb290LAogICAgICAgICAgcSwKICAgICAgICAgIGk7CgogICAgICBpZiAobm9kZSkgcXVhZHMucHVzaChuZXcgUXVhZChub2RlLCB4MCwgeTAsIHgzLCB5MykpOwogICAgICBpZiAocmFkaXVzID09IG51bGwpIHJhZGl1cyA9IEluZmluaXR5OwogICAgICBlbHNlIHsKICAgICAgICB4MCA9IHggLSByYWRpdXMsIHkwID0geSAtIHJhZGl1czsKICAgICAgICB4MyA9IHggKyByYWRpdXMsIHkzID0geSArIHJhZGl1czsKICAgICAgICByYWRpdXMgKj0gcmFkaXVzOwogICAgICB9CgogICAgICB3aGlsZSAocSA9IHF1YWRzLnBvcCgpKSB7CgogICAgICAgIC8vIFN0b3Agc2VhcmNoaW5nIGlmIHRoaXMgcXVhZHJhbnQgY2Fu4oCZdCBjb250YWluIGEgY2xvc2VyIG5vZGUuCiAgICAgICAgaWYgKCEobm9kZSA9IHEubm9kZSkKICAgICAgICAgICAgfHwgKHgxID0gcS54MCkgPiB4MwogICAgICAgICAgICB8fCAoeTEgPSBxLnkwKSA+IHkzCiAgICAgICAgICAgIHx8ICh4MiA9IHEueDEpIDwgeDAKICAgICAgICAgICAgfHwgKHkyID0gcS55MSkgPCB5MCkgY29udGludWU7CgogICAgICAgIC8vIEJpc2VjdCB0aGUgY3VycmVudCBxdWFkcmFudC4KICAgICAgICBpZiAobm9kZS5sZW5ndGgpIHsKICAgICAgICAgIHZhciB4bSA9ICh4MSArIHgyKSAvIDIsCiAgICAgICAgICAgICAgeW0gPSAoeTEgKyB5MikgLyAyOwoKICAgICAgICAgIHF1YWRzLnB1c2goCiAgICAgICAgICAgIG5ldyBRdWFkKG5vZGVbM10sIHhtLCB5bSwgeDIsIHkyKSwKICAgICAgICAgICAgbmV3IFF1YWQobm9kZVsyXSwgeDEsIHltLCB4bSwgeTIpLAogICAgICAgICAgICBuZXcgUXVhZChub2RlWzFdLCB4bSwgeTEsIHgyLCB5bSksCiAgICAgICAgICAgIG5ldyBRdWFkKG5vZGVbMF0sIHgxLCB5MSwgeG0sIHltKQogICAgICAgICAgKTsKCiAgICAgICAgICAvLyBWaXNpdCB0aGUgY2xvc2VzdCBxdWFkcmFudCBmaXJzdC4KICAgICAgICAgIGlmIChpID0gKHkgPj0geW0pIDw8IDEgfCAoeCA+PSB4bSkpIHsKICAgICAgICAgICAgcSA9IHF1YWRzW3F1YWRzLmxlbmd0aCAtIDFdOwogICAgICAgICAgICBxdWFkc1txdWFkcy5sZW5ndGggLSAxXSA9IHF1YWRzW3F1YWRzLmxlbmd0aCAtIDEgLSBpXTsKICAgICAgICAgICAgcXVhZHNbcXVhZHMubGVuZ3RoIC0gMSAtIGldID0gcTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIFZpc2l0IHRoaXMgcG9pbnQuIChWaXNpdGluZyBjb2luY2lkZW50IHBvaW50cyBpc27igJl0IG5lY2Vzc2FyeSEpCiAgICAgICAgZWxzZSB7CiAgICAgICAgICB2YXIgZHggPSB4IC0gK3RoaXMuX3guY2FsbChudWxsLCBub2RlLmRhdGEpLAogICAgICAgICAgICAgIGR5ID0geSAtICt0aGlzLl95LmNhbGwobnVsbCwgbm9kZS5kYXRhKSwKICAgICAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5OwogICAgICAgICAgaWYgKGQyIDwgcmFkaXVzKSB7CiAgICAgICAgICAgIHZhciBkID0gTWF0aC5zcXJ0KHJhZGl1cyA9IGQyKTsKICAgICAgICAgICAgeDAgPSB4IC0gZCwgeTAgPSB5IC0gZDsKICAgICAgICAgICAgeDMgPSB4ICsgZCwgeTMgPSB5ICsgZDsKICAgICAgICAgICAgZGF0YSA9IG5vZGUuZGF0YTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBkYXRhOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfcmVtb3ZlKGQpIHsKICAgICAgaWYgKGlzTmFOKHggPSArdGhpcy5feC5jYWxsKG51bGwsIGQpKSB8fCBpc05hTih5ID0gK3RoaXMuX3kuY2FsbChudWxsLCBkKSkpIHJldHVybiB0aGlzOyAvLyBpZ25vcmUgaW52YWxpZCBwb2ludHMKCiAgICAgIHZhciBwYXJlbnQsCiAgICAgICAgICBub2RlID0gdGhpcy5fcm9vdCwKICAgICAgICAgIHJldGFpbmVyLAogICAgICAgICAgcHJldmlvdXMsCiAgICAgICAgICBuZXh0LAogICAgICAgICAgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSA9IHRoaXMuX3gxLAogICAgICAgICAgeTEgPSB0aGlzLl95MSwKICAgICAgICAgIHgsCiAgICAgICAgICB5LAogICAgICAgICAgeG0sCiAgICAgICAgICB5bSwKICAgICAgICAgIHJpZ2h0LAogICAgICAgICAgYm90dG9tLAogICAgICAgICAgaSwKICAgICAgICAgIGo7CgogICAgICAvLyBJZiB0aGUgdHJlZSBpcyBlbXB0eSwgaW5pdGlhbGl6ZSB0aGUgcm9vdCBhcyBhIGxlYWYuCiAgICAgIGlmICghbm9kZSkgcmV0dXJuIHRoaXM7CgogICAgICAvLyBGaW5kIHRoZSBsZWFmIG5vZGUgZm9yIHRoZSBwb2ludC4KICAgICAgLy8gV2hpbGUgZGVzY2VuZGluZywgYWxzbyByZXRhaW4gdGhlIGRlZXBlc3QgcGFyZW50IHdpdGggYSBub24tcmVtb3ZlZCBzaWJsaW5nLgogICAgICBpZiAobm9kZS5sZW5ndGgpIHdoaWxlICh0cnVlKSB7CiAgICAgICAgaWYgKHJpZ2h0ID0geCA+PSAoeG0gPSAoeDAgKyB4MSkgLyAyKSkgeDAgPSB4bTsgZWxzZSB4MSA9IHhtOwogICAgICAgIGlmIChib3R0b20gPSB5ID49ICh5bSA9ICh5MCArIHkxKSAvIDIpKSB5MCA9IHltOyBlbHNlIHkxID0geW07CiAgICAgICAgaWYgKCEocGFyZW50ID0gbm9kZSwgbm9kZSA9IG5vZGVbaSA9IGJvdHRvbSA8PCAxIHwgcmlnaHRdKSkgcmV0dXJuIHRoaXM7CiAgICAgICAgaWYgKCFub2RlLmxlbmd0aCkgYnJlYWs7CiAgICAgICAgaWYgKHBhcmVudFsoaSArIDEpICYgM10gfHwgcGFyZW50WyhpICsgMikgJiAzXSB8fCBwYXJlbnRbKGkgKyAzKSAmIDNdKSByZXRhaW5lciA9IHBhcmVudCwgaiA9IGk7CiAgICAgIH0KCiAgICAgIC8vIEZpbmQgdGhlIHBvaW50IHRvIHJlbW92ZS4KICAgICAgd2hpbGUgKG5vZGUuZGF0YSAhPT0gZCkgaWYgKCEocHJldmlvdXMgPSBub2RlLCBub2RlID0gbm9kZS5uZXh0KSkgcmV0dXJuIHRoaXM7CiAgICAgIGlmIChuZXh0ID0gbm9kZS5uZXh0KSBkZWxldGUgbm9kZS5uZXh0OwoKICAgICAgLy8gSWYgdGhlcmUgYXJlIG11bHRpcGxlIGNvaW5jaWRlbnQgcG9pbnRzLCByZW1vdmUganVzdCB0aGUgcG9pbnQuCiAgICAgIGlmIChwcmV2aW91cykgcmV0dXJuIChuZXh0ID8gcHJldmlvdXMubmV4dCA9IG5leHQgOiBkZWxldGUgcHJldmlvdXMubmV4dCksIHRoaXM7CgogICAgICAvLyBJZiB0aGlzIGlzIHRoZSByb290IHBvaW50LCByZW1vdmUgaXQuCiAgICAgIGlmICghcGFyZW50KSByZXR1cm4gdGhpcy5fcm9vdCA9IG5leHQsIHRoaXM7CgogICAgICAvLyBSZW1vdmUgdGhpcyBsZWFmLgogICAgICBuZXh0ID8gcGFyZW50W2ldID0gbmV4dCA6IGRlbGV0ZSBwYXJlbnRbaV07CgogICAgICAvLyBJZiB0aGUgcGFyZW50IG5vdyBjb250YWlucyBleGFjdGx5IG9uZSBsZWFmLCBjb2xsYXBzZSBzdXBlcmZsdW91cyBwYXJlbnRzLgogICAgICBpZiAoKG5vZGUgPSBwYXJlbnRbMF0gfHwgcGFyZW50WzFdIHx8IHBhcmVudFsyXSB8fCBwYXJlbnRbM10pCiAgICAgICAgICAmJiBub2RlID09PSAocGFyZW50WzNdIHx8IHBhcmVudFsyXSB8fCBwYXJlbnRbMV0gfHwgcGFyZW50WzBdKQogICAgICAgICAgJiYgIW5vZGUubGVuZ3RoKSB7CiAgICAgICAgaWYgKHJldGFpbmVyKSByZXRhaW5lcltqXSA9IG5vZGU7CiAgICAgICAgZWxzZSB0aGlzLl9yb290ID0gbm9kZTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlQWxsKGRhdGEpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBkYXRhLmxlbmd0aDsgaSA8IG47ICsraSkgdGhpcy5yZW1vdmUoZGF0YVtpXSk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfcm9vdCgpIHsKICAgICAgcmV0dXJuIHRoaXMuX3Jvb3Q7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9zaXplKCkgewogICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgIHRoaXMudmlzaXQoZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmICghbm9kZS5sZW5ndGgpIGRvICsrc2l6ZTsgd2hpbGUgKG5vZGUgPSBub2RlLm5leHQpCiAgICAgIH0pOwogICAgICByZXR1cm4gc2l6ZTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3Zpc2l0KGNhbGxiYWNrKSB7CiAgICAgIHZhciBxdWFkcyA9IFtdLCBxLCBub2RlID0gdGhpcy5fcm9vdCwgY2hpbGQsIHgwLCB5MCwgeDEsIHkxOwogICAgICBpZiAobm9kZSkgcXVhZHMucHVzaChuZXcgUXVhZChub2RlLCB0aGlzLl94MCwgdGhpcy5feTAsIHRoaXMuX3gxLCB0aGlzLl95MSkpOwogICAgICB3aGlsZSAocSA9IHF1YWRzLnBvcCgpKSB7CiAgICAgICAgaWYgKCFjYWxsYmFjayhub2RlID0gcS5ub2RlLCB4MCA9IHEueDAsIHkwID0gcS55MCwgeDEgPSBxLngxLCB5MSA9IHEueTEpICYmIG5vZGUubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgeG0gPSAoeDAgKyB4MSkgLyAyLCB5bSA9ICh5MCArIHkxKSAvIDI7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzNdKSBxdWFkcy5wdXNoKG5ldyBRdWFkKGNoaWxkLCB4bSwgeW0sIHgxLCB5MSkpOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVsyXSkgcXVhZHMucHVzaChuZXcgUXVhZChjaGlsZCwgeDAsIHltLCB4bSwgeTEpKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMV0pIHF1YWRzLnB1c2gobmV3IFF1YWQoY2hpbGQsIHhtLCB5MCwgeDEsIHltKSk7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzBdKSBxdWFkcy5wdXNoKG5ldyBRdWFkKGNoaWxkLCB4MCwgeTAsIHhtLCB5bSkpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3Zpc2l0QWZ0ZXIoY2FsbGJhY2spIHsKICAgICAgdmFyIHF1YWRzID0gW10sIG5leHQgPSBbXSwgcTsKICAgICAgaWYgKHRoaXMuX3Jvb3QpIHF1YWRzLnB1c2gobmV3IFF1YWQodGhpcy5fcm9vdCwgdGhpcy5feDAsIHRoaXMuX3kwLCB0aGlzLl94MSwgdGhpcy5feTEpKTsKICAgICAgd2hpbGUgKHEgPSBxdWFkcy5wb3AoKSkgewogICAgICAgIHZhciBub2RlID0gcS5ub2RlOwogICAgICAgIGlmIChub2RlLmxlbmd0aCkgewogICAgICAgICAgdmFyIGNoaWxkLCB4MCA9IHEueDAsIHkwID0gcS55MCwgeDEgPSBxLngxLCB5MSA9IHEueTEsIHhtID0gKHgwICsgeDEpIC8gMiwgeW0gPSAoeTAgKyB5MSkgLyAyOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVswXSkgcXVhZHMucHVzaChuZXcgUXVhZChjaGlsZCwgeDAsIHkwLCB4bSwgeW0pKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMV0pIHF1YWRzLnB1c2gobmV3IFF1YWQoY2hpbGQsIHhtLCB5MCwgeDEsIHltKSk7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzJdKSBxdWFkcy5wdXNoKG5ldyBRdWFkKGNoaWxkLCB4MCwgeW0sIHhtLCB5MSkpOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVszXSkgcXVhZHMucHVzaChuZXcgUXVhZChjaGlsZCwgeG0sIHltLCB4MSwgeTEpKTsKICAgICAgICB9CiAgICAgICAgbmV4dC5wdXNoKHEpOwogICAgICB9CiAgICAgIHdoaWxlIChxID0gbmV4dC5wb3AoKSkgewogICAgICAgIGNhbGxiYWNrKHEubm9kZSwgcS54MCwgcS55MCwgcS54MSwgcS55MSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFgkMShkKSB7CiAgICAgIHJldHVybiBkWzBdOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfeChfKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRoaXMuX3ggPSBfLCB0aGlzKSA6IHRoaXMuX3g7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFkkMShkKSB7CiAgICAgIHJldHVybiBkWzFdOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfeShfKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRoaXMuX3kgPSBfLCB0aGlzKSA6IHRoaXMuX3k7CiAgICB9CgogICAgZnVuY3Rpb24gcXVhZHRyZWUobm9kZXMsIHgsIHkpIHsKICAgICAgdmFyIHRyZWUgPSBuZXcgUXVhZHRyZWUoeCA9PSBudWxsID8gZGVmYXVsdFgkMSA6IHgsIHkgPT0gbnVsbCA/IGRlZmF1bHRZJDEgOiB5LCBOYU4sIE5hTiwgTmFOLCBOYU4pOwogICAgICByZXR1cm4gbm9kZXMgPT0gbnVsbCA/IHRyZWUgOiB0cmVlLmFkZEFsbChub2Rlcyk7CiAgICB9CgogICAgZnVuY3Rpb24gUXVhZHRyZWUoeCwgeSwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdGhpcy5feCA9IHg7CiAgICAgIHRoaXMuX3kgPSB5OwogICAgICB0aGlzLl94MCA9IHgwOwogICAgICB0aGlzLl95MCA9IHkwOwogICAgICB0aGlzLl94MSA9IHgxOwogICAgICB0aGlzLl95MSA9IHkxOwogICAgICB0aGlzLl9yb290ID0gdW5kZWZpbmVkOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlYWZfY29weShsZWFmKSB7CiAgICAgIHZhciBjb3B5ID0ge2RhdGE6IGxlYWYuZGF0YX0sIG5leHQgPSBjb3B5OwogICAgICB3aGlsZSAobGVhZiA9IGxlYWYubmV4dCkgbmV4dCA9IG5leHQubmV4dCA9IHtkYXRhOiBsZWFmLmRhdGF9OwogICAgICByZXR1cm4gY29weTsKICAgIH0KCiAgICB2YXIgdHJlZVByb3RvID0gcXVhZHRyZWUucHJvdG90eXBlID0gUXVhZHRyZWUucHJvdG90eXBlOwoKICAgIHRyZWVQcm90by5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBjb3B5ID0gbmV3IFF1YWR0cmVlKHRoaXMuX3gsIHRoaXMuX3ksIHRoaXMuX3gwLCB0aGlzLl95MCwgdGhpcy5feDEsIHRoaXMuX3kxKSwKICAgICAgICAgIG5vZGUgPSB0aGlzLl9yb290LAogICAgICAgICAgbm9kZXMsCiAgICAgICAgICBjaGlsZDsKCiAgICAgIGlmICghbm9kZSkgcmV0dXJuIGNvcHk7CgogICAgICBpZiAoIW5vZGUubGVuZ3RoKSByZXR1cm4gY29weS5fcm9vdCA9IGxlYWZfY29weShub2RlKSwgY29weTsKCiAgICAgIG5vZGVzID0gW3tzb3VyY2U6IG5vZGUsIHRhcmdldDogY29weS5fcm9vdCA9IG5ldyBBcnJheSg0KX1dOwogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCA0OyArK2kpIHsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGUuc291cmNlW2ldKSB7CiAgICAgICAgICAgIGlmIChjaGlsZC5sZW5ndGgpIG5vZGVzLnB1c2goe3NvdXJjZTogY2hpbGQsIHRhcmdldDogbm9kZS50YXJnZXRbaV0gPSBuZXcgQXJyYXkoNCl9KTsKICAgICAgICAgICAgZWxzZSBub2RlLnRhcmdldFtpXSA9IGxlYWZfY29weShjaGlsZCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gY29weTsKICAgIH07CgogICAgdHJlZVByb3RvLmFkZCA9IHRyZWVfYWRkOwogICAgdHJlZVByb3RvLmFkZEFsbCA9IGFkZEFsbDsKICAgIHRyZWVQcm90by5jb3ZlciA9IHRyZWVfY292ZXI7CiAgICB0cmVlUHJvdG8uZGF0YSA9IHRyZWVfZGF0YTsKICAgIHRyZWVQcm90by5leHRlbnQgPSB0cmVlX2V4dGVudDsKICAgIHRyZWVQcm90by5maW5kID0gdHJlZV9maW5kOwogICAgdHJlZVByb3RvLnJlbW92ZSA9IHRyZWVfcmVtb3ZlOwogICAgdHJlZVByb3RvLnJlbW92ZUFsbCA9IHJlbW92ZUFsbDsKICAgIHRyZWVQcm90by5yb290ID0gdHJlZV9yb290OwogICAgdHJlZVByb3RvLnNpemUgPSB0cmVlX3NpemU7CiAgICB0cmVlUHJvdG8udmlzaXQgPSB0cmVlX3Zpc2l0OwogICAgdHJlZVByb3RvLnZpc2l0QWZ0ZXIgPSB0cmVlX3Zpc2l0QWZ0ZXI7CiAgICB0cmVlUHJvdG8ueCA9IHRyZWVfeDsKICAgIHRyZWVQcm90by55ID0gdHJlZV95OwoKICAgIGZ1bmN0aW9uIHgoZCkgewogICAgICByZXR1cm4gZC54ICsgZC52eDsKICAgIH0KCiAgICBmdW5jdGlvbiB5KGQpIHsKICAgICAgcmV0dXJuIGQueSArIGQudnk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sbGlkZShyYWRpdXMpIHsKICAgICAgdmFyIG5vZGVzLAogICAgICAgICAgcmFkaWksCiAgICAgICAgICBzdHJlbmd0aCA9IDEsCiAgICAgICAgICBpdGVyYXRpb25zID0gMTsKCiAgICAgIGlmICh0eXBlb2YgcmFkaXVzICE9PSAiZnVuY3Rpb24iKSByYWRpdXMgPSBjb25zdGFudCQ3KHJhZGl1cyA9PSBudWxsID8gMSA6ICtyYWRpdXMpOwoKICAgICAgZnVuY3Rpb24gZm9yY2UoKSB7CiAgICAgICAgdmFyIGksIG4gPSBub2Rlcy5sZW5ndGgsCiAgICAgICAgICAgIHRyZWUsCiAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgIHhpLAogICAgICAgICAgICB5aSwKICAgICAgICAgICAgcmksCiAgICAgICAgICAgIHJpMjsKCiAgICAgICAgZm9yICh2YXIgayA9IDA7IGsgPCBpdGVyYXRpb25zOyArK2spIHsKICAgICAgICAgIHRyZWUgPSBxdWFkdHJlZShub2RlcywgeCwgeSkudmlzaXRBZnRlcihwcmVwYXJlKTsKICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgbm9kZSA9IG5vZGVzW2ldOwogICAgICAgICAgICByaSA9IHJhZGlpW25vZGUuaW5kZXhdLCByaTIgPSByaSAqIHJpOwogICAgICAgICAgICB4aSA9IG5vZGUueCArIG5vZGUudng7CiAgICAgICAgICAgIHlpID0gbm9kZS55ICsgbm9kZS52eTsKICAgICAgICAgICAgdHJlZS52aXNpdChhcHBseSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBhcHBseShxdWFkLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICAgICAgdmFyIGRhdGEgPSBxdWFkLmRhdGEsIHJqID0gcXVhZC5yLCByID0gcmkgKyByajsKICAgICAgICAgIGlmIChkYXRhKSB7CiAgICAgICAgICAgIGlmIChkYXRhLmluZGV4ID4gbm9kZS5pbmRleCkgewogICAgICAgICAgICAgIHZhciB4ID0geGkgLSBkYXRhLnggLSBkYXRhLnZ4LAogICAgICAgICAgICAgICAgICB5ID0geWkgLSBkYXRhLnkgLSBkYXRhLnZ5LAogICAgICAgICAgICAgICAgICBsID0geCAqIHggKyB5ICogeTsKICAgICAgICAgICAgICBpZiAobCA8IHIgKiByKSB7CiAgICAgICAgICAgICAgICBpZiAoeCA9PT0gMCkgeCA9IGppZ2dsZSgpLCBsICs9IHggKiB4OwogICAgICAgICAgICAgICAgaWYgKHkgPT09IDApIHkgPSBqaWdnbGUoKSwgbCArPSB5ICogeTsKICAgICAgICAgICAgICAgIGwgPSAociAtIChsID0gTWF0aC5zcXJ0KGwpKSkgLyBsICogc3RyZW5ndGg7CiAgICAgICAgICAgICAgICBub2RlLnZ4ICs9ICh4ICo9IGwpICogKHIgPSAocmogKj0gcmopIC8gKHJpMiArIHJqKSk7CiAgICAgICAgICAgICAgICBub2RlLnZ5ICs9ICh5ICo9IGwpICogcjsKICAgICAgICAgICAgICAgIGRhdGEudnggLT0geCAqIChyID0gMSAtIHIpOwogICAgICAgICAgICAgICAgZGF0YS52eSAtPSB5ICogcjsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHgwID4geGkgKyByIHx8IHgxIDwgeGkgLSByIHx8IHkwID4geWkgKyByIHx8IHkxIDwgeWkgLSByOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gcHJlcGFyZShxdWFkKSB7CiAgICAgICAgaWYgKHF1YWQuZGF0YSkgcmV0dXJuIHF1YWQuciA9IHJhZGlpW3F1YWQuZGF0YS5pbmRleF07CiAgICAgICAgZm9yICh2YXIgaSA9IHF1YWQuciA9IDA7IGkgPCA0OyArK2kpIHsKICAgICAgICAgIGlmIChxdWFkW2ldICYmIHF1YWRbaV0uciA+IHF1YWQucikgewogICAgICAgICAgICBxdWFkLnIgPSBxdWFkW2ldLnI7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBpbml0aWFsaXplKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aCwgbm9kZTsKICAgICAgICByYWRpaSA9IG5ldyBBcnJheShuKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBub2RlID0gbm9kZXNbaV0sIHJhZGlpW25vZGUuaW5kZXhdID0gK3JhZGl1cyhub2RlLCBpLCBub2Rlcyk7CiAgICAgIH0KCiAgICAgIGZvcmNlLmluaXRpYWxpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgbm9kZXMgPSBfOwogICAgICAgIGluaXRpYWxpemUoKTsKICAgICAgfTsKCiAgICAgIGZvcmNlLml0ZXJhdGlvbnMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaXRlcmF0aW9ucyA9ICtfLCBmb3JjZSkgOiBpdGVyYXRpb25zOwogICAgICB9OwoKICAgICAgZm9yY2Uuc3RyZW5ndGggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RyZW5ndGggPSArXywgZm9yY2UpIDogc3RyZW5ndGg7CiAgICAgIH07CgogICAgICBmb3JjZS5yYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocmFkaXVzID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkNygrXyksIGluaXRpYWxpemUoKSwgZm9yY2UpIDogcmFkaXVzOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIGluZGV4KGQpIHsKICAgICAgcmV0dXJuIGQuaW5kZXg7CiAgICB9CgogICAgZnVuY3Rpb24gZmluZChub2RlQnlJZCwgbm9kZUlkKSB7CiAgICAgIHZhciBub2RlID0gbm9kZUJ5SWQuZ2V0KG5vZGVJZCk7CiAgICAgIGlmICghbm9kZSkgdGhyb3cgbmV3IEVycm9yKCJtaXNzaW5nOiAiICsgbm9kZUlkKTsKICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgZnVuY3Rpb24gbGluayhsaW5rcykgewogICAgICB2YXIgaWQgPSBpbmRleCwKICAgICAgICAgIHN0cmVuZ3RoID0gZGVmYXVsdFN0cmVuZ3RoLAogICAgICAgICAgc3RyZW5ndGhzLAogICAgICAgICAgZGlzdGFuY2UgPSBjb25zdGFudCQ3KDMwKSwKICAgICAgICAgIGRpc3RhbmNlcywKICAgICAgICAgIG5vZGVzLAogICAgICAgICAgY291bnQsCiAgICAgICAgICBiaWFzLAogICAgICAgICAgaXRlcmF0aW9ucyA9IDE7CgogICAgICBpZiAobGlua3MgPT0gbnVsbCkgbGlua3MgPSBbXTsKCiAgICAgIGZ1bmN0aW9uIGRlZmF1bHRTdHJlbmd0aChsaW5rKSB7CiAgICAgICAgcmV0dXJuIDEgLyBNYXRoLm1pbihjb3VudFtsaW5rLnNvdXJjZS5pbmRleF0sIGNvdW50W2xpbmsudGFyZ2V0LmluZGV4XSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcmNlKGFscGhhKSB7CiAgICAgICAgZm9yICh2YXIgayA9IDAsIG4gPSBsaW5rcy5sZW5ndGg7IGsgPCBpdGVyYXRpb25zOyArK2spIHsKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBsaW5rLCBzb3VyY2UsIHRhcmdldCwgeCwgeSwgbCwgYjsgaSA8IG47ICsraSkgewogICAgICAgICAgICBsaW5rID0gbGlua3NbaV0sIHNvdXJjZSA9IGxpbmsuc291cmNlLCB0YXJnZXQgPSBsaW5rLnRhcmdldDsKICAgICAgICAgICAgeCA9IHRhcmdldC54ICsgdGFyZ2V0LnZ4IC0gc291cmNlLnggLSBzb3VyY2UudnggfHwgamlnZ2xlKCk7CiAgICAgICAgICAgIHkgPSB0YXJnZXQueSArIHRhcmdldC52eSAtIHNvdXJjZS55IC0gc291cmNlLnZ5IHx8IGppZ2dsZSgpOwogICAgICAgICAgICBsID0gTWF0aC5zcXJ0KHggKiB4ICsgeSAqIHkpOwogICAgICAgICAgICBsID0gKGwgLSBkaXN0YW5jZXNbaV0pIC8gbCAqIGFscGhhICogc3RyZW5ndGhzW2ldOwogICAgICAgICAgICB4ICo9IGwsIHkgKj0gbDsKICAgICAgICAgICAgdGFyZ2V0LnZ4IC09IHggKiAoYiA9IGJpYXNbaV0pOwogICAgICAgICAgICB0YXJnZXQudnkgLT0geSAqIGI7CiAgICAgICAgICAgIHNvdXJjZS52eCArPSB4ICogKGIgPSAxIC0gYik7CiAgICAgICAgICAgIHNvdXJjZS52eSArPSB5ICogYjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwoKICAgICAgICB2YXIgaSwKICAgICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgICAgbSA9IGxpbmtzLmxlbmd0aCwKICAgICAgICAgICAgbm9kZUJ5SWQgPSBtYXAkMShub2RlcywgaWQpLAogICAgICAgICAgICBsaW5rOwoKICAgICAgICBmb3IgKGkgPSAwLCBjb3VudCA9IG5ldyBBcnJheShuKTsgaSA8IG07ICsraSkgewogICAgICAgICAgbGluayA9IGxpbmtzW2ldLCBsaW5rLmluZGV4ID0gaTsKICAgICAgICAgIGlmICh0eXBlb2YgbGluay5zb3VyY2UgIT09ICJvYmplY3QiKSBsaW5rLnNvdXJjZSA9IGZpbmQobm9kZUJ5SWQsIGxpbmsuc291cmNlKTsKICAgICAgICAgIGlmICh0eXBlb2YgbGluay50YXJnZXQgIT09ICJvYmplY3QiKSBsaW5rLnRhcmdldCA9IGZpbmQobm9kZUJ5SWQsIGxpbmsudGFyZ2V0KTsKICAgICAgICAgIGNvdW50W2xpbmsuc291cmNlLmluZGV4XSA9IChjb3VudFtsaW5rLnNvdXJjZS5pbmRleF0gfHwgMCkgKyAxOwogICAgICAgICAgY291bnRbbGluay50YXJnZXQuaW5kZXhdID0gKGNvdW50W2xpbmsudGFyZ2V0LmluZGV4XSB8fCAwKSArIDE7CiAgICAgICAgfQoKICAgICAgICBmb3IgKGkgPSAwLCBiaWFzID0gbmV3IEFycmF5KG0pOyBpIDwgbTsgKytpKSB7CiAgICAgICAgICBsaW5rID0gbGlua3NbaV0sIGJpYXNbaV0gPSBjb3VudFtsaW5rLnNvdXJjZS5pbmRleF0gLyAoY291bnRbbGluay5zb3VyY2UuaW5kZXhdICsgY291bnRbbGluay50YXJnZXQuaW5kZXhdKTsKICAgICAgICB9CgogICAgICAgIHN0cmVuZ3RocyA9IG5ldyBBcnJheShtKSwgaW5pdGlhbGl6ZVN0cmVuZ3RoKCk7CiAgICAgICAgZGlzdGFuY2VzID0gbmV3IEFycmF5KG0pLCBpbml0aWFsaXplRGlzdGFuY2UoKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5pdGlhbGl6ZVN0cmVuZ3RoKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKCiAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBsaW5rcy5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHN0cmVuZ3Roc1tpXSA9ICtzdHJlbmd0aChsaW5rc1tpXSwgaSwgbGlua3MpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5pdGlhbGl6ZURpc3RhbmNlKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKCiAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBsaW5rcy5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGRpc3RhbmNlc1tpXSA9ICtkaXN0YW5jZShsaW5rc1tpXSwgaSwgbGlua3MpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yY2UuaW5pdGlhbGl6ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBub2RlcyA9IF87CiAgICAgICAgaW5pdGlhbGl6ZSgpOwogICAgICB9OwoKICAgICAgZm9yY2UubGlua3MgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAobGlua3MgPSBfLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IGxpbmtzOwogICAgICB9OwoKICAgICAgZm9yY2UuaWQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaWQgPSBfLCBmb3JjZSkgOiBpZDsKICAgICAgfTsKCiAgICAgIGZvcmNlLml0ZXJhdGlvbnMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaXRlcmF0aW9ucyA9ICtfLCBmb3JjZSkgOiBpdGVyYXRpb25zOwogICAgICB9OwoKICAgICAgZm9yY2Uuc3RyZW5ndGggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RyZW5ndGggPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ3KCtfKSwgaW5pdGlhbGl6ZVN0cmVuZ3RoKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UuZGlzdGFuY2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGlzdGFuY2UgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ3KCtfKSwgaW5pdGlhbGl6ZURpc3RhbmNlKCksIGZvcmNlKSA6IGRpc3RhbmNlOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHgkMShkKSB7CiAgICAgIHJldHVybiBkLng7CiAgICB9CgogICAgZnVuY3Rpb24geSQxKGQpIHsKICAgICAgcmV0dXJuIGQueTsKICAgIH0KCiAgICB2YXIgaW5pdGlhbFJhZGl1cyA9IDEwLAogICAgICAgIGluaXRpYWxBbmdsZSA9IE1hdGguUEkgKiAoMyAtIE1hdGguc3FydCg1KSk7CgogICAgZnVuY3Rpb24gc2ltdWxhdGlvbihub2RlcykgewogICAgICB2YXIgc2ltdWxhdGlvbiwKICAgICAgICAgIGFscGhhID0gMSwKICAgICAgICAgIGFscGhhTWluID0gMC4wMDEsCiAgICAgICAgICBhbHBoYURlY2F5ID0gMSAtIE1hdGgucG93KGFscGhhTWluLCAxIC8gMzAwKSwKICAgICAgICAgIGFscGhhVGFyZ2V0ID0gMCwKICAgICAgICAgIHZlbG9jaXR5RGVjYXkgPSAwLjYsCiAgICAgICAgICBmb3JjZXMgPSBtYXAkMSgpLAogICAgICAgICAgc3RlcHBlciA9IHRpbWVyKHN0ZXApLAogICAgICAgICAgZXZlbnQgPSBkaXNwYXRjaCgidGljayIsICJlbmQiKTsKCiAgICAgIGlmIChub2RlcyA9PSBudWxsKSBub2RlcyA9IFtdOwoKICAgICAgZnVuY3Rpb24gc3RlcCgpIHsKICAgICAgICB0aWNrKCk7CiAgICAgICAgZXZlbnQuY2FsbCgidGljayIsIHNpbXVsYXRpb24pOwogICAgICAgIGlmIChhbHBoYSA8IGFscGhhTWluKSB7CiAgICAgICAgICBzdGVwcGVyLnN0b3AoKTsKICAgICAgICAgIGV2ZW50LmNhbGwoImVuZCIsIHNpbXVsYXRpb24pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gdGljayhpdGVyYXRpb25zKSB7CiAgICAgICAgdmFyIGksIG4gPSBub2Rlcy5sZW5ndGgsIG5vZGU7CgogICAgICAgIGlmIChpdGVyYXRpb25zID09PSB1bmRlZmluZWQpIGl0ZXJhdGlvbnMgPSAxOwoKICAgICAgICBmb3IgKHZhciBrID0gMDsgayA8IGl0ZXJhdGlvbnM7ICsraykgewogICAgICAgICAgYWxwaGEgKz0gKGFscGhhVGFyZ2V0IC0gYWxwaGEpICogYWxwaGFEZWNheTsKCiAgICAgICAgICBmb3JjZXMuZWFjaChmdW5jdGlvbiAoZm9yY2UpIHsKICAgICAgICAgICAgZm9yY2UoYWxwaGEpOwogICAgICAgICAgfSk7CgogICAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBub2RlID0gbm9kZXNbaV07CiAgICAgICAgICAgIGlmIChub2RlLmZ4ID09IG51bGwpIG5vZGUueCArPSBub2RlLnZ4ICo9IHZlbG9jaXR5RGVjYXk7CiAgICAgICAgICAgIGVsc2Ugbm9kZS54ID0gbm9kZS5meCwgbm9kZS52eCA9IDA7CiAgICAgICAgICAgIGlmIChub2RlLmZ5ID09IG51bGwpIG5vZGUueSArPSBub2RlLnZ5ICo9IHZlbG9jaXR5RGVjYXk7CiAgICAgICAgICAgIGVsc2Ugbm9kZS55ID0gbm9kZS5meSwgbm9kZS52eSA9IDA7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gc2ltdWxhdGlvbjsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5pdGlhbGl6ZU5vZGVzKCkgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbm9kZXMubGVuZ3RoLCBub2RlOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUuaW5kZXggPSBpOwogICAgICAgICAgaWYgKG5vZGUuZnggIT0gbnVsbCkgbm9kZS54ID0gbm9kZS5meDsKICAgICAgICAgIGlmIChub2RlLmZ5ICE9IG51bGwpIG5vZGUueSA9IG5vZGUuZnk7CiAgICAgICAgICBpZiAoaXNOYU4obm9kZS54KSB8fCBpc05hTihub2RlLnkpKSB7CiAgICAgICAgICAgIHZhciByYWRpdXMgPSBpbml0aWFsUmFkaXVzICogTWF0aC5zcXJ0KGkpLCBhbmdsZSA9IGkgKiBpbml0aWFsQW5nbGU7CiAgICAgICAgICAgIG5vZGUueCA9IHJhZGl1cyAqIE1hdGguY29zKGFuZ2xlKTsKICAgICAgICAgICAgbm9kZS55ID0gcmFkaXVzICogTWF0aC5zaW4oYW5nbGUpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzTmFOKG5vZGUudngpIHx8IGlzTmFOKG5vZGUudnkpKSB7CiAgICAgICAgICAgIG5vZGUudnggPSBub2RlLnZ5ID0gMDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemVGb3JjZShmb3JjZSkgewogICAgICAgIGlmIChmb3JjZS5pbml0aWFsaXplKSBmb3JjZS5pbml0aWFsaXplKG5vZGVzKTsKICAgICAgICByZXR1cm4gZm9yY2U7CiAgICAgIH0KCiAgICAgIGluaXRpYWxpemVOb2RlcygpOwoKICAgICAgcmV0dXJuIHNpbXVsYXRpb24gPSB7CiAgICAgICAgdGljazogdGljaywKCiAgICAgICAgcmVzdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gc3RlcHBlci5yZXN0YXJ0KHN0ZXApLCBzaW11bGF0aW9uOwogICAgICAgIH0sCgogICAgICAgIHN0b3A6IGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHN0ZXBwZXIuc3RvcCgpLCBzaW11bGF0aW9uOwogICAgICAgIH0sCgogICAgICAgIG5vZGVzOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChub2RlcyA9IF8sIGluaXRpYWxpemVOb2RlcygpLCBmb3JjZXMuZWFjaChpbml0aWFsaXplRm9yY2UpLCBzaW11bGF0aW9uKSA6IG5vZGVzOwogICAgICAgIH0sCgogICAgICAgIGFscGhhOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChhbHBoYSA9ICtfLCBzaW11bGF0aW9uKSA6IGFscGhhOwogICAgICAgIH0sCgogICAgICAgIGFscGhhTWluOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChhbHBoYU1pbiA9ICtfLCBzaW11bGF0aW9uKSA6IGFscGhhTWluOwogICAgICAgIH0sCgogICAgICAgIGFscGhhRGVjYXk6IGZ1bmN0aW9uKF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGFscGhhRGVjYXkgPSArXywgc2ltdWxhdGlvbikgOiArYWxwaGFEZWNheTsKICAgICAgICB9LAoKICAgICAgICBhbHBoYVRhcmdldDogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoYWxwaGFUYXJnZXQgPSArXywgc2ltdWxhdGlvbikgOiBhbHBoYVRhcmdldDsKICAgICAgICB9LAoKICAgICAgICB2ZWxvY2l0eURlY2F5OiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh2ZWxvY2l0eURlY2F5ID0gMSAtIF8sIHNpbXVsYXRpb24pIDogMSAtIHZlbG9jaXR5RGVjYXk7CiAgICAgICAgfSwKCiAgICAgICAgZm9yY2U6IGZ1bmN0aW9uKG5hbWUsIF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMSA/ICgoXyA9PSBudWxsID8gZm9yY2VzLnJlbW92ZShuYW1lKSA6IGZvcmNlcy5zZXQobmFtZSwgaW5pdGlhbGl6ZUZvcmNlKF8pKSksIHNpbXVsYXRpb24pIDogZm9yY2VzLmdldChuYW1lKTsKICAgICAgICB9LAoKICAgICAgICBmaW5kOiBmdW5jdGlvbih4LCB5LCByYWRpdXMpIHsKICAgICAgICAgIHZhciBpID0gMCwKICAgICAgICAgICAgICBuID0gbm9kZXMubGVuZ3RoLAogICAgICAgICAgICAgIGR4LAogICAgICAgICAgICAgIGR5LAogICAgICAgICAgICAgIGQyLAogICAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgICAgY2xvc2VzdDsKCiAgICAgICAgICBpZiAocmFkaXVzID09IG51bGwpIHJhZGl1cyA9IEluZmluaXR5OwogICAgICAgICAgZWxzZSByYWRpdXMgKj0gcmFkaXVzOwoKICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgbm9kZSA9IG5vZGVzW2ldOwogICAgICAgICAgICBkeCA9IHggLSBub2RlLng7CiAgICAgICAgICAgIGR5ID0geSAtIG5vZGUueTsKICAgICAgICAgICAgZDIgPSBkeCAqIGR4ICsgZHkgKiBkeTsKICAgICAgICAgICAgaWYgKGQyIDwgcmFkaXVzKSBjbG9zZXN0ID0gbm9kZSwgcmFkaXVzID0gZDI7CiAgICAgICAgICB9CgogICAgICAgICAgcmV0dXJuIGNsb3Nlc3Q7CiAgICAgICAgfSwKCiAgICAgICAgb246IGZ1bmN0aW9uKG5hbWUsIF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMSA/IChldmVudC5vbihuYW1lLCBfKSwgc2ltdWxhdGlvbikgOiBldmVudC5vbihuYW1lKTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbWFueUJvZHkoKSB7CiAgICAgIHZhciBub2RlcywKICAgICAgICAgIG5vZGUsCiAgICAgICAgICBhbHBoYSwKICAgICAgICAgIHN0cmVuZ3RoID0gY29uc3RhbnQkNygtMzApLAogICAgICAgICAgc3RyZW5ndGhzLAogICAgICAgICAgZGlzdGFuY2VNaW4yID0gMSwKICAgICAgICAgIGRpc3RhbmNlTWF4MiA9IEluZmluaXR5LAogICAgICAgICAgdGhldGEyID0gMC44MTsKCiAgICAgIGZ1bmN0aW9uIGZvcmNlKF8pIHsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aCwgdHJlZSA9IHF1YWR0cmVlKG5vZGVzLCB4JDEsIHkkMSkudmlzaXRBZnRlcihhY2N1bXVsYXRlKTsKICAgICAgICBmb3IgKGFscGhhID0gXywgaSA9IDA7IGkgPCBuOyArK2kpIG5vZGUgPSBub2Rlc1tpXSwgdHJlZS52aXNpdChhcHBseSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoLCBub2RlOwogICAgICAgIHN0cmVuZ3RocyA9IG5ldyBBcnJheShuKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBub2RlID0gbm9kZXNbaV0sIHN0cmVuZ3Roc1tub2RlLmluZGV4XSA9ICtzdHJlbmd0aChub2RlLCBpLCBub2Rlcyk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGFjY3VtdWxhdGUocXVhZCkgewogICAgICAgIHZhciBzdHJlbmd0aCA9IDAsIHEsIGMsIHdlaWdodCA9IDAsIHgsIHksIGk7CgogICAgICAgIC8vIEZvciBpbnRlcm5hbCBub2RlcywgYWNjdW11bGF0ZSBmb3JjZXMgZnJvbSBjaGlsZCBxdWFkcmFudHMuCiAgICAgICAgaWYgKHF1YWQubGVuZ3RoKSB7CiAgICAgICAgICBmb3IgKHggPSB5ID0gaSA9IDA7IGkgPCA0OyArK2kpIHsKICAgICAgICAgICAgaWYgKChxID0gcXVhZFtpXSkgJiYgKGMgPSBNYXRoLmFicyhxLnZhbHVlKSkpIHsKICAgICAgICAgICAgICBzdHJlbmd0aCArPSBxLnZhbHVlLCB3ZWlnaHQgKz0gYywgeCArPSBjICogcS54LCB5ICs9IGMgKiBxLnk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHF1YWQueCA9IHggLyB3ZWlnaHQ7CiAgICAgICAgICBxdWFkLnkgPSB5IC8gd2VpZ2h0OwogICAgICAgIH0KCiAgICAgICAgLy8gRm9yIGxlYWYgbm9kZXMsIGFjY3VtdWxhdGUgZm9yY2VzIGZyb20gY29pbmNpZGVudCBxdWFkcmFudHMuCiAgICAgICAgZWxzZSB7CiAgICAgICAgICBxID0gcXVhZDsKICAgICAgICAgIHEueCA9IHEuZGF0YS54OwogICAgICAgICAgcS55ID0gcS5kYXRhLnk7CiAgICAgICAgICBkbyBzdHJlbmd0aCArPSBzdHJlbmd0aHNbcS5kYXRhLmluZGV4XTsKICAgICAgICAgIHdoaWxlIChxID0gcS5uZXh0KTsKICAgICAgICB9CgogICAgICAgIHF1YWQudmFsdWUgPSBzdHJlbmd0aDsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gYXBwbHkocXVhZCwgeDEsIF8sIHgyKSB7CiAgICAgICAgaWYgKCFxdWFkLnZhbHVlKSByZXR1cm4gdHJ1ZTsKCiAgICAgICAgdmFyIHggPSBxdWFkLnggLSBub2RlLngsCiAgICAgICAgICAgIHkgPSBxdWFkLnkgLSBub2RlLnksCiAgICAgICAgICAgIHcgPSB4MiAtIHgxLAogICAgICAgICAgICBsID0geCAqIHggKyB5ICogeTsKCiAgICAgICAgLy8gQXBwbHkgdGhlIEJhcm5lcy1IdXQgYXBwcm94aW1hdGlvbiBpZiBwb3NzaWJsZS4KICAgICAgICAvLyBMaW1pdCBmb3JjZXMgZm9yIHZlcnkgY2xvc2Ugbm9kZXM7IHJhbmRvbWl6ZSBkaXJlY3Rpb24gaWYgY29pbmNpZGVudC4KICAgICAgICBpZiAodyAqIHcgLyB0aGV0YTIgPCBsKSB7CiAgICAgICAgICBpZiAobCA8IGRpc3RhbmNlTWF4MikgewogICAgICAgICAgICBpZiAoeCA9PT0gMCkgeCA9IGppZ2dsZSgpLCBsICs9IHggKiB4OwogICAgICAgICAgICBpZiAoeSA9PT0gMCkgeSA9IGppZ2dsZSgpLCBsICs9IHkgKiB5OwogICAgICAgICAgICBpZiAobCA8IGRpc3RhbmNlTWluMikgbCA9IE1hdGguc3FydChkaXN0YW5jZU1pbjIgKiBsKTsKICAgICAgICAgICAgbm9kZS52eCArPSB4ICogcXVhZC52YWx1ZSAqIGFscGhhIC8gbDsKICAgICAgICAgICAgbm9kZS52eSArPSB5ICogcXVhZC52YWx1ZSAqIGFscGhhIC8gbDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBwcm9jZXNzIHBvaW50cyBkaXJlY3RseS4KICAgICAgICBlbHNlIGlmIChxdWFkLmxlbmd0aCB8fCBsID49IGRpc3RhbmNlTWF4MikgcmV0dXJuOwoKICAgICAgICAvLyBMaW1pdCBmb3JjZXMgZm9yIHZlcnkgY2xvc2Ugbm9kZXM7IHJhbmRvbWl6ZSBkaXJlY3Rpb24gaWYgY29pbmNpZGVudC4KICAgICAgICBpZiAocXVhZC5kYXRhICE9PSBub2RlIHx8IHF1YWQubmV4dCkgewogICAgICAgICAgaWYgKHggPT09IDApIHggPSBqaWdnbGUoKSwgbCArPSB4ICogeDsKICAgICAgICAgIGlmICh5ID09PSAwKSB5ID0gamlnZ2xlKCksIGwgKz0geSAqIHk7CiAgICAgICAgICBpZiAobCA8IGRpc3RhbmNlTWluMikgbCA9IE1hdGguc3FydChkaXN0YW5jZU1pbjIgKiBsKTsKICAgICAgICB9CgogICAgICAgIGRvIGlmIChxdWFkLmRhdGEgIT09IG5vZGUpIHsKICAgICAgICAgIHcgPSBzdHJlbmd0aHNbcXVhZC5kYXRhLmluZGV4XSAqIGFscGhhIC8gbDsKICAgICAgICAgIG5vZGUudnggKz0geCAqIHc7CiAgICAgICAgICBub2RlLnZ5ICs9IHkgKiB3OwogICAgICAgIH0gd2hpbGUgKHF1YWQgPSBxdWFkLm5leHQpOwogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXzsKICAgICAgICBpbml0aWFsaXplKCk7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDcoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UuZGlzdGFuY2VNaW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGlzdGFuY2VNaW4yID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydChkaXN0YW5jZU1pbjIpOwogICAgICB9OwoKICAgICAgZm9yY2UuZGlzdGFuY2VNYXggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGlzdGFuY2VNYXgyID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydChkaXN0YW5jZU1heDIpOwogICAgICB9OwoKICAgICAgZm9yY2UudGhldGEgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGhldGEyID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydCh0aGV0YTIpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhZGlhbChyYWRpdXMsIHgsIHkpIHsKICAgICAgdmFyIG5vZGVzLAogICAgICAgICAgc3RyZW5ndGggPSBjb25zdGFudCQ3KDAuMSksCiAgICAgICAgICBzdHJlbmd0aHMsCiAgICAgICAgICByYWRpdXNlczsKCiAgICAgIGlmICh0eXBlb2YgcmFkaXVzICE9PSAiZnVuY3Rpb24iKSByYWRpdXMgPSBjb25zdGFudCQ3KCtyYWRpdXMpOwogICAgICBpZiAoeCA9PSBudWxsKSB4ID0gMDsKICAgICAgaWYgKHkgPT0gbnVsbCkgeSA9IDA7CgogICAgICBmdW5jdGlvbiBmb3JjZShhbHBoYSkgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbm9kZXMubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB2YXIgbm9kZSA9IG5vZGVzW2ldLAogICAgICAgICAgICAgIGR4ID0gbm9kZS54IC0geCB8fCAxZS02LAogICAgICAgICAgICAgIGR5ID0gbm9kZS55IC0geSB8fCAxZS02LAogICAgICAgICAgICAgIHIgPSBNYXRoLnNxcnQoZHggKiBkeCArIGR5ICogZHkpLAogICAgICAgICAgICAgIGsgPSAocmFkaXVzZXNbaV0gLSByKSAqIHN0cmVuZ3Roc1tpXSAqIGFscGhhIC8gcjsKICAgICAgICAgIG5vZGUudnggKz0gZHggKiBrOwogICAgICAgICAgbm9kZS52eSArPSBkeSAqIGs7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBpbml0aWFsaXplKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aDsKICAgICAgICBzdHJlbmd0aHMgPSBuZXcgQXJyYXkobik7CiAgICAgICAgcmFkaXVzZXMgPSBuZXcgQXJyYXkobik7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgcmFkaXVzZXNbaV0gPSArcmFkaXVzKG5vZGVzW2ldLCBpLCBub2Rlcyk7CiAgICAgICAgICBzdHJlbmd0aHNbaV0gPSBpc05hTihyYWRpdXNlc1tpXSkgPyAwIDogK3N0cmVuZ3RoKG5vZGVzW2ldLCBpLCBub2Rlcyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXywgaW5pdGlhbGl6ZSgpOwogICAgICB9OwoKICAgICAgZm9yY2Uuc3RyZW5ndGggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RyZW5ndGggPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ3KCtfKSwgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiBzdHJlbmd0aDsKICAgICAgfTsKCiAgICAgIGZvcmNlLnJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ3KCtfKSwgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiByYWRpdXM7CiAgICAgIH07CgogICAgICBmb3JjZS54ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHggPSArXywgZm9yY2UpIDogeDsKICAgICAgfTsKCiAgICAgIGZvcmNlLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeSA9ICtfLCBmb3JjZSkgOiB5OwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHgkMih4KSB7CiAgICAgIHZhciBzdHJlbmd0aCA9IGNvbnN0YW50JDcoMC4xKSwKICAgICAgICAgIG5vZGVzLAogICAgICAgICAgc3RyZW5ndGhzLAogICAgICAgICAgeHo7CgogICAgICBpZiAodHlwZW9mIHggIT09ICJmdW5jdGlvbiIpIHggPSBjb25zdGFudCQ3KHggPT0gbnVsbCA/IDAgOiAreCk7CgogICAgICBmdW5jdGlvbiBmb3JjZShhbHBoYSkgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbm9kZXMubGVuZ3RoLCBub2RlOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUudnggKz0gKHh6W2ldIC0gbm9kZS54KSAqIHN0cmVuZ3Roc1tpXSAqIGFscGhhOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5pdGlhbGl6ZSgpIHsKICAgICAgICBpZiAoIW5vZGVzKSByZXR1cm47CiAgICAgICAgdmFyIGksIG4gPSBub2Rlcy5sZW5ndGg7CiAgICAgICAgc3RyZW5ndGhzID0gbmV3IEFycmF5KG4pOwogICAgICAgIHh6ID0gbmV3IEFycmF5KG4pOwogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHN0cmVuZ3Roc1tpXSA9IGlzTmFOKHh6W2ldID0gK3gobm9kZXNbaV0sIGksIG5vZGVzKSkgPyAwIDogK3N0cmVuZ3RoKG5vZGVzW2ldLCBpLCBub2Rlcyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXzsKICAgICAgICBpbml0aWFsaXplKCk7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDcoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkNygrXyksIGluaXRpYWxpemUoKSwgZm9yY2UpIDogeDsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3JjZTsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDIoeSkgewogICAgICB2YXIgc3RyZW5ndGggPSBjb25zdGFudCQ3KDAuMSksCiAgICAgICAgICBub2RlcywKICAgICAgICAgIHN0cmVuZ3RocywKICAgICAgICAgIHl6OwoKICAgICAgaWYgKHR5cGVvZiB5ICE9PSAiZnVuY3Rpb24iKSB5ID0gY29uc3RhbnQkNyh5ID09IG51bGwgPyAwIDogK3kpOwoKICAgICAgZnVuY3Rpb24gZm9yY2UoYWxwaGEpIHsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IG5vZGVzLmxlbmd0aCwgbm9kZTsgaSA8IG47ICsraSkgewogICAgICAgICAgbm9kZSA9IG5vZGVzW2ldLCBub2RlLnZ5ICs9ICh5eltpXSAtIG5vZGUueSkgKiBzdHJlbmd0aHNbaV0gKiBhbHBoYTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoOwogICAgICAgIHN0cmVuZ3RocyA9IG5ldyBBcnJheShuKTsKICAgICAgICB5eiA9IG5ldyBBcnJheShuKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBzdHJlbmd0aHNbaV0gPSBpc05hTih5eltpXSA9ICt5KG5vZGVzW2ldLCBpLCBub2RlcykpID8gMCA6ICtzdHJlbmd0aChub2Rlc1tpXSwgaSwgbm9kZXMpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yY2UuaW5pdGlhbGl6ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBub2RlcyA9IF87CiAgICAgICAgaW5pdGlhbGl6ZSgpOwogICAgICB9OwoKICAgICAgZm9yY2Uuc3RyZW5ndGggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RyZW5ndGggPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ3KCtfKSwgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiBzdHJlbmd0aDsKICAgICAgfTsKCiAgICAgIGZvcmNlLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDcoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHk7CiAgICAgIH07CgogICAgICByZXR1cm4gZm9yY2U7CiAgICB9CgogICAgLy8gQ29tcHV0ZXMgdGhlIGRlY2ltYWwgY29lZmZpY2llbnQgYW5kIGV4cG9uZW50IG9mIHRoZSBzcGVjaWZpZWQgbnVtYmVyIHggd2l0aAogICAgLy8gc2lnbmlmaWNhbnQgZGlnaXRzIHAsIHdoZXJlIHggaXMgcG9zaXRpdmUgYW5kIHAgaXMgaW4gWzEsIDIxXSBvciB1bmRlZmluZWQuCiAgICAvLyBGb3IgZXhhbXBsZSwgZm9ybWF0RGVjaW1hbCgxLjIzKSByZXR1cm5zIFsiMTIzIiwgMF0uCiAgICBmdW5jdGlvbiBmb3JtYXREZWNpbWFsKHgsIHApIHsKICAgICAgaWYgKChpID0gKHggPSBwID8geC50b0V4cG9uZW50aWFsKHAgLSAxKSA6IHgudG9FeHBvbmVudGlhbCgpKS5pbmRleE9mKCJlIikpIDwgMCkgcmV0dXJuIG51bGw7IC8vIE5hTiwgwrFJbmZpbml0eQogICAgICB2YXIgaSwgY29lZmZpY2llbnQgPSB4LnNsaWNlKDAsIGkpOwoKICAgICAgLy8gVGhlIHN0cmluZyByZXR1cm5lZCBieSB0b0V4cG9uZW50aWFsIGVpdGhlciBoYXMgdGhlIGZvcm0gXGRcLlxkK2VbLStdXGQrCiAgICAgIC8vIChlLmcuLCAxLjJlKzMpIG9yIHRoZSBmb3JtIFxkZVstK11cZCsgKGUuZy4sIDFlKzMpLgogICAgICByZXR1cm4gWwogICAgICAgIGNvZWZmaWNpZW50Lmxlbmd0aCA+IDEgPyBjb2VmZmljaWVudFswXSArIGNvZWZmaWNpZW50LnNsaWNlKDIpIDogY29lZmZpY2llbnQsCiAgICAgICAgK3guc2xpY2UoaSArIDEpCiAgICAgIF07CiAgICB9CgogICAgZnVuY3Rpb24gZXhwb25lbnQkMSh4KSB7CiAgICAgIHJldHVybiB4ID0gZm9ybWF0RGVjaW1hbChNYXRoLmFicyh4KSksIHggPyB4WzFdIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEdyb3VwKGdyb3VwaW5nLCB0aG91c2FuZHMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHZhbHVlLCB3aWR0aCkgewogICAgICAgIHZhciBpID0gdmFsdWUubGVuZ3RoLAogICAgICAgICAgICB0ID0gW10sCiAgICAgICAgICAgIGogPSAwLAogICAgICAgICAgICBnID0gZ3JvdXBpbmdbMF0sCiAgICAgICAgICAgIGxlbmd0aCA9IDA7CgogICAgICAgIHdoaWxlIChpID4gMCAmJiBnID4gMCkgewogICAgICAgICAgaWYgKGxlbmd0aCArIGcgKyAxID4gd2lkdGgpIGcgPSBNYXRoLm1heCgxLCB3aWR0aCAtIGxlbmd0aCk7CiAgICAgICAgICB0LnB1c2godmFsdWUuc3Vic3RyaW5nKGkgLT0gZywgaSArIGcpKTsKICAgICAgICAgIGlmICgobGVuZ3RoICs9IGcgKyAxKSA+IHdpZHRoKSBicmVhazsKICAgICAgICAgIGcgPSBncm91cGluZ1tqID0gKGogKyAxKSAlIGdyb3VwaW5nLmxlbmd0aF07CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdC5yZXZlcnNlKCkuam9pbih0aG91c2FuZHMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdE51bWVyYWxzKG51bWVyYWxzKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgIHJldHVybiB2YWx1ZS5yZXBsYWNlKC9bMC05XS9nLCBmdW5jdGlvbihpKSB7CiAgICAgICAgICByZXR1cm4gbnVtZXJhbHNbK2ldOwogICAgICAgIH0pOwogICAgICB9OwogICAgfQoKICAgIC8vIFtbZmlsbF1hbGlnbl1bc2lnbl1bc3ltYm9sXVswXVt3aWR0aF1bLF1bLnByZWNpc2lvbl1bfl1bdHlwZV0KICAgIHZhciByZSA9IC9eKD86KC4pPyhbPD49Xl0pKT8oWytcLSggXSk/KFskI10pPygwKT8oXGQrKT8oLCk/KFwuXGQrKT8ofik/KFthLXolXSk/JC9pOwoKICAgIGZ1bmN0aW9uIGZvcm1hdFNwZWNpZmllcihzcGVjaWZpZXIpIHsKICAgICAgaWYgKCEobWF0Y2ggPSByZS5leGVjKHNwZWNpZmllcikpKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgZm9ybWF0OiAiICsgc3BlY2lmaWVyKTsKICAgICAgdmFyIG1hdGNoOwogICAgICByZXR1cm4gbmV3IEZvcm1hdFNwZWNpZmllcih7CiAgICAgICAgZmlsbDogbWF0Y2hbMV0sCiAgICAgICAgYWxpZ246IG1hdGNoWzJdLAogICAgICAgIHNpZ246IG1hdGNoWzNdLAogICAgICAgIHN5bWJvbDogbWF0Y2hbNF0sCiAgICAgICAgemVybzogbWF0Y2hbNV0sCiAgICAgICAgd2lkdGg6IG1hdGNoWzZdLAogICAgICAgIGNvbW1hOiBtYXRjaFs3XSwKICAgICAgICBwcmVjaXNpb246IG1hdGNoWzhdICYmIG1hdGNoWzhdLnNsaWNlKDEpLAogICAgICAgIHRyaW06IG1hdGNoWzldLAogICAgICAgIHR5cGU6IG1hdGNoWzEwXQogICAgICB9KTsKICAgIH0KCiAgICBmb3JtYXRTcGVjaWZpZXIucHJvdG90eXBlID0gRm9ybWF0U3BlY2lmaWVyLnByb3RvdHlwZTsgLy8gaW5zdGFuY2VvZgoKICAgIGZ1bmN0aW9uIEZvcm1hdFNwZWNpZmllcihzcGVjaWZpZXIpIHsKICAgICAgdGhpcy5maWxsID0gc3BlY2lmaWVyLmZpbGwgPT09IHVuZGVmaW5lZCA/ICIgIiA6IHNwZWNpZmllci5maWxsICsgIiI7CiAgICAgIHRoaXMuYWxpZ24gPSBzcGVjaWZpZXIuYWxpZ24gPT09IHVuZGVmaW5lZCA/ICI+IiA6IHNwZWNpZmllci5hbGlnbiArICIiOwogICAgICB0aGlzLnNpZ24gPSBzcGVjaWZpZXIuc2lnbiA9PT0gdW5kZWZpbmVkID8gIi0iIDogc3BlY2lmaWVyLnNpZ24gKyAiIjsKICAgICAgdGhpcy5zeW1ib2wgPSBzcGVjaWZpZXIuc3ltYm9sID09PSB1bmRlZmluZWQgPyAiIiA6IHNwZWNpZmllci5zeW1ib2wgKyAiIjsKICAgICAgdGhpcy56ZXJvID0gISFzcGVjaWZpZXIuemVybzsKICAgICAgdGhpcy53aWR0aCA9IHNwZWNpZmllci53aWR0aCA9PT0gdW5kZWZpbmVkID8gdW5kZWZpbmVkIDogK3NwZWNpZmllci53aWR0aDsKICAgICAgdGhpcy5jb21tYSA9ICEhc3BlY2lmaWVyLmNvbW1hOwogICAgICB0aGlzLnByZWNpc2lvbiA9IHNwZWNpZmllci5wcmVjaXNpb24gPT09IHVuZGVmaW5lZCA/IHVuZGVmaW5lZCA6ICtzcGVjaWZpZXIucHJlY2lzaW9uOwogICAgICB0aGlzLnRyaW0gPSAhIXNwZWNpZmllci50cmltOwogICAgICB0aGlzLnR5cGUgPSBzcGVjaWZpZXIudHlwZSA9PT0gdW5kZWZpbmVkID8gIiIgOiBzcGVjaWZpZXIudHlwZSArICIiOwogICAgfQoKICAgIEZvcm1hdFNwZWNpZmllci5wcm90b3R5cGUudG9TdHJpbmcgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIHRoaXMuZmlsbAogICAgICAgICAgKyB0aGlzLmFsaWduCiAgICAgICAgICArIHRoaXMuc2lnbgogICAgICAgICAgKyB0aGlzLnN5bWJvbAogICAgICAgICAgKyAodGhpcy56ZXJvID8gIjAiIDogIiIpCiAgICAgICAgICArICh0aGlzLndpZHRoID09PSB1bmRlZmluZWQgPyAiIiA6IE1hdGgubWF4KDEsIHRoaXMud2lkdGggfCAwKSkKICAgICAgICAgICsgKHRoaXMuY29tbWEgPyAiLCIgOiAiIikKICAgICAgICAgICsgKHRoaXMucHJlY2lzaW9uID09PSB1bmRlZmluZWQgPyAiIiA6ICIuIiArIE1hdGgubWF4KDAsIHRoaXMucHJlY2lzaW9uIHwgMCkpCiAgICAgICAgICArICh0aGlzLnRyaW0gPyAifiIgOiAiIikKICAgICAgICAgICsgdGhpcy50eXBlOwogICAgfTsKCiAgICAvLyBUcmltcyBpbnNpZ25pZmljYW50IHplcm9zLCBlLmcuLCByZXBsYWNlcyAxLjIwMDBrIHdpdGggMS4yay4KICAgIGZ1bmN0aW9uIGZvcm1hdFRyaW0ocykgewogICAgICBvdXQ6IGZvciAodmFyIG4gPSBzLmxlbmd0aCwgaSA9IDEsIGkwID0gLTEsIGkxOyBpIDwgbjsgKytpKSB7CiAgICAgICAgc3dpdGNoIChzW2ldKSB7CiAgICAgICAgICBjYXNlICIuIjogaTAgPSBpMSA9IGk7IGJyZWFrOwogICAgICAgICAgY2FzZSAiMCI6IGlmIChpMCA9PT0gMCkgaTAgPSBpOyBpMSA9IGk7IGJyZWFrOwogICAgICAgICAgZGVmYXVsdDogaWYgKCErc1tpXSkgYnJlYWsgb3V0OyBpZiAoaTAgPiAwKSBpMCA9IDA7IGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gaTAgPiAwID8gcy5zbGljZSgwLCBpMCkgKyBzLnNsaWNlKGkxICsgMSkgOiBzOwogICAgfQoKICAgIHZhciBwcmVmaXhFeHBvbmVudDsKCiAgICBmdW5jdGlvbiBmb3JtYXRQcmVmaXhBdXRvKHgsIHApIHsKICAgICAgdmFyIGQgPSBmb3JtYXREZWNpbWFsKHgsIHApOwogICAgICBpZiAoIWQpIHJldHVybiB4ICsgIiI7CiAgICAgIHZhciBjb2VmZmljaWVudCA9IGRbMF0sCiAgICAgICAgICBleHBvbmVudCA9IGRbMV0sCiAgICAgICAgICBpID0gZXhwb25lbnQgLSAocHJlZml4RXhwb25lbnQgPSBNYXRoLm1heCgtOCwgTWF0aC5taW4oOCwgTWF0aC5mbG9vcihleHBvbmVudCAvIDMpKSkgKiAzKSArIDEsCiAgICAgICAgICBuID0gY29lZmZpY2llbnQubGVuZ3RoOwogICAgICByZXR1cm4gaSA9PT0gbiA/IGNvZWZmaWNpZW50CiAgICAgICAgICA6IGkgPiBuID8gY29lZmZpY2llbnQgKyBuZXcgQXJyYXkoaSAtIG4gKyAxKS5qb2luKCIwIikKICAgICAgICAgIDogaSA+IDAgPyBjb2VmZmljaWVudC5zbGljZSgwLCBpKSArICIuIiArIGNvZWZmaWNpZW50LnNsaWNlKGkpCiAgICAgICAgICA6ICIwLiIgKyBuZXcgQXJyYXkoMSAtIGkpLmpvaW4oIjAiKSArIGZvcm1hdERlY2ltYWwoeCwgTWF0aC5tYXgoMCwgcCArIGkgLSAxKSlbMF07IC8vIGxlc3MgdGhhbiAxeSEKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRSb3VuZGVkKHgsIHApIHsKICAgICAgdmFyIGQgPSBmb3JtYXREZWNpbWFsKHgsIHApOwogICAgICBpZiAoIWQpIHJldHVybiB4ICsgIiI7CiAgICAgIHZhciBjb2VmZmljaWVudCA9IGRbMF0sCiAgICAgICAgICBleHBvbmVudCA9IGRbMV07CiAgICAgIHJldHVybiBleHBvbmVudCA8IDAgPyAiMC4iICsgbmV3IEFycmF5KC1leHBvbmVudCkuam9pbigiMCIpICsgY29lZmZpY2llbnQKICAgICAgICAgIDogY29lZmZpY2llbnQubGVuZ3RoID4gZXhwb25lbnQgKyAxID8gY29lZmZpY2llbnQuc2xpY2UoMCwgZXhwb25lbnQgKyAxKSArICIuIiArIGNvZWZmaWNpZW50LnNsaWNlKGV4cG9uZW50ICsgMSkKICAgICAgICAgIDogY29lZmZpY2llbnQgKyBuZXcgQXJyYXkoZXhwb25lbnQgLSBjb2VmZmljaWVudC5sZW5ndGggKyAyKS5qb2luKCIwIik7CiAgICB9CgogICAgdmFyIGZvcm1hdFR5cGVzID0gewogICAgICAiJSI6IGZ1bmN0aW9uKHgsIHApIHsgcmV0dXJuICh4ICogMTAwKS50b0ZpeGVkKHApOyB9LAogICAgICAiYiI6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgucm91bmQoeCkudG9TdHJpbmcoMik7IH0sCiAgICAgICJjIjogZnVuY3Rpb24oeCkgeyByZXR1cm4geCArICIiOyB9LAogICAgICAiZCI6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgucm91bmQoeCkudG9TdHJpbmcoMTApOyB9LAogICAgICAiZSI6IGZ1bmN0aW9uKHgsIHApIHsgcmV0dXJuIHgudG9FeHBvbmVudGlhbChwKTsgfSwKICAgICAgImYiOiBmdW5jdGlvbih4LCBwKSB7IHJldHVybiB4LnRvRml4ZWQocCk7IH0sCiAgICAgICJnIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4geC50b1ByZWNpc2lvbihwKTsgfSwKICAgICAgIm8iOiBmdW5jdGlvbih4KSB7IHJldHVybiBNYXRoLnJvdW5kKHgpLnRvU3RyaW5nKDgpOyB9LAogICAgICAicCI6IGZ1bmN0aW9uKHgsIHApIHsgcmV0dXJuIGZvcm1hdFJvdW5kZWQoeCAqIDEwMCwgcCk7IH0sCiAgICAgICJyIjogZm9ybWF0Um91bmRlZCwKICAgICAgInMiOiBmb3JtYXRQcmVmaXhBdXRvLAogICAgICAiWCI6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgucm91bmQoeCkudG9TdHJpbmcoMTYpLnRvVXBwZXJDYXNlKCk7IH0sCiAgICAgICJ4IjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygxNik7IH0KICAgIH07CgogICAgZnVuY3Rpb24gaWRlbnRpdHkkMyh4KSB7CiAgICAgIHJldHVybiB4OwogICAgfQoKICAgIHZhciBtYXAkMiA9IEFycmF5LnByb3RvdHlwZS5tYXAsCiAgICAgICAgcHJlZml4ZXMgPSBbInkiLCJ6IiwiYSIsImYiLCJwIiwibiIsIsK1IiwibSIsIiIsImsiLCJNIiwiRyIsIlQiLCJQIiwiRSIsIloiLCJZIl07CgogICAgZnVuY3Rpb24gZm9ybWF0TG9jYWxlKGxvY2FsZSkgewogICAgICB2YXIgZ3JvdXAgPSBsb2NhbGUuZ3JvdXBpbmcgPT09IHVuZGVmaW5lZCB8fCBsb2NhbGUudGhvdXNhbmRzID09PSB1bmRlZmluZWQgPyBpZGVudGl0eSQzIDogZm9ybWF0R3JvdXAobWFwJDIuY2FsbChsb2NhbGUuZ3JvdXBpbmcsIE51bWJlciksIGxvY2FsZS50aG91c2FuZHMgKyAiIiksCiAgICAgICAgICBjdXJyZW5jeVByZWZpeCA9IGxvY2FsZS5jdXJyZW5jeSA9PT0gdW5kZWZpbmVkID8gIiIgOiBsb2NhbGUuY3VycmVuY3lbMF0gKyAiIiwKICAgICAgICAgIGN1cnJlbmN5U3VmZml4ID0gbG9jYWxlLmN1cnJlbmN5ID09PSB1bmRlZmluZWQgPyAiIiA6IGxvY2FsZS5jdXJyZW5jeVsxXSArICIiLAogICAgICAgICAgZGVjaW1hbCA9IGxvY2FsZS5kZWNpbWFsID09PSB1bmRlZmluZWQgPyAiLiIgOiBsb2NhbGUuZGVjaW1hbCArICIiLAogICAgICAgICAgbnVtZXJhbHMgPSBsb2NhbGUubnVtZXJhbHMgPT09IHVuZGVmaW5lZCA/IGlkZW50aXR5JDMgOiBmb3JtYXROdW1lcmFscyhtYXAkMi5jYWxsKGxvY2FsZS5udW1lcmFscywgU3RyaW5nKSksCiAgICAgICAgICBwZXJjZW50ID0gbG9jYWxlLnBlcmNlbnQgPT09IHVuZGVmaW5lZCA/ICIlIiA6IGxvY2FsZS5wZXJjZW50ICsgIiIsCiAgICAgICAgICBtaW51cyA9IGxvY2FsZS5taW51cyA9PT0gdW5kZWZpbmVkID8gIi0iIDogbG9jYWxlLm1pbnVzICsgIiIsCiAgICAgICAgICBuYW4gPSBsb2NhbGUubmFuID09PSB1bmRlZmluZWQgPyAiTmFOIiA6IGxvY2FsZS5uYW4gKyAiIjsKCiAgICAgIGZ1bmN0aW9uIG5ld0Zvcm1hdChzcGVjaWZpZXIpIHsKICAgICAgICBzcGVjaWZpZXIgPSBmb3JtYXRTcGVjaWZpZXIoc3BlY2lmaWVyKTsKCiAgICAgICAgdmFyIGZpbGwgPSBzcGVjaWZpZXIuZmlsbCwKICAgICAgICAgICAgYWxpZ24gPSBzcGVjaWZpZXIuYWxpZ24sCiAgICAgICAgICAgIHNpZ24gPSBzcGVjaWZpZXIuc2lnbiwKICAgICAgICAgICAgc3ltYm9sID0gc3BlY2lmaWVyLnN5bWJvbCwKICAgICAgICAgICAgemVybyA9IHNwZWNpZmllci56ZXJvLAogICAgICAgICAgICB3aWR0aCA9IHNwZWNpZmllci53aWR0aCwKICAgICAgICAgICAgY29tbWEgPSBzcGVjaWZpZXIuY29tbWEsCiAgICAgICAgICAgIHByZWNpc2lvbiA9IHNwZWNpZmllci5wcmVjaXNpb24sCiAgICAgICAgICAgIHRyaW0gPSBzcGVjaWZpZXIudHJpbSwKICAgICAgICAgICAgdHlwZSA9IHNwZWNpZmllci50eXBlOwoKICAgICAgICAvLyBUaGUgIm4iIHR5cGUgaXMgYW4gYWxpYXMgZm9yICIsZyIuCiAgICAgICAgaWYgKHR5cGUgPT09ICJuIikgY29tbWEgPSB0cnVlLCB0eXBlID0gImciOwoKICAgICAgICAvLyBUaGUgIiIgdHlwZSwgYW5kIGFueSBpbnZhbGlkIHR5cGUsIGlzIGFuIGFsaWFzIGZvciAiLjEyfmciLgogICAgICAgIGVsc2UgaWYgKCFmb3JtYXRUeXBlc1t0eXBlXSkgcHJlY2lzaW9uID09PSB1bmRlZmluZWQgJiYgKHByZWNpc2lvbiA9IDEyKSwgdHJpbSA9IHRydWUsIHR5cGUgPSAiZyI7CgogICAgICAgIC8vIElmIHplcm8gZmlsbCBpcyBzcGVjaWZpZWQsIHBhZGRpbmcgZ29lcyBhZnRlciBzaWduIGFuZCBiZWZvcmUgZGlnaXRzLgogICAgICAgIGlmICh6ZXJvIHx8IChmaWxsID09PSAiMCIgJiYgYWxpZ24gPT09ICI9IikpIHplcm8gPSB0cnVlLCBmaWxsID0gIjAiLCBhbGlnbiA9ICI9IjsKCiAgICAgICAgLy8gQ29tcHV0ZSB0aGUgcHJlZml4IGFuZCBzdWZmaXguCiAgICAgICAgLy8gRm9yIFNJLXByZWZpeCwgdGhlIHN1ZmZpeCBpcyBsYXppbHkgY29tcHV0ZWQuCiAgICAgICAgdmFyIHByZWZpeCA9IHN5bWJvbCA9PT0gIiQiID8gY3VycmVuY3lQcmVmaXggOiBzeW1ib2wgPT09ICIjIiAmJiAvW2JveFhdLy50ZXN0KHR5cGUpID8gIjAiICsgdHlwZS50b0xvd2VyQ2FzZSgpIDogIiIsCiAgICAgICAgICAgIHN1ZmZpeCA9IHN5bWJvbCA9PT0gIiQiID8gY3VycmVuY3lTdWZmaXggOiAvWyVwXS8udGVzdCh0eXBlKSA/IHBlcmNlbnQgOiAiIjsKCiAgICAgICAgLy8gV2hhdCBmb3JtYXQgZnVuY3Rpb24gc2hvdWxkIHdlIHVzZT8KICAgICAgICAvLyBJcyB0aGlzIGFuIGludGVnZXIgdHlwZT8KICAgICAgICAvLyBDYW4gdGhpcyB0eXBlIGdlbmVyYXRlIGV4cG9uZW50aWFsIG5vdGF0aW9uPwogICAgICAgIHZhciBmb3JtYXRUeXBlID0gZm9ybWF0VHlwZXNbdHlwZV0sCiAgICAgICAgICAgIG1heWJlU3VmZml4ID0gL1tkZWZncHJzJV0vLnRlc3QodHlwZSk7CgogICAgICAgIC8vIFNldCB0aGUgZGVmYXVsdCBwcmVjaXNpb24gaWYgbm90IHNwZWNpZmllZCwKICAgICAgICAvLyBvciBjbGFtcCB0aGUgc3BlY2lmaWVkIHByZWNpc2lvbiB0byB0aGUgc3VwcG9ydGVkIHJhbmdlLgogICAgICAgIC8vIEZvciBzaWduaWZpY2FudCBwcmVjaXNpb24sIGl0IG11c3QgYmUgaW4gWzEsIDIxXS4KICAgICAgICAvLyBGb3IgZml4ZWQgcHJlY2lzaW9uLCBpdCBtdXN0IGJlIGluIFswLCAyMF0uCiAgICAgICAgcHJlY2lzaW9uID0gcHJlY2lzaW9uID09PSB1bmRlZmluZWQgPyA2CiAgICAgICAgICAgIDogL1tncHJzXS8udGVzdCh0eXBlKSA/IE1hdGgubWF4KDEsIE1hdGgubWluKDIxLCBwcmVjaXNpb24pKQogICAgICAgICAgICA6IE1hdGgubWF4KDAsIE1hdGgubWluKDIwLCBwcmVjaXNpb24pKTsKCiAgICAgICAgZnVuY3Rpb24gZm9ybWF0KHZhbHVlKSB7CiAgICAgICAgICB2YXIgdmFsdWVQcmVmaXggPSBwcmVmaXgsCiAgICAgICAgICAgICAgdmFsdWVTdWZmaXggPSBzdWZmaXgsCiAgICAgICAgICAgICAgaSwgbiwgYzsKCiAgICAgICAgICBpZiAodHlwZSA9PT0gImMiKSB7CiAgICAgICAgICAgIHZhbHVlU3VmZml4ID0gZm9ybWF0VHlwZSh2YWx1ZSkgKyB2YWx1ZVN1ZmZpeDsKICAgICAgICAgICAgdmFsdWUgPSAiIjsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHZhbHVlID0gK3ZhbHVlOwoKICAgICAgICAgICAgLy8gRGV0ZXJtaW5lIHRoZSBzaWduLiAtMCBpcyBub3QgbGVzcyB0aGFuIDAsIGJ1dCAxIC8gLTAgaXMhCiAgICAgICAgICAgIHZhciB2YWx1ZU5lZ2F0aXZlID0gdmFsdWUgPCAwIHx8IDEgLyB2YWx1ZSA8IDA7CgogICAgICAgICAgICAvLyBQZXJmb3JtIHRoZSBpbml0aWFsIGZvcm1hdHRpbmcuCiAgICAgICAgICAgIHZhbHVlID0gaXNOYU4odmFsdWUpID8gbmFuIDogZm9ybWF0VHlwZShNYXRoLmFicyh2YWx1ZSksIHByZWNpc2lvbik7CgogICAgICAgICAgICAvLyBUcmltIGluc2lnbmlmaWNhbnQgemVyb3MuCiAgICAgICAgICAgIGlmICh0cmltKSB2YWx1ZSA9IGZvcm1hdFRyaW0odmFsdWUpOwoKICAgICAgICAgICAgLy8gSWYgYSBuZWdhdGl2ZSB2YWx1ZSByb3VuZHMgdG8gemVybyBhZnRlciBmb3JtYXR0aW5nLCBhbmQgbm8gZXhwbGljaXQgcG9zaXRpdmUgc2lnbiBpcyByZXF1ZXN0ZWQsIGhpZGUgdGhlIHNpZ24uCiAgICAgICAgICAgIGlmICh2YWx1ZU5lZ2F0aXZlICYmICt2YWx1ZSA9PT0gMCAmJiBzaWduICE9PSAiKyIpIHZhbHVlTmVnYXRpdmUgPSBmYWxzZTsKCiAgICAgICAgICAgIC8vIENvbXB1dGUgdGhlIHByZWZpeCBhbmQgc3VmZml4LgogICAgICAgICAgICB2YWx1ZVByZWZpeCA9ICh2YWx1ZU5lZ2F0aXZlID8gKHNpZ24gPT09ICIoIiA/IHNpZ24gOiBtaW51cykgOiBzaWduID09PSAiLSIgfHwgc2lnbiA9PT0gIigiID8gIiIgOiBzaWduKSArIHZhbHVlUHJlZml4OwogICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9ICh0eXBlID09PSAicyIgPyBwcmVmaXhlc1s4ICsgcHJlZml4RXhwb25lbnQgLyAzXSA6ICIiKSArIHZhbHVlU3VmZml4ICsgKHZhbHVlTmVnYXRpdmUgJiYgc2lnbiA9PT0gIigiID8gIikiIDogIiIpOwoKICAgICAgICAgICAgLy8gQnJlYWsgdGhlIGZvcm1hdHRlZCB2YWx1ZSBpbnRvIHRoZSBpbnRlZ2VyIOKAnHZhbHVl4oCdIHBhcnQgdGhhdCBjYW4gYmUKICAgICAgICAgICAgLy8gZ3JvdXBlZCwgYW5kIGZyYWN0aW9uYWwgb3IgZXhwb25lbnRpYWwg4oCcc3VmZml44oCdIHBhcnQgdGhhdCBpcyBub3QuCiAgICAgICAgICAgIGlmIChtYXliZVN1ZmZpeCkgewogICAgICAgICAgICAgIGkgPSAtMSwgbiA9IHZhbHVlLmxlbmd0aDsKICAgICAgICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgICAgICAgaWYgKGMgPSB2YWx1ZS5jaGFyQ29kZUF0KGkpLCA0OCA+IGMgfHwgYyA+IDU3KSB7CiAgICAgICAgICAgICAgICAgIHZhbHVlU3VmZml4ID0gKGMgPT09IDQ2ID8gZGVjaW1hbCArIHZhbHVlLnNsaWNlKGkgKyAxKSA6IHZhbHVlLnNsaWNlKGkpKSArIHZhbHVlU3VmZml4OwogICAgICAgICAgICAgICAgICB2YWx1ZSA9IHZhbHVlLnNsaWNlKDAsIGkpOwogICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvLyBJZiB0aGUgZmlsbCBjaGFyYWN0ZXIgaXMgbm90ICIwIiwgZ3JvdXBpbmcgaXMgYXBwbGllZCBiZWZvcmUgcGFkZGluZy4KICAgICAgICAgIGlmIChjb21tYSAmJiAhemVybykgdmFsdWUgPSBncm91cCh2YWx1ZSwgSW5maW5pdHkpOwoKICAgICAgICAgIC8vIENvbXB1dGUgdGhlIHBhZGRpbmcuCiAgICAgICAgICB2YXIgbGVuZ3RoID0gdmFsdWVQcmVmaXgubGVuZ3RoICsgdmFsdWUubGVuZ3RoICsgdmFsdWVTdWZmaXgubGVuZ3RoLAogICAgICAgICAgICAgIHBhZGRpbmcgPSBsZW5ndGggPCB3aWR0aCA/IG5ldyBBcnJheSh3aWR0aCAtIGxlbmd0aCArIDEpLmpvaW4oZmlsbCkgOiAiIjsKCiAgICAgICAgICAvLyBJZiB0aGUgZmlsbCBjaGFyYWN0ZXIgaXMgIjAiLCBncm91cGluZyBpcyBhcHBsaWVkIGFmdGVyIHBhZGRpbmcuCiAgICAgICAgICBpZiAoY29tbWEgJiYgemVybykgdmFsdWUgPSBncm91cChwYWRkaW5nICsgdmFsdWUsIHBhZGRpbmcubGVuZ3RoID8gd2lkdGggLSB2YWx1ZVN1ZmZpeC5sZW5ndGggOiBJbmZpbml0eSksIHBhZGRpbmcgPSAiIjsKCiAgICAgICAgICAvLyBSZWNvbnN0cnVjdCB0aGUgZmluYWwgb3V0cHV0IGJhc2VkIG9uIHRoZSBkZXNpcmVkIGFsaWdubWVudC4KICAgICAgICAgIHN3aXRjaCAoYWxpZ24pIHsKICAgICAgICAgICAgY2FzZSAiPCI6IHZhbHVlID0gdmFsdWVQcmVmaXggKyB2YWx1ZSArIHZhbHVlU3VmZml4ICsgcGFkZGluZzsgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgIj0iOiB2YWx1ZSA9IHZhbHVlUHJlZml4ICsgcGFkZGluZyArIHZhbHVlICsgdmFsdWVTdWZmaXg7IGJyZWFrOwogICAgICAgICAgICBjYXNlICJeIjogdmFsdWUgPSBwYWRkaW5nLnNsaWNlKDAsIGxlbmd0aCA9IHBhZGRpbmcubGVuZ3RoID4+IDEpICsgdmFsdWVQcmVmaXggKyB2YWx1ZSArIHZhbHVlU3VmZml4ICsgcGFkZGluZy5zbGljZShsZW5ndGgpOyBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDogdmFsdWUgPSBwYWRkaW5nICsgdmFsdWVQcmVmaXggKyB2YWx1ZSArIHZhbHVlU3VmZml4OyBicmVhazsKICAgICAgICAgIH0KCiAgICAgICAgICByZXR1cm4gbnVtZXJhbHModmFsdWUpOwogICAgICAgIH0KCiAgICAgICAgZm9ybWF0LnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gc3BlY2lmaWVyICsgIiI7CiAgICAgICAgfTsKCiAgICAgICAgcmV0dXJuIGZvcm1hdDsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0UHJlZml4KHNwZWNpZmllciwgdmFsdWUpIHsKICAgICAgICB2YXIgZiA9IG5ld0Zvcm1hdCgoc3BlY2lmaWVyID0gZm9ybWF0U3BlY2lmaWVyKHNwZWNpZmllciksIHNwZWNpZmllci50eXBlID0gImYiLCBzcGVjaWZpZXIpKSwKICAgICAgICAgICAgZSA9IE1hdGgubWF4KC04LCBNYXRoLm1pbig4LCBNYXRoLmZsb29yKGV4cG9uZW50JDEodmFsdWUpIC8gMykpKSAqIDMsCiAgICAgICAgICAgIGsgPSBNYXRoLnBvdygxMCwgLWUpLAogICAgICAgICAgICBwcmVmaXggPSBwcmVmaXhlc1s4ICsgZSAvIDNdOwogICAgICAgIHJldHVybiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgcmV0dXJuIGYoayAqIHZhbHVlKSArIHByZWZpeDsKICAgICAgICB9OwogICAgICB9CgogICAgICByZXR1cm4gewogICAgICAgIGZvcm1hdDogbmV3Rm9ybWF0LAogICAgICAgIGZvcm1hdFByZWZpeDogZm9ybWF0UHJlZml4CiAgICAgIH07CiAgICB9CgogICAgdmFyIGxvY2FsZTsKICAgIHZhciBmb3JtYXQ7CiAgICB2YXIgZm9ybWF0UHJlZml4OwoKICAgIGRlZmF1bHRMb2NhbGUoewogICAgICBkZWNpbWFsOiAiLiIsCiAgICAgIHRob3VzYW5kczogIiwiLAogICAgICBncm91cGluZzogWzNdLAogICAgICBjdXJyZW5jeTogWyIkIiwgIiJdLAogICAgICBtaW51czogIi0iCiAgICB9KTsKCiAgICBmdW5jdGlvbiBkZWZhdWx0TG9jYWxlKGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlID0gZm9ybWF0TG9jYWxlKGRlZmluaXRpb24pOwogICAgICBmb3JtYXQgPSBsb2NhbGUuZm9ybWF0OwogICAgICBmb3JtYXRQcmVmaXggPSBsb2NhbGUuZm9ybWF0UHJlZml4OwogICAgICByZXR1cm4gbG9jYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvbkZpeGVkKHN0ZXApIHsKICAgICAgcmV0dXJuIE1hdGgubWF4KDAsIC1leHBvbmVudCQxKE1hdGguYWJzKHN0ZXApKSk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJlY2lzaW9uUHJlZml4KHN0ZXAsIHZhbHVlKSB7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCBNYXRoLm1heCgtOCwgTWF0aC5taW4oOCwgTWF0aC5mbG9vcihleHBvbmVudCQxKHZhbHVlKSAvIDMpKSkgKiAzIC0gZXhwb25lbnQkMShNYXRoLmFicyhzdGVwKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvblJvdW5kKHN0ZXAsIG1heCkgewogICAgICBzdGVwID0gTWF0aC5hYnMoc3RlcCksIG1heCA9IE1hdGguYWJzKG1heCkgLSBzdGVwOwogICAgICByZXR1cm4gTWF0aC5tYXgoMCwgZXhwb25lbnQkMShtYXgpIC0gZXhwb25lbnQkMShzdGVwKSkgKyAxOwogICAgfQoKICAgIC8vIEFkZHMgZmxvYXRpbmcgcG9pbnQgbnVtYmVycyB3aXRoIHR3aWNlIHRoZSBub3JtYWwgcHJlY2lzaW9uLgogICAgLy8gUmVmZXJlbmNlOiBKLiBSLiBTaGV3Y2h1aywgQWRhcHRpdmUgUHJlY2lzaW9uIEZsb2F0aW5nLVBvaW50IEFyaXRobWV0aWMgYW5kCiAgICAvLyBGYXN0IFJvYnVzdCBHZW9tZXRyaWMgUHJlZGljYXRlcywgRGlzY3JldGUgJiBDb21wdXRhdGlvbmFsIEdlb21ldHJ5IDE4KDMpCiAgICAvLyAzMDXigJMzNjMgKDE5OTcpLgogICAgLy8gQ29kZSBhZGFwdGVkIGZyb20gR2VvZ3JhcGhpY0xpYiBieSBDaGFybGVzIEYuIEYuIEthcm5leSwKICAgIC8vIGh0dHA6Ly9nZW9ncmFwaGljbGliLnNvdXJjZWZvcmdlLm5ldC8KCiAgICBmdW5jdGlvbiBhZGRlcigpIHsKICAgICAgcmV0dXJuIG5ldyBBZGRlcjsKICAgIH0KCiAgICBmdW5jdGlvbiBBZGRlcigpIHsKICAgICAgdGhpcy5yZXNldCgpOwogICAgfQoKICAgIEFkZGVyLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IEFkZGVyLAogICAgICByZXNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zID0gLy8gcm91bmRlZCB2YWx1ZQogICAgICAgIHRoaXMudCA9IDA7IC8vIGV4YWN0IGVycm9yCiAgICAgIH0sCiAgICAgIGFkZDogZnVuY3Rpb24oeSkgewogICAgICAgIGFkZCQxKHRlbXAsIHksIHRoaXMudCk7CiAgICAgICAgYWRkJDEodGhpcywgdGVtcC5zLCB0aGlzLnMpOwogICAgICAgIGlmICh0aGlzLnMpIHRoaXMudCArPSB0ZW1wLnQ7CiAgICAgICAgZWxzZSB0aGlzLnMgPSB0ZW1wLnQ7CiAgICAgIH0sCiAgICAgIHZhbHVlT2Y6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnM7CiAgICAgIH0KICAgIH07CgogICAgdmFyIHRlbXAgPSBuZXcgQWRkZXI7CgogICAgZnVuY3Rpb24gYWRkJDEoYWRkZXIsIGEsIGIpIHsKICAgICAgdmFyIHggPSBhZGRlci5zID0gYSArIGIsCiAgICAgICAgICBidiA9IHggLSBhLAogICAgICAgICAgYXYgPSB4IC0gYnY7CiAgICAgIGFkZGVyLnQgPSAoYSAtIGF2KSArIChiIC0gYnYpOwogICAgfQoKICAgIHZhciBlcHNpbG9uJDIgPSAxZS02OwogICAgdmFyIGVwc2lsb24yJDEgPSAxZS0xMjsKICAgIHZhciBwaSQzID0gTWF0aC5QSTsKICAgIHZhciBoYWxmUGkkMiA9IHBpJDMgLyAyOwogICAgdmFyIHF1YXJ0ZXJQaSA9IHBpJDMgLyA0OwogICAgdmFyIHRhdSQzID0gcGkkMyAqIDI7CgogICAgdmFyIGRlZ3JlZXMkMSA9IDE4MCAvIHBpJDM7CiAgICB2YXIgcmFkaWFucyA9IHBpJDMgLyAxODA7CgogICAgdmFyIGFicyA9IE1hdGguYWJzOwogICAgdmFyIGF0YW4gPSBNYXRoLmF0YW47CiAgICB2YXIgYXRhbjIgPSBNYXRoLmF0YW4yOwogICAgdmFyIGNvcyQxID0gTWF0aC5jb3M7CiAgICB2YXIgY2VpbCA9IE1hdGguY2VpbDsKICAgIHZhciBleHAgPSBNYXRoLmV4cDsKICAgIHZhciBsb2cgPSBNYXRoLmxvZzsKICAgIHZhciBwb3cgPSBNYXRoLnBvdzsKICAgIHZhciBzaW4kMSA9IE1hdGguc2luOwogICAgdmFyIHNpZ24gPSBNYXRoLnNpZ24gfHwgZnVuY3Rpb24oeCkgeyByZXR1cm4geCA+IDAgPyAxIDogeCA8IDAgPyAtMSA6IDA7IH07CiAgICB2YXIgc3FydCA9IE1hdGguc3FydDsKICAgIHZhciB0YW4gPSBNYXRoLnRhbjsKCiAgICBmdW5jdGlvbiBhY29zKHgpIHsKICAgICAgcmV0dXJuIHggPiAxID8gMCA6IHggPCAtMSA/IHBpJDMgOiBNYXRoLmFjb3MoeCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXNpbih4KSB7CiAgICAgIHJldHVybiB4ID4gMSA/IGhhbGZQaSQyIDogeCA8IC0xID8gLWhhbGZQaSQyIDogTWF0aC5hc2luKHgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhhdmVyc2luKHgpIHsKICAgICAgcmV0dXJuICh4ID0gc2luJDEoeCAvIDIpKSAqIHg7CiAgICB9CgogICAgZnVuY3Rpb24gbm9vcCQyKCkge30KCiAgICBmdW5jdGlvbiBzdHJlYW1HZW9tZXRyeShnZW9tZXRyeSwgc3RyZWFtKSB7CiAgICAgIGlmIChnZW9tZXRyeSAmJiBzdHJlYW1HZW9tZXRyeVR5cGUuaGFzT3duUHJvcGVydHkoZ2VvbWV0cnkudHlwZSkpIHsKICAgICAgICBzdHJlYW1HZW9tZXRyeVR5cGVbZ2VvbWV0cnkudHlwZV0oZ2VvbWV0cnksIHN0cmVhbSk7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgc3RyZWFtT2JqZWN0VHlwZSA9IHsKICAgICAgRmVhdHVyZTogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICBzdHJlYW1HZW9tZXRyeShvYmplY3QuZ2VvbWV0cnksIHN0cmVhbSk7CiAgICAgIH0sCiAgICAgIEZlYXR1cmVDb2xsZWN0aW9uOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHZhciBmZWF0dXJlcyA9IG9iamVjdC5mZWF0dXJlcywgaSA9IC0xLCBuID0gZmVhdHVyZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBzdHJlYW1HZW9tZXRyeShmZWF0dXJlc1tpXS5nZW9tZXRyeSwgc3RyZWFtKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgc3RyZWFtR2VvbWV0cnlUeXBlID0gewogICAgICBTcGhlcmU6IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgc3RyZWFtLnNwaGVyZSgpOwogICAgICB9LAogICAgICBQb2ludDogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICBvYmplY3QgPSBvYmplY3QuY29vcmRpbmF0ZXM7CiAgICAgICAgc3RyZWFtLnBvaW50KG9iamVjdFswXSwgb2JqZWN0WzFdLCBvYmplY3RbMl0pOwogICAgICB9LAogICAgICBNdWx0aVBvaW50OiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHZhciBjb29yZGluYXRlcyA9IG9iamVjdC5jb29yZGluYXRlcywgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBvYmplY3QgPSBjb29yZGluYXRlc1tpXSwgc3RyZWFtLnBvaW50KG9iamVjdFswXSwgb2JqZWN0WzFdLCBvYmplY3RbMl0pOwogICAgICB9LAogICAgICBMaW5lU3RyaW5nOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHN0cmVhbUxpbmUob2JqZWN0LmNvb3JkaW5hdGVzLCBzdHJlYW0sIDApOwogICAgICB9LAogICAgICBNdWx0aUxpbmVTdHJpbmc6IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgdmFyIGNvb3JkaW5hdGVzID0gb2JqZWN0LmNvb3JkaW5hdGVzLCBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHN0cmVhbUxpbmUoY29vcmRpbmF0ZXNbaV0sIHN0cmVhbSwgMCk7CiAgICAgIH0sCiAgICAgIFBvbHlnb246IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgc3RyZWFtUG9seWdvbihvYmplY3QuY29vcmRpbmF0ZXMsIHN0cmVhbSk7CiAgICAgIH0sCiAgICAgIE11bHRpUG9seWdvbjogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICB2YXIgY29vcmRpbmF0ZXMgPSBvYmplY3QuY29vcmRpbmF0ZXMsIGkgPSAtMSwgbiA9IGNvb3JkaW5hdGVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgc3RyZWFtUG9seWdvbihjb29yZGluYXRlc1tpXSwgc3RyZWFtKTsKICAgICAgfSwKICAgICAgR2VvbWV0cnlDb2xsZWN0aW9uOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHZhciBnZW9tZXRyaWVzID0gb2JqZWN0Lmdlb21ldHJpZXMsIGkgPSAtMSwgbiA9IGdlb21ldHJpZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBzdHJlYW1HZW9tZXRyeShnZW9tZXRyaWVzW2ldLCBzdHJlYW0pOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHN0cmVhbUxpbmUoY29vcmRpbmF0ZXMsIHN0cmVhbSwgY2xvc2VkKSB7CiAgICAgIHZhciBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGggLSBjbG9zZWQsIGNvb3JkaW5hdGU7CiAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgd2hpbGUgKCsraSA8IG4pIGNvb3JkaW5hdGUgPSBjb29yZGluYXRlc1tpXSwgc3RyZWFtLnBvaW50KGNvb3JkaW5hdGVbMF0sIGNvb3JkaW5hdGVbMV0sIGNvb3JkaW5hdGVbMl0pOwogICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0cmVhbVBvbHlnb24oY29vcmRpbmF0ZXMsIHN0cmVhbSkgewogICAgICB2YXIgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICBzdHJlYW0ucG9seWdvblN0YXJ0KCk7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBzdHJlYW1MaW5lKGNvb3JkaW5hdGVzW2ldLCBzdHJlYW0sIDEpOwogICAgICBzdHJlYW0ucG9seWdvbkVuZCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGdlb1N0cmVhbShvYmplY3QsIHN0cmVhbSkgewogICAgICBpZiAob2JqZWN0ICYmIHN0cmVhbU9iamVjdFR5cGUuaGFzT3duUHJvcGVydHkob2JqZWN0LnR5cGUpKSB7CiAgICAgICAgc3RyZWFtT2JqZWN0VHlwZVtvYmplY3QudHlwZV0ob2JqZWN0LCBzdHJlYW0pOwogICAgICB9IGVsc2UgewogICAgICAgIHN0cmVhbUdlb21ldHJ5KG9iamVjdCwgc3RyZWFtKTsKICAgICAgfQogICAgfQoKICAgIHZhciBhcmVhUmluZ1N1bSA9IGFkZGVyKCk7CgogICAgdmFyIGFyZWFTdW0gPSBhZGRlcigpLAogICAgICAgIGxhbWJkYTAwLAogICAgICAgIHBoaTAwLAogICAgICAgIGxhbWJkYTAsCiAgICAgICAgY29zUGhpMCwKICAgICAgICBzaW5QaGkwOwoKICAgIHZhciBhcmVhU3RyZWFtID0gewogICAgICBwb2ludDogbm9vcCQyLAogICAgICBsaW5lU3RhcnQ6IG5vb3AkMiwKICAgICAgbGluZUVuZDogbm9vcCQyLAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGFyZWFSaW5nU3VtLnJlc2V0KCk7CiAgICAgICAgYXJlYVN0cmVhbS5saW5lU3RhcnQgPSBhcmVhUmluZ1N0YXJ0OwogICAgICAgIGFyZWFTdHJlYW0ubGluZUVuZCA9IGFyZWFSaW5nRW5kOwogICAgICB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYXJlYVJpbmcgPSArYXJlYVJpbmdTdW07CiAgICAgICAgYXJlYVN1bS5hZGQoYXJlYVJpbmcgPCAwID8gdGF1JDMgKyBhcmVhUmluZyA6IGFyZWFSaW5nKTsKICAgICAgICB0aGlzLmxpbmVTdGFydCA9IHRoaXMubGluZUVuZCA9IHRoaXMucG9pbnQgPSBub29wJDI7CiAgICAgIH0sCiAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7CiAgICAgICAgYXJlYVN1bS5hZGQodGF1JDMpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGFyZWFSaW5nU3RhcnQoKSB7CiAgICAgIGFyZWFTdHJlYW0ucG9pbnQgPSBhcmVhUG9pbnRGaXJzdDsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhUmluZ0VuZCgpIHsKICAgICAgYXJlYVBvaW50KGxhbWJkYTAwLCBwaGkwMCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJlYVBvaW50Rmlyc3QobGFtYmRhLCBwaGkpIHsKICAgICAgYXJlYVN0cmVhbS5wb2ludCA9IGFyZWFQb2ludDsKICAgICAgbGFtYmRhMDAgPSBsYW1iZGEsIHBoaTAwID0gcGhpOwogICAgICBsYW1iZGEgKj0gcmFkaWFucywgcGhpICo9IHJhZGlhbnM7CiAgICAgIGxhbWJkYTAgPSBsYW1iZGEsIGNvc1BoaTAgPSBjb3MkMShwaGkgPSBwaGkgLyAyICsgcXVhcnRlclBpKSwgc2luUGhpMCA9IHNpbiQxKHBoaSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJlYVBvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zLCBwaGkgKj0gcmFkaWFuczsKICAgICAgcGhpID0gcGhpIC8gMiArIHF1YXJ0ZXJQaTsgLy8gaGFsZiB0aGUgYW5ndWxhciBkaXN0YW5jZSBmcm9tIHNvdXRoIHBvbGUKCiAgICAgIC8vIFNwaGVyaWNhbCBleGNlc3MgRSBmb3IgYSBzcGhlcmljYWwgdHJpYW5nbGUgd2l0aCB2ZXJ0aWNlczogc291dGggcG9sZSwKICAgICAgLy8gcHJldmlvdXMgcG9pbnQsIGN1cnJlbnQgcG9pbnQuICBVc2VzIGEgZm9ybXVsYSBkZXJpdmVkIGZyb20gQ2Fnbm9saeKAmXMKICAgICAgLy8gdGhlb3JlbS4gIFNlZSBUb2RodW50ZXIsIFNwaGVyaWNhbCBUcmlnLiAoMTg3MSksIFNlYy4gMTAzLCBFcS4gKDIpLgogICAgICB2YXIgZExhbWJkYSA9IGxhbWJkYSAtIGxhbWJkYTAsCiAgICAgICAgICBzZExhbWJkYSA9IGRMYW1iZGEgPj0gMCA/IDEgOiAtMSwKICAgICAgICAgIGFkTGFtYmRhID0gc2RMYW1iZGEgKiBkTGFtYmRhLAogICAgICAgICAgY29zUGhpID0gY29zJDEocGhpKSwKICAgICAgICAgIHNpblBoaSA9IHNpbiQxKHBoaSksCiAgICAgICAgICBrID0gc2luUGhpMCAqIHNpblBoaSwKICAgICAgICAgIHUgPSBjb3NQaGkwICogY29zUGhpICsgayAqIGNvcyQxKGFkTGFtYmRhKSwKICAgICAgICAgIHYgPSBrICogc2RMYW1iZGEgKiBzaW4kMShhZExhbWJkYSk7CiAgICAgIGFyZWFSaW5nU3VtLmFkZChhdGFuMih2LCB1KSk7CgogICAgICAvLyBBZHZhbmNlIHRoZSBwcmV2aW91cyBwb2ludHMuCiAgICAgIGxhbWJkYTAgPSBsYW1iZGEsIGNvc1BoaTAgPSBjb3NQaGksIHNpblBoaTAgPSBzaW5QaGk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJlYSQxKG9iamVjdCkgewogICAgICBhcmVhU3VtLnJlc2V0KCk7CiAgICAgIGdlb1N0cmVhbShvYmplY3QsIGFyZWFTdHJlYW0pOwogICAgICByZXR1cm4gYXJlYVN1bSAqIDI7CiAgICB9CgogICAgZnVuY3Rpb24gc3BoZXJpY2FsKGNhcnRlc2lhbikgewogICAgICByZXR1cm4gW2F0YW4yKGNhcnRlc2lhblsxXSwgY2FydGVzaWFuWzBdKSwgYXNpbihjYXJ0ZXNpYW5bMl0pXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW4oc3BoZXJpY2FsKSB7CiAgICAgIHZhciBsYW1iZGEgPSBzcGhlcmljYWxbMF0sIHBoaSA9IHNwaGVyaWNhbFsxXSwgY29zUGhpID0gY29zJDEocGhpKTsKICAgICAgcmV0dXJuIFtjb3NQaGkgKiBjb3MkMShsYW1iZGEpLCBjb3NQaGkgKiBzaW4kMShsYW1iZGEpLCBzaW4kMShwaGkpXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5Eb3QoYSwgYikgewogICAgICByZXR1cm4gYVswXSAqIGJbMF0gKyBhWzFdICogYlsxXSArIGFbMl0gKiBiWzJdOwogICAgfQoKICAgIGZ1bmN0aW9uIGNhcnRlc2lhbkNyb3NzKGEsIGIpIHsKICAgICAgcmV0dXJuIFthWzFdICogYlsyXSAtIGFbMl0gKiBiWzFdLCBhWzJdICogYlswXSAtIGFbMF0gKiBiWzJdLCBhWzBdICogYlsxXSAtIGFbMV0gKiBiWzBdXTsKICAgIH0KCiAgICAvLyBUT0RPIHJldHVybiBhCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5BZGRJblBsYWNlKGEsIGIpIHsKICAgICAgYVswXSArPSBiWzBdLCBhWzFdICs9IGJbMV0sIGFbMl0gKz0gYlsyXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5TY2FsZSh2ZWN0b3IsIGspIHsKICAgICAgcmV0dXJuIFt2ZWN0b3JbMF0gKiBrLCB2ZWN0b3JbMV0gKiBrLCB2ZWN0b3JbMl0gKiBrXTsKICAgIH0KCiAgICAvLyBUT0RPIHJldHVybiBkCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5Ob3JtYWxpemVJblBsYWNlKGQpIHsKICAgICAgdmFyIGwgPSBzcXJ0KGRbMF0gKiBkWzBdICsgZFsxXSAqIGRbMV0gKyBkWzJdICogZFsyXSk7CiAgICAgIGRbMF0gLz0gbCwgZFsxXSAvPSBsLCBkWzJdIC89IGw7CiAgICB9CgogICAgdmFyIGxhbWJkYTAkMSwgcGhpMCwgbGFtYmRhMSwgcGhpMSwgLy8gYm91bmRzCiAgICAgICAgbGFtYmRhMiwgLy8gcHJldmlvdXMgbGFtYmRhLWNvb3JkaW5hdGUKICAgICAgICBsYW1iZGEwMCQxLCBwaGkwMCQxLCAvLyBmaXJzdCBwb2ludAogICAgICAgIHAwLCAvLyBwcmV2aW91cyAzRCBwb2ludAogICAgICAgIGRlbHRhU3VtID0gYWRkZXIoKSwKICAgICAgICByYW5nZXMsCiAgICAgICAgcmFuZ2U7CgogICAgdmFyIGJvdW5kc1N0cmVhbSA9IHsKICAgICAgcG9pbnQ6IGJvdW5kc1BvaW50LAogICAgICBsaW5lU3RhcnQ6IGJvdW5kc0xpbmVTdGFydCwKICAgICAgbGluZUVuZDogYm91bmRzTGluZUVuZCwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBib3VuZHNTdHJlYW0ucG9pbnQgPSBib3VuZHNSaW5nUG9pbnQ7CiAgICAgICAgYm91bmRzU3RyZWFtLmxpbmVTdGFydCA9IGJvdW5kc1JpbmdTdGFydDsKICAgICAgICBib3VuZHNTdHJlYW0ubGluZUVuZCA9IGJvdW5kc1JpbmdFbmQ7CiAgICAgICAgZGVsdGFTdW0ucmVzZXQoKTsKICAgICAgICBhcmVhU3RyZWFtLnBvbHlnb25TdGFydCgpOwogICAgICB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBhcmVhU3RyZWFtLnBvbHlnb25FbmQoKTsKICAgICAgICBib3VuZHNTdHJlYW0ucG9pbnQgPSBib3VuZHNQb2ludDsKICAgICAgICBib3VuZHNTdHJlYW0ubGluZVN0YXJ0ID0gYm91bmRzTGluZVN0YXJ0OwogICAgICAgIGJvdW5kc1N0cmVhbS5saW5lRW5kID0gYm91bmRzTGluZUVuZDsKICAgICAgICBpZiAoYXJlYVJpbmdTdW0gPCAwKSBsYW1iZGEwJDEgPSAtKGxhbWJkYTEgPSAxODApLCBwaGkwID0gLShwaGkxID0gOTApOwogICAgICAgIGVsc2UgaWYgKGRlbHRhU3VtID4gZXBzaWxvbiQyKSBwaGkxID0gOTA7CiAgICAgICAgZWxzZSBpZiAoZGVsdGFTdW0gPCAtZXBzaWxvbiQyKSBwaGkwID0gLTkwOwogICAgICAgIHJhbmdlWzBdID0gbGFtYmRhMCQxLCByYW5nZVsxXSA9IGxhbWJkYTE7CiAgICAgIH0sCiAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7CiAgICAgICAgbGFtYmRhMCQxID0gLShsYW1iZGExID0gMTgwKSwgcGhpMCA9IC0ocGhpMSA9IDkwKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBib3VuZHNQb2ludChsYW1iZGEsIHBoaSkgewogICAgICByYW5nZXMucHVzaChyYW5nZSA9IFtsYW1iZGEwJDEgPSBsYW1iZGEsIGxhbWJkYTEgPSBsYW1iZGFdKTsKICAgICAgaWYgKHBoaSA8IHBoaTApIHBoaTAgPSBwaGk7CiAgICAgIGlmIChwaGkgPiBwaGkxKSBwaGkxID0gcGhpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVQb2ludChsYW1iZGEsIHBoaSkgewogICAgICB2YXIgcCA9IGNhcnRlc2lhbihbbGFtYmRhICogcmFkaWFucywgcGhpICogcmFkaWFuc10pOwogICAgICBpZiAocDApIHsKICAgICAgICB2YXIgbm9ybWFsID0gY2FydGVzaWFuQ3Jvc3MocDAsIHApLAogICAgICAgICAgICBlcXVhdG9yaWFsID0gW25vcm1hbFsxXSwgLW5vcm1hbFswXSwgMF0sCiAgICAgICAgICAgIGluZmxlY3Rpb24gPSBjYXJ0ZXNpYW5Dcm9zcyhlcXVhdG9yaWFsLCBub3JtYWwpOwogICAgICAgIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UoaW5mbGVjdGlvbik7CiAgICAgICAgaW5mbGVjdGlvbiA9IHNwaGVyaWNhbChpbmZsZWN0aW9uKTsKICAgICAgICB2YXIgZGVsdGEgPSBsYW1iZGEgLSBsYW1iZGEyLAogICAgICAgICAgICBzaWduID0gZGVsdGEgPiAwID8gMSA6IC0xLAogICAgICAgICAgICBsYW1iZGFpID0gaW5mbGVjdGlvblswXSAqIGRlZ3JlZXMkMSAqIHNpZ24sCiAgICAgICAgICAgIHBoaWksCiAgICAgICAgICAgIGFudGltZXJpZGlhbiA9IGFicyhkZWx0YSkgPiAxODA7CiAgICAgICAgaWYgKGFudGltZXJpZGlhbiBeIChzaWduICogbGFtYmRhMiA8IGxhbWJkYWkgJiYgbGFtYmRhaSA8IHNpZ24gKiBsYW1iZGEpKSB7CiAgICAgICAgICBwaGlpID0gaW5mbGVjdGlvblsxXSAqIGRlZ3JlZXMkMTsKICAgICAgICAgIGlmIChwaGlpID4gcGhpMSkgcGhpMSA9IHBoaWk7CiAgICAgICAgfSBlbHNlIGlmIChsYW1iZGFpID0gKGxhbWJkYWkgKyAzNjApICUgMzYwIC0gMTgwLCBhbnRpbWVyaWRpYW4gXiAoc2lnbiAqIGxhbWJkYTIgPCBsYW1iZGFpICYmIGxhbWJkYWkgPCBzaWduICogbGFtYmRhKSkgewogICAgICAgICAgcGhpaSA9IC1pbmZsZWN0aW9uWzFdICogZGVncmVlcyQxOwogICAgICAgICAgaWYgKHBoaWkgPCBwaGkwKSBwaGkwID0gcGhpaTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgaWYgKHBoaSA8IHBoaTApIHBoaTAgPSBwaGk7CiAgICAgICAgICBpZiAocGhpID4gcGhpMSkgcGhpMSA9IHBoaTsKICAgICAgICB9CiAgICAgICAgaWYgKGFudGltZXJpZGlhbikgewogICAgICAgICAgaWYgKGxhbWJkYSA8IGxhbWJkYTIpIHsKICAgICAgICAgICAgaWYgKGFuZ2xlKGxhbWJkYTAkMSwgbGFtYmRhKSA+IGFuZ2xlKGxhbWJkYTAkMSwgbGFtYmRhMSkpIGxhbWJkYTEgPSBsYW1iZGE7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoYW5nbGUobGFtYmRhLCBsYW1iZGExKSA+IGFuZ2xlKGxhbWJkYTAkMSwgbGFtYmRhMSkpIGxhbWJkYTAkMSA9IGxhbWJkYTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgaWYgKGxhbWJkYTEgPj0gbGFtYmRhMCQxKSB7CiAgICAgICAgICAgIGlmIChsYW1iZGEgPCBsYW1iZGEwJDEpIGxhbWJkYTAkMSA9IGxhbWJkYTsKICAgICAgICAgICAgaWYgKGxhbWJkYSA+IGxhbWJkYTEpIGxhbWJkYTEgPSBsYW1iZGE7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAobGFtYmRhID4gbGFtYmRhMikgewogICAgICAgICAgICAgIGlmIChhbmdsZShsYW1iZGEwJDEsIGxhbWJkYSkgPiBhbmdsZShsYW1iZGEwJDEsIGxhbWJkYTEpKSBsYW1iZGExID0gbGFtYmRhOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGlmIChhbmdsZShsYW1iZGEsIGxhbWJkYTEpID4gYW5nbGUobGFtYmRhMCQxLCBsYW1iZGExKSkgbGFtYmRhMCQxID0gbGFtYmRhOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIHJhbmdlcy5wdXNoKHJhbmdlID0gW2xhbWJkYTAkMSA9IGxhbWJkYSwgbGFtYmRhMSA9IGxhbWJkYV0pOwogICAgICB9CiAgICAgIGlmIChwaGkgPCBwaGkwKSBwaGkwID0gcGhpOwogICAgICBpZiAocGhpID4gcGhpMSkgcGhpMSA9IHBoaTsKICAgICAgcDAgPSBwLCBsYW1iZGEyID0gbGFtYmRhOwogICAgfQoKICAgIGZ1bmN0aW9uIGJvdW5kc0xpbmVTdGFydCgpIHsKICAgICAgYm91bmRzU3RyZWFtLnBvaW50ID0gbGluZVBvaW50OwogICAgfQoKICAgIGZ1bmN0aW9uIGJvdW5kc0xpbmVFbmQoKSB7CiAgICAgIHJhbmdlWzBdID0gbGFtYmRhMCQxLCByYW5nZVsxXSA9IGxhbWJkYTE7CiAgICAgIGJvdW5kc1N0cmVhbS5wb2ludCA9IGJvdW5kc1BvaW50OwogICAgICBwMCA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmRzUmluZ1BvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgIGlmIChwMCkgewogICAgICAgIHZhciBkZWx0YSA9IGxhbWJkYSAtIGxhbWJkYTI7CiAgICAgICAgZGVsdGFTdW0uYWRkKGFicyhkZWx0YSkgPiAxODAgPyBkZWx0YSArIChkZWx0YSA+IDAgPyAzNjAgOiAtMzYwKSA6IGRlbHRhKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBsYW1iZGEwMCQxID0gbGFtYmRhLCBwaGkwMCQxID0gcGhpOwogICAgICB9CiAgICAgIGFyZWFTdHJlYW0ucG9pbnQobGFtYmRhLCBwaGkpOwogICAgICBsaW5lUG9pbnQobGFtYmRhLCBwaGkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJvdW5kc1JpbmdTdGFydCgpIHsKICAgICAgYXJlYVN0cmVhbS5saW5lU3RhcnQoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBib3VuZHNSaW5nRW5kKCkgewogICAgICBib3VuZHNSaW5nUG9pbnQobGFtYmRhMDAkMSwgcGhpMDAkMSk7CiAgICAgIGFyZWFTdHJlYW0ubGluZUVuZCgpOwogICAgICBpZiAoYWJzKGRlbHRhU3VtKSA+IGVwc2lsb24kMikgbGFtYmRhMCQxID0gLShsYW1iZGExID0gMTgwKTsKICAgICAgcmFuZ2VbMF0gPSBsYW1iZGEwJDEsIHJhbmdlWzFdID0gbGFtYmRhMTsKICAgICAgcDAgPSBudWxsOwogICAgfQoKICAgIC8vIEZpbmRzIHRoZSBsZWZ0LXJpZ2h0IGRpc3RhbmNlIGJldHdlZW4gdHdvIGxvbmdpdHVkZXMuCiAgICAvLyBUaGlzIGlzIGFsbW9zdCB0aGUgc2FtZSBhcyAobGFtYmRhMSAtIGxhbWJkYTAgKyAzNjDCsCkgJSAzNjDCsCwgZXhjZXB0IHRoYXQgd2Ugd2FudAogICAgLy8gdGhlIGRpc3RhbmNlIGJldHdlZW4gwrExODDCsCB0byBiZSAzNjDCsC4KICAgIGZ1bmN0aW9uIGFuZ2xlKGxhbWJkYTAsIGxhbWJkYTEpIHsKICAgICAgcmV0dXJuIChsYW1iZGExIC09IGxhbWJkYTApIDwgMCA/IGxhbWJkYTEgKyAzNjAgOiBsYW1iZGExOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhbmdlQ29tcGFyZShhLCBiKSB7CiAgICAgIHJldHVybiBhWzBdIC0gYlswXTsKICAgIH0KCiAgICBmdW5jdGlvbiByYW5nZUNvbnRhaW5zKHJhbmdlLCB4KSB7CiAgICAgIHJldHVybiByYW5nZVswXSA8PSByYW5nZVsxXSA/IHJhbmdlWzBdIDw9IHggJiYgeCA8PSByYW5nZVsxXSA6IHggPCByYW5nZVswXSB8fCByYW5nZVsxXSA8IHg7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmRzKGZlYXR1cmUpIHsKICAgICAgdmFyIGksIG4sIGEsIGIsIG1lcmdlZCwgZGVsdGFNYXgsIGRlbHRhOwoKICAgICAgcGhpMSA9IGxhbWJkYTEgPSAtKGxhbWJkYTAkMSA9IHBoaTAgPSBJbmZpbml0eSk7CiAgICAgIHJhbmdlcyA9IFtdOwogICAgICBnZW9TdHJlYW0oZmVhdHVyZSwgYm91bmRzU3RyZWFtKTsKCiAgICAgIC8vIEZpcnN0LCBzb3J0IHJhbmdlcyBieSB0aGVpciBtaW5pbXVtIGxvbmdpdHVkZXMuCiAgICAgIGlmIChuID0gcmFuZ2VzLmxlbmd0aCkgewogICAgICAgIHJhbmdlcy5zb3J0KHJhbmdlQ29tcGFyZSk7CgogICAgICAgIC8vIFRoZW4sIG1lcmdlIGFueSByYW5nZXMgdGhhdCBvdmVybGFwLgogICAgICAgIGZvciAoaSA9IDEsIGEgPSByYW5nZXNbMF0sIG1lcmdlZCA9IFthXTsgaSA8IG47ICsraSkgewogICAgICAgICAgYiA9IHJhbmdlc1tpXTsKICAgICAgICAgIGlmIChyYW5nZUNvbnRhaW5zKGEsIGJbMF0pIHx8IHJhbmdlQ29udGFpbnMoYSwgYlsxXSkpIHsKICAgICAgICAgICAgaWYgKGFuZ2xlKGFbMF0sIGJbMV0pID4gYW5nbGUoYVswXSwgYVsxXSkpIGFbMV0gPSBiWzFdOwogICAgICAgICAgICBpZiAoYW5nbGUoYlswXSwgYVsxXSkgPiBhbmdsZShhWzBdLCBhWzFdKSkgYVswXSA9IGJbMF07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBtZXJnZWQucHVzaChhID0gYik7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBGaW5hbGx5LCBmaW5kIHRoZSBsYXJnZXN0IGdhcCBiZXR3ZWVuIHRoZSBtZXJnZWQgcmFuZ2VzLgogICAgICAgIC8vIFRoZSBmaW5hbCBib3VuZGluZyBib3ggd2lsbCBiZSB0aGUgaW52ZXJzZSBvZiB0aGlzIGdhcC4KICAgICAgICBmb3IgKGRlbHRhTWF4ID0gLUluZmluaXR5LCBuID0gbWVyZ2VkLmxlbmd0aCAtIDEsIGkgPSAwLCBhID0gbWVyZ2VkW25dOyBpIDw9IG47IGEgPSBiLCArK2kpIHsKICAgICAgICAgIGIgPSBtZXJnZWRbaV07CiAgICAgICAgICBpZiAoKGRlbHRhID0gYW5nbGUoYVsxXSwgYlswXSkpID4gZGVsdGFNYXgpIGRlbHRhTWF4ID0gZGVsdGEsIGxhbWJkYTAkMSA9IGJbMF0sIGxhbWJkYTEgPSBhWzFdOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmFuZ2VzID0gcmFuZ2UgPSBudWxsOwoKICAgICAgcmV0dXJuIGxhbWJkYTAkMSA9PT0gSW5maW5pdHkgfHwgcGhpMCA9PT0gSW5maW5pdHkKICAgICAgICAgID8gW1tOYU4sIE5hTl0sIFtOYU4sIE5hTl1dCiAgICAgICAgICA6IFtbbGFtYmRhMCQxLCBwaGkwXSwgW2xhbWJkYTEsIHBoaTFdXTsKICAgIH0KCiAgICB2YXIgVzAsIFcxLAogICAgICAgIFgwLCBZMCwgWjAsCiAgICAgICAgWDEsIFkxLCBaMSwKICAgICAgICBYMiwgWTIsIFoyLAogICAgICAgIGxhbWJkYTAwJDIsIHBoaTAwJDIsIC8vIGZpcnN0IHBvaW50CiAgICAgICAgeDAsIHkwLCB6MDsgLy8gcHJldmlvdXMgcG9pbnQKCiAgICB2YXIgY2VudHJvaWRTdHJlYW0gPSB7CiAgICAgIHNwaGVyZTogbm9vcCQyLAogICAgICBwb2ludDogY2VudHJvaWRQb2ludCwKICAgICAgbGluZVN0YXJ0OiBjZW50cm9pZExpbmVTdGFydCwKICAgICAgbGluZUVuZDogY2VudHJvaWRMaW5lRW5kLAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGNlbnRyb2lkU3RyZWFtLmxpbmVTdGFydCA9IGNlbnRyb2lkUmluZ1N0YXJ0OwogICAgICAgIGNlbnRyb2lkU3RyZWFtLmxpbmVFbmQgPSBjZW50cm9pZFJpbmdFbmQ7CiAgICAgIH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGNlbnRyb2lkU3RyZWFtLmxpbmVTdGFydCA9IGNlbnRyb2lkTGluZVN0YXJ0OwogICAgICAgIGNlbnRyb2lkU3RyZWFtLmxpbmVFbmQgPSBjZW50cm9pZExpbmVFbmQ7CiAgICAgIH0KICAgIH07CgogICAgLy8gQXJpdGhtZXRpYyBtZWFuIG9mIENhcnRlc2lhbiB2ZWN0b3JzLgogICAgZnVuY3Rpb24gY2VudHJvaWRQb2ludChsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucywgcGhpICo9IHJhZGlhbnM7CiAgICAgIHZhciBjb3NQaGkgPSBjb3MkMShwaGkpOwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuKGNvc1BoaSAqIGNvcyQxKGxhbWJkYSksIGNvc1BoaSAqIHNpbiQxKGxhbWJkYSksIHNpbiQxKHBoaSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnRDYXJ0ZXNpYW4oeCwgeSwgeikgewogICAgICArK1cwOwogICAgICBYMCArPSAoeCAtIFgwKSAvIFcwOwogICAgICBZMCArPSAoeSAtIFkwKSAvIFcwOwogICAgICBaMCArPSAoeiAtIFowKSAvIFcwOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZVN0YXJ0KCkgewogICAgICBjZW50cm9pZFN0cmVhbS5wb2ludCA9IGNlbnRyb2lkTGluZVBvaW50Rmlyc3Q7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRMaW5lUG9pbnRGaXJzdChsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucywgcGhpICo9IHJhZGlhbnM7CiAgICAgIHZhciBjb3NQaGkgPSBjb3MkMShwaGkpOwogICAgICB4MCA9IGNvc1BoaSAqIGNvcyQxKGxhbWJkYSk7CiAgICAgIHkwID0gY29zUGhpICogc2luJDEobGFtYmRhKTsKICAgICAgejAgPSBzaW4kMShwaGkpOwogICAgICBjZW50cm9pZFN0cmVhbS5wb2ludCA9IGNlbnRyb2lkTGluZVBvaW50OwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuKHgwLCB5MCwgejApOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZVBvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zLCBwaGkgKj0gcmFkaWFuczsKICAgICAgdmFyIGNvc1BoaSA9IGNvcyQxKHBoaSksCiAgICAgICAgICB4ID0gY29zUGhpICogY29zJDEobGFtYmRhKSwKICAgICAgICAgIHkgPSBjb3NQaGkgKiBzaW4kMShsYW1iZGEpLAogICAgICAgICAgeiA9IHNpbiQxKHBoaSksCiAgICAgICAgICB3ID0gYXRhbjIoc3FydCgodyA9IHkwICogeiAtIHowICogeSkgKiB3ICsgKHcgPSB6MCAqIHggLSB4MCAqIHopICogdyArICh3ID0geDAgKiB5IC0geTAgKiB4KSAqIHcpLCB4MCAqIHggKyB5MCAqIHkgKyB6MCAqIHopOwogICAgICBXMSArPSB3OwogICAgICBYMSArPSB3ICogKHgwICsgKHgwID0geCkpOwogICAgICBZMSArPSB3ICogKHkwICsgKHkwID0geSkpOwogICAgICBaMSArPSB3ICogKHowICsgKHowID0geikpOwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuKHgwLCB5MCwgejApOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZUVuZCgpIHsKICAgICAgY2VudHJvaWRTdHJlYW0ucG9pbnQgPSBjZW50cm9pZFBvaW50OwogICAgfQoKICAgIC8vIFNlZSBKLiBFLiBCcm9jaywgVGhlIEluZXJ0aWEgVGVuc29yIGZvciBhIFNwaGVyaWNhbCBUcmlhbmdsZSwKICAgIC8vIEouIEFwcGxpZWQgTWVjaGFuaWNzIDQyLCAyMzkgKDE5NzUpLgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nU3RhcnQoKSB7CiAgICAgIGNlbnRyb2lkU3RyZWFtLnBvaW50ID0gY2VudHJvaWRSaW5nUG9pbnRGaXJzdDsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZFJpbmdFbmQoKSB7CiAgICAgIGNlbnRyb2lkUmluZ1BvaW50KGxhbWJkYTAwJDIsIHBoaTAwJDIpOwogICAgICBjZW50cm9pZFN0cmVhbS5wb2ludCA9IGNlbnRyb2lkUG9pbnQ7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nUG9pbnRGaXJzdChsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEwMCQyID0gbGFtYmRhLCBwaGkwMCQyID0gcGhpOwogICAgICBsYW1iZGEgKj0gcmFkaWFucywgcGhpICo9IHJhZGlhbnM7CiAgICAgIGNlbnRyb2lkU3RyZWFtLnBvaW50ID0gY2VudHJvaWRSaW5nUG9pbnQ7CiAgICAgIHZhciBjb3NQaGkgPSBjb3MkMShwaGkpOwogICAgICB4MCA9IGNvc1BoaSAqIGNvcyQxKGxhbWJkYSk7CiAgICAgIHkwID0gY29zUGhpICogc2luJDEobGFtYmRhKTsKICAgICAgejAgPSBzaW4kMShwaGkpOwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuKHgwLCB5MCwgejApOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUmluZ1BvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zLCBwaGkgKj0gcmFkaWFuczsKICAgICAgdmFyIGNvc1BoaSA9IGNvcyQxKHBoaSksCiAgICAgICAgICB4ID0gY29zUGhpICogY29zJDEobGFtYmRhKSwKICAgICAgICAgIHkgPSBjb3NQaGkgKiBzaW4kMShsYW1iZGEpLAogICAgICAgICAgeiA9IHNpbiQxKHBoaSksCiAgICAgICAgICBjeCA9IHkwICogeiAtIHowICogeSwKICAgICAgICAgIGN5ID0gejAgKiB4IC0geDAgKiB6LAogICAgICAgICAgY3ogPSB4MCAqIHkgLSB5MCAqIHgsCiAgICAgICAgICBtID0gc3FydChjeCAqIGN4ICsgY3kgKiBjeSArIGN6ICogY3opLAogICAgICAgICAgdyA9IGFzaW4obSksIC8vIGxpbmUgd2VpZ2h0ID0gYW5nbGUKICAgICAgICAgIHYgPSBtICYmIC13IC8gbTsgLy8gYXJlYSB3ZWlnaHQgbXVsdGlwbGllcgogICAgICBYMiArPSB2ICogY3g7CiAgICAgIFkyICs9IHYgKiBjeTsKICAgICAgWjIgKz0gdiAqIGN6OwogICAgICBXMSArPSB3OwogICAgICBYMSArPSB3ICogKHgwICsgKHgwID0geCkpOwogICAgICBZMSArPSB3ICogKHkwICsgKHkwID0geSkpOwogICAgICBaMSArPSB3ICogKHowICsgKHowID0geikpOwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuKHgwLCB5MCwgejApOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkKG9iamVjdCkgewogICAgICBXMCA9IFcxID0KICAgICAgWDAgPSBZMCA9IFowID0KICAgICAgWDEgPSBZMSA9IFoxID0KICAgICAgWDIgPSBZMiA9IFoyID0gMDsKICAgICAgZ2VvU3RyZWFtKG9iamVjdCwgY2VudHJvaWRTdHJlYW0pOwoKICAgICAgdmFyIHggPSBYMiwKICAgICAgICAgIHkgPSBZMiwKICAgICAgICAgIHogPSBaMiwKICAgICAgICAgIG0gPSB4ICogeCArIHkgKiB5ICsgeiAqIHo7CgogICAgICAvLyBJZiB0aGUgYXJlYS13ZWlnaHRlZCBjY2VudHJvaWQgaXMgdW5kZWZpbmVkLCBmYWxsIGJhY2sgdG8gbGVuZ3RoLXdlaWdodGVkIGNjZW50cm9pZC4KICAgICAgaWYgKG0gPCBlcHNpbG9uMiQxKSB7CiAgICAgICAgeCA9IFgxLCB5ID0gWTEsIHogPSBaMTsKICAgICAgICAvLyBJZiB0aGUgZmVhdHVyZSBoYXMgemVybyBsZW5ndGgsIGZhbGwgYmFjayB0byBhcml0aG1ldGljIG1lYW4gb2YgcG9pbnQgdmVjdG9ycy4KICAgICAgICBpZiAoVzEgPCBlcHNpbG9uJDIpIHggPSBYMCwgeSA9IFkwLCB6ID0gWjA7CiAgICAgICAgbSA9IHggKiB4ICsgeSAqIHkgKyB6ICogejsKICAgICAgICAvLyBJZiB0aGUgZmVhdHVyZSBzdGlsbCBoYXMgYW4gdW5kZWZpbmVkIGNjZW50cm9pZCwgdGhlbiByZXR1cm4uCiAgICAgICAgaWYgKG0gPCBlcHNpbG9uMiQxKSByZXR1cm4gW05hTiwgTmFOXTsKICAgICAgfQoKICAgICAgcmV0dXJuIFthdGFuMih5LCB4KSAqIGRlZ3JlZXMkMSwgYXNpbih6IC8gc3FydChtKSkgKiBkZWdyZWVzJDFdOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JDgoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY29tcG9zZShhLCBiKSB7CgogICAgICBmdW5jdGlvbiBjb21wb3NlKHgsIHkpIHsKICAgICAgICByZXR1cm4geCA9IGEoeCwgeSksIGIoeFswXSwgeFsxXSk7CiAgICAgIH0KCiAgICAgIGlmIChhLmludmVydCAmJiBiLmludmVydCkgY29tcG9zZS5pbnZlcnQgPSBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgcmV0dXJuIHggPSBiLmludmVydCh4LCB5KSwgeCAmJiBhLmludmVydCh4WzBdLCB4WzFdKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBjb21wb3NlOwogICAgfQoKICAgIGZ1bmN0aW9uIHJvdGF0aW9uSWRlbnRpdHkobGFtYmRhLCBwaGkpIHsKICAgICAgcmV0dXJuIFthYnMobGFtYmRhKSA+IHBpJDMgPyBsYW1iZGEgKyBNYXRoLnJvdW5kKC1sYW1iZGEgLyB0YXUkMykgKiB0YXUkMyA6IGxhbWJkYSwgcGhpXTsKICAgIH0KCiAgICByb3RhdGlvbklkZW50aXR5LmludmVydCA9IHJvdGF0aW9uSWRlbnRpdHk7CgogICAgZnVuY3Rpb24gcm90YXRlUmFkaWFucyhkZWx0YUxhbWJkYSwgZGVsdGFQaGksIGRlbHRhR2FtbWEpIHsKICAgICAgcmV0dXJuIChkZWx0YUxhbWJkYSAlPSB0YXUkMykgPyAoZGVsdGFQaGkgfHwgZGVsdGFHYW1tYSA/IGNvbXBvc2Uocm90YXRpb25MYW1iZGEoZGVsdGFMYW1iZGEpLCByb3RhdGlvblBoaUdhbW1hKGRlbHRhUGhpLCBkZWx0YUdhbW1hKSkKICAgICAgICA6IHJvdGF0aW9uTGFtYmRhKGRlbHRhTGFtYmRhKSkKICAgICAgICA6IChkZWx0YVBoaSB8fCBkZWx0YUdhbW1hID8gcm90YXRpb25QaGlHYW1tYShkZWx0YVBoaSwgZGVsdGFHYW1tYSkKICAgICAgICA6IHJvdGF0aW9uSWRlbnRpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcndhcmRSb3RhdGlvbkxhbWJkYShkZWx0YUxhbWJkYSkgewogICAgICByZXR1cm4gZnVuY3Rpb24obGFtYmRhLCBwaGkpIHsKICAgICAgICByZXR1cm4gbGFtYmRhICs9IGRlbHRhTGFtYmRhLCBbbGFtYmRhID4gcGkkMyA/IGxhbWJkYSAtIHRhdSQzIDogbGFtYmRhIDwgLXBpJDMgPyBsYW1iZGEgKyB0YXUkMyA6IGxhbWJkYSwgcGhpXTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiByb3RhdGlvbkxhbWJkYShkZWx0YUxhbWJkYSkgewogICAgICB2YXIgcm90YXRpb24gPSBmb3J3YXJkUm90YXRpb25MYW1iZGEoZGVsdGFMYW1iZGEpOwogICAgICByb3RhdGlvbi5pbnZlcnQgPSBmb3J3YXJkUm90YXRpb25MYW1iZGEoLWRlbHRhTGFtYmRhKTsKICAgICAgcmV0dXJuIHJvdGF0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIHJvdGF0aW9uUGhpR2FtbWEoZGVsdGFQaGksIGRlbHRhR2FtbWEpIHsKICAgICAgdmFyIGNvc0RlbHRhUGhpID0gY29zJDEoZGVsdGFQaGkpLAogICAgICAgICAgc2luRGVsdGFQaGkgPSBzaW4kMShkZWx0YVBoaSksCiAgICAgICAgICBjb3NEZWx0YUdhbW1hID0gY29zJDEoZGVsdGFHYW1tYSksCiAgICAgICAgICBzaW5EZWx0YUdhbW1hID0gc2luJDEoZGVsdGFHYW1tYSk7CgogICAgICBmdW5jdGlvbiByb3RhdGlvbihsYW1iZGEsIHBoaSkgewogICAgICAgIHZhciBjb3NQaGkgPSBjb3MkMShwaGkpLAogICAgICAgICAgICB4ID0gY29zJDEobGFtYmRhKSAqIGNvc1BoaSwKICAgICAgICAgICAgeSA9IHNpbiQxKGxhbWJkYSkgKiBjb3NQaGksCiAgICAgICAgICAgIHogPSBzaW4kMShwaGkpLAogICAgICAgICAgICBrID0geiAqIGNvc0RlbHRhUGhpICsgeCAqIHNpbkRlbHRhUGhpOwogICAgICAgIHJldHVybiBbCiAgICAgICAgICBhdGFuMih5ICogY29zRGVsdGFHYW1tYSAtIGsgKiBzaW5EZWx0YUdhbW1hLCB4ICogY29zRGVsdGFQaGkgLSB6ICogc2luRGVsdGFQaGkpLAogICAgICAgICAgYXNpbihrICogY29zRGVsdGFHYW1tYSArIHkgKiBzaW5EZWx0YUdhbW1hKQogICAgICAgIF07CiAgICAgIH0KCiAgICAgIHJvdGF0aW9uLmludmVydCA9IGZ1bmN0aW9uKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgdmFyIGNvc1BoaSA9IGNvcyQxKHBoaSksCiAgICAgICAgICAgIHggPSBjb3MkMShsYW1iZGEpICogY29zUGhpLAogICAgICAgICAgICB5ID0gc2luJDEobGFtYmRhKSAqIGNvc1BoaSwKICAgICAgICAgICAgeiA9IHNpbiQxKHBoaSksCiAgICAgICAgICAgIGsgPSB6ICogY29zRGVsdGFHYW1tYSAtIHkgKiBzaW5EZWx0YUdhbW1hOwogICAgICAgIHJldHVybiBbCiAgICAgICAgICBhdGFuMih5ICogY29zRGVsdGFHYW1tYSArIHogKiBzaW5EZWx0YUdhbW1hLCB4ICogY29zRGVsdGFQaGkgKyBrICogc2luRGVsdGFQaGkpLAogICAgICAgICAgYXNpbihrICogY29zRGVsdGFQaGkgLSB4ICogc2luRGVsdGFQaGkpCiAgICAgICAgXTsKICAgICAgfTsKCiAgICAgIHJldHVybiByb3RhdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiByb3RhdGlvbihyb3RhdGUpIHsKICAgICAgcm90YXRlID0gcm90YXRlUmFkaWFucyhyb3RhdGVbMF0gKiByYWRpYW5zLCByb3RhdGVbMV0gKiByYWRpYW5zLCByb3RhdGUubGVuZ3RoID4gMiA/IHJvdGF0ZVsyXSAqIHJhZGlhbnMgOiAwKTsKCiAgICAgIGZ1bmN0aW9uIGZvcndhcmQoY29vcmRpbmF0ZXMpIHsKICAgICAgICBjb29yZGluYXRlcyA9IHJvdGF0ZShjb29yZGluYXRlc1swXSAqIHJhZGlhbnMsIGNvb3JkaW5hdGVzWzFdICogcmFkaWFucyk7CiAgICAgICAgcmV0dXJuIGNvb3JkaW5hdGVzWzBdICo9IGRlZ3JlZXMkMSwgY29vcmRpbmF0ZXNbMV0gKj0gZGVncmVlcyQxLCBjb29yZGluYXRlczsKICAgICAgfQoKICAgICAgZm9yd2FyZC5pbnZlcnQgPSBmdW5jdGlvbihjb29yZGluYXRlcykgewogICAgICAgIGNvb3JkaW5hdGVzID0gcm90YXRlLmludmVydChjb29yZGluYXRlc1swXSAqIHJhZGlhbnMsIGNvb3JkaW5hdGVzWzFdICogcmFkaWFucyk7CiAgICAgICAgcmV0dXJuIGNvb3JkaW5hdGVzWzBdICo9IGRlZ3JlZXMkMSwgY29vcmRpbmF0ZXNbMV0gKj0gZGVncmVlcyQxLCBjb29yZGluYXRlczsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3J3YXJkOwogICAgfQoKICAgIC8vIEdlbmVyYXRlcyBhIGNpcmNsZSBjZW50ZXJlZCBhdCBbMMKwLCAwwrBdLCB3aXRoIGEgZ2l2ZW4gcmFkaXVzIGFuZCBwcmVjaXNpb24uCiAgICBmdW5jdGlvbiBjaXJjbGVTdHJlYW0oc3RyZWFtLCByYWRpdXMsIGRlbHRhLCBkaXJlY3Rpb24sIHQwLCB0MSkgewogICAgICBpZiAoIWRlbHRhKSByZXR1cm47CiAgICAgIHZhciBjb3NSYWRpdXMgPSBjb3MkMShyYWRpdXMpLAogICAgICAgICAgc2luUmFkaXVzID0gc2luJDEocmFkaXVzKSwKICAgICAgICAgIHN0ZXAgPSBkaXJlY3Rpb24gKiBkZWx0YTsKICAgICAgaWYgKHQwID09IG51bGwpIHsKICAgICAgICB0MCA9IHJhZGl1cyArIGRpcmVjdGlvbiAqIHRhdSQzOwogICAgICAgIHQxID0gcmFkaXVzIC0gc3RlcCAvIDI7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgdDAgPSBjaXJjbGVSYWRpdXMoY29zUmFkaXVzLCB0MCk7CiAgICAgICAgdDEgPSBjaXJjbGVSYWRpdXMoY29zUmFkaXVzLCB0MSk7CiAgICAgICAgaWYgKGRpcmVjdGlvbiA+IDAgPyB0MCA8IHQxIDogdDAgPiB0MSkgdDAgKz0gZGlyZWN0aW9uICogdGF1JDM7CiAgICAgIH0KICAgICAgZm9yICh2YXIgcG9pbnQsIHQgPSB0MDsgZGlyZWN0aW9uID4gMCA/IHQgPiB0MSA6IHQgPCB0MTsgdCAtPSBzdGVwKSB7CiAgICAgICAgcG9pbnQgPSBzcGhlcmljYWwoW2Nvc1JhZGl1cywgLXNpblJhZGl1cyAqIGNvcyQxKHQpLCAtc2luUmFkaXVzICogc2luJDEodCldKTsKICAgICAgICBzdHJlYW0ucG9pbnQocG9pbnRbMF0sIHBvaW50WzFdKTsKICAgICAgfQogICAgfQoKICAgIC8vIFJldHVybnMgdGhlIHNpZ25lZCBhbmdsZSBvZiBhIGNhcnRlc2lhbiBwb2ludCByZWxhdGl2ZSB0byBbY29zUmFkaXVzLCAwLCAwXS4KICAgIGZ1bmN0aW9uIGNpcmNsZVJhZGl1cyhjb3NSYWRpdXMsIHBvaW50KSB7CiAgICAgIHBvaW50ID0gY2FydGVzaWFuKHBvaW50KSwgcG9pbnRbMF0gLT0gY29zUmFkaXVzOwogICAgICBjYXJ0ZXNpYW5Ob3JtYWxpemVJblBsYWNlKHBvaW50KTsKICAgICAgdmFyIHJhZGl1cyA9IGFjb3MoLXBvaW50WzFdKTsKICAgICAgcmV0dXJuICgoLXBvaW50WzJdIDwgMCA/IC1yYWRpdXMgOiByYWRpdXMpICsgdGF1JDMgLSBlcHNpbG9uJDIpICUgdGF1JDM7CiAgICB9CgogICAgZnVuY3Rpb24gY2lyY2xlKCkgewogICAgICB2YXIgY2VudGVyID0gY29uc3RhbnQkOChbMCwgMF0pLAogICAgICAgICAgcmFkaXVzID0gY29uc3RhbnQkOCg5MCksCiAgICAgICAgICBwcmVjaXNpb24gPSBjb25zdGFudCQ4KDYpLAogICAgICAgICAgcmluZywKICAgICAgICAgIHJvdGF0ZSwKICAgICAgICAgIHN0cmVhbSA9IHtwb2ludDogcG9pbnR9OwoKICAgICAgZnVuY3Rpb24gcG9pbnQoeCwgeSkgewogICAgICAgIHJpbmcucHVzaCh4ID0gcm90YXRlKHgsIHkpKTsKICAgICAgICB4WzBdICo9IGRlZ3JlZXMkMSwgeFsxXSAqPSBkZWdyZWVzJDE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGNpcmNsZSgpIHsKICAgICAgICB2YXIgYyA9IGNlbnRlci5hcHBseSh0aGlzLCBhcmd1bWVudHMpLAogICAgICAgICAgICByID0gcmFkaXVzLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgKiByYWRpYW5zLAogICAgICAgICAgICBwID0gcHJlY2lzaW9uLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgKiByYWRpYW5zOwogICAgICAgIHJpbmcgPSBbXTsKICAgICAgICByb3RhdGUgPSByb3RhdGVSYWRpYW5zKC1jWzBdICogcmFkaWFucywgLWNbMV0gKiByYWRpYW5zLCAwKS5pbnZlcnQ7CiAgICAgICAgY2lyY2xlU3RyZWFtKHN0cmVhbSwgciwgcCwgMSk7CiAgICAgICAgYyA9IHt0eXBlOiAiUG9seWdvbiIsIGNvb3JkaW5hdGVzOiBbcmluZ119OwogICAgICAgIHJpbmcgPSByb3RhdGUgPSBudWxsOwogICAgICAgIHJldHVybiBjOwogICAgICB9CgogICAgICBjaXJjbGUuY2VudGVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNlbnRlciA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JDgoWytfWzBdLCArX1sxXV0pLCBjaXJjbGUpIDogY2VudGVyOwogICAgICB9OwoKICAgICAgY2lyY2xlLnJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCQ4KCtfKSwgY2lyY2xlKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIGNpcmNsZS5wcmVjaXNpb24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocHJlY2lzaW9uID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkOCgrXyksIGNpcmNsZSkgOiBwcmVjaXNpb247CiAgICAgIH07CgogICAgICByZXR1cm4gY2lyY2xlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsaXBCdWZmZXIoKSB7CiAgICAgIHZhciBsaW5lcyA9IFtdLAogICAgICAgICAgbGluZTsKICAgICAgcmV0dXJuIHsKICAgICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSwgbSkgewogICAgICAgICAgbGluZS5wdXNoKFt4LCB5LCBtXSk7CiAgICAgICAgfSwKICAgICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgbGluZXMucHVzaChsaW5lID0gW10pOwogICAgICAgIH0sCiAgICAgICAgbGluZUVuZDogbm9vcCQyLAogICAgICAgIHJlam9pbjogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAobGluZXMubGVuZ3RoID4gMSkgbGluZXMucHVzaChsaW5lcy5wb3AoKS5jb25jYXQobGluZXMuc2hpZnQoKSkpOwogICAgICAgIH0sCiAgICAgICAgcmVzdWx0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBsaW5lczsKICAgICAgICAgIGxpbmVzID0gW107CiAgICAgICAgICBsaW5lID0gbnVsbDsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50RXF1YWwoYSwgYikgewogICAgICByZXR1cm4gYWJzKGFbMF0gLSBiWzBdKSA8IGVwc2lsb24kMiAmJiBhYnMoYVsxXSAtIGJbMV0pIDwgZXBzaWxvbiQyOwogICAgfQoKICAgIGZ1bmN0aW9uIEludGVyc2VjdGlvbihwb2ludCwgcG9pbnRzLCBvdGhlciwgZW50cnkpIHsKICAgICAgdGhpcy54ID0gcG9pbnQ7CiAgICAgIHRoaXMueiA9IHBvaW50czsKICAgICAgdGhpcy5vID0gb3RoZXI7IC8vIGFub3RoZXIgaW50ZXJzZWN0aW9uCiAgICAgIHRoaXMuZSA9IGVudHJ5OyAvLyBpcyBhbiBlbnRyeT8KICAgICAgdGhpcy52ID0gZmFsc2U7IC8vIHZpc2l0ZWQKICAgICAgdGhpcy5uID0gdGhpcy5wID0gbnVsbDsgLy8gbmV4dCAmIHByZXZpb3VzCiAgICB9CgogICAgLy8gQSBnZW5lcmFsaXplZCBwb2x5Z29uIGNsaXBwaW5nIGFsZ29yaXRobTogZ2l2ZW4gYSBwb2x5Z29uIHRoYXQgaGFzIGJlZW4gY3V0CiAgICAvLyBpbnRvIGl0cyB2aXNpYmxlIGxpbmUgc2VnbWVudHMsIGFuZCByZWpvaW5zIHRoZSBzZWdtZW50cyBieSBpbnRlcnBvbGF0aW5nCiAgICAvLyBhbG9uZyB0aGUgY2xpcCBlZGdlLgogICAgZnVuY3Rpb24gY2xpcFJlam9pbihzZWdtZW50cywgY29tcGFyZUludGVyc2VjdGlvbiwgc3RhcnRJbnNpZGUsIGludGVycG9sYXRlLCBzdHJlYW0pIHsKICAgICAgdmFyIHN1YmplY3QgPSBbXSwKICAgICAgICAgIGNsaXAgPSBbXSwKICAgICAgICAgIGksCiAgICAgICAgICBuOwoKICAgICAgc2VnbWVudHMuZm9yRWFjaChmdW5jdGlvbihzZWdtZW50KSB7CiAgICAgICAgaWYgKChuID0gc2VnbWVudC5sZW5ndGggLSAxKSA8PSAwKSByZXR1cm47CiAgICAgICAgdmFyIG4sIHAwID0gc2VnbWVudFswXSwgcDEgPSBzZWdtZW50W25dLCB4OwoKICAgICAgICBpZiAocG9pbnRFcXVhbChwMCwgcDEpKSB7CiAgICAgICAgICBpZiAoIXAwWzJdICYmICFwMVsyXSkgewogICAgICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHN0cmVhbS5wb2ludCgocDAgPSBzZWdtZW50W2ldKVswXSwgcDBbMV0pOwogICAgICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICAvLyBoYW5kbGUgZGVnZW5lcmF0ZSBjYXNlcyBieSBtb3ZpbmcgdGhlIHBvaW50CiAgICAgICAgICBwMVswXSArPSAyICogZXBzaWxvbiQyOwogICAgICAgIH0KCiAgICAgICAgc3ViamVjdC5wdXNoKHggPSBuZXcgSW50ZXJzZWN0aW9uKHAwLCBzZWdtZW50LCBudWxsLCB0cnVlKSk7CiAgICAgICAgY2xpcC5wdXNoKHgubyA9IG5ldyBJbnRlcnNlY3Rpb24ocDAsIG51bGwsIHgsIGZhbHNlKSk7CiAgICAgICAgc3ViamVjdC5wdXNoKHggPSBuZXcgSW50ZXJzZWN0aW9uKHAxLCBzZWdtZW50LCBudWxsLCBmYWxzZSkpOwogICAgICAgIGNsaXAucHVzaCh4Lm8gPSBuZXcgSW50ZXJzZWN0aW9uKHAxLCBudWxsLCB4LCB0cnVlKSk7CiAgICAgIH0pOwoKICAgICAgaWYgKCFzdWJqZWN0Lmxlbmd0aCkgcmV0dXJuOwoKICAgICAgY2xpcC5zb3J0KGNvbXBhcmVJbnRlcnNlY3Rpb24pOwogICAgICBsaW5rJDEoc3ViamVjdCk7CiAgICAgIGxpbmskMShjbGlwKTsKCiAgICAgIGZvciAoaSA9IDAsIG4gPSBjbGlwLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgIGNsaXBbaV0uZSA9IHN0YXJ0SW5zaWRlID0gIXN0YXJ0SW5zaWRlOwogICAgICB9CgogICAgICB2YXIgc3RhcnQgPSBzdWJqZWN0WzBdLAogICAgICAgICAgcG9pbnRzLAogICAgICAgICAgcG9pbnQ7CgogICAgICB3aGlsZSAoMSkgewogICAgICAgIC8vIEZpbmQgZmlyc3QgdW52aXNpdGVkIGludGVyc2VjdGlvbi4KICAgICAgICB2YXIgY3VycmVudCA9IHN0YXJ0LAogICAgICAgICAgICBpc1N1YmplY3QgPSB0cnVlOwogICAgICAgIHdoaWxlIChjdXJyZW50LnYpIGlmICgoY3VycmVudCA9IGN1cnJlbnQubikgPT09IHN0YXJ0KSByZXR1cm47CiAgICAgICAgcG9pbnRzID0gY3VycmVudC56OwogICAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgICBkbyB7CiAgICAgICAgICBjdXJyZW50LnYgPSBjdXJyZW50Lm8udiA9IHRydWU7CiAgICAgICAgICBpZiAoY3VycmVudC5lKSB7CiAgICAgICAgICAgIGlmIChpc1N1YmplY3QpIHsKICAgICAgICAgICAgICBmb3IgKGkgPSAwLCBuID0gcG9pbnRzLmxlbmd0aDsgaSA8IG47ICsraSkgc3RyZWFtLnBvaW50KChwb2ludCA9IHBvaW50c1tpXSlbMF0sIHBvaW50WzFdKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpbnRlcnBvbGF0ZShjdXJyZW50LngsIGN1cnJlbnQubi54LCAxLCBzdHJlYW0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGN1cnJlbnQgPSBjdXJyZW50Lm47CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoaXNTdWJqZWN0KSB7CiAgICAgICAgICAgICAgcG9pbnRzID0gY3VycmVudC5wLno7CiAgICAgICAgICAgICAgZm9yIChpID0gcG9pbnRzLmxlbmd0aCAtIDE7IGkgPj0gMDsgLS1pKSBzdHJlYW0ucG9pbnQoKHBvaW50ID0gcG9pbnRzW2ldKVswXSwgcG9pbnRbMV0pOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGludGVycG9sYXRlKGN1cnJlbnQueCwgY3VycmVudC5wLngsIC0xLCBzdHJlYW0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGN1cnJlbnQgPSBjdXJyZW50LnA7CiAgICAgICAgICB9CiAgICAgICAgICBjdXJyZW50ID0gY3VycmVudC5vOwogICAgICAgICAgcG9pbnRzID0gY3VycmVudC56OwogICAgICAgICAgaXNTdWJqZWN0ID0gIWlzU3ViamVjdDsKICAgICAgICB9IHdoaWxlICghY3VycmVudC52KTsKICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gbGluayQxKGFycmF5KSB7CiAgICAgIGlmICghKG4gPSBhcnJheS5sZW5ndGgpKSByZXR1cm47CiAgICAgIHZhciBuLAogICAgICAgICAgaSA9IDAsCiAgICAgICAgICBhID0gYXJyYXlbMF0sCiAgICAgICAgICBiOwogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIGEubiA9IGIgPSBhcnJheVtpXTsKICAgICAgICBiLnAgPSBhOwogICAgICAgIGEgPSBiOwogICAgICB9CiAgICAgIGEubiA9IGIgPSBhcnJheVswXTsKICAgICAgYi5wID0gYTsKICAgIH0KCiAgICB2YXIgc3VtJDEgPSBhZGRlcigpOwoKICAgIGZ1bmN0aW9uIGxvbmdpdHVkZShwb2ludCkgewogICAgICBpZiAoYWJzKHBvaW50WzBdKSA8PSBwaSQzKQogICAgICAgIHJldHVybiBwb2ludFswXTsKICAgICAgZWxzZQogICAgICAgIHJldHVybiBzaWduKHBvaW50WzBdKSAqICgoYWJzKHBvaW50WzBdKSArIHBpJDMpICUgdGF1JDMgLSBwaSQzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb2x5Z29uQ29udGFpbnMocG9seWdvbiwgcG9pbnQpIHsKICAgICAgdmFyIGxhbWJkYSA9IGxvbmdpdHVkZShwb2ludCksCiAgICAgICAgICBwaGkgPSBwb2ludFsxXSwKICAgICAgICAgIHNpblBoaSA9IHNpbiQxKHBoaSksCiAgICAgICAgICBub3JtYWwgPSBbc2luJDEobGFtYmRhKSwgLWNvcyQxKGxhbWJkYSksIDBdLAogICAgICAgICAgYW5nbGUgPSAwLAogICAgICAgICAgd2luZGluZyA9IDA7CgogICAgICBzdW0kMS5yZXNldCgpOwoKICAgICAgaWYgKHNpblBoaSA9PT0gMSkgcGhpID0gaGFsZlBpJDIgKyBlcHNpbG9uJDI7CiAgICAgIGVsc2UgaWYgKHNpblBoaSA9PT0gLTEpIHBoaSA9IC1oYWxmUGkkMiAtIGVwc2lsb24kMjsKCiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gcG9seWdvbi5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoIShtID0gKHJpbmcgPSBwb2x5Z29uW2ldKS5sZW5ndGgpKSBjb250aW51ZTsKICAgICAgICB2YXIgcmluZywKICAgICAgICAgICAgbSwKICAgICAgICAgICAgcG9pbnQwID0gcmluZ1ttIC0gMV0sCiAgICAgICAgICAgIGxhbWJkYTAgPSBsb25naXR1ZGUocG9pbnQwKSwKICAgICAgICAgICAgcGhpMCA9IHBvaW50MFsxXSAvIDIgKyBxdWFydGVyUGksCiAgICAgICAgICAgIHNpblBoaTAgPSBzaW4kMShwaGkwKSwKICAgICAgICAgICAgY29zUGhpMCA9IGNvcyQxKHBoaTApOwoKICAgICAgICBmb3IgKHZhciBqID0gMDsgaiA8IG07ICsraiwgbGFtYmRhMCA9IGxhbWJkYTEsIHNpblBoaTAgPSBzaW5QaGkxLCBjb3NQaGkwID0gY29zUGhpMSwgcG9pbnQwID0gcG9pbnQxKSB7CiAgICAgICAgICB2YXIgcG9pbnQxID0gcmluZ1tqXSwKICAgICAgICAgICAgICBsYW1iZGExID0gbG9uZ2l0dWRlKHBvaW50MSksCiAgICAgICAgICAgICAgcGhpMSA9IHBvaW50MVsxXSAvIDIgKyBxdWFydGVyUGksCiAgICAgICAgICAgICAgc2luUGhpMSA9IHNpbiQxKHBoaTEpLAogICAgICAgICAgICAgIGNvc1BoaTEgPSBjb3MkMShwaGkxKSwKICAgICAgICAgICAgICBkZWx0YSA9IGxhbWJkYTEgLSBsYW1iZGEwLAogICAgICAgICAgICAgIHNpZ24gPSBkZWx0YSA+PSAwID8gMSA6IC0xLAogICAgICAgICAgICAgIGFic0RlbHRhID0gc2lnbiAqIGRlbHRhLAogICAgICAgICAgICAgIGFudGltZXJpZGlhbiA9IGFic0RlbHRhID4gcGkkMywKICAgICAgICAgICAgICBrID0gc2luUGhpMCAqIHNpblBoaTE7CgogICAgICAgICAgc3VtJDEuYWRkKGF0YW4yKGsgKiBzaWduICogc2luJDEoYWJzRGVsdGEpLCBjb3NQaGkwICogY29zUGhpMSArIGsgKiBjb3MkMShhYnNEZWx0YSkpKTsKICAgICAgICAgIGFuZ2xlICs9IGFudGltZXJpZGlhbiA/IGRlbHRhICsgc2lnbiAqIHRhdSQzIDogZGVsdGE7CgogICAgICAgICAgLy8gQXJlIHRoZSBsb25naXR1ZGVzIGVpdGhlciBzaWRlIG9mIHRoZSBwb2ludOKAmXMgbWVyaWRpYW4gKGxhbWJkYSksCiAgICAgICAgICAvLyBhbmQgYXJlIHRoZSBsYXRpdHVkZXMgc21hbGxlciB0aGFuIHRoZSBwYXJhbGxlbCAocGhpKT8KICAgICAgICAgIGlmIChhbnRpbWVyaWRpYW4gXiBsYW1iZGEwID49IGxhbWJkYSBeIGxhbWJkYTEgPj0gbGFtYmRhKSB7CiAgICAgICAgICAgIHZhciBhcmMgPSBjYXJ0ZXNpYW5Dcm9zcyhjYXJ0ZXNpYW4ocG9pbnQwKSwgY2FydGVzaWFuKHBvaW50MSkpOwogICAgICAgICAgICBjYXJ0ZXNpYW5Ob3JtYWxpemVJblBsYWNlKGFyYyk7CiAgICAgICAgICAgIHZhciBpbnRlcnNlY3Rpb24gPSBjYXJ0ZXNpYW5Dcm9zcyhub3JtYWwsIGFyYyk7CiAgICAgICAgICAgIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UoaW50ZXJzZWN0aW9uKTsKICAgICAgICAgICAgdmFyIHBoaUFyYyA9IChhbnRpbWVyaWRpYW4gXiBkZWx0YSA+PSAwID8gLTEgOiAxKSAqIGFzaW4oaW50ZXJzZWN0aW9uWzJdKTsKICAgICAgICAgICAgaWYgKHBoaSA+IHBoaUFyYyB8fCBwaGkgPT09IHBoaUFyYyAmJiAoYXJjWzBdIHx8IGFyY1sxXSkpIHsKICAgICAgICAgICAgICB3aW5kaW5nICs9IGFudGltZXJpZGlhbiBeIGRlbHRhID49IDAgPyAxIDogLTE7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIEZpcnN0LCBkZXRlcm1pbmUgd2hldGhlciB0aGUgU291dGggcG9sZSBpcyBpbnNpZGUgb3Igb3V0c2lkZToKICAgICAgLy8KICAgICAgLy8gSXQgaXMgaW5zaWRlIGlmOgogICAgICAvLyAqIHRoZSBwb2x5Z29uIHdpbmRzIGFyb3VuZCBpdCBpbiBhIGNsb2Nrd2lzZSBkaXJlY3Rpb24uCiAgICAgIC8vICogdGhlIHBvbHlnb24gZG9lcyBub3QgKGN1bXVsYXRpdmVseSkgd2luZCBhcm91bmQgaXQsIGJ1dCBoYXMgYSBuZWdhdGl2ZQogICAgICAvLyAgIChjb3VudGVyLWNsb2Nrd2lzZSkgYXJlYS4KICAgICAgLy8KICAgICAgLy8gU2Vjb25kLCBjb3VudCB0aGUgKHNpZ25lZCkgbnVtYmVyIG9mIHRpbWVzIGEgc2VnbWVudCBjcm9zc2VzIGEgbGFtYmRhCiAgICAgIC8vIGZyb20gdGhlIHBvaW50IHRvIHRoZSBTb3V0aCBwb2xlLiAgSWYgaXQgaXMgemVybywgdGhlbiB0aGUgcG9pbnQgaXMgdGhlCiAgICAgIC8vIHNhbWUgc2lkZSBhcyB0aGUgU291dGggcG9sZS4KCiAgICAgIHJldHVybiAoYW5nbGUgPCAtZXBzaWxvbiQyIHx8IGFuZ2xlIDwgZXBzaWxvbiQyICYmIHN1bSQxIDwgLWVwc2lsb24kMikgXiAod2luZGluZyAmIDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsaXAocG9pbnRWaXNpYmxlLCBjbGlwTGluZSwgaW50ZXJwb2xhdGUsIHN0YXJ0KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihzaW5rKSB7CiAgICAgICAgdmFyIGxpbmUgPSBjbGlwTGluZShzaW5rKSwKICAgICAgICAgICAgcmluZ0J1ZmZlciA9IGNsaXBCdWZmZXIoKSwKICAgICAgICAgICAgcmluZ1NpbmsgPSBjbGlwTGluZShyaW5nQnVmZmVyKSwKICAgICAgICAgICAgcG9seWdvblN0YXJ0ZWQgPSBmYWxzZSwKICAgICAgICAgICAgcG9seWdvbiwKICAgICAgICAgICAgc2VnbWVudHMsCiAgICAgICAgICAgIHJpbmc7CgogICAgICAgIHZhciBjbGlwID0gewogICAgICAgICAgcG9pbnQ6IHBvaW50LAogICAgICAgICAgbGluZVN0YXJ0OiBsaW5lU3RhcnQsCiAgICAgICAgICBsaW5lRW5kOiBsaW5lRW5kLAogICAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50UmluZzsKICAgICAgICAgICAgY2xpcC5saW5lU3RhcnQgPSByaW5nU3RhcnQ7CiAgICAgICAgICAgIGNsaXAubGluZUVuZCA9IHJpbmdFbmQ7CiAgICAgICAgICAgIHNlZ21lbnRzID0gW107CiAgICAgICAgICAgIHBvbHlnb24gPSBbXTsKICAgICAgICAgIH0sCiAgICAgICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50OwogICAgICAgICAgICBjbGlwLmxpbmVTdGFydCA9IGxpbmVTdGFydDsKICAgICAgICAgICAgY2xpcC5saW5lRW5kID0gbGluZUVuZDsKICAgICAgICAgICAgc2VnbWVudHMgPSBtZXJnZShzZWdtZW50cyk7CiAgICAgICAgICAgIHZhciBzdGFydEluc2lkZSA9IHBvbHlnb25Db250YWlucyhwb2x5Z29uLCBzdGFydCk7CiAgICAgICAgICAgIGlmIChzZWdtZW50cy5sZW5ndGgpIHsKICAgICAgICAgICAgICBpZiAoIXBvbHlnb25TdGFydGVkKSBzaW5rLnBvbHlnb25TdGFydCgpLCBwb2x5Z29uU3RhcnRlZCA9IHRydWU7CiAgICAgICAgICAgICAgY2xpcFJlam9pbihzZWdtZW50cywgY29tcGFyZUludGVyc2VjdGlvbiwgc3RhcnRJbnNpZGUsIGludGVycG9sYXRlLCBzaW5rKTsKICAgICAgICAgICAgfSBlbHNlIGlmIChzdGFydEluc2lkZSkgewogICAgICAgICAgICAgIGlmICghcG9seWdvblN0YXJ0ZWQpIHNpbmsucG9seWdvblN0YXJ0KCksIHBvbHlnb25TdGFydGVkID0gdHJ1ZTsKICAgICAgICAgICAgICBzaW5rLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgIGludGVycG9sYXRlKG51bGwsIG51bGwsIDEsIHNpbmspOwogICAgICAgICAgICAgIHNpbmsubGluZUVuZCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChwb2x5Z29uU3RhcnRlZCkgc2luay5wb2x5Z29uRW5kKCksIHBvbHlnb25TdGFydGVkID0gZmFsc2U7CiAgICAgICAgICAgIHNlZ21lbnRzID0gcG9seWdvbiA9IG51bGw7CiAgICAgICAgICB9LAogICAgICAgICAgc3BoZXJlOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgc2luay5wb2x5Z29uU3RhcnQoKTsKICAgICAgICAgICAgc2luay5saW5lU3RhcnQoKTsKICAgICAgICAgICAgaW50ZXJwb2xhdGUobnVsbCwgbnVsbCwgMSwgc2luayk7CiAgICAgICAgICAgIHNpbmsubGluZUVuZCgpOwogICAgICAgICAgICBzaW5rLnBvbHlnb25FbmQoKTsKICAgICAgICAgIH0KICAgICAgICB9OwoKICAgICAgICBmdW5jdGlvbiBwb2ludChsYW1iZGEsIHBoaSkgewogICAgICAgICAgaWYgKHBvaW50VmlzaWJsZShsYW1iZGEsIHBoaSkpIHNpbmsucG9pbnQobGFtYmRhLCBwaGkpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcG9pbnRMaW5lKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICBsaW5lLnBvaW50KGxhbWJkYSwgcGhpKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGxpbmVTdGFydCgpIHsKICAgICAgICAgIGNsaXAucG9pbnQgPSBwb2ludExpbmU7CiAgICAgICAgICBsaW5lLmxpbmVTdGFydCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbGluZUVuZCgpIHsKICAgICAgICAgIGNsaXAucG9pbnQgPSBwb2ludDsKICAgICAgICAgIGxpbmUubGluZUVuZCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcG9pbnRSaW5nKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICByaW5nLnB1c2goW2xhbWJkYSwgcGhpXSk7CiAgICAgICAgICByaW5nU2luay5wb2ludChsYW1iZGEsIHBoaSk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiByaW5nU3RhcnQoKSB7CiAgICAgICAgICByaW5nU2luay5saW5lU3RhcnQoKTsKICAgICAgICAgIHJpbmcgPSBbXTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHJpbmdFbmQoKSB7CiAgICAgICAgICBwb2ludFJpbmcocmluZ1swXVswXSwgcmluZ1swXVsxXSk7CiAgICAgICAgICByaW5nU2luay5saW5lRW5kKCk7CgogICAgICAgICAgdmFyIGNsZWFuID0gcmluZ1NpbmsuY2xlYW4oKSwKICAgICAgICAgICAgICByaW5nU2VnbWVudHMgPSByaW5nQnVmZmVyLnJlc3VsdCgpLAogICAgICAgICAgICAgIGksIG4gPSByaW5nU2VnbWVudHMubGVuZ3RoLCBtLAogICAgICAgICAgICAgIHNlZ21lbnQsCiAgICAgICAgICAgICAgcG9pbnQ7CgogICAgICAgICAgcmluZy5wb3AoKTsKICAgICAgICAgIHBvbHlnb24ucHVzaChyaW5nKTsKICAgICAgICAgIHJpbmcgPSBudWxsOwoKICAgICAgICAgIGlmICghbikgcmV0dXJuOwoKICAgICAgICAgIC8vIE5vIGludGVyc2VjdGlvbnMuCiAgICAgICAgICBpZiAoY2xlYW4gJiAxKSB7CiAgICAgICAgICAgIHNlZ21lbnQgPSByaW5nU2VnbWVudHNbMF07CiAgICAgICAgICAgIGlmICgobSA9IHNlZ21lbnQubGVuZ3RoIC0gMSkgPiAwKSB7CiAgICAgICAgICAgICAgaWYgKCFwb2x5Z29uU3RhcnRlZCkgc2luay5wb2x5Z29uU3RhcnQoKSwgcG9seWdvblN0YXJ0ZWQgPSB0cnVlOwogICAgICAgICAgICAgIHNpbmsubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgZm9yIChpID0gMDsgaSA8IG07ICsraSkgc2luay5wb2ludCgocG9pbnQgPSBzZWdtZW50W2ldKVswXSwgcG9pbnRbMV0pOwogICAgICAgICAgICAgIHNpbmsubGluZUVuZCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBSZWpvaW4gY29ubmVjdGVkIHNlZ21lbnRzLgogICAgICAgICAgLy8gVE9ETyByZXVzZSByaW5nQnVmZmVyLnJlam9pbigpPwogICAgICAgICAgaWYgKG4gPiAxICYmIGNsZWFuICYgMikgcmluZ1NlZ21lbnRzLnB1c2gocmluZ1NlZ21lbnRzLnBvcCgpLmNvbmNhdChyaW5nU2VnbWVudHMuc2hpZnQoKSkpOwoKICAgICAgICAgIHNlZ21lbnRzLnB1c2gocmluZ1NlZ21lbnRzLmZpbHRlcih2YWxpZFNlZ21lbnQpKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBjbGlwOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHZhbGlkU2VnbWVudChzZWdtZW50KSB7CiAgICAgIHJldHVybiBzZWdtZW50Lmxlbmd0aCA+IDE7CiAgICB9CgogICAgLy8gSW50ZXJzZWN0aW9ucyBhcmUgc29ydGVkIGFsb25nIHRoZSBjbGlwIGVkZ2UuIEZvciBib3RoIGFudGltZXJpZGlhbiBjdXR0aW5nCiAgICAvLyBhbmQgY2lyY2xlIGNsaXBwaW5nLCB0aGUgc2FtZSBjb21wYXJpc29uIGlzIHVzZWQuCiAgICBmdW5jdGlvbiBjb21wYXJlSW50ZXJzZWN0aW9uKGEsIGIpIHsKICAgICAgcmV0dXJuICgoYSA9IGEueClbMF0gPCAwID8gYVsxXSAtIGhhbGZQaSQyIC0gZXBzaWxvbiQyIDogaGFsZlBpJDIgLSBhWzFdKQogICAgICAgICAgIC0gKChiID0gYi54KVswXSA8IDAgPyBiWzFdIC0gaGFsZlBpJDIgLSBlcHNpbG9uJDIgOiBoYWxmUGkkMiAtIGJbMV0pOwogICAgfQoKICAgIHZhciBjbGlwQW50aW1lcmlkaWFuID0gY2xpcCgKICAgICAgZnVuY3Rpb24oKSB7IHJldHVybiB0cnVlOyB9LAogICAgICBjbGlwQW50aW1lcmlkaWFuTGluZSwKICAgICAgY2xpcEFudGltZXJpZGlhbkludGVycG9sYXRlLAogICAgICBbLXBpJDMsIC1oYWxmUGkkMl0KICAgICk7CgogICAgLy8gVGFrZXMgYSBsaW5lIGFuZCBjdXRzIGludG8gdmlzaWJsZSBzZWdtZW50cy4gUmV0dXJuIHZhbHVlczogMCAtIHRoZXJlIHdlcmUKICAgIC8vIGludGVyc2VjdGlvbnMgb3IgdGhlIGxpbmUgd2FzIGVtcHR5OyAxIC0gbm8gaW50ZXJzZWN0aW9uczsgMiAtIHRoZXJlIHdlcmUKICAgIC8vIGludGVyc2VjdGlvbnMsIGFuZCB0aGUgZmlyc3QgYW5kIGxhc3Qgc2VnbWVudHMgc2hvdWxkIGJlIHJlam9pbmVkLgogICAgZnVuY3Rpb24gY2xpcEFudGltZXJpZGlhbkxpbmUoc3RyZWFtKSB7CiAgICAgIHZhciBsYW1iZGEwID0gTmFOLAogICAgICAgICAgcGhpMCA9IE5hTiwKICAgICAgICAgIHNpZ24wID0gTmFOLAogICAgICAgICAgY2xlYW47IC8vIG5vIGludGVyc2VjdGlvbnMKCiAgICAgIHJldHVybiB7CiAgICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgICAgIGNsZWFuID0gMTsKICAgICAgICB9LAogICAgICAgIHBvaW50OiBmdW5jdGlvbihsYW1iZGExLCBwaGkxKSB7CiAgICAgICAgICB2YXIgc2lnbjEgPSBsYW1iZGExID4gMCA/IHBpJDMgOiAtcGkkMywKICAgICAgICAgICAgICBkZWx0YSA9IGFicyhsYW1iZGExIC0gbGFtYmRhMCk7CiAgICAgICAgICBpZiAoYWJzKGRlbHRhIC0gcGkkMykgPCBlcHNpbG9uJDIpIHsgLy8gbGluZSBjcm9zc2VzIGEgcG9sZQogICAgICAgICAgICBzdHJlYW0ucG9pbnQobGFtYmRhMCwgcGhpMCA9IChwaGkwICsgcGhpMSkgLyAyID4gMCA/IGhhbGZQaSQyIDogLWhhbGZQaSQyKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHNpZ24wLCBwaGkwKTsKICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICBzdHJlYW0ucG9pbnQoc2lnbjEsIHBoaTApOwogICAgICAgICAgICBzdHJlYW0ucG9pbnQobGFtYmRhMSwgcGhpMCk7CiAgICAgICAgICAgIGNsZWFuID0gMDsKICAgICAgICAgIH0gZWxzZSBpZiAoc2lnbjAgIT09IHNpZ24xICYmIGRlbHRhID49IHBpJDMpIHsgLy8gbGluZSBjcm9zc2VzIGFudGltZXJpZGlhbgogICAgICAgICAgICBpZiAoYWJzKGxhbWJkYTAgLSBzaWduMCkgPCBlcHNpbG9uJDIpIGxhbWJkYTAgLT0gc2lnbjAgKiBlcHNpbG9uJDI7IC8vIGhhbmRsZSBkZWdlbmVyYWNpZXMKICAgICAgICAgICAgaWYgKGFicyhsYW1iZGExIC0gc2lnbjEpIDwgZXBzaWxvbiQyKSBsYW1iZGExIC09IHNpZ24xICogZXBzaWxvbiQyOwogICAgICAgICAgICBwaGkwID0gY2xpcEFudGltZXJpZGlhbkludGVyc2VjdChsYW1iZGEwLCBwaGkwLCBsYW1iZGExLCBwaGkxKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHNpZ24wLCBwaGkwKTsKICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICBzdHJlYW0ucG9pbnQoc2lnbjEsIHBoaTApOwogICAgICAgICAgICBjbGVhbiA9IDA7CiAgICAgICAgICB9CiAgICAgICAgICBzdHJlYW0ucG9pbnQobGFtYmRhMCA9IGxhbWJkYTEsIHBoaTAgPSBwaGkxKTsKICAgICAgICAgIHNpZ24wID0gc2lnbjE7CiAgICAgICAgfSwKICAgICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICBsYW1iZGEwID0gcGhpMCA9IE5hTjsKICAgICAgICB9LAogICAgICAgIGNsZWFuOiBmdW5jdGlvbigpIHsKICAgICAgICAgIHJldHVybiAyIC0gY2xlYW47IC8vIGlmIGludGVyc2VjdGlvbnMsIHJlam9pbiBmaXJzdCBhbmQgbGFzdCBzZWdtZW50cwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwQW50aW1lcmlkaWFuSW50ZXJzZWN0KGxhbWJkYTAsIHBoaTAsIGxhbWJkYTEsIHBoaTEpIHsKICAgICAgdmFyIGNvc1BoaTAsCiAgICAgICAgICBjb3NQaGkxLAogICAgICAgICAgc2luTGFtYmRhMExhbWJkYTEgPSBzaW4kMShsYW1iZGEwIC0gbGFtYmRhMSk7CiAgICAgIHJldHVybiBhYnMoc2luTGFtYmRhMExhbWJkYTEpID4gZXBzaWxvbiQyCiAgICAgICAgICA/IGF0YW4oKHNpbiQxKHBoaTApICogKGNvc1BoaTEgPSBjb3MkMShwaGkxKSkgKiBzaW4kMShsYW1iZGExKQogICAgICAgICAgICAgIC0gc2luJDEocGhpMSkgKiAoY29zUGhpMCA9IGNvcyQxKHBoaTApKSAqIHNpbiQxKGxhbWJkYTApKQogICAgICAgICAgICAgIC8gKGNvc1BoaTAgKiBjb3NQaGkxICogc2luTGFtYmRhMExhbWJkYTEpKQogICAgICAgICAgOiAocGhpMCArIHBoaTEpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwQW50aW1lcmlkaWFuSW50ZXJwb2xhdGUoZnJvbSwgdG8sIGRpcmVjdGlvbiwgc3RyZWFtKSB7CiAgICAgIHZhciBwaGk7CiAgICAgIGlmIChmcm9tID09IG51bGwpIHsKICAgICAgICBwaGkgPSBkaXJlY3Rpb24gKiBoYWxmUGkkMjsKICAgICAgICBzdHJlYW0ucG9pbnQoLXBpJDMsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KDAsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KHBpJDMsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KHBpJDMsIDApOwogICAgICAgIHN0cmVhbS5wb2ludChwaSQzLCAtcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQoMCwgLXBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KC1waSQzLCAtcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQoLXBpJDMsIDApOwogICAgICAgIHN0cmVhbS5wb2ludCgtcGkkMywgcGhpKTsKICAgICAgfSBlbHNlIGlmIChhYnMoZnJvbVswXSAtIHRvWzBdKSA+IGVwc2lsb24kMikgewogICAgICAgIHZhciBsYW1iZGEgPSBmcm9tWzBdIDwgdG9bMF0gPyBwaSQzIDogLXBpJDM7CiAgICAgICAgcGhpID0gZGlyZWN0aW9uICogbGFtYmRhIC8gMjsKICAgICAgICBzdHJlYW0ucG9pbnQoLWxhbWJkYSwgcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQoMCwgcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQobGFtYmRhLCBwaGkpOwogICAgICB9IGVsc2UgewogICAgICAgIHN0cmVhbS5wb2ludCh0b1swXSwgdG9bMV0pOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcENpcmNsZShyYWRpdXMpIHsKICAgICAgdmFyIGNyID0gY29zJDEocmFkaXVzKSwKICAgICAgICAgIGRlbHRhID0gNiAqIHJhZGlhbnMsCiAgICAgICAgICBzbWFsbFJhZGl1cyA9IGNyID4gMCwKICAgICAgICAgIG5vdEhlbWlzcGhlcmUgPSBhYnMoY3IpID4gZXBzaWxvbiQyOyAvLyBUT0RPIG9wdGltaXNlIGZvciB0aGlzIGNvbW1vbiBjYXNlCgogICAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZShmcm9tLCB0bywgZGlyZWN0aW9uLCBzdHJlYW0pIHsKICAgICAgICBjaXJjbGVTdHJlYW0oc3RyZWFtLCByYWRpdXMsIGRlbHRhLCBkaXJlY3Rpb24sIGZyb20sIHRvKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gdmlzaWJsZShsYW1iZGEsIHBoaSkgewogICAgICAgIHJldHVybiBjb3MkMShsYW1iZGEpICogY29zJDEocGhpKSA+IGNyOwogICAgICB9CgogICAgICAvLyBUYWtlcyBhIGxpbmUgYW5kIGN1dHMgaW50byB2aXNpYmxlIHNlZ21lbnRzLiBSZXR1cm4gdmFsdWVzIHVzZWQgZm9yIHBvbHlnb24KICAgICAgLy8gY2xpcHBpbmc6IDAgLSB0aGVyZSB3ZXJlIGludGVyc2VjdGlvbnMgb3IgdGhlIGxpbmUgd2FzIGVtcHR5OyAxIC0gbm8KICAgICAgLy8gaW50ZXJzZWN0aW9ucyAyIC0gdGhlcmUgd2VyZSBpbnRlcnNlY3Rpb25zLCBhbmQgdGhlIGZpcnN0IGFuZCBsYXN0IHNlZ21lbnRzCiAgICAgIC8vIHNob3VsZCBiZSByZWpvaW5lZC4KICAgICAgZnVuY3Rpb24gY2xpcExpbmUoc3RyZWFtKSB7CiAgICAgICAgdmFyIHBvaW50MCwgLy8gcHJldmlvdXMgcG9pbnQKICAgICAgICAgICAgYzAsIC8vIGNvZGUgZm9yIHByZXZpb3VzIHBvaW50CiAgICAgICAgICAgIHYwLCAvLyB2aXNpYmlsaXR5IG9mIHByZXZpb3VzIHBvaW50CiAgICAgICAgICAgIHYwMCwgLy8gdmlzaWJpbGl0eSBvZiBmaXJzdCBwb2ludAogICAgICAgICAgICBjbGVhbjsgLy8gbm8gaW50ZXJzZWN0aW9ucwogICAgICAgIHJldHVybiB7CiAgICAgICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICB2MDAgPSB2MCA9IGZhbHNlOwogICAgICAgICAgICBjbGVhbiA9IDE7CiAgICAgICAgICB9LAogICAgICAgICAgcG9pbnQ6IGZ1bmN0aW9uKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICAgIHZhciBwb2ludDEgPSBbbGFtYmRhLCBwaGldLAogICAgICAgICAgICAgICAgcG9pbnQyLAogICAgICAgICAgICAgICAgdiA9IHZpc2libGUobGFtYmRhLCBwaGkpLAogICAgICAgICAgICAgICAgYyA9IHNtYWxsUmFkaXVzCiAgICAgICAgICAgICAgICAgID8gdiA/IDAgOiBjb2RlKGxhbWJkYSwgcGhpKQogICAgICAgICAgICAgICAgICA6IHYgPyBjb2RlKGxhbWJkYSArIChsYW1iZGEgPCAwID8gcGkkMyA6IC1waSQzKSwgcGhpKSA6IDA7CiAgICAgICAgICAgIGlmICghcG9pbnQwICYmICh2MDAgPSB2MCA9IHYpKSBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgIGlmICh2ICE9PSB2MCkgewogICAgICAgICAgICAgIHBvaW50MiA9IGludGVyc2VjdChwb2ludDAsIHBvaW50MSk7CiAgICAgICAgICAgICAgaWYgKCFwb2ludDIgfHwgcG9pbnRFcXVhbChwb2ludDAsIHBvaW50MikgfHwgcG9pbnRFcXVhbChwb2ludDEsIHBvaW50MikpCiAgICAgICAgICAgICAgICBwb2ludDFbMl0gPSAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh2ICE9PSB2MCkgewogICAgICAgICAgICAgIGNsZWFuID0gMDsKICAgICAgICAgICAgICBpZiAodikgewogICAgICAgICAgICAgICAgLy8gb3V0c2lkZSBnb2luZyBpbgogICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgICAgcG9pbnQyID0gaW50ZXJzZWN0KHBvaW50MSwgcG9pbnQwKTsKICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludChwb2ludDJbMF0sIHBvaW50MlsxXSk7CiAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIGluc2lkZSBnb2luZyBvdXQKICAgICAgICAgICAgICAgIHBvaW50MiA9IGludGVyc2VjdChwb2ludDAsIHBvaW50MSk7CiAgICAgICAgICAgICAgICBzdHJlYW0ucG9pbnQocG9pbnQyWzBdLCBwb2ludDJbMV0sIDIpOwogICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcG9pbnQwID0gcG9pbnQyOwogICAgICAgICAgICB9IGVsc2UgaWYgKG5vdEhlbWlzcGhlcmUgJiYgcG9pbnQwICYmIHNtYWxsUmFkaXVzIF4gdikgewogICAgICAgICAgICAgIHZhciB0OwogICAgICAgICAgICAgIC8vIElmIHRoZSBjb2RlcyBmb3IgdHdvIHBvaW50cyBhcmUgZGlmZmVyZW50LCBvciBhcmUgYm90aCB6ZXJvLAogICAgICAgICAgICAgIC8vIGFuZCB0aGVyZSB0aGlzIHNlZ21lbnQgaW50ZXJzZWN0cyB3aXRoIHRoZSBzbWFsbCBjaXJjbGUuCiAgICAgICAgICAgICAgaWYgKCEoYyAmIGMwKSAmJiAodCA9IGludGVyc2VjdChwb2ludDEsIHBvaW50MCwgdHJ1ZSkpKSB7CiAgICAgICAgICAgICAgICBjbGVhbiA9IDA7CiAgICAgICAgICAgICAgICBpZiAoc21hbGxSYWRpdXMpIHsKICAgICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgICAgICBzdHJlYW0ucG9pbnQodFswXVswXSwgdFswXVsxXSk7CiAgICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludCh0WzFdWzBdLCB0WzFdWzFdKTsKICAgICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludCh0WzFdWzBdLCB0WzFdWzFdKTsKICAgICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgICAgICBzdHJlYW0ucG9pbnQodFswXVswXSwgdFswXVsxXSwgMyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh2ICYmICghcG9pbnQwIHx8ICFwb2ludEVxdWFsKHBvaW50MCwgcG9pbnQxKSkpIHsKICAgICAgICAgICAgICBzdHJlYW0ucG9pbnQocG9pbnQxWzBdLCBwb2ludDFbMV0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHBvaW50MCA9IHBvaW50MSwgdjAgPSB2LCBjMCA9IGM7CiAgICAgICAgICB9LAogICAgICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIGlmICh2MCkgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgcG9pbnQwID0gbnVsbDsKICAgICAgICAgIH0sCiAgICAgICAgICAvLyBSZWpvaW4gZmlyc3QgYW5kIGxhc3Qgc2VnbWVudHMgaWYgdGhlcmUgd2VyZSBpbnRlcnNlY3Rpb25zIGFuZCB0aGUgZmlyc3QKICAgICAgICAgIC8vIGFuZCBsYXN0IHBvaW50cyB3ZXJlIHZpc2libGUuCiAgICAgICAgICBjbGVhbjogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiBjbGVhbiB8ICgodjAwICYmIHYwKSA8PCAxKTsKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICB9CgogICAgICAvLyBJbnRlcnNlY3RzIHRoZSBncmVhdCBjaXJjbGUgYmV0d2VlbiBhIGFuZCBiIHdpdGggdGhlIGNsaXAgY2lyY2xlLgogICAgICBmdW5jdGlvbiBpbnRlcnNlY3QoYSwgYiwgdHdvKSB7CiAgICAgICAgdmFyIHBhID0gY2FydGVzaWFuKGEpLAogICAgICAgICAgICBwYiA9IGNhcnRlc2lhbihiKTsKCiAgICAgICAgLy8gV2UgaGF2ZSB0d28gcGxhbmVzLCBuMS5wID0gZDEgYW5kIG4yLnAgPSBkMi4KICAgICAgICAvLyBGaW5kIGludGVyc2VjdGlvbiBsaW5lIHAodCkgPSBjMSBuMSArIGMyIG4yICsgdCAobjEg4qivIG4yKS4KICAgICAgICB2YXIgbjEgPSBbMSwgMCwgMF0sIC8vIG5vcm1hbAogICAgICAgICAgICBuMiA9IGNhcnRlc2lhbkNyb3NzKHBhLCBwYiksCiAgICAgICAgICAgIG4ybjIgPSBjYXJ0ZXNpYW5Eb3QobjIsIG4yKSwKICAgICAgICAgICAgbjFuMiA9IG4yWzBdLCAvLyBjYXJ0ZXNpYW5Eb3QobjEsIG4yKSwKICAgICAgICAgICAgZGV0ZXJtaW5hbnQgPSBuMm4yIC0gbjFuMiAqIG4xbjI7CgogICAgICAgIC8vIFR3byBwb2xhciBwb2ludHMuCiAgICAgICAgaWYgKCFkZXRlcm1pbmFudCkgcmV0dXJuICF0d28gJiYgYTsKCiAgICAgICAgdmFyIGMxID0gIGNyICogbjJuMiAvIGRldGVybWluYW50LAogICAgICAgICAgICBjMiA9IC1jciAqIG4xbjIgLyBkZXRlcm1pbmFudCwKICAgICAgICAgICAgbjF4bjIgPSBjYXJ0ZXNpYW5Dcm9zcyhuMSwgbjIpLAogICAgICAgICAgICBBID0gY2FydGVzaWFuU2NhbGUobjEsIGMxKSwKICAgICAgICAgICAgQiA9IGNhcnRlc2lhblNjYWxlKG4yLCBjMik7CiAgICAgICAgY2FydGVzaWFuQWRkSW5QbGFjZShBLCBCKTsKCiAgICAgICAgLy8gU29sdmUgfHAodCl8XjIgPSAxLgogICAgICAgIHZhciB1ID0gbjF4bjIsCiAgICAgICAgICAgIHcgPSBjYXJ0ZXNpYW5Eb3QoQSwgdSksCiAgICAgICAgICAgIHV1ID0gY2FydGVzaWFuRG90KHUsIHUpLAogICAgICAgICAgICB0MiA9IHcgKiB3IC0gdXUgKiAoY2FydGVzaWFuRG90KEEsIEEpIC0gMSk7CgogICAgICAgIGlmICh0MiA8IDApIHJldHVybjsKCiAgICAgICAgdmFyIHQgPSBzcXJ0KHQyKSwKICAgICAgICAgICAgcSA9IGNhcnRlc2lhblNjYWxlKHUsICgtdyAtIHQpIC8gdXUpOwogICAgICAgIGNhcnRlc2lhbkFkZEluUGxhY2UocSwgQSk7CiAgICAgICAgcSA9IHNwaGVyaWNhbChxKTsKCiAgICAgICAgaWYgKCF0d28pIHJldHVybiBxOwoKICAgICAgICAvLyBUd28gaW50ZXJzZWN0aW9uIHBvaW50cy4KICAgICAgICB2YXIgbGFtYmRhMCA9IGFbMF0sCiAgICAgICAgICAgIGxhbWJkYTEgPSBiWzBdLAogICAgICAgICAgICBwaGkwID0gYVsxXSwKICAgICAgICAgICAgcGhpMSA9IGJbMV0sCiAgICAgICAgICAgIHo7CgogICAgICAgIGlmIChsYW1iZGExIDwgbGFtYmRhMCkgeiA9IGxhbWJkYTAsIGxhbWJkYTAgPSBsYW1iZGExLCBsYW1iZGExID0gejsKCiAgICAgICAgdmFyIGRlbHRhID0gbGFtYmRhMSAtIGxhbWJkYTAsCiAgICAgICAgICAgIHBvbGFyID0gYWJzKGRlbHRhIC0gcGkkMykgPCBlcHNpbG9uJDIsCiAgICAgICAgICAgIG1lcmlkaWFuID0gcG9sYXIgfHwgZGVsdGEgPCBlcHNpbG9uJDI7CgogICAgICAgIGlmICghcG9sYXIgJiYgcGhpMSA8IHBoaTApIHogPSBwaGkwLCBwaGkwID0gcGhpMSwgcGhpMSA9IHo7CgogICAgICAgIC8vIENoZWNrIHRoYXQgdGhlIGZpcnN0IHBvaW50IGlzIGJldHdlZW4gYSBhbmQgYi4KICAgICAgICBpZiAobWVyaWRpYW4KICAgICAgICAgICAgPyBwb2xhcgogICAgICAgICAgICAgID8gcGhpMCArIHBoaTEgPiAwIF4gcVsxXSA8IChhYnMocVswXSAtIGxhbWJkYTApIDwgZXBzaWxvbiQyID8gcGhpMCA6IHBoaTEpCiAgICAgICAgICAgICAgOiBwaGkwIDw9IHFbMV0gJiYgcVsxXSA8PSBwaGkxCiAgICAgICAgICAgIDogZGVsdGEgPiBwaSQzIF4gKGxhbWJkYTAgPD0gcVswXSAmJiBxWzBdIDw9IGxhbWJkYTEpKSB7CiAgICAgICAgICB2YXIgcTEgPSBjYXJ0ZXNpYW5TY2FsZSh1LCAoLXcgKyB0KSAvIHV1KTsKICAgICAgICAgIGNhcnRlc2lhbkFkZEluUGxhY2UocTEsIEEpOwogICAgICAgICAgcmV0dXJuIFtxLCBzcGhlcmljYWwocTEpXTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIEdlbmVyYXRlcyBhIDQtYml0IHZlY3RvciByZXByZXNlbnRpbmcgdGhlIGxvY2F0aW9uIG9mIGEgcG9pbnQgcmVsYXRpdmUgdG8KICAgICAgLy8gdGhlIHNtYWxsIGNpcmNsZSdzIGJvdW5kaW5nIGJveC4KICAgICAgZnVuY3Rpb24gY29kZShsYW1iZGEsIHBoaSkgewogICAgICAgIHZhciByID0gc21hbGxSYWRpdXMgPyByYWRpdXMgOiBwaSQzIC0gcmFkaXVzLAogICAgICAgICAgICBjb2RlID0gMDsKICAgICAgICBpZiAobGFtYmRhIDwgLXIpIGNvZGUgfD0gMTsgLy8gbGVmdAogICAgICAgIGVsc2UgaWYgKGxhbWJkYSA+IHIpIGNvZGUgfD0gMjsgLy8gcmlnaHQKICAgICAgICBpZiAocGhpIDwgLXIpIGNvZGUgfD0gNDsgLy8gYmVsb3cKICAgICAgICBlbHNlIGlmIChwaGkgPiByKSBjb2RlIHw9IDg7IC8vIGFib3ZlCiAgICAgICAgcmV0dXJuIGNvZGU7CiAgICAgIH0KCiAgICAgIHJldHVybiBjbGlwKHZpc2libGUsIGNsaXBMaW5lLCBpbnRlcnBvbGF0ZSwgc21hbGxSYWRpdXMgPyBbMCwgLXJhZGl1c10gOiBbLXBpJDMsIHJhZGl1cyAtIHBpJDNdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwTGluZShhLCBiLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgYXggPSBhWzBdLAogICAgICAgICAgYXkgPSBhWzFdLAogICAgICAgICAgYnggPSBiWzBdLAogICAgICAgICAgYnkgPSBiWzFdLAogICAgICAgICAgdDAgPSAwLAogICAgICAgICAgdDEgPSAxLAogICAgICAgICAgZHggPSBieCAtIGF4LAogICAgICAgICAgZHkgPSBieSAtIGF5LAogICAgICAgICAgcjsKCiAgICAgIHIgPSB4MCAtIGF4OwogICAgICBpZiAoIWR4ICYmIHIgPiAwKSByZXR1cm47CiAgICAgIHIgLz0gZHg7CiAgICAgIGlmIChkeCA8IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9IGVsc2UgaWYgKGR4ID4gMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB4MSAtIGF4OwogICAgICBpZiAoIWR4ICYmIHIgPCAwKSByZXR1cm47CiAgICAgIHIgLz0gZHg7CiAgICAgIGlmIChkeCA8IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9IGVsc2UgaWYgKGR4ID4gMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB5MCAtIGF5OwogICAgICBpZiAoIWR5ICYmIHIgPiAwKSByZXR1cm47CiAgICAgIHIgLz0gZHk7CiAgICAgIGlmIChkeSA8IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9IGVsc2UgaWYgKGR5ID4gMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB5MSAtIGF5OwogICAgICBpZiAoIWR5ICYmIHIgPCAwKSByZXR1cm47CiAgICAgIHIgLz0gZHk7CiAgICAgIGlmIChkeSA8IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9IGVsc2UgaWYgKGR5ID4gMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0KCiAgICAgIGlmICh0MCA+IDApIGFbMF0gPSBheCArIHQwICogZHgsIGFbMV0gPSBheSArIHQwICogZHk7CiAgICAgIGlmICh0MSA8IDEpIGJbMF0gPSBheCArIHQxICogZHgsIGJbMV0gPSBheSArIHQxICogZHk7CiAgICAgIHJldHVybiB0cnVlOwogICAgfQoKICAgIHZhciBjbGlwTWF4ID0gMWU5LCBjbGlwTWluID0gLWNsaXBNYXg7CgogICAgLy8gVE9ETyBVc2UgZDMtcG9seWdvbuKAmXMgcG9seWdvbkNvbnRhaW5zIGhlcmUgZm9yIHRoZSByaW5nIGNoZWNrPwogICAgLy8gVE9ETyBFbGltaW5hdGUgZHVwbGljYXRlIGJ1ZmZlcmluZyBpbiBjbGlwQnVmZmVyIGFuZCBwb2x5Z29uLnB1c2g/CgogICAgZnVuY3Rpb24gY2xpcFJlY3RhbmdsZSh4MCwgeTAsIHgxLCB5MSkgewoKICAgICAgZnVuY3Rpb24gdmlzaWJsZSh4LCB5KSB7CiAgICAgICAgcmV0dXJuIHgwIDw9IHggJiYgeCA8PSB4MSAmJiB5MCA8PSB5ICYmIHkgPD0geTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGludGVycG9sYXRlKGZyb20sIHRvLCBkaXJlY3Rpb24sIHN0cmVhbSkgewogICAgICAgIHZhciBhID0gMCwgYTEgPSAwOwogICAgICAgIGlmIChmcm9tID09IG51bGwKICAgICAgICAgICAgfHwgKGEgPSBjb3JuZXIoZnJvbSwgZGlyZWN0aW9uKSkgIT09IChhMSA9IGNvcm5lcih0bywgZGlyZWN0aW9uKSkKICAgICAgICAgICAgfHwgY29tcGFyZVBvaW50KGZyb20sIHRvKSA8IDAgXiBkaXJlY3Rpb24gPiAwKSB7CiAgICAgICAgICBkbyBzdHJlYW0ucG9pbnQoYSA9PT0gMCB8fCBhID09PSAzID8geDAgOiB4MSwgYSA+IDEgPyB5MSA6IHkwKTsKICAgICAgICAgIHdoaWxlICgoYSA9IChhICsgZGlyZWN0aW9uICsgNCkgJSA0KSAhPT0gYTEpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBzdHJlYW0ucG9pbnQodG9bMF0sIHRvWzFdKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGNvcm5lcihwLCBkaXJlY3Rpb24pIHsKICAgICAgICByZXR1cm4gYWJzKHBbMF0gLSB4MCkgPCBlcHNpbG9uJDIgPyBkaXJlY3Rpb24gPiAwID8gMCA6IDMKICAgICAgICAgICAgOiBhYnMocFswXSAtIHgxKSA8IGVwc2lsb24kMiA/IGRpcmVjdGlvbiA+IDAgPyAyIDogMQogICAgICAgICAgICA6IGFicyhwWzFdIC0geTApIDwgZXBzaWxvbiQyID8gZGlyZWN0aW9uID4gMCA/IDEgOiAwCiAgICAgICAgICAgIDogZGlyZWN0aW9uID4gMCA/IDMgOiAyOyAvLyBhYnMocFsxXSAtIHkxKSA8IGVwc2lsb24KICAgICAgfQoKICAgICAgZnVuY3Rpb24gY29tcGFyZUludGVyc2VjdGlvbihhLCBiKSB7CiAgICAgICAgcmV0dXJuIGNvbXBhcmVQb2ludChhLngsIGIueCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGNvbXBhcmVQb2ludChhLCBiKSB7CiAgICAgICAgdmFyIGNhID0gY29ybmVyKGEsIDEpLAogICAgICAgICAgICBjYiA9IGNvcm5lcihiLCAxKTsKICAgICAgICByZXR1cm4gY2EgIT09IGNiID8gY2EgLSBjYgogICAgICAgICAgICA6IGNhID09PSAwID8gYlsxXSAtIGFbMV0KICAgICAgICAgICAgOiBjYSA9PT0gMSA/IGFbMF0gLSBiWzBdCiAgICAgICAgICAgIDogY2EgPT09IDIgPyBhWzFdIC0gYlsxXQogICAgICAgICAgICA6IGJbMF0gLSBhWzBdOwogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24oc3RyZWFtKSB7CiAgICAgICAgdmFyIGFjdGl2ZVN0cmVhbSA9IHN0cmVhbSwKICAgICAgICAgICAgYnVmZmVyU3RyZWFtID0gY2xpcEJ1ZmZlcigpLAogICAgICAgICAgICBzZWdtZW50cywKICAgICAgICAgICAgcG9seWdvbiwKICAgICAgICAgICAgcmluZywKICAgICAgICAgICAgeF9fLCB5X18sIHZfXywgLy8gZmlyc3QgcG9pbnQKICAgICAgICAgICAgeF8sIHlfLCB2XywgLy8gcHJldmlvdXMgcG9pbnQKICAgICAgICAgICAgZmlyc3QsCiAgICAgICAgICAgIGNsZWFuOwoKICAgICAgICB2YXIgY2xpcFN0cmVhbSA9IHsKICAgICAgICAgIHBvaW50OiBwb2ludCwKICAgICAgICAgIGxpbmVTdGFydDogbGluZVN0YXJ0LAogICAgICAgICAgbGluZUVuZDogbGluZUVuZCwKICAgICAgICAgIHBvbHlnb25TdGFydDogcG9seWdvblN0YXJ0LAogICAgICAgICAgcG9seWdvbkVuZDogcG9seWdvbkVuZAogICAgICAgIH07CgogICAgICAgIGZ1bmN0aW9uIHBvaW50KHgsIHkpIHsKICAgICAgICAgIGlmICh2aXNpYmxlKHgsIHkpKSBhY3RpdmVTdHJlYW0ucG9pbnQoeCwgeSk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBwb2x5Z29uSW5zaWRlKCkgewogICAgICAgICAgdmFyIHdpbmRpbmcgPSAwOwoKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gcG9seWdvbi5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgZm9yICh2YXIgcmluZyA9IHBvbHlnb25baV0sIGogPSAxLCBtID0gcmluZy5sZW5ndGgsIHBvaW50ID0gcmluZ1swXSwgYTAsIGExLCBiMCA9IHBvaW50WzBdLCBiMSA9IHBvaW50WzFdOyBqIDwgbTsgKytqKSB7CiAgICAgICAgICAgICAgYTAgPSBiMCwgYTEgPSBiMSwgcG9pbnQgPSByaW5nW2pdLCBiMCA9IHBvaW50WzBdLCBiMSA9IHBvaW50WzFdOwogICAgICAgICAgICAgIGlmIChhMSA8PSB5MSkgeyBpZiAoYjEgPiB5MSAmJiAoYjAgLSBhMCkgKiAoeTEgLSBhMSkgPiAoYjEgLSBhMSkgKiAoeDAgLSBhMCkpICsrd2luZGluZzsgfQogICAgICAgICAgICAgIGVsc2UgeyBpZiAoYjEgPD0geTEgJiYgKGIwIC0gYTApICogKHkxIC0gYTEpIDwgKGIxIC0gYTEpICogKHgwIC0gYTApKSAtLXdpbmRpbmc7IH0KICAgICAgICAgICAgfQogICAgICAgICAgfQoKICAgICAgICAgIHJldHVybiB3aW5kaW5nOwogICAgICAgIH0KCiAgICAgICAgLy8gQnVmZmVyIGdlb21ldHJ5IHdpdGhpbiBhIHBvbHlnb24gYW5kIHRoZW4gY2xpcCBpdCBlbiBtYXNzZS4KICAgICAgICBmdW5jdGlvbiBwb2x5Z29uU3RhcnQoKSB7CiAgICAgICAgICBhY3RpdmVTdHJlYW0gPSBidWZmZXJTdHJlYW0sIHNlZ21lbnRzID0gW10sIHBvbHlnb24gPSBbXSwgY2xlYW4gPSB0cnVlOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcG9seWdvbkVuZCgpIHsKICAgICAgICAgIHZhciBzdGFydEluc2lkZSA9IHBvbHlnb25JbnNpZGUoKSwKICAgICAgICAgICAgICBjbGVhbkluc2lkZSA9IGNsZWFuICYmIHN0YXJ0SW5zaWRlLAogICAgICAgICAgICAgIHZpc2libGUgPSAoc2VnbWVudHMgPSBtZXJnZShzZWdtZW50cykpLmxlbmd0aDsKICAgICAgICAgIGlmIChjbGVhbkluc2lkZSB8fCB2aXNpYmxlKSB7CiAgICAgICAgICAgIHN0cmVhbS5wb2x5Z29uU3RhcnQoKTsKICAgICAgICAgICAgaWYgKGNsZWFuSW5zaWRlKSB7CiAgICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgIGludGVycG9sYXRlKG51bGwsIG51bGwsIDEsIHN0cmVhbSk7CiAgICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodmlzaWJsZSkgewogICAgICAgICAgICAgIGNsaXBSZWpvaW4oc2VnbWVudHMsIGNvbXBhcmVJbnRlcnNlY3Rpb24sIHN0YXJ0SW5zaWRlLCBpbnRlcnBvbGF0ZSwgc3RyZWFtKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzdHJlYW0ucG9seWdvbkVuZCgpOwogICAgICAgICAgfQogICAgICAgICAgYWN0aXZlU3RyZWFtID0gc3RyZWFtLCBzZWdtZW50cyA9IHBvbHlnb24gPSByaW5nID0gbnVsbDsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGxpbmVTdGFydCgpIHsKICAgICAgICAgIGNsaXBTdHJlYW0ucG9pbnQgPSBsaW5lUG9pbnQ7CiAgICAgICAgICBpZiAocG9seWdvbikgcG9seWdvbi5wdXNoKHJpbmcgPSBbXSk7CiAgICAgICAgICBmaXJzdCA9IHRydWU7CiAgICAgICAgICB2XyA9IGZhbHNlOwogICAgICAgICAgeF8gPSB5XyA9IE5hTjsKICAgICAgICB9CgogICAgICAgIC8vIFRPRE8gcmF0aGVyIHRoYW4gc3BlY2lhbC1jYXNlIHBvbHlnb25zLCBzaW1wbHkgaGFuZGxlIHRoZW0gc2VwYXJhdGVseS4KICAgICAgICAvLyBJZGVhbGx5LCBjb2luY2lkZW50IGludGVyc2VjdGlvbiBwb2ludHMgc2hvdWxkIGJlIGppdHRlcmVkIHRvIGF2b2lkCiAgICAgICAgLy8gY2xpcHBpbmcgaXNzdWVzLgogICAgICAgIGZ1bmN0aW9uIGxpbmVFbmQoKSB7CiAgICAgICAgICBpZiAoc2VnbWVudHMpIHsKICAgICAgICAgICAgbGluZVBvaW50KHhfXywgeV9fKTsKICAgICAgICAgICAgaWYgKHZfXyAmJiB2XykgYnVmZmVyU3RyZWFtLnJlam9pbigpOwogICAgICAgICAgICBzZWdtZW50cy5wdXNoKGJ1ZmZlclN0cmVhbS5yZXN1bHQoKSk7CiAgICAgICAgICB9CiAgICAgICAgICBjbGlwU3RyZWFtLnBvaW50ID0gcG9pbnQ7CiAgICAgICAgICBpZiAodl8pIGFjdGl2ZVN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBsaW5lUG9pbnQoeCwgeSkgewogICAgICAgICAgdmFyIHYgPSB2aXNpYmxlKHgsIHkpOwogICAgICAgICAgaWYgKHBvbHlnb24pIHJpbmcucHVzaChbeCwgeV0pOwogICAgICAgICAgaWYgKGZpcnN0KSB7CiAgICAgICAgICAgIHhfXyA9IHgsIHlfXyA9IHksIHZfXyA9IHY7CiAgICAgICAgICAgIGZpcnN0ID0gZmFsc2U7CiAgICAgICAgICAgIGlmICh2KSB7CiAgICAgICAgICAgICAgYWN0aXZlU3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgIGFjdGl2ZVN0cmVhbS5wb2ludCh4LCB5KTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKHYgJiYgdl8pIGFjdGl2ZVN0cmVhbS5wb2ludCh4LCB5KTsKICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgdmFyIGEgPSBbeF8gPSBNYXRoLm1heChjbGlwTWluLCBNYXRoLm1pbihjbGlwTWF4LCB4XykpLCB5XyA9IE1hdGgubWF4KGNsaXBNaW4sIE1hdGgubWluKGNsaXBNYXgsIHlfKSldLAogICAgICAgICAgICAgICAgICBiID0gW3ggPSBNYXRoLm1heChjbGlwTWluLCBNYXRoLm1pbihjbGlwTWF4LCB4KSksIHkgPSBNYXRoLm1heChjbGlwTWluLCBNYXRoLm1pbihjbGlwTWF4LCB5KSldOwogICAgICAgICAgICAgIGlmIChjbGlwTGluZShhLCBiLCB4MCwgeTAsIHgxLCB5MSkpIHsKICAgICAgICAgICAgICAgIGlmICghdl8pIHsKICAgICAgICAgICAgICAgICAgYWN0aXZlU3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ucG9pbnQoYVswXSwgYVsxXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ucG9pbnQoYlswXSwgYlsxXSk7CiAgICAgICAgICAgICAgICBpZiAoIXYpIGFjdGl2ZVN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICAgICAgICBjbGVhbiA9IGZhbHNlOwogICAgICAgICAgICAgIH0gZWxzZSBpZiAodikgewogICAgICAgICAgICAgICAgYWN0aXZlU3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgICAgYWN0aXZlU3RyZWFtLnBvaW50KHgsIHkpOwogICAgICAgICAgICAgICAgY2xlYW4gPSBmYWxzZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHhfID0geCwgeV8gPSB5LCB2XyA9IHY7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gY2xpcFN0cmVhbTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBleHRlbnQkMSgpIHsKICAgICAgdmFyIHgwID0gMCwKICAgICAgICAgIHkwID0gMCwKICAgICAgICAgIHgxID0gOTYwLAogICAgICAgICAgeTEgPSA1MDAsCiAgICAgICAgICBjYWNoZSwKICAgICAgICAgIGNhY2hlU3RyZWFtLAogICAgICAgICAgY2xpcDsKCiAgICAgIHJldHVybiBjbGlwID0gewogICAgICAgIHN0cmVhbTogZnVuY3Rpb24oc3RyZWFtKSB7CiAgICAgICAgICByZXR1cm4gY2FjaGUgJiYgY2FjaGVTdHJlYW0gPT09IHN0cmVhbSA/IGNhY2hlIDogY2FjaGUgPSBjbGlwUmVjdGFuZ2xlKHgwLCB5MCwgeDEsIHkxKShjYWNoZVN0cmVhbSA9IHN0cmVhbSk7CiAgICAgICAgfSwKICAgICAgICBleHRlbnQ6IGZ1bmN0aW9uKF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHgwID0gK19bMF1bMF0sIHkwID0gK19bMF1bMV0sIHgxID0gK19bMV1bMF0sIHkxID0gK19bMV1bMV0sIGNhY2hlID0gY2FjaGVTdHJlYW0gPSBudWxsLCBjbGlwKSA6IFtbeDAsIHkwXSwgW3gxLCB5MV1dOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICB2YXIgbGVuZ3RoU3VtID0gYWRkZXIoKSwKICAgICAgICBsYW1iZGEwJDIsCiAgICAgICAgc2luUGhpMCQxLAogICAgICAgIGNvc1BoaTAkMTsKCiAgICB2YXIgbGVuZ3RoU3RyZWFtID0gewogICAgICBzcGhlcmU6IG5vb3AkMiwKICAgICAgcG9pbnQ6IG5vb3AkMiwKICAgICAgbGluZVN0YXJ0OiBsZW5ndGhMaW5lU3RhcnQsCiAgICAgIGxpbmVFbmQ6IG5vb3AkMiwKICAgICAgcG9seWdvblN0YXJ0OiBub29wJDIsCiAgICAgIHBvbHlnb25FbmQ6IG5vb3AkMgogICAgfTsKCiAgICBmdW5jdGlvbiBsZW5ndGhMaW5lU3RhcnQoKSB7CiAgICAgIGxlbmd0aFN0cmVhbS5wb2ludCA9IGxlbmd0aFBvaW50Rmlyc3Q7CiAgICAgIGxlbmd0aFN0cmVhbS5saW5lRW5kID0gbGVuZ3RoTGluZUVuZDsKICAgIH0KCiAgICBmdW5jdGlvbiBsZW5ndGhMaW5lRW5kKCkgewogICAgICBsZW5ndGhTdHJlYW0ucG9pbnQgPSBsZW5ndGhTdHJlYW0ubGluZUVuZCA9IG5vb3AkMjsKICAgIH0KCiAgICBmdW5jdGlvbiBsZW5ndGhQb2ludEZpcnN0KGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zLCBwaGkgKj0gcmFkaWFuczsKICAgICAgbGFtYmRhMCQyID0gbGFtYmRhLCBzaW5QaGkwJDEgPSBzaW4kMShwaGkpLCBjb3NQaGkwJDEgPSBjb3MkMShwaGkpOwogICAgICBsZW5ndGhTdHJlYW0ucG9pbnQgPSBsZW5ndGhQb2ludDsKICAgIH0KCiAgICBmdW5jdGlvbiBsZW5ndGhQb2ludChsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucywgcGhpICo9IHJhZGlhbnM7CiAgICAgIHZhciBzaW5QaGkgPSBzaW4kMShwaGkpLAogICAgICAgICAgY29zUGhpID0gY29zJDEocGhpKSwKICAgICAgICAgIGRlbHRhID0gYWJzKGxhbWJkYSAtIGxhbWJkYTAkMiksCiAgICAgICAgICBjb3NEZWx0YSA9IGNvcyQxKGRlbHRhKSwKICAgICAgICAgIHNpbkRlbHRhID0gc2luJDEoZGVsdGEpLAogICAgICAgICAgeCA9IGNvc1BoaSAqIHNpbkRlbHRhLAogICAgICAgICAgeSA9IGNvc1BoaTAkMSAqIHNpblBoaSAtIHNpblBoaTAkMSAqIGNvc1BoaSAqIGNvc0RlbHRhLAogICAgICAgICAgeiA9IHNpblBoaTAkMSAqIHNpblBoaSArIGNvc1BoaTAkMSAqIGNvc1BoaSAqIGNvc0RlbHRhOwogICAgICBsZW5ndGhTdW0uYWRkKGF0YW4yKHNxcnQoeCAqIHggKyB5ICogeSksIHopKTsKICAgICAgbGFtYmRhMCQyID0gbGFtYmRhLCBzaW5QaGkwJDEgPSBzaW5QaGksIGNvc1BoaTAkMSA9IGNvc1BoaTsKICAgIH0KCiAgICBmdW5jdGlvbiBsZW5ndGgkMShvYmplY3QpIHsKICAgICAgbGVuZ3RoU3VtLnJlc2V0KCk7CiAgICAgIGdlb1N0cmVhbShvYmplY3QsIGxlbmd0aFN0cmVhbSk7CiAgICAgIHJldHVybiArbGVuZ3RoU3VtOwogICAgfQoKICAgIHZhciBjb29yZGluYXRlcyA9IFtudWxsLCBudWxsXSwKICAgICAgICBvYmplY3QkMSA9IHt0eXBlOiAiTGluZVN0cmluZyIsIGNvb3JkaW5hdGVzOiBjb29yZGluYXRlc307CgogICAgZnVuY3Rpb24gZGlzdGFuY2UoYSwgYikgewogICAgICBjb29yZGluYXRlc1swXSA9IGE7CiAgICAgIGNvb3JkaW5hdGVzWzFdID0gYjsKICAgICAgcmV0dXJuIGxlbmd0aCQxKG9iamVjdCQxKTsKICAgIH0KCiAgICB2YXIgY29udGFpbnNPYmplY3RUeXBlID0gewogICAgICBGZWF0dXJlOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zR2VvbWV0cnkob2JqZWN0Lmdlb21ldHJ5LCBwb2ludCk7CiAgICAgIH0sCiAgICAgIEZlYXR1cmVDb2xsZWN0aW9uOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgdmFyIGZlYXR1cmVzID0gb2JqZWN0LmZlYXR1cmVzLCBpID0gLTEsIG4gPSBmZWF0dXJlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmIChjb250YWluc0dlb21ldHJ5KGZlYXR1cmVzW2ldLmdlb21ldHJ5LCBwb2ludCkpIHJldHVybiB0cnVlOwogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgY29udGFpbnNHZW9tZXRyeVR5cGUgPSB7CiAgICAgIFNwaGVyZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0sCiAgICAgIFBvaW50OiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zUG9pbnQob2JqZWN0LmNvb3JkaW5hdGVzLCBwb2ludCk7CiAgICAgIH0sCiAgICAgIE11bHRpUG9pbnQ6IGZ1bmN0aW9uKG9iamVjdCwgcG9pbnQpIHsKICAgICAgICB2YXIgY29vcmRpbmF0ZXMgPSBvYmplY3QuY29vcmRpbmF0ZXMsIGkgPSAtMSwgbiA9IGNvb3JkaW5hdGVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKGNvbnRhaW5zUG9pbnQoY29vcmRpbmF0ZXNbaV0sIHBvaW50KSkgcmV0dXJuIHRydWU7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAogICAgICBMaW5lU3RyaW5nOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zTGluZShvYmplY3QuY29vcmRpbmF0ZXMsIHBvaW50KTsKICAgICAgfSwKICAgICAgTXVsdGlMaW5lU3RyaW5nOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgdmFyIGNvb3JkaW5hdGVzID0gb2JqZWN0LmNvb3JkaW5hdGVzLCBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmIChjb250YWluc0xpbmUoY29vcmRpbmF0ZXNbaV0sIHBvaW50KSkgcmV0dXJuIHRydWU7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAogICAgICBQb2x5Z29uOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zUG9seWdvbihvYmplY3QuY29vcmRpbmF0ZXMsIHBvaW50KTsKICAgICAgfSwKICAgICAgTXVsdGlQb2x5Z29uOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgdmFyIGNvb3JkaW5hdGVzID0gb2JqZWN0LmNvb3JkaW5hdGVzLCBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmIChjb250YWluc1BvbHlnb24oY29vcmRpbmF0ZXNbaV0sIHBvaW50KSkgcmV0dXJuIHRydWU7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAogICAgICBHZW9tZXRyeUNvbGxlY3Rpb246IGZ1bmN0aW9uKG9iamVjdCwgcG9pbnQpIHsKICAgICAgICB2YXIgZ2VvbWV0cmllcyA9IG9iamVjdC5nZW9tZXRyaWVzLCBpID0gLTEsIG4gPSBnZW9tZXRyaWVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKGNvbnRhaW5zR2VvbWV0cnkoZ2VvbWV0cmllc1tpXSwgcG9pbnQpKSByZXR1cm4gdHJ1ZTsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY29udGFpbnNHZW9tZXRyeShnZW9tZXRyeSwgcG9pbnQpIHsKICAgICAgcmV0dXJuIGdlb21ldHJ5ICYmIGNvbnRhaW5zR2VvbWV0cnlUeXBlLmhhc093blByb3BlcnR5KGdlb21ldHJ5LnR5cGUpCiAgICAgICAgICA/IGNvbnRhaW5zR2VvbWV0cnlUeXBlW2dlb21ldHJ5LnR5cGVdKGdlb21ldHJ5LCBwb2ludCkKICAgICAgICAgIDogZmFsc2U7CiAgICB9CgogICAgZnVuY3Rpb24gY29udGFpbnNQb2ludChjb29yZGluYXRlcywgcG9pbnQpIHsKICAgICAgcmV0dXJuIGRpc3RhbmNlKGNvb3JkaW5hdGVzLCBwb2ludCkgPT09IDA7CiAgICB9CgogICAgZnVuY3Rpb24gY29udGFpbnNMaW5lKGNvb3JkaW5hdGVzLCBwb2ludCkgewogICAgICB2YXIgYW8sIGJvLCBhYjsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7IGkgPCBuOyBpKyspIHsKICAgICAgICBibyA9IGRpc3RhbmNlKGNvb3JkaW5hdGVzW2ldLCBwb2ludCk7CiAgICAgICAgaWYgKGJvID09PSAwKSByZXR1cm4gdHJ1ZTsKICAgICAgICBpZiAoaSA+IDApIHsKICAgICAgICAgIGFiID0gZGlzdGFuY2UoY29vcmRpbmF0ZXNbaV0sIGNvb3JkaW5hdGVzW2kgLSAxXSk7CiAgICAgICAgICBpZiAoCiAgICAgICAgICAgIGFiID4gMCAmJgogICAgICAgICAgICBhbyA8PSBhYiAmJgogICAgICAgICAgICBibyA8PSBhYiAmJgogICAgICAgICAgICAoYW8gKyBibyAtIGFiKSAqICgxIC0gTWF0aC5wb3coKGFvIC0gYm8pIC8gYWIsIDIpKSA8IGVwc2lsb24yJDEgKiBhYgogICAgICAgICAgKQogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgYW8gPSBibzsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CgogICAgZnVuY3Rpb24gY29udGFpbnNQb2x5Z29uKGNvb3JkaW5hdGVzLCBwb2ludCkgewogICAgICByZXR1cm4gISFwb2x5Z29uQ29udGFpbnMoY29vcmRpbmF0ZXMubWFwKHJpbmdSYWRpYW5zKSwgcG9pbnRSYWRpYW5zKHBvaW50KSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmluZ1JhZGlhbnMocmluZykgewogICAgICByZXR1cm4gcmluZyA9IHJpbmcubWFwKHBvaW50UmFkaWFucyksIHJpbmcucG9wKCksIHJpbmc7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnRSYWRpYW5zKHBvaW50KSB7CiAgICAgIHJldHVybiBbcG9pbnRbMF0gKiByYWRpYW5zLCBwb2ludFsxXSAqIHJhZGlhbnNdOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRhaW5zJDEob2JqZWN0LCBwb2ludCkgewogICAgICByZXR1cm4gKG9iamVjdCAmJiBjb250YWluc09iamVjdFR5cGUuaGFzT3duUHJvcGVydHkob2JqZWN0LnR5cGUpCiAgICAgICAgICA/IGNvbnRhaW5zT2JqZWN0VHlwZVtvYmplY3QudHlwZV0KICAgICAgICAgIDogY29udGFpbnNHZW9tZXRyeSkob2JqZWN0LCBwb2ludCk7CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlWCh5MCwgeTEsIGR5KSB7CiAgICAgIHZhciB5ID0gc2VxdWVuY2UoeTAsIHkxIC0gZXBzaWxvbiQyLCBkeSkuY29uY2F0KHkxKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgpIHsgcmV0dXJuIHkubWFwKGZ1bmN0aW9uKHkpIHsgcmV0dXJuIFt4LCB5XTsgfSk7IH07CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlWSh4MCwgeDEsIGR4KSB7CiAgICAgIHZhciB4ID0gc2VxdWVuY2UoeDAsIHgxIC0gZXBzaWxvbiQyLCBkeCkuY29uY2F0KHgxKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHkpIHsgcmV0dXJuIHgubWFwKGZ1bmN0aW9uKHgpIHsgcmV0dXJuIFt4LCB5XTsgfSk7IH07CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlKCkgewogICAgICB2YXIgeDEsIHgwLCBYMSwgWDAsCiAgICAgICAgICB5MSwgeTAsIFkxLCBZMCwKICAgICAgICAgIGR4ID0gMTAsIGR5ID0gZHgsIERYID0gOTAsIERZID0gMzYwLAogICAgICAgICAgeCwgeSwgWCwgWSwKICAgICAgICAgIHByZWNpc2lvbiA9IDIuNTsKCiAgICAgIGZ1bmN0aW9uIGdyYXRpY3VsZSgpIHsKICAgICAgICByZXR1cm4ge3R5cGU6ICJNdWx0aUxpbmVTdHJpbmciLCBjb29yZGluYXRlczogbGluZXMoKX07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGxpbmVzKCkgewogICAgICAgIHJldHVybiBzZXF1ZW5jZShjZWlsKFgwIC8gRFgpICogRFgsIFgxLCBEWCkubWFwKFgpCiAgICAgICAgICAgIC5jb25jYXQoc2VxdWVuY2UoY2VpbChZMCAvIERZKSAqIERZLCBZMSwgRFkpLm1hcChZKSkKICAgICAgICAgICAgLmNvbmNhdChzZXF1ZW5jZShjZWlsKHgwIC8gZHgpICogZHgsIHgxLCBkeCkuZmlsdGVyKGZ1bmN0aW9uKHgpIHsgcmV0dXJuIGFicyh4ICUgRFgpID4gZXBzaWxvbiQyOyB9KS5tYXAoeCkpCiAgICAgICAgICAgIC5jb25jYXQoc2VxdWVuY2UoY2VpbCh5MCAvIGR5KSAqIGR5LCB5MSwgZHkpLmZpbHRlcihmdW5jdGlvbih5KSB7IHJldHVybiBhYnMoeSAlIERZKSA+IGVwc2lsb24kMjsgfSkubWFwKHkpKTsKICAgICAgfQoKICAgICAgZ3JhdGljdWxlLmxpbmVzID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGxpbmVzKCkubWFwKGZ1bmN0aW9uKGNvb3JkaW5hdGVzKSB7IHJldHVybiB7dHlwZTogIkxpbmVTdHJpbmciLCBjb29yZGluYXRlczogY29vcmRpbmF0ZXN9OyB9KTsKICAgICAgfTsKCiAgICAgIGdyYXRpY3VsZS5vdXRsaW5lID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIHR5cGU6ICJQb2x5Z29uIiwKICAgICAgICAgIGNvb3JkaW5hdGVzOiBbCiAgICAgICAgICAgIFgoWDApLmNvbmNhdCgKICAgICAgICAgICAgWShZMSkuc2xpY2UoMSksCiAgICAgICAgICAgIFgoWDEpLnJldmVyc2UoKS5zbGljZSgxKSwKICAgICAgICAgICAgWShZMCkucmV2ZXJzZSgpLnNsaWNlKDEpKQogICAgICAgICAgXQogICAgICAgIH07CiAgICAgIH07CgogICAgICBncmF0aWN1bGUuZXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIGdyYXRpY3VsZS5leHRlbnRNaW5vcigpOwogICAgICAgIHJldHVybiBncmF0aWN1bGUuZXh0ZW50TWFqb3IoXykuZXh0ZW50TWlub3IoXyk7CiAgICAgIH07CgogICAgICBncmF0aWN1bGUuZXh0ZW50TWFqb3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW1tYMCwgWTBdLCBbWDEsIFkxXV07CiAgICAgICAgWDAgPSArX1swXVswXSwgWDEgPSArX1sxXVswXTsKICAgICAgICBZMCA9ICtfWzBdWzFdLCBZMSA9ICtfWzFdWzFdOwogICAgICAgIGlmIChYMCA+IFgxKSBfID0gWDAsIFgwID0gWDEsIFgxID0gXzsKICAgICAgICBpZiAoWTAgPiBZMSkgXyA9IFkwLCBZMCA9IFkxLCBZMSA9IF87CiAgICAgICAgcmV0dXJuIGdyYXRpY3VsZS5wcmVjaXNpb24ocHJlY2lzaW9uKTsKICAgICAgfTsKCiAgICAgIGdyYXRpY3VsZS5leHRlbnRNaW5vciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgICB4MCA9ICtfWzBdWzBdLCB4MSA9ICtfWzFdWzBdOwogICAgICAgIHkwID0gK19bMF1bMV0sIHkxID0gK19bMV1bMV07CiAgICAgICAgaWYgKHgwID4geDEpIF8gPSB4MCwgeDAgPSB4MSwgeDEgPSBfOwogICAgICAgIGlmICh5MCA+IHkxKSBfID0geTAsIHkwID0geTEsIHkxID0gXzsKICAgICAgICByZXR1cm4gZ3JhdGljdWxlLnByZWNpc2lvbihwcmVjaXNpb24pOwogICAgICB9OwoKICAgICAgZ3JhdGljdWxlLnN0ZXAgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gZ3JhdGljdWxlLnN0ZXBNaW5vcigpOwogICAgICAgIHJldHVybiBncmF0aWN1bGUuc3RlcE1ham9yKF8pLnN0ZXBNaW5vcihfKTsKICAgICAgfTsKCiAgICAgIGdyYXRpY3VsZS5zdGVwTWFqb3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW0RYLCBEWV07CiAgICAgICAgRFggPSArX1swXSwgRFkgPSArX1sxXTsKICAgICAgICByZXR1cm4gZ3JhdGljdWxlOwogICAgICB9OwoKICAgICAgZ3JhdGljdWxlLnN0ZXBNaW5vciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBbZHgsIGR5XTsKICAgICAgICBkeCA9ICtfWzBdLCBkeSA9ICtfWzFdOwogICAgICAgIHJldHVybiBncmF0aWN1bGU7CiAgICAgIH07CgogICAgICBncmF0aWN1bGUucHJlY2lzaW9uID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIHByZWNpc2lvbjsKICAgICAgICBwcmVjaXNpb24gPSArXzsKICAgICAgICB4ID0gZ3JhdGljdWxlWCh5MCwgeTEsIDkwKTsKICAgICAgICB5ID0gZ3JhdGljdWxlWSh4MCwgeDEsIHByZWNpc2lvbik7CiAgICAgICAgWCA9IGdyYXRpY3VsZVgoWTAsIFkxLCA5MCk7CiAgICAgICAgWSA9IGdyYXRpY3VsZVkoWDAsIFgxLCBwcmVjaXNpb24pOwogICAgICAgIHJldHVybiBncmF0aWN1bGU7CiAgICAgIH07CgogICAgICByZXR1cm4gZ3JhdGljdWxlCiAgICAgICAgICAuZXh0ZW50TWFqb3IoW1stMTgwLCAtOTAgKyBlcHNpbG9uJDJdLCBbMTgwLCA5MCAtIGVwc2lsb24kMl1dKQogICAgICAgICAgLmV4dGVudE1pbm9yKFtbLTE4MCwgLTgwIC0gZXBzaWxvbiQyXSwgWzE4MCwgODAgKyBlcHNpbG9uJDJdXSk7CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlMTAoKSB7CiAgICAgIHJldHVybiBncmF0aWN1bGUoKSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlJDEoYSwgYikgewogICAgICB2YXIgeDAgPSBhWzBdICogcmFkaWFucywKICAgICAgICAgIHkwID0gYVsxXSAqIHJhZGlhbnMsCiAgICAgICAgICB4MSA9IGJbMF0gKiByYWRpYW5zLAogICAgICAgICAgeTEgPSBiWzFdICogcmFkaWFucywKICAgICAgICAgIGN5MCA9IGNvcyQxKHkwKSwKICAgICAgICAgIHN5MCA9IHNpbiQxKHkwKSwKICAgICAgICAgIGN5MSA9IGNvcyQxKHkxKSwKICAgICAgICAgIHN5MSA9IHNpbiQxKHkxKSwKICAgICAgICAgIGt4MCA9IGN5MCAqIGNvcyQxKHgwKSwKICAgICAgICAgIGt5MCA9IGN5MCAqIHNpbiQxKHgwKSwKICAgICAgICAgIGt4MSA9IGN5MSAqIGNvcyQxKHgxKSwKICAgICAgICAgIGt5MSA9IGN5MSAqIHNpbiQxKHgxKSwKICAgICAgICAgIGQgPSAyICogYXNpbihzcXJ0KGhhdmVyc2luKHkxIC0geTApICsgY3kwICogY3kxICogaGF2ZXJzaW4oeDEgLSB4MCkpKSwKICAgICAgICAgIGsgPSBzaW4kMShkKTsKCiAgICAgIHZhciBpbnRlcnBvbGF0ZSA9IGQgPyBmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIEIgPSBzaW4kMSh0ICo9IGQpIC8gaywKICAgICAgICAgICAgQSA9IHNpbiQxKGQgLSB0KSAvIGssCiAgICAgICAgICAgIHggPSBBICoga3gwICsgQiAqIGt4MSwKICAgICAgICAgICAgeSA9IEEgKiBreTAgKyBCICoga3kxLAogICAgICAgICAgICB6ID0gQSAqIHN5MCArIEIgKiBzeTE7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgIGF0YW4yKHksIHgpICogZGVncmVlcyQxLAogICAgICAgICAgYXRhbjIoeiwgc3FydCh4ICogeCArIHkgKiB5KSkgKiBkZWdyZWVzJDEKICAgICAgICBdOwogICAgICB9IDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIFt4MCAqIGRlZ3JlZXMkMSwgeTAgKiBkZWdyZWVzJDFdOwogICAgICB9OwoKICAgICAgaW50ZXJwb2xhdGUuZGlzdGFuY2UgPSBkOwoKICAgICAgcmV0dXJuIGludGVycG9sYXRlOwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JDQoeCkgewogICAgICByZXR1cm4geDsKICAgIH0KCiAgICB2YXIgYXJlYVN1bSQxID0gYWRkZXIoKSwKICAgICAgICBhcmVhUmluZ1N1bSQxID0gYWRkZXIoKSwKICAgICAgICB4MDAsCiAgICAgICAgeTAwLAogICAgICAgIHgwJDEsCiAgICAgICAgeTAkMTsKCiAgICB2YXIgYXJlYVN0cmVhbSQxID0gewogICAgICBwb2ludDogbm9vcCQyLAogICAgICBsaW5lU3RhcnQ6IG5vb3AkMiwKICAgICAgbGluZUVuZDogbm9vcCQyLAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGFyZWFTdHJlYW0kMS5saW5lU3RhcnQgPSBhcmVhUmluZ1N0YXJ0JDE7CiAgICAgICAgYXJlYVN0cmVhbSQxLmxpbmVFbmQgPSBhcmVhUmluZ0VuZCQxOwogICAgICB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBhcmVhU3RyZWFtJDEubGluZVN0YXJ0ID0gYXJlYVN0cmVhbSQxLmxpbmVFbmQgPSBhcmVhU3RyZWFtJDEucG9pbnQgPSBub29wJDI7CiAgICAgICAgYXJlYVN1bSQxLmFkZChhYnMoYXJlYVJpbmdTdW0kMSkpOwogICAgICAgIGFyZWFSaW5nU3VtJDEucmVzZXQoKTsKICAgICAgfSwKICAgICAgcmVzdWx0OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYXJlYSA9IGFyZWFTdW0kMSAvIDI7CiAgICAgICAgYXJlYVN1bSQxLnJlc2V0KCk7CiAgICAgICAgcmV0dXJuIGFyZWE7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYXJlYVJpbmdTdGFydCQxKCkgewogICAgICBhcmVhU3RyZWFtJDEucG9pbnQgPSBhcmVhUG9pbnRGaXJzdCQxOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWFQb2ludEZpcnN0JDEoeCwgeSkgewogICAgICBhcmVhU3RyZWFtJDEucG9pbnQgPSBhcmVhUG9pbnQkMTsKICAgICAgeDAwID0geDAkMSA9IHgsIHkwMCA9IHkwJDEgPSB5OwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWFQb2ludCQxKHgsIHkpIHsKICAgICAgYXJlYVJpbmdTdW0kMS5hZGQoeTAkMSAqIHggLSB4MCQxICogeSk7CiAgICAgIHgwJDEgPSB4LCB5MCQxID0geTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhUmluZ0VuZCQxKCkgewogICAgICBhcmVhUG9pbnQkMSh4MDAsIHkwMCk7CiAgICB9CgogICAgdmFyIHgwJDIgPSBJbmZpbml0eSwKICAgICAgICB5MCQyID0geDAkMiwKICAgICAgICB4MSA9IC14MCQyLAogICAgICAgIHkxID0geDE7CgogICAgdmFyIGJvdW5kc1N0cmVhbSQxID0gewogICAgICBwb2ludDogYm91bmRzUG9pbnQkMSwKICAgICAgbGluZVN0YXJ0OiBub29wJDIsCiAgICAgIGxpbmVFbmQ6IG5vb3AkMiwKICAgICAgcG9seWdvblN0YXJ0OiBub29wJDIsCiAgICAgIHBvbHlnb25FbmQ6IG5vb3AkMiwKICAgICAgcmVzdWx0OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYm91bmRzID0gW1t4MCQyLCB5MCQyXSwgW3gxLCB5MV1dOwogICAgICAgIHgxID0geTEgPSAtKHkwJDIgPSB4MCQyID0gSW5maW5pdHkpOwogICAgICAgIHJldHVybiBib3VuZHM7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYm91bmRzUG9pbnQkMSh4LCB5KSB7CiAgICAgIGlmICh4IDwgeDAkMikgeDAkMiA9IHg7CiAgICAgIGlmICh4ID4geDEpIHgxID0geDsKICAgICAgaWYgKHkgPCB5MCQyKSB5MCQyID0geTsKICAgICAgaWYgKHkgPiB5MSkgeTEgPSB5OwogICAgfQoKICAgIC8vIFRPRE8gRW5mb3JjZSBwb3NpdGl2ZSBhcmVhIGZvciBleHRlcmlvciwgbmVnYXRpdmUgYXJlYSBmb3IgaW50ZXJpb3I/CgogICAgdmFyIFgwJDEgPSAwLAogICAgICAgIFkwJDEgPSAwLAogICAgICAgIFowJDEgPSAwLAogICAgICAgIFgxJDEgPSAwLAogICAgICAgIFkxJDEgPSAwLAogICAgICAgIFoxJDEgPSAwLAogICAgICAgIFgyJDEgPSAwLAogICAgICAgIFkyJDEgPSAwLAogICAgICAgIFoyJDEgPSAwLAogICAgICAgIHgwMCQxLAogICAgICAgIHkwMCQxLAogICAgICAgIHgwJDMsCiAgICAgICAgeTAkMzsKCiAgICB2YXIgY2VudHJvaWRTdHJlYW0kMSA9IHsKICAgICAgcG9pbnQ6IGNlbnRyb2lkUG9pbnQkMSwKICAgICAgbGluZVN0YXJ0OiBjZW50cm9pZExpbmVTdGFydCQxLAogICAgICBsaW5lRW5kOiBjZW50cm9pZExpbmVFbmQkMSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBjZW50cm9pZFN0cmVhbSQxLmxpbmVTdGFydCA9IGNlbnRyb2lkUmluZ1N0YXJ0JDE7CiAgICAgICAgY2VudHJvaWRTdHJlYW0kMS5saW5lRW5kID0gY2VudHJvaWRSaW5nRW5kJDE7CiAgICAgIH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGNlbnRyb2lkU3RyZWFtJDEucG9pbnQgPSBjZW50cm9pZFBvaW50JDE7CiAgICAgICAgY2VudHJvaWRTdHJlYW0kMS5saW5lU3RhcnQgPSBjZW50cm9pZExpbmVTdGFydCQxOwogICAgICAgIGNlbnRyb2lkU3RyZWFtJDEubGluZUVuZCA9IGNlbnRyb2lkTGluZUVuZCQxOwogICAgICB9LAogICAgICByZXN1bHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBjZW50cm9pZCA9IFoyJDEgPyBbWDIkMSAvIFoyJDEsIFkyJDEgLyBaMiQxXQogICAgICAgICAgICA6IFoxJDEgPyBbWDEkMSAvIFoxJDEsIFkxJDEgLyBaMSQxXQogICAgICAgICAgICA6IFowJDEgPyBbWDAkMSAvIFowJDEsIFkwJDEgLyBaMCQxXQogICAgICAgICAgICA6IFtOYU4sIE5hTl07CiAgICAgICAgWDAkMSA9IFkwJDEgPSBaMCQxID0KICAgICAgICBYMSQxID0gWTEkMSA9IFoxJDEgPQogICAgICAgIFgyJDEgPSBZMiQxID0gWjIkMSA9IDA7CiAgICAgICAgcmV0dXJuIGNlbnRyb2lkOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnQkMSh4LCB5KSB7CiAgICAgIFgwJDEgKz0geDsKICAgICAgWTAkMSArPSB5OwogICAgICArK1owJDE7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRMaW5lU3RhcnQkMSgpIHsKICAgICAgY2VudHJvaWRTdHJlYW0kMS5wb2ludCA9IGNlbnRyb2lkUG9pbnRGaXJzdExpbmU7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRQb2ludEZpcnN0TGluZSh4LCB5KSB7CiAgICAgIGNlbnRyb2lkU3RyZWFtJDEucG9pbnQgPSBjZW50cm9pZFBvaW50TGluZTsKICAgICAgY2VudHJvaWRQb2ludCQxKHgwJDMgPSB4LCB5MCQzID0geSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRQb2ludExpbmUoeCwgeSkgewogICAgICB2YXIgZHggPSB4IC0geDAkMywgZHkgPSB5IC0geTAkMywgeiA9IHNxcnQoZHggKiBkeCArIGR5ICogZHkpOwogICAgICBYMSQxICs9IHogKiAoeDAkMyArIHgpIC8gMjsKICAgICAgWTEkMSArPSB6ICogKHkwJDMgKyB5KSAvIDI7CiAgICAgIFoxJDEgKz0gejsKICAgICAgY2VudHJvaWRQb2ludCQxKHgwJDMgPSB4LCB5MCQzID0geSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRMaW5lRW5kJDEoKSB7CiAgICAgIGNlbnRyb2lkU3RyZWFtJDEucG9pbnQgPSBjZW50cm9pZFBvaW50JDE7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nU3RhcnQkMSgpIHsKICAgICAgY2VudHJvaWRTdHJlYW0kMS5wb2ludCA9IGNlbnRyb2lkUG9pbnRGaXJzdFJpbmc7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nRW5kJDEoKSB7CiAgICAgIGNlbnRyb2lkUG9pbnRSaW5nKHgwMCQxLCB5MDAkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRQb2ludEZpcnN0UmluZyh4LCB5KSB7CiAgICAgIGNlbnRyb2lkU3RyZWFtJDEucG9pbnQgPSBjZW50cm9pZFBvaW50UmluZzsKICAgICAgY2VudHJvaWRQb2ludCQxKHgwMCQxID0geDAkMyA9IHgsIHkwMCQxID0geTAkMyA9IHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnRSaW5nKHgsIHkpIHsKICAgICAgdmFyIGR4ID0geCAtIHgwJDMsCiAgICAgICAgICBkeSA9IHkgLSB5MCQzLAogICAgICAgICAgeiA9IHNxcnQoZHggKiBkeCArIGR5ICogZHkpOwoKICAgICAgWDEkMSArPSB6ICogKHgwJDMgKyB4KSAvIDI7CiAgICAgIFkxJDEgKz0geiAqICh5MCQzICsgeSkgLyAyOwogICAgICBaMSQxICs9IHo7CgogICAgICB6ID0geTAkMyAqIHggLSB4MCQzICogeTsKICAgICAgWDIkMSArPSB6ICogKHgwJDMgKyB4KTsKICAgICAgWTIkMSArPSB6ICogKHkwJDMgKyB5KTsKICAgICAgWjIkMSArPSB6ICogMzsKICAgICAgY2VudHJvaWRQb2ludCQxKHgwJDMgPSB4LCB5MCQzID0geSk7CiAgICB9CgogICAgZnVuY3Rpb24gUGF0aENvbnRleHQoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBQYXRoQ29udGV4dC5wcm90b3R5cGUgPSB7CiAgICAgIF9yYWRpdXM6IDQuNSwKICAgICAgcG9pbnRSYWRpdXM6IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gdGhpcy5fcmFkaXVzID0gXywgdGhpczsKICAgICAgfSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lID09PSAwKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX3BvaW50ID0gTmFOOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogewogICAgICAgICAgICB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4LCB5KTsKICAgICAgICAgICAgdGhpcy5fcG9pbnQgPSAxOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGNhc2UgMTogewogICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBkZWZhdWx0OiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKHggKyB0aGlzLl9yYWRpdXMsIHkpOwogICAgICAgICAgICB0aGlzLl9jb250ZXh0LmFyYyh4LCB5LCB0aGlzLl9yYWRpdXMsIDAsIHRhdSQzKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICByZXN1bHQ6IG5vb3AkMgogICAgfTsKCiAgICB2YXIgbGVuZ3RoU3VtJDEgPSBhZGRlcigpLAogICAgICAgIGxlbmd0aFJpbmcsCiAgICAgICAgeDAwJDIsCiAgICAgICAgeTAwJDIsCiAgICAgICAgeDAkNCwKICAgICAgICB5MCQ0OwoKICAgIHZhciBsZW5ndGhTdHJlYW0kMSA9IHsKICAgICAgcG9pbnQ6IG5vb3AkMiwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBsZW5ndGhTdHJlYW0kMS5wb2ludCA9IGxlbmd0aFBvaW50Rmlyc3QkMTsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKGxlbmd0aFJpbmcpIGxlbmd0aFBvaW50JDEoeDAwJDIsIHkwMCQyKTsKICAgICAgICBsZW5ndGhTdHJlYW0kMS5wb2ludCA9IG5vb3AkMjsKICAgICAgfSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBsZW5ndGhSaW5nID0gdHJ1ZTsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgbGVuZ3RoUmluZyA9IG51bGw7CiAgICAgIH0sCiAgICAgIHJlc3VsdDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGxlbmd0aCA9ICtsZW5ndGhTdW0kMTsKICAgICAgICBsZW5ndGhTdW0kMS5yZXNldCgpOwogICAgICAgIHJldHVybiBsZW5ndGg7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gbGVuZ3RoUG9pbnRGaXJzdCQxKHgsIHkpIHsKICAgICAgbGVuZ3RoU3RyZWFtJDEucG9pbnQgPSBsZW5ndGhQb2ludCQxOwogICAgICB4MDAkMiA9IHgwJDQgPSB4LCB5MDAkMiA9IHkwJDQgPSB5OwogICAgfQoKICAgIGZ1bmN0aW9uIGxlbmd0aFBvaW50JDEoeCwgeSkgewogICAgICB4MCQ0IC09IHgsIHkwJDQgLT0geTsKICAgICAgbGVuZ3RoU3VtJDEuYWRkKHNxcnQoeDAkNCAqIHgwJDQgKyB5MCQ0ICogeTAkNCkpOwogICAgICB4MCQ0ID0geCwgeTAkNCA9IHk7CiAgICB9CgogICAgZnVuY3Rpb24gUGF0aFN0cmluZygpIHsKICAgICAgdGhpcy5fc3RyaW5nID0gW107CiAgICB9CgogICAgUGF0aFN0cmluZy5wcm90b3R5cGUgPSB7CiAgICAgIF9yYWRpdXM6IDQuNSwKICAgICAgX2NpcmNsZTogY2lyY2xlJDEoNC41KSwKICAgICAgcG9pbnRSYWRpdXM6IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoKF8gPSArXykgIT09IHRoaXMuX3JhZGl1cykgdGhpcy5fcmFkaXVzID0gXywgdGhpcy5fY2lyY2xlID0gbnVsbDsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lID09PSAwKSB0aGlzLl9zdHJpbmcucHVzaCgiWiIpOwogICAgICAgIHRoaXMuX3BvaW50ID0gTmFOOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogewogICAgICAgICAgICB0aGlzLl9zdHJpbmcucHVzaCgiTSIsIHgsICIsIiwgeSk7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ID0gMTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgdGhpcy5fc3RyaW5nLnB1c2goIkwiLCB4LCAiLCIsIHkpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGRlZmF1bHQ6IHsKICAgICAgICAgICAgaWYgKHRoaXMuX2NpcmNsZSA9PSBudWxsKSB0aGlzLl9jaXJjbGUgPSBjaXJjbGUkMSh0aGlzLl9yYWRpdXMpOwogICAgICAgICAgICB0aGlzLl9zdHJpbmcucHVzaCgiTSIsIHgsICIsIiwgeSwgdGhpcy5fY2lyY2xlKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICByZXN1bHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9zdHJpbmcubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gdGhpcy5fc3RyaW5nLmpvaW4oIiIpOwogICAgICAgICAgdGhpcy5fc3RyaW5nID0gW107CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY2lyY2xlJDEocmFkaXVzKSB7CiAgICAgIHJldHVybiAibTAsIiArIHJhZGl1cwogICAgICAgICAgKyAiYSIgKyByYWRpdXMgKyAiLCIgKyByYWRpdXMgKyAiIDAgMSwxIDAsIiArIC0yICogcmFkaXVzCiAgICAgICAgICArICJhIiArIHJhZGl1cyArICIsIiArIHJhZGl1cyArICIgMCAxLDEgMCwiICsgMiAqIHJhZGl1cwogICAgICAgICAgKyAieiI7CiAgICB9CgogICAgZnVuY3Rpb24gaW5kZXgkMShwcm9qZWN0aW9uLCBjb250ZXh0KSB7CiAgICAgIHZhciBwb2ludFJhZGl1cyA9IDQuNSwKICAgICAgICAgIHByb2plY3Rpb25TdHJlYW0sCiAgICAgICAgICBjb250ZXh0U3RyZWFtOwoKICAgICAgZnVuY3Rpb24gcGF0aChvYmplY3QpIHsKICAgICAgICBpZiAob2JqZWN0KSB7CiAgICAgICAgICBpZiAodHlwZW9mIHBvaW50UmFkaXVzID09PSAiZnVuY3Rpb24iKSBjb250ZXh0U3RyZWFtLnBvaW50UmFkaXVzKCtwb2ludFJhZGl1cy5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgICAgIGdlb1N0cmVhbShvYmplY3QsIHByb2plY3Rpb25TdHJlYW0oY29udGV4dFN0cmVhbSkpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gY29udGV4dFN0cmVhbS5yZXN1bHQoKTsKICAgICAgfQoKICAgICAgcGF0aC5hcmVhID0gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgZ2VvU3RyZWFtKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShhcmVhU3RyZWFtJDEpKTsKICAgICAgICByZXR1cm4gYXJlYVN0cmVhbSQxLnJlc3VsdCgpOwogICAgICB9OwoKICAgICAgcGF0aC5tZWFzdXJlID0gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgZ2VvU3RyZWFtKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShsZW5ndGhTdHJlYW0kMSkpOwogICAgICAgIHJldHVybiBsZW5ndGhTdHJlYW0kMS5yZXN1bHQoKTsKICAgICAgfTsKCiAgICAgIHBhdGguYm91bmRzID0gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgZ2VvU3RyZWFtKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShib3VuZHNTdHJlYW0kMSkpOwogICAgICAgIHJldHVybiBib3VuZHNTdHJlYW0kMS5yZXN1bHQoKTsKICAgICAgfTsKCiAgICAgIHBhdGguY2VudHJvaWQgPSBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICBnZW9TdHJlYW0ob2JqZWN0LCBwcm9qZWN0aW9uU3RyZWFtKGNlbnRyb2lkU3RyZWFtJDEpKTsKICAgICAgICByZXR1cm4gY2VudHJvaWRTdHJlYW0kMS5yZXN1bHQoKTsKICAgICAgfTsKCiAgICAgIHBhdGgucHJvamVjdGlvbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwcm9qZWN0aW9uU3RyZWFtID0gXyA9PSBudWxsID8gKHByb2plY3Rpb24gPSBudWxsLCBpZGVudGl0eSQ0KSA6IChwcm9qZWN0aW9uID0gXykuc3RyZWFtLCBwYXRoKSA6IHByb2plY3Rpb247CiAgICAgIH07CgogICAgICBwYXRoLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gY29udGV4dDsKICAgICAgICBjb250ZXh0U3RyZWFtID0gXyA9PSBudWxsID8gKGNvbnRleHQgPSBudWxsLCBuZXcgUGF0aFN0cmluZykgOiBuZXcgUGF0aENvbnRleHQoY29udGV4dCA9IF8pOwogICAgICAgIGlmICh0eXBlb2YgcG9pbnRSYWRpdXMgIT09ICJmdW5jdGlvbiIpIGNvbnRleHRTdHJlYW0ucG9pbnRSYWRpdXMocG9pbnRSYWRpdXMpOwogICAgICAgIHJldHVybiBwYXRoOwogICAgICB9OwoKICAgICAgcGF0aC5wb2ludFJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBwb2ludFJhZGl1czsKICAgICAgICBwb2ludFJhZGl1cyA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IChjb250ZXh0U3RyZWFtLnBvaW50UmFkaXVzKCtfKSwgK18pOwogICAgICAgIHJldHVybiBwYXRoOwogICAgICB9OwoKICAgICAgcmV0dXJuIHBhdGgucHJvamVjdGlvbihwcm9qZWN0aW9uKS5jb250ZXh0KGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybShtZXRob2RzKSB7CiAgICAgIHJldHVybiB7CiAgICAgICAgc3RyZWFtOiB0cmFuc2Zvcm1lcihtZXRob2RzKQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybWVyKG1ldGhvZHMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHZhciBzID0gbmV3IFRyYW5zZm9ybVN0cmVhbTsKICAgICAgICBmb3IgKHZhciBrZXkgaW4gbWV0aG9kcykgc1trZXldID0gbWV0aG9kc1trZXldOwogICAgICAgIHMuc3RyZWFtID0gc3RyZWFtOwogICAgICAgIHJldHVybiBzOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIFRyYW5zZm9ybVN0cmVhbSgpIHt9CgogICAgVHJhbnNmb3JtU3RyZWFtLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRyYW5zZm9ybVN0cmVhbSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsgdGhpcy5zdHJlYW0ucG9pbnQoeCwgeSk7IH0sCiAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7IHRoaXMuc3RyZWFtLnNwaGVyZSgpOyB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgeyB0aGlzLnN0cmVhbS5saW5lU3RhcnQoKTsgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7IHRoaXMuc3RyZWFtLmxpbmVFbmQoKTsgfSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsgdGhpcy5zdHJlYW0ucG9seWdvblN0YXJ0KCk7IH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgeyB0aGlzLnN0cmVhbS5wb2x5Z29uRW5kKCk7IH0KICAgIH07CgogICAgZnVuY3Rpb24gZml0KHByb2plY3Rpb24sIGZpdEJvdW5kcywgb2JqZWN0KSB7CiAgICAgIHZhciBjbGlwID0gcHJvamVjdGlvbi5jbGlwRXh0ZW50ICYmIHByb2plY3Rpb24uY2xpcEV4dGVudCgpOwogICAgICBwcm9qZWN0aW9uLnNjYWxlKDE1MCkudHJhbnNsYXRlKFswLCAwXSk7CiAgICAgIGlmIChjbGlwICE9IG51bGwpIHByb2plY3Rpb24uY2xpcEV4dGVudChudWxsKTsKICAgICAgZ2VvU3RyZWFtKG9iamVjdCwgcHJvamVjdGlvbi5zdHJlYW0oYm91bmRzU3RyZWFtJDEpKTsKICAgICAgZml0Qm91bmRzKGJvdW5kc1N0cmVhbSQxLnJlc3VsdCgpKTsKICAgICAgaWYgKGNsaXAgIT0gbnVsbCkgcHJvamVjdGlvbi5jbGlwRXh0ZW50KGNsaXApOwogICAgICByZXR1cm4gcHJvamVjdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBmaXRFeHRlbnQocHJvamVjdGlvbiwgZXh0ZW50LCBvYmplY3QpIHsKICAgICAgcmV0dXJuIGZpdChwcm9qZWN0aW9uLCBmdW5jdGlvbihiKSB7CiAgICAgICAgdmFyIHcgPSBleHRlbnRbMV1bMF0gLSBleHRlbnRbMF1bMF0sCiAgICAgICAgICAgIGggPSBleHRlbnRbMV1bMV0gLSBleHRlbnRbMF1bMV0sCiAgICAgICAgICAgIGsgPSBNYXRoLm1pbih3IC8gKGJbMV1bMF0gLSBiWzBdWzBdKSwgaCAvIChiWzFdWzFdIC0gYlswXVsxXSkpLAogICAgICAgICAgICB4ID0gK2V4dGVudFswXVswXSArICh3IC0gayAqIChiWzFdWzBdICsgYlswXVswXSkpIC8gMiwKICAgICAgICAgICAgeSA9ICtleHRlbnRbMF1bMV0gKyAoaCAtIGsgKiAoYlsxXVsxXSArIGJbMF1bMV0pKSAvIDI7CiAgICAgICAgcHJvamVjdGlvbi5zY2FsZSgxNTAgKiBrKS50cmFuc2xhdGUoW3gsIHldKTsKICAgICAgfSwgb2JqZWN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmaXRTaXplKHByb2plY3Rpb24sIHNpemUsIG9iamVjdCkgewogICAgICByZXR1cm4gZml0RXh0ZW50KHByb2plY3Rpb24sIFtbMCwgMF0sIHNpemVdLCBvYmplY3QpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZpdFdpZHRoKHByb2plY3Rpb24sIHdpZHRoLCBvYmplY3QpIHsKICAgICAgcmV0dXJuIGZpdChwcm9qZWN0aW9uLCBmdW5jdGlvbihiKSB7CiAgICAgICAgdmFyIHcgPSArd2lkdGgsCiAgICAgICAgICAgIGsgPSB3IC8gKGJbMV1bMF0gLSBiWzBdWzBdKSwKICAgICAgICAgICAgeCA9ICh3IC0gayAqIChiWzFdWzBdICsgYlswXVswXSkpIC8gMiwKICAgICAgICAgICAgeSA9IC1rICogYlswXVsxXTsKICAgICAgICBwcm9qZWN0aW9uLnNjYWxlKDE1MCAqIGspLnRyYW5zbGF0ZShbeCwgeV0pOwogICAgICB9LCBvYmplY3QpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZpdEhlaWdodChwcm9qZWN0aW9uLCBoZWlnaHQsIG9iamVjdCkgewogICAgICByZXR1cm4gZml0KHByb2plY3Rpb24sIGZ1bmN0aW9uKGIpIHsKICAgICAgICB2YXIgaCA9ICtoZWlnaHQsCiAgICAgICAgICAgIGsgPSBoIC8gKGJbMV1bMV0gLSBiWzBdWzFdKSwKICAgICAgICAgICAgeCA9IC1rICogYlswXVswXSwKICAgICAgICAgICAgeSA9IChoIC0gayAqIChiWzFdWzFdICsgYlswXVsxXSkpIC8gMjsKICAgICAgICBwcm9qZWN0aW9uLnNjYWxlKDE1MCAqIGspLnRyYW5zbGF0ZShbeCwgeV0pOwogICAgICB9LCBvYmplY3QpOwogICAgfQoKICAgIHZhciBtYXhEZXB0aCA9IDE2LCAvLyBtYXhpbXVtIGRlcHRoIG9mIHN1YmRpdmlzaW9uCiAgICAgICAgY29zTWluRGlzdGFuY2UgPSBjb3MkMSgzMCAqIHJhZGlhbnMpOyAvLyBjb3MobWluaW11bSBhbmd1bGFyIGRpc3RhbmNlKQoKICAgIGZ1bmN0aW9uIHJlc2FtcGxlKHByb2plY3QsIGRlbHRhMikgewogICAgICByZXR1cm4gK2RlbHRhMiA/IHJlc2FtcGxlJDEocHJvamVjdCwgZGVsdGEyKSA6IHJlc2FtcGxlTm9uZShwcm9qZWN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXNhbXBsZU5vbmUocHJvamVjdCkgewogICAgICByZXR1cm4gdHJhbnNmb3JtZXIoewogICAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgICB4ID0gcHJvamVjdCh4LCB5KTsKICAgICAgICAgIHRoaXMuc3RyZWFtLnBvaW50KHhbMF0sIHhbMV0pOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVzYW1wbGUkMShwcm9qZWN0LCBkZWx0YTIpIHsKCiAgICAgIGZ1bmN0aW9uIHJlc2FtcGxlTGluZVRvKHgwLCB5MCwgbGFtYmRhMCwgYTAsIGIwLCBjMCwgeDEsIHkxLCBsYW1iZGExLCBhMSwgYjEsIGMxLCBkZXB0aCwgc3RyZWFtKSB7CiAgICAgICAgdmFyIGR4ID0geDEgLSB4MCwKICAgICAgICAgICAgZHkgPSB5MSAtIHkwLAogICAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5OwogICAgICAgIGlmIChkMiA+IDQgKiBkZWx0YTIgJiYgZGVwdGgtLSkgewogICAgICAgICAgdmFyIGEgPSBhMCArIGExLAogICAgICAgICAgICAgIGIgPSBiMCArIGIxLAogICAgICAgICAgICAgIGMgPSBjMCArIGMxLAogICAgICAgICAgICAgIG0gPSBzcXJ0KGEgKiBhICsgYiAqIGIgKyBjICogYyksCiAgICAgICAgICAgICAgcGhpMiA9IGFzaW4oYyAvPSBtKSwKICAgICAgICAgICAgICBsYW1iZGEyID0gYWJzKGFicyhjKSAtIDEpIDwgZXBzaWxvbiQyIHx8IGFicyhsYW1iZGEwIC0gbGFtYmRhMSkgPCBlcHNpbG9uJDIgPyAobGFtYmRhMCArIGxhbWJkYTEpIC8gMiA6IGF0YW4yKGIsIGEpLAogICAgICAgICAgICAgIHAgPSBwcm9qZWN0KGxhbWJkYTIsIHBoaTIpLAogICAgICAgICAgICAgIHgyID0gcFswXSwKICAgICAgICAgICAgICB5MiA9IHBbMV0sCiAgICAgICAgICAgICAgZHgyID0geDIgLSB4MCwKICAgICAgICAgICAgICBkeTIgPSB5MiAtIHkwLAogICAgICAgICAgICAgIGR6ID0gZHkgKiBkeDIgLSBkeCAqIGR5MjsKICAgICAgICAgIGlmIChkeiAqIGR6IC8gZDIgPiBkZWx0YTIgLy8gcGVycGVuZGljdWxhciBwcm9qZWN0ZWQgZGlzdGFuY2UKICAgICAgICAgICAgICB8fCBhYnMoKGR4ICogZHgyICsgZHkgKiBkeTIpIC8gZDIgLSAwLjUpID4gMC4zIC8vIG1pZHBvaW50IGNsb3NlIHRvIGFuIGVuZAogICAgICAgICAgICAgIHx8IGEwICogYTEgKyBiMCAqIGIxICsgYzAgKiBjMSA8IGNvc01pbkRpc3RhbmNlKSB7IC8vIGFuZ3VsYXIgZGlzdGFuY2UKICAgICAgICAgICAgcmVzYW1wbGVMaW5lVG8oeDAsIHkwLCBsYW1iZGEwLCBhMCwgYjAsIGMwLCB4MiwgeTIsIGxhbWJkYTIsIGEgLz0gbSwgYiAvPSBtLCBjLCBkZXB0aCwgc3RyZWFtKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHgyLCB5Mik7CiAgICAgICAgICAgIHJlc2FtcGxlTGluZVRvKHgyLCB5MiwgbGFtYmRhMiwgYSwgYiwgYywgeDEsIHkxLCBsYW1iZGExLCBhMSwgYjEsIGMxLCBkZXB0aCwgc3RyZWFtKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHZhciBsYW1iZGEwMCwgeDAwLCB5MDAsIGEwMCwgYjAwLCBjMDAsIC8vIGZpcnN0IHBvaW50CiAgICAgICAgICAgIGxhbWJkYTAsIHgwLCB5MCwgYTAsIGIwLCBjMDsgLy8gcHJldmlvdXMgcG9pbnQKCiAgICAgICAgdmFyIHJlc2FtcGxlU3RyZWFtID0gewogICAgICAgICAgcG9pbnQ6IHBvaW50LAogICAgICAgICAgbGluZVN0YXJ0OiBsaW5lU3RhcnQsCiAgICAgICAgICBsaW5lRW5kOiBsaW5lRW5kLAogICAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsgc3RyZWFtLnBvbHlnb25TdGFydCgpOyByZXNhbXBsZVN0cmVhbS5saW5lU3RhcnQgPSByaW5nU3RhcnQ7IH0sCiAgICAgICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsgc3RyZWFtLnBvbHlnb25FbmQoKTsgcmVzYW1wbGVTdHJlYW0ubGluZVN0YXJ0ID0gbGluZVN0YXJ0OyB9CiAgICAgICAgfTsKCiAgICAgICAgZnVuY3Rpb24gcG9pbnQoeCwgeSkgewogICAgICAgICAgeCA9IHByb2plY3QoeCwgeSk7CiAgICAgICAgICBzdHJlYW0ucG9pbnQoeFswXSwgeFsxXSk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBsaW5lU3RhcnQoKSB7CiAgICAgICAgICB4MCA9IE5hTjsKICAgICAgICAgIHJlc2FtcGxlU3RyZWFtLnBvaW50ID0gbGluZVBvaW50OwogICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbGluZVBvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICB2YXIgYyA9IGNhcnRlc2lhbihbbGFtYmRhLCBwaGldKSwgcCA9IHByb2plY3QobGFtYmRhLCBwaGkpOwogICAgICAgICAgcmVzYW1wbGVMaW5lVG8oeDAsIHkwLCBsYW1iZGEwLCBhMCwgYjAsIGMwLCB4MCA9IHBbMF0sIHkwID0gcFsxXSwgbGFtYmRhMCA9IGxhbWJkYSwgYTAgPSBjWzBdLCBiMCA9IGNbMV0sIGMwID0gY1syXSwgbWF4RGVwdGgsIHN0cmVhbSk7CiAgICAgICAgICBzdHJlYW0ucG9pbnQoeDAsIHkwKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGxpbmVFbmQoKSB7CiAgICAgICAgICByZXNhbXBsZVN0cmVhbS5wb2ludCA9IHBvaW50OwogICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHJpbmdTdGFydCgpIHsKICAgICAgICAgIGxpbmVTdGFydCgpOwogICAgICAgICAgcmVzYW1wbGVTdHJlYW0ucG9pbnQgPSByaW5nUG9pbnQ7CiAgICAgICAgICByZXNhbXBsZVN0cmVhbS5saW5lRW5kID0gcmluZ0VuZDsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHJpbmdQb2ludChsYW1iZGEsIHBoaSkgewogICAgICAgICAgbGluZVBvaW50KGxhbWJkYTAwID0gbGFtYmRhLCBwaGkpLCB4MDAgPSB4MCwgeTAwID0geTAsIGEwMCA9IGEwLCBiMDAgPSBiMCwgYzAwID0gYzA7CiAgICAgICAgICByZXNhbXBsZVN0cmVhbS5wb2ludCA9IGxpbmVQb2ludDsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHJpbmdFbmQoKSB7CiAgICAgICAgICByZXNhbXBsZUxpbmVUbyh4MCwgeTAsIGxhbWJkYTAsIGEwLCBiMCwgYzAsIHgwMCwgeTAwLCBsYW1iZGEwMCwgYTAwLCBiMDAsIGMwMCwgbWF4RGVwdGgsIHN0cmVhbSk7CiAgICAgICAgICByZXNhbXBsZVN0cmVhbS5saW5lRW5kID0gbGluZUVuZDsKICAgICAgICAgIGxpbmVFbmQoKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiByZXNhbXBsZVN0cmVhbTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgdHJhbnNmb3JtUmFkaWFucyA9IHRyYW5zZm9ybWVyKHsKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB0aGlzLnN0cmVhbS5wb2ludCh4ICogcmFkaWFucywgeSAqIHJhZGlhbnMpOwogICAgICB9CiAgICB9KTsKCiAgICBmdW5jdGlvbiB0cmFuc2Zvcm1Sb3RhdGUocm90YXRlKSB7CiAgICAgIHJldHVybiB0cmFuc2Zvcm1lcih7CiAgICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICAgIHZhciByID0gcm90YXRlKHgsIHkpOwogICAgICAgICAgcmV0dXJuIHRoaXMuc3RyZWFtLnBvaW50KHJbMF0sIHJbMV0pOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2NhbGVUcmFuc2xhdGUoaywgZHgsIGR5LCBzeCwgc3kpIHsKICAgICAgZnVuY3Rpb24gdHJhbnNmb3JtKHgsIHkpIHsKICAgICAgICB4ICo9IHN4OyB5ICo9IHN5OwogICAgICAgIHJldHVybiBbZHggKyBrICogeCwgZHkgLSBrICogeV07CiAgICAgIH0KICAgICAgdHJhbnNmb3JtLmludmVydCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICByZXR1cm4gWyh4IC0gZHgpIC8gayAqIHN4LCAoZHkgLSB5KSAvIGsgKiBzeV07CiAgICAgIH07CiAgICAgIHJldHVybiB0cmFuc2Zvcm07CiAgICB9CgogICAgZnVuY3Rpb24gc2NhbGVUcmFuc2xhdGVSb3RhdGUoaywgZHgsIGR5LCBzeCwgc3ksIGFscGhhKSB7CiAgICAgIHZhciBjb3NBbHBoYSA9IGNvcyQxKGFscGhhKSwKICAgICAgICAgIHNpbkFscGhhID0gc2luJDEoYWxwaGEpLAogICAgICAgICAgYSA9IGNvc0FscGhhICogaywKICAgICAgICAgIGIgPSBzaW5BbHBoYSAqIGssCiAgICAgICAgICBhaSA9IGNvc0FscGhhIC8gaywKICAgICAgICAgIGJpID0gc2luQWxwaGEgLyBrLAogICAgICAgICAgY2kgPSAoc2luQWxwaGEgKiBkeSAtIGNvc0FscGhhICogZHgpIC8gaywKICAgICAgICAgIGZpID0gKHNpbkFscGhhICogZHggKyBjb3NBbHBoYSAqIGR5KSAvIGs7CiAgICAgIGZ1bmN0aW9uIHRyYW5zZm9ybSh4LCB5KSB7CiAgICAgICAgeCAqPSBzeDsgeSAqPSBzeTsKICAgICAgICByZXR1cm4gW2EgKiB4IC0gYiAqIHkgKyBkeCwgZHkgLSBiICogeCAtIGEgKiB5XTsKICAgICAgfQogICAgICB0cmFuc2Zvcm0uaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHJldHVybiBbc3ggKiAoYWkgKiB4IC0gYmkgKiB5ICsgY2kpLCBzeSAqIChmaSAtIGJpICogeCAtIGFpICogeSldOwogICAgICB9OwogICAgICByZXR1cm4gdHJhbnNmb3JtOwogICAgfQoKICAgIGZ1bmN0aW9uIHByb2plY3Rpb24ocHJvamVjdCkgewogICAgICByZXR1cm4gcHJvamVjdGlvbk11dGF0b3IoZnVuY3Rpb24oKSB7IHJldHVybiBwcm9qZWN0OyB9KSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByb2plY3Rpb25NdXRhdG9yKHByb2plY3RBdCkgewogICAgICB2YXIgcHJvamVjdCwKICAgICAgICAgIGsgPSAxNTAsIC8vIHNjYWxlCiAgICAgICAgICB4ID0gNDgwLCB5ID0gMjUwLCAvLyB0cmFuc2xhdGUKICAgICAgICAgIGxhbWJkYSA9IDAsIHBoaSA9IDAsIC8vIGNlbnRlcgogICAgICAgICAgZGVsdGFMYW1iZGEgPSAwLCBkZWx0YVBoaSA9IDAsIGRlbHRhR2FtbWEgPSAwLCByb3RhdGUsIC8vIHByZS1yb3RhdGUKICAgICAgICAgIGFscGhhID0gMCwgLy8gcG9zdC1yb3RhdGUgYW5nbGUKICAgICAgICAgIHN4ID0gMSwgLy8gcmVmbGVjdFgKICAgICAgICAgIHN5ID0gMSwgLy8gcmVmbGVjdFgKICAgICAgICAgIHRoZXRhID0gbnVsbCwgcHJlY2xpcCA9IGNsaXBBbnRpbWVyaWRpYW4sIC8vIHByZS1jbGlwIGFuZ2xlCiAgICAgICAgICB4MCA9IG51bGwsIHkwLCB4MSwgeTEsIHBvc3RjbGlwID0gaWRlbnRpdHkkNCwgLy8gcG9zdC1jbGlwIGV4dGVudAogICAgICAgICAgZGVsdGEyID0gMC41LCAvLyBwcmVjaXNpb24KICAgICAgICAgIHByb2plY3RSZXNhbXBsZSwKICAgICAgICAgIHByb2plY3RUcmFuc2Zvcm0sCiAgICAgICAgICBwcm9qZWN0Um90YXRlVHJhbnNmb3JtLAogICAgICAgICAgY2FjaGUsCiAgICAgICAgICBjYWNoZVN0cmVhbTsKCiAgICAgIGZ1bmN0aW9uIHByb2plY3Rpb24ocG9pbnQpIHsKICAgICAgICByZXR1cm4gcHJvamVjdFJvdGF0ZVRyYW5zZm9ybShwb2ludFswXSAqIHJhZGlhbnMsIHBvaW50WzFdICogcmFkaWFucyk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGludmVydChwb2ludCkgewogICAgICAgIHBvaW50ID0gcHJvamVjdFJvdGF0ZVRyYW5zZm9ybS5pbnZlcnQocG9pbnRbMF0sIHBvaW50WzFdKTsKICAgICAgICByZXR1cm4gcG9pbnQgJiYgW3BvaW50WzBdICogZGVncmVlcyQxLCBwb2ludFsxXSAqIGRlZ3JlZXMkMV07CiAgICAgIH0KCiAgICAgIHByb2plY3Rpb24uc3RyZWFtID0gZnVuY3Rpb24oc3RyZWFtKSB7CiAgICAgICAgcmV0dXJuIGNhY2hlICYmIGNhY2hlU3RyZWFtID09PSBzdHJlYW0gPyBjYWNoZSA6IGNhY2hlID0gdHJhbnNmb3JtUmFkaWFucyh0cmFuc2Zvcm1Sb3RhdGUocm90YXRlKShwcmVjbGlwKHByb2plY3RSZXNhbXBsZShwb3N0Y2xpcChjYWNoZVN0cmVhbSA9IHN0cmVhbSkpKSkpOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5wcmVjbGlwID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHByZWNsaXAgPSBfLCB0aGV0YSA9IHVuZGVmaW5lZCwgcmVzZXQoKSkgOiBwcmVjbGlwOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5wb3N0Y2xpcCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwb3N0Y2xpcCA9IF8sIHgwID0geTAgPSB4MSA9IHkxID0gbnVsbCwgcmVzZXQoKSkgOiBwb3N0Y2xpcDsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uY2xpcEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHByZWNsaXAgPSArXyA/IGNsaXBDaXJjbGUodGhldGEgPSBfICogcmFkaWFucykgOiAodGhldGEgPSBudWxsLCBjbGlwQW50aW1lcmlkaWFuKSwgcmVzZXQoKSkgOiB0aGV0YSAqIGRlZ3JlZXMkMTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uY2xpcEV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwb3N0Y2xpcCA9IF8gPT0gbnVsbCA/ICh4MCA9IHkwID0geDEgPSB5MSA9IG51bGwsIGlkZW50aXR5JDQpIDogY2xpcFJlY3RhbmdsZSh4MCA9ICtfWzBdWzBdLCB5MCA9ICtfWzBdWzFdLCB4MSA9ICtfWzFdWzBdLCB5MSA9ICtfWzFdWzFdKSwgcmVzZXQoKSkgOiB4MCA9PSBudWxsID8gbnVsbCA6IFtbeDAsIHkwXSwgW3gxLCB5MV1dOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5zY2FsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChrID0gK18sIHJlY2VudGVyKCkpIDogazsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24udHJhbnNsYXRlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHggPSArX1swXSwgeSA9ICtfWzFdLCByZWNlbnRlcigpKSA6IFt4LCB5XTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uY2VudGVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGxhbWJkYSA9IF9bMF0gJSAzNjAgKiByYWRpYW5zLCBwaGkgPSBfWzFdICUgMzYwICogcmFkaWFucywgcmVjZW50ZXIoKSkgOiBbbGFtYmRhICogZGVncmVlcyQxLCBwaGkgKiBkZWdyZWVzJDFdOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5yb3RhdGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGVsdGFMYW1iZGEgPSBfWzBdICUgMzYwICogcmFkaWFucywgZGVsdGFQaGkgPSBfWzFdICUgMzYwICogcmFkaWFucywgZGVsdGFHYW1tYSA9IF8ubGVuZ3RoID4gMiA/IF9bMl0gJSAzNjAgKiByYWRpYW5zIDogMCwgcmVjZW50ZXIoKSkgOiBbZGVsdGFMYW1iZGEgKiBkZWdyZWVzJDEsIGRlbHRhUGhpICogZGVncmVlcyQxLCBkZWx0YUdhbW1hICogZGVncmVlcyQxXTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uYW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoYWxwaGEgPSBfICUgMzYwICogcmFkaWFucywgcmVjZW50ZXIoKSkgOiBhbHBoYSAqIGRlZ3JlZXMkMTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24ucmVmbGVjdFggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3ggPSBfID8gLTEgOiAxLCByZWNlbnRlcigpKSA6IHN4IDwgMDsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24ucmVmbGVjdFkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3kgPSBfID8gLTEgOiAxLCByZWNlbnRlcigpKSA6IHN5IDwgMDsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24ucHJlY2lzaW9uID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHByb2plY3RSZXNhbXBsZSA9IHJlc2FtcGxlKHByb2plY3RUcmFuc2Zvcm0sIGRlbHRhMiA9IF8gKiBfKSwgcmVzZXQoKSkgOiBzcXJ0KGRlbHRhMik7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmZpdEV4dGVudCA9IGZ1bmN0aW9uKGV4dGVudCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEV4dGVudChwcm9qZWN0aW9uLCBleHRlbnQsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmZpdFNpemUgPSBmdW5jdGlvbihzaXplLCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0U2l6ZShwcm9qZWN0aW9uLCBzaXplLCBvYmplY3QpOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5maXRXaWR0aCA9IGZ1bmN0aW9uKHdpZHRoLCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0V2lkdGgocHJvamVjdGlvbiwgd2lkdGgsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmZpdEhlaWdodCA9IGZ1bmN0aW9uKGhlaWdodCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEhlaWdodChwcm9qZWN0aW9uLCBoZWlnaHQsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBmdW5jdGlvbiByZWNlbnRlcigpIHsKICAgICAgICB2YXIgY2VudGVyID0gc2NhbGVUcmFuc2xhdGVSb3RhdGUoaywgMCwgMCwgc3gsIHN5LCBhbHBoYSkuYXBwbHkobnVsbCwgcHJvamVjdChsYW1iZGEsIHBoaSkpLAogICAgICAgICAgICB0cmFuc2Zvcm0gPSAoYWxwaGEgPyBzY2FsZVRyYW5zbGF0ZVJvdGF0ZSA6IHNjYWxlVHJhbnNsYXRlKShrLCB4IC0gY2VudGVyWzBdLCB5IC0gY2VudGVyWzFdLCBzeCwgc3ksIGFscGhhKTsKICAgICAgICByb3RhdGUgPSByb3RhdGVSYWRpYW5zKGRlbHRhTGFtYmRhLCBkZWx0YVBoaSwgZGVsdGFHYW1tYSk7CiAgICAgICAgcHJvamVjdFRyYW5zZm9ybSA9IGNvbXBvc2UocHJvamVjdCwgdHJhbnNmb3JtKTsKICAgICAgICBwcm9qZWN0Um90YXRlVHJhbnNmb3JtID0gY29tcG9zZShyb3RhdGUsIHByb2plY3RUcmFuc2Zvcm0pOwogICAgICAgIHByb2plY3RSZXNhbXBsZSA9IHJlc2FtcGxlKHByb2plY3RUcmFuc2Zvcm0sIGRlbHRhMik7CiAgICAgICAgcmV0dXJuIHJlc2V0KCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHJlc2V0KCkgewogICAgICAgIGNhY2hlID0gY2FjaGVTdHJlYW0gPSBudWxsOwogICAgICAgIHJldHVybiBwcm9qZWN0aW9uOwogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcHJvamVjdCA9IHByb2plY3RBdC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHByb2plY3Rpb24uaW52ZXJ0ID0gcHJvamVjdC5pbnZlcnQgJiYgaW52ZXJ0OwogICAgICAgIHJldHVybiByZWNlbnRlcigpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljUHJvamVjdGlvbihwcm9qZWN0QXQpIHsKICAgICAgdmFyIHBoaTAgPSAwLAogICAgICAgICAgcGhpMSA9IHBpJDMgLyAzLAogICAgICAgICAgbSA9IHByb2plY3Rpb25NdXRhdG9yKHByb2plY3RBdCksCiAgICAgICAgICBwID0gbShwaGkwLCBwaGkxKTsKCiAgICAgIHAucGFyYWxsZWxzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gbShwaGkwID0gX1swXSAqIHJhZGlhbnMsIHBoaTEgPSBfWzFdICogcmFkaWFucykgOiBbcGhpMCAqIGRlZ3JlZXMkMSwgcGhpMSAqIGRlZ3JlZXMkMV07CiAgICAgIH07CgogICAgICByZXR1cm4gcDsKICAgIH0KCiAgICBmdW5jdGlvbiBjeWxpbmRyaWNhbEVxdWFsQXJlYVJhdyhwaGkwKSB7CiAgICAgIHZhciBjb3NQaGkwID0gY29zJDEocGhpMCk7CgogICAgICBmdW5jdGlvbiBmb3J3YXJkKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgcmV0dXJuIFtsYW1iZGEgKiBjb3NQaGkwLCBzaW4kMShwaGkpIC8gY29zUGhpMF07CiAgICAgIH0KCiAgICAgIGZvcndhcmQuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHJldHVybiBbeCAvIGNvc1BoaTAsIGFzaW4oeSAqIGNvc1BoaTApXTsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3J3YXJkOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljRXF1YWxBcmVhUmF3KHkwLCB5MSkgewogICAgICB2YXIgc3kwID0gc2luJDEoeTApLCBuID0gKHN5MCArIHNpbiQxKHkxKSkgLyAyOwoKICAgICAgLy8gQXJlIHRoZSBwYXJhbGxlbHMgc3ltbWV0cmljYWwgYXJvdW5kIHRoZSBFcXVhdG9yPwogICAgICBpZiAoYWJzKG4pIDwgZXBzaWxvbiQyKSByZXR1cm4gY3lsaW5kcmljYWxFcXVhbEFyZWFSYXcoeTApOwoKICAgICAgdmFyIGMgPSAxICsgc3kwICogKDIgKiBuIC0gc3kwKSwgcjAgPSBzcXJ0KGMpIC8gbjsKCiAgICAgIGZ1bmN0aW9uIHByb2plY3QoeCwgeSkgewogICAgICAgIHZhciByID0gc3FydChjIC0gMiAqIG4gKiBzaW4kMSh5KSkgLyBuOwogICAgICAgIHJldHVybiBbciAqIHNpbiQxKHggKj0gbiksIHIwIC0gciAqIGNvcyQxKHgpXTsKICAgICAgfQoKICAgICAgcHJvamVjdC5pbnZlcnQgPSBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdmFyIHIweSA9IHIwIC0geSwKICAgICAgICAgICAgbCA9IGF0YW4yKHgsIGFicyhyMHkpKSAqIHNpZ24ocjB5KTsKICAgICAgICBpZiAocjB5ICogbiA8IDApCiAgICAgICAgICBsIC09IHBpJDMgKiBzaWduKHgpICogc2lnbihyMHkpOwogICAgICAgIHJldHVybiBbbCAvIG4sIGFzaW4oKGMgLSAoeCAqIHggKyByMHkgKiByMHkpICogbiAqIG4pIC8gKDIgKiBuKSldOwogICAgICB9OwoKICAgICAgcmV0dXJuIHByb2plY3Q7CiAgICB9CgogICAgZnVuY3Rpb24gY29uaWNFcXVhbEFyZWEoKSB7CiAgICAgIHJldHVybiBjb25pY1Byb2plY3Rpb24oY29uaWNFcXVhbEFyZWFSYXcpCiAgICAgICAgICAuc2NhbGUoMTU1LjQyNCkKICAgICAgICAgIC5jZW50ZXIoWzAsIDMzLjY0NDJdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhbGJlcnMoKSB7CiAgICAgIHJldHVybiBjb25pY0VxdWFsQXJlYSgpCiAgICAgICAgICAucGFyYWxsZWxzKFsyOS41LCA0NS41XSkKICAgICAgICAgIC5zY2FsZSgxMDcwKQogICAgICAgICAgLnRyYW5zbGF0ZShbNDgwLCAyNTBdKQogICAgICAgICAgLnJvdGF0ZShbOTYsIDBdKQogICAgICAgICAgLmNlbnRlcihbLTAuNiwgMzguN10pOwogICAgfQoKICAgIC8vIFRoZSBwcm9qZWN0aW9ucyBtdXN0IGhhdmUgbXV0dWFsbHkgZXhjbHVzaXZlIGNsaXAgcmVnaW9ucyBvbiB0aGUgc3BoZXJlLAogICAgLy8gYXMgdGhpcyB3aWxsIGF2b2lkIGVtaXR0aW5nIGludGVybGVhdmluZyBsaW5lcyBhbmQgcG9seWdvbnMuCiAgICBmdW5jdGlvbiBtdWx0aXBsZXgoc3RyZWFtcykgewogICAgICB2YXIgbiA9IHN0cmVhbXMubGVuZ3RoOwogICAgICByZXR1cm4gewogICAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnBvaW50KHgsIHkpOyB9LAogICAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnNwaGVyZSgpOyB9LAogICAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLmxpbmVTdGFydCgpOyB9LAogICAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgeyB2YXIgaSA9IC0xOyB3aGlsZSAoKytpIDwgbikgc3RyZWFtc1tpXS5saW5lRW5kKCk7IH0sCiAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsgdmFyIGkgPSAtMTsgd2hpbGUgKCsraSA8IG4pIHN0cmVhbXNbaV0ucG9seWdvblN0YXJ0KCk7IH0sCiAgICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnBvbHlnb25FbmQoKTsgfQogICAgICB9OwogICAgfQoKICAgIC8vIEEgY29tcG9zaXRlIHByb2plY3Rpb24gZm9yIHRoZSBVbml0ZWQgU3RhdGVzLCBjb25maWd1cmVkIGJ5IGRlZmF1bHQgZm9yCiAgICAvLyA5NjDDlzUwMC4gVGhlIHByb2plY3Rpb24gYWxzbyB3b3JrcyBxdWl0ZSB3ZWxsIGF0IDk2MMOXNjAwIGlmIHlvdSBjaGFuZ2UgdGhlCiAgICAvLyBzY2FsZSB0byAxMjg1IGFuZCBhZGp1c3QgdGhlIHRyYW5zbGF0ZSBhY2NvcmRpbmdseS4gVGhlIHNldCBvZiBzdGFuZGFyZAogICAgLy8gcGFyYWxsZWxzIGZvciBlYWNoIHJlZ2lvbiBjb21lcyBmcm9tIFVTR1MsIHdoaWNoIGlzIHB1Ymxpc2hlZCBoZXJlOgogICAgLy8gaHR0cDovL2Vnc2MudXNncy5nb3YvaXNiL3B1YnMvTWFwUHJvamVjdGlvbnMvcHJvamVjdGlvbnMuaHRtbCNhbGJlcnMKICAgIGZ1bmN0aW9uIGFsYmVyc1VzYSgpIHsKICAgICAgdmFyIGNhY2hlLAogICAgICAgICAgY2FjaGVTdHJlYW0sCiAgICAgICAgICBsb3dlcjQ4ID0gYWxiZXJzKCksIGxvd2VyNDhQb2ludCwKICAgICAgICAgIGFsYXNrYSA9IGNvbmljRXF1YWxBcmVhKCkucm90YXRlKFsxNTQsIDBdKS5jZW50ZXIoWy0yLCA1OC41XSkucGFyYWxsZWxzKFs1NSwgNjVdKSwgYWxhc2thUG9pbnQsIC8vIEVQU0c6MzMzOAogICAgICAgICAgaGF3YWlpID0gY29uaWNFcXVhbEFyZWEoKS5yb3RhdGUoWzE1NywgMF0pLmNlbnRlcihbLTMsIDE5LjldKS5wYXJhbGxlbHMoWzgsIDE4XSksIGhhd2FpaVBvaW50LCAvLyBFU1JJOjEwMjAwNwogICAgICAgICAgcG9pbnQsIHBvaW50U3RyZWFtID0ge3BvaW50OiBmdW5jdGlvbih4LCB5KSB7IHBvaW50ID0gW3gsIHldOyB9fTsKCiAgICAgIGZ1bmN0aW9uIGFsYmVyc1VzYShjb29yZGluYXRlcykgewogICAgICAgIHZhciB4ID0gY29vcmRpbmF0ZXNbMF0sIHkgPSBjb29yZGluYXRlc1sxXTsKICAgICAgICByZXR1cm4gcG9pbnQgPSBudWxsLAogICAgICAgICAgICAobG93ZXI0OFBvaW50LnBvaW50KHgsIHkpLCBwb2ludCkKICAgICAgICAgICAgfHwgKGFsYXNrYVBvaW50LnBvaW50KHgsIHkpLCBwb2ludCkKICAgICAgICAgICAgfHwgKGhhd2FpaVBvaW50LnBvaW50KHgsIHkpLCBwb2ludCk7CiAgICAgIH0KCiAgICAgIGFsYmVyc1VzYS5pbnZlcnQgPSBmdW5jdGlvbihjb29yZGluYXRlcykgewogICAgICAgIHZhciBrID0gbG93ZXI0OC5zY2FsZSgpLAogICAgICAgICAgICB0ID0gbG93ZXI0OC50cmFuc2xhdGUoKSwKICAgICAgICAgICAgeCA9IChjb29yZGluYXRlc1swXSAtIHRbMF0pIC8gaywKICAgICAgICAgICAgeSA9IChjb29yZGluYXRlc1sxXSAtIHRbMV0pIC8gazsKICAgICAgICByZXR1cm4gKHkgPj0gMC4xMjAgJiYgeSA8IDAuMjM0ICYmIHggPj0gLTAuNDI1ICYmIHggPCAtMC4yMTQgPyBhbGFza2EKICAgICAgICAgICAgOiB5ID49IDAuMTY2ICYmIHkgPCAwLjIzNCAmJiB4ID49IC0wLjIxNCAmJiB4IDwgLTAuMTE1ID8gaGF3YWlpCiAgICAgICAgICAgIDogbG93ZXI0OCkuaW52ZXJ0KGNvb3JkaW5hdGVzKTsKICAgICAgfTsKCiAgICAgIGFsYmVyc1VzYS5zdHJlYW0gPSBmdW5jdGlvbihzdHJlYW0pIHsKICAgICAgICByZXR1cm4gY2FjaGUgJiYgY2FjaGVTdHJlYW0gPT09IHN0cmVhbSA/IGNhY2hlIDogY2FjaGUgPSBtdWx0aXBsZXgoW2xvd2VyNDguc3RyZWFtKGNhY2hlU3RyZWFtID0gc3RyZWFtKSwgYWxhc2thLnN0cmVhbShzdHJlYW0pLCBoYXdhaWkuc3RyZWFtKHN0cmVhbSldKTsKICAgICAgfTsKCiAgICAgIGFsYmVyc1VzYS5wcmVjaXNpb24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gbG93ZXI0OC5wcmVjaXNpb24oKTsKICAgICAgICBsb3dlcjQ4LnByZWNpc2lvbihfKSwgYWxhc2thLnByZWNpc2lvbihfKSwgaGF3YWlpLnByZWNpc2lvbihfKTsKICAgICAgICByZXR1cm4gcmVzZXQoKTsKICAgICAgfTsKCiAgICAgIGFsYmVyc1VzYS5zY2FsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBsb3dlcjQ4LnNjYWxlKCk7CiAgICAgICAgbG93ZXI0OC5zY2FsZShfKSwgYWxhc2thLnNjYWxlKF8gKiAwLjM1KSwgaGF3YWlpLnNjYWxlKF8pOwogICAgICAgIHJldHVybiBhbGJlcnNVc2EudHJhbnNsYXRlKGxvd2VyNDgudHJhbnNsYXRlKCkpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLnRyYW5zbGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBsb3dlcjQ4LnRyYW5zbGF0ZSgpOwogICAgICAgIHZhciBrID0gbG93ZXI0OC5zY2FsZSgpLCB4ID0gK19bMF0sIHkgPSArX1sxXTsKCiAgICAgICAgbG93ZXI0OFBvaW50ID0gbG93ZXI0OAogICAgICAgICAgICAudHJhbnNsYXRlKF8pCiAgICAgICAgICAgIC5jbGlwRXh0ZW50KFtbeCAtIDAuNDU1ICogaywgeSAtIDAuMjM4ICoga10sIFt4ICsgMC40NTUgKiBrLCB5ICsgMC4yMzggKiBrXV0pCiAgICAgICAgICAgIC5zdHJlYW0ocG9pbnRTdHJlYW0pOwoKICAgICAgICBhbGFza2FQb2ludCA9IGFsYXNrYQogICAgICAgICAgICAudHJhbnNsYXRlKFt4IC0gMC4zMDcgKiBrLCB5ICsgMC4yMDEgKiBrXSkKICAgICAgICAgICAgLmNsaXBFeHRlbnQoW1t4IC0gMC40MjUgKiBrICsgZXBzaWxvbiQyLCB5ICsgMC4xMjAgKiBrICsgZXBzaWxvbiQyXSwgW3ggLSAwLjIxNCAqIGsgLSBlcHNpbG9uJDIsIHkgKyAwLjIzNCAqIGsgLSBlcHNpbG9uJDJdXSkKICAgICAgICAgICAgLnN0cmVhbShwb2ludFN0cmVhbSk7CgogICAgICAgIGhhd2FpaVBvaW50ID0gaGF3YWlpCiAgICAgICAgICAgIC50cmFuc2xhdGUoW3ggLSAwLjIwNSAqIGssIHkgKyAwLjIxMiAqIGtdKQogICAgICAgICAgICAuY2xpcEV4dGVudChbW3ggLSAwLjIxNCAqIGsgKyBlcHNpbG9uJDIsIHkgKyAwLjE2NiAqIGsgKyBlcHNpbG9uJDJdLCBbeCAtIDAuMTE1ICogayAtIGVwc2lsb24kMiwgeSArIDAuMjM0ICogayAtIGVwc2lsb24kMl1dKQogICAgICAgICAgICAuc3RyZWFtKHBvaW50U3RyZWFtKTsKCiAgICAgICAgcmV0dXJuIHJlc2V0KCk7CiAgICAgIH07CgogICAgICBhbGJlcnNVc2EuZml0RXh0ZW50ID0gZnVuY3Rpb24oZXh0ZW50LCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0RXh0ZW50KGFsYmVyc1VzYSwgZXh0ZW50LCBvYmplY3QpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLmZpdFNpemUgPSBmdW5jdGlvbihzaXplLCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0U2l6ZShhbGJlcnNVc2EsIHNpemUsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBhbGJlcnNVc2EuZml0V2lkdGggPSBmdW5jdGlvbih3aWR0aCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdFdpZHRoKGFsYmVyc1VzYSwgd2lkdGgsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBhbGJlcnNVc2EuZml0SGVpZ2h0ID0gZnVuY3Rpb24oaGVpZ2h0LCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0SGVpZ2h0KGFsYmVyc1VzYSwgaGVpZ2h0LCBvYmplY3QpOwogICAgICB9OwoKICAgICAgZnVuY3Rpb24gcmVzZXQoKSB7CiAgICAgICAgY2FjaGUgPSBjYWNoZVN0cmVhbSA9IG51bGw7CiAgICAgICAgcmV0dXJuIGFsYmVyc1VzYTsKICAgICAgfQoKICAgICAgcmV0dXJuIGFsYmVyc1VzYS5zY2FsZSgxMDcwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhemltdXRoYWxSYXcoc2NhbGUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB2YXIgY3ggPSBjb3MkMSh4KSwKICAgICAgICAgICAgY3kgPSBjb3MkMSh5KSwKICAgICAgICAgICAgayA9IHNjYWxlKGN4ICogY3kpOwogICAgICAgIHJldHVybiBbCiAgICAgICAgICBrICogY3kgKiBzaW4kMSh4KSwKICAgICAgICAgIGsgKiBzaW4kMSh5KQogICAgICAgIF07CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBhemltdXRoYWxJbnZlcnQoYW5nbGUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB2YXIgeiA9IHNxcnQoeCAqIHggKyB5ICogeSksCiAgICAgICAgICAgIGMgPSBhbmdsZSh6KSwKICAgICAgICAgICAgc2MgPSBzaW4kMShjKSwKICAgICAgICAgICAgY2MgPSBjb3MkMShjKTsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgYXRhbjIoeCAqIHNjLCB6ICogY2MpLAogICAgICAgICAgYXNpbih6ICYmIHkgKiBzYyAvIHopCiAgICAgICAgXTsKICAgICAgfQogICAgfQoKICAgIHZhciBhemltdXRoYWxFcXVhbEFyZWFSYXcgPSBhemltdXRoYWxSYXcoZnVuY3Rpb24oY3hjeSkgewogICAgICByZXR1cm4gc3FydCgyIC8gKDEgKyBjeGN5KSk7CiAgICB9KTsKCiAgICBhemltdXRoYWxFcXVhbEFyZWFSYXcuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0KGZ1bmN0aW9uKHopIHsKICAgICAgcmV0dXJuIDIgKiBhc2luKHogLyAyKTsKICAgIH0pOwoKICAgIGZ1bmN0aW9uIGF6aW11dGhhbEVxdWFsQXJlYSgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24oYXppbXV0aGFsRXF1YWxBcmVhUmF3KQogICAgICAgICAgLnNjYWxlKDEyNC43NSkKICAgICAgICAgIC5jbGlwQW5nbGUoMTgwIC0gMWUtMyk7CiAgICB9CgogICAgdmFyIGF6aW11dGhhbEVxdWlkaXN0YW50UmF3ID0gYXppbXV0aGFsUmF3KGZ1bmN0aW9uKGMpIHsKICAgICAgcmV0dXJuIChjID0gYWNvcyhjKSkgJiYgYyAvIHNpbiQxKGMpOwogICAgfSk7CgogICAgYXppbXV0aGFsRXF1aWRpc3RhbnRSYXcuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0KGZ1bmN0aW9uKHopIHsKICAgICAgcmV0dXJuIHo7CiAgICB9KTsKCiAgICBmdW5jdGlvbiBhemltdXRoYWxFcXVpZGlzdGFudCgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24oYXppbXV0aGFsRXF1aWRpc3RhbnRSYXcpCiAgICAgICAgICAuc2NhbGUoNzkuNDE4OCkKICAgICAgICAgIC5jbGlwQW5nbGUoMTgwIC0gMWUtMyk7CiAgICB9CgogICAgZnVuY3Rpb24gbWVyY2F0b3JSYXcobGFtYmRhLCBwaGkpIHsKICAgICAgcmV0dXJuIFtsYW1iZGEsIGxvZyh0YW4oKGhhbGZQaSQyICsgcGhpKSAvIDIpKV07CiAgICB9CgogICAgbWVyY2F0b3JSYXcuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICByZXR1cm4gW3gsIDIgKiBhdGFuKGV4cCh5KSkgLSBoYWxmUGkkMl07CiAgICB9OwoKICAgIGZ1bmN0aW9uIG1lcmNhdG9yKCkgewogICAgICByZXR1cm4gbWVyY2F0b3JQcm9qZWN0aW9uKG1lcmNhdG9yUmF3KQogICAgICAgICAgLnNjYWxlKDk2MSAvIHRhdSQzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBtZXJjYXRvclByb2plY3Rpb24ocHJvamVjdCkgewogICAgICB2YXIgbSA9IHByb2plY3Rpb24ocHJvamVjdCksCiAgICAgICAgICBjZW50ZXIgPSBtLmNlbnRlciwKICAgICAgICAgIHNjYWxlID0gbS5zY2FsZSwKICAgICAgICAgIHRyYW5zbGF0ZSA9IG0udHJhbnNsYXRlLAogICAgICAgICAgY2xpcEV4dGVudCA9IG0uY2xpcEV4dGVudCwKICAgICAgICAgIHgwID0gbnVsbCwgeTAsIHgxLCB5MTsgLy8gY2xpcCBleHRlbnQKCiAgICAgIG0uc2NhbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2NhbGUoXyksIHJlY2xpcCgpKSA6IHNjYWxlKCk7CiAgICAgIH07CgogICAgICBtLnRyYW5zbGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0cmFuc2xhdGUoXyksIHJlY2xpcCgpKSA6IHRyYW5zbGF0ZSgpOwogICAgICB9OwoKICAgICAgbS5jZW50ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY2VudGVyKF8pLCByZWNsaXAoKSkgOiBjZW50ZXIoKTsKICAgICAgfTsKCiAgICAgIG0uY2xpcEV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICgoXyA9PSBudWxsID8geDAgPSB5MCA9IHgxID0geTEgPSBudWxsIDogKHgwID0gK19bMF1bMF0sIHkwID0gK19bMF1bMV0sIHgxID0gK19bMV1bMF0sIHkxID0gK19bMV1bMV0pKSwgcmVjbGlwKCkpIDogeDAgPT0gbnVsbCA/IG51bGwgOiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgfTsKCiAgICAgIGZ1bmN0aW9uIHJlY2xpcCgpIHsKICAgICAgICB2YXIgayA9IHBpJDMgKiBzY2FsZSgpLAogICAgICAgICAgICB0ID0gbShyb3RhdGlvbihtLnJvdGF0ZSgpKS5pbnZlcnQoWzAsIDBdKSk7CiAgICAgICAgcmV0dXJuIGNsaXBFeHRlbnQoeDAgPT0gbnVsbAogICAgICAgICAgICA/IFtbdFswXSAtIGssIHRbMV0gLSBrXSwgW3RbMF0gKyBrLCB0WzFdICsga11dIDogcHJvamVjdCA9PT0gbWVyY2F0b3JSYXcKICAgICAgICAgICAgPyBbW01hdGgubWF4KHRbMF0gLSBrLCB4MCksIHkwXSwgW01hdGgubWluKHRbMF0gKyBrLCB4MSksIHkxXV0KICAgICAgICAgICAgOiBbW3gwLCBNYXRoLm1heCh0WzFdIC0gaywgeTApXSwgW3gxLCBNYXRoLm1pbih0WzFdICsgaywgeTEpXV0pOwogICAgICB9CgogICAgICByZXR1cm4gcmVjbGlwKCk7CiAgICB9CgogICAgZnVuY3Rpb24gdGFueSh5KSB7CiAgICAgIHJldHVybiB0YW4oKGhhbGZQaSQyICsgeSkgLyAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25pY0NvbmZvcm1hbFJhdyh5MCwgeTEpIHsKICAgICAgdmFyIGN5MCA9IGNvcyQxKHkwKSwKICAgICAgICAgIG4gPSB5MCA9PT0geTEgPyBzaW4kMSh5MCkgOiBsb2coY3kwIC8gY29zJDEoeTEpKSAvIGxvZyh0YW55KHkxKSAvIHRhbnkoeTApKSwKICAgICAgICAgIGYgPSBjeTAgKiBwb3codGFueSh5MCksIG4pIC8gbjsKCiAgICAgIGlmICghbikgcmV0dXJuIG1lcmNhdG9yUmF3OwoKICAgICAgZnVuY3Rpb24gcHJvamVjdCh4LCB5KSB7CiAgICAgICAgaWYgKGYgPiAwKSB7IGlmICh5IDwgLWhhbGZQaSQyICsgZXBzaWxvbiQyKSB5ID0gLWhhbGZQaSQyICsgZXBzaWxvbiQyOyB9CiAgICAgICAgZWxzZSB7IGlmICh5ID4gaGFsZlBpJDIgLSBlcHNpbG9uJDIpIHkgPSBoYWxmUGkkMiAtIGVwc2lsb24kMjsgfQogICAgICAgIHZhciByID0gZiAvIHBvdyh0YW55KHkpLCBuKTsKICAgICAgICByZXR1cm4gW3IgKiBzaW4kMShuICogeCksIGYgLSByICogY29zJDEobiAqIHgpXTsKICAgICAgfQoKICAgICAgcHJvamVjdC5pbnZlcnQgPSBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdmFyIGZ5ID0gZiAtIHksIHIgPSBzaWduKG4pICogc3FydCh4ICogeCArIGZ5ICogZnkpLAogICAgICAgICAgbCA9IGF0YW4yKHgsIGFicyhmeSkpICogc2lnbihmeSk7CiAgICAgICAgaWYgKGZ5ICogbiA8IDApCiAgICAgICAgICBsIC09IHBpJDMgKiBzaWduKHgpICogc2lnbihmeSk7CiAgICAgICAgcmV0dXJuIFtsIC8gbiwgMiAqIGF0YW4ocG93KGYgLyByLCAxIC8gbikpIC0gaGFsZlBpJDJdOwogICAgICB9OwoKICAgICAgcmV0dXJuIHByb2plY3Q7CiAgICB9CgogICAgZnVuY3Rpb24gY29uaWNDb25mb3JtYWwoKSB7CiAgICAgIHJldHVybiBjb25pY1Byb2plY3Rpb24oY29uaWNDb25mb3JtYWxSYXcpCiAgICAgICAgICAuc2NhbGUoMTA5LjUpCiAgICAgICAgICAucGFyYWxsZWxzKFszMCwgMzBdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBlcXVpcmVjdGFuZ3VsYXJSYXcobGFtYmRhLCBwaGkpIHsKICAgICAgcmV0dXJuIFtsYW1iZGEsIHBoaV07CiAgICB9CgogICAgZXF1aXJlY3Rhbmd1bGFyUmF3LmludmVydCA9IGVxdWlyZWN0YW5ndWxhclJhdzsKCiAgICBmdW5jdGlvbiBlcXVpcmVjdGFuZ3VsYXIoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uKGVxdWlyZWN0YW5ndWxhclJhdykKICAgICAgICAgIC5zY2FsZSgxNTIuNjMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljRXF1aWRpc3RhbnRSYXcoeTAsIHkxKSB7CiAgICAgIHZhciBjeTAgPSBjb3MkMSh5MCksCiAgICAgICAgICBuID0geTAgPT09IHkxID8gc2luJDEoeTApIDogKGN5MCAtIGNvcyQxKHkxKSkgLyAoeTEgLSB5MCksCiAgICAgICAgICBnID0gY3kwIC8gbiArIHkwOwoKICAgICAgaWYgKGFicyhuKSA8IGVwc2lsb24kMikgcmV0dXJuIGVxdWlyZWN0YW5ndWxhclJhdzsKCiAgICAgIGZ1bmN0aW9uIHByb2plY3QoeCwgeSkgewogICAgICAgIHZhciBneSA9IGcgLSB5LCBueCA9IG4gKiB4OwogICAgICAgIHJldHVybiBbZ3kgKiBzaW4kMShueCksIGcgLSBneSAqIGNvcyQxKG54KV07CiAgICAgIH0KCiAgICAgIHByb2plY3QuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciBneSA9IGcgLSB5LAogICAgICAgICAgICBsID0gYXRhbjIoeCwgYWJzKGd5KSkgKiBzaWduKGd5KTsKICAgICAgICBpZiAoZ3kgKiBuIDwgMCkKICAgICAgICAgIGwgLT0gcGkkMyAqIHNpZ24oeCkgKiBzaWduKGd5KTsKICAgICAgICByZXR1cm4gW2wgLyBuLCBnIC0gc2lnbihuKSAqIHNxcnQoeCAqIHggKyBneSAqIGd5KV07CiAgICAgIH07CgogICAgICByZXR1cm4gcHJvamVjdDsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25pY0VxdWlkaXN0YW50KCkgewogICAgICByZXR1cm4gY29uaWNQcm9qZWN0aW9uKGNvbmljRXF1aWRpc3RhbnRSYXcpCiAgICAgICAgICAuc2NhbGUoMTMxLjE1NCkKICAgICAgICAgIC5jZW50ZXIoWzAsIDEzLjkzODldKTsKICAgIH0KCiAgICB2YXIgQTEgPSAxLjM0MDI2NCwKICAgICAgICBBMiA9IC0wLjA4MTEwNiwKICAgICAgICBBMyA9IDAuMDAwODkzLAogICAgICAgIEE0ID0gMC4wMDM3OTYsCiAgICAgICAgTSA9IHNxcnQoMykgLyAyLAogICAgICAgIGl0ZXJhdGlvbnMgPSAxMjsKCiAgICBmdW5jdGlvbiBlcXVhbEVhcnRoUmF3KGxhbWJkYSwgcGhpKSB7CiAgICAgIHZhciBsID0gYXNpbihNICogc2luJDEocGhpKSksIGwyID0gbCAqIGwsIGw2ID0gbDIgKiBsMiAqIGwyOwogICAgICByZXR1cm4gWwogICAgICAgIGxhbWJkYSAqIGNvcyQxKGwpIC8gKE0gKiAoQTEgKyAzICogQTIgKiBsMiArIGw2ICogKDcgKiBBMyArIDkgKiBBNCAqIGwyKSkpLAogICAgICAgIGwgKiAoQTEgKyBBMiAqIGwyICsgbDYgKiAoQTMgKyBBNCAqIGwyKSkKICAgICAgXTsKICAgIH0KCiAgICBlcXVhbEVhcnRoUmF3LmludmVydCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgdmFyIGwgPSB5LCBsMiA9IGwgKiBsLCBsNiA9IGwyICogbDIgKiBsMjsKICAgICAgZm9yICh2YXIgaSA9IDAsIGRlbHRhLCBmeSwgZnB5OyBpIDwgaXRlcmF0aW9uczsgKytpKSB7CiAgICAgICAgZnkgPSBsICogKEExICsgQTIgKiBsMiArIGw2ICogKEEzICsgQTQgKiBsMikpIC0geTsKICAgICAgICBmcHkgPSBBMSArIDMgKiBBMiAqIGwyICsgbDYgKiAoNyAqIEEzICsgOSAqIEE0ICogbDIpOwogICAgICAgIGwgLT0gZGVsdGEgPSBmeSAvIGZweSwgbDIgPSBsICogbCwgbDYgPSBsMiAqIGwyICogbDI7CiAgICAgICAgaWYgKGFicyhkZWx0YSkgPCBlcHNpbG9uMiQxKSBicmVhazsKICAgICAgfQogICAgICByZXR1cm4gWwogICAgICAgIE0gKiB4ICogKEExICsgMyAqIEEyICogbDIgKyBsNiAqICg3ICogQTMgKyA5ICogQTQgKiBsMikpIC8gY29zJDEobCksCiAgICAgICAgYXNpbihzaW4kMShsKSAvIE0pCiAgICAgIF07CiAgICB9OwoKICAgIGZ1bmN0aW9uIGVxdWFsRWFydGgoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uKGVxdWFsRWFydGhSYXcpCiAgICAgICAgICAuc2NhbGUoMTc3LjE1OCk7CiAgICB9CgogICAgZnVuY3Rpb24gZ25vbW9uaWNSYXcoeCwgeSkgewogICAgICB2YXIgY3kgPSBjb3MkMSh5KSwgayA9IGNvcyQxKHgpICogY3k7CiAgICAgIHJldHVybiBbY3kgKiBzaW4kMSh4KSAvIGssIHNpbiQxKHkpIC8ga107CiAgICB9CgogICAgZ25vbW9uaWNSYXcuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0KGF0YW4pOwoKICAgIGZ1bmN0aW9uIGdub21vbmljKCkgewogICAgICByZXR1cm4gcHJvamVjdGlvbihnbm9tb25pY1JhdykKICAgICAgICAgIC5zY2FsZSgxNDQuMDQ5KQogICAgICAgICAgLmNsaXBBbmdsZSg2MCk7CiAgICB9CgogICAgZnVuY3Rpb24gaWRlbnRpdHkkNSgpIHsKICAgICAgdmFyIGsgPSAxLCB0eCA9IDAsIHR5ID0gMCwgc3ggPSAxLCBzeSA9IDEsIC8vIHNjYWxlLCB0cmFuc2xhdGUgYW5kIHJlZmxlY3QKICAgICAgICAgIGFscGhhID0gMCwgY2EsIHNhLCAvLyBhbmdsZQogICAgICAgICAgeDAgPSBudWxsLCB5MCwgeDEsIHkxLCAvLyBjbGlwIGV4dGVudAogICAgICAgICAga3ggPSAxLCBreSA9IDEsCiAgICAgICAgICB0cmFuc2Zvcm0gPSB0cmFuc2Zvcm1lcih7CiAgICAgICAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgICAgICAgdmFyIHAgPSBwcm9qZWN0aW9uKFt4LCB5XSk7CiAgICAgICAgICAgICAgdGhpcy5zdHJlYW0ucG9pbnQocFswXSwgcFsxXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pLAogICAgICAgICAgcG9zdGNsaXAgPSBpZGVudGl0eSQ0LAogICAgICAgICAgY2FjaGUsCiAgICAgICAgICBjYWNoZVN0cmVhbTsKCiAgICAgIGZ1bmN0aW9uIHJlc2V0KCkgewogICAgICAgIGt4ID0gayAqIHN4OwogICAgICAgIGt5ID0gayAqIHN5OwogICAgICAgIGNhY2hlID0gY2FjaGVTdHJlYW0gPSBudWxsOwogICAgICAgIHJldHVybiBwcm9qZWN0aW9uOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwcm9qZWN0aW9uIChwKSB7CiAgICAgICAgdmFyIHggPSBwWzBdICoga3gsIHkgPSBwWzFdICoga3k7CiAgICAgICAgaWYgKGFscGhhKSB7CiAgICAgICAgICB2YXIgdCA9IHkgKiBjYSAtIHggKiBzYTsKICAgICAgICAgIHggPSB4ICogY2EgKyB5ICogc2E7CiAgICAgICAgICB5ID0gdDsKICAgICAgICB9ICAgIAogICAgICAgIHJldHVybiBbeCArIHR4LCB5ICsgdHldOwogICAgICB9CiAgICAgIHByb2plY3Rpb24uaW52ZXJ0ID0gZnVuY3Rpb24ocCkgewogICAgICAgIHZhciB4ID0gcFswXSAtIHR4LCB5ID0gcFsxXSAtIHR5OwogICAgICAgIGlmIChhbHBoYSkgewogICAgICAgICAgdmFyIHQgPSB5ICogY2EgKyB4ICogc2E7CiAgICAgICAgICB4ID0geCAqIGNhIC0geSAqIHNhOwogICAgICAgICAgeSA9IHQ7CiAgICAgICAgfQogICAgICAgIHJldHVybiBbeCAvIGt4LCB5IC8ga3ldOwogICAgICB9OwogICAgICBwcm9qZWN0aW9uLnN0cmVhbSA9IGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHJldHVybiBjYWNoZSAmJiBjYWNoZVN0cmVhbSA9PT0gc3RyZWFtID8gY2FjaGUgOiBjYWNoZSA9IHRyYW5zZm9ybShwb3N0Y2xpcChjYWNoZVN0cmVhbSA9IHN0cmVhbSkpOwogICAgICB9OwogICAgICBwcm9qZWN0aW9uLnBvc3RjbGlwID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBvc3RjbGlwID0gXywgeDAgPSB5MCA9IHgxID0geTEgPSBudWxsLCByZXNldCgpKSA6IHBvc3RjbGlwOwogICAgICB9OwogICAgICBwcm9qZWN0aW9uLmNsaXBFeHRlbnQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocG9zdGNsaXAgPSBfID09IG51bGwgPyAoeDAgPSB5MCA9IHgxID0geTEgPSBudWxsLCBpZGVudGl0eSQ0KSA6IGNsaXBSZWN0YW5nbGUoeDAgPSArX1swXVswXSwgeTAgPSArX1swXVsxXSwgeDEgPSArX1sxXVswXSwgeTEgPSArX1sxXVsxXSksIHJlc2V0KCkpIDogeDAgPT0gbnVsbCA/IG51bGwgOiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgfTsKICAgICAgcHJvamVjdGlvbi5zY2FsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChrID0gK18sIHJlc2V0KCkpIDogazsKICAgICAgfTsKICAgICAgcHJvamVjdGlvbi50cmFuc2xhdGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodHggPSArX1swXSwgdHkgPSArX1sxXSwgcmVzZXQoKSkgOiBbdHgsIHR5XTsKICAgICAgfTsKICAgICAgcHJvamVjdGlvbi5hbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChhbHBoYSA9IF8gJSAzNjAgKiByYWRpYW5zLCBzYSA9IHNpbiQxKGFscGhhKSwgY2EgPSBjb3MkMShhbHBoYSksIHJlc2V0KCkpIDogYWxwaGEgKiBkZWdyZWVzJDE7CiAgICAgIH07CiAgICAgIHByb2plY3Rpb24ucmVmbGVjdFggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3ggPSBfID8gLTEgOiAxLCByZXNldCgpKSA6IHN4IDwgMDsKICAgICAgfTsKICAgICAgcHJvamVjdGlvbi5yZWZsZWN0WSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzeSA9IF8gPyAtMSA6IDEsIHJlc2V0KCkpIDogc3kgPCAwOwogICAgICB9OwogICAgICBwcm9qZWN0aW9uLmZpdEV4dGVudCA9IGZ1bmN0aW9uKGV4dGVudCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEV4dGVudChwcm9qZWN0aW9uLCBleHRlbnQsIG9iamVjdCk7CiAgICAgIH07CiAgICAgIHByb2plY3Rpb24uZml0U2l6ZSA9IGZ1bmN0aW9uKHNpemUsIG9iamVjdCkgewogICAgICAgIHJldHVybiBmaXRTaXplKHByb2plY3Rpb24sIHNpemUsIG9iamVjdCk7CiAgICAgIH07CiAgICAgIHByb2plY3Rpb24uZml0V2lkdGggPSBmdW5jdGlvbih3aWR0aCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdFdpZHRoKHByb2plY3Rpb24sIHdpZHRoLCBvYmplY3QpOwogICAgICB9OwogICAgICBwcm9qZWN0aW9uLmZpdEhlaWdodCA9IGZ1bmN0aW9uKGhlaWdodCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEhlaWdodChwcm9qZWN0aW9uLCBoZWlnaHQsIG9iamVjdCk7CiAgICAgIH07CgogICAgICByZXR1cm4gcHJvamVjdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBuYXR1cmFsRWFydGgxUmF3KGxhbWJkYSwgcGhpKSB7CiAgICAgIHZhciBwaGkyID0gcGhpICogcGhpLCBwaGk0ID0gcGhpMiAqIHBoaTI7CiAgICAgIHJldHVybiBbCiAgICAgICAgbGFtYmRhICogKDAuODcwNyAtIDAuMTMxOTc5ICogcGhpMiArIHBoaTQgKiAoLTAuMDEzNzkxICsgcGhpNCAqICgwLjAwMzk3MSAqIHBoaTIgLSAwLjAwMTUyOSAqIHBoaTQpKSksCiAgICAgICAgcGhpICogKDEuMDA3MjI2ICsgcGhpMiAqICgwLjAxNTA4NSArIHBoaTQgKiAoLTAuMDQ0NDc1ICsgMC4wMjg4NzQgKiBwaGkyIC0gMC4wMDU5MTYgKiBwaGk0KSkpCiAgICAgIF07CiAgICB9CgogICAgbmF0dXJhbEVhcnRoMVJhdy5pbnZlcnQgPSBmdW5jdGlvbih4LCB5KSB7CiAgICAgIHZhciBwaGkgPSB5LCBpID0gMjUsIGRlbHRhOwogICAgICBkbyB7CiAgICAgICAgdmFyIHBoaTIgPSBwaGkgKiBwaGksIHBoaTQgPSBwaGkyICogcGhpMjsKICAgICAgICBwaGkgLT0gZGVsdGEgPSAocGhpICogKDEuMDA3MjI2ICsgcGhpMiAqICgwLjAxNTA4NSArIHBoaTQgKiAoLTAuMDQ0NDc1ICsgMC4wMjg4NzQgKiBwaGkyIC0gMC4wMDU5MTYgKiBwaGk0KSkpIC0geSkgLwogICAgICAgICAgICAoMS4wMDcyMjYgKyBwaGkyICogKDAuMDE1MDg1ICogMyArIHBoaTQgKiAoLTAuMDQ0NDc1ICogNyArIDAuMDI4ODc0ICogOSAqIHBoaTIgLSAwLjAwNTkxNiAqIDExICogcGhpNCkpKTsKICAgICAgfSB3aGlsZSAoYWJzKGRlbHRhKSA+IGVwc2lsb24kMiAmJiAtLWkgPiAwKTsKICAgICAgcmV0dXJuIFsKICAgICAgICB4IC8gKDAuODcwNyArIChwaGkyID0gcGhpICogcGhpKSAqICgtMC4xMzE5NzkgKyBwaGkyICogKC0wLjAxMzc5MSArIHBoaTIgKiBwaGkyICogcGhpMiAqICgwLjAwMzk3MSAtIDAuMDAxNTI5ICogcGhpMikpKSksCiAgICAgICAgcGhpCiAgICAgIF07CiAgICB9OwoKICAgIGZ1bmN0aW9uIG5hdHVyYWxFYXJ0aDEoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uKG5hdHVyYWxFYXJ0aDFSYXcpCiAgICAgICAgICAuc2NhbGUoMTc1LjI5NSk7CiAgICB9CgogICAgZnVuY3Rpb24gb3J0aG9ncmFwaGljUmF3KHgsIHkpIHsKICAgICAgcmV0dXJuIFtjb3MkMSh5KSAqIHNpbiQxKHgpLCBzaW4kMSh5KV07CiAgICB9CgogICAgb3J0aG9ncmFwaGljUmF3LmludmVydCA9IGF6aW11dGhhbEludmVydChhc2luKTsKCiAgICBmdW5jdGlvbiBvcnRob2dyYXBoaWMoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uKG9ydGhvZ3JhcGhpY1JhdykKICAgICAgICAgIC5zY2FsZSgyNDkuNSkKICAgICAgICAgIC5jbGlwQW5nbGUoOTAgKyBlcHNpbG9uJDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0ZXJlb2dyYXBoaWNSYXcoeCwgeSkgewogICAgICB2YXIgY3kgPSBjb3MkMSh5KSwgayA9IDEgKyBjb3MkMSh4KSAqIGN5OwogICAgICByZXR1cm4gW2N5ICogc2luJDEoeCkgLyBrLCBzaW4kMSh5KSAvIGtdOwogICAgfQoKICAgIHN0ZXJlb2dyYXBoaWNSYXcuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0KGZ1bmN0aW9uKHopIHsKICAgICAgcmV0dXJuIDIgKiBhdGFuKHopOwogICAgfSk7CgogICAgZnVuY3Rpb24gc3RlcmVvZ3JhcGhpYygpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24oc3RlcmVvZ3JhcGhpY1JhdykKICAgICAgICAgIC5zY2FsZSgyNTApCiAgICAgICAgICAuY2xpcEFuZ2xlKDE0Mik7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnN2ZXJzZU1lcmNhdG9yUmF3KGxhbWJkYSwgcGhpKSB7CiAgICAgIHJldHVybiBbbG9nKHRhbigoaGFsZlBpJDIgKyBwaGkpIC8gMikpLCAtbGFtYmRhXTsKICAgIH0KCiAgICB0cmFuc3ZlcnNlTWVyY2F0b3JSYXcuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICByZXR1cm4gWy15LCAyICogYXRhbihleHAoeCkpIC0gaGFsZlBpJDJdOwogICAgfTsKCiAgICBmdW5jdGlvbiB0cmFuc3ZlcnNlTWVyY2F0b3IoKSB7CiAgICAgIHZhciBtID0gbWVyY2F0b3JQcm9qZWN0aW9uKHRyYW5zdmVyc2VNZXJjYXRvclJhdyksCiAgICAgICAgICBjZW50ZXIgPSBtLmNlbnRlciwKICAgICAgICAgIHJvdGF0ZSA9IG0ucm90YXRlOwoKICAgICAgbS5jZW50ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyBjZW50ZXIoWy1fWzFdLCBfWzBdXSkgOiAoXyA9IGNlbnRlcigpLCBbX1sxXSwgLV9bMF1dKTsKICAgICAgfTsKCiAgICAgIG0ucm90YXRlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gcm90YXRlKFtfWzBdLCBfWzFdLCBfLmxlbmd0aCA+IDIgPyBfWzJdICsgOTAgOiA5MF0pIDogKF8gPSByb3RhdGUoKSwgW19bMF0sIF9bMV0sIF9bMl0gLSA5MF0pOwogICAgICB9OwoKICAgICAgcmV0dXJuIHJvdGF0ZShbMCwgMCwgOTBdKQogICAgICAgICAgLnNjYWxlKDE1OS4xNTUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRTZXBhcmF0aW9uKGEsIGIpIHsKICAgICAgcmV0dXJuIGEucGFyZW50ID09PSBiLnBhcmVudCA/IDEgOiAyOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lYW5YKGNoaWxkcmVuKSB7CiAgICAgIHJldHVybiBjaGlsZHJlbi5yZWR1Y2UobWVhblhSZWR1Y2UsIDApIC8gY2hpbGRyZW4ubGVuZ3RoOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lYW5YUmVkdWNlKHgsIGMpIHsKICAgICAgcmV0dXJuIHggKyBjLng7CiAgICB9CgogICAgZnVuY3Rpb24gbWF4WShjaGlsZHJlbikgewogICAgICByZXR1cm4gMSArIGNoaWxkcmVuLnJlZHVjZShtYXhZUmVkdWNlLCAwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBtYXhZUmVkdWNlKHksIGMpIHsKICAgICAgcmV0dXJuIE1hdGgubWF4KHksIGMueSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGVhZkxlZnQobm9kZSkgewogICAgICB2YXIgY2hpbGRyZW47CiAgICAgIHdoaWxlIChjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW4pIG5vZGUgPSBjaGlsZHJlblswXTsKICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgZnVuY3Rpb24gbGVhZlJpZ2h0KG5vZGUpIHsKICAgICAgdmFyIGNoaWxkcmVuOwogICAgICB3aGlsZSAoY2hpbGRyZW4gPSBub2RlLmNoaWxkcmVuKSBub2RlID0gY2hpbGRyZW5bY2hpbGRyZW4ubGVuZ3RoIC0gMV07CiAgICAgIHJldHVybiBub2RlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsdXN0ZXIoKSB7CiAgICAgIHZhciBzZXBhcmF0aW9uID0gZGVmYXVsdFNlcGFyYXRpb24sCiAgICAgICAgICBkeCA9IDEsCiAgICAgICAgICBkeSA9IDEsCiAgICAgICAgICBub2RlU2l6ZSA9IGZhbHNlOwoKICAgICAgZnVuY3Rpb24gY2x1c3Rlcihyb290KSB7CiAgICAgICAgdmFyIHByZXZpb3VzTm9kZSwKICAgICAgICAgICAgeCA9IDA7CgogICAgICAgIC8vIEZpcnN0IHdhbGssIGNvbXB1dGluZyB0aGUgaW5pdGlhbCB4ICYgeSB2YWx1ZXMuCiAgICAgICAgcm9vdC5lYWNoQWZ0ZXIoZnVuY3Rpb24obm9kZSkgewogICAgICAgICAgdmFyIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbjsKICAgICAgICAgIGlmIChjaGlsZHJlbikgewogICAgICAgICAgICBub2RlLnggPSBtZWFuWChjaGlsZHJlbik7CiAgICAgICAgICAgIG5vZGUueSA9IG1heFkoY2hpbGRyZW4pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZS54ID0gcHJldmlvdXNOb2RlID8geCArPSBzZXBhcmF0aW9uKG5vZGUsIHByZXZpb3VzTm9kZSkgOiAwOwogICAgICAgICAgICBub2RlLnkgPSAwOwogICAgICAgICAgICBwcmV2aW91c05vZGUgPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICB2YXIgbGVmdCA9IGxlYWZMZWZ0KHJvb3QpLAogICAgICAgICAgICByaWdodCA9IGxlYWZSaWdodChyb290KSwKICAgICAgICAgICAgeDAgPSBsZWZ0LnggLSBzZXBhcmF0aW9uKGxlZnQsIHJpZ2h0KSAvIDIsCiAgICAgICAgICAgIHgxID0gcmlnaHQueCArIHNlcGFyYXRpb24ocmlnaHQsIGxlZnQpIC8gMjsKCiAgICAgICAgLy8gU2Vjb25kIHdhbGssIG5vcm1hbGl6aW5nIHggJiB5IHRvIHRoZSBkZXNpcmVkIHNpemUuCiAgICAgICAgcmV0dXJuIHJvb3QuZWFjaEFmdGVyKG5vZGVTaXplID8gZnVuY3Rpb24obm9kZSkgewogICAgICAgICAgbm9kZS54ID0gKG5vZGUueCAtIHJvb3QueCkgKiBkeDsKICAgICAgICAgIG5vZGUueSA9IChyb290LnkgLSBub2RlLnkpICogZHk7CiAgICAgICAgfSA6IGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgIG5vZGUueCA9IChub2RlLnggLSB4MCkgLyAoeDEgLSB4MCkgKiBkeDsKICAgICAgICAgIG5vZGUueSA9ICgxIC0gKHJvb3QueSA/IG5vZGUueSAvIHJvb3QueSA6IDEpKSAqIGR5OwogICAgICAgIH0pOwogICAgICB9CgogICAgICBjbHVzdGVyLnNlcGFyYXRpb24gPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2VwYXJhdGlvbiA9IHgsIGNsdXN0ZXIpIDogc2VwYXJhdGlvbjsKICAgICAgfTsKCiAgICAgIGNsdXN0ZXIuc2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChub2RlU2l6ZSA9IGZhbHNlLCBkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCBjbHVzdGVyKSA6IChub2RlU2l6ZSA/IG51bGwgOiBbZHgsIGR5XSk7CiAgICAgIH07CgogICAgICBjbHVzdGVyLm5vZGVTaXplID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG5vZGVTaXplID0gdHJ1ZSwgZHggPSAreFswXSwgZHkgPSAreFsxXSwgY2x1c3RlcikgOiAobm9kZVNpemUgPyBbZHgsIGR5XSA6IG51bGwpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNsdXN0ZXI7CiAgICB9CgogICAgZnVuY3Rpb24gY291bnQobm9kZSkgewogICAgICB2YXIgc3VtID0gMCwKICAgICAgICAgIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbiwKICAgICAgICAgIGkgPSBjaGlsZHJlbiAmJiBjaGlsZHJlbi5sZW5ndGg7CiAgICAgIGlmICghaSkgc3VtID0gMTsKICAgICAgZWxzZSB3aGlsZSAoLS1pID49IDApIHN1bSArPSBjaGlsZHJlbltpXS52YWx1ZTsKICAgICAgbm9kZS52YWx1ZSA9IHN1bTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2NvdW50KCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoQWZ0ZXIoY291bnQpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfZWFjaChjYWxsYmFjaykgewogICAgICB2YXIgbm9kZSA9IHRoaXMsIGN1cnJlbnQsIG5leHQgPSBbbm9kZV0sIGNoaWxkcmVuLCBpLCBuOwogICAgICBkbyB7CiAgICAgICAgY3VycmVudCA9IG5leHQucmV2ZXJzZSgpLCBuZXh0ID0gW107CiAgICAgICAgd2hpbGUgKG5vZGUgPSBjdXJyZW50LnBvcCgpKSB7CiAgICAgICAgICBjYWxsYmFjayhub2RlKSwgY2hpbGRyZW4gPSBub2RlLmNoaWxkcmVuOwogICAgICAgICAgaWYgKGNoaWxkcmVuKSBmb3IgKGkgPSAwLCBuID0gY2hpbGRyZW4ubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIG5leHQucHVzaChjaGlsZHJlbltpXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9IHdoaWxlIChuZXh0Lmxlbmd0aCk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfZWFjaEJlZm9yZShjYWxsYmFjaykgewogICAgICB2YXIgbm9kZSA9IHRoaXMsIG5vZGVzID0gW25vZGVdLCBjaGlsZHJlbiwgaTsKICAgICAgd2hpbGUgKG5vZGUgPSBub2Rlcy5wb3AoKSkgewogICAgICAgIGNhbGxiYWNrKG5vZGUpLCBjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW47CiAgICAgICAgaWYgKGNoaWxkcmVuKSBmb3IgKGkgPSBjaGlsZHJlbi5sZW5ndGggLSAxOyBpID49IDA7IC0taSkgewogICAgICAgICAgbm9kZXMucHVzaChjaGlsZHJlbltpXSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfZWFjaEFmdGVyKGNhbGxiYWNrKSB7CiAgICAgIHZhciBub2RlID0gdGhpcywgbm9kZXMgPSBbbm9kZV0sIG5leHQgPSBbXSwgY2hpbGRyZW4sIGksIG47CiAgICAgIHdoaWxlIChub2RlID0gbm9kZXMucG9wKCkpIHsKICAgICAgICBuZXh0LnB1c2gobm9kZSksIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbjsKICAgICAgICBpZiAoY2hpbGRyZW4pIGZvciAoaSA9IDAsIG4gPSBjaGlsZHJlbi5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIG5vZGVzLnB1c2goY2hpbGRyZW5baV0pOwogICAgICAgIH0KICAgICAgfQogICAgICB3aGlsZSAobm9kZSA9IG5leHQucG9wKCkpIHsKICAgICAgICBjYWxsYmFjayhub2RlKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX3N1bSh2YWx1ZSkgewogICAgICByZXR1cm4gdGhpcy5lYWNoQWZ0ZXIoZnVuY3Rpb24obm9kZSkgewogICAgICAgIHZhciBzdW0gPSArdmFsdWUobm9kZS5kYXRhKSB8fCAwLAogICAgICAgICAgICBjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW4sCiAgICAgICAgICAgIGkgPSBjaGlsZHJlbiAmJiBjaGlsZHJlbi5sZW5ndGg7CiAgICAgICAgd2hpbGUgKC0taSA+PSAwKSBzdW0gKz0gY2hpbGRyZW5baV0udmFsdWU7CiAgICAgICAgbm9kZS52YWx1ZSA9IHN1bTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9zb3J0KGNvbXBhcmUpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaEJlZm9yZShmdW5jdGlvbihub2RlKSB7CiAgICAgICAgaWYgKG5vZGUuY2hpbGRyZW4pIHsKICAgICAgICAgIG5vZGUuY2hpbGRyZW4uc29ydChjb21wYXJlKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfcGF0aChlbmQpIHsKICAgICAgdmFyIHN0YXJ0ID0gdGhpcywKICAgICAgICAgIGFuY2VzdG9yID0gbGVhc3RDb21tb25BbmNlc3RvcihzdGFydCwgZW5kKSwKICAgICAgICAgIG5vZGVzID0gW3N0YXJ0XTsKICAgICAgd2hpbGUgKHN0YXJ0ICE9PSBhbmNlc3RvcikgewogICAgICAgIHN0YXJ0ID0gc3RhcnQucGFyZW50OwogICAgICAgIG5vZGVzLnB1c2goc3RhcnQpOwogICAgICB9CiAgICAgIHZhciBrID0gbm9kZXMubGVuZ3RoOwogICAgICB3aGlsZSAoZW5kICE9PSBhbmNlc3RvcikgewogICAgICAgIG5vZGVzLnNwbGljZShrLCAwLCBlbmQpOwogICAgICAgIGVuZCA9IGVuZC5wYXJlbnQ7CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlYXN0Q29tbW9uQW5jZXN0b3IoYSwgYikgewogICAgICBpZiAoYSA9PT0gYikgcmV0dXJuIGE7CiAgICAgIHZhciBhTm9kZXMgPSBhLmFuY2VzdG9ycygpLAogICAgICAgICAgYk5vZGVzID0gYi5hbmNlc3RvcnMoKSwKICAgICAgICAgIGMgPSBudWxsOwogICAgICBhID0gYU5vZGVzLnBvcCgpOwogICAgICBiID0gYk5vZGVzLnBvcCgpOwogICAgICB3aGlsZSAoYSA9PT0gYikgewogICAgICAgIGMgPSBhOwogICAgICAgIGEgPSBhTm9kZXMucG9wKCk7CiAgICAgICAgYiA9IGJOb2Rlcy5wb3AoKTsKICAgICAgfQogICAgICByZXR1cm4gYzsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2FuY2VzdG9ycygpIHsKICAgICAgdmFyIG5vZGUgPSB0aGlzLCBub2RlcyA9IFtub2RlXTsKICAgICAgd2hpbGUgKG5vZGUgPSBub2RlLnBhcmVudCkgewogICAgICAgIG5vZGVzLnB1c2gobm9kZSk7CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfZGVzY2VuZGFudHMoKSB7CiAgICAgIHZhciBub2RlcyA9IFtdOwogICAgICB0aGlzLmVhY2goZnVuY3Rpb24obm9kZSkgewogICAgICAgIG5vZGVzLnB1c2gobm9kZSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gbm9kZXM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9sZWF2ZXMoKSB7CiAgICAgIHZhciBsZWF2ZXMgPSBbXTsKICAgICAgdGhpcy5lYWNoQmVmb3JlKGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICBpZiAoIW5vZGUuY2hpbGRyZW4pIHsKICAgICAgICAgIGxlYXZlcy5wdXNoKG5vZGUpOwogICAgICAgIH0KICAgICAgfSk7CiAgICAgIHJldHVybiBsZWF2ZXM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9saW5rcygpIHsKICAgICAgdmFyIHJvb3QgPSB0aGlzLCBsaW5rcyA9IFtdOwogICAgICByb290LmVhY2goZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmIChub2RlICE9PSByb290KSB7IC8vIERvbuKAmXQgaW5jbHVkZSB0aGUgcm9vdOKAmXMgcGFyZW50LCBpZiBhbnkuCiAgICAgICAgICBsaW5rcy5wdXNoKHtzb3VyY2U6IG5vZGUucGFyZW50LCB0YXJnZXQ6IG5vZGV9KTsKICAgICAgICB9CiAgICAgIH0pOwogICAgICByZXR1cm4gbGlua3M7CiAgICB9CgogICAgZnVuY3Rpb24gaGllcmFyY2h5KGRhdGEsIGNoaWxkcmVuKSB7CiAgICAgIHZhciByb290ID0gbmV3IE5vZGUkMShkYXRhKSwKICAgICAgICAgIHZhbHVlZCA9ICtkYXRhLnZhbHVlICYmIChyb290LnZhbHVlID0gZGF0YS52YWx1ZSksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZXMgPSBbcm9vdF0sCiAgICAgICAgICBjaGlsZCwKICAgICAgICAgIGNoaWxkcywKICAgICAgICAgIGksCiAgICAgICAgICBuOwoKICAgICAgaWYgKGNoaWxkcmVuID09IG51bGwpIGNoaWxkcmVuID0gZGVmYXVsdENoaWxkcmVuOwoKICAgICAgd2hpbGUgKG5vZGUgPSBub2Rlcy5wb3AoKSkgewogICAgICAgIGlmICh2YWx1ZWQpIG5vZGUudmFsdWUgPSArbm9kZS5kYXRhLnZhbHVlOwogICAgICAgIGlmICgoY2hpbGRzID0gY2hpbGRyZW4obm9kZS5kYXRhKSkgJiYgKG4gPSBjaGlsZHMubGVuZ3RoKSkgewogICAgICAgICAgbm9kZS5jaGlsZHJlbiA9IG5ldyBBcnJheShuKTsKICAgICAgICAgIGZvciAoaSA9IG4gLSAxOyBpID49IDA7IC0taSkgewogICAgICAgICAgICBub2Rlcy5wdXNoKGNoaWxkID0gbm9kZS5jaGlsZHJlbltpXSA9IG5ldyBOb2RlJDEoY2hpbGRzW2ldKSk7CiAgICAgICAgICAgIGNoaWxkLnBhcmVudCA9IG5vZGU7CiAgICAgICAgICAgIGNoaWxkLmRlcHRoID0gbm9kZS5kZXB0aCArIDE7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gcm9vdC5lYWNoQmVmb3JlKGNvbXB1dGVIZWlnaHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfY29weSgpIHsKICAgICAgcmV0dXJuIGhpZXJhcmNoeSh0aGlzKS5lYWNoQmVmb3JlKGNvcHlEYXRhKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0Q2hpbGRyZW4oZCkgewogICAgICByZXR1cm4gZC5jaGlsZHJlbjsKICAgIH0KCiAgICBmdW5jdGlvbiBjb3B5RGF0YShub2RlKSB7CiAgICAgIG5vZGUuZGF0YSA9IG5vZGUuZGF0YS5kYXRhOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbXB1dGVIZWlnaHQobm9kZSkgewogICAgICB2YXIgaGVpZ2h0ID0gMDsKICAgICAgZG8gbm9kZS5oZWlnaHQgPSBoZWlnaHQ7CiAgICAgIHdoaWxlICgobm9kZSA9IG5vZGUucGFyZW50KSAmJiAobm9kZS5oZWlnaHQgPCArK2hlaWdodCkpOwogICAgfQoKICAgIGZ1bmN0aW9uIE5vZGUkMShkYXRhKSB7CiAgICAgIHRoaXMuZGF0YSA9IGRhdGE7CiAgICAgIHRoaXMuZGVwdGggPQogICAgICB0aGlzLmhlaWdodCA9IDA7CiAgICAgIHRoaXMucGFyZW50ID0gbnVsbDsKICAgIH0KCiAgICBOb2RlJDEucHJvdG90eXBlID0gaGllcmFyY2h5LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IE5vZGUkMSwKICAgICAgY291bnQ6IG5vZGVfY291bnQsCiAgICAgIGVhY2g6IG5vZGVfZWFjaCwKICAgICAgZWFjaEFmdGVyOiBub2RlX2VhY2hBZnRlciwKICAgICAgZWFjaEJlZm9yZTogbm9kZV9lYWNoQmVmb3JlLAogICAgICBzdW06IG5vZGVfc3VtLAogICAgICBzb3J0OiBub2RlX3NvcnQsCiAgICAgIHBhdGg6IG5vZGVfcGF0aCwKICAgICAgYW5jZXN0b3JzOiBub2RlX2FuY2VzdG9ycywKICAgICAgZGVzY2VuZGFudHM6IG5vZGVfZGVzY2VuZGFudHMsCiAgICAgIGxlYXZlczogbm9kZV9sZWF2ZXMsCiAgICAgIGxpbmtzOiBub2RlX2xpbmtzLAogICAgICBjb3B5OiBub2RlX2NvcHkKICAgIH07CgogICAgdmFyIHNsaWNlJDQgPSBBcnJheS5wcm90b3R5cGUuc2xpY2U7CgogICAgZnVuY3Rpb24gc2h1ZmZsZSQxKGFycmF5KSB7CiAgICAgIHZhciBtID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgdCwKICAgICAgICAgIGk7CgogICAgICB3aGlsZSAobSkgewogICAgICAgIGkgPSBNYXRoLnJhbmRvbSgpICogbS0tIHwgMDsKICAgICAgICB0ID0gYXJyYXlbbV07CiAgICAgICAgYXJyYXlbbV0gPSBhcnJheVtpXTsKICAgICAgICBhcnJheVtpXSA9IHQ7CiAgICAgIH0KCiAgICAgIHJldHVybiBhcnJheTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3NlKGNpcmNsZXMpIHsKICAgICAgdmFyIGkgPSAwLCBuID0gKGNpcmNsZXMgPSBzaHVmZmxlJDEoc2xpY2UkNC5jYWxsKGNpcmNsZXMpKSkubGVuZ3RoLCBCID0gW10sIHAsIGU7CgogICAgICB3aGlsZSAoaSA8IG4pIHsKICAgICAgICBwID0gY2lyY2xlc1tpXTsKICAgICAgICBpZiAoZSAmJiBlbmNsb3Nlc1dlYWsoZSwgcCkpICsraTsKICAgICAgICBlbHNlIGUgPSBlbmNsb3NlQmFzaXMoQiA9IGV4dGVuZEJhc2lzKEIsIHApKSwgaSA9IDA7CiAgICAgIH0KCiAgICAgIHJldHVybiBlOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVuZEJhc2lzKEIsIHApIHsKICAgICAgdmFyIGksIGo7CgogICAgICBpZiAoZW5jbG9zZXNXZWFrQWxsKHAsIEIpKSByZXR1cm4gW3BdOwoKICAgICAgLy8gSWYgd2UgZ2V0IGhlcmUgdGhlbiBCIG11c3QgaGF2ZSBhdCBsZWFzdCBvbmUgZWxlbWVudC4KICAgICAgZm9yIChpID0gMDsgaSA8IEIubGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAoZW5jbG9zZXNOb3QocCwgQltpXSkKICAgICAgICAgICAgJiYgZW5jbG9zZXNXZWFrQWxsKGVuY2xvc2VCYXNpczIoQltpXSwgcCksIEIpKSB7CiAgICAgICAgICByZXR1cm4gW0JbaV0sIHBdOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gSWYgd2UgZ2V0IGhlcmUgdGhlbiBCIG11c3QgaGF2ZSBhdCBsZWFzdCB0d28gZWxlbWVudHMuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBCLmxlbmd0aCAtIDE7ICsraSkgewogICAgICAgIGZvciAoaiA9IGkgKyAxOyBqIDwgQi5sZW5ndGg7ICsraikgewogICAgICAgICAgaWYgKGVuY2xvc2VzTm90KGVuY2xvc2VCYXNpczIoQltpXSwgQltqXSksIHApCiAgICAgICAgICAgICAgJiYgZW5jbG9zZXNOb3QoZW5jbG9zZUJhc2lzMihCW2ldLCBwKSwgQltqXSkKICAgICAgICAgICAgICAmJiBlbmNsb3Nlc05vdChlbmNsb3NlQmFzaXMyKEJbal0sIHApLCBCW2ldKQogICAgICAgICAgICAgICYmIGVuY2xvc2VzV2Vha0FsbChlbmNsb3NlQmFzaXMzKEJbaV0sIEJbal0sIHApLCBCKSkgewogICAgICAgICAgICByZXR1cm4gW0JbaV0sIEJbal0sIHBdOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gSWYgd2UgZ2V0IGhlcmUgdGhlbiBzb21ldGhpbmcgaXMgdmVyeSB3cm9uZy4KICAgICAgdGhyb3cgbmV3IEVycm9yOwogICAgfQoKICAgIGZ1bmN0aW9uIGVuY2xvc2VzTm90KGEsIGIpIHsKICAgICAgdmFyIGRyID0gYS5yIC0gYi5yLCBkeCA9IGIueCAtIGEueCwgZHkgPSBiLnkgLSBhLnk7CiAgICAgIHJldHVybiBkciA8IDAgfHwgZHIgKiBkciA8IGR4ICogZHggKyBkeSAqIGR5OwogICAgfQoKICAgIGZ1bmN0aW9uIGVuY2xvc2VzV2VhayhhLCBiKSB7CiAgICAgIHZhciBkciA9IGEuciAtIGIuciArIDFlLTYsIGR4ID0gYi54IC0gYS54LCBkeSA9IGIueSAtIGEueTsKICAgICAgcmV0dXJuIGRyID4gMCAmJiBkciAqIGRyID4gZHggKiBkeCArIGR5ICogZHk7CiAgICB9CgogICAgZnVuY3Rpb24gZW5jbG9zZXNXZWFrQWxsKGEsIEIpIHsKICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBCLmxlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKCFlbmNsb3Nlc1dlYWsoYSwgQltpXSkpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHRydWU7CiAgICB9CgogICAgZnVuY3Rpb24gZW5jbG9zZUJhc2lzKEIpIHsKICAgICAgc3dpdGNoIChCLmxlbmd0aCkgewogICAgICAgIGNhc2UgMTogcmV0dXJuIGVuY2xvc2VCYXNpczEoQlswXSk7CiAgICAgICAgY2FzZSAyOiByZXR1cm4gZW5jbG9zZUJhc2lzMihCWzBdLCBCWzFdKTsKICAgICAgICBjYXNlIDM6IHJldHVybiBlbmNsb3NlQmFzaXMzKEJbMF0sIEJbMV0sIEJbMl0pOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZW5jbG9zZUJhc2lzMShhKSB7CiAgICAgIHJldHVybiB7CiAgICAgICAgeDogYS54LAogICAgICAgIHk6IGEueSwKICAgICAgICByOiBhLnIKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3NlQmFzaXMyKGEsIGIpIHsKICAgICAgdmFyIHgxID0gYS54LCB5MSA9IGEueSwgcjEgPSBhLnIsCiAgICAgICAgICB4MiA9IGIueCwgeTIgPSBiLnksIHIyID0gYi5yLAogICAgICAgICAgeDIxID0geDIgLSB4MSwgeTIxID0geTIgLSB5MSwgcjIxID0gcjIgLSByMSwKICAgICAgICAgIGwgPSBNYXRoLnNxcnQoeDIxICogeDIxICsgeTIxICogeTIxKTsKICAgICAgcmV0dXJuIHsKICAgICAgICB4OiAoeDEgKyB4MiArIHgyMSAvIGwgKiByMjEpIC8gMiwKICAgICAgICB5OiAoeTEgKyB5MiArIHkyMSAvIGwgKiByMjEpIC8gMiwKICAgICAgICByOiAobCArIHIxICsgcjIpIC8gMgogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGVuY2xvc2VCYXNpczMoYSwgYiwgYykgewogICAgICB2YXIgeDEgPSBhLngsIHkxID0gYS55LCByMSA9IGEuciwKICAgICAgICAgIHgyID0gYi54LCB5MiA9IGIueSwgcjIgPSBiLnIsCiAgICAgICAgICB4MyA9IGMueCwgeTMgPSBjLnksIHIzID0gYy5yLAogICAgICAgICAgYTIgPSB4MSAtIHgyLAogICAgICAgICAgYTMgPSB4MSAtIHgzLAogICAgICAgICAgYjIgPSB5MSAtIHkyLAogICAgICAgICAgYjMgPSB5MSAtIHkzLAogICAgICAgICAgYzIgPSByMiAtIHIxLAogICAgICAgICAgYzMgPSByMyAtIHIxLAogICAgICAgICAgZDEgPSB4MSAqIHgxICsgeTEgKiB5MSAtIHIxICogcjEsCiAgICAgICAgICBkMiA9IGQxIC0geDIgKiB4MiAtIHkyICogeTIgKyByMiAqIHIyLAogICAgICAgICAgZDMgPSBkMSAtIHgzICogeDMgLSB5MyAqIHkzICsgcjMgKiByMywKICAgICAgICAgIGFiID0gYTMgKiBiMiAtIGEyICogYjMsCiAgICAgICAgICB4YSA9IChiMiAqIGQzIC0gYjMgKiBkMikgLyAoYWIgKiAyKSAtIHgxLAogICAgICAgICAgeGIgPSAoYjMgKiBjMiAtIGIyICogYzMpIC8gYWIsCiAgICAgICAgICB5YSA9IChhMyAqIGQyIC0gYTIgKiBkMykgLyAoYWIgKiAyKSAtIHkxLAogICAgICAgICAgeWIgPSAoYTIgKiBjMyAtIGEzICogYzIpIC8gYWIsCiAgICAgICAgICBBID0geGIgKiB4YiArIHliICogeWIgLSAxLAogICAgICAgICAgQiA9IDIgKiAocjEgKyB4YSAqIHhiICsgeWEgKiB5YiksCiAgICAgICAgICBDID0geGEgKiB4YSArIHlhICogeWEgLSByMSAqIHIxLAogICAgICAgICAgciA9IC0oQSA/IChCICsgTWF0aC5zcXJ0KEIgKiBCIC0gNCAqIEEgKiBDKSkgLyAoMiAqIEEpIDogQyAvIEIpOwogICAgICByZXR1cm4gewogICAgICAgIHg6IHgxICsgeGEgKyB4YiAqIHIsCiAgICAgICAgeTogeTEgKyB5YSArIHliICogciwKICAgICAgICByOiByCiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcGxhY2UoYiwgYSwgYykgewogICAgICB2YXIgZHggPSBiLnggLSBhLngsIHgsIGEyLAogICAgICAgICAgZHkgPSBiLnkgLSBhLnksIHksIGIyLAogICAgICAgICAgZDIgPSBkeCAqIGR4ICsgZHkgKiBkeTsKICAgICAgaWYgKGQyKSB7CiAgICAgICAgYTIgPSBhLnIgKyBjLnIsIGEyICo9IGEyOwogICAgICAgIGIyID0gYi5yICsgYy5yLCBiMiAqPSBiMjsKICAgICAgICBpZiAoYTIgPiBiMikgewogICAgICAgICAgeCA9IChkMiArIGIyIC0gYTIpIC8gKDIgKiBkMik7CiAgICAgICAgICB5ID0gTWF0aC5zcXJ0KE1hdGgubWF4KDAsIGIyIC8gZDIgLSB4ICogeCkpOwogICAgICAgICAgYy54ID0gYi54IC0geCAqIGR4IC0geSAqIGR5OwogICAgICAgICAgYy55ID0gYi55IC0geCAqIGR5ICsgeSAqIGR4OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB4ID0gKGQyICsgYTIgLSBiMikgLyAoMiAqIGQyKTsKICAgICAgICAgIHkgPSBNYXRoLnNxcnQoTWF0aC5tYXgoMCwgYTIgLyBkMiAtIHggKiB4KSk7CiAgICAgICAgICBjLnggPSBhLnggKyB4ICogZHggLSB5ICogZHk7CiAgICAgICAgICBjLnkgPSBhLnkgKyB4ICogZHkgKyB5ICogZHg7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIGMueCA9IGEueCArIGMucjsKICAgICAgICBjLnkgPSBhLnk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnNlY3RzKGEsIGIpIHsKICAgICAgdmFyIGRyID0gYS5yICsgYi5yIC0gMWUtNiwgZHggPSBiLnggLSBhLngsIGR5ID0gYi55IC0gYS55OwogICAgICByZXR1cm4gZHIgPiAwICYmIGRyICogZHIgPiBkeCAqIGR4ICsgZHkgKiBkeTsKICAgIH0KCiAgICBmdW5jdGlvbiBzY29yZShub2RlKSB7CiAgICAgIHZhciBhID0gbm9kZS5fLAogICAgICAgICAgYiA9IG5vZGUubmV4dC5fLAogICAgICAgICAgYWIgPSBhLnIgKyBiLnIsCiAgICAgICAgICBkeCA9IChhLnggKiBiLnIgKyBiLnggKiBhLnIpIC8gYWIsCiAgICAgICAgICBkeSA9IChhLnkgKiBiLnIgKyBiLnkgKiBhLnIpIC8gYWI7CiAgICAgIHJldHVybiBkeCAqIGR4ICsgZHkgKiBkeTsKICAgIH0KCiAgICBmdW5jdGlvbiBOb2RlJDIoY2lyY2xlKSB7CiAgICAgIHRoaXMuXyA9IGNpcmNsZTsKICAgICAgdGhpcy5uZXh0ID0gbnVsbDsKICAgICAgdGhpcy5wcmV2aW91cyA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gcGFja0VuY2xvc2UoY2lyY2xlcykgewogICAgICBpZiAoIShuID0gY2lyY2xlcy5sZW5ndGgpKSByZXR1cm4gMDsKCiAgICAgIHZhciBhLCBiLCBjLCBuLCBhYSwgY2EsIGksIGosIGssIHNqLCBzazsKCiAgICAgIC8vIFBsYWNlIHRoZSBmaXJzdCBjaXJjbGUuCiAgICAgIGEgPSBjaXJjbGVzWzBdLCBhLnggPSAwLCBhLnkgPSAwOwogICAgICBpZiAoIShuID4gMSkpIHJldHVybiBhLnI7CgogICAgICAvLyBQbGFjZSB0aGUgc2Vjb25kIGNpcmNsZS4KICAgICAgYiA9IGNpcmNsZXNbMV0sIGEueCA9IC1iLnIsIGIueCA9IGEuciwgYi55ID0gMDsKICAgICAgaWYgKCEobiA+IDIpKSByZXR1cm4gYS5yICsgYi5yOwoKICAgICAgLy8gUGxhY2UgdGhlIHRoaXJkIGNpcmNsZS4KICAgICAgcGxhY2UoYiwgYSwgYyA9IGNpcmNsZXNbMl0pOwoKICAgICAgLy8gSW5pdGlhbGl6ZSB0aGUgZnJvbnQtY2hhaW4gdXNpbmcgdGhlIGZpcnN0IHRocmVlIGNpcmNsZXMgYSwgYiBhbmQgYy4KICAgICAgYSA9IG5ldyBOb2RlJDIoYSksIGIgPSBuZXcgTm9kZSQyKGIpLCBjID0gbmV3IE5vZGUkMihjKTsKICAgICAgYS5uZXh0ID0gYy5wcmV2aW91cyA9IGI7CiAgICAgIGIubmV4dCA9IGEucHJldmlvdXMgPSBjOwogICAgICBjLm5leHQgPSBiLnByZXZpb3VzID0gYTsKCiAgICAgIC8vIEF0dGVtcHQgdG8gcGxhY2UgZWFjaCByZW1haW5pbmcgY2lyY2xl4oCmCiAgICAgIHBhY2s6IGZvciAoaSA9IDM7IGkgPCBuOyArK2kpIHsKICAgICAgICBwbGFjZShhLl8sIGIuXywgYyA9IGNpcmNsZXNbaV0pLCBjID0gbmV3IE5vZGUkMihjKTsKCiAgICAgICAgLy8gRmluZCB0aGUgY2xvc2VzdCBpbnRlcnNlY3RpbmcgY2lyY2xlIG9uIHRoZSBmcm9udC1jaGFpbiwgaWYgYW55LgogICAgICAgIC8vIOKAnENsb3NlbmVzc+KAnSBpcyBkZXRlcm1pbmVkIGJ5IGxpbmVhciBkaXN0YW5jZSBhbG9uZyB0aGUgZnJvbnQtY2hhaW4uCiAgICAgICAgLy8g4oCcQWhlYWTigJ0gb3Ig4oCcYmVoaW5k4oCdIGlzIGxpa2V3aXNlIGRldGVybWluZWQgYnkgbGluZWFyIGRpc3RhbmNlLgogICAgICAgIGogPSBiLm5leHQsIGsgPSBhLnByZXZpb3VzLCBzaiA9IGIuXy5yLCBzayA9IGEuXy5yOwogICAgICAgIGRvIHsKICAgICAgICAgIGlmIChzaiA8PSBzaykgewogICAgICAgICAgICBpZiAoaW50ZXJzZWN0cyhqLl8sIGMuXykpIHsKICAgICAgICAgICAgICBiID0gaiwgYS5uZXh0ID0gYiwgYi5wcmV2aW91cyA9IGEsIC0taTsKICAgICAgICAgICAgICBjb250aW51ZSBwYWNrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHNqICs9IGouXy5yLCBqID0gai5uZXh0OwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKGludGVyc2VjdHMoay5fLCBjLl8pKSB7CiAgICAgICAgICAgICAgYSA9IGssIGEubmV4dCA9IGIsIGIucHJldmlvdXMgPSBhLCAtLWk7CiAgICAgICAgICAgICAgY29udGludWUgcGFjazsKICAgICAgICAgICAgfQogICAgICAgICAgICBzayArPSBrLl8uciwgayA9IGsucHJldmlvdXM7CiAgICAgICAgICB9CiAgICAgICAgfSB3aGlsZSAoaiAhPT0gay5uZXh0KTsKCiAgICAgICAgLy8gU3VjY2VzcyEgSW5zZXJ0IHRoZSBuZXcgY2lyY2xlIGMgYmV0d2VlbiBhIGFuZCBiLgogICAgICAgIGMucHJldmlvdXMgPSBhLCBjLm5leHQgPSBiLCBhLm5leHQgPSBiLnByZXZpb3VzID0gYiA9IGM7CgogICAgICAgIC8vIENvbXB1dGUgdGhlIG5ldyBjbG9zZXN0IGNpcmNsZSBwYWlyIHRvIHRoZSBjZW50cm9pZC4KICAgICAgICBhYSA9IHNjb3JlKGEpOwogICAgICAgIHdoaWxlICgoYyA9IGMubmV4dCkgIT09IGIpIHsKICAgICAgICAgIGlmICgoY2EgPSBzY29yZShjKSkgPCBhYSkgewogICAgICAgICAgICBhID0gYywgYWEgPSBjYTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgYiA9IGEubmV4dDsKICAgICAgfQoKICAgICAgLy8gQ29tcHV0ZSB0aGUgZW5jbG9zaW5nIGNpcmNsZSBvZiB0aGUgZnJvbnQgY2hhaW4uCiAgICAgIGEgPSBbYi5fXSwgYyA9IGI7IHdoaWxlICgoYyA9IGMubmV4dCkgIT09IGIpIGEucHVzaChjLl8pOyBjID0gZW5jbG9zZShhKTsKCiAgICAgIC8vIFRyYW5zbGF0ZSB0aGUgY2lyY2xlcyB0byBwdXQgdGhlIGVuY2xvc2luZyBjaXJjbGUgYXJvdW5kIHRoZSBvcmlnaW4uCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIGEgPSBjaXJjbGVzW2ldLCBhLnggLT0gYy54LCBhLnkgLT0gYy55OwoKICAgICAgcmV0dXJuIGMucjsKICAgIH0KCiAgICBmdW5jdGlvbiBzaWJsaW5ncyhjaXJjbGVzKSB7CiAgICAgIHBhY2tFbmNsb3NlKGNpcmNsZXMpOwogICAgICByZXR1cm4gY2lyY2xlczsKICAgIH0KCiAgICBmdW5jdGlvbiBvcHRpb25hbChmKSB7CiAgICAgIHJldHVybiBmID09IG51bGwgPyBudWxsIDogcmVxdWlyZWQoZik7CiAgICB9CgogICAgZnVuY3Rpb24gcmVxdWlyZWQoZikgewogICAgICBpZiAodHlwZW9mIGYgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgcmV0dXJuIGY7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnRaZXJvKCkgewogICAgICByZXR1cm4gMDsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudCQ5KHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRSYWRpdXMkMShkKSB7CiAgICAgIHJldHVybiBNYXRoLnNxcnQoZC52YWx1ZSk7CiAgICB9CgogICAgZnVuY3Rpb24gaW5kZXgkMigpIHsKICAgICAgdmFyIHJhZGl1cyA9IG51bGwsCiAgICAgICAgICBkeCA9IDEsCiAgICAgICAgICBkeSA9IDEsCiAgICAgICAgICBwYWRkaW5nID0gY29uc3RhbnRaZXJvOwoKICAgICAgZnVuY3Rpb24gcGFjayhyb290KSB7CiAgICAgICAgcm9vdC54ID0gZHggLyAyLCByb290LnkgPSBkeSAvIDI7CiAgICAgICAgaWYgKHJhZGl1cykgewogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKHJhZGl1c0xlYWYocmFkaXVzKSkKICAgICAgICAgICAgICAuZWFjaEFmdGVyKHBhY2tDaGlsZHJlbihwYWRkaW5nLCAwLjUpKQogICAgICAgICAgICAgIC5lYWNoQmVmb3JlKHRyYW5zbGF0ZUNoaWxkKDEpKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKHJhZGl1c0xlYWYoZGVmYXVsdFJhZGl1cyQxKSkKICAgICAgICAgICAgICAuZWFjaEFmdGVyKHBhY2tDaGlsZHJlbihjb25zdGFudFplcm8sIDEpKQogICAgICAgICAgICAgIC5lYWNoQWZ0ZXIocGFja0NoaWxkcmVuKHBhZGRpbmcsIHJvb3QuciAvIE1hdGgubWluKGR4LCBkeSkpKQogICAgICAgICAgICAgIC5lYWNoQmVmb3JlKHRyYW5zbGF0ZUNoaWxkKE1hdGgubWluKGR4LCBkeSkgLyAoMiAqIHJvb3QucikpKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHJvb3Q7CiAgICAgIH0KCiAgICAgIHBhY2sucmFkaXVzID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhZGl1cyA9IG9wdGlvbmFsKHgpLCBwYWNrKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIHBhY2suc2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCBwYWNrKSA6IFtkeCwgZHldOwogICAgICB9OwoKICAgICAgcGFjay5wYWRkaW5nID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmcgPSB0eXBlb2YgeCA9PT0gImZ1bmN0aW9uIiA/IHggOiBjb25zdGFudCQ5KCt4KSwgcGFjaykgOiBwYWRkaW5nOwogICAgICB9OwoKICAgICAgcmV0dXJuIHBhY2s7CiAgICB9CgogICAgZnVuY3Rpb24gcmFkaXVzTGVhZihyYWRpdXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICBpZiAoIW5vZGUuY2hpbGRyZW4pIHsKICAgICAgICAgIG5vZGUuciA9IE1hdGgubWF4KDAsICtyYWRpdXMobm9kZSkgfHwgMCk7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBhY2tDaGlsZHJlbihwYWRkaW5nLCBrKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgaWYgKGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbikgewogICAgICAgICAgdmFyIGNoaWxkcmVuLAogICAgICAgICAgICAgIGksCiAgICAgICAgICAgICAgbiA9IGNoaWxkcmVuLmxlbmd0aCwKICAgICAgICAgICAgICByID0gcGFkZGluZyhub2RlKSAqIGsgfHwgMCwKICAgICAgICAgICAgICBlOwoKICAgICAgICAgIGlmIChyKSBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBjaGlsZHJlbltpXS5yICs9IHI7CiAgICAgICAgICBlID0gcGFja0VuY2xvc2UoY2hpbGRyZW4pOwogICAgICAgICAgaWYgKHIpIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIGNoaWxkcmVuW2ldLnIgLT0gcjsKICAgICAgICAgIG5vZGUuciA9IGUgKyByOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVDaGlsZChrKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IG5vZGUucGFyZW50OwogICAgICAgIG5vZGUuciAqPSBrOwogICAgICAgIGlmIChwYXJlbnQpIHsKICAgICAgICAgIG5vZGUueCA9IHBhcmVudC54ICsgayAqIG5vZGUueDsKICAgICAgICAgIG5vZGUueSA9IHBhcmVudC55ICsgayAqIG5vZGUueTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcm91bmROb2RlKG5vZGUpIHsKICAgICAgbm9kZS54MCA9IE1hdGgucm91bmQobm9kZS54MCk7CiAgICAgIG5vZGUueTAgPSBNYXRoLnJvdW5kKG5vZGUueTApOwogICAgICBub2RlLngxID0gTWF0aC5yb3VuZChub2RlLngxKTsKICAgICAgbm9kZS55MSA9IE1hdGgucm91bmQobm9kZS55MSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZW1hcERpY2UocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgbm9kZXMgPSBwYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICBub2RlLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIGsgPSBwYXJlbnQudmFsdWUgJiYgKHgxIC0geDApIC8gcGFyZW50LnZhbHVlOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUueTAgPSB5MCwgbm9kZS55MSA9IHkxOwogICAgICAgIG5vZGUueDAgPSB4MCwgbm9kZS54MSA9IHgwICs9IG5vZGUudmFsdWUgKiBrOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcGFydGl0aW9uKCkgewogICAgICB2YXIgZHggPSAxLAogICAgICAgICAgZHkgPSAxLAogICAgICAgICAgcGFkZGluZyA9IDAsCiAgICAgICAgICByb3VuZCA9IGZhbHNlOwoKICAgICAgZnVuY3Rpb24gcGFydGl0aW9uKHJvb3QpIHsKICAgICAgICB2YXIgbiA9IHJvb3QuaGVpZ2h0ICsgMTsKICAgICAgICByb290LngwID0KICAgICAgICByb290LnkwID0gcGFkZGluZzsKICAgICAgICByb290LngxID0gZHg7CiAgICAgICAgcm9vdC55MSA9IGR5IC8gbjsKICAgICAgICByb290LmVhY2hCZWZvcmUocG9zaXRpb25Ob2RlKGR5LCBuKSk7CiAgICAgICAgaWYgKHJvdW5kKSByb290LmVhY2hCZWZvcmUocm91bmROb2RlKTsKICAgICAgICByZXR1cm4gcm9vdDsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcG9zaXRpb25Ob2RlKGR5LCBuKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgIGlmIChub2RlLmNoaWxkcmVuKSB7CiAgICAgICAgICAgIHRyZWVtYXBEaWNlKG5vZGUsIG5vZGUueDAsIGR5ICogKG5vZGUuZGVwdGggKyAxKSAvIG4sIG5vZGUueDEsIGR5ICogKG5vZGUuZGVwdGggKyAyKSAvIG4pOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHgwID0gbm9kZS54MCwKICAgICAgICAgICAgICB5MCA9IG5vZGUueTAsCiAgICAgICAgICAgICAgeDEgPSBub2RlLngxIC0gcGFkZGluZywKICAgICAgICAgICAgICB5MSA9IG5vZGUueTEgLSBwYWRkaW5nOwogICAgICAgICAgaWYgKHgxIDwgeDApIHgwID0geDEgPSAoeDAgKyB4MSkgLyAyOwogICAgICAgICAgaWYgKHkxIDwgeTApIHkwID0geTEgPSAoeTAgKyB5MSkgLyAyOwogICAgICAgICAgbm9kZS54MCA9IHgwOwogICAgICAgICAgbm9kZS55MCA9IHkwOwogICAgICAgICAgbm9kZS54MSA9IHgxOwogICAgICAgICAgbm9kZS55MSA9IHkxOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHBhcnRpdGlvbi5yb3VuZCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyb3VuZCA9ICEheCwgcGFydGl0aW9uKSA6IHJvdW5kOwogICAgICB9OwoKICAgICAgcGFydGl0aW9uLnNpemUgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZHggPSAreFswXSwgZHkgPSAreFsxXSwgcGFydGl0aW9uKSA6IFtkeCwgZHldOwogICAgICB9OwoKICAgICAgcGFydGl0aW9uLnBhZGRpbmcgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZyA9ICt4LCBwYXJ0aXRpb24pIDogcGFkZGluZzsKICAgICAgfTsKCiAgICAgIHJldHVybiBwYXJ0aXRpb247CiAgICB9CgogICAgdmFyIGtleVByZWZpeCQxID0gIiQiLCAvLyBQcm90ZWN0IGFnYWluc3Qga2V5cyBsaWtlIOKAnF9fcHJvdG9fX+KAnS4KICAgICAgICBwcmVyb290ID0ge2RlcHRoOiAtMX0sCiAgICAgICAgYW1iaWd1b3VzID0ge307CgogICAgZnVuY3Rpb24gZGVmYXVsdElkKGQpIHsKICAgICAgcmV0dXJuIGQuaWQ7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFBhcmVudElkKGQpIHsKICAgICAgcmV0dXJuIGQucGFyZW50SWQ7CiAgICB9CgogICAgZnVuY3Rpb24gc3RyYXRpZnkoKSB7CiAgICAgIHZhciBpZCA9IGRlZmF1bHRJZCwKICAgICAgICAgIHBhcmVudElkID0gZGVmYXVsdFBhcmVudElkOwoKICAgICAgZnVuY3Rpb24gc3RyYXRpZnkoZGF0YSkgewogICAgICAgIHZhciBkLAogICAgICAgICAgICBpLAogICAgICAgICAgICBuID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIHJvb3QsCiAgICAgICAgICAgIHBhcmVudCwKICAgICAgICAgICAgbm9kZSwKICAgICAgICAgICAgbm9kZXMgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIG5vZGVJZCwKICAgICAgICAgICAgbm9kZUtleSwKICAgICAgICAgICAgbm9kZUJ5S2V5ID0ge307CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGQgPSBkYXRhW2ldLCBub2RlID0gbm9kZXNbaV0gPSBuZXcgTm9kZSQxKGQpOwogICAgICAgICAgaWYgKChub2RlSWQgPSBpZChkLCBpLCBkYXRhKSkgIT0gbnVsbCAmJiAobm9kZUlkICs9ICIiKSkgewogICAgICAgICAgICBub2RlS2V5ID0ga2V5UHJlZml4JDEgKyAobm9kZS5pZCA9IG5vZGVJZCk7CiAgICAgICAgICAgIG5vZGVCeUtleVtub2RlS2V5XSA9IG5vZGVLZXkgaW4gbm9kZUJ5S2V5ID8gYW1iaWd1b3VzIDogbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIG5vZGUgPSBub2Rlc1tpXSwgbm9kZUlkID0gcGFyZW50SWQoZGF0YVtpXSwgaSwgZGF0YSk7CiAgICAgICAgICBpZiAobm9kZUlkID09IG51bGwgfHwgIShub2RlSWQgKz0gIiIpKSB7CiAgICAgICAgICAgIGlmIChyb290KSB0aHJvdyBuZXcgRXJyb3IoIm11bHRpcGxlIHJvb3RzIik7CiAgICAgICAgICAgIHJvb3QgPSBub2RlOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcGFyZW50ID0gbm9kZUJ5S2V5W2tleVByZWZpeCQxICsgbm9kZUlkXTsKICAgICAgICAgICAgaWYgKCFwYXJlbnQpIHRocm93IG5ldyBFcnJvcigibWlzc2luZzogIiArIG5vZGVJZCk7CiAgICAgICAgICAgIGlmIChwYXJlbnQgPT09IGFtYmlndW91cykgdGhyb3cgbmV3IEVycm9yKCJhbWJpZ3VvdXM6ICIgKyBub2RlSWQpOwogICAgICAgICAgICBpZiAocGFyZW50LmNoaWxkcmVuKSBwYXJlbnQuY2hpbGRyZW4ucHVzaChub2RlKTsKICAgICAgICAgICAgZWxzZSBwYXJlbnQuY2hpbGRyZW4gPSBbbm9kZV07CiAgICAgICAgICAgIG5vZGUucGFyZW50ID0gcGFyZW50OwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKCFyb290KSB0aHJvdyBuZXcgRXJyb3IoIm5vIHJvb3QiKTsKICAgICAgICByb290LnBhcmVudCA9IHByZXJvb3Q7CiAgICAgICAgcm9vdC5lYWNoQmVmb3JlKGZ1bmN0aW9uKG5vZGUpIHsgbm9kZS5kZXB0aCA9IG5vZGUucGFyZW50LmRlcHRoICsgMTsgLS1uOyB9KS5lYWNoQmVmb3JlKGNvbXB1dGVIZWlnaHQpOwogICAgICAgIHJvb3QucGFyZW50ID0gbnVsbDsKICAgICAgICBpZiAobiA+IDApIHRocm93IG5ldyBFcnJvcigiY3ljbGUiKTsKCiAgICAgICAgcmV0dXJuIHJvb3Q7CiAgICAgIH0KCiAgICAgIHN0cmF0aWZ5LmlkID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGlkID0gcmVxdWlyZWQoeCksIHN0cmF0aWZ5KSA6IGlkOwogICAgICB9OwoKICAgICAgc3RyYXRpZnkucGFyZW50SWQgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFyZW50SWQgPSByZXF1aXJlZCh4KSwgc3RyYXRpZnkpIDogcGFyZW50SWQ7CiAgICAgIH07CgogICAgICByZXR1cm4gc3RyYXRpZnk7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFNlcGFyYXRpb24kMShhLCBiKSB7CiAgICAgIHJldHVybiBhLnBhcmVudCA9PT0gYi5wYXJlbnQgPyAxIDogMjsKICAgIH0KCiAgICAvLyBmdW5jdGlvbiByYWRpYWxTZXBhcmF0aW9uKGEsIGIpIHsKICAgIC8vICAgcmV0dXJuIChhLnBhcmVudCA9PT0gYi5wYXJlbnQgPyAxIDogMikgLyBhLmRlcHRoOwogICAgLy8gfQoKICAgIC8vIFRoaXMgZnVuY3Rpb24gaXMgdXNlZCB0byB0cmF2ZXJzZSB0aGUgbGVmdCBjb250b3VyIG9mIGEgc3VidHJlZSAob3IKICAgIC8vIHN1YmZvcmVzdCkuIEl0IHJldHVybnMgdGhlIHN1Y2Nlc3NvciBvZiB2IG9uIHRoaXMgY29udG91ci4gVGhpcyBzdWNjZXNzb3IgaXMKICAgIC8vIGVpdGhlciBnaXZlbiBieSB0aGUgbGVmdG1vc3QgY2hpbGQgb2YgdiBvciBieSB0aGUgdGhyZWFkIG9mIHYuIFRoZSBmdW5jdGlvbgogICAgLy8gcmV0dXJucyBudWxsIGlmIGFuZCBvbmx5IGlmIHYgaXMgb24gdGhlIGhpZ2hlc3QgbGV2ZWwgb2YgaXRzIHN1YnRyZWUuCiAgICBmdW5jdGlvbiBuZXh0TGVmdCh2KSB7CiAgICAgIHZhciBjaGlsZHJlbiA9IHYuY2hpbGRyZW47CiAgICAgIHJldHVybiBjaGlsZHJlbiA/IGNoaWxkcmVuWzBdIDogdi50OwogICAgfQoKICAgIC8vIFRoaXMgZnVuY3Rpb24gd29ya3MgYW5hbG9nb3VzbHkgdG8gbmV4dExlZnQuCiAgICBmdW5jdGlvbiBuZXh0UmlnaHQodikgewogICAgICB2YXIgY2hpbGRyZW4gPSB2LmNoaWxkcmVuOwogICAgICByZXR1cm4gY2hpbGRyZW4gPyBjaGlsZHJlbltjaGlsZHJlbi5sZW5ndGggLSAxXSA6IHYudDsKICAgIH0KCiAgICAvLyBTaGlmdHMgdGhlIGN1cnJlbnQgc3VidHJlZSByb290ZWQgYXQgdysuIFRoaXMgaXMgZG9uZSBieSBpbmNyZWFzaW5nCiAgICAvLyBwcmVsaW0odyspIGFuZCBtb2QodyspIGJ5IHNoaWZ0LgogICAgZnVuY3Rpb24gbW92ZVN1YnRyZWUod20sIHdwLCBzaGlmdCkgewogICAgICB2YXIgY2hhbmdlID0gc2hpZnQgLyAod3AuaSAtIHdtLmkpOwogICAgICB3cC5jIC09IGNoYW5nZTsKICAgICAgd3AucyArPSBzaGlmdDsKICAgICAgd20uYyArPSBjaGFuZ2U7CiAgICAgIHdwLnogKz0gc2hpZnQ7CiAgICAgIHdwLm0gKz0gc2hpZnQ7CiAgICB9CgogICAgLy8gQWxsIG90aGVyIHNoaWZ0cywgYXBwbGllZCB0byB0aGUgc21hbGxlciBzdWJ0cmVlcyBiZXR3ZWVuIHctIGFuZCB3KywgYXJlCiAgICAvLyBwZXJmb3JtZWQgYnkgdGhpcyBmdW5jdGlvbi4gVG8gcHJlcGFyZSB0aGUgc2hpZnRzLCB3ZSBoYXZlIHRvIGFkanVzdAogICAgLy8gY2hhbmdlKHcrKSwgc2hpZnQodyspLCBhbmQgY2hhbmdlKHctKS4KICAgIGZ1bmN0aW9uIGV4ZWN1dGVTaGlmdHModikgewogICAgICB2YXIgc2hpZnQgPSAwLAogICAgICAgICAgY2hhbmdlID0gMCwKICAgICAgICAgIGNoaWxkcmVuID0gdi5jaGlsZHJlbiwKICAgICAgICAgIGkgPSBjaGlsZHJlbi5sZW5ndGgsCiAgICAgICAgICB3OwogICAgICB3aGlsZSAoLS1pID49IDApIHsKICAgICAgICB3ID0gY2hpbGRyZW5baV07CiAgICAgICAgdy56ICs9IHNoaWZ0OwogICAgICAgIHcubSArPSBzaGlmdDsKICAgICAgICBzaGlmdCArPSB3LnMgKyAoY2hhbmdlICs9IHcuYyk7CiAgICAgIH0KICAgIH0KCiAgICAvLyBJZiB2aS3igJlzIGFuY2VzdG9yIGlzIGEgc2libGluZyBvZiB2LCByZXR1cm5zIHZpLeKAmXMgYW5jZXN0b3IuIE90aGVyd2lzZSwKICAgIC8vIHJldHVybnMgdGhlIHNwZWNpZmllZCAoZGVmYXVsdCkgYW5jZXN0b3IuCiAgICBmdW5jdGlvbiBuZXh0QW5jZXN0b3IodmltLCB2LCBhbmNlc3RvcikgewogICAgICByZXR1cm4gdmltLmEucGFyZW50ID09PSB2LnBhcmVudCA/IHZpbS5hIDogYW5jZXN0b3I7CiAgICB9CgogICAgZnVuY3Rpb24gVHJlZU5vZGUobm9kZSwgaSkgewogICAgICB0aGlzLl8gPSBub2RlOwogICAgICB0aGlzLnBhcmVudCA9IG51bGw7CiAgICAgIHRoaXMuY2hpbGRyZW4gPSBudWxsOwogICAgICB0aGlzLkEgPSBudWxsOyAvLyBkZWZhdWx0IGFuY2VzdG9yCiAgICAgIHRoaXMuYSA9IHRoaXM7IC8vIGFuY2VzdG9yCiAgICAgIHRoaXMueiA9IDA7IC8vIHByZWxpbQogICAgICB0aGlzLm0gPSAwOyAvLyBtb2QKICAgICAgdGhpcy5jID0gMDsgLy8gY2hhbmdlCiAgICAgIHRoaXMucyA9IDA7IC8vIHNoaWZ0CiAgICAgIHRoaXMudCA9IG51bGw7IC8vIHRocmVhZAogICAgICB0aGlzLmkgPSBpOyAvLyBudW1iZXIKICAgIH0KCiAgICBUcmVlTm9kZS5wcm90b3R5cGUgPSBPYmplY3QuY3JlYXRlKE5vZGUkMS5wcm90b3R5cGUpOwoKICAgIGZ1bmN0aW9uIHRyZWVSb290KHJvb3QpIHsKICAgICAgdmFyIHRyZWUgPSBuZXcgVHJlZU5vZGUocm9vdCwgMCksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZXMgPSBbdHJlZV0sCiAgICAgICAgICBjaGlsZCwKICAgICAgICAgIGNoaWxkcmVuLAogICAgICAgICAgaSwKICAgICAgICAgIG47CgogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgaWYgKGNoaWxkcmVuID0gbm9kZS5fLmNoaWxkcmVuKSB7CiAgICAgICAgICBub2RlLmNoaWxkcmVuID0gbmV3IEFycmF5KG4gPSBjaGlsZHJlbi5sZW5ndGgpOwogICAgICAgICAgZm9yIChpID0gbiAtIDE7IGkgPj0gMDsgLS1pKSB7CiAgICAgICAgICAgIG5vZGVzLnB1c2goY2hpbGQgPSBub2RlLmNoaWxkcmVuW2ldID0gbmV3IFRyZWVOb2RlKGNoaWxkcmVuW2ldLCBpKSk7CiAgICAgICAgICAgIGNoaWxkLnBhcmVudCA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAodHJlZS5wYXJlbnQgPSBuZXcgVHJlZU5vZGUobnVsbCwgMCkpLmNoaWxkcmVuID0gW3RyZWVdOwogICAgICByZXR1cm4gdHJlZTsKICAgIH0KCiAgICAvLyBOb2RlLWxpbmsgdHJlZSBkaWFncmFtIHVzaW5nIHRoZSBSZWluZ29sZC1UaWxmb3JkICJ0aWR5IiBhbGdvcml0aG0KICAgIGZ1bmN0aW9uIHRyZWUoKSB7CiAgICAgIHZhciBzZXBhcmF0aW9uID0gZGVmYXVsdFNlcGFyYXRpb24kMSwKICAgICAgICAgIGR4ID0gMSwKICAgICAgICAgIGR5ID0gMSwKICAgICAgICAgIG5vZGVTaXplID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIHRyZWUocm9vdCkgewogICAgICAgIHZhciB0ID0gdHJlZVJvb3Qocm9vdCk7CgogICAgICAgIC8vIENvbXB1dGUgdGhlIGxheW91dCB1c2luZyBCdWNoaGVpbSBldCBhbC7igJlzIGFsZ29yaXRobS4KICAgICAgICB0LmVhY2hBZnRlcihmaXJzdFdhbGspLCB0LnBhcmVudC5tID0gLXQuejsKICAgICAgICB0LmVhY2hCZWZvcmUoc2Vjb25kV2Fsayk7CgogICAgICAgIC8vIElmIGEgZml4ZWQgbm9kZSBzaXplIGlzIHNwZWNpZmllZCwgc2NhbGUgeCBhbmQgeS4KICAgICAgICBpZiAobm9kZVNpemUpIHJvb3QuZWFjaEJlZm9yZShzaXplTm9kZSk7CgogICAgICAgIC8vIElmIGEgZml4ZWQgdHJlZSBzaXplIGlzIHNwZWNpZmllZCwgc2NhbGUgeCBhbmQgeSBiYXNlZCBvbiB0aGUgZXh0ZW50LgogICAgICAgIC8vIENvbXB1dGUgdGhlIGxlZnQtbW9zdCwgcmlnaHQtbW9zdCwgYW5kIGRlcHRoLW1vc3Qgbm9kZXMgZm9yIGV4dGVudHMuCiAgICAgICAgZWxzZSB7CiAgICAgICAgICB2YXIgbGVmdCA9IHJvb3QsCiAgICAgICAgICAgICAgcmlnaHQgPSByb290LAogICAgICAgICAgICAgIGJvdHRvbSA9IHJvb3Q7CiAgICAgICAgICByb290LmVhY2hCZWZvcmUoZnVuY3Rpb24obm9kZSkgewogICAgICAgICAgICBpZiAobm9kZS54IDwgbGVmdC54KSBsZWZ0ID0gbm9kZTsKICAgICAgICAgICAgaWYgKG5vZGUueCA+IHJpZ2h0LngpIHJpZ2h0ID0gbm9kZTsKICAgICAgICAgICAgaWYgKG5vZGUuZGVwdGggPiBib3R0b20uZGVwdGgpIGJvdHRvbSA9IG5vZGU7CiAgICAgICAgICB9KTsKICAgICAgICAgIHZhciBzID0gbGVmdCA9PT0gcmlnaHQgPyAxIDogc2VwYXJhdGlvbihsZWZ0LCByaWdodCkgLyAyLAogICAgICAgICAgICAgIHR4ID0gcyAtIGxlZnQueCwKICAgICAgICAgICAgICBreCA9IGR4IC8gKHJpZ2h0LnggKyBzICsgdHgpLAogICAgICAgICAgICAgIGt5ID0gZHkgLyAoYm90dG9tLmRlcHRoIHx8IDEpOwogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgICAgbm9kZS54ID0gKG5vZGUueCArIHR4KSAqIGt4OwogICAgICAgICAgICBub2RlLnkgPSBub2RlLmRlcHRoICoga3k7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIHJldHVybiByb290OwogICAgICB9CgogICAgICAvLyBDb21wdXRlcyBhIHByZWxpbWluYXJ5IHgtY29vcmRpbmF0ZSBmb3Igdi4gQmVmb3JlIHRoYXQsIEZJUlNUIFdBTEsgaXMKICAgICAgLy8gYXBwbGllZCByZWN1cnNpdmVseSB0byB0aGUgY2hpbGRyZW4gb2YgdiwgYXMgd2VsbCBhcyB0aGUgZnVuY3Rpb24KICAgICAgLy8gQVBQT1JUSU9OLiBBZnRlciBzcGFjaW5nIG91dCB0aGUgY2hpbGRyZW4gYnkgY2FsbGluZyBFWEVDVVRFIFNISUZUUywgdGhlCiAgICAgIC8vIG5vZGUgdiBpcyBwbGFjZWQgdG8gdGhlIG1pZHBvaW50IG9mIGl0cyBvdXRlcm1vc3QgY2hpbGRyZW4uCiAgICAgIGZ1bmN0aW9uIGZpcnN0V2Fsayh2KSB7CiAgICAgICAgdmFyIGNoaWxkcmVuID0gdi5jaGlsZHJlbiwKICAgICAgICAgICAgc2libGluZ3MgPSB2LnBhcmVudC5jaGlsZHJlbiwKICAgICAgICAgICAgdyA9IHYuaSA/IHNpYmxpbmdzW3YuaSAtIDFdIDogbnVsbDsKICAgICAgICBpZiAoY2hpbGRyZW4pIHsKICAgICAgICAgIGV4ZWN1dGVTaGlmdHModik7CiAgICAgICAgICB2YXIgbWlkcG9pbnQgPSAoY2hpbGRyZW5bMF0ueiArIGNoaWxkcmVuW2NoaWxkcmVuLmxlbmd0aCAtIDFdLnopIC8gMjsKICAgICAgICAgIGlmICh3KSB7CiAgICAgICAgICAgIHYueiA9IHcueiArIHNlcGFyYXRpb24odi5fLCB3Ll8pOwogICAgICAgICAgICB2Lm0gPSB2LnogLSBtaWRwb2ludDsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHYueiA9IG1pZHBvaW50OwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSBpZiAodykgewogICAgICAgICAgdi56ID0gdy56ICsgc2VwYXJhdGlvbih2Ll8sIHcuXyk7CiAgICAgICAgfQogICAgICAgIHYucGFyZW50LkEgPSBhcHBvcnRpb24odiwgdywgdi5wYXJlbnQuQSB8fCBzaWJsaW5nc1swXSk7CiAgICAgIH0KCiAgICAgIC8vIENvbXB1dGVzIGFsbCByZWFsIHgtY29vcmRpbmF0ZXMgYnkgc3VtbWluZyB1cCB0aGUgbW9kaWZpZXJzIHJlY3Vyc2l2ZWx5LgogICAgICBmdW5jdGlvbiBzZWNvbmRXYWxrKHYpIHsKICAgICAgICB2Ll8ueCA9IHYueiArIHYucGFyZW50Lm07CiAgICAgICAgdi5tICs9IHYucGFyZW50Lm07CiAgICAgIH0KCiAgICAgIC8vIFRoZSBjb3JlIG9mIHRoZSBhbGdvcml0aG0uIEhlcmUsIGEgbmV3IHN1YnRyZWUgaXMgY29tYmluZWQgd2l0aCB0aGUKICAgICAgLy8gcHJldmlvdXMgc3VidHJlZXMuIFRocmVhZHMgYXJlIHVzZWQgdG8gdHJhdmVyc2UgdGhlIGluc2lkZSBhbmQgb3V0c2lkZQogICAgICAvLyBjb250b3VycyBvZiB0aGUgbGVmdCBhbmQgcmlnaHQgc3VidHJlZSB1cCB0byB0aGUgaGlnaGVzdCBjb21tb24gbGV2ZWwuIFRoZQogICAgICAvLyB2ZXJ0aWNlcyB1c2VkIGZvciB0aGUgdHJhdmVyc2FscyBhcmUgdmkrLCB2aS0sIHZvLSwgYW5kIHZvKywgd2hlcmUgdGhlCiAgICAgIC8vIHN1cGVyc2NyaXB0IG8gbWVhbnMgb3V0c2lkZSBhbmQgaSBtZWFucyBpbnNpZGUsIHRoZSBzdWJzY3JpcHQgLSBtZWFucyBsZWZ0CiAgICAgIC8vIHN1YnRyZWUgYW5kICsgbWVhbnMgcmlnaHQgc3VidHJlZS4gRm9yIHN1bW1pbmcgdXAgdGhlIG1vZGlmaWVycyBhbG9uZyB0aGUKICAgICAgLy8gY29udG91ciwgd2UgdXNlIHJlc3BlY3RpdmUgdmFyaWFibGVzIHNpKywgc2ktLCBzby0sIGFuZCBzbysuIFdoZW5ldmVyIHR3bwogICAgICAvLyBub2RlcyBvZiB0aGUgaW5zaWRlIGNvbnRvdXJzIGNvbmZsaWN0LCB3ZSBjb21wdXRlIHRoZSBsZWZ0IG9uZSBvZiB0aGUKICAgICAgLy8gZ3JlYXRlc3QgdW5jb21tb24gYW5jZXN0b3JzIHVzaW5nIHRoZSBmdW5jdGlvbiBBTkNFU1RPUiBhbmQgY2FsbCBNT1ZFCiAgICAgIC8vIFNVQlRSRUUgdG8gc2hpZnQgdGhlIHN1YnRyZWUgYW5kIHByZXBhcmUgdGhlIHNoaWZ0cyBvZiBzbWFsbGVyIHN1YnRyZWVzLgogICAgICAvLyBGaW5hbGx5LCB3ZSBhZGQgYSBuZXcgdGhyZWFkIChpZiBuZWNlc3NhcnkpLgogICAgICBmdW5jdGlvbiBhcHBvcnRpb24odiwgdywgYW5jZXN0b3IpIHsKICAgICAgICBpZiAodykgewogICAgICAgICAgdmFyIHZpcCA9IHYsCiAgICAgICAgICAgICAgdm9wID0gdiwKICAgICAgICAgICAgICB2aW0gPSB3LAogICAgICAgICAgICAgIHZvbSA9IHZpcC5wYXJlbnQuY2hpbGRyZW5bMF0sCiAgICAgICAgICAgICAgc2lwID0gdmlwLm0sCiAgICAgICAgICAgICAgc29wID0gdm9wLm0sCiAgICAgICAgICAgICAgc2ltID0gdmltLm0sCiAgICAgICAgICAgICAgc29tID0gdm9tLm0sCiAgICAgICAgICAgICAgc2hpZnQ7CiAgICAgICAgICB3aGlsZSAodmltID0gbmV4dFJpZ2h0KHZpbSksIHZpcCA9IG5leHRMZWZ0KHZpcCksIHZpbSAmJiB2aXApIHsKICAgICAgICAgICAgdm9tID0gbmV4dExlZnQodm9tKTsKICAgICAgICAgICAgdm9wID0gbmV4dFJpZ2h0KHZvcCk7CiAgICAgICAgICAgIHZvcC5hID0gdjsKICAgICAgICAgICAgc2hpZnQgPSB2aW0ueiArIHNpbSAtIHZpcC56IC0gc2lwICsgc2VwYXJhdGlvbih2aW0uXywgdmlwLl8pOwogICAgICAgICAgICBpZiAoc2hpZnQgPiAwKSB7CiAgICAgICAgICAgICAgbW92ZVN1YnRyZWUobmV4dEFuY2VzdG9yKHZpbSwgdiwgYW5jZXN0b3IpLCB2LCBzaGlmdCk7CiAgICAgICAgICAgICAgc2lwICs9IHNoaWZ0OwogICAgICAgICAgICAgIHNvcCArPSBzaGlmdDsKICAgICAgICAgICAgfQogICAgICAgICAgICBzaW0gKz0gdmltLm07CiAgICAgICAgICAgIHNpcCArPSB2aXAubTsKICAgICAgICAgICAgc29tICs9IHZvbS5tOwogICAgICAgICAgICBzb3AgKz0gdm9wLm07CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodmltICYmICFuZXh0UmlnaHQodm9wKSkgewogICAgICAgICAgICB2b3AudCA9IHZpbTsKICAgICAgICAgICAgdm9wLm0gKz0gc2ltIC0gc29wOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHZpcCAmJiAhbmV4dExlZnQodm9tKSkgewogICAgICAgICAgICB2b20udCA9IHZpcDsKICAgICAgICAgICAgdm9tLm0gKz0gc2lwIC0gc29tOwogICAgICAgICAgICBhbmNlc3RvciA9IHY7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBhbmNlc3RvcjsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2l6ZU5vZGUobm9kZSkgewogICAgICAgIG5vZGUueCAqPSBkeDsKICAgICAgICBub2RlLnkgPSBub2RlLmRlcHRoICogZHk7CiAgICAgIH0KCiAgICAgIHRyZWUuc2VwYXJhdGlvbiA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzZXBhcmF0aW9uID0geCwgdHJlZSkgOiBzZXBhcmF0aW9uOwogICAgICB9OwoKICAgICAgdHJlZS5zaXplID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG5vZGVTaXplID0gZmFsc2UsIGR4ID0gK3hbMF0sIGR5ID0gK3hbMV0sIHRyZWUpIDogKG5vZGVTaXplID8gbnVsbCA6IFtkeCwgZHldKTsKICAgICAgfTsKCiAgICAgIHRyZWUubm9kZVNpemUgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAobm9kZVNpemUgPSB0cnVlLCBkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCB0cmVlKSA6IChub2RlU2l6ZSA/IFtkeCwgZHldIDogbnVsbCk7CiAgICAgIH07CgogICAgICByZXR1cm4gdHJlZTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlbWFwU2xpY2UocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgbm9kZXMgPSBwYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICBub2RlLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIGsgPSBwYXJlbnQudmFsdWUgJiYgKHkxIC0geTApIC8gcGFyZW50LnZhbHVlOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUueDAgPSB4MCwgbm9kZS54MSA9IHgxOwogICAgICAgIG5vZGUueTAgPSB5MCwgbm9kZS55MSA9IHkwICs9IG5vZGUudmFsdWUgKiBrOwogICAgICB9CiAgICB9CgogICAgdmFyIHBoaSA9ICgxICsgTWF0aC5zcXJ0KDUpKSAvIDI7CgogICAgZnVuY3Rpb24gc3F1YXJpZnlSYXRpbyhyYXRpbywgcGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgcm93cyA9IFtdLAogICAgICAgICAgbm9kZXMgPSBwYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICByb3csCiAgICAgICAgICBub2RlVmFsdWUsCiAgICAgICAgICBpMCA9IDAsCiAgICAgICAgICBpMSA9IDAsCiAgICAgICAgICBuID0gbm9kZXMubGVuZ3RoLAogICAgICAgICAgZHgsIGR5LAogICAgICAgICAgdmFsdWUgPSBwYXJlbnQudmFsdWUsCiAgICAgICAgICBzdW1WYWx1ZSwKICAgICAgICAgIG1pblZhbHVlLAogICAgICAgICAgbWF4VmFsdWUsCiAgICAgICAgICBuZXdSYXRpbywKICAgICAgICAgIG1pblJhdGlvLAogICAgICAgICAgYWxwaGEsCiAgICAgICAgICBiZXRhOwoKICAgICAgd2hpbGUgKGkwIDwgbikgewogICAgICAgIGR4ID0geDEgLSB4MCwgZHkgPSB5MSAtIHkwOwoKICAgICAgICAvLyBGaW5kIHRoZSBuZXh0IG5vbi1lbXB0eSBub2RlLgogICAgICAgIGRvIHN1bVZhbHVlID0gbm9kZXNbaTErK10udmFsdWU7IHdoaWxlICghc3VtVmFsdWUgJiYgaTEgPCBuKTsKICAgICAgICBtaW5WYWx1ZSA9IG1heFZhbHVlID0gc3VtVmFsdWU7CiAgICAgICAgYWxwaGEgPSBNYXRoLm1heChkeSAvIGR4LCBkeCAvIGR5KSAvICh2YWx1ZSAqIHJhdGlvKTsKICAgICAgICBiZXRhID0gc3VtVmFsdWUgKiBzdW1WYWx1ZSAqIGFscGhhOwogICAgICAgIG1pblJhdGlvID0gTWF0aC5tYXgobWF4VmFsdWUgLyBiZXRhLCBiZXRhIC8gbWluVmFsdWUpOwoKICAgICAgICAvLyBLZWVwIGFkZGluZyBub2RlcyB3aGlsZSB0aGUgYXNwZWN0IHJhdGlvIG1haW50YWlucyBvciBpbXByb3Zlcy4KICAgICAgICBmb3IgKDsgaTEgPCBuOyArK2kxKSB7CiAgICAgICAgICBzdW1WYWx1ZSArPSBub2RlVmFsdWUgPSBub2Rlc1tpMV0udmFsdWU7CiAgICAgICAgICBpZiAobm9kZVZhbHVlIDwgbWluVmFsdWUpIG1pblZhbHVlID0gbm9kZVZhbHVlOwogICAgICAgICAgaWYgKG5vZGVWYWx1ZSA+IG1heFZhbHVlKSBtYXhWYWx1ZSA9IG5vZGVWYWx1ZTsKICAgICAgICAgIGJldGEgPSBzdW1WYWx1ZSAqIHN1bVZhbHVlICogYWxwaGE7CiAgICAgICAgICBuZXdSYXRpbyA9IE1hdGgubWF4KG1heFZhbHVlIC8gYmV0YSwgYmV0YSAvIG1pblZhbHVlKTsKICAgICAgICAgIGlmIChuZXdSYXRpbyA+IG1pblJhdGlvKSB7IHN1bVZhbHVlIC09IG5vZGVWYWx1ZTsgYnJlYWs7IH0KICAgICAgICAgIG1pblJhdGlvID0gbmV3UmF0aW87CiAgICAgICAgfQoKICAgICAgICAvLyBQb3NpdGlvbiBhbmQgcmVjb3JkIHRoZSByb3cgb3JpZW50YXRpb24uCiAgICAgICAgcm93cy5wdXNoKHJvdyA9IHt2YWx1ZTogc3VtVmFsdWUsIGRpY2U6IGR4IDwgZHksIGNoaWxkcmVuOiBub2Rlcy5zbGljZShpMCwgaTEpfSk7CiAgICAgICAgaWYgKHJvdy5kaWNlKSB0cmVlbWFwRGljZShyb3csIHgwLCB5MCwgeDEsIHZhbHVlID8geTAgKz0gZHkgKiBzdW1WYWx1ZSAvIHZhbHVlIDogeTEpOwogICAgICAgIGVsc2UgdHJlZW1hcFNsaWNlKHJvdywgeDAsIHkwLCB2YWx1ZSA/IHgwICs9IGR4ICogc3VtVmFsdWUgLyB2YWx1ZSA6IHgxLCB5MSk7CiAgICAgICAgdmFsdWUgLT0gc3VtVmFsdWUsIGkwID0gaTE7CiAgICAgIH0KCiAgICAgIHJldHVybiByb3dzOwogICAgfQoKICAgIHZhciBzcXVhcmlmeSA9IChmdW5jdGlvbiBjdXN0b20ocmF0aW8pIHsKCiAgICAgIGZ1bmN0aW9uIHNxdWFyaWZ5KHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgICBzcXVhcmlmeVJhdGlvKHJhdGlvLCBwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKTsKICAgICAgfQoKICAgICAgc3F1YXJpZnkucmF0aW8gPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgoeCA9ICt4KSA+IDEgPyB4IDogMSk7CiAgICAgIH07CgogICAgICByZXR1cm4gc3F1YXJpZnk7CiAgICB9KShwaGkpOwoKICAgIGZ1bmN0aW9uIGluZGV4JDMoKSB7CiAgICAgIHZhciB0aWxlID0gc3F1YXJpZnksCiAgICAgICAgICByb3VuZCA9IGZhbHNlLAogICAgICAgICAgZHggPSAxLAogICAgICAgICAgZHkgPSAxLAogICAgICAgICAgcGFkZGluZ1N0YWNrID0gWzBdLAogICAgICAgICAgcGFkZGluZ0lubmVyID0gY29uc3RhbnRaZXJvLAogICAgICAgICAgcGFkZGluZ1RvcCA9IGNvbnN0YW50WmVybywKICAgICAgICAgIHBhZGRpbmdSaWdodCA9IGNvbnN0YW50WmVybywKICAgICAgICAgIHBhZGRpbmdCb3R0b20gPSBjb25zdGFudFplcm8sCiAgICAgICAgICBwYWRkaW5nTGVmdCA9IGNvbnN0YW50WmVybzsKCiAgICAgIGZ1bmN0aW9uIHRyZWVtYXAocm9vdCkgewogICAgICAgIHJvb3QueDAgPQogICAgICAgIHJvb3QueTAgPSAwOwogICAgICAgIHJvb3QueDEgPSBkeDsKICAgICAgICByb290LnkxID0gZHk7CiAgICAgICAgcm9vdC5lYWNoQmVmb3JlKHBvc2l0aW9uTm9kZSk7CiAgICAgICAgcGFkZGluZ1N0YWNrID0gWzBdOwogICAgICAgIGlmIChyb3VuZCkgcm9vdC5lYWNoQmVmb3JlKHJvdW5kTm9kZSk7CiAgICAgICAgcmV0dXJuIHJvb3Q7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBvc2l0aW9uTm9kZShub2RlKSB7CiAgICAgICAgdmFyIHAgPSBwYWRkaW5nU3RhY2tbbm9kZS5kZXB0aF0sCiAgICAgICAgICAgIHgwID0gbm9kZS54MCArIHAsCiAgICAgICAgICAgIHkwID0gbm9kZS55MCArIHAsCiAgICAgICAgICAgIHgxID0gbm9kZS54MSAtIHAsCiAgICAgICAgICAgIHkxID0gbm9kZS55MSAtIHA7CiAgICAgICAgaWYgKHgxIDwgeDApIHgwID0geDEgPSAoeDAgKyB4MSkgLyAyOwogICAgICAgIGlmICh5MSA8IHkwKSB5MCA9IHkxID0gKHkwICsgeTEpIC8gMjsKICAgICAgICBub2RlLngwID0geDA7CiAgICAgICAgbm9kZS55MCA9IHkwOwogICAgICAgIG5vZGUueDEgPSB4MTsKICAgICAgICBub2RlLnkxID0geTE7CiAgICAgICAgaWYgKG5vZGUuY2hpbGRyZW4pIHsKICAgICAgICAgIHAgPSBwYWRkaW5nU3RhY2tbbm9kZS5kZXB0aCArIDFdID0gcGFkZGluZ0lubmVyKG5vZGUpIC8gMjsKICAgICAgICAgIHgwICs9IHBhZGRpbmdMZWZ0KG5vZGUpIC0gcDsKICAgICAgICAgIHkwICs9IHBhZGRpbmdUb3Aobm9kZSkgLSBwOwogICAgICAgICAgeDEgLT0gcGFkZGluZ1JpZ2h0KG5vZGUpIC0gcDsKICAgICAgICAgIHkxIC09IHBhZGRpbmdCb3R0b20obm9kZSkgLSBwOwogICAgICAgICAgaWYgKHgxIDwgeDApIHgwID0geDEgPSAoeDAgKyB4MSkgLyAyOwogICAgICAgICAgaWYgKHkxIDwgeTApIHkwID0geTEgPSAoeTAgKyB5MSkgLyAyOwogICAgICAgICAgdGlsZShub2RlLCB4MCwgeTAsIHgxLCB5MSk7CiAgICAgICAgfQogICAgICB9CgogICAgICB0cmVlbWFwLnJvdW5kID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJvdW5kID0gISF4LCB0cmVlbWFwKSA6IHJvdW5kOwogICAgICB9OwoKICAgICAgdHJlZW1hcC5zaXplID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGR4ID0gK3hbMF0sIGR5ID0gK3hbMV0sIHRyZWVtYXApIDogW2R4LCBkeV07CiAgICAgIH07CgogICAgICB0cmVlbWFwLnRpbGUgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGlsZSA9IHJlcXVpcmVkKHgpLCB0cmVlbWFwKSA6IHRpbGU7CiAgICAgIH07CgogICAgICB0cmVlbWFwLnBhZGRpbmcgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyB0cmVlbWFwLnBhZGRpbmdJbm5lcih4KS5wYWRkaW5nT3V0ZXIoeCkgOiB0cmVlbWFwLnBhZGRpbmdJbm5lcigpOwogICAgICB9OwoKICAgICAgdHJlZW1hcC5wYWRkaW5nSW5uZXIgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ0lubmVyID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkOSgreCksIHRyZWVtYXApIDogcGFkZGluZ0lubmVyOwogICAgICB9OwoKICAgICAgdHJlZW1hcC5wYWRkaW5nT3V0ZXIgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyB0cmVlbWFwLnBhZGRpbmdUb3AoeCkucGFkZGluZ1JpZ2h0KHgpLnBhZGRpbmdCb3R0b20oeCkucGFkZGluZ0xlZnQoeCkgOiB0cmVlbWFwLnBhZGRpbmdUb3AoKTsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ1RvcCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRkaW5nVG9wID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkOSgreCksIHRyZWVtYXApIDogcGFkZGluZ1RvcDsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ1JpZ2h0ID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmdSaWdodCA9IHR5cGVvZiB4ID09PSAiZnVuY3Rpb24iID8geCA6IGNvbnN0YW50JDkoK3gpLCB0cmVlbWFwKSA6IHBhZGRpbmdSaWdodDsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ0JvdHRvbSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRkaW5nQm90dG9tID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkOSgreCksIHRyZWVtYXApIDogcGFkZGluZ0JvdHRvbTsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ0xlZnQgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ0xlZnQgPSB0eXBlb2YgeCA9PT0gImZ1bmN0aW9uIiA/IHggOiBjb25zdGFudCQ5KCt4KSwgdHJlZW1hcCkgOiBwYWRkaW5nTGVmdDsKICAgICAgfTsKCiAgICAgIHJldHVybiB0cmVlbWFwOwogICAgfQoKICAgIGZ1bmN0aW9uIGJpbmFyeShwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIHZhciBub2RlcyA9IHBhcmVudC5jaGlsZHJlbiwKICAgICAgICAgIGksIG4gPSBub2Rlcy5sZW5ndGgsCiAgICAgICAgICBzdW0sIHN1bXMgPSBuZXcgQXJyYXkobiArIDEpOwoKICAgICAgZm9yIChzdW1zWzBdID0gc3VtID0gaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBzdW1zW2kgKyAxXSA9IHN1bSArPSBub2Rlc1tpXS52YWx1ZTsKICAgICAgfQoKICAgICAgcGFydGl0aW9uKDAsIG4sIHBhcmVudC52YWx1ZSwgeDAsIHkwLCB4MSwgeTEpOwoKICAgICAgZnVuY3Rpb24gcGFydGl0aW9uKGksIGosIHZhbHVlLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICAgIGlmIChpID49IGogLSAxKSB7CiAgICAgICAgICB2YXIgbm9kZSA9IG5vZGVzW2ldOwogICAgICAgICAgbm9kZS54MCA9IHgwLCBub2RlLnkwID0geTA7CiAgICAgICAgICBub2RlLngxID0geDEsIG5vZGUueTEgPSB5MTsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHZhciB2YWx1ZU9mZnNldCA9IHN1bXNbaV0sCiAgICAgICAgICAgIHZhbHVlVGFyZ2V0ID0gKHZhbHVlIC8gMikgKyB2YWx1ZU9mZnNldCwKICAgICAgICAgICAgayA9IGkgKyAxLAogICAgICAgICAgICBoaSA9IGogLSAxOwoKICAgICAgICB3aGlsZSAoayA8IGhpKSB7CiAgICAgICAgICB2YXIgbWlkID0gayArIGhpID4+PiAxOwogICAgICAgICAgaWYgKHN1bXNbbWlkXSA8IHZhbHVlVGFyZ2V0KSBrID0gbWlkICsgMTsKICAgICAgICAgIGVsc2UgaGkgPSBtaWQ7CiAgICAgICAgfQoKICAgICAgICBpZiAoKHZhbHVlVGFyZ2V0IC0gc3Vtc1trIC0gMV0pIDwgKHN1bXNba10gLSB2YWx1ZVRhcmdldCkgJiYgaSArIDEgPCBrKSAtLWs7CgogICAgICAgIHZhciB2YWx1ZUxlZnQgPSBzdW1zW2tdIC0gdmFsdWVPZmZzZXQsCiAgICAgICAgICAgIHZhbHVlUmlnaHQgPSB2YWx1ZSAtIHZhbHVlTGVmdDsKCiAgICAgICAgaWYgKCh4MSAtIHgwKSA+ICh5MSAtIHkwKSkgewogICAgICAgICAgdmFyIHhrID0gKHgwICogdmFsdWVSaWdodCArIHgxICogdmFsdWVMZWZ0KSAvIHZhbHVlOwogICAgICAgICAgcGFydGl0aW9uKGksIGssIHZhbHVlTGVmdCwgeDAsIHkwLCB4aywgeTEpOwogICAgICAgICAgcGFydGl0aW9uKGssIGosIHZhbHVlUmlnaHQsIHhrLCB5MCwgeDEsIHkxKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFyIHlrID0gKHkwICogdmFsdWVSaWdodCArIHkxICogdmFsdWVMZWZ0KSAvIHZhbHVlOwogICAgICAgICAgcGFydGl0aW9uKGksIGssIHZhbHVlTGVmdCwgeDAsIHkwLCB4MSwgeWspOwogICAgICAgICAgcGFydGl0aW9uKGssIGosIHZhbHVlUmlnaHQsIHgwLCB5aywgeDEsIHkxKTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzbGljZURpY2UocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICAocGFyZW50LmRlcHRoICYgMSA/IHRyZWVtYXBTbGljZSA6IHRyZWVtYXBEaWNlKShwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKTsKICAgIH0KCiAgICB2YXIgcmVzcXVhcmlmeSA9IChmdW5jdGlvbiBjdXN0b20ocmF0aW8pIHsKCiAgICAgIGZ1bmN0aW9uIHJlc3F1YXJpZnkocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICAgIGlmICgocm93cyA9IHBhcmVudC5fc3F1YXJpZnkpICYmIChyb3dzLnJhdGlvID09PSByYXRpbykpIHsKICAgICAgICAgIHZhciByb3dzLAogICAgICAgICAgICAgIHJvdywKICAgICAgICAgICAgICBub2RlcywKICAgICAgICAgICAgICBpLAogICAgICAgICAgICAgIGogPSAtMSwKICAgICAgICAgICAgICBuLAogICAgICAgICAgICAgIG0gPSByb3dzLmxlbmd0aCwKICAgICAgICAgICAgICB2YWx1ZSA9IHBhcmVudC52YWx1ZTsKCiAgICAgICAgICB3aGlsZSAoKytqIDwgbSkgewogICAgICAgICAgICByb3cgPSByb3dzW2pdLCBub2RlcyA9IHJvdy5jaGlsZHJlbjsKICAgICAgICAgICAgZm9yIChpID0gcm93LnZhbHVlID0gMCwgbiA9IG5vZGVzLmxlbmd0aDsgaSA8IG47ICsraSkgcm93LnZhbHVlICs9IG5vZGVzW2ldLnZhbHVlOwogICAgICAgICAgICBpZiAocm93LmRpY2UpIHRyZWVtYXBEaWNlKHJvdywgeDAsIHkwLCB4MSwgeTAgKz0gKHkxIC0geTApICogcm93LnZhbHVlIC8gdmFsdWUpOwogICAgICAgICAgICBlbHNlIHRyZWVtYXBTbGljZShyb3csIHgwLCB5MCwgeDAgKz0gKHgxIC0geDApICogcm93LnZhbHVlIC8gdmFsdWUsIHkxKTsKICAgICAgICAgICAgdmFsdWUgLT0gcm93LnZhbHVlOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBwYXJlbnQuX3NxdWFyaWZ5ID0gcm93cyA9IHNxdWFyaWZ5UmF0aW8ocmF0aW8sIHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpOwogICAgICAgICAgcm93cy5yYXRpbyA9IHJhdGlvOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmVzcXVhcmlmeS5yYXRpbyA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCh4ID0gK3gpID4gMSA/IHggOiAxKTsKICAgICAgfTsKCiAgICAgIHJldHVybiByZXNxdWFyaWZ5OwogICAgfSkocGhpKTsKCiAgICBmdW5jdGlvbiBhcmVhJDIocG9seWdvbikgewogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IHBvbHlnb24ubGVuZ3RoLAogICAgICAgICAgYSwKICAgICAgICAgIGIgPSBwb2x5Z29uW24gLSAxXSwKICAgICAgICAgIGFyZWEgPSAwOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBhID0gYjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICBhcmVhICs9IGFbMV0gKiBiWzBdIC0gYVswXSAqIGJbMV07CiAgICAgIH0KCiAgICAgIHJldHVybiBhcmVhIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZCQxKHBvbHlnb24pIHsKICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgIG4gPSBwb2x5Z29uLmxlbmd0aCwKICAgICAgICAgIHggPSAwLAogICAgICAgICAgeSA9IDAsCiAgICAgICAgICBhLAogICAgICAgICAgYiA9IHBvbHlnb25bbiAtIDFdLAogICAgICAgICAgYywKICAgICAgICAgIGsgPSAwOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBhID0gYjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICBrICs9IGMgPSBhWzBdICogYlsxXSAtIGJbMF0gKiBhWzFdOwogICAgICAgIHggKz0gKGFbMF0gKyBiWzBdKSAqIGM7CiAgICAgICAgeSArPSAoYVsxXSArIGJbMV0pICogYzsKICAgICAgfQoKICAgICAgcmV0dXJuIGsgKj0gMywgW3ggLyBrLCB5IC8ga107CiAgICB9CgogICAgLy8gUmV0dXJucyB0aGUgMkQgY3Jvc3MgcHJvZHVjdCBvZiBBQiBhbmQgQUMgdmVjdG9ycywgaS5lLiwgdGhlIHotY29tcG9uZW50IG9mCiAgICAvLyB0aGUgM0QgY3Jvc3MgcHJvZHVjdCBpbiBhIHF1YWRyYW50IEkgQ2FydGVzaWFuIGNvb3JkaW5hdGUgc3lzdGVtICgreCBpcwogICAgLy8gcmlnaHQsICt5IGlzIHVwKS4gUmV0dXJucyBhIHBvc2l0aXZlIHZhbHVlIGlmIEFCQyBpcyBjb3VudGVyLWNsb2Nrd2lzZSwKICAgIC8vIG5lZ2F0aXZlIGlmIGNsb2Nrd2lzZSwgYW5kIHplcm8gaWYgdGhlIHBvaW50cyBhcmUgY29sbGluZWFyLgogICAgZnVuY3Rpb24gY3Jvc3MkMShhLCBiLCBjKSB7CiAgICAgIHJldHVybiAoYlswXSAtIGFbMF0pICogKGNbMV0gLSBhWzFdKSAtIChiWzFdIC0gYVsxXSkgKiAoY1swXSAtIGFbMF0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGxleGljb2dyYXBoaWNPcmRlcihhLCBiKSB7CiAgICAgIHJldHVybiBhWzBdIC0gYlswXSB8fCBhWzFdIC0gYlsxXTsKICAgIH0KCiAgICAvLyBDb21wdXRlcyB0aGUgdXBwZXIgY29udmV4IGh1bGwgcGVyIHRoZSBtb25vdG9uZSBjaGFpbiBhbGdvcml0aG0uCiAgICAvLyBBc3N1bWVzIHBvaW50cy5sZW5ndGggPj0gMywgaXMgc29ydGVkIGJ5IHgsIHVuaXF1ZSBpbiB5LgogICAgLy8gUmV0dXJucyBhbiBhcnJheSBvZiBpbmRpY2VzIGludG8gcG9pbnRzIGluIGxlZnQtdG8tcmlnaHQgb3JkZXIuCiAgICBmdW5jdGlvbiBjb21wdXRlVXBwZXJIdWxsSW5kZXhlcyhwb2ludHMpIHsKICAgICAgdmFyIG4gPSBwb2ludHMubGVuZ3RoLAogICAgICAgICAgaW5kZXhlcyA9IFswLCAxXSwKICAgICAgICAgIHNpemUgPSAyOwoKICAgICAgZm9yICh2YXIgaSA9IDI7IGkgPCBuOyArK2kpIHsKICAgICAgICB3aGlsZSAoc2l6ZSA+IDEgJiYgY3Jvc3MkMShwb2ludHNbaW5kZXhlc1tzaXplIC0gMl1dLCBwb2ludHNbaW5kZXhlc1tzaXplIC0gMV1dLCBwb2ludHNbaV0pIDw9IDApIC0tc2l6ZTsKICAgICAgICBpbmRleGVzW3NpemUrK10gPSBpOwogICAgICB9CgogICAgICByZXR1cm4gaW5kZXhlcy5zbGljZSgwLCBzaXplKTsgLy8gcmVtb3ZlIHBvcHBlZCBwb2ludHMKICAgIH0KCiAgICBmdW5jdGlvbiBodWxsKHBvaW50cykgewogICAgICBpZiAoKG4gPSBwb2ludHMubGVuZ3RoKSA8IDMpIHJldHVybiBudWxsOwoKICAgICAgdmFyIGksCiAgICAgICAgICBuLAogICAgICAgICAgc29ydGVkUG9pbnRzID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgZmxpcHBlZFBvaW50cyA9IG5ldyBBcnJheShuKTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHNvcnRlZFBvaW50c1tpXSA9IFsrcG9pbnRzW2ldWzBdLCArcG9pbnRzW2ldWzFdLCBpXTsKICAgICAgc29ydGVkUG9pbnRzLnNvcnQobGV4aWNvZ3JhcGhpY09yZGVyKTsKICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgZmxpcHBlZFBvaW50c1tpXSA9IFtzb3J0ZWRQb2ludHNbaV1bMF0sIC1zb3J0ZWRQb2ludHNbaV1bMV1dOwoKICAgICAgdmFyIHVwcGVySW5kZXhlcyA9IGNvbXB1dGVVcHBlckh1bGxJbmRleGVzKHNvcnRlZFBvaW50cyksCiAgICAgICAgICBsb3dlckluZGV4ZXMgPSBjb21wdXRlVXBwZXJIdWxsSW5kZXhlcyhmbGlwcGVkUG9pbnRzKTsKCiAgICAgIC8vIENvbnN0cnVjdCB0aGUgaHVsbCBwb2x5Z29uLCByZW1vdmluZyBwb3NzaWJsZSBkdXBsaWNhdGUgZW5kcG9pbnRzLgogICAgICB2YXIgc2tpcExlZnQgPSBsb3dlckluZGV4ZXNbMF0gPT09IHVwcGVySW5kZXhlc1swXSwKICAgICAgICAgIHNraXBSaWdodCA9IGxvd2VySW5kZXhlc1tsb3dlckluZGV4ZXMubGVuZ3RoIC0gMV0gPT09IHVwcGVySW5kZXhlc1t1cHBlckluZGV4ZXMubGVuZ3RoIC0gMV0sCiAgICAgICAgICBodWxsID0gW107CgogICAgICAvLyBBZGQgdXBwZXIgaHVsbCBpbiByaWdodC10by1sIG9yZGVyLgogICAgICAvLyBUaGVuIGFkZCBsb3dlciBodWxsIGluIGxlZnQtdG8tcmlnaHQgb3JkZXIuCiAgICAgIGZvciAoaSA9IHVwcGVySW5kZXhlcy5sZW5ndGggLSAxOyBpID49IDA7IC0taSkgaHVsbC5wdXNoKHBvaW50c1tzb3J0ZWRQb2ludHNbdXBwZXJJbmRleGVzW2ldXVsyXV0pOwogICAgICBmb3IgKGkgPSArc2tpcExlZnQ7IGkgPCBsb3dlckluZGV4ZXMubGVuZ3RoIC0gc2tpcFJpZ2h0OyArK2kpIGh1bGwucHVzaChwb2ludHNbc29ydGVkUG9pbnRzW2xvd2VySW5kZXhlc1tpXV1bMl1dKTsKCiAgICAgIHJldHVybiBodWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRhaW5zJDIocG9seWdvbiwgcG9pbnQpIHsKICAgICAgdmFyIG4gPSBwb2x5Z29uLmxlbmd0aCwKICAgICAgICAgIHAgPSBwb2x5Z29uW24gLSAxXSwKICAgICAgICAgIHggPSBwb2ludFswXSwgeSA9IHBvaW50WzFdLAogICAgICAgICAgeDAgPSBwWzBdLCB5MCA9IHBbMV0sCiAgICAgICAgICB4MSwgeTEsCiAgICAgICAgICBpbnNpZGUgPSBmYWxzZTsKCiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgcCA9IHBvbHlnb25baV0sIHgxID0gcFswXSwgeTEgPSBwWzFdOwogICAgICAgIGlmICgoKHkxID4geSkgIT09ICh5MCA+IHkpKSAmJiAoeCA8ICh4MCAtIHgxKSAqICh5IC0geTEpIC8gKHkwIC0geTEpICsgeDEpKSBpbnNpZGUgPSAhaW5zaWRlOwogICAgICAgIHgwID0geDEsIHkwID0geTE7CiAgICAgIH0KCiAgICAgIHJldHVybiBpbnNpZGU7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoJDIocG9seWdvbikgewogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IHBvbHlnb24ubGVuZ3RoLAogICAgICAgICAgYiA9IHBvbHlnb25bbiAtIDFdLAogICAgICAgICAgeGEsCiAgICAgICAgICB5YSwKICAgICAgICAgIHhiID0gYlswXSwKICAgICAgICAgIHliID0gYlsxXSwKICAgICAgICAgIHBlcmltZXRlciA9IDA7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIHhhID0geGI7CiAgICAgICAgeWEgPSB5YjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICB4YiA9IGJbMF07CiAgICAgICAgeWIgPSBiWzFdOwogICAgICAgIHhhIC09IHhiOwogICAgICAgIHlhIC09IHliOwogICAgICAgIHBlcmltZXRlciArPSBNYXRoLnNxcnQoeGEgKiB4YSArIHlhICogeWEpOwogICAgICB9CgogICAgICByZXR1cm4gcGVyaW1ldGVyOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRTb3VyY2UkMSgpIHsKICAgICAgcmV0dXJuIE1hdGgucmFuZG9tKCk7CiAgICB9CgogICAgdmFyIHVuaWZvcm0gPSAoZnVuY3Rpb24gc291cmNlUmFuZG9tVW5pZm9ybShzb3VyY2UpIHsKICAgICAgZnVuY3Rpb24gcmFuZG9tVW5pZm9ybShtaW4sIG1heCkgewogICAgICAgIG1pbiA9IG1pbiA9PSBudWxsID8gMCA6ICttaW47CiAgICAgICAgbWF4ID0gbWF4ID09IG51bGwgPyAxIDogK21heDsKICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA9PT0gMSkgbWF4ID0gbWluLCBtaW4gPSAwOwogICAgICAgIGVsc2UgbWF4IC09IG1pbjsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gc291cmNlKCkgKiBtYXggKyBtaW47CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgcmFuZG9tVW5pZm9ybS5zb3VyY2UgPSBzb3VyY2VSYW5kb21Vbmlmb3JtOwoKICAgICAgcmV0dXJuIHJhbmRvbVVuaWZvcm07CiAgICB9KShkZWZhdWx0U291cmNlJDEpOwoKICAgIHZhciBub3JtYWwgPSAoZnVuY3Rpb24gc291cmNlUmFuZG9tTm9ybWFsKHNvdXJjZSkgewogICAgICBmdW5jdGlvbiByYW5kb21Ob3JtYWwobXUsIHNpZ21hKSB7CiAgICAgICAgdmFyIHgsIHI7CiAgICAgICAgbXUgPSBtdSA9PSBudWxsID8gMCA6ICttdTsKICAgICAgICBzaWdtYSA9IHNpZ21hID09IG51bGwgPyAxIDogK3NpZ21hOwogICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciB5OwoKICAgICAgICAgIC8vIElmIGF2YWlsYWJsZSwgdXNlIHRoZSBzZWNvbmQgcHJldmlvdXNseS1nZW5lcmF0ZWQgdW5pZm9ybSByYW5kb20uCiAgICAgICAgICBpZiAoeCAhPSBudWxsKSB5ID0geCwgeCA9IG51bGw7CgogICAgICAgICAgLy8gT3RoZXJ3aXNlLCBnZW5lcmF0ZSBhIG5ldyB4IGFuZCB5LgogICAgICAgICAgZWxzZSBkbyB7CiAgICAgICAgICAgIHggPSBzb3VyY2UoKSAqIDIgLSAxOwogICAgICAgICAgICB5ID0gc291cmNlKCkgKiAyIC0gMTsKICAgICAgICAgICAgciA9IHggKiB4ICsgeSAqIHk7CiAgICAgICAgICB9IHdoaWxlICghciB8fCByID4gMSk7CgogICAgICAgICAgcmV0dXJuIG11ICsgc2lnbWEgKiB5ICogTWF0aC5zcXJ0KC0yICogTWF0aC5sb2cocikgLyByKTsKICAgICAgICB9OwogICAgICB9CgogICAgICByYW5kb21Ob3JtYWwuc291cmNlID0gc291cmNlUmFuZG9tTm9ybWFsOwoKICAgICAgcmV0dXJuIHJhbmRvbU5vcm1hbDsKICAgIH0pKGRlZmF1bHRTb3VyY2UkMSk7CgogICAgdmFyIGxvZ05vcm1hbCA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21Mb2dOb3JtYWwoc291cmNlKSB7CiAgICAgIGZ1bmN0aW9uIHJhbmRvbUxvZ05vcm1hbCgpIHsKICAgICAgICB2YXIgcmFuZG9tTm9ybWFsID0gbm9ybWFsLnNvdXJjZShzb3VyY2UpLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIE1hdGguZXhwKHJhbmRvbU5vcm1hbCgpKTsKICAgICAgICB9OwogICAgICB9CgogICAgICByYW5kb21Mb2dOb3JtYWwuc291cmNlID0gc291cmNlUmFuZG9tTG9nTm9ybWFsOwoKICAgICAgcmV0dXJuIHJhbmRvbUxvZ05vcm1hbDsKICAgIH0pKGRlZmF1bHRTb3VyY2UkMSk7CgogICAgdmFyIGlyd2luSGFsbCA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21JcndpbkhhbGwoc291cmNlKSB7CiAgICAgIGZ1bmN0aW9uIHJhbmRvbUlyd2luSGFsbChuKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgZm9yICh2YXIgc3VtID0gMCwgaSA9IDA7IGkgPCBuOyArK2kpIHN1bSArPSBzb3VyY2UoKTsKICAgICAgICAgIHJldHVybiBzdW07CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgcmFuZG9tSXJ3aW5IYWxsLnNvdXJjZSA9IHNvdXJjZVJhbmRvbUlyd2luSGFsbDsKCiAgICAgIHJldHVybiByYW5kb21JcndpbkhhbGw7CiAgICB9KShkZWZhdWx0U291cmNlJDEpOwoKICAgIHZhciBiYXRlcyA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21CYXRlcyhzb3VyY2UpIHsKICAgICAgZnVuY3Rpb24gcmFuZG9tQmF0ZXMobikgewogICAgICAgIHZhciByYW5kb21JcndpbkhhbGwgPSBpcndpbkhhbGwuc291cmNlKHNvdXJjZSkobik7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHJhbmRvbUlyd2luSGFsbCgpIC8gbjsKICAgICAgICB9OwogICAgICB9CgogICAgICByYW5kb21CYXRlcy5zb3VyY2UgPSBzb3VyY2VSYW5kb21CYXRlczsKCiAgICAgIHJldHVybiByYW5kb21CYXRlczsKICAgIH0pKGRlZmF1bHRTb3VyY2UkMSk7CgogICAgdmFyIGV4cG9uZW50aWFsJDEgPSAoZnVuY3Rpb24gc291cmNlUmFuZG9tRXhwb25lbnRpYWwoc291cmNlKSB7CiAgICAgIGZ1bmN0aW9uIHJhbmRvbUV4cG9uZW50aWFsKGxhbWJkYSkgewogICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgIHJldHVybiAtTWF0aC5sb2coMSAtIHNvdXJjZSgpKSAvIGxhbWJkYTsKICAgICAgICB9OwogICAgICB9CgogICAgICByYW5kb21FeHBvbmVudGlhbC5zb3VyY2UgPSBzb3VyY2VSYW5kb21FeHBvbmVudGlhbDsKCiAgICAgIHJldHVybiByYW5kb21FeHBvbmVudGlhbDsKICAgIH0pKGRlZmF1bHRTb3VyY2UkMSk7CgogICAgZnVuY3Rpb24gaW5pdFJhbmdlKGRvbWFpbiwgcmFuZ2UpIHsKICAgICAgc3dpdGNoIChhcmd1bWVudHMubGVuZ3RoKSB7CiAgICAgICAgY2FzZSAwOiBicmVhazsKICAgICAgICBjYXNlIDE6IHRoaXMucmFuZ2UoZG9tYWluKTsgYnJlYWs7CiAgICAgICAgZGVmYXVsdDogdGhpcy5yYW5nZShyYW5nZSkuZG9tYWluKGRvbWFpbik7IGJyZWFrOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGluaXRJbnRlcnBvbGF0b3IoZG9tYWluLCBpbnRlcnBvbGF0b3IpIHsKICAgICAgc3dpdGNoIChhcmd1bWVudHMubGVuZ3RoKSB7CiAgICAgICAgY2FzZSAwOiBicmVhazsKICAgICAgICBjYXNlIDE6IHRoaXMuaW50ZXJwb2xhdG9yKGRvbWFpbik7IGJyZWFrOwogICAgICAgIGRlZmF1bHQ6IHRoaXMuaW50ZXJwb2xhdG9yKGludGVycG9sYXRvcikuZG9tYWluKGRvbWFpbik7IGJyZWFrOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIHZhciBhcnJheSQzID0gQXJyYXkucHJvdG90eXBlOwoKICAgIHZhciBtYXAkMyA9IGFycmF5JDMubWFwOwogICAgdmFyIHNsaWNlJDUgPSBhcnJheSQzLnNsaWNlOwoKICAgIHZhciBpbXBsaWNpdCA9IHtuYW1lOiAiaW1wbGljaXQifTsKCiAgICBmdW5jdGlvbiBvcmRpbmFsKCkgewogICAgICB2YXIgaW5kZXggPSBtYXAkMSgpLAogICAgICAgICAgZG9tYWluID0gW10sCiAgICAgICAgICByYW5nZSA9IFtdLAogICAgICAgICAgdW5rbm93biA9IGltcGxpY2l0OwoKICAgICAgZnVuY3Rpb24gc2NhbGUoZCkgewogICAgICAgIHZhciBrZXkgPSBkICsgIiIsIGkgPSBpbmRleC5nZXQoa2V5KTsKICAgICAgICBpZiAoIWkpIHsKICAgICAgICAgIGlmICh1bmtub3duICE9PSBpbXBsaWNpdCkgcmV0dXJuIHVua25vd247CiAgICAgICAgICBpbmRleC5zZXQoa2V5LCBpID0gZG9tYWluLnB1c2goZCkpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gcmFuZ2VbKGkgLSAxKSAlIHJhbmdlLmxlbmd0aF07CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBkb21haW4uc2xpY2UoKTsKICAgICAgICBkb21haW4gPSBbXSwgaW5kZXggPSBtYXAkMSgpOwogICAgICAgIHZhciBpID0gLTEsIG4gPSBfLmxlbmd0aCwgZCwga2V5OwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoIWluZGV4LmhhcyhrZXkgPSAoZCA9IF9baV0pICsgIiIpKSBpbmRleC5zZXQoa2V5LCBkb21haW4ucHVzaChkKSk7CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9OwoKICAgICAgc2NhbGUucmFuZ2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocmFuZ2UgPSBzbGljZSQ1LmNhbGwoXyksIHNjYWxlKSA6IHJhbmdlLnNsaWNlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS51bmtub3duID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHVua25vd24gPSBfLCBzY2FsZSkgOiB1bmtub3duOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBvcmRpbmFsKGRvbWFpbiwgcmFuZ2UpLnVua25vd24odW5rbm93bik7CiAgICAgIH07CgogICAgICBpbml0UmFuZ2UuYXBwbHkoc2NhbGUsIGFyZ3VtZW50cyk7CgogICAgICByZXR1cm4gc2NhbGU7CiAgICB9CgogICAgZnVuY3Rpb24gYmFuZCgpIHsKICAgICAgdmFyIHNjYWxlID0gb3JkaW5hbCgpLnVua25vd24odW5kZWZpbmVkKSwKICAgICAgICAgIGRvbWFpbiA9IHNjYWxlLmRvbWFpbiwKICAgICAgICAgIG9yZGluYWxSYW5nZSA9IHNjYWxlLnJhbmdlLAogICAgICAgICAgcmFuZ2UgPSBbMCwgMV0sCiAgICAgICAgICBzdGVwLAogICAgICAgICAgYmFuZHdpZHRoLAogICAgICAgICAgcm91bmQgPSBmYWxzZSwKICAgICAgICAgIHBhZGRpbmdJbm5lciA9IDAsCiAgICAgICAgICBwYWRkaW5nT3V0ZXIgPSAwLAogICAgICAgICAgYWxpZ24gPSAwLjU7CgogICAgICBkZWxldGUgc2NhbGUudW5rbm93bjsKCiAgICAgIGZ1bmN0aW9uIHJlc2NhbGUoKSB7CiAgICAgICAgdmFyIG4gPSBkb21haW4oKS5sZW5ndGgsCiAgICAgICAgICAgIHJldmVyc2UgPSByYW5nZVsxXSA8IHJhbmdlWzBdLAogICAgICAgICAgICBzdGFydCA9IHJhbmdlW3JldmVyc2UgLSAwXSwKICAgICAgICAgICAgc3RvcCA9IHJhbmdlWzEgLSByZXZlcnNlXTsKICAgICAgICBzdGVwID0gKHN0b3AgLSBzdGFydCkgLyBNYXRoLm1heCgxLCBuIC0gcGFkZGluZ0lubmVyICsgcGFkZGluZ091dGVyICogMik7CiAgICAgICAgaWYgKHJvdW5kKSBzdGVwID0gTWF0aC5mbG9vcihzdGVwKTsKICAgICAgICBzdGFydCArPSAoc3RvcCAtIHN0YXJ0IC0gc3RlcCAqIChuIC0gcGFkZGluZ0lubmVyKSkgKiBhbGlnbjsKICAgICAgICBiYW5kd2lkdGggPSBzdGVwICogKDEgLSBwYWRkaW5nSW5uZXIpOwogICAgICAgIGlmIChyb3VuZCkgc3RhcnQgPSBNYXRoLnJvdW5kKHN0YXJ0KSwgYmFuZHdpZHRoID0gTWF0aC5yb3VuZChiYW5kd2lkdGgpOwogICAgICAgIHZhciB2YWx1ZXMgPSBzZXF1ZW5jZShuKS5tYXAoZnVuY3Rpb24oaSkgeyByZXR1cm4gc3RhcnQgKyBzdGVwICogaTsgfSk7CiAgICAgICAgcmV0dXJuIG9yZGluYWxSYW5nZShyZXZlcnNlID8gdmFsdWVzLnJldmVyc2UoKSA6IHZhbHVlcyk7CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkb21haW4oXyksIHJlc2NhbGUoKSkgOiBkb21haW4oKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhbmdlID0gWytfWzBdLCArX1sxXV0sIHJlc2NhbGUoKSkgOiByYW5nZS5zbGljZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUucmFuZ2VSb3VuZCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gcmFuZ2UgPSBbK19bMF0sICtfWzFdXSwgcm91bmQgPSB0cnVlLCByZXNjYWxlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS5iYW5kd2lkdGggPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYmFuZHdpZHRoOwogICAgICB9OwoKICAgICAgc2NhbGUuc3RlcCA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBzdGVwOwogICAgICB9OwoKICAgICAgc2NhbGUucm91bmQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocm91bmQgPSAhIV8sIHJlc2NhbGUoKSkgOiByb3VuZDsKICAgICAgfTsKCiAgICAgIHNjYWxlLnBhZGRpbmcgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ0lubmVyID0gTWF0aC5taW4oMSwgcGFkZGluZ091dGVyID0gK18pLCByZXNjYWxlKCkpIDogcGFkZGluZ0lubmVyOwogICAgICB9OwoKICAgICAgc2NhbGUucGFkZGluZ0lubmVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmdJbm5lciA9IE1hdGgubWluKDEsIF8pLCByZXNjYWxlKCkpIDogcGFkZGluZ0lubmVyOwogICAgICB9OwoKICAgICAgc2NhbGUucGFkZGluZ091dGVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmdPdXRlciA9ICtfLCByZXNjYWxlKCkpIDogcGFkZGluZ091dGVyOwogICAgICB9OwoKICAgICAgc2NhbGUuYWxpZ24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoYWxpZ24gPSBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBfKSksIHJlc2NhbGUoKSkgOiBhbGlnbjsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYmFuZChkb21haW4oKSwgcmFuZ2UpCiAgICAgICAgICAgIC5yb3VuZChyb3VuZCkKICAgICAgICAgICAgLnBhZGRpbmdJbm5lcihwYWRkaW5nSW5uZXIpCiAgICAgICAgICAgIC5wYWRkaW5nT3V0ZXIocGFkZGluZ091dGVyKQogICAgICAgICAgICAuYWxpZ24oYWxpZ24pOwogICAgICB9OwoKICAgICAgcmV0dXJuIGluaXRSYW5nZS5hcHBseShyZXNjYWxlKCksIGFyZ3VtZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnRpc2goc2NhbGUpIHsKICAgICAgdmFyIGNvcHkgPSBzY2FsZS5jb3B5OwoKICAgICAgc2NhbGUucGFkZGluZyA9IHNjYWxlLnBhZGRpbmdPdXRlcjsKICAgICAgZGVsZXRlIHNjYWxlLnBhZGRpbmdJbm5lcjsKICAgICAgZGVsZXRlIHNjYWxlLnBhZGRpbmdPdXRlcjsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gcG9pbnRpc2goY29weSgpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBzY2FsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb2ludCQxKCkgewogICAgICByZXR1cm4gcG9pbnRpc2goYmFuZC5hcHBseShudWxsLCBhcmd1bWVudHMpLnBhZGRpbmdJbm5lcigxKSk7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkYSh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBudW1iZXIkMih4KSB7CiAgICAgIHJldHVybiAreDsKICAgIH0KCiAgICB2YXIgdW5pdCA9IFswLCAxXTsKCiAgICBmdW5jdGlvbiBpZGVudGl0eSQ2KHgpIHsKICAgICAgcmV0dXJuIHg7CiAgICB9CgogICAgZnVuY3Rpb24gbm9ybWFsaXplJDEoYSwgYikgewogICAgICByZXR1cm4gKGIgLT0gKGEgPSArYSkpCiAgICAgICAgICA/IGZ1bmN0aW9uKHgpIHsgcmV0dXJuICh4IC0gYSkgLyBiOyB9CiAgICAgICAgICA6IGNvbnN0YW50JGEoaXNOYU4oYikgPyBOYU4gOiAwLjUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYW1wZXIoZG9tYWluKSB7CiAgICAgIHZhciBhID0gZG9tYWluWzBdLCBiID0gZG9tYWluW2RvbWFpbi5sZW5ndGggLSAxXSwgdDsKICAgICAgaWYgKGEgPiBiKSB0ID0gYSwgYSA9IGIsIGIgPSB0OwogICAgICByZXR1cm4gZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5tYXgoYSwgTWF0aC5taW4oYiwgeCkpOyB9OwogICAgfQoKICAgIC8vIG5vcm1hbGl6ZShhLCBiKSh4KSB0YWtlcyBhIGRvbWFpbiB2YWx1ZSB4IGluIFthLGJdIGFuZCByZXR1cm5zIHRoZSBjb3JyZXNwb25kaW5nIHBhcmFtZXRlciB0IGluIFswLDFdLgogICAgLy8gaW50ZXJwb2xhdGUoYSwgYikodCkgdGFrZXMgYSBwYXJhbWV0ZXIgdCBpbiBbMCwxXSBhbmQgcmV0dXJucyB0aGUgY29ycmVzcG9uZGluZyByYW5nZSB2YWx1ZSB4IGluIFthLGJdLgogICAgZnVuY3Rpb24gYmltYXAoZG9tYWluLCByYW5nZSwgaW50ZXJwb2xhdGUpIHsKICAgICAgdmFyIGQwID0gZG9tYWluWzBdLCBkMSA9IGRvbWFpblsxXSwgcjAgPSByYW5nZVswXSwgcjEgPSByYW5nZVsxXTsKICAgICAgaWYgKGQxIDwgZDApIGQwID0gbm9ybWFsaXplJDEoZDEsIGQwKSwgcjAgPSBpbnRlcnBvbGF0ZShyMSwgcjApOwogICAgICBlbHNlIGQwID0gbm9ybWFsaXplJDEoZDAsIGQxKSwgcjAgPSBpbnRlcnBvbGF0ZShyMCwgcjEpOwogICAgICByZXR1cm4gZnVuY3Rpb24oeCkgeyByZXR1cm4gcjAoZDAoeCkpOyB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvbHltYXAoZG9tYWluLCByYW5nZSwgaW50ZXJwb2xhdGUpIHsKICAgICAgdmFyIGogPSBNYXRoLm1pbihkb21haW4ubGVuZ3RoLCByYW5nZS5sZW5ndGgpIC0gMSwKICAgICAgICAgIGQgPSBuZXcgQXJyYXkoaiksCiAgICAgICAgICByID0gbmV3IEFycmF5KGopLAogICAgICAgICAgaSA9IC0xOwoKICAgICAgLy8gUmV2ZXJzZSBkZXNjZW5kaW5nIGRvbWFpbnMuCiAgICAgIGlmIChkb21haW5bal0gPCBkb21haW5bMF0pIHsKICAgICAgICBkb21haW4gPSBkb21haW4uc2xpY2UoKS5yZXZlcnNlKCk7CiAgICAgICAgcmFuZ2UgPSByYW5nZS5zbGljZSgpLnJldmVyc2UoKTsKICAgICAgfQoKICAgICAgd2hpbGUgKCsraSA8IGopIHsKICAgICAgICBkW2ldID0gbm9ybWFsaXplJDEoZG9tYWluW2ldLCBkb21haW5baSArIDFdKTsKICAgICAgICByW2ldID0gaW50ZXJwb2xhdGUocmFuZ2VbaV0sIHJhbmdlW2kgKyAxXSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbih4KSB7CiAgICAgICAgdmFyIGkgPSBiaXNlY3RSaWdodChkb21haW4sIHgsIDEsIGopIC0gMTsKICAgICAgICByZXR1cm4gcltpXShkW2ldKHgpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb3B5KHNvdXJjZSwgdGFyZ2V0KSB7CiAgICAgIHJldHVybiB0YXJnZXQKICAgICAgICAgIC5kb21haW4oc291cmNlLmRvbWFpbigpKQogICAgICAgICAgLnJhbmdlKHNvdXJjZS5yYW5nZSgpKQogICAgICAgICAgLmludGVycG9sYXRlKHNvdXJjZS5pbnRlcnBvbGF0ZSgpKQogICAgICAgICAgLmNsYW1wKHNvdXJjZS5jbGFtcCgpKQogICAgICAgICAgLnVua25vd24oc291cmNlLnVua25vd24oKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtZXIkMSgpIHsKICAgICAgdmFyIGRvbWFpbiA9IHVuaXQsCiAgICAgICAgICByYW5nZSA9IHVuaXQsCiAgICAgICAgICBpbnRlcnBvbGF0ZSA9IGludGVycG9sYXRlVmFsdWUsCiAgICAgICAgICB0cmFuc2Zvcm0sCiAgICAgICAgICB1bnRyYW5zZm9ybSwKICAgICAgICAgIHVua25vd24sCiAgICAgICAgICBjbGFtcCA9IGlkZW50aXR5JDYsCiAgICAgICAgICBwaWVjZXdpc2UsCiAgICAgICAgICBvdXRwdXQsCiAgICAgICAgICBpbnB1dDsKCiAgICAgIGZ1bmN0aW9uIHJlc2NhbGUoKSB7CiAgICAgICAgcGllY2V3aXNlID0gTWF0aC5taW4oZG9tYWluLmxlbmd0aCwgcmFuZ2UubGVuZ3RoKSA+IDIgPyBwb2x5bWFwIDogYmltYXA7CiAgICAgICAgb3V0cHV0ID0gaW5wdXQgPSBudWxsOwogICAgICAgIHJldHVybiBzY2FsZTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeCkgewogICAgICAgIHJldHVybiBpc05hTih4ID0gK3gpID8gdW5rbm93biA6IChvdXRwdXQgfHwgKG91dHB1dCA9IHBpZWNld2lzZShkb21haW4ubWFwKHRyYW5zZm9ybSksIHJhbmdlLCBpbnRlcnBvbGF0ZSkpKSh0cmFuc2Zvcm0oY2xhbXAoeCkpKTsKICAgICAgfQoKICAgICAgc2NhbGUuaW52ZXJ0ID0gZnVuY3Rpb24oeSkgewogICAgICAgIHJldHVybiBjbGFtcCh1bnRyYW5zZm9ybSgoaW5wdXQgfHwgKGlucHV0ID0gcGllY2V3aXNlKHJhbmdlLCBkb21haW4ubWFwKHRyYW5zZm9ybSksIGludGVycG9sYXRlTnVtYmVyKSkpKHkpKSk7CiAgICAgIH07CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluID0gbWFwJDMuY2FsbChfLCBudW1iZXIkMiksIGNsYW1wID09PSBpZGVudGl0eSQ2IHx8IChjbGFtcCA9IGNsYW1wZXIoZG9tYWluKSksIHJlc2NhbGUoKSkgOiBkb21haW4uc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhbmdlID0gc2xpY2UkNS5jYWxsKF8pLCByZXNjYWxlKCkpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlUm91bmQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIHJhbmdlID0gc2xpY2UkNS5jYWxsKF8pLCBpbnRlcnBvbGF0ZSA9IGludGVycG9sYXRlUm91bmQsIHJlc2NhbGUoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNsYW1wID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNsYW1wID0gXyA/IGNsYW1wZXIoZG9tYWluKSA6IGlkZW50aXR5JDYsIHNjYWxlKSA6IGNsYW1wICE9PSBpZGVudGl0eSQ2OwogICAgICB9OwoKICAgICAgc2NhbGUuaW50ZXJwb2xhdGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaW50ZXJwb2xhdGUgPSBfLCByZXNjYWxlKCkpIDogaW50ZXJwb2xhdGU7CiAgICAgIH07CgogICAgICBzY2FsZS51bmtub3duID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHVua25vd24gPSBfLCBzY2FsZSkgOiB1bmtub3duOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQsIHUpIHsKICAgICAgICB0cmFuc2Zvcm0gPSB0LCB1bnRyYW5zZm9ybSA9IHU7CiAgICAgICAgcmV0dXJuIHJlc2NhbGUoKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb250aW51b3VzKHRyYW5zZm9ybSwgdW50cmFuc2Zvcm0pIHsKICAgICAgcmV0dXJuIHRyYW5zZm9ybWVyJDEoKSh0cmFuc2Zvcm0sIHVudHJhbnNmb3JtKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aWNrRm9ybWF0KHN0YXJ0LCBzdG9wLCBjb3VudCwgc3BlY2lmaWVyKSB7CiAgICAgIHZhciBzdGVwID0gdGlja1N0ZXAoc3RhcnQsIHN0b3AsIGNvdW50KSwKICAgICAgICAgIHByZWNpc2lvbjsKICAgICAgc3BlY2lmaWVyID0gZm9ybWF0U3BlY2lmaWVyKHNwZWNpZmllciA9PSBudWxsID8gIixmIiA6IHNwZWNpZmllcik7CiAgICAgIHN3aXRjaCAoc3BlY2lmaWVyLnR5cGUpIHsKICAgICAgICBjYXNlICJzIjogewogICAgICAgICAgdmFyIHZhbHVlID0gTWF0aC5tYXgoTWF0aC5hYnMoc3RhcnQpLCBNYXRoLmFicyhzdG9wKSk7CiAgICAgICAgICBpZiAoc3BlY2lmaWVyLnByZWNpc2lvbiA9PSBudWxsICYmICFpc05hTihwcmVjaXNpb24gPSBwcmVjaXNpb25QcmVmaXgoc3RlcCwgdmFsdWUpKSkgc3BlY2lmaWVyLnByZWNpc2lvbiA9IHByZWNpc2lvbjsKICAgICAgICAgIHJldHVybiBmb3JtYXRQcmVmaXgoc3BlY2lmaWVyLCB2YWx1ZSk7CiAgICAgICAgfQogICAgICAgIGNhc2UgIiI6CiAgICAgICAgY2FzZSAiZSI6CiAgICAgICAgY2FzZSAiZyI6CiAgICAgICAgY2FzZSAicCI6CiAgICAgICAgY2FzZSAiciI6IHsKICAgICAgICAgIGlmIChzcGVjaWZpZXIucHJlY2lzaW9uID09IG51bGwgJiYgIWlzTmFOKHByZWNpc2lvbiA9IHByZWNpc2lvblJvdW5kKHN0ZXAsIE1hdGgubWF4KE1hdGguYWJzKHN0YXJ0KSwgTWF0aC5hYnMoc3RvcCkpKSkpIHNwZWNpZmllci5wcmVjaXNpb24gPSBwcmVjaXNpb24gLSAoc3BlY2lmaWVyLnR5cGUgPT09ICJlIik7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgY2FzZSAiZiI6CiAgICAgICAgY2FzZSAiJSI6IHsKICAgICAgICAgIGlmIChzcGVjaWZpZXIucHJlY2lzaW9uID09IG51bGwgJiYgIWlzTmFOKHByZWNpc2lvbiA9IHByZWNpc2lvbkZpeGVkKHN0ZXApKSkgc3BlY2lmaWVyLnByZWNpc2lvbiA9IHByZWNpc2lvbiAtIChzcGVjaWZpZXIudHlwZSA9PT0gIiUiKSAqIDI7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZvcm1hdChzcGVjaWZpZXIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVhcmlzaChzY2FsZSkgewogICAgICB2YXIgZG9tYWluID0gc2NhbGUuZG9tYWluOwoKICAgICAgc2NhbGUudGlja3MgPSBmdW5jdGlvbihjb3VudCkgewogICAgICAgIHZhciBkID0gZG9tYWluKCk7CiAgICAgICAgcmV0dXJuIHRpY2tzKGRbMF0sIGRbZC5sZW5ndGggLSAxXSwgY291bnQgPT0gbnVsbCA/IDEwIDogY291bnQpOwogICAgICB9OwoKICAgICAgc2NhbGUudGlja0Zvcm1hdCA9IGZ1bmN0aW9uKGNvdW50LCBzcGVjaWZpZXIpIHsKICAgICAgICB2YXIgZCA9IGRvbWFpbigpOwogICAgICAgIHJldHVybiB0aWNrRm9ybWF0KGRbMF0sIGRbZC5sZW5ndGggLSAxXSwgY291bnQgPT0gbnVsbCA/IDEwIDogY291bnQsIHNwZWNpZmllcik7CiAgICAgIH07CgogICAgICBzY2FsZS5uaWNlID0gZnVuY3Rpb24oY291bnQpIHsKICAgICAgICBpZiAoY291bnQgPT0gbnVsbCkgY291bnQgPSAxMDsKCiAgICAgICAgdmFyIGQgPSBkb21haW4oKSwKICAgICAgICAgICAgaTAgPSAwLAogICAgICAgICAgICBpMSA9IGQubGVuZ3RoIC0gMSwKICAgICAgICAgICAgc3RhcnQgPSBkW2kwXSwKICAgICAgICAgICAgc3RvcCA9IGRbaTFdLAogICAgICAgICAgICBzdGVwOwoKICAgICAgICBpZiAoc3RvcCA8IHN0YXJ0KSB7CiAgICAgICAgICBzdGVwID0gc3RhcnQsIHN0YXJ0ID0gc3RvcCwgc3RvcCA9IHN0ZXA7CiAgICAgICAgICBzdGVwID0gaTAsIGkwID0gaTEsIGkxID0gc3RlcDsKICAgICAgICB9CgogICAgICAgIHN0ZXAgPSB0aWNrSW5jcmVtZW50KHN0YXJ0LCBzdG9wLCBjb3VudCk7CgogICAgICAgIGlmIChzdGVwID4gMCkgewogICAgICAgICAgc3RhcnQgPSBNYXRoLmZsb29yKHN0YXJ0IC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgc3RvcCA9IE1hdGguY2VpbChzdG9wIC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgc3RlcCA9IHRpY2tJbmNyZW1lbnQoc3RhcnQsIHN0b3AsIGNvdW50KTsKICAgICAgICB9IGVsc2UgaWYgKHN0ZXAgPCAwKSB7CiAgICAgICAgICBzdGFydCA9IE1hdGguY2VpbChzdGFydCAqIHN0ZXApIC8gc3RlcDsKICAgICAgICAgIHN0b3AgPSBNYXRoLmZsb29yKHN0b3AgKiBzdGVwKSAvIHN0ZXA7CiAgICAgICAgICBzdGVwID0gdGlja0luY3JlbWVudChzdGFydCwgc3RvcCwgY291bnQpOwogICAgICAgIH0KCiAgICAgICAgaWYgKHN0ZXAgPiAwKSB7CiAgICAgICAgICBkW2kwXSA9IE1hdGguZmxvb3Ioc3RhcnQgLyBzdGVwKSAqIHN0ZXA7CiAgICAgICAgICBkW2kxXSA9IE1hdGguY2VpbChzdG9wIC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgZG9tYWluKGQpOwogICAgICAgIH0gZWxzZSBpZiAoc3RlcCA8IDApIHsKICAgICAgICAgIGRbaTBdID0gTWF0aC5jZWlsKHN0YXJ0ICogc3RlcCkgLyBzdGVwOwogICAgICAgICAgZFtpMV0gPSBNYXRoLmZsb29yKHN0b3AgKiBzdGVwKSAvIHN0ZXA7CiAgICAgICAgICBkb21haW4oZCk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gc2NhbGU7CiAgICAgIH07CgogICAgICByZXR1cm4gc2NhbGU7CiAgICB9CgogICAgZnVuY3Rpb24gbGluZWFyJDIoKSB7CiAgICAgIHZhciBzY2FsZSA9IGNvbnRpbnVvdXMoaWRlbnRpdHkkNiwgaWRlbnRpdHkkNik7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkoc2NhbGUsIGxpbmVhciQyKCkpOwogICAgICB9OwoKICAgICAgaW5pdFJhbmdlLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwoKICAgICAgcmV0dXJuIGxpbmVhcmlzaChzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gaWRlbnRpdHkkNyhkb21haW4pIHsKICAgICAgdmFyIHVua25vd247CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgcmV0dXJuIGlzTmFOKHggPSAreCkgPyB1bmtub3duIDogeDsKICAgICAgfQoKICAgICAgc2NhbGUuaW52ZXJ0ID0gc2NhbGU7CgogICAgICBzY2FsZS5kb21haW4gPSBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkb21haW4gPSBtYXAkMy5jYWxsKF8sIG51bWJlciQyKSwgc2NhbGUpIDogZG9tYWluLnNsaWNlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS51bmtub3duID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHVua25vd24gPSBfLCBzY2FsZSkgOiB1bmtub3duOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBpZGVudGl0eSQ3KGRvbWFpbikudW5rbm93bih1bmtub3duKTsKICAgICAgfTsKCiAgICAgIGRvbWFpbiA9IGFyZ3VtZW50cy5sZW5ndGggPyBtYXAkMy5jYWxsKGRvbWFpbiwgbnVtYmVyJDIpIDogWzAsIDFdOwoKICAgICAgcmV0dXJuIGxpbmVhcmlzaChzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gbmljZShkb21haW4sIGludGVydmFsKSB7CiAgICAgIGRvbWFpbiA9IGRvbWFpbi5zbGljZSgpOwoKICAgICAgdmFyIGkwID0gMCwKICAgICAgICAgIGkxID0gZG9tYWluLmxlbmd0aCAtIDEsCiAgICAgICAgICB4MCA9IGRvbWFpbltpMF0sCiAgICAgICAgICB4MSA9IGRvbWFpbltpMV0sCiAgICAgICAgICB0OwoKICAgICAgaWYgKHgxIDwgeDApIHsKICAgICAgICB0ID0gaTAsIGkwID0gaTEsIGkxID0gdDsKICAgICAgICB0ID0geDAsIHgwID0geDEsIHgxID0gdDsKICAgICAgfQoKICAgICAgZG9tYWluW2kwXSA9IGludGVydmFsLmZsb29yKHgwKTsKICAgICAgZG9tYWluW2kxXSA9IGludGVydmFsLmNlaWwoeDEpOwogICAgICByZXR1cm4gZG9tYWluOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybUxvZyh4KSB7CiAgICAgIHJldHVybiBNYXRoLmxvZyh4KTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2Zvcm1FeHAoeCkgewogICAgICByZXR1cm4gTWF0aC5leHAoeCk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtTG9nbih4KSB7CiAgICAgIHJldHVybiAtTWF0aC5sb2coLXgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybUV4cG4oeCkgewogICAgICByZXR1cm4gLU1hdGguZXhwKC14KTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb3cxMCh4KSB7CiAgICAgIHJldHVybiBpc0Zpbml0ZSh4KSA/ICsoIjFlIiArIHgpIDogeCA8IDAgPyAwIDogeDsKICAgIH0KCiAgICBmdW5jdGlvbiBwb3dwKGJhc2UpIHsKICAgICAgcmV0dXJuIGJhc2UgPT09IDEwID8gcG93MTAKICAgICAgICAgIDogYmFzZSA9PT0gTWF0aC5FID8gTWF0aC5leHAKICAgICAgICAgIDogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5wb3coYmFzZSwgeCk7IH07CiAgICB9CgogICAgZnVuY3Rpb24gbG9ncChiYXNlKSB7CiAgICAgIHJldHVybiBiYXNlID09PSBNYXRoLkUgPyBNYXRoLmxvZwogICAgICAgICAgOiBiYXNlID09PSAxMCAmJiBNYXRoLmxvZzEwCiAgICAgICAgICB8fCBiYXNlID09PSAyICYmIE1hdGgubG9nMgogICAgICAgICAgfHwgKGJhc2UgPSBNYXRoLmxvZyhiYXNlKSwgZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5sb2coeCkgLyBiYXNlOyB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZWZsZWN0KGYpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gLWYoLXgpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGxvZ2dpc2godHJhbnNmb3JtKSB7CiAgICAgIHZhciBzY2FsZSA9IHRyYW5zZm9ybSh0cmFuc2Zvcm1Mb2csIHRyYW5zZm9ybUV4cCksCiAgICAgICAgICBkb21haW4gPSBzY2FsZS5kb21haW4sCiAgICAgICAgICBiYXNlID0gMTAsCiAgICAgICAgICBsb2dzLAogICAgICAgICAgcG93czsKCiAgICAgIGZ1bmN0aW9uIHJlc2NhbGUoKSB7CiAgICAgICAgbG9ncyA9IGxvZ3AoYmFzZSksIHBvd3MgPSBwb3dwKGJhc2UpOwogICAgICAgIGlmIChkb21haW4oKVswXSA8IDApIHsKICAgICAgICAgIGxvZ3MgPSByZWZsZWN0KGxvZ3MpLCBwb3dzID0gcmVmbGVjdChwb3dzKTsKICAgICAgICAgIHRyYW5zZm9ybSh0cmFuc2Zvcm1Mb2duLCB0cmFuc2Zvcm1FeHBuKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdHJhbnNmb3JtKHRyYW5zZm9ybUxvZywgdHJhbnNmb3JtRXhwKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9CgogICAgICBzY2FsZS5iYXNlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGJhc2UgPSArXywgcmVzY2FsZSgpKSA6IGJhc2U7CiAgICAgIH07CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluKF8pLCByZXNjYWxlKCkpIDogZG9tYWluKCk7CiAgICAgIH07CgogICAgICBzY2FsZS50aWNrcyA9IGZ1bmN0aW9uKGNvdW50KSB7CiAgICAgICAgdmFyIGQgPSBkb21haW4oKSwKICAgICAgICAgICAgdSA9IGRbMF0sCiAgICAgICAgICAgIHYgPSBkW2QubGVuZ3RoIC0gMV0sCiAgICAgICAgICAgIHI7CgogICAgICAgIGlmIChyID0gdiA8IHUpIGkgPSB1LCB1ID0gdiwgdiA9IGk7CgogICAgICAgIHZhciBpID0gbG9ncyh1KSwKICAgICAgICAgICAgaiA9IGxvZ3ModiksCiAgICAgICAgICAgIHAsCiAgICAgICAgICAgIGssCiAgICAgICAgICAgIHQsCiAgICAgICAgICAgIG4gPSBjb3VudCA9PSBudWxsID8gMTAgOiArY291bnQsCiAgICAgICAgICAgIHogPSBbXTsKCiAgICAgICAgaWYgKCEoYmFzZSAlIDEpICYmIGogLSBpIDwgbikgewogICAgICAgICAgaSA9IE1hdGgucm91bmQoaSkgLSAxLCBqID0gTWF0aC5yb3VuZChqKSArIDE7CiAgICAgICAgICBpZiAodSA+IDApIGZvciAoOyBpIDwgajsgKytpKSB7CiAgICAgICAgICAgIGZvciAoayA9IDEsIHAgPSBwb3dzKGkpOyBrIDwgYmFzZTsgKytrKSB7CiAgICAgICAgICAgICAgdCA9IHAgKiBrOwogICAgICAgICAgICAgIGlmICh0IDwgdSkgY29udGludWU7CiAgICAgICAgICAgICAgaWYgKHQgPiB2KSBicmVhazsKICAgICAgICAgICAgICB6LnB1c2godCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBmb3IgKDsgaSA8IGo7ICsraSkgewogICAgICAgICAgICBmb3IgKGsgPSBiYXNlIC0gMSwgcCA9IHBvd3MoaSk7IGsgPj0gMTsgLS1rKSB7CiAgICAgICAgICAgICAgdCA9IHAgKiBrOwogICAgICAgICAgICAgIGlmICh0IDwgdSkgY29udGludWU7CiAgICAgICAgICAgICAgaWYgKHQgPiB2KSBicmVhazsKICAgICAgICAgICAgICB6LnB1c2godCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgeiA9IHRpY2tzKGksIGosIE1hdGgubWluKGogLSBpLCBuKSkubWFwKHBvd3MpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHIgPyB6LnJldmVyc2UoKSA6IHo7CiAgICAgIH07CgogICAgICBzY2FsZS50aWNrRm9ybWF0ID0gZnVuY3Rpb24oY291bnQsIHNwZWNpZmllcikgewogICAgICAgIGlmIChzcGVjaWZpZXIgPT0gbnVsbCkgc3BlY2lmaWVyID0gYmFzZSA9PT0gMTAgPyAiLjBlIiA6ICIsIjsKICAgICAgICBpZiAodHlwZW9mIHNwZWNpZmllciAhPT0gImZ1bmN0aW9uIikgc3BlY2lmaWVyID0gZm9ybWF0KHNwZWNpZmllcik7CiAgICAgICAgaWYgKGNvdW50ID09PSBJbmZpbml0eSkgcmV0dXJuIHNwZWNpZmllcjsKICAgICAgICBpZiAoY291bnQgPT0gbnVsbCkgY291bnQgPSAxMDsKICAgICAgICB2YXIgayA9IE1hdGgubWF4KDEsIGJhc2UgKiBjb3VudCAvIHNjYWxlLnRpY2tzKCkubGVuZ3RoKTsgLy8gVE9ETyBmYXN0IGVzdGltYXRlPwogICAgICAgIHJldHVybiBmdW5jdGlvbihkKSB7CiAgICAgICAgICB2YXIgaSA9IGQgLyBwb3dzKE1hdGgucm91bmQobG9ncyhkKSkpOwogICAgICAgICAgaWYgKGkgKiBiYXNlIDwgYmFzZSAtIDAuNSkgaSAqPSBiYXNlOwogICAgICAgICAgcmV0dXJuIGkgPD0gayA/IHNwZWNpZmllcihkKSA6ICIiOwogICAgICAgIH07CiAgICAgIH07CgogICAgICBzY2FsZS5uaWNlID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRvbWFpbihuaWNlKGRvbWFpbigpLCB7CiAgICAgICAgICBmbG9vcjogZnVuY3Rpb24oeCkgeyByZXR1cm4gcG93cyhNYXRoLmZsb29yKGxvZ3MoeCkpKTsgfSwKICAgICAgICAgIGNlaWw6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIHBvd3MoTWF0aC5jZWlsKGxvZ3MoeCkpKTsgfQogICAgICAgIH0pKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBzY2FsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBsb2ckMSgpIHsKICAgICAgdmFyIHNjYWxlID0gbG9nZ2lzaCh0cmFuc2Zvcm1lciQxKCkpLmRvbWFpbihbMSwgMTBdKTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gY29weShzY2FsZSwgbG9nJDEoKSkuYmFzZShzY2FsZS5iYXNlKCkpOwogICAgICB9OwoKICAgICAgaW5pdFJhbmdlLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybVN5bWxvZyhjKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIE1hdGguc2lnbih4KSAqIE1hdGgubG9nMXAoTWF0aC5hYnMoeCAvIGMpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2Zvcm1TeW1leHAoYykgewogICAgICByZXR1cm4gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBNYXRoLnNpZ24oeCkgKiBNYXRoLmV4cG0xKE1hdGguYWJzKHgpKSAqIGM7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3ltbG9naXNoKHRyYW5zZm9ybSkgewogICAgICB2YXIgYyA9IDEsIHNjYWxlID0gdHJhbnNmb3JtKHRyYW5zZm9ybVN5bWxvZyhjKSwgdHJhbnNmb3JtU3ltZXhwKGMpKTsKCiAgICAgIHNjYWxlLmNvbnN0YW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gdHJhbnNmb3JtKHRyYW5zZm9ybVN5bWxvZyhjID0gK18pLCB0cmFuc2Zvcm1TeW1leHAoYykpIDogYzsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5lYXJpc2goc2NhbGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN5bWxvZygpIHsKICAgICAgdmFyIHNjYWxlID0gc3ltbG9naXNoKHRyYW5zZm9ybWVyJDEoKSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkoc2NhbGUsIHN5bWxvZygpKS5jb25zdGFudChzY2FsZS5jb25zdGFudCgpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0UmFuZ2UuYXBwbHkoc2NhbGUsIGFyZ3VtZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtUG93KGV4cG9uZW50KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIHggPCAwID8gLU1hdGgucG93KC14LCBleHBvbmVudCkgOiBNYXRoLnBvdyh4LCBleHBvbmVudCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtU3FydCh4KSB7CiAgICAgIHJldHVybiB4IDwgMCA/IC1NYXRoLnNxcnQoLXgpIDogTWF0aC5zcXJ0KHgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybVNxdWFyZSh4KSB7CiAgICAgIHJldHVybiB4IDwgMCA/IC14ICogeCA6IHggKiB4OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvd2lzaCh0cmFuc2Zvcm0pIHsKICAgICAgdmFyIHNjYWxlID0gdHJhbnNmb3JtKGlkZW50aXR5JDYsIGlkZW50aXR5JDYpLAogICAgICAgICAgZXhwb25lbnQgPSAxOwoKICAgICAgZnVuY3Rpb24gcmVzY2FsZSgpIHsKICAgICAgICByZXR1cm4gZXhwb25lbnQgPT09IDEgPyB0cmFuc2Zvcm0oaWRlbnRpdHkkNiwgaWRlbnRpdHkkNikKICAgICAgICAgICAgOiBleHBvbmVudCA9PT0gMC41ID8gdHJhbnNmb3JtKHRyYW5zZm9ybVNxcnQsIHRyYW5zZm9ybVNxdWFyZSkKICAgICAgICAgICAgOiB0cmFuc2Zvcm0odHJhbnNmb3JtUG93KGV4cG9uZW50KSwgdHJhbnNmb3JtUG93KDEgLyBleHBvbmVudCkpOwogICAgICB9CgogICAgICBzY2FsZS5leHBvbmVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChleHBvbmVudCA9ICtfLCByZXNjYWxlKCkpIDogZXhwb25lbnQ7CiAgICAgIH07CgogICAgICByZXR1cm4gbGluZWFyaXNoKHNjYWxlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb3ckMSgpIHsKICAgICAgdmFyIHNjYWxlID0gcG93aXNoKHRyYW5zZm9ybWVyJDEoKSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkoc2NhbGUsIHBvdyQxKCkpLmV4cG9uZW50KHNjYWxlLmV4cG9uZW50KCkpOwogICAgICB9OwoKICAgICAgaW5pdFJhbmdlLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNxcnQkMSgpIHsKICAgICAgcmV0dXJuIHBvdyQxLmFwcGx5KG51bGwsIGFyZ3VtZW50cykuZXhwb25lbnQoMC41KTsKICAgIH0KCiAgICBmdW5jdGlvbiBxdWFudGlsZSgpIHsKICAgICAgdmFyIGRvbWFpbiA9IFtdLAogICAgICAgICAgcmFuZ2UgPSBbXSwKICAgICAgICAgIHRocmVzaG9sZHMgPSBbXSwKICAgICAgICAgIHVua25vd247CgogICAgICBmdW5jdGlvbiByZXNjYWxlKCkgewogICAgICAgIHZhciBpID0gMCwgbiA9IE1hdGgubWF4KDEsIHJhbmdlLmxlbmd0aCk7CiAgICAgICAgdGhyZXNob2xkcyA9IG5ldyBBcnJheShuIC0gMSk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHRocmVzaG9sZHNbaSAtIDFdID0gdGhyZXNob2xkKGRvbWFpbiwgaSAvIG4pOwogICAgICAgIHJldHVybiBzY2FsZTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeCkgewogICAgICAgIHJldHVybiBpc05hTih4ID0gK3gpID8gdW5rbm93biA6IHJhbmdlW2Jpc2VjdFJpZ2h0KHRocmVzaG9sZHMsIHgpXTsKICAgICAgfQoKICAgICAgc2NhbGUuaW52ZXJ0RXh0ZW50ID0gZnVuY3Rpb24oeSkgewogICAgICAgIHZhciBpID0gcmFuZ2UuaW5kZXhPZih5KTsKICAgICAgICByZXR1cm4gaSA8IDAgPyBbTmFOLCBOYU5dIDogWwogICAgICAgICAgaSA+IDAgPyB0aHJlc2hvbGRzW2kgLSAxXSA6IGRvbWFpblswXSwKICAgICAgICAgIGkgPCB0aHJlc2hvbGRzLmxlbmd0aCA/IHRocmVzaG9sZHNbaV0gOiBkb21haW5bZG9tYWluLmxlbmd0aCAtIDFdCiAgICAgICAgXTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBkb21haW4uc2xpY2UoKTsKICAgICAgICBkb21haW4gPSBbXTsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IF8ubGVuZ3RoLCBkOyBpIDwgbjsgKytpKSBpZiAoZCA9IF9baV0sIGQgIT0gbnVsbCAmJiAhaXNOYU4oZCA9ICtkKSkgZG9tYWluLnB1c2goZCk7CiAgICAgICAgZG9tYWluLnNvcnQoYXNjZW5kaW5nKTsKICAgICAgICByZXR1cm4gcmVzY2FsZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUucmFuZ2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocmFuZ2UgPSBzbGljZSQ1LmNhbGwoXyksIHJlc2NhbGUoKSkgOiByYW5nZS5zbGljZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUudW5rbm93biA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh1bmtub3duID0gXywgc2NhbGUpIDogdW5rbm93bjsKICAgICAgfTsKCiAgICAgIHNjYWxlLnF1YW50aWxlcyA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aHJlc2hvbGRzLnNsaWNlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHF1YW50aWxlKCkKICAgICAgICAgICAgLmRvbWFpbihkb21haW4pCiAgICAgICAgICAgIC5yYW5nZShyYW5nZSkKICAgICAgICAgICAgLnVua25vd24odW5rbm93bik7CiAgICAgIH07CgogICAgICByZXR1cm4gaW5pdFJhbmdlLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YW50aXplJDEoKSB7CiAgICAgIHZhciB4MCA9IDAsCiAgICAgICAgICB4MSA9IDEsCiAgICAgICAgICBuID0gMSwKICAgICAgICAgIGRvbWFpbiA9IFswLjVdLAogICAgICAgICAgcmFuZ2UgPSBbMCwgMV0sCiAgICAgICAgICB1bmtub3duOwoKICAgICAgZnVuY3Rpb24gc2NhbGUoeCkgewogICAgICAgIHJldHVybiB4IDw9IHggPyByYW5nZVtiaXNlY3RSaWdodChkb21haW4sIHgsIDAsIG4pXSA6IHVua25vd247CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHJlc2NhbGUoKSB7CiAgICAgICAgdmFyIGkgPSAtMTsKICAgICAgICBkb21haW4gPSBuZXcgQXJyYXkobik7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGRvbWFpbltpXSA9ICgoaSArIDEpICogeDEgLSAoaSAtIG4pICogeDApIC8gKG4gKyAxKTsKICAgICAgICByZXR1cm4gc2NhbGU7CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4MCA9ICtfWzBdLCB4MSA9ICtfWzFdLCByZXNjYWxlKCkpIDogW3gwLCB4MV07CiAgICAgIH07CgogICAgICBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChuID0gKHJhbmdlID0gc2xpY2UkNS5jYWxsKF8pKS5sZW5ndGggLSAxLCByZXNjYWxlKCkpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmludmVydEV4dGVudCA9IGZ1bmN0aW9uKHkpIHsKICAgICAgICB2YXIgaSA9IHJhbmdlLmluZGV4T2YoeSk7CiAgICAgICAgcmV0dXJuIGkgPCAwID8gW05hTiwgTmFOXQogICAgICAgICAgICA6IGkgPCAxID8gW3gwLCBkb21haW5bMF1dCiAgICAgICAgICAgIDogaSA+PSBuID8gW2RvbWFpbltuIC0gMV0sIHgxXQogICAgICAgICAgICA6IFtkb21haW5baSAtIDFdLCBkb21haW5baV1dOwogICAgICB9OwoKICAgICAgc2NhbGUudW5rbm93biA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh1bmtub3duID0gXywgc2NhbGUpIDogc2NhbGU7CiAgICAgIH07CgogICAgICBzY2FsZS50aHJlc2hvbGRzID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRvbWFpbi5zbGljZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBxdWFudGl6ZSQxKCkKICAgICAgICAgICAgLmRvbWFpbihbeDAsIHgxXSkKICAgICAgICAgICAgLnJhbmdlKHJhbmdlKQogICAgICAgICAgICAudW5rbm93bih1bmtub3duKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0UmFuZ2UuYXBwbHkobGluZWFyaXNoKHNjYWxlKSwgYXJndW1lbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aHJlc2hvbGQkMSgpIHsKICAgICAgdmFyIGRvbWFpbiA9IFswLjVdLAogICAgICAgICAgcmFuZ2UgPSBbMCwgMV0sCiAgICAgICAgICB1bmtub3duLAogICAgICAgICAgbiA9IDE7CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgcmV0dXJuIHggPD0geCA/IHJhbmdlW2Jpc2VjdFJpZ2h0KGRvbWFpbiwgeCwgMCwgbildIDogdW5rbm93bjsKICAgICAgfQoKICAgICAgc2NhbGUuZG9tYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRvbWFpbiA9IHNsaWNlJDUuY2FsbChfKSwgbiA9IE1hdGgubWluKGRvbWFpbi5sZW5ndGgsIHJhbmdlLmxlbmd0aCAtIDEpLCBzY2FsZSkgOiBkb21haW4uc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhbmdlID0gc2xpY2UkNS5jYWxsKF8pLCBuID0gTWF0aC5taW4oZG9tYWluLmxlbmd0aCwgcmFuZ2UubGVuZ3RoIC0gMSksIHNjYWxlKSA6IHJhbmdlLnNsaWNlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS5pbnZlcnRFeHRlbnQgPSBmdW5jdGlvbih5KSB7CiAgICAgICAgdmFyIGkgPSByYW5nZS5pbmRleE9mKHkpOwogICAgICAgIHJldHVybiBbZG9tYWluW2kgLSAxXSwgZG9tYWluW2ldXTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnVua25vd24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodW5rbm93biA9IF8sIHNjYWxlKSA6IHVua25vd247CiAgICAgIH07CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRocmVzaG9sZCQxKCkKICAgICAgICAgICAgLmRvbWFpbihkb21haW4pCiAgICAgICAgICAgIC5yYW5nZShyYW5nZSkKICAgICAgICAgICAgLnVua25vd24odW5rbm93bik7CiAgICAgIH07CgogICAgICByZXR1cm4gaW5pdFJhbmdlLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIHZhciB0MCQxID0gbmV3IERhdGUsCiAgICAgICAgdDEkMSA9IG5ldyBEYXRlOwoKICAgIGZ1bmN0aW9uIG5ld0ludGVydmFsKGZsb29yaSwgb2Zmc2V0aSwgY291bnQsIGZpZWxkKSB7CgogICAgICBmdW5jdGlvbiBpbnRlcnZhbChkYXRlKSB7CiAgICAgICAgcmV0dXJuIGZsb29yaShkYXRlID0gYXJndW1lbnRzLmxlbmd0aCA9PT0gMCA/IG5ldyBEYXRlIDogbmV3IERhdGUoK2RhdGUpKSwgZGF0ZTsKICAgICAgfQoKICAgICAgaW50ZXJ2YWwuZmxvb3IgPSBmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgcmV0dXJuIGZsb29yaShkYXRlID0gbmV3IERhdGUoK2RhdGUpKSwgZGF0ZTsKICAgICAgfTsKCiAgICAgIGludGVydmFsLmNlaWwgPSBmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgcmV0dXJuIGZsb29yaShkYXRlID0gbmV3IERhdGUoZGF0ZSAtIDEpKSwgb2Zmc2V0aShkYXRlLCAxKSwgZmxvb3JpKGRhdGUpLCBkYXRlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwucm91bmQgPSBmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgdmFyIGQwID0gaW50ZXJ2YWwoZGF0ZSksCiAgICAgICAgICAgIGQxID0gaW50ZXJ2YWwuY2VpbChkYXRlKTsKICAgICAgICByZXR1cm4gZGF0ZSAtIGQwIDwgZDEgLSBkYXRlID8gZDAgOiBkMTsKICAgICAgfTsKCiAgICAgIGludGVydmFsLm9mZnNldCA9IGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICByZXR1cm4gb2Zmc2V0aShkYXRlID0gbmV3IERhdGUoK2RhdGUpLCBzdGVwID09IG51bGwgPyAxIDogTWF0aC5mbG9vcihzdGVwKSksIGRhdGU7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5yYW5nZSA9IGZ1bmN0aW9uKHN0YXJ0LCBzdG9wLCBzdGVwKSB7CiAgICAgICAgdmFyIHJhbmdlID0gW10sIHByZXZpb3VzOwogICAgICAgIHN0YXJ0ID0gaW50ZXJ2YWwuY2VpbChzdGFydCk7CiAgICAgICAgc3RlcCA9IHN0ZXAgPT0gbnVsbCA/IDEgOiBNYXRoLmZsb29yKHN0ZXApOwogICAgICAgIGlmICghKHN0YXJ0IDwgc3RvcCkgfHwgIShzdGVwID4gMCkpIHJldHVybiByYW5nZTsgLy8gYWxzbyBoYW5kbGVzIEludmFsaWQgRGF0ZQogICAgICAgIGRvIHJhbmdlLnB1c2gocHJldmlvdXMgPSBuZXcgRGF0ZSgrc3RhcnQpKSwgb2Zmc2V0aShzdGFydCwgc3RlcCksIGZsb29yaShzdGFydCk7CiAgICAgICAgd2hpbGUgKHByZXZpb3VzIDwgc3RhcnQgJiYgc3RhcnQgPCBzdG9wKTsKICAgICAgICByZXR1cm4gcmFuZ2U7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5maWx0ZXIgPSBmdW5jdGlvbih0ZXN0KSB7CiAgICAgICAgcmV0dXJuIG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHdoaWxlIChmbG9vcmkoZGF0ZSksICF0ZXN0KGRhdGUpKSBkYXRlLnNldFRpbWUoZGF0ZSAtIDEpOwogICAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHsKICAgICAgICAgICAgaWYgKHN0ZXAgPCAwKSB3aGlsZSAoKytzdGVwIDw9IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCAtMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0gZWxzZSB3aGlsZSAoLS1zdGVwID49IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCArMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIGlmIChjb3VudCkgewogICAgICAgIGludGVydmFsLmNvdW50ID0gZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgICAgdDAkMS5zZXRUaW1lKCtzdGFydCksIHQxJDEuc2V0VGltZSgrZW5kKTsKICAgICAgICAgIGZsb29yaSh0MCQxKSwgZmxvb3JpKHQxJDEpOwogICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IoY291bnQodDAkMSwgdDEkMSkpOwogICAgICAgIH07CgogICAgICAgIGludGVydmFsLmV2ZXJ5ID0gZnVuY3Rpb24oc3RlcCkgewogICAgICAgICAgc3RlcCA9IE1hdGguZmxvb3Ioc3RlcCk7CiAgICAgICAgICByZXR1cm4gIWlzRmluaXRlKHN0ZXApIHx8ICEoc3RlcCA+IDApID8gbnVsbAogICAgICAgICAgICAgIDogIShzdGVwID4gMSkgPyBpbnRlcnZhbAogICAgICAgICAgICAgIDogaW50ZXJ2YWwuZmlsdGVyKGZpZWxkCiAgICAgICAgICAgICAgICAgID8gZnVuY3Rpb24oZCkgeyByZXR1cm4gZmllbGQoZCkgJSBzdGVwID09PSAwOyB9CiAgICAgICAgICAgICAgICAgIDogZnVuY3Rpb24oZCkgeyByZXR1cm4gaW50ZXJ2YWwuY291bnQoMCwgZCkgJSBzdGVwID09PSAwOyB9KTsKICAgICAgICB9OwogICAgICB9CgogICAgICByZXR1cm4gaW50ZXJ2YWw7CiAgICB9CgogICAgdmFyIG1pbGxpc2Vjb25kID0gbmV3SW50ZXJ2YWwoZnVuY3Rpb24oKSB7CiAgICAgIC8vIG5vb3AKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiBlbmQgLSBzdGFydDsKICAgIH0pOwoKICAgIC8vIEFuIG9wdGltaXplZCBpbXBsZW1lbnRhdGlvbiBmb3IgdGhpcyBzaW1wbGUgY2FzZS4KICAgIG1pbGxpc2Vjb25kLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICBrID0gTWF0aC5mbG9vcihrKTsKICAgICAgaWYgKCFpc0Zpbml0ZShrKSB8fCAhKGsgPiAwKSkgcmV0dXJuIG51bGw7CiAgICAgIGlmICghKGsgPiAxKSkgcmV0dXJuIG1pbGxpc2Vjb25kOwogICAgICByZXR1cm4gbmV3SW50ZXJ2YWwoZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIGRhdGUuc2V0VGltZShNYXRoLmZsb29yKGRhdGUgLyBrKSAqIGspOwogICAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGspOwogICAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBrOwogICAgICB9KTsKICAgIH07CiAgICB2YXIgbWlsbGlzZWNvbmRzID0gbWlsbGlzZWNvbmQucmFuZ2U7CgogICAgdmFyIGR1cmF0aW9uU2Vjb25kID0gMWUzOwogICAgdmFyIGR1cmF0aW9uTWludXRlID0gNmU0OwogICAgdmFyIGR1cmF0aW9uSG91ciA9IDM2ZTU7CiAgICB2YXIgZHVyYXRpb25EYXkgPSA4NjRlNTsKICAgIHZhciBkdXJhdGlvbldlZWsgPSA2MDQ4ZTU7CgogICAgdmFyIHNlY29uZCA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRUaW1lKGRhdGUgLSBkYXRlLmdldE1pbGxpc2Vjb25kcygpKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGR1cmF0aW9uU2Vjb25kKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBkdXJhdGlvblNlY29uZDsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDU2Vjb25kcygpOwogICAgfSk7CiAgICB2YXIgc2Vjb25kcyA9IHNlY29uZC5yYW5nZTsKCiAgICB2YXIgbWludXRlID0gbmV3SW50ZXJ2YWwoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFRpbWUoZGF0ZSAtIGRhdGUuZ2V0TWlsbGlzZWNvbmRzKCkgLSBkYXRlLmdldFNlY29uZHMoKSAqIGR1cmF0aW9uU2Vjb25kKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGR1cmF0aW9uTWludXRlKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBkdXJhdGlvbk1pbnV0ZTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0TWludXRlcygpOwogICAgfSk7CiAgICB2YXIgbWludXRlcyA9IG1pbnV0ZS5yYW5nZTsKCiAgICB2YXIgaG91ciA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRUaW1lKGRhdGUgLSBkYXRlLmdldE1pbGxpc2Vjb25kcygpIC0gZGF0ZS5nZXRTZWNvbmRzKCkgKiBkdXJhdGlvblNlY29uZCAtIGRhdGUuZ2V0TWludXRlcygpICogZHVyYXRpb25NaW51dGUpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25Ib3VyKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBkdXJhdGlvbkhvdXI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldEhvdXJzKCk7CiAgICB9KTsKICAgIHZhciBob3VycyA9IGhvdXIucmFuZ2U7CgogICAgdmFyIGRheSA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXREYXRlKGRhdGUuZ2V0RGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQgLSAoZW5kLmdldFRpbWV6b25lT2Zmc2V0KCkgLSBzdGFydC5nZXRUaW1lem9uZU9mZnNldCgpKSAqIGR1cmF0aW9uTWludXRlKSAvIGR1cmF0aW9uRGF5OwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXREYXRlKCkgLSAxOwogICAgfSk7CiAgICB2YXIgZGF5cyA9IGRheS5yYW5nZTsKCiAgICBmdW5jdGlvbiB3ZWVrZGF5KGkpIHsKICAgICAgcmV0dXJuIG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldERhdGUoZGF0ZS5nZXREYXRlKCkgLSAoZGF0ZS5nZXREYXkoKSArIDcgLSBpKSAlIDcpOwogICAgICAgIGRhdGUuc2V0SG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldERhdGUoZGF0ZS5nZXREYXRlKCkgKyBzdGVwICogNyk7CiAgICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0IC0gKGVuZC5nZXRUaW1lem9uZU9mZnNldCgpIC0gc3RhcnQuZ2V0VGltZXpvbmVPZmZzZXQoKSkgKiBkdXJhdGlvbk1pbnV0ZSkgLyBkdXJhdGlvbldlZWs7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBzdW5kYXkgPSB3ZWVrZGF5KDApOwogICAgdmFyIG1vbmRheSA9IHdlZWtkYXkoMSk7CiAgICB2YXIgdHVlc2RheSA9IHdlZWtkYXkoMik7CiAgICB2YXIgd2VkbmVzZGF5ID0gd2Vla2RheSgzKTsKICAgIHZhciB0aHVyc2RheSA9IHdlZWtkYXkoNCk7CiAgICB2YXIgZnJpZGF5ID0gd2Vla2RheSg1KTsKICAgIHZhciBzYXR1cmRheSA9IHdlZWtkYXkoNik7CgogICAgdmFyIHN1bmRheXMgPSBzdW5kYXkucmFuZ2U7CiAgICB2YXIgbW9uZGF5cyA9IG1vbmRheS5yYW5nZTsKICAgIHZhciB0dWVzZGF5cyA9IHR1ZXNkYXkucmFuZ2U7CiAgICB2YXIgd2VkbmVzZGF5cyA9IHdlZG5lc2RheS5yYW5nZTsKICAgIHZhciB0aHVyc2RheXMgPSB0aHVyc2RheS5yYW5nZTsKICAgIHZhciBmcmlkYXlzID0gZnJpZGF5LnJhbmdlOwogICAgdmFyIHNhdHVyZGF5cyA9IHNhdHVyZGF5LnJhbmdlOwoKICAgIHZhciBtb250aCA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXREYXRlKDEpOwogICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldE1vbnRoKGRhdGUuZ2V0TW9udGgoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldE1vbnRoKCkgLSBzdGFydC5nZXRNb250aCgpICsgKGVuZC5nZXRGdWxsWWVhcigpIC0gc3RhcnQuZ2V0RnVsbFllYXIoKSkgKiAxMjsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0TW9udGgoKTsKICAgIH0pOwogICAgdmFyIG1vbnRocyA9IG1vbnRoLnJhbmdlOwoKICAgIHZhciB5ZWFyID0gbmV3SW50ZXJ2YWwoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldE1vbnRoKDAsIDEpOwogICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldEZ1bGxZZWFyKGRhdGUuZ2V0RnVsbFllYXIoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldEZ1bGxZZWFyKCkgLSBzdGFydC5nZXRGdWxsWWVhcigpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRGdWxsWWVhcigpOwogICAgfSk7CgogICAgLy8gQW4gb3B0aW1pemVkIGltcGxlbWVudGF0aW9uIGZvciB0aGlzIHNpbXBsZSBjYXNlLgogICAgeWVhci5ldmVyeSA9IGZ1bmN0aW9uKGspIHsKICAgICAgcmV0dXJuICFpc0Zpbml0ZShrID0gTWF0aC5mbG9vcihrKSkgfHwgIShrID4gMCkgPyBudWxsIDogbmV3SW50ZXJ2YWwoZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIGRhdGUuc2V0RnVsbFllYXIoTWF0aC5mbG9vcihkYXRlLmdldEZ1bGxZZWFyKCkgLyBrKSAqIGspOwogICAgICAgIGRhdGUuc2V0TW9udGgoMCwgMSk7CiAgICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0RnVsbFllYXIoZGF0ZS5nZXRGdWxsWWVhcigpICsgc3RlcCAqIGspOwogICAgICB9KTsKICAgIH07CiAgICB2YXIgeWVhcnMgPSB5ZWFyLnJhbmdlOwoKICAgIHZhciB1dGNNaW51dGUgPSBuZXdJbnRlcnZhbChmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VVRDU2Vjb25kcygwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGR1cmF0aW9uTWludXRlKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBkdXJhdGlvbk1pbnV0ZTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDTWludXRlcygpOwogICAgfSk7CiAgICB2YXIgdXRjTWludXRlcyA9IHV0Y01pbnV0ZS5yYW5nZTsKCiAgICB2YXIgdXRjSG91ciA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENNaW51dGVzKDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25Ib3VyKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCkgLyBkdXJhdGlvbkhvdXI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ0hvdXJzKCk7CiAgICB9KTsKICAgIHZhciB1dGNIb3VycyA9IHV0Y0hvdXIucmFuZ2U7CgogICAgdmFyIHV0Y0RheSA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENEYXRlKGRhdGUuZ2V0VVRDRGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25EYXk7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ0RhdGUoKSAtIDE7CiAgICB9KTsKICAgIHZhciB1dGNEYXlzID0gdXRjRGF5LnJhbmdlOwoKICAgIGZ1bmN0aW9uIHV0Y1dlZWtkYXkoaSkgewogICAgICByZXR1cm4gbmV3SW50ZXJ2YWwoZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIGRhdGUuc2V0VVRDRGF0ZShkYXRlLmdldFVUQ0RhdGUoKSAtIChkYXRlLmdldFVUQ0RheSgpICsgNyAtIGkpICUgNyk7CiAgICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0VVRDRGF0ZShkYXRlLmdldFVUQ0RhdGUoKSArIHN0ZXAgKiA3KTsKICAgICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25XZWVrOwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgdXRjU3VuZGF5ID0gdXRjV2Vla2RheSgwKTsKICAgIHZhciB1dGNNb25kYXkgPSB1dGNXZWVrZGF5KDEpOwogICAgdmFyIHV0Y1R1ZXNkYXkgPSB1dGNXZWVrZGF5KDIpOwogICAgdmFyIHV0Y1dlZG5lc2RheSA9IHV0Y1dlZWtkYXkoMyk7CiAgICB2YXIgdXRjVGh1cnNkYXkgPSB1dGNXZWVrZGF5KDQpOwogICAgdmFyIHV0Y0ZyaWRheSA9IHV0Y1dlZWtkYXkoNSk7CiAgICB2YXIgdXRjU2F0dXJkYXkgPSB1dGNXZWVrZGF5KDYpOwoKICAgIHZhciB1dGNTdW5kYXlzID0gdXRjU3VuZGF5LnJhbmdlOwogICAgdmFyIHV0Y01vbmRheXMgPSB1dGNNb25kYXkucmFuZ2U7CiAgICB2YXIgdXRjVHVlc2RheXMgPSB1dGNUdWVzZGF5LnJhbmdlOwogICAgdmFyIHV0Y1dlZG5lc2RheXMgPSB1dGNXZWRuZXNkYXkucmFuZ2U7CiAgICB2YXIgdXRjVGh1cnNkYXlzID0gdXRjVGh1cnNkYXkucmFuZ2U7CiAgICB2YXIgdXRjRnJpZGF5cyA9IHV0Y0ZyaWRheS5yYW5nZTsKICAgIHZhciB1dGNTYXR1cmRheXMgPSB1dGNTYXR1cmRheS5yYW5nZTsKCiAgICB2YXIgdXRjTW9udGggPSBuZXdJbnRlcnZhbChmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VVRDRGF0ZSgxKTsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENNb250aChkYXRlLmdldFVUQ01vbnRoKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRVVENNb250aCgpIC0gc3RhcnQuZ2V0VVRDTW9udGgoKSArIChlbmQuZ2V0VVRDRnVsbFllYXIoKSAtIHN0YXJ0LmdldFVUQ0Z1bGxZZWFyKCkpICogMTI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ01vbnRoKCk7CiAgICB9KTsKICAgIHZhciB1dGNNb250aHMgPSB1dGNNb250aC5yYW5nZTsKCiAgICB2YXIgdXRjWWVhciA9IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENNb250aCgwLCAxKTsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENGdWxsWWVhcihkYXRlLmdldFVUQ0Z1bGxZZWFyKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRVVENGdWxsWWVhcigpIC0gc3RhcnQuZ2V0VVRDRnVsbFllYXIoKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDRnVsbFllYXIoKTsKICAgIH0pOwoKICAgIC8vIEFuIG9wdGltaXplZCBpbXBsZW1lbnRhdGlvbiBmb3IgdGhpcyBzaW1wbGUgY2FzZS4KICAgIHV0Y1llYXIuZXZlcnkgPSBmdW5jdGlvbihrKSB7CiAgICAgIHJldHVybiAhaXNGaW5pdGUoayA9IE1hdGguZmxvb3IoaykpIHx8ICEoayA+IDApID8gbnVsbCA6IG5ld0ludGVydmFsKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKE1hdGguZmxvb3IoZGF0ZS5nZXRVVENGdWxsWWVhcigpIC8gaykgKiBrKTsKICAgICAgICBkYXRlLnNldFVUQ01vbnRoKDAsIDEpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSArIHN0ZXAgKiBrKTsKICAgICAgfSk7CiAgICB9OwogICAgdmFyIHV0Y1llYXJzID0gdXRjWWVhci5yYW5nZTsKCiAgICBmdW5jdGlvbiBsb2NhbERhdGUoZCkgewogICAgICBpZiAoMCA8PSBkLnkgJiYgZC55IDwgMTAwKSB7CiAgICAgICAgdmFyIGRhdGUgPSBuZXcgRGF0ZSgtMSwgZC5tLCBkLmQsIGQuSCwgZC5NLCBkLlMsIGQuTCk7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkLnkpOwogICAgICAgIHJldHVybiBkYXRlOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgRGF0ZShkLnksIGQubSwgZC5kLCBkLkgsIGQuTSwgZC5TLCBkLkwpOwogICAgfQoKICAgIGZ1bmN0aW9uIHV0Y0RhdGUoZCkgewogICAgICBpZiAoMCA8PSBkLnkgJiYgZC55IDwgMTAwKSB7CiAgICAgICAgdmFyIGRhdGUgPSBuZXcgRGF0ZShEYXRlLlVUQygtMSwgZC5tLCBkLmQsIGQuSCwgZC5NLCBkLlMsIGQuTCkpOwogICAgICAgIGRhdGUuc2V0VVRDRnVsbFllYXIoZC55KTsKICAgICAgICByZXR1cm4gZGF0ZTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERhdGUoRGF0ZS5VVEMoZC55LCBkLm0sIGQuZCwgZC5ILCBkLk0sIGQuUywgZC5MKSk7CiAgICB9CgogICAgZnVuY3Rpb24gbmV3RGF0ZSh5LCBtLCBkKSB7CiAgICAgIHJldHVybiB7eTogeSwgbTogbSwgZDogZCwgSDogMCwgTTogMCwgUzogMCwgTDogMH07CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TG9jYWxlJDEobG9jYWxlKSB7CiAgICAgIHZhciBsb2NhbGVfZGF0ZVRpbWUgPSBsb2NhbGUuZGF0ZVRpbWUsCiAgICAgICAgICBsb2NhbGVfZGF0ZSA9IGxvY2FsZS5kYXRlLAogICAgICAgICAgbG9jYWxlX3RpbWUgPSBsb2NhbGUudGltZSwKICAgICAgICAgIGxvY2FsZV9wZXJpb2RzID0gbG9jYWxlLnBlcmlvZHMsCiAgICAgICAgICBsb2NhbGVfd2Vla2RheXMgPSBsb2NhbGUuZGF5cywKICAgICAgICAgIGxvY2FsZV9zaG9ydFdlZWtkYXlzID0gbG9jYWxlLnNob3J0RGF5cywKICAgICAgICAgIGxvY2FsZV9tb250aHMgPSBsb2NhbGUubW9udGhzLAogICAgICAgICAgbG9jYWxlX3Nob3J0TW9udGhzID0gbG9jYWxlLnNob3J0TW9udGhzOwoKICAgICAgdmFyIHBlcmlvZFJlID0gZm9ybWF0UmUobG9jYWxlX3BlcmlvZHMpLAogICAgICAgICAgcGVyaW9kTG9va3VwID0gZm9ybWF0TG9va3VwKGxvY2FsZV9wZXJpb2RzKSwKICAgICAgICAgIHdlZWtkYXlSZSA9IGZvcm1hdFJlKGxvY2FsZV93ZWVrZGF5cyksCiAgICAgICAgICB3ZWVrZGF5TG9va3VwID0gZm9ybWF0TG9va3VwKGxvY2FsZV93ZWVrZGF5cyksCiAgICAgICAgICBzaG9ydFdlZWtkYXlSZSA9IGZvcm1hdFJlKGxvY2FsZV9zaG9ydFdlZWtkYXlzKSwKICAgICAgICAgIHNob3J0V2Vla2RheUxvb2t1cCA9IGZvcm1hdExvb2t1cChsb2NhbGVfc2hvcnRXZWVrZGF5cyksCiAgICAgICAgICBtb250aFJlID0gZm9ybWF0UmUobG9jYWxlX21vbnRocyksCiAgICAgICAgICBtb250aExvb2t1cCA9IGZvcm1hdExvb2t1cChsb2NhbGVfbW9udGhzKSwKICAgICAgICAgIHNob3J0TW9udGhSZSA9IGZvcm1hdFJlKGxvY2FsZV9zaG9ydE1vbnRocyksCiAgICAgICAgICBzaG9ydE1vbnRoTG9va3VwID0gZm9ybWF0TG9va3VwKGxvY2FsZV9zaG9ydE1vbnRocyk7CgogICAgICB2YXIgZm9ybWF0cyA9IHsKICAgICAgICAiYSI6IGZvcm1hdFNob3J0V2Vla2RheSwKICAgICAgICAiQSI6IGZvcm1hdFdlZWtkYXksCiAgICAgICAgImIiOiBmb3JtYXRTaG9ydE1vbnRoLAogICAgICAgICJCIjogZm9ybWF0TW9udGgsCiAgICAgICAgImMiOiBudWxsLAogICAgICAgICJkIjogZm9ybWF0RGF5T2ZNb250aCwKICAgICAgICAiZSI6IGZvcm1hdERheU9mTW9udGgsCiAgICAgICAgImYiOiBmb3JtYXRNaWNyb3NlY29uZHMsCiAgICAgICAgIkgiOiBmb3JtYXRIb3VyMjQsCiAgICAgICAgIkkiOiBmb3JtYXRIb3VyMTIsCiAgICAgICAgImoiOiBmb3JtYXREYXlPZlllYXIsCiAgICAgICAgIkwiOiBmb3JtYXRNaWxsaXNlY29uZHMsCiAgICAgICAgIm0iOiBmb3JtYXRNb250aE51bWJlciwKICAgICAgICAiTSI6IGZvcm1hdE1pbnV0ZXMsCiAgICAgICAgInAiOiBmb3JtYXRQZXJpb2QsCiAgICAgICAgInEiOiBmb3JtYXRRdWFydGVyLAogICAgICAgICJRIjogZm9ybWF0VW5peFRpbWVzdGFtcCwKICAgICAgICAicyI6IGZvcm1hdFVuaXhUaW1lc3RhbXBTZWNvbmRzLAogICAgICAgICJTIjogZm9ybWF0U2Vjb25kcywKICAgICAgICAidSI6IGZvcm1hdFdlZWtkYXlOdW1iZXJNb25kYXksCiAgICAgICAgIlUiOiBmb3JtYXRXZWVrTnVtYmVyU3VuZGF5LAogICAgICAgICJWIjogZm9ybWF0V2Vla051bWJlcklTTywKICAgICAgICAidyI6IGZvcm1hdFdlZWtkYXlOdW1iZXJTdW5kYXksCiAgICAgICAgIlciOiBmb3JtYXRXZWVrTnVtYmVyTW9uZGF5LAogICAgICAgICJ4IjogbnVsbCwKICAgICAgICAiWCI6IG51bGwsCiAgICAgICAgInkiOiBmb3JtYXRZZWFyJDEsCiAgICAgICAgIlkiOiBmb3JtYXRGdWxsWWVhciwKICAgICAgICAiWiI6IGZvcm1hdFpvbmUsCiAgICAgICAgIiUiOiBmb3JtYXRMaXRlcmFsUGVyY2VudAogICAgICB9OwoKICAgICAgdmFyIHV0Y0Zvcm1hdHMgPSB7CiAgICAgICAgImEiOiBmb3JtYXRVVENTaG9ydFdlZWtkYXksCiAgICAgICAgIkEiOiBmb3JtYXRVVENXZWVrZGF5LAogICAgICAgICJiIjogZm9ybWF0VVRDU2hvcnRNb250aCwKICAgICAgICAiQiI6IGZvcm1hdFVUQ01vbnRoLAogICAgICAgICJjIjogbnVsbCwKICAgICAgICAiZCI6IGZvcm1hdFVUQ0RheU9mTW9udGgsCiAgICAgICAgImUiOiBmb3JtYXRVVENEYXlPZk1vbnRoLAogICAgICAgICJmIjogZm9ybWF0VVRDTWljcm9zZWNvbmRzLAogICAgICAgICJIIjogZm9ybWF0VVRDSG91cjI0LAogICAgICAgICJJIjogZm9ybWF0VVRDSG91cjEyLAogICAgICAgICJqIjogZm9ybWF0VVRDRGF5T2ZZZWFyLAogICAgICAgICJMIjogZm9ybWF0VVRDTWlsbGlzZWNvbmRzLAogICAgICAgICJtIjogZm9ybWF0VVRDTW9udGhOdW1iZXIsCiAgICAgICAgIk0iOiBmb3JtYXRVVENNaW51dGVzLAogICAgICAgICJwIjogZm9ybWF0VVRDUGVyaW9kLAogICAgICAgICJxIjogZm9ybWF0VVRDUXVhcnRlciwKICAgICAgICAiUSI6IGZvcm1hdFVuaXhUaW1lc3RhbXAsCiAgICAgICAgInMiOiBmb3JtYXRVbml4VGltZXN0YW1wU2Vjb25kcywKICAgICAgICAiUyI6IGZvcm1hdFVUQ1NlY29uZHMsCiAgICAgICAgInUiOiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyTW9uZGF5LAogICAgICAgICJVIjogZm9ybWF0VVRDV2Vla051bWJlclN1bmRheSwKICAgICAgICAiViI6IGZvcm1hdFVUQ1dlZWtOdW1iZXJJU08sCiAgICAgICAgInciOiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyU3VuZGF5LAogICAgICAgICJXIjogZm9ybWF0VVRDV2Vla051bWJlck1vbmRheSwKICAgICAgICAieCI6IG51bGwsCiAgICAgICAgIlgiOiBudWxsLAogICAgICAgICJ5IjogZm9ybWF0VVRDWWVhciwKICAgICAgICAiWSI6IGZvcm1hdFVUQ0Z1bGxZZWFyLAogICAgICAgICJaIjogZm9ybWF0VVRDWm9uZSwKICAgICAgICAiJSI6IGZvcm1hdExpdGVyYWxQZXJjZW50CiAgICAgIH07CgogICAgICB2YXIgcGFyc2VzID0gewogICAgICAgICJhIjogcGFyc2VTaG9ydFdlZWtkYXksCiAgICAgICAgIkEiOiBwYXJzZVdlZWtkYXksCiAgICAgICAgImIiOiBwYXJzZVNob3J0TW9udGgsCiAgICAgICAgIkIiOiBwYXJzZU1vbnRoLAogICAgICAgICJjIjogcGFyc2VMb2NhbGVEYXRlVGltZSwKICAgICAgICAiZCI6IHBhcnNlRGF5T2ZNb250aCwKICAgICAgICAiZSI6IHBhcnNlRGF5T2ZNb250aCwKICAgICAgICAiZiI6IHBhcnNlTWljcm9zZWNvbmRzLAogICAgICAgICJIIjogcGFyc2VIb3VyMjQsCiAgICAgICAgIkkiOiBwYXJzZUhvdXIyNCwKICAgICAgICAiaiI6IHBhcnNlRGF5T2ZZZWFyLAogICAgICAgICJMIjogcGFyc2VNaWxsaXNlY29uZHMsCiAgICAgICAgIm0iOiBwYXJzZU1vbnRoTnVtYmVyLAogICAgICAgICJNIjogcGFyc2VNaW51dGVzLAogICAgICAgICJwIjogcGFyc2VQZXJpb2QsCiAgICAgICAgInEiOiBwYXJzZVF1YXJ0ZXIsCiAgICAgICAgIlEiOiBwYXJzZVVuaXhUaW1lc3RhbXAsCiAgICAgICAgInMiOiBwYXJzZVVuaXhUaW1lc3RhbXBTZWNvbmRzLAogICAgICAgICJTIjogcGFyc2VTZWNvbmRzLAogICAgICAgICJ1IjogcGFyc2VXZWVrZGF5TnVtYmVyTW9uZGF5LAogICAgICAgICJVIjogcGFyc2VXZWVrTnVtYmVyU3VuZGF5LAogICAgICAgICJWIjogcGFyc2VXZWVrTnVtYmVySVNPLAogICAgICAgICJ3IjogcGFyc2VXZWVrZGF5TnVtYmVyU3VuZGF5LAogICAgICAgICJXIjogcGFyc2VXZWVrTnVtYmVyTW9uZGF5LAogICAgICAgICJ4IjogcGFyc2VMb2NhbGVEYXRlLAogICAgICAgICJYIjogcGFyc2VMb2NhbGVUaW1lLAogICAgICAgICJ5IjogcGFyc2VZZWFyLAogICAgICAgICJZIjogcGFyc2VGdWxsWWVhciwKICAgICAgICAiWiI6IHBhcnNlWm9uZSwKICAgICAgICAiJSI6IHBhcnNlTGl0ZXJhbFBlcmNlbnQKICAgICAgfTsKCiAgICAgIC8vIFRoZXNlIHJlY3Vyc2l2ZSBkaXJlY3RpdmUgZGVmaW5pdGlvbnMgbXVzdCBiZSBkZWZlcnJlZC4KICAgICAgZm9ybWF0cy54ID0gbmV3Rm9ybWF0KGxvY2FsZV9kYXRlLCBmb3JtYXRzKTsKICAgICAgZm9ybWF0cy5YID0gbmV3Rm9ybWF0KGxvY2FsZV90aW1lLCBmb3JtYXRzKTsKICAgICAgZm9ybWF0cy5jID0gbmV3Rm9ybWF0KGxvY2FsZV9kYXRlVGltZSwgZm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMueCA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZSwgdXRjRm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMuWCA9IG5ld0Zvcm1hdChsb2NhbGVfdGltZSwgdXRjRm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMuYyA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZVRpbWUsIHV0Y0Zvcm1hdHMpOwoKICAgICAgZnVuY3Rpb24gbmV3Rm9ybWF0KHNwZWNpZmllciwgZm9ybWF0cykgewogICAgICAgIHJldHVybiBmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgICB2YXIgc3RyaW5nID0gW10sCiAgICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICAgIGogPSAwLAogICAgICAgICAgICAgIG4gPSBzcGVjaWZpZXIubGVuZ3RoLAogICAgICAgICAgICAgIGMsCiAgICAgICAgICAgICAgcGFkLAogICAgICAgICAgICAgIGZvcm1hdDsKCiAgICAgICAgICBpZiAoIShkYXRlIGluc3RhbmNlb2YgRGF0ZSkpIGRhdGUgPSBuZXcgRGF0ZSgrZGF0ZSk7CgogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgICAgaWYgKHNwZWNpZmllci5jaGFyQ29kZUF0KGkpID09PSAzNykgewogICAgICAgICAgICAgIHN0cmluZy5wdXNoKHNwZWNpZmllci5zbGljZShqLCBpKSk7CiAgICAgICAgICAgICAgaWYgKChwYWQgPSBwYWRzW2MgPSBzcGVjaWZpZXIuY2hhckF0KCsraSldKSAhPSBudWxsKSBjID0gc3BlY2lmaWVyLmNoYXJBdCgrK2kpOwogICAgICAgICAgICAgIGVsc2UgcGFkID0gYyA9PT0gImUiID8gIiAiIDogIjAiOwogICAgICAgICAgICAgIGlmIChmb3JtYXQgPSBmb3JtYXRzW2NdKSBjID0gZm9ybWF0KGRhdGUsIHBhZCk7CiAgICAgICAgICAgICAgc3RyaW5nLnB1c2goYyk7CiAgICAgICAgICAgICAgaiA9IGkgKyAxOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgc3RyaW5nLnB1c2goc3BlY2lmaWVyLnNsaWNlKGosIGkpKTsKICAgICAgICAgIHJldHVybiBzdHJpbmcuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gbmV3UGFyc2Uoc3BlY2lmaWVyLCBaKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmluZykgewogICAgICAgICAgdmFyIGQgPSBuZXdEYXRlKDE5MDAsIHVuZGVmaW5lZCwgMSksCiAgICAgICAgICAgICAgaSA9IHBhcnNlU3BlY2lmaWVyKGQsIHNwZWNpZmllciwgc3RyaW5nICs9ICIiLCAwKSwKICAgICAgICAgICAgICB3ZWVrLCBkYXkkMTsKICAgICAgICAgIGlmIChpICE9IHN0cmluZy5sZW5ndGgpIHJldHVybiBudWxsOwoKICAgICAgICAgIC8vIElmIGEgVU5JWCB0aW1lc3RhbXAgaXMgc3BlY2lmaWVkLCByZXR1cm4gaXQuCiAgICAgICAgICBpZiAoIlEiIGluIGQpIHJldHVybiBuZXcgRGF0ZShkLlEpOwogICAgICAgICAgaWYgKCJzIiBpbiBkKSByZXR1cm4gbmV3IERhdGUoZC5zICogMTAwMCArICgiTCIgaW4gZCA/IGQuTCA6IDApKTsKCiAgICAgICAgICAvLyBJZiB0aGlzIGlzIHV0Y1BhcnNlLCBuZXZlciB1c2UgdGhlIGxvY2FsIHRpbWV6b25lLgogICAgICAgICAgaWYgKFogJiYgISgiWiIgaW4gZCkpIGQuWiA9IDA7CgogICAgICAgICAgLy8gVGhlIGFtLXBtIGZsYWcgaXMgMCBmb3IgQU0sIGFuZCAxIGZvciBQTS4KICAgICAgICAgIGlmICgicCIgaW4gZCkgZC5IID0gZC5IICUgMTIgKyBkLnAgKiAxMjsKCiAgICAgICAgICAvLyBJZiB0aGUgbW9udGggd2FzIG5vdCBzcGVjaWZpZWQsIGluaGVyaXQgZnJvbSB0aGUgcXVhcnRlci4KICAgICAgICAgIGlmIChkLm0gPT09IHVuZGVmaW5lZCkgZC5tID0gInEiIGluIGQgPyBkLnEgOiAwOwoKICAgICAgICAgIC8vIENvbnZlcnQgZGF5LW9mLXdlZWsgYW5kIHdlZWstb2YteWVhciB0byBkYXktb2YteWVhci4KICAgICAgICAgIGlmICgiViIgaW4gZCkgewogICAgICAgICAgICBpZiAoZC5WIDwgMSB8fCBkLlYgPiA1MykgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIGlmICghKCJ3IiBpbiBkKSkgZC53ID0gMTsKICAgICAgICAgICAgaWYgKCJaIiBpbiBkKSB7CiAgICAgICAgICAgICAgd2VlayA9IHV0Y0RhdGUobmV3RGF0ZShkLnksIDAsIDEpKSwgZGF5JDEgPSB3ZWVrLmdldFVUQ0RheSgpOwogICAgICAgICAgICAgIHdlZWsgPSBkYXkkMSA+IDQgfHwgZGF5JDEgPT09IDAgPyB1dGNNb25kYXkuY2VpbCh3ZWVrKSA6IHV0Y01vbmRheSh3ZWVrKTsKICAgICAgICAgICAgICB3ZWVrID0gdXRjRGF5Lm9mZnNldCh3ZWVrLCAoZC5WIC0gMSkgKiA3KTsKICAgICAgICAgICAgICBkLnkgPSB3ZWVrLmdldFVUQ0Z1bGxZZWFyKCk7CiAgICAgICAgICAgICAgZC5tID0gd2Vlay5nZXRVVENNb250aCgpOwogICAgICAgICAgICAgIGQuZCA9IHdlZWsuZ2V0VVRDRGF0ZSgpICsgKGQudyArIDYpICUgNzsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICB3ZWVrID0gbG9jYWxEYXRlKG5ld0RhdGUoZC55LCAwLCAxKSksIGRheSQxID0gd2Vlay5nZXREYXkoKTsKICAgICAgICAgICAgICB3ZWVrID0gZGF5JDEgPiA0IHx8IGRheSQxID09PSAwID8gbW9uZGF5LmNlaWwod2VlaykgOiBtb25kYXkod2Vlayk7CiAgICAgICAgICAgICAgd2VlayA9IGRheS5vZmZzZXQod2VlaywgKGQuViAtIDEpICogNyk7CiAgICAgICAgICAgICAgZC55ID0gd2Vlay5nZXRGdWxsWWVhcigpOwogICAgICAgICAgICAgIGQubSA9IHdlZWsuZ2V0TW9udGgoKTsKICAgICAgICAgICAgICBkLmQgPSB3ZWVrLmdldERhdGUoKSArIChkLncgKyA2KSAlIDc7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAoIlciIGluIGQgfHwgIlUiIGluIGQpIHsKICAgICAgICAgICAgaWYgKCEoInciIGluIGQpKSBkLncgPSAidSIgaW4gZCA/IGQudSAlIDcgOiAiVyIgaW4gZCA/IDEgOiAwOwogICAgICAgICAgICBkYXkkMSA9ICJaIiBpbiBkID8gdXRjRGF0ZShuZXdEYXRlKGQueSwgMCwgMSkpLmdldFVUQ0RheSgpIDogbG9jYWxEYXRlKG5ld0RhdGUoZC55LCAwLCAxKSkuZ2V0RGF5KCk7CiAgICAgICAgICAgIGQubSA9IDA7CiAgICAgICAgICAgIGQuZCA9ICJXIiBpbiBkID8gKGQudyArIDYpICUgNyArIGQuVyAqIDcgLSAoZGF5JDEgKyA1KSAlIDcgOiBkLncgKyBkLlUgKiA3IC0gKGRheSQxICsgNikgJSA3OwogICAgICAgICAgfQoKICAgICAgICAgIC8vIElmIGEgdGltZSB6b25lIGlzIHNwZWNpZmllZCwgYWxsIGZpZWxkcyBhcmUgaW50ZXJwcmV0ZWQgYXMgVVRDIGFuZCB0aGVuCiAgICAgICAgICAvLyBvZmZzZXQgYWNjb3JkaW5nIHRvIHRoZSBzcGVjaWZpZWQgdGltZSB6b25lLgogICAgICAgICAgaWYgKCJaIiBpbiBkKSB7CiAgICAgICAgICAgIGQuSCArPSBkLlogLyAxMDAgfCAwOwogICAgICAgICAgICBkLk0gKz0gZC5aICUgMTAwOwogICAgICAgICAgICByZXR1cm4gdXRjRGF0ZShkKTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBPdGhlcndpc2UsIGFsbCBmaWVsZHMgYXJlIGluIGxvY2FsIHRpbWUuCiAgICAgICAgICByZXR1cm4gbG9jYWxEYXRlKGQpOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlU3BlY2lmaWVyKGQsIHNwZWNpZmllciwgc3RyaW5nLCBqKSB7CiAgICAgICAgdmFyIGkgPSAwLAogICAgICAgICAgICBuID0gc3BlY2lmaWVyLmxlbmd0aCwKICAgICAgICAgICAgbSA9IHN0cmluZy5sZW5ndGgsCiAgICAgICAgICAgIGMsCiAgICAgICAgICAgIHBhcnNlOwoKICAgICAgICB3aGlsZSAoaSA8IG4pIHsKICAgICAgICAgIGlmIChqID49IG0pIHJldHVybiAtMTsKICAgICAgICAgIGMgPSBzcGVjaWZpZXIuY2hhckNvZGVBdChpKyspOwogICAgICAgICAgaWYgKGMgPT09IDM3KSB7CiAgICAgICAgICAgIGMgPSBzcGVjaWZpZXIuY2hhckF0KGkrKyk7CiAgICAgICAgICAgIHBhcnNlID0gcGFyc2VzW2MgaW4gcGFkcyA/IHNwZWNpZmllci5jaGFyQXQoaSsrKSA6IGNdOwogICAgICAgICAgICBpZiAoIXBhcnNlIHx8ICgoaiA9IHBhcnNlKGQsIHN0cmluZywgaikpIDwgMCkpIHJldHVybiAtMTsKICAgICAgICAgIH0gZWxzZSBpZiAoYyAhPSBzdHJpbmcuY2hhckNvZGVBdChqKyspKSB7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHJldHVybiBqOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZVBlcmlvZChkLCBzdHJpbmcsIGkpIHsKICAgICAgICB2YXIgbiA9IHBlcmlvZFJlLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgICByZXR1cm4gbiA/IChkLnAgPSBwZXJpb2RMb29rdXBbblswXS50b0xvd2VyQ2FzZSgpXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZVNob3J0V2Vla2RheShkLCBzdHJpbmcsIGkpIHsKICAgICAgICB2YXIgbiA9IHNob3J0V2Vla2RheVJlLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgICByZXR1cm4gbiA/IChkLncgPSBzaG9ydFdlZWtkYXlMb29rdXBbblswXS50b0xvd2VyQ2FzZSgpXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZVdlZWtkYXkoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgdmFyIG4gPSB3ZWVrZGF5UmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICAgIHJldHVybiBuID8gKGQudyA9IHdlZWtkYXlMb29rdXBbblswXS50b0xvd2VyQ2FzZSgpXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZVNob3J0TW9udGgoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgdmFyIG4gPSBzaG9ydE1vbnRoUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICAgIHJldHVybiBuID8gKGQubSA9IHNob3J0TW9udGhMb29rdXBbblswXS50b0xvd2VyQ2FzZSgpXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZU1vbnRoKGQsIHN0cmluZywgaSkgewogICAgICAgIHZhciBuID0gbW9udGhSZS5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgICAgcmV0dXJuIG4gPyAoZC5tID0gbW9udGhMb29rdXBbblswXS50b0xvd2VyQ2FzZSgpXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZUxvY2FsZURhdGVUaW1lKGQsIHN0cmluZywgaSkgewogICAgICAgIHJldHVybiBwYXJzZVNwZWNpZmllcihkLCBsb2NhbGVfZGF0ZVRpbWUsIHN0cmluZywgaSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlTG9jYWxlRGF0ZShkLCBzdHJpbmcsIGkpIHsKICAgICAgICByZXR1cm4gcGFyc2VTcGVjaWZpZXIoZCwgbG9jYWxlX2RhdGUsIHN0cmluZywgaSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlTG9jYWxlVGltZShkLCBzdHJpbmcsIGkpIHsKICAgICAgICByZXR1cm4gcGFyc2VTcGVjaWZpZXIoZCwgbG9jYWxlX3RpbWUsIHN0cmluZywgaSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFNob3J0V2Vla2RheShkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9zaG9ydFdlZWtkYXlzW2QuZ2V0RGF5KCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRXZWVrZGF5KGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3dlZWtkYXlzW2QuZ2V0RGF5KCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRTaG9ydE1vbnRoKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3Nob3J0TW9udGhzW2QuZ2V0TW9udGgoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdE1vbnRoKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX21vbnRoc1tkLmdldE1vbnRoKCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRQZXJpb2QoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfcGVyaW9kc1srKGQuZ2V0SG91cnMoKSA+PSAxMildOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRRdWFydGVyKGQpIHsKICAgICAgICByZXR1cm4gMSArIH5+KGQuZ2V0TW9udGgoKSAvIDMpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRVVENTaG9ydFdlZWtkYXkoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfc2hvcnRXZWVrZGF5c1tkLmdldFVUQ0RheSgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla2RheShkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV93ZWVrZGF5c1tkLmdldFVUQ0RheSgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDU2hvcnRNb250aChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9zaG9ydE1vbnRoc1tkLmdldFVUQ01vbnRoKCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRVVENNb250aChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9tb250aHNbZC5nZXRVVENNb250aCgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDUGVyaW9kKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3BlcmlvZHNbKyhkLmdldFVUQ0hvdXJzKCkgPj0gMTIpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDUXVhcnRlcihkKSB7CiAgICAgICAgcmV0dXJuIDEgKyB+fihkLmdldFVUQ01vbnRoKCkgLyAzKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHsKICAgICAgICBmb3JtYXQ6IGZ1bmN0aW9uKHNwZWNpZmllcikgewogICAgICAgICAgdmFyIGYgPSBuZXdGb3JtYXQoc3BlY2lmaWVyICs9ICIiLCBmb3JtYXRzKTsKICAgICAgICAgIGYudG9TdHJpbmcgPSBmdW5jdGlvbigpIHsgcmV0dXJuIHNwZWNpZmllcjsgfTsKICAgICAgICAgIHJldHVybiBmOwogICAgICAgIH0sCiAgICAgICAgcGFyc2U6IGZ1bmN0aW9uKHNwZWNpZmllcikgewogICAgICAgICAgdmFyIHAgPSBuZXdQYXJzZShzcGVjaWZpZXIgKz0gIiIsIGZhbHNlKTsKICAgICAgICAgIHAudG9TdHJpbmcgPSBmdW5jdGlvbigpIHsgcmV0dXJuIHNwZWNpZmllcjsgfTsKICAgICAgICAgIHJldHVybiBwOwogICAgICAgIH0sCiAgICAgICAgdXRjRm9ybWF0OiBmdW5jdGlvbihzcGVjaWZpZXIpIHsKICAgICAgICAgIHZhciBmID0gbmV3Rm9ybWF0KHNwZWNpZmllciArPSAiIiwgdXRjRm9ybWF0cyk7CiAgICAgICAgICBmLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7IHJldHVybiBzcGVjaWZpZXI7IH07CiAgICAgICAgICByZXR1cm4gZjsKICAgICAgICB9LAogICAgICAgIHV0Y1BhcnNlOiBmdW5jdGlvbihzcGVjaWZpZXIpIHsKICAgICAgICAgIHZhciBwID0gbmV3UGFyc2Uoc3BlY2lmaWVyICs9ICIiLCB0cnVlKTsKICAgICAgICAgIHAudG9TdHJpbmcgPSBmdW5jdGlvbigpIHsgcmV0dXJuIHNwZWNpZmllcjsgfTsKICAgICAgICAgIHJldHVybiBwOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICB2YXIgcGFkcyA9IHsiLSI6ICIiLCAiXyI6ICIgIiwgIjAiOiAiMCJ9LAogICAgICAgIG51bWJlclJlID0gL15ccypcZCsvLCAvLyBub3RlOiBpZ25vcmVzIG5leHQgZGlyZWN0aXZlCiAgICAgICAgcGVyY2VudFJlID0gL14lLywKICAgICAgICByZXF1b3RlUmUgPSAvW1xcXiQqKz98W1xdKCkue31dL2c7CgogICAgZnVuY3Rpb24gcGFkJDEodmFsdWUsIGZpbGwsIHdpZHRoKSB7CiAgICAgIHZhciBzaWduID0gdmFsdWUgPCAwID8gIi0iIDogIiIsCiAgICAgICAgICBzdHJpbmcgPSAoc2lnbiA/IC12YWx1ZSA6IHZhbHVlKSArICIiLAogICAgICAgICAgbGVuZ3RoID0gc3RyaW5nLmxlbmd0aDsKICAgICAgcmV0dXJuIHNpZ24gKyAobGVuZ3RoIDwgd2lkdGggPyBuZXcgQXJyYXkod2lkdGggLSBsZW5ndGggKyAxKS5qb2luKGZpbGwpICsgc3RyaW5nIDogc3RyaW5nKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXF1b3RlKHMpIHsKICAgICAgcmV0dXJuIHMucmVwbGFjZShyZXF1b3RlUmUsICJcXCQmIik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0UmUobmFtZXMpIHsKICAgICAgcmV0dXJuIG5ldyBSZWdFeHAoIl4oPzoiICsgbmFtZXMubWFwKHJlcXVvdGUpLmpvaW4oInwiKSArICIpIiwgImkiKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRMb29rdXAobmFtZXMpIHsKICAgICAgdmFyIG1hcCA9IHt9LCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBtYXBbbmFtZXNbaV0udG9Mb3dlckNhc2UoKV0gPSBpOwogICAgICByZXR1cm4gbWFwOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla2RheU51bWJlclN1bmRheShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IChkLncgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla2RheU51bWJlck1vbmRheShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IChkLnUgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla051bWJlclN1bmRheShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlUgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla051bWJlcklTTyhkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlYgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla051bWJlck1vbmRheShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlcgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRnVsbFllYXIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDQpKTsKICAgICAgcmV0dXJuIG4gPyAoZC55ID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVllYXIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC55ID0gK25bMF0gKyAoK25bMF0gPiA2OCA/IDE5MDAgOiAyMDAwKSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlWm9uZShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSAvXihaKXwoWystXVxkXGQpKD86Oj8oXGRcZCkpPy8uZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDYpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5aID0gblsxXSA/IDAgOiAtKG5bMl0gKyAoblszXSB8fCAiMDAiKSksIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVF1YXJ0ZXIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDEpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5xID0gblswXSAqIDMgLSAzLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VNb250aE51bWJlcihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLm0gPSBuWzBdIC0gMSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRGF5T2ZNb250aChkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLmQgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRGF5T2ZZZWFyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAzKSk7CiAgICAgIHJldHVybiBuID8gKGQubSA9IDAsIGQuZCA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VIb3VyMjQoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5IID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1pbnV0ZXMoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5NID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVNlY29uZHMoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5TID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1pbGxpc2Vjb25kcyhkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMykpOwogICAgICByZXR1cm4gbiA/IChkLkwgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlTWljcm9zZWNvbmRzKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyA2KSk7CiAgICAgIHJldHVybiBuID8gKGQuTCA9IE1hdGguZmxvb3IoblswXSAvIDEwMDApLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VMaXRlcmFsUGVyY2VudChkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBwZXJjZW50UmUuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDEpKTsKICAgICAgcmV0dXJuIG4gPyBpICsgblswXS5sZW5ndGggOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVVuaXhUaW1lc3RhbXAoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICByZXR1cm4gbiA/IChkLlEgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVW5peFRpbWVzdGFtcFNlY29uZHMoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICByZXR1cm4gbiA/IChkLnMgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdERheU9mTW9udGgoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDEoZC5nZXREYXRlKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEhvdXIyNChkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldEhvdXJzKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEhvdXIxMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldEhvdXJzKCkgJSAxMiB8fCAxMiwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0RGF5T2ZZZWFyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKDEgKyBkYXkuY291bnQoeWVhcihkKSwgZCksIHAsIDMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdE1pbGxpc2Vjb25kcyhkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldE1pbGxpc2Vjb25kcygpLCBwLCAzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRNaWNyb3NlY29uZHMoZCwgcCkgewogICAgICByZXR1cm4gZm9ybWF0TWlsbGlzZWNvbmRzKGQsIHApICsgIjAwMCI7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TW9udGhOdW1iZXIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDEoZC5nZXRNb250aCgpICsgMSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TWludXRlcyhkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldE1pbnV0ZXMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0U2Vjb25kcyhkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldFNlY29uZHMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0V2Vla2RheU51bWJlck1vbmRheShkKSB7CiAgICAgIHZhciBkYXkgPSBkLmdldERheSgpOwogICAgICByZXR1cm4gZGF5ID09PSAwID8gNyA6IGRheTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRXZWVrTnVtYmVyU3VuZGF5KGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKHN1bmRheS5jb3VudCh5ZWFyKGQpIC0gMSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtOdW1iZXJJU08oZCwgcCkgewogICAgICB2YXIgZGF5ID0gZC5nZXREYXkoKTsKICAgICAgZCA9IChkYXkgPj0gNCB8fCBkYXkgPT09IDApID8gdGh1cnNkYXkoZCkgOiB0aHVyc2RheS5jZWlsKGQpOwogICAgICByZXR1cm4gcGFkJDEodGh1cnNkYXkuY291bnQoeWVhcihkKSwgZCkgKyAoeWVhcihkKS5nZXREYXkoKSA9PT0gNCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtkYXlOdW1iZXJTdW5kYXkoZCkgewogICAgICByZXR1cm4gZC5nZXREYXkoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRXZWVrTnVtYmVyTW9uZGF5KGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKG1vbmRheS5jb3VudCh5ZWFyKGQpIC0gMSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFllYXIkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldEZ1bGxZZWFyKCkgJSAxMDAsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEZ1bGxZZWFyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0RnVsbFllYXIoKSAlIDEwMDAwLCBwLCA0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRab25lKGQpIHsKICAgICAgdmFyIHogPSBkLmdldFRpbWV6b25lT2Zmc2V0KCk7CiAgICAgIHJldHVybiAoeiA+IDAgPyAiLSIgOiAoeiAqPSAtMSwgIisiKSkKICAgICAgICAgICsgcGFkJDEoeiAvIDYwIHwgMCwgIjAiLCAyKQogICAgICAgICAgKyBwYWQkMSh6ICUgNjAsICIwIiwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDRGF5T2ZNb250aChkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldFVUQ0RhdGUoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDSG91cjI0KGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDSG91cnMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDSG91cjEyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDSG91cnMoKSAlIDEyIHx8IDEyLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENEYXlPZlllYXIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDEoMSArIHV0Y0RheS5jb3VudCh1dGNZZWFyKGQpLCBkKSwgcCwgMyk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDTWlsbGlzZWNvbmRzKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDTWlsbGlzZWNvbmRzKCksIHAsIDMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ01pY3Jvc2Vjb25kcyhkLCBwKSB7CiAgICAgIHJldHVybiBmb3JtYXRVVENNaWxsaXNlY29uZHMoZCwgcCkgKyAiMDAwIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENNb250aE51bWJlcihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldFVUQ01vbnRoKCkgKyAxLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENNaW51dGVzKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDTWludXRlcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENTZWNvbmRzKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDU2Vjb25kcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyTW9uZGF5KGQpIHsKICAgICAgdmFyIGRvdyA9IGQuZ2V0VVRDRGF5KCk7CiAgICAgIHJldHVybiBkb3cgPT09IDAgPyA3IDogZG93OwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1dlZWtOdW1iZXJTdW5kYXkoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDEodXRjU3VuZGF5LmNvdW50KHV0Y1llYXIoZCkgLSAxLCBkKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla051bWJlcklTTyhkLCBwKSB7CiAgICAgIHZhciBkYXkgPSBkLmdldFVUQ0RheSgpOwogICAgICBkID0gKGRheSA+PSA0IHx8IGRheSA9PT0gMCkgPyB1dGNUaHVyc2RheShkKSA6IHV0Y1RodXJzZGF5LmNlaWwoZCk7CiAgICAgIHJldHVybiBwYWQkMSh1dGNUaHVyc2RheS5jb3VudCh1dGNZZWFyKGQpLCBkKSArICh1dGNZZWFyKGQpLmdldFVUQ0RheSgpID09PSA0KSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla2RheU51bWJlclN1bmRheShkKSB7CiAgICAgIHJldHVybiBkLmdldFVUQ0RheSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1dlZWtOdW1iZXJNb25kYXkoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDEodXRjTW9uZGF5LmNvdW50KHV0Y1llYXIoZCkgLSAxLCBkKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDWWVhcihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMShkLmdldFVUQ0Z1bGxZZWFyKCkgJSAxMDAsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0Z1bGxZZWFyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQxKGQuZ2V0VVRDRnVsbFllYXIoKSAlIDEwMDAwLCBwLCA0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENab25lKCkgewogICAgICByZXR1cm4gIiswMDAwIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRMaXRlcmFsUGVyY2VudCgpIHsKICAgICAgcmV0dXJuICIlIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVbml4VGltZXN0YW1wKGQpIHsKICAgICAgcmV0dXJuICtkOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVuaXhUaW1lc3RhbXBTZWNvbmRzKGQpIHsKICAgICAgcmV0dXJuIE1hdGguZmxvb3IoK2QgLyAxMDAwKTsKICAgIH0KCiAgICB2YXIgbG9jYWxlJDE7CiAgICB2YXIgdGltZUZvcm1hdDsKICAgIHZhciB0aW1lUGFyc2U7CiAgICB2YXIgdXRjRm9ybWF0OwogICAgdmFyIHV0Y1BhcnNlOwoKICAgIGRlZmF1bHRMb2NhbGUkMSh7CiAgICAgIGRhdGVUaW1lOiAiJXgsICVYIiwKICAgICAgZGF0ZTogIiUtbS8lLWQvJVkiLAogICAgICB0aW1lOiAiJS1JOiVNOiVTICVwIiwKICAgICAgcGVyaW9kczogWyJBTSIsICJQTSJdLAogICAgICBkYXlzOiBbIlN1bmRheSIsICJNb25kYXkiLCAiVHVlc2RheSIsICJXZWRuZXNkYXkiLCAiVGh1cnNkYXkiLCAiRnJpZGF5IiwgIlNhdHVyZGF5Il0sCiAgICAgIHNob3J0RGF5czogWyJTdW4iLCAiTW9uIiwgIlR1ZSIsICJXZWQiLCAiVGh1IiwgIkZyaSIsICJTYXQiXSwKICAgICAgbW9udGhzOiBbIkphbnVhcnkiLCAiRmVicnVhcnkiLCAiTWFyY2giLCAiQXByaWwiLCAiTWF5IiwgIkp1bmUiLCAiSnVseSIsICJBdWd1c3QiLCAiU2VwdGVtYmVyIiwgIk9jdG9iZXIiLCAiTm92ZW1iZXIiLCAiRGVjZW1iZXIiXSwKICAgICAgc2hvcnRNb250aHM6IFsiSmFuIiwgIkZlYiIsICJNYXIiLCAiQXByIiwgIk1heSIsICJKdW4iLCAiSnVsIiwgIkF1ZyIsICJTZXAiLCAiT2N0IiwgIk5vdiIsICJEZWMiXQogICAgfSk7CgogICAgZnVuY3Rpb24gZGVmYXVsdExvY2FsZSQxKGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlJDEgPSBmb3JtYXRMb2NhbGUkMShkZWZpbml0aW9uKTsKICAgICAgdGltZUZvcm1hdCA9IGxvY2FsZSQxLmZvcm1hdDsKICAgICAgdGltZVBhcnNlID0gbG9jYWxlJDEucGFyc2U7CiAgICAgIHV0Y0Zvcm1hdCA9IGxvY2FsZSQxLnV0Y0Zvcm1hdDsKICAgICAgdXRjUGFyc2UgPSBsb2NhbGUkMS51dGNQYXJzZTsKICAgICAgcmV0dXJuIGxvY2FsZSQxOwogICAgfQoKICAgIHZhciBpc29TcGVjaWZpZXIgPSAiJVktJW0tJWRUJUg6JU06JVMuJUxaIjsKCiAgICBmdW5jdGlvbiBmb3JtYXRJc29OYXRpdmUoZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS50b0lTT1N0cmluZygpOwogICAgfQoKICAgIHZhciBmb3JtYXRJc28gPSBEYXRlLnByb3RvdHlwZS50b0lTT1N0cmluZwogICAgICAgID8gZm9ybWF0SXNvTmF0aXZlCiAgICAgICAgOiB1dGNGb3JtYXQoaXNvU3BlY2lmaWVyKTsKCiAgICBmdW5jdGlvbiBwYXJzZUlzb05hdGl2ZShzdHJpbmcpIHsKICAgICAgdmFyIGRhdGUgPSBuZXcgRGF0ZShzdHJpbmcpOwogICAgICByZXR1cm4gaXNOYU4oZGF0ZSkgPyBudWxsIDogZGF0ZTsKICAgIH0KCiAgICB2YXIgcGFyc2VJc28gPSArbmV3IERhdGUoIjIwMDAtMDEtMDFUMDA6MDA6MDAuMDAwWiIpCiAgICAgICAgPyBwYXJzZUlzb05hdGl2ZQogICAgICAgIDogdXRjUGFyc2UoaXNvU3BlY2lmaWVyKTsKCiAgICB2YXIgZHVyYXRpb25TZWNvbmQkMSA9IDEwMDAsCiAgICAgICAgZHVyYXRpb25NaW51dGUkMSA9IGR1cmF0aW9uU2Vjb25kJDEgKiA2MCwKICAgICAgICBkdXJhdGlvbkhvdXIkMSA9IGR1cmF0aW9uTWludXRlJDEgKiA2MCwKICAgICAgICBkdXJhdGlvbkRheSQxID0gZHVyYXRpb25Ib3VyJDEgKiAyNCwKICAgICAgICBkdXJhdGlvbldlZWskMSA9IGR1cmF0aW9uRGF5JDEgKiA3LAogICAgICAgIGR1cmF0aW9uTW9udGggPSBkdXJhdGlvbkRheSQxICogMzAsCiAgICAgICAgZHVyYXRpb25ZZWFyID0gZHVyYXRpb25EYXkkMSAqIDM2NTsKCiAgICBmdW5jdGlvbiBkYXRlJDEodCkgewogICAgICByZXR1cm4gbmV3IERhdGUodCk7CiAgICB9CgogICAgZnVuY3Rpb24gbnVtYmVyJDModCkgewogICAgICByZXR1cm4gdCBpbnN0YW5jZW9mIERhdGUgPyArdCA6ICtuZXcgRGF0ZSgrdCk7CiAgICB9CgogICAgZnVuY3Rpb24gY2FsZW5kYXIoeWVhciwgbW9udGgsIHdlZWssIGRheSwgaG91ciwgbWludXRlLCBzZWNvbmQsIG1pbGxpc2Vjb25kLCBmb3JtYXQpIHsKICAgICAgdmFyIHNjYWxlID0gY29udGludW91cyhpZGVudGl0eSQ2LCBpZGVudGl0eSQ2KSwKICAgICAgICAgIGludmVydCA9IHNjYWxlLmludmVydCwKICAgICAgICAgIGRvbWFpbiA9IHNjYWxlLmRvbWFpbjsKCiAgICAgIHZhciBmb3JtYXRNaWxsaXNlY29uZCA9IGZvcm1hdCgiLiVMIiksCiAgICAgICAgICBmb3JtYXRTZWNvbmQgPSBmb3JtYXQoIjolUyIpLAogICAgICAgICAgZm9ybWF0TWludXRlID0gZm9ybWF0KCIlSTolTSIpLAogICAgICAgICAgZm9ybWF0SG91ciA9IGZvcm1hdCgiJUkgJXAiKSwKICAgICAgICAgIGZvcm1hdERheSA9IGZvcm1hdCgiJWEgJWQiKSwKICAgICAgICAgIGZvcm1hdFdlZWsgPSBmb3JtYXQoIiViICVkIiksCiAgICAgICAgICBmb3JtYXRNb250aCA9IGZvcm1hdCgiJUIiKSwKICAgICAgICAgIGZvcm1hdFllYXIgPSBmb3JtYXQoIiVZIik7CgogICAgICB2YXIgdGlja0ludGVydmFscyA9IFsKICAgICAgICBbc2Vjb25kLCAgMSwgICAgICBkdXJhdGlvblNlY29uZCQxXSwKICAgICAgICBbc2Vjb25kLCAgNSwgIDUgKiBkdXJhdGlvblNlY29uZCQxXSwKICAgICAgICBbc2Vjb25kLCAxNSwgMTUgKiBkdXJhdGlvblNlY29uZCQxXSwKICAgICAgICBbc2Vjb25kLCAzMCwgMzAgKiBkdXJhdGlvblNlY29uZCQxXSwKICAgICAgICBbbWludXRlLCAgMSwgICAgICBkdXJhdGlvbk1pbnV0ZSQxXSwKICAgICAgICBbbWludXRlLCAgNSwgIDUgKiBkdXJhdGlvbk1pbnV0ZSQxXSwKICAgICAgICBbbWludXRlLCAxNSwgMTUgKiBkdXJhdGlvbk1pbnV0ZSQxXSwKICAgICAgICBbbWludXRlLCAzMCwgMzAgKiBkdXJhdGlvbk1pbnV0ZSQxXSwKICAgICAgICBbICBob3VyLCAgMSwgICAgICBkdXJhdGlvbkhvdXIkMSAgXSwKICAgICAgICBbICBob3VyLCAgMywgIDMgKiBkdXJhdGlvbkhvdXIkMSAgXSwKICAgICAgICBbICBob3VyLCAgNiwgIDYgKiBkdXJhdGlvbkhvdXIkMSAgXSwKICAgICAgICBbICBob3VyLCAxMiwgMTIgKiBkdXJhdGlvbkhvdXIkMSAgXSwKICAgICAgICBbICAgZGF5LCAgMSwgICAgICBkdXJhdGlvbkRheSQxICAgXSwKICAgICAgICBbICAgZGF5LCAgMiwgIDIgKiBkdXJhdGlvbkRheSQxICAgXSwKICAgICAgICBbICB3ZWVrLCAgMSwgICAgICBkdXJhdGlvbldlZWskMSAgXSwKICAgICAgICBbIG1vbnRoLCAgMSwgICAgICBkdXJhdGlvbk1vbnRoIF0sCiAgICAgICAgWyBtb250aCwgIDMsICAzICogZHVyYXRpb25Nb250aCBdLAogICAgICAgIFsgIHllYXIsICAxLCAgICAgIGR1cmF0aW9uWWVhciAgXQogICAgICBdOwoKICAgICAgZnVuY3Rpb24gdGlja0Zvcm1hdChkYXRlKSB7CiAgICAgICAgcmV0dXJuIChzZWNvbmQoZGF0ZSkgPCBkYXRlID8gZm9ybWF0TWlsbGlzZWNvbmQKICAgICAgICAgICAgOiBtaW51dGUoZGF0ZSkgPCBkYXRlID8gZm9ybWF0U2Vjb25kCiAgICAgICAgICAgIDogaG91cihkYXRlKSA8IGRhdGUgPyBmb3JtYXRNaW51dGUKICAgICAgICAgICAgOiBkYXkoZGF0ZSkgPCBkYXRlID8gZm9ybWF0SG91cgogICAgICAgICAgICA6IG1vbnRoKGRhdGUpIDwgZGF0ZSA/ICh3ZWVrKGRhdGUpIDwgZGF0ZSA/IGZvcm1hdERheSA6IGZvcm1hdFdlZWspCiAgICAgICAgICAgIDogeWVhcihkYXRlKSA8IGRhdGUgPyBmb3JtYXRNb250aAogICAgICAgICAgICA6IGZvcm1hdFllYXIpKGRhdGUpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0aWNrSW50ZXJ2YWwoaW50ZXJ2YWwsIHN0YXJ0LCBzdG9wLCBzdGVwKSB7CiAgICAgICAgaWYgKGludGVydmFsID09IG51bGwpIGludGVydmFsID0gMTA7CgogICAgICAgIC8vIElmIGEgZGVzaXJlZCB0aWNrIGNvdW50IGlzIHNwZWNpZmllZCwgcGljayBhIHJlYXNvbmFibGUgdGljayBpbnRlcnZhbAogICAgICAgIC8vIGJhc2VkIG9uIHRoZSBleHRlbnQgb2YgdGhlIGRvbWFpbiBhbmQgYSByb3VnaCBlc3RpbWF0ZSBvZiB0aWNrIHNpemUuCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBhc3N1bWUgaW50ZXJ2YWwgaXMgYWxyZWFkeSBhIHRpbWUgaW50ZXJ2YWwgYW5kIHVzZSBpdC4KICAgICAgICBpZiAodHlwZW9mIGludGVydmFsID09PSAibnVtYmVyIikgewogICAgICAgICAgdmFyIHRhcmdldCA9IE1hdGguYWJzKHN0b3AgLSBzdGFydCkgLyBpbnRlcnZhbCwKICAgICAgICAgICAgICBpID0gYmlzZWN0b3IoZnVuY3Rpb24oaSkgeyByZXR1cm4gaVsyXTsgfSkucmlnaHQodGlja0ludGVydmFscywgdGFyZ2V0KTsKICAgICAgICAgIGlmIChpID09PSB0aWNrSW50ZXJ2YWxzLmxlbmd0aCkgewogICAgICAgICAgICBzdGVwID0gdGlja1N0ZXAoc3RhcnQgLyBkdXJhdGlvblllYXIsIHN0b3AgLyBkdXJhdGlvblllYXIsIGludGVydmFsKTsKICAgICAgICAgICAgaW50ZXJ2YWwgPSB5ZWFyOwogICAgICAgICAgfSBlbHNlIGlmIChpKSB7CiAgICAgICAgICAgIGkgPSB0aWNrSW50ZXJ2YWxzW3RhcmdldCAvIHRpY2tJbnRlcnZhbHNbaSAtIDFdWzJdIDwgdGlja0ludGVydmFsc1tpXVsyXSAvIHRhcmdldCA/IGkgLSAxIDogaV07CiAgICAgICAgICAgIHN0ZXAgPSBpWzFdOwogICAgICAgICAgICBpbnRlcnZhbCA9IGlbMF07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBzdGVwID0gTWF0aC5tYXgodGlja1N0ZXAoc3RhcnQsIHN0b3AsIGludGVydmFsKSwgMSk7CiAgICAgICAgICAgIGludGVydmFsID0gbWlsbGlzZWNvbmQ7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gc3RlcCA9PSBudWxsID8gaW50ZXJ2YWwgOiBpbnRlcnZhbC5ldmVyeShzdGVwKTsKICAgICAgfQoKICAgICAgc2NhbGUuaW52ZXJ0ID0gZnVuY3Rpb24oeSkgewogICAgICAgIHJldHVybiBuZXcgRGF0ZShpbnZlcnQoeSkpOwogICAgICB9OwoKICAgICAgc2NhbGUuZG9tYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gZG9tYWluKG1hcCQzLmNhbGwoXywgbnVtYmVyJDMpKSA6IGRvbWFpbigpLm1hcChkYXRlJDEpOwogICAgICB9OwoKICAgICAgc2NhbGUudGlja3MgPSBmdW5jdGlvbihpbnRlcnZhbCwgc3RlcCkgewogICAgICAgIHZhciBkID0gZG9tYWluKCksCiAgICAgICAgICAgIHQwID0gZFswXSwKICAgICAgICAgICAgdDEgPSBkW2QubGVuZ3RoIC0gMV0sCiAgICAgICAgICAgIHIgPSB0MSA8IHQwLAogICAgICAgICAgICB0OwogICAgICAgIGlmIChyKSB0ID0gdDAsIHQwID0gdDEsIHQxID0gdDsKICAgICAgICB0ID0gdGlja0ludGVydmFsKGludGVydmFsLCB0MCwgdDEsIHN0ZXApOwogICAgICAgIHQgPSB0ID8gdC5yYW5nZSh0MCwgdDEgKyAxKSA6IFtdOyAvLyBpbmNsdXNpdmUgc3RvcAogICAgICAgIHJldHVybiByID8gdC5yZXZlcnNlKCkgOiB0OwogICAgICB9OwoKICAgICAgc2NhbGUudGlja0Zvcm1hdCA9IGZ1bmN0aW9uKGNvdW50LCBzcGVjaWZpZXIpIHsKICAgICAgICByZXR1cm4gc3BlY2lmaWVyID09IG51bGwgPyB0aWNrRm9ybWF0IDogZm9ybWF0KHNwZWNpZmllcik7CiAgICAgIH07CgogICAgICBzY2FsZS5uaWNlID0gZnVuY3Rpb24oaW50ZXJ2YWwsIHN0ZXApIHsKICAgICAgICB2YXIgZCA9IGRvbWFpbigpOwogICAgICAgIHJldHVybiAoaW50ZXJ2YWwgPSB0aWNrSW50ZXJ2YWwoaW50ZXJ2YWwsIGRbMF0sIGRbZC5sZW5ndGggLSAxXSwgc3RlcCkpCiAgICAgICAgICAgID8gZG9tYWluKG5pY2UoZCwgaW50ZXJ2YWwpKQogICAgICAgICAgICA6IHNjYWxlOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5KHNjYWxlLCBjYWxlbmRhcih5ZWFyLCBtb250aCwgd2VlaywgZGF5LCBob3VyLCBtaW51dGUsIHNlY29uZCwgbWlsbGlzZWNvbmQsIGZvcm1hdCkpOwogICAgICB9OwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWUoKSB7CiAgICAgIHJldHVybiBpbml0UmFuZ2UuYXBwbHkoY2FsZW5kYXIoeWVhciwgbW9udGgsIHN1bmRheSwgZGF5LCBob3VyLCBtaW51dGUsIHNlY29uZCwgbWlsbGlzZWNvbmQsIHRpbWVGb3JtYXQpLmRvbWFpbihbbmV3IERhdGUoMjAwMCwgMCwgMSksIG5ldyBEYXRlKDIwMDAsIDAsIDIpXSksIGFyZ3VtZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gdXRjVGltZSgpIHsKICAgICAgcmV0dXJuIGluaXRSYW5nZS5hcHBseShjYWxlbmRhcih1dGNZZWFyLCB1dGNNb250aCwgdXRjU3VuZGF5LCB1dGNEYXksIHV0Y0hvdXIsIHV0Y01pbnV0ZSwgc2Vjb25kLCBtaWxsaXNlY29uZCwgdXRjRm9ybWF0KS5kb21haW4oW0RhdGUuVVRDKDIwMDAsIDAsIDEpLCBEYXRlLlVUQygyMDAwLCAwLCAyKV0pLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybWVyJDIoKSB7CiAgICAgIHZhciB4MCA9IDAsCiAgICAgICAgICB4MSA9IDEsCiAgICAgICAgICB0MCwKICAgICAgICAgIHQxLAogICAgICAgICAgazEwLAogICAgICAgICAgdHJhbnNmb3JtLAogICAgICAgICAgaW50ZXJwb2xhdG9yID0gaWRlbnRpdHkkNiwKICAgICAgICAgIGNsYW1wID0gZmFsc2UsCiAgICAgICAgICB1bmtub3duOwoKICAgICAgZnVuY3Rpb24gc2NhbGUoeCkgewogICAgICAgIHJldHVybiBpc05hTih4ID0gK3gpID8gdW5rbm93biA6IGludGVycG9sYXRvcihrMTAgPT09IDAgPyAwLjUgOiAoeCA9ICh0cmFuc2Zvcm0oeCkgLSB0MCkgKiBrMTAsIGNsYW1wID8gTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgeCkpIDogeCkpOwogICAgICB9CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodDAgPSB0cmFuc2Zvcm0oeDAgPSArX1swXSksIHQxID0gdHJhbnNmb3JtKHgxID0gK19bMV0pLCBrMTAgPSB0MCA9PT0gdDEgPyAwIDogMSAvICh0MSAtIHQwKSwgc2NhbGUpIDogW3gwLCB4MV07CiAgICAgIH07CgogICAgICBzY2FsZS5jbGFtcCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjbGFtcCA9ICEhXywgc2NhbGUpIDogY2xhbXA7CiAgICAgIH07CgogICAgICBzY2FsZS5pbnRlcnBvbGF0b3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaW50ZXJwb2xhdG9yID0gXywgc2NhbGUpIDogaW50ZXJwb2xhdG9yOwogICAgICB9OwoKICAgICAgc2NhbGUudW5rbm93biA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh1bmtub3duID0gXywgc2NhbGUpIDogdW5rbm93bjsKICAgICAgfTsKCiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdHJhbnNmb3JtID0gdCwgdDAgPSB0KHgwKSwgdDEgPSB0KHgxKSwgazEwID0gdDAgPT09IHQxID8gMCA6IDEgLyAodDEgLSB0MCk7CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvcHkkMShzb3VyY2UsIHRhcmdldCkgewogICAgICByZXR1cm4gdGFyZ2V0CiAgICAgICAgICAuZG9tYWluKHNvdXJjZS5kb21haW4oKSkKICAgICAgICAgIC5pbnRlcnBvbGF0b3Ioc291cmNlLmludGVycG9sYXRvcigpKQogICAgICAgICAgLmNsYW1wKHNvdXJjZS5jbGFtcCgpKQogICAgICAgICAgLnVua25vd24oc291cmNlLnVua25vd24oKSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VxdWVudGlhbCgpIHsKICAgICAgdmFyIHNjYWxlID0gbGluZWFyaXNoKHRyYW5zZm9ybWVyJDIoKShpZGVudGl0eSQ2KSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkkMShzY2FsZSwgc2VxdWVudGlhbCgpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0SW50ZXJwb2xhdG9yLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlcXVlbnRpYWxMb2coKSB7CiAgICAgIHZhciBzY2FsZSA9IGxvZ2dpc2godHJhbnNmb3JtZXIkMigpKS5kb21haW4oWzEsIDEwXSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkkMShzY2FsZSwgc2VxdWVudGlhbExvZygpKS5iYXNlKHNjYWxlLmJhc2UoKSk7CiAgICAgIH07CgogICAgICByZXR1cm4gaW5pdEludGVycG9sYXRvci5hcHBseShzY2FsZSwgYXJndW1lbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZXF1ZW50aWFsU3ltbG9nKCkgewogICAgICB2YXIgc2NhbGUgPSBzeW1sb2dpc2godHJhbnNmb3JtZXIkMigpKTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gY29weSQxKHNjYWxlLCBzZXF1ZW50aWFsU3ltbG9nKCkpLmNvbnN0YW50KHNjYWxlLmNvbnN0YW50KCkpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGluaXRJbnRlcnBvbGF0b3IuYXBwbHkoc2NhbGUsIGFyZ3VtZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VxdWVudGlhbFBvdygpIHsKICAgICAgdmFyIHNjYWxlID0gcG93aXNoKHRyYW5zZm9ybWVyJDIoKSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkkMShzY2FsZSwgc2VxdWVudGlhbFBvdygpKS5leHBvbmVudChzY2FsZS5leHBvbmVudCgpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0SW50ZXJwb2xhdG9yLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlcXVlbnRpYWxTcXJ0KCkgewogICAgICByZXR1cm4gc2VxdWVudGlhbFBvdy5hcHBseShudWxsLCBhcmd1bWVudHMpLmV4cG9uZW50KDAuNSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VxdWVudGlhbFF1YW50aWxlKCkgewogICAgICB2YXIgZG9tYWluID0gW10sCiAgICAgICAgICBpbnRlcnBvbGF0b3IgPSBpZGVudGl0eSQ2OwoKICAgICAgZnVuY3Rpb24gc2NhbGUoeCkgewogICAgICAgIGlmICghaXNOYU4oeCA9ICt4KSkgcmV0dXJuIGludGVycG9sYXRvcigoYmlzZWN0UmlnaHQoZG9tYWluLCB4KSAtIDEpIC8gKGRvbWFpbi5sZW5ndGggLSAxKSk7CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBkb21haW4uc2xpY2UoKTsKICAgICAgICBkb21haW4gPSBbXTsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IF8ubGVuZ3RoLCBkOyBpIDwgbjsgKytpKSBpZiAoZCA9IF9baV0sIGQgIT0gbnVsbCAmJiAhaXNOYU4oZCA9ICtkKSkgZG9tYWluLnB1c2goZCk7CiAgICAgICAgZG9tYWluLnNvcnQoYXNjZW5kaW5nKTsKICAgICAgICByZXR1cm4gc2NhbGU7CiAgICAgIH07CgogICAgICBzY2FsZS5pbnRlcnBvbGF0b3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaW50ZXJwb2xhdG9yID0gXywgc2NhbGUpIDogaW50ZXJwb2xhdG9yOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBzZXF1ZW50aWFsUXVhbnRpbGUoaW50ZXJwb2xhdG9yKS5kb21haW4oZG9tYWluKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0SW50ZXJwb2xhdG9yLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybWVyJDMoKSB7CiAgICAgIHZhciB4MCA9IDAsCiAgICAgICAgICB4MSA9IDAuNSwKICAgICAgICAgIHgyID0gMSwKICAgICAgICAgIHQwLAogICAgICAgICAgdDEsCiAgICAgICAgICB0MiwKICAgICAgICAgIGsxMCwKICAgICAgICAgIGsyMSwKICAgICAgICAgIGludGVycG9sYXRvciA9IGlkZW50aXR5JDYsCiAgICAgICAgICB0cmFuc2Zvcm0sCiAgICAgICAgICBjbGFtcCA9IGZhbHNlLAogICAgICAgICAgdW5rbm93bjsKCiAgICAgIGZ1bmN0aW9uIHNjYWxlKHgpIHsKICAgICAgICByZXR1cm4gaXNOYU4oeCA9ICt4KSA/IHVua25vd24gOiAoeCA9IDAuNSArICgoeCA9ICt0cmFuc2Zvcm0oeCkpIC0gdDEpICogKHggPCB0MSA/IGsxMCA6IGsyMSksIGludGVycG9sYXRvcihjbGFtcCA/IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIHgpKSA6IHgpKTsKICAgICAgfQoKICAgICAgc2NhbGUuZG9tYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHQwID0gdHJhbnNmb3JtKHgwID0gK19bMF0pLCB0MSA9IHRyYW5zZm9ybSh4MSA9ICtfWzFdKSwgdDIgPSB0cmFuc2Zvcm0oeDIgPSArX1syXSksIGsxMCA9IHQwID09PSB0MSA/IDAgOiAwLjUgLyAodDEgLSB0MCksIGsyMSA9IHQxID09PSB0MiA/IDAgOiAwLjUgLyAodDIgLSB0MSksIHNjYWxlKSA6IFt4MCwgeDEsIHgyXTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNsYW1wID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNsYW1wID0gISFfLCBzY2FsZSkgOiBjbGFtcDsKICAgICAgfTsKCiAgICAgIHNjYWxlLmludGVycG9sYXRvciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpbnRlcnBvbGF0b3IgPSBfLCBzY2FsZSkgOiBpbnRlcnBvbGF0b3I7CiAgICAgIH07CgogICAgICBzY2FsZS51bmtub3duID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHVua25vd24gPSBfLCBzY2FsZSkgOiB1bmtub3duOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB0cmFuc2Zvcm0gPSB0LCB0MCA9IHQoeDApLCB0MSA9IHQoeDEpLCB0MiA9IHQoeDIpLCBrMTAgPSB0MCA9PT0gdDEgPyAwIDogMC41IC8gKHQxIC0gdDApLCBrMjEgPSB0MSA9PT0gdDIgPyAwIDogMC41IC8gKHQyIC0gdDEpOwogICAgICAgIHJldHVybiBzY2FsZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXZlcmdpbmcoKSB7CiAgICAgIHZhciBzY2FsZSA9IGxpbmVhcmlzaCh0cmFuc2Zvcm1lciQzKCkoaWRlbnRpdHkkNikpOwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5JDEoc2NhbGUsIGRpdmVyZ2luZygpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0SW50ZXJwb2xhdG9yLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRpdmVyZ2luZ0xvZygpIHsKICAgICAgdmFyIHNjYWxlID0gbG9nZ2lzaCh0cmFuc2Zvcm1lciQzKCkpLmRvbWFpbihbMC4xLCAxLCAxMF0pOwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5JDEoc2NhbGUsIGRpdmVyZ2luZ0xvZygpKS5iYXNlKHNjYWxlLmJhc2UoKSk7CiAgICAgIH07CgogICAgICByZXR1cm4gaW5pdEludGVycG9sYXRvci5hcHBseShzY2FsZSwgYXJndW1lbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXZlcmdpbmdTeW1sb2coKSB7CiAgICAgIHZhciBzY2FsZSA9IHN5bWxvZ2lzaCh0cmFuc2Zvcm1lciQzKCkpOwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5JDEoc2NhbGUsIGRpdmVyZ2luZ1N5bWxvZygpKS5jb25zdGFudChzY2FsZS5jb25zdGFudCgpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBpbml0SW50ZXJwb2xhdG9yLmFwcGx5KHNjYWxlLCBhcmd1bWVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRpdmVyZ2luZ1BvdygpIHsKICAgICAgdmFyIHNjYWxlID0gcG93aXNoKHRyYW5zZm9ybWVyJDMoKSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkkMShzY2FsZSwgZGl2ZXJnaW5nUG93KCkpLmV4cG9uZW50KHNjYWxlLmV4cG9uZW50KCkpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGluaXRJbnRlcnBvbGF0b3IuYXBwbHkoc2NhbGUsIGFyZ3VtZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gZGl2ZXJnaW5nU3FydCgpIHsKICAgICAgcmV0dXJuIGRpdmVyZ2luZ1Bvdy5hcHBseShudWxsLCBhcmd1bWVudHMpLmV4cG9uZW50KDAuNSk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3JzKHNwZWNpZmllcikgewogICAgICB2YXIgbiA9IHNwZWNpZmllci5sZW5ndGggLyA2IHwgMCwgY29sb3JzID0gbmV3IEFycmF5KG4pLCBpID0gMDsKICAgICAgd2hpbGUgKGkgPCBuKSBjb2xvcnNbaV0gPSAiIyIgKyBzcGVjaWZpZXIuc2xpY2UoaSAqIDYsICsraSAqIDYpOwogICAgICByZXR1cm4gY29sb3JzOwogICAgfQoKICAgIHZhciBjYXRlZ29yeTEwID0gY29sb3JzKCIxZjc3YjRmZjdmMGUyY2EwMmNkNjI3Mjg5NDY3YmQ4YzU2NGJlMzc3YzI3ZjdmN2ZiY2JkMjIxN2JlY2YiKTsKCiAgICB2YXIgQWNjZW50ID0gY29sb3JzKCI3ZmM5N2ZiZWFlZDRmZGMwODZmZmZmOTkzODZjYjBmMDAyN2ZiZjViMTc2NjY2NjYiKTsKCiAgICB2YXIgRGFyazIgPSBjb2xvcnMoIjFiOWU3N2Q5NWYwMjc1NzBiM2U3Mjk4YTY2YTYxZWU2YWIwMmE2NzYxZDY2NjY2NiIpOwoKICAgIHZhciBQYWlyZWQgPSBjb2xvcnMoImE2Y2VlMzFmNzhiNGIyZGY4YTMzYTAyY2ZiOWE5OWUzMWExY2ZkYmY2ZmZmN2YwMGNhYjJkNjZhM2Q5YWZmZmY5OWIxNTkyOCIpOwoKICAgIHZhciBQYXN0ZWwxID0gY29sb3JzKCJmYmI0YWViM2NkZTNjY2ViYzVkZWNiZTRmZWQ5YTZmZmZmY2NlNWQ4YmRmZGRhZWNmMmYyZjIiKTsKCiAgICB2YXIgUGFzdGVsMiA9IGNvbG9ycygiYjNlMmNkZmRjZGFjY2JkNWU4ZjRjYWU0ZTZmNWM5ZmZmMmFlZjFlMmNjY2NjY2NjIik7CgogICAgdmFyIFNldDEgPSBjb2xvcnMoImU0MWExYzM3N2ViODRkYWY0YTk4NGVhM2ZmN2YwMGZmZmYzM2E2NTYyOGY3ODFiZjk5OTk5OSIpOwoKICAgIHZhciBTZXQyID0gY29sb3JzKCI2NmMyYTVmYzhkNjI4ZGEwY2JlNzhhYzNhNmQ4NTRmZmQ5MmZlNWM0OTRiM2IzYjMiKTsKCiAgICB2YXIgU2V0MyA9IGNvbG9ycygiOGRkM2M3ZmZmZmIzYmViYWRhZmI4MDcyODBiMWQzZmRiNDYyYjNkZTY5ZmNjZGU1ZDlkOWQ5YmM4MGJkY2NlYmM1ZmZlZDZmIik7CgogICAgdmFyIFRhYmxlYXUxMCA9IGNvbG9ycygiNGU3OWE3ZjI4ZTJjZTE1NzU5NzZiN2IyNTlhMTRmZWRjOTQ5YWY3YWExZmY5ZGE3OWM3NTVmYmFiMGFiIik7CgogICAgZnVuY3Rpb24gcmFtcChzY2hlbWUpIHsKICAgICAgcmV0dXJuIHJnYkJhc2lzKHNjaGVtZVtzY2hlbWUubGVuZ3RoIC0gMV0pOwogICAgfQoKICAgIHZhciBzY2hlbWUgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZDhiMzY1ZjVmNWY1NWFiNGFjIiwKICAgICAgImE2NjExYWRmYzI3ZDgwY2RjMTAxODU3MSIsCiAgICAgICJhNjYxMWFkZmMyN2RmNWY1ZjU4MGNkYzEwMTg1NzEiLAogICAgICAiOGM1MTBhZDhiMzY1ZjZlOGMzYzdlYWU1NWFiNGFjMDE2NjVlIiwKICAgICAgIjhjNTEwYWQ4YjM2NWY2ZThjM2Y1ZjVmNWM3ZWFlNTVhYjRhYzAxNjY1ZSIsCiAgICAgICI4YzUxMGFiZjgxMmRkZmMyN2RmNmU4YzNjN2VhZTU4MGNkYzEzNTk3OGYwMTY2NWUiLAogICAgICAiOGM1MTBhYmY4MTJkZGZjMjdkZjZlOGMzZjVmNWY1YzdlYWU1ODBjZGMxMzU5NzhmMDE2NjVlIiwKICAgICAgIjU0MzAwNThjNTEwYWJmODEyZGRmYzI3ZGY2ZThjM2M3ZWFlNTgwY2RjMTM1OTc4ZjAxNjY1ZTAwM2MzMCIsCiAgICAgICI1NDMwMDU4YzUxMGFiZjgxMmRkZmMyN2RmNmU4YzNmNWY1ZjVjN2VhZTU4MGNkYzEzNTk3OGYwMTY2NWUwMDNjMzAiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBCckJHID0gcmFtcChzY2hlbWUpOwoKICAgIHZhciBzY2hlbWUkMSA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJhZjhkYzNmN2Y3Zjc3ZmJmN2IiLAogICAgICAiN2IzMjk0YzJhNWNmYTZkYmEwMDA4ODM3IiwKICAgICAgIjdiMzI5NGMyYTVjZmY3ZjdmN2E2ZGJhMDAwODgzNyIsCiAgICAgICI3NjJhODNhZjhkYzNlN2Q0ZThkOWYwZDM3ZmJmN2IxYjc4MzciLAogICAgICAiNzYyYTgzYWY4ZGMzZTdkNGU4ZjdmN2Y3ZDlmMGQzN2ZiZjdiMWI3ODM3IiwKICAgICAgIjc2MmE4Mzk5NzBhYmMyYTVjZmU3ZDRlOGQ5ZjBkM2E2ZGJhMDVhYWU2MTFiNzgzNyIsCiAgICAgICI3NjJhODM5OTcwYWJjMmE1Y2ZlN2Q0ZThmN2Y3ZjdkOWYwZDNhNmRiYTA1YWFlNjExYjc4MzciLAogICAgICAiNDAwMDRiNzYyYTgzOTk3MGFiYzJhNWNmZTdkNGU4ZDlmMGQzYTZkYmEwNWFhZTYxMWI3ODM3MDA0NDFiIiwKICAgICAgIjQwMDA0Yjc2MmE4Mzk5NzBhYmMyYTVjZmU3ZDRlOGY3ZjdmN2Q5ZjBkM2E2ZGJhMDVhYWU2MTFiNzgzNzAwNDQxYiIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIFBSR24gPSByYW1wKHNjaGVtZSQxKTsKCiAgICB2YXIgc2NoZW1lJDIgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZTlhM2M5ZjdmN2Y3YTFkNzZhIiwKICAgICAgImQwMWM4YmYxYjZkYWI4ZTE4NjRkYWMyNiIsCiAgICAgICJkMDFjOGJmMWI2ZGFmN2Y3ZjdiOGUxODY0ZGFjMjYiLAogICAgICAiYzUxYjdkZTlhM2M5ZmRlMGVmZTZmNWQwYTFkNzZhNGQ5MjIxIiwKICAgICAgImM1MWI3ZGU5YTNjOWZkZTBlZmY3ZjdmN2U2ZjVkMGExZDc2YTRkOTIyMSIsCiAgICAgICJjNTFiN2RkZTc3YWVmMWI2ZGFmZGUwZWZlNmY1ZDBiOGUxODY3ZmJjNDE0ZDkyMjEiLAogICAgICAiYzUxYjdkZGU3N2FlZjFiNmRhZmRlMGVmZjdmN2Y3ZTZmNWQwYjhlMTg2N2ZiYzQxNGQ5MjIxIiwKICAgICAgIjhlMDE1MmM1MWI3ZGRlNzdhZWYxYjZkYWZkZTBlZmU2ZjVkMGI4ZTE4NjdmYmM0MTRkOTIyMTI3NjQxOSIsCiAgICAgICI4ZTAxNTJjNTFiN2RkZTc3YWVmMWI2ZGFmZGUwZWZmN2Y3ZjdlNmY1ZDBiOGUxODY3ZmJjNDE0ZDkyMjEyNzY0MTkiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBQaVlHID0gcmFtcChzY2hlbWUkMik7CgogICAgdmFyIHNjaGVtZSQzID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgIjk5OGVjM2Y3ZjdmN2YxYTM0MCIsCiAgICAgICI1ZTNjOTliMmFiZDJmZGI4NjNlNjYxMDEiLAogICAgICAiNWUzYzk5YjJhYmQyZjdmN2Y3ZmRiODYzZTY2MTAxIiwKICAgICAgIjU0Mjc4ODk5OGVjM2Q4ZGFlYmZlZTBiNmYxYTM0MGIzNTgwNiIsCiAgICAgICI1NDI3ODg5OThlYzNkOGRhZWJmN2Y3ZjdmZWUwYjZmMWEzNDBiMzU4MDYiLAogICAgICAiNTQyNzg4ODA3M2FjYjJhYmQyZDhkYWViZmVlMGI2ZmRiODYzZTA4MjE0YjM1ODA2IiwKICAgICAgIjU0Mjc4ODgwNzNhY2IyYWJkMmQ4ZGFlYmY3ZjdmN2ZlZTBiNmZkYjg2M2UwODIxNGIzNTgwNiIsCiAgICAgICIyZDAwNGI1NDI3ODg4MDczYWNiMmFiZDJkOGRhZWJmZWUwYjZmZGI4NjNlMDgyMTRiMzU4MDY3ZjNiMDgiLAogICAgICAiMmQwMDRiNTQyNzg4ODA3M2FjYjJhYmQyZDhkYWViZjdmN2Y3ZmVlMGI2ZmRiODYzZTA4MjE0YjM1ODA2N2YzYjA4IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgUHVPciA9IHJhbXAoc2NoZW1lJDMpOwoKICAgIHZhciBzY2hlbWUkNCA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJlZjhhNjJmN2Y3Zjc2N2E5Y2YiLAogICAgICAiY2EwMDIwZjRhNTgyOTJjNWRlMDU3MWIwIiwKICAgICAgImNhMDAyMGY0YTU4MmY3ZjdmNzkyYzVkZTA1NzFiMCIsCiAgICAgICJiMjE4MmJlZjhhNjJmZGRiYzdkMWU1ZjA2N2E5Y2YyMTY2YWMiLAogICAgICAiYjIxODJiZWY4YTYyZmRkYmM3ZjdmN2Y3ZDFlNWYwNjdhOWNmMjE2NmFjIiwKICAgICAgImIyMTgyYmQ2NjA0ZGY0YTU4MmZkZGJjN2QxZTVmMDkyYzVkZTQzOTNjMzIxNjZhYyIsCiAgICAgICJiMjE4MmJkNjYwNGRmNGE1ODJmZGRiYzdmN2Y3ZjdkMWU1ZjA5MmM1ZGU0MzkzYzMyMTY2YWMiLAogICAgICAiNjcwMDFmYjIxODJiZDY2MDRkZjRhNTgyZmRkYmM3ZDFlNWYwOTJjNWRlNDM5M2MzMjE2NmFjMDUzMDYxIiwKICAgICAgIjY3MDAxZmIyMTgyYmQ2NjA0ZGY0YTU4MmZkZGJjN2Y3ZjdmN2QxZTVmMDkyYzVkZTQzOTNjMzIxNjZhYzA1MzA2MSIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIFJkQnUgPSByYW1wKHNjaGVtZSQ0KTsKCiAgICB2YXIgc2NoZW1lJDUgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZWY4YTYyZmZmZmZmOTk5OTk5IiwKICAgICAgImNhMDAyMGY0YTU4MmJhYmFiYTQwNDA0MCIsCiAgICAgICJjYTAwMjBmNGE1ODJmZmZmZmZiYWJhYmE0MDQwNDAiLAogICAgICAiYjIxODJiZWY4YTYyZmRkYmM3ZTBlMGUwOTk5OTk5NGQ0ZDRkIiwKICAgICAgImIyMTgyYmVmOGE2MmZkZGJjN2ZmZmZmZmUwZTBlMDk5OTk5OTRkNGQ0ZCIsCiAgICAgICJiMjE4MmJkNjYwNGRmNGE1ODJmZGRiYzdlMGUwZTBiYWJhYmE4Nzg3ODc0ZDRkNGQiLAogICAgICAiYjIxODJiZDY2MDRkZjRhNTgyZmRkYmM3ZmZmZmZmZTBlMGUwYmFiYWJhODc4Nzg3NGQ0ZDRkIiwKICAgICAgIjY3MDAxZmIyMTgyYmQ2NjA0ZGY0YTU4MmZkZGJjN2UwZTBlMGJhYmFiYTg3ODc4NzRkNGQ0ZDFhMWExYSIsCiAgICAgICI2NzAwMWZiMjE4MmJkNjYwNGRmNGE1ODJmZGRiYzdmZmZmZmZlMGUwZTBiYWJhYmE4Nzg3ODc0ZDRkNGQxYTFhMWEiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBSZEd5ID0gcmFtcChzY2hlbWUkNSk7CgogICAgdmFyIHNjaGVtZSQ2ID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZjOGQ1OWZmZmZiZjkxYmZkYiIsCiAgICAgICJkNzE5MWNmZGFlNjFhYmQ5ZTkyYzdiYjYiLAogICAgICAiZDcxOTFjZmRhZTYxZmZmZmJmYWJkOWU5MmM3YmI2IiwKICAgICAgImQ3MzAyN2ZjOGQ1OWZlZTA5MGUwZjNmODkxYmZkYjQ1NzViNCIsCiAgICAgICJkNzMwMjdmYzhkNTlmZWUwOTBmZmZmYmZlMGYzZjg5MWJmZGI0NTc1YjQiLAogICAgICAiZDczMDI3ZjQ2ZDQzZmRhZTYxZmVlMDkwZTBmM2Y4YWJkOWU5NzRhZGQxNDU3NWI0IiwKICAgICAgImQ3MzAyN2Y0NmQ0M2ZkYWU2MWZlZTA5MGZmZmZiZmUwZjNmOGFiZDllOTc0YWRkMTQ1NzViNCIsCiAgICAgICJhNTAwMjZkNzMwMjdmNDZkNDNmZGFlNjFmZWUwOTBlMGYzZjhhYmQ5ZTk3NGFkZDE0NTc1YjQzMTM2OTUiLAogICAgICAiYTUwMDI2ZDczMDI3ZjQ2ZDQzZmRhZTYxZmVlMDkwZmZmZmJmZTBmM2Y4YWJkOWU5NzRhZGQxNDU3NWI0MzEzNjk1IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgUmRZbEJ1ID0gcmFtcChzY2hlbWUkNik7CgogICAgdmFyIHNjaGVtZSQ3ID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZjOGQ1OWZmZmZiZjkxY2Y2MCIsCiAgICAgICJkNzE5MWNmZGFlNjFhNmQ5NmExYTk2NDEiLAogICAgICAiZDcxOTFjZmRhZTYxZmZmZmJmYTZkOTZhMWE5NjQxIiwKICAgICAgImQ3MzAyN2ZjOGQ1OWZlZTA4YmQ5ZWY4YjkxY2Y2MDFhOTg1MCIsCiAgICAgICJkNzMwMjdmYzhkNTlmZWUwOGJmZmZmYmZkOWVmOGI5MWNmNjAxYTk4NTAiLAogICAgICAiZDczMDI3ZjQ2ZDQzZmRhZTYxZmVlMDhiZDllZjhiYTZkOTZhNjZiZDYzMWE5ODUwIiwKICAgICAgImQ3MzAyN2Y0NmQ0M2ZkYWU2MWZlZTA4YmZmZmZiZmQ5ZWY4YmE2ZDk2YTY2YmQ2MzFhOTg1MCIsCiAgICAgICJhNTAwMjZkNzMwMjdmNDZkNDNmZGFlNjFmZWUwOGJkOWVmOGJhNmQ5NmE2NmJkNjMxYTk4NTAwMDY4MzciLAogICAgICAiYTUwMDI2ZDczMDI3ZjQ2ZDQzZmRhZTYxZmVlMDhiZmZmZmJmZDllZjhiYTZkOTZhNjZiZDYzMWE5ODUwMDA2ODM3IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgUmRZbEduID0gcmFtcChzY2hlbWUkNyk7CgogICAgdmFyIHNjaGVtZSQ4ID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZjOGQ1OWZmZmZiZjk5ZDU5NCIsCiAgICAgICJkNzE5MWNmZGFlNjFhYmRkYTQyYjgzYmEiLAogICAgICAiZDcxOTFjZmRhZTYxZmZmZmJmYWJkZGE0MmI4M2JhIiwKICAgICAgImQ1M2U0ZmZjOGQ1OWZlZTA4YmU2ZjU5ODk5ZDU5NDMyODhiZCIsCiAgICAgICJkNTNlNGZmYzhkNTlmZWUwOGJmZmZmYmZlNmY1OTg5OWQ1OTQzMjg4YmQiLAogICAgICAiZDUzZTRmZjQ2ZDQzZmRhZTYxZmVlMDhiZTZmNTk4YWJkZGE0NjZjMmE1MzI4OGJkIiwKICAgICAgImQ1M2U0ZmY0NmQ0M2ZkYWU2MWZlZTA4YmZmZmZiZmU2ZjU5OGFiZGRhNDY2YzJhNTMyODhiZCIsCiAgICAgICI5ZTAxNDJkNTNlNGZmNDZkNDNmZGFlNjFmZWUwOGJlNmY1OThhYmRkYTQ2NmMyYTUzMjg4YmQ1ZTRmYTIiLAogICAgICAiOWUwMTQyZDUzZTRmZjQ2ZDQzZmRhZTYxZmVlMDhiZmZmZmJmZTZmNTk4YWJkZGE0NjZjMmE1MzI4OGJkNWU0ZmEyIgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgU3BlY3RyYWwgPSByYW1wKHNjaGVtZSQ4KTsKCiAgICB2YXIgc2NoZW1lJDkgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZTVmNWY5OTlkOGM5MmNhMjVmIiwKICAgICAgImVkZjhmYmIyZTJlMjY2YzJhNDIzOGI0NSIsCiAgICAgICJlZGY4ZmJiMmUyZTI2NmMyYTQyY2EyNWYwMDZkMmMiLAogICAgICAiZWRmOGZiY2NlY2U2OTlkOGM5NjZjMmE0MmNhMjVmMDA2ZDJjIiwKICAgICAgImVkZjhmYmNjZWNlNjk5ZDhjOTY2YzJhNDQxYWU3NjIzOGI0NTAwNTgyNCIsCiAgICAgICJmN2ZjZmRlNWY1ZjljY2VjZTY5OWQ4Yzk2NmMyYTQ0MWFlNzYyMzhiNDUwMDU4MjQiLAogICAgICAiZjdmY2ZkZTVmNWY5Y2NlY2U2OTlkOGM5NjZjMmE0NDFhZTc2MjM4YjQ1MDA2ZDJjMDA0NDFiIgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgQnVHbiA9IHJhbXAoc2NoZW1lJDkpOwoKICAgIHZhciBzY2hlbWUkYSA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJlMGVjZjQ5ZWJjZGE4ODU2YTciLAogICAgICAiZWRmOGZiYjNjZGUzOGM5NmM2ODg0MTlkIiwKICAgICAgImVkZjhmYmIzY2RlMzhjOTZjNjg4NTZhNzgxMGY3YyIsCiAgICAgICJlZGY4ZmJiZmQzZTY5ZWJjZGE4Yzk2YzY4ODU2YTc4MTBmN2MiLAogICAgICAiZWRmOGZiYmZkM2U2OWViY2RhOGM5NmM2OGM2YmIxODg0MTlkNmUwMTZiIiwKICAgICAgImY3ZmNmZGUwZWNmNGJmZDNlNjllYmNkYThjOTZjNjhjNmJiMTg4NDE5ZDZlMDE2YiIsCiAgICAgICJmN2ZjZmRlMGVjZjRiZmQzZTY5ZWJjZGE4Yzk2YzY4YzZiYjE4ODQxOWQ4MTBmN2M0ZDAwNGIiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBCdVB1ID0gcmFtcChzY2hlbWUkYSk7CgogICAgdmFyIHNjaGVtZSRiID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImUwZjNkYmE4ZGRiNTQzYTJjYSIsCiAgICAgICJmMGY5ZThiYWU0YmM3YmNjYzQyYjhjYmUiLAogICAgICAiZjBmOWU4YmFlNGJjN2JjY2M0NDNhMmNhMDg2OGFjIiwKICAgICAgImYwZjllOGNjZWJjNWE4ZGRiNTdiY2NjNDQzYTJjYTA4NjhhYyIsCiAgICAgICJmMGY5ZThjY2ViYzVhOGRkYjU3YmNjYzQ0ZWIzZDMyYjhjYmUwODU4OWUiLAogICAgICAiZjdmY2YwZTBmM2RiY2NlYmM1YThkZGI1N2JjY2M0NGViM2QzMmI4Y2JlMDg1ODllIiwKICAgICAgImY3ZmNmMGUwZjNkYmNjZWJjNWE4ZGRiNTdiY2NjNDRlYjNkMzJiOGNiZTA4NjhhYzA4NDA4MSIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIEduQnUgPSByYW1wKHNjaGVtZSRiKTsKCiAgICB2YXIgc2NoZW1lJGMgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZmVlOGM4ZmRiYjg0ZTM0YTMzIiwKICAgICAgImZlZjBkOWZkY2M4YWZjOGQ1OWQ3MzAxZiIsCiAgICAgICJmZWYwZDlmZGNjOGFmYzhkNTllMzRhMzNiMzAwMDAiLAogICAgICAiZmVmMGQ5ZmRkNDllZmRiYjg0ZmM4ZDU5ZTM0YTMzYjMwMDAwIiwKICAgICAgImZlZjBkOWZkZDQ5ZWZkYmI4NGZjOGQ1OWVmNjU0OGQ3MzAxZjk5MDAwMCIsCiAgICAgICJmZmY3ZWNmZWU4YzhmZGQ0OWVmZGJiODRmYzhkNTllZjY1NDhkNzMwMWY5OTAwMDAiLAogICAgICAiZmZmN2VjZmVlOGM4ZmRkNDllZmRiYjg0ZmM4ZDU5ZWY2NTQ4ZDczMDFmYjMwMDAwN2YwMDAwIgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgT3JSZCA9IHJhbXAoc2NoZW1lJGMpOwoKICAgIHZhciBzY2hlbWUkZCA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJlY2UyZjBhNmJkZGIxYzkwOTkiLAogICAgICAiZjZlZmY3YmRjOWUxNjdhOWNmMDI4MThhIiwKICAgICAgImY2ZWZmN2JkYzllMTY3YTljZjFjOTA5OTAxNmM1OSIsCiAgICAgICJmNmVmZjdkMGQxZTZhNmJkZGI2N2E5Y2YxYzkwOTkwMTZjNTkiLAogICAgICAiZjZlZmY3ZDBkMWU2YTZiZGRiNjdhOWNmMzY5MGMwMDI4MThhMDE2NDUwIiwKICAgICAgImZmZjdmYmVjZTJmMGQwZDFlNmE2YmRkYjY3YTljZjM2OTBjMDAyODE4YTAxNjQ1MCIsCiAgICAgICJmZmY3ZmJlY2UyZjBkMGQxZTZhNmJkZGI2N2E5Y2YzNjkwYzAwMjgxOGEwMTZjNTkwMTQ2MzYiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBQdUJ1R24gPSByYW1wKHNjaGVtZSRkKTsKCiAgICB2YXIgc2NoZW1lJGUgPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZWNlN2YyYTZiZGRiMmI4Y2JlIiwKICAgICAgImYxZWVmNmJkYzllMTc0YTljZjA1NzBiMCIsCiAgICAgICJmMWVlZjZiZGM5ZTE3NGE5Y2YyYjhjYmUwNDVhOGQiLAogICAgICAiZjFlZWY2ZDBkMWU2YTZiZGRiNzRhOWNmMmI4Y2JlMDQ1YThkIiwKICAgICAgImYxZWVmNmQwZDFlNmE2YmRkYjc0YTljZjM2OTBjMDA1NzBiMDAzNGU3YiIsCiAgICAgICJmZmY3ZmJlY2U3ZjJkMGQxZTZhNmJkZGI3NGE5Y2YzNjkwYzAwNTcwYjAwMzRlN2IiLAogICAgICAiZmZmN2ZiZWNlN2YyZDBkMWU2YTZiZGRiNzRhOWNmMzY5MGMwMDU3MGIwMDQ1YThkMDIzODU4IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgUHVCdSA9IHJhbXAoc2NoZW1lJGUpOwoKICAgIHZhciBzY2hlbWUkZiA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJlN2UxZWZjOTk0YzdkZDFjNzciLAogICAgICAiZjFlZWY2ZDdiNWQ4ZGY2NWIwY2UxMjU2IiwKICAgICAgImYxZWVmNmQ3YjVkOGRmNjViMGRkMWM3Nzk4MDA0MyIsCiAgICAgICJmMWVlZjZkNGI5ZGFjOTk0YzdkZjY1YjBkZDFjNzc5ODAwNDMiLAogICAgICAiZjFlZWY2ZDRiOWRhYzk5NGM3ZGY2NWIwZTcyOThhY2UxMjU2OTEwMDNmIiwKICAgICAgImY3ZjRmOWU3ZTFlZmQ0YjlkYWM5OTRjN2RmNjViMGU3Mjk4YWNlMTI1NjkxMDAzZiIsCiAgICAgICJmN2Y0ZjllN2UxZWZkNGI5ZGFjOTk0YzdkZjY1YjBlNzI5OGFjZTEyNTY5ODAwNDM2NzAwMWYiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBQdVJkID0gcmFtcChzY2hlbWUkZik7CgogICAgdmFyIHNjaGVtZSRnID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZkZTBkZGZhOWZiNWM1MWI4YSIsCiAgICAgICJmZWViZTJmYmI0YjlmNzY4YTFhZTAxN2UiLAogICAgICAiZmVlYmUyZmJiNGI5Zjc2OGExYzUxYjhhN2EwMTc3IiwKICAgICAgImZlZWJlMmZjYzVjMGZhOWZiNWY3NjhhMWM1MWI4YTdhMDE3NyIsCiAgICAgICJmZWViZTJmY2M1YzBmYTlmYjVmNzY4YTFkZDM0OTdhZTAxN2U3YTAxNzciLAogICAgICAiZmZmN2YzZmRlMGRkZmNjNWMwZmE5ZmI1Zjc2OGExZGQzNDk3YWUwMTdlN2EwMTc3IiwKICAgICAgImZmZjdmM2ZkZTBkZGZjYzVjMGZhOWZiNWY3NjhhMWRkMzQ5N2FlMDE3ZTdhMDE3NzQ5MDA2YSIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIFJkUHUgPSByYW1wKHNjaGVtZSRnKTsKCiAgICB2YXIgc2NoZW1lJGggPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZWRmOGIxN2ZjZGJiMmM3ZmI4IiwKICAgICAgImZmZmZjY2ExZGFiNDQxYjZjNDIyNWVhOCIsCiAgICAgICJmZmZmY2NhMWRhYjQ0MWI2YzQyYzdmYjgyNTM0OTQiLAogICAgICAiZmZmZmNjYzdlOWI0N2ZjZGJiNDFiNmM0MmM3ZmI4MjUzNDk0IiwKICAgICAgImZmZmZjY2M3ZTliNDdmY2RiYjQxYjZjNDFkOTFjMDIyNWVhODBjMmM4NCIsCiAgICAgICJmZmZmZDllZGY4YjFjN2U5YjQ3ZmNkYmI0MWI2YzQxZDkxYzAyMjVlYTgwYzJjODQiLAogICAgICAiZmZmZmQ5ZWRmOGIxYzdlOWI0N2ZjZGJiNDFiNmM0MWQ5MWMwMjI1ZWE4MjUzNDk0MDgxZDU4IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgWWxHbkJ1ID0gcmFtcChzY2hlbWUkaCk7CgogICAgdmFyIHNjaGVtZSRpID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImY3ZmNiOWFkZGQ4ZTMxYTM1NCIsCiAgICAgICJmZmZmY2NjMmU2OTk3OGM2NzkyMzg0NDMiLAogICAgICAiZmZmZmNjYzJlNjk5NzhjNjc5MzFhMzU0MDA2ODM3IiwKICAgICAgImZmZmZjY2Q5ZjBhM2FkZGQ4ZTc4YzY3OTMxYTM1NDAwNjgzNyIsCiAgICAgICJmZmZmY2NkOWYwYTNhZGRkOGU3OGM2Nzk0MWFiNWQyMzg0NDMwMDVhMzIiLAogICAgICAiZmZmZmU1ZjdmY2I5ZDlmMGEzYWRkZDhlNzhjNjc5NDFhYjVkMjM4NDQzMDA1YTMyIiwKICAgICAgImZmZmZlNWY3ZmNiOWQ5ZjBhM2FkZGQ4ZTc4YzY3OTQxYWI1ZDIzODQ0MzAwNjgzNzAwNDUyOSIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIFlsR24gPSByYW1wKHNjaGVtZSRpKTsKCiAgICB2YXIgc2NoZW1lJGogPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZmZmN2JjZmVjNDRmZDk1ZjBlIiwKICAgICAgImZmZmZkNGZlZDk4ZWZlOTkyOWNjNGMwMiIsCiAgICAgICJmZmZmZDRmZWQ5OGVmZTk5MjlkOTVmMGU5OTM0MDQiLAogICAgICAiZmZmZmQ0ZmVlMzkxZmVjNDRmZmU5OTI5ZDk1ZjBlOTkzNDA0IiwKICAgICAgImZmZmZkNGZlZTM5MWZlYzQ0ZmZlOTkyOWVjNzAxNGNjNGMwMjhjMmQwNCIsCiAgICAgICJmZmZmZTVmZmY3YmNmZWUzOTFmZWM0NGZmZTk5MjllYzcwMTRjYzRjMDI4YzJkMDQiLAogICAgICAiZmZmZmU1ZmZmN2JjZmVlMzkxZmVjNDRmZmU5OTI5ZWM3MDE0Y2M0YzAyOTkzNDA0NjYyNTA2IgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgWWxPckJyID0gcmFtcChzY2hlbWUkaik7CgogICAgdmFyIHNjaGVtZSRrID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZmZWRhMGZlYjI0Y2YwM2IyMCIsCiAgICAgICJmZmZmYjJmZWNjNWNmZDhkM2NlMzFhMWMiLAogICAgICAiZmZmZmIyZmVjYzVjZmQ4ZDNjZjAzYjIwYmQwMDI2IiwKICAgICAgImZmZmZiMmZlZDk3NmZlYjI0Y2ZkOGQzY2YwM2IyMGJkMDAyNiIsCiAgICAgICJmZmZmYjJmZWQ5NzZmZWIyNGNmZDhkM2NmYzRlMmFlMzFhMWNiMTAwMjYiLAogICAgICAiZmZmZmNjZmZlZGEwZmVkOTc2ZmViMjRjZmQ4ZDNjZmM0ZTJhZTMxYTFjYjEwMDI2IiwKICAgICAgImZmZmZjY2ZmZWRhMGZlZDk3NmZlYjI0Y2ZkOGQzY2ZjNGUyYWUzMWExY2JkMDAyNjgwMDAyNiIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIFlsT3JSZCA9IHJhbXAoc2NoZW1lJGspOwoKICAgIHZhciBzY2hlbWUkbCA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJkZWViZjc5ZWNhZTEzMTgyYmQiLAogICAgICAiZWZmM2ZmYmRkN2U3NmJhZWQ2MjE3MWI1IiwKICAgICAgImVmZjNmZmJkZDdlNzZiYWVkNjMxODJiZDA4NTE5YyIsCiAgICAgICJlZmYzZmZjNmRiZWY5ZWNhZTE2YmFlZDYzMTgyYmQwODUxOWMiLAogICAgICAiZWZmM2ZmYzZkYmVmOWVjYWUxNmJhZWQ2NDI5MmM2MjE3MWI1MDg0NTk0IiwKICAgICAgImY3ZmJmZmRlZWJmN2M2ZGJlZjllY2FlMTZiYWVkNjQyOTJjNjIxNzFiNTA4NDU5NCIsCiAgICAgICJmN2ZiZmZkZWViZjdjNmRiZWY5ZWNhZTE2YmFlZDY0MjkyYzYyMTcxYjUwODUxOWMwODMwNmIiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBCbHVlcyA9IHJhbXAoc2NoZW1lJGwpOwoKICAgIHZhciBzY2hlbWUkbSA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJlNWY1ZTBhMWQ5OWIzMWEzNTQiLAogICAgICAiZWRmOGU5YmFlNGIzNzRjNDc2MjM4YjQ1IiwKICAgICAgImVkZjhlOWJhZTRiMzc0YzQ3NjMxYTM1NDAwNmQyYyIsCiAgICAgICJlZGY4ZTljN2U5YzBhMWQ5OWI3NGM0NzYzMWEzNTQwMDZkMmMiLAogICAgICAiZWRmOGU5YzdlOWMwYTFkOTliNzRjNDc2NDFhYjVkMjM4YjQ1MDA1YTMyIiwKICAgICAgImY3ZmNmNWU1ZjVlMGM3ZTljMGExZDk5Yjc0YzQ3NjQxYWI1ZDIzOGI0NTAwNWEzMiIsCiAgICAgICJmN2ZjZjVlNWY1ZTBjN2U5YzBhMWQ5OWI3NGM0NzY0MWFiNWQyMzhiNDUwMDZkMmMwMDQ0MWIiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBHcmVlbnMgPSByYW1wKHNjaGVtZSRtKTsKCiAgICB2YXIgc2NoZW1lJG4gPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZjBmMGYwYmRiZGJkNjM2MzYzIiwKICAgICAgImY3ZjdmN2NjY2NjYzk2OTY5NjUyNTI1MiIsCiAgICAgICJmN2Y3ZjdjY2NjY2M5Njk2OTY2MzYzNjMyNTI1MjUiLAogICAgICAiZjdmN2Y3ZDlkOWQ5YmRiZGJkOTY5Njk2NjM2MzYzMjUyNTI1IiwKICAgICAgImY3ZjdmN2Q5ZDlkOWJkYmRiZDk2OTY5NjczNzM3MzUyNTI1MjI1MjUyNSIsCiAgICAgICJmZmZmZmZmMGYwZjBkOWQ5ZDliZGJkYmQ5Njk2OTY3MzczNzM1MjUyNTIyNTI1MjUiLAogICAgICAiZmZmZmZmZjBmMGYwZDlkOWQ5YmRiZGJkOTY5Njk2NzM3MzczNTI1MjUyMjUyNTI1MDAwMDAwIgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgR3JleXMgPSByYW1wKHNjaGVtZSRuKTsKCiAgICB2YXIgc2NoZW1lJG8gPSBuZXcgQXJyYXkoMykuY29uY2F0KAogICAgICAiZWZlZGY1YmNiZGRjNzU2YmIxIiwKICAgICAgImYyZjBmN2NiYzllMjllOWFjODZhNTFhMyIsCiAgICAgICJmMmYwZjdjYmM5ZTI5ZTlhYzg3NTZiYjE1NDI3OGYiLAogICAgICAiZjJmMGY3ZGFkYWViYmNiZGRjOWU5YWM4NzU2YmIxNTQyNzhmIiwKICAgICAgImYyZjBmN2RhZGFlYmJjYmRkYzllOWFjODgwN2RiYTZhNTFhMzRhMTQ4NiIsCiAgICAgICJmY2ZiZmRlZmVkZjVkYWRhZWJiY2JkZGM5ZTlhYzg4MDdkYmE2YTUxYTM0YTE0ODYiLAogICAgICAiZmNmYmZkZWZlZGY1ZGFkYWViYmNiZGRjOWU5YWM4ODA3ZGJhNmE1MWEzNTQyNzhmM2YwMDdkIgogICAgKS5tYXAoY29sb3JzKTsKCiAgICB2YXIgUHVycGxlcyA9IHJhbXAoc2NoZW1lJG8pOwoKICAgIHZhciBzY2hlbWUkcCA9IG5ldyBBcnJheSgzKS5jb25jYXQoCiAgICAgICJmZWUwZDJmYzkyNzJkZTJkMjYiLAogICAgICAiZmVlNWQ5ZmNhZTkxZmI2YTRhY2IxODFkIiwKICAgICAgImZlZTVkOWZjYWU5MWZiNmE0YWRlMmQyNmE1MGYxNSIsCiAgICAgICJmZWU1ZDlmY2JiYTFmYzkyNzJmYjZhNGFkZTJkMjZhNTBmMTUiLAogICAgICAiZmVlNWQ5ZmNiYmExZmM5MjcyZmI2YTRhZWYzYjJjY2IxODFkOTkwMDBkIiwKICAgICAgImZmZjVmMGZlZTBkMmZjYmJhMWZjOTI3MmZiNmE0YWVmM2IyY2NiMTgxZDk5MDAwZCIsCiAgICAgICJmZmY1ZjBmZWUwZDJmY2JiYTFmYzkyNzJmYjZhNGFlZjNiMmNjYjE4MWRhNTBmMTU2NzAwMGQiCiAgICApLm1hcChjb2xvcnMpOwoKICAgIHZhciBSZWRzID0gcmFtcChzY2hlbWUkcCk7CgogICAgdmFyIHNjaGVtZSRxID0gbmV3IEFycmF5KDMpLmNvbmNhdCgKICAgICAgImZlZTZjZWZkYWU2YmU2NTUwZCIsCiAgICAgICJmZWVkZGVmZGJlODVmZDhkM2NkOTQ3MDEiLAogICAgICAiZmVlZGRlZmRiZTg1ZmQ4ZDNjZTY1NTBkYTYzNjAzIiwKICAgICAgImZlZWRkZWZkZDBhMmZkYWU2YmZkOGQzY2U2NTUwZGE2MzYwMyIsCiAgICAgICJmZWVkZGVmZGQwYTJmZGFlNmJmZDhkM2NmMTY5MTNkOTQ4MDE4YzJkMDQiLAogICAgICAiZmZmNWViZmVlNmNlZmRkMGEyZmRhZTZiZmQ4ZDNjZjE2OTEzZDk0ODAxOGMyZDA0IiwKICAgICAgImZmZjVlYmZlZTZjZWZkZDBhMmZkYWU2YmZkOGQzY2YxNjkxM2Q5NDgwMWE2MzYwMzdmMjcwNCIKICAgICkubWFwKGNvbG9ycyk7CgogICAgdmFyIE9yYW5nZXMgPSByYW1wKHNjaGVtZSRxKTsKCiAgICBmdW5jdGlvbiBjaXZpZGlzKHQpIHsKICAgICAgdCA9IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIHQpKTsKICAgICAgcmV0dXJuICJyZ2IoIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQoLTQuNTQgLSB0ICogKDM1LjM0IC0gdCAqICgyMzgxLjczIC0gdCAqICg2NDAyLjcgLSB0ICogKDcwMjQuNzIgLSB0ICogMjcxMC41NykpKSkpKSkgKyAiLCAiCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCgzMi40OSArIHQgKiAoMTcwLjczICsgdCAqICg1Mi44MiAtIHQgKiAoMTMxLjQ2IC0gdCAqICgxNzYuNTggLSB0ICogNjcuMzcpKSkpKSkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQoODEuMjQgKyB0ICogKDQ0Mi4zNiAtIHQgKiAoMjQ4Mi40MyAtIHQgKiAoNjE2Ny4yNCAtIHQgKiAoNjYxNC45NCAtIHQgKiAyNDc1LjY3KSkpKSkpKQogICAgICAgICAgKyAiKSI7CiAgICB9CgogICAgdmFyIGN1YmVoZWxpeCQzID0gY3ViZWhlbGl4TG9uZyhjdWJlaGVsaXgoMzAwLCAwLjUsIDAuMCksIGN1YmVoZWxpeCgtMjQwLCAwLjUsIDEuMCkpOwoKICAgIHZhciB3YXJtID0gY3ViZWhlbGl4TG9uZyhjdWJlaGVsaXgoLTEwMCwgMC43NSwgMC4zNSksIGN1YmVoZWxpeCg4MCwgMS41MCwgMC44KSk7CgogICAgdmFyIGNvb2wgPSBjdWJlaGVsaXhMb25nKGN1YmVoZWxpeCgyNjAsIDAuNzUsIDAuMzUpLCBjdWJlaGVsaXgoODAsIDEuNTAsIDAuOCkpOwoKICAgIHZhciBjID0gY3ViZWhlbGl4KCk7CgogICAgZnVuY3Rpb24gcmFpbmJvdyh0KSB7CiAgICAgIGlmICh0IDwgMCB8fCB0ID4gMSkgdCAtPSBNYXRoLmZsb29yKHQpOwogICAgICB2YXIgdHMgPSBNYXRoLmFicyh0IC0gMC41KTsKICAgICAgYy5oID0gMzYwICogdCAtIDEwMDsKICAgICAgYy5zID0gMS41IC0gMS41ICogdHM7CiAgICAgIGMubCA9IDAuOCAtIDAuOSAqIHRzOwogICAgICByZXR1cm4gYyArICIiOwogICAgfQoKICAgIHZhciBjJDEgPSByZ2IoKSwKICAgICAgICBwaV8xXzMgPSBNYXRoLlBJIC8gMywKICAgICAgICBwaV8yXzMgPSBNYXRoLlBJICogMiAvIDM7CgogICAgZnVuY3Rpb24gc2luZWJvdyh0KSB7CiAgICAgIHZhciB4OwogICAgICB0ID0gKDAuNSAtIHQpICogTWF0aC5QSTsKICAgICAgYyQxLnIgPSAyNTUgKiAoeCA9IE1hdGguc2luKHQpKSAqIHg7CiAgICAgIGMkMS5nID0gMjU1ICogKHggPSBNYXRoLnNpbih0ICsgcGlfMV8zKSkgKiB4OwogICAgICBjJDEuYiA9IDI1NSAqICh4ID0gTWF0aC5zaW4odCArIHBpXzJfMykpICogeDsKICAgICAgcmV0dXJuIGMkMSArICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIHR1cmJvKHQpIHsKICAgICAgdCA9IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIHQpKTsKICAgICAgcmV0dXJuICJyZ2IoIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQoMzQuNjEgKyB0ICogKDExNzIuMzMgLSB0ICogKDEwNzkzLjU2IC0gdCAqICgzMzMwMC4xMiAtIHQgKiAoMzgzOTQuNDkgLSB0ICogMTQ4MjUuMDUpKSkpKSkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQoMjMuMzEgKyB0ICogKDU1Ny4zMyArIHQgKiAoMTIyNS4zMyAtIHQgKiAoMzU3NC45NiAtIHQgKiAoMTA3My43NyArIHQgKiA3MDcuNTYpKSkpKSkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQoMjcuMiArIHQgKiAoMzIxMS4xIC0gdCAqICgxNTMyNy45NyAtIHQgKiAoMjc4MTQgLSB0ICogKDIyNTY5LjE4IC0gdCAqIDY4MzguNjYpKSkpKSkpCiAgICAgICAgICArICIpIjsKICAgIH0KCiAgICBmdW5jdGlvbiByYW1wJDEocmFuZ2UpIHsKICAgICAgdmFyIG4gPSByYW5nZS5sZW5ndGg7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIHJhbmdlW01hdGgubWF4KDAsIE1hdGgubWluKG4gLSAxLCBNYXRoLmZsb29yKHQgKiBuKSkpXTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgdmlyaWRpcyA9IHJhbXAkMShjb2xvcnMoIjQ0MDE1NDQ0MDI1NjQ1MDQ1NzQ1MDU1OTQ2MDc1YTQ2MDg1YzQ2MGE1ZDQ2MGI1ZTQ3MGQ2MDQ3MGU2MTQ3MTA2MzQ3MTE2NDQ3MTM2NTQ4MTQ2NzQ4MTY2ODQ4MTc2OTQ4MTg2YTQ4MWE2YzQ4MWI2ZDQ4MWM2ZTQ4MWQ2ZjQ4MWY3MDQ4MjA3MTQ4MjE3MzQ4MjM3NDQ4MjQ3NTQ4MjU3NjQ4MjY3NzQ4Mjg3ODQ4Mjk3OTQ3MmE3YTQ3MmM3YTQ3MmQ3YjQ3MmU3YzQ3MmY3ZDQ2MzA3ZTQ2MzI3ZTQ2MzM3ZjQ2MzQ4MDQ1MzU4MTQ1Mzc4MTQ1Mzg4MjQ0Mzk4MzQ0M2E4MzQ0M2I4NDQzM2Q4NDQzM2U4NTQyM2Y4NTQyNDA4NjQyNDE4NjQxNDI4NzQxNDQ4NzQwNDU4ODQwNDY4ODNmNDc4ODNmNDg4OTNlNDk4OTNlNGE4OTNlNGM4YTNkNGQ4YTNkNGU4YTNjNGY4YTNjNTA4YjNiNTE4YjNiNTI4YjNhNTM4YjNhNTQ4YzM5NTU4YzM5NTY4YzM4NTg4YzM4NTk4YzM3NWE4YzM3NWI4ZDM2NWM4ZDM2NWQ4ZDM1NWU4ZDM1NWY4ZDM0NjA4ZDM0NjE4ZDMzNjI4ZDMzNjM4ZDMyNjQ4ZTMyNjU4ZTMxNjY4ZTMxNjc4ZTMxNjg4ZTMwNjk4ZTMwNmE4ZTJmNmI4ZTJmNmM4ZTJlNmQ4ZTJlNmU4ZTJlNmY4ZTJkNzA4ZTJkNzE4ZTJjNzE4ZTJjNzI4ZTJjNzM4ZTJiNzQ4ZTJiNzU4ZTJhNzY4ZTJhNzc4ZTJhNzg4ZTI5Nzk4ZTI5N2E4ZTI5N2I4ZTI4N2M4ZTI4N2Q4ZTI3N2U4ZTI3N2Y4ZTI3ODA4ZTI2ODE4ZTI2ODI4ZTI2ODI4ZTI1ODM4ZTI1ODQ4ZTI1ODU4ZTI0ODY4ZTI0ODc4ZTIzODg4ZTIzODk4ZTIzOGE4ZDIyOGI4ZDIyOGM4ZDIyOGQ4ZDIxOGU4ZDIxOGY4ZDIxOTA4ZDIxOTE4YzIwOTI4YzIwOTI4YzIwOTM4YzFmOTQ4YzFmOTU4YjFmOTY4YjFmOTc4YjFmOTg4YjFmOTk4YTFmOWE4YTFlOWI4YTFlOWM4OTFlOWQ4OTFmOWU4OTFmOWY4ODFmYTA4ODFmYTE4ODFmYTE4NzFmYTI4NzIwYTM4NjIwYTQ4NjIxYTU4NTIxYTY4NTIyYTc4NTIyYTg4NDIzYTk4MzI0YWE4MzI1YWI4MjI1YWM4MjI2YWQ4MTI3YWQ4MTI4YWU4MDI5YWY3ZjJhYjA3ZjJjYjE3ZTJkYjI3ZDJlYjM3YzJmYjQ3YzMxYjU3YjMyYjY3YTM0YjY3OTM1Yjc3OTM3Yjg3ODM4Yjk3NzNhYmE3NjNiYmI3NTNkYmM3NDNmYmM3MzQwYmQ3MjQyYmU3MTQ0YmY3MDQ2YzA2ZjQ4YzE2ZTRhYzE2ZDRjYzI2YzRlYzM2YjUwYzQ2YTUyYzU2OTU0YzU2ODU2YzY2NzU4Yzc2NTVhYzg2NDVjYzg2MzVlYzk2MjYwY2E2MDYzY2I1ZjY1Y2I1ZTY3Y2M1YzY5Y2Q1YjZjY2Q1YTZlY2U1ODcwY2Y1NzczZDA1Njc1ZDA1NDc3ZDE1MzdhZDE1MTdjZDI1MDdmZDM0ZTgxZDM0ZDg0ZDQ0Yjg2ZDU0OTg5ZDU0ODhiZDY0NjhlZDY0NTkwZDc0MzkzZDc0MTk1ZDg0MDk4ZDgzZTliZDkzYzlkZDkzYmEwZGEzOWEyZGEzN2E1ZGIzNmE4ZGIzNGFhZGMzMmFkZGMzMGIwZGQyZmIyZGQyZGI1ZGUyYmI4ZGUyOWJhZGUyOGJkZGYyNmMwZGYyNWMyZGYyM2M1ZTAyMWM4ZTAyMGNhZTExZmNkZTExZGQwZTExY2QyZTIxYmQ1ZTIxYWQ4ZTIxOWRhZTMxOWRkZTMxOGRmZTMxOGUyZTQxOGU1ZTQxOWU3ZTQxOWVhZTUxYWVjZTUxYmVmZTUxY2YxZTUxZGY0ZTYxZWY2ZTYyMGY4ZTYyMWZiZTcyM2ZkZTcyNSIpKTsKCiAgICB2YXIgbWFnbWEgPSByYW1wJDEoY29sb3JzKCIwMDAwMDQwMTAwMDUwMTAxMDYwMTAxMDgwMjAxMDkwMjAyMGIwMjAyMGQwMzAzMGYwMzAzMTIwNDA0MTQwNTA0MTYwNjA1MTgwNjA1MWEwNzA2MWMwODA3MWUwOTA3MjAwYTA4MjIwYjA5MjQwYzA5MjYwZDBhMjkwZTBiMmIxMDBiMmQxMTBjMmYxMjBkMzExMzBkMzQxNDBlMzYxNTBlMzgxNjBmM2IxODBmM2QxOTEwM2YxYTEwNDIxYzEwNDQxZDExNDcxZTExNDkyMDExNGIyMTExNGUyMjExNTAyNDEyNTMyNTEyNTUyNzEyNTgyOTExNWEyYTExNWMyYzExNWYyZDExNjEyZjExNjMzMTExNjUzMzEwNjczNDEwNjkzNjEwNmIzODEwNmMzOTBmNmUzYjBmNzAzZDBmNzEzZjBmNzI0MDBmNzQ0MjBmNzU0NDBmNzY0NTEwNzc0NzEwNzg0OTEwNzg0YTEwNzk0YzExN2E0ZTExN2I0ZjEyN2I1MTEyN2M1MjEzN2M1NDEzN2Q1NjE0N2Q1NzE1N2U1OTE1N2U1YTE2N2U1YzE2N2Y1ZDE3N2Y1ZjE4N2Y2MDE4ODA2MjE5ODA2NDFhODA2NTFhODA2NzFiODA2ODFjODE2YTFjODE2YjFkODE2ZDFkODE2ZTFlODE3MDFmODE3MjFmODE3MzIwODE3NTIxODE3NjIxODE3ODIyODE3OTIyODI3YjIzODI3YzIzODI3ZTI0ODI4MDI1ODI4MTI1ODE4MzI2ODE4NDI2ODE4NjI3ODE4ODI3ODE4OTI4ODE4YjI5ODE4YzI5ODE4ZTJhODE5MDJhODE5MTJiODE5MzJiODA5NDJjODA5NjJjODA5ODJkODA5OTJkODA5YjJlN2Y5YzJlN2Y5ZTJmN2ZhMDJmN2ZhMTMwN2VhMzMwN2VhNTMxN2VhNjMxN2RhODMyN2RhYTMzN2RhYjMzN2NhZDM0N2NhZTM0N2JiMDM1N2JiMjM1N2JiMzM2N2FiNTM2N2FiNzM3NzliODM3NzliYTM4NzhiYzM5NzhiZDM5NzdiZjNhNzdjMDNhNzZjMjNiNzVjNDNjNzVjNTNjNzRjNzNkNzNjODNlNzNjYTNlNzJjYzNmNzFjZDQwNzFjZjQwNzBkMDQxNmZkMjQyNmZkMzQzNmVkNTQ0NmRkNjQ1NmNkODQ1NmNkOTQ2NmJkYjQ3NmFkYzQ4NjlkZTQ5NjhkZjRhNjhlMDRjNjdlMjRkNjZlMzRlNjVlNDRmNjRlNTUwNjRlNzUyNjNlODUzNjJlOTU0NjJlYTU2NjFlYjU3NjBlYzU4NjBlZDVhNWZlZTViNWVlZjVkNWVmMDVmNWVmMTYwNWRmMjYyNWRmMjY0NWNmMzY1NWNmNDY3NWNmNDY5NWNmNTZiNWNmNjZjNWNmNjZlNWNmNzcwNWNmNzcyNWNmODc0NWNmODc2NWNmOTc4NWRmOTc5NWRmOTdiNWRmYTdkNWVmYTdmNWVmYTgxNWZmYjgzNWZmYjg1NjBmYjg3NjFmYzg5NjFmYzhhNjJmYzhjNjNmYzhlNjRmYzkwNjVmZDkyNjZmZDk0NjdmZDk2NjhmZDk4NjlmZDlhNmFmZDliNmJmZTlkNmNmZTlmNmRmZWExNmVmZWEzNmZmZWE1NzFmZWE3NzJmZWE5NzNmZWFhNzRmZWFjNzZmZWFlNzdmZWIwNzhmZWIyN2FmZWI0N2JmZWI2N2NmZWI3N2VmZWI5N2ZmZWJiODFmZWJkODJmZWJmODRmZWMxODVmZWMyODdmZWM0ODhmZWM2OGFmZWM4OGNmZWNhOGRmZWNjOGZmZWNkOTBmZWNmOTJmZWQxOTRmZWQzOTVmZWQ1OTdmZWQ3OTlmZWQ4OWFmZGRhOWNmZGRjOWVmZGRlYTBmZGUwYTFmZGUyYTNmZGUzYTVmZGU1YTdmZGU3YTlmZGU5YWFmZGViYWNmY2VjYWVmY2VlYjBmY2YwYjJmY2YyYjRmY2Y0YjZmY2Y2YjhmY2Y3YjlmY2Y5YmJmY2ZiYmRmY2ZkYmYiKSk7CgogICAgdmFyIGluZmVybm8gPSByYW1wJDEoY29sb3JzKCIwMDAwMDQwMTAwMDUwMTAxMDYwMTAxMDgwMjAxMGEwMjAyMGMwMjAyMGUwMzAyMTAwNDAzMTIwNDAzMTQwNTA0MTcwNjA0MTkwNzA1MWIwODA1MWQwOTA2MWYwYTA3MjIwYjA3MjQwYzA4MjYwZDA4MjkwZTA5MmIxMDA5MmQxMTBhMzAxMjBhMzIxNDBiMzQxNTBiMzcxNjBiMzkxODBjM2MxOTBjM2UxYjBjNDExYzBjNDMxZTBjNDUxZjBjNDgyMTBjNGEyMzBjNGMyNDBjNGYyNjBjNTEyODBiNTMyOTBiNTUyYjBiNTcyZDBiNTkyZjBhNWIzMTBhNWMzMjBhNWUzNDBhNWYzNjA5NjEzODA5NjIzOTA5NjMzYjA5NjQzZDA5NjUzZTA5NjY0MDBhNjc0MjBhNjg0NDBhNjg0NTBhNjk0NzBiNmE0OTBiNmE0YTBjNmI0YzBjNmI0ZDBkNmM0ZjBkNmM1MTBlNmM1MjBlNmQ1NDBmNmQ1NTBmNmQ1NzEwNmU1OTEwNmU1YTExNmU1YzEyNmU1ZDEyNmU1ZjEzNmU2MTEzNmU2MjE0NmU2NDE1NmU2NTE1NmU2NzE2NmU2OTE2NmU2YTE3NmU2YzE4NmU2ZDE4NmU2ZjE5NmU3MTE5NmU3MjFhNmU3NDFhNmU3NTFiNmU3NzFjNmQ3ODFjNmQ3YTFkNmQ3YzFkNmQ3ZDFlNmQ3ZjFlNmM4MDFmNmM4MjIwNmM4NDIwNmI4NTIxNmI4NzIxNmI4ODIyNmE4YTIyNmE4YzIzNjk4ZDIzNjk4ZjI0Njk5MDI1Njg5MjI1Njg5MzI2Njc5NTI2Njc5NzI3NjY5ODI3NjY5YTI4NjU5YjI5NjQ5ZDI5NjQ5ZjJhNjNhMDJhNjNhMjJiNjJhMzJjNjFhNTJjNjBhNjJkNjBhODJlNWZhOTJlNWVhYjJmNWVhZDMwNWRhZTMwNWNiMDMxNWJiMTMyNWFiMzMyNWFiNDMzNTliNjM0NThiNzM1NTdiOTM1NTZiYTM2NTViYzM3NTRiZDM4NTNiZjM5NTJjMDNhNTFjMTNhNTBjMzNiNGZjNDNjNGVjNjNkNGRjNzNlNGNjODNmNGJjYTQwNGFjYjQxNDljYzQyNDhjZTQzNDdjZjQ0NDZkMDQ1NDVkMjQ2NDRkMzQ3NDNkNDQ4NDJkNTRhNDFkNzRiM2ZkODRjM2VkOTRkM2RkYTRlM2NkYjUwM2JkZDUxM2FkZTUyMzhkZjUzMzdlMDU1MzZlMTU2MzVlMjU3MzRlMzU5MzNlNDVhMzFlNTVjMzBlNjVkMmZlNzVlMmVlODYwMmRlOTYxMmJlYTYzMmFlYjY0MjllYjY2MjhlYzY3MjZlZDY5MjVlZTZhMjRlZjZjMjNlZjZlMjFmMDZmMjBmMTcxMWZmMTczMWRmMjc0MWNmMzc2MWJmMzc4MTlmNDc5MThmNTdiMTdmNTdkMTVmNjdlMTRmNjgwMTNmNzgyMTJmNzg0MTBmODg1MGZmODg3MGVmODg5MGNmOThiMGJmOThjMGFmOThlMDlmYTkwMDhmYTkyMDdmYTk0MDdmYjk2MDZmYjk3MDZmYjk5MDZmYjliMDZmYjlkMDdmYzlmMDdmY2ExMDhmY2EzMDlmY2E1MGFmY2E2MGNmY2E4MGRmY2FhMGZmY2FjMTFmY2FlMTJmY2IwMTRmY2IyMTZmY2I0MThmYmI2MWFmYmI4MWRmYmJhMWZmYmJjMjFmYmJlMjNmYWMwMjZmYWMyMjhmYWM0MmFmYWM2MmRmOWM3MmZmOWM5MzJmOWNiMzVmOGNkMzdmOGNmM2FmN2QxM2RmN2QzNDBmNmQ1NDNmNmQ3NDZmNWQ5NDlmNWRiNGNmNGRkNGZmNGRmNTNmNGUxNTZmM2UzNWFmM2U1NWRmMmU2NjFmMmU4NjVmMmVhNjlmMWVjNmRmMWVkNzFmMWVmNzVmMWYxNzlmMmYyN2RmMmY0ODJmM2Y1ODZmM2Y2OGFmNGY4OGVmNWY5OTJmNmZhOTZmOGZiOWFmOWZjOWRmYWZkYTFmY2ZmYTQiKSk7CgogICAgdmFyIHBsYXNtYSA9IHJhbXAkMShjb2xvcnMoIjBkMDg4NzEwMDc4ODEzMDc4OTE2MDc4YTE5MDY4YzFiMDY4ZDFkMDY4ZTIwMDY4ZjIyMDY5MDI0MDY5MTI2MDU5MTI4MDU5MjJhMDU5MzJjMDU5NDJlMDU5NTJmMDU5NjMxMDU5NzMzMDU5NzM1MDQ5ODM3MDQ5OTM4MDQ5YTNhMDQ5YTNjMDQ5YjNlMDQ5YzNmMDQ5YzQxMDQ5ZDQzMDM5ZTQ0MDM5ZTQ2MDM5ZjQ4MDM5ZjQ5MDNhMDRiMDNhMTRjMDJhMTRlMDJhMjUwMDJhMjUxMDJhMzUzMDJhMzU1MDJhNDU2MDFhNDU4MDFhNDU5MDFhNTViMDFhNTVjMDFhNjVlMDFhNjYwMDFhNjYxMDBhNzYzMDBhNzY0MDBhNzY2MDBhNzY3MDBhODY5MDBhODZhMDBhODZjMDBhODZlMDBhODZmMDBhODcxMDBhODcyMDFhODc0MDFhODc1MDFhODc3MDFhODc4MDFhODdhMDJhODdiMDJhODdkMDNhODdlMDNhODgwMDRhODgxMDRhNzgzMDVhNzg0MDVhNzg2MDZhNjg3MDdhNjg4MDhhNjhhMDlhNThiMGFhNThkMGJhNThlMGNhNDhmMGRhNDkxMGVhMzkyMGZhMzk0MTBhMjk1MTFhMTk2MTNhMTk4MTRhMDk5MTU5ZjlhMTY5ZjljMTc5ZTlkMTg5ZDllMTk5ZGEwMWE5Y2ExMWI5YmEyMWQ5YWEzMWU5YWE1MWY5OWE2MjA5OGE3MjE5N2E4MjI5NmFhMjM5NWFiMjQ5NGFjMjY5NGFkMjc5M2FlMjg5MmIwMjk5MWIxMmE5MGIyMmI4ZmIzMmM4ZWI0MmU4ZGI1MmY4Y2I2MzA4YmI3MzE4YWI4MzI4OWJhMzM4OGJiMzQ4OGJjMzU4N2JkMzc4NmJlMzg4NWJmMzk4NGMwM2E4M2MxM2I4MmMyM2M4MWMzM2Q4MGM0M2U3ZmM1NDA3ZWM2NDE3ZGM3NDI3Y2M4NDM3YmM5NDQ3YWNhNDU3YWNiNDY3OWNjNDc3OGNjNDk3N2NkNGE3NmNlNGI3NWNmNGM3NGQwNGQ3M2QxNGU3MmQyNGY3MWQzNTE3MWQ0NTI3MGQ1NTM2ZmQ1NTQ2ZWQ2NTU2ZGQ3NTY2Y2Q4NTc2YmQ5NTg2YWRhNWE2YWRhNWI2OWRiNWM2OGRjNWQ2N2RkNWU2NmRlNWY2NWRlNjE2NGRmNjI2M2UwNjM2M2UxNjQ2MmUyNjU2MWUyNjY2MGUzNjg1ZmU0Njk1ZWU1NmE1ZGU1NmI1ZGU2NmM1Y2U3NmU1YmU3NmY1YWU4NzA1OWU5NzE1OGU5NzI1N2VhNzQ1N2ViNzU1NmViNzY1NWVjNzc1NGVkNzk1M2VkN2E1MmVlN2I1MWVmN2M1MWVmN2U1MGYwN2Y0ZmYwODA0ZWYxODE0ZGYxODM0Y2YyODQ0YmYzODU0YmYzODc0YWY0ODg0OWY0ODk0OGY1OGI0N2Y1OGM0NmY2OGQ0NWY2OGY0NGY3OTA0NGY3OTE0M2Y3OTM0MmY4OTQ0MWY4OTU0MGY5OTczZmY5OTgzZWY5OWEzZWZhOWIzZGZhOWMzY2ZhOWUzYmZiOWYzYWZiYTEzOWZiYTIzOGZjYTMzOGZjYTUzN2ZjYTYzNmZjYTgzNWZjYTkzNGZkYWIzM2ZkYWMzM2ZkYWUzMmZkYWYzMWZkYjEzMGZkYjIyZmZkYjQyZmZkYjUyZWZlYjcyZGZlYjgyY2ZlYmEyY2ZlYmIyYmZlYmQyYWZlYmUyYWZlYzAyOWZkYzIyOWZkYzMyOGZkYzUyN2ZkYzYyN2ZkYzgyN2ZkY2EyNmZkY2IyNmZjY2QyNWZjY2UyNWZjZDAyNWZjZDIyNWZiZDMyNGZiZDUyNGZiZDcyNGZhZDgyNGZhZGEyNGY5ZGMyNGY5ZGQyNWY4ZGYyNWY4ZTEyNWY3ZTIyNWY3ZTQyNWY2ZTYyNmY2ZTgyNmY1ZTkyNmY1ZWIyN2Y0ZWQyN2YzZWUyN2YzZjAyN2YyZjIyN2YxZjQyNmYxZjUyNWYwZjcyNGYwZjkyMSIpKTsKCiAgICBmdW5jdGlvbiBjb25zdGFudCRiKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uIGNvbnN0YW50KCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIHZhciBhYnMkMSA9IE1hdGguYWJzOwogICAgdmFyIGF0YW4yJDEgPSBNYXRoLmF0YW4yOwogICAgdmFyIGNvcyQyID0gTWF0aC5jb3M7CiAgICB2YXIgbWF4JDIgPSBNYXRoLm1heDsKICAgIHZhciBtaW4kMSA9IE1hdGgubWluOwogICAgdmFyIHNpbiQyID0gTWF0aC5zaW47CiAgICB2YXIgc3FydCQyID0gTWF0aC5zcXJ0OwoKICAgIHZhciBlcHNpbG9uJDMgPSAxZS0xMjsKICAgIHZhciBwaSQ0ID0gTWF0aC5QSTsKICAgIHZhciBoYWxmUGkkMyA9IHBpJDQgLyAyOwogICAgdmFyIHRhdSQ0ID0gMiAqIHBpJDQ7CgogICAgZnVuY3Rpb24gYWNvcyQxKHgpIHsKICAgICAgcmV0dXJuIHggPiAxID8gMCA6IHggPCAtMSA/IHBpJDQgOiBNYXRoLmFjb3MoeCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXNpbiQxKHgpIHsKICAgICAgcmV0dXJuIHggPj0gMSA/IGhhbGZQaSQzIDogeCA8PSAtMSA/IC1oYWxmUGkkMyA6IE1hdGguYXNpbih4KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmNJbm5lclJhZGl1cyhkKSB7CiAgICAgIHJldHVybiBkLmlubmVyUmFkaXVzOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyY091dGVyUmFkaXVzKGQpIHsKICAgICAgcmV0dXJuIGQub3V0ZXJSYWRpdXM7CiAgICB9CgogICAgZnVuY3Rpb24gYXJjU3RhcnRBbmdsZShkKSB7CiAgICAgIHJldHVybiBkLnN0YXJ0QW5nbGU7CiAgICB9CgogICAgZnVuY3Rpb24gYXJjRW5kQW5nbGUoZCkgewogICAgICByZXR1cm4gZC5lbmRBbmdsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmNQYWRBbmdsZShkKSB7CiAgICAgIHJldHVybiBkICYmIGQucGFkQW5nbGU7IC8vIE5vdGU6IG9wdGlvbmFsIQogICAgfQoKICAgIGZ1bmN0aW9uIGludGVyc2VjdCh4MCwgeTAsIHgxLCB5MSwgeDIsIHkyLCB4MywgeTMpIHsKICAgICAgdmFyIHgxMCA9IHgxIC0geDAsIHkxMCA9IHkxIC0geTAsCiAgICAgICAgICB4MzIgPSB4MyAtIHgyLCB5MzIgPSB5MyAtIHkyLAogICAgICAgICAgdCA9IHkzMiAqIHgxMCAtIHgzMiAqIHkxMDsKICAgICAgaWYgKHQgKiB0IDwgZXBzaWxvbiQzKSByZXR1cm47CiAgICAgIHQgPSAoeDMyICogKHkwIC0geTIpIC0geTMyICogKHgwIC0geDIpKSAvIHQ7CiAgICAgIHJldHVybiBbeDAgKyB0ICogeDEwLCB5MCArIHQgKiB5MTBdOwogICAgfQoKICAgIC8vIENvbXB1dGUgcGVycGVuZGljdWxhciBvZmZzZXQgbGluZSBvZiBsZW5ndGggcmMuCiAgICAvLyBodHRwOi8vbWF0aHdvcmxkLndvbGZyYW0uY29tL0NpcmNsZS1MaW5lSW50ZXJzZWN0aW9uLmh0bWwKICAgIGZ1bmN0aW9uIGNvcm5lclRhbmdlbnRzKHgwLCB5MCwgeDEsIHkxLCByMSwgcmMsIGN3KSB7CiAgICAgIHZhciB4MDEgPSB4MCAtIHgxLAogICAgICAgICAgeTAxID0geTAgLSB5MSwKICAgICAgICAgIGxvID0gKGN3ID8gcmMgOiAtcmMpIC8gc3FydCQyKHgwMSAqIHgwMSArIHkwMSAqIHkwMSksCiAgICAgICAgICBveCA9IGxvICogeTAxLAogICAgICAgICAgb3kgPSAtbG8gKiB4MDEsCiAgICAgICAgICB4MTEgPSB4MCArIG94LAogICAgICAgICAgeTExID0geTAgKyBveSwKICAgICAgICAgIHgxMCA9IHgxICsgb3gsCiAgICAgICAgICB5MTAgPSB5MSArIG95LAogICAgICAgICAgeDAwID0gKHgxMSArIHgxMCkgLyAyLAogICAgICAgICAgeTAwID0gKHkxMSArIHkxMCkgLyAyLAogICAgICAgICAgZHggPSB4MTAgLSB4MTEsCiAgICAgICAgICBkeSA9IHkxMCAtIHkxMSwKICAgICAgICAgIGQyID0gZHggKiBkeCArIGR5ICogZHksCiAgICAgICAgICByID0gcjEgLSByYywKICAgICAgICAgIEQgPSB4MTEgKiB5MTAgLSB4MTAgKiB5MTEsCiAgICAgICAgICBkID0gKGR5IDwgMCA/IC0xIDogMSkgKiBzcXJ0JDIobWF4JDIoMCwgciAqIHIgKiBkMiAtIEQgKiBEKSksCiAgICAgICAgICBjeDAgPSAoRCAqIGR5IC0gZHggKiBkKSAvIGQyLAogICAgICAgICAgY3kwID0gKC1EICogZHggLSBkeSAqIGQpIC8gZDIsCiAgICAgICAgICBjeDEgPSAoRCAqIGR5ICsgZHggKiBkKSAvIGQyLAogICAgICAgICAgY3kxID0gKC1EICogZHggKyBkeSAqIGQpIC8gZDIsCiAgICAgICAgICBkeDAgPSBjeDAgLSB4MDAsCiAgICAgICAgICBkeTAgPSBjeTAgLSB5MDAsCiAgICAgICAgICBkeDEgPSBjeDEgLSB4MDAsCiAgICAgICAgICBkeTEgPSBjeTEgLSB5MDA7CgogICAgICAvLyBQaWNrIHRoZSBjbG9zZXIgb2YgdGhlIHR3byBpbnRlcnNlY3Rpb24gcG9pbnRzLgogICAgICAvLyBUT0RPIElzIHRoZXJlIGEgZmFzdGVyIHdheSB0byBkZXRlcm1pbmUgd2hpY2ggaW50ZXJzZWN0aW9uIHRvIHVzZT8KICAgICAgaWYgKGR4MCAqIGR4MCArIGR5MCAqIGR5MCA+IGR4MSAqIGR4MSArIGR5MSAqIGR5MSkgY3gwID0gY3gxLCBjeTAgPSBjeTE7CgogICAgICByZXR1cm4gewogICAgICAgIGN4OiBjeDAsCiAgICAgICAgY3k6IGN5MCwKICAgICAgICB4MDE6IC1veCwKICAgICAgICB5MDE6IC1veSwKICAgICAgICB4MTE6IGN4MCAqIChyMSAvIHIgLSAxKSwKICAgICAgICB5MTE6IGN5MCAqIChyMSAvIHIgLSAxKQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGFyYygpIHsKICAgICAgdmFyIGlubmVyUmFkaXVzID0gYXJjSW5uZXJSYWRpdXMsCiAgICAgICAgICBvdXRlclJhZGl1cyA9IGFyY091dGVyUmFkaXVzLAogICAgICAgICAgY29ybmVyUmFkaXVzID0gY29uc3RhbnQkYigwKSwKICAgICAgICAgIHBhZFJhZGl1cyA9IG51bGwsCiAgICAgICAgICBzdGFydEFuZ2xlID0gYXJjU3RhcnRBbmdsZSwKICAgICAgICAgIGVuZEFuZ2xlID0gYXJjRW5kQW5nbGUsCiAgICAgICAgICBwYWRBbmdsZSA9IGFyY1BhZEFuZ2xlLAogICAgICAgICAgY29udGV4dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBhcmMoKSB7CiAgICAgICAgdmFyIGJ1ZmZlciwKICAgICAgICAgICAgciwKICAgICAgICAgICAgcjAgPSAraW5uZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgcjEgPSArb3V0ZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgYTAgPSBzdGFydEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgLSBoYWxmUGkkMywKICAgICAgICAgICAgYTEgPSBlbmRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIC0gaGFsZlBpJDMsCiAgICAgICAgICAgIGRhID0gYWJzJDEoYTEgLSBhMCksCiAgICAgICAgICAgIGN3ID0gYTEgPiBhMDsKCiAgICAgICAgaWYgKCFjb250ZXh0KSBjb250ZXh0ID0gYnVmZmVyID0gcGF0aCgpOwoKICAgICAgICAvLyBFbnN1cmUgdGhhdCB0aGUgb3V0ZXIgcmFkaXVzIGlzIGFsd2F5cyBsYXJnZXIgdGhhbiB0aGUgaW5uZXIgcmFkaXVzLgogICAgICAgIGlmIChyMSA8IHIwKSByID0gcjEsIHIxID0gcjAsIHIwID0gcjsKCiAgICAgICAgLy8gSXMgaXQgYSBwb2ludD8KICAgICAgICBpZiAoIShyMSA+IGVwc2lsb24kMykpIGNvbnRleHQubW92ZVRvKDAsIDApOwoKICAgICAgICAvLyBPciBpcyBpdCBhIGNpcmNsZSBvciBhbm51bHVzPwogICAgICAgIGVsc2UgaWYgKGRhID4gdGF1JDQgLSBlcHNpbG9uJDMpIHsKICAgICAgICAgIGNvbnRleHQubW92ZVRvKHIxICogY29zJDIoYTApLCByMSAqIHNpbiQyKGEwKSk7CiAgICAgICAgICBjb250ZXh0LmFyYygwLCAwLCByMSwgYTAsIGExLCAhY3cpOwogICAgICAgICAgaWYgKHIwID4gZXBzaWxvbiQzKSB7CiAgICAgICAgICAgIGNvbnRleHQubW92ZVRvKHIwICogY29zJDIoYTEpLCByMCAqIHNpbiQyKGExKSk7CiAgICAgICAgICAgIGNvbnRleHQuYXJjKDAsIDAsIHIwLCBhMSwgYTAsIGN3KTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIE9yIGlzIGl0IGEgY2lyY3VsYXIgb3IgYW5udWxhciBzZWN0b3I/CiAgICAgICAgZWxzZSB7CiAgICAgICAgICB2YXIgYTAxID0gYTAsCiAgICAgICAgICAgICAgYTExID0gYTEsCiAgICAgICAgICAgICAgYTAwID0gYTAsCiAgICAgICAgICAgICAgYTEwID0gYTEsCiAgICAgICAgICAgICAgZGEwID0gZGEsCiAgICAgICAgICAgICAgZGExID0gZGEsCiAgICAgICAgICAgICAgYXAgPSBwYWRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIC8gMiwKICAgICAgICAgICAgICBycCA9IChhcCA+IGVwc2lsb24kMykgJiYgKHBhZFJhZGl1cyA/ICtwYWRSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSA6IHNxcnQkMihyMCAqIHIwICsgcjEgKiByMSkpLAogICAgICAgICAgICAgIHJjID0gbWluJDEoYWJzJDEocjEgLSByMCkgLyAyLCArY29ybmVyUmFkaXVzLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpLAogICAgICAgICAgICAgIHJjMCA9IHJjLAogICAgICAgICAgICAgIHJjMSA9IHJjLAogICAgICAgICAgICAgIHQwLAogICAgICAgICAgICAgIHQxOwoKICAgICAgICAgIC8vIEFwcGx5IHBhZGRpbmc/IE5vdGUgdGhhdCBzaW5jZSByMSDiiaUgcjAsIGRhMSDiiaUgZGEwLgogICAgICAgICAgaWYgKHJwID4gZXBzaWxvbiQzKSB7CiAgICAgICAgICAgIHZhciBwMCA9IGFzaW4kMShycCAvIHIwICogc2luJDIoYXApKSwKICAgICAgICAgICAgICAgIHAxID0gYXNpbiQxKHJwIC8gcjEgKiBzaW4kMihhcCkpOwogICAgICAgICAgICBpZiAoKGRhMCAtPSBwMCAqIDIpID4gZXBzaWxvbiQzKSBwMCAqPSAoY3cgPyAxIDogLTEpLCBhMDAgKz0gcDAsIGExMCAtPSBwMDsKICAgICAgICAgICAgZWxzZSBkYTAgPSAwLCBhMDAgPSBhMTAgPSAoYTAgKyBhMSkgLyAyOwogICAgICAgICAgICBpZiAoKGRhMSAtPSBwMSAqIDIpID4gZXBzaWxvbiQzKSBwMSAqPSAoY3cgPyAxIDogLTEpLCBhMDEgKz0gcDEsIGExMSAtPSBwMTsKICAgICAgICAgICAgZWxzZSBkYTEgPSAwLCBhMDEgPSBhMTEgPSAoYTAgKyBhMSkgLyAyOwogICAgICAgICAgfQoKICAgICAgICAgIHZhciB4MDEgPSByMSAqIGNvcyQyKGEwMSksCiAgICAgICAgICAgICAgeTAxID0gcjEgKiBzaW4kMihhMDEpLAogICAgICAgICAgICAgIHgxMCA9IHIwICogY29zJDIoYTEwKSwKICAgICAgICAgICAgICB5MTAgPSByMCAqIHNpbiQyKGExMCk7CgogICAgICAgICAgLy8gQXBwbHkgcm91bmRlZCBjb3JuZXJzPwogICAgICAgICAgaWYgKHJjID4gZXBzaWxvbiQzKSB7CiAgICAgICAgICAgIHZhciB4MTEgPSByMSAqIGNvcyQyKGExMSksCiAgICAgICAgICAgICAgICB5MTEgPSByMSAqIHNpbiQyKGExMSksCiAgICAgICAgICAgICAgICB4MDAgPSByMCAqIGNvcyQyKGEwMCksCiAgICAgICAgICAgICAgICB5MDAgPSByMCAqIHNpbiQyKGEwMCksCiAgICAgICAgICAgICAgICBvYzsKCiAgICAgICAgICAgIC8vIFJlc3RyaWN0IHRoZSBjb3JuZXIgcmFkaXVzIGFjY29yZGluZyB0byB0aGUgc2VjdG9yIGFuZ2xlLgogICAgICAgICAgICBpZiAoZGEgPCBwaSQ0ICYmIChvYyA9IGludGVyc2VjdCh4MDEsIHkwMSwgeDAwLCB5MDAsIHgxMSwgeTExLCB4MTAsIHkxMCkpKSB7CiAgICAgICAgICAgICAgdmFyIGF4ID0geDAxIC0gb2NbMF0sCiAgICAgICAgICAgICAgICAgIGF5ID0geTAxIC0gb2NbMV0sCiAgICAgICAgICAgICAgICAgIGJ4ID0geDExIC0gb2NbMF0sCiAgICAgICAgICAgICAgICAgIGJ5ID0geTExIC0gb2NbMV0sCiAgICAgICAgICAgICAgICAgIGtjID0gMSAvIHNpbiQyKGFjb3MkMSgoYXggKiBieCArIGF5ICogYnkpIC8gKHNxcnQkMihheCAqIGF4ICsgYXkgKiBheSkgKiBzcXJ0JDIoYnggKiBieCArIGJ5ICogYnkpKSkgLyAyKSwKICAgICAgICAgICAgICAgICAgbGMgPSBzcXJ0JDIob2NbMF0gKiBvY1swXSArIG9jWzFdICogb2NbMV0pOwogICAgICAgICAgICAgIHJjMCA9IG1pbiQxKHJjLCAocjAgLSBsYykgLyAoa2MgLSAxKSk7CiAgICAgICAgICAgICAgcmMxID0gbWluJDEocmMsIChyMSAtIGxjKSAvIChrYyArIDEpKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQoKICAgICAgICAgIC8vIElzIHRoZSBzZWN0b3IgY29sbGFwc2VkIHRvIGEgbGluZT8KICAgICAgICAgIGlmICghKGRhMSA+IGVwc2lsb24kMykpIGNvbnRleHQubW92ZVRvKHgwMSwgeTAxKTsKCiAgICAgICAgICAvLyBEb2VzIHRoZSBzZWN0b3LigJlzIG91dGVyIHJpbmcgaGF2ZSByb3VuZGVkIGNvcm5lcnM/CiAgICAgICAgICBlbHNlIGlmIChyYzEgPiBlcHNpbG9uJDMpIHsKICAgICAgICAgICAgdDAgPSBjb3JuZXJUYW5nZW50cyh4MDAsIHkwMCwgeDAxLCB5MDEsIHIxLCByYzEsIGN3KTsKICAgICAgICAgICAgdDEgPSBjb3JuZXJUYW5nZW50cyh4MTEsIHkxMSwgeDEwLCB5MTAsIHIxLCByYzEsIGN3KTsKCiAgICAgICAgICAgIGNvbnRleHQubW92ZVRvKHQwLmN4ICsgdDAueDAxLCB0MC5jeSArIHQwLnkwMSk7CgogICAgICAgICAgICAvLyBIYXZlIHRoZSBjb3JuZXJzIG1lcmdlZD8KICAgICAgICAgICAgaWYgKHJjMSA8IHJjKSBjb250ZXh0LmFyYyh0MC5jeCwgdDAuY3ksIHJjMSwgYXRhbjIkMSh0MC55MDEsIHQwLngwMSksIGF0YW4yJDEodDEueTAxLCB0MS54MDEpLCAhY3cpOwoKICAgICAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IHRoZSB0d28gY29ybmVycyBhbmQgdGhlIHJpbmcuCiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQwLmN4LCB0MC5jeSwgcmMxLCBhdGFuMiQxKHQwLnkwMSwgdDAueDAxKSwgYXRhbjIkMSh0MC55MTEsIHQwLngxMSksICFjdyk7CiAgICAgICAgICAgICAgY29udGV4dC5hcmMoMCwgMCwgcjEsIGF0YW4yJDEodDAuY3kgKyB0MC55MTEsIHQwLmN4ICsgdDAueDExKSwgYXRhbjIkMSh0MS5jeSArIHQxLnkxMSwgdDEuY3ggKyB0MS54MTEpLCAhY3cpOwogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQxLmN4LCB0MS5jeSwgcmMxLCBhdGFuMiQxKHQxLnkxMSwgdDEueDExKSwgYXRhbjIkMSh0MS55MDEsIHQxLngwMSksICFjdyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvLyBPciBpcyB0aGUgb3V0ZXIgcmluZyBqdXN0IGEgY2lyY3VsYXIgYXJjPwogICAgICAgICAgZWxzZSBjb250ZXh0Lm1vdmVUbyh4MDEsIHkwMSksIGNvbnRleHQuYXJjKDAsIDAsIHIxLCBhMDEsIGExMSwgIWN3KTsKCiAgICAgICAgICAvLyBJcyB0aGVyZSBubyBpbm5lciByaW5nLCBhbmQgaXTigJlzIGEgY2lyY3VsYXIgc2VjdG9yPwogICAgICAgICAgLy8gT3IgcGVyaGFwcyBpdOKAmXMgYW4gYW5udWxhciBzZWN0b3IgY29sbGFwc2VkIGR1ZSB0byBwYWRkaW5nPwogICAgICAgICAgaWYgKCEocjAgPiBlcHNpbG9uJDMpIHx8ICEoZGEwID4gZXBzaWxvbiQzKSkgY29udGV4dC5saW5lVG8oeDEwLCB5MTApOwoKICAgICAgICAgIC8vIERvZXMgdGhlIHNlY3RvcuKAmXMgaW5uZXIgcmluZyAob3IgcG9pbnQpIGhhdmUgcm91bmRlZCBjb3JuZXJzPwogICAgICAgICAgZWxzZSBpZiAocmMwID4gZXBzaWxvbiQzKSB7CiAgICAgICAgICAgIHQwID0gY29ybmVyVGFuZ2VudHMoeDEwLCB5MTAsIHgxMSwgeTExLCByMCwgLXJjMCwgY3cpOwogICAgICAgICAgICB0MSA9IGNvcm5lclRhbmdlbnRzKHgwMSwgeTAxLCB4MDAsIHkwMCwgcjAsIC1yYzAsIGN3KTsKCiAgICAgICAgICAgIGNvbnRleHQubGluZVRvKHQwLmN4ICsgdDAueDAxLCB0MC5jeSArIHQwLnkwMSk7CgogICAgICAgICAgICAvLyBIYXZlIHRoZSBjb3JuZXJzIG1lcmdlZD8KICAgICAgICAgICAgaWYgKHJjMCA8IHJjKSBjb250ZXh0LmFyYyh0MC5jeCwgdDAuY3ksIHJjMCwgYXRhbjIkMSh0MC55MDEsIHQwLngwMSksIGF0YW4yJDEodDEueTAxLCB0MS54MDEpLCAhY3cpOwoKICAgICAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IHRoZSB0d28gY29ybmVycyBhbmQgdGhlIHJpbmcuCiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQwLmN4LCB0MC5jeSwgcmMwLCBhdGFuMiQxKHQwLnkwMSwgdDAueDAxKSwgYXRhbjIkMSh0MC55MTEsIHQwLngxMSksICFjdyk7CiAgICAgICAgICAgICAgY29udGV4dC5hcmMoMCwgMCwgcjAsIGF0YW4yJDEodDAuY3kgKyB0MC55MTEsIHQwLmN4ICsgdDAueDExKSwgYXRhbjIkMSh0MS5jeSArIHQxLnkxMSwgdDEuY3ggKyB0MS54MTEpLCBjdyk7CiAgICAgICAgICAgICAgY29udGV4dC5hcmModDEuY3gsIHQxLmN5LCByYzAsIGF0YW4yJDEodDEueTExLCB0MS54MTEpLCBhdGFuMiQxKHQxLnkwMSwgdDEueDAxKSwgIWN3KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQoKICAgICAgICAgIC8vIE9yIGlzIHRoZSBpbm5lciByaW5nIGp1c3QgYSBjaXJjdWxhciBhcmM/CiAgICAgICAgICBlbHNlIGNvbnRleHQuYXJjKDAsIDAsIHIwLCBhMTAsIGEwMCwgY3cpOwogICAgICAgIH0KCiAgICAgICAgY29udGV4dC5jbG9zZVBhdGgoKTsKCiAgICAgICAgaWYgKGJ1ZmZlcikgcmV0dXJuIGNvbnRleHQgPSBudWxsLCBidWZmZXIgKyAiIiB8fCBudWxsOwogICAgICB9CgogICAgICBhcmMuY2VudHJvaWQgPSBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgciA9ICgraW5uZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSArICtvdXRlclJhZGl1cy5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSAvIDIsCiAgICAgICAgICAgIGEgPSAoK3N0YXJ0QW5nbGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSArICtlbmRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSAvIDIgLSBwaSQ0IC8gMjsKICAgICAgICByZXR1cm4gW2NvcyQyKGEpICogciwgc2luJDIoYSkgKiByXTsKICAgICAgfTsKCiAgICAgIGFyYy5pbm5lclJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpbm5lclJhZGl1cyA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBhcmMpIDogaW5uZXJSYWRpdXM7CiAgICAgIH07CgogICAgICBhcmMub3V0ZXJSYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAob3V0ZXJSYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgYXJjKSA6IG91dGVyUmFkaXVzOwogICAgICB9OwoKICAgICAgYXJjLmNvcm5lclJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjb3JuZXJSYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgYXJjKSA6IGNvcm5lclJhZGl1czsKICAgICAgfTsKCiAgICAgIGFyYy5wYWRSYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkUmFkaXVzID0gXyA9PSBudWxsID8gbnVsbCA6IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBhcmMpIDogcGFkUmFkaXVzOwogICAgICB9OwoKICAgICAgYXJjLnN0YXJ0QW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RhcnRBbmdsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBhcmMpIDogc3RhcnRBbmdsZTsKICAgICAgfTsKCiAgICAgIGFyYy5lbmRBbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChlbmRBbmdsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBhcmMpIDogZW5kQW5nbGU7CiAgICAgIH07CgogICAgICBhcmMucGFkQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkQW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgYXJjKSA6IHBhZEFuZ2xlOwogICAgICB9OwoKICAgICAgYXJjLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoKGNvbnRleHQgPSBfID09IG51bGwgPyBudWxsIDogXyksIGFyYykgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIGFyYzsKICAgIH0KCiAgICBmdW5jdGlvbiBMaW5lYXIoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBMaW5lYXIucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgfHwgKHRoaXMuX2xpbmUgIT09IDAgJiYgdGhpcy5fcG9pbnQgPT09IDEpKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX2xpbmUgPSAxIC0gdGhpcy5fbGluZTsKICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpOyBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY3VydmVMaW5lYXIoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IExpbmVhcihjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiB4JDMocCkgewogICAgICByZXR1cm4gcFswXTsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDMocCkgewogICAgICByZXR1cm4gcFsxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5lKCkgewogICAgICB2YXIgeCA9IHgkMywKICAgICAgICAgIHkgPSB5JDMsCiAgICAgICAgICBkZWZpbmVkID0gY29uc3RhbnQkYih0cnVlKSwKICAgICAgICAgIGNvbnRleHQgPSBudWxsLAogICAgICAgICAgY3VydmUgPSBjdXJ2ZUxpbmVhciwKICAgICAgICAgIG91dHB1dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBsaW5lKGRhdGEpIHsKICAgICAgICB2YXIgaSwKICAgICAgICAgICAgbiA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBkLAogICAgICAgICAgICBkZWZpbmVkMCA9IGZhbHNlLAogICAgICAgICAgICBidWZmZXI7CgogICAgICAgIGlmIChjb250ZXh0ID09IG51bGwpIG91dHB1dCA9IGN1cnZlKGJ1ZmZlciA9IHBhdGgoKSk7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPD0gbjsgKytpKSB7CiAgICAgICAgICBpZiAoIShpIDwgbiAmJiBkZWZpbmVkKGQgPSBkYXRhW2ldLCBpLCBkYXRhKSkgPT09IGRlZmluZWQwKSB7CiAgICAgICAgICAgIGlmIChkZWZpbmVkMCA9ICFkZWZpbmVkMCkgb3V0cHV0LmxpbmVTdGFydCgpOwogICAgICAgICAgICBlbHNlIG91dHB1dC5saW5lRW5kKCk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoZGVmaW5lZDApIG91dHB1dC5wb2ludCgreChkLCBpLCBkYXRhKSwgK3koZCwgaSwgZGF0YSkpOwogICAgICAgIH0KCiAgICAgICAgaWYgKGJ1ZmZlcikgcmV0dXJuIG91dHB1dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIGxpbmUueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIGxpbmUpIDogeDsKICAgICAgfTsKCiAgICAgIGxpbmUueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIGxpbmUpIDogeTsKICAgICAgfTsKCiAgICAgIGxpbmUuZGVmaW5lZCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkZWZpbmVkID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYighIV8pLCBsaW5lKSA6IGRlZmluZWQ7CiAgICAgIH07CgogICAgICBsaW5lLmN1cnZlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGN1cnZlID0gXywgY29udGV4dCAhPSBudWxsICYmIChvdXRwdXQgPSBjdXJ2ZShjb250ZXh0KSksIGxpbmUpIDogY3VydmU7CiAgICAgIH07CgogICAgICBsaW5lLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoXyA9PSBudWxsID8gY29udGV4dCA9IG91dHB1dCA9IG51bGwgOiBvdXRwdXQgPSBjdXJ2ZShjb250ZXh0ID0gXyksIGxpbmUpIDogY29udGV4dDsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5lOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWEkMygpIHsKICAgICAgdmFyIHgwID0geCQzLAogICAgICAgICAgeDEgPSBudWxsLAogICAgICAgICAgeTAgPSBjb25zdGFudCRiKDApLAogICAgICAgICAgeTEgPSB5JDMsCiAgICAgICAgICBkZWZpbmVkID0gY29uc3RhbnQkYih0cnVlKSwKICAgICAgICAgIGNvbnRleHQgPSBudWxsLAogICAgICAgICAgY3VydmUgPSBjdXJ2ZUxpbmVhciwKICAgICAgICAgIG91dHB1dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBhcmVhKGRhdGEpIHsKICAgICAgICB2YXIgaSwKICAgICAgICAgICAgaiwKICAgICAgICAgICAgaywKICAgICAgICAgICAgbiA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBkLAogICAgICAgICAgICBkZWZpbmVkMCA9IGZhbHNlLAogICAgICAgICAgICBidWZmZXIsCiAgICAgICAgICAgIHgweiA9IG5ldyBBcnJheShuKSwKICAgICAgICAgICAgeTB6ID0gbmV3IEFycmF5KG4pOwoKICAgICAgICBpZiAoY29udGV4dCA9PSBudWxsKSBvdXRwdXQgPSBjdXJ2ZShidWZmZXIgPSBwYXRoKCkpOwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDw9IG47ICsraSkgewogICAgICAgICAgaWYgKCEoaSA8IG4gJiYgZGVmaW5lZChkID0gZGF0YVtpXSwgaSwgZGF0YSkpID09PSBkZWZpbmVkMCkgewogICAgICAgICAgICBpZiAoZGVmaW5lZDAgPSAhZGVmaW5lZDApIHsKICAgICAgICAgICAgICBqID0gaTsKICAgICAgICAgICAgICBvdXRwdXQuYXJlYVN0YXJ0KCk7CiAgICAgICAgICAgICAgb3V0cHV0LmxpbmVTdGFydCgpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIG91dHB1dC5saW5lRW5kKCk7CiAgICAgICAgICAgICAgb3V0cHV0LmxpbmVTdGFydCgpOwogICAgICAgICAgICAgIGZvciAoayA9IGkgLSAxOyBrID49IGo7IC0taykgewogICAgICAgICAgICAgICAgb3V0cHV0LnBvaW50KHgweltrXSwgeTB6W2tdKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgb3V0cHV0LmxpbmVFbmQoKTsKICAgICAgICAgICAgICBvdXRwdXQuYXJlYUVuZCgpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoZGVmaW5lZDApIHsKICAgICAgICAgICAgeDB6W2ldID0gK3gwKGQsIGksIGRhdGEpLCB5MHpbaV0gPSAreTAoZCwgaSwgZGF0YSk7CiAgICAgICAgICAgIG91dHB1dC5wb2ludCh4MSA/ICt4MShkLCBpLCBkYXRhKSA6IHgweltpXSwgeTEgPyAreTEoZCwgaSwgZGF0YSkgOiB5MHpbaV0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKGJ1ZmZlcikgcmV0dXJuIG91dHB1dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGFyZWFsaW5lKCkgewogICAgICAgIHJldHVybiBsaW5lKCkuZGVmaW5lZChkZWZpbmVkKS5jdXJ2ZShjdXJ2ZSkuY29udGV4dChjb250ZXh0KTsKICAgICAgfQoKICAgICAgYXJlYS54ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHgwID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIHgxID0gbnVsbCwgYXJlYSkgOiB4MDsKICAgICAgfTsKCiAgICAgIGFyZWEueDAgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeDAgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgYXJlYSkgOiB4MDsKICAgICAgfTsKCiAgICAgIGFyZWEueDEgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeDEgPSBfID09IG51bGwgPyBudWxsIDogdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIGFyZWEpIDogeDE7CiAgICAgIH07CgogICAgICBhcmVhLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeTAgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgeTEgPSBudWxsLCBhcmVhKSA6IHkwOwogICAgICB9OwoKICAgICAgYXJlYS55MCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5MCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBhcmVhKSA6IHkwOwogICAgICB9OwoKICAgICAgYXJlYS55MSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5MSA9IF8gPT0gbnVsbCA/IG51bGwgOiB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgYXJlYSkgOiB5MTsKICAgICAgfTsKCiAgICAgIGFyZWEubGluZVgwID0KICAgICAgYXJlYS5saW5lWTAgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYXJlYWxpbmUoKS54KHgwKS55KHkwKTsKICAgICAgfTsKCiAgICAgIGFyZWEubGluZVkxID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGFyZWFsaW5lKCkueCh4MCkueSh5MSk7CiAgICAgIH07CgogICAgICBhcmVhLmxpbmVYMSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBhcmVhbGluZSgpLngoeDEpLnkoeTApOwogICAgICB9OwoKICAgICAgYXJlYS5kZWZpbmVkID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRlZmluZWQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCEhXyksIGFyZWEpIDogZGVmaW5lZDsKICAgICAgfTsKCiAgICAgIGFyZWEuY3VydmUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY3VydmUgPSBfLCBjb250ZXh0ICE9IG51bGwgJiYgKG91dHB1dCA9IGN1cnZlKGNvbnRleHQpKSwgYXJlYSkgOiBjdXJ2ZTsKICAgICAgfTsKCiAgICAgIGFyZWEuY29udGV4dCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChfID09IG51bGwgPyBjb250ZXh0ID0gb3V0cHV0ID0gbnVsbCA6IG91dHB1dCA9IGN1cnZlKGNvbnRleHQgPSBfKSwgYXJlYSkgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIGFyZWE7CiAgICB9CgogICAgZnVuY3Rpb24gZGVzY2VuZGluZyQxKGEsIGIpIHsKICAgICAgcmV0dXJuIGIgPCBhID8gLTEgOiBiID4gYSA/IDEgOiBiID49IGEgPyAwIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JDgoZCkgewogICAgICByZXR1cm4gZDsKICAgIH0KCiAgICBmdW5jdGlvbiBwaWUoKSB7CiAgICAgIHZhciB2YWx1ZSA9IGlkZW50aXR5JDgsCiAgICAgICAgICBzb3J0VmFsdWVzID0gZGVzY2VuZGluZyQxLAogICAgICAgICAgc29ydCA9IG51bGwsCiAgICAgICAgICBzdGFydEFuZ2xlID0gY29uc3RhbnQkYigwKSwKICAgICAgICAgIGVuZEFuZ2xlID0gY29uc3RhbnQkYih0YXUkNCksCiAgICAgICAgICBwYWRBbmdsZSA9IGNvbnN0YW50JGIoMCk7CgogICAgICBmdW5jdGlvbiBwaWUoZGF0YSkgewogICAgICAgIHZhciBpLAogICAgICAgICAgICBuID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIGosCiAgICAgICAgICAgIGssCiAgICAgICAgICAgIHN1bSA9IDAsCiAgICAgICAgICAgIGluZGV4ID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBhcmNzID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBhMCA9ICtzdGFydEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksCiAgICAgICAgICAgIGRhID0gTWF0aC5taW4odGF1JDQsIE1hdGgubWF4KC10YXUkNCwgZW5kQW5nbGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSAtIGEwKSksCiAgICAgICAgICAgIGExLAogICAgICAgICAgICBwID0gTWF0aC5taW4oTWF0aC5hYnMoZGEpIC8gbiwgcGFkQW5nbGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSksCiAgICAgICAgICAgIHBhID0gcCAqIChkYSA8IDAgPyAtMSA6IDEpLAogICAgICAgICAgICB2OwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKHYgPSBhcmNzW2luZGV4W2ldID0gaV0gPSArdmFsdWUoZGF0YVtpXSwgaSwgZGF0YSkpID4gMCkgewogICAgICAgICAgICBzdW0gKz0gdjsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIE9wdGlvbmFsbHkgc29ydCB0aGUgYXJjcyBieSBwcmV2aW91c2x5LWNvbXB1dGVkIHZhbHVlcyBvciBieSBkYXRhLgogICAgICAgIGlmIChzb3J0VmFsdWVzICE9IG51bGwpIGluZGV4LnNvcnQoZnVuY3Rpb24oaSwgaikgeyByZXR1cm4gc29ydFZhbHVlcyhhcmNzW2ldLCBhcmNzW2pdKTsgfSk7CiAgICAgICAgZWxzZSBpZiAoc29ydCAhPSBudWxsKSBpbmRleC5zb3J0KGZ1bmN0aW9uKGksIGopIHsgcmV0dXJuIHNvcnQoZGF0YVtpXSwgZGF0YVtqXSk7IH0pOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBhcmNzISBUaGV5IGFyZSBzdG9yZWQgaW4gdGhlIG9yaWdpbmFsIGRhdGEncyBvcmRlci4KICAgICAgICBmb3IgKGkgPSAwLCBrID0gc3VtID8gKGRhIC0gbiAqIHBhKSAvIHN1bSA6IDA7IGkgPCBuOyArK2ksIGEwID0gYTEpIHsKICAgICAgICAgIGogPSBpbmRleFtpXSwgdiA9IGFyY3Nbal0sIGExID0gYTAgKyAodiA+IDAgPyB2ICogayA6IDApICsgcGEsIGFyY3Nbal0gPSB7CiAgICAgICAgICAgIGRhdGE6IGRhdGFbal0sCiAgICAgICAgICAgIGluZGV4OiBpLAogICAgICAgICAgICB2YWx1ZTogdiwKICAgICAgICAgICAgc3RhcnRBbmdsZTogYTAsCiAgICAgICAgICAgIGVuZEFuZ2xlOiBhMSwKICAgICAgICAgICAgcGFkQW5nbGU6IHAKICAgICAgICAgIH07CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gYXJjczsKICAgICAgfQoKICAgICAgcGllLnZhbHVlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHZhbHVlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIHBpZSkgOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIHBpZS5zb3J0VmFsdWVzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNvcnRWYWx1ZXMgPSBfLCBzb3J0ID0gbnVsbCwgcGllKSA6IHNvcnRWYWx1ZXM7CiAgICAgIH07CgogICAgICBwaWUuc29ydCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzb3J0ID0gXywgc29ydFZhbHVlcyA9IG51bGwsIHBpZSkgOiBzb3J0OwogICAgICB9OwoKICAgICAgcGllLnN0YXJ0QW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3RhcnRBbmdsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBwaWUpIDogc3RhcnRBbmdsZTsKICAgICAgfTsKCiAgICAgIHBpZS5lbmRBbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChlbmRBbmdsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoK18pLCBwaWUpIDogZW5kQW5nbGU7CiAgICAgIH07CgogICAgICBwaWUucGFkQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkQW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgcGllKSA6IHBhZEFuZ2xlOwogICAgICB9OwoKICAgICAgcmV0dXJuIHBpZTsKICAgIH0KCiAgICB2YXIgY3VydmVSYWRpYWxMaW5lYXIgPSBjdXJ2ZVJhZGlhbChjdXJ2ZUxpbmVhcik7CgogICAgZnVuY3Rpb24gUmFkaWFsKGN1cnZlKSB7CiAgICAgIHRoaXMuX2N1cnZlID0gY3VydmU7CiAgICB9CgogICAgUmFkaWFsLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9jdXJ2ZS5hcmVhU3RhcnQoKTsKICAgICAgfSwKICAgICAgYXJlYUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fY3VydmUuYXJlYUVuZCgpOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2N1cnZlLmxpbmVTdGFydCgpOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9jdXJ2ZS5saW5lRW5kKCk7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbihhLCByKSB7CiAgICAgICAgdGhpcy5fY3VydmUucG9pbnQociAqIE1hdGguc2luKGEpLCByICogLU1hdGguY29zKGEpKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjdXJ2ZVJhZGlhbChjdXJ2ZSkgewoKICAgICAgZnVuY3Rpb24gcmFkaWFsKGNvbnRleHQpIHsKICAgICAgICByZXR1cm4gbmV3IFJhZGlhbChjdXJ2ZShjb250ZXh0KSk7CiAgICAgIH0KCiAgICAgIHJhZGlhbC5fY3VydmUgPSBjdXJ2ZTsKCiAgICAgIHJldHVybiByYWRpYWw7CiAgICB9CgogICAgZnVuY3Rpb24gbGluZVJhZGlhbChsKSB7CiAgICAgIHZhciBjID0gbC5jdXJ2ZTsKCiAgICAgIGwuYW5nbGUgPSBsLngsIGRlbGV0ZSBsLng7CiAgICAgIGwucmFkaXVzID0gbC55LCBkZWxldGUgbC55OwoKICAgICAgbC5jdXJ2ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IGMoY3VydmVSYWRpYWwoXykpIDogYygpLl9jdXJ2ZTsKICAgICAgfTsKCiAgICAgIHJldHVybiBsOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVSYWRpYWwkMSgpIHsKICAgICAgcmV0dXJuIGxpbmVSYWRpYWwobGluZSgpLmN1cnZlKGN1cnZlUmFkaWFsTGluZWFyKSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJlYVJhZGlhbCgpIHsKICAgICAgdmFyIGEgPSBhcmVhJDMoKS5jdXJ2ZShjdXJ2ZVJhZGlhbExpbmVhciksCiAgICAgICAgICBjID0gYS5jdXJ2ZSwKICAgICAgICAgIHgwID0gYS5saW5lWDAsCiAgICAgICAgICB4MSA9IGEubGluZVgxLAogICAgICAgICAgeTAgPSBhLmxpbmVZMCwKICAgICAgICAgIHkxID0gYS5saW5lWTE7CgogICAgICBhLmFuZ2xlID0gYS54LCBkZWxldGUgYS54OwogICAgICBhLnN0YXJ0QW5nbGUgPSBhLngwLCBkZWxldGUgYS54MDsKICAgICAgYS5lbmRBbmdsZSA9IGEueDEsIGRlbGV0ZSBhLngxOwogICAgICBhLnJhZGl1cyA9IGEueSwgZGVsZXRlIGEueTsKICAgICAgYS5pbm5lclJhZGl1cyA9IGEueTAsIGRlbGV0ZSBhLnkwOwogICAgICBhLm91dGVyUmFkaXVzID0gYS55MSwgZGVsZXRlIGEueTE7CiAgICAgIGEubGluZVN0YXJ0QW5nbGUgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwoeDAoKSk7IH0sIGRlbGV0ZSBhLmxpbmVYMDsKICAgICAgYS5saW5lRW5kQW5nbGUgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwoeDEoKSk7IH0sIGRlbGV0ZSBhLmxpbmVYMTsKICAgICAgYS5saW5lSW5uZXJSYWRpdXMgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwoeTAoKSk7IH0sIGRlbGV0ZSBhLmxpbmVZMDsKICAgICAgYS5saW5lT3V0ZXJSYWRpdXMgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwoeTEoKSk7IH0sIGRlbGV0ZSBhLmxpbmVZMTsKCiAgICAgIGEuY3VydmUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyBjKGN1cnZlUmFkaWFsKF8pKSA6IGMoKS5fY3VydmU7CiAgICAgIH07CgogICAgICByZXR1cm4gYTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb2ludFJhZGlhbCh4LCB5KSB7CiAgICAgIHJldHVybiBbKHkgPSAreSkgKiBNYXRoLmNvcyh4IC09IE1hdGguUEkgLyAyKSwgeSAqIE1hdGguc2luKHgpXTsKICAgIH0KCiAgICB2YXIgc2xpY2UkNiA9IEFycmF5LnByb3RvdHlwZS5zbGljZTsKCiAgICBmdW5jdGlvbiBsaW5rU291cmNlKGQpIHsKICAgICAgcmV0dXJuIGQuc291cmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmtUYXJnZXQoZCkgewogICAgICByZXR1cm4gZC50YXJnZXQ7CiAgICB9CgogICAgZnVuY3Rpb24gbGluayQyKGN1cnZlKSB7CiAgICAgIHZhciBzb3VyY2UgPSBsaW5rU291cmNlLAogICAgICAgICAgdGFyZ2V0ID0gbGlua1RhcmdldCwKICAgICAgICAgIHggPSB4JDMsCiAgICAgICAgICB5ID0geSQzLAogICAgICAgICAgY29udGV4dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBsaW5rKCkgewogICAgICAgIHZhciBidWZmZXIsIGFyZ3YgPSBzbGljZSQ2LmNhbGwoYXJndW1lbnRzKSwgcyA9IHNvdXJjZS5hcHBseSh0aGlzLCBhcmd2KSwgdCA9IHRhcmdldC5hcHBseSh0aGlzLCBhcmd2KTsKICAgICAgICBpZiAoIWNvbnRleHQpIGNvbnRleHQgPSBidWZmZXIgPSBwYXRoKCk7CiAgICAgICAgY3VydmUoY29udGV4dCwgK3guYXBwbHkodGhpcywgKGFyZ3ZbMF0gPSBzLCBhcmd2KSksICt5LmFwcGx5KHRoaXMsIGFyZ3YpLCAreC5hcHBseSh0aGlzLCAoYXJndlswXSA9IHQsIGFyZ3YpKSwgK3kuYXBwbHkodGhpcywgYXJndikpOwogICAgICAgIGlmIChidWZmZXIpIHJldHVybiBjb250ZXh0ID0gbnVsbCwgYnVmZmVyICsgIiIgfHwgbnVsbDsKICAgICAgfQoKICAgICAgbGluay5zb3VyY2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc291cmNlID0gXywgbGluaykgOiBzb3VyY2U7CiAgICAgIH07CgogICAgICBsaW5rLnRhcmdldCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0YXJnZXQgPSBfLCBsaW5rKSA6IHRhcmdldDsKICAgICAgfTsKCiAgICAgIGxpbmsueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIGxpbmspIDogeDsKICAgICAgfTsKCiAgICAgIGxpbmsueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIGxpbmspIDogeTsKICAgICAgfTsKCiAgICAgIGxpbmsuY29udGV4dCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICgoY29udGV4dCA9IF8gPT0gbnVsbCA/IG51bGwgOiBfKSwgbGluaykgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIGxpbms7CiAgICB9CgogICAgZnVuY3Rpb24gY3VydmVIb3Jpem9udGFsKGNvbnRleHQsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIGNvbnRleHQubW92ZVRvKHgwLCB5MCk7CiAgICAgIGNvbnRleHQuYmV6aWVyQ3VydmVUbyh4MCA9ICh4MCArIHgxKSAvIDIsIHkwLCB4MCwgeTEsIHgxLCB5MSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3VydmVWZXJ0aWNhbChjb250ZXh0LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICBjb250ZXh0Lm1vdmVUbyh4MCwgeTApOwogICAgICBjb250ZXh0LmJlemllckN1cnZlVG8oeDAsIHkwID0gKHkwICsgeTEpIC8gMiwgeDEsIHkwLCB4MSwgeTEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1cnZlUmFkaWFsJDEoY29udGV4dCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdmFyIHAwID0gcG9pbnRSYWRpYWwoeDAsIHkwKSwKICAgICAgICAgIHAxID0gcG9pbnRSYWRpYWwoeDAsIHkwID0gKHkwICsgeTEpIC8gMiksCiAgICAgICAgICBwMiA9IHBvaW50UmFkaWFsKHgxLCB5MCksCiAgICAgICAgICBwMyA9IHBvaW50UmFkaWFsKHgxLCB5MSk7CiAgICAgIGNvbnRleHQubW92ZVRvKHAwWzBdLCBwMFsxXSk7CiAgICAgIGNvbnRleHQuYmV6aWVyQ3VydmVUbyhwMVswXSwgcDFbMV0sIHAyWzBdLCBwMlsxXSwgcDNbMF0sIHAzWzFdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5rSG9yaXpvbnRhbCgpIHsKICAgICAgcmV0dXJuIGxpbmskMihjdXJ2ZUhvcml6b250YWwpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmtWZXJ0aWNhbCgpIHsKICAgICAgcmV0dXJuIGxpbmskMihjdXJ2ZVZlcnRpY2FsKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5rUmFkaWFsKCkgewogICAgICB2YXIgbCA9IGxpbmskMihjdXJ2ZVJhZGlhbCQxKTsKICAgICAgbC5hbmdsZSA9IGwueCwgZGVsZXRlIGwueDsKICAgICAgbC5yYWRpdXMgPSBsLnksIGRlbGV0ZSBsLnk7CiAgICAgIHJldHVybiBsOwogICAgfQoKICAgIHZhciBjaXJjbGUkMiA9IHsKICAgICAgZHJhdzogZnVuY3Rpb24oY29udGV4dCwgc2l6ZSkgewogICAgICAgIHZhciByID0gTWF0aC5zcXJ0KHNpemUgLyBwaSQ0KTsKICAgICAgICBjb250ZXh0Lm1vdmVUbyhyLCAwKTsKICAgICAgICBjb250ZXh0LmFyYygwLCAwLCByLCAwLCB0YXUkNCk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGNyb3NzJDIgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgciA9IE1hdGguc3FydChzaXplIC8gNSkgLyAyOwogICAgICAgIGNvbnRleHQubW92ZVRvKC0zICogciwgLXIpOwogICAgICAgIGNvbnRleHQubGluZVRvKC1yLCAtcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oLXIsIC0zICogcik7CiAgICAgICAgY29udGV4dC5saW5lVG8ociwgLTMgKiByKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhyLCAtcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oMyAqIHIsIC1yKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygzICogciwgcik7CiAgICAgICAgY29udGV4dC5saW5lVG8ociwgcik7CiAgICAgICAgY29udGV4dC5saW5lVG8ociwgMyAqIHIpOwogICAgICAgIGNvbnRleHQubGluZVRvKC1yLCAzICogcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oLXIsIHIpOwogICAgICAgIGNvbnRleHQubGluZVRvKC0zICogciwgcik7CiAgICAgICAgY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgdGFuMzAgPSBNYXRoLnNxcnQoMSAvIDMpLAogICAgICAgIHRhbjMwXzIgPSB0YW4zMCAqIDI7CgogICAgdmFyIGRpYW1vbmQgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgeSA9IE1hdGguc3FydChzaXplIC8gdGFuMzBfMiksCiAgICAgICAgICAgIHggPSB5ICogdGFuMzA7CiAgICAgICAgY29udGV4dC5tb3ZlVG8oMCwgLXkpOwogICAgICAgIGNvbnRleHQubGluZVRvKHgsIDApOwogICAgICAgIGNvbnRleHQubGluZVRvKDAsIHkpOwogICAgICAgIGNvbnRleHQubGluZVRvKC14LCAwKTsKICAgICAgICBjb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICB9CiAgICB9OwoKICAgIHZhciBrYSA9IDAuODkwODEzMDkxNTI5Mjg1MjI4MTAsCiAgICAgICAga3IgPSBNYXRoLnNpbihwaSQ0IC8gMTApIC8gTWF0aC5zaW4oNyAqIHBpJDQgLyAxMCksCiAgICAgICAga3ggPSBNYXRoLnNpbih0YXUkNCAvIDEwKSAqIGtyLAogICAgICAgIGt5ID0gLU1hdGguY29zKHRhdSQ0IC8gMTApICoga3I7CgogICAgdmFyIHN0YXIgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgciA9IE1hdGguc3FydChzaXplICoga2EpLAogICAgICAgICAgICB4ID0ga3ggKiByLAogICAgICAgICAgICB5ID0ga3kgKiByOwogICAgICAgIGNvbnRleHQubW92ZVRvKDAsIC1yKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICBmb3IgKHZhciBpID0gMTsgaSA8IDU7ICsraSkgewogICAgICAgICAgdmFyIGEgPSB0YXUkNCAqIGkgLyA1LAogICAgICAgICAgICAgIGMgPSBNYXRoLmNvcyhhKSwKICAgICAgICAgICAgICBzID0gTWF0aC5zaW4oYSk7CiAgICAgICAgICBjb250ZXh0LmxpbmVUbyhzICogciwgLWMgKiByKTsKICAgICAgICAgIGNvbnRleHQubGluZVRvKGMgKiB4IC0gcyAqIHksIHMgKiB4ICsgYyAqIHkpOwogICAgICAgIH0KICAgICAgICBjb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICB9CiAgICB9OwoKICAgIHZhciBzcXVhcmUgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgdyA9IE1hdGguc3FydChzaXplKSwKICAgICAgICAgICAgeCA9IC13IC8gMjsKICAgICAgICBjb250ZXh0LnJlY3QoeCwgeCwgdywgdyk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIHNxcnQzID0gTWF0aC5zcXJ0KDMpOwoKICAgIHZhciB0cmlhbmdsZSA9IHsKICAgICAgZHJhdzogZnVuY3Rpb24oY29udGV4dCwgc2l6ZSkgewogICAgICAgIHZhciB5ID0gLU1hdGguc3FydChzaXplIC8gKHNxcnQzICogMykpOwogICAgICAgIGNvbnRleHQubW92ZVRvKDAsIHkgKiAyKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygtc3FydDMgKiB5LCAteSk7CiAgICAgICAgY29udGV4dC5saW5lVG8oc3FydDMgKiB5LCAteSk7CiAgICAgICAgY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgYyQyID0gLTAuNSwKICAgICAgICBzID0gTWF0aC5zcXJ0KDMpIC8gMiwKICAgICAgICBrID0gMSAvIE1hdGguc3FydCgxMiksCiAgICAgICAgYSA9IChrIC8gMiArIDEpICogMzsKCiAgICB2YXIgd3llID0gewogICAgICBkcmF3OiBmdW5jdGlvbihjb250ZXh0LCBzaXplKSB7CiAgICAgICAgdmFyIHIgPSBNYXRoLnNxcnQoc2l6ZSAvIGEpLAogICAgICAgICAgICB4MCA9IHIgLyAyLAogICAgICAgICAgICB5MCA9IHIgKiBrLAogICAgICAgICAgICB4MSA9IHgwLAogICAgICAgICAgICB5MSA9IHIgKiBrICsgciwKICAgICAgICAgICAgeDIgPSAteDEsCiAgICAgICAgICAgIHkyID0geTE7CiAgICAgICAgY29udGV4dC5tb3ZlVG8oeDAsIHkwKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyh4MSwgeTEpOwogICAgICAgIGNvbnRleHQubGluZVRvKHgyLCB5Mik7CiAgICAgICAgY29udGV4dC5saW5lVG8oYyQyICogeDAgLSBzICogeTAsIHMgKiB4MCArIGMkMiAqIHkwKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDIgKiB4MSAtIHMgKiB5MSwgcyAqIHgxICsgYyQyICogeTEpOwogICAgICAgIGNvbnRleHQubGluZVRvKGMkMiAqIHgyIC0gcyAqIHkyLCBzICogeDIgKyBjJDIgKiB5Mik7CiAgICAgICAgY29udGV4dC5saW5lVG8oYyQyICogeDAgKyBzICogeTAsIGMkMiAqIHkwIC0gcyAqIHgwKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDIgKiB4MSArIHMgKiB5MSwgYyQyICogeTEgLSBzICogeDEpOwogICAgICAgIGNvbnRleHQubGluZVRvKGMkMiAqIHgyICsgcyAqIHkyLCBjJDIgKiB5MiAtIHMgKiB4Mik7CiAgICAgICAgY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgc3ltYm9scyA9IFsKICAgICAgY2lyY2xlJDIsCiAgICAgIGNyb3NzJDIsCiAgICAgIGRpYW1vbmQsCiAgICAgIHNxdWFyZSwKICAgICAgc3RhciwKICAgICAgdHJpYW5nbGUsCiAgICAgIHd5ZQogICAgXTsKCiAgICBmdW5jdGlvbiBzeW1ib2woKSB7CiAgICAgIHZhciB0eXBlID0gY29uc3RhbnQkYihjaXJjbGUkMiksCiAgICAgICAgICBzaXplID0gY29uc3RhbnQkYig2NCksCiAgICAgICAgICBjb250ZXh0ID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIHN5bWJvbCgpIHsKICAgICAgICB2YXIgYnVmZmVyOwogICAgICAgIGlmICghY29udGV4dCkgY29udGV4dCA9IGJ1ZmZlciA9IHBhdGgoKTsKICAgICAgICB0eXBlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykuZHJhdyhjb250ZXh0LCArc2l6ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgICBpZiAoYnVmZmVyKSByZXR1cm4gY29udGV4dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIHN5bWJvbC50eXBlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHR5cGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKF8pLCBzeW1ib2wpIDogdHlwZTsKICAgICAgfTsKCiAgICAgIHN5bWJvbC5zaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNpemUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKCtfKSwgc3ltYm9sKSA6IHNpemU7CiAgICAgIH07CgogICAgICBzeW1ib2wuY29udGV4dCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjb250ZXh0ID0gXyA9PSBudWxsID8gbnVsbCA6IF8sIHN5bWJvbCkgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIHN5bWJvbDsKICAgIH0KCiAgICBmdW5jdGlvbiBub29wJDMoKSB7fQoKICAgIGZ1bmN0aW9uIHBvaW50JDIodGhhdCwgeCwgeSkgewogICAgICB0aGF0Ll9jb250ZXh0LmJlemllckN1cnZlVG8oCiAgICAgICAgKDIgKiB0aGF0Ll94MCArIHRoYXQuX3gxKSAvIDMsCiAgICAgICAgKDIgKiB0aGF0Ll95MCArIHRoYXQuX3kxKSAvIDMsCiAgICAgICAgKHRoYXQuX3gwICsgMiAqIHRoYXQuX3gxKSAvIDMsCiAgICAgICAgKHRoYXQuX3kwICsgMiAqIHRoYXQuX3kxKSAvIDMsCiAgICAgICAgKHRoYXQuX3gwICsgNCAqIHRoYXQuX3gxICsgeCkgLyA2LAogICAgICAgICh0aGF0Ll95MCArIDQgKiB0aGF0Ll95MSArIHkpIC8gNgogICAgICApOwogICAgfQoKICAgIGZ1bmN0aW9uIEJhc2lzKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgQmFzaXMucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDM6IHBvaW50JDIodGhpcywgdGhpcy5feDEsIHRoaXMuX3kxKTsgLy8gcHJvY2VlZAogICAgICAgICAgY2FzZSAyOiB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94MSwgdGhpcy5feTEpOyBicmVhazsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgfHwgKHRoaXMuX2xpbmUgIT09IDAgJiYgdGhpcy5fcG9pbnQgPT09IDEpKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX2xpbmUgPSAxIC0gdGhpcy5fbGluZTsKICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHRoaXMuX2NvbnRleHQubGluZVRvKCg1ICogdGhpcy5feDAgKyB0aGlzLl94MSkgLyA2LCAoNSAqIHRoaXMuX3kwICsgdGhpcy5feTEpIC8gNik7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JDIodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB5OwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGJhc2lzJDIoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IEJhc2lzKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIEJhc2lzQ2xvc2VkKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgQmFzaXNDbG9zZWQucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IG5vb3AkMywKICAgICAgYXJlYUVuZDogbm9vcCQzLAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPSB0aGlzLl94MiA9IHRoaXMuX3gzID0gdGhpcy5feDQgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPSB0aGlzLl95MiA9IHRoaXMuX3kzID0gdGhpcy5feTQgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDIsIHRoaXMuX3kyKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDI6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5tb3ZlVG8oKHRoaXMuX3gyICsgMiAqIHRoaXMuX3gzKSAvIDMsICh0aGlzLl95MiArIDIgKiB0aGlzLl95MykgLyAzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5saW5lVG8oKHRoaXMuX3gzICsgMiAqIHRoaXMuX3gyKSAvIDMsICh0aGlzLl95MyArIDIgKiB0aGlzLl95MikgLyAzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDM6IHsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94MiwgdGhpcy5feTIpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3gzLCB0aGlzLl95Myk7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDQsIHRoaXMuX3k0KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl94MiA9IHgsIHRoaXMuX3kyID0geTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgdGhpcy5feDMgPSB4LCB0aGlzLl95MyA9IHk7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHRoaXMuX3g0ID0geCwgdGhpcy5feTQgPSB5OyB0aGlzLl9jb250ZXh0Lm1vdmVUbygodGhpcy5feDAgKyA0ICogdGhpcy5feDEgKyB4KSAvIDYsICh0aGlzLl95MCArIDQgKiB0aGlzLl95MSArIHkpIC8gNik7IGJyZWFrOwogICAgICAgICAgZGVmYXVsdDogcG9pbnQkMih0aGlzLCB4LCB5KTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEsIHRoaXMuX3gxID0geDsKICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxLCB0aGlzLl95MSA9IHk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYmFzaXNDbG9zZWQkMShjb250ZXh0KSB7CiAgICAgIHJldHVybiBuZXcgQmFzaXNDbG9zZWQoY29udGV4dCk7CiAgICB9CgogICAgZnVuY3Rpb24gQmFzaXNPcGVuKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgQmFzaXNPcGVuLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgYXJlYUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgfHwgKHRoaXMuX2xpbmUgIT09IDAgJiYgdGhpcy5fcG9pbnQgPT09IDMpKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX2xpbmUgPSAxIC0gdGhpcy5fbGluZTsKICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgYnJlYWs7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX3BvaW50ID0gMzsgdmFyIHgwID0gKHRoaXMuX3gwICsgNCAqIHRoaXMuX3gxICsgeCkgLyA2LCB5MCA9ICh0aGlzLl95MCArIDQgKiB0aGlzLl95MSArIHkpIC8gNjsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgwLCB5MCkgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4MCwgeTApOyBicmVhazsKICAgICAgICAgIGNhc2UgMzogdGhpcy5fcG9pbnQgPSA0OyAvLyBwcm9jZWVkCiAgICAgICAgICBkZWZhdWx0OiBwb2ludCQyKHRoaXMsIHgsIHkpOyBicmVhazsKICAgICAgICB9CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSwgdGhpcy5feDEgPSB4OwogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEsIHRoaXMuX3kxID0geTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBiYXNpc09wZW4oY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IEJhc2lzT3Blbihjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBCdW5kbGUoY29udGV4dCwgYmV0YSkgewogICAgICB0aGlzLl9iYXNpcyA9IG5ldyBCYXNpcyhjb250ZXh0KTsKICAgICAgdGhpcy5fYmV0YSA9IGJldGE7CiAgICB9CgogICAgQnVuZGxlLnByb3RvdHlwZSA9IHsKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94ID0gW107CiAgICAgICAgdGhpcy5feSA9IFtdOwogICAgICAgIHRoaXMuX2Jhc2lzLmxpbmVTdGFydCgpOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgeCA9IHRoaXMuX3gsCiAgICAgICAgICAgIHkgPSB0aGlzLl95LAogICAgICAgICAgICBqID0geC5sZW5ndGggLSAxOwoKICAgICAgICBpZiAoaiA+IDApIHsKICAgICAgICAgIHZhciB4MCA9IHhbMF0sCiAgICAgICAgICAgICAgeTAgPSB5WzBdLAogICAgICAgICAgICAgIGR4ID0geFtqXSAtIHgwLAogICAgICAgICAgICAgIGR5ID0geVtqXSAtIHkwLAogICAgICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgICAgICB0OwoKICAgICAgICAgIHdoaWxlICgrK2kgPD0gaikgewogICAgICAgICAgICB0ID0gaSAvIGo7CiAgICAgICAgICAgIHRoaXMuX2Jhc2lzLnBvaW50KAogICAgICAgICAgICAgIHRoaXMuX2JldGEgKiB4W2ldICsgKDEgLSB0aGlzLl9iZXRhKSAqICh4MCArIHQgKiBkeCksCiAgICAgICAgICAgICAgdGhpcy5fYmV0YSAqIHlbaV0gKyAoMSAtIHRoaXMuX2JldGEpICogKHkwICsgdCAqIGR5KQogICAgICAgICAgICApOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5feCA9IHRoaXMuX3kgPSBudWxsOwogICAgICAgIHRoaXMuX2Jhc2lzLmxpbmVFbmQoKTsKICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB0aGlzLl94LnB1c2goK3gpOwogICAgICAgIHRoaXMuX3kucHVzaCgreSk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGJ1bmRsZSA9IChmdW5jdGlvbiBjdXN0b20oYmV0YSkgewoKICAgICAgZnVuY3Rpb24gYnVuZGxlKGNvbnRleHQpIHsKICAgICAgICByZXR1cm4gYmV0YSA9PT0gMSA/IG5ldyBCYXNpcyhjb250ZXh0KSA6IG5ldyBCdW5kbGUoY29udGV4dCwgYmV0YSk7CiAgICAgIH0KCiAgICAgIGJ1bmRsZS5iZXRhID0gZnVuY3Rpb24oYmV0YSkgewogICAgICAgIHJldHVybiBjdXN0b20oK2JldGEpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGJ1bmRsZTsKICAgIH0pKDAuODUpOwoKICAgIGZ1bmN0aW9uIHBvaW50JDModGhhdCwgeCwgeSkgewogICAgICB0aGF0Ll9jb250ZXh0LmJlemllckN1cnZlVG8oCiAgICAgICAgdGhhdC5feDEgKyB0aGF0Ll9rICogKHRoYXQuX3gyIC0gdGhhdC5feDApLAogICAgICAgIHRoYXQuX3kxICsgdGhhdC5fayAqICh0aGF0Ll95MiAtIHRoYXQuX3kwKSwKICAgICAgICB0aGF0Ll94MiArIHRoYXQuX2sgKiAodGhhdC5feDEgLSB4KSwKICAgICAgICB0aGF0Ll95MiArIHRoYXQuX2sgKiAodGhhdC5feTEgLSB5KSwKICAgICAgICB0aGF0Ll94MiwKICAgICAgICB0aGF0Ll95MgogICAgICApOwogICAgfQoKICAgIGZ1bmN0aW9uIENhcmRpbmFsKGNvbnRleHQsIHRlbnNpb24pIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICAgIHRoaXMuX2sgPSAoMSAtIHRlbnNpb24pIC8gNjsKICAgIH0KCiAgICBDYXJkaW5hbC5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX2NvbnRleHQubGluZVRvKHRoaXMuX3gyLCB0aGlzLl95Mik7IGJyZWFrOwogICAgICAgICAgY2FzZSAzOiBwb2ludCQzKHRoaXMsIHRoaXMuX3gxLCB0aGlzLl95MSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fbGluZSA9IDEgLSB0aGlzLl9saW5lOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8oeCwgeSkgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4LCB5KTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgdGhpcy5feDEgPSB4LCB0aGlzLl95MSA9IHk7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JDModGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXJkaW5hbCA9IChmdW5jdGlvbiBjdXN0b20odGVuc2lvbikgewoKICAgICAgZnVuY3Rpb24gY2FyZGluYWwoY29udGV4dCkgewogICAgICAgIHJldHVybiBuZXcgQ2FyZGluYWwoY29udGV4dCwgdGVuc2lvbik7CiAgICAgIH0KCiAgICAgIGNhcmRpbmFsLnRlbnNpb24gPSBmdW5jdGlvbih0ZW5zaW9uKSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgrdGVuc2lvbik7CiAgICAgIH07CgogICAgICByZXR1cm4gY2FyZGluYWw7CiAgICB9KSgwKTsKCiAgICBmdW5jdGlvbiBDYXJkaW5hbENsb3NlZChjb250ZXh0LCB0ZW5zaW9uKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9rID0gKDEgLSB0ZW5zaW9uKSAvIDY7CiAgICB9CgogICAgQ2FyZGluYWxDbG9zZWQucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IG5vb3AkMywKICAgICAgYXJlYUVuZDogbm9vcCQzLAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPSB0aGlzLl94MiA9IHRoaXMuX3gzID0gdGhpcy5feDQgPSB0aGlzLl94NSA9CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSA9IHRoaXMuX3kyID0gdGhpcy5feTMgPSB0aGlzLl95NCA9IHRoaXMuX3k1ID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAxOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3gzLCB0aGlzLl95Myk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAyOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKHRoaXMuX3gzLCB0aGlzLl95Myk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAzOiB7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94NCwgdGhpcy5feTQpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3g1LCB0aGlzLl95NSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5feDMgPSB4LCB0aGlzLl95MyA9IHk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3g0ID0geCwgdGhpcy5feTQgPSB5KTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX3BvaW50ID0gMzsgdGhpcy5feDUgPSB4LCB0aGlzLl95NSA9IHk7IGJyZWFrOwogICAgICAgICAgZGVmYXVsdDogcG9pbnQkMyh0aGlzLCB4LCB5KTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEsIHRoaXMuX3gxID0gdGhpcy5feDIsIHRoaXMuX3gyID0geDsKICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxLCB0aGlzLl95MSA9IHRoaXMuX3kyLCB0aGlzLl95MiA9IHk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGNhcmRpbmFsQ2xvc2VkID0gKGZ1bmN0aW9uIGN1c3RvbSh0ZW5zaW9uKSB7CgogICAgICBmdW5jdGlvbiBjYXJkaW5hbChjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIG5ldyBDYXJkaW5hbENsb3NlZChjb250ZXh0LCB0ZW5zaW9uKTsKICAgICAgfQoKICAgICAgY2FyZGluYWwudGVuc2lvbiA9IGZ1bmN0aW9uKHRlbnNpb24pIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCt0ZW5zaW9uKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBjYXJkaW5hbDsKICAgIH0pKDApOwoKICAgIGZ1bmN0aW9uIENhcmRpbmFsT3Blbihjb250ZXh0LCB0ZW5zaW9uKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9rID0gKDEgLSB0ZW5zaW9uKSAvIDY7CiAgICB9CgogICAgQ2FyZGluYWxPcGVuLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgYXJlYUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxID0gdGhpcy5feDIgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPSB0aGlzLl95MiA9IE5hTjsKICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAzKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94MiwgdGhpcy5feTIpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDIsIHRoaXMuX3kyKTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDM6IHRoaXMuX3BvaW50ID0gNDsgLy8gcHJvY2VlZAogICAgICAgICAgZGVmYXVsdDogcG9pbnQkMyh0aGlzLCB4LCB5KTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEsIHRoaXMuX3gxID0gdGhpcy5feDIsIHRoaXMuX3gyID0geDsKICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxLCB0aGlzLl95MSA9IHRoaXMuX3kyLCB0aGlzLl95MiA9IHk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGNhcmRpbmFsT3BlbiA9IChmdW5jdGlvbiBjdXN0b20odGVuc2lvbikgewoKICAgICAgZnVuY3Rpb24gY2FyZGluYWwoY29udGV4dCkgewogICAgICAgIHJldHVybiBuZXcgQ2FyZGluYWxPcGVuKGNvbnRleHQsIHRlbnNpb24pOwogICAgICB9CgogICAgICBjYXJkaW5hbC50ZW5zaW9uID0gZnVuY3Rpb24odGVuc2lvbikgewogICAgICAgIHJldHVybiBjdXN0b20oK3RlbnNpb24pOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNhcmRpbmFsOwogICAgfSkoMCk7CgogICAgZnVuY3Rpb24gcG9pbnQkNCh0aGF0LCB4LCB5KSB7CiAgICAgIHZhciB4MSA9IHRoYXQuX3gxLAogICAgICAgICAgeTEgPSB0aGF0Ll95MSwKICAgICAgICAgIHgyID0gdGhhdC5feDIsCiAgICAgICAgICB5MiA9IHRoYXQuX3kyOwoKICAgICAgaWYgKHRoYXQuX2wwMV9hID4gZXBzaWxvbiQzKSB7CiAgICAgICAgdmFyIGEgPSAyICogdGhhdC5fbDAxXzJhICsgMyAqIHRoYXQuX2wwMV9hICogdGhhdC5fbDEyX2EgKyB0aGF0Ll9sMTJfMmEsCiAgICAgICAgICAgIG4gPSAzICogdGhhdC5fbDAxX2EgKiAodGhhdC5fbDAxX2EgKyB0aGF0Ll9sMTJfYSk7CiAgICAgICAgeDEgPSAoeDEgKiBhIC0gdGhhdC5feDAgKiB0aGF0Ll9sMTJfMmEgKyB0aGF0Ll94MiAqIHRoYXQuX2wwMV8yYSkgLyBuOwogICAgICAgIHkxID0gKHkxICogYSAtIHRoYXQuX3kwICogdGhhdC5fbDEyXzJhICsgdGhhdC5feTIgKiB0aGF0Ll9sMDFfMmEpIC8gbjsKICAgICAgfQoKICAgICAgaWYgKHRoYXQuX2wyM19hID4gZXBzaWxvbiQzKSB7CiAgICAgICAgdmFyIGIgPSAyICogdGhhdC5fbDIzXzJhICsgMyAqIHRoYXQuX2wyM19hICogdGhhdC5fbDEyX2EgKyB0aGF0Ll9sMTJfMmEsCiAgICAgICAgICAgIG0gPSAzICogdGhhdC5fbDIzX2EgKiAodGhhdC5fbDIzX2EgKyB0aGF0Ll9sMTJfYSk7CiAgICAgICAgeDIgPSAoeDIgKiBiICsgdGhhdC5feDEgKiB0aGF0Ll9sMjNfMmEgLSB4ICogdGhhdC5fbDEyXzJhKSAvIG07CiAgICAgICAgeTIgPSAoeTIgKiBiICsgdGhhdC5feTEgKiB0aGF0Ll9sMjNfMmEgLSB5ICogdGhhdC5fbDEyXzJhKSAvIG07CiAgICAgIH0KCiAgICAgIHRoYXQuX2NvbnRleHQuYmV6aWVyQ3VydmVUbyh4MSwgeTEsIHgyLCB5MiwgdGhhdC5feDIsIHRoYXQuX3kyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBDYXRtdWxsUm9tKGNvbnRleHQsIGFscGhhKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9hbHBoYSA9IGFscGhhOwogICAgfQoKICAgIENhdG11bGxSb20ucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPSB0aGlzLl94MiA9CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSA9IHRoaXMuX3kyID0gTmFOOwogICAgICAgIHRoaXMuX2wwMV9hID0gdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYSA9CiAgICAgICAgdGhpcy5fbDAxXzJhID0gdGhpcy5fbDEyXzJhID0gdGhpcy5fbDIzXzJhID0KICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDIsIHRoaXMuX3kyKTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDM6IHRoaXMucG9pbnQodGhpcy5feDIsIHRoaXMuX3kyKTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAxKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CgogICAgICAgIGlmICh0aGlzLl9wb2ludCkgewogICAgICAgICAgdmFyIHgyMyA9IHRoaXMuX3gyIC0geCwKICAgICAgICAgICAgICB5MjMgPSB0aGlzLl95MiAtIHk7CiAgICAgICAgICB0aGlzLl9sMjNfYSA9IE1hdGguc3FydCh0aGlzLl9sMjNfMmEgPSBNYXRoLnBvdyh4MjMgKiB4MjMgKyB5MjMgKiB5MjMsIHRoaXMuX2FscGhhKSk7CiAgICAgICAgfQoKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JDQodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSwgdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYTsKICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEsIHRoaXMuX2wxMl8yYSA9IHRoaXMuX2wyM18yYTsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXRtdWxsUm9tID0gKGZ1bmN0aW9uIGN1c3RvbShhbHBoYSkgewoKICAgICAgZnVuY3Rpb24gY2F0bXVsbFJvbShjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIGFscGhhID8gbmV3IENhdG11bGxSb20oY29udGV4dCwgYWxwaGEpIDogbmV3IENhcmRpbmFsKGNvbnRleHQsIDApOwogICAgICB9CgogICAgICBjYXRtdWxsUm9tLmFscGhhID0gZnVuY3Rpb24oYWxwaGEpIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCthbHBoYSk7CiAgICAgIH07CgogICAgICByZXR1cm4gY2F0bXVsbFJvbTsKICAgIH0pKDAuNSk7CgogICAgZnVuY3Rpb24gQ2F0bXVsbFJvbUNsb3NlZChjb250ZXh0LCBhbHBoYSkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgICAgdGhpcy5fYWxwaGEgPSBhbHBoYTsKICAgIH0KCiAgICBDYXRtdWxsUm9tQ2xvc2VkLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBub29wJDMsCiAgICAgIGFyZWFFbmQ6IG5vb3AkMywKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxID0gdGhpcy5feDIgPSB0aGlzLl94MyA9IHRoaXMuX3g0ID0gdGhpcy5feDUgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPSB0aGlzLl95MiA9IHRoaXMuX3kzID0gdGhpcy5feTQgPSB0aGlzLl95NSA9IE5hTjsKICAgICAgICB0aGlzLl9sMDFfYSA9IHRoaXMuX2wxMl9hID0gdGhpcy5fbDIzX2EgPQogICAgICAgIHRoaXMuX2wwMV8yYSA9IHRoaXMuX2wxMl8yYSA9IHRoaXMuX2wyM18yYSA9CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDI6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDM6IHsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94MywgdGhpcy5feTMpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3g0LCB0aGlzLl95NCk7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDUsIHRoaXMuX3k1KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwoKICAgICAgICBpZiAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIHZhciB4MjMgPSB0aGlzLl94MiAtIHgsCiAgICAgICAgICAgICAgeTIzID0gdGhpcy5feTIgLSB5OwogICAgICAgICAgdGhpcy5fbDIzX2EgPSBNYXRoLnNxcnQodGhpcy5fbDIzXzJhID0gTWF0aC5wb3coeDIzICogeDIzICsgeTIzICogeTIzLCB0aGlzLl9hbHBoYSkpOwogICAgICAgIH0KCiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IHRoaXMuX3gzID0geCwgdGhpcy5feTMgPSB5OyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyB0aGlzLl9jb250ZXh0Lm1vdmVUbyh0aGlzLl94NCA9IHgsIHRoaXMuX3k0ID0geSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHRoaXMuX3g1ID0geCwgdGhpcy5feTUgPSB5OyBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JDQodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSwgdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYTsKICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEsIHRoaXMuX2wxMl8yYSA9IHRoaXMuX2wyM18yYTsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXRtdWxsUm9tQ2xvc2VkID0gKGZ1bmN0aW9uIGN1c3RvbShhbHBoYSkgewoKICAgICAgZnVuY3Rpb24gY2F0bXVsbFJvbShjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIGFscGhhID8gbmV3IENhdG11bGxSb21DbG9zZWQoY29udGV4dCwgYWxwaGEpIDogbmV3IENhcmRpbmFsQ2xvc2VkKGNvbnRleHQsIDApOwogICAgICB9CgogICAgICBjYXRtdWxsUm9tLmFscGhhID0gZnVuY3Rpb24oYWxwaGEpIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCthbHBoYSk7CiAgICAgIH07CgogICAgICByZXR1cm4gY2F0bXVsbFJvbTsKICAgIH0pKDAuNSk7CgogICAgZnVuY3Rpb24gQ2F0bXVsbFJvbU9wZW4oY29udGV4dCwgYWxwaGEpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICAgIHRoaXMuX2FscGhhID0gYWxwaGE7CiAgICB9CgogICAgQ2F0bXVsbFJvbU9wZW4ucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPSB0aGlzLl94MiA9CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSA9IHRoaXMuX3kyID0gTmFOOwogICAgICAgIHRoaXMuX2wwMV9hID0gdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYSA9CiAgICAgICAgdGhpcy5fbDAxXzJhID0gdGhpcy5fbDEyXzJhID0gdGhpcy5fbDIzXzJhID0KICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAzKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CgogICAgICAgIGlmICh0aGlzLl9wb2ludCkgewogICAgICAgICAgdmFyIHgyMyA9IHRoaXMuX3gyIC0geCwKICAgICAgICAgICAgICB5MjMgPSB0aGlzLl95MiAtIHk7CiAgICAgICAgICB0aGlzLl9sMjNfYSA9IE1hdGguc3FydCh0aGlzLl9sMjNfMmEgPSBNYXRoLnBvdyh4MjMgKiB4MjMgKyB5MjMgKiB5MjMsIHRoaXMuX2FscGhhKSk7CiAgICAgICAgfQoKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgYnJlYWs7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX3BvaW50ID0gMzsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHRoaXMuX3gyLCB0aGlzLl95MikgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh0aGlzLl94MiwgdGhpcy5feTIpOyBicmVhazsKICAgICAgICAgIGNhc2UgMzogdGhpcy5fcG9pbnQgPSA0OyAvLyBwcm9jZWVkCiAgICAgICAgICBkZWZhdWx0OiBwb2ludCQ0KHRoaXMsIHgsIHkpOyBicmVhazsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2wwMV9hID0gdGhpcy5fbDEyX2EsIHRoaXMuX2wxMl9hID0gdGhpcy5fbDIzX2E7CiAgICAgICAgdGhpcy5fbDAxXzJhID0gdGhpcy5fbDEyXzJhLCB0aGlzLl9sMTJfMmEgPSB0aGlzLl9sMjNfMmE7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSwgdGhpcy5feDEgPSB0aGlzLl94MiwgdGhpcy5feDIgPSB4OwogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEsIHRoaXMuX3kxID0gdGhpcy5feTIsIHRoaXMuX3kyID0geTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgY2F0bXVsbFJvbU9wZW4gPSAoZnVuY3Rpb24gY3VzdG9tKGFscGhhKSB7CgogICAgICBmdW5jdGlvbiBjYXRtdWxsUm9tKGNvbnRleHQpIHsKICAgICAgICByZXR1cm4gYWxwaGEgPyBuZXcgQ2F0bXVsbFJvbU9wZW4oY29udGV4dCwgYWxwaGEpIDogbmV3IENhcmRpbmFsT3Blbihjb250ZXh0LCAwKTsKICAgICAgfQoKICAgICAgY2F0bXVsbFJvbS5hbHBoYSA9IGZ1bmN0aW9uKGFscGhhKSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgrYWxwaGEpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNhdG11bGxSb207CiAgICB9KSgwLjUpOwoKICAgIGZ1bmN0aW9uIExpbmVhckNsb3NlZChjb250ZXh0KSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgfQoKICAgIExpbmVhckNsb3NlZC5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogbm9vcCQzLAogICAgICBhcmVhRW5kOiBub29wJDMsCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fcG9pbnQpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgaWYgKHRoaXMuX3BvaW50KSB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICBlbHNlIHRoaXMuX3BvaW50ID0gMSwgdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gbGluZWFyQ2xvc2VkKGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBMaW5lYXJDbG9zZWQoY29udGV4dCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2lnbiQxKHgpIHsKICAgICAgcmV0dXJuIHggPCAwID8gLTEgOiAxOwogICAgfQoKICAgIC8vIENhbGN1bGF0ZSB0aGUgc2xvcGVzIG9mIHRoZSB0YW5nZW50cyAoSGVybWl0ZS10eXBlIGludGVycG9sYXRpb24pIGJhc2VkIG9uCiAgICAvLyB0aGUgZm9sbG93aW5nIHBhcGVyOiBTdGVmZmVuLCBNLiAxOTkwLiBBIFNpbXBsZSBNZXRob2QgZm9yIE1vbm90b25pYwogICAgLy8gSW50ZXJwb2xhdGlvbiBpbiBPbmUgRGltZW5zaW9uLiBBc3Ryb25vbXkgYW5kIEFzdHJvcGh5c2ljcywgVm9sLiAyMzksIE5PLgogICAgLy8gTk9WKElJKSwgUC4gNDQzLCAxOTkwLgogICAgZnVuY3Rpb24gc2xvcGUzKHRoYXQsIHgyLCB5MikgewogICAgICB2YXIgaDAgPSB0aGF0Ll94MSAtIHRoYXQuX3gwLAogICAgICAgICAgaDEgPSB4MiAtIHRoYXQuX3gxLAogICAgICAgICAgczAgPSAodGhhdC5feTEgLSB0aGF0Ll95MCkgLyAoaDAgfHwgaDEgPCAwICYmIC0wKSwKICAgICAgICAgIHMxID0gKHkyIC0gdGhhdC5feTEpIC8gKGgxIHx8IGgwIDwgMCAmJiAtMCksCiAgICAgICAgICBwID0gKHMwICogaDEgKyBzMSAqIGgwKSAvIChoMCArIGgxKTsKICAgICAgcmV0dXJuIChzaWduJDEoczApICsgc2lnbiQxKHMxKSkgKiBNYXRoLm1pbihNYXRoLmFicyhzMCksIE1hdGguYWJzKHMxKSwgMC41ICogTWF0aC5hYnMocCkpIHx8IDA7CiAgICB9CgogICAgLy8gQ2FsY3VsYXRlIGEgb25lLXNpZGVkIHNsb3BlLgogICAgZnVuY3Rpb24gc2xvcGUyKHRoYXQsIHQpIHsKICAgICAgdmFyIGggPSB0aGF0Ll94MSAtIHRoYXQuX3gwOwogICAgICByZXR1cm4gaCA/ICgzICogKHRoYXQuX3kxIC0gdGhhdC5feTApIC8gaCAtIHQpIC8gMiA6IHQ7CiAgICB9CgogICAgLy8gQWNjb3JkaW5nIHRvIGh0dHBzOi8vZW4ud2lraXBlZGlhLm9yZy93aWtpL0N1YmljX0hlcm1pdGVfc3BsaW5lI1JlcHJlc2VudGF0aW9ucwogICAgLy8gInlvdSBjYW4gZXhwcmVzcyBjdWJpYyBIZXJtaXRlIGludGVycG9sYXRpb24gaW4gdGVybXMgb2YgY3ViaWMgQsOpemllciBjdXJ2ZXMKICAgIC8vIHdpdGggcmVzcGVjdCB0byB0aGUgZm91ciB2YWx1ZXMgcDAsIHAwICsgbTAgLyAzLCBwMSAtIG0xIC8gMywgcDEiLgogICAgZnVuY3Rpb24gcG9pbnQkNSh0aGF0LCB0MCwgdDEpIHsKICAgICAgdmFyIHgwID0gdGhhdC5feDAsCiAgICAgICAgICB5MCA9IHRoYXQuX3kwLAogICAgICAgICAgeDEgPSB0aGF0Ll94MSwKICAgICAgICAgIHkxID0gdGhhdC5feTEsCiAgICAgICAgICBkeCA9ICh4MSAtIHgwKSAvIDM7CiAgICAgIHRoYXQuX2NvbnRleHQuYmV6aWVyQ3VydmVUbyh4MCArIGR4LCB5MCArIGR4ICogdDAsIHgxIC0gZHgsIHkxIC0gZHggKiB0MSwgeDEsIHkxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBNb25vdG9uZVgoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBNb25vdG9uZVgucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPQogICAgICAgIHRoaXMuX3QwID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAyOiB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94MSwgdGhpcy5feTEpOyBicmVhazsKICAgICAgICAgIGNhc2UgMzogcG9pbnQkNSh0aGlzLCB0aGlzLl90MCwgc2xvcGUyKHRoaXMsIHRoaXMuX3QwKSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fbGluZSA9IDEgLSB0aGlzLl9saW5lOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciB0MSA9IE5hTjsKCiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgaWYgKHggPT09IHRoaXMuX3gxICYmIHkgPT09IHRoaXMuX3kxKSByZXR1cm47IC8vIElnbm9yZSBjb2luY2lkZW50IHBvaW50cy4KICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHBvaW50JDUodGhpcywgc2xvcGUyKHRoaXMsIHQxID0gc2xvcGUzKHRoaXMsIHgsIHkpKSwgdDEpOyBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JDUodGhpcywgdGhpcy5fdDAsIHQxID0gc2xvcGUzKHRoaXMsIHgsIHkpKTsgYnJlYWs7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB5OwogICAgICAgIHRoaXMuX3QwID0gdDE7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gTW9ub3RvbmVZKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IG5ldyBSZWZsZWN0Q29udGV4dChjb250ZXh0KTsKICAgIH0KCiAgICAoTW9ub3RvbmVZLnByb3RvdHlwZSA9IE9iamVjdC5jcmVhdGUoTW9ub3RvbmVYLnByb3RvdHlwZSkpLnBvaW50ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICBNb25vdG9uZVgucHJvdG90eXBlLnBvaW50LmNhbGwodGhpcywgeSwgeCk7CiAgICB9OwoKICAgIGZ1bmN0aW9uIFJlZmxlY3RDb250ZXh0KGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgUmVmbGVjdENvbnRleHQucHJvdG90eXBlID0gewogICAgICBtb3ZlVG86IGZ1bmN0aW9uKHgsIHkpIHsgdGhpcy5fY29udGV4dC5tb3ZlVG8oeSwgeCk7IH0sCiAgICAgIGNsb3NlUGF0aDogZnVuY3Rpb24oKSB7IHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7IH0sCiAgICAgIGxpbmVUbzogZnVuY3Rpb24oeCwgeSkgeyB0aGlzLl9jb250ZXh0LmxpbmVUbyh5LCB4KTsgfSwKICAgICAgYmV6aWVyQ3VydmVUbzogZnVuY3Rpb24oeDEsIHkxLCB4MiwgeTIsIHgsIHkpIHsgdGhpcy5fY29udGV4dC5iZXppZXJDdXJ2ZVRvKHkxLCB4MSwgeTIsIHgyLCB5LCB4KTsgfQogICAgfTsKCiAgICBmdW5jdGlvbiBtb25vdG9uZVgoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IE1vbm90b25lWChjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBtb25vdG9uZVkoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IE1vbm90b25lWShjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBOYXR1cmFsKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgTmF0dXJhbC5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feCA9IFtdOwogICAgICAgIHRoaXMuX3kgPSBbXTsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHggPSB0aGlzLl94LAogICAgICAgICAgICB5ID0gdGhpcy5feSwKICAgICAgICAgICAgbiA9IHgubGVuZ3RoOwoKICAgICAgICBpZiAobikgewogICAgICAgICAgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHhbMF0sIHlbMF0pIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeFswXSwgeVswXSk7CiAgICAgICAgICBpZiAobiA9PT0gMikgewogICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4WzFdLCB5WzFdKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHZhciBweCA9IGNvbnRyb2xQb2ludHMoeCksCiAgICAgICAgICAgICAgICBweSA9IGNvbnRyb2xQb2ludHMoeSk7CiAgICAgICAgICAgIGZvciAodmFyIGkwID0gMCwgaTEgPSAxOyBpMSA8IG47ICsraTAsICsraTEpIHsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmJlemllckN1cnZlVG8ocHhbMF1baTBdLCBweVswXVtpMF0sIHB4WzFdW2kwXSwgcHlbMV1baTBdLCB4W2kxXSwgeVtpMV0pOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiBuID09PSAxKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgICAgdGhpcy5feCA9IHRoaXMuX3kgPSBudWxsOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHRoaXMuX3gucHVzaCgreCk7CiAgICAgICAgdGhpcy5feS5wdXNoKCt5KTsKICAgICAgfQogICAgfTsKCiAgICAvLyBTZWUgaHR0cHM6Ly93d3cucGFydGljbGVpbmNlbGwuY29tLzIwMTIvYmV6aWVyLXNwbGluZXMvIGZvciBkZXJpdmF0aW9uLgogICAgZnVuY3Rpb24gY29udHJvbFBvaW50cyh4KSB7CiAgICAgIHZhciBpLAogICAgICAgICAgbiA9IHgubGVuZ3RoIC0gMSwKICAgICAgICAgIG0sCiAgICAgICAgICBhID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgYiA9IG5ldyBBcnJheShuKSwKICAgICAgICAgIHIgPSBuZXcgQXJyYXkobik7CiAgICAgIGFbMF0gPSAwLCBiWzBdID0gMiwgclswXSA9IHhbMF0gKyAyICogeFsxXTsKICAgICAgZm9yIChpID0gMTsgaSA8IG4gLSAxOyArK2kpIGFbaV0gPSAxLCBiW2ldID0gNCwgcltpXSA9IDQgKiB4W2ldICsgMiAqIHhbaSArIDFdOwogICAgICBhW24gLSAxXSA9IDIsIGJbbiAtIDFdID0gNywgcltuIC0gMV0gPSA4ICogeFtuIC0gMV0gKyB4W25dOwogICAgICBmb3IgKGkgPSAxOyBpIDwgbjsgKytpKSBtID0gYVtpXSAvIGJbaSAtIDFdLCBiW2ldIC09IG0sIHJbaV0gLT0gbSAqIHJbaSAtIDFdOwogICAgICBhW24gLSAxXSA9IHJbbiAtIDFdIC8gYltuIC0gMV07CiAgICAgIGZvciAoaSA9IG4gLSAyOyBpID49IDA7IC0taSkgYVtpXSA9IChyW2ldIC0gYVtpICsgMV0pIC8gYltpXTsKICAgICAgYltuIC0gMV0gPSAoeFtuXSArIGFbbiAtIDFdKSAvIDI7CiAgICAgIGZvciAoaSA9IDA7IGkgPCBuIC0gMTsgKytpKSBiW2ldID0gMiAqIHhbaSArIDFdIC0gYVtpICsgMV07CiAgICAgIHJldHVybiBbYSwgYl07CiAgICB9CgogICAgZnVuY3Rpb24gbmF0dXJhbChjb250ZXh0KSB7CiAgICAgIHJldHVybiBuZXcgTmF0dXJhbChjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBTdGVwKGNvbnRleHQsIHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICAgIHRoaXMuX3QgPSB0OwogICAgfQoKICAgIFN0ZXAucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3ggPSB0aGlzLl95ID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKDAgPCB0aGlzLl90ICYmIHRoaXMuX3QgPCAxICYmIHRoaXMuX3BvaW50ID09PSAyKSB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94LCB0aGlzLl95KTsKICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgPj0gMCkgdGhpcy5fdCA9IDEgLSB0aGlzLl90LCB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHgsIHkpOyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyAvLyBwcm9jZWVkCiAgICAgICAgICBkZWZhdWx0OiB7CiAgICAgICAgICAgIGlmICh0aGlzLl90IDw9IDApIHsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94LCB5KTsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICB2YXIgeDEgPSB0aGlzLl94ICogKDEgLSB0aGlzLl90KSArIHggKiB0aGlzLl90OwogICAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKHgxLCB0aGlzLl95KTsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4MSwgeSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuX3ggPSB4LCB0aGlzLl95ID0geTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBzdGVwKGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBTdGVwKGNvbnRleHQsIDAuNSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3RlcEJlZm9yZShjb250ZXh0KSB7CiAgICAgIHJldHVybiBuZXcgU3RlcChjb250ZXh0LCAwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdGVwQWZ0ZXIoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IFN0ZXAoY29udGV4dCwgMSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9uZSQxKHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDEpKSByZXR1cm47CiAgICAgIGZvciAodmFyIGkgPSAxLCBqLCBzMCwgczEgPSBzZXJpZXNbb3JkZXJbMF1dLCBuLCBtID0gczEubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgczAgPSBzMSwgczEgPSBzZXJpZXNbb3JkZXJbaV1dOwogICAgICAgIGZvciAoaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICAgIHMxW2pdWzFdICs9IHMxW2pdWzBdID0gaXNOYU4oczBbal1bMV0pID8gczBbal1bMF0gOiBzMFtqXVsxXTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBub25lJDIoc2VyaWVzKSB7CiAgICAgIHZhciBuID0gc2VyaWVzLmxlbmd0aCwgbyA9IG5ldyBBcnJheShuKTsKICAgICAgd2hpbGUgKC0tbiA+PSAwKSBvW25dID0gbjsKICAgICAgcmV0dXJuIG87CiAgICB9CgogICAgZnVuY3Rpb24gc3RhY2tWYWx1ZShkLCBrZXkpIHsKICAgICAgcmV0dXJuIGRba2V5XTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdGFjaygpIHsKICAgICAgdmFyIGtleXMgPSBjb25zdGFudCRiKFtdKSwKICAgICAgICAgIG9yZGVyID0gbm9uZSQyLAogICAgICAgICAgb2Zmc2V0ID0gbm9uZSQxLAogICAgICAgICAgdmFsdWUgPSBzdGFja1ZhbHVlOwoKICAgICAgZnVuY3Rpb24gc3RhY2soZGF0YSkgewogICAgICAgIHZhciBreiA9IGtleXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgaSwKICAgICAgICAgICAgbSA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBuID0ga3oubGVuZ3RoLAogICAgICAgICAgICBzeiA9IG5ldyBBcnJheShuKSwKICAgICAgICAgICAgb3o7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGZvciAodmFyIGtpID0ga3pbaV0sIHNpID0gc3pbaV0gPSBuZXcgQXJyYXkobSksIGogPSAwLCBzaWo7IGogPCBtOyArK2opIHsKICAgICAgICAgICAgc2lbal0gPSBzaWogPSBbMCwgK3ZhbHVlKGRhdGFbal0sIGtpLCBqLCBkYXRhKV07CiAgICAgICAgICAgIHNpai5kYXRhID0gZGF0YVtqXTsKICAgICAgICAgIH0KICAgICAgICAgIHNpLmtleSA9IGtpOwogICAgICAgIH0KCiAgICAgICAgZm9yIChpID0gMCwgb3ogPSBvcmRlcihzeik7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHN6W296W2ldXS5pbmRleCA9IGk7CiAgICAgICAgfQoKICAgICAgICBvZmZzZXQoc3osIG96KTsKICAgICAgICByZXR1cm4gc3o7CiAgICAgIH0KCiAgICAgIHN0YWNrLmtleXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoa2V5cyA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGIoc2xpY2UkNi5jYWxsKF8pKSwgc3RhY2spIDoga2V5czsKICAgICAgfTsKCiAgICAgIHN0YWNrLnZhbHVlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHZhbHVlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYigrXyksIHN0YWNrKSA6IHZhbHVlOwogICAgICB9OwoKICAgICAgc3RhY2sub3JkZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAob3JkZXIgPSBfID09IG51bGwgPyBub25lJDIgOiB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRiKHNsaWNlJDYuY2FsbChfKSksIHN0YWNrKSA6IG9yZGVyOwogICAgICB9OwoKICAgICAgc3RhY2sub2Zmc2V0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG9mZnNldCA9IF8gPT0gbnVsbCA/IG5vbmUkMSA6IF8sIHN0YWNrKSA6IG9mZnNldDsKICAgICAgfTsKCiAgICAgIHJldHVybiBzdGFjazsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBhbmQoc2VyaWVzLCBvcmRlcikgewogICAgICBpZiAoISgobiA9IHNlcmllcy5sZW5ndGgpID4gMCkpIHJldHVybjsKICAgICAgZm9yICh2YXIgaSwgbiwgaiA9IDAsIG0gPSBzZXJpZXNbMF0ubGVuZ3RoLCB5OyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh5ID0gaSA9IDA7IGkgPCBuOyArK2kpIHkgKz0gc2VyaWVzW2ldW2pdWzFdIHx8IDA7CiAgICAgICAgaWYgKHkpIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHNlcmllc1tpXVtqXVsxXSAvPSB5OwogICAgICB9CiAgICAgIG5vbmUkMShzZXJpZXMsIG9yZGVyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXZlcmdpbmckMShzZXJpZXMsIG9yZGVyKSB7CiAgICAgIGlmICghKChuID0gc2VyaWVzLmxlbmd0aCkgPiAwKSkgcmV0dXJuOwogICAgICBmb3IgKHZhciBpLCBqID0gMCwgZCwgZHksIHlwLCB5biwgbiwgbSA9IHNlcmllc1tvcmRlclswXV0ubGVuZ3RoOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh5cCA9IHluID0gMCwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgoZHkgPSAoZCA9IHNlcmllc1tvcmRlcltpXV1bal0pWzFdIC0gZFswXSkgPiAwKSB7CiAgICAgICAgICAgIGRbMF0gPSB5cCwgZFsxXSA9IHlwICs9IGR5OwogICAgICAgICAgfSBlbHNlIGlmIChkeSA8IDApIHsKICAgICAgICAgICAgZFsxXSA9IHluLCBkWzBdID0geW4gKz0gZHk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBkWzBdID0gMCwgZFsxXSA9IGR5OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHNpbGhvdWV0dGUoc2VyaWVzLCBvcmRlcikgewogICAgICBpZiAoISgobiA9IHNlcmllcy5sZW5ndGgpID4gMCkpIHJldHVybjsKICAgICAgZm9yICh2YXIgaiA9IDAsIHMwID0gc2VyaWVzW29yZGVyWzBdXSwgbiwgbSA9IHMwLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGkgPSAwLCB5ID0gMDsgaSA8IG47ICsraSkgeSArPSBzZXJpZXNbaV1bal1bMV0gfHwgMDsKICAgICAgICBzMFtqXVsxXSArPSBzMFtqXVswXSA9IC15IC8gMjsKICAgICAgfQogICAgICBub25lJDEoc2VyaWVzLCBvcmRlcik7CiAgICB9CgogICAgZnVuY3Rpb24gd2lnZ2xlKHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDApIHx8ICEoKG0gPSAoczAgPSBzZXJpZXNbb3JkZXJbMF1dKS5sZW5ndGgpID4gMCkpIHJldHVybjsKICAgICAgZm9yICh2YXIgeSA9IDAsIGogPSAxLCBzMCwgbSwgbjsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBzMSA9IDAsIHMyID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdmFyIHNpID0gc2VyaWVzW29yZGVyW2ldXSwKICAgICAgICAgICAgICBzaWowID0gc2lbal1bMV0gfHwgMCwKICAgICAgICAgICAgICBzaWoxID0gc2lbaiAtIDFdWzFdIHx8IDAsCiAgICAgICAgICAgICAgczMgPSAoc2lqMCAtIHNpajEpIC8gMjsKICAgICAgICAgIGZvciAodmFyIGsgPSAwOyBrIDwgaTsgKytrKSB7CiAgICAgICAgICAgIHZhciBzayA9IHNlcmllc1tvcmRlcltrXV0sCiAgICAgICAgICAgICAgICBza2owID0gc2tbal1bMV0gfHwgMCwKICAgICAgICAgICAgICAgIHNrajEgPSBza1tqIC0gMV1bMV0gfHwgMDsKICAgICAgICAgICAgczMgKz0gc2tqMCAtIHNrajE7CiAgICAgICAgICB9CiAgICAgICAgICBzMSArPSBzaWowLCBzMiArPSBzMyAqIHNpajA7CiAgICAgICAgfQogICAgICAgIHMwW2ogLSAxXVsxXSArPSBzMFtqIC0gMV1bMF0gPSB5OwogICAgICAgIGlmIChzMSkgeSAtPSBzMiAvIHMxOwogICAgICB9CiAgICAgIHMwW2ogLSAxXVsxXSArPSBzMFtqIC0gMV1bMF0gPSB5OwogICAgICBub25lJDEoc2VyaWVzLCBvcmRlcik7CiAgICB9CgogICAgZnVuY3Rpb24gYXBwZWFyYW5jZShzZXJpZXMpIHsKICAgICAgdmFyIHBlYWtzID0gc2VyaWVzLm1hcChwZWFrKTsKICAgICAgcmV0dXJuIG5vbmUkMihzZXJpZXMpLnNvcnQoZnVuY3Rpb24oYSwgYikgeyByZXR1cm4gcGVha3NbYV0gLSBwZWFrc1tiXTsgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcGVhayhzZXJpZXMpIHsKICAgICAgdmFyIGkgPSAtMSwgaiA9IDAsIG4gPSBzZXJpZXMubGVuZ3RoLCB2aSwgdmogPSAtSW5maW5pdHk7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoKHZpID0gK3Nlcmllc1tpXVsxXSkgPiB2aikgdmogPSB2aSwgaiA9IGk7CiAgICAgIHJldHVybiBqOwogICAgfQoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyQzKHNlcmllcykgewogICAgICB2YXIgc3VtcyA9IHNlcmllcy5tYXAoc3VtJDIpOwogICAgICByZXR1cm4gbm9uZSQyKHNlcmllcykuc29ydChmdW5jdGlvbihhLCBiKSB7IHJldHVybiBzdW1zW2FdIC0gc3Vtc1tiXTsgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3VtJDIoc2VyaWVzKSB7CiAgICAgIHZhciBzID0gMCwgaSA9IC0xLCBuID0gc2VyaWVzLmxlbmd0aCwgdjsKICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICh2ID0gK3Nlcmllc1tpXVsxXSkgcyArPSB2OwogICAgICByZXR1cm4gczsKICAgIH0KCiAgICBmdW5jdGlvbiBkZXNjZW5kaW5nJDIoc2VyaWVzKSB7CiAgICAgIHJldHVybiBhc2NlbmRpbmckMyhzZXJpZXMpLnJldmVyc2UoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnNpZGVPdXQoc2VyaWVzKSB7CiAgICAgIHZhciBuID0gc2VyaWVzLmxlbmd0aCwKICAgICAgICAgIGksCiAgICAgICAgICBqLAogICAgICAgICAgc3VtcyA9IHNlcmllcy5tYXAoc3VtJDIpLAogICAgICAgICAgb3JkZXIgPSBhcHBlYXJhbmNlKHNlcmllcyksCiAgICAgICAgICB0b3AgPSAwLAogICAgICAgICAgYm90dG9tID0gMCwKICAgICAgICAgIHRvcHMgPSBbXSwKICAgICAgICAgIGJvdHRvbXMgPSBbXTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBqID0gb3JkZXJbaV07CiAgICAgICAgaWYgKHRvcCA8IGJvdHRvbSkgewogICAgICAgICAgdG9wICs9IHN1bXNbal07CiAgICAgICAgICB0b3BzLnB1c2goaik7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGJvdHRvbSArPSBzdW1zW2pdOwogICAgICAgICAgYm90dG9tcy5wdXNoKGopOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIGJvdHRvbXMucmV2ZXJzZSgpLmNvbmNhdCh0b3BzKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXZlcnNlKHNlcmllcykgewogICAgICByZXR1cm4gbm9uZSQyKHNlcmllcykucmV2ZXJzZSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGMoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24geCQ0KGQpIHsKICAgICAgcmV0dXJuIGRbMF07CiAgICB9CgogICAgZnVuY3Rpb24geSQ0KGQpIHsKICAgICAgcmV0dXJuIGRbMV07CiAgICB9CgogICAgZnVuY3Rpb24gUmVkQmxhY2tUcmVlKCkgewogICAgICB0aGlzLl8gPSBudWxsOyAvLyByb290IG5vZGUKICAgIH0KCiAgICBmdW5jdGlvbiBSZWRCbGFja05vZGUobm9kZSkgewogICAgICBub2RlLlUgPSAvLyBwYXJlbnQgbm9kZQogICAgICBub2RlLkMgPSAvLyBjb2xvciAtIHRydWUgZm9yIHJlZCwgZmFsc2UgZm9yIGJsYWNrCiAgICAgIG5vZGUuTCA9IC8vIGxlZnQgbm9kZQogICAgICBub2RlLlIgPSAvLyByaWdodCBub2RlCiAgICAgIG5vZGUuUCA9IC8vIHByZXZpb3VzIG5vZGUKICAgICAgbm9kZS5OID0gbnVsbDsgLy8gbmV4dCBub2RlCiAgICB9CgogICAgUmVkQmxhY2tUcmVlLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFJlZEJsYWNrVHJlZSwKCiAgICAgIGluc2VydDogZnVuY3Rpb24oYWZ0ZXIsIG5vZGUpIHsKICAgICAgICB2YXIgcGFyZW50LCBncmFuZHBhLCB1bmNsZTsKCiAgICAgICAgaWYgKGFmdGVyKSB7CiAgICAgICAgICBub2RlLlAgPSBhZnRlcjsKICAgICAgICAgIG5vZGUuTiA9IGFmdGVyLk47CiAgICAgICAgICBpZiAoYWZ0ZXIuTikgYWZ0ZXIuTi5QID0gbm9kZTsKICAgICAgICAgIGFmdGVyLk4gPSBub2RlOwogICAgICAgICAgaWYgKGFmdGVyLlIpIHsKICAgICAgICAgICAgYWZ0ZXIgPSBhZnRlci5SOwogICAgICAgICAgICB3aGlsZSAoYWZ0ZXIuTCkgYWZ0ZXIgPSBhZnRlci5MOwogICAgICAgICAgICBhZnRlci5MID0gbm9kZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGFmdGVyLlIgPSBub2RlOwogICAgICAgICAgfQogICAgICAgICAgcGFyZW50ID0gYWZ0ZXI7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl8pIHsKICAgICAgICAgIGFmdGVyID0gUmVkQmxhY2tGaXJzdCh0aGlzLl8pOwogICAgICAgICAgbm9kZS5QID0gbnVsbDsKICAgICAgICAgIG5vZGUuTiA9IGFmdGVyOwogICAgICAgICAgYWZ0ZXIuUCA9IGFmdGVyLkwgPSBub2RlOwogICAgICAgICAgcGFyZW50ID0gYWZ0ZXI7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIG5vZGUuUCA9IG5vZGUuTiA9IG51bGw7CiAgICAgICAgICB0aGlzLl8gPSBub2RlOwogICAgICAgICAgcGFyZW50ID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgbm9kZS5MID0gbm9kZS5SID0gbnVsbDsKICAgICAgICBub2RlLlUgPSBwYXJlbnQ7CiAgICAgICAgbm9kZS5DID0gdHJ1ZTsKCiAgICAgICAgYWZ0ZXIgPSBub2RlOwogICAgICAgIHdoaWxlIChwYXJlbnQgJiYgcGFyZW50LkMpIHsKICAgICAgICAgIGdyYW5kcGEgPSBwYXJlbnQuVTsKICAgICAgICAgIGlmIChwYXJlbnQgPT09IGdyYW5kcGEuTCkgewogICAgICAgICAgICB1bmNsZSA9IGdyYW5kcGEuUjsKICAgICAgICAgICAgaWYgKHVuY2xlICYmIHVuY2xlLkMpIHsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHVuY2xlLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIGFmdGVyID0gZ3JhbmRwYTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpZiAoYWZ0ZXIgPT09IHBhcmVudC5SKSB7CiAgICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZUxlZnQodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICAgIGFmdGVyID0gcGFyZW50OwogICAgICAgICAgICAgICAgcGFyZW50ID0gYWZ0ZXIuVTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcGFyZW50LkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIFJlZEJsYWNrUm90YXRlUmlnaHQodGhpcywgZ3JhbmRwYSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHVuY2xlID0gZ3JhbmRwYS5MOwogICAgICAgICAgICBpZiAodW5jbGUgJiYgdW5jbGUuQykgewogICAgICAgICAgICAgIHBhcmVudC5DID0gdW5jbGUuQyA9IGZhbHNlOwogICAgICAgICAgICAgIGdyYW5kcGEuQyA9IHRydWU7CiAgICAgICAgICAgICAgYWZ0ZXIgPSBncmFuZHBhOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGlmIChhZnRlciA9PT0gcGFyZW50LkwpIHsKICAgICAgICAgICAgICAgIFJlZEJsYWNrUm90YXRlUmlnaHQodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICAgIGFmdGVyID0gcGFyZW50OwogICAgICAgICAgICAgICAgcGFyZW50ID0gYWZ0ZXIuVTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcGFyZW50LkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIFJlZEJsYWNrUm90YXRlTGVmdCh0aGlzLCBncmFuZHBhKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgcGFyZW50ID0gYWZ0ZXIuVTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fLkMgPSBmYWxzZTsKICAgICAgfSwKCiAgICAgIHJlbW92ZTogZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmIChub2RlLk4pIG5vZGUuTi5QID0gbm9kZS5QOwogICAgICAgIGlmIChub2RlLlApIG5vZGUuUC5OID0gbm9kZS5OOwogICAgICAgIG5vZGUuTiA9IG5vZGUuUCA9IG51bGw7CgogICAgICAgIHZhciBwYXJlbnQgPSBub2RlLlUsCiAgICAgICAgICAgIHNpYmxpbmcsCiAgICAgICAgICAgIGxlZnQgPSBub2RlLkwsCiAgICAgICAgICAgIHJpZ2h0ID0gbm9kZS5SLAogICAgICAgICAgICBuZXh0LAogICAgICAgICAgICByZWQ7CgogICAgICAgIGlmICghbGVmdCkgbmV4dCA9IHJpZ2h0OwogICAgICAgIGVsc2UgaWYgKCFyaWdodCkgbmV4dCA9IGxlZnQ7CiAgICAgICAgZWxzZSBuZXh0ID0gUmVkQmxhY2tGaXJzdChyaWdodCk7CgogICAgICAgIGlmIChwYXJlbnQpIHsKICAgICAgICAgIGlmIChwYXJlbnQuTCA9PT0gbm9kZSkgcGFyZW50LkwgPSBuZXh0OwogICAgICAgICAgZWxzZSBwYXJlbnQuUiA9IG5leHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuXyA9IG5leHQ7CiAgICAgICAgfQoKICAgICAgICBpZiAobGVmdCAmJiByaWdodCkgewogICAgICAgICAgcmVkID0gbmV4dC5DOwogICAgICAgICAgbmV4dC5DID0gbm9kZS5DOwogICAgICAgICAgbmV4dC5MID0gbGVmdDsKICAgICAgICAgIGxlZnQuVSA9IG5leHQ7CiAgICAgICAgICBpZiAobmV4dCAhPT0gcmlnaHQpIHsKICAgICAgICAgICAgcGFyZW50ID0gbmV4dC5VOwogICAgICAgICAgICBuZXh0LlUgPSBub2RlLlU7CiAgICAgICAgICAgIG5vZGUgPSBuZXh0LlI7CiAgICAgICAgICAgIHBhcmVudC5MID0gbm9kZTsKICAgICAgICAgICAgbmV4dC5SID0gcmlnaHQ7CiAgICAgICAgICAgIHJpZ2h0LlUgPSBuZXh0OwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbmV4dC5VID0gcGFyZW50OwogICAgICAgICAgICBwYXJlbnQgPSBuZXh0OwogICAgICAgICAgICBub2RlID0gbmV4dC5SOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICByZWQgPSBub2RlLkM7CiAgICAgICAgICBub2RlID0gbmV4dDsKICAgICAgICB9CgogICAgICAgIGlmIChub2RlKSBub2RlLlUgPSBwYXJlbnQ7CiAgICAgICAgaWYgKHJlZCkgcmV0dXJuOwogICAgICAgIGlmIChub2RlICYmIG5vZGUuQykgeyBub2RlLkMgPSBmYWxzZTsgcmV0dXJuOyB9CgogICAgICAgIGRvIHsKICAgICAgICAgIGlmIChub2RlID09PSB0aGlzLl8pIGJyZWFrOwogICAgICAgICAgaWYgKG5vZGUgPT09IHBhcmVudC5MKSB7CiAgICAgICAgICAgIHNpYmxpbmcgPSBwYXJlbnQuUjsKICAgICAgICAgICAgaWYgKHNpYmxpbmcuQykgewogICAgICAgICAgICAgIHNpYmxpbmcuQyA9IGZhbHNlOwogICAgICAgICAgICAgIHBhcmVudC5DID0gdHJ1ZTsKICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZUxlZnQodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50LlI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKChzaWJsaW5nLkwgJiYgc2libGluZy5MLkMpCiAgICAgICAgICAgICAgICB8fCAoc2libGluZy5SICYmIHNpYmxpbmcuUi5DKSkgewogICAgICAgICAgICAgIGlmICghc2libGluZy5SIHx8ICFzaWJsaW5nLlIuQykgewogICAgICAgICAgICAgICAgc2libGluZy5MLkMgPSBmYWxzZTsKICAgICAgICAgICAgICAgIHNpYmxpbmcuQyA9IHRydWU7CiAgICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZVJpZ2h0KHRoaXMsIHNpYmxpbmcpOwogICAgICAgICAgICAgICAgc2libGluZyA9IHBhcmVudC5SOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBzaWJsaW5nLkMgPSBwYXJlbnQuQzsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHNpYmxpbmcuUi5DID0gZmFsc2U7CiAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVMZWZ0KHRoaXMsIHBhcmVudCk7CiAgICAgICAgICAgICAgbm9kZSA9IHRoaXMuXzsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgc2libGluZyA9IHBhcmVudC5MOwogICAgICAgICAgICBpZiAoc2libGluZy5DKSB7CiAgICAgICAgICAgICAgc2libGluZy5DID0gZmFsc2U7CiAgICAgICAgICAgICAgcGFyZW50LkMgPSB0cnVlOwogICAgICAgICAgICAgIFJlZEJsYWNrUm90YXRlUmlnaHQodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50Lkw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKChzaWJsaW5nLkwgJiYgc2libGluZy5MLkMpCiAgICAgICAgICAgICAgfHwgKHNpYmxpbmcuUiAmJiBzaWJsaW5nLlIuQykpIHsKICAgICAgICAgICAgICBpZiAoIXNpYmxpbmcuTCB8fCAhc2libGluZy5MLkMpIHsKICAgICAgICAgICAgICAgIHNpYmxpbmcuUi5DID0gZmFsc2U7CiAgICAgICAgICAgICAgICBzaWJsaW5nLkMgPSB0cnVlOwogICAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVMZWZ0KHRoaXMsIHNpYmxpbmcpOwogICAgICAgICAgICAgICAgc2libGluZyA9IHBhcmVudC5MOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBzaWJsaW5nLkMgPSBwYXJlbnQuQzsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHNpYmxpbmcuTC5DID0gZmFsc2U7CiAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVSaWdodCh0aGlzLCBwYXJlbnQpOwogICAgICAgICAgICAgIG5vZGUgPSB0aGlzLl87CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHNpYmxpbmcuQyA9IHRydWU7CiAgICAgICAgICBub2RlID0gcGFyZW50OwogICAgICAgICAgcGFyZW50ID0gcGFyZW50LlU7CiAgICAgICAgfSB3aGlsZSAoIW5vZGUuQyk7CgogICAgICAgIGlmIChub2RlKSBub2RlLkMgPSBmYWxzZTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBSZWRCbGFja1JvdGF0ZUxlZnQodHJlZSwgbm9kZSkgewogICAgICB2YXIgcCA9IG5vZGUsCiAgICAgICAgICBxID0gbm9kZS5SLAogICAgICAgICAgcGFyZW50ID0gcC5VOwoKICAgICAgaWYgKHBhcmVudCkgewogICAgICAgIGlmIChwYXJlbnQuTCA9PT0gcCkgcGFyZW50LkwgPSBxOwogICAgICAgIGVsc2UgcGFyZW50LlIgPSBxOwogICAgICB9IGVsc2UgewogICAgICAgIHRyZWUuXyA9IHE7CiAgICAgIH0KCiAgICAgIHEuVSA9IHBhcmVudDsKICAgICAgcC5VID0gcTsKICAgICAgcC5SID0gcS5MOwogICAgICBpZiAocC5SKSBwLlIuVSA9IHA7CiAgICAgIHEuTCA9IHA7CiAgICB9CgogICAgZnVuY3Rpb24gUmVkQmxhY2tSb3RhdGVSaWdodCh0cmVlLCBub2RlKSB7CiAgICAgIHZhciBwID0gbm9kZSwKICAgICAgICAgIHEgPSBub2RlLkwsCiAgICAgICAgICBwYXJlbnQgPSBwLlU7CgogICAgICBpZiAocGFyZW50KSB7CiAgICAgICAgaWYgKHBhcmVudC5MID09PSBwKSBwYXJlbnQuTCA9IHE7CiAgICAgICAgZWxzZSBwYXJlbnQuUiA9IHE7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgdHJlZS5fID0gcTsKICAgICAgfQoKICAgICAgcS5VID0gcGFyZW50OwogICAgICBwLlUgPSBxOwogICAgICBwLkwgPSBxLlI7CiAgICAgIGlmIChwLkwpIHAuTC5VID0gcDsKICAgICAgcS5SID0gcDsKICAgIH0KCiAgICBmdW5jdGlvbiBSZWRCbGFja0ZpcnN0KG5vZGUpIHsKICAgICAgd2hpbGUgKG5vZGUuTCkgbm9kZSA9IG5vZGUuTDsKICAgICAgcmV0dXJuIG5vZGU7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlRWRnZShsZWZ0LCByaWdodCwgdjAsIHYxKSB7CiAgICAgIHZhciBlZGdlID0gW251bGwsIG51bGxdLAogICAgICAgICAgaW5kZXggPSBlZGdlcy5wdXNoKGVkZ2UpIC0gMTsKICAgICAgZWRnZS5sZWZ0ID0gbGVmdDsKICAgICAgZWRnZS5yaWdodCA9IHJpZ2h0OwogICAgICBpZiAodjApIHNldEVkZ2VFbmQoZWRnZSwgbGVmdCwgcmlnaHQsIHYwKTsKICAgICAgaWYgKHYxKSBzZXRFZGdlRW5kKGVkZ2UsIHJpZ2h0LCBsZWZ0LCB2MSk7CiAgICAgIGNlbGxzW2xlZnQuaW5kZXhdLmhhbGZlZGdlcy5wdXNoKGluZGV4KTsKICAgICAgY2VsbHNbcmlnaHQuaW5kZXhdLmhhbGZlZGdlcy5wdXNoKGluZGV4KTsKICAgICAgcmV0dXJuIGVkZ2U7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlQm9yZGVyRWRnZShsZWZ0LCB2MCwgdjEpIHsKICAgICAgdmFyIGVkZ2UgPSBbdjAsIHYxXTsKICAgICAgZWRnZS5sZWZ0ID0gbGVmdDsKICAgICAgcmV0dXJuIGVkZ2U7CiAgICB9CgogICAgZnVuY3Rpb24gc2V0RWRnZUVuZChlZGdlLCBsZWZ0LCByaWdodCwgdmVydGV4KSB7CiAgICAgIGlmICghZWRnZVswXSAmJiAhZWRnZVsxXSkgewogICAgICAgIGVkZ2VbMF0gPSB2ZXJ0ZXg7CiAgICAgICAgZWRnZS5sZWZ0ID0gbGVmdDsKICAgICAgICBlZGdlLnJpZ2h0ID0gcmlnaHQ7CiAgICAgIH0gZWxzZSBpZiAoZWRnZS5sZWZ0ID09PSByaWdodCkgewogICAgICAgIGVkZ2VbMV0gPSB2ZXJ0ZXg7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgZWRnZVswXSA9IHZlcnRleDsKICAgICAgfQogICAgfQoKICAgIC8vIExpYW5n4oCTQmFyc2t5IGxpbmUgY2xpcHBpbmcuCiAgICBmdW5jdGlvbiBjbGlwRWRnZShlZGdlLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgYSA9IGVkZ2VbMF0sCiAgICAgICAgICBiID0gZWRnZVsxXSwKICAgICAgICAgIGF4ID0gYVswXSwKICAgICAgICAgIGF5ID0gYVsxXSwKICAgICAgICAgIGJ4ID0gYlswXSwKICAgICAgICAgIGJ5ID0gYlsxXSwKICAgICAgICAgIHQwID0gMCwKICAgICAgICAgIHQxID0gMSwKICAgICAgICAgIGR4ID0gYnggLSBheCwKICAgICAgICAgIGR5ID0gYnkgLSBheSwKICAgICAgICAgIHI7CgogICAgICByID0geDAgLSBheDsKICAgICAgaWYgKCFkeCAmJiByID4gMCkgcmV0dXJuOwogICAgICByIC89IGR4OwogICAgICBpZiAoZHggPCAwKSB7CiAgICAgICAgaWYgKHIgPCB0MCkgcmV0dXJuOwogICAgICAgIGlmIChyIDwgdDEpIHQxID0gcjsKICAgICAgfSBlbHNlIGlmIChkeCA+IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9CgogICAgICByID0geDEgLSBheDsKICAgICAgaWYgKCFkeCAmJiByIDwgMCkgcmV0dXJuOwogICAgICByIC89IGR4OwogICAgICBpZiAoZHggPCAwKSB7CiAgICAgICAgaWYgKHIgPiB0MSkgcmV0dXJuOwogICAgICAgIGlmIChyID4gdDApIHQwID0gcjsKICAgICAgfSBlbHNlIGlmIChkeCA+IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9CgogICAgICByID0geTAgLSBheTsKICAgICAgaWYgKCFkeSAmJiByID4gMCkgcmV0dXJuOwogICAgICByIC89IGR5OwogICAgICBpZiAoZHkgPCAwKSB7CiAgICAgICAgaWYgKHIgPCB0MCkgcmV0dXJuOwogICAgICAgIGlmIChyIDwgdDEpIHQxID0gcjsKICAgICAgfSBlbHNlIGlmIChkeSA+IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9CgogICAgICByID0geTEgLSBheTsKICAgICAgaWYgKCFkeSAmJiByIDwgMCkgcmV0dXJuOwogICAgICByIC89IGR5OwogICAgICBpZiAoZHkgPCAwKSB7CiAgICAgICAgaWYgKHIgPiB0MSkgcmV0dXJuOwogICAgICAgIGlmIChyID4gdDApIHQwID0gcjsKICAgICAgfSBlbHNlIGlmIChkeSA+IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9CgogICAgICBpZiAoISh0MCA+IDApICYmICEodDEgPCAxKSkgcmV0dXJuIHRydWU7IC8vIFRPRE8gQmV0dGVyIGNoZWNrPwoKICAgICAgaWYgKHQwID4gMCkgZWRnZVswXSA9IFtheCArIHQwICogZHgsIGF5ICsgdDAgKiBkeV07CiAgICAgIGlmICh0MSA8IDEpIGVkZ2VbMV0gPSBbYXggKyB0MSAqIGR4LCBheSArIHQxICogZHldOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25uZWN0RWRnZShlZGdlLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgdjEgPSBlZGdlWzFdOwogICAgICBpZiAodjEpIHJldHVybiB0cnVlOwoKICAgICAgdmFyIHYwID0gZWRnZVswXSwKICAgICAgICAgIGxlZnQgPSBlZGdlLmxlZnQsCiAgICAgICAgICByaWdodCA9IGVkZ2UucmlnaHQsCiAgICAgICAgICBseCA9IGxlZnRbMF0sCiAgICAgICAgICBseSA9IGxlZnRbMV0sCiAgICAgICAgICByeCA9IHJpZ2h0WzBdLAogICAgICAgICAgcnkgPSByaWdodFsxXSwKICAgICAgICAgIGZ4ID0gKGx4ICsgcngpIC8gMiwKICAgICAgICAgIGZ5ID0gKGx5ICsgcnkpIC8gMiwKICAgICAgICAgIGZtLAogICAgICAgICAgZmI7CgogICAgICBpZiAocnkgPT09IGx5KSB7CiAgICAgICAgaWYgKGZ4IDwgeDAgfHwgZnggPj0geDEpIHJldHVybjsKICAgICAgICBpZiAobHggPiByeCkgewogICAgICAgICAgaWYgKCF2MCkgdjAgPSBbZngsIHkwXTsKICAgICAgICAgIGVsc2UgaWYgKHYwWzFdID49IHkxKSByZXR1cm47CiAgICAgICAgICB2MSA9IFtmeCwgeTFdOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAoIXYwKSB2MCA9IFtmeCwgeTFdOwogICAgICAgICAgZWxzZSBpZiAodjBbMV0gPCB5MCkgcmV0dXJuOwogICAgICAgICAgdjEgPSBbZngsIHkwXTsKICAgICAgICB9CiAgICAgIH0gZWxzZSB7CiAgICAgICAgZm0gPSAobHggLSByeCkgLyAocnkgLSBseSk7CiAgICAgICAgZmIgPSBmeSAtIGZtICogZng7CiAgICAgICAgaWYgKGZtIDwgLTEgfHwgZm0gPiAxKSB7CiAgICAgICAgICBpZiAobHggPiByeCkgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFsoeTAgLSBmYikgLyBmbSwgeTBdOwogICAgICAgICAgICBlbHNlIGlmICh2MFsxXSA+PSB5MSkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFsoeTEgLSBmYikgLyBmbSwgeTFdOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKCF2MCkgdjAgPSBbKHkxIC0gZmIpIC8gZm0sIHkxXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMV0gPCB5MCkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFsoeTAgLSBmYikgLyBmbSwgeTBdOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAobHkgPCByeSkgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFt4MCwgZm0gKiB4MCArIGZiXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMF0gPj0geDEpIHJldHVybjsKICAgICAgICAgICAgdjEgPSBbeDEsIGZtICogeDEgKyBmYl07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFt4MSwgZm0gKiB4MSArIGZiXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMF0gPCB4MCkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFt4MCwgZm0gKiB4MCArIGZiXTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVkZ2VbMF0gPSB2MDsKICAgICAgZWRnZVsxXSA9IHYxOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwRWRnZXMoeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdmFyIGkgPSBlZGdlcy5sZW5ndGgsCiAgICAgICAgICBlZGdlOwoKICAgICAgd2hpbGUgKGktLSkgewogICAgICAgIGlmICghY29ubmVjdEVkZ2UoZWRnZSA9IGVkZ2VzW2ldLCB4MCwgeTAsIHgxLCB5MSkKICAgICAgICAgICAgfHwgIWNsaXBFZGdlKGVkZ2UsIHgwLCB5MCwgeDEsIHkxKQogICAgICAgICAgICB8fCAhKE1hdGguYWJzKGVkZ2VbMF1bMF0gLSBlZGdlWzFdWzBdKSA+IGVwc2lsb24kNAogICAgICAgICAgICAgICAgfHwgTWF0aC5hYnMoZWRnZVswXVsxXSAtIGVkZ2VbMV1bMV0pID4gZXBzaWxvbiQ0KSkgewogICAgICAgICAgZGVsZXRlIGVkZ2VzW2ldOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZUNlbGwoc2l0ZSkgewogICAgICByZXR1cm4gY2VsbHNbc2l0ZS5pbmRleF0gPSB7CiAgICAgICAgc2l0ZTogc2l0ZSwKICAgICAgICBoYWxmZWRnZXM6IFtdCiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2VsbEhhbGZlZGdlQW5nbGUoY2VsbCwgZWRnZSkgewogICAgICB2YXIgc2l0ZSA9IGNlbGwuc2l0ZSwKICAgICAgICAgIHZhID0gZWRnZS5sZWZ0LAogICAgICAgICAgdmIgPSBlZGdlLnJpZ2h0OwogICAgICBpZiAoc2l0ZSA9PT0gdmIpIHZiID0gdmEsIHZhID0gc2l0ZTsKICAgICAgaWYgKHZiKSByZXR1cm4gTWF0aC5hdGFuMih2YlsxXSAtIHZhWzFdLCB2YlswXSAtIHZhWzBdKTsKICAgICAgaWYgKHNpdGUgPT09IHZhKSB2YSA9IGVkZ2VbMV0sIHZiID0gZWRnZVswXTsKICAgICAgZWxzZSB2YSA9IGVkZ2VbMF0sIHZiID0gZWRnZVsxXTsKICAgICAgcmV0dXJuIE1hdGguYXRhbjIodmFbMF0gLSB2YlswXSwgdmJbMV0gLSB2YVsxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VsbEhhbGZlZGdlU3RhcnQoY2VsbCwgZWRnZSkgewogICAgICByZXR1cm4gZWRnZVsrKGVkZ2UubGVmdCAhPT0gY2VsbC5zaXRlKV07CiAgICB9CgogICAgZnVuY3Rpb24gY2VsbEhhbGZlZGdlRW5kKGNlbGwsIGVkZ2UpIHsKICAgICAgcmV0dXJuIGVkZ2VbKyhlZGdlLmxlZnQgPT09IGNlbGwuc2l0ZSldOwogICAgfQoKICAgIGZ1bmN0aW9uIHNvcnRDZWxsSGFsZmVkZ2VzKCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGNlbGxzLmxlbmd0aCwgY2VsbCwgaGFsZmVkZ2VzLCBqLCBtOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKChjZWxsID0gY2VsbHNbaV0pICYmIChtID0gKGhhbGZlZGdlcyA9IGNlbGwuaGFsZmVkZ2VzKS5sZW5ndGgpKSB7CiAgICAgICAgICB2YXIgaW5kZXggPSBuZXcgQXJyYXkobSksCiAgICAgICAgICAgICAgYXJyYXkgPSBuZXcgQXJyYXkobSk7CiAgICAgICAgICBmb3IgKGogPSAwOyBqIDwgbTsgKytqKSBpbmRleFtqXSA9IGosIGFycmF5W2pdID0gY2VsbEhhbGZlZGdlQW5nbGUoY2VsbCwgZWRnZXNbaGFsZmVkZ2VzW2pdXSk7CiAgICAgICAgICBpbmRleC5zb3J0KGZ1bmN0aW9uKGksIGopIHsgcmV0dXJuIGFycmF5W2pdIC0gYXJyYXlbaV07IH0pOwogICAgICAgICAgZm9yIChqID0gMDsgaiA8IG07ICsraikgYXJyYXlbal0gPSBoYWxmZWRnZXNbaW5kZXhbal1dOwogICAgICAgICAgZm9yIChqID0gMDsgaiA8IG07ICsraikgaGFsZmVkZ2VzW2pdID0gYXJyYXlbal07CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcENlbGxzKHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIHZhciBuQ2VsbHMgPSBjZWxscy5sZW5ndGgsCiAgICAgICAgICBpQ2VsbCwKICAgICAgICAgIGNlbGwsCiAgICAgICAgICBzaXRlLAogICAgICAgICAgaUhhbGZlZGdlLAogICAgICAgICAgaGFsZmVkZ2VzLAogICAgICAgICAgbkhhbGZlZGdlcywKICAgICAgICAgIHN0YXJ0LAogICAgICAgICAgc3RhcnRYLAogICAgICAgICAgc3RhcnRZLAogICAgICAgICAgZW5kLAogICAgICAgICAgZW5kWCwKICAgICAgICAgIGVuZFksCiAgICAgICAgICBjb3ZlciA9IHRydWU7CgogICAgICBmb3IgKGlDZWxsID0gMDsgaUNlbGwgPCBuQ2VsbHM7ICsraUNlbGwpIHsKICAgICAgICBpZiAoY2VsbCA9IGNlbGxzW2lDZWxsXSkgewogICAgICAgICAgc2l0ZSA9IGNlbGwuc2l0ZTsKICAgICAgICAgIGhhbGZlZGdlcyA9IGNlbGwuaGFsZmVkZ2VzOwogICAgICAgICAgaUhhbGZlZGdlID0gaGFsZmVkZ2VzLmxlbmd0aDsKCiAgICAgICAgICAvLyBSZW1vdmUgYW55IGRhbmdsaW5nIGNsaXBwZWQgZWRnZXMuCiAgICAgICAgICB3aGlsZSAoaUhhbGZlZGdlLS0pIHsKICAgICAgICAgICAgaWYgKCFlZGdlc1toYWxmZWRnZXNbaUhhbGZlZGdlXV0pIHsKICAgICAgICAgICAgICBoYWxmZWRnZXMuc3BsaWNlKGlIYWxmZWRnZSwgMSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvLyBJbnNlcnQgYW55IGJvcmRlciBlZGdlcyBhcyBuZWNlc3NhcnkuCiAgICAgICAgICBpSGFsZmVkZ2UgPSAwLCBuSGFsZmVkZ2VzID0gaGFsZmVkZ2VzLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChpSGFsZmVkZ2UgPCBuSGFsZmVkZ2VzKSB7CiAgICAgICAgICAgIGVuZCA9IGNlbGxIYWxmZWRnZUVuZChjZWxsLCBlZGdlc1toYWxmZWRnZXNbaUhhbGZlZGdlXV0pLCBlbmRYID0gZW5kWzBdLCBlbmRZID0gZW5kWzFdOwogICAgICAgICAgICBzdGFydCA9IGNlbGxIYWxmZWRnZVN0YXJ0KGNlbGwsIGVkZ2VzW2hhbGZlZGdlc1srK2lIYWxmZWRnZSAlIG5IYWxmZWRnZXNdXSksIHN0YXJ0WCA9IHN0YXJ0WzBdLCBzdGFydFkgPSBzdGFydFsxXTsKICAgICAgICAgICAgaWYgKE1hdGguYWJzKGVuZFggLSBzdGFydFgpID4gZXBzaWxvbiQ0IHx8IE1hdGguYWJzKGVuZFkgLSBzdGFydFkpID4gZXBzaWxvbiQ0KSB7CiAgICAgICAgICAgICAgaGFsZmVkZ2VzLnNwbGljZShpSGFsZmVkZ2UsIDAsIGVkZ2VzLnB1c2goY3JlYXRlQm9yZGVyRWRnZShzaXRlLCBlbmQsCiAgICAgICAgICAgICAgICAgIE1hdGguYWJzKGVuZFggLSB4MCkgPCBlcHNpbG9uJDQgJiYgeTEgLSBlbmRZID4gZXBzaWxvbiQ0ID8gW3gwLCBNYXRoLmFicyhzdGFydFggLSB4MCkgPCBlcHNpbG9uJDQgPyBzdGFydFkgOiB5MV0KICAgICAgICAgICAgICAgICAgOiBNYXRoLmFicyhlbmRZIC0geTEpIDwgZXBzaWxvbiQ0ICYmIHgxIC0gZW5kWCA+IGVwc2lsb24kNCA/IFtNYXRoLmFicyhzdGFydFkgLSB5MSkgPCBlcHNpbG9uJDQgPyBzdGFydFggOiB4MSwgeTFdCiAgICAgICAgICAgICAgICAgIDogTWF0aC5hYnMoZW5kWCAtIHgxKSA8IGVwc2lsb24kNCAmJiBlbmRZIC0geTAgPiBlcHNpbG9uJDQgPyBbeDEsIE1hdGguYWJzKHN0YXJ0WCAtIHgxKSA8IGVwc2lsb24kNCA/IHN0YXJ0WSA6IHkwXQogICAgICAgICAgICAgICAgICA6IE1hdGguYWJzKGVuZFkgLSB5MCkgPCBlcHNpbG9uJDQgJiYgZW5kWCAtIHgwID4gZXBzaWxvbiQ0ID8gW01hdGguYWJzKHN0YXJ0WSAtIHkwKSA8IGVwc2lsb24kNCA/IHN0YXJ0WCA6IHgwLCB5MF0KICAgICAgICAgICAgICAgICAgOiBudWxsKSkgLSAxKTsKICAgICAgICAgICAgICArK25IYWxmZWRnZXM7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICBpZiAobkhhbGZlZGdlcykgY292ZXIgPSBmYWxzZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIElmIHRoZXJlIHdlcmVu4oCZdCBhbnkgZWRnZXMsIGhhdmUgdGhlIGNsb3Nlc3Qgc2l0ZSBjb3ZlciB0aGUgZXh0ZW50LgogICAgICAvLyBJdCBkb2VzbuKAmXQgbWF0dGVyIHdoaWNoIGNvcm5lciBvZiB0aGUgZXh0ZW50IHdlIG1lYXN1cmUhCiAgICAgIGlmIChjb3ZlcikgewogICAgICAgIHZhciBkeCwgZHksIGQyLCBkYyA9IEluZmluaXR5OwoKICAgICAgICBmb3IgKGlDZWxsID0gMCwgY292ZXIgPSBudWxsOyBpQ2VsbCA8IG5DZWxsczsgKytpQ2VsbCkgewogICAgICAgICAgaWYgKGNlbGwgPSBjZWxsc1tpQ2VsbF0pIHsKICAgICAgICAgICAgc2l0ZSA9IGNlbGwuc2l0ZTsKICAgICAgICAgICAgZHggPSBzaXRlWzBdIC0geDA7CiAgICAgICAgICAgIGR5ID0gc2l0ZVsxXSAtIHkwOwogICAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5OwogICAgICAgICAgICBpZiAoZDIgPCBkYykgZGMgPSBkMiwgY292ZXIgPSBjZWxsOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKGNvdmVyKSB7CiAgICAgICAgICB2YXIgdjAwID0gW3gwLCB5MF0sIHYwMSA9IFt4MCwgeTFdLCB2MTEgPSBbeDEsIHkxXSwgdjEwID0gW3gxLCB5MF07CiAgICAgICAgICBjb3Zlci5oYWxmZWRnZXMucHVzaCgKICAgICAgICAgICAgZWRnZXMucHVzaChjcmVhdGVCb3JkZXJFZGdlKHNpdGUgPSBjb3Zlci5zaXRlLCB2MDAsIHYwMSkpIC0gMSwKICAgICAgICAgICAgZWRnZXMucHVzaChjcmVhdGVCb3JkZXJFZGdlKHNpdGUsIHYwMSwgdjExKSkgLSAxLAogICAgICAgICAgICBlZGdlcy5wdXNoKGNyZWF0ZUJvcmRlckVkZ2Uoc2l0ZSwgdjExLCB2MTApKSAtIDEsCiAgICAgICAgICAgIGVkZ2VzLnB1c2goY3JlYXRlQm9yZGVyRWRnZShzaXRlLCB2MTAsIHYwMCkpIC0gMQogICAgICAgICAgKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIExhc3RseSBkZWxldGUgYW55IGNlbGxzIHdpdGggbm8gZWRnZXM7IHRoZXNlIHdlcmUgZW50aXJlbHkgY2xpcHBlZC4KICAgICAgZm9yIChpQ2VsbCA9IDA7IGlDZWxsIDwgbkNlbGxzOyArK2lDZWxsKSB7CiAgICAgICAgaWYgKGNlbGwgPSBjZWxsc1tpQ2VsbF0pIHsKICAgICAgICAgIGlmICghY2VsbC5oYWxmZWRnZXMubGVuZ3RoKSB7CiAgICAgICAgICAgIGRlbGV0ZSBjZWxsc1tpQ2VsbF07CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgdmFyIGNpcmNsZVBvb2wgPSBbXTsKCiAgICB2YXIgZmlyc3RDaXJjbGU7CgogICAgZnVuY3Rpb24gQ2lyY2xlKCkgewogICAgICBSZWRCbGFja05vZGUodGhpcyk7CiAgICAgIHRoaXMueCA9CiAgICAgIHRoaXMueSA9CiAgICAgIHRoaXMuYXJjID0KICAgICAgdGhpcy5zaXRlID0KICAgICAgdGhpcy5jeSA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gYXR0YWNoQ2lyY2xlKGFyYykgewogICAgICB2YXIgbEFyYyA9IGFyYy5QLAogICAgICAgICAgckFyYyA9IGFyYy5OOwoKICAgICAgaWYgKCFsQXJjIHx8ICFyQXJjKSByZXR1cm47CgogICAgICB2YXIgbFNpdGUgPSBsQXJjLnNpdGUsCiAgICAgICAgICBjU2l0ZSA9IGFyYy5zaXRlLAogICAgICAgICAgclNpdGUgPSByQXJjLnNpdGU7CgogICAgICBpZiAobFNpdGUgPT09IHJTaXRlKSByZXR1cm47CgogICAgICB2YXIgYnggPSBjU2l0ZVswXSwKICAgICAgICAgIGJ5ID0gY1NpdGVbMV0sCiAgICAgICAgICBheCA9IGxTaXRlWzBdIC0gYngsCiAgICAgICAgICBheSA9IGxTaXRlWzFdIC0gYnksCiAgICAgICAgICBjeCA9IHJTaXRlWzBdIC0gYngsCiAgICAgICAgICBjeSA9IHJTaXRlWzFdIC0gYnk7CgogICAgICB2YXIgZCA9IDIgKiAoYXggKiBjeSAtIGF5ICogY3gpOwogICAgICBpZiAoZCA+PSAtZXBzaWxvbjIkMikgcmV0dXJuOwoKICAgICAgdmFyIGhhID0gYXggKiBheCArIGF5ICogYXksCiAgICAgICAgICBoYyA9IGN4ICogY3ggKyBjeSAqIGN5LAogICAgICAgICAgeCA9IChjeSAqIGhhIC0gYXkgKiBoYykgLyBkLAogICAgICAgICAgeSA9IChheCAqIGhjIC0gY3ggKiBoYSkgLyBkOwoKICAgICAgdmFyIGNpcmNsZSA9IGNpcmNsZVBvb2wucG9wKCkgfHwgbmV3IENpcmNsZTsKICAgICAgY2lyY2xlLmFyYyA9IGFyYzsKICAgICAgY2lyY2xlLnNpdGUgPSBjU2l0ZTsKICAgICAgY2lyY2xlLnggPSB4ICsgYng7CiAgICAgIGNpcmNsZS55ID0gKGNpcmNsZS5jeSA9IHkgKyBieSkgKyBNYXRoLnNxcnQoeCAqIHggKyB5ICogeSk7IC8vIHkgYm90dG9tCgogICAgICBhcmMuY2lyY2xlID0gY2lyY2xlOwoKICAgICAgdmFyIGJlZm9yZSA9IG51bGwsCiAgICAgICAgICBub2RlID0gY2lyY2xlcy5fOwoKICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICBpZiAoY2lyY2xlLnkgPCBub2RlLnkgfHwgKGNpcmNsZS55ID09PSBub2RlLnkgJiYgY2lyY2xlLnggPD0gbm9kZS54KSkgewogICAgICAgICAgaWYgKG5vZGUuTCkgbm9kZSA9IG5vZGUuTDsKICAgICAgICAgIGVsc2UgeyBiZWZvcmUgPSBub2RlLlA7IGJyZWFrOyB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChub2RlLlIpIG5vZGUgPSBub2RlLlI7CiAgICAgICAgICBlbHNlIHsgYmVmb3JlID0gbm9kZTsgYnJlYWs7IH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGNpcmNsZXMuaW5zZXJ0KGJlZm9yZSwgY2lyY2xlKTsKICAgICAgaWYgKCFiZWZvcmUpIGZpcnN0Q2lyY2xlID0gY2lyY2xlOwogICAgfQoKICAgIGZ1bmN0aW9uIGRldGFjaENpcmNsZShhcmMpIHsKICAgICAgdmFyIGNpcmNsZSA9IGFyYy5jaXJjbGU7CiAgICAgIGlmIChjaXJjbGUpIHsKICAgICAgICBpZiAoIWNpcmNsZS5QKSBmaXJzdENpcmNsZSA9IGNpcmNsZS5OOwogICAgICAgIGNpcmNsZXMucmVtb3ZlKGNpcmNsZSk7CiAgICAgICAgY2lyY2xlUG9vbC5wdXNoKGNpcmNsZSk7CiAgICAgICAgUmVkQmxhY2tOb2RlKGNpcmNsZSk7CiAgICAgICAgYXJjLmNpcmNsZSA9IG51bGw7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgYmVhY2hQb29sID0gW107CgogICAgZnVuY3Rpb24gQmVhY2goKSB7CiAgICAgIFJlZEJsYWNrTm9kZSh0aGlzKTsKICAgICAgdGhpcy5lZGdlID0KICAgICAgdGhpcy5zaXRlID0KICAgICAgdGhpcy5jaXJjbGUgPSBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZUJlYWNoKHNpdGUpIHsKICAgICAgdmFyIGJlYWNoID0gYmVhY2hQb29sLnBvcCgpIHx8IG5ldyBCZWFjaDsKICAgICAgYmVhY2guc2l0ZSA9IHNpdGU7CiAgICAgIHJldHVybiBiZWFjaDsKICAgIH0KCiAgICBmdW5jdGlvbiBkZXRhY2hCZWFjaChiZWFjaCkgewogICAgICBkZXRhY2hDaXJjbGUoYmVhY2gpOwogICAgICBiZWFjaGVzLnJlbW92ZShiZWFjaCk7CiAgICAgIGJlYWNoUG9vbC5wdXNoKGJlYWNoKTsKICAgICAgUmVkQmxhY2tOb2RlKGJlYWNoKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVCZWFjaChiZWFjaCkgewogICAgICB2YXIgY2lyY2xlID0gYmVhY2guY2lyY2xlLAogICAgICAgICAgeCA9IGNpcmNsZS54LAogICAgICAgICAgeSA9IGNpcmNsZS5jeSwKICAgICAgICAgIHZlcnRleCA9IFt4LCB5XSwKICAgICAgICAgIHByZXZpb3VzID0gYmVhY2guUCwKICAgICAgICAgIG5leHQgPSBiZWFjaC5OLAogICAgICAgICAgZGlzYXBwZWFyaW5nID0gW2JlYWNoXTsKCiAgICAgIGRldGFjaEJlYWNoKGJlYWNoKTsKCiAgICAgIHZhciBsQXJjID0gcHJldmlvdXM7CiAgICAgIHdoaWxlIChsQXJjLmNpcmNsZQogICAgICAgICAgJiYgTWF0aC5hYnMoeCAtIGxBcmMuY2lyY2xlLngpIDwgZXBzaWxvbiQ0CiAgICAgICAgICAmJiBNYXRoLmFicyh5IC0gbEFyYy5jaXJjbGUuY3kpIDwgZXBzaWxvbiQ0KSB7CiAgICAgICAgcHJldmlvdXMgPSBsQXJjLlA7CiAgICAgICAgZGlzYXBwZWFyaW5nLnVuc2hpZnQobEFyYyk7CiAgICAgICAgZGV0YWNoQmVhY2gobEFyYyk7CiAgICAgICAgbEFyYyA9IHByZXZpb3VzOwogICAgICB9CgogICAgICBkaXNhcHBlYXJpbmcudW5zaGlmdChsQXJjKTsKICAgICAgZGV0YWNoQ2lyY2xlKGxBcmMpOwoKICAgICAgdmFyIHJBcmMgPSBuZXh0OwogICAgICB3aGlsZSAockFyYy5jaXJjbGUKICAgICAgICAgICYmIE1hdGguYWJzKHggLSByQXJjLmNpcmNsZS54KSA8IGVwc2lsb24kNAogICAgICAgICAgJiYgTWF0aC5hYnMoeSAtIHJBcmMuY2lyY2xlLmN5KSA8IGVwc2lsb24kNCkgewogICAgICAgIG5leHQgPSByQXJjLk47CiAgICAgICAgZGlzYXBwZWFyaW5nLnB1c2gockFyYyk7CiAgICAgICAgZGV0YWNoQmVhY2gockFyYyk7CiAgICAgICAgckFyYyA9IG5leHQ7CiAgICAgIH0KCiAgICAgIGRpc2FwcGVhcmluZy5wdXNoKHJBcmMpOwogICAgICBkZXRhY2hDaXJjbGUockFyYyk7CgogICAgICB2YXIgbkFyY3MgPSBkaXNhcHBlYXJpbmcubGVuZ3RoLAogICAgICAgICAgaUFyYzsKICAgICAgZm9yIChpQXJjID0gMTsgaUFyYyA8IG5BcmNzOyArK2lBcmMpIHsKICAgICAgICByQXJjID0gZGlzYXBwZWFyaW5nW2lBcmNdOwogICAgICAgIGxBcmMgPSBkaXNhcHBlYXJpbmdbaUFyYyAtIDFdOwogICAgICAgIHNldEVkZ2VFbmQockFyYy5lZGdlLCBsQXJjLnNpdGUsIHJBcmMuc2l0ZSwgdmVydGV4KTsKICAgICAgfQoKICAgICAgbEFyYyA9IGRpc2FwcGVhcmluZ1swXTsKICAgICAgckFyYyA9IGRpc2FwcGVhcmluZ1tuQXJjcyAtIDFdOwogICAgICByQXJjLmVkZ2UgPSBjcmVhdGVFZGdlKGxBcmMuc2l0ZSwgckFyYy5zaXRlLCBudWxsLCB2ZXJ0ZXgpOwoKICAgICAgYXR0YWNoQ2lyY2xlKGxBcmMpOwogICAgICBhdHRhY2hDaXJjbGUockFyYyk7CiAgICB9CgogICAgZnVuY3Rpb24gYWRkQmVhY2goc2l0ZSkgewogICAgICB2YXIgeCA9IHNpdGVbMF0sCiAgICAgICAgICBkaXJlY3RyaXggPSBzaXRlWzFdLAogICAgICAgICAgbEFyYywKICAgICAgICAgIHJBcmMsCiAgICAgICAgICBkeGwsCiAgICAgICAgICBkeHIsCiAgICAgICAgICBub2RlID0gYmVhY2hlcy5fOwoKICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICBkeGwgPSBsZWZ0QnJlYWtQb2ludChub2RlLCBkaXJlY3RyaXgpIC0geDsKICAgICAgICBpZiAoZHhsID4gZXBzaWxvbiQ0KSBub2RlID0gbm9kZS5MOyBlbHNlIHsKICAgICAgICAgIGR4ciA9IHggLSByaWdodEJyZWFrUG9pbnQobm9kZSwgZGlyZWN0cml4KTsKICAgICAgICAgIGlmIChkeHIgPiBlcHNpbG9uJDQpIHsKICAgICAgICAgICAgaWYgKCFub2RlLlIpIHsKICAgICAgICAgICAgICBsQXJjID0gbm9kZTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBub2RlID0gbm9kZS5SOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKGR4bCA+IC1lcHNpbG9uJDQpIHsKICAgICAgICAgICAgICBsQXJjID0gbm9kZS5QOwogICAgICAgICAgICAgIHJBcmMgPSBub2RlOwogICAgICAgICAgICB9IGVsc2UgaWYgKGR4ciA+IC1lcHNpbG9uJDQpIHsKICAgICAgICAgICAgICBsQXJjID0gbm9kZTsKICAgICAgICAgICAgICByQXJjID0gbm9kZS5OOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGxBcmMgPSByQXJjID0gbm9kZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGNyZWF0ZUNlbGwoc2l0ZSk7CiAgICAgIHZhciBuZXdBcmMgPSBjcmVhdGVCZWFjaChzaXRlKTsKICAgICAgYmVhY2hlcy5pbnNlcnQobEFyYywgbmV3QXJjKTsKCiAgICAgIGlmICghbEFyYyAmJiAhckFyYykgcmV0dXJuOwoKICAgICAgaWYgKGxBcmMgPT09IHJBcmMpIHsKICAgICAgICBkZXRhY2hDaXJjbGUobEFyYyk7CiAgICAgICAgckFyYyA9IGNyZWF0ZUJlYWNoKGxBcmMuc2l0ZSk7CiAgICAgICAgYmVhY2hlcy5pbnNlcnQobmV3QXJjLCByQXJjKTsKICAgICAgICBuZXdBcmMuZWRnZSA9IHJBcmMuZWRnZSA9IGNyZWF0ZUVkZ2UobEFyYy5zaXRlLCBuZXdBcmMuc2l0ZSk7CiAgICAgICAgYXR0YWNoQ2lyY2xlKGxBcmMpOwogICAgICAgIGF0dGFjaENpcmNsZShyQXJjKTsKICAgICAgICByZXR1cm47CiAgICAgIH0KCiAgICAgIGlmICghckFyYykgeyAvLyAmJiBsQXJjCiAgICAgICAgbmV3QXJjLmVkZ2UgPSBjcmVhdGVFZGdlKGxBcmMuc2l0ZSwgbmV3QXJjLnNpdGUpOwogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgLy8gZWxzZSBsQXJjICE9PSByQXJjCiAgICAgIGRldGFjaENpcmNsZShsQXJjKTsKICAgICAgZGV0YWNoQ2lyY2xlKHJBcmMpOwoKICAgICAgdmFyIGxTaXRlID0gbEFyYy5zaXRlLAogICAgICAgICAgYXggPSBsU2l0ZVswXSwKICAgICAgICAgIGF5ID0gbFNpdGVbMV0sCiAgICAgICAgICBieCA9IHNpdGVbMF0gLSBheCwKICAgICAgICAgIGJ5ID0gc2l0ZVsxXSAtIGF5LAogICAgICAgICAgclNpdGUgPSByQXJjLnNpdGUsCiAgICAgICAgICBjeCA9IHJTaXRlWzBdIC0gYXgsCiAgICAgICAgICBjeSA9IHJTaXRlWzFdIC0gYXksCiAgICAgICAgICBkID0gMiAqIChieCAqIGN5IC0gYnkgKiBjeCksCiAgICAgICAgICBoYiA9IGJ4ICogYnggKyBieSAqIGJ5LAogICAgICAgICAgaGMgPSBjeCAqIGN4ICsgY3kgKiBjeSwKICAgICAgICAgIHZlcnRleCA9IFsoY3kgKiBoYiAtIGJ5ICogaGMpIC8gZCArIGF4LCAoYnggKiBoYyAtIGN4ICogaGIpIC8gZCArIGF5XTsKCiAgICAgIHNldEVkZ2VFbmQockFyYy5lZGdlLCBsU2l0ZSwgclNpdGUsIHZlcnRleCk7CiAgICAgIG5ld0FyYy5lZGdlID0gY3JlYXRlRWRnZShsU2l0ZSwgc2l0ZSwgbnVsbCwgdmVydGV4KTsKICAgICAgckFyYy5lZGdlID0gY3JlYXRlRWRnZShzaXRlLCByU2l0ZSwgbnVsbCwgdmVydGV4KTsKICAgICAgYXR0YWNoQ2lyY2xlKGxBcmMpOwogICAgICBhdHRhY2hDaXJjbGUockFyYyk7CiAgICB9CgogICAgZnVuY3Rpb24gbGVmdEJyZWFrUG9pbnQoYXJjLCBkaXJlY3RyaXgpIHsKICAgICAgdmFyIHNpdGUgPSBhcmMuc2l0ZSwKICAgICAgICAgIHJmb2N4ID0gc2l0ZVswXSwKICAgICAgICAgIHJmb2N5ID0gc2l0ZVsxXSwKICAgICAgICAgIHBieTIgPSByZm9jeSAtIGRpcmVjdHJpeDsKCiAgICAgIGlmICghcGJ5MikgcmV0dXJuIHJmb2N4OwoKICAgICAgdmFyIGxBcmMgPSBhcmMuUDsKICAgICAgaWYgKCFsQXJjKSByZXR1cm4gLUluZmluaXR5OwoKICAgICAgc2l0ZSA9IGxBcmMuc2l0ZTsKICAgICAgdmFyIGxmb2N4ID0gc2l0ZVswXSwKICAgICAgICAgIGxmb2N5ID0gc2l0ZVsxXSwKICAgICAgICAgIHBsYnkyID0gbGZvY3kgLSBkaXJlY3RyaXg7CgogICAgICBpZiAoIXBsYnkyKSByZXR1cm4gbGZvY3g7CgogICAgICB2YXIgaGwgPSBsZm9jeCAtIHJmb2N4LAogICAgICAgICAgYWJ5MiA9IDEgLyBwYnkyIC0gMSAvIHBsYnkyLAogICAgICAgICAgYiA9IGhsIC8gcGxieTI7CgogICAgICBpZiAoYWJ5MikgcmV0dXJuICgtYiArIE1hdGguc3FydChiICogYiAtIDIgKiBhYnkyICogKGhsICogaGwgLyAoLTIgKiBwbGJ5MikgLSBsZm9jeSArIHBsYnkyIC8gMiArIHJmb2N5IC0gcGJ5MiAvIDIpKSkgLyBhYnkyICsgcmZvY3g7CgogICAgICByZXR1cm4gKHJmb2N4ICsgbGZvY3gpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiByaWdodEJyZWFrUG9pbnQoYXJjLCBkaXJlY3RyaXgpIHsKICAgICAgdmFyIHJBcmMgPSBhcmMuTjsKICAgICAgaWYgKHJBcmMpIHJldHVybiBsZWZ0QnJlYWtQb2ludChyQXJjLCBkaXJlY3RyaXgpOwogICAgICB2YXIgc2l0ZSA9IGFyYy5zaXRlOwogICAgICByZXR1cm4gc2l0ZVsxXSA9PT0gZGlyZWN0cml4ID8gc2l0ZVswXSA6IEluZmluaXR5OwogICAgfQoKICAgIHZhciBlcHNpbG9uJDQgPSAxZS02OwogICAgdmFyIGVwc2lsb24yJDIgPSAxZS0xMjsKICAgIHZhciBiZWFjaGVzOwogICAgdmFyIGNlbGxzOwogICAgdmFyIGNpcmNsZXM7CiAgICB2YXIgZWRnZXM7CgogICAgZnVuY3Rpb24gdHJpYW5nbGVBcmVhKGEsIGIsIGMpIHsKICAgICAgcmV0dXJuIChhWzBdIC0gY1swXSkgKiAoYlsxXSAtIGFbMV0pIC0gKGFbMF0gLSBiWzBdKSAqIChjWzFdIC0gYVsxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGV4aWNvZ3JhcGhpYyhhLCBiKSB7CiAgICAgIHJldHVybiBiWzFdIC0gYVsxXQogICAgICAgICAgfHwgYlswXSAtIGFbMF07CiAgICB9CgogICAgZnVuY3Rpb24gRGlhZ3JhbShzaXRlcywgZXh0ZW50KSB7CiAgICAgIHZhciBzaXRlID0gc2l0ZXMuc29ydChsZXhpY29ncmFwaGljKS5wb3AoKSwKICAgICAgICAgIHgsCiAgICAgICAgICB5LAogICAgICAgICAgY2lyY2xlOwoKICAgICAgZWRnZXMgPSBbXTsKICAgICAgY2VsbHMgPSBuZXcgQXJyYXkoc2l0ZXMubGVuZ3RoKTsKICAgICAgYmVhY2hlcyA9IG5ldyBSZWRCbGFja1RyZWU7CiAgICAgIGNpcmNsZXMgPSBuZXcgUmVkQmxhY2tUcmVlOwoKICAgICAgd2hpbGUgKHRydWUpIHsKICAgICAgICBjaXJjbGUgPSBmaXJzdENpcmNsZTsKICAgICAgICBpZiAoc2l0ZSAmJiAoIWNpcmNsZSB8fCBzaXRlWzFdIDwgY2lyY2xlLnkgfHwgKHNpdGVbMV0gPT09IGNpcmNsZS55ICYmIHNpdGVbMF0gPCBjaXJjbGUueCkpKSB7CiAgICAgICAgICBpZiAoc2l0ZVswXSAhPT0geCB8fCBzaXRlWzFdICE9PSB5KSB7CiAgICAgICAgICAgIGFkZEJlYWNoKHNpdGUpOwogICAgICAgICAgICB4ID0gc2l0ZVswXSwgeSA9IHNpdGVbMV07CiAgICAgICAgICB9CiAgICAgICAgICBzaXRlID0gc2l0ZXMucG9wKCk7CiAgICAgICAgfSBlbHNlIGlmIChjaXJjbGUpIHsKICAgICAgICAgIHJlbW92ZUJlYWNoKGNpcmNsZS5hcmMpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHNvcnRDZWxsSGFsZmVkZ2VzKCk7CgogICAgICBpZiAoZXh0ZW50KSB7CiAgICAgICAgdmFyIHgwID0gK2V4dGVudFswXVswXSwKICAgICAgICAgICAgeTAgPSArZXh0ZW50WzBdWzFdLAogICAgICAgICAgICB4MSA9ICtleHRlbnRbMV1bMF0sCiAgICAgICAgICAgIHkxID0gK2V4dGVudFsxXVsxXTsKICAgICAgICBjbGlwRWRnZXMoeDAsIHkwLCB4MSwgeTEpOwogICAgICAgIGNsaXBDZWxscyh4MCwgeTAsIHgxLCB5MSk7CiAgICAgIH0KCiAgICAgIHRoaXMuZWRnZXMgPSBlZGdlczsKICAgICAgdGhpcy5jZWxscyA9IGNlbGxzOwoKICAgICAgYmVhY2hlcyA9CiAgICAgIGNpcmNsZXMgPQogICAgICBlZGdlcyA9CiAgICAgIGNlbGxzID0gbnVsbDsKICAgIH0KCiAgICBEaWFncmFtLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IERpYWdyYW0sCgogICAgICBwb2x5Z29uczogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGVkZ2VzID0gdGhpcy5lZGdlczsKCiAgICAgICAgcmV0dXJuIHRoaXMuY2VsbHMubWFwKGZ1bmN0aW9uKGNlbGwpIHsKICAgICAgICAgIHZhciBwb2x5Z29uID0gY2VsbC5oYWxmZWRnZXMubWFwKGZ1bmN0aW9uKGkpIHsgcmV0dXJuIGNlbGxIYWxmZWRnZVN0YXJ0KGNlbGwsIGVkZ2VzW2ldKTsgfSk7CiAgICAgICAgICBwb2x5Z29uLmRhdGEgPSBjZWxsLnNpdGUuZGF0YTsKICAgICAgICAgIHJldHVybiBwb2x5Z29uOwogICAgICAgIH0pOwogICAgICB9LAoKICAgICAgdHJpYW5nbGVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdHJpYW5nbGVzID0gW10sCiAgICAgICAgICAgIGVkZ2VzID0gdGhpcy5lZGdlczsKCiAgICAgICAgdGhpcy5jZWxscy5mb3JFYWNoKGZ1bmN0aW9uKGNlbGwsIGkpIHsKICAgICAgICAgIGlmICghKG0gPSAoaGFsZmVkZ2VzID0gY2VsbC5oYWxmZWRnZXMpLmxlbmd0aCkpIHJldHVybjsKICAgICAgICAgIHZhciBzaXRlID0gY2VsbC5zaXRlLAogICAgICAgICAgICAgIGhhbGZlZGdlcywKICAgICAgICAgICAgICBqID0gLTEsCiAgICAgICAgICAgICAgbSwKICAgICAgICAgICAgICBzMCwKICAgICAgICAgICAgICBlMSA9IGVkZ2VzW2hhbGZlZGdlc1ttIC0gMV1dLAogICAgICAgICAgICAgIHMxID0gZTEubGVmdCA9PT0gc2l0ZSA/IGUxLnJpZ2h0IDogZTEubGVmdDsKCiAgICAgICAgICB3aGlsZSAoKytqIDwgbSkgewogICAgICAgICAgICBzMCA9IHMxOwogICAgICAgICAgICBlMSA9IGVkZ2VzW2hhbGZlZGdlc1tqXV07CiAgICAgICAgICAgIHMxID0gZTEubGVmdCA9PT0gc2l0ZSA/IGUxLnJpZ2h0IDogZTEubGVmdDsKICAgICAgICAgICAgaWYgKHMwICYmIHMxICYmIGkgPCBzMC5pbmRleCAmJiBpIDwgczEuaW5kZXggJiYgdHJpYW5nbGVBcmVhKHNpdGUsIHMwLCBzMSkgPCAwKSB7CiAgICAgICAgICAgICAgdHJpYW5nbGVzLnB1c2goW3NpdGUuZGF0YSwgczAuZGF0YSwgczEuZGF0YV0pOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIHJldHVybiB0cmlhbmdsZXM7CiAgICAgIH0sCgogICAgICBsaW5rczogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZWRnZXMuZmlsdGVyKGZ1bmN0aW9uKGVkZ2UpIHsKICAgICAgICAgIHJldHVybiBlZGdlLnJpZ2h0OwogICAgICAgIH0pLm1hcChmdW5jdGlvbihlZGdlKSB7CiAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICBzb3VyY2U6IGVkZ2UubGVmdC5kYXRhLAogICAgICAgICAgICB0YXJnZXQ6IGVkZ2UucmlnaHQuZGF0YQogICAgICAgICAgfTsKICAgICAgICB9KTsKICAgICAgfSwKCiAgICAgIGZpbmQ6IGZ1bmN0aW9uKHgsIHksIHJhZGl1cykgewogICAgICAgIHZhciB0aGF0ID0gdGhpcywgaTAsIGkxID0gdGhhdC5fZm91bmQgfHwgMCwgbiA9IHRoYXQuY2VsbHMubGVuZ3RoLCBjZWxsOwoKICAgICAgICAvLyBVc2UgdGhlIHByZXZpb3VzbHktZm91bmQgY2VsbCwgb3Igc3RhcnQgd2l0aCBhbiBhcmJpdHJhcnkgb25lLgogICAgICAgIHdoaWxlICghKGNlbGwgPSB0aGF0LmNlbGxzW2kxXSkpIGlmICgrK2kxID49IG4pIHJldHVybiBudWxsOwogICAgICAgIHZhciBkeCA9IHggLSBjZWxsLnNpdGVbMF0sIGR5ID0geSAtIGNlbGwuc2l0ZVsxXSwgZDIgPSBkeCAqIGR4ICsgZHkgKiBkeTsKCiAgICAgICAgLy8gVHJhdmVyc2UgdGhlIGhhbGYtZWRnZXMgdG8gZmluZCBhIGNsb3NlciBjZWxsLCBpZiBhbnkuCiAgICAgICAgZG8gewogICAgICAgICAgY2VsbCA9IHRoYXQuY2VsbHNbaTAgPSBpMV0sIGkxID0gbnVsbDsKICAgICAgICAgIGNlbGwuaGFsZmVkZ2VzLmZvckVhY2goZnVuY3Rpb24oZSkgewogICAgICAgICAgICB2YXIgZWRnZSA9IHRoYXQuZWRnZXNbZV0sIHYgPSBlZGdlLmxlZnQ7CiAgICAgICAgICAgIGlmICgodiA9PT0gY2VsbC5zaXRlIHx8ICF2KSAmJiAhKHYgPSBlZGdlLnJpZ2h0KSkgcmV0dXJuOwogICAgICAgICAgICB2YXIgdnggPSB4IC0gdlswXSwgdnkgPSB5IC0gdlsxXSwgdjIgPSB2eCAqIHZ4ICsgdnkgKiB2eTsKICAgICAgICAgICAgaWYgKHYyIDwgZDIpIGQyID0gdjIsIGkxID0gdi5pbmRleDsKICAgICAgICAgIH0pOwogICAgICAgIH0gd2hpbGUgKGkxICE9PSBudWxsKTsKCiAgICAgICAgdGhhdC5fZm91bmQgPSBpMDsKCiAgICAgICAgcmV0dXJuIHJhZGl1cyA9PSBudWxsIHx8IGQyIDw9IHJhZGl1cyAqIHJhZGl1cyA/IGNlbGwuc2l0ZSA6IG51bGw7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gdm9yb25vaSgpIHsKICAgICAgdmFyIHggPSB4JDQsCiAgICAgICAgICB5ID0geSQ0LAogICAgICAgICAgZXh0ZW50ID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIHZvcm9ub2koZGF0YSkgewogICAgICAgIHJldHVybiBuZXcgRGlhZ3JhbShkYXRhLm1hcChmdW5jdGlvbihkLCBpKSB7CiAgICAgICAgICB2YXIgcyA9IFtNYXRoLnJvdW5kKHgoZCwgaSwgZGF0YSkgLyBlcHNpbG9uJDQpICogZXBzaWxvbiQ0LCBNYXRoLnJvdW5kKHkoZCwgaSwgZGF0YSkgLyBlcHNpbG9uJDQpICogZXBzaWxvbiQ0XTsKICAgICAgICAgIHMuaW5kZXggPSBpOwogICAgICAgICAgcy5kYXRhID0gZDsKICAgICAgICAgIHJldHVybiBzOwogICAgICAgIH0pLCBleHRlbnQpOwogICAgICB9CgogICAgICB2b3Jvbm9pLnBvbHlnb25zID0gZnVuY3Rpb24oZGF0YSkgewogICAgICAgIHJldHVybiB2b3Jvbm9pKGRhdGEpLnBvbHlnb25zKCk7CiAgICAgIH07CgogICAgICB2b3Jvbm9pLmxpbmtzID0gZnVuY3Rpb24oZGF0YSkgewogICAgICAgIHJldHVybiB2b3Jvbm9pKGRhdGEpLmxpbmtzKCk7CiAgICAgIH07CgogICAgICB2b3Jvbm9pLnRyaWFuZ2xlcyA9IGZ1bmN0aW9uKGRhdGEpIHsKICAgICAgICByZXR1cm4gdm9yb25vaShkYXRhKS50cmlhbmdsZXMoKTsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYygrXyksIHZvcm9ub2kpIDogeDsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkYygrXyksIHZvcm9ub2kpIDogeTsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kuZXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGV4dGVudCA9IF8gPT0gbnVsbCA/IG51bGwgOiBbWytfWzBdWzBdLCArX1swXVsxXV0sIFsrX1sxXVswXSwgK19bMV1bMV1dXSwgdm9yb25vaSkgOiBleHRlbnQgJiYgW1tleHRlbnRbMF1bMF0sIGV4dGVudFswXVsxXV0sIFtleHRlbnRbMV1bMF0sIGV4dGVudFsxXVsxXV1dOwogICAgICB9OwoKICAgICAgdm9yb25vaS5zaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGV4dGVudCA9IF8gPT0gbnVsbCA/IG51bGwgOiBbWzAsIDBdLCBbK19bMF0sICtfWzFdXV0sIHZvcm9ub2kpIDogZXh0ZW50ICYmIFtleHRlbnRbMV1bMF0gLSBleHRlbnRbMF1bMF0sIGV4dGVudFsxXVsxXSAtIGV4dGVudFswXVsxXV07CiAgICAgIH07CgogICAgICByZXR1cm4gdm9yb25vaTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudCRkKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIFpvb21FdmVudCh0YXJnZXQsIHR5cGUsIHRyYW5zZm9ybSkgewogICAgICB0aGlzLnRhcmdldCA9IHRhcmdldDsKICAgICAgdGhpcy50eXBlID0gdHlwZTsKICAgICAgdGhpcy50cmFuc2Zvcm0gPSB0cmFuc2Zvcm07CiAgICB9CgogICAgZnVuY3Rpb24gVHJhbnNmb3JtKGssIHgsIHkpIHsKICAgICAgdGhpcy5rID0gazsKICAgICAgdGhpcy54ID0geDsKICAgICAgdGhpcy55ID0geTsKICAgIH0KCiAgICBUcmFuc2Zvcm0ucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVHJhbnNmb3JtLAogICAgICBzY2FsZTogZnVuY3Rpb24oaykgewogICAgICAgIHJldHVybiBrID09PSAxID8gdGhpcyA6IG5ldyBUcmFuc2Zvcm0odGhpcy5rICogaywgdGhpcy54LCB0aGlzLnkpOwogICAgICB9LAogICAgICB0cmFuc2xhdGU6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICByZXR1cm4geCA9PT0gMCAmIHkgPT09IDAgPyB0aGlzIDogbmV3IFRyYW5zZm9ybSh0aGlzLmssIHRoaXMueCArIHRoaXMuayAqIHgsIHRoaXMueSArIHRoaXMuayAqIHkpOwogICAgICB9LAogICAgICBhcHBseTogZnVuY3Rpb24ocG9pbnQpIHsKICAgICAgICByZXR1cm4gW3BvaW50WzBdICogdGhpcy5rICsgdGhpcy54LCBwb2ludFsxXSAqIHRoaXMuayArIHRoaXMueV07CiAgICAgIH0sCiAgICAgIGFwcGx5WDogZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiB4ICogdGhpcy5rICsgdGhpcy54OwogICAgICB9LAogICAgICBhcHBseVk6IGZ1bmN0aW9uKHkpIHsKICAgICAgICByZXR1cm4geSAqIHRoaXMuayArIHRoaXMueTsKICAgICAgfSwKICAgICAgaW52ZXJ0OiBmdW5jdGlvbihsb2NhdGlvbikgewogICAgICAgIHJldHVybiBbKGxvY2F0aW9uWzBdIC0gdGhpcy54KSAvIHRoaXMuaywgKGxvY2F0aW9uWzFdIC0gdGhpcy55KSAvIHRoaXMua107CiAgICAgIH0sCiAgICAgIGludmVydFg6IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gKHggLSB0aGlzLngpIC8gdGhpcy5rOwogICAgICB9LAogICAgICBpbnZlcnRZOiBmdW5jdGlvbih5KSB7CiAgICAgICAgcmV0dXJuICh5IC0gdGhpcy55KSAvIHRoaXMuazsKICAgICAgfSwKICAgICAgcmVzY2FsZVg6IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4geC5jb3B5KCkuZG9tYWluKHgucmFuZ2UoKS5tYXAodGhpcy5pbnZlcnRYLCB0aGlzKS5tYXAoeC5pbnZlcnQsIHgpKTsKICAgICAgfSwKICAgICAgcmVzY2FsZVk6IGZ1bmN0aW9uKHkpIHsKICAgICAgICByZXR1cm4geS5jb3B5KCkuZG9tYWluKHkucmFuZ2UoKS5tYXAodGhpcy5pbnZlcnRZLCB0aGlzKS5tYXAoeS5pbnZlcnQsIHkpKTsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAidHJhbnNsYXRlKCIgKyB0aGlzLnggKyAiLCIgKyB0aGlzLnkgKyAiKSBzY2FsZSgiICsgdGhpcy5rICsgIikiOwogICAgICB9CiAgICB9OwoKICAgIHZhciBpZGVudGl0eSQ5ID0gbmV3IFRyYW5zZm9ybSgxLCAwLCAwKTsKCiAgICB0cmFuc2Zvcm0kMS5wcm90b3R5cGUgPSBUcmFuc2Zvcm0ucHJvdG90eXBlOwoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybSQxKG5vZGUpIHsKICAgICAgd2hpbGUgKCFub2RlLl9fem9vbSkgaWYgKCEobm9kZSA9IG5vZGUucGFyZW50Tm9kZSkpIHJldHVybiBpZGVudGl0eSQ5OwogICAgICByZXR1cm4gbm9kZS5fX3pvb207CiAgICB9CgogICAgZnVuY3Rpb24gbm9wcm9wYWdhdGlvbiQyKCkgewogICAgICBldmVudC5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2V2ZW50JDIoKSB7CiAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CiAgICAgIGV2ZW50LnN0b3BJbW1lZGlhdGVQcm9wYWdhdGlvbigpOwogICAgfQoKICAgIC8vIElnbm9yZSByaWdodC1jbGljaywgc2luY2UgdGhhdCBzaG91bGQgb3BlbiB0aGUgY29udGV4dCBtZW51LgogICAgZnVuY3Rpb24gZGVmYXVsdEZpbHRlciQyKCkgewogICAgICByZXR1cm4gIWV2ZW50LmN0cmxLZXkgJiYgIWV2ZW50LmJ1dHRvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0RXh0ZW50JDEoKSB7CiAgICAgIHZhciBlID0gdGhpczsKICAgICAgaWYgKGUgaW5zdGFuY2VvZiBTVkdFbGVtZW50KSB7CiAgICAgICAgZSA9IGUub3duZXJTVkdFbGVtZW50IHx8IGU7CiAgICAgICAgaWYgKGUuaGFzQXR0cmlidXRlKCJ2aWV3Qm94IikpIHsKICAgICAgICAgIGUgPSBlLnZpZXdCb3guYmFzZVZhbDsKICAgICAgICAgIHJldHVybiBbW2UueCwgZS55XSwgW2UueCArIGUud2lkdGgsIGUueSArIGUuaGVpZ2h0XV07CiAgICAgICAgfQogICAgICAgIHJldHVybiBbWzAsIDBdLCBbZS53aWR0aC5iYXNlVmFsLnZhbHVlLCBlLmhlaWdodC5iYXNlVmFsLnZhbHVlXV07CiAgICAgIH0KICAgICAgcmV0dXJuIFtbMCwgMF0sIFtlLmNsaWVudFdpZHRoLCBlLmNsaWVudEhlaWdodF1dOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRUcmFuc2Zvcm0oKSB7CiAgICAgIHJldHVybiB0aGlzLl9fem9vbSB8fCBpZGVudGl0eSQ5OwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRXaGVlbERlbHRhKCkgewogICAgICByZXR1cm4gLWV2ZW50LmRlbHRhWSAqIChldmVudC5kZWx0YU1vZGUgPT09IDEgPyAwLjA1IDogZXZlbnQuZGVsdGFNb2RlID8gMSA6IDAuMDAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0VG91Y2hhYmxlJDIoKSB7CiAgICAgIHJldHVybiBuYXZpZ2F0b3IubWF4VG91Y2hQb2ludHMgfHwgKCJvbnRvdWNoc3RhcnQiIGluIHRoaXMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRDb25zdHJhaW4odHJhbnNmb3JtLCBleHRlbnQsIHRyYW5zbGF0ZUV4dGVudCkgewogICAgICB2YXIgZHgwID0gdHJhbnNmb3JtLmludmVydFgoZXh0ZW50WzBdWzBdKSAtIHRyYW5zbGF0ZUV4dGVudFswXVswXSwKICAgICAgICAgIGR4MSA9IHRyYW5zZm9ybS5pbnZlcnRYKGV4dGVudFsxXVswXSkgLSB0cmFuc2xhdGVFeHRlbnRbMV1bMF0sCiAgICAgICAgICBkeTAgPSB0cmFuc2Zvcm0uaW52ZXJ0WShleHRlbnRbMF1bMV0pIC0gdHJhbnNsYXRlRXh0ZW50WzBdWzFdLAogICAgICAgICAgZHkxID0gdHJhbnNmb3JtLmludmVydFkoZXh0ZW50WzFdWzFdKSAtIHRyYW5zbGF0ZUV4dGVudFsxXVsxXTsKICAgICAgcmV0dXJuIHRyYW5zZm9ybS50cmFuc2xhdGUoCiAgICAgICAgZHgxID4gZHgwID8gKGR4MCArIGR4MSkgLyAyIDogTWF0aC5taW4oMCwgZHgwKSB8fCBNYXRoLm1heCgwLCBkeDEpLAogICAgICAgIGR5MSA+IGR5MCA/IChkeTAgKyBkeTEpIC8gMiA6IE1hdGgubWluKDAsIGR5MCkgfHwgTWF0aC5tYXgoMCwgZHkxKQogICAgICApOwogICAgfQoKICAgIGZ1bmN0aW9uIHpvb20oKSB7CiAgICAgIHZhciBmaWx0ZXIgPSBkZWZhdWx0RmlsdGVyJDIsCiAgICAgICAgICBleHRlbnQgPSBkZWZhdWx0RXh0ZW50JDEsCiAgICAgICAgICBjb25zdHJhaW4gPSBkZWZhdWx0Q29uc3RyYWluLAogICAgICAgICAgd2hlZWxEZWx0YSA9IGRlZmF1bHRXaGVlbERlbHRhLAogICAgICAgICAgdG91Y2hhYmxlID0gZGVmYXVsdFRvdWNoYWJsZSQyLAogICAgICAgICAgc2NhbGVFeHRlbnQgPSBbMCwgSW5maW5pdHldLAogICAgICAgICAgdHJhbnNsYXRlRXh0ZW50ID0gW1stSW5maW5pdHksIC1JbmZpbml0eV0sIFtJbmZpbml0eSwgSW5maW5pdHldXSwKICAgICAgICAgIGR1cmF0aW9uID0gMjUwLAogICAgICAgICAgaW50ZXJwb2xhdGUgPSBpbnRlcnBvbGF0ZVpvb20sCiAgICAgICAgICBsaXN0ZW5lcnMgPSBkaXNwYXRjaCgic3RhcnQiLCAiem9vbSIsICJlbmQiKSwKICAgICAgICAgIHRvdWNoc3RhcnRpbmcsCiAgICAgICAgICB0b3VjaGVuZGluZywKICAgICAgICAgIHRvdWNoRGVsYXkgPSA1MDAsCiAgICAgICAgICB3aGVlbERlbGF5ID0gMTUwLAogICAgICAgICAgY2xpY2tEaXN0YW5jZTIgPSAwOwoKICAgICAgZnVuY3Rpb24gem9vbShzZWxlY3Rpb24pIHsKICAgICAgICBzZWxlY3Rpb24KICAgICAgICAgICAgLnByb3BlcnR5KCJfX3pvb20iLCBkZWZhdWx0VHJhbnNmb3JtKQogICAgICAgICAgICAub24oIndoZWVsLnpvb20iLCB3aGVlbGVkKQogICAgICAgICAgICAub24oIm1vdXNlZG93bi56b29tIiwgbW91c2Vkb3duZWQpCiAgICAgICAgICAgIC5vbigiZGJsY2xpY2suem9vbSIsIGRibGNsaWNrZWQpCiAgICAgICAgICAuZmlsdGVyKHRvdWNoYWJsZSkKICAgICAgICAgICAgLm9uKCJ0b3VjaHN0YXJ0Lnpvb20iLCB0b3VjaHN0YXJ0ZWQpCiAgICAgICAgICAgIC5vbigidG91Y2htb3ZlLnpvb20iLCB0b3VjaG1vdmVkKQogICAgICAgICAgICAub24oInRvdWNoZW5kLnpvb20gdG91Y2hjYW5jZWwuem9vbSIsIHRvdWNoZW5kZWQpCiAgICAgICAgICAgIC5zdHlsZSgidG91Y2gtYWN0aW9uIiwgIm5vbmUiKQogICAgICAgICAgICAuc3R5bGUoIi13ZWJraXQtdGFwLWhpZ2hsaWdodC1jb2xvciIsICJyZ2JhKDAsMCwwLDApIik7CiAgICAgIH0KCiAgICAgIHpvb20udHJhbnNmb3JtID0gZnVuY3Rpb24oY29sbGVjdGlvbiwgdHJhbnNmb3JtLCBwb2ludCkgewogICAgICAgIHZhciBzZWxlY3Rpb24gPSBjb2xsZWN0aW9uLnNlbGVjdGlvbiA/IGNvbGxlY3Rpb24uc2VsZWN0aW9uKCkgOiBjb2xsZWN0aW9uOwogICAgICAgIHNlbGVjdGlvbi5wcm9wZXJ0eSgiX196b29tIiwgZGVmYXVsdFRyYW5zZm9ybSk7CiAgICAgICAgaWYgKGNvbGxlY3Rpb24gIT09IHNlbGVjdGlvbikgewogICAgICAgICAgc2NoZWR1bGUoY29sbGVjdGlvbiwgdHJhbnNmb3JtLCBwb2ludCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHNlbGVjdGlvbi5pbnRlcnJ1cHQoKS5lYWNoKGZ1bmN0aW9uKCkgewogICAgICAgICAgICBnZXN0dXJlKHRoaXMsIGFyZ3VtZW50cykKICAgICAgICAgICAgICAgIC5zdGFydCgpCiAgICAgICAgICAgICAgICAuem9vbShudWxsLCB0eXBlb2YgdHJhbnNmb3JtID09PSAiZnVuY3Rpb24iID8gdHJhbnNmb3JtLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiB0cmFuc2Zvcm0pCiAgICAgICAgICAgICAgICAuZW5kKCk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH07CgogICAgICB6b29tLnNjYWxlQnkgPSBmdW5jdGlvbihzZWxlY3Rpb24sIGssIHApIHsKICAgICAgICB6b29tLnNjYWxlVG8oc2VsZWN0aW9uLCBmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciBrMCA9IHRoaXMuX196b29tLmssCiAgICAgICAgICAgICAgazEgPSB0eXBlb2YgayA9PT0gImZ1bmN0aW9uIiA/IGsuYXBwbHkodGhpcywgYXJndW1lbnRzKSA6IGs7CiAgICAgICAgICByZXR1cm4gazAgKiBrMTsKICAgICAgICB9LCBwKTsKICAgICAgfTsKCiAgICAgIHpvb20uc2NhbGVUbyA9IGZ1bmN0aW9uKHNlbGVjdGlvbiwgaywgcCkgewogICAgICAgIHpvb20udHJhbnNmb3JtKHNlbGVjdGlvbiwgZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgZSA9IGV4dGVudC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLAogICAgICAgICAgICAgIHQwID0gdGhpcy5fX3pvb20sCiAgICAgICAgICAgICAgcDAgPSBwID09IG51bGwgPyBjZW50cm9pZChlKSA6IHR5cGVvZiBwID09PSAiZnVuY3Rpb24iID8gcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogcCwKICAgICAgICAgICAgICBwMSA9IHQwLmludmVydChwMCksCiAgICAgICAgICAgICAgazEgPSB0eXBlb2YgayA9PT0gImZ1bmN0aW9uIiA/IGsuYXBwbHkodGhpcywgYXJndW1lbnRzKSA6IGs7CiAgICAgICAgICByZXR1cm4gY29uc3RyYWluKHRyYW5zbGF0ZShzY2FsZSh0MCwgazEpLCBwMCwgcDEpLCBlLCB0cmFuc2xhdGVFeHRlbnQpOwogICAgICAgIH0sIHApOwogICAgICB9OwoKICAgICAgem9vbS50cmFuc2xhdGVCeSA9IGZ1bmN0aW9uKHNlbGVjdGlvbiwgeCwgeSkgewogICAgICAgIHpvb20udHJhbnNmb3JtKHNlbGVjdGlvbiwgZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gY29uc3RyYWluKHRoaXMuX196b29tLnRyYW5zbGF0ZSgKICAgICAgICAgICAgdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiB4LAogICAgICAgICAgICB0eXBlb2YgeSA9PT0gImZ1bmN0aW9uIiA/IHkuYXBwbHkodGhpcywgYXJndW1lbnRzKSA6IHkKICAgICAgICAgICksIGV4dGVudC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCB0cmFuc2xhdGVFeHRlbnQpOwogICAgICAgIH0pOwogICAgICB9OwoKICAgICAgem9vbS50cmFuc2xhdGVUbyA9IGZ1bmN0aW9uKHNlbGVjdGlvbiwgeCwgeSwgcCkgewogICAgICAgIHpvb20udHJhbnNmb3JtKHNlbGVjdGlvbiwgZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgZSA9IGV4dGVudC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLAogICAgICAgICAgICAgIHQgPSB0aGlzLl9fem9vbSwKICAgICAgICAgICAgICBwMCA9IHAgPT0gbnVsbCA/IGNlbnRyb2lkKGUpIDogdHlwZW9mIHAgPT09ICJmdW5jdGlvbiIgPyBwLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiBwOwogICAgICAgICAgcmV0dXJuIGNvbnN0cmFpbihpZGVudGl0eSQ5LnRyYW5zbGF0ZShwMFswXSwgcDBbMV0pLnNjYWxlKHQuaykudHJhbnNsYXRlKAogICAgICAgICAgICB0eXBlb2YgeCA9PT0gImZ1bmN0aW9uIiA/IC14LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiAteCwKICAgICAgICAgICAgdHlwZW9mIHkgPT09ICJmdW5jdGlvbiIgPyAteS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogLXkKICAgICAgICAgICksIGUsIHRyYW5zbGF0ZUV4dGVudCk7CiAgICAgICAgfSwgcCk7CiAgICAgIH07CgogICAgICBmdW5jdGlvbiBzY2FsZSh0cmFuc2Zvcm0sIGspIHsKICAgICAgICBrID0gTWF0aC5tYXgoc2NhbGVFeHRlbnRbMF0sIE1hdGgubWluKHNjYWxlRXh0ZW50WzFdLCBrKSk7CiAgICAgICAgcmV0dXJuIGsgPT09IHRyYW5zZm9ybS5rID8gdHJhbnNmb3JtIDogbmV3IFRyYW5zZm9ybShrLCB0cmFuc2Zvcm0ueCwgdHJhbnNmb3JtLnkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2xhdGUodHJhbnNmb3JtLCBwMCwgcDEpIHsKICAgICAgICB2YXIgeCA9IHAwWzBdIC0gcDFbMF0gKiB0cmFuc2Zvcm0uaywgeSA9IHAwWzFdIC0gcDFbMV0gKiB0cmFuc2Zvcm0uazsKICAgICAgICByZXR1cm4geCA9PT0gdHJhbnNmb3JtLnggJiYgeSA9PT0gdHJhbnNmb3JtLnkgPyB0cmFuc2Zvcm0gOiBuZXcgVHJhbnNmb3JtKHRyYW5zZm9ybS5rLCB4LCB5KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gY2VudHJvaWQoZXh0ZW50KSB7CiAgICAgICAgcmV0dXJuIFsoK2V4dGVudFswXVswXSArICtleHRlbnRbMV1bMF0pIC8gMiwgKCtleHRlbnRbMF1bMV0gKyArZXh0ZW50WzFdWzFdKSAvIDJdOwogICAgICB9CgogICAgICBmdW5jdGlvbiBzY2hlZHVsZSh0cmFuc2l0aW9uLCB0cmFuc2Zvcm0sIHBvaW50KSB7CiAgICAgICAgdHJhbnNpdGlvbgogICAgICAgICAgICAub24oInN0YXJ0Lnpvb20iLCBmdW5jdGlvbigpIHsgZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpLnN0YXJ0KCk7IH0pCiAgICAgICAgICAgIC5vbigiaW50ZXJydXB0Lnpvb20gZW5kLnpvb20iLCBmdW5jdGlvbigpIHsgZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpLmVuZCgpOyB9KQogICAgICAgICAgICAudHdlZW4oInpvb20iLCBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICB2YXIgdGhhdCA9IHRoaXMsCiAgICAgICAgICAgICAgICAgIGFyZ3MgPSBhcmd1bWVudHMsCiAgICAgICAgICAgICAgICAgIGcgPSBnZXN0dXJlKHRoYXQsIGFyZ3MpLAogICAgICAgICAgICAgICAgICBlID0gZXh0ZW50LmFwcGx5KHRoYXQsIGFyZ3MpLAogICAgICAgICAgICAgICAgICBwID0gcG9pbnQgPT0gbnVsbCA/IGNlbnRyb2lkKGUpIDogdHlwZW9mIHBvaW50ID09PSAiZnVuY3Rpb24iID8gcG9pbnQuYXBwbHkodGhhdCwgYXJncykgOiBwb2ludCwKICAgICAgICAgICAgICAgICAgdyA9IE1hdGgubWF4KGVbMV1bMF0gLSBlWzBdWzBdLCBlWzFdWzFdIC0gZVswXVsxXSksCiAgICAgICAgICAgICAgICAgIGEgPSB0aGF0Ll9fem9vbSwKICAgICAgICAgICAgICAgICAgYiA9IHR5cGVvZiB0cmFuc2Zvcm0gPT09ICJmdW5jdGlvbiIgPyB0cmFuc2Zvcm0uYXBwbHkodGhhdCwgYXJncykgOiB0cmFuc2Zvcm0sCiAgICAgICAgICAgICAgICAgIGkgPSBpbnRlcnBvbGF0ZShhLmludmVydChwKS5jb25jYXQodyAvIGEuayksIGIuaW52ZXJ0KHApLmNvbmNhdCh3IC8gYi5rKSk7CiAgICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgICAgICAgIGlmICh0ID09PSAxKSB0ID0gYjsgLy8gQXZvaWQgcm91bmRpbmcgZXJyb3Igb24gZW5kLgogICAgICAgICAgICAgICAgZWxzZSB7IHZhciBsID0gaSh0KSwgayA9IHcgLyBsWzJdOyB0ID0gbmV3IFRyYW5zZm9ybShrLCBwWzBdIC0gbFswXSAqIGssIHBbMV0gLSBsWzFdICogayk7IH0KICAgICAgICAgICAgICAgIGcuem9vbShudWxsLCB0KTsKICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZ2VzdHVyZSh0aGF0LCBhcmdzLCBjbGVhbikgewogICAgICAgIHJldHVybiAoIWNsZWFuICYmIHRoYXQuX196b29taW5nKSB8fCBuZXcgR2VzdHVyZSh0aGF0LCBhcmdzKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gR2VzdHVyZSh0aGF0LCBhcmdzKSB7CiAgICAgICAgdGhpcy50aGF0ID0gdGhhdDsKICAgICAgICB0aGlzLmFyZ3MgPSBhcmdzOwogICAgICAgIHRoaXMuYWN0aXZlID0gMDsKICAgICAgICB0aGlzLmV4dGVudCA9IGV4dGVudC5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgICB0aGlzLnRhcHMgPSAwOwogICAgICB9CgogICAgICBHZXN0dXJlLnByb3RvdHlwZSA9IHsKICAgICAgICBzdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoKyt0aGlzLmFjdGl2ZSA9PT0gMSkgewogICAgICAgICAgICB0aGlzLnRoYXQuX196b29taW5nID0gdGhpczsKICAgICAgICAgICAgdGhpcy5lbWl0KCJzdGFydCIpOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfSwKICAgICAgICB6b29tOiBmdW5jdGlvbihrZXksIHRyYW5zZm9ybSkgewogICAgICAgICAgaWYgKHRoaXMubW91c2UgJiYga2V5ICE9PSAibW91c2UiKSB0aGlzLm1vdXNlWzFdID0gdHJhbnNmb3JtLmludmVydCh0aGlzLm1vdXNlWzBdKTsKICAgICAgICAgIGlmICh0aGlzLnRvdWNoMCAmJiBrZXkgIT09ICJ0b3VjaCIpIHRoaXMudG91Y2gwWzFdID0gdHJhbnNmb3JtLmludmVydCh0aGlzLnRvdWNoMFswXSk7CiAgICAgICAgICBpZiAodGhpcy50b3VjaDEgJiYga2V5ICE9PSAidG91Y2giKSB0aGlzLnRvdWNoMVsxXSA9IHRyYW5zZm9ybS5pbnZlcnQodGhpcy50b3VjaDFbMF0pOwogICAgICAgICAgdGhpcy50aGF0Ll9fem9vbSA9IHRyYW5zZm9ybTsKICAgICAgICAgIHRoaXMuZW1pdCgiem9vbSIpOwogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfSwKICAgICAgICBlbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgaWYgKC0tdGhpcy5hY3RpdmUgPT09IDApIHsKICAgICAgICAgICAgZGVsZXRlIHRoaXMudGhhdC5fX3pvb21pbmc7CiAgICAgICAgICAgIHRoaXMuZW1pdCgiZW5kIik7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIGVtaXQ6IGZ1bmN0aW9uKHR5cGUpIHsKICAgICAgICAgIGN1c3RvbUV2ZW50KG5ldyBab29tRXZlbnQoem9vbSwgdHlwZSwgdGhpcy50aGF0Ll9fem9vbSksIGxpc3RlbmVycy5hcHBseSwgbGlzdGVuZXJzLCBbdHlwZSwgdGhpcy50aGF0LCB0aGlzLmFyZ3NdKTsKICAgICAgICB9CiAgICAgIH07CgogICAgICBmdW5jdGlvbiB3aGVlbGVkKCkgewogICAgICAgIGlmICghZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgdCA9IHRoaXMuX196b29tLAogICAgICAgICAgICBrID0gTWF0aC5tYXgoc2NhbGVFeHRlbnRbMF0sIE1hdGgubWluKHNjYWxlRXh0ZW50WzFdLCB0LmsgKiBNYXRoLnBvdygyLCB3aGVlbERlbHRhLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpKSksCiAgICAgICAgICAgIHAgPSBtb3VzZSh0aGlzKTsKCiAgICAgICAgLy8gSWYgdGhlIG1vdXNlIGlzIGluIHRoZSBzYW1lIGxvY2F0aW9uIGFzIGJlZm9yZSwgcmV1c2UgaXQuCiAgICAgICAgLy8gSWYgdGhlcmUgd2VyZSByZWNlbnQgd2hlZWwgZXZlbnRzLCByZXNldCB0aGUgd2hlZWwgaWRsZSB0aW1lb3V0LgogICAgICAgIGlmIChnLndoZWVsKSB7CiAgICAgICAgICBpZiAoZy5tb3VzZVswXVswXSAhPT0gcFswXSB8fCBnLm1vdXNlWzBdWzFdICE9PSBwWzFdKSB7CiAgICAgICAgICAgIGcubW91c2VbMV0gPSB0LmludmVydChnLm1vdXNlWzBdID0gcCk7CiAgICAgICAgICB9CiAgICAgICAgICBjbGVhclRpbWVvdXQoZy53aGVlbCk7CiAgICAgICAgfQoKICAgICAgICAvLyBJZiB0aGlzIHdoZWVsIGV2ZW50IHdvbuKAmXQgdHJpZ2dlciBhIHRyYW5zZm9ybSBjaGFuZ2UsIGlnbm9yZSBpdC4KICAgICAgICBlbHNlIGlmICh0LmsgPT09IGspIHJldHVybjsKCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjYXB0dXJlIHRoZSBtb3VzZSBwb2ludCBhbmQgbG9jYXRpb24gYXQgdGhlIHN0YXJ0LgogICAgICAgIGVsc2UgewogICAgICAgICAgZy5tb3VzZSA9IFtwLCB0LmludmVydChwKV07CiAgICAgICAgICBpbnRlcnJ1cHQodGhpcyk7CiAgICAgICAgICBnLnN0YXJ0KCk7CiAgICAgICAgfQoKICAgICAgICBub2V2ZW50JDIoKTsKICAgICAgICBnLndoZWVsID0gc2V0VGltZW91dCh3aGVlbGlkbGVkLCB3aGVlbERlbGF5KTsKICAgICAgICBnLnpvb20oIm1vdXNlIiwgY29uc3RyYWluKHRyYW5zbGF0ZShzY2FsZSh0LCBrKSwgZy5tb3VzZVswXSwgZy5tb3VzZVsxXSksIGcuZXh0ZW50LCB0cmFuc2xhdGVFeHRlbnQpKTsKCiAgICAgICAgZnVuY3Rpb24gd2hlZWxpZGxlZCgpIHsKICAgICAgICAgIGcud2hlZWwgPSBudWxsOwogICAgICAgICAgZy5lbmQoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIG1vdXNlZG93bmVkKCkgewogICAgICAgIGlmICh0b3VjaGVuZGluZyB8fCAhZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzLCB0cnVlKSwKICAgICAgICAgICAgdiA9IHNlbGVjdChldmVudC52aWV3KS5vbigibW91c2Vtb3ZlLnpvb20iLCBtb3VzZW1vdmVkLCB0cnVlKS5vbigibW91c2V1cC56b29tIiwgbW91c2V1cHBlZCwgdHJ1ZSksCiAgICAgICAgICAgIHAgPSBtb3VzZSh0aGlzKSwKICAgICAgICAgICAgeDAgPSBldmVudC5jbGllbnRYLAogICAgICAgICAgICB5MCA9IGV2ZW50LmNsaWVudFk7CgogICAgICAgIGRyYWdEaXNhYmxlKGV2ZW50LnZpZXcpOwogICAgICAgIG5vcHJvcGFnYXRpb24kMigpOwogICAgICAgIGcubW91c2UgPSBbcCwgdGhpcy5fX3pvb20uaW52ZXJ0KHApXTsKICAgICAgICBpbnRlcnJ1cHQodGhpcyk7CiAgICAgICAgZy5zdGFydCgpOwoKICAgICAgICBmdW5jdGlvbiBtb3VzZW1vdmVkKCkgewogICAgICAgICAgbm9ldmVudCQyKCk7CiAgICAgICAgICBpZiAoIWcubW92ZWQpIHsKICAgICAgICAgICAgdmFyIGR4ID0gZXZlbnQuY2xpZW50WCAtIHgwLCBkeSA9IGV2ZW50LmNsaWVudFkgLSB5MDsKICAgICAgICAgICAgZy5tb3ZlZCA9IGR4ICogZHggKyBkeSAqIGR5ID4gY2xpY2tEaXN0YW5jZTI7CiAgICAgICAgICB9CiAgICAgICAgICBnLnpvb20oIm1vdXNlIiwgY29uc3RyYWluKHRyYW5zbGF0ZShnLnRoYXQuX196b29tLCBnLm1vdXNlWzBdID0gbW91c2UoZy50aGF0KSwgZy5tb3VzZVsxXSksIGcuZXh0ZW50LCB0cmFuc2xhdGVFeHRlbnQpKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIG1vdXNldXBwZWQoKSB7CiAgICAgICAgICB2Lm9uKCJtb3VzZW1vdmUuem9vbSBtb3VzZXVwLnpvb20iLCBudWxsKTsKICAgICAgICAgIHllc2RyYWcoZXZlbnQudmlldywgZy5tb3ZlZCk7CiAgICAgICAgICBub2V2ZW50JDIoKTsKICAgICAgICAgIGcuZW5kKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBkYmxjbGlja2VkKCkgewogICAgICAgIGlmICghZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgdDAgPSB0aGlzLl9fem9vbSwKICAgICAgICAgICAgcDAgPSBtb3VzZSh0aGlzKSwKICAgICAgICAgICAgcDEgPSB0MC5pbnZlcnQocDApLAogICAgICAgICAgICBrMSA9IHQwLmsgKiAoZXZlbnQuc2hpZnRLZXkgPyAwLjUgOiAyKSwKICAgICAgICAgICAgdDEgPSBjb25zdHJhaW4odHJhbnNsYXRlKHNjYWxlKHQwLCBrMSksIHAwLCBwMSksIGV4dGVudC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCB0cmFuc2xhdGVFeHRlbnQpOwoKICAgICAgICBub2V2ZW50JDIoKTsKICAgICAgICBpZiAoZHVyYXRpb24gPiAwKSBzZWxlY3QodGhpcykudHJhbnNpdGlvbigpLmR1cmF0aW9uKGR1cmF0aW9uKS5jYWxsKHNjaGVkdWxlLCB0MSwgcDApOwogICAgICAgIGVsc2Ugc2VsZWN0KHRoaXMpLmNhbGwoem9vbS50cmFuc2Zvcm0sIHQxKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gdG91Y2hzdGFydGVkKCkgewogICAgICAgIGlmICghZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgdG91Y2hlcyA9IGV2ZW50LnRvdWNoZXMsCiAgICAgICAgICAgIG4gPSB0b3VjaGVzLmxlbmd0aCwKICAgICAgICAgICAgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzLCBldmVudC5jaGFuZ2VkVG91Y2hlcy5sZW5ndGggPT09IG4pLAogICAgICAgICAgICBzdGFydGVkLCBpLCB0LCBwOwoKICAgICAgICBub3Byb3BhZ2F0aW9uJDIoKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB0ID0gdG91Y2hlc1tpXSwgcCA9IHRvdWNoKHRoaXMsIHRvdWNoZXMsIHQuaWRlbnRpZmllcik7CiAgICAgICAgICBwID0gW3AsIHRoaXMuX196b29tLmludmVydChwKSwgdC5pZGVudGlmaWVyXTsKICAgICAgICAgIGlmICghZy50b3VjaDApIGcudG91Y2gwID0gcCwgc3RhcnRlZCA9IHRydWUsIGcudGFwcyA9IDEgKyAhIXRvdWNoc3RhcnRpbmc7CiAgICAgICAgICBlbHNlIGlmICghZy50b3VjaDEgJiYgZy50b3VjaDBbMl0gIT09IHBbMl0pIGcudG91Y2gxID0gcCwgZy50YXBzID0gMDsKICAgICAgICB9CgogICAgICAgIGlmICh0b3VjaHN0YXJ0aW5nKSB0b3VjaHN0YXJ0aW5nID0gY2xlYXJUaW1lb3V0KHRvdWNoc3RhcnRpbmcpOwoKICAgICAgICBpZiAoc3RhcnRlZCkgewogICAgICAgICAgaWYgKGcudGFwcyA8IDIpIHRvdWNoc3RhcnRpbmcgPSBzZXRUaW1lb3V0KGZ1bmN0aW9uKCkgeyB0b3VjaHN0YXJ0aW5nID0gbnVsbDsgfSwgdG91Y2hEZWxheSk7CiAgICAgICAgICBpbnRlcnJ1cHQodGhpcyk7CiAgICAgICAgICBnLnN0YXJ0KCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiB0b3VjaG1vdmVkKCkgewogICAgICAgIGlmICghdGhpcy5fX3pvb21pbmcpIHJldHVybjsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgdG91Y2hlcyA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBuID0gdG91Y2hlcy5sZW5ndGgsIGksIHQsIHAsIGw7CgogICAgICAgIG5vZXZlbnQkMigpOwogICAgICAgIGlmICh0b3VjaHN0YXJ0aW5nKSB0b3VjaHN0YXJ0aW5nID0gY2xlYXJUaW1lb3V0KHRvdWNoc3RhcnRpbmcpOwogICAgICAgIGcudGFwcyA9IDA7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdCA9IHRvdWNoZXNbaV0sIHAgPSB0b3VjaCh0aGlzLCB0b3VjaGVzLCB0LmlkZW50aWZpZXIpOwogICAgICAgICAgaWYgKGcudG91Y2gwICYmIGcudG91Y2gwWzJdID09PSB0LmlkZW50aWZpZXIpIGcudG91Y2gwWzBdID0gcDsKICAgICAgICAgIGVsc2UgaWYgKGcudG91Y2gxICYmIGcudG91Y2gxWzJdID09PSB0LmlkZW50aWZpZXIpIGcudG91Y2gxWzBdID0gcDsKICAgICAgICB9CiAgICAgICAgdCA9IGcudGhhdC5fX3pvb207CiAgICAgICAgaWYgKGcudG91Y2gxKSB7CiAgICAgICAgICB2YXIgcDAgPSBnLnRvdWNoMFswXSwgbDAgPSBnLnRvdWNoMFsxXSwKICAgICAgICAgICAgICBwMSA9IGcudG91Y2gxWzBdLCBsMSA9IGcudG91Y2gxWzFdLAogICAgICAgICAgICAgIGRwID0gKGRwID0gcDFbMF0gLSBwMFswXSkgKiBkcCArIChkcCA9IHAxWzFdIC0gcDBbMV0pICogZHAsCiAgICAgICAgICAgICAgZGwgPSAoZGwgPSBsMVswXSAtIGwwWzBdKSAqIGRsICsgKGRsID0gbDFbMV0gLSBsMFsxXSkgKiBkbDsKICAgICAgICAgIHQgPSBzY2FsZSh0LCBNYXRoLnNxcnQoZHAgLyBkbCkpOwogICAgICAgICAgcCA9IFsocDBbMF0gKyBwMVswXSkgLyAyLCAocDBbMV0gKyBwMVsxXSkgLyAyXTsKICAgICAgICAgIGwgPSBbKGwwWzBdICsgbDFbMF0pIC8gMiwgKGwwWzFdICsgbDFbMV0pIC8gMl07CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKGcudG91Y2gwKSBwID0gZy50b3VjaDBbMF0sIGwgPSBnLnRvdWNoMFsxXTsKICAgICAgICBlbHNlIHJldHVybjsKICAgICAgICBnLnpvb20oInRvdWNoIiwgY29uc3RyYWluKHRyYW5zbGF0ZSh0LCBwLCBsKSwgZy5leHRlbnQsIHRyYW5zbGF0ZUV4dGVudCkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0b3VjaGVuZGVkKCkgewogICAgICAgIGlmICghdGhpcy5fX3pvb21pbmcpIHJldHVybjsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgdG91Y2hlcyA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBuID0gdG91Y2hlcy5sZW5ndGgsIGksIHQ7CgogICAgICAgIG5vcHJvcGFnYXRpb24kMigpOwogICAgICAgIGlmICh0b3VjaGVuZGluZykgY2xlYXJUaW1lb3V0KHRvdWNoZW5kaW5nKTsKICAgICAgICB0b3VjaGVuZGluZyA9IHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHRvdWNoZW5kaW5nID0gbnVsbDsgfSwgdG91Y2hEZWxheSk7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdCA9IHRvdWNoZXNbaV07CiAgICAgICAgICBpZiAoZy50b3VjaDAgJiYgZy50b3VjaDBbMl0gPT09IHQuaWRlbnRpZmllcikgZGVsZXRlIGcudG91Y2gwOwogICAgICAgICAgZWxzZSBpZiAoZy50b3VjaDEgJiYgZy50b3VjaDFbMl0gPT09IHQuaWRlbnRpZmllcikgZGVsZXRlIGcudG91Y2gxOwogICAgICAgIH0KICAgICAgICBpZiAoZy50b3VjaDEgJiYgIWcudG91Y2gwKSBnLnRvdWNoMCA9IGcudG91Y2gxLCBkZWxldGUgZy50b3VjaDE7CiAgICAgICAgaWYgKGcudG91Y2gwKSBnLnRvdWNoMFsxXSA9IHRoaXMuX196b29tLmludmVydChnLnRvdWNoMFswXSk7CiAgICAgICAgZWxzZSB7CiAgICAgICAgICBnLmVuZCgpOwogICAgICAgICAgLy8gSWYgdGhpcyB3YXMgYSBkYmx0YXAsIHJlcm91dGUgdG8gdGhlIChvcHRpb25hbCkgZGJsY2xpY2suem9vbSBoYW5kbGVyLgogICAgICAgICAgaWYgKGcudGFwcyA9PT0gMikgewogICAgICAgICAgICB2YXIgcCA9IHNlbGVjdCh0aGlzKS5vbigiZGJsY2xpY2suem9vbSIpOwogICAgICAgICAgICBpZiAocCkgcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgem9vbS53aGVlbERlbHRhID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHdoZWVsRGVsdGEgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRkKCtfKSwgem9vbSkgOiB3aGVlbERlbHRhOwogICAgICB9OwoKICAgICAgem9vbS5maWx0ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZmlsdGVyID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkZCghIV8pLCB6b29tKSA6IGZpbHRlcjsKICAgICAgfTsKCiAgICAgIHpvb20udG91Y2hhYmxlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRvdWNoYWJsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGQoISFfKSwgem9vbSkgOiB0b3VjaGFibGU7CiAgICAgIH07CgogICAgICB6b29tLmV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChleHRlbnQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRkKFtbK19bMF1bMF0sICtfWzBdWzFdXSwgWytfWzFdWzBdLCArX1sxXVsxXV1dKSwgem9vbSkgOiBleHRlbnQ7CiAgICAgIH07CgogICAgICB6b29tLnNjYWxlRXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNjYWxlRXh0ZW50WzBdID0gK19bMF0sIHNjYWxlRXh0ZW50WzFdID0gK19bMV0sIHpvb20pIDogW3NjYWxlRXh0ZW50WzBdLCBzY2FsZUV4dGVudFsxXV07CiAgICAgIH07CgogICAgICB6b29tLnRyYW5zbGF0ZUV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0cmFuc2xhdGVFeHRlbnRbMF1bMF0gPSArX1swXVswXSwgdHJhbnNsYXRlRXh0ZW50WzFdWzBdID0gK19bMV1bMF0sIHRyYW5zbGF0ZUV4dGVudFswXVsxXSA9ICtfWzBdWzFdLCB0cmFuc2xhdGVFeHRlbnRbMV1bMV0gPSArX1sxXVsxXSwgem9vbSkgOiBbW3RyYW5zbGF0ZUV4dGVudFswXVswXSwgdHJhbnNsYXRlRXh0ZW50WzBdWzFdXSwgW3RyYW5zbGF0ZUV4dGVudFsxXVswXSwgdHJhbnNsYXRlRXh0ZW50WzFdWzFdXV07CiAgICAgIH07CgogICAgICB6b29tLmNvbnN0cmFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjb25zdHJhaW4gPSBfLCB6b29tKSA6IGNvbnN0cmFpbjsKICAgICAgfTsKCiAgICAgIHpvb20uZHVyYXRpb24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZHVyYXRpb24gPSArXywgem9vbSkgOiBkdXJhdGlvbjsKICAgICAgfTsKCiAgICAgIHpvb20uaW50ZXJwb2xhdGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaW50ZXJwb2xhdGUgPSBfLCB6b29tKSA6IGludGVycG9sYXRlOwogICAgICB9OwoKICAgICAgem9vbS5vbiA9IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZSA9IGxpc3RlbmVycy5vbi5hcHBseShsaXN0ZW5lcnMsIGFyZ3VtZW50cyk7CiAgICAgICAgcmV0dXJuIHZhbHVlID09PSBsaXN0ZW5lcnMgPyB6b29tIDogdmFsdWU7CiAgICAgIH07CgogICAgICB6b29tLmNsaWNrRGlzdGFuY2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY2xpY2tEaXN0YW5jZTIgPSAoXyA9ICtfKSAqIF8sIHpvb20pIDogTWF0aC5zcXJ0KGNsaWNrRGlzdGFuY2UyKTsKICAgICAgfTsKCiAgICAgIHJldHVybiB6b29tOwogICAgfQoKICAgIHZhciBkM1R5cGVkID0gLyojX19QVVJFX18qL09iamVjdC5mcmVlemUoewogICAgICAgIF9fcHJvdG9fXzogbnVsbCwKICAgICAgICB2ZXJzaW9uOiB2ZXJzaW9uJDEsCiAgICAgICAgYmlzZWN0OiBiaXNlY3RSaWdodCwKICAgICAgICBiaXNlY3RSaWdodDogYmlzZWN0UmlnaHQsCiAgICAgICAgYmlzZWN0TGVmdDogYmlzZWN0TGVmdCwKICAgICAgICBhc2NlbmRpbmc6IGFzY2VuZGluZywKICAgICAgICBiaXNlY3RvcjogYmlzZWN0b3IsCiAgICAgICAgY3Jvc3M6IGNyb3NzLAogICAgICAgIGRlc2NlbmRpbmc6IGRlc2NlbmRpbmcsCiAgICAgICAgZGV2aWF0aW9uOiBkZXZpYXRpb24sCiAgICAgICAgZXh0ZW50OiBleHRlbnQsCiAgICAgICAgaGlzdG9ncmFtOiBoaXN0b2dyYW0sCiAgICAgICAgdGhyZXNob2xkRnJlZWRtYW5EaWFjb25pczogZnJlZWRtYW5EaWFjb25pcywKICAgICAgICB0aHJlc2hvbGRTY290dDogc2NvdHQsCiAgICAgICAgdGhyZXNob2xkU3R1cmdlczogdGhyZXNob2xkU3R1cmdlcywKICAgICAgICBtYXg6IG1heCwKICAgICAgICBtZWFuOiBtZWFuLAogICAgICAgIG1lZGlhbjogbWVkaWFuLAogICAgICAgIG1lcmdlOiBtZXJnZSwKICAgICAgICBtaW46IG1pbiwKICAgICAgICBwYWlyczogcGFpcnMsCiAgICAgICAgcGVybXV0ZTogcGVybXV0ZSwKICAgICAgICBxdWFudGlsZTogdGhyZXNob2xkLAogICAgICAgIHJhbmdlOiBzZXF1ZW5jZSwKICAgICAgICBzY2FuOiBzY2FuLAogICAgICAgIHNodWZmbGU6IHNodWZmbGUsCiAgICAgICAgc3VtOiBzdW0sCiAgICAgICAgdGlja3M6IHRpY2tzLAogICAgICAgIHRpY2tJbmNyZW1lbnQ6IHRpY2tJbmNyZW1lbnQsCiAgICAgICAgdGlja1N0ZXA6IHRpY2tTdGVwLAogICAgICAgIHRyYW5zcG9zZTogdHJhbnNwb3NlLAogICAgICAgIHZhcmlhbmNlOiB2YXJpYW5jZSwKICAgICAgICB6aXA6IHppcCwKICAgICAgICBheGlzVG9wOiBheGlzVG9wLAogICAgICAgIGF4aXNSaWdodDogYXhpc1JpZ2h0LAogICAgICAgIGF4aXNCb3R0b206IGF4aXNCb3R0b20sCiAgICAgICAgYXhpc0xlZnQ6IGF4aXNMZWZ0LAogICAgICAgIGJydXNoOiBicnVzaCwKICAgICAgICBicnVzaFg6IGJydXNoWCwKICAgICAgICBicnVzaFk6IGJydXNoWSwKICAgICAgICBicnVzaFNlbGVjdGlvbjogYnJ1c2hTZWxlY3Rpb24sCiAgICAgICAgY2hvcmQ6IGNob3JkLAogICAgICAgIHJpYmJvbjogcmliYm9uLAogICAgICAgIG5lc3Q6IG5lc3QsCiAgICAgICAgc2V0OiBzZXQkMywKICAgICAgICBtYXA6IG1hcCQxLAogICAgICAgIGtleXM6IGtleXMsCiAgICAgICAgdmFsdWVzOiB2YWx1ZXMsCiAgICAgICAgZW50cmllczogZW50cmllcywKICAgICAgICBjb2xvcjogY29sb3IsCiAgICAgICAgcmdiOiByZ2IsCiAgICAgICAgaHNsOiBoc2wsCiAgICAgICAgbGFiOiBsYWIsCiAgICAgICAgaGNsOiBoY2wsCiAgICAgICAgbGNoOiBsY2gsCiAgICAgICAgZ3JheTogZ3JheSwKICAgICAgICBjdWJlaGVsaXg6IGN1YmVoZWxpeCwKICAgICAgICBjb250b3VyczogY29udG91cnMsCiAgICAgICAgY29udG91ckRlbnNpdHk6IGRlbnNpdHksCiAgICAgICAgZGlzcGF0Y2g6IGRpc3BhdGNoLAogICAgICAgIGRyYWc6IGRyYWcsCiAgICAgICAgZHJhZ0Rpc2FibGU6IGRyYWdEaXNhYmxlLAogICAgICAgIGRyYWdFbmFibGU6IHllc2RyYWcsCiAgICAgICAgZHN2Rm9ybWF0OiBkc3ZGb3JtYXQsCiAgICAgICAgY3N2UGFyc2U6IGNzdlBhcnNlLAogICAgICAgIGNzdlBhcnNlUm93czogY3N2UGFyc2VSb3dzLAogICAgICAgIGNzdkZvcm1hdDogY3N2Rm9ybWF0LAogICAgICAgIGNzdkZvcm1hdEJvZHk6IGNzdkZvcm1hdEJvZHksCiAgICAgICAgY3N2Rm9ybWF0Um93czogY3N2Rm9ybWF0Um93cywKICAgICAgICBjc3ZGb3JtYXRSb3c6IGNzdkZvcm1hdFJvdywKICAgICAgICBjc3ZGb3JtYXRWYWx1ZTogY3N2Rm9ybWF0VmFsdWUsCiAgICAgICAgdHN2UGFyc2U6IHRzdlBhcnNlLAogICAgICAgIHRzdlBhcnNlUm93czogdHN2UGFyc2VSb3dzLAogICAgICAgIHRzdkZvcm1hdDogdHN2Rm9ybWF0LAogICAgICAgIHRzdkZvcm1hdEJvZHk6IHRzdkZvcm1hdEJvZHksCiAgICAgICAgdHN2Rm9ybWF0Um93czogdHN2Rm9ybWF0Um93cywKICAgICAgICB0c3ZGb3JtYXRSb3c6IHRzdkZvcm1hdFJvdywKICAgICAgICB0c3ZGb3JtYXRWYWx1ZTogdHN2Rm9ybWF0VmFsdWUsCiAgICAgICAgYXV0b1R5cGU6IGF1dG9UeXBlLAogICAgICAgIGVhc2VMaW5lYXI6IGxpbmVhciQxLAogICAgICAgIGVhc2VRdWFkOiBxdWFkSW5PdXQsCiAgICAgICAgZWFzZVF1YWRJbjogcXVhZEluLAogICAgICAgIGVhc2VRdWFkT3V0OiBxdWFkT3V0LAogICAgICAgIGVhc2VRdWFkSW5PdXQ6IHF1YWRJbk91dCwKICAgICAgICBlYXNlQ3ViaWM6IGN1YmljSW5PdXQsCiAgICAgICAgZWFzZUN1YmljSW46IGN1YmljSW4sCiAgICAgICAgZWFzZUN1YmljT3V0OiBjdWJpY091dCwKICAgICAgICBlYXNlQ3ViaWNJbk91dDogY3ViaWNJbk91dCwKICAgICAgICBlYXNlUG9seTogcG9seUluT3V0LAogICAgICAgIGVhc2VQb2x5SW46IHBvbHlJbiwKICAgICAgICBlYXNlUG9seU91dDogcG9seU91dCwKICAgICAgICBlYXNlUG9seUluT3V0OiBwb2x5SW5PdXQsCiAgICAgICAgZWFzZVNpbjogc2luSW5PdXQsCiAgICAgICAgZWFzZVNpbkluOiBzaW5JbiwKICAgICAgICBlYXNlU2luT3V0OiBzaW5PdXQsCiAgICAgICAgZWFzZVNpbkluT3V0OiBzaW5Jbk91dCwKICAgICAgICBlYXNlRXhwOiBleHBJbk91dCwKICAgICAgICBlYXNlRXhwSW46IGV4cEluLAogICAgICAgIGVhc2VFeHBPdXQ6IGV4cE91dCwKICAgICAgICBlYXNlRXhwSW5PdXQ6IGV4cEluT3V0LAogICAgICAgIGVhc2VDaXJjbGU6IGNpcmNsZUluT3V0LAogICAgICAgIGVhc2VDaXJjbGVJbjogY2lyY2xlSW4sCiAgICAgICAgZWFzZUNpcmNsZU91dDogY2lyY2xlT3V0LAogICAgICAgIGVhc2VDaXJjbGVJbk91dDogY2lyY2xlSW5PdXQsCiAgICAgICAgZWFzZUJvdW5jZTogYm91bmNlT3V0LAogICAgICAgIGVhc2VCb3VuY2VJbjogYm91bmNlSW4sCiAgICAgICAgZWFzZUJvdW5jZU91dDogYm91bmNlT3V0LAogICAgICAgIGVhc2VCb3VuY2VJbk91dDogYm91bmNlSW5PdXQsCiAgICAgICAgZWFzZUJhY2s6IGJhY2tJbk91dCwKICAgICAgICBlYXNlQmFja0luOiBiYWNrSW4sCiAgICAgICAgZWFzZUJhY2tPdXQ6IGJhY2tPdXQsCiAgICAgICAgZWFzZUJhY2tJbk91dDogYmFja0luT3V0LAogICAgICAgIGVhc2VFbGFzdGljOiBlbGFzdGljT3V0LAogICAgICAgIGVhc2VFbGFzdGljSW46IGVsYXN0aWNJbiwKICAgICAgICBlYXNlRWxhc3RpY091dDogZWxhc3RpY091dCwKICAgICAgICBlYXNlRWxhc3RpY0luT3V0OiBlbGFzdGljSW5PdXQsCiAgICAgICAgYmxvYjogYmxvYiwKICAgICAgICBidWZmZXI6IGJ1ZmZlciwKICAgICAgICBkc3Y6IGRzdiwKICAgICAgICBjc3Y6IGNzdiQxLAogICAgICAgIHRzdjogdHN2JDEsCiAgICAgICAgaW1hZ2U6IGltYWdlLAogICAgICAgIGpzb246IGpzb24sCiAgICAgICAgdGV4dDogdGV4dCwKICAgICAgICB4bWw6IHhtbCwKICAgICAgICBodG1sOiBodG1sJDEsCiAgICAgICAgc3ZnOiBzdmcsCiAgICAgICAgZm9yY2VDZW50ZXI6IGNlbnRlciQxLAogICAgICAgIGZvcmNlQ29sbGlkZTogY29sbGlkZSwKICAgICAgICBmb3JjZUxpbms6IGxpbmssCiAgICAgICAgZm9yY2VNYW55Qm9keTogbWFueUJvZHksCiAgICAgICAgZm9yY2VSYWRpYWw6IHJhZGlhbCwKICAgICAgICBmb3JjZVNpbXVsYXRpb246IHNpbXVsYXRpb24sCiAgICAgICAgZm9yY2VYOiB4JDIsCiAgICAgICAgZm9yY2VZOiB5JDIsCiAgICAgICAgZm9ybWF0RGVmYXVsdExvY2FsZTogZGVmYXVsdExvY2FsZSwKICAgICAgICBnZXQgZm9ybWF0ICgpIHsgcmV0dXJuIGZvcm1hdDsgfSwKICAgICAgICBnZXQgZm9ybWF0UHJlZml4ICgpIHsgcmV0dXJuIGZvcm1hdFByZWZpeDsgfSwKICAgICAgICBmb3JtYXRMb2NhbGU6IGZvcm1hdExvY2FsZSwKICAgICAgICBmb3JtYXRTcGVjaWZpZXI6IGZvcm1hdFNwZWNpZmllciwKICAgICAgICBGb3JtYXRTcGVjaWZpZXI6IEZvcm1hdFNwZWNpZmllciwKICAgICAgICBwcmVjaXNpb25GaXhlZDogcHJlY2lzaW9uRml4ZWQsCiAgICAgICAgcHJlY2lzaW9uUHJlZml4OiBwcmVjaXNpb25QcmVmaXgsCiAgICAgICAgcHJlY2lzaW9uUm91bmQ6IHByZWNpc2lvblJvdW5kLAogICAgICAgIGdlb0FyZWE6IGFyZWEkMSwKICAgICAgICBnZW9Cb3VuZHM6IGJvdW5kcywKICAgICAgICBnZW9DZW50cm9pZDogY2VudHJvaWQsCiAgICAgICAgZ2VvQ2lyY2xlOiBjaXJjbGUsCiAgICAgICAgZ2VvQ2xpcEFudGltZXJpZGlhbjogY2xpcEFudGltZXJpZGlhbiwKICAgICAgICBnZW9DbGlwQ2lyY2xlOiBjbGlwQ2lyY2xlLAogICAgICAgIGdlb0NsaXBFeHRlbnQ6IGV4dGVudCQxLAogICAgICAgIGdlb0NsaXBSZWN0YW5nbGU6IGNsaXBSZWN0YW5nbGUsCiAgICAgICAgZ2VvQ29udGFpbnM6IGNvbnRhaW5zJDEsCiAgICAgICAgZ2VvRGlzdGFuY2U6IGRpc3RhbmNlLAogICAgICAgIGdlb0dyYXRpY3VsZTogZ3JhdGljdWxlLAogICAgICAgIGdlb0dyYXRpY3VsZTEwOiBncmF0aWN1bGUxMCwKICAgICAgICBnZW9JbnRlcnBvbGF0ZTogaW50ZXJwb2xhdGUkMSwKICAgICAgICBnZW9MZW5ndGg6IGxlbmd0aCQxLAogICAgICAgIGdlb1BhdGg6IGluZGV4JDEsCiAgICAgICAgZ2VvQWxiZXJzOiBhbGJlcnMsCiAgICAgICAgZ2VvQWxiZXJzVXNhOiBhbGJlcnNVc2EsCiAgICAgICAgZ2VvQXppbXV0aGFsRXF1YWxBcmVhOiBhemltdXRoYWxFcXVhbEFyZWEsCiAgICAgICAgZ2VvQXppbXV0aGFsRXF1YWxBcmVhUmF3OiBhemltdXRoYWxFcXVhbEFyZWFSYXcsCiAgICAgICAgZ2VvQXppbXV0aGFsRXF1aWRpc3RhbnQ6IGF6aW11dGhhbEVxdWlkaXN0YW50LAogICAgICAgIGdlb0F6aW11dGhhbEVxdWlkaXN0YW50UmF3OiBhemltdXRoYWxFcXVpZGlzdGFudFJhdywKICAgICAgICBnZW9Db25pY0NvbmZvcm1hbDogY29uaWNDb25mb3JtYWwsCiAgICAgICAgZ2VvQ29uaWNDb25mb3JtYWxSYXc6IGNvbmljQ29uZm9ybWFsUmF3LAogICAgICAgIGdlb0NvbmljRXF1YWxBcmVhOiBjb25pY0VxdWFsQXJlYSwKICAgICAgICBnZW9Db25pY0VxdWFsQXJlYVJhdzogY29uaWNFcXVhbEFyZWFSYXcsCiAgICAgICAgZ2VvQ29uaWNFcXVpZGlzdGFudDogY29uaWNFcXVpZGlzdGFudCwKICAgICAgICBnZW9Db25pY0VxdWlkaXN0YW50UmF3OiBjb25pY0VxdWlkaXN0YW50UmF3LAogICAgICAgIGdlb0VxdWFsRWFydGg6IGVxdWFsRWFydGgsCiAgICAgICAgZ2VvRXF1YWxFYXJ0aFJhdzogZXF1YWxFYXJ0aFJhdywKICAgICAgICBnZW9FcXVpcmVjdGFuZ3VsYXI6IGVxdWlyZWN0YW5ndWxhciwKICAgICAgICBnZW9FcXVpcmVjdGFuZ3VsYXJSYXc6IGVxdWlyZWN0YW5ndWxhclJhdywKICAgICAgICBnZW9Hbm9tb25pYzogZ25vbW9uaWMsCiAgICAgICAgZ2VvR25vbW9uaWNSYXc6IGdub21vbmljUmF3LAogICAgICAgIGdlb0lkZW50aXR5OiBpZGVudGl0eSQ1LAogICAgICAgIGdlb1Byb2plY3Rpb246IHByb2plY3Rpb24sCiAgICAgICAgZ2VvUHJvamVjdGlvbk11dGF0b3I6IHByb2plY3Rpb25NdXRhdG9yLAogICAgICAgIGdlb01lcmNhdG9yOiBtZXJjYXRvciwKICAgICAgICBnZW9NZXJjYXRvclJhdzogbWVyY2F0b3JSYXcsCiAgICAgICAgZ2VvTmF0dXJhbEVhcnRoMTogbmF0dXJhbEVhcnRoMSwKICAgICAgICBnZW9OYXR1cmFsRWFydGgxUmF3OiBuYXR1cmFsRWFydGgxUmF3LAogICAgICAgIGdlb09ydGhvZ3JhcGhpYzogb3J0aG9ncmFwaGljLAogICAgICAgIGdlb09ydGhvZ3JhcGhpY1Jhdzogb3J0aG9ncmFwaGljUmF3LAogICAgICAgIGdlb1N0ZXJlb2dyYXBoaWM6IHN0ZXJlb2dyYXBoaWMsCiAgICAgICAgZ2VvU3RlcmVvZ3JhcGhpY1Jhdzogc3RlcmVvZ3JhcGhpY1JhdywKICAgICAgICBnZW9UcmFuc3ZlcnNlTWVyY2F0b3I6IHRyYW5zdmVyc2VNZXJjYXRvciwKICAgICAgICBnZW9UcmFuc3ZlcnNlTWVyY2F0b3JSYXc6IHRyYW5zdmVyc2VNZXJjYXRvclJhdywKICAgICAgICBnZW9Sb3RhdGlvbjogcm90YXRpb24sCiAgICAgICAgZ2VvU3RyZWFtOiBnZW9TdHJlYW0sCiAgICAgICAgZ2VvVHJhbnNmb3JtOiB0cmFuc2Zvcm0sCiAgICAgICAgY2x1c3RlcjogY2x1c3RlciwKICAgICAgICBoaWVyYXJjaHk6IGhpZXJhcmNoeSwKICAgICAgICBwYWNrOiBpbmRleCQyLAogICAgICAgIHBhY2tTaWJsaW5nczogc2libGluZ3MsCiAgICAgICAgcGFja0VuY2xvc2U6IGVuY2xvc2UsCiAgICAgICAgcGFydGl0aW9uOiBwYXJ0aXRpb24sCiAgICAgICAgc3RyYXRpZnk6IHN0cmF0aWZ5LAogICAgICAgIHRyZWU6IHRyZWUsCiAgICAgICAgdHJlZW1hcDogaW5kZXgkMywKICAgICAgICB0cmVlbWFwQmluYXJ5OiBiaW5hcnksCiAgICAgICAgdHJlZW1hcERpY2U6IHRyZWVtYXBEaWNlLAogICAgICAgIHRyZWVtYXBTbGljZTogdHJlZW1hcFNsaWNlLAogICAgICAgIHRyZWVtYXBTbGljZURpY2U6IHNsaWNlRGljZSwKICAgICAgICB0cmVlbWFwU3F1YXJpZnk6IHNxdWFyaWZ5LAogICAgICAgIHRyZWVtYXBSZXNxdWFyaWZ5OiByZXNxdWFyaWZ5LAogICAgICAgIGludGVycG9sYXRlOiBpbnRlcnBvbGF0ZVZhbHVlLAogICAgICAgIGludGVycG9sYXRlQXJyYXk6IGFycmF5JDEsCiAgICAgICAgaW50ZXJwb2xhdGVCYXNpczogYmFzaXMkMSwKICAgICAgICBpbnRlcnBvbGF0ZUJhc2lzQ2xvc2VkOiBiYXNpc0Nsb3NlZCwKICAgICAgICBpbnRlcnBvbGF0ZURhdGU6IGRhdGUsCiAgICAgICAgaW50ZXJwb2xhdGVEaXNjcmV0ZTogZGlzY3JldGUsCiAgICAgICAgaW50ZXJwb2xhdGVIdWU6IGh1ZSQxLAogICAgICAgIGludGVycG9sYXRlTnVtYmVyOiBpbnRlcnBvbGF0ZU51bWJlciwKICAgICAgICBpbnRlcnBvbGF0ZU51bWJlckFycmF5OiBudW1iZXJBcnJheSwKICAgICAgICBpbnRlcnBvbGF0ZU9iamVjdDogb2JqZWN0LAogICAgICAgIGludGVycG9sYXRlUm91bmQ6IGludGVycG9sYXRlUm91bmQsCiAgICAgICAgaW50ZXJwb2xhdGVTdHJpbmc6IGludGVycG9sYXRlU3RyaW5nLAogICAgICAgIGludGVycG9sYXRlVHJhbnNmb3JtQ3NzOiBpbnRlcnBvbGF0ZVRyYW5zZm9ybUNzcywKICAgICAgICBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZzogaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmcsCiAgICAgICAgaW50ZXJwb2xhdGVab29tOiBpbnRlcnBvbGF0ZVpvb20sCiAgICAgICAgaW50ZXJwb2xhdGVSZ2I6IGludGVycG9sYXRlUmdiLAogICAgICAgIGludGVycG9sYXRlUmdiQmFzaXM6IHJnYkJhc2lzLAogICAgICAgIGludGVycG9sYXRlUmdiQmFzaXNDbG9zZWQ6IHJnYkJhc2lzQ2xvc2VkLAogICAgICAgIGludGVycG9sYXRlSHNsOiBoc2wkMiwKICAgICAgICBpbnRlcnBvbGF0ZUhzbExvbmc6IGhzbExvbmcsCiAgICAgICAgaW50ZXJwb2xhdGVMYWI6IGxhYiQxLAogICAgICAgIGludGVycG9sYXRlSGNsOiBoY2wkMiwKICAgICAgICBpbnRlcnBvbGF0ZUhjbExvbmc6IGhjbExvbmcsCiAgICAgICAgaW50ZXJwb2xhdGVDdWJlaGVsaXg6IGN1YmVoZWxpeCQyLAogICAgICAgIGludGVycG9sYXRlQ3ViZWhlbGl4TG9uZzogY3ViZWhlbGl4TG9uZywKICAgICAgICBwaWVjZXdpc2U6IHBpZWNld2lzZSwKICAgICAgICBxdWFudGl6ZTogcXVhbnRpemUsCiAgICAgICAgcGF0aDogcGF0aCwKICAgICAgICBwb2x5Z29uQXJlYTogYXJlYSQyLAogICAgICAgIHBvbHlnb25DZW50cm9pZDogY2VudHJvaWQkMSwKICAgICAgICBwb2x5Z29uSHVsbDogaHVsbCwKICAgICAgICBwb2x5Z29uQ29udGFpbnM6IGNvbnRhaW5zJDIsCiAgICAgICAgcG9seWdvbkxlbmd0aDogbGVuZ3RoJDIsCiAgICAgICAgcXVhZHRyZWU6IHF1YWR0cmVlLAogICAgICAgIHJhbmRvbVVuaWZvcm06IHVuaWZvcm0sCiAgICAgICAgcmFuZG9tTm9ybWFsOiBub3JtYWwsCiAgICAgICAgcmFuZG9tTG9nTm9ybWFsOiBsb2dOb3JtYWwsCiAgICAgICAgcmFuZG9tQmF0ZXM6IGJhdGVzLAogICAgICAgIHJhbmRvbUlyd2luSGFsbDogaXJ3aW5IYWxsLAogICAgICAgIHJhbmRvbUV4cG9uZW50aWFsOiBleHBvbmVudGlhbCQxLAogICAgICAgIHNjYWxlQmFuZDogYmFuZCwKICAgICAgICBzY2FsZVBvaW50OiBwb2ludCQxLAogICAgICAgIHNjYWxlSWRlbnRpdHk6IGlkZW50aXR5JDcsCiAgICAgICAgc2NhbGVMaW5lYXI6IGxpbmVhciQyLAogICAgICAgIHNjYWxlTG9nOiBsb2ckMSwKICAgICAgICBzY2FsZVN5bWxvZzogc3ltbG9nLAogICAgICAgIHNjYWxlT3JkaW5hbDogb3JkaW5hbCwKICAgICAgICBzY2FsZUltcGxpY2l0OiBpbXBsaWNpdCwKICAgICAgICBzY2FsZVBvdzogcG93JDEsCiAgICAgICAgc2NhbGVTcXJ0OiBzcXJ0JDEsCiAgICAgICAgc2NhbGVRdWFudGlsZTogcXVhbnRpbGUsCiAgICAgICAgc2NhbGVRdWFudGl6ZTogcXVhbnRpemUkMSwKICAgICAgICBzY2FsZVRocmVzaG9sZDogdGhyZXNob2xkJDEsCiAgICAgICAgc2NhbGVUaW1lOiB0aW1lLAogICAgICAgIHNjYWxlVXRjOiB1dGNUaW1lLAogICAgICAgIHNjYWxlU2VxdWVudGlhbDogc2VxdWVudGlhbCwKICAgICAgICBzY2FsZVNlcXVlbnRpYWxMb2c6IHNlcXVlbnRpYWxMb2csCiAgICAgICAgc2NhbGVTZXF1ZW50aWFsUG93OiBzZXF1ZW50aWFsUG93LAogICAgICAgIHNjYWxlU2VxdWVudGlhbFNxcnQ6IHNlcXVlbnRpYWxTcXJ0LAogICAgICAgIHNjYWxlU2VxdWVudGlhbFN5bWxvZzogc2VxdWVudGlhbFN5bWxvZywKICAgICAgICBzY2FsZVNlcXVlbnRpYWxRdWFudGlsZTogc2VxdWVudGlhbFF1YW50aWxlLAogICAgICAgIHNjYWxlRGl2ZXJnaW5nOiBkaXZlcmdpbmcsCiAgICAgICAgc2NhbGVEaXZlcmdpbmdMb2c6IGRpdmVyZ2luZ0xvZywKICAgICAgICBzY2FsZURpdmVyZ2luZ1BvdzogZGl2ZXJnaW5nUG93LAogICAgICAgIHNjYWxlRGl2ZXJnaW5nU3FydDogZGl2ZXJnaW5nU3FydCwKICAgICAgICBzY2FsZURpdmVyZ2luZ1N5bWxvZzogZGl2ZXJnaW5nU3ltbG9nLAogICAgICAgIHRpY2tGb3JtYXQ6IHRpY2tGb3JtYXQsCiAgICAgICAgc2NoZW1lQ2F0ZWdvcnkxMDogY2F0ZWdvcnkxMCwKICAgICAgICBzY2hlbWVBY2NlbnQ6IEFjY2VudCwKICAgICAgICBzY2hlbWVEYXJrMjogRGFyazIsCiAgICAgICAgc2NoZW1lUGFpcmVkOiBQYWlyZWQsCiAgICAgICAgc2NoZW1lUGFzdGVsMTogUGFzdGVsMSwKICAgICAgICBzY2hlbWVQYXN0ZWwyOiBQYXN0ZWwyLAogICAgICAgIHNjaGVtZVNldDE6IFNldDEsCiAgICAgICAgc2NoZW1lU2V0MjogU2V0MiwKICAgICAgICBzY2hlbWVTZXQzOiBTZXQzLAogICAgICAgIHNjaGVtZVRhYmxlYXUxMDogVGFibGVhdTEwLAogICAgICAgIGludGVycG9sYXRlQnJCRzogQnJCRywKICAgICAgICBzY2hlbWVCckJHOiBzY2hlbWUsCiAgICAgICAgaW50ZXJwb2xhdGVQUkduOiBQUkduLAogICAgICAgIHNjaGVtZVBSR246IHNjaGVtZSQxLAogICAgICAgIGludGVycG9sYXRlUGlZRzogUGlZRywKICAgICAgICBzY2hlbWVQaVlHOiBzY2hlbWUkMiwKICAgICAgICBpbnRlcnBvbGF0ZVB1T3I6IFB1T3IsCiAgICAgICAgc2NoZW1lUHVPcjogc2NoZW1lJDMsCiAgICAgICAgaW50ZXJwb2xhdGVSZEJ1OiBSZEJ1LAogICAgICAgIHNjaGVtZVJkQnU6IHNjaGVtZSQ0LAogICAgICAgIGludGVycG9sYXRlUmRHeTogUmRHeSwKICAgICAgICBzY2hlbWVSZEd5OiBzY2hlbWUkNSwKICAgICAgICBpbnRlcnBvbGF0ZVJkWWxCdTogUmRZbEJ1LAogICAgICAgIHNjaGVtZVJkWWxCdTogc2NoZW1lJDYsCiAgICAgICAgaW50ZXJwb2xhdGVSZFlsR246IFJkWWxHbiwKICAgICAgICBzY2hlbWVSZFlsR246IHNjaGVtZSQ3LAogICAgICAgIGludGVycG9sYXRlU3BlY3RyYWw6IFNwZWN0cmFsLAogICAgICAgIHNjaGVtZVNwZWN0cmFsOiBzY2hlbWUkOCwKICAgICAgICBpbnRlcnBvbGF0ZUJ1R246IEJ1R24sCiAgICAgICAgc2NoZW1lQnVHbjogc2NoZW1lJDksCiAgICAgICAgaW50ZXJwb2xhdGVCdVB1OiBCdVB1LAogICAgICAgIHNjaGVtZUJ1UHU6IHNjaGVtZSRhLAogICAgICAgIGludGVycG9sYXRlR25CdTogR25CdSwKICAgICAgICBzY2hlbWVHbkJ1OiBzY2hlbWUkYiwKICAgICAgICBpbnRlcnBvbGF0ZU9yUmQ6IE9yUmQsCiAgICAgICAgc2NoZW1lT3JSZDogc2NoZW1lJGMsCiAgICAgICAgaW50ZXJwb2xhdGVQdUJ1R246IFB1QnVHbiwKICAgICAgICBzY2hlbWVQdUJ1R246IHNjaGVtZSRkLAogICAgICAgIGludGVycG9sYXRlUHVCdTogUHVCdSwKICAgICAgICBzY2hlbWVQdUJ1OiBzY2hlbWUkZSwKICAgICAgICBpbnRlcnBvbGF0ZVB1UmQ6IFB1UmQsCiAgICAgICAgc2NoZW1lUHVSZDogc2NoZW1lJGYsCiAgICAgICAgaW50ZXJwb2xhdGVSZFB1OiBSZFB1LAogICAgICAgIHNjaGVtZVJkUHU6IHNjaGVtZSRnLAogICAgICAgIGludGVycG9sYXRlWWxHbkJ1OiBZbEduQnUsCiAgICAgICAgc2NoZW1lWWxHbkJ1OiBzY2hlbWUkaCwKICAgICAgICBpbnRlcnBvbGF0ZVlsR246IFlsR24sCiAgICAgICAgc2NoZW1lWWxHbjogc2NoZW1lJGksCiAgICAgICAgaW50ZXJwb2xhdGVZbE9yQnI6IFlsT3JCciwKICAgICAgICBzY2hlbWVZbE9yQnI6IHNjaGVtZSRqLAogICAgICAgIGludGVycG9sYXRlWWxPclJkOiBZbE9yUmQsCiAgICAgICAgc2NoZW1lWWxPclJkOiBzY2hlbWUkaywKICAgICAgICBpbnRlcnBvbGF0ZUJsdWVzOiBCbHVlcywKICAgICAgICBzY2hlbWVCbHVlczogc2NoZW1lJGwsCiAgICAgICAgaW50ZXJwb2xhdGVHcmVlbnM6IEdyZWVucywKICAgICAgICBzY2hlbWVHcmVlbnM6IHNjaGVtZSRtLAogICAgICAgIGludGVycG9sYXRlR3JleXM6IEdyZXlzLAogICAgICAgIHNjaGVtZUdyZXlzOiBzY2hlbWUkbiwKICAgICAgICBpbnRlcnBvbGF0ZVB1cnBsZXM6IFB1cnBsZXMsCiAgICAgICAgc2NoZW1lUHVycGxlczogc2NoZW1lJG8sCiAgICAgICAgaW50ZXJwb2xhdGVSZWRzOiBSZWRzLAogICAgICAgIHNjaGVtZVJlZHM6IHNjaGVtZSRwLAogICAgICAgIGludGVycG9sYXRlT3JhbmdlczogT3JhbmdlcywKICAgICAgICBzY2hlbWVPcmFuZ2VzOiBzY2hlbWUkcSwKICAgICAgICBpbnRlcnBvbGF0ZUNpdmlkaXM6IGNpdmlkaXMsCiAgICAgICAgaW50ZXJwb2xhdGVDdWJlaGVsaXhEZWZhdWx0OiBjdWJlaGVsaXgkMywKICAgICAgICBpbnRlcnBvbGF0ZVJhaW5ib3c6IHJhaW5ib3csCiAgICAgICAgaW50ZXJwb2xhdGVXYXJtOiB3YXJtLAogICAgICAgIGludGVycG9sYXRlQ29vbDogY29vbCwKICAgICAgICBpbnRlcnBvbGF0ZVNpbmVib3c6IHNpbmVib3csCiAgICAgICAgaW50ZXJwb2xhdGVUdXJibzogdHVyYm8sCiAgICAgICAgaW50ZXJwb2xhdGVWaXJpZGlzOiB2aXJpZGlzLAogICAgICAgIGludGVycG9sYXRlTWFnbWE6IG1hZ21hLAogICAgICAgIGludGVycG9sYXRlSW5mZXJubzogaW5mZXJubywKICAgICAgICBpbnRlcnBvbGF0ZVBsYXNtYTogcGxhc21hLAogICAgICAgIGNyZWF0ZTogY3JlYXRlLAogICAgICAgIGNyZWF0b3I6IGNyZWF0b3IsCiAgICAgICAgbG9jYWw6IGxvY2FsLAogICAgICAgIG1hdGNoZXI6IG1hdGNoZXIsCiAgICAgICAgbW91c2U6IG1vdXNlLAogICAgICAgIG5hbWVzcGFjZTogbmFtZXNwYWNlLAogICAgICAgIG5hbWVzcGFjZXM6IG5hbWVzcGFjZXMsCiAgICAgICAgY2xpZW50UG9pbnQ6IHBvaW50LAogICAgICAgIHNlbGVjdDogc2VsZWN0LAogICAgICAgIHNlbGVjdEFsbDogc2VsZWN0QWxsLAogICAgICAgIHNlbGVjdGlvbjogc2VsZWN0aW9uLAogICAgICAgIHNlbGVjdG9yOiBzZWxlY3RvciwKICAgICAgICBzZWxlY3RvckFsbDogc2VsZWN0b3JBbGwsCiAgICAgICAgc3R5bGU6IHN0eWxlVmFsdWUsCiAgICAgICAgdG91Y2g6IHRvdWNoLAogICAgICAgIHRvdWNoZXM6IHRvdWNoZXMsCiAgICAgICAgd2luZG93OiBkZWZhdWx0VmlldywKICAgICAgICBnZXQgZXZlbnQgKCkgeyByZXR1cm4gZXZlbnQ7IH0sCiAgICAgICAgY3VzdG9tRXZlbnQ6IGN1c3RvbUV2ZW50LAogICAgICAgIGFyYzogYXJjLAogICAgICAgIGFyZWE6IGFyZWEkMywKICAgICAgICBsaW5lOiBsaW5lLAogICAgICAgIHBpZTogcGllLAogICAgICAgIGFyZWFSYWRpYWw6IGFyZWFSYWRpYWwsCiAgICAgICAgcmFkaWFsQXJlYTogYXJlYVJhZGlhbCwKICAgICAgICBsaW5lUmFkaWFsOiBsaW5lUmFkaWFsJDEsCiAgICAgICAgcmFkaWFsTGluZTogbGluZVJhZGlhbCQxLAogICAgICAgIHBvaW50UmFkaWFsOiBwb2ludFJhZGlhbCwKICAgICAgICBsaW5rSG9yaXpvbnRhbDogbGlua0hvcml6b250YWwsCiAgICAgICAgbGlua1ZlcnRpY2FsOiBsaW5rVmVydGljYWwsCiAgICAgICAgbGlua1JhZGlhbDogbGlua1JhZGlhbCwKICAgICAgICBzeW1ib2w6IHN5bWJvbCwKICAgICAgICBzeW1ib2xzOiBzeW1ib2xzLAogICAgICAgIHN5bWJvbENpcmNsZTogY2lyY2xlJDIsCiAgICAgICAgc3ltYm9sQ3Jvc3M6IGNyb3NzJDIsCiAgICAgICAgc3ltYm9sRGlhbW9uZDogZGlhbW9uZCwKICAgICAgICBzeW1ib2xTcXVhcmU6IHNxdWFyZSwKICAgICAgICBzeW1ib2xTdGFyOiBzdGFyLAogICAgICAgIHN5bWJvbFRyaWFuZ2xlOiB0cmlhbmdsZSwKICAgICAgICBzeW1ib2xXeWU6IHd5ZSwKICAgICAgICBjdXJ2ZUJhc2lzQ2xvc2VkOiBiYXNpc0Nsb3NlZCQxLAogICAgICAgIGN1cnZlQmFzaXNPcGVuOiBiYXNpc09wZW4sCiAgICAgICAgY3VydmVCYXNpczogYmFzaXMkMiwKICAgICAgICBjdXJ2ZUJ1bmRsZTogYnVuZGxlLAogICAgICAgIGN1cnZlQ2FyZGluYWxDbG9zZWQ6IGNhcmRpbmFsQ2xvc2VkLAogICAgICAgIGN1cnZlQ2FyZGluYWxPcGVuOiBjYXJkaW5hbE9wZW4sCiAgICAgICAgY3VydmVDYXJkaW5hbDogY2FyZGluYWwsCiAgICAgICAgY3VydmVDYXRtdWxsUm9tQ2xvc2VkOiBjYXRtdWxsUm9tQ2xvc2VkLAogICAgICAgIGN1cnZlQ2F0bXVsbFJvbU9wZW46IGNhdG11bGxSb21PcGVuLAogICAgICAgIGN1cnZlQ2F0bXVsbFJvbTogY2F0bXVsbFJvbSwKICAgICAgICBjdXJ2ZUxpbmVhckNsb3NlZDogbGluZWFyQ2xvc2VkLAogICAgICAgIGN1cnZlTGluZWFyOiBjdXJ2ZUxpbmVhciwKICAgICAgICBjdXJ2ZU1vbm90b25lWDogbW9ub3RvbmVYLAogICAgICAgIGN1cnZlTW9ub3RvbmVZOiBtb25vdG9uZVksCiAgICAgICAgY3VydmVOYXR1cmFsOiBuYXR1cmFsLAogICAgICAgIGN1cnZlU3RlcDogc3RlcCwKICAgICAgICBjdXJ2ZVN0ZXBBZnRlcjogc3RlcEFmdGVyLAogICAgICAgIGN1cnZlU3RlcEJlZm9yZTogc3RlcEJlZm9yZSwKICAgICAgICBzdGFjazogc3RhY2ssCiAgICAgICAgc3RhY2tPZmZzZXRFeHBhbmQ6IGV4cGFuZCwKICAgICAgICBzdGFja09mZnNldERpdmVyZ2luZzogZGl2ZXJnaW5nJDEsCiAgICAgICAgc3RhY2tPZmZzZXROb25lOiBub25lJDEsCiAgICAgICAgc3RhY2tPZmZzZXRTaWxob3VldHRlOiBzaWxob3VldHRlLAogICAgICAgIHN0YWNrT2Zmc2V0V2lnZ2xlOiB3aWdnbGUsCiAgICAgICAgc3RhY2tPcmRlckFwcGVhcmFuY2U6IGFwcGVhcmFuY2UsCiAgICAgICAgc3RhY2tPcmRlckFzY2VuZGluZzogYXNjZW5kaW5nJDMsCiAgICAgICAgc3RhY2tPcmRlckRlc2NlbmRpbmc6IGRlc2NlbmRpbmckMiwKICAgICAgICBzdGFja09yZGVySW5zaWRlT3V0OiBpbnNpZGVPdXQsCiAgICAgICAgc3RhY2tPcmRlck5vbmU6IG5vbmUkMiwKICAgICAgICBzdGFja09yZGVyUmV2ZXJzZTogcmV2ZXJzZSwKICAgICAgICB0aW1lSW50ZXJ2YWw6IG5ld0ludGVydmFsLAogICAgICAgIHRpbWVNaWxsaXNlY29uZDogbWlsbGlzZWNvbmQsCiAgICAgICAgdGltZU1pbGxpc2Vjb25kczogbWlsbGlzZWNvbmRzLAogICAgICAgIHV0Y01pbGxpc2Vjb25kOiBtaWxsaXNlY29uZCwKICAgICAgICB1dGNNaWxsaXNlY29uZHM6IG1pbGxpc2Vjb25kcywKICAgICAgICB0aW1lU2Vjb25kOiBzZWNvbmQsCiAgICAgICAgdGltZVNlY29uZHM6IHNlY29uZHMsCiAgICAgICAgdXRjU2Vjb25kOiBzZWNvbmQsCiAgICAgICAgdXRjU2Vjb25kczogc2Vjb25kcywKICAgICAgICB0aW1lTWludXRlOiBtaW51dGUsCiAgICAgICAgdGltZU1pbnV0ZXM6IG1pbnV0ZXMsCiAgICAgICAgdGltZUhvdXI6IGhvdXIsCiAgICAgICAgdGltZUhvdXJzOiBob3VycywKICAgICAgICB0aW1lRGF5OiBkYXksCiAgICAgICAgdGltZURheXM6IGRheXMsCiAgICAgICAgdGltZVdlZWs6IHN1bmRheSwKICAgICAgICB0aW1lV2Vla3M6IHN1bmRheXMsCiAgICAgICAgdGltZVN1bmRheTogc3VuZGF5LAogICAgICAgIHRpbWVTdW5kYXlzOiBzdW5kYXlzLAogICAgICAgIHRpbWVNb25kYXk6IG1vbmRheSwKICAgICAgICB0aW1lTW9uZGF5czogbW9uZGF5cywKICAgICAgICB0aW1lVHVlc2RheTogdHVlc2RheSwKICAgICAgICB0aW1lVHVlc2RheXM6IHR1ZXNkYXlzLAogICAgICAgIHRpbWVXZWRuZXNkYXk6IHdlZG5lc2RheSwKICAgICAgICB0aW1lV2VkbmVzZGF5czogd2VkbmVzZGF5cywKICAgICAgICB0aW1lVGh1cnNkYXk6IHRodXJzZGF5LAogICAgICAgIHRpbWVUaHVyc2RheXM6IHRodXJzZGF5cywKICAgICAgICB0aW1lRnJpZGF5OiBmcmlkYXksCiAgICAgICAgdGltZUZyaWRheXM6IGZyaWRheXMsCiAgICAgICAgdGltZVNhdHVyZGF5OiBzYXR1cmRheSwKICAgICAgICB0aW1lU2F0dXJkYXlzOiBzYXR1cmRheXMsCiAgICAgICAgdGltZU1vbnRoOiBtb250aCwKICAgICAgICB0aW1lTW9udGhzOiBtb250aHMsCiAgICAgICAgdGltZVllYXI6IHllYXIsCiAgICAgICAgdGltZVllYXJzOiB5ZWFycywKICAgICAgICB1dGNNaW51dGU6IHV0Y01pbnV0ZSwKICAgICAgICB1dGNNaW51dGVzOiB1dGNNaW51dGVzLAogICAgICAgIHV0Y0hvdXI6IHV0Y0hvdXIsCiAgICAgICAgdXRjSG91cnM6IHV0Y0hvdXJzLAogICAgICAgIHV0Y0RheTogdXRjRGF5LAogICAgICAgIHV0Y0RheXM6IHV0Y0RheXMsCiAgICAgICAgdXRjV2VlazogdXRjU3VuZGF5LAogICAgICAgIHV0Y1dlZWtzOiB1dGNTdW5kYXlzLAogICAgICAgIHV0Y1N1bmRheTogdXRjU3VuZGF5LAogICAgICAgIHV0Y1N1bmRheXM6IHV0Y1N1bmRheXMsCiAgICAgICAgdXRjTW9uZGF5OiB1dGNNb25kYXksCiAgICAgICAgdXRjTW9uZGF5czogdXRjTW9uZGF5cywKICAgICAgICB1dGNUdWVzZGF5OiB1dGNUdWVzZGF5LAogICAgICAgIHV0Y1R1ZXNkYXlzOiB1dGNUdWVzZGF5cywKICAgICAgICB1dGNXZWRuZXNkYXk6IHV0Y1dlZG5lc2RheSwKICAgICAgICB1dGNXZWRuZXNkYXlzOiB1dGNXZWRuZXNkYXlzLAogICAgICAgIHV0Y1RodXJzZGF5OiB1dGNUaHVyc2RheSwKICAgICAgICB1dGNUaHVyc2RheXM6IHV0Y1RodXJzZGF5cywKICAgICAgICB1dGNGcmlkYXk6IHV0Y0ZyaWRheSwKICAgICAgICB1dGNGcmlkYXlzOiB1dGNGcmlkYXlzLAogICAgICAgIHV0Y1NhdHVyZGF5OiB1dGNTYXR1cmRheSwKICAgICAgICB1dGNTYXR1cmRheXM6IHV0Y1NhdHVyZGF5cywKICAgICAgICB1dGNNb250aDogdXRjTW9udGgsCiAgICAgICAgdXRjTW9udGhzOiB1dGNNb250aHMsCiAgICAgICAgdXRjWWVhcjogdXRjWWVhciwKICAgICAgICB1dGNZZWFyczogdXRjWWVhcnMsCiAgICAgICAgdGltZUZvcm1hdERlZmF1bHRMb2NhbGU6IGRlZmF1bHRMb2NhbGUkMSwKICAgICAgICBnZXQgdGltZUZvcm1hdCAoKSB7IHJldHVybiB0aW1lRm9ybWF0OyB9LAogICAgICAgIGdldCB0aW1lUGFyc2UgKCkgeyByZXR1cm4gdGltZVBhcnNlOyB9LAogICAgICAgIGdldCB1dGNGb3JtYXQgKCkgeyByZXR1cm4gdXRjRm9ybWF0OyB9LAogICAgICAgIGdldCB1dGNQYXJzZSAoKSB7IHJldHVybiB1dGNQYXJzZTsgfSwKICAgICAgICB0aW1lRm9ybWF0TG9jYWxlOiBmb3JtYXRMb2NhbGUkMSwKICAgICAgICBpc29Gb3JtYXQ6IGZvcm1hdElzbywKICAgICAgICBpc29QYXJzZTogcGFyc2VJc28sCiAgICAgICAgbm93OiBub3csCiAgICAgICAgdGltZXI6IHRpbWVyLAogICAgICAgIHRpbWVyRmx1c2g6IHRpbWVyRmx1c2gsCiAgICAgICAgdGltZW91dDogdGltZW91dCQxLAogICAgICAgIGludGVydmFsOiBpbnRlcnZhbCQxLAogICAgICAgIHRyYW5zaXRpb246IHRyYW5zaXRpb24sCiAgICAgICAgYWN0aXZlOiBhY3RpdmUsCiAgICAgICAgaW50ZXJydXB0OiBpbnRlcnJ1cHQsCiAgICAgICAgdm9yb25vaTogdm9yb25vaSwKICAgICAgICB6b29tOiB6b29tLAogICAgICAgIHpvb21UcmFuc2Zvcm06IHRyYW5zZm9ybSQxLAogICAgICAgIHpvb21JZGVudGl0eTogaWRlbnRpdHkkOQogICAgfSk7CgogICAgLyogQ29weXJpZ2h0IDIwMTYgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjb25zdCBwYWxldHRlcyA9IHsKICAgICAgICBnb29nbGVTdGFuZGFyZDogWwogICAgICAgICAgICAnI2RiNDQzNycsCiAgICAgICAgICAgICcjZmY3MDQzJywKICAgICAgICAgICAgJyNmNGI0MDAnLAogICAgICAgICAgICAnIzBmOWQ1OCcsCiAgICAgICAgICAgICcjMDA3OTZiJywKICAgICAgICAgICAgJyMwMGFjYzEnLAogICAgICAgICAgICAnIzQyODVmNCcsCiAgICAgICAgICAgICcjNWM2YmMwJywKICAgICAgICAgICAgJyNhYjQ3YmMnLAogICAgICAgIF0sCiAgICAgICAgZ29vZ2xlQ29vbDogWwogICAgICAgICAgICAnIzllOWQyNCcsCiAgICAgICAgICAgICcjMGY5ZDU4JywKICAgICAgICAgICAgJyMwMDc5NmInLAogICAgICAgICAgICAnIzAwYWNjMScsCiAgICAgICAgICAgICcjNDI4NWY0JywKICAgICAgICAgICAgJyM1YzZiYzAnLAogICAgICAgICAgICAnIzYwN2Q4YicsCiAgICAgICAgXSwKICAgICAgICBnb29nbGVXYXJtOiBbCiAgICAgICAgICAgICcjNzk1NTQ4JywKICAgICAgICAgICAgJyNhYjQ3YmMnLAogICAgICAgICAgICAnI2YwNjI5MicsCiAgICAgICAgICAgICcjYzIxODViJywKICAgICAgICAgICAgJyNkYjQ0MzcnLAogICAgICAgICAgICAnI2ZmNzA0MycsCiAgICAgICAgICAgICcjZjRiNDAwJywKICAgICAgICBdLAogICAgICAgIGdvb2dsZUNvbG9yQmxpbmRBc3Npc3Q6IFsKICAgICAgICAgICAgJyNmZjcwNDMnLAogICAgICAgICAgICAnIzAwQUNDMScsCiAgICAgICAgICAgICcjQUI0N0JDJywKICAgICAgICAgICAgJyMyQTU2QzYnLAogICAgICAgICAgICAnIzBiODA0MycsCiAgICAgICAgICAgICcjRjdDQjREJywKICAgICAgICAgICAgJyNjMGNhMzMnLAogICAgICAgICAgICAnIzVlMzViMScsCiAgICAgICAgICAgICcjQTUyNzE0JywKICAgICAgICBdLAogICAgICAgIC8vIEEgY29sb3JibGluZC1mcmllbmRseSBwYWxldHRlIGRlc2lnbmVkIGZvciBUZW5zb3JCb2FyZCBieSBQYXVsIFRvbAogICAgICAgIC8vIChodHRwczovL3BlcnNvbmFsLnNyb24ubmwvfnBhdWx0LykuCiAgICAgICAgdGVuc29yYm9hcmRDb2xvckJsaW5kQXNzaXN0OiBbCiAgICAgICAgICAgICcjZmY3MDQzJywKICAgICAgICAgICAgJyMwMDc3YmInLAogICAgICAgICAgICAnI2NjMzMxMScsCiAgICAgICAgICAgICcjMzNiYmVlJywKICAgICAgICAgICAgJyNlZTMzNzcnLAogICAgICAgICAgICAnIzAwOTk4OCcsCiAgICAgICAgICAgICcjYmJiYmJiJywKICAgICAgICBdLAogICAgICAgIC8vIFRoZXNlIHBhbGV0dGVzIHRyeSB0byBiZSBiZXR0ZXIgZm9yIGNvbG9yIGRpZmZlcmVudGlhdGlvbi4KICAgICAgICAvLyBodHRwczovL3BlcnNvbmFsLnNyb24ubmwvfnBhdWx0LwogICAgICAgIGNvbG9yQmxpbmRBc3Npc3QxOiBbCiAgICAgICAgICAgICcjNDQ3N2FhJywKICAgICAgICAgICAgJyM0NGFhYWEnLAogICAgICAgICAgICAnI2FhYWE0NCcsCiAgICAgICAgICAgICcjYWE3NzQ0JywKICAgICAgICAgICAgJyNhYTQ0NTUnLAogICAgICAgICAgICAnI2FhNDQ4OCcsCiAgICAgICAgXSwKICAgICAgICBjb2xvckJsaW5kQXNzaXN0MjogWwogICAgICAgICAgICAnIzg4Y2NlZScsCiAgICAgICAgICAgICcjNDRhYTk5JywKICAgICAgICAgICAgJyMxMTc3MzMnLAogICAgICAgICAgICAnIzk5OTkzMycsCiAgICAgICAgICAgICcjZGRjYzc3JywKICAgICAgICAgICAgJyNjYzY2NzcnLAogICAgICAgICAgICAnIzg4MjI1NScsCiAgICAgICAgICAgICcjYWE0NDk5JywKICAgICAgICBdLAogICAgICAgIGNvbG9yQmxpbmRBc3Npc3QzOiBbCiAgICAgICAgICAgICcjMzMyMjg4JywKICAgICAgICAgICAgJyM2Njk5Y2MnLAogICAgICAgICAgICAnIzg4Y2NlZScsCiAgICAgICAgICAgICcjNDRhYTk5JywKICAgICAgICAgICAgJyMxMTc3MzMnLAogICAgICAgICAgICAnIzk5OTkzMycsCiAgICAgICAgICAgICcjZGRjYzc3JywKICAgICAgICAgICAgJyNjYzY2NzcnLAogICAgICAgICAgICAnI2FhNDQ2NicsCiAgICAgICAgICAgICcjODgyMjU1JywKICAgICAgICAgICAgJyM2NjExMDAnLAogICAgICAgICAgICAnI2FhNDQ5OScsCiAgICAgICAgXSwKICAgICAgICBjb2xvckJsaW5kQXNzaXN0NDogWwogICAgICAgICAgICAvLyBQYXVsIFRvbCdzICJBbHRlcm5hdGl2ZSBTY2hlbWUgZm9yIFF1YWxpdGF0aXZlIERhdGEiLiBQcmVmZXJyZWQKICAgICAgICAgICAgLy8gaWYgYHRlbnNvcmJvYXJkQ29sb3JCbGluZEFzc2lzdGAgY2Fubm90IGJlIHVzZWQgZm9yIGFueSByZWFzb24uCiAgICAgICAgICAgICcjNDQ3N2FhJywKICAgICAgICAgICAgJyM2NmNjZWUnLAogICAgICAgICAgICAnIzIyODgzMycsCiAgICAgICAgICAgICcjY2NiYjQ0JywKICAgICAgICAgICAgJyNlZTY2NzcnLAogICAgICAgICAgICAnI2FhMzM3NycsCiAgICAgICAgICAgICcjYmJiYmJiJywKICAgICAgICBdLAogICAgICAgIC8vIGJhc2VkIG9uIHRoaXMgcGFsZXR0ZTogaHR0cDovL21rd2ViLmJjZ3NjLmNhL2Jpb3ZpczIwMTIvCiAgICAgICAgY29sb3JCbGluZEFzc2lzdDU6IFsKICAgICAgICAgICAgJyNGRjZEQjYnLAogICAgICAgICAgICAnIzkyMDAwMCcsCiAgICAgICAgICAgICcjOTI0OTAwJywKICAgICAgICAgICAgJyNEQkQxMDAnLAogICAgICAgICAgICAnIzI0RkYyNCcsCiAgICAgICAgICAgICcjMDA2RERCJywKICAgICAgICAgICAgJyM0OTAwOTInLAogICAgICAgIF0sCiAgICAgICAgbWxkYXNoOiBbCiAgICAgICAgICAgICcjRTQ3RUFEJywKICAgICAgICAgICAgJyNGNDY0MEQnLAogICAgICAgICAgICAnI0ZBQTMwMCcsCiAgICAgICAgICAgICcjRjVFNjM2JywKICAgICAgICAgICAgJyMwMEEwNzcnLAogICAgICAgICAgICAnIzAwNzdCOCcsCiAgICAgICAgICAgICcjMDBCN0VEJywKICAgICAgICBdLAogICAgfTsKICAgIGNvbnN0IHN0YW5kYXJkID0gcGFsZXR0ZXMudGVuc29yYm9hcmRDb2xvckJsaW5kQXNzaXN0OwoKICAgIC8qIENvcHlyaWdodCAyMDE4IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY2xhc3MgRXhwZXJpbWVudHNTdG9yZSBleHRlbmRzIEJhc2VTdG9yZSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX2V4cGVyaW1lbnRzID0gW107CiAgICAgICAgfQogICAgICAgIGxvYWQoKSB7CiAgICAgICAgICAgIGNvbnN0IHVybCA9IGdldFJvdXRlcigpLmV4cGVyaW1lbnRzKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJlcXVlc3RNYW5hZ2VyLnJlcXVlc3QodXJsKS50aGVuKChuZXdFeHBlcmltZW50cykgPT4gewogICAgICAgICAgICAgICAgaWYgKCFsb2Rhc2guaXNFcXVhbCh0aGlzLl9leHBlcmltZW50cywgbmV3RXhwZXJpbWVudHMpKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fZXhwZXJpbWVudHMgPSBuZXdFeHBlcmltZW50czsKICAgICAgICAgICAgICAgICAgICB0aGlzLmVtaXRDaGFuZ2UoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdldCB0aGUgY3VycmVudCBsaXN0IG9mIGV4cGVyaW1lbnRzLiBJZiBubyBkYXRhIGlzIGF2YWlsYWJsZSwgdGhpcyB3aWxsIGJlCiAgICAgICAgICogYW4gZW1wdHkgYXJyYXkgKGkuZS4sIHRoZXJlIGlzIG5vIGRpc3RpbmN0aW9uIGJldHdlZW4gIm5vIGV4cGVyaW1lbnQiIGFuZAogICAgICAgICAqICJubyBleHBlcmltZW50IHlldCIpLgogICAgICAgICAqLwogICAgICAgIGdldEV4cGVyaW1lbnRzKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZXhwZXJpbWVudHMuc2xpY2UoKTsKICAgICAgICB9CiAgICB9CiAgICBjb25zdCBleHBlcmltZW50c1N0b3JlID0gbmV3IEV4cGVyaW1lbnRzU3RvcmUoKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8vIEV4YW1wbGUgdXNhZ2U6CiAgICAvLyBydW5zID0gWyJ0cmFpbiIsICJ0ZXN0IiwgInRlc3QxIiwgInRlc3QyIl0KICAgIC8vIGNjcyA9IG5ldyBDb2xvclNjYWxlKCk7CiAgICAvLyBjY3MuZG9tYWluKHJ1bnMpOwogICAgLy8gY2NzLmdldENvbG9yKCJ0cmFpbiIpOwogICAgLy8gY2NzLmdldENvbG9yKCJ0ZXN0MSIpOwogICAgY2xhc3MgQ29sb3JTY2FsZSB7CiAgICAgICAgLyoqCiAgICAgICAgICogQ3JlYXRlcyBhIGNvbG9yIHNjYWxlIHdpdGggb3B0aW9uYWwgY3VzdG9tIHBhbGV0dGUuCiAgICAgICAgICogQHBhcmFtIHtBcnJheTxzdHJpbmc+fSBwYWxldHRlIFRoZSBjb2xvciBwYWxldHRlIHRvIHVzZSwgYXMgYW4KICAgICAgICAgKiAgIEFycmF5IG9mIGhleCBzdHJpbmdzLiBEZWZhdWx0cyB0byB0aGUgc3RhbmRhcmQgcGFsZXR0ZS4KICAgICAgICAgKi8KICAgICAgICBjb25zdHJ1Y3RvcihwYWxldHRlID0gc3RhbmRhcmQpIHsKICAgICAgICAgICAgdGhpcy5wYWxldHRlID0gcGFsZXR0ZTsKICAgICAgICAgICAgdGhpcy5pZGVudGlmaWVycyA9IG1hcCQxKCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFNldCB0aGUgZG9tYWluIG9mIHN0cmluZ3MuCiAgICAgICAgICogQHBhcmFtIHtBcnJheTxzdHJpbmc+fSBzdHJpbmdzIC0gQW4gYXJyYXkgb2YgcG9zc2libGUgc3RyaW5ncyB0byB1c2UgYXMgdGhlCiAgICAgICAgICogICAgIGRvbWFpbiBmb3IgeW91ciBzY2FsZS4KICAgICAgICAgKi8KICAgICAgICBzZXREb21haW4oc3RyaW5ncykgewogICAgICAgICAgICB0aGlzLmlkZW50aWZpZXJzID0gbWFwJDEoKTsKICAgICAgICAgICAgc3RyaW5ncy5mb3JFYWNoKChzLCBpKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLmlkZW50aWZpZXJzLnNldChzLCB0aGlzLnBhbGV0dGVbaSAlIHRoaXMucGFsZXR0ZS5sZW5ndGhdKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBVc2UgdGhlIGNvbG9yIHNjYWxlIHRvIHRyYW5zZm9ybSBhbiBlbGVtZW50IGluIHRoZSBkb21haW4gaW50byBhIGNvbG9yLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBUaGUgaW5wdXQgc3RyaW5nIHRvIG1hcCB0byBhIGNvbG9yLgogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gVGhlIGNvbG9yIGNvcnJlc3BvbmRpbmcgdG8gdGhhdCBpbnB1dCBzdHJpbmcuCiAgICAgICAgICogQHRocm93cyBXaWxsIGVycm9yIGlmIGlucHV0IHN0cmluZyBpcyBub3QgaW4gdGhlIHNjYWxlJ3MgZG9tYWluLgogICAgICAgICAqLwogICAgICAgIGdldENvbG9yKHMpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLmlkZW50aWZpZXJzLmhhcyhzKSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGBTdHJpbmcgJHtzfSB3YXMgbm90IGluIHRoZSBkb21haW4uYCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuaWRlbnRpZmllcnMuZ2V0KHMpOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQSBjb2xvciBzY2FsZSBvZiBhIGRvbWFpbiBmcm9tIGEgc3RvcmUuIEF1dG9tYXRpY2FsbHkgdXBkYXRlZCB3aGVuIHRoZSBzdG9yZQogICAgICogZW1pdHMgYSBjaGFuZ2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNyZWF0ZUF1dG9VcGRhdGVDb2xvclNjYWxlKHN0b3JlLCBnZXREb21haW4pIHsKICAgICAgICBjb25zdCBjb2xvclNjYWxlID0gbmV3IENvbG9yU2NhbGUoKTsKICAgICAgICBmdW5jdGlvbiB1cGRhdGVSdW5zQ29sb3JTY2FsZSgpIHsKICAgICAgICAgICAgY29sb3JTY2FsZS5zZXREb21haW4oZ2V0RG9tYWluKCkpOwogICAgICAgIH0KICAgICAgICBzdG9yZS5hZGRMaXN0ZW5lcih1cGRhdGVSdW5zQ29sb3JTY2FsZSk7CiAgICAgICAgdXBkYXRlUnVuc0NvbG9yU2NhbGUoKTsKICAgICAgICByZXR1cm4gKGRvbWFpbikgPT4gY29sb3JTY2FsZS5nZXRDb2xvcihkb21haW4pOwogICAgfQogICAgY29uc3QgcnVuc0NvbG9yU2NhbGUgPSBjcmVhdGVBdXRvVXBkYXRlQ29sb3JTY2FsZShydW5zU3RvcmUsICgpID0+IHJ1bnNTdG9yZS5nZXRSdW5zKCkpOwogICAgY29uc3QgZXhwZXJpbWVudHNDb2xvclNjYWxlID0gY3JlYXRlQXV0b1VwZGF0ZUNvbG9yU2NhbGUoZXhwZXJpbWVudHNTdG9yZSwgKCkgPT4gewogICAgICAgIHJldHVybiBleHBlcmltZW50c1N0b3JlLmdldEV4cGVyaW1lbnRzKCkubWFwKCh7IG5hbWUgfSkgPT4gbmFtZSk7CiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHJlZ2lzdGVyU3R5bGVEb21Nb2R1bGUoewogICAgICAgIG1vZHVsZU5hbWU6ICdydW4tY29sb3Itc3R5bGUnLAogICAgICAgIHN0eWxlQ29udGVudDogYAogICAgW2NvbG9yLWNsYXNzPSdsaWdodC1ibHVlJ10gcGFwZXItY2hlY2tib3ggewogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLWxpZ2h0LWJsdWUtNTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWluay1jb2xvcjogdmFyKC0tcGFwZXItbGlnaHQtYmx1ZS01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItbGlnaHQtYmx1ZS05MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLWxpZ2h0LWJsdWUtOTAwKTsKICAgIH0KICAgIFtjb2xvci1jbGFzcz0ncmVkJ10gcGFwZXItY2hlY2tib3ggewogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLXJlZC01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1yZWQtNTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLXJlZC05MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLXJlZC05MDApOwogICAgfQogICAgW2NvbG9yLWNsYXNzPSdncmVlbiddIHBhcGVyLWNoZWNrYm94IHsKICAgICAgLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWNvbG9yOiB2YXIoLS1wYXBlci1ncmVlbi01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1ncmVlbi01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItZ3JlZW4tOTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1ncmVlbi05MDApOwogICAgfQogICAgW2NvbG9yLWNsYXNzPSdwdXJwbGUnXSBwYXBlci1jaGVja2JveCB7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItcHVycGxlLTUwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLXB1cnBsZS01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItcHVycGxlLTkwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtdW5jaGVja2VkLWluay1jb2xvcjogdmFyKC0tcGFwZXItcHVycGxlLTkwMCk7CiAgICB9CiAgICBbY29sb3ItY2xhc3M9J3RlYWwnXSBwYXBlci1jaGVja2JveCB7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItdGVhbC01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci10ZWFsLTUwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtdW5jaGVja2VkLWNvbG9yOiB2YXIoLS1wYXBlci10ZWFsLTkwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtdW5jaGVja2VkLWluay1jb2xvcjogdmFyKC0tcGFwZXItdGVhbC05MDApOwogICAgfQogICAgW2NvbG9yLWNsYXNzPSdwaW5rJ10gcGFwZXItY2hlY2tib3ggewogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLXBpbmstNTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWluay1jb2xvcjogdmFyKC0tcGFwZXItcGluay01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItcGluay05MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLXBpbmstOTAwKTsKICAgIH0KICAgIFtjb2xvci1jbGFzcz0nb3JhbmdlJ10gcGFwZXItY2hlY2tib3ggewogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLW9yYW5nZS01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1vcmFuZ2UtNTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtY29sb3I6IHZhcigtLXBhcGVyLW9yYW5nZS05MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLW9yYW5nZS05MDApOwogICAgfQogICAgW2NvbG9yLWNsYXNzPSdicm93biddIHBhcGVyLWNoZWNrYm94IHsKICAgICAgLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWNvbG9yOiB2YXIoLS1wYXBlci1icm93bi01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LWNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1icm93bi01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItYnJvd24tOTAwKTsKICAgICAgLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtaW5rLWNvbG9yOiB2YXIoLS1wYXBlci1icm93bi05MDApOwogICAgfQogICAgW2NvbG9yLWNsYXNzPSdpbmRpZ28nXSBwYXBlci1jaGVja2JveCB7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItaW5kaWdvLTUwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1pbmstY29sb3I6IHZhcigtLXBhcGVyLWluZGlnby01MDApOwogICAgICAtLXBhcGVyLWNoZWNrYm94LXVuY2hlY2tlZC1jb2xvcjogdmFyKC0tcGFwZXItaW5kaWdvLTkwMCk7CiAgICAgIC0tcGFwZXItY2hlY2tib3gtdW5jaGVja2VkLWluay1jb2xvcjogdmFyKC0tcGFwZXItaW5kaWdvLTkwMCk7CiAgICB9CiAgYCwKICAgIH0pOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoKICAgIHRmLW11bHRpLWNoZWNrYm94IGNyZWF0ZXMgYSBsaXN0IG9mIGNoZWNrYm94ZXMgdGhhdCBjYW4gYmUgdXNlZCB0byB0b2dnbGUgb24gb3Igb2ZmCiAgICBhIGxhcmdlIG51bWJlciBvZiB2YWx1ZXMuIEVhY2ggY2hlY2tib3ggZGlzcGxheXMgYSBuYW1lLCBhbmQgbWF5IGFsc28gaGF2ZSBhbgogICAgYXNzb2NpYXRlZCB0b29sdGlwIHZhbHVlLiBDaGVja2JveGVzIGNhbiBiZSBoaWdobGlnaHRlZCwgaGlkZGVuLCBhbmQgcmUtb3JkZXJlZC4KCiAgICB0Zi1tdWx0aS1jaGVja2JveCBhc3N1bWVzIHRoYXQgdGhlIG5hbWVzIG1heSBiZSB2ZXJ5IGxvbmcgY29tcGFyZWQgdG8gdGhlIHdpZHRoCiAgICBvZiB0aGUgY2hlY2tib3gsIGFuZCB0aGUgbnVtYmVyIG9mIG5hbWVzIG1heSBhbHNvIGJlIHZlcnkgbGFyZ2UsIGFuZCB3b3JrcyB0bwogICAgaGFuZGxlIHRoZXNlIHNpdHVhdGlvbnMgZ3JhY2VmdWxseS4KICAgICovCiAgICBsZXQgVGZNdWx0aUNoZWNrYm94ID0gY2xhc3MgVGZNdWx0aUNoZWNrYm94IGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8vIEFsbCB0aGUgdmFsdWVzIG9mIHRoZSBjaGVja2JveC4KICAgICAgICAgICAgdGhpcy5uYW1lcyA9IFtdOwogICAgICAgICAgICB0aGlzLmNvbG9yaW5nID0gewogICAgICAgICAgICAgICAgZ2V0Q29sb3I6ICgpID0+ICcnLAogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyBSZWdleCBmb3IgZmlsdGVyaW5nIHRoZSBuYW1lcy4KICAgICAgICAgICAgdGhpcy5yZWdleCA9ICcnOwogICAgICAgICAgICB0aGlzLnNlbGVjdGlvblN0YXRlID0ge307CiAgICAgICAgICAgIHRoaXMubWF4TmFtZXNUb0VuYWJsZUJ5RGVmYXVsdCA9IDQwOwogICAgICAgICAgICAvLyBVcGRhdGluZyB0aGUgcmVnZXggY2FuIGJlIHNsb3csIGJlY2F1c2UgaXQgaW52b2x2ZXMgdXBkYXRpbmcgc3R5bGVzCiAgICAgICAgICAgIC8vIG9uIGEgbGFyZ2UgbnVtYmVyIG9mIFBvbHltZXIgcGFwZXItY2hlY2tib3hlcy4gV2UgZG9uJ3Qgd2FudCB0byBkbwogICAgICAgICAgICAvLyB0aGlzIHdoaWxlIHRoZSB1c2VyIGlzIHR5cGluZywgYXMgaXQgbWF5IG1ha2UgYSBiYWQsIGxhZ2d5IFVJLgogICAgICAgICAgICAvLyBTbyB3ZSBkZWJvdW5jZSB0aGUgdXBkYXRlcyB0aGF0IGNvbWUgZnJvbSB1c2VyIHR5cGluZy4KICAgICAgICAgICAgdGhpcy5fZGVib3VuY2VkUmVnZXhDaGFuZ2UgPSB0aGlzLl9kZWJvdW5jZWRSZWdleENoYW5nZUltcGwoKTsKICAgICAgICB9CiAgICAgICAgX2RlYm91bmNlZFJlZ2V4Q2hhbmdlSW1wbCgpIHsKICAgICAgICAgICAgdmFyIGRlYm91bmNlZCA9IGxvZGFzaC5kZWJvdW5jZSgocikgPT4gewogICAgICAgICAgICAgICAgdGhpcy5yZWdleCA9IHI7CiAgICAgICAgICAgIH0sIDE1MCwgeyBsZWFkaW5nOiBmYWxzZSB9KTsKICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHZhciByID0gdGhpcy4kJCgnI25hbWVzLXJlZ2V4JykudmFsdWU7CiAgICAgICAgICAgICAgICBpZiAociA9PSAnJykgewogICAgICAgICAgICAgICAgICAgIC8vIElmIHRoZSB1c2VyIGNsZWFyZWQgdGhlIGZpZWxkLCB0aGV5IG1heSBiZSBkb25lIHR5cGluZywgc28KICAgICAgICAgICAgICAgICAgICAvLyB1cGRhdGUgbW9yZSBxdWlja2x5LgogICAgICAgICAgICAgICAgICAgIHRoaXMuYXN5bmMoKCkgPT4gewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLnJlZ2V4ID0gcjsKICAgICAgICAgICAgICAgICAgICB9LCAzMCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBkZWJvdW5jZWQocik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIGdldCBfcmVnZXgoKSB7CiAgICAgICAgICAgIHZhciByZWdleFN0cmluZyA9IHRoaXMucmVnZXg7CiAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IFJlZ0V4cChyZWdleFN0cmluZyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9zZXRJc29sYXRvckljb24oKSB7CiAgICAgICAgICAgIHZhciBzZWxlY3Rpb25NYXAgPSB0aGlzLnNlbGVjdGlvblN0YXRlOwogICAgICAgICAgICB2YXIgbnVtQ2hlY2tlZCA9IGxvZGFzaC5maWx0ZXIobG9kYXNoLnZhbHVlcyhzZWxlY3Rpb25NYXApKS5sZW5ndGg7CiAgICAgICAgICAgIHZhciBidXR0b25zID0gQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwodGhpcy5yb290LnF1ZXJ5U2VsZWN0b3JBbGwoJy5pc29sYXRvcicpKTsKICAgICAgICAgICAgYnV0dG9ucy5mb3JFYWNoKGZ1bmN0aW9uIChiKSB7CiAgICAgICAgICAgICAgICBpZiAobnVtQ2hlY2tlZCA9PT0gMSAmJiBzZWxlY3Rpb25NYXBbYi5uYW1lXSkgewogICAgICAgICAgICAgICAgICAgIGIuaWNvbiA9ICdyYWRpby1idXR0b24tY2hlY2tlZCc7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBiLmljb24gPSAncmFkaW8tYnV0dG9uLXVuY2hlY2tlZCc7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBjb21wdXRlTmFtZXNNYXRjaGluZ1JlZ2V4KF9fLCBfX18pIHsKICAgICAgICAgICAgY29uc3QgcmVnZXggPSB0aGlzLl9yZWdleDsKICAgICAgICAgICAgcmV0dXJuIHJlZ2V4ID8gdGhpcy5uYW1lcy5maWx0ZXIoKG4pID0+IHJlZ2V4LnRlc3QobikpIDogdGhpcy5uYW1lczsKICAgICAgICB9CiAgICAgICAgY29tcHV0ZU91dFNlbGVjdGVkKF9fLCBfX18pIHsKICAgICAgICAgICAgdmFyIHNlbGVjdGlvblN0YXRlID0gdGhpcy5zZWxlY3Rpb25TdGF0ZTsKICAgICAgICAgICAgdmFyIG51bSA9IHRoaXMubWF4TmFtZXNUb0VuYWJsZUJ5RGVmYXVsdDsKICAgICAgICAgICAgdmFyIGFsbEVuYWJsZWQgPSB0aGlzLm5hbWVzTWF0Y2hpbmdSZWdleC5sZW5ndGggPD0gbnVtOwogICAgICAgICAgICByZXR1cm4gdGhpcy5uYW1lc01hdGNoaW5nUmVnZXguZmlsdGVyKChuKSA9PiB7CiAgICAgICAgICAgICAgICByZXR1cm4gc2VsZWN0aW9uU3RhdGVbbl0gPT0gbnVsbCA/IGFsbEVuYWJsZWQgOiBzZWxlY3Rpb25TdGF0ZVtuXTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIHN5bmNocm9uaXplQ29sb3JzKGUpIHsKICAgICAgICAgICAgdGhpcy5fc2V0SXNvbGF0b3JJY29uKCk7CiAgICAgICAgICAgIGNvbnN0IGNoZWNrYm94ZXMgPSB0aGlzLnJvb3QucXVlcnlTZWxlY3RvckFsbCgncGFwZXItY2hlY2tib3gnKTsKICAgICAgICAgICAgY2hlY2tib3hlcy5mb3JFYWNoKChwKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBjb2xvciA9IHRoaXMuY29sb3JpbmcuZ2V0Q29sb3IocC5uYW1lKTsKICAgICAgICAgICAgICAgIHAudXBkYXRlU3R5bGVzKHsKICAgICAgICAgICAgICAgICAgICAnLS1wYXBlci1jaGVja2JveC1jaGVja2VkLWNvbG9yJzogY29sb3IsCiAgICAgICAgICAgICAgICAgICAgJy0tcGFwZXItY2hlY2tib3gtY2hlY2tlZC1pbmstY29sb3InOiBjb2xvciwKICAgICAgICAgICAgICAgICAgICAnLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtY29sb3InOiBjb2xvciwKICAgICAgICAgICAgICAgICAgICAnLS1wYXBlci1jaGVja2JveC11bmNoZWNrZWQtaW5rLWNvbG9yJzogY29sb3IsCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGNvbnN0IGJ1dHRvbnMgPSB0aGlzLnJvb3QucXVlcnlTZWxlY3RvckFsbCgnLmlzb2xhdG9yJyk7CiAgICAgICAgICAgIGJ1dHRvbnMuZm9yRWFjaCgocCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgY29sb3IgPSB0aGlzLmNvbG9yaW5nLmdldENvbG9yKHAubmFtZSk7CiAgICAgICAgICAgICAgICBwLnN0eWxlWydjb2xvciddID0gY29sb3I7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBUaGUgdXBkYXRlU3R5bGVzIGNhbGwgZmFpbHMgc2lsZW50bHkgaWYgdGhlIGJyb3dzZXIgZG9lc24ndCBoYXZlIGZvY3VzLAogICAgICAgICAgICAvLyBlLmcuIGlmIFRlbnNvckJvYXJkIHdhcyBvcGVuZWQgaW50byBhIG5ldyB0YWIgdGhhdCBpc24ndCB2aXNpYmxlLgogICAgICAgICAgICAvLyBTbyB3ZSB3YWl0IGZvciByZXF1ZXN0QW5pbWF0aW9uRnJhbWUuCiAgICAgICAgICAgIHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy51cGRhdGVTdHlsZXMoKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9pc29sYXRlTmFtZShlKSB7CiAgICAgICAgICAgIC8vIElmIHVzZXIgY2xpY2tzIG9uIHRoZSBsYWJlbCBmb3Igb25lIG5hbWUsIGVuYWJsZSBpdCBhbmQgZGlzYWJsZSBhbGwgb3RoZXIKICAgICAgICAgICAgLy8gbmFtZXMuCiAgICAgICAgICAgIHZhciBuYW1lID0gZS50YXJnZXQubmFtZTsKICAgICAgICAgICAgdmFyIHNlbGVjdGlvblN0YXRlID0ge307CiAgICAgICAgICAgIHRoaXMubmFtZXMuZm9yRWFjaChmdW5jdGlvbiAobikgewogICAgICAgICAgICAgICAgc2VsZWN0aW9uU3RhdGVbbl0gPSBuID09IG5hbWU7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLnNlbGVjdGlvblN0YXRlID0gc2VsZWN0aW9uU3RhdGU7CiAgICAgICAgfQogICAgICAgIF9jaGVja2JveENoYW5nZShlKSB7CiAgICAgICAgICAgIHZhciB0YXJnZXQgPSBlLnRhcmdldDsKICAgICAgICAgICAgY29uc3QgbmV3U2VsZWN0aW9uU3RhdGUgPSBsb2Rhc2guY2xvbmUodGhpcy5zZWxlY3Rpb25TdGF0ZSk7CiAgICAgICAgICAgIG5ld1NlbGVjdGlvblN0YXRlW3RhcmdldC5uYW1lXSA9IHRhcmdldC5jaGVja2VkOwogICAgICAgICAgICAvLyBuLmIuIG5vdGlmeVBhdGggd29uJ3Qgd29yayBiZWNhdXNlIG5hbWVzIG1heSBoYXZlIHBlcmlvZHMuCiAgICAgICAgICAgIHRoaXMuc2VsZWN0aW9uU3RhdGUgPSBuZXdTZWxlY3Rpb25TdGF0ZTsKICAgICAgICB9CiAgICAgICAgX2lzQ2hlY2tlZChpdGVtLCBvdXRTZWxlY3RlZENoYW5nZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5vdXRTZWxlY3RlZC5pbmRleE9mKGl0ZW0pICE9IC0xOwogICAgICAgIH0KICAgICAgICB0b2dnbGVBbGwoKSB7CiAgICAgICAgICAgIC8vIElmIGFueSBhcmUgdG9nZ2xlZCBvbiwgd2UgdHVybiBldmVyeXRoaW5nIG9mZi4gT3IsIGlmIG5vbmUgYXJlIHRvZ2dsZWQKICAgICAgICAgICAgLy8gb24sIHdlIHR1cm4gZXZlcnl0aGluZyBvbi4KICAgICAgICAgICAgY29uc3QgYW55VG9nZ2xlZE9uID0gdGhpcy5uYW1lc01hdGNoaW5nUmVnZXguc29tZSgobmFtZSkgPT4gdGhpcy5vdXRTZWxlY3RlZC5pbmNsdWRlcyhuYW1lKSk7CiAgICAgICAgICAgIGNvbnN0IG5ld1NlbGVjdGlvblN0YXRlID0ge307CiAgICAgICAgICAgIHRoaXMubmFtZXMuZm9yRWFjaCgobikgPT4gewogICAgICAgICAgICAgICAgbmV3U2VsZWN0aW9uU3RhdGVbbl0gPSAhYW55VG9nZ2xlZE9uOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5zZWxlY3Rpb25TdGF0ZSA9IG5ld1NlbGVjdGlvblN0YXRlOwogICAgICAgIH0KICAgIH07CiAgICBUZk11bHRpQ2hlY2tib3gudGVtcGxhdGUgPSBodG1sIGAKICAgIDxzdHlsZSBpbmNsdWRlPSJzY3JvbGxiYXItc3R5bGUiPjwvc3R5bGU+CiAgICA8c3R5bGUgaW5jbHVkZT0icnVuLWNvbG9yLXN0eWxlIj48L3N0eWxlPgoKICAgIDxwYXBlci1pbnB1dAogICAgICBpZD0ibmFtZXMtcmVnZXgiCiAgICAgIG5vLWxhYmVsLWZsb2F0PSIiCiAgICAgIGxhYmVsPSJXcml0ZSBhIHJlZ2V4IHRvIGZpbHRlciBydW5zIgogICAgICB2YWx1ZT0iW1tyZWdleF1dIgogICAgICBvbi1iaW5kLXZhbHVlLWNoYW5nZWQ9Il9kZWJvdW5jZWRSZWdleENoYW5nZSIKICAgID48L3BhcGVyLWlucHV0PgogICAgPGRpdiBpZD0ib3V0ZXItY29udGFpbmVyIiBjbGFzcz0ic2Nyb2xsYmFyIj4KICAgICAgPHRlbXBsYXRlCiAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgaXRlbXM9IltbbmFtZXNNYXRjaGluZ1JlZ2V4XV0iCiAgICAgICAgb24tZG9tLWNoYW5nZT0ic3luY2hyb25pemVDb2xvcnMiCiAgICAgID4KICAgICAgICA8ZGl2IGNsYXNzPSJuYW1lLXJvdyI+CiAgICAgICAgICA8ZGl2CiAgICAgICAgICAgIGNsYXNzPSJpY29uLWNvbnRhaW5lciBjaGVja2JveC1jb250YWluZXIgdmVydGljYWwtYWxpZ24tY29udGFpbmVyIgogICAgICAgICAgPgogICAgICAgICAgICA8cGFwZXItY2hlY2tib3gKICAgICAgICAgICAgICBjbGFzcz0iY2hlY2tib3ggdmVydGljYWwtYWxpZ24tY2VudGVyIgogICAgICAgICAgICAgIGlkJD0iY2hlY2tib3gtW1tpdGVtXV0iCiAgICAgICAgICAgICAgbmFtZT0iW1tpdGVtXV0iCiAgICAgICAgICAgICAgY2hlY2tlZCQ9IltbX2lzQ2hlY2tlZChpdGVtLCBzZWxlY3Rpb25TdGF0ZS4qKV1dIgogICAgICAgICAgICAgIG9uLWNoYW5nZT0iX2NoZWNrYm94Q2hhbmdlIgogICAgICAgICAgICA+PC9wYXBlci1jaGVja2JveD4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPGRpdgogICAgICAgICAgICBjbGFzcz0iaWNvbi1jb250YWluZXIgaXNvbGF0b3ItY29udGFpbmVyIHZlcnRpY2FsLWFsaWduLWNvbnRhaW5lciIKICAgICAgICAgID4KICAgICAgICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgICAgICAgaWNvbj0icmFkaW8tYnV0dG9uLXVuY2hlY2tlZCIKICAgICAgICAgICAgICBjbGFzcz0iaXNvbGF0b3IgdmVydGljYWwtYWxpZ24tY2VudGVyIgogICAgICAgICAgICAgIG9uLXRhcD0iX2lzb2xhdGVOYW1lIgogICAgICAgICAgICAgIG5hbWU9IltbaXRlbV1dIgogICAgICAgICAgICA+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPGRpdiBjbGFzcz0iaXRlbS1sYWJlbC1jb250YWluZXIiPgogICAgICAgICAgICA8c3Bhbj5bW2l0ZW1dXTwvc3Bhbj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIHBhcGVyLWlucHV0IHsKICAgICAgICAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1mb2N1cy1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgICAgLS1wYXBlci1pbnB1dC1jb250YWluZXItaW5wdXQ6IHsKICAgICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICB9CiAgICAgICAgLS1wYXBlci1pbnB1dC1jb250YWluZXItbGFiZWw6IHsKICAgICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICB9CiAgICAgIH0KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgfQogICAgICAjb3V0ZXItY29udGFpbmVyIHsKICAgICAgICBjb250YWluOiBjb250ZW50OwogICAgICAgIGZsZXgtZ3JvdzogMTsKICAgICAgICBmbGV4LXNocmluazogMTsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICAgIHdvcmQtd3JhcDogYnJlYWstd29yZDsKICAgICAgfQogICAgICAubmFtZS1yb3cgewogICAgICAgIGNvbnRhaW46IGNvbnRlbnQ7CiAgICAgICAgcGFkZGluZy10b3A6IDVweDsKICAgICAgICBwYWRkaW5nLWJvdHRvbTogNXB4OwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgICBmb250LXNpemU6IDEzcHg7CiAgICAgICAgd29yZC1icmVhazogYnJlYWstYWxsOyAvKiBtYWtlcyB3cmFwcGluZyBvZiBoeXBlcnBhcmFtIHN0cmluZ3MgYmV0dGVyICovCiAgICAgIH0KICAgICAgLmljb24tY29udGFpbmVyIHsKICAgICAgICBmbGV4LWdyb3c6IDA7CiAgICAgICAgZmxleC1zaHJpbms6IDA7CiAgICAgICAgcGFkZGluZy1sZWZ0OiAycHg7CiAgICAgIH0KICAgICAgLmNoZWNrYm94IHsKICAgICAgICBwYWRkaW5nLWxlZnQ6IDJweDsKICAgICAgICB3aWR0aDogMThweDsKICAgICAgICBoZWlnaHQ6IDE4cHg7CiAgICAgIH0KICAgICAgLmlzb2xhdG9yIHsKICAgICAgICB3aWR0aDogMThweDsKICAgICAgICBoZWlnaHQ6IDE4cHg7CiAgICAgICAgcGFkZGluZzogMHB4OwogICAgICB9CiAgICAgIC5pc29sYXRvci1jb250YWluZXIgewogICAgICAgIHBhZGRpbmctbGVmdDogNnB4OwogICAgICAgIHBhZGRpbmctcmlnaHQ6IDNweDsKICAgICAgfQogICAgICAuY2hlY2tib3gtY29udGFpbmVyIHsKICAgICAgICBwYWRkaW5nLWxlZnQ6IDJweDsKICAgICAgfQogICAgICAuaXRlbS1sYWJlbC1jb250YWluZXIgewogICAgICAgIHBhZGRpbmctbGVmdDogNXB4OwogICAgICAgIGZsZXgtZ3JvdzogMTsKICAgICAgICBmbGV4LXNocmluazogMTsKICAgICAgICB3aWR0aDogMHB4OyAvKiBoYWNrIHRvIGdldCB0aGUgZmxleC1ncm93IHRvIHdvcmsgcHJvcGVybHkgKi8KICAgICAgfQogICAgICAudG9vbHRpcC12YWx1ZS1jb250YWluZXIgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgZmxleC1ncm93OiAwOwogICAgICAgIGZsZXgtc2hyaW5rOiAwOwogICAgICAgIHRleHQtYWxpZ246IHJpZ2h0OwogICAgICAgIHBhZGRpbmctbGVmdDogMnB4OwogICAgICB9CiAgICAgIC52ZXJ0aWNhbC1hbGlnbi1jb250YWluZXIgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7CiAgICAgIH0KICAgICAgLnZlcnRpY2FsLWFsaWduLWNvbnRhaW5lciAudmVydGljYWwtYWxpZ24tY2VudGVyIHsKICAgICAgICBhbGlnbi1zZWxmOiBjZW50ZXI7CiAgICAgIH0KICAgICAgLnZlcnRpY2FsLWFsaWduLWNvbnRhaW5lciAudmVydGljYWwtYWxpZ24tdG9wIHsKICAgICAgICBhbGlnbi1zZWxmOiBzdGFydDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgIm5hbWVzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgImNvbG9yaW5nIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk11bHRpQ2hlY2tib3gucHJvdG90eXBlLCAicmVnZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgY29tcHV0ZWQ6ICdjb21wdXRlTmFtZXNNYXRjaGluZ1JlZ2V4KG5hbWVzLiosIF9yZWdleCknLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZk11bHRpQ2hlY2tib3gucHJvdG90eXBlLCAibmFtZXNNYXRjaGluZ1JlZ2V4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgLy8gSWYgYSBuYW1lIGlzIGV4cGxpY2l0bHkgZW5hYmxlZCBieSB1c2VyIGdlc3R1cmUsIFRydWUsIGlmIGV4cGxpY2l0bHkKICAgICAgICAgICAgLy8gZGlzYWJsZWQsIEZhbHNlLiBJZiB1bmRlZmluZWQsIGRlZmF1bHQgdmFsdWUgKGVuYWJsZSBmb3IgZmlyc3QgawogICAgICAgICAgICAvLyBuYW1lcywgZGlzYWJsZSBhZnRlcikuCiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgInNlbGVjdGlvblN0YXRlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgY29tcHV0ZWQ6ICdjb21wdXRlT3V0U2VsZWN0ZWQobmFtZXNNYXRjaGluZ1JlZ2V4LiosIHNlbGVjdGlvblN0YXRlLiopJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgIm91dFNlbGVjdGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgLy8gV2hlbiBUQiBmaXJzdCBsb2FkcywgaWYgaXQgaGFzIGsgb3IgZmV3ZXIgbmFtZXMsIHRoZXkgYXJlIGFsbCBlbmFibGVkCiAgICAgICAgICAgIC8vIGJ5IGRlZmF1bHQuIElmIHRoZXJlIGFyZSBtb3JlLCB0aGVuIHRoZXkgYXJlIGFsbCBkaXNhYmxlZC4KICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgIm1heE5hbWVzVG9FbmFibGVCeURlZmF1bHQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk11bHRpQ2hlY2tib3gucHJvdG90eXBlLCAiX2RlYm91bmNlZFJlZ2V4Q2hhbmdlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdyZWdleCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVnRXhwKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZNdWx0aUNoZWNrYm94LnByb3RvdHlwZSwgIl9yZWdleCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnc2VsZWN0aW9uU3RhdGUnLCAnbmFtZXMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmTXVsdGlDaGVja2JveC5wcm90b3R5cGUsICJfc2V0SXNvbGF0b3JJY29uIiwgbnVsbCk7CiAgICBUZk11bHRpQ2hlY2tib3ggPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1tdWx0aS1jaGVja2JveCcpCiAgICBdLCBUZk11bHRpQ2hlY2tib3gpOwoKICAgIC8qIENvcHlyaWdodCAyMDE5IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gdGYtd2JyLXN0cmluZyBzYWZlbHkgcmVuZGVycyBhIHN0cmluZywgd2l0aCA8d2JyPiB3b3JkIGJyZWFrIGVsZW1lbnRzIGluc2VydGVkCiAgICAvLyBhZnRlciBzdWJzdHJpbmdzIHRoYXQgbWF0Y2ggYSByZWd1bGFyIGV4cHJlc3Npb24gcGF0dGVybi4KICAgIGxldCBUZldiclN0cmluZyA9IGNsYXNzIFRmV2JyU3RyaW5nIGV4dGVuZHMgUG9seW1lckVsZW1lbnQgewogICAgICAgIGdldCBfcGFydHMoKSB7CiAgICAgICAgICAgIHZhciB2YWx1ZSA9IHRoaXMudmFsdWU7CiAgICAgICAgICAgIHZhciBkZWxpbWl0ZXJQYXR0ZXJuID0gdGhpcy5kZWxpbWl0ZXJQYXR0ZXJuOwogICAgICAgICAgICBjb25zdCByZXN1bHQgPSBbXTsKICAgICAgICAgICAgd2hpbGUgKHRydWUpIHsKICAgICAgICAgICAgICAgIGNvbnN0IGRlbGltaXRlclJlZ0V4cCA9IG5ldyBSZWdFeHAoZGVsaW1pdGVyUGF0dGVybiwgJ2cnKTsKICAgICAgICAgICAgICAgIGRlbGltaXRlclJlZ0V4cC50ZXN0KHZhbHVlKTsKICAgICAgICAgICAgICAgIGlmIChkZWxpbWl0ZXJSZWdFeHAubGFzdEluZGV4ID09PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmVzdWx0LnB1c2godmFsdWUpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgcmVzdWx0LnB1c2godmFsdWUuc2xpY2UoMCwgZGVsaW1pdGVyUmVnRXhwLmxhc3RJbmRleCkpOwogICAgICAgICAgICAgICAgICAgIHZhbHVlID0gdmFsdWUuc2xpY2UoZGVsaW1pdGVyUmVnRXhwLmxhc3RJbmRleCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICB9CiAgICB9OwogICAgVGZXYnJTdHJpbmcudGVtcGxhdGUgPSBodG1sIGAKICAgIDwhLS0KICAgICAgVGhpcyB1Z2x5IGZvcm1hdHRpbmcgaXMgcmVxdWlyZWQgdG8gcHJldmVudCBzcGFjZXMgZnJvbSBzbGlwcGluZwogICAgICBpbnRvIHRoZSBIVE1MLgogICAgLS0+CiAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19wYXJ0c11dIiBhcz0icGFydCIKICAgICAgPltbcGFydF1dPHdicgogICAgLz48L3RlbXBsYXRlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmV2JyU3RyaW5nLnByb3RvdHlwZSwgInZhbHVlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZXYnJTdHJpbmcucHJvdG90eXBlLCAiZGVsaW1pdGVyUGF0dGVybiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgndmFsdWUnLCAnZGVsaW1pdGVyUGF0dGVybicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZldiclN0cmluZy5wcm90b3R5cGUsICJfcGFydHMiLCBudWxsKTsKICAgIFRmV2JyU3RyaW5nID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtd2JyLXN0cmluZycpCiAgICBdLCBUZldiclN0cmluZyk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZSdW5zU2VsZWN0b3IgPSBjbGFzcyBUZlJ1bnNTZWxlY3RvciBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLnJ1blNlbGVjdGlvblN0YXRlID0gZ2V0T2JqZWN0SW5pdGlhbGl6ZXIoJ3J1blNlbGVjdGlvblN0YXRlJywgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiB7fSwKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLnJlZ2V4SW5wdXQgPSBnZXRTdHJpbmdJbml0aWFsaXplcigncmVnZXhJbnB1dCcsIHsKICAgICAgICAgICAgICAgIGRlZmF1bHRWYWx1ZTogJycsCiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fZGF0YUxvY2F0aW9uQ2xpcExlbmd0aCA9IDI1MDsKICAgICAgICAgICAgdGhpcy5fZGF0YUxvY2F0aW9uRGVsaW1pdGVyUGF0dGVybiA9ICdbLz1fLC1dJzsKICAgICAgICAgICAgdGhpcy5jb2xvcmluZyA9IHsKICAgICAgICAgICAgICAgIGdldENvbG9yOiBydW5zQ29sb3JTY2FsZSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5fc3RvcmVSdW5TZWxlY3Rpb25TdGF0ZSA9IGdldE9iamVjdE9ic2VydmVyKCdydW5TZWxlY3Rpb25TdGF0ZScsIHsKICAgICAgICAgICAgICAgIGRlZmF1bHRWYWx1ZToge30sCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9yZWdleE9ic2VydmVyID0gZ2V0U3RyaW5nT2JzZXJ2ZXIoJ3JlZ2V4SW5wdXQnLCB7CiAgICAgICAgICAgICAgICBkZWZhdWx0VmFsdWU6ICcnLAogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuX3J1blN0b3JlTGlzdGVuZXIgPSBydW5zU3RvcmUuYWRkTGlzdGVuZXIoKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ3J1bnMnLCBydW5zU3RvcmUuZ2V0UnVucygpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuc2V0KCdydW5zJywgcnVuc1N0b3JlLmdldFJ1bnMoKSk7CiAgICAgICAgICAgIHRoaXMuX2VudlN0b3JlTGlzdGVuZXIgPSBlbnZpcm9ubWVudFN0b3JlLmFkZExpc3RlbmVyKCgpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdkYXRhTG9jYXRpb24nLCBlbnZpcm9ubWVudFN0b3JlLmdldERhdGFMb2NhdGlvbigpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuc2V0KCdkYXRhTG9jYXRpb24nLCBlbnZpcm9ubWVudFN0b3JlLmdldERhdGFMb2NhdGlvbigpKTsKICAgICAgICB9CiAgICAgICAgZGV0YWNoZWQoKSB7CiAgICAgICAgICAgIHJ1bnNTdG9yZS5yZW1vdmVMaXN0ZW5lckJ5S2V5KHRoaXMuX3J1blN0b3JlTGlzdGVuZXIpOwogICAgICAgICAgICBlbnZpcm9ubWVudFN0b3JlLnJlbW92ZUxpc3RlbmVyQnlLZXkodGhpcy5fZW52U3RvcmVMaXN0ZW5lcik7CiAgICAgICAgfQogICAgICAgIF90b2dnbGVBbGwoKSB7CiAgICAgICAgICAgIHRoaXMuJC5tdWx0aUNoZWNrYm94LnRvZ2dsZUFsbCgpOwogICAgICAgIH0KICAgICAgICBnZXQgX2NsaXBwZWREYXRhTG9jYXRpb24oKSB7CiAgICAgICAgICAgIHZhciBkYXRhTG9jYXRpb24gPSB0aGlzLmRhdGFMb2NhdGlvbjsKICAgICAgICAgICAgdmFyIGRhdGFMb2NhdGlvbkNsaXBMZW5ndGggPSB0aGlzLl9kYXRhTG9jYXRpb25DbGlwTGVuZ3RoOwogICAgICAgICAgICBpZiAoZGF0YUxvY2F0aW9uID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSBkYXRhTG9jYXRpb24gaGFzIG5vdCBiZWVuIHNldCB5ZXQuCiAgICAgICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChkYXRhTG9jYXRpb24ubGVuZ3RoID4gZGF0YUxvY2F0aW9uQ2xpcExlbmd0aCkgewogICAgICAgICAgICAgICAgLy8gQ2xpcCB0aGUgZGF0YUxvY2F0aW9uIHRvIGF2b2lkIGJsb2NraW5nIHRoZSBydW5zIHNlbGVjdG9yLiBMZXQgdGhlCiAgICAgICAgICAgICAgICAvLyB1c2VyIHZpZXcgYSBtb3JlIGZ1bGwgdmVyc2lvbiBvZiB0aGUgZGF0YUxvY2F0aW9uLgogICAgICAgICAgICAgICAgcmV0dXJuIGRhdGFMb2NhdGlvbi5zdWJzdHJpbmcoMCwgZGF0YUxvY2F0aW9uQ2xpcExlbmd0aCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZGF0YUxvY2F0aW9uOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9vcGVuRGF0YUxvY2F0aW9uRGlhbG9nKGV2ZW50KSB7CiAgICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICAgIHRoaXMuJCQoJyNkYXRhLWxvY2F0aW9uLWRpYWxvZycpLm9wZW4oKTsKICAgICAgICB9CiAgICAgICAgX3Nob3VsZFNob3dFeHBhbmREYXRhTG9jYXRpb25CdXR0b24oZGF0YUxvY2F0aW9uLCBfZGF0YUxvY2F0aW9uQ2xpcExlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gZGF0YUxvY2F0aW9uICYmIGRhdGFMb2NhdGlvbi5sZW5ndGggPiBfZGF0YUxvY2F0aW9uQ2xpcExlbmd0aDsKICAgICAgICB9CiAgICB9OwogICAgVGZSdW5zU2VsZWN0b3IudGVtcGxhdGUgPSBodG1sIGAKICAgIDxwYXBlci1kaWFsb2cgd2l0aC1iYWNrZHJvcD0iIiBpZD0iZGF0YS1sb2NhdGlvbi1kaWFsb2ciPgogICAgICA8aDI+RGF0YSBMb2NhdGlvbjwvaDI+CiAgICAgIDx0Zi13YnItc3RyaW5nCiAgICAgICAgdmFsdWU9IltbZGF0YUxvY2F0aW9uXV0iCiAgICAgICAgZGVsaW1pdGVyLXBhdHRlcm49IltbX2RhdGFMb2NhdGlvbkRlbGltaXRlclBhdHRlcm5dXSIKICAgICAgPgogICAgICA8L3RmLXdici1zdHJpbmcKICAgID48L3BhcGVyLWRpYWxvZz4KICAgIDxkaXYgaWQ9InRvcC10ZXh0Ij4KICAgICAgPGgzIGlkPSJ0b29sdGlwLWhlbHAiIGNsYXNzPSJ0b29sdGlwLWNvbnRhaW5lciI+UnVuczwvaDM+CiAgICA8L2Rpdj4KICAgIDx0Zi1tdWx0aS1jaGVja2JveAogICAgICBpZD0ibXVsdGlDaGVja2JveCIKICAgICAgbmFtZXM9IltbcnVuc11dIgogICAgICBzZWxlY3Rpb24tc3RhdGU9Int7cnVuU2VsZWN0aW9uU3RhdGV9fSIKICAgICAgb3V0LXNlbGVjdGVkPSJ7e3NlbGVjdGVkUnVuc319IgogICAgICByZWdleD0ie3tyZWdleElucHV0fX0iCiAgICAgIGNvbG9yaW5nPSJbW2NvbG9yaW5nXV0iCiAgICA+PC90Zi1tdWx0aS1jaGVja2JveD4KICAgIDxwYXBlci1idXR0b24gY2xhc3M9IngtYnV0dG9uIiBpZD0idG9nZ2xlLWFsbCIgb24tdGFwPSJfdG9nZ2xlQWxsIj4KICAgICAgVG9nZ2xlIEFsbCBSdW5zCiAgICA8L3BhcGVyLWJ1dHRvbj4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tkYXRhTG9jYXRpb25dXSI+CiAgICAgIDxkaXYgaWQ9ImRhdGEtbG9jYXRpb24iPgogICAgICAgIDx0Zi13YnItc3RyaW5nCiAgICAgICAgICB2YWx1ZT0iW1tfY2xpcHBlZERhdGFMb2NhdGlvbl1dIgogICAgICAgICAgZGVsaW1pdGVyLXBhdHRlcm49IltbX2RhdGFMb2NhdGlvbkRlbGltaXRlclBhdHRlcm5dXSIKICAgICAgICA+PC90Zi13YnItc3RyaW5nCiAgICAgICAgPjwhLS0KICAgICAgICAgIFdlIHVzZSBIVE1MIGNvbW1lbnRzIHRvIHJlbW92ZSBzcGFjZXMgYmVmb3JlIHRoZSBlbGxpcHNpcy4KICAgICAgICAtLT48dGVtcGxhdGUKICAgICAgICAgIGlzPSJkb20taWYiCiAgICAgICAgICBpZj0iW1tfc2hvdWxkU2hvd0V4cGFuZERhdGFMb2NhdGlvbkJ1dHRvbihkYXRhTG9jYXRpb24sIF9kYXRhTG9jYXRpb25DbGlwTGVuZ3RoKV1dIgogICAgICAgICAgPjwhLS0KICAgICAgICAgIC0tPjxhIGhyZWY9IiIgb24tY2xpY2s9Il9vcGVuRGF0YUxvY2F0aW9uRGlhbG9nIj7igKY8L2E+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9kaXY+CiAgICA8L3RlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgcGFkZGluZy1ib3R0b206IDEwcHg7CiAgICAgIH0KICAgICAgI3RvcC10ZXh0IHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBmbGV4LWdyb3c6IDA7CiAgICAgICAgZmxleC1zaHJpbms6IDA7CiAgICAgICAgcGFkZGluZy1yaWdodDogMTZweDsKICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1ncmV5LTgwMCk7CiAgICAgIH0KICAgICAgdGYtbXVsdGktY2hlY2tib3ggewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICAgIGZsZXgtc2hyaW5rOiAxOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KICAgICAgLngtYnV0dG9uIHsKICAgICAgICBmb250LXNpemU6IDEzcHg7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tdGItdWktbGlnaHQtYWNjZW50KTsKICAgICAgICBjb2xvcjogdmFyKC0tdGItdWktZGFyay1hY2NlbnQpOwogICAgICB9CiAgICAgICN0b29sdGlwLWhlbHAgewogICAgICAgIGNvbG9yOiB2YXIoLS1wYXBlci1ncmV5LTgwMCk7CiAgICAgICAgbWFyZ2luOiAwOwogICAgICAgIGZvbnQtd2VpZ2h0OiBub3JtYWw7CiAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIG1hcmdpbi1ib3R0b206IDVweDsKICAgICAgfQogICAgICBwYXBlci1idXR0b24gewogICAgICAgIG1hcmdpbi1sZWZ0OiAwOwogICAgICB9CiAgICAgICNkYXRhLWxvY2F0aW9uIHsKICAgICAgICBjb2xvcjogdmFyKC0tdGItdWktZGFyay1hY2NlbnQpOwogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBtYXJnaW46IDVweCAwIDAgMDsKICAgICAgICBtYXgtd2lkdGg6IDI4OHB4OwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfc3RvcmVSdW5TZWxlY3Rpb25TdGF0ZScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZlJ1bnNTZWxlY3Rvci5wcm90b3R5cGUsICJydW5TZWxlY3Rpb25TdGF0ZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfcmVnZXhPYnNlcnZlcicsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZlJ1bnNTZWxlY3Rvci5wcm90b3R5cGUsICJyZWdleElucHV0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZSdW5zU2VsZWN0b3IucHJvdG90eXBlLCAic2VsZWN0ZWRSdW5zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmUnVuc1NlbGVjdG9yLnByb3RvdHlwZSwgInJ1bnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmUnVuc1NlbGVjdG9yLnByb3RvdHlwZSwgImRhdGFMb2NhdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmUnVuc1NlbGVjdG9yLnByb3RvdHlwZSwgIl9kYXRhTG9jYXRpb25DbGlwTGVuZ3RoIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZSdW5zU2VsZWN0b3IucHJvdG90eXBlLCAiX2RhdGFMb2NhdGlvbkRlbGltaXRlclBhdHRlcm4iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZlJ1bnNTZWxlY3Rvci5wcm90b3R5cGUsICJjb2xvcmluZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnZGF0YUxvY2F0aW9uJywgJ19kYXRhTG9jYXRpb25DbGlwTGVuZ3RoJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZlJ1bnNTZWxlY3Rvci5wcm90b3R5cGUsICJfY2xpcHBlZERhdGFMb2NhdGlvbiIsIG51bGwpOwogICAgVGZSdW5zU2VsZWN0b3IgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ydW5zLXNlbGVjdG9yJykKICAgIF0sIFRmUnVuc1NlbGVjdG9yKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNyBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogQSBjbGFzcyB0aGF0IGFsbG93cyBtYXJraW5nIHByb21pc2VzIGFzIGNhbmNlbGxlZC4KICAgICAqCiAgICAgKiBUaGlzIGNhbiBiZSB1c2VmdWwgdG8sIGUuZy4sIHByZXZlbnQgb2xkIG5ldHdvcmsgcmVxdWVzdHMgZnJvbQogICAgICogc3RvbXBpbmcgbmV3IG9uZXMgYW5kIHdyaXRpbmcgYmFkIGRhdGEuCiAgICAgKgogICAgICogVXNhZ2U6CiAgICAgKgogICAgICogICAgIGNvbnN0IGNhbmNlbGxlciA9IG5ldyBDYW5jZWxsZXIoKTsKICAgICAqICAgICBsZXQgbXlQcm9taXNlOiBQcm9taXNlPEZvbz4gPSBnZXRQcm9taXNlKCk7CiAgICAgKiAgICAgbXlQcm9taXNlLnRoZW4oY2FuY2VsbGVyLmNhbmNlbGxhYmxlKCh7dmFsdWUsIGNhbmNlbGxlZH0gPT4gewogICAgICogICAgICAgaWYgKGNhbmNlbGxlZCkgewogICAgICogICAgICAgICBjb25zb2xlLndhcm4oIkRvbid0IG1ha2UgcHJvbWlzZXMgeW91IGNhbid0IGtlZXAgPjoteyIpOwogICAgICogICAgICAgfQogICAgICogICAgICAgY29uc29sZS5sb2coIkVuam95IHlvdXIgdmFsdWU6IiwgdmFsdWUpOwogICAgICogICAgIH0pKTsKICAgICAqCiAgICAgKiAgICAgLy8gSWYgYG15UHJvbWlzZWAgaXMgcmVzb2x2ZWQgbm93LCB0aGVuIGBjYW5jZWxsZWRgIHdpbGwgYmUgYGZhbHNlYC4KICAgICAqICAgICBjYW5jZWxsZXIuY2FuY2VsQWxsKCk7CiAgICAgKiAgICAgLy8gSWYgYG15UHJvbWlzZWAgaXMgcmVzb2x2ZWQgbm93LCB0aGVuIGBjYW5jZWxsZWRgIHdpbGwgYmUgYHRydWVgLgogICAgICovCiAgICBjbGFzcyBDYW5jZWxsZXIgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogSG93IG1hbnkgdGltZXMgaGFzIGBjYW5jZWxBbGxgIGJlZW4gY2FsbGVkPwogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5jYW5jZWxsYXRpb25Db3VudCA9IDA7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZSBhIGNhbmNlbGxhYmxlIHRhc2suIFRoaXMgcmV0dXJucyBhIG5ldyBmdW5jdGlvbiB0aGF0LCB3aGVuCiAgICAgICAgICogaW52b2tlZCwgd2lsbCBwYXNzIGl0cyBhcmd1bWVudCB0byB0aGUgcHJvdmlkZWQgZnVuY3Rpb24gYXMgd2VsbCBhcwogICAgICAgICAqIGEgYGNhbmNlbGxlZGAgYXJndW1lbnQuIFRoaXMgYXJndW1lbnQgd2lsbCBiZSBgZmFsc2VgIHVubGVzcyBhbmQKICAgICAgICAgKiB1bnRpbCBgY2FuY2VsQWxsYCBpcyBpbnZva2VkIGFmdGVyIHRoZSBjcmVhdGlvbiBvZiB0aGlzIHRhc2suCiAgICAgICAgICovCiAgICAgICAgY2FuY2VsbGFibGUoZikgewogICAgICAgICAgICBjb25zdCBvcmlnaW5hbENhbmNlbGxhdGlvbkNvdW50ID0gdGhpcy5jYW5jZWxsYXRpb25Db3VudDsKICAgICAgICAgICAgcmV0dXJuICh2YWx1ZSkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgY2FuY2VsbGVkID0gdGhpcy5jYW5jZWxsYXRpb25Db3VudCAhPT0gb3JpZ2luYWxDYW5jZWxsYXRpb25Db3VudDsKICAgICAgICAgICAgICAgIHJldHVybiBmKHsgdmFsdWUsIGNhbmNlbGxlZCB9KTsKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogTWFyayBhbGwgb3V0c3RhbmRpbmcgdGFza3MgYXMgY2FuY2VsbGVkLiBUYXNrcyBub3QgeWV0IGNyZWF0ZWQgd2lsbAogICAgICAgICAqIG5vdCBiZSBhZmZlY3RlZC4KICAgICAgICAgKi8KICAgICAgICBjYW5jZWxBbGwoKSB7CiAgICAgICAgICAgIHRoaXMuY2FuY2VsbGF0aW9uQ291bnQrKzsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIERvZXMgbm90IGFjdHVhbGx5IHNhbml0aXplIGh0bWwuCiAgICAgKgogICAgICogVGhpcyBleHBvcnRlZCBmdW5jdGlvbiBpcyBvdmVycmlkZW4gaW4gdGhlIGludGVybmFsIEdvb2dsZSByZXBvc2l0b3J5IGZvcgogICAgICogY29tcGF0aWJpbGl0eSB3aXRoIHNlY3VyaXR5IGxpYnJhcmllcyB1c2VkIGludGVybmFsbHkgYXQgR29vZ2xlLgogICAgICovCiAgICBmdW5jdGlvbiBzYW5pdGl6ZShodG1sKSB7CiAgICAgICAgcmV0dXJuIGh0bWw7CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTcgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvLyB0Zi1tYXJrZG93bi12aWV3IHJlbmRlcnMgcmF3IEhUTUwgdGhhdCBoYXMgYmVlbiBjb252ZXJ0ZWQgZnJvbQogICAgLy8gTWFya2Rvd24gYnkgc29tZSBvdGhlciBhZ2VudC4gVGhlIEhUTUwgbXVzdCBiZSBzYW5pdGl6ZWQsIGFuZCBtdXN0IGJlCiAgICAvLyBzYWZlIHRvIGluamVjdCBkaXJlY3RseSBpbnRvIHRoZSBET00uCiAgICAvLyBUZW5zb3JCb2FyZCBwbHVnaW5zIGNhbiB1c2UgdGhlIGBtYXJrZG93bl90b19zYWZlX2h0bWxgIGZ1bmN0aW9uIGZyb20KICAgIC8vIHRoZSBgdGVuc29yYm9hcmQucGx1Z2luX3V0aWxgIG1vZHVsZSBvbiB0aGUgYmFja2VuZCB0byBnZW5lcmF0ZSBIVE1MCiAgICAvLyBzdWl0YWJsZSBmb3IgdXNlIHdpdGggdGhpcyBjb21wb25lbnQuCiAgICBsZXQgVGZNYXJrZG93blZpZXcgPSBjbGFzcyBUZk1hcmtkb3duVmlldyBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLmh0bWwgPSAnJzsKICAgICAgICB9CiAgICAgICAgZ2V0IHNhbml0aXplZEh0bWwoKSB7CiAgICAgICAgICAgIHJldHVybiBzYW5pdGl6ZSh0aGlzLmh0bWwpOwogICAgICAgIH0KICAgICAgICBhdHRhY2hlZCgpIHsKICAgICAgICAgICAgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLnNjb3BlU3VidHJlZSh0aGlzLiQubWFya2Rvd24sIC8qc2hvdWxkT2JzZXJ2ZT0qLyB0cnVlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgfTsKICAgIFRmTWFya2Rvd25WaWV3LnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJtYXJrZG93biIgaW5uZXItaC10LW0tbD0iW1tzYW5pdGl6ZWRIdG1sXV0iPjwvZGl2PgogICAgPHN0eWxlPgogICAgICAvKgogICAgICAgKiBSZWR1Y2UgdG9wbW9zdCBhbmQgYm90dG9tbW9zdCBtYXJnaW5zIGZyb20gMTZweCB0byAwLjNlbSAocmVuZGVycwogICAgICAgKiBhdCBhYm91dCA0LjhweCkgdG8ga2VlcCB0aGUgbGF5b3V0IGNvbXBhY3QuIFRoaXMgaW1wcm92ZXMgdGhlCiAgICAgICAqIGFwcGVhcmFuY2Ugd2hlbiB0aGVyZSBpcyBvbmx5IG9uZSBsaW5lIG9mIHRleHQ7IHN0YW5kYXJkIE1hcmtkb3duCiAgICAgICAqIHJlbmRlcmVycyB3aWxsIHN0aWxsIGluY2x1ZGUgYSBcYDxwPlxgIGVsZW1lbnQuCiAgICAgICAqCiAgICAgICAqIEJ5IHRhcmdldGluZyBvbmx5IHRoZSB0b3AtbGV2ZWwsIGV4dHJlbWFsIGVsZW1lbnRzLCB3ZSBwcmVzZXJ2ZSBhbnkKICAgICAgICogYWN0dWFsIHBhcmFncmFwaCBicmVha3MgYW5kIG9ubHkgY2hhbmdlIHRoZSBwYWRkaW5nIGFnYWluc3QgdGhlCiAgICAgICAqIGNvbXBvbmVudCBlZGdlcy4KICAgICAgICovCiAgICAgICNtYXJrZG93biA+IHA6Zmlyc3QtY2hpbGQgewogICAgICAgIG1hcmdpbi10b3A6IDAuM2VtOwogICAgICB9CiAgICAgICNtYXJrZG93biA+IHA6bGFzdC1jaGlsZCB7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMC4zZW07CiAgICAgIH0KCiAgICAgIC8qIFBsZWFzYW50IHN0eWxlcyBmb3IgTWFya2Rvd24gdGFibGVzLiAqLwogICAgICAjbWFya2Rvd24gdGFibGUgewogICAgICAgIGJvcmRlci1jb2xsYXBzZTogY29sbGFwc2U7CiAgICAgIH0KICAgICAgI21hcmtkb3duIHRhYmxlIHRoIHsKICAgICAgICBmb250LXdlaWdodDogNjAwOwogICAgICB9CiAgICAgICNtYXJrZG93biB0YWJsZSB0aCwKICAgICAgI21hcmtkb3duIHRhYmxlIHRkIHsKICAgICAgICBwYWRkaW5nOiA2cHggMTNweDsKICAgICAgICBib3JkZXI6IDFweCBzb2xpZCAjZGZlMmU1OwogICAgICB9CiAgICAgICNtYXJrZG93biB0YWJsZSB0ciB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2ZmZjsKICAgICAgICBib3JkZXItdG9wOiAxcHggc29saWQgI2M2Y2JkMTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk1hcmtkb3duVmlldy5wcm90b3R5cGUsICJodG1sIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdodG1sJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZk1hcmtkb3duVmlldy5wcm90b3R5cGUsICJzYW5pdGl6ZWRIdG1sIiwgbnVsbCk7CiAgICBUZk1hcmtkb3duVmlldyA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLW1hcmtkb3duLXZpZXcnKQogICAgXSwgVGZNYXJrZG93blZpZXcpOwoKICAgIC8qIENvcHlyaWdodCAyMDE3IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBmdW5jdGlvbiBmb3JtYXREYXRlJDEoZGF0ZSkgewogICAgICAgIGlmICghZGF0ZSkgewogICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgfQogICAgICAgIC8vIFR1cm4gdGhpbmdzIGxpa2UgIkdNVC0wNzAwIChQRFQpIiBpbnRvIGp1c3QgIlBEVCIuCiAgICAgICAgcmV0dXJuIGRhdGUudG9TdHJpbmcoKS5yZXBsYWNlKC9HTVQtXGQrIFwoKFteKV0rKVwpLywgJyQxJyk7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgQ1NTIGNvbG9yIHRoYXQgd2lsbCBjb250cmFzdCBhZ2FpbnN0IGJhY2tncm91bmQuCiAgICAgKiBAcGFyYW0gez9zdHJpbmd9IGJhY2tncm91bmQgUkdCIGhleCBjb2xvciBjb2RlLCBlLmcuICNlZWUsICNlZWVlZWUuCiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHBpY2tUZXh0Q29sb3IoYmFja2dyb3VuZCkgewogICAgICAgIGNvbnN0IHJnYiA9IGNvbnZlcnRIZXhUb1JnYihiYWNrZ3JvdW5kKTsKICAgICAgICBpZiAoIXJnYikgewogICAgICAgICAgICByZXR1cm4gJ2luaGVyaXQnOwogICAgICAgIH0KICAgICAgICAvLyBTZWU6IGh0dHA6Ly93d3cudzMub3JnL1RSL0FFUlQjY29sb3ItY29udHJhc3QKICAgICAgICBjb25zdCBicmlnaHRuZXNzID0gTWF0aC5yb3VuZCgocmdiWzBdICogMjk5ICsgcmdiWzFdICogNTg3ICsgcmdiWzJdICogMTE0KSAvIDEwMDApOwogICAgICAgIHJldHVybiBicmlnaHRuZXNzID4gMTI1ID8gJ2luaGVyaXQnIDogJyNlZWUnOwogICAgfQogICAgLyoqCiAgICAgKiBUdXJucyBhIGhleCBzdHJpbmcgaW50byBhbiBSR0IgYXJyYXkuCiAgICAgKiBAcGFyYW0gez9zdHJpbmd9IGNvbG9yIFJHQiBoZXggY29sb3IgY29kZSwgZS5nLiAjZWVlLCAjZWVlZWVlLgogICAgICogQHJldHVybiB7QXJyYXk8bnVtYmVyPn0KICAgICAqLwogICAgZnVuY3Rpb24gY29udmVydEhleFRvUmdiKGNvbG9yKSB7CiAgICAgICAgaWYgKCFjb2xvcikgewogICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgICAgbGV0IG0gPSBjb2xvci5tYXRjaCgvXiMoWzAtOWEtZl17MSwyfSkoWzAtOWEtZl17MSwyfSkoWzAtOWEtZl17MSwyfSkkLyk7CiAgICAgICAgaWYgKCFtKSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICBpZiAoY29sb3IubGVuZ3RoID09IDQpIHsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDE7IGkgPD0gMzsgaSsrKSB7CiAgICAgICAgICAgICAgICBtW2ldID0gbVtpXSArIG1baV07CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIFtwYXJzZUludChtWzFdLCAxNiksIHBhcnNlSW50KG1bMl0sIDE2KSwgcGFyc2VJbnQobVszXSwgMTYpXTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNyBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHJlZ2lzdGVyU3R5bGVEb21Nb2R1bGUoewogICAgICAgIG1vZHVsZU5hbWU6ICd0Zi1jYXJkLWhlYWRpbmctc3R5bGUnLAogICAgICAgIHN0eWxlQ29udGVudDogYAogICAgZmlnY2FwdGlvbiB7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgfQoKICAgIC8qKiBIb3Jpem9udGFsIGxpbmUgb2YgbGFiZWxzLiAqLwogICAgLmhlYWRpbmctcm93IHsKICAgICAgbWFyZ2luLXRvcDogLTRweDsKICAgICAgZGlzcGxheTogZmxleDsKICAgICAgZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgZmxleC13cmFwOiB3cmFwOwogICAgfQoKICAgIC8qKiBQaWVjZSBvZiB0ZXh0IGluIHRoZSBmaWd1cmUgY2FwdGlvbi4gKi8KICAgIC5oZWFkaW5nLWxhYmVsIHsKICAgICAgZmxleC1ncm93OiAxOwogICAgICBtYXJnaW4tdG9wOiA0cHg7CiAgICAgIG1heC13aWR0aDogMTAwJTsKICAgICAgd29yZC13cmFwOiBicmVhay13b3JkOwogICAgfQoKICAgIC8qKiBNYWtlcyBsYWJlbCBzaG93IG9uIHRoZSByaWdodC4gKi8KICAgIC5oZWFkaW5nLXJpZ2h0IHsKICAgICAgZmxleC1ncm93OiAwOwogICAgfQogIGAsCiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNyBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogQSBjb21wYWN0IGhlYWRpbmcgdG8gYXBwZWFyIGFib3ZlIGEgc2luZ2xlIHZpc3VhbGl6YXRpb24sIHN1bW1hcml6aW5nCiAgICAgKiB0aGUgbWV0YWRhdGEgYWJvdXQgYSB0YWcgb3IgcnVuLXRhZyBjb21iaW5hdGlvbi4KICAgICAqCiAgICAgKiBQcm9wZXJ0aWVzIChhbGwgb3B0aW9uYWwpOgogICAgICogICAtIGBkaXNwbGF5TmFtZWAsIGB0YWdgLCBhbmQgYGRlc2NyaXB0aW9uYCBhcmUgcHJvcGVydGllcyBmcm9tIHRoZQogICAgICogICAgIHJlbGV2YW50IFN1bW1hcnkgcHJvdG9idWYuCiAgICAgKiAgIC0gYHJ1bmAgaXMgdGhlIG5hbWUgb2YgdGhlIFRlbnNvckZsb3cgcnVuLCBpZiBhcHBsaWNhYmxlLgogICAgICogICAtIGBjb2xvcmAgY2FuIGJlIHNldCB0byBkaXNwbGF5IGEgY29sb3JlZCBib3JkZXIgYXQgdGhlIGxlZnQgb2YgdGhlCiAgICAgKiAgICAgY2FyZDsgaWYgbGVmdCB1bnNldCwgbm8gYm9yZGVyIHdpbGwgYmUgZGlzcGxheWVkLgogICAgICogICAtIEFueSBjaGlsZHJlbiBvZiB0aGlzIGNvbXBvbmVudCB3aWxsIGJlIHJlbmRlcmVkIGJlbG93IHRoZSBhYm92ZQogICAgICogICAgIGluZm9ybWF0aW9uLCBhbmQgY2FuIGJlIHVzZWQgdG8gZGlzcGxheSAoZm9yIGV4YW1wbGUpIHNvbWUgc21hbGwKICAgICAqICAgICBjb250cm9sIHdpZGdldHMuCiAgICAgKi8KICAgIGxldCBUZkNhcmRIZWFkaW5nID0gY2xhc3MgVGZDYXJkSGVhZGluZyBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5kaXNwbGF5TmFtZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMudGFnID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5ydW4gPSBudWxsOwogICAgICAgICAgICB0aGlzLmRlc2NyaXB0aW9uID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5jb2xvciA9IG51bGw7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVIZWFkaW5nU3R5bGUoKSB7CiAgICAgICAgICAgIHRoaXMudXBkYXRlU3R5bGVzKHsKICAgICAgICAgICAgICAgICctLXRmLWNhcmQtaGVhZGluZy1iYWNrZ3JvdW5kLWNvbG9yJzogdGhpcy5fcnVuQmFja2dyb3VuZCwKICAgICAgICAgICAgICAgICctLXRmLWNhcmQtaGVhZGluZy1jb2xvcic6IHRoaXMuX3J1bkNvbG9yLAogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVSdW5CYWNrZ3JvdW5kKGNvbG9yKSB7CiAgICAgICAgICAgIHJldHVybiBjb2xvciB8fCAnbm9uZSc7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlUnVuQ29sb3IoY29sb3IpIHsKICAgICAgICAgICAgcmV0dXJuIHBpY2tUZXh0Q29sb3IoY29sb3IpOwogICAgICAgIH0KICAgICAgICBnZXQgX25hbWVMYWJlbCgpIHsKICAgICAgICAgICAgdmFyIGRpc3BsYXlOYW1lID0gdGhpcy5kaXNwbGF5TmFtZTsKICAgICAgICAgICAgdmFyIHRhZyA9IHRoaXMudGFnOwogICAgICAgICAgICByZXR1cm4gZGlzcGxheU5hbWUgfHwgdGFnIHx8ICcnOwogICAgICAgIH0KICAgICAgICBnZXQgX3RhZ0xhYmVsKCkgewogICAgICAgICAgICB2YXIgZGlzcGxheU5hbWUgPSB0aGlzLmRpc3BsYXlOYW1lOwogICAgICAgICAgICB2YXIgdGFnID0gdGhpcy50YWc7CiAgICAgICAgICAgIHJldHVybiB0YWcgJiYgdGFnICE9PSBkaXNwbGF5TmFtZSA/IHRhZyA6ICcnOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlRGVzY3JpcHRpb25EaWFsb2coZSkgewogICAgICAgICAgICBjb25zdCBkaWFsb2cgPSB0aGlzLiQuZGVzY3JpcHRpb25EaWFsb2c7CiAgICAgICAgICAgIGRpYWxvZy5wb3NpdGlvblRhcmdldCA9IGUudGFyZ2V0OwogICAgICAgICAgICBkaWFsb2cudG9nZ2xlKCk7CiAgICAgICAgfQogICAgfTsKICAgIFRmQ2FyZEhlYWRpbmcudGVtcGxhdGUgPSBodG1sIGAKICAgIDxkaXYgY2xhc3M9ImNvbnRhaW5lciI+CiAgICAgIDxmaWdjYXB0aW9uIGNsYXNzPSJjb250ZW50Ij4KICAgICAgICA8ZGl2IGNsYXNzPSJoZWFkaW5nLXJvdyI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX25hbWVMYWJlbF1dIj4KICAgICAgICAgICAgPGRpdiBpdGVtcHJvcD0ibmFtZSIgY2xhc3M9ImhlYWRpbmctbGFiZWwgbmFtZSI+W1tfbmFtZUxhYmVsXV08L2Rpdj4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbcnVuXV0iPgogICAgICAgICAgICA8IS0tIEV4dHJhIHdyYXBwaW5nIHNwYW4gbmVlZGVkIHRvIGF2b2lkIGZsZXhib3ggYmxvY2tpZmljYXRpb24uIC0tPgogICAgICAgICAgICA8IS0tIChzZWUgZmxleGJveCBzcGVjLCBzZWN0aW9uIDQgIkZsZXggSXRlbXMiKSAtLT4KICAgICAgICAgICAgPHNwYW4+CiAgICAgICAgICAgICAgPHNwYW4KICAgICAgICAgICAgICAgIGl0ZW1wcm9wPSJydW4iCiAgICAgICAgICAgICAgICBpZD0iaGVhZGluZy1ydW4iCiAgICAgICAgICAgICAgICBjbGFzcz0iaGVhZGluZy1sYWJlbCBoZWFkaW5nLXJpZ2h0IHJ1biIKICAgICAgICAgICAgICAgID5bW3J1bl1dPC9zcGFuCiAgICAgICAgICAgICAgPgogICAgICAgICAgICA8L3NwYW4+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvZGl2PgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfdGFnTGFiZWxdXSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJoZWFkaW5nLXJvdyI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9ImhlYWRpbmctbGFiZWwiPgogICAgICAgICAgICAgIHRhZzogPHNwYW4gaXRlbXByb3A9InRhZyI+W1tfdGFnTGFiZWxdXTwvc3Bhbj4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDxzbG90Pjwvc2xvdD4KICAgICAgPC9maWdjYXB0aW9uPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbZGVzY3JpcHRpb25dXSI+CiAgICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgICBpY29uPSJpbmZvIgogICAgICAgICAgb24tdGFwPSJfdG9nZ2xlRGVzY3JpcHRpb25EaWFsb2ciCiAgICAgICAgICB0aXRsZT0iU2hvdyBzdW1tYXJ5IGRlc2NyaXB0aW9uIgogICAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICA8L3RlbXBsYXRlPgogICAgICA8cGFwZXItZGlhbG9nCiAgICAgICAgaWQ9ImRlc2NyaXB0aW9uRGlhbG9nIgogICAgICAgIG5vLW92ZXJsYXA9IiIKICAgICAgICBob3Jpem9udGFsLWFsaWduPSJhdXRvIgogICAgICAgIHZlcnRpY2FsLWFsaWduPSJhdXRvIgogICAgICA+CiAgICAgICAgPHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlPgogICAgICAgICAgPHRmLW1hcmtkb3duLXZpZXcgaHRtbD0iW1tkZXNjcmlwdGlvbl1dIj48L3RmLW1hcmtkb3duLXZpZXc+CiAgICAgICAgPC9wYXBlci1kaWFsb2ctc2Nyb2xsYWJsZT4KICAgICAgPC9wYXBlci1kaWFsb2c+CiAgICA8L2Rpdj4KICAgIDxzdHlsZSBpbmNsdWRlPSJ0Zi1jYXJkLWhlYWRpbmctc3R5bGUiPgogICAgICAuY29udGFpbmVyIHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICB9CiAgICAgIC5jb250ZW50IHsKICAgICAgICBmb250LXNpemU6IDEycHg7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICB9CiAgICAgIC5uYW1lIHsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgIH0KICAgICAgLnJ1biB7CiAgICAgICAgZm9udC1zaXplOiAxMXB4OwogICAgICAgIHdpZHRoOiBhdXRvOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDNweDsKICAgICAgICBmb250LXdlaWdodDogYm9sZDsKICAgICAgICBwYWRkaW5nOiAxcHggNHB4IDJweDsKICAgICAgfQogICAgICBwYXBlci1pY29uLWJ1dHRvbiB7CiAgICAgICAgZmxleC1ncm93OiAwOwogICAgICB9CiAgICAgIHBhcGVyLWRpYWxvZy1zY3JvbGxhYmxlIHsKICAgICAgICBtYXgtd2lkdGg6IDY0MHB4OwogICAgICB9CiAgICAgICNoZWFkaW5nLXJ1biB7CiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tdGYtY2FyZC1oZWFkaW5nLWJhY2tncm91bmQtY29sb3IpOwogICAgICAgIGNvbG9yOiB2YXIoLS10Zi1jYXJkLWhlYWRpbmctY29sb3IpOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmQ2FyZEhlYWRpbmcucHJvdG90eXBlLCAiZGlzcGxheU5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkNhcmRIZWFkaW5nLnByb3RvdHlwZSwgInRhZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmQ2FyZEhlYWRpbmcucHJvdG90eXBlLCAicnVuIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXJkSGVhZGluZy5wcm90b3R5cGUsICJkZXNjcmlwdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmQ2FyZEhlYWRpbmcucHJvdG90eXBlLCAiY29sb3IiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVSdW5CYWNrZ3JvdW5kKGNvbG9yKScsCiAgICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ191cGRhdGVIZWFkaW5nU3R5bGUnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXJkSGVhZGluZy5wcm90b3R5cGUsICJfcnVuQmFja2dyb3VuZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgY29tcHV0ZWQ6ICdfY29tcHV0ZVJ1bkNvbG9yKGNvbG9yKScsCiAgICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ191cGRhdGVIZWFkaW5nU3R5bGUnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZDYXJkSGVhZGluZy5wcm90b3R5cGUsICJfcnVuQ29sb3IiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ2Rpc3BsYXlOYW1lJywgJ3RhZycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDYXJkSGVhZGluZy5wcm90b3R5cGUsICJfbmFtZUxhYmVsIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnZGlzcGxheU5hbWUnLCAndGFnJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkNhcmRIZWFkaW5nLnByb3RvdHlwZSwgIl90YWdMYWJlbCIsIG51bGwpOwogICAgVGZDYXJkSGVhZGluZyA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWNhcmQtaGVhZGluZycpCiAgICBdLCBUZkNhcmRIZWFkaW5nKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qCiAgICB0Zi1hdWRpby1sb2FkZXIgbG9hZHMgYW4gaW5kaXZpZHVhbCBhdWRpbyBjbGlwIGZyb20gdGhlIFRlbnNvckJvYXJkCiAgICBiYWNrZW5kLgogICAgKi8KICAgIGxldCBfVGZBdWRpb0xvYWRlciA9IGNsYXNzIF9UZkF1ZGlvTG9hZGVyIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX21ldGFkYXRhQ2FuY2VsbGVyID0gbmV3IENhbmNlbGxlcigpOwogICAgICAgICAgICB0aGlzLl9zdGVwcyA9IFtdOwogICAgICAgICAgICB0aGlzLl9hdHRhY2hlZCA9IGZhbHNlOwogICAgICAgIH0KICAgICAgICBnZXQgX3J1bkNvbG9yKCkgewogICAgICAgICAgICB2YXIgcnVuID0gdGhpcy5ydW47CiAgICAgICAgICAgIHJldHVybiBydW5zQ29sb3JTY2FsZShydW4pOwogICAgICAgIH0KICAgICAgICBnZXQgX2hhc0F0TGVhc3RPbmVTdGVwKCkgewogICAgICAgICAgICB2YXIgc3RlcHMgPSB0aGlzLl9zdGVwczsKICAgICAgICAgICAgcmV0dXJuICEhc3RlcHMgJiYgc3RlcHMubGVuZ3RoID4gMDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9oYXNNdWx0aXBsZVN0ZXBzKCkgewogICAgICAgICAgICB2YXIgc3RlcHMgPSB0aGlzLl9zdGVwczsKICAgICAgICAgICAgcmV0dXJuICEhc3RlcHMgJiYgc3RlcHMubGVuZ3RoID4gMTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9tYXhTdGVwSW5kZXgoKSB7CiAgICAgICAgICAgIHZhciBzdGVwcyA9IHRoaXMuX3N0ZXBzOwogICAgICAgICAgICByZXR1cm4gc3RlcHMubGVuZ3RoIC0gMTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jdXJyZW50RGF0dW0oKSB7CiAgICAgICAgICAgIHZhciBzdGVwcyA9IHRoaXMuX3N0ZXBzOwogICAgICAgICAgICB2YXIgc3RlcEluZGV4ID0gdGhpcy5fc3RlcEluZGV4OwogICAgICAgICAgICByZXR1cm4gc3RlcHNbc3RlcEluZGV4XTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9zYW1wbGVUZXh0KCkgewogICAgICAgICAgICB2YXIgc2FtcGxlID0gdGhpcy5zYW1wbGU7CiAgICAgICAgICAgIHJldHVybiBgJHtzYW1wbGUgKyAxfWA7CiAgICAgICAgfQogICAgICAgIGdldCBfaGFzTXVsdGlwbGVTYW1wbGVzKCkgewogICAgICAgICAgICB2YXIgdG90YWxTYW1wbGVzID0gdGhpcy50b3RhbFNhbXBsZXM7CiAgICAgICAgICAgIHJldHVybiB0b3RhbFNhbXBsZXMgPiAxOwogICAgICAgIH0KICAgICAgICBhdHRhY2hlZCgpIHsKICAgICAgICAgICAgdGhpcy5fYXR0YWNoZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICBfcmVsb2FkT25SdW5UYWdDaGFuZ2UoKSB7CiAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgfQogICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9hdHRhY2hlZCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX21ldGFkYXRhQ2FuY2VsbGVyLmNhbmNlbEFsbCgpOwogICAgICAgICAgICBjb25zdCByb3V0ZXIgPSBnZXRSb3V0ZXIoKTsKICAgICAgICAgICAgY29uc3QgdXJsID0gcm91dGVyLnBsdWdpblJvdXRlKCdhdWRpbycsICcvYXVkaW8nLCBuZXcgVVJMU2VhcmNoUGFyYW1zKHsKICAgICAgICAgICAgICAgIHRhZzogdGhpcy50YWcsCiAgICAgICAgICAgICAgICBydW46IHRoaXMucnVuLAogICAgICAgICAgICAgICAgc2FtcGxlOiBTdHJpbmcodGhpcy5zYW1wbGUpLAogICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIGNvbnN0IHVwZGF0ZVN0ZXBzID0gdGhpcy5fbWV0YWRhdGFDYW5jZWxsZXIuY2FuY2VsbGFibGUoKHJlc3VsdCkgPT4gewogICAgICAgICAgICAgICAgaWYgKHJlc3VsdC5jYW5jZWxsZWQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb25zdCBkYXRhID0gcmVzdWx0LnZhbHVlOwogICAgICAgICAgICAgICAgY29uc3Qgc3RlcHMgPSBkYXRhLm1hcCh0aGlzLl9jcmVhdGVTdGVwRGF0dW0uYmluZCh0aGlzKSk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3N0ZXBzJywgc3RlcHMpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19zdGVwSW5kZXgnLCBzdGVwcy5sZW5ndGggLSAxKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMucmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwpLnRoZW4odXBkYXRlU3RlcHMpOwogICAgICAgIH0KICAgICAgICBfY3JlYXRlU3RlcERhdHVtKGF1ZGlvTWV0YWRhdGEpIHsKICAgICAgICAgICAgY29uc3Qgc2VhcmNoUGFyYW0gPSBuZXcgVVJMU2VhcmNoUGFyYW1zKGF1ZGlvTWV0YWRhdGEucXVlcnkpOwogICAgICAgICAgICAvLyBJbmNsdWRlIHdhbGxfdGltZSBqdXN0IHRvIGRpc2FtYmlndWF0ZSB0aGUgVVJMIGFuZCBmb3JjZQogICAgICAgICAgICAvLyB0aGUgYnJvd3NlciB0byByZWxvYWQgdGhlIGF1ZGlvIHdoZW4gdGhlIFVSTCBjaGFuZ2VzLiBUaGUKICAgICAgICAgICAgLy8gYmFja2VuZCBkb2Vzbid0IGNhcmUgYWJvdXQgdGhlIHZhbHVlLgogICAgICAgICAgICBzZWFyY2hQYXJhbS5hcHBlbmQoJ3RzJywgU3RyaW5nKGF1ZGlvTWV0YWRhdGEud2FsbF90aW1lKSk7CiAgICAgICAgICAgIGNvbnN0IHVybCA9IGdldFJvdXRlcigpLnBsdWdpblJvdXRlKCdhdWRpbycsICcvaW5kaXZpZHVhbEF1ZGlvJywgc2VhcmNoUGFyYW0pOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgd2FsbF90aW1lOiBmb3JtYXREYXRlJDEobmV3IERhdGUoYXVkaW9NZXRhZGF0YS53YWxsX3RpbWUgKiAxMDAwKSksCiAgICAgICAgICAgICAgICBzdGVwOiBhdWRpb01ldGFkYXRhLnN0ZXAsCiAgICAgICAgICAgICAgICBsYWJlbDogYXVkaW9NZXRhZGF0YS5sYWJlbCwKICAgICAgICAgICAgICAgIGNvbnRlbnRUeXBlOiBhdWRpb01ldGFkYXRhLmNvbnRlbnRUeXBlLAogICAgICAgICAgICAgICAgdXJsLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgIH07CiAgICBfVGZBdWRpb0xvYWRlci50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWNhcmQtaGVhZGluZwogICAgICB0YWc9IltbdGFnXV0iCiAgICAgIHJ1bj0iW1tydW5dXSIKICAgICAgZGlzcGxheS1uYW1lPSJbW3RhZ01ldGFkYXRhLmRpc3BsYXlOYW1lXV0iCiAgICAgIGRlc2NyaXB0aW9uPSJbW3RhZ01ldGFkYXRhLmRlc2NyaXB0aW9uXV0iCiAgICAgIGNvbG9yPSJbW19ydW5Db2xvcl1dIgogICAgPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc011bHRpcGxlU2FtcGxlc11dIj4KICAgICAgICA8ZGl2IGNsYXNzPSJoZWFkaW5nLXJvdyI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJoZWFkaW5nLWxhYmVsIj4KICAgICAgICAgICAgc2FtcGxlOiBbW19zYW1wbGVUZXh0XV0gb2YgW1t0b3RhbFNhbXBsZXNdXQogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaGFzQXRMZWFzdE9uZVN0ZXBdXSI+CiAgICAgICAgPGRpdiBjbGFzcz0iaGVhZGluZy1yb3ciPgogICAgICAgICAgPGRpdiBjbGFzcz0iaGVhZGluZy1sYWJlbCI+CiAgICAgICAgICAgIHN0ZXAgPHN0cm9uZz5bW19jdXJyZW50RGF0dW0uc3RlcF1dPC9zdHJvbmc+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfY3VycmVudERhdHVtLndhbGxfdGltZV1dIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iaGVhZGluZy1sYWJlbCBoZWFkaW5nLXJpZ2h0Ij4KICAgICAgICAgICAgICBbW19jdXJyZW50RGF0dW0ud2FsbF90aW1lXV0KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc011bHRpcGxlU3RlcHNdXSI+CiAgICAgICAgPGRpdiBjbGFzcz0iaGVhZGluZy1yb3ciPgogICAgICAgICAgPHBhcGVyLXNsaWRlcgogICAgICAgICAgICBpZD0ic3RlcHMiCiAgICAgICAgICAgIGltbWVkaWF0ZS12YWx1ZT0ie3tfc3RlcEluZGV4fX0iCiAgICAgICAgICAgIG1heD0iW1tfbWF4U3RlcEluZGV4XV0iCiAgICAgICAgICAgIG1heC1tYXJrZXJzPSJbW19tYXhTdGVwSW5kZXhdXSIKICAgICAgICAgICAgc25hcHM9IiIKICAgICAgICAgICAgc3RlcD0iMSIKICAgICAgICAgICAgdmFsdWU9Int7X3N0ZXBJbmRleH19IgogICAgICAgICAgPjwvcGFwZXItc2xpZGVyPgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgPC90Zi1jYXJkLWhlYWRpbmc+CiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc0F0TGVhc3RPbmVTdGVwXV0iPgogICAgICA8YXVkaW8KICAgICAgICBjb250cm9scz0iIgogICAgICAgIHNyYyQ9IltbX2N1cnJlbnREYXR1bS51cmxdXSIKICAgICAgICB0eXBlJD0iW1tfY3VycmVudERhdHVtLmNvbnRlbnRUeXBlXV0iCiAgICAgID48L2F1ZGlvPgogICAgICA8dGYtbWFya2Rvd24tdmlldyBodG1sPSJbW19jdXJyZW50RGF0dW0ubGFiZWxdXSI+PC90Zi1tYXJrZG93bi12aWV3PgogICAgPC90ZW1wbGF0ZT4KICAgIDxkaXYgaWQ9Im1haW4tYXVkaW8tY29udGFpbmVyIj48L2Rpdj4KCiAgICA8c3R5bGUgaW5jbHVkZT0idGYtY2FyZC1oZWFkaW5nLXN0eWxlIj4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHdpZHRoOiAzNTBweDsKICAgICAgICBoZWlnaHQ6IGF1dG87CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIC0tc3RlcC1zbGlkZXIta25vYi1jb2xvcjogIzQyNDI0MjsKICAgICAgICBtYXJnaW4tcmlnaHQ6IDE1cHg7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMTVweDsKICAgICAgfQoKICAgICAgI3N0ZXBzIHsKICAgICAgICBoZWlnaHQ6IDE1cHg7CiAgICAgICAgbWFyZ2luOiAwIDAgMCAtMTVweDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgIHBhZGRpbmc6IDAgNXB4OyAvKiBzbyB0aGUgc2xpZGVyIGtub2IgZG9lc24ndCBidXR0IG91dCAqLwogICAgICAgIG1hcmdpbi10b3A6IDVweDsKICAgICAgICAtLXBhcGVyLXNsaWRlci1hY3RpdmUtY29sb3I6IHZhcigtLXN0ZXAtc2xpZGVyLWtub2ItY29sb3IpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLWtub2ItY29sb3I6IHZhcigtLXN0ZXAtc2xpZGVyLWtub2ItY29sb3IpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLXBpbi1jb2xvcjogdmFyKC0tc3RlcC1zbGlkZXIta25vYi1jb2xvcik7CiAgICAgICAgLS1wYXBlci1zbGlkZXIta25vYi1zdGFydC1jb2xvcjogdmFyKC0tc3RlcC1zbGlkZXIta25vYi1jb2xvcik7CiAgICAgICAgLS1wYXBlci1zbGlkZXIta25vYi1zdGFydC1ib3JkZXItY29sb3I6IHZhcigtLXN0ZXAtc2xpZGVyLWtub2ItY29sb3IpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLXBpbi1zdGFydC1jb2xvcjogdmFyKC0tc3RlcC1zbGlkZXIta25vYi1jb2xvcik7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAicnVuIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAidGFnIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAic2FtcGxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAidG90YWxTYW1wbGVzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAidGFnTWV0YWRhdGEiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBSZXF1ZXN0TWFuYWdlcikKICAgIF0sIF9UZkF1ZGlvTG9hZGVyLnByb3RvdHlwZSwgInJlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQ2FuY2VsbGVyKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX21ldGFkYXRhQ2FuY2VsbGVyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIF9UZkF1ZGlvTG9hZGVyLnByb3RvdHlwZSwgIl9zdGVwcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIF9UZkF1ZGlvTG9hZGVyLnByb3RvdHlwZSwgIl9zdGVwSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ3J1bicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX3J1bkNvbG9yIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX3N0ZXBzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX2hhc0F0TGVhc3RPbmVTdGVwIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX3N0ZXBzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX2hhc011bHRpcGxlU3RlcHMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfc3RlcHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlciksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkF1ZGlvTG9hZGVyLnByb3RvdHlwZSwgIl9tYXhTdGVwSW5kZXgiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfc3RlcHMnLCAnX3N0ZXBJbmRleCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX2N1cnJlbnREYXR1bSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ3NhbXBsZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQXVkaW9Mb2FkZXIucHJvdG90eXBlLCAiX3NhbXBsZVRleHQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCd0b3RhbFNhbXBsZXMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBfVGZBdWRpb0xvYWRlci5wcm90b3R5cGUsICJfaGFzTXVsdGlwbGVTYW1wbGVzIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdydW4nLCAndGFnJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVGZBdWRpb0xvYWRlci5wcm90b3R5cGUsICJfcmVsb2FkT25SdW5UYWdDaGFuZ2UiLCBudWxsKTsKICAgIF9UZkF1ZGlvTG9hZGVyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtYXVkaW8tbG9hZGVyJykKICAgIF0sIF9UZkF1ZGlvTG9hZGVyKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qCiAgICB0Zi1hdWRpby1kYXNoYm9hcmQgZGlzcGxheXMgYSBkYXNoYm9hcmQgdGhhdCBsb2FkcyBhdWRpbyBmcm9tIGEgVGVuc29yRmxvdyBydW4uCiAgICAqLwogICAgbGV0IFRmQXVkaW9EYXNoYm9hcmQgPSBjbGFzcyBUZkF1ZGlvRGFzaGJvYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMucmVsb2FkT25SZWFkeSA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX3RhZ0ZpbHRlciA9ICcnOwogICAgICAgICAgICB0aGlzLl9yZXF1ZXN0TWFuYWdlciA9IG5ldyBSZXF1ZXN0TWFuYWdlcigpOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgaWYgKHRoaXMucmVsb2FkT25SZWFkeSkKICAgICAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgfQogICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgdGhpcy5fZmV0Y2hUYWdzKCkudGhlbigoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9yZWxvYWRBdWRpbygpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2ZldGNoVGFncygpIHsKICAgICAgICAgICAgY29uc3QgdXJsID0gZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2F1ZGlvJywgJy90YWdzJyk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9yZXF1ZXN0TWFuYWdlci5yZXF1ZXN0KHVybCkudGhlbigocnVuVG9UYWdJbmZvKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAobG9kYXNoLmlzRXF1YWwocnVuVG9UYWdJbmZvLCB0aGlzLl9ydW5Ub1RhZ0luZm8pKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gTm8gbmVlZCB0byB1cGRhdGUgYW55dGhpbmcgaWYgdGhlcmUgYXJlIG5vIGNoYW5nZXMuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29uc3QgcnVuVG9UYWcgPSBsb2Rhc2gubWFwVmFsdWVzKHJ1blRvVGFnSW5mbywgKHgpID0+IE9iamVjdC5rZXlzKHgpKTsKICAgICAgICAgICAgICAgIGNvbnN0IHRhZ3MgPSBnZXRUYWdzKHJ1blRvVGFnKTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfZGF0YU5vdEZvdW5kJywgdGFncy5sZW5ndGggPT09IDApOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19ydW5Ub1RhZ0luZm8nLCBydW5Ub1RhZ0luZm8pOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX3JlbG9hZEF1ZGlvKCkgewogICAgICAgICAgICB0aGlzLnJvb3QucXVlcnlTZWxlY3RvckFsbCgndGYtYXVkaW8tbG9hZGVyJykuZm9yRWFjaCgoYXVkaW8pID0+IHsKICAgICAgICAgICAgICAgIGF1ZGlvLnJlbG9hZCgpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX3Nob3VsZE9wZW4oaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIGluZGV4IDw9IDI7CiAgICAgICAgfQogICAgICAgIGdldCBfY2F0ZWdvcmllcygpIHsKICAgICAgICAgICAgdmFyIHJ1blRvVGFnSW5mbyA9IHRoaXMuX3J1blRvVGFnSW5mbzsKICAgICAgICAgICAgdmFyIHNlbGVjdGVkUnVucyA9IHRoaXMuX3NlbGVjdGVkUnVuczsKICAgICAgICAgICAgdmFyIHRhZ0ZpbHRlciA9IHRoaXMuX3RhZ0ZpbHRlcjsKICAgICAgICAgICAgY29uc3QgcnVuVG9UYWcgPSBsb2Rhc2gubWFwVmFsdWVzKHJ1blRvVGFnSW5mbywgKHgpID0+IE9iamVjdC5rZXlzKHgpKTsKICAgICAgICAgICAgY29uc3QgYmFzZUNhdGVnb3JpZXMgPSBjYXRlZ29yaXplUnVuVGFnQ29tYmluYXRpb25zKHJ1blRvVGFnLCBzZWxlY3RlZFJ1bnMsIHRhZ0ZpbHRlcik7CiAgICAgICAgICAgIGZ1bmN0aW9uIGV4cGxvZGVJdGVtKGl0ZW0pIHsKICAgICAgICAgICAgICAgIGNvbnN0IHNhbXBsZXMgPSBydW5Ub1RhZ0luZm9baXRlbS5ydW5dW2l0ZW0udGFnXS5zYW1wbGVzOwogICAgICAgICAgICAgICAgcmV0dXJuIGxvZGFzaC5yYW5nZShzYW1wbGVzKS5tYXAoKGkpID0+IE9iamVjdC5hc3NpZ24oe30sIGl0ZW0sIHsKICAgICAgICAgICAgICAgICAgICBzYW1wbGU6IGksCiAgICAgICAgICAgICAgICAgICAgdG90YWxTYW1wbGVzOiBzYW1wbGVzLAogICAgICAgICAgICAgICAgfSkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHdpdGhTYW1wbGVzID0gYmFzZUNhdGVnb3JpZXMubWFwKChjYXRlZ29yeSkgPT4gT2JqZWN0LmFzc2lnbih7fSwgY2F0ZWdvcnksIHsKICAgICAgICAgICAgICAgIGl0ZW1zOiBbXS5jb25jYXQuYXBwbHkoW10sIGNhdGVnb3J5Lml0ZW1zLm1hcChleHBsb2RlSXRlbSkpLAogICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIHJldHVybiB3aXRoU2FtcGxlczsKICAgICAgICB9CiAgICAgICAgX3RhZ01ldGFkYXRhKHJ1blRvVGFnSW5mbywgcnVuLCB0YWcpIHsKICAgICAgICAgICAgcmV0dXJuIHJ1blRvVGFnSW5mb1tydW5dW3RhZ107CiAgICAgICAgfQogICAgfTsKICAgIFRmQXVkaW9EYXNoYm9hcmQudGVtcGxhdGUgPSBodG1sIGAKICAgIDx0Zi1kYXNoYm9hcmQtbGF5b3V0PgogICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyIiBzbG90PSJzaWRlYmFyIj4KICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24gcnVucy1zZWxlY3RvciI+CiAgICAgICAgICA8dGYtcnVucy1zZWxlY3RvcgogICAgICAgICAgICBpZD0icnVucy1zZWxlY3RvciIKICAgICAgICAgICAgc2VsZWN0ZWQtcnVucz0ie3tfc2VsZWN0ZWRSdW5zfX0iCiAgICAgICAgICA+PC90Zi1ydW5zLXNlbGVjdG9yPgogICAgICAgIDwvZGl2PgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBjbGFzcz0iY2VudGVyIiBzbG90PSJjZW50ZXIiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPGRpdiBjbGFzcz0ibm8tZGF0YS13YXJuaW5nIj4KICAgICAgICAgICAgPGgzPk5vIGF1ZGlvIGRhdGEgd2FzIGZvdW5kLjwvaDM+CiAgICAgICAgICAgIDxwPlByb2JhYmxlIGNhdXNlczo8L3A+CiAgICAgICAgICAgIDx1bD4KICAgICAgICAgICAgICA8bGk+WW91IGhhdmVu4oCZdCB3cml0dGVuIGFueSBhdWRpbyBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgICA8bGk+VGVuc29yQm9hcmQgY2Fu4oCZdCBmaW5kIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgPC91bD4KCiAgICAgICAgICAgIDxwPgogICAgICAgICAgICAgIElmIHlvdeKAmXJlIG5ldyB0byB1c2luZyBUZW5zb3JCb2FyZCwgYW5kIHdhbnQgdG8gZmluZCBvdXQgaG93IHRvCiAgICAgICAgICAgICAgYWRkIGRhdGEgYW5kIHNldCB1cCB5b3VyIGV2ZW50IGZpbGVzLCBjaGVjayBvdXQgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS90ZW5zb3JmbG93L3RlbnNvcmJvYXJkL2Jsb2IvbWFzdGVyL1JFQURNRS5tZCIKICAgICAgICAgICAgICAgID5SRUFETUU8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIHBlcmhhcHMgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vd3d3LnRlbnNvcmZsb3cub3JnL2dldF9zdGFydGVkL3N1bW1hcmllc19hbmRfdGVuc29yYm9hcmQiCiAgICAgICAgICAgICAgICA+VGVuc29yQm9hcmQgdHV0b3JpYWw8L2EKICAgICAgICAgICAgICA+LgogICAgICAgICAgICA8L3A+CgogICAgICAgICAgICA8cD4KICAgICAgICAgICAgICBJZiB5b3UgdGhpbmsgVGVuc29yQm9hcmQgaXMgY29uZmlndXJlZCBwcm9wZXJseSwgcGxlYXNlIHNlZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9ibG9iL21hc3Rlci9SRUFETUUubWQjbXktdGVuc29yYm9hcmQtaXNudC1zaG93aW5nLWFueS1kYXRhLXdoYXRzLXdyb25nIgogICAgICAgICAgICAgICAgPnRoZSBzZWN0aW9uIG9mIHRoZSBSRUFETUUgZGV2b3RlZCB0byBtaXNzaW5nIGRhdGEgcHJvYmxlbXM8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIGNvbnNpZGVyIGZpbGluZyBhbiBpc3N1ZSBvbiBHaXRIdWIuCiAgICAgICAgICAgIDwvcD4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbWyFfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPHRmLXRhZy1maWx0ZXJlciB0YWctZmlsdGVyPSJ7e190YWdGaWx0ZXJ9fSI+PC90Zi10YWctZmlsdGVyZXI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19jYXRlZ29yaWVzXV0iIGFzPSJjYXRlZ29yeSI+CiAgICAgICAgICAgIDx0Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldwogICAgICAgICAgICAgIGNhdGVnb3J5PSJbW2NhdGVnb3J5XV0iCiAgICAgICAgICAgICAgaW5pdGlhbC1vcGVuZWQ9IltbX3Nob3VsZE9wZW4oaW5kZXgpXV0iCiAgICAgICAgICAgID4KICAgICAgICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICAgICAgICA8dGYtYXVkaW8tbG9hZGVyCiAgICAgICAgICAgICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICAgICAgICAgICAgcnVuPSJbW2l0ZW0ucnVuXV0iCiAgICAgICAgICAgICAgICAgIHRhZz0iW1tpdGVtLnRhZ11dIgogICAgICAgICAgICAgICAgICBzYW1wbGU9IltbaXRlbS5zYW1wbGVdXSIKICAgICAgICAgICAgICAgICAgdG90YWwtc2FtcGxlcz0iW1tpdGVtLnRvdGFsU2FtcGxlc11dIgogICAgICAgICAgICAgICAgICB0YWctbWV0YWRhdGE9IltbX3RhZ01ldGFkYXRhKF9ydW5Ub1RhZ0luZm8sIGl0ZW0ucnVuLCBpdGVtLnRhZyldXSIKICAgICAgICAgICAgICAgICAgcmVxdWVzdC1tYW5hZ2VyPSJbW19yZXF1ZXN0TWFuYWdlcl1dIgogICAgICAgICAgICAgICAgPjwvdGYtYXVkaW8tbG9hZGVyPgogICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDwvdGYtY2F0ZWdvcnktcGFnaW5hdGVkLXZpZXc+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgPC90Zi1kYXNoYm9hcmQtbGF5b3V0PgogICAgPHN0eWxlIGluY2x1ZGU9ImRhc2hib2FyZC1zdHlsZSI+PC9zdHlsZT4KICAgIDxzdHlsZT4KICAgICAgLm5vLWRhdGEtd2FybmluZyB7CiAgICAgICAgbWF4LXdpZHRoOiA1NDBweDsKICAgICAgICBtYXJnaW46IDgwcHggYXV0byAwIGF1dG87CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkF1ZGlvRGFzaGJvYXJkLnByb3RvdHlwZSwgInJlbG9hZE9uUmVhZHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZBdWRpb0Rhc2hib2FyZC5wcm90b3R5cGUsICJfc2VsZWN0ZWRSdW5zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZBdWRpb0Rhc2hib2FyZC5wcm90b3R5cGUsICJfcnVuVG9UYWdJbmZvIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkF1ZGlvRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kYXRhTm90Rm91bmQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkF1ZGlvRGFzaGJvYXJkLnByb3RvdHlwZSwgIl90YWdGaWx0ZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBSZXF1ZXN0TWFuYWdlcikKICAgIF0sIFRmQXVkaW9EYXNoYm9hcmQucHJvdG90eXBlLCAiX3JlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfcnVuVG9UYWdJbmZvJywgJ19zZWxlY3RlZFJ1bnMnLCAnX3RhZ0ZpbHRlcicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkF1ZGlvRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9jYXRlZ29yaWVzIiwgbnVsbCk7CiAgICBUZkF1ZGlvRGFzaGJvYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtYXVkaW8tZGFzaGJvYXJkJykKICAgIF0sIFRmQXVkaW9EYXNoYm9hcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmT3B0aW9uU2VsZWN0b3IgPSBjbGFzcyBUZk9wdGlvblNlbGVjdG9yIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdGhpcy5nZXRFZmZlY3RpdmVDaGlsZHJlbigpLmZvckVhY2goZnVuY3Rpb24gKG5vZGUpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLmxpc3Rlbihub2RlLCAndGFwJywgJ19zZWxlY3RUYXJnZXQnKTsKICAgICAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfc2VsZWN0VGFyZ2V0KGUpIHsKICAgICAgICAgICAgdGhpcy5zZWxlY3RlZElkID0gZS5jdXJyZW50VGFyZ2V0LmlkOwogICAgICAgIH0KICAgICAgICBfc2VsZWN0ZWRJZENoYW5nZWQoKSB7CiAgICAgICAgICAgIHZhciBzZWxlY3RlZCA9IHRoaXMucXVlcnlFZmZlY3RpdmVDaGlsZHJlbignIycgKyB0aGlzLnNlbGVjdGVkSWQpOwogICAgICAgICAgICBpZiAoIXNlbGVjdGVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5nZXRFZmZlY3RpdmVDaGlsZHJlbigpLmZvckVhY2goZnVuY3Rpb24gKG5vZGUpIHsKICAgICAgICAgICAgICAgIG5vZGUuY2xhc3NMaXN0LnJlbW92ZSgnc2VsZWN0ZWQnKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHNlbGVjdGVkLmNsYXNzTGlzdC5hZGQoJ3NlbGVjdGVkJyk7CiAgICAgICAgfQogICAgfTsKICAgIFRmT3B0aW9uU2VsZWN0b3IudGVtcGxhdGUgPSBodG1sIGAKICAgIDxkaXYgaWQ9IndyYXAiPgogICAgICA8aDM+W1tuYW1lXV08L2gzPgogICAgICA8ZGl2IGNsYXNzPSJjb250ZW50LXdyYXBwZXIiPjxzbG90Pjwvc2xvdD48L2Rpdj4KICAgIDwvZGl2PgogICAgPHN0eWxlPgogICAgICAuY29udGVudC13cmFwcGVyIDo6c2xvdHRlZCgqKSB7CiAgICAgICAgYmFja2dyb3VuZDogbm9uZTsKICAgICAgICBjb2xvcjogdmFyKC0tdGItdWktZGFyay1hY2NlbnQpOwogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBtYXJnaW4tdG9wOiAxMHB4OwogICAgICB9CgogICAgICAuY29udGVudC13cmFwcGVyIDo6c2xvdHRlZCgqKSB7CiAgICAgICAgYmFja2dyb3VuZDogbm9uZTsKICAgICAgICBjb2xvcjogdmFyKC0tdGItdWktZGFyay1hY2NlbnQpOwogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBtYXJnaW4tdG9wOiAxMHB4OwogICAgICB9CgogICAgICAuY29udGVudC13cmFwcGVyIDo6c2xvdHRlZCguc2VsZWN0ZWQpIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS10Yi11aS1kYXJrLWFjY2VudCk7CiAgICAgICAgY29sb3I6IHdoaXRlICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIGgzIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItZ3JleS04MDApOwogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICBmb250LXdlaWdodDogbm9ybWFsOwogICAgICAgIG1hcmdpbjogMCAwIDVweDsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk9wdGlvblNlbGVjdG9yLnByb3RvdHlwZSwgIm5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfc2VsZWN0ZWRJZENoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZPcHRpb25TZWxlY3Rvci5wcm90b3R5cGUsICJzZWxlY3RlZElkIiwgdm9pZCAwKTsKICAgIFRmT3B0aW9uU2VsZWN0b3IgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1vcHRpb24tc2VsZWN0b3InKQogICAgXSwgVGZPcHRpb25TZWxlY3Rvcik7CgogICAgLyogQ29weXJpZ2h0IDIwMTcgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIEdpdmVuIG1hbnkgb2NjdXJyZW5jZXMgb2YgdGFnIGluZm8gZm9yIGEgcGFydGljdWxhciB0YWcgYWNyb3NzCiAgICAgKiBtdWx0aXBsZSBydW5zLCBjcmVhdGUgYSByZXByZXNlbnRhdGl2ZSBpbmZvIG9iamVjdC4gVGhpcyBpcyB1c2VmdWwKICAgICAqIGZvciBwbHVnaW5zIHRoYXQgZGlzcGxheSBqdXN0IG9uZSB2aXN1YWxpemF0aW9uIHBlciB0YWcsIGluc3RlYWQgb2YKICAgICAqIG9uZSBwZXIgcnVuLS10YWcgY29tYmluYXRpb246IGVhY2ggcnVuLS10YWcgY29tYmluYXRpb24gY2FuIGhhdmUgaXRzCiAgICAgKiBvd24gZGlzcGxheSBuYW1lIG9yIGRlc2NyaXB0aW9uLCBzbyB0aGVyZSBpcyBhIGRpbWVuc2lvbiBtaXNtYXRjaC4gV2UKICAgICAqIHJlY29uY2lsZSB0aGlzIGFzIGZvbGxvd3M6CiAgICAgKgogICAgICogICAtIFdlIG9ubHkgc2hvdyBhIGRpc3BsYXkgbmFtZSBpZiBhbGwgcnVucyBhZ3JlZS4gT3RoZXJ3aXNlLCBvciBpZgogICAgICogICAgIHRoZXJlIGFyZSBubyBydW5zLCB3ZSB1c2UgdGhlIHByb3ZpZGVkIGBkZWZhdWx0RGlzcGxheU5hbWVgLgogICAgICoKICAgICAqICAgLSBJZiBhbGwgcnVucyBhZ3JlZSBvbiBhIGRlc2NyaXB0aW9uLCB3ZSB1c2UgaXQuIE90aGVyd2lzZSwKICAgICAqICAgICB3ZSBjb25jYXRlbmF0ZSBhbGwgZGVzY3JpcHRpb25zLCBhbm5vdGF0aW5nIHdoaWNoIG9uZXMKICAgICAqICAgICBjYW1lIGZyb20gd2hpY2ggcnVuLCBhbmQgZGlzcGxheSB0aGVtIGluIGEgbGlzdC4KICAgICAqCiAgICAgKiBOT1RFOiBQZXIgVGVuc29yQm9hcmQgY29udmVudGlvbiwgd2UgYXNzdW1lIHRoYXQgdGhlIHByb3ZpZGVkCiAgICAgKiBgZGVzY3JpcHRpb25gcyBoYXZlIHNhbml0aXplZCBIVE1MIGFuZCBhcmUgc2FmZSB0byByZW5kZXIgaW50byB0aGUKICAgICAqIERPTSwgd2hpbGUgdGhlIGBkaXNwbGF5TmFtZWAgbWF5IGJlIGFuIGFyYml0cmFyeSBzdHJpbmcuIFRoZSBvdXRwdXQKICAgICAqIG9mIHRoaXMgZnVuY3Rpb24gcmVzcGVjdHMgdGhpcyBjb252ZW50aW9uIGFzIHdlbGwuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFnZ3JlZ2F0ZVRhZ0luZm8ocnVuVG9UYWdJbmZvLCBkZWZhdWx0RGlzcGxheU5hbWUpIHsKICAgICAgICBsZXQgdW5hbmltb3VzRGlzcGxheU5hbWUgPSB1bmRlZmluZWQ7CiAgICAgICAgY29uc3QgZGVzY3JpcHRpb25Ub1J1bnMgPSB7fTsKICAgICAgICBPYmplY3Qua2V5cyhydW5Ub1RhZ0luZm8pLmZvckVhY2goKHJ1bikgPT4gewogICAgICAgICAgICBjb25zdCBpbmZvID0gcnVuVG9UYWdJbmZvW3J1bl07CiAgICAgICAgICAgIGlmICh1bmFuaW1vdXNEaXNwbGF5TmFtZSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICB1bmFuaW1vdXNEaXNwbGF5TmFtZSA9IGluZm8uZGlzcGxheU5hbWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHVuYW5pbW91c0Rpc3BsYXlOYW1lICE9PSBpbmZvLmRpc3BsYXlOYW1lKSB7CiAgICAgICAgICAgICAgICB1bmFuaW1vdXNEaXNwbGF5TmFtZSA9IG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGRlc2NyaXB0aW9uVG9SdW5zW2luZm8uZGVzY3JpcHRpb25dID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIGRlc2NyaXB0aW9uVG9SdW5zW2luZm8uZGVzY3JpcHRpb25dID0gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZGVzY3JpcHRpb25Ub1J1bnNbaW5mby5kZXNjcmlwdGlvbl0ucHVzaChydW4pOwogICAgICAgIH0pOwogICAgICAgIGNvbnN0IGRpc3BsYXlOYW1lID0gdW5hbmltb3VzRGlzcGxheU5hbWUgIT0gbnVsbCA/IHVuYW5pbW91c0Rpc3BsYXlOYW1lIDogZGVmYXVsdERpc3BsYXlOYW1lOwogICAgICAgIGNvbnN0IGRlc2NyaXB0aW9uID0gKCgpID0+IHsKICAgICAgICAgICAgY29uc3QgZGVzY3JpcHRpb25zID0gT2JqZWN0LmtleXMoZGVzY3JpcHRpb25Ub1J1bnMpOwogICAgICAgICAgICBpZiAoZGVzY3JpcHRpb25zLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGRlc2NyaXB0aW9ucy5sZW5ndGggPT09IDEpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkZXNjcmlwdGlvbnNbMF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBjb25zdCBpdGVtcyA9IGRlc2NyaXB0aW9ucy5tYXAoKGRlc2NyaXB0aW9uKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcnVucyA9IGRlc2NyaXB0aW9uVG9SdW5zW2Rlc2NyaXB0aW9uXS5tYXAoKHJ1bikgPT4gewogICAgICAgICAgICAgICAgICAgICAgICAvLyBXZSdyZSBzcGxpY2luZyBwb3RlbnRpYWxseSB1bnNhZmUgZGlzcGxheSBuYW1lcyBpbnRvCiAgICAgICAgICAgICAgICAgICAgICAgIC8vIHNhbml0aXplZCBkZXNjcmlwdGlvbnMsIHNvIHdlIG5lZWQgdG8gc2FuaXRpemUgdGhlbS4KICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2FmZVJ1biA9IHJ1bgogICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoLzwvZywgJyZsdDsnKQogICAgICAgICAgICAgICAgICAgICAgICAgICAgLnJlcGxhY2UoLz4vZywgJyZndDsnKSAvLyBmb3Igc3ltbWV0cnkgOi0pCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAucmVwbGFjZSgvJi9nLCAnJmFtcDsnKTsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGA8Y29kZT4ke3NhZmVSdW59PC9jb2RlPmA7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgY29uc3Qgam9pbmVkID0gcnVucy5sZW5ndGggPiAyCiAgICAgICAgICAgICAgICAgICAgICAgID8gcnVucy5zbGljZSgwLCBydW5zLmxlbmd0aCAtIDEpLmpvaW4oJywgJykgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgJywgYW5kICcgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgcnVuc1tydW5zLmxlbmd0aCAtIDFdCiAgICAgICAgICAgICAgICAgICAgICAgIDogcnVucy5qb2luKCcgYW5kICcpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHJ1bk5vdW4gPSBuZ2V0dGV4dChydW5zLmxlbmd0aCwgJ3J1bicsICdydW5zJyk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGA8bGk+PHA+Rm9yICR7cnVuTm91bn0gJHtqb2luZWR9OjwvcD4ke2Rlc2NyaXB0aW9ufTwvbGk+YDsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgY29uc3QgcHJlZml4ID0gJzxwPjxzdHJvbmc+TXVsdGlwbGUgZGVzY3JpcHRpb25zOjwvc3Ryb25nPjwvcD4nOwogICAgICAgICAgICAgICAgcmV0dXJuIGAke3ByZWZpeH08dWw+JHtpdGVtcy5qb2luKCcnKX08L3VsPmA7CiAgICAgICAgICAgIH0KICAgICAgICB9KSgpOwogICAgICAgIHJldHVybiB7IGRpc3BsYXlOYW1lLCBkZXNjcmlwdGlvbiB9OwogICAgfQogICAgZnVuY3Rpb24gbmdldHRleHQoaywgZW5TaW5ndWxhciwgZW5QbHVyYWwpIHsKICAgICAgICAvLyBQb3RlbnRpYWwgZXh0ZW5zaW9uIHBvaW50IGZvciBwcm9wZXIgaTE4biBpbmZyYXN0cnVjdHVyZSwgaWYgd2UKICAgICAgICAvLyBldmVyIGltcGxlbWVudCBpdC4KICAgICAgICByZXR1cm4gayA9PT0gMSA/IGVuU2luZ3VsYXIgOiBlblBsdXJhbDsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogdGYtc21vb3RoaW5nLWlucHV0IGNyZWF0ZXMgYW4gaW5wdXQgY29tcG9uZW50IGZvciBleHBvbmVudGlhbCBzbW9vdGhpbmcuCiAgICAgKi8KICAgIGxldCBUZlNtb290aGluZ0lucHV0ID0gCiAgICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bm8tdW51c2VkLXZhcmlhYmxlCiAgICBjbGFzcyBUZlNtb290aGluZ0lucHV0IGV4dGVuZHMgUG9seW1lckVsZW1lbnQgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLndlaWdodCA9IDAuNjsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlV2VpZ2h0ID0gbG9kYXNoLmRlYm91bmNlKGZ1bmN0aW9uICh2YWwpIHsKICAgICAgICAgICAgICAgIHRoaXMud2VpZ2h0ID0gdmFsOwogICAgICAgICAgICB9LCAyNTApOwogICAgICAgIH0KICAgICAgICBfaW1tZWRpYXRlV2VpZ2h0TnVtYmVyRm9yUGFwZXJTbGlkZXJDaGFuZ2VkKCkgewogICAgICAgICAgICB0aGlzLl9pbnB1dFdlaWdodFN0cmluZ0ZvclBhcGVySW5wdXQgPSB0aGlzLl9pbW1lZGlhdGVXZWlnaHROdW1iZXJGb3JQYXBlclNsaWRlci50b1N0cmluZygpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVXZWlnaHQuY2FsbCh0aGlzLCB0aGlzLl9pbW1lZGlhdGVXZWlnaHROdW1iZXJGb3JQYXBlclNsaWRlcik7CiAgICAgICAgfQogICAgICAgIF9pbnB1dFdlaWdodFN0cmluZ0ZvclBhcGVySW5wdXRDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAoK3RoaXMuX2lucHV0V2VpZ2h0U3RyaW5nRm9yUGFwZXJJbnB1dCA8IDApIHsKICAgICAgICAgICAgICAgIHRoaXMuX2lucHV0V2VpZ2h0U3RyaW5nRm9yUGFwZXJJbnB1dCA9ICcwJzsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICgrdGhpcy5faW5wdXRXZWlnaHRTdHJpbmdGb3JQYXBlcklucHV0ID4gMSkgewogICAgICAgICAgICAgICAgdGhpcy5faW5wdXRXZWlnaHRTdHJpbmdGb3JQYXBlcklucHV0ID0gJzEnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBkID0gK3RoaXMuX2lucHV0V2VpZ2h0U3RyaW5nRm9yUGFwZXJJbnB1dDsKICAgICAgICAgICAgaWYgKCFpc05hTihkKSkgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlV2VpZ2h0LmNhbGwodGhpcywgZCk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICB9OwogICAgVGZTbW9vdGhpbmdJbnB1dC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPGgzIGNsYXNzPSJ0aXRsZSI+U21vb3RoaW5nPC9oMz4KICAgIDxkaXYgY2xhc3M9InNtb290aGluZy1ibG9jayI+CiAgICAgIDxwYXBlci1zbGlkZXIKICAgICAgICBpZD0ic2xpZGVyIgogICAgICAgIGltbWVkaWF0ZS12YWx1ZT0ie3tfaW1tZWRpYXRlV2VpZ2h0TnVtYmVyRm9yUGFwZXJTbGlkZXJ9fSIKICAgICAgICBtYXg9IltbbWF4XV0iCiAgICAgICAgbWluPSJbW21pbl1dIgogICAgICAgIHBpbgogICAgICAgIHN0ZXA9Iltbc3RlcF1dIgogICAgICAgIHR5cGU9Im51bWJlciIKICAgICAgICB2YWx1ZT0ie3t3ZWlnaHR9fSIKICAgICAgPjwvcGFwZXItc2xpZGVyPgogICAgICA8cGFwZXItaW5wdXQKICAgICAgICBpZD0iaW5wdXQiCiAgICAgICAgbGFiZWw9IndlaWdodCIKICAgICAgICBuby1sYWJlbC1mbG9hdAogICAgICAgIHZhbHVlPSJ7e19pbnB1dFdlaWdodFN0cmluZ0ZvclBhcGVySW5wdXR9fSIKICAgICAgICB0eXBlPSJudW1iZXIiCiAgICAgICAgc3RlcD0iW1tzdGVwXV0iCiAgICAgICAgbWluPSJbW21pbl1dIgogICAgICAgIG1heD0iW1ttYXhdXSIKICAgICAgPjwvcGFwZXItaW5wdXQ+CiAgICA8L2Rpdj4KICAgIDxzdHlsZT4KICAgICAgLnRpdGxlIHsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItZ3JleS04MDApOwogICAgICAgIG1hcmdpbjogMDsKICAgICAgICBmb250LXdlaWdodDogbm9ybWFsOwogICAgICAgIGZvbnQtc2l6ZTogMTRweDsKICAgICAgICBtYXJnaW4tYm90dG9tOiA1cHg7CiAgICAgIH0KCiAgICAgIC5zbW9vdGhpbmctYmxvY2sgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgIH0KCiAgICAgIHBhcGVyLXNsaWRlciB7CiAgICAgICAgLS1wYXBlci1zbGlkZXItYWN0aXZlLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1rbm9iLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1rbm9iLXN0YXJ0LWJvcmRlci1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgICAgLS1wYXBlci1zbGlkZXIta25vYi1zdGFydC1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgICAgLS1wYXBlci1zbGlkZXItbWFya2Vycy1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgICAgLS1wYXBlci1zbGlkZXItcGluLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1waW4tc3RhcnQtY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIGZsZXgtZ3JvdzogMjsKICAgICAgfQoKICAgICAgcGFwZXItaW5wdXQgewogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWZvY3VzLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1pbnB1dDogewogICAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIH0KICAgICAgICAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1sYWJlbDogewogICAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIH0KICAgICAgICB3aWR0aDogNjBweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZlNtb290aGluZ0lucHV0LnByb3RvdHlwZSwgInN0ZXAiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZlNtb290aGluZ0lucHV0LnByb3RvdHlwZSwgIm1heCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmU21vb3RoaW5nSW5wdXQucHJvdG90eXBlLCAibWluIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZlNtb290aGluZ0lucHV0LnByb3RvdHlwZSwgIndlaWdodCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ19pbW1lZGlhdGVXZWlnaHROdW1iZXJGb3JQYXBlclNsaWRlckNoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZTbW9vdGhpbmdJbnB1dC5wcm90b3R5cGUsICJfaW1tZWRpYXRlV2VpZ2h0TnVtYmVyRm9yUGFwZXJTbGlkZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfaW5wdXRXZWlnaHRTdHJpbmdGb3JQYXBlcklucHV0Q2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZlNtb290aGluZ0lucHV0LnByb3RvdHlwZSwgIl9pbnB1dFdlaWdodFN0cmluZ0ZvclBhcGVySW5wdXQiLCB2b2lkIDApOwogICAgVGZTbW9vdGhpbmdJbnB1dCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLXNtb290aGluZy1pbnB1dCcpCiAgICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLXVudXNlZC12YXJpYWJsZQogICAgXSwgVGZTbW9vdGhpbmdJbnB1dCk7CgogICAgLyogQ29weXJpZ2h0IDIwMTUgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgJ0xpY2Vuc2UnKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAnQVMgSVMnIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIEFkZCBxdWVyeSBwYXJhbWV0ZXJzIHRvIGEgVVJMLiBWYWx1ZXMgd2lsbCBiZSBVUkwtZW5jb2RlZC4gVGhlIFVSTAogICAgICogbWF5IG9yIG1heSBub3QgYWxyZWFkeSBoYXZlIHF1ZXJ5IHBhcmFtZXRlcnMuIEZvciBjb252ZW5pZW5jZSwKICAgICAqIHBhcmFtZXRlcnMgd2hvc2UgdmFsdWUgaXMgYHVuZGVmaW5lZGAgd2lsbCBiZSBkcm9wcGVkLgogICAgICoKICAgICAqIEZvciBleGFtcGxlLCB0aGUgZm9sbG93aW5nIGV4cHJlc3Npb25zIGFyZSBlcXVpdmFsZW50OgogICAgICoKICAgICAqICAgICBhZGRQYXJhbXMoImh0dHA6Ly9mb28iLCB7YTogIjEiLCBiOiBbIjIiLCAiMys0Il0sIGM6ICI1In0pCiAgICAgKiAgICAgYWRkUGFyYW1zKCJodHRwOi8vZm9vP2E9MSIsIHtiOiBbIjIiLCAiMys0Il0sIGM6ICI1IiwgZDogdW5kZWZpbmVkfSkKICAgICAqICAgICAiaHR0cDovL2Zvbz9hPTEmYj0yJmI9MyUyQjQmYz01IgogICAgICoKICAgICAqIEBkZXByZWNhdGVkIElmIHVzZWQgd2l0aCBgcm91dGVyLnBsdWdpblJvdXRlYCwgcGxlYXNlIHVzZSB0aGUgcXVlcnlQYXJhbXMKICAgICAqIGFyZ3VtZW50LgogICAgICovCiAgICBmdW5jdGlvbiBhZGRQYXJhbXMoYmFzZVVSTCwgcGFyYW1zKSB7CiAgICAgICAgY29uc3Qga2V5cyA9IE9iamVjdC5rZXlzKHBhcmFtcykKICAgICAgICAgICAgLnNvcnQoKQogICAgICAgICAgICAuZmlsdGVyKChrKSA9PiBwYXJhbXNba10gIT09IHVuZGVmaW5lZCk7CiAgICAgICAgaWYgKCFrZXlzLmxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gYmFzZVVSTDsgLy8gbm8gbmVlZCB0byBjaGFuZ2UgJy9mb28nIHRvICcvZm9vPycKICAgICAgICB9CiAgICAgICAgY29uc3QgZGVsaW1pdGVyID0gYmFzZVVSTC5pbmRleE9mKCc/JykgIT09IC0xID8gJyYnIDogJz8nOwogICAgICAgIGNvbnN0IHBhcnRzID0gW10uY29uY2F0KC4uLmtleXMubWFwKChrZXkpID0+IHsKICAgICAgICAgICAgY29uc3QgcmF3VmFsdWUgPSBwYXJhbXNba2V5XTsKICAgICAgICAgICAgY29uc3QgdmFsdWVzID0gQXJyYXkuaXNBcnJheShyYXdWYWx1ZSkgPyByYXdWYWx1ZSA6IFtyYXdWYWx1ZV07CiAgICAgICAgICAgIHJldHVybiB2YWx1ZXMubWFwKCh2YWx1ZSkgPT4gYCR7a2V5fT0ke19lbmNvZGVVUklDb21wb25lbnQodmFsdWUpfWApOwogICAgICAgIH0pKTsKICAgICAgICBjb25zdCBxdWVyeSA9IHBhcnRzLmpvaW4oJyYnKTsKICAgICAgICByZXR1cm4gYmFzZVVSTCArIGRlbGltaXRlciArIHF1ZXJ5OwogICAgfQogICAgZnVuY3Rpb24gX2VuY29kZVVSSUNvbXBvbmVudCh4KSB7CiAgICAgICAgLy8gUmVwbGFjZSBwYXJlbnRoZXNlcyBmb3IgY29uc2lzdGVuY3kgd2l0aCBQeXRob24ncyB1cmxsaWIudXJsZW5jb2RlLgogICAgICAgIHJldHVybiBlbmNvZGVVUklDb21wb25lbnQoeCkucmVwbGFjZSgvXCgvZywgJyUyOCcpLnJlcGxhY2UoL1wpL2csICclMjknKTsKICAgIH0KCiAgICAvKiEgKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioNCiAgICBDb3B5cmlnaHQgKGMpIE1pY3Jvc29mdCBDb3Jwb3JhdGlvbi4gQWxsIHJpZ2h0cyByZXNlcnZlZC4NCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBub3QgdXNlDQogICAgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUNCiAgICBMaWNlbnNlIGF0IGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMA0KDQogICAgVEhJUyBDT0RFIElTIFBST1ZJREVEIE9OIEFOICpBUyBJUyogQkFTSVMsIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWQ0KICAgIEtJTkQsIEVJVEhFUiBFWFBSRVNTIE9SIElNUExJRUQsIElOQ0xVRElORyBXSVRIT1VUIExJTUlUQVRJT04gQU5ZIElNUExJRUQNCiAgICBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgVElUTEUsIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFLA0KICAgIE1FUkNIQU5UQUJMSVRZIE9SIE5PTi1JTkZSSU5HRU1FTlQuDQoNCiAgICBTZWUgdGhlIEFwYWNoZSBWZXJzaW9uIDIuMCBMaWNlbnNlIGZvciBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMNCiAgICBhbmQgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuDQogICAgKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKiogKi8NCiAgICAvKiBnbG9iYWwgUmVmbGVjdCwgUHJvbWlzZSAqLw0KDQogICAgdmFyIGV4dGVuZFN0YXRpY3MgPSBPYmplY3Quc2V0UHJvdG90eXBlT2YgfHwNCiAgICAgICAgKHsgX19wcm90b19fOiBbXSB9IGluc3RhbmNlb2YgQXJyYXkgJiYgZnVuY3Rpb24gKGQsIGIpIHsgZC5fX3Byb3RvX18gPSBiOyB9KSB8fA0KICAgICAgICBmdW5jdGlvbiAoZCwgYikgeyBmb3IgKHZhciBwIGluIGIpIGlmIChiLmhhc093blByb3BlcnR5KHApKSBkW3BdID0gYltwXTsgfTsNCg0KICAgIGZ1bmN0aW9uIF9fZXh0ZW5kcyhkLCBiKSB7DQogICAgICAgIGV4dGVuZFN0YXRpY3MoZCwgYik7DQogICAgICAgIGZ1bmN0aW9uIF9fKCkgeyB0aGlzLmNvbnN0cnVjdG9yID0gZDsgfQ0KICAgICAgICBkLnByb3RvdHlwZSA9IGIgPT09IG51bGwgPyBPYmplY3QuY3JlYXRlKGIpIDogKF9fLnByb3RvdHlwZSA9IGIucHJvdG90eXBlLCBuZXcgX18oKSk7DQogICAgfQ0KDQogICAgdmFyIF9fYXNzaWduID0gT2JqZWN0LmFzc2lnbiB8fCBmdW5jdGlvbiBfX2Fzc2lnbih0KSB7DQogICAgICAgIGZvciAodmFyIHMsIGkgPSAxLCBuID0gYXJndW1lbnRzLmxlbmd0aDsgaSA8IG47IGkrKykgew0KICAgICAgICAgICAgcyA9IGFyZ3VtZW50c1tpXTsNCiAgICAgICAgICAgIGZvciAodmFyIHAgaW4gcykgaWYgKE9iamVjdC5wcm90b3R5cGUuaGFzT3duUHJvcGVydHkuY2FsbChzLCBwKSkgdFtwXSA9IHNbcF07DQogICAgICAgIH0NCiAgICAgICAgcmV0dXJuIHQ7DQogICAgfTsNCg0KICAgIGZ1bmN0aW9uIF9fcmVzdChzLCBlKSB7DQogICAgICAgIHZhciB0ID0ge307DQogICAgICAgIGZvciAodmFyIHAgaW4gcykgaWYgKE9iamVjdC5wcm90b3R5cGUuaGFzT3duUHJvcGVydHkuY2FsbChzLCBwKSAmJiBlLmluZGV4T2YocCkgPCAwKQ0KICAgICAgICAgICAgdFtwXSA9IHNbcF07DQogICAgICAgIGlmIChzICE9IG51bGwgJiYgdHlwZW9mIE9iamVjdC5nZXRPd25Qcm9wZXJ0eVN5bWJvbHMgPT09ICJmdW5jdGlvbiIpDQogICAgICAgICAgICBmb3IgKHZhciBpID0gMCwgcCA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eVN5bWJvbHMocyk7IGkgPCBwLmxlbmd0aDsgaSsrKSBpZiAoZS5pbmRleE9mKHBbaV0pIDwgMCkNCiAgICAgICAgICAgICAgICB0W3BbaV1dID0gc1twW2ldXTsNCiAgICAgICAgcmV0dXJuIHQ7DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19kZWNvcmF0ZSQxKGRlY29yYXRvcnMsIHRhcmdldCwga2V5LCBkZXNjKSB7DQogICAgICAgIHZhciBjID0gYXJndW1lbnRzLmxlbmd0aCwgciA9IGMgPCAzID8gdGFyZ2V0IDogZGVzYyA9PT0gbnVsbCA/IGRlc2MgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKHRhcmdldCwga2V5KSA6IGRlc2MsIGQ7DQogICAgICAgIGlmICh0eXBlb2YgUmVmbGVjdCA9PT0gIm9iamVjdCIgJiYgdHlwZW9mIFJlZmxlY3QuZGVjb3JhdGUgPT09ICJmdW5jdGlvbiIpIHIgPSBSZWZsZWN0LmRlY29yYXRlKGRlY29yYXRvcnMsIHRhcmdldCwga2V5LCBkZXNjKTsNCiAgICAgICAgZWxzZSBmb3IgKHZhciBpID0gZGVjb3JhdG9ycy5sZW5ndGggLSAxOyBpID49IDA7IGktLSkgaWYgKGQgPSBkZWNvcmF0b3JzW2ldKSByID0gKGMgPCAzID8gZChyKSA6IGMgPiAzID8gZCh0YXJnZXQsIGtleSwgcikgOiBkKHRhcmdldCwga2V5KSkgfHwgcjsNCiAgICAgICAgcmV0dXJuIGMgPiAzICYmIHIgJiYgT2JqZWN0LmRlZmluZVByb3BlcnR5KHRhcmdldCwga2V5LCByKSwgcjsNCiAgICB9DQoNCiAgICBmdW5jdGlvbiBfX3BhcmFtKHBhcmFtSW5kZXgsIGRlY29yYXRvcikgew0KICAgICAgICByZXR1cm4gZnVuY3Rpb24gKHRhcmdldCwga2V5KSB7IGRlY29yYXRvcih0YXJnZXQsIGtleSwgcGFyYW1JbmRleCk7IH0NCiAgICB9DQoNCiAgICBmdW5jdGlvbiBfX21ldGFkYXRhJDEobWV0YWRhdGFLZXksIG1ldGFkYXRhVmFsdWUpIHsNCiAgICAgICAgaWYgKHR5cGVvZiBSZWZsZWN0ID09PSAib2JqZWN0IiAmJiB0eXBlb2YgUmVmbGVjdC5tZXRhZGF0YSA9PT0gImZ1bmN0aW9uIikgcmV0dXJuIFJlZmxlY3QubWV0YWRhdGEobWV0YWRhdGFLZXksIG1ldGFkYXRhVmFsdWUpOw0KICAgIH0NCg0KICAgIGZ1bmN0aW9uIF9fYXdhaXRlciQxKHRoaXNBcmcsIF9hcmd1bWVudHMsIFAsIGdlbmVyYXRvcikgew0KICAgICAgICByZXR1cm4gbmV3IChQIHx8IChQID0gUHJvbWlzZSkpKGZ1bmN0aW9uIChyZXNvbHZlLCByZWplY3QpIHsNCiAgICAgICAgICAgIGZ1bmN0aW9uIGZ1bGZpbGxlZCh2YWx1ZSkgeyB0cnkgeyBzdGVwKGdlbmVyYXRvci5uZXh0KHZhbHVlKSk7IH0gY2F0Y2ggKGUpIHsgcmVqZWN0KGUpOyB9IH0NCiAgICAgICAgICAgIGZ1bmN0aW9uIHJlamVjdGVkKHZhbHVlKSB7IHRyeSB7IHN0ZXAoZ2VuZXJhdG9yWyJ0aHJvdyJdKHZhbHVlKSk7IH0gY2F0Y2ggKGUpIHsgcmVqZWN0KGUpOyB9IH0NCiAgICAgICAgICAgIGZ1bmN0aW9uIHN0ZXAocmVzdWx0KSB7IHJlc3VsdC5kb25lID8gcmVzb2x2ZShyZXN1bHQudmFsdWUpIDogbmV3IFAoZnVuY3Rpb24gKHJlc29sdmUpIHsgcmVzb2x2ZShyZXN1bHQudmFsdWUpOyB9KS50aGVuKGZ1bGZpbGxlZCwgcmVqZWN0ZWQpOyB9DQogICAgICAgICAgICBzdGVwKChnZW5lcmF0b3IgPSBnZW5lcmF0b3IuYXBwbHkodGhpc0FyZywgX2FyZ3VtZW50cyB8fCBbXSkpLm5leHQoKSk7DQogICAgICAgIH0pOw0KICAgIH0NCg0KICAgIGZ1bmN0aW9uIF9fZ2VuZXJhdG9yKHRoaXNBcmcsIGJvZHkpIHsNCiAgICAgICAgdmFyIF8gPSB7IGxhYmVsOiAwLCBzZW50OiBmdW5jdGlvbigpIHsgaWYgKHRbMF0gJiAxKSB0aHJvdyB0WzFdOyByZXR1cm4gdFsxXTsgfSwgdHJ5czogW10sIG9wczogW10gfSwgZiwgeSwgdCwgZzsNCiAgICAgICAgcmV0dXJuIGcgPSB7IG5leHQ6IHZlcmIoMCksICJ0aHJvdyI6IHZlcmIoMSksICJyZXR1cm4iOiB2ZXJiKDIpIH0sIHR5cGVvZiBTeW1ib2wgPT09ICJmdW5jdGlvbiIgJiYgKGdbU3ltYm9sLml0ZXJhdG9yXSA9IGZ1bmN0aW9uKCkgeyByZXR1cm4gdGhpczsgfSksIGc7DQogICAgICAgIGZ1bmN0aW9uIHZlcmIobikgeyByZXR1cm4gZnVuY3Rpb24gKHYpIHsgcmV0dXJuIHN0ZXAoW24sIHZdKTsgfTsgfQ0KICAgICAgICBmdW5jdGlvbiBzdGVwKG9wKSB7DQogICAgICAgICAgICBpZiAoZikgdGhyb3cgbmV3IFR5cGVFcnJvcigiR2VuZXJhdG9yIGlzIGFscmVhZHkgZXhlY3V0aW5nLiIpOw0KICAgICAgICAgICAgd2hpbGUgKF8pIHRyeSB7DQogICAgICAgICAgICAgICAgaWYgKGYgPSAxLCB5ICYmICh0ID0geVtvcFswXSAmIDIgPyAicmV0dXJuIiA6IG9wWzBdID8gInRocm93IiA6ICJuZXh0Il0pICYmICEodCA9IHQuY2FsbCh5LCBvcFsxXSkpLmRvbmUpIHJldHVybiB0Ow0KICAgICAgICAgICAgICAgIGlmICh5ID0gMCwgdCkgb3AgPSBbMCwgdC52YWx1ZV07DQogICAgICAgICAgICAgICAgc3dpdGNoIChvcFswXSkgew0KICAgICAgICAgICAgICAgICAgICBjYXNlIDA6IGNhc2UgMTogdCA9IG9wOyBicmVhazsNCiAgICAgICAgICAgICAgICAgICAgY2FzZSA0OiBfLmxhYmVsKys7IHJldHVybiB7IHZhbHVlOiBvcFsxXSwgZG9uZTogZmFsc2UgfTsNCiAgICAgICAgICAgICAgICAgICAgY2FzZSA1OiBfLmxhYmVsKys7IHkgPSBvcFsxXTsgb3AgPSBbMF07IGNvbnRpbnVlOw0KICAgICAgICAgICAgICAgICAgICBjYXNlIDc6IG9wID0gXy5vcHMucG9wKCk7IF8udHJ5cy5wb3AoKTsgY29udGludWU7DQogICAgICAgICAgICAgICAgICAgIGRlZmF1bHQ6DQogICAgICAgICAgICAgICAgICAgICAgICBpZiAoISh0ID0gXy50cnlzLCB0ID0gdC5sZW5ndGggPiAwICYmIHRbdC5sZW5ndGggLSAxXSkgJiYgKG9wWzBdID09PSA2IHx8IG9wWzBdID09PSAyKSkgeyBfID0gMDsgY29udGludWU7IH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChvcFswXSA9PT0gMyAmJiAoIXQgfHwgKG9wWzFdID4gdFswXSAmJiBvcFsxXSA8IHRbM10pKSkgeyBfLmxhYmVsID0gb3BbMV07IGJyZWFrOyB9DQogICAgICAgICAgICAgICAgICAgICAgICBpZiAob3BbMF0gPT09IDYgJiYgXy5sYWJlbCA8IHRbMV0pIHsgXy5sYWJlbCA9IHRbMV07IHQgPSBvcDsgYnJlYWs7IH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGlmICh0ICYmIF8ubGFiZWwgPCB0WzJdKSB7IF8ubGFiZWwgPSB0WzJdOyBfLm9wcy5wdXNoKG9wKTsgYnJlYWs7IH0NCiAgICAgICAgICAgICAgICAgICAgICAgIGlmICh0WzJdKSBfLm9wcy5wb3AoKTsNCiAgICAgICAgICAgICAgICAgICAgICAgIF8udHJ5cy5wb3AoKTsgY29udGludWU7DQogICAgICAgICAgICAgICAgfQ0KICAgICAgICAgICAgICAgIG9wID0gYm9keS5jYWxsKHRoaXNBcmcsIF8pOw0KICAgICAgICAgICAgfSBjYXRjaCAoZSkgeyBvcCA9IFs2LCBlXTsgeSA9IDA7IH0gZmluYWxseSB7IGYgPSB0ID0gMDsgfQ0KICAgICAgICAgICAgaWYgKG9wWzBdICYgNSkgdGhyb3cgb3BbMV07IHJldHVybiB7IHZhbHVlOiBvcFswXSA/IG9wWzFdIDogdm9pZCAwLCBkb25lOiB0cnVlIH07DQogICAgICAgIH0NCiAgICB9DQoNCiAgICBmdW5jdGlvbiBfX2V4cG9ydFN0YXIobSwgZXhwb3J0cykgew0KICAgICAgICBmb3IgKHZhciBwIGluIG0pIGlmICghZXhwb3J0cy5oYXNPd25Qcm9wZXJ0eShwKSkgZXhwb3J0c1twXSA9IG1bcF07DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX192YWx1ZXMobykgew0KICAgICAgICB2YXIgbSA9IHR5cGVvZiBTeW1ib2wgPT09ICJmdW5jdGlvbiIgJiYgb1tTeW1ib2wuaXRlcmF0b3JdLCBpID0gMDsNCiAgICAgICAgaWYgKG0pIHJldHVybiBtLmNhbGwobyk7DQogICAgICAgIHJldHVybiB7DQogICAgICAgICAgICBuZXh0OiBmdW5jdGlvbiAoKSB7DQogICAgICAgICAgICAgICAgaWYgKG8gJiYgaSA+PSBvLmxlbmd0aCkgbyA9IHZvaWQgMDsNCiAgICAgICAgICAgICAgICByZXR1cm4geyB2YWx1ZTogbyAmJiBvW2krK10sIGRvbmU6ICFvIH07DQogICAgICAgICAgICB9DQogICAgICAgIH07DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19yZWFkKG8sIG4pIHsNCiAgICAgICAgdmFyIG0gPSB0eXBlb2YgU3ltYm9sID09PSAiZnVuY3Rpb24iICYmIG9bU3ltYm9sLml0ZXJhdG9yXTsNCiAgICAgICAgaWYgKCFtKSByZXR1cm4gbzsNCiAgICAgICAgdmFyIGkgPSBtLmNhbGwobyksIHIsIGFyID0gW10sIGU7DQogICAgICAgIHRyeSB7DQogICAgICAgICAgICB3aGlsZSAoKG4gPT09IHZvaWQgMCB8fCBuLS0gPiAwKSAmJiAhKHIgPSBpLm5leHQoKSkuZG9uZSkgYXIucHVzaChyLnZhbHVlKTsNCiAgICAgICAgfQ0KICAgICAgICBjYXRjaCAoZXJyb3IpIHsgZSA9IHsgZXJyb3I6IGVycm9yIH07IH0NCiAgICAgICAgZmluYWxseSB7DQogICAgICAgICAgICB0cnkgew0KICAgICAgICAgICAgICAgIGlmIChyICYmICFyLmRvbmUgJiYgKG0gPSBpWyJyZXR1cm4iXSkpIG0uY2FsbChpKTsNCiAgICAgICAgICAgIH0NCiAgICAgICAgICAgIGZpbmFsbHkgeyBpZiAoZSkgdGhyb3cgZS5lcnJvcjsgfQ0KICAgICAgICB9DQogICAgICAgIHJldHVybiBhcjsNCiAgICB9DQoNCiAgICBmdW5jdGlvbiBfX3NwcmVhZCgpIHsNCiAgICAgICAgZm9yICh2YXIgYXIgPSBbXSwgaSA9IDA7IGkgPCBhcmd1bWVudHMubGVuZ3RoOyBpKyspDQogICAgICAgICAgICBhciA9IGFyLmNvbmNhdChfX3JlYWQoYXJndW1lbnRzW2ldKSk7DQogICAgICAgIHJldHVybiBhcjsNCiAgICB9DQoNCiAgICBmdW5jdGlvbiBfX2F3YWl0KHYpIHsNCiAgICAgICAgcmV0dXJuIHRoaXMgaW5zdGFuY2VvZiBfX2F3YWl0ID8gKHRoaXMudiA9IHYsIHRoaXMpIDogbmV3IF9fYXdhaXQodik7DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19hc3luY0dlbmVyYXRvcih0aGlzQXJnLCBfYXJndW1lbnRzLCBnZW5lcmF0b3IpIHsNCiAgICAgICAgaWYgKCFTeW1ib2wuYXN5bmNJdGVyYXRvcikgdGhyb3cgbmV3IFR5cGVFcnJvcigiU3ltYm9sLmFzeW5jSXRlcmF0b3IgaXMgbm90IGRlZmluZWQuIik7DQogICAgICAgIHZhciBnID0gZ2VuZXJhdG9yLmFwcGx5KHRoaXNBcmcsIF9hcmd1bWVudHMgfHwgW10pLCBpLCBxID0gW107DQogICAgICAgIHJldHVybiBpID0ge30sIHZlcmIoIm5leHQiKSwgdmVyYigidGhyb3ciKSwgdmVyYigicmV0dXJuIiksIGlbU3ltYm9sLmFzeW5jSXRlcmF0b3JdID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gdGhpczsgfSwgaTsNCiAgICAgICAgZnVuY3Rpb24gdmVyYihuKSB7IGlmIChnW25dKSBpW25dID0gZnVuY3Rpb24gKHYpIHsgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uIChhLCBiKSB7IHEucHVzaChbbiwgdiwgYSwgYl0pID4gMSB8fCByZXN1bWUobiwgdik7IH0pOyB9OyB9DQogICAgICAgIGZ1bmN0aW9uIHJlc3VtZShuLCB2KSB7IHRyeSB7IHN0ZXAoZ1tuXSh2KSk7IH0gY2F0Y2ggKGUpIHsgc2V0dGxlKHFbMF1bM10sIGUpOyB9IH0NCiAgICAgICAgZnVuY3Rpb24gc3RlcChyKSB7IHIudmFsdWUgaW5zdGFuY2VvZiBfX2F3YWl0ID8gUHJvbWlzZS5yZXNvbHZlKHIudmFsdWUudikudGhlbihmdWxmaWxsLCByZWplY3QpIDogc2V0dGxlKHFbMF1bMl0sIHIpOyAgfQ0KICAgICAgICBmdW5jdGlvbiBmdWxmaWxsKHZhbHVlKSB7IHJlc3VtZSgibmV4dCIsIHZhbHVlKTsgfQ0KICAgICAgICBmdW5jdGlvbiByZWplY3QodmFsdWUpIHsgcmVzdW1lKCJ0aHJvdyIsIHZhbHVlKTsgfQ0KICAgICAgICBmdW5jdGlvbiBzZXR0bGUoZiwgdikgeyBpZiAoZih2KSwgcS5zaGlmdCgpLCBxLmxlbmd0aCkgcmVzdW1lKHFbMF1bMF0sIHFbMF1bMV0pOyB9DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19hc3luY0RlbGVnYXRvcihvKSB7DQogICAgICAgIHZhciBpLCBwOw0KICAgICAgICByZXR1cm4gaSA9IHt9LCB2ZXJiKCJuZXh0IiksIHZlcmIoInRocm93IiwgZnVuY3Rpb24gKGUpIHsgdGhyb3cgZTsgfSksIHZlcmIoInJldHVybiIpLCBpW1N5bWJvbC5pdGVyYXRvcl0gPSBmdW5jdGlvbiAoKSB7IHJldHVybiB0aGlzOyB9LCBpOw0KICAgICAgICBmdW5jdGlvbiB2ZXJiKG4sIGYpIHsgaWYgKG9bbl0pIGlbbl0gPSBmdW5jdGlvbiAodikgeyByZXR1cm4gKHAgPSAhcCkgPyB7IHZhbHVlOiBfX2F3YWl0KG9bbl0odikpLCBkb25lOiBuID09PSAicmV0dXJuIiB9IDogZiA/IGYodikgOiB2OyB9OyB9DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19hc3luY1ZhbHVlcyhvKSB7DQogICAgICAgIGlmICghU3ltYm9sLmFzeW5jSXRlcmF0b3IpIHRocm93IG5ldyBUeXBlRXJyb3IoIlN5bWJvbC5hc3luY0l0ZXJhdG9yIGlzIG5vdCBkZWZpbmVkLiIpOw0KICAgICAgICB2YXIgbSA9IG9bU3ltYm9sLmFzeW5jSXRlcmF0b3JdOw0KICAgICAgICByZXR1cm4gbSA/IG0uY2FsbChvKSA6IHR5cGVvZiBfX3ZhbHVlcyA9PT0gImZ1bmN0aW9uIiA/IF9fdmFsdWVzKG8pIDogb1tTeW1ib2wuaXRlcmF0b3JdKCk7DQogICAgfQ0KDQogICAgZnVuY3Rpb24gX19tYWtlVGVtcGxhdGVPYmplY3QoY29va2VkLCByYXcpIHsNCiAgICAgICAgaWYgKE9iamVjdC5kZWZpbmVQcm9wZXJ0eSkgeyBPYmplY3QuZGVmaW5lUHJvcGVydHkoY29va2VkLCAicmF3IiwgeyB2YWx1ZTogcmF3IH0pOyB9IGVsc2UgeyBjb29rZWQucmF3ID0gcmF3OyB9DQogICAgICAgIHJldHVybiBjb29rZWQ7DQogICAgfQoKICAgIHZhciB0c2xpYl9lczYgPSAvKiNfX1BVUkVfXyovT2JqZWN0LmZyZWV6ZSh7CiAgICAgICAgX19wcm90b19fOiBudWxsLAogICAgICAgIF9fZXh0ZW5kczogX19leHRlbmRzLAogICAgICAgIF9fYXNzaWduOiBfX2Fzc2lnbiwKICAgICAgICBfX3Jlc3Q6IF9fcmVzdCwKICAgICAgICBfX2RlY29yYXRlOiBfX2RlY29yYXRlJDEsCiAgICAgICAgX19wYXJhbTogX19wYXJhbSwKICAgICAgICBfX21ldGFkYXRhOiBfX21ldGFkYXRhJDEsCiAgICAgICAgX19hd2FpdGVyOiBfX2F3YWl0ZXIkMSwKICAgICAgICBfX2dlbmVyYXRvcjogX19nZW5lcmF0b3IsCiAgICAgICAgX19leHBvcnRTdGFyOiBfX2V4cG9ydFN0YXIsCiAgICAgICAgX192YWx1ZXM6IF9fdmFsdWVzLAogICAgICAgIF9fcmVhZDogX19yZWFkLAogICAgICAgIF9fc3ByZWFkOiBfX3NwcmVhZCwKICAgICAgICBfX2F3YWl0OiBfX2F3YWl0LAogICAgICAgIF9fYXN5bmNHZW5lcmF0b3I6IF9fYXN5bmNHZW5lcmF0b3IsCiAgICAgICAgX19hc3luY0RlbGVnYXRvcjogX19hc3luY0RlbGVnYXRvciwKICAgICAgICBfX2FzeW5jVmFsdWVzOiBfX2FzeW5jVmFsdWVzLAogICAgICAgIF9fbWFrZVRlbXBsYXRlT2JqZWN0OiBfX21ha2VUZW1wbGF0ZU9iamVjdAogICAgfSk7CgogICAgdmFyIHZlcnNpb24kMiA9ICI0LjEzLjAiOwoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyQ0KGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPCBiID8gLTEgOiBhID4gYiA/IDEgOiBhID49IGIgPyAwIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGJpc2VjdG9yJDEoY29tcGFyZSkgewogICAgICBpZiAoY29tcGFyZS5sZW5ndGggPT09IDEpIGNvbXBhcmUgPSBhc2NlbmRpbmdDb21wYXJhdG9yJDEoY29tcGFyZSk7CiAgICAgIHJldHVybiB7CiAgICAgICAgbGVmdDogZnVuY3Rpb24oYSwgeCwgbG8sIGhpKSB7CiAgICAgICAgICBpZiAobG8gPT0gbnVsbCkgbG8gPSAwOwogICAgICAgICAgaWYgKGhpID09IG51bGwpIGhpID0gYS5sZW5ndGg7CiAgICAgICAgICB3aGlsZSAobG8gPCBoaSkgewogICAgICAgICAgICB2YXIgbWlkID0gbG8gKyBoaSA+Pj4gMTsKICAgICAgICAgICAgaWYgKGNvbXBhcmUoYVttaWRdLCB4KSA8IDApIGxvID0gbWlkICsgMTsKICAgICAgICAgICAgZWxzZSBoaSA9IG1pZDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBsbzsKICAgICAgICB9LAogICAgICAgIHJpZ2h0OiBmdW5jdGlvbihhLCB4LCBsbywgaGkpIHsKICAgICAgICAgIGlmIChsbyA9PSBudWxsKSBsbyA9IDA7CiAgICAgICAgICBpZiAoaGkgPT0gbnVsbCkgaGkgPSBhLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChsbyA8IGhpKSB7CiAgICAgICAgICAgIHZhciBtaWQgPSBsbyArIGhpID4+PiAxOwogICAgICAgICAgICBpZiAoY29tcGFyZShhW21pZF0sIHgpID4gMCkgaGkgPSBtaWQ7CiAgICAgICAgICAgIGVsc2UgbG8gPSBtaWQgKyAxOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGxvOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2NlbmRpbmdDb21wYXJhdG9yJDEoZikgewogICAgICByZXR1cm4gZnVuY3Rpb24oZCwgeCkgewogICAgICAgIHJldHVybiBhc2NlbmRpbmckNChmKGQpLCB4KTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgYXNjZW5kaW5nQmlzZWN0JDEgPSBiaXNlY3RvciQxKGFzY2VuZGluZyQ0KTsKICAgIHZhciBiaXNlY3RSaWdodCQxID0gYXNjZW5kaW5nQmlzZWN0JDEucmlnaHQ7CiAgICB2YXIgYmlzZWN0TGVmdCQxID0gYXNjZW5kaW5nQmlzZWN0JDEubGVmdDsKCiAgICBmdW5jdGlvbiBwYWlycyQxKGFycmF5LCBmKSB7CiAgICAgIGlmIChmID09IG51bGwpIGYgPSBwYWlyJDE7CiAgICAgIHZhciBpID0gMCwgbiA9IGFycmF5Lmxlbmd0aCAtIDEsIHAgPSBhcnJheVswXSwgcGFpcnMgPSBuZXcgQXJyYXkobiA8IDAgPyAwIDogbik7CiAgICAgIHdoaWxlIChpIDwgbikgcGFpcnNbaV0gPSBmKHAsIHAgPSBhcnJheVsrK2ldKTsKICAgICAgcmV0dXJuIHBhaXJzOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhaXIkMShhLCBiKSB7CiAgICAgIHJldHVybiBbYSwgYl07CiAgICB9CgogICAgZnVuY3Rpb24gY3Jvc3MkMyh2YWx1ZXMwLCB2YWx1ZXMxLCByZWR1Y2UpIHsKICAgICAgdmFyIG4wID0gdmFsdWVzMC5sZW5ndGgsCiAgICAgICAgICBuMSA9IHZhbHVlczEubGVuZ3RoLAogICAgICAgICAgdmFsdWVzID0gbmV3IEFycmF5KG4wICogbjEpLAogICAgICAgICAgaTAsCiAgICAgICAgICBpMSwKICAgICAgICAgIGksCiAgICAgICAgICB2YWx1ZTA7CgogICAgICBpZiAocmVkdWNlID09IG51bGwpIHJlZHVjZSA9IHBhaXIkMTsKCiAgICAgIGZvciAoaTAgPSBpID0gMDsgaTAgPCBuMDsgKytpMCkgewogICAgICAgIGZvciAodmFsdWUwID0gdmFsdWVzMFtpMF0sIGkxID0gMDsgaTEgPCBuMTsgKytpMSwgKytpKSB7CiAgICAgICAgICB2YWx1ZXNbaV0gPSByZWR1Y2UodmFsdWUwLCB2YWx1ZXMxW2kxXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gdmFsdWVzOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlc2NlbmRpbmckMyhhLCBiKSB7CiAgICAgIHJldHVybiBiIDwgYSA/IC0xIDogYiA+IGEgPyAxIDogYiA+PSBhID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBudW1iZXIkNCh4KSB7CiAgICAgIHJldHVybiB4ID09PSBudWxsID8gTmFOIDogK3g7CiAgICB9CgogICAgZnVuY3Rpb24gdmFyaWFuY2UkMSh2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgbSA9IDAsCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICBtZWFuID0gMCwKICAgICAgICAgIHZhbHVlLAogICAgICAgICAgZGVsdGEsCiAgICAgICAgICBzdW0gPSAwOwoKICAgICAgaWYgKHZhbHVlb2YgPT0gbnVsbCkgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyJDQodmFsdWVzW2ldKSkpIHsKICAgICAgICAgICAgZGVsdGEgPSB2YWx1ZSAtIG1lYW47CiAgICAgICAgICAgIG1lYW4gKz0gZGVsdGEgLyArK207CiAgICAgICAgICAgIHN1bSArPSBkZWx0YSAqICh2YWx1ZSAtIG1lYW4pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZWxzZSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICghaXNOYU4odmFsdWUgPSBudW1iZXIkNCh2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkpKSB7CiAgICAgICAgICAgIGRlbHRhID0gdmFsdWUgLSBtZWFuOwogICAgICAgICAgICBtZWFuICs9IGRlbHRhIC8gKyttOwogICAgICAgICAgICBzdW0gKz0gZGVsdGEgKiAodmFsdWUgLSBtZWFuKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGlmIChtID4gMSkgcmV0dXJuIHN1bSAvIChtIC0gMSk7CiAgICB9CgogICAgZnVuY3Rpb24gZGV2aWF0aW9uJDEoYXJyYXksIGYpIHsKICAgICAgdmFyIHYgPSB2YXJpYW5jZSQxKGFycmF5LCBmKTsKICAgICAgcmV0dXJuIHYgPyBNYXRoLnNxcnQodikgOiB2OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVudCQyKHZhbHVlcywgdmFsdWVvZikgewogICAgICB2YXIgbiA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICB2YWx1ZSwKICAgICAgICAgIG1pbiwKICAgICAgICAgIG1heDsKCiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCAmJiB2YWx1ZSA+PSB2YWx1ZSkgewogICAgICAgICAgICBtaW4gPSBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gQ29tcGFyZSB0aGUgcmVtYWluaW5nIHZhbHVlcy4KICAgICAgICAgICAgICBpZiAoKHZhbHVlID0gdmFsdWVzW2ldKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBpZiAobWluID4gdmFsdWUpIG1pbiA9IHZhbHVlOwogICAgICAgICAgICAgICAgaWYgKG1heCA8IHZhbHVlKSBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIEZpbmQgdGhlIGZpcnN0IGNvbXBhcmFibGUgdmFsdWUuCiAgICAgICAgICBpZiAoKHZhbHVlID0gdmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWluID0gbWF4ID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBpZiAobWluID4gdmFsdWUpIG1pbiA9IHZhbHVlOwogICAgICAgICAgICAgICAgaWYgKG1heCA8IHZhbHVlKSBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBbbWluLCBtYXhdOwogICAgfQoKICAgIHZhciBhcnJheSQ0ID0gQXJyYXkucHJvdG90eXBlOwoKICAgIHZhciBzbGljZSQ3ID0gYXJyYXkkNC5zbGljZTsKICAgIHZhciBtYXAkNCA9IGFycmF5JDQubWFwOwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGUoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaWRlbnRpdHkkYSh4KSB7CiAgICAgIHJldHVybiB4OwogICAgfQoKICAgIGZ1bmN0aW9uIHJhbmdlJDEoc3RhcnQsIHN0b3AsIHN0ZXApIHsKICAgICAgc3RhcnQgPSArc3RhcnQsIHN0b3AgPSArc3RvcCwgc3RlcCA9IChuID0gYXJndW1lbnRzLmxlbmd0aCkgPCAyID8gKHN0b3AgPSBzdGFydCwgc3RhcnQgPSAwLCAxKSA6IG4gPCAzID8gMSA6ICtzdGVwOwoKICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgIG4gPSBNYXRoLm1heCgwLCBNYXRoLmNlaWwoKHN0b3AgLSBzdGFydCkgLyBzdGVwKSkgfCAwLAogICAgICAgICAgcmFuZ2UgPSBuZXcgQXJyYXkobik7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIHJhbmdlW2ldID0gc3RhcnQgKyBpICogc3RlcDsKICAgICAgfQoKICAgICAgcmV0dXJuIHJhbmdlOwogICAgfQoKICAgIHZhciBlMTAkMSA9IE1hdGguc3FydCg1MCksCiAgICAgICAgZTUkMSA9IE1hdGguc3FydCgxMCksCiAgICAgICAgZTIkMSA9IE1hdGguc3FydCgyKTsKCiAgICBmdW5jdGlvbiB0aWNrcyQxKHN0YXJ0LCBzdG9wLCBjb3VudCkgewogICAgICB2YXIgcmV2ZXJzZSwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIG4sCiAgICAgICAgICB0aWNrcywKICAgICAgICAgIHN0ZXA7CgogICAgICBzdG9wID0gK3N0b3AsIHN0YXJ0ID0gK3N0YXJ0LCBjb3VudCA9ICtjb3VudDsKICAgICAgaWYgKHN0YXJ0ID09PSBzdG9wICYmIGNvdW50ID4gMCkgcmV0dXJuIFtzdGFydF07CiAgICAgIGlmIChyZXZlcnNlID0gc3RvcCA8IHN0YXJ0KSBuID0gc3RhcnQsIHN0YXJ0ID0gc3RvcCwgc3RvcCA9IG47CiAgICAgIGlmICgoc3RlcCA9IHRpY2tJbmNyZW1lbnQkMShzdGFydCwgc3RvcCwgY291bnQpKSA9PT0gMCB8fCAhaXNGaW5pdGUoc3RlcCkpIHJldHVybiBbXTsKCiAgICAgIGlmIChzdGVwID4gMCkgewogICAgICAgIHN0YXJ0ID0gTWF0aC5jZWlsKHN0YXJ0IC8gc3RlcCk7CiAgICAgICAgc3RvcCA9IE1hdGguZmxvb3Ioc3RvcCAvIHN0ZXApOwogICAgICAgIHRpY2tzID0gbmV3IEFycmF5KG4gPSBNYXRoLmNlaWwoc3RvcCAtIHN0YXJ0ICsgMSkpOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSB0aWNrc1tpXSA9IChzdGFydCArIGkpICogc3RlcDsKICAgICAgfSBlbHNlIHsKICAgICAgICBzdGFydCA9IE1hdGguZmxvb3Ioc3RhcnQgKiBzdGVwKTsKICAgICAgICBzdG9wID0gTWF0aC5jZWlsKHN0b3AgKiBzdGVwKTsKICAgICAgICB0aWNrcyA9IG5ldyBBcnJheShuID0gTWF0aC5jZWlsKHN0YXJ0IC0gc3RvcCArIDEpKTsKICAgICAgICB3aGlsZSAoKytpIDwgbikgdGlja3NbaV0gPSAoc3RhcnQgLSBpKSAvIHN0ZXA7CiAgICAgIH0KCiAgICAgIGlmIChyZXZlcnNlKSB0aWNrcy5yZXZlcnNlKCk7CgogICAgICByZXR1cm4gdGlja3M7CiAgICB9CgogICAgZnVuY3Rpb24gdGlja0luY3JlbWVudCQxKHN0YXJ0LCBzdG9wLCBjb3VudCkgewogICAgICB2YXIgc3RlcCA9IChzdG9wIC0gc3RhcnQpIC8gTWF0aC5tYXgoMCwgY291bnQpLAogICAgICAgICAgcG93ZXIgPSBNYXRoLmZsb29yKE1hdGgubG9nKHN0ZXApIC8gTWF0aC5MTjEwKSwKICAgICAgICAgIGVycm9yID0gc3RlcCAvIE1hdGgucG93KDEwLCBwb3dlcik7CiAgICAgIHJldHVybiBwb3dlciA+PSAwCiAgICAgICAgICA/IChlcnJvciA+PSBlMTAkMSA/IDEwIDogZXJyb3IgPj0gZTUkMSA/IDUgOiBlcnJvciA+PSBlMiQxID8gMiA6IDEpICogTWF0aC5wb3coMTAsIHBvd2VyKQogICAgICAgICAgOiAtTWF0aC5wb3coMTAsIC1wb3dlcikgLyAoZXJyb3IgPj0gZTEwJDEgPyAxMCA6IGVycm9yID49IGU1JDEgPyA1IDogZXJyb3IgPj0gZTIkMSA/IDIgOiAxKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aWNrU3RlcCQxKHN0YXJ0LCBzdG9wLCBjb3VudCkgewogICAgICB2YXIgc3RlcDAgPSBNYXRoLmFicyhzdG9wIC0gc3RhcnQpIC8gTWF0aC5tYXgoMCwgY291bnQpLAogICAgICAgICAgc3RlcDEgPSBNYXRoLnBvdygxMCwgTWF0aC5mbG9vcihNYXRoLmxvZyhzdGVwMCkgLyBNYXRoLkxOMTApKSwKICAgICAgICAgIGVycm9yID0gc3RlcDAgLyBzdGVwMTsKICAgICAgaWYgKGVycm9yID49IGUxMCQxKSBzdGVwMSAqPSAxMDsKICAgICAgZWxzZSBpZiAoZXJyb3IgPj0gZTUkMSkgc3RlcDEgKj0gNTsKICAgICAgZWxzZSBpZiAoZXJyb3IgPj0gZTIkMSkgc3RlcDEgKj0gMjsKICAgICAgcmV0dXJuIHN0b3AgPCBzdGFydCA/IC1zdGVwMSA6IHN0ZXAxOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0dXJnZXModmFsdWVzKSB7CiAgICAgIHJldHVybiBNYXRoLmNlaWwoTWF0aC5sb2codmFsdWVzLmxlbmd0aCkgLyBNYXRoLkxOMikgKyAxOwogICAgfQoKICAgIGZ1bmN0aW9uIGhpc3RvZ3JhbSQxKCkgewogICAgICB2YXIgdmFsdWUgPSBpZGVudGl0eSRhLAogICAgICAgICAgZG9tYWluID0gZXh0ZW50JDIsCiAgICAgICAgICB0aHJlc2hvbGQgPSBzdHVyZ2VzOwoKICAgICAgZnVuY3Rpb24gaGlzdG9ncmFtKGRhdGEpIHsKICAgICAgICB2YXIgaSwKICAgICAgICAgICAgbiA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICB4LAogICAgICAgICAgICB2YWx1ZXMgPSBuZXcgQXJyYXkobik7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHZhbHVlc1tpXSA9IHZhbHVlKGRhdGFbaV0sIGksIGRhdGEpOwogICAgICAgIH0KCiAgICAgICAgdmFyIHh6ID0gZG9tYWluKHZhbHVlcyksCiAgICAgICAgICAgIHgwID0geHpbMF0sCiAgICAgICAgICAgIHgxID0geHpbMV0sCiAgICAgICAgICAgIHR6ID0gdGhyZXNob2xkKHZhbHVlcywgeDAsIHgxKTsKCiAgICAgICAgLy8gQ29udmVydCBudW1iZXIgb2YgdGhyZXNob2xkcyBpbnRvIHVuaWZvcm0gdGhyZXNob2xkcy4KICAgICAgICBpZiAoIUFycmF5LmlzQXJyYXkodHopKSB7CiAgICAgICAgICB0eiA9IHRpY2tTdGVwJDEoeDAsIHgxLCB0eik7CiAgICAgICAgICB0eiA9IHJhbmdlJDEoTWF0aC5jZWlsKHgwIC8gdHopICogdHosIE1hdGguZmxvb3IoeDEgLyB0eikgKiB0eiwgdHopOyAvLyBleGNsdXNpdmUKICAgICAgICB9CgogICAgICAgIC8vIFJlbW92ZSBhbnkgdGhyZXNob2xkcyBvdXRzaWRlIHRoZSBkb21haW4uCiAgICAgICAgdmFyIG0gPSB0ei5sZW5ndGg7CiAgICAgICAgd2hpbGUgKHR6WzBdIDw9IHgwKSB0ei5zaGlmdCgpLCAtLW07CiAgICAgICAgd2hpbGUgKHR6W20gLSAxXSA+IHgxKSB0ei5wb3AoKSwgLS1tOwoKICAgICAgICB2YXIgYmlucyA9IG5ldyBBcnJheShtICsgMSksCiAgICAgICAgICAgIGJpbjsKCiAgICAgICAgLy8gSW5pdGlhbGl6ZSBiaW5zLgogICAgICAgIGZvciAoaSA9IDA7IGkgPD0gbTsgKytpKSB7CiAgICAgICAgICBiaW4gPSBiaW5zW2ldID0gW107CiAgICAgICAgICBiaW4ueDAgPSBpID4gMCA/IHR6W2kgLSAxXSA6IHgwOwogICAgICAgICAgYmluLngxID0gaSA8IG0gPyB0eltpXSA6IHgxOwogICAgICAgIH0KCiAgICAgICAgLy8gQXNzaWduIGRhdGEgdG8gYmlucyBieSB2YWx1ZSwgaWdub3JpbmcgYW55IG91dHNpZGUgdGhlIGRvbWFpbi4KICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB4ID0gdmFsdWVzW2ldOwogICAgICAgICAgaWYgKHgwIDw9IHggJiYgeCA8PSB4MSkgewogICAgICAgICAgICBiaW5zW2Jpc2VjdFJpZ2h0JDEodHosIHgsIDAsIG0pXS5wdXNoKGRhdGFbaV0pOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIGJpbnM7CiAgICAgIH0KCiAgICAgIGhpc3RvZ3JhbS52YWx1ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh2YWx1ZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGUoXyksIGhpc3RvZ3JhbSkgOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIGhpc3RvZ3JhbS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkZShbX1swXSwgX1sxXV0pLCBoaXN0b2dyYW0pIDogZG9tYWluOwogICAgICB9OwoKICAgICAgaGlzdG9ncmFtLnRocmVzaG9sZHMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGhyZXNob2xkID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogQXJyYXkuaXNBcnJheShfKSA/IGNvbnN0YW50JGUoc2xpY2UkNy5jYWxsKF8pKSA6IGNvbnN0YW50JGUoXyksIGhpc3RvZ3JhbSkgOiB0aHJlc2hvbGQ7CiAgICAgIH07CgogICAgICByZXR1cm4gaGlzdG9ncmFtOwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YW50aWxlJDEodmFsdWVzLCBwLCB2YWx1ZW9mKSB7CiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHZhbHVlb2YgPSBudW1iZXIkNDsKICAgICAgaWYgKCEobiA9IHZhbHVlcy5sZW5ndGgpKSByZXR1cm47CiAgICAgIGlmICgocCA9ICtwKSA8PSAwIHx8IG4gPCAyKSByZXR1cm4gK3ZhbHVlb2YodmFsdWVzWzBdLCAwLCB2YWx1ZXMpOwogICAgICBpZiAocCA+PSAxKSByZXR1cm4gK3ZhbHVlb2YodmFsdWVzW24gLSAxXSwgbiAtIDEsIHZhbHVlcyk7CiAgICAgIHZhciBuLAogICAgICAgICAgaSA9IChuIC0gMSkgKiBwLAogICAgICAgICAgaTAgPSBNYXRoLmZsb29yKGkpLAogICAgICAgICAgdmFsdWUwID0gK3ZhbHVlb2YodmFsdWVzW2kwXSwgaTAsIHZhbHVlcyksCiAgICAgICAgICB2YWx1ZTEgPSArdmFsdWVvZih2YWx1ZXNbaTAgKyAxXSwgaTAgKyAxLCB2YWx1ZXMpOwogICAgICByZXR1cm4gdmFsdWUwICsgKHZhbHVlMSAtIHZhbHVlMCkgKiAoaSAtIGkwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmcmVlZG1hbkRpYWNvbmlzJDEodmFsdWVzLCBtaW4sIG1heCkgewogICAgICB2YWx1ZXMgPSBtYXAkNC5jYWxsKHZhbHVlcywgbnVtYmVyJDQpLnNvcnQoYXNjZW5kaW5nJDQpOwogICAgICByZXR1cm4gTWF0aC5jZWlsKChtYXggLSBtaW4pIC8gKDIgKiAocXVhbnRpbGUkMSh2YWx1ZXMsIDAuNzUpIC0gcXVhbnRpbGUkMSh2YWx1ZXMsIDAuMjUpKSAqIE1hdGgucG93KHZhbHVlcy5sZW5ndGgsIC0xIC8gMykpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzY290dCQxKHZhbHVlcywgbWluLCBtYXgpIHsKICAgICAgcmV0dXJuIE1hdGguY2VpbCgobWF4IC0gbWluKSAvICgzLjUgKiBkZXZpYXRpb24kMSh2YWx1ZXMpICogTWF0aC5wb3codmFsdWVzLmxlbmd0aCwgLTEgLyAzKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1heCQzKHZhbHVlcywgdmFsdWVvZikgewogICAgICB2YXIgbiA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICB2YWx1ZSwKICAgICAgICAgIG1heDsKCiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCAmJiB2YWx1ZSA+PSB2YWx1ZSkgewogICAgICAgICAgICBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gQ29tcGFyZSB0aGUgcmVtYWluaW5nIHZhbHVlcy4KICAgICAgICAgICAgICBpZiAoKHZhbHVlID0gdmFsdWVzW2ldKSAhPSBudWxsICYmIHZhbHVlID4gbWF4KSB7CiAgICAgICAgICAgICAgICBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIEZpbmQgdGhlIGZpcnN0IGNvbXBhcmFibGUgdmFsdWUuCiAgICAgICAgICBpZiAoKHZhbHVlID0gdmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWF4ID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsICYmIHZhbHVlID4gbWF4KSB7CiAgICAgICAgICAgICAgICBtYXggPSB2YWx1ZTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBtYXg7CiAgICB9CgogICAgZnVuY3Rpb24gbWVhbiQxKHZhbHVlcywgdmFsdWVvZikgewogICAgICB2YXIgbiA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBtID0gbiwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIHZhbHVlLAogICAgICAgICAgc3VtID0gMDsKCiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaWYgKCFpc05hTih2YWx1ZSA9IG51bWJlciQ0KHZhbHVlc1tpXSkpKSBzdW0gKz0gdmFsdWU7CiAgICAgICAgICBlbHNlIC0tbTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyJDQodmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpKSkgc3VtICs9IHZhbHVlOwogICAgICAgICAgZWxzZSAtLW07CiAgICAgICAgfQogICAgICB9CgogICAgICBpZiAobSkgcmV0dXJuIHN1bSAvIG07CiAgICB9CgogICAgZnVuY3Rpb24gbWVkaWFuJDEodmFsdWVzLCB2YWx1ZW9mKSB7CiAgICAgIHZhciBuID0gdmFsdWVzLmxlbmd0aCwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIHZhbHVlLAogICAgICAgICAgbnVtYmVycyA9IFtdOwoKICAgICAgaWYgKHZhbHVlb2YgPT0gbnVsbCkgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyJDQodmFsdWVzW2ldKSkpIHsKICAgICAgICAgICAgbnVtYmVycy5wdXNoKHZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAoIWlzTmFOKHZhbHVlID0gbnVtYmVyJDQodmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpKSkgewogICAgICAgICAgICBudW1iZXJzLnB1c2godmFsdWUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHF1YW50aWxlJDEobnVtYmVycy5zb3J0KGFzY2VuZGluZyQ0KSwgMC41KTsKICAgIH0KCiAgICBmdW5jdGlvbiBtZXJnZSQxKGFycmF5cykgewogICAgICB2YXIgbiA9IGFycmF5cy5sZW5ndGgsCiAgICAgICAgICBtLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgaiA9IDAsCiAgICAgICAgICBtZXJnZWQsCiAgICAgICAgICBhcnJheTsKCiAgICAgIHdoaWxlICgrK2kgPCBuKSBqICs9IGFycmF5c1tpXS5sZW5ndGg7CiAgICAgIG1lcmdlZCA9IG5ldyBBcnJheShqKTsKCiAgICAgIHdoaWxlICgtLW4gPj0gMCkgewogICAgICAgIGFycmF5ID0gYXJyYXlzW25dOwogICAgICAgIG0gPSBhcnJheS5sZW5ndGg7CiAgICAgICAgd2hpbGUgKC0tbSA+PSAwKSB7CiAgICAgICAgICBtZXJnZWRbLS1qXSA9IGFycmF5W21dOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG1lcmdlZDsKICAgIH0KCiAgICBmdW5jdGlvbiBtaW4kMih2YWx1ZXMsIHZhbHVlb2YpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgdmFsdWUsCiAgICAgICAgICBtaW47CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsgLy8gRmluZCB0aGUgZmlyc3QgY29tcGFyYWJsZSB2YWx1ZS4KICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZXNbaV0pICE9IG51bGwgJiYgdmFsdWUgPj0gdmFsdWUpIHsKICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7IC8vIENvbXBhcmUgdGhlIHJlbWFpbmluZyB2YWx1ZXMuCiAgICAgICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlc1tpXSkgIT0gbnVsbCAmJiBtaW4gPiB2YWx1ZSkgewogICAgICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBlbHNlIHsKICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBGaW5kIHRoZSBmaXJzdCBjb21wYXJhYmxlIHZhbHVlLgogICAgICAgICAgaWYgKCh2YWx1ZSA9IHZhbHVlb2YodmFsdWVzW2ldLCBpLCB2YWx1ZXMpKSAhPSBudWxsICYmIHZhbHVlID49IHZhbHVlKSB7CiAgICAgICAgICAgIG1pbiA9IHZhbHVlOwogICAgICAgICAgICB3aGlsZSAoKytpIDwgbikgeyAvLyBDb21wYXJlIHRoZSByZW1haW5pbmcgdmFsdWVzLgogICAgICAgICAgICAgIGlmICgodmFsdWUgPSB2YWx1ZW9mKHZhbHVlc1tpXSwgaSwgdmFsdWVzKSkgIT0gbnVsbCAmJiBtaW4gPiB2YWx1ZSkgewogICAgICAgICAgICAgICAgbWluID0gdmFsdWU7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbWluOwogICAgfQoKICAgIGZ1bmN0aW9uIHBlcm11dGUkMShhcnJheSwgaW5kZXhlcykgewogICAgICB2YXIgaSA9IGluZGV4ZXMubGVuZ3RoLCBwZXJtdXRlcyA9IG5ldyBBcnJheShpKTsKICAgICAgd2hpbGUgKGktLSkgcGVybXV0ZXNbaV0gPSBhcnJheVtpbmRleGVzW2ldXTsKICAgICAgcmV0dXJuIHBlcm11dGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNjYW4kMSh2YWx1ZXMsIGNvbXBhcmUpIHsKICAgICAgaWYgKCEobiA9IHZhbHVlcy5sZW5ndGgpKSByZXR1cm47CiAgICAgIHZhciBuLAogICAgICAgICAgaSA9IDAsCiAgICAgICAgICBqID0gMCwKICAgICAgICAgIHhpLAogICAgICAgICAgeGogPSB2YWx1ZXNbal07CgogICAgICBpZiAoY29tcGFyZSA9PSBudWxsKSBjb21wYXJlID0gYXNjZW5kaW5nJDQ7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIGlmIChjb21wYXJlKHhpID0gdmFsdWVzW2ldLCB4aikgPCAwIHx8IGNvbXBhcmUoeGosIHhqKSAhPT0gMCkgewogICAgICAgICAgeGogPSB4aSwgaiA9IGk7CiAgICAgICAgfQogICAgICB9CgogICAgICBpZiAoY29tcGFyZSh4aiwgeGopID09PSAwKSByZXR1cm4gajsKICAgIH0KCiAgICBmdW5jdGlvbiBzaHVmZmxlJDIoYXJyYXksIGkwLCBpMSkgewogICAgICB2YXIgbSA9IChpMSA9PSBudWxsID8gYXJyYXkubGVuZ3RoIDogaTEpIC0gKGkwID0gaTAgPT0gbnVsbCA/IDAgOiAraTApLAogICAgICAgICAgdCwKICAgICAgICAgIGk7CgogICAgICB3aGlsZSAobSkgewogICAgICAgIGkgPSBNYXRoLnJhbmRvbSgpICogbS0tIHwgMDsKICAgICAgICB0ID0gYXJyYXlbbSArIGkwXTsKICAgICAgICBhcnJheVttICsgaTBdID0gYXJyYXlbaSArIGkwXTsKICAgICAgICBhcnJheVtpICsgaTBdID0gdDsKICAgICAgfQoKICAgICAgcmV0dXJuIGFycmF5OwogICAgfQoKICAgIGZ1bmN0aW9uIHN1bSQzKHZhbHVlcywgdmFsdWVvZikgewogICAgICB2YXIgbiA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBpID0gLTEsCiAgICAgICAgICB2YWx1ZSwKICAgICAgICAgIHN1bSA9IDA7CgogICAgICBpZiAodmFsdWVvZiA9PSBudWxsKSB7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICh2YWx1ZSA9ICt2YWx1ZXNbaV0pIHN1bSArPSB2YWx1ZTsgLy8gTm90ZTogemVybyBhbmQgbnVsbCBhcmUgZXF1aXZhbGVudC4KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVsc2UgewogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAodmFsdWUgPSArdmFsdWVvZih2YWx1ZXNbaV0sIGksIHZhbHVlcykpIHN1bSArPSB2YWx1ZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBzdW07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNwb3NlJDEobWF0cml4KSB7CiAgICAgIGlmICghKG4gPSBtYXRyaXgubGVuZ3RoKSkgcmV0dXJuIFtdOwogICAgICBmb3IgKHZhciBpID0gLTEsIG0gPSBtaW4kMihtYXRyaXgsIGxlbmd0aCQzKSwgdHJhbnNwb3NlID0gbmV3IEFycmF5KG0pOyArK2kgPCBtOykgewogICAgICAgIGZvciAodmFyIGogPSAtMSwgbiwgcm93ID0gdHJhbnNwb3NlW2ldID0gbmV3IEFycmF5KG4pOyArK2ogPCBuOykgewogICAgICAgICAgcm93W2pdID0gbWF0cml4W2pdW2ldOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdHJhbnNwb3NlOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlbmd0aCQzKGQpIHsKICAgICAgcmV0dXJuIGQubGVuZ3RoOwogICAgfQoKICAgIGZ1bmN0aW9uIHppcCQxKCkgewogICAgICByZXR1cm4gdHJhbnNwb3NlJDEoYXJndW1lbnRzKTsKICAgIH0KCiAgICB2YXIgc2xpY2UkOCA9IEFycmF5LnByb3RvdHlwZS5zbGljZTsKCiAgICBmdW5jdGlvbiBpZGVudGl0eSRiKHgpIHsKICAgICAgcmV0dXJuIHg7CiAgICB9CgogICAgdmFyIHRvcCQxID0gMSwKICAgICAgICByaWdodCQxID0gMiwKICAgICAgICBib3R0b20kMSA9IDMsCiAgICAgICAgbGVmdCQxID0gNCwKICAgICAgICBlcHNpbG9uJDUgPSAxZS02OwoKICAgIGZ1bmN0aW9uIHRyYW5zbGF0ZVgkMSh4KSB7CiAgICAgIHJldHVybiAidHJhbnNsYXRlKCIgKyAoeCArIDAuNSkgKyAiLDApIjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVZJDEoeSkgewogICAgICByZXR1cm4gInRyYW5zbGF0ZSgwLCIgKyAoeSArIDAuNSkgKyAiKSI7CiAgICB9CgogICAgZnVuY3Rpb24gbnVtYmVyJDUoc2NhbGUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQpIHsKICAgICAgICByZXR1cm4gK3NjYWxlKGQpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRlciQyKHNjYWxlKSB7CiAgICAgIHZhciBvZmZzZXQgPSBNYXRoLm1heCgwLCBzY2FsZS5iYW5kd2lkdGgoKSAtIDEpIC8gMjsgLy8gQWRqdXN0IGZvciAwLjVweCBvZmZzZXQuCiAgICAgIGlmIChzY2FsZS5yb3VuZCgpKSBvZmZzZXQgPSBNYXRoLnJvdW5kKG9mZnNldCk7CiAgICAgIHJldHVybiBmdW5jdGlvbihkKSB7CiAgICAgICAgcmV0dXJuICtzY2FsZShkKSArIG9mZnNldDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbnRlcmluZyQxKCkgewogICAgICByZXR1cm4gIXRoaXMuX19heGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGF4aXMkMShvcmllbnQsIHNjYWxlKSB7CiAgICAgIHZhciB0aWNrQXJndW1lbnRzID0gW10sCiAgICAgICAgICB0aWNrVmFsdWVzID0gbnVsbCwKICAgICAgICAgIHRpY2tGb3JtYXQgPSBudWxsLAogICAgICAgICAgdGlja1NpemVJbm5lciA9IDYsCiAgICAgICAgICB0aWNrU2l6ZU91dGVyID0gNiwKICAgICAgICAgIHRpY2tQYWRkaW5nID0gMywKICAgICAgICAgIGsgPSBvcmllbnQgPT09IHRvcCQxIHx8IG9yaWVudCA9PT0gbGVmdCQxID8gLTEgOiAxLAogICAgICAgICAgeCA9IG9yaWVudCA9PT0gbGVmdCQxIHx8IG9yaWVudCA9PT0gcmlnaHQkMSA/ICJ4IiA6ICJ5IiwKICAgICAgICAgIHRyYW5zZm9ybSA9IG9yaWVudCA9PT0gdG9wJDEgfHwgb3JpZW50ID09PSBib3R0b20kMSA/IHRyYW5zbGF0ZVgkMSA6IHRyYW5zbGF0ZVkkMTsKCiAgICAgIGZ1bmN0aW9uIGF4aXMoY29udGV4dCkgewogICAgICAgIHZhciB2YWx1ZXMgPSB0aWNrVmFsdWVzID09IG51bGwgPyAoc2NhbGUudGlja3MgPyBzY2FsZS50aWNrcy5hcHBseShzY2FsZSwgdGlja0FyZ3VtZW50cykgOiBzY2FsZS5kb21haW4oKSkgOiB0aWNrVmFsdWVzLAogICAgICAgICAgICBmb3JtYXQgPSB0aWNrRm9ybWF0ID09IG51bGwgPyAoc2NhbGUudGlja0Zvcm1hdCA/IHNjYWxlLnRpY2tGb3JtYXQuYXBwbHkoc2NhbGUsIHRpY2tBcmd1bWVudHMpIDogaWRlbnRpdHkkYikgOiB0aWNrRm9ybWF0LAogICAgICAgICAgICBzcGFjaW5nID0gTWF0aC5tYXgodGlja1NpemVJbm5lciwgMCkgKyB0aWNrUGFkZGluZywKICAgICAgICAgICAgcmFuZ2UgPSBzY2FsZS5yYW5nZSgpLAogICAgICAgICAgICByYW5nZTAgPSArcmFuZ2VbMF0gKyAwLjUsCiAgICAgICAgICAgIHJhbmdlMSA9ICtyYW5nZVtyYW5nZS5sZW5ndGggLSAxXSArIDAuNSwKICAgICAgICAgICAgcG9zaXRpb24gPSAoc2NhbGUuYmFuZHdpZHRoID8gY2VudGVyJDIgOiBudW1iZXIkNSkoc2NhbGUuY29weSgpKSwKICAgICAgICAgICAgc2VsZWN0aW9uID0gY29udGV4dC5zZWxlY3Rpb24gPyBjb250ZXh0LnNlbGVjdGlvbigpIDogY29udGV4dCwKICAgICAgICAgICAgcGF0aCA9IHNlbGVjdGlvbi5zZWxlY3RBbGwoIi5kb21haW4iKS5kYXRhKFtudWxsXSksCiAgICAgICAgICAgIHRpY2sgPSBzZWxlY3Rpb24uc2VsZWN0QWxsKCIudGljayIpLmRhdGEodmFsdWVzLCBzY2FsZSkub3JkZXIoKSwKICAgICAgICAgICAgdGlja0V4aXQgPSB0aWNrLmV4aXQoKSwKICAgICAgICAgICAgdGlja0VudGVyID0gdGljay5lbnRlcigpLmFwcGVuZCgiZyIpLmF0dHIoImNsYXNzIiwgInRpY2siKSwKICAgICAgICAgICAgbGluZSA9IHRpY2suc2VsZWN0KCJsaW5lIiksCiAgICAgICAgICAgIHRleHQgPSB0aWNrLnNlbGVjdCgidGV4dCIpOwoKICAgICAgICBwYXRoID0gcGF0aC5tZXJnZShwYXRoLmVudGVyKCkuaW5zZXJ0KCJwYXRoIiwgIi50aWNrIikKICAgICAgICAgICAgLmF0dHIoImNsYXNzIiwgImRvbWFpbiIpCiAgICAgICAgICAgIC5hdHRyKCJzdHJva2UiLCAiIzAwMCIpKTsKCiAgICAgICAgdGljayA9IHRpY2subWVyZ2UodGlja0VudGVyKTsKCiAgICAgICAgbGluZSA9IGxpbmUubWVyZ2UodGlja0VudGVyLmFwcGVuZCgibGluZSIpCiAgICAgICAgICAgIC5hdHRyKCJzdHJva2UiLCAiIzAwMCIpCiAgICAgICAgICAgIC5hdHRyKHggKyAiMiIsIGsgKiB0aWNrU2l6ZUlubmVyKSk7CgogICAgICAgIHRleHQgPSB0ZXh0Lm1lcmdlKHRpY2tFbnRlci5hcHBlbmQoInRleHQiKQogICAgICAgICAgICAuYXR0cigiZmlsbCIsICIjMDAwIikKICAgICAgICAgICAgLmF0dHIoeCwgayAqIHNwYWNpbmcpCiAgICAgICAgICAgIC5hdHRyKCJkeSIsIG9yaWVudCA9PT0gdG9wJDEgPyAiMGVtIiA6IG9yaWVudCA9PT0gYm90dG9tJDEgPyAiMC43MWVtIiA6ICIwLjMyZW0iKSk7CgogICAgICAgIGlmIChjb250ZXh0ICE9PSBzZWxlY3Rpb24pIHsKICAgICAgICAgIHBhdGggPSBwYXRoLnRyYW5zaXRpb24oY29udGV4dCk7CiAgICAgICAgICB0aWNrID0gdGljay50cmFuc2l0aW9uKGNvbnRleHQpOwogICAgICAgICAgbGluZSA9IGxpbmUudHJhbnNpdGlvbihjb250ZXh0KTsKICAgICAgICAgIHRleHQgPSB0ZXh0LnRyYW5zaXRpb24oY29udGV4dCk7CgogICAgICAgICAgdGlja0V4aXQgPSB0aWNrRXhpdC50cmFuc2l0aW9uKGNvbnRleHQpCiAgICAgICAgICAgICAgLmF0dHIoIm9wYWNpdHkiLCBlcHNpbG9uJDUpCiAgICAgICAgICAgICAgLmF0dHIoInRyYW5zZm9ybSIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGlzRmluaXRlKGQgPSBwb3NpdGlvbihkKSkgPyB0cmFuc2Zvcm0oZCkgOiB0aGlzLmdldEF0dHJpYnV0ZSgidHJhbnNmb3JtIik7IH0pOwoKICAgICAgICAgIHRpY2tFbnRlcgogICAgICAgICAgICAgIC5hdHRyKCJvcGFjaXR5IiwgZXBzaWxvbiQ1KQogICAgICAgICAgICAgIC5hdHRyKCJ0cmFuc2Zvcm0iLCBmdW5jdGlvbihkKSB7IHZhciBwID0gdGhpcy5wYXJlbnROb2RlLl9fYXhpczsgcmV0dXJuIHRyYW5zZm9ybShwICYmIGlzRmluaXRlKHAgPSBwKGQpKSA/IHAgOiBwb3NpdGlvbihkKSk7IH0pOwogICAgICAgIH0KCiAgICAgICAgdGlja0V4aXQucmVtb3ZlKCk7CgogICAgICAgIHBhdGgKICAgICAgICAgICAgLmF0dHIoImQiLCBvcmllbnQgPT09IGxlZnQkMSB8fCBvcmllbnQgPT0gcmlnaHQkMQogICAgICAgICAgICAgICAgPyAiTSIgKyBrICogdGlja1NpemVPdXRlciArICIsIiArIHJhbmdlMCArICJIMC41ViIgKyByYW5nZTEgKyAiSCIgKyBrICogdGlja1NpemVPdXRlcgogICAgICAgICAgICAgICAgOiAiTSIgKyByYW5nZTAgKyAiLCIgKyBrICogdGlja1NpemVPdXRlciArICJWMC41SCIgKyByYW5nZTEgKyAiViIgKyBrICogdGlja1NpemVPdXRlcik7CgogICAgICAgIHRpY2sKICAgICAgICAgICAgLmF0dHIoIm9wYWNpdHkiLCAxKQogICAgICAgICAgICAuYXR0cigidHJhbnNmb3JtIiwgZnVuY3Rpb24oZCkgeyByZXR1cm4gdHJhbnNmb3JtKHBvc2l0aW9uKGQpKTsgfSk7CgogICAgICAgIGxpbmUKICAgICAgICAgICAgLmF0dHIoeCArICIyIiwgayAqIHRpY2tTaXplSW5uZXIpOwoKICAgICAgICB0ZXh0CiAgICAgICAgICAgIC5hdHRyKHgsIGsgKiBzcGFjaW5nKQogICAgICAgICAgICAudGV4dChmb3JtYXQpOwoKICAgICAgICBzZWxlY3Rpb24uZmlsdGVyKGVudGVyaW5nJDEpCiAgICAgICAgICAgIC5hdHRyKCJmaWxsIiwgIm5vbmUiKQogICAgICAgICAgICAuYXR0cigiZm9udC1zaXplIiwgMTApCiAgICAgICAgICAgIC5hdHRyKCJmb250LWZhbWlseSIsICJzYW5zLXNlcmlmIikKICAgICAgICAgICAgLmF0dHIoInRleHQtYW5jaG9yIiwgb3JpZW50ID09PSByaWdodCQxID8gInN0YXJ0IiA6IG9yaWVudCA9PT0gbGVmdCQxID8gImVuZCIgOiAibWlkZGxlIik7CgogICAgICAgIHNlbGVjdGlvbgogICAgICAgICAgICAuZWFjaChmdW5jdGlvbigpIHsgdGhpcy5fX2F4aXMgPSBwb3NpdGlvbjsgfSk7CiAgICAgIH0KCiAgICAgIGF4aXMuc2NhbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2NhbGUgPSBfLCBheGlzKSA6IHNjYWxlOwogICAgICB9OwoKICAgICAgYXhpcy50aWNrcyA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aWNrQXJndW1lbnRzID0gc2xpY2UkOC5jYWxsKGFyZ3VtZW50cyksIGF4aXM7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tBcmd1bWVudHMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGlja0FyZ3VtZW50cyA9IF8gPT0gbnVsbCA/IFtdIDogc2xpY2UkOC5jYWxsKF8pLCBheGlzKSA6IHRpY2tBcmd1bWVudHMuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja1ZhbHVlcyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrVmFsdWVzID0gXyA9PSBudWxsID8gbnVsbCA6IHNsaWNlJDguY2FsbChfKSwgYXhpcykgOiB0aWNrVmFsdWVzICYmIHRpY2tWYWx1ZXMuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIGF4aXMudGlja0Zvcm1hdCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrRm9ybWF0ID0gXywgYXhpcykgOiB0aWNrRm9ybWF0OwogICAgICB9OwoKICAgICAgYXhpcy50aWNrU2l6ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aWNrU2l6ZUlubmVyID0gdGlja1NpemVPdXRlciA9ICtfLCBheGlzKSA6IHRpY2tTaXplSW5uZXI7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tTaXplSW5uZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGlja1NpemVJbm5lciA9ICtfLCBheGlzKSA6IHRpY2tTaXplSW5uZXI7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tTaXplT3V0ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGlja1NpemVPdXRlciA9ICtfLCBheGlzKSA6IHRpY2tTaXplT3V0ZXI7CiAgICAgIH07CgogICAgICBheGlzLnRpY2tQYWRkaW5nID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRpY2tQYWRkaW5nID0gK18sIGF4aXMpIDogdGlja1BhZGRpbmc7CiAgICAgIH07CgogICAgICByZXR1cm4gYXhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBheGlzVG9wJDEoc2NhbGUpIHsKICAgICAgcmV0dXJuIGF4aXMkMSh0b3AkMSwgc2NhbGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGF4aXNSaWdodCQxKHNjYWxlKSB7CiAgICAgIHJldHVybiBheGlzJDEocmlnaHQkMSwgc2NhbGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGF4aXNCb3R0b20kMShzY2FsZSkgewogICAgICByZXR1cm4gYXhpcyQxKGJvdHRvbSQxLCBzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXhpc0xlZnQkMShzY2FsZSkgewogICAgICByZXR1cm4gYXhpcyQxKGxlZnQkMSwgc2NhbGUpOwogICAgfQoKICAgIHZhciBub29wJDQgPSB7dmFsdWU6IGZ1bmN0aW9uKCkge319OwoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoJDEoKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gYXJndW1lbnRzLmxlbmd0aCwgXyA9IHt9LCB0OyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKCEodCA9IGFyZ3VtZW50c1tpXSArICIiKSB8fCAodCBpbiBfKSB8fCAvW1xzLl0vLnRlc3QodCkpIHRocm93IG5ldyBFcnJvcigiaWxsZWdhbCB0eXBlOiAiICsgdCk7CiAgICAgICAgX1t0XSA9IFtdOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgRGlzcGF0Y2gkMShfKTsKICAgIH0KCiAgICBmdW5jdGlvbiBEaXNwYXRjaCQxKF8pIHsKICAgICAgdGhpcy5fID0gXzsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVR5cGVuYW1lcyQyKHR5cGVuYW1lcywgdHlwZXMpIHsKICAgICAgcmV0dXJuIHR5cGVuYW1lcy50cmltKCkuc3BsaXQoL158XHMrLykubWFwKGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgbmFtZSA9ICIiLCBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgbmFtZSA9IHQuc2xpY2UoaSArIDEpLCB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICBpZiAodCAmJiAhdHlwZXMuaGFzT3duUHJvcGVydHkodCkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdCk7CiAgICAgICAgcmV0dXJuIHt0eXBlOiB0LCBuYW1lOiBuYW1lfTsKICAgICAgfSk7CiAgICB9CgogICAgRGlzcGF0Y2gkMS5wcm90b3R5cGUgPSBkaXNwYXRjaCQxLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IERpc3BhdGNoJDEsCiAgICAgIG9uOiBmdW5jdGlvbih0eXBlbmFtZSwgY2FsbGJhY2spIHsKICAgICAgICB2YXIgXyA9IHRoaXMuXywKICAgICAgICAgICAgVCA9IHBhcnNlVHlwZW5hbWVzJDIodHlwZW5hbWUgKyAiIiwgXyksCiAgICAgICAgICAgIHQsCiAgICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgICAgbiA9IFQubGVuZ3RoOwoKICAgICAgICAvLyBJZiBubyBjYWxsYmFjayB3YXMgc3BlY2lmaWVkLCByZXR1cm4gdGhlIGNhbGxiYWNrIG9mIHRoZSBnaXZlbiB0eXBlIGFuZCBuYW1lLgogICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICgodCA9ICh0eXBlbmFtZSA9IFRbaV0pLnR5cGUpICYmICh0ID0gZ2V0JDMoX1t0XSwgdHlwZW5hbWUubmFtZSkpKSByZXR1cm4gdDsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIElmIGEgdHlwZSB3YXMgc3BlY2lmaWVkLCBzZXQgdGhlIGNhbGxiYWNrIGZvciB0aGUgZ2l2ZW4gdHlwZSBhbmQgbmFtZS4KICAgICAgICAvLyBPdGhlcndpc2UsIGlmIGEgbnVsbCBjYWxsYmFjayB3YXMgc3BlY2lmaWVkLCByZW1vdmUgY2FsbGJhY2tzIG9mIHRoZSBnaXZlbiBuYW1lLgogICAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsICYmIHR5cGVvZiBjYWxsYmFjayAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIGNhbGxiYWNrOiAiICsgY2FsbGJhY2spOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAodCA9ICh0eXBlbmFtZSA9IFRbaV0pLnR5cGUpIF9bdF0gPSBzZXQkNChfW3RdLCB0eXBlbmFtZS5uYW1lLCBjYWxsYmFjayk7CiAgICAgICAgICBlbHNlIGlmIChjYWxsYmFjayA9PSBudWxsKSBmb3IgKHQgaW4gXykgX1t0XSA9IHNldCQ0KF9bdF0sIHR5cGVuYW1lLm5hbWUsIG51bGwpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIGNvcHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBjb3B5ID0ge30sIF8gPSB0aGlzLl87CiAgICAgICAgZm9yICh2YXIgdCBpbiBfKSBjb3B5W3RdID0gX1t0XS5zbGljZSgpOwogICAgICAgIHJldHVybiBuZXcgRGlzcGF0Y2gkMShjb3B5KTsKICAgICAgfSwKICAgICAgY2FsbDogZnVuY3Rpb24odHlwZSwgdGhhdCkgewogICAgICAgIGlmICgobiA9IGFyZ3VtZW50cy5sZW5ndGggLSAyKSA+IDApIGZvciAodmFyIGFyZ3MgPSBuZXcgQXJyYXkobiksIGkgPSAwLCBuLCB0OyBpIDwgbjsgKytpKSBhcmdzW2ldID0gYXJndW1lbnRzW2kgKyAyXTsKICAgICAgICBpZiAoIXRoaXMuXy5oYXNPd25Qcm9wZXJ0eSh0eXBlKSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0eXBlKTsKICAgICAgICBmb3IgKHQgPSB0aGlzLl9bdHlwZV0sIGkgPSAwLCBuID0gdC5sZW5ndGg7IGkgPCBuOyArK2kpIHRbaV0udmFsdWUuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0sCiAgICAgIGFwcGx5OiBmdW5jdGlvbih0eXBlLCB0aGF0LCBhcmdzKSB7CiAgICAgICAgaWYgKCF0aGlzLl8uaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdHlwZSk7CiAgICAgICAgZm9yICh2YXIgdCA9IHRoaXMuX1t0eXBlXSwgaSA9IDAsIG4gPSB0Lmxlbmd0aDsgaSA8IG47ICsraSkgdFtpXS52YWx1ZS5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBnZXQkMyh0eXBlLCBuYW1lKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHlwZS5sZW5ndGgsIGM7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoKGMgPSB0eXBlW2ldKS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICByZXR1cm4gYy52YWx1ZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZXQkNCh0eXBlLCBuYW1lLCBjYWxsYmFjaykgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR5cGUubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKHR5cGVbaV0ubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgdHlwZVtpXSA9IG5vb3AkNCwgdHlwZSA9IHR5cGUuc2xpY2UoMCwgaSkuY29uY2F0KHR5cGUuc2xpY2UoaSArIDEpKTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICBpZiAoY2FsbGJhY2sgIT0gbnVsbCkgdHlwZS5wdXNoKHtuYW1lOiBuYW1lLCB2YWx1ZTogY2FsbGJhY2t9KTsKICAgICAgcmV0dXJuIHR5cGU7CiAgICB9CgogICAgdmFyIHhodG1sJDEgPSAiaHR0cDovL3d3dy53My5vcmcvMTk5OS94aHRtbCI7CgogICAgdmFyIG5hbWVzcGFjZXMkMSA9IHsKICAgICAgc3ZnOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciLAogICAgICB4aHRtbDogeGh0bWwkMSwKICAgICAgeGxpbms6ICJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rIiwKICAgICAgeG1sOiAiaHR0cDovL3d3dy53My5vcmcvWE1MLzE5OTgvbmFtZXNwYWNlIiwKICAgICAgeG1sbnM6ICJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3htbG5zLyIKICAgIH07CgogICAgZnVuY3Rpb24gbmFtZXNwYWNlJDEobmFtZSkgewogICAgICB2YXIgcHJlZml4ID0gbmFtZSArPSAiIiwgaSA9IHByZWZpeC5pbmRleE9mKCI6Iik7CiAgICAgIGlmIChpID49IDAgJiYgKHByZWZpeCA9IG5hbWUuc2xpY2UoMCwgaSkpICE9PSAieG1sbnMiKSBuYW1lID0gbmFtZS5zbGljZShpICsgMSk7CiAgICAgIHJldHVybiBuYW1lc3BhY2VzJDEuaGFzT3duUHJvcGVydHkocHJlZml4KSA/IHtzcGFjZTogbmFtZXNwYWNlcyQxW3ByZWZpeF0sIGxvY2FsOiBuYW1lfSA6IG5hbWU7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvckluaGVyaXQkMShuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZG9jdW1lbnQgPSB0aGlzLm93bmVyRG9jdW1lbnQsCiAgICAgICAgICAgIHVyaSA9IHRoaXMubmFtZXNwYWNlVVJJOwogICAgICAgIHJldHVybiB1cmkgPT09IHhodG1sJDEgJiYgZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50Lm5hbWVzcGFjZVVSSSA9PT0geGh0bWwkMQogICAgICAgICAgICA/IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQobmFtZSkKICAgICAgICAgICAgOiBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlModXJpLCBuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdG9yRml4ZWQkMShmdWxsbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMub3duZXJEb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdG9yJDEobmFtZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UkMShuYW1lKTsKICAgICAgcmV0dXJuIChmdWxsbmFtZS5sb2NhbAogICAgICAgICAgPyBjcmVhdG9yRml4ZWQkMQogICAgICAgICAgOiBjcmVhdG9ySW5oZXJpdCQxKShmdWxsbmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9uZSQzKCkge30KCiAgICBmdW5jdGlvbiBzZWxlY3RvciQxKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBzZWxlY3RvciA9PSBudWxsID8gbm9uZSQzIDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucXVlcnlTZWxlY3RvcihzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NlbGVjdCQxKHNlbGVjdCkgewogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3IkMShzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgc3Vibm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiAoc3Vibm9kZSA9IHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkpIHsKICAgICAgICAgICAgaWYgKCJfX2RhdGFfXyIgaW4gbm9kZSkgc3Vibm9kZS5fX2RhdGFfXyA9IG5vZGUuX19kYXRhX187CiAgICAgICAgICAgIHN1Ymdyb3VwW2ldID0gc3Vibm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDIoc3ViZ3JvdXBzLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbXB0eSQyKCkgewogICAgICByZXR1cm4gW107CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0b3JBbGwkMShzZWxlY3RvcikgewogICAgICByZXR1cm4gc2VsZWN0b3IgPT0gbnVsbCA/IGVtcHR5JDIgOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5xdWVyeVNlbGVjdG9yQWxsKHNlbGVjdG9yKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2VsZWN0QWxsJDEoc2VsZWN0KSB7CiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvckFsbCQxKHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBbXSwgcGFyZW50cyA9IFtdLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBzdWJncm91cHMucHVzaChzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpOwogICAgICAgICAgICBwYXJlbnRzLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQyKHN1Ymdyb3VwcywgcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gbWF0Y2hlciQxKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5tYXRjaGVzKHNlbGVjdG9yKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZmlsdGVyJDEobWF0Y2gpIHsKICAgICAgaWYgKHR5cGVvZiBtYXRjaCAhPT0gImZ1bmN0aW9uIikgbWF0Y2ggPSBtYXRjaGVyJDEobWF0Y2gpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IFtdLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIG1hdGNoLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSB7CiAgICAgICAgICAgIHN1Ymdyb3VwLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQyKHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc3BhcnNlJDEodXBkYXRlKSB7CiAgICAgIHJldHVybiBuZXcgQXJyYXkodXBkYXRlLmxlbmd0aCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VudGVyJDEoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDIodGhpcy5fZW50ZXIgfHwgdGhpcy5fZ3JvdXBzLm1hcChzcGFyc2UkMSksIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIEVudGVyTm9kZSQxKHBhcmVudCwgZGF0dW0pIHsKICAgICAgdGhpcy5vd25lckRvY3VtZW50ID0gcGFyZW50Lm93bmVyRG9jdW1lbnQ7CiAgICAgIHRoaXMubmFtZXNwYWNlVVJJID0gcGFyZW50Lm5hbWVzcGFjZVVSSTsKICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICAgIHRoaXMuX3BhcmVudCA9IHBhcmVudDsKICAgICAgdGhpcy5fX2RhdGFfXyA9IGRhdHVtOwogICAgfQoKICAgIEVudGVyTm9kZSQxLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IEVudGVyTm9kZSQxLAogICAgICBhcHBlbmRDaGlsZDogZnVuY3Rpb24oY2hpbGQpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5pbnNlcnRCZWZvcmUoY2hpbGQsIHRoaXMuX25leHQpOyB9LAogICAgICBpbnNlcnRCZWZvcmU6IGZ1bmN0aW9uKGNoaWxkLCBuZXh0KSB7IHJldHVybiB0aGlzLl9wYXJlbnQuaW5zZXJ0QmVmb3JlKGNoaWxkLCBuZXh0KTsgfSwKICAgICAgcXVlcnlTZWxlY3RvcjogZnVuY3Rpb24oc2VsZWN0b3IpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKTsgfSwKICAgICAgcXVlcnlTZWxlY3RvckFsbDogZnVuY3Rpb24oc2VsZWN0b3IpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5xdWVyeVNlbGVjdG9yQWxsKHNlbGVjdG9yKTsgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjb25zdGFudCRmKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIHZhciBrZXlQcmVmaXgkMiA9ICIkIjsgLy8gUHJvdGVjdCBhZ2FpbnN0IGtleXMgbGlrZSDigJxfX3Byb3RvX1/igJ0uCgogICAgZnVuY3Rpb24gYmluZEluZGV4JDEocGFyZW50LCBncm91cCwgZW50ZXIsIHVwZGF0ZSwgZXhpdCwgZGF0YSkgewogICAgICB2YXIgaSA9IDAsCiAgICAgICAgICBub2RlLAogICAgICAgICAgZ3JvdXBMZW5ndGggPSBncm91cC5sZW5ndGgsCiAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGg7CgogICAgICAvLyBQdXQgYW55IG5vbi1udWxsIG5vZGVzIHRoYXQgZml0IGludG8gdXBkYXRlLgogICAgICAvLyBQdXQgYW55IG51bGwgbm9kZXMgaW50byBlbnRlci4KICAgICAgLy8gUHV0IGFueSByZW1haW5pbmcgZGF0YSBpbnRvIGVudGVyLgogICAgICBmb3IgKDsgaSA8IGRhdGFMZW5ndGg7ICsraSkgewogICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgIG5vZGUuX19kYXRhX18gPSBkYXRhW2ldOwogICAgICAgICAgdXBkYXRlW2ldID0gbm9kZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZW50ZXJbaV0gPSBuZXcgRW50ZXJOb2RlJDEocGFyZW50LCBkYXRhW2ldKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIFB1dCBhbnkgbm9uLW51bGwgbm9kZXMgdGhhdCBkb27igJl0IGZpdCBpbnRvIGV4aXQuCiAgICAgIGZvciAoOyBpIDwgZ3JvdXBMZW5ndGg7ICsraSkgewogICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgIGV4aXRbaV0gPSBub2RlOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGJpbmRLZXkkMShwYXJlbnQsIGdyb3VwLCBlbnRlciwgdXBkYXRlLCBleGl0LCBkYXRhLCBrZXkpIHsKICAgICAgdmFyIGksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZUJ5S2V5VmFsdWUgPSB7fSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoLAogICAgICAgICAga2V5VmFsdWVzID0gbmV3IEFycmF5KGdyb3VwTGVuZ3RoKSwKICAgICAgICAgIGtleVZhbHVlOwoKICAgICAgLy8gQ29tcHV0ZSB0aGUga2V5IGZvciBlYWNoIG5vZGUuCiAgICAgIC8vIElmIG11bHRpcGxlIG5vZGVzIGhhdmUgdGhlIHNhbWUga2V5LCB0aGUgZHVwbGljYXRlcyBhcmUgYWRkZWQgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBrZXlWYWx1ZXNbaV0gPSBrZXlWYWx1ZSA9IGtleVByZWZpeCQyICsga2V5LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApOwogICAgICAgICAgaWYgKGtleVZhbHVlIGluIG5vZGVCeUtleVZhbHVlKSB7CiAgICAgICAgICAgIGV4aXRbaV0gPSBub2RlOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIENvbXB1dGUgdGhlIGtleSBmb3IgZWFjaCBkYXR1bS4KICAgICAgLy8gSWYgdGhlcmUgYSBub2RlIGFzc29jaWF0ZWQgd2l0aCB0aGlzIGtleSwgam9pbiBhbmQgYWRkIGl0IHRvIHVwZGF0ZS4KICAgICAgLy8gSWYgdGhlcmUgaXMgbm90IChvciB0aGUga2V5IGlzIGEgZHVwbGljYXRlKSwgYWRkIGl0IHRvIGVudGVyLgogICAgICBmb3IgKGkgPSAwOyBpIDwgZGF0YUxlbmd0aDsgKytpKSB7CiAgICAgICAga2V5VmFsdWUgPSBrZXlQcmVmaXgkMiArIGtleS5jYWxsKHBhcmVudCwgZGF0YVtpXSwgaSwgZGF0YSk7CiAgICAgICAgaWYgKG5vZGUgPSBub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZV0pIHsKICAgICAgICAgIHVwZGF0ZVtpXSA9IG5vZGU7CiAgICAgICAgICBub2RlLl9fZGF0YV9fID0gZGF0YVtpXTsKICAgICAgICAgIG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSA9IG51bGw7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVudGVyW2ldID0gbmV3IEVudGVyTm9kZSQxKHBhcmVudCwgZGF0YVtpXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBBZGQgYW55IHJlbWFpbmluZyBub2RlcyB0aGF0IHdlcmUgbm90IGJvdW5kIHRvIGRhdGEgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKG5vZGVCeUtleVZhbHVlW2tleVZhbHVlc1tpXV0gPT09IG5vZGUpKSB7CiAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGF0YSQxKHZhbHVlLCBrZXkpIHsKICAgICAgaWYgKCF2YWx1ZSkgewogICAgICAgIGRhdGEgPSBuZXcgQXJyYXkodGhpcy5zaXplKCkpLCBqID0gLTE7CiAgICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKGQpIHsgZGF0YVsrK2pdID0gZDsgfSk7CiAgICAgICAgcmV0dXJuIGRhdGE7CiAgICAgIH0KCiAgICAgIHZhciBiaW5kID0ga2V5ID8gYmluZEtleSQxIDogYmluZEluZGV4JDEsCiAgICAgICAgICBwYXJlbnRzID0gdGhpcy5fcGFyZW50cywKICAgICAgICAgIGdyb3VwcyA9IHRoaXMuX2dyb3VwczsKCiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHZhbHVlID0gY29uc3RhbnQkZih2YWx1ZSk7CgogICAgICBmb3IgKHZhciBtID0gZ3JvdXBzLmxlbmd0aCwgdXBkYXRlID0gbmV3IEFycmF5KG0pLCBlbnRlciA9IG5ldyBBcnJheShtKSwgZXhpdCA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICB2YXIgcGFyZW50ID0gcGFyZW50c1tqXSwKICAgICAgICAgICAgZ3JvdXAgPSBncm91cHNbal0sCiAgICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgICBkYXRhID0gdmFsdWUuY2FsbChwYXJlbnQsIHBhcmVudCAmJiBwYXJlbnQuX19kYXRhX18sIGosIHBhcmVudHMpLAogICAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIGVudGVyR3JvdXAgPSBlbnRlcltqXSA9IG5ldyBBcnJheShkYXRhTGVuZ3RoKSwKICAgICAgICAgICAgdXBkYXRlR3JvdXAgPSB1cGRhdGVbal0gPSBuZXcgQXJyYXkoZGF0YUxlbmd0aCksCiAgICAgICAgICAgIGV4aXRHcm91cCA9IGV4aXRbal0gPSBuZXcgQXJyYXkoZ3JvdXBMZW5ndGgpOwoKICAgICAgICBiaW5kKHBhcmVudCwgZ3JvdXAsIGVudGVyR3JvdXAsIHVwZGF0ZUdyb3VwLCBleGl0R3JvdXAsIGRhdGEsIGtleSk7CgogICAgICAgIC8vIE5vdyBjb25uZWN0IHRoZSBlbnRlciBub2RlcyB0byB0aGVpciBmb2xsb3dpbmcgdXBkYXRlIG5vZGUsIHN1Y2ggdGhhdAogICAgICAgIC8vIGFwcGVuZENoaWxkIGNhbiBpbnNlcnQgdGhlIG1hdGVyaWFsaXplZCBlbnRlciBub2RlIGJlZm9yZSB0aGlzIG5vZGUsCiAgICAgICAgLy8gcmF0aGVyIHRoYW4gYXQgdGhlIGVuZCBvZiB0aGUgcGFyZW50IG5vZGUuCiAgICAgICAgZm9yICh2YXIgaTAgPSAwLCBpMSA9IDAsIHByZXZpb3VzLCBuZXh0OyBpMCA8IGRhdGFMZW5ndGg7ICsraTApIHsKICAgICAgICAgIGlmIChwcmV2aW91cyA9IGVudGVyR3JvdXBbaTBdKSB7CiAgICAgICAgICAgIGlmIChpMCA+PSBpMSkgaTEgPSBpMCArIDE7CiAgICAgICAgICAgIHdoaWxlICghKG5leHQgPSB1cGRhdGVHcm91cFtpMV0pICYmICsraTEgPCBkYXRhTGVuZ3RoKTsKICAgICAgICAgICAgcHJldmlvdXMuX25leHQgPSBuZXh0IHx8IG51bGw7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICB1cGRhdGUgPSBuZXcgU2VsZWN0aW9uJDIodXBkYXRlLCBwYXJlbnRzKTsKICAgICAgdXBkYXRlLl9lbnRlciA9IGVudGVyOwogICAgICB1cGRhdGUuX2V4aXQgPSBleGl0OwogICAgICByZXR1cm4gdXBkYXRlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9leGl0JDEoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDIodGhpcy5fZXhpdCB8fCB0aGlzLl9ncm91cHMubWFwKHNwYXJzZSQxKSwgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2pvaW4kMShvbmVudGVyLCBvbnVwZGF0ZSwgb25leGl0KSB7CiAgICAgIHZhciBlbnRlciA9IHRoaXMuZW50ZXIoKSwgdXBkYXRlID0gdGhpcywgZXhpdCA9IHRoaXMuZXhpdCgpOwogICAgICBlbnRlciA9IHR5cGVvZiBvbmVudGVyID09PSAiZnVuY3Rpb24iID8gb25lbnRlcihlbnRlcikgOiBlbnRlci5hcHBlbmQob25lbnRlciArICIiKTsKICAgICAgaWYgKG9udXBkYXRlICE9IG51bGwpIHVwZGF0ZSA9IG9udXBkYXRlKHVwZGF0ZSk7CiAgICAgIGlmIChvbmV4aXQgPT0gbnVsbCkgZXhpdC5yZW1vdmUoKTsgZWxzZSBvbmV4aXQoZXhpdCk7CiAgICAgIHJldHVybiBlbnRlciAmJiB1cGRhdGUgPyBlbnRlci5tZXJnZSh1cGRhdGUpLm9yZGVyKCkgOiB1cGRhdGU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX21lcmdlJDEoc2VsZWN0aW9uKSB7CgogICAgICBmb3IgKHZhciBncm91cHMwID0gdGhpcy5fZ3JvdXBzLCBncm91cHMxID0gc2VsZWN0aW9uLl9ncm91cHMsIG0wID0gZ3JvdXBzMC5sZW5ndGgsIG0xID0gZ3JvdXBzMS5sZW5ndGgsIG0gPSBNYXRoLm1pbihtMCwgbTEpLCBtZXJnZXMgPSBuZXcgQXJyYXkobTApLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwMCA9IGdyb3VwczBbal0sIGdyb3VwMSA9IGdyb3VwczFbal0sIG4gPSBncm91cDAubGVuZ3RoLCBtZXJnZSA9IG1lcmdlc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXAwW2ldIHx8IGdyb3VwMVtpXSkgewogICAgICAgICAgICBtZXJnZVtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3IgKDsgaiA8IG0wOyArK2opIHsKICAgICAgICBtZXJnZXNbal0gPSBncm91cHMwW2pdOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQyKG1lcmdlcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX29yZGVyJDEoKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAtMSwgbSA9IGdyb3Vwcy5sZW5ndGg7ICsraiA8IG07KSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIGkgPSBncm91cC5sZW5ndGggLSAxLCBuZXh0ID0gZ3JvdXBbaV0sIG5vZGU7IC0taSA+PSAwOykgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBpZiAobmV4dCAmJiBub2RlLmNvbXBhcmVEb2N1bWVudFBvc2l0aW9uKG5leHQpIF4gNCkgbmV4dC5wYXJlbnROb2RlLmluc2VydEJlZm9yZShub2RlLCBuZXh0KTsKICAgICAgICAgICAgbmV4dCA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc29ydCQxKGNvbXBhcmUpIHsKICAgICAgaWYgKCFjb21wYXJlKSBjb21wYXJlID0gYXNjZW5kaW5nJDU7CgogICAgICBmdW5jdGlvbiBjb21wYXJlTm9kZShhLCBiKSB7CiAgICAgICAgcmV0dXJuIGEgJiYgYiA/IGNvbXBhcmUoYS5fX2RhdGFfXywgYi5fX2RhdGFfXykgOiAhYSAtICFiOwogICAgICB9CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzb3J0Z3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzb3J0Z3JvdXAgPSBzb3J0Z3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBzb3J0Z3JvdXBbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBzb3J0Z3JvdXAuc29ydChjb21wYXJlTm9kZSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDIoc29ydGdyb3VwcywgdGhpcy5fcGFyZW50cykub3JkZXIoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2NlbmRpbmckNShhLCBiKSB7CiAgICAgIHJldHVybiBhIDwgYiA/IC0xIDogYSA+IGIgPyAxIDogYSA+PSBiID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2FsbCQxKCkgewogICAgICB2YXIgY2FsbGJhY2sgPSBhcmd1bWVudHNbMF07CiAgICAgIGFyZ3VtZW50c1swXSA9IHRoaXM7CiAgICAgIGNhbGxiYWNrLmFwcGx5KG51bGwsIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9ub2RlcyQxKCkgewogICAgICB2YXIgbm9kZXMgPSBuZXcgQXJyYXkodGhpcy5zaXplKCkpLCBpID0gLTE7CiAgICAgIHRoaXMuZWFjaChmdW5jdGlvbigpIHsgbm9kZXNbKytpXSA9IHRoaXM7IH0pOwogICAgICByZXR1cm4gbm9kZXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX25vZGUkMSgpIHsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgaiA9IDAsIG0gPSBncm91cHMubGVuZ3RoOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIGkgPSAwLCBuID0gZ3JvdXAubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB2YXIgbm9kZSA9IGdyb3VwW2ldOwogICAgICAgICAgaWYgKG5vZGUpIHJldHVybiBub2RlOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NpemUkMSgpIHsKICAgICAgdmFyIHNpemUgPSAwOwogICAgICB0aGlzLmVhY2goZnVuY3Rpb24oKSB7ICsrc2l6ZTsgfSk7CiAgICAgIHJldHVybiBzaXplOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9lbXB0eSQxKCkgewogICAgICByZXR1cm4gIXRoaXMubm9kZSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9lYWNoJDEoY2FsbGJhY2spIHsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgaiA9IDAsIG0gPSBncm91cHMubGVuZ3RoOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIGkgPSAwLCBuID0gZ3JvdXAubGVuZ3RoLCBub2RlOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSBjYWxsYmFjay5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJSZW1vdmUkMihuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlTlMkMihmdWxsbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudCQyKG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZShuYW1lLCB2YWx1ZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckNvbnN0YW50TlMkMihmdWxsbmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCB2YWx1ZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckZ1bmN0aW9uJDIobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICBlbHNlIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIHYpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbk5TJDIoZnVsbG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5yZW1vdmVBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICAgIGVsc2UgdGhpcy5zZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwsIHYpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9hdHRyJDEobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlJDEobmFtZSk7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgbm9kZSA9IHRoaXMubm9kZSgpOwogICAgICAgIHJldHVybiBmdWxsbmFtZS5sb2NhbAogICAgICAgICAgICA/IG5vZGUuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKQogICAgICAgICAgICA6IG5vZGUuZ2V0QXR0cmlidXRlKGZ1bGxuYW1lKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyUmVtb3ZlTlMkMiA6IGF0dHJSZW1vdmUkMikgOiAodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJGdW5jdGlvbk5TJDIgOiBhdHRyRnVuY3Rpb24kMikKICAgICAgICAgIDogKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckNvbnN0YW50TlMkMiA6IGF0dHJDb25zdGFudCQyKSkpKGZ1bGxuYW1lLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRWaWV3JDEobm9kZSkgewogICAgICByZXR1cm4gKG5vZGUub3duZXJEb2N1bWVudCAmJiBub2RlLm93bmVyRG9jdW1lbnQuZGVmYXVsdFZpZXcpIC8vIG5vZGUgaXMgYSBOb2RlCiAgICAgICAgICB8fCAobm9kZS5kb2N1bWVudCAmJiBub2RlKSAvLyBub2RlIGlzIGEgV2luZG93CiAgICAgICAgICB8fCBub2RlLmRlZmF1bHRWaWV3OyAvLyBub2RlIGlzIGEgRG9jdW1lbnQKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVJlbW92ZSQyKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVDb25zdGFudCQyKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5zZXRQcm9wZXJ0eShuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlRnVuY3Rpb24kMihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSB0aGlzLnN0eWxlLnJlbW92ZVByb3BlcnR5KG5hbWUpOwogICAgICAgIGVsc2UgdGhpcy5zdHlsZS5zZXRQcm9wZXJ0eShuYW1lLCB2LCBwcmlvcml0eSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3N0eWxlJDEobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMQogICAgICAgICAgPyB0aGlzLmVhY2goKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICAgID8gc3R5bGVSZW1vdmUkMiA6IHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgICAgPyBzdHlsZUZ1bmN0aW9uJDIKICAgICAgICAgICAgICAgIDogc3R5bGVDb25zdGFudCQyKShuYW1lLCB2YWx1ZSwgcHJpb3JpdHkgPT0gbnVsbCA/ICIiIDogcHJpb3JpdHkpKQogICAgICAgICAgOiBzdHlsZVZhbHVlJDEodGhpcy5ub2RlKCksIG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlVmFsdWUkMShub2RlLCBuYW1lKSB7CiAgICAgIHJldHVybiBub2RlLnN0eWxlLmdldFByb3BlcnR5VmFsdWUobmFtZSkKICAgICAgICAgIHx8IGRlZmF1bHRWaWV3JDEobm9kZSkuZ2V0Q29tcHV0ZWRTdHlsZShub2RlLCBudWxsKS5nZXRQcm9wZXJ0eVZhbHVlKG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5UmVtb3ZlJDEobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgZGVsZXRlIHRoaXNbbmFtZV07CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlDb25zdGFudCQxKG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzW25hbWVdID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlGdW5jdGlvbiQxKG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgZGVsZXRlIHRoaXNbbmFtZV07CiAgICAgICAgZWxzZSB0aGlzW25hbWVdID0gdjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fcHJvcGVydHkkMShuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA+IDEKICAgICAgICAgID8gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyBwcm9wZXJ0eVJlbW92ZSQxIDogdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBwcm9wZXJ0eUZ1bmN0aW9uJDEKICAgICAgICAgICAgICA6IHByb3BlcnR5Q29uc3RhbnQkMSkobmFtZSwgdmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKVtuYW1lXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc0FycmF5JDEoc3RyaW5nKSB7CiAgICAgIHJldHVybiBzdHJpbmcudHJpbSgpLnNwbGl0KC9efFxzKy8pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzTGlzdCQxKG5vZGUpIHsKICAgICAgcmV0dXJuIG5vZGUuY2xhc3NMaXN0IHx8IG5ldyBDbGFzc0xpc3QkMShub2RlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBDbGFzc0xpc3QkMShub2RlKSB7CiAgICAgIHRoaXMuX25vZGUgPSBub2RlOwogICAgICB0aGlzLl9uYW1lcyA9IGNsYXNzQXJyYXkkMShub2RlLmdldEF0dHJpYnV0ZSgiY2xhc3MiKSB8fCAiIik7CiAgICB9CgogICAgQ2xhc3NMaXN0JDEucHJvdG90eXBlID0gewogICAgICBhZGQ6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICB2YXIgaSA9IHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSk7CiAgICAgICAgaWYgKGkgPCAwKSB7CiAgICAgICAgICB0aGlzLl9uYW1lcy5wdXNoKG5hbWUpOwogICAgICAgICAgdGhpcy5fbm9kZS5zZXRBdHRyaWJ1dGUoImNsYXNzIiwgdGhpcy5fbmFtZXMuam9pbigiICIpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIHJlbW92ZTogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHZhciBpID0gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKTsKICAgICAgICBpZiAoaSA+PSAwKSB7CiAgICAgICAgICB0aGlzLl9uYW1lcy5zcGxpY2UoaSwgMSk7CiAgICAgICAgICB0aGlzLl9ub2RlLnNldEF0dHJpYnV0ZSgiY2xhc3MiLCB0aGlzLl9uYW1lcy5qb2luKCIgIikpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgY29udGFpbnM6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICByZXR1cm4gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKSA+PSAwOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNsYXNzZWRBZGQkMShub2RlLCBuYW1lcykgewogICAgICB2YXIgbGlzdCA9IGNsYXNzTGlzdCQxKG5vZGUpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBsaXN0LmFkZChuYW1lc1tpXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZFJlbW92ZSQxKG5vZGUsIG5hbWVzKSB7CiAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0JDEobm9kZSksIGkgPSAtMSwgbiA9IG5hbWVzLmxlbmd0aDsKICAgICAgd2hpbGUgKCsraSA8IG4pIGxpc3QucmVtb3ZlKG5hbWVzW2ldKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkVHJ1ZSQxKG5hbWVzKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBjbGFzc2VkQWRkJDEodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRGYWxzZSQxKG5hbWVzKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBjbGFzc2VkUmVtb3ZlJDEodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRGdW5jdGlvbiQxKG5hbWVzLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgKHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgPyBjbGFzc2VkQWRkJDEgOiBjbGFzc2VkUmVtb3ZlJDEpKHRoaXMsIG5hbWVzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xhc3NlZCQxKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBuYW1lcyA9IGNsYXNzQXJyYXkkMShuYW1lICsgIiIpOwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3QkMSh0aGlzLm5vZGUoKSksIGkgPSAtMSwgbiA9IG5hbWVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKCFsaXN0LmNvbnRhaW5zKG5hbWVzW2ldKSkgcmV0dXJuIGZhbHNlOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CgogICAgICByZXR1cm4gdGhpcy5lYWNoKCh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gY2xhc3NlZEZ1bmN0aW9uJDEgOiB2YWx1ZQogICAgICAgICAgPyBjbGFzc2VkVHJ1ZSQxCiAgICAgICAgICA6IGNsYXNzZWRGYWxzZSQxKShuYW1lcywgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0UmVtb3ZlJDEoKSB7CiAgICAgIHRoaXMudGV4dENvbnRlbnQgPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0Q29uc3RhbnQkMih2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRGdW5jdGlvbiQyKHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHYgPT0gbnVsbCA/ICIiIDogdjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fdGV4dCQxKHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyB0ZXh0UmVtb3ZlJDEgOiAodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyB0ZXh0RnVuY3Rpb24kMgogICAgICAgICAgICAgIDogdGV4dENvbnN0YW50JDIpKHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKCkudGV4dENvbnRlbnQ7CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbFJlbW92ZSQxKCkgewogICAgICB0aGlzLmlubmVySFRNTCA9ICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIGh0bWxDb25zdGFudCQxKHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLmlubmVySFRNTCA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGh0bWxGdW5jdGlvbiQxKHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgdGhpcy5pbm5lckhUTUwgPSB2ID09IG51bGwgPyAiIiA6IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2h0bWwkMSh2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2godmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgID8gaHRtbFJlbW92ZSQxIDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gaHRtbEZ1bmN0aW9uJDEKICAgICAgICAgICAgICA6IGh0bWxDb25zdGFudCQxKSh2YWx1ZSkpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLmlubmVySFRNTDsKICAgIH0KCiAgICBmdW5jdGlvbiByYWlzZSQxKCkgewogICAgICBpZiAodGhpcy5uZXh0U2libGluZykgdGhpcy5wYXJlbnROb2RlLmFwcGVuZENoaWxkKHRoaXMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9yYWlzZSQxKCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKHJhaXNlJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxvd2VyJDEoKSB7CiAgICAgIGlmICh0aGlzLnByZXZpb3VzU2libGluZykgdGhpcy5wYXJlbnROb2RlLmluc2VydEJlZm9yZSh0aGlzLCB0aGlzLnBhcmVudE5vZGUuZmlyc3RDaGlsZCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2xvd2VyJDEoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2gobG93ZXIkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2FwcGVuZCQxKG5hbWUpIHsKICAgICAgdmFyIGNyZWF0ZSA9IHR5cGVvZiBuYW1lID09PSAiZnVuY3Rpb24iID8gbmFtZSA6IGNyZWF0b3IkMShuYW1lKTsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLmFwcGVuZENoaWxkKGNyZWF0ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnROdWxsJDEoKSB7CiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9pbnNlcnQkMShuYW1lLCBiZWZvcmUpIHsKICAgICAgdmFyIGNyZWF0ZSA9IHR5cGVvZiBuYW1lID09PSAiZnVuY3Rpb24iID8gbmFtZSA6IGNyZWF0b3IkMShuYW1lKSwKICAgICAgICAgIHNlbGVjdCA9IGJlZm9yZSA9PSBudWxsID8gY29uc3RhbnROdWxsJDEgOiB0eXBlb2YgYmVmb3JlID09PSAiZnVuY3Rpb24iID8gYmVmb3JlIDogc2VsZWN0b3IkMShiZWZvcmUpOwogICAgICByZXR1cm4gdGhpcy5zZWxlY3QoZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaW5zZXJ0QmVmb3JlKGNyZWF0ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCBzZWxlY3QuYXBwbHkodGhpcywgYXJndW1lbnRzKSB8fCBudWxsKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlJDEoKSB7CiAgICAgIHZhciBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIGlmIChwYXJlbnQpIHBhcmVudC5yZW1vdmVDaGlsZCh0aGlzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fcmVtb3ZlJDEoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2gocmVtb3ZlJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZVNoYWxsb3ckMSgpIHsKICAgICAgdmFyIGNsb25lID0gdGhpcy5jbG9uZU5vZGUoZmFsc2UpLCBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIHJldHVybiBwYXJlbnQgPyBwYXJlbnQuaW5zZXJ0QmVmb3JlKGNsb25lLCB0aGlzLm5leHRTaWJsaW5nKSA6IGNsb25lOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZURlZXAkMSgpIHsKICAgICAgdmFyIGNsb25lID0gdGhpcy5jbG9uZU5vZGUodHJ1ZSksIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgcmV0dXJuIHBhcmVudCA/IHBhcmVudC5pbnNlcnRCZWZvcmUoY2xvbmUsIHRoaXMubmV4dFNpYmxpbmcpIDogY2xvbmU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Nsb25lJDEoZGVlcCkgewogICAgICByZXR1cm4gdGhpcy5zZWxlY3QoZGVlcCA/IHNlbGVjdGlvbl9jbG9uZURlZXAkMSA6IHNlbGVjdGlvbl9jbG9uZVNoYWxsb3ckMSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2RhdHVtJDEodmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5wcm9wZXJ0eSgiX19kYXRhX18iLCB2YWx1ZSkKICAgICAgICAgIDogdGhpcy5ub2RlKCkuX19kYXRhX187CiAgICB9CgogICAgdmFyIGZpbHRlckV2ZW50cyQxID0ge307CgogICAgdmFyIGV2ZW50JDEgPSBudWxsOwoKICAgIGlmICh0eXBlb2YgZG9jdW1lbnQgIT09ICJ1bmRlZmluZWQiKSB7CiAgICAgIHZhciBlbGVtZW50JDEgPSBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQ7CiAgICAgIGlmICghKCJvbm1vdXNlZW50ZXIiIGluIGVsZW1lbnQkMSkpIHsKICAgICAgICBmaWx0ZXJFdmVudHMkMSA9IHttb3VzZWVudGVyOiAibW91c2VvdmVyIiwgbW91c2VsZWF2ZTogIm1vdXNlb3V0In07CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBmaWx0ZXJDb250ZXh0TGlzdGVuZXIkMShsaXN0ZW5lciwgaW5kZXgsIGdyb3VwKSB7CiAgICAgIGxpc3RlbmVyID0gY29udGV4dExpc3RlbmVyJDEobGlzdGVuZXIsIGluZGV4LCBncm91cCk7CiAgICAgIHJldHVybiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciByZWxhdGVkID0gZXZlbnQucmVsYXRlZFRhcmdldDsKICAgICAgICBpZiAoIXJlbGF0ZWQgfHwgKHJlbGF0ZWQgIT09IHRoaXMgJiYgIShyZWxhdGVkLmNvbXBhcmVEb2N1bWVudFBvc2l0aW9uKHRoaXMpICYgOCkpKSB7CiAgICAgICAgICBsaXN0ZW5lci5jYWxsKHRoaXMsIGV2ZW50KTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY29udGV4dExpc3RlbmVyJDEobGlzdGVuZXIsIGluZGV4LCBncm91cCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oZXZlbnQxKSB7CiAgICAgICAgdmFyIGV2ZW50MCA9IGV2ZW50JDE7IC8vIEV2ZW50cyBjYW4gYmUgcmVlbnRyYW50IChlLmcuLCBmb2N1cykuCiAgICAgICAgZXZlbnQkMSA9IGV2ZW50MTsKICAgICAgICB0cnkgewogICAgICAgICAgbGlzdGVuZXIuY2FsbCh0aGlzLCB0aGlzLl9fZGF0YV9fLCBpbmRleCwgZ3JvdXApOwogICAgICAgIH0gZmluYWxseSB7CiAgICAgICAgICBldmVudCQxID0gZXZlbnQwOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVR5cGVuYW1lcyQzKHR5cGVuYW1lcykgewogICAgICByZXR1cm4gdHlwZW5hbWVzLnRyaW0oKS5zcGxpdCgvXnxccysvKS5tYXAoZnVuY3Rpb24odCkgewogICAgICAgIHZhciBuYW1lID0gIiIsIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSBuYW1lID0gdC5zbGljZShpICsgMSksIHQgPSB0LnNsaWNlKDAsIGkpOwogICAgICAgIHJldHVybiB7dHlwZTogdCwgbmFtZTogbmFtZX07CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIG9uUmVtb3ZlJDEodHlwZW5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBvbiA9IHRoaXMuX19vbjsKICAgICAgICBpZiAoIW9uKSByZXR1cm47CiAgICAgICAgZm9yICh2YXIgaiA9IDAsIGkgPSAtMSwgbSA9IG9uLmxlbmd0aCwgbzsgaiA8IG07ICsraikgewogICAgICAgICAgaWYgKG8gPSBvbltqXSwgKCF0eXBlbmFtZS50eXBlIHx8IG8udHlwZSA9PT0gdHlwZW5hbWUudHlwZSkgJiYgby5uYW1lID09PSB0eXBlbmFtZS5uYW1lKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIsIG8uY2FwdHVyZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBvblsrK2ldID0gbzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKCsraSkgb24ubGVuZ3RoID0gaTsKICAgICAgICBlbHNlIGRlbGV0ZSB0aGlzLl9fb247CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb25BZGQkMSh0eXBlbmFtZSwgdmFsdWUsIGNhcHR1cmUpIHsKICAgICAgdmFyIHdyYXAgPSBmaWx0ZXJFdmVudHMkMS5oYXNPd25Qcm9wZXJ0eSh0eXBlbmFtZS50eXBlKSA/IGZpbHRlckNvbnRleHRMaXN0ZW5lciQxIDogY29udGV4dExpc3RlbmVyJDE7CiAgICAgIHJldHVybiBmdW5jdGlvbihkLCBpLCBncm91cCkgewogICAgICAgIHZhciBvbiA9IHRoaXMuX19vbiwgbywgbGlzdGVuZXIgPSB3cmFwKHZhbHVlLCBpLCBncm91cCk7CiAgICAgICAgaWYgKG9uKSBmb3IgKHZhciBqID0gMCwgbSA9IG9uLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgICAgaWYgKChvID0gb25bal0pLnR5cGUgPT09IHR5cGVuYW1lLnR5cGUgJiYgby5uYW1lID09PSB0eXBlbmFtZS5uYW1lKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIsIG8uY2FwdHVyZSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIgPSBsaXN0ZW5lciwgby5jYXB0dXJlID0gY2FwdHVyZSk7CiAgICAgICAgICAgIG8udmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIodHlwZW5hbWUudHlwZSwgbGlzdGVuZXIsIGNhcHR1cmUpOwogICAgICAgIG8gPSB7dHlwZTogdHlwZW5hbWUudHlwZSwgbmFtZTogdHlwZW5hbWUubmFtZSwgdmFsdWU6IHZhbHVlLCBsaXN0ZW5lcjogbGlzdGVuZXIsIGNhcHR1cmU6IGNhcHR1cmV9OwogICAgICAgIGlmICghb24pIHRoaXMuX19vbiA9IFtvXTsKICAgICAgICBlbHNlIG9uLnB1c2gobyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX29uJDEodHlwZW5hbWUsIHZhbHVlLCBjYXB0dXJlKSB7CiAgICAgIHZhciB0eXBlbmFtZXMgPSBwYXJzZVR5cGVuYW1lcyQzKHR5cGVuYW1lICsgIiIpLCBpLCBuID0gdHlwZW5hbWVzLmxlbmd0aCwgdDsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBvbiA9IHRoaXMubm9kZSgpLl9fb247CiAgICAgICAgaWYgKG9uKSBmb3IgKHZhciBqID0gMCwgbSA9IG9uLmxlbmd0aCwgbzsgaiA8IG07ICsraikgewogICAgICAgICAgZm9yIChpID0gMCwgbyA9IG9uW2pdOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGlmICgodCA9IHR5cGVuYW1lc1tpXSkudHlwZSA9PT0gby50eXBlICYmIHQubmFtZSA9PT0gby5uYW1lKSB7CiAgICAgICAgICAgICAgcmV0dXJuIG8udmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBvbiA9IHZhbHVlID8gb25BZGQkMSA6IG9uUmVtb3ZlJDE7CiAgICAgIGlmIChjYXB0dXJlID09IG51bGwpIGNhcHR1cmUgPSBmYWxzZTsKICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgdGhpcy5lYWNoKG9uKHR5cGVuYW1lc1tpXSwgdmFsdWUsIGNhcHR1cmUpKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gY3VzdG9tRXZlbnQkMShldmVudDEsIGxpc3RlbmVyLCB0aGF0LCBhcmdzKSB7CiAgICAgIHZhciBldmVudDAgPSBldmVudCQxOwogICAgICBldmVudDEuc291cmNlRXZlbnQgPSBldmVudCQxOwogICAgICBldmVudCQxID0gZXZlbnQxOwogICAgICB0cnkgewogICAgICAgIHJldHVybiBsaXN0ZW5lci5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBldmVudCQxID0gZXZlbnQwOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hFdmVudCQxKG5vZGUsIHR5cGUsIHBhcmFtcykgewogICAgICB2YXIgd2luZG93ID0gZGVmYXVsdFZpZXckMShub2RlKSwKICAgICAgICAgIGV2ZW50ID0gd2luZG93LkN1c3RvbUV2ZW50OwoKICAgICAgaWYgKHR5cGVvZiBldmVudCA9PT0gImZ1bmN0aW9uIikgewogICAgICAgIGV2ZW50ID0gbmV3IGV2ZW50KHR5cGUsIHBhcmFtcyk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgZXZlbnQgPSB3aW5kb3cuZG9jdW1lbnQuY3JlYXRlRXZlbnQoIkV2ZW50Iik7CiAgICAgICAgaWYgKHBhcmFtcykgZXZlbnQuaW5pdEV2ZW50KHR5cGUsIHBhcmFtcy5idWJibGVzLCBwYXJhbXMuY2FuY2VsYWJsZSksIGV2ZW50LmRldGFpbCA9IHBhcmFtcy5kZXRhaWw7CiAgICAgICAgZWxzZSBldmVudC5pbml0RXZlbnQodHlwZSwgZmFsc2UsIGZhbHNlKTsKICAgICAgfQoKICAgICAgbm9kZS5kaXNwYXRjaEV2ZW50KGV2ZW50KTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXNwYXRjaENvbnN0YW50JDEodHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gZGlzcGF0Y2hFdmVudCQxKHRoaXMsIHR5cGUsIHBhcmFtcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hGdW5jdGlvbiQxKHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRpc3BhdGNoRXZlbnQkMSh0aGlzLCB0eXBlLCBwYXJhbXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Rpc3BhdGNoJDEodHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiBwYXJhbXMgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gZGlzcGF0Y2hGdW5jdGlvbiQxCiAgICAgICAgICA6IGRpc3BhdGNoQ29uc3RhbnQkMSkodHlwZSwgcGFyYW1zKSk7CiAgICB9CgogICAgdmFyIHJvb3QkMyA9IFtudWxsXTsKCiAgICBmdW5jdGlvbiBTZWxlY3Rpb24kMihncm91cHMsIHBhcmVudHMpIHsKICAgICAgdGhpcy5fZ3JvdXBzID0gZ3JvdXBzOwogICAgICB0aGlzLl9wYXJlbnRzID0gcGFyZW50czsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb24kMSgpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kMihbW2RvY3VtZW50LmRvY3VtZW50RWxlbWVudF1dLCByb290JDMpOwogICAgfQoKICAgIFNlbGVjdGlvbiQyLnByb3RvdHlwZSA9IHNlbGVjdGlvbiQxLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFNlbGVjdGlvbiQyLAogICAgICBzZWxlY3Q6IHNlbGVjdGlvbl9zZWxlY3QkMSwKICAgICAgc2VsZWN0QWxsOiBzZWxlY3Rpb25fc2VsZWN0QWxsJDEsCiAgICAgIGZpbHRlcjogc2VsZWN0aW9uX2ZpbHRlciQxLAogICAgICBkYXRhOiBzZWxlY3Rpb25fZGF0YSQxLAogICAgICBlbnRlcjogc2VsZWN0aW9uX2VudGVyJDEsCiAgICAgIGV4aXQ6IHNlbGVjdGlvbl9leGl0JDEsCiAgICAgIGpvaW46IHNlbGVjdGlvbl9qb2luJDEsCiAgICAgIG1lcmdlOiBzZWxlY3Rpb25fbWVyZ2UkMSwKICAgICAgb3JkZXI6IHNlbGVjdGlvbl9vcmRlciQxLAogICAgICBzb3J0OiBzZWxlY3Rpb25fc29ydCQxLAogICAgICBjYWxsOiBzZWxlY3Rpb25fY2FsbCQxLAogICAgICBub2Rlczogc2VsZWN0aW9uX25vZGVzJDEsCiAgICAgIG5vZGU6IHNlbGVjdGlvbl9ub2RlJDEsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9zaXplJDEsCiAgICAgIGVtcHR5OiBzZWxlY3Rpb25fZW1wdHkkMSwKICAgICAgZWFjaDogc2VsZWN0aW9uX2VhY2gkMSwKICAgICAgYXR0cjogc2VsZWN0aW9uX2F0dHIkMSwKICAgICAgc3R5bGU6IHNlbGVjdGlvbl9zdHlsZSQxLAogICAgICBwcm9wZXJ0eTogc2VsZWN0aW9uX3Byb3BlcnR5JDEsCiAgICAgIGNsYXNzZWQ6IHNlbGVjdGlvbl9jbGFzc2VkJDEsCiAgICAgIHRleHQ6IHNlbGVjdGlvbl90ZXh0JDEsCiAgICAgIGh0bWw6IHNlbGVjdGlvbl9odG1sJDEsCiAgICAgIHJhaXNlOiBzZWxlY3Rpb25fcmFpc2UkMSwKICAgICAgbG93ZXI6IHNlbGVjdGlvbl9sb3dlciQxLAogICAgICBhcHBlbmQ6IHNlbGVjdGlvbl9hcHBlbmQkMSwKICAgICAgaW5zZXJ0OiBzZWxlY3Rpb25faW5zZXJ0JDEsCiAgICAgIHJlbW92ZTogc2VsZWN0aW9uX3JlbW92ZSQxLAogICAgICBjbG9uZTogc2VsZWN0aW9uX2Nsb25lJDEsCiAgICAgIGRhdHVtOiBzZWxlY3Rpb25fZGF0dW0kMSwKICAgICAgb246IHNlbGVjdGlvbl9vbiQxLAogICAgICBkaXNwYXRjaDogc2VsZWN0aW9uX2Rpc3BhdGNoJDEKICAgIH07CgogICAgZnVuY3Rpb24gc2VsZWN0JDEoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHR5cGVvZiBzZWxlY3RvciA9PT0gInN0cmluZyIKICAgICAgICAgID8gbmV3IFNlbGVjdGlvbiQyKFtbZG9jdW1lbnQucXVlcnlTZWxlY3RvcihzZWxlY3RvcildXSwgW2RvY3VtZW50LmRvY3VtZW50RWxlbWVudF0pCiAgICAgICAgICA6IG5ldyBTZWxlY3Rpb24kMihbW3NlbGVjdG9yXV0sIHJvb3QkMyk7CiAgICB9CgogICAgZnVuY3Rpb24gc291cmNlRXZlbnQkMSgpIHsKICAgICAgdmFyIGN1cnJlbnQgPSBldmVudCQxLCBzb3VyY2U7CiAgICAgIHdoaWxlIChzb3VyY2UgPSBjdXJyZW50LnNvdXJjZUV2ZW50KSBjdXJyZW50ID0gc291cmNlOwogICAgICByZXR1cm4gY3VycmVudDsKICAgIH0KCiAgICBmdW5jdGlvbiBwb2ludCQ2KG5vZGUsIGV2ZW50KSB7CiAgICAgIHZhciBzdmcgPSBub2RlLm93bmVyU1ZHRWxlbWVudCB8fCBub2RlOwoKICAgICAgaWYgKHN2Zy5jcmVhdGVTVkdQb2ludCkgewogICAgICAgIHZhciBwb2ludCA9IHN2Zy5jcmVhdGVTVkdQb2ludCgpOwogICAgICAgIHBvaW50LnggPSBldmVudC5jbGllbnRYLCBwb2ludC55ID0gZXZlbnQuY2xpZW50WTsKICAgICAgICBwb2ludCA9IHBvaW50Lm1hdHJpeFRyYW5zZm9ybShub2RlLmdldFNjcmVlbkNUTSgpLmludmVyc2UoKSk7CiAgICAgICAgcmV0dXJuIFtwb2ludC54LCBwb2ludC55XTsKICAgICAgfQoKICAgICAgdmFyIHJlY3QgPSBub2RlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICByZXR1cm4gW2V2ZW50LmNsaWVudFggLSByZWN0LmxlZnQgLSBub2RlLmNsaWVudExlZnQsIGV2ZW50LmNsaWVudFkgLSByZWN0LnRvcCAtIG5vZGUuY2xpZW50VG9wXTsKICAgIH0KCiAgICBmdW5jdGlvbiBtb3VzZSQxKG5vZGUpIHsKICAgICAgdmFyIGV2ZW50ID0gc291cmNlRXZlbnQkMSgpOwogICAgICBpZiAoZXZlbnQuY2hhbmdlZFRvdWNoZXMpIGV2ZW50ID0gZXZlbnQuY2hhbmdlZFRvdWNoZXNbMF07CiAgICAgIHJldHVybiBwb2ludCQ2KG5vZGUsIGV2ZW50KTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2V2ZW50JDMoKSB7CiAgICAgIGV2ZW50JDEucHJldmVudERlZmF1bHQoKTsKICAgICAgZXZlbnQkMS5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkcmFnRGlzYWJsZSQxKHZpZXcpIHsKICAgICAgdmFyIHJvb3QgPSB2aWV3LmRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwKICAgICAgICAgIHNlbGVjdGlvbiA9IHNlbGVjdCQxKHZpZXcpLm9uKCJkcmFnc3RhcnQuZHJhZyIsIG5vZXZlbnQkMywgdHJ1ZSk7CiAgICAgIGlmICgib25zZWxlY3RzdGFydCIgaW4gcm9vdCkgewogICAgICAgIHNlbGVjdGlvbi5vbigic2VsZWN0c3RhcnQuZHJhZyIsIG5vZXZlbnQkMywgdHJ1ZSk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcm9vdC5fX25vc2VsZWN0ID0gcm9vdC5zdHlsZS5Nb3pVc2VyU2VsZWN0OwogICAgICAgIHJvb3Quc3R5bGUuTW96VXNlclNlbGVjdCA9ICJub25lIjsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHllc2RyYWckMSh2aWV3LCBub2NsaWNrKSB7CiAgICAgIHZhciByb290ID0gdmlldy5kb2N1bWVudC5kb2N1bWVudEVsZW1lbnQsCiAgICAgICAgICBzZWxlY3Rpb24gPSBzZWxlY3QkMSh2aWV3KS5vbigiZHJhZ3N0YXJ0LmRyYWciLCBudWxsKTsKICAgICAgaWYgKG5vY2xpY2spIHsKICAgICAgICBzZWxlY3Rpb24ub24oImNsaWNrLmRyYWciLCBub2V2ZW50JDMsIHRydWUpOwogICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHNlbGVjdGlvbi5vbigiY2xpY2suZHJhZyIsIG51bGwpOyB9LCAwKTsKICAgICAgfQogICAgICBpZiAoIm9uc2VsZWN0c3RhcnQiIGluIHJvb3QpIHsKICAgICAgICBzZWxlY3Rpb24ub24oInNlbGVjdHN0YXJ0LmRyYWciLCBudWxsKTsKICAgICAgfSBlbHNlIHsKICAgICAgICByb290LnN0eWxlLk1velVzZXJTZWxlY3QgPSByb290Ll9fbm9zZWxlY3Q7CiAgICAgICAgZGVsZXRlIHJvb3QuX19ub3NlbGVjdDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmluZSQxKGNvbnN0cnVjdG9yLCBmYWN0b3J5LCBwcm90b3R5cGUpIHsKICAgICAgY29uc3RydWN0b3IucHJvdG90eXBlID0gZmFjdG9yeS5wcm90b3R5cGUgPSBwcm90b3R5cGU7CiAgICAgIHByb3RvdHlwZS5jb25zdHJ1Y3RvciA9IGNvbnN0cnVjdG9yOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVuZCQxKHBhcmVudCwgZGVmaW5pdGlvbikgewogICAgICB2YXIgcHJvdG90eXBlID0gT2JqZWN0LmNyZWF0ZShwYXJlbnQucHJvdG90eXBlKTsKICAgICAgZm9yICh2YXIga2V5IGluIGRlZmluaXRpb24pIHByb3RvdHlwZVtrZXldID0gZGVmaW5pdGlvbltrZXldOwogICAgICByZXR1cm4gcHJvdG90eXBlOwogICAgfQoKICAgIGZ1bmN0aW9uIENvbG9yJDEoKSB7fQoKICAgIHZhciBkYXJrZXIkMSA9IDAuNzsKICAgIHZhciBicmlnaHRlciQxID0gMSAvIGRhcmtlciQxOwoKICAgIHZhciByZUkkMSA9ICJcXHMqKFsrLV0/XFxkKylcXHMqIiwKICAgICAgICByZU4kMSA9ICJcXHMqKFsrLV0/XFxkKlxcLj9cXGQrKD86W2VFXVsrLV0/XFxkKyk/KVxccyoiLAogICAgICAgIHJlUCQxID0gIlxccyooWystXT9cXGQqXFwuP1xcZCsoPzpbZUVdWystXT9cXGQrKT8pJVxccyoiLAogICAgICAgIHJlSGV4JDEgPSAvXiMoWzAtOWEtZl17Myw4fSkkLywKICAgICAgICByZVJnYkludGVnZXIkMSA9IG5ldyBSZWdFeHAoIl5yZ2JcXCgiICsgW3JlSSQxLCByZUkkMSwgcmVJJDFdICsgIlxcKSQiKSwKICAgICAgICByZVJnYlBlcmNlbnQkMSA9IG5ldyBSZWdFeHAoIl5yZ2JcXCgiICsgW3JlUCQxLCByZVAkMSwgcmVQJDFdICsgIlxcKSQiKSwKICAgICAgICByZVJnYmFJbnRlZ2VyJDEgPSBuZXcgUmVnRXhwKCJecmdiYVxcKCIgKyBbcmVJJDEsIHJlSSQxLCByZUkkMSwgcmVOJDFdICsgIlxcKSQiKSwKICAgICAgICByZVJnYmFQZXJjZW50JDEgPSBuZXcgUmVnRXhwKCJecmdiYVxcKCIgKyBbcmVQJDEsIHJlUCQxLCByZVAkMSwgcmVOJDFdICsgIlxcKSQiKSwKICAgICAgICByZUhzbFBlcmNlbnQkMSA9IG5ldyBSZWdFeHAoIl5oc2xcXCgiICsgW3JlTiQxLCByZVAkMSwgcmVQJDFdICsgIlxcKSQiKSwKICAgICAgICByZUhzbGFQZXJjZW50JDEgPSBuZXcgUmVnRXhwKCJeaHNsYVxcKCIgKyBbcmVOJDEsIHJlUCQxLCByZVAkMSwgcmVOJDFdICsgIlxcKSQiKTsKCiAgICB2YXIgbmFtZWQkMSA9IHsKICAgICAgYWxpY2VibHVlOiAweGYwZjhmZiwKICAgICAgYW50aXF1ZXdoaXRlOiAweGZhZWJkNywKICAgICAgYXF1YTogMHgwMGZmZmYsCiAgICAgIGFxdWFtYXJpbmU6IDB4N2ZmZmQ0LAogICAgICBhenVyZTogMHhmMGZmZmYsCiAgICAgIGJlaWdlOiAweGY1ZjVkYywKICAgICAgYmlzcXVlOiAweGZmZTRjNCwKICAgICAgYmxhY2s6IDB4MDAwMDAwLAogICAgICBibGFuY2hlZGFsbW9uZDogMHhmZmViY2QsCiAgICAgIGJsdWU6IDB4MDAwMGZmLAogICAgICBibHVldmlvbGV0OiAweDhhMmJlMiwKICAgICAgYnJvd246IDB4YTUyYTJhLAogICAgICBidXJseXdvb2Q6IDB4ZGViODg3LAogICAgICBjYWRldGJsdWU6IDB4NWY5ZWEwLAogICAgICBjaGFydHJldXNlOiAweDdmZmYwMCwKICAgICAgY2hvY29sYXRlOiAweGQyNjkxZSwKICAgICAgY29yYWw6IDB4ZmY3ZjUwLAogICAgICBjb3JuZmxvd2VyYmx1ZTogMHg2NDk1ZWQsCiAgICAgIGNvcm5zaWxrOiAweGZmZjhkYywKICAgICAgY3JpbXNvbjogMHhkYzE0M2MsCiAgICAgIGN5YW46IDB4MDBmZmZmLAogICAgICBkYXJrYmx1ZTogMHgwMDAwOGIsCiAgICAgIGRhcmtjeWFuOiAweDAwOGI4YiwKICAgICAgZGFya2dvbGRlbnJvZDogMHhiODg2MGIsCiAgICAgIGRhcmtncmF5OiAweGE5YTlhOSwKICAgICAgZGFya2dyZWVuOiAweDAwNjQwMCwKICAgICAgZGFya2dyZXk6IDB4YTlhOWE5LAogICAgICBkYXJra2hha2k6IDB4YmRiNzZiLAogICAgICBkYXJrbWFnZW50YTogMHg4YjAwOGIsCiAgICAgIGRhcmtvbGl2ZWdyZWVuOiAweDU1NmIyZiwKICAgICAgZGFya29yYW5nZTogMHhmZjhjMDAsCiAgICAgIGRhcmtvcmNoaWQ6IDB4OTkzMmNjLAogICAgICBkYXJrcmVkOiAweDhiMDAwMCwKICAgICAgZGFya3NhbG1vbjogMHhlOTk2N2EsCiAgICAgIGRhcmtzZWFncmVlbjogMHg4ZmJjOGYsCiAgICAgIGRhcmtzbGF0ZWJsdWU6IDB4NDgzZDhiLAogICAgICBkYXJrc2xhdGVncmF5OiAweDJmNGY0ZiwKICAgICAgZGFya3NsYXRlZ3JleTogMHgyZjRmNGYsCiAgICAgIGRhcmt0dXJxdW9pc2U6IDB4MDBjZWQxLAogICAgICBkYXJrdmlvbGV0OiAweDk0MDBkMywKICAgICAgZGVlcHBpbms6IDB4ZmYxNDkzLAogICAgICBkZWVwc2t5Ymx1ZTogMHgwMGJmZmYsCiAgICAgIGRpbWdyYXk6IDB4Njk2OTY5LAogICAgICBkaW1ncmV5OiAweDY5Njk2OSwKICAgICAgZG9kZ2VyYmx1ZTogMHgxZTkwZmYsCiAgICAgIGZpcmVicmljazogMHhiMjIyMjIsCiAgICAgIGZsb3JhbHdoaXRlOiAweGZmZmFmMCwKICAgICAgZm9yZXN0Z3JlZW46IDB4MjI4YjIyLAogICAgICBmdWNoc2lhOiAweGZmMDBmZiwKICAgICAgZ2FpbnNib3JvOiAweGRjZGNkYywKICAgICAgZ2hvc3R3aGl0ZTogMHhmOGY4ZmYsCiAgICAgIGdvbGQ6IDB4ZmZkNzAwLAogICAgICBnb2xkZW5yb2Q6IDB4ZGFhNTIwLAogICAgICBncmF5OiAweDgwODA4MCwKICAgICAgZ3JlZW46IDB4MDA4MDAwLAogICAgICBncmVlbnllbGxvdzogMHhhZGZmMmYsCiAgICAgIGdyZXk6IDB4ODA4MDgwLAogICAgICBob25leWRldzogMHhmMGZmZjAsCiAgICAgIGhvdHBpbms6IDB4ZmY2OWI0LAogICAgICBpbmRpYW5yZWQ6IDB4Y2Q1YzVjLAogICAgICBpbmRpZ286IDB4NGIwMDgyLAogICAgICBpdm9yeTogMHhmZmZmZjAsCiAgICAgIGtoYWtpOiAweGYwZTY4YywKICAgICAgbGF2ZW5kZXI6IDB4ZTZlNmZhLAogICAgICBsYXZlbmRlcmJsdXNoOiAweGZmZjBmNSwKICAgICAgbGF3bmdyZWVuOiAweDdjZmMwMCwKICAgICAgbGVtb25jaGlmZm9uOiAweGZmZmFjZCwKICAgICAgbGlnaHRibHVlOiAweGFkZDhlNiwKICAgICAgbGlnaHRjb3JhbDogMHhmMDgwODAsCiAgICAgIGxpZ2h0Y3lhbjogMHhlMGZmZmYsCiAgICAgIGxpZ2h0Z29sZGVucm9keWVsbG93OiAweGZhZmFkMiwKICAgICAgbGlnaHRncmF5OiAweGQzZDNkMywKICAgICAgbGlnaHRncmVlbjogMHg5MGVlOTAsCiAgICAgIGxpZ2h0Z3JleTogMHhkM2QzZDMsCiAgICAgIGxpZ2h0cGluazogMHhmZmI2YzEsCiAgICAgIGxpZ2h0c2FsbW9uOiAweGZmYTA3YSwKICAgICAgbGlnaHRzZWFncmVlbjogMHgyMGIyYWEsCiAgICAgIGxpZ2h0c2t5Ymx1ZTogMHg4N2NlZmEsCiAgICAgIGxpZ2h0c2xhdGVncmF5OiAweDc3ODg5OSwKICAgICAgbGlnaHRzbGF0ZWdyZXk6IDB4Nzc4ODk5LAogICAgICBsaWdodHN0ZWVsYmx1ZTogMHhiMGM0ZGUsCiAgICAgIGxpZ2h0eWVsbG93OiAweGZmZmZlMCwKICAgICAgbGltZTogMHgwMGZmMDAsCiAgICAgIGxpbWVncmVlbjogMHgzMmNkMzIsCiAgICAgIGxpbmVuOiAweGZhZjBlNiwKICAgICAgbWFnZW50YTogMHhmZjAwZmYsCiAgICAgIG1hcm9vbjogMHg4MDAwMDAsCiAgICAgIG1lZGl1bWFxdWFtYXJpbmU6IDB4NjZjZGFhLAogICAgICBtZWRpdW1ibHVlOiAweDAwMDBjZCwKICAgICAgbWVkaXVtb3JjaGlkOiAweGJhNTVkMywKICAgICAgbWVkaXVtcHVycGxlOiAweDkzNzBkYiwKICAgICAgbWVkaXVtc2VhZ3JlZW46IDB4M2NiMzcxLAogICAgICBtZWRpdW1zbGF0ZWJsdWU6IDB4N2I2OGVlLAogICAgICBtZWRpdW1zcHJpbmdncmVlbjogMHgwMGZhOWEsCiAgICAgIG1lZGl1bXR1cnF1b2lzZTogMHg0OGQxY2MsCiAgICAgIG1lZGl1bXZpb2xldHJlZDogMHhjNzE1ODUsCiAgICAgIG1pZG5pZ2h0Ymx1ZTogMHgxOTE5NzAsCiAgICAgIG1pbnRjcmVhbTogMHhmNWZmZmEsCiAgICAgIG1pc3R5cm9zZTogMHhmZmU0ZTEsCiAgICAgIG1vY2Nhc2luOiAweGZmZTRiNSwKICAgICAgbmF2YWpvd2hpdGU6IDB4ZmZkZWFkLAogICAgICBuYXZ5OiAweDAwMDA4MCwKICAgICAgb2xkbGFjZTogMHhmZGY1ZTYsCiAgICAgIG9saXZlOiAweDgwODAwMCwKICAgICAgb2xpdmVkcmFiOiAweDZiOGUyMywKICAgICAgb3JhbmdlOiAweGZmYTUwMCwKICAgICAgb3JhbmdlcmVkOiAweGZmNDUwMCwKICAgICAgb3JjaGlkOiAweGRhNzBkNiwKICAgICAgcGFsZWdvbGRlbnJvZDogMHhlZWU4YWEsCiAgICAgIHBhbGVncmVlbjogMHg5OGZiOTgsCiAgICAgIHBhbGV0dXJxdW9pc2U6IDB4YWZlZWVlLAogICAgICBwYWxldmlvbGV0cmVkOiAweGRiNzA5MywKICAgICAgcGFwYXlhd2hpcDogMHhmZmVmZDUsCiAgICAgIHBlYWNocHVmZjogMHhmZmRhYjksCiAgICAgIHBlcnU6IDB4Y2Q4NTNmLAogICAgICBwaW5rOiAweGZmYzBjYiwKICAgICAgcGx1bTogMHhkZGEwZGQsCiAgICAgIHBvd2RlcmJsdWU6IDB4YjBlMGU2LAogICAgICBwdXJwbGU6IDB4ODAwMDgwLAogICAgICByZWJlY2NhcHVycGxlOiAweDY2MzM5OSwKICAgICAgcmVkOiAweGZmMDAwMCwKICAgICAgcm9zeWJyb3duOiAweGJjOGY4ZiwKICAgICAgcm95YWxibHVlOiAweDQxNjllMSwKICAgICAgc2FkZGxlYnJvd246IDB4OGI0NTEzLAogICAgICBzYWxtb246IDB4ZmE4MDcyLAogICAgICBzYW5keWJyb3duOiAweGY0YTQ2MCwKICAgICAgc2VhZ3JlZW46IDB4MmU4YjU3LAogICAgICBzZWFzaGVsbDogMHhmZmY1ZWUsCiAgICAgIHNpZW5uYTogMHhhMDUyMmQsCiAgICAgIHNpbHZlcjogMHhjMGMwYzAsCiAgICAgIHNreWJsdWU6IDB4ODdjZWViLAogICAgICBzbGF0ZWJsdWU6IDB4NmE1YWNkLAogICAgICBzbGF0ZWdyYXk6IDB4NzA4MDkwLAogICAgICBzbGF0ZWdyZXk6IDB4NzA4MDkwLAogICAgICBzbm93OiAweGZmZmFmYSwKICAgICAgc3ByaW5nZ3JlZW46IDB4MDBmZjdmLAogICAgICBzdGVlbGJsdWU6IDB4NDY4MmI0LAogICAgICB0YW46IDB4ZDJiNDhjLAogICAgICB0ZWFsOiAweDAwODA4MCwKICAgICAgdGhpc3RsZTogMHhkOGJmZDgsCiAgICAgIHRvbWF0bzogMHhmZjYzNDcsCiAgICAgIHR1cnF1b2lzZTogMHg0MGUwZDAsCiAgICAgIHZpb2xldDogMHhlZTgyZWUsCiAgICAgIHdoZWF0OiAweGY1ZGViMywKICAgICAgd2hpdGU6IDB4ZmZmZmZmLAogICAgICB3aGl0ZXNtb2tlOiAweGY1ZjVmNSwKICAgICAgeWVsbG93OiAweGZmZmYwMCwKICAgICAgeWVsbG93Z3JlZW46IDB4OWFjZDMyCiAgICB9OwoKICAgIGRlZmluZSQxKENvbG9yJDEsIGNvbG9yJDEsIHsKICAgICAgY29weTogZnVuY3Rpb24oY2hhbm5lbHMpIHsKICAgICAgICByZXR1cm4gT2JqZWN0LmFzc2lnbihuZXcgdGhpcy5jb25zdHJ1Y3RvciwgdGhpcywgY2hhbm5lbHMpOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZGlzcGxheWFibGUoKTsKICAgICAgfSwKICAgICAgaGV4OiBjb2xvcl9mb3JtYXRIZXgkMSwgLy8gRGVwcmVjYXRlZCEgVXNlIGNvbG9yLmZvcm1hdEhleC4KICAgICAgZm9ybWF0SGV4OiBjb2xvcl9mb3JtYXRIZXgkMSwKICAgICAgZm9ybWF0SHNsOiBjb2xvcl9mb3JtYXRIc2wkMSwKICAgICAgZm9ybWF0UmdiOiBjb2xvcl9mb3JtYXRSZ2IkMSwKICAgICAgdG9TdHJpbmc6IGNvbG9yX2Zvcm1hdFJnYiQxCiAgICB9KTsKCiAgICBmdW5jdGlvbiBjb2xvcl9mb3JtYXRIZXgkMSgpIHsKICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZm9ybWF0SGV4KCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0SHNsJDEoKSB7CiAgICAgIHJldHVybiBoc2xDb252ZXJ0JDEodGhpcykuZm9ybWF0SHNsKCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0UmdiJDEoKSB7CiAgICAgIHJldHVybiB0aGlzLnJnYigpLmZvcm1hdFJnYigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yJDEoZm9ybWF0KSB7CiAgICAgIHZhciBtLCBsOwogICAgICBmb3JtYXQgPSAoZm9ybWF0ICsgIiIpLnRyaW0oKS50b0xvd2VyQ2FzZSgpOwogICAgICByZXR1cm4gKG0gPSByZUhleCQxLmV4ZWMoZm9ybWF0KSkgPyAobCA9IG1bMV0ubGVuZ3RoLCBtID0gcGFyc2VJbnQobVsxXSwgMTYpLCBsID09PSA2ID8gcmdibiQxKG0pIC8vICNmZjAwMDAKICAgICAgICAgIDogbCA9PT0gMyA/IG5ldyBSZ2IkMSgobSA+PiA4ICYgMHhmKSB8IChtID4+IDQgJiAweGYwKSwgKG0gPj4gNCAmIDB4ZikgfCAobSAmIDB4ZjApLCAoKG0gJiAweGYpIDw8IDQpIHwgKG0gJiAweGYpLCAxKSAvLyAjZjAwCiAgICAgICAgICA6IGwgPT09IDggPyByZ2JhJDEobSA+PiAyNCAmIDB4ZmYsIG0gPj4gMTYgJiAweGZmLCBtID4+IDggJiAweGZmLCAobSAmIDB4ZmYpIC8gMHhmZikgLy8gI2ZmMDAwMDAwCiAgICAgICAgICA6IGwgPT09IDQgPyByZ2JhJDEoKG0gPj4gMTIgJiAweGYpIHwgKG0gPj4gOCAmIDB4ZjApLCAobSA+PiA4ICYgMHhmKSB8IChtID4+IDQgJiAweGYwKSwgKG0gPj4gNCAmIDB4ZikgfCAobSAmIDB4ZjApLCAoKChtICYgMHhmKSA8PCA0KSB8IChtICYgMHhmKSkgLyAweGZmKSAvLyAjZjAwMAogICAgICAgICAgOiBudWxsKSAvLyBpbnZhbGlkIGhleAogICAgICAgICAgOiAobSA9IHJlUmdiSW50ZWdlciQxLmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiJDEobVsxXSwgbVsyXSwgbVszXSwgMSkgLy8gcmdiKDI1NSwgMCwgMCkKICAgICAgICAgIDogKG0gPSByZVJnYlBlcmNlbnQkMS5leGVjKGZvcm1hdCkpID8gbmV3IFJnYiQxKG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIDEpIC8vIHJnYigxMDAlLCAwJSwgMCUpCiAgICAgICAgICA6IChtID0gcmVSZ2JhSW50ZWdlciQxLmV4ZWMoZm9ybWF0KSkgPyByZ2JhJDEobVsxXSwgbVsyXSwgbVszXSwgbVs0XSkgLy8gcmdiYSgyNTUsIDAsIDAsIDEpCiAgICAgICAgICA6IChtID0gcmVSZ2JhUGVyY2VudCQxLmV4ZWMoZm9ybWF0KSkgPyByZ2JhJDEobVsxXSAqIDI1NSAvIDEwMCwgbVsyXSAqIDI1NSAvIDEwMCwgbVszXSAqIDI1NSAvIDEwMCwgbVs0XSkgLy8gcmdiKDEwMCUsIDAlLCAwJSwgMSkKICAgICAgICAgIDogKG0gPSByZUhzbFBlcmNlbnQkMS5leGVjKGZvcm1hdCkpID8gaHNsYSQxKG1bMV0sIG1bMl0gLyAxMDAsIG1bM10gLyAxMDAsIDEpIC8vIGhzbCgxMjAsIDUwJSwgNTAlKQogICAgICAgICAgOiAobSA9IHJlSHNsYVBlcmNlbnQkMS5leGVjKGZvcm1hdCkpID8gaHNsYSQxKG1bMV0sIG1bMl0gLyAxMDAsIG1bM10gLyAxMDAsIG1bNF0pIC8vIGhzbGEoMTIwLCA1MCUsIDUwJSwgMSkKICAgICAgICAgIDogbmFtZWQkMS5oYXNPd25Qcm9wZXJ0eShmb3JtYXQpID8gcmdibiQxKG5hbWVkJDFbZm9ybWF0XSkgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby1wcm90b3R5cGUtYnVpbHRpbnMKICAgICAgICAgIDogZm9ybWF0ID09PSAidHJhbnNwYXJlbnQiID8gbmV3IFJnYiQxKE5hTiwgTmFOLCBOYU4sIDApCiAgICAgICAgICA6IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gcmdibiQxKG4pIHsKICAgICAgcmV0dXJuIG5ldyBSZ2IkMShuID4+IDE2ICYgMHhmZiwgbiA+PiA4ICYgMHhmZiwgbiAmIDB4ZmYsIDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYmEkMShyLCBnLCBiLCBhKSB7CiAgICAgIGlmIChhIDw9IDApIHIgPSBnID0gYiA9IE5hTjsKICAgICAgcmV0dXJuIG5ldyBSZ2IkMShyLCBnLCBiLCBhKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JDb252ZXJ0JDEobykgewogICAgICBpZiAoIShvIGluc3RhbmNlb2YgQ29sb3IkMSkpIG8gPSBjb2xvciQxKG8pOwogICAgICBpZiAoIW8pIHJldHVybiBuZXcgUmdiJDE7CiAgICAgIG8gPSBvLnJnYigpOwogICAgICByZXR1cm4gbmV3IFJnYiQxKG8uciwgby5nLCBvLmIsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiJDEociwgZywgYiwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IHJnYkNvbnZlcnQkMShyKSA6IG5ldyBSZ2IkMShyLCBnLCBiLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gUmdiJDEociwgZywgYiwgb3BhY2l0eSkgewogICAgICB0aGlzLnIgPSArcjsKICAgICAgdGhpcy5nID0gK2c7CiAgICAgIHRoaXMuYiA9ICtiOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkMShSZ2IkMSwgcmdiJDEsIGV4dGVuZCQxKENvbG9yJDEsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIkMSA6IE1hdGgucG93KGJyaWdodGVyJDEsIGspOwogICAgICAgIHJldHVybiBuZXcgUmdiJDEodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciQxIDogTWF0aC5wb3coZGFya2VyJDEsIGspOwogICAgICAgIHJldHVybiBuZXcgUmdiJDEodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoLTAuNSA8PSB0aGlzLnIgJiYgdGhpcy5yIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgtMC41IDw9IHRoaXMuZyAmJiB0aGlzLmcgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKC0wLjUgPD0gdGhpcy5iICYmIHRoaXMuYiA8IDI1NS41KQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9LAogICAgICBoZXg6IHJnYl9mb3JtYXRIZXgkMSwgLy8gRGVwcmVjYXRlZCEgVXNlIGNvbG9yLmZvcm1hdEhleC4KICAgICAgZm9ybWF0SGV4OiByZ2JfZm9ybWF0SGV4JDEsCiAgICAgIGZvcm1hdFJnYjogcmdiX2Zvcm1hdFJnYiQxLAogICAgICB0b1N0cmluZzogcmdiX2Zvcm1hdFJnYiQxCiAgICB9KSk7CgogICAgZnVuY3Rpb24gcmdiX2Zvcm1hdEhleCQxKCkgewogICAgICByZXR1cm4gIiMiICsgaGV4JDEodGhpcy5yKSArIGhleCQxKHRoaXMuZykgKyBoZXgkMSh0aGlzLmIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYl9mb3JtYXRSZ2IkMSgpIHsKICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgIHJldHVybiAoYSA9PT0gMSA/ICJyZ2IoIiA6ICJyZ2JhKCIpCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLnIpIHx8IDApKSArICIsICIKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuZykgfHwgMCkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5iKSB8fCAwKSkKICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICB9CgogICAgZnVuY3Rpb24gaGV4JDEodmFsdWUpIHsKICAgICAgdmFsdWUgPSBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodmFsdWUpIHx8IDApKTsKICAgICAgcmV0dXJuICh2YWx1ZSA8IDE2ID8gIjAiIDogIiIpICsgdmFsdWUudG9TdHJpbmcoMTYpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbGEkMShoLCBzLCBsLCBhKSB7CiAgICAgIGlmIChhIDw9IDApIGggPSBzID0gbCA9IE5hTjsKICAgICAgZWxzZSBpZiAobCA8PSAwIHx8IGwgPj0gMSkgaCA9IHMgPSBOYU47CiAgICAgIGVsc2UgaWYgKHMgPD0gMCkgaCA9IE5hTjsKICAgICAgcmV0dXJuIG5ldyBIc2wkMShoLCBzLCBsLCBhKTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xDb252ZXJ0JDEobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIEhzbCQxKSByZXR1cm4gbmV3IEhzbCQxKG8uaCwgby5zLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvciQxKSkgbyA9IGNvbG9yJDEobyk7CiAgICAgIGlmICghbykgcmV0dXJuIG5ldyBIc2wkMTsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wkMSkgcmV0dXJuIG87CiAgICAgIG8gPSBvLnJnYigpOwogICAgICB2YXIgciA9IG8uciAvIDI1NSwKICAgICAgICAgIGcgPSBvLmcgLyAyNTUsCiAgICAgICAgICBiID0gby5iIC8gMjU1LAogICAgICAgICAgbWluID0gTWF0aC5taW4ociwgZywgYiksCiAgICAgICAgICBtYXggPSBNYXRoLm1heChyLCBnLCBiKSwKICAgICAgICAgIGggPSBOYU4sCiAgICAgICAgICBzID0gbWF4IC0gbWluLAogICAgICAgICAgbCA9IChtYXggKyBtaW4pIC8gMjsKICAgICAgaWYgKHMpIHsKICAgICAgICBpZiAociA9PT0gbWF4KSBoID0gKGcgLSBiKSAvIHMgKyAoZyA8IGIpICogNjsKICAgICAgICBlbHNlIGlmIChnID09PSBtYXgpIGggPSAoYiAtIHIpIC8gcyArIDI7CiAgICAgICAgZWxzZSBoID0gKHIgLSBnKSAvIHMgKyA0OwogICAgICAgIHMgLz0gbCA8IDAuNSA/IG1heCArIG1pbiA6IDIgLSBtYXggLSBtaW47CiAgICAgICAgaCAqPSA2MDsKICAgICAgfSBlbHNlIHsKICAgICAgICBzID0gbCA+IDAgJiYgbCA8IDEgPyAwIDogaDsKICAgICAgfQogICAgICByZXR1cm4gbmV3IEhzbCQxKGgsIHMsIGwsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsJDMoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGhzbENvbnZlcnQkMShoKSA6IG5ldyBIc2wkMShoLCBzLCBsLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gSHNsJDEoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICB0aGlzLmggPSAraDsKICAgICAgdGhpcy5zID0gK3M7CiAgICAgIHRoaXMubCA9ICtsOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkMShIc2wkMSwgaHNsJDMsIGV4dGVuZCQxKENvbG9yJDEsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIkMSA6IE1hdGgucG93KGJyaWdodGVyJDEsIGspOwogICAgICAgIHJldHVybiBuZXcgSHNsJDEodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIkMSA6IE1hdGgucG93KGRhcmtlciQxLCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCQxKHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBoID0gdGhpcy5oICUgMzYwICsgKHRoaXMuaCA8IDApICogMzYwLAogICAgICAgICAgICBzID0gaXNOYU4oaCkgfHwgaXNOYU4odGhpcy5zKSA/IDAgOiB0aGlzLnMsCiAgICAgICAgICAgIGwgPSB0aGlzLmwsCiAgICAgICAgICAgIG0yID0gbCArIChsIDwgMC41ID8gbCA6IDEgLSBsKSAqIHMsCiAgICAgICAgICAgIG0xID0gMiAqIGwgLSBtMjsKICAgICAgICByZXR1cm4gbmV3IFJnYiQxKAogICAgICAgICAgaHNsMnJnYiQxKGggPj0gMjQwID8gaCAtIDI0MCA6IGggKyAxMjAsIG0xLCBtMiksCiAgICAgICAgICBoc2wycmdiJDEoaCwgbTEsIG0yKSwKICAgICAgICAgIGhzbDJyZ2IkMShoIDwgMTIwID8gaCArIDI0MCA6IGggLSAxMjAsIG0xLCBtMiksCiAgICAgICAgICB0aGlzLm9wYWNpdHkKICAgICAgICApOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuICgwIDw9IHRoaXMucyAmJiB0aGlzLnMgPD0gMSB8fCBpc05hTih0aGlzLnMpKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLmwgJiYgdGhpcy5sIDw9IDEpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMub3BhY2l0eSAmJiB0aGlzLm9wYWNpdHkgPD0gMSk7CiAgICAgIH0sCiAgICAgIGZvcm1hdEhzbDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgICAgcmV0dXJuIChhID09PSAxID8gImhzbCgiIDogImhzbGEoIikKICAgICAgICAgICAgKyAodGhpcy5oIHx8IDApICsgIiwgIgogICAgICAgICAgICArICh0aGlzLnMgfHwgMCkgKiAxMDAgKyAiJSwgIgogICAgICAgICAgICArICh0aGlzLmwgfHwgMCkgKiAxMDAgKyAiJSIKICAgICAgICAgICAgKyAoYSA9PT0gMSA/ICIpIiA6ICIsICIgKyBhICsgIikiKTsKICAgICAgfQogICAgfSkpOwoKICAgIC8qIEZyb20gRnZEIDEzLjM3LCBDU1MgQ29sb3IgTW9kdWxlIExldmVsIDMgKi8KICAgIGZ1bmN0aW9uIGhzbDJyZ2IkMShoLCBtMSwgbTIpIHsKICAgICAgcmV0dXJuIChoIDwgNjAgPyBtMSArIChtMiAtIG0xKSAqIGggLyA2MAogICAgICAgICAgOiBoIDwgMTgwID8gbTIKICAgICAgICAgIDogaCA8IDI0MCA/IG0xICsgKG0yIC0gbTEpICogKDI0MCAtIGgpIC8gNjAKICAgICAgICAgIDogbTEpICogMjU1OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGcoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbGluZWFyJDMoYSwgZCkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICsgdCAqIGQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZXhwb25lbnRpYWwkMihhLCBiLCB5KSB7CiAgICAgIHJldHVybiBhID0gTWF0aC5wb3coYSwgeSksIGIgPSBNYXRoLnBvdyhiLCB5KSAtIGEsIHkgPSAxIC8geSwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBNYXRoLnBvdyhhICsgdCAqIGIsIHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGdhbW1hJDEoeSkgewogICAgICByZXR1cm4gKHkgPSAreSkgPT09IDEgPyBub2dhbW1hJDEgOiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgcmV0dXJuIGIgLSBhID8gZXhwb25lbnRpYWwkMihhLCBiLCB5KSA6IGNvbnN0YW50JGcoaXNOYU4oYSkgPyBiIDogYSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbm9nYW1tYSQxKGEsIGIpIHsKICAgICAgdmFyIGQgPSBiIC0gYTsKICAgICAgcmV0dXJuIGQgPyBsaW5lYXIkMyhhLCBkKSA6IGNvbnN0YW50JGcoaXNOYU4oYSkgPyBiIDogYSk7CiAgICB9CgogICAgdmFyIGludGVycG9sYXRlUmdiJDEgPSAoZnVuY3Rpb24gcmdiR2FtbWEoeSkgewogICAgICB2YXIgY29sb3IgPSBnYW1tYSQxKHkpOwoKICAgICAgZnVuY3Rpb24gcmdiKHN0YXJ0LCBlbmQpIHsKICAgICAgICB2YXIgciA9IGNvbG9yKChzdGFydCA9IHJnYiQxKHN0YXJ0KSkuciwgKGVuZCA9IHJnYiQxKGVuZCkpLnIpLAogICAgICAgICAgICBnID0gY29sb3Ioc3RhcnQuZywgZW5kLmcpLAogICAgICAgICAgICBiID0gY29sb3Ioc3RhcnQuYiwgZW5kLmIpLAogICAgICAgICAgICBvcGFjaXR5ID0gbm9nYW1tYSQxKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgc3RhcnQuciA9IHIodCk7CiAgICAgICAgICBzdGFydC5nID0gZyh0KTsKICAgICAgICAgIHN0YXJ0LmIgPSBiKHQpOwogICAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICB9OwogICAgICB9CgogICAgICByZ2IuZ2FtbWEgPSByZ2JHYW1tYTsKCiAgICAgIHJldHVybiByZ2I7CiAgICB9KSgxKTsKCiAgICBmdW5jdGlvbiBudW1iZXJBcnJheSQxKGEsIGIpIHsKICAgICAgaWYgKCFiKSBiID0gW107CiAgICAgIHZhciBuID0gYSA/IE1hdGgubWluKGIubGVuZ3RoLCBhLmxlbmd0aCkgOiAwLAogICAgICAgICAgYyA9IGIuc2xpY2UoKSwKICAgICAgICAgIGk7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgY1tpXSA9IGFbaV0gKiAoMSAtIHQpICsgYltpXSAqIHQ7CiAgICAgICAgcmV0dXJuIGM7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaXNOdW1iZXJBcnJheSQxKHgpIHsKICAgICAgcmV0dXJuIEFycmF5QnVmZmVyLmlzVmlldyh4KSAmJiAhKHggaW5zdGFuY2VvZiBEYXRhVmlldyk7CiAgICB9CgogICAgZnVuY3Rpb24gZ2VuZXJpY0FycmF5JDEoYSwgYikgewogICAgICB2YXIgbmIgPSBiID8gYi5sZW5ndGggOiAwLAogICAgICAgICAgbmEgPSBhID8gTWF0aC5taW4obmIsIGEubGVuZ3RoKSA6IDAsCiAgICAgICAgICB4ID0gbmV3IEFycmF5KG5hKSwKICAgICAgICAgIGMgPSBuZXcgQXJyYXkobmIpLAogICAgICAgICAgaTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuYTsgKytpKSB4W2ldID0gaW50ZXJwb2xhdGUkMihhW2ldLCBiW2ldKTsKICAgICAgZm9yICg7IGkgPCBuYjsgKytpKSBjW2ldID0gYltpXTsKCiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG5hOyArK2kpIGNbaV0gPSB4W2ldKHQpOwogICAgICAgIHJldHVybiBjOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRhdGUkMihhLCBiKSB7CiAgICAgIHZhciBkID0gbmV3IERhdGU7CiAgICAgIHJldHVybiBhID0gK2EsIGIgPSArYiwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBkLnNldFRpbWUoYSAqICgxIC0gdCkgKyBiICogdCksIGQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGVOdW1iZXIkMShhLCBiKSB7CiAgICAgIHJldHVybiBhID0gK2EsIGIgPSArYiwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICogKDEgLSB0KSArIGIgKiB0OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9iamVjdCQyKGEsIGIpIHsKICAgICAgdmFyIGkgPSB7fSwKICAgICAgICAgIGMgPSB7fSwKICAgICAgICAgIGs7CgogICAgICBpZiAoYSA9PT0gbnVsbCB8fCB0eXBlb2YgYSAhPT0gIm9iamVjdCIpIGEgPSB7fTsKICAgICAgaWYgKGIgPT09IG51bGwgfHwgdHlwZW9mIGIgIT09ICJvYmplY3QiKSBiID0ge307CgogICAgICBmb3IgKGsgaW4gYikgewogICAgICAgIGlmIChrIGluIGEpIHsKICAgICAgICAgIGlba10gPSBpbnRlcnBvbGF0ZSQyKGFba10sIGJba10pOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBjW2tdID0gYltrXTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChrIGluIGkpIGNba10gPSBpW2tdKHQpOwogICAgICAgIHJldHVybiBjOwogICAgICB9OwogICAgfQoKICAgIHZhciByZUEkMSA9IC9bLStdPyg/OlxkK1wuP1xkKnxcLj9cZCspKD86W2VFXVstK10/XGQrKT8vZywKICAgICAgICByZUIkMSA9IG5ldyBSZWdFeHAocmVBJDEuc291cmNlLCAiZyIpOwoKICAgIGZ1bmN0aW9uIHplcm8kMShiKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBvbmUkMShiKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGIodCkgKyAiIjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZVN0cmluZyQxKGEsIGIpIHsKICAgICAgdmFyIGJpID0gcmVBJDEubGFzdEluZGV4ID0gcmVCJDEubGFzdEluZGV4ID0gMCwgLy8gc2NhbiBpbmRleCBmb3IgbmV4dCBudW1iZXIgaW4gYgogICAgICAgICAgYW0sIC8vIGN1cnJlbnQgbWF0Y2ggaW4gYQogICAgICAgICAgYm0sIC8vIGN1cnJlbnQgbWF0Y2ggaW4gYgogICAgICAgICAgYnMsIC8vIHN0cmluZyBwcmVjZWRpbmcgY3VycmVudCBudW1iZXIgaW4gYiwgaWYgYW55CiAgICAgICAgICBpID0gLTEsIC8vIGluZGV4IGluIHMKICAgICAgICAgIHMgPSBbXSwgLy8gc3RyaW5nIGNvbnN0YW50cyBhbmQgcGxhY2Vob2xkZXJzCiAgICAgICAgICBxID0gW107IC8vIG51bWJlciBpbnRlcnBvbGF0b3JzCgogICAgICAvLyBDb2VyY2UgaW5wdXRzIHRvIHN0cmluZ3MuCiAgICAgIGEgPSBhICsgIiIsIGIgPSBiICsgIiI7CgogICAgICAvLyBJbnRlcnBvbGF0ZSBwYWlycyBvZiBudW1iZXJzIGluIGEgJiBiLgogICAgICB3aGlsZSAoKGFtID0gcmVBJDEuZXhlYyhhKSkKICAgICAgICAgICYmIChibSA9IHJlQiQxLmV4ZWMoYikpKSB7CiAgICAgICAgaWYgKChicyA9IGJtLmluZGV4KSA+IGJpKSB7IC8vIGEgc3RyaW5nIHByZWNlZGVzIHRoZSBuZXh0IG51bWJlciBpbiBiCiAgICAgICAgICBicyA9IGIuc2xpY2UoYmksIGJzKTsKICAgICAgICAgIGlmIChzW2ldKSBzW2ldICs9IGJzOyAvLyBjb2FsZXNjZSB3aXRoIHByZXZpb3VzIHN0cmluZwogICAgICAgICAgZWxzZSBzWysraV0gPSBiczsKICAgICAgICB9CiAgICAgICAgaWYgKChhbSA9IGFtWzBdKSA9PT0gKGJtID0gYm1bMF0pKSB7IC8vIG51bWJlcnMgaW4gYSAmIGIgbWF0Y2gKICAgICAgICAgIGlmIChzW2ldKSBzW2ldICs9IGJtOyAvLyBjb2FsZXNjZSB3aXRoIHByZXZpb3VzIHN0cmluZwogICAgICAgICAgZWxzZSBzWysraV0gPSBibTsKICAgICAgICB9IGVsc2UgeyAvLyBpbnRlcnBvbGF0ZSBub24tbWF0Y2hpbmcgbnVtYmVycwogICAgICAgICAgc1srK2ldID0gbnVsbDsKICAgICAgICAgIHEucHVzaCh7aTogaSwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMShhbSwgYm0pfSk7CiAgICAgICAgfQogICAgICAgIGJpID0gcmVCJDEubGFzdEluZGV4OwogICAgICB9CgogICAgICAvLyBBZGQgcmVtYWlucyBvZiBiLgogICAgICBpZiAoYmkgPCBiLmxlbmd0aCkgewogICAgICAgIGJzID0gYi5zbGljZShiaSk7CiAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgZWxzZSBzWysraV0gPSBiczsKICAgICAgfQoKICAgICAgLy8gU3BlY2lhbCBvcHRpbWl6YXRpb24gZm9yIG9ubHkgYSBzaW5nbGUgbWF0Y2guCiAgICAgIC8vIE90aGVyd2lzZSwgaW50ZXJwb2xhdGUgZWFjaCBvZiB0aGUgbnVtYmVycyBhbmQgcmVqb2luIHRoZSBzdHJpbmcuCiAgICAgIHJldHVybiBzLmxlbmd0aCA8IDIgPyAocVswXQogICAgICAgICAgPyBvbmUkMShxWzBdLngpCiAgICAgICAgICA6IHplcm8kMShiKSkKICAgICAgICAgIDogKGIgPSBxLmxlbmd0aCwgZnVuY3Rpb24odCkgewogICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBvOyBpIDwgYjsgKytpKSBzWyhvID0gcVtpXSkuaV0gPSBvLngodCk7CiAgICAgICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlJDIoYSwgYikgewogICAgICB2YXIgdCA9IHR5cGVvZiBiLCBjOwogICAgICByZXR1cm4gYiA9PSBudWxsIHx8IHQgPT09ICJib29sZWFuIiA/IGNvbnN0YW50JGcoYikKICAgICAgICAgIDogKHQgPT09ICJudW1iZXIiID8gaW50ZXJwb2xhdGVOdW1iZXIkMQogICAgICAgICAgOiB0ID09PSAic3RyaW5nIiA/ICgoYyA9IGNvbG9yJDEoYikpID8gKGIgPSBjLCBpbnRlcnBvbGF0ZVJnYiQxKSA6IGludGVycG9sYXRlU3RyaW5nJDEpCiAgICAgICAgICA6IGIgaW5zdGFuY2VvZiBjb2xvciQxID8gaW50ZXJwb2xhdGVSZ2IkMQogICAgICAgICAgOiBiIGluc3RhbmNlb2YgRGF0ZSA/IGRhdGUkMgogICAgICAgICAgOiBpc051bWJlckFycmF5JDEoYikgPyBudW1iZXJBcnJheSQxCiAgICAgICAgICA6IEFycmF5LmlzQXJyYXkoYikgPyBnZW5lcmljQXJyYXkkMQogICAgICAgICAgOiB0eXBlb2YgYi52YWx1ZU9mICE9PSAiZnVuY3Rpb24iICYmIHR5cGVvZiBiLnRvU3RyaW5nICE9PSAiZnVuY3Rpb24iIHx8IGlzTmFOKGIpID8gb2JqZWN0JDIKICAgICAgICAgIDogaW50ZXJwb2xhdGVOdW1iZXIkMSkoYSwgYik7CiAgICB9CgogICAgdmFyIGRlZ3JlZXMkMiA9IDE4MCAvIE1hdGguUEk7CgogICAgdmFyIGlkZW50aXR5JGMgPSB7CiAgICAgIHRyYW5zbGF0ZVg6IDAsCiAgICAgIHRyYW5zbGF0ZVk6IDAsCiAgICAgIHJvdGF0ZTogMCwKICAgICAgc2tld1g6IDAsCiAgICAgIHNjYWxlWDogMSwKICAgICAgc2NhbGVZOiAxCiAgICB9OwoKICAgIGZ1bmN0aW9uIGRlY29tcG9zZSQxKGEsIGIsIGMsIGQsIGUsIGYpIHsKICAgICAgdmFyIHNjYWxlWCwgc2NhbGVZLCBza2V3WDsKICAgICAgaWYgKHNjYWxlWCA9IE1hdGguc3FydChhICogYSArIGIgKiBiKSkgYSAvPSBzY2FsZVgsIGIgLz0gc2NhbGVYOwogICAgICBpZiAoc2tld1ggPSBhICogYyArIGIgKiBkKSBjIC09IGEgKiBza2V3WCwgZCAtPSBiICogc2tld1g7CiAgICAgIGlmIChzY2FsZVkgPSBNYXRoLnNxcnQoYyAqIGMgKyBkICogZCkpIGMgLz0gc2NhbGVZLCBkIC89IHNjYWxlWSwgc2tld1ggLz0gc2NhbGVZOwogICAgICBpZiAoYSAqIGQgPCBiICogYykgYSA9IC1hLCBiID0gLWIsIHNrZXdYID0gLXNrZXdYLCBzY2FsZVggPSAtc2NhbGVYOwogICAgICByZXR1cm4gewogICAgICAgIHRyYW5zbGF0ZVg6IGUsCiAgICAgICAgdHJhbnNsYXRlWTogZiwKICAgICAgICByb3RhdGU6IE1hdGguYXRhbjIoYiwgYSkgKiBkZWdyZWVzJDIsCiAgICAgICAgc2tld1g6IE1hdGguYXRhbihza2V3WCkgKiBkZWdyZWVzJDIsCiAgICAgICAgc2NhbGVYOiBzY2FsZVgsCiAgICAgICAgc2NhbGVZOiBzY2FsZVkKICAgICAgfTsKICAgIH0KCiAgICB2YXIgY3NzTm9kZSQxLAogICAgICAgIGNzc1Jvb3QkMSwKICAgICAgICBjc3NWaWV3JDEsCiAgICAgICAgc3ZnTm9kZSQxOwoKICAgIGZ1bmN0aW9uIHBhcnNlQ3NzJDIodmFsdWUpIHsKICAgICAgaWYgKHZhbHVlID09PSAibm9uZSIpIHJldHVybiBpZGVudGl0eSRjOwogICAgICBpZiAoIWNzc05vZGUkMSkgY3NzTm9kZSQxID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgiRElWIiksIGNzc1Jvb3QkMSA9IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwgY3NzVmlldyQxID0gZG9jdW1lbnQuZGVmYXVsdFZpZXc7CiAgICAgIGNzc05vZGUkMS5zdHlsZS50cmFuc2Zvcm0gPSB2YWx1ZTsKICAgICAgdmFsdWUgPSBjc3NWaWV3JDEuZ2V0Q29tcHV0ZWRTdHlsZShjc3NSb290JDEuYXBwZW5kQ2hpbGQoY3NzTm9kZSQxKSwgbnVsbCkuZ2V0UHJvcGVydHlWYWx1ZSgidHJhbnNmb3JtIik7CiAgICAgIGNzc1Jvb3QkMS5yZW1vdmVDaGlsZChjc3NOb2RlJDEpOwogICAgICB2YWx1ZSA9IHZhbHVlLnNsaWNlKDcsIC0xKS5zcGxpdCgiLCIpOwogICAgICByZXR1cm4gZGVjb21wb3NlJDEoK3ZhbHVlWzBdLCArdmFsdWVbMV0sICt2YWx1ZVsyXSwgK3ZhbHVlWzNdLCArdmFsdWVbNF0sICt2YWx1ZVs1XSk7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VTdmckMSh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIGlkZW50aXR5JGM7CiAgICAgIGlmICghc3ZnTm9kZSQxKSBzdmdOb2RlJDEgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiwgImciKTsKICAgICAgc3ZnTm9kZSQxLnNldEF0dHJpYnV0ZSgidHJhbnNmb3JtIiwgdmFsdWUpOwogICAgICBpZiAoISh2YWx1ZSA9IHN2Z05vZGUkMS50cmFuc2Zvcm0uYmFzZVZhbC5jb25zb2xpZGF0ZSgpKSkgcmV0dXJuIGlkZW50aXR5JGM7CiAgICAgIHZhbHVlID0gdmFsdWUubWF0cml4OwogICAgICByZXR1cm4gZGVjb21wb3NlJDEodmFsdWUuYSwgdmFsdWUuYiwgdmFsdWUuYywgdmFsdWUuZCwgdmFsdWUuZSwgdmFsdWUuZik7CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGVUcmFuc2Zvcm0kMShwYXJzZSwgcHhDb21tYSwgcHhQYXJlbiwgZGVnUGFyZW4pIHsKCiAgICAgIGZ1bmN0aW9uIHBvcChzKSB7CiAgICAgICAgcmV0dXJuIHMubGVuZ3RoID8gcy5wb3AoKSArICIgIiA6ICIiOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2xhdGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2goInRyYW5zbGF0ZSgiLCBudWxsLCBweENvbW1hLCBudWxsLCBweFBhcmVuKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IGludGVycG9sYXRlTnVtYmVyJDEoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMSh5YSwgeWIpfSk7CiAgICAgICAgfSBlbHNlIGlmICh4YiB8fCB5YikgewogICAgICAgICAgcy5wdXNoKCJ0cmFuc2xhdGUoIiArIHhiICsgcHhDb21tYSArIHliICsgcHhQYXJlbik7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiByb3RhdGUoYSwgYiwgcywgcSkgewogICAgICAgIGlmIChhICE9PSBiKSB7CiAgICAgICAgICBpZiAoYSAtIGIgPiAxODApIGIgKz0gMzYwOyBlbHNlIGlmIChiIC0gYSA+IDE4MCkgYSArPSAzNjA7IC8vIHNob3J0ZXN0IHBhdGgKICAgICAgICAgIHEucHVzaCh7aTogcy5wdXNoKHBvcChzKSArICJyb3RhdGUoIiwgbnVsbCwgZGVnUGFyZW4pIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMShhLCBiKX0pOwogICAgICAgIH0gZWxzZSBpZiAoYikgewogICAgICAgICAgcy5wdXNoKHBvcChzKSArICJyb3RhdGUoIiArIGIgKyBkZWdQYXJlbik7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBza2V3WChhLCBiLCBzLCBxKSB7CiAgICAgICAgaWYgKGEgIT09IGIpIHsKICAgICAgICAgIHEucHVzaCh7aTogcy5wdXNoKHBvcChzKSArICJza2V3WCgiLCBudWxsLCBkZWdQYXJlbikgLSAyLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQxKGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIgKyBiICsgZGVnUGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIsIG51bGwsICIsIiwgbnVsbCwgIikiKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IGludGVycG9sYXRlTnVtYmVyJDEoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMSh5YSwgeWIpfSk7CiAgICAgICAgfSBlbHNlIGlmICh4YiAhPT0gMSB8fCB5YiAhPT0gMSkgewogICAgICAgICAgcy5wdXNoKHBvcChzKSArICJzY2FsZSgiICsgeGIgKyAiLCIgKyB5YiArICIpIik7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24oYSwgYikgewogICAgICAgIHZhciBzID0gW10sIC8vIHN0cmluZyBjb25zdGFudHMgYW5kIHBsYWNlaG9sZGVycwogICAgICAgICAgICBxID0gW107IC8vIG51bWJlciBpbnRlcnBvbGF0b3JzCiAgICAgICAgYSA9IHBhcnNlKGEpLCBiID0gcGFyc2UoYik7CiAgICAgICAgdHJhbnNsYXRlKGEudHJhbnNsYXRlWCwgYS50cmFuc2xhdGVZLCBiLnRyYW5zbGF0ZVgsIGIudHJhbnNsYXRlWSwgcywgcSk7CiAgICAgICAgcm90YXRlKGEucm90YXRlLCBiLnJvdGF0ZSwgcywgcSk7CiAgICAgICAgc2tld1goYS5za2V3WCwgYi5za2V3WCwgcywgcSk7CiAgICAgICAgc2NhbGUoYS5zY2FsZVgsIGEuc2NhbGVZLCBiLnNjYWxlWCwgYi5zY2FsZVksIHMsIHEpOwogICAgICAgIGEgPSBiID0gbnVsbDsgLy8gZ2MKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgdmFyIGkgPSAtMSwgbiA9IHEubGVuZ3RoLCBvOwogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHNbKG8gPSBxW2ldKS5pXSA9IG8ueCh0KTsKICAgICAgICAgIHJldHVybiBzLmpvaW4oIiIpOwogICAgICAgIH07CiAgICAgIH07CiAgICB9CgogICAgdmFyIGludGVycG9sYXRlVHJhbnNmb3JtQ3NzJDEgPSBpbnRlcnBvbGF0ZVRyYW5zZm9ybSQxKHBhcnNlQ3NzJDIsICJweCwgIiwgInB4KSIsICJkZWcpIik7CiAgICB2YXIgaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmckMSA9IGludGVycG9sYXRlVHJhbnNmb3JtJDEocGFyc2VTdmckMSwgIiwgIiwgIikiLCAiKSIpOwoKICAgIHZhciBmcmFtZSQxID0gMCwgLy8gaXMgYW4gYW5pbWF0aW9uIGZyYW1lIHBlbmRpbmc/CiAgICAgICAgdGltZW91dCQyID0gMCwgLy8gaXMgYSB0aW1lb3V0IHBlbmRpbmc/CiAgICAgICAgaW50ZXJ2YWwkMiA9IDAsIC8vIGFyZSBhbnkgdGltZXJzIGFjdGl2ZT8KICAgICAgICBwb2tlRGVsYXkkMSA9IDEwMDAsIC8vIGhvdyBmcmVxdWVudGx5IHdlIGNoZWNrIGZvciBjbG9jayBza2V3CiAgICAgICAgdGFza0hlYWQkMSwKICAgICAgICB0YXNrVGFpbCQxLAogICAgICAgIGNsb2NrTGFzdCQxID0gMCwKICAgICAgICBjbG9ja05vdyQxID0gMCwKICAgICAgICBjbG9ja1NrZXckMSA9IDAsCiAgICAgICAgY2xvY2skMSA9IHR5cGVvZiBwZXJmb3JtYW5jZSA9PT0gIm9iamVjdCIgJiYgcGVyZm9ybWFuY2Uubm93ID8gcGVyZm9ybWFuY2UgOiBEYXRlLAogICAgICAgIHNldEZyYW1lJDEgPSB0eXBlb2Ygd2luZG93ID09PSAib2JqZWN0IiAmJiB3aW5kb3cucmVxdWVzdEFuaW1hdGlvbkZyYW1lID8gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZS5iaW5kKHdpbmRvdykgOiBmdW5jdGlvbihmKSB7IHNldFRpbWVvdXQoZiwgMTcpOyB9OwoKICAgIGZ1bmN0aW9uIG5vdyQxKCkgewogICAgICByZXR1cm4gY2xvY2tOb3ckMSB8fCAoc2V0RnJhbWUkMShjbGVhck5vdyQxKSwgY2xvY2tOb3ckMSA9IGNsb2NrJDEubm93KCkgKyBjbG9ja1NrZXckMSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xlYXJOb3ckMSgpIHsKICAgICAgY2xvY2tOb3ckMSA9IDA7CiAgICB9CgogICAgZnVuY3Rpb24gVGltZXIkMSgpIHsKICAgICAgdGhpcy5fY2FsbCA9CiAgICAgIHRoaXMuX3RpbWUgPQogICAgICB0aGlzLl9uZXh0ID0gbnVsbDsKICAgIH0KCiAgICBUaW1lciQxLnByb3RvdHlwZSA9IHRpbWVyJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVGltZXIkMSwKICAgICAgcmVzdGFydDogZnVuY3Rpb24oY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgICAgaWYgKHR5cGVvZiBjYWxsYmFjayAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IFR5cGVFcnJvcigiY2FsbGJhY2sgaXMgbm90IGEgZnVuY3Rpb24iKTsKICAgICAgICB0aW1lID0gKHRpbWUgPT0gbnVsbCA/IG5vdyQxKCkgOiArdGltZSkgKyAoZGVsYXkgPT0gbnVsbCA/IDAgOiArZGVsYXkpOwogICAgICAgIGlmICghdGhpcy5fbmV4dCAmJiB0YXNrVGFpbCQxICE9PSB0aGlzKSB7CiAgICAgICAgICBpZiAodGFza1RhaWwkMSkgdGFza1RhaWwkMS5fbmV4dCA9IHRoaXM7CiAgICAgICAgICBlbHNlIHRhc2tIZWFkJDEgPSB0aGlzOwogICAgICAgICAgdGFza1RhaWwkMSA9IHRoaXM7CiAgICAgICAgfQogICAgICAgIHRoaXMuX2NhbGwgPSBjYWxsYmFjazsKICAgICAgICB0aGlzLl90aW1lID0gdGltZTsKICAgICAgICBzbGVlcCQxKCk7CiAgICAgIH0sCiAgICAgIHN0b3A6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9jYWxsKSB7CiAgICAgICAgICB0aGlzLl9jYWxsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX3RpbWUgPSBJbmZpbml0eTsKICAgICAgICAgIHNsZWVwJDEoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gdGltZXIkMShjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIkMTsKICAgICAgdC5yZXN0YXJ0KGNhbGxiYWNrLCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVyRmx1c2gkMSgpIHsKICAgICAgbm93JDEoKTsgLy8gR2V0IHRoZSBjdXJyZW50IHRpbWUsIGlmIG5vdCBhbHJlYWR5IHNldC4KICAgICAgKytmcmFtZSQxOyAvLyBQcmV0ZW5kIHdl4oCZdmUgc2V0IGFuIGFsYXJtLCBpZiB3ZSBoYXZlbuKAmXQgYWxyZWFkeS4KICAgICAgdmFyIHQgPSB0YXNrSGVhZCQxLCBlOwogICAgICB3aGlsZSAodCkgewogICAgICAgIGlmICgoZSA9IGNsb2NrTm93JDEgLSB0Ll90aW1lKSA+PSAwKSB0Ll9jYWxsLmNhbGwobnVsbCwgZSk7CiAgICAgICAgdCA9IHQuX25leHQ7CiAgICAgIH0KICAgICAgLS1mcmFtZSQxOwogICAgfQoKICAgIGZ1bmN0aW9uIHdha2UkMSgpIHsKICAgICAgY2xvY2tOb3ckMSA9IChjbG9ja0xhc3QkMSA9IGNsb2NrJDEubm93KCkpICsgY2xvY2tTa2V3JDE7CiAgICAgIGZyYW1lJDEgPSB0aW1lb3V0JDIgPSAwOwogICAgICB0cnkgewogICAgICAgIHRpbWVyRmx1c2gkMSgpOwogICAgICB9IGZpbmFsbHkgewogICAgICAgIGZyYW1lJDEgPSAwOwogICAgICAgIG5hcCQxKCk7CiAgICAgICAgY2xvY2tOb3ckMSA9IDA7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBwb2tlJDEoKSB7CiAgICAgIHZhciBub3cgPSBjbG9jayQxLm5vdygpLCBkZWxheSA9IG5vdyAtIGNsb2NrTGFzdCQxOwogICAgICBpZiAoZGVsYXkgPiBwb2tlRGVsYXkkMSkgY2xvY2tTa2V3JDEgLT0gZGVsYXksIGNsb2NrTGFzdCQxID0gbm93OwogICAgfQoKICAgIGZ1bmN0aW9uIG5hcCQxKCkgewogICAgICB2YXIgdDAsIHQxID0gdGFza0hlYWQkMSwgdDIsIHRpbWUgPSBJbmZpbml0eTsKICAgICAgd2hpbGUgKHQxKSB7CiAgICAgICAgaWYgKHQxLl9jYWxsKSB7CiAgICAgICAgICBpZiAodGltZSA+IHQxLl90aW1lKSB0aW1lID0gdDEuX3RpbWU7CiAgICAgICAgICB0MCA9IHQxLCB0MSA9IHQxLl9uZXh0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0MiA9IHQxLl9uZXh0LCB0MS5fbmV4dCA9IG51bGw7CiAgICAgICAgICB0MSA9IHQwID8gdDAuX25leHQgPSB0MiA6IHRhc2tIZWFkJDEgPSB0MjsKICAgICAgICB9CiAgICAgIH0KICAgICAgdGFza1RhaWwkMSA9IHQwOwogICAgICBzbGVlcCQxKHRpbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNsZWVwJDEodGltZSkgewogICAgICBpZiAoZnJhbWUkMSkgcmV0dXJuOyAvLyBTb29uZXN0IGFsYXJtIGFscmVhZHkgc2V0LCBvciB3aWxsIGJlLgogICAgICBpZiAodGltZW91dCQyKSB0aW1lb3V0JDIgPSBjbGVhclRpbWVvdXQodGltZW91dCQyKTsKICAgICAgdmFyIGRlbGF5ID0gdGltZSAtIGNsb2NrTm93JDE7IC8vIFN0cmljdGx5IGxlc3MgdGhhbiBpZiB3ZSByZWNvbXB1dGVkIGNsb2NrTm93LgogICAgICBpZiAoZGVsYXkgPiAyNCkgewogICAgICAgIGlmICh0aW1lIDwgSW5maW5pdHkpIHRpbWVvdXQkMiA9IHNldFRpbWVvdXQod2FrZSQxLCB0aW1lIC0gY2xvY2skMS5ub3coKSAtIGNsb2NrU2tldyQxKTsKICAgICAgICBpZiAoaW50ZXJ2YWwkMikgaW50ZXJ2YWwkMiA9IGNsZWFySW50ZXJ2YWwoaW50ZXJ2YWwkMik7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgaWYgKCFpbnRlcnZhbCQyKSBjbG9ja0xhc3QkMSA9IGNsb2NrJDEubm93KCksIGludGVydmFsJDIgPSBzZXRJbnRlcnZhbChwb2tlJDEsIHBva2VEZWxheSQxKTsKICAgICAgICBmcmFtZSQxID0gMSwgc2V0RnJhbWUkMSh3YWtlJDEpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gdGltZW91dCQzKGNhbGxiYWNrLCBkZWxheSwgdGltZSkgewogICAgICB2YXIgdCA9IG5ldyBUaW1lciQxOwogICAgICBkZWxheSA9IGRlbGF5ID09IG51bGwgPyAwIDogK2RlbGF5OwogICAgICB0LnJlc3RhcnQoZnVuY3Rpb24oZWxhcHNlZCkgewogICAgICAgIHQuc3RvcCgpOwogICAgICAgIGNhbGxiYWNrKGVsYXBzZWQgKyBkZWxheSk7CiAgICAgIH0sIGRlbGF5LCB0aW1lKTsKICAgICAgcmV0dXJuIHQ7CiAgICB9CgogICAgdmFyIGVtcHR5T24kMSA9IGRpc3BhdGNoJDEoInN0YXJ0IiwgImVuZCIsICJjYW5jZWwiLCAiaW50ZXJydXB0Iik7CiAgICB2YXIgZW1wdHlUd2VlbiQxID0gW107CgogICAgdmFyIENSRUFURUQkMSA9IDA7CiAgICB2YXIgU0NIRURVTEVEJDEgPSAxOwogICAgdmFyIFNUQVJUSU5HJDEgPSAyOwogICAgdmFyIFNUQVJURUQkMSA9IDM7CiAgICB2YXIgUlVOTklORyQxID0gNDsKICAgIHZhciBFTkRJTkckMSA9IDU7CiAgICB2YXIgRU5ERUQkMSA9IDY7CgogICAgZnVuY3Rpb24gc2NoZWR1bGUkMihub2RlLCBuYW1lLCBpZCwgaW5kZXgsIGdyb3VwLCB0aW1pbmcpIHsKICAgICAgdmFyIHNjaGVkdWxlcyA9IG5vZGUuX190cmFuc2l0aW9uOwogICAgICBpZiAoIXNjaGVkdWxlcykgbm9kZS5fX3RyYW5zaXRpb24gPSB7fTsKICAgICAgZWxzZSBpZiAoaWQgaW4gc2NoZWR1bGVzKSByZXR1cm47CiAgICAgIGNyZWF0ZSQyKG5vZGUsIGlkLCB7CiAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICBpbmRleDogaW5kZXgsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBncm91cDogZ3JvdXAsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBvbjogZW1wdHlPbiQxLAogICAgICAgIHR3ZWVuOiBlbXB0eVR3ZWVuJDEsCiAgICAgICAgdGltZTogdGltaW5nLnRpbWUsCiAgICAgICAgZGVsYXk6IHRpbWluZy5kZWxheSwKICAgICAgICBkdXJhdGlvbjogdGltaW5nLmR1cmF0aW9uLAogICAgICAgIGVhc2U6IHRpbWluZy5lYXNlLAogICAgICAgIHRpbWVyOiBudWxsLAogICAgICAgIHN0YXRlOiBDUkVBVEVEJDEKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gaW5pdCQxKG5vZGUsIGlkKSB7CiAgICAgIHZhciBzY2hlZHVsZSA9IGdldCQ0KG5vZGUsIGlkKTsKICAgICAgaWYgKHNjaGVkdWxlLnN0YXRlID4gQ1JFQVRFRCQxKSB0aHJvdyBuZXcgRXJyb3IoInRvbyBsYXRlOyBhbHJlYWR5IHNjaGVkdWxlZCIpOwogICAgICByZXR1cm4gc2NoZWR1bGU7CiAgICB9CgogICAgZnVuY3Rpb24gc2V0JDUobm9kZSwgaWQpIHsKICAgICAgdmFyIHNjaGVkdWxlID0gZ2V0JDQobm9kZSwgaWQpOwogICAgICBpZiAoc2NoZWR1bGUuc3RhdGUgPiBTVEFSVEVEJDEpIHRocm93IG5ldyBFcnJvcigidG9vIGxhdGU7IGFscmVhZHkgcnVubmluZyIpOwogICAgICByZXR1cm4gc2NoZWR1bGU7CiAgICB9CgogICAgZnVuY3Rpb24gZ2V0JDQobm9kZSwgaWQpIHsKICAgICAgdmFyIHNjaGVkdWxlID0gbm9kZS5fX3RyYW5zaXRpb247CiAgICAgIGlmICghc2NoZWR1bGUgfHwgIShzY2hlZHVsZSA9IHNjaGVkdWxlW2lkXSkpIHRocm93IG5ldyBFcnJvcigidHJhbnNpdGlvbiBub3QgZm91bmQiKTsKICAgICAgcmV0dXJuIHNjaGVkdWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZSQyKG5vZGUsIGlkLCBzZWxmKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbiwKICAgICAgICAgIHR3ZWVuOwoKICAgICAgLy8gSW5pdGlhbGl6ZSB0aGUgc2VsZiB0aW1lciB3aGVuIHRoZSB0cmFuc2l0aW9uIGlzIGNyZWF0ZWQuCiAgICAgIC8vIE5vdGUgdGhlIGFjdHVhbCBkZWxheSBpcyBub3Qga25vd24gdW50aWwgdGhlIGZpcnN0IGNhbGxiYWNrIQogICAgICBzY2hlZHVsZXNbaWRdID0gc2VsZjsKICAgICAgc2VsZi50aW1lciA9IHRpbWVyJDEoc2NoZWR1bGUsIDAsIHNlbGYudGltZSk7CgogICAgICBmdW5jdGlvbiBzY2hlZHVsZShlbGFwc2VkKSB7CiAgICAgICAgc2VsZi5zdGF0ZSA9IFNDSEVEVUxFRCQxOwogICAgICAgIHNlbGYudGltZXIucmVzdGFydChzdGFydCwgc2VsZi5kZWxheSwgc2VsZi50aW1lKTsKCiAgICAgICAgLy8gSWYgdGhlIGVsYXBzZWQgZGVsYXkgaXMgbGVzcyB0aGFuIG91ciBmaXJzdCBzbGVlcCwgc3RhcnQgaW1tZWRpYXRlbHkuCiAgICAgICAgaWYgKHNlbGYuZGVsYXkgPD0gZWxhcHNlZCkgc3RhcnQoZWxhcHNlZCAtIHNlbGYuZGVsYXkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBzdGFydChlbGFwc2VkKSB7CiAgICAgICAgdmFyIGksIGosIG4sIG87CgogICAgICAgIC8vIElmIHRoZSBzdGF0ZSBpcyBub3QgU0NIRURVTEVELCB0aGVuIHdlIHByZXZpb3VzbHkgZXJyb3JlZCBvbiBzdGFydC4KICAgICAgICBpZiAoc2VsZi5zdGF0ZSAhPT0gU0NIRURVTEVEJDEpIHJldHVybiBzdG9wKCk7CgogICAgICAgIGZvciAoaSBpbiBzY2hlZHVsZXMpIHsKICAgICAgICAgIG8gPSBzY2hlZHVsZXNbaV07CiAgICAgICAgICBpZiAoby5uYW1lICE9PSBzZWxmLm5hbWUpIGNvbnRpbnVlOwoKICAgICAgICAgIC8vIFdoaWxlIHRoaXMgZWxlbWVudCBhbHJlYWR5IGhhcyBhIHN0YXJ0aW5nIHRyYW5zaXRpb24gZHVyaW5nIHRoaXMgZnJhbWUsCiAgICAgICAgICAvLyBkZWZlciBzdGFydGluZyBhbiBpbnRlcnJ1cHRpbmcgdHJhbnNpdGlvbiB1bnRpbCB0aGF0IHRyYW5zaXRpb24gaGFzIGEKICAgICAgICAgIC8vIGNoYW5jZSB0byB0aWNrIChhbmQgcG9zc2libHkgZW5kKTsgc2VlIGQzL2QzLXRyYW5zaXRpb24jNTQhCiAgICAgICAgICBpZiAoby5zdGF0ZSA9PT0gU1RBUlRFRCQxKSByZXR1cm4gdGltZW91dCQzKHN0YXJ0KTsKCiAgICAgICAgICAvLyBJbnRlcnJ1cHQgdGhlIGFjdGl2ZSB0cmFuc2l0aW9uLCBpZiBhbnkuCiAgICAgICAgICBpZiAoby5zdGF0ZSA9PT0gUlVOTklORyQxKSB7CiAgICAgICAgICAgIG8uc3RhdGUgPSBFTkRFRCQxOwogICAgICAgICAgICBvLnRpbWVyLnN0b3AoKTsKICAgICAgICAgICAgby5vbi5jYWxsKCJpbnRlcnJ1cHQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBvLmluZGV4LCBvLmdyb3VwKTsKICAgICAgICAgICAgZGVsZXRlIHNjaGVkdWxlc1tpXTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBDYW5jZWwgYW55IHByZS1lbXB0ZWQgdHJhbnNpdGlvbnMuCiAgICAgICAgICBlbHNlIGlmICgraSA8IGlkKSB7CiAgICAgICAgICAgIG8uc3RhdGUgPSBFTkRFRCQxOwogICAgICAgICAgICBvLnRpbWVyLnN0b3AoKTsKICAgICAgICAgICAgby5vbi5jYWxsKCJjYW5jZWwiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBvLmluZGV4LCBvLmdyb3VwKTsKICAgICAgICAgICAgZGVsZXRlIHNjaGVkdWxlc1tpXTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIERlZmVyIHRoZSBmaXJzdCB0aWNrIHRvIGVuZCBvZiB0aGUgY3VycmVudCBmcmFtZTsgc2VlIGQzL2QzIzE1NzYuCiAgICAgICAgLy8gTm90ZSB0aGUgdHJhbnNpdGlvbiBtYXkgYmUgY2FuY2VsZWQgYWZ0ZXIgc3RhcnQgYW5kIGJlZm9yZSB0aGUgZmlyc3QgdGljayEKICAgICAgICAvLyBOb3RlIHRoaXMgbXVzdCBiZSBzY2hlZHVsZWQgYmVmb3JlIHRoZSBzdGFydCBldmVudDsgc2VlIGQzL2QzLXRyYW5zaXRpb24jMTYhCiAgICAgICAgLy8gQXNzdW1pbmcgdGhpcyBpcyBzdWNjZXNzZnVsLCBzdWJzZXF1ZW50IGNhbGxiYWNrcyBnbyBzdHJhaWdodCB0byB0aWNrLgogICAgICAgIHRpbWVvdXQkMyhmdW5jdGlvbigpIHsKICAgICAgICAgIGlmIChzZWxmLnN0YXRlID09PSBTVEFSVEVEJDEpIHsKICAgICAgICAgICAgc2VsZi5zdGF0ZSA9IFJVTk5JTkckMTsKICAgICAgICAgICAgc2VsZi50aW1lci5yZXN0YXJ0KHRpY2ssIHNlbGYuZGVsYXksIHNlbGYudGltZSk7CiAgICAgICAgICAgIHRpY2soZWxhcHNlZCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8vIERpc3BhdGNoIHRoZSBzdGFydCBldmVudC4KICAgICAgICAvLyBOb3RlIHRoaXMgbXVzdCBiZSBkb25lIGJlZm9yZSB0aGUgdHdlZW4gYXJlIGluaXRpYWxpemVkLgogICAgICAgIHNlbGYuc3RhdGUgPSBTVEFSVElORyQxOwogICAgICAgIHNlbGYub24uY2FsbCgic3RhcnQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKTsKICAgICAgICBpZiAoc2VsZi5zdGF0ZSAhPT0gU1RBUlRJTkckMSkgcmV0dXJuOyAvLyBpbnRlcnJ1cHRlZAogICAgICAgIHNlbGYuc3RhdGUgPSBTVEFSVEVEJDE7CgogICAgICAgIC8vIEluaXRpYWxpemUgdGhlIHR3ZWVuLCBkZWxldGluZyBudWxsIHR3ZWVuLgogICAgICAgIHR3ZWVuID0gbmV3IEFycmF5KG4gPSBzZWxmLnR3ZWVuLmxlbmd0aCk7CiAgICAgICAgZm9yIChpID0gMCwgaiA9IC0xOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobyA9IHNlbGYudHdlZW5baV0udmFsdWUuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKSkgewogICAgICAgICAgICB0d2VlblsrK2pdID0gbzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdHdlZW4ubGVuZ3RoID0gaiArIDE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRpY2soZWxhcHNlZCkgewogICAgICAgIHZhciB0ID0gZWxhcHNlZCA8IHNlbGYuZHVyYXRpb24gPyBzZWxmLmVhc2UuY2FsbChudWxsLCBlbGFwc2VkIC8gc2VsZi5kdXJhdGlvbikgOiAoc2VsZi50aW1lci5yZXN0YXJ0KHN0b3ApLCBzZWxmLnN0YXRlID0gRU5ESU5HJDEsIDEpLAogICAgICAgICAgICBpID0gLTEsCiAgICAgICAgICAgIG4gPSB0d2Vlbi5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICB0d2VlbltpXS5jYWxsKG5vZGUsIHQpOwogICAgICAgIH0KCiAgICAgICAgLy8gRGlzcGF0Y2ggdGhlIGVuZCBldmVudC4KICAgICAgICBpZiAoc2VsZi5zdGF0ZSA9PT0gRU5ESU5HJDEpIHsKICAgICAgICAgIHNlbGYub24uY2FsbCgiZW5kIiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgc2VsZi5pbmRleCwgc2VsZi5ncm91cCk7CiAgICAgICAgICBzdG9wKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBzdG9wKCkgewogICAgICAgIHNlbGYuc3RhdGUgPSBFTkRFRCQxOwogICAgICAgIHNlbGYudGltZXIuc3RvcCgpOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaWRdOwogICAgICAgIGZvciAodmFyIGkgaW4gc2NoZWR1bGVzKSByZXR1cm47IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKICAgICAgICBkZWxldGUgbm9kZS5fX3RyYW5zaXRpb247CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnJ1cHQkMShub2RlLCBuYW1lKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbiwKICAgICAgICAgIHNjaGVkdWxlLAogICAgICAgICAgYWN0aXZlLAogICAgICAgICAgZW1wdHkgPSB0cnVlLAogICAgICAgICAgaTsKCiAgICAgIGlmICghc2NoZWR1bGVzKSByZXR1cm47CgogICAgICBuYW1lID0gbmFtZSA9PSBudWxsID8gbnVsbCA6IG5hbWUgKyAiIjsKCiAgICAgIGZvciAoaSBpbiBzY2hlZHVsZXMpIHsKICAgICAgICBpZiAoKHNjaGVkdWxlID0gc2NoZWR1bGVzW2ldKS5uYW1lICE9PSBuYW1lKSB7IGVtcHR5ID0gZmFsc2U7IGNvbnRpbnVlOyB9CiAgICAgICAgYWN0aXZlID0gc2NoZWR1bGUuc3RhdGUgPiBTVEFSVElORyQxICYmIHNjaGVkdWxlLnN0YXRlIDwgRU5ESU5HJDE7CiAgICAgICAgc2NoZWR1bGUuc3RhdGUgPSBFTkRFRCQxOwogICAgICAgIHNjaGVkdWxlLnRpbWVyLnN0b3AoKTsKICAgICAgICBzY2hlZHVsZS5vbi5jYWxsKGFjdGl2ZSA/ICJpbnRlcnJ1cHQiIDogImNhbmNlbCIsIG5vZGUsIG5vZGUuX19kYXRhX18sIHNjaGVkdWxlLmluZGV4LCBzY2hlZHVsZS5ncm91cCk7CiAgICAgICAgZGVsZXRlIHNjaGVkdWxlc1tpXTsKICAgICAgfQoKICAgICAgaWYgKGVtcHR5KSBkZWxldGUgbm9kZS5fX3RyYW5zaXRpb247CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2ludGVycnVwdCQxKG5hbWUpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICBpbnRlcnJ1cHQkMSh0aGlzLCBuYW1lKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHdlZW5SZW1vdmUkMShpZCwgbmFtZSkgewogICAgICB2YXIgdHdlZW4wLCB0d2VlbjE7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2NoZWR1bGUgPSBzZXQkNSh0aGlzLCBpZCksCiAgICAgICAgICAgIHR3ZWVuID0gc2NoZWR1bGUudHdlZW47CgogICAgICAgIC8vIElmIHRoaXMgbm9kZSBzaGFyZWQgdHdlZW4gd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAvLyBqdXN0IGFzc2lnbiB0aGUgdXBkYXRlZCBzaGFyZWQgdHdlZW4gYW5kIHdl4oCZcmUgZG9uZSEKICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgaWYgKHR3ZWVuICE9PSB0d2VlbjApIHsKICAgICAgICAgIHR3ZWVuMSA9IHR3ZWVuMCA9IHR3ZWVuOwogICAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0d2VlbjEubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGlmICh0d2VlbjFbaV0ubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgICAgIHR3ZWVuMSA9IHR3ZWVuMS5zbGljZSgpOwogICAgICAgICAgICAgIHR3ZWVuMS5zcGxpY2UoaSwgMSk7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHNjaGVkdWxlLnR3ZWVuID0gdHdlZW4xOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHR3ZWVuRnVuY3Rpb24kMShpZCwgbmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIHR3ZWVuMCwgdHdlZW4xOwogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3I7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2NoZWR1bGUgPSBzZXQkNSh0aGlzLCBpZCksCiAgICAgICAgICAgIHR3ZWVuID0gc2NoZWR1bGUudHdlZW47CgogICAgICAgIC8vIElmIHRoaXMgbm9kZSBzaGFyZWQgdHdlZW4gd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAvLyBqdXN0IGFzc2lnbiB0aGUgdXBkYXRlZCBzaGFyZWQgdHdlZW4gYW5kIHdl4oCZcmUgZG9uZSEKICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgaWYgKHR3ZWVuICE9PSB0d2VlbjApIHsKICAgICAgICAgIHR3ZWVuMSA9ICh0d2VlbjAgPSB0d2Vlbikuc2xpY2UoKTsKICAgICAgICAgIGZvciAodmFyIHQgPSB7bmFtZTogbmFtZSwgdmFsdWU6IHZhbHVlfSwgaSA9IDAsIG4gPSB0d2VlbjEubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGlmICh0d2VlbjFbaV0ubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgICAgIHR3ZWVuMVtpXSA9IHQ7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGlmIChpID09PSBuKSB0d2VlbjEucHVzaCh0KTsKICAgICAgICB9CgogICAgICAgIHNjaGVkdWxlLnR3ZWVuID0gdHdlZW4xOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fdHdlZW4kMShuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIG5hbWUgKz0gIiI7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgdHdlZW4gPSBnZXQkNCh0aGlzLm5vZGUoKSwgaWQpLnR3ZWVuOwogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHdlZW4ubGVuZ3RoLCB0OyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKHQgPSB0d2VlbltpXSkubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgICByZXR1cm4gdC52YWx1ZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHZhbHVlID09IG51bGwgPyB0d2VlblJlbW92ZSQxIDogdHdlZW5GdW5jdGlvbiQxKShpZCwgbmFtZSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0d2VlblZhbHVlJDEodHJhbnNpdGlvbiwgbmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGlkID0gdHJhbnNpdGlvbi5faWQ7CgogICAgICB0cmFuc2l0aW9uLmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JDUodGhpcywgaWQpOwogICAgICAgIChzY2hlZHVsZS52YWx1ZSB8fCAoc2NoZWR1bGUudmFsdWUgPSB7fSkpW25hbWVdID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfSk7CgogICAgICByZXR1cm4gZnVuY3Rpb24obm9kZSkgewogICAgICAgIHJldHVybiBnZXQkNChub2RlLCBpZCkudmFsdWVbbmFtZV07CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGUkMyhhLCBiKSB7CiAgICAgIHZhciBjOwogICAgICByZXR1cm4gKHR5cGVvZiBiID09PSAibnVtYmVyIiA/IGludGVycG9sYXRlTnVtYmVyJDEKICAgICAgICAgIDogYiBpbnN0YW5jZW9mIGNvbG9yJDEgPyBpbnRlcnBvbGF0ZVJnYiQxCiAgICAgICAgICA6IChjID0gY29sb3IkMShiKSkgPyAoYiA9IGMsIGludGVycG9sYXRlUmdiJDEpCiAgICAgICAgICA6IGludGVycG9sYXRlU3RyaW5nJDEpKGEsIGIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJSZW1vdmUkMyhuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlTlMkMyhmdWxsbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudCQzKG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZTEpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMSA9IHZhbHVlMSArICIiLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHN0cmluZzAgPSB0aGlzLmdldEF0dHJpYnV0ZShuYW1lKTsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgdmFsdWUxKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnROUyQzKGZ1bGxuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUxKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIiwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbiQzKG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwLCB2YWx1ZTEgPSB2YWx1ZSh0aGlzKSwgc3RyaW5nMTsKICAgICAgICBpZiAodmFsdWUxID09IG51bGwpIHJldHVybiB2b2lkIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgIHN0cmluZzAgPSB0aGlzLmdldEF0dHJpYnV0ZShuYW1lKTsKICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiI7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgJiYgc3RyaW5nMSA9PT0gc3RyaW5nMTAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiAoc3RyaW5nMTAgPSBzdHJpbmcxLCBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbk5TJDMoZnVsbG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwLCB2YWx1ZTEgPSB2YWx1ZSh0aGlzKSwgc3RyaW5nMTsKICAgICAgICBpZiAodmFsdWUxID09IG51bGwpIHJldHVybiB2b2lkIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIjsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCAmJiBzdHJpbmcxID09PSBzdHJpbmcxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IChzdHJpbmcxMCA9IHN0cmluZzEsIGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgdmFsdWUxKSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9hdHRyJDEobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlJDEobmFtZSksIGkgPSBmdWxsbmFtZSA9PT0gInRyYW5zZm9ybSIgPyBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZyQxIDogaW50ZXJwb2xhdGUkMzsKICAgICAgcmV0dXJuIHRoaXMuYXR0clR3ZWVuKG5hbWUsIHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyRnVuY3Rpb25OUyQzIDogYXR0ckZ1bmN0aW9uJDMpKGZ1bGxuYW1lLCBpLCB0d2VlblZhbHVlJDEodGhpcywgImF0dHIuIiArIG5hbWUsIHZhbHVlKSkKICAgICAgICAgIDogdmFsdWUgPT0gbnVsbCA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJSZW1vdmVOUyQzIDogYXR0clJlbW92ZSQzKShmdWxsbmFtZSkKICAgICAgICAgIDogKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckNvbnN0YW50TlMkMyA6IGF0dHJDb25zdGFudCQzKShmdWxsbmFtZSwgaSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRySW50ZXJwb2xhdGUkMShuYW1lLCBpKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgaS5jYWxsKHRoaXMsIHQpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRySW50ZXJwb2xhdGVOUyQxKGZ1bGxuYW1lLCBpKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwsIGkuY2FsbCh0aGlzLCB0KSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clR3ZWVuTlMkMShmdWxsbmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIHQwLCBpMDsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChpICE9PSBpMCkgdDAgPSAoaTAgPSBpKSAmJiBhdHRySW50ZXJwb2xhdGVOUyQxKGZ1bGxuYW1lLCBpKTsKICAgICAgICByZXR1cm4gdDA7CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyVHdlZW4kMShuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgdDAsIGkwOwogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgaSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKGkgIT09IGkwKSB0MCA9IChpMCA9IGkpICYmIGF0dHJJbnRlcnBvbGF0ZSQxKG5hbWUsIGkpOwogICAgICAgIHJldHVybiB0MDsKICAgICAgfQogICAgICB0d2Vlbi5fdmFsdWUgPSB2YWx1ZTsKICAgICAgcmV0dXJuIHR3ZWVuOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0clR3ZWVuJDEobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGtleSA9ICJhdHRyLiIgKyBuYW1lOwogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHJldHVybiAoa2V5ID0gdGhpcy50d2VlbihrZXkpKSAmJiBrZXkuX3ZhbHVlOwogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCBudWxsKTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UkMShuYW1lKTsKICAgICAgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCAoZnVsbG5hbWUubG9jYWwgPyBhdHRyVHdlZW5OUyQxIDogYXR0clR3ZWVuJDEpKGZ1bGxuYW1lLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlbGF5RnVuY3Rpb24kMShpZCwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGluaXQkMSh0aGlzLCBpZCkuZGVsYXkgPSArdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWxheUNvbnN0YW50JDEoaWQsIHZhbHVlKSB7CiAgICAgIHJldHVybiB2YWx1ZSA9ICt2YWx1ZSwgZnVuY3Rpb24oKSB7CiAgICAgICAgaW5pdCQxKHRoaXMsIGlkKS5kZWxheSA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZGVsYXkkMSh2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCgodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBkZWxheUZ1bmN0aW9uJDEKICAgICAgICAgICAgICA6IGRlbGF5Q29uc3RhbnQkMSkoaWQsIHZhbHVlKSkKICAgICAgICAgIDogZ2V0JDQodGhpcy5ub2RlKCksIGlkKS5kZWxheTsKICAgIH0KCiAgICBmdW5jdGlvbiBkdXJhdGlvbkZ1bmN0aW9uJDEoaWQsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBzZXQkNSh0aGlzLCBpZCkuZHVyYXRpb24gPSArdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkdXJhdGlvbkNvbnN0YW50JDEoaWQsIHZhbHVlKSB7CiAgICAgIHJldHVybiB2YWx1ZSA9ICt2YWx1ZSwgZnVuY3Rpb24oKSB7CiAgICAgICAgc2V0JDUodGhpcywgaWQpLmR1cmF0aW9uID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9kdXJhdGlvbiQxKHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRoaXMuX2lkOwoKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKCh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IGR1cmF0aW9uRnVuY3Rpb24kMQogICAgICAgICAgICAgIDogZHVyYXRpb25Db25zdGFudCQxKShpZCwgdmFsdWUpKQogICAgICAgICAgOiBnZXQkNCh0aGlzLm5vZGUoKSwgaWQpLmR1cmF0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIGVhc2VDb25zdGFudCQxKGlkLCB2YWx1ZSkgewogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3I7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBzZXQkNSh0aGlzLCBpZCkuZWFzZSA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZWFzZSQxKHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRoaXMuX2lkOwoKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKGVhc2VDb25zdGFudCQxKGlkLCB2YWx1ZSkpCiAgICAgICAgICA6IGdldCQ0KHRoaXMubm9kZSgpLCBpZCkuZWFzZTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2ZpbHRlciQxKG1hdGNoKSB7CiAgICAgIGlmICh0eXBlb2YgbWF0Y2ggIT09ICJmdW5jdGlvbiIpIG1hdGNoID0gbWF0Y2hlciQxKG1hdGNoKTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBbXSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiBtYXRjaC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkgewogICAgICAgICAgICBzdWJncm91cC5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDEoc3ViZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCB0aGlzLl9uYW1lLCB0aGlzLl9pZCk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9tZXJnZSQxKHRyYW5zaXRpb24pIHsKICAgICAgaWYgKHRyYW5zaXRpb24uX2lkICE9PSB0aGlzLl9pZCkgdGhyb3cgbmV3IEVycm9yOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzMCA9IHRoaXMuX2dyb3VwcywgZ3JvdXBzMSA9IHRyYW5zaXRpb24uX2dyb3VwcywgbTAgPSBncm91cHMwLmxlbmd0aCwgbTEgPSBncm91cHMxLmxlbmd0aCwgbSA9IE1hdGgubWluKG0wLCBtMSksIG1lcmdlcyA9IG5ldyBBcnJheShtMCksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAwID0gZ3JvdXBzMFtqXSwgZ3JvdXAxID0gZ3JvdXBzMVtqXSwgbiA9IGdyb3VwMC5sZW5ndGgsIG1lcmdlID0gbWVyZ2VzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cDBbaV0gfHwgZ3JvdXAxW2ldKSB7CiAgICAgICAgICAgIG1lcmdlW2ldID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZvciAoOyBqIDwgbTA7ICsraikgewogICAgICAgIG1lcmdlc1tqXSA9IGdyb3VwczBbal07CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQxKG1lcmdlcywgdGhpcy5fcGFyZW50cywgdGhpcy5fbmFtZSwgdGhpcy5faWQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0YXJ0JDEobmFtZSkgewogICAgICByZXR1cm4gKG5hbWUgKyAiIikudHJpbSgpLnNwbGl0KC9efFxzKy8pLmV2ZXJ5KGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgaSA9IHQuaW5kZXhPZigiLiIpOwogICAgICAgIGlmIChpID49IDApIHQgPSB0LnNsaWNlKDAsIGkpOwogICAgICAgIHJldHVybiAhdCB8fCB0ID09PSAic3RhcnQiOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBvbkZ1bmN0aW9uJDEoaWQsIG5hbWUsIGxpc3RlbmVyKSB7CiAgICAgIHZhciBvbjAsIG9uMSwgc2l0ID0gc3RhcnQkMShuYW1lKSA/IGluaXQkMSA6IHNldCQ1OwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2l0KHRoaXMsIGlkKSwKICAgICAgICAgICAgb24gPSBzY2hlZHVsZS5vbjsKCiAgICAgICAgLy8gSWYgdGhpcyBub2RlIHNoYXJlZCBhIGRpc3BhdGNoIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIGRpc3BhdGNoIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmIChvbiAhPT0gb24wKSAob24xID0gKG9uMCA9IG9uKS5jb3B5KCkpLm9uKG5hbWUsIGxpc3RlbmVyKTsKCiAgICAgICAgc2NoZWR1bGUub24gPSBvbjE7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9vbiQxKG5hbWUsIGxpc3RlbmVyKSB7CiAgICAgIHZhciBpZCA9IHRoaXMuX2lkOwoKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPCAyCiAgICAgICAgICA/IGdldCQ0KHRoaXMubm9kZSgpLCBpZCkub24ub24obmFtZSkKICAgICAgICAgIDogdGhpcy5lYWNoKG9uRnVuY3Rpb24kMShpZCwgbmFtZSwgbGlzdGVuZXIpKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVGdW5jdGlvbiQxKGlkKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICAgIGZvciAodmFyIGkgaW4gdGhpcy5fX3RyYW5zaXRpb24pIGlmICgraSAhPT0gaWQpIHJldHVybjsKICAgICAgICBpZiAocGFyZW50KSBwYXJlbnQucmVtb3ZlQ2hpbGQodGhpcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9yZW1vdmUkMSgpIHsKICAgICAgcmV0dXJuIHRoaXMub24oImVuZC5yZW1vdmUiLCByZW1vdmVGdW5jdGlvbiQxKHRoaXMuX2lkKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zZWxlY3QkMShzZWxlY3QpIHsKICAgICAgdmFyIG5hbWUgPSB0aGlzLl9uYW1lLAogICAgICAgICAgaWQgPSB0aGlzLl9pZDsKCiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvciQxKHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBzdWJub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChzdWJub2RlID0gc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSkgewogICAgICAgICAgICBpZiAoIl9fZGF0YV9fIiBpbiBub2RlKSBzdWJub2RlLl9fZGF0YV9fID0gbm9kZS5fX2RhdGFfXzsKICAgICAgICAgICAgc3ViZ3JvdXBbaV0gPSBzdWJub2RlOwogICAgICAgICAgICBzY2hlZHVsZSQyKHN1Ymdyb3VwW2ldLCBuYW1lLCBpZCwgaSwgc3ViZ3JvdXAsIGdldCQ0KG5vZGUsIGlkKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMShzdWJncm91cHMsIHRoaXMuX3BhcmVudHMsIG5hbWUsIGlkKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3NlbGVjdEFsbCQxKHNlbGVjdCkgewogICAgICB2YXIgbmFtZSA9IHRoaXMuX25hbWUsCiAgICAgICAgICBpZCA9IHRoaXMuX2lkOwoKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yQWxsJDEoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IFtdLCBwYXJlbnRzID0gW10sIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIGZvciAodmFyIGNoaWxkcmVuID0gc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApLCBjaGlsZCwgaW5oZXJpdCA9IGdldCQ0KG5vZGUsIGlkKSwgayA9IDAsIGwgPSBjaGlsZHJlbi5sZW5ndGg7IGsgPCBsOyArK2spIHsKICAgICAgICAgICAgICBpZiAoY2hpbGQgPSBjaGlsZHJlbltrXSkgewogICAgICAgICAgICAgICAgc2NoZWR1bGUkMihjaGlsZCwgbmFtZSwgaWQsIGssIGNoaWxkcmVuLCBpbmhlcml0KTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc3ViZ3JvdXBzLnB1c2goY2hpbGRyZW4pOwogICAgICAgICAgICBwYXJlbnRzLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMShzdWJncm91cHMsIHBhcmVudHMsIG5hbWUsIGlkKTsKICAgIH0KCiAgICB2YXIgU2VsZWN0aW9uJDMgPSBzZWxlY3Rpb24kMS5wcm90b3R5cGUuY29uc3RydWN0b3I7CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zZWxlY3Rpb24kMSgpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kMyh0aGlzLl9ncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlTnVsbCQxKG5hbWUsIGludGVycG9sYXRlKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEwLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHN0cmluZzAgPSBzdHlsZVZhbHVlJDEodGhpcywgbmFtZSksCiAgICAgICAgICAgIHN0cmluZzEgPSAodGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKSwgc3R5bGVWYWx1ZSQxKHRoaXMsIG5hbWUpKTsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCAmJiBzdHJpbmcxID09PSBzdHJpbmcxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgc3RyaW5nMTAgPSBzdHJpbmcxKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVJlbW92ZSQzKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVDb25zdGFudCQzKG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZTEpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMSA9IHZhbHVlMSArICIiLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHN0cmluZzAgPSBzdHlsZVZhbHVlJDEodGhpcywgbmFtZSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVGdW5jdGlvbiQzKG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gc3R5bGVWYWx1ZSQxKHRoaXMsIG5hbWUpLAogICAgICAgICAgICB2YWx1ZTEgPSB2YWx1ZSh0aGlzKSwKICAgICAgICAgICAgc3RyaW5nMSA9IHZhbHVlMSArICIiOwogICAgICAgIGlmICh2YWx1ZTEgPT0gbnVsbCkgc3RyaW5nMSA9IHZhbHVlMSA9ICh0aGlzLnN0eWxlLnJlbW92ZVByb3BlcnR5KG5hbWUpLCBzdHlsZVZhbHVlJDEodGhpcywgbmFtZSkpOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwICYmIHN0cmluZzEgPT09IHN0cmluZzEwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogKHN0cmluZzEwID0gc3RyaW5nMSwgaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCB2YWx1ZTEpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZU1heWJlUmVtb3ZlJDEoaWQsIG5hbWUpIHsKICAgICAgdmFyIG9uMCwgb24xLCBsaXN0ZW5lcjAsIGtleSA9ICJzdHlsZS4iICsgbmFtZSwgZXZlbnQgPSAiZW5kLiIgKyBrZXksIHJlbW92ZTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCQ1KHRoaXMsIGlkKSwKICAgICAgICAgICAgb24gPSBzY2hlZHVsZS5vbiwKICAgICAgICAgICAgbGlzdGVuZXIgPSBzY2hlZHVsZS52YWx1ZVtrZXldID09IG51bGwgPyByZW1vdmUgfHwgKHJlbW92ZSA9IHN0eWxlUmVtb3ZlJDMobmFtZSkpIDogdW5kZWZpbmVkOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIGEgZGlzcGF0Y2ggd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAvLyBqdXN0IGFzc2lnbiB0aGUgdXBkYXRlZCBzaGFyZWQgZGlzcGF0Y2ggYW5kIHdl4oCZcmUgZG9uZSEKICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgaWYgKG9uICE9PSBvbjAgfHwgbGlzdGVuZXIwICE9PSBsaXN0ZW5lcikgKG9uMSA9IChvbjAgPSBvbikuY29weSgpKS5vbihldmVudCwgbGlzdGVuZXIwID0gbGlzdGVuZXIpOwoKICAgICAgICBzY2hlZHVsZS5vbiA9IG9uMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3N0eWxlJDEobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHZhciBpID0gKG5hbWUgKz0gIiIpID09PSAidHJhbnNmb3JtIiA/IGludGVycG9sYXRlVHJhbnNmb3JtQ3NzJDEgOiBpbnRlcnBvbGF0ZSQzOwogICAgICByZXR1cm4gdmFsdWUgPT0gbnVsbCA/IHRoaXMKICAgICAgICAgIC5zdHlsZVR3ZWVuKG5hbWUsIHN0eWxlTnVsbCQxKG5hbWUsIGkpKQogICAgICAgICAgLm9uKCJlbmQuc3R5bGUuIiArIG5hbWUsIHN0eWxlUmVtb3ZlJDMobmFtZSkpCiAgICAgICAgOiB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIgPyB0aGlzCiAgICAgICAgICAuc3R5bGVUd2VlbihuYW1lLCBzdHlsZUZ1bmN0aW9uJDMobmFtZSwgaSwgdHdlZW5WYWx1ZSQxKHRoaXMsICJzdHlsZS4iICsgbmFtZSwgdmFsdWUpKSkKICAgICAgICAgIC5lYWNoKHN0eWxlTWF5YmVSZW1vdmUkMSh0aGlzLl9pZCwgbmFtZSkpCiAgICAgICAgOiB0aGlzCiAgICAgICAgICAuc3R5bGVUd2VlbihuYW1lLCBzdHlsZUNvbnN0YW50JDMobmFtZSwgaSwgdmFsdWUpLCBwcmlvcml0eSkKICAgICAgICAgIC5vbigiZW5kLnN0eWxlLiIgKyBuYW1lLCBudWxsKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUludGVycG9sYXRlJDEobmFtZSwgaSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICB0aGlzLnN0eWxlLnNldFByb3BlcnR5KG5hbWUsIGkuY2FsbCh0aGlzLCB0KSwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlVHdlZW4kMShuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIHQsIGkwOwogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgaSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKGkgIT09IGkwKSB0ID0gKGkwID0gaSkgJiYgc3R5bGVJbnRlcnBvbGF0ZSQxKG5hbWUsIGksIHByaW9yaXR5KTsKICAgICAgICByZXR1cm4gdDsKICAgICAgfQogICAgICB0d2Vlbi5fdmFsdWUgPSB2YWx1ZTsKICAgICAgcmV0dXJuIHR3ZWVuOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc3R5bGVUd2VlbiQxKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICB2YXIga2V5ID0gInN0eWxlLiIgKyAobmFtZSArPSAiIik7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgcmV0dXJuIChrZXkgPSB0aGlzLnR3ZWVuKGtleSkpICYmIGtleS5fdmFsdWU7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gdGhpcy50d2VlbihrZXksIG51bGwpOwogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3I7CiAgICAgIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgc3R5bGVUd2VlbiQxKG5hbWUsIHZhbHVlLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRDb25zdGFudCQzKHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dEZ1bmN0aW9uJDModmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZTEgPSB2YWx1ZSh0aGlzKTsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdmFsdWUxID09IG51bGwgPyAiIiA6IHZhbHVlMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3RleHQkMSh2YWx1ZSkgewogICAgICByZXR1cm4gdGhpcy50d2VlbigidGV4dCIsIHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyB0ZXh0RnVuY3Rpb24kMyh0d2VlblZhbHVlJDEodGhpcywgInRleHQiLCB2YWx1ZSkpCiAgICAgICAgICA6IHRleHRDb25zdGFudCQzKHZhbHVlID09IG51bGwgPyAiIiA6IHZhbHVlICsgIiIpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0SW50ZXJwb2xhdGUkMShpKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IGkuY2FsbCh0aGlzLCB0KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0VHdlZW4kMSh2YWx1ZSkgewogICAgICB2YXIgdDAsIGkwOwogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgaSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKGkgIT09IGkwKSB0MCA9IChpMCA9IGkpICYmIHRleHRJbnRlcnBvbGF0ZSQxKGkpOwogICAgICAgIHJldHVybiB0MDsKICAgICAgfQogICAgICB0d2Vlbi5fdmFsdWUgPSB2YWx1ZTsKICAgICAgcmV0dXJuIHR3ZWVuOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fdGV4dFR3ZWVuJDEodmFsdWUpIHsKICAgICAgdmFyIGtleSA9ICJ0ZXh0IjsKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAxKSByZXR1cm4gKGtleSA9IHRoaXMudHdlZW4oa2V5KSkgJiYga2V5Ll92YWx1ZTsKICAgICAgaWYgKHZhbHVlID09IG51bGwpIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgbnVsbCk7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCB0ZXh0VHdlZW4kMSh2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fdHJhbnNpdGlvbiQxKCkgewogICAgICB2YXIgbmFtZSA9IHRoaXMuX25hbWUsCiAgICAgICAgICBpZDAgPSB0aGlzLl9pZCwKICAgICAgICAgIGlkMSA9IG5ld0lkJDEoKTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHZhciBpbmhlcml0ID0gZ2V0JDQobm9kZSwgaWQwKTsKICAgICAgICAgICAgc2NoZWR1bGUkMihub2RlLCBuYW1lLCBpZDEsIGksIGdyb3VwLCB7CiAgICAgICAgICAgICAgdGltZTogaW5oZXJpdC50aW1lICsgaW5oZXJpdC5kZWxheSArIGluaGVyaXQuZHVyYXRpb24sCiAgICAgICAgICAgICAgZGVsYXk6IDAsCiAgICAgICAgICAgICAgZHVyYXRpb246IGluaGVyaXQuZHVyYXRpb24sCiAgICAgICAgICAgICAgZWFzZTogaW5oZXJpdC5lYXNlCiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDEoZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCBuYW1lLCBpZDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZW5kJDEoKSB7CiAgICAgIHZhciBvbjAsIG9uMSwgdGhhdCA9IHRoaXMsIGlkID0gdGhhdC5faWQsIHNpemUgPSB0aGF0LnNpemUoKTsKICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uKHJlc29sdmUsIHJlamVjdCkgewogICAgICAgIHZhciBjYW5jZWwgPSB7dmFsdWU6IHJlamVjdH0sCiAgICAgICAgICAgIGVuZCA9IHt2YWx1ZTogZnVuY3Rpb24oKSB7IGlmICgtLXNpemUgPT09IDApIHJlc29sdmUoKTsgfX07CgogICAgICAgIHRoYXQuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCQ1KHRoaXMsIGlkKSwKICAgICAgICAgICAgICBvbiA9IHNjaGVkdWxlLm9uOwoKICAgICAgICAgIC8vIElmIHRoaXMgbm9kZSBzaGFyZWQgYSBkaXNwYXRjaCB3aXRoIHRoZSBwcmV2aW91cyBub2RlLAogICAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIGRpc3BhdGNoIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgICBpZiAob24gIT09IG9uMCkgewogICAgICAgICAgICBvbjEgPSAob24wID0gb24pLmNvcHkoKTsKICAgICAgICAgICAgb24xLl8uY2FuY2VsLnB1c2goY2FuY2VsKTsKICAgICAgICAgICAgb24xLl8uaW50ZXJydXB0LnB1c2goY2FuY2VsKTsKICAgICAgICAgICAgb24xLl8uZW5kLnB1c2goZW5kKTsKICAgICAgICAgIH0KCiAgICAgICAgICBzY2hlZHVsZS5vbiA9IG9uMTsKICAgICAgICB9KTsKICAgICAgfSk7CiAgICB9CgogICAgdmFyIGlkJDEgPSAwOwoKICAgIGZ1bmN0aW9uIFRyYW5zaXRpb24kMShncm91cHMsIHBhcmVudHMsIG5hbWUsIGlkKSB7CiAgICAgIHRoaXMuX2dyb3VwcyA9IGdyb3VwczsKICAgICAgdGhpcy5fcGFyZW50cyA9IHBhcmVudHM7CiAgICAgIHRoaXMuX25hbWUgPSBuYW1lOwogICAgICB0aGlzLl9pZCA9IGlkOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb24kMShuYW1lKSB7CiAgICAgIHJldHVybiBzZWxlY3Rpb24kMSgpLnRyYW5zaXRpb24obmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gbmV3SWQkMSgpIHsKICAgICAgcmV0dXJuICsraWQkMTsKICAgIH0KCiAgICB2YXIgc2VsZWN0aW9uX3Byb3RvdHlwZSQxID0gc2VsZWN0aW9uJDEucHJvdG90eXBlOwoKICAgIFRyYW5zaXRpb24kMS5wcm90b3R5cGUgPSB0cmFuc2l0aW9uJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVHJhbnNpdGlvbiQxLAogICAgICBzZWxlY3Q6IHRyYW5zaXRpb25fc2VsZWN0JDEsCiAgICAgIHNlbGVjdEFsbDogdHJhbnNpdGlvbl9zZWxlY3RBbGwkMSwKICAgICAgZmlsdGVyOiB0cmFuc2l0aW9uX2ZpbHRlciQxLAogICAgICBtZXJnZTogdHJhbnNpdGlvbl9tZXJnZSQxLAogICAgICBzZWxlY3Rpb246IHRyYW5zaXRpb25fc2VsZWN0aW9uJDEsCiAgICAgIHRyYW5zaXRpb246IHRyYW5zaXRpb25fdHJhbnNpdGlvbiQxLAogICAgICBjYWxsOiBzZWxlY3Rpb25fcHJvdG90eXBlJDEuY2FsbCwKICAgICAgbm9kZXM6IHNlbGVjdGlvbl9wcm90b3R5cGUkMS5ub2RlcywKICAgICAgbm9kZTogc2VsZWN0aW9uX3Byb3RvdHlwZSQxLm5vZGUsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9wcm90b3R5cGUkMS5zaXplLAogICAgICBlbXB0eTogc2VsZWN0aW9uX3Byb3RvdHlwZSQxLmVtcHR5LAogICAgICBlYWNoOiBzZWxlY3Rpb25fcHJvdG90eXBlJDEuZWFjaCwKICAgICAgb246IHRyYW5zaXRpb25fb24kMSwKICAgICAgYXR0cjogdHJhbnNpdGlvbl9hdHRyJDEsCiAgICAgIGF0dHJUd2VlbjogdHJhbnNpdGlvbl9hdHRyVHdlZW4kMSwKICAgICAgc3R5bGU6IHRyYW5zaXRpb25fc3R5bGUkMSwKICAgICAgc3R5bGVUd2VlbjogdHJhbnNpdGlvbl9zdHlsZVR3ZWVuJDEsCiAgICAgIHRleHQ6IHRyYW5zaXRpb25fdGV4dCQxLAogICAgICB0ZXh0VHdlZW46IHRyYW5zaXRpb25fdGV4dFR3ZWVuJDEsCiAgICAgIHJlbW92ZTogdHJhbnNpdGlvbl9yZW1vdmUkMSwKICAgICAgdHdlZW46IHRyYW5zaXRpb25fdHdlZW4kMSwKICAgICAgZGVsYXk6IHRyYW5zaXRpb25fZGVsYXkkMSwKICAgICAgZHVyYXRpb246IHRyYW5zaXRpb25fZHVyYXRpb24kMSwKICAgICAgZWFzZTogdHJhbnNpdGlvbl9lYXNlJDEsCiAgICAgIGVuZDogdHJhbnNpdGlvbl9lbmQkMQogICAgfTsKCiAgICB2YXIgZGVmYXVsdFRpbWluZyQxID0gewogICAgICB0aW1lOiBudWxsLCAvLyBTZXQgb24gdXNlLgogICAgICBkZWxheTogMCwKICAgICAgZHVyYXRpb246IDI1MCwKICAgICAgZWFzZTogY3ViaWNJbk91dAogICAgfTsKCiAgICBmdW5jdGlvbiBpbmhlcml0JDEobm9kZSwgaWQpIHsKICAgICAgdmFyIHRpbWluZzsKICAgICAgd2hpbGUgKCEodGltaW5nID0gbm9kZS5fX3RyYW5zaXRpb24pIHx8ICEodGltaW5nID0gdGltaW5nW2lkXSkpIHsKICAgICAgICBpZiAoIShub2RlID0gbm9kZS5wYXJlbnROb2RlKSkgewogICAgICAgICAgcmV0dXJuIGRlZmF1bHRUaW1pbmckMS50aW1lID0gbm93JDEoKSwgZGVmYXVsdFRpbWluZyQxOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGltaW5nOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl90cmFuc2l0aW9uJDEobmFtZSkgewogICAgICB2YXIgaWQsCiAgICAgICAgICB0aW1pbmc7CgogICAgICBpZiAobmFtZSBpbnN0YW5jZW9mIFRyYW5zaXRpb24kMSkgewogICAgICAgIGlkID0gbmFtZS5faWQsIG5hbWUgPSBuYW1lLl9uYW1lOwogICAgICB9IGVsc2UgewogICAgICAgIGlkID0gbmV3SWQkMSgpLCAodGltaW5nID0gZGVmYXVsdFRpbWluZyQxKS50aW1lID0gbm93JDEoKSwgbmFtZSA9IG5hbWUgPT0gbnVsbCA/IG51bGwgOiBuYW1lICsgIiI7CiAgICAgIH0KCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHNjaGVkdWxlJDIobm9kZSwgbmFtZSwgaWQsIGksIGdyb3VwLCB0aW1pbmcgfHwgaW5oZXJpdCQxKG5vZGUsIGlkKSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMShncm91cHMsIHRoaXMuX3BhcmVudHMsIG5hbWUsIGlkKTsKICAgIH0KCiAgICBzZWxlY3Rpb24kMS5wcm90b3R5cGUuaW50ZXJydXB0ID0gc2VsZWN0aW9uX2ludGVycnVwdCQxOwogICAgc2VsZWN0aW9uJDEucHJvdG90eXBlLnRyYW5zaXRpb24gPSBzZWxlY3Rpb25fdHJhbnNpdGlvbiQxOwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGgoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gQnJ1c2hFdmVudCQxKHRhcmdldCwgdHlwZSwgc2VsZWN0aW9uKSB7CiAgICAgIHRoaXMudGFyZ2V0ID0gdGFyZ2V0OwogICAgICB0aGlzLnR5cGUgPSB0eXBlOwogICAgICB0aGlzLnNlbGVjdGlvbiA9IHNlbGVjdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBub3Byb3BhZ2F0aW9uJDMoKSB7CiAgICAgIGV2ZW50JDEuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9ldmVudCQ0KCkgewogICAgICBldmVudCQxLnByZXZlbnREZWZhdWx0KCk7CiAgICAgIGV2ZW50JDEuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgdmFyIE1PREVfRFJBRyQxID0ge25hbWU6ICJkcmFnIn0sCiAgICAgICAgTU9ERV9TUEFDRSQxID0ge25hbWU6ICJzcGFjZSJ9LAogICAgICAgIE1PREVfSEFORExFJDEgPSB7bmFtZTogImhhbmRsZSJ9LAogICAgICAgIE1PREVfQ0VOVEVSJDEgPSB7bmFtZTogImNlbnRlciJ9OwoKICAgIHZhciBYJDEgPSB7CiAgICAgIG5hbWU6ICJ4IiwKICAgICAgaGFuZGxlczogWyJlIiwgInciXS5tYXAodHlwZSQxKSwKICAgICAgaW5wdXQ6IGZ1bmN0aW9uKHgsIGUpIHsgcmV0dXJuIHggJiYgW1t4WzBdLCBlWzBdWzFdXSwgW3hbMV0sIGVbMV1bMV1dXTsgfSwKICAgICAgb3V0cHV0OiBmdW5jdGlvbih4eSkgeyByZXR1cm4geHkgJiYgW3h5WzBdWzBdLCB4eVsxXVswXV07IH0KICAgIH07CgogICAgdmFyIFkkMSA9IHsKICAgICAgbmFtZTogInkiLAogICAgICBoYW5kbGVzOiBbIm4iLCAicyJdLm1hcCh0eXBlJDEpLAogICAgICBpbnB1dDogZnVuY3Rpb24oeSwgZSkgeyByZXR1cm4geSAmJiBbW2VbMF1bMF0sIHlbMF1dLCBbZVsxXVswXSwgeVsxXV1dOyB9LAogICAgICBvdXRwdXQ6IGZ1bmN0aW9uKHh5KSB7IHJldHVybiB4eSAmJiBbeHlbMF1bMV0sIHh5WzFdWzFdXTsgfQogICAgfTsKCiAgICB2YXIgWFkkMSA9IHsKICAgICAgbmFtZTogInh5IiwKICAgICAgaGFuZGxlczogWyJuIiwgImUiLCAicyIsICJ3IiwgIm53IiwgIm5lIiwgInNlIiwgInN3Il0ubWFwKHR5cGUkMSksCiAgICAgIGlucHV0OiBmdW5jdGlvbih4eSkgeyByZXR1cm4geHk7IH0sCiAgICAgIG91dHB1dDogZnVuY3Rpb24oeHkpIHsgcmV0dXJuIHh5OyB9CiAgICB9OwoKICAgIHZhciBjdXJzb3JzJDEgPSB7CiAgICAgIG92ZXJsYXk6ICJjcm9zc2hhaXIiLAogICAgICBzZWxlY3Rpb246ICJtb3ZlIiwKICAgICAgbjogIm5zLXJlc2l6ZSIsCiAgICAgIGU6ICJldy1yZXNpemUiLAogICAgICBzOiAibnMtcmVzaXplIiwKICAgICAgdzogImV3LXJlc2l6ZSIsCiAgICAgIG53OiAibndzZS1yZXNpemUiLAogICAgICBuZTogIm5lc3ctcmVzaXplIiwKICAgICAgc2U6ICJud3NlLXJlc2l6ZSIsCiAgICAgIHN3OiAibmVzdy1yZXNpemUiCiAgICB9OwoKICAgIHZhciBmbGlwWCQxID0gewogICAgICBlOiAidyIsCiAgICAgIHc6ICJlIiwKICAgICAgbnc6ICJuZSIsCiAgICAgIG5lOiAibnciLAogICAgICBzZTogInN3IiwKICAgICAgc3c6ICJzZSIKICAgIH07CgogICAgdmFyIGZsaXBZJDEgPSB7CiAgICAgIG46ICJzIiwKICAgICAgczogIm4iLAogICAgICBudzogInN3IiwKICAgICAgbmU6ICJzZSIsCiAgICAgIHNlOiAibmUiLAogICAgICBzdzogIm53IgogICAgfTsKCiAgICB2YXIgc2lnbnNYJDEgPSB7CiAgICAgIG92ZXJsYXk6ICsxLAogICAgICBzZWxlY3Rpb246ICsxLAogICAgICBuOiBudWxsLAogICAgICBlOiArMSwKICAgICAgczogbnVsbCwKICAgICAgdzogLTEsCiAgICAgIG53OiAtMSwKICAgICAgbmU6ICsxLAogICAgICBzZTogKzEsCiAgICAgIHN3OiAtMQogICAgfTsKCiAgICB2YXIgc2lnbnNZJDEgPSB7CiAgICAgIG92ZXJsYXk6ICsxLAogICAgICBzZWxlY3Rpb246ICsxLAogICAgICBuOiAtMSwKICAgICAgZTogbnVsbCwKICAgICAgczogKzEsCiAgICAgIHc6IG51bGwsCiAgICAgIG53OiAtMSwKICAgICAgbmU6IC0xLAogICAgICBzZTogKzEsCiAgICAgIHN3OiArMQogICAgfTsKCiAgICBmdW5jdGlvbiB0eXBlJDEodCkgewogICAgICByZXR1cm4ge3R5cGU6IHR9OwogICAgfQoKICAgIC8vIElnbm9yZSByaWdodC1jbGljaywgc2luY2UgdGhhdCBzaG91bGQgb3BlbiB0aGUgY29udGV4dCBtZW51LgogICAgZnVuY3Rpb24gZGVmYXVsdEZpbHRlciQzKCkgewogICAgICByZXR1cm4gIWV2ZW50JDEuYnV0dG9uOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRFeHRlbnQkMigpIHsKICAgICAgdmFyIHN2ZyA9IHRoaXMub3duZXJTVkdFbGVtZW50IHx8IHRoaXM7CiAgICAgIHJldHVybiBbWzAsIDBdLCBbc3ZnLndpZHRoLmJhc2VWYWwudmFsdWUsIHN2Zy5oZWlnaHQuYmFzZVZhbC52YWx1ZV1dOwogICAgfQoKICAgIC8vIExpa2UgZDMubG9jYWwsIGJ1dCB3aXRoIHRoZSBuYW1lIOKAnF9fYnJ1c2jigJ0gcmF0aGVyIHRoYW4gYXV0by1nZW5lcmF0ZWQuCiAgICBmdW5jdGlvbiBsb2NhbCQyKG5vZGUpIHsKICAgICAgd2hpbGUgKCFub2RlLl9fYnJ1c2gpIGlmICghKG5vZGUgPSBub2RlLnBhcmVudE5vZGUpKSByZXR1cm47CiAgICAgIHJldHVybiBub2RlLl9fYnJ1c2g7CiAgICB9CgogICAgZnVuY3Rpb24gZW1wdHkkMyhleHRlbnQpIHsKICAgICAgcmV0dXJuIGV4dGVudFswXVswXSA9PT0gZXh0ZW50WzFdWzBdCiAgICAgICAgICB8fCBleHRlbnRbMF1bMV0gPT09IGV4dGVudFsxXVsxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBicnVzaFNlbGVjdGlvbiQxKG5vZGUpIHsKICAgICAgdmFyIHN0YXRlID0gbm9kZS5fX2JydXNoOwogICAgICByZXR1cm4gc3RhdGUgPyBzdGF0ZS5kaW0ub3V0cHV0KHN0YXRlLnNlbGVjdGlvbikgOiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIGJydXNoWCQxKCkgewogICAgICByZXR1cm4gYnJ1c2gkMyhYJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJydXNoWSQxKCkgewogICAgICByZXR1cm4gYnJ1c2gkMyhZJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJydXNoJDIoKSB7CiAgICAgIHJldHVybiBicnVzaCQzKFhZJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJydXNoJDMoZGltKSB7CiAgICAgIHZhciBleHRlbnQgPSBkZWZhdWx0RXh0ZW50JDIsCiAgICAgICAgICBmaWx0ZXIgPSBkZWZhdWx0RmlsdGVyJDMsCiAgICAgICAgICBsaXN0ZW5lcnMgPSBkaXNwYXRjaCQxKGJydXNoLCAic3RhcnQiLCAiYnJ1c2giLCAiZW5kIiksCiAgICAgICAgICBoYW5kbGVTaXplID0gNiwKICAgICAgICAgIHRvdWNoZW5kaW5nOwoKICAgICAgZnVuY3Rpb24gYnJ1c2goZ3JvdXApIHsKICAgICAgICB2YXIgb3ZlcmxheSA9IGdyb3VwCiAgICAgICAgICAgIC5wcm9wZXJ0eSgiX19icnVzaCIsIGluaXRpYWxpemUpCiAgICAgICAgICAuc2VsZWN0QWxsKCIub3ZlcmxheSIpCiAgICAgICAgICAuZGF0YShbdHlwZSQxKCJvdmVybGF5IildKTsKCiAgICAgICAgb3ZlcmxheS5lbnRlcigpLmFwcGVuZCgicmVjdCIpCiAgICAgICAgICAgIC5hdHRyKCJjbGFzcyIsICJvdmVybGF5IikKICAgICAgICAgICAgLmF0dHIoInBvaW50ZXItZXZlbnRzIiwgImFsbCIpCiAgICAgICAgICAgIC5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzJDEub3ZlcmxheSkKICAgICAgICAgIC5tZXJnZShvdmVybGF5KQogICAgICAgICAgICAuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICAgICAgICB2YXIgZXh0ZW50ID0gbG9jYWwkMih0aGlzKS5leHRlbnQ7CiAgICAgICAgICAgICAgc2VsZWN0JDEodGhpcykKICAgICAgICAgICAgICAgICAgLmF0dHIoIngiLCBleHRlbnRbMF1bMF0pCiAgICAgICAgICAgICAgICAgIC5hdHRyKCJ5IiwgZXh0ZW50WzBdWzFdKQogICAgICAgICAgICAgICAgICAuYXR0cigid2lkdGgiLCBleHRlbnRbMV1bMF0gLSBleHRlbnRbMF1bMF0pCiAgICAgICAgICAgICAgICAgIC5hdHRyKCJoZWlnaHQiLCBleHRlbnRbMV1bMV0gLSBleHRlbnRbMF1bMV0pOwogICAgICAgICAgICB9KTsKCiAgICAgICAgZ3JvdXAuc2VsZWN0QWxsKCIuc2VsZWN0aW9uIikKICAgICAgICAgIC5kYXRhKFt0eXBlJDEoInNlbGVjdGlvbiIpXSkKICAgICAgICAgIC5lbnRlcigpLmFwcGVuZCgicmVjdCIpCiAgICAgICAgICAgIC5hdHRyKCJjbGFzcyIsICJzZWxlY3Rpb24iKQogICAgICAgICAgICAuYXR0cigiY3Vyc29yIiwgY3Vyc29ycyQxLnNlbGVjdGlvbikKICAgICAgICAgICAgLmF0dHIoImZpbGwiLCAiIzc3NyIpCiAgICAgICAgICAgIC5hdHRyKCJmaWxsLW9wYWNpdHkiLCAwLjMpCiAgICAgICAgICAgIC5hdHRyKCJzdHJva2UiLCAiI2ZmZiIpCiAgICAgICAgICAgIC5hdHRyKCJzaGFwZS1yZW5kZXJpbmciLCAiY3Jpc3BFZGdlcyIpOwoKICAgICAgICB2YXIgaGFuZGxlID0gZ3JvdXAuc2VsZWN0QWxsKCIuaGFuZGxlIikKICAgICAgICAgIC5kYXRhKGRpbS5oYW5kbGVzLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGU7IH0pOwoKICAgICAgICBoYW5kbGUuZXhpdCgpLnJlbW92ZSgpOwoKICAgICAgICBoYW5kbGUuZW50ZXIoKS5hcHBlbmQoInJlY3QiKQogICAgICAgICAgICAuYXR0cigiY2xhc3MiLCBmdW5jdGlvbihkKSB7IHJldHVybiAiaGFuZGxlIGhhbmRsZS0tIiArIGQudHlwZTsgfSkKICAgICAgICAgICAgLmF0dHIoImN1cnNvciIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGN1cnNvcnMkMVtkLnR5cGVdOyB9KTsKCiAgICAgICAgZ3JvdXAKICAgICAgICAgICAgLmVhY2gocmVkcmF3KQogICAgICAgICAgICAuYXR0cigiZmlsbCIsICJub25lIikKICAgICAgICAgICAgLmF0dHIoInBvaW50ZXItZXZlbnRzIiwgImFsbCIpCiAgICAgICAgICAgIC5zdHlsZSgiLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yIiwgInJnYmEoMCwwLDAsMCkiKQogICAgICAgICAgICAub24oIm1vdXNlZG93bi5icnVzaCB0b3VjaHN0YXJ0LmJydXNoIiwgc3RhcnRlZCk7CiAgICAgIH0KCiAgICAgIGJydXNoLm1vdmUgPSBmdW5jdGlvbihncm91cCwgc2VsZWN0aW9uKSB7CiAgICAgICAgaWYgKGdyb3VwLnNlbGVjdGlvbikgewogICAgICAgICAgZ3JvdXAKICAgICAgICAgICAgICAub24oInN0YXJ0LmJydXNoIiwgZnVuY3Rpb24oKSB7IGVtaXR0ZXIodGhpcywgYXJndW1lbnRzKS5iZWZvcmVzdGFydCgpLnN0YXJ0KCk7IH0pCiAgICAgICAgICAgICAgLm9uKCJpbnRlcnJ1cHQuYnJ1c2ggZW5kLmJydXNoIiwgZnVuY3Rpb24oKSB7IGVtaXR0ZXIodGhpcywgYXJndW1lbnRzKS5lbmQoKTsgfSkKICAgICAgICAgICAgICAudHdlZW4oImJydXNoIiwgZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgICB2YXIgdGhhdCA9IHRoaXMsCiAgICAgICAgICAgICAgICAgICAgc3RhdGUgPSB0aGF0Ll9fYnJ1c2gsCiAgICAgICAgICAgICAgICAgICAgZW1pdCA9IGVtaXR0ZXIodGhhdCwgYXJndW1lbnRzKSwKICAgICAgICAgICAgICAgICAgICBzZWxlY3Rpb24wID0gc3RhdGUuc2VsZWN0aW9uLAogICAgICAgICAgICAgICAgICAgIHNlbGVjdGlvbjEgPSBkaW0uaW5wdXQodHlwZW9mIHNlbGVjdGlvbiA9PT0gImZ1bmN0aW9uIiA/IHNlbGVjdGlvbi5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogc2VsZWN0aW9uLCBzdGF0ZS5leHRlbnQpLAogICAgICAgICAgICAgICAgICAgIGkgPSBpbnRlcnBvbGF0ZSQyKHNlbGVjdGlvbjAsIHNlbGVjdGlvbjEpOwoKICAgICAgICAgICAgICAgIGZ1bmN0aW9uIHR3ZWVuKHQpIHsKICAgICAgICAgICAgICAgICAgc3RhdGUuc2VsZWN0aW9uID0gdCA9PT0gMSAmJiBlbXB0eSQzKHNlbGVjdGlvbjEpID8gbnVsbCA6IGkodCk7CiAgICAgICAgICAgICAgICAgIHJlZHJhdy5jYWxsKHRoYXQpOwogICAgICAgICAgICAgICAgICBlbWl0LmJydXNoKCk7CiAgICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgICAgcmV0dXJuIHNlbGVjdGlvbjAgJiYgc2VsZWN0aW9uMSA/IHR3ZWVuIDogdHdlZW4oMSk7CiAgICAgICAgICAgICAgfSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGdyb3VwCiAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgICB2YXIgdGhhdCA9IHRoaXMsCiAgICAgICAgICAgICAgICAgICAgYXJncyA9IGFyZ3VtZW50cywKICAgICAgICAgICAgICAgICAgICBzdGF0ZSA9IHRoYXQuX19icnVzaCwKICAgICAgICAgICAgICAgICAgICBzZWxlY3Rpb24xID0gZGltLmlucHV0KHR5cGVvZiBzZWxlY3Rpb24gPT09ICJmdW5jdGlvbiIgPyBzZWxlY3Rpb24uYXBwbHkodGhhdCwgYXJncykgOiBzZWxlY3Rpb24sIHN0YXRlLmV4dGVudCksCiAgICAgICAgICAgICAgICAgICAgZW1pdCA9IGVtaXR0ZXIodGhhdCwgYXJncykuYmVmb3Jlc3RhcnQoKTsKCiAgICAgICAgICAgICAgICBpbnRlcnJ1cHQkMSh0aGF0KTsKICAgICAgICAgICAgICAgIHN0YXRlLnNlbGVjdGlvbiA9IHNlbGVjdGlvbjEgPT0gbnVsbCB8fCBlbXB0eSQzKHNlbGVjdGlvbjEpID8gbnVsbCA6IHNlbGVjdGlvbjE7CiAgICAgICAgICAgICAgICByZWRyYXcuY2FsbCh0aGF0KTsKICAgICAgICAgICAgICAgIGVtaXQuc3RhcnQoKS5icnVzaCgpLmVuZCgpOwogICAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfTsKCiAgICAgIGZ1bmN0aW9uIHJlZHJhdygpIHsKICAgICAgICB2YXIgZ3JvdXAgPSBzZWxlY3QkMSh0aGlzKSwKICAgICAgICAgICAgc2VsZWN0aW9uID0gbG9jYWwkMih0aGlzKS5zZWxlY3Rpb247CgogICAgICAgIGlmIChzZWxlY3Rpb24pIHsKICAgICAgICAgIGdyb3VwLnNlbGVjdEFsbCgiLnNlbGVjdGlvbiIpCiAgICAgICAgICAgICAgLnN0eWxlKCJkaXNwbGF5IiwgbnVsbCkKICAgICAgICAgICAgICAuYXR0cigieCIsIHNlbGVjdGlvblswXVswXSkKICAgICAgICAgICAgICAuYXR0cigieSIsIHNlbGVjdGlvblswXVsxXSkKICAgICAgICAgICAgICAuYXR0cigid2lkdGgiLCBzZWxlY3Rpb25bMV1bMF0gLSBzZWxlY3Rpb25bMF1bMF0pCiAgICAgICAgICAgICAgLmF0dHIoImhlaWdodCIsIHNlbGVjdGlvblsxXVsxXSAtIHNlbGVjdGlvblswXVsxXSk7CgogICAgICAgICAgZ3JvdXAuc2VsZWN0QWxsKCIuaGFuZGxlIikKICAgICAgICAgICAgICAuc3R5bGUoImRpc3BsYXkiLCBudWxsKQogICAgICAgICAgICAgIC5hdHRyKCJ4IiwgZnVuY3Rpb24oZCkgeyByZXR1cm4gZC50eXBlW2QudHlwZS5sZW5ndGggLSAxXSA9PT0gImUiID8gc2VsZWN0aW9uWzFdWzBdIC0gaGFuZGxlU2l6ZSAvIDIgOiBzZWxlY3Rpb25bMF1bMF0gLSBoYW5kbGVTaXplIC8gMjsgfSkKICAgICAgICAgICAgICAuYXR0cigieSIsIGZ1bmN0aW9uKGQpIHsgcmV0dXJuIGQudHlwZVswXSA9PT0gInMiID8gc2VsZWN0aW9uWzFdWzFdIC0gaGFuZGxlU2l6ZSAvIDIgOiBzZWxlY3Rpb25bMF1bMV0gLSBoYW5kbGVTaXplIC8gMjsgfSkKICAgICAgICAgICAgICAuYXR0cigid2lkdGgiLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGUgPT09ICJuIiB8fCBkLnR5cGUgPT09ICJzIiA/IHNlbGVjdGlvblsxXVswXSAtIHNlbGVjdGlvblswXVswXSArIGhhbmRsZVNpemUgOiBoYW5kbGVTaXplOyB9KQogICAgICAgICAgICAgIC5hdHRyKCJoZWlnaHQiLCBmdW5jdGlvbihkKSB7IHJldHVybiBkLnR5cGUgPT09ICJlIiB8fCBkLnR5cGUgPT09ICJ3IiA/IHNlbGVjdGlvblsxXVsxXSAtIHNlbGVjdGlvblswXVsxXSArIGhhbmRsZVNpemUgOiBoYW5kbGVTaXplOyB9KTsKICAgICAgICB9CgogICAgICAgIGVsc2UgewogICAgICAgICAgZ3JvdXAuc2VsZWN0QWxsKCIuc2VsZWN0aW9uLC5oYW5kbGUiKQogICAgICAgICAgICAgIC5zdHlsZSgiZGlzcGxheSIsICJub25lIikKICAgICAgICAgICAgICAuYXR0cigieCIsIG51bGwpCiAgICAgICAgICAgICAgLmF0dHIoInkiLCBudWxsKQogICAgICAgICAgICAgIC5hdHRyKCJ3aWR0aCIsIG51bGwpCiAgICAgICAgICAgICAgLmF0dHIoImhlaWdodCIsIG51bGwpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gZW1pdHRlcih0aGF0LCBhcmdzKSB7CiAgICAgICAgcmV0dXJuIHRoYXQuX19icnVzaC5lbWl0dGVyIHx8IG5ldyBFbWl0dGVyKHRoYXQsIGFyZ3MpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBFbWl0dGVyKHRoYXQsIGFyZ3MpIHsKICAgICAgICB0aGlzLnRoYXQgPSB0aGF0OwogICAgICAgIHRoaXMuYXJncyA9IGFyZ3M7CiAgICAgICAgdGhpcy5zdGF0ZSA9IHRoYXQuX19icnVzaDsKICAgICAgICB0aGlzLmFjdGl2ZSA9IDA7CiAgICAgIH0KCiAgICAgIEVtaXR0ZXIucHJvdG90eXBlID0gewogICAgICAgIGJlZm9yZXN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIGlmICgrK3RoaXMuYWN0aXZlID09PSAxKSB0aGlzLnN0YXRlLmVtaXR0ZXIgPSB0aGlzLCB0aGlzLnN0YXJ0aW5nID0gdHJ1ZTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0sCiAgICAgICAgc3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgaWYgKHRoaXMuc3RhcnRpbmcpIHRoaXMuc3RhcnRpbmcgPSBmYWxzZSwgdGhpcy5lbWl0KCJzdGFydCIpOwogICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfSwKICAgICAgICBicnVzaDogZnVuY3Rpb24oKSB7CiAgICAgICAgICB0aGlzLmVtaXQoImJydXNoIik7CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIGVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoLS10aGlzLmFjdGl2ZSA9PT0gMCkgZGVsZXRlIHRoaXMuc3RhdGUuZW1pdHRlciwgdGhpcy5lbWl0KCJlbmQiKTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0sCiAgICAgICAgZW1pdDogZnVuY3Rpb24odHlwZSkgewogICAgICAgICAgY3VzdG9tRXZlbnQkMShuZXcgQnJ1c2hFdmVudCQxKGJydXNoLCB0eXBlLCBkaW0ub3V0cHV0KHRoaXMuc3RhdGUuc2VsZWN0aW9uKSksIGxpc3RlbmVycy5hcHBseSwgbGlzdGVuZXJzLCBbdHlwZSwgdGhpcy50aGF0LCB0aGlzLmFyZ3NdKTsKICAgICAgICB9CiAgICAgIH07CgogICAgICBmdW5jdGlvbiBzdGFydGVkKCkgewogICAgICAgIGlmIChldmVudCQxLnRvdWNoZXMpIHsgaWYgKGV2ZW50JDEuY2hhbmdlZFRvdWNoZXMubGVuZ3RoIDwgZXZlbnQkMS50b3VjaGVzLmxlbmd0aCkgcmV0dXJuIG5vZXZlbnQkNCgpOyB9CiAgICAgICAgZWxzZSBpZiAodG91Y2hlbmRpbmcpIHJldHVybjsKICAgICAgICBpZiAoIWZpbHRlci5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSByZXR1cm47CgogICAgICAgIHZhciB0aGF0ID0gdGhpcywKICAgICAgICAgICAgdHlwZSA9IGV2ZW50JDEudGFyZ2V0Ll9fZGF0YV9fLnR5cGUsCiAgICAgICAgICAgIG1vZGUgPSAoZXZlbnQkMS5tZXRhS2V5ID8gdHlwZSA9ICJvdmVybGF5IiA6IHR5cGUpID09PSAic2VsZWN0aW9uIiA/IE1PREVfRFJBRyQxIDogKGV2ZW50JDEuYWx0S2V5ID8gTU9ERV9DRU5URVIkMSA6IE1PREVfSEFORExFJDEpLAogICAgICAgICAgICBzaWduWCA9IGRpbSA9PT0gWSQxID8gbnVsbCA6IHNpZ25zWCQxW3R5cGVdLAogICAgICAgICAgICBzaWduWSA9IGRpbSA9PT0gWCQxID8gbnVsbCA6IHNpZ25zWSQxW3R5cGVdLAogICAgICAgICAgICBzdGF0ZSA9IGxvY2FsJDIodGhhdCksCiAgICAgICAgICAgIGV4dGVudCA9IHN0YXRlLmV4dGVudCwKICAgICAgICAgICAgc2VsZWN0aW9uID0gc3RhdGUuc2VsZWN0aW9uLAogICAgICAgICAgICBXID0gZXh0ZW50WzBdWzBdLCB3MCwgdzEsCiAgICAgICAgICAgIE4gPSBleHRlbnRbMF1bMV0sIG4wLCBuMSwKICAgICAgICAgICAgRSA9IGV4dGVudFsxXVswXSwgZTAsIGUxLAogICAgICAgICAgICBTID0gZXh0ZW50WzFdWzFdLCBzMCwgczEsCiAgICAgICAgICAgIGR4LAogICAgICAgICAgICBkeSwKICAgICAgICAgICAgbW92aW5nLAogICAgICAgICAgICBzaGlmdGluZyA9IHNpZ25YICYmIHNpZ25ZICYmIGV2ZW50JDEuc2hpZnRLZXksCiAgICAgICAgICAgIGxvY2tYLAogICAgICAgICAgICBsb2NrWSwKICAgICAgICAgICAgcG9pbnQwID0gbW91c2UkMSh0aGF0KSwKICAgICAgICAgICAgcG9pbnQgPSBwb2ludDAsCiAgICAgICAgICAgIGVtaXQgPSBlbWl0dGVyKHRoYXQsIGFyZ3VtZW50cykuYmVmb3Jlc3RhcnQoKTsKCiAgICAgICAgaWYgKHR5cGUgPT09ICJvdmVybGF5IikgewogICAgICAgICAgc3RhdGUuc2VsZWN0aW9uID0gc2VsZWN0aW9uID0gWwogICAgICAgICAgICBbdzAgPSBkaW0gPT09IFkkMSA/IFcgOiBwb2ludDBbMF0sIG4wID0gZGltID09PSBYJDEgPyBOIDogcG9pbnQwWzFdXSwKICAgICAgICAgICAgW2UwID0gZGltID09PSBZJDEgPyBFIDogdzAsIHMwID0gZGltID09PSBYJDEgPyBTIDogbjBdCiAgICAgICAgICBdOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB3MCA9IHNlbGVjdGlvblswXVswXTsKICAgICAgICAgIG4wID0gc2VsZWN0aW9uWzBdWzFdOwogICAgICAgICAgZTAgPSBzZWxlY3Rpb25bMV1bMF07CiAgICAgICAgICBzMCA9IHNlbGVjdGlvblsxXVsxXTsKICAgICAgICB9CgogICAgICAgIHcxID0gdzA7CiAgICAgICAgbjEgPSBuMDsKICAgICAgICBlMSA9IGUwOwogICAgICAgIHMxID0gczA7CgogICAgICAgIHZhciBncm91cCA9IHNlbGVjdCQxKHRoYXQpCiAgICAgICAgICAgIC5hdHRyKCJwb2ludGVyLWV2ZW50cyIsICJub25lIik7CgogICAgICAgIHZhciBvdmVybGF5ID0gZ3JvdXAuc2VsZWN0QWxsKCIub3ZlcmxheSIpCiAgICAgICAgICAgIC5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzJDFbdHlwZV0pOwoKICAgICAgICBpZiAoZXZlbnQkMS50b3VjaGVzKSB7CiAgICAgICAgICBncm91cAogICAgICAgICAgICAgIC5vbigidG91Y2htb3ZlLmJydXNoIiwgbW92ZWQsIHRydWUpCiAgICAgICAgICAgICAgLm9uKCJ0b3VjaGVuZC5icnVzaCB0b3VjaGNhbmNlbC5icnVzaCIsIGVuZGVkLCB0cnVlKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFyIHZpZXcgPSBzZWxlY3QkMShldmVudCQxLnZpZXcpCiAgICAgICAgICAgICAgLm9uKCJrZXlkb3duLmJydXNoIiwga2V5ZG93bmVkLCB0cnVlKQogICAgICAgICAgICAgIC5vbigia2V5dXAuYnJ1c2giLCBrZXl1cHBlZCwgdHJ1ZSkKICAgICAgICAgICAgICAub24oIm1vdXNlbW92ZS5icnVzaCIsIG1vdmVkLCB0cnVlKQogICAgICAgICAgICAgIC5vbigibW91c2V1cC5icnVzaCIsIGVuZGVkLCB0cnVlKTsKCiAgICAgICAgICBkcmFnRGlzYWJsZSQxKGV2ZW50JDEudmlldyk7CiAgICAgICAgfQoKICAgICAgICBub3Byb3BhZ2F0aW9uJDMoKTsKICAgICAgICBpbnRlcnJ1cHQkMSh0aGF0KTsKICAgICAgICByZWRyYXcuY2FsbCh0aGF0KTsKICAgICAgICBlbWl0LnN0YXJ0KCk7CgogICAgICAgIGZ1bmN0aW9uIG1vdmVkKCkgewogICAgICAgICAgdmFyIHBvaW50MSA9IG1vdXNlJDEodGhhdCk7CiAgICAgICAgICBpZiAoc2hpZnRpbmcgJiYgIWxvY2tYICYmICFsb2NrWSkgewogICAgICAgICAgICBpZiAoTWF0aC5hYnMocG9pbnQxWzBdIC0gcG9pbnRbMF0pID4gTWF0aC5hYnMocG9pbnQxWzFdIC0gcG9pbnRbMV0pKSBsb2NrWSA9IHRydWU7CiAgICAgICAgICAgIGVsc2UgbG9ja1ggPSB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgcG9pbnQgPSBwb2ludDE7CiAgICAgICAgICBtb3ZpbmcgPSB0cnVlOwogICAgICAgICAgbm9ldmVudCQ0KCk7CiAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBtb3ZlKCkgewogICAgICAgICAgdmFyIHQ7CgogICAgICAgICAgZHggPSBwb2ludFswXSAtIHBvaW50MFswXTsKICAgICAgICAgIGR5ID0gcG9pbnRbMV0gLSBwb2ludDBbMV07CgogICAgICAgICAgc3dpdGNoIChtb2RlKSB7CiAgICAgICAgICAgIGNhc2UgTU9ERV9TUEFDRSQxOgogICAgICAgICAgICBjYXNlIE1PREVfRFJBRyQxOiB7CiAgICAgICAgICAgICAgaWYgKHNpZ25YKSBkeCA9IE1hdGgubWF4KFcgLSB3MCwgTWF0aC5taW4oRSAtIGUwLCBkeCkpLCB3MSA9IHcwICsgZHgsIGUxID0gZTAgKyBkeDsKICAgICAgICAgICAgICBpZiAoc2lnblkpIGR5ID0gTWF0aC5tYXgoTiAtIG4wLCBNYXRoLm1pbihTIC0gczAsIGR5KSksIG4xID0gbjAgKyBkeSwgczEgPSBzMCArIGR5OwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgTU9ERV9IQU5ETEUkMTogewogICAgICAgICAgICAgIGlmIChzaWduWCA8IDApIGR4ID0gTWF0aC5tYXgoVyAtIHcwLCBNYXRoLm1pbihFIC0gdzAsIGR4KSksIHcxID0gdzAgKyBkeCwgZTEgPSBlMDsKICAgICAgICAgICAgICBlbHNlIGlmIChzaWduWCA+IDApIGR4ID0gTWF0aC5tYXgoVyAtIGUwLCBNYXRoLm1pbihFIC0gZTAsIGR4KSksIHcxID0gdzAsIGUxID0gZTAgKyBkeDsKICAgICAgICAgICAgICBpZiAoc2lnblkgPCAwKSBkeSA9IE1hdGgubWF4KE4gLSBuMCwgTWF0aC5taW4oUyAtIG4wLCBkeSkpLCBuMSA9IG4wICsgZHksIHMxID0gczA7CiAgICAgICAgICAgICAgZWxzZSBpZiAoc2lnblkgPiAwKSBkeSA9IE1hdGgubWF4KE4gLSBzMCwgTWF0aC5taW4oUyAtIHMwLCBkeSkpLCBuMSA9IG4wLCBzMSA9IHMwICsgZHk7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSBNT0RFX0NFTlRFUiQxOiB7CiAgICAgICAgICAgICAgaWYgKHNpZ25YKSB3MSA9IE1hdGgubWF4KFcsIE1hdGgubWluKEUsIHcwIC0gZHggKiBzaWduWCkpLCBlMSA9IE1hdGgubWF4KFcsIE1hdGgubWluKEUsIGUwICsgZHggKiBzaWduWCkpOwogICAgICAgICAgICAgIGlmIChzaWduWSkgbjEgPSBNYXRoLm1heChOLCBNYXRoLm1pbihTLCBuMCAtIGR5ICogc2lnblkpKSwgczEgPSBNYXRoLm1heChOLCBNYXRoLm1pbihTLCBzMCArIGR5ICogc2lnblkpKTsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgfQoKICAgICAgICAgIGlmIChlMSA8IHcxKSB7CiAgICAgICAgICAgIHNpZ25YICo9IC0xOwogICAgICAgICAgICB0ID0gdzAsIHcwID0gZTAsIGUwID0gdDsKICAgICAgICAgICAgdCA9IHcxLCB3MSA9IGUxLCBlMSA9IHQ7CiAgICAgICAgICAgIGlmICh0eXBlIGluIGZsaXBYJDEpIG92ZXJsYXkuYXR0cigiY3Vyc29yIiwgY3Vyc29ycyQxW3R5cGUgPSBmbGlwWCQxW3R5cGVdXSk7CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKHMxIDwgbjEpIHsKICAgICAgICAgICAgc2lnblkgKj0gLTE7CiAgICAgICAgICAgIHQgPSBuMCwgbjAgPSBzMCwgczAgPSB0OwogICAgICAgICAgICB0ID0gbjEsIG4xID0gczEsIHMxID0gdDsKICAgICAgICAgICAgaWYgKHR5cGUgaW4gZmxpcFkkMSkgb3ZlcmxheS5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzJDFbdHlwZSA9IGZsaXBZJDFbdHlwZV1dKTsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAoc3RhdGUuc2VsZWN0aW9uKSBzZWxlY3Rpb24gPSBzdGF0ZS5zZWxlY3Rpb247IC8vIE1heSBiZSBzZXQgYnkgYnJ1c2gubW92ZSEKICAgICAgICAgIGlmIChsb2NrWCkgdzEgPSBzZWxlY3Rpb25bMF1bMF0sIGUxID0gc2VsZWN0aW9uWzFdWzBdOwogICAgICAgICAgaWYgKGxvY2tZKSBuMSA9IHNlbGVjdGlvblswXVsxXSwgczEgPSBzZWxlY3Rpb25bMV1bMV07CgogICAgICAgICAgaWYgKHNlbGVjdGlvblswXVswXSAhPT0gdzEKICAgICAgICAgICAgICB8fCBzZWxlY3Rpb25bMF1bMV0gIT09IG4xCiAgICAgICAgICAgICAgfHwgc2VsZWN0aW9uWzFdWzBdICE9PSBlMQogICAgICAgICAgICAgIHx8IHNlbGVjdGlvblsxXVsxXSAhPT0gczEpIHsKICAgICAgICAgICAgc3RhdGUuc2VsZWN0aW9uID0gW1t3MSwgbjFdLCBbZTEsIHMxXV07CiAgICAgICAgICAgIHJlZHJhdy5jYWxsKHRoYXQpOwogICAgICAgICAgICBlbWl0LmJydXNoKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBlbmRlZCgpIHsKICAgICAgICAgIG5vcHJvcGFnYXRpb24kMygpOwogICAgICAgICAgaWYgKGV2ZW50JDEudG91Y2hlcykgewogICAgICAgICAgICBpZiAoZXZlbnQkMS50b3VjaGVzLmxlbmd0aCkgcmV0dXJuOwogICAgICAgICAgICBpZiAodG91Y2hlbmRpbmcpIGNsZWFyVGltZW91dCh0b3VjaGVuZGluZyk7CiAgICAgICAgICAgIHRvdWNoZW5kaW5nID0gc2V0VGltZW91dChmdW5jdGlvbigpIHsgdG91Y2hlbmRpbmcgPSBudWxsOyB9LCA1MDApOyAvLyBHaG9zdCBjbGlja3MgYXJlIGRlbGF5ZWQhCiAgICAgICAgICAgIGdyb3VwLm9uKCJ0b3VjaG1vdmUuYnJ1c2ggdG91Y2hlbmQuYnJ1c2ggdG91Y2hjYW5jZWwuYnJ1c2giLCBudWxsKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHllc2RyYWckMShldmVudCQxLnZpZXcsIG1vdmluZyk7CiAgICAgICAgICAgIHZpZXcub24oImtleWRvd24uYnJ1c2gga2V5dXAuYnJ1c2ggbW91c2Vtb3ZlLmJydXNoIG1vdXNldXAuYnJ1c2giLCBudWxsKTsKICAgICAgICAgIH0KICAgICAgICAgIGdyb3VwLmF0dHIoInBvaW50ZXItZXZlbnRzIiwgImFsbCIpOwogICAgICAgICAgb3ZlcmxheS5hdHRyKCJjdXJzb3IiLCBjdXJzb3JzJDEub3ZlcmxheSk7CiAgICAgICAgICBpZiAoc3RhdGUuc2VsZWN0aW9uKSBzZWxlY3Rpb24gPSBzdGF0ZS5zZWxlY3Rpb247IC8vIE1heSBiZSBzZXQgYnkgYnJ1c2gubW92ZSAob24gc3RhcnQpIQogICAgICAgICAgaWYgKGVtcHR5JDMoc2VsZWN0aW9uKSkgc3RhdGUuc2VsZWN0aW9uID0gbnVsbCwgcmVkcmF3LmNhbGwodGhhdCk7CiAgICAgICAgICBlbWl0LmVuZCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24ga2V5ZG93bmVkKCkgewogICAgICAgICAgc3dpdGNoIChldmVudCQxLmtleUNvZGUpIHsKICAgICAgICAgICAgY2FzZSAxNjogeyAvLyBTSElGVAogICAgICAgICAgICAgIHNoaWZ0aW5nID0gc2lnblggJiYgc2lnblk7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSAxODogeyAvLyBBTFQKICAgICAgICAgICAgICBpZiAobW9kZSA9PT0gTU9ERV9IQU5ETEUkMSkgewogICAgICAgICAgICAgICAgaWYgKHNpZ25YKSBlMCA9IGUxIC0gZHggKiBzaWduWCwgdzAgPSB3MSArIGR4ICogc2lnblg7CiAgICAgICAgICAgICAgICBpZiAoc2lnblkpIHMwID0gczEgLSBkeSAqIHNpZ25ZLCBuMCA9IG4xICsgZHkgKiBzaWduWTsKICAgICAgICAgICAgICAgIG1vZGUgPSBNT0RFX0NFTlRFUiQxOwogICAgICAgICAgICAgICAgbW92ZSgpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBjYXNlIDMyOiB7IC8vIFNQQUNFOyB0YWtlcyBwcmlvcml0eSBvdmVyIEFMVAogICAgICAgICAgICAgIGlmIChtb2RlID09PSBNT0RFX0hBTkRMRSQxIHx8IG1vZGUgPT09IE1PREVfQ0VOVEVSJDEpIHsKICAgICAgICAgICAgICAgIGlmIChzaWduWCA8IDApIGUwID0gZTEgLSBkeDsgZWxzZSBpZiAoc2lnblggPiAwKSB3MCA9IHcxIC0gZHg7CiAgICAgICAgICAgICAgICBpZiAoc2lnblkgPCAwKSBzMCA9IHMxIC0gZHk7IGVsc2UgaWYgKHNpZ25ZID4gMCkgbjAgPSBuMSAtIGR5OwogICAgICAgICAgICAgICAgbW9kZSA9IE1PREVfU1BBQ0UkMTsKICAgICAgICAgICAgICAgIG92ZXJsYXkuYXR0cigiY3Vyc29yIiwgY3Vyc29ycyQxLnNlbGVjdGlvbik7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGRlZmF1bHQ6IHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIG5vZXZlbnQkNCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24ga2V5dXBwZWQoKSB7CiAgICAgICAgICBzd2l0Y2ggKGV2ZW50JDEua2V5Q29kZSkgewogICAgICAgICAgICBjYXNlIDE2OiB7IC8vIFNISUZUCiAgICAgICAgICAgICAgaWYgKHNoaWZ0aW5nKSB7CiAgICAgICAgICAgICAgICBsb2NrWCA9IGxvY2tZID0gc2hpZnRpbmcgPSBmYWxzZTsKICAgICAgICAgICAgICAgIG1vdmUoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSAxODogeyAvLyBBTFQKICAgICAgICAgICAgICBpZiAobW9kZSA9PT0gTU9ERV9DRU5URVIkMSkgewogICAgICAgICAgICAgICAgaWYgKHNpZ25YIDwgMCkgZTAgPSBlMTsgZWxzZSBpZiAoc2lnblggPiAwKSB3MCA9IHcxOwogICAgICAgICAgICAgICAgaWYgKHNpZ25ZIDwgMCkgczAgPSBzMTsgZWxzZSBpZiAoc2lnblkgPiAwKSBuMCA9IG4xOwogICAgICAgICAgICAgICAgbW9kZSA9IE1PREVfSEFORExFJDE7CiAgICAgICAgICAgICAgICBtb3ZlKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgMzI6IHsgLy8gU1BBQ0UKICAgICAgICAgICAgICBpZiAobW9kZSA9PT0gTU9ERV9TUEFDRSQxKSB7CiAgICAgICAgICAgICAgICBpZiAoZXZlbnQkMS5hbHRLZXkpIHsKICAgICAgICAgICAgICAgICAgaWYgKHNpZ25YKSBlMCA9IGUxIC0gZHggKiBzaWduWCwgdzAgPSB3MSArIGR4ICogc2lnblg7CiAgICAgICAgICAgICAgICAgIGlmIChzaWduWSkgczAgPSBzMSAtIGR5ICogc2lnblksIG4wID0gbjEgKyBkeSAqIHNpZ25ZOwogICAgICAgICAgICAgICAgICBtb2RlID0gTU9ERV9DRU5URVIkMTsKICAgICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICAgIGlmIChzaWduWCA8IDApIGUwID0gZTE7IGVsc2UgaWYgKHNpZ25YID4gMCkgdzAgPSB3MTsKICAgICAgICAgICAgICAgICAgaWYgKHNpZ25ZIDwgMCkgczAgPSBzMTsgZWxzZSBpZiAoc2lnblkgPiAwKSBuMCA9IG4xOwogICAgICAgICAgICAgICAgICBtb2RlID0gTU9ERV9IQU5ETEUkMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIG92ZXJsYXkuYXR0cigiY3Vyc29yIiwgY3Vyc29ycyQxW3R5cGVdKTsKICAgICAgICAgICAgICAgIG1vdmUoKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZGVmYXVsdDogcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgbm9ldmVudCQ0KCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBpbml0aWFsaXplKCkgewogICAgICAgIHZhciBzdGF0ZSA9IHRoaXMuX19icnVzaCB8fCB7c2VsZWN0aW9uOiBudWxsfTsKICAgICAgICBzdGF0ZS5leHRlbnQgPSBleHRlbnQuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBzdGF0ZS5kaW0gPSBkaW07CiAgICAgICAgcmV0dXJuIHN0YXRlOwogICAgICB9CgogICAgICBicnVzaC5leHRlbnQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZXh0ZW50ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkaChbWytfWzBdWzBdLCArX1swXVsxXV0sIFsrX1sxXVswXSwgK19bMV1bMV1dXSksIGJydXNoKSA6IGV4dGVudDsKICAgICAgfTsKCiAgICAgIGJydXNoLmZpbHRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChmaWx0ZXIgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRoKCEhXyksIGJydXNoKSA6IGZpbHRlcjsKICAgICAgfTsKCiAgICAgIGJydXNoLmhhbmRsZVNpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaGFuZGxlU2l6ZSA9ICtfLCBicnVzaCkgOiBoYW5kbGVTaXplOwogICAgICB9OwoKICAgICAgYnJ1c2gub24gPSBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUgPSBsaXN0ZW5lcnMub24uYXBwbHkobGlzdGVuZXJzLCBhcmd1bWVudHMpOwogICAgICAgIHJldHVybiB2YWx1ZSA9PT0gbGlzdGVuZXJzID8gYnJ1c2ggOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIHJldHVybiBicnVzaDsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2NlbmRpbmckNihhLCBiKSB7CiAgICAgIHJldHVybiBhIDwgYiA/IC0xIDogYSA+IGIgPyAxIDogYSA+PSBiID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBiaXNlY3RvciQyKGNvbXBhcmUpIHsKICAgICAgaWYgKGNvbXBhcmUubGVuZ3RoID09PSAxKSBjb21wYXJlID0gYXNjZW5kaW5nQ29tcGFyYXRvciQyKGNvbXBhcmUpOwogICAgICByZXR1cm4gewogICAgICAgIGxlZnQ6IGZ1bmN0aW9uKGEsIHgsIGxvLCBoaSkgewogICAgICAgICAgaWYgKGxvID09IG51bGwpIGxvID0gMDsKICAgICAgICAgIGlmIChoaSA9PSBudWxsKSBoaSA9IGEubGVuZ3RoOwogICAgICAgICAgd2hpbGUgKGxvIDwgaGkpIHsKICAgICAgICAgICAgdmFyIG1pZCA9IGxvICsgaGkgPj4+IDE7CiAgICAgICAgICAgIGlmIChjb21wYXJlKGFbbWlkXSwgeCkgPCAwKSBsbyA9IG1pZCArIDE7CiAgICAgICAgICAgIGVsc2UgaGkgPSBtaWQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbG87CiAgICAgICAgfSwKICAgICAgICByaWdodDogZnVuY3Rpb24oYSwgeCwgbG8sIGhpKSB7CiAgICAgICAgICBpZiAobG8gPT0gbnVsbCkgbG8gPSAwOwogICAgICAgICAgaWYgKGhpID09IG51bGwpIGhpID0gYS5sZW5ndGg7CiAgICAgICAgICB3aGlsZSAobG8gPCBoaSkgewogICAgICAgICAgICB2YXIgbWlkID0gbG8gKyBoaSA+Pj4gMTsKICAgICAgICAgICAgaWYgKGNvbXBhcmUoYVttaWRdLCB4KSA+IDApIGhpID0gbWlkOwogICAgICAgICAgICBlbHNlIGxvID0gbWlkICsgMTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBsbzsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nQ29tcGFyYXRvciQyKGYpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQsIHgpIHsKICAgICAgICByZXR1cm4gYXNjZW5kaW5nJDYoZihkKSwgeCk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGFzY2VuZGluZ0Jpc2VjdCQyID0gYmlzZWN0b3IkMihhc2NlbmRpbmckNik7CgogICAgZnVuY3Rpb24gcmFuZ2UkMihzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICBzdGFydCA9ICtzdGFydCwgc3RvcCA9ICtzdG9wLCBzdGVwID0gKG4gPSBhcmd1bWVudHMubGVuZ3RoKSA8IDIgPyAoc3RvcCA9IHN0YXJ0LCBzdGFydCA9IDAsIDEpIDogbiA8IDMgPyAxIDogK3N0ZXA7CgogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IE1hdGgubWF4KDAsIE1hdGguY2VpbCgoc3RvcCAtIHN0YXJ0KSAvIHN0ZXApKSB8IDAsCiAgICAgICAgICByYW5nZSA9IG5ldyBBcnJheShuKTsKCiAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgcmFuZ2VbaV0gPSBzdGFydCArIGkgKiBzdGVwOwogICAgICB9CgogICAgICByZXR1cm4gcmFuZ2U7CiAgICB9CgogICAgdmFyIGNvcyQzID0gTWF0aC5jb3M7CiAgICB2YXIgc2luJDMgPSBNYXRoLnNpbjsKICAgIHZhciBwaSQ1ID0gTWF0aC5QSTsKICAgIHZhciBoYWxmUGkkNCA9IHBpJDUgLyAyOwogICAgdmFyIHRhdSQ1ID0gcGkkNSAqIDI7CiAgICB2YXIgbWF4JDQgPSBNYXRoLm1heDsKCiAgICBmdW5jdGlvbiBjb21wYXJlVmFsdWUkMShjb21wYXJlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgcmV0dXJuIGNvbXBhcmUoCiAgICAgICAgICBhLnNvdXJjZS52YWx1ZSArIGEudGFyZ2V0LnZhbHVlLAogICAgICAgICAgYi5zb3VyY2UudmFsdWUgKyBiLnRhcmdldC52YWx1ZQogICAgICAgICk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2hvcmQkMSgpIHsKICAgICAgdmFyIHBhZEFuZ2xlID0gMCwKICAgICAgICAgIHNvcnRHcm91cHMgPSBudWxsLAogICAgICAgICAgc29ydFN1Ymdyb3VwcyA9IG51bGwsCiAgICAgICAgICBzb3J0Q2hvcmRzID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIGNob3JkKG1hdHJpeCkgewogICAgICAgIHZhciBuID0gbWF0cml4Lmxlbmd0aCwKICAgICAgICAgICAgZ3JvdXBTdW1zID0gW10sCiAgICAgICAgICAgIGdyb3VwSW5kZXggPSByYW5nZSQyKG4pLAogICAgICAgICAgICBzdWJncm91cEluZGV4ID0gW10sCiAgICAgICAgICAgIGNob3JkcyA9IFtdLAogICAgICAgICAgICBncm91cHMgPSBjaG9yZHMuZ3JvdXBzID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICBzdWJncm91cHMgPSBuZXcgQXJyYXkobiAqIG4pLAogICAgICAgICAgICBrLAogICAgICAgICAgICB4LAogICAgICAgICAgICB4MCwKICAgICAgICAgICAgZHgsCiAgICAgICAgICAgIGksCiAgICAgICAgICAgIGo7CgogICAgICAgIC8vIENvbXB1dGUgdGhlIHN1bS4KICAgICAgICBrID0gMCwgaSA9IC0xOyB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgeCA9IDAsIGogPSAtMTsgd2hpbGUgKCsraiA8IG4pIHsKICAgICAgICAgICAgeCArPSBtYXRyaXhbaV1bal07CiAgICAgICAgICB9CiAgICAgICAgICBncm91cFN1bXMucHVzaCh4KTsKICAgICAgICAgIHN1Ymdyb3VwSW5kZXgucHVzaChyYW5nZSQyKG4pKTsKICAgICAgICAgIGsgKz0geDsKICAgICAgICB9CgogICAgICAgIC8vIFNvcnQgZ3JvdXBz4oCmCiAgICAgICAgaWYgKHNvcnRHcm91cHMpIGdyb3VwSW5kZXguc29ydChmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgICByZXR1cm4gc29ydEdyb3Vwcyhncm91cFN1bXNbYV0sIGdyb3VwU3Vtc1tiXSk7CiAgICAgICAgfSk7CgogICAgICAgIC8vIFNvcnQgc3ViZ3JvdXBz4oCmCiAgICAgICAgaWYgKHNvcnRTdWJncm91cHMpIHN1Ymdyb3VwSW5kZXguZm9yRWFjaChmdW5jdGlvbihkLCBpKSB7CiAgICAgICAgICBkLnNvcnQoZnVuY3Rpb24oYSwgYikgewogICAgICAgICAgICByZXR1cm4gc29ydFN1Ymdyb3VwcyhtYXRyaXhbaV1bYV0sIG1hdHJpeFtpXVtiXSk7CiAgICAgICAgICB9KTsKICAgICAgICB9KTsKCiAgICAgICAgLy8gQ29udmVydCB0aGUgc3VtIHRvIHNjYWxpbmcgZmFjdG9yIGZvciBbMCwgMnBpXS4KICAgICAgICAvLyBUT0RPIEFsbG93IHN0YXJ0IGFuZCBlbmQgYW5nbGUgdG8gYmUgc3BlY2lmaWVkPwogICAgICAgIC8vIFRPRE8gQWxsb3cgcGFkZGluZyB0byBiZSBzcGVjaWZpZWQgYXMgcGVyY2VudGFnZT8KICAgICAgICBrID0gbWF4JDQoMCwgdGF1JDUgLSBwYWRBbmdsZSAqIG4pIC8gazsKICAgICAgICBkeCA9IGsgPyBwYWRBbmdsZSA6IHRhdSQ1IC8gbjsKCiAgICAgICAgLy8gQ29tcHV0ZSB0aGUgc3RhcnQgYW5kIGVuZCBhbmdsZSBmb3IgZWFjaCBncm91cCBhbmQgc3ViZ3JvdXAuCiAgICAgICAgLy8gTm90ZTogT3BlcmEgaGFzIGEgYnVnIHJlb3JkZXJpbmcgb2JqZWN0IGxpdGVyYWwgcHJvcGVydGllcyEKICAgICAgICB4ID0gMCwgaSA9IC0xOyB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgeDAgPSB4LCBqID0gLTE7IHdoaWxlICgrK2ogPCBuKSB7CiAgICAgICAgICAgIHZhciBkaSA9IGdyb3VwSW5kZXhbaV0sCiAgICAgICAgICAgICAgICBkaiA9IHN1Ymdyb3VwSW5kZXhbZGldW2pdLAogICAgICAgICAgICAgICAgdiA9IG1hdHJpeFtkaV1bZGpdLAogICAgICAgICAgICAgICAgYTAgPSB4LAogICAgICAgICAgICAgICAgYTEgPSB4ICs9IHYgKiBrOwogICAgICAgICAgICBzdWJncm91cHNbZGogKiBuICsgZGldID0gewogICAgICAgICAgICAgIGluZGV4OiBkaSwKICAgICAgICAgICAgICBzdWJpbmRleDogZGosCiAgICAgICAgICAgICAgc3RhcnRBbmdsZTogYTAsCiAgICAgICAgICAgICAgZW5kQW5nbGU6IGExLAogICAgICAgICAgICAgIHZhbHVlOiB2CiAgICAgICAgICAgIH07CiAgICAgICAgICB9CiAgICAgICAgICBncm91cHNbZGldID0gewogICAgICAgICAgICBpbmRleDogZGksCiAgICAgICAgICAgIHN0YXJ0QW5nbGU6IHgwLAogICAgICAgICAgICBlbmRBbmdsZTogeCwKICAgICAgICAgICAgdmFsdWU6IGdyb3VwU3Vtc1tkaV0KICAgICAgICAgIH07CiAgICAgICAgICB4ICs9IGR4OwogICAgICAgIH0KCiAgICAgICAgLy8gR2VuZXJhdGUgY2hvcmRzIGZvciBlYWNoIChub24tZW1wdHkpIHN1Ymdyb3VwLXN1Ymdyb3VwIGxpbmsuCiAgICAgICAgaSA9IC0xOyB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaiA9IGkgLSAxOyB3aGlsZSAoKytqIDwgbikgewogICAgICAgICAgICB2YXIgc291cmNlID0gc3ViZ3JvdXBzW2ogKiBuICsgaV0sCiAgICAgICAgICAgICAgICB0YXJnZXQgPSBzdWJncm91cHNbaSAqIG4gKyBqXTsKICAgICAgICAgICAgaWYgKHNvdXJjZS52YWx1ZSB8fCB0YXJnZXQudmFsdWUpIHsKICAgICAgICAgICAgICBjaG9yZHMucHVzaChzb3VyY2UudmFsdWUgPCB0YXJnZXQudmFsdWUKICAgICAgICAgICAgICAgICAgPyB7c291cmNlOiB0YXJnZXQsIHRhcmdldDogc291cmNlfQogICAgICAgICAgICAgICAgICA6IHtzb3VyY2U6IHNvdXJjZSwgdGFyZ2V0OiB0YXJnZXR9KTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHNvcnRDaG9yZHMgPyBjaG9yZHMuc29ydChzb3J0Q2hvcmRzKSA6IGNob3JkczsKICAgICAgfQoKICAgICAgY2hvcmQucGFkQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkQW5nbGUgPSBtYXgkNCgwLCBfKSwgY2hvcmQpIDogcGFkQW5nbGU7CiAgICAgIH07CgogICAgICBjaG9yZC5zb3J0R3JvdXBzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNvcnRHcm91cHMgPSBfLCBjaG9yZCkgOiBzb3J0R3JvdXBzOwogICAgICB9OwoKICAgICAgY2hvcmQuc29ydFN1Ymdyb3VwcyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzb3J0U3ViZ3JvdXBzID0gXywgY2hvcmQpIDogc29ydFN1Ymdyb3VwczsKICAgICAgfTsKCiAgICAgIGNob3JkLnNvcnRDaG9yZHMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoXyA9PSBudWxsID8gc29ydENob3JkcyA9IG51bGwgOiAoc29ydENob3JkcyA9IGNvbXBhcmVWYWx1ZSQxKF8pKS5fID0gXywgY2hvcmQpIDogc29ydENob3JkcyAmJiBzb3J0Q2hvcmRzLl87CiAgICAgIH07CgogICAgICByZXR1cm4gY2hvcmQ7CiAgICB9CgogICAgdmFyIHNsaWNlJDkgPSBBcnJheS5wcm90b3R5cGUuc2xpY2U7CgogICAgZnVuY3Rpb24gY29uc3RhbnQkaSh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcGkkNiA9IE1hdGguUEksCiAgICAgICAgdGF1JDYgPSAyICogcGkkNiwKICAgICAgICBlcHNpbG9uJDYgPSAxZS02LAogICAgICAgIHRhdUVwc2lsb24kMSA9IHRhdSQ2IC0gZXBzaWxvbiQ2OwoKICAgIGZ1bmN0aW9uIFBhdGgkMSgpIHsKICAgICAgdGhpcy5feDAgPSB0aGlzLl95MCA9IC8vIHN0YXJ0IG9mIGN1cnJlbnQgc3VicGF0aAogICAgICB0aGlzLl94MSA9IHRoaXMuX3kxID0gbnVsbDsgLy8gZW5kIG9mIGN1cnJlbnQgc3VicGF0aAogICAgICB0aGlzLl8gPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXRoJDEoKSB7CiAgICAgIHJldHVybiBuZXcgUGF0aCQxOwogICAgfQoKICAgIFBhdGgkMS5wcm90b3R5cGUgPSBwYXRoJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogUGF0aCQxLAogICAgICBtb3ZlVG86IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB0aGlzLl8gKz0gIk0iICsgKHRoaXMuX3gwID0gdGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTAgPSB0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgY2xvc2VQYXRoOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5feDEgIT09IG51bGwpIHsKICAgICAgICAgIHRoaXMuX3gxID0gdGhpcy5feDAsIHRoaXMuX3kxID0gdGhpcy5feTA7CiAgICAgICAgICB0aGlzLl8gKz0gIloiOwogICAgICAgIH0KICAgICAgfSwKICAgICAgbGluZVRvOiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJMIiArICh0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgcXVhZHJhdGljQ3VydmVUbzogZnVuY3Rpb24oeDEsIHkxLCB4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJRIiArICgreDEpICsgIiwiICsgKCt5MSkgKyAiLCIgKyAodGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTEgPSAreSk7CiAgICAgIH0sCiAgICAgIGJlemllckN1cnZlVG86IGZ1bmN0aW9uKHgxLCB5MSwgeDIsIHkyLCB4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJDIiArICgreDEpICsgIiwiICsgKCt5MSkgKyAiLCIgKyAoK3gyKSArICIsIiArICgreTIpICsgIiwiICsgKHRoaXMuX3gxID0gK3gpICsgIiwiICsgKHRoaXMuX3kxID0gK3kpOwogICAgICB9LAogICAgICBhcmNUbzogZnVuY3Rpb24oeDEsIHkxLCB4MiwgeTIsIHIpIHsKICAgICAgICB4MSA9ICt4MSwgeTEgPSAreTEsIHgyID0gK3gyLCB5MiA9ICt5MiwgciA9ICtyOwogICAgICAgIHZhciB4MCA9IHRoaXMuX3gxLAogICAgICAgICAgICB5MCA9IHRoaXMuX3kxLAogICAgICAgICAgICB4MjEgPSB4MiAtIHgxLAogICAgICAgICAgICB5MjEgPSB5MiAtIHkxLAogICAgICAgICAgICB4MDEgPSB4MCAtIHgxLAogICAgICAgICAgICB5MDEgPSB5MCAtIHkxLAogICAgICAgICAgICBsMDFfMiA9IHgwMSAqIHgwMSArIHkwMSAqIHkwMTsKCiAgICAgICAgLy8gSXMgdGhlIHJhZGl1cyBuZWdhdGl2ZT8gRXJyb3IuCiAgICAgICAgaWYgKHIgPCAwKSB0aHJvdyBuZXcgRXJyb3IoIm5lZ2F0aXZlIHJhZGl1czogIiArIHIpOwoKICAgICAgICAvLyBJcyB0aGlzIHBhdGggZW1wdHk/IE1vdmUgdG8gKHgxLHkxKS4KICAgICAgICBpZiAodGhpcy5feDEgPT09IG51bGwpIHsKICAgICAgICAgIHRoaXMuXyArPSAiTSIgKyAodGhpcy5feDEgPSB4MSkgKyAiLCIgKyAodGhpcy5feTEgPSB5MSk7CiAgICAgICAgfQoKICAgICAgICAvLyBPciwgaXMgKHgxLHkxKSBjb2luY2lkZW50IHdpdGggKHgwLHkwKT8gRG8gbm90aGluZy4KICAgICAgICBlbHNlIGlmICghKGwwMV8yID4gZXBzaWxvbiQ2KSk7CgogICAgICAgIC8vIE9yLCBhcmUgKHgwLHkwKSwgKHgxLHkxKSBhbmQgKHgyLHkyKSBjb2xsaW5lYXI/CiAgICAgICAgLy8gRXF1aXZhbGVudGx5LCBpcyAoeDEseTEpIGNvaW5jaWRlbnQgd2l0aCAoeDIseTIpPwogICAgICAgIC8vIE9yLCBpcyB0aGUgcmFkaXVzIHplcm8/IExpbmUgdG8gKHgxLHkxKS4KICAgICAgICBlbHNlIGlmICghKE1hdGguYWJzKHkwMSAqIHgyMSAtIHkyMSAqIHgwMSkgPiBlcHNpbG9uJDYpIHx8ICFyKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkwiICsgKHRoaXMuX3gxID0geDEpICsgIiwiICsgKHRoaXMuX3kxID0geTEpOwogICAgICAgIH0KCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IGFuIGFyYyEKICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciB4MjAgPSB4MiAtIHgwLAogICAgICAgICAgICAgIHkyMCA9IHkyIC0geTAsCiAgICAgICAgICAgICAgbDIxXzIgPSB4MjEgKiB4MjEgKyB5MjEgKiB5MjEsCiAgICAgICAgICAgICAgbDIwXzIgPSB4MjAgKiB4MjAgKyB5MjAgKiB5MjAsCiAgICAgICAgICAgICAgbDIxID0gTWF0aC5zcXJ0KGwyMV8yKSwKICAgICAgICAgICAgICBsMDEgPSBNYXRoLnNxcnQobDAxXzIpLAogICAgICAgICAgICAgIGwgPSByICogTWF0aC50YW4oKHBpJDYgLSBNYXRoLmFjb3MoKGwyMV8yICsgbDAxXzIgLSBsMjBfMikgLyAoMiAqIGwyMSAqIGwwMSkpKSAvIDIpLAogICAgICAgICAgICAgIHQwMSA9IGwgLyBsMDEsCiAgICAgICAgICAgICAgdDIxID0gbCAvIGwyMTsKCiAgICAgICAgICAvLyBJZiB0aGUgc3RhcnQgdGFuZ2VudCBpcyBub3QgY29pbmNpZGVudCB3aXRoICh4MCx5MCksIGxpbmUgdG8uCiAgICAgICAgICBpZiAoTWF0aC5hYnModDAxIC0gMSkgPiBlcHNpbG9uJDYpIHsKICAgICAgICAgICAgdGhpcy5fICs9ICJMIiArICh4MSArIHQwMSAqIHgwMSkgKyAiLCIgKyAoeTEgKyB0MDEgKiB5MDEpOwogICAgICAgICAgfQoKICAgICAgICAgIHRoaXMuXyArPSAiQSIgKyByICsgIiwiICsgciArICIsMCwwLCIgKyAoKyh5MDEgKiB4MjAgPiB4MDEgKiB5MjApKSArICIsIiArICh0aGlzLl94MSA9IHgxICsgdDIxICogeDIxKSArICIsIiArICh0aGlzLl95MSA9IHkxICsgdDIxICogeTIxKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGFyYzogZnVuY3Rpb24oeCwgeSwgciwgYTAsIGExLCBjY3cpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreSwgciA9ICtyLCBjY3cgPSAhIWNjdzsKICAgICAgICB2YXIgZHggPSByICogTWF0aC5jb3MoYTApLAogICAgICAgICAgICBkeSA9IHIgKiBNYXRoLnNpbihhMCksCiAgICAgICAgICAgIHgwID0geCArIGR4LAogICAgICAgICAgICB5MCA9IHkgKyBkeSwKICAgICAgICAgICAgY3cgPSAxIF4gY2N3LAogICAgICAgICAgICBkYSA9IGNjdyA/IGEwIC0gYTEgOiBhMSAtIGEwOwoKICAgICAgICAvLyBJcyB0aGUgcmFkaXVzIG5lZ2F0aXZlPyBFcnJvci4KICAgICAgICBpZiAociA8IDApIHRocm93IG5ldyBFcnJvcigibmVnYXRpdmUgcmFkaXVzOiAiICsgcik7CgogICAgICAgIC8vIElzIHRoaXMgcGF0aCBlbXB0eT8gTW92ZSB0byAoeDAseTApLgogICAgICAgIGlmICh0aGlzLl94MSA9PT0gbnVsbCkgewogICAgICAgICAgdGhpcy5fICs9ICJNIiArIHgwICsgIiwiICsgeTA7CiAgICAgICAgfQoKICAgICAgICAvLyBPciwgaXMgKHgwLHkwKSBub3QgY29pbmNpZGVudCB3aXRoIHRoZSBwcmV2aW91cyBwb2ludD8gTGluZSB0byAoeDAseTApLgogICAgICAgIGVsc2UgaWYgKE1hdGguYWJzKHRoaXMuX3gxIC0geDApID4gZXBzaWxvbiQ2IHx8IE1hdGguYWJzKHRoaXMuX3kxIC0geTApID4gZXBzaWxvbiQ2KSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkwiICsgeDAgKyAiLCIgKyB5MDsKICAgICAgICB9CgogICAgICAgIC8vIElzIHRoaXMgYXJjIGVtcHR5PyBXZeKAmXJlIGRvbmUuCiAgICAgICAgaWYgKCFyKSByZXR1cm47CgogICAgICAgIC8vIERvZXMgdGhlIGFuZ2xlIGdvIHRoZSB3cm9uZyB3YXk/IEZsaXAgdGhlIGRpcmVjdGlvbi4KICAgICAgICBpZiAoZGEgPCAwKSBkYSA9IGRhICUgdGF1JDYgKyB0YXUkNjsKCiAgICAgICAgLy8gSXMgdGhpcyBhIGNvbXBsZXRlIGNpcmNsZT8gRHJhdyB0d28gYXJjcyB0byBjb21wbGV0ZSB0aGUgY2lyY2xlLgogICAgICAgIGlmIChkYSA+IHRhdUVwc2lsb24kMSkgewogICAgICAgICAgdGhpcy5fICs9ICJBIiArIHIgKyAiLCIgKyByICsgIiwwLDEsIiArIGN3ICsgIiwiICsgKHggLSBkeCkgKyAiLCIgKyAoeSAtIGR5KSArICJBIiArIHIgKyAiLCIgKyByICsgIiwwLDEsIiArIGN3ICsgIiwiICsgKHRoaXMuX3gxID0geDApICsgIiwiICsgKHRoaXMuX3kxID0geTApOwogICAgICAgIH0KCiAgICAgICAgLy8gSXMgdGhpcyBhcmMgbm9uLWVtcHR5PyBEcmF3IGFuIGFyYyEKICAgICAgICBlbHNlIGlmIChkYSA+IGVwc2lsb24kNikgewogICAgICAgICAgdGhpcy5fICs9ICJBIiArIHIgKyAiLCIgKyByICsgIiwwLCIgKyAoKyhkYSA+PSBwaSQ2KSkgKyAiLCIgKyBjdyArICIsIiArICh0aGlzLl94MSA9IHggKyByICogTWF0aC5jb3MoYTEpKSArICIsIiArICh0aGlzLl95MSA9IHkgKyByICogTWF0aC5zaW4oYTEpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIHJlY3Q6IGZ1bmN0aW9uKHgsIHksIHcsIGgpIHsKICAgICAgICB0aGlzLl8gKz0gIk0iICsgKHRoaXMuX3gwID0gdGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTAgPSB0aGlzLl95MSA9ICt5KSArICJoIiArICgrdykgKyAidiIgKyAoK2gpICsgImgiICsgKC13KSArICJaIjsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl87CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gZGVmYXVsdFNvdXJjZSQyKGQpIHsKICAgICAgcmV0dXJuIGQuc291cmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRUYXJnZXQkMShkKSB7CiAgICAgIHJldHVybiBkLnRhcmdldDsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0UmFkaXVzJDIoZCkgewogICAgICByZXR1cm4gZC5yYWRpdXM7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFN0YXJ0QW5nbGUkMShkKSB7CiAgICAgIHJldHVybiBkLnN0YXJ0QW5nbGU7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdEVuZEFuZ2xlJDEoZCkgewogICAgICByZXR1cm4gZC5lbmRBbmdsZTsKICAgIH0KCiAgICBmdW5jdGlvbiByaWJib24kMSgpIHsKICAgICAgdmFyIHNvdXJjZSA9IGRlZmF1bHRTb3VyY2UkMiwKICAgICAgICAgIHRhcmdldCA9IGRlZmF1bHRUYXJnZXQkMSwKICAgICAgICAgIHJhZGl1cyA9IGRlZmF1bHRSYWRpdXMkMiwKICAgICAgICAgIHN0YXJ0QW5nbGUgPSBkZWZhdWx0U3RhcnRBbmdsZSQxLAogICAgICAgICAgZW5kQW5nbGUgPSBkZWZhdWx0RW5kQW5nbGUkMSwKICAgICAgICAgIGNvbnRleHQgPSBudWxsOwoKICAgICAgZnVuY3Rpb24gcmliYm9uKCkgewogICAgICAgIHZhciBidWZmZXIsCiAgICAgICAgICAgIGFyZ3YgPSBzbGljZSQ5LmNhbGwoYXJndW1lbnRzKSwKICAgICAgICAgICAgcyA9IHNvdXJjZS5hcHBseSh0aGlzLCBhcmd2KSwKICAgICAgICAgICAgdCA9IHRhcmdldC5hcHBseSh0aGlzLCBhcmd2KSwKICAgICAgICAgICAgc3IgPSArcmFkaXVzLmFwcGx5KHRoaXMsIChhcmd2WzBdID0gcywgYXJndikpLAogICAgICAgICAgICBzYTAgPSBzdGFydEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3YpIC0gaGFsZlBpJDQsCiAgICAgICAgICAgIHNhMSA9IGVuZEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3YpIC0gaGFsZlBpJDQsCiAgICAgICAgICAgIHN4MCA9IHNyICogY29zJDMoc2EwKSwKICAgICAgICAgICAgc3kwID0gc3IgKiBzaW4kMyhzYTApLAogICAgICAgICAgICB0ciA9ICtyYWRpdXMuYXBwbHkodGhpcywgKGFyZ3ZbMF0gPSB0LCBhcmd2KSksCiAgICAgICAgICAgIHRhMCA9IHN0YXJ0QW5nbGUuYXBwbHkodGhpcywgYXJndikgLSBoYWxmUGkkNCwKICAgICAgICAgICAgdGExID0gZW5kQW5nbGUuYXBwbHkodGhpcywgYXJndikgLSBoYWxmUGkkNDsKCiAgICAgICAgaWYgKCFjb250ZXh0KSBjb250ZXh0ID0gYnVmZmVyID0gcGF0aCQxKCk7CgogICAgICAgIGNvbnRleHQubW92ZVRvKHN4MCwgc3kwKTsKICAgICAgICBjb250ZXh0LmFyYygwLCAwLCBzciwgc2EwLCBzYTEpOwogICAgICAgIGlmIChzYTAgIT09IHRhMCB8fCBzYTEgIT09IHRhMSkgeyAvLyBUT0RPIHNyICE9PSB0cj8KICAgICAgICAgIGNvbnRleHQucXVhZHJhdGljQ3VydmVUbygwLCAwLCB0ciAqIGNvcyQzKHRhMCksIHRyICogc2luJDModGEwKSk7CiAgICAgICAgICBjb250ZXh0LmFyYygwLCAwLCB0ciwgdGEwLCB0YTEpOwogICAgICAgIH0KICAgICAgICBjb250ZXh0LnF1YWRyYXRpY0N1cnZlVG8oMCwgMCwgc3gwLCBzeTApOwogICAgICAgIGNvbnRleHQuY2xvc2VQYXRoKCk7CgogICAgICAgIGlmIChidWZmZXIpIHJldHVybiBjb250ZXh0ID0gbnVsbCwgYnVmZmVyICsgIiIgfHwgbnVsbDsKICAgICAgfQoKICAgICAgcmliYm9uLnJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRpKCtfKSwgcmliYm9uKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIHJpYmJvbi5zdGFydEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN0YXJ0QW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRpKCtfKSwgcmliYm9uKSA6IHN0YXJ0QW5nbGU7CiAgICAgIH07CgogICAgICByaWJib24uZW5kQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZW5kQW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRpKCtfKSwgcmliYm9uKSA6IGVuZEFuZ2xlOwogICAgICB9OwoKICAgICAgcmliYm9uLnNvdXJjZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzb3VyY2UgPSBfLCByaWJib24pIDogc291cmNlOwogICAgICB9OwoKICAgICAgcmliYm9uLnRhcmdldCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0YXJnZXQgPSBfLCByaWJib24pIDogdGFyZ2V0OwogICAgICB9OwoKICAgICAgcmliYm9uLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoKGNvbnRleHQgPSBfID09IG51bGwgPyBudWxsIDogXyksIHJpYmJvbikgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIHJpYmJvbjsKICAgIH0KCiAgICB2YXIgcHJlZml4JDEgPSAiJCI7CgogICAgZnVuY3Rpb24gTWFwJDIoKSB7fQoKICAgIE1hcCQyLnByb3RvdHlwZSA9IG1hcCQ1LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IE1hcCQyLAogICAgICBoYXM6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHJldHVybiAocHJlZml4JDEgKyBrZXkpIGluIHRoaXM7CiAgICAgIH0sCiAgICAgIGdldDogZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgcmV0dXJuIHRoaXNbcHJlZml4JDEgKyBrZXldOwogICAgICB9LAogICAgICBzZXQ6IGZ1bmN0aW9uKGtleSwgdmFsdWUpIHsKICAgICAgICB0aGlzW3ByZWZpeCQxICsga2V5XSA9IHZhbHVlOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICByZW1vdmU6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHZhciBwcm9wZXJ0eSA9IHByZWZpeCQxICsga2V5OwogICAgICAgIHJldHVybiBwcm9wZXJ0eSBpbiB0aGlzICYmIGRlbGV0ZSB0aGlzW3Byb3BlcnR5XTsKICAgICAgfSwKICAgICAgY2xlYXI6IGZ1bmN0aW9uKCkgewogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4JDEpIGRlbGV0ZSB0aGlzW3Byb3BlcnR5XTsKICAgICAgfSwKICAgICAga2V5czogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGtleXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQxKSBrZXlzLnB1c2gocHJvcGVydHkuc2xpY2UoMSkpOwogICAgICAgIHJldHVybiBrZXlzOwogICAgICB9LAogICAgICB2YWx1ZXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQxKSB2YWx1ZXMucHVzaCh0aGlzW3Byb3BlcnR5XSk7CiAgICAgICAgcmV0dXJuIHZhbHVlczsKICAgICAgfSwKICAgICAgZW50cmllczogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGVudHJpZXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQxKSBlbnRyaWVzLnB1c2goe2tleTogcHJvcGVydHkuc2xpY2UoMSksIHZhbHVlOiB0aGlzW3Byb3BlcnR5XX0pOwogICAgICAgIHJldHVybiBlbnRyaWVzOwogICAgICB9LAogICAgICBzaXplOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMSkgKytzaXplOwogICAgICAgIHJldHVybiBzaXplOwogICAgICB9LAogICAgICBlbXB0eTogZnVuY3Rpb24oKSB7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMSkgcmV0dXJuIGZhbHNlOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9LAogICAgICBlYWNoOiBmdW5jdGlvbihmKSB7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMSkgZih0aGlzW3Byb3BlcnR5XSwgcHJvcGVydHkuc2xpY2UoMSksIHRoaXMpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIG1hcCQ1KG9iamVjdCwgZikgewogICAgICB2YXIgbWFwID0gbmV3IE1hcCQyOwoKICAgICAgLy8gQ29weSBjb25zdHJ1Y3Rvci4KICAgICAgaWYgKG9iamVjdCBpbnN0YW5jZW9mIE1hcCQyKSBvYmplY3QuZWFjaChmdW5jdGlvbih2YWx1ZSwga2V5KSB7IG1hcC5zZXQoa2V5LCB2YWx1ZSk7IH0pOwoKICAgICAgLy8gSW5kZXggYXJyYXkgYnkgbnVtZXJpYyBpbmRleCBvciBzcGVjaWZpZWQga2V5IGZ1bmN0aW9uLgogICAgICBlbHNlIGlmIChBcnJheS5pc0FycmF5KG9iamVjdCkpIHsKICAgICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgICBuID0gb2JqZWN0Lmxlbmd0aCwKICAgICAgICAgICAgbzsKCiAgICAgICAgaWYgKGYgPT0gbnVsbCkgd2hpbGUgKCsraSA8IG4pIG1hcC5zZXQoaSwgb2JqZWN0W2ldKTsKICAgICAgICBlbHNlIHdoaWxlICgrK2kgPCBuKSBtYXAuc2V0KGYobyA9IG9iamVjdFtpXSwgaSwgb2JqZWN0KSwgbyk7CiAgICAgIH0KCiAgICAgIC8vIENvbnZlcnQgb2JqZWN0IHRvIG1hcC4KICAgICAgZWxzZSBpZiAob2JqZWN0KSBmb3IgKHZhciBrZXkgaW4gb2JqZWN0KSBtYXAuc2V0KGtleSwgb2JqZWN0W2tleV0pOwoKICAgICAgcmV0dXJuIG1hcDsKICAgIH0KCiAgICBmdW5jdGlvbiBuZXN0JDEoKSB7CiAgICAgIHZhciBrZXlzID0gW10sCiAgICAgICAgICBzb3J0S2V5cyA9IFtdLAogICAgICAgICAgc29ydFZhbHVlcywKICAgICAgICAgIHJvbGx1cCwKICAgICAgICAgIG5lc3Q7CgogICAgICBmdW5jdGlvbiBhcHBseShhcnJheSwgZGVwdGgsIGNyZWF0ZVJlc3VsdCwgc2V0UmVzdWx0KSB7CiAgICAgICAgaWYgKGRlcHRoID49IGtleXMubGVuZ3RoKSB7CiAgICAgICAgICBpZiAoc29ydFZhbHVlcyAhPSBudWxsKSBhcnJheS5zb3J0KHNvcnRWYWx1ZXMpOwogICAgICAgICAgcmV0dXJuIHJvbGx1cCAhPSBudWxsID8gcm9sbHVwKGFycmF5KSA6IGFycmF5OwogICAgICAgIH0KCiAgICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgICAgbiA9IGFycmF5Lmxlbmd0aCwKICAgICAgICAgICAga2V5ID0ga2V5c1tkZXB0aCsrXSwKICAgICAgICAgICAga2V5VmFsdWUsCiAgICAgICAgICAgIHZhbHVlLAogICAgICAgICAgICB2YWx1ZXNCeUtleSA9IG1hcCQ1KCksCiAgICAgICAgICAgIHZhbHVlcywKICAgICAgICAgICAgcmVzdWx0ID0gY3JlYXRlUmVzdWx0KCk7CgogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAodmFsdWVzID0gdmFsdWVzQnlLZXkuZ2V0KGtleVZhbHVlID0ga2V5KHZhbHVlID0gYXJyYXlbaV0pICsgIiIpKSB7CiAgICAgICAgICAgIHZhbHVlcy5wdXNoKHZhbHVlKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHZhbHVlc0J5S2V5LnNldChrZXlWYWx1ZSwgW3ZhbHVlXSk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICB2YWx1ZXNCeUtleS5lYWNoKGZ1bmN0aW9uKHZhbHVlcywga2V5KSB7CiAgICAgICAgICBzZXRSZXN1bHQocmVzdWx0LCBrZXksIGFwcGx5KHZhbHVlcywgZGVwdGgsIGNyZWF0ZVJlc3VsdCwgc2V0UmVzdWx0KSk7CiAgICAgICAgfSk7CgogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGVudHJpZXMobWFwLCBkZXB0aCkgewogICAgICAgIGlmICgrK2RlcHRoID4ga2V5cy5sZW5ndGgpIHJldHVybiBtYXA7CiAgICAgICAgdmFyIGFycmF5LCBzb3J0S2V5ID0gc29ydEtleXNbZGVwdGggLSAxXTsKICAgICAgICBpZiAocm9sbHVwICE9IG51bGwgJiYgZGVwdGggPj0ga2V5cy5sZW5ndGgpIGFycmF5ID0gbWFwLmVudHJpZXMoKTsKICAgICAgICBlbHNlIGFycmF5ID0gW10sIG1hcC5lYWNoKGZ1bmN0aW9uKHYsIGspIHsgYXJyYXkucHVzaCh7a2V5OiBrLCB2YWx1ZXM6IGVudHJpZXModiwgZGVwdGgpfSk7IH0pOwogICAgICAgIHJldHVybiBzb3J0S2V5ICE9IG51bGwgPyBhcnJheS5zb3J0KGZ1bmN0aW9uKGEsIGIpIHsgcmV0dXJuIHNvcnRLZXkoYS5rZXksIGIua2V5KTsgfSkgOiBhcnJheTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5lc3QgPSB7CiAgICAgICAgb2JqZWN0OiBmdW5jdGlvbihhcnJheSkgeyByZXR1cm4gYXBwbHkoYXJyYXksIDAsIGNyZWF0ZU9iamVjdCQxLCBzZXRPYmplY3QkMik7IH0sCiAgICAgICAgbWFwOiBmdW5jdGlvbihhcnJheSkgeyByZXR1cm4gYXBwbHkoYXJyYXksIDAsIGNyZWF0ZU1hcCQxLCBzZXRNYXAkMSk7IH0sCiAgICAgICAgZW50cmllczogZnVuY3Rpb24oYXJyYXkpIHsgcmV0dXJuIGVudHJpZXMoYXBwbHkoYXJyYXksIDAsIGNyZWF0ZU1hcCQxLCBzZXRNYXAkMSksIDApOyB9LAogICAgICAgIGtleTogZnVuY3Rpb24oZCkgeyBrZXlzLnB1c2goZCk7IHJldHVybiBuZXN0OyB9LAogICAgICAgIHNvcnRLZXlzOiBmdW5jdGlvbihvcmRlcikgeyBzb3J0S2V5c1trZXlzLmxlbmd0aCAtIDFdID0gb3JkZXI7IHJldHVybiBuZXN0OyB9LAogICAgICAgIHNvcnRWYWx1ZXM6IGZ1bmN0aW9uKG9yZGVyKSB7IHNvcnRWYWx1ZXMgPSBvcmRlcjsgcmV0dXJuIG5lc3Q7IH0sCiAgICAgICAgcm9sbHVwOiBmdW5jdGlvbihmKSB7IHJvbGx1cCA9IGY7IHJldHVybiBuZXN0OyB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlT2JqZWN0JDEoKSB7CiAgICAgIHJldHVybiB7fTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZXRPYmplY3QkMihvYmplY3QsIGtleSwgdmFsdWUpIHsKICAgICAgb2JqZWN0W2tleV0gPSB2YWx1ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdGVNYXAkMSgpIHsKICAgICAgcmV0dXJuIG1hcCQ1KCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2V0TWFwJDEobWFwLCBrZXksIHZhbHVlKSB7CiAgICAgIG1hcC5zZXQoa2V5LCB2YWx1ZSk7CiAgICB9CgogICAgZnVuY3Rpb24gU2V0JDIoKSB7fQoKICAgIHZhciBwcm90byQyID0gbWFwJDUucHJvdG90eXBlOwoKICAgIFNldCQyLnByb3RvdHlwZSA9IHNldCQ2LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFNldCQyLAogICAgICBoYXM6IHByb3RvJDIuaGFzLAogICAgICBhZGQ6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgdmFsdWUgKz0gIiI7CiAgICAgICAgdGhpc1twcmVmaXgkMSArIHZhbHVlXSA9IHZhbHVlOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICByZW1vdmU6IHByb3RvJDIucmVtb3ZlLAogICAgICBjbGVhcjogcHJvdG8kMi5jbGVhciwKICAgICAgdmFsdWVzOiBwcm90byQyLmtleXMsCiAgICAgIHNpemU6IHByb3RvJDIuc2l6ZSwKICAgICAgZW1wdHk6IHByb3RvJDIuZW1wdHksCiAgICAgIGVhY2g6IHByb3RvJDIuZWFjaAogICAgfTsKCiAgICBmdW5jdGlvbiBzZXQkNihvYmplY3QsIGYpIHsKICAgICAgdmFyIHNldCA9IG5ldyBTZXQkMjsKCiAgICAgIC8vIENvcHkgY29uc3RydWN0b3IuCiAgICAgIGlmIChvYmplY3QgaW5zdGFuY2VvZiBTZXQkMikgb2JqZWN0LmVhY2goZnVuY3Rpb24odmFsdWUpIHsgc2V0LmFkZCh2YWx1ZSk7IH0pOwoKICAgICAgLy8gT3RoZXJ3aXNlLCBhc3N1bWUgaXTigJlzIGFuIGFycmF5LgogICAgICBlbHNlIGlmIChvYmplY3QpIHsKICAgICAgICB2YXIgaSA9IC0xLCBuID0gb2JqZWN0Lmxlbmd0aDsKICAgICAgICBpZiAoZiA9PSBudWxsKSB3aGlsZSAoKytpIDwgbikgc2V0LmFkZChvYmplY3RbaV0pOwogICAgICAgIGVsc2Ugd2hpbGUgKCsraSA8IG4pIHNldC5hZGQoZihvYmplY3RbaV0sIGksIG9iamVjdCkpOwogICAgICB9CgogICAgICByZXR1cm4gc2V0OwogICAgfQoKICAgIGZ1bmN0aW9uIGtleXMkMShtYXApIHsKICAgICAgdmFyIGtleXMgPSBbXTsKICAgICAgZm9yICh2YXIga2V5IGluIG1hcCkga2V5cy5wdXNoKGtleSk7CiAgICAgIHJldHVybiBrZXlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHZhbHVlcyQxKG1hcCkgewogICAgICB2YXIgdmFsdWVzID0gW107CiAgICAgIGZvciAodmFyIGtleSBpbiBtYXApIHZhbHVlcy5wdXNoKG1hcFtrZXldKTsKICAgICAgcmV0dXJuIHZhbHVlczsKICAgIH0KCiAgICBmdW5jdGlvbiBlbnRyaWVzJDEobWFwKSB7CiAgICAgIHZhciBlbnRyaWVzID0gW107CiAgICAgIGZvciAodmFyIGtleSBpbiBtYXApIGVudHJpZXMucHVzaCh7a2V5OiBrZXksIHZhbHVlOiBtYXBba2V5XX0pOwogICAgICByZXR1cm4gZW50cmllczsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZpbmUkMihjb25zdHJ1Y3RvciwgZmFjdG9yeSwgcHJvdG90eXBlKSB7CiAgICAgIGNvbnN0cnVjdG9yLnByb3RvdHlwZSA9IGZhY3RvcnkucHJvdG90eXBlID0gcHJvdG90eXBlOwogICAgICBwcm90b3R5cGUuY29uc3RydWN0b3IgPSBjb25zdHJ1Y3RvcjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHRlbmQkMihwYXJlbnQsIGRlZmluaXRpb24pIHsKICAgICAgdmFyIHByb3RvdHlwZSA9IE9iamVjdC5jcmVhdGUocGFyZW50LnByb3RvdHlwZSk7CiAgICAgIGZvciAodmFyIGtleSBpbiBkZWZpbml0aW9uKSBwcm90b3R5cGVba2V5XSA9IGRlZmluaXRpb25ba2V5XTsKICAgICAgcmV0dXJuIHByb3RvdHlwZTsKICAgIH0KCiAgICBmdW5jdGlvbiBDb2xvciQyKCkge30KCiAgICB2YXIgZGFya2VyJDIgPSAwLjc7CiAgICB2YXIgYnJpZ2h0ZXIkMiA9IDEgLyBkYXJrZXIkMjsKCiAgICB2YXIgcmVJJDIgPSAiXFxzKihbKy1dP1xcZCspXFxzKiIsCiAgICAgICAgcmVOJDIgPSAiXFxzKihbKy1dP1xcZCpcXC4/XFxkKyg/OltlRV1bKy1dP1xcZCspPylcXHMqIiwKICAgICAgICByZVAkMiA9ICJcXHMqKFsrLV0/XFxkKlxcLj9cXGQrKD86W2VFXVsrLV0/XFxkKyk/KSVcXHMqIiwKICAgICAgICByZUhleDMgPSAvXiMoWzAtOWEtZl17M30pJC8sCiAgICAgICAgcmVIZXg2ID0gL14jKFswLTlhLWZdezZ9KSQvLAogICAgICAgIHJlUmdiSW50ZWdlciQyID0gbmV3IFJlZ0V4cCgiXnJnYlxcKCIgKyBbcmVJJDIsIHJlSSQyLCByZUkkMl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiUGVyY2VudCQyID0gbmV3IFJlZ0V4cCgiXnJnYlxcKCIgKyBbcmVQJDIsIHJlUCQyLCByZVAkMl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiYUludGVnZXIkMiA9IG5ldyBSZWdFeHAoIl5yZ2JhXFwoIiArIFtyZUkkMiwgcmVJJDIsIHJlSSQyLCByZU4kMl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiYVBlcmNlbnQkMiA9IG5ldyBSZWdFeHAoIl5yZ2JhXFwoIiArIFtyZVAkMiwgcmVQJDIsIHJlUCQyLCByZU4kMl0gKyAiXFwpJCIpLAogICAgICAgIHJlSHNsUGVyY2VudCQyID0gbmV3IFJlZ0V4cCgiXmhzbFxcKCIgKyBbcmVOJDIsIHJlUCQyLCByZVAkMl0gKyAiXFwpJCIpLAogICAgICAgIHJlSHNsYVBlcmNlbnQkMiA9IG5ldyBSZWdFeHAoIl5oc2xhXFwoIiArIFtyZU4kMiwgcmVQJDIsIHJlUCQyLCByZU4kMl0gKyAiXFwpJCIpOwoKICAgIHZhciBuYW1lZCQyID0gewogICAgICBhbGljZWJsdWU6IDB4ZjBmOGZmLAogICAgICBhbnRpcXVld2hpdGU6IDB4ZmFlYmQ3LAogICAgICBhcXVhOiAweDAwZmZmZiwKICAgICAgYXF1YW1hcmluZTogMHg3ZmZmZDQsCiAgICAgIGF6dXJlOiAweGYwZmZmZiwKICAgICAgYmVpZ2U6IDB4ZjVmNWRjLAogICAgICBiaXNxdWU6IDB4ZmZlNGM0LAogICAgICBibGFjazogMHgwMDAwMDAsCiAgICAgIGJsYW5jaGVkYWxtb25kOiAweGZmZWJjZCwKICAgICAgYmx1ZTogMHgwMDAwZmYsCiAgICAgIGJsdWV2aW9sZXQ6IDB4OGEyYmUyLAogICAgICBicm93bjogMHhhNTJhMmEsCiAgICAgIGJ1cmx5d29vZDogMHhkZWI4ODcsCiAgICAgIGNhZGV0Ymx1ZTogMHg1ZjllYTAsCiAgICAgIGNoYXJ0cmV1c2U6IDB4N2ZmZjAwLAogICAgICBjaG9jb2xhdGU6IDB4ZDI2OTFlLAogICAgICBjb3JhbDogMHhmZjdmNTAsCiAgICAgIGNvcm5mbG93ZXJibHVlOiAweDY0OTVlZCwKICAgICAgY29ybnNpbGs6IDB4ZmZmOGRjLAogICAgICBjcmltc29uOiAweGRjMTQzYywKICAgICAgY3lhbjogMHgwMGZmZmYsCiAgICAgIGRhcmtibHVlOiAweDAwMDA4YiwKICAgICAgZGFya2N5YW46IDB4MDA4YjhiLAogICAgICBkYXJrZ29sZGVucm9kOiAweGI4ODYwYiwKICAgICAgZGFya2dyYXk6IDB4YTlhOWE5LAogICAgICBkYXJrZ3JlZW46IDB4MDA2NDAwLAogICAgICBkYXJrZ3JleTogMHhhOWE5YTksCiAgICAgIGRhcmtraGFraTogMHhiZGI3NmIsCiAgICAgIGRhcmttYWdlbnRhOiAweDhiMDA4YiwKICAgICAgZGFya29saXZlZ3JlZW46IDB4NTU2YjJmLAogICAgICBkYXJrb3JhbmdlOiAweGZmOGMwMCwKICAgICAgZGFya29yY2hpZDogMHg5OTMyY2MsCiAgICAgIGRhcmtyZWQ6IDB4OGIwMDAwLAogICAgICBkYXJrc2FsbW9uOiAweGU5OTY3YSwKICAgICAgZGFya3NlYWdyZWVuOiAweDhmYmM4ZiwKICAgICAgZGFya3NsYXRlYmx1ZTogMHg0ODNkOGIsCiAgICAgIGRhcmtzbGF0ZWdyYXk6IDB4MmY0ZjRmLAogICAgICBkYXJrc2xhdGVncmV5OiAweDJmNGY0ZiwKICAgICAgZGFya3R1cnF1b2lzZTogMHgwMGNlZDEsCiAgICAgIGRhcmt2aW9sZXQ6IDB4OTQwMGQzLAogICAgICBkZWVwcGluazogMHhmZjE0OTMsCiAgICAgIGRlZXBza3libHVlOiAweDAwYmZmZiwKICAgICAgZGltZ3JheTogMHg2OTY5NjksCiAgICAgIGRpbWdyZXk6IDB4Njk2OTY5LAogICAgICBkb2RnZXJibHVlOiAweDFlOTBmZiwKICAgICAgZmlyZWJyaWNrOiAweGIyMjIyMiwKICAgICAgZmxvcmFsd2hpdGU6IDB4ZmZmYWYwLAogICAgICBmb3Jlc3RncmVlbjogMHgyMjhiMjIsCiAgICAgIGZ1Y2hzaWE6IDB4ZmYwMGZmLAogICAgICBnYWluc2Jvcm86IDB4ZGNkY2RjLAogICAgICBnaG9zdHdoaXRlOiAweGY4ZjhmZiwKICAgICAgZ29sZDogMHhmZmQ3MDAsCiAgICAgIGdvbGRlbnJvZDogMHhkYWE1MjAsCiAgICAgIGdyYXk6IDB4ODA4MDgwLAogICAgICBncmVlbjogMHgwMDgwMDAsCiAgICAgIGdyZWVueWVsbG93OiAweGFkZmYyZiwKICAgICAgZ3JleTogMHg4MDgwODAsCiAgICAgIGhvbmV5ZGV3OiAweGYwZmZmMCwKICAgICAgaG90cGluazogMHhmZjY5YjQsCiAgICAgIGluZGlhbnJlZDogMHhjZDVjNWMsCiAgICAgIGluZGlnbzogMHg0YjAwODIsCiAgICAgIGl2b3J5OiAweGZmZmZmMCwKICAgICAga2hha2k6IDB4ZjBlNjhjLAogICAgICBsYXZlbmRlcjogMHhlNmU2ZmEsCiAgICAgIGxhdmVuZGVyYmx1c2g6IDB4ZmZmMGY1LAogICAgICBsYXduZ3JlZW46IDB4N2NmYzAwLAogICAgICBsZW1vbmNoaWZmb246IDB4ZmZmYWNkLAogICAgICBsaWdodGJsdWU6IDB4YWRkOGU2LAogICAgICBsaWdodGNvcmFsOiAweGYwODA4MCwKICAgICAgbGlnaHRjeWFuOiAweGUwZmZmZiwKICAgICAgbGlnaHRnb2xkZW5yb2R5ZWxsb3c6IDB4ZmFmYWQyLAogICAgICBsaWdodGdyYXk6IDB4ZDNkM2QzLAogICAgICBsaWdodGdyZWVuOiAweDkwZWU5MCwKICAgICAgbGlnaHRncmV5OiAweGQzZDNkMywKICAgICAgbGlnaHRwaW5rOiAweGZmYjZjMSwKICAgICAgbGlnaHRzYWxtb246IDB4ZmZhMDdhLAogICAgICBsaWdodHNlYWdyZWVuOiAweDIwYjJhYSwKICAgICAgbGlnaHRza3libHVlOiAweDg3Y2VmYSwKICAgICAgbGlnaHRzbGF0ZWdyYXk6IDB4Nzc4ODk5LAogICAgICBsaWdodHNsYXRlZ3JleTogMHg3Nzg4OTksCiAgICAgIGxpZ2h0c3RlZWxibHVlOiAweGIwYzRkZSwKICAgICAgbGlnaHR5ZWxsb3c6IDB4ZmZmZmUwLAogICAgICBsaW1lOiAweDAwZmYwMCwKICAgICAgbGltZWdyZWVuOiAweDMyY2QzMiwKICAgICAgbGluZW46IDB4ZmFmMGU2LAogICAgICBtYWdlbnRhOiAweGZmMDBmZiwKICAgICAgbWFyb29uOiAweDgwMDAwMCwKICAgICAgbWVkaXVtYXF1YW1hcmluZTogMHg2NmNkYWEsCiAgICAgIG1lZGl1bWJsdWU6IDB4MDAwMGNkLAogICAgICBtZWRpdW1vcmNoaWQ6IDB4YmE1NWQzLAogICAgICBtZWRpdW1wdXJwbGU6IDB4OTM3MGRiLAogICAgICBtZWRpdW1zZWFncmVlbjogMHgzY2IzNzEsCiAgICAgIG1lZGl1bXNsYXRlYmx1ZTogMHg3YjY4ZWUsCiAgICAgIG1lZGl1bXNwcmluZ2dyZWVuOiAweDAwZmE5YSwKICAgICAgbWVkaXVtdHVycXVvaXNlOiAweDQ4ZDFjYywKICAgICAgbWVkaXVtdmlvbGV0cmVkOiAweGM3MTU4NSwKICAgICAgbWlkbmlnaHRibHVlOiAweDE5MTk3MCwKICAgICAgbWludGNyZWFtOiAweGY1ZmZmYSwKICAgICAgbWlzdHlyb3NlOiAweGZmZTRlMSwKICAgICAgbW9jY2FzaW46IDB4ZmZlNGI1LAogICAgICBuYXZham93aGl0ZTogMHhmZmRlYWQsCiAgICAgIG5hdnk6IDB4MDAwMDgwLAogICAgICBvbGRsYWNlOiAweGZkZjVlNiwKICAgICAgb2xpdmU6IDB4ODA4MDAwLAogICAgICBvbGl2ZWRyYWI6IDB4NmI4ZTIzLAogICAgICBvcmFuZ2U6IDB4ZmZhNTAwLAogICAgICBvcmFuZ2VyZWQ6IDB4ZmY0NTAwLAogICAgICBvcmNoaWQ6IDB4ZGE3MGQ2LAogICAgICBwYWxlZ29sZGVucm9kOiAweGVlZThhYSwKICAgICAgcGFsZWdyZWVuOiAweDk4ZmI5OCwKICAgICAgcGFsZXR1cnF1b2lzZTogMHhhZmVlZWUsCiAgICAgIHBhbGV2aW9sZXRyZWQ6IDB4ZGI3MDkzLAogICAgICBwYXBheWF3aGlwOiAweGZmZWZkNSwKICAgICAgcGVhY2hwdWZmOiAweGZmZGFiOSwKICAgICAgcGVydTogMHhjZDg1M2YsCiAgICAgIHBpbms6IDB4ZmZjMGNiLAogICAgICBwbHVtOiAweGRkYTBkZCwKICAgICAgcG93ZGVyYmx1ZTogMHhiMGUwZTYsCiAgICAgIHB1cnBsZTogMHg4MDAwODAsCiAgICAgIHJlYmVjY2FwdXJwbGU6IDB4NjYzMzk5LAogICAgICByZWQ6IDB4ZmYwMDAwLAogICAgICByb3N5YnJvd246IDB4YmM4ZjhmLAogICAgICByb3lhbGJsdWU6IDB4NDE2OWUxLAogICAgICBzYWRkbGVicm93bjogMHg4YjQ1MTMsCiAgICAgIHNhbG1vbjogMHhmYTgwNzIsCiAgICAgIHNhbmR5YnJvd246IDB4ZjRhNDYwLAogICAgICBzZWFncmVlbjogMHgyZThiNTcsCiAgICAgIHNlYXNoZWxsOiAweGZmZjVlZSwKICAgICAgc2llbm5hOiAweGEwNTIyZCwKICAgICAgc2lsdmVyOiAweGMwYzBjMCwKICAgICAgc2t5Ymx1ZTogMHg4N2NlZWIsCiAgICAgIHNsYXRlYmx1ZTogMHg2YTVhY2QsCiAgICAgIHNsYXRlZ3JheTogMHg3MDgwOTAsCiAgICAgIHNsYXRlZ3JleTogMHg3MDgwOTAsCiAgICAgIHNub3c6IDB4ZmZmYWZhLAogICAgICBzcHJpbmdncmVlbjogMHgwMGZmN2YsCiAgICAgIHN0ZWVsYmx1ZTogMHg0NjgyYjQsCiAgICAgIHRhbjogMHhkMmI0OGMsCiAgICAgIHRlYWw6IDB4MDA4MDgwLAogICAgICB0aGlzdGxlOiAweGQ4YmZkOCwKICAgICAgdG9tYXRvOiAweGZmNjM0NywKICAgICAgdHVycXVvaXNlOiAweDQwZTBkMCwKICAgICAgdmlvbGV0OiAweGVlODJlZSwKICAgICAgd2hlYXQ6IDB4ZjVkZWIzLAogICAgICB3aGl0ZTogMHhmZmZmZmYsCiAgICAgIHdoaXRlc21va2U6IDB4ZjVmNWY1LAogICAgICB5ZWxsb3c6IDB4ZmZmZjAwLAogICAgICB5ZWxsb3dncmVlbjogMHg5YWNkMzIKICAgIH07CgogICAgZGVmaW5lJDIoQ29sb3IkMiwgY29sb3IkMiwgewogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZGlzcGxheWFibGUoKTsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnJnYigpICsgIiI7CiAgICAgIH0KICAgIH0pOwoKICAgIGZ1bmN0aW9uIGNvbG9yJDIoZm9ybWF0KSB7CiAgICAgIHZhciBtOwogICAgICBmb3JtYXQgPSAoZm9ybWF0ICsgIiIpLnRyaW0oKS50b0xvd2VyQ2FzZSgpOwogICAgICByZXR1cm4gKG0gPSByZUhleDMuZXhlYyhmb3JtYXQpKSA/IChtID0gcGFyc2VJbnQobVsxXSwgMTYpLCBuZXcgUmdiJDIoKG0gPj4gOCAmIDB4ZikgfCAobSA+PiA0ICYgMHgwZjApLCAobSA+PiA0ICYgMHhmKSB8IChtICYgMHhmMCksICgobSAmIDB4ZikgPDwgNCkgfCAobSAmIDB4ZiksIDEpKSAvLyAjZjAwCiAgICAgICAgICA6IChtID0gcmVIZXg2LmV4ZWMoZm9ybWF0KSkgPyByZ2JuJDIocGFyc2VJbnQobVsxXSwgMTYpKSAvLyAjZmYwMDAwCiAgICAgICAgICA6IChtID0gcmVSZ2JJbnRlZ2VyJDIuZXhlYyhmb3JtYXQpKSA/IG5ldyBSZ2IkMihtWzFdLCBtWzJdLCBtWzNdLCAxKSAvLyByZ2IoMjU1LCAwLCAwKQogICAgICAgICAgOiAobSA9IHJlUmdiUGVyY2VudCQyLmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiJDIobVsxXSAqIDI1NSAvIDEwMCwgbVsyXSAqIDI1NSAvIDEwMCwgbVszXSAqIDI1NSAvIDEwMCwgMSkgLy8gcmdiKDEwMCUsIDAlLCAwJSkKICAgICAgICAgIDogKG0gPSByZVJnYmFJbnRlZ2VyJDIuZXhlYyhmb3JtYXQpKSA/IHJnYmEkMihtWzFdLCBtWzJdLCBtWzNdLCBtWzRdKSAvLyByZ2JhKDI1NSwgMCwgMCwgMSkKICAgICAgICAgIDogKG0gPSByZVJnYmFQZXJjZW50JDIuZXhlYyhmb3JtYXQpKSA/IHJnYmEkMihtWzFdICogMjU1IC8gMTAwLCBtWzJdICogMjU1IC8gMTAwLCBtWzNdICogMjU1IC8gMTAwLCBtWzRdKSAvLyByZ2IoMTAwJSwgMCUsIDAlLCAxKQogICAgICAgICAgOiAobSA9IHJlSHNsUGVyY2VudCQyLmV4ZWMoZm9ybWF0KSkgPyBoc2xhJDIobVsxXSwgbVsyXSAvIDEwMCwgbVszXSAvIDEwMCwgMSkgLy8gaHNsKDEyMCwgNTAlLCA1MCUpCiAgICAgICAgICA6IChtID0gcmVIc2xhUGVyY2VudCQyLmV4ZWMoZm9ybWF0KSkgPyBoc2xhJDIobVsxXSwgbVsyXSAvIDEwMCwgbVszXSAvIDEwMCwgbVs0XSkgLy8gaHNsYSgxMjAsIDUwJSwgNTAlLCAxKQogICAgICAgICAgOiBuYW1lZCQyLmhhc093blByb3BlcnR5KGZvcm1hdCkgPyByZ2JuJDIobmFtZWQkMltmb3JtYXRdKQogICAgICAgICAgOiBmb3JtYXQgPT09ICJ0cmFuc3BhcmVudCIgPyBuZXcgUmdiJDIoTmFOLCBOYU4sIE5hTiwgMCkKICAgICAgICAgIDogbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JuJDIobikgewogICAgICByZXR1cm4gbmV3IFJnYiQyKG4gPj4gMTYgJiAweGZmLCBuID4+IDggJiAweGZmLCBuICYgMHhmZiwgMSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiYSQyKHIsIGcsIGIsIGEpIHsKICAgICAgaWYgKGEgPD0gMCkgciA9IGcgPSBiID0gTmFOOwogICAgICByZXR1cm4gbmV3IFJnYiQyKHIsIGcsIGIsIGEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYkNvbnZlcnQkMihvKSB7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvciQyKSkgbyA9IGNvbG9yJDIobyk7CiAgICAgIGlmICghbykgcmV0dXJuIG5ldyBSZ2IkMjsKICAgICAgbyA9IG8ucmdiKCk7CiAgICAgIHJldHVybiBuZXcgUmdiJDIoby5yLCBvLmcsIG8uYiwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2IkMihyLCBnLCBiLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gcmdiQ29udmVydCQyKHIpIDogbmV3IFJnYiQyKHIsIGcsIGIsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBSZ2IkMihyLCBnLCBiLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuciA9ICtyOwogICAgICB0aGlzLmcgPSArZzsKICAgICAgdGhpcy5iID0gK2I7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGRlZmluZSQyKFJnYiQyLCByZ2IkMiwgZXh0ZW5kJDIoQ29sb3IkMiwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBicmlnaHRlciQyIDogTWF0aC5wb3coYnJpZ2h0ZXIkMiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMih0aGlzLnIgKiBrLCB0aGlzLmcgKiBrLCB0aGlzLmIgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDIgOiBNYXRoLnBvdyhkYXJrZXIkMiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMih0aGlzLnIgKiBrLCB0aGlzLmcgKiBrLCB0aGlzLmIgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuICgwIDw9IHRoaXMuciAmJiB0aGlzLnIgPD0gMjU1KQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLmcgJiYgdGhpcy5nIDw9IDI1NSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5iICYmIHRoaXMuYiA8PSAyNTUpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMub3BhY2l0eSAmJiB0aGlzLm9wYWNpdHkgPD0gMSk7CiAgICAgIH0sCiAgICAgIHRvU3RyaW5nOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYSA9IHRoaXMub3BhY2l0eTsgYSA9IGlzTmFOKGEpID8gMSA6IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIGEpKTsKICAgICAgICByZXR1cm4gKGEgPT09IDEgPyAicmdiKCIgOiAicmdiYSgiKQogICAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLnIpIHx8IDApKSArICIsICIKICAgICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5nKSB8fCAwKSkgKyAiLCAiCiAgICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuYikgfHwgMCkpCiAgICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICAgIH0KICAgIH0pKTsKCiAgICBmdW5jdGlvbiBoc2xhJDIoaCwgcywgbCwgYSkgewogICAgICBpZiAoYSA8PSAwKSBoID0gcyA9IGwgPSBOYU47CiAgICAgIGVsc2UgaWYgKGwgPD0gMCB8fCBsID49IDEpIGggPSBzID0gTmFOOwogICAgICBlbHNlIGlmIChzIDw9IDApIGggPSBOYU47CiAgICAgIHJldHVybiBuZXcgSHNsJDIoaCwgcywgbCwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsQ29udmVydCQyKG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wkMikgcmV0dXJuIG5ldyBIc2wkMihvLmgsIG8ucywgby5sLCBvLm9wYWNpdHkpOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgQ29sb3IkMikpIG8gPSBjb2xvciQyKG8pOwogICAgICBpZiAoIW8pIHJldHVybiBuZXcgSHNsJDI7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgSHNsJDIpIHJldHVybiBvOwogICAgICBvID0gby5yZ2IoKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIG1pbiA9IE1hdGgubWluKHIsIGcsIGIpLAogICAgICAgICAgbWF4ID0gTWF0aC5tYXgociwgZywgYiksCiAgICAgICAgICBoID0gTmFOLAogICAgICAgICAgcyA9IG1heCAtIG1pbiwKICAgICAgICAgIGwgPSAobWF4ICsgbWluKSAvIDI7CiAgICAgIGlmIChzKSB7CiAgICAgICAgaWYgKHIgPT09IG1heCkgaCA9IChnIC0gYikgLyBzICsgKGcgPCBiKSAqIDY7CiAgICAgICAgZWxzZSBpZiAoZyA9PT0gbWF4KSBoID0gKGIgLSByKSAvIHMgKyAyOwogICAgICAgIGVsc2UgaCA9IChyIC0gZykgLyBzICsgNDsKICAgICAgICBzIC89IGwgPCAwLjUgPyBtYXggKyBtaW4gOiAyIC0gbWF4IC0gbWluOwogICAgICAgIGggKj0gNjA7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcyA9IGwgPiAwICYmIGwgPCAxID8gMCA6IGg7CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBIc2wkMihoLCBzLCBsLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbCQ0KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBoc2xDb252ZXJ0JDIoaCkgOiBuZXcgSHNsJDIoaCwgcywgbCwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIEhzbCQyKGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5oID0gK2g7CiAgICAgIHRoaXMucyA9ICtzOwogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDIoSHNsJDIsIGhzbCQ0LCBleHRlbmQkMihDb2xvciQyLCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDIgOiBNYXRoLnBvdyhicmlnaHRlciQyLCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCQyKHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDIgOiBNYXRoLnBvdyhkYXJrZXIkMiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBIc2wkMih0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaCA9IHRoaXMuaCAlIDM2MCArICh0aGlzLmggPCAwKSAqIDM2MCwKICAgICAgICAgICAgcyA9IGlzTmFOKGgpIHx8IGlzTmFOKHRoaXMucykgPyAwIDogdGhpcy5zLAogICAgICAgICAgICBsID0gdGhpcy5sLAogICAgICAgICAgICBtMiA9IGwgKyAobCA8IDAuNSA/IGwgOiAxIC0gbCkgKiBzLAogICAgICAgICAgICBtMSA9IDIgKiBsIC0gbTI7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMigKICAgICAgICAgIGhzbDJyZ2IkMihoID49IDI0MCA/IGggLSAyNDAgOiBoICsgMTIwLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYiQyKGgsIG0xLCBtMiksCiAgICAgICAgICBoc2wycmdiJDIoaCA8IDEyMCA/IGggKyAyNDAgOiBoIC0gMTIwLCBtMSwgbTIpLAogICAgICAgICAgdGhpcy5vcGFjaXR5CiAgICAgICAgKTsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoMCA8PSB0aGlzLnMgJiYgdGhpcy5zIDw9IDEgfHwgaXNOYU4odGhpcy5zKSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5sICYmIHRoaXMubCA8PSAxKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9CiAgICB9KSk7CgogICAgLyogRnJvbSBGdkQgMTMuMzcsIENTUyBDb2xvciBNb2R1bGUgTGV2ZWwgMyAqLwogICAgZnVuY3Rpb24gaHNsMnJnYiQyKGgsIG0xLCBtMikgewogICAgICByZXR1cm4gKGggPCA2MCA/IG0xICsgKG0yIC0gbTEpICogaCAvIDYwCiAgICAgICAgICA6IGggPCAxODAgPyBtMgogICAgICAgICAgOiBoIDwgMjQwID8gbTEgKyAobTIgLSBtMSkgKiAoMjQwIC0gaCkgLyA2MAogICAgICAgICAgOiBtMSkgKiAyNTU7CiAgICB9CgogICAgdmFyIGRlZzJyYWQkMSA9IE1hdGguUEkgLyAxODA7CiAgICB2YXIgcmFkMmRlZyQxID0gMTgwIC8gTWF0aC5QSTsKCiAgICB2YXIgS24gPSAxOCwKICAgICAgICBYbiQxID0gMC45NTA0NzAsIC8vIEQ2NSBzdGFuZGFyZCByZWZlcmVudAogICAgICAgIFluJDEgPSAxLAogICAgICAgIFpuJDEgPSAxLjA4ODgzMCwKICAgICAgICB0MCQyID0gNCAvIDI5LAogICAgICAgIHQxJDIgPSA2IC8gMjksCiAgICAgICAgdDIkMSA9IDMgKiB0MSQyICogdDEkMiwKICAgICAgICB0MyQxID0gdDEkMiAqIHQxJDIgKiB0MSQyOwoKICAgIGZ1bmN0aW9uIGxhYkNvbnZlcnQkMShvKSB7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgTGFiJDEpIHJldHVybiBuZXcgTGFiJDEoby5sLCBvLmEsIG8uYiwgby5vcGFjaXR5KTsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIY2wkMSkgewogICAgICAgIHZhciBoID0gby5oICogZGVnMnJhZCQxOwogICAgICAgIHJldHVybiBuZXcgTGFiJDEoby5sLCBNYXRoLmNvcyhoKSAqIG8uYywgTWF0aC5zaW4oaCkgKiBvLmMsIG8ub3BhY2l0eSk7CiAgICAgIH0KICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIFJnYiQyKSkgbyA9IHJnYkNvbnZlcnQkMihvKTsKICAgICAgdmFyIGIgPSByZ2IyeHl6KG8uciksCiAgICAgICAgICBhID0gcmdiMnh5eihvLmcpLAogICAgICAgICAgbCA9IHJnYjJ4eXooby5iKSwKICAgICAgICAgIHggPSB4eXoybGFiJDEoKDAuNDEyNDU2NCAqIGIgKyAwLjM1NzU3NjEgKiBhICsgMC4xODA0Mzc1ICogbCkgLyBYbiQxKSwKICAgICAgICAgIHkgPSB4eXoybGFiJDEoKDAuMjEyNjcyOSAqIGIgKyAwLjcxNTE1MjIgKiBhICsgMC4wNzIxNzUwICogbCkgLyBZbiQxKSwKICAgICAgICAgIHogPSB4eXoybGFiJDEoKDAuMDE5MzMzOSAqIGIgKyAwLjExOTE5MjAgKiBhICsgMC45NTAzMDQxICogbCkgLyBabiQxKTsKICAgICAgcmV0dXJuIG5ldyBMYWIkMSgxMTYgKiB5IC0gMTYsIDUwMCAqICh4IC0geSksIDIwMCAqICh5IC0geiksIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGFiJDIobCwgYSwgYiwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGxhYkNvbnZlcnQkMShsKSA6IG5ldyBMYWIkMShsLCBhLCBiLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gTGFiJDEobCwgYSwgYiwgb3BhY2l0eSkgewogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5hID0gK2E7CiAgICAgIHRoaXMuYiA9ICtiOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkMihMYWIkMSwgbGFiJDIsIGV4dGVuZCQyKENvbG9yJDIsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICByZXR1cm4gbmV3IExhYiQxKHRoaXMubCArIEtuICogKGsgPT0gbnVsbCA/IDEgOiBrKSwgdGhpcy5hLCB0aGlzLmIsIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIHJldHVybiBuZXcgTGFiJDEodGhpcy5sIC0gS24gKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLmEsIHRoaXMuYiwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgeSA9ICh0aGlzLmwgKyAxNikgLyAxMTYsCiAgICAgICAgICAgIHggPSBpc05hTih0aGlzLmEpID8geSA6IHkgKyB0aGlzLmEgLyA1MDAsCiAgICAgICAgICAgIHogPSBpc05hTih0aGlzLmIpID8geSA6IHkgLSB0aGlzLmIgLyAyMDA7CiAgICAgICAgeSA9IFluJDEgKiBsYWIyeHl6JDEoeSk7CiAgICAgICAgeCA9IFhuJDEgKiBsYWIyeHl6JDEoeCk7CiAgICAgICAgeiA9IFpuJDEgKiBsYWIyeHl6JDEoeik7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMigKICAgICAgICAgIHh5ejJyZ2IoIDMuMjQwNDU0MiAqIHggLSAxLjUzNzEzODUgKiB5IC0gMC40OTg1MzE0ICogeiksIC8vIEQ2NSAtPiBzUkdCCiAgICAgICAgICB4eXoycmdiKC0wLjk2OTI2NjAgKiB4ICsgMS44NzYwMTA4ICogeSArIDAuMDQxNTU2MCAqIHopLAogICAgICAgICAgeHl6MnJnYiggMC4wNTU2NDM0ICogeCAtIDAuMjA0MDI1OSAqIHkgKyAxLjA1NzIyNTIgKiB6KSwKICAgICAgICAgIHRoaXMub3BhY2l0eQogICAgICAgICk7CiAgICAgIH0KICAgIH0pKTsKCiAgICBmdW5jdGlvbiB4eXoybGFiJDEodCkgewogICAgICByZXR1cm4gdCA+IHQzJDEgPyBNYXRoLnBvdyh0LCAxIC8gMykgOiB0IC8gdDIkMSArIHQwJDI7CiAgICB9CgogICAgZnVuY3Rpb24gbGFiMnh5eiQxKHQpIHsKICAgICAgcmV0dXJuIHQgPiB0MSQyID8gdCAqIHQgKiB0IDogdDIkMSAqICh0IC0gdDAkMik7CiAgICB9CgogICAgZnVuY3Rpb24geHl6MnJnYih4KSB7CiAgICAgIHJldHVybiAyNTUgKiAoeCA8PSAwLjAwMzEzMDggPyAxMi45MiAqIHggOiAxLjA1NSAqIE1hdGgucG93KHgsIDEgLyAyLjQpIC0gMC4wNTUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYjJ4eXooeCkgewogICAgICByZXR1cm4gKHggLz0gMjU1KSA8PSAwLjA0MDQ1ID8geCAvIDEyLjkyIDogTWF0aC5wb3coKHggKyAwLjA1NSkgLyAxLjA1NSwgMi40KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2xDb252ZXJ0JDEobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIEhjbCQxKSByZXR1cm4gbmV3IEhjbCQxKG8uaCwgby5jLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBMYWIkMSkpIG8gPSBsYWJDb252ZXJ0JDEobyk7CiAgICAgIHZhciBoID0gTWF0aC5hdGFuMihvLmIsIG8uYSkgKiByYWQyZGVnJDE7CiAgICAgIHJldHVybiBuZXcgSGNsJDEoaCA8IDAgPyBoICsgMzYwIDogaCwgTWF0aC5zcXJ0KG8uYSAqIG8uYSArIG8uYiAqIG8uYiksIG8ubCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2wkMyhoLCBjLCBsLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gaGNsQ29udmVydCQxKGgpIDogbmV3IEhjbCQxKGgsIGMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBIY2wkMShoLCBjLCBsLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuaCA9ICtoOwogICAgICB0aGlzLmMgPSArYzsKICAgICAgdGhpcy5sID0gK2w7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGRlZmluZSQyKEhjbCQxLCBoY2wkMywgZXh0ZW5kJDIoQ29sb3IkMiwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIHJldHVybiBuZXcgSGNsJDEodGhpcy5oLCB0aGlzLmMsIHRoaXMubCArIEtuICogKGsgPT0gbnVsbCA/IDEgOiBrKSwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBIY2wkMSh0aGlzLmgsIHRoaXMuYywgdGhpcy5sIC0gS24gKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBsYWJDb252ZXJ0JDEodGhpcykucmdiKCk7CiAgICAgIH0KICAgIH0pKTsKCiAgICB2YXIgQSQxID0gLTAuMTQ4NjEsCiAgICAgICAgQiQxID0gKzEuNzgyNzcsCiAgICAgICAgQyQxID0gLTAuMjkyMjcsCiAgICAgICAgRCQxID0gLTAuOTA2NDksCiAgICAgICAgRSQxID0gKzEuOTcyOTQsCiAgICAgICAgRUQkMSA9IEUkMSAqIEQkMSwKICAgICAgICBFQiQxID0gRSQxICogQiQxLAogICAgICAgIEJDX0RBJDEgPSBCJDEgKiBDJDEgLSBEJDEgKiBBJDE7CgogICAgZnVuY3Rpb24gY3ViZWhlbGl4Q29udmVydCQxKG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBDdWJlaGVsaXgkMSkgcmV0dXJuIG5ldyBDdWJlaGVsaXgkMShvLmgsIG8ucywgby5sLCBvLm9wYWNpdHkpOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgUmdiJDIpKSBvID0gcmdiQ29udmVydCQyKG8pOwogICAgICB2YXIgciA9IG8uciAvIDI1NSwKICAgICAgICAgIGcgPSBvLmcgLyAyNTUsCiAgICAgICAgICBiID0gby5iIC8gMjU1LAogICAgICAgICAgbCA9IChCQ19EQSQxICogYiArIEVEJDEgKiByIC0gRUIkMSAqIGcpIC8gKEJDX0RBJDEgKyBFRCQxIC0gRUIkMSksCiAgICAgICAgICBibCA9IGIgLSBsLAogICAgICAgICAgayA9IChFJDEgKiAoZyAtIGwpIC0gQyQxICogYmwpIC8gRCQxLAogICAgICAgICAgcyA9IE1hdGguc3FydChrICogayArIGJsICogYmwpIC8gKEUkMSAqIGwgKiAoMSAtIGwpKSwgLy8gTmFOIGlmIGw9MCBvciBsPTEKICAgICAgICAgIGggPSBzID8gTWF0aC5hdGFuMihrLCBibCkgKiByYWQyZGVnJDEgLSAxMjAgOiBOYU47CiAgICAgIHJldHVybiBuZXcgQ3ViZWhlbGl4JDEoaCA8IDAgPyBoICsgMzYwIDogaCwgcywgbCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjdWJlaGVsaXgkNChoLCBzLCBsLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gY3ViZWhlbGl4Q29udmVydCQxKGgpIDogbmV3IEN1YmVoZWxpeCQxKGgsIHMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBDdWJlaGVsaXgkMShoLCBzLCBsLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuaCA9ICtoOwogICAgICB0aGlzLnMgPSArczsKICAgICAgdGhpcy5sID0gK2w7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGRlZmluZSQyKEN1YmVoZWxpeCQxLCBjdWJlaGVsaXgkNCwgZXh0ZW5kJDIoQ29sb3IkMiwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBicmlnaHRlciQyIDogTWF0aC5wb3coYnJpZ2h0ZXIkMiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBDdWJlaGVsaXgkMSh0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciQyIDogTWF0aC5wb3coZGFya2VyJDIsIGspOwogICAgICAgIHJldHVybiBuZXcgQ3ViZWhlbGl4JDEodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIHJnYjogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGggPSBpc05hTih0aGlzLmgpID8gMCA6ICh0aGlzLmggKyAxMjApICogZGVnMnJhZCQxLAogICAgICAgICAgICBsID0gK3RoaXMubCwKICAgICAgICAgICAgYSA9IGlzTmFOKHRoaXMucykgPyAwIDogdGhpcy5zICogbCAqICgxIC0gbCksCiAgICAgICAgICAgIGNvc2ggPSBNYXRoLmNvcyhoKSwKICAgICAgICAgICAgc2luaCA9IE1hdGguc2luKGgpOwogICAgICAgIHJldHVybiBuZXcgUmdiJDIoCiAgICAgICAgICAyNTUgKiAobCArIGEgKiAoQSQxICogY29zaCArIEIkMSAqIHNpbmgpKSwKICAgICAgICAgIDI1NSAqIChsICsgYSAqIChDJDEgKiBjb3NoICsgRCQxICogc2luaCkpLAogICAgICAgICAgMjU1ICogKGwgKyBhICogKEUkMSAqIGNvc2gpKSwKICAgICAgICAgIHRoaXMub3BhY2l0eQogICAgICAgICk7CiAgICAgIH0KICAgIH0pKTsKCiAgICB2YXIgbm9vcCQ1ID0ge3ZhbHVlOiBmdW5jdGlvbigpIHt9fTsKCiAgICBmdW5jdGlvbiBkaXNwYXRjaCQyKCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGFyZ3VtZW50cy5sZW5ndGgsIF8gPSB7fSwgdDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICghKHQgPSBhcmd1bWVudHNbaV0gKyAiIikgfHwgKHQgaW4gXykpIHRocm93IG5ldyBFcnJvcigiaWxsZWdhbCB0eXBlOiAiICsgdCk7CiAgICAgICAgX1t0XSA9IFtdOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgRGlzcGF0Y2gkMihfKTsKICAgIH0KCiAgICBmdW5jdGlvbiBEaXNwYXRjaCQyKF8pIHsKICAgICAgdGhpcy5fID0gXzsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVR5cGVuYW1lcyQ0KHR5cGVuYW1lcywgdHlwZXMpIHsKICAgICAgcmV0dXJuIHR5cGVuYW1lcy50cmltKCkuc3BsaXQoL158XHMrLykubWFwKGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgbmFtZSA9ICIiLCBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgbmFtZSA9IHQuc2xpY2UoaSArIDEpLCB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICBpZiAodCAmJiAhdHlwZXMuaGFzT3duUHJvcGVydHkodCkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdCk7CiAgICAgICAgcmV0dXJuIHt0eXBlOiB0LCBuYW1lOiBuYW1lfTsKICAgICAgfSk7CiAgICB9CgogICAgRGlzcGF0Y2gkMi5wcm90b3R5cGUgPSBkaXNwYXRjaCQyLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IERpc3BhdGNoJDIsCiAgICAgIG9uOiBmdW5jdGlvbih0eXBlbmFtZSwgY2FsbGJhY2spIHsKICAgICAgICB2YXIgXyA9IHRoaXMuXywKICAgICAgICAgICAgVCA9IHBhcnNlVHlwZW5hbWVzJDQodHlwZW5hbWUgKyAiIiwgXyksCiAgICAgICAgICAgIHQsCiAgICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgICAgbiA9IFQubGVuZ3RoOwoKICAgICAgICAvLyBJZiBubyBjYWxsYmFjayB3YXMgc3BlY2lmaWVkLCByZXR1cm4gdGhlIGNhbGxiYWNrIG9mIHRoZSBnaXZlbiB0eXBlIGFuZCBuYW1lLgogICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICgodCA9ICh0eXBlbmFtZSA9IFRbaV0pLnR5cGUpICYmICh0ID0gZ2V0JDUoX1t0XSwgdHlwZW5hbWUubmFtZSkpKSByZXR1cm4gdDsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIElmIGEgdHlwZSB3YXMgc3BlY2lmaWVkLCBzZXQgdGhlIGNhbGxiYWNrIGZvciB0aGUgZ2l2ZW4gdHlwZSBhbmQgbmFtZS4KICAgICAgICAvLyBPdGhlcndpc2UsIGlmIGEgbnVsbCBjYWxsYmFjayB3YXMgc3BlY2lmaWVkLCByZW1vdmUgY2FsbGJhY2tzIG9mIHRoZSBnaXZlbiBuYW1lLgogICAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsICYmIHR5cGVvZiBjYWxsYmFjayAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIGNhbGxiYWNrOiAiICsgY2FsbGJhY2spOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICBpZiAodCA9ICh0eXBlbmFtZSA9IFRbaV0pLnR5cGUpIF9bdF0gPSBzZXQkNyhfW3RdLCB0eXBlbmFtZS5uYW1lLCBjYWxsYmFjayk7CiAgICAgICAgICBlbHNlIGlmIChjYWxsYmFjayA9PSBudWxsKSBmb3IgKHQgaW4gXykgX1t0XSA9IHNldCQ3KF9bdF0sIHR5cGVuYW1lLm5hbWUsIG51bGwpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIGNvcHk6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBjb3B5ID0ge30sIF8gPSB0aGlzLl87CiAgICAgICAgZm9yICh2YXIgdCBpbiBfKSBjb3B5W3RdID0gX1t0XS5zbGljZSgpOwogICAgICAgIHJldHVybiBuZXcgRGlzcGF0Y2gkMihjb3B5KTsKICAgICAgfSwKICAgICAgY2FsbDogZnVuY3Rpb24odHlwZSwgdGhhdCkgewogICAgICAgIGlmICgobiA9IGFyZ3VtZW50cy5sZW5ndGggLSAyKSA+IDApIGZvciAodmFyIGFyZ3MgPSBuZXcgQXJyYXkobiksIGkgPSAwLCBuLCB0OyBpIDwgbjsgKytpKSBhcmdzW2ldID0gYXJndW1lbnRzW2kgKyAyXTsKICAgICAgICBpZiAoIXRoaXMuXy5oYXNPd25Qcm9wZXJ0eSh0eXBlKSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0eXBlKTsKICAgICAgICBmb3IgKHQgPSB0aGlzLl9bdHlwZV0sIGkgPSAwLCBuID0gdC5sZW5ndGg7IGkgPCBuOyArK2kpIHRbaV0udmFsdWUuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0sCiAgICAgIGFwcGx5OiBmdW5jdGlvbih0eXBlLCB0aGF0LCBhcmdzKSB7CiAgICAgICAgaWYgKCF0aGlzLl8uaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdHlwZSk7CiAgICAgICAgZm9yICh2YXIgdCA9IHRoaXMuX1t0eXBlXSwgaSA9IDAsIG4gPSB0Lmxlbmd0aDsgaSA8IG47ICsraSkgdFtpXS52YWx1ZS5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBnZXQkNSh0eXBlLCBuYW1lKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHlwZS5sZW5ndGgsIGM7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoKGMgPSB0eXBlW2ldKS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICByZXR1cm4gYy52YWx1ZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZXQkNyh0eXBlLCBuYW1lLCBjYWxsYmFjaykgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR5cGUubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKHR5cGVbaV0ubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgdHlwZVtpXSA9IG5vb3AkNSwgdHlwZSA9IHR5cGUuc2xpY2UoMCwgaSkuY29uY2F0KHR5cGUuc2xpY2UoaSArIDEpKTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICBpZiAoY2FsbGJhY2sgIT0gbnVsbCkgdHlwZS5wdXNoKHtuYW1lOiBuYW1lLCB2YWx1ZTogY2FsbGJhY2t9KTsKICAgICAgcmV0dXJuIHR5cGU7CiAgICB9CgogICAgdmFyIG5vb3AkNiA9IHt2YWx1ZTogZnVuY3Rpb24oKSB7fX07CgogICAgZnVuY3Rpb24gZGlzcGF0Y2gkMygpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBhcmd1bWVudHMubGVuZ3RoLCBfID0ge30sIHQ7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoISh0ID0gYXJndW1lbnRzW2ldICsgIiIpIHx8ICh0IGluIF8pIHx8IC9bXHMuXS8udGVzdCh0KSkgdGhyb3cgbmV3IEVycm9yKCJpbGxlZ2FsIHR5cGU6ICIgKyB0KTsKICAgICAgICBfW3RdID0gW107CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBEaXNwYXRjaCQzKF8pOwogICAgfQoKICAgIGZ1bmN0aW9uIERpc3BhdGNoJDMoXykgewogICAgICB0aGlzLl8gPSBfOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVHlwZW5hbWVzJDUodHlwZW5hbWVzLCB0eXBlcykgewogICAgICByZXR1cm4gdHlwZW5hbWVzLnRyaW0oKS5zcGxpdCgvXnxccysvKS5tYXAoZnVuY3Rpb24odCkgewogICAgICAgIHZhciBuYW1lID0gIiIsIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSBuYW1lID0gdC5zbGljZShpICsgMSksIHQgPSB0LnNsaWNlKDAsIGkpOwogICAgICAgIGlmICh0ICYmICF0eXBlcy5oYXNPd25Qcm9wZXJ0eSh0KSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0KTsKICAgICAgICByZXR1cm4ge3R5cGU6IHQsIG5hbWU6IG5hbWV9OwogICAgICB9KTsKICAgIH0KCiAgICBEaXNwYXRjaCQzLnByb3RvdHlwZSA9IGRpc3BhdGNoJDMucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogRGlzcGF0Y2gkMywKICAgICAgb246IGZ1bmN0aW9uKHR5cGVuYW1lLCBjYWxsYmFjaykgewogICAgICAgIHZhciBfID0gdGhpcy5fLAogICAgICAgICAgICBUID0gcGFyc2VUeXBlbmFtZXMkNSh0eXBlbmFtZSArICIiLCBfKSwKICAgICAgICAgICAgdCwKICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICBuID0gVC5sZW5ndGg7CgogICAgICAgIC8vIElmIG5vIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJldHVybiB0aGUgY2FsbGJhY2sgb2YgdGhlIGdpdmVuIHR5cGUgYW5kIG5hbWUuCiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKCh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgJiYgKHQgPSBnZXQkNihfW3RdLCB0eXBlbmFtZS5uYW1lKSkpIHJldHVybiB0OwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gSWYgYSB0eXBlIHdhcyBzcGVjaWZpZWQsIHNldCB0aGUgY2FsbGJhY2sgZm9yIHRoZSBnaXZlbiB0eXBlIGFuZCBuYW1lLgogICAgICAgIC8vIE90aGVyd2lzZSwgaWYgYSBudWxsIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJlbW92ZSBjYWxsYmFja3Mgb2YgdGhlIGdpdmVuIG5hbWUuCiAgICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwgJiYgdHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2FsbGJhY2s6ICIgKyBjYWxsYmFjayk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgX1t0XSA9IHNldCQ4KF9bdF0sIHR5cGVuYW1lLm5hbWUsIGNhbGxiYWNrKTsKICAgICAgICAgIGVsc2UgaWYgKGNhbGxiYWNrID09IG51bGwpIGZvciAodCBpbiBfKSBfW3RdID0gc2V0JDgoX1t0XSwgdHlwZW5hbWUubmFtZSwgbnVsbCk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgY29weTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGNvcHkgPSB7fSwgXyA9IHRoaXMuXzsKICAgICAgICBmb3IgKHZhciB0IGluIF8pIGNvcHlbdF0gPSBfW3RdLnNsaWNlKCk7CiAgICAgICAgcmV0dXJuIG5ldyBEaXNwYXRjaCQzKGNvcHkpOwogICAgICB9LAogICAgICBjYWxsOiBmdW5jdGlvbih0eXBlLCB0aGF0KSB7CiAgICAgICAgaWYgKChuID0gYXJndW1lbnRzLmxlbmd0aCAtIDIpID4gMCkgZm9yICh2YXIgYXJncyA9IG5ldyBBcnJheShuKSwgaSA9IDAsIG4sIHQ7IGkgPCBuOyArK2kpIGFyZ3NbaV0gPSBhcmd1bWVudHNbaSArIDJdOwogICAgICAgIGlmICghdGhpcy5fLmhhc093blByb3BlcnR5KHR5cGUpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHR5cGUpOwogICAgICAgIGZvciAodCA9IHRoaXMuX1t0eXBlXSwgaSA9IDAsIG4gPSB0Lmxlbmd0aDsgaSA8IG47ICsraSkgdFtpXS52YWx1ZS5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfSwKICAgICAgYXBwbHk6IGZ1bmN0aW9uKHR5cGUsIHRoYXQsIGFyZ3MpIHsKICAgICAgICBpZiAoIXRoaXMuXy5oYXNPd25Qcm9wZXJ0eSh0eXBlKSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0eXBlKTsKICAgICAgICBmb3IgKHZhciB0ID0gdGhpcy5fW3R5cGVdLCBpID0gMCwgbiA9IHQubGVuZ3RoOyBpIDwgbjsgKytpKSB0W2ldLnZhbHVlLmFwcGx5KHRoYXQsIGFyZ3MpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGdldCQ2KHR5cGUsIG5hbWUpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0eXBlLmxlbmd0aCwgYzsgaSA8IG47ICsraSkgewogICAgICAgIGlmICgoYyA9IHR5cGVbaV0pLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgIHJldHVybiBjLnZhbHVlOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHNldCQ4KHR5cGUsIG5hbWUsIGNhbGxiYWNrKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHlwZS5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAodHlwZVtpXS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICB0eXBlW2ldID0gbm9vcCQ2LCB0eXBlID0gdHlwZS5zbGljZSgwLCBpKS5jb25jYXQodHlwZS5zbGljZShpICsgMSkpOwogICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsKSB0eXBlLnB1c2goe25hbWU6IG5hbWUsIHZhbHVlOiBjYWxsYmFja30pOwogICAgICByZXR1cm4gdHlwZTsKICAgIH0KCiAgICB2YXIgeGh0bWwkMiA9ICJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sIjsKCiAgICB2YXIgbmFtZXNwYWNlcyQyID0gewogICAgICBzdmc6ICJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIsCiAgICAgIHhodG1sOiB4aHRtbCQyLAogICAgICB4bGluazogImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiLAogICAgICB4bWw6ICJodHRwOi8vd3d3LnczLm9yZy9YTUwvMTk5OC9uYW1lc3BhY2UiLAogICAgICB4bWxuczogImh0dHA6Ly93d3cudzMub3JnLzIwMDAveG1sbnMvIgogICAgfTsKCiAgICBmdW5jdGlvbiBuYW1lc3BhY2UkMihuYW1lKSB7CiAgICAgIHZhciBwcmVmaXggPSBuYW1lICs9ICIiLCBpID0gcHJlZml4LmluZGV4T2YoIjoiKTsKICAgICAgaWYgKGkgPj0gMCAmJiAocHJlZml4ID0gbmFtZS5zbGljZSgwLCBpKSkgIT09ICJ4bWxucyIpIG5hbWUgPSBuYW1lLnNsaWNlKGkgKyAxKTsKICAgICAgcmV0dXJuIG5hbWVzcGFjZXMkMi5oYXNPd25Qcm9wZXJ0eShwcmVmaXgpID8ge3NwYWNlOiBuYW1lc3BhY2VzJDJbcHJlZml4XSwgbG9jYWw6IG5hbWV9IDogbmFtZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdG9ySW5oZXJpdCQyKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBkb2N1bWVudCA9IHRoaXMub3duZXJEb2N1bWVudCwKICAgICAgICAgICAgdXJpID0gdGhpcy5uYW1lc3BhY2VVUkk7CiAgICAgICAgcmV0dXJuIHVyaSA9PT0geGh0bWwkMiAmJiBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQubmFtZXNwYWNlVVJJID09PSB4aHRtbCQyCiAgICAgICAgICAgID8gZG9jdW1lbnQuY3JlYXRlRWxlbWVudChuYW1lKQogICAgICAgICAgICA6IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyh1cmksIG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3JGaXhlZCQyKGZ1bGxuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5vd25lckRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3IkMihuYW1lKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQyKG5hbWUpOwogICAgICByZXR1cm4gKGZ1bGxuYW1lLmxvY2FsCiAgICAgICAgICA/IGNyZWF0b3JGaXhlZCQyCiAgICAgICAgICA6IGNyZWF0b3JJbmhlcml0JDIpKGZ1bGxuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub25lJDQoKSB7fQoKICAgIGZ1bmN0aW9uIHNlbGVjdG9yJDIoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHNlbGVjdG9yID09IG51bGwgPyBub25lJDQgOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2VsZWN0JDIoc2VsZWN0KSB7CiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvciQyKHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBzdWJub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChzdWJub2RlID0gc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSkgewogICAgICAgICAgICBpZiAoIl9fZGF0YV9fIiBpbiBub2RlKSBzdWJub2RlLl9fZGF0YV9fID0gbm9kZS5fX2RhdGFfXzsKICAgICAgICAgICAgc3ViZ3JvdXBbaV0gPSBzdWJub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNChzdWJncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGVtcHR5JDQoKSB7CiAgICAgIHJldHVybiBbXTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3RvckFsbCQyKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBzZWxlY3RvciA9PSBudWxsID8gZW1wdHkkNCA6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5U2VsZWN0b3JBbGwoc2VsZWN0b3IpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zZWxlY3RBbGwkMihzZWxlY3QpIHsKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yQWxsJDIoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IFtdLCBwYXJlbnRzID0gW10sIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHN1Ymdyb3Vwcy5wdXNoKHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSk7CiAgICAgICAgICAgIHBhcmVudHMucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDQoc3ViZ3JvdXBzLCBwYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBtYXRjaGVyJDIoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLm1hdGNoZXMoc2VsZWN0b3IpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9maWx0ZXIkMihtYXRjaCkgewogICAgICBpZiAodHlwZW9mIG1hdGNoICE9PSAiZnVuY3Rpb24iKSBtYXRjaCA9IG1hdGNoZXIkMihtYXRjaCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gW10sIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgbWF0Y2guY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpIHsKICAgICAgICAgICAgc3ViZ3JvdXAucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDQoc3ViZ3JvdXBzLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzcGFyc2UkMih1cGRhdGUpIHsKICAgICAgcmV0dXJuIG5ldyBBcnJheSh1cGRhdGUubGVuZ3RoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZW50ZXIkMigpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNCh0aGlzLl9lbnRlciB8fCB0aGlzLl9ncm91cHMubWFwKHNwYXJzZSQyKSwgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gRW50ZXJOb2RlJDIocGFyZW50LCBkYXR1bSkgewogICAgICB0aGlzLm93bmVyRG9jdW1lbnQgPSBwYXJlbnQub3duZXJEb2N1bWVudDsKICAgICAgdGhpcy5uYW1lc3BhY2VVUkkgPSBwYXJlbnQubmFtZXNwYWNlVVJJOwogICAgICB0aGlzLl9uZXh0ID0gbnVsbDsKICAgICAgdGhpcy5fcGFyZW50ID0gcGFyZW50OwogICAgICB0aGlzLl9fZGF0YV9fID0gZGF0dW07CiAgICB9CgogICAgRW50ZXJOb2RlJDIucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogRW50ZXJOb2RlJDIsCiAgICAgIGFwcGVuZENoaWxkOiBmdW5jdGlvbihjaGlsZCkgeyByZXR1cm4gdGhpcy5fcGFyZW50Lmluc2VydEJlZm9yZShjaGlsZCwgdGhpcy5fbmV4dCk7IH0sCiAgICAgIGluc2VydEJlZm9yZTogZnVuY3Rpb24oY2hpbGQsIG5leHQpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5pbnNlcnRCZWZvcmUoY2hpbGQsIG5leHQpOyB9LAogICAgICBxdWVyeVNlbGVjdG9yOiBmdW5jdGlvbihzZWxlY3RvcikgeyByZXR1cm4gdGhpcy5fcGFyZW50LnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpOyB9LAogICAgICBxdWVyeVNlbGVjdG9yQWxsOiBmdW5jdGlvbihzZWxlY3RvcikgeyByZXR1cm4gdGhpcy5fcGFyZW50LnF1ZXJ5U2VsZWN0b3JBbGwoc2VsZWN0b3IpOyB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGooeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGtleVByZWZpeCQzID0gIiQiOyAvLyBQcm90ZWN0IGFnYWluc3Qga2V5cyBsaWtlIOKAnF9fcHJvdG9fX+KAnS4KCiAgICBmdW5jdGlvbiBiaW5kSW5kZXgkMihwYXJlbnQsIGdyb3VwLCBlbnRlciwgdXBkYXRlLCBleGl0LCBkYXRhKSB7CiAgICAgIHZhciBpID0gMCwKICAgICAgICAgIG5vZGUsCiAgICAgICAgICBncm91cExlbmd0aCA9IGdyb3VwLmxlbmd0aCwKICAgICAgICAgIGRhdGFMZW5ndGggPSBkYXRhLmxlbmd0aDsKCiAgICAgIC8vIFB1dCBhbnkgbm9uLW51bGwgbm9kZXMgdGhhdCBmaXQgaW50byB1cGRhdGUuCiAgICAgIC8vIFB1dCBhbnkgbnVsbCBub2RlcyBpbnRvIGVudGVyLgogICAgICAvLyBQdXQgYW55IHJlbWFpbmluZyBkYXRhIGludG8gZW50ZXIuCiAgICAgIGZvciAoOyBpIDwgZGF0YUxlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgbm9kZS5fX2RhdGFfXyA9IGRhdGFbaV07CiAgICAgICAgICB1cGRhdGVbaV0gPSBub2RlOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlbnRlcltpXSA9IG5ldyBFbnRlck5vZGUkMihwYXJlbnQsIGRhdGFbaV0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gUHV0IGFueSBub24tbnVsbCBub2RlcyB0aGF0IGRvbuKAmXQgZml0IGludG8gZXhpdC4KICAgICAgZm9yICg7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgZXhpdFtpXSA9IG5vZGU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gYmluZEtleSQyKHBhcmVudCwgZ3JvdXAsIGVudGVyLCB1cGRhdGUsIGV4aXQsIGRhdGEsIGtleSkgewogICAgICB2YXIgaSwKICAgICAgICAgIG5vZGUsCiAgICAgICAgICBub2RlQnlLZXlWYWx1ZSA9IHt9LAogICAgICAgICAgZ3JvdXBMZW5ndGggPSBncm91cC5sZW5ndGgsCiAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICBrZXlWYWx1ZXMgPSBuZXcgQXJyYXkoZ3JvdXBMZW5ndGgpLAogICAgICAgICAga2V5VmFsdWU7CgogICAgICAvLyBDb21wdXRlIHRoZSBrZXkgZm9yIGVhY2ggbm9kZS4KICAgICAgLy8gSWYgbXVsdGlwbGUgbm9kZXMgaGF2ZSB0aGUgc2FtZSBrZXksIHRoZSBkdXBsaWNhdGVzIGFyZSBhZGRlZCB0byBleGl0LgogICAgICBmb3IgKGkgPSAwOyBpIDwgZ3JvdXBMZW5ndGg7ICsraSkgewogICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgIGtleVZhbHVlc1tpXSA9IGtleVZhbHVlID0ga2V5UHJlZml4JDMgKyBrZXkuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCk7CiAgICAgICAgICBpZiAoa2V5VmFsdWUgaW4gbm9kZUJ5S2V5VmFsdWUpIHsKICAgICAgICAgICAgZXhpdFtpXSA9IG5vZGU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gQ29tcHV0ZSB0aGUga2V5IGZvciBlYWNoIGRhdHVtLgogICAgICAvLyBJZiB0aGVyZSBhIG5vZGUgYXNzb2NpYXRlZCB3aXRoIHRoaXMga2V5LCBqb2luIGFuZCBhZGQgaXQgdG8gdXBkYXRlLgogICAgICAvLyBJZiB0aGVyZSBpcyBub3QgKG9yIHRoZSBrZXkgaXMgYSBkdXBsaWNhdGUpLCBhZGQgaXQgdG8gZW50ZXIuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBkYXRhTGVuZ3RoOyArK2kpIHsKICAgICAgICBrZXlWYWx1ZSA9IGtleVByZWZpeCQzICsga2V5LmNhbGwocGFyZW50LCBkYXRhW2ldLCBpLCBkYXRhKTsKICAgICAgICBpZiAobm9kZSA9IG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSkgewogICAgICAgICAgdXBkYXRlW2ldID0gbm9kZTsKICAgICAgICAgIG5vZGUuX19kYXRhX18gPSBkYXRhW2ldOwogICAgICAgICAgbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdID0gbnVsbDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZW50ZXJbaV0gPSBuZXcgRW50ZXJOb2RlJDIocGFyZW50LCBkYXRhW2ldKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIEFkZCBhbnkgcmVtYWluaW5nIG5vZGVzIHRoYXQgd2VyZSBub3QgYm91bmQgdG8gZGF0YSB0byBleGl0LgogICAgICBmb3IgKGkgPSAwOyBpIDwgZ3JvdXBMZW5ndGg7ICsraSkgewogICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiAobm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVzW2ldXSA9PT0gbm9kZSkpIHsKICAgICAgICAgIGV4aXRbaV0gPSBub2RlOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kYXRhJDIodmFsdWUsIGtleSkgewogICAgICBpZiAoIXZhbHVlKSB7CiAgICAgICAgZGF0YSA9IG5ldyBBcnJheSh0aGlzLnNpemUoKSksIGogPSAtMTsKICAgICAgICB0aGlzLmVhY2goZnVuY3Rpb24oZCkgeyBkYXRhWysral0gPSBkOyB9KTsKICAgICAgICByZXR1cm4gZGF0YTsKICAgICAgfQoKICAgICAgdmFyIGJpbmQgPSBrZXkgPyBiaW5kS2V5JDIgOiBiaW5kSW5kZXgkMiwKICAgICAgICAgIHBhcmVudHMgPSB0aGlzLl9wYXJlbnRzLAogICAgICAgICAgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzOwoKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdmFsdWUgPSBjb25zdGFudCRqKHZhbHVlKTsKCiAgICAgIGZvciAodmFyIG0gPSBncm91cHMubGVuZ3RoLCB1cGRhdGUgPSBuZXcgQXJyYXkobSksIGVudGVyID0gbmV3IEFycmF5KG0pLCBleGl0ID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIHZhciBwYXJlbnQgPSBwYXJlbnRzW2pdLAogICAgICAgICAgICBncm91cCA9IGdyb3Vwc1tqXSwKICAgICAgICAgICAgZ3JvdXBMZW5ndGggPSBncm91cC5sZW5ndGgsCiAgICAgICAgICAgIGRhdGEgPSB2YWx1ZS5jYWxsKHBhcmVudCwgcGFyZW50ICYmIHBhcmVudC5fX2RhdGFfXywgaiwgcGFyZW50cyksCiAgICAgICAgICAgIGRhdGFMZW5ndGggPSBkYXRhLmxlbmd0aCwKICAgICAgICAgICAgZW50ZXJHcm91cCA9IGVudGVyW2pdID0gbmV3IEFycmF5KGRhdGFMZW5ndGgpLAogICAgICAgICAgICB1cGRhdGVHcm91cCA9IHVwZGF0ZVtqXSA9IG5ldyBBcnJheShkYXRhTGVuZ3RoKSwKICAgICAgICAgICAgZXhpdEdyb3VwID0gZXhpdFtqXSA9IG5ldyBBcnJheShncm91cExlbmd0aCk7CgogICAgICAgIGJpbmQocGFyZW50LCBncm91cCwgZW50ZXJHcm91cCwgdXBkYXRlR3JvdXAsIGV4aXRHcm91cCwgZGF0YSwga2V5KTsKCiAgICAgICAgLy8gTm93IGNvbm5lY3QgdGhlIGVudGVyIG5vZGVzIHRvIHRoZWlyIGZvbGxvd2luZyB1cGRhdGUgbm9kZSwgc3VjaCB0aGF0CiAgICAgICAgLy8gYXBwZW5kQ2hpbGQgY2FuIGluc2VydCB0aGUgbWF0ZXJpYWxpemVkIGVudGVyIG5vZGUgYmVmb3JlIHRoaXMgbm9kZSwKICAgICAgICAvLyByYXRoZXIgdGhhbiBhdCB0aGUgZW5kIG9mIHRoZSBwYXJlbnQgbm9kZS4KICAgICAgICBmb3IgKHZhciBpMCA9IDAsIGkxID0gMCwgcHJldmlvdXMsIG5leHQ7IGkwIDwgZGF0YUxlbmd0aDsgKytpMCkgewogICAgICAgICAgaWYgKHByZXZpb3VzID0gZW50ZXJHcm91cFtpMF0pIHsKICAgICAgICAgICAgaWYgKGkwID49IGkxKSBpMSA9IGkwICsgMTsKICAgICAgICAgICAgd2hpbGUgKCEobmV4dCA9IHVwZGF0ZUdyb3VwW2kxXSkgJiYgKytpMSA8IGRhdGFMZW5ndGgpOwogICAgICAgICAgICBwcmV2aW91cy5fbmV4dCA9IG5leHQgfHwgbnVsbDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHVwZGF0ZSA9IG5ldyBTZWxlY3Rpb24kNCh1cGRhdGUsIHBhcmVudHMpOwogICAgICB1cGRhdGUuX2VudGVyID0gZW50ZXI7CiAgICAgIHVwZGF0ZS5fZXhpdCA9IGV4aXQ7CiAgICAgIHJldHVybiB1cGRhdGU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2V4aXQkMigpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNCh0aGlzLl9leGl0IHx8IHRoaXMuX2dyb3Vwcy5tYXAoc3BhcnNlJDIpLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fam9pbiQyKG9uZW50ZXIsIG9udXBkYXRlLCBvbmV4aXQpIHsKICAgICAgdmFyIGVudGVyID0gdGhpcy5lbnRlcigpLCB1cGRhdGUgPSB0aGlzLCBleGl0ID0gdGhpcy5leGl0KCk7CiAgICAgIGVudGVyID0gdHlwZW9mIG9uZW50ZXIgPT09ICJmdW5jdGlvbiIgPyBvbmVudGVyKGVudGVyKSA6IGVudGVyLmFwcGVuZChvbmVudGVyICsgIiIpOwogICAgICBpZiAob251cGRhdGUgIT0gbnVsbCkgdXBkYXRlID0gb251cGRhdGUodXBkYXRlKTsKICAgICAgaWYgKG9uZXhpdCA9PSBudWxsKSBleGl0LnJlbW92ZSgpOyBlbHNlIG9uZXhpdChleGl0KTsKICAgICAgcmV0dXJuIGVudGVyICYmIHVwZGF0ZSA/IGVudGVyLm1lcmdlKHVwZGF0ZSkub3JkZXIoKSA6IHVwZGF0ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbWVyZ2UkMihzZWxlY3Rpb24pIHsKCiAgICAgIGZvciAodmFyIGdyb3VwczAgPSB0aGlzLl9ncm91cHMsIGdyb3VwczEgPSBzZWxlY3Rpb24uX2dyb3VwcywgbTAgPSBncm91cHMwLmxlbmd0aCwgbTEgPSBncm91cHMxLmxlbmd0aCwgbSA9IE1hdGgubWluKG0wLCBtMSksIG1lcmdlcyA9IG5ldyBBcnJheShtMCksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAwID0gZ3JvdXBzMFtqXSwgZ3JvdXAxID0gZ3JvdXBzMVtqXSwgbiA9IGdyb3VwMC5sZW5ndGgsIG1lcmdlID0gbWVyZ2VzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cDBbaV0gfHwgZ3JvdXAxW2ldKSB7CiAgICAgICAgICAgIG1lcmdlW2ldID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZvciAoOyBqIDwgbTA7ICsraikgewogICAgICAgIG1lcmdlc1tqXSA9IGdyb3VwczBbal07CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDQobWVyZ2VzLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fb3JkZXIkMigpIHsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgaiA9IC0xLCBtID0gZ3JvdXBzLmxlbmd0aDsgKytqIDwgbTspIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IGdyb3VwLmxlbmd0aCAtIDEsIG5leHQgPSBncm91cFtpXSwgbm9kZTsgLS1pID49IDA7KSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIGlmIChuZXh0ICYmIG5vZGUuY29tcGFyZURvY3VtZW50UG9zaXRpb24obmV4dCkgXiA0KSBuZXh0LnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKG5vZGUsIG5leHQpOwogICAgICAgICAgICBuZXh0ID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zb3J0JDIoY29tcGFyZSkgewogICAgICBpZiAoIWNvbXBhcmUpIGNvbXBhcmUgPSBhc2NlbmRpbmckNzsKCiAgICAgIGZ1bmN0aW9uIGNvbXBhcmVOb2RlKGEsIGIpIHsKICAgICAgICByZXR1cm4gYSAmJiBiID8gY29tcGFyZShhLl9fZGF0YV9fLCBiLl9fZGF0YV9fKSA6ICFhIC0gIWI7CiAgICAgIH0KCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHNvcnRncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHNvcnRncm91cCA9IHNvcnRncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHNvcnRncm91cFtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHNvcnRncm91cC5zb3J0KGNvbXBhcmVOb2RlKTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNChzb3J0Z3JvdXBzLCB0aGlzLl9wYXJlbnRzKS5vcmRlcigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyQ3KGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPCBiID8gLTEgOiBhID4gYiA/IDEgOiBhID49IGIgPyAwIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jYWxsJDIoKSB7CiAgICAgIHZhciBjYWxsYmFjayA9IGFyZ3VtZW50c1swXTsKICAgICAgYXJndW1lbnRzWzBdID0gdGhpczsKICAgICAgY2FsbGJhY2suYXBwbHkobnVsbCwgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX25vZGVzJDIoKSB7CiAgICAgIHZhciBub2RlcyA9IG5ldyBBcnJheSh0aGlzLnNpemUoKSksIGkgPSAtMTsKICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKCkgeyBub2Rlc1srK2ldID0gdGhpczsgfSk7CiAgICAgIHJldHVybiBub2RlczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbm9kZSQyKCkgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gMCwgbSA9IGdyb3Vwcy5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IDAsIG4gPSBncm91cC5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHZhciBub2RlID0gZ3JvdXBbaV07CiAgICAgICAgICBpZiAobm9kZSkgcmV0dXJuIG5vZGU7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2l6ZSQyKCkgewogICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgIHRoaXMuZWFjaChmdW5jdGlvbigpIHsgKytzaXplOyB9KTsKICAgICAgcmV0dXJuIHNpemU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VtcHR5JDIoKSB7CiAgICAgIHJldHVybiAhdGhpcy5ub2RlKCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VhY2gkMihjYWxsYmFjaykgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gMCwgbSA9IGdyb3Vwcy5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IDAsIG4gPSBncm91cC5sZW5ndGgsIG5vZGU7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIGNhbGxiYWNrLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZSQ0KG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJSZW1vdmVOUyQ0KGZ1bGxuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckNvbnN0YW50JDQobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIHZhbHVlKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnROUyQ0KGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwsIHZhbHVlKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb24kNChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgIGVsc2UgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgdik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckZ1bmN0aW9uTlMkNChmdWxsbmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgICAgZWxzZSB0aGlzLnNldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCwgdik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2F0dHIkMihuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UkMihuYW1lKTsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBub2RlID0gdGhpcy5ub2RlKCk7CiAgICAgICAgcmV0dXJuIGZ1bGxuYW1lLmxvY2FsCiAgICAgICAgICAgID8gbm9kZS5nZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpCiAgICAgICAgICAgIDogbm9kZS5nZXRBdHRyaWJ1dGUoZnVsbG5hbWUpOwogICAgICB9CgogICAgICByZXR1cm4gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJSZW1vdmVOUyQ0IDogYXR0clJlbW92ZSQ0KSA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckZ1bmN0aW9uTlMkNCA6IGF0dHJGdW5jdGlvbiQ0KQogICAgICAgICAgOiAoZnVsbG5hbWUubG9jYWwgPyBhdHRyQ29uc3RhbnROUyQ0IDogYXR0ckNvbnN0YW50JDQpKSkoZnVsbG5hbWUsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFZpZXckMihub2RlKSB7CiAgICAgIHJldHVybiAobm9kZS5vd25lckRvY3VtZW50ICYmIG5vZGUub3duZXJEb2N1bWVudC5kZWZhdWx0VmlldykgLy8gbm9kZSBpcyBhIE5vZGUKICAgICAgICAgIHx8IChub2RlLmRvY3VtZW50ICYmIG5vZGUpIC8vIG5vZGUgaXMgYSBXaW5kb3cKICAgICAgICAgIHx8IG5vZGUuZGVmYXVsdFZpZXc7IC8vIG5vZGUgaXMgYSBEb2N1bWVudAogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlUmVtb3ZlJDQobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUNvbnN0YW50JDQobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLnNldFByb3BlcnR5KG5hbWUsIHZhbHVlLCBwcmlvcml0eSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVGdW5jdGlvbiQ0KG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSk7CiAgICAgICAgZWxzZSB0aGlzLnN0eWxlLnNldFByb3BlcnR5KG5hbWUsIHYsIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc3R5bGUkMihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPiAxCiAgICAgICAgICA/IHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgICAgPyBzdHlsZVJlbW92ZSQ0IDogdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgICA/IHN0eWxlRnVuY3Rpb24kNAogICAgICAgICAgICAgICAgOiBzdHlsZUNvbnN0YW50JDQpKG5hbWUsIHZhbHVlLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSkpCiAgICAgICAgICA6IHN0eWxlVmFsdWUkMih0aGlzLm5vZGUoKSwgbmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVWYWx1ZSQyKG5vZGUsIG5hbWUpIHsKICAgICAgcmV0dXJuIG5vZGUuc3R5bGUuZ2V0UHJvcGVydHlWYWx1ZShuYW1lKQogICAgICAgICAgfHwgZGVmYXVsdFZpZXckMihub2RlKS5nZXRDb21wdXRlZFN0eWxlKG5vZGUsIG51bGwpLmdldFByb3BlcnR5VmFsdWUobmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlSZW1vdmUkMihuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBkZWxldGUgdGhpc1tuYW1lXTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eUNvbnN0YW50JDIobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXNbbmFtZV0gPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eUZ1bmN0aW9uJDIobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSBkZWxldGUgdGhpc1tuYW1lXTsKICAgICAgICBlbHNlIHRoaXNbbmFtZV0gPSB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9wcm9wZXJ0eSQyKG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMQogICAgICAgICAgPyB0aGlzLmVhY2goKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IHByb3BlcnR5UmVtb3ZlJDIgOiB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IHByb3BlcnR5RnVuY3Rpb24kMgogICAgICAgICAgICAgIDogcHJvcGVydHlDb25zdGFudCQyKShuYW1lLCB2YWx1ZSkpCiAgICAgICAgICA6IHRoaXMubm9kZSgpW25hbWVdOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzQXJyYXkkMihzdHJpbmcpIHsKICAgICAgcmV0dXJuIHN0cmluZy50cmltKCkuc3BsaXQoL158XHMrLyk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NMaXN0JDIobm9kZSkgewogICAgICByZXR1cm4gbm9kZS5jbGFzc0xpc3QgfHwgbmV3IENsYXNzTGlzdCQyKG5vZGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIENsYXNzTGlzdCQyKG5vZGUpIHsKICAgICAgdGhpcy5fbm9kZSA9IG5vZGU7CiAgICAgIHRoaXMuX25hbWVzID0gY2xhc3NBcnJheSQyKG5vZGUuZ2V0QXR0cmlidXRlKCJjbGFzcyIpIHx8ICIiKTsKICAgIH0KCiAgICBDbGFzc0xpc3QkMi5wcm90b3R5cGUgPSB7CiAgICAgIGFkZDogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHZhciBpID0gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKTsKICAgICAgICBpZiAoaSA8IDApIHsKICAgICAgICAgIHRoaXMuX25hbWVzLnB1c2gobmFtZSk7CiAgICAgICAgICB0aGlzLl9ub2RlLnNldEF0dHJpYnV0ZSgiY2xhc3MiLCB0aGlzLl9uYW1lcy5qb2luKCIgIikpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgcmVtb3ZlOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpOwogICAgICAgIGlmIChpID49IDApIHsKICAgICAgICAgIHRoaXMuX25hbWVzLnNwbGljZShpLCAxKTsKICAgICAgICAgIHRoaXMuX25vZGUuc2V0QXR0cmlidXRlKCJjbGFzcyIsIHRoaXMuX25hbWVzLmpvaW4oIiAiKSk7CiAgICAgICAgfQogICAgICB9LAogICAgICBjb250YWluczogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHJldHVybiB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpID49IDA7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY2xhc3NlZEFkZCQyKG5vZGUsIG5hbWVzKSB7CiAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0JDIobm9kZSksIGkgPSAtMSwgbiA9IG5hbWVzLmxlbmd0aDsKICAgICAgd2hpbGUgKCsraSA8IG4pIGxpc3QuYWRkKG5hbWVzW2ldKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkUmVtb3ZlJDIobm9kZSwgbmFtZXMpIHsKICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3QkMihub2RlKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbGlzdC5yZW1vdmUobmFtZXNbaV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRUcnVlJDIobmFtZXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGNsYXNzZWRBZGQkMih0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZEZhbHNlJDIobmFtZXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGNsYXNzZWRSZW1vdmUkMih0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZEZ1bmN0aW9uJDIobmFtZXMsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAodmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKSA/IGNsYXNzZWRBZGQkMiA6IGNsYXNzZWRSZW1vdmUkMikodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbGFzc2VkJDIobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIG5hbWVzID0gY2xhc3NBcnJheSQyKG5hbWUgKyAiIik7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgbGlzdCA9IGNsYXNzTGlzdCQyKHRoaXMubm9kZSgpKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoIWxpc3QuY29udGFpbnMobmFtZXNbaV0pKSByZXR1cm4gZmFsc2U7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyBjbGFzc2VkRnVuY3Rpb24kMiA6IHZhbHVlCiAgICAgICAgICA/IGNsYXNzZWRUcnVlJDIKICAgICAgICAgIDogY2xhc3NlZEZhbHNlJDIpKG5hbWVzLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRSZW1vdmUkMigpIHsKICAgICAgdGhpcy50ZXh0Q29udGVudCA9ICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRDb25zdGFudCQ0KHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dEZ1bmN0aW9uJDQodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdiA9PSBudWxsID8gIiIgOiB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl90ZXh0JDIodmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IHRleHRSZW1vdmUkMiA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IHRleHRGdW5jdGlvbiQ0CiAgICAgICAgICAgICAgOiB0ZXh0Q29uc3RhbnQkNCkodmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS50ZXh0Q29udGVudDsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sUmVtb3ZlJDIoKSB7CiAgICAgIHRoaXMuaW5uZXJIVE1MID0gIiI7CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbENvbnN0YW50JDIodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuaW5uZXJIVE1MID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbEZ1bmN0aW9uJDIodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLmlubmVySFRNTCA9IHYgPT0gbnVsbCA/ICIiIDogdjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25faHRtbCQyKHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyBodG1sUmVtb3ZlJDIgOiAodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBodG1sRnVuY3Rpb24kMgogICAgICAgICAgICAgIDogaHRtbENvbnN0YW50JDIpKHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKCkuaW5uZXJIVE1MOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhaXNlJDIoKSB7CiAgICAgIGlmICh0aGlzLm5leHRTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuYXBwZW5kQ2hpbGQodGhpcyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3JhaXNlJDIoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2gocmFpc2UkMik7CiAgICB9CgogICAgZnVuY3Rpb24gbG93ZXIkMigpIHsKICAgICAgaWYgKHRoaXMucHJldmlvdXNTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKHRoaXMsIHRoaXMucGFyZW50Tm9kZS5maXJzdENoaWxkKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbG93ZXIkMigpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChsb3dlciQyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fYXBwZW5kJDIobmFtZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvciQyKG5hbWUpOwogICAgICByZXR1cm4gdGhpcy5zZWxlY3QoZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuYXBwZW5kQ2hpbGQoY3JlYXRlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudE51bGwkMigpIHsKICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2luc2VydCQyKG5hbWUsIGJlZm9yZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvciQyKG5hbWUpLAogICAgICAgICAgc2VsZWN0ID0gYmVmb3JlID09IG51bGwgPyBjb25zdGFudE51bGwkMiA6IHR5cGVvZiBiZWZvcmUgPT09ICJmdW5jdGlvbiIgPyBiZWZvcmUgOiBzZWxlY3RvciQyKGJlZm9yZSk7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5pbnNlcnRCZWZvcmUoY3JlYXRlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksIHNlbGVjdC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIHx8IG51bGwpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmUkMigpIHsKICAgICAgdmFyIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgaWYgKHBhcmVudCkgcGFyZW50LnJlbW92ZUNoaWxkKHRoaXMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9yZW1vdmUkMigpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChyZW1vdmUkMik7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Nsb25lU2hhbGxvdyQyKCkgewogICAgICB2YXIgY2xvbmUgPSB0aGlzLmNsb25lTm9kZShmYWxzZSksIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgcmV0dXJuIHBhcmVudCA/IHBhcmVudC5pbnNlcnRCZWZvcmUoY2xvbmUsIHRoaXMubmV4dFNpYmxpbmcpIDogY2xvbmU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Nsb25lRGVlcCQyKCkgewogICAgICB2YXIgY2xvbmUgPSB0aGlzLmNsb25lTm9kZSh0cnVlKSwgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICByZXR1cm4gcGFyZW50ID8gcGFyZW50Lmluc2VydEJlZm9yZShjbG9uZSwgdGhpcy5uZXh0U2libGluZykgOiBjbG9uZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xvbmUkMihkZWVwKSB7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChkZWVwID8gc2VsZWN0aW9uX2Nsb25lRGVlcCQyIDogc2VsZWN0aW9uX2Nsb25lU2hhbGxvdyQyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGF0dW0kMih2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLnByb3BlcnR5KCJfX2RhdGFfXyIsIHZhbHVlKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS5fX2RhdGFfXzsKICAgIH0KCiAgICB2YXIgZmlsdGVyRXZlbnRzJDIgPSB7fTsKCiAgICB2YXIgZXZlbnQkMiA9IG51bGw7CgogICAgaWYgKHR5cGVvZiBkb2N1bWVudCAhPT0gInVuZGVmaW5lZCIpIHsKICAgICAgdmFyIGVsZW1lbnQkMiA9IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudDsKICAgICAgaWYgKCEoIm9ubW91c2VlbnRlciIgaW4gZWxlbWVudCQyKSkgewogICAgICAgIGZpbHRlckV2ZW50cyQyID0ge21vdXNlZW50ZXI6ICJtb3VzZW92ZXIiLCBtb3VzZWxlYXZlOiAibW91c2VvdXQifTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGZpbHRlckNvbnRleHRMaXN0ZW5lciQyKGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApIHsKICAgICAgbGlzdGVuZXIgPSBjb250ZXh0TGlzdGVuZXIkMihsaXN0ZW5lciwgaW5kZXgsIGdyb3VwKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgICAgdmFyIHJlbGF0ZWQgPSBldmVudC5yZWxhdGVkVGFyZ2V0OwogICAgICAgIGlmICghcmVsYXRlZCB8fCAocmVsYXRlZCAhPT0gdGhpcyAmJiAhKHJlbGF0ZWQuY29tcGFyZURvY3VtZW50UG9zaXRpb24odGhpcykgJiA4KSkpIHsKICAgICAgICAgIGxpc3RlbmVyLmNhbGwodGhpcywgZXZlbnQpOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb250ZXh0TGlzdGVuZXIkMihsaXN0ZW5lciwgaW5kZXgsIGdyb3VwKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihldmVudDEpIHsKICAgICAgICB2YXIgZXZlbnQwID0gZXZlbnQkMjsgLy8gRXZlbnRzIGNhbiBiZSByZWVudHJhbnQgKGUuZy4sIGZvY3VzKS4KICAgICAgICBldmVudCQyID0gZXZlbnQxOwogICAgICAgIHRyeSB7CiAgICAgICAgICBsaXN0ZW5lci5jYWxsKHRoaXMsIHRoaXMuX19kYXRhX18sIGluZGV4LCBncm91cCk7CiAgICAgICAgfSBmaW5hbGx5IHsKICAgICAgICAgIGV2ZW50JDIgPSBldmVudDA7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVHlwZW5hbWVzJDYodHlwZW5hbWVzKSB7CiAgICAgIHJldHVybiB0eXBlbmFtZXMudHJpbSgpLnNwbGl0KC9efFxzKy8pLm1hcChmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIG5hbWUgPSAiIiwgaSA9IHQuaW5kZXhPZigiLiIpOwogICAgICAgIGlmIChpID49IDApIG5hbWUgPSB0LnNsaWNlKGkgKyAxKSwgdCA9IHQuc2xpY2UoMCwgaSk7CiAgICAgICAgcmV0dXJuIHt0eXBlOiB0LCBuYW1lOiBuYW1lfTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gb25SZW1vdmUkMih0eXBlbmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIG9uID0gdGhpcy5fX29uOwogICAgICAgIGlmICghb24pIHJldHVybjsKICAgICAgICBmb3IgKHZhciBqID0gMCwgaSA9IC0xLCBtID0gb24ubGVuZ3RoLCBvOyBqIDwgbTsgKytqKSB7CiAgICAgICAgICBpZiAobyA9IG9uW2pdLCAoIXR5cGVuYW1lLnR5cGUgfHwgby50eXBlID09PSB0eXBlbmFtZS50eXBlKSAmJiBvLm5hbWUgPT09IHR5cGVuYW1lLm5hbWUpIHsKICAgICAgICAgICAgdGhpcy5yZW1vdmVFdmVudExpc3RlbmVyKG8udHlwZSwgby5saXN0ZW5lciwgby5jYXB0dXJlKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG9uWysraV0gPSBvOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoKytpKSBvbi5sZW5ndGggPSBpOwogICAgICAgIGVsc2UgZGVsZXRlIHRoaXMuX19vbjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBvbkFkZCQyKHR5cGVuYW1lLCB2YWx1ZSwgY2FwdHVyZSkgewogICAgICB2YXIgd3JhcCA9IGZpbHRlckV2ZW50cyQyLmhhc093blByb3BlcnR5KHR5cGVuYW1lLnR5cGUpID8gZmlsdGVyQ29udGV4dExpc3RlbmVyJDIgOiBjb250ZXh0TGlzdGVuZXIkMjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQsIGksIGdyb3VwKSB7CiAgICAgICAgdmFyIG9uID0gdGhpcy5fX29uLCBvLCBsaXN0ZW5lciA9IHdyYXAodmFsdWUsIGksIGdyb3VwKTsKICAgICAgICBpZiAob24pIGZvciAodmFyIGogPSAwLCBtID0gb24ubGVuZ3RoOyBqIDwgbTsgKytqKSB7CiAgICAgICAgICBpZiAoKG8gPSBvbltqXSkudHlwZSA9PT0gdHlwZW5hbWUudHlwZSAmJiBvLm5hbWUgPT09IHR5cGVuYW1lLm5hbWUpIHsKICAgICAgICAgICAgdGhpcy5yZW1vdmVFdmVudExpc3RlbmVyKG8udHlwZSwgby5saXN0ZW5lciwgby5jYXB0dXJlKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKG8udHlwZSwgby5saXN0ZW5lciA9IGxpc3RlbmVyLCBvLmNhcHR1cmUgPSBjYXB0dXJlKTsKICAgICAgICAgICAgby52YWx1ZSA9IHZhbHVlOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcih0eXBlbmFtZS50eXBlLCBsaXN0ZW5lciwgY2FwdHVyZSk7CiAgICAgICAgbyA9IHt0eXBlOiB0eXBlbmFtZS50eXBlLCBuYW1lOiB0eXBlbmFtZS5uYW1lLCB2YWx1ZTogdmFsdWUsIGxpc3RlbmVyOiBsaXN0ZW5lciwgY2FwdHVyZTogY2FwdHVyZX07CiAgICAgICAgaWYgKCFvbikgdGhpcy5fX29uID0gW29dOwogICAgICAgIGVsc2Ugb24ucHVzaChvKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fb24kMih0eXBlbmFtZSwgdmFsdWUsIGNhcHR1cmUpIHsKICAgICAgdmFyIHR5cGVuYW1lcyA9IHBhcnNlVHlwZW5hbWVzJDYodHlwZW5hbWUgKyAiIiksIGksIG4gPSB0eXBlbmFtZXMubGVuZ3RoLCB0OwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIG9uID0gdGhpcy5ub2RlKCkuX19vbjsKICAgICAgICBpZiAob24pIGZvciAodmFyIGogPSAwLCBtID0gb24ubGVuZ3RoLCBvOyBqIDwgbTsgKytqKSB7CiAgICAgICAgICBmb3IgKGkgPSAwLCBvID0gb25bal07IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgaWYgKCh0ID0gdHlwZW5hbWVzW2ldKS50eXBlID09PSBvLnR5cGUgJiYgdC5uYW1lID09PSBvLm5hbWUpIHsKICAgICAgICAgICAgICByZXR1cm4gby52YWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm47CiAgICAgIH0KCiAgICAgIG9uID0gdmFsdWUgPyBvbkFkZCQyIDogb25SZW1vdmUkMjsKICAgICAgaWYgKGNhcHR1cmUgPT0gbnVsbCkgY2FwdHVyZSA9IGZhbHNlOwogICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB0aGlzLmVhY2gob24odHlwZW5hbWVzW2ldLCB2YWx1ZSwgY2FwdHVyZSkpOwogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBjdXN0b21FdmVudCQyKGV2ZW50MSwgbGlzdGVuZXIsIHRoYXQsIGFyZ3MpIHsKICAgICAgdmFyIGV2ZW50MCA9IGV2ZW50JDI7CiAgICAgIGV2ZW50MS5zb3VyY2VFdmVudCA9IGV2ZW50JDI7CiAgICAgIGV2ZW50JDIgPSBldmVudDE7CiAgICAgIHRyeSB7CiAgICAgICAgcmV0dXJuIGxpc3RlbmVyLmFwcGx5KHRoYXQsIGFyZ3MpOwogICAgICB9IGZpbmFsbHkgewogICAgICAgIGV2ZW50JDIgPSBldmVudDA7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBkaXNwYXRjaEV2ZW50JDIobm9kZSwgdHlwZSwgcGFyYW1zKSB7CiAgICAgIHZhciB3aW5kb3cgPSBkZWZhdWx0VmlldyQyKG5vZGUpLAogICAgICAgICAgZXZlbnQgPSB3aW5kb3cuQ3VzdG9tRXZlbnQ7CgogICAgICBpZiAodHlwZW9mIGV2ZW50ID09PSAiZnVuY3Rpb24iKSB7CiAgICAgICAgZXZlbnQgPSBuZXcgZXZlbnQodHlwZSwgcGFyYW1zKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBldmVudCA9IHdpbmRvdy5kb2N1bWVudC5jcmVhdGVFdmVudCgiRXZlbnQiKTsKICAgICAgICBpZiAocGFyYW1zKSBldmVudC5pbml0RXZlbnQodHlwZSwgcGFyYW1zLmJ1YmJsZXMsIHBhcmFtcy5jYW5jZWxhYmxlKSwgZXZlbnQuZGV0YWlsID0gcGFyYW1zLmRldGFpbDsKICAgICAgICBlbHNlIGV2ZW50LmluaXRFdmVudCh0eXBlLCBmYWxzZSwgZmFsc2UpOwogICAgICB9CgogICAgICBub2RlLmRpc3BhdGNoRXZlbnQoZXZlbnQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoQ29uc3RhbnQkMih0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkaXNwYXRjaEV2ZW50JDIodGhpcywgdHlwZSwgcGFyYW1zKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXNwYXRjaEZ1bmN0aW9uJDIodHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gZGlzcGF0Y2hFdmVudCQyKHRoaXMsIHR5cGUsIHBhcmFtcy5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGlzcGF0Y2gkMih0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaCgodHlwZW9mIHBhcmFtcyA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyBkaXNwYXRjaEZ1bmN0aW9uJDIKICAgICAgICAgIDogZGlzcGF0Y2hDb25zdGFudCQyKSh0eXBlLCBwYXJhbXMpKTsKICAgIH0KCiAgICB2YXIgcm9vdCQ0ID0gW251bGxdOwoKICAgIGZ1bmN0aW9uIFNlbGVjdGlvbiQ0KGdyb3VwcywgcGFyZW50cykgewogICAgICB0aGlzLl9ncm91cHMgPSBncm91cHM7CiAgICAgIHRoaXMuX3BhcmVudHMgPSBwYXJlbnRzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbiQyKCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ0KFtbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XV0sIHJvb3QkNCk7CiAgICB9CgogICAgU2VsZWN0aW9uJDQucHJvdG90eXBlID0gc2VsZWN0aW9uJDIucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogU2VsZWN0aW9uJDQsCiAgICAgIHNlbGVjdDogc2VsZWN0aW9uX3NlbGVjdCQyLAogICAgICBzZWxlY3RBbGw6IHNlbGVjdGlvbl9zZWxlY3RBbGwkMiwKICAgICAgZmlsdGVyOiBzZWxlY3Rpb25fZmlsdGVyJDIsCiAgICAgIGRhdGE6IHNlbGVjdGlvbl9kYXRhJDIsCiAgICAgIGVudGVyOiBzZWxlY3Rpb25fZW50ZXIkMiwKICAgICAgZXhpdDogc2VsZWN0aW9uX2V4aXQkMiwKICAgICAgam9pbjogc2VsZWN0aW9uX2pvaW4kMiwKICAgICAgbWVyZ2U6IHNlbGVjdGlvbl9tZXJnZSQyLAogICAgICBvcmRlcjogc2VsZWN0aW9uX29yZGVyJDIsCiAgICAgIHNvcnQ6IHNlbGVjdGlvbl9zb3J0JDIsCiAgICAgIGNhbGw6IHNlbGVjdGlvbl9jYWxsJDIsCiAgICAgIG5vZGVzOiBzZWxlY3Rpb25fbm9kZXMkMiwKICAgICAgbm9kZTogc2VsZWN0aW9uX25vZGUkMiwKICAgICAgc2l6ZTogc2VsZWN0aW9uX3NpemUkMiwKICAgICAgZW1wdHk6IHNlbGVjdGlvbl9lbXB0eSQyLAogICAgICBlYWNoOiBzZWxlY3Rpb25fZWFjaCQyLAogICAgICBhdHRyOiBzZWxlY3Rpb25fYXR0ciQyLAogICAgICBzdHlsZTogc2VsZWN0aW9uX3N0eWxlJDIsCiAgICAgIHByb3BlcnR5OiBzZWxlY3Rpb25fcHJvcGVydHkkMiwKICAgICAgY2xhc3NlZDogc2VsZWN0aW9uX2NsYXNzZWQkMiwKICAgICAgdGV4dDogc2VsZWN0aW9uX3RleHQkMiwKICAgICAgaHRtbDogc2VsZWN0aW9uX2h0bWwkMiwKICAgICAgcmFpc2U6IHNlbGVjdGlvbl9yYWlzZSQyLAogICAgICBsb3dlcjogc2VsZWN0aW9uX2xvd2VyJDIsCiAgICAgIGFwcGVuZDogc2VsZWN0aW9uX2FwcGVuZCQyLAogICAgICBpbnNlcnQ6IHNlbGVjdGlvbl9pbnNlcnQkMiwKICAgICAgcmVtb3ZlOiBzZWxlY3Rpb25fcmVtb3ZlJDIsCiAgICAgIGNsb25lOiBzZWxlY3Rpb25fY2xvbmUkMiwKICAgICAgZGF0dW06IHNlbGVjdGlvbl9kYXR1bSQyLAogICAgICBvbjogc2VsZWN0aW9uX29uJDIsCiAgICAgIGRpc3BhdGNoOiBzZWxlY3Rpb25fZGlzcGF0Y2gkMgogICAgfTsKCiAgICBmdW5jdGlvbiBzZWxlY3QkMihzZWxlY3RvcikgewogICAgICByZXR1cm4gdHlwZW9mIHNlbGVjdG9yID09PSAic3RyaW5nIgogICAgICAgICAgPyBuZXcgU2VsZWN0aW9uJDQoW1tkb2N1bWVudC5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKV1dLCBbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XSkKICAgICAgICAgIDogbmV3IFNlbGVjdGlvbiQ0KFtbc2VsZWN0b3JdXSwgcm9vdCQ0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzb3VyY2VFdmVudCQyKCkgewogICAgICB2YXIgY3VycmVudCA9IGV2ZW50JDIsIHNvdXJjZTsKICAgICAgd2hpbGUgKHNvdXJjZSA9IGN1cnJlbnQuc291cmNlRXZlbnQpIGN1cnJlbnQgPSBzb3VyY2U7CiAgICAgIHJldHVybiBjdXJyZW50OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50JDcobm9kZSwgZXZlbnQpIHsKICAgICAgdmFyIHN2ZyA9IG5vZGUub3duZXJTVkdFbGVtZW50IHx8IG5vZGU7CgogICAgICBpZiAoc3ZnLmNyZWF0ZVNWR1BvaW50KSB7CiAgICAgICAgdmFyIHBvaW50ID0gc3ZnLmNyZWF0ZVNWR1BvaW50KCk7CiAgICAgICAgcG9pbnQueCA9IGV2ZW50LmNsaWVudFgsIHBvaW50LnkgPSBldmVudC5jbGllbnRZOwogICAgICAgIHBvaW50ID0gcG9pbnQubWF0cml4VHJhbnNmb3JtKG5vZGUuZ2V0U2NyZWVuQ1RNKCkuaW52ZXJzZSgpKTsKICAgICAgICByZXR1cm4gW3BvaW50LngsIHBvaW50LnldOwogICAgICB9CgogICAgICB2YXIgcmVjdCA9IG5vZGUuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgIHJldHVybiBbZXZlbnQuY2xpZW50WCAtIHJlY3QubGVmdCAtIG5vZGUuY2xpZW50TGVmdCwgZXZlbnQuY2xpZW50WSAtIHJlY3QudG9wIC0gbm9kZS5jbGllbnRUb3BdOwogICAgfQoKICAgIGZ1bmN0aW9uIG1vdXNlJDIobm9kZSkgewogICAgICB2YXIgZXZlbnQgPSBzb3VyY2VFdmVudCQyKCk7CiAgICAgIGlmIChldmVudC5jaGFuZ2VkVG91Y2hlcykgZXZlbnQgPSBldmVudC5jaGFuZ2VkVG91Y2hlc1swXTsKICAgICAgcmV0dXJuIHBvaW50JDcobm9kZSwgZXZlbnQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRvdWNoJDEobm9kZSwgdG91Y2hlcywgaWRlbnRpZmllcikgewogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDMpIGlkZW50aWZpZXIgPSB0b3VjaGVzLCB0b3VjaGVzID0gc291cmNlRXZlbnQkMigpLmNoYW5nZWRUb3VjaGVzOwoKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0b3VjaGVzID8gdG91Y2hlcy5sZW5ndGggOiAwLCB0b3VjaDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICgodG91Y2ggPSB0b3VjaGVzW2ldKS5pZGVudGlmaWVyID09PSBpZGVudGlmaWVyKSB7CiAgICAgICAgICByZXR1cm4gcG9pbnQkNyhub2RlLCB0b3VjaCk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBub3Byb3BhZ2F0aW9uJDQoKSB7CiAgICAgIGV2ZW50JDIuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9ldmVudCQ1KCkgewogICAgICBldmVudCQyLnByZXZlbnREZWZhdWx0KCk7CiAgICAgIGV2ZW50JDIuc3RvcEltbWVkaWF0ZVByb3BhZ2F0aW9uKCk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kcmFnKHZpZXcpIHsKICAgICAgdmFyIHJvb3QgPSB2aWV3LmRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwKICAgICAgICAgIHNlbGVjdGlvbiA9IHNlbGVjdCQyKHZpZXcpLm9uKCJkcmFnc3RhcnQuZHJhZyIsIG5vZXZlbnQkNSwgdHJ1ZSk7CiAgICAgIGlmICgib25zZWxlY3RzdGFydCIgaW4gcm9vdCkgewogICAgICAgIHNlbGVjdGlvbi5vbigic2VsZWN0c3RhcnQuZHJhZyIsIG5vZXZlbnQkNSwgdHJ1ZSk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcm9vdC5fX25vc2VsZWN0ID0gcm9vdC5zdHlsZS5Nb3pVc2VyU2VsZWN0OwogICAgICAgIHJvb3Quc3R5bGUuTW96VXNlclNlbGVjdCA9ICJub25lIjsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHllc2RyYWckMih2aWV3LCBub2NsaWNrKSB7CiAgICAgIHZhciByb290ID0gdmlldy5kb2N1bWVudC5kb2N1bWVudEVsZW1lbnQsCiAgICAgICAgICBzZWxlY3Rpb24gPSBzZWxlY3QkMih2aWV3KS5vbigiZHJhZ3N0YXJ0LmRyYWciLCBudWxsKTsKICAgICAgaWYgKG5vY2xpY2spIHsKICAgICAgICBzZWxlY3Rpb24ub24oImNsaWNrLmRyYWciLCBub2V2ZW50JDUsIHRydWUpOwogICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHNlbGVjdGlvbi5vbigiY2xpY2suZHJhZyIsIG51bGwpOyB9LCAwKTsKICAgICAgfQogICAgICBpZiAoIm9uc2VsZWN0c3RhcnQiIGluIHJvb3QpIHsKICAgICAgICBzZWxlY3Rpb24ub24oInNlbGVjdHN0YXJ0LmRyYWciLCBudWxsKTsKICAgICAgfSBlbHNlIHsKICAgICAgICByb290LnN0eWxlLk1velVzZXJTZWxlY3QgPSByb290Ll9fbm9zZWxlY3Q7CiAgICAgICAgZGVsZXRlIHJvb3QuX19ub3NlbGVjdDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JGsoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gRHJhZ0V2ZW50JDEodGFyZ2V0LCB0eXBlLCBzdWJqZWN0LCBpZCwgYWN0aXZlLCB4LCB5LCBkeCwgZHksIGRpc3BhdGNoKSB7CiAgICAgIHRoaXMudGFyZ2V0ID0gdGFyZ2V0OwogICAgICB0aGlzLnR5cGUgPSB0eXBlOwogICAgICB0aGlzLnN1YmplY3QgPSBzdWJqZWN0OwogICAgICB0aGlzLmlkZW50aWZpZXIgPSBpZDsKICAgICAgdGhpcy5hY3RpdmUgPSBhY3RpdmU7CiAgICAgIHRoaXMueCA9IHg7CiAgICAgIHRoaXMueSA9IHk7CiAgICAgIHRoaXMuZHggPSBkeDsKICAgICAgdGhpcy5keSA9IGR5OwogICAgICB0aGlzLl8gPSBkaXNwYXRjaDsKICAgIH0KCiAgICBEcmFnRXZlbnQkMS5wcm90b3R5cGUub24gPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIHZhbHVlID0gdGhpcy5fLm9uLmFwcGx5KHRoaXMuXywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIHZhbHVlID09PSB0aGlzLl8gPyB0aGlzIDogdmFsdWU7CiAgICB9OwoKICAgIC8vIElnbm9yZSByaWdodC1jbGljaywgc2luY2UgdGhhdCBzaG91bGQgb3BlbiB0aGUgY29udGV4dCBtZW51LgogICAgZnVuY3Rpb24gZGVmYXVsdEZpbHRlciQ0KCkgewogICAgICByZXR1cm4gIWV2ZW50JDIuYnV0dG9uOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRDb250YWluZXIkMSgpIHsKICAgICAgcmV0dXJuIHRoaXMucGFyZW50Tm9kZTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0U3ViamVjdCQxKGQpIHsKICAgICAgcmV0dXJuIGQgPT0gbnVsbCA/IHt4OiBldmVudCQyLngsIHk6IGV2ZW50JDIueX0gOiBkOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRUb3VjaGFibGUkMygpIHsKICAgICAgcmV0dXJuICJvbnRvdWNoc3RhcnQiIGluIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gZHJhZyQxKCkgewogICAgICB2YXIgZmlsdGVyID0gZGVmYXVsdEZpbHRlciQ0LAogICAgICAgICAgY29udGFpbmVyID0gZGVmYXVsdENvbnRhaW5lciQxLAogICAgICAgICAgc3ViamVjdCA9IGRlZmF1bHRTdWJqZWN0JDEsCiAgICAgICAgICB0b3VjaGFibGUgPSBkZWZhdWx0VG91Y2hhYmxlJDMsCiAgICAgICAgICBnZXN0dXJlcyA9IHt9LAogICAgICAgICAgbGlzdGVuZXJzID0gZGlzcGF0Y2gkMygic3RhcnQiLCAiZHJhZyIsICJlbmQiKSwKICAgICAgICAgIGFjdGl2ZSA9IDAsCiAgICAgICAgICBtb3VzZWRvd254LAogICAgICAgICAgbW91c2Vkb3dueSwKICAgICAgICAgIG1vdXNlbW92aW5nLAogICAgICAgICAgdG91Y2hlbmRpbmcsCiAgICAgICAgICBjbGlja0Rpc3RhbmNlMiA9IDA7CgogICAgICBmdW5jdGlvbiBkcmFnKHNlbGVjdGlvbikgewogICAgICAgIHNlbGVjdGlvbgogICAgICAgICAgICAub24oIm1vdXNlZG93bi5kcmFnIiwgbW91c2Vkb3duZWQpCiAgICAgICAgICAuZmlsdGVyKHRvdWNoYWJsZSkKICAgICAgICAgICAgLm9uKCJ0b3VjaHN0YXJ0LmRyYWciLCB0b3VjaHN0YXJ0ZWQpCiAgICAgICAgICAgIC5vbigidG91Y2htb3ZlLmRyYWciLCB0b3VjaG1vdmVkKQogICAgICAgICAgICAub24oInRvdWNoZW5kLmRyYWcgdG91Y2hjYW5jZWwuZHJhZyIsIHRvdWNoZW5kZWQpCiAgICAgICAgICAgIC5zdHlsZSgidG91Y2gtYWN0aW9uIiwgIm5vbmUiKQogICAgICAgICAgICAuc3R5bGUoIi13ZWJraXQtdGFwLWhpZ2hsaWdodC1jb2xvciIsICJyZ2JhKDAsMCwwLDApIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIG1vdXNlZG93bmVkKCkgewogICAgICAgIGlmICh0b3VjaGVuZGluZyB8fCAhZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgZ2VzdHVyZSA9IGJlZm9yZXN0YXJ0KCJtb3VzZSIsIGNvbnRhaW5lci5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCBtb3VzZSQyLCB0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICghZ2VzdHVyZSkgcmV0dXJuOwogICAgICAgIHNlbGVjdCQyKGV2ZW50JDIudmlldykub24oIm1vdXNlbW92ZS5kcmFnIiwgbW91c2Vtb3ZlZCwgdHJ1ZSkub24oIm1vdXNldXAuZHJhZyIsIG1vdXNldXBwZWQsIHRydWUpOwogICAgICAgIG5vZHJhZyhldmVudCQyLnZpZXcpOwogICAgICAgIG5vcHJvcGFnYXRpb24kNCgpOwogICAgICAgIG1vdXNlbW92aW5nID0gZmFsc2U7CiAgICAgICAgbW91c2Vkb3dueCA9IGV2ZW50JDIuY2xpZW50WDsKICAgICAgICBtb3VzZWRvd255ID0gZXZlbnQkMi5jbGllbnRZOwogICAgICAgIGdlc3R1cmUoInN0YXJ0Iik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIG1vdXNlbW92ZWQoKSB7CiAgICAgICAgbm9ldmVudCQ1KCk7CiAgICAgICAgaWYgKCFtb3VzZW1vdmluZykgewogICAgICAgICAgdmFyIGR4ID0gZXZlbnQkMi5jbGllbnRYIC0gbW91c2Vkb3dueCwgZHkgPSBldmVudCQyLmNsaWVudFkgLSBtb3VzZWRvd255OwogICAgICAgICAgbW91c2Vtb3ZpbmcgPSBkeCAqIGR4ICsgZHkgKiBkeSA+IGNsaWNrRGlzdGFuY2UyOwogICAgICAgIH0KICAgICAgICBnZXN0dXJlcy5tb3VzZSgiZHJhZyIpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBtb3VzZXVwcGVkKCkgewogICAgICAgIHNlbGVjdCQyKGV2ZW50JDIudmlldykub24oIm1vdXNlbW92ZS5kcmFnIG1vdXNldXAuZHJhZyIsIG51bGwpOwogICAgICAgIHllc2RyYWckMihldmVudCQyLnZpZXcsIG1vdXNlbW92aW5nKTsKICAgICAgICBub2V2ZW50JDUoKTsKICAgICAgICBnZXN0dXJlcy5tb3VzZSgiZW5kIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNoc3RhcnRlZCgpIHsKICAgICAgICBpZiAoIWZpbHRlci5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSByZXR1cm47CiAgICAgICAgdmFyIHRvdWNoZXMgPSBldmVudCQyLmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBjID0gY29udGFpbmVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksCiAgICAgICAgICAgIG4gPSB0b3VjaGVzLmxlbmd0aCwgaSwgZ2VzdHVyZTsKCiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKGdlc3R1cmUgPSBiZWZvcmVzdGFydCh0b3VjaGVzW2ldLmlkZW50aWZpZXIsIGMsIHRvdWNoJDEsIHRoaXMsIGFyZ3VtZW50cykpIHsKICAgICAgICAgICAgbm9wcm9wYWdhdGlvbiQ0KCk7CiAgICAgICAgICAgIGdlc3R1cmUoInN0YXJ0Iik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiB0b3VjaG1vdmVkKCkgewogICAgICAgIHZhciB0b3VjaGVzID0gZXZlbnQkMi5jaGFuZ2VkVG91Y2hlcywKICAgICAgICAgICAgbiA9IHRvdWNoZXMubGVuZ3RoLCBpLCBnZXN0dXJlOwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoZ2VzdHVyZSA9IGdlc3R1cmVzW3RvdWNoZXNbaV0uaWRlbnRpZmllcl0pIHsKICAgICAgICAgICAgbm9ldmVudCQ1KCk7CiAgICAgICAgICAgIGdlc3R1cmUoImRyYWciKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNoZW5kZWQoKSB7CiAgICAgICAgdmFyIHRvdWNoZXMgPSBldmVudCQyLmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBuID0gdG91Y2hlcy5sZW5ndGgsIGksIGdlc3R1cmU7CgogICAgICAgIGlmICh0b3VjaGVuZGluZykgY2xlYXJUaW1lb3V0KHRvdWNoZW5kaW5nKTsKICAgICAgICB0b3VjaGVuZGluZyA9IHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHRvdWNoZW5kaW5nID0gbnVsbDsgfSwgNTAwKTsgLy8gR2hvc3QgY2xpY2tzIGFyZSBkZWxheWVkIQogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChnZXN0dXJlID0gZ2VzdHVyZXNbdG91Y2hlc1tpXS5pZGVudGlmaWVyXSkgewogICAgICAgICAgICBub3Byb3BhZ2F0aW9uJDQoKTsKICAgICAgICAgICAgZ2VzdHVyZSgiZW5kIik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBiZWZvcmVzdGFydChpZCwgY29udGFpbmVyLCBwb2ludCwgdGhhdCwgYXJncykgewogICAgICAgIHZhciBwID0gcG9pbnQoY29udGFpbmVyLCBpZCksIHMsIGR4LCBkeSwKICAgICAgICAgICAgc3VibGlzdGVuZXJzID0gbGlzdGVuZXJzLmNvcHkoKTsKCiAgICAgICAgaWYgKCFjdXN0b21FdmVudCQyKG5ldyBEcmFnRXZlbnQkMShkcmFnLCAiYmVmb3Jlc3RhcnQiLCBzLCBpZCwgYWN0aXZlLCBwWzBdLCBwWzFdLCAwLCAwLCBzdWJsaXN0ZW5lcnMpLCBmdW5jdGlvbigpIHsKICAgICAgICAgIGlmICgoZXZlbnQkMi5zdWJqZWN0ID0gcyA9IHN1YmplY3QuYXBwbHkodGhhdCwgYXJncykpID09IG51bGwpIHJldHVybiBmYWxzZTsKICAgICAgICAgIGR4ID0gcy54IC0gcFswXSB8fCAwOwogICAgICAgICAgZHkgPSBzLnkgLSBwWzFdIHx8IDA7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9KSkgcmV0dXJuOwoKICAgICAgICByZXR1cm4gZnVuY3Rpb24gZ2VzdHVyZSh0eXBlKSB7CiAgICAgICAgICB2YXIgcDAgPSBwLCBuOwogICAgICAgICAgc3dpdGNoICh0eXBlKSB7CiAgICAgICAgICAgIGNhc2UgInN0YXJ0IjogZ2VzdHVyZXNbaWRdID0gZ2VzdHVyZSwgbiA9IGFjdGl2ZSsrOyBicmVhazsKICAgICAgICAgICAgY2FzZSAiZW5kIjogZGVsZXRlIGdlc3R1cmVzW2lkXSwgLS1hY3RpdmU7IC8vIG5vYnJlYWsKICAgICAgICAgICAgY2FzZSAiZHJhZyI6IHAgPSBwb2ludChjb250YWluZXIsIGlkKSwgbiA9IGFjdGl2ZTsgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjdXN0b21FdmVudCQyKG5ldyBEcmFnRXZlbnQkMShkcmFnLCB0eXBlLCBzLCBpZCwgbiwgcFswXSArIGR4LCBwWzFdICsgZHksIHBbMF0gLSBwMFswXSwgcFsxXSAtIHAwWzFdLCBzdWJsaXN0ZW5lcnMpLCBzdWJsaXN0ZW5lcnMuYXBwbHksIHN1Ymxpc3RlbmVycywgW3R5cGUsIHRoYXQsIGFyZ3NdKTsKICAgICAgICB9OwogICAgICB9CgogICAgICBkcmFnLmZpbHRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChmaWx0ZXIgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRrKCEhXyksIGRyYWcpIDogZmlsdGVyOwogICAgICB9OwoKICAgICAgZHJhZy5jb250YWluZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY29udGFpbmVyID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkayhfKSwgZHJhZykgOiBjb250YWluZXI7CiAgICAgIH07CgogICAgICBkcmFnLnN1YmplY3QgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc3ViamVjdCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGsoXyksIGRyYWcpIDogc3ViamVjdDsKICAgICAgfTsKCiAgICAgIGRyYWcudG91Y2hhYmxlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRvdWNoYWJsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGsoISFfKSwgZHJhZykgOiB0b3VjaGFibGU7CiAgICAgIH07CgogICAgICBkcmFnLm9uID0gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHZhbHVlID0gbGlzdGVuZXJzLm9uLmFwcGx5KGxpc3RlbmVycywgYXJndW1lbnRzKTsKICAgICAgICByZXR1cm4gdmFsdWUgPT09IGxpc3RlbmVycyA/IGRyYWcgOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIGRyYWcuY2xpY2tEaXN0YW5jZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjbGlja0Rpc3RhbmNlMiA9IChfID0gK18pICogXywgZHJhZykgOiBNYXRoLnNxcnQoY2xpY2tEaXN0YW5jZTIpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGRyYWc7CiAgICB9CgogICAgdmFyIEVPTCQxID0ge30sCiAgICAgICAgRU9GJDEgPSB7fSwKICAgICAgICBRVU9URSQxID0gMzQsCiAgICAgICAgTkVXTElORSQxID0gMTAsCiAgICAgICAgUkVUVVJOJDEgPSAxMzsKCiAgICBmdW5jdGlvbiBvYmplY3RDb252ZXJ0ZXIkMShjb2x1bW5zKSB7CiAgICAgIHJldHVybiBuZXcgRnVuY3Rpb24oImQiLCAicmV0dXJuIHsiICsgY29sdW1ucy5tYXAoZnVuY3Rpb24obmFtZSwgaSkgewogICAgICAgIHJldHVybiBKU09OLnN0cmluZ2lmeShuYW1lKSArICI6IGRbIiArIGkgKyAiXSI7CiAgICAgIH0pLmpvaW4oIiwiKSArICJ9Iik7CiAgICB9CgogICAgZnVuY3Rpb24gY3VzdG9tQ29udmVydGVyJDEoY29sdW1ucywgZikgewogICAgICB2YXIgb2JqZWN0ID0gb2JqZWN0Q29udmVydGVyJDEoY29sdW1ucyk7CiAgICAgIHJldHVybiBmdW5jdGlvbihyb3csIGkpIHsKICAgICAgICByZXR1cm4gZihvYmplY3Qocm93KSwgaSwgY29sdW1ucyk7CiAgICAgIH07CiAgICB9CgogICAgLy8gQ29tcHV0ZSB1bmlxdWUgY29sdW1ucyBpbiBvcmRlciBvZiBkaXNjb3ZlcnkuCiAgICBmdW5jdGlvbiBpbmZlckNvbHVtbnMkMShyb3dzKSB7CiAgICAgIHZhciBjb2x1bW5TZXQgPSBPYmplY3QuY3JlYXRlKG51bGwpLAogICAgICAgICAgY29sdW1ucyA9IFtdOwoKICAgICAgcm93cy5mb3JFYWNoKGZ1bmN0aW9uKHJvdykgewogICAgICAgIGZvciAodmFyIGNvbHVtbiBpbiByb3cpIHsKICAgICAgICAgIGlmICghKGNvbHVtbiBpbiBjb2x1bW5TZXQpKSB7CiAgICAgICAgICAgIGNvbHVtbnMucHVzaChjb2x1bW5TZXRbY29sdW1uXSA9IGNvbHVtbik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9KTsKCiAgICAgIHJldHVybiBjb2x1bW5zOwogICAgfQoKICAgIGZ1bmN0aW9uIGRzdiQxKGRlbGltaXRlcikgewogICAgICB2YXIgcmVGb3JtYXQgPSBuZXcgUmVnRXhwKCJbXCIiICsgZGVsaW1pdGVyICsgIlxuXHJdIiksCiAgICAgICAgICBERUxJTUlURVIgPSBkZWxpbWl0ZXIuY2hhckNvZGVBdCgwKTsKCiAgICAgIGZ1bmN0aW9uIHBhcnNlKHRleHQsIGYpIHsKICAgICAgICB2YXIgY29udmVydCwgY29sdW1ucywgcm93cyA9IHBhcnNlUm93cyh0ZXh0LCBmdW5jdGlvbihyb3csIGkpIHsKICAgICAgICAgIGlmIChjb252ZXJ0KSByZXR1cm4gY29udmVydChyb3csIGkgLSAxKTsKICAgICAgICAgIGNvbHVtbnMgPSByb3csIGNvbnZlcnQgPSBmID8gY3VzdG9tQ29udmVydGVyJDEocm93LCBmKSA6IG9iamVjdENvbnZlcnRlciQxKHJvdyk7CiAgICAgICAgfSk7CiAgICAgICAgcm93cy5jb2x1bW5zID0gY29sdW1ucyB8fCBbXTsKICAgICAgICByZXR1cm4gcm93czsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VSb3dzKHRleHQsIGYpIHsKICAgICAgICB2YXIgcm93cyA9IFtdLCAvLyBvdXRwdXQgcm93cwogICAgICAgICAgICBOID0gdGV4dC5sZW5ndGgsCiAgICAgICAgICAgIEkgPSAwLCAvLyBjdXJyZW50IGNoYXJhY3RlciBpbmRleAogICAgICAgICAgICBuID0gMCwgLy8gY3VycmVudCBsaW5lIG51bWJlcgogICAgICAgICAgICB0LCAvLyBjdXJyZW50IHRva2VuCiAgICAgICAgICAgIGVvZiA9IE4gPD0gMCwgLy8gY3VycmVudCB0b2tlbiBmb2xsb3dlZCBieSBFT0Y/CiAgICAgICAgICAgIGVvbCA9IGZhbHNlOyAvLyBjdXJyZW50IHRva2VuIGZvbGxvd2VkIGJ5IEVPTD8KCiAgICAgICAgLy8gU3RyaXAgdGhlIHRyYWlsaW5nIG5ld2xpbmUuCiAgICAgICAgaWYgKHRleHQuY2hhckNvZGVBdChOIC0gMSkgPT09IE5FV0xJTkUkMSkgLS1OOwogICAgICAgIGlmICh0ZXh0LmNoYXJDb2RlQXQoTiAtIDEpID09PSBSRVRVUk4kMSkgLS1OOwoKICAgICAgICBmdW5jdGlvbiB0b2tlbigpIHsKICAgICAgICAgIGlmIChlb2YpIHJldHVybiBFT0YkMTsKICAgICAgICAgIGlmIChlb2wpIHJldHVybiBlb2wgPSBmYWxzZSwgRU9MJDE7CgogICAgICAgICAgLy8gVW5lc2NhcGUgcXVvdGVzLgogICAgICAgICAgdmFyIGksIGogPSBJLCBjOwogICAgICAgICAgaWYgKHRleHQuY2hhckNvZGVBdChqKSA9PT0gUVVPVEUkMSkgewogICAgICAgICAgICB3aGlsZSAoSSsrIDwgTiAmJiB0ZXh0LmNoYXJDb2RlQXQoSSkgIT09IFFVT1RFJDEgfHwgdGV4dC5jaGFyQ29kZUF0KCsrSSkgPT09IFFVT1RFJDEpOwogICAgICAgICAgICBpZiAoKGkgPSBJKSA+PSBOKSBlb2YgPSB0cnVlOwogICAgICAgICAgICBlbHNlIGlmICgoYyA9IHRleHQuY2hhckNvZGVBdChJKyspKSA9PT0gTkVXTElORSQxKSBlb2wgPSB0cnVlOwogICAgICAgICAgICBlbHNlIGlmIChjID09PSBSRVRVUk4kMSkgeyBlb2wgPSB0cnVlOyBpZiAodGV4dC5jaGFyQ29kZUF0KEkpID09PSBORVdMSU5FJDEpICsrSTsgfQogICAgICAgICAgICByZXR1cm4gdGV4dC5zbGljZShqICsgMSwgaSAtIDEpLnJlcGxhY2UoLyIiL2csICJcIiIpOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIEZpbmQgbmV4dCBkZWxpbWl0ZXIgb3IgbmV3bGluZS4KICAgICAgICAgIHdoaWxlIChJIDwgTikgewogICAgICAgICAgICBpZiAoKGMgPSB0ZXh0LmNoYXJDb2RlQXQoaSA9IEkrKykpID09PSBORVdMSU5FJDEpIGVvbCA9IHRydWU7CiAgICAgICAgICAgIGVsc2UgaWYgKGMgPT09IFJFVFVSTiQxKSB7IGVvbCA9IHRydWU7IGlmICh0ZXh0LmNoYXJDb2RlQXQoSSkgPT09IE5FV0xJTkUkMSkgKytJOyB9CiAgICAgICAgICAgIGVsc2UgaWYgKGMgIT09IERFTElNSVRFUikgY29udGludWU7CiAgICAgICAgICAgIHJldHVybiB0ZXh0LnNsaWNlKGosIGkpOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIFJldHVybiBsYXN0IHRva2VuIGJlZm9yZSBFT0YuCiAgICAgICAgICByZXR1cm4gZW9mID0gdHJ1ZSwgdGV4dC5zbGljZShqLCBOKTsKICAgICAgICB9CgogICAgICAgIHdoaWxlICgodCA9IHRva2VuKCkpICE9PSBFT0YkMSkgewogICAgICAgICAgdmFyIHJvdyA9IFtdOwogICAgICAgICAgd2hpbGUgKHQgIT09IEVPTCQxICYmIHQgIT09IEVPRiQxKSByb3cucHVzaCh0KSwgdCA9IHRva2VuKCk7CiAgICAgICAgICBpZiAoZiAmJiAocm93ID0gZihyb3csIG4rKykpID09IG51bGwpIGNvbnRpbnVlOwogICAgICAgICAgcm93cy5wdXNoKHJvdyk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gcm93czsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0KHJvd3MsIGNvbHVtbnMpIHsKICAgICAgICBpZiAoY29sdW1ucyA9PSBudWxsKSBjb2x1bW5zID0gaW5mZXJDb2x1bW5zJDEocm93cyk7CiAgICAgICAgcmV0dXJuIFtjb2x1bW5zLm1hcChmb3JtYXRWYWx1ZSkuam9pbihkZWxpbWl0ZXIpXS5jb25jYXQocm93cy5tYXAoZnVuY3Rpb24ocm93KSB7CiAgICAgICAgICByZXR1cm4gY29sdW1ucy5tYXAoZnVuY3Rpb24oY29sdW1uKSB7CiAgICAgICAgICAgIHJldHVybiBmb3JtYXRWYWx1ZShyb3dbY29sdW1uXSk7CiAgICAgICAgICB9KS5qb2luKGRlbGltaXRlcik7CiAgICAgICAgfSkpLmpvaW4oIlxuIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFJvd3Mocm93cykgewogICAgICAgIHJldHVybiByb3dzLm1hcChmb3JtYXRSb3cpLmpvaW4oIlxuIik7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFJvdyhyb3cpIHsKICAgICAgICByZXR1cm4gcm93Lm1hcChmb3JtYXRWYWx1ZSkuam9pbihkZWxpbWl0ZXIpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRWYWx1ZSh0ZXh0KSB7CiAgICAgICAgcmV0dXJuIHRleHQgPT0gbnVsbCA/ICIiCiAgICAgICAgICAgIDogcmVGb3JtYXQudGVzdCh0ZXh0ICs9ICIiKSA/ICJcIiIgKyB0ZXh0LnJlcGxhY2UoLyIvZywgIlwiXCIiKSArICJcIiIKICAgICAgICAgICAgOiB0ZXh0OwogICAgICB9CgogICAgICByZXR1cm4gewogICAgICAgIHBhcnNlOiBwYXJzZSwKICAgICAgICBwYXJzZVJvd3M6IHBhcnNlUm93cywKICAgICAgICBmb3JtYXQ6IGZvcm1hdCwKICAgICAgICBmb3JtYXRSb3dzOiBmb3JtYXRSb3dzCiAgICAgIH07CiAgICB9CgogICAgdmFyIGNzdiQyID0gZHN2JDEoIiwiKTsKCiAgICB2YXIgY3N2UGFyc2UkMSA9IGNzdiQyLnBhcnNlOwogICAgdmFyIGNzdlBhcnNlUm93cyQxID0gY3N2JDIucGFyc2VSb3dzOwogICAgdmFyIGNzdkZvcm1hdCQxID0gY3N2JDIuZm9ybWF0OwogICAgdmFyIGNzdkZvcm1hdFJvd3MkMSA9IGNzdiQyLmZvcm1hdFJvd3M7CgogICAgdmFyIHRzdiQyID0gZHN2JDEoIlx0Iik7CgogICAgdmFyIHRzdlBhcnNlJDEgPSB0c3YkMi5wYXJzZTsKICAgIHZhciB0c3ZQYXJzZVJvd3MkMSA9IHRzdiQyLnBhcnNlUm93czsKICAgIHZhciB0c3ZGb3JtYXQkMSA9IHRzdiQyLmZvcm1hdDsKICAgIHZhciB0c3ZGb3JtYXRSb3dzJDEgPSB0c3YkMi5mb3JtYXRSb3dzOwoKICAgIGZ1bmN0aW9uIGxpbmVhciQ0KHQpIHsKICAgICAgcmV0dXJuICt0OwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YWRJbiQxKHQpIHsKICAgICAgcmV0dXJuIHQgKiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YWRPdXQkMSh0KSB7CiAgICAgIHJldHVybiB0ICogKDIgLSB0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBxdWFkSW5PdXQkMSh0KSB7CiAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IHQgKiB0IDogLS10ICogKDIgLSB0KSArIDEpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjdWJpY0luJDEodCkgewogICAgICByZXR1cm4gdCAqIHQgKiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmljT3V0JDEodCkgewogICAgICByZXR1cm4gLS10ICogdCAqIHQgKyAxOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmljSW5PdXQkMSh0KSB7CiAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IHQgKiB0ICogdCA6ICh0IC09IDIpICogdCAqIHQgKyAyKSAvIDI7CiAgICB9CgogICAgdmFyIGV4cG9uZW50JDIgPSAzOwoKICAgIHZhciBwb2x5SW4kMSA9IChmdW5jdGlvbiBjdXN0b20oZSkgewogICAgICBlID0gK2U7CgogICAgICBmdW5jdGlvbiBwb2x5SW4odCkgewogICAgICAgIHJldHVybiBNYXRoLnBvdyh0LCBlKTsKICAgICAgfQoKICAgICAgcG9seUluLmV4cG9uZW50ID0gY3VzdG9tOwoKICAgICAgcmV0dXJuIHBvbHlJbjsKICAgIH0pKGV4cG9uZW50JDIpOwoKICAgIHZhciBwb2x5T3V0JDEgPSAoZnVuY3Rpb24gY3VzdG9tKGUpIHsKICAgICAgZSA9ICtlOwoKICAgICAgZnVuY3Rpb24gcG9seU91dCh0KSB7CiAgICAgICAgcmV0dXJuIDEgLSBNYXRoLnBvdygxIC0gdCwgZSk7CiAgICAgIH0KCiAgICAgIHBvbHlPdXQuZXhwb25lbnQgPSBjdXN0b207CgogICAgICByZXR1cm4gcG9seU91dDsKICAgIH0pKGV4cG9uZW50JDIpOwoKICAgIHZhciBwb2x5SW5PdXQkMSA9IChmdW5jdGlvbiBjdXN0b20oZSkgewogICAgICBlID0gK2U7CgogICAgICBmdW5jdGlvbiBwb2x5SW5PdXQodCkgewogICAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IE1hdGgucG93KHQsIGUpIDogMiAtIE1hdGgucG93KDIgLSB0LCBlKSkgLyAyOwogICAgICB9CgogICAgICBwb2x5SW5PdXQuZXhwb25lbnQgPSBjdXN0b207CgogICAgICByZXR1cm4gcG9seUluT3V0OwogICAgfSkoZXhwb25lbnQkMik7CgogICAgdmFyIHBpJDcgPSBNYXRoLlBJLAogICAgICAgIGhhbGZQaSQ1ID0gcGkkNyAvIDI7CgogICAgZnVuY3Rpb24gc2luSW4kMSh0KSB7CiAgICAgIHJldHVybiAxIC0gTWF0aC5jb3ModCAqIGhhbGZQaSQ1KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzaW5PdXQkMSh0KSB7CiAgICAgIHJldHVybiBNYXRoLnNpbih0ICogaGFsZlBpJDUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNpbkluT3V0JDEodCkgewogICAgICByZXR1cm4gKDEgLSBNYXRoLmNvcyhwaSQ3ICogdCkpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBJbiQxKHQpIHsKICAgICAgcmV0dXJuIE1hdGgucG93KDIsIDEwICogdCAtIDEwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBPdXQkMSh0KSB7CiAgICAgIHJldHVybiAxIC0gTWF0aC5wb3coMiwgLTEwICogdCk7CiAgICB9CgogICAgZnVuY3Rpb24gZXhwSW5PdXQkMSh0KSB7CiAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IE1hdGgucG93KDIsIDEwICogdCAtIDEwKSA6IDIgLSBNYXRoLnBvdygyLCAxMCAtIDEwICogdCkpIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjaXJjbGVJbiQxKHQpIHsKICAgICAgcmV0dXJuIDEgLSBNYXRoLnNxcnQoMSAtIHQgKiB0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjaXJjbGVPdXQkMSh0KSB7CiAgICAgIHJldHVybiBNYXRoLnNxcnQoMSAtIC0tdCAqIHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNpcmNsZUluT3V0JDEodCkgewogICAgICByZXR1cm4gKCh0ICo9IDIpIDw9IDEgPyAxIC0gTWF0aC5zcXJ0KDEgLSB0ICogdCkgOiBNYXRoLnNxcnQoMSAtICh0IC09IDIpICogdCkgKyAxKSAvIDI7CiAgICB9CgogICAgdmFyIGIxJDEgPSA0IC8gMTEsCiAgICAgICAgYjIkMSA9IDYgLyAxMSwKICAgICAgICBiMyQxID0gOCAvIDExLAogICAgICAgIGI0JDEgPSAzIC8gNCwKICAgICAgICBiNSQxID0gOSAvIDExLAogICAgICAgIGI2JDEgPSAxMCAvIDExLAogICAgICAgIGI3JDEgPSAxNSAvIDE2LAogICAgICAgIGI4JDEgPSAyMSAvIDIyLAogICAgICAgIGI5JDEgPSA2MyAvIDY0LAogICAgICAgIGIwJDEgPSAxIC8gYjEkMSAvIGIxJDE7CgogICAgZnVuY3Rpb24gYm91bmNlSW4kMSh0KSB7CiAgICAgIHJldHVybiAxIC0gYm91bmNlT3V0JDEoMSAtIHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGJvdW5jZU91dCQxKHQpIHsKICAgICAgcmV0dXJuICh0ID0gK3QpIDwgYjEkMSA/IGIwJDEgKiB0ICogdCA6IHQgPCBiMyQxID8gYjAkMSAqICh0IC09IGIyJDEpICogdCArIGI0JDEgOiB0IDwgYjYkMSA/IGIwJDEgKiAodCAtPSBiNSQxKSAqIHQgKyBiNyQxIDogYjAkMSAqICh0IC09IGI4JDEpICogdCArIGI5JDE7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmNlSW5PdXQkMSh0KSB7CiAgICAgIHJldHVybiAoKHQgKj0gMikgPD0gMSA/IDEgLSBib3VuY2VPdXQkMSgxIC0gdCkgOiBib3VuY2VPdXQkMSh0IC0gMSkgKyAxKSAvIDI7CiAgICB9CgogICAgdmFyIG92ZXJzaG9vdCQxID0gMS43MDE1ODsKCiAgICB2YXIgYmFja0luJDEgPSAoZnVuY3Rpb24gY3VzdG9tKHMpIHsKICAgICAgcyA9ICtzOwoKICAgICAgZnVuY3Rpb24gYmFja0luKHQpIHsKICAgICAgICByZXR1cm4gdCAqIHQgKiAoKHMgKyAxKSAqIHQgLSBzKTsKICAgICAgfQoKICAgICAgYmFja0luLm92ZXJzaG9vdCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBiYWNrSW47CiAgICB9KShvdmVyc2hvb3QkMSk7CgogICAgdmFyIGJhY2tPdXQkMSA9IChmdW5jdGlvbiBjdXN0b20ocykgewogICAgICBzID0gK3M7CgogICAgICBmdW5jdGlvbiBiYWNrT3V0KHQpIHsKICAgICAgICByZXR1cm4gLS10ICogdCAqICgocyArIDEpICogdCArIHMpICsgMTsKICAgICAgfQoKICAgICAgYmFja091dC5vdmVyc2hvb3QgPSBjdXN0b207CgogICAgICByZXR1cm4gYmFja091dDsKICAgIH0pKG92ZXJzaG9vdCQxKTsKCiAgICB2YXIgYmFja0luT3V0JDEgPSAoZnVuY3Rpb24gY3VzdG9tKHMpIHsKICAgICAgcyA9ICtzOwoKICAgICAgZnVuY3Rpb24gYmFja0luT3V0KHQpIHsKICAgICAgICByZXR1cm4gKCh0ICo9IDIpIDwgMSA/IHQgKiB0ICogKChzICsgMSkgKiB0IC0gcykgOiAodCAtPSAyKSAqIHQgKiAoKHMgKyAxKSAqIHQgKyBzKSArIDIpIC8gMjsKICAgICAgfQoKICAgICAgYmFja0luT3V0Lm92ZXJzaG9vdCA9IGN1c3RvbTsKCiAgICAgIHJldHVybiBiYWNrSW5PdXQ7CiAgICB9KShvdmVyc2hvb3QkMSk7CgogICAgdmFyIHRhdSQ3ID0gMiAqIE1hdGguUEksCiAgICAgICAgYW1wbGl0dWRlJDEgPSAxLAogICAgICAgIHBlcmlvZCQxID0gMC4zOwoKICAgIHZhciBlbGFzdGljSW4kMSA9IChmdW5jdGlvbiBjdXN0b20oYSwgcCkgewogICAgICB2YXIgcyA9IE1hdGguYXNpbigxIC8gKGEgPSBNYXRoLm1heCgxLCBhKSkpICogKHAgLz0gdGF1JDcpOwoKICAgICAgZnVuY3Rpb24gZWxhc3RpY0luKHQpIHsKICAgICAgICByZXR1cm4gYSAqIE1hdGgucG93KDIsIDEwICogLS10KSAqIE1hdGguc2luKChzIC0gdCkgLyBwKTsKICAgICAgfQoKICAgICAgZWxhc3RpY0luLmFtcGxpdHVkZSA9IGZ1bmN0aW9uKGEpIHsgcmV0dXJuIGN1c3RvbShhLCBwICogdGF1JDcpOyB9OwogICAgICBlbGFzdGljSW4ucGVyaW9kID0gZnVuY3Rpb24ocCkgeyByZXR1cm4gY3VzdG9tKGEsIHApOyB9OwoKICAgICAgcmV0dXJuIGVsYXN0aWNJbjsKICAgIH0pKGFtcGxpdHVkZSQxLCBwZXJpb2QkMSk7CgogICAgdmFyIGVsYXN0aWNPdXQkMSA9IChmdW5jdGlvbiBjdXN0b20oYSwgcCkgewogICAgICB2YXIgcyA9IE1hdGguYXNpbigxIC8gKGEgPSBNYXRoLm1heCgxLCBhKSkpICogKHAgLz0gdGF1JDcpOwoKICAgICAgZnVuY3Rpb24gZWxhc3RpY091dCh0KSB7CiAgICAgICAgcmV0dXJuIDEgLSBhICogTWF0aC5wb3coMiwgLTEwICogKHQgPSArdCkpICogTWF0aC5zaW4oKHQgKyBzKSAvIHApOwogICAgICB9CgogICAgICBlbGFzdGljT3V0LmFtcGxpdHVkZSA9IGZ1bmN0aW9uKGEpIHsgcmV0dXJuIGN1c3RvbShhLCBwICogdGF1JDcpOyB9OwogICAgICBlbGFzdGljT3V0LnBlcmlvZCA9IGZ1bmN0aW9uKHApIHsgcmV0dXJuIGN1c3RvbShhLCBwKTsgfTsKCiAgICAgIHJldHVybiBlbGFzdGljT3V0OwogICAgfSkoYW1wbGl0dWRlJDEsIHBlcmlvZCQxKTsKCiAgICB2YXIgZWxhc3RpY0luT3V0JDEgPSAoZnVuY3Rpb24gY3VzdG9tKGEsIHApIHsKICAgICAgdmFyIHMgPSBNYXRoLmFzaW4oMSAvIChhID0gTWF0aC5tYXgoMSwgYSkpKSAqIChwIC89IHRhdSQ3KTsKCiAgICAgIGZ1bmN0aW9uIGVsYXN0aWNJbk91dCh0KSB7CiAgICAgICAgcmV0dXJuICgodCA9IHQgKiAyIC0gMSkgPCAwCiAgICAgICAgICAgID8gYSAqIE1hdGgucG93KDIsIDEwICogdCkgKiBNYXRoLnNpbigocyAtIHQpIC8gcCkKICAgICAgICAgICAgOiAyIC0gYSAqIE1hdGgucG93KDIsIC0xMCAqIHQpICogTWF0aC5zaW4oKHMgKyB0KSAvIHApKSAvIDI7CiAgICAgIH0KCiAgICAgIGVsYXN0aWNJbk91dC5hbXBsaXR1ZGUgPSBmdW5jdGlvbihhKSB7IHJldHVybiBjdXN0b20oYSwgcCAqIHRhdSQ3KTsgfTsKICAgICAgZWxhc3RpY0luT3V0LnBlcmlvZCA9IGZ1bmN0aW9uKHApIHsgcmV0dXJuIGN1c3RvbShhLCBwKTsgfTsKCiAgICAgIHJldHVybiBlbGFzdGljSW5PdXQ7CiAgICB9KShhbXBsaXR1ZGUkMSwgcGVyaW9kJDEpOwoKICAgIGZ1bmN0aW9uIGNlbnRlciQzKHgsIHkpIHsKICAgICAgdmFyIG5vZGVzOwoKICAgICAgaWYgKHggPT0gbnVsbCkgeCA9IDA7CiAgICAgIGlmICh5ID09IG51bGwpIHkgPSAwOwoKICAgICAgZnVuY3Rpb24gZm9yY2UoKSB7CiAgICAgICAgdmFyIGksCiAgICAgICAgICAgIG4gPSBub2Rlcy5sZW5ndGgsCiAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgIHN4ID0gMCwKICAgICAgICAgICAgc3kgPSAwOwoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIHN4ICs9IG5vZGUueCwgc3kgKz0gbm9kZS55OwogICAgICAgIH0KCiAgICAgICAgZm9yIChzeCA9IHN4IC8gbiAtIHgsIHN5ID0gc3kgLyBuIC0geSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIG5vZGUgPSBub2Rlc1tpXSwgbm9kZS54IC09IHN4LCBub2RlLnkgLT0gc3k7CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXzsKICAgICAgfTsKCiAgICAgIGZvcmNlLnggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeCA9ICtfLCBmb3JjZSkgOiB4OwogICAgICB9OwoKICAgICAgZm9yY2UueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gK18sIGZvcmNlKSA6IHk7CiAgICAgIH07CgogICAgICByZXR1cm4gZm9yY2U7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkbCh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBqaWdnbGUkMSgpIHsKICAgICAgcmV0dXJuIChNYXRoLnJhbmRvbSgpIC0gMC41KSAqIDFlLTY7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9hZGQkMShkKSB7CiAgICAgIHZhciB4ID0gK3RoaXMuX3guY2FsbChudWxsLCBkKSwKICAgICAgICAgIHkgPSArdGhpcy5feS5jYWxsKG51bGwsIGQpOwogICAgICByZXR1cm4gYWRkJDIodGhpcy5jb3Zlcih4LCB5KSwgeCwgeSwgZCk7CiAgICB9CgogICAgZnVuY3Rpb24gYWRkJDIodHJlZSwgeCwgeSwgZCkgewogICAgICBpZiAoaXNOYU4oeCkgfHwgaXNOYU4oeSkpIHJldHVybiB0cmVlOyAvLyBpZ25vcmUgaW52YWxpZCBwb2ludHMKCiAgICAgIHZhciBwYXJlbnQsCiAgICAgICAgICBub2RlID0gdHJlZS5fcm9vdCwKICAgICAgICAgIGxlYWYgPSB7ZGF0YTogZH0sCiAgICAgICAgICB4MCA9IHRyZWUuX3gwLAogICAgICAgICAgeTAgPSB0cmVlLl95MCwKICAgICAgICAgIHgxID0gdHJlZS5feDEsCiAgICAgICAgICB5MSA9IHRyZWUuX3kxLAogICAgICAgICAgeG0sCiAgICAgICAgICB5bSwKICAgICAgICAgIHhwLAogICAgICAgICAgeXAsCiAgICAgICAgICByaWdodCwKICAgICAgICAgIGJvdHRvbSwKICAgICAgICAgIGksCiAgICAgICAgICBqOwoKICAgICAgLy8gSWYgdGhlIHRyZWUgaXMgZW1wdHksIGluaXRpYWxpemUgdGhlIHJvb3QgYXMgYSBsZWFmLgogICAgICBpZiAoIW5vZGUpIHJldHVybiB0cmVlLl9yb290ID0gbGVhZiwgdHJlZTsKCiAgICAgIC8vIEZpbmQgdGhlIGV4aXN0aW5nIGxlYWYgZm9yIHRoZSBuZXcgcG9pbnQsIG9yIGFkZCBpdC4KICAgICAgd2hpbGUgKG5vZGUubGVuZ3RoKSB7CiAgICAgICAgaWYgKHJpZ2h0ID0geCA+PSAoeG0gPSAoeDAgKyB4MSkgLyAyKSkgeDAgPSB4bTsgZWxzZSB4MSA9IHhtOwogICAgICAgIGlmIChib3R0b20gPSB5ID49ICh5bSA9ICh5MCArIHkxKSAvIDIpKSB5MCA9IHltOyBlbHNlIHkxID0geW07CiAgICAgICAgaWYgKHBhcmVudCA9IG5vZGUsICEobm9kZSA9IG5vZGVbaSA9IGJvdHRvbSA8PCAxIHwgcmlnaHRdKSkgcmV0dXJuIHBhcmVudFtpXSA9IGxlYWYsIHRyZWU7CiAgICAgIH0KCiAgICAgIC8vIElzIHRoZSBuZXcgcG9pbnQgaXMgZXhhY3RseSBjb2luY2lkZW50IHdpdGggdGhlIGV4aXN0aW5nIHBvaW50PwogICAgICB4cCA9ICt0cmVlLl94LmNhbGwobnVsbCwgbm9kZS5kYXRhKTsKICAgICAgeXAgPSArdHJlZS5feS5jYWxsKG51bGwsIG5vZGUuZGF0YSk7CiAgICAgIGlmICh4ID09PSB4cCAmJiB5ID09PSB5cCkgcmV0dXJuIGxlYWYubmV4dCA9IG5vZGUsIHBhcmVudCA/IHBhcmVudFtpXSA9IGxlYWYgOiB0cmVlLl9yb290ID0gbGVhZiwgdHJlZTsKCiAgICAgIC8vIE90aGVyd2lzZSwgc3BsaXQgdGhlIGxlYWYgbm9kZSB1bnRpbCB0aGUgb2xkIGFuZCBuZXcgcG9pbnQgYXJlIHNlcGFyYXRlZC4KICAgICAgZG8gewogICAgICAgIHBhcmVudCA9IHBhcmVudCA/IHBhcmVudFtpXSA9IG5ldyBBcnJheSg0KSA6IHRyZWUuX3Jvb3QgPSBuZXcgQXJyYXkoNCk7CiAgICAgICAgaWYgKHJpZ2h0ID0geCA+PSAoeG0gPSAoeDAgKyB4MSkgLyAyKSkgeDAgPSB4bTsgZWxzZSB4MSA9IHhtOwogICAgICAgIGlmIChib3R0b20gPSB5ID49ICh5bSA9ICh5MCArIHkxKSAvIDIpKSB5MCA9IHltOyBlbHNlIHkxID0geW07CiAgICAgIH0gd2hpbGUgKChpID0gYm90dG9tIDw8IDEgfCByaWdodCkgPT09IChqID0gKHlwID49IHltKSA8PCAxIHwgKHhwID49IHhtKSkpOwogICAgICByZXR1cm4gcGFyZW50W2pdID0gbm9kZSwgcGFyZW50W2ldID0gbGVhZiwgdHJlZTsKICAgIH0KCiAgICBmdW5jdGlvbiBhZGRBbGwkMShkYXRhKSB7CiAgICAgIHZhciBkLCBpLCBuID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICB4LAogICAgICAgICAgeSwKICAgICAgICAgIHh6ID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgeXogPSBuZXcgQXJyYXkobiksCiAgICAgICAgICB4MCA9IEluZmluaXR5LAogICAgICAgICAgeTAgPSBJbmZpbml0eSwKICAgICAgICAgIHgxID0gLUluZmluaXR5LAogICAgICAgICAgeTEgPSAtSW5maW5pdHk7CgogICAgICAvLyBDb21wdXRlIHRoZSBwb2ludHMgYW5kIHRoZWlyIGV4dGVudC4KICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgIGlmIChpc05hTih4ID0gK3RoaXMuX3guY2FsbChudWxsLCBkID0gZGF0YVtpXSkpIHx8IGlzTmFOKHkgPSArdGhpcy5feS5jYWxsKG51bGwsIGQpKSkgY29udGludWU7CiAgICAgICAgeHpbaV0gPSB4OwogICAgICAgIHl6W2ldID0geTsKICAgICAgICBpZiAoeCA8IHgwKSB4MCA9IHg7CiAgICAgICAgaWYgKHggPiB4MSkgeDEgPSB4OwogICAgICAgIGlmICh5IDwgeTApIHkwID0geTsKICAgICAgICBpZiAoeSA+IHkxKSB5MSA9IHk7CiAgICAgIH0KCiAgICAgIC8vIElmIHRoZXJlIHdlcmUgbm8gKHZhbGlkKSBwb2ludHMsIGFib3J0LgogICAgICBpZiAoeDAgPiB4MSB8fCB5MCA+IHkxKSByZXR1cm4gdGhpczsKCiAgICAgIC8vIEV4cGFuZCB0aGUgdHJlZSB0byBjb3ZlciB0aGUgbmV3IHBvaW50cy4KICAgICAgdGhpcy5jb3Zlcih4MCwgeTApLmNvdmVyKHgxLCB5MSk7CgogICAgICAvLyBBZGQgdGhlIG5ldyBwb2ludHMuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBhZGQkMih0aGlzLCB4eltpXSwgeXpbaV0sIGRhdGFbaV0pOwogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX2NvdmVyJDEoeCwgeSkgewogICAgICBpZiAoaXNOYU4oeCA9ICt4KSB8fCBpc05hTih5ID0gK3kpKSByZXR1cm4gdGhpczsgLy8gaWdub3JlIGludmFsaWQgcG9pbnRzCgogICAgICB2YXIgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSA9IHRoaXMuX3gxLAogICAgICAgICAgeTEgPSB0aGlzLl95MTsKCiAgICAgIC8vIElmIHRoZSBxdWFkdHJlZSBoYXMgbm8gZXh0ZW50LCBpbml0aWFsaXplIHRoZW0uCiAgICAgIC8vIEludGVnZXIgZXh0ZW50IGFyZSBuZWNlc3Nhcnkgc28gdGhhdCBpZiB3ZSBsYXRlciBkb3VibGUgdGhlIGV4dGVudCwKICAgICAgLy8gdGhlIGV4aXN0aW5nIHF1YWRyYW50IGJvdW5kYXJpZXMgZG9u4oCZdCBjaGFuZ2UgZHVlIHRvIGZsb2F0aW5nIHBvaW50IGVycm9yIQogICAgICBpZiAoaXNOYU4oeDApKSB7CiAgICAgICAgeDEgPSAoeDAgPSBNYXRoLmZsb29yKHgpKSArIDE7CiAgICAgICAgeTEgPSAoeTAgPSBNYXRoLmZsb29yKHkpKSArIDE7CiAgICAgIH0KCiAgICAgIC8vIE90aGVyd2lzZSwgZG91YmxlIHJlcGVhdGVkbHkgdG8gY292ZXIuCiAgICAgIGVsc2UgewogICAgICAgIHZhciB6ID0geDEgLSB4MCwKICAgICAgICAgICAgbm9kZSA9IHRoaXMuX3Jvb3QsCiAgICAgICAgICAgIHBhcmVudCwKICAgICAgICAgICAgaTsKCiAgICAgICAgd2hpbGUgKHgwID4geCB8fCB4ID49IHgxIHx8IHkwID4geSB8fCB5ID49IHkxKSB7CiAgICAgICAgICBpID0gKHkgPCB5MCkgPDwgMSB8ICh4IDwgeDApOwogICAgICAgICAgcGFyZW50ID0gbmV3IEFycmF5KDQpLCBwYXJlbnRbaV0gPSBub2RlLCBub2RlID0gcGFyZW50LCB6ICo9IDI7CiAgICAgICAgICBzd2l0Y2ggKGkpIHsKICAgICAgICAgICAgY2FzZSAwOiB4MSA9IHgwICsgeiwgeTEgPSB5MCArIHo7IGJyZWFrOwogICAgICAgICAgICBjYXNlIDE6IHgwID0geDEgLSB6LCB5MSA9IHkwICsgejsgYnJlYWs7CiAgICAgICAgICAgIGNhc2UgMjogeDEgPSB4MCArIHosIHkwID0geTEgLSB6OyBicmVhazsKICAgICAgICAgICAgY2FzZSAzOiB4MCA9IHgxIC0geiwgeTAgPSB5MSAtIHo7IGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuX3Jvb3QgJiYgdGhpcy5fcm9vdC5sZW5ndGgpIHRoaXMuX3Jvb3QgPSBub2RlOwogICAgICB9CgogICAgICB0aGlzLl94MCA9IHgwOwogICAgICB0aGlzLl95MCA9IHkwOwogICAgICB0aGlzLl94MSA9IHgxOwogICAgICB0aGlzLl95MSA9IHkxOwogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX2RhdGEkMSgpIHsKICAgICAgdmFyIGRhdGEgPSBbXTsKICAgICAgdGhpcy52aXNpdChmdW5jdGlvbihub2RlKSB7CiAgICAgICAgaWYgKCFub2RlLmxlbmd0aCkgZG8gZGF0YS5wdXNoKG5vZGUuZGF0YSk7IHdoaWxlIChub2RlID0gbm9kZS5uZXh0KQogICAgICB9KTsKICAgICAgcmV0dXJuIGRhdGE7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9leHRlbnQkMShfKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuY292ZXIoK19bMF1bMF0sICtfWzBdWzFdKS5jb3ZlcigrX1sxXVswXSwgK19bMV1bMV0pCiAgICAgICAgICA6IGlzTmFOKHRoaXMuX3gwKSA/IHVuZGVmaW5lZCA6IFtbdGhpcy5feDAsIHRoaXMuX3kwXSwgW3RoaXMuX3gxLCB0aGlzLl95MV1dOwogICAgfQoKICAgIGZ1bmN0aW9uIFF1YWQkMShub2RlLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB0aGlzLm5vZGUgPSBub2RlOwogICAgICB0aGlzLngwID0geDA7CiAgICAgIHRoaXMueTAgPSB5MDsKICAgICAgdGhpcy54MSA9IHgxOwogICAgICB0aGlzLnkxID0geTE7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9maW5kJDEoeCwgeSwgcmFkaXVzKSB7CiAgICAgIHZhciBkYXRhLAogICAgICAgICAgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSwKICAgICAgICAgIHkxLAogICAgICAgICAgeDIsCiAgICAgICAgICB5MiwKICAgICAgICAgIHgzID0gdGhpcy5feDEsCiAgICAgICAgICB5MyA9IHRoaXMuX3kxLAogICAgICAgICAgcXVhZHMgPSBbXSwKICAgICAgICAgIG5vZGUgPSB0aGlzLl9yb290LAogICAgICAgICAgcSwKICAgICAgICAgIGk7CgogICAgICBpZiAobm9kZSkgcXVhZHMucHVzaChuZXcgUXVhZCQxKG5vZGUsIHgwLCB5MCwgeDMsIHkzKSk7CiAgICAgIGlmIChyYWRpdXMgPT0gbnVsbCkgcmFkaXVzID0gSW5maW5pdHk7CiAgICAgIGVsc2UgewogICAgICAgIHgwID0geCAtIHJhZGl1cywgeTAgPSB5IC0gcmFkaXVzOwogICAgICAgIHgzID0geCArIHJhZGl1cywgeTMgPSB5ICsgcmFkaXVzOwogICAgICAgIHJhZGl1cyAqPSByYWRpdXM7CiAgICAgIH0KCiAgICAgIHdoaWxlIChxID0gcXVhZHMucG9wKCkpIHsKCiAgICAgICAgLy8gU3RvcCBzZWFyY2hpbmcgaWYgdGhpcyBxdWFkcmFudCBjYW7igJl0IGNvbnRhaW4gYSBjbG9zZXIgbm9kZS4KICAgICAgICBpZiAoIShub2RlID0gcS5ub2RlKQogICAgICAgICAgICB8fCAoeDEgPSBxLngwKSA+IHgzCiAgICAgICAgICAgIHx8ICh5MSA9IHEueTApID4geTMKICAgICAgICAgICAgfHwgKHgyID0gcS54MSkgPCB4MAogICAgICAgICAgICB8fCAoeTIgPSBxLnkxKSA8IHkwKSBjb250aW51ZTsKCiAgICAgICAgLy8gQmlzZWN0IHRoZSBjdXJyZW50IHF1YWRyYW50LgogICAgICAgIGlmIChub2RlLmxlbmd0aCkgewogICAgICAgICAgdmFyIHhtID0gKHgxICsgeDIpIC8gMiwKICAgICAgICAgICAgICB5bSA9ICh5MSArIHkyKSAvIDI7CgogICAgICAgICAgcXVhZHMucHVzaCgKICAgICAgICAgICAgbmV3IFF1YWQkMShub2RlWzNdLCB4bSwgeW0sIHgyLCB5MiksCiAgICAgICAgICAgIG5ldyBRdWFkJDEobm9kZVsyXSwgeDEsIHltLCB4bSwgeTIpLAogICAgICAgICAgICBuZXcgUXVhZCQxKG5vZGVbMV0sIHhtLCB5MSwgeDIsIHltKSwKICAgICAgICAgICAgbmV3IFF1YWQkMShub2RlWzBdLCB4MSwgeTEsIHhtLCB5bSkKICAgICAgICAgICk7CgogICAgICAgICAgLy8gVmlzaXQgdGhlIGNsb3Nlc3QgcXVhZHJhbnQgZmlyc3QuCiAgICAgICAgICBpZiAoaSA9ICh5ID49IHltKSA8PCAxIHwgKHggPj0geG0pKSB7CiAgICAgICAgICAgIHEgPSBxdWFkc1txdWFkcy5sZW5ndGggLSAxXTsKICAgICAgICAgICAgcXVhZHNbcXVhZHMubGVuZ3RoIC0gMV0gPSBxdWFkc1txdWFkcy5sZW5ndGggLSAxIC0gaV07CiAgICAgICAgICAgIHF1YWRzW3F1YWRzLmxlbmd0aCAtIDEgLSBpXSA9IHE7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBWaXNpdCB0aGlzIHBvaW50LiAoVmlzaXRpbmcgY29pbmNpZGVudCBwb2ludHMgaXNu4oCZdCBuZWNlc3NhcnkhKQogICAgICAgIGVsc2UgewogICAgICAgICAgdmFyIGR4ID0geCAtICt0aGlzLl94LmNhbGwobnVsbCwgbm9kZS5kYXRhKSwKICAgICAgICAgICAgICBkeSA9IHkgLSArdGhpcy5feS5jYWxsKG51bGwsIG5vZGUuZGF0YSksCiAgICAgICAgICAgICAgZDIgPSBkeCAqIGR4ICsgZHkgKiBkeTsKICAgICAgICAgIGlmIChkMiA8IHJhZGl1cykgewogICAgICAgICAgICB2YXIgZCA9IE1hdGguc3FydChyYWRpdXMgPSBkMik7CiAgICAgICAgICAgIHgwID0geCAtIGQsIHkwID0geSAtIGQ7CiAgICAgICAgICAgIHgzID0geCArIGQsIHkzID0geSArIGQ7CiAgICAgICAgICAgIGRhdGEgPSBub2RlLmRhdGE7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZGF0YTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3JlbW92ZSQxKGQpIHsKICAgICAgaWYgKGlzTmFOKHggPSArdGhpcy5feC5jYWxsKG51bGwsIGQpKSB8fCBpc05hTih5ID0gK3RoaXMuX3kuY2FsbChudWxsLCBkKSkpIHJldHVybiB0aGlzOyAvLyBpZ25vcmUgaW52YWxpZCBwb2ludHMKCiAgICAgIHZhciBwYXJlbnQsCiAgICAgICAgICBub2RlID0gdGhpcy5fcm9vdCwKICAgICAgICAgIHJldGFpbmVyLAogICAgICAgICAgcHJldmlvdXMsCiAgICAgICAgICBuZXh0LAogICAgICAgICAgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSA9IHRoaXMuX3gxLAogICAgICAgICAgeTEgPSB0aGlzLl95MSwKICAgICAgICAgIHgsCiAgICAgICAgICB5LAogICAgICAgICAgeG0sCiAgICAgICAgICB5bSwKICAgICAgICAgIHJpZ2h0LAogICAgICAgICAgYm90dG9tLAogICAgICAgICAgaSwKICAgICAgICAgIGo7CgogICAgICAvLyBJZiB0aGUgdHJlZSBpcyBlbXB0eSwgaW5pdGlhbGl6ZSB0aGUgcm9vdCBhcyBhIGxlYWYuCiAgICAgIGlmICghbm9kZSkgcmV0dXJuIHRoaXM7CgogICAgICAvLyBGaW5kIHRoZSBsZWFmIG5vZGUgZm9yIHRoZSBwb2ludC4KICAgICAgLy8gV2hpbGUgZGVzY2VuZGluZywgYWxzbyByZXRhaW4gdGhlIGRlZXBlc3QgcGFyZW50IHdpdGggYSBub24tcmVtb3ZlZCBzaWJsaW5nLgogICAgICBpZiAobm9kZS5sZW5ndGgpIHdoaWxlICh0cnVlKSB7CiAgICAgICAgaWYgKHJpZ2h0ID0geCA+PSAoeG0gPSAoeDAgKyB4MSkgLyAyKSkgeDAgPSB4bTsgZWxzZSB4MSA9IHhtOwogICAgICAgIGlmIChib3R0b20gPSB5ID49ICh5bSA9ICh5MCArIHkxKSAvIDIpKSB5MCA9IHltOyBlbHNlIHkxID0geW07CiAgICAgICAgaWYgKCEocGFyZW50ID0gbm9kZSwgbm9kZSA9IG5vZGVbaSA9IGJvdHRvbSA8PCAxIHwgcmlnaHRdKSkgcmV0dXJuIHRoaXM7CiAgICAgICAgaWYgKCFub2RlLmxlbmd0aCkgYnJlYWs7CiAgICAgICAgaWYgKHBhcmVudFsoaSArIDEpICYgM10gfHwgcGFyZW50WyhpICsgMikgJiAzXSB8fCBwYXJlbnRbKGkgKyAzKSAmIDNdKSByZXRhaW5lciA9IHBhcmVudCwgaiA9IGk7CiAgICAgIH0KCiAgICAgIC8vIEZpbmQgdGhlIHBvaW50IHRvIHJlbW92ZS4KICAgICAgd2hpbGUgKG5vZGUuZGF0YSAhPT0gZCkgaWYgKCEocHJldmlvdXMgPSBub2RlLCBub2RlID0gbm9kZS5uZXh0KSkgcmV0dXJuIHRoaXM7CiAgICAgIGlmIChuZXh0ID0gbm9kZS5uZXh0KSBkZWxldGUgbm9kZS5uZXh0OwoKICAgICAgLy8gSWYgdGhlcmUgYXJlIG11bHRpcGxlIGNvaW5jaWRlbnQgcG9pbnRzLCByZW1vdmUganVzdCB0aGUgcG9pbnQuCiAgICAgIGlmIChwcmV2aW91cykgcmV0dXJuIChuZXh0ID8gcHJldmlvdXMubmV4dCA9IG5leHQgOiBkZWxldGUgcHJldmlvdXMubmV4dCksIHRoaXM7CgogICAgICAvLyBJZiB0aGlzIGlzIHRoZSByb290IHBvaW50LCByZW1vdmUgaXQuCiAgICAgIGlmICghcGFyZW50KSByZXR1cm4gdGhpcy5fcm9vdCA9IG5leHQsIHRoaXM7CgogICAgICAvLyBSZW1vdmUgdGhpcyBsZWFmLgogICAgICBuZXh0ID8gcGFyZW50W2ldID0gbmV4dCA6IGRlbGV0ZSBwYXJlbnRbaV07CgogICAgICAvLyBJZiB0aGUgcGFyZW50IG5vdyBjb250YWlucyBleGFjdGx5IG9uZSBsZWFmLCBjb2xsYXBzZSBzdXBlcmZsdW91cyBwYXJlbnRzLgogICAgICBpZiAoKG5vZGUgPSBwYXJlbnRbMF0gfHwgcGFyZW50WzFdIHx8IHBhcmVudFsyXSB8fCBwYXJlbnRbM10pCiAgICAgICAgICAmJiBub2RlID09PSAocGFyZW50WzNdIHx8IHBhcmVudFsyXSB8fCBwYXJlbnRbMV0gfHwgcGFyZW50WzBdKQogICAgICAgICAgJiYgIW5vZGUubGVuZ3RoKSB7CiAgICAgICAgaWYgKHJldGFpbmVyKSByZXRhaW5lcltqXSA9IG5vZGU7CiAgICAgICAgZWxzZSB0aGlzLl9yb290ID0gbm9kZTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlQWxsJDEoZGF0YSkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGRhdGEubGVuZ3RoOyBpIDwgbjsgKytpKSB0aGlzLnJlbW92ZShkYXRhW2ldKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9yb290JDEoKSB7CiAgICAgIHJldHVybiB0aGlzLl9yb290OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfc2l6ZSQxKCkgewogICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgIHRoaXMudmlzaXQoZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmICghbm9kZS5sZW5ndGgpIGRvICsrc2l6ZTsgd2hpbGUgKG5vZGUgPSBub2RlLm5leHQpCiAgICAgIH0pOwogICAgICByZXR1cm4gc2l6ZTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3Zpc2l0JDEoY2FsbGJhY2spIHsKICAgICAgdmFyIHF1YWRzID0gW10sIHEsIG5vZGUgPSB0aGlzLl9yb290LCBjaGlsZCwgeDAsIHkwLCB4MSwgeTE7CiAgICAgIGlmIChub2RlKSBxdWFkcy5wdXNoKG5ldyBRdWFkJDEobm9kZSwgdGhpcy5feDAsIHRoaXMuX3kwLCB0aGlzLl94MSwgdGhpcy5feTEpKTsKICAgICAgd2hpbGUgKHEgPSBxdWFkcy5wb3AoKSkgewogICAgICAgIGlmICghY2FsbGJhY2sobm9kZSA9IHEubm9kZSwgeDAgPSBxLngwLCB5MCA9IHEueTAsIHgxID0gcS54MSwgeTEgPSBxLnkxKSAmJiBub2RlLmxlbmd0aCkgewogICAgICAgICAgdmFyIHhtID0gKHgwICsgeDEpIC8gMiwgeW0gPSAoeTAgKyB5MSkgLyAyOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVszXSkgcXVhZHMucHVzaChuZXcgUXVhZCQxKGNoaWxkLCB4bSwgeW0sIHgxLCB5MSkpOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVsyXSkgcXVhZHMucHVzaChuZXcgUXVhZCQxKGNoaWxkLCB4MCwgeW0sIHhtLCB5MSkpOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVsxXSkgcXVhZHMucHVzaChuZXcgUXVhZCQxKGNoaWxkLCB4bSwgeTAsIHgxLCB5bSkpOwogICAgICAgICAgaWYgKGNoaWxkID0gbm9kZVswXSkgcXVhZHMucHVzaChuZXcgUXVhZCQxKGNoaWxkLCB4MCwgeTAsIHhtLCB5bSkpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3Zpc2l0QWZ0ZXIkMShjYWxsYmFjaykgewogICAgICB2YXIgcXVhZHMgPSBbXSwgbmV4dCA9IFtdLCBxOwogICAgICBpZiAodGhpcy5fcm9vdCkgcXVhZHMucHVzaChuZXcgUXVhZCQxKHRoaXMuX3Jvb3QsIHRoaXMuX3gwLCB0aGlzLl95MCwgdGhpcy5feDEsIHRoaXMuX3kxKSk7CiAgICAgIHdoaWxlIChxID0gcXVhZHMucG9wKCkpIHsKICAgICAgICB2YXIgbm9kZSA9IHEubm9kZTsKICAgICAgICBpZiAobm9kZS5sZW5ndGgpIHsKICAgICAgICAgIHZhciBjaGlsZCwgeDAgPSBxLngwLCB5MCA9IHEueTAsIHgxID0gcS54MSwgeTEgPSBxLnkxLCB4bSA9ICh4MCArIHgxKSAvIDIsIHltID0gKHkwICsgeTEpIC8gMjsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMF0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMShjaGlsZCwgeDAsIHkwLCB4bSwgeW0pKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMV0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMShjaGlsZCwgeG0sIHkwLCB4MSwgeW0pKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMl0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMShjaGlsZCwgeDAsIHltLCB4bSwgeTEpKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbM10pIHF1YWRzLnB1c2gobmV3IFF1YWQkMShjaGlsZCwgeG0sIHltLCB4MSwgeTEpKTsKICAgICAgICB9CiAgICAgICAgbmV4dC5wdXNoKHEpOwogICAgICB9CiAgICAgIHdoaWxlIChxID0gbmV4dC5wb3AoKSkgewogICAgICAgIGNhbGxiYWNrKHEubm9kZSwgcS54MCwgcS55MCwgcS54MSwgcS55MSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFgkMihkKSB7CiAgICAgIHJldHVybiBkWzBdOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfeCQxKF8pIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGhpcy5feCA9IF8sIHRoaXMpIDogdGhpcy5feDsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0WSQyKGQpIHsKICAgICAgcmV0dXJuIGRbMV07CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV95JDEoXykgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0aGlzLl95ID0gXywgdGhpcykgOiB0aGlzLl95OwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YWR0cmVlJDEobm9kZXMsIHgsIHkpIHsKICAgICAgdmFyIHRyZWUgPSBuZXcgUXVhZHRyZWUkMSh4ID09IG51bGwgPyBkZWZhdWx0WCQyIDogeCwgeSA9PSBudWxsID8gZGVmYXVsdFkkMiA6IHksIE5hTiwgTmFOLCBOYU4sIE5hTik7CiAgICAgIHJldHVybiBub2RlcyA9PSBudWxsID8gdHJlZSA6IHRyZWUuYWRkQWxsKG5vZGVzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBRdWFkdHJlZSQxKHgsIHksIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIHRoaXMuX3ggPSB4OwogICAgICB0aGlzLl95ID0geTsKICAgICAgdGhpcy5feDAgPSB4MDsKICAgICAgdGhpcy5feTAgPSB5MDsKICAgICAgdGhpcy5feDEgPSB4MTsKICAgICAgdGhpcy5feTEgPSB5MTsKICAgICAgdGhpcy5fcm9vdCA9IHVuZGVmaW5lZDsKICAgIH0KCiAgICBmdW5jdGlvbiBsZWFmX2NvcHkkMShsZWFmKSB7CiAgICAgIHZhciBjb3B5ID0ge2RhdGE6IGxlYWYuZGF0YX0sIG5leHQgPSBjb3B5OwogICAgICB3aGlsZSAobGVhZiA9IGxlYWYubmV4dCkgbmV4dCA9IG5leHQubmV4dCA9IHtkYXRhOiBsZWFmLmRhdGF9OwogICAgICByZXR1cm4gY29weTsKICAgIH0KCiAgICB2YXIgdHJlZVByb3RvJDEgPSBxdWFkdHJlZSQxLnByb3RvdHlwZSA9IFF1YWR0cmVlJDEucHJvdG90eXBlOwoKICAgIHRyZWVQcm90byQxLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIGNvcHkgPSBuZXcgUXVhZHRyZWUkMSh0aGlzLl94LCB0aGlzLl95LCB0aGlzLl94MCwgdGhpcy5feTAsIHRoaXMuX3gxLCB0aGlzLl95MSksCiAgICAgICAgICBub2RlID0gdGhpcy5fcm9vdCwKICAgICAgICAgIG5vZGVzLAogICAgICAgICAgY2hpbGQ7CgogICAgICBpZiAoIW5vZGUpIHJldHVybiBjb3B5OwoKICAgICAgaWYgKCFub2RlLmxlbmd0aCkgcmV0dXJuIGNvcHkuX3Jvb3QgPSBsZWFmX2NvcHkkMShub2RlKSwgY29weTsKCiAgICAgIG5vZGVzID0gW3tzb3VyY2U6IG5vZGUsIHRhcmdldDogY29weS5fcm9vdCA9IG5ldyBBcnJheSg0KX1dOwogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCA0OyArK2kpIHsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGUuc291cmNlW2ldKSB7CiAgICAgICAgICAgIGlmIChjaGlsZC5sZW5ndGgpIG5vZGVzLnB1c2goe3NvdXJjZTogY2hpbGQsIHRhcmdldDogbm9kZS50YXJnZXRbaV0gPSBuZXcgQXJyYXkoNCl9KTsKICAgICAgICAgICAgZWxzZSBub2RlLnRhcmdldFtpXSA9IGxlYWZfY29weSQxKGNoaWxkKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBjb3B5OwogICAgfTsKCiAgICB0cmVlUHJvdG8kMS5hZGQgPSB0cmVlX2FkZCQxOwogICAgdHJlZVByb3RvJDEuYWRkQWxsID0gYWRkQWxsJDE7CiAgICB0cmVlUHJvdG8kMS5jb3ZlciA9IHRyZWVfY292ZXIkMTsKICAgIHRyZWVQcm90byQxLmRhdGEgPSB0cmVlX2RhdGEkMTsKICAgIHRyZWVQcm90byQxLmV4dGVudCA9IHRyZWVfZXh0ZW50JDE7CiAgICB0cmVlUHJvdG8kMS5maW5kID0gdHJlZV9maW5kJDE7CiAgICB0cmVlUHJvdG8kMS5yZW1vdmUgPSB0cmVlX3JlbW92ZSQxOwogICAgdHJlZVByb3RvJDEucmVtb3ZlQWxsID0gcmVtb3ZlQWxsJDE7CiAgICB0cmVlUHJvdG8kMS5yb290ID0gdHJlZV9yb290JDE7CiAgICB0cmVlUHJvdG8kMS5zaXplID0gdHJlZV9zaXplJDE7CiAgICB0cmVlUHJvdG8kMS52aXNpdCA9IHRyZWVfdmlzaXQkMTsKICAgIHRyZWVQcm90byQxLnZpc2l0QWZ0ZXIgPSB0cmVlX3Zpc2l0QWZ0ZXIkMTsKICAgIHRyZWVQcm90byQxLnggPSB0cmVlX3gkMTsKICAgIHRyZWVQcm90byQxLnkgPSB0cmVlX3kkMTsKCiAgICBmdW5jdGlvbiB4JDUoZCkgewogICAgICByZXR1cm4gZC54ICsgZC52eDsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDUoZCkgewogICAgICByZXR1cm4gZC55ICsgZC52eTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xsaWRlJDEocmFkaXVzKSB7CiAgICAgIHZhciBub2RlcywKICAgICAgICAgIHJhZGlpLAogICAgICAgICAgc3RyZW5ndGggPSAxLAogICAgICAgICAgaXRlcmF0aW9ucyA9IDE7CgogICAgICBpZiAodHlwZW9mIHJhZGl1cyAhPT0gImZ1bmN0aW9uIikgcmFkaXVzID0gY29uc3RhbnQkbChyYWRpdXMgPT0gbnVsbCA/IDEgOiArcmFkaXVzKTsKCiAgICAgIGZ1bmN0aW9uIGZvcmNlKCkgewogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoLAogICAgICAgICAgICB0cmVlLAogICAgICAgICAgICBub2RlLAogICAgICAgICAgICB4aSwKICAgICAgICAgICAgeWksCiAgICAgICAgICAgIHJpLAogICAgICAgICAgICByaTI7CgogICAgICAgIGZvciAodmFyIGsgPSAwOyBrIDwgaXRlcmF0aW9uczsgKytrKSB7CiAgICAgICAgICB0cmVlID0gcXVhZHRyZWUkMShub2RlcywgeCQ1LCB5JDUpLnZpc2l0QWZ0ZXIocHJlcGFyZSk7CiAgICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIG5vZGUgPSBub2Rlc1tpXTsKICAgICAgICAgICAgcmkgPSByYWRpaVtub2RlLmluZGV4XSwgcmkyID0gcmkgKiByaTsKICAgICAgICAgICAgeGkgPSBub2RlLnggKyBub2RlLnZ4OwogICAgICAgICAgICB5aSA9IG5vZGUueSArIG5vZGUudnk7CiAgICAgICAgICAgIHRyZWUudmlzaXQoYXBwbHkpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gYXBwbHkocXVhZCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgICAgIHZhciBkYXRhID0gcXVhZC5kYXRhLCByaiA9IHF1YWQuciwgciA9IHJpICsgcmo7CiAgICAgICAgICBpZiAoZGF0YSkgewogICAgICAgICAgICBpZiAoZGF0YS5pbmRleCA+IG5vZGUuaW5kZXgpIHsKICAgICAgICAgICAgICB2YXIgeCA9IHhpIC0gZGF0YS54IC0gZGF0YS52eCwKICAgICAgICAgICAgICAgICAgeSA9IHlpIC0gZGF0YS55IC0gZGF0YS52eSwKICAgICAgICAgICAgICAgICAgbCA9IHggKiB4ICsgeSAqIHk7CiAgICAgICAgICAgICAgaWYgKGwgPCByICogcikgewogICAgICAgICAgICAgICAgaWYgKHggPT09IDApIHggPSBqaWdnbGUkMSgpLCBsICs9IHggKiB4OwogICAgICAgICAgICAgICAgaWYgKHkgPT09IDApIHkgPSBqaWdnbGUkMSgpLCBsICs9IHkgKiB5OwogICAgICAgICAgICAgICAgbCA9IChyIC0gKGwgPSBNYXRoLnNxcnQobCkpKSAvIGwgKiBzdHJlbmd0aDsKICAgICAgICAgICAgICAgIG5vZGUudnggKz0gKHggKj0gbCkgKiAociA9IChyaiAqPSByaikgLyAocmkyICsgcmopKTsKICAgICAgICAgICAgICAgIG5vZGUudnkgKz0gKHkgKj0gbCkgKiByOwogICAgICAgICAgICAgICAgZGF0YS52eCAtPSB4ICogKHIgPSAxIC0gcik7CiAgICAgICAgICAgICAgICBkYXRhLnZ5IC09IHkgKiByOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4geDAgPiB4aSArIHIgfHwgeDEgPCB4aSAtIHIgfHwgeTAgPiB5aSArIHIgfHwgeTEgPCB5aSAtIHI7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBwcmVwYXJlKHF1YWQpIHsKICAgICAgICBpZiAocXVhZC5kYXRhKSByZXR1cm4gcXVhZC5yID0gcmFkaWlbcXVhZC5kYXRhLmluZGV4XTsKICAgICAgICBmb3IgKHZhciBpID0gcXVhZC5yID0gMDsgaSA8IDQ7ICsraSkgewogICAgICAgICAgaWYgKHF1YWRbaV0gJiYgcXVhZFtpXS5yID4gcXVhZC5yKSB7CiAgICAgICAgICAgIHF1YWQuciA9IHF1YWRbaV0ucjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoLCBub2RlOwogICAgICAgIHJhZGlpID0gbmV3IEFycmF5KG4pOwogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIG5vZGUgPSBub2Rlc1tpXSwgcmFkaWlbbm9kZS5pbmRleF0gPSArcmFkaXVzKG5vZGUsIGksIG5vZGVzKTsKICAgICAgfQoKICAgICAgZm9yY2UuaW5pdGlhbGl6ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBub2RlcyA9IF87CiAgICAgICAgaW5pdGlhbGl6ZSgpOwogICAgICB9OwoKICAgICAgZm9yY2UuaXRlcmF0aW9ucyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpdGVyYXRpb25zID0gK18sIGZvcmNlKSA6IGl0ZXJhdGlvbnM7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9ICtfLCBmb3JjZSkgOiBzdHJlbmd0aDsKICAgICAgfTsKCiAgICAgIGZvcmNlLnJhZGl1cyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRsKCtfKSwgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiByYWRpdXM7CiAgICAgIH07CgogICAgICByZXR1cm4gZm9yY2U7CiAgICB9CgogICAgdmFyIHByZWZpeCQyID0gIiQiOwoKICAgIGZ1bmN0aW9uIE1hcCQzKCkge30KCiAgICBNYXAkMy5wcm90b3R5cGUgPSBtYXAkNi5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBNYXAkMywKICAgICAgaGFzOiBmdW5jdGlvbihrZXkpIHsKICAgICAgICByZXR1cm4gKHByZWZpeCQyICsga2V5KSBpbiB0aGlzOwogICAgICB9LAogICAgICBnZXQ6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHJldHVybiB0aGlzW3ByZWZpeCQyICsga2V5XTsKICAgICAgfSwKICAgICAgc2V0OiBmdW5jdGlvbihrZXksIHZhbHVlKSB7CiAgICAgICAgdGhpc1twcmVmaXgkMiArIGtleV0gPSB2YWx1ZTsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgcmVtb3ZlOiBmdW5jdGlvbihrZXkpIHsKICAgICAgICB2YXIgcHJvcGVydHkgPSBwcmVmaXgkMiArIGtleTsKICAgICAgICByZXR1cm4gcHJvcGVydHkgaW4gdGhpcyAmJiBkZWxldGUgdGhpc1twcm9wZXJ0eV07CiAgICAgIH0sCiAgICAgIGNsZWFyOiBmdW5jdGlvbigpIHsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQyKSBkZWxldGUgdGhpc1twcm9wZXJ0eV07CiAgICAgIH0sCiAgICAgIGtleXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBrZXlzID0gW107CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMikga2V5cy5wdXNoKHByb3BlcnR5LnNsaWNlKDEpKTsKICAgICAgICByZXR1cm4ga2V5czsKICAgICAgfSwKICAgICAgdmFsdWVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWVzID0gW107CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMikgdmFsdWVzLnB1c2godGhpc1twcm9wZXJ0eV0pOwogICAgICAgIHJldHVybiB2YWx1ZXM7CiAgICAgIH0sCiAgICAgIGVudHJpZXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBlbnRyaWVzID0gW107CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMikgZW50cmllcy5wdXNoKHtrZXk6IHByb3BlcnR5LnNsaWNlKDEpLCB2YWx1ZTogdGhpc1twcm9wZXJ0eV19KTsKICAgICAgICByZXR1cm4gZW50cmllczsKICAgICAgfSwKICAgICAgc2l6ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNpemUgPSAwOwogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4JDIpICsrc2l6ZTsKICAgICAgICByZXR1cm4gc2l6ZTsKICAgICAgfSwKICAgICAgZW1wdHk6IGZ1bmN0aW9uKCkgewogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4JDIpIHJldHVybiBmYWxzZTsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfSwKICAgICAgZWFjaDogZnVuY3Rpb24oZikgewogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4JDIpIGYodGhpc1twcm9wZXJ0eV0sIHByb3BlcnR5LnNsaWNlKDEpLCB0aGlzKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBtYXAkNihvYmplY3QsIGYpIHsKICAgICAgdmFyIG1hcCA9IG5ldyBNYXAkMzsKCiAgICAgIC8vIENvcHkgY29uc3RydWN0b3IuCiAgICAgIGlmIChvYmplY3QgaW5zdGFuY2VvZiBNYXAkMykgb2JqZWN0LmVhY2goZnVuY3Rpb24odmFsdWUsIGtleSkgeyBtYXAuc2V0KGtleSwgdmFsdWUpOyB9KTsKCiAgICAgIC8vIEluZGV4IGFycmF5IGJ5IG51bWVyaWMgaW5kZXggb3Igc3BlY2lmaWVkIGtleSBmdW5jdGlvbi4KICAgICAgZWxzZSBpZiAoQXJyYXkuaXNBcnJheShvYmplY3QpKSB7CiAgICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgICAgbiA9IG9iamVjdC5sZW5ndGgsCiAgICAgICAgICAgIG87CgogICAgICAgIGlmIChmID09IG51bGwpIHdoaWxlICgrK2kgPCBuKSBtYXAuc2V0KGksIG9iamVjdFtpXSk7CiAgICAgICAgZWxzZSB3aGlsZSAoKytpIDwgbikgbWFwLnNldChmKG8gPSBvYmplY3RbaV0sIGksIG9iamVjdCksIG8pOwogICAgICB9CgogICAgICAvLyBDb252ZXJ0IG9iamVjdCB0byBtYXAuCiAgICAgIGVsc2UgaWYgKG9iamVjdCkgZm9yICh2YXIga2V5IGluIG9iamVjdCkgbWFwLnNldChrZXksIG9iamVjdFtrZXldKTsKCiAgICAgIHJldHVybiBtYXA7CiAgICB9CgogICAgZnVuY3Rpb24gU2V0JDMoKSB7fQoKICAgIHZhciBwcm90byQzID0gbWFwJDYucHJvdG90eXBlOwoKICAgIFNldCQzLnByb3RvdHlwZSA9IHNldCQ5LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFNldCQzLAogICAgICBoYXM6IHByb3RvJDMuaGFzLAogICAgICBhZGQ6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgdmFsdWUgKz0gIiI7CiAgICAgICAgdGhpc1twcmVmaXgkMiArIHZhbHVlXSA9IHZhbHVlOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICByZW1vdmU6IHByb3RvJDMucmVtb3ZlLAogICAgICBjbGVhcjogcHJvdG8kMy5jbGVhciwKICAgICAgdmFsdWVzOiBwcm90byQzLmtleXMsCiAgICAgIHNpemU6IHByb3RvJDMuc2l6ZSwKICAgICAgZW1wdHk6IHByb3RvJDMuZW1wdHksCiAgICAgIGVhY2g6IHByb3RvJDMuZWFjaAogICAgfTsKCiAgICBmdW5jdGlvbiBzZXQkOShvYmplY3QsIGYpIHsKICAgICAgdmFyIHNldCA9IG5ldyBTZXQkMzsKCiAgICAgIC8vIENvcHkgY29uc3RydWN0b3IuCiAgICAgIGlmIChvYmplY3QgaW5zdGFuY2VvZiBTZXQkMykgb2JqZWN0LmVhY2goZnVuY3Rpb24odmFsdWUpIHsgc2V0LmFkZCh2YWx1ZSk7IH0pOwoKICAgICAgLy8gT3RoZXJ3aXNlLCBhc3N1bWUgaXTigJlzIGFuIGFycmF5LgogICAgICBlbHNlIGlmIChvYmplY3QpIHsKICAgICAgICB2YXIgaSA9IC0xLCBuID0gb2JqZWN0Lmxlbmd0aDsKICAgICAgICBpZiAoZiA9PSBudWxsKSB3aGlsZSAoKytpIDwgbikgc2V0LmFkZChvYmplY3RbaV0pOwogICAgICAgIGVsc2Ugd2hpbGUgKCsraSA8IG4pIHNldC5hZGQoZihvYmplY3RbaV0sIGksIG9iamVjdCkpOwogICAgICB9CgogICAgICByZXR1cm4gc2V0OwogICAgfQoKICAgIGZ1bmN0aW9uIGluZGV4JDQoZCkgewogICAgICByZXR1cm4gZC5pbmRleDsKICAgIH0KCiAgICBmdW5jdGlvbiBmaW5kJDEobm9kZUJ5SWQsIG5vZGVJZCkgewogICAgICB2YXIgbm9kZSA9IG5vZGVCeUlkLmdldChub2RlSWQpOwogICAgICBpZiAoIW5vZGUpIHRocm93IG5ldyBFcnJvcigibWlzc2luZzogIiArIG5vZGVJZCk7CiAgICAgIHJldHVybiBub2RlOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmskMyhsaW5rcykgewogICAgICB2YXIgaWQgPSBpbmRleCQ0LAogICAgICAgICAgc3RyZW5ndGggPSBkZWZhdWx0U3RyZW5ndGgsCiAgICAgICAgICBzdHJlbmd0aHMsCiAgICAgICAgICBkaXN0YW5jZSA9IGNvbnN0YW50JGwoMzApLAogICAgICAgICAgZGlzdGFuY2VzLAogICAgICAgICAgbm9kZXMsCiAgICAgICAgICBjb3VudCwKICAgICAgICAgIGJpYXMsCiAgICAgICAgICBpdGVyYXRpb25zID0gMTsKCiAgICAgIGlmIChsaW5rcyA9PSBudWxsKSBsaW5rcyA9IFtdOwoKICAgICAgZnVuY3Rpb24gZGVmYXVsdFN0cmVuZ3RoKGxpbmspIHsKICAgICAgICByZXR1cm4gMSAvIE1hdGgubWluKGNvdW50W2xpbmsuc291cmNlLmluZGV4XSwgY291bnRbbGluay50YXJnZXQuaW5kZXhdKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9yY2UoYWxwaGEpIHsKICAgICAgICBmb3IgKHZhciBrID0gMCwgbiA9IGxpbmtzLmxlbmd0aDsgayA8IGl0ZXJhdGlvbnM7ICsraykgewogICAgICAgICAgZm9yICh2YXIgaSA9IDAsIGxpbmssIHNvdXJjZSwgdGFyZ2V0LCB4LCB5LCBsLCBiOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGxpbmsgPSBsaW5rc1tpXSwgc291cmNlID0gbGluay5zb3VyY2UsIHRhcmdldCA9IGxpbmsudGFyZ2V0OwogICAgICAgICAgICB4ID0gdGFyZ2V0LnggKyB0YXJnZXQudnggLSBzb3VyY2UueCAtIHNvdXJjZS52eCB8fCBqaWdnbGUkMSgpOwogICAgICAgICAgICB5ID0gdGFyZ2V0LnkgKyB0YXJnZXQudnkgLSBzb3VyY2UueSAtIHNvdXJjZS52eSB8fCBqaWdnbGUkMSgpOwogICAgICAgICAgICBsID0gTWF0aC5zcXJ0KHggKiB4ICsgeSAqIHkpOwogICAgICAgICAgICBsID0gKGwgLSBkaXN0YW5jZXNbaV0pIC8gbCAqIGFscGhhICogc3RyZW5ndGhzW2ldOwogICAgICAgICAgICB4ICo9IGwsIHkgKj0gbDsKICAgICAgICAgICAgdGFyZ2V0LnZ4IC09IHggKiAoYiA9IGJpYXNbaV0pOwogICAgICAgICAgICB0YXJnZXQudnkgLT0geSAqIGI7CiAgICAgICAgICAgIHNvdXJjZS52eCArPSB4ICogKGIgPSAxIC0gYik7CiAgICAgICAgICAgIHNvdXJjZS52eSArPSB5ICogYjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwoKICAgICAgICB2YXIgaSwKICAgICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgICAgbSA9IGxpbmtzLmxlbmd0aCwKICAgICAgICAgICAgbm9kZUJ5SWQgPSBtYXAkNihub2RlcywgaWQpLAogICAgICAgICAgICBsaW5rOwoKICAgICAgICBmb3IgKGkgPSAwLCBjb3VudCA9IG5ldyBBcnJheShuKTsgaSA8IG07ICsraSkgewogICAgICAgICAgbGluayA9IGxpbmtzW2ldLCBsaW5rLmluZGV4ID0gaTsKICAgICAgICAgIGlmICh0eXBlb2YgbGluay5zb3VyY2UgIT09ICJvYmplY3QiKSBsaW5rLnNvdXJjZSA9IGZpbmQkMShub2RlQnlJZCwgbGluay5zb3VyY2UpOwogICAgICAgICAgaWYgKHR5cGVvZiBsaW5rLnRhcmdldCAhPT0gIm9iamVjdCIpIGxpbmsudGFyZ2V0ID0gZmluZCQxKG5vZGVCeUlkLCBsaW5rLnRhcmdldCk7CiAgICAgICAgICBjb3VudFtsaW5rLnNvdXJjZS5pbmRleF0gPSAoY291bnRbbGluay5zb3VyY2UuaW5kZXhdIHx8IDApICsgMTsKICAgICAgICAgIGNvdW50W2xpbmsudGFyZ2V0LmluZGV4XSA9IChjb3VudFtsaW5rLnRhcmdldC5pbmRleF0gfHwgMCkgKyAxOwogICAgICAgIH0KCiAgICAgICAgZm9yIChpID0gMCwgYmlhcyA9IG5ldyBBcnJheShtKTsgaSA8IG07ICsraSkgewogICAgICAgICAgbGluayA9IGxpbmtzW2ldLCBiaWFzW2ldID0gY291bnRbbGluay5zb3VyY2UuaW5kZXhdIC8gKGNvdW50W2xpbmsuc291cmNlLmluZGV4XSArIGNvdW50W2xpbmsudGFyZ2V0LmluZGV4XSk7CiAgICAgICAgfQoKICAgICAgICBzdHJlbmd0aHMgPSBuZXcgQXJyYXkobSksIGluaXRpYWxpemVTdHJlbmd0aCgpOwogICAgICAgIGRpc3RhbmNlcyA9IG5ldyBBcnJheShtKSwgaW5pdGlhbGl6ZURpc3RhbmNlKCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemVTdHJlbmd0aCgpIHsKICAgICAgICBpZiAoIW5vZGVzKSByZXR1cm47CgogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbGlua3MubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBzdHJlbmd0aHNbaV0gPSArc3RyZW5ndGgobGlua3NbaV0sIGksIGxpbmtzKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemVEaXN0YW5jZSgpIHsKICAgICAgICBpZiAoIW5vZGVzKSByZXR1cm47CgogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbGlua3MubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBkaXN0YW5jZXNbaV0gPSArZGlzdGFuY2UobGlua3NbaV0sIGksIGxpbmtzKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZvcmNlLmluaXRpYWxpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgbm9kZXMgPSBfOwogICAgICAgIGluaXRpYWxpemUoKTsKICAgICAgfTsKCiAgICAgIGZvcmNlLmxpbmtzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGxpbmtzID0gXywgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiBsaW5rczsKICAgICAgfTsKCiAgICAgIGZvcmNlLmlkID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGlkID0gXywgZm9yY2UpIDogaWQ7CiAgICAgIH07CgogICAgICBmb3JjZS5pdGVyYXRpb25zID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGl0ZXJhdGlvbnMgPSArXywgZm9yY2UpIDogaXRlcmF0aW9uczsKICAgICAgfTsKCiAgICAgIGZvcmNlLnN0cmVuZ3RoID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN0cmVuZ3RoID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkbCgrXyksIGluaXRpYWxpemVTdHJlbmd0aCgpLCBmb3JjZSkgOiBzdHJlbmd0aDsKICAgICAgfTsKCiAgICAgIGZvcmNlLmRpc3RhbmNlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRpc3RhbmNlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkbCgrXyksIGluaXRpYWxpemVEaXN0YW5jZSgpLCBmb3JjZSkgOiBkaXN0YW5jZTsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3JjZTsKICAgIH0KCiAgICB2YXIgbm9vcCQ3ID0ge3ZhbHVlOiBmdW5jdGlvbigpIHt9fTsKCiAgICBmdW5jdGlvbiBkaXNwYXRjaCQ0KCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGFyZ3VtZW50cy5sZW5ndGgsIF8gPSB7fSwgdDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICghKHQgPSBhcmd1bWVudHNbaV0gKyAiIikgfHwgKHQgaW4gXykgfHwgL1tccy5dLy50ZXN0KHQpKSB0aHJvdyBuZXcgRXJyb3IoImlsbGVnYWwgdHlwZTogIiArIHQpOwogICAgICAgIF9bdF0gPSBbXTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERpc3BhdGNoJDQoXyk7CiAgICB9CgogICAgZnVuY3Rpb24gRGlzcGF0Y2gkNChfKSB7CiAgICAgIHRoaXMuXyA9IF87CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VUeXBlbmFtZXMkNyh0eXBlbmFtZXMsIHR5cGVzKSB7CiAgICAgIHJldHVybiB0eXBlbmFtZXMudHJpbSgpLnNwbGl0KC9efFxzKy8pLm1hcChmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIG5hbWUgPSAiIiwgaSA9IHQuaW5kZXhPZigiLiIpOwogICAgICAgIGlmIChpID49IDApIG5hbWUgPSB0LnNsaWNlKGkgKyAxKSwgdCA9IHQuc2xpY2UoMCwgaSk7CiAgICAgICAgaWYgKHQgJiYgIXR5cGVzLmhhc093blByb3BlcnR5KHQpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHQpOwogICAgICAgIHJldHVybiB7dHlwZTogdCwgbmFtZTogbmFtZX07CiAgICAgIH0pOwogICAgfQoKICAgIERpc3BhdGNoJDQucHJvdG90eXBlID0gZGlzcGF0Y2gkNC5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBEaXNwYXRjaCQ0LAogICAgICBvbjogZnVuY3Rpb24odHlwZW5hbWUsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIF8gPSB0aGlzLl8sCiAgICAgICAgICAgIFQgPSBwYXJzZVR5cGVuYW1lcyQ3KHR5cGVuYW1lICsgIiIsIF8pLAogICAgICAgICAgICB0LAogICAgICAgICAgICBpID0gLTEsCiAgICAgICAgICAgIG4gPSBULmxlbmd0aDsKCiAgICAgICAgLy8gSWYgbm8gY2FsbGJhY2sgd2FzIHNwZWNpZmllZCwgcmV0dXJuIHRoZSBjYWxsYmFjayBvZiB0aGUgZ2l2ZW4gdHlwZSBhbmQgbmFtZS4KICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoKHQgPSAodHlwZW5hbWUgPSBUW2ldKS50eXBlKSAmJiAodCA9IGdldCQ3KF9bdF0sIHR5cGVuYW1lLm5hbWUpKSkgcmV0dXJuIHQ7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBJZiBhIHR5cGUgd2FzIHNwZWNpZmllZCwgc2V0IHRoZSBjYWxsYmFjayBmb3IgdGhlIGdpdmVuIHR5cGUgYW5kIG5hbWUuCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBpZiBhIG51bGwgY2FsbGJhY2sgd2FzIHNwZWNpZmllZCwgcmVtb3ZlIGNhbGxiYWNrcyBvZiB0aGUgZ2l2ZW4gbmFtZS4KICAgICAgICBpZiAoY2FsbGJhY2sgIT0gbnVsbCAmJiB0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcigiaW52YWxpZCBjYWxsYmFjazogIiArIGNhbGxiYWNrKTsKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaWYgKHQgPSAodHlwZW5hbWUgPSBUW2ldKS50eXBlKSBfW3RdID0gc2V0JGEoX1t0XSwgdHlwZW5hbWUubmFtZSwgY2FsbGJhY2spOwogICAgICAgICAgZWxzZSBpZiAoY2FsbGJhY2sgPT0gbnVsbCkgZm9yICh0IGluIF8pIF9bdF0gPSBzZXQkYShfW3RdLCB0eXBlbmFtZS5uYW1lLCBudWxsKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICBjb3B5OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgY29weSA9IHt9LCBfID0gdGhpcy5fOwogICAgICAgIGZvciAodmFyIHQgaW4gXykgY29weVt0XSA9IF9bdF0uc2xpY2UoKTsKICAgICAgICByZXR1cm4gbmV3IERpc3BhdGNoJDQoY29weSk7CiAgICAgIH0sCiAgICAgIGNhbGw6IGZ1bmN0aW9uKHR5cGUsIHRoYXQpIHsKICAgICAgICBpZiAoKG4gPSBhcmd1bWVudHMubGVuZ3RoIC0gMikgPiAwKSBmb3IgKHZhciBhcmdzID0gbmV3IEFycmF5KG4pLCBpID0gMCwgbiwgdDsgaSA8IG47ICsraSkgYXJnc1tpXSA9IGFyZ3VtZW50c1tpICsgMl07CiAgICAgICAgaWYgKCF0aGlzLl8uaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdHlwZSk7CiAgICAgICAgZm9yICh0ID0gdGhpcy5fW3R5cGVdLCBpID0gMCwgbiA9IHQubGVuZ3RoOyBpIDwgbjsgKytpKSB0W2ldLnZhbHVlLmFwcGx5KHRoYXQsIGFyZ3MpOwogICAgICB9LAogICAgICBhcHBseTogZnVuY3Rpb24odHlwZSwgdGhhdCwgYXJncykgewogICAgICAgIGlmICghdGhpcy5fLmhhc093blByb3BlcnR5KHR5cGUpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHR5cGUpOwogICAgICAgIGZvciAodmFyIHQgPSB0aGlzLl9bdHlwZV0sIGkgPSAwLCBuID0gdC5sZW5ndGg7IGkgPCBuOyArK2kpIHRbaV0udmFsdWUuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gZ2V0JDcodHlwZSwgbmFtZSkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR5cGUubGVuZ3RoLCBjOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKChjID0gdHlwZVtpXSkubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgcmV0dXJuIGMudmFsdWU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc2V0JGEodHlwZSwgbmFtZSwgY2FsbGJhY2spIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0eXBlLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICh0eXBlW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgIHR5cGVbaV0gPSBub29wJDcsIHR5cGUgPSB0eXBlLnNsaWNlKDAsIGkpLmNvbmNhdCh0eXBlLnNsaWNlKGkgKyAxKSk7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwpIHR5cGUucHVzaCh7bmFtZTogbmFtZSwgdmFsdWU6IGNhbGxiYWNrfSk7CiAgICAgIHJldHVybiB0eXBlOwogICAgfQoKICAgIHZhciBmcmFtZSQyID0gMCwgLy8gaXMgYW4gYW5pbWF0aW9uIGZyYW1lIHBlbmRpbmc/CiAgICAgICAgdGltZW91dCQ0ID0gMCwgLy8gaXMgYSB0aW1lb3V0IHBlbmRpbmc/CiAgICAgICAgaW50ZXJ2YWwkMyA9IDAsIC8vIGFyZSBhbnkgdGltZXJzIGFjdGl2ZT8KICAgICAgICBwb2tlRGVsYXkkMiA9IDEwMDAsIC8vIGhvdyBmcmVxdWVudGx5IHdlIGNoZWNrIGZvciBjbG9jayBza2V3CiAgICAgICAgdGFza0hlYWQkMiwKICAgICAgICB0YXNrVGFpbCQyLAogICAgICAgIGNsb2NrTGFzdCQyID0gMCwKICAgICAgICBjbG9ja05vdyQyID0gMCwKICAgICAgICBjbG9ja1NrZXckMiA9IDAsCiAgICAgICAgY2xvY2skMiA9IHR5cGVvZiBwZXJmb3JtYW5jZSA9PT0gIm9iamVjdCIgJiYgcGVyZm9ybWFuY2Uubm93ID8gcGVyZm9ybWFuY2UgOiBEYXRlLAogICAgICAgIHNldEZyYW1lJDIgPSB0eXBlb2Ygd2luZG93ID09PSAib2JqZWN0IiAmJiB3aW5kb3cucmVxdWVzdEFuaW1hdGlvbkZyYW1lID8gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZS5iaW5kKHdpbmRvdykgOiBmdW5jdGlvbihmKSB7IHNldFRpbWVvdXQoZiwgMTcpOyB9OwoKICAgIGZ1bmN0aW9uIG5vdyQyKCkgewogICAgICByZXR1cm4gY2xvY2tOb3ckMiB8fCAoc2V0RnJhbWUkMihjbGVhck5vdyQyKSwgY2xvY2tOb3ckMiA9IGNsb2NrJDIubm93KCkgKyBjbG9ja1NrZXckMik7CiAgICB9CgogICAgZnVuY3Rpb24gY2xlYXJOb3ckMigpIHsKICAgICAgY2xvY2tOb3ckMiA9IDA7CiAgICB9CgogICAgZnVuY3Rpb24gVGltZXIkMigpIHsKICAgICAgdGhpcy5fY2FsbCA9CiAgICAgIHRoaXMuX3RpbWUgPQogICAgICB0aGlzLl9uZXh0ID0gbnVsbDsKICAgIH0KCiAgICBUaW1lciQyLnByb3RvdHlwZSA9IHRpbWVyJDIucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVGltZXIkMiwKICAgICAgcmVzdGFydDogZnVuY3Rpb24oY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgICAgaWYgKHR5cGVvZiBjYWxsYmFjayAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IFR5cGVFcnJvcigiY2FsbGJhY2sgaXMgbm90IGEgZnVuY3Rpb24iKTsKICAgICAgICB0aW1lID0gKHRpbWUgPT0gbnVsbCA/IG5vdyQyKCkgOiArdGltZSkgKyAoZGVsYXkgPT0gbnVsbCA/IDAgOiArZGVsYXkpOwogICAgICAgIGlmICghdGhpcy5fbmV4dCAmJiB0YXNrVGFpbCQyICE9PSB0aGlzKSB7CiAgICAgICAgICBpZiAodGFza1RhaWwkMikgdGFza1RhaWwkMi5fbmV4dCA9IHRoaXM7CiAgICAgICAgICBlbHNlIHRhc2tIZWFkJDIgPSB0aGlzOwogICAgICAgICAgdGFza1RhaWwkMiA9IHRoaXM7CiAgICAgICAgfQogICAgICAgIHRoaXMuX2NhbGwgPSBjYWxsYmFjazsKICAgICAgICB0aGlzLl90aW1lID0gdGltZTsKICAgICAgICBzbGVlcCQyKCk7CiAgICAgIH0sCiAgICAgIHN0b3A6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9jYWxsKSB7CiAgICAgICAgICB0aGlzLl9jYWxsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX3RpbWUgPSBJbmZpbml0eTsKICAgICAgICAgIHNsZWVwJDIoKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gdGltZXIkMihjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIkMjsKICAgICAgdC5yZXN0YXJ0KGNhbGxiYWNrLCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVyRmx1c2gkMigpIHsKICAgICAgbm93JDIoKTsgLy8gR2V0IHRoZSBjdXJyZW50IHRpbWUsIGlmIG5vdCBhbHJlYWR5IHNldC4KICAgICAgKytmcmFtZSQyOyAvLyBQcmV0ZW5kIHdl4oCZdmUgc2V0IGFuIGFsYXJtLCBpZiB3ZSBoYXZlbuKAmXQgYWxyZWFkeS4KICAgICAgdmFyIHQgPSB0YXNrSGVhZCQyLCBlOwogICAgICB3aGlsZSAodCkgewogICAgICAgIGlmICgoZSA9IGNsb2NrTm93JDIgLSB0Ll90aW1lKSA+PSAwKSB0Ll9jYWxsLmNhbGwobnVsbCwgZSk7CiAgICAgICAgdCA9IHQuX25leHQ7CiAgICAgIH0KICAgICAgLS1mcmFtZSQyOwogICAgfQoKICAgIGZ1bmN0aW9uIHdha2UkMigpIHsKICAgICAgY2xvY2tOb3ckMiA9IChjbG9ja0xhc3QkMiA9IGNsb2NrJDIubm93KCkpICsgY2xvY2tTa2V3JDI7CiAgICAgIGZyYW1lJDIgPSB0aW1lb3V0JDQgPSAwOwogICAgICB0cnkgewogICAgICAgIHRpbWVyRmx1c2gkMigpOwogICAgICB9IGZpbmFsbHkgewogICAgICAgIGZyYW1lJDIgPSAwOwogICAgICAgIG5hcCQyKCk7CiAgICAgICAgY2xvY2tOb3ckMiA9IDA7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBwb2tlJDIoKSB7CiAgICAgIHZhciBub3cgPSBjbG9jayQyLm5vdygpLCBkZWxheSA9IG5vdyAtIGNsb2NrTGFzdCQyOwogICAgICBpZiAoZGVsYXkgPiBwb2tlRGVsYXkkMikgY2xvY2tTa2V3JDIgLT0gZGVsYXksIGNsb2NrTGFzdCQyID0gbm93OwogICAgfQoKICAgIGZ1bmN0aW9uIG5hcCQyKCkgewogICAgICB2YXIgdDAsIHQxID0gdGFza0hlYWQkMiwgdDIsIHRpbWUgPSBJbmZpbml0eTsKICAgICAgd2hpbGUgKHQxKSB7CiAgICAgICAgaWYgKHQxLl9jYWxsKSB7CiAgICAgICAgICBpZiAodGltZSA+IHQxLl90aW1lKSB0aW1lID0gdDEuX3RpbWU7CiAgICAgICAgICB0MCA9IHQxLCB0MSA9IHQxLl9uZXh0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0MiA9IHQxLl9uZXh0LCB0MS5fbmV4dCA9IG51bGw7CiAgICAgICAgICB0MSA9IHQwID8gdDAuX25leHQgPSB0MiA6IHRhc2tIZWFkJDIgPSB0MjsKICAgICAgICB9CiAgICAgIH0KICAgICAgdGFza1RhaWwkMiA9IHQwOwogICAgICBzbGVlcCQyKHRpbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNsZWVwJDIodGltZSkgewogICAgICBpZiAoZnJhbWUkMikgcmV0dXJuOyAvLyBTb29uZXN0IGFsYXJtIGFscmVhZHkgc2V0LCBvciB3aWxsIGJlLgogICAgICBpZiAodGltZW91dCQ0KSB0aW1lb3V0JDQgPSBjbGVhclRpbWVvdXQodGltZW91dCQ0KTsKICAgICAgdmFyIGRlbGF5ID0gdGltZSAtIGNsb2NrTm93JDI7IC8vIFN0cmljdGx5IGxlc3MgdGhhbiBpZiB3ZSByZWNvbXB1dGVkIGNsb2NrTm93LgogICAgICBpZiAoZGVsYXkgPiAyNCkgewogICAgICAgIGlmICh0aW1lIDwgSW5maW5pdHkpIHRpbWVvdXQkNCA9IHNldFRpbWVvdXQod2FrZSQyLCB0aW1lIC0gY2xvY2skMi5ub3coKSAtIGNsb2NrU2tldyQyKTsKICAgICAgICBpZiAoaW50ZXJ2YWwkMykgaW50ZXJ2YWwkMyA9IGNsZWFySW50ZXJ2YWwoaW50ZXJ2YWwkMyk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgaWYgKCFpbnRlcnZhbCQzKSBjbG9ja0xhc3QkMiA9IGNsb2NrJDIubm93KCksIGludGVydmFsJDMgPSBzZXRJbnRlcnZhbChwb2tlJDIsIHBva2VEZWxheSQyKTsKICAgICAgICBmcmFtZSQyID0gMSwgc2V0RnJhbWUkMih3YWtlJDIpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24geCQ2KGQpIHsKICAgICAgcmV0dXJuIGQueDsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDYoZCkgewogICAgICByZXR1cm4gZC55OwogICAgfQoKICAgIHZhciBpbml0aWFsUmFkaXVzJDEgPSAxMCwKICAgICAgICBpbml0aWFsQW5nbGUkMSA9IE1hdGguUEkgKiAoMyAtIE1hdGguc3FydCg1KSk7CgogICAgZnVuY3Rpb24gc2ltdWxhdGlvbiQxKG5vZGVzKSB7CiAgICAgIHZhciBzaW11bGF0aW9uLAogICAgICAgICAgYWxwaGEgPSAxLAogICAgICAgICAgYWxwaGFNaW4gPSAwLjAwMSwKICAgICAgICAgIGFscGhhRGVjYXkgPSAxIC0gTWF0aC5wb3coYWxwaGFNaW4sIDEgLyAzMDApLAogICAgICAgICAgYWxwaGFUYXJnZXQgPSAwLAogICAgICAgICAgdmVsb2NpdHlEZWNheSA9IDAuNiwKICAgICAgICAgIGZvcmNlcyA9IG1hcCQ2KCksCiAgICAgICAgICBzdGVwcGVyID0gdGltZXIkMihzdGVwKSwKICAgICAgICAgIGV2ZW50ID0gZGlzcGF0Y2gkNCgidGljayIsICJlbmQiKTsKCiAgICAgIGlmIChub2RlcyA9PSBudWxsKSBub2RlcyA9IFtdOwoKICAgICAgZnVuY3Rpb24gc3RlcCgpIHsKICAgICAgICB0aWNrKCk7CiAgICAgICAgZXZlbnQuY2FsbCgidGljayIsIHNpbXVsYXRpb24pOwogICAgICAgIGlmIChhbHBoYSA8IGFscGhhTWluKSB7CiAgICAgICAgICBzdGVwcGVyLnN0b3AoKTsKICAgICAgICAgIGV2ZW50LmNhbGwoImVuZCIsIHNpbXVsYXRpb24pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gdGljaygpIHsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aCwgbm9kZTsKCiAgICAgICAgYWxwaGEgKz0gKGFscGhhVGFyZ2V0IC0gYWxwaGEpICogYWxwaGFEZWNheTsKCiAgICAgICAgZm9yY2VzLmVhY2goZnVuY3Rpb24oZm9yY2UpIHsKICAgICAgICAgIGZvcmNlKGFscGhhKTsKICAgICAgICB9KTsKCiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgbm9kZSA9IG5vZGVzW2ldOwogICAgICAgICAgaWYgKG5vZGUuZnggPT0gbnVsbCkgbm9kZS54ICs9IG5vZGUudnggKj0gdmVsb2NpdHlEZWNheTsKICAgICAgICAgIGVsc2Ugbm9kZS54ID0gbm9kZS5meCwgbm9kZS52eCA9IDA7CiAgICAgICAgICBpZiAobm9kZS5meSA9PSBudWxsKSBub2RlLnkgKz0gbm9kZS52eSAqPSB2ZWxvY2l0eURlY2F5OwogICAgICAgICAgZWxzZSBub2RlLnkgPSBub2RlLmZ5LCBub2RlLnZ5ID0gMDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemVOb2RlcygpIHsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IG5vZGVzLmxlbmd0aCwgbm9kZTsgaSA8IG47ICsraSkgewogICAgICAgICAgbm9kZSA9IG5vZGVzW2ldLCBub2RlLmluZGV4ID0gaTsKICAgICAgICAgIGlmIChpc05hTihub2RlLngpIHx8IGlzTmFOKG5vZGUueSkpIHsKICAgICAgICAgICAgdmFyIHJhZGl1cyA9IGluaXRpYWxSYWRpdXMkMSAqIE1hdGguc3FydChpKSwgYW5nbGUgPSBpICogaW5pdGlhbEFuZ2xlJDE7CiAgICAgICAgICAgIG5vZGUueCA9IHJhZGl1cyAqIE1hdGguY29zKGFuZ2xlKTsKICAgICAgICAgICAgbm9kZS55ID0gcmFkaXVzICogTWF0aC5zaW4oYW5nbGUpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGlzTmFOKG5vZGUudngpIHx8IGlzTmFOKG5vZGUudnkpKSB7CiAgICAgICAgICAgIG5vZGUudnggPSBub2RlLnZ5ID0gMDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemVGb3JjZShmb3JjZSkgewogICAgICAgIGlmIChmb3JjZS5pbml0aWFsaXplKSBmb3JjZS5pbml0aWFsaXplKG5vZGVzKTsKICAgICAgICByZXR1cm4gZm9yY2U7CiAgICAgIH0KCiAgICAgIGluaXRpYWxpemVOb2RlcygpOwoKICAgICAgcmV0dXJuIHNpbXVsYXRpb24gPSB7CiAgICAgICAgdGljazogdGljaywKCiAgICAgICAgcmVzdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gc3RlcHBlci5yZXN0YXJ0KHN0ZXApLCBzaW11bGF0aW9uOwogICAgICAgIH0sCgogICAgICAgIHN0b3A6IGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHN0ZXBwZXIuc3RvcCgpLCBzaW11bGF0aW9uOwogICAgICAgIH0sCgogICAgICAgIG5vZGVzOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChub2RlcyA9IF8sIGluaXRpYWxpemVOb2RlcygpLCBmb3JjZXMuZWFjaChpbml0aWFsaXplRm9yY2UpLCBzaW11bGF0aW9uKSA6IG5vZGVzOwogICAgICAgIH0sCgogICAgICAgIGFscGhhOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChhbHBoYSA9ICtfLCBzaW11bGF0aW9uKSA6IGFscGhhOwogICAgICAgIH0sCgogICAgICAgIGFscGhhTWluOiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChhbHBoYU1pbiA9ICtfLCBzaW11bGF0aW9uKSA6IGFscGhhTWluOwogICAgICAgIH0sCgogICAgICAgIGFscGhhRGVjYXk6IGZ1bmN0aW9uKF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGFscGhhRGVjYXkgPSArXywgc2ltdWxhdGlvbikgOiArYWxwaGFEZWNheTsKICAgICAgICB9LAoKICAgICAgICBhbHBoYVRhcmdldDogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoYWxwaGFUYXJnZXQgPSArXywgc2ltdWxhdGlvbikgOiBhbHBoYVRhcmdldDsKICAgICAgICB9LAoKICAgICAgICB2ZWxvY2l0eURlY2F5OiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh2ZWxvY2l0eURlY2F5ID0gMSAtIF8sIHNpbXVsYXRpb24pIDogMSAtIHZlbG9jaXR5RGVjYXk7CiAgICAgICAgfSwKCiAgICAgICAgZm9yY2U6IGZ1bmN0aW9uKG5hbWUsIF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMSA/ICgoXyA9PSBudWxsID8gZm9yY2VzLnJlbW92ZShuYW1lKSA6IGZvcmNlcy5zZXQobmFtZSwgaW5pdGlhbGl6ZUZvcmNlKF8pKSksIHNpbXVsYXRpb24pIDogZm9yY2VzLmdldChuYW1lKTsKICAgICAgICB9LAoKICAgICAgICBmaW5kOiBmdW5jdGlvbih4LCB5LCByYWRpdXMpIHsKICAgICAgICAgIHZhciBpID0gMCwKICAgICAgICAgICAgICBuID0gbm9kZXMubGVuZ3RoLAogICAgICAgICAgICAgIGR4LAogICAgICAgICAgICAgIGR5LAogICAgICAgICAgICAgIGQyLAogICAgICAgICAgICAgIG5vZGUsCiAgICAgICAgICAgICAgY2xvc2VzdDsKCiAgICAgICAgICBpZiAocmFkaXVzID09IG51bGwpIHJhZGl1cyA9IEluZmluaXR5OwogICAgICAgICAgZWxzZSByYWRpdXMgKj0gcmFkaXVzOwoKICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgICAgbm9kZSA9IG5vZGVzW2ldOwogICAgICAgICAgICBkeCA9IHggLSBub2RlLng7CiAgICAgICAgICAgIGR5ID0geSAtIG5vZGUueTsKICAgICAgICAgICAgZDIgPSBkeCAqIGR4ICsgZHkgKiBkeTsKICAgICAgICAgICAgaWYgKGQyIDwgcmFkaXVzKSBjbG9zZXN0ID0gbm9kZSwgcmFkaXVzID0gZDI7CiAgICAgICAgICB9CgogICAgICAgICAgcmV0dXJuIGNsb3Nlc3Q7CiAgICAgICAgfSwKCiAgICAgICAgb246IGZ1bmN0aW9uKG5hbWUsIF8pIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMSA/IChldmVudC5vbihuYW1lLCBfKSwgc2ltdWxhdGlvbikgOiBldmVudC5vbihuYW1lKTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbWFueUJvZHkkMSgpIHsKICAgICAgdmFyIG5vZGVzLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIGFscGhhLAogICAgICAgICAgc3RyZW5ndGggPSBjb25zdGFudCRsKC0zMCksCiAgICAgICAgICBzdHJlbmd0aHMsCiAgICAgICAgICBkaXN0YW5jZU1pbjIgPSAxLAogICAgICAgICAgZGlzdGFuY2VNYXgyID0gSW5maW5pdHksCiAgICAgICAgICB0aGV0YTIgPSAwLjgxOwoKICAgICAgZnVuY3Rpb24gZm9yY2UoXykgewogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoLCB0cmVlID0gcXVhZHRyZWUkMShub2RlcywgeCQ2LCB5JDYpLnZpc2l0QWZ0ZXIoYWNjdW11bGF0ZSk7CiAgICAgICAgZm9yIChhbHBoYSA9IF8sIGkgPSAwOyBpIDwgbjsgKytpKSBub2RlID0gbm9kZXNbaV0sIHRyZWUudmlzaXQoYXBwbHkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBpbml0aWFsaXplKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aCwgbm9kZTsKICAgICAgICBzdHJlbmd0aHMgPSBuZXcgQXJyYXkobik7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgbm9kZSA9IG5vZGVzW2ldLCBzdHJlbmd0aHNbbm9kZS5pbmRleF0gPSArc3RyZW5ndGgobm9kZSwgaSwgbm9kZXMpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBhY2N1bXVsYXRlKHF1YWQpIHsKICAgICAgICB2YXIgc3RyZW5ndGggPSAwLCBxLCBjLCB3ZWlnaHQgPSAwLCB4LCB5LCBpOwoKICAgICAgICAvLyBGb3IgaW50ZXJuYWwgbm9kZXMsIGFjY3VtdWxhdGUgZm9yY2VzIGZyb20gY2hpbGQgcXVhZHJhbnRzLgogICAgICAgIGlmIChxdWFkLmxlbmd0aCkgewogICAgICAgICAgZm9yICh4ID0geSA9IGkgPSAwOyBpIDwgNDsgKytpKSB7CiAgICAgICAgICAgIGlmICgocSA9IHF1YWRbaV0pICYmIChjID0gTWF0aC5hYnMocS52YWx1ZSkpKSB7CiAgICAgICAgICAgICAgc3RyZW5ndGggKz0gcS52YWx1ZSwgd2VpZ2h0ICs9IGMsIHggKz0gYyAqIHEueCwgeSArPSBjICogcS55OwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBxdWFkLnggPSB4IC8gd2VpZ2h0OwogICAgICAgICAgcXVhZC55ID0geSAvIHdlaWdodDsKICAgICAgICB9CgogICAgICAgIC8vIEZvciBsZWFmIG5vZGVzLCBhY2N1bXVsYXRlIGZvcmNlcyBmcm9tIGNvaW5jaWRlbnQgcXVhZHJhbnRzLgogICAgICAgIGVsc2UgewogICAgICAgICAgcSA9IHF1YWQ7CiAgICAgICAgICBxLnggPSBxLmRhdGEueDsKICAgICAgICAgIHEueSA9IHEuZGF0YS55OwogICAgICAgICAgZG8gc3RyZW5ndGggKz0gc3RyZW5ndGhzW3EuZGF0YS5pbmRleF07CiAgICAgICAgICB3aGlsZSAocSA9IHEubmV4dCk7CiAgICAgICAgfQoKICAgICAgICBxdWFkLnZhbHVlID0gc3RyZW5ndGg7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGFwcGx5KHF1YWQsIHgxLCBfLCB4MikgewogICAgICAgIGlmICghcXVhZC52YWx1ZSkgcmV0dXJuIHRydWU7CgogICAgICAgIHZhciB4ID0gcXVhZC54IC0gbm9kZS54LAogICAgICAgICAgICB5ID0gcXVhZC55IC0gbm9kZS55LAogICAgICAgICAgICB3ID0geDIgLSB4MSwKICAgICAgICAgICAgbCA9IHggKiB4ICsgeSAqIHk7CgogICAgICAgIC8vIEFwcGx5IHRoZSBCYXJuZXMtSHV0IGFwcHJveGltYXRpb24gaWYgcG9zc2libGUuCiAgICAgICAgLy8gTGltaXQgZm9yY2VzIGZvciB2ZXJ5IGNsb3NlIG5vZGVzOyByYW5kb21pemUgZGlyZWN0aW9uIGlmIGNvaW5jaWRlbnQuCiAgICAgICAgaWYgKHcgKiB3IC8gdGhldGEyIDwgbCkgewogICAgICAgICAgaWYgKGwgPCBkaXN0YW5jZU1heDIpIHsKICAgICAgICAgICAgaWYgKHggPT09IDApIHggPSBqaWdnbGUkMSgpLCBsICs9IHggKiB4OwogICAgICAgICAgICBpZiAoeSA9PT0gMCkgeSA9IGppZ2dsZSQxKCksIGwgKz0geSAqIHk7CiAgICAgICAgICAgIGlmIChsIDwgZGlzdGFuY2VNaW4yKSBsID0gTWF0aC5zcXJ0KGRpc3RhbmNlTWluMiAqIGwpOwogICAgICAgICAgICBub2RlLnZ4ICs9IHggKiBxdWFkLnZhbHVlICogYWxwaGEgLyBsOwogICAgICAgICAgICBub2RlLnZ5ICs9IHkgKiBxdWFkLnZhbHVlICogYWxwaGEgLyBsOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQoKICAgICAgICAvLyBPdGhlcndpc2UsIHByb2Nlc3MgcG9pbnRzIGRpcmVjdGx5LgogICAgICAgIGVsc2UgaWYgKHF1YWQubGVuZ3RoIHx8IGwgPj0gZGlzdGFuY2VNYXgyKSByZXR1cm47CgogICAgICAgIC8vIExpbWl0IGZvcmNlcyBmb3IgdmVyeSBjbG9zZSBub2RlczsgcmFuZG9taXplIGRpcmVjdGlvbiBpZiBjb2luY2lkZW50LgogICAgICAgIGlmIChxdWFkLmRhdGEgIT09IG5vZGUgfHwgcXVhZC5uZXh0KSB7CiAgICAgICAgICBpZiAoeCA9PT0gMCkgeCA9IGppZ2dsZSQxKCksIGwgKz0geCAqIHg7CiAgICAgICAgICBpZiAoeSA9PT0gMCkgeSA9IGppZ2dsZSQxKCksIGwgKz0geSAqIHk7CiAgICAgICAgICBpZiAobCA8IGRpc3RhbmNlTWluMikgbCA9IE1hdGguc3FydChkaXN0YW5jZU1pbjIgKiBsKTsKICAgICAgICB9CgogICAgICAgIGRvIGlmIChxdWFkLmRhdGEgIT09IG5vZGUpIHsKICAgICAgICAgIHcgPSBzdHJlbmd0aHNbcXVhZC5kYXRhLmluZGV4XSAqIGFscGhhIC8gbDsKICAgICAgICAgIG5vZGUudnggKz0geCAqIHc7CiAgICAgICAgICBub2RlLnZ5ICs9IHkgKiB3OwogICAgICAgIH0gd2hpbGUgKHF1YWQgPSBxdWFkLm5leHQpOwogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXzsKICAgICAgICBpbml0aWFsaXplKCk7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGwoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UuZGlzdGFuY2VNaW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGlzdGFuY2VNaW4yID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydChkaXN0YW5jZU1pbjIpOwogICAgICB9OwoKICAgICAgZm9yY2UuZGlzdGFuY2VNYXggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZGlzdGFuY2VNYXgyID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydChkaXN0YW5jZU1heDIpOwogICAgICB9OwoKICAgICAgZm9yY2UudGhldGEgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGhldGEyID0gXyAqIF8sIGZvcmNlKSA6IE1hdGguc3FydCh0aGV0YTIpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhZGlhbCQxKHJhZGl1cywgeCwgeSkgewogICAgICB2YXIgbm9kZXMsCiAgICAgICAgICBzdHJlbmd0aCA9IGNvbnN0YW50JGwoMC4xKSwKICAgICAgICAgIHN0cmVuZ3RocywKICAgICAgICAgIHJhZGl1c2VzOwoKICAgICAgaWYgKHR5cGVvZiByYWRpdXMgIT09ICJmdW5jdGlvbiIpIHJhZGl1cyA9IGNvbnN0YW50JGwoK3JhZGl1cyk7CiAgICAgIGlmICh4ID09IG51bGwpIHggPSAwOwogICAgICBpZiAoeSA9PSBudWxsKSB5ID0gMDsKCiAgICAgIGZ1bmN0aW9uIGZvcmNlKGFscGhhKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBub2Rlcy5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHZhciBub2RlID0gbm9kZXNbaV0sCiAgICAgICAgICAgICAgZHggPSBub2RlLnggLSB4IHx8IDFlLTYsCiAgICAgICAgICAgICAgZHkgPSBub2RlLnkgLSB5IHx8IDFlLTYsCiAgICAgICAgICAgICAgciA9IE1hdGguc3FydChkeCAqIGR4ICsgZHkgKiBkeSksCiAgICAgICAgICAgICAgayA9IChyYWRpdXNlc1tpXSAtIHIpICogc3RyZW5ndGhzW2ldICogYWxwaGEgLyByOwogICAgICAgICAgbm9kZS52eCArPSBkeCAqIGs7CiAgICAgICAgICBub2RlLnZ5ICs9IGR5ICogazsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGluaXRpYWxpemUoKSB7CiAgICAgICAgaWYgKCFub2RlcykgcmV0dXJuOwogICAgICAgIHZhciBpLCBuID0gbm9kZXMubGVuZ3RoOwogICAgICAgIHN0cmVuZ3RocyA9IG5ldyBBcnJheShuKTsKICAgICAgICByYWRpdXNlcyA9IG5ldyBBcnJheShuKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICByYWRpdXNlc1tpXSA9ICtyYWRpdXMobm9kZXNbaV0sIGksIG5vZGVzKTsKICAgICAgICAgIHN0cmVuZ3Roc1tpXSA9IGlzTmFOKHJhZGl1c2VzW2ldKSA/IDAgOiArc3RyZW5ndGgobm9kZXNbaV0sIGksIG5vZGVzKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZvcmNlLmluaXRpYWxpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgbm9kZXMgPSBfLCBpbml0aWFsaXplKCk7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGwoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UucmFkaXVzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhZGl1cyA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGwoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIGZvcmNlLnggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeCA9ICtfLCBmb3JjZSkgOiB4OwogICAgICB9OwoKICAgICAgZm9yY2UueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gK18sIGZvcmNlKSA6IHk7CiAgICAgIH07CgogICAgICByZXR1cm4gZm9yY2U7CiAgICB9CgogICAgZnVuY3Rpb24geCQ3KHgpIHsKICAgICAgdmFyIHN0cmVuZ3RoID0gY29uc3RhbnQkbCgwLjEpLAogICAgICAgICAgbm9kZXMsCiAgICAgICAgICBzdHJlbmd0aHMsCiAgICAgICAgICB4ejsKCiAgICAgIGlmICh0eXBlb2YgeCAhPT0gImZ1bmN0aW9uIikgeCA9IGNvbnN0YW50JGwoeCA9PSBudWxsID8gMCA6ICt4KTsKCiAgICAgIGZ1bmN0aW9uIGZvcmNlKGFscGhhKSB7CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBub2Rlcy5sZW5ndGgsIG5vZGU7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIG5vZGUgPSBub2Rlc1tpXSwgbm9kZS52eCArPSAoeHpbaV0gLSBub2RlLngpICogc3RyZW5ndGhzW2ldICogYWxwaGE7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBpbml0aWFsaXplKCkgewogICAgICAgIGlmICghbm9kZXMpIHJldHVybjsKICAgICAgICB2YXIgaSwgbiA9IG5vZGVzLmxlbmd0aDsKICAgICAgICBzdHJlbmd0aHMgPSBuZXcgQXJyYXkobik7CiAgICAgICAgeHogPSBuZXcgQXJyYXkobik7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgc3RyZW5ndGhzW2ldID0gaXNOYU4oeHpbaV0gPSAreChub2Rlc1tpXSwgaSwgbm9kZXMpKSA/IDAgOiArc3RyZW5ndGgobm9kZXNbaV0sIGksIG5vZGVzKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZvcmNlLmluaXRpYWxpemUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgbm9kZXMgPSBfOwogICAgICAgIGluaXRpYWxpemUoKTsKICAgICAgfTsKCiAgICAgIGZvcmNlLnN0cmVuZ3RoID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN0cmVuZ3RoID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkbCgrXyksIGluaXRpYWxpemUoKSwgZm9yY2UpIDogc3RyZW5ndGg7CiAgICAgIH07CgogICAgICBmb3JjZS54ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHggPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRsKCtfKSwgaW5pdGlhbGl6ZSgpLCBmb3JjZSkgOiB4OwogICAgICB9OwoKICAgICAgcmV0dXJuIGZvcmNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHkkNyh5KSB7CiAgICAgIHZhciBzdHJlbmd0aCA9IGNvbnN0YW50JGwoMC4xKSwKICAgICAgICAgIG5vZGVzLAogICAgICAgICAgc3RyZW5ndGhzLAogICAgICAgICAgeXo7CgogICAgICBpZiAodHlwZW9mIHkgIT09ICJmdW5jdGlvbiIpIHkgPSBjb25zdGFudCRsKHkgPT0gbnVsbCA/IDAgOiAreSk7CgogICAgICBmdW5jdGlvbiBmb3JjZShhbHBoYSkgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gbm9kZXMubGVuZ3RoLCBub2RlOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUudnkgKz0gKHl6W2ldIC0gbm9kZS55KSAqIHN0cmVuZ3Roc1tpXSAqIGFscGhhOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW5pdGlhbGl6ZSgpIHsKICAgICAgICBpZiAoIW5vZGVzKSByZXR1cm47CiAgICAgICAgdmFyIGksIG4gPSBub2Rlcy5sZW5ndGg7CiAgICAgICAgc3RyZW5ndGhzID0gbmV3IEFycmF5KG4pOwogICAgICAgIHl6ID0gbmV3IEFycmF5KG4pOwogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHN0cmVuZ3Roc1tpXSA9IGlzTmFOKHl6W2ldID0gK3kobm9kZXNbaV0sIGksIG5vZGVzKSkgPyAwIDogK3N0cmVuZ3RoKG5vZGVzW2ldLCBpLCBub2Rlcyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3JjZS5pbml0aWFsaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIG5vZGVzID0gXzsKICAgICAgICBpbml0aWFsaXplKCk7CiAgICAgIH07CgogICAgICBmb3JjZS5zdHJlbmd0aCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdHJlbmd0aCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JGwoK18pLCBpbml0aWFsaXplKCksIGZvcmNlKSA6IHN0cmVuZ3RoOwogICAgICB9OwoKICAgICAgZm9yY2UueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkbCgrXyksIGluaXRpYWxpemUoKSwgZm9yY2UpIDogeTsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3JjZTsKICAgIH0KCiAgICAvLyBDb21wdXRlcyB0aGUgZGVjaW1hbCBjb2VmZmljaWVudCBhbmQgZXhwb25lbnQgb2YgdGhlIHNwZWNpZmllZCBudW1iZXIgeCB3aXRoCiAgICAvLyBzaWduaWZpY2FudCBkaWdpdHMgcCwgd2hlcmUgeCBpcyBwb3NpdGl2ZSBhbmQgcCBpcyBpbiBbMSwgMjFdIG9yIHVuZGVmaW5lZC4KICAgIC8vIEZvciBleGFtcGxlLCBmb3JtYXREZWNpbWFsKDEuMjMpIHJldHVybnMgWyIxMjMiLCAwXS4KICAgIGZ1bmN0aW9uIGZvcm1hdERlY2ltYWwkMSh4LCBwKSB7CiAgICAgIGlmICgoaSA9ICh4ID0gcCA/IHgudG9FeHBvbmVudGlhbChwIC0gMSkgOiB4LnRvRXhwb25lbnRpYWwoKSkuaW5kZXhPZigiZSIpKSA8IDApIHJldHVybiBudWxsOyAvLyBOYU4sIMKxSW5maW5pdHkKICAgICAgdmFyIGksIGNvZWZmaWNpZW50ID0geC5zbGljZSgwLCBpKTsKCiAgICAgIC8vIFRoZSBzdHJpbmcgcmV0dXJuZWQgYnkgdG9FeHBvbmVudGlhbCBlaXRoZXIgaGFzIHRoZSBmb3JtIFxkXC5cZCtlWy0rXVxkKwogICAgICAvLyAoZS5nLiwgMS4yZSszKSBvciB0aGUgZm9ybSBcZGVbLStdXGQrIChlLmcuLCAxZSszKS4KICAgICAgcmV0dXJuIFsKICAgICAgICBjb2VmZmljaWVudC5sZW5ndGggPiAxID8gY29lZmZpY2llbnRbMF0gKyBjb2VmZmljaWVudC5zbGljZSgyKSA6IGNvZWZmaWNpZW50LAogICAgICAgICt4LnNsaWNlKGkgKyAxKQogICAgICBdOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4cG9uZW50JDMoeCkgewogICAgICByZXR1cm4geCA9IGZvcm1hdERlY2ltYWwkMShNYXRoLmFicyh4KSksIHggPyB4WzFdIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEdyb3VwJDEoZ3JvdXBpbmcsIHRob3VzYW5kcykgewogICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUsIHdpZHRoKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5sZW5ndGgsCiAgICAgICAgICAgIHQgPSBbXSwKICAgICAgICAgICAgaiA9IDAsCiAgICAgICAgICAgIGcgPSBncm91cGluZ1swXSwKICAgICAgICAgICAgbGVuZ3RoID0gMDsKCiAgICAgICAgd2hpbGUgKGkgPiAwICYmIGcgPiAwKSB7CiAgICAgICAgICBpZiAobGVuZ3RoICsgZyArIDEgPiB3aWR0aCkgZyA9IE1hdGgubWF4KDEsIHdpZHRoIC0gbGVuZ3RoKTsKICAgICAgICAgIHQucHVzaCh2YWx1ZS5zdWJzdHJpbmcoaSAtPSBnLCBpICsgZykpOwogICAgICAgICAgaWYgKChsZW5ndGggKz0gZyArIDEpID4gd2lkdGgpIGJyZWFrOwogICAgICAgICAgZyA9IGdyb3VwaW5nW2ogPSAoaiArIDEpICUgZ3JvdXBpbmcubGVuZ3RoXTsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0LnJldmVyc2UoKS5qb2luKHRob3VzYW5kcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TnVtZXJhbHMkMShudW1lcmFscykgewogICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICByZXR1cm4gdmFsdWUucmVwbGFjZSgvWzAtOV0vZywgZnVuY3Rpb24oaSkgewogICAgICAgICAgcmV0dXJuIG51bWVyYWxzWytpXTsKICAgICAgICB9KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXREZWZhdWx0KHgsIHApIHsKICAgICAgeCA9IHgudG9QcmVjaXNpb24ocCk7CgogICAgICBvdXQ6IGZvciAodmFyIG4gPSB4Lmxlbmd0aCwgaSA9IDEsIGkwID0gLTEsIGkxOyBpIDwgbjsgKytpKSB7CiAgICAgICAgc3dpdGNoICh4W2ldKSB7CiAgICAgICAgICBjYXNlICIuIjogaTAgPSBpMSA9IGk7IGJyZWFrOwogICAgICAgICAgY2FzZSAiMCI6IGlmIChpMCA9PT0gMCkgaTAgPSBpOyBpMSA9IGk7IGJyZWFrOwogICAgICAgICAgY2FzZSAiZSI6IGJyZWFrIG91dDsKICAgICAgICAgIGRlZmF1bHQ6IGlmIChpMCA+IDApIGkwID0gMDsgYnJlYWs7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gaTAgPiAwID8geC5zbGljZSgwLCBpMCkgKyB4LnNsaWNlKGkxICsgMSkgOiB4OwogICAgfQoKICAgIHZhciBwcmVmaXhFeHBvbmVudCQxOwoKICAgIGZ1bmN0aW9uIGZvcm1hdFByZWZpeEF1dG8kMSh4LCBwKSB7CiAgICAgIHZhciBkID0gZm9ybWF0RGVjaW1hbCQxKHgsIHApOwogICAgICBpZiAoIWQpIHJldHVybiB4ICsgIiI7CiAgICAgIHZhciBjb2VmZmljaWVudCA9IGRbMF0sCiAgICAgICAgICBleHBvbmVudCA9IGRbMV0sCiAgICAgICAgICBpID0gZXhwb25lbnQgLSAocHJlZml4RXhwb25lbnQkMSA9IE1hdGgubWF4KC04LCBNYXRoLm1pbig4LCBNYXRoLmZsb29yKGV4cG9uZW50IC8gMykpKSAqIDMpICsgMSwKICAgICAgICAgIG4gPSBjb2VmZmljaWVudC5sZW5ndGg7CiAgICAgIHJldHVybiBpID09PSBuID8gY29lZmZpY2llbnQKICAgICAgICAgIDogaSA+IG4gPyBjb2VmZmljaWVudCArIG5ldyBBcnJheShpIC0gbiArIDEpLmpvaW4oIjAiKQogICAgICAgICAgOiBpID4gMCA/IGNvZWZmaWNpZW50LnNsaWNlKDAsIGkpICsgIi4iICsgY29lZmZpY2llbnQuc2xpY2UoaSkKICAgICAgICAgIDogIjAuIiArIG5ldyBBcnJheSgxIC0gaSkuam9pbigiMCIpICsgZm9ybWF0RGVjaW1hbCQxKHgsIE1hdGgubWF4KDAsIHAgKyBpIC0gMSkpWzBdOyAvLyBsZXNzIHRoYW4gMXkhCiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0Um91bmRlZCQxKHgsIHApIHsKICAgICAgdmFyIGQgPSBmb3JtYXREZWNpbWFsJDEoeCwgcCk7CiAgICAgIGlmICghZCkgcmV0dXJuIHggKyAiIjsKICAgICAgdmFyIGNvZWZmaWNpZW50ID0gZFswXSwKICAgICAgICAgIGV4cG9uZW50ID0gZFsxXTsKICAgICAgcmV0dXJuIGV4cG9uZW50IDwgMCA/ICIwLiIgKyBuZXcgQXJyYXkoLWV4cG9uZW50KS5qb2luKCIwIikgKyBjb2VmZmljaWVudAogICAgICAgICAgOiBjb2VmZmljaWVudC5sZW5ndGggPiBleHBvbmVudCArIDEgPyBjb2VmZmljaWVudC5zbGljZSgwLCBleHBvbmVudCArIDEpICsgIi4iICsgY29lZmZpY2llbnQuc2xpY2UoZXhwb25lbnQgKyAxKQogICAgICAgICAgOiBjb2VmZmljaWVudCArIG5ldyBBcnJheShleHBvbmVudCAtIGNvZWZmaWNpZW50Lmxlbmd0aCArIDIpLmpvaW4oIjAiKTsKICAgIH0KCiAgICB2YXIgZm9ybWF0VHlwZXMkMSA9IHsKICAgICAgIiI6IGZvcm1hdERlZmF1bHQsCiAgICAgICIlIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4gKHggKiAxMDApLnRvRml4ZWQocCk7IH0sCiAgICAgICJiIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygyKTsgfSwKICAgICAgImMiOiBmdW5jdGlvbih4KSB7IHJldHVybiB4ICsgIiI7IH0sCiAgICAgICJkIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygxMCk7IH0sCiAgICAgICJlIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4geC50b0V4cG9uZW50aWFsKHApOyB9LAogICAgICAiZiI6IGZ1bmN0aW9uKHgsIHApIHsgcmV0dXJuIHgudG9GaXhlZChwKTsgfSwKICAgICAgImciOiBmdW5jdGlvbih4LCBwKSB7IHJldHVybiB4LnRvUHJlY2lzaW9uKHApOyB9LAogICAgICAibyI6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgucm91bmQoeCkudG9TdHJpbmcoOCk7IH0sCiAgICAgICJwIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4gZm9ybWF0Um91bmRlZCQxKHggKiAxMDAsIHApOyB9LAogICAgICAiciI6IGZvcm1hdFJvdW5kZWQkMSwKICAgICAgInMiOiBmb3JtYXRQcmVmaXhBdXRvJDEsCiAgICAgICJYIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygxNikudG9VcHBlckNhc2UoKTsgfSwKICAgICAgIngiOiBmdW5jdGlvbih4KSB7IHJldHVybiBNYXRoLnJvdW5kKHgpLnRvU3RyaW5nKDE2KTsgfQogICAgfTsKCiAgICAvLyBbW2ZpbGxdYWxpZ25dW3NpZ25dW3N5bWJvbF1bMF1bd2lkdGhdWyxdWy5wcmVjaXNpb25dW3R5cGVdCiAgICB2YXIgcmUkMSA9IC9eKD86KC4pPyhbPD49Xl0pKT8oWytcLVwoIF0pPyhbJCNdKT8oMCk/KFxkKyk/KCwpPyhcLlxkKyk/KFthLXolXSk/JC9pOwoKICAgIGZ1bmN0aW9uIGZvcm1hdFNwZWNpZmllciQxKHNwZWNpZmllcikgewogICAgICByZXR1cm4gbmV3IEZvcm1hdFNwZWNpZmllciQxKHNwZWNpZmllcik7CiAgICB9CgogICAgZm9ybWF0U3BlY2lmaWVyJDEucHJvdG90eXBlID0gRm9ybWF0U3BlY2lmaWVyJDEucHJvdG90eXBlOyAvLyBpbnN0YW5jZW9mCgogICAgZnVuY3Rpb24gRm9ybWF0U3BlY2lmaWVyJDEoc3BlY2lmaWVyKSB7CiAgICAgIGlmICghKG1hdGNoID0gcmUkMS5leGVjKHNwZWNpZmllcikpKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgZm9ybWF0OiAiICsgc3BlY2lmaWVyKTsKCiAgICAgIHZhciBtYXRjaCwKICAgICAgICAgIGZpbGwgPSBtYXRjaFsxXSB8fCAiICIsCiAgICAgICAgICBhbGlnbiA9IG1hdGNoWzJdIHx8ICI+IiwKICAgICAgICAgIHNpZ24gPSBtYXRjaFszXSB8fCAiLSIsCiAgICAgICAgICBzeW1ib2wgPSBtYXRjaFs0XSB8fCAiIiwKICAgICAgICAgIHplcm8gPSAhIW1hdGNoWzVdLAogICAgICAgICAgd2lkdGggPSBtYXRjaFs2XSAmJiArbWF0Y2hbNl0sCiAgICAgICAgICBjb21tYSA9ICEhbWF0Y2hbN10sCiAgICAgICAgICBwcmVjaXNpb24gPSBtYXRjaFs4XSAmJiArbWF0Y2hbOF0uc2xpY2UoMSksCiAgICAgICAgICB0eXBlID0gbWF0Y2hbOV0gfHwgIiI7CgogICAgICAvLyBUaGUgIm4iIHR5cGUgaXMgYW4gYWxpYXMgZm9yICIsZyIuCiAgICAgIGlmICh0eXBlID09PSAibiIpIGNvbW1hID0gdHJ1ZSwgdHlwZSA9ICJnIjsKCiAgICAgIC8vIE1hcCBpbnZhbGlkIHR5cGVzIHRvIHRoZSBkZWZhdWx0IGZvcm1hdC4KICAgICAgZWxzZSBpZiAoIWZvcm1hdFR5cGVzJDFbdHlwZV0pIHR5cGUgPSAiIjsKCiAgICAgIC8vIElmIHplcm8gZmlsbCBpcyBzcGVjaWZpZWQsIHBhZGRpbmcgZ29lcyBhZnRlciBzaWduIGFuZCBiZWZvcmUgZGlnaXRzLgogICAgICBpZiAoemVybyB8fCAoZmlsbCA9PT0gIjAiICYmIGFsaWduID09PSAiPSIpKSB6ZXJvID0gdHJ1ZSwgZmlsbCA9ICIwIiwgYWxpZ24gPSAiPSI7CgogICAgICB0aGlzLmZpbGwgPSBmaWxsOwogICAgICB0aGlzLmFsaWduID0gYWxpZ247CiAgICAgIHRoaXMuc2lnbiA9IHNpZ247CiAgICAgIHRoaXMuc3ltYm9sID0gc3ltYm9sOwogICAgICB0aGlzLnplcm8gPSB6ZXJvOwogICAgICB0aGlzLndpZHRoID0gd2lkdGg7CiAgICAgIHRoaXMuY29tbWEgPSBjb21tYTsKICAgICAgdGhpcy5wcmVjaXNpb24gPSBwcmVjaXNpb247CiAgICAgIHRoaXMudHlwZSA9IHR5cGU7CiAgICB9CgogICAgRm9ybWF0U3BlY2lmaWVyJDEucHJvdG90eXBlLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLmZpbGwKICAgICAgICAgICsgdGhpcy5hbGlnbgogICAgICAgICAgKyB0aGlzLnNpZ24KICAgICAgICAgICsgdGhpcy5zeW1ib2wKICAgICAgICAgICsgKHRoaXMuemVybyA/ICIwIiA6ICIiKQogICAgICAgICAgKyAodGhpcy53aWR0aCA9PSBudWxsID8gIiIgOiBNYXRoLm1heCgxLCB0aGlzLndpZHRoIHwgMCkpCiAgICAgICAgICArICh0aGlzLmNvbW1hID8gIiwiIDogIiIpCiAgICAgICAgICArICh0aGlzLnByZWNpc2lvbiA9PSBudWxsID8gIiIgOiAiLiIgKyBNYXRoLm1heCgwLCB0aGlzLnByZWNpc2lvbiB8IDApKQogICAgICAgICAgKyB0aGlzLnR5cGU7CiAgICB9OwoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JGQoeCkgewogICAgICByZXR1cm4geDsKICAgIH0KCiAgICB2YXIgcHJlZml4ZXMkMSA9IFsieSIsInoiLCJhIiwiZiIsInAiLCJuIiwiwrUiLCJtIiwiIiwiayIsIk0iLCJHIiwiVCIsIlAiLCJFIiwiWiIsIlkiXTsKCiAgICBmdW5jdGlvbiBmb3JtYXRMb2NhbGUkMihsb2NhbGUpIHsKICAgICAgdmFyIGdyb3VwID0gbG9jYWxlLmdyb3VwaW5nICYmIGxvY2FsZS50aG91c2FuZHMgPyBmb3JtYXRHcm91cCQxKGxvY2FsZS5ncm91cGluZywgbG9jYWxlLnRob3VzYW5kcykgOiBpZGVudGl0eSRkLAogICAgICAgICAgY3VycmVuY3kgPSBsb2NhbGUuY3VycmVuY3ksCiAgICAgICAgICBkZWNpbWFsID0gbG9jYWxlLmRlY2ltYWwsCiAgICAgICAgICBudW1lcmFscyA9IGxvY2FsZS5udW1lcmFscyA/IGZvcm1hdE51bWVyYWxzJDEobG9jYWxlLm51bWVyYWxzKSA6IGlkZW50aXR5JGQsCiAgICAgICAgICBwZXJjZW50ID0gbG9jYWxlLnBlcmNlbnQgfHwgIiUiOwoKICAgICAgZnVuY3Rpb24gbmV3Rm9ybWF0KHNwZWNpZmllcikgewogICAgICAgIHNwZWNpZmllciA9IGZvcm1hdFNwZWNpZmllciQxKHNwZWNpZmllcik7CgogICAgICAgIHZhciBmaWxsID0gc3BlY2lmaWVyLmZpbGwsCiAgICAgICAgICAgIGFsaWduID0gc3BlY2lmaWVyLmFsaWduLAogICAgICAgICAgICBzaWduID0gc3BlY2lmaWVyLnNpZ24sCiAgICAgICAgICAgIHN5bWJvbCA9IHNwZWNpZmllci5zeW1ib2wsCiAgICAgICAgICAgIHplcm8gPSBzcGVjaWZpZXIuemVybywKICAgICAgICAgICAgd2lkdGggPSBzcGVjaWZpZXIud2lkdGgsCiAgICAgICAgICAgIGNvbW1hID0gc3BlY2lmaWVyLmNvbW1hLAogICAgICAgICAgICBwcmVjaXNpb24gPSBzcGVjaWZpZXIucHJlY2lzaW9uLAogICAgICAgICAgICB0eXBlID0gc3BlY2lmaWVyLnR5cGU7CgogICAgICAgIC8vIENvbXB1dGUgdGhlIHByZWZpeCBhbmQgc3VmZml4LgogICAgICAgIC8vIEZvciBTSS1wcmVmaXgsIHRoZSBzdWZmaXggaXMgbGF6aWx5IGNvbXB1dGVkLgogICAgICAgIHZhciBwcmVmaXggPSBzeW1ib2wgPT09ICIkIiA/IGN1cnJlbmN5WzBdIDogc3ltYm9sID09PSAiIyIgJiYgL1tib3hYXS8udGVzdCh0eXBlKSA/ICIwIiArIHR5cGUudG9Mb3dlckNhc2UoKSA6ICIiLAogICAgICAgICAgICBzdWZmaXggPSBzeW1ib2wgPT09ICIkIiA/IGN1cnJlbmN5WzFdIDogL1slcF0vLnRlc3QodHlwZSkgPyBwZXJjZW50IDogIiI7CgogICAgICAgIC8vIFdoYXQgZm9ybWF0IGZ1bmN0aW9uIHNob3VsZCB3ZSB1c2U/CiAgICAgICAgLy8gSXMgdGhpcyBhbiBpbnRlZ2VyIHR5cGU/CiAgICAgICAgLy8gQ2FuIHRoaXMgdHlwZSBnZW5lcmF0ZSBleHBvbmVudGlhbCBub3RhdGlvbj8KICAgICAgICB2YXIgZm9ybWF0VHlwZSA9IGZvcm1hdFR5cGVzJDFbdHlwZV0sCiAgICAgICAgICAgIG1heWJlU3VmZml4ID0gIXR5cGUgfHwgL1tkZWZncHJzJV0vLnRlc3QodHlwZSk7CgogICAgICAgIC8vIFNldCB0aGUgZGVmYXVsdCBwcmVjaXNpb24gaWYgbm90IHNwZWNpZmllZCwKICAgICAgICAvLyBvciBjbGFtcCB0aGUgc3BlY2lmaWVkIHByZWNpc2lvbiB0byB0aGUgc3VwcG9ydGVkIHJhbmdlLgogICAgICAgIC8vIEZvciBzaWduaWZpY2FudCBwcmVjaXNpb24sIGl0IG11c3QgYmUgaW4gWzEsIDIxXS4KICAgICAgICAvLyBGb3IgZml4ZWQgcHJlY2lzaW9uLCBpdCBtdXN0IGJlIGluIFswLCAyMF0uCiAgICAgICAgcHJlY2lzaW9uID0gcHJlY2lzaW9uID09IG51bGwgPyAodHlwZSA/IDYgOiAxMikKICAgICAgICAgICAgOiAvW2dwcnNdLy50ZXN0KHR5cGUpID8gTWF0aC5tYXgoMSwgTWF0aC5taW4oMjEsIHByZWNpc2lvbikpCiAgICAgICAgICAgIDogTWF0aC5tYXgoMCwgTWF0aC5taW4oMjAsIHByZWNpc2lvbikpOwoKICAgICAgICBmdW5jdGlvbiBmb3JtYXQodmFsdWUpIHsKICAgICAgICAgIHZhciB2YWx1ZVByZWZpeCA9IHByZWZpeCwKICAgICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9IHN1ZmZpeCwKICAgICAgICAgICAgICBpLCBuLCBjOwoKICAgICAgICAgIGlmICh0eXBlID09PSAiYyIpIHsKICAgICAgICAgICAgdmFsdWVTdWZmaXggPSBmb3JtYXRUeXBlKHZhbHVlKSArIHZhbHVlU3VmZml4OwogICAgICAgICAgICB2YWx1ZSA9ICIiOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdmFsdWUgPSArdmFsdWU7CgogICAgICAgICAgICAvLyBQZXJmb3JtIHRoZSBpbml0aWFsIGZvcm1hdHRpbmcuCiAgICAgICAgICAgIHZhciB2YWx1ZU5lZ2F0aXZlID0gdmFsdWUgPCAwOwogICAgICAgICAgICB2YWx1ZSA9IGZvcm1hdFR5cGUoTWF0aC5hYnModmFsdWUpLCBwcmVjaXNpb24pOwoKICAgICAgICAgICAgLy8gSWYgYSBuZWdhdGl2ZSB2YWx1ZSByb3VuZHMgdG8gemVybyBkdXJpbmcgZm9ybWF0dGluZywgdHJlYXQgYXMgcG9zaXRpdmUuCiAgICAgICAgICAgIGlmICh2YWx1ZU5lZ2F0aXZlICYmICt2YWx1ZSA9PT0gMCkgdmFsdWVOZWdhdGl2ZSA9IGZhbHNlOwoKICAgICAgICAgICAgLy8gQ29tcHV0ZSB0aGUgcHJlZml4IGFuZCBzdWZmaXguCiAgICAgICAgICAgIHZhbHVlUHJlZml4ID0gKHZhbHVlTmVnYXRpdmUgPyAoc2lnbiA9PT0gIigiID8gc2lnbiA6ICItIikgOiBzaWduID09PSAiLSIgfHwgc2lnbiA9PT0gIigiID8gIiIgOiBzaWduKSArIHZhbHVlUHJlZml4OwogICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9ICh0eXBlID09PSAicyIgPyBwcmVmaXhlcyQxWzggKyBwcmVmaXhFeHBvbmVudCQxIC8gM10gOiAiIikgKyB2YWx1ZVN1ZmZpeCArICh2YWx1ZU5lZ2F0aXZlICYmIHNpZ24gPT09ICIoIiA/ICIpIiA6ICIiKTsKCiAgICAgICAgICAgIC8vIEJyZWFrIHRoZSBmb3JtYXR0ZWQgdmFsdWUgaW50byB0aGUgaW50ZWdlciDigJx2YWx1ZeKAnSBwYXJ0IHRoYXQgY2FuIGJlCiAgICAgICAgICAgIC8vIGdyb3VwZWQsIGFuZCBmcmFjdGlvbmFsIG9yIGV4cG9uZW50aWFsIOKAnHN1ZmZpeOKAnSBwYXJ0IHRoYXQgaXMgbm90LgogICAgICAgICAgICBpZiAobWF5YmVTdWZmaXgpIHsKICAgICAgICAgICAgICBpID0gLTEsIG4gPSB2YWx1ZS5sZW5ndGg7CiAgICAgICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgICAgICAgIGlmIChjID0gdmFsdWUuY2hhckNvZGVBdChpKSwgNDggPiBjIHx8IGMgPiA1NykgewogICAgICAgICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9IChjID09PSA0NiA/IGRlY2ltYWwgKyB2YWx1ZS5zbGljZShpICsgMSkgOiB2YWx1ZS5zbGljZShpKSkgKyB2YWx1ZVN1ZmZpeDsKICAgICAgICAgICAgICAgICAgdmFsdWUgPSB2YWx1ZS5zbGljZSgwLCBpKTsKICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgLy8gSWYgdGhlIGZpbGwgY2hhcmFjdGVyIGlzIG5vdCAiMCIsIGdyb3VwaW5nIGlzIGFwcGxpZWQgYmVmb3JlIHBhZGRpbmcuCiAgICAgICAgICBpZiAoY29tbWEgJiYgIXplcm8pIHZhbHVlID0gZ3JvdXAodmFsdWUsIEluZmluaXR5KTsKCiAgICAgICAgICAvLyBDb21wdXRlIHRoZSBwYWRkaW5nLgogICAgICAgICAgdmFyIGxlbmd0aCA9IHZhbHVlUHJlZml4Lmxlbmd0aCArIHZhbHVlLmxlbmd0aCArIHZhbHVlU3VmZml4Lmxlbmd0aCwKICAgICAgICAgICAgICBwYWRkaW5nID0gbGVuZ3RoIDwgd2lkdGggPyBuZXcgQXJyYXkod2lkdGggLSBsZW5ndGggKyAxKS5qb2luKGZpbGwpIDogIiI7CgogICAgICAgICAgLy8gSWYgdGhlIGZpbGwgY2hhcmFjdGVyIGlzICIwIiwgZ3JvdXBpbmcgaXMgYXBwbGllZCBhZnRlciBwYWRkaW5nLgogICAgICAgICAgaWYgKGNvbW1hICYmIHplcm8pIHZhbHVlID0gZ3JvdXAocGFkZGluZyArIHZhbHVlLCBwYWRkaW5nLmxlbmd0aCA/IHdpZHRoIC0gdmFsdWVTdWZmaXgubGVuZ3RoIDogSW5maW5pdHkpLCBwYWRkaW5nID0gIiI7CgogICAgICAgICAgLy8gUmVjb25zdHJ1Y3QgdGhlIGZpbmFsIG91dHB1dCBiYXNlZCBvbiB0aGUgZGVzaXJlZCBhbGlnbm1lbnQuCiAgICAgICAgICBzd2l0Y2ggKGFsaWduKSB7CiAgICAgICAgICAgIGNhc2UgIjwiOiB2YWx1ZSA9IHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeCArIHBhZGRpbmc7IGJyZWFrOwogICAgICAgICAgICBjYXNlICI9IjogdmFsdWUgPSB2YWx1ZVByZWZpeCArIHBhZGRpbmcgKyB2YWx1ZSArIHZhbHVlU3VmZml4OyBicmVhazsKICAgICAgICAgICAgY2FzZSAiXiI6IHZhbHVlID0gcGFkZGluZy5zbGljZSgwLCBsZW5ndGggPSBwYWRkaW5nLmxlbmd0aCA+PiAxKSArIHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeCArIHBhZGRpbmcuc2xpY2UobGVuZ3RoKTsgYnJlYWs7CiAgICAgICAgICAgIGRlZmF1bHQ6IHZhbHVlID0gcGFkZGluZyArIHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeDsgYnJlYWs7CiAgICAgICAgICB9CgogICAgICAgICAgcmV0dXJuIG51bWVyYWxzKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIGZvcm1hdC50b1N0cmluZyA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHNwZWNpZmllciArICIiOwogICAgICAgIH07CgogICAgICAgIHJldHVybiBmb3JtYXQ7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFByZWZpeChzcGVjaWZpZXIsIHZhbHVlKSB7CiAgICAgICAgdmFyIGYgPSBuZXdGb3JtYXQoKHNwZWNpZmllciA9IGZvcm1hdFNwZWNpZmllciQxKHNwZWNpZmllciksIHNwZWNpZmllci50eXBlID0gImYiLCBzcGVjaWZpZXIpKSwKICAgICAgICAgICAgZSA9IE1hdGgubWF4KC04LCBNYXRoLm1pbig4LCBNYXRoLmZsb29yKGV4cG9uZW50JDModmFsdWUpIC8gMykpKSAqIDMsCiAgICAgICAgICAgIGsgPSBNYXRoLnBvdygxMCwgLWUpLAogICAgICAgICAgICBwcmVmaXggPSBwcmVmaXhlcyQxWzggKyBlIC8gM107CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gZihrICogdmFsdWUpICsgcHJlZml4OwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJldHVybiB7CiAgICAgICAgZm9ybWF0OiBuZXdGb3JtYXQsCiAgICAgICAgZm9ybWF0UHJlZml4OiBmb3JtYXRQcmVmaXgKICAgICAgfTsKICAgIH0KCiAgICB2YXIgbG9jYWxlJDI7CiAgICB2YXIgZm9ybWF0JDE7CiAgICB2YXIgZm9ybWF0UHJlZml4JDE7CgogICAgZGVmYXVsdExvY2FsZSQyKHsKICAgICAgZGVjaW1hbDogIi4iLAogICAgICB0aG91c2FuZHM6ICIsIiwKICAgICAgZ3JvdXBpbmc6IFszXSwKICAgICAgY3VycmVuY3k6IFsiJCIsICIiXQogICAgfSk7CgogICAgZnVuY3Rpb24gZGVmYXVsdExvY2FsZSQyKGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlJDIgPSBmb3JtYXRMb2NhbGUkMihkZWZpbml0aW9uKTsKICAgICAgZm9ybWF0JDEgPSBsb2NhbGUkMi5mb3JtYXQ7CiAgICAgIGZvcm1hdFByZWZpeCQxID0gbG9jYWxlJDIuZm9ybWF0UHJlZml4OwogICAgICByZXR1cm4gbG9jYWxlJDI7CiAgICB9CgogICAgZnVuY3Rpb24gcHJlY2lzaW9uRml4ZWQkMShzdGVwKSB7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCAtZXhwb25lbnQkMyhNYXRoLmFicyhzdGVwKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvblByZWZpeCQxKHN0ZXAsIHZhbHVlKSB7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCBNYXRoLm1heCgtOCwgTWF0aC5taW4oOCwgTWF0aC5mbG9vcihleHBvbmVudCQzKHZhbHVlKSAvIDMpKSkgKiAzIC0gZXhwb25lbnQkMyhNYXRoLmFicyhzdGVwKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvblJvdW5kJDEoc3RlcCwgbWF4KSB7CiAgICAgIHN0ZXAgPSBNYXRoLmFicyhzdGVwKSwgbWF4ID0gTWF0aC5hYnMobWF4KSAtIHN0ZXA7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCBleHBvbmVudCQzKG1heCkgLSBleHBvbmVudCQzKHN0ZXApKSArIDE7CiAgICB9CgogICAgLy8gQWRkcyBmbG9hdGluZyBwb2ludCBudW1iZXJzIHdpdGggdHdpY2UgdGhlIG5vcm1hbCBwcmVjaXNpb24uCiAgICAvLyBSZWZlcmVuY2U6IEouIFIuIFNoZXdjaHVrLCBBZGFwdGl2ZSBQcmVjaXNpb24gRmxvYXRpbmctUG9pbnQgQXJpdGhtZXRpYyBhbmQKICAgIC8vIEZhc3QgUm9idXN0IEdlb21ldHJpYyBQcmVkaWNhdGVzLCBEaXNjcmV0ZSAmIENvbXB1dGF0aW9uYWwgR2VvbWV0cnkgMTgoMykKICAgIC8vIDMwNeKAkzM2MyAoMTk5NykuCiAgICAvLyBDb2RlIGFkYXB0ZWQgZnJvbSBHZW9ncmFwaGljTGliIGJ5IENoYXJsZXMgRi4gRi4gS2FybmV5LAogICAgLy8gaHR0cDovL2dlb2dyYXBoaWNsaWIuc291cmNlZm9yZ2UubmV0LwoKICAgIGZ1bmN0aW9uIGFkZGVyJDEoKSB7CiAgICAgIHJldHVybiBuZXcgQWRkZXIkMTsKICAgIH0KCiAgICBmdW5jdGlvbiBBZGRlciQxKCkgewogICAgICB0aGlzLnJlc2V0KCk7CiAgICB9CgogICAgQWRkZXIkMS5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBBZGRlciQxLAogICAgICByZXNldDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zID0gLy8gcm91bmRlZCB2YWx1ZQogICAgICAgIHRoaXMudCA9IDA7IC8vIGV4YWN0IGVycm9yCiAgICAgIH0sCiAgICAgIGFkZDogZnVuY3Rpb24oeSkgewogICAgICAgIGFkZCQzKHRlbXAkMSwgeSwgdGhpcy50KTsKICAgICAgICBhZGQkMyh0aGlzLCB0ZW1wJDEucywgdGhpcy5zKTsKICAgICAgICBpZiAodGhpcy5zKSB0aGlzLnQgKz0gdGVtcCQxLnQ7CiAgICAgICAgZWxzZSB0aGlzLnMgPSB0ZW1wJDEudDsKICAgICAgfSwKICAgICAgdmFsdWVPZjogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuczsKICAgICAgfQogICAgfTsKCiAgICB2YXIgdGVtcCQxID0gbmV3IEFkZGVyJDE7CgogICAgZnVuY3Rpb24gYWRkJDMoYWRkZXIsIGEsIGIpIHsKICAgICAgdmFyIHggPSBhZGRlci5zID0gYSArIGIsCiAgICAgICAgICBidiA9IHggLSBhLAogICAgICAgICAgYXYgPSB4IC0gYnY7CiAgICAgIGFkZGVyLnQgPSAoYSAtIGF2KSArIChiIC0gYnYpOwogICAgfQoKICAgIHZhciBlcHNpbG9uJDcgPSAxZS02OwogICAgdmFyIGVwc2lsb24yJDMgPSAxZS0xMjsKICAgIHZhciBwaSQ4ID0gTWF0aC5QSTsKICAgIHZhciBoYWxmUGkkNiA9IHBpJDggLyAyOwogICAgdmFyIHF1YXJ0ZXJQaSQxID0gcGkkOCAvIDQ7CiAgICB2YXIgdGF1JDggPSBwaSQ4ICogMjsKCiAgICB2YXIgZGVncmVlcyQzID0gMTgwIC8gcGkkODsKICAgIHZhciByYWRpYW5zJDEgPSBwaSQ4IC8gMTgwOwoKICAgIHZhciBhYnMkMiA9IE1hdGguYWJzOwogICAgdmFyIGF0YW4kMSA9IE1hdGguYXRhbjsKICAgIHZhciBhdGFuMiQyID0gTWF0aC5hdGFuMjsKICAgIHZhciBjb3MkNCA9IE1hdGguY29zOwogICAgdmFyIGNlaWwkMSA9IE1hdGguY2VpbDsKICAgIHZhciBleHAkMSA9IE1hdGguZXhwOwogICAgdmFyIGxvZyQyID0gTWF0aC5sb2c7CiAgICB2YXIgcG93JDIgPSBNYXRoLnBvdzsKICAgIHZhciBzaW4kNCA9IE1hdGguc2luOwogICAgdmFyIHNpZ24kMiA9IE1hdGguc2lnbiB8fCBmdW5jdGlvbih4KSB7IHJldHVybiB4ID4gMCA/IDEgOiB4IDwgMCA/IC0xIDogMDsgfTsKICAgIHZhciBzcXJ0JDMgPSBNYXRoLnNxcnQ7CiAgICB2YXIgdGFuJDEgPSBNYXRoLnRhbjsKCiAgICBmdW5jdGlvbiBhY29zJDIoeCkgewogICAgICByZXR1cm4geCA+IDEgPyAwIDogeCA8IC0xID8gcGkkOCA6IE1hdGguYWNvcyh4KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2luJDIoeCkgewogICAgICByZXR1cm4geCA+IDEgPyBoYWxmUGkkNiA6IHggPCAtMSA/IC1oYWxmUGkkNiA6IE1hdGguYXNpbih4KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoYXZlcnNpbiQxKHgpIHsKICAgICAgcmV0dXJuICh4ID0gc2luJDQoeCAvIDIpKSAqIHg7CiAgICB9CgogICAgZnVuY3Rpb24gbm9vcCQ4KCkge30KCiAgICBmdW5jdGlvbiBzdHJlYW1HZW9tZXRyeSQxKGdlb21ldHJ5LCBzdHJlYW0pIHsKICAgICAgaWYgKGdlb21ldHJ5ICYmIHN0cmVhbUdlb21ldHJ5VHlwZSQxLmhhc093blByb3BlcnR5KGdlb21ldHJ5LnR5cGUpKSB7CiAgICAgICAgc3RyZWFtR2VvbWV0cnlUeXBlJDFbZ2VvbWV0cnkudHlwZV0oZ2VvbWV0cnksIHN0cmVhbSk7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgc3RyZWFtT2JqZWN0VHlwZSQxID0gewogICAgICBGZWF0dXJlOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHN0cmVhbUdlb21ldHJ5JDEob2JqZWN0Lmdlb21ldHJ5LCBzdHJlYW0pOwogICAgICB9LAogICAgICBGZWF0dXJlQ29sbGVjdGlvbjogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICB2YXIgZmVhdHVyZXMgPSBvYmplY3QuZmVhdHVyZXMsIGkgPSAtMSwgbiA9IGZlYXR1cmVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgc3RyZWFtR2VvbWV0cnkkMShmZWF0dXJlc1tpXS5nZW9tZXRyeSwgc3RyZWFtKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgc3RyZWFtR2VvbWV0cnlUeXBlJDEgPSB7CiAgICAgIFNwaGVyZTogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICBzdHJlYW0uc3BoZXJlKCk7CiAgICAgIH0sCiAgICAgIFBvaW50OiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIG9iamVjdCA9IG9iamVjdC5jb29yZGluYXRlczsKICAgICAgICBzdHJlYW0ucG9pbnQob2JqZWN0WzBdLCBvYmplY3RbMV0sIG9iamVjdFsyXSk7CiAgICAgIH0sCiAgICAgIE11bHRpUG9pbnQ6IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgdmFyIGNvb3JkaW5hdGVzID0gb2JqZWN0LmNvb3JkaW5hdGVzLCBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIG9iamVjdCA9IGNvb3JkaW5hdGVzW2ldLCBzdHJlYW0ucG9pbnQob2JqZWN0WzBdLCBvYmplY3RbMV0sIG9iamVjdFsyXSk7CiAgICAgIH0sCiAgICAgIExpbmVTdHJpbmc6IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgc3RyZWFtTGluZSQxKG9iamVjdC5jb29yZGluYXRlcywgc3RyZWFtLCAwKTsKICAgICAgfSwKICAgICAgTXVsdGlMaW5lU3RyaW5nOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHZhciBjb29yZGluYXRlcyA9IG9iamVjdC5jb29yZGluYXRlcywgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBzdHJlYW1MaW5lJDEoY29vcmRpbmF0ZXNbaV0sIHN0cmVhbSwgMCk7CiAgICAgIH0sCiAgICAgIFBvbHlnb246IGZ1bmN0aW9uKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgICAgc3RyZWFtUG9seWdvbiQxKG9iamVjdC5jb29yZGluYXRlcywgc3RyZWFtKTsKICAgICAgfSwKICAgICAgTXVsdGlQb2x5Z29uOiBmdW5jdGlvbihvYmplY3QsIHN0cmVhbSkgewogICAgICAgIHZhciBjb29yZGluYXRlcyA9IG9iamVjdC5jb29yZGluYXRlcywgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBzdHJlYW1Qb2x5Z29uJDEoY29vcmRpbmF0ZXNbaV0sIHN0cmVhbSk7CiAgICAgIH0sCiAgICAgIEdlb21ldHJ5Q29sbGVjdGlvbjogZnVuY3Rpb24ob2JqZWN0LCBzdHJlYW0pIHsKICAgICAgICB2YXIgZ2VvbWV0cmllcyA9IG9iamVjdC5nZW9tZXRyaWVzLCBpID0gLTEsIG4gPSBnZW9tZXRyaWVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgc3RyZWFtR2VvbWV0cnkkMShnZW9tZXRyaWVzW2ldLCBzdHJlYW0pOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHN0cmVhbUxpbmUkMShjb29yZGluYXRlcywgc3RyZWFtLCBjbG9zZWQpIHsKICAgICAgdmFyIGkgPSAtMSwgbiA9IGNvb3JkaW5hdGVzLmxlbmd0aCAtIGNsb3NlZCwgY29vcmRpbmF0ZTsKICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICB3aGlsZSAoKytpIDwgbikgY29vcmRpbmF0ZSA9IGNvb3JkaW5hdGVzW2ldLCBzdHJlYW0ucG9pbnQoY29vcmRpbmF0ZVswXSwgY29vcmRpbmF0ZVsxXSwgY29vcmRpbmF0ZVsyXSk7CiAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICB9CgogICAgZnVuY3Rpb24gc3RyZWFtUG9seWdvbiQxKGNvb3JkaW5hdGVzLCBzdHJlYW0pIHsKICAgICAgdmFyIGkgPSAtMSwgbiA9IGNvb3JkaW5hdGVzLmxlbmd0aDsKICAgICAgc3RyZWFtLnBvbHlnb25TdGFydCgpOwogICAgICB3aGlsZSAoKytpIDwgbikgc3RyZWFtTGluZSQxKGNvb3JkaW5hdGVzW2ldLCBzdHJlYW0sIDEpOwogICAgICBzdHJlYW0ucG9seWdvbkVuZCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGdlb1N0cmVhbSQxKG9iamVjdCwgc3RyZWFtKSB7CiAgICAgIGlmIChvYmplY3QgJiYgc3RyZWFtT2JqZWN0VHlwZSQxLmhhc093blByb3BlcnR5KG9iamVjdC50eXBlKSkgewogICAgICAgIHN0cmVhbU9iamVjdFR5cGUkMVtvYmplY3QudHlwZV0ob2JqZWN0LCBzdHJlYW0pOwogICAgICB9IGVsc2UgewogICAgICAgIHN0cmVhbUdlb21ldHJ5JDEob2JqZWN0LCBzdHJlYW0pOwogICAgICB9CiAgICB9CgogICAgdmFyIGFyZWFSaW5nU3VtJDIgPSBhZGRlciQxKCk7CgogICAgdmFyIGFyZWFTdW0kMiA9IGFkZGVyJDEoKSwKICAgICAgICBsYW1iZGEwMCQzLAogICAgICAgIHBoaTAwJDMsCiAgICAgICAgbGFtYmRhMCQzLAogICAgICAgIGNvc1BoaTAkMiwKICAgICAgICBzaW5QaGkwJDI7CgogICAgdmFyIGFyZWFTdHJlYW0kMiA9IHsKICAgICAgcG9pbnQ6IG5vb3AkOCwKICAgICAgbGluZVN0YXJ0OiBub29wJDgsCiAgICAgIGxpbmVFbmQ6IG5vb3AkOCwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBhcmVhUmluZ1N1bSQyLnJlc2V0KCk7CiAgICAgICAgYXJlYVN0cmVhbSQyLmxpbmVTdGFydCA9IGFyZWFSaW5nU3RhcnQkMjsKICAgICAgICBhcmVhU3RyZWFtJDIubGluZUVuZCA9IGFyZWFSaW5nRW5kJDI7CiAgICAgIH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBhcmVhUmluZyA9ICthcmVhUmluZ1N1bSQyOwogICAgICAgIGFyZWFTdW0kMi5hZGQoYXJlYVJpbmcgPCAwID8gdGF1JDggKyBhcmVhUmluZyA6IGFyZWFSaW5nKTsKICAgICAgICB0aGlzLmxpbmVTdGFydCA9IHRoaXMubGluZUVuZCA9IHRoaXMucG9pbnQgPSBub29wJDg7CiAgICAgIH0sCiAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7CiAgICAgICAgYXJlYVN1bSQyLmFkZCh0YXUkOCk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYXJlYVJpbmdTdGFydCQyKCkgewogICAgICBhcmVhU3RyZWFtJDIucG9pbnQgPSBhcmVhUG9pbnRGaXJzdCQyOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWFSaW5nRW5kJDIoKSB7CiAgICAgIGFyZWFQb2ludCQyKGxhbWJkYTAwJDMsIHBoaTAwJDMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWFQb2ludEZpcnN0JDIobGFtYmRhLCBwaGkpIHsKICAgICAgYXJlYVN0cmVhbSQyLnBvaW50ID0gYXJlYVBvaW50JDI7CiAgICAgIGxhbWJkYTAwJDMgPSBsYW1iZGEsIHBoaTAwJDMgPSBwaGk7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zJDEsIHBoaSAqPSByYWRpYW5zJDE7CiAgICAgIGxhbWJkYTAkMyA9IGxhbWJkYSwgY29zUGhpMCQyID0gY29zJDQocGhpID0gcGhpIC8gMiArIHF1YXJ0ZXJQaSQxKSwgc2luUGhpMCQyID0gc2luJDQocGhpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhUG9pbnQkMihsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucyQxLCBwaGkgKj0gcmFkaWFucyQxOwogICAgICBwaGkgPSBwaGkgLyAyICsgcXVhcnRlclBpJDE7IC8vIGhhbGYgdGhlIGFuZ3VsYXIgZGlzdGFuY2UgZnJvbSBzb3V0aCBwb2xlCgogICAgICAvLyBTcGhlcmljYWwgZXhjZXNzIEUgZm9yIGEgc3BoZXJpY2FsIHRyaWFuZ2xlIHdpdGggdmVydGljZXM6IHNvdXRoIHBvbGUsCiAgICAgIC8vIHByZXZpb3VzIHBvaW50LCBjdXJyZW50IHBvaW50LiAgVXNlcyBhIGZvcm11bGEgZGVyaXZlZCBmcm9tIENhZ25vbGnigJlzCiAgICAgIC8vIHRoZW9yZW0uICBTZWUgVG9kaHVudGVyLCBTcGhlcmljYWwgVHJpZy4gKDE4NzEpLCBTZWMuIDEwMywgRXEuICgyKS4KICAgICAgdmFyIGRMYW1iZGEgPSBsYW1iZGEgLSBsYW1iZGEwJDMsCiAgICAgICAgICBzZExhbWJkYSA9IGRMYW1iZGEgPj0gMCA/IDEgOiAtMSwKICAgICAgICAgIGFkTGFtYmRhID0gc2RMYW1iZGEgKiBkTGFtYmRhLAogICAgICAgICAgY29zUGhpID0gY29zJDQocGhpKSwKICAgICAgICAgIHNpblBoaSA9IHNpbiQ0KHBoaSksCiAgICAgICAgICBrID0gc2luUGhpMCQyICogc2luUGhpLAogICAgICAgICAgdSA9IGNvc1BoaTAkMiAqIGNvc1BoaSArIGsgKiBjb3MkNChhZExhbWJkYSksCiAgICAgICAgICB2ID0gayAqIHNkTGFtYmRhICogc2luJDQoYWRMYW1iZGEpOwogICAgICBhcmVhUmluZ1N1bSQyLmFkZChhdGFuMiQyKHYsIHUpKTsKCiAgICAgIC8vIEFkdmFuY2UgdGhlIHByZXZpb3VzIHBvaW50cy4KICAgICAgbGFtYmRhMCQzID0gbGFtYmRhLCBjb3NQaGkwJDIgPSBjb3NQaGksIHNpblBoaTAkMiA9IHNpblBoaTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhJDQob2JqZWN0KSB7CiAgICAgIGFyZWFTdW0kMi5yZXNldCgpOwogICAgICBnZW9TdHJlYW0kMShvYmplY3QsIGFyZWFTdHJlYW0kMik7CiAgICAgIHJldHVybiBhcmVhU3VtJDIgKiAyOwogICAgfQoKICAgIGZ1bmN0aW9uIHNwaGVyaWNhbCQxKGNhcnRlc2lhbikgewogICAgICByZXR1cm4gW2F0YW4yJDIoY2FydGVzaWFuWzFdLCBjYXJ0ZXNpYW5bMF0pLCBhc2luJDIoY2FydGVzaWFuWzJdKV07CiAgICB9CgogICAgZnVuY3Rpb24gY2FydGVzaWFuJDEoc3BoZXJpY2FsKSB7CiAgICAgIHZhciBsYW1iZGEgPSBzcGhlcmljYWxbMF0sIHBoaSA9IHNwaGVyaWNhbFsxXSwgY29zUGhpID0gY29zJDQocGhpKTsKICAgICAgcmV0dXJuIFtjb3NQaGkgKiBjb3MkNChsYW1iZGEpLCBjb3NQaGkgKiBzaW4kNChsYW1iZGEpLCBzaW4kNChwaGkpXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5Eb3QkMShhLCBiKSB7CiAgICAgIHJldHVybiBhWzBdICogYlswXSArIGFbMV0gKiBiWzFdICsgYVsyXSAqIGJbMl07CiAgICB9CgogICAgZnVuY3Rpb24gY2FydGVzaWFuQ3Jvc3MkMShhLCBiKSB7CiAgICAgIHJldHVybiBbYVsxXSAqIGJbMl0gLSBhWzJdICogYlsxXSwgYVsyXSAqIGJbMF0gLSBhWzBdICogYlsyXSwgYVswXSAqIGJbMV0gLSBhWzFdICogYlswXV07CiAgICB9CgogICAgLy8gVE9ETyByZXR1cm4gYQogICAgZnVuY3Rpb24gY2FydGVzaWFuQWRkSW5QbGFjZSQxKGEsIGIpIHsKICAgICAgYVswXSArPSBiWzBdLCBhWzFdICs9IGJbMV0sIGFbMl0gKz0gYlsyXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYXJ0ZXNpYW5TY2FsZSQxKHZlY3RvciwgaykgewogICAgICByZXR1cm4gW3ZlY3RvclswXSAqIGssIHZlY3RvclsxXSAqIGssIHZlY3RvclsyXSAqIGtdOwogICAgfQoKICAgIC8vIFRPRE8gcmV0dXJuIGQKICAgIGZ1bmN0aW9uIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UkMShkKSB7CiAgICAgIHZhciBsID0gc3FydCQzKGRbMF0gKiBkWzBdICsgZFsxXSAqIGRbMV0gKyBkWzJdICogZFsyXSk7CiAgICAgIGRbMF0gLz0gbCwgZFsxXSAvPSBsLCBkWzJdIC89IGw7CiAgICB9CgogICAgdmFyIGxhbWJkYTAkNCwgcGhpMCQxLCBsYW1iZGExJDEsIHBoaTEkMSwgLy8gYm91bmRzCiAgICAgICAgbGFtYmRhMiQxLCAvLyBwcmV2aW91cyBsYW1iZGEtY29vcmRpbmF0ZQogICAgICAgIGxhbWJkYTAwJDQsIHBoaTAwJDQsIC8vIGZpcnN0IHBvaW50CiAgICAgICAgcDAkMSwgLy8gcHJldmlvdXMgM0QgcG9pbnQKICAgICAgICBkZWx0YVN1bSQxID0gYWRkZXIkMSgpLAogICAgICAgIHJhbmdlcyQxLAogICAgICAgIHJhbmdlJDM7CgogICAgdmFyIGJvdW5kc1N0cmVhbSQyID0gewogICAgICBwb2ludDogYm91bmRzUG9pbnQkMiwKICAgICAgbGluZVN0YXJ0OiBib3VuZHNMaW5lU3RhcnQkMSwKICAgICAgbGluZUVuZDogYm91bmRzTGluZUVuZCQxLAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGJvdW5kc1N0cmVhbSQyLnBvaW50ID0gYm91bmRzUmluZ1BvaW50JDE7CiAgICAgICAgYm91bmRzU3RyZWFtJDIubGluZVN0YXJ0ID0gYm91bmRzUmluZ1N0YXJ0JDE7CiAgICAgICAgYm91bmRzU3RyZWFtJDIubGluZUVuZCA9IGJvdW5kc1JpbmdFbmQkMTsKICAgICAgICBkZWx0YVN1bSQxLnJlc2V0KCk7CiAgICAgICAgYXJlYVN0cmVhbSQyLnBvbHlnb25TdGFydCgpOwogICAgICB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBhcmVhU3RyZWFtJDIucG9seWdvbkVuZCgpOwogICAgICAgIGJvdW5kc1N0cmVhbSQyLnBvaW50ID0gYm91bmRzUG9pbnQkMjsKICAgICAgICBib3VuZHNTdHJlYW0kMi5saW5lU3RhcnQgPSBib3VuZHNMaW5lU3RhcnQkMTsKICAgICAgICBib3VuZHNTdHJlYW0kMi5saW5lRW5kID0gYm91bmRzTGluZUVuZCQxOwogICAgICAgIGlmIChhcmVhUmluZ1N1bSQyIDwgMCkgbGFtYmRhMCQ0ID0gLShsYW1iZGExJDEgPSAxODApLCBwaGkwJDEgPSAtKHBoaTEkMSA9IDkwKTsKICAgICAgICBlbHNlIGlmIChkZWx0YVN1bSQxID4gZXBzaWxvbiQ3KSBwaGkxJDEgPSA5MDsKICAgICAgICBlbHNlIGlmIChkZWx0YVN1bSQxIDwgLWVwc2lsb24kNykgcGhpMCQxID0gLTkwOwogICAgICAgIHJhbmdlJDNbMF0gPSBsYW1iZGEwJDQsIHJhbmdlJDNbMV0gPSBsYW1iZGExJDE7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYm91bmRzUG9pbnQkMihsYW1iZGEsIHBoaSkgewogICAgICByYW5nZXMkMS5wdXNoKHJhbmdlJDMgPSBbbGFtYmRhMCQ0ID0gbGFtYmRhLCBsYW1iZGExJDEgPSBsYW1iZGFdKTsKICAgICAgaWYgKHBoaSA8IHBoaTAkMSkgcGhpMCQxID0gcGhpOwogICAgICBpZiAocGhpID4gcGhpMSQxKSBwaGkxJDEgPSBwaGk7CiAgICB9CgogICAgZnVuY3Rpb24gbGluZVBvaW50JDEobGFtYmRhLCBwaGkpIHsKICAgICAgdmFyIHAgPSBjYXJ0ZXNpYW4kMShbbGFtYmRhICogcmFkaWFucyQxLCBwaGkgKiByYWRpYW5zJDFdKTsKICAgICAgaWYgKHAwJDEpIHsKICAgICAgICB2YXIgbm9ybWFsID0gY2FydGVzaWFuQ3Jvc3MkMShwMCQxLCBwKSwKICAgICAgICAgICAgZXF1YXRvcmlhbCA9IFtub3JtYWxbMV0sIC1ub3JtYWxbMF0sIDBdLAogICAgICAgICAgICBpbmZsZWN0aW9uID0gY2FydGVzaWFuQ3Jvc3MkMShlcXVhdG9yaWFsLCBub3JtYWwpOwogICAgICAgIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UkMShpbmZsZWN0aW9uKTsKICAgICAgICBpbmZsZWN0aW9uID0gc3BoZXJpY2FsJDEoaW5mbGVjdGlvbik7CiAgICAgICAgdmFyIGRlbHRhID0gbGFtYmRhIC0gbGFtYmRhMiQxLAogICAgICAgICAgICBzaWduID0gZGVsdGEgPiAwID8gMSA6IC0xLAogICAgICAgICAgICBsYW1iZGFpID0gaW5mbGVjdGlvblswXSAqIGRlZ3JlZXMkMyAqIHNpZ24sCiAgICAgICAgICAgIHBoaWksCiAgICAgICAgICAgIGFudGltZXJpZGlhbiA9IGFicyQyKGRlbHRhKSA+IDE4MDsKICAgICAgICBpZiAoYW50aW1lcmlkaWFuIF4gKHNpZ24gKiBsYW1iZGEyJDEgPCBsYW1iZGFpICYmIGxhbWJkYWkgPCBzaWduICogbGFtYmRhKSkgewogICAgICAgICAgcGhpaSA9IGluZmxlY3Rpb25bMV0gKiBkZWdyZWVzJDM7CiAgICAgICAgICBpZiAocGhpaSA+IHBoaTEkMSkgcGhpMSQxID0gcGhpaTsKICAgICAgICB9IGVsc2UgaWYgKGxhbWJkYWkgPSAobGFtYmRhaSArIDM2MCkgJSAzNjAgLSAxODAsIGFudGltZXJpZGlhbiBeIChzaWduICogbGFtYmRhMiQxIDwgbGFtYmRhaSAmJiBsYW1iZGFpIDwgc2lnbiAqIGxhbWJkYSkpIHsKICAgICAgICAgIHBoaWkgPSAtaW5mbGVjdGlvblsxXSAqIGRlZ3JlZXMkMzsKICAgICAgICAgIGlmIChwaGlpIDwgcGhpMCQxKSBwaGkwJDEgPSBwaGlpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAocGhpIDwgcGhpMCQxKSBwaGkwJDEgPSBwaGk7CiAgICAgICAgICBpZiAocGhpID4gcGhpMSQxKSBwaGkxJDEgPSBwaGk7CiAgICAgICAgfQogICAgICAgIGlmIChhbnRpbWVyaWRpYW4pIHsKICAgICAgICAgIGlmIChsYW1iZGEgPCBsYW1iZGEyJDEpIHsKICAgICAgICAgICAgaWYgKGFuZ2xlJDEobGFtYmRhMCQ0LCBsYW1iZGEpID4gYW5nbGUkMShsYW1iZGEwJDQsIGxhbWJkYTEkMSkpIGxhbWJkYTEkMSA9IGxhbWJkYTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGlmIChhbmdsZSQxKGxhbWJkYSwgbGFtYmRhMSQxKSA+IGFuZ2xlJDEobGFtYmRhMCQ0LCBsYW1iZGExJDEpKSBsYW1iZGEwJDQgPSBsYW1iZGE7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChsYW1iZGExJDEgPj0gbGFtYmRhMCQ0KSB7CiAgICAgICAgICAgIGlmIChsYW1iZGEgPCBsYW1iZGEwJDQpIGxhbWJkYTAkNCA9IGxhbWJkYTsKICAgICAgICAgICAgaWYgKGxhbWJkYSA+IGxhbWJkYTEkMSkgbGFtYmRhMSQxID0gbGFtYmRhOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKGxhbWJkYSA+IGxhbWJkYTIkMSkgewogICAgICAgICAgICAgIGlmIChhbmdsZSQxKGxhbWJkYTAkNCwgbGFtYmRhKSA+IGFuZ2xlJDEobGFtYmRhMCQ0LCBsYW1iZGExJDEpKSBsYW1iZGExJDEgPSBsYW1iZGE7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgaWYgKGFuZ2xlJDEobGFtYmRhLCBsYW1iZGExJDEpID4gYW5nbGUkMShsYW1iZGEwJDQsIGxhbWJkYTEkMSkpIGxhbWJkYTAkNCA9IGxhbWJkYTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSBlbHNlIHsKICAgICAgICByYW5nZXMkMS5wdXNoKHJhbmdlJDMgPSBbbGFtYmRhMCQ0ID0gbGFtYmRhLCBsYW1iZGExJDEgPSBsYW1iZGFdKTsKICAgICAgfQogICAgICBpZiAocGhpIDwgcGhpMCQxKSBwaGkwJDEgPSBwaGk7CiAgICAgIGlmIChwaGkgPiBwaGkxJDEpIHBoaTEkMSA9IHBoaTsKICAgICAgcDAkMSA9IHAsIGxhbWJkYTIkMSA9IGxhbWJkYTsKICAgIH0KCiAgICBmdW5jdGlvbiBib3VuZHNMaW5lU3RhcnQkMSgpIHsKICAgICAgYm91bmRzU3RyZWFtJDIucG9pbnQgPSBsaW5lUG9pbnQkMTsKICAgIH0KCiAgICBmdW5jdGlvbiBib3VuZHNMaW5lRW5kJDEoKSB7CiAgICAgIHJhbmdlJDNbMF0gPSBsYW1iZGEwJDQsIHJhbmdlJDNbMV0gPSBsYW1iZGExJDE7CiAgICAgIGJvdW5kc1N0cmVhbSQyLnBvaW50ID0gYm91bmRzUG9pbnQkMjsKICAgICAgcDAkMSA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmRzUmluZ1BvaW50JDEobGFtYmRhLCBwaGkpIHsKICAgICAgaWYgKHAwJDEpIHsKICAgICAgICB2YXIgZGVsdGEgPSBsYW1iZGEgLSBsYW1iZGEyJDE7CiAgICAgICAgZGVsdGFTdW0kMS5hZGQoYWJzJDIoZGVsdGEpID4gMTgwID8gZGVsdGEgKyAoZGVsdGEgPiAwID8gMzYwIDogLTM2MCkgOiBkZWx0YSk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgbGFtYmRhMDAkNCA9IGxhbWJkYSwgcGhpMDAkNCA9IHBoaTsKICAgICAgfQogICAgICBhcmVhU3RyZWFtJDIucG9pbnQobGFtYmRhLCBwaGkpOwogICAgICBsaW5lUG9pbnQkMShsYW1iZGEsIHBoaSk7CiAgICB9CgogICAgZnVuY3Rpb24gYm91bmRzUmluZ1N0YXJ0JDEoKSB7CiAgICAgIGFyZWFTdHJlYW0kMi5saW5lU3RhcnQoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBib3VuZHNSaW5nRW5kJDEoKSB7CiAgICAgIGJvdW5kc1JpbmdQb2ludCQxKGxhbWJkYTAwJDQsIHBoaTAwJDQpOwogICAgICBhcmVhU3RyZWFtJDIubGluZUVuZCgpOwogICAgICBpZiAoYWJzJDIoZGVsdGFTdW0kMSkgPiBlcHNpbG9uJDcpIGxhbWJkYTAkNCA9IC0obGFtYmRhMSQxID0gMTgwKTsKICAgICAgcmFuZ2UkM1swXSA9IGxhbWJkYTAkNCwgcmFuZ2UkM1sxXSA9IGxhbWJkYTEkMTsKICAgICAgcDAkMSA9IG51bGw7CiAgICB9CgogICAgLy8gRmluZHMgdGhlIGxlZnQtcmlnaHQgZGlzdGFuY2UgYmV0d2VlbiB0d28gbG9uZ2l0dWRlcy4KICAgIC8vIFRoaXMgaXMgYWxtb3N0IHRoZSBzYW1lIGFzIChsYW1iZGExIC0gbGFtYmRhMCArIDM2MMKwKSAlIDM2MMKwLCBleGNlcHQgdGhhdCB3ZSB3YW50CiAgICAvLyB0aGUgZGlzdGFuY2UgYmV0d2VlbiDCsTE4MMKwIHRvIGJlIDM2MMKwLgogICAgZnVuY3Rpb24gYW5nbGUkMShsYW1iZGEwLCBsYW1iZGExKSB7CiAgICAgIHJldHVybiAobGFtYmRhMSAtPSBsYW1iZGEwKSA8IDAgPyBsYW1iZGExICsgMzYwIDogbGFtYmRhMTsKICAgIH0KCiAgICBmdW5jdGlvbiByYW5nZUNvbXBhcmUkMShhLCBiKSB7CiAgICAgIHJldHVybiBhWzBdIC0gYlswXTsKICAgIH0KCiAgICBmdW5jdGlvbiByYW5nZUNvbnRhaW5zJDEocmFuZ2UsIHgpIHsKICAgICAgcmV0dXJuIHJhbmdlWzBdIDw9IHJhbmdlWzFdID8gcmFuZ2VbMF0gPD0geCAmJiB4IDw9IHJhbmdlWzFdIDogeCA8IHJhbmdlWzBdIHx8IHJhbmdlWzFdIDwgeDsKICAgIH0KCiAgICBmdW5jdGlvbiBib3VuZHMkMShmZWF0dXJlKSB7CiAgICAgIHZhciBpLCBuLCBhLCBiLCBtZXJnZWQsIGRlbHRhTWF4LCBkZWx0YTsKCiAgICAgIHBoaTEkMSA9IGxhbWJkYTEkMSA9IC0obGFtYmRhMCQ0ID0gcGhpMCQxID0gSW5maW5pdHkpOwogICAgICByYW5nZXMkMSA9IFtdOwogICAgICBnZW9TdHJlYW0kMShmZWF0dXJlLCBib3VuZHNTdHJlYW0kMik7CgogICAgICAvLyBGaXJzdCwgc29ydCByYW5nZXMgYnkgdGhlaXIgbWluaW11bSBsb25naXR1ZGVzLgogICAgICBpZiAobiA9IHJhbmdlcyQxLmxlbmd0aCkgewogICAgICAgIHJhbmdlcyQxLnNvcnQocmFuZ2VDb21wYXJlJDEpOwoKICAgICAgICAvLyBUaGVuLCBtZXJnZSBhbnkgcmFuZ2VzIHRoYXQgb3ZlcmxhcC4KICAgICAgICBmb3IgKGkgPSAxLCBhID0gcmFuZ2VzJDFbMF0sIG1lcmdlZCA9IFthXTsgaSA8IG47ICsraSkgewogICAgICAgICAgYiA9IHJhbmdlcyQxW2ldOwogICAgICAgICAgaWYgKHJhbmdlQ29udGFpbnMkMShhLCBiWzBdKSB8fCByYW5nZUNvbnRhaW5zJDEoYSwgYlsxXSkpIHsKICAgICAgICAgICAgaWYgKGFuZ2xlJDEoYVswXSwgYlsxXSkgPiBhbmdsZSQxKGFbMF0sIGFbMV0pKSBhWzFdID0gYlsxXTsKICAgICAgICAgICAgaWYgKGFuZ2xlJDEoYlswXSwgYVsxXSkgPiBhbmdsZSQxKGFbMF0sIGFbMV0pKSBhWzBdID0gYlswXTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG1lcmdlZC5wdXNoKGEgPSBiKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIEZpbmFsbHksIGZpbmQgdGhlIGxhcmdlc3QgZ2FwIGJldHdlZW4gdGhlIG1lcmdlZCByYW5nZXMuCiAgICAgICAgLy8gVGhlIGZpbmFsIGJvdW5kaW5nIGJveCB3aWxsIGJlIHRoZSBpbnZlcnNlIG9mIHRoaXMgZ2FwLgogICAgICAgIGZvciAoZGVsdGFNYXggPSAtSW5maW5pdHksIG4gPSBtZXJnZWQubGVuZ3RoIC0gMSwgaSA9IDAsIGEgPSBtZXJnZWRbbl07IGkgPD0gbjsgYSA9IGIsICsraSkgewogICAgICAgICAgYiA9IG1lcmdlZFtpXTsKICAgICAgICAgIGlmICgoZGVsdGEgPSBhbmdsZSQxKGFbMV0sIGJbMF0pKSA+IGRlbHRhTWF4KSBkZWx0YU1heCA9IGRlbHRhLCBsYW1iZGEwJDQgPSBiWzBdLCBsYW1iZGExJDEgPSBhWzFdOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmFuZ2VzJDEgPSByYW5nZSQzID0gbnVsbDsKCiAgICAgIHJldHVybiBsYW1iZGEwJDQgPT09IEluZmluaXR5IHx8IHBoaTAkMSA9PT0gSW5maW5pdHkKICAgICAgICAgID8gW1tOYU4sIE5hTl0sIFtOYU4sIE5hTl1dCiAgICAgICAgICA6IFtbbGFtYmRhMCQ0LCBwaGkwJDFdLCBbbGFtYmRhMSQxLCBwaGkxJDFdXTsKICAgIH0KCiAgICB2YXIgVzAkMSwgVzEkMSwKICAgICAgICBYMCQyLCBZMCQyLCBaMCQyLAogICAgICAgIFgxJDIsIFkxJDIsIFoxJDIsCiAgICAgICAgWDIkMiwgWTIkMiwgWjIkMiwKICAgICAgICBsYW1iZGEwMCQ1LCBwaGkwMCQ1LCAvLyBmaXJzdCBwb2ludAogICAgICAgIHgwJDUsIHkwJDUsIHowJDE7IC8vIHByZXZpb3VzIHBvaW50CgogICAgdmFyIGNlbnRyb2lkU3RyZWFtJDIgPSB7CiAgICAgIHNwaGVyZTogbm9vcCQ4LAogICAgICBwb2ludDogY2VudHJvaWRQb2ludCQyLAogICAgICBsaW5lU3RhcnQ6IGNlbnRyb2lkTGluZVN0YXJ0JDIsCiAgICAgIGxpbmVFbmQ6IGNlbnRyb2lkTGluZUVuZCQyLAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGNlbnRyb2lkU3RyZWFtJDIubGluZVN0YXJ0ID0gY2VudHJvaWRSaW5nU3RhcnQkMjsKICAgICAgICBjZW50cm9pZFN0cmVhbSQyLmxpbmVFbmQgPSBjZW50cm9pZFJpbmdFbmQkMjsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgY2VudHJvaWRTdHJlYW0kMi5saW5lU3RhcnQgPSBjZW50cm9pZExpbmVTdGFydCQyOwogICAgICAgIGNlbnRyb2lkU3RyZWFtJDIubGluZUVuZCA9IGNlbnRyb2lkTGluZUVuZCQyOwogICAgICB9CiAgICB9OwoKICAgIC8vIEFyaXRobWV0aWMgbWVhbiBvZiBDYXJ0ZXNpYW4gdmVjdG9ycy4KICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnQkMihsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucyQxLCBwaGkgKj0gcmFkaWFucyQxOwogICAgICB2YXIgY29zUGhpID0gY29zJDQocGhpKTsKICAgICAgY2VudHJvaWRQb2ludENhcnRlc2lhbiQxKGNvc1BoaSAqIGNvcyQ0KGxhbWJkYSksIGNvc1BoaSAqIHNpbiQ0KGxhbWJkYSksIHNpbiQ0KHBoaSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnRDYXJ0ZXNpYW4kMSh4LCB5LCB6KSB7CiAgICAgICsrVzAkMTsKICAgICAgWDAkMiArPSAoeCAtIFgwJDIpIC8gVzAkMTsKICAgICAgWTAkMiArPSAoeSAtIFkwJDIpIC8gVzAkMTsKICAgICAgWjAkMiArPSAoeiAtIFowJDIpIC8gVzAkMTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZExpbmVTdGFydCQyKCkgewogICAgICBjZW50cm9pZFN0cmVhbSQyLnBvaW50ID0gY2VudHJvaWRMaW5lUG9pbnRGaXJzdCQxOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZVBvaW50Rmlyc3QkMShsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucyQxLCBwaGkgKj0gcmFkaWFucyQxOwogICAgICB2YXIgY29zUGhpID0gY29zJDQocGhpKTsKICAgICAgeDAkNSA9IGNvc1BoaSAqIGNvcyQ0KGxhbWJkYSk7CiAgICAgIHkwJDUgPSBjb3NQaGkgKiBzaW4kNChsYW1iZGEpOwogICAgICB6MCQxID0gc2luJDQocGhpKTsKICAgICAgY2VudHJvaWRTdHJlYW0kMi5wb2ludCA9IGNlbnRyb2lkTGluZVBvaW50JDE7CiAgICAgIGNlbnRyb2lkUG9pbnRDYXJ0ZXNpYW4kMSh4MCQ1LCB5MCQ1LCB6MCQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZExpbmVQb2ludCQxKGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zJDEsIHBoaSAqPSByYWRpYW5zJDE7CiAgICAgIHZhciBjb3NQaGkgPSBjb3MkNChwaGkpLAogICAgICAgICAgeCA9IGNvc1BoaSAqIGNvcyQ0KGxhbWJkYSksCiAgICAgICAgICB5ID0gY29zUGhpICogc2luJDQobGFtYmRhKSwKICAgICAgICAgIHogPSBzaW4kNChwaGkpLAogICAgICAgICAgdyA9IGF0YW4yJDIoc3FydCQzKCh3ID0geTAkNSAqIHogLSB6MCQxICogeSkgKiB3ICsgKHcgPSB6MCQxICogeCAtIHgwJDUgKiB6KSAqIHcgKyAodyA9IHgwJDUgKiB5IC0geTAkNSAqIHgpICogdyksIHgwJDUgKiB4ICsgeTAkNSAqIHkgKyB6MCQxICogeik7CiAgICAgIFcxJDEgKz0gdzsKICAgICAgWDEkMiArPSB3ICogKHgwJDUgKyAoeDAkNSA9IHgpKTsKICAgICAgWTEkMiArPSB3ICogKHkwJDUgKyAoeTAkNSA9IHkpKTsKICAgICAgWjEkMiArPSB3ICogKHowJDEgKyAoejAkMSA9IHopKTsKICAgICAgY2VudHJvaWRQb2ludENhcnRlc2lhbiQxKHgwJDUsIHkwJDUsIHowJDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZUVuZCQyKCkgewogICAgICBjZW50cm9pZFN0cmVhbSQyLnBvaW50ID0gY2VudHJvaWRQb2ludCQyOwogICAgfQoKICAgIC8vIFNlZSBKLiBFLiBCcm9jaywgVGhlIEluZXJ0aWEgVGVuc29yIGZvciBhIFNwaGVyaWNhbCBUcmlhbmdsZSwKICAgIC8vIEouIEFwcGxpZWQgTWVjaGFuaWNzIDQyLCAyMzkgKDE5NzUpLgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nU3RhcnQkMigpIHsKICAgICAgY2VudHJvaWRTdHJlYW0kMi5wb2ludCA9IGNlbnRyb2lkUmluZ1BvaW50Rmlyc3QkMTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZFJpbmdFbmQkMigpIHsKICAgICAgY2VudHJvaWRSaW5nUG9pbnQkMShsYW1iZGEwMCQ1LCBwaGkwMCQ1KTsKICAgICAgY2VudHJvaWRTdHJlYW0kMi5wb2ludCA9IGNlbnRyb2lkUG9pbnQkMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZFJpbmdQb2ludEZpcnN0JDEobGFtYmRhLCBwaGkpIHsKICAgICAgbGFtYmRhMDAkNSA9IGxhbWJkYSwgcGhpMDAkNSA9IHBoaTsKICAgICAgbGFtYmRhICo9IHJhZGlhbnMkMSwgcGhpICo9IHJhZGlhbnMkMTsKICAgICAgY2VudHJvaWRTdHJlYW0kMi5wb2ludCA9IGNlbnRyb2lkUmluZ1BvaW50JDE7CiAgICAgIHZhciBjb3NQaGkgPSBjb3MkNChwaGkpOwogICAgICB4MCQ1ID0gY29zUGhpICogY29zJDQobGFtYmRhKTsKICAgICAgeTAkNSA9IGNvc1BoaSAqIHNpbiQ0KGxhbWJkYSk7CiAgICAgIHowJDEgPSBzaW4kNChwaGkpOwogICAgICBjZW50cm9pZFBvaW50Q2FydGVzaWFuJDEoeDAkNSwgeTAkNSwgejAkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nUG9pbnQkMShsYW1iZGEsIHBoaSkgewogICAgICBsYW1iZGEgKj0gcmFkaWFucyQxLCBwaGkgKj0gcmFkaWFucyQxOwogICAgICB2YXIgY29zUGhpID0gY29zJDQocGhpKSwKICAgICAgICAgIHggPSBjb3NQaGkgKiBjb3MkNChsYW1iZGEpLAogICAgICAgICAgeSA9IGNvc1BoaSAqIHNpbiQ0KGxhbWJkYSksCiAgICAgICAgICB6ID0gc2luJDQocGhpKSwKICAgICAgICAgIGN4ID0geTAkNSAqIHogLSB6MCQxICogeSwKICAgICAgICAgIGN5ID0gejAkMSAqIHggLSB4MCQ1ICogeiwKICAgICAgICAgIGN6ID0geDAkNSAqIHkgLSB5MCQ1ICogeCwKICAgICAgICAgIG0gPSBzcXJ0JDMoY3ggKiBjeCArIGN5ICogY3kgKyBjeiAqIGN6KSwKICAgICAgICAgIHcgPSBhc2luJDIobSksIC8vIGxpbmUgd2VpZ2h0ID0gYW5nbGUKICAgICAgICAgIHYgPSBtICYmIC13IC8gbTsgLy8gYXJlYSB3ZWlnaHQgbXVsdGlwbGllcgogICAgICBYMiQyICs9IHYgKiBjeDsKICAgICAgWTIkMiArPSB2ICogY3k7CiAgICAgIFoyJDIgKz0gdiAqIGN6OwogICAgICBXMSQxICs9IHc7CiAgICAgIFgxJDIgKz0gdyAqICh4MCQ1ICsgKHgwJDUgPSB4KSk7CiAgICAgIFkxJDIgKz0gdyAqICh5MCQ1ICsgKHkwJDUgPSB5KSk7CiAgICAgIFoxJDIgKz0gdyAqICh6MCQxICsgKHowJDEgPSB6KSk7CiAgICAgIGNlbnRyb2lkUG9pbnRDYXJ0ZXNpYW4kMSh4MCQ1LCB5MCQ1LCB6MCQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZCQyKG9iamVjdCkgewogICAgICBXMCQxID0gVzEkMSA9CiAgICAgIFgwJDIgPSBZMCQyID0gWjAkMiA9CiAgICAgIFgxJDIgPSBZMSQyID0gWjEkMiA9CiAgICAgIFgyJDIgPSBZMiQyID0gWjIkMiA9IDA7CiAgICAgIGdlb1N0cmVhbSQxKG9iamVjdCwgY2VudHJvaWRTdHJlYW0kMik7CgogICAgICB2YXIgeCA9IFgyJDIsCiAgICAgICAgICB5ID0gWTIkMiwKICAgICAgICAgIHogPSBaMiQyLAogICAgICAgICAgbSA9IHggKiB4ICsgeSAqIHkgKyB6ICogejsKCiAgICAgIC8vIElmIHRoZSBhcmVhLXdlaWdodGVkIGNjZW50cm9pZCBpcyB1bmRlZmluZWQsIGZhbGwgYmFjayB0byBsZW5ndGgtd2VpZ2h0ZWQgY2NlbnRyb2lkLgogICAgICBpZiAobSA8IGVwc2lsb24yJDMpIHsKICAgICAgICB4ID0gWDEkMiwgeSA9IFkxJDIsIHogPSBaMSQyOwogICAgICAgIC8vIElmIHRoZSBmZWF0dXJlIGhhcyB6ZXJvIGxlbmd0aCwgZmFsbCBiYWNrIHRvIGFyaXRobWV0aWMgbWVhbiBvZiBwb2ludCB2ZWN0b3JzLgogICAgICAgIGlmIChXMSQxIDwgZXBzaWxvbiQ3KSB4ID0gWDAkMiwgeSA9IFkwJDIsIHogPSBaMCQyOwogICAgICAgIG0gPSB4ICogeCArIHkgKiB5ICsgeiAqIHo7CiAgICAgICAgLy8gSWYgdGhlIGZlYXR1cmUgc3RpbGwgaGFzIGFuIHVuZGVmaW5lZCBjY2VudHJvaWQsIHRoZW4gcmV0dXJuLgogICAgICAgIGlmIChtIDwgZXBzaWxvbjIkMykgcmV0dXJuIFtOYU4sIE5hTl07CiAgICAgIH0KCiAgICAgIHJldHVybiBbYXRhbjIkMih5LCB4KSAqIGRlZ3JlZXMkMywgYXNpbiQyKHogLyBzcXJ0JDMobSkpICogZGVncmVlcyQzXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudCRtKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbXBvc2UkMShhLCBiKSB7CgogICAgICBmdW5jdGlvbiBjb21wb3NlKHgsIHkpIHsKICAgICAgICByZXR1cm4geCA9IGEoeCwgeSksIGIoeFswXSwgeFsxXSk7CiAgICAgIH0KCiAgICAgIGlmIChhLmludmVydCAmJiBiLmludmVydCkgY29tcG9zZS5pbnZlcnQgPSBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgcmV0dXJuIHggPSBiLmludmVydCh4LCB5KSwgeCAmJiBhLmludmVydCh4WzBdLCB4WzFdKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBjb21wb3NlOwogICAgfQoKICAgIGZ1bmN0aW9uIHJvdGF0aW9uSWRlbnRpdHkkMShsYW1iZGEsIHBoaSkgewogICAgICByZXR1cm4gW2xhbWJkYSA+IHBpJDggPyBsYW1iZGEgLSB0YXUkOCA6IGxhbWJkYSA8IC1waSQ4ID8gbGFtYmRhICsgdGF1JDggOiBsYW1iZGEsIHBoaV07CiAgICB9CgogICAgcm90YXRpb25JZGVudGl0eSQxLmludmVydCA9IHJvdGF0aW9uSWRlbnRpdHkkMTsKCiAgICBmdW5jdGlvbiByb3RhdGVSYWRpYW5zJDEoZGVsdGFMYW1iZGEsIGRlbHRhUGhpLCBkZWx0YUdhbW1hKSB7CiAgICAgIHJldHVybiAoZGVsdGFMYW1iZGEgJT0gdGF1JDgpID8gKGRlbHRhUGhpIHx8IGRlbHRhR2FtbWEgPyBjb21wb3NlJDEocm90YXRpb25MYW1iZGEkMShkZWx0YUxhbWJkYSksIHJvdGF0aW9uUGhpR2FtbWEkMShkZWx0YVBoaSwgZGVsdGFHYW1tYSkpCiAgICAgICAgOiByb3RhdGlvbkxhbWJkYSQxKGRlbHRhTGFtYmRhKSkKICAgICAgICA6IChkZWx0YVBoaSB8fCBkZWx0YUdhbW1hID8gcm90YXRpb25QaGlHYW1tYSQxKGRlbHRhUGhpLCBkZWx0YUdhbW1hKQogICAgICAgIDogcm90YXRpb25JZGVudGl0eSQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3J3YXJkUm90YXRpb25MYW1iZGEkMShkZWx0YUxhbWJkYSkgewogICAgICByZXR1cm4gZnVuY3Rpb24obGFtYmRhLCBwaGkpIHsKICAgICAgICByZXR1cm4gbGFtYmRhICs9IGRlbHRhTGFtYmRhLCBbbGFtYmRhID4gcGkkOCA/IGxhbWJkYSAtIHRhdSQ4IDogbGFtYmRhIDwgLXBpJDggPyBsYW1iZGEgKyB0YXUkOCA6IGxhbWJkYSwgcGhpXTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiByb3RhdGlvbkxhbWJkYSQxKGRlbHRhTGFtYmRhKSB7CiAgICAgIHZhciByb3RhdGlvbiA9IGZvcndhcmRSb3RhdGlvbkxhbWJkYSQxKGRlbHRhTGFtYmRhKTsKICAgICAgcm90YXRpb24uaW52ZXJ0ID0gZm9yd2FyZFJvdGF0aW9uTGFtYmRhJDEoLWRlbHRhTGFtYmRhKTsKICAgICAgcmV0dXJuIHJvdGF0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIHJvdGF0aW9uUGhpR2FtbWEkMShkZWx0YVBoaSwgZGVsdGFHYW1tYSkgewogICAgICB2YXIgY29zRGVsdGFQaGkgPSBjb3MkNChkZWx0YVBoaSksCiAgICAgICAgICBzaW5EZWx0YVBoaSA9IHNpbiQ0KGRlbHRhUGhpKSwKICAgICAgICAgIGNvc0RlbHRhR2FtbWEgPSBjb3MkNChkZWx0YUdhbW1hKSwKICAgICAgICAgIHNpbkRlbHRhR2FtbWEgPSBzaW4kNChkZWx0YUdhbW1hKTsKCiAgICAgIGZ1bmN0aW9uIHJvdGF0aW9uKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgdmFyIGNvc1BoaSA9IGNvcyQ0KHBoaSksCiAgICAgICAgICAgIHggPSBjb3MkNChsYW1iZGEpICogY29zUGhpLAogICAgICAgICAgICB5ID0gc2luJDQobGFtYmRhKSAqIGNvc1BoaSwKICAgICAgICAgICAgeiA9IHNpbiQ0KHBoaSksCiAgICAgICAgICAgIGsgPSB6ICogY29zRGVsdGFQaGkgKyB4ICogc2luRGVsdGFQaGk7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgIGF0YW4yJDIoeSAqIGNvc0RlbHRhR2FtbWEgLSBrICogc2luRGVsdGFHYW1tYSwgeCAqIGNvc0RlbHRhUGhpIC0geiAqIHNpbkRlbHRhUGhpKSwKICAgICAgICAgIGFzaW4kMihrICogY29zRGVsdGFHYW1tYSArIHkgKiBzaW5EZWx0YUdhbW1hKQogICAgICAgIF07CiAgICAgIH0KCiAgICAgIHJvdGF0aW9uLmludmVydCA9IGZ1bmN0aW9uKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgdmFyIGNvc1BoaSA9IGNvcyQ0KHBoaSksCiAgICAgICAgICAgIHggPSBjb3MkNChsYW1iZGEpICogY29zUGhpLAogICAgICAgICAgICB5ID0gc2luJDQobGFtYmRhKSAqIGNvc1BoaSwKICAgICAgICAgICAgeiA9IHNpbiQ0KHBoaSksCiAgICAgICAgICAgIGsgPSB6ICogY29zRGVsdGFHYW1tYSAtIHkgKiBzaW5EZWx0YUdhbW1hOwogICAgICAgIHJldHVybiBbCiAgICAgICAgICBhdGFuMiQyKHkgKiBjb3NEZWx0YUdhbW1hICsgeiAqIHNpbkRlbHRhR2FtbWEsIHggKiBjb3NEZWx0YVBoaSArIGsgKiBzaW5EZWx0YVBoaSksCiAgICAgICAgICBhc2luJDIoayAqIGNvc0RlbHRhUGhpIC0geCAqIHNpbkRlbHRhUGhpKQogICAgICAgIF07CiAgICAgIH07CgogICAgICByZXR1cm4gcm90YXRpb247CiAgICB9CgogICAgZnVuY3Rpb24gcm90YXRpb24kMShyb3RhdGUpIHsKICAgICAgcm90YXRlID0gcm90YXRlUmFkaWFucyQxKHJvdGF0ZVswXSAqIHJhZGlhbnMkMSwgcm90YXRlWzFdICogcmFkaWFucyQxLCByb3RhdGUubGVuZ3RoID4gMiA/IHJvdGF0ZVsyXSAqIHJhZGlhbnMkMSA6IDApOwoKICAgICAgZnVuY3Rpb24gZm9yd2FyZChjb29yZGluYXRlcykgewogICAgICAgIGNvb3JkaW5hdGVzID0gcm90YXRlKGNvb3JkaW5hdGVzWzBdICogcmFkaWFucyQxLCBjb29yZGluYXRlc1sxXSAqIHJhZGlhbnMkMSk7CiAgICAgICAgcmV0dXJuIGNvb3JkaW5hdGVzWzBdICo9IGRlZ3JlZXMkMywgY29vcmRpbmF0ZXNbMV0gKj0gZGVncmVlcyQzLCBjb29yZGluYXRlczsKICAgICAgfQoKICAgICAgZm9yd2FyZC5pbnZlcnQgPSBmdW5jdGlvbihjb29yZGluYXRlcykgewogICAgICAgIGNvb3JkaW5hdGVzID0gcm90YXRlLmludmVydChjb29yZGluYXRlc1swXSAqIHJhZGlhbnMkMSwgY29vcmRpbmF0ZXNbMV0gKiByYWRpYW5zJDEpOwogICAgICAgIHJldHVybiBjb29yZGluYXRlc1swXSAqPSBkZWdyZWVzJDMsIGNvb3JkaW5hdGVzWzFdICo9IGRlZ3JlZXMkMywgY29vcmRpbmF0ZXM7CiAgICAgIH07CgogICAgICByZXR1cm4gZm9yd2FyZDsKICAgIH0KCiAgICAvLyBHZW5lcmF0ZXMgYSBjaXJjbGUgY2VudGVyZWQgYXQgWzDCsCwgMMKwXSwgd2l0aCBhIGdpdmVuIHJhZGl1cyBhbmQgcHJlY2lzaW9uLgogICAgZnVuY3Rpb24gY2lyY2xlU3RyZWFtJDEoc3RyZWFtLCByYWRpdXMsIGRlbHRhLCBkaXJlY3Rpb24sIHQwLCB0MSkgewogICAgICBpZiAoIWRlbHRhKSByZXR1cm47CiAgICAgIHZhciBjb3NSYWRpdXMgPSBjb3MkNChyYWRpdXMpLAogICAgICAgICAgc2luUmFkaXVzID0gc2luJDQocmFkaXVzKSwKICAgICAgICAgIHN0ZXAgPSBkaXJlY3Rpb24gKiBkZWx0YTsKICAgICAgaWYgKHQwID09IG51bGwpIHsKICAgICAgICB0MCA9IHJhZGl1cyArIGRpcmVjdGlvbiAqIHRhdSQ4OwogICAgICAgIHQxID0gcmFkaXVzIC0gc3RlcCAvIDI7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgdDAgPSBjaXJjbGVSYWRpdXMkMShjb3NSYWRpdXMsIHQwKTsKICAgICAgICB0MSA9IGNpcmNsZVJhZGl1cyQxKGNvc1JhZGl1cywgdDEpOwogICAgICAgIGlmIChkaXJlY3Rpb24gPiAwID8gdDAgPCB0MSA6IHQwID4gdDEpIHQwICs9IGRpcmVjdGlvbiAqIHRhdSQ4OwogICAgICB9CiAgICAgIGZvciAodmFyIHBvaW50LCB0ID0gdDA7IGRpcmVjdGlvbiA+IDAgPyB0ID4gdDEgOiB0IDwgdDE7IHQgLT0gc3RlcCkgewogICAgICAgIHBvaW50ID0gc3BoZXJpY2FsJDEoW2Nvc1JhZGl1cywgLXNpblJhZGl1cyAqIGNvcyQ0KHQpLCAtc2luUmFkaXVzICogc2luJDQodCldKTsKICAgICAgICBzdHJlYW0ucG9pbnQocG9pbnRbMF0sIHBvaW50WzFdKTsKICAgICAgfQogICAgfQoKICAgIC8vIFJldHVybnMgdGhlIHNpZ25lZCBhbmdsZSBvZiBhIGNhcnRlc2lhbiBwb2ludCByZWxhdGl2ZSB0byBbY29zUmFkaXVzLCAwLCAwXS4KICAgIGZ1bmN0aW9uIGNpcmNsZVJhZGl1cyQxKGNvc1JhZGl1cywgcG9pbnQpIHsKICAgICAgcG9pbnQgPSBjYXJ0ZXNpYW4kMShwb2ludCksIHBvaW50WzBdIC09IGNvc1JhZGl1czsKICAgICAgY2FydGVzaWFuTm9ybWFsaXplSW5QbGFjZSQxKHBvaW50KTsKICAgICAgdmFyIHJhZGl1cyA9IGFjb3MkMigtcG9pbnRbMV0pOwogICAgICByZXR1cm4gKCgtcG9pbnRbMl0gPCAwID8gLXJhZGl1cyA6IHJhZGl1cykgKyB0YXUkOCAtIGVwc2lsb24kNykgJSB0YXUkODsKICAgIH0KCiAgICBmdW5jdGlvbiBjaXJjbGUkMygpIHsKICAgICAgdmFyIGNlbnRlciA9IGNvbnN0YW50JG0oWzAsIDBdKSwKICAgICAgICAgIHJhZGl1cyA9IGNvbnN0YW50JG0oOTApLAogICAgICAgICAgcHJlY2lzaW9uID0gY29uc3RhbnQkbSg2KSwKICAgICAgICAgIHJpbmcsCiAgICAgICAgICByb3RhdGUsCiAgICAgICAgICBzdHJlYW0gPSB7cG9pbnQ6IHBvaW50fTsKCiAgICAgIGZ1bmN0aW9uIHBvaW50KHgsIHkpIHsKICAgICAgICByaW5nLnB1c2goeCA9IHJvdGF0ZSh4LCB5KSk7CiAgICAgICAgeFswXSAqPSBkZWdyZWVzJDMsIHhbMV0gKj0gZGVncmVlcyQzOwogICAgICB9CgogICAgICBmdW5jdGlvbiBjaXJjbGUoKSB7CiAgICAgICAgdmFyIGMgPSBjZW50ZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgciA9IHJhZGl1cy5hcHBseSh0aGlzLCBhcmd1bWVudHMpICogcmFkaWFucyQxLAogICAgICAgICAgICBwID0gcHJlY2lzaW9uLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgKiByYWRpYW5zJDE7CiAgICAgICAgcmluZyA9IFtdOwogICAgICAgIHJvdGF0ZSA9IHJvdGF0ZVJhZGlhbnMkMSgtY1swXSAqIHJhZGlhbnMkMSwgLWNbMV0gKiByYWRpYW5zJDEsIDApLmludmVydDsKICAgICAgICBjaXJjbGVTdHJlYW0kMShzdHJlYW0sIHIsIHAsIDEpOwogICAgICAgIGMgPSB7dHlwZTogIlBvbHlnb24iLCBjb29yZGluYXRlczogW3JpbmddfTsKICAgICAgICByaW5nID0gcm90YXRlID0gbnVsbDsKICAgICAgICByZXR1cm4gYzsKICAgICAgfQoKICAgICAgY2lyY2xlLmNlbnRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjZW50ZXIgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRtKFsrX1swXSwgK19bMV1dKSwgY2lyY2xlKSA6IGNlbnRlcjsKICAgICAgfTsKCiAgICAgIGNpcmNsZS5yYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocmFkaXVzID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkbSgrXyksIGNpcmNsZSkgOiByYWRpdXM7CiAgICAgIH07CgogICAgICBjaXJjbGUucHJlY2lzaW9uID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHByZWNpc2lvbiA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JG0oK18pLCBjaXJjbGUpIDogcHJlY2lzaW9uOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNpcmNsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwQnVmZmVyJDEoKSB7CiAgICAgIHZhciBsaW5lcyA9IFtdLAogICAgICAgICAgbGluZTsKICAgICAgcmV0dXJuIHsKICAgICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgICAgbGluZS5wdXNoKFt4LCB5XSk7CiAgICAgICAgfSwKICAgICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgbGluZXMucHVzaChsaW5lID0gW10pOwogICAgICAgIH0sCiAgICAgICAgbGluZUVuZDogbm9vcCQ4LAogICAgICAgIHJlam9pbjogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAobGluZXMubGVuZ3RoID4gMSkgbGluZXMucHVzaChsaW5lcy5wb3AoKS5jb25jYXQobGluZXMuc2hpZnQoKSkpOwogICAgICAgIH0sCiAgICAgICAgcmVzdWx0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIHZhciByZXN1bHQgPSBsaW5lczsKICAgICAgICAgIGxpbmVzID0gW107CiAgICAgICAgICBsaW5lID0gbnVsbDsKICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50RXF1YWwkMShhLCBiKSB7CiAgICAgIHJldHVybiBhYnMkMihhWzBdIC0gYlswXSkgPCBlcHNpbG9uJDcgJiYgYWJzJDIoYVsxXSAtIGJbMV0pIDwgZXBzaWxvbiQ3OwogICAgfQoKICAgIGZ1bmN0aW9uIEludGVyc2VjdGlvbiQxKHBvaW50LCBwb2ludHMsIG90aGVyLCBlbnRyeSkgewogICAgICB0aGlzLnggPSBwb2ludDsKICAgICAgdGhpcy56ID0gcG9pbnRzOwogICAgICB0aGlzLm8gPSBvdGhlcjsgLy8gYW5vdGhlciBpbnRlcnNlY3Rpb24KICAgICAgdGhpcy5lID0gZW50cnk7IC8vIGlzIGFuIGVudHJ5PwogICAgICB0aGlzLnYgPSBmYWxzZTsgLy8gdmlzaXRlZAogICAgICB0aGlzLm4gPSB0aGlzLnAgPSBudWxsOyAvLyBuZXh0ICYgcHJldmlvdXMKICAgIH0KCiAgICAvLyBBIGdlbmVyYWxpemVkIHBvbHlnb24gY2xpcHBpbmcgYWxnb3JpdGhtOiBnaXZlbiBhIHBvbHlnb24gdGhhdCBoYXMgYmVlbiBjdXQKICAgIC8vIGludG8gaXRzIHZpc2libGUgbGluZSBzZWdtZW50cywgYW5kIHJlam9pbnMgdGhlIHNlZ21lbnRzIGJ5IGludGVycG9sYXRpbmcKICAgIC8vIGFsb25nIHRoZSBjbGlwIGVkZ2UuCiAgICBmdW5jdGlvbiBjbGlwUmVqb2luJDEoc2VnbWVudHMsIGNvbXBhcmVJbnRlcnNlY3Rpb24sIHN0YXJ0SW5zaWRlLCBpbnRlcnBvbGF0ZSwgc3RyZWFtKSB7CiAgICAgIHZhciBzdWJqZWN0ID0gW10sCiAgICAgICAgICBjbGlwID0gW10sCiAgICAgICAgICBpLAogICAgICAgICAgbjsKCiAgICAgIHNlZ21lbnRzLmZvckVhY2goZnVuY3Rpb24oc2VnbWVudCkgewogICAgICAgIGlmICgobiA9IHNlZ21lbnQubGVuZ3RoIC0gMSkgPD0gMCkgcmV0dXJuOwogICAgICAgIHZhciBuLCBwMCA9IHNlZ21lbnRbMF0sIHAxID0gc2VnbWVudFtuXSwgeDsKCiAgICAgICAgLy8gSWYgdGhlIGZpcnN0IGFuZCBsYXN0IHBvaW50cyBvZiBhIHNlZ21lbnQgYXJlIGNvaW5jaWRlbnQsIHRoZW4gdHJlYXQgYXMgYQogICAgICAgIC8vIGNsb3NlZCByaW5nLiBUT0RPIGlmIGFsbCByaW5ncyBhcmUgY2xvc2VkLCB0aGVuIHRoZSB3aW5kaW5nIG9yZGVyIG9mIHRoZQogICAgICAgIC8vIGV4dGVyaW9yIHJpbmcgc2hvdWxkIGJlIGNoZWNrZWQuCiAgICAgICAgaWYgKHBvaW50RXF1YWwkMShwMCwgcDEpKSB7CiAgICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBzdHJlYW0ucG9pbnQoKHAwID0gc2VnbWVudFtpXSlbMF0sIHAwWzFdKTsKICAgICAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBzdWJqZWN0LnB1c2goeCA9IG5ldyBJbnRlcnNlY3Rpb24kMShwMCwgc2VnbWVudCwgbnVsbCwgdHJ1ZSkpOwogICAgICAgIGNsaXAucHVzaCh4Lm8gPSBuZXcgSW50ZXJzZWN0aW9uJDEocDAsIG51bGwsIHgsIGZhbHNlKSk7CiAgICAgICAgc3ViamVjdC5wdXNoKHggPSBuZXcgSW50ZXJzZWN0aW9uJDEocDEsIHNlZ21lbnQsIG51bGwsIGZhbHNlKSk7CiAgICAgICAgY2xpcC5wdXNoKHgubyA9IG5ldyBJbnRlcnNlY3Rpb24kMShwMSwgbnVsbCwgeCwgdHJ1ZSkpOwogICAgICB9KTsKCiAgICAgIGlmICghc3ViamVjdC5sZW5ndGgpIHJldHVybjsKCiAgICAgIGNsaXAuc29ydChjb21wYXJlSW50ZXJzZWN0aW9uKTsKICAgICAgbGluayQ0KHN1YmplY3QpOwogICAgICBsaW5rJDQoY2xpcCk7CgogICAgICBmb3IgKGkgPSAwLCBuID0gY2xpcC5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICBjbGlwW2ldLmUgPSBzdGFydEluc2lkZSA9ICFzdGFydEluc2lkZTsKICAgICAgfQoKICAgICAgdmFyIHN0YXJ0ID0gc3ViamVjdFswXSwKICAgICAgICAgIHBvaW50cywKICAgICAgICAgIHBvaW50OwoKICAgICAgd2hpbGUgKDEpIHsKICAgICAgICAvLyBGaW5kIGZpcnN0IHVudmlzaXRlZCBpbnRlcnNlY3Rpb24uCiAgICAgICAgdmFyIGN1cnJlbnQgPSBzdGFydCwKICAgICAgICAgICAgaXNTdWJqZWN0ID0gdHJ1ZTsKICAgICAgICB3aGlsZSAoY3VycmVudC52KSBpZiAoKGN1cnJlbnQgPSBjdXJyZW50Lm4pID09PSBzdGFydCkgcmV0dXJuOwogICAgICAgIHBvaW50cyA9IGN1cnJlbnQuejsKICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgZG8gewogICAgICAgICAgY3VycmVudC52ID0gY3VycmVudC5vLnYgPSB0cnVlOwogICAgICAgICAgaWYgKGN1cnJlbnQuZSkgewogICAgICAgICAgICBpZiAoaXNTdWJqZWN0KSB7CiAgICAgICAgICAgICAgZm9yIChpID0gMCwgbiA9IHBvaW50cy5sZW5ndGg7IGkgPCBuOyArK2kpIHN0cmVhbS5wb2ludCgocG9pbnQgPSBwb2ludHNbaV0pWzBdLCBwb2ludFsxXSk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgaW50ZXJwb2xhdGUoY3VycmVudC54LCBjdXJyZW50Lm4ueCwgMSwgc3RyZWFtKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjdXJyZW50ID0gY3VycmVudC5uOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKGlzU3ViamVjdCkgewogICAgICAgICAgICAgIHBvaW50cyA9IGN1cnJlbnQucC56OwogICAgICAgICAgICAgIGZvciAoaSA9IHBvaW50cy5sZW5ndGggLSAxOyBpID49IDA7IC0taSkgc3RyZWFtLnBvaW50KChwb2ludCA9IHBvaW50c1tpXSlbMF0sIHBvaW50WzFdKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpbnRlcnBvbGF0ZShjdXJyZW50LngsIGN1cnJlbnQucC54LCAtMSwgc3RyZWFtKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjdXJyZW50ID0gY3VycmVudC5wOwogICAgICAgICAgfQogICAgICAgICAgY3VycmVudCA9IGN1cnJlbnQubzsKICAgICAgICAgIHBvaW50cyA9IGN1cnJlbnQuejsKICAgICAgICAgIGlzU3ViamVjdCA9ICFpc1N1YmplY3Q7CiAgICAgICAgfSB3aGlsZSAoIWN1cnJlbnQudik7CiAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmskNChhcnJheSkgewogICAgICBpZiAoIShuID0gYXJyYXkubGVuZ3RoKSkgcmV0dXJuOwogICAgICB2YXIgbiwKICAgICAgICAgIGkgPSAwLAogICAgICAgICAgYSA9IGFycmF5WzBdLAogICAgICAgICAgYjsKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBhLm4gPSBiID0gYXJyYXlbaV07CiAgICAgICAgYi5wID0gYTsKICAgICAgICBhID0gYjsKICAgICAgfQogICAgICBhLm4gPSBiID0gYXJyYXlbMF07CiAgICAgIGIucCA9IGE7CiAgICB9CgogICAgdmFyIHN1bSQ0ID0gYWRkZXIkMSgpOwoKICAgIGZ1bmN0aW9uIHBvbHlnb25Db250YWlucyQxKHBvbHlnb24sIHBvaW50KSB7CiAgICAgIHZhciBsYW1iZGEgPSBwb2ludFswXSwKICAgICAgICAgIHBoaSA9IHBvaW50WzFdLAogICAgICAgICAgbm9ybWFsID0gW3NpbiQ0KGxhbWJkYSksIC1jb3MkNChsYW1iZGEpLCAwXSwKICAgICAgICAgIGFuZ2xlID0gMCwKICAgICAgICAgIHdpbmRpbmcgPSAwOwoKICAgICAgc3VtJDQucmVzZXQoKTsKCiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gcG9seWdvbi5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoIShtID0gKHJpbmcgPSBwb2x5Z29uW2ldKS5sZW5ndGgpKSBjb250aW51ZTsKICAgICAgICB2YXIgcmluZywKICAgICAgICAgICAgbSwKICAgICAgICAgICAgcG9pbnQwID0gcmluZ1ttIC0gMV0sCiAgICAgICAgICAgIGxhbWJkYTAgPSBwb2ludDBbMF0sCiAgICAgICAgICAgIHBoaTAgPSBwb2ludDBbMV0gLyAyICsgcXVhcnRlclBpJDEsCiAgICAgICAgICAgIHNpblBoaTAgPSBzaW4kNChwaGkwKSwKICAgICAgICAgICAgY29zUGhpMCA9IGNvcyQ0KHBoaTApOwoKICAgICAgICBmb3IgKHZhciBqID0gMDsgaiA8IG07ICsraiwgbGFtYmRhMCA9IGxhbWJkYTEsIHNpblBoaTAgPSBzaW5QaGkxLCBjb3NQaGkwID0gY29zUGhpMSwgcG9pbnQwID0gcG9pbnQxKSB7CiAgICAgICAgICB2YXIgcG9pbnQxID0gcmluZ1tqXSwKICAgICAgICAgICAgICBsYW1iZGExID0gcG9pbnQxWzBdLAogICAgICAgICAgICAgIHBoaTEgPSBwb2ludDFbMV0gLyAyICsgcXVhcnRlclBpJDEsCiAgICAgICAgICAgICAgc2luUGhpMSA9IHNpbiQ0KHBoaTEpLAogICAgICAgICAgICAgIGNvc1BoaTEgPSBjb3MkNChwaGkxKSwKICAgICAgICAgICAgICBkZWx0YSA9IGxhbWJkYTEgLSBsYW1iZGEwLAogICAgICAgICAgICAgIHNpZ24gPSBkZWx0YSA+PSAwID8gMSA6IC0xLAogICAgICAgICAgICAgIGFic0RlbHRhID0gc2lnbiAqIGRlbHRhLAogICAgICAgICAgICAgIGFudGltZXJpZGlhbiA9IGFic0RlbHRhID4gcGkkOCwKICAgICAgICAgICAgICBrID0gc2luUGhpMCAqIHNpblBoaTE7CgogICAgICAgICAgc3VtJDQuYWRkKGF0YW4yJDIoayAqIHNpZ24gKiBzaW4kNChhYnNEZWx0YSksIGNvc1BoaTAgKiBjb3NQaGkxICsgayAqIGNvcyQ0KGFic0RlbHRhKSkpOwogICAgICAgICAgYW5nbGUgKz0gYW50aW1lcmlkaWFuID8gZGVsdGEgKyBzaWduICogdGF1JDggOiBkZWx0YTsKCiAgICAgICAgICAvLyBBcmUgdGhlIGxvbmdpdHVkZXMgZWl0aGVyIHNpZGUgb2YgdGhlIHBvaW504oCZcyBtZXJpZGlhbiAobGFtYmRhKSwKICAgICAgICAgIC8vIGFuZCBhcmUgdGhlIGxhdGl0dWRlcyBzbWFsbGVyIHRoYW4gdGhlIHBhcmFsbGVsIChwaGkpPwogICAgICAgICAgaWYgKGFudGltZXJpZGlhbiBeIGxhbWJkYTAgPj0gbGFtYmRhIF4gbGFtYmRhMSA+PSBsYW1iZGEpIHsKICAgICAgICAgICAgdmFyIGFyYyA9IGNhcnRlc2lhbkNyb3NzJDEoY2FydGVzaWFuJDEocG9pbnQwKSwgY2FydGVzaWFuJDEocG9pbnQxKSk7CiAgICAgICAgICAgIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UkMShhcmMpOwogICAgICAgICAgICB2YXIgaW50ZXJzZWN0aW9uID0gY2FydGVzaWFuQ3Jvc3MkMShub3JtYWwsIGFyYyk7CiAgICAgICAgICAgIGNhcnRlc2lhbk5vcm1hbGl6ZUluUGxhY2UkMShpbnRlcnNlY3Rpb24pOwogICAgICAgICAgICB2YXIgcGhpQXJjID0gKGFudGltZXJpZGlhbiBeIGRlbHRhID49IDAgPyAtMSA6IDEpICogYXNpbiQyKGludGVyc2VjdGlvblsyXSk7CiAgICAgICAgICAgIGlmIChwaGkgPiBwaGlBcmMgfHwgcGhpID09PSBwaGlBcmMgJiYgKGFyY1swXSB8fCBhcmNbMV0pKSB7CiAgICAgICAgICAgICAgd2luZGluZyArPSBhbnRpbWVyaWRpYW4gXiBkZWx0YSA+PSAwID8gMSA6IC0xOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBGaXJzdCwgZGV0ZXJtaW5lIHdoZXRoZXIgdGhlIFNvdXRoIHBvbGUgaXMgaW5zaWRlIG9yIG91dHNpZGU6CiAgICAgIC8vCiAgICAgIC8vIEl0IGlzIGluc2lkZSBpZjoKICAgICAgLy8gKiB0aGUgcG9seWdvbiB3aW5kcyBhcm91bmQgaXQgaW4gYSBjbG9ja3dpc2UgZGlyZWN0aW9uLgogICAgICAvLyAqIHRoZSBwb2x5Z29uIGRvZXMgbm90IChjdW11bGF0aXZlbHkpIHdpbmQgYXJvdW5kIGl0LCBidXQgaGFzIGEgbmVnYXRpdmUKICAgICAgLy8gICAoY291bnRlci1jbG9ja3dpc2UpIGFyZWEuCiAgICAgIC8vCiAgICAgIC8vIFNlY29uZCwgY291bnQgdGhlIChzaWduZWQpIG51bWJlciBvZiB0aW1lcyBhIHNlZ21lbnQgY3Jvc3NlcyBhIGxhbWJkYQogICAgICAvLyBmcm9tIHRoZSBwb2ludCB0byB0aGUgU291dGggcG9sZS4gIElmIGl0IGlzIHplcm8sIHRoZW4gdGhlIHBvaW50IGlzIHRoZQogICAgICAvLyBzYW1lIHNpZGUgYXMgdGhlIFNvdXRoIHBvbGUuCgogICAgICByZXR1cm4gKGFuZ2xlIDwgLWVwc2lsb24kNyB8fCBhbmdsZSA8IGVwc2lsb24kNyAmJiBzdW0kNCA8IC1lcHNpbG9uJDcpIF4gKHdpbmRpbmcgJiAxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc2NlbmRpbmckOChhLCBiKSB7CiAgICAgIHJldHVybiBhIDwgYiA/IC0xIDogYSA+IGIgPyAxIDogYSA+PSBiID8gMCA6IE5hTjsKICAgIH0KCiAgICBmdW5jdGlvbiBiaXNlY3RvciQzKGNvbXBhcmUpIHsKICAgICAgaWYgKGNvbXBhcmUubGVuZ3RoID09PSAxKSBjb21wYXJlID0gYXNjZW5kaW5nQ29tcGFyYXRvciQzKGNvbXBhcmUpOwogICAgICByZXR1cm4gewogICAgICAgIGxlZnQ6IGZ1bmN0aW9uKGEsIHgsIGxvLCBoaSkgewogICAgICAgICAgaWYgKGxvID09IG51bGwpIGxvID0gMDsKICAgICAgICAgIGlmIChoaSA9PSBudWxsKSBoaSA9IGEubGVuZ3RoOwogICAgICAgICAgd2hpbGUgKGxvIDwgaGkpIHsKICAgICAgICAgICAgdmFyIG1pZCA9IGxvICsgaGkgPj4+IDE7CiAgICAgICAgICAgIGlmIChjb21wYXJlKGFbbWlkXSwgeCkgPCAwKSBsbyA9IG1pZCArIDE7CiAgICAgICAgICAgIGVsc2UgaGkgPSBtaWQ7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbG87CiAgICAgICAgfSwKICAgICAgICByaWdodDogZnVuY3Rpb24oYSwgeCwgbG8sIGhpKSB7CiAgICAgICAgICBpZiAobG8gPT0gbnVsbCkgbG8gPSAwOwogICAgICAgICAgaWYgKGhpID09IG51bGwpIGhpID0gYS5sZW5ndGg7CiAgICAgICAgICB3aGlsZSAobG8gPCBoaSkgewogICAgICAgICAgICB2YXIgbWlkID0gbG8gKyBoaSA+Pj4gMTsKICAgICAgICAgICAgaWYgKGNvbXBhcmUoYVttaWRdLCB4KSA+IDApIGhpID0gbWlkOwogICAgICAgICAgICBlbHNlIGxvID0gbWlkICsgMTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiBsbzsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nQ29tcGFyYXRvciQzKGYpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGQsIHgpIHsKICAgICAgICByZXR1cm4gYXNjZW5kaW5nJDgoZihkKSwgeCk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGFzY2VuZGluZ0Jpc2VjdCQzID0gYmlzZWN0b3IkMyhhc2NlbmRpbmckOCk7CgogICAgZnVuY3Rpb24gcmFuZ2UkNChzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICBzdGFydCA9ICtzdGFydCwgc3RvcCA9ICtzdG9wLCBzdGVwID0gKG4gPSBhcmd1bWVudHMubGVuZ3RoKSA8IDIgPyAoc3RvcCA9IHN0YXJ0LCBzdGFydCA9IDAsIDEpIDogbiA8IDMgPyAxIDogK3N0ZXA7CgogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IE1hdGgubWF4KDAsIE1hdGguY2VpbCgoc3RvcCAtIHN0YXJ0KSAvIHN0ZXApKSB8IDAsCiAgICAgICAgICByYW5nZSA9IG5ldyBBcnJheShuKTsKCiAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgcmFuZ2VbaV0gPSBzdGFydCArIGkgKiBzdGVwOwogICAgICB9CgogICAgICByZXR1cm4gcmFuZ2U7CiAgICB9CgogICAgZnVuY3Rpb24gbWVyZ2UkMihhcnJheXMpIHsKICAgICAgdmFyIG4gPSBhcnJheXMubGVuZ3RoLAogICAgICAgICAgbSwKICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgIGogPSAwLAogICAgICAgICAgbWVyZ2VkLAogICAgICAgICAgYXJyYXk7CgogICAgICB3aGlsZSAoKytpIDwgbikgaiArPSBhcnJheXNbaV0ubGVuZ3RoOwogICAgICBtZXJnZWQgPSBuZXcgQXJyYXkoaik7CgogICAgICB3aGlsZSAoLS1uID49IDApIHsKICAgICAgICBhcnJheSA9IGFycmF5c1tuXTsKICAgICAgICBtID0gYXJyYXkubGVuZ3RoOwogICAgICAgIHdoaWxlICgtLW0gPj0gMCkgewogICAgICAgICAgbWVyZ2VkWy0tal0gPSBhcnJheVttXTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBtZXJnZWQ7CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcCQxKHBvaW50VmlzaWJsZSwgY2xpcExpbmUsIGludGVycG9sYXRlLCBzdGFydCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oc2luaykgewogICAgICAgIHZhciBsaW5lID0gY2xpcExpbmUoc2luayksCiAgICAgICAgICAgIHJpbmdCdWZmZXIgPSBjbGlwQnVmZmVyJDEoKSwKICAgICAgICAgICAgcmluZ1NpbmsgPSBjbGlwTGluZShyaW5nQnVmZmVyKSwKICAgICAgICAgICAgcG9seWdvblN0YXJ0ZWQgPSBmYWxzZSwKICAgICAgICAgICAgcG9seWdvbiwKICAgICAgICAgICAgc2VnbWVudHMsCiAgICAgICAgICAgIHJpbmc7CgogICAgICAgIHZhciBjbGlwID0gewogICAgICAgICAgcG9pbnQ6IHBvaW50LAogICAgICAgICAgbGluZVN0YXJ0OiBsaW5lU3RhcnQsCiAgICAgICAgICBsaW5lRW5kOiBsaW5lRW5kLAogICAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50UmluZzsKICAgICAgICAgICAgY2xpcC5saW5lU3RhcnQgPSByaW5nU3RhcnQ7CiAgICAgICAgICAgIGNsaXAubGluZUVuZCA9IHJpbmdFbmQ7CiAgICAgICAgICAgIHNlZ21lbnRzID0gW107CiAgICAgICAgICAgIHBvbHlnb24gPSBbXTsKICAgICAgICAgIH0sCiAgICAgICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50OwogICAgICAgICAgICBjbGlwLmxpbmVTdGFydCA9IGxpbmVTdGFydDsKICAgICAgICAgICAgY2xpcC5saW5lRW5kID0gbGluZUVuZDsKICAgICAgICAgICAgc2VnbWVudHMgPSBtZXJnZSQyKHNlZ21lbnRzKTsKICAgICAgICAgICAgdmFyIHN0YXJ0SW5zaWRlID0gcG9seWdvbkNvbnRhaW5zJDEocG9seWdvbiwgc3RhcnQpOwogICAgICAgICAgICBpZiAoc2VnbWVudHMubGVuZ3RoKSB7CiAgICAgICAgICAgICAgaWYgKCFwb2x5Z29uU3RhcnRlZCkgc2luay5wb2x5Z29uU3RhcnQoKSwgcG9seWdvblN0YXJ0ZWQgPSB0cnVlOwogICAgICAgICAgICAgIGNsaXBSZWpvaW4kMShzZWdtZW50cywgY29tcGFyZUludGVyc2VjdGlvbiQxLCBzdGFydEluc2lkZSwgaW50ZXJwb2xhdGUsIHNpbmspOwogICAgICAgICAgICB9IGVsc2UgaWYgKHN0YXJ0SW5zaWRlKSB7CiAgICAgICAgICAgICAgaWYgKCFwb2x5Z29uU3RhcnRlZCkgc2luay5wb2x5Z29uU3RhcnQoKSwgcG9seWdvblN0YXJ0ZWQgPSB0cnVlOwogICAgICAgICAgICAgIHNpbmsubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgaW50ZXJwb2xhdGUobnVsbCwgbnVsbCwgMSwgc2luayk7CiAgICAgICAgICAgICAgc2luay5saW5lRW5kKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHBvbHlnb25TdGFydGVkKSBzaW5rLnBvbHlnb25FbmQoKSwgcG9seWdvblN0YXJ0ZWQgPSBmYWxzZTsKICAgICAgICAgICAgc2VnbWVudHMgPSBwb2x5Z29uID0gbnVsbDsKICAgICAgICAgIH0sCiAgICAgICAgICBzcGhlcmU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBzaW5rLnBvbHlnb25TdGFydCgpOwogICAgICAgICAgICBzaW5rLmxpbmVTdGFydCgpOwogICAgICAgICAgICBpbnRlcnBvbGF0ZShudWxsLCBudWxsLCAxLCBzaW5rKTsKICAgICAgICAgICAgc2luay5saW5lRW5kKCk7CiAgICAgICAgICAgIHNpbmsucG9seWdvbkVuZCgpOwogICAgICAgICAgfQogICAgICAgIH07CgogICAgICAgIGZ1bmN0aW9uIHBvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICBpZiAocG9pbnRWaXNpYmxlKGxhbWJkYSwgcGhpKSkgc2luay5wb2ludChsYW1iZGEsIHBoaSk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBwb2ludExpbmUobGFtYmRhLCBwaGkpIHsKICAgICAgICAgIGxpbmUucG9pbnQobGFtYmRhLCBwaGkpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbGluZVN0YXJ0KCkgewogICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50TGluZTsKICAgICAgICAgIGxpbmUubGluZVN0YXJ0KCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBsaW5lRW5kKCkgewogICAgICAgICAgY2xpcC5wb2ludCA9IHBvaW50OwogICAgICAgICAgbGluZS5saW5lRW5kKCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBwb2ludFJpbmcobGFtYmRhLCBwaGkpIHsKICAgICAgICAgIHJpbmcucHVzaChbbGFtYmRhLCBwaGldKTsKICAgICAgICAgIHJpbmdTaW5rLnBvaW50KGxhbWJkYSwgcGhpKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHJpbmdTdGFydCgpIHsKICAgICAgICAgIHJpbmdTaW5rLmxpbmVTdGFydCgpOwogICAgICAgICAgcmluZyA9IFtdOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcmluZ0VuZCgpIHsKICAgICAgICAgIHBvaW50UmluZyhyaW5nWzBdWzBdLCByaW5nWzBdWzFdKTsKICAgICAgICAgIHJpbmdTaW5rLmxpbmVFbmQoKTsKCiAgICAgICAgICB2YXIgY2xlYW4gPSByaW5nU2luay5jbGVhbigpLAogICAgICAgICAgICAgIHJpbmdTZWdtZW50cyA9IHJpbmdCdWZmZXIucmVzdWx0KCksCiAgICAgICAgICAgICAgaSwgbiA9IHJpbmdTZWdtZW50cy5sZW5ndGgsIG0sCiAgICAgICAgICAgICAgc2VnbWVudCwKICAgICAgICAgICAgICBwb2ludDsKCiAgICAgICAgICByaW5nLnBvcCgpOwogICAgICAgICAgcG9seWdvbi5wdXNoKHJpbmcpOwogICAgICAgICAgcmluZyA9IG51bGw7CgogICAgICAgICAgaWYgKCFuKSByZXR1cm47CgogICAgICAgICAgLy8gTm8gaW50ZXJzZWN0aW9ucy4KICAgICAgICAgIGlmIChjbGVhbiAmIDEpIHsKICAgICAgICAgICAgc2VnbWVudCA9IHJpbmdTZWdtZW50c1swXTsKICAgICAgICAgICAgaWYgKChtID0gc2VnbWVudC5sZW5ndGggLSAxKSA+IDApIHsKICAgICAgICAgICAgICBpZiAoIXBvbHlnb25TdGFydGVkKSBzaW5rLnBvbHlnb25TdGFydCgpLCBwb2x5Z29uU3RhcnRlZCA9IHRydWU7CiAgICAgICAgICAgICAgc2luay5saW5lU3RhcnQoKTsKICAgICAgICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbTsgKytpKSBzaW5rLnBvaW50KChwb2ludCA9IHNlZ21lbnRbaV0pWzBdLCBwb2ludFsxXSk7CiAgICAgICAgICAgICAgc2luay5saW5lRW5kKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIFJlam9pbiBjb25uZWN0ZWQgc2VnbWVudHMuCiAgICAgICAgICAvLyBUT0RPIHJldXNlIHJpbmdCdWZmZXIucmVqb2luKCk/CiAgICAgICAgICBpZiAobiA+IDEgJiYgY2xlYW4gJiAyKSByaW5nU2VnbWVudHMucHVzaChyaW5nU2VnbWVudHMucG9wKCkuY29uY2F0KHJpbmdTZWdtZW50cy5zaGlmdCgpKSk7CgogICAgICAgICAgc2VnbWVudHMucHVzaChyaW5nU2VnbWVudHMuZmlsdGVyKHZhbGlkU2VnbWVudCQxKSk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gY2xpcDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB2YWxpZFNlZ21lbnQkMShzZWdtZW50KSB7CiAgICAgIHJldHVybiBzZWdtZW50Lmxlbmd0aCA+IDE7CiAgICB9CgogICAgLy8gSW50ZXJzZWN0aW9ucyBhcmUgc29ydGVkIGFsb25nIHRoZSBjbGlwIGVkZ2UuIEZvciBib3RoIGFudGltZXJpZGlhbiBjdXR0aW5nCiAgICAvLyBhbmQgY2lyY2xlIGNsaXBwaW5nLCB0aGUgc2FtZSBjb21wYXJpc29uIGlzIHVzZWQuCiAgICBmdW5jdGlvbiBjb21wYXJlSW50ZXJzZWN0aW9uJDEoYSwgYikgewogICAgICByZXR1cm4gKChhID0gYS54KVswXSA8IDAgPyBhWzFdIC0gaGFsZlBpJDYgLSBlcHNpbG9uJDcgOiBoYWxmUGkkNiAtIGFbMV0pCiAgICAgICAgICAgLSAoKGIgPSBiLngpWzBdIDwgMCA/IGJbMV0gLSBoYWxmUGkkNiAtIGVwc2lsb24kNyA6IGhhbGZQaSQ2IC0gYlsxXSk7CiAgICB9CgogICAgdmFyIGNsaXBBbnRpbWVyaWRpYW4kMSA9IGNsaXAkMSgKICAgICAgZnVuY3Rpb24oKSB7IHJldHVybiB0cnVlOyB9LAogICAgICBjbGlwQW50aW1lcmlkaWFuTGluZSQxLAogICAgICBjbGlwQW50aW1lcmlkaWFuSW50ZXJwb2xhdGUkMSwKICAgICAgWy1waSQ4LCAtaGFsZlBpJDZdCiAgICApOwoKICAgIC8vIFRha2VzIGEgbGluZSBhbmQgY3V0cyBpbnRvIHZpc2libGUgc2VnbWVudHMuIFJldHVybiB2YWx1ZXM6IDAgLSB0aGVyZSB3ZXJlCiAgICAvLyBpbnRlcnNlY3Rpb25zIG9yIHRoZSBsaW5lIHdhcyBlbXB0eTsgMSAtIG5vIGludGVyc2VjdGlvbnM7IDIgLSB0aGVyZSB3ZXJlCiAgICAvLyBpbnRlcnNlY3Rpb25zLCBhbmQgdGhlIGZpcnN0IGFuZCBsYXN0IHNlZ21lbnRzIHNob3VsZCBiZSByZWpvaW5lZC4KICAgIGZ1bmN0aW9uIGNsaXBBbnRpbWVyaWRpYW5MaW5lJDEoc3RyZWFtKSB7CiAgICAgIHZhciBsYW1iZGEwID0gTmFOLAogICAgICAgICAgcGhpMCA9IE5hTiwKICAgICAgICAgIHNpZ24wID0gTmFOLAogICAgICAgICAgY2xlYW47IC8vIG5vIGludGVyc2VjdGlvbnMKCiAgICAgIHJldHVybiB7CiAgICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgICAgIGNsZWFuID0gMTsKICAgICAgICB9LAogICAgICAgIHBvaW50OiBmdW5jdGlvbihsYW1iZGExLCBwaGkxKSB7CiAgICAgICAgICB2YXIgc2lnbjEgPSBsYW1iZGExID4gMCA/IHBpJDggOiAtcGkkOCwKICAgICAgICAgICAgICBkZWx0YSA9IGFicyQyKGxhbWJkYTEgLSBsYW1iZGEwKTsKICAgICAgICAgIGlmIChhYnMkMihkZWx0YSAtIHBpJDgpIDwgZXBzaWxvbiQ3KSB7IC8vIGxpbmUgY3Jvc3NlcyBhIHBvbGUKICAgICAgICAgICAgc3RyZWFtLnBvaW50KGxhbWJkYTAsIHBoaTAgPSAocGhpMCArIHBoaTEpIC8gMiA+IDAgPyBoYWxmUGkkNiA6IC1oYWxmUGkkNik7CiAgICAgICAgICAgIHN0cmVhbS5wb2ludChzaWduMCwgcGhpMCk7CiAgICAgICAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHNpZ24xLCBwaGkwKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KGxhbWJkYTEsIHBoaTApOwogICAgICAgICAgICBjbGVhbiA9IDA7CiAgICAgICAgICB9IGVsc2UgaWYgKHNpZ24wICE9PSBzaWduMSAmJiBkZWx0YSA+PSBwaSQ4KSB7IC8vIGxpbmUgY3Jvc3NlcyBhbnRpbWVyaWRpYW4KICAgICAgICAgICAgaWYgKGFicyQyKGxhbWJkYTAgLSBzaWduMCkgPCBlcHNpbG9uJDcpIGxhbWJkYTAgLT0gc2lnbjAgKiBlcHNpbG9uJDc7IC8vIGhhbmRsZSBkZWdlbmVyYWNpZXMKICAgICAgICAgICAgaWYgKGFicyQyKGxhbWJkYTEgLSBzaWduMSkgPCBlcHNpbG9uJDcpIGxhbWJkYTEgLT0gc2lnbjEgKiBlcHNpbG9uJDc7CiAgICAgICAgICAgIHBoaTAgPSBjbGlwQW50aW1lcmlkaWFuSW50ZXJzZWN0JDEobGFtYmRhMCwgcGhpMCwgbGFtYmRhMSwgcGhpMSk7CiAgICAgICAgICAgIHN0cmVhbS5wb2ludChzaWduMCwgcGhpMCk7CiAgICAgICAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICAgIHN0cmVhbS5saW5lU3RhcnQoKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHNpZ24xLCBwaGkwKTsKICAgICAgICAgICAgY2xlYW4gPSAwOwogICAgICAgICAgfQogICAgICAgICAgc3RyZWFtLnBvaW50KGxhbWJkYTAgPSBsYW1iZGExLCBwaGkwID0gcGhpMSk7CiAgICAgICAgICBzaWduMCA9IHNpZ24xOwogICAgICAgIH0sCiAgICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICAgICAgbGFtYmRhMCA9IHBoaTAgPSBOYU47CiAgICAgICAgfSwKICAgICAgICBjbGVhbjogZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gMiAtIGNsZWFuOyAvLyBpZiBpbnRlcnNlY3Rpb25zLCByZWpvaW4gZmlyc3QgYW5kIGxhc3Qgc2VnbWVudHMKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcEFudGltZXJpZGlhbkludGVyc2VjdCQxKGxhbWJkYTAsIHBoaTAsIGxhbWJkYTEsIHBoaTEpIHsKICAgICAgdmFyIGNvc1BoaTAsCiAgICAgICAgICBjb3NQaGkxLAogICAgICAgICAgc2luTGFtYmRhMExhbWJkYTEgPSBzaW4kNChsYW1iZGEwIC0gbGFtYmRhMSk7CiAgICAgIHJldHVybiBhYnMkMihzaW5MYW1iZGEwTGFtYmRhMSkgPiBlcHNpbG9uJDcKICAgICAgICAgID8gYXRhbiQxKChzaW4kNChwaGkwKSAqIChjb3NQaGkxID0gY29zJDQocGhpMSkpICogc2luJDQobGFtYmRhMSkKICAgICAgICAgICAgICAtIHNpbiQ0KHBoaTEpICogKGNvc1BoaTAgPSBjb3MkNChwaGkwKSkgKiBzaW4kNChsYW1iZGEwKSkKICAgICAgICAgICAgICAvIChjb3NQaGkwICogY29zUGhpMSAqIHNpbkxhbWJkYTBMYW1iZGExKSkKICAgICAgICAgIDogKHBoaTAgKyBwaGkxKSAvIDI7CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcEFudGltZXJpZGlhbkludGVycG9sYXRlJDEoZnJvbSwgdG8sIGRpcmVjdGlvbiwgc3RyZWFtKSB7CiAgICAgIHZhciBwaGk7CiAgICAgIGlmIChmcm9tID09IG51bGwpIHsKICAgICAgICBwaGkgPSBkaXJlY3Rpb24gKiBoYWxmUGkkNjsKICAgICAgICBzdHJlYW0ucG9pbnQoLXBpJDgsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KDAsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KHBpJDgsIHBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KHBpJDgsIDApOwogICAgICAgIHN0cmVhbS5wb2ludChwaSQ4LCAtcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQoMCwgLXBoaSk7CiAgICAgICAgc3RyZWFtLnBvaW50KC1waSQ4LCAtcGhpKTsKICAgICAgICBzdHJlYW0ucG9pbnQoLXBpJDgsIDApOwogICAgICAgIHN0cmVhbS5wb2ludCgtcGkkOCwgcGhpKTsKICAgICAgfSBlbHNlIGlmIChhYnMkMihmcm9tWzBdIC0gdG9bMF0pID4gZXBzaWxvbiQ3KSB7CiAgICAgICAgdmFyIGxhbWJkYSA9IGZyb21bMF0gPCB0b1swXSA/IHBpJDggOiAtcGkkODsKICAgICAgICBwaGkgPSBkaXJlY3Rpb24gKiBsYW1iZGEgLyAyOwogICAgICAgIHN0cmVhbS5wb2ludCgtbGFtYmRhLCBwaGkpOwogICAgICAgIHN0cmVhbS5wb2ludCgwLCBwaGkpOwogICAgICAgIHN0cmVhbS5wb2ludChsYW1iZGEsIHBoaSk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgc3RyZWFtLnBvaW50KHRvWzBdLCB0b1sxXSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwQ2lyY2xlJDEocmFkaXVzKSB7CiAgICAgIHZhciBjciA9IGNvcyQ0KHJhZGl1cyksCiAgICAgICAgICBkZWx0YSA9IDYgKiByYWRpYW5zJDEsCiAgICAgICAgICBzbWFsbFJhZGl1cyA9IGNyID4gMCwKICAgICAgICAgIG5vdEhlbWlzcGhlcmUgPSBhYnMkMihjcikgPiBlcHNpbG9uJDc7IC8vIFRPRE8gb3B0aW1pc2UgZm9yIHRoaXMgY29tbW9uIGNhc2UKCiAgICAgIGZ1bmN0aW9uIGludGVycG9sYXRlKGZyb20sIHRvLCBkaXJlY3Rpb24sIHN0cmVhbSkgewogICAgICAgIGNpcmNsZVN0cmVhbSQxKHN0cmVhbSwgcmFkaXVzLCBkZWx0YSwgZGlyZWN0aW9uLCBmcm9tLCB0byk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHZpc2libGUobGFtYmRhLCBwaGkpIHsKICAgICAgICByZXR1cm4gY29zJDQobGFtYmRhKSAqIGNvcyQ0KHBoaSkgPiBjcjsKICAgICAgfQoKICAgICAgLy8gVGFrZXMgYSBsaW5lIGFuZCBjdXRzIGludG8gdmlzaWJsZSBzZWdtZW50cy4gUmV0dXJuIHZhbHVlcyB1c2VkIGZvciBwb2x5Z29uCiAgICAgIC8vIGNsaXBwaW5nOiAwIC0gdGhlcmUgd2VyZSBpbnRlcnNlY3Rpb25zIG9yIHRoZSBsaW5lIHdhcyBlbXB0eTsgMSAtIG5vCiAgICAgIC8vIGludGVyc2VjdGlvbnMgMiAtIHRoZXJlIHdlcmUgaW50ZXJzZWN0aW9ucywgYW5kIHRoZSBmaXJzdCBhbmQgbGFzdCBzZWdtZW50cwogICAgICAvLyBzaG91bGQgYmUgcmVqb2luZWQuCiAgICAgIGZ1bmN0aW9uIGNsaXBMaW5lKHN0cmVhbSkgewogICAgICAgIHZhciBwb2ludDAsIC8vIHByZXZpb3VzIHBvaW50CiAgICAgICAgICAgIGMwLCAvLyBjb2RlIGZvciBwcmV2aW91cyBwb2ludAogICAgICAgICAgICB2MCwgLy8gdmlzaWJpbGl0eSBvZiBwcmV2aW91cyBwb2ludAogICAgICAgICAgICB2MDAsIC8vIHZpc2liaWxpdHkgb2YgZmlyc3QgcG9pbnQKICAgICAgICAgICAgY2xlYW47IC8vIG5vIGludGVyc2VjdGlvbnMKICAgICAgICByZXR1cm4gewogICAgICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgdjAwID0gdjAgPSBmYWxzZTsKICAgICAgICAgICAgY2xlYW4gPSAxOwogICAgICAgICAgfSwKICAgICAgICAgIHBvaW50OiBmdW5jdGlvbihsYW1iZGEsIHBoaSkgewogICAgICAgICAgICB2YXIgcG9pbnQxID0gW2xhbWJkYSwgcGhpXSwKICAgICAgICAgICAgICAgIHBvaW50MiwKICAgICAgICAgICAgICAgIHYgPSB2aXNpYmxlKGxhbWJkYSwgcGhpKSwKICAgICAgICAgICAgICAgIGMgPSBzbWFsbFJhZGl1cwogICAgICAgICAgICAgICAgICA/IHYgPyAwIDogY29kZShsYW1iZGEsIHBoaSkKICAgICAgICAgICAgICAgICAgOiB2ID8gY29kZShsYW1iZGEgKyAobGFtYmRhIDwgMCA/IHBpJDggOiAtcGkkOCksIHBoaSkgOiAwOwogICAgICAgICAgICBpZiAoIXBvaW50MCAmJiAodjAwID0gdjAgPSB2KSkgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAvLyBIYW5kbGUgZGVnZW5lcmFjaWVzLgogICAgICAgICAgICAvLyBUT0RPIGlnbm9yZSBpZiBub3QgY2xpcHBpbmcgcG9seWdvbnMuCiAgICAgICAgICAgIGlmICh2ICE9PSB2MCkgewogICAgICAgICAgICAgIHBvaW50MiA9IGludGVyc2VjdChwb2ludDAsIHBvaW50MSk7CiAgICAgICAgICAgICAgaWYgKCFwb2ludDIgfHwgcG9pbnRFcXVhbCQxKHBvaW50MCwgcG9pbnQyKSB8fCBwb2ludEVxdWFsJDEocG9pbnQxLCBwb2ludDIpKSB7CiAgICAgICAgICAgICAgICBwb2ludDFbMF0gKz0gZXBzaWxvbiQ3OwogICAgICAgICAgICAgICAgcG9pbnQxWzFdICs9IGVwc2lsb24kNzsKICAgICAgICAgICAgICAgIHYgPSB2aXNpYmxlKHBvaW50MVswXSwgcG9pbnQxWzFdKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHYgIT09IHYwKSB7CiAgICAgICAgICAgICAgY2xlYW4gPSAwOwogICAgICAgICAgICAgIGlmICh2KSB7CiAgICAgICAgICAgICAgICAvLyBvdXRzaWRlIGdvaW5nIGluCiAgICAgICAgICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgICBwb2ludDIgPSBpbnRlcnNlY3QocG9pbnQxLCBwb2ludDApOwogICAgICAgICAgICAgICAgc3RyZWFtLnBvaW50KHBvaW50MlswXSwgcG9pbnQyWzFdKTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgLy8gaW5zaWRlIGdvaW5nIG91dAogICAgICAgICAgICAgICAgcG9pbnQyID0gaW50ZXJzZWN0KHBvaW50MCwgcG9pbnQxKTsKICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludChwb2ludDJbMF0sIHBvaW50MlsxXSk7CiAgICAgICAgICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBwb2ludDAgPSBwb2ludDI7CiAgICAgICAgICAgIH0gZWxzZSBpZiAobm90SGVtaXNwaGVyZSAmJiBwb2ludDAgJiYgc21hbGxSYWRpdXMgXiB2KSB7CiAgICAgICAgICAgICAgdmFyIHQ7CiAgICAgICAgICAgICAgLy8gSWYgdGhlIGNvZGVzIGZvciB0d28gcG9pbnRzIGFyZSBkaWZmZXJlbnQsIG9yIGFyZSBib3RoIHplcm8sCiAgICAgICAgICAgICAgLy8gYW5kIHRoZXJlIHRoaXMgc2VnbWVudCBpbnRlcnNlY3RzIHdpdGggdGhlIHNtYWxsIGNpcmNsZS4KICAgICAgICAgICAgICBpZiAoIShjICYgYzApICYmICh0ID0gaW50ZXJzZWN0KHBvaW50MSwgcG9pbnQwLCB0cnVlKSkpIHsKICAgICAgICAgICAgICAgIGNsZWFuID0gMDsKICAgICAgICAgICAgICAgIGlmIChzbWFsbFJhZGl1cykgewogICAgICAgICAgICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludCh0WzBdWzBdLCB0WzBdWzFdKTsKICAgICAgICAgICAgICAgICAgc3RyZWFtLnBvaW50KHRbMV1bMF0sIHRbMV1bMV0pOwogICAgICAgICAgICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICAgICAgc3RyZWFtLnBvaW50KHRbMV1bMF0sIHRbMV1bMV0pOwogICAgICAgICAgICAgICAgICBzdHJlYW0ubGluZUVuZCgpOwogICAgICAgICAgICAgICAgICBzdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgICAgIHN0cmVhbS5wb2ludCh0WzBdWzBdLCB0WzBdWzFdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHYgJiYgKCFwb2ludDAgfHwgIXBvaW50RXF1YWwkMShwb2ludDAsIHBvaW50MSkpKSB7CiAgICAgICAgICAgICAgc3RyZWFtLnBvaW50KHBvaW50MVswXSwgcG9pbnQxWzFdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBwb2ludDAgPSBwb2ludDEsIHYwID0gdiwgYzAgPSBjOwogICAgICAgICAgfSwKICAgICAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICBpZiAodjApIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgICAgIHBvaW50MCA9IG51bGw7CiAgICAgICAgICB9LAogICAgICAgICAgLy8gUmVqb2luIGZpcnN0IGFuZCBsYXN0IHNlZ21lbnRzIGlmIHRoZXJlIHdlcmUgaW50ZXJzZWN0aW9ucyBhbmQgdGhlIGZpcnN0CiAgICAgICAgICAvLyBhbmQgbGFzdCBwb2ludHMgd2VyZSB2aXNpYmxlLgogICAgICAgICAgY2xlYW46IGZ1bmN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gY2xlYW4gfCAoKHYwMCAmJiB2MCkgPDwgMSk7CiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLy8gSW50ZXJzZWN0cyB0aGUgZ3JlYXQgY2lyY2xlIGJldHdlZW4gYSBhbmQgYiB3aXRoIHRoZSBjbGlwIGNpcmNsZS4KICAgICAgZnVuY3Rpb24gaW50ZXJzZWN0KGEsIGIsIHR3bykgewogICAgICAgIHZhciBwYSA9IGNhcnRlc2lhbiQxKGEpLAogICAgICAgICAgICBwYiA9IGNhcnRlc2lhbiQxKGIpOwoKICAgICAgICAvLyBXZSBoYXZlIHR3byBwbGFuZXMsIG4xLnAgPSBkMSBhbmQgbjIucCA9IGQyLgogICAgICAgIC8vIEZpbmQgaW50ZXJzZWN0aW9uIGxpbmUgcCh0KSA9IGMxIG4xICsgYzIgbjIgKyB0IChuMSDiqK8gbjIpLgogICAgICAgIHZhciBuMSA9IFsxLCAwLCAwXSwgLy8gbm9ybWFsCiAgICAgICAgICAgIG4yID0gY2FydGVzaWFuQ3Jvc3MkMShwYSwgcGIpLAogICAgICAgICAgICBuMm4yID0gY2FydGVzaWFuRG90JDEobjIsIG4yKSwKICAgICAgICAgICAgbjFuMiA9IG4yWzBdLCAvLyBjYXJ0ZXNpYW5Eb3QobjEsIG4yKSwKICAgICAgICAgICAgZGV0ZXJtaW5hbnQgPSBuMm4yIC0gbjFuMiAqIG4xbjI7CgogICAgICAgIC8vIFR3byBwb2xhciBwb2ludHMuCiAgICAgICAgaWYgKCFkZXRlcm1pbmFudCkgcmV0dXJuICF0d28gJiYgYTsKCiAgICAgICAgdmFyIGMxID0gIGNyICogbjJuMiAvIGRldGVybWluYW50LAogICAgICAgICAgICBjMiA9IC1jciAqIG4xbjIgLyBkZXRlcm1pbmFudCwKICAgICAgICAgICAgbjF4bjIgPSBjYXJ0ZXNpYW5Dcm9zcyQxKG4xLCBuMiksCiAgICAgICAgICAgIEEgPSBjYXJ0ZXNpYW5TY2FsZSQxKG4xLCBjMSksCiAgICAgICAgICAgIEIgPSBjYXJ0ZXNpYW5TY2FsZSQxKG4yLCBjMik7CiAgICAgICAgY2FydGVzaWFuQWRkSW5QbGFjZSQxKEEsIEIpOwoKICAgICAgICAvLyBTb2x2ZSB8cCh0KXxeMiA9IDEuCiAgICAgICAgdmFyIHUgPSBuMXhuMiwKICAgICAgICAgICAgdyA9IGNhcnRlc2lhbkRvdCQxKEEsIHUpLAogICAgICAgICAgICB1dSA9IGNhcnRlc2lhbkRvdCQxKHUsIHUpLAogICAgICAgICAgICB0MiA9IHcgKiB3IC0gdXUgKiAoY2FydGVzaWFuRG90JDEoQSwgQSkgLSAxKTsKCiAgICAgICAgaWYgKHQyIDwgMCkgcmV0dXJuOwoKICAgICAgICB2YXIgdCA9IHNxcnQkMyh0MiksCiAgICAgICAgICAgIHEgPSBjYXJ0ZXNpYW5TY2FsZSQxKHUsICgtdyAtIHQpIC8gdXUpOwogICAgICAgIGNhcnRlc2lhbkFkZEluUGxhY2UkMShxLCBBKTsKICAgICAgICBxID0gc3BoZXJpY2FsJDEocSk7CgogICAgICAgIGlmICghdHdvKSByZXR1cm4gcTsKCiAgICAgICAgLy8gVHdvIGludGVyc2VjdGlvbiBwb2ludHMuCiAgICAgICAgdmFyIGxhbWJkYTAgPSBhWzBdLAogICAgICAgICAgICBsYW1iZGExID0gYlswXSwKICAgICAgICAgICAgcGhpMCA9IGFbMV0sCiAgICAgICAgICAgIHBoaTEgPSBiWzFdLAogICAgICAgICAgICB6OwoKICAgICAgICBpZiAobGFtYmRhMSA8IGxhbWJkYTApIHogPSBsYW1iZGEwLCBsYW1iZGEwID0gbGFtYmRhMSwgbGFtYmRhMSA9IHo7CgogICAgICAgIHZhciBkZWx0YSA9IGxhbWJkYTEgLSBsYW1iZGEwLAogICAgICAgICAgICBwb2xhciA9IGFicyQyKGRlbHRhIC0gcGkkOCkgPCBlcHNpbG9uJDcsCiAgICAgICAgICAgIG1lcmlkaWFuID0gcG9sYXIgfHwgZGVsdGEgPCBlcHNpbG9uJDc7CgogICAgICAgIGlmICghcG9sYXIgJiYgcGhpMSA8IHBoaTApIHogPSBwaGkwLCBwaGkwID0gcGhpMSwgcGhpMSA9IHo7CgogICAgICAgIC8vIENoZWNrIHRoYXQgdGhlIGZpcnN0IHBvaW50IGlzIGJldHdlZW4gYSBhbmQgYi4KICAgICAgICBpZiAobWVyaWRpYW4KICAgICAgICAgICAgPyBwb2xhcgogICAgICAgICAgICAgID8gcGhpMCArIHBoaTEgPiAwIF4gcVsxXSA8IChhYnMkMihxWzBdIC0gbGFtYmRhMCkgPCBlcHNpbG9uJDcgPyBwaGkwIDogcGhpMSkKICAgICAgICAgICAgICA6IHBoaTAgPD0gcVsxXSAmJiBxWzFdIDw9IHBoaTEKICAgICAgICAgICAgOiBkZWx0YSA+IHBpJDggXiAobGFtYmRhMCA8PSBxWzBdICYmIHFbMF0gPD0gbGFtYmRhMSkpIHsKICAgICAgICAgIHZhciBxMSA9IGNhcnRlc2lhblNjYWxlJDEodSwgKC13ICsgdCkgLyB1dSk7CiAgICAgICAgICBjYXJ0ZXNpYW5BZGRJblBsYWNlJDEocTEsIEEpOwogICAgICAgICAgcmV0dXJuIFtxLCBzcGhlcmljYWwkMShxMSldOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gR2VuZXJhdGVzIGEgNC1iaXQgdmVjdG9yIHJlcHJlc2VudGluZyB0aGUgbG9jYXRpb24gb2YgYSBwb2ludCByZWxhdGl2ZSB0bwogICAgICAvLyB0aGUgc21hbGwgY2lyY2xlJ3MgYm91bmRpbmcgYm94LgogICAgICBmdW5jdGlvbiBjb2RlKGxhbWJkYSwgcGhpKSB7CiAgICAgICAgdmFyIHIgPSBzbWFsbFJhZGl1cyA/IHJhZGl1cyA6IHBpJDggLSByYWRpdXMsCiAgICAgICAgICAgIGNvZGUgPSAwOwogICAgICAgIGlmIChsYW1iZGEgPCAtcikgY29kZSB8PSAxOyAvLyBsZWZ0CiAgICAgICAgZWxzZSBpZiAobGFtYmRhID4gcikgY29kZSB8PSAyOyAvLyByaWdodAogICAgICAgIGlmIChwaGkgPCAtcikgY29kZSB8PSA0OyAvLyBiZWxvdwogICAgICAgIGVsc2UgaWYgKHBoaSA+IHIpIGNvZGUgfD0gODsgLy8gYWJvdmUKICAgICAgICByZXR1cm4gY29kZTsKICAgICAgfQoKICAgICAgcmV0dXJuIGNsaXAkMSh2aXNpYmxlLCBjbGlwTGluZSwgaW50ZXJwb2xhdGUsIHNtYWxsUmFkaXVzID8gWzAsIC1yYWRpdXNdIDogWy1waSQ4LCByYWRpdXMgLSBwaSQ4XSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xpcExpbmUkMShhLCBiLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgYXggPSBhWzBdLAogICAgICAgICAgYXkgPSBhWzFdLAogICAgICAgICAgYnggPSBiWzBdLAogICAgICAgICAgYnkgPSBiWzFdLAogICAgICAgICAgdDAgPSAwLAogICAgICAgICAgdDEgPSAxLAogICAgICAgICAgZHggPSBieCAtIGF4LAogICAgICAgICAgZHkgPSBieSAtIGF5LAogICAgICAgICAgcjsKCiAgICAgIHIgPSB4MCAtIGF4OwogICAgICBpZiAoIWR4ICYmIHIgPiAwKSByZXR1cm47CiAgICAgIHIgLz0gZHg7CiAgICAgIGlmIChkeCA8IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9IGVsc2UgaWYgKGR4ID4gMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB4MSAtIGF4OwogICAgICBpZiAoIWR4ICYmIHIgPCAwKSByZXR1cm47CiAgICAgIHIgLz0gZHg7CiAgICAgIGlmIChkeCA8IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9IGVsc2UgaWYgKGR4ID4gMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB5MCAtIGF5OwogICAgICBpZiAoIWR5ICYmIHIgPiAwKSByZXR1cm47CiAgICAgIHIgLz0gZHk7CiAgICAgIGlmIChkeSA8IDApIHsKICAgICAgICBpZiAociA8IHQwKSByZXR1cm47CiAgICAgICAgaWYgKHIgPCB0MSkgdDEgPSByOwogICAgICB9IGVsc2UgaWYgKGR5ID4gMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0KCiAgICAgIHIgPSB5MSAtIGF5OwogICAgICBpZiAoIWR5ICYmIHIgPCAwKSByZXR1cm47CiAgICAgIHIgLz0gZHk7CiAgICAgIGlmIChkeSA8IDApIHsKICAgICAgICBpZiAociA+IHQxKSByZXR1cm47CiAgICAgICAgaWYgKHIgPiB0MCkgdDAgPSByOwogICAgICB9IGVsc2UgaWYgKGR5ID4gMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0KCiAgICAgIGlmICh0MCA+IDApIGFbMF0gPSBheCArIHQwICogZHgsIGFbMV0gPSBheSArIHQwICogZHk7CiAgICAgIGlmICh0MSA8IDEpIGJbMF0gPSBheCArIHQxICogZHgsIGJbMV0gPSBheSArIHQxICogZHk7CiAgICAgIHJldHVybiB0cnVlOwogICAgfQoKICAgIHZhciBjbGlwTWF4JDEgPSAxZTksIGNsaXBNaW4kMSA9IC1jbGlwTWF4JDE7CgogICAgLy8gVE9ETyBVc2UgZDMtcG9seWdvbuKAmXMgcG9seWdvbkNvbnRhaW5zIGhlcmUgZm9yIHRoZSByaW5nIGNoZWNrPwogICAgLy8gVE9ETyBFbGltaW5hdGUgZHVwbGljYXRlIGJ1ZmZlcmluZyBpbiBjbGlwQnVmZmVyIGFuZCBwb2x5Z29uLnB1c2g/CgogICAgZnVuY3Rpb24gY2xpcFJlY3RhbmdsZSQxKHgwLCB5MCwgeDEsIHkxKSB7CgogICAgICBmdW5jdGlvbiB2aXNpYmxlKHgsIHkpIHsKICAgICAgICByZXR1cm4geDAgPD0geCAmJiB4IDw9IHgxICYmIHkwIDw9IHkgJiYgeSA8PSB5MTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW50ZXJwb2xhdGUoZnJvbSwgdG8sIGRpcmVjdGlvbiwgc3RyZWFtKSB7CiAgICAgICAgdmFyIGEgPSAwLCBhMSA9IDA7CiAgICAgICAgaWYgKGZyb20gPT0gbnVsbAogICAgICAgICAgICB8fCAoYSA9IGNvcm5lcihmcm9tLCBkaXJlY3Rpb24pKSAhPT0gKGExID0gY29ybmVyKHRvLCBkaXJlY3Rpb24pKQogICAgICAgICAgICB8fCBjb21wYXJlUG9pbnQoZnJvbSwgdG8pIDwgMCBeIGRpcmVjdGlvbiA+IDApIHsKICAgICAgICAgIGRvIHN0cmVhbS5wb2ludChhID09PSAwIHx8IGEgPT09IDMgPyB4MCA6IHgxLCBhID4gMSA/IHkxIDogeTApOwogICAgICAgICAgd2hpbGUgKChhID0gKGEgKyBkaXJlY3Rpb24gKyA0KSAlIDQpICE9PSBhMSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHN0cmVhbS5wb2ludCh0b1swXSwgdG9bMV0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gY29ybmVyKHAsIGRpcmVjdGlvbikgewogICAgICAgIHJldHVybiBhYnMkMihwWzBdIC0geDApIDwgZXBzaWxvbiQ3ID8gZGlyZWN0aW9uID4gMCA/IDAgOiAzCiAgICAgICAgICAgIDogYWJzJDIocFswXSAtIHgxKSA8IGVwc2lsb24kNyA/IGRpcmVjdGlvbiA+IDAgPyAyIDogMQogICAgICAgICAgICA6IGFicyQyKHBbMV0gLSB5MCkgPCBlcHNpbG9uJDcgPyBkaXJlY3Rpb24gPiAwID8gMSA6IDAKICAgICAgICAgICAgOiBkaXJlY3Rpb24gPiAwID8gMyA6IDI7IC8vIGFicyhwWzFdIC0geTEpIDwgZXBzaWxvbgogICAgICB9CgogICAgICBmdW5jdGlvbiBjb21wYXJlSW50ZXJzZWN0aW9uKGEsIGIpIHsKICAgICAgICByZXR1cm4gY29tcGFyZVBvaW50KGEueCwgYi54KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gY29tcGFyZVBvaW50KGEsIGIpIHsKICAgICAgICB2YXIgY2EgPSBjb3JuZXIoYSwgMSksCiAgICAgICAgICAgIGNiID0gY29ybmVyKGIsIDEpOwogICAgICAgIHJldHVybiBjYSAhPT0gY2IgPyBjYSAtIGNiCiAgICAgICAgICAgIDogY2EgPT09IDAgPyBiWzFdIC0gYVsxXQogICAgICAgICAgICA6IGNhID09PSAxID8gYVswXSAtIGJbMF0KICAgICAgICAgICAgOiBjYSA9PT0gMiA/IGFbMV0gLSBiWzFdCiAgICAgICAgICAgIDogYlswXSAtIGFbMF07CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbihzdHJlYW0pIHsKICAgICAgICB2YXIgYWN0aXZlU3RyZWFtID0gc3RyZWFtLAogICAgICAgICAgICBidWZmZXJTdHJlYW0gPSBjbGlwQnVmZmVyJDEoKSwKICAgICAgICAgICAgc2VnbWVudHMsCiAgICAgICAgICAgIHBvbHlnb24sCiAgICAgICAgICAgIHJpbmcsCiAgICAgICAgICAgIHhfXywgeV9fLCB2X18sIC8vIGZpcnN0IHBvaW50CiAgICAgICAgICAgIHhfLCB5Xywgdl8sIC8vIHByZXZpb3VzIHBvaW50CiAgICAgICAgICAgIGZpcnN0LAogICAgICAgICAgICBjbGVhbjsKCiAgICAgICAgdmFyIGNsaXBTdHJlYW0gPSB7CiAgICAgICAgICBwb2ludDogcG9pbnQsCiAgICAgICAgICBsaW5lU3RhcnQ6IGxpbmVTdGFydCwKICAgICAgICAgIGxpbmVFbmQ6IGxpbmVFbmQsCiAgICAgICAgICBwb2x5Z29uU3RhcnQ6IHBvbHlnb25TdGFydCwKICAgICAgICAgIHBvbHlnb25FbmQ6IHBvbHlnb25FbmQKICAgICAgICB9OwoKICAgICAgICBmdW5jdGlvbiBwb2ludCh4LCB5KSB7CiAgICAgICAgICBpZiAodmlzaWJsZSh4LCB5KSkgYWN0aXZlU3RyZWFtLnBvaW50KHgsIHkpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gcG9seWdvbkluc2lkZSgpIHsKICAgICAgICAgIHZhciB3aW5kaW5nID0gMDsKCiAgICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHBvbHlnb24ubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGZvciAodmFyIHJpbmcgPSBwb2x5Z29uW2ldLCBqID0gMSwgbSA9IHJpbmcubGVuZ3RoLCBwb2ludCA9IHJpbmdbMF0sIGEwLCBhMSwgYjAgPSBwb2ludFswXSwgYjEgPSBwb2ludFsxXTsgaiA8IG07ICsraikgewogICAgICAgICAgICAgIGEwID0gYjAsIGExID0gYjEsIHBvaW50ID0gcmluZ1tqXSwgYjAgPSBwb2ludFswXSwgYjEgPSBwb2ludFsxXTsKICAgICAgICAgICAgICBpZiAoYTEgPD0geTEpIHsgaWYgKGIxID4geTEgJiYgKGIwIC0gYTApICogKHkxIC0gYTEpID4gKGIxIC0gYTEpICogKHgwIC0gYTApKSArK3dpbmRpbmc7IH0KICAgICAgICAgICAgICBlbHNlIHsgaWYgKGIxIDw9IHkxICYmIChiMCAtIGEwKSAqICh5MSAtIGExKSA8IChiMSAtIGExKSAqICh4MCAtIGEwKSkgLS13aW5kaW5nOyB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICByZXR1cm4gd2luZGluZzsKICAgICAgICB9CgogICAgICAgIC8vIEJ1ZmZlciBnZW9tZXRyeSB3aXRoaW4gYSBwb2x5Z29uIGFuZCB0aGVuIGNsaXAgaXQgZW4gbWFzc2UuCiAgICAgICAgZnVuY3Rpb24gcG9seWdvblN0YXJ0KCkgewogICAgICAgICAgYWN0aXZlU3RyZWFtID0gYnVmZmVyU3RyZWFtLCBzZWdtZW50cyA9IFtdLCBwb2x5Z29uID0gW10sIGNsZWFuID0gdHJ1ZTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIHBvbHlnb25FbmQoKSB7CiAgICAgICAgICB2YXIgc3RhcnRJbnNpZGUgPSBwb2x5Z29uSW5zaWRlKCksCiAgICAgICAgICAgICAgY2xlYW5JbnNpZGUgPSBjbGVhbiAmJiBzdGFydEluc2lkZSwKICAgICAgICAgICAgICB2aXNpYmxlID0gKHNlZ21lbnRzID0gbWVyZ2UkMihzZWdtZW50cykpLmxlbmd0aDsKICAgICAgICAgIGlmIChjbGVhbkluc2lkZSB8fCB2aXNpYmxlKSB7CiAgICAgICAgICAgIHN0cmVhbS5wb2x5Z29uU3RhcnQoKTsKICAgICAgICAgICAgaWYgKGNsZWFuSW5zaWRlKSB7CiAgICAgICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgICAgICAgIGludGVycG9sYXRlKG51bGwsIG51bGwsIDEsIHN0cmVhbSk7CiAgICAgICAgICAgICAgc3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodmlzaWJsZSkgewogICAgICAgICAgICAgIGNsaXBSZWpvaW4kMShzZWdtZW50cywgY29tcGFyZUludGVyc2VjdGlvbiwgc3RhcnRJbnNpZGUsIGludGVycG9sYXRlLCBzdHJlYW0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHN0cmVhbS5wb2x5Z29uRW5kKCk7CiAgICAgICAgICB9CiAgICAgICAgICBhY3RpdmVTdHJlYW0gPSBzdHJlYW0sIHNlZ21lbnRzID0gcG9seWdvbiA9IHJpbmcgPSBudWxsOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbGluZVN0YXJ0KCkgewogICAgICAgICAgY2xpcFN0cmVhbS5wb2ludCA9IGxpbmVQb2ludDsKICAgICAgICAgIGlmIChwb2x5Z29uKSBwb2x5Z29uLnB1c2gocmluZyA9IFtdKTsKICAgICAgICAgIGZpcnN0ID0gdHJ1ZTsKICAgICAgICAgIHZfID0gZmFsc2U7CiAgICAgICAgICB4XyA9IHlfID0gTmFOOwogICAgICAgIH0KCiAgICAgICAgLy8gVE9ETyByYXRoZXIgdGhhbiBzcGVjaWFsLWNhc2UgcG9seWdvbnMsIHNpbXBseSBoYW5kbGUgdGhlbSBzZXBhcmF0ZWx5LgogICAgICAgIC8vIElkZWFsbHksIGNvaW5jaWRlbnQgaW50ZXJzZWN0aW9uIHBvaW50cyBzaG91bGQgYmUgaml0dGVyZWQgdG8gYXZvaWQKICAgICAgICAvLyBjbGlwcGluZyBpc3N1ZXMuCiAgICAgICAgZnVuY3Rpb24gbGluZUVuZCgpIHsKICAgICAgICAgIGlmIChzZWdtZW50cykgewogICAgICAgICAgICBsaW5lUG9pbnQoeF9fLCB5X18pOwogICAgICAgICAgICBpZiAodl9fICYmIHZfKSBidWZmZXJTdHJlYW0ucmVqb2luKCk7CiAgICAgICAgICAgIHNlZ21lbnRzLnB1c2goYnVmZmVyU3RyZWFtLnJlc3VsdCgpKTsKICAgICAgICAgIH0KICAgICAgICAgIGNsaXBTdHJlYW0ucG9pbnQgPSBwb2ludDsKICAgICAgICAgIGlmICh2XykgYWN0aXZlU3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICB9CgogICAgICAgIGZ1bmN0aW9uIGxpbmVQb2ludCh4LCB5KSB7CiAgICAgICAgICB2YXIgdiA9IHZpc2libGUoeCwgeSk7CiAgICAgICAgICBpZiAocG9seWdvbikgcmluZy5wdXNoKFt4LCB5XSk7CiAgICAgICAgICBpZiAoZmlyc3QpIHsKICAgICAgICAgICAgeF9fID0geCwgeV9fID0geSwgdl9fID0gdjsKICAgICAgICAgICAgZmlyc3QgPSBmYWxzZTsKICAgICAgICAgICAgaWYgKHYpIHsKICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgYWN0aXZlU3RyZWFtLnBvaW50KHgsIHkpOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAodiAmJiB2XykgYWN0aXZlU3RyZWFtLnBvaW50KHgsIHkpOwogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICB2YXIgYSA9IFt4XyA9IE1hdGgubWF4KGNsaXBNaW4kMSwgTWF0aC5taW4oY2xpcE1heCQxLCB4XykpLCB5XyA9IE1hdGgubWF4KGNsaXBNaW4kMSwgTWF0aC5taW4oY2xpcE1heCQxLCB5XykpXSwKICAgICAgICAgICAgICAgICAgYiA9IFt4ID0gTWF0aC5tYXgoY2xpcE1pbiQxLCBNYXRoLm1pbihjbGlwTWF4JDEsIHgpKSwgeSA9IE1hdGgubWF4KGNsaXBNaW4kMSwgTWF0aC5taW4oY2xpcE1heCQxLCB5KSldOwogICAgICAgICAgICAgIGlmIChjbGlwTGluZSQxKGEsIGIsIHgwLCB5MCwgeDEsIHkxKSkgewogICAgICAgICAgICAgICAgaWYgKCF2XykgewogICAgICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgICAgIGFjdGl2ZVN0cmVhbS5wb2ludChhWzBdLCBhWzFdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGFjdGl2ZVN0cmVhbS5wb2ludChiWzBdLCBiWzFdKTsKICAgICAgICAgICAgICAgIGlmICghdikgYWN0aXZlU3RyZWFtLmxpbmVFbmQoKTsKICAgICAgICAgICAgICAgIGNsZWFuID0gZmFsc2U7CiAgICAgICAgICAgICAgfSBlbHNlIGlmICh2KSB7CiAgICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ubGluZVN0YXJ0KCk7CiAgICAgICAgICAgICAgICBhY3RpdmVTdHJlYW0ucG9pbnQoeCwgeSk7CiAgICAgICAgICAgICAgICBjbGVhbiA9IGZhbHNlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgeF8gPSB4LCB5XyA9IHksIHZfID0gdjsKICAgICAgICB9CgogICAgICAgIHJldHVybiBjbGlwU3RyZWFtOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVudCQzKCkgewogICAgICB2YXIgeDAgPSAwLAogICAgICAgICAgeTAgPSAwLAogICAgICAgICAgeDEgPSA5NjAsCiAgICAgICAgICB5MSA9IDUwMCwKICAgICAgICAgIGNhY2hlLAogICAgICAgICAgY2FjaGVTdHJlYW0sCiAgICAgICAgICBjbGlwOwoKICAgICAgcmV0dXJuIGNsaXAgPSB7CiAgICAgICAgc3RyZWFtOiBmdW5jdGlvbihzdHJlYW0pIHsKICAgICAgICAgIHJldHVybiBjYWNoZSAmJiBjYWNoZVN0cmVhbSA9PT0gc3RyZWFtID8gY2FjaGUgOiBjYWNoZSA9IGNsaXBSZWN0YW5nbGUkMSh4MCwgeTAsIHgxLCB5MSkoY2FjaGVTdHJlYW0gPSBzdHJlYW0pOwogICAgICAgIH0sCiAgICAgICAgZXh0ZW50OiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4MCA9ICtfWzBdWzBdLCB5MCA9ICtfWzBdWzFdLCB4MSA9ICtfWzFdWzBdLCB5MSA9ICtfWzFdWzFdLCBjYWNoZSA9IGNhY2hlU3RyZWFtID0gbnVsbCwgY2xpcCkgOiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgdmFyIGxlbmd0aFN1bSQyID0gYWRkZXIkMSgpLAogICAgICAgIGxhbWJkYTAkNSwKICAgICAgICBzaW5QaGkwJDMsCiAgICAgICAgY29zUGhpMCQzOwoKICAgIHZhciBsZW5ndGhTdHJlYW0kMiA9IHsKICAgICAgc3BoZXJlOiBub29wJDgsCiAgICAgIHBvaW50OiBub29wJDgsCiAgICAgIGxpbmVTdGFydDogbGVuZ3RoTGluZVN0YXJ0JDEsCiAgICAgIGxpbmVFbmQ6IG5vb3AkOCwKICAgICAgcG9seWdvblN0YXJ0OiBub29wJDgsCiAgICAgIHBvbHlnb25FbmQ6IG5vb3AkOAogICAgfTsKCiAgICBmdW5jdGlvbiBsZW5ndGhMaW5lU3RhcnQkMSgpIHsKICAgICAgbGVuZ3RoU3RyZWFtJDIucG9pbnQgPSBsZW5ndGhQb2ludEZpcnN0JDI7CiAgICAgIGxlbmd0aFN0cmVhbSQyLmxpbmVFbmQgPSBsZW5ndGhMaW5lRW5kJDE7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoTGluZUVuZCQxKCkgewogICAgICBsZW5ndGhTdHJlYW0kMi5wb2ludCA9IGxlbmd0aFN0cmVhbSQyLmxpbmVFbmQgPSBub29wJDg7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoUG9pbnRGaXJzdCQyKGxhbWJkYSwgcGhpKSB7CiAgICAgIGxhbWJkYSAqPSByYWRpYW5zJDEsIHBoaSAqPSByYWRpYW5zJDE7CiAgICAgIGxhbWJkYTAkNSA9IGxhbWJkYSwgc2luUGhpMCQzID0gc2luJDQocGhpKSwgY29zUGhpMCQzID0gY29zJDQocGhpKTsKICAgICAgbGVuZ3RoU3RyZWFtJDIucG9pbnQgPSBsZW5ndGhQb2ludCQyOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlbmd0aFBvaW50JDIobGFtYmRhLCBwaGkpIHsKICAgICAgbGFtYmRhICo9IHJhZGlhbnMkMSwgcGhpICo9IHJhZGlhbnMkMTsKICAgICAgdmFyIHNpblBoaSA9IHNpbiQ0KHBoaSksCiAgICAgICAgICBjb3NQaGkgPSBjb3MkNChwaGkpLAogICAgICAgICAgZGVsdGEgPSBhYnMkMihsYW1iZGEgLSBsYW1iZGEwJDUpLAogICAgICAgICAgY29zRGVsdGEgPSBjb3MkNChkZWx0YSksCiAgICAgICAgICBzaW5EZWx0YSA9IHNpbiQ0KGRlbHRhKSwKICAgICAgICAgIHggPSBjb3NQaGkgKiBzaW5EZWx0YSwKICAgICAgICAgIHkgPSBjb3NQaGkwJDMgKiBzaW5QaGkgLSBzaW5QaGkwJDMgKiBjb3NQaGkgKiBjb3NEZWx0YSwKICAgICAgICAgIHogPSBzaW5QaGkwJDMgKiBzaW5QaGkgKyBjb3NQaGkwJDMgKiBjb3NQaGkgKiBjb3NEZWx0YTsKICAgICAgbGVuZ3RoU3VtJDIuYWRkKGF0YW4yJDIoc3FydCQzKHggKiB4ICsgeSAqIHkpLCB6KSk7CiAgICAgIGxhbWJkYTAkNSA9IGxhbWJkYSwgc2luUGhpMCQzID0gc2luUGhpLCBjb3NQaGkwJDMgPSBjb3NQaGk7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoJDQob2JqZWN0KSB7CiAgICAgIGxlbmd0aFN1bSQyLnJlc2V0KCk7CiAgICAgIGdlb1N0cmVhbSQxKG9iamVjdCwgbGVuZ3RoU3RyZWFtJDIpOwogICAgICByZXR1cm4gK2xlbmd0aFN1bSQyOwogICAgfQoKICAgIHZhciBjb29yZGluYXRlcyQxID0gW251bGwsIG51bGxdLAogICAgICAgIG9iamVjdCQzID0ge3R5cGU6ICJMaW5lU3RyaW5nIiwgY29vcmRpbmF0ZXM6IGNvb3JkaW5hdGVzJDF9OwoKICAgIGZ1bmN0aW9uIGRpc3RhbmNlJDEoYSwgYikgewogICAgICBjb29yZGluYXRlcyQxWzBdID0gYTsKICAgICAgY29vcmRpbmF0ZXMkMVsxXSA9IGI7CiAgICAgIHJldHVybiBsZW5ndGgkNChvYmplY3QkMyk7CiAgICB9CgogICAgdmFyIGNvbnRhaW5zT2JqZWN0VHlwZSQxID0gewogICAgICBGZWF0dXJlOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zR2VvbWV0cnkkMShvYmplY3QuZ2VvbWV0cnksIHBvaW50KTsKICAgICAgfSwKICAgICAgRmVhdHVyZUNvbGxlY3Rpb246IGZ1bmN0aW9uKG9iamVjdCwgcG9pbnQpIHsKICAgICAgICB2YXIgZmVhdHVyZXMgPSBvYmplY3QuZmVhdHVyZXMsIGkgPSAtMSwgbiA9IGZlYXR1cmVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKGNvbnRhaW5zR2VvbWV0cnkkMShmZWF0dXJlc1tpXS5nZW9tZXRyeSwgcG9pbnQpKSByZXR1cm4gdHJ1ZTsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGNvbnRhaW5zR2VvbWV0cnlUeXBlJDEgPSB7CiAgICAgIFNwaGVyZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0sCiAgICAgIFBvaW50OiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgcmV0dXJuIGNvbnRhaW5zUG9pbnQkMShvYmplY3QuY29vcmRpbmF0ZXMsIHBvaW50KTsKICAgICAgfSwKICAgICAgTXVsdGlQb2ludDogZnVuY3Rpb24ob2JqZWN0LCBwb2ludCkgewogICAgICAgIHZhciBjb29yZGluYXRlcyA9IG9iamVjdC5jb29yZGluYXRlcywgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoY29udGFpbnNQb2ludCQxKGNvb3JkaW5hdGVzW2ldLCBwb2ludCkpIHJldHVybiB0cnVlOwogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfSwKICAgICAgTGluZVN0cmluZzogZnVuY3Rpb24ob2JqZWN0LCBwb2ludCkgewogICAgICAgIHJldHVybiBjb250YWluc0xpbmUkMShvYmplY3QuY29vcmRpbmF0ZXMsIHBvaW50KTsKICAgICAgfSwKICAgICAgTXVsdGlMaW5lU3RyaW5nOiBmdW5jdGlvbihvYmplY3QsIHBvaW50KSB7CiAgICAgICAgdmFyIGNvb3JkaW5hdGVzID0gb2JqZWN0LmNvb3JkaW5hdGVzLCBpID0gLTEsIG4gPSBjb29yZGluYXRlcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmIChjb250YWluc0xpbmUkMShjb29yZGluYXRlc1tpXSwgcG9pbnQpKSByZXR1cm4gdHJ1ZTsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0sCiAgICAgIFBvbHlnb246IGZ1bmN0aW9uKG9iamVjdCwgcG9pbnQpIHsKICAgICAgICByZXR1cm4gY29udGFpbnNQb2x5Z29uJDEob2JqZWN0LmNvb3JkaW5hdGVzLCBwb2ludCk7CiAgICAgIH0sCiAgICAgIE11bHRpUG9seWdvbjogZnVuY3Rpb24ob2JqZWN0LCBwb2ludCkgewogICAgICAgIHZhciBjb29yZGluYXRlcyA9IG9iamVjdC5jb29yZGluYXRlcywgaSA9IC0xLCBuID0gY29vcmRpbmF0ZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoY29udGFpbnNQb2x5Z29uJDEoY29vcmRpbmF0ZXNbaV0sIHBvaW50KSkgcmV0dXJuIHRydWU7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9LAogICAgICBHZW9tZXRyeUNvbGxlY3Rpb246IGZ1bmN0aW9uKG9iamVjdCwgcG9pbnQpIHsKICAgICAgICB2YXIgZ2VvbWV0cmllcyA9IG9iamVjdC5nZW9tZXRyaWVzLCBpID0gLTEsIG4gPSBnZW9tZXRyaWVzLmxlbmd0aDsKICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKGNvbnRhaW5zR2VvbWV0cnkkMShnZW9tZXRyaWVzW2ldLCBwb2ludCkpIHJldHVybiB0cnVlOwogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjb250YWluc0dlb21ldHJ5JDEoZ2VvbWV0cnksIHBvaW50KSB7CiAgICAgIHJldHVybiBnZW9tZXRyeSAmJiBjb250YWluc0dlb21ldHJ5VHlwZSQxLmhhc093blByb3BlcnR5KGdlb21ldHJ5LnR5cGUpCiAgICAgICAgICA/IGNvbnRhaW5zR2VvbWV0cnlUeXBlJDFbZ2VvbWV0cnkudHlwZV0oZ2VvbWV0cnksIHBvaW50KQogICAgICAgICAgOiBmYWxzZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb250YWluc1BvaW50JDEoY29vcmRpbmF0ZXMsIHBvaW50KSB7CiAgICAgIHJldHVybiBkaXN0YW5jZSQxKGNvb3JkaW5hdGVzLCBwb2ludCkgPT09IDA7CiAgICB9CgogICAgZnVuY3Rpb24gY29udGFpbnNMaW5lJDEoY29vcmRpbmF0ZXMsIHBvaW50KSB7CiAgICAgIHZhciBhYiA9IGRpc3RhbmNlJDEoY29vcmRpbmF0ZXNbMF0sIGNvb3JkaW5hdGVzWzFdKSwKICAgICAgICAgIGFvID0gZGlzdGFuY2UkMShjb29yZGluYXRlc1swXSwgcG9pbnQpLAogICAgICAgICAgb2IgPSBkaXN0YW5jZSQxKHBvaW50LCBjb29yZGluYXRlc1sxXSk7CiAgICAgIHJldHVybiBhbyArIG9iIDw9IGFiICsgZXBzaWxvbiQ3OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRhaW5zUG9seWdvbiQxKGNvb3JkaW5hdGVzLCBwb2ludCkgewogICAgICByZXR1cm4gISFwb2x5Z29uQ29udGFpbnMkMShjb29yZGluYXRlcy5tYXAocmluZ1JhZGlhbnMkMSksIHBvaW50UmFkaWFucyQxKHBvaW50KSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmluZ1JhZGlhbnMkMShyaW5nKSB7CiAgICAgIHJldHVybiByaW5nID0gcmluZy5tYXAocG9pbnRSYWRpYW5zJDEpLCByaW5nLnBvcCgpLCByaW5nOwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50UmFkaWFucyQxKHBvaW50KSB7CiAgICAgIHJldHVybiBbcG9pbnRbMF0gKiByYWRpYW5zJDEsIHBvaW50WzFdICogcmFkaWFucyQxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb250YWlucyQzKG9iamVjdCwgcG9pbnQpIHsKICAgICAgcmV0dXJuIChvYmplY3QgJiYgY29udGFpbnNPYmplY3RUeXBlJDEuaGFzT3duUHJvcGVydHkob2JqZWN0LnR5cGUpCiAgICAgICAgICA/IGNvbnRhaW5zT2JqZWN0VHlwZSQxW29iamVjdC50eXBlXQogICAgICAgICAgOiBjb250YWluc0dlb21ldHJ5JDEpKG9iamVjdCwgcG9pbnQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGdyYXRpY3VsZVgkMSh5MCwgeTEsIGR5KSB7CiAgICAgIHZhciB5ID0gcmFuZ2UkNCh5MCwgeTEgLSBlcHNpbG9uJDcsIGR5KS5jb25jYXQoeTEpOwogICAgICByZXR1cm4gZnVuY3Rpb24oeCkgeyByZXR1cm4geS5tYXAoZnVuY3Rpb24oeSkgeyByZXR1cm4gW3gsIHldOyB9KTsgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBncmF0aWN1bGVZJDEoeDAsIHgxLCBkeCkgewogICAgICB2YXIgeCA9IHJhbmdlJDQoeDAsIHgxIC0gZXBzaWxvbiQ3LCBkeCkuY29uY2F0KHgxKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHkpIHsgcmV0dXJuIHgubWFwKGZ1bmN0aW9uKHgpIHsgcmV0dXJuIFt4LCB5XTsgfSk7IH07CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlJDEoKSB7CiAgICAgIHZhciB4MSwgeDAsIFgxLCBYMCwKICAgICAgICAgIHkxLCB5MCwgWTEsIFkwLAogICAgICAgICAgZHggPSAxMCwgZHkgPSBkeCwgRFggPSA5MCwgRFkgPSAzNjAsCiAgICAgICAgICB4LCB5LCBYLCBZLAogICAgICAgICAgcHJlY2lzaW9uID0gMi41OwoKICAgICAgZnVuY3Rpb24gZ3JhdGljdWxlKCkgewogICAgICAgIHJldHVybiB7dHlwZTogIk11bHRpTGluZVN0cmluZyIsIGNvb3JkaW5hdGVzOiBsaW5lcygpfTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gbGluZXMoKSB7CiAgICAgICAgcmV0dXJuIHJhbmdlJDQoY2VpbCQxKFgwIC8gRFgpICogRFgsIFgxLCBEWCkubWFwKFgpCiAgICAgICAgICAgIC5jb25jYXQocmFuZ2UkNChjZWlsJDEoWTAgLyBEWSkgKiBEWSwgWTEsIERZKS5tYXAoWSkpCiAgICAgICAgICAgIC5jb25jYXQocmFuZ2UkNChjZWlsJDEoeDAgLyBkeCkgKiBkeCwgeDEsIGR4KS5maWx0ZXIoZnVuY3Rpb24oeCkgeyByZXR1cm4gYWJzJDIoeCAlIERYKSA+IGVwc2lsb24kNzsgfSkubWFwKHgpKQogICAgICAgICAgICAuY29uY2F0KHJhbmdlJDQoY2VpbCQxKHkwIC8gZHkpICogZHksIHkxLCBkeSkuZmlsdGVyKGZ1bmN0aW9uKHkpIHsgcmV0dXJuIGFicyQyKHkgJSBEWSkgPiBlcHNpbG9uJDc7IH0pLm1hcCh5KSk7CiAgICAgIH0KCiAgICAgIGdyYXRpY3VsZS5saW5lcyA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBsaW5lcygpLm1hcChmdW5jdGlvbihjb29yZGluYXRlcykgeyByZXR1cm4ge3R5cGU6ICJMaW5lU3RyaW5nIiwgY29vcmRpbmF0ZXM6IGNvb3JkaW5hdGVzfTsgfSk7CiAgICAgIH07CgogICAgICBncmF0aWN1bGUub3V0bGluZSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICB0eXBlOiAiUG9seWdvbiIsCiAgICAgICAgICBjb29yZGluYXRlczogWwogICAgICAgICAgICBYKFgwKS5jb25jYXQoCiAgICAgICAgICAgIFkoWTEpLnNsaWNlKDEpLAogICAgICAgICAgICBYKFgxKS5yZXZlcnNlKCkuc2xpY2UoMSksCiAgICAgICAgICAgIFkoWTApLnJldmVyc2UoKS5zbGljZSgxKSkKICAgICAgICAgIF0KICAgICAgICB9OwogICAgICB9OwoKICAgICAgZ3JhdGljdWxlLmV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBncmF0aWN1bGUuZXh0ZW50TWlub3IoKTsKICAgICAgICByZXR1cm4gZ3JhdGljdWxlLmV4dGVudE1ham9yKF8pLmV4dGVudE1pbm9yKF8pOwogICAgICB9OwoKICAgICAgZ3JhdGljdWxlLmV4dGVudE1ham9yID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIFtbWDAsIFkwXSwgW1gxLCBZMV1dOwogICAgICAgIFgwID0gK19bMF1bMF0sIFgxID0gK19bMV1bMF07CiAgICAgICAgWTAgPSArX1swXVsxXSwgWTEgPSArX1sxXVsxXTsKICAgICAgICBpZiAoWDAgPiBYMSkgXyA9IFgwLCBYMCA9IFgxLCBYMSA9IF87CiAgICAgICAgaWYgKFkwID4gWTEpIF8gPSBZMCwgWTAgPSBZMSwgWTEgPSBfOwogICAgICAgIHJldHVybiBncmF0aWN1bGUucHJlY2lzaW9uKHByZWNpc2lvbik7CiAgICAgIH07CgogICAgICBncmF0aWN1bGUuZXh0ZW50TWlub3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW1t4MCwgeTBdLCBbeDEsIHkxXV07CiAgICAgICAgeDAgPSArX1swXVswXSwgeDEgPSArX1sxXVswXTsKICAgICAgICB5MCA9ICtfWzBdWzFdLCB5MSA9ICtfWzFdWzFdOwogICAgICAgIGlmICh4MCA+IHgxKSBfID0geDAsIHgwID0geDEsIHgxID0gXzsKICAgICAgICBpZiAoeTAgPiB5MSkgXyA9IHkwLCB5MCA9IHkxLCB5MSA9IF87CiAgICAgICAgcmV0dXJuIGdyYXRpY3VsZS5wcmVjaXNpb24ocHJlY2lzaW9uKTsKICAgICAgfTsKCiAgICAgIGdyYXRpY3VsZS5zdGVwID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIGdyYXRpY3VsZS5zdGVwTWlub3IoKTsKICAgICAgICByZXR1cm4gZ3JhdGljdWxlLnN0ZXBNYWpvcihfKS5zdGVwTWlub3IoXyk7CiAgICAgIH07CgogICAgICBncmF0aWN1bGUuc3RlcE1ham9yID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIFtEWCwgRFldOwogICAgICAgIERYID0gK19bMF0sIERZID0gK19bMV07CiAgICAgICAgcmV0dXJuIGdyYXRpY3VsZTsKICAgICAgfTsKCiAgICAgIGdyYXRpY3VsZS5zdGVwTWlub3IgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gW2R4LCBkeV07CiAgICAgICAgZHggPSArX1swXSwgZHkgPSArX1sxXTsKICAgICAgICByZXR1cm4gZ3JhdGljdWxlOwogICAgICB9OwoKICAgICAgZ3JhdGljdWxlLnByZWNpc2lvbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoIWFyZ3VtZW50cy5sZW5ndGgpIHJldHVybiBwcmVjaXNpb247CiAgICAgICAgcHJlY2lzaW9uID0gK187CiAgICAgICAgeCA9IGdyYXRpY3VsZVgkMSh5MCwgeTEsIDkwKTsKICAgICAgICB5ID0gZ3JhdGljdWxlWSQxKHgwLCB4MSwgcHJlY2lzaW9uKTsKICAgICAgICBYID0gZ3JhdGljdWxlWCQxKFkwLCBZMSwgOTApOwogICAgICAgIFkgPSBncmF0aWN1bGVZJDEoWDAsIFgxLCBwcmVjaXNpb24pOwogICAgICAgIHJldHVybiBncmF0aWN1bGU7CiAgICAgIH07CgogICAgICByZXR1cm4gZ3JhdGljdWxlCiAgICAgICAgICAuZXh0ZW50TWFqb3IoW1stMTgwLCAtOTAgKyBlcHNpbG9uJDddLCBbMTgwLCA5MCAtIGVwc2lsb24kN11dKQogICAgICAgICAgLmV4dGVudE1pbm9yKFtbLTE4MCwgLTgwIC0gZXBzaWxvbiQ3XSwgWzE4MCwgODAgKyBlcHNpbG9uJDddXSk7CiAgICB9CgogICAgZnVuY3Rpb24gZ3JhdGljdWxlMTAkMSgpIHsKICAgICAgcmV0dXJuIGdyYXRpY3VsZSQxKCkoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZSQ0KGEsIGIpIHsKICAgICAgdmFyIHgwID0gYVswXSAqIHJhZGlhbnMkMSwKICAgICAgICAgIHkwID0gYVsxXSAqIHJhZGlhbnMkMSwKICAgICAgICAgIHgxID0gYlswXSAqIHJhZGlhbnMkMSwKICAgICAgICAgIHkxID0gYlsxXSAqIHJhZGlhbnMkMSwKICAgICAgICAgIGN5MCA9IGNvcyQ0KHkwKSwKICAgICAgICAgIHN5MCA9IHNpbiQ0KHkwKSwKICAgICAgICAgIGN5MSA9IGNvcyQ0KHkxKSwKICAgICAgICAgIHN5MSA9IHNpbiQ0KHkxKSwKICAgICAgICAgIGt4MCA9IGN5MCAqIGNvcyQ0KHgwKSwKICAgICAgICAgIGt5MCA9IGN5MCAqIHNpbiQ0KHgwKSwKICAgICAgICAgIGt4MSA9IGN5MSAqIGNvcyQ0KHgxKSwKICAgICAgICAgIGt5MSA9IGN5MSAqIHNpbiQ0KHgxKSwKICAgICAgICAgIGQgPSAyICogYXNpbiQyKHNxcnQkMyhoYXZlcnNpbiQxKHkxIC0geTApICsgY3kwICogY3kxICogaGF2ZXJzaW4kMSh4MSAtIHgwKSkpLAogICAgICAgICAgayA9IHNpbiQ0KGQpOwoKICAgICAgdmFyIGludGVycG9sYXRlID0gZCA/IGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgQiA9IHNpbiQ0KHQgKj0gZCkgLyBrLAogICAgICAgICAgICBBID0gc2luJDQoZCAtIHQpIC8gaywKICAgICAgICAgICAgeCA9IEEgKiBreDAgKyBCICoga3gxLAogICAgICAgICAgICB5ID0gQSAqIGt5MCArIEIgKiBreTEsCiAgICAgICAgICAgIHogPSBBICogc3kwICsgQiAqIHN5MTsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgYXRhbjIkMih5LCB4KSAqIGRlZ3JlZXMkMywKICAgICAgICAgIGF0YW4yJDIoeiwgc3FydCQzKHggKiB4ICsgeSAqIHkpKSAqIGRlZ3JlZXMkMwogICAgICAgIF07CiAgICAgIH0gOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gW3gwICogZGVncmVlcyQzLCB5MCAqIGRlZ3JlZXMkM107CiAgICAgIH07CgogICAgICBpbnRlcnBvbGF0ZS5kaXN0YW5jZSA9IGQ7CgogICAgICByZXR1cm4gaW50ZXJwb2xhdGU7CiAgICB9CgogICAgZnVuY3Rpb24gaWRlbnRpdHkkZSh4KSB7CiAgICAgIHJldHVybiB4OwogICAgfQoKICAgIHZhciBhcmVhU3VtJDMgPSBhZGRlciQxKCksCiAgICAgICAgYXJlYVJpbmdTdW0kMyA9IGFkZGVyJDEoKSwKICAgICAgICB4MDAkMywKICAgICAgICB5MDAkMywKICAgICAgICB4MCQ2LAogICAgICAgIHkwJDY7CgogICAgdmFyIGFyZWFTdHJlYW0kMyA9IHsKICAgICAgcG9pbnQ6IG5vb3AkOCwKICAgICAgbGluZVN0YXJ0OiBub29wJDgsCiAgICAgIGxpbmVFbmQ6IG5vb3AkOCwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBhcmVhU3RyZWFtJDMubGluZVN0YXJ0ID0gYXJlYVJpbmdTdGFydCQzOwogICAgICAgIGFyZWFTdHJlYW0kMy5saW5lRW5kID0gYXJlYVJpbmdFbmQkMzsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgYXJlYVN0cmVhbSQzLmxpbmVTdGFydCA9IGFyZWFTdHJlYW0kMy5saW5lRW5kID0gYXJlYVN0cmVhbSQzLnBvaW50ID0gbm9vcCQ4OwogICAgICAgIGFyZWFTdW0kMy5hZGQoYWJzJDIoYXJlYVJpbmdTdW0kMykpOwogICAgICAgIGFyZWFSaW5nU3VtJDMucmVzZXQoKTsKICAgICAgfSwKICAgICAgcmVzdWx0OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYXJlYSA9IGFyZWFTdW0kMyAvIDI7CiAgICAgICAgYXJlYVN1bSQzLnJlc2V0KCk7CiAgICAgICAgcmV0dXJuIGFyZWE7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYXJlYVJpbmdTdGFydCQzKCkgewogICAgICBhcmVhU3RyZWFtJDMucG9pbnQgPSBhcmVhUG9pbnRGaXJzdCQzOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWFQb2ludEZpcnN0JDMoeCwgeSkgewogICAgICBhcmVhU3RyZWFtJDMucG9pbnQgPSBhcmVhUG9pbnQkMzsKICAgICAgeDAwJDMgPSB4MCQ2ID0geCwgeTAwJDMgPSB5MCQ2ID0geTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhUG9pbnQkMyh4LCB5KSB7CiAgICAgIGFyZWFSaW5nU3VtJDMuYWRkKHkwJDYgKiB4IC0geDAkNiAqIHkpOwogICAgICB4MCQ2ID0geCwgeTAkNiA9IHk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJlYVJpbmdFbmQkMygpIHsKICAgICAgYXJlYVBvaW50JDMoeDAwJDMsIHkwMCQzKTsKICAgIH0KCiAgICB2YXIgeDAkNyA9IEluZmluaXR5LAogICAgICAgIHkwJDcgPSB4MCQ3LAogICAgICAgIHgxJDEgPSAteDAkNywKICAgICAgICB5MSQxID0geDEkMTsKCiAgICB2YXIgYm91bmRzU3RyZWFtJDMgPSB7CiAgICAgIHBvaW50OiBib3VuZHNQb2ludCQzLAogICAgICBsaW5lU3RhcnQ6IG5vb3AkOCwKICAgICAgbGluZUVuZDogbm9vcCQ4LAogICAgICBwb2x5Z29uU3RhcnQ6IG5vb3AkOCwKICAgICAgcG9seWdvbkVuZDogbm9vcCQ4LAogICAgICByZXN1bHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBib3VuZHMgPSBbW3gwJDcsIHkwJDddLCBbeDEkMSwgeTEkMV1dOwogICAgICAgIHgxJDEgPSB5MSQxID0gLSh5MCQ3ID0geDAkNyA9IEluZmluaXR5KTsKICAgICAgICByZXR1cm4gYm91bmRzOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGJvdW5kc1BvaW50JDMoeCwgeSkgewogICAgICBpZiAoeCA8IHgwJDcpIHgwJDcgPSB4OwogICAgICBpZiAoeCA+IHgxJDEpIHgxJDEgPSB4OwogICAgICBpZiAoeSA8IHkwJDcpIHkwJDcgPSB5OwogICAgICBpZiAoeSA+IHkxJDEpIHkxJDEgPSB5OwogICAgfQoKICAgIC8vIFRPRE8gRW5mb3JjZSBwb3NpdGl2ZSBhcmVhIGZvciBleHRlcmlvciwgbmVnYXRpdmUgYXJlYSBmb3IgaW50ZXJpb3I/CgogICAgdmFyIFgwJDMgPSAwLAogICAgICAgIFkwJDMgPSAwLAogICAgICAgIFowJDMgPSAwLAogICAgICAgIFgxJDMgPSAwLAogICAgICAgIFkxJDMgPSAwLAogICAgICAgIFoxJDMgPSAwLAogICAgICAgIFgyJDMgPSAwLAogICAgICAgIFkyJDMgPSAwLAogICAgICAgIFoyJDMgPSAwLAogICAgICAgIHgwMCQ0LAogICAgICAgIHkwMCQ0LAogICAgICAgIHgwJDgsCiAgICAgICAgeTAkODsKCiAgICB2YXIgY2VudHJvaWRTdHJlYW0kMyA9IHsKICAgICAgcG9pbnQ6IGNlbnRyb2lkUG9pbnQkMywKICAgICAgbGluZVN0YXJ0OiBjZW50cm9pZExpbmVTdGFydCQzLAogICAgICBsaW5lRW5kOiBjZW50cm9pZExpbmVFbmQkMywKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBjZW50cm9pZFN0cmVhbSQzLmxpbmVTdGFydCA9IGNlbnRyb2lkUmluZ1N0YXJ0JDM7CiAgICAgICAgY2VudHJvaWRTdHJlYW0kMy5saW5lRW5kID0gY2VudHJvaWRSaW5nRW5kJDM7CiAgICAgIH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGNlbnRyb2lkU3RyZWFtJDMucG9pbnQgPSBjZW50cm9pZFBvaW50JDM7CiAgICAgICAgY2VudHJvaWRTdHJlYW0kMy5saW5lU3RhcnQgPSBjZW50cm9pZExpbmVTdGFydCQzOwogICAgICAgIGNlbnRyb2lkU3RyZWFtJDMubGluZUVuZCA9IGNlbnRyb2lkTGluZUVuZCQzOwogICAgICB9LAogICAgICByZXN1bHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBjZW50cm9pZCA9IFoyJDMgPyBbWDIkMyAvIFoyJDMsIFkyJDMgLyBaMiQzXQogICAgICAgICAgICA6IFoxJDMgPyBbWDEkMyAvIFoxJDMsIFkxJDMgLyBaMSQzXQogICAgICAgICAgICA6IFowJDMgPyBbWDAkMyAvIFowJDMsIFkwJDMgLyBaMCQzXQogICAgICAgICAgICA6IFtOYU4sIE5hTl07CiAgICAgICAgWDAkMyA9IFkwJDMgPSBaMCQzID0KICAgICAgICBYMSQzID0gWTEkMyA9IFoxJDMgPQogICAgICAgIFgyJDMgPSBZMiQzID0gWjIkMyA9IDA7CiAgICAgICAgcmV0dXJuIGNlbnRyb2lkOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnQkMyh4LCB5KSB7CiAgICAgIFgwJDMgKz0geDsKICAgICAgWTAkMyArPSB5OwogICAgICArK1owJDM7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRMaW5lU3RhcnQkMygpIHsKICAgICAgY2VudHJvaWRTdHJlYW0kMy5wb2ludCA9IGNlbnRyb2lkUG9pbnRGaXJzdExpbmUkMTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZFBvaW50Rmlyc3RMaW5lJDEoeCwgeSkgewogICAgICBjZW50cm9pZFN0cmVhbSQzLnBvaW50ID0gY2VudHJvaWRQb2ludExpbmUkMTsKICAgICAgY2VudHJvaWRQb2ludCQzKHgwJDggPSB4LCB5MCQ4ID0geSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRQb2ludExpbmUkMSh4LCB5KSB7CiAgICAgIHZhciBkeCA9IHggLSB4MCQ4LCBkeSA9IHkgLSB5MCQ4LCB6ID0gc3FydCQzKGR4ICogZHggKyBkeSAqIGR5KTsKICAgICAgWDEkMyArPSB6ICogKHgwJDggKyB4KSAvIDI7CiAgICAgIFkxJDMgKz0geiAqICh5MCQ4ICsgeSkgLyAyOwogICAgICBaMSQzICs9IHo7CiAgICAgIGNlbnRyb2lkUG9pbnQkMyh4MCQ4ID0geCwgeTAkOCA9IHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkTGluZUVuZCQzKCkgewogICAgICBjZW50cm9pZFN0cmVhbSQzLnBvaW50ID0gY2VudHJvaWRQb2ludCQzOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUmluZ1N0YXJ0JDMoKSB7CiAgICAgIGNlbnRyb2lkU3RyZWFtJDMucG9pbnQgPSBjZW50cm9pZFBvaW50Rmlyc3RSaW5nJDE7CiAgICB9CgogICAgZnVuY3Rpb24gY2VudHJvaWRSaW5nRW5kJDMoKSB7CiAgICAgIGNlbnRyb2lkUG9pbnRSaW5nJDEoeDAwJDQsIHkwMCQ0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZFBvaW50Rmlyc3RSaW5nJDEoeCwgeSkgewogICAgICBjZW50cm9pZFN0cmVhbSQzLnBvaW50ID0gY2VudHJvaWRQb2ludFJpbmckMTsKICAgICAgY2VudHJvaWRQb2ludCQzKHgwMCQ0ID0geDAkOCA9IHgsIHkwMCQ0ID0geTAkOCA9IHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbnRyb2lkUG9pbnRSaW5nJDEoeCwgeSkgewogICAgICB2YXIgZHggPSB4IC0geDAkOCwKICAgICAgICAgIGR5ID0geSAtIHkwJDgsCiAgICAgICAgICB6ID0gc3FydCQzKGR4ICogZHggKyBkeSAqIGR5KTsKCiAgICAgIFgxJDMgKz0geiAqICh4MCQ4ICsgeCkgLyAyOwogICAgICBZMSQzICs9IHogKiAoeTAkOCArIHkpIC8gMjsKICAgICAgWjEkMyArPSB6OwoKICAgICAgeiA9IHkwJDggKiB4IC0geDAkOCAqIHk7CiAgICAgIFgyJDMgKz0geiAqICh4MCQ4ICsgeCk7CiAgICAgIFkyJDMgKz0geiAqICh5MCQ4ICsgeSk7CiAgICAgIFoyJDMgKz0geiAqIDM7CiAgICAgIGNlbnRyb2lkUG9pbnQkMyh4MCQ4ID0geCwgeTAkOCA9IHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIFBhdGhDb250ZXh0JDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBQYXRoQ29udGV4dCQxLnByb3RvdHlwZSA9IHsKICAgICAgX3JhZGl1czogNC41LAogICAgICBwb2ludFJhZGl1czogZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiB0aGlzLl9yYWRpdXMgPSBfLCB0aGlzOwogICAgICB9LAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgPT09IDApIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fcG9pbnQgPSBOYU47CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKHgsIHkpOwogICAgICAgICAgICB0aGlzLl9wb2ludCA9IDE7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAxOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGRlZmF1bHQ6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5tb3ZlVG8oeCArIHRoaXMuX3JhZGl1cywgeSk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuYXJjKHgsIHksIHRoaXMuX3JhZGl1cywgMCwgdGF1JDgpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCiAgICAgIHJlc3VsdDogbm9vcCQ4CiAgICB9OwoKICAgIHZhciBsZW5ndGhTdW0kMyA9IGFkZGVyJDEoKSwKICAgICAgICBsZW5ndGhSaW5nJDEsCiAgICAgICAgeDAwJDUsCiAgICAgICAgeTAwJDUsCiAgICAgICAgeDAkOSwKICAgICAgICB5MCQ5OwoKICAgIHZhciBsZW5ndGhTdHJlYW0kMyA9IHsKICAgICAgcG9pbnQ6IG5vb3AkOCwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICBsZW5ndGhTdHJlYW0kMy5wb2ludCA9IGxlbmd0aFBvaW50Rmlyc3QkMzsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKGxlbmd0aFJpbmckMSkgbGVuZ3RoUG9pbnQkMyh4MDAkNSwgeTAwJDUpOwogICAgICAgIGxlbmd0aFN0cmVhbSQzLnBvaW50ID0gbm9vcCQ4OwogICAgICB9LAogICAgICBwb2x5Z29uU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGxlbmd0aFJpbmckMSA9IHRydWU7CiAgICAgIH0sCiAgICAgIHBvbHlnb25FbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGxlbmd0aFJpbmckMSA9IG51bGw7CiAgICAgIH0sCiAgICAgIHJlc3VsdDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGxlbmd0aCA9ICtsZW5ndGhTdW0kMzsKICAgICAgICBsZW5ndGhTdW0kMy5yZXNldCgpOwogICAgICAgIHJldHVybiBsZW5ndGg7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gbGVuZ3RoUG9pbnRGaXJzdCQzKHgsIHkpIHsKICAgICAgbGVuZ3RoU3RyZWFtJDMucG9pbnQgPSBsZW5ndGhQb2ludCQzOwogICAgICB4MDAkNSA9IHgwJDkgPSB4LCB5MDAkNSA9IHkwJDkgPSB5OwogICAgfQoKICAgIGZ1bmN0aW9uIGxlbmd0aFBvaW50JDMoeCwgeSkgewogICAgICB4MCQ5IC09IHgsIHkwJDkgLT0geTsKICAgICAgbGVuZ3RoU3VtJDMuYWRkKHNxcnQkMyh4MCQ5ICogeDAkOSArIHkwJDkgKiB5MCQ5KSk7CiAgICAgIHgwJDkgPSB4LCB5MCQ5ID0geTsKICAgIH0KCiAgICBmdW5jdGlvbiBQYXRoU3RyaW5nJDEoKSB7CiAgICAgIHRoaXMuX3N0cmluZyA9IFtdOwogICAgfQoKICAgIFBhdGhTdHJpbmckMS5wcm90b3R5cGUgPSB7CiAgICAgIF9yYWRpdXM6IDQuNSwKICAgICAgX2NpcmNsZTogY2lyY2xlJDQoNC41KSwKICAgICAgcG9pbnRSYWRpdXM6IGZ1bmN0aW9uKF8pIHsKICAgICAgICBpZiAoKF8gPSArXykgIT09IHRoaXMuX3JhZGl1cykgdGhpcy5fcmFkaXVzID0gXywgdGhpcy5fY2lyY2xlID0gbnVsbDsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lID09PSAwKSB0aGlzLl9zdHJpbmcucHVzaCgiWiIpOwogICAgICAgIHRoaXMuX3BvaW50ID0gTmFOOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogewogICAgICAgICAgICB0aGlzLl9zdHJpbmcucHVzaCgiTSIsIHgsICIsIiwgeSk7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ID0gMTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgdGhpcy5fc3RyaW5nLnB1c2goIkwiLCB4LCAiLCIsIHkpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGRlZmF1bHQ6IHsKICAgICAgICAgICAgaWYgKHRoaXMuX2NpcmNsZSA9PSBudWxsKSB0aGlzLl9jaXJjbGUgPSBjaXJjbGUkNCh0aGlzLl9yYWRpdXMpOwogICAgICAgICAgICB0aGlzLl9zdHJpbmcucHVzaCgiTSIsIHgsICIsIiwgeSwgdGhpcy5fY2lyY2xlKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICByZXN1bHQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9zdHJpbmcubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gdGhpcy5fc3RyaW5nLmpvaW4oIiIpOwogICAgICAgICAgdGhpcy5fc3RyaW5nID0gW107CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY2lyY2xlJDQocmFkaXVzKSB7CiAgICAgIHJldHVybiAibTAsIiArIHJhZGl1cwogICAgICAgICAgKyAiYSIgKyByYWRpdXMgKyAiLCIgKyByYWRpdXMgKyAiIDAgMSwxIDAsIiArIC0yICogcmFkaXVzCiAgICAgICAgICArICJhIiArIHJhZGl1cyArICIsIiArIHJhZGl1cyArICIgMCAxLDEgMCwiICsgMiAqIHJhZGl1cwogICAgICAgICAgKyAieiI7CiAgICB9CgogICAgZnVuY3Rpb24gaW5kZXgkNShwcm9qZWN0aW9uLCBjb250ZXh0KSB7CiAgICAgIHZhciBwb2ludFJhZGl1cyA9IDQuNSwKICAgICAgICAgIHByb2plY3Rpb25TdHJlYW0sCiAgICAgICAgICBjb250ZXh0U3RyZWFtOwoKICAgICAgZnVuY3Rpb24gcGF0aChvYmplY3QpIHsKICAgICAgICBpZiAob2JqZWN0KSB7CiAgICAgICAgICBpZiAodHlwZW9mIHBvaW50UmFkaXVzID09PSAiZnVuY3Rpb24iKSBjb250ZXh0U3RyZWFtLnBvaW50UmFkaXVzKCtwb2ludFJhZGl1cy5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgICAgIGdlb1N0cmVhbSQxKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShjb250ZXh0U3RyZWFtKSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBjb250ZXh0U3RyZWFtLnJlc3VsdCgpOwogICAgICB9CgogICAgICBwYXRoLmFyZWEgPSBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICBnZW9TdHJlYW0kMShvYmplY3QsIHByb2plY3Rpb25TdHJlYW0oYXJlYVN0cmVhbSQzKSk7CiAgICAgICAgcmV0dXJuIGFyZWFTdHJlYW0kMy5yZXN1bHQoKTsKICAgICAgfTsKCiAgICAgIHBhdGgubWVhc3VyZSA9IGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgIGdlb1N0cmVhbSQxKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShsZW5ndGhTdHJlYW0kMykpOwogICAgICAgIHJldHVybiBsZW5ndGhTdHJlYW0kMy5yZXN1bHQoKTsKICAgICAgfTsKCiAgICAgIHBhdGguYm91bmRzID0gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgZ2VvU3RyZWFtJDEob2JqZWN0LCBwcm9qZWN0aW9uU3RyZWFtKGJvdW5kc1N0cmVhbSQzKSk7CiAgICAgICAgcmV0dXJuIGJvdW5kc1N0cmVhbSQzLnJlc3VsdCgpOwogICAgICB9OwoKICAgICAgcGF0aC5jZW50cm9pZCA9IGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgIGdlb1N0cmVhbSQxKG9iamVjdCwgcHJvamVjdGlvblN0cmVhbShjZW50cm9pZFN0cmVhbSQzKSk7CiAgICAgICAgcmV0dXJuIGNlbnRyb2lkU3RyZWFtJDMucmVzdWx0KCk7CiAgICAgIH07CgogICAgICBwYXRoLnByb2plY3Rpb24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocHJvamVjdGlvblN0cmVhbSA9IF8gPT0gbnVsbCA/IChwcm9qZWN0aW9uID0gbnVsbCwgaWRlbnRpdHkkZSkgOiAocHJvamVjdGlvbiA9IF8pLnN0cmVhbSwgcGF0aCkgOiBwcm9qZWN0aW9uOwogICAgICB9OwoKICAgICAgcGF0aC5jb250ZXh0ID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIGNvbnRleHQ7CiAgICAgICAgY29udGV4dFN0cmVhbSA9IF8gPT0gbnVsbCA/IChjb250ZXh0ID0gbnVsbCwgbmV3IFBhdGhTdHJpbmckMSkgOiBuZXcgUGF0aENvbnRleHQkMShjb250ZXh0ID0gXyk7CiAgICAgICAgaWYgKHR5cGVvZiBwb2ludFJhZGl1cyAhPT0gImZ1bmN0aW9uIikgY29udGV4dFN0cmVhbS5wb2ludFJhZGl1cyhwb2ludFJhZGl1cyk7CiAgICAgICAgcmV0dXJuIHBhdGg7CiAgICAgIH07CgogICAgICBwYXRoLnBvaW50UmFkaXVzID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIHBvaW50UmFkaXVzOwogICAgICAgIHBvaW50UmFkaXVzID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogKGNvbnRleHRTdHJlYW0ucG9pbnRSYWRpdXMoK18pLCArXyk7CiAgICAgICAgcmV0dXJuIHBhdGg7CiAgICAgIH07CgogICAgICByZXR1cm4gcGF0aC5wcm9qZWN0aW9uKHByb2plY3Rpb24pLmNvbnRleHQoY29udGV4dCk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNmb3JtJDIobWV0aG9kcykgewogICAgICByZXR1cm4gewogICAgICAgIHN0cmVhbTogdHJhbnNmb3JtZXIkNChtZXRob2RzKQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybWVyJDQobWV0aG9kcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oc3RyZWFtKSB7CiAgICAgICAgdmFyIHMgPSBuZXcgVHJhbnNmb3JtU3RyZWFtJDE7CiAgICAgICAgZm9yICh2YXIga2V5IGluIG1ldGhvZHMpIHNba2V5XSA9IG1ldGhvZHNba2V5XTsKICAgICAgICBzLnN0cmVhbSA9IHN0cmVhbTsKICAgICAgICByZXR1cm4gczsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBUcmFuc2Zvcm1TdHJlYW0kMSgpIHt9CgogICAgVHJhbnNmb3JtU3RyZWFtJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVHJhbnNmb3JtU3RyZWFtJDEsCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7IHRoaXMuc3RyZWFtLnBvaW50KHgsIHkpOyB9LAogICAgICBzcGhlcmU6IGZ1bmN0aW9uKCkgeyB0aGlzLnN0cmVhbS5zcGhlcmUoKTsgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsgdGhpcy5zdHJlYW0ubGluZVN0YXJ0KCk7IH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgeyB0aGlzLnN0cmVhbS5saW5lRW5kKCk7IH0sCiAgICAgIHBvbHlnb25TdGFydDogZnVuY3Rpb24oKSB7IHRoaXMuc3RyZWFtLnBvbHlnb25TdGFydCgpOyB9LAogICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsgdGhpcy5zdHJlYW0ucG9seWdvbkVuZCgpOyB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGZpdCQxKHByb2plY3Rpb24sIGZpdEJvdW5kcywgb2JqZWN0KSB7CiAgICAgIHZhciBjbGlwID0gcHJvamVjdGlvbi5jbGlwRXh0ZW50ICYmIHByb2plY3Rpb24uY2xpcEV4dGVudCgpOwogICAgICBwcm9qZWN0aW9uLnNjYWxlKDE1MCkudHJhbnNsYXRlKFswLCAwXSk7CiAgICAgIGlmIChjbGlwICE9IG51bGwpIHByb2plY3Rpb24uY2xpcEV4dGVudChudWxsKTsKICAgICAgZ2VvU3RyZWFtJDEob2JqZWN0LCBwcm9qZWN0aW9uLnN0cmVhbShib3VuZHNTdHJlYW0kMykpOwogICAgICBmaXRCb3VuZHMoYm91bmRzU3RyZWFtJDMucmVzdWx0KCkpOwogICAgICBpZiAoY2xpcCAhPSBudWxsKSBwcm9qZWN0aW9uLmNsaXBFeHRlbnQoY2xpcCk7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIGZpdEV4dGVudCQxKHByb2plY3Rpb24sIGV4dGVudCwgb2JqZWN0KSB7CiAgICAgIHJldHVybiBmaXQkMShwcm9qZWN0aW9uLCBmdW5jdGlvbihiKSB7CiAgICAgICAgdmFyIHcgPSBleHRlbnRbMV1bMF0gLSBleHRlbnRbMF1bMF0sCiAgICAgICAgICAgIGggPSBleHRlbnRbMV1bMV0gLSBleHRlbnRbMF1bMV0sCiAgICAgICAgICAgIGsgPSBNYXRoLm1pbih3IC8gKGJbMV1bMF0gLSBiWzBdWzBdKSwgaCAvIChiWzFdWzFdIC0gYlswXVsxXSkpLAogICAgICAgICAgICB4ID0gK2V4dGVudFswXVswXSArICh3IC0gayAqIChiWzFdWzBdICsgYlswXVswXSkpIC8gMiwKICAgICAgICAgICAgeSA9ICtleHRlbnRbMF1bMV0gKyAoaCAtIGsgKiAoYlsxXVsxXSArIGJbMF1bMV0pKSAvIDI7CiAgICAgICAgcHJvamVjdGlvbi5zY2FsZSgxNTAgKiBrKS50cmFuc2xhdGUoW3gsIHldKTsKICAgICAgfSwgb2JqZWN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmaXRTaXplJDEocHJvamVjdGlvbiwgc2l6ZSwgb2JqZWN0KSB7CiAgICAgIHJldHVybiBmaXRFeHRlbnQkMShwcm9qZWN0aW9uLCBbWzAsIDBdLCBzaXplXSwgb2JqZWN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmaXRXaWR0aCQxKHByb2plY3Rpb24sIHdpZHRoLCBvYmplY3QpIHsKICAgICAgcmV0dXJuIGZpdCQxKHByb2plY3Rpb24sIGZ1bmN0aW9uKGIpIHsKICAgICAgICB2YXIgdyA9ICt3aWR0aCwKICAgICAgICAgICAgayA9IHcgLyAoYlsxXVswXSAtIGJbMF1bMF0pLAogICAgICAgICAgICB4ID0gKHcgLSBrICogKGJbMV1bMF0gKyBiWzBdWzBdKSkgLyAyLAogICAgICAgICAgICB5ID0gLWsgKiBiWzBdWzFdOwogICAgICAgIHByb2plY3Rpb24uc2NhbGUoMTUwICogaykudHJhbnNsYXRlKFt4LCB5XSk7CiAgICAgIH0sIG9iamVjdCk7CiAgICB9CgogICAgZnVuY3Rpb24gZml0SGVpZ2h0JDEocHJvamVjdGlvbiwgaGVpZ2h0LCBvYmplY3QpIHsKICAgICAgcmV0dXJuIGZpdCQxKHByb2plY3Rpb24sIGZ1bmN0aW9uKGIpIHsKICAgICAgICB2YXIgaCA9ICtoZWlnaHQsCiAgICAgICAgICAgIGsgPSBoIC8gKGJbMV1bMV0gLSBiWzBdWzFdKSwKICAgICAgICAgICAgeCA9IC1rICogYlswXVswXSwKICAgICAgICAgICAgeSA9IChoIC0gayAqIChiWzFdWzFdICsgYlswXVsxXSkpIC8gMjsKICAgICAgICBwcm9qZWN0aW9uLnNjYWxlKDE1MCAqIGspLnRyYW5zbGF0ZShbeCwgeV0pOwogICAgICB9LCBvYmplY3QpOwogICAgfQoKICAgIHZhciBtYXhEZXB0aCQxID0gMTYsIC8vIG1heGltdW0gZGVwdGggb2Ygc3ViZGl2aXNpb24KICAgICAgICBjb3NNaW5EaXN0YW5jZSQxID0gY29zJDQoMzAgKiByYWRpYW5zJDEpOyAvLyBjb3MobWluaW11bSBhbmd1bGFyIGRpc3RhbmNlKQoKICAgIGZ1bmN0aW9uIHJlc2FtcGxlJDIocHJvamVjdCwgZGVsdGEyKSB7CiAgICAgIHJldHVybiArZGVsdGEyID8gcmVzYW1wbGUkMyhwcm9qZWN0LCBkZWx0YTIpIDogcmVzYW1wbGVOb25lJDEocHJvamVjdCk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVzYW1wbGVOb25lJDEocHJvamVjdCkgewogICAgICByZXR1cm4gdHJhbnNmb3JtZXIkNCh7CiAgICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICAgIHggPSBwcm9qZWN0KHgsIHkpOwogICAgICAgICAgdGhpcy5zdHJlYW0ucG9pbnQoeFswXSwgeFsxXSk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXNhbXBsZSQzKHByb2plY3QsIGRlbHRhMikgewoKICAgICAgZnVuY3Rpb24gcmVzYW1wbGVMaW5lVG8oeDAsIHkwLCBsYW1iZGEwLCBhMCwgYjAsIGMwLCB4MSwgeTEsIGxhbWJkYTEsIGExLCBiMSwgYzEsIGRlcHRoLCBzdHJlYW0pIHsKICAgICAgICB2YXIgZHggPSB4MSAtIHgwLAogICAgICAgICAgICBkeSA9IHkxIC0geTAsCiAgICAgICAgICAgIGQyID0gZHggKiBkeCArIGR5ICogZHk7CiAgICAgICAgaWYgKGQyID4gNCAqIGRlbHRhMiAmJiBkZXB0aC0tKSB7CiAgICAgICAgICB2YXIgYSA9IGEwICsgYTEsCiAgICAgICAgICAgICAgYiA9IGIwICsgYjEsCiAgICAgICAgICAgICAgYyA9IGMwICsgYzEsCiAgICAgICAgICAgICAgbSA9IHNxcnQkMyhhICogYSArIGIgKiBiICsgYyAqIGMpLAogICAgICAgICAgICAgIHBoaTIgPSBhc2luJDIoYyAvPSBtKSwKICAgICAgICAgICAgICBsYW1iZGEyID0gYWJzJDIoYWJzJDIoYykgLSAxKSA8IGVwc2lsb24kNyB8fCBhYnMkMihsYW1iZGEwIC0gbGFtYmRhMSkgPCBlcHNpbG9uJDcgPyAobGFtYmRhMCArIGxhbWJkYTEpIC8gMiA6IGF0YW4yJDIoYiwgYSksCiAgICAgICAgICAgICAgcCA9IHByb2plY3QobGFtYmRhMiwgcGhpMiksCiAgICAgICAgICAgICAgeDIgPSBwWzBdLAogICAgICAgICAgICAgIHkyID0gcFsxXSwKICAgICAgICAgICAgICBkeDIgPSB4MiAtIHgwLAogICAgICAgICAgICAgIGR5MiA9IHkyIC0geTAsCiAgICAgICAgICAgICAgZHogPSBkeSAqIGR4MiAtIGR4ICogZHkyOwogICAgICAgICAgaWYgKGR6ICogZHogLyBkMiA+IGRlbHRhMiAvLyBwZXJwZW5kaWN1bGFyIHByb2plY3RlZCBkaXN0YW5jZQogICAgICAgICAgICAgIHx8IGFicyQyKChkeCAqIGR4MiArIGR5ICogZHkyKSAvIGQyIC0gMC41KSA+IDAuMyAvLyBtaWRwb2ludCBjbG9zZSB0byBhbiBlbmQKICAgICAgICAgICAgICB8fCBhMCAqIGExICsgYjAgKiBiMSArIGMwICogYzEgPCBjb3NNaW5EaXN0YW5jZSQxKSB7IC8vIGFuZ3VsYXIgZGlzdGFuY2UKICAgICAgICAgICAgcmVzYW1wbGVMaW5lVG8oeDAsIHkwLCBsYW1iZGEwLCBhMCwgYjAsIGMwLCB4MiwgeTIsIGxhbWJkYTIsIGEgLz0gbSwgYiAvPSBtLCBjLCBkZXB0aCwgc3RyZWFtKTsKICAgICAgICAgICAgc3RyZWFtLnBvaW50KHgyLCB5Mik7CiAgICAgICAgICAgIHJlc2FtcGxlTGluZVRvKHgyLCB5MiwgbGFtYmRhMiwgYSwgYiwgYywgeDEsIHkxLCBsYW1iZGExLCBhMSwgYjEsIGMxLCBkZXB0aCwgc3RyZWFtKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHZhciBsYW1iZGEwMCwgeDAwLCB5MDAsIGEwMCwgYjAwLCBjMDAsIC8vIGZpcnN0IHBvaW50CiAgICAgICAgICAgIGxhbWJkYTAsIHgwLCB5MCwgYTAsIGIwLCBjMDsgLy8gcHJldmlvdXMgcG9pbnQKCiAgICAgICAgdmFyIHJlc2FtcGxlU3RyZWFtID0gewogICAgICAgICAgcG9pbnQ6IHBvaW50LAogICAgICAgICAgbGluZVN0YXJ0OiBsaW5lU3RhcnQsCiAgICAgICAgICBsaW5lRW5kOiBsaW5lRW5kLAogICAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsgc3RyZWFtLnBvbHlnb25TdGFydCgpOyByZXNhbXBsZVN0cmVhbS5saW5lU3RhcnQgPSByaW5nU3RhcnQ7IH0sCiAgICAgICAgICBwb2x5Z29uRW5kOiBmdW5jdGlvbigpIHsgc3RyZWFtLnBvbHlnb25FbmQoKTsgcmVzYW1wbGVTdHJlYW0ubGluZVN0YXJ0ID0gbGluZVN0YXJ0OyB9CiAgICAgICAgfTsKCiAgICAgICAgZnVuY3Rpb24gcG9pbnQoeCwgeSkgewogICAgICAgICAgeCA9IHByb2plY3QoeCwgeSk7CiAgICAgICAgICBzdHJlYW0ucG9pbnQoeFswXSwgeFsxXSk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBsaW5lU3RhcnQoKSB7CiAgICAgICAgICB4MCA9IE5hTjsKICAgICAgICAgIHJlc2FtcGxlU3RyZWFtLnBvaW50ID0gbGluZVBvaW50OwogICAgICAgICAgc3RyZWFtLmxpbmVTdGFydCgpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbGluZVBvaW50KGxhbWJkYSwgcGhpKSB7CiAgICAgICAgICB2YXIgYyA9IGNhcnRlc2lhbiQxKFtsYW1iZGEsIHBoaV0pLCBwID0gcHJvamVjdChsYW1iZGEsIHBoaSk7CiAgICAgICAgICByZXNhbXBsZUxpbmVUbyh4MCwgeTAsIGxhbWJkYTAsIGEwLCBiMCwgYzAsIHgwID0gcFswXSwgeTAgPSBwWzFdLCBsYW1iZGEwID0gbGFtYmRhLCBhMCA9IGNbMF0sIGIwID0gY1sxXSwgYzAgPSBjWzJdLCBtYXhEZXB0aCQxLCBzdHJlYW0pOwogICAgICAgICAgc3RyZWFtLnBvaW50KHgwLCB5MCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiBsaW5lRW5kKCkgewogICAgICAgICAgcmVzYW1wbGVTdHJlYW0ucG9pbnQgPSBwb2ludDsKICAgICAgICAgIHN0cmVhbS5saW5lRW5kKCk7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiByaW5nU3RhcnQoKSB7CiAgICAgICAgICBsaW5lU3RhcnQoKTsKICAgICAgICAgIHJlc2FtcGxlU3RyZWFtLnBvaW50ID0gcmluZ1BvaW50OwogICAgICAgICAgcmVzYW1wbGVTdHJlYW0ubGluZUVuZCA9IHJpbmdFbmQ7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiByaW5nUG9pbnQobGFtYmRhLCBwaGkpIHsKICAgICAgICAgIGxpbmVQb2ludChsYW1iZGEwMCA9IGxhbWJkYSwgcGhpKSwgeDAwID0geDAsIHkwMCA9IHkwLCBhMDAgPSBhMCwgYjAwID0gYjAsIGMwMCA9IGMwOwogICAgICAgICAgcmVzYW1wbGVTdHJlYW0ucG9pbnQgPSBsaW5lUG9pbnQ7CiAgICAgICAgfQoKICAgICAgICBmdW5jdGlvbiByaW5nRW5kKCkgewogICAgICAgICAgcmVzYW1wbGVMaW5lVG8oeDAsIHkwLCBsYW1iZGEwLCBhMCwgYjAsIGMwLCB4MDAsIHkwMCwgbGFtYmRhMDAsIGEwMCwgYjAwLCBjMDAsIG1heERlcHRoJDEsIHN0cmVhbSk7CiAgICAgICAgICByZXNhbXBsZVN0cmVhbS5saW5lRW5kID0gbGluZUVuZDsKICAgICAgICAgIGxpbmVFbmQoKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiByZXNhbXBsZVN0cmVhbTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgdHJhbnNmb3JtUmFkaWFucyQxID0gdHJhbnNmb3JtZXIkNCh7CiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdGhpcy5zdHJlYW0ucG9pbnQoeCAqIHJhZGlhbnMkMSwgeSAqIHJhZGlhbnMkMSk7CiAgICAgIH0KICAgIH0pOwoKICAgIGZ1bmN0aW9uIHRyYW5zZm9ybVJvdGF0ZSQxKHJvdGF0ZSkgewogICAgICByZXR1cm4gdHJhbnNmb3JtZXIkNCh7CiAgICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICAgIHZhciByID0gcm90YXRlKHgsIHkpOwogICAgICAgICAgcmV0dXJuIHRoaXMuc3RyZWFtLnBvaW50KHJbMF0sIHJbMV0pOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJvamVjdGlvbiQxKHByb2plY3QpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb25NdXRhdG9yJDEoZnVuY3Rpb24oKSB7IHJldHVybiBwcm9qZWN0OyB9KSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByb2plY3Rpb25NdXRhdG9yJDEocHJvamVjdEF0KSB7CiAgICAgIHZhciBwcm9qZWN0LAogICAgICAgICAgayA9IDE1MCwgLy8gc2NhbGUKICAgICAgICAgIHggPSA0ODAsIHkgPSAyNTAsIC8vIHRyYW5zbGF0ZQogICAgICAgICAgZHgsIGR5LCBsYW1iZGEgPSAwLCBwaGkgPSAwLCAvLyBjZW50ZXIKICAgICAgICAgIGRlbHRhTGFtYmRhID0gMCwgZGVsdGFQaGkgPSAwLCBkZWx0YUdhbW1hID0gMCwgcm90YXRlLCBwcm9qZWN0Um90YXRlLCAvLyByb3RhdGUKICAgICAgICAgIHRoZXRhID0gbnVsbCwgcHJlY2xpcCA9IGNsaXBBbnRpbWVyaWRpYW4kMSwgLy8gY2xpcCBhbmdsZQogICAgICAgICAgeDAgPSBudWxsLCB5MCwgeDEsIHkxLCBwb3N0Y2xpcCA9IGlkZW50aXR5JGUsIC8vIGNsaXAgZXh0ZW50CiAgICAgICAgICBkZWx0YTIgPSAwLjUsIHByb2plY3RSZXNhbXBsZSA9IHJlc2FtcGxlJDIocHJvamVjdFRyYW5zZm9ybSwgZGVsdGEyKSwgLy8gcHJlY2lzaW9uCiAgICAgICAgICBjYWNoZSwKICAgICAgICAgIGNhY2hlU3RyZWFtOwoKICAgICAgZnVuY3Rpb24gcHJvamVjdGlvbihwb2ludCkgewogICAgICAgIHBvaW50ID0gcHJvamVjdFJvdGF0ZShwb2ludFswXSAqIHJhZGlhbnMkMSwgcG9pbnRbMV0gKiByYWRpYW5zJDEpOwogICAgICAgIHJldHVybiBbcG9pbnRbMF0gKiBrICsgZHgsIGR5IC0gcG9pbnRbMV0gKiBrXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gaW52ZXJ0KHBvaW50KSB7CiAgICAgICAgcG9pbnQgPSBwcm9qZWN0Um90YXRlLmludmVydCgocG9pbnRbMF0gLSBkeCkgLyBrLCAoZHkgLSBwb2ludFsxXSkgLyBrKTsKICAgICAgICByZXR1cm4gcG9pbnQgJiYgW3BvaW50WzBdICogZGVncmVlcyQzLCBwb2ludFsxXSAqIGRlZ3JlZXMkM107CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHByb2plY3RUcmFuc2Zvcm0oeCwgeSkgewogICAgICAgIHJldHVybiB4ID0gcHJvamVjdCh4LCB5KSwgW3hbMF0gKiBrICsgZHgsIGR5IC0geFsxXSAqIGtdOwogICAgICB9CgogICAgICBwcm9qZWN0aW9uLnN0cmVhbSA9IGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHJldHVybiBjYWNoZSAmJiBjYWNoZVN0cmVhbSA9PT0gc3RyZWFtID8gY2FjaGUgOiBjYWNoZSA9IHRyYW5zZm9ybVJhZGlhbnMkMSh0cmFuc2Zvcm1Sb3RhdGUkMShyb3RhdGUpKHByZWNsaXAocHJvamVjdFJlc2FtcGxlKHBvc3RjbGlwKGNhY2hlU3RyZWFtID0gc3RyZWFtKSkpKSk7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLnByZWNsaXAgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocHJlY2xpcCA9IF8sIHRoZXRhID0gdW5kZWZpbmVkLCByZXNldCgpKSA6IHByZWNsaXA7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLnBvc3RjbGlwID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBvc3RjbGlwID0gXywgeDAgPSB5MCA9IHgxID0geTEgPSBudWxsLCByZXNldCgpKSA6IHBvc3RjbGlwOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5jbGlwQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocHJlY2xpcCA9ICtfID8gY2xpcENpcmNsZSQxKHRoZXRhID0gXyAqIHJhZGlhbnMkMSkgOiAodGhldGEgPSBudWxsLCBjbGlwQW50aW1lcmlkaWFuJDEpLCByZXNldCgpKSA6IHRoZXRhICogZGVncmVlcyQzOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5jbGlwRXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBvc3RjbGlwID0gXyA9PSBudWxsID8gKHgwID0geTAgPSB4MSA9IHkxID0gbnVsbCwgaWRlbnRpdHkkZSkgOiBjbGlwUmVjdGFuZ2xlJDEoeDAgPSArX1swXVswXSwgeTAgPSArX1swXVsxXSwgeDEgPSArX1sxXVswXSwgeTEgPSArX1sxXVsxXSksIHJlc2V0KCkpIDogeDAgPT0gbnVsbCA/IG51bGwgOiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uc2NhbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoayA9ICtfLCByZWNlbnRlcigpKSA6IGs7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLnRyYW5zbGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gK19bMF0sIHkgPSArX1sxXSwgcmVjZW50ZXIoKSkgOiBbeCwgeV07CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmNlbnRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChsYW1iZGEgPSBfWzBdICUgMzYwICogcmFkaWFucyQxLCBwaGkgPSBfWzFdICUgMzYwICogcmFkaWFucyQxLCByZWNlbnRlcigpKSA6IFtsYW1iZGEgKiBkZWdyZWVzJDMsIHBoaSAqIGRlZ3JlZXMkM107CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLnJvdGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkZWx0YUxhbWJkYSA9IF9bMF0gJSAzNjAgKiByYWRpYW5zJDEsIGRlbHRhUGhpID0gX1sxXSAlIDM2MCAqIHJhZGlhbnMkMSwgZGVsdGFHYW1tYSA9IF8ubGVuZ3RoID4gMiA/IF9bMl0gJSAzNjAgKiByYWRpYW5zJDEgOiAwLCByZWNlbnRlcigpKSA6IFtkZWx0YUxhbWJkYSAqIGRlZ3JlZXMkMywgZGVsdGFQaGkgKiBkZWdyZWVzJDMsIGRlbHRhR2FtbWEgKiBkZWdyZWVzJDNdOwogICAgICB9OwoKICAgICAgcHJvamVjdGlvbi5wcmVjaXNpb24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocHJvamVjdFJlc2FtcGxlID0gcmVzYW1wbGUkMihwcm9qZWN0VHJhbnNmb3JtLCBkZWx0YTIgPSBfICogXyksIHJlc2V0KCkpIDogc3FydCQzKGRlbHRhMik7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmZpdEV4dGVudCA9IGZ1bmN0aW9uKGV4dGVudCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEV4dGVudCQxKHByb2plY3Rpb24sIGV4dGVudCwgb2JqZWN0KTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uZml0U2l6ZSA9IGZ1bmN0aW9uKHNpemUsIG9iamVjdCkgewogICAgICAgIHJldHVybiBmaXRTaXplJDEocHJvamVjdGlvbiwgc2l6ZSwgb2JqZWN0KTsKICAgICAgfTsKCiAgICAgIHByb2plY3Rpb24uZml0V2lkdGggPSBmdW5jdGlvbih3aWR0aCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdFdpZHRoJDEocHJvamVjdGlvbiwgd2lkdGgsIG9iamVjdCk7CiAgICAgIH07CgogICAgICBwcm9qZWN0aW9uLmZpdEhlaWdodCA9IGZ1bmN0aW9uKGhlaWdodCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEhlaWdodCQxKHByb2plY3Rpb24sIGhlaWdodCwgb2JqZWN0KTsKICAgICAgfTsKCiAgICAgIGZ1bmN0aW9uIHJlY2VudGVyKCkgewogICAgICAgIHByb2plY3RSb3RhdGUgPSBjb21wb3NlJDEocm90YXRlID0gcm90YXRlUmFkaWFucyQxKGRlbHRhTGFtYmRhLCBkZWx0YVBoaSwgZGVsdGFHYW1tYSksIHByb2plY3QpOwogICAgICAgIHZhciBjZW50ZXIgPSBwcm9qZWN0KGxhbWJkYSwgcGhpKTsKICAgICAgICBkeCA9IHggLSBjZW50ZXJbMF0gKiBrOwogICAgICAgIGR5ID0geSArIGNlbnRlclsxXSAqIGs7CiAgICAgICAgcmV0dXJuIHJlc2V0KCk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHJlc2V0KCkgewogICAgICAgIGNhY2hlID0gY2FjaGVTdHJlYW0gPSBudWxsOwogICAgICAgIHJldHVybiBwcm9qZWN0aW9uOwogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcHJvamVjdCA9IHByb2plY3RBdC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHByb2plY3Rpb24uaW52ZXJ0ID0gcHJvamVjdC5pbnZlcnQgJiYgaW52ZXJ0OwogICAgICAgIHJldHVybiByZWNlbnRlcigpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljUHJvamVjdGlvbiQxKHByb2plY3RBdCkgewogICAgICB2YXIgcGhpMCA9IDAsCiAgICAgICAgICBwaGkxID0gcGkkOCAvIDMsCiAgICAgICAgICBtID0gcHJvamVjdGlvbk11dGF0b3IkMShwcm9qZWN0QXQpLAogICAgICAgICAgcCA9IG0ocGhpMCwgcGhpMSk7CgogICAgICBwLnBhcmFsbGVscyA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IG0ocGhpMCA9IF9bMF0gKiByYWRpYW5zJDEsIHBoaTEgPSBfWzFdICogcmFkaWFucyQxKSA6IFtwaGkwICogZGVncmVlcyQzLCBwaGkxICogZGVncmVlcyQzXTsKICAgICAgfTsKCiAgICAgIHJldHVybiBwOwogICAgfQoKICAgIGZ1bmN0aW9uIGN5bGluZHJpY2FsRXF1YWxBcmVhUmF3JDEocGhpMCkgewogICAgICB2YXIgY29zUGhpMCA9IGNvcyQ0KHBoaTApOwoKICAgICAgZnVuY3Rpb24gZm9yd2FyZChsYW1iZGEsIHBoaSkgewogICAgICAgIHJldHVybiBbbGFtYmRhICogY29zUGhpMCwgc2luJDQocGhpKSAvIGNvc1BoaTBdOwogICAgICB9CgogICAgICBmb3J3YXJkLmludmVydCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICByZXR1cm4gW3ggLyBjb3NQaGkwLCBhc2luJDIoeSAqIGNvc1BoaTApXTsKICAgICAgfTsKCiAgICAgIHJldHVybiBmb3J3YXJkOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljRXF1YWxBcmVhUmF3JDEoeTAsIHkxKSB7CiAgICAgIHZhciBzeTAgPSBzaW4kNCh5MCksIG4gPSAoc3kwICsgc2luJDQoeTEpKSAvIDI7CgogICAgICAvLyBBcmUgdGhlIHBhcmFsbGVscyBzeW1tZXRyaWNhbCBhcm91bmQgdGhlIEVxdWF0b3I/CiAgICAgIGlmIChhYnMkMihuKSA8IGVwc2lsb24kNykgcmV0dXJuIGN5bGluZHJpY2FsRXF1YWxBcmVhUmF3JDEoeTApOwoKICAgICAgdmFyIGMgPSAxICsgc3kwICogKDIgKiBuIC0gc3kwKSwgcjAgPSBzcXJ0JDMoYykgLyBuOwoKICAgICAgZnVuY3Rpb24gcHJvamVjdCh4LCB5KSB7CiAgICAgICAgdmFyIHIgPSBzcXJ0JDMoYyAtIDIgKiBuICogc2luJDQoeSkpIC8gbjsKICAgICAgICByZXR1cm4gW3IgKiBzaW4kNCh4ICo9IG4pLCByMCAtIHIgKiBjb3MkNCh4KV07CiAgICAgIH0KCiAgICAgIHByb2plY3QuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciByMHkgPSByMCAtIHk7CiAgICAgICAgcmV0dXJuIFthdGFuMiQyKHgsIGFicyQyKHIweSkpIC8gbiAqIHNpZ24kMihyMHkpLCBhc2luJDIoKGMgLSAoeCAqIHggKyByMHkgKiByMHkpICogbiAqIG4pIC8gKDIgKiBuKSldOwogICAgICB9OwoKICAgICAgcmV0dXJuIHByb2plY3Q7CiAgICB9CgogICAgZnVuY3Rpb24gY29uaWNFcXVhbEFyZWEkMSgpIHsKICAgICAgcmV0dXJuIGNvbmljUHJvamVjdGlvbiQxKGNvbmljRXF1YWxBcmVhUmF3JDEpCiAgICAgICAgICAuc2NhbGUoMTU1LjQyNCkKICAgICAgICAgIC5jZW50ZXIoWzAsIDMzLjY0NDJdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhbGJlcnMkMSgpIHsKICAgICAgcmV0dXJuIGNvbmljRXF1YWxBcmVhJDEoKQogICAgICAgICAgLnBhcmFsbGVscyhbMjkuNSwgNDUuNV0pCiAgICAgICAgICAuc2NhbGUoMTA3MCkKICAgICAgICAgIC50cmFuc2xhdGUoWzQ4MCwgMjUwXSkKICAgICAgICAgIC5yb3RhdGUoWzk2LCAwXSkKICAgICAgICAgIC5jZW50ZXIoWy0wLjYsIDM4LjddKTsKICAgIH0KCiAgICAvLyBUaGUgcHJvamVjdGlvbnMgbXVzdCBoYXZlIG11dHVhbGx5IGV4Y2x1c2l2ZSBjbGlwIHJlZ2lvbnMgb24gdGhlIHNwaGVyZSwKICAgIC8vIGFzIHRoaXMgd2lsbCBhdm9pZCBlbWl0dGluZyBpbnRlcmxlYXZpbmcgbGluZXMgYW5kIHBvbHlnb25zLgogICAgZnVuY3Rpb24gbXVsdGlwbGV4JDEoc3RyZWFtcykgewogICAgICB2YXIgbiA9IHN0cmVhbXMubGVuZ3RoOwogICAgICByZXR1cm4gewogICAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnBvaW50KHgsIHkpOyB9LAogICAgICAgIHNwaGVyZTogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnNwaGVyZSgpOyB9LAogICAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLmxpbmVTdGFydCgpOyB9LAogICAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgeyB2YXIgaSA9IC0xOyB3aGlsZSAoKytpIDwgbikgc3RyZWFtc1tpXS5saW5lRW5kKCk7IH0sCiAgICAgICAgcG9seWdvblN0YXJ0OiBmdW5jdGlvbigpIHsgdmFyIGkgPSAtMTsgd2hpbGUgKCsraSA8IG4pIHN0cmVhbXNbaV0ucG9seWdvblN0YXJ0KCk7IH0sCiAgICAgICAgcG9seWdvbkVuZDogZnVuY3Rpb24oKSB7IHZhciBpID0gLTE7IHdoaWxlICgrK2kgPCBuKSBzdHJlYW1zW2ldLnBvbHlnb25FbmQoKTsgfQogICAgICB9OwogICAgfQoKICAgIC8vIEEgY29tcG9zaXRlIHByb2plY3Rpb24gZm9yIHRoZSBVbml0ZWQgU3RhdGVzLCBjb25maWd1cmVkIGJ5IGRlZmF1bHQgZm9yCiAgICAvLyA5NjDDlzUwMC4gVGhlIHByb2plY3Rpb24gYWxzbyB3b3JrcyBxdWl0ZSB3ZWxsIGF0IDk2MMOXNjAwIGlmIHlvdSBjaGFuZ2UgdGhlCiAgICAvLyBzY2FsZSB0byAxMjg1IGFuZCBhZGp1c3QgdGhlIHRyYW5zbGF0ZSBhY2NvcmRpbmdseS4gVGhlIHNldCBvZiBzdGFuZGFyZAogICAgLy8gcGFyYWxsZWxzIGZvciBlYWNoIHJlZ2lvbiBjb21lcyBmcm9tIFVTR1MsIHdoaWNoIGlzIHB1Ymxpc2hlZCBoZXJlOgogICAgLy8gaHR0cDovL2Vnc2MudXNncy5nb3YvaXNiL3B1YnMvTWFwUHJvamVjdGlvbnMvcHJvamVjdGlvbnMuaHRtbCNhbGJlcnMKICAgIGZ1bmN0aW9uIGFsYmVyc1VzYSQxKCkgewogICAgICB2YXIgY2FjaGUsCiAgICAgICAgICBjYWNoZVN0cmVhbSwKICAgICAgICAgIGxvd2VyNDggPSBhbGJlcnMkMSgpLCBsb3dlcjQ4UG9pbnQsCiAgICAgICAgICBhbGFza2EgPSBjb25pY0VxdWFsQXJlYSQxKCkucm90YXRlKFsxNTQsIDBdKS5jZW50ZXIoWy0yLCA1OC41XSkucGFyYWxsZWxzKFs1NSwgNjVdKSwgYWxhc2thUG9pbnQsIC8vIEVQU0c6MzMzOAogICAgICAgICAgaGF3YWlpID0gY29uaWNFcXVhbEFyZWEkMSgpLnJvdGF0ZShbMTU3LCAwXSkuY2VudGVyKFstMywgMTkuOV0pLnBhcmFsbGVscyhbOCwgMThdKSwgaGF3YWlpUG9pbnQsIC8vIEVTUkk6MTAyMDA3CiAgICAgICAgICBwb2ludCwgcG9pbnRTdHJlYW0gPSB7cG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsgcG9pbnQgPSBbeCwgeV07IH19OwoKICAgICAgZnVuY3Rpb24gYWxiZXJzVXNhKGNvb3JkaW5hdGVzKSB7CiAgICAgICAgdmFyIHggPSBjb29yZGluYXRlc1swXSwgeSA9IGNvb3JkaW5hdGVzWzFdOwogICAgICAgIHJldHVybiBwb2ludCA9IG51bGwsCiAgICAgICAgICAgIChsb3dlcjQ4UG9pbnQucG9pbnQoeCwgeSksIHBvaW50KQogICAgICAgICAgICB8fCAoYWxhc2thUG9pbnQucG9pbnQoeCwgeSksIHBvaW50KQogICAgICAgICAgICB8fCAoaGF3YWlpUG9pbnQucG9pbnQoeCwgeSksIHBvaW50KTsKICAgICAgfQoKICAgICAgYWxiZXJzVXNhLmludmVydCA9IGZ1bmN0aW9uKGNvb3JkaW5hdGVzKSB7CiAgICAgICAgdmFyIGsgPSBsb3dlcjQ4LnNjYWxlKCksCiAgICAgICAgICAgIHQgPSBsb3dlcjQ4LnRyYW5zbGF0ZSgpLAogICAgICAgICAgICB4ID0gKGNvb3JkaW5hdGVzWzBdIC0gdFswXSkgLyBrLAogICAgICAgICAgICB5ID0gKGNvb3JkaW5hdGVzWzFdIC0gdFsxXSkgLyBrOwogICAgICAgIHJldHVybiAoeSA+PSAwLjEyMCAmJiB5IDwgMC4yMzQgJiYgeCA+PSAtMC40MjUgJiYgeCA8IC0wLjIxNCA/IGFsYXNrYQogICAgICAgICAgICA6IHkgPj0gMC4xNjYgJiYgeSA8IDAuMjM0ICYmIHggPj0gLTAuMjE0ICYmIHggPCAtMC4xMTUgPyBoYXdhaWkKICAgICAgICAgICAgOiBsb3dlcjQ4KS5pbnZlcnQoY29vcmRpbmF0ZXMpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLnN0cmVhbSA9IGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgIHJldHVybiBjYWNoZSAmJiBjYWNoZVN0cmVhbSA9PT0gc3RyZWFtID8gY2FjaGUgOiBjYWNoZSA9IG11bHRpcGxleCQxKFtsb3dlcjQ4LnN0cmVhbShjYWNoZVN0cmVhbSA9IHN0cmVhbSksIGFsYXNrYS5zdHJlYW0oc3RyZWFtKSwgaGF3YWlpLnN0cmVhbShzdHJlYW0pXSk7CiAgICAgIH07CgogICAgICBhbGJlcnNVc2EucHJlY2lzaW9uID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIGxvd2VyNDgucHJlY2lzaW9uKCk7CiAgICAgICAgbG93ZXI0OC5wcmVjaXNpb24oXyksIGFsYXNrYS5wcmVjaXNpb24oXyksIGhhd2FpaS5wcmVjaXNpb24oXyk7CiAgICAgICAgcmV0dXJuIHJlc2V0KCk7CiAgICAgIH07CgogICAgICBhbGJlcnNVc2Euc2NhbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gbG93ZXI0OC5zY2FsZSgpOwogICAgICAgIGxvd2VyNDguc2NhbGUoXyksIGFsYXNrYS5zY2FsZShfICogMC4zNSksIGhhd2FpaS5zY2FsZShfKTsKICAgICAgICByZXR1cm4gYWxiZXJzVXNhLnRyYW5zbGF0ZShsb3dlcjQ4LnRyYW5zbGF0ZSgpKTsKICAgICAgfTsKCiAgICAgIGFsYmVyc1VzYS50cmFuc2xhdGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gbG93ZXI0OC50cmFuc2xhdGUoKTsKICAgICAgICB2YXIgayA9IGxvd2VyNDguc2NhbGUoKSwgeCA9ICtfWzBdLCB5ID0gK19bMV07CgogICAgICAgIGxvd2VyNDhQb2ludCA9IGxvd2VyNDgKICAgICAgICAgICAgLnRyYW5zbGF0ZShfKQogICAgICAgICAgICAuY2xpcEV4dGVudChbW3ggLSAwLjQ1NSAqIGssIHkgLSAwLjIzOCAqIGtdLCBbeCArIDAuNDU1ICogaywgeSArIDAuMjM4ICoga11dKQogICAgICAgICAgICAuc3RyZWFtKHBvaW50U3RyZWFtKTsKCiAgICAgICAgYWxhc2thUG9pbnQgPSBhbGFza2EKICAgICAgICAgICAgLnRyYW5zbGF0ZShbeCAtIDAuMzA3ICogaywgeSArIDAuMjAxICoga10pCiAgICAgICAgICAgIC5jbGlwRXh0ZW50KFtbeCAtIDAuNDI1ICogayArIGVwc2lsb24kNywgeSArIDAuMTIwICogayArIGVwc2lsb24kN10sIFt4IC0gMC4yMTQgKiBrIC0gZXBzaWxvbiQ3LCB5ICsgMC4yMzQgKiBrIC0gZXBzaWxvbiQ3XV0pCiAgICAgICAgICAgIC5zdHJlYW0ocG9pbnRTdHJlYW0pOwoKICAgICAgICBoYXdhaWlQb2ludCA9IGhhd2FpaQogICAgICAgICAgICAudHJhbnNsYXRlKFt4IC0gMC4yMDUgKiBrLCB5ICsgMC4yMTIgKiBrXSkKICAgICAgICAgICAgLmNsaXBFeHRlbnQoW1t4IC0gMC4yMTQgKiBrICsgZXBzaWxvbiQ3LCB5ICsgMC4xNjYgKiBrICsgZXBzaWxvbiQ3XSwgW3ggLSAwLjExNSAqIGsgLSBlcHNpbG9uJDcsIHkgKyAwLjIzNCAqIGsgLSBlcHNpbG9uJDddXSkKICAgICAgICAgICAgLnN0cmVhbShwb2ludFN0cmVhbSk7CgogICAgICAgIHJldHVybiByZXNldCgpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLmZpdEV4dGVudCA9IGZ1bmN0aW9uKGV4dGVudCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEV4dGVudCQxKGFsYmVyc1VzYSwgZXh0ZW50LCBvYmplY3QpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLmZpdFNpemUgPSBmdW5jdGlvbihzaXplLCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0U2l6ZSQxKGFsYmVyc1VzYSwgc2l6ZSwgb2JqZWN0KTsKICAgICAgfTsKCiAgICAgIGFsYmVyc1VzYS5maXRXaWR0aCA9IGZ1bmN0aW9uKHdpZHRoLCBvYmplY3QpIHsKICAgICAgICByZXR1cm4gZml0V2lkdGgkMShhbGJlcnNVc2EsIHdpZHRoLCBvYmplY3QpOwogICAgICB9OwoKICAgICAgYWxiZXJzVXNhLmZpdEhlaWdodCA9IGZ1bmN0aW9uKGhlaWdodCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGZpdEhlaWdodCQxKGFsYmVyc1VzYSwgaGVpZ2h0LCBvYmplY3QpOwogICAgICB9OwoKICAgICAgZnVuY3Rpb24gcmVzZXQoKSB7CiAgICAgICAgY2FjaGUgPSBjYWNoZVN0cmVhbSA9IG51bGw7CiAgICAgICAgcmV0dXJuIGFsYmVyc1VzYTsKICAgICAgfQoKICAgICAgcmV0dXJuIGFsYmVyc1VzYS5zY2FsZSgxMDcwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhemltdXRoYWxSYXckMShzY2FsZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciBjeCA9IGNvcyQ0KHgpLAogICAgICAgICAgICBjeSA9IGNvcyQ0KHkpLAogICAgICAgICAgICBrID0gc2NhbGUoY3ggKiBjeSk7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgIGsgKiBjeSAqIHNpbiQ0KHgpLAogICAgICAgICAgayAqIHNpbiQ0KHkpCiAgICAgICAgXTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGF6aW11dGhhbEludmVydCQxKGFuZ2xlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdmFyIHogPSBzcXJ0JDMoeCAqIHggKyB5ICogeSksCiAgICAgICAgICAgIGMgPSBhbmdsZSh6KSwKICAgICAgICAgICAgc2MgPSBzaW4kNChjKSwKICAgICAgICAgICAgY2MgPSBjb3MkNChjKTsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgYXRhbjIkMih4ICogc2MsIHogKiBjYyksCiAgICAgICAgICBhc2luJDIoeiAmJiB5ICogc2MgLyB6KQogICAgICAgIF07CiAgICAgIH0KICAgIH0KCiAgICB2YXIgYXppbXV0aGFsRXF1YWxBcmVhUmF3JDEgPSBhemltdXRoYWxSYXckMShmdW5jdGlvbihjeGN5KSB7CiAgICAgIHJldHVybiBzcXJ0JDMoMiAvICgxICsgY3hjeSkpOwogICAgfSk7CgogICAgYXppbXV0aGFsRXF1YWxBcmVhUmF3JDEuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0JDEoZnVuY3Rpb24oeikgewogICAgICByZXR1cm4gMiAqIGFzaW4kMih6IC8gMik7CiAgICB9KTsKCiAgICBmdW5jdGlvbiBhemltdXRoYWxFcXVhbEFyZWEkMSgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24kMShhemltdXRoYWxFcXVhbEFyZWFSYXckMSkKICAgICAgICAgIC5zY2FsZSgxMjQuNzUpCiAgICAgICAgICAuY2xpcEFuZ2xlKDE4MCAtIDFlLTMpOwogICAgfQoKICAgIHZhciBhemltdXRoYWxFcXVpZGlzdGFudFJhdyQxID0gYXppbXV0aGFsUmF3JDEoZnVuY3Rpb24oYykgewogICAgICByZXR1cm4gKGMgPSBhY29zJDIoYykpICYmIGMgLyBzaW4kNChjKTsKICAgIH0pOwoKICAgIGF6aW11dGhhbEVxdWlkaXN0YW50UmF3JDEuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0JDEoZnVuY3Rpb24oeikgewogICAgICByZXR1cm4gejsKICAgIH0pOwoKICAgIGZ1bmN0aW9uIGF6aW11dGhhbEVxdWlkaXN0YW50JDEoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uJDEoYXppbXV0aGFsRXF1aWRpc3RhbnRSYXckMSkKICAgICAgICAgIC5zY2FsZSg3OS40MTg4KQogICAgICAgICAgLmNsaXBBbmdsZSgxODAgLSAxZS0zKTsKICAgIH0KCiAgICBmdW5jdGlvbiBtZXJjYXRvclJhdyQxKGxhbWJkYSwgcGhpKSB7CiAgICAgIHJldHVybiBbbGFtYmRhLCBsb2ckMih0YW4kMSgoaGFsZlBpJDYgKyBwaGkpIC8gMikpXTsKICAgIH0KCiAgICBtZXJjYXRvclJhdyQxLmludmVydCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgcmV0dXJuIFt4LCAyICogYXRhbiQxKGV4cCQxKHkpKSAtIGhhbGZQaSQ2XTsKICAgIH07CgogICAgZnVuY3Rpb24gbWVyY2F0b3IkMSgpIHsKICAgICAgcmV0dXJuIG1lcmNhdG9yUHJvamVjdGlvbiQxKG1lcmNhdG9yUmF3JDEpCiAgICAgICAgICAuc2NhbGUoOTYxIC8gdGF1JDgpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lcmNhdG9yUHJvamVjdGlvbiQxKHByb2plY3QpIHsKICAgICAgdmFyIG0gPSBwcm9qZWN0aW9uJDEocHJvamVjdCksCiAgICAgICAgICBjZW50ZXIgPSBtLmNlbnRlciwKICAgICAgICAgIHNjYWxlID0gbS5zY2FsZSwKICAgICAgICAgIHRyYW5zbGF0ZSA9IG0udHJhbnNsYXRlLAogICAgICAgICAgY2xpcEV4dGVudCA9IG0uY2xpcEV4dGVudCwKICAgICAgICAgIHgwID0gbnVsbCwgeTAsIHgxLCB5MTsgLy8gY2xpcCBleHRlbnQKCiAgICAgIG0uc2NhbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2NhbGUoXyksIHJlY2xpcCgpKSA6IHNjYWxlKCk7CiAgICAgIH07CgogICAgICBtLnRyYW5zbGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh0cmFuc2xhdGUoXyksIHJlY2xpcCgpKSA6IHRyYW5zbGF0ZSgpOwogICAgICB9OwoKICAgICAgbS5jZW50ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY2VudGVyKF8pLCByZWNsaXAoKSkgOiBjZW50ZXIoKTsKICAgICAgfTsKCiAgICAgIG0uY2xpcEV4dGVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICgoXyA9PSBudWxsID8geDAgPSB5MCA9IHgxID0geTEgPSBudWxsIDogKHgwID0gK19bMF1bMF0sIHkwID0gK19bMF1bMV0sIHgxID0gK19bMV1bMF0sIHkxID0gK19bMV1bMV0pKSwgcmVjbGlwKCkpIDogeDAgPT0gbnVsbCA/IG51bGwgOiBbW3gwLCB5MF0sIFt4MSwgeTFdXTsKICAgICAgfTsKCiAgICAgIGZ1bmN0aW9uIHJlY2xpcCgpIHsKICAgICAgICB2YXIgayA9IHBpJDggKiBzY2FsZSgpLAogICAgICAgICAgICB0ID0gbShyb3RhdGlvbiQxKG0ucm90YXRlKCkpLmludmVydChbMCwgMF0pKTsKICAgICAgICByZXR1cm4gY2xpcEV4dGVudCh4MCA9PSBudWxsCiAgICAgICAgICAgID8gW1t0WzBdIC0gaywgdFsxXSAtIGtdLCBbdFswXSArIGssIHRbMV0gKyBrXV0gOiBwcm9qZWN0ID09PSBtZXJjYXRvclJhdyQxCiAgICAgICAgICAgID8gW1tNYXRoLm1heCh0WzBdIC0gaywgeDApLCB5MF0sIFtNYXRoLm1pbih0WzBdICsgaywgeDEpLCB5MV1dCiAgICAgICAgICAgIDogW1t4MCwgTWF0aC5tYXgodFsxXSAtIGssIHkwKV0sIFt4MSwgTWF0aC5taW4odFsxXSArIGssIHkxKV1dKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHJlY2xpcCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRhbnkkMSh5KSB7CiAgICAgIHJldHVybiB0YW4kMSgoaGFsZlBpJDYgKyB5KSAvIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljQ29uZm9ybWFsUmF3JDEoeTAsIHkxKSB7CiAgICAgIHZhciBjeTAgPSBjb3MkNCh5MCksCiAgICAgICAgICBuID0geTAgPT09IHkxID8gc2luJDQoeTApIDogbG9nJDIoY3kwIC8gY29zJDQoeTEpKSAvIGxvZyQyKHRhbnkkMSh5MSkgLyB0YW55JDEoeTApKSwKICAgICAgICAgIGYgPSBjeTAgKiBwb3ckMih0YW55JDEoeTApLCBuKSAvIG47CgogICAgICBpZiAoIW4pIHJldHVybiBtZXJjYXRvclJhdyQxOwoKICAgICAgZnVuY3Rpb24gcHJvamVjdCh4LCB5KSB7CiAgICAgICAgaWYgKGYgPiAwKSB7IGlmICh5IDwgLWhhbGZQaSQ2ICsgZXBzaWxvbiQ3KSB5ID0gLWhhbGZQaSQ2ICsgZXBzaWxvbiQ3OyB9CiAgICAgICAgZWxzZSB7IGlmICh5ID4gaGFsZlBpJDYgLSBlcHNpbG9uJDcpIHkgPSBoYWxmUGkkNiAtIGVwc2lsb24kNzsgfQogICAgICAgIHZhciByID0gZiAvIHBvdyQyKHRhbnkkMSh5KSwgbik7CiAgICAgICAgcmV0dXJuIFtyICogc2luJDQobiAqIHgpLCBmIC0gciAqIGNvcyQ0KG4gKiB4KV07CiAgICAgIH0KCiAgICAgIHByb2plY3QuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHZhciBmeSA9IGYgLSB5LCByID0gc2lnbiQyKG4pICogc3FydCQzKHggKiB4ICsgZnkgKiBmeSk7CiAgICAgICAgcmV0dXJuIFthdGFuMiQyKHgsIGFicyQyKGZ5KSkgLyBuICogc2lnbiQyKGZ5KSwgMiAqIGF0YW4kMShwb3ckMihmIC8gciwgMSAvIG4pKSAtIGhhbGZQaSQ2XTsKICAgICAgfTsKCiAgICAgIHJldHVybiBwcm9qZWN0OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbmljQ29uZm9ybWFsJDEoKSB7CiAgICAgIHJldHVybiBjb25pY1Byb2plY3Rpb24kMShjb25pY0NvbmZvcm1hbFJhdyQxKQogICAgICAgICAgLnNjYWxlKDEwOS41KQogICAgICAgICAgLnBhcmFsbGVscyhbMzAsIDMwXSk7CiAgICB9CgogICAgZnVuY3Rpb24gZXF1aXJlY3Rhbmd1bGFyUmF3JDEobGFtYmRhLCBwaGkpIHsKICAgICAgcmV0dXJuIFtsYW1iZGEsIHBoaV07CiAgICB9CgogICAgZXF1aXJlY3Rhbmd1bGFyUmF3JDEuaW52ZXJ0ID0gZXF1aXJlY3Rhbmd1bGFyUmF3JDE7CgogICAgZnVuY3Rpb24gZXF1aXJlY3Rhbmd1bGFyJDEoKSB7CiAgICAgIHJldHVybiBwcm9qZWN0aW9uJDEoZXF1aXJlY3Rhbmd1bGFyUmF3JDEpCiAgICAgICAgICAuc2NhbGUoMTUyLjYzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25pY0VxdWlkaXN0YW50UmF3JDEoeTAsIHkxKSB7CiAgICAgIHZhciBjeTAgPSBjb3MkNCh5MCksCiAgICAgICAgICBuID0geTAgPT09IHkxID8gc2luJDQoeTApIDogKGN5MCAtIGNvcyQ0KHkxKSkgLyAoeTEgLSB5MCksCiAgICAgICAgICBnID0gY3kwIC8gbiArIHkwOwoKICAgICAgaWYgKGFicyQyKG4pIDwgZXBzaWxvbiQ3KSByZXR1cm4gZXF1aXJlY3Rhbmd1bGFyUmF3JDE7CgogICAgICBmdW5jdGlvbiBwcm9qZWN0KHgsIHkpIHsKICAgICAgICB2YXIgZ3kgPSBnIC0geSwgbnggPSBuICogeDsKICAgICAgICByZXR1cm4gW2d5ICogc2luJDQobngpLCBnIC0gZ3kgKiBjb3MkNChueCldOwogICAgICB9CgogICAgICBwcm9qZWN0LmludmVydCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB2YXIgZ3kgPSBnIC0geTsKICAgICAgICByZXR1cm4gW2F0YW4yJDIoeCwgYWJzJDIoZ3kpKSAvIG4gKiBzaWduJDIoZ3kpLCBnIC0gc2lnbiQyKG4pICogc3FydCQzKHggKiB4ICsgZ3kgKiBneSldOwogICAgICB9OwoKICAgICAgcmV0dXJuIHByb2plY3Q7CiAgICB9CgogICAgZnVuY3Rpb24gY29uaWNFcXVpZGlzdGFudCQxKCkgewogICAgICByZXR1cm4gY29uaWNQcm9qZWN0aW9uJDEoY29uaWNFcXVpZGlzdGFudFJhdyQxKQogICAgICAgICAgLnNjYWxlKDEzMS4xNTQpCiAgICAgICAgICAuY2VudGVyKFswLCAxMy45Mzg5XSk7CiAgICB9CgogICAgZnVuY3Rpb24gZ25vbW9uaWNSYXckMSh4LCB5KSB7CiAgICAgIHZhciBjeSA9IGNvcyQ0KHkpLCBrID0gY29zJDQoeCkgKiBjeTsKICAgICAgcmV0dXJuIFtjeSAqIHNpbiQ0KHgpIC8gaywgc2luJDQoeSkgLyBrXTsKICAgIH0KCiAgICBnbm9tb25pY1JhdyQxLmludmVydCA9IGF6aW11dGhhbEludmVydCQxKGF0YW4kMSk7CgogICAgZnVuY3Rpb24gZ25vbW9uaWMkMSgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24kMShnbm9tb25pY1JhdyQxKQogICAgICAgICAgLnNjYWxlKDE0NC4wNDkpCiAgICAgICAgICAuY2xpcEFuZ2xlKDYwKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzY2FsZVRyYW5zbGF0ZSQxKGt4LCBreSwgdHgsIHR5KSB7CiAgICAgIHJldHVybiBreCA9PT0gMSAmJiBreSA9PT0gMSAmJiB0eCA9PT0gMCAmJiB0eSA9PT0gMCA/IGlkZW50aXR5JGUgOiB0cmFuc2Zvcm1lciQ0KHsKICAgICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgICAgdGhpcy5zdHJlYW0ucG9pbnQoeCAqIGt4ICsgdHgsIHkgKiBreSArIHR5KTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JGYoKSB7CiAgICAgIHZhciBrID0gMSwgdHggPSAwLCB0eSA9IDAsIHN4ID0gMSwgc3kgPSAxLCB0cmFuc2Zvcm0gPSBpZGVudGl0eSRlLCAvLyBzY2FsZSwgdHJhbnNsYXRlIGFuZCByZWZsZWN0CiAgICAgICAgICB4MCA9IG51bGwsIHkwLCB4MSwgeTEsIC8vIGNsaXAgZXh0ZW50CiAgICAgICAgICBwb3N0Y2xpcCA9IGlkZW50aXR5JGUsCiAgICAgICAgICBjYWNoZSwKICAgICAgICAgIGNhY2hlU3RyZWFtLAogICAgICAgICAgcHJvamVjdGlvbjsKCiAgICAgIGZ1bmN0aW9uIHJlc2V0KCkgewogICAgICAgIGNhY2hlID0gY2FjaGVTdHJlYW0gPSBudWxsOwogICAgICAgIHJldHVybiBwcm9qZWN0aW9uOwogICAgICB9CgogICAgICByZXR1cm4gcHJvamVjdGlvbiA9IHsKICAgICAgICBzdHJlYW06IGZ1bmN0aW9uKHN0cmVhbSkgewogICAgICAgICAgcmV0dXJuIGNhY2hlICYmIGNhY2hlU3RyZWFtID09PSBzdHJlYW0gPyBjYWNoZSA6IGNhY2hlID0gdHJhbnNmb3JtKHBvc3RjbGlwKGNhY2hlU3RyZWFtID0gc3RyZWFtKSk7CiAgICAgICAgfSwKICAgICAgICBwb3N0Y2xpcDogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocG9zdGNsaXAgPSBfLCB4MCA9IHkwID0geDEgPSB5MSA9IG51bGwsIHJlc2V0KCkpIDogcG9zdGNsaXA7CiAgICAgICAgfSwKICAgICAgICBjbGlwRXh0ZW50OiBmdW5jdGlvbihfKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwb3N0Y2xpcCA9IF8gPT0gbnVsbCA/ICh4MCA9IHkwID0geDEgPSB5MSA9IG51bGwsIGlkZW50aXR5JGUpIDogY2xpcFJlY3RhbmdsZSQxKHgwID0gK19bMF1bMF0sIHkwID0gK19bMF1bMV0sIHgxID0gK19bMV1bMF0sIHkxID0gK19bMV1bMV0pLCByZXNldCgpKSA6IHgwID09IG51bGwgPyBudWxsIDogW1t4MCwgeTBdLCBbeDEsIHkxXV07CiAgICAgICAgfSwKICAgICAgICBzY2FsZTogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodHJhbnNmb3JtID0gc2NhbGVUcmFuc2xhdGUkMSgoayA9ICtfKSAqIHN4LCBrICogc3ksIHR4LCB0eSksIHJlc2V0KCkpIDogazsKICAgICAgICB9LAogICAgICAgIHRyYW5zbGF0ZTogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodHJhbnNmb3JtID0gc2NhbGVUcmFuc2xhdGUkMShrICogc3gsIGsgKiBzeSwgdHggPSArX1swXSwgdHkgPSArX1sxXSksIHJlc2V0KCkpIDogW3R4LCB0eV07CiAgICAgICAgfSwKICAgICAgICByZWZsZWN0WDogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodHJhbnNmb3JtID0gc2NhbGVUcmFuc2xhdGUkMShrICogKHN4ID0gXyA/IC0xIDogMSksIGsgKiBzeSwgdHgsIHR5KSwgcmVzZXQoKSkgOiBzeCA8IDA7CiAgICAgICAgfSwKICAgICAgICByZWZsZWN0WTogZnVuY3Rpb24oXykgewogICAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodHJhbnNmb3JtID0gc2NhbGVUcmFuc2xhdGUkMShrICogc3gsIGsgKiAoc3kgPSBfID8gLTEgOiAxKSwgdHgsIHR5KSwgcmVzZXQoKSkgOiBzeSA8IDA7CiAgICAgICAgfSwKICAgICAgICBmaXRFeHRlbnQ6IGZ1bmN0aW9uKGV4dGVudCwgb2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gZml0RXh0ZW50JDEocHJvamVjdGlvbiwgZXh0ZW50LCBvYmplY3QpOwogICAgICAgIH0sCiAgICAgICAgZml0U2l6ZTogZnVuY3Rpb24oc2l6ZSwgb2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gZml0U2l6ZSQxKHByb2plY3Rpb24sIHNpemUsIG9iamVjdCk7CiAgICAgICAgfSwKICAgICAgICBmaXRXaWR0aDogZnVuY3Rpb24od2lkdGgsIG9iamVjdCkgewogICAgICAgICAgcmV0dXJuIGZpdFdpZHRoJDEocHJvamVjdGlvbiwgd2lkdGgsIG9iamVjdCk7CiAgICAgICAgfSwKICAgICAgICBmaXRIZWlnaHQ6IGZ1bmN0aW9uKGhlaWdodCwgb2JqZWN0KSB7CiAgICAgICAgICByZXR1cm4gZml0SGVpZ2h0JDEocHJvamVjdGlvbiwgaGVpZ2h0LCBvYmplY3QpOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBuYXR1cmFsRWFydGgxUmF3JDEobGFtYmRhLCBwaGkpIHsKICAgICAgdmFyIHBoaTIgPSBwaGkgKiBwaGksIHBoaTQgPSBwaGkyICogcGhpMjsKICAgICAgcmV0dXJuIFsKICAgICAgICBsYW1iZGEgKiAoMC44NzA3IC0gMC4xMzE5NzkgKiBwaGkyICsgcGhpNCAqICgtMC4wMTM3OTEgKyBwaGk0ICogKDAuMDAzOTcxICogcGhpMiAtIDAuMDAxNTI5ICogcGhpNCkpKSwKICAgICAgICBwaGkgKiAoMS4wMDcyMjYgKyBwaGkyICogKDAuMDE1MDg1ICsgcGhpNCAqICgtMC4wNDQ0NzUgKyAwLjAyODg3NCAqIHBoaTIgLSAwLjAwNTkxNiAqIHBoaTQpKSkKICAgICAgXTsKICAgIH0KCiAgICBuYXR1cmFsRWFydGgxUmF3JDEuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICB2YXIgcGhpID0geSwgaSA9IDI1LCBkZWx0YTsKICAgICAgZG8gewogICAgICAgIHZhciBwaGkyID0gcGhpICogcGhpLCBwaGk0ID0gcGhpMiAqIHBoaTI7CiAgICAgICAgcGhpIC09IGRlbHRhID0gKHBoaSAqICgxLjAwNzIyNiArIHBoaTIgKiAoMC4wMTUwODUgKyBwaGk0ICogKC0wLjA0NDQ3NSArIDAuMDI4ODc0ICogcGhpMiAtIDAuMDA1OTE2ICogcGhpNCkpKSAtIHkpIC8KICAgICAgICAgICAgKDEuMDA3MjI2ICsgcGhpMiAqICgwLjAxNTA4NSAqIDMgKyBwaGk0ICogKC0wLjA0NDQ3NSAqIDcgKyAwLjAyODg3NCAqIDkgKiBwaGkyIC0gMC4wMDU5MTYgKiAxMSAqIHBoaTQpKSk7CiAgICAgIH0gd2hpbGUgKGFicyQyKGRlbHRhKSA+IGVwc2lsb24kNyAmJiAtLWkgPiAwKTsKICAgICAgcmV0dXJuIFsKICAgICAgICB4IC8gKDAuODcwNyArIChwaGkyID0gcGhpICogcGhpKSAqICgtMC4xMzE5NzkgKyBwaGkyICogKC0wLjAxMzc5MSArIHBoaTIgKiBwaGkyICogcGhpMiAqICgwLjAwMzk3MSAtIDAuMDAxNTI5ICogcGhpMikpKSksCiAgICAgICAgcGhpCiAgICAgIF07CiAgICB9OwoKICAgIGZ1bmN0aW9uIG5hdHVyYWxFYXJ0aDEkMSgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24kMShuYXR1cmFsRWFydGgxUmF3JDEpCiAgICAgICAgICAuc2NhbGUoMTc1LjI5NSk7CiAgICB9CgogICAgZnVuY3Rpb24gb3J0aG9ncmFwaGljUmF3JDEoeCwgeSkgewogICAgICByZXR1cm4gW2NvcyQ0KHkpICogc2luJDQoeCksIHNpbiQ0KHkpXTsKICAgIH0KCiAgICBvcnRob2dyYXBoaWNSYXckMS5pbnZlcnQgPSBhemltdXRoYWxJbnZlcnQkMShhc2luJDIpOwoKICAgIGZ1bmN0aW9uIG9ydGhvZ3JhcGhpYyQxKCkgewogICAgICByZXR1cm4gcHJvamVjdGlvbiQxKG9ydGhvZ3JhcGhpY1JhdyQxKQogICAgICAgICAgLnNjYWxlKDI0OS41KQogICAgICAgICAgLmNsaXBBbmdsZSg5MCArIGVwc2lsb24kNyk7CiAgICB9CgogICAgZnVuY3Rpb24gc3RlcmVvZ3JhcGhpY1JhdyQxKHgsIHkpIHsKICAgICAgdmFyIGN5ID0gY29zJDQoeSksIGsgPSAxICsgY29zJDQoeCkgKiBjeTsKICAgICAgcmV0dXJuIFtjeSAqIHNpbiQ0KHgpIC8gaywgc2luJDQoeSkgLyBrXTsKICAgIH0KCiAgICBzdGVyZW9ncmFwaGljUmF3JDEuaW52ZXJ0ID0gYXppbXV0aGFsSW52ZXJ0JDEoZnVuY3Rpb24oeikgewogICAgICByZXR1cm4gMiAqIGF0YW4kMSh6KTsKICAgIH0pOwoKICAgIGZ1bmN0aW9uIHN0ZXJlb2dyYXBoaWMkMSgpIHsKICAgICAgcmV0dXJuIHByb2plY3Rpb24kMShzdGVyZW9ncmFwaGljUmF3JDEpCiAgICAgICAgICAuc2NhbGUoMjUwKQogICAgICAgICAgLmNsaXBBbmdsZSgxNDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zdmVyc2VNZXJjYXRvclJhdyQxKGxhbWJkYSwgcGhpKSB7CiAgICAgIHJldHVybiBbbG9nJDIodGFuJDEoKGhhbGZQaSQ2ICsgcGhpKSAvIDIpKSwgLWxhbWJkYV07CiAgICB9CgogICAgdHJhbnN2ZXJzZU1lcmNhdG9yUmF3JDEuaW52ZXJ0ID0gZnVuY3Rpb24oeCwgeSkgewogICAgICByZXR1cm4gWy15LCAyICogYXRhbiQxKGV4cCQxKHgpKSAtIGhhbGZQaSQ2XTsKICAgIH07CgogICAgZnVuY3Rpb24gdHJhbnN2ZXJzZU1lcmNhdG9yJDEoKSB7CiAgICAgIHZhciBtID0gbWVyY2F0b3JQcm9qZWN0aW9uJDEodHJhbnN2ZXJzZU1lcmNhdG9yUmF3JDEpLAogICAgICAgICAgY2VudGVyID0gbS5jZW50ZXIsCiAgICAgICAgICByb3RhdGUgPSBtLnJvdGF0ZTsKCiAgICAgIG0uY2VudGVyID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gY2VudGVyKFstX1sxXSwgX1swXV0pIDogKF8gPSBjZW50ZXIoKSwgW19bMV0sIC1fWzBdXSk7CiAgICAgIH07CgogICAgICBtLnJvdGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IHJvdGF0ZShbX1swXSwgX1sxXSwgXy5sZW5ndGggPiAyID8gX1syXSArIDkwIDogOTBdKSA6IChfID0gcm90YXRlKCksIFtfWzBdLCBfWzFdLCBfWzJdIC0gOTBdKTsKICAgICAgfTsKCiAgICAgIHJldHVybiByb3RhdGUoWzAsIDAsIDkwXSkKICAgICAgICAgIC5zY2FsZSgxNTkuMTU1KTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0U2VwYXJhdGlvbiQyKGEsIGIpIHsKICAgICAgcmV0dXJuIGEucGFyZW50ID09PSBiLnBhcmVudCA/IDEgOiAyOwogICAgfQoKICAgIGZ1bmN0aW9uIG1lYW5YJDEoY2hpbGRyZW4pIHsKICAgICAgcmV0dXJuIGNoaWxkcmVuLnJlZHVjZShtZWFuWFJlZHVjZSQxLCAwKSAvIGNoaWxkcmVuLmxlbmd0aDsKICAgIH0KCiAgICBmdW5jdGlvbiBtZWFuWFJlZHVjZSQxKHgsIGMpIHsKICAgICAgcmV0dXJuIHggKyBjLng7CiAgICB9CgogICAgZnVuY3Rpb24gbWF4WSQxKGNoaWxkcmVuKSB7CiAgICAgIHJldHVybiAxICsgY2hpbGRyZW4ucmVkdWNlKG1heFlSZWR1Y2UkMSwgMCk7CiAgICB9CgogICAgZnVuY3Rpb24gbWF4WVJlZHVjZSQxKHksIGMpIHsKICAgICAgcmV0dXJuIE1hdGgubWF4KHksIGMueSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGVhZkxlZnQkMShub2RlKSB7CiAgICAgIHZhciBjaGlsZHJlbjsKICAgICAgd2hpbGUgKGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbikgbm9kZSA9IGNoaWxkcmVuWzBdOwogICAgICByZXR1cm4gbm9kZTsKICAgIH0KCiAgICBmdW5jdGlvbiBsZWFmUmlnaHQkMShub2RlKSB7CiAgICAgIHZhciBjaGlsZHJlbjsKICAgICAgd2hpbGUgKGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbikgbm9kZSA9IGNoaWxkcmVuW2NoaWxkcmVuLmxlbmd0aCAtIDFdOwogICAgICByZXR1cm4gbm9kZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbHVzdGVyJDEoKSB7CiAgICAgIHZhciBzZXBhcmF0aW9uID0gZGVmYXVsdFNlcGFyYXRpb24kMiwKICAgICAgICAgIGR4ID0gMSwKICAgICAgICAgIGR5ID0gMSwKICAgICAgICAgIG5vZGVTaXplID0gZmFsc2U7CgogICAgICBmdW5jdGlvbiBjbHVzdGVyKHJvb3QpIHsKICAgICAgICB2YXIgcHJldmlvdXNOb2RlLAogICAgICAgICAgICB4ID0gMDsKCiAgICAgICAgLy8gRmlyc3Qgd2FsaywgY29tcHV0aW5nIHRoZSBpbml0aWFsIHggJiB5IHZhbHVlcy4KICAgICAgICByb290LmVhY2hBZnRlcihmdW5jdGlvbihub2RlKSB7CiAgICAgICAgICB2YXIgY2hpbGRyZW4gPSBub2RlLmNoaWxkcmVuOwogICAgICAgICAgaWYgKGNoaWxkcmVuKSB7CiAgICAgICAgICAgIG5vZGUueCA9IG1lYW5YJDEoY2hpbGRyZW4pOwogICAgICAgICAgICBub2RlLnkgPSBtYXhZJDEoY2hpbGRyZW4pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZS54ID0gcHJldmlvdXNOb2RlID8geCArPSBzZXBhcmF0aW9uKG5vZGUsIHByZXZpb3VzTm9kZSkgOiAwOwogICAgICAgICAgICBub2RlLnkgPSAwOwogICAgICAgICAgICBwcmV2aW91c05vZGUgPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICB2YXIgbGVmdCA9IGxlYWZMZWZ0JDEocm9vdCksCiAgICAgICAgICAgIHJpZ2h0ID0gbGVhZlJpZ2h0JDEocm9vdCksCiAgICAgICAgICAgIHgwID0gbGVmdC54IC0gc2VwYXJhdGlvbihsZWZ0LCByaWdodCkgLyAyLAogICAgICAgICAgICB4MSA9IHJpZ2h0LnggKyBzZXBhcmF0aW9uKHJpZ2h0LCBsZWZ0KSAvIDI7CgogICAgICAgIC8vIFNlY29uZCB3YWxrLCBub3JtYWxpemluZyB4ICYgeSB0byB0aGUgZGVzaXJlZCBzaXplLgogICAgICAgIHJldHVybiByb290LmVhY2hBZnRlcihub2RlU2l6ZSA/IGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgIG5vZGUueCA9IChub2RlLnggLSByb290LngpICogZHg7CiAgICAgICAgICBub2RlLnkgPSAocm9vdC55IC0gbm9kZS55KSAqIGR5OwogICAgICAgIH0gOiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgICBub2RlLnggPSAobm9kZS54IC0geDApIC8gKHgxIC0geDApICogZHg7CiAgICAgICAgICBub2RlLnkgPSAoMSAtIChyb290LnkgPyBub2RlLnkgLyByb290LnkgOiAxKSkgKiBkeTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgY2x1c3Rlci5zZXBhcmF0aW9uID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNlcGFyYXRpb24gPSB4LCBjbHVzdGVyKSA6IHNlcGFyYXRpb247CiAgICAgIH07CgogICAgICBjbHVzdGVyLnNpemUgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAobm9kZVNpemUgPSBmYWxzZSwgZHggPSAreFswXSwgZHkgPSAreFsxXSwgY2x1c3RlcikgOiAobm9kZVNpemUgPyBudWxsIDogW2R4LCBkeV0pOwogICAgICB9OwoKICAgICAgY2x1c3Rlci5ub2RlU2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChub2RlU2l6ZSA9IHRydWUsIGR4ID0gK3hbMF0sIGR5ID0gK3hbMV0sIGNsdXN0ZXIpIDogKG5vZGVTaXplID8gW2R4LCBkeV0gOiBudWxsKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBjbHVzdGVyOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvdW50JDEobm9kZSkgewogICAgICB2YXIgc3VtID0gMCwKICAgICAgICAgIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbiwKICAgICAgICAgIGkgPSBjaGlsZHJlbiAmJiBjaGlsZHJlbi5sZW5ndGg7CiAgICAgIGlmICghaSkgc3VtID0gMTsKICAgICAgZWxzZSB3aGlsZSAoLS1pID49IDApIHN1bSArPSBjaGlsZHJlbltpXS52YWx1ZTsKICAgICAgbm9kZS52YWx1ZSA9IHN1bTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2NvdW50JDEoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2hBZnRlcihjb3VudCQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2VhY2gkMShjYWxsYmFjaykgewogICAgICB2YXIgbm9kZSA9IHRoaXMsIGN1cnJlbnQsIG5leHQgPSBbbm9kZV0sIGNoaWxkcmVuLCBpLCBuOwogICAgICBkbyB7CiAgICAgICAgY3VycmVudCA9IG5leHQucmV2ZXJzZSgpLCBuZXh0ID0gW107CiAgICAgICAgd2hpbGUgKG5vZGUgPSBjdXJyZW50LnBvcCgpKSB7CiAgICAgICAgICBjYWxsYmFjayhub2RlKSwgY2hpbGRyZW4gPSBub2RlLmNoaWxkcmVuOwogICAgICAgICAgaWYgKGNoaWxkcmVuKSBmb3IgKGkgPSAwLCBuID0gY2hpbGRyZW4ubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIG5leHQucHVzaChjaGlsZHJlbltpXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9IHdoaWxlIChuZXh0Lmxlbmd0aCk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfZWFjaEJlZm9yZSQxKGNhbGxiYWNrKSB7CiAgICAgIHZhciBub2RlID0gdGhpcywgbm9kZXMgPSBbbm9kZV0sIGNoaWxkcmVuLCBpOwogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgY2FsbGJhY2sobm9kZSksIGNoaWxkcmVuID0gbm9kZS5jaGlsZHJlbjsKICAgICAgICBpZiAoY2hpbGRyZW4pIGZvciAoaSA9IGNoaWxkcmVuLmxlbmd0aCAtIDE7IGkgPj0gMDsgLS1pKSB7CiAgICAgICAgICBub2Rlcy5wdXNoKGNoaWxkcmVuW2ldKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9lYWNoQWZ0ZXIkMShjYWxsYmFjaykgewogICAgICB2YXIgbm9kZSA9IHRoaXMsIG5vZGVzID0gW25vZGVdLCBuZXh0ID0gW10sIGNoaWxkcmVuLCBpLCBuOwogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgbmV4dC5wdXNoKG5vZGUpLCBjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW47CiAgICAgICAgaWYgKGNoaWxkcmVuKSBmb3IgKGkgPSAwLCBuID0gY2hpbGRyZW4ubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2Rlcy5wdXNoKGNoaWxkcmVuW2ldKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgd2hpbGUgKG5vZGUgPSBuZXh0LnBvcCgpKSB7CiAgICAgICAgY2FsbGJhY2sobm9kZSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9zdW0kMSh2YWx1ZSkgewogICAgICByZXR1cm4gdGhpcy5lYWNoQWZ0ZXIoZnVuY3Rpb24obm9kZSkgewogICAgICAgIHZhciBzdW0gPSArdmFsdWUobm9kZS5kYXRhKSB8fCAwLAogICAgICAgICAgICBjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW4sCiAgICAgICAgICAgIGkgPSBjaGlsZHJlbiAmJiBjaGlsZHJlbi5sZW5ndGg7CiAgICAgICAgd2hpbGUgKC0taSA+PSAwKSBzdW0gKz0gY2hpbGRyZW5baV0udmFsdWU7CiAgICAgICAgbm9kZS52YWx1ZSA9IHN1bTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9zb3J0JDEoY29tcGFyZSkgewogICAgICByZXR1cm4gdGhpcy5lYWNoQmVmb3JlKGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICBpZiAobm9kZS5jaGlsZHJlbikgewogICAgICAgICAgbm9kZS5jaGlsZHJlbi5zb3J0KGNvbXBhcmUpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9wYXRoJDEoZW5kKSB7CiAgICAgIHZhciBzdGFydCA9IHRoaXMsCiAgICAgICAgICBhbmNlc3RvciA9IGxlYXN0Q29tbW9uQW5jZXN0b3IkMShzdGFydCwgZW5kKSwKICAgICAgICAgIG5vZGVzID0gW3N0YXJ0XTsKICAgICAgd2hpbGUgKHN0YXJ0ICE9PSBhbmNlc3RvcikgewogICAgICAgIHN0YXJ0ID0gc3RhcnQucGFyZW50OwogICAgICAgIG5vZGVzLnB1c2goc3RhcnQpOwogICAgICB9CiAgICAgIHZhciBrID0gbm9kZXMubGVuZ3RoOwogICAgICB3aGlsZSAoZW5kICE9PSBhbmNlc3RvcikgewogICAgICAgIG5vZGVzLnNwbGljZShrLCAwLCBlbmQpOwogICAgICAgIGVuZCA9IGVuZC5wYXJlbnQ7CiAgICAgIH0KICAgICAgcmV0dXJuIG5vZGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlYXN0Q29tbW9uQW5jZXN0b3IkMShhLCBiKSB7CiAgICAgIGlmIChhID09PSBiKSByZXR1cm4gYTsKICAgICAgdmFyIGFOb2RlcyA9IGEuYW5jZXN0b3JzKCksCiAgICAgICAgICBiTm9kZXMgPSBiLmFuY2VzdG9ycygpLAogICAgICAgICAgYyA9IG51bGw7CiAgICAgIGEgPSBhTm9kZXMucG9wKCk7CiAgICAgIGIgPSBiTm9kZXMucG9wKCk7CiAgICAgIHdoaWxlIChhID09PSBiKSB7CiAgICAgICAgYyA9IGE7CiAgICAgICAgYSA9IGFOb2Rlcy5wb3AoKTsKICAgICAgICBiID0gYk5vZGVzLnBvcCgpOwogICAgICB9CiAgICAgIHJldHVybiBjOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZGVfYW5jZXN0b3JzJDEoKSB7CiAgICAgIHZhciBub2RlID0gdGhpcywgbm9kZXMgPSBbbm9kZV07CiAgICAgIHdoaWxlIChub2RlID0gbm9kZS5wYXJlbnQpIHsKICAgICAgICBub2Rlcy5wdXNoKG5vZGUpOwogICAgICB9CiAgICAgIHJldHVybiBub2RlczsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2Rlc2NlbmRhbnRzJDEoKSB7CiAgICAgIHZhciBub2RlcyA9IFtdOwogICAgICB0aGlzLmVhY2goZnVuY3Rpb24obm9kZSkgewogICAgICAgIG5vZGVzLnB1c2gobm9kZSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gbm9kZXM7CiAgICB9CgogICAgZnVuY3Rpb24gbm9kZV9sZWF2ZXMkMSgpIHsKICAgICAgdmFyIGxlYXZlcyA9IFtdOwogICAgICB0aGlzLmVhY2hCZWZvcmUoZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmICghbm9kZS5jaGlsZHJlbikgewogICAgICAgICAgbGVhdmVzLnB1c2gobm9kZSk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgcmV0dXJuIGxlYXZlczsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2xpbmtzJDEoKSB7CiAgICAgIHZhciByb290ID0gdGhpcywgbGlua3MgPSBbXTsKICAgICAgcm9vdC5lYWNoKGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICBpZiAobm9kZSAhPT0gcm9vdCkgeyAvLyBEb27igJl0IGluY2x1ZGUgdGhlIHJvb3TigJlzIHBhcmVudCwgaWYgYW55LgogICAgICAgICAgbGlua3MucHVzaCh7c291cmNlOiBub2RlLnBhcmVudCwgdGFyZ2V0OiBub2RlfSk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgcmV0dXJuIGxpbmtzOwogICAgfQoKICAgIGZ1bmN0aW9uIGhpZXJhcmNoeSQxKGRhdGEsIGNoaWxkcmVuKSB7CiAgICAgIHZhciByb290ID0gbmV3IE5vZGUkMyhkYXRhKSwKICAgICAgICAgIHZhbHVlZCA9ICtkYXRhLnZhbHVlICYmIChyb290LnZhbHVlID0gZGF0YS52YWx1ZSksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZXMgPSBbcm9vdF0sCiAgICAgICAgICBjaGlsZCwKICAgICAgICAgIGNoaWxkcywKICAgICAgICAgIGksCiAgICAgICAgICBuOwoKICAgICAgaWYgKGNoaWxkcmVuID09IG51bGwpIGNoaWxkcmVuID0gZGVmYXVsdENoaWxkcmVuJDE7CgogICAgICB3aGlsZSAobm9kZSA9IG5vZGVzLnBvcCgpKSB7CiAgICAgICAgaWYgKHZhbHVlZCkgbm9kZS52YWx1ZSA9ICtub2RlLmRhdGEudmFsdWU7CiAgICAgICAgaWYgKChjaGlsZHMgPSBjaGlsZHJlbihub2RlLmRhdGEpKSAmJiAobiA9IGNoaWxkcy5sZW5ndGgpKSB7CiAgICAgICAgICBub2RlLmNoaWxkcmVuID0gbmV3IEFycmF5KG4pOwogICAgICAgICAgZm9yIChpID0gbiAtIDE7IGkgPj0gMDsgLS1pKSB7CiAgICAgICAgICAgIG5vZGVzLnB1c2goY2hpbGQgPSBub2RlLmNoaWxkcmVuW2ldID0gbmV3IE5vZGUkMyhjaGlsZHNbaV0pKTsKICAgICAgICAgICAgY2hpbGQucGFyZW50ID0gbm9kZTsKICAgICAgICAgICAgY2hpbGQuZGVwdGggPSBub2RlLmRlcHRoICsgMTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiByb290LmVhY2hCZWZvcmUoY29tcHV0ZUhlaWdodCQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2RlX2NvcHkkMSgpIHsKICAgICAgcmV0dXJuIGhpZXJhcmNoeSQxKHRoaXMpLmVhY2hCZWZvcmUoY29weURhdGEkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdENoaWxkcmVuJDEoZCkgewogICAgICByZXR1cm4gZC5jaGlsZHJlbjsKICAgIH0KCiAgICBmdW5jdGlvbiBjb3B5RGF0YSQxKG5vZGUpIHsKICAgICAgbm9kZS5kYXRhID0gbm9kZS5kYXRhLmRhdGE7CiAgICB9CgogICAgZnVuY3Rpb24gY29tcHV0ZUhlaWdodCQxKG5vZGUpIHsKICAgICAgdmFyIGhlaWdodCA9IDA7CiAgICAgIGRvIG5vZGUuaGVpZ2h0ID0gaGVpZ2h0OwogICAgICB3aGlsZSAoKG5vZGUgPSBub2RlLnBhcmVudCkgJiYgKG5vZGUuaGVpZ2h0IDwgKytoZWlnaHQpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBOb2RlJDMoZGF0YSkgewogICAgICB0aGlzLmRhdGEgPSBkYXRhOwogICAgICB0aGlzLmRlcHRoID0KICAgICAgdGhpcy5oZWlnaHQgPSAwOwogICAgICB0aGlzLnBhcmVudCA9IG51bGw7CiAgICB9CgogICAgTm9kZSQzLnByb3RvdHlwZSA9IGhpZXJhcmNoeSQxLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IE5vZGUkMywKICAgICAgY291bnQ6IG5vZGVfY291bnQkMSwKICAgICAgZWFjaDogbm9kZV9lYWNoJDEsCiAgICAgIGVhY2hBZnRlcjogbm9kZV9lYWNoQWZ0ZXIkMSwKICAgICAgZWFjaEJlZm9yZTogbm9kZV9lYWNoQmVmb3JlJDEsCiAgICAgIHN1bTogbm9kZV9zdW0kMSwKICAgICAgc29ydDogbm9kZV9zb3J0JDEsCiAgICAgIHBhdGg6IG5vZGVfcGF0aCQxLAogICAgICBhbmNlc3RvcnM6IG5vZGVfYW5jZXN0b3JzJDEsCiAgICAgIGRlc2NlbmRhbnRzOiBub2RlX2Rlc2NlbmRhbnRzJDEsCiAgICAgIGxlYXZlczogbm9kZV9sZWF2ZXMkMSwKICAgICAgbGlua3M6IG5vZGVfbGlua3MkMSwKICAgICAgY29weTogbm9kZV9jb3B5JDEKICAgIH07CgogICAgdmFyIHNsaWNlJGEgPSBBcnJheS5wcm90b3R5cGUuc2xpY2U7CgogICAgZnVuY3Rpb24gc2h1ZmZsZSQzKGFycmF5KSB7CiAgICAgIHZhciBtID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgdCwKICAgICAgICAgIGk7CgogICAgICB3aGlsZSAobSkgewogICAgICAgIGkgPSBNYXRoLnJhbmRvbSgpICogbS0tIHwgMDsKICAgICAgICB0ID0gYXJyYXlbbV07CiAgICAgICAgYXJyYXlbbV0gPSBhcnJheVtpXTsKICAgICAgICBhcnJheVtpXSA9IHQ7CiAgICAgIH0KCiAgICAgIHJldHVybiBhcnJheTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3NlJDEoY2lyY2xlcykgewogICAgICB2YXIgaSA9IDAsIG4gPSAoY2lyY2xlcyA9IHNodWZmbGUkMyhzbGljZSRhLmNhbGwoY2lyY2xlcykpKS5sZW5ndGgsIEIgPSBbXSwgcCwgZTsKCiAgICAgIHdoaWxlIChpIDwgbikgewogICAgICAgIHAgPSBjaXJjbGVzW2ldOwogICAgICAgIGlmIChlICYmIGVuY2xvc2VzV2VhayQxKGUsIHApKSArK2k7CiAgICAgICAgZWxzZSBlID0gZW5jbG9zZUJhc2lzJDEoQiA9IGV4dGVuZEJhc2lzJDEoQiwgcCkpLCBpID0gMDsKICAgICAgfQoKICAgICAgcmV0dXJuIGU7CiAgICB9CgogICAgZnVuY3Rpb24gZXh0ZW5kQmFzaXMkMShCLCBwKSB7CiAgICAgIHZhciBpLCBqOwoKICAgICAgaWYgKGVuY2xvc2VzV2Vha0FsbCQxKHAsIEIpKSByZXR1cm4gW3BdOwoKICAgICAgLy8gSWYgd2UgZ2V0IGhlcmUgdGhlbiBCIG11c3QgaGF2ZSBhdCBsZWFzdCBvbmUgZWxlbWVudC4KICAgICAgZm9yIChpID0gMDsgaSA8IEIubGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAoZW5jbG9zZXNOb3QkMShwLCBCW2ldKQogICAgICAgICAgICAmJiBlbmNsb3Nlc1dlYWtBbGwkMShlbmNsb3NlQmFzaXMyJDEoQltpXSwgcCksIEIpKSB7CiAgICAgICAgICByZXR1cm4gW0JbaV0sIHBdOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gSWYgd2UgZ2V0IGhlcmUgdGhlbiBCIG11c3QgaGF2ZSBhdCBsZWFzdCB0d28gZWxlbWVudHMuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBCLmxlbmd0aCAtIDE7ICsraSkgewogICAgICAgIGZvciAoaiA9IGkgKyAxOyBqIDwgQi5sZW5ndGg7ICsraikgewogICAgICAgICAgaWYgKGVuY2xvc2VzTm90JDEoZW5jbG9zZUJhc2lzMiQxKEJbaV0sIEJbal0pLCBwKQogICAgICAgICAgICAgICYmIGVuY2xvc2VzTm90JDEoZW5jbG9zZUJhc2lzMiQxKEJbaV0sIHApLCBCW2pdKQogICAgICAgICAgICAgICYmIGVuY2xvc2VzTm90JDEoZW5jbG9zZUJhc2lzMiQxKEJbal0sIHApLCBCW2ldKQogICAgICAgICAgICAgICYmIGVuY2xvc2VzV2Vha0FsbCQxKGVuY2xvc2VCYXNpczMkMShCW2ldLCBCW2pdLCBwKSwgQikpIHsKICAgICAgICAgICAgcmV0dXJuIFtCW2ldLCBCW2pdLCBwXTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIElmIHdlIGdldCBoZXJlIHRoZW4gc29tZXRoaW5nIGlzIHZlcnkgd3JvbmcuCiAgICAgIHRocm93IG5ldyBFcnJvcjsKICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3Nlc05vdCQxKGEsIGIpIHsKICAgICAgdmFyIGRyID0gYS5yIC0gYi5yLCBkeCA9IGIueCAtIGEueCwgZHkgPSBiLnkgLSBhLnk7CiAgICAgIHJldHVybiBkciA8IDAgfHwgZHIgKiBkciA8IGR4ICogZHggKyBkeSAqIGR5OwogICAgfQoKICAgIGZ1bmN0aW9uIGVuY2xvc2VzV2VhayQxKGEsIGIpIHsKICAgICAgdmFyIGRyID0gYS5yIC0gYi5yICsgMWUtNiwgZHggPSBiLnggLSBhLngsIGR5ID0gYi55IC0gYS55OwogICAgICByZXR1cm4gZHIgPiAwICYmIGRyICogZHIgPiBkeCAqIGR4ICsgZHkgKiBkeTsKICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3Nlc1dlYWtBbGwkMShhLCBCKSB7CiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgQi5sZW5ndGg7ICsraSkgewogICAgICAgIGlmICghZW5jbG9zZXNXZWFrJDEoYSwgQltpXSkpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHRydWU7CiAgICB9CgogICAgZnVuY3Rpb24gZW5jbG9zZUJhc2lzJDEoQikgewogICAgICBzd2l0Y2ggKEIubGVuZ3RoKSB7CiAgICAgICAgY2FzZSAxOiByZXR1cm4gZW5jbG9zZUJhc2lzMSQxKEJbMF0pOwogICAgICAgIGNhc2UgMjogcmV0dXJuIGVuY2xvc2VCYXNpczIkMShCWzBdLCBCWzFdKTsKICAgICAgICBjYXNlIDM6IHJldHVybiBlbmNsb3NlQmFzaXMzJDEoQlswXSwgQlsxXSwgQlsyXSk7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBlbmNsb3NlQmFzaXMxJDEoYSkgewogICAgICByZXR1cm4gewogICAgICAgIHg6IGEueCwKICAgICAgICB5OiBhLnksCiAgICAgICAgcjogYS5yCiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZW5jbG9zZUJhc2lzMiQxKGEsIGIpIHsKICAgICAgdmFyIHgxID0gYS54LCB5MSA9IGEueSwgcjEgPSBhLnIsCiAgICAgICAgICB4MiA9IGIueCwgeTIgPSBiLnksIHIyID0gYi5yLAogICAgICAgICAgeDIxID0geDIgLSB4MSwgeTIxID0geTIgLSB5MSwgcjIxID0gcjIgLSByMSwKICAgICAgICAgIGwgPSBNYXRoLnNxcnQoeDIxICogeDIxICsgeTIxICogeTIxKTsKICAgICAgcmV0dXJuIHsKICAgICAgICB4OiAoeDEgKyB4MiArIHgyMSAvIGwgKiByMjEpIC8gMiwKICAgICAgICB5OiAoeTEgKyB5MiArIHkyMSAvIGwgKiByMjEpIC8gMiwKICAgICAgICByOiAobCArIHIxICsgcjIpIC8gMgogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGVuY2xvc2VCYXNpczMkMShhLCBiLCBjKSB7CiAgICAgIHZhciB4MSA9IGEueCwgeTEgPSBhLnksIHIxID0gYS5yLAogICAgICAgICAgeDIgPSBiLngsIHkyID0gYi55LCByMiA9IGIuciwKICAgICAgICAgIHgzID0gYy54LCB5MyA9IGMueSwgcjMgPSBjLnIsCiAgICAgICAgICBhMiA9IHgxIC0geDIsCiAgICAgICAgICBhMyA9IHgxIC0geDMsCiAgICAgICAgICBiMiA9IHkxIC0geTIsCiAgICAgICAgICBiMyA9IHkxIC0geTMsCiAgICAgICAgICBjMiA9IHIyIC0gcjEsCiAgICAgICAgICBjMyA9IHIzIC0gcjEsCiAgICAgICAgICBkMSA9IHgxICogeDEgKyB5MSAqIHkxIC0gcjEgKiByMSwKICAgICAgICAgIGQyID0gZDEgLSB4MiAqIHgyIC0geTIgKiB5MiArIHIyICogcjIsCiAgICAgICAgICBkMyA9IGQxIC0geDMgKiB4MyAtIHkzICogeTMgKyByMyAqIHIzLAogICAgICAgICAgYWIgPSBhMyAqIGIyIC0gYTIgKiBiMywKICAgICAgICAgIHhhID0gKGIyICogZDMgLSBiMyAqIGQyKSAvIChhYiAqIDIpIC0geDEsCiAgICAgICAgICB4YiA9IChiMyAqIGMyIC0gYjIgKiBjMykgLyBhYiwKICAgICAgICAgIHlhID0gKGEzICogZDIgLSBhMiAqIGQzKSAvIChhYiAqIDIpIC0geTEsCiAgICAgICAgICB5YiA9IChhMiAqIGMzIC0gYTMgKiBjMikgLyBhYiwKICAgICAgICAgIEEgPSB4YiAqIHhiICsgeWIgKiB5YiAtIDEsCiAgICAgICAgICBCID0gMiAqIChyMSArIHhhICogeGIgKyB5YSAqIHliKSwKICAgICAgICAgIEMgPSB4YSAqIHhhICsgeWEgKiB5YSAtIHIxICogcjEsCiAgICAgICAgICByID0gLShBID8gKEIgKyBNYXRoLnNxcnQoQiAqIEIgLSA0ICogQSAqIEMpKSAvICgyICogQSkgOiBDIC8gQik7CiAgICAgIHJldHVybiB7CiAgICAgICAgeDogeDEgKyB4YSArIHhiICogciwKICAgICAgICB5OiB5MSArIHlhICsgeWIgKiByLAogICAgICAgIHI6IHIKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwbGFjZSQxKGEsIGIsIGMpIHsKICAgICAgdmFyIGF4ID0gYS54LAogICAgICAgICAgYXkgPSBhLnksCiAgICAgICAgICBkYSA9IGIuciArIGMuciwKICAgICAgICAgIGRiID0gYS5yICsgYy5yLAogICAgICAgICAgZHggPSBiLnggLSBheCwKICAgICAgICAgIGR5ID0gYi55IC0gYXksCiAgICAgICAgICBkYyA9IGR4ICogZHggKyBkeSAqIGR5OwogICAgICBpZiAoZGMpIHsKICAgICAgICB2YXIgeCA9IDAuNSArICgoZGIgKj0gZGIpIC0gKGRhICo9IGRhKSkgLyAoMiAqIGRjKSwKICAgICAgICAgICAgeSA9IE1hdGguc3FydChNYXRoLm1heCgwLCAyICogZGEgKiAoZGIgKyBkYykgLSAoZGIgLT0gZGMpICogZGIgLSBkYSAqIGRhKSkgLyAoMiAqIGRjKTsKICAgICAgICBjLnggPSBheCArIHggKiBkeCArIHkgKiBkeTsKICAgICAgICBjLnkgPSBheSArIHggKiBkeSAtIHkgKiBkeDsKICAgICAgfSBlbHNlIHsKICAgICAgICBjLnggPSBheCArIGRiOwogICAgICAgIGMueSA9IGF5OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJzZWN0cyQxKGEsIGIpIHsKICAgICAgdmFyIGR4ID0gYi54IC0gYS54LAogICAgICAgICAgZHkgPSBiLnkgLSBhLnksCiAgICAgICAgICBkciA9IGEuciArIGIucjsKICAgICAgcmV0dXJuIGRyICogZHIgLSAxZS02ID4gZHggKiBkeCArIGR5ICogZHk7CiAgICB9CgogICAgZnVuY3Rpb24gc2NvcmUkMShub2RlKSB7CiAgICAgIHZhciBhID0gbm9kZS5fLAogICAgICAgICAgYiA9IG5vZGUubmV4dC5fLAogICAgICAgICAgYWIgPSBhLnIgKyBiLnIsCiAgICAgICAgICBkeCA9IChhLnggKiBiLnIgKyBiLnggKiBhLnIpIC8gYWIsCiAgICAgICAgICBkeSA9IChhLnkgKiBiLnIgKyBiLnkgKiBhLnIpIC8gYWI7CiAgICAgIHJldHVybiBkeCAqIGR4ICsgZHkgKiBkeTsKICAgIH0KCiAgICBmdW5jdGlvbiBOb2RlJDQoY2lyY2xlKSB7CiAgICAgIHRoaXMuXyA9IGNpcmNsZTsKICAgICAgdGhpcy5uZXh0ID0gbnVsbDsKICAgICAgdGhpcy5wcmV2aW91cyA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gcGFja0VuY2xvc2UkMShjaXJjbGVzKSB7CiAgICAgIGlmICghKG4gPSBjaXJjbGVzLmxlbmd0aCkpIHJldHVybiAwOwoKICAgICAgdmFyIGEsIGIsIGMsIG4sIGFhLCBjYSwgaSwgaiwgaywgc2osIHNrOwoKICAgICAgLy8gUGxhY2UgdGhlIGZpcnN0IGNpcmNsZS4KICAgICAgYSA9IGNpcmNsZXNbMF0sIGEueCA9IDAsIGEueSA9IDA7CiAgICAgIGlmICghKG4gPiAxKSkgcmV0dXJuIGEucjsKCiAgICAgIC8vIFBsYWNlIHRoZSBzZWNvbmQgY2lyY2xlLgogICAgICBiID0gY2lyY2xlc1sxXSwgYS54ID0gLWIuciwgYi54ID0gYS5yLCBiLnkgPSAwOwogICAgICBpZiAoIShuID4gMikpIHJldHVybiBhLnIgKyBiLnI7CgogICAgICAvLyBQbGFjZSB0aGUgdGhpcmQgY2lyY2xlLgogICAgICBwbGFjZSQxKGIsIGEsIGMgPSBjaXJjbGVzWzJdKTsKCiAgICAgIC8vIEluaXRpYWxpemUgdGhlIGZyb250LWNoYWluIHVzaW5nIHRoZSBmaXJzdCB0aHJlZSBjaXJjbGVzIGEsIGIgYW5kIGMuCiAgICAgIGEgPSBuZXcgTm9kZSQ0KGEpLCBiID0gbmV3IE5vZGUkNChiKSwgYyA9IG5ldyBOb2RlJDQoYyk7CiAgICAgIGEubmV4dCA9IGMucHJldmlvdXMgPSBiOwogICAgICBiLm5leHQgPSBhLnByZXZpb3VzID0gYzsKICAgICAgYy5uZXh0ID0gYi5wcmV2aW91cyA9IGE7CgogICAgICAvLyBBdHRlbXB0IHRvIHBsYWNlIGVhY2ggcmVtYWluaW5nIGNpcmNsZeKApgogICAgICBwYWNrOiBmb3IgKGkgPSAzOyBpIDwgbjsgKytpKSB7CiAgICAgICAgcGxhY2UkMShhLl8sIGIuXywgYyA9IGNpcmNsZXNbaV0pLCBjID0gbmV3IE5vZGUkNChjKTsKCiAgICAgICAgLy8gRmluZCB0aGUgY2xvc2VzdCBpbnRlcnNlY3RpbmcgY2lyY2xlIG9uIHRoZSBmcm9udC1jaGFpbiwgaWYgYW55LgogICAgICAgIC8vIOKAnENsb3NlbmVzc+KAnSBpcyBkZXRlcm1pbmVkIGJ5IGxpbmVhciBkaXN0YW5jZSBhbG9uZyB0aGUgZnJvbnQtY2hhaW4uCiAgICAgICAgLy8g4oCcQWhlYWTigJ0gb3Ig4oCcYmVoaW5k4oCdIGlzIGxpa2V3aXNlIGRldGVybWluZWQgYnkgbGluZWFyIGRpc3RhbmNlLgogICAgICAgIGogPSBiLm5leHQsIGsgPSBhLnByZXZpb3VzLCBzaiA9IGIuXy5yLCBzayA9IGEuXy5yOwogICAgICAgIGRvIHsKICAgICAgICAgIGlmIChzaiA8PSBzaykgewogICAgICAgICAgICBpZiAoaW50ZXJzZWN0cyQxKGouXywgYy5fKSkgewogICAgICAgICAgICAgIGIgPSBqLCBhLm5leHQgPSBiLCBiLnByZXZpb3VzID0gYSwgLS1pOwogICAgICAgICAgICAgIGNvbnRpbnVlIHBhY2s7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc2ogKz0gai5fLnIsIGogPSBqLm5leHQ7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoaW50ZXJzZWN0cyQxKGsuXywgYy5fKSkgewogICAgICAgICAgICAgIGEgPSBrLCBhLm5leHQgPSBiLCBiLnByZXZpb3VzID0gYSwgLS1pOwogICAgICAgICAgICAgIGNvbnRpbnVlIHBhY2s7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc2sgKz0gay5fLnIsIGsgPSBrLnByZXZpb3VzOwogICAgICAgICAgfQogICAgICAgIH0gd2hpbGUgKGogIT09IGsubmV4dCk7CgogICAgICAgIC8vIFN1Y2Nlc3MhIEluc2VydCB0aGUgbmV3IGNpcmNsZSBjIGJldHdlZW4gYSBhbmQgYi4KICAgICAgICBjLnByZXZpb3VzID0gYSwgYy5uZXh0ID0gYiwgYS5uZXh0ID0gYi5wcmV2aW91cyA9IGIgPSBjOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBuZXcgY2xvc2VzdCBjaXJjbGUgcGFpciB0byB0aGUgY2VudHJvaWQuCiAgICAgICAgYWEgPSBzY29yZSQxKGEpOwogICAgICAgIHdoaWxlICgoYyA9IGMubmV4dCkgIT09IGIpIHsKICAgICAgICAgIGlmICgoY2EgPSBzY29yZSQxKGMpKSA8IGFhKSB7CiAgICAgICAgICAgIGEgPSBjLCBhYSA9IGNhOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBiID0gYS5uZXh0OwogICAgICB9CgogICAgICAvLyBDb21wdXRlIHRoZSBlbmNsb3NpbmcgY2lyY2xlIG9mIHRoZSBmcm9udCBjaGFpbi4KICAgICAgYSA9IFtiLl9dLCBjID0gYjsgd2hpbGUgKChjID0gYy5uZXh0KSAhPT0gYikgYS5wdXNoKGMuXyk7IGMgPSBlbmNsb3NlJDEoYSk7CgogICAgICAvLyBUcmFuc2xhdGUgdGhlIGNpcmNsZXMgdG8gcHV0IHRoZSBlbmNsb3NpbmcgY2lyY2xlIGFyb3VuZCB0aGUgb3JpZ2luLgogICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBhID0gY2lyY2xlc1tpXSwgYS54IC09IGMueCwgYS55IC09IGMueTsKCiAgICAgIHJldHVybiBjLnI7CiAgICB9CgogICAgZnVuY3Rpb24gc2libGluZ3MkMShjaXJjbGVzKSB7CiAgICAgIHBhY2tFbmNsb3NlJDEoY2lyY2xlcyk7CiAgICAgIHJldHVybiBjaXJjbGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIG9wdGlvbmFsJDEoZikgewogICAgICByZXR1cm4gZiA9PSBudWxsID8gbnVsbCA6IHJlcXVpcmVkJDEoZik7CiAgICB9CgogICAgZnVuY3Rpb24gcmVxdWlyZWQkMShmKSB7CiAgICAgIGlmICh0eXBlb2YgZiAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gZjsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudFplcm8kMSgpIHsKICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkbih4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0UmFkaXVzJDMoZCkgewogICAgICByZXR1cm4gTWF0aC5zcXJ0KGQudmFsdWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGluZGV4JDYoKSB7CiAgICAgIHZhciByYWRpdXMgPSBudWxsLAogICAgICAgICAgZHggPSAxLAogICAgICAgICAgZHkgPSAxLAogICAgICAgICAgcGFkZGluZyA9IGNvbnN0YW50WmVybyQxOwoKICAgICAgZnVuY3Rpb24gcGFjayhyb290KSB7CiAgICAgICAgcm9vdC54ID0gZHggLyAyLCByb290LnkgPSBkeSAvIDI7CiAgICAgICAgaWYgKHJhZGl1cykgewogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKHJhZGl1c0xlYWYkMShyYWRpdXMpKQogICAgICAgICAgICAgIC5lYWNoQWZ0ZXIocGFja0NoaWxkcmVuJDEocGFkZGluZywgMC41KSkKICAgICAgICAgICAgICAuZWFjaEJlZm9yZSh0cmFuc2xhdGVDaGlsZCQxKDEpKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKHJhZGl1c0xlYWYkMShkZWZhdWx0UmFkaXVzJDMpKQogICAgICAgICAgICAgIC5lYWNoQWZ0ZXIocGFja0NoaWxkcmVuJDEoY29uc3RhbnRaZXJvJDEsIDEpKQogICAgICAgICAgICAgIC5lYWNoQWZ0ZXIocGFja0NoaWxkcmVuJDEocGFkZGluZywgcm9vdC5yIC8gTWF0aC5taW4oZHgsIGR5KSkpCiAgICAgICAgICAgICAgLmVhY2hCZWZvcmUodHJhbnNsYXRlQ2hpbGQkMShNYXRoLm1pbihkeCwgZHkpIC8gKDIgKiByb290LnIpKSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByb290OwogICAgICB9CgogICAgICBwYWNrLnJhZGl1cyA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYWRpdXMgPSBvcHRpb25hbCQxKHgpLCBwYWNrKSA6IHJhZGl1czsKICAgICAgfTsKCiAgICAgIHBhY2suc2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCBwYWNrKSA6IFtkeCwgZHldOwogICAgICB9OwoKICAgICAgcGFjay5wYWRkaW5nID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmcgPSB0eXBlb2YgeCA9PT0gImZ1bmN0aW9uIiA/IHggOiBjb25zdGFudCRuKCt4KSwgcGFjaykgOiBwYWRkaW5nOwogICAgICB9OwoKICAgICAgcmV0dXJuIHBhY2s7CiAgICB9CgogICAgZnVuY3Rpb24gcmFkaXVzTGVhZiQxKHJhZGl1cykgewogICAgICByZXR1cm4gZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmICghbm9kZS5jaGlsZHJlbikgewogICAgICAgICAgbm9kZS5yID0gTWF0aC5tYXgoMCwgK3JhZGl1cyhub2RlKSB8fCAwKTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcGFja0NoaWxkcmVuJDEocGFkZGluZywgaykgewogICAgICByZXR1cm4gZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmIChjaGlsZHJlbiA9IG5vZGUuY2hpbGRyZW4pIHsKICAgICAgICAgIHZhciBjaGlsZHJlbiwKICAgICAgICAgICAgICBpLAogICAgICAgICAgICAgIG4gPSBjaGlsZHJlbi5sZW5ndGgsCiAgICAgICAgICAgICAgciA9IHBhZGRpbmcobm9kZSkgKiBrIHx8IDAsCiAgICAgICAgICAgICAgZTsKCiAgICAgICAgICBpZiAocikgZm9yIChpID0gMDsgaSA8IG47ICsraSkgY2hpbGRyZW5baV0uciArPSByOwogICAgICAgICAgZSA9IHBhY2tFbmNsb3NlJDEoY2hpbGRyZW4pOwogICAgICAgICAgaWYgKHIpIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIGNoaWxkcmVuW2ldLnIgLT0gcjsKICAgICAgICAgIG5vZGUuciA9IGUgKyByOwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVDaGlsZCQxKGspIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICB2YXIgcGFyZW50ID0gbm9kZS5wYXJlbnQ7CiAgICAgICAgbm9kZS5yICo9IGs7CiAgICAgICAgaWYgKHBhcmVudCkgewogICAgICAgICAgbm9kZS54ID0gcGFyZW50LnggKyBrICogbm9kZS54OwogICAgICAgICAgbm9kZS55ID0gcGFyZW50LnkgKyBrICogbm9kZS55OwogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiByb3VuZE5vZGUkMShub2RlKSB7CiAgICAgIG5vZGUueDAgPSBNYXRoLnJvdW5kKG5vZGUueDApOwogICAgICBub2RlLnkwID0gTWF0aC5yb3VuZChub2RlLnkwKTsKICAgICAgbm9kZS54MSA9IE1hdGgucm91bmQobm9kZS54MSk7CiAgICAgIG5vZGUueTEgPSBNYXRoLnJvdW5kKG5vZGUueTEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVtYXBEaWNlJDEocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgbm9kZXMgPSBwYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICBub2RlLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIGsgPSBwYXJlbnQudmFsdWUgJiYgKHgxIC0geDApIC8gcGFyZW50LnZhbHVlOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUueTAgPSB5MCwgbm9kZS55MSA9IHkxOwogICAgICAgIG5vZGUueDAgPSB4MCwgbm9kZS54MSA9IHgwICs9IG5vZGUudmFsdWUgKiBrOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcGFydGl0aW9uJDEoKSB7CiAgICAgIHZhciBkeCA9IDEsCiAgICAgICAgICBkeSA9IDEsCiAgICAgICAgICBwYWRkaW5nID0gMCwKICAgICAgICAgIHJvdW5kID0gZmFsc2U7CgogICAgICBmdW5jdGlvbiBwYXJ0aXRpb24ocm9vdCkgewogICAgICAgIHZhciBuID0gcm9vdC5oZWlnaHQgKyAxOwogICAgICAgIHJvb3QueDAgPQogICAgICAgIHJvb3QueTAgPSBwYWRkaW5nOwogICAgICAgIHJvb3QueDEgPSBkeDsKICAgICAgICByb290LnkxID0gZHkgLyBuOwogICAgICAgIHJvb3QuZWFjaEJlZm9yZShwb3NpdGlvbk5vZGUoZHksIG4pKTsKICAgICAgICBpZiAocm91bmQpIHJvb3QuZWFjaEJlZm9yZShyb3VuZE5vZGUkMSk7CiAgICAgICAgcmV0dXJuIHJvb3Q7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBvc2l0aW9uTm9kZShkeSwgbikgewogICAgICAgIHJldHVybiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgICBpZiAobm9kZS5jaGlsZHJlbikgewogICAgICAgICAgICB0cmVlbWFwRGljZSQxKG5vZGUsIG5vZGUueDAsIGR5ICogKG5vZGUuZGVwdGggKyAxKSAvIG4sIG5vZGUueDEsIGR5ICogKG5vZGUuZGVwdGggKyAyKSAvIG4pOwogICAgICAgICAgfQogICAgICAgICAgdmFyIHgwID0gbm9kZS54MCwKICAgICAgICAgICAgICB5MCA9IG5vZGUueTAsCiAgICAgICAgICAgICAgeDEgPSBub2RlLngxIC0gcGFkZGluZywKICAgICAgICAgICAgICB5MSA9IG5vZGUueTEgLSBwYWRkaW5nOwogICAgICAgICAgaWYgKHgxIDwgeDApIHgwID0geDEgPSAoeDAgKyB4MSkgLyAyOwogICAgICAgICAgaWYgKHkxIDwgeTApIHkwID0geTEgPSAoeTAgKyB5MSkgLyAyOwogICAgICAgICAgbm9kZS54MCA9IHgwOwogICAgICAgICAgbm9kZS55MCA9IHkwOwogICAgICAgICAgbm9kZS54MSA9IHgxOwogICAgICAgICAgbm9kZS55MSA9IHkxOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHBhcnRpdGlvbi5yb3VuZCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyb3VuZCA9ICEheCwgcGFydGl0aW9uKSA6IHJvdW5kOwogICAgICB9OwoKICAgICAgcGFydGl0aW9uLnNpemUgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZHggPSAreFswXSwgZHkgPSAreFsxXSwgcGFydGl0aW9uKSA6IFtkeCwgZHldOwogICAgICB9OwoKICAgICAgcGFydGl0aW9uLnBhZGRpbmcgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZyA9ICt4LCBwYXJ0aXRpb24pIDogcGFkZGluZzsKICAgICAgfTsKCiAgICAgIHJldHVybiBwYXJ0aXRpb247CiAgICB9CgogICAgdmFyIGtleVByZWZpeCQ0ID0gIiQiLCAvLyBQcm90ZWN0IGFnYWluc3Qga2V5cyBsaWtlIOKAnF9fcHJvdG9fX+KAnS4KICAgICAgICBwcmVyb290JDEgPSB7ZGVwdGg6IC0xfSwKICAgICAgICBhbWJpZ3VvdXMkMSA9IHt9OwoKICAgIGZ1bmN0aW9uIGRlZmF1bHRJZCQxKGQpIHsKICAgICAgcmV0dXJuIGQuaWQ7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFBhcmVudElkJDEoZCkgewogICAgICByZXR1cm4gZC5wYXJlbnRJZDsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHJhdGlmeSQxKCkgewogICAgICB2YXIgaWQgPSBkZWZhdWx0SWQkMSwKICAgICAgICAgIHBhcmVudElkID0gZGVmYXVsdFBhcmVudElkJDE7CgogICAgICBmdW5jdGlvbiBzdHJhdGlmeShkYXRhKSB7CiAgICAgICAgdmFyIGQsCiAgICAgICAgICAgIGksCiAgICAgICAgICAgIG4gPSBkYXRhLmxlbmd0aCwKICAgICAgICAgICAgcm9vdCwKICAgICAgICAgICAgcGFyZW50LAogICAgICAgICAgICBub2RlLAogICAgICAgICAgICBub2RlcyA9IG5ldyBBcnJheShuKSwKICAgICAgICAgICAgbm9kZUlkLAogICAgICAgICAgICBub2RlS2V5LAogICAgICAgICAgICBub2RlQnlLZXkgPSB7fTsKCiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgZCA9IGRhdGFbaV0sIG5vZGUgPSBub2Rlc1tpXSA9IG5ldyBOb2RlJDMoZCk7CiAgICAgICAgICBpZiAoKG5vZGVJZCA9IGlkKGQsIGksIGRhdGEpKSAhPSBudWxsICYmIChub2RlSWQgKz0gIiIpKSB7CiAgICAgICAgICAgIG5vZGVLZXkgPSBrZXlQcmVmaXgkNCArIChub2RlLmlkID0gbm9kZUlkKTsKICAgICAgICAgICAgbm9kZUJ5S2V5W25vZGVLZXldID0gbm9kZUtleSBpbiBub2RlQnlLZXkgPyBhbWJpZ3VvdXMkMSA6IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGVJZCA9IHBhcmVudElkKGRhdGFbaV0sIGksIGRhdGEpOwogICAgICAgICAgaWYgKG5vZGVJZCA9PSBudWxsIHx8ICEobm9kZUlkICs9ICIiKSkgewogICAgICAgICAgICBpZiAocm9vdCkgdGhyb3cgbmV3IEVycm9yKCJtdWx0aXBsZSByb290cyIpOwogICAgICAgICAgICByb290ID0gbm9kZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHBhcmVudCA9IG5vZGVCeUtleVtrZXlQcmVmaXgkNCArIG5vZGVJZF07CiAgICAgICAgICAgIGlmICghcGFyZW50KSB0aHJvdyBuZXcgRXJyb3IoIm1pc3Npbmc6ICIgKyBub2RlSWQpOwogICAgICAgICAgICBpZiAocGFyZW50ID09PSBhbWJpZ3VvdXMkMSkgdGhyb3cgbmV3IEVycm9yKCJhbWJpZ3VvdXM6ICIgKyBub2RlSWQpOwogICAgICAgICAgICBpZiAocGFyZW50LmNoaWxkcmVuKSBwYXJlbnQuY2hpbGRyZW4ucHVzaChub2RlKTsKICAgICAgICAgICAgZWxzZSBwYXJlbnQuY2hpbGRyZW4gPSBbbm9kZV07CiAgICAgICAgICAgIG5vZGUucGFyZW50ID0gcGFyZW50OwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKCFyb290KSB0aHJvdyBuZXcgRXJyb3IoIm5vIHJvb3QiKTsKICAgICAgICByb290LnBhcmVudCA9IHByZXJvb3QkMTsKICAgICAgICByb290LmVhY2hCZWZvcmUoZnVuY3Rpb24obm9kZSkgeyBub2RlLmRlcHRoID0gbm9kZS5wYXJlbnQuZGVwdGggKyAxOyAtLW47IH0pLmVhY2hCZWZvcmUoY29tcHV0ZUhlaWdodCQxKTsKICAgICAgICByb290LnBhcmVudCA9IG51bGw7CiAgICAgICAgaWYgKG4gPiAwKSB0aHJvdyBuZXcgRXJyb3IoImN5Y2xlIik7CgogICAgICAgIHJldHVybiByb290OwogICAgICB9CgogICAgICBzdHJhdGlmeS5pZCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpZCA9IHJlcXVpcmVkJDEoeCksIHN0cmF0aWZ5KSA6IGlkOwogICAgICB9OwoKICAgICAgc3RyYXRpZnkucGFyZW50SWQgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFyZW50SWQgPSByZXF1aXJlZCQxKHgpLCBzdHJhdGlmeSkgOiBwYXJlbnRJZDsKICAgICAgfTsKCiAgICAgIHJldHVybiBzdHJhdGlmeTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0U2VwYXJhdGlvbiQzKGEsIGIpIHsKICAgICAgcmV0dXJuIGEucGFyZW50ID09PSBiLnBhcmVudCA/IDEgOiAyOwogICAgfQoKICAgIC8vIGZ1bmN0aW9uIHJhZGlhbFNlcGFyYXRpb24oYSwgYikgewogICAgLy8gICByZXR1cm4gKGEucGFyZW50ID09PSBiLnBhcmVudCA/IDEgOiAyKSAvIGEuZGVwdGg7CiAgICAvLyB9CgogICAgLy8gVGhpcyBmdW5jdGlvbiBpcyB1c2VkIHRvIHRyYXZlcnNlIHRoZSBsZWZ0IGNvbnRvdXIgb2YgYSBzdWJ0cmVlIChvcgogICAgLy8gc3ViZm9yZXN0KS4gSXQgcmV0dXJucyB0aGUgc3VjY2Vzc29yIG9mIHYgb24gdGhpcyBjb250b3VyLiBUaGlzIHN1Y2Nlc3NvciBpcwogICAgLy8gZWl0aGVyIGdpdmVuIGJ5IHRoZSBsZWZ0bW9zdCBjaGlsZCBvZiB2IG9yIGJ5IHRoZSB0aHJlYWQgb2Ygdi4gVGhlIGZ1bmN0aW9uCiAgICAvLyByZXR1cm5zIG51bGwgaWYgYW5kIG9ubHkgaWYgdiBpcyBvbiB0aGUgaGlnaGVzdCBsZXZlbCBvZiBpdHMgc3VidHJlZS4KICAgIGZ1bmN0aW9uIG5leHRMZWZ0JDEodikgewogICAgICB2YXIgY2hpbGRyZW4gPSB2LmNoaWxkcmVuOwogICAgICByZXR1cm4gY2hpbGRyZW4gPyBjaGlsZHJlblswXSA6IHYudDsKICAgIH0KCiAgICAvLyBUaGlzIGZ1bmN0aW9uIHdvcmtzIGFuYWxvZ291c2x5IHRvIG5leHRMZWZ0LgogICAgZnVuY3Rpb24gbmV4dFJpZ2h0JDEodikgewogICAgICB2YXIgY2hpbGRyZW4gPSB2LmNoaWxkcmVuOwogICAgICByZXR1cm4gY2hpbGRyZW4gPyBjaGlsZHJlbltjaGlsZHJlbi5sZW5ndGggLSAxXSA6IHYudDsKICAgIH0KCiAgICAvLyBTaGlmdHMgdGhlIGN1cnJlbnQgc3VidHJlZSByb290ZWQgYXQgdysuIFRoaXMgaXMgZG9uZSBieSBpbmNyZWFzaW5nCiAgICAvLyBwcmVsaW0odyspIGFuZCBtb2QodyspIGJ5IHNoaWZ0LgogICAgZnVuY3Rpb24gbW92ZVN1YnRyZWUkMSh3bSwgd3AsIHNoaWZ0KSB7CiAgICAgIHZhciBjaGFuZ2UgPSBzaGlmdCAvICh3cC5pIC0gd20uaSk7CiAgICAgIHdwLmMgLT0gY2hhbmdlOwogICAgICB3cC5zICs9IHNoaWZ0OwogICAgICB3bS5jICs9IGNoYW5nZTsKICAgICAgd3AueiArPSBzaGlmdDsKICAgICAgd3AubSArPSBzaGlmdDsKICAgIH0KCiAgICAvLyBBbGwgb3RoZXIgc2hpZnRzLCBhcHBsaWVkIHRvIHRoZSBzbWFsbGVyIHN1YnRyZWVzIGJldHdlZW4gdy0gYW5kIHcrLCBhcmUKICAgIC8vIHBlcmZvcm1lZCBieSB0aGlzIGZ1bmN0aW9uLiBUbyBwcmVwYXJlIHRoZSBzaGlmdHMsIHdlIGhhdmUgdG8gYWRqdXN0CiAgICAvLyBjaGFuZ2UodyspLCBzaGlmdCh3KyksIGFuZCBjaGFuZ2Uody0pLgogICAgZnVuY3Rpb24gZXhlY3V0ZVNoaWZ0cyQxKHYpIHsKICAgICAgdmFyIHNoaWZ0ID0gMCwKICAgICAgICAgIGNoYW5nZSA9IDAsCiAgICAgICAgICBjaGlsZHJlbiA9IHYuY2hpbGRyZW4sCiAgICAgICAgICBpID0gY2hpbGRyZW4ubGVuZ3RoLAogICAgICAgICAgdzsKICAgICAgd2hpbGUgKC0taSA+PSAwKSB7CiAgICAgICAgdyA9IGNoaWxkcmVuW2ldOwogICAgICAgIHcueiArPSBzaGlmdDsKICAgICAgICB3Lm0gKz0gc2hpZnQ7CiAgICAgICAgc2hpZnQgKz0gdy5zICsgKGNoYW5nZSArPSB3LmMpOwogICAgICB9CiAgICB9CgogICAgLy8gSWYgdmkt4oCZcyBhbmNlc3RvciBpcyBhIHNpYmxpbmcgb2YgdiwgcmV0dXJucyB2aS3igJlzIGFuY2VzdG9yLiBPdGhlcndpc2UsCiAgICAvLyByZXR1cm5zIHRoZSBzcGVjaWZpZWQgKGRlZmF1bHQpIGFuY2VzdG9yLgogICAgZnVuY3Rpb24gbmV4dEFuY2VzdG9yJDEodmltLCB2LCBhbmNlc3RvcikgewogICAgICByZXR1cm4gdmltLmEucGFyZW50ID09PSB2LnBhcmVudCA/IHZpbS5hIDogYW5jZXN0b3I7CiAgICB9CgogICAgZnVuY3Rpb24gVHJlZU5vZGUkMShub2RlLCBpKSB7CiAgICAgIHRoaXMuXyA9IG5vZGU7CiAgICAgIHRoaXMucGFyZW50ID0gbnVsbDsKICAgICAgdGhpcy5jaGlsZHJlbiA9IG51bGw7CiAgICAgIHRoaXMuQSA9IG51bGw7IC8vIGRlZmF1bHQgYW5jZXN0b3IKICAgICAgdGhpcy5hID0gdGhpczsgLy8gYW5jZXN0b3IKICAgICAgdGhpcy56ID0gMDsgLy8gcHJlbGltCiAgICAgIHRoaXMubSA9IDA7IC8vIG1vZAogICAgICB0aGlzLmMgPSAwOyAvLyBjaGFuZ2UKICAgICAgdGhpcy5zID0gMDsgLy8gc2hpZnQKICAgICAgdGhpcy50ID0gbnVsbDsgLy8gdGhyZWFkCiAgICAgIHRoaXMuaSA9IGk7IC8vIG51bWJlcgogICAgfQoKICAgIFRyZWVOb2RlJDEucHJvdG90eXBlID0gT2JqZWN0LmNyZWF0ZShOb2RlJDMucHJvdG90eXBlKTsKCiAgICBmdW5jdGlvbiB0cmVlUm9vdCQxKHJvb3QpIHsKICAgICAgdmFyIHRyZWUgPSBuZXcgVHJlZU5vZGUkMShyb290LCAwKSwKICAgICAgICAgIG5vZGUsCiAgICAgICAgICBub2RlcyA9IFt0cmVlXSwKICAgICAgICAgIGNoaWxkLAogICAgICAgICAgY2hpbGRyZW4sCiAgICAgICAgICBpLAogICAgICAgICAgbjsKCiAgICAgIHdoaWxlIChub2RlID0gbm9kZXMucG9wKCkpIHsKICAgICAgICBpZiAoY2hpbGRyZW4gPSBub2RlLl8uY2hpbGRyZW4pIHsKICAgICAgICAgIG5vZGUuY2hpbGRyZW4gPSBuZXcgQXJyYXkobiA9IGNoaWxkcmVuLmxlbmd0aCk7CiAgICAgICAgICBmb3IgKGkgPSBuIC0gMTsgaSA+PSAwOyAtLWkpIHsKICAgICAgICAgICAgbm9kZXMucHVzaChjaGlsZCA9IG5vZGUuY2hpbGRyZW5baV0gPSBuZXcgVHJlZU5vZGUkMShjaGlsZHJlbltpXSwgaSkpOwogICAgICAgICAgICBjaGlsZC5wYXJlbnQgPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgKHRyZWUucGFyZW50ID0gbmV3IFRyZWVOb2RlJDEobnVsbCwgMCkpLmNoaWxkcmVuID0gW3RyZWVdOwogICAgICByZXR1cm4gdHJlZTsKICAgIH0KCiAgICAvLyBOb2RlLWxpbmsgdHJlZSBkaWFncmFtIHVzaW5nIHRoZSBSZWluZ29sZC1UaWxmb3JkICJ0aWR5IiBhbGdvcml0aG0KICAgIGZ1bmN0aW9uIHRyZWUkMSgpIHsKICAgICAgdmFyIHNlcGFyYXRpb24gPSBkZWZhdWx0U2VwYXJhdGlvbiQzLAogICAgICAgICAgZHggPSAxLAogICAgICAgICAgZHkgPSAxLAogICAgICAgICAgbm9kZVNpemUgPSBudWxsOwoKICAgICAgZnVuY3Rpb24gdHJlZShyb290KSB7CiAgICAgICAgdmFyIHQgPSB0cmVlUm9vdCQxKHJvb3QpOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBsYXlvdXQgdXNpbmcgQnVjaGhlaW0gZXQgYWwu4oCZcyBhbGdvcml0aG0uCiAgICAgICAgdC5lYWNoQWZ0ZXIoZmlyc3RXYWxrKSwgdC5wYXJlbnQubSA9IC10Lno7CiAgICAgICAgdC5lYWNoQmVmb3JlKHNlY29uZFdhbGspOwoKICAgICAgICAvLyBJZiBhIGZpeGVkIG5vZGUgc2l6ZSBpcyBzcGVjaWZpZWQsIHNjYWxlIHggYW5kIHkuCiAgICAgICAgaWYgKG5vZGVTaXplKSByb290LmVhY2hCZWZvcmUoc2l6ZU5vZGUpOwoKICAgICAgICAvLyBJZiBhIGZpeGVkIHRyZWUgc2l6ZSBpcyBzcGVjaWZpZWQsIHNjYWxlIHggYW5kIHkgYmFzZWQgb24gdGhlIGV4dGVudC4KICAgICAgICAvLyBDb21wdXRlIHRoZSBsZWZ0LW1vc3QsIHJpZ2h0LW1vc3QsIGFuZCBkZXB0aC1tb3N0IG5vZGVzIGZvciBleHRlbnRzLgogICAgICAgIGVsc2UgewogICAgICAgICAgdmFyIGxlZnQgPSByb290LAogICAgICAgICAgICAgIHJpZ2h0ID0gcm9vdCwKICAgICAgICAgICAgICBib3R0b20gPSByb290OwogICAgICAgICAgcm9vdC5lYWNoQmVmb3JlKGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgICAgaWYgKG5vZGUueCA8IGxlZnQueCkgbGVmdCA9IG5vZGU7CiAgICAgICAgICAgIGlmIChub2RlLnggPiByaWdodC54KSByaWdodCA9IG5vZGU7CiAgICAgICAgICAgIGlmIChub2RlLmRlcHRoID4gYm90dG9tLmRlcHRoKSBib3R0b20gPSBub2RlOwogICAgICAgICAgfSk7CiAgICAgICAgICB2YXIgcyA9IGxlZnQgPT09IHJpZ2h0ID8gMSA6IHNlcGFyYXRpb24obGVmdCwgcmlnaHQpIC8gMiwKICAgICAgICAgICAgICB0eCA9IHMgLSBsZWZ0LngsCiAgICAgICAgICAgICAga3ggPSBkeCAvIChyaWdodC54ICsgcyArIHR4KSwKICAgICAgICAgICAgICBreSA9IGR5IC8gKGJvdHRvbS5kZXB0aCB8fCAxKTsKICAgICAgICAgIHJvb3QuZWFjaEJlZm9yZShmdW5jdGlvbihub2RlKSB7CiAgICAgICAgICAgIG5vZGUueCA9IChub2RlLnggKyB0eCkgKiBreDsKICAgICAgICAgICAgbm9kZS55ID0gbm9kZS5kZXB0aCAqIGt5OwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gcm9vdDsKICAgICAgfQoKICAgICAgLy8gQ29tcHV0ZXMgYSBwcmVsaW1pbmFyeSB4LWNvb3JkaW5hdGUgZm9yIHYuIEJlZm9yZSB0aGF0LCBGSVJTVCBXQUxLIGlzCiAgICAgIC8vIGFwcGxpZWQgcmVjdXJzaXZlbHkgdG8gdGhlIGNoaWxkcmVuIG9mIHYsIGFzIHdlbGwgYXMgdGhlIGZ1bmN0aW9uCiAgICAgIC8vIEFQUE9SVElPTi4gQWZ0ZXIgc3BhY2luZyBvdXQgdGhlIGNoaWxkcmVuIGJ5IGNhbGxpbmcgRVhFQ1VURSBTSElGVFMsIHRoZQogICAgICAvLyBub2RlIHYgaXMgcGxhY2VkIHRvIHRoZSBtaWRwb2ludCBvZiBpdHMgb3V0ZXJtb3N0IGNoaWxkcmVuLgogICAgICBmdW5jdGlvbiBmaXJzdFdhbGsodikgewogICAgICAgIHZhciBjaGlsZHJlbiA9IHYuY2hpbGRyZW4sCiAgICAgICAgICAgIHNpYmxpbmdzID0gdi5wYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICAgIHcgPSB2LmkgPyBzaWJsaW5nc1t2LmkgLSAxXSA6IG51bGw7CiAgICAgICAgaWYgKGNoaWxkcmVuKSB7CiAgICAgICAgICBleGVjdXRlU2hpZnRzJDEodik7CiAgICAgICAgICB2YXIgbWlkcG9pbnQgPSAoY2hpbGRyZW5bMF0ueiArIGNoaWxkcmVuW2NoaWxkcmVuLmxlbmd0aCAtIDFdLnopIC8gMjsKICAgICAgICAgIGlmICh3KSB7CiAgICAgICAgICAgIHYueiA9IHcueiArIHNlcGFyYXRpb24odi5fLCB3Ll8pOwogICAgICAgICAgICB2Lm0gPSB2LnogLSBtaWRwb2ludDsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHYueiA9IG1pZHBvaW50OwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSBpZiAodykgewogICAgICAgICAgdi56ID0gdy56ICsgc2VwYXJhdGlvbih2Ll8sIHcuXyk7CiAgICAgICAgfQogICAgICAgIHYucGFyZW50LkEgPSBhcHBvcnRpb24odiwgdywgdi5wYXJlbnQuQSB8fCBzaWJsaW5nc1swXSk7CiAgICAgIH0KCiAgICAgIC8vIENvbXB1dGVzIGFsbCByZWFsIHgtY29vcmRpbmF0ZXMgYnkgc3VtbWluZyB1cCB0aGUgbW9kaWZpZXJzIHJlY3Vyc2l2ZWx5LgogICAgICBmdW5jdGlvbiBzZWNvbmRXYWxrKHYpIHsKICAgICAgICB2Ll8ueCA9IHYueiArIHYucGFyZW50Lm07CiAgICAgICAgdi5tICs9IHYucGFyZW50Lm07CiAgICAgIH0KCiAgICAgIC8vIFRoZSBjb3JlIG9mIHRoZSBhbGdvcml0aG0uIEhlcmUsIGEgbmV3IHN1YnRyZWUgaXMgY29tYmluZWQgd2l0aCB0aGUKICAgICAgLy8gcHJldmlvdXMgc3VidHJlZXMuIFRocmVhZHMgYXJlIHVzZWQgdG8gdHJhdmVyc2UgdGhlIGluc2lkZSBhbmQgb3V0c2lkZQogICAgICAvLyBjb250b3VycyBvZiB0aGUgbGVmdCBhbmQgcmlnaHQgc3VidHJlZSB1cCB0byB0aGUgaGlnaGVzdCBjb21tb24gbGV2ZWwuIFRoZQogICAgICAvLyB2ZXJ0aWNlcyB1c2VkIGZvciB0aGUgdHJhdmVyc2FscyBhcmUgdmkrLCB2aS0sIHZvLSwgYW5kIHZvKywgd2hlcmUgdGhlCiAgICAgIC8vIHN1cGVyc2NyaXB0IG8gbWVhbnMgb3V0c2lkZSBhbmQgaSBtZWFucyBpbnNpZGUsIHRoZSBzdWJzY3JpcHQgLSBtZWFucyBsZWZ0CiAgICAgIC8vIHN1YnRyZWUgYW5kICsgbWVhbnMgcmlnaHQgc3VidHJlZS4gRm9yIHN1bW1pbmcgdXAgdGhlIG1vZGlmaWVycyBhbG9uZyB0aGUKICAgICAgLy8gY29udG91ciwgd2UgdXNlIHJlc3BlY3RpdmUgdmFyaWFibGVzIHNpKywgc2ktLCBzby0sIGFuZCBzbysuIFdoZW5ldmVyIHR3bwogICAgICAvLyBub2RlcyBvZiB0aGUgaW5zaWRlIGNvbnRvdXJzIGNvbmZsaWN0LCB3ZSBjb21wdXRlIHRoZSBsZWZ0IG9uZSBvZiB0aGUKICAgICAgLy8gZ3JlYXRlc3QgdW5jb21tb24gYW5jZXN0b3JzIHVzaW5nIHRoZSBmdW5jdGlvbiBBTkNFU1RPUiBhbmQgY2FsbCBNT1ZFCiAgICAgIC8vIFNVQlRSRUUgdG8gc2hpZnQgdGhlIHN1YnRyZWUgYW5kIHByZXBhcmUgdGhlIHNoaWZ0cyBvZiBzbWFsbGVyIHN1YnRyZWVzLgogICAgICAvLyBGaW5hbGx5LCB3ZSBhZGQgYSBuZXcgdGhyZWFkIChpZiBuZWNlc3NhcnkpLgogICAgICBmdW5jdGlvbiBhcHBvcnRpb24odiwgdywgYW5jZXN0b3IpIHsKICAgICAgICBpZiAodykgewogICAgICAgICAgdmFyIHZpcCA9IHYsCiAgICAgICAgICAgICAgdm9wID0gdiwKICAgICAgICAgICAgICB2aW0gPSB3LAogICAgICAgICAgICAgIHZvbSA9IHZpcC5wYXJlbnQuY2hpbGRyZW5bMF0sCiAgICAgICAgICAgICAgc2lwID0gdmlwLm0sCiAgICAgICAgICAgICAgc29wID0gdm9wLm0sCiAgICAgICAgICAgICAgc2ltID0gdmltLm0sCiAgICAgICAgICAgICAgc29tID0gdm9tLm0sCiAgICAgICAgICAgICAgc2hpZnQ7CiAgICAgICAgICB3aGlsZSAodmltID0gbmV4dFJpZ2h0JDEodmltKSwgdmlwID0gbmV4dExlZnQkMSh2aXApLCB2aW0gJiYgdmlwKSB7CiAgICAgICAgICAgIHZvbSA9IG5leHRMZWZ0JDEodm9tKTsKICAgICAgICAgICAgdm9wID0gbmV4dFJpZ2h0JDEodm9wKTsKICAgICAgICAgICAgdm9wLmEgPSB2OwogICAgICAgICAgICBzaGlmdCA9IHZpbS56ICsgc2ltIC0gdmlwLnogLSBzaXAgKyBzZXBhcmF0aW9uKHZpbS5fLCB2aXAuXyk7CiAgICAgICAgICAgIGlmIChzaGlmdCA+IDApIHsKICAgICAgICAgICAgICBtb3ZlU3VidHJlZSQxKG5leHRBbmNlc3RvciQxKHZpbSwgdiwgYW5jZXN0b3IpLCB2LCBzaGlmdCk7CiAgICAgICAgICAgICAgc2lwICs9IHNoaWZ0OwogICAgICAgICAgICAgIHNvcCArPSBzaGlmdDsKICAgICAgICAgICAgfQogICAgICAgICAgICBzaW0gKz0gdmltLm07CiAgICAgICAgICAgIHNpcCArPSB2aXAubTsKICAgICAgICAgICAgc29tICs9IHZvbS5tOwogICAgICAgICAgICBzb3AgKz0gdm9wLm07CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodmltICYmICFuZXh0UmlnaHQkMSh2b3ApKSB7CiAgICAgICAgICAgIHZvcC50ID0gdmltOwogICAgICAgICAgICB2b3AubSArPSBzaW0gLSBzb3A7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodmlwICYmICFuZXh0TGVmdCQxKHZvbSkpIHsKICAgICAgICAgICAgdm9tLnQgPSB2aXA7CiAgICAgICAgICAgIHZvbS5tICs9IHNpcCAtIHNvbTsKICAgICAgICAgICAgYW5jZXN0b3IgPSB2OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gYW5jZXN0b3I7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNpemVOb2RlKG5vZGUpIHsKICAgICAgICBub2RlLnggKj0gZHg7CiAgICAgICAgbm9kZS55ID0gbm9kZS5kZXB0aCAqIGR5OwogICAgICB9CgogICAgICB0cmVlLnNlcGFyYXRpb24gPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2VwYXJhdGlvbiA9IHgsIHRyZWUpIDogc2VwYXJhdGlvbjsKICAgICAgfTsKCiAgICAgIHRyZWUuc2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChub2RlU2l6ZSA9IGZhbHNlLCBkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCB0cmVlKSA6IChub2RlU2l6ZSA/IG51bGwgOiBbZHgsIGR5XSk7CiAgICAgIH07CgogICAgICB0cmVlLm5vZGVTaXplID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG5vZGVTaXplID0gdHJ1ZSwgZHggPSAreFswXSwgZHkgPSAreFsxXSwgdHJlZSkgOiAobm9kZVNpemUgPyBbZHgsIGR5XSA6IG51bGwpOwogICAgICB9OwoKICAgICAgcmV0dXJuIHRyZWU7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZW1hcFNsaWNlJDEocGFyZW50LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgbm9kZXMgPSBwYXJlbnQuY2hpbGRyZW4sCiAgICAgICAgICBub2RlLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIGsgPSBwYXJlbnQudmFsdWUgJiYgKHkxIC0geTApIC8gcGFyZW50LnZhbHVlOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBub2RlID0gbm9kZXNbaV0sIG5vZGUueDAgPSB4MCwgbm9kZS54MSA9IHgxOwogICAgICAgIG5vZGUueTAgPSB5MCwgbm9kZS55MSA9IHkwICs9IG5vZGUudmFsdWUgKiBrOwogICAgICB9CiAgICB9CgogICAgdmFyIHBoaSQxID0gKDEgKyBNYXRoLnNxcnQoNSkpIC8gMjsKCiAgICBmdW5jdGlvbiBzcXVhcmlmeVJhdGlvJDEocmF0aW8sIHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdmFyIHJvd3MgPSBbXSwKICAgICAgICAgIG5vZGVzID0gcGFyZW50LmNoaWxkcmVuLAogICAgICAgICAgcm93LAogICAgICAgICAgbm9kZVZhbHVlLAogICAgICAgICAgaTAgPSAwLAogICAgICAgICAgaTEgPSAwLAogICAgICAgICAgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIGR4LCBkeSwKICAgICAgICAgIHZhbHVlID0gcGFyZW50LnZhbHVlLAogICAgICAgICAgc3VtVmFsdWUsCiAgICAgICAgICBtaW5WYWx1ZSwKICAgICAgICAgIG1heFZhbHVlLAogICAgICAgICAgbmV3UmF0aW8sCiAgICAgICAgICBtaW5SYXRpbywKICAgICAgICAgIGFscGhhLAogICAgICAgICAgYmV0YTsKCiAgICAgIHdoaWxlIChpMCA8IG4pIHsKICAgICAgICBkeCA9IHgxIC0geDAsIGR5ID0geTEgLSB5MDsKCiAgICAgICAgLy8gRmluZCB0aGUgbmV4dCBub24tZW1wdHkgbm9kZS4KICAgICAgICBkbyBzdW1WYWx1ZSA9IG5vZGVzW2kxKytdLnZhbHVlOyB3aGlsZSAoIXN1bVZhbHVlICYmIGkxIDwgbik7CiAgICAgICAgbWluVmFsdWUgPSBtYXhWYWx1ZSA9IHN1bVZhbHVlOwogICAgICAgIGFscGhhID0gTWF0aC5tYXgoZHkgLyBkeCwgZHggLyBkeSkgLyAodmFsdWUgKiByYXRpbyk7CiAgICAgICAgYmV0YSA9IHN1bVZhbHVlICogc3VtVmFsdWUgKiBhbHBoYTsKICAgICAgICBtaW5SYXRpbyA9IE1hdGgubWF4KG1heFZhbHVlIC8gYmV0YSwgYmV0YSAvIG1pblZhbHVlKTsKCiAgICAgICAgLy8gS2VlcCBhZGRpbmcgbm9kZXMgd2hpbGUgdGhlIGFzcGVjdCByYXRpbyBtYWludGFpbnMgb3IgaW1wcm92ZXMuCiAgICAgICAgZm9yICg7IGkxIDwgbjsgKytpMSkgewogICAgICAgICAgc3VtVmFsdWUgKz0gbm9kZVZhbHVlID0gbm9kZXNbaTFdLnZhbHVlOwogICAgICAgICAgaWYgKG5vZGVWYWx1ZSA8IG1pblZhbHVlKSBtaW5WYWx1ZSA9IG5vZGVWYWx1ZTsKICAgICAgICAgIGlmIChub2RlVmFsdWUgPiBtYXhWYWx1ZSkgbWF4VmFsdWUgPSBub2RlVmFsdWU7CiAgICAgICAgICBiZXRhID0gc3VtVmFsdWUgKiBzdW1WYWx1ZSAqIGFscGhhOwogICAgICAgICAgbmV3UmF0aW8gPSBNYXRoLm1heChtYXhWYWx1ZSAvIGJldGEsIGJldGEgLyBtaW5WYWx1ZSk7CiAgICAgICAgICBpZiAobmV3UmF0aW8gPiBtaW5SYXRpbykgeyBzdW1WYWx1ZSAtPSBub2RlVmFsdWU7IGJyZWFrOyB9CiAgICAgICAgICBtaW5SYXRpbyA9IG5ld1JhdGlvOwogICAgICAgIH0KCiAgICAgICAgLy8gUG9zaXRpb24gYW5kIHJlY29yZCB0aGUgcm93IG9yaWVudGF0aW9uLgogICAgICAgIHJvd3MucHVzaChyb3cgPSB7dmFsdWU6IHN1bVZhbHVlLCBkaWNlOiBkeCA8IGR5LCBjaGlsZHJlbjogbm9kZXMuc2xpY2UoaTAsIGkxKX0pOwogICAgICAgIGlmIChyb3cuZGljZSkgdHJlZW1hcERpY2UkMShyb3csIHgwLCB5MCwgeDEsIHZhbHVlID8geTAgKz0gZHkgKiBzdW1WYWx1ZSAvIHZhbHVlIDogeTEpOwogICAgICAgIGVsc2UgdHJlZW1hcFNsaWNlJDEocm93LCB4MCwgeTAsIHZhbHVlID8geDAgKz0gZHggKiBzdW1WYWx1ZSAvIHZhbHVlIDogeDEsIHkxKTsKICAgICAgICB2YWx1ZSAtPSBzdW1WYWx1ZSwgaTAgPSBpMTsKICAgICAgfQoKICAgICAgcmV0dXJuIHJvd3M7CiAgICB9CgogICAgdmFyIHNxdWFyaWZ5JDEgPSAoZnVuY3Rpb24gY3VzdG9tKHJhdGlvKSB7CgogICAgICBmdW5jdGlvbiBzcXVhcmlmeShwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgICAgc3F1YXJpZnlSYXRpbyQxKHJhdGlvLCBwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKTsKICAgICAgfQoKICAgICAgc3F1YXJpZnkucmF0aW8gPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgoeCA9ICt4KSA+IDEgPyB4IDogMSk7CiAgICAgIH07CgogICAgICByZXR1cm4gc3F1YXJpZnk7CiAgICB9KShwaGkkMSk7CgogICAgZnVuY3Rpb24gaW5kZXgkNygpIHsKICAgICAgdmFyIHRpbGUgPSBzcXVhcmlmeSQxLAogICAgICAgICAgcm91bmQgPSBmYWxzZSwKICAgICAgICAgIGR4ID0gMSwKICAgICAgICAgIGR5ID0gMSwKICAgICAgICAgIHBhZGRpbmdTdGFjayA9IFswXSwKICAgICAgICAgIHBhZGRpbmdJbm5lciA9IGNvbnN0YW50WmVybyQxLAogICAgICAgICAgcGFkZGluZ1RvcCA9IGNvbnN0YW50WmVybyQxLAogICAgICAgICAgcGFkZGluZ1JpZ2h0ID0gY29uc3RhbnRaZXJvJDEsCiAgICAgICAgICBwYWRkaW5nQm90dG9tID0gY29uc3RhbnRaZXJvJDEsCiAgICAgICAgICBwYWRkaW5nTGVmdCA9IGNvbnN0YW50WmVybyQxOwoKICAgICAgZnVuY3Rpb24gdHJlZW1hcChyb290KSB7CiAgICAgICAgcm9vdC54MCA9CiAgICAgICAgcm9vdC55MCA9IDA7CiAgICAgICAgcm9vdC54MSA9IGR4OwogICAgICAgIHJvb3QueTEgPSBkeTsKICAgICAgICByb290LmVhY2hCZWZvcmUocG9zaXRpb25Ob2RlKTsKICAgICAgICBwYWRkaW5nU3RhY2sgPSBbMF07CiAgICAgICAgaWYgKHJvdW5kKSByb290LmVhY2hCZWZvcmUocm91bmROb2RlJDEpOwogICAgICAgIHJldHVybiByb290OwogICAgICB9CgogICAgICBmdW5jdGlvbiBwb3NpdGlvbk5vZGUobm9kZSkgewogICAgICAgIHZhciBwID0gcGFkZGluZ1N0YWNrW25vZGUuZGVwdGhdLAogICAgICAgICAgICB4MCA9IG5vZGUueDAgKyBwLAogICAgICAgICAgICB5MCA9IG5vZGUueTAgKyBwLAogICAgICAgICAgICB4MSA9IG5vZGUueDEgLSBwLAogICAgICAgICAgICB5MSA9IG5vZGUueTEgLSBwOwogICAgICAgIGlmICh4MSA8IHgwKSB4MCA9IHgxID0gKHgwICsgeDEpIC8gMjsKICAgICAgICBpZiAoeTEgPCB5MCkgeTAgPSB5MSA9ICh5MCArIHkxKSAvIDI7CiAgICAgICAgbm9kZS54MCA9IHgwOwogICAgICAgIG5vZGUueTAgPSB5MDsKICAgICAgICBub2RlLngxID0geDE7CiAgICAgICAgbm9kZS55MSA9IHkxOwogICAgICAgIGlmIChub2RlLmNoaWxkcmVuKSB7CiAgICAgICAgICBwID0gcGFkZGluZ1N0YWNrW25vZGUuZGVwdGggKyAxXSA9IHBhZGRpbmdJbm5lcihub2RlKSAvIDI7CiAgICAgICAgICB4MCArPSBwYWRkaW5nTGVmdChub2RlKSAtIHA7CiAgICAgICAgICB5MCArPSBwYWRkaW5nVG9wKG5vZGUpIC0gcDsKICAgICAgICAgIHgxIC09IHBhZGRpbmdSaWdodChub2RlKSAtIHA7CiAgICAgICAgICB5MSAtPSBwYWRkaW5nQm90dG9tKG5vZGUpIC0gcDsKICAgICAgICAgIGlmICh4MSA8IHgwKSB4MCA9IHgxID0gKHgwICsgeDEpIC8gMjsKICAgICAgICAgIGlmICh5MSA8IHkwKSB5MCA9IHkxID0gKHkwICsgeTEpIC8gMjsKICAgICAgICAgIHRpbGUobm9kZSwgeDAsIHkwLCB4MSwgeTEpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgdHJlZW1hcC5yb3VuZCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyb3VuZCA9ICEheCwgdHJlZW1hcCkgOiByb3VuZDsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAuc2l6ZSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkeCA9ICt4WzBdLCBkeSA9ICt4WzFdLCB0cmVlbWFwKSA6IFtkeCwgZHldOwogICAgICB9OwoKICAgICAgdHJlZW1hcC50aWxlID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRpbGUgPSByZXF1aXJlZCQxKHgpLCB0cmVlbWFwKSA6IHRpbGU7CiAgICAgIH07CgogICAgICB0cmVlbWFwLnBhZGRpbmcgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyB0cmVlbWFwLnBhZGRpbmdJbm5lcih4KS5wYWRkaW5nT3V0ZXIoeCkgOiB0cmVlbWFwLnBhZGRpbmdJbm5lcigpOwogICAgICB9OwoKICAgICAgdHJlZW1hcC5wYWRkaW5nSW5uZXIgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ0lubmVyID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkbigreCksIHRyZWVtYXApIDogcGFkZGluZ0lubmVyOwogICAgICB9OwoKICAgICAgdHJlZW1hcC5wYWRkaW5nT3V0ZXIgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyB0cmVlbWFwLnBhZGRpbmdUb3AoeCkucGFkZGluZ1JpZ2h0KHgpLnBhZGRpbmdCb3R0b20oeCkucGFkZGluZ0xlZnQoeCkgOiB0cmVlbWFwLnBhZGRpbmdUb3AoKTsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ1RvcCA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRkaW5nVG9wID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkbigreCksIHRyZWVtYXApIDogcGFkZGluZ1RvcDsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ1JpZ2h0ID0gZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmdSaWdodCA9IHR5cGVvZiB4ID09PSAiZnVuY3Rpb24iID8geCA6IGNvbnN0YW50JG4oK3gpLCB0cmVlbWFwKSA6IHBhZGRpbmdSaWdodDsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ0JvdHRvbSA9IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRkaW5nQm90dG9tID0gdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyB4IDogY29uc3RhbnQkbigreCksIHRyZWVtYXApIDogcGFkZGluZ0JvdHRvbTsKICAgICAgfTsKCiAgICAgIHRyZWVtYXAucGFkZGluZ0xlZnQgPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ0xlZnQgPSB0eXBlb2YgeCA9PT0gImZ1bmN0aW9uIiA/IHggOiBjb25zdGFudCRuKCt4KSwgdHJlZW1hcCkgOiBwYWRkaW5nTGVmdDsKICAgICAgfTsKCiAgICAgIHJldHVybiB0cmVlbWFwOwogICAgfQoKICAgIGZ1bmN0aW9uIGJpbmFyeSQxKHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdmFyIG5vZGVzID0gcGFyZW50LmNoaWxkcmVuLAogICAgICAgICAgaSwgbiA9IG5vZGVzLmxlbmd0aCwKICAgICAgICAgIHN1bSwgc3VtcyA9IG5ldyBBcnJheShuICsgMSk7CgogICAgICBmb3IgKHN1bXNbMF0gPSBzdW0gPSBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgIHN1bXNbaSArIDFdID0gc3VtICs9IG5vZGVzW2ldLnZhbHVlOwogICAgICB9CgogICAgICBwYXJ0aXRpb24oMCwgbiwgcGFyZW50LnZhbHVlLCB4MCwgeTAsIHgxLCB5MSk7CgogICAgICBmdW5jdGlvbiBwYXJ0aXRpb24oaSwgaiwgdmFsdWUsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgICAgaWYgKGkgPj0gaiAtIDEpIHsKICAgICAgICAgIHZhciBub2RlID0gbm9kZXNbaV07CiAgICAgICAgICBub2RlLngwID0geDAsIG5vZGUueTAgPSB5MDsKICAgICAgICAgIG5vZGUueDEgPSB4MSwgbm9kZS55MSA9IHkxOwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdmFyIHZhbHVlT2Zmc2V0ID0gc3Vtc1tpXSwKICAgICAgICAgICAgdmFsdWVUYXJnZXQgPSAodmFsdWUgLyAyKSArIHZhbHVlT2Zmc2V0LAogICAgICAgICAgICBrID0gaSArIDEsCiAgICAgICAgICAgIGhpID0gaiAtIDE7CgogICAgICAgIHdoaWxlIChrIDwgaGkpIHsKICAgICAgICAgIHZhciBtaWQgPSBrICsgaGkgPj4+IDE7CiAgICAgICAgICBpZiAoc3Vtc1ttaWRdIDwgdmFsdWVUYXJnZXQpIGsgPSBtaWQgKyAxOwogICAgICAgICAgZWxzZSBoaSA9IG1pZDsKICAgICAgICB9CgogICAgICAgIGlmICgodmFsdWVUYXJnZXQgLSBzdW1zW2sgLSAxXSkgPCAoc3Vtc1trXSAtIHZhbHVlVGFyZ2V0KSAmJiBpICsgMSA8IGspIC0tazsKCiAgICAgICAgdmFyIHZhbHVlTGVmdCA9IHN1bXNba10gLSB2YWx1ZU9mZnNldCwKICAgICAgICAgICAgdmFsdWVSaWdodCA9IHZhbHVlIC0gdmFsdWVMZWZ0OwoKICAgICAgICBpZiAoKHgxIC0geDApID4gKHkxIC0geTApKSB7CiAgICAgICAgICB2YXIgeGsgPSAoeDAgKiB2YWx1ZVJpZ2h0ICsgeDEgKiB2YWx1ZUxlZnQpIC8gdmFsdWU7CiAgICAgICAgICBwYXJ0aXRpb24oaSwgaywgdmFsdWVMZWZ0LCB4MCwgeTAsIHhrLCB5MSk7CiAgICAgICAgICBwYXJ0aXRpb24oaywgaiwgdmFsdWVSaWdodCwgeGssIHkwLCB4MSwgeTEpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB2YXIgeWsgPSAoeTAgKiB2YWx1ZVJpZ2h0ICsgeTEgKiB2YWx1ZUxlZnQpIC8gdmFsdWU7CiAgICAgICAgICBwYXJ0aXRpb24oaSwgaywgdmFsdWVMZWZ0LCB4MCwgeTAsIHgxLCB5ayk7CiAgICAgICAgICBwYXJ0aXRpb24oaywgaiwgdmFsdWVSaWdodCwgeDAsIHlrLCB4MSwgeTEpOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHNsaWNlRGljZSQxKHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgKHBhcmVudC5kZXB0aCAmIDEgPyB0cmVlbWFwU2xpY2UkMSA6IHRyZWVtYXBEaWNlJDEpKHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpOwogICAgfQoKICAgIHZhciByZXNxdWFyaWZ5JDEgPSAoZnVuY3Rpb24gY3VzdG9tKHJhdGlvKSB7CgogICAgICBmdW5jdGlvbiByZXNxdWFyaWZ5KHBhcmVudCwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgICBpZiAoKHJvd3MgPSBwYXJlbnQuX3NxdWFyaWZ5KSAmJiAocm93cy5yYXRpbyA9PT0gcmF0aW8pKSB7CiAgICAgICAgICB2YXIgcm93cywKICAgICAgICAgICAgICByb3csCiAgICAgICAgICAgICAgbm9kZXMsCiAgICAgICAgICAgICAgaSwKICAgICAgICAgICAgICBqID0gLTEsCiAgICAgICAgICAgICAgbiwKICAgICAgICAgICAgICBtID0gcm93cy5sZW5ndGgsCiAgICAgICAgICAgICAgdmFsdWUgPSBwYXJlbnQudmFsdWU7CgogICAgICAgICAgd2hpbGUgKCsraiA8IG0pIHsKICAgICAgICAgICAgcm93ID0gcm93c1tqXSwgbm9kZXMgPSByb3cuY2hpbGRyZW47CiAgICAgICAgICAgIGZvciAoaSA9IHJvdy52YWx1ZSA9IDAsIG4gPSBub2Rlcy5sZW5ndGg7IGkgPCBuOyArK2kpIHJvdy52YWx1ZSArPSBub2Rlc1tpXS52YWx1ZTsKICAgICAgICAgICAgaWYgKHJvdy5kaWNlKSB0cmVlbWFwRGljZSQxKHJvdywgeDAsIHkwLCB4MSwgeTAgKz0gKHkxIC0geTApICogcm93LnZhbHVlIC8gdmFsdWUpOwogICAgICAgICAgICBlbHNlIHRyZWVtYXBTbGljZSQxKHJvdywgeDAsIHkwLCB4MCArPSAoeDEgLSB4MCkgKiByb3cudmFsdWUgLyB2YWx1ZSwgeTEpOwogICAgICAgICAgICB2YWx1ZSAtPSByb3cudmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHBhcmVudC5fc3F1YXJpZnkgPSByb3dzID0gc3F1YXJpZnlSYXRpbyQxKHJhdGlvLCBwYXJlbnQsIHgwLCB5MCwgeDEsIHkxKTsKICAgICAgICAgIHJvd3MucmF0aW8gPSByYXRpbzsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJlc3F1YXJpZnkucmF0aW8gPSBmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgoeCA9ICt4KSA+IDEgPyB4IDogMSk7CiAgICAgIH07CgogICAgICByZXR1cm4gcmVzcXVhcmlmeTsKICAgIH0pKHBoaSQxKTsKCiAgICBmdW5jdGlvbiBkZWZpbmUkMyhjb25zdHJ1Y3RvciwgZmFjdG9yeSwgcHJvdG90eXBlKSB7CiAgICAgIGNvbnN0cnVjdG9yLnByb3RvdHlwZSA9IGZhY3RvcnkucHJvdG90eXBlID0gcHJvdG90eXBlOwogICAgICBwcm90b3R5cGUuY29uc3RydWN0b3IgPSBjb25zdHJ1Y3RvcjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHRlbmQkMyhwYXJlbnQsIGRlZmluaXRpb24pIHsKICAgICAgdmFyIHByb3RvdHlwZSA9IE9iamVjdC5jcmVhdGUocGFyZW50LnByb3RvdHlwZSk7CiAgICAgIGZvciAodmFyIGtleSBpbiBkZWZpbml0aW9uKSBwcm90b3R5cGVba2V5XSA9IGRlZmluaXRpb25ba2V5XTsKICAgICAgcmV0dXJuIHByb3RvdHlwZTsKICAgIH0KCiAgICBmdW5jdGlvbiBDb2xvciQzKCkge30KCiAgICB2YXIgZGFya2VyJDMgPSAwLjc7CiAgICB2YXIgYnJpZ2h0ZXIkMyA9IDEgLyBkYXJrZXIkMzsKCiAgICB2YXIgcmVJJDMgPSAiXFxzKihbKy1dP1xcZCspXFxzKiIsCiAgICAgICAgcmVOJDMgPSAiXFxzKihbKy1dP1xcZCpcXC4/XFxkKyg/OltlRV1bKy1dP1xcZCspPylcXHMqIiwKICAgICAgICByZVAkMyA9ICJcXHMqKFsrLV0/XFxkKlxcLj9cXGQrKD86W2VFXVsrLV0/XFxkKyk/KSVcXHMqIiwKICAgICAgICByZUhleCQyID0gL14jKFswLTlhLWZdezMsOH0pJC8sCiAgICAgICAgcmVSZ2JJbnRlZ2VyJDMgPSBuZXcgUmVnRXhwKCJecmdiXFwoIiArIFtyZUkkMywgcmVJJDMsIHJlSSQzXSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JQZXJjZW50JDMgPSBuZXcgUmVnRXhwKCJecmdiXFwoIiArIFtyZVAkMywgcmVQJDMsIHJlUCQzXSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JhSW50ZWdlciQzID0gbmV3IFJlZ0V4cCgiXnJnYmFcXCgiICsgW3JlSSQzLCByZUkkMywgcmVJJDMsIHJlTiQzXSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JhUGVyY2VudCQzID0gbmV3IFJlZ0V4cCgiXnJnYmFcXCgiICsgW3JlUCQzLCByZVAkMywgcmVQJDMsIHJlTiQzXSArICJcXCkkIiksCiAgICAgICAgcmVIc2xQZXJjZW50JDMgPSBuZXcgUmVnRXhwKCJeaHNsXFwoIiArIFtyZU4kMywgcmVQJDMsIHJlUCQzXSArICJcXCkkIiksCiAgICAgICAgcmVIc2xhUGVyY2VudCQzID0gbmV3IFJlZ0V4cCgiXmhzbGFcXCgiICsgW3JlTiQzLCByZVAkMywgcmVQJDMsIHJlTiQzXSArICJcXCkkIik7CgogICAgdmFyIG5hbWVkJDMgPSB7CiAgICAgIGFsaWNlYmx1ZTogMHhmMGY4ZmYsCiAgICAgIGFudGlxdWV3aGl0ZTogMHhmYWViZDcsCiAgICAgIGFxdWE6IDB4MDBmZmZmLAogICAgICBhcXVhbWFyaW5lOiAweDdmZmZkNCwKICAgICAgYXp1cmU6IDB4ZjBmZmZmLAogICAgICBiZWlnZTogMHhmNWY1ZGMsCiAgICAgIGJpc3F1ZTogMHhmZmU0YzQsCiAgICAgIGJsYWNrOiAweDAwMDAwMCwKICAgICAgYmxhbmNoZWRhbG1vbmQ6IDB4ZmZlYmNkLAogICAgICBibHVlOiAweDAwMDBmZiwKICAgICAgYmx1ZXZpb2xldDogMHg4YTJiZTIsCiAgICAgIGJyb3duOiAweGE1MmEyYSwKICAgICAgYnVybHl3b29kOiAweGRlYjg4NywKICAgICAgY2FkZXRibHVlOiAweDVmOWVhMCwKICAgICAgY2hhcnRyZXVzZTogMHg3ZmZmMDAsCiAgICAgIGNob2NvbGF0ZTogMHhkMjY5MWUsCiAgICAgIGNvcmFsOiAweGZmN2Y1MCwKICAgICAgY29ybmZsb3dlcmJsdWU6IDB4NjQ5NWVkLAogICAgICBjb3Juc2lsazogMHhmZmY4ZGMsCiAgICAgIGNyaW1zb246IDB4ZGMxNDNjLAogICAgICBjeWFuOiAweDAwZmZmZiwKICAgICAgZGFya2JsdWU6IDB4MDAwMDhiLAogICAgICBkYXJrY3lhbjogMHgwMDhiOGIsCiAgICAgIGRhcmtnb2xkZW5yb2Q6IDB4Yjg4NjBiLAogICAgICBkYXJrZ3JheTogMHhhOWE5YTksCiAgICAgIGRhcmtncmVlbjogMHgwMDY0MDAsCiAgICAgIGRhcmtncmV5OiAweGE5YTlhOSwKICAgICAgZGFya2toYWtpOiAweGJkYjc2YiwKICAgICAgZGFya21hZ2VudGE6IDB4OGIwMDhiLAogICAgICBkYXJrb2xpdmVncmVlbjogMHg1NTZiMmYsCiAgICAgIGRhcmtvcmFuZ2U6IDB4ZmY4YzAwLAogICAgICBkYXJrb3JjaGlkOiAweDk5MzJjYywKICAgICAgZGFya3JlZDogMHg4YjAwMDAsCiAgICAgIGRhcmtzYWxtb246IDB4ZTk5NjdhLAogICAgICBkYXJrc2VhZ3JlZW46IDB4OGZiYzhmLAogICAgICBkYXJrc2xhdGVibHVlOiAweDQ4M2Q4YiwKICAgICAgZGFya3NsYXRlZ3JheTogMHgyZjRmNGYsCiAgICAgIGRhcmtzbGF0ZWdyZXk6IDB4MmY0ZjRmLAogICAgICBkYXJrdHVycXVvaXNlOiAweDAwY2VkMSwKICAgICAgZGFya3Zpb2xldDogMHg5NDAwZDMsCiAgICAgIGRlZXBwaW5rOiAweGZmMTQ5MywKICAgICAgZGVlcHNreWJsdWU6IDB4MDBiZmZmLAogICAgICBkaW1ncmF5OiAweDY5Njk2OSwKICAgICAgZGltZ3JleTogMHg2OTY5NjksCiAgICAgIGRvZGdlcmJsdWU6IDB4MWU5MGZmLAogICAgICBmaXJlYnJpY2s6IDB4YjIyMjIyLAogICAgICBmbG9yYWx3aGl0ZTogMHhmZmZhZjAsCiAgICAgIGZvcmVzdGdyZWVuOiAweDIyOGIyMiwKICAgICAgZnVjaHNpYTogMHhmZjAwZmYsCiAgICAgIGdhaW5zYm9ybzogMHhkY2RjZGMsCiAgICAgIGdob3N0d2hpdGU6IDB4ZjhmOGZmLAogICAgICBnb2xkOiAweGZmZDcwMCwKICAgICAgZ29sZGVucm9kOiAweGRhYTUyMCwKICAgICAgZ3JheTogMHg4MDgwODAsCiAgICAgIGdyZWVuOiAweDAwODAwMCwKICAgICAgZ3JlZW55ZWxsb3c6IDB4YWRmZjJmLAogICAgICBncmV5OiAweDgwODA4MCwKICAgICAgaG9uZXlkZXc6IDB4ZjBmZmYwLAogICAgICBob3RwaW5rOiAweGZmNjliNCwKICAgICAgaW5kaWFucmVkOiAweGNkNWM1YywKICAgICAgaW5kaWdvOiAweDRiMDA4MiwKICAgICAgaXZvcnk6IDB4ZmZmZmYwLAogICAgICBraGFraTogMHhmMGU2OGMsCiAgICAgIGxhdmVuZGVyOiAweGU2ZTZmYSwKICAgICAgbGF2ZW5kZXJibHVzaDogMHhmZmYwZjUsCiAgICAgIGxhd25ncmVlbjogMHg3Y2ZjMDAsCiAgICAgIGxlbW9uY2hpZmZvbjogMHhmZmZhY2QsCiAgICAgIGxpZ2h0Ymx1ZTogMHhhZGQ4ZTYsCiAgICAgIGxpZ2h0Y29yYWw6IDB4ZjA4MDgwLAogICAgICBsaWdodGN5YW46IDB4ZTBmZmZmLAogICAgICBsaWdodGdvbGRlbnJvZHllbGxvdzogMHhmYWZhZDIsCiAgICAgIGxpZ2h0Z3JheTogMHhkM2QzZDMsCiAgICAgIGxpZ2h0Z3JlZW46IDB4OTBlZTkwLAogICAgICBsaWdodGdyZXk6IDB4ZDNkM2QzLAogICAgICBsaWdodHBpbms6IDB4ZmZiNmMxLAogICAgICBsaWdodHNhbG1vbjogMHhmZmEwN2EsCiAgICAgIGxpZ2h0c2VhZ3JlZW46IDB4MjBiMmFhLAogICAgICBsaWdodHNreWJsdWU6IDB4ODdjZWZhLAogICAgICBsaWdodHNsYXRlZ3JheTogMHg3Nzg4OTksCiAgICAgIGxpZ2h0c2xhdGVncmV5OiAweDc3ODg5OSwKICAgICAgbGlnaHRzdGVlbGJsdWU6IDB4YjBjNGRlLAogICAgICBsaWdodHllbGxvdzogMHhmZmZmZTAsCiAgICAgIGxpbWU6IDB4MDBmZjAwLAogICAgICBsaW1lZ3JlZW46IDB4MzJjZDMyLAogICAgICBsaW5lbjogMHhmYWYwZTYsCiAgICAgIG1hZ2VudGE6IDB4ZmYwMGZmLAogICAgICBtYXJvb246IDB4ODAwMDAwLAogICAgICBtZWRpdW1hcXVhbWFyaW5lOiAweDY2Y2RhYSwKICAgICAgbWVkaXVtYmx1ZTogMHgwMDAwY2QsCiAgICAgIG1lZGl1bW9yY2hpZDogMHhiYTU1ZDMsCiAgICAgIG1lZGl1bXB1cnBsZTogMHg5MzcwZGIsCiAgICAgIG1lZGl1bXNlYWdyZWVuOiAweDNjYjM3MSwKICAgICAgbWVkaXVtc2xhdGVibHVlOiAweDdiNjhlZSwKICAgICAgbWVkaXVtc3ByaW5nZ3JlZW46IDB4MDBmYTlhLAogICAgICBtZWRpdW10dXJxdW9pc2U6IDB4NDhkMWNjLAogICAgICBtZWRpdW12aW9sZXRyZWQ6IDB4YzcxNTg1LAogICAgICBtaWRuaWdodGJsdWU6IDB4MTkxOTcwLAogICAgICBtaW50Y3JlYW06IDB4ZjVmZmZhLAogICAgICBtaXN0eXJvc2U6IDB4ZmZlNGUxLAogICAgICBtb2NjYXNpbjogMHhmZmU0YjUsCiAgICAgIG5hdmFqb3doaXRlOiAweGZmZGVhZCwKICAgICAgbmF2eTogMHgwMDAwODAsCiAgICAgIG9sZGxhY2U6IDB4ZmRmNWU2LAogICAgICBvbGl2ZTogMHg4MDgwMDAsCiAgICAgIG9saXZlZHJhYjogMHg2YjhlMjMsCiAgICAgIG9yYW5nZTogMHhmZmE1MDAsCiAgICAgIG9yYW5nZXJlZDogMHhmZjQ1MDAsCiAgICAgIG9yY2hpZDogMHhkYTcwZDYsCiAgICAgIHBhbGVnb2xkZW5yb2Q6IDB4ZWVlOGFhLAogICAgICBwYWxlZ3JlZW46IDB4OThmYjk4LAogICAgICBwYWxldHVycXVvaXNlOiAweGFmZWVlZSwKICAgICAgcGFsZXZpb2xldHJlZDogMHhkYjcwOTMsCiAgICAgIHBhcGF5YXdoaXA6IDB4ZmZlZmQ1LAogICAgICBwZWFjaHB1ZmY6IDB4ZmZkYWI5LAogICAgICBwZXJ1OiAweGNkODUzZiwKICAgICAgcGluazogMHhmZmMwY2IsCiAgICAgIHBsdW06IDB4ZGRhMGRkLAogICAgICBwb3dkZXJibHVlOiAweGIwZTBlNiwKICAgICAgcHVycGxlOiAweDgwMDA4MCwKICAgICAgcmViZWNjYXB1cnBsZTogMHg2NjMzOTksCiAgICAgIHJlZDogMHhmZjAwMDAsCiAgICAgIHJvc3licm93bjogMHhiYzhmOGYsCiAgICAgIHJveWFsYmx1ZTogMHg0MTY5ZTEsCiAgICAgIHNhZGRsZWJyb3duOiAweDhiNDUxMywKICAgICAgc2FsbW9uOiAweGZhODA3MiwKICAgICAgc2FuZHlicm93bjogMHhmNGE0NjAsCiAgICAgIHNlYWdyZWVuOiAweDJlOGI1NywKICAgICAgc2Vhc2hlbGw6IDB4ZmZmNWVlLAogICAgICBzaWVubmE6IDB4YTA1MjJkLAogICAgICBzaWx2ZXI6IDB4YzBjMGMwLAogICAgICBza3libHVlOiAweDg3Y2VlYiwKICAgICAgc2xhdGVibHVlOiAweDZhNWFjZCwKICAgICAgc2xhdGVncmF5OiAweDcwODA5MCwKICAgICAgc2xhdGVncmV5OiAweDcwODA5MCwKICAgICAgc25vdzogMHhmZmZhZmEsCiAgICAgIHNwcmluZ2dyZWVuOiAweDAwZmY3ZiwKICAgICAgc3RlZWxibHVlOiAweDQ2ODJiNCwKICAgICAgdGFuOiAweGQyYjQ4YywKICAgICAgdGVhbDogMHgwMDgwODAsCiAgICAgIHRoaXN0bGU6IDB4ZDhiZmQ4LAogICAgICB0b21hdG86IDB4ZmY2MzQ3LAogICAgICB0dXJxdW9pc2U6IDB4NDBlMGQwLAogICAgICB2aW9sZXQ6IDB4ZWU4MmVlLAogICAgICB3aGVhdDogMHhmNWRlYjMsCiAgICAgIHdoaXRlOiAweGZmZmZmZiwKICAgICAgd2hpdGVzbW9rZTogMHhmNWY1ZjUsCiAgICAgIHllbGxvdzogMHhmZmZmMDAsCiAgICAgIHllbGxvd2dyZWVuOiAweDlhY2QzMgogICAgfTsKCiAgICBkZWZpbmUkMyhDb2xvciQzLCBjb2xvciQzLCB7CiAgICAgIGNvcHk6IGZ1bmN0aW9uKGNoYW5uZWxzKSB7CiAgICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24obmV3IHRoaXMuY29uc3RydWN0b3IsIHRoaXMsIGNoYW5uZWxzKTsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnJnYigpLmRpc3BsYXlhYmxlKCk7CiAgICAgIH0sCiAgICAgIGhleDogY29sb3JfZm9ybWF0SGV4JDIsIC8vIERlcHJlY2F0ZWQhIFVzZSBjb2xvci5mb3JtYXRIZXguCiAgICAgIGZvcm1hdEhleDogY29sb3JfZm9ybWF0SGV4JDIsCiAgICAgIGZvcm1hdEhzbDogY29sb3JfZm9ybWF0SHNsJDIsCiAgICAgIGZvcm1hdFJnYjogY29sb3JfZm9ybWF0UmdiJDIsCiAgICAgIHRvU3RyaW5nOiBjb2xvcl9mb3JtYXRSZ2IkMgogICAgfSk7CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0SGV4JDIoKSB7CiAgICAgIHJldHVybiB0aGlzLnJnYigpLmZvcm1hdEhleCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdEhzbCQyKCkgewogICAgICByZXR1cm4gaHNsQ29udmVydCQzKHRoaXMpLmZvcm1hdEhzbCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdFJnYiQyKCkgewogICAgICByZXR1cm4gdGhpcy5yZ2IoKS5mb3JtYXRSZ2IoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvciQzKGZvcm1hdCkgewogICAgICB2YXIgbSwgbDsKICAgICAgZm9ybWF0ID0gKGZvcm1hdCArICIiKS50cmltKCkudG9Mb3dlckNhc2UoKTsKICAgICAgcmV0dXJuIChtID0gcmVIZXgkMi5leGVjKGZvcm1hdCkpID8gKGwgPSBtWzFdLmxlbmd0aCwgbSA9IHBhcnNlSW50KG1bMV0sIDE2KSwgbCA9PT0gNiA/IHJnYm4kMyhtKSAvLyAjZmYwMDAwCiAgICAgICAgICA6IGwgPT09IDMgPyBuZXcgUmdiJDMoKG0gPj4gOCAmIDB4ZikgfCAobSA+PiA0ICYgMHhmMCksIChtID4+IDQgJiAweGYpIHwgKG0gJiAweGYwKSwgKChtICYgMHhmKSA8PCA0KSB8IChtICYgMHhmKSwgMSkgLy8gI2YwMAogICAgICAgICAgOiBsID09PSA4ID8gcmdiYSQzKG0gPj4gMjQgJiAweGZmLCBtID4+IDE2ICYgMHhmZiwgbSA+PiA4ICYgMHhmZiwgKG0gJiAweGZmKSAvIDB4ZmYpIC8vICNmZjAwMDAwMAogICAgICAgICAgOiBsID09PSA0ID8gcmdiYSQzKChtID4+IDEyICYgMHhmKSB8IChtID4+IDggJiAweGYwKSwgKG0gPj4gOCAmIDB4ZikgfCAobSA+PiA0ICYgMHhmMCksIChtID4+IDQgJiAweGYpIHwgKG0gJiAweGYwKSwgKCgobSAmIDB4ZikgPDwgNCkgfCAobSAmIDB4ZikpIC8gMHhmZikgLy8gI2YwMDAKICAgICAgICAgIDogbnVsbCkgLy8gaW52YWxpZCBoZXgKICAgICAgICAgIDogKG0gPSByZVJnYkludGVnZXIkMy5leGVjKGZvcm1hdCkpID8gbmV3IFJnYiQzKG1bMV0sIG1bMl0sIG1bM10sIDEpIC8vIHJnYigyNTUsIDAsIDApCiAgICAgICAgICA6IChtID0gcmVSZ2JQZXJjZW50JDMuZXhlYyhmb3JtYXQpKSA/IG5ldyBSZ2IkMyhtWzFdICogMjU1IC8gMTAwLCBtWzJdICogMjU1IC8gMTAwLCBtWzNdICogMjU1IC8gMTAwLCAxKSAvLyByZ2IoMTAwJSwgMCUsIDAlKQogICAgICAgICAgOiAobSA9IHJlUmdiYUludGVnZXIkMy5leGVjKGZvcm1hdCkpID8gcmdiYSQzKG1bMV0sIG1bMl0sIG1bM10sIG1bNF0pIC8vIHJnYmEoMjU1LCAwLCAwLCAxKQogICAgICAgICAgOiAobSA9IHJlUmdiYVBlcmNlbnQkMy5leGVjKGZvcm1hdCkpID8gcmdiYSQzKG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIG1bNF0pIC8vIHJnYigxMDAlLCAwJSwgMCUsIDEpCiAgICAgICAgICA6IChtID0gcmVIc2xQZXJjZW50JDMuZXhlYyhmb3JtYXQpKSA/IGhzbGEkMyhtWzFdLCBtWzJdIC8gMTAwLCBtWzNdIC8gMTAwLCAxKSAvLyBoc2woMTIwLCA1MCUsIDUwJSkKICAgICAgICAgIDogKG0gPSByZUhzbGFQZXJjZW50JDMuZXhlYyhmb3JtYXQpKSA/IGhzbGEkMyhtWzFdLCBtWzJdIC8gMTAwLCBtWzNdIC8gMTAwLCBtWzRdKSAvLyBoc2xhKDEyMCwgNTAlLCA1MCUsIDEpCiAgICAgICAgICA6IG5hbWVkJDMuaGFzT3duUHJvcGVydHkoZm9ybWF0KSA/IHJnYm4kMyhuYW1lZCQzW2Zvcm1hdF0pIC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tcHJvdG90eXBlLWJ1aWx0aW5zCiAgICAgICAgICA6IGZvcm1hdCA9PT0gInRyYW5zcGFyZW50IiA/IG5ldyBSZ2IkMyhOYU4sIE5hTiwgTmFOLCAwKQogICAgICAgICAgOiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYm4kMyhuKSB7CiAgICAgIHJldHVybiBuZXcgUmdiJDMobiA+PiAxNiAmIDB4ZmYsIG4gPj4gOCAmIDB4ZmYsIG4gJiAweGZmLCAxKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JhJDMociwgZywgYiwgYSkgewogICAgICBpZiAoYSA8PSAwKSByID0gZyA9IGIgPSBOYU47CiAgICAgIHJldHVybiBuZXcgUmdiJDMociwgZywgYiwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiQ29udmVydCQzKG8pIHsKICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIENvbG9yJDMpKSBvID0gY29sb3IkMyhvKTsKICAgICAgaWYgKCFvKSByZXR1cm4gbmV3IFJnYiQzOwogICAgICBvID0gby5yZ2IoKTsKICAgICAgcmV0dXJuIG5ldyBSZ2IkMyhvLnIsIG8uZywgby5iLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYiQzKHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyByZ2JDb252ZXJ0JDMocikgOiBuZXcgUmdiJDMociwgZywgYiwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIFJnYiQzKHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5yID0gK3I7CiAgICAgIHRoaXMuZyA9ICtnOwogICAgICB0aGlzLmIgPSArYjsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDMoUmdiJDMsIHJnYiQzLCBleHRlbmQkMyhDb2xvciQzLCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDMgOiBNYXRoLnBvdyhicmlnaHRlciQzLCBrKTsKICAgICAgICByZXR1cm4gbmV3IFJnYiQzKHRoaXMuciAqIGssIHRoaXMuZyAqIGssIHRoaXMuYiAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIkMyA6IE1hdGgucG93KGRhcmtlciQzLCBrKTsKICAgICAgICByZXR1cm4gbmV3IFJnYiQzKHRoaXMuciAqIGssIHRoaXMuZyAqIGssIHRoaXMuYiAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIHJnYjogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIGRpc3BsYXlhYmxlOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gKC0wLjUgPD0gdGhpcy5yICYmIHRoaXMuciA8IDI1NS41KQogICAgICAgICAgICAmJiAoLTAuNSA8PSB0aGlzLmcgJiYgdGhpcy5nIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgtMC41IDw9IHRoaXMuYiAmJiB0aGlzLmIgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5vcGFjaXR5ICYmIHRoaXMub3BhY2l0eSA8PSAxKTsKICAgICAgfSwKICAgICAgaGV4OiByZ2JfZm9ybWF0SGV4JDIsIC8vIERlcHJlY2F0ZWQhIFVzZSBjb2xvci5mb3JtYXRIZXguCiAgICAgIGZvcm1hdEhleDogcmdiX2Zvcm1hdEhleCQyLAogICAgICBmb3JtYXRSZ2I6IHJnYl9mb3JtYXRSZ2IkMiwKICAgICAgdG9TdHJpbmc6IHJnYl9mb3JtYXRSZ2IkMgogICAgfSkpOwoKICAgIGZ1bmN0aW9uIHJnYl9mb3JtYXRIZXgkMigpIHsKICAgICAgcmV0dXJuICIjIiArIGhleCQyKHRoaXMucikgKyBoZXgkMih0aGlzLmcpICsgaGV4JDIodGhpcy5iKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JfZm9ybWF0UmdiJDIoKSB7CiAgICAgIHZhciBhID0gdGhpcy5vcGFjaXR5OyBhID0gaXNOYU4oYSkgPyAxIDogTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgYSkpOwogICAgICByZXR1cm4gKGEgPT09IDEgPyAicmdiKCIgOiAicmdiYSgiKQogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5yKSB8fCAwKSkgKyAiLCAiCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLmcpIHx8IDApKSArICIsICIKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuYikgfHwgMCkpCiAgICAgICAgICArIChhID09PSAxID8gIikiIDogIiwgIiArIGEgKyAiKSIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhleCQyKHZhbHVlKSB7CiAgICAgIHZhbHVlID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHZhbHVlKSB8fCAwKSk7CiAgICAgIHJldHVybiAodmFsdWUgPCAxNiA/ICIwIiA6ICIiKSArIHZhbHVlLnRvU3RyaW5nKDE2KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xhJDMoaCwgcywgbCwgYSkgewogICAgICBpZiAoYSA8PSAwKSBoID0gcyA9IGwgPSBOYU47CiAgICAgIGVsc2UgaWYgKGwgPD0gMCB8fCBsID49IDEpIGggPSBzID0gTmFOOwogICAgICBlbHNlIGlmIChzIDw9IDApIGggPSBOYU47CiAgICAgIHJldHVybiBuZXcgSHNsJDMoaCwgcywgbCwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsQ29udmVydCQzKG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wkMykgcmV0dXJuIG5ldyBIc2wkMyhvLmgsIG8ucywgby5sLCBvLm9wYWNpdHkpOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgQ29sb3IkMykpIG8gPSBjb2xvciQzKG8pOwogICAgICBpZiAoIW8pIHJldHVybiBuZXcgSHNsJDM7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgSHNsJDMpIHJldHVybiBvOwogICAgICBvID0gby5yZ2IoKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIG1pbiA9IE1hdGgubWluKHIsIGcsIGIpLAogICAgICAgICAgbWF4ID0gTWF0aC5tYXgociwgZywgYiksCiAgICAgICAgICBoID0gTmFOLAogICAgICAgICAgcyA9IG1heCAtIG1pbiwKICAgICAgICAgIGwgPSAobWF4ICsgbWluKSAvIDI7CiAgICAgIGlmIChzKSB7CiAgICAgICAgaWYgKHIgPT09IG1heCkgaCA9IChnIC0gYikgLyBzICsgKGcgPCBiKSAqIDY7CiAgICAgICAgZWxzZSBpZiAoZyA9PT0gbWF4KSBoID0gKGIgLSByKSAvIHMgKyAyOwogICAgICAgIGVsc2UgaCA9IChyIC0gZykgLyBzICsgNDsKICAgICAgICBzIC89IGwgPCAwLjUgPyBtYXggKyBtaW4gOiAyIC0gbWF4IC0gbWluOwogICAgICAgIGggKj0gNjA7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcyA9IGwgPiAwICYmIGwgPCAxID8gMCA6IGg7CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBIc2wkMyhoLCBzLCBsLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbCQ1KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBoc2xDb252ZXJ0JDMoaCkgOiBuZXcgSHNsJDMoaCwgcywgbCwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIEhzbCQzKGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5oID0gK2g7CiAgICAgIHRoaXMucyA9ICtzOwogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDMoSHNsJDMsIGhzbCQ1LCBleHRlbmQkMyhDb2xvciQzLCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDMgOiBNYXRoLnBvdyhicmlnaHRlciQzLCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCQzKHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDMgOiBNYXRoLnBvdyhkYXJrZXIkMywgayk7CiAgICAgICAgcmV0dXJuIG5ldyBIc2wkMyh0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaCA9IHRoaXMuaCAlIDM2MCArICh0aGlzLmggPCAwKSAqIDM2MCwKICAgICAgICAgICAgcyA9IGlzTmFOKGgpIHx8IGlzTmFOKHRoaXMucykgPyAwIDogdGhpcy5zLAogICAgICAgICAgICBsID0gdGhpcy5sLAogICAgICAgICAgICBtMiA9IGwgKyAobCA8IDAuNSA/IGwgOiAxIC0gbCkgKiBzLAogICAgICAgICAgICBtMSA9IDIgKiBsIC0gbTI7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMygKICAgICAgICAgIGhzbDJyZ2IkMyhoID49IDI0MCA/IGggLSAyNDAgOiBoICsgMTIwLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYiQzKGgsIG0xLCBtMiksCiAgICAgICAgICBoc2wycmdiJDMoaCA8IDEyMCA/IGggKyAyNDAgOiBoIC0gMTIwLCBtMSwgbTIpLAogICAgICAgICAgdGhpcy5vcGFjaXR5CiAgICAgICAgKTsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoMCA8PSB0aGlzLnMgJiYgdGhpcy5zIDw9IDEgfHwgaXNOYU4odGhpcy5zKSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5sICYmIHRoaXMubCA8PSAxKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9LAogICAgICBmb3JtYXRIc2w6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBhID0gdGhpcy5vcGFjaXR5OyBhID0gaXNOYU4oYSkgPyAxIDogTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgYSkpOwogICAgICAgIHJldHVybiAoYSA9PT0gMSA/ICJoc2woIiA6ICJoc2xhKCIpCiAgICAgICAgICAgICsgKHRoaXMuaCB8fCAwKSArICIsICIKICAgICAgICAgICAgKyAodGhpcy5zIHx8IDApICogMTAwICsgIiUsICIKICAgICAgICAgICAgKyAodGhpcy5sIHx8IDApICogMTAwICsgIiUiCiAgICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICAgIH0KICAgIH0pKTsKCiAgICAvKiBGcm9tIEZ2RCAxMy4zNywgQ1NTIENvbG9yIE1vZHVsZSBMZXZlbCAzICovCiAgICBmdW5jdGlvbiBoc2wycmdiJDMoaCwgbTEsIG0yKSB7CiAgICAgIHJldHVybiAoaCA8IDYwID8gbTEgKyAobTIgLSBtMSkgKiBoIC8gNjAKICAgICAgICAgIDogaCA8IDE4MCA/IG0yCiAgICAgICAgICA6IGggPCAyNDAgPyBtMSArIChtMiAtIG0xKSAqICgyNDAgLSBoKSAvIDYwCiAgICAgICAgICA6IG0xKSAqIDI1NTsKICAgIH0KCiAgICB2YXIgZGVnMnJhZCQyID0gTWF0aC5QSSAvIDE4MDsKICAgIHZhciByYWQyZGVnJDIgPSAxODAgLyBNYXRoLlBJOwoKICAgIC8vIGh0dHBzOi8vb2JzZXJ2YWJsZWhxLmNvbS9AbWJvc3RvY2svbGFiLWFuZC1yZ2IKICAgIHZhciBLJDEgPSAxOCwKICAgICAgICBYbiQyID0gMC45NjQyMiwKICAgICAgICBZbiQyID0gMSwKICAgICAgICBabiQyID0gMC44MjUyMSwKICAgICAgICB0MCQzID0gNCAvIDI5LAogICAgICAgIHQxJDMgPSA2IC8gMjksCiAgICAgICAgdDIkMiA9IDMgKiB0MSQzICogdDEkMywKICAgICAgICB0MyQyID0gdDEkMyAqIHQxJDMgKiB0MSQzOwoKICAgIGZ1bmN0aW9uIGxhYkNvbnZlcnQkMihvKSB7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgTGFiJDIpIHJldHVybiBuZXcgTGFiJDIoby5sLCBvLmEsIG8uYiwgby5vcGFjaXR5KTsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIY2wkMikgcmV0dXJuIGhjbDJsYWIkMShvKTsKICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIFJnYiQzKSkgbyA9IHJnYkNvbnZlcnQkMyhvKTsKICAgICAgdmFyIHIgPSByZ2IybHJnYiQxKG8uciksCiAgICAgICAgICBnID0gcmdiMmxyZ2IkMShvLmcpLAogICAgICAgICAgYiA9IHJnYjJscmdiJDEoby5iKSwKICAgICAgICAgIHkgPSB4eXoybGFiJDIoKDAuMjIyNTA0NSAqIHIgKyAwLjcxNjg3ODYgKiBnICsgMC4wNjA2MTY5ICogYikgLyBZbiQyKSwgeCwgejsKICAgICAgaWYgKHIgPT09IGcgJiYgZyA9PT0gYikgeCA9IHogPSB5OyBlbHNlIHsKICAgICAgICB4ID0geHl6MmxhYiQyKCgwLjQzNjA3NDcgKiByICsgMC4zODUwNjQ5ICogZyArIDAuMTQzMDgwNCAqIGIpIC8gWG4kMik7CiAgICAgICAgeiA9IHh5ejJsYWIkMigoMC4wMTM5MzIyICogciArIDAuMDk3MTA0NSAqIGcgKyAwLjcxNDE3MzMgKiBiKSAvIFpuJDIpOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgTGFiJDIoMTE2ICogeSAtIDE2LCA1MDAgKiAoeCAtIHkpLCAyMDAgKiAoeSAtIHopLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGxhYiQzKGwsIGEsIGIsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBsYWJDb252ZXJ0JDIobCkgOiBuZXcgTGFiJDIobCwgYSwgYiwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIExhYiQyKGwsIGEsIGIsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5sID0gK2w7CiAgICAgIHRoaXMuYSA9ICthOwogICAgICB0aGlzLmIgPSArYjsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDMoTGFiJDIsIGxhYiQzLCBleHRlbmQkMyhDb2xvciQzLCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBMYWIkMih0aGlzLmwgKyBLJDEgKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLmEsIHRoaXMuYiwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBMYWIkMih0aGlzLmwgLSBLJDEgKiAoayA9PSBudWxsID8gMSA6IGspLCB0aGlzLmEsIHRoaXMuYiwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgeSA9ICh0aGlzLmwgKyAxNikgLyAxMTYsCiAgICAgICAgICAgIHggPSBpc05hTih0aGlzLmEpID8geSA6IHkgKyB0aGlzLmEgLyA1MDAsCiAgICAgICAgICAgIHogPSBpc05hTih0aGlzLmIpID8geSA6IHkgLSB0aGlzLmIgLyAyMDA7CiAgICAgICAgeCA9IFhuJDIgKiBsYWIyeHl6JDIoeCk7CiAgICAgICAgeSA9IFluJDIgKiBsYWIyeHl6JDIoeSk7CiAgICAgICAgeiA9IFpuJDIgKiBsYWIyeHl6JDIoeik7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkMygKICAgICAgICAgIGxyZ2IycmdiJDEoIDMuMTMzODU2MSAqIHggLSAxLjYxNjg2NjcgKiB5IC0gMC40OTA2MTQ2ICogeiksCiAgICAgICAgICBscmdiMnJnYiQxKC0wLjk3ODc2ODQgKiB4ICsgMS45MTYxNDE1ICogeSArIDAuMDMzNDU0MCAqIHopLAogICAgICAgICAgbHJnYjJyZ2IkMSggMC4wNzE5NDUzICogeCAtIDAuMjI4OTkxNCAqIHkgKyAxLjQwNTI0MjcgKiB6KSwKICAgICAgICAgIHRoaXMub3BhY2l0eQogICAgICAgICk7CiAgICAgIH0KICAgIH0pKTsKCiAgICBmdW5jdGlvbiB4eXoybGFiJDIodCkgewogICAgICByZXR1cm4gdCA+IHQzJDIgPyBNYXRoLnBvdyh0LCAxIC8gMykgOiB0IC8gdDIkMiArIHQwJDM7CiAgICB9CgogICAgZnVuY3Rpb24gbGFiMnh5eiQyKHQpIHsKICAgICAgcmV0dXJuIHQgPiB0MSQzID8gdCAqIHQgKiB0IDogdDIkMiAqICh0IC0gdDAkMyk7CiAgICB9CgogICAgZnVuY3Rpb24gbHJnYjJyZ2IkMSh4KSB7CiAgICAgIHJldHVybiAyNTUgKiAoeCA8PSAwLjAwMzEzMDggPyAxMi45MiAqIHggOiAxLjA1NSAqIE1hdGgucG93KHgsIDEgLyAyLjQpIC0gMC4wNTUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYjJscmdiJDEoeCkgewogICAgICByZXR1cm4gKHggLz0gMjU1KSA8PSAwLjA0MDQ1ID8geCAvIDEyLjkyIDogTWF0aC5wb3coKHggKyAwLjA1NSkgLyAxLjA1NSwgMi40KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2xDb252ZXJ0JDIobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIEhjbCQyKSByZXR1cm4gbmV3IEhjbCQyKG8uaCwgby5jLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBMYWIkMikpIG8gPSBsYWJDb252ZXJ0JDIobyk7CiAgICAgIGlmIChvLmEgPT09IDAgJiYgby5iID09PSAwKSByZXR1cm4gbmV3IEhjbCQyKE5hTiwgMCA8IG8ubCAmJiBvLmwgPCAxMDAgPyAwIDogTmFOLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIHZhciBoID0gTWF0aC5hdGFuMihvLmIsIG8uYSkgKiByYWQyZGVnJDI7CiAgICAgIHJldHVybiBuZXcgSGNsJDIoaCA8IDAgPyBoICsgMzYwIDogaCwgTWF0aC5zcXJ0KG8uYSAqIG8uYSArIG8uYiAqIG8uYiksIG8ubCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoY2wkNChoLCBjLCBsLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gaGNsQ29udmVydCQyKGgpIDogbmV3IEhjbCQyKGgsIGMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBIY2wkMihoLCBjLCBsLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuaCA9ICtoOwogICAgICB0aGlzLmMgPSArYzsKICAgICAgdGhpcy5sID0gK2w7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGZ1bmN0aW9uIGhjbDJsYWIkMShvKSB7CiAgICAgIGlmIChpc05hTihvLmgpKSByZXR1cm4gbmV3IExhYiQyKG8ubCwgMCwgMCwgby5vcGFjaXR5KTsKICAgICAgdmFyIGggPSBvLmggKiBkZWcycmFkJDI7CiAgICAgIHJldHVybiBuZXcgTGFiJDIoby5sLCBNYXRoLmNvcyhoKSAqIG8uYywgTWF0aC5zaW4oaCkgKiBvLmMsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZGVmaW5lJDMoSGNsJDIsIGhjbCQ0LCBleHRlbmQkMyhDb2xvciQzLCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBIY2wkMih0aGlzLmgsIHRoaXMuYywgdGhpcy5sICsgSyQxICogKGsgPT0gbnVsbCA/IDEgOiBrKSwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIG5ldyBIY2wkMih0aGlzLmgsIHRoaXMuYywgdGhpcy5sIC0gSyQxICogKGsgPT0gbnVsbCA/IDEgOiBrKSwgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gaGNsMmxhYiQxKHRoaXMpLnJnYigpOwogICAgICB9CiAgICB9KSk7CgogICAgdmFyIEEkMiA9IC0wLjE0ODYxLAogICAgICAgIEIkMiA9ICsxLjc4Mjc3LAogICAgICAgIEMkMiA9IC0wLjI5MjI3LAogICAgICAgIEQkMiA9IC0wLjkwNjQ5LAogICAgICAgIEUkMiA9ICsxLjk3Mjk0LAogICAgICAgIEVEJDIgPSBFJDIgKiBEJDIsCiAgICAgICAgRUIkMiA9IEUkMiAqIEIkMiwKICAgICAgICBCQ19EQSQyID0gQiQyICogQyQyIC0gRCQyICogQSQyOwoKICAgIGZ1bmN0aW9uIGN1YmVoZWxpeENvbnZlcnQkMihvKSB7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgQ3ViZWhlbGl4JDIpIHJldHVybiBuZXcgQ3ViZWhlbGl4JDIoby5oLCBvLnMsIG8ubCwgby5vcGFjaXR5KTsKICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIFJnYiQzKSkgbyA9IHJnYkNvbnZlcnQkMyhvKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIGwgPSAoQkNfREEkMiAqIGIgKyBFRCQyICogciAtIEVCJDIgKiBnKSAvIChCQ19EQSQyICsgRUQkMiAtIEVCJDIpLAogICAgICAgICAgYmwgPSBiIC0gbCwKICAgICAgICAgIGsgPSAoRSQyICogKGcgLSBsKSAtIEMkMiAqIGJsKSAvIEQkMiwKICAgICAgICAgIHMgPSBNYXRoLnNxcnQoayAqIGsgKyBibCAqIGJsKSAvIChFJDIgKiBsICogKDEgLSBsKSksIC8vIE5hTiBpZiBsPTAgb3IgbD0xCiAgICAgICAgICBoID0gcyA/IE1hdGguYXRhbjIoaywgYmwpICogcmFkMmRlZyQyIC0gMTIwIDogTmFOOwogICAgICByZXR1cm4gbmV3IEN1YmVoZWxpeCQyKGggPCAwID8gaCArIDM2MCA6IGgsIHMsIGwsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3ViZWhlbGl4JDUoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGN1YmVoZWxpeENvbnZlcnQkMihoKSA6IG5ldyBDdWJlaGVsaXgkMihoLCBzLCBsLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gQ3ViZWhlbGl4JDIoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICB0aGlzLmggPSAraDsKICAgICAgdGhpcy5zID0gK3M7CiAgICAgIHRoaXMubCA9ICtsOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkMyhDdWJlaGVsaXgkMiwgY3ViZWhlbGl4JDUsIGV4dGVuZCQzKENvbG9yJDMsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIkMyA6IE1hdGgucG93KGJyaWdodGVyJDMsIGspOwogICAgICAgIHJldHVybiBuZXcgQ3ViZWhlbGl4JDIodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIkMyA6IE1hdGgucG93KGRhcmtlciQzLCBrKTsKICAgICAgICByZXR1cm4gbmV3IEN1YmVoZWxpeCQyKHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBoID0gaXNOYU4odGhpcy5oKSA/IDAgOiAodGhpcy5oICsgMTIwKSAqIGRlZzJyYWQkMiwKICAgICAgICAgICAgbCA9ICt0aGlzLmwsCiAgICAgICAgICAgIGEgPSBpc05hTih0aGlzLnMpID8gMCA6IHRoaXMucyAqIGwgKiAoMSAtIGwpLAogICAgICAgICAgICBjb3NoID0gTWF0aC5jb3MoaCksCiAgICAgICAgICAgIHNpbmggPSBNYXRoLnNpbihoKTsKICAgICAgICByZXR1cm4gbmV3IFJnYiQzKAogICAgICAgICAgMjU1ICogKGwgKyBhICogKEEkMiAqIGNvc2ggKyBCJDIgKiBzaW5oKSksCiAgICAgICAgICAyNTUgKiAobCArIGEgKiAoQyQyICogY29zaCArIEQkMiAqIHNpbmgpKSwKICAgICAgICAgIDI1NSAqIChsICsgYSAqIChFJDIgKiBjb3NoKSksCiAgICAgICAgICB0aGlzLm9wYWNpdHkKICAgICAgICApOwogICAgICB9CiAgICB9KSk7CgogICAgZnVuY3Rpb24gYmFzaXMkMyh0MSwgdjAsIHYxLCB2MiwgdjMpIHsKICAgICAgdmFyIHQyID0gdDEgKiB0MSwgdDMgPSB0MiAqIHQxOwogICAgICByZXR1cm4gKCgxIC0gMyAqIHQxICsgMyAqIHQyIC0gdDMpICogdjAKICAgICAgICAgICsgKDQgLSA2ICogdDIgKyAzICogdDMpICogdjEKICAgICAgICAgICsgKDEgKyAzICogdDEgKyAzICogdDIgLSAzICogdDMpICogdjIKICAgICAgICAgICsgdDMgKiB2MykgLyA2OwogICAgfQoKICAgIGZ1bmN0aW9uIGJhc2lzJDQodmFsdWVzKSB7CiAgICAgIHZhciBuID0gdmFsdWVzLmxlbmd0aCAtIDE7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIGkgPSB0IDw9IDAgPyAodCA9IDApIDogdCA+PSAxID8gKHQgPSAxLCBuIC0gMSkgOiBNYXRoLmZsb29yKHQgKiBuKSwKICAgICAgICAgICAgdjEgPSB2YWx1ZXNbaV0sCiAgICAgICAgICAgIHYyID0gdmFsdWVzW2kgKyAxXSwKICAgICAgICAgICAgdjAgPSBpID4gMCA/IHZhbHVlc1tpIC0gMV0gOiAyICogdjEgLSB2MiwKICAgICAgICAgICAgdjMgPSBpIDwgbiAtIDEgPyB2YWx1ZXNbaSArIDJdIDogMiAqIHYyIC0gdjE7CiAgICAgICAgcmV0dXJuIGJhc2lzJDMoKHQgLSBpIC8gbikgKiBuLCB2MCwgdjEsIHYyLCB2Myk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYmFzaXNDbG9zZWQkMih2YWx1ZXMpIHsKICAgICAgdmFyIG4gPSB2YWx1ZXMubGVuZ3RoOwogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHZhciBpID0gTWF0aC5mbG9vcigoKHQgJT0gMSkgPCAwID8gKyt0IDogdCkgKiBuKSwKICAgICAgICAgICAgdjAgPSB2YWx1ZXNbKGkgKyBuIC0gMSkgJSBuXSwKICAgICAgICAgICAgdjEgPSB2YWx1ZXNbaSAlIG5dLAogICAgICAgICAgICB2MiA9IHZhbHVlc1soaSArIDEpICUgbl0sCiAgICAgICAgICAgIHYzID0gdmFsdWVzWyhpICsgMikgJSBuXTsKICAgICAgICByZXR1cm4gYmFzaXMkMygodCAtIGkgLyBuKSAqIG4sIHYwLCB2MSwgdjIsIHYzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudCRvKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVhciQ1KGEsIGQpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICByZXR1cm4gYSArIHQgKiBkOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4cG9uZW50aWFsJDMoYSwgYiwgeSkgewogICAgICByZXR1cm4gYSA9IE1hdGgucG93KGEsIHkpLCBiID0gTWF0aC5wb3coYiwgeSkgLSBhLCB5ID0gMSAvIHksIGZ1bmN0aW9uKHQpIHsKICAgICAgICByZXR1cm4gTWF0aC5wb3coYSArIHQgKiBiLCB5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBodWUkMihhLCBiKSB7CiAgICAgIHZhciBkID0gYiAtIGE7CiAgICAgIHJldHVybiBkID8gbGluZWFyJDUoYSwgZCA+IDE4MCB8fCBkIDwgLTE4MCA/IGQgLSAzNjAgKiBNYXRoLnJvdW5kKGQgLyAzNjApIDogZCkgOiBjb25zdGFudCRvKGlzTmFOKGEpID8gYiA6IGEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGdhbW1hJDIoeSkgewogICAgICByZXR1cm4gKHkgPSAreSkgPT09IDEgPyBub2dhbW1hJDIgOiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgcmV0dXJuIGIgLSBhID8gZXhwb25lbnRpYWwkMyhhLCBiLCB5KSA6IGNvbnN0YW50JG8oaXNOYU4oYSkgPyBiIDogYSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbm9nYW1tYSQyKGEsIGIpIHsKICAgICAgdmFyIGQgPSBiIC0gYTsKICAgICAgcmV0dXJuIGQgPyBsaW5lYXIkNShhLCBkKSA6IGNvbnN0YW50JG8oaXNOYU4oYSkgPyBiIDogYSk7CiAgICB9CgogICAgdmFyIHJnYiQ0ID0gKGZ1bmN0aW9uIHJnYkdhbW1hKHkpIHsKICAgICAgdmFyIGNvbG9yID0gZ2FtbWEkMih5KTsKCiAgICAgIGZ1bmN0aW9uIHJnYihzdGFydCwgZW5kKSB7CiAgICAgICAgdmFyIHIgPSBjb2xvcigoc3RhcnQgPSByZ2IkMyhzdGFydCkpLnIsIChlbmQgPSByZ2IkMyhlbmQpKS5yKSwKICAgICAgICAgICAgZyA9IGNvbG9yKHN0YXJ0LmcsIGVuZC5nKSwKICAgICAgICAgICAgYiA9IGNvbG9yKHN0YXJ0LmIsIGVuZC5iKSwKICAgICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEkMihzdGFydC5vcGFjaXR5LCBlbmQub3BhY2l0eSk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHN0YXJ0LnIgPSByKHQpOwogICAgICAgICAgc3RhcnQuZyA9IGcodCk7CiAgICAgICAgICBzdGFydC5iID0gYih0KTsKICAgICAgICAgIHN0YXJ0Lm9wYWNpdHkgPSBvcGFjaXR5KHQpOwogICAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgcmdiLmdhbW1hID0gcmdiR2FtbWE7CgogICAgICByZXR1cm4gcmdiOwogICAgfSkoMSk7CgogICAgZnVuY3Rpb24gcmdiU3BsaW5lJDEoc3BsaW5lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihjb2xvcnMpIHsKICAgICAgICB2YXIgbiA9IGNvbG9ycy5sZW5ndGgsCiAgICAgICAgICAgIHIgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIGcgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIGIgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIGksIGNvbG9yOwogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGNvbG9yID0gcmdiJDMoY29sb3JzW2ldKTsKICAgICAgICAgIHJbaV0gPSBjb2xvci5yIHx8IDA7CiAgICAgICAgICBnW2ldID0gY29sb3IuZyB8fCAwOwogICAgICAgICAgYltpXSA9IGNvbG9yLmIgfHwgMDsKICAgICAgICB9CiAgICAgICAgciA9IHNwbGluZShyKTsKICAgICAgICBnID0gc3BsaW5lKGcpOwogICAgICAgIGIgPSBzcGxpbmUoYik7CiAgICAgICAgY29sb3Iub3BhY2l0eSA9IDE7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIGNvbG9yLnIgPSByKHQpOwogICAgICAgICAgY29sb3IuZyA9IGcodCk7CiAgICAgICAgICBjb2xvci5iID0gYih0KTsKICAgICAgICAgIHJldHVybiBjb2xvciArICIiOwogICAgICAgIH07CiAgICAgIH07CiAgICB9CgogICAgdmFyIHJnYkJhc2lzJDEgPSByZ2JTcGxpbmUkMShiYXNpcyQ0KTsKICAgIHZhciByZ2JCYXNpc0Nsb3NlZCQxID0gcmdiU3BsaW5lJDEoYmFzaXNDbG9zZWQkMik7CgogICAgZnVuY3Rpb24gYXJyYXkkNShhLCBiKSB7CiAgICAgIHZhciBuYiA9IGIgPyBiLmxlbmd0aCA6IDAsCiAgICAgICAgICBuYSA9IGEgPyBNYXRoLm1pbihuYiwgYS5sZW5ndGgpIDogMCwKICAgICAgICAgIHggPSBuZXcgQXJyYXkobmEpLAogICAgICAgICAgYyA9IG5ldyBBcnJheShuYiksCiAgICAgICAgICBpOwoKICAgICAgZm9yIChpID0gMDsgaSA8IG5hOyArK2kpIHhbaV0gPSB2YWx1ZShhW2ldLCBiW2ldKTsKICAgICAgZm9yICg7IGkgPCBuYjsgKytpKSBjW2ldID0gYltpXTsKCiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG5hOyArK2kpIGNbaV0gPSB4W2ldKHQpOwogICAgICAgIHJldHVybiBjOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRhdGUkMyhhLCBiKSB7CiAgICAgIHZhciBkID0gbmV3IERhdGU7CiAgICAgIHJldHVybiBhID0gK2EsIGIgLT0gYSwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBkLnNldFRpbWUoYSArIGIgKiB0KSwgZDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBudW1iZXIkNihhLCBiKSB7CiAgICAgIHJldHVybiBhID0gK2EsIGIgLT0gYSwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICsgYiAqIHQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb2JqZWN0JDQoYSwgYikgewogICAgICB2YXIgaSA9IHt9LAogICAgICAgICAgYyA9IHt9LAogICAgICAgICAgazsKCiAgICAgIGlmIChhID09PSBudWxsIHx8IHR5cGVvZiBhICE9PSAib2JqZWN0IikgYSA9IHt9OwogICAgICBpZiAoYiA9PT0gbnVsbCB8fCB0eXBlb2YgYiAhPT0gIm9iamVjdCIpIGIgPSB7fTsKCiAgICAgIGZvciAoayBpbiBiKSB7CiAgICAgICAgaWYgKGsgaW4gYSkgewogICAgICAgICAgaVtrXSA9IHZhbHVlKGFba10sIGJba10pOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBjW2tdID0gYltrXTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChrIGluIGkpIGNba10gPSBpW2tdKHQpOwogICAgICAgIHJldHVybiBjOwogICAgICB9OwogICAgfQoKICAgIHZhciByZUEkMiA9IC9bLStdPyg/OlxkK1wuP1xkKnxcLj9cZCspKD86W2VFXVstK10/XGQrKT8vZywKICAgICAgICByZUIkMiA9IG5ldyBSZWdFeHAocmVBJDIuc291cmNlLCAiZyIpOwoKICAgIGZ1bmN0aW9uIHplcm8kMihiKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBvbmUkMihiKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGIodCkgKyAiIjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHJpbmcoYSwgYikgewogICAgICB2YXIgYmkgPSByZUEkMi5sYXN0SW5kZXggPSByZUIkMi5sYXN0SW5kZXggPSAwLCAvLyBzY2FuIGluZGV4IGZvciBuZXh0IG51bWJlciBpbiBiCiAgICAgICAgICBhbSwgLy8gY3VycmVudCBtYXRjaCBpbiBhCiAgICAgICAgICBibSwgLy8gY3VycmVudCBtYXRjaCBpbiBiCiAgICAgICAgICBicywgLy8gc3RyaW5nIHByZWNlZGluZyBjdXJyZW50IG51bWJlciBpbiBiLCBpZiBhbnkKICAgICAgICAgIGkgPSAtMSwgLy8gaW5kZXggaW4gcwogICAgICAgICAgcyA9IFtdLCAvLyBzdHJpbmcgY29uc3RhbnRzIGFuZCBwbGFjZWhvbGRlcnMKICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKCiAgICAgIC8vIENvZXJjZSBpbnB1dHMgdG8gc3RyaW5ncy4KICAgICAgYSA9IGEgKyAiIiwgYiA9IGIgKyAiIjsKCiAgICAgIC8vIEludGVycG9sYXRlIHBhaXJzIG9mIG51bWJlcnMgaW4gYSAmIGIuCiAgICAgIHdoaWxlICgoYW0gPSByZUEkMi5leGVjKGEpKQogICAgICAgICAgJiYgKGJtID0gcmVCJDIuZXhlYyhiKSkpIHsKICAgICAgICBpZiAoKGJzID0gYm0uaW5kZXgpID4gYmkpIHsgLy8gYSBzdHJpbmcgcHJlY2VkZXMgdGhlIG5leHQgbnVtYmVyIGluIGIKICAgICAgICAgIGJzID0gYi5zbGljZShiaSwgYnMpOwogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICAgIH0KICAgICAgICBpZiAoKGFtID0gYW1bMF0pID09PSAoYm0gPSBibVswXSkpIHsgLy8gbnVtYmVycyBpbiBhICYgYiBtYXRjaAogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYm07IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJtOwogICAgICAgIH0gZWxzZSB7IC8vIGludGVycG9sYXRlIG5vbi1tYXRjaGluZyBudW1iZXJzCiAgICAgICAgICBzWysraV0gPSBudWxsOwogICAgICAgICAgcS5wdXNoKHtpOiBpLCB4OiBudW1iZXIkNihhbSwgYm0pfSk7CiAgICAgICAgfQogICAgICAgIGJpID0gcmVCJDIubGFzdEluZGV4OwogICAgICB9CgogICAgICAvLyBBZGQgcmVtYWlucyBvZiBiLgogICAgICBpZiAoYmkgPCBiLmxlbmd0aCkgewogICAgICAgIGJzID0gYi5zbGljZShiaSk7CiAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgZWxzZSBzWysraV0gPSBiczsKICAgICAgfQoKICAgICAgLy8gU3BlY2lhbCBvcHRpbWl6YXRpb24gZm9yIG9ubHkgYSBzaW5nbGUgbWF0Y2guCiAgICAgIC8vIE90aGVyd2lzZSwgaW50ZXJwb2xhdGUgZWFjaCBvZiB0aGUgbnVtYmVycyBhbmQgcmVqb2luIHRoZSBzdHJpbmcuCiAgICAgIHJldHVybiBzLmxlbmd0aCA8IDIgPyAocVswXQogICAgICAgICAgPyBvbmUkMihxWzBdLngpCiAgICAgICAgICA6IHplcm8kMihiKSkKICAgICAgICAgIDogKGIgPSBxLmxlbmd0aCwgZnVuY3Rpb24odCkgewogICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBvOyBpIDwgYjsgKytpKSBzWyhvID0gcVtpXSkuaV0gPSBvLngodCk7CiAgICAgICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHZhbHVlKGEsIGIpIHsKICAgICAgdmFyIHQgPSB0eXBlb2YgYiwgYzsKICAgICAgcmV0dXJuIGIgPT0gbnVsbCB8fCB0ID09PSAiYm9vbGVhbiIgPyBjb25zdGFudCRvKGIpCiAgICAgICAgICA6ICh0ID09PSAibnVtYmVyIiA/IG51bWJlciQ2CiAgICAgICAgICA6IHQgPT09ICJzdHJpbmciID8gKChjID0gY29sb3IkMyhiKSkgPyAoYiA9IGMsIHJnYiQ0KSA6IHN0cmluZykKICAgICAgICAgIDogYiBpbnN0YW5jZW9mIGNvbG9yJDMgPyByZ2IkNAogICAgICAgICAgOiBiIGluc3RhbmNlb2YgRGF0ZSA/IGRhdGUkMwogICAgICAgICAgOiBBcnJheS5pc0FycmF5KGIpID8gYXJyYXkkNQogICAgICAgICAgOiB0eXBlb2YgYi52YWx1ZU9mICE9PSAiZnVuY3Rpb24iICYmIHR5cGVvZiBiLnRvU3RyaW5nICE9PSAiZnVuY3Rpb24iIHx8IGlzTmFOKGIpID8gb2JqZWN0JDQKICAgICAgICAgIDogbnVtYmVyJDYpKGEsIGIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJvdW5kKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPSArYSwgYiAtPSBhLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIE1hdGgucm91bmQoYSArIGIgKiB0KTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgZGVncmVlcyQ0ID0gMTgwIC8gTWF0aC5QSTsKCiAgICB2YXIgaWRlbnRpdHkkZyA9IHsKICAgICAgdHJhbnNsYXRlWDogMCwKICAgICAgdHJhbnNsYXRlWTogMCwKICAgICAgcm90YXRlOiAwLAogICAgICBza2V3WDogMCwKICAgICAgc2NhbGVYOiAxLAogICAgICBzY2FsZVk6IDEKICAgIH07CgogICAgZnVuY3Rpb24gZGVjb21wb3NlJDIoYSwgYiwgYywgZCwgZSwgZikgewogICAgICB2YXIgc2NhbGVYLCBzY2FsZVksIHNrZXdYOwogICAgICBpZiAoc2NhbGVYID0gTWF0aC5zcXJ0KGEgKiBhICsgYiAqIGIpKSBhIC89IHNjYWxlWCwgYiAvPSBzY2FsZVg7CiAgICAgIGlmIChza2V3WCA9IGEgKiBjICsgYiAqIGQpIGMgLT0gYSAqIHNrZXdYLCBkIC09IGIgKiBza2V3WDsKICAgICAgaWYgKHNjYWxlWSA9IE1hdGguc3FydChjICogYyArIGQgKiBkKSkgYyAvPSBzY2FsZVksIGQgLz0gc2NhbGVZLCBza2V3WCAvPSBzY2FsZVk7CiAgICAgIGlmIChhICogZCA8IGIgKiBjKSBhID0gLWEsIGIgPSAtYiwgc2tld1ggPSAtc2tld1gsIHNjYWxlWCA9IC1zY2FsZVg7CiAgICAgIHJldHVybiB7CiAgICAgICAgdHJhbnNsYXRlWDogZSwKICAgICAgICB0cmFuc2xhdGVZOiBmLAogICAgICAgIHJvdGF0ZTogTWF0aC5hdGFuMihiLCBhKSAqIGRlZ3JlZXMkNCwKICAgICAgICBza2V3WDogTWF0aC5hdGFuKHNrZXdYKSAqIGRlZ3JlZXMkNCwKICAgICAgICBzY2FsZVg6IHNjYWxlWCwKICAgICAgICBzY2FsZVk6IHNjYWxlWQogICAgICB9OwogICAgfQoKICAgIHZhciBjc3NOb2RlJDIsCiAgICAgICAgY3NzUm9vdCQyLAogICAgICAgIGNzc1ZpZXckMiwKICAgICAgICBzdmdOb2RlJDI7CgogICAgZnVuY3Rpb24gcGFyc2VDc3MkMyh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgPT09ICJub25lIikgcmV0dXJuIGlkZW50aXR5JGc7CiAgICAgIGlmICghY3NzTm9kZSQyKSBjc3NOb2RlJDIgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCJESVYiKSwgY3NzUm9vdCQyID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LCBjc3NWaWV3JDIgPSBkb2N1bWVudC5kZWZhdWx0VmlldzsKICAgICAgY3NzTm9kZSQyLnN0eWxlLnRyYW5zZm9ybSA9IHZhbHVlOwogICAgICB2YWx1ZSA9IGNzc1ZpZXckMi5nZXRDb21wdXRlZFN0eWxlKGNzc1Jvb3QkMi5hcHBlbmRDaGlsZChjc3NOb2RlJDIpLCBudWxsKS5nZXRQcm9wZXJ0eVZhbHVlKCJ0cmFuc2Zvcm0iKTsKICAgICAgY3NzUm9vdCQyLnJlbW92ZUNoaWxkKGNzc05vZGUkMik7CiAgICAgIHZhbHVlID0gdmFsdWUuc2xpY2UoNywgLTEpLnNwbGl0KCIsIik7CiAgICAgIHJldHVybiBkZWNvbXBvc2UkMigrdmFsdWVbMF0sICt2YWx1ZVsxXSwgK3ZhbHVlWzJdLCArdmFsdWVbM10sICt2YWx1ZVs0XSwgK3ZhbHVlWzVdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVN2ZyQyKHZhbHVlKSB7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gaWRlbnRpdHkkZzsKICAgICAgaWYgKCFzdmdOb2RlJDIpIHN2Z05vZGUkMiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciLCAiZyIpOwogICAgICBzdmdOb2RlJDIuc2V0QXR0cmlidXRlKCJ0cmFuc2Zvcm0iLCB2YWx1ZSk7CiAgICAgIGlmICghKHZhbHVlID0gc3ZnTm9kZSQyLnRyYW5zZm9ybS5iYXNlVmFsLmNvbnNvbGlkYXRlKCkpKSByZXR1cm4gaWRlbnRpdHkkZzsKICAgICAgdmFsdWUgPSB2YWx1ZS5tYXRyaXg7CiAgICAgIHJldHVybiBkZWNvbXBvc2UkMih2YWx1ZS5hLCB2YWx1ZS5iLCB2YWx1ZS5jLCB2YWx1ZS5kLCB2YWx1ZS5lLCB2YWx1ZS5mKTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZVRyYW5zZm9ybSQyKHBhcnNlLCBweENvbW1hLCBweFBhcmVuLCBkZWdQYXJlbikgewoKICAgICAgZnVuY3Rpb24gcG9wKHMpIHsKICAgICAgICByZXR1cm4gcy5sZW5ndGggPyBzLnBvcCgpICsgIiAiIDogIiI7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRyYW5zbGF0ZSh4YSwgeWEsIHhiLCB5YiwgcywgcSkgewogICAgICAgIGlmICh4YSAhPT0geGIgfHwgeWEgIT09IHliKSB7CiAgICAgICAgICB2YXIgaSA9IHMucHVzaCgidHJhbnNsYXRlKCIsIG51bGwsIHB4Q29tbWEsIG51bGwsIHB4UGFyZW4pOwogICAgICAgICAgcS5wdXNoKHtpOiBpIC0gNCwgeDogbnVtYmVyJDYoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogbnVtYmVyJDYoeWEsIHliKX0pOwogICAgICAgIH0gZWxzZSBpZiAoeGIgfHwgeWIpIHsKICAgICAgICAgIHMucHVzaCgidHJhbnNsYXRlKCIgKyB4YiArIHB4Q29tbWEgKyB5YiArIHB4UGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gcm90YXRlKGEsIGIsIHMsIHEpIHsKICAgICAgICBpZiAoYSAhPT0gYikgewogICAgICAgICAgaWYgKGEgLSBiID4gMTgwKSBiICs9IDM2MDsgZWxzZSBpZiAoYiAtIGEgPiAxODApIGEgKz0gMzYwOyAvLyBzaG9ydGVzdCBwYXRoCiAgICAgICAgICBxLnB1c2goe2k6IHMucHVzaChwb3AocykgKyAicm90YXRlKCIsIG51bGwsIGRlZ1BhcmVuKSAtIDIsIHg6IG51bWJlciQ2KGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInJvdGF0ZSgiICsgYiArIGRlZ1BhcmVuKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNrZXdYKGEsIGIsIHMsIHEpIHsKICAgICAgICBpZiAoYSAhPT0gYikgewogICAgICAgICAgcS5wdXNoKHtpOiBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIsIG51bGwsIGRlZ1BhcmVuKSAtIDIsIHg6IG51bWJlciQ2KGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIgKyBiICsgZGVnUGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIsIG51bGwsICIsIiwgbnVsbCwgIikiKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IG51bWJlciQ2KHhhLCB4Yil9LCB7aTogaSAtIDIsIHg6IG51bWJlciQ2KHlhLCB5Yil9KTsKICAgICAgICB9IGVsc2UgaWYgKHhiICE9PSAxIHx8IHliICE9PSAxKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIgKyB4YiArICIsIiArIHliICsgIikiKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgdmFyIHMgPSBbXSwgLy8gc3RyaW5nIGNvbnN0YW50cyBhbmQgcGxhY2Vob2xkZXJzCiAgICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKICAgICAgICBhID0gcGFyc2UoYSksIGIgPSBwYXJzZShiKTsKICAgICAgICB0cmFuc2xhdGUoYS50cmFuc2xhdGVYLCBhLnRyYW5zbGF0ZVksIGIudHJhbnNsYXRlWCwgYi50cmFuc2xhdGVZLCBzLCBxKTsKICAgICAgICByb3RhdGUoYS5yb3RhdGUsIGIucm90YXRlLCBzLCBxKTsKICAgICAgICBza2V3WChhLnNrZXdYLCBiLnNrZXdYLCBzLCBxKTsKICAgICAgICBzY2FsZShhLnNjYWxlWCwgYS5zY2FsZVksIGIuc2NhbGVYLCBiLnNjYWxlWSwgcywgcSk7CiAgICAgICAgYSA9IGIgPSBudWxsOyAvLyBnYwogICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICB2YXIgaSA9IC0xLCBuID0gcS5sZW5ndGgsIG87CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgc1sobyA9IHFbaV0pLmldID0gby54KHQpOwogICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgaW50ZXJwb2xhdGVUcmFuc2Zvcm1Dc3MkMiA9IGludGVycG9sYXRlVHJhbnNmb3JtJDIocGFyc2VDc3MkMywgInB4LCAiLCAicHgpIiwgImRlZykiKTsKICAgIHZhciBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZyQyID0gaW50ZXJwb2xhdGVUcmFuc2Zvcm0kMihwYXJzZVN2ZyQyLCAiLCAiLCAiKSIsICIpIik7CgogICAgdmFyIHJobyQxID0gTWF0aC5TUVJUMiwKICAgICAgICByaG8yJDEgPSAyLAogICAgICAgIHJobzQkMSA9IDQsCiAgICAgICAgZXBzaWxvbjIkNCA9IDFlLTEyOwoKICAgIGZ1bmN0aW9uIGNvc2gkMSh4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCh4KSkgKyAxIC8geCkgLyAyOwogICAgfQoKICAgIGZ1bmN0aW9uIHNpbmgkMSh4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCh4KSkgLSAxIC8geCkgLyAyOwogICAgfQoKICAgIGZ1bmN0aW9uIHRhbmgkMSh4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCgyICogeCkpIC0gMSkgLyAoeCArIDEpOwogICAgfQoKICAgIC8vIHAwID0gW3V4MCwgdXkwLCB3MF0KICAgIC8vIHAxID0gW3V4MSwgdXkxLCB3MV0KICAgIGZ1bmN0aW9uIHpvb20kMShwMCwgcDEpIHsKICAgICAgdmFyIHV4MCA9IHAwWzBdLCB1eTAgPSBwMFsxXSwgdzAgPSBwMFsyXSwKICAgICAgICAgIHV4MSA9IHAxWzBdLCB1eTEgPSBwMVsxXSwgdzEgPSBwMVsyXSwKICAgICAgICAgIGR4ID0gdXgxIC0gdXgwLAogICAgICAgICAgZHkgPSB1eTEgLSB1eTAsCiAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5LAogICAgICAgICAgaSwKICAgICAgICAgIFM7CgogICAgICAvLyBTcGVjaWFsIGNhc2UgZm9yIHUwIOKJhSB1MS4KICAgICAgaWYgKGQyIDwgZXBzaWxvbjIkNCkgewogICAgICAgIFMgPSBNYXRoLmxvZyh3MSAvIHcwKSAvIHJobyQxOwogICAgICAgIGkgPSBmdW5jdGlvbih0KSB7CiAgICAgICAgICByZXR1cm4gWwogICAgICAgICAgICB1eDAgKyB0ICogZHgsCiAgICAgICAgICAgIHV5MCArIHQgKiBkeSwKICAgICAgICAgICAgdzAgKiBNYXRoLmV4cChyaG8kMSAqIHQgKiBTKQogICAgICAgICAgXTsKICAgICAgICB9OwogICAgICB9CgogICAgICAvLyBHZW5lcmFsIGNhc2UuCiAgICAgIGVsc2UgewogICAgICAgIHZhciBkMSA9IE1hdGguc3FydChkMiksCiAgICAgICAgICAgIGIwID0gKHcxICogdzEgLSB3MCAqIHcwICsgcmhvNCQxICogZDIpIC8gKDIgKiB3MCAqIHJobzIkMSAqIGQxKSwKICAgICAgICAgICAgYjEgPSAodzEgKiB3MSAtIHcwICogdzAgLSByaG80JDEgKiBkMikgLyAoMiAqIHcxICogcmhvMiQxICogZDEpLAogICAgICAgICAgICByMCA9IE1hdGgubG9nKE1hdGguc3FydChiMCAqIGIwICsgMSkgLSBiMCksCiAgICAgICAgICAgIHIxID0gTWF0aC5sb2coTWF0aC5zcXJ0KGIxICogYjEgKyAxKSAtIGIxKTsKICAgICAgICBTID0gKHIxIC0gcjApIC8gcmhvJDE7CiAgICAgICAgaSA9IGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHZhciBzID0gdCAqIFMsCiAgICAgICAgICAgICAgY29zaHIwID0gY29zaCQxKHIwKSwKICAgICAgICAgICAgICB1ID0gdzAgLyAocmhvMiQxICogZDEpICogKGNvc2hyMCAqIHRhbmgkMShyaG8kMSAqIHMgKyByMCkgLSBzaW5oJDEocjApKTsKICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgIHV4MCArIHUgKiBkeCwKICAgICAgICAgICAgdXkwICsgdSAqIGR5LAogICAgICAgICAgICB3MCAqIGNvc2hyMCAvIGNvc2gkMShyaG8kMSAqIHMgKyByMCkKICAgICAgICAgIF07CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgaS5kdXJhdGlvbiA9IFMgKiAxMDAwOwoKICAgICAgcmV0dXJuIGk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsJDYoaHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgdmFyIGggPSBodWUoKHN0YXJ0ID0gaHNsJDUoc3RhcnQpKS5oLCAoZW5kID0gaHNsJDUoZW5kKSkuaCksCiAgICAgICAgICAgIHMgPSBub2dhbW1hJDIoc3RhcnQucywgZW5kLnMpLAogICAgICAgICAgICBsID0gbm9nYW1tYSQyKHN0YXJ0LmwsIGVuZC5sKSwKICAgICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEkMihzdGFydC5vcGFjaXR5LCBlbmQub3BhY2l0eSk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHN0YXJ0LmggPSBoKHQpOwogICAgICAgICAgc3RhcnQucyA9IHModCk7CiAgICAgICAgICBzdGFydC5sID0gbCh0KTsKICAgICAgICAgIHN0YXJ0Lm9wYWNpdHkgPSBvcGFjaXR5KHQpOwogICAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgICAgfTsKICAgICAgfQogICAgfQoKICAgIHZhciBoc2wkNyA9IGhzbCQ2KGh1ZSQyKTsKICAgIHZhciBoc2xMb25nJDEgPSBoc2wkNihub2dhbW1hJDIpOwoKICAgIGZ1bmN0aW9uIGxhYiQ0KHN0YXJ0LCBlbmQpIHsKICAgICAgdmFyIGwgPSBub2dhbW1hJDIoKHN0YXJ0ID0gbGFiJDMoc3RhcnQpKS5sLCAoZW5kID0gbGFiJDMoZW5kKSkubCksCiAgICAgICAgICBhID0gbm9nYW1tYSQyKHN0YXJ0LmEsIGVuZC5hKSwKICAgICAgICAgIGIgPSBub2dhbW1hJDIoc3RhcnQuYiwgZW5kLmIpLAogICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEkMihzdGFydC5vcGFjaXR5LCBlbmQub3BhY2l0eSk7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgc3RhcnQubCA9IGwodCk7CiAgICAgICAgc3RhcnQuYSA9IGEodCk7CiAgICAgICAgc3RhcnQuYiA9IGIodCk7CiAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaGNsJDUoaHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgdmFyIGggPSBodWUoKHN0YXJ0ID0gaGNsJDQoc3RhcnQpKS5oLCAoZW5kID0gaGNsJDQoZW5kKSkuaCksCiAgICAgICAgICAgIGMgPSBub2dhbW1hJDIoc3RhcnQuYywgZW5kLmMpLAogICAgICAgICAgICBsID0gbm9nYW1tYSQyKHN0YXJ0LmwsIGVuZC5sKSwKICAgICAgICAgICAgb3BhY2l0eSA9IG5vZ2FtbWEkMihzdGFydC5vcGFjaXR5LCBlbmQub3BhY2l0eSk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHN0YXJ0LmggPSBoKHQpOwogICAgICAgICAgc3RhcnQuYyA9IGModCk7CiAgICAgICAgICBzdGFydC5sID0gbCh0KTsKICAgICAgICAgIHN0YXJ0Lm9wYWNpdHkgPSBvcGFjaXR5KHQpOwogICAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgICAgfTsKICAgICAgfQogICAgfQoKICAgIHZhciBoY2wkNiA9IGhjbCQ1KGh1ZSQyKTsKICAgIHZhciBoY2xMb25nJDEgPSBoY2wkNShub2dhbW1hJDIpOwoKICAgIGZ1bmN0aW9uIGN1YmVoZWxpeCQ2KGh1ZSkgewogICAgICByZXR1cm4gKGZ1bmN0aW9uIGN1YmVoZWxpeEdhbW1hKHkpIHsKICAgICAgICB5ID0gK3k7CgogICAgICAgIGZ1bmN0aW9uIGN1YmVoZWxpeChzdGFydCwgZW5kKSB7CiAgICAgICAgICB2YXIgaCA9IGh1ZSgoc3RhcnQgPSBjdWJlaGVsaXgkNShzdGFydCkpLmgsIChlbmQgPSBjdWJlaGVsaXgkNShlbmQpKS5oKSwKICAgICAgICAgICAgICBzID0gbm9nYW1tYSQyKHN0YXJ0LnMsIGVuZC5zKSwKICAgICAgICAgICAgICBsID0gbm9nYW1tYSQyKHN0YXJ0LmwsIGVuZC5sKSwKICAgICAgICAgICAgICBvcGFjaXR5ID0gbm9nYW1tYSQyKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICAgIHN0YXJ0LmggPSBoKHQpOwogICAgICAgICAgICBzdGFydC5zID0gcyh0KTsKICAgICAgICAgICAgc3RhcnQubCA9IGwoTWF0aC5wb3codCwgeSkpOwogICAgICAgICAgICBzdGFydC5vcGFjaXR5ID0gb3BhY2l0eSh0KTsKICAgICAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgY3ViZWhlbGl4LmdhbW1hID0gY3ViZWhlbGl4R2FtbWE7CgogICAgICAgIHJldHVybiBjdWJlaGVsaXg7CiAgICAgIH0pKDEpOwogICAgfQoKICAgIHZhciBjdWJlaGVsaXgkNyA9IGN1YmVoZWxpeCQ2KGh1ZSQyKTsKICAgIHZhciBjdWJlaGVsaXhMb25nJDEgPSBjdWJlaGVsaXgkNihub2dhbW1hJDIpOwoKICAgIGZ1bmN0aW9uIHF1YW50aXplJDIoaW50ZXJwb2xhdG9yLCBuKSB7CiAgICAgIHZhciBzYW1wbGVzID0gbmV3IEFycmF5KG4pOwogICAgICBmb3IgKHZhciBpID0gMDsgaSA8IG47ICsraSkgc2FtcGxlc1tpXSA9IGludGVycG9sYXRvcihpIC8gKG4gLSAxKSk7CiAgICAgIHJldHVybiBzYW1wbGVzOwogICAgfQoKICAgIHZhciBwaSQ5ID0gTWF0aC5QSSwKICAgICAgICB0YXUkOSA9IDIgKiBwaSQ5LAogICAgICAgIGVwc2lsb24kOCA9IDFlLTYsCiAgICAgICAgdGF1RXBzaWxvbiQyID0gdGF1JDkgLSBlcHNpbG9uJDg7CgogICAgZnVuY3Rpb24gUGF0aCQyKCkgewogICAgICB0aGlzLl94MCA9IHRoaXMuX3kwID0gLy8gc3RhcnQgb2YgY3VycmVudCBzdWJwYXRoCiAgICAgIHRoaXMuX3gxID0gdGhpcy5feTEgPSBudWxsOyAvLyBlbmQgb2YgY3VycmVudCBzdWJwYXRoCiAgICAgIHRoaXMuXyA9ICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhdGgkMigpIHsKICAgICAgcmV0dXJuIG5ldyBQYXRoJDI7CiAgICB9CgogICAgUGF0aCQyLnByb3RvdHlwZSA9IHBhdGgkMi5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBQYXRoJDIsCiAgICAgIG1vdmVUbzogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHRoaXMuXyArPSAiTSIgKyAodGhpcy5feDAgPSB0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MCA9IHRoaXMuX3kxID0gK3kpOwogICAgICB9LAogICAgICBjbG9zZVBhdGg6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl94MSAhPT0gbnVsbCkgewogICAgICAgICAgdGhpcy5feDEgPSB0aGlzLl94MCwgdGhpcy5feTEgPSB0aGlzLl95MDsKICAgICAgICAgIHRoaXMuXyArPSAiWiI7CiAgICAgICAgfQogICAgICB9LAogICAgICBsaW5lVG86IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB0aGlzLl8gKz0gIkwiICsgKHRoaXMuX3gxID0gK3gpICsgIiwiICsgKHRoaXMuX3kxID0gK3kpOwogICAgICB9LAogICAgICBxdWFkcmF0aWNDdXJ2ZVRvOiBmdW5jdGlvbih4MSwgeTEsIHgsIHkpIHsKICAgICAgICB0aGlzLl8gKz0gIlEiICsgKCt4MSkgKyAiLCIgKyAoK3kxKSArICIsIiArICh0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgYmV6aWVyQ3VydmVUbzogZnVuY3Rpb24oeDEsIHkxLCB4MiwgeTIsIHgsIHkpIHsKICAgICAgICB0aGlzLl8gKz0gIkMiICsgKCt4MSkgKyAiLCIgKyAoK3kxKSArICIsIiArICgreDIpICsgIiwiICsgKCt5MikgKyAiLCIgKyAodGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTEgPSAreSk7CiAgICAgIH0sCiAgICAgIGFyY1RvOiBmdW5jdGlvbih4MSwgeTEsIHgyLCB5MiwgcikgewogICAgICAgIHgxID0gK3gxLCB5MSA9ICt5MSwgeDIgPSAreDIsIHkyID0gK3kyLCByID0gK3I7CiAgICAgICAgdmFyIHgwID0gdGhpcy5feDEsCiAgICAgICAgICAgIHkwID0gdGhpcy5feTEsCiAgICAgICAgICAgIHgyMSA9IHgyIC0geDEsCiAgICAgICAgICAgIHkyMSA9IHkyIC0geTEsCiAgICAgICAgICAgIHgwMSA9IHgwIC0geDEsCiAgICAgICAgICAgIHkwMSA9IHkwIC0geTEsCiAgICAgICAgICAgIGwwMV8yID0geDAxICogeDAxICsgeTAxICogeTAxOwoKICAgICAgICAvLyBJcyB0aGUgcmFkaXVzIG5lZ2F0aXZlPyBFcnJvci4KICAgICAgICBpZiAociA8IDApIHRocm93IG5ldyBFcnJvcigibmVnYXRpdmUgcmFkaXVzOiAiICsgcik7CgogICAgICAgIC8vIElzIHRoaXMgcGF0aCBlbXB0eT8gTW92ZSB0byAoeDEseTEpLgogICAgICAgIGlmICh0aGlzLl94MSA9PT0gbnVsbCkgewogICAgICAgICAgdGhpcy5fICs9ICJNIiArICh0aGlzLl94MSA9IHgxKSArICIsIiArICh0aGlzLl95MSA9IHkxKTsKICAgICAgICB9CgogICAgICAgIC8vIE9yLCBpcyAoeDEseTEpIGNvaW5jaWRlbnQgd2l0aCAoeDAseTApPyBEbyBub3RoaW5nLgogICAgICAgIGVsc2UgaWYgKCEobDAxXzIgPiBlcHNpbG9uJDgpKSA7CgogICAgICAgIC8vIE9yLCBhcmUgKHgwLHkwKSwgKHgxLHkxKSBhbmQgKHgyLHkyKSBjb2xsaW5lYXI/CiAgICAgICAgLy8gRXF1aXZhbGVudGx5LCBpcyAoeDEseTEpIGNvaW5jaWRlbnQgd2l0aCAoeDIseTIpPwogICAgICAgIC8vIE9yLCBpcyB0aGUgcmFkaXVzIHplcm8/IExpbmUgdG8gKHgxLHkxKS4KICAgICAgICBlbHNlIGlmICghKE1hdGguYWJzKHkwMSAqIHgyMSAtIHkyMSAqIHgwMSkgPiBlcHNpbG9uJDgpIHx8ICFyKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkwiICsgKHRoaXMuX3gxID0geDEpICsgIiwiICsgKHRoaXMuX3kxID0geTEpOwogICAgICAgIH0KCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IGFuIGFyYyEKICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciB4MjAgPSB4MiAtIHgwLAogICAgICAgICAgICAgIHkyMCA9IHkyIC0geTAsCiAgICAgICAgICAgICAgbDIxXzIgPSB4MjEgKiB4MjEgKyB5MjEgKiB5MjEsCiAgICAgICAgICAgICAgbDIwXzIgPSB4MjAgKiB4MjAgKyB5MjAgKiB5MjAsCiAgICAgICAgICAgICAgbDIxID0gTWF0aC5zcXJ0KGwyMV8yKSwKICAgICAgICAgICAgICBsMDEgPSBNYXRoLnNxcnQobDAxXzIpLAogICAgICAgICAgICAgIGwgPSByICogTWF0aC50YW4oKHBpJDkgLSBNYXRoLmFjb3MoKGwyMV8yICsgbDAxXzIgLSBsMjBfMikgLyAoMiAqIGwyMSAqIGwwMSkpKSAvIDIpLAogICAgICAgICAgICAgIHQwMSA9IGwgLyBsMDEsCiAgICAgICAgICAgICAgdDIxID0gbCAvIGwyMTsKCiAgICAgICAgICAvLyBJZiB0aGUgc3RhcnQgdGFuZ2VudCBpcyBub3QgY29pbmNpZGVudCB3aXRoICh4MCx5MCksIGxpbmUgdG8uCiAgICAgICAgICBpZiAoTWF0aC5hYnModDAxIC0gMSkgPiBlcHNpbG9uJDgpIHsKICAgICAgICAgICAgdGhpcy5fICs9ICJMIiArICh4MSArIHQwMSAqIHgwMSkgKyAiLCIgKyAoeTEgKyB0MDEgKiB5MDEpOwogICAgICAgICAgfQoKICAgICAgICAgIHRoaXMuXyArPSAiQSIgKyByICsgIiwiICsgciArICIsMCwwLCIgKyAoKyh5MDEgKiB4MjAgPiB4MDEgKiB5MjApKSArICIsIiArICh0aGlzLl94MSA9IHgxICsgdDIxICogeDIxKSArICIsIiArICh0aGlzLl95MSA9IHkxICsgdDIxICogeTIxKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGFyYzogZnVuY3Rpb24oeCwgeSwgciwgYTAsIGExLCBjY3cpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreSwgciA9ICtyOwogICAgICAgIHZhciBkeCA9IHIgKiBNYXRoLmNvcyhhMCksCiAgICAgICAgICAgIGR5ID0gciAqIE1hdGguc2luKGEwKSwKICAgICAgICAgICAgeDAgPSB4ICsgZHgsCiAgICAgICAgICAgIHkwID0geSArIGR5LAogICAgICAgICAgICBjdyA9IDEgXiBjY3csCiAgICAgICAgICAgIGRhID0gY2N3ID8gYTAgLSBhMSA6IGExIC0gYTA7CgogICAgICAgIC8vIElzIHRoZSByYWRpdXMgbmVnYXRpdmU/IEVycm9yLgogICAgICAgIGlmIChyIDwgMCkgdGhyb3cgbmV3IEVycm9yKCJuZWdhdGl2ZSByYWRpdXM6ICIgKyByKTsKCiAgICAgICAgLy8gSXMgdGhpcyBwYXRoIGVtcHR5PyBNb3ZlIHRvICh4MCx5MCkuCiAgICAgICAgaWYgKHRoaXMuX3gxID09PSBudWxsKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIk0iICsgeDAgKyAiLCIgKyB5MDsKICAgICAgICB9CgogICAgICAgIC8vIE9yLCBpcyAoeDAseTApIG5vdCBjb2luY2lkZW50IHdpdGggdGhlIHByZXZpb3VzIHBvaW50PyBMaW5lIHRvICh4MCx5MCkuCiAgICAgICAgZWxzZSBpZiAoTWF0aC5hYnModGhpcy5feDEgLSB4MCkgPiBlcHNpbG9uJDggfHwgTWF0aC5hYnModGhpcy5feTEgLSB5MCkgPiBlcHNpbG9uJDgpIHsKICAgICAgICAgIHRoaXMuXyArPSAiTCIgKyB4MCArICIsIiArIHkwOwogICAgICAgIH0KCiAgICAgICAgLy8gSXMgdGhpcyBhcmMgZW1wdHk/IFdl4oCZcmUgZG9uZS4KICAgICAgICBpZiAoIXIpIHJldHVybjsKCiAgICAgICAgLy8gRG9lcyB0aGUgYW5nbGUgZ28gdGhlIHdyb25nIHdheT8gRmxpcCB0aGUgZGlyZWN0aW9uLgogICAgICAgIGlmIChkYSA8IDApIGRhID0gZGEgJSB0YXUkOSArIHRhdSQ5OwoKICAgICAgICAvLyBJcyB0aGlzIGEgY29tcGxldGUgY2lyY2xlPyBEcmF3IHR3byBhcmNzIHRvIGNvbXBsZXRlIHRoZSBjaXJjbGUuCiAgICAgICAgaWYgKGRhID4gdGF1RXBzaWxvbiQyKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkEiICsgciArICIsIiArIHIgKyAiLDAsMSwiICsgY3cgKyAiLCIgKyAoeCAtIGR4KSArICIsIiArICh5IC0gZHkpICsgIkEiICsgciArICIsIiArIHIgKyAiLDAsMSwiICsgY3cgKyAiLCIgKyAodGhpcy5feDEgPSB4MCkgKyAiLCIgKyAodGhpcy5feTEgPSB5MCk7CiAgICAgICAgfQoKICAgICAgICAvLyBJcyB0aGlzIGFyYyBub24tZW1wdHk/IERyYXcgYW4gYXJjIQogICAgICAgIGVsc2UgaWYgKGRhID4gZXBzaWxvbiQ4KSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkEiICsgciArICIsIiArIHIgKyAiLDAsIiArICgrKGRhID49IHBpJDkpKSArICIsIiArIGN3ICsgIiwiICsgKHRoaXMuX3gxID0geCArIHIgKiBNYXRoLmNvcyhhMSkpICsgIiwiICsgKHRoaXMuX3kxID0geSArIHIgKiBNYXRoLnNpbihhMSkpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgcmVjdDogZnVuY3Rpb24oeCwgeSwgdywgaCkgewogICAgICAgIHRoaXMuXyArPSAiTSIgKyAodGhpcy5feDAgPSB0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MCA9IHRoaXMuX3kxID0gK3kpICsgImgiICsgKCt3KSArICJ2IiArICgraCkgKyAiaCIgKyAoLXcpICsgIloiOwogICAgICB9LAogICAgICB0b1N0cmluZzogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuXzsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBhcmVhJDUocG9seWdvbikgewogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IHBvbHlnb24ubGVuZ3RoLAogICAgICAgICAgYSwKICAgICAgICAgIGIgPSBwb2x5Z29uW24gLSAxXSwKICAgICAgICAgIGFyZWEgPSAwOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBhID0gYjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICBhcmVhICs9IGFbMV0gKiBiWzBdIC0gYVswXSAqIGJbMV07CiAgICAgIH0KCiAgICAgIHJldHVybiBhcmVhIC8gMjsKICAgIH0KCiAgICBmdW5jdGlvbiBjZW50cm9pZCQzKHBvbHlnb24pIHsKICAgICAgdmFyIGkgPSAtMSwKICAgICAgICAgIG4gPSBwb2x5Z29uLmxlbmd0aCwKICAgICAgICAgIHggPSAwLAogICAgICAgICAgeSA9IDAsCiAgICAgICAgICBhLAogICAgICAgICAgYiA9IHBvbHlnb25bbiAtIDFdLAogICAgICAgICAgYywKICAgICAgICAgIGsgPSAwOwoKICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICBhID0gYjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICBrICs9IGMgPSBhWzBdICogYlsxXSAtIGJbMF0gKiBhWzFdOwogICAgICAgIHggKz0gKGFbMF0gKyBiWzBdKSAqIGM7CiAgICAgICAgeSArPSAoYVsxXSArIGJbMV0pICogYzsKICAgICAgfQoKICAgICAgcmV0dXJuIGsgKj0gMywgW3ggLyBrLCB5IC8ga107CiAgICB9CgogICAgLy8gUmV0dXJucyB0aGUgMkQgY3Jvc3MgcHJvZHVjdCBvZiBBQiBhbmQgQUMgdmVjdG9ycywgaS5lLiwgdGhlIHotY29tcG9uZW50IG9mCiAgICAvLyB0aGUgM0QgY3Jvc3MgcHJvZHVjdCBpbiBhIHF1YWRyYW50IEkgQ2FydGVzaWFuIGNvb3JkaW5hdGUgc3lzdGVtICgreCBpcwogICAgLy8gcmlnaHQsICt5IGlzIHVwKS4gUmV0dXJucyBhIHBvc2l0aXZlIHZhbHVlIGlmIEFCQyBpcyBjb3VudGVyLWNsb2Nrd2lzZSwKICAgIC8vIG5lZ2F0aXZlIGlmIGNsb2Nrd2lzZSwgYW5kIHplcm8gaWYgdGhlIHBvaW50cyBhcmUgY29sbGluZWFyLgogICAgZnVuY3Rpb24gY3Jvc3MkNChhLCBiLCBjKSB7CiAgICAgIHJldHVybiAoYlswXSAtIGFbMF0pICogKGNbMV0gLSBhWzFdKSAtIChiWzFdIC0gYVsxXSkgKiAoY1swXSAtIGFbMF0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGxleGljb2dyYXBoaWNPcmRlciQxKGEsIGIpIHsKICAgICAgcmV0dXJuIGFbMF0gLSBiWzBdIHx8IGFbMV0gLSBiWzFdOwogICAgfQoKICAgIC8vIENvbXB1dGVzIHRoZSB1cHBlciBjb252ZXggaHVsbCBwZXIgdGhlIG1vbm90b25lIGNoYWluIGFsZ29yaXRobS4KICAgIC8vIEFzc3VtZXMgcG9pbnRzLmxlbmd0aCA+PSAzLCBpcyBzb3J0ZWQgYnkgeCwgdW5pcXVlIGluIHkuCiAgICAvLyBSZXR1cm5zIGFuIGFycmF5IG9mIGluZGljZXMgaW50byBwb2ludHMgaW4gbGVmdC10by1yaWdodCBvcmRlci4KICAgIGZ1bmN0aW9uIGNvbXB1dGVVcHBlckh1bGxJbmRleGVzJDEocG9pbnRzKSB7CiAgICAgIHZhciBuID0gcG9pbnRzLmxlbmd0aCwKICAgICAgICAgIGluZGV4ZXMgPSBbMCwgMV0sCiAgICAgICAgICBzaXplID0gMjsKCiAgICAgIGZvciAodmFyIGkgPSAyOyBpIDwgbjsgKytpKSB7CiAgICAgICAgd2hpbGUgKHNpemUgPiAxICYmIGNyb3NzJDQocG9pbnRzW2luZGV4ZXNbc2l6ZSAtIDJdXSwgcG9pbnRzW2luZGV4ZXNbc2l6ZSAtIDFdXSwgcG9pbnRzW2ldKSA8PSAwKSAtLXNpemU7CiAgICAgICAgaW5kZXhlc1tzaXplKytdID0gaTsKICAgICAgfQoKICAgICAgcmV0dXJuIGluZGV4ZXMuc2xpY2UoMCwgc2l6ZSk7IC8vIHJlbW92ZSBwb3BwZWQgcG9pbnRzCiAgICB9CgogICAgZnVuY3Rpb24gaHVsbCQxKHBvaW50cykgewogICAgICBpZiAoKG4gPSBwb2ludHMubGVuZ3RoKSA8IDMpIHJldHVybiBudWxsOwoKICAgICAgdmFyIGksCiAgICAgICAgICBuLAogICAgICAgICAgc29ydGVkUG9pbnRzID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgZmxpcHBlZFBvaW50cyA9IG5ldyBBcnJheShuKTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHNvcnRlZFBvaW50c1tpXSA9IFsrcG9pbnRzW2ldWzBdLCArcG9pbnRzW2ldWzFdLCBpXTsKICAgICAgc29ydGVkUG9pbnRzLnNvcnQobGV4aWNvZ3JhcGhpY09yZGVyJDEpOwogICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSBmbGlwcGVkUG9pbnRzW2ldID0gW3NvcnRlZFBvaW50c1tpXVswXSwgLXNvcnRlZFBvaW50c1tpXVsxXV07CgogICAgICB2YXIgdXBwZXJJbmRleGVzID0gY29tcHV0ZVVwcGVySHVsbEluZGV4ZXMkMShzb3J0ZWRQb2ludHMpLAogICAgICAgICAgbG93ZXJJbmRleGVzID0gY29tcHV0ZVVwcGVySHVsbEluZGV4ZXMkMShmbGlwcGVkUG9pbnRzKTsKCiAgICAgIC8vIENvbnN0cnVjdCB0aGUgaHVsbCBwb2x5Z29uLCByZW1vdmluZyBwb3NzaWJsZSBkdXBsaWNhdGUgZW5kcG9pbnRzLgogICAgICB2YXIgc2tpcExlZnQgPSBsb3dlckluZGV4ZXNbMF0gPT09IHVwcGVySW5kZXhlc1swXSwKICAgICAgICAgIHNraXBSaWdodCA9IGxvd2VySW5kZXhlc1tsb3dlckluZGV4ZXMubGVuZ3RoIC0gMV0gPT09IHVwcGVySW5kZXhlc1t1cHBlckluZGV4ZXMubGVuZ3RoIC0gMV0sCiAgICAgICAgICBodWxsID0gW107CgogICAgICAvLyBBZGQgdXBwZXIgaHVsbCBpbiByaWdodC10by1sIG9yZGVyLgogICAgICAvLyBUaGVuIGFkZCBsb3dlciBodWxsIGluIGxlZnQtdG8tcmlnaHQgb3JkZXIuCiAgICAgIGZvciAoaSA9IHVwcGVySW5kZXhlcy5sZW5ndGggLSAxOyBpID49IDA7IC0taSkgaHVsbC5wdXNoKHBvaW50c1tzb3J0ZWRQb2ludHNbdXBwZXJJbmRleGVzW2ldXVsyXV0pOwogICAgICBmb3IgKGkgPSArc2tpcExlZnQ7IGkgPCBsb3dlckluZGV4ZXMubGVuZ3RoIC0gc2tpcFJpZ2h0OyArK2kpIGh1bGwucHVzaChwb2ludHNbc29ydGVkUG9pbnRzW2xvd2VySW5kZXhlc1tpXV1bMl1dKTsKCiAgICAgIHJldHVybiBodWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRhaW5zJDQocG9seWdvbiwgcG9pbnQpIHsKICAgICAgdmFyIG4gPSBwb2x5Z29uLmxlbmd0aCwKICAgICAgICAgIHAgPSBwb2x5Z29uW24gLSAxXSwKICAgICAgICAgIHggPSBwb2ludFswXSwgeSA9IHBvaW50WzFdLAogICAgICAgICAgeDAgPSBwWzBdLCB5MCA9IHBbMV0sCiAgICAgICAgICB4MSwgeTEsCiAgICAgICAgICBpbnNpZGUgPSBmYWxzZTsKCiAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgcCA9IHBvbHlnb25baV0sIHgxID0gcFswXSwgeTEgPSBwWzFdOwogICAgICAgIGlmICgoKHkxID4geSkgIT09ICh5MCA+IHkpKSAmJiAoeCA8ICh4MCAtIHgxKSAqICh5IC0geTEpIC8gKHkwIC0geTEpICsgeDEpKSBpbnNpZGUgPSAhaW5zaWRlOwogICAgICAgIHgwID0geDEsIHkwID0geTE7CiAgICAgIH0KCiAgICAgIHJldHVybiBpbnNpZGU7CiAgICB9CgogICAgZnVuY3Rpb24gbGVuZ3RoJDUocG9seWdvbikgewogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IHBvbHlnb24ubGVuZ3RoLAogICAgICAgICAgYiA9IHBvbHlnb25bbiAtIDFdLAogICAgICAgICAgeGEsCiAgICAgICAgICB5YSwKICAgICAgICAgIHhiID0gYlswXSwKICAgICAgICAgIHliID0gYlsxXSwKICAgICAgICAgIHBlcmltZXRlciA9IDA7CgogICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgIHhhID0geGI7CiAgICAgICAgeWEgPSB5YjsKICAgICAgICBiID0gcG9seWdvbltpXTsKICAgICAgICB4YiA9IGJbMF07CiAgICAgICAgeWIgPSBiWzFdOwogICAgICAgIHhhIC09IHhiOwogICAgICAgIHlhIC09IHliOwogICAgICAgIHBlcmltZXRlciArPSBNYXRoLnNxcnQoeGEgKiB4YSArIHlhICogeWEpOwogICAgICB9CgogICAgICByZXR1cm4gcGVyaW1ldGVyOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfYWRkJDIoZCkgewogICAgICB2YXIgeCA9ICt0aGlzLl94LmNhbGwobnVsbCwgZCksCiAgICAgICAgICB5ID0gK3RoaXMuX3kuY2FsbChudWxsLCBkKTsKICAgICAgcmV0dXJuIGFkZCQ0KHRoaXMuY292ZXIoeCwgeSksIHgsIHksIGQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFkZCQ0KHRyZWUsIHgsIHksIGQpIHsKICAgICAgaWYgKGlzTmFOKHgpIHx8IGlzTmFOKHkpKSByZXR1cm4gdHJlZTsgLy8gaWdub3JlIGludmFsaWQgcG9pbnRzCgogICAgICB2YXIgcGFyZW50LAogICAgICAgICAgbm9kZSA9IHRyZWUuX3Jvb3QsCiAgICAgICAgICBsZWFmID0ge2RhdGE6IGR9LAogICAgICAgICAgeDAgPSB0cmVlLl94MCwKICAgICAgICAgIHkwID0gdHJlZS5feTAsCiAgICAgICAgICB4MSA9IHRyZWUuX3gxLAogICAgICAgICAgeTEgPSB0cmVlLl95MSwKICAgICAgICAgIHhtLAogICAgICAgICAgeW0sCiAgICAgICAgICB4cCwKICAgICAgICAgIHlwLAogICAgICAgICAgcmlnaHQsCiAgICAgICAgICBib3R0b20sCiAgICAgICAgICBpLAogICAgICAgICAgajsKCiAgICAgIC8vIElmIHRoZSB0cmVlIGlzIGVtcHR5LCBpbml0aWFsaXplIHRoZSByb290IGFzIGEgbGVhZi4KICAgICAgaWYgKCFub2RlKSByZXR1cm4gdHJlZS5fcm9vdCA9IGxlYWYsIHRyZWU7CgogICAgICAvLyBGaW5kIHRoZSBleGlzdGluZyBsZWFmIGZvciB0aGUgbmV3IHBvaW50LCBvciBhZGQgaXQuCiAgICAgIHdoaWxlIChub2RlLmxlbmd0aCkgewogICAgICAgIGlmIChyaWdodCA9IHggPj0gKHhtID0gKHgwICsgeDEpIC8gMikpIHgwID0geG07IGVsc2UgeDEgPSB4bTsKICAgICAgICBpZiAoYm90dG9tID0geSA+PSAoeW0gPSAoeTAgKyB5MSkgLyAyKSkgeTAgPSB5bTsgZWxzZSB5MSA9IHltOwogICAgICAgIGlmIChwYXJlbnQgPSBub2RlLCAhKG5vZGUgPSBub2RlW2kgPSBib3R0b20gPDwgMSB8IHJpZ2h0XSkpIHJldHVybiBwYXJlbnRbaV0gPSBsZWFmLCB0cmVlOwogICAgICB9CgogICAgICAvLyBJcyB0aGUgbmV3IHBvaW50IGlzIGV4YWN0bHkgY29pbmNpZGVudCB3aXRoIHRoZSBleGlzdGluZyBwb2ludD8KICAgICAgeHAgPSArdHJlZS5feC5jYWxsKG51bGwsIG5vZGUuZGF0YSk7CiAgICAgIHlwID0gK3RyZWUuX3kuY2FsbChudWxsLCBub2RlLmRhdGEpOwogICAgICBpZiAoeCA9PT0geHAgJiYgeSA9PT0geXApIHJldHVybiBsZWFmLm5leHQgPSBub2RlLCBwYXJlbnQgPyBwYXJlbnRbaV0gPSBsZWFmIDogdHJlZS5fcm9vdCA9IGxlYWYsIHRyZWU7CgogICAgICAvLyBPdGhlcndpc2UsIHNwbGl0IHRoZSBsZWFmIG5vZGUgdW50aWwgdGhlIG9sZCBhbmQgbmV3IHBvaW50IGFyZSBzZXBhcmF0ZWQuCiAgICAgIGRvIHsKICAgICAgICBwYXJlbnQgPSBwYXJlbnQgPyBwYXJlbnRbaV0gPSBuZXcgQXJyYXkoNCkgOiB0cmVlLl9yb290ID0gbmV3IEFycmF5KDQpOwogICAgICAgIGlmIChyaWdodCA9IHggPj0gKHhtID0gKHgwICsgeDEpIC8gMikpIHgwID0geG07IGVsc2UgeDEgPSB4bTsKICAgICAgICBpZiAoYm90dG9tID0geSA+PSAoeW0gPSAoeTAgKyB5MSkgLyAyKSkgeTAgPSB5bTsgZWxzZSB5MSA9IHltOwogICAgICB9IHdoaWxlICgoaSA9IGJvdHRvbSA8PCAxIHwgcmlnaHQpID09PSAoaiA9ICh5cCA+PSB5bSkgPDwgMSB8ICh4cCA+PSB4bSkpKTsKICAgICAgcmV0dXJuIHBhcmVudFtqXSA9IG5vZGUsIHBhcmVudFtpXSA9IGxlYWYsIHRyZWU7CiAgICB9CgogICAgZnVuY3Rpb24gYWRkQWxsJDIoZGF0YSkgewogICAgICB2YXIgZCwgaSwgbiA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgeCwKICAgICAgICAgIHksCiAgICAgICAgICB4eiA9IG5ldyBBcnJheShuKSwKICAgICAgICAgIHl6ID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgeDAgPSBJbmZpbml0eSwKICAgICAgICAgIHkwID0gSW5maW5pdHksCiAgICAgICAgICB4MSA9IC1JbmZpbml0eSwKICAgICAgICAgIHkxID0gLUluZmluaXR5OwoKICAgICAgLy8gQ29tcHV0ZSB0aGUgcG9pbnRzIGFuZCB0aGVpciBleHRlbnQuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoaXNOYU4oeCA9ICt0aGlzLl94LmNhbGwobnVsbCwgZCA9IGRhdGFbaV0pKSB8fCBpc05hTih5ID0gK3RoaXMuX3kuY2FsbChudWxsLCBkKSkpIGNvbnRpbnVlOwogICAgICAgIHh6W2ldID0geDsKICAgICAgICB5eltpXSA9IHk7CiAgICAgICAgaWYgKHggPCB4MCkgeDAgPSB4OwogICAgICAgIGlmICh4ID4geDEpIHgxID0geDsKICAgICAgICBpZiAoeSA8IHkwKSB5MCA9IHk7CiAgICAgICAgaWYgKHkgPiB5MSkgeTEgPSB5OwogICAgICB9CgogICAgICAvLyBJZiB0aGVyZSB3ZXJlIG5vICh2YWxpZCkgcG9pbnRzLCBpbmhlcml0IHRoZSBleGlzdGluZyBleHRlbnQuCiAgICAgIGlmICh4MSA8IHgwKSB4MCA9IHRoaXMuX3gwLCB4MSA9IHRoaXMuX3gxOwogICAgICBpZiAoeTEgPCB5MCkgeTAgPSB0aGlzLl95MCwgeTEgPSB0aGlzLl95MTsKCiAgICAgIC8vIEV4cGFuZCB0aGUgdHJlZSB0byBjb3ZlciB0aGUgbmV3IHBvaW50cy4KICAgICAgdGhpcy5jb3Zlcih4MCwgeTApLmNvdmVyKHgxLCB5MSk7CgogICAgICAvLyBBZGQgdGhlIG5ldyBwb2ludHMuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBhZGQkNCh0aGlzLCB4eltpXSwgeXpbaV0sIGRhdGFbaV0pOwogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX2NvdmVyJDIoeCwgeSkgewogICAgICBpZiAoaXNOYU4oeCA9ICt4KSB8fCBpc05hTih5ID0gK3kpKSByZXR1cm4gdGhpczsgLy8gaWdub3JlIGludmFsaWQgcG9pbnRzCgogICAgICB2YXIgeDAgPSB0aGlzLl94MCwKICAgICAgICAgIHkwID0gdGhpcy5feTAsCiAgICAgICAgICB4MSA9IHRoaXMuX3gxLAogICAgICAgICAgeTEgPSB0aGlzLl95MTsKCiAgICAgIC8vIElmIHRoZSBxdWFkdHJlZSBoYXMgbm8gZXh0ZW50LCBpbml0aWFsaXplIHRoZW0uCiAgICAgIC8vIEludGVnZXIgZXh0ZW50IGFyZSBuZWNlc3Nhcnkgc28gdGhhdCBpZiB3ZSBsYXRlciBkb3VibGUgdGhlIGV4dGVudCwKICAgICAgLy8gdGhlIGV4aXN0aW5nIHF1YWRyYW50IGJvdW5kYXJpZXMgZG9u4oCZdCBjaGFuZ2UgZHVlIHRvIGZsb2F0aW5nIHBvaW50IGVycm9yIQogICAgICBpZiAoaXNOYU4oeDApKSB7CiAgICAgICAgeDEgPSAoeDAgPSBNYXRoLmZsb29yKHgpKSArIDE7CiAgICAgICAgeTEgPSAoeTAgPSBNYXRoLmZsb29yKHkpKSArIDE7CiAgICAgIH0KCiAgICAgIC8vIE90aGVyd2lzZSwgZG91YmxlIHJlcGVhdGVkbHkgdG8gY292ZXIuCiAgICAgIGVsc2UgaWYgKHgwID4geCB8fCB4ID4geDEgfHwgeTAgPiB5IHx8IHkgPiB5MSkgewogICAgICAgIHZhciB6ID0geDEgLSB4MCwKICAgICAgICAgICAgbm9kZSA9IHRoaXMuX3Jvb3QsCiAgICAgICAgICAgIHBhcmVudCwKICAgICAgICAgICAgaTsKCiAgICAgICAgc3dpdGNoIChpID0gKHkgPCAoeTAgKyB5MSkgLyAyKSA8PCAxIHwgKHggPCAoeDAgKyB4MSkgLyAyKSkgewogICAgICAgICAgY2FzZSAwOiB7CiAgICAgICAgICAgIGRvIHBhcmVudCA9IG5ldyBBcnJheSg0KSwgcGFyZW50W2ldID0gbm9kZSwgbm9kZSA9IHBhcmVudDsKICAgICAgICAgICAgd2hpbGUgKHogKj0gMiwgeDEgPSB4MCArIHosIHkxID0geTAgKyB6LCB4ID4geDEgfHwgeSA+IHkxKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgZG8gcGFyZW50ID0gbmV3IEFycmF5KDQpLCBwYXJlbnRbaV0gPSBub2RlLCBub2RlID0gcGFyZW50OwogICAgICAgICAgICB3aGlsZSAoeiAqPSAyLCB4MCA9IHgxIC0geiwgeTEgPSB5MCArIHosIHgwID4geCB8fCB5ID4geTEpOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGNhc2UgMjogewogICAgICAgICAgICBkbyBwYXJlbnQgPSBuZXcgQXJyYXkoNCksIHBhcmVudFtpXSA9IG5vZGUsIG5vZGUgPSBwYXJlbnQ7CiAgICAgICAgICAgIHdoaWxlICh6ICo9IDIsIHgxID0geDAgKyB6LCB5MCA9IHkxIC0geiwgeCA+IHgxIHx8IHkwID4geSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAzOiB7CiAgICAgICAgICAgIGRvIHBhcmVudCA9IG5ldyBBcnJheSg0KSwgcGFyZW50W2ldID0gbm9kZSwgbm9kZSA9IHBhcmVudDsKICAgICAgICAgICAgd2hpbGUgKHogKj0gMiwgeDAgPSB4MSAtIHosIHkwID0geTEgLSB6LCB4MCA+IHggfHwgeTAgPiB5KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy5fcm9vdCAmJiB0aGlzLl9yb290Lmxlbmd0aCkgdGhpcy5fcm9vdCA9IG5vZGU7CiAgICAgIH0KCiAgICAgIC8vIElmIHRoZSBxdWFkdHJlZSBjb3ZlcnMgdGhlIHBvaW50IGFscmVhZHksIGp1c3QgcmV0dXJuLgogICAgICBlbHNlIHJldHVybiB0aGlzOwoKICAgICAgdGhpcy5feDAgPSB4MDsKICAgICAgdGhpcy5feTAgPSB5MDsKICAgICAgdGhpcy5feDEgPSB4MTsKICAgICAgdGhpcy5feTEgPSB5MTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9kYXRhJDIoKSB7CiAgICAgIHZhciBkYXRhID0gW107CiAgICAgIHRoaXMudmlzaXQoZnVuY3Rpb24obm9kZSkgewogICAgICAgIGlmICghbm9kZS5sZW5ndGgpIGRvIGRhdGEucHVzaChub2RlLmRhdGEpOyB3aGlsZSAobm9kZSA9IG5vZGUubmV4dCkKICAgICAgfSk7CiAgICAgIHJldHVybiBkYXRhOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfZXh0ZW50JDIoXykgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmNvdmVyKCtfWzBdWzBdLCArX1swXVsxXSkuY292ZXIoK19bMV1bMF0sICtfWzFdWzFdKQogICAgICAgICAgOiBpc05hTih0aGlzLl94MCkgPyB1bmRlZmluZWQgOiBbW3RoaXMuX3gwLCB0aGlzLl95MF0sIFt0aGlzLl94MSwgdGhpcy5feTFdXTsKICAgIH0KCiAgICBmdW5jdGlvbiBRdWFkJDIobm9kZSwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdGhpcy5ub2RlID0gbm9kZTsKICAgICAgdGhpcy54MCA9IHgwOwogICAgICB0aGlzLnkwID0geTA7CiAgICAgIHRoaXMueDEgPSB4MTsKICAgICAgdGhpcy55MSA9IHkxOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfZmluZCQyKHgsIHksIHJhZGl1cykgewogICAgICB2YXIgZGF0YSwKICAgICAgICAgIHgwID0gdGhpcy5feDAsCiAgICAgICAgICB5MCA9IHRoaXMuX3kwLAogICAgICAgICAgeDEsCiAgICAgICAgICB5MSwKICAgICAgICAgIHgyLAogICAgICAgICAgeTIsCiAgICAgICAgICB4MyA9IHRoaXMuX3gxLAogICAgICAgICAgeTMgPSB0aGlzLl95MSwKICAgICAgICAgIHF1YWRzID0gW10sCiAgICAgICAgICBub2RlID0gdGhpcy5fcm9vdCwKICAgICAgICAgIHEsCiAgICAgICAgICBpOwoKICAgICAgaWYgKG5vZGUpIHF1YWRzLnB1c2gobmV3IFF1YWQkMihub2RlLCB4MCwgeTAsIHgzLCB5MykpOwogICAgICBpZiAocmFkaXVzID09IG51bGwpIHJhZGl1cyA9IEluZmluaXR5OwogICAgICBlbHNlIHsKICAgICAgICB4MCA9IHggLSByYWRpdXMsIHkwID0geSAtIHJhZGl1czsKICAgICAgICB4MyA9IHggKyByYWRpdXMsIHkzID0geSArIHJhZGl1czsKICAgICAgICByYWRpdXMgKj0gcmFkaXVzOwogICAgICB9CgogICAgICB3aGlsZSAocSA9IHF1YWRzLnBvcCgpKSB7CgogICAgICAgIC8vIFN0b3Agc2VhcmNoaW5nIGlmIHRoaXMgcXVhZHJhbnQgY2Fu4oCZdCBjb250YWluIGEgY2xvc2VyIG5vZGUuCiAgICAgICAgaWYgKCEobm9kZSA9IHEubm9kZSkKICAgICAgICAgICAgfHwgKHgxID0gcS54MCkgPiB4MwogICAgICAgICAgICB8fCAoeTEgPSBxLnkwKSA+IHkzCiAgICAgICAgICAgIHx8ICh4MiA9IHEueDEpIDwgeDAKICAgICAgICAgICAgfHwgKHkyID0gcS55MSkgPCB5MCkgY29udGludWU7CgogICAgICAgIC8vIEJpc2VjdCB0aGUgY3VycmVudCBxdWFkcmFudC4KICAgICAgICBpZiAobm9kZS5sZW5ndGgpIHsKICAgICAgICAgIHZhciB4bSA9ICh4MSArIHgyKSAvIDIsCiAgICAgICAgICAgICAgeW0gPSAoeTEgKyB5MikgLyAyOwoKICAgICAgICAgIHF1YWRzLnB1c2goCiAgICAgICAgICAgIG5ldyBRdWFkJDIobm9kZVszXSwgeG0sIHltLCB4MiwgeTIpLAogICAgICAgICAgICBuZXcgUXVhZCQyKG5vZGVbMl0sIHgxLCB5bSwgeG0sIHkyKSwKICAgICAgICAgICAgbmV3IFF1YWQkMihub2RlWzFdLCB4bSwgeTEsIHgyLCB5bSksCiAgICAgICAgICAgIG5ldyBRdWFkJDIobm9kZVswXSwgeDEsIHkxLCB4bSwgeW0pCiAgICAgICAgICApOwoKICAgICAgICAgIC8vIFZpc2l0IHRoZSBjbG9zZXN0IHF1YWRyYW50IGZpcnN0LgogICAgICAgICAgaWYgKGkgPSAoeSA+PSB5bSkgPDwgMSB8ICh4ID49IHhtKSkgewogICAgICAgICAgICBxID0gcXVhZHNbcXVhZHMubGVuZ3RoIC0gMV07CiAgICAgICAgICAgIHF1YWRzW3F1YWRzLmxlbmd0aCAtIDFdID0gcXVhZHNbcXVhZHMubGVuZ3RoIC0gMSAtIGldOwogICAgICAgICAgICBxdWFkc1txdWFkcy5sZW5ndGggLSAxIC0gaV0gPSBxOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gVmlzaXQgdGhpcyBwb2ludC4gKFZpc2l0aW5nIGNvaW5jaWRlbnQgcG9pbnRzIGlzbuKAmXQgbmVjZXNzYXJ5ISkKICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciBkeCA9IHggLSArdGhpcy5feC5jYWxsKG51bGwsIG5vZGUuZGF0YSksCiAgICAgICAgICAgICAgZHkgPSB5IC0gK3RoaXMuX3kuY2FsbChudWxsLCBub2RlLmRhdGEpLAogICAgICAgICAgICAgIGQyID0gZHggKiBkeCArIGR5ICogZHk7CiAgICAgICAgICBpZiAoZDIgPCByYWRpdXMpIHsKICAgICAgICAgICAgdmFyIGQgPSBNYXRoLnNxcnQocmFkaXVzID0gZDIpOwogICAgICAgICAgICB4MCA9IHggLSBkLCB5MCA9IHkgLSBkOwogICAgICAgICAgICB4MyA9IHggKyBkLCB5MyA9IHkgKyBkOwogICAgICAgICAgICBkYXRhID0gbm9kZS5kYXRhOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIGRhdGE7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV9yZW1vdmUkMihkKSB7CiAgICAgIGlmIChpc05hTih4ID0gK3RoaXMuX3guY2FsbChudWxsLCBkKSkgfHwgaXNOYU4oeSA9ICt0aGlzLl95LmNhbGwobnVsbCwgZCkpKSByZXR1cm4gdGhpczsgLy8gaWdub3JlIGludmFsaWQgcG9pbnRzCgogICAgICB2YXIgcGFyZW50LAogICAgICAgICAgbm9kZSA9IHRoaXMuX3Jvb3QsCiAgICAgICAgICByZXRhaW5lciwKICAgICAgICAgIHByZXZpb3VzLAogICAgICAgICAgbmV4dCwKICAgICAgICAgIHgwID0gdGhpcy5feDAsCiAgICAgICAgICB5MCA9IHRoaXMuX3kwLAogICAgICAgICAgeDEgPSB0aGlzLl94MSwKICAgICAgICAgIHkxID0gdGhpcy5feTEsCiAgICAgICAgICB4LAogICAgICAgICAgeSwKICAgICAgICAgIHhtLAogICAgICAgICAgeW0sCiAgICAgICAgICByaWdodCwKICAgICAgICAgIGJvdHRvbSwKICAgICAgICAgIGksCiAgICAgICAgICBqOwoKICAgICAgLy8gSWYgdGhlIHRyZWUgaXMgZW1wdHksIGluaXRpYWxpemUgdGhlIHJvb3QgYXMgYSBsZWFmLgogICAgICBpZiAoIW5vZGUpIHJldHVybiB0aGlzOwoKICAgICAgLy8gRmluZCB0aGUgbGVhZiBub2RlIGZvciB0aGUgcG9pbnQuCiAgICAgIC8vIFdoaWxlIGRlc2NlbmRpbmcsIGFsc28gcmV0YWluIHRoZSBkZWVwZXN0IHBhcmVudCB3aXRoIGEgbm9uLXJlbW92ZWQgc2libGluZy4KICAgICAgaWYgKG5vZGUubGVuZ3RoKSB3aGlsZSAodHJ1ZSkgewogICAgICAgIGlmIChyaWdodCA9IHggPj0gKHhtID0gKHgwICsgeDEpIC8gMikpIHgwID0geG07IGVsc2UgeDEgPSB4bTsKICAgICAgICBpZiAoYm90dG9tID0geSA+PSAoeW0gPSAoeTAgKyB5MSkgLyAyKSkgeTAgPSB5bTsgZWxzZSB5MSA9IHltOwogICAgICAgIGlmICghKHBhcmVudCA9IG5vZGUsIG5vZGUgPSBub2RlW2kgPSBib3R0b20gPDwgMSB8IHJpZ2h0XSkpIHJldHVybiB0aGlzOwogICAgICAgIGlmICghbm9kZS5sZW5ndGgpIGJyZWFrOwogICAgICAgIGlmIChwYXJlbnRbKGkgKyAxKSAmIDNdIHx8IHBhcmVudFsoaSArIDIpICYgM10gfHwgcGFyZW50WyhpICsgMykgJiAzXSkgcmV0YWluZXIgPSBwYXJlbnQsIGogPSBpOwogICAgICB9CgogICAgICAvLyBGaW5kIHRoZSBwb2ludCB0byByZW1vdmUuCiAgICAgIHdoaWxlIChub2RlLmRhdGEgIT09IGQpIGlmICghKHByZXZpb3VzID0gbm9kZSwgbm9kZSA9IG5vZGUubmV4dCkpIHJldHVybiB0aGlzOwogICAgICBpZiAobmV4dCA9IG5vZGUubmV4dCkgZGVsZXRlIG5vZGUubmV4dDsKCiAgICAgIC8vIElmIHRoZXJlIGFyZSBtdWx0aXBsZSBjb2luY2lkZW50IHBvaW50cywgcmVtb3ZlIGp1c3QgdGhlIHBvaW50LgogICAgICBpZiAocHJldmlvdXMpIHJldHVybiAobmV4dCA/IHByZXZpb3VzLm5leHQgPSBuZXh0IDogZGVsZXRlIHByZXZpb3VzLm5leHQpLCB0aGlzOwoKICAgICAgLy8gSWYgdGhpcyBpcyB0aGUgcm9vdCBwb2ludCwgcmVtb3ZlIGl0LgogICAgICBpZiAoIXBhcmVudCkgcmV0dXJuIHRoaXMuX3Jvb3QgPSBuZXh0LCB0aGlzOwoKICAgICAgLy8gUmVtb3ZlIHRoaXMgbGVhZi4KICAgICAgbmV4dCA/IHBhcmVudFtpXSA9IG5leHQgOiBkZWxldGUgcGFyZW50W2ldOwoKICAgICAgLy8gSWYgdGhlIHBhcmVudCBub3cgY29udGFpbnMgZXhhY3RseSBvbmUgbGVhZiwgY29sbGFwc2Ugc3VwZXJmbHVvdXMgcGFyZW50cy4KICAgICAgaWYgKChub2RlID0gcGFyZW50WzBdIHx8IHBhcmVudFsxXSB8fCBwYXJlbnRbMl0gfHwgcGFyZW50WzNdKQogICAgICAgICAgJiYgbm9kZSA9PT0gKHBhcmVudFszXSB8fCBwYXJlbnRbMl0gfHwgcGFyZW50WzFdIHx8IHBhcmVudFswXSkKICAgICAgICAgICYmICFub2RlLmxlbmd0aCkgewogICAgICAgIGlmIChyZXRhaW5lcikgcmV0YWluZXJbal0gPSBub2RlOwogICAgICAgIGVsc2UgdGhpcy5fcm9vdCA9IG5vZGU7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHJlbW92ZUFsbCQyKGRhdGEpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBkYXRhLmxlbmd0aDsgaSA8IG47ICsraSkgdGhpcy5yZW1vdmUoZGF0YVtpXSk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfcm9vdCQyKCkgewogICAgICByZXR1cm4gdGhpcy5fcm9vdDsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3NpemUkMigpIHsKICAgICAgdmFyIHNpemUgPSAwOwogICAgICB0aGlzLnZpc2l0KGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICBpZiAoIW5vZGUubGVuZ3RoKSBkbyArK3NpemU7IHdoaWxlIChub2RlID0gbm9kZS5uZXh0KQogICAgICB9KTsKICAgICAgcmV0dXJuIHNpemU7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV92aXNpdCQyKGNhbGxiYWNrKSB7CiAgICAgIHZhciBxdWFkcyA9IFtdLCBxLCBub2RlID0gdGhpcy5fcm9vdCwgY2hpbGQsIHgwLCB5MCwgeDEsIHkxOwogICAgICBpZiAobm9kZSkgcXVhZHMucHVzaChuZXcgUXVhZCQyKG5vZGUsIHRoaXMuX3gwLCB0aGlzLl95MCwgdGhpcy5feDEsIHRoaXMuX3kxKSk7CiAgICAgIHdoaWxlIChxID0gcXVhZHMucG9wKCkpIHsKICAgICAgICBpZiAoIWNhbGxiYWNrKG5vZGUgPSBxLm5vZGUsIHgwID0gcS54MCwgeTAgPSBxLnkwLCB4MSA9IHEueDEsIHkxID0gcS55MSkgJiYgbm9kZS5sZW5ndGgpIHsKICAgICAgICAgIHZhciB4bSA9ICh4MCArIHgxKSAvIDIsIHltID0gKHkwICsgeTEpIC8gMjsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbM10pIHF1YWRzLnB1c2gobmV3IFF1YWQkMihjaGlsZCwgeG0sIHltLCB4MSwgeTEpKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMl0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMihjaGlsZCwgeDAsIHltLCB4bSwgeTEpKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMV0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMihjaGlsZCwgeG0sIHkwLCB4MSwgeW0pKTsKICAgICAgICAgIGlmIChjaGlsZCA9IG5vZGVbMF0pIHF1YWRzLnB1c2gobmV3IFF1YWQkMihjaGlsZCwgeDAsIHkwLCB4bSwgeW0pKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gdHJlZV92aXNpdEFmdGVyJDIoY2FsbGJhY2spIHsKICAgICAgdmFyIHF1YWRzID0gW10sIG5leHQgPSBbXSwgcTsKICAgICAgaWYgKHRoaXMuX3Jvb3QpIHF1YWRzLnB1c2gobmV3IFF1YWQkMih0aGlzLl9yb290LCB0aGlzLl94MCwgdGhpcy5feTAsIHRoaXMuX3gxLCB0aGlzLl95MSkpOwogICAgICB3aGlsZSAocSA9IHF1YWRzLnBvcCgpKSB7CiAgICAgICAgdmFyIG5vZGUgPSBxLm5vZGU7CiAgICAgICAgaWYgKG5vZGUubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgY2hpbGQsIHgwID0gcS54MCwgeTAgPSBxLnkwLCB4MSA9IHEueDEsIHkxID0gcS55MSwgeG0gPSAoeDAgKyB4MSkgLyAyLCB5bSA9ICh5MCArIHkxKSAvIDI7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzBdKSBxdWFkcy5wdXNoKG5ldyBRdWFkJDIoY2hpbGQsIHgwLCB5MCwgeG0sIHltKSk7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzFdKSBxdWFkcy5wdXNoKG5ldyBRdWFkJDIoY2hpbGQsIHhtLCB5MCwgeDEsIHltKSk7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzJdKSBxdWFkcy5wdXNoKG5ldyBRdWFkJDIoY2hpbGQsIHgwLCB5bSwgeG0sIHkxKSk7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlWzNdKSBxdWFkcy5wdXNoKG5ldyBRdWFkJDIoY2hpbGQsIHhtLCB5bSwgeDEsIHkxKSk7CiAgICAgICAgfQogICAgICAgIG5leHQucHVzaChxKTsKICAgICAgfQogICAgICB3aGlsZSAocSA9IG5leHQucG9wKCkpIHsKICAgICAgICBjYWxsYmFjayhxLm5vZGUsIHEueDAsIHEueTAsIHEueDEsIHEueTEpOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRYJDMoZCkgewogICAgICByZXR1cm4gZFswXTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmVlX3gkMihfKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRoaXMuX3ggPSBfLCB0aGlzKSA6IHRoaXMuX3g7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFkkMyhkKSB7CiAgICAgIHJldHVybiBkWzFdOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVfeSQyKF8pIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGhpcy5feSA9IF8sIHRoaXMpIDogdGhpcy5feTsKICAgIH0KCiAgICBmdW5jdGlvbiBxdWFkdHJlZSQyKG5vZGVzLCB4LCB5KSB7CiAgICAgIHZhciB0cmVlID0gbmV3IFF1YWR0cmVlJDIoeCA9PSBudWxsID8gZGVmYXVsdFgkMyA6IHgsIHkgPT0gbnVsbCA/IGRlZmF1bHRZJDMgOiB5LCBOYU4sIE5hTiwgTmFOLCBOYU4pOwogICAgICByZXR1cm4gbm9kZXMgPT0gbnVsbCA/IHRyZWUgOiB0cmVlLmFkZEFsbChub2Rlcyk7CiAgICB9CgogICAgZnVuY3Rpb24gUXVhZHRyZWUkMih4LCB5LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB0aGlzLl94ID0geDsKICAgICAgdGhpcy5feSA9IHk7CiAgICAgIHRoaXMuX3gwID0geDA7CiAgICAgIHRoaXMuX3kwID0geTA7CiAgICAgIHRoaXMuX3gxID0geDE7CiAgICAgIHRoaXMuX3kxID0geTE7CiAgICAgIHRoaXMuX3Jvb3QgPSB1bmRlZmluZWQ7CiAgICB9CgogICAgZnVuY3Rpb24gbGVhZl9jb3B5JDIobGVhZikgewogICAgICB2YXIgY29weSA9IHtkYXRhOiBsZWFmLmRhdGF9LCBuZXh0ID0gY29weTsKICAgICAgd2hpbGUgKGxlYWYgPSBsZWFmLm5leHQpIG5leHQgPSBuZXh0Lm5leHQgPSB7ZGF0YTogbGVhZi5kYXRhfTsKICAgICAgcmV0dXJuIGNvcHk7CiAgICB9CgogICAgdmFyIHRyZWVQcm90byQyID0gcXVhZHRyZWUkMi5wcm90b3R5cGUgPSBRdWFkdHJlZSQyLnByb3RvdHlwZTsKCiAgICB0cmVlUHJvdG8kMi5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBjb3B5ID0gbmV3IFF1YWR0cmVlJDIodGhpcy5feCwgdGhpcy5feSwgdGhpcy5feDAsIHRoaXMuX3kwLCB0aGlzLl94MSwgdGhpcy5feTEpLAogICAgICAgICAgbm9kZSA9IHRoaXMuX3Jvb3QsCiAgICAgICAgICBub2RlcywKICAgICAgICAgIGNoaWxkOwoKICAgICAgaWYgKCFub2RlKSByZXR1cm4gY29weTsKCiAgICAgIGlmICghbm9kZS5sZW5ndGgpIHJldHVybiBjb3B5Ll9yb290ID0gbGVhZl9jb3B5JDIobm9kZSksIGNvcHk7CgogICAgICBub2RlcyA9IFt7c291cmNlOiBub2RlLCB0YXJnZXQ6IGNvcHkuX3Jvb3QgPSBuZXcgQXJyYXkoNCl9XTsKICAgICAgd2hpbGUgKG5vZGUgPSBub2Rlcy5wb3AoKSkgewogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgNDsgKytpKSB7CiAgICAgICAgICBpZiAoY2hpbGQgPSBub2RlLnNvdXJjZVtpXSkgewogICAgICAgICAgICBpZiAoY2hpbGQubGVuZ3RoKSBub2Rlcy5wdXNoKHtzb3VyY2U6IGNoaWxkLCB0YXJnZXQ6IG5vZGUudGFyZ2V0W2ldID0gbmV3IEFycmF5KDQpfSk7CiAgICAgICAgICAgIGVsc2Ugbm9kZS50YXJnZXRbaV0gPSBsZWFmX2NvcHkkMihjaGlsZCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gY29weTsKICAgIH07CgogICAgdHJlZVByb3RvJDIuYWRkID0gdHJlZV9hZGQkMjsKICAgIHRyZWVQcm90byQyLmFkZEFsbCA9IGFkZEFsbCQyOwogICAgdHJlZVByb3RvJDIuY292ZXIgPSB0cmVlX2NvdmVyJDI7CiAgICB0cmVlUHJvdG8kMi5kYXRhID0gdHJlZV9kYXRhJDI7CiAgICB0cmVlUHJvdG8kMi5leHRlbnQgPSB0cmVlX2V4dGVudCQyOwogICAgdHJlZVByb3RvJDIuZmluZCA9IHRyZWVfZmluZCQyOwogICAgdHJlZVByb3RvJDIucmVtb3ZlID0gdHJlZV9yZW1vdmUkMjsKICAgIHRyZWVQcm90byQyLnJlbW92ZUFsbCA9IHJlbW92ZUFsbCQyOwogICAgdHJlZVByb3RvJDIucm9vdCA9IHRyZWVfcm9vdCQyOwogICAgdHJlZVByb3RvJDIuc2l6ZSA9IHRyZWVfc2l6ZSQyOwogICAgdHJlZVByb3RvJDIudmlzaXQgPSB0cmVlX3Zpc2l0JDI7CiAgICB0cmVlUHJvdG8kMi52aXNpdEFmdGVyID0gdHJlZV92aXNpdEFmdGVyJDI7CiAgICB0cmVlUHJvdG8kMi54ID0gdHJlZV94JDI7CiAgICB0cmVlUHJvdG8kMi55ID0gdHJlZV95JDI7CgogICAgdmFyIHNsaWNlJGIgPSBbXS5zbGljZTsKCiAgICB2YXIgbm9hYm9ydCA9IHt9OwoKICAgIGZ1bmN0aW9uIFF1ZXVlKHNpemUpIHsKICAgICAgdGhpcy5fc2l6ZSA9IHNpemU7CiAgICAgIHRoaXMuX2NhbGwgPQogICAgICB0aGlzLl9lcnJvciA9IG51bGw7CiAgICAgIHRoaXMuX3Rhc2tzID0gW107CiAgICAgIHRoaXMuX2RhdGEgPSBbXTsKICAgICAgdGhpcy5fd2FpdGluZyA9CiAgICAgIHRoaXMuX2FjdGl2ZSA9CiAgICAgIHRoaXMuX2VuZGVkID0KICAgICAgdGhpcy5fc3RhcnQgPSAwOyAvLyBpbnNpZGUgYSBzeW5jaHJvbm91cyB0YXNrIGNhbGxiYWNrPwogICAgfQoKICAgIFF1ZXVlLnByb3RvdHlwZSA9IHF1ZXVlLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFF1ZXVlLAogICAgICBkZWZlcjogZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgICBpZiAodHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2FsbGJhY2siKTsKICAgICAgICBpZiAodGhpcy5fY2FsbCkgdGhyb3cgbmV3IEVycm9yKCJkZWZlciBhZnRlciBhd2FpdCIpOwogICAgICAgIGlmICh0aGlzLl9lcnJvciAhPSBudWxsKSByZXR1cm4gdGhpczsKICAgICAgICB2YXIgdCA9IHNsaWNlJGIuY2FsbChhcmd1bWVudHMsIDEpOwogICAgICAgIHQucHVzaChjYWxsYmFjayk7CiAgICAgICAgKyt0aGlzLl93YWl0aW5nLCB0aGlzLl90YXNrcy5wdXNoKHQpOwogICAgICAgIHBva2UkMyh0aGlzKTsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgYWJvcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9lcnJvciA9PSBudWxsKSBhYm9ydCh0aGlzLCBuZXcgRXJyb3IoImFib3J0IikpOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICBhd2FpdDogZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgICBpZiAodHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2FsbGJhY2siKTsKICAgICAgICBpZiAodGhpcy5fY2FsbCkgdGhyb3cgbmV3IEVycm9yKCJtdWx0aXBsZSBhd2FpdCIpOwogICAgICAgIHRoaXMuX2NhbGwgPSBmdW5jdGlvbihlcnJvciwgcmVzdWx0cykgeyBjYWxsYmFjay5hcHBseShudWxsLCBbZXJyb3JdLmNvbmNhdChyZXN1bHRzKSk7IH07CiAgICAgICAgbWF5YmVOb3RpZnkodGhpcyk7CiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIGF3YWl0QWxsOiBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICAgIGlmICh0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcigiaW52YWxpZCBjYWxsYmFjayIpOwogICAgICAgIGlmICh0aGlzLl9jYWxsKSB0aHJvdyBuZXcgRXJyb3IoIm11bHRpcGxlIGF3YWl0Iik7CiAgICAgICAgdGhpcy5fY2FsbCA9IGNhbGxiYWNrOwogICAgICAgIG1heWJlTm90aWZ5KHRoaXMpOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHBva2UkMyhxKSB7CiAgICAgIGlmICghcS5fc3RhcnQpIHsKICAgICAgICB0cnkgeyBzdGFydCQyKHEpOyB9IC8vIGxldCB0aGUgY3VycmVudCB0YXNrIGNvbXBsZXRlCiAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgIGlmIChxLl90YXNrc1txLl9lbmRlZCArIHEuX2FjdGl2ZSAtIDFdKSBhYm9ydChxLCBlKTsgLy8gdGFzayBlcnJvcmVkIHN5bmNocm9ub3VzbHkKICAgICAgICAgIGVsc2UgaWYgKCFxLl9kYXRhKSB0aHJvdyBlOyAvLyBhd2FpdCBjYWxsYmFjayBlcnJvcmVkIHN5bmNocm9ub3VzbHkKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzdGFydCQyKHEpIHsKICAgICAgd2hpbGUgKHEuX3N0YXJ0ID0gcS5fd2FpdGluZyAmJiBxLl9hY3RpdmUgPCBxLl9zaXplKSB7CiAgICAgICAgdmFyIGkgPSBxLl9lbmRlZCArIHEuX2FjdGl2ZSwKICAgICAgICAgICAgdCA9IHEuX3Rhc2tzW2ldLAogICAgICAgICAgICBqID0gdC5sZW5ndGggLSAxLAogICAgICAgICAgICBjID0gdFtqXTsKICAgICAgICB0W2pdID0gZW5kKHEsIGkpOwogICAgICAgIC0tcS5fd2FpdGluZywgKytxLl9hY3RpdmU7CiAgICAgICAgdCA9IGMuYXBwbHkobnVsbCwgdCk7CiAgICAgICAgaWYgKCFxLl90YXNrc1tpXSkgY29udGludWU7IC8vIHRhc2sgZmluaXNoZWQgc3luY2hyb25vdXNseQogICAgICAgIHEuX3Rhc2tzW2ldID0gdCB8fCBub2Fib3J0OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZW5kKHEsIGkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGUsIHIpIHsKICAgICAgICBpZiAoIXEuX3Rhc2tzW2ldKSByZXR1cm47IC8vIGlnbm9yZSBtdWx0aXBsZSBjYWxsYmFja3MKICAgICAgICAtLXEuX2FjdGl2ZSwgKytxLl9lbmRlZDsKICAgICAgICBxLl90YXNrc1tpXSA9IG51bGw7CiAgICAgICAgaWYgKHEuX2Vycm9yICE9IG51bGwpIHJldHVybjsgLy8gaWdub3JlIHNlY29uZGFyeSBlcnJvcnMKICAgICAgICBpZiAoZSAhPSBudWxsKSB7CiAgICAgICAgICBhYm9ydChxLCBlKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcS5fZGF0YVtpXSA9IHI7CiAgICAgICAgICBpZiAocS5fd2FpdGluZykgcG9rZSQzKHEpOwogICAgICAgICAgZWxzZSBtYXliZU5vdGlmeShxKTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYWJvcnQocSwgZSkgewogICAgICB2YXIgaSA9IHEuX3Rhc2tzLmxlbmd0aCwgdDsKICAgICAgcS5fZXJyb3IgPSBlOyAvLyBpZ25vcmUgYWN0aXZlIGNhbGxiYWNrcwogICAgICBxLl9kYXRhID0gdW5kZWZpbmVkOyAvLyBhbGxvdyBnYwogICAgICBxLl93YWl0aW5nID0gTmFOOyAvLyBwcmV2ZW50IHN0YXJ0aW5nCgogICAgICB3aGlsZSAoLS1pID49IDApIHsKICAgICAgICBpZiAodCA9IHEuX3Rhc2tzW2ldKSB7CiAgICAgICAgICBxLl90YXNrc1tpXSA9IG51bGw7CiAgICAgICAgICBpZiAodC5hYm9ydCkgewogICAgICAgICAgICB0cnkgeyB0LmFib3J0KCk7IH0KICAgICAgICAgICAgY2F0Y2ggKGUpIHsgLyogaWdub3JlICovIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHEuX2FjdGl2ZSA9IE5hTjsgLy8gYWxsb3cgbm90aWZpY2F0aW9uCiAgICAgIG1heWJlTm90aWZ5KHEpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1heWJlTm90aWZ5KHEpIHsKICAgICAgaWYgKCFxLl9hY3RpdmUgJiYgcS5fY2FsbCkgewogICAgICAgIHZhciBkID0gcS5fZGF0YTsKICAgICAgICBxLl9kYXRhID0gdW5kZWZpbmVkOyAvLyBhbGxvdyBnYwogICAgICAgIHEuX2NhbGwocS5fZXJyb3IsIGQpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcXVldWUoY29uY3VycmVuY3kpIHsKICAgICAgaWYgKGNvbmN1cnJlbmN5ID09IG51bGwpIGNvbmN1cnJlbmN5ID0gSW5maW5pdHk7CiAgICAgIGVsc2UgaWYgKCEoKGNvbmN1cnJlbmN5ID0gK2NvbmN1cnJlbmN5KSA+PSAxKSkgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIGNvbmN1cnJlbmN5Iik7CiAgICAgIHJldHVybiBuZXcgUXVldWUoY29uY3VycmVuY3kpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmF1bHRTb3VyY2UkMygpIHsKICAgICAgcmV0dXJuIE1hdGgucmFuZG9tKCk7CiAgICB9CgogICAgdmFyIHVuaWZvcm0kMSA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21Vbmlmb3JtKHNvdXJjZSkgewogICAgICBmdW5jdGlvbiByYW5kb21Vbmlmb3JtKG1pbiwgbWF4KSB7CiAgICAgICAgbWluID0gbWluID09IG51bGwgPyAwIDogK21pbjsKICAgICAgICBtYXggPSBtYXggPT0gbnVsbCA/IDEgOiArbWF4OwogICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID09PSAxKSBtYXggPSBtaW4sIG1pbiA9IDA7CiAgICAgICAgZWxzZSBtYXggLT0gbWluOwogICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgIHJldHVybiBzb3VyY2UoKSAqIG1heCArIG1pbjsKICAgICAgICB9OwogICAgICB9CgogICAgICByYW5kb21Vbmlmb3JtLnNvdXJjZSA9IHNvdXJjZVJhbmRvbVVuaWZvcm07CgogICAgICByZXR1cm4gcmFuZG9tVW5pZm9ybTsKICAgIH0pKGRlZmF1bHRTb3VyY2UkMyk7CgogICAgdmFyIG5vcm1hbCQxID0gKGZ1bmN0aW9uIHNvdXJjZVJhbmRvbU5vcm1hbChzb3VyY2UpIHsKICAgICAgZnVuY3Rpb24gcmFuZG9tTm9ybWFsKG11LCBzaWdtYSkgewogICAgICAgIHZhciB4LCByOwogICAgICAgIG11ID0gbXUgPT0gbnVsbCA/IDAgOiArbXU7CiAgICAgICAgc2lnbWEgPSBzaWdtYSA9PSBudWxsID8gMSA6ICtzaWdtYTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgeTsKCiAgICAgICAgICAvLyBJZiBhdmFpbGFibGUsIHVzZSB0aGUgc2Vjb25kIHByZXZpb3VzbHktZ2VuZXJhdGVkIHVuaWZvcm0gcmFuZG9tLgogICAgICAgICAgaWYgKHggIT0gbnVsbCkgeSA9IHgsIHggPSBudWxsOwoKICAgICAgICAgIC8vIE90aGVyd2lzZSwgZ2VuZXJhdGUgYSBuZXcgeCBhbmQgeS4KICAgICAgICAgIGVsc2UgZG8gewogICAgICAgICAgICB4ID0gc291cmNlKCkgKiAyIC0gMTsKICAgICAgICAgICAgeSA9IHNvdXJjZSgpICogMiAtIDE7CiAgICAgICAgICAgIHIgPSB4ICogeCArIHkgKiB5OwogICAgICAgICAgfSB3aGlsZSAoIXIgfHwgciA+IDEpOwoKICAgICAgICAgIHJldHVybiBtdSArIHNpZ21hICogeSAqIE1hdGguc3FydCgtMiAqIE1hdGgubG9nKHIpIC8gcik7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgcmFuZG9tTm9ybWFsLnNvdXJjZSA9IHNvdXJjZVJhbmRvbU5vcm1hbDsKCiAgICAgIHJldHVybiByYW5kb21Ob3JtYWw7CiAgICB9KShkZWZhdWx0U291cmNlJDMpOwoKICAgIHZhciBsb2dOb3JtYWwkMSA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21Mb2dOb3JtYWwoc291cmNlKSB7CiAgICAgIGZ1bmN0aW9uIHJhbmRvbUxvZ05vcm1hbCgpIHsKICAgICAgICB2YXIgcmFuZG9tTm9ybWFsID0gbm9ybWFsJDEuc291cmNlKHNvdXJjZSkuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gTWF0aC5leHAocmFuZG9tTm9ybWFsKCkpOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJhbmRvbUxvZ05vcm1hbC5zb3VyY2UgPSBzb3VyY2VSYW5kb21Mb2dOb3JtYWw7CgogICAgICByZXR1cm4gcmFuZG9tTG9nTm9ybWFsOwogICAgfSkoZGVmYXVsdFNvdXJjZSQzKTsKCiAgICB2YXIgaXJ3aW5IYWxsJDEgPSAoZnVuY3Rpb24gc291cmNlUmFuZG9tSXJ3aW5IYWxsKHNvdXJjZSkgewogICAgICBmdW5jdGlvbiByYW5kb21JcndpbkhhbGwobikgewogICAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAgIGZvciAodmFyIHN1bSA9IDAsIGkgPSAwOyBpIDwgbjsgKytpKSBzdW0gKz0gc291cmNlKCk7CiAgICAgICAgICByZXR1cm4gc3VtOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJhbmRvbUlyd2luSGFsbC5zb3VyY2UgPSBzb3VyY2VSYW5kb21JcndpbkhhbGw7CgogICAgICByZXR1cm4gcmFuZG9tSXJ3aW5IYWxsOwogICAgfSkoZGVmYXVsdFNvdXJjZSQzKTsKCiAgICB2YXIgYmF0ZXMkMSA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21CYXRlcyhzb3VyY2UpIHsKICAgICAgZnVuY3Rpb24gcmFuZG9tQmF0ZXMobikgewogICAgICAgIHZhciByYW5kb21JcndpbkhhbGwgPSBpcndpbkhhbGwkMS5zb3VyY2Uoc291cmNlKShuKTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICByZXR1cm4gcmFuZG9tSXJ3aW5IYWxsKCkgLyBuOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJhbmRvbUJhdGVzLnNvdXJjZSA9IHNvdXJjZVJhbmRvbUJhdGVzOwoKICAgICAgcmV0dXJuIHJhbmRvbUJhdGVzOwogICAgfSkoZGVmYXVsdFNvdXJjZSQzKTsKCiAgICB2YXIgZXhwb25lbnRpYWwkNCA9IChmdW5jdGlvbiBzb3VyY2VSYW5kb21FeHBvbmVudGlhbChzb3VyY2UpIHsKICAgICAgZnVuY3Rpb24gcmFuZG9tRXhwb25lbnRpYWwobGFtYmRhKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIC1NYXRoLmxvZygxIC0gc291cmNlKCkpIC8gbGFtYmRhOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJhbmRvbUV4cG9uZW50aWFsLnNvdXJjZSA9IHNvdXJjZVJhbmRvbUV4cG9uZW50aWFsOwoKICAgICAgcmV0dXJuIHJhbmRvbUV4cG9uZW50aWFsOwogICAgfSkoZGVmYXVsdFNvdXJjZSQzKTsKCiAgICBmdW5jdGlvbiByZXF1ZXN0KHVybCwgY2FsbGJhY2spIHsKICAgICAgdmFyIHJlcXVlc3QsCiAgICAgICAgICBldmVudCA9IGRpc3BhdGNoKCJiZWZvcmVzZW5kIiwgInByb2dyZXNzIiwgImxvYWQiLCAiZXJyb3IiKSwKICAgICAgICAgIG1pbWVUeXBlLAogICAgICAgICAgaGVhZGVycyA9IG1hcCQxKCksCiAgICAgICAgICB4aHIgPSBuZXcgWE1MSHR0cFJlcXVlc3QsCiAgICAgICAgICB1c2VyID0gbnVsbCwKICAgICAgICAgIHBhc3N3b3JkID0gbnVsbCwKICAgICAgICAgIHJlc3BvbnNlLAogICAgICAgICAgcmVzcG9uc2VUeXBlLAogICAgICAgICAgdGltZW91dCA9IDA7CgogICAgICAvLyBJZiBJRSBkb2VzIG5vdCBzdXBwb3J0IENPUlMsIHVzZSBYRG9tYWluUmVxdWVzdC4KICAgICAgaWYgKHR5cGVvZiBYRG9tYWluUmVxdWVzdCAhPT0gInVuZGVmaW5lZCIKICAgICAgICAgICYmICEoIndpdGhDcmVkZW50aWFscyIgaW4geGhyKQogICAgICAgICAgJiYgL14oaHR0cChzKT86KT9cL1wvLy50ZXN0KHVybCkpIHhociA9IG5ldyBYRG9tYWluUmVxdWVzdDsKCiAgICAgICJvbmxvYWQiIGluIHhocgogICAgICAgICAgPyB4aHIub25sb2FkID0geGhyLm9uZXJyb3IgPSB4aHIub250aW1lb3V0ID0gcmVzcG9uZAogICAgICAgICAgOiB4aHIub25yZWFkeXN0YXRlY2hhbmdlID0gZnVuY3Rpb24obykgeyB4aHIucmVhZHlTdGF0ZSA+IDMgJiYgcmVzcG9uZChvKTsgfTsKCiAgICAgIGZ1bmN0aW9uIHJlc3BvbmQobykgewogICAgICAgIHZhciBzdGF0dXMgPSB4aHIuc3RhdHVzLCByZXN1bHQ7CiAgICAgICAgaWYgKCFzdGF0dXMgJiYgaGFzUmVzcG9uc2UoeGhyKQogICAgICAgICAgICB8fCBzdGF0dXMgPj0gMjAwICYmIHN0YXR1cyA8IDMwMAogICAgICAgICAgICB8fCBzdGF0dXMgPT09IDMwNCkgewogICAgICAgICAgaWYgKHJlc3BvbnNlKSB7CiAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgcmVzdWx0ID0gcmVzcG9uc2UuY2FsbChyZXF1ZXN0LCB4aHIpOwogICAgICAgICAgICB9IGNhdGNoIChlKSB7CiAgICAgICAgICAgICAgZXZlbnQuY2FsbCgiZXJyb3IiLCByZXF1ZXN0LCBlKTsKICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHJlc3VsdCA9IHhocjsKICAgICAgICAgIH0KICAgICAgICAgIGV2ZW50LmNhbGwoImxvYWQiLCByZXF1ZXN0LCByZXN1bHQpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBldmVudC5jYWxsKCJlcnJvciIsIHJlcXVlc3QsIG8pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgeGhyLm9ucHJvZ3Jlc3MgPSBmdW5jdGlvbihlKSB7CiAgICAgICAgZXZlbnQuY2FsbCgicHJvZ3Jlc3MiLCByZXF1ZXN0LCBlKTsKICAgICAgfTsKCiAgICAgIHJlcXVlc3QgPSB7CiAgICAgICAgaGVhZGVyOiBmdW5jdGlvbihuYW1lLCB2YWx1ZSkgewogICAgICAgICAgbmFtZSA9IChuYW1lICsgIiIpLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHJldHVybiBoZWFkZXJzLmdldChuYW1lKTsKICAgICAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSBoZWFkZXJzLnJlbW92ZShuYW1lKTsKICAgICAgICAgIGVsc2UgaGVhZGVycy5zZXQobmFtZSwgdmFsdWUgKyAiIik7CiAgICAgICAgICByZXR1cm4gcmVxdWVzdDsKICAgICAgICB9LAoKICAgICAgICAvLyBJZiBtaW1lVHlwZSBpcyBub24tbnVsbCBhbmQgbm8gQWNjZXB0IGhlYWRlciBpcyBzZXQsIGEgZGVmYXVsdCBpcyB1c2VkLgogICAgICAgIG1pbWVUeXBlOiBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gbWltZVR5cGU7CiAgICAgICAgICBtaW1lVHlwZSA9IHZhbHVlID09IG51bGwgPyBudWxsIDogdmFsdWUgKyAiIjsKICAgICAgICAgIHJldHVybiByZXF1ZXN0OwogICAgICAgIH0sCgogICAgICAgIC8vIFNwZWNpZmllcyB3aGF0IHR5cGUgdGhlIHJlc3BvbnNlIHZhbHVlIHNob3VsZCB0YWtlOwogICAgICAgIC8vIGZvciBpbnN0YW5jZSwgYXJyYXlidWZmZXIsIGJsb2IsIGRvY3VtZW50LCBvciB0ZXh0LgogICAgICAgIHJlc3BvbnNlVHlwZTogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIHJlc3BvbnNlVHlwZTsKICAgICAgICAgIHJlc3BvbnNlVHlwZSA9IHZhbHVlOwogICAgICAgICAgcmV0dXJuIHJlcXVlc3Q7CiAgICAgICAgfSwKCiAgICAgICAgdGltZW91dDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIHRpbWVvdXQ7CiAgICAgICAgICB0aW1lb3V0ID0gK3ZhbHVlOwogICAgICAgICAgcmV0dXJuIHJlcXVlc3Q7CiAgICAgICAgfSwKCiAgICAgICAgdXNlcjogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoIDwgMSA/IHVzZXIgOiAodXNlciA9IHZhbHVlID09IG51bGwgPyBudWxsIDogdmFsdWUgKyAiIiwgcmVxdWVzdCk7CiAgICAgICAgfSwKCiAgICAgICAgcGFzc3dvcmQ6IGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA8IDEgPyBwYXNzd29yZCA6IChwYXNzd29yZCA9IHZhbHVlID09IG51bGwgPyBudWxsIDogdmFsdWUgKyAiIiwgcmVxdWVzdCk7CiAgICAgICAgfSwKCiAgICAgICAgLy8gU3BlY2lmeSBob3cgdG8gY29udmVydCB0aGUgcmVzcG9uc2UgY29udGVudCB0byBhIHNwZWNpZmljIHR5cGU7CiAgICAgICAgLy8gY2hhbmdlcyB0aGUgY2FsbGJhY2sgdmFsdWUgb24gImxvYWQiIGV2ZW50cy4KICAgICAgICByZXNwb25zZTogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICAgIHJlc3BvbnNlID0gdmFsdWU7CiAgICAgICAgICByZXR1cm4gcmVxdWVzdDsKICAgICAgICB9LAoKICAgICAgICAvLyBBbGlhcyBmb3Igc2VuZCgiR0VUIiwg4oCmKS4KICAgICAgICBnZXQ6IGZ1bmN0aW9uKGRhdGEsIGNhbGxiYWNrKSB7CiAgICAgICAgICByZXR1cm4gcmVxdWVzdC5zZW5kKCJHRVQiLCBkYXRhLCBjYWxsYmFjayk7CiAgICAgICAgfSwKCiAgICAgICAgLy8gQWxpYXMgZm9yIHNlbmQoIlBPU1QiLCDigKYpLgogICAgICAgIHBvc3Q6IGZ1bmN0aW9uKGRhdGEsIGNhbGxiYWNrKSB7CiAgICAgICAgICByZXR1cm4gcmVxdWVzdC5zZW5kKCJQT1NUIiwgZGF0YSwgY2FsbGJhY2spOwogICAgICAgIH0sCgogICAgICAgIC8vIElmIGNhbGxiYWNrIGlzIG5vbi1udWxsLCBpdCB3aWxsIGJlIHVzZWQgZm9yIGVycm9yIGFuZCBsb2FkIGV2ZW50cy4KICAgICAgICBzZW5kOiBmdW5jdGlvbihtZXRob2QsIGRhdGEsIGNhbGxiYWNrKSB7CiAgICAgICAgICB4aHIub3BlbihtZXRob2QsIHVybCwgdHJ1ZSwgdXNlciwgcGFzc3dvcmQpOwogICAgICAgICAgaWYgKG1pbWVUeXBlICE9IG51bGwgJiYgIWhlYWRlcnMuaGFzKCJhY2NlcHQiKSkgaGVhZGVycy5zZXQoImFjY2VwdCIsIG1pbWVUeXBlICsgIiwqLyoiKTsKICAgICAgICAgIGlmICh4aHIuc2V0UmVxdWVzdEhlYWRlcikgaGVhZGVycy5lYWNoKGZ1bmN0aW9uKHZhbHVlLCBuYW1lKSB7IHhoci5zZXRSZXF1ZXN0SGVhZGVyKG5hbWUsIHZhbHVlKTsgfSk7CiAgICAgICAgICBpZiAobWltZVR5cGUgIT0gbnVsbCAmJiB4aHIub3ZlcnJpZGVNaW1lVHlwZSkgeGhyLm92ZXJyaWRlTWltZVR5cGUobWltZVR5cGUpOwogICAgICAgICAgaWYgKHJlc3BvbnNlVHlwZSAhPSBudWxsKSB4aHIucmVzcG9uc2VUeXBlID0gcmVzcG9uc2VUeXBlOwogICAgICAgICAgaWYgKHRpbWVvdXQgPiAwKSB4aHIudGltZW91dCA9IHRpbWVvdXQ7CiAgICAgICAgICBpZiAoY2FsbGJhY2sgPT0gbnVsbCAmJiB0eXBlb2YgZGF0YSA9PT0gImZ1bmN0aW9uIikgY2FsbGJhY2sgPSBkYXRhLCBkYXRhID0gbnVsbDsKICAgICAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsICYmIGNhbGxiYWNrLmxlbmd0aCA9PT0gMSkgY2FsbGJhY2sgPSBmaXhDYWxsYmFjayhjYWxsYmFjayk7CiAgICAgICAgICBpZiAoY2FsbGJhY2sgIT0gbnVsbCkgcmVxdWVzdC5vbigiZXJyb3IiLCBjYWxsYmFjaykub24oImxvYWQiLCBmdW5jdGlvbih4aHIpIHsgY2FsbGJhY2sobnVsbCwgeGhyKTsgfSk7CiAgICAgICAgICBldmVudC5jYWxsKCJiZWZvcmVzZW5kIiwgcmVxdWVzdCwgeGhyKTsKICAgICAgICAgIHhoci5zZW5kKGRhdGEgPT0gbnVsbCA/IG51bGwgOiBkYXRhKTsKICAgICAgICAgIHJldHVybiByZXF1ZXN0OwogICAgICAgIH0sCgogICAgICAgIGFib3J0OiBmdW5jdGlvbigpIHsKICAgICAgICAgIHhoci5hYm9ydCgpOwogICAgICAgICAgcmV0dXJuIHJlcXVlc3Q7CiAgICAgICAgfSwKCiAgICAgICAgb246IGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIHZhbHVlID0gZXZlbnQub24uYXBwbHkoZXZlbnQsIGFyZ3VtZW50cyk7CiAgICAgICAgICByZXR1cm4gdmFsdWUgPT09IGV2ZW50ID8gcmVxdWVzdCA6IHZhbHVlOwogICAgICAgIH0KICAgICAgfTsKCiAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsKSB7CiAgICAgICAgaWYgKHR5cGVvZiBjYWxsYmFjayAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIGNhbGxiYWNrOiAiICsgY2FsbGJhY2spOwogICAgICAgIHJldHVybiByZXF1ZXN0LmdldChjYWxsYmFjayk7CiAgICAgIH0KCiAgICAgIHJldHVybiByZXF1ZXN0OwogICAgfQoKICAgIGZ1bmN0aW9uIGZpeENhbGxiYWNrKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihlcnJvciwgeGhyKSB7CiAgICAgICAgY2FsbGJhY2soZXJyb3IgPT0gbnVsbCA/IHhociA6IG51bGwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGhhc1Jlc3BvbnNlKHhocikgewogICAgICB2YXIgdHlwZSA9IHhoci5yZXNwb25zZVR5cGU7CiAgICAgIHJldHVybiB0eXBlICYmIHR5cGUgIT09ICJ0ZXh0IgogICAgICAgICAgPyB4aHIucmVzcG9uc2UgLy8gbnVsbCBvbiBlcnJvcgogICAgICAgICAgOiB4aHIucmVzcG9uc2VUZXh0OyAvLyAiIiBvbiBlcnJvcgogICAgfQoKICAgIGZ1bmN0aW9uIHR5cGUkMihkZWZhdWx0TWltZVR5cGUsIHJlc3BvbnNlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih1cmwsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIHIgPSByZXF1ZXN0KHVybCkubWltZVR5cGUoZGVmYXVsdE1pbWVUeXBlKS5yZXNwb25zZShyZXNwb25zZSk7CiAgICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwpIHsKICAgICAgICAgIGlmICh0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcigiaW52YWxpZCBjYWxsYmFjazogIiArIGNhbGxiYWNrKTsKICAgICAgICAgIHJldHVybiByLmdldChjYWxsYmFjayk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByOwogICAgICB9OwogICAgfQoKICAgIHZhciBodG1sJDIgPSB0eXBlJDIoInRleHQvaHRtbCIsIGZ1bmN0aW9uKHhocikgewogICAgICByZXR1cm4gZG9jdW1lbnQuY3JlYXRlUmFuZ2UoKS5jcmVhdGVDb250ZXh0dWFsRnJhZ21lbnQoeGhyLnJlc3BvbnNlVGV4dCk7CiAgICB9KTsKCiAgICB2YXIganNvbiQxID0gdHlwZSQyKCJhcHBsaWNhdGlvbi9qc29uIiwgZnVuY3Rpb24oeGhyKSB7CiAgICAgIHJldHVybiBKU09OLnBhcnNlKHhoci5yZXNwb25zZVRleHQpOwogICAgfSk7CgogICAgdmFyIHRleHQkMSA9IHR5cGUkMigidGV4dC9wbGFpbiIsIGZ1bmN0aW9uKHhocikgewogICAgICByZXR1cm4geGhyLnJlc3BvbnNlVGV4dDsKICAgIH0pOwoKICAgIHZhciB4bWwkMSA9IHR5cGUkMigiYXBwbGljYXRpb24veG1sIiwgZnVuY3Rpb24oeGhyKSB7CiAgICAgIHZhciB4bWwgPSB4aHIucmVzcG9uc2VYTUw7CiAgICAgIGlmICgheG1sKSB0aHJvdyBuZXcgRXJyb3IoInBhcnNlIGVycm9yIik7CiAgICAgIHJldHVybiB4bWw7CiAgICB9KTsKCiAgICBmdW5jdGlvbiBkc3YkMihkZWZhdWx0TWltZVR5cGUsIHBhcnNlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih1cmwsIHJvdywgY2FsbGJhY2spIHsKICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDMpIGNhbGxiYWNrID0gcm93LCByb3cgPSBudWxsOwogICAgICAgIHZhciByID0gcmVxdWVzdCh1cmwpLm1pbWVUeXBlKGRlZmF1bHRNaW1lVHlwZSk7CiAgICAgICAgci5yb3cgPSBmdW5jdGlvbihfKSB7IHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gci5yZXNwb25zZShyZXNwb25zZU9mKHBhcnNlLCByb3cgPSBfKSkgOiByb3c7IH07CiAgICAgICAgci5yb3cocm93KTsKICAgICAgICByZXR1cm4gY2FsbGJhY2sgPyByLmdldChjYWxsYmFjaykgOiByOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHJlc3BvbnNlT2YocGFyc2UsIHJvdykgewogICAgICByZXR1cm4gZnVuY3Rpb24ocmVxdWVzdCkgewogICAgICAgIHJldHVybiBwYXJzZShyZXF1ZXN0LnJlc3BvbnNlVGV4dCwgcm93KTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgY3N2JDMgPSBkc3YkMigidGV4dC9jc3YiLCBjc3ZQYXJzZSk7CgogICAgdmFyIHRzdiQzID0gZHN2JDIoInRleHQvdGFiLXNlcGFyYXRlZC12YWx1ZXMiLCB0c3ZQYXJzZSk7CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nJDkoYSwgYikgewogICAgICByZXR1cm4gYSA8IGIgPyAtMSA6IGEgPiBiID8gMSA6IGEgPj0gYiA/IDAgOiBOYU47CiAgICB9CgogICAgZnVuY3Rpb24gYmlzZWN0b3IkNChjb21wYXJlKSB7CiAgICAgIGlmIChjb21wYXJlLmxlbmd0aCA9PT0gMSkgY29tcGFyZSA9IGFzY2VuZGluZ0NvbXBhcmF0b3IkNChjb21wYXJlKTsKICAgICAgcmV0dXJuIHsKICAgICAgICBsZWZ0OiBmdW5jdGlvbihhLCB4LCBsbywgaGkpIHsKICAgICAgICAgIGlmIChsbyA9PSBudWxsKSBsbyA9IDA7CiAgICAgICAgICBpZiAoaGkgPT0gbnVsbCkgaGkgPSBhLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChsbyA8IGhpKSB7CiAgICAgICAgICAgIHZhciBtaWQgPSBsbyArIGhpID4+PiAxOwogICAgICAgICAgICBpZiAoY29tcGFyZShhW21pZF0sIHgpIDwgMCkgbG8gPSBtaWQgKyAxOwogICAgICAgICAgICBlbHNlIGhpID0gbWlkOwogICAgICAgICAgfQogICAgICAgICAgcmV0dXJuIGxvOwogICAgICAgIH0sCiAgICAgICAgcmlnaHQ6IGZ1bmN0aW9uKGEsIHgsIGxvLCBoaSkgewogICAgICAgICAgaWYgKGxvID09IG51bGwpIGxvID0gMDsKICAgICAgICAgIGlmIChoaSA9PSBudWxsKSBoaSA9IGEubGVuZ3RoOwogICAgICAgICAgd2hpbGUgKGxvIDwgaGkpIHsKICAgICAgICAgICAgdmFyIG1pZCA9IGxvICsgaGkgPj4+IDE7CiAgICAgICAgICAgIGlmIChjb21wYXJlKGFbbWlkXSwgeCkgPiAwKSBoaSA9IG1pZDsKICAgICAgICAgICAgZWxzZSBsbyA9IG1pZCArIDE7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gbG87CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZ0NvbXBhcmF0b3IkNChmKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihkLCB4KSB7CiAgICAgICAgcmV0dXJuIGFzY2VuZGluZyQ5KGYoZCksIHgpOwogICAgICB9OwogICAgfQoKICAgIHZhciBhc2NlbmRpbmdCaXNlY3QkNCA9IGJpc2VjdG9yJDQoYXNjZW5kaW5nJDkpOwogICAgdmFyIGJpc2VjdFJpZ2h0JDIgPSBhc2NlbmRpbmdCaXNlY3QkNC5yaWdodDsKCiAgICBmdW5jdGlvbiBudW1iZXIkNyh4KSB7CiAgICAgIHJldHVybiB4ID09PSBudWxsID8gTmFOIDogK3g7CiAgICB9CgogICAgZnVuY3Rpb24gc2VxdWVuY2UkMShzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICBzdGFydCA9ICtzdGFydCwgc3RvcCA9ICtzdG9wLCBzdGVwID0gKG4gPSBhcmd1bWVudHMubGVuZ3RoKSA8IDIgPyAoc3RvcCA9IHN0YXJ0LCBzdGFydCA9IDAsIDEpIDogbiA8IDMgPyAxIDogK3N0ZXA7CgogICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgbiA9IE1hdGgubWF4KDAsIE1hdGguY2VpbCgoc3RvcCAtIHN0YXJ0KSAvIHN0ZXApKSB8IDAsCiAgICAgICAgICByYW5nZSA9IG5ldyBBcnJheShuKTsKCiAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgcmFuZ2VbaV0gPSBzdGFydCArIGkgKiBzdGVwOwogICAgICB9CgogICAgICByZXR1cm4gcmFuZ2U7CiAgICB9CgogICAgdmFyIGUxMCQyID0gTWF0aC5zcXJ0KDUwKSwKICAgICAgICBlNSQyID0gTWF0aC5zcXJ0KDEwKSwKICAgICAgICBlMiQyID0gTWF0aC5zcXJ0KDIpOwoKICAgIGZ1bmN0aW9uIHRpY2tzJDIoc3RhcnQsIHN0b3AsIGNvdW50KSB7CiAgICAgIHZhciByZXZlcnNlLAogICAgICAgICAgaSA9IC0xLAogICAgICAgICAgbiwKICAgICAgICAgIHRpY2tzLAogICAgICAgICAgc3RlcDsKCiAgICAgIHN0b3AgPSArc3RvcCwgc3RhcnQgPSArc3RhcnQsIGNvdW50ID0gK2NvdW50OwogICAgICBpZiAoc3RhcnQgPT09IHN0b3AgJiYgY291bnQgPiAwKSByZXR1cm4gW3N0YXJ0XTsKICAgICAgaWYgKHJldmVyc2UgPSBzdG9wIDwgc3RhcnQpIG4gPSBzdGFydCwgc3RhcnQgPSBzdG9wLCBzdG9wID0gbjsKICAgICAgaWYgKChzdGVwID0gdGlja0luY3JlbWVudCQyKHN0YXJ0LCBzdG9wLCBjb3VudCkpID09PSAwIHx8ICFpc0Zpbml0ZShzdGVwKSkgcmV0dXJuIFtdOwoKICAgICAgaWYgKHN0ZXAgPiAwKSB7CiAgICAgICAgc3RhcnQgPSBNYXRoLmNlaWwoc3RhcnQgLyBzdGVwKTsKICAgICAgICBzdG9wID0gTWF0aC5mbG9vcihzdG9wIC8gc3RlcCk7CiAgICAgICAgdGlja3MgPSBuZXcgQXJyYXkobiA9IE1hdGguY2VpbChzdG9wIC0gc3RhcnQgKyAxKSk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHRpY2tzW2ldID0gKHN0YXJ0ICsgaSkgKiBzdGVwOwogICAgICB9IGVsc2UgewogICAgICAgIHN0YXJ0ID0gTWF0aC5mbG9vcihzdGFydCAqIHN0ZXApOwogICAgICAgIHN0b3AgPSBNYXRoLmNlaWwoc3RvcCAqIHN0ZXApOwogICAgICAgIHRpY2tzID0gbmV3IEFycmF5KG4gPSBNYXRoLmNlaWwoc3RhcnQgLSBzdG9wICsgMSkpOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSB0aWNrc1tpXSA9IChzdGFydCAtIGkpIC8gc3RlcDsKICAgICAgfQoKICAgICAgaWYgKHJldmVyc2UpIHRpY2tzLnJldmVyc2UoKTsKCiAgICAgIHJldHVybiB0aWNrczsKICAgIH0KCiAgICBmdW5jdGlvbiB0aWNrSW5jcmVtZW50JDIoc3RhcnQsIHN0b3AsIGNvdW50KSB7CiAgICAgIHZhciBzdGVwID0gKHN0b3AgLSBzdGFydCkgLyBNYXRoLm1heCgwLCBjb3VudCksCiAgICAgICAgICBwb3dlciA9IE1hdGguZmxvb3IoTWF0aC5sb2coc3RlcCkgLyBNYXRoLkxOMTApLAogICAgICAgICAgZXJyb3IgPSBzdGVwIC8gTWF0aC5wb3coMTAsIHBvd2VyKTsKICAgICAgcmV0dXJuIHBvd2VyID49IDAKICAgICAgICAgID8gKGVycm9yID49IGUxMCQyID8gMTAgOiBlcnJvciA+PSBlNSQyID8gNSA6IGVycm9yID49IGUyJDIgPyAyIDogMSkgKiBNYXRoLnBvdygxMCwgcG93ZXIpCiAgICAgICAgICA6IC1NYXRoLnBvdygxMCwgLXBvd2VyKSAvIChlcnJvciA+PSBlMTAkMiA/IDEwIDogZXJyb3IgPj0gZTUkMiA/IDUgOiBlcnJvciA+PSBlMiQyID8gMiA6IDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRpY2tTdGVwJDIoc3RhcnQsIHN0b3AsIGNvdW50KSB7CiAgICAgIHZhciBzdGVwMCA9IE1hdGguYWJzKHN0b3AgLSBzdGFydCkgLyBNYXRoLm1heCgwLCBjb3VudCksCiAgICAgICAgICBzdGVwMSA9IE1hdGgucG93KDEwLCBNYXRoLmZsb29yKE1hdGgubG9nKHN0ZXAwKSAvIE1hdGguTE4xMCkpLAogICAgICAgICAgZXJyb3IgPSBzdGVwMCAvIHN0ZXAxOwogICAgICBpZiAoZXJyb3IgPj0gZTEwJDIpIHN0ZXAxICo9IDEwOwogICAgICBlbHNlIGlmIChlcnJvciA+PSBlNSQyKSBzdGVwMSAqPSA1OwogICAgICBlbHNlIGlmIChlcnJvciA+PSBlMiQyKSBzdGVwMSAqPSAyOwogICAgICByZXR1cm4gc3RvcCA8IHN0YXJ0ID8gLXN0ZXAxIDogc3RlcDE7CiAgICB9CgogICAgZnVuY3Rpb24gdGhyZXNob2xkJDIodmFsdWVzLCBwLCB2YWx1ZW9mKSB7CiAgICAgIGlmICh2YWx1ZW9mID09IG51bGwpIHZhbHVlb2YgPSBudW1iZXIkNzsKICAgICAgaWYgKCEobiA9IHZhbHVlcy5sZW5ndGgpKSByZXR1cm47CiAgICAgIGlmICgocCA9ICtwKSA8PSAwIHx8IG4gPCAyKSByZXR1cm4gK3ZhbHVlb2YodmFsdWVzWzBdLCAwLCB2YWx1ZXMpOwogICAgICBpZiAocCA+PSAxKSByZXR1cm4gK3ZhbHVlb2YodmFsdWVzW24gLSAxXSwgbiAtIDEsIHZhbHVlcyk7CiAgICAgIHZhciBuLAogICAgICAgICAgaSA9IChuIC0gMSkgKiBwLAogICAgICAgICAgaTAgPSBNYXRoLmZsb29yKGkpLAogICAgICAgICAgdmFsdWUwID0gK3ZhbHVlb2YodmFsdWVzW2kwXSwgaTAsIHZhbHVlcyksCiAgICAgICAgICB2YWx1ZTEgPSArdmFsdWVvZih2YWx1ZXNbaTAgKyAxXSwgaTAgKyAxLCB2YWx1ZXMpOwogICAgICByZXR1cm4gdmFsdWUwICsgKHZhbHVlMSAtIHZhbHVlMCkgKiAoaSAtIGkwKTsKICAgIH0KCiAgICB2YXIgcHJlZml4JDMgPSAiJCI7CgogICAgZnVuY3Rpb24gTWFwJDQoKSB7fQoKICAgIE1hcCQ0LnByb3RvdHlwZSA9IG1hcCQ3LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IE1hcCQ0LAogICAgICBoYXM6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHJldHVybiAocHJlZml4JDMgKyBrZXkpIGluIHRoaXM7CiAgICAgIH0sCiAgICAgIGdldDogZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgcmV0dXJuIHRoaXNbcHJlZml4JDMgKyBrZXldOwogICAgICB9LAogICAgICBzZXQ6IGZ1bmN0aW9uKGtleSwgdmFsdWUpIHsKICAgICAgICB0aGlzW3ByZWZpeCQzICsga2V5XSA9IHZhbHVlOwogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICByZW1vdmU6IGZ1bmN0aW9uKGtleSkgewogICAgICAgIHZhciBwcm9wZXJ0eSA9IHByZWZpeCQzICsga2V5OwogICAgICAgIHJldHVybiBwcm9wZXJ0eSBpbiB0aGlzICYmIGRlbGV0ZSB0aGlzW3Byb3BlcnR5XTsKICAgICAgfSwKICAgICAgY2xlYXI6IGZ1bmN0aW9uKCkgewogICAgICAgIGZvciAodmFyIHByb3BlcnR5IGluIHRoaXMpIGlmIChwcm9wZXJ0eVswXSA9PT0gcHJlZml4JDMpIGRlbGV0ZSB0aGlzW3Byb3BlcnR5XTsKICAgICAgfSwKICAgICAga2V5czogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGtleXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQzKSBrZXlzLnB1c2gocHJvcGVydHkuc2xpY2UoMSkpOwogICAgICAgIHJldHVybiBrZXlzOwogICAgICB9LAogICAgICB2YWx1ZXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQzKSB2YWx1ZXMucHVzaCh0aGlzW3Byb3BlcnR5XSk7CiAgICAgICAgcmV0dXJuIHZhbHVlczsKICAgICAgfSwKICAgICAgZW50cmllczogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGVudHJpZXMgPSBbXTsKICAgICAgICBmb3IgKHZhciBwcm9wZXJ0eSBpbiB0aGlzKSBpZiAocHJvcGVydHlbMF0gPT09IHByZWZpeCQzKSBlbnRyaWVzLnB1c2goe2tleTogcHJvcGVydHkuc2xpY2UoMSksIHZhbHVlOiB0aGlzW3Byb3BlcnR5XX0pOwogICAgICAgIHJldHVybiBlbnRyaWVzOwogICAgICB9LAogICAgICBzaXplOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMykgKytzaXplOwogICAgICAgIHJldHVybiBzaXplOwogICAgICB9LAogICAgICBlbXB0eTogZnVuY3Rpb24oKSB7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMykgcmV0dXJuIGZhbHNlOwogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9LAogICAgICBlYWNoOiBmdW5jdGlvbihmKSB7CiAgICAgICAgZm9yICh2YXIgcHJvcGVydHkgaW4gdGhpcykgaWYgKHByb3BlcnR5WzBdID09PSBwcmVmaXgkMykgZih0aGlzW3Byb3BlcnR5XSwgcHJvcGVydHkuc2xpY2UoMSksIHRoaXMpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIG1hcCQ3KG9iamVjdCwgZikgewogICAgICB2YXIgbWFwID0gbmV3IE1hcCQ0OwoKICAgICAgLy8gQ29weSBjb25zdHJ1Y3Rvci4KICAgICAgaWYgKG9iamVjdCBpbnN0YW5jZW9mIE1hcCQ0KSBvYmplY3QuZWFjaChmdW5jdGlvbih2YWx1ZSwga2V5KSB7IG1hcC5zZXQoa2V5LCB2YWx1ZSk7IH0pOwoKICAgICAgLy8gSW5kZXggYXJyYXkgYnkgbnVtZXJpYyBpbmRleCBvciBzcGVjaWZpZWQga2V5IGZ1bmN0aW9uLgogICAgICBlbHNlIGlmIChBcnJheS5pc0FycmF5KG9iamVjdCkpIHsKICAgICAgICB2YXIgaSA9IC0xLAogICAgICAgICAgICBuID0gb2JqZWN0Lmxlbmd0aCwKICAgICAgICAgICAgbzsKCiAgICAgICAgaWYgKGYgPT0gbnVsbCkgd2hpbGUgKCsraSA8IG4pIG1hcC5zZXQoaSwgb2JqZWN0W2ldKTsKICAgICAgICBlbHNlIHdoaWxlICgrK2kgPCBuKSBtYXAuc2V0KGYobyA9IG9iamVjdFtpXSwgaSwgb2JqZWN0KSwgbyk7CiAgICAgIH0KCiAgICAgIC8vIENvbnZlcnQgb2JqZWN0IHRvIG1hcC4KICAgICAgZWxzZSBpZiAob2JqZWN0KSBmb3IgKHZhciBrZXkgaW4gb2JqZWN0KSBtYXAuc2V0KGtleSwgb2JqZWN0W2tleV0pOwoKICAgICAgcmV0dXJuIG1hcDsKICAgIH0KCiAgICBmdW5jdGlvbiBTZXQkNCgpIHt9CgogICAgdmFyIHByb3RvJDQgPSBtYXAkNy5wcm90b3R5cGU7CgogICAgU2V0JDQucHJvdG90eXBlID0gc2V0JGIucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogU2V0JDQsCiAgICAgIGhhczogcHJvdG8kNC5oYXMsCiAgICAgIGFkZDogZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICB2YWx1ZSArPSAiIjsKICAgICAgICB0aGlzW3ByZWZpeCQzICsgdmFsdWVdID0gdmFsdWU7CiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIHJlbW92ZTogcHJvdG8kNC5yZW1vdmUsCiAgICAgIGNsZWFyOiBwcm90byQ0LmNsZWFyLAogICAgICB2YWx1ZXM6IHByb3RvJDQua2V5cywKICAgICAgc2l6ZTogcHJvdG8kNC5zaXplLAogICAgICBlbXB0eTogcHJvdG8kNC5lbXB0eSwKICAgICAgZWFjaDogcHJvdG8kNC5lYWNoCiAgICB9OwoKICAgIGZ1bmN0aW9uIHNldCRiKG9iamVjdCwgZikgewogICAgICB2YXIgc2V0ID0gbmV3IFNldCQ0OwoKICAgICAgLy8gQ29weSBjb25zdHJ1Y3Rvci4KICAgICAgaWYgKG9iamVjdCBpbnN0YW5jZW9mIFNldCQ0KSBvYmplY3QuZWFjaChmdW5jdGlvbih2YWx1ZSkgeyBzZXQuYWRkKHZhbHVlKTsgfSk7CgogICAgICAvLyBPdGhlcndpc2UsIGFzc3VtZSBpdOKAmXMgYW4gYXJyYXkuCiAgICAgIGVsc2UgaWYgKG9iamVjdCkgewogICAgICAgIHZhciBpID0gLTEsIG4gPSBvYmplY3QubGVuZ3RoOwogICAgICAgIGlmIChmID09IG51bGwpIHdoaWxlICgrK2kgPCBuKSBzZXQuYWRkKG9iamVjdFtpXSk7CiAgICAgICAgZWxzZSB3aGlsZSAoKytpIDwgbikgc2V0LmFkZChmKG9iamVjdFtpXSwgaSwgb2JqZWN0KSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBzZXQ7CiAgICB9CgogICAgdmFyIGFycmF5JDYgPSBBcnJheS5wcm90b3R5cGU7CgogICAgdmFyIG1hcCQ4ID0gYXJyYXkkNi5tYXA7CiAgICB2YXIgc2xpY2UkYyA9IGFycmF5JDYuc2xpY2U7CgogICAgdmFyIGltcGxpY2l0JDEgPSB7bmFtZTogImltcGxpY2l0In07CgogICAgZnVuY3Rpb24gb3JkaW5hbCQxKHJhbmdlKSB7CiAgICAgIHZhciBpbmRleCA9IG1hcCQ3KCksCiAgICAgICAgICBkb21haW4gPSBbXSwKICAgICAgICAgIHVua25vd24gPSBpbXBsaWNpdCQxOwoKICAgICAgcmFuZ2UgPSByYW5nZSA9PSBudWxsID8gW10gOiBzbGljZSRjLmNhbGwocmFuZ2UpOwoKICAgICAgZnVuY3Rpb24gc2NhbGUoZCkgewogICAgICAgIHZhciBrZXkgPSBkICsgIiIsIGkgPSBpbmRleC5nZXQoa2V5KTsKICAgICAgICBpZiAoIWkpIHsKICAgICAgICAgIGlmICh1bmtub3duICE9PSBpbXBsaWNpdCQxKSByZXR1cm4gdW5rbm93bjsKICAgICAgICAgIGluZGV4LnNldChrZXksIGkgPSBkb21haW4ucHVzaChkKSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByYW5nZVsoaSAtIDEpICUgcmFuZ2UubGVuZ3RoXTsKICAgICAgfQoKICAgICAgc2NhbGUuZG9tYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIGlmICghYXJndW1lbnRzLmxlbmd0aCkgcmV0dXJuIGRvbWFpbi5zbGljZSgpOwogICAgICAgIGRvbWFpbiA9IFtdLCBpbmRleCA9IG1hcCQ3KCk7CiAgICAgICAgdmFyIGkgPSAtMSwgbiA9IF8ubGVuZ3RoLCBkLCBrZXk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICghaW5kZXguaGFzKGtleSA9IChkID0gX1tpXSkgKyAiIikpIGluZGV4LnNldChrZXksIGRvbWFpbi5wdXNoKGQpKTsKICAgICAgICByZXR1cm4gc2NhbGU7CiAgICAgIH07CgogICAgICBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYW5nZSA9IHNsaWNlJGMuY2FsbChfKSwgc2NhbGUpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnVua25vd24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodW5rbm93biA9IF8sIHNjYWxlKSA6IHVua25vd247CiAgICAgIH07CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIG9yZGluYWwkMSgpCiAgICAgICAgICAgIC5kb21haW4oZG9tYWluKQogICAgICAgICAgICAucmFuZ2UocmFuZ2UpCiAgICAgICAgICAgIC51bmtub3duKHVua25vd24pOwogICAgICB9OwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGJhbmQkMSgpIHsKICAgICAgdmFyIHNjYWxlID0gb3JkaW5hbCQxKCkudW5rbm93bih1bmRlZmluZWQpLAogICAgICAgICAgZG9tYWluID0gc2NhbGUuZG9tYWluLAogICAgICAgICAgb3JkaW5hbFJhbmdlID0gc2NhbGUucmFuZ2UsCiAgICAgICAgICByYW5nZSA9IFswLCAxXSwKICAgICAgICAgIHN0ZXAsCiAgICAgICAgICBiYW5kd2lkdGgsCiAgICAgICAgICByb3VuZCA9IGZhbHNlLAogICAgICAgICAgcGFkZGluZ0lubmVyID0gMCwKICAgICAgICAgIHBhZGRpbmdPdXRlciA9IDAsCiAgICAgICAgICBhbGlnbiA9IDAuNTsKCiAgICAgIGRlbGV0ZSBzY2FsZS51bmtub3duOwoKICAgICAgZnVuY3Rpb24gcmVzY2FsZSgpIHsKICAgICAgICB2YXIgbiA9IGRvbWFpbigpLmxlbmd0aCwKICAgICAgICAgICAgcmV2ZXJzZSA9IHJhbmdlWzFdIDwgcmFuZ2VbMF0sCiAgICAgICAgICAgIHN0YXJ0ID0gcmFuZ2VbcmV2ZXJzZSAtIDBdLAogICAgICAgICAgICBzdG9wID0gcmFuZ2VbMSAtIHJldmVyc2VdOwogICAgICAgIHN0ZXAgPSAoc3RvcCAtIHN0YXJ0KSAvIE1hdGgubWF4KDEsIG4gLSBwYWRkaW5nSW5uZXIgKyBwYWRkaW5nT3V0ZXIgKiAyKTsKICAgICAgICBpZiAocm91bmQpIHN0ZXAgPSBNYXRoLmZsb29yKHN0ZXApOwogICAgICAgIHN0YXJ0ICs9IChzdG9wIC0gc3RhcnQgLSBzdGVwICogKG4gLSBwYWRkaW5nSW5uZXIpKSAqIGFsaWduOwogICAgICAgIGJhbmR3aWR0aCA9IHN0ZXAgKiAoMSAtIHBhZGRpbmdJbm5lcik7CiAgICAgICAgaWYgKHJvdW5kKSBzdGFydCA9IE1hdGgucm91bmQoc3RhcnQpLCBiYW5kd2lkdGggPSBNYXRoLnJvdW5kKGJhbmR3aWR0aCk7CiAgICAgICAgdmFyIHZhbHVlcyA9IHNlcXVlbmNlJDEobikubWFwKGZ1bmN0aW9uKGkpIHsgcmV0dXJuIHN0YXJ0ICsgc3RlcCAqIGk7IH0pOwogICAgICAgIHJldHVybiBvcmRpbmFsUmFuZ2UocmV2ZXJzZSA/IHZhbHVlcy5yZXZlcnNlKCkgOiB2YWx1ZXMpOwogICAgICB9CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluKF8pLCByZXNjYWxlKCkpIDogZG9tYWluKCk7CiAgICAgIH07CgogICAgICBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYW5nZSA9IFsrX1swXSwgK19bMV1dLCByZXNjYWxlKCkpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlUm91bmQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIHJhbmdlID0gWytfWzBdLCArX1sxXV0sIHJvdW5kID0gdHJ1ZSwgcmVzY2FsZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUuYmFuZHdpZHRoID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGJhbmR3aWR0aDsKICAgICAgfTsKCiAgICAgIHNjYWxlLnN0ZXAgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gc3RlcDsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJvdW5kID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJvdW5kID0gISFfLCByZXNjYWxlKCkpIDogcm91bmQ7CiAgICAgIH07CgogICAgICBzY2FsZS5wYWRkaW5nID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZGRpbmdJbm5lciA9IHBhZGRpbmdPdXRlciA9IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIF8pKSwgcmVzY2FsZSgpKSA6IHBhZGRpbmdJbm5lcjsKICAgICAgfTsKCiAgICAgIHNjYWxlLnBhZGRpbmdJbm5lciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRkaW5nSW5uZXIgPSBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBfKSksIHJlc2NhbGUoKSkgOiBwYWRkaW5nSW5uZXI7CiAgICAgIH07CgogICAgICBzY2FsZS5wYWRkaW5nT3V0ZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocGFkZGluZ091dGVyID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgXykpLCByZXNjYWxlKCkpIDogcGFkZGluZ091dGVyOwogICAgICB9OwoKICAgICAgc2NhbGUuYWxpZ24gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoYWxpZ24gPSBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBfKSksIHJlc2NhbGUoKSkgOiBhbGlnbjsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYmFuZCQxKCkKICAgICAgICAgICAgLmRvbWFpbihkb21haW4oKSkKICAgICAgICAgICAgLnJhbmdlKHJhbmdlKQogICAgICAgICAgICAucm91bmQocm91bmQpCiAgICAgICAgICAgIC5wYWRkaW5nSW5uZXIocGFkZGluZ0lubmVyKQogICAgICAgICAgICAucGFkZGluZ091dGVyKHBhZGRpbmdPdXRlcikKICAgICAgICAgICAgLmFsaWduKGFsaWduKTsKICAgICAgfTsKCiAgICAgIHJldHVybiByZXNjYWxlKCk7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnRpc2gkMShzY2FsZSkgewogICAgICB2YXIgY29weSA9IHNjYWxlLmNvcHk7CgogICAgICBzY2FsZS5wYWRkaW5nID0gc2NhbGUucGFkZGluZ091dGVyOwogICAgICBkZWxldGUgc2NhbGUucGFkZGluZ0lubmVyOwogICAgICBkZWxldGUgc2NhbGUucGFkZGluZ091dGVyOwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBwb2ludGlzaCQxKGNvcHkoKSk7CiAgICAgIH07CgogICAgICByZXR1cm4gc2NhbGU7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnQkOCgpIHsKICAgICAgcmV0dXJuIHBvaW50aXNoJDEoYmFuZCQxKCkucGFkZGluZ0lubmVyKDEpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZpbmUkNChjb25zdHJ1Y3RvciwgZmFjdG9yeSwgcHJvdG90eXBlKSB7CiAgICAgIGNvbnN0cnVjdG9yLnByb3RvdHlwZSA9IGZhY3RvcnkucHJvdG90eXBlID0gcHJvdG90eXBlOwogICAgICBwcm90b3R5cGUuY29uc3RydWN0b3IgPSBjb25zdHJ1Y3RvcjsKICAgIH0KCiAgICBmdW5jdGlvbiBleHRlbmQkNChwYXJlbnQsIGRlZmluaXRpb24pIHsKICAgICAgdmFyIHByb3RvdHlwZSA9IE9iamVjdC5jcmVhdGUocGFyZW50LnByb3RvdHlwZSk7CiAgICAgIGZvciAodmFyIGtleSBpbiBkZWZpbml0aW9uKSBwcm90b3R5cGVba2V5XSA9IGRlZmluaXRpb25ba2V5XTsKICAgICAgcmV0dXJuIHByb3RvdHlwZTsKICAgIH0KCiAgICBmdW5jdGlvbiBDb2xvciQ0KCkge30KCiAgICB2YXIgZGFya2VyJDQgPSAwLjc7CiAgICB2YXIgYnJpZ2h0ZXIkNCA9IDEgLyBkYXJrZXIkNDsKCiAgICB2YXIgcmVJJDQgPSAiXFxzKihbKy1dP1xcZCspXFxzKiIsCiAgICAgICAgcmVOJDQgPSAiXFxzKihbKy1dP1xcZCpcXC4/XFxkKyg/OltlRV1bKy1dP1xcZCspPylcXHMqIiwKICAgICAgICByZVAkNCA9ICJcXHMqKFsrLV0/XFxkKlxcLj9cXGQrKD86W2VFXVsrLV0/XFxkKyk/KSVcXHMqIiwKICAgICAgICByZUhleCQzID0gL14jKFswLTlhLWZdezMsOH0pJC8sCiAgICAgICAgcmVSZ2JJbnRlZ2VyJDQgPSBuZXcgUmVnRXhwKCJecmdiXFwoIiArIFtyZUkkNCwgcmVJJDQsIHJlSSQ0XSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JQZXJjZW50JDQgPSBuZXcgUmVnRXhwKCJecmdiXFwoIiArIFtyZVAkNCwgcmVQJDQsIHJlUCQ0XSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JhSW50ZWdlciQ0ID0gbmV3IFJlZ0V4cCgiXnJnYmFcXCgiICsgW3JlSSQ0LCByZUkkNCwgcmVJJDQsIHJlTiQ0XSArICJcXCkkIiksCiAgICAgICAgcmVSZ2JhUGVyY2VudCQ0ID0gbmV3IFJlZ0V4cCgiXnJnYmFcXCgiICsgW3JlUCQ0LCByZVAkNCwgcmVQJDQsIHJlTiQ0XSArICJcXCkkIiksCiAgICAgICAgcmVIc2xQZXJjZW50JDQgPSBuZXcgUmVnRXhwKCJeaHNsXFwoIiArIFtyZU4kNCwgcmVQJDQsIHJlUCQ0XSArICJcXCkkIiksCiAgICAgICAgcmVIc2xhUGVyY2VudCQ0ID0gbmV3IFJlZ0V4cCgiXmhzbGFcXCgiICsgW3JlTiQ0LCByZVAkNCwgcmVQJDQsIHJlTiQ0XSArICJcXCkkIik7CgogICAgdmFyIG5hbWVkJDQgPSB7CiAgICAgIGFsaWNlYmx1ZTogMHhmMGY4ZmYsCiAgICAgIGFudGlxdWV3aGl0ZTogMHhmYWViZDcsCiAgICAgIGFxdWE6IDB4MDBmZmZmLAogICAgICBhcXVhbWFyaW5lOiAweDdmZmZkNCwKICAgICAgYXp1cmU6IDB4ZjBmZmZmLAogICAgICBiZWlnZTogMHhmNWY1ZGMsCiAgICAgIGJpc3F1ZTogMHhmZmU0YzQsCiAgICAgIGJsYWNrOiAweDAwMDAwMCwKICAgICAgYmxhbmNoZWRhbG1vbmQ6IDB4ZmZlYmNkLAogICAgICBibHVlOiAweDAwMDBmZiwKICAgICAgYmx1ZXZpb2xldDogMHg4YTJiZTIsCiAgICAgIGJyb3duOiAweGE1MmEyYSwKICAgICAgYnVybHl3b29kOiAweGRlYjg4NywKICAgICAgY2FkZXRibHVlOiAweDVmOWVhMCwKICAgICAgY2hhcnRyZXVzZTogMHg3ZmZmMDAsCiAgICAgIGNob2NvbGF0ZTogMHhkMjY5MWUsCiAgICAgIGNvcmFsOiAweGZmN2Y1MCwKICAgICAgY29ybmZsb3dlcmJsdWU6IDB4NjQ5NWVkLAogICAgICBjb3Juc2lsazogMHhmZmY4ZGMsCiAgICAgIGNyaW1zb246IDB4ZGMxNDNjLAogICAgICBjeWFuOiAweDAwZmZmZiwKICAgICAgZGFya2JsdWU6IDB4MDAwMDhiLAogICAgICBkYXJrY3lhbjogMHgwMDhiOGIsCiAgICAgIGRhcmtnb2xkZW5yb2Q6IDB4Yjg4NjBiLAogICAgICBkYXJrZ3JheTogMHhhOWE5YTksCiAgICAgIGRhcmtncmVlbjogMHgwMDY0MDAsCiAgICAgIGRhcmtncmV5OiAweGE5YTlhOSwKICAgICAgZGFya2toYWtpOiAweGJkYjc2YiwKICAgICAgZGFya21hZ2VudGE6IDB4OGIwMDhiLAogICAgICBkYXJrb2xpdmVncmVlbjogMHg1NTZiMmYsCiAgICAgIGRhcmtvcmFuZ2U6IDB4ZmY4YzAwLAogICAgICBkYXJrb3JjaGlkOiAweDk5MzJjYywKICAgICAgZGFya3JlZDogMHg4YjAwMDAsCiAgICAgIGRhcmtzYWxtb246IDB4ZTk5NjdhLAogICAgICBkYXJrc2VhZ3JlZW46IDB4OGZiYzhmLAogICAgICBkYXJrc2xhdGVibHVlOiAweDQ4M2Q4YiwKICAgICAgZGFya3NsYXRlZ3JheTogMHgyZjRmNGYsCiAgICAgIGRhcmtzbGF0ZWdyZXk6IDB4MmY0ZjRmLAogICAgICBkYXJrdHVycXVvaXNlOiAweDAwY2VkMSwKICAgICAgZGFya3Zpb2xldDogMHg5NDAwZDMsCiAgICAgIGRlZXBwaW5rOiAweGZmMTQ5MywKICAgICAgZGVlcHNreWJsdWU6IDB4MDBiZmZmLAogICAgICBkaW1ncmF5OiAweDY5Njk2OSwKICAgICAgZGltZ3JleTogMHg2OTY5NjksCiAgICAgIGRvZGdlcmJsdWU6IDB4MWU5MGZmLAogICAgICBmaXJlYnJpY2s6IDB4YjIyMjIyLAogICAgICBmbG9yYWx3aGl0ZTogMHhmZmZhZjAsCiAgICAgIGZvcmVzdGdyZWVuOiAweDIyOGIyMiwKICAgICAgZnVjaHNpYTogMHhmZjAwZmYsCiAgICAgIGdhaW5zYm9ybzogMHhkY2RjZGMsCiAgICAgIGdob3N0d2hpdGU6IDB4ZjhmOGZmLAogICAgICBnb2xkOiAweGZmZDcwMCwKICAgICAgZ29sZGVucm9kOiAweGRhYTUyMCwKICAgICAgZ3JheTogMHg4MDgwODAsCiAgICAgIGdyZWVuOiAweDAwODAwMCwKICAgICAgZ3JlZW55ZWxsb3c6IDB4YWRmZjJmLAogICAgICBncmV5OiAweDgwODA4MCwKICAgICAgaG9uZXlkZXc6IDB4ZjBmZmYwLAogICAgICBob3RwaW5rOiAweGZmNjliNCwKICAgICAgaW5kaWFucmVkOiAweGNkNWM1YywKICAgICAgaW5kaWdvOiAweDRiMDA4MiwKICAgICAgaXZvcnk6IDB4ZmZmZmYwLAogICAgICBraGFraTogMHhmMGU2OGMsCiAgICAgIGxhdmVuZGVyOiAweGU2ZTZmYSwKICAgICAgbGF2ZW5kZXJibHVzaDogMHhmZmYwZjUsCiAgICAgIGxhd25ncmVlbjogMHg3Y2ZjMDAsCiAgICAgIGxlbW9uY2hpZmZvbjogMHhmZmZhY2QsCiAgICAgIGxpZ2h0Ymx1ZTogMHhhZGQ4ZTYsCiAgICAgIGxpZ2h0Y29yYWw6IDB4ZjA4MDgwLAogICAgICBsaWdodGN5YW46IDB4ZTBmZmZmLAogICAgICBsaWdodGdvbGRlbnJvZHllbGxvdzogMHhmYWZhZDIsCiAgICAgIGxpZ2h0Z3JheTogMHhkM2QzZDMsCiAgICAgIGxpZ2h0Z3JlZW46IDB4OTBlZTkwLAogICAgICBsaWdodGdyZXk6IDB4ZDNkM2QzLAogICAgICBsaWdodHBpbms6IDB4ZmZiNmMxLAogICAgICBsaWdodHNhbG1vbjogMHhmZmEwN2EsCiAgICAgIGxpZ2h0c2VhZ3JlZW46IDB4MjBiMmFhLAogICAgICBsaWdodHNreWJsdWU6IDB4ODdjZWZhLAogICAgICBsaWdodHNsYXRlZ3JheTogMHg3Nzg4OTksCiAgICAgIGxpZ2h0c2xhdGVncmV5OiAweDc3ODg5OSwKICAgICAgbGlnaHRzdGVlbGJsdWU6IDB4YjBjNGRlLAogICAgICBsaWdodHllbGxvdzogMHhmZmZmZTAsCiAgICAgIGxpbWU6IDB4MDBmZjAwLAogICAgICBsaW1lZ3JlZW46IDB4MzJjZDMyLAogICAgICBsaW5lbjogMHhmYWYwZTYsCiAgICAgIG1hZ2VudGE6IDB4ZmYwMGZmLAogICAgICBtYXJvb246IDB4ODAwMDAwLAogICAgICBtZWRpdW1hcXVhbWFyaW5lOiAweDY2Y2RhYSwKICAgICAgbWVkaXVtYmx1ZTogMHgwMDAwY2QsCiAgICAgIG1lZGl1bW9yY2hpZDogMHhiYTU1ZDMsCiAgICAgIG1lZGl1bXB1cnBsZTogMHg5MzcwZGIsCiAgICAgIG1lZGl1bXNlYWdyZWVuOiAweDNjYjM3MSwKICAgICAgbWVkaXVtc2xhdGVibHVlOiAweDdiNjhlZSwKICAgICAgbWVkaXVtc3ByaW5nZ3JlZW46IDB4MDBmYTlhLAogICAgICBtZWRpdW10dXJxdW9pc2U6IDB4NDhkMWNjLAogICAgICBtZWRpdW12aW9sZXRyZWQ6IDB4YzcxNTg1LAogICAgICBtaWRuaWdodGJsdWU6IDB4MTkxOTcwLAogICAgICBtaW50Y3JlYW06IDB4ZjVmZmZhLAogICAgICBtaXN0eXJvc2U6IDB4ZmZlNGUxLAogICAgICBtb2NjYXNpbjogMHhmZmU0YjUsCiAgICAgIG5hdmFqb3doaXRlOiAweGZmZGVhZCwKICAgICAgbmF2eTogMHgwMDAwODAsCiAgICAgIG9sZGxhY2U6IDB4ZmRmNWU2LAogICAgICBvbGl2ZTogMHg4MDgwMDAsCiAgICAgIG9saXZlZHJhYjogMHg2YjhlMjMsCiAgICAgIG9yYW5nZTogMHhmZmE1MDAsCiAgICAgIG9yYW5nZXJlZDogMHhmZjQ1MDAsCiAgICAgIG9yY2hpZDogMHhkYTcwZDYsCiAgICAgIHBhbGVnb2xkZW5yb2Q6IDB4ZWVlOGFhLAogICAgICBwYWxlZ3JlZW46IDB4OThmYjk4LAogICAgICBwYWxldHVycXVvaXNlOiAweGFmZWVlZSwKICAgICAgcGFsZXZpb2xldHJlZDogMHhkYjcwOTMsCiAgICAgIHBhcGF5YXdoaXA6IDB4ZmZlZmQ1LAogICAgICBwZWFjaHB1ZmY6IDB4ZmZkYWI5LAogICAgICBwZXJ1OiAweGNkODUzZiwKICAgICAgcGluazogMHhmZmMwY2IsCiAgICAgIHBsdW06IDB4ZGRhMGRkLAogICAgICBwb3dkZXJibHVlOiAweGIwZTBlNiwKICAgICAgcHVycGxlOiAweDgwMDA4MCwKICAgICAgcmViZWNjYXB1cnBsZTogMHg2NjMzOTksCiAgICAgIHJlZDogMHhmZjAwMDAsCiAgICAgIHJvc3licm93bjogMHhiYzhmOGYsCiAgICAgIHJveWFsYmx1ZTogMHg0MTY5ZTEsCiAgICAgIHNhZGRsZWJyb3duOiAweDhiNDUxMywKICAgICAgc2FsbW9uOiAweGZhODA3MiwKICAgICAgc2FuZHlicm93bjogMHhmNGE0NjAsCiAgICAgIHNlYWdyZWVuOiAweDJlOGI1NywKICAgICAgc2Vhc2hlbGw6IDB4ZmZmNWVlLAogICAgICBzaWVubmE6IDB4YTA1MjJkLAogICAgICBzaWx2ZXI6IDB4YzBjMGMwLAogICAgICBza3libHVlOiAweDg3Y2VlYiwKICAgICAgc2xhdGVibHVlOiAweDZhNWFjZCwKICAgICAgc2xhdGVncmF5OiAweDcwODA5MCwKICAgICAgc2xhdGVncmV5OiAweDcwODA5MCwKICAgICAgc25vdzogMHhmZmZhZmEsCiAgICAgIHNwcmluZ2dyZWVuOiAweDAwZmY3ZiwKICAgICAgc3RlZWxibHVlOiAweDQ2ODJiNCwKICAgICAgdGFuOiAweGQyYjQ4YywKICAgICAgdGVhbDogMHgwMDgwODAsCiAgICAgIHRoaXN0bGU6IDB4ZDhiZmQ4LAogICAgICB0b21hdG86IDB4ZmY2MzQ3LAogICAgICB0dXJxdW9pc2U6IDB4NDBlMGQwLAogICAgICB2aW9sZXQ6IDB4ZWU4MmVlLAogICAgICB3aGVhdDogMHhmNWRlYjMsCiAgICAgIHdoaXRlOiAweGZmZmZmZiwKICAgICAgd2hpdGVzbW9rZTogMHhmNWY1ZjUsCiAgICAgIHllbGxvdzogMHhmZmZmMDAsCiAgICAgIHllbGxvd2dyZWVuOiAweDlhY2QzMgogICAgfTsKCiAgICBkZWZpbmUkNChDb2xvciQ0LCBjb2xvciQ0LCB7CiAgICAgIGNvcHk6IGZ1bmN0aW9uKGNoYW5uZWxzKSB7CiAgICAgICAgcmV0dXJuIE9iamVjdC5hc3NpZ24obmV3IHRoaXMuY29uc3RydWN0b3IsIHRoaXMsIGNoYW5uZWxzKTsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnJnYigpLmRpc3BsYXlhYmxlKCk7CiAgICAgIH0sCiAgICAgIGhleDogY29sb3JfZm9ybWF0SGV4JDMsIC8vIERlcHJlY2F0ZWQhIFVzZSBjb2xvci5mb3JtYXRIZXguCiAgICAgIGZvcm1hdEhleDogY29sb3JfZm9ybWF0SGV4JDMsCiAgICAgIGZvcm1hdEhzbDogY29sb3JfZm9ybWF0SHNsJDMsCiAgICAgIGZvcm1hdFJnYjogY29sb3JfZm9ybWF0UmdiJDMsCiAgICAgIHRvU3RyaW5nOiBjb2xvcl9mb3JtYXRSZ2IkMwogICAgfSk7CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0SGV4JDMoKSB7CiAgICAgIHJldHVybiB0aGlzLnJnYigpLmZvcm1hdEhleCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdEhzbCQzKCkgewogICAgICByZXR1cm4gaHNsQ29udmVydCQ0KHRoaXMpLmZvcm1hdEhzbCgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdFJnYiQzKCkgewogICAgICByZXR1cm4gdGhpcy5yZ2IoKS5mb3JtYXRSZ2IoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvciQ0KGZvcm1hdCkgewogICAgICB2YXIgbSwgbDsKICAgICAgZm9ybWF0ID0gKGZvcm1hdCArICIiKS50cmltKCkudG9Mb3dlckNhc2UoKTsKICAgICAgcmV0dXJuIChtID0gcmVIZXgkMy5leGVjKGZvcm1hdCkpID8gKGwgPSBtWzFdLmxlbmd0aCwgbSA9IHBhcnNlSW50KG1bMV0sIDE2KSwgbCA9PT0gNiA/IHJnYm4kNChtKSAvLyAjZmYwMDAwCiAgICAgICAgICA6IGwgPT09IDMgPyBuZXcgUmdiJDQoKG0gPj4gOCAmIDB4ZikgfCAobSA+PiA0ICYgMHhmMCksIChtID4+IDQgJiAweGYpIHwgKG0gJiAweGYwKSwgKChtICYgMHhmKSA8PCA0KSB8IChtICYgMHhmKSwgMSkgLy8gI2YwMAogICAgICAgICAgOiBsID09PSA4ID8gcmdiYSQ0KG0gPj4gMjQgJiAweGZmLCBtID4+IDE2ICYgMHhmZiwgbSA+PiA4ICYgMHhmZiwgKG0gJiAweGZmKSAvIDB4ZmYpIC8vICNmZjAwMDAwMAogICAgICAgICAgOiBsID09PSA0ID8gcmdiYSQ0KChtID4+IDEyICYgMHhmKSB8IChtID4+IDggJiAweGYwKSwgKG0gPj4gOCAmIDB4ZikgfCAobSA+PiA0ICYgMHhmMCksIChtID4+IDQgJiAweGYpIHwgKG0gJiAweGYwKSwgKCgobSAmIDB4ZikgPDwgNCkgfCAobSAmIDB4ZikpIC8gMHhmZikgLy8gI2YwMDAKICAgICAgICAgIDogbnVsbCkgLy8gaW52YWxpZCBoZXgKICAgICAgICAgIDogKG0gPSByZVJnYkludGVnZXIkNC5leGVjKGZvcm1hdCkpID8gbmV3IFJnYiQ0KG1bMV0sIG1bMl0sIG1bM10sIDEpIC8vIHJnYigyNTUsIDAsIDApCiAgICAgICAgICA6IChtID0gcmVSZ2JQZXJjZW50JDQuZXhlYyhmb3JtYXQpKSA/IG5ldyBSZ2IkNChtWzFdICogMjU1IC8gMTAwLCBtWzJdICogMjU1IC8gMTAwLCBtWzNdICogMjU1IC8gMTAwLCAxKSAvLyByZ2IoMTAwJSwgMCUsIDAlKQogICAgICAgICAgOiAobSA9IHJlUmdiYUludGVnZXIkNC5leGVjKGZvcm1hdCkpID8gcmdiYSQ0KG1bMV0sIG1bMl0sIG1bM10sIG1bNF0pIC8vIHJnYmEoMjU1LCAwLCAwLCAxKQogICAgICAgICAgOiAobSA9IHJlUmdiYVBlcmNlbnQkNC5leGVjKGZvcm1hdCkpID8gcmdiYSQ0KG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIG1bNF0pIC8vIHJnYigxMDAlLCAwJSwgMCUsIDEpCiAgICAgICAgICA6IChtID0gcmVIc2xQZXJjZW50JDQuZXhlYyhmb3JtYXQpKSA/IGhzbGEkNChtWzFdLCBtWzJdIC8gMTAwLCBtWzNdIC8gMTAwLCAxKSAvLyBoc2woMTIwLCA1MCUsIDUwJSkKICAgICAgICAgIDogKG0gPSByZUhzbGFQZXJjZW50JDQuZXhlYyhmb3JtYXQpKSA/IGhzbGEkNChtWzFdLCBtWzJdIC8gMTAwLCBtWzNdIC8gMTAwLCBtWzRdKSAvLyBoc2xhKDEyMCwgNTAlLCA1MCUsIDEpCiAgICAgICAgICA6IG5hbWVkJDQuaGFzT3duUHJvcGVydHkoZm9ybWF0KSA/IHJnYm4kNChuYW1lZCQ0W2Zvcm1hdF0pIC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tcHJvdG90eXBlLWJ1aWx0aW5zCiAgICAgICAgICA6IGZvcm1hdCA9PT0gInRyYW5zcGFyZW50IiA/IG5ldyBSZ2IkNChOYU4sIE5hTiwgTmFOLCAwKQogICAgICAgICAgOiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYm4kNChuKSB7CiAgICAgIHJldHVybiBuZXcgUmdiJDQobiA+PiAxNiAmIDB4ZmYsIG4gPj4gOCAmIDB4ZmYsIG4gJiAweGZmLCAxKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JhJDQociwgZywgYiwgYSkgewogICAgICBpZiAoYSA8PSAwKSByID0gZyA9IGIgPSBOYU47CiAgICAgIHJldHVybiBuZXcgUmdiJDQociwgZywgYiwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiQ29udmVydCQ0KG8pIHsKICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIENvbG9yJDQpKSBvID0gY29sb3IkNChvKTsKICAgICAgaWYgKCFvKSByZXR1cm4gbmV3IFJnYiQ0OwogICAgICBvID0gby5yZ2IoKTsKICAgICAgcmV0dXJuIG5ldyBSZ2IkNChvLnIsIG8uZywgby5iLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYiQ1KHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyByZ2JDb252ZXJ0JDQocikgOiBuZXcgUmdiJDQociwgZywgYiwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIFJnYiQ0KHIsIGcsIGIsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5yID0gK3I7CiAgICAgIHRoaXMuZyA9ICtnOwogICAgICB0aGlzLmIgPSArYjsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDQoUmdiJDQsIHJnYiQ1LCBleHRlbmQkNChDb2xvciQ0LCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDQgOiBNYXRoLnBvdyhicmlnaHRlciQ0LCBrKTsKICAgICAgICByZXR1cm4gbmV3IFJnYiQ0KHRoaXMuciAqIGssIHRoaXMuZyAqIGssIHRoaXMuYiAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIkNCA6IE1hdGgucG93KGRhcmtlciQ0LCBrKTsKICAgICAgICByZXR1cm4gbmV3IFJnYiQ0KHRoaXMuciAqIGssIHRoaXMuZyAqIGssIHRoaXMuYiAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIHJnYjogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0sCiAgICAgIGRpc3BsYXlhYmxlOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gKC0wLjUgPD0gdGhpcy5yICYmIHRoaXMuciA8IDI1NS41KQogICAgICAgICAgICAmJiAoLTAuNSA8PSB0aGlzLmcgJiYgdGhpcy5nIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgtMC41IDw9IHRoaXMuYiAmJiB0aGlzLmIgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5vcGFjaXR5ICYmIHRoaXMub3BhY2l0eSA8PSAxKTsKICAgICAgfSwKICAgICAgaGV4OiByZ2JfZm9ybWF0SGV4JDMsIC8vIERlcHJlY2F0ZWQhIFVzZSBjb2xvci5mb3JtYXRIZXguCiAgICAgIGZvcm1hdEhleDogcmdiX2Zvcm1hdEhleCQzLAogICAgICBmb3JtYXRSZ2I6IHJnYl9mb3JtYXRSZ2IkMywKICAgICAgdG9TdHJpbmc6IHJnYl9mb3JtYXRSZ2IkMwogICAgfSkpOwoKICAgIGZ1bmN0aW9uIHJnYl9mb3JtYXRIZXgkMygpIHsKICAgICAgcmV0dXJuICIjIiArIGhleCQzKHRoaXMucikgKyBoZXgkMyh0aGlzLmcpICsgaGV4JDModGhpcy5iKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JfZm9ybWF0UmdiJDMoKSB7CiAgICAgIHZhciBhID0gdGhpcy5vcGFjaXR5OyBhID0gaXNOYU4oYSkgPyAxIDogTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgYSkpOwogICAgICByZXR1cm4gKGEgPT09IDEgPyAicmdiKCIgOiAicmdiYSgiKQogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5yKSB8fCAwKSkgKyAiLCAiCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLmcpIHx8IDApKSArICIsICIKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuYikgfHwgMCkpCiAgICAgICAgICArIChhID09PSAxID8gIikiIDogIiwgIiArIGEgKyAiKSIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhleCQzKHZhbHVlKSB7CiAgICAgIHZhbHVlID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHZhbHVlKSB8fCAwKSk7CiAgICAgIHJldHVybiAodmFsdWUgPCAxNiA/ICIwIiA6ICIiKSArIHZhbHVlLnRvU3RyaW5nKDE2KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xhJDQoaCwgcywgbCwgYSkgewogICAgICBpZiAoYSA8PSAwKSBoID0gcyA9IGwgPSBOYU47CiAgICAgIGVsc2UgaWYgKGwgPD0gMCB8fCBsID49IDEpIGggPSBzID0gTmFOOwogICAgICBlbHNlIGlmIChzIDw9IDApIGggPSBOYU47CiAgICAgIHJldHVybiBuZXcgSHNsJDQoaCwgcywgbCwgYSk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsQ29udmVydCQ0KG8pIHsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wkNCkgcmV0dXJuIG5ldyBIc2wkNChvLmgsIG8ucywgby5sLCBvLm9wYWNpdHkpOwogICAgICBpZiAoIShvIGluc3RhbmNlb2YgQ29sb3IkNCkpIG8gPSBjb2xvciQ0KG8pOwogICAgICBpZiAoIW8pIHJldHVybiBuZXcgSHNsJDQ7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgSHNsJDQpIHJldHVybiBvOwogICAgICBvID0gby5yZ2IoKTsKICAgICAgdmFyIHIgPSBvLnIgLyAyNTUsCiAgICAgICAgICBnID0gby5nIC8gMjU1LAogICAgICAgICAgYiA9IG8uYiAvIDI1NSwKICAgICAgICAgIG1pbiA9IE1hdGgubWluKHIsIGcsIGIpLAogICAgICAgICAgbWF4ID0gTWF0aC5tYXgociwgZywgYiksCiAgICAgICAgICBoID0gTmFOLAogICAgICAgICAgcyA9IG1heCAtIG1pbiwKICAgICAgICAgIGwgPSAobWF4ICsgbWluKSAvIDI7CiAgICAgIGlmIChzKSB7CiAgICAgICAgaWYgKHIgPT09IG1heCkgaCA9IChnIC0gYikgLyBzICsgKGcgPCBiKSAqIDY7CiAgICAgICAgZWxzZSBpZiAoZyA9PT0gbWF4KSBoID0gKGIgLSByKSAvIHMgKyAyOwogICAgICAgIGVsc2UgaCA9IChyIC0gZykgLyBzICsgNDsKICAgICAgICBzIC89IGwgPCAwLjUgPyBtYXggKyBtaW4gOiAyIC0gbWF4IC0gbWluOwogICAgICAgIGggKj0gNjA7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcyA9IGwgPiAwICYmIGwgPCAxID8gMCA6IGg7CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBIc2wkNChoLCBzLCBsLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbCQ4KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBoc2xDb252ZXJ0JDQoaCkgOiBuZXcgSHNsJDQoaCwgcywgbCwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIEhzbCQ0KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5oID0gK2g7CiAgICAgIHRoaXMucyA9ICtzOwogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDQoSHNsJDQsIGhzbCQ4LCBleHRlbmQkNChDb2xvciQ0LCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDQgOiBNYXRoLnBvdyhicmlnaHRlciQ0LCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCQ0KHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDQgOiBNYXRoLnBvdyhkYXJrZXIkNCwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBIc2wkNCh0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaCA9IHRoaXMuaCAlIDM2MCArICh0aGlzLmggPCAwKSAqIDM2MCwKICAgICAgICAgICAgcyA9IGlzTmFOKGgpIHx8IGlzTmFOKHRoaXMucykgPyAwIDogdGhpcy5zLAogICAgICAgICAgICBsID0gdGhpcy5sLAogICAgICAgICAgICBtMiA9IGwgKyAobCA8IDAuNSA/IGwgOiAxIC0gbCkgKiBzLAogICAgICAgICAgICBtMSA9IDIgKiBsIC0gbTI7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkNCgKICAgICAgICAgIGhzbDJyZ2IkNChoID49IDI0MCA/IGggLSAyNDAgOiBoICsgMTIwLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYiQ0KGgsIG0xLCBtMiksCiAgICAgICAgICBoc2wycmdiJDQoaCA8IDEyMCA/IGggKyAyNDAgOiBoIC0gMTIwLCBtMSwgbTIpLAogICAgICAgICAgdGhpcy5vcGFjaXR5CiAgICAgICAgKTsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoMCA8PSB0aGlzLnMgJiYgdGhpcy5zIDw9IDEgfHwgaXNOYU4odGhpcy5zKSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5sICYmIHRoaXMubCA8PSAxKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9LAogICAgICBmb3JtYXRIc2w6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBhID0gdGhpcy5vcGFjaXR5OyBhID0gaXNOYU4oYSkgPyAxIDogTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgYSkpOwogICAgICAgIHJldHVybiAoYSA9PT0gMSA/ICJoc2woIiA6ICJoc2xhKCIpCiAgICAgICAgICAgICsgKHRoaXMuaCB8fCAwKSArICIsICIKICAgICAgICAgICAgKyAodGhpcy5zIHx8IDApICogMTAwICsgIiUsICIKICAgICAgICAgICAgKyAodGhpcy5sIHx8IDApICogMTAwICsgIiUiCiAgICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICAgIH0KICAgIH0pKTsKCiAgICAvKiBGcm9tIEZ2RCAxMy4zNywgQ1NTIENvbG9yIE1vZHVsZSBMZXZlbCAzICovCiAgICBmdW5jdGlvbiBoc2wycmdiJDQoaCwgbTEsIG0yKSB7CiAgICAgIHJldHVybiAoaCA8IDYwID8gbTEgKyAobTIgLSBtMSkgKiBoIC8gNjAKICAgICAgICAgIDogaCA8IDE4MCA/IG0yCiAgICAgICAgICA6IGggPCAyNDAgPyBtMSArIChtMiAtIG0xKSAqICgyNDAgLSBoKSAvIDYwCiAgICAgICAgICA6IG0xKSAqIDI1NTsKICAgIH0KCiAgICB2YXIgZGVnMnJhZCQzID0gTWF0aC5QSSAvIDE4MDsKICAgIHZhciByYWQyZGVnJDMgPSAxODAgLyBNYXRoLlBJOwoKICAgIHZhciBBJDMgPSAtMC4xNDg2MSwKICAgICAgICBCJDMgPSArMS43ODI3NywKICAgICAgICBDJDMgPSAtMC4yOTIyNywKICAgICAgICBEJDMgPSAtMC45MDY0OSwKICAgICAgICBFJDMgPSArMS45NzI5NCwKICAgICAgICBFRCQzID0gRSQzICogRCQzLAogICAgICAgIEVCJDMgPSBFJDMgKiBCJDMsCiAgICAgICAgQkNfREEkMyA9IEIkMyAqIEMkMyAtIEQkMyAqIEEkMzsKCiAgICBmdW5jdGlvbiBjdWJlaGVsaXhDb252ZXJ0JDMobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIEN1YmVoZWxpeCQzKSByZXR1cm4gbmV3IEN1YmVoZWxpeCQzKG8uaCwgby5zLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBSZ2IkNCkpIG8gPSByZ2JDb252ZXJ0JDQobyk7CiAgICAgIHZhciByID0gby5yIC8gMjU1LAogICAgICAgICAgZyA9IG8uZyAvIDI1NSwKICAgICAgICAgIGIgPSBvLmIgLyAyNTUsCiAgICAgICAgICBsID0gKEJDX0RBJDMgKiBiICsgRUQkMyAqIHIgLSBFQiQzICogZykgLyAoQkNfREEkMyArIEVEJDMgLSBFQiQzKSwKICAgICAgICAgIGJsID0gYiAtIGwsCiAgICAgICAgICBrID0gKEUkMyAqIChnIC0gbCkgLSBDJDMgKiBibCkgLyBEJDMsCiAgICAgICAgICBzID0gTWF0aC5zcXJ0KGsgKiBrICsgYmwgKiBibCkgLyAoRSQzICogbCAqICgxIC0gbCkpLCAvLyBOYU4gaWYgbD0wIG9yIGw9MQogICAgICAgICAgaCA9IHMgPyBNYXRoLmF0YW4yKGssIGJsKSAqIHJhZDJkZWckMyAtIDEyMCA6IE5hTjsKICAgICAgcmV0dXJuIG5ldyBDdWJlaGVsaXgkMyhoIDwgMCA/IGggKyAzNjAgOiBoLCBzLCBsLCBvLm9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmVoZWxpeCQ4KGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPT09IDEgPyBjdWJlaGVsaXhDb252ZXJ0JDMoaCkgOiBuZXcgQ3ViZWhlbGl4JDMoaCwgcywgbCwgb3BhY2l0eSA9PSBudWxsID8gMSA6IG9wYWNpdHkpOwogICAgfQoKICAgIGZ1bmN0aW9uIEN1YmVoZWxpeCQzKGgsIHMsIGwsIG9wYWNpdHkpIHsKICAgICAgdGhpcy5oID0gK2g7CiAgICAgIHRoaXMucyA9ICtzOwogICAgICB0aGlzLmwgPSArbDsKICAgICAgdGhpcy5vcGFjaXR5ID0gK29wYWNpdHk7CiAgICB9CgogICAgZGVmaW5lJDQoQ3ViZWhlbGl4JDMsIGN1YmVoZWxpeCQ4LCBleHRlbmQkNChDb2xvciQ0LCB7CiAgICAgIGJyaWdodGVyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGJyaWdodGVyJDQgOiBNYXRoLnBvdyhicmlnaHRlciQ0LCBrKTsKICAgICAgICByZXR1cm4gbmV3IEN1YmVoZWxpeCQzKHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDQgOiBNYXRoLnBvdyhkYXJrZXIkNCwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBDdWJlaGVsaXgkMyh0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgaCA9IGlzTmFOKHRoaXMuaCkgPyAwIDogKHRoaXMuaCArIDEyMCkgKiBkZWcycmFkJDMsCiAgICAgICAgICAgIGwgPSArdGhpcy5sLAogICAgICAgICAgICBhID0gaXNOYU4odGhpcy5zKSA/IDAgOiB0aGlzLnMgKiBsICogKDEgLSBsKSwKICAgICAgICAgICAgY29zaCA9IE1hdGguY29zKGgpLAogICAgICAgICAgICBzaW5oID0gTWF0aC5zaW4oaCk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkNCgKICAgICAgICAgIDI1NSAqIChsICsgYSAqIChBJDMgKiBjb3NoICsgQiQzICogc2luaCkpLAogICAgICAgICAgMjU1ICogKGwgKyBhICogKEMkMyAqIGNvc2ggKyBEJDMgKiBzaW5oKSksCiAgICAgICAgICAyNTUgKiAobCArIGEgKiAoRSQzICogY29zaCkpLAogICAgICAgICAgdGhpcy5vcGFjaXR5CiAgICAgICAgKTsKICAgICAgfQogICAgfSkpOwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JHAoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbGluZWFyJDYoYSwgZCkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICsgdCAqIGQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZXhwb25lbnRpYWwkNShhLCBiLCB5KSB7CiAgICAgIHJldHVybiBhID0gTWF0aC5wb3coYSwgeSksIGIgPSBNYXRoLnBvdyhiLCB5KSAtIGEsIHkgPSAxIC8geSwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBNYXRoLnBvdyhhICsgdCAqIGIsIHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGh1ZSQzKGEsIGIpIHsKICAgICAgdmFyIGQgPSBiIC0gYTsKICAgICAgcmV0dXJuIGQgPyBsaW5lYXIkNihhLCBkID4gMTgwIHx8IGQgPCAtMTgwID8gZCAtIDM2MCAqIE1hdGgucm91bmQoZCAvIDM2MCkgOiBkKSA6IGNvbnN0YW50JHAoaXNOYU4oYSkgPyBiIDogYSk7CiAgICB9CgogICAgZnVuY3Rpb24gZ2FtbWEkMyh5KSB7CiAgICAgIHJldHVybiAoeSA9ICt5KSA9PT0gMSA/IG5vZ2FtbWEkMyA6IGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICByZXR1cm4gYiAtIGEgPyBleHBvbmVudGlhbCQ1KGEsIGIsIHkpIDogY29uc3RhbnQkcChpc05hTihhKSA/IGIgOiBhKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2dhbW1hJDMoYSwgYikgewogICAgICB2YXIgZCA9IGIgLSBhOwogICAgICByZXR1cm4gZCA/IGxpbmVhciQ2KGEsIGQpIDogY29uc3RhbnQkcChpc05hTihhKSA/IGIgOiBhKTsKICAgIH0KCiAgICB2YXIgcmdiJDYgPSAoZnVuY3Rpb24gcmdiR2FtbWEoeSkgewogICAgICB2YXIgY29sb3IgPSBnYW1tYSQzKHkpOwoKICAgICAgZnVuY3Rpb24gcmdiKHN0YXJ0LCBlbmQpIHsKICAgICAgICB2YXIgciA9IGNvbG9yKChzdGFydCA9IHJnYiQ1KHN0YXJ0KSkuciwgKGVuZCA9IHJnYiQ1KGVuZCkpLnIpLAogICAgICAgICAgICBnID0gY29sb3Ioc3RhcnQuZywgZW5kLmcpLAogICAgICAgICAgICBiID0gY29sb3Ioc3RhcnQuYiwgZW5kLmIpLAogICAgICAgICAgICBvcGFjaXR5ID0gbm9nYW1tYSQzKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgc3RhcnQuciA9IHIodCk7CiAgICAgICAgICBzdGFydC5nID0gZyh0KTsKICAgICAgICAgIHN0YXJ0LmIgPSBiKHQpOwogICAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICB9OwogICAgICB9CgogICAgICByZ2IuZ2FtbWEgPSByZ2JHYW1tYTsKCiAgICAgIHJldHVybiByZ2I7CiAgICB9KSgxKTsKCiAgICBmdW5jdGlvbiBudW1iZXJBcnJheSQyKGEsIGIpIHsKICAgICAgaWYgKCFiKSBiID0gW107CiAgICAgIHZhciBuID0gYSA/IE1hdGgubWluKGIubGVuZ3RoLCBhLmxlbmd0aCkgOiAwLAogICAgICAgICAgYyA9IGIuc2xpY2UoKSwKICAgICAgICAgIGk7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgY1tpXSA9IGFbaV0gKiAoMSAtIHQpICsgYltpXSAqIHQ7CiAgICAgICAgcmV0dXJuIGM7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaXNOdW1iZXJBcnJheSQyKHgpIHsKICAgICAgcmV0dXJuIEFycmF5QnVmZmVyLmlzVmlldyh4KSAmJiAhKHggaW5zdGFuY2VvZiBEYXRhVmlldyk7CiAgICB9CgogICAgZnVuY3Rpb24gZ2VuZXJpY0FycmF5JDIoYSwgYikgewogICAgICB2YXIgbmIgPSBiID8gYi5sZW5ndGggOiAwLAogICAgICAgICAgbmEgPSBhID8gTWF0aC5taW4obmIsIGEubGVuZ3RoKSA6IDAsCiAgICAgICAgICB4ID0gbmV3IEFycmF5KG5hKSwKICAgICAgICAgIGMgPSBuZXcgQXJyYXkobmIpLAogICAgICAgICAgaTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuYTsgKytpKSB4W2ldID0gaW50ZXJwb2xhdGVWYWx1ZSQxKGFbaV0sIGJbaV0pOwogICAgICBmb3IgKDsgaSA8IG5iOyArK2kpIGNbaV0gPSBiW2ldOwoKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbmE7ICsraSkgY1tpXSA9IHhbaV0odCk7CiAgICAgICAgcmV0dXJuIGM7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZGF0ZSQ0KGEsIGIpIHsKICAgICAgdmFyIGQgPSBuZXcgRGF0ZTsKICAgICAgcmV0dXJuIGEgPSArYSwgYiA9ICtiLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGQuc2V0VGltZShhICogKDEgLSB0KSArIGIgKiB0KSwgZDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiByZWludGVycG9sYXRlKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPSArYSwgYiA9ICtiLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGEgKiAoMSAtIHQpICsgYiAqIHQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb2JqZWN0JDUoYSwgYikgewogICAgICB2YXIgaSA9IHt9LAogICAgICAgICAgYyA9IHt9LAogICAgICAgICAgazsKCiAgICAgIGlmIChhID09PSBudWxsIHx8IHR5cGVvZiBhICE9PSAib2JqZWN0IikgYSA9IHt9OwogICAgICBpZiAoYiA9PT0gbnVsbCB8fCB0eXBlb2YgYiAhPT0gIm9iamVjdCIpIGIgPSB7fTsKCiAgICAgIGZvciAoayBpbiBiKSB7CiAgICAgICAgaWYgKGsgaW4gYSkgewogICAgICAgICAgaVtrXSA9IGludGVycG9sYXRlVmFsdWUkMShhW2tdLCBiW2tdKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY1trXSA9IGJba107CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIGZvciAoayBpbiBpKSBjW2tdID0gaVtrXSh0KTsKICAgICAgICByZXR1cm4gYzsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcmVBJDMgPSAvWy0rXT8oPzpcZCtcLj9cZCp8XC4/XGQrKSg/OltlRV1bLStdP1xkKyk/L2csCiAgICAgICAgcmVCJDMgPSBuZXcgUmVnRXhwKHJlQSQzLnNvdXJjZSwgImciKTsKCiAgICBmdW5jdGlvbiB6ZXJvJDMoYikgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGI7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb25lJDMoYikgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBiKHQpICsgIiI7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3RyaW5nJDEoYSwgYikgewogICAgICB2YXIgYmkgPSByZUEkMy5sYXN0SW5kZXggPSByZUIkMy5sYXN0SW5kZXggPSAwLCAvLyBzY2FuIGluZGV4IGZvciBuZXh0IG51bWJlciBpbiBiCiAgICAgICAgICBhbSwgLy8gY3VycmVudCBtYXRjaCBpbiBhCiAgICAgICAgICBibSwgLy8gY3VycmVudCBtYXRjaCBpbiBiCiAgICAgICAgICBicywgLy8gc3RyaW5nIHByZWNlZGluZyBjdXJyZW50IG51bWJlciBpbiBiLCBpZiBhbnkKICAgICAgICAgIGkgPSAtMSwgLy8gaW5kZXggaW4gcwogICAgICAgICAgcyA9IFtdLCAvLyBzdHJpbmcgY29uc3RhbnRzIGFuZCBwbGFjZWhvbGRlcnMKICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKCiAgICAgIC8vIENvZXJjZSBpbnB1dHMgdG8gc3RyaW5ncy4KICAgICAgYSA9IGEgKyAiIiwgYiA9IGIgKyAiIjsKCiAgICAgIC8vIEludGVycG9sYXRlIHBhaXJzIG9mIG51bWJlcnMgaW4gYSAmIGIuCiAgICAgIHdoaWxlICgoYW0gPSByZUEkMy5leGVjKGEpKQogICAgICAgICAgJiYgKGJtID0gcmVCJDMuZXhlYyhiKSkpIHsKICAgICAgICBpZiAoKGJzID0gYm0uaW5kZXgpID4gYmkpIHsgLy8gYSBzdHJpbmcgcHJlY2VkZXMgdGhlIG5leHQgbnVtYmVyIGluIGIKICAgICAgICAgIGJzID0gYi5zbGljZShiaSwgYnMpOwogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICAgIH0KICAgICAgICBpZiAoKGFtID0gYW1bMF0pID09PSAoYm0gPSBibVswXSkpIHsgLy8gbnVtYmVycyBpbiBhICYgYiBtYXRjaAogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYm07IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJtOwogICAgICAgIH0gZWxzZSB7IC8vIGludGVycG9sYXRlIG5vbi1tYXRjaGluZyBudW1iZXJzCiAgICAgICAgICBzWysraV0gPSBudWxsOwogICAgICAgICAgcS5wdXNoKHtpOiBpLCB4OiByZWludGVycG9sYXRlKGFtLCBibSl9KTsKICAgICAgICB9CiAgICAgICAgYmkgPSByZUIkMy5sYXN0SW5kZXg7CiAgICAgIH0KCiAgICAgIC8vIEFkZCByZW1haW5zIG9mIGIuCiAgICAgIGlmIChiaSA8IGIubGVuZ3RoKSB7CiAgICAgICAgYnMgPSBiLnNsaWNlKGJpKTsKICAgICAgICBpZiAoc1tpXSkgc1tpXSArPSBiczsgLy8gY29hbGVzY2Ugd2l0aCBwcmV2aW91cyBzdHJpbmcKICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICB9CgogICAgICAvLyBTcGVjaWFsIG9wdGltaXphdGlvbiBmb3Igb25seSBhIHNpbmdsZSBtYXRjaC4KICAgICAgLy8gT3RoZXJ3aXNlLCBpbnRlcnBvbGF0ZSBlYWNoIG9mIHRoZSBudW1iZXJzIGFuZCByZWpvaW4gdGhlIHN0cmluZy4KICAgICAgcmV0dXJuIHMubGVuZ3RoIDwgMiA/IChxWzBdCiAgICAgICAgICA/IG9uZSQzKHFbMF0ueCkKICAgICAgICAgIDogemVybyQzKGIpKQogICAgICAgICAgOiAoYiA9IHEubGVuZ3RoLCBmdW5jdGlvbih0KSB7CiAgICAgICAgICAgICAgZm9yICh2YXIgaSA9IDAsIG87IGkgPCBiOyArK2kpIHNbKG8gPSBxW2ldKS5pXSA9IG8ueCh0KTsKICAgICAgICAgICAgICByZXR1cm4gcy5qb2luKCIiKTsKICAgICAgICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGVWYWx1ZSQxKGEsIGIpIHsKICAgICAgdmFyIHQgPSB0eXBlb2YgYiwgYzsKICAgICAgcmV0dXJuIGIgPT0gbnVsbCB8fCB0ID09PSAiYm9vbGVhbiIgPyBjb25zdGFudCRwKGIpCiAgICAgICAgICA6ICh0ID09PSAibnVtYmVyIiA/IHJlaW50ZXJwb2xhdGUKICAgICAgICAgIDogdCA9PT0gInN0cmluZyIgPyAoKGMgPSBjb2xvciQ0KGIpKSA/IChiID0gYywgcmdiJDYpIDogc3RyaW5nJDEpCiAgICAgICAgICA6IGIgaW5zdGFuY2VvZiBjb2xvciQ0ID8gcmdiJDYKICAgICAgICAgIDogYiBpbnN0YW5jZW9mIERhdGUgPyBkYXRlJDQKICAgICAgICAgIDogaXNOdW1iZXJBcnJheSQyKGIpID8gbnVtYmVyQXJyYXkkMgogICAgICAgICAgOiBBcnJheS5pc0FycmF5KGIpID8gZ2VuZXJpY0FycmF5JDIKICAgICAgICAgIDogdHlwZW9mIGIudmFsdWVPZiAhPT0gImZ1bmN0aW9uIiAmJiB0eXBlb2YgYi50b1N0cmluZyAhPT0gImZ1bmN0aW9uIiB8fCBpc05hTihiKSA/IG9iamVjdCQ1CiAgICAgICAgICA6IHJlaW50ZXJwb2xhdGUpKGEsIGIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlUm91bmQkMShhLCBiKSB7CiAgICAgIHJldHVybiBhID0gK2EsIGIgPSArYiwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBNYXRoLnJvdW5kKGEgKiAoMSAtIHQpICsgYiAqIHQpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGN1YmVoZWxpeCQ5KGh1ZSkgewogICAgICByZXR1cm4gKGZ1bmN0aW9uIGN1YmVoZWxpeEdhbW1hKHkpIHsKICAgICAgICB5ID0gK3k7CgogICAgICAgIGZ1bmN0aW9uIGN1YmVoZWxpeChzdGFydCwgZW5kKSB7CiAgICAgICAgICB2YXIgaCA9IGh1ZSgoc3RhcnQgPSBjdWJlaGVsaXgkOChzdGFydCkpLmgsIChlbmQgPSBjdWJlaGVsaXgkOChlbmQpKS5oKSwKICAgICAgICAgICAgICBzID0gbm9nYW1tYSQzKHN0YXJ0LnMsIGVuZC5zKSwKICAgICAgICAgICAgICBsID0gbm9nYW1tYSQzKHN0YXJ0LmwsIGVuZC5sKSwKICAgICAgICAgICAgICBvcGFjaXR5ID0gbm9nYW1tYSQzKHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICAgIHN0YXJ0LmggPSBoKHQpOwogICAgICAgICAgICBzdGFydC5zID0gcyh0KTsKICAgICAgICAgICAgc3RhcnQubCA9IGwoTWF0aC5wb3codCwgeSkpOwogICAgICAgICAgICBzdGFydC5vcGFjaXR5ID0gb3BhY2l0eSh0KTsKICAgICAgICAgICAgcmV0dXJuIHN0YXJ0ICsgIiI7CiAgICAgICAgICB9OwogICAgICAgIH0KCiAgICAgICAgY3ViZWhlbGl4LmdhbW1hID0gY3ViZWhlbGl4R2FtbWE7CgogICAgICAgIHJldHVybiBjdWJlaGVsaXg7CiAgICAgIH0pKDEpOwogICAgfQoKICAgIGN1YmVoZWxpeCQ5KGh1ZSQzKTsKICAgIHZhciBjdWJlaGVsaXhMb25nJDIgPSBjdWJlaGVsaXgkOShub2dhbW1hJDMpOwoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JHEoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbnVtYmVyJDgoeCkgewogICAgICByZXR1cm4gK3g7CiAgICB9CgogICAgdmFyIHVuaXQkMSA9IFswLCAxXTsKCiAgICBmdW5jdGlvbiBkZWludGVycG9sYXRlTGluZWFyKGEsIGIpIHsKICAgICAgcmV0dXJuIChiIC09IChhID0gK2EpKQogICAgICAgICAgPyBmdW5jdGlvbih4KSB7IHJldHVybiAoeCAtIGEpIC8gYjsgfQogICAgICAgICAgOiBjb25zdGFudCRxKGIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlaW50ZXJwb2xhdGVDbGFtcChkZWludGVycG9sYXRlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgdmFyIGQgPSBkZWludGVycG9sYXRlKGEgPSArYSwgYiA9ICtiKTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oeCkgeyByZXR1cm4geCA8PSBhID8gMCA6IHggPj0gYiA/IDEgOiBkKHgpOyB9OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHJlaW50ZXJwb2xhdGVDbGFtcChyZWludGVycG9sYXRlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgdmFyIHIgPSByZWludGVycG9sYXRlKGEgPSArYSwgYiA9ICtiKTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgeyByZXR1cm4gdCA8PSAwID8gYSA6IHQgPj0gMSA/IGIgOiByKHQpOyB9OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGJpbWFwJDEoZG9tYWluLCByYW5nZSwgZGVpbnRlcnBvbGF0ZSwgcmVpbnRlcnBvbGF0ZSkgewogICAgICB2YXIgZDAgPSBkb21haW5bMF0sIGQxID0gZG9tYWluWzFdLCByMCA9IHJhbmdlWzBdLCByMSA9IHJhbmdlWzFdOwogICAgICBpZiAoZDEgPCBkMCkgZDAgPSBkZWludGVycG9sYXRlKGQxLCBkMCksIHIwID0gcmVpbnRlcnBvbGF0ZShyMSwgcjApOwogICAgICBlbHNlIGQwID0gZGVpbnRlcnBvbGF0ZShkMCwgZDEpLCByMCA9IHJlaW50ZXJwb2xhdGUocjAsIHIxKTsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgpIHsgcmV0dXJuIHIwKGQwKHgpKTsgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwb2x5bWFwJDEoZG9tYWluLCByYW5nZSwgZGVpbnRlcnBvbGF0ZSwgcmVpbnRlcnBvbGF0ZSkgewogICAgICB2YXIgaiA9IE1hdGgubWluKGRvbWFpbi5sZW5ndGgsIHJhbmdlLmxlbmd0aCkgLSAxLAogICAgICAgICAgZCA9IG5ldyBBcnJheShqKSwKICAgICAgICAgIHIgPSBuZXcgQXJyYXkoaiksCiAgICAgICAgICBpID0gLTE7CgogICAgICAvLyBSZXZlcnNlIGRlc2NlbmRpbmcgZG9tYWlucy4KICAgICAgaWYgKGRvbWFpbltqXSA8IGRvbWFpblswXSkgewogICAgICAgIGRvbWFpbiA9IGRvbWFpbi5zbGljZSgpLnJldmVyc2UoKTsKICAgICAgICByYW5nZSA9IHJhbmdlLnNsaWNlKCkucmV2ZXJzZSgpOwogICAgICB9CgogICAgICB3aGlsZSAoKytpIDwgaikgewogICAgICAgIGRbaV0gPSBkZWludGVycG9sYXRlKGRvbWFpbltpXSwgZG9tYWluW2kgKyAxXSk7CiAgICAgICAgcltpXSA9IHJlaW50ZXJwb2xhdGUocmFuZ2VbaV0sIHJhbmdlW2kgKyAxXSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbih4KSB7CiAgICAgICAgdmFyIGkgPSBiaXNlY3RSaWdodCQyKGRvbWFpbiwgeCwgMSwgaikgLSAxOwogICAgICAgIHJldHVybiByW2ldKGRbaV0oeCkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvcHkkMihzb3VyY2UsIHRhcmdldCkgewogICAgICByZXR1cm4gdGFyZ2V0CiAgICAgICAgICAuZG9tYWluKHNvdXJjZS5kb21haW4oKSkKICAgICAgICAgIC5yYW5nZShzb3VyY2UucmFuZ2UoKSkKICAgICAgICAgIC5pbnRlcnBvbGF0ZShzb3VyY2UuaW50ZXJwb2xhdGUoKSkKICAgICAgICAgIC5jbGFtcChzb3VyY2UuY2xhbXAoKSk7CiAgICB9CgogICAgLy8gZGVpbnRlcnBvbGF0ZShhLCBiKSh4KSB0YWtlcyBhIGRvbWFpbiB2YWx1ZSB4IGluIFthLGJdIGFuZCByZXR1cm5zIHRoZSBjb3JyZXNwb25kaW5nIHBhcmFtZXRlciB0IGluIFswLDFdLgogICAgLy8gcmVpbnRlcnBvbGF0ZShhLCBiKSh0KSB0YWtlcyBhIHBhcmFtZXRlciB0IGluIFswLDFdIGFuZCByZXR1cm5zIHRoZSBjb3JyZXNwb25kaW5nIGRvbWFpbiB2YWx1ZSB4IGluIFthLGJdLgogICAgZnVuY3Rpb24gY29udGludW91cyQxKGRlaW50ZXJwb2xhdGUsIHJlaW50ZXJwb2xhdGUpIHsKICAgICAgdmFyIGRvbWFpbiA9IHVuaXQkMSwKICAgICAgICAgIHJhbmdlID0gdW5pdCQxLAogICAgICAgICAgaW50ZXJwb2xhdGUgPSBpbnRlcnBvbGF0ZVZhbHVlJDEsCiAgICAgICAgICBjbGFtcCA9IGZhbHNlLAogICAgICAgICAgcGllY2V3aXNlLAogICAgICAgICAgb3V0cHV0LAogICAgICAgICAgaW5wdXQ7CgogICAgICBmdW5jdGlvbiByZXNjYWxlKCkgewogICAgICAgIHBpZWNld2lzZSA9IE1hdGgubWluKGRvbWFpbi5sZW5ndGgsIHJhbmdlLmxlbmd0aCkgPiAyID8gcG9seW1hcCQxIDogYmltYXAkMTsKICAgICAgICBvdXRwdXQgPSBpbnB1dCA9IG51bGw7CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgcmV0dXJuIChvdXRwdXQgfHwgKG91dHB1dCA9IHBpZWNld2lzZShkb21haW4sIHJhbmdlLCBjbGFtcCA/IGRlaW50ZXJwb2xhdGVDbGFtcChkZWludGVycG9sYXRlKSA6IGRlaW50ZXJwb2xhdGUsIGludGVycG9sYXRlKSkpKCt4KTsKICAgICAgfQoKICAgICAgc2NhbGUuaW52ZXJ0ID0gZnVuY3Rpb24oeSkgewogICAgICAgIHJldHVybiAoaW5wdXQgfHwgKGlucHV0ID0gcGllY2V3aXNlKHJhbmdlLCBkb21haW4sIGRlaW50ZXJwb2xhdGVMaW5lYXIsIGNsYW1wID8gcmVpbnRlcnBvbGF0ZUNsYW1wKHJlaW50ZXJwb2xhdGUpIDogcmVpbnRlcnBvbGF0ZSkpKSgreSk7CiAgICAgIH07CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluID0gbWFwJDguY2FsbChfLCBudW1iZXIkOCksIHJlc2NhbGUoKSkgOiBkb21haW4uc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHJhbmdlID0gc2xpY2UkYy5jYWxsKF8pLCByZXNjYWxlKCkpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnJhbmdlUm91bmQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIHJhbmdlID0gc2xpY2UkYy5jYWxsKF8pLCBpbnRlcnBvbGF0ZSA9IGludGVycG9sYXRlUm91bmQkMSwgcmVzY2FsZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUuY2xhbXAgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY2xhbXAgPSAhIV8sIHJlc2NhbGUoKSkgOiBjbGFtcDsKICAgICAgfTsKCiAgICAgIHNjYWxlLmludGVycG9sYXRlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGludGVycG9sYXRlID0gXywgcmVzY2FsZSgpKSA6IGludGVycG9sYXRlOwogICAgICB9OwoKICAgICAgcmV0dXJuIHJlc2NhbGUoKTsKICAgIH0KCiAgICAvLyBDb21wdXRlcyB0aGUgZGVjaW1hbCBjb2VmZmljaWVudCBhbmQgZXhwb25lbnQgb2YgdGhlIHNwZWNpZmllZCBudW1iZXIgeCB3aXRoCiAgICAvLyBzaWduaWZpY2FudCBkaWdpdHMgcCwgd2hlcmUgeCBpcyBwb3NpdGl2ZSBhbmQgcCBpcyBpbiBbMSwgMjFdIG9yIHVuZGVmaW5lZC4KICAgIC8vIEZvciBleGFtcGxlLCBmb3JtYXREZWNpbWFsKDEuMjMpIHJldHVybnMgWyIxMjMiLCAwXS4KICAgIGZ1bmN0aW9uIGZvcm1hdERlY2ltYWwkMih4LCBwKSB7CiAgICAgIGlmICgoaSA9ICh4ID0gcCA/IHgudG9FeHBvbmVudGlhbChwIC0gMSkgOiB4LnRvRXhwb25lbnRpYWwoKSkuaW5kZXhPZigiZSIpKSA8IDApIHJldHVybiBudWxsOyAvLyBOYU4sIMKxSW5maW5pdHkKICAgICAgdmFyIGksIGNvZWZmaWNpZW50ID0geC5zbGljZSgwLCBpKTsKCiAgICAgIC8vIFRoZSBzdHJpbmcgcmV0dXJuZWQgYnkgdG9FeHBvbmVudGlhbCBlaXRoZXIgaGFzIHRoZSBmb3JtIFxkXC5cZCtlWy0rXVxkKwogICAgICAvLyAoZS5nLiwgMS4yZSszKSBvciB0aGUgZm9ybSBcZGVbLStdXGQrIChlLmcuLCAxZSszKS4KICAgICAgcmV0dXJuIFsKICAgICAgICBjb2VmZmljaWVudC5sZW5ndGggPiAxID8gY29lZmZpY2llbnRbMF0gKyBjb2VmZmljaWVudC5zbGljZSgyKSA6IGNvZWZmaWNpZW50LAogICAgICAgICt4LnNsaWNlKGkgKyAxKQogICAgICBdOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4cG9uZW50JDQoeCkgewogICAgICByZXR1cm4geCA9IGZvcm1hdERlY2ltYWwkMihNYXRoLmFicyh4KSksIHggPyB4WzFdIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEdyb3VwJDIoZ3JvdXBpbmcsIHRob3VzYW5kcykgewogICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUsIHdpZHRoKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5sZW5ndGgsCiAgICAgICAgICAgIHQgPSBbXSwKICAgICAgICAgICAgaiA9IDAsCiAgICAgICAgICAgIGcgPSBncm91cGluZ1swXSwKICAgICAgICAgICAgbGVuZ3RoID0gMDsKCiAgICAgICAgd2hpbGUgKGkgPiAwICYmIGcgPiAwKSB7CiAgICAgICAgICBpZiAobGVuZ3RoICsgZyArIDEgPiB3aWR0aCkgZyA9IE1hdGgubWF4KDEsIHdpZHRoIC0gbGVuZ3RoKTsKICAgICAgICAgIHQucHVzaCh2YWx1ZS5zdWJzdHJpbmcoaSAtPSBnLCBpICsgZykpOwogICAgICAgICAgaWYgKChsZW5ndGggKz0gZyArIDEpID4gd2lkdGgpIGJyZWFrOwogICAgICAgICAgZyA9IGdyb3VwaW5nW2ogPSAoaiArIDEpICUgZ3JvdXBpbmcubGVuZ3RoXTsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0LnJldmVyc2UoKS5qb2luKHRob3VzYW5kcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TnVtZXJhbHMkMihudW1lcmFscykgewogICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICByZXR1cm4gdmFsdWUucmVwbGFjZSgvWzAtOV0vZywgZnVuY3Rpb24oaSkgewogICAgICAgICAgcmV0dXJuIG51bWVyYWxzWytpXTsKICAgICAgICB9KTsKICAgICAgfTsKICAgIH0KCiAgICAvLyBbW2ZpbGxdYWxpZ25dW3NpZ25dW3N5bWJvbF1bMF1bd2lkdGhdWyxdWy5wcmVjaXNpb25dW35dW3R5cGVdCiAgICB2YXIgcmUkMiA9IC9eKD86KC4pPyhbPD49Xl0pKT8oWytcLSggXSk/KFskI10pPygwKT8oXGQrKT8oLCk/KFwuXGQrKT8ofik/KFthLXolXSk/JC9pOwoKICAgIGZ1bmN0aW9uIGZvcm1hdFNwZWNpZmllciQyKHNwZWNpZmllcikgewogICAgICBpZiAoIShtYXRjaCA9IHJlJDIuZXhlYyhzcGVjaWZpZXIpKSkgdGhyb3cgbmV3IEVycm9yKCJpbnZhbGlkIGZvcm1hdDogIiArIHNwZWNpZmllcik7CiAgICAgIHZhciBtYXRjaDsKICAgICAgcmV0dXJuIG5ldyBGb3JtYXRTcGVjaWZpZXIkMih7CiAgICAgICAgZmlsbDogbWF0Y2hbMV0sCiAgICAgICAgYWxpZ246IG1hdGNoWzJdLAogICAgICAgIHNpZ246IG1hdGNoWzNdLAogICAgICAgIHN5bWJvbDogbWF0Y2hbNF0sCiAgICAgICAgemVybzogbWF0Y2hbNV0sCiAgICAgICAgd2lkdGg6IG1hdGNoWzZdLAogICAgICAgIGNvbW1hOiBtYXRjaFs3XSwKICAgICAgICBwcmVjaXNpb246IG1hdGNoWzhdICYmIG1hdGNoWzhdLnNsaWNlKDEpLAogICAgICAgIHRyaW06IG1hdGNoWzldLAogICAgICAgIHR5cGU6IG1hdGNoWzEwXQogICAgICB9KTsKICAgIH0KCiAgICBmb3JtYXRTcGVjaWZpZXIkMi5wcm90b3R5cGUgPSBGb3JtYXRTcGVjaWZpZXIkMi5wcm90b3R5cGU7IC8vIGluc3RhbmNlb2YKCiAgICBmdW5jdGlvbiBGb3JtYXRTcGVjaWZpZXIkMihzcGVjaWZpZXIpIHsKICAgICAgdGhpcy5maWxsID0gc3BlY2lmaWVyLmZpbGwgPT09IHVuZGVmaW5lZCA/ICIgIiA6IHNwZWNpZmllci5maWxsICsgIiI7CiAgICAgIHRoaXMuYWxpZ24gPSBzcGVjaWZpZXIuYWxpZ24gPT09IHVuZGVmaW5lZCA/ICI+IiA6IHNwZWNpZmllci5hbGlnbiArICIiOwogICAgICB0aGlzLnNpZ24gPSBzcGVjaWZpZXIuc2lnbiA9PT0gdW5kZWZpbmVkID8gIi0iIDogc3BlY2lmaWVyLnNpZ24gKyAiIjsKICAgICAgdGhpcy5zeW1ib2wgPSBzcGVjaWZpZXIuc3ltYm9sID09PSB1bmRlZmluZWQgPyAiIiA6IHNwZWNpZmllci5zeW1ib2wgKyAiIjsKICAgICAgdGhpcy56ZXJvID0gISFzcGVjaWZpZXIuemVybzsKICAgICAgdGhpcy53aWR0aCA9IHNwZWNpZmllci53aWR0aCA9PT0gdW5kZWZpbmVkID8gdW5kZWZpbmVkIDogK3NwZWNpZmllci53aWR0aDsKICAgICAgdGhpcy5jb21tYSA9ICEhc3BlY2lmaWVyLmNvbW1hOwogICAgICB0aGlzLnByZWNpc2lvbiA9IHNwZWNpZmllci5wcmVjaXNpb24gPT09IHVuZGVmaW5lZCA/IHVuZGVmaW5lZCA6ICtzcGVjaWZpZXIucHJlY2lzaW9uOwogICAgICB0aGlzLnRyaW0gPSAhIXNwZWNpZmllci50cmltOwogICAgICB0aGlzLnR5cGUgPSBzcGVjaWZpZXIudHlwZSA9PT0gdW5kZWZpbmVkID8gIiIgOiBzcGVjaWZpZXIudHlwZSArICIiOwogICAgfQoKICAgIEZvcm1hdFNwZWNpZmllciQyLnByb3RvdHlwZS50b1N0cmluZyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5maWxsCiAgICAgICAgICArIHRoaXMuYWxpZ24KICAgICAgICAgICsgdGhpcy5zaWduCiAgICAgICAgICArIHRoaXMuc3ltYm9sCiAgICAgICAgICArICh0aGlzLnplcm8gPyAiMCIgOiAiIikKICAgICAgICAgICsgKHRoaXMud2lkdGggPT09IHVuZGVmaW5lZCA/ICIiIDogTWF0aC5tYXgoMSwgdGhpcy53aWR0aCB8IDApKQogICAgICAgICAgKyAodGhpcy5jb21tYSA/ICIsIiA6ICIiKQogICAgICAgICAgKyAodGhpcy5wcmVjaXNpb24gPT09IHVuZGVmaW5lZCA/ICIiIDogIi4iICsgTWF0aC5tYXgoMCwgdGhpcy5wcmVjaXNpb24gfCAwKSkKICAgICAgICAgICsgKHRoaXMudHJpbSA/ICJ+IiA6ICIiKQogICAgICAgICAgKyB0aGlzLnR5cGU7CiAgICB9OwoKICAgIC8vIFRyaW1zIGluc2lnbmlmaWNhbnQgemVyb3MsIGUuZy4sIHJlcGxhY2VzIDEuMjAwMGsgd2l0aCAxLjJrLgogICAgZnVuY3Rpb24gZm9ybWF0VHJpbSQxKHMpIHsKICAgICAgb3V0OiBmb3IgKHZhciBuID0gcy5sZW5ndGgsIGkgPSAxLCBpMCA9IC0xLCBpMTsgaSA8IG47ICsraSkgewogICAgICAgIHN3aXRjaCAoc1tpXSkgewogICAgICAgICAgY2FzZSAiLiI6IGkwID0gaTEgPSBpOyBicmVhazsKICAgICAgICAgIGNhc2UgIjAiOiBpZiAoaTAgPT09IDApIGkwID0gaTsgaTEgPSBpOyBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6IGlmICghK3NbaV0pIGJyZWFrIG91dDsgaWYgKGkwID4gMCkgaTAgPSAwOyBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGkwID4gMCA/IHMuc2xpY2UoMCwgaTApICsgcy5zbGljZShpMSArIDEpIDogczsKICAgIH0KCiAgICB2YXIgcHJlZml4RXhwb25lbnQkMjsKCiAgICBmdW5jdGlvbiBmb3JtYXRQcmVmaXhBdXRvJDIoeCwgcCkgewogICAgICB2YXIgZCA9IGZvcm1hdERlY2ltYWwkMih4LCBwKTsKICAgICAgaWYgKCFkKSByZXR1cm4geCArICIiOwogICAgICB2YXIgY29lZmZpY2llbnQgPSBkWzBdLAogICAgICAgICAgZXhwb25lbnQgPSBkWzFdLAogICAgICAgICAgaSA9IGV4cG9uZW50IC0gKHByZWZpeEV4cG9uZW50JDIgPSBNYXRoLm1heCgtOCwgTWF0aC5taW4oOCwgTWF0aC5mbG9vcihleHBvbmVudCAvIDMpKSkgKiAzKSArIDEsCiAgICAgICAgICBuID0gY29lZmZpY2llbnQubGVuZ3RoOwogICAgICByZXR1cm4gaSA9PT0gbiA/IGNvZWZmaWNpZW50CiAgICAgICAgICA6IGkgPiBuID8gY29lZmZpY2llbnQgKyBuZXcgQXJyYXkoaSAtIG4gKyAxKS5qb2luKCIwIikKICAgICAgICAgIDogaSA+IDAgPyBjb2VmZmljaWVudC5zbGljZSgwLCBpKSArICIuIiArIGNvZWZmaWNpZW50LnNsaWNlKGkpCiAgICAgICAgICA6ICIwLiIgKyBuZXcgQXJyYXkoMSAtIGkpLmpvaW4oIjAiKSArIGZvcm1hdERlY2ltYWwkMih4LCBNYXRoLm1heCgwLCBwICsgaSAtIDEpKVswXTsgLy8gbGVzcyB0aGFuIDF5IQogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFJvdW5kZWQkMih4LCBwKSB7CiAgICAgIHZhciBkID0gZm9ybWF0RGVjaW1hbCQyKHgsIHApOwogICAgICBpZiAoIWQpIHJldHVybiB4ICsgIiI7CiAgICAgIHZhciBjb2VmZmljaWVudCA9IGRbMF0sCiAgICAgICAgICBleHBvbmVudCA9IGRbMV07CiAgICAgIHJldHVybiBleHBvbmVudCA8IDAgPyAiMC4iICsgbmV3IEFycmF5KC1leHBvbmVudCkuam9pbigiMCIpICsgY29lZmZpY2llbnQKICAgICAgICAgIDogY29lZmZpY2llbnQubGVuZ3RoID4gZXhwb25lbnQgKyAxID8gY29lZmZpY2llbnQuc2xpY2UoMCwgZXhwb25lbnQgKyAxKSArICIuIiArIGNvZWZmaWNpZW50LnNsaWNlKGV4cG9uZW50ICsgMSkKICAgICAgICAgIDogY29lZmZpY2llbnQgKyBuZXcgQXJyYXkoZXhwb25lbnQgLSBjb2VmZmljaWVudC5sZW5ndGggKyAyKS5qb2luKCIwIik7CiAgICB9CgogICAgdmFyIGZvcm1hdFR5cGVzJDIgPSB7CiAgICAgICIlIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4gKHggKiAxMDApLnRvRml4ZWQocCk7IH0sCiAgICAgICJiIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygyKTsgfSwKICAgICAgImMiOiBmdW5jdGlvbih4KSB7IHJldHVybiB4ICsgIiI7IH0sCiAgICAgICJkIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygxMCk7IH0sCiAgICAgICJlIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4geC50b0V4cG9uZW50aWFsKHApOyB9LAogICAgICAiZiI6IGZ1bmN0aW9uKHgsIHApIHsgcmV0dXJuIHgudG9GaXhlZChwKTsgfSwKICAgICAgImciOiBmdW5jdGlvbih4LCBwKSB7IHJldHVybiB4LnRvUHJlY2lzaW9uKHApOyB9LAogICAgICAibyI6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgucm91bmQoeCkudG9TdHJpbmcoOCk7IH0sCiAgICAgICJwIjogZnVuY3Rpb24oeCwgcCkgeyByZXR1cm4gZm9ybWF0Um91bmRlZCQyKHggKiAxMDAsIHApOyB9LAogICAgICAiciI6IGZvcm1hdFJvdW5kZWQkMiwKICAgICAgInMiOiBmb3JtYXRQcmVmaXhBdXRvJDIsCiAgICAgICJYIjogZnVuY3Rpb24oeCkgeyByZXR1cm4gTWF0aC5yb3VuZCh4KS50b1N0cmluZygxNikudG9VcHBlckNhc2UoKTsgfSwKICAgICAgIngiOiBmdW5jdGlvbih4KSB7IHJldHVybiBNYXRoLnJvdW5kKHgpLnRvU3RyaW5nKDE2KTsgfQogICAgfTsKCiAgICBmdW5jdGlvbiBpZGVudGl0eSRoKHgpIHsKICAgICAgcmV0dXJuIHg7CiAgICB9CgogICAgdmFyIG1hcCQ5ID0gQXJyYXkucHJvdG90eXBlLm1hcCwKICAgICAgICBwcmVmaXhlcyQyID0gWyJ5IiwieiIsImEiLCJmIiwicCIsIm4iLCLCtSIsIm0iLCIiLCJrIiwiTSIsIkciLCJUIiwiUCIsIkUiLCJaIiwiWSJdOwoKICAgIGZ1bmN0aW9uIGZvcm1hdExvY2FsZSQzKGxvY2FsZSkgewogICAgICB2YXIgZ3JvdXAgPSBsb2NhbGUuZ3JvdXBpbmcgPT09IHVuZGVmaW5lZCB8fCBsb2NhbGUudGhvdXNhbmRzID09PSB1bmRlZmluZWQgPyBpZGVudGl0eSRoIDogZm9ybWF0R3JvdXAkMihtYXAkOS5jYWxsKGxvY2FsZS5ncm91cGluZywgTnVtYmVyKSwgbG9jYWxlLnRob3VzYW5kcyArICIiKSwKICAgICAgICAgIGN1cnJlbmN5UHJlZml4ID0gbG9jYWxlLmN1cnJlbmN5ID09PSB1bmRlZmluZWQgPyAiIiA6IGxvY2FsZS5jdXJyZW5jeVswXSArICIiLAogICAgICAgICAgY3VycmVuY3lTdWZmaXggPSBsb2NhbGUuY3VycmVuY3kgPT09IHVuZGVmaW5lZCA/ICIiIDogbG9jYWxlLmN1cnJlbmN5WzFdICsgIiIsCiAgICAgICAgICBkZWNpbWFsID0gbG9jYWxlLmRlY2ltYWwgPT09IHVuZGVmaW5lZCA/ICIuIiA6IGxvY2FsZS5kZWNpbWFsICsgIiIsCiAgICAgICAgICBudW1lcmFscyA9IGxvY2FsZS5udW1lcmFscyA9PT0gdW5kZWZpbmVkID8gaWRlbnRpdHkkaCA6IGZvcm1hdE51bWVyYWxzJDIobWFwJDkuY2FsbChsb2NhbGUubnVtZXJhbHMsIFN0cmluZykpLAogICAgICAgICAgcGVyY2VudCA9IGxvY2FsZS5wZXJjZW50ID09PSB1bmRlZmluZWQgPyAiJSIgOiBsb2NhbGUucGVyY2VudCArICIiLAogICAgICAgICAgbWludXMgPSBsb2NhbGUubWludXMgPT09IHVuZGVmaW5lZCA/ICItIiA6IGxvY2FsZS5taW51cyArICIiLAogICAgICAgICAgbmFuID0gbG9jYWxlLm5hbiA9PT0gdW5kZWZpbmVkID8gIk5hTiIgOiBsb2NhbGUubmFuICsgIiI7CgogICAgICBmdW5jdGlvbiBuZXdGb3JtYXQoc3BlY2lmaWVyKSB7CiAgICAgICAgc3BlY2lmaWVyID0gZm9ybWF0U3BlY2lmaWVyJDIoc3BlY2lmaWVyKTsKCiAgICAgICAgdmFyIGZpbGwgPSBzcGVjaWZpZXIuZmlsbCwKICAgICAgICAgICAgYWxpZ24gPSBzcGVjaWZpZXIuYWxpZ24sCiAgICAgICAgICAgIHNpZ24gPSBzcGVjaWZpZXIuc2lnbiwKICAgICAgICAgICAgc3ltYm9sID0gc3BlY2lmaWVyLnN5bWJvbCwKICAgICAgICAgICAgemVybyA9IHNwZWNpZmllci56ZXJvLAogICAgICAgICAgICB3aWR0aCA9IHNwZWNpZmllci53aWR0aCwKICAgICAgICAgICAgY29tbWEgPSBzcGVjaWZpZXIuY29tbWEsCiAgICAgICAgICAgIHByZWNpc2lvbiA9IHNwZWNpZmllci5wcmVjaXNpb24sCiAgICAgICAgICAgIHRyaW0gPSBzcGVjaWZpZXIudHJpbSwKICAgICAgICAgICAgdHlwZSA9IHNwZWNpZmllci50eXBlOwoKICAgICAgICAvLyBUaGUgIm4iIHR5cGUgaXMgYW4gYWxpYXMgZm9yICIsZyIuCiAgICAgICAgaWYgKHR5cGUgPT09ICJuIikgY29tbWEgPSB0cnVlLCB0eXBlID0gImciOwoKICAgICAgICAvLyBUaGUgIiIgdHlwZSwgYW5kIGFueSBpbnZhbGlkIHR5cGUsIGlzIGFuIGFsaWFzIGZvciAiLjEyfmciLgogICAgICAgIGVsc2UgaWYgKCFmb3JtYXRUeXBlcyQyW3R5cGVdKSBwcmVjaXNpb24gPT09IHVuZGVmaW5lZCAmJiAocHJlY2lzaW9uID0gMTIpLCB0cmltID0gdHJ1ZSwgdHlwZSA9ICJnIjsKCiAgICAgICAgLy8gSWYgemVybyBmaWxsIGlzIHNwZWNpZmllZCwgcGFkZGluZyBnb2VzIGFmdGVyIHNpZ24gYW5kIGJlZm9yZSBkaWdpdHMuCiAgICAgICAgaWYgKHplcm8gfHwgKGZpbGwgPT09ICIwIiAmJiBhbGlnbiA9PT0gIj0iKSkgemVybyA9IHRydWUsIGZpbGwgPSAiMCIsIGFsaWduID0gIj0iOwoKICAgICAgICAvLyBDb21wdXRlIHRoZSBwcmVmaXggYW5kIHN1ZmZpeC4KICAgICAgICAvLyBGb3IgU0ktcHJlZml4LCB0aGUgc3VmZml4IGlzIGxhemlseSBjb21wdXRlZC4KICAgICAgICB2YXIgcHJlZml4ID0gc3ltYm9sID09PSAiJCIgPyBjdXJyZW5jeVByZWZpeCA6IHN5bWJvbCA9PT0gIiMiICYmIC9bYm94WF0vLnRlc3QodHlwZSkgPyAiMCIgKyB0eXBlLnRvTG93ZXJDYXNlKCkgOiAiIiwKICAgICAgICAgICAgc3VmZml4ID0gc3ltYm9sID09PSAiJCIgPyBjdXJyZW5jeVN1ZmZpeCA6IC9bJXBdLy50ZXN0KHR5cGUpID8gcGVyY2VudCA6ICIiOwoKICAgICAgICAvLyBXaGF0IGZvcm1hdCBmdW5jdGlvbiBzaG91bGQgd2UgdXNlPwogICAgICAgIC8vIElzIHRoaXMgYW4gaW50ZWdlciB0eXBlPwogICAgICAgIC8vIENhbiB0aGlzIHR5cGUgZ2VuZXJhdGUgZXhwb25lbnRpYWwgbm90YXRpb24/CiAgICAgICAgdmFyIGZvcm1hdFR5cGUgPSBmb3JtYXRUeXBlcyQyW3R5cGVdLAogICAgICAgICAgICBtYXliZVN1ZmZpeCA9IC9bZGVmZ3BycyVdLy50ZXN0KHR5cGUpOwoKICAgICAgICAvLyBTZXQgdGhlIGRlZmF1bHQgcHJlY2lzaW9uIGlmIG5vdCBzcGVjaWZpZWQsCiAgICAgICAgLy8gb3IgY2xhbXAgdGhlIHNwZWNpZmllZCBwcmVjaXNpb24gdG8gdGhlIHN1cHBvcnRlZCByYW5nZS4KICAgICAgICAvLyBGb3Igc2lnbmlmaWNhbnQgcHJlY2lzaW9uLCBpdCBtdXN0IGJlIGluIFsxLCAyMV0uCiAgICAgICAgLy8gRm9yIGZpeGVkIHByZWNpc2lvbiwgaXQgbXVzdCBiZSBpbiBbMCwgMjBdLgogICAgICAgIHByZWNpc2lvbiA9IHByZWNpc2lvbiA9PT0gdW5kZWZpbmVkID8gNgogICAgICAgICAgICA6IC9bZ3Byc10vLnRlc3QodHlwZSkgPyBNYXRoLm1heCgxLCBNYXRoLm1pbigyMSwgcHJlY2lzaW9uKSkKICAgICAgICAgICAgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigyMCwgcHJlY2lzaW9uKSk7CgogICAgICAgIGZ1bmN0aW9uIGZvcm1hdCh2YWx1ZSkgewogICAgICAgICAgdmFyIHZhbHVlUHJlZml4ID0gcHJlZml4LAogICAgICAgICAgICAgIHZhbHVlU3VmZml4ID0gc3VmZml4LAogICAgICAgICAgICAgIGksIG4sIGM7CgogICAgICAgICAgaWYgKHR5cGUgPT09ICJjIikgewogICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9IGZvcm1hdFR5cGUodmFsdWUpICsgdmFsdWVTdWZmaXg7CiAgICAgICAgICAgIHZhbHVlID0gIiI7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB2YWx1ZSA9ICt2YWx1ZTsKCiAgICAgICAgICAgIC8vIERldGVybWluZSB0aGUgc2lnbi4gLTAgaXMgbm90IGxlc3MgdGhhbiAwLCBidXQgMSAvIC0wIGlzIQogICAgICAgICAgICB2YXIgdmFsdWVOZWdhdGl2ZSA9IHZhbHVlIDwgMCB8fCAxIC8gdmFsdWUgPCAwOwoKICAgICAgICAgICAgLy8gUGVyZm9ybSB0aGUgaW5pdGlhbCBmb3JtYXR0aW5nLgogICAgICAgICAgICB2YWx1ZSA9IGlzTmFOKHZhbHVlKSA/IG5hbiA6IGZvcm1hdFR5cGUoTWF0aC5hYnModmFsdWUpLCBwcmVjaXNpb24pOwoKICAgICAgICAgICAgLy8gVHJpbSBpbnNpZ25pZmljYW50IHplcm9zLgogICAgICAgICAgICBpZiAodHJpbSkgdmFsdWUgPSBmb3JtYXRUcmltJDEodmFsdWUpOwoKICAgICAgICAgICAgLy8gSWYgYSBuZWdhdGl2ZSB2YWx1ZSByb3VuZHMgdG8gemVybyBhZnRlciBmb3JtYXR0aW5nLCBhbmQgbm8gZXhwbGljaXQgcG9zaXRpdmUgc2lnbiBpcyByZXF1ZXN0ZWQsIGhpZGUgdGhlIHNpZ24uCiAgICAgICAgICAgIGlmICh2YWx1ZU5lZ2F0aXZlICYmICt2YWx1ZSA9PT0gMCAmJiBzaWduICE9PSAiKyIpIHZhbHVlTmVnYXRpdmUgPSBmYWxzZTsKCiAgICAgICAgICAgIC8vIENvbXB1dGUgdGhlIHByZWZpeCBhbmQgc3VmZml4LgogICAgICAgICAgICB2YWx1ZVByZWZpeCA9ICh2YWx1ZU5lZ2F0aXZlID8gKHNpZ24gPT09ICIoIiA/IHNpZ24gOiBtaW51cykgOiBzaWduID09PSAiLSIgfHwgc2lnbiA9PT0gIigiID8gIiIgOiBzaWduKSArIHZhbHVlUHJlZml4OwogICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9ICh0eXBlID09PSAicyIgPyBwcmVmaXhlcyQyWzggKyBwcmVmaXhFeHBvbmVudCQyIC8gM10gOiAiIikgKyB2YWx1ZVN1ZmZpeCArICh2YWx1ZU5lZ2F0aXZlICYmIHNpZ24gPT09ICIoIiA/ICIpIiA6ICIiKTsKCiAgICAgICAgICAgIC8vIEJyZWFrIHRoZSBmb3JtYXR0ZWQgdmFsdWUgaW50byB0aGUgaW50ZWdlciDigJx2YWx1ZeKAnSBwYXJ0IHRoYXQgY2FuIGJlCiAgICAgICAgICAgIC8vIGdyb3VwZWQsIGFuZCBmcmFjdGlvbmFsIG9yIGV4cG9uZW50aWFsIOKAnHN1ZmZpeOKAnSBwYXJ0IHRoYXQgaXMgbm90LgogICAgICAgICAgICBpZiAobWF5YmVTdWZmaXgpIHsKICAgICAgICAgICAgICBpID0gLTEsIG4gPSB2YWx1ZS5sZW5ndGg7CiAgICAgICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgICAgICAgIGlmIChjID0gdmFsdWUuY2hhckNvZGVBdChpKSwgNDggPiBjIHx8IGMgPiA1NykgewogICAgICAgICAgICAgICAgICB2YWx1ZVN1ZmZpeCA9IChjID09PSA0NiA/IGRlY2ltYWwgKyB2YWx1ZS5zbGljZShpICsgMSkgOiB2YWx1ZS5zbGljZShpKSkgKyB2YWx1ZVN1ZmZpeDsKICAgICAgICAgICAgICAgICAgdmFsdWUgPSB2YWx1ZS5zbGljZSgwLCBpKTsKICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgLy8gSWYgdGhlIGZpbGwgY2hhcmFjdGVyIGlzIG5vdCAiMCIsIGdyb3VwaW5nIGlzIGFwcGxpZWQgYmVmb3JlIHBhZGRpbmcuCiAgICAgICAgICBpZiAoY29tbWEgJiYgIXplcm8pIHZhbHVlID0gZ3JvdXAodmFsdWUsIEluZmluaXR5KTsKCiAgICAgICAgICAvLyBDb21wdXRlIHRoZSBwYWRkaW5nLgogICAgICAgICAgdmFyIGxlbmd0aCA9IHZhbHVlUHJlZml4Lmxlbmd0aCArIHZhbHVlLmxlbmd0aCArIHZhbHVlU3VmZml4Lmxlbmd0aCwKICAgICAgICAgICAgICBwYWRkaW5nID0gbGVuZ3RoIDwgd2lkdGggPyBuZXcgQXJyYXkod2lkdGggLSBsZW5ndGggKyAxKS5qb2luKGZpbGwpIDogIiI7CgogICAgICAgICAgLy8gSWYgdGhlIGZpbGwgY2hhcmFjdGVyIGlzICIwIiwgZ3JvdXBpbmcgaXMgYXBwbGllZCBhZnRlciBwYWRkaW5nLgogICAgICAgICAgaWYgKGNvbW1hICYmIHplcm8pIHZhbHVlID0gZ3JvdXAocGFkZGluZyArIHZhbHVlLCBwYWRkaW5nLmxlbmd0aCA/IHdpZHRoIC0gdmFsdWVTdWZmaXgubGVuZ3RoIDogSW5maW5pdHkpLCBwYWRkaW5nID0gIiI7CgogICAgICAgICAgLy8gUmVjb25zdHJ1Y3QgdGhlIGZpbmFsIG91dHB1dCBiYXNlZCBvbiB0aGUgZGVzaXJlZCBhbGlnbm1lbnQuCiAgICAgICAgICBzd2l0Y2ggKGFsaWduKSB7CiAgICAgICAgICAgIGNhc2UgIjwiOiB2YWx1ZSA9IHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeCArIHBhZGRpbmc7IGJyZWFrOwogICAgICAgICAgICBjYXNlICI9IjogdmFsdWUgPSB2YWx1ZVByZWZpeCArIHBhZGRpbmcgKyB2YWx1ZSArIHZhbHVlU3VmZml4OyBicmVhazsKICAgICAgICAgICAgY2FzZSAiXiI6IHZhbHVlID0gcGFkZGluZy5zbGljZSgwLCBsZW5ndGggPSBwYWRkaW5nLmxlbmd0aCA+PiAxKSArIHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeCArIHBhZGRpbmcuc2xpY2UobGVuZ3RoKTsgYnJlYWs7CiAgICAgICAgICAgIGRlZmF1bHQ6IHZhbHVlID0gcGFkZGluZyArIHZhbHVlUHJlZml4ICsgdmFsdWUgKyB2YWx1ZVN1ZmZpeDsgYnJlYWs7CiAgICAgICAgICB9CgogICAgICAgICAgcmV0dXJuIG51bWVyYWxzKHZhbHVlKTsKICAgICAgICB9CgogICAgICAgIGZvcm1hdC50b1N0cmluZyA9IGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIHNwZWNpZmllciArICIiOwogICAgICAgIH07CgogICAgICAgIHJldHVybiBmb3JtYXQ7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFByZWZpeChzcGVjaWZpZXIsIHZhbHVlKSB7CiAgICAgICAgdmFyIGYgPSBuZXdGb3JtYXQoKHNwZWNpZmllciA9IGZvcm1hdFNwZWNpZmllciQyKHNwZWNpZmllciksIHNwZWNpZmllci50eXBlID0gImYiLCBzcGVjaWZpZXIpKSwKICAgICAgICAgICAgZSA9IE1hdGgubWF4KC04LCBNYXRoLm1pbig4LCBNYXRoLmZsb29yKGV4cG9uZW50JDQodmFsdWUpIC8gMykpKSAqIDMsCiAgICAgICAgICAgIGsgPSBNYXRoLnBvdygxMCwgLWUpLAogICAgICAgICAgICBwcmVmaXggPSBwcmVmaXhlcyQyWzggKyBlIC8gM107CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gZihrICogdmFsdWUpICsgcHJlZml4OwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJldHVybiB7CiAgICAgICAgZm9ybWF0OiBuZXdGb3JtYXQsCiAgICAgICAgZm9ybWF0UHJlZml4OiBmb3JtYXRQcmVmaXgKICAgICAgfTsKICAgIH0KCiAgICB2YXIgbG9jYWxlJDM7CiAgICB2YXIgZm9ybWF0JDI7CiAgICB2YXIgZm9ybWF0UHJlZml4JDI7CgogICAgZGVmYXVsdExvY2FsZSQzKHsKICAgICAgZGVjaW1hbDogIi4iLAogICAgICB0aG91c2FuZHM6ICIsIiwKICAgICAgZ3JvdXBpbmc6IFszXSwKICAgICAgY3VycmVuY3k6IFsiJCIsICIiXSwKICAgICAgbWludXM6ICItIgogICAgfSk7CgogICAgZnVuY3Rpb24gZGVmYXVsdExvY2FsZSQzKGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlJDMgPSBmb3JtYXRMb2NhbGUkMyhkZWZpbml0aW9uKTsKICAgICAgZm9ybWF0JDIgPSBsb2NhbGUkMy5mb3JtYXQ7CiAgICAgIGZvcm1hdFByZWZpeCQyID0gbG9jYWxlJDMuZm9ybWF0UHJlZml4OwogICAgICByZXR1cm4gbG9jYWxlJDM7CiAgICB9CgogICAgZnVuY3Rpb24gcHJlY2lzaW9uRml4ZWQkMihzdGVwKSB7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCAtZXhwb25lbnQkNChNYXRoLmFicyhzdGVwKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvblByZWZpeCQyKHN0ZXAsIHZhbHVlKSB7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCBNYXRoLm1heCgtOCwgTWF0aC5taW4oOCwgTWF0aC5mbG9vcihleHBvbmVudCQ0KHZhbHVlKSAvIDMpKSkgKiAzIC0gZXhwb25lbnQkNChNYXRoLmFicyhzdGVwKSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHByZWNpc2lvblJvdW5kJDIoc3RlcCwgbWF4KSB7CiAgICAgIHN0ZXAgPSBNYXRoLmFicyhzdGVwKSwgbWF4ID0gTWF0aC5hYnMobWF4KSAtIHN0ZXA7CiAgICAgIHJldHVybiBNYXRoLm1heCgwLCBleHBvbmVudCQ0KG1heCkgLSBleHBvbmVudCQ0KHN0ZXApKSArIDE7CiAgICB9CgogICAgZnVuY3Rpb24gdGlja0Zvcm1hdCQxKGRvbWFpbiwgY291bnQsIHNwZWNpZmllcikgewogICAgICB2YXIgc3RhcnQgPSBkb21haW5bMF0sCiAgICAgICAgICBzdG9wID0gZG9tYWluW2RvbWFpbi5sZW5ndGggLSAxXSwKICAgICAgICAgIHN0ZXAgPSB0aWNrU3RlcCQyKHN0YXJ0LCBzdG9wLCBjb3VudCA9PSBudWxsID8gMTAgOiBjb3VudCksCiAgICAgICAgICBwcmVjaXNpb247CiAgICAgIHNwZWNpZmllciA9IGZvcm1hdFNwZWNpZmllciQyKHNwZWNpZmllciA9PSBudWxsID8gIixmIiA6IHNwZWNpZmllcik7CiAgICAgIHN3aXRjaCAoc3BlY2lmaWVyLnR5cGUpIHsKICAgICAgICBjYXNlICJzIjogewogICAgICAgICAgdmFyIHZhbHVlID0gTWF0aC5tYXgoTWF0aC5hYnMoc3RhcnQpLCBNYXRoLmFicyhzdG9wKSk7CiAgICAgICAgICBpZiAoc3BlY2lmaWVyLnByZWNpc2lvbiA9PSBudWxsICYmICFpc05hTihwcmVjaXNpb24gPSBwcmVjaXNpb25QcmVmaXgkMihzdGVwLCB2YWx1ZSkpKSBzcGVjaWZpZXIucHJlY2lzaW9uID0gcHJlY2lzaW9uOwogICAgICAgICAgcmV0dXJuIGZvcm1hdFByZWZpeCQyKHNwZWNpZmllciwgdmFsdWUpOwogICAgICAgIH0KICAgICAgICBjYXNlICIiOgogICAgICAgIGNhc2UgImUiOgogICAgICAgIGNhc2UgImciOgogICAgICAgIGNhc2UgInAiOgogICAgICAgIGNhc2UgInIiOiB7CiAgICAgICAgICBpZiAoc3BlY2lmaWVyLnByZWNpc2lvbiA9PSBudWxsICYmICFpc05hTihwcmVjaXNpb24gPSBwcmVjaXNpb25Sb3VuZCQyKHN0ZXAsIE1hdGgubWF4KE1hdGguYWJzKHN0YXJ0KSwgTWF0aC5hYnMoc3RvcCkpKSkpIHNwZWNpZmllci5wcmVjaXNpb24gPSBwcmVjaXNpb24gLSAoc3BlY2lmaWVyLnR5cGUgPT09ICJlIik7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgY2FzZSAiZiI6CiAgICAgICAgY2FzZSAiJSI6IHsKICAgICAgICAgIGlmIChzcGVjaWZpZXIucHJlY2lzaW9uID09IG51bGwgJiYgIWlzTmFOKHByZWNpc2lvbiA9IHByZWNpc2lvbkZpeGVkJDIoc3RlcCkpKSBzcGVjaWZpZXIucHJlY2lzaW9uID0gcHJlY2lzaW9uIC0gKHNwZWNpZmllci50eXBlID09PSAiJSIpICogMjsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gZm9ybWF0JDIoc3BlY2lmaWVyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5lYXJpc2gkMShzY2FsZSkgewogICAgICB2YXIgZG9tYWluID0gc2NhbGUuZG9tYWluOwoKICAgICAgc2NhbGUudGlja3MgPSBmdW5jdGlvbihjb3VudCkgewogICAgICAgIHZhciBkID0gZG9tYWluKCk7CiAgICAgICAgcmV0dXJuIHRpY2tzJDIoZFswXSwgZFtkLmxlbmd0aCAtIDFdLCBjb3VudCA9PSBudWxsID8gMTAgOiBjb3VudCk7CiAgICAgIH07CgogICAgICBzY2FsZS50aWNrRm9ybWF0ID0gZnVuY3Rpb24oY291bnQsIHNwZWNpZmllcikgewogICAgICAgIHJldHVybiB0aWNrRm9ybWF0JDEoZG9tYWluKCksIGNvdW50LCBzcGVjaWZpZXIpOwogICAgICB9OwoKICAgICAgc2NhbGUubmljZSA9IGZ1bmN0aW9uKGNvdW50KSB7CiAgICAgICAgaWYgKGNvdW50ID09IG51bGwpIGNvdW50ID0gMTA7CgogICAgICAgIHZhciBkID0gZG9tYWluKCksCiAgICAgICAgICAgIGkwID0gMCwKICAgICAgICAgICAgaTEgPSBkLmxlbmd0aCAtIDEsCiAgICAgICAgICAgIHN0YXJ0ID0gZFtpMF0sCiAgICAgICAgICAgIHN0b3AgPSBkW2kxXSwKICAgICAgICAgICAgc3RlcDsKCiAgICAgICAgaWYgKHN0b3AgPCBzdGFydCkgewogICAgICAgICAgc3RlcCA9IHN0YXJ0LCBzdGFydCA9IHN0b3AsIHN0b3AgPSBzdGVwOwogICAgICAgICAgc3RlcCA9IGkwLCBpMCA9IGkxLCBpMSA9IHN0ZXA7CiAgICAgICAgfQoKICAgICAgICBzdGVwID0gdGlja0luY3JlbWVudCQyKHN0YXJ0LCBzdG9wLCBjb3VudCk7CgogICAgICAgIGlmIChzdGVwID4gMCkgewogICAgICAgICAgc3RhcnQgPSBNYXRoLmZsb29yKHN0YXJ0IC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgc3RvcCA9IE1hdGguY2VpbChzdG9wIC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgc3RlcCA9IHRpY2tJbmNyZW1lbnQkMihzdGFydCwgc3RvcCwgY291bnQpOwogICAgICAgIH0gZWxzZSBpZiAoc3RlcCA8IDApIHsKICAgICAgICAgIHN0YXJ0ID0gTWF0aC5jZWlsKHN0YXJ0ICogc3RlcCkgLyBzdGVwOwogICAgICAgICAgc3RvcCA9IE1hdGguZmxvb3Ioc3RvcCAqIHN0ZXApIC8gc3RlcDsKICAgICAgICAgIHN0ZXAgPSB0aWNrSW5jcmVtZW50JDIoc3RhcnQsIHN0b3AsIGNvdW50KTsKICAgICAgICB9CgogICAgICAgIGlmIChzdGVwID4gMCkgewogICAgICAgICAgZFtpMF0gPSBNYXRoLmZsb29yKHN0YXJ0IC8gc3RlcCkgKiBzdGVwOwogICAgICAgICAgZFtpMV0gPSBNYXRoLmNlaWwoc3RvcCAvIHN0ZXApICogc3RlcDsKICAgICAgICAgIGRvbWFpbihkKTsKICAgICAgICB9IGVsc2UgaWYgKHN0ZXAgPCAwKSB7CiAgICAgICAgICBkW2kwXSA9IE1hdGguY2VpbChzdGFydCAqIHN0ZXApIC8gc3RlcDsKICAgICAgICAgIGRbaTFdID0gTWF0aC5mbG9vcihzdG9wICogc3RlcCkgLyBzdGVwOwogICAgICAgICAgZG9tYWluKGQpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9OwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVhciQ3KCkgewogICAgICB2YXIgc2NhbGUgPSBjb250aW51b3VzJDEoZGVpbnRlcnBvbGF0ZUxpbmVhciwgcmVpbnRlcnBvbGF0ZSk7CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGNvcHkkMihzY2FsZSwgbGluZWFyJDcoKSk7CiAgICAgIH07CgogICAgICByZXR1cm4gbGluZWFyaXNoJDEoc2NhbGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JGkoKSB7CiAgICAgIHZhciBkb21haW4gPSBbMCwgMV07CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgcmV0dXJuICt4OwogICAgICB9CgogICAgICBzY2FsZS5pbnZlcnQgPSBzY2FsZTsKCiAgICAgIHNjYWxlLmRvbWFpbiA9IHNjYWxlLnJhbmdlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRvbWFpbiA9IG1hcCQ4LmNhbGwoXywgbnVtYmVyJDgpLCBzY2FsZSkgOiBkb21haW4uc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gaWRlbnRpdHkkaSgpLmRvbWFpbihkb21haW4pOwogICAgICB9OwoKICAgICAgcmV0dXJuIGxpbmVhcmlzaCQxKHNjYWxlKTsKICAgIH0KCiAgICBmdW5jdGlvbiBuaWNlJDEoZG9tYWluLCBpbnRlcnZhbCkgewogICAgICBkb21haW4gPSBkb21haW4uc2xpY2UoKTsKCiAgICAgIHZhciBpMCA9IDAsCiAgICAgICAgICBpMSA9IGRvbWFpbi5sZW5ndGggLSAxLAogICAgICAgICAgeDAgPSBkb21haW5baTBdLAogICAgICAgICAgeDEgPSBkb21haW5baTFdLAogICAgICAgICAgdDsKCiAgICAgIGlmICh4MSA8IHgwKSB7CiAgICAgICAgdCA9IGkwLCBpMCA9IGkxLCBpMSA9IHQ7CiAgICAgICAgdCA9IHgwLCB4MCA9IHgxLCB4MSA9IHQ7CiAgICAgIH0KCiAgICAgIGRvbWFpbltpMF0gPSBpbnRlcnZhbC5mbG9vcih4MCk7CiAgICAgIGRvbWFpbltpMV0gPSBpbnRlcnZhbC5jZWlsKHgxKTsKICAgICAgcmV0dXJuIGRvbWFpbjsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWludGVycG9sYXRlKGEsIGIpIHsKICAgICAgcmV0dXJuIChiID0gTWF0aC5sb2coYiAvIGEpKQogICAgICAgICAgPyBmdW5jdGlvbih4KSB7IHJldHVybiBNYXRoLmxvZyh4IC8gYSkgLyBiOyB9CiAgICAgICAgICA6IGNvbnN0YW50JHEoYik7CiAgICB9CgogICAgZnVuY3Rpb24gcmVpbnRlcnBvbGF0ZSQxKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPCAwCiAgICAgICAgICA/IGZ1bmN0aW9uKHQpIHsgcmV0dXJuIC1NYXRoLnBvdygtYiwgdCkgKiBNYXRoLnBvdygtYSwgMSAtIHQpOyB9CiAgICAgICAgICA6IGZ1bmN0aW9uKHQpIHsgcmV0dXJuIE1hdGgucG93KGIsIHQpICogTWF0aC5wb3coYSwgMSAtIHQpOyB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvdzEwJDEoeCkgewogICAgICByZXR1cm4gaXNGaW5pdGUoeCkgPyArKCIxZSIgKyB4KSA6IHggPCAwID8gMCA6IHg7CiAgICB9CgogICAgZnVuY3Rpb24gcG93cCQxKGJhc2UpIHsKICAgICAgcmV0dXJuIGJhc2UgPT09IDEwID8gcG93MTAkMQogICAgICAgICAgOiBiYXNlID09PSBNYXRoLkUgPyBNYXRoLmV4cAogICAgICAgICAgOiBmdW5jdGlvbih4KSB7IHJldHVybiBNYXRoLnBvdyhiYXNlLCB4KTsgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBsb2dwJDEoYmFzZSkgewogICAgICByZXR1cm4gYmFzZSA9PT0gTWF0aC5FID8gTWF0aC5sb2cKICAgICAgICAgIDogYmFzZSA9PT0gMTAgJiYgTWF0aC5sb2cxMAogICAgICAgICAgfHwgYmFzZSA9PT0gMiAmJiBNYXRoLmxvZzIKICAgICAgICAgIHx8IChiYXNlID0gTWF0aC5sb2coYmFzZSksIGZ1bmN0aW9uKHgpIHsgcmV0dXJuIE1hdGgubG9nKHgpIC8gYmFzZTsgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVmbGVjdCQxKGYpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gLWYoLXgpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGxvZyQzKCkgewogICAgICB2YXIgc2NhbGUgPSBjb250aW51b3VzJDEoZGVpbnRlcnBvbGF0ZSwgcmVpbnRlcnBvbGF0ZSQxKS5kb21haW4oWzEsIDEwXSksCiAgICAgICAgICBkb21haW4gPSBzY2FsZS5kb21haW4sCiAgICAgICAgICBiYXNlID0gMTAsCiAgICAgICAgICBsb2dzID0gbG9ncCQxKDEwKSwKICAgICAgICAgIHBvd3MgPSBwb3dwJDEoMTApOwoKICAgICAgZnVuY3Rpb24gcmVzY2FsZSgpIHsKICAgICAgICBsb2dzID0gbG9ncCQxKGJhc2UpLCBwb3dzID0gcG93cCQxKGJhc2UpOwogICAgICAgIGlmIChkb21haW4oKVswXSA8IDApIGxvZ3MgPSByZWZsZWN0JDEobG9ncyksIHBvd3MgPSByZWZsZWN0JDEocG93cyk7CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9CgogICAgICBzY2FsZS5iYXNlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGJhc2UgPSArXywgcmVzY2FsZSgpKSA6IGJhc2U7CiAgICAgIH07CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZG9tYWluKF8pLCByZXNjYWxlKCkpIDogZG9tYWluKCk7CiAgICAgIH07CgogICAgICBzY2FsZS50aWNrcyA9IGZ1bmN0aW9uKGNvdW50KSB7CiAgICAgICAgdmFyIGQgPSBkb21haW4oKSwKICAgICAgICAgICAgdSA9IGRbMF0sCiAgICAgICAgICAgIHYgPSBkW2QubGVuZ3RoIC0gMV0sCiAgICAgICAgICAgIHI7CgogICAgICAgIGlmIChyID0gdiA8IHUpIGkgPSB1LCB1ID0gdiwgdiA9IGk7CgogICAgICAgIHZhciBpID0gbG9ncyh1KSwKICAgICAgICAgICAgaiA9IGxvZ3ModiksCiAgICAgICAgICAgIHAsCiAgICAgICAgICAgIGssCiAgICAgICAgICAgIHQsCiAgICAgICAgICAgIG4gPSBjb3VudCA9PSBudWxsID8gMTAgOiArY291bnQsCiAgICAgICAgICAgIHogPSBbXTsKCiAgICAgICAgaWYgKCEoYmFzZSAlIDEpICYmIGogLSBpIDwgbikgewogICAgICAgICAgaSA9IE1hdGgucm91bmQoaSkgLSAxLCBqID0gTWF0aC5yb3VuZChqKSArIDE7CiAgICAgICAgICBpZiAodSA+IDApIGZvciAoOyBpIDwgajsgKytpKSB7CiAgICAgICAgICAgIGZvciAoayA9IDEsIHAgPSBwb3dzKGkpOyBrIDwgYmFzZTsgKytrKSB7CiAgICAgICAgICAgICAgdCA9IHAgKiBrOwogICAgICAgICAgICAgIGlmICh0IDwgdSkgY29udGludWU7CiAgICAgICAgICAgICAgaWYgKHQgPiB2KSBicmVhazsKICAgICAgICAgICAgICB6LnB1c2godCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBmb3IgKDsgaSA8IGo7ICsraSkgewogICAgICAgICAgICBmb3IgKGsgPSBiYXNlIC0gMSwgcCA9IHBvd3MoaSk7IGsgPj0gMTsgLS1rKSB7CiAgICAgICAgICAgICAgdCA9IHAgKiBrOwogICAgICAgICAgICAgIGlmICh0IDwgdSkgY29udGludWU7CiAgICAgICAgICAgICAgaWYgKHQgPiB2KSBicmVhazsKICAgICAgICAgICAgICB6LnB1c2godCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgeiA9IHRpY2tzJDIoaSwgaiwgTWF0aC5taW4oaiAtIGksIG4pKS5tYXAocG93cyk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gciA/IHoucmV2ZXJzZSgpIDogejsKICAgICAgfTsKCiAgICAgIHNjYWxlLnRpY2tGb3JtYXQgPSBmdW5jdGlvbihjb3VudCwgc3BlY2lmaWVyKSB7CiAgICAgICAgaWYgKHNwZWNpZmllciA9PSBudWxsKSBzcGVjaWZpZXIgPSBiYXNlID09PSAxMCA/ICIuMGUiIDogIiwiOwogICAgICAgIGlmICh0eXBlb2Ygc3BlY2lmaWVyICE9PSAiZnVuY3Rpb24iKSBzcGVjaWZpZXIgPSBmb3JtYXQkMihzcGVjaWZpZXIpOwogICAgICAgIGlmIChjb3VudCA9PT0gSW5maW5pdHkpIHJldHVybiBzcGVjaWZpZXI7CiAgICAgICAgaWYgKGNvdW50ID09IG51bGwpIGNvdW50ID0gMTA7CiAgICAgICAgdmFyIGsgPSBNYXRoLm1heCgxLCBiYXNlICogY291bnQgLyBzY2FsZS50aWNrcygpLmxlbmd0aCk7IC8vIFRPRE8gZmFzdCBlc3RpbWF0ZT8KICAgICAgICByZXR1cm4gZnVuY3Rpb24oZCkgewogICAgICAgICAgdmFyIGkgPSBkIC8gcG93cyhNYXRoLnJvdW5kKGxvZ3MoZCkpKTsKICAgICAgICAgIGlmIChpICogYmFzZSA8IGJhc2UgLSAwLjUpIGkgKj0gYmFzZTsKICAgICAgICAgIHJldHVybiBpIDw9IGsgPyBzcGVjaWZpZXIoZCkgOiAiIjsKICAgICAgICB9OwogICAgICB9OwoKICAgICAgc2NhbGUubmljZSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkb21haW4obmljZSQxKGRvbWFpbigpLCB7CiAgICAgICAgICBmbG9vcjogZnVuY3Rpb24oeCkgeyByZXR1cm4gcG93cyhNYXRoLmZsb29yKGxvZ3MoeCkpKTsgfSwKICAgICAgICAgIGNlaWw6IGZ1bmN0aW9uKHgpIHsgcmV0dXJuIHBvd3MoTWF0aC5jZWlsKGxvZ3MoeCkpKTsgfQogICAgICAgIH0pKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gY29weSQyKHNjYWxlLCBsb2ckMygpLmJhc2UoYmFzZSkpOwogICAgICB9OwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhaXNlJDMoeCwgZXhwb25lbnQpIHsKICAgICAgcmV0dXJuIHggPCAwID8gLU1hdGgucG93KC14LCBleHBvbmVudCkgOiBNYXRoLnBvdyh4LCBleHBvbmVudCk7CiAgICB9CgogICAgZnVuY3Rpb24gcG93JDMoKSB7CiAgICAgIHZhciBleHBvbmVudCA9IDEsCiAgICAgICAgICBzY2FsZSA9IGNvbnRpbnVvdXMkMShkZWludGVycG9sYXRlLCByZWludGVycG9sYXRlKSwKICAgICAgICAgIGRvbWFpbiA9IHNjYWxlLmRvbWFpbjsKCiAgICAgIGZ1bmN0aW9uIGRlaW50ZXJwb2xhdGUoYSwgYikgewogICAgICAgIHJldHVybiAoYiA9IHJhaXNlJDMoYiwgZXhwb25lbnQpIC0gKGEgPSByYWlzZSQzKGEsIGV4cG9uZW50KSkpCiAgICAgICAgICAgID8gZnVuY3Rpb24oeCkgeyByZXR1cm4gKHJhaXNlJDMoeCwgZXhwb25lbnQpIC0gYSkgLyBiOyB9CiAgICAgICAgICAgIDogY29uc3RhbnQkcShiKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcmVpbnRlcnBvbGF0ZShhLCBiKSB7CiAgICAgICAgYiA9IHJhaXNlJDMoYiwgZXhwb25lbnQpIC0gKGEgPSByYWlzZSQzKGEsIGV4cG9uZW50KSk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsgcmV0dXJuIHJhaXNlJDMoYSArIGIgKiB0LCAxIC8gZXhwb25lbnQpOyB9OwogICAgICB9CgogICAgICBzY2FsZS5leHBvbmVudCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChleHBvbmVudCA9ICtfLCBkb21haW4oZG9tYWluKCkpKSA6IGV4cG9uZW50OwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5JDIoc2NhbGUsIHBvdyQzKCkuZXhwb25lbnQoZXhwb25lbnQpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5lYXJpc2gkMShzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3FydCQ0KCkgewogICAgICByZXR1cm4gcG93JDMoKS5leHBvbmVudCgwLjUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YW50aWxlJDIoKSB7CiAgICAgIHZhciBkb21haW4gPSBbXSwKICAgICAgICAgIHJhbmdlID0gW10sCiAgICAgICAgICB0aHJlc2hvbGRzID0gW107CgogICAgICBmdW5jdGlvbiByZXNjYWxlKCkgewogICAgICAgIHZhciBpID0gMCwgbiA9IE1hdGgubWF4KDEsIHJhbmdlLmxlbmd0aCk7CiAgICAgICAgdGhyZXNob2xkcyA9IG5ldyBBcnJheShuIC0gMSk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHRocmVzaG9sZHNbaSAtIDFdID0gdGhyZXNob2xkJDIoZG9tYWluLCBpIC8gbik7CiAgICAgICAgcmV0dXJuIHNjYWxlOwogICAgICB9CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgaWYgKCFpc05hTih4ID0gK3gpKSByZXR1cm4gcmFuZ2VbYmlzZWN0UmlnaHQkMih0aHJlc2hvbGRzLCB4KV07CiAgICAgIH0KCiAgICAgIHNjYWxlLmludmVydEV4dGVudCA9IGZ1bmN0aW9uKHkpIHsKICAgICAgICB2YXIgaSA9IHJhbmdlLmluZGV4T2YoeSk7CiAgICAgICAgcmV0dXJuIGkgPCAwID8gW05hTiwgTmFOXSA6IFsKICAgICAgICAgIGkgPiAwID8gdGhyZXNob2xkc1tpIC0gMV0gOiBkb21haW5bMF0sCiAgICAgICAgICBpIDwgdGhyZXNob2xkcy5sZW5ndGggPyB0aHJlc2hvbGRzW2ldIDogZG9tYWluW2RvbWFpbi5sZW5ndGggLSAxXQogICAgICAgIF07CiAgICAgIH07CgogICAgICBzY2FsZS5kb21haW4gPSBmdW5jdGlvbihfKSB7CiAgICAgICAgaWYgKCFhcmd1bWVudHMubGVuZ3RoKSByZXR1cm4gZG9tYWluLnNsaWNlKCk7CiAgICAgICAgZG9tYWluID0gW107CiAgICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBfLmxlbmd0aCwgZDsgaSA8IG47ICsraSkgaWYgKGQgPSBfW2ldLCBkICE9IG51bGwgJiYgIWlzTmFOKGQgPSArZCkpIGRvbWFpbi5wdXNoKGQpOwogICAgICAgIGRvbWFpbi5zb3J0KGFzY2VuZGluZyQ5KTsKICAgICAgICByZXR1cm4gcmVzY2FsZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUucmFuZ2UgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAocmFuZ2UgPSBzbGljZSRjLmNhbGwoXyksIHJlc2NhbGUoKSkgOiByYW5nZS5zbGljZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUucXVhbnRpbGVzID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRocmVzaG9sZHMuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNvcHkgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gcXVhbnRpbGUkMigpCiAgICAgICAgICAgIC5kb21haW4oZG9tYWluKQogICAgICAgICAgICAucmFuZ2UocmFuZ2UpOwogICAgICB9OwoKICAgICAgcmV0dXJuIHNjYWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHF1YW50aXplJDMoKSB7CiAgICAgIHZhciB4MCA9IDAsCiAgICAgICAgICB4MSA9IDEsCiAgICAgICAgICBuID0gMSwKICAgICAgICAgIGRvbWFpbiA9IFswLjVdLAogICAgICAgICAgcmFuZ2UgPSBbMCwgMV07CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgaWYgKHggPD0geCkgcmV0dXJuIHJhbmdlW2Jpc2VjdFJpZ2h0JDIoZG9tYWluLCB4LCAwLCBuKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHJlc2NhbGUoKSB7CiAgICAgICAgdmFyIGkgPSAtMTsKICAgICAgICBkb21haW4gPSBuZXcgQXJyYXkobik7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGRvbWFpbltpXSA9ICgoaSArIDEpICogeDEgLSAoaSAtIG4pICogeDApIC8gKG4gKyAxKTsKICAgICAgICByZXR1cm4gc2NhbGU7CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4MCA9ICtfWzBdLCB4MSA9ICtfWzFdLCByZXNjYWxlKCkpIDogW3gwLCB4MV07CiAgICAgIH07CgogICAgICBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChuID0gKHJhbmdlID0gc2xpY2UkYy5jYWxsKF8pKS5sZW5ndGggLSAxLCByZXNjYWxlKCkpIDogcmFuZ2Uuc2xpY2UoKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmludmVydEV4dGVudCA9IGZ1bmN0aW9uKHkpIHsKICAgICAgICB2YXIgaSA9IHJhbmdlLmluZGV4T2YoeSk7CiAgICAgICAgcmV0dXJuIGkgPCAwID8gW05hTiwgTmFOXQogICAgICAgICAgICA6IGkgPCAxID8gW3gwLCBkb21haW5bMF1dCiAgICAgICAgICAgIDogaSA+PSBuID8gW2RvbWFpbltuIC0gMV0sIHgxXQogICAgICAgICAgICA6IFtkb21haW5baSAtIDFdLCBkb21haW5baV1dOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBxdWFudGl6ZSQzKCkKICAgICAgICAgICAgLmRvbWFpbihbeDAsIHgxXSkKICAgICAgICAgICAgLnJhbmdlKHJhbmdlKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5lYXJpc2gkMShzY2FsZSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGhyZXNob2xkJDMoKSB7CiAgICAgIHZhciBkb21haW4gPSBbMC41XSwKICAgICAgICAgIHJhbmdlID0gWzAsIDFdLAogICAgICAgICAgbiA9IDE7CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgaWYgKHggPD0geCkgcmV0dXJuIHJhbmdlW2Jpc2VjdFJpZ2h0JDIoZG9tYWluLCB4LCAwLCBuKV07CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkb21haW4gPSBzbGljZSRjLmNhbGwoXyksIG4gPSBNYXRoLm1pbihkb21haW4ubGVuZ3RoLCByYW5nZS5sZW5ndGggLSAxKSwgc2NhbGUpIDogZG9tYWluLnNsaWNlKCk7CiAgICAgIH07CgogICAgICBzY2FsZS5yYW5nZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChyYW5nZSA9IHNsaWNlJGMuY2FsbChfKSwgbiA9IE1hdGgubWluKGRvbWFpbi5sZW5ndGgsIHJhbmdlLmxlbmd0aCAtIDEpLCBzY2FsZSkgOiByYW5nZS5zbGljZSgpOwogICAgICB9OwoKICAgICAgc2NhbGUuaW52ZXJ0RXh0ZW50ID0gZnVuY3Rpb24oeSkgewogICAgICAgIHZhciBpID0gcmFuZ2UuaW5kZXhPZih5KTsKICAgICAgICByZXR1cm4gW2RvbWFpbltpIC0gMV0sIGRvbWFpbltpXV07CiAgICAgIH07CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRocmVzaG9sZCQzKCkKICAgICAgICAgICAgLmRvbWFpbihkb21haW4pCiAgICAgICAgICAgIC5yYW5nZShyYW5nZSk7CiAgICAgIH07CgogICAgICByZXR1cm4gc2NhbGU7CiAgICB9CgogICAgdmFyIHQwJDQgPSBuZXcgRGF0ZSwKICAgICAgICB0MSQ0ID0gbmV3IERhdGU7CgogICAgZnVuY3Rpb24gbmV3SW50ZXJ2YWwkMShmbG9vcmksIG9mZnNldGksIGNvdW50LCBmaWVsZCkgewoKICAgICAgZnVuY3Rpb24gaW50ZXJ2YWwoZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IGFyZ3VtZW50cy5sZW5ndGggPT09IDAgPyBuZXcgRGF0ZSA6IG5ldyBEYXRlKCtkYXRlKSksIGRhdGU7CiAgICAgIH0KCiAgICAgIGludGVydmFsLmZsb29yID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSksIGRhdGU7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5jZWlsID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKGRhdGUgLSAxKSksIG9mZnNldGkoZGF0ZSwgMSksIGZsb29yaShkYXRlKSwgZGF0ZTsKICAgICAgfTsKCiAgICAgIGludGVydmFsLnJvdW5kID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHZhciBkMCA9IGludGVydmFsKGRhdGUpLAogICAgICAgICAgICBkMSA9IGludGVydmFsLmNlaWwoZGF0ZSk7CiAgICAgICAgcmV0dXJuIGRhdGUgLSBkMCA8IGQxIC0gZGF0ZSA/IGQwIDogZDE7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5vZmZzZXQgPSBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgcmV0dXJuIG9mZnNldGkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSwgc3RlcCA9PSBudWxsID8gMSA6IE1hdGguZmxvb3Ioc3RlcCkpLCBkYXRlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwucmFuZ2UgPSBmdW5jdGlvbihzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICAgIHZhciByYW5nZSA9IFtdLCBwcmV2aW91czsKICAgICAgICBzdGFydCA9IGludGVydmFsLmNlaWwoc3RhcnQpOwogICAgICAgIHN0ZXAgPSBzdGVwID09IG51bGwgPyAxIDogTWF0aC5mbG9vcihzdGVwKTsKICAgICAgICBpZiAoIShzdGFydCA8IHN0b3ApIHx8ICEoc3RlcCA+IDApKSByZXR1cm4gcmFuZ2U7IC8vIGFsc28gaGFuZGxlcyBJbnZhbGlkIERhdGUKICAgICAgICBkbyByYW5nZS5wdXNoKHByZXZpb3VzID0gbmV3IERhdGUoK3N0YXJ0KSksIG9mZnNldGkoc3RhcnQsIHN0ZXApLCBmbG9vcmkoc3RhcnQpOwogICAgICAgIHdoaWxlIChwcmV2aW91cyA8IHN0YXJ0ICYmIHN0YXJ0IDwgc3RvcCk7CiAgICAgICAgcmV0dXJuIHJhbmdlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwuZmlsdGVyID0gZnVuY3Rpb24odGVzdCkgewogICAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHdoaWxlIChmbG9vcmkoZGF0ZSksICF0ZXN0KGRhdGUpKSBkYXRlLnNldFRpbWUoZGF0ZSAtIDEpOwogICAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHsKICAgICAgICAgICAgaWYgKHN0ZXAgPCAwKSB3aGlsZSAoKytzdGVwIDw9IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCAtMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0gZWxzZSB3aGlsZSAoLS1zdGVwID49IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCArMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIGlmIChjb3VudCkgewogICAgICAgIGludGVydmFsLmNvdW50ID0gZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgICAgdDAkNC5zZXRUaW1lKCtzdGFydCksIHQxJDQuc2V0VGltZSgrZW5kKTsKICAgICAgICAgIGZsb29yaSh0MCQ0KSwgZmxvb3JpKHQxJDQpOwogICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IoY291bnQodDAkNCwgdDEkNCkpOwogICAgICAgIH07CgogICAgICAgIGludGVydmFsLmV2ZXJ5ID0gZnVuY3Rpb24oc3RlcCkgewogICAgICAgICAgc3RlcCA9IE1hdGguZmxvb3Ioc3RlcCk7CiAgICAgICAgICByZXR1cm4gIWlzRmluaXRlKHN0ZXApIHx8ICEoc3RlcCA+IDApID8gbnVsbAogICAgICAgICAgICAgIDogIShzdGVwID4gMSkgPyBpbnRlcnZhbAogICAgICAgICAgICAgIDogaW50ZXJ2YWwuZmlsdGVyKGZpZWxkCiAgICAgICAgICAgICAgICAgID8gZnVuY3Rpb24oZCkgeyByZXR1cm4gZmllbGQoZCkgJSBzdGVwID09PSAwOyB9CiAgICAgICAgICAgICAgICAgIDogZnVuY3Rpb24oZCkgeyByZXR1cm4gaW50ZXJ2YWwuY291bnQoMCwgZCkgJSBzdGVwID09PSAwOyB9KTsKICAgICAgICB9OwogICAgICB9CgogICAgICByZXR1cm4gaW50ZXJ2YWw7CiAgICB9CgogICAgdmFyIG1pbGxpc2Vjb25kJDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKCkgewogICAgICAvLyBub29wCiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0VGltZSgrZGF0ZSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kIC0gc3RhcnQ7CiAgICB9KTsKCiAgICAvLyBBbiBvcHRpbWl6ZWQgaW1wbGVtZW50YXRpb24gZm9yIHRoaXMgc2ltcGxlIGNhc2UuCiAgICBtaWxsaXNlY29uZCQxLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICBrID0gTWF0aC5mbG9vcihrKTsKICAgICAgaWYgKCFpc0Zpbml0ZShrKSB8fCAhKGsgPiAwKSkgcmV0dXJuIG51bGw7CiAgICAgIGlmICghKGsgPiAxKSkgcmV0dXJuIG1pbGxpc2Vjb25kJDE7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFRpbWUoTWF0aC5mbG9vcihkYXRlIC8gaykgKiBrKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0VGltZSgrZGF0ZSArIHN0ZXAgKiBrKTsKICAgICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gazsKICAgICAgfSk7CiAgICB9OwoKICAgIHZhciBkdXJhdGlvblNlY29uZCQyID0gMWUzOwogICAgdmFyIGR1cmF0aW9uTWludXRlJDIgPSA2ZTQ7CiAgICB2YXIgZHVyYXRpb25Ib3VyJDIgPSAzNmU1OwogICAgdmFyIGR1cmF0aW9uRGF5JDIgPSA4NjRlNTsKICAgIHZhciBkdXJhdGlvbldlZWskMiA9IDYwNDhlNTsKCiAgICB2YXIgc2Vjb25kJDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRUaW1lKGRhdGUgLSBkYXRlLmdldE1pbGxpc2Vjb25kcygpKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGR1cmF0aW9uU2Vjb25kJDIpOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uU2Vjb25kJDI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ1NlY29uZHMoKTsKICAgIH0pOwoKICAgIHZhciBtaW51dGUkMSA9IG5ld0ludGVydmFsJDEoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFRpbWUoZGF0ZSAtIGRhdGUuZ2V0TWlsbGlzZWNvbmRzKCkgLSBkYXRlLmdldFNlY29uZHMoKSAqIGR1cmF0aW9uU2Vjb25kJDIpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25NaW51dGUkMik7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25NaW51dGUkMjsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0TWludXRlcygpOwogICAgfSk7CgogICAgdmFyIGhvdXIkMSA9IG5ld0ludGVydmFsJDEoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFRpbWUoZGF0ZSAtIGRhdGUuZ2V0TWlsbGlzZWNvbmRzKCkgLSBkYXRlLmdldFNlY29uZHMoKSAqIGR1cmF0aW9uU2Vjb25kJDIgLSBkYXRlLmdldE1pbnV0ZXMoKSAqIGR1cmF0aW9uTWludXRlJDIpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25Ib3VyJDIpOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uSG91ciQyOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRIb3VycygpOwogICAgfSk7CgogICAgdmFyIGRheSQxID0gbmV3SW50ZXJ2YWwkMShmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0SG91cnMoMCwgMCwgMCwgMCk7CiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0RGF0ZShkYXRlLmdldERhdGUoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0IC0gKGVuZC5nZXRUaW1lem9uZU9mZnNldCgpIC0gc3RhcnQuZ2V0VGltZXpvbmVPZmZzZXQoKSkgKiBkdXJhdGlvbk1pbnV0ZSQyKSAvIGR1cmF0aW9uRGF5JDI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldERhdGUoKSAtIDE7CiAgICB9KTsKCiAgICBmdW5jdGlvbiB3ZWVrZGF5JDEoaSkgewogICAgICByZXR1cm4gbmV3SW50ZXJ2YWwkMShmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgZGF0ZS5zZXREYXRlKGRhdGUuZ2V0RGF0ZSgpIC0gKGRhdGUuZ2V0RGF5KCkgKyA3IC0gaSkgJSA3KTsKICAgICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgZGF0ZS5zZXREYXRlKGRhdGUuZ2V0RGF0ZSgpICsgc3RlcCAqIDcpOwogICAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCAtIChlbmQuZ2V0VGltZXpvbmVPZmZzZXQoKSAtIHN0YXJ0LmdldFRpbWV6b25lT2Zmc2V0KCkpICogZHVyYXRpb25NaW51dGUkMikgLyBkdXJhdGlvbldlZWskMjsKICAgICAgfSk7CiAgICB9CgogICAgdmFyIHN1bmRheSQxID0gd2Vla2RheSQxKDApOwogICAgdmFyIG1vbmRheSQxID0gd2Vla2RheSQxKDEpOwogICAgdmFyIHR1ZXNkYXkkMSA9IHdlZWtkYXkkMSgyKTsKICAgIHZhciB3ZWRuZXNkYXkkMSA9IHdlZWtkYXkkMSgzKTsKICAgIHZhciB0aHVyc2RheSQxID0gd2Vla2RheSQxKDQpOwogICAgdmFyIGZyaWRheSQxID0gd2Vla2RheSQxKDUpOwogICAgdmFyIHNhdHVyZGF5JDEgPSB3ZWVrZGF5JDEoNik7CgogICAgdmFyIG1vbnRoJDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXREYXRlKDEpOwogICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldE1vbnRoKGRhdGUuZ2V0TW9udGgoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldE1vbnRoKCkgLSBzdGFydC5nZXRNb250aCgpICsgKGVuZC5nZXRGdWxsWWVhcigpIC0gc3RhcnQuZ2V0RnVsbFllYXIoKSkgKiAxMjsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0TW9udGgoKTsKICAgIH0pOwoKICAgIHZhciB5ZWFyJDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRNb250aCgwLCAxKTsKICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkYXRlLmdldEZ1bGxZZWFyKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRGdWxsWWVhcigpIC0gc3RhcnQuZ2V0RnVsbFllYXIoKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0RnVsbFllYXIoKTsKICAgIH0pOwoKICAgIC8vIEFuIG9wdGltaXplZCBpbXBsZW1lbnRhdGlvbiBmb3IgdGhpcyBzaW1wbGUgY2FzZS4KICAgIHllYXIkMS5ldmVyeSA9IGZ1bmN0aW9uKGspIHsKICAgICAgcmV0dXJuICFpc0Zpbml0ZShrID0gTWF0aC5mbG9vcihrKSkgfHwgIShrID4gMCkgPyBudWxsIDogbmV3SW50ZXJ2YWwkMShmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihNYXRoLmZsb29yKGRhdGUuZ2V0RnVsbFllYXIoKSAvIGspICogayk7CiAgICAgICAgZGF0ZS5zZXRNb250aCgwLCAxKTsKICAgICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkYXRlLmdldEZ1bGxZZWFyKCkgKyBzdGVwICogayk7CiAgICAgIH0pOwogICAgfTsKCiAgICB2YXIgdXRjTWludXRlJDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENTZWNvbmRzKDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25NaW51dGUkMik7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25NaW51dGUkMjsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDTWludXRlcygpOwogICAgfSk7CgogICAgdmFyIHV0Y0hvdXIkMSA9IG5ld0ludGVydmFsJDEoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFVUQ01pbnV0ZXMoMCwgMCwgMCk7CiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0VGltZSgrZGF0ZSArIHN0ZXAgKiBkdXJhdGlvbkhvdXIkMik7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25Ib3VyJDI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ0hvdXJzKCk7CiAgICB9KTsKCiAgICB2YXIgdXRjRGF5JDEgPSBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENEYXRlKGRhdGUuZ2V0VVRDRGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25EYXkkMjsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDRGF0ZSgpIC0gMTsKICAgIH0pOwoKICAgIGZ1bmN0aW9uIHV0Y1dlZWtkYXkkMShpKSB7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgLSAoZGF0ZS5nZXRVVENEYXkoKSArIDcgLSBpKSAlIDcpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgKyBzdGVwICogNyk7CiAgICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uV2VlayQyOwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgdXRjU3VuZGF5JDEgPSB1dGNXZWVrZGF5JDEoMCk7CiAgICB2YXIgdXRjTW9uZGF5JDEgPSB1dGNXZWVrZGF5JDEoMSk7CiAgICB2YXIgdXRjVHVlc2RheSQxID0gdXRjV2Vla2RheSQxKDIpOwogICAgdmFyIHV0Y1dlZG5lc2RheSQxID0gdXRjV2Vla2RheSQxKDMpOwogICAgdmFyIHV0Y1RodXJzZGF5JDEgPSB1dGNXZWVrZGF5JDEoNCk7CiAgICB2YXIgdXRjRnJpZGF5JDEgPSB1dGNXZWVrZGF5JDEoNSk7CiAgICB2YXIgdXRjU2F0dXJkYXkkMSA9IHV0Y1dlZWtkYXkkMSg2KTsKCiAgICB2YXIgdXRjTW9udGgkMSA9IG5ld0ludGVydmFsJDEoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFVUQ0RhdGUoMSk7CiAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0VVRDTW9udGgoZGF0ZS5nZXRVVENNb250aCgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiBlbmQuZ2V0VVRDTW9udGgoKSAtIHN0YXJ0LmdldFVUQ01vbnRoKCkgKyAoZW5kLmdldFVUQ0Z1bGxZZWFyKCkgLSBzdGFydC5nZXRVVENGdWxsWWVhcigpKSAqIDEyOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRVVENNb250aCgpOwogICAgfSk7CgogICAgdmFyIHV0Y1llYXIkMSA9IG5ld0ludGVydmFsJDEoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFVUQ01vbnRoKDAsIDEpOwogICAgICBkYXRlLnNldFVUQ0hvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldFVUQ0Z1bGxZZWFyKCkgLSBzdGFydC5nZXRVVENGdWxsWWVhcigpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRVVENGdWxsWWVhcigpOwogICAgfSk7CgogICAgLy8gQW4gb3B0aW1pemVkIGltcGxlbWVudGF0aW9uIGZvciB0aGlzIHNpbXBsZSBjYXNlLgogICAgdXRjWWVhciQxLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICByZXR1cm4gIWlzRmluaXRlKGsgPSBNYXRoLmZsb29yKGspKSB8fCAhKGsgPiAwKSA/IG51bGwgOiBuZXdJbnRlcnZhbCQxKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKE1hdGguZmxvb3IoZGF0ZS5nZXRVVENGdWxsWWVhcigpIC8gaykgKiBrKTsKICAgICAgICBkYXRlLnNldFVUQ01vbnRoKDAsIDEpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSArIHN0ZXAgKiBrKTsKICAgICAgfSk7CiAgICB9OwoKICAgIGZ1bmN0aW9uIGxvY2FsRGF0ZSQxKGQpIHsKICAgICAgaWYgKDAgPD0gZC55ICYmIGQueSA8IDEwMCkgewogICAgICAgIHZhciBkYXRlID0gbmV3IERhdGUoLTEsIGQubSwgZC5kLCBkLkgsIGQuTSwgZC5TLCBkLkwpOwogICAgICAgIGRhdGUuc2V0RnVsbFllYXIoZC55KTsKICAgICAgICByZXR1cm4gZGF0ZTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERhdGUoZC55LCBkLm0sIGQuZCwgZC5ILCBkLk0sIGQuUywgZC5MKTsKICAgIH0KCiAgICBmdW5jdGlvbiB1dGNEYXRlJDEoZCkgewogICAgICBpZiAoMCA8PSBkLnkgJiYgZC55IDwgMTAwKSB7CiAgICAgICAgdmFyIGRhdGUgPSBuZXcgRGF0ZShEYXRlLlVUQygtMSwgZC5tLCBkLmQsIGQuSCwgZC5NLCBkLlMsIGQuTCkpOwogICAgICAgIGRhdGUuc2V0VVRDRnVsbFllYXIoZC55KTsKICAgICAgICByZXR1cm4gZGF0ZTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERhdGUoRGF0ZS5VVEMoZC55LCBkLm0sIGQuZCwgZC5ILCBkLk0sIGQuUywgZC5MKSk7CiAgICB9CgogICAgZnVuY3Rpb24gbmV3RGF0ZSQxKHksIG0sIGQpIHsKICAgICAgcmV0dXJuIHt5OiB5LCBtOiBtLCBkOiBkLCBIOiAwLCBNOiAwLCBTOiAwLCBMOiAwfTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRMb2NhbGUkNChsb2NhbGUpIHsKICAgICAgdmFyIGxvY2FsZV9kYXRlVGltZSA9IGxvY2FsZS5kYXRlVGltZSwKICAgICAgICAgIGxvY2FsZV9kYXRlID0gbG9jYWxlLmRhdGUsCiAgICAgICAgICBsb2NhbGVfdGltZSA9IGxvY2FsZS50aW1lLAogICAgICAgICAgbG9jYWxlX3BlcmlvZHMgPSBsb2NhbGUucGVyaW9kcywKICAgICAgICAgIGxvY2FsZV93ZWVrZGF5cyA9IGxvY2FsZS5kYXlzLAogICAgICAgICAgbG9jYWxlX3Nob3J0V2Vla2RheXMgPSBsb2NhbGUuc2hvcnREYXlzLAogICAgICAgICAgbG9jYWxlX21vbnRocyA9IGxvY2FsZS5tb250aHMsCiAgICAgICAgICBsb2NhbGVfc2hvcnRNb250aHMgPSBsb2NhbGUuc2hvcnRNb250aHM7CgogICAgICB2YXIgcGVyaW9kUmUgPSBmb3JtYXRSZSQxKGxvY2FsZV9wZXJpb2RzKSwKICAgICAgICAgIHBlcmlvZExvb2t1cCA9IGZvcm1hdExvb2t1cCQxKGxvY2FsZV9wZXJpb2RzKSwKICAgICAgICAgIHdlZWtkYXlSZSA9IGZvcm1hdFJlJDEobG9jYWxlX3dlZWtkYXlzKSwKICAgICAgICAgIHdlZWtkYXlMb29rdXAgPSBmb3JtYXRMb29rdXAkMShsb2NhbGVfd2Vla2RheXMpLAogICAgICAgICAgc2hvcnRXZWVrZGF5UmUgPSBmb3JtYXRSZSQxKGxvY2FsZV9zaG9ydFdlZWtkYXlzKSwKICAgICAgICAgIHNob3J0V2Vla2RheUxvb2t1cCA9IGZvcm1hdExvb2t1cCQxKGxvY2FsZV9zaG9ydFdlZWtkYXlzKSwKICAgICAgICAgIG1vbnRoUmUgPSBmb3JtYXRSZSQxKGxvY2FsZV9tb250aHMpLAogICAgICAgICAgbW9udGhMb29rdXAgPSBmb3JtYXRMb29rdXAkMShsb2NhbGVfbW9udGhzKSwKICAgICAgICAgIHNob3J0TW9udGhSZSA9IGZvcm1hdFJlJDEobG9jYWxlX3Nob3J0TW9udGhzKSwKICAgICAgICAgIHNob3J0TW9udGhMb29rdXAgPSBmb3JtYXRMb29rdXAkMShsb2NhbGVfc2hvcnRNb250aHMpOwoKICAgICAgdmFyIGZvcm1hdHMgPSB7CiAgICAgICAgImEiOiBmb3JtYXRTaG9ydFdlZWtkYXksCiAgICAgICAgIkEiOiBmb3JtYXRXZWVrZGF5LAogICAgICAgICJiIjogZm9ybWF0U2hvcnRNb250aCwKICAgICAgICAiQiI6IGZvcm1hdE1vbnRoLAogICAgICAgICJjIjogbnVsbCwKICAgICAgICAiZCI6IGZvcm1hdERheU9mTW9udGgkMSwKICAgICAgICAiZSI6IGZvcm1hdERheU9mTW9udGgkMSwKICAgICAgICAiZiI6IGZvcm1hdE1pY3Jvc2Vjb25kcyQxLAogICAgICAgICJIIjogZm9ybWF0SG91cjI0JDEsCiAgICAgICAgIkkiOiBmb3JtYXRIb3VyMTIkMSwKICAgICAgICAiaiI6IGZvcm1hdERheU9mWWVhciQxLAogICAgICAgICJMIjogZm9ybWF0TWlsbGlzZWNvbmRzJDEsCiAgICAgICAgIm0iOiBmb3JtYXRNb250aE51bWJlciQxLAogICAgICAgICJNIjogZm9ybWF0TWludXRlcyQxLAogICAgICAgICJwIjogZm9ybWF0UGVyaW9kLAogICAgICAgICJxIjogZm9ybWF0UXVhcnRlciwKICAgICAgICAiUSI6IGZvcm1hdFVuaXhUaW1lc3RhbXAkMSwKICAgICAgICAicyI6IGZvcm1hdFVuaXhUaW1lc3RhbXBTZWNvbmRzJDEsCiAgICAgICAgIlMiOiBmb3JtYXRTZWNvbmRzJDEsCiAgICAgICAgInUiOiBmb3JtYXRXZWVrZGF5TnVtYmVyTW9uZGF5JDEsCiAgICAgICAgIlUiOiBmb3JtYXRXZWVrTnVtYmVyU3VuZGF5JDEsCiAgICAgICAgIlYiOiBmb3JtYXRXZWVrTnVtYmVySVNPJDEsCiAgICAgICAgInciOiBmb3JtYXRXZWVrZGF5TnVtYmVyU3VuZGF5JDEsCiAgICAgICAgIlciOiBmb3JtYXRXZWVrTnVtYmVyTW9uZGF5JDEsCiAgICAgICAgIngiOiBudWxsLAogICAgICAgICJYIjogbnVsbCwKICAgICAgICAieSI6IGZvcm1hdFllYXIkMiwKICAgICAgICAiWSI6IGZvcm1hdEZ1bGxZZWFyJDEsCiAgICAgICAgIloiOiBmb3JtYXRab25lJDEsCiAgICAgICAgIiUiOiBmb3JtYXRMaXRlcmFsUGVyY2VudCQxCiAgICAgIH07CgogICAgICB2YXIgdXRjRm9ybWF0cyA9IHsKICAgICAgICAiYSI6IGZvcm1hdFVUQ1Nob3J0V2Vla2RheSwKICAgICAgICAiQSI6IGZvcm1hdFVUQ1dlZWtkYXksCiAgICAgICAgImIiOiBmb3JtYXRVVENTaG9ydE1vbnRoLAogICAgICAgICJCIjogZm9ybWF0VVRDTW9udGgsCiAgICAgICAgImMiOiBudWxsLAogICAgICAgICJkIjogZm9ybWF0VVRDRGF5T2ZNb250aCQxLAogICAgICAgICJlIjogZm9ybWF0VVRDRGF5T2ZNb250aCQxLAogICAgICAgICJmIjogZm9ybWF0VVRDTWljcm9zZWNvbmRzJDEsCiAgICAgICAgIkgiOiBmb3JtYXRVVENIb3VyMjQkMSwKICAgICAgICAiSSI6IGZvcm1hdFVUQ0hvdXIxMiQxLAogICAgICAgICJqIjogZm9ybWF0VVRDRGF5T2ZZZWFyJDEsCiAgICAgICAgIkwiOiBmb3JtYXRVVENNaWxsaXNlY29uZHMkMSwKICAgICAgICAibSI6IGZvcm1hdFVUQ01vbnRoTnVtYmVyJDEsCiAgICAgICAgIk0iOiBmb3JtYXRVVENNaW51dGVzJDEsCiAgICAgICAgInAiOiBmb3JtYXRVVENQZXJpb2QsCiAgICAgICAgInEiOiBmb3JtYXRVVENRdWFydGVyLAogICAgICAgICJRIjogZm9ybWF0VW5peFRpbWVzdGFtcCQxLAogICAgICAgICJzIjogZm9ybWF0VW5peFRpbWVzdGFtcFNlY29uZHMkMSwKICAgICAgICAiUyI6IGZvcm1hdFVUQ1NlY29uZHMkMSwKICAgICAgICAidSI6IGZvcm1hdFVUQ1dlZWtkYXlOdW1iZXJNb25kYXkkMSwKICAgICAgICAiVSI6IGZvcm1hdFVUQ1dlZWtOdW1iZXJTdW5kYXkkMSwKICAgICAgICAiViI6IGZvcm1hdFVUQ1dlZWtOdW1iZXJJU08kMSwKICAgICAgICAidyI6IGZvcm1hdFVUQ1dlZWtkYXlOdW1iZXJTdW5kYXkkMSwKICAgICAgICAiVyI6IGZvcm1hdFVUQ1dlZWtOdW1iZXJNb25kYXkkMSwKICAgICAgICAieCI6IG51bGwsCiAgICAgICAgIlgiOiBudWxsLAogICAgICAgICJ5IjogZm9ybWF0VVRDWWVhciQxLAogICAgICAgICJZIjogZm9ybWF0VVRDRnVsbFllYXIkMSwKICAgICAgICAiWiI6IGZvcm1hdFVUQ1pvbmUkMSwKICAgICAgICAiJSI6IGZvcm1hdExpdGVyYWxQZXJjZW50JDEKICAgICAgfTsKCiAgICAgIHZhciBwYXJzZXMgPSB7CiAgICAgICAgImEiOiBwYXJzZVNob3J0V2Vla2RheSwKICAgICAgICAiQSI6IHBhcnNlV2Vla2RheSwKICAgICAgICAiYiI6IHBhcnNlU2hvcnRNb250aCwKICAgICAgICAiQiI6IHBhcnNlTW9udGgsCiAgICAgICAgImMiOiBwYXJzZUxvY2FsZURhdGVUaW1lLAogICAgICAgICJkIjogcGFyc2VEYXlPZk1vbnRoJDEsCiAgICAgICAgImUiOiBwYXJzZURheU9mTW9udGgkMSwKICAgICAgICAiZiI6IHBhcnNlTWljcm9zZWNvbmRzJDEsCiAgICAgICAgIkgiOiBwYXJzZUhvdXIyNCQxLAogICAgICAgICJJIjogcGFyc2VIb3VyMjQkMSwKICAgICAgICAiaiI6IHBhcnNlRGF5T2ZZZWFyJDEsCiAgICAgICAgIkwiOiBwYXJzZU1pbGxpc2Vjb25kcyQxLAogICAgICAgICJtIjogcGFyc2VNb250aE51bWJlciQxLAogICAgICAgICJNIjogcGFyc2VNaW51dGVzJDEsCiAgICAgICAgInAiOiBwYXJzZVBlcmlvZCwKICAgICAgICAicSI6IHBhcnNlUXVhcnRlciQxLAogICAgICAgICJRIjogcGFyc2VVbml4VGltZXN0YW1wJDEsCiAgICAgICAgInMiOiBwYXJzZVVuaXhUaW1lc3RhbXBTZWNvbmRzJDEsCiAgICAgICAgIlMiOiBwYXJzZVNlY29uZHMkMSwKICAgICAgICAidSI6IHBhcnNlV2Vla2RheU51bWJlck1vbmRheSQxLAogICAgICAgICJVIjogcGFyc2VXZWVrTnVtYmVyU3VuZGF5JDEsCiAgICAgICAgIlYiOiBwYXJzZVdlZWtOdW1iZXJJU08kMSwKICAgICAgICAidyI6IHBhcnNlV2Vla2RheU51bWJlclN1bmRheSQxLAogICAgICAgICJXIjogcGFyc2VXZWVrTnVtYmVyTW9uZGF5JDEsCiAgICAgICAgIngiOiBwYXJzZUxvY2FsZURhdGUsCiAgICAgICAgIlgiOiBwYXJzZUxvY2FsZVRpbWUsCiAgICAgICAgInkiOiBwYXJzZVllYXIkMSwKICAgICAgICAiWSI6IHBhcnNlRnVsbFllYXIkMSwKICAgICAgICAiWiI6IHBhcnNlWm9uZSQxLAogICAgICAgICIlIjogcGFyc2VMaXRlcmFsUGVyY2VudCQxCiAgICAgIH07CgogICAgICAvLyBUaGVzZSByZWN1cnNpdmUgZGlyZWN0aXZlIGRlZmluaXRpb25zIG11c3QgYmUgZGVmZXJyZWQuCiAgICAgIGZvcm1hdHMueCA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZSwgZm9ybWF0cyk7CiAgICAgIGZvcm1hdHMuWCA9IG5ld0Zvcm1hdChsb2NhbGVfdGltZSwgZm9ybWF0cyk7CiAgICAgIGZvcm1hdHMuYyA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZVRpbWUsIGZvcm1hdHMpOwogICAgICB1dGNGb3JtYXRzLnggPSBuZXdGb3JtYXQobG9jYWxlX2RhdGUsIHV0Y0Zvcm1hdHMpOwogICAgICB1dGNGb3JtYXRzLlggPSBuZXdGb3JtYXQobG9jYWxlX3RpbWUsIHV0Y0Zvcm1hdHMpOwogICAgICB1dGNGb3JtYXRzLmMgPSBuZXdGb3JtYXQobG9jYWxlX2RhdGVUaW1lLCB1dGNGb3JtYXRzKTsKCiAgICAgIGZ1bmN0aW9uIG5ld0Zvcm1hdChzcGVjaWZpZXIsIGZvcm1hdHMpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgICAgdmFyIHN0cmluZyA9IFtdLAogICAgICAgICAgICAgIGkgPSAtMSwKICAgICAgICAgICAgICBqID0gMCwKICAgICAgICAgICAgICBuID0gc3BlY2lmaWVyLmxlbmd0aCwKICAgICAgICAgICAgICBjLAogICAgICAgICAgICAgIHBhZCwKICAgICAgICAgICAgICBmb3JtYXQ7CgogICAgICAgICAgaWYgKCEoZGF0ZSBpbnN0YW5jZW9mIERhdGUpKSBkYXRlID0gbmV3IERhdGUoK2RhdGUpOwoKICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICAgIGlmIChzcGVjaWZpZXIuY2hhckNvZGVBdChpKSA9PT0gMzcpIHsKICAgICAgICAgICAgICBzdHJpbmcucHVzaChzcGVjaWZpZXIuc2xpY2UoaiwgaSkpOwogICAgICAgICAgICAgIGlmICgocGFkID0gcGFkcyQxW2MgPSBzcGVjaWZpZXIuY2hhckF0KCsraSldKSAhPSBudWxsKSBjID0gc3BlY2lmaWVyLmNoYXJBdCgrK2kpOwogICAgICAgICAgICAgIGVsc2UgcGFkID0gYyA9PT0gImUiID8gIiAiIDogIjAiOwogICAgICAgICAgICAgIGlmIChmb3JtYXQgPSBmb3JtYXRzW2NdKSBjID0gZm9ybWF0KGRhdGUsIHBhZCk7CiAgICAgICAgICAgICAgc3RyaW5nLnB1c2goYyk7CiAgICAgICAgICAgICAgaiA9IGkgKyAxOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgc3RyaW5nLnB1c2goc3BlY2lmaWVyLnNsaWNlKGosIGkpKTsKICAgICAgICAgIHJldHVybiBzdHJpbmcuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gbmV3UGFyc2Uoc3BlY2lmaWVyLCBaKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0cmluZykgewogICAgICAgICAgdmFyIGQgPSBuZXdEYXRlJDEoMTkwMCwgdW5kZWZpbmVkLCAxKSwKICAgICAgICAgICAgICBpID0gcGFyc2VTcGVjaWZpZXIoZCwgc3BlY2lmaWVyLCBzdHJpbmcgKz0gIiIsIDApLAogICAgICAgICAgICAgIHdlZWssIGRheTsKICAgICAgICAgIGlmIChpICE9IHN0cmluZy5sZW5ndGgpIHJldHVybiBudWxsOwoKICAgICAgICAgIC8vIElmIGEgVU5JWCB0aW1lc3RhbXAgaXMgc3BlY2lmaWVkLCByZXR1cm4gaXQuCiAgICAgICAgICBpZiAoIlEiIGluIGQpIHJldHVybiBuZXcgRGF0ZShkLlEpOwogICAgICAgICAgaWYgKCJzIiBpbiBkKSByZXR1cm4gbmV3IERhdGUoZC5zICogMTAwMCArICgiTCIgaW4gZCA/IGQuTCA6IDApKTsKCiAgICAgICAgICAvLyBJZiB0aGlzIGlzIHV0Y1BhcnNlLCBuZXZlciB1c2UgdGhlIGxvY2FsIHRpbWV6b25lLgogICAgICAgICAgaWYgKFogJiYgISgiWiIgaW4gZCkpIGQuWiA9IDA7CgogICAgICAgICAgLy8gVGhlIGFtLXBtIGZsYWcgaXMgMCBmb3IgQU0sIGFuZCAxIGZvciBQTS4KICAgICAgICAgIGlmICgicCIgaW4gZCkgZC5IID0gZC5IICUgMTIgKyBkLnAgKiAxMjsKCiAgICAgICAgICAvLyBJZiB0aGUgbW9udGggd2FzIG5vdCBzcGVjaWZpZWQsIGluaGVyaXQgZnJvbSB0aGUgcXVhcnRlci4KICAgICAgICAgIGlmIChkLm0gPT09IHVuZGVmaW5lZCkgZC5tID0gInEiIGluIGQgPyBkLnEgOiAwOwoKICAgICAgICAgIC8vIENvbnZlcnQgZGF5LW9mLXdlZWsgYW5kIHdlZWstb2YteWVhciB0byBkYXktb2YteWVhci4KICAgICAgICAgIGlmICgiViIgaW4gZCkgewogICAgICAgICAgICBpZiAoZC5WIDwgMSB8fCBkLlYgPiA1MykgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIGlmICghKCJ3IiBpbiBkKSkgZC53ID0gMTsKICAgICAgICAgICAgaWYgKCJaIiBpbiBkKSB7CiAgICAgICAgICAgICAgd2VlayA9IHV0Y0RhdGUkMShuZXdEYXRlJDEoZC55LCAwLCAxKSksIGRheSA9IHdlZWsuZ2V0VVRDRGF5KCk7CiAgICAgICAgICAgICAgd2VlayA9IGRheSA+IDQgfHwgZGF5ID09PSAwID8gdXRjTW9uZGF5JDEuY2VpbCh3ZWVrKSA6IHV0Y01vbmRheSQxKHdlZWspOwogICAgICAgICAgICAgIHdlZWsgPSB1dGNEYXkkMS5vZmZzZXQod2VlaywgKGQuViAtIDEpICogNyk7CiAgICAgICAgICAgICAgZC55ID0gd2Vlay5nZXRVVENGdWxsWWVhcigpOwogICAgICAgICAgICAgIGQubSA9IHdlZWsuZ2V0VVRDTW9udGgoKTsKICAgICAgICAgICAgICBkLmQgPSB3ZWVrLmdldFVUQ0RhdGUoKSArIChkLncgKyA2KSAlIDc7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgd2VlayA9IGxvY2FsRGF0ZSQxKG5ld0RhdGUkMShkLnksIDAsIDEpKSwgZGF5ID0gd2Vlay5nZXREYXkoKTsKICAgICAgICAgICAgICB3ZWVrID0gZGF5ID4gNCB8fCBkYXkgPT09IDAgPyBtb25kYXkkMS5jZWlsKHdlZWspIDogbW9uZGF5JDEod2Vlayk7CiAgICAgICAgICAgICAgd2VlayA9IGRheSQxLm9mZnNldCh3ZWVrLCAoZC5WIC0gMSkgKiA3KTsKICAgICAgICAgICAgICBkLnkgPSB3ZWVrLmdldEZ1bGxZZWFyKCk7CiAgICAgICAgICAgICAgZC5tID0gd2Vlay5nZXRNb250aCgpOwogICAgICAgICAgICAgIGQuZCA9IHdlZWsuZ2V0RGF0ZSgpICsgKGQudyArIDYpICUgNzsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIGlmICgiVyIgaW4gZCB8fCAiVSIgaW4gZCkgewogICAgICAgICAgICBpZiAoISgidyIgaW4gZCkpIGQudyA9ICJ1IiBpbiBkID8gZC51ICUgNyA6ICJXIiBpbiBkID8gMSA6IDA7CiAgICAgICAgICAgIGRheSA9ICJaIiBpbiBkID8gdXRjRGF0ZSQxKG5ld0RhdGUkMShkLnksIDAsIDEpKS5nZXRVVENEYXkoKSA6IGxvY2FsRGF0ZSQxKG5ld0RhdGUkMShkLnksIDAsIDEpKS5nZXREYXkoKTsKICAgICAgICAgICAgZC5tID0gMDsKICAgICAgICAgICAgZC5kID0gIlciIGluIGQgPyAoZC53ICsgNikgJSA3ICsgZC5XICogNyAtIChkYXkgKyA1KSAlIDcgOiBkLncgKyBkLlUgKiA3IC0gKGRheSArIDYpICUgNzsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBJZiBhIHRpbWUgem9uZSBpcyBzcGVjaWZpZWQsIGFsbCBmaWVsZHMgYXJlIGludGVycHJldGVkIGFzIFVUQyBhbmQgdGhlbgogICAgICAgICAgLy8gb2Zmc2V0IGFjY29yZGluZyB0byB0aGUgc3BlY2lmaWVkIHRpbWUgem9uZS4KICAgICAgICAgIGlmICgiWiIgaW4gZCkgewogICAgICAgICAgICBkLkggKz0gZC5aIC8gMTAwIHwgMDsKICAgICAgICAgICAgZC5NICs9IGQuWiAlIDEwMDsKICAgICAgICAgICAgcmV0dXJuIHV0Y0RhdGUkMShkKTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBPdGhlcndpc2UsIGFsbCBmaWVsZHMgYXJlIGluIGxvY2FsIHRpbWUuCiAgICAgICAgICByZXR1cm4gbG9jYWxEYXRlJDEoZCk7CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VTcGVjaWZpZXIoZCwgc3BlY2lmaWVyLCBzdHJpbmcsIGopIHsKICAgICAgICB2YXIgaSA9IDAsCiAgICAgICAgICAgIG4gPSBzcGVjaWZpZXIubGVuZ3RoLAogICAgICAgICAgICBtID0gc3RyaW5nLmxlbmd0aCwKICAgICAgICAgICAgYywKICAgICAgICAgICAgcGFyc2U7CgogICAgICAgIHdoaWxlIChpIDwgbikgewogICAgICAgICAgaWYgKGogPj0gbSkgcmV0dXJuIC0xOwogICAgICAgICAgYyA9IHNwZWNpZmllci5jaGFyQ29kZUF0KGkrKyk7CiAgICAgICAgICBpZiAoYyA9PT0gMzcpIHsKICAgICAgICAgICAgYyA9IHNwZWNpZmllci5jaGFyQXQoaSsrKTsKICAgICAgICAgICAgcGFyc2UgPSBwYXJzZXNbYyBpbiBwYWRzJDEgPyBzcGVjaWZpZXIuY2hhckF0KGkrKykgOiBjXTsKICAgICAgICAgICAgaWYgKCFwYXJzZSB8fCAoKGogPSBwYXJzZShkLCBzdHJpbmcsIGopKSA8IDApKSByZXR1cm4gLTE7CiAgICAgICAgICB9IGVsc2UgaWYgKGMgIT0gc3RyaW5nLmNoYXJDb2RlQXQoaisrKSkgewogICAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gajsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VQZXJpb2QoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgdmFyIG4gPSBwZXJpb2RSZS5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgICAgcmV0dXJuIG4gPyAoZC5wID0gcGVyaW9kTG9va3VwW25bMF0udG9Mb3dlckNhc2UoKV0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VTaG9ydFdlZWtkYXkoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgdmFyIG4gPSBzaG9ydFdlZWtkYXlSZS5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgICAgcmV0dXJuIG4gPyAoZC53ID0gc2hvcnRXZWVrZGF5TG9va3VwW25bMF0udG9Mb3dlckNhc2UoKV0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VXZWVrZGF5KGQsIHN0cmluZywgaSkgewogICAgICAgIHZhciBuID0gd2Vla2RheVJlLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgICByZXR1cm4gbiA/IChkLncgPSB3ZWVrZGF5TG9va3VwW25bMF0udG9Mb3dlckNhc2UoKV0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VTaG9ydE1vbnRoKGQsIHN0cmluZywgaSkgewogICAgICAgIHZhciBuID0gc2hvcnRNb250aFJlLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgICByZXR1cm4gbiA/IChkLm0gPSBzaG9ydE1vbnRoTG9va3VwW25bMF0udG9Mb3dlckNhc2UoKV0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VNb250aChkLCBzdHJpbmcsIGkpIHsKICAgICAgICB2YXIgbiA9IG1vbnRoUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICAgIHJldHVybiBuID8gKGQubSA9IG1vbnRoTG9va3VwW25bMF0udG9Mb3dlckNhc2UoKV0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VMb2NhbGVEYXRlVGltZShkLCBzdHJpbmcsIGkpIHsKICAgICAgICByZXR1cm4gcGFyc2VTcGVjaWZpZXIoZCwgbG9jYWxlX2RhdGVUaW1lLCBzdHJpbmcsIGkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZUxvY2FsZURhdGUoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgcmV0dXJuIHBhcnNlU3BlY2lmaWVyKGQsIGxvY2FsZV9kYXRlLCBzdHJpbmcsIGkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBwYXJzZUxvY2FsZVRpbWUoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgcmV0dXJuIHBhcnNlU3BlY2lmaWVyKGQsIGxvY2FsZV90aW1lLCBzdHJpbmcsIGkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRTaG9ydFdlZWtkYXkoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfc2hvcnRXZWVrZGF5c1tkLmdldERheSgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0V2Vla2RheShkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV93ZWVrZGF5c1tkLmdldERheSgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0U2hvcnRNb250aChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9zaG9ydE1vbnRoc1tkLmdldE1vbnRoKCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRNb250aChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9tb250aHNbZC5nZXRNb250aCgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0UGVyaW9kKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3BlcmlvZHNbKyhkLmdldEhvdXJzKCkgPj0gMTIpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0UXVhcnRlcihkKSB7CiAgICAgICAgcmV0dXJuIDEgKyB+fihkLmdldE1vbnRoKCkgLyAzKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDU2hvcnRXZWVrZGF5KGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3Nob3J0V2Vla2RheXNbZC5nZXRVVENEYXkoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1dlZWtkYXkoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfd2Vla2RheXNbZC5nZXRVVENEYXkoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1Nob3J0TW9udGgoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfc2hvcnRNb250aHNbZC5nZXRVVENNb250aCgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0VVRDTW9udGgoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfbW9udGhzW2QuZ2V0VVRDTW9udGgoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1BlcmlvZChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9wZXJpb2RzWysoZC5nZXRVVENIb3VycygpID49IDEyKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1F1YXJ0ZXIoZCkgewogICAgICAgIHJldHVybiAxICsgfn4oZC5nZXRVVENNb250aCgpIC8gMyk7CiAgICAgIH0KCiAgICAgIHJldHVybiB7CiAgICAgICAgZm9ybWF0OiBmdW5jdGlvbihzcGVjaWZpZXIpIHsKICAgICAgICAgIHZhciBmID0gbmV3Rm9ybWF0KHNwZWNpZmllciArPSAiIiwgZm9ybWF0cyk7CiAgICAgICAgICBmLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7IHJldHVybiBzcGVjaWZpZXI7IH07CiAgICAgICAgICByZXR1cm4gZjsKICAgICAgICB9LAogICAgICAgIHBhcnNlOiBmdW5jdGlvbihzcGVjaWZpZXIpIHsKICAgICAgICAgIHZhciBwID0gbmV3UGFyc2Uoc3BlY2lmaWVyICs9ICIiLCBmYWxzZSk7CiAgICAgICAgICBwLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7IHJldHVybiBzcGVjaWZpZXI7IH07CiAgICAgICAgICByZXR1cm4gcDsKICAgICAgICB9LAogICAgICAgIHV0Y0Zvcm1hdDogZnVuY3Rpb24oc3BlY2lmaWVyKSB7CiAgICAgICAgICB2YXIgZiA9IG5ld0Zvcm1hdChzcGVjaWZpZXIgKz0gIiIsIHV0Y0Zvcm1hdHMpOwogICAgICAgICAgZi50b1N0cmluZyA9IGZ1bmN0aW9uKCkgeyByZXR1cm4gc3BlY2lmaWVyOyB9OwogICAgICAgICAgcmV0dXJuIGY7CiAgICAgICAgfSwKICAgICAgICB1dGNQYXJzZTogZnVuY3Rpb24oc3BlY2lmaWVyKSB7CiAgICAgICAgICB2YXIgcCA9IG5ld1BhcnNlKHNwZWNpZmllciArPSAiIiwgdHJ1ZSk7CiAgICAgICAgICBwLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7IHJldHVybiBzcGVjaWZpZXI7IH07CiAgICAgICAgICByZXR1cm4gcDsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgdmFyIHBhZHMkMSA9IHsiLSI6ICIiLCAiXyI6ICIgIiwgIjAiOiAiMCJ9LAogICAgICAgIG51bWJlclJlJDEgPSAvXlxzKlxkKy8sIC8vIG5vdGU6IGlnbm9yZXMgbmV4dCBkaXJlY3RpdmUKICAgICAgICBwZXJjZW50UmUkMSA9IC9eJS8sCiAgICAgICAgcmVxdW90ZVJlJDEgPSAvW1xcXiQqKz98W1xdKCkue31dL2c7CgogICAgZnVuY3Rpb24gcGFkJDIodmFsdWUsIGZpbGwsIHdpZHRoKSB7CiAgICAgIHZhciBzaWduID0gdmFsdWUgPCAwID8gIi0iIDogIiIsCiAgICAgICAgICBzdHJpbmcgPSAoc2lnbiA/IC12YWx1ZSA6IHZhbHVlKSArICIiLAogICAgICAgICAgbGVuZ3RoID0gc3RyaW5nLmxlbmd0aDsKICAgICAgcmV0dXJuIHNpZ24gKyAobGVuZ3RoIDwgd2lkdGggPyBuZXcgQXJyYXkod2lkdGggLSBsZW5ndGggKyAxKS5qb2luKGZpbGwpICsgc3RyaW5nIDogc3RyaW5nKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXF1b3RlJDEocykgewogICAgICByZXR1cm4gcy5yZXBsYWNlKHJlcXVvdGVSZSQxLCAiXFwkJiIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFJlJDEobmFtZXMpIHsKICAgICAgcmV0dXJuIG5ldyBSZWdFeHAoIl4oPzoiICsgbmFtZXMubWFwKHJlcXVvdGUkMSkuam9pbigifCIpICsgIikiLCAiaSIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdExvb2t1cCQxKG5hbWVzKSB7CiAgICAgIHZhciBtYXAgPSB7fSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbWFwW25hbWVzW2ldLnRvTG93ZXJDYXNlKCldID0gaTsKICAgICAgcmV0dXJuIG1hcDsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVdlZWtkYXlOdW1iZXJTdW5kYXkkMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQxLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAxKSk7CiAgICAgIHJldHVybiBuID8gKGQudyA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VXZWVrZGF5TnVtYmVyTW9uZGF5JDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IChkLnUgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla051bWJlclN1bmRheSQxKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDEuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5VID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVdlZWtOdW1iZXJJU08kMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQxLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAyKSk7CiAgICAgIHJldHVybiBuID8gKGQuViA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VXZWVrTnVtYmVyTW9uZGF5JDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlcgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRnVsbFllYXIkMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQxLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyA0KSk7CiAgICAgIHJldHVybiBuID8gKGQueSA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VZZWFyJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLnkgPSArblswXSArICgrblswXSA+IDY4ID8gMTkwMCA6IDIwMDApLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2Vab25lJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gL14oWil8KFsrLV1cZFxkKSg/Ojo/KFxkXGQpKT8vLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyA2KSk7CiAgICAgIHJldHVybiBuID8gKGQuWiA9IG5bMV0gPyAwIDogLShuWzJdICsgKG5bM10gfHwgIjAwIikpLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VRdWFydGVyJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IChkLnEgPSBuWzBdICogMyAtIDMsIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1vbnRoTnVtYmVyJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLm0gPSBuWzBdIC0gMSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRGF5T2ZNb250aCQxKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDEuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5kID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZURheU9mWWVhciQxKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDEuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDMpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5tID0gMCwgZC5kID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZUhvdXIyNCQxKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDEuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5IID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1pbnV0ZXMkMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQxLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAyKSk7CiAgICAgIHJldHVybiBuID8gKGQuTSA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VTZWNvbmRzJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlMgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlTWlsbGlzZWNvbmRzJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMykpOwogICAgICByZXR1cm4gbiA/IChkLkwgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlTWljcm9zZWNvbmRzJDEoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgNikpOwogICAgICByZXR1cm4gbiA/IChkLkwgPSBNYXRoLmZsb29yKG5bMF0gLyAxMDAwKSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlTGl0ZXJhbFBlcmNlbnQkMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBwZXJjZW50UmUkMS5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IGkgKyBuWzBdLmxlbmd0aCA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVW5peFRpbWVzdGFtcCQxKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDEuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICByZXR1cm4gbiA/IChkLlEgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVW5peFRpbWVzdGFtcFNlY29uZHMkMShkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQxLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5zID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXREYXlPZk1vbnRoJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXREYXRlKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEhvdXIyNCQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0SG91cnMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0SG91cjEyJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXRIb3VycygpICUgMTIgfHwgMTIsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdERheU9mWWVhciQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKDEgKyBkYXkkMS5jb3VudCh5ZWFyJDEoZCksIGQpLCBwLCAzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRNaWxsaXNlY29uZHMkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihkLmdldE1pbGxpc2Vjb25kcygpLCBwLCAzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRNaWNyb3NlY29uZHMkMShkLCBwKSB7CiAgICAgIHJldHVybiBmb3JtYXRNaWxsaXNlY29uZHMkMShkLCBwKSArICIwMDAiOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdE1vbnRoTnVtYmVyJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXRNb250aCgpICsgMSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TWludXRlcyQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0TWludXRlcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRTZWNvbmRzJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXRTZWNvbmRzKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtkYXlOdW1iZXJNb25kYXkkMShkKSB7CiAgICAgIHZhciBkYXkgPSBkLmdldERheSgpOwogICAgICByZXR1cm4gZGF5ID09PSAwID8gNyA6IGRheTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRXZWVrTnVtYmVyU3VuZGF5JDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoc3VuZGF5JDEuY291bnQoeWVhciQxKGQpIC0gMSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtOdW1iZXJJU08kMShkLCBwKSB7CiAgICAgIHZhciBkYXkgPSBkLmdldERheSgpOwogICAgICBkID0gKGRheSA+PSA0IHx8IGRheSA9PT0gMCkgPyB0aHVyc2RheSQxKGQpIDogdGh1cnNkYXkkMS5jZWlsKGQpOwogICAgICByZXR1cm4gcGFkJDIodGh1cnNkYXkkMS5jb3VudCh5ZWFyJDEoZCksIGQpICsgKHllYXIkMShkKS5nZXREYXkoKSA9PT0gNCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtkYXlOdW1iZXJTdW5kYXkkMShkKSB7CiAgICAgIHJldHVybiBkLmdldERheSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtOdW1iZXJNb25kYXkkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihtb25kYXkkMS5jb3VudCh5ZWFyJDEoZCkgLSAxLCBkKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0WWVhciQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0RnVsbFllYXIoKSAlIDEwMCwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0RnVsbFllYXIkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihkLmdldEZ1bGxZZWFyKCkgJSAxMDAwMCwgcCwgNCk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0Wm9uZSQxKGQpIHsKICAgICAgdmFyIHogPSBkLmdldFRpbWV6b25lT2Zmc2V0KCk7CiAgICAgIHJldHVybiAoeiA+IDAgPyAiLSIgOiAoeiAqPSAtMSwgIisiKSkKICAgICAgICAgICsgcGFkJDIoeiAvIDYwIHwgMCwgIjAiLCAyKQogICAgICAgICAgKyBwYWQkMih6ICUgNjAsICIwIiwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDRGF5T2ZNb250aCQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0VVRDRGF0ZSgpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENIb3VyMjQkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihkLmdldFVUQ0hvdXJzKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0hvdXIxMiQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0VVRDSG91cnMoKSAlIDEyIHx8IDEyLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENEYXlPZlllYXIkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMigxICsgdXRjRGF5JDEuY291bnQodXRjWWVhciQxKGQpLCBkKSwgcCwgMyk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDTWlsbGlzZWNvbmRzJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXRVVENNaWxsaXNlY29uZHMoKSwgcCwgMyk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDTWljcm9zZWNvbmRzJDEoZCwgcCkgewogICAgICByZXR1cm4gZm9ybWF0VVRDTWlsbGlzZWNvbmRzJDEoZCwgcCkgKyAiMDAwIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENNb250aE51bWJlciQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0VVRDTW9udGgoKSArIDEsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ01pbnV0ZXMkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihkLmdldFVUQ01pbnV0ZXMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDU2Vjb25kcyQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKGQuZ2V0VVRDU2Vjb25kcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyTW9uZGF5JDEoZCkgewogICAgICB2YXIgZG93ID0gZC5nZXRVVENEYXkoKTsKICAgICAgcmV0dXJuIGRvdyA9PT0gMCA/IDcgOiBkb3c7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla051bWJlclN1bmRheSQxKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQyKHV0Y1N1bmRheSQxLmNvdW50KHV0Y1llYXIkMShkKSAtIDEsIGQpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrTnVtYmVySVNPJDEoZCwgcCkgewogICAgICB2YXIgZGF5ID0gZC5nZXRVVENEYXkoKTsKICAgICAgZCA9IChkYXkgPj0gNCB8fCBkYXkgPT09IDApID8gdXRjVGh1cnNkYXkkMShkKSA6IHV0Y1RodXJzZGF5JDEuY2VpbChkKTsKICAgICAgcmV0dXJuIHBhZCQyKHV0Y1RodXJzZGF5JDEuY291bnQodXRjWWVhciQxKGQpLCBkKSArICh1dGNZZWFyJDEoZCkuZ2V0VVRDRGF5KCkgPT09IDQpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyU3VuZGF5JDEoZCkgewogICAgICByZXR1cm4gZC5nZXRVVENEYXkoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrTnVtYmVyTW9uZGF5JDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIodXRjTW9uZGF5JDEuY291bnQodXRjWWVhciQxKGQpIC0gMSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1llYXIkMShkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMihkLmdldFVUQ0Z1bGxZZWFyKCkgJSAxMDAsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0Z1bGxZZWFyJDEoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDIoZC5nZXRVVENGdWxsWWVhcigpICUgMTAwMDAsIHAsIDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1pvbmUkMSgpIHsKICAgICAgcmV0dXJuICIrMDAwMCI7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TGl0ZXJhbFBlcmNlbnQkMSgpIHsKICAgICAgcmV0dXJuICIlIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVbml4VGltZXN0YW1wJDEoZCkgewogICAgICByZXR1cm4gK2Q7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VW5peFRpbWVzdGFtcFNlY29uZHMkMShkKSB7CiAgICAgIHJldHVybiBNYXRoLmZsb29yKCtkIC8gMTAwMCk7CiAgICB9CgogICAgdmFyIGxvY2FsZSQ0OwogICAgdmFyIHRpbWVGb3JtYXQkMTsKICAgIHZhciB0aW1lUGFyc2UkMTsKICAgIHZhciB1dGNGb3JtYXQkMTsKICAgIHZhciB1dGNQYXJzZSQxOwoKICAgIGRlZmF1bHRMb2NhbGUkNCh7CiAgICAgIGRhdGVUaW1lOiAiJXgsICVYIiwKICAgICAgZGF0ZTogIiUtbS8lLWQvJVkiLAogICAgICB0aW1lOiAiJS1JOiVNOiVTICVwIiwKICAgICAgcGVyaW9kczogWyJBTSIsICJQTSJdLAogICAgICBkYXlzOiBbIlN1bmRheSIsICJNb25kYXkiLCAiVHVlc2RheSIsICJXZWRuZXNkYXkiLCAiVGh1cnNkYXkiLCAiRnJpZGF5IiwgIlNhdHVyZGF5Il0sCiAgICAgIHNob3J0RGF5czogWyJTdW4iLCAiTW9uIiwgIlR1ZSIsICJXZWQiLCAiVGh1IiwgIkZyaSIsICJTYXQiXSwKICAgICAgbW9udGhzOiBbIkphbnVhcnkiLCAiRmVicnVhcnkiLCAiTWFyY2giLCAiQXByaWwiLCAiTWF5IiwgIkp1bmUiLCAiSnVseSIsICJBdWd1c3QiLCAiU2VwdGVtYmVyIiwgIk9jdG9iZXIiLCAiTm92ZW1iZXIiLCAiRGVjZW1iZXIiXSwKICAgICAgc2hvcnRNb250aHM6IFsiSmFuIiwgIkZlYiIsICJNYXIiLCAiQXByIiwgIk1heSIsICJKdW4iLCAiSnVsIiwgIkF1ZyIsICJTZXAiLCAiT2N0IiwgIk5vdiIsICJEZWMiXQogICAgfSk7CgogICAgZnVuY3Rpb24gZGVmYXVsdExvY2FsZSQ0KGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlJDQgPSBmb3JtYXRMb2NhbGUkNChkZWZpbml0aW9uKTsKICAgICAgdGltZUZvcm1hdCQxID0gbG9jYWxlJDQuZm9ybWF0OwogICAgICB0aW1lUGFyc2UkMSA9IGxvY2FsZSQ0LnBhcnNlOwogICAgICB1dGNGb3JtYXQkMSA9IGxvY2FsZSQ0LnV0Y0Zvcm1hdDsKICAgICAgdXRjUGFyc2UkMSA9IGxvY2FsZSQ0LnV0Y1BhcnNlOwogICAgICByZXR1cm4gbG9jYWxlJDQ7CiAgICB9CgogICAgdmFyIGR1cmF0aW9uU2Vjb25kJDMgPSAxMDAwLAogICAgICAgIGR1cmF0aW9uTWludXRlJDMgPSBkdXJhdGlvblNlY29uZCQzICogNjAsCiAgICAgICAgZHVyYXRpb25Ib3VyJDMgPSBkdXJhdGlvbk1pbnV0ZSQzICogNjAsCiAgICAgICAgZHVyYXRpb25EYXkkMyA9IGR1cmF0aW9uSG91ciQzICogMjQsCiAgICAgICAgZHVyYXRpb25XZWVrJDMgPSBkdXJhdGlvbkRheSQzICogNywKICAgICAgICBkdXJhdGlvbk1vbnRoJDEgPSBkdXJhdGlvbkRheSQzICogMzAsCiAgICAgICAgZHVyYXRpb25ZZWFyJDEgPSBkdXJhdGlvbkRheSQzICogMzY1OwoKICAgIGZ1bmN0aW9uIGRhdGUkNSh0KSB7CiAgICAgIHJldHVybiBuZXcgRGF0ZSh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBudW1iZXIkOSh0KSB7CiAgICAgIHJldHVybiB0IGluc3RhbmNlb2YgRGF0ZSA/ICt0IDogK25ldyBEYXRlKCt0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjYWxlbmRhciQxKHllYXIsIG1vbnRoLCB3ZWVrLCBkYXksIGhvdXIsIG1pbnV0ZSwgc2Vjb25kLCBtaWxsaXNlY29uZCwgZm9ybWF0KSB7CiAgICAgIHZhciBzY2FsZSA9IGNvbnRpbnVvdXMkMShkZWludGVycG9sYXRlTGluZWFyLCByZWludGVycG9sYXRlKSwKICAgICAgICAgIGludmVydCA9IHNjYWxlLmludmVydCwKICAgICAgICAgIGRvbWFpbiA9IHNjYWxlLmRvbWFpbjsKCiAgICAgIHZhciBmb3JtYXRNaWxsaXNlY29uZCA9IGZvcm1hdCgiLiVMIiksCiAgICAgICAgICBmb3JtYXRTZWNvbmQgPSBmb3JtYXQoIjolUyIpLAogICAgICAgICAgZm9ybWF0TWludXRlID0gZm9ybWF0KCIlSTolTSIpLAogICAgICAgICAgZm9ybWF0SG91ciA9IGZvcm1hdCgiJUkgJXAiKSwKICAgICAgICAgIGZvcm1hdERheSA9IGZvcm1hdCgiJWEgJWQiKSwKICAgICAgICAgIGZvcm1hdFdlZWsgPSBmb3JtYXQoIiViICVkIiksCiAgICAgICAgICBmb3JtYXRNb250aCA9IGZvcm1hdCgiJUIiKSwKICAgICAgICAgIGZvcm1hdFllYXIgPSBmb3JtYXQoIiVZIik7CgogICAgICB2YXIgdGlja0ludGVydmFscyA9IFsKICAgICAgICBbc2Vjb25kLCAgMSwgICAgICBkdXJhdGlvblNlY29uZCQzXSwKICAgICAgICBbc2Vjb25kLCAgNSwgIDUgKiBkdXJhdGlvblNlY29uZCQzXSwKICAgICAgICBbc2Vjb25kLCAxNSwgMTUgKiBkdXJhdGlvblNlY29uZCQzXSwKICAgICAgICBbc2Vjb25kLCAzMCwgMzAgKiBkdXJhdGlvblNlY29uZCQzXSwKICAgICAgICBbbWludXRlLCAgMSwgICAgICBkdXJhdGlvbk1pbnV0ZSQzXSwKICAgICAgICBbbWludXRlLCAgNSwgIDUgKiBkdXJhdGlvbk1pbnV0ZSQzXSwKICAgICAgICBbbWludXRlLCAxNSwgMTUgKiBkdXJhdGlvbk1pbnV0ZSQzXSwKICAgICAgICBbbWludXRlLCAzMCwgMzAgKiBkdXJhdGlvbk1pbnV0ZSQzXSwKICAgICAgICBbICBob3VyLCAgMSwgICAgICBkdXJhdGlvbkhvdXIkMyAgXSwKICAgICAgICBbICBob3VyLCAgMywgIDMgKiBkdXJhdGlvbkhvdXIkMyAgXSwKICAgICAgICBbICBob3VyLCAgNiwgIDYgKiBkdXJhdGlvbkhvdXIkMyAgXSwKICAgICAgICBbICBob3VyLCAxMiwgMTIgKiBkdXJhdGlvbkhvdXIkMyAgXSwKICAgICAgICBbICAgZGF5LCAgMSwgICAgICBkdXJhdGlvbkRheSQzICAgXSwKICAgICAgICBbICAgZGF5LCAgMiwgIDIgKiBkdXJhdGlvbkRheSQzICAgXSwKICAgICAgICBbICB3ZWVrLCAgMSwgICAgICBkdXJhdGlvbldlZWskMyAgXSwKICAgICAgICBbIG1vbnRoLCAgMSwgICAgICBkdXJhdGlvbk1vbnRoJDEgXSwKICAgICAgICBbIG1vbnRoLCAgMywgIDMgKiBkdXJhdGlvbk1vbnRoJDEgXSwKICAgICAgICBbICB5ZWFyLCAgMSwgICAgICBkdXJhdGlvblllYXIkMSAgXQogICAgICBdOwoKICAgICAgZnVuY3Rpb24gdGlja0Zvcm1hdChkYXRlKSB7CiAgICAgICAgcmV0dXJuIChzZWNvbmQoZGF0ZSkgPCBkYXRlID8gZm9ybWF0TWlsbGlzZWNvbmQKICAgICAgICAgICAgOiBtaW51dGUoZGF0ZSkgPCBkYXRlID8gZm9ybWF0U2Vjb25kCiAgICAgICAgICAgIDogaG91cihkYXRlKSA8IGRhdGUgPyBmb3JtYXRNaW51dGUKICAgICAgICAgICAgOiBkYXkoZGF0ZSkgPCBkYXRlID8gZm9ybWF0SG91cgogICAgICAgICAgICA6IG1vbnRoKGRhdGUpIDwgZGF0ZSA/ICh3ZWVrKGRhdGUpIDwgZGF0ZSA/IGZvcm1hdERheSA6IGZvcm1hdFdlZWspCiAgICAgICAgICAgIDogeWVhcihkYXRlKSA8IGRhdGUgPyBmb3JtYXRNb250aAogICAgICAgICAgICA6IGZvcm1hdFllYXIpKGRhdGUpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0aWNrSW50ZXJ2YWwoaW50ZXJ2YWwsIHN0YXJ0LCBzdG9wLCBzdGVwKSB7CiAgICAgICAgaWYgKGludGVydmFsID09IG51bGwpIGludGVydmFsID0gMTA7CgogICAgICAgIC8vIElmIGEgZGVzaXJlZCB0aWNrIGNvdW50IGlzIHNwZWNpZmllZCwgcGljayBhIHJlYXNvbmFibGUgdGljayBpbnRlcnZhbAogICAgICAgIC8vIGJhc2VkIG9uIHRoZSBleHRlbnQgb2YgdGhlIGRvbWFpbiBhbmQgYSByb3VnaCBlc3RpbWF0ZSBvZiB0aWNrIHNpemUuCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBhc3N1bWUgaW50ZXJ2YWwgaXMgYWxyZWFkeSBhIHRpbWUgaW50ZXJ2YWwgYW5kIHVzZSBpdC4KICAgICAgICBpZiAodHlwZW9mIGludGVydmFsID09PSAibnVtYmVyIikgewogICAgICAgICAgdmFyIHRhcmdldCA9IE1hdGguYWJzKHN0b3AgLSBzdGFydCkgLyBpbnRlcnZhbCwKICAgICAgICAgICAgICBpID0gYmlzZWN0b3IkNChmdW5jdGlvbihpKSB7IHJldHVybiBpWzJdOyB9KS5yaWdodCh0aWNrSW50ZXJ2YWxzLCB0YXJnZXQpOwogICAgICAgICAgaWYgKGkgPT09IHRpY2tJbnRlcnZhbHMubGVuZ3RoKSB7CiAgICAgICAgICAgIHN0ZXAgPSB0aWNrU3RlcCQyKHN0YXJ0IC8gZHVyYXRpb25ZZWFyJDEsIHN0b3AgLyBkdXJhdGlvblllYXIkMSwgaW50ZXJ2YWwpOwogICAgICAgICAgICBpbnRlcnZhbCA9IHllYXI7CiAgICAgICAgICB9IGVsc2UgaWYgKGkpIHsKICAgICAgICAgICAgaSA9IHRpY2tJbnRlcnZhbHNbdGFyZ2V0IC8gdGlja0ludGVydmFsc1tpIC0gMV1bMl0gPCB0aWNrSW50ZXJ2YWxzW2ldWzJdIC8gdGFyZ2V0ID8gaSAtIDEgOiBpXTsKICAgICAgICAgICAgc3RlcCA9IGlbMV07CiAgICAgICAgICAgIGludGVydmFsID0gaVswXTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHN0ZXAgPSBNYXRoLm1heCh0aWNrU3RlcCQyKHN0YXJ0LCBzdG9wLCBpbnRlcnZhbCksIDEpOwogICAgICAgICAgICBpbnRlcnZhbCA9IG1pbGxpc2Vjb25kOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHN0ZXAgPT0gbnVsbCA/IGludGVydmFsIDogaW50ZXJ2YWwuZXZlcnkoc3RlcCk7CiAgICAgIH0KCiAgICAgIHNjYWxlLmludmVydCA9IGZ1bmN0aW9uKHkpIHsKICAgICAgICByZXR1cm4gbmV3IERhdGUoaW52ZXJ0KHkpKTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IGRvbWFpbihtYXAkOC5jYWxsKF8sIG51bWJlciQ5KSkgOiBkb21haW4oKS5tYXAoZGF0ZSQ1KTsKICAgICAgfTsKCiAgICAgIHNjYWxlLnRpY2tzID0gZnVuY3Rpb24oaW50ZXJ2YWwsIHN0ZXApIHsKICAgICAgICB2YXIgZCA9IGRvbWFpbigpLAogICAgICAgICAgICB0MCA9IGRbMF0sCiAgICAgICAgICAgIHQxID0gZFtkLmxlbmd0aCAtIDFdLAogICAgICAgICAgICByID0gdDEgPCB0MCwKICAgICAgICAgICAgdDsKICAgICAgICBpZiAocikgdCA9IHQwLCB0MCA9IHQxLCB0MSA9IHQ7CiAgICAgICAgdCA9IHRpY2tJbnRlcnZhbChpbnRlcnZhbCwgdDAsIHQxLCBzdGVwKTsKICAgICAgICB0ID0gdCA/IHQucmFuZ2UodDAsIHQxICsgMSkgOiBbXTsgLy8gaW5jbHVzaXZlIHN0b3AKICAgICAgICByZXR1cm4gciA/IHQucmV2ZXJzZSgpIDogdDsKICAgICAgfTsKCiAgICAgIHNjYWxlLnRpY2tGb3JtYXQgPSBmdW5jdGlvbihjb3VudCwgc3BlY2lmaWVyKSB7CiAgICAgICAgcmV0dXJuIHNwZWNpZmllciA9PSBudWxsID8gdGlja0Zvcm1hdCA6IGZvcm1hdChzcGVjaWZpZXIpOwogICAgICB9OwoKICAgICAgc2NhbGUubmljZSA9IGZ1bmN0aW9uKGludGVydmFsLCBzdGVwKSB7CiAgICAgICAgdmFyIGQgPSBkb21haW4oKTsKICAgICAgICByZXR1cm4gKGludGVydmFsID0gdGlja0ludGVydmFsKGludGVydmFsLCBkWzBdLCBkW2QubGVuZ3RoIC0gMV0sIHN0ZXApKQogICAgICAgICAgICA/IGRvbWFpbihuaWNlJDEoZCwgaW50ZXJ2YWwpKQogICAgICAgICAgICA6IHNjYWxlOwogICAgICB9OwoKICAgICAgc2NhbGUuY29weSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBjb3B5JDIoc2NhbGUsIGNhbGVuZGFyJDEoeWVhciwgbW9udGgsIHdlZWssIGRheSwgaG91ciwgbWludXRlLCBzZWNvbmQsIG1pbGxpc2Vjb25kLCBmb3JtYXQpKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBzY2FsZTsKICAgIH0KCiAgICBmdW5jdGlvbiB0aW1lJDEoKSB7CiAgICAgIHJldHVybiBjYWxlbmRhciQxKHllYXIkMSwgbW9udGgkMSwgc3VuZGF5JDEsIGRheSQxLCBob3VyJDEsIG1pbnV0ZSQxLCBzZWNvbmQkMSwgbWlsbGlzZWNvbmQkMSwgdGltZUZvcm1hdCQxKS5kb21haW4oW25ldyBEYXRlKDIwMDAsIDAsIDEpLCBuZXcgRGF0ZSgyMDAwLCAwLCAyKV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHV0Y1RpbWUkMSgpIHsKICAgICAgcmV0dXJuIGNhbGVuZGFyJDEodXRjWWVhciQxLCB1dGNNb250aCQxLCB1dGNTdW5kYXkkMSwgdXRjRGF5JDEsIHV0Y0hvdXIkMSwgdXRjTWludXRlJDEsIHNlY29uZCQxLCBtaWxsaXNlY29uZCQxLCB1dGNGb3JtYXQkMSkuZG9tYWluKFtEYXRlLlVUQygyMDAwLCAwLCAxKSwgRGF0ZS5VVEMoMjAwMCwgMCwgMildKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvcnMkMShzKSB7CiAgICAgIHJldHVybiBzLm1hdGNoKC8uezZ9L2cpLm1hcChmdW5jdGlvbih4KSB7CiAgICAgICAgcmV0dXJuICIjIiArIHg7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBjYXRlZ29yeTEwJDEgPSBjb2xvcnMkMSgiMWY3N2I0ZmY3ZjBlMmNhMDJjZDYyNzI4OTQ2N2JkOGM1NjRiZTM3N2MyN2Y3ZjdmYmNiZDIyMTdiZWNmIik7CgogICAgdmFyIGNhdGVnb3J5MjBiID0gY29sb3JzJDEoIjM5M2I3OTUyNTRhMzZiNmVjZjljOWVkZTYzNzkzOThjYTI1MmI1Y2Y2YmNlZGI5YzhjNmQzMWJkOWUzOWU3YmE1MmU3Y2I5NDg0M2MzOWFkNDk0YWQ2NjE2YmU3OTY5YzdiNDE3M2E1NTE5NGNlNmRiZGRlOWVkNiIpOwoKICAgIHZhciBjYXRlZ29yeTIwYyA9IGNvbG9ycyQxKCIzMTgyYmQ2YmFlZDY5ZWNhZTFjNmRiZWZlNjU1MGRmZDhkM2NmZGFlNmJmZGQwYTIzMWEzNTQ3NGM0NzZhMWQ5OWJjN2U5YzA3NTZiYjE5ZTlhYzhiY2JkZGNkYWRhZWI2MzYzNjM5Njk2OTZiZGJkYmRkOWQ5ZDkiKTsKCiAgICB2YXIgY2F0ZWdvcnkyMCA9IGNvbG9ycyQxKCIxZjc3YjRhZWM3ZThmZjdmMGVmZmJiNzgyY2EwMmM5OGRmOGFkNjI3MjhmZjk4OTY5NDY3YmRjNWIwZDU4YzU2NGJjNDljOTRlMzc3YzJmN2I2ZDI3ZjdmN2ZjN2M3YzdiY2JkMjJkYmRiOGQxN2JlY2Y5ZWRhZTUiKTsKCiAgICB2YXIgY3ViZWhlbGl4JGEgPSBjdWJlaGVsaXhMb25nJDIoY3ViZWhlbGl4JDgoMzAwLCAwLjUsIDAuMCksIGN1YmVoZWxpeCQ4KC0yNDAsIDAuNSwgMS4wKSk7CgogICAgdmFyIHdhcm0kMSA9IGN1YmVoZWxpeExvbmckMihjdWJlaGVsaXgkOCgtMTAwLCAwLjc1LCAwLjM1KSwgY3ViZWhlbGl4JDgoODAsIDEuNTAsIDAuOCkpOwoKICAgIHZhciBjb29sJDEgPSBjdWJlaGVsaXhMb25nJDIoY3ViZWhlbGl4JDgoMjYwLCAwLjc1LCAwLjM1KSwgY3ViZWhlbGl4JDgoODAsIDEuNTAsIDAuOCkpOwoKICAgIHZhciByYWluYm93JDEgPSBjdWJlaGVsaXgkOCgpOwoKICAgIGZ1bmN0aW9uIHJhaW5ib3ckMih0KSB7CiAgICAgIGlmICh0IDwgMCB8fCB0ID4gMSkgdCAtPSBNYXRoLmZsb29yKHQpOwogICAgICB2YXIgdHMgPSBNYXRoLmFicyh0IC0gMC41KTsKICAgICAgcmFpbmJvdyQxLmggPSAzNjAgKiB0IC0gMTAwOwogICAgICByYWluYm93JDEucyA9IDEuNSAtIDEuNSAqIHRzOwogICAgICByYWluYm93JDEubCA9IDAuOCAtIDAuOSAqIHRzOwogICAgICByZXR1cm4gcmFpbmJvdyQxICsgIiI7CiAgICB9CgogICAgZnVuY3Rpb24gcmFtcCQyKHJhbmdlKSB7CiAgICAgIHZhciBuID0gcmFuZ2UubGVuZ3RoOwogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiByYW5nZVtNYXRoLm1heCgwLCBNYXRoLm1pbihuIC0gMSwgTWF0aC5mbG9vcih0ICogbikpKV07CiAgICAgIH07CiAgICB9CgogICAgdmFyIHZpcmlkaXMkMSA9IHJhbXAkMihjb2xvcnMkMSgiNDQwMTU0NDQwMjU2NDUwNDU3NDUwNTU5NDYwNzVhNDYwODVjNDYwYTVkNDYwYjVlNDcwZDYwNDcwZTYxNDcxMDYzNDcxMTY0NDcxMzY1NDgxNDY3NDgxNjY4NDgxNzY5NDgxODZhNDgxYTZjNDgxYjZkNDgxYzZlNDgxZDZmNDgxZjcwNDgyMDcxNDgyMTczNDgyMzc0NDgyNDc1NDgyNTc2NDgyNjc3NDgyODc4NDgyOTc5NDcyYTdhNDcyYzdhNDcyZDdiNDcyZTdjNDcyZjdkNDYzMDdlNDYzMjdlNDYzMzdmNDYzNDgwNDUzNTgxNDUzNzgxNDUzODgyNDQzOTgzNDQzYTgzNDQzYjg0NDMzZDg0NDMzZTg1NDIzZjg1NDI0MDg2NDI0MTg2NDE0Mjg3NDE0NDg3NDA0NTg4NDA0Njg4M2Y0Nzg4M2Y0ODg5M2U0OTg5M2U0YTg5M2U0YzhhM2Q0ZDhhM2Q0ZThhM2M0ZjhhM2M1MDhiM2I1MThiM2I1MjhiM2E1MzhiM2E1NDhjMzk1NThjMzk1NjhjMzg1ODhjMzg1OThjMzc1YThjMzc1YjhkMzY1YzhkMzY1ZDhkMzU1ZThkMzU1ZjhkMzQ2MDhkMzQ2MThkMzM2MjhkMzM2MzhkMzI2NDhlMzI2NThlMzE2NjhlMzE2NzhlMzE2ODhlMzA2OThlMzA2YThlMmY2YjhlMmY2YzhlMmU2ZDhlMmU2ZThlMmU2ZjhlMmQ3MDhlMmQ3MThlMmM3MThlMmM3MjhlMmM3MzhlMmI3NDhlMmI3NThlMmE3NjhlMmE3NzhlMmE3ODhlMjk3OThlMjk3YThlMjk3YjhlMjg3YzhlMjg3ZDhlMjc3ZThlMjc3ZjhlMjc4MDhlMjY4MThlMjY4MjhlMjY4MjhlMjU4MzhlMjU4NDhlMjU4NThlMjQ4NjhlMjQ4NzhlMjM4ODhlMjM4OThlMjM4YThkMjI4YjhkMjI4YzhkMjI4ZDhkMjE4ZThkMjE4ZjhkMjE5MDhkMjE5MThjMjA5MjhjMjA5MjhjMjA5MzhjMWY5NDhjMWY5NThiMWY5NjhiMWY5NzhiMWY5ODhiMWY5OThhMWY5YThhMWU5YjhhMWU5Yzg5MWU5ZDg5MWY5ZTg5MWY5Zjg4MWZhMDg4MWZhMTg4MWZhMTg3MWZhMjg3MjBhMzg2MjBhNDg2MjFhNTg1MjFhNjg1MjJhNzg1MjJhODg0MjNhOTgzMjRhYTgzMjVhYjgyMjVhYzgyMjZhZDgxMjdhZDgxMjhhZTgwMjlhZjdmMmFiMDdmMmNiMTdlMmRiMjdkMmViMzdjMmZiNDdjMzFiNTdiMzJiNjdhMzRiNjc5MzViNzc5MzdiODc4MzhiOTc3M2FiYTc2M2JiYjc1M2RiYzc0M2ZiYzczNDBiZDcyNDJiZTcxNDRiZjcwNDZjMDZmNDhjMTZlNGFjMTZkNGNjMjZjNGVjMzZiNTBjNDZhNTJjNTY5NTRjNTY4NTZjNjY3NThjNzY1NWFjODY0NWNjODYzNWVjOTYyNjBjYTYwNjNjYjVmNjVjYjVlNjdjYzVjNjljZDViNmNjZDVhNmVjZTU4NzBjZjU3NzNkMDU2NzVkMDU0NzdkMTUzN2FkMTUxN2NkMjUwN2ZkMzRlODFkMzRkODRkNDRiODZkNTQ5ODlkNTQ4OGJkNjQ2OGVkNjQ1OTBkNzQzOTNkNzQxOTVkODQwOThkODNlOWJkOTNjOWRkOTNiYTBkYTM5YTJkYTM3YTVkYjM2YThkYjM0YWFkYzMyYWRkYzMwYjBkZDJmYjJkZDJkYjVkZTJiYjhkZTI5YmFkZTI4YmRkZjI2YzBkZjI1YzJkZjIzYzVlMDIxYzhlMDIwY2FlMTFmY2RlMTFkZDBlMTFjZDJlMjFiZDVlMjFhZDhlMjE5ZGFlMzE5ZGRlMzE4ZGZlMzE4ZTJlNDE4ZTVlNDE5ZTdlNDE5ZWFlNTFhZWNlNTFiZWZlNTFjZjFlNTFkZjRlNjFlZjZlNjIwZjhlNjIxZmJlNzIzZmRlNzI1IikpOwoKICAgIHZhciBtYWdtYSQxID0gcmFtcCQyKGNvbG9ycyQxKCIwMDAwMDQwMTAwMDUwMTAxMDYwMTAxMDgwMjAxMDkwMjAyMGIwMjAyMGQwMzAzMGYwMzAzMTIwNDA0MTQwNTA0MTYwNjA1MTgwNjA1MWEwNzA2MWMwODA3MWUwOTA3MjAwYTA4MjIwYjA5MjQwYzA5MjYwZDBhMjkwZTBiMmIxMDBiMmQxMTBjMmYxMjBkMzExMzBkMzQxNDBlMzYxNTBlMzgxNjBmM2IxODBmM2QxOTEwM2YxYTEwNDIxYzEwNDQxZDExNDcxZTExNDkyMDExNGIyMTExNGUyMjExNTAyNDEyNTMyNTEyNTUyNzEyNTgyOTExNWEyYTExNWMyYzExNWYyZDExNjEyZjExNjMzMTExNjUzMzEwNjczNDEwNjkzNjEwNmIzODEwNmMzOTBmNmUzYjBmNzAzZDBmNzEzZjBmNzI0MDBmNzQ0MjBmNzU0NDBmNzY0NTEwNzc0NzEwNzg0OTEwNzg0YTEwNzk0YzExN2E0ZTExN2I0ZjEyN2I1MTEyN2M1MjEzN2M1NDEzN2Q1NjE0N2Q1NzE1N2U1OTE1N2U1YTE2N2U1YzE2N2Y1ZDE3N2Y1ZjE4N2Y2MDE4ODA2MjE5ODA2NDFhODA2NTFhODA2NzFiODA2ODFjODE2YTFjODE2YjFkODE2ZDFkODE2ZTFlODE3MDFmODE3MjFmODE3MzIwODE3NTIxODE3NjIxODE3ODIyODE3OTIyODI3YjIzODI3YzIzODI3ZTI0ODI4MDI1ODI4MTI1ODE4MzI2ODE4NDI2ODE4NjI3ODE4ODI3ODE4OTI4ODE4YjI5ODE4YzI5ODE4ZTJhODE5MDJhODE5MTJiODE5MzJiODA5NDJjODA5NjJjODA5ODJkODA5OTJkODA5YjJlN2Y5YzJlN2Y5ZTJmN2ZhMDJmN2ZhMTMwN2VhMzMwN2VhNTMxN2VhNjMxN2RhODMyN2RhYTMzN2RhYjMzN2NhZDM0N2NhZTM0N2JiMDM1N2JiMjM1N2JiMzM2N2FiNTM2N2FiNzM3NzliODM3NzliYTM4NzhiYzM5NzhiZDM5NzdiZjNhNzdjMDNhNzZjMjNiNzVjNDNjNzVjNTNjNzRjNzNkNzNjODNlNzNjYTNlNzJjYzNmNzFjZDQwNzFjZjQwNzBkMDQxNmZkMjQyNmZkMzQzNmVkNTQ0NmRkNjQ1NmNkODQ1NmNkOTQ2NmJkYjQ3NmFkYzQ4NjlkZTQ5NjhkZjRhNjhlMDRjNjdlMjRkNjZlMzRlNjVlNDRmNjRlNTUwNjRlNzUyNjNlODUzNjJlOTU0NjJlYTU2NjFlYjU3NjBlYzU4NjBlZDVhNWZlZTViNWVlZjVkNWVmMDVmNWVmMTYwNWRmMjYyNWRmMjY0NWNmMzY1NWNmNDY3NWNmNDY5NWNmNTZiNWNmNjZjNWNmNjZlNWNmNzcwNWNmNzcyNWNmODc0NWNmODc2NWNmOTc4NWRmOTc5NWRmOTdiNWRmYTdkNWVmYTdmNWVmYTgxNWZmYjgzNWZmYjg1NjBmYjg3NjFmYzg5NjFmYzhhNjJmYzhjNjNmYzhlNjRmYzkwNjVmZDkyNjZmZDk0NjdmZDk2NjhmZDk4NjlmZDlhNmFmZDliNmJmZTlkNmNmZTlmNmRmZWExNmVmZWEzNmZmZWE1NzFmZWE3NzJmZWE5NzNmZWFhNzRmZWFjNzZmZWFlNzdmZWIwNzhmZWIyN2FmZWI0N2JmZWI2N2NmZWI3N2VmZWI5N2ZmZWJiODFmZWJkODJmZWJmODRmZWMxODVmZWMyODdmZWM0ODhmZWM2OGFmZWM4OGNmZWNhOGRmZWNjOGZmZWNkOTBmZWNmOTJmZWQxOTRmZWQzOTVmZWQ1OTdmZWQ3OTlmZWQ4OWFmZGRhOWNmZGRjOWVmZGRlYTBmZGUwYTFmZGUyYTNmZGUzYTVmZGU1YTdmZGU3YTlmZGU5YWFmZGViYWNmY2VjYWVmY2VlYjBmY2YwYjJmY2YyYjRmY2Y0YjZmY2Y2YjhmY2Y3YjlmY2Y5YmJmY2ZiYmRmY2ZkYmYiKSk7CgogICAgdmFyIGluZmVybm8kMSA9IHJhbXAkMihjb2xvcnMkMSgiMDAwMDA0MDEwMDA1MDEwMTA2MDEwMTA4MDIwMTBhMDIwMjBjMDIwMjBlMDMwMjEwMDQwMzEyMDQwMzE0MDUwNDE3MDYwNDE5MDcwNTFiMDgwNTFkMDkwNjFmMGEwNzIyMGIwNzI0MGMwODI2MGQwODI5MGUwOTJiMTAwOTJkMTEwYTMwMTIwYTMyMTQwYjM0MTUwYjM3MTYwYjM5MTgwYzNjMTkwYzNlMWIwYzQxMWMwYzQzMWUwYzQ1MWYwYzQ4MjEwYzRhMjMwYzRjMjQwYzRmMjYwYzUxMjgwYjUzMjkwYjU1MmIwYjU3MmQwYjU5MmYwYTViMzEwYTVjMzIwYTVlMzQwYTVmMzYwOTYxMzgwOTYyMzkwOTYzM2IwOTY0M2QwOTY1M2UwOTY2NDAwYTY3NDIwYTY4NDQwYTY4NDUwYTY5NDcwYjZhNDkwYjZhNGEwYzZiNGMwYzZiNGQwZDZjNGYwZDZjNTEwZTZjNTIwZTZkNTQwZjZkNTUwZjZkNTcxMDZlNTkxMDZlNWExMTZlNWMxMjZlNWQxMjZlNWYxMzZlNjExMzZlNjIxNDZlNjQxNTZlNjUxNTZlNjcxNjZlNjkxNjZlNmExNzZlNmMxODZlNmQxODZlNmYxOTZlNzExOTZlNzIxYTZlNzQxYTZlNzUxYjZlNzcxYzZkNzgxYzZkN2ExZDZkN2MxZDZkN2QxZTZkN2YxZTZjODAxZjZjODIyMDZjODQyMDZiODUyMTZiODcyMTZiODgyMjZhOGEyMjZhOGMyMzY5OGQyMzY5OGYyNDY5OTAyNTY4OTIyNTY4OTMyNjY3OTUyNjY3OTcyNzY2OTgyNzY2OWEyODY1OWIyOTY0OWQyOTY0OWYyYTYzYTAyYTYzYTIyYjYyYTMyYzYxYTUyYzYwYTYyZDYwYTgyZTVmYTkyZTVlYWIyZjVlYWQzMDVkYWUzMDVjYjAzMTViYjEzMjVhYjMzMjVhYjQzMzU5YjYzNDU4YjczNTU3YjkzNTU2YmEzNjU1YmMzNzU0YmQzODUzYmYzOTUyYzAzYTUxYzEzYTUwYzMzYjRmYzQzYzRlYzYzZDRkYzczZTRjYzgzZjRiY2E0MDRhY2I0MTQ5Y2M0MjQ4Y2U0MzQ3Y2Y0NDQ2ZDA0NTQ1ZDI0NjQ0ZDM0NzQzZDQ0ODQyZDU0YTQxZDc0YjNmZDg0YzNlZDk0ZDNkZGE0ZTNjZGI1MDNiZGQ1MTNhZGU1MjM4ZGY1MzM3ZTA1NTM2ZTE1NjM1ZTI1NzM0ZTM1OTMzZTQ1YTMxZTU1YzMwZTY1ZDJmZTc1ZTJlZTg2MDJkZTk2MTJiZWE2MzJhZWI2NDI5ZWI2NjI4ZWM2NzI2ZWQ2OTI1ZWU2YTI0ZWY2YzIzZWY2ZTIxZjA2ZjIwZjE3MTFmZjE3MzFkZjI3NDFjZjM3NjFiZjM3ODE5ZjQ3OTE4ZjU3YjE3ZjU3ZDE1ZjY3ZTE0ZjY4MDEzZjc4MjEyZjc4NDEwZjg4NTBmZjg4NzBlZjg4OTBjZjk4YjBiZjk4YzBhZjk4ZTA5ZmE5MDA4ZmE5MjA3ZmE5NDA3ZmI5NjA2ZmI5NzA2ZmI5OTA2ZmI5YjA2ZmI5ZDA3ZmM5ZjA3ZmNhMTA4ZmNhMzA5ZmNhNTBhZmNhNjBjZmNhODBkZmNhYTBmZmNhYzExZmNhZTEyZmNiMDE0ZmNiMjE2ZmNiNDE4ZmJiNjFhZmJiODFkZmJiYTFmZmJiYzIxZmJiZTIzZmFjMDI2ZmFjMjI4ZmFjNDJhZmFjNjJkZjljNzJmZjljOTMyZjljYjM1ZjhjZDM3ZjhjZjNhZjdkMTNkZjdkMzQwZjZkNTQzZjZkNzQ2ZjVkOTQ5ZjVkYjRjZjRkZDRmZjRkZjUzZjRlMTU2ZjNlMzVhZjNlNTVkZjJlNjYxZjJlODY1ZjJlYTY5ZjFlYzZkZjFlZDcxZjFlZjc1ZjFmMTc5ZjJmMjdkZjJmNDgyZjNmNTg2ZjNmNjhhZjRmODhlZjVmOTkyZjZmYTk2ZjhmYjlhZjlmYzlkZmFmZGExZmNmZmE0IikpOwoKICAgIHZhciBwbGFzbWEkMSA9IHJhbXAkMihjb2xvcnMkMSgiMGQwODg3MTAwNzg4MTMwNzg5MTYwNzhhMTkwNjhjMWIwNjhkMWQwNjhlMjAwNjhmMjIwNjkwMjQwNjkxMjYwNTkxMjgwNTkyMmEwNTkzMmMwNTk0MmUwNTk1MmYwNTk2MzEwNTk3MzMwNTk3MzUwNDk4MzcwNDk5MzgwNDlhM2EwNDlhM2MwNDliM2UwNDljM2YwNDljNDEwNDlkNDMwMzllNDQwMzllNDYwMzlmNDgwMzlmNDkwM2EwNGIwM2ExNGMwMmExNGUwMmEyNTAwMmEyNTEwMmEzNTMwMmEzNTUwMmE0NTYwMWE0NTgwMWE0NTkwMWE1NWIwMWE1NWMwMWE2NWUwMWE2NjAwMWE2NjEwMGE3NjMwMGE3NjQwMGE3NjYwMGE3NjcwMGE4NjkwMGE4NmEwMGE4NmMwMGE4NmUwMGE4NmYwMGE4NzEwMGE4NzIwMWE4NzQwMWE4NzUwMWE4NzcwMWE4NzgwMWE4N2EwMmE4N2IwMmE4N2QwM2E4N2UwM2E4ODAwNGE4ODEwNGE3ODMwNWE3ODQwNWE3ODYwNmE2ODcwN2E2ODgwOGE2OGEwOWE1OGIwYWE1OGQwYmE1OGUwY2E0OGYwZGE0OTEwZWEzOTIwZmEzOTQxMGEyOTUxMWExOTYxM2ExOTgxNGEwOTkxNTlmOWExNjlmOWMxNzllOWQxODlkOWUxOTlkYTAxYTljYTExYjliYTIxZDlhYTMxZTlhYTUxZjk5YTYyMDk4YTcyMTk3YTgyMjk2YWEyMzk1YWIyNDk0YWMyNjk0YWQyNzkzYWUyODkyYjAyOTkxYjEyYTkwYjIyYjhmYjMyYzhlYjQyZThkYjUyZjhjYjYzMDhiYjczMThhYjgzMjg5YmEzMzg4YmIzNDg4YmMzNTg3YmQzNzg2YmUzODg1YmYzOTg0YzAzYTgzYzEzYjgyYzIzYzgxYzMzZDgwYzQzZTdmYzU0MDdlYzY0MTdkYzc0MjdjYzg0MzdiYzk0NDdhY2E0NTdhY2I0Njc5Y2M0Nzc4Y2M0OTc3Y2Q0YTc2Y2U0Yjc1Y2Y0Yzc0ZDA0ZDczZDE0ZTcyZDI0ZjcxZDM1MTcxZDQ1MjcwZDU1MzZmZDU1NDZlZDY1NTZkZDc1NjZjZDg1NzZiZDk1ODZhZGE1YTZhZGE1YjY5ZGI1YzY4ZGM1ZDY3ZGQ1ZTY2ZGU1ZjY1ZGU2MTY0ZGY2MjYzZTA2MzYzZTE2NDYyZTI2NTYxZTI2NjYwZTM2ODVmZTQ2OTVlZTU2YTVkZTU2YjVkZTY2YzVjZTc2ZTViZTc2ZjVhZTg3MDU5ZTk3MTU4ZTk3MjU3ZWE3NDU3ZWI3NTU2ZWI3NjU1ZWM3NzU0ZWQ3OTUzZWQ3YTUyZWU3YjUxZWY3YzUxZWY3ZTUwZjA3ZjRmZjA4MDRlZjE4MTRkZjE4MzRjZjI4NDRiZjM4NTRiZjM4NzRhZjQ4ODQ5ZjQ4OTQ4ZjU4YjQ3ZjU4YzQ2ZjY4ZDQ1ZjY4ZjQ0Zjc5MDQ0Zjc5MTQzZjc5MzQyZjg5NDQxZjg5NTQwZjk5NzNmZjk5ODNlZjk5YTNlZmE5YjNkZmE5YzNjZmE5ZTNiZmI5ZjNhZmJhMTM5ZmJhMjM4ZmNhMzM4ZmNhNTM3ZmNhNjM2ZmNhODM1ZmNhOTM0ZmRhYjMzZmRhYzMzZmRhZTMyZmRhZjMxZmRiMTMwZmRiMjJmZmRiNDJmZmRiNTJlZmViNzJkZmViODJjZmViYTJjZmViYjJiZmViZDJhZmViZTJhZmVjMDI5ZmRjMjI5ZmRjMzI4ZmRjNTI3ZmRjNjI3ZmRjODI3ZmRjYTI2ZmRjYjI2ZmNjZDI1ZmNjZTI1ZmNkMDI1ZmNkMjI1ZmJkMzI0ZmJkNTI0ZmJkNzI0ZmFkODI0ZmFkYTI0ZjlkYzI0ZjlkZDI1ZjhkZjI1ZjhlMTI1ZjdlMjI1ZjdlNDI1ZjZlNjI2ZjZlODI2ZjVlOTI2ZjVlYjI3ZjRlZDI3ZjNlZTI3ZjNmMDI3ZjJmMjI3ZjFmNDI2ZjFmNTI1ZjBmNzI0ZjBmOTIxIikpOwoKICAgIGZ1bmN0aW9uIHNlcXVlbnRpYWwkMShpbnRlcnBvbGF0b3IpIHsKICAgICAgdmFyIHgwID0gMCwKICAgICAgICAgIHgxID0gMSwKICAgICAgICAgIGNsYW1wID0gZmFsc2U7CgogICAgICBmdW5jdGlvbiBzY2FsZSh4KSB7CiAgICAgICAgdmFyIHQgPSAoeCAtIHgwKSAvICh4MSAtIHgwKTsKICAgICAgICByZXR1cm4gaW50ZXJwb2xhdG9yKGNsYW1wID8gTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgdCkpIDogdCk7CiAgICAgIH0KCiAgICAgIHNjYWxlLmRvbWFpbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4MCA9ICtfWzBdLCB4MSA9ICtfWzFdLCBzY2FsZSkgOiBbeDAsIHgxXTsKICAgICAgfTsKCiAgICAgIHNjYWxlLmNsYW1wID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNsYW1wID0gISFfLCBzY2FsZSkgOiBjbGFtcDsKICAgICAgfTsKCiAgICAgIHNjYWxlLmludGVycG9sYXRvciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpbnRlcnBvbGF0b3IgPSBfLCBzY2FsZSkgOiBpbnRlcnBvbGF0b3I7CiAgICAgIH07CgogICAgICBzY2FsZS5jb3B5ID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHNlcXVlbnRpYWwkMShpbnRlcnBvbGF0b3IpLmRvbWFpbihbeDAsIHgxXSkuY2xhbXAoY2xhbXApOwogICAgICB9OwoKICAgICAgcmV0dXJuIGxpbmVhcmlzaCQxKHNjYWxlKTsKICAgIH0KCiAgICB2YXIgeGh0bWwkMyA9ICJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sIjsKCiAgICB2YXIgbmFtZXNwYWNlcyQzID0gewogICAgICBzdmc6ICJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIsCiAgICAgIHhodG1sOiB4aHRtbCQzLAogICAgICB4bGluazogImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiLAogICAgICB4bWw6ICJodHRwOi8vd3d3LnczLm9yZy9YTUwvMTk5OC9uYW1lc3BhY2UiLAogICAgICB4bWxuczogImh0dHA6Ly93d3cudzMub3JnLzIwMDAveG1sbnMvIgogICAgfTsKCiAgICBmdW5jdGlvbiBuYW1lc3BhY2UkMyhuYW1lKSB7CiAgICAgIHZhciBwcmVmaXggPSBuYW1lICs9ICIiLCBpID0gcHJlZml4LmluZGV4T2YoIjoiKTsKICAgICAgaWYgKGkgPj0gMCAmJiAocHJlZml4ID0gbmFtZS5zbGljZSgwLCBpKSkgIT09ICJ4bWxucyIpIG5hbWUgPSBuYW1lLnNsaWNlKGkgKyAxKTsKICAgICAgcmV0dXJuIG5hbWVzcGFjZXMkMy5oYXNPd25Qcm9wZXJ0eShwcmVmaXgpID8ge3NwYWNlOiBuYW1lc3BhY2VzJDNbcHJlZml4XSwgbG9jYWw6IG5hbWV9IDogbmFtZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdG9ySW5oZXJpdCQzKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBkb2N1bWVudCA9IHRoaXMub3duZXJEb2N1bWVudCwKICAgICAgICAgICAgdXJpID0gdGhpcy5uYW1lc3BhY2VVUkk7CiAgICAgICAgcmV0dXJuIHVyaSA9PT0geGh0bWwkMyAmJiBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQubmFtZXNwYWNlVVJJID09PSB4aHRtbCQzCiAgICAgICAgICAgID8gZG9jdW1lbnQuY3JlYXRlRWxlbWVudChuYW1lKQogICAgICAgICAgICA6IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyh1cmksIG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3JGaXhlZCQzKGZ1bGxuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5vd25lckRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3IkMyhuYW1lKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQzKG5hbWUpOwogICAgICByZXR1cm4gKGZ1bGxuYW1lLmxvY2FsCiAgICAgICAgICA/IGNyZWF0b3JGaXhlZCQzCiAgICAgICAgICA6IGNyZWF0b3JJbmhlcml0JDMpKGZ1bGxuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub25lJDUoKSB7fQoKICAgIGZ1bmN0aW9uIHNlbGVjdG9yJDMoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHNlbGVjdG9yID09IG51bGwgPyBub25lJDUgOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2VsZWN0JDMoc2VsZWN0KSB7CiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvciQzKHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gbmV3IEFycmF5KG4pLCBub2RlLCBzdWJub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChzdWJub2RlID0gc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSkgewogICAgICAgICAgICBpZiAoIl9fZGF0YV9fIiBpbiBub2RlKSBzdWJub2RlLl9fZGF0YV9fID0gbm9kZS5fX2RhdGFfXzsKICAgICAgICAgICAgc3ViZ3JvdXBbaV0gPSBzdWJub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNShzdWJncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGVtcHR5JDUoKSB7CiAgICAgIHJldHVybiBbXTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3RvckFsbCQzKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiBzZWxlY3RvciA9PSBudWxsID8gZW1wdHkkNSA6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5U2VsZWN0b3JBbGwoc2VsZWN0b3IpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zZWxlY3RBbGwkMyhzZWxlY3QpIHsKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yQWxsJDMoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IFtdLCBwYXJlbnRzID0gW10sIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHN1Ymdyb3Vwcy5wdXNoKHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSk7CiAgICAgICAgICAgIHBhcmVudHMucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDUoc3ViZ3JvdXBzLCBwYXJlbnRzKTsKICAgIH0KCiAgICB2YXIgbWF0Y2hlciQzID0gZnVuY3Rpb24oc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLm1hdGNoZXMoc2VsZWN0b3IpOwogICAgICB9OwogICAgfTsKCiAgICBpZiAodHlwZW9mIGRvY3VtZW50ICE9PSAidW5kZWZpbmVkIikgewogICAgICB2YXIgZWxlbWVudCQzID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50OwogICAgICBpZiAoIWVsZW1lbnQkMy5tYXRjaGVzKSB7CiAgICAgICAgdmFyIHZlbmRvck1hdGNoZXMgPSBlbGVtZW50JDMud2Via2l0TWF0Y2hlc1NlbGVjdG9yCiAgICAgICAgICAgIHx8IGVsZW1lbnQkMy5tc01hdGNoZXNTZWxlY3RvcgogICAgICAgICAgICB8fCBlbGVtZW50JDMubW96TWF0Y2hlc1NlbGVjdG9yCiAgICAgICAgICAgIHx8IGVsZW1lbnQkMy5vTWF0Y2hlc1NlbGVjdG9yOwogICAgICAgIG1hdGNoZXIkMyA9IGZ1bmN0aW9uKHNlbGVjdG9yKSB7CiAgICAgICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB2ZW5kb3JNYXRjaGVzLmNhbGwodGhpcywgc2VsZWN0b3IpOwogICAgICAgICAgfTsKICAgICAgICB9OwogICAgICB9CiAgICB9CgogICAgdmFyIG1hdGNoZXIkNCA9IG1hdGNoZXIkMzsKCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZmlsdGVyJDMobWF0Y2gpIHsKICAgICAgaWYgKHR5cGVvZiBtYXRjaCAhPT0gImZ1bmN0aW9uIikgbWF0Y2ggPSBtYXRjaGVyJDQobWF0Y2gpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IFtdLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIG1hdGNoLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSB7CiAgICAgICAgICAgIHN1Ymdyb3VwLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ1KHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc3BhcnNlJDModXBkYXRlKSB7CiAgICAgIHJldHVybiBuZXcgQXJyYXkodXBkYXRlLmxlbmd0aCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VudGVyJDMoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDUodGhpcy5fZW50ZXIgfHwgdGhpcy5fZ3JvdXBzLm1hcChzcGFyc2UkMyksIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIEVudGVyTm9kZSQzKHBhcmVudCwgZGF0dW0pIHsKICAgICAgdGhpcy5vd25lckRvY3VtZW50ID0gcGFyZW50Lm93bmVyRG9jdW1lbnQ7CiAgICAgIHRoaXMubmFtZXNwYWNlVVJJID0gcGFyZW50Lm5hbWVzcGFjZVVSSTsKICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICAgIHRoaXMuX3BhcmVudCA9IHBhcmVudDsKICAgICAgdGhpcy5fX2RhdGFfXyA9IGRhdHVtOwogICAgfQoKICAgIEVudGVyTm9kZSQzLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IEVudGVyTm9kZSQzLAogICAgICBhcHBlbmRDaGlsZDogZnVuY3Rpb24oY2hpbGQpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5pbnNlcnRCZWZvcmUoY2hpbGQsIHRoaXMuX25leHQpOyB9LAogICAgICBpbnNlcnRCZWZvcmU6IGZ1bmN0aW9uKGNoaWxkLCBuZXh0KSB7IHJldHVybiB0aGlzLl9wYXJlbnQuaW5zZXJ0QmVmb3JlKGNoaWxkLCBuZXh0KTsgfSwKICAgICAgcXVlcnlTZWxlY3RvcjogZnVuY3Rpb24oc2VsZWN0b3IpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKTsgfSwKICAgICAgcXVlcnlTZWxlY3RvckFsbDogZnVuY3Rpb24oc2VsZWN0b3IpIHsgcmV0dXJuIHRoaXMuX3BhcmVudC5xdWVyeVNlbGVjdG9yQWxsKHNlbGVjdG9yKTsgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjb25zdGFudCRyKHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIHZhciBrZXlQcmVmaXgkNSA9ICIkIjsgLy8gUHJvdGVjdCBhZ2FpbnN0IGtleXMgbGlrZSDigJxfX3Byb3RvX1/igJ0uCgogICAgZnVuY3Rpb24gYmluZEluZGV4JDMocGFyZW50LCBncm91cCwgZW50ZXIsIHVwZGF0ZSwgZXhpdCwgZGF0YSkgewogICAgICB2YXIgaSA9IDAsCiAgICAgICAgICBub2RlLAogICAgICAgICAgZ3JvdXBMZW5ndGggPSBncm91cC5sZW5ndGgsCiAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGg7CgogICAgICAvLyBQdXQgYW55IG5vbi1udWxsIG5vZGVzIHRoYXQgZml0IGludG8gdXBkYXRlLgogICAgICAvLyBQdXQgYW55IG51bGwgbm9kZXMgaW50byBlbnRlci4KICAgICAgLy8gUHV0IGFueSByZW1haW5pbmcgZGF0YSBpbnRvIGVudGVyLgogICAgICBmb3IgKDsgaSA8IGRhdGFMZW5ndGg7ICsraSkgewogICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgIG5vZGUuX19kYXRhX18gPSBkYXRhW2ldOwogICAgICAgICAgdXBkYXRlW2ldID0gbm9kZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgZW50ZXJbaV0gPSBuZXcgRW50ZXJOb2RlJDMocGFyZW50LCBkYXRhW2ldKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIFB1dCBhbnkgbm9uLW51bGwgbm9kZXMgdGhhdCBkb27igJl0IGZpdCBpbnRvIGV4aXQuCiAgICAgIGZvciAoOyBpIDwgZ3JvdXBMZW5ndGg7ICsraSkgewogICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgIGV4aXRbaV0gPSBub2RlOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGJpbmRLZXkkMyhwYXJlbnQsIGdyb3VwLCBlbnRlciwgdXBkYXRlLCBleGl0LCBkYXRhLCBrZXkpIHsKICAgICAgdmFyIGksCiAgICAgICAgICBub2RlLAogICAgICAgICAgbm9kZUJ5S2V5VmFsdWUgPSB7fSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoLAogICAgICAgICAga2V5VmFsdWVzID0gbmV3IEFycmF5KGdyb3VwTGVuZ3RoKSwKICAgICAgICAgIGtleVZhbHVlOwoKICAgICAgLy8gQ29tcHV0ZSB0aGUga2V5IGZvciBlYWNoIG5vZGUuCiAgICAgIC8vIElmIG11bHRpcGxlIG5vZGVzIGhhdmUgdGhlIHNhbWUga2V5LCB0aGUgZHVwbGljYXRlcyBhcmUgYWRkZWQgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBrZXlWYWx1ZXNbaV0gPSBrZXlWYWx1ZSA9IGtleVByZWZpeCQ1ICsga2V5LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApOwogICAgICAgICAgaWYgKGtleVZhbHVlIGluIG5vZGVCeUtleVZhbHVlKSB7CiAgICAgICAgICAgIGV4aXRbaV0gPSBub2RlOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIENvbXB1dGUgdGhlIGtleSBmb3IgZWFjaCBkYXR1bS4KICAgICAgLy8gSWYgdGhlcmUgYSBub2RlIGFzc29jaWF0ZWQgd2l0aCB0aGlzIGtleSwgam9pbiBhbmQgYWRkIGl0IHRvIHVwZGF0ZS4KICAgICAgLy8gSWYgdGhlcmUgaXMgbm90IChvciB0aGUga2V5IGlzIGEgZHVwbGljYXRlKSwgYWRkIGl0IHRvIGVudGVyLgogICAgICBmb3IgKGkgPSAwOyBpIDwgZGF0YUxlbmd0aDsgKytpKSB7CiAgICAgICAga2V5VmFsdWUgPSBrZXlQcmVmaXgkNSArIGtleS5jYWxsKHBhcmVudCwgZGF0YVtpXSwgaSwgZGF0YSk7CiAgICAgICAgaWYgKG5vZGUgPSBub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZV0pIHsKICAgICAgICAgIHVwZGF0ZVtpXSA9IG5vZGU7CiAgICAgICAgICBub2RlLl9fZGF0YV9fID0gZGF0YVtpXTsKICAgICAgICAgIG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSA9IG51bGw7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVudGVyW2ldID0gbmV3IEVudGVyTm9kZSQzKHBhcmVudCwgZGF0YVtpXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBBZGQgYW55IHJlbWFpbmluZyBub2RlcyB0aGF0IHdlcmUgbm90IGJvdW5kIHRvIGRhdGEgdG8gZXhpdC4KICAgICAgZm9yIChpID0gMDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKG5vZGVCeUtleVZhbHVlW2tleVZhbHVlc1tpXV0gPT09IG5vZGUpKSB7CiAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZGF0YSQzKHZhbHVlLCBrZXkpIHsKICAgICAgaWYgKCF2YWx1ZSkgewogICAgICAgIGRhdGEgPSBuZXcgQXJyYXkodGhpcy5zaXplKCkpLCBqID0gLTE7CiAgICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKGQpIHsgZGF0YVsrK2pdID0gZDsgfSk7CiAgICAgICAgcmV0dXJuIGRhdGE7CiAgICAgIH0KCiAgICAgIHZhciBiaW5kID0ga2V5ID8gYmluZEtleSQzIDogYmluZEluZGV4JDMsCiAgICAgICAgICBwYXJlbnRzID0gdGhpcy5fcGFyZW50cywKICAgICAgICAgIGdyb3VwcyA9IHRoaXMuX2dyb3VwczsKCiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHZhbHVlID0gY29uc3RhbnQkcih2YWx1ZSk7CgogICAgICBmb3IgKHZhciBtID0gZ3JvdXBzLmxlbmd0aCwgdXBkYXRlID0gbmV3IEFycmF5KG0pLCBlbnRlciA9IG5ldyBBcnJheShtKSwgZXhpdCA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICB2YXIgcGFyZW50ID0gcGFyZW50c1tqXSwKICAgICAgICAgICAgZ3JvdXAgPSBncm91cHNbal0sCiAgICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgICBkYXRhID0gdmFsdWUuY2FsbChwYXJlbnQsIHBhcmVudCAmJiBwYXJlbnQuX19kYXRhX18sIGosIHBhcmVudHMpLAogICAgICAgICAgICBkYXRhTGVuZ3RoID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIGVudGVyR3JvdXAgPSBlbnRlcltqXSA9IG5ldyBBcnJheShkYXRhTGVuZ3RoKSwKICAgICAgICAgICAgdXBkYXRlR3JvdXAgPSB1cGRhdGVbal0gPSBuZXcgQXJyYXkoZGF0YUxlbmd0aCksCiAgICAgICAgICAgIGV4aXRHcm91cCA9IGV4aXRbal0gPSBuZXcgQXJyYXkoZ3JvdXBMZW5ndGgpOwoKICAgICAgICBiaW5kKHBhcmVudCwgZ3JvdXAsIGVudGVyR3JvdXAsIHVwZGF0ZUdyb3VwLCBleGl0R3JvdXAsIGRhdGEsIGtleSk7CgogICAgICAgIC8vIE5vdyBjb25uZWN0IHRoZSBlbnRlciBub2RlcyB0byB0aGVpciBmb2xsb3dpbmcgdXBkYXRlIG5vZGUsIHN1Y2ggdGhhdAogICAgICAgIC8vIGFwcGVuZENoaWxkIGNhbiBpbnNlcnQgdGhlIG1hdGVyaWFsaXplZCBlbnRlciBub2RlIGJlZm9yZSB0aGlzIG5vZGUsCiAgICAgICAgLy8gcmF0aGVyIHRoYW4gYXQgdGhlIGVuZCBvZiB0aGUgcGFyZW50IG5vZGUuCiAgICAgICAgZm9yICh2YXIgaTAgPSAwLCBpMSA9IDAsIHByZXZpb3VzLCBuZXh0OyBpMCA8IGRhdGFMZW5ndGg7ICsraTApIHsKICAgICAgICAgIGlmIChwcmV2aW91cyA9IGVudGVyR3JvdXBbaTBdKSB7CiAgICAgICAgICAgIGlmIChpMCA+PSBpMSkgaTEgPSBpMCArIDE7CiAgICAgICAgICAgIHdoaWxlICghKG5leHQgPSB1cGRhdGVHcm91cFtpMV0pICYmICsraTEgPCBkYXRhTGVuZ3RoKTsKICAgICAgICAgICAgcHJldmlvdXMuX25leHQgPSBuZXh0IHx8IG51bGw7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICB1cGRhdGUgPSBuZXcgU2VsZWN0aW9uJDUodXBkYXRlLCBwYXJlbnRzKTsKICAgICAgdXBkYXRlLl9lbnRlciA9IGVudGVyOwogICAgICB1cGRhdGUuX2V4aXQgPSBleGl0OwogICAgICByZXR1cm4gdXBkYXRlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9leGl0JDMoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDUodGhpcy5fZXhpdCB8fCB0aGlzLl9ncm91cHMubWFwKHNwYXJzZSQzKSwgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX21lcmdlJDMoc2VsZWN0aW9uKSB7CgogICAgICBmb3IgKHZhciBncm91cHMwID0gdGhpcy5fZ3JvdXBzLCBncm91cHMxID0gc2VsZWN0aW9uLl9ncm91cHMsIG0wID0gZ3JvdXBzMC5sZW5ndGgsIG0xID0gZ3JvdXBzMS5sZW5ndGgsIG0gPSBNYXRoLm1pbihtMCwgbTEpLCBtZXJnZXMgPSBuZXcgQXJyYXkobTApLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwMCA9IGdyb3VwczBbal0sIGdyb3VwMSA9IGdyb3VwczFbal0sIG4gPSBncm91cDAubGVuZ3RoLCBtZXJnZSA9IG1lcmdlc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXAwW2ldIHx8IGdyb3VwMVtpXSkgewogICAgICAgICAgICBtZXJnZVtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3IgKDsgaiA8IG0wOyArK2opIHsKICAgICAgICBtZXJnZXNbal0gPSBncm91cHMwW2pdOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ1KG1lcmdlcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX29yZGVyJDMoKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAtMSwgbSA9IGdyb3Vwcy5sZW5ndGg7ICsraiA8IG07KSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIGkgPSBncm91cC5sZW5ndGggLSAxLCBuZXh0ID0gZ3JvdXBbaV0sIG5vZGU7IC0taSA+PSAwOykgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBpZiAobmV4dCAmJiBuZXh0ICE9PSBub2RlLm5leHRTaWJsaW5nKSBuZXh0LnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKG5vZGUsIG5leHQpOwogICAgICAgICAgICBuZXh0ID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zb3J0JDMoY29tcGFyZSkgewogICAgICBpZiAoIWNvbXBhcmUpIGNvbXBhcmUgPSBhc2NlbmRpbmckYTsKCiAgICAgIGZ1bmN0aW9uIGNvbXBhcmVOb2RlKGEsIGIpIHsKICAgICAgICByZXR1cm4gYSAmJiBiID8gY29tcGFyZShhLl9fZGF0YV9fLCBiLl9fZGF0YV9fKSA6ICFhIC0gIWI7CiAgICAgIH0KCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHNvcnRncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHNvcnRncm91cCA9IHNvcnRncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICAgIHNvcnRncm91cFtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHNvcnRncm91cC5zb3J0KGNvbXBhcmVOb2RlKTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNShzb3J0Z3JvdXBzLCB0aGlzLl9wYXJlbnRzKS5vcmRlcigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFzY2VuZGluZyRhKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPCBiID8gLTEgOiBhID4gYiA/IDEgOiBhID49IGIgPyAwIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jYWxsJDMoKSB7CiAgICAgIHZhciBjYWxsYmFjayA9IGFyZ3VtZW50c1swXTsKICAgICAgYXJndW1lbnRzWzBdID0gdGhpczsKICAgICAgY2FsbGJhY2suYXBwbHkobnVsbCwgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX25vZGVzJDMoKSB7CiAgICAgIHZhciBub2RlcyA9IG5ldyBBcnJheSh0aGlzLnNpemUoKSksIGkgPSAtMTsKICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKCkgeyBub2Rlc1srK2ldID0gdGhpczsgfSk7CiAgICAgIHJldHVybiBub2RlczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbm9kZSQzKCkgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gMCwgbSA9IGdyb3Vwcy5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IDAsIG4gPSBncm91cC5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHZhciBub2RlID0gZ3JvdXBbaV07CiAgICAgICAgICBpZiAobm9kZSkgcmV0dXJuIG5vZGU7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc2l6ZSQzKCkgewogICAgICB2YXIgc2l6ZSA9IDA7CiAgICAgIHRoaXMuZWFjaChmdW5jdGlvbigpIHsgKytzaXplOyB9KTsKICAgICAgcmV0dXJuIHNpemU7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VtcHR5JDMoKSB7CiAgICAgIHJldHVybiAhdGhpcy5ub2RlKCk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2VhY2gkMyhjYWxsYmFjaykgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gMCwgbSA9IGdyb3Vwcy5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgaSA9IDAsIG4gPSBncm91cC5sZW5ndGgsIG5vZGU7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIGNhbGxiYWNrLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZSQ1KG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJSZW1vdmVOUyQ1KGZ1bGxuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckNvbnN0YW50JDUobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIHZhbHVlKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnROUyQ1KGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwsIHZhbHVlKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb24kNShuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgIGVsc2UgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgdik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckZ1bmN0aW9uTlMkNShmdWxsbmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgICAgZWxzZSB0aGlzLnNldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCwgdik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2F0dHIkMyhuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgZnVsbG5hbWUgPSBuYW1lc3BhY2UkMyhuYW1lKTsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBub2RlID0gdGhpcy5ub2RlKCk7CiAgICAgICAgcmV0dXJuIGZ1bGxuYW1lLmxvY2FsCiAgICAgICAgICAgID8gbm9kZS5nZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpCiAgICAgICAgICAgIDogbm9kZS5nZXRBdHRyaWJ1dGUoZnVsbG5hbWUpOwogICAgICB9CgogICAgICByZXR1cm4gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICA/IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJSZW1vdmVOUyQ1IDogYXR0clJlbW92ZSQ1KSA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckZ1bmN0aW9uTlMkNSA6IGF0dHJGdW5jdGlvbiQ1KQogICAgICAgICAgOiAoZnVsbG5hbWUubG9jYWwgPyBhdHRyQ29uc3RhbnROUyQ1IDogYXR0ckNvbnN0YW50JDUpKSkoZnVsbG5hbWUsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFZpZXckMyhub2RlKSB7CiAgICAgIHJldHVybiAobm9kZS5vd25lckRvY3VtZW50ICYmIG5vZGUub3duZXJEb2N1bWVudC5kZWZhdWx0VmlldykgLy8gbm9kZSBpcyBhIE5vZGUKICAgICAgICAgIHx8IChub2RlLmRvY3VtZW50ICYmIG5vZGUpIC8vIG5vZGUgaXMgYSBXaW5kb3cKICAgICAgICAgIHx8IG5vZGUuZGVmYXVsdFZpZXc7IC8vIG5vZGUgaXMgYSBEb2N1bWVudAogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlUmVtb3ZlJDUobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUNvbnN0YW50JDUobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLnNldFByb3BlcnR5KG5hbWUsIHZhbHVlLCBwcmlvcml0eSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVGdW5jdGlvbiQ1KG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSk7CiAgICAgICAgZWxzZSB0aGlzLnN0eWxlLnNldFByb3BlcnR5KG5hbWUsIHYsIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc3R5bGUkMyhuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPiAxCiAgICAgICAgICA/IHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgICAgPyBzdHlsZVJlbW92ZSQ1IDogdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgICA/IHN0eWxlRnVuY3Rpb24kNQogICAgICAgICAgICAgICAgOiBzdHlsZUNvbnN0YW50JDUpKG5hbWUsIHZhbHVlLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSkpCiAgICAgICAgICA6IHN0eWxlVmFsdWUkMyh0aGlzLm5vZGUoKSwgbmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVWYWx1ZSQzKG5vZGUsIG5hbWUpIHsKICAgICAgcmV0dXJuIG5vZGUuc3R5bGUuZ2V0UHJvcGVydHlWYWx1ZShuYW1lKQogICAgICAgICAgfHwgZGVmYXVsdFZpZXckMyhub2RlKS5nZXRDb21wdXRlZFN0eWxlKG5vZGUsIG51bGwpLmdldFByb3BlcnR5VmFsdWUobmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJvcGVydHlSZW1vdmUkMyhuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBkZWxldGUgdGhpc1tuYW1lXTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eUNvbnN0YW50JDMobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXNbbmFtZV0gPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eUZ1bmN0aW9uJDMobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAodiA9PSBudWxsKSBkZWxldGUgdGhpc1tuYW1lXTsKICAgICAgICBlbHNlIHRoaXNbbmFtZV0gPSB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9wcm9wZXJ0eSQzKG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID4gMQogICAgICAgICAgPyB0aGlzLmVhY2goKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IHByb3BlcnR5UmVtb3ZlJDMgOiB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IHByb3BlcnR5RnVuY3Rpb24kMwogICAgICAgICAgICAgIDogcHJvcGVydHlDb25zdGFudCQzKShuYW1lLCB2YWx1ZSkpCiAgICAgICAgICA6IHRoaXMubm9kZSgpW25hbWVdOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzQXJyYXkkMyhzdHJpbmcpIHsKICAgICAgcmV0dXJuIHN0cmluZy50cmltKCkuc3BsaXQoL158XHMrLyk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NMaXN0JDMobm9kZSkgewogICAgICByZXR1cm4gbm9kZS5jbGFzc0xpc3QgfHwgbmV3IENsYXNzTGlzdCQzKG5vZGUpOwogICAgfQoKICAgIGZ1bmN0aW9uIENsYXNzTGlzdCQzKG5vZGUpIHsKICAgICAgdGhpcy5fbm9kZSA9IG5vZGU7CiAgICAgIHRoaXMuX25hbWVzID0gY2xhc3NBcnJheSQzKG5vZGUuZ2V0QXR0cmlidXRlKCJjbGFzcyIpIHx8ICIiKTsKICAgIH0KCiAgICBDbGFzc0xpc3QkMy5wcm90b3R5cGUgPSB7CiAgICAgIGFkZDogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHZhciBpID0gdGhpcy5fbmFtZXMuaW5kZXhPZihuYW1lKTsKICAgICAgICBpZiAoaSA8IDApIHsKICAgICAgICAgIHRoaXMuX25hbWVzLnB1c2gobmFtZSk7CiAgICAgICAgICB0aGlzLl9ub2RlLnNldEF0dHJpYnV0ZSgiY2xhc3MiLCB0aGlzLl9uYW1lcy5qb2luKCIgIikpOwogICAgICAgIH0KICAgICAgfSwKICAgICAgcmVtb3ZlOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpOwogICAgICAgIGlmIChpID49IDApIHsKICAgICAgICAgIHRoaXMuX25hbWVzLnNwbGljZShpLCAxKTsKICAgICAgICAgIHRoaXMuX25vZGUuc2V0QXR0cmlidXRlKCJjbGFzcyIsIHRoaXMuX25hbWVzLmpvaW4oIiAiKSk7CiAgICAgICAgfQogICAgICB9LAogICAgICBjb250YWluczogZnVuY3Rpb24obmFtZSkgewogICAgICAgIHJldHVybiB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpID49IDA7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY2xhc3NlZEFkZCQzKG5vZGUsIG5hbWVzKSB7CiAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0JDMobm9kZSksIGkgPSAtMSwgbiA9IG5hbWVzLmxlbmd0aDsKICAgICAgd2hpbGUgKCsraSA8IG4pIGxpc3QuYWRkKG5hbWVzW2ldKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkUmVtb3ZlJDMobm9kZSwgbmFtZXMpIHsKICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3QkMyhub2RlKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbGlzdC5yZW1vdmUobmFtZXNbaV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRUcnVlJDMobmFtZXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGNsYXNzZWRBZGQkMyh0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZEZhbHNlJDMobmFtZXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGNsYXNzZWRSZW1vdmUkMyh0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZEZ1bmN0aW9uJDMobmFtZXMsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICAodmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKSA/IGNsYXNzZWRBZGQkMyA6IGNsYXNzZWRSZW1vdmUkMykodGhpcywgbmFtZXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbGFzc2VkJDMobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIG5hbWVzID0gY2xhc3NBcnJheSQzKG5hbWUgKyAiIik7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgbGlzdCA9IGNsYXNzTGlzdCQzKHRoaXMubm9kZSgpKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoIWxpc3QuY29udGFpbnMobmFtZXNbaV0pKSByZXR1cm4gZmFsc2U7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyBjbGFzc2VkRnVuY3Rpb24kMyA6IHZhbHVlCiAgICAgICAgICA/IGNsYXNzZWRUcnVlJDMKICAgICAgICAgIDogY2xhc3NlZEZhbHNlJDMpKG5hbWVzLCB2YWx1ZSkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRSZW1vdmUkMygpIHsKICAgICAgdGhpcy50ZXh0Q29udGVudCA9ICIiOwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRDb25zdGFudCQ1KHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dEZ1bmN0aW9uJDUodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLnRleHRDb250ZW50ID0gdiA9PSBudWxsID8gIiIgOiB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl90ZXh0JDModmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IHRleHRSZW1vdmUkMyA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IHRleHRGdW5jdGlvbiQ1CiAgICAgICAgICAgICAgOiB0ZXh0Q29uc3RhbnQkNSkodmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS50ZXh0Q29udGVudDsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sUmVtb3ZlJDMoKSB7CiAgICAgIHRoaXMuaW5uZXJIVE1MID0gIiI7CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbENvbnN0YW50JDModmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuaW5uZXJIVE1MID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaHRtbEZ1bmN0aW9uJDModmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2ID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICB0aGlzLmlubmVySFRNTCA9IHYgPT0gbnVsbCA/ICIiIDogdjsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25faHRtbCQzKHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgPyBodG1sUmVtb3ZlJDMgOiAodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBodG1sRnVuY3Rpb24kMwogICAgICAgICAgICAgIDogaHRtbENvbnN0YW50JDMpKHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKCkuaW5uZXJIVE1MOwogICAgfQoKICAgIGZ1bmN0aW9uIHJhaXNlJDQoKSB7CiAgICAgIGlmICh0aGlzLm5leHRTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuYXBwZW5kQ2hpbGQodGhpcyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3JhaXNlJDMoKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2gocmFpc2UkNCk7CiAgICB9CgogICAgZnVuY3Rpb24gbG93ZXIkMygpIHsKICAgICAgaWYgKHRoaXMucHJldmlvdXNTaWJsaW5nKSB0aGlzLnBhcmVudE5vZGUuaW5zZXJ0QmVmb3JlKHRoaXMsIHRoaXMucGFyZW50Tm9kZS5maXJzdENoaWxkKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbG93ZXIkMygpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChsb3dlciQzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fYXBwZW5kJDMobmFtZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvciQzKG5hbWUpOwogICAgICByZXR1cm4gdGhpcy5zZWxlY3QoZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuYXBwZW5kQ2hpbGQoY3JlYXRlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb25zdGFudE51bGwkMygpIHsKICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2luc2VydCQzKG5hbWUsIGJlZm9yZSkgewogICAgICB2YXIgY3JlYXRlID0gdHlwZW9mIG5hbWUgPT09ICJmdW5jdGlvbiIgPyBuYW1lIDogY3JlYXRvciQzKG5hbWUpLAogICAgICAgICAgc2VsZWN0ID0gYmVmb3JlID09IG51bGwgPyBjb25zdGFudE51bGwkMyA6IHR5cGVvZiBiZWZvcmUgPT09ICJmdW5jdGlvbiIgPyBiZWZvcmUgOiBzZWxlY3RvciQzKGJlZm9yZSk7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5pbnNlcnRCZWZvcmUoY3JlYXRlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksIHNlbGVjdC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIHx8IG51bGwpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmUkMygpIHsKICAgICAgdmFyIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgaWYgKHBhcmVudCkgcGFyZW50LnJlbW92ZUNoaWxkKHRoaXMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9yZW1vdmUkMygpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChyZW1vdmUkMyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Nsb25lU2hhbGxvdyQzKCkgewogICAgICByZXR1cm4gdGhpcy5wYXJlbnROb2RlLmluc2VydEJlZm9yZSh0aGlzLmNsb25lTm9kZShmYWxzZSksIHRoaXMubmV4dFNpYmxpbmcpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZURlZXAkMygpIHsKICAgICAgcmV0dXJuIHRoaXMucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUodGhpcy5jbG9uZU5vZGUodHJ1ZSksIHRoaXMubmV4dFNpYmxpbmcpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZSQzKGRlZXApIHsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGRlZXAgPyBzZWxlY3Rpb25fY2xvbmVEZWVwJDMgOiBzZWxlY3Rpb25fY2xvbmVTaGFsbG93JDMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kYXR1bSQzKHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMucHJvcGVydHkoIl9fZGF0YV9fIiwgdmFsdWUpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLl9fZGF0YV9fOwogICAgfQoKICAgIHZhciBmaWx0ZXJFdmVudHMkMyA9IHt9OwoKICAgIHZhciBldmVudCQzID0gbnVsbDsKCiAgICBpZiAodHlwZW9mIGRvY3VtZW50ICE9PSAidW5kZWZpbmVkIikgewogICAgICB2YXIgZWxlbWVudCQ0ID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50OwogICAgICBpZiAoISgib25tb3VzZWVudGVyIiBpbiBlbGVtZW50JDQpKSB7CiAgICAgICAgZmlsdGVyRXZlbnRzJDMgPSB7bW91c2VlbnRlcjogIm1vdXNlb3ZlciIsIG1vdXNlbGVhdmU6ICJtb3VzZW91dCJ9OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZmlsdGVyQ29udGV4dExpc3RlbmVyJDMobGlzdGVuZXIsIGluZGV4LCBncm91cCkgewogICAgICBsaXN0ZW5lciA9IGNvbnRleHRMaXN0ZW5lciQzKGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApOwogICAgICByZXR1cm4gZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgcmVsYXRlZCA9IGV2ZW50LnJlbGF0ZWRUYXJnZXQ7CiAgICAgICAgaWYgKCFyZWxhdGVkIHx8IChyZWxhdGVkICE9PSB0aGlzICYmICEocmVsYXRlZC5jb21wYXJlRG9jdW1lbnRQb3NpdGlvbih0aGlzKSAmIDgpKSkgewogICAgICAgICAgbGlzdGVuZXIuY2FsbCh0aGlzLCBldmVudCk7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRleHRMaXN0ZW5lciQzKGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGV2ZW50MSkgewogICAgICAgIHZhciBldmVudDAgPSBldmVudCQzOyAvLyBFdmVudHMgY2FuIGJlIHJlZW50cmFudCAoZS5nLiwgZm9jdXMpLgogICAgICAgIGV2ZW50JDMgPSBldmVudDE7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIGxpc3RlbmVyLmNhbGwodGhpcywgdGhpcy5fX2RhdGFfXywgaW5kZXgsIGdyb3VwKTsKICAgICAgICB9IGZpbmFsbHkgewogICAgICAgICAgZXZlbnQkMyA9IGV2ZW50MDsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VUeXBlbmFtZXMkOCh0eXBlbmFtZXMpIHsKICAgICAgcmV0dXJuIHR5cGVuYW1lcy50cmltKCkuc3BsaXQoL158XHMrLykubWFwKGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgbmFtZSA9ICIiLCBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgbmFtZSA9IHQuc2xpY2UoaSArIDEpLCB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICByZXR1cm4ge3R5cGU6IHQsIG5hbWU6IG5hbWV9OwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBvblJlbW92ZSQzKHR5cGVuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgb24gPSB0aGlzLl9fb247CiAgICAgICAgaWYgKCFvbikgcmV0dXJuOwogICAgICAgIGZvciAodmFyIGogPSAwLCBpID0gLTEsIG0gPSBvbi5sZW5ndGgsIG87IGogPCBtOyArK2opIHsKICAgICAgICAgIGlmIChvID0gb25bal0sICghdHlwZW5hbWUudHlwZSB8fCBvLnR5cGUgPT09IHR5cGVuYW1lLnR5cGUpICYmIG8ubmFtZSA9PT0gdHlwZW5hbWUubmFtZSkgewogICAgICAgICAgICB0aGlzLnJlbW92ZUV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyLCBvLmNhcHR1cmUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgb25bKytpXSA9IG87CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGlmICgrK2kpIG9uLmxlbmd0aCA9IGk7CiAgICAgICAgZWxzZSBkZWxldGUgdGhpcy5fX29uOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9uQWRkJDModHlwZW5hbWUsIHZhbHVlLCBjYXB0dXJlKSB7CiAgICAgIHZhciB3cmFwID0gZmlsdGVyRXZlbnRzJDMuaGFzT3duUHJvcGVydHkodHlwZW5hbWUudHlwZSkgPyBmaWx0ZXJDb250ZXh0TGlzdGVuZXIkMyA6IGNvbnRleHRMaXN0ZW5lciQzOwogICAgICByZXR1cm4gZnVuY3Rpb24oZCwgaSwgZ3JvdXApIHsKICAgICAgICB2YXIgb24gPSB0aGlzLl9fb24sIG8sIGxpc3RlbmVyID0gd3JhcCh2YWx1ZSwgaSwgZ3JvdXApOwogICAgICAgIGlmIChvbikgZm9yICh2YXIgaiA9IDAsIG0gPSBvbi5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICAgIGlmICgobyA9IG9uW2pdKS50eXBlID09PSB0eXBlbmFtZS50eXBlICYmIG8ubmFtZSA9PT0gdHlwZW5hbWUubmFtZSkgewogICAgICAgICAgICB0aGlzLnJlbW92ZUV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyLCBvLmNhcHR1cmUpOwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyID0gbGlzdGVuZXIsIG8uY2FwdHVyZSA9IGNhcHR1cmUpOwogICAgICAgICAgICBvLnZhbHVlID0gdmFsdWU7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKHR5cGVuYW1lLnR5cGUsIGxpc3RlbmVyLCBjYXB0dXJlKTsKICAgICAgICBvID0ge3R5cGU6IHR5cGVuYW1lLnR5cGUsIG5hbWU6IHR5cGVuYW1lLm5hbWUsIHZhbHVlOiB2YWx1ZSwgbGlzdGVuZXI6IGxpc3RlbmVyLCBjYXB0dXJlOiBjYXB0dXJlfTsKICAgICAgICBpZiAoIW9uKSB0aGlzLl9fb24gPSBbb107CiAgICAgICAgZWxzZSBvbi5wdXNoKG8pOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9vbiQzKHR5cGVuYW1lLCB2YWx1ZSwgY2FwdHVyZSkgewogICAgICB2YXIgdHlwZW5hbWVzID0gcGFyc2VUeXBlbmFtZXMkOCh0eXBlbmFtZSArICIiKSwgaSwgbiA9IHR5cGVuYW1lcy5sZW5ndGgsIHQ7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgb24gPSB0aGlzLm5vZGUoKS5fX29uOwogICAgICAgIGlmIChvbikgZm9yICh2YXIgaiA9IDAsIG0gPSBvbi5sZW5ndGgsIG87IGogPCBtOyArK2opIHsKICAgICAgICAgIGZvciAoaSA9IDAsIG8gPSBvbltqXTsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAoKHQgPSB0eXBlbmFtZXNbaV0pLnR5cGUgPT09IG8udHlwZSAmJiB0Lm5hbWUgPT09IG8ubmFtZSkgewogICAgICAgICAgICAgIHJldHVybiBvLnZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgb24gPSB2YWx1ZSA/IG9uQWRkJDMgOiBvblJlbW92ZSQzOwogICAgICBpZiAoY2FwdHVyZSA9PSBudWxsKSBjYXB0dXJlID0gZmFsc2U7CiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHRoaXMuZWFjaChvbih0eXBlbmFtZXNbaV0sIHZhbHVlLCBjYXB0dXJlKSk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1c3RvbUV2ZW50JDMoZXZlbnQxLCBsaXN0ZW5lciwgdGhhdCwgYXJncykgewogICAgICB2YXIgZXZlbnQwID0gZXZlbnQkMzsKICAgICAgZXZlbnQxLnNvdXJjZUV2ZW50ID0gZXZlbnQkMzsKICAgICAgZXZlbnQkMyA9IGV2ZW50MTsKICAgICAgdHJ5IHsKICAgICAgICByZXR1cm4gbGlzdGVuZXIuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0gZmluYWxseSB7CiAgICAgICAgZXZlbnQkMyA9IGV2ZW50MDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoRXZlbnQkMyhub2RlLCB0eXBlLCBwYXJhbXMpIHsKICAgICAgdmFyIHdpbmRvdyA9IGRlZmF1bHRWaWV3JDMobm9kZSksCiAgICAgICAgICBldmVudCA9IHdpbmRvdy5DdXN0b21FdmVudDsKCiAgICAgIGlmICh0eXBlb2YgZXZlbnQgPT09ICJmdW5jdGlvbiIpIHsKICAgICAgICBldmVudCA9IG5ldyBldmVudCh0eXBlLCBwYXJhbXMpOwogICAgICB9IGVsc2UgewogICAgICAgIGV2ZW50ID0gd2luZG93LmRvY3VtZW50LmNyZWF0ZUV2ZW50KCJFdmVudCIpOwogICAgICAgIGlmIChwYXJhbXMpIGV2ZW50LmluaXRFdmVudCh0eXBlLCBwYXJhbXMuYnViYmxlcywgcGFyYW1zLmNhbmNlbGFibGUpLCBldmVudC5kZXRhaWwgPSBwYXJhbXMuZGV0YWlsOwogICAgICAgIGVsc2UgZXZlbnQuaW5pdEV2ZW50KHR5cGUsIGZhbHNlLCBmYWxzZSk7CiAgICAgIH0KCiAgICAgIG5vZGUuZGlzcGF0Y2hFdmVudChldmVudCk7CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hDb25zdGFudCQzKHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRpc3BhdGNoRXZlbnQkMyh0aGlzLCB0eXBlLCBwYXJhbXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoRnVuY3Rpb24kMyh0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkaXNwYXRjaEV2ZW50JDModGhpcywgdHlwZSwgcGFyYW1zLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kaXNwYXRjaCQzKHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gdGhpcy5lYWNoKCh0eXBlb2YgcGFyYW1zID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IGRpc3BhdGNoRnVuY3Rpb24kMwogICAgICAgICAgOiBkaXNwYXRjaENvbnN0YW50JDMpKHR5cGUsIHBhcmFtcykpOwogICAgfQoKICAgIHZhciByb290JDUgPSBbbnVsbF07CgogICAgZnVuY3Rpb24gU2VsZWN0aW9uJDUoZ3JvdXBzLCBwYXJlbnRzKSB7CiAgICAgIHRoaXMuX2dyb3VwcyA9IGdyb3VwczsKICAgICAgdGhpcy5fcGFyZW50cyA9IHBhcmVudHM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uJDMoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDUoW1tkb2N1bWVudC5kb2N1bWVudEVsZW1lbnRdXSwgcm9vdCQ1KTsKICAgIH0KCiAgICBTZWxlY3Rpb24kNS5wcm90b3R5cGUgPSBzZWxlY3Rpb24kMy5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBTZWxlY3Rpb24kNSwKICAgICAgc2VsZWN0OiBzZWxlY3Rpb25fc2VsZWN0JDMsCiAgICAgIHNlbGVjdEFsbDogc2VsZWN0aW9uX3NlbGVjdEFsbCQzLAogICAgICBmaWx0ZXI6IHNlbGVjdGlvbl9maWx0ZXIkMywKICAgICAgZGF0YTogc2VsZWN0aW9uX2RhdGEkMywKICAgICAgZW50ZXI6IHNlbGVjdGlvbl9lbnRlciQzLAogICAgICBleGl0OiBzZWxlY3Rpb25fZXhpdCQzLAogICAgICBtZXJnZTogc2VsZWN0aW9uX21lcmdlJDMsCiAgICAgIG9yZGVyOiBzZWxlY3Rpb25fb3JkZXIkMywKICAgICAgc29ydDogc2VsZWN0aW9uX3NvcnQkMywKICAgICAgY2FsbDogc2VsZWN0aW9uX2NhbGwkMywKICAgICAgbm9kZXM6IHNlbGVjdGlvbl9ub2RlcyQzLAogICAgICBub2RlOiBzZWxlY3Rpb25fbm9kZSQzLAogICAgICBzaXplOiBzZWxlY3Rpb25fc2l6ZSQzLAogICAgICBlbXB0eTogc2VsZWN0aW9uX2VtcHR5JDMsCiAgICAgIGVhY2g6IHNlbGVjdGlvbl9lYWNoJDMsCiAgICAgIGF0dHI6IHNlbGVjdGlvbl9hdHRyJDMsCiAgICAgIHN0eWxlOiBzZWxlY3Rpb25fc3R5bGUkMywKICAgICAgcHJvcGVydHk6IHNlbGVjdGlvbl9wcm9wZXJ0eSQzLAogICAgICBjbGFzc2VkOiBzZWxlY3Rpb25fY2xhc3NlZCQzLAogICAgICB0ZXh0OiBzZWxlY3Rpb25fdGV4dCQzLAogICAgICBodG1sOiBzZWxlY3Rpb25faHRtbCQzLAogICAgICByYWlzZTogc2VsZWN0aW9uX3JhaXNlJDMsCiAgICAgIGxvd2VyOiBzZWxlY3Rpb25fbG93ZXIkMywKICAgICAgYXBwZW5kOiBzZWxlY3Rpb25fYXBwZW5kJDMsCiAgICAgIGluc2VydDogc2VsZWN0aW9uX2luc2VydCQzLAogICAgICByZW1vdmU6IHNlbGVjdGlvbl9yZW1vdmUkMywKICAgICAgY2xvbmU6IHNlbGVjdGlvbl9jbG9uZSQzLAogICAgICBkYXR1bTogc2VsZWN0aW9uX2RhdHVtJDMsCiAgICAgIG9uOiBzZWxlY3Rpb25fb24kMywKICAgICAgZGlzcGF0Y2g6IHNlbGVjdGlvbl9kaXNwYXRjaCQzCiAgICB9OwoKICAgIGZ1bmN0aW9uIHNlbGVjdCQzKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiB0eXBlb2Ygc2VsZWN0b3IgPT09ICJzdHJpbmciCiAgICAgICAgICA/IG5ldyBTZWxlY3Rpb24kNShbW2RvY3VtZW50LnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpXV0sIFtkb2N1bWVudC5kb2N1bWVudEVsZW1lbnRdKQogICAgICAgICAgOiBuZXcgU2VsZWN0aW9uJDUoW1tzZWxlY3Rvcl1dLCByb290JDUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZSQzKG5hbWUpIHsKICAgICAgcmV0dXJuIHNlbGVjdCQzKGNyZWF0b3IkMyhuYW1lKS5jYWxsKGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCkpOwogICAgfQoKICAgIHZhciBuZXh0SWQkMSA9IDA7CgogICAgZnVuY3Rpb24gbG9jYWwkMygpIHsKICAgICAgcmV0dXJuIG5ldyBMb2NhbCQxOwogICAgfQoKICAgIGZ1bmN0aW9uIExvY2FsJDEoKSB7CiAgICAgIHRoaXMuXyA9ICJAIiArICgrK25leHRJZCQxKS50b1N0cmluZygzNik7CiAgICB9CgogICAgTG9jYWwkMS5wcm90b3R5cGUgPSBsb2NhbCQzLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IExvY2FsJDEsCiAgICAgIGdldDogZnVuY3Rpb24obm9kZSkgewogICAgICAgIHZhciBpZCA9IHRoaXMuXzsKICAgICAgICB3aGlsZSAoIShpZCBpbiBub2RlKSkgaWYgKCEobm9kZSA9IG5vZGUucGFyZW50Tm9kZSkpIHJldHVybjsKICAgICAgICByZXR1cm4gbm9kZVtpZF07CiAgICAgIH0sCiAgICAgIHNldDogZnVuY3Rpb24obm9kZSwgdmFsdWUpIHsKICAgICAgICByZXR1cm4gbm9kZVt0aGlzLl9dID0gdmFsdWU7CiAgICAgIH0sCiAgICAgIHJlbW92ZTogZnVuY3Rpb24obm9kZSkgewogICAgICAgIHJldHVybiB0aGlzLl8gaW4gbm9kZSAmJiBkZWxldGUgbm9kZVt0aGlzLl9dOwogICAgICB9LAogICAgICB0b1N0cmluZzogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuXzsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBzb3VyY2VFdmVudCQzKCkgewogICAgICB2YXIgY3VycmVudCA9IGV2ZW50JDMsIHNvdXJjZTsKICAgICAgd2hpbGUgKHNvdXJjZSA9IGN1cnJlbnQuc291cmNlRXZlbnQpIGN1cnJlbnQgPSBzb3VyY2U7CiAgICAgIHJldHVybiBjdXJyZW50OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvaW50JDkobm9kZSwgZXZlbnQpIHsKICAgICAgdmFyIHN2ZyA9IG5vZGUub3duZXJTVkdFbGVtZW50IHx8IG5vZGU7CgogICAgICBpZiAoc3ZnLmNyZWF0ZVNWR1BvaW50KSB7CiAgICAgICAgdmFyIHBvaW50ID0gc3ZnLmNyZWF0ZVNWR1BvaW50KCk7CiAgICAgICAgcG9pbnQueCA9IGV2ZW50LmNsaWVudFgsIHBvaW50LnkgPSBldmVudC5jbGllbnRZOwogICAgICAgIHBvaW50ID0gcG9pbnQubWF0cml4VHJhbnNmb3JtKG5vZGUuZ2V0U2NyZWVuQ1RNKCkuaW52ZXJzZSgpKTsKICAgICAgICByZXR1cm4gW3BvaW50LngsIHBvaW50LnldOwogICAgICB9CgogICAgICB2YXIgcmVjdCA9IG5vZGUuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgIHJldHVybiBbZXZlbnQuY2xpZW50WCAtIHJlY3QubGVmdCAtIG5vZGUuY2xpZW50TGVmdCwgZXZlbnQuY2xpZW50WSAtIHJlY3QudG9wIC0gbm9kZS5jbGllbnRUb3BdOwogICAgfQoKICAgIGZ1bmN0aW9uIG1vdXNlJDMobm9kZSkgewogICAgICB2YXIgZXZlbnQgPSBzb3VyY2VFdmVudCQzKCk7CiAgICAgIGlmIChldmVudC5jaGFuZ2VkVG91Y2hlcykgZXZlbnQgPSBldmVudC5jaGFuZ2VkVG91Y2hlc1swXTsKICAgICAgcmV0dXJuIHBvaW50JDkobm9kZSwgZXZlbnQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdEFsbCQxKHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiB0eXBlb2Ygc2VsZWN0b3IgPT09ICJzdHJpbmciCiAgICAgICAgICA/IG5ldyBTZWxlY3Rpb24kNShbZG9jdW1lbnQucXVlcnlTZWxlY3RvckFsbChzZWxlY3RvcildLCBbZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50XSkKICAgICAgICAgIDogbmV3IFNlbGVjdGlvbiQ1KFtzZWxlY3RvciA9PSBudWxsID8gW10gOiBzZWxlY3Rvcl0sIHJvb3QkNSk7CiAgICB9CgogICAgZnVuY3Rpb24gdG91Y2gkMihub2RlLCB0b3VjaGVzLCBpZGVudGlmaWVyKSB7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMykgaWRlbnRpZmllciA9IHRvdWNoZXMsIHRvdWNoZXMgPSBzb3VyY2VFdmVudCQzKCkuY2hhbmdlZFRvdWNoZXM7CgogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHRvdWNoZXMgPyB0b3VjaGVzLmxlbmd0aCA6IDAsIHRvdWNoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKCh0b3VjaCA9IHRvdWNoZXNbaV0pLmlkZW50aWZpZXIgPT09IGlkZW50aWZpZXIpIHsKICAgICAgICAgIHJldHVybiBwb2ludCQ5KG5vZGUsIHRvdWNoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHRvdWNoZXMkMShub2RlLCB0b3VjaGVzKSB7CiAgICAgIGlmICh0b3VjaGVzID09IG51bGwpIHRvdWNoZXMgPSBzb3VyY2VFdmVudCQzKCkudG91Y2hlczsKCiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdG91Y2hlcyA/IHRvdWNoZXMubGVuZ3RoIDogMCwgcG9pbnRzID0gbmV3IEFycmF5KG4pOyBpIDwgbjsgKytpKSB7CiAgICAgICAgcG9pbnRzW2ldID0gcG9pbnQkOShub2RlLCB0b3VjaGVzW2ldKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHBvaW50czsKICAgIH0KCiAgICB2YXIgcGkkYSA9IE1hdGguUEksCiAgICAgICAgdGF1JGEgPSAyICogcGkkYSwKICAgICAgICBlcHNpbG9uJDkgPSAxZS02LAogICAgICAgIHRhdUVwc2lsb24kMyA9IHRhdSRhIC0gZXBzaWxvbiQ5OwoKICAgIGZ1bmN0aW9uIFBhdGgkMygpIHsKICAgICAgdGhpcy5feDAgPSB0aGlzLl95MCA9IC8vIHN0YXJ0IG9mIGN1cnJlbnQgc3VicGF0aAogICAgICB0aGlzLl94MSA9IHRoaXMuX3kxID0gbnVsbDsgLy8gZW5kIG9mIGN1cnJlbnQgc3VicGF0aAogICAgICB0aGlzLl8gPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXRoJDMoKSB7CiAgICAgIHJldHVybiBuZXcgUGF0aCQzOwogICAgfQoKICAgIFBhdGgkMy5wcm90b3R5cGUgPSBwYXRoJDMucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogUGF0aCQzLAogICAgICBtb3ZlVG86IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB0aGlzLl8gKz0gIk0iICsgKHRoaXMuX3gwID0gdGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTAgPSB0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgY2xvc2VQYXRoOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5feDEgIT09IG51bGwpIHsKICAgICAgICAgIHRoaXMuX3gxID0gdGhpcy5feDAsIHRoaXMuX3kxID0gdGhpcy5feTA7CiAgICAgICAgICB0aGlzLl8gKz0gIloiOwogICAgICAgIH0KICAgICAgfSwKICAgICAgbGluZVRvOiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJMIiArICh0aGlzLl94MSA9ICt4KSArICIsIiArICh0aGlzLl95MSA9ICt5KTsKICAgICAgfSwKICAgICAgcXVhZHJhdGljQ3VydmVUbzogZnVuY3Rpb24oeDEsIHkxLCB4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJRIiArICgreDEpICsgIiwiICsgKCt5MSkgKyAiLCIgKyAodGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTEgPSAreSk7CiAgICAgIH0sCiAgICAgIGJlemllckN1cnZlVG86IGZ1bmN0aW9uKHgxLCB5MSwgeDIsIHkyLCB4LCB5KSB7CiAgICAgICAgdGhpcy5fICs9ICJDIiArICgreDEpICsgIiwiICsgKCt5MSkgKyAiLCIgKyAoK3gyKSArICIsIiArICgreTIpICsgIiwiICsgKHRoaXMuX3gxID0gK3gpICsgIiwiICsgKHRoaXMuX3kxID0gK3kpOwogICAgICB9LAogICAgICBhcmNUbzogZnVuY3Rpb24oeDEsIHkxLCB4MiwgeTIsIHIpIHsKICAgICAgICB4MSA9ICt4MSwgeTEgPSAreTEsIHgyID0gK3gyLCB5MiA9ICt5MiwgciA9ICtyOwogICAgICAgIHZhciB4MCA9IHRoaXMuX3gxLAogICAgICAgICAgICB5MCA9IHRoaXMuX3kxLAogICAgICAgICAgICB4MjEgPSB4MiAtIHgxLAogICAgICAgICAgICB5MjEgPSB5MiAtIHkxLAogICAgICAgICAgICB4MDEgPSB4MCAtIHgxLAogICAgICAgICAgICB5MDEgPSB5MCAtIHkxLAogICAgICAgICAgICBsMDFfMiA9IHgwMSAqIHgwMSArIHkwMSAqIHkwMTsKCiAgICAgICAgLy8gSXMgdGhlIHJhZGl1cyBuZWdhdGl2ZT8gRXJyb3IuCiAgICAgICAgaWYgKHIgPCAwKSB0aHJvdyBuZXcgRXJyb3IoIm5lZ2F0aXZlIHJhZGl1czogIiArIHIpOwoKICAgICAgICAvLyBJcyB0aGlzIHBhdGggZW1wdHk/IE1vdmUgdG8gKHgxLHkxKS4KICAgICAgICBpZiAodGhpcy5feDEgPT09IG51bGwpIHsKICAgICAgICAgIHRoaXMuXyArPSAiTSIgKyAodGhpcy5feDEgPSB4MSkgKyAiLCIgKyAodGhpcy5feTEgPSB5MSk7CiAgICAgICAgfQoKICAgICAgICAvLyBPciwgaXMgKHgxLHkxKSBjb2luY2lkZW50IHdpdGggKHgwLHkwKT8gRG8gbm90aGluZy4KICAgICAgICBlbHNlIGlmICghKGwwMV8yID4gZXBzaWxvbiQ5KSk7CgogICAgICAgIC8vIE9yLCBhcmUgKHgwLHkwKSwgKHgxLHkxKSBhbmQgKHgyLHkyKSBjb2xsaW5lYXI/CiAgICAgICAgLy8gRXF1aXZhbGVudGx5LCBpcyAoeDEseTEpIGNvaW5jaWRlbnQgd2l0aCAoeDIseTIpPwogICAgICAgIC8vIE9yLCBpcyB0aGUgcmFkaXVzIHplcm8/IExpbmUgdG8gKHgxLHkxKS4KICAgICAgICBlbHNlIGlmICghKE1hdGguYWJzKHkwMSAqIHgyMSAtIHkyMSAqIHgwMSkgPiBlcHNpbG9uJDkpIHx8ICFyKSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkwiICsgKHRoaXMuX3gxID0geDEpICsgIiwiICsgKHRoaXMuX3kxID0geTEpOwogICAgICAgIH0KCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IGFuIGFyYyEKICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciB4MjAgPSB4MiAtIHgwLAogICAgICAgICAgICAgIHkyMCA9IHkyIC0geTAsCiAgICAgICAgICAgICAgbDIxXzIgPSB4MjEgKiB4MjEgKyB5MjEgKiB5MjEsCiAgICAgICAgICAgICAgbDIwXzIgPSB4MjAgKiB4MjAgKyB5MjAgKiB5MjAsCiAgICAgICAgICAgICAgbDIxID0gTWF0aC5zcXJ0KGwyMV8yKSwKICAgICAgICAgICAgICBsMDEgPSBNYXRoLnNxcnQobDAxXzIpLAogICAgICAgICAgICAgIGwgPSByICogTWF0aC50YW4oKHBpJGEgLSBNYXRoLmFjb3MoKGwyMV8yICsgbDAxXzIgLSBsMjBfMikgLyAoMiAqIGwyMSAqIGwwMSkpKSAvIDIpLAogICAgICAgICAgICAgIHQwMSA9IGwgLyBsMDEsCiAgICAgICAgICAgICAgdDIxID0gbCAvIGwyMTsKCiAgICAgICAgICAvLyBJZiB0aGUgc3RhcnQgdGFuZ2VudCBpcyBub3QgY29pbmNpZGVudCB3aXRoICh4MCx5MCksIGxpbmUgdG8uCiAgICAgICAgICBpZiAoTWF0aC5hYnModDAxIC0gMSkgPiBlcHNpbG9uJDkpIHsKICAgICAgICAgICAgdGhpcy5fICs9ICJMIiArICh4MSArIHQwMSAqIHgwMSkgKyAiLCIgKyAoeTEgKyB0MDEgKiB5MDEpOwogICAgICAgICAgfQoKICAgICAgICAgIHRoaXMuXyArPSAiQSIgKyByICsgIiwiICsgciArICIsMCwwLCIgKyAoKyh5MDEgKiB4MjAgPiB4MDEgKiB5MjApKSArICIsIiArICh0aGlzLl94MSA9IHgxICsgdDIxICogeDIxKSArICIsIiArICh0aGlzLl95MSA9IHkxICsgdDIxICogeTIxKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGFyYzogZnVuY3Rpb24oeCwgeSwgciwgYTAsIGExLCBjY3cpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreSwgciA9ICtyLCBjY3cgPSAhIWNjdzsKICAgICAgICB2YXIgZHggPSByICogTWF0aC5jb3MoYTApLAogICAgICAgICAgICBkeSA9IHIgKiBNYXRoLnNpbihhMCksCiAgICAgICAgICAgIHgwID0geCArIGR4LAogICAgICAgICAgICB5MCA9IHkgKyBkeSwKICAgICAgICAgICAgY3cgPSAxIF4gY2N3LAogICAgICAgICAgICBkYSA9IGNjdyA/IGEwIC0gYTEgOiBhMSAtIGEwOwoKICAgICAgICAvLyBJcyB0aGUgcmFkaXVzIG5lZ2F0aXZlPyBFcnJvci4KICAgICAgICBpZiAociA8IDApIHRocm93IG5ldyBFcnJvcigibmVnYXRpdmUgcmFkaXVzOiAiICsgcik7CgogICAgICAgIC8vIElzIHRoaXMgcGF0aCBlbXB0eT8gTW92ZSB0byAoeDAseTApLgogICAgICAgIGlmICh0aGlzLl94MSA9PT0gbnVsbCkgewogICAgICAgICAgdGhpcy5fICs9ICJNIiArIHgwICsgIiwiICsgeTA7CiAgICAgICAgfQoKICAgICAgICAvLyBPciwgaXMgKHgwLHkwKSBub3QgY29pbmNpZGVudCB3aXRoIHRoZSBwcmV2aW91cyBwb2ludD8gTGluZSB0byAoeDAseTApLgogICAgICAgIGVsc2UgaWYgKE1hdGguYWJzKHRoaXMuX3gxIC0geDApID4gZXBzaWxvbiQ5IHx8IE1hdGguYWJzKHRoaXMuX3kxIC0geTApID4gZXBzaWxvbiQ5KSB7CiAgICAgICAgICB0aGlzLl8gKz0gIkwiICsgeDAgKyAiLCIgKyB5MDsKICAgICAgICB9CgogICAgICAgIC8vIElzIHRoaXMgYXJjIGVtcHR5PyBXZeKAmXJlIGRvbmUuCiAgICAgICAgaWYgKCFyKSByZXR1cm47CgogICAgICAgIC8vIERvZXMgdGhlIGFuZ2xlIGdvIHRoZSB3cm9uZyB3YXk/IEZsaXAgdGhlIGRpcmVjdGlvbi4KICAgICAgICBpZiAoZGEgPCAwKSBkYSA9IGRhICUgdGF1JGEgKyB0YXUkYTsKCiAgICAgICAgLy8gSXMgdGhpcyBhIGNvbXBsZXRlIGNpcmNsZT8gRHJhdyB0d28gYXJjcyB0byBjb21wbGV0ZSB0aGUgY2lyY2xlLgogICAgICAgIGlmIChkYSA+IHRhdUVwc2lsb24kMykgewogICAgICAgICAgdGhpcy5fICs9ICJBIiArIHIgKyAiLCIgKyByICsgIiwwLDEsIiArIGN3ICsgIiwiICsgKHggLSBkeCkgKyAiLCIgKyAoeSAtIGR5KSArICJBIiArIHIgKyAiLCIgKyByICsgIiwwLDEsIiArIGN3ICsgIiwiICsgKHRoaXMuX3gxID0geDApICsgIiwiICsgKHRoaXMuX3kxID0geTApOwogICAgICAgIH0KCiAgICAgICAgLy8gSXMgdGhpcyBhcmMgbm9uLWVtcHR5PyBEcmF3IGFuIGFyYyEKICAgICAgICBlbHNlIGlmIChkYSA+IGVwc2lsb24kOSkgewogICAgICAgICAgdGhpcy5fICs9ICJBIiArIHIgKyAiLCIgKyByICsgIiwwLCIgKyAoKyhkYSA+PSBwaSRhKSkgKyAiLCIgKyBjdyArICIsIiArICh0aGlzLl94MSA9IHggKyByICogTWF0aC5jb3MoYTEpKSArICIsIiArICh0aGlzLl95MSA9IHkgKyByICogTWF0aC5zaW4oYTEpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIHJlY3Q6IGZ1bmN0aW9uKHgsIHksIHcsIGgpIHsKICAgICAgICB0aGlzLl8gKz0gIk0iICsgKHRoaXMuX3gwID0gdGhpcy5feDEgPSAreCkgKyAiLCIgKyAodGhpcy5feTAgPSB0aGlzLl95MSA9ICt5KSArICJoIiArICgrdykgKyAidiIgKyAoK2gpICsgImgiICsgKC13KSArICJaIjsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl87CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gY29uc3RhbnQkcyh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbiBjb25zdGFudCgpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgYWJzJDMgPSBNYXRoLmFiczsKICAgIHZhciBhdGFuMiQzID0gTWF0aC5hdGFuMjsKICAgIHZhciBjb3MkNSA9IE1hdGguY29zOwogICAgdmFyIG1heCQ1ID0gTWF0aC5tYXg7CiAgICB2YXIgbWluJDMgPSBNYXRoLm1pbjsKICAgIHZhciBzaW4kNSA9IE1hdGguc2luOwogICAgdmFyIHNxcnQkNSA9IE1hdGguc3FydDsKCiAgICB2YXIgZXBzaWxvbiRhID0gMWUtMTI7CiAgICB2YXIgcGkkYiA9IE1hdGguUEk7CiAgICB2YXIgaGFsZlBpJDcgPSBwaSRiIC8gMjsKICAgIHZhciB0YXUkYiA9IDIgKiBwaSRiOwoKICAgIGZ1bmN0aW9uIGFjb3MkMyh4KSB7CiAgICAgIHJldHVybiB4ID4gMSA/IDAgOiB4IDwgLTEgPyBwaSRiIDogTWF0aC5hY29zKHgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGFzaW4kMyh4KSB7CiAgICAgIHJldHVybiB4ID49IDEgPyBoYWxmUGkkNyA6IHggPD0gLTEgPyAtaGFsZlBpJDcgOiBNYXRoLmFzaW4oeCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXJjSW5uZXJSYWRpdXMkMShkKSB7CiAgICAgIHJldHVybiBkLmlubmVyUmFkaXVzOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyY091dGVyUmFkaXVzJDEoZCkgewogICAgICByZXR1cm4gZC5vdXRlclJhZGl1czsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmNTdGFydEFuZ2xlJDEoZCkgewogICAgICByZXR1cm4gZC5zdGFydEFuZ2xlOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyY0VuZEFuZ2xlJDEoZCkgewogICAgICByZXR1cm4gZC5lbmRBbmdsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmNQYWRBbmdsZSQxKGQpIHsKICAgICAgcmV0dXJuIGQgJiYgZC5wYWRBbmdsZTsgLy8gTm90ZTogb3B0aW9uYWwhCiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJzZWN0JDEoeDAsIHkwLCB4MSwgeTEsIHgyLCB5MiwgeDMsIHkzKSB7CiAgICAgIHZhciB4MTAgPSB4MSAtIHgwLCB5MTAgPSB5MSAtIHkwLAogICAgICAgICAgeDMyID0geDMgLSB4MiwgeTMyID0geTMgLSB5MiwKICAgICAgICAgIHQgPSAoeDMyICogKHkwIC0geTIpIC0geTMyICogKHgwIC0geDIpKSAvICh5MzIgKiB4MTAgLSB4MzIgKiB5MTApOwogICAgICByZXR1cm4gW3gwICsgdCAqIHgxMCwgeTAgKyB0ICogeTEwXTsKICAgIH0KCiAgICAvLyBDb21wdXRlIHBlcnBlbmRpY3VsYXIgb2Zmc2V0IGxpbmUgb2YgbGVuZ3RoIHJjLgogICAgLy8gaHR0cDovL21hdGh3b3JsZC53b2xmcmFtLmNvbS9DaXJjbGUtTGluZUludGVyc2VjdGlvbi5odG1sCiAgICBmdW5jdGlvbiBjb3JuZXJUYW5nZW50cyQxKHgwLCB5MCwgeDEsIHkxLCByMSwgcmMsIGN3KSB7CiAgICAgIHZhciB4MDEgPSB4MCAtIHgxLAogICAgICAgICAgeTAxID0geTAgLSB5MSwKICAgICAgICAgIGxvID0gKGN3ID8gcmMgOiAtcmMpIC8gc3FydCQ1KHgwMSAqIHgwMSArIHkwMSAqIHkwMSksCiAgICAgICAgICBveCA9IGxvICogeTAxLAogICAgICAgICAgb3kgPSAtbG8gKiB4MDEsCiAgICAgICAgICB4MTEgPSB4MCArIG94LAogICAgICAgICAgeTExID0geTAgKyBveSwKICAgICAgICAgIHgxMCA9IHgxICsgb3gsCiAgICAgICAgICB5MTAgPSB5MSArIG95LAogICAgICAgICAgeDAwID0gKHgxMSArIHgxMCkgLyAyLAogICAgICAgICAgeTAwID0gKHkxMSArIHkxMCkgLyAyLAogICAgICAgICAgZHggPSB4MTAgLSB4MTEsCiAgICAgICAgICBkeSA9IHkxMCAtIHkxMSwKICAgICAgICAgIGQyID0gZHggKiBkeCArIGR5ICogZHksCiAgICAgICAgICByID0gcjEgLSByYywKICAgICAgICAgIEQgPSB4MTEgKiB5MTAgLSB4MTAgKiB5MTEsCiAgICAgICAgICBkID0gKGR5IDwgMCA/IC0xIDogMSkgKiBzcXJ0JDUobWF4JDUoMCwgciAqIHIgKiBkMiAtIEQgKiBEKSksCiAgICAgICAgICBjeDAgPSAoRCAqIGR5IC0gZHggKiBkKSAvIGQyLAogICAgICAgICAgY3kwID0gKC1EICogZHggLSBkeSAqIGQpIC8gZDIsCiAgICAgICAgICBjeDEgPSAoRCAqIGR5ICsgZHggKiBkKSAvIGQyLAogICAgICAgICAgY3kxID0gKC1EICogZHggKyBkeSAqIGQpIC8gZDIsCiAgICAgICAgICBkeDAgPSBjeDAgLSB4MDAsCiAgICAgICAgICBkeTAgPSBjeTAgLSB5MDAsCiAgICAgICAgICBkeDEgPSBjeDEgLSB4MDAsCiAgICAgICAgICBkeTEgPSBjeTEgLSB5MDA7CgogICAgICAvLyBQaWNrIHRoZSBjbG9zZXIgb2YgdGhlIHR3byBpbnRlcnNlY3Rpb24gcG9pbnRzLgogICAgICAvLyBUT0RPIElzIHRoZXJlIGEgZmFzdGVyIHdheSB0byBkZXRlcm1pbmUgd2hpY2ggaW50ZXJzZWN0aW9uIHRvIHVzZT8KICAgICAgaWYgKGR4MCAqIGR4MCArIGR5MCAqIGR5MCA+IGR4MSAqIGR4MSArIGR5MSAqIGR5MSkgY3gwID0gY3gxLCBjeTAgPSBjeTE7CgogICAgICByZXR1cm4gewogICAgICAgIGN4OiBjeDAsCiAgICAgICAgY3k6IGN5MCwKICAgICAgICB4MDE6IC1veCwKICAgICAgICB5MDE6IC1veSwKICAgICAgICB4MTE6IGN4MCAqIChyMSAvIHIgLSAxKSwKICAgICAgICB5MTE6IGN5MCAqIChyMSAvIHIgLSAxKQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGFyYyQxKCkgewogICAgICB2YXIgaW5uZXJSYWRpdXMgPSBhcmNJbm5lclJhZGl1cyQxLAogICAgICAgICAgb3V0ZXJSYWRpdXMgPSBhcmNPdXRlclJhZGl1cyQxLAogICAgICAgICAgY29ybmVyUmFkaXVzID0gY29uc3RhbnQkcygwKSwKICAgICAgICAgIHBhZFJhZGl1cyA9IG51bGwsCiAgICAgICAgICBzdGFydEFuZ2xlID0gYXJjU3RhcnRBbmdsZSQxLAogICAgICAgICAgZW5kQW5nbGUgPSBhcmNFbmRBbmdsZSQxLAogICAgICAgICAgcGFkQW5nbGUgPSBhcmNQYWRBbmdsZSQxLAogICAgICAgICAgY29udGV4dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBhcmMoKSB7CiAgICAgICAgdmFyIGJ1ZmZlciwKICAgICAgICAgICAgciwKICAgICAgICAgICAgcjAgPSAraW5uZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgcjEgPSArb3V0ZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgYTAgPSBzdGFydEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgLSBoYWxmUGkkNywKICAgICAgICAgICAgYTEgPSBlbmRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIC0gaGFsZlBpJDcsCiAgICAgICAgICAgIGRhID0gYWJzJDMoYTEgLSBhMCksCiAgICAgICAgICAgIGN3ID0gYTEgPiBhMDsKCiAgICAgICAgaWYgKCFjb250ZXh0KSBjb250ZXh0ID0gYnVmZmVyID0gcGF0aCQzKCk7CgogICAgICAgIC8vIEVuc3VyZSB0aGF0IHRoZSBvdXRlciByYWRpdXMgaXMgYWx3YXlzIGxhcmdlciB0aGFuIHRoZSBpbm5lciByYWRpdXMuCiAgICAgICAgaWYgKHIxIDwgcjApIHIgPSByMSwgcjEgPSByMCwgcjAgPSByOwoKICAgICAgICAvLyBJcyBpdCBhIHBvaW50PwogICAgICAgIGlmICghKHIxID4gZXBzaWxvbiRhKSkgY29udGV4dC5tb3ZlVG8oMCwgMCk7CgogICAgICAgIC8vIE9yIGlzIGl0IGEgY2lyY2xlIG9yIGFubnVsdXM/CiAgICAgICAgZWxzZSBpZiAoZGEgPiB0YXUkYiAtIGVwc2lsb24kYSkgewogICAgICAgICAgY29udGV4dC5tb3ZlVG8ocjEgKiBjb3MkNShhMCksIHIxICogc2luJDUoYTApKTsKICAgICAgICAgIGNvbnRleHQuYXJjKDAsIDAsIHIxLCBhMCwgYTEsICFjdyk7CiAgICAgICAgICBpZiAocjAgPiBlcHNpbG9uJGEpIHsKICAgICAgICAgICAgY29udGV4dC5tb3ZlVG8ocjAgKiBjb3MkNShhMSksIHIwICogc2luJDUoYTEpKTsKICAgICAgICAgICAgY29udGV4dC5hcmMoMCwgMCwgcjAsIGExLCBhMCwgY3cpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gT3IgaXMgaXQgYSBjaXJjdWxhciBvciBhbm51bGFyIHNlY3Rvcj8KICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciBhMDEgPSBhMCwKICAgICAgICAgICAgICBhMTEgPSBhMSwKICAgICAgICAgICAgICBhMDAgPSBhMCwKICAgICAgICAgICAgICBhMTAgPSBhMSwKICAgICAgICAgICAgICBkYTAgPSBkYSwKICAgICAgICAgICAgICBkYTEgPSBkYSwKICAgICAgICAgICAgICBhcCA9IHBhZEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgLyAyLAogICAgICAgICAgICAgIHJwID0gKGFwID4gZXBzaWxvbiRhKSAmJiAocGFkUmFkaXVzID8gK3BhZFJhZGl1cy5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogc3FydCQ1KHIwICogcjAgKyByMSAqIHIxKSksCiAgICAgICAgICAgICAgcmMgPSBtaW4kMyhhYnMkMyhyMSAtIHIwKSAvIDIsICtjb3JuZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSksCiAgICAgICAgICAgICAgcmMwID0gcmMsCiAgICAgICAgICAgICAgcmMxID0gcmMsCiAgICAgICAgICAgICAgdDAsCiAgICAgICAgICAgICAgdDE7CgogICAgICAgICAgLy8gQXBwbHkgcGFkZGluZz8gTm90ZSB0aGF0IHNpbmNlIHIxIOKJpSByMCwgZGExIOKJpSBkYTAuCiAgICAgICAgICBpZiAocnAgPiBlcHNpbG9uJGEpIHsKICAgICAgICAgICAgdmFyIHAwID0gYXNpbiQzKHJwIC8gcjAgKiBzaW4kNShhcCkpLAogICAgICAgICAgICAgICAgcDEgPSBhc2luJDMocnAgLyByMSAqIHNpbiQ1KGFwKSk7CiAgICAgICAgICAgIGlmICgoZGEwIC09IHAwICogMikgPiBlcHNpbG9uJGEpIHAwICo9IChjdyA/IDEgOiAtMSksIGEwMCArPSBwMCwgYTEwIC09IHAwOwogICAgICAgICAgICBlbHNlIGRhMCA9IDAsIGEwMCA9IGExMCA9IChhMCArIGExKSAvIDI7CiAgICAgICAgICAgIGlmICgoZGExIC09IHAxICogMikgPiBlcHNpbG9uJGEpIHAxICo9IChjdyA/IDEgOiAtMSksIGEwMSArPSBwMSwgYTExIC09IHAxOwogICAgICAgICAgICBlbHNlIGRhMSA9IDAsIGEwMSA9IGExMSA9IChhMCArIGExKSAvIDI7CiAgICAgICAgICB9CgogICAgICAgICAgdmFyIHgwMSA9IHIxICogY29zJDUoYTAxKSwKICAgICAgICAgICAgICB5MDEgPSByMSAqIHNpbiQ1KGEwMSksCiAgICAgICAgICAgICAgeDEwID0gcjAgKiBjb3MkNShhMTApLAogICAgICAgICAgICAgIHkxMCA9IHIwICogc2luJDUoYTEwKTsKCiAgICAgICAgICAvLyBBcHBseSByb3VuZGVkIGNvcm5lcnM/CiAgICAgICAgICBpZiAocmMgPiBlcHNpbG9uJGEpIHsKICAgICAgICAgICAgdmFyIHgxMSA9IHIxICogY29zJDUoYTExKSwKICAgICAgICAgICAgICAgIHkxMSA9IHIxICogc2luJDUoYTExKSwKICAgICAgICAgICAgICAgIHgwMCA9IHIwICogY29zJDUoYTAwKSwKICAgICAgICAgICAgICAgIHkwMCA9IHIwICogc2luJDUoYTAwKTsKCiAgICAgICAgICAgIC8vIFJlc3RyaWN0IHRoZSBjb3JuZXIgcmFkaXVzIGFjY29yZGluZyB0byB0aGUgc2VjdG9yIGFuZ2xlLgogICAgICAgICAgICBpZiAoZGEgPCBwaSRiKSB7CiAgICAgICAgICAgICAgdmFyIG9jID0gZGEwID4gZXBzaWxvbiRhID8gaW50ZXJzZWN0JDEoeDAxLCB5MDEsIHgwMCwgeTAwLCB4MTEsIHkxMSwgeDEwLCB5MTApIDogW3gxMCwgeTEwXSwKICAgICAgICAgICAgICAgICAgYXggPSB4MDEgLSBvY1swXSwKICAgICAgICAgICAgICAgICAgYXkgPSB5MDEgLSBvY1sxXSwKICAgICAgICAgICAgICAgICAgYnggPSB4MTEgLSBvY1swXSwKICAgICAgICAgICAgICAgICAgYnkgPSB5MTEgLSBvY1sxXSwKICAgICAgICAgICAgICAgICAga2MgPSAxIC8gc2luJDUoYWNvcyQzKChheCAqIGJ4ICsgYXkgKiBieSkgLyAoc3FydCQ1KGF4ICogYXggKyBheSAqIGF5KSAqIHNxcnQkNShieCAqIGJ4ICsgYnkgKiBieSkpKSAvIDIpLAogICAgICAgICAgICAgICAgICBsYyA9IHNxcnQkNShvY1swXSAqIG9jWzBdICsgb2NbMV0gKiBvY1sxXSk7CiAgICAgICAgICAgICAgcmMwID0gbWluJDMocmMsIChyMCAtIGxjKSAvIChrYyAtIDEpKTsKICAgICAgICAgICAgICByYzEgPSBtaW4kMyhyYywgKHIxIC0gbGMpIC8gKGtjICsgMSkpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgLy8gSXMgdGhlIHNlY3RvciBjb2xsYXBzZWQgdG8gYSBsaW5lPwogICAgICAgICAgaWYgKCEoZGExID4gZXBzaWxvbiRhKSkgY29udGV4dC5tb3ZlVG8oeDAxLCB5MDEpOwoKICAgICAgICAgIC8vIERvZXMgdGhlIHNlY3RvcuKAmXMgb3V0ZXIgcmluZyBoYXZlIHJvdW5kZWQgY29ybmVycz8KICAgICAgICAgIGVsc2UgaWYgKHJjMSA+IGVwc2lsb24kYSkgewogICAgICAgICAgICB0MCA9IGNvcm5lclRhbmdlbnRzJDEoeDAwLCB5MDAsIHgwMSwgeTAxLCByMSwgcmMxLCBjdyk7CiAgICAgICAgICAgIHQxID0gY29ybmVyVGFuZ2VudHMkMSh4MTEsIHkxMSwgeDEwLCB5MTAsIHIxLCByYzEsIGN3KTsKCiAgICAgICAgICAgIGNvbnRleHQubW92ZVRvKHQwLmN4ICsgdDAueDAxLCB0MC5jeSArIHQwLnkwMSk7CgogICAgICAgICAgICAvLyBIYXZlIHRoZSBjb3JuZXJzIG1lcmdlZD8KICAgICAgICAgICAgaWYgKHJjMSA8IHJjKSBjb250ZXh0LmFyYyh0MC5jeCwgdDAuY3ksIHJjMSwgYXRhbjIkMyh0MC55MDEsIHQwLngwMSksIGF0YW4yJDModDEueTAxLCB0MS54MDEpLCAhY3cpOwoKICAgICAgICAgICAgLy8gT3RoZXJ3aXNlLCBkcmF3IHRoZSB0d28gY29ybmVycyBhbmQgdGhlIHJpbmcuCiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQwLmN4LCB0MC5jeSwgcmMxLCBhdGFuMiQzKHQwLnkwMSwgdDAueDAxKSwgYXRhbjIkMyh0MC55MTEsIHQwLngxMSksICFjdyk7CiAgICAgICAgICAgICAgY29udGV4dC5hcmMoMCwgMCwgcjEsIGF0YW4yJDModDAuY3kgKyB0MC55MTEsIHQwLmN4ICsgdDAueDExKSwgYXRhbjIkMyh0MS5jeSArIHQxLnkxMSwgdDEuY3ggKyB0MS54MTEpLCAhY3cpOwogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQxLmN4LCB0MS5jeSwgcmMxLCBhdGFuMiQzKHQxLnkxMSwgdDEueDExKSwgYXRhbjIkMyh0MS55MDEsIHQxLngwMSksICFjdyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvLyBPciBpcyB0aGUgb3V0ZXIgcmluZyBqdXN0IGEgY2lyY3VsYXIgYXJjPwogICAgICAgICAgZWxzZSBjb250ZXh0Lm1vdmVUbyh4MDEsIHkwMSksIGNvbnRleHQuYXJjKDAsIDAsIHIxLCBhMDEsIGExMSwgIWN3KTsKCiAgICAgICAgICAvLyBJcyB0aGVyZSBubyBpbm5lciByaW5nLCBhbmQgaXTigJlzIGEgY2lyY3VsYXIgc2VjdG9yPwogICAgICAgICAgLy8gT3IgcGVyaGFwcyBpdOKAmXMgYW4gYW5udWxhciBzZWN0b3IgY29sbGFwc2VkIGR1ZSB0byBwYWRkaW5nPwogICAgICAgICAgaWYgKCEocjAgPiBlcHNpbG9uJGEpIHx8ICEoZGEwID4gZXBzaWxvbiRhKSkgY29udGV4dC5saW5lVG8oeDEwLCB5MTApOwoKICAgICAgICAgIC8vIERvZXMgdGhlIHNlY3RvcuKAmXMgaW5uZXIgcmluZyAob3IgcG9pbnQpIGhhdmUgcm91bmRlZCBjb3JuZXJzPwogICAgICAgICAgZWxzZSBpZiAocmMwID4gZXBzaWxvbiRhKSB7CiAgICAgICAgICAgIHQwID0gY29ybmVyVGFuZ2VudHMkMSh4MTAsIHkxMCwgeDExLCB5MTEsIHIwLCAtcmMwLCBjdyk7CiAgICAgICAgICAgIHQxID0gY29ybmVyVGFuZ2VudHMkMSh4MDEsIHkwMSwgeDAwLCB5MDAsIHIwLCAtcmMwLCBjdyk7CgogICAgICAgICAgICBjb250ZXh0LmxpbmVUbyh0MC5jeCArIHQwLngwMSwgdDAuY3kgKyB0MC55MDEpOwoKICAgICAgICAgICAgLy8gSGF2ZSB0aGUgY29ybmVycyBtZXJnZWQ/CiAgICAgICAgICAgIGlmIChyYzAgPCByYykgY29udGV4dC5hcmModDAuY3gsIHQwLmN5LCByYzAsIGF0YW4yJDModDAueTAxLCB0MC54MDEpLCBhdGFuMiQzKHQxLnkwMSwgdDEueDAxKSwgIWN3KTsKCiAgICAgICAgICAgIC8vIE90aGVyd2lzZSwgZHJhdyB0aGUgdHdvIGNvcm5lcnMgYW5kIHRoZSByaW5nLgogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICBjb250ZXh0LmFyYyh0MC5jeCwgdDAuY3ksIHJjMCwgYXRhbjIkMyh0MC55MDEsIHQwLngwMSksIGF0YW4yJDModDAueTExLCB0MC54MTEpLCAhY3cpOwogICAgICAgICAgICAgIGNvbnRleHQuYXJjKDAsIDAsIHIwLCBhdGFuMiQzKHQwLmN5ICsgdDAueTExLCB0MC5jeCArIHQwLngxMSksIGF0YW4yJDModDEuY3kgKyB0MS55MTEsIHQxLmN4ICsgdDEueDExKSwgY3cpOwogICAgICAgICAgICAgIGNvbnRleHQuYXJjKHQxLmN4LCB0MS5jeSwgcmMwLCBhdGFuMiQzKHQxLnkxMSwgdDEueDExKSwgYXRhbjIkMyh0MS55MDEsIHQxLngwMSksICFjdyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICAvLyBPciBpcyB0aGUgaW5uZXIgcmluZyBqdXN0IGEgY2lyY3VsYXIgYXJjPwogICAgICAgICAgZWxzZSBjb250ZXh0LmFyYygwLCAwLCByMCwgYTEwLCBhMDAsIGN3KTsKICAgICAgICB9CgogICAgICAgIGNvbnRleHQuY2xvc2VQYXRoKCk7CgogICAgICAgIGlmIChidWZmZXIpIHJldHVybiBjb250ZXh0ID0gbnVsbCwgYnVmZmVyICsgIiIgfHwgbnVsbDsKICAgICAgfQoKICAgICAgYXJjLmNlbnRyb2lkID0gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHIgPSAoK2lubmVyUmFkaXVzLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgKyArb3V0ZXJSYWRpdXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgLyAyLAogICAgICAgICAgICBhID0gKCtzdGFydEFuZ2xlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgKyArZW5kQW5nbGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgLyAyIC0gcGkkYiAvIDI7CiAgICAgICAgcmV0dXJuIFtjb3MkNShhKSAqIHIsIHNpbiQ1KGEpICogcl07CiAgICAgIH07CgogICAgICBhcmMuaW5uZXJSYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoaW5uZXJSYWRpdXMgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJjKSA6IGlubmVyUmFkaXVzOwogICAgICB9OwoKICAgICAgYXJjLm91dGVyUmFkaXVzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG91dGVyUmFkaXVzID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGFyYykgOiBvdXRlclJhZGl1czsKICAgICAgfTsKCiAgICAgIGFyYy5jb3JuZXJSYWRpdXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY29ybmVyUmFkaXVzID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGFyYykgOiBjb3JuZXJSYWRpdXM7CiAgICAgIH07CgogICAgICBhcmMucGFkUmFkaXVzID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZFJhZGl1cyA9IF8gPT0gbnVsbCA/IG51bGwgOiB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJjKSA6IHBhZFJhZGl1czsKICAgICAgfTsKCiAgICAgIGFyYy5zdGFydEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHN0YXJ0QW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJjKSA6IHN0YXJ0QW5nbGU7CiAgICAgIH07CgogICAgICBhcmMuZW5kQW5nbGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoZW5kQW5nbGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJjKSA6IGVuZEFuZ2xlOwogICAgICB9OwoKICAgICAgYXJjLnBhZEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHBhZEFuZ2xlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGFyYykgOiBwYWRBbmdsZTsKICAgICAgfTsKCiAgICAgIGFyYy5jb250ZXh0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKChjb250ZXh0ID0gXyA9PSBudWxsID8gbnVsbCA6IF8pLCBhcmMpIDogY29udGV4dDsKICAgICAgfTsKCiAgICAgIHJldHVybiBhcmM7CiAgICB9CgogICAgZnVuY3Rpb24gTGluZWFyJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBMaW5lYXIkMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fbGluZSA9IDEgLSB0aGlzLl9saW5lOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8oeCwgeSkgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4LCB5KTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgLy8gcHJvY2VlZAogICAgICAgICAgZGVmYXVsdDogdGhpcy5fY29udGV4dC5saW5lVG8oeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjdXJ2ZUxpbmVhciQxKGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBMaW5lYXIkMShjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiB4JDgocCkgewogICAgICByZXR1cm4gcFswXTsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDgocCkgewogICAgICByZXR1cm4gcFsxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5lJDEoKSB7CiAgICAgIHZhciB4ID0geCQ4LAogICAgICAgICAgeSA9IHkkOCwKICAgICAgICAgIGRlZmluZWQgPSBjb25zdGFudCRzKHRydWUpLAogICAgICAgICAgY29udGV4dCA9IG51bGwsCiAgICAgICAgICBjdXJ2ZSA9IGN1cnZlTGluZWFyJDEsCiAgICAgICAgICBvdXRwdXQgPSBudWxsOwoKICAgICAgZnVuY3Rpb24gbGluZShkYXRhKSB7CiAgICAgICAgdmFyIGksCiAgICAgICAgICAgIG4gPSBkYXRhLmxlbmd0aCwKICAgICAgICAgICAgZCwKICAgICAgICAgICAgZGVmaW5lZDAgPSBmYWxzZSwKICAgICAgICAgICAgYnVmZmVyOwoKICAgICAgICBpZiAoY29udGV4dCA9PSBudWxsKSBvdXRwdXQgPSBjdXJ2ZShidWZmZXIgPSBwYXRoJDMoKSk7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPD0gbjsgKytpKSB7CiAgICAgICAgICBpZiAoIShpIDwgbiAmJiBkZWZpbmVkKGQgPSBkYXRhW2ldLCBpLCBkYXRhKSkgPT09IGRlZmluZWQwKSB7CiAgICAgICAgICAgIGlmIChkZWZpbmVkMCA9ICFkZWZpbmVkMCkgb3V0cHV0LmxpbmVTdGFydCgpOwogICAgICAgICAgICBlbHNlIG91dHB1dC5saW5lRW5kKCk7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoZGVmaW5lZDApIG91dHB1dC5wb2ludCgreChkLCBpLCBkYXRhKSwgK3koZCwgaSwgZGF0YSkpOwogICAgICAgIH0KCiAgICAgICAgaWYgKGJ1ZmZlcikgcmV0dXJuIG91dHB1dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIGxpbmUueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGxpbmUpIDogeDsKICAgICAgfTsKCiAgICAgIGxpbmUueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGxpbmUpIDogeTsKICAgICAgfTsKCiAgICAgIGxpbmUuZGVmaW5lZCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkZWZpbmVkID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcyghIV8pLCBsaW5lKSA6IGRlZmluZWQ7CiAgICAgIH07CgogICAgICBsaW5lLmN1cnZlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGN1cnZlID0gXywgY29udGV4dCAhPSBudWxsICYmIChvdXRwdXQgPSBjdXJ2ZShjb250ZXh0KSksIGxpbmUpIDogY3VydmU7CiAgICAgIH07CgogICAgICBsaW5lLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoXyA9PSBudWxsID8gY29udGV4dCA9IG91dHB1dCA9IG51bGwgOiBvdXRwdXQgPSBjdXJ2ZShjb250ZXh0ID0gXyksIGxpbmUpIDogY29udGV4dDsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5lOwogICAgfQoKICAgIGZ1bmN0aW9uIGFyZWEkNigpIHsKICAgICAgdmFyIHgwID0geCQ4LAogICAgICAgICAgeDEgPSBudWxsLAogICAgICAgICAgeTAgPSBjb25zdGFudCRzKDApLAogICAgICAgICAgeTEgPSB5JDgsCiAgICAgICAgICBkZWZpbmVkID0gY29uc3RhbnQkcyh0cnVlKSwKICAgICAgICAgIGNvbnRleHQgPSBudWxsLAogICAgICAgICAgY3VydmUgPSBjdXJ2ZUxpbmVhciQxLAogICAgICAgICAgb3V0cHV0ID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIGFyZWEoZGF0YSkgewogICAgICAgIHZhciBpLAogICAgICAgICAgICBqLAogICAgICAgICAgICBrLAogICAgICAgICAgICBuID0gZGF0YS5sZW5ndGgsCiAgICAgICAgICAgIGQsCiAgICAgICAgICAgIGRlZmluZWQwID0gZmFsc2UsCiAgICAgICAgICAgIGJ1ZmZlciwKICAgICAgICAgICAgeDB6ID0gbmV3IEFycmF5KG4pLAogICAgICAgICAgICB5MHogPSBuZXcgQXJyYXkobik7CgogICAgICAgIGlmIChjb250ZXh0ID09IG51bGwpIG91dHB1dCA9IGN1cnZlKGJ1ZmZlciA9IHBhdGgkMygpKTsKCiAgICAgICAgZm9yIChpID0gMDsgaSA8PSBuOyArK2kpIHsKICAgICAgICAgIGlmICghKGkgPCBuICYmIGRlZmluZWQoZCA9IGRhdGFbaV0sIGksIGRhdGEpKSA9PT0gZGVmaW5lZDApIHsKICAgICAgICAgICAgaWYgKGRlZmluZWQwID0gIWRlZmluZWQwKSB7CiAgICAgICAgICAgICAgaiA9IGk7CiAgICAgICAgICAgICAgb3V0cHV0LmFyZWFTdGFydCgpOwogICAgICAgICAgICAgIG91dHB1dC5saW5lU3RhcnQoKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBvdXRwdXQubGluZUVuZCgpOwogICAgICAgICAgICAgIG91dHB1dC5saW5lU3RhcnQoKTsKICAgICAgICAgICAgICBmb3IgKGsgPSBpIC0gMTsgayA+PSBqOyAtLWspIHsKICAgICAgICAgICAgICAgIG91dHB1dC5wb2ludCh4MHpba10sIHkweltrXSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIG91dHB1dC5saW5lRW5kKCk7CiAgICAgICAgICAgICAgb3V0cHV0LmFyZWFFbmQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgaWYgKGRlZmluZWQwKSB7CiAgICAgICAgICAgIHgweltpXSA9ICt4MChkLCBpLCBkYXRhKSwgeTB6W2ldID0gK3kwKGQsIGksIGRhdGEpOwogICAgICAgICAgICBvdXRwdXQucG9pbnQoeDEgPyAreDEoZCwgaSwgZGF0YSkgOiB4MHpbaV0sIHkxID8gK3kxKGQsIGksIGRhdGEpIDogeTB6W2ldKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmIChidWZmZXIpIHJldHVybiBvdXRwdXQgPSBudWxsLCBidWZmZXIgKyAiIiB8fCBudWxsOwogICAgICB9CgogICAgICBmdW5jdGlvbiBhcmVhbGluZSgpIHsKICAgICAgICByZXR1cm4gbGluZSQxKCkuZGVmaW5lZChkZWZpbmVkKS5jdXJ2ZShjdXJ2ZSkuY29udGV4dChjb250ZXh0KTsKICAgICAgfQoKICAgICAgYXJlYS54ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHgwID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIHgxID0gbnVsbCwgYXJlYSkgOiB4MDsKICAgICAgfTsKCiAgICAgIGFyZWEueDAgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeDAgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJlYSkgOiB4MDsKICAgICAgfTsKCiAgICAgIGFyZWEueDEgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeDEgPSBfID09IG51bGwgPyBudWxsIDogdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIGFyZWEpIDogeDE7CiAgICAgIH07CgogICAgICBhcmVhLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeTAgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgeTEgPSBudWxsLCBhcmVhKSA6IHkwOwogICAgICB9OwoKICAgICAgYXJlYS55MCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5MCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHMoK18pLCBhcmVhKSA6IHkwOwogICAgICB9OwoKICAgICAgYXJlYS55MSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5MSA9IF8gPT0gbnVsbCA/IG51bGwgOiB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgYXJlYSkgOiB5MTsKICAgICAgfTsKCiAgICAgIGFyZWEubGluZVgwID0KICAgICAgYXJlYS5saW5lWTAgPSBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gYXJlYWxpbmUoKS54KHgwKS55KHkwKTsKICAgICAgfTsKCiAgICAgIGFyZWEubGluZVkxID0gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGFyZWFsaW5lKCkueCh4MCkueSh5MSk7CiAgICAgIH07CgogICAgICBhcmVhLmxpbmVYMSA9IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBhcmVhbGluZSgpLngoeDEpLnkoeTApOwogICAgICB9OwoKICAgICAgYXJlYS5kZWZpbmVkID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGRlZmluZWQgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCEhXyksIGFyZWEpIDogZGVmaW5lZDsKICAgICAgfTsKCiAgICAgIGFyZWEuY3VydmUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoY3VydmUgPSBfLCBjb250ZXh0ICE9IG51bGwgJiYgKG91dHB1dCA9IGN1cnZlKGNvbnRleHQpKSwgYXJlYSkgOiBjdXJ2ZTsKICAgICAgfTsKCiAgICAgIGFyZWEuY29udGV4dCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChfID09IG51bGwgPyBjb250ZXh0ID0gb3V0cHV0ID0gbnVsbCA6IG91dHB1dCA9IGN1cnZlKGNvbnRleHQgPSBfKSwgYXJlYSkgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIGFyZWE7CiAgICB9CgogICAgZnVuY3Rpb24gZGVzY2VuZGluZyQ0KGEsIGIpIHsKICAgICAgcmV0dXJuIGIgPCBhID8gLTEgOiBiID4gYSA/IDEgOiBiID49IGEgPyAwIDogTmFOOwogICAgfQoKICAgIGZ1bmN0aW9uIGlkZW50aXR5JGooZCkgewogICAgICByZXR1cm4gZDsKICAgIH0KCiAgICBmdW5jdGlvbiBwaWUkMSgpIHsKICAgICAgdmFyIHZhbHVlID0gaWRlbnRpdHkkaiwKICAgICAgICAgIHNvcnRWYWx1ZXMgPSBkZXNjZW5kaW5nJDQsCiAgICAgICAgICBzb3J0ID0gbnVsbCwKICAgICAgICAgIHN0YXJ0QW5nbGUgPSBjb25zdGFudCRzKDApLAogICAgICAgICAgZW5kQW5nbGUgPSBjb25zdGFudCRzKHRhdSRiKSwKICAgICAgICAgIHBhZEFuZ2xlID0gY29uc3RhbnQkcygwKTsKCiAgICAgIGZ1bmN0aW9uIHBpZShkYXRhKSB7CiAgICAgICAgdmFyIGksCiAgICAgICAgICAgIG4gPSBkYXRhLmxlbmd0aCwKICAgICAgICAgICAgaiwKICAgICAgICAgICAgaywKICAgICAgICAgICAgc3VtID0gMCwKICAgICAgICAgICAgaW5kZXggPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIGFyY3MgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICAgIGEwID0gK3N0YXJ0QW5nbGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgZGEgPSBNYXRoLm1pbih0YXUkYiwgTWF0aC5tYXgoLXRhdSRiLCBlbmRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIC0gYTApKSwKICAgICAgICAgICAgYTEsCiAgICAgICAgICAgIHAgPSBNYXRoLm1pbihNYXRoLmFicyhkYSkgLyBuLCBwYWRBbmdsZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSwKICAgICAgICAgICAgcGEgPSBwICogKGRhIDwgMCA/IC0xIDogMSksCiAgICAgICAgICAgIHY7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgodiA9IGFyY3NbaW5kZXhbaV0gPSBpXSA9ICt2YWx1ZShkYXRhW2ldLCBpLCBkYXRhKSkgPiAwKSB7CiAgICAgICAgICAgIHN1bSArPSB2OwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgLy8gT3B0aW9uYWxseSBzb3J0IHRoZSBhcmNzIGJ5IHByZXZpb3VzbHktY29tcHV0ZWQgdmFsdWVzIG9yIGJ5IGRhdGEuCiAgICAgICAgaWYgKHNvcnRWYWx1ZXMgIT0gbnVsbCkgaW5kZXguc29ydChmdW5jdGlvbihpLCBqKSB7IHJldHVybiBzb3J0VmFsdWVzKGFyY3NbaV0sIGFyY3Nbal0pOyB9KTsKICAgICAgICBlbHNlIGlmIChzb3J0ICE9IG51bGwpIGluZGV4LnNvcnQoZnVuY3Rpb24oaSwgaikgeyByZXR1cm4gc29ydChkYXRhW2ldLCBkYXRhW2pdKTsgfSk7CgogICAgICAgIC8vIENvbXB1dGUgdGhlIGFyY3MhIFRoZXkgYXJlIHN0b3JlZCBpbiB0aGUgb3JpZ2luYWwgZGF0YSdzIG9yZGVyLgogICAgICAgIGZvciAoaSA9IDAsIGsgPSBzdW0gPyAoZGEgLSBuICogcGEpIC8gc3VtIDogMDsgaSA8IG47ICsraSwgYTAgPSBhMSkgewogICAgICAgICAgaiA9IGluZGV4W2ldLCB2ID0gYXJjc1tqXSwgYTEgPSBhMCArICh2ID4gMCA/IHYgKiBrIDogMCkgKyBwYSwgYXJjc1tqXSA9IHsKICAgICAgICAgICAgZGF0YTogZGF0YVtqXSwKICAgICAgICAgICAgaW5kZXg6IGksCiAgICAgICAgICAgIHZhbHVlOiB2LAogICAgICAgICAgICBzdGFydEFuZ2xlOiBhMCwKICAgICAgICAgICAgZW5kQW5nbGU6IGExLAogICAgICAgICAgICBwYWRBbmdsZTogcAogICAgICAgICAgfTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBhcmNzOwogICAgICB9CgogICAgICBwaWUudmFsdWUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodmFsdWUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgcGllKSA6IHZhbHVlOwogICAgICB9OwoKICAgICAgcGllLnNvcnRWYWx1ZXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc29ydFZhbHVlcyA9IF8sIHNvcnQgPSBudWxsLCBwaWUpIDogc29ydFZhbHVlczsKICAgICAgfTsKCiAgICAgIHBpZS5zb3J0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNvcnQgPSBfLCBzb3J0VmFsdWVzID0gbnVsbCwgcGllKSA6IHNvcnQ7CiAgICAgIH07CgogICAgICBwaWUuc3RhcnRBbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChzdGFydEFuZ2xlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIHBpZSkgOiBzdGFydEFuZ2xlOwogICAgICB9OwoKICAgICAgcGllLmVuZEFuZ2xlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGVuZEFuZ2xlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIHBpZSkgOiBlbmRBbmdsZTsKICAgICAgfTsKCiAgICAgIHBpZS5wYWRBbmdsZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChwYWRBbmdsZSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHMoK18pLCBwaWUpIDogcGFkQW5nbGU7CiAgICAgIH07CgogICAgICByZXR1cm4gcGllOwogICAgfQoKICAgIHZhciBjdXJ2ZVJhZGlhbExpbmVhciQxID0gY3VydmVSYWRpYWwkMihjdXJ2ZUxpbmVhciQxKTsKCiAgICBmdW5jdGlvbiBSYWRpYWwkMShjdXJ2ZSkgewogICAgICB0aGlzLl9jdXJ2ZSA9IGN1cnZlOwogICAgfQoKICAgIFJhZGlhbCQxLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9jdXJ2ZS5hcmVhU3RhcnQoKTsKICAgICAgfSwKICAgICAgYXJlYUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fY3VydmUuYXJlYUVuZCgpOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2N1cnZlLmxpbmVTdGFydCgpOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9jdXJ2ZS5saW5lRW5kKCk7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbihhLCByKSB7CiAgICAgICAgdGhpcy5fY3VydmUucG9pbnQociAqIE1hdGguc2luKGEpLCByICogLU1hdGguY29zKGEpKTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjdXJ2ZVJhZGlhbCQyKGN1cnZlKSB7CgogICAgICBmdW5jdGlvbiByYWRpYWwoY29udGV4dCkgewogICAgICAgIHJldHVybiBuZXcgUmFkaWFsJDEoY3VydmUoY29udGV4dCkpOwogICAgICB9CgogICAgICByYWRpYWwuX2N1cnZlID0gY3VydmU7CgogICAgICByZXR1cm4gcmFkaWFsOwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmVSYWRpYWwkMihsKSB7CiAgICAgIHZhciBjID0gbC5jdXJ2ZTsKCiAgICAgIGwuYW5nbGUgPSBsLngsIGRlbGV0ZSBsLng7CiAgICAgIGwucmFkaXVzID0gbC55LCBkZWxldGUgbC55OwoKICAgICAgbC5jdXJ2ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IGMoY3VydmVSYWRpYWwkMihfKSkgOiBjKCkuX2N1cnZlOwogICAgICB9OwoKICAgICAgcmV0dXJuIGw7CiAgICB9CgogICAgZnVuY3Rpb24gbGluZVJhZGlhbCQzKCkgewogICAgICByZXR1cm4gbGluZVJhZGlhbCQyKGxpbmUkMSgpLmN1cnZlKGN1cnZlUmFkaWFsTGluZWFyJDEpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhcmVhUmFkaWFsJDEoKSB7CiAgICAgIHZhciBhID0gYXJlYSQ2KCkuY3VydmUoY3VydmVSYWRpYWxMaW5lYXIkMSksCiAgICAgICAgICBjID0gYS5jdXJ2ZSwKICAgICAgICAgIHgwID0gYS5saW5lWDAsCiAgICAgICAgICB4MSA9IGEubGluZVgxLAogICAgICAgICAgeTAgPSBhLmxpbmVZMCwKICAgICAgICAgIHkxID0gYS5saW5lWTE7CgogICAgICBhLmFuZ2xlID0gYS54LCBkZWxldGUgYS54OwogICAgICBhLnN0YXJ0QW5nbGUgPSBhLngwLCBkZWxldGUgYS54MDsKICAgICAgYS5lbmRBbmdsZSA9IGEueDEsIGRlbGV0ZSBhLngxOwogICAgICBhLnJhZGl1cyA9IGEueSwgZGVsZXRlIGEueTsKICAgICAgYS5pbm5lclJhZGl1cyA9IGEueTAsIGRlbGV0ZSBhLnkwOwogICAgICBhLm91dGVyUmFkaXVzID0gYS55MSwgZGVsZXRlIGEueTE7CiAgICAgIGEubGluZVN0YXJ0QW5nbGUgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwkMih4MCgpKTsgfSwgZGVsZXRlIGEubGluZVgwOwogICAgICBhLmxpbmVFbmRBbmdsZSA9IGZ1bmN0aW9uKCkgeyByZXR1cm4gbGluZVJhZGlhbCQyKHgxKCkpOyB9LCBkZWxldGUgYS5saW5lWDE7CiAgICAgIGEubGluZUlubmVyUmFkaXVzID0gZnVuY3Rpb24oKSB7IHJldHVybiBsaW5lUmFkaWFsJDIoeTAoKSk7IH0sIGRlbGV0ZSBhLmxpbmVZMDsKICAgICAgYS5saW5lT3V0ZXJSYWRpdXMgPSBmdW5jdGlvbigpIHsgcmV0dXJuIGxpbmVSYWRpYWwkMih5MSgpKTsgfSwgZGVsZXRlIGEubGluZVkxOwoKICAgICAgYS5jdXJ2ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IGMoY3VydmVSYWRpYWwkMihfKSkgOiBjKCkuX2N1cnZlOwogICAgICB9OwoKICAgICAgcmV0dXJuIGE7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnRSYWRpYWwkMSh4LCB5KSB7CiAgICAgIHJldHVybiBbKHkgPSAreSkgKiBNYXRoLmNvcyh4IC09IE1hdGguUEkgLyAyKSwgeSAqIE1hdGguc2luKHgpXTsKICAgIH0KCiAgICB2YXIgc2xpY2UkZCA9IEFycmF5LnByb3RvdHlwZS5zbGljZTsKCiAgICBmdW5jdGlvbiBsaW5rU291cmNlJDEoZCkgewogICAgICByZXR1cm4gZC5zb3VyY2U7CiAgICB9CgogICAgZnVuY3Rpb24gbGlua1RhcmdldCQxKGQpIHsKICAgICAgcmV0dXJuIGQudGFyZ2V0OwogICAgfQoKICAgIGZ1bmN0aW9uIGxpbmskNShjdXJ2ZSkgewogICAgICB2YXIgc291cmNlID0gbGlua1NvdXJjZSQxLAogICAgICAgICAgdGFyZ2V0ID0gbGlua1RhcmdldCQxLAogICAgICAgICAgeCA9IHgkOCwKICAgICAgICAgIHkgPSB5JDgsCiAgICAgICAgICBjb250ZXh0ID0gbnVsbDsKCiAgICAgIGZ1bmN0aW9uIGxpbmsoKSB7CiAgICAgICAgdmFyIGJ1ZmZlciwgYXJndiA9IHNsaWNlJGQuY2FsbChhcmd1bWVudHMpLCBzID0gc291cmNlLmFwcGx5KHRoaXMsIGFyZ3YpLCB0ID0gdGFyZ2V0LmFwcGx5KHRoaXMsIGFyZ3YpOwogICAgICAgIGlmICghY29udGV4dCkgY29udGV4dCA9IGJ1ZmZlciA9IHBhdGgkMygpOwogICAgICAgIGN1cnZlKGNvbnRleHQsICt4LmFwcGx5KHRoaXMsIChhcmd2WzBdID0gcywgYXJndikpLCAreS5hcHBseSh0aGlzLCBhcmd2KSwgK3guYXBwbHkodGhpcywgKGFyZ3ZbMF0gPSB0LCBhcmd2KSksICt5LmFwcGx5KHRoaXMsIGFyZ3YpKTsKICAgICAgICBpZiAoYnVmZmVyKSByZXR1cm4gY29udGV4dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIGxpbmsuc291cmNlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNvdXJjZSA9IF8sIGxpbmspIDogc291cmNlOwogICAgICB9OwoKICAgICAgbGluay50YXJnZXQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodGFyZ2V0ID0gXywgbGluaykgOiB0YXJnZXQ7CiAgICAgIH07CgogICAgICBsaW5rLnggPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHMoK18pLCBsaW5rKSA6IHg7CiAgICAgIH07CgogICAgICBsaW5rLnkgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoeSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHMoK18pLCBsaW5rKSA6IHk7CiAgICAgIH07CgogICAgICBsaW5rLmNvbnRleHQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoKGNvbnRleHQgPSBfID09IG51bGwgPyBudWxsIDogXyksIGxpbmspIDogY29udGV4dDsKICAgICAgfTsKCiAgICAgIHJldHVybiBsaW5rOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1cnZlSG9yaXpvbnRhbCQxKGNvbnRleHQsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIGNvbnRleHQubW92ZVRvKHgwLCB5MCk7CiAgICAgIGNvbnRleHQuYmV6aWVyQ3VydmVUbyh4MCA9ICh4MCArIHgxKSAvIDIsIHkwLCB4MCwgeTEsIHgxLCB5MSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3VydmVWZXJ0aWNhbCQxKGNvbnRleHQsIHgwLCB5MCwgeDEsIHkxKSB7CiAgICAgIGNvbnRleHQubW92ZVRvKHgwLCB5MCk7CiAgICAgIGNvbnRleHQuYmV6aWVyQ3VydmVUbyh4MCwgeTAgPSAoeTAgKyB5MSkgLyAyLCB4MSwgeTAsIHgxLCB5MSk7CiAgICB9CgogICAgZnVuY3Rpb24gY3VydmVSYWRpYWwkMyhjb250ZXh0LCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgcDAgPSBwb2ludFJhZGlhbCQxKHgwLCB5MCksCiAgICAgICAgICBwMSA9IHBvaW50UmFkaWFsJDEoeDAsIHkwID0gKHkwICsgeTEpIC8gMiksCiAgICAgICAgICBwMiA9IHBvaW50UmFkaWFsJDEoeDEsIHkwKSwKICAgICAgICAgIHAzID0gcG9pbnRSYWRpYWwkMSh4MSwgeTEpOwogICAgICBjb250ZXh0Lm1vdmVUbyhwMFswXSwgcDBbMV0pOwogICAgICBjb250ZXh0LmJlemllckN1cnZlVG8ocDFbMF0sIHAxWzFdLCBwMlswXSwgcDJbMV0sIHAzWzBdLCBwM1sxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGlua0hvcml6b250YWwkMSgpIHsKICAgICAgcmV0dXJuIGxpbmskNShjdXJ2ZUhvcml6b250YWwkMSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGlua1ZlcnRpY2FsJDEoKSB7CiAgICAgIHJldHVybiBsaW5rJDUoY3VydmVWZXJ0aWNhbCQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5rUmFkaWFsJDEoKSB7CiAgICAgIHZhciBsID0gbGluayQ1KGN1cnZlUmFkaWFsJDMpOwogICAgICBsLmFuZ2xlID0gbC54LCBkZWxldGUgbC54OwogICAgICBsLnJhZGl1cyA9IGwueSwgZGVsZXRlIGwueTsKICAgICAgcmV0dXJuIGw7CiAgICB9CgogICAgdmFyIGNpcmNsZSQ1ID0gewogICAgICBkcmF3OiBmdW5jdGlvbihjb250ZXh0LCBzaXplKSB7CiAgICAgICAgdmFyIHIgPSBNYXRoLnNxcnQoc2l6ZSAvIHBpJGIpOwogICAgICAgIGNvbnRleHQubW92ZVRvKHIsIDApOwogICAgICAgIGNvbnRleHQuYXJjKDAsIDAsIHIsIDAsIHRhdSRiKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgY3Jvc3MkNSA9IHsKICAgICAgZHJhdzogZnVuY3Rpb24oY29udGV4dCwgc2l6ZSkgewogICAgICAgIHZhciByID0gTWF0aC5zcXJ0KHNpemUgLyA1KSAvIDI7CiAgICAgICAgY29udGV4dC5tb3ZlVG8oLTMgKiByLCAtcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oLXIsIC1yKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygtciwgLTMgKiByKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhyLCAtMyAqIHIpOwogICAgICAgIGNvbnRleHQubGluZVRvKHIsIC1yKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygzICogciwgLXIpOwogICAgICAgIGNvbnRleHQubGluZVRvKDMgKiByLCByKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhyLCByKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhyLCAzICogcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oLXIsIDMgKiByKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygtciwgcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oLTMgKiByLCByKTsKICAgICAgICBjb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICB9CiAgICB9OwoKICAgIHZhciB0YW4zMCQxID0gTWF0aC5zcXJ0KDEgLyAzKSwKICAgICAgICB0YW4zMF8yJDEgPSB0YW4zMCQxICogMjsKCiAgICB2YXIgZGlhbW9uZCQxID0gewogICAgICBkcmF3OiBmdW5jdGlvbihjb250ZXh0LCBzaXplKSB7CiAgICAgICAgdmFyIHkgPSBNYXRoLnNxcnQoc2l6ZSAvIHRhbjMwXzIkMSksCiAgICAgICAgICAgIHggPSB5ICogdGFuMzAkMTsKICAgICAgICBjb250ZXh0Lm1vdmVUbygwLCAteSk7CiAgICAgICAgY29udGV4dC5saW5lVG8oeCwgMCk7CiAgICAgICAgY29udGV4dC5saW5lVG8oMCwgeSk7CiAgICAgICAgY29udGV4dC5saW5lVG8oLXgsIDApOwogICAgICAgIGNvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGthJDEgPSAwLjg5MDgxMzA5MTUyOTI4NTIyODEwLAogICAgICAgIGtyJDEgPSBNYXRoLnNpbihwaSRiIC8gMTApIC8gTWF0aC5zaW4oNyAqIHBpJGIgLyAxMCksCiAgICAgICAga3gkMSA9IE1hdGguc2luKHRhdSRiIC8gMTApICoga3IkMSwKICAgICAgICBreSQxID0gLU1hdGguY29zKHRhdSRiIC8gMTApICoga3IkMTsKCiAgICB2YXIgc3RhciQxID0gewogICAgICBkcmF3OiBmdW5jdGlvbihjb250ZXh0LCBzaXplKSB7CiAgICAgICAgdmFyIHIgPSBNYXRoLnNxcnQoc2l6ZSAqIGthJDEpLAogICAgICAgICAgICB4ID0ga3gkMSAqIHIsCiAgICAgICAgICAgIHkgPSBreSQxICogcjsKICAgICAgICBjb250ZXh0Lm1vdmVUbygwLCAtcik7CiAgICAgICAgY29udGV4dC5saW5lVG8oeCwgeSk7CiAgICAgICAgZm9yICh2YXIgaSA9IDE7IGkgPCA1OyArK2kpIHsKICAgICAgICAgIHZhciBhID0gdGF1JGIgKiBpIC8gNSwKICAgICAgICAgICAgICBjID0gTWF0aC5jb3MoYSksCiAgICAgICAgICAgICAgcyA9IE1hdGguc2luKGEpOwogICAgICAgICAgY29udGV4dC5saW5lVG8ocyAqIHIsIC1jICogcik7CiAgICAgICAgICBjb250ZXh0LmxpbmVUbyhjICogeCAtIHMgKiB5LCBzICogeCArIGMgKiB5KTsKICAgICAgICB9CiAgICAgICAgY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgc3F1YXJlJDEgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgdyA9IE1hdGguc3FydChzaXplKSwKICAgICAgICAgICAgeCA9IC13IC8gMjsKICAgICAgICBjb250ZXh0LnJlY3QoeCwgeCwgdywgdyk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIHNxcnQzJDEgPSBNYXRoLnNxcnQoMyk7CgogICAgdmFyIHRyaWFuZ2xlJDEgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgeSA9IC1NYXRoLnNxcnQoc2l6ZSAvIChzcXJ0MyQxICogMykpOwogICAgICAgIGNvbnRleHQubW92ZVRvKDAsIHkgKiAyKTsKICAgICAgICBjb250ZXh0LmxpbmVUbygtc3FydDMkMSAqIHksIC15KTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhzcXJ0MyQxICogeSwgLXkpOwogICAgICAgIGNvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGMkMyA9IC0wLjUsCiAgICAgICAgcyQxID0gTWF0aC5zcXJ0KDMpIC8gMiwKICAgICAgICBrJDEgPSAxIC8gTWF0aC5zcXJ0KDEyKSwKICAgICAgICBhJDEgPSAoayQxIC8gMiArIDEpICogMzsKCiAgICB2YXIgd3llJDEgPSB7CiAgICAgIGRyYXc6IGZ1bmN0aW9uKGNvbnRleHQsIHNpemUpIHsKICAgICAgICB2YXIgciA9IE1hdGguc3FydChzaXplIC8gYSQxKSwKICAgICAgICAgICAgeDAgPSByIC8gMiwKICAgICAgICAgICAgeTAgPSByICogayQxLAogICAgICAgICAgICB4MSA9IHgwLAogICAgICAgICAgICB5MSA9IHIgKiBrJDEgKyByLAogICAgICAgICAgICB4MiA9IC14MSwKICAgICAgICAgICAgeTIgPSB5MTsKICAgICAgICBjb250ZXh0Lm1vdmVUbyh4MCwgeTApOwogICAgICAgIGNvbnRleHQubGluZVRvKHgxLCB5MSk7CiAgICAgICAgY29udGV4dC5saW5lVG8oeDIsIHkyKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MCAtIHMkMSAqIHkwLCBzJDEgKiB4MCArIGMkMyAqIHkwKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MSAtIHMkMSAqIHkxLCBzJDEgKiB4MSArIGMkMyAqIHkxKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MiAtIHMkMSAqIHkyLCBzJDEgKiB4MiArIGMkMyAqIHkyKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MCArIHMkMSAqIHkwLCBjJDMgKiB5MCAtIHMkMSAqIHgwKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MSArIHMkMSAqIHkxLCBjJDMgKiB5MSAtIHMkMSAqIHgxKTsKICAgICAgICBjb250ZXh0LmxpbmVUbyhjJDMgKiB4MiArIHMkMSAqIHkyLCBjJDMgKiB5MiAtIHMkMSAqIHgyKTsKICAgICAgICBjb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICB9CiAgICB9OwoKICAgIHZhciBzeW1ib2xzJDEgPSBbCiAgICAgIGNpcmNsZSQ1LAogICAgICBjcm9zcyQ1LAogICAgICBkaWFtb25kJDEsCiAgICAgIHNxdWFyZSQxLAogICAgICBzdGFyJDEsCiAgICAgIHRyaWFuZ2xlJDEsCiAgICAgIHd5ZSQxCiAgICBdOwoKICAgIGZ1bmN0aW9uIHN5bWJvbCQxKCkgewogICAgICB2YXIgdHlwZSA9IGNvbnN0YW50JHMoY2lyY2xlJDUpLAogICAgICAgICAgc2l6ZSA9IGNvbnN0YW50JHMoNjQpLAogICAgICAgICAgY29udGV4dCA9IG51bGw7CgogICAgICBmdW5jdGlvbiBzeW1ib2woKSB7CiAgICAgICAgdmFyIGJ1ZmZlcjsKICAgICAgICBpZiAoIWNvbnRleHQpIGNvbnRleHQgPSBidWZmZXIgPSBwYXRoJDMoKTsKICAgICAgICB0eXBlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykuZHJhdyhjb250ZXh0LCArc2l6ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpKTsKICAgICAgICBpZiAoYnVmZmVyKSByZXR1cm4gY29udGV4dCA9IG51bGwsIGJ1ZmZlciArICIiIHx8IG51bGw7CiAgICAgIH0KCiAgICAgIHN5bWJvbC50eXBlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHR5cGUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKF8pLCBzeW1ib2wpIDogdHlwZTsKICAgICAgfTsKCiAgICAgIHN5bWJvbC5zaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHNpemUgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKCtfKSwgc3ltYm9sKSA6IHNpemU7CiAgICAgIH07CgogICAgICBzeW1ib2wuY29udGV4dCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjb250ZXh0ID0gXyA9PSBudWxsID8gbnVsbCA6IF8sIHN5bWJvbCkgOiBjb250ZXh0OwogICAgICB9OwoKICAgICAgcmV0dXJuIHN5bWJvbDsKICAgIH0KCiAgICBmdW5jdGlvbiBub29wJDkoKSB7fQoKICAgIGZ1bmN0aW9uIHBvaW50JGEodGhhdCwgeCwgeSkgewogICAgICB0aGF0Ll9jb250ZXh0LmJlemllckN1cnZlVG8oCiAgICAgICAgKDIgKiB0aGF0Ll94MCArIHRoYXQuX3gxKSAvIDMsCiAgICAgICAgKDIgKiB0aGF0Ll95MCArIHRoYXQuX3kxKSAvIDMsCiAgICAgICAgKHRoYXQuX3gwICsgMiAqIHRoYXQuX3gxKSAvIDMsCiAgICAgICAgKHRoYXQuX3kwICsgMiAqIHRoYXQuX3kxKSAvIDMsCiAgICAgICAgKHRoYXQuX3gwICsgNCAqIHRoYXQuX3gxICsgeCkgLyA2LAogICAgICAgICh0aGF0Ll95MCArIDQgKiB0aGF0Ll95MSArIHkpIC8gNgogICAgICApOwogICAgfQoKICAgIGZ1bmN0aW9uIEJhc2lzJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBCYXNpcyQxLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gMDsKICAgICAgfSwKICAgICAgYXJlYUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IE5hTjsKICAgICAgfSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAzOiBwb2ludCRhKHRoaXMsIHRoaXMuX3gxLCB0aGlzLl95MSk7IC8vIHByb2NlZWQKICAgICAgICAgIGNhc2UgMjogdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDEsIHRoaXMuX3kxKTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAxKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHgsIHkpOyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl9jb250ZXh0LmxpbmVUbygoNSAqIHRoaXMuX3gwICsgdGhpcy5feDEpIC8gNiwgKDUgKiB0aGlzLl95MCArIHRoaXMuX3kxKSAvIDYpOyAvLyBwcm9jZWVkCiAgICAgICAgICBkZWZhdWx0OiBwb2ludCRhKHRoaXMsIHgsIHkpOyBicmVhazsKICAgICAgICB9CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSwgdGhpcy5feDEgPSB4OwogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEsIHRoaXMuX3kxID0geTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBiYXNpcyQ1KGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBCYXNpcyQxKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIEJhc2lzQ2xvc2VkJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBCYXNpc0Nsb3NlZCQxLnByb3RvdHlwZSA9IHsKICAgICAgYXJlYVN0YXJ0OiBub29wJDksCiAgICAgIGFyZWFFbmQ6IG5vb3AkOSwKICAgICAgbGluZVN0YXJ0OiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxID0gdGhpcy5feDIgPSB0aGlzLl94MyA9IHRoaXMuX3g0ID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSB0aGlzLl95MyA9IHRoaXMuX3k0ID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAxOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3gyLCB0aGlzLl95Mik7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAyOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKCh0aGlzLl94MiArIDIgKiB0aGlzLl94MykgLyAzLCAodGhpcy5feTIgKyAyICogdGhpcy5feTMpIC8gMyk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKCh0aGlzLl94MyArIDIgKiB0aGlzLl94MikgLyAzLCAodGhpcy5feTMgKyAyICogdGhpcy5feTIpIC8gMyk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAzOiB7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDIsIHRoaXMuX3kyKTsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94MywgdGhpcy5feTMpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3g0LCB0aGlzLl95NCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5feDIgPSB4LCB0aGlzLl95MiA9IHk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IHRoaXMuX3gzID0geCwgdGhpcy5feTMgPSB5OyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl94NCA9IHgsIHRoaXMuX3k0ID0geTsgdGhpcy5fY29udGV4dC5tb3ZlVG8oKHRoaXMuX3gwICsgNCAqIHRoaXMuX3gxICsgeCkgLyA2LCAodGhpcy5feTAgKyA0ICogdGhpcy5feTEgKyB5KSAvIDYpOyBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGEodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB5OwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGJhc2lzQ2xvc2VkJDMoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IEJhc2lzQ2xvc2VkJDEoY29udGV4dCk7CiAgICB9CgogICAgZnVuY3Rpb24gQmFzaXNPcGVuJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBCYXNpc09wZW4kMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSA9IE5hTjsKICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAzKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IHZhciB4MCA9ICh0aGlzLl94MCArIDQgKiB0aGlzLl94MSArIHgpIC8gNiwgeTAgPSAodGhpcy5feTAgKyA0ICogdGhpcy5feTEgKyB5KSAvIDY7IHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh4MCwgeTApIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeDAsIHkwKTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDM6IHRoaXMuX3BvaW50ID0gNDsgLy8gcHJvY2VlZAogICAgICAgICAgZGVmYXVsdDogcG9pbnQkYSh0aGlzLCB4LCB5KTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEsIHRoaXMuX3gxID0geDsKICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxLCB0aGlzLl95MSA9IHk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gYmFzaXNPcGVuJDEoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IEJhc2lzT3BlbiQxKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIEJ1bmRsZSQxKGNvbnRleHQsIGJldGEpIHsKICAgICAgdGhpcy5fYmFzaXMgPSBuZXcgQmFzaXMkMShjb250ZXh0KTsKICAgICAgdGhpcy5fYmV0YSA9IGJldGE7CiAgICB9CgogICAgQnVuZGxlJDEucHJvdG90eXBlID0gewogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3ggPSBbXTsKICAgICAgICB0aGlzLl95ID0gW107CiAgICAgICAgdGhpcy5fYmFzaXMubGluZVN0YXJ0KCk7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB4ID0gdGhpcy5feCwKICAgICAgICAgICAgeSA9IHRoaXMuX3ksCiAgICAgICAgICAgIGogPSB4Lmxlbmd0aCAtIDE7CgogICAgICAgIGlmIChqID4gMCkgewogICAgICAgICAgdmFyIHgwID0geFswXSwKICAgICAgICAgICAgICB5MCA9IHlbMF0sCiAgICAgICAgICAgICAgZHggPSB4W2pdIC0geDAsCiAgICAgICAgICAgICAgZHkgPSB5W2pdIC0geTAsCiAgICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICAgIHQ7CgogICAgICAgICAgd2hpbGUgKCsraSA8PSBqKSB7CiAgICAgICAgICAgIHQgPSBpIC8gajsKICAgICAgICAgICAgdGhpcy5fYmFzaXMucG9pbnQoCiAgICAgICAgICAgICAgdGhpcy5fYmV0YSAqIHhbaV0gKyAoMSAtIHRoaXMuX2JldGEpICogKHgwICsgdCAqIGR4KSwKICAgICAgICAgICAgICB0aGlzLl9iZXRhICogeVtpXSArICgxIC0gdGhpcy5fYmV0YSkgKiAoeTAgKyB0ICogZHkpCiAgICAgICAgICAgICk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICB0aGlzLl94ID0gdGhpcy5feSA9IG51bGw7CiAgICAgICAgdGhpcy5fYmFzaXMubGluZUVuZCgpOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHRoaXMuX3gucHVzaCgreCk7CiAgICAgICAgdGhpcy5feS5wdXNoKCt5KTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgYnVuZGxlJDEgPSAoZnVuY3Rpb24gY3VzdG9tKGJldGEpIHsKCiAgICAgIGZ1bmN0aW9uIGJ1bmRsZShjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIGJldGEgPT09IDEgPyBuZXcgQmFzaXMkMShjb250ZXh0KSA6IG5ldyBCdW5kbGUkMShjb250ZXh0LCBiZXRhKTsKICAgICAgfQoKICAgICAgYnVuZGxlLmJldGEgPSBmdW5jdGlvbihiZXRhKSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgrYmV0YSk7CiAgICAgIH07CgogICAgICByZXR1cm4gYnVuZGxlOwogICAgfSkoMC44NSk7CgogICAgZnVuY3Rpb24gcG9pbnQkYih0aGF0LCB4LCB5KSB7CiAgICAgIHRoYXQuX2NvbnRleHQuYmV6aWVyQ3VydmVUbygKICAgICAgICB0aGF0Ll94MSArIHRoYXQuX2sgKiAodGhhdC5feDIgLSB0aGF0Ll94MCksCiAgICAgICAgdGhhdC5feTEgKyB0aGF0Ll9rICogKHRoYXQuX3kyIC0gdGhhdC5feTApLAogICAgICAgIHRoYXQuX3gyICsgdGhhdC5fayAqICh0aGF0Ll94MSAtIHgpLAogICAgICAgIHRoYXQuX3kyICsgdGhhdC5fayAqICh0aGF0Ll95MSAtIHkpLAogICAgICAgIHRoYXQuX3gyLAogICAgICAgIHRoYXQuX3kyCiAgICAgICk7CiAgICB9CgogICAgZnVuY3Rpb24gQ2FyZGluYWwkMShjb250ZXh0LCB0ZW5zaW9uKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9rID0gKDEgLSB0ZW5zaW9uKSAvIDY7CiAgICB9CgogICAgQ2FyZGluYWwkMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX2NvbnRleHQubGluZVRvKHRoaXMuX3gyLCB0aGlzLl95Mik7IGJyZWFrOwogICAgICAgICAgY2FzZSAzOiBwb2ludCRiKHRoaXMsIHRoaXMuX3gxLCB0aGlzLl95MSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fbGluZSA9IDEgLSB0aGlzLl9saW5lOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8oeCwgeSkgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4LCB5KTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgdGhpcy5feDEgPSB4LCB0aGlzLl95MSA9IHk7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGIodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXJkaW5hbCQxID0gKGZ1bmN0aW9uIGN1c3RvbSh0ZW5zaW9uKSB7CgogICAgICBmdW5jdGlvbiBjYXJkaW5hbChjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIG5ldyBDYXJkaW5hbCQxKGNvbnRleHQsIHRlbnNpb24pOwogICAgICB9CgogICAgICBjYXJkaW5hbC50ZW5zaW9uID0gZnVuY3Rpb24odGVuc2lvbikgewogICAgICAgIHJldHVybiBjdXN0b20oK3RlbnNpb24pOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNhcmRpbmFsOwogICAgfSkoMCk7CgogICAgZnVuY3Rpb24gQ2FyZGluYWxDbG9zZWQkMShjb250ZXh0LCB0ZW5zaW9uKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9rID0gKDEgLSB0ZW5zaW9uKSAvIDY7CiAgICB9CgogICAgQ2FyZGluYWxDbG9zZWQkMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogbm9vcCQ5LAogICAgICBhcmVhRW5kOiBub29wJDksCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0gdGhpcy5feDMgPSB0aGlzLl94NCA9IHRoaXMuX3g1ID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSB0aGlzLl95MyA9IHRoaXMuX3k0ID0gdGhpcy5feTUgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDE6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDI6IHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjYXNlIDM6IHsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94MywgdGhpcy5feTMpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3g0LCB0aGlzLl95NCk7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDUsIHRoaXMuX3k1KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl94MyA9IHgsIHRoaXMuX3kzID0geTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDQgPSB4LCB0aGlzLl95NCA9IHkpOyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl94NSA9IHgsIHRoaXMuX3k1ID0geTsgYnJlYWs7CiAgICAgICAgICBkZWZhdWx0OiBwb2ludCRiKHRoaXMsIHgsIHkpOyBicmVhazsKICAgICAgICB9CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSwgdGhpcy5feDEgPSB0aGlzLl94MiwgdGhpcy5feDIgPSB4OwogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEsIHRoaXMuX3kxID0gdGhpcy5feTIsIHRoaXMuX3kyID0geTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgY2FyZGluYWxDbG9zZWQkMSA9IChmdW5jdGlvbiBjdXN0b20odGVuc2lvbikgewoKICAgICAgZnVuY3Rpb24gY2FyZGluYWwoY29udGV4dCkgewogICAgICAgIHJldHVybiBuZXcgQ2FyZGluYWxDbG9zZWQkMShjb250ZXh0LCB0ZW5zaW9uKTsKICAgICAgfQoKICAgICAgY2FyZGluYWwudGVuc2lvbiA9IGZ1bmN0aW9uKHRlbnNpb24pIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCt0ZW5zaW9uKTsKICAgICAgfTsKCiAgICAgIHJldHVybiBjYXJkaW5hbDsKICAgIH0pKDApOwoKICAgIGZ1bmN0aW9uIENhcmRpbmFsT3BlbiQxKGNvbnRleHQsIHRlbnNpb24pIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICAgIHRoaXMuX2sgPSAoMSAtIHRlbnNpb24pIC8gNjsKICAgIH0KCiAgICBDYXJkaW5hbE9wZW4kMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSBOYU47CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMykpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgdGhpcy5fbGluZSA9IDEgLSB0aGlzLl9saW5lOwogICAgICB9LAogICAgICBwb2ludDogZnVuY3Rpb24oeCwgeSkgewogICAgICAgIHggPSAreCwgeSA9ICt5OwogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDIsIHRoaXMuX3kyKSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3gyLCB0aGlzLl95Mik7IGJyZWFrOwogICAgICAgICAgY2FzZSAzOiB0aGlzLl9wb2ludCA9IDQ7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGIodGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXJkaW5hbE9wZW4kMSA9IChmdW5jdGlvbiBjdXN0b20odGVuc2lvbikgewoKICAgICAgZnVuY3Rpb24gY2FyZGluYWwoY29udGV4dCkgewogICAgICAgIHJldHVybiBuZXcgQ2FyZGluYWxPcGVuJDEoY29udGV4dCwgdGVuc2lvbik7CiAgICAgIH0KCiAgICAgIGNhcmRpbmFsLnRlbnNpb24gPSBmdW5jdGlvbih0ZW5zaW9uKSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgrdGVuc2lvbik7CiAgICAgIH07CgogICAgICByZXR1cm4gY2FyZGluYWw7CiAgICB9KSgwKTsKCiAgICBmdW5jdGlvbiBwb2ludCRjKHRoYXQsIHgsIHkpIHsKICAgICAgdmFyIHgxID0gdGhhdC5feDEsCiAgICAgICAgICB5MSA9IHRoYXQuX3kxLAogICAgICAgICAgeDIgPSB0aGF0Ll94MiwKICAgICAgICAgIHkyID0gdGhhdC5feTI7CgogICAgICBpZiAodGhhdC5fbDAxX2EgPiBlcHNpbG9uJGEpIHsKICAgICAgICB2YXIgYSA9IDIgKiB0aGF0Ll9sMDFfMmEgKyAzICogdGhhdC5fbDAxX2EgKiB0aGF0Ll9sMTJfYSArIHRoYXQuX2wxMl8yYSwKICAgICAgICAgICAgbiA9IDMgKiB0aGF0Ll9sMDFfYSAqICh0aGF0Ll9sMDFfYSArIHRoYXQuX2wxMl9hKTsKICAgICAgICB4MSA9ICh4MSAqIGEgLSB0aGF0Ll94MCAqIHRoYXQuX2wxMl8yYSArIHRoYXQuX3gyICogdGhhdC5fbDAxXzJhKSAvIG47CiAgICAgICAgeTEgPSAoeTEgKiBhIC0gdGhhdC5feTAgKiB0aGF0Ll9sMTJfMmEgKyB0aGF0Ll95MiAqIHRoYXQuX2wwMV8yYSkgLyBuOwogICAgICB9CgogICAgICBpZiAodGhhdC5fbDIzX2EgPiBlcHNpbG9uJGEpIHsKICAgICAgICB2YXIgYiA9IDIgKiB0aGF0Ll9sMjNfMmEgKyAzICogdGhhdC5fbDIzX2EgKiB0aGF0Ll9sMTJfYSArIHRoYXQuX2wxMl8yYSwKICAgICAgICAgICAgbSA9IDMgKiB0aGF0Ll9sMjNfYSAqICh0aGF0Ll9sMjNfYSArIHRoYXQuX2wxMl9hKTsKICAgICAgICB4MiA9ICh4MiAqIGIgKyB0aGF0Ll94MSAqIHRoYXQuX2wyM18yYSAtIHggKiB0aGF0Ll9sMTJfMmEpIC8gbTsKICAgICAgICB5MiA9ICh5MiAqIGIgKyB0aGF0Ll95MSAqIHRoYXQuX2wyM18yYSAtIHkgKiB0aGF0Ll9sMTJfMmEpIC8gbTsKICAgICAgfQoKICAgICAgdGhhdC5fY29udGV4dC5iZXppZXJDdXJ2ZVRvKHgxLCB5MSwgeDIsIHkyLCB0aGF0Ll94MiwgdGhhdC5feTIpOwogICAgfQoKICAgIGZ1bmN0aW9uIENhdG11bGxSb20kMShjb250ZXh0LCBhbHBoYSkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgICAgdGhpcy5fYWxwaGEgPSBhbHBoYTsKICAgIH0KCiAgICBDYXRtdWxsUm9tJDEucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPSB0aGlzLl94MiA9CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSA9IHRoaXMuX3kyID0gTmFOOwogICAgICAgIHRoaXMuX2wwMV9hID0gdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYSA9CiAgICAgICAgdGhpcy5fbDAxXzJhID0gdGhpcy5fbDEyXzJhID0gdGhpcy5fbDIzXzJhID0KICAgICAgICB0aGlzLl9wb2ludCA9IDA7CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDIsIHRoaXMuX3kyKTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDM6IHRoaXMucG9pbnQodGhpcy5feDIsIHRoaXMuX3kyKTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAxKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CgogICAgICAgIGlmICh0aGlzLl9wb2ludCkgewogICAgICAgICAgdmFyIHgyMyA9IHRoaXMuX3gyIC0geCwKICAgICAgICAgICAgICB5MjMgPSB0aGlzLl95MiAtIHk7CiAgICAgICAgICB0aGlzLl9sMjNfYSA9IE1hdGguc3FydCh0aGlzLl9sMjNfMmEgPSBNYXRoLnBvdyh4MjMgKiB4MjMgKyB5MjMgKiB5MjMsIHRoaXMuX2FscGhhKSk7CiAgICAgICAgfQoKICAgICAgICBzd2l0Y2ggKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICBjYXNlIDA6IHRoaXMuX3BvaW50ID0gMTsgdGhpcy5fbGluZSA/IHRoaXMuX2NvbnRleHQubGluZVRvKHgsIHkpIDogdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7IGJyZWFrOwogICAgICAgICAgY2FzZSAxOiB0aGlzLl9wb2ludCA9IDI7IGJyZWFrOwogICAgICAgICAgY2FzZSAyOiB0aGlzLl9wb2ludCA9IDM7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGModGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSwgdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYTsKICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEsIHRoaXMuX2wxMl8yYSA9IHRoaXMuX2wyM18yYTsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXRtdWxsUm9tJDEgPSAoZnVuY3Rpb24gY3VzdG9tKGFscGhhKSB7CgogICAgICBmdW5jdGlvbiBjYXRtdWxsUm9tKGNvbnRleHQpIHsKICAgICAgICByZXR1cm4gYWxwaGEgPyBuZXcgQ2F0bXVsbFJvbSQxKGNvbnRleHQsIGFscGhhKSA6IG5ldyBDYXJkaW5hbCQxKGNvbnRleHQsIDApOwogICAgICB9CgogICAgICBjYXRtdWxsUm9tLmFscGhhID0gZnVuY3Rpb24oYWxwaGEpIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCthbHBoYSk7CiAgICAgIH07CgogICAgICByZXR1cm4gY2F0bXVsbFJvbTsKICAgIH0pKDAuNSk7CgogICAgZnVuY3Rpb24gQ2F0bXVsbFJvbUNsb3NlZCQxKGNvbnRleHQsIGFscGhhKSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl9hbHBoYSA9IGFscGhhOwogICAgfQoKICAgIENhdG11bGxSb21DbG9zZWQkMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogbm9vcCQ5LAogICAgICBhcmVhRW5kOiBub29wJDksCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0gdGhpcy5feDMgPSB0aGlzLl94NCA9IHRoaXMuX3g1ID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSB0aGlzLl95MyA9IHRoaXMuX3k0ID0gdGhpcy5feTUgPSBOYU47CiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSA9IHRoaXMuX2wyM19hID0KICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEgPSB0aGlzLl9sMjNfMmEgPQogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAxOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3gzLCB0aGlzLl95Myk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAyOiB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKHRoaXMuX3gzLCB0aGlzLl95Myk7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgICAgY2FzZSAzOiB7CiAgICAgICAgICAgIHRoaXMucG9pbnQodGhpcy5feDMsIHRoaXMuX3kzKTsKICAgICAgICAgICAgdGhpcy5wb2ludCh0aGlzLl94NCwgdGhpcy5feTQpOwogICAgICAgICAgICB0aGlzLnBvaW50KHRoaXMuX3g1LCB0aGlzLl95NSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKCiAgICAgICAgaWYgKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICB2YXIgeDIzID0gdGhpcy5feDIgLSB4LAogICAgICAgICAgICAgIHkyMyA9IHRoaXMuX3kyIC0geTsKICAgICAgICAgIHRoaXMuX2wyM19hID0gTWF0aC5zcXJ0KHRoaXMuX2wyM18yYSA9IE1hdGgucG93KHgyMyAqIHgyMyArIHkyMyAqIHkyMywgdGhpcy5fYWxwaGEpKTsKICAgICAgICB9CgogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl94MyA9IHgsIHRoaXMuX3kzID0geTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgdGhpcy5fY29udGV4dC5tb3ZlVG8odGhpcy5feDQgPSB4LCB0aGlzLl95NCA9IHkpOyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl94NSA9IHgsIHRoaXMuX3k1ID0geTsgYnJlYWs7CiAgICAgICAgICBkZWZhdWx0OiBwb2ludCRjKHRoaXMsIHgsIHkpOyBicmVhazsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2wwMV9hID0gdGhpcy5fbDEyX2EsIHRoaXMuX2wxMl9hID0gdGhpcy5fbDIzX2E7CiAgICAgICAgdGhpcy5fbDAxXzJhID0gdGhpcy5fbDEyXzJhLCB0aGlzLl9sMTJfMmEgPSB0aGlzLl9sMjNfMmE7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSwgdGhpcy5feDEgPSB0aGlzLl94MiwgdGhpcy5feDIgPSB4OwogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEsIHRoaXMuX3kxID0gdGhpcy5feTIsIHRoaXMuX3kyID0geTsKICAgICAgfQogICAgfTsKCiAgICB2YXIgY2F0bXVsbFJvbUNsb3NlZCQxID0gKGZ1bmN0aW9uIGN1c3RvbShhbHBoYSkgewoKICAgICAgZnVuY3Rpb24gY2F0bXVsbFJvbShjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIGFscGhhID8gbmV3IENhdG11bGxSb21DbG9zZWQkMShjb250ZXh0LCBhbHBoYSkgOiBuZXcgQ2FyZGluYWxDbG9zZWQkMShjb250ZXh0LCAwKTsKICAgICAgfQoKICAgICAgY2F0bXVsbFJvbS5hbHBoYSA9IGZ1bmN0aW9uKGFscGhhKSB7CiAgICAgICAgcmV0dXJuIGN1c3RvbSgrYWxwaGEpOwogICAgICB9OwoKICAgICAgcmV0dXJuIGNhdG11bGxSb207CiAgICB9KSgwLjUpOwoKICAgIGZ1bmN0aW9uIENhdG11bGxSb21PcGVuJDEoY29udGV4dCwgYWxwaGEpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICAgIHRoaXMuX2FscGhhID0gYWxwaGE7CiAgICB9CgogICAgQ2F0bXVsbFJvbU9wZW4kMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fbGluZSA9IDA7CiAgICAgIH0sCiAgICAgIGFyZWFFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSBOYU47CiAgICAgIH0sCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5feDAgPSB0aGlzLl94MSA9IHRoaXMuX3gyID0KICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxID0gdGhpcy5feTIgPSBOYU47CiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSA9IHRoaXMuX2wyM19hID0KICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEgPSB0aGlzLl9sMjNfMmEgPQogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgfHwgKHRoaXMuX2xpbmUgIT09IDAgJiYgdGhpcy5fcG9pbnQgPT09IDMpKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX2xpbmUgPSAxIC0gdGhpcy5fbGluZTsKICAgICAgfSwKICAgICAgcG9pbnQ6IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgICB4ID0gK3gsIHkgPSAreTsKCiAgICAgICAgaWYgKHRoaXMuX3BvaW50KSB7CiAgICAgICAgICB2YXIgeDIzID0gdGhpcy5feDIgLSB4LAogICAgICAgICAgICAgIHkyMyA9IHRoaXMuX3kyIC0geTsKICAgICAgICAgIHRoaXMuX2wyM19hID0gTWF0aC5zcXJ0KHRoaXMuX2wyM18yYSA9IE1hdGgucG93KHgyMyAqIHgyMyArIHkyMyAqIHkyMywgdGhpcy5fYWxwaGEpKTsKICAgICAgICB9CgogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyBicmVhazsKICAgICAgICAgIGNhc2UgMjogdGhpcy5fcG9pbnQgPSAzOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8odGhpcy5feDIsIHRoaXMuX3kyKSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHRoaXMuX3gyLCB0aGlzLl95Mik7IGJyZWFrOwogICAgICAgICAgY2FzZSAzOiB0aGlzLl9wb2ludCA9IDQ7IC8vIHByb2NlZWQKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGModGhpcywgeCwgeSk7IGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fbDAxX2EgPSB0aGlzLl9sMTJfYSwgdGhpcy5fbDEyX2EgPSB0aGlzLl9sMjNfYTsKICAgICAgICB0aGlzLl9sMDFfMmEgPSB0aGlzLl9sMTJfMmEsIHRoaXMuX2wxMl8yYSA9IHRoaXMuX2wyM18yYTsKICAgICAgICB0aGlzLl94MCA9IHRoaXMuX3gxLCB0aGlzLl94MSA9IHRoaXMuX3gyLCB0aGlzLl94MiA9IHg7CiAgICAgICAgdGhpcy5feTAgPSB0aGlzLl95MSwgdGhpcy5feTEgPSB0aGlzLl95MiwgdGhpcy5feTIgPSB5OwogICAgICB9CiAgICB9OwoKICAgIHZhciBjYXRtdWxsUm9tT3BlbiQxID0gKGZ1bmN0aW9uIGN1c3RvbShhbHBoYSkgewoKICAgICAgZnVuY3Rpb24gY2F0bXVsbFJvbShjb250ZXh0KSB7CiAgICAgICAgcmV0dXJuIGFscGhhID8gbmV3IENhdG11bGxSb21PcGVuJDEoY29udGV4dCwgYWxwaGEpIDogbmV3IENhcmRpbmFsT3BlbiQxKGNvbnRleHQsIDApOwogICAgICB9CgogICAgICBjYXRtdWxsUm9tLmFscGhhID0gZnVuY3Rpb24oYWxwaGEpIHsKICAgICAgICByZXR1cm4gY3VzdG9tKCthbHBoYSk7CiAgICAgIH07CgogICAgICByZXR1cm4gY2F0bXVsbFJvbTsKICAgIH0pKDAuNSk7CgogICAgZnVuY3Rpb24gTGluZWFyQ2xvc2VkJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBMaW5lYXJDbG9zZWQkMS5wcm90b3R5cGUgPSB7CiAgICAgIGFyZWFTdGFydDogbm9vcCQ5LAogICAgICBhcmVhRW5kOiBub29wJDksCiAgICAgIGxpbmVTdGFydDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcG9pbnQgPSAwOwogICAgICB9LAogICAgICBsaW5lRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fcG9pbnQpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgaWYgKHRoaXMuX3BvaW50KSB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICBlbHNlIHRoaXMuX3BvaW50ID0gMSwgdGhpcy5fY29udGV4dC5tb3ZlVG8oeCwgeSk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gbGluZWFyQ2xvc2VkJDEoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IExpbmVhckNsb3NlZCQxKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNpZ24kMyh4KSB7CiAgICAgIHJldHVybiB4IDwgMCA/IC0xIDogMTsKICAgIH0KCiAgICAvLyBDYWxjdWxhdGUgdGhlIHNsb3BlcyBvZiB0aGUgdGFuZ2VudHMgKEhlcm1pdGUtdHlwZSBpbnRlcnBvbGF0aW9uKSBiYXNlZCBvbgogICAgLy8gdGhlIGZvbGxvd2luZyBwYXBlcjogU3RlZmZlbiwgTS4gMTk5MC4gQSBTaW1wbGUgTWV0aG9kIGZvciBNb25vdG9uaWMKICAgIC8vIEludGVycG9sYXRpb24gaW4gT25lIERpbWVuc2lvbi4gQXN0cm9ub215IGFuZCBBc3Ryb3BoeXNpY3MsIFZvbC4gMjM5LCBOTy4KICAgIC8vIE5PVihJSSksIFAuIDQ0MywgMTk5MC4KICAgIGZ1bmN0aW9uIHNsb3BlMyQxKHRoYXQsIHgyLCB5MikgewogICAgICB2YXIgaDAgPSB0aGF0Ll94MSAtIHRoYXQuX3gwLAogICAgICAgICAgaDEgPSB4MiAtIHRoYXQuX3gxLAogICAgICAgICAgczAgPSAodGhhdC5feTEgLSB0aGF0Ll95MCkgLyAoaDAgfHwgaDEgPCAwICYmIC0wKSwKICAgICAgICAgIHMxID0gKHkyIC0gdGhhdC5feTEpIC8gKGgxIHx8IGgwIDwgMCAmJiAtMCksCiAgICAgICAgICBwID0gKHMwICogaDEgKyBzMSAqIGgwKSAvIChoMCArIGgxKTsKICAgICAgcmV0dXJuIChzaWduJDMoczApICsgc2lnbiQzKHMxKSkgKiBNYXRoLm1pbihNYXRoLmFicyhzMCksIE1hdGguYWJzKHMxKSwgMC41ICogTWF0aC5hYnMocCkpIHx8IDA7CiAgICB9CgogICAgLy8gQ2FsY3VsYXRlIGEgb25lLXNpZGVkIHNsb3BlLgogICAgZnVuY3Rpb24gc2xvcGUyJDEodGhhdCwgdCkgewogICAgICB2YXIgaCA9IHRoYXQuX3gxIC0gdGhhdC5feDA7CiAgICAgIHJldHVybiBoID8gKDMgKiAodGhhdC5feTEgLSB0aGF0Ll95MCkgLyBoIC0gdCkgLyAyIDogdDsKICAgIH0KCiAgICAvLyBBY2NvcmRpbmcgdG8gaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvQ3ViaWNfSGVybWl0ZV9zcGxpbmUjUmVwcmVzZW50YXRpb25zCiAgICAvLyAieW91IGNhbiBleHByZXNzIGN1YmljIEhlcm1pdGUgaW50ZXJwb2xhdGlvbiBpbiB0ZXJtcyBvZiBjdWJpYyBCw6l6aWVyIGN1cnZlcwogICAgLy8gd2l0aCByZXNwZWN0IHRvIHRoZSBmb3VyIHZhbHVlcyBwMCwgcDAgKyBtMCAvIDMsIHAxIC0gbTEgLyAzLCBwMSIuCiAgICBmdW5jdGlvbiBwb2ludCRkKHRoYXQsIHQwLCB0MSkgewogICAgICB2YXIgeDAgPSB0aGF0Ll94MCwKICAgICAgICAgIHkwID0gdGhhdC5feTAsCiAgICAgICAgICB4MSA9IHRoYXQuX3gxLAogICAgICAgICAgeTEgPSB0aGF0Ll95MSwKICAgICAgICAgIGR4ID0gKHgxIC0geDApIC8gMzsKICAgICAgdGhhdC5fY29udGV4dC5iZXppZXJDdXJ2ZVRvKHgwICsgZHgsIHkwICsgZHggKiB0MCwgeDEgLSBkeCwgeTEgLSBkeCAqIHQxLCB4MSwgeTEpOwogICAgfQoKICAgIGZ1bmN0aW9uIE1vbm90b25lWCQxKGNvbnRleHQpIHsKICAgICAgdGhpcy5fY29udGV4dCA9IGNvbnRleHQ7CiAgICB9CgogICAgTW9ub3RvbmVYJDEucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEgPQogICAgICAgIHRoaXMuX3kwID0gdGhpcy5feTEgPQogICAgICAgIHRoaXMuX3QwID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAyOiB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94MSwgdGhpcy5feTEpOyBicmVhazsKICAgICAgICAgIGNhc2UgMzogcG9pbnQkZCh0aGlzLCB0aGlzLl90MCwgc2xvcGUyJDEodGhpcywgdGhpcy5fdDApKTsgYnJlYWs7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIHRoaXMuX3BvaW50ID09PSAxKSkgdGhpcy5fY29udGV4dC5jbG9zZVBhdGgoKTsKICAgICAgICB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdmFyIHQxID0gTmFOOwoKICAgICAgICB4ID0gK3gsIHkgPSAreTsKICAgICAgICBpZiAoeCA9PT0gdGhpcy5feDEgJiYgeSA9PT0gdGhpcy5feTEpIHJldHVybjsgLy8gSWdub3JlIGNvaW5jaWRlbnQgcG9pbnRzLgogICAgICAgIHN3aXRjaCAodGhpcy5fcG9pbnQpIHsKICAgICAgICAgIGNhc2UgMDogdGhpcy5fcG9pbnQgPSAxOyB0aGlzLl9saW5lID8gdGhpcy5fY29udGV4dC5saW5lVG8oeCwgeSkgOiB0aGlzLl9jb250ZXh0Lm1vdmVUbyh4LCB5KTsgYnJlYWs7CiAgICAgICAgICBjYXNlIDE6IHRoaXMuX3BvaW50ID0gMjsgYnJlYWs7CiAgICAgICAgICBjYXNlIDI6IHRoaXMuX3BvaW50ID0gMzsgcG9pbnQkZCh0aGlzLCBzbG9wZTIkMSh0aGlzLCB0MSA9IHNsb3BlMyQxKHRoaXMsIHgsIHkpKSwgdDEpOyBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6IHBvaW50JGQodGhpcywgdGhpcy5fdDAsIHQxID0gc2xvcGUzJDEodGhpcywgeCwgeSkpOyBicmVhazsKICAgICAgICB9CgogICAgICAgIHRoaXMuX3gwID0gdGhpcy5feDEsIHRoaXMuX3gxID0geDsKICAgICAgICB0aGlzLl95MCA9IHRoaXMuX3kxLCB0aGlzLl95MSA9IHk7CiAgICAgICAgdGhpcy5fdDAgPSB0MTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBNb25vdG9uZVkkMShjb250ZXh0KSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBuZXcgUmVmbGVjdENvbnRleHQkMShjb250ZXh0KTsKICAgIH0KCiAgICAoTW9ub3RvbmVZJDEucHJvdG90eXBlID0gT2JqZWN0LmNyZWF0ZShNb25vdG9uZVgkMS5wcm90b3R5cGUpKS5wb2ludCA9IGZ1bmN0aW9uKHgsIHkpIHsKICAgICAgTW9ub3RvbmVYJDEucHJvdG90eXBlLnBvaW50LmNhbGwodGhpcywgeSwgeCk7CiAgICB9OwoKICAgIGZ1bmN0aW9uIFJlZmxlY3RDb250ZXh0JDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBSZWZsZWN0Q29udGV4dCQxLnByb3RvdHlwZSA9IHsKICAgICAgbW92ZVRvOiBmdW5jdGlvbih4LCB5KSB7IHRoaXMuX2NvbnRleHQubW92ZVRvKHksIHgpOyB9LAogICAgICBjbG9zZVBhdGg6IGZ1bmN0aW9uKCkgeyB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOyB9LAogICAgICBsaW5lVG86IGZ1bmN0aW9uKHgsIHkpIHsgdGhpcy5fY29udGV4dC5saW5lVG8oeSwgeCk7IH0sCiAgICAgIGJlemllckN1cnZlVG86IGZ1bmN0aW9uKHgxLCB5MSwgeDIsIHkyLCB4LCB5KSB7IHRoaXMuX2NvbnRleHQuYmV6aWVyQ3VydmVUbyh5MSwgeDEsIHkyLCB4MiwgeSwgeCk7IH0KICAgIH07CgogICAgZnVuY3Rpb24gbW9ub3RvbmVYJDEoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IE1vbm90b25lWCQxKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1vbm90b25lWSQxKGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBNb25vdG9uZVkkMShjb250ZXh0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBOYXR1cmFsJDEoY29udGV4dCkgewogICAgICB0aGlzLl9jb250ZXh0ID0gY29udGV4dDsKICAgIH0KCiAgICBOYXR1cmFsJDEucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3ggPSBbXTsKICAgICAgICB0aGlzLl95ID0gW107CiAgICAgIH0sCiAgICAgIGxpbmVFbmQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB4ID0gdGhpcy5feCwKICAgICAgICAgICAgeSA9IHRoaXMuX3ksCiAgICAgICAgICAgIG4gPSB4Lmxlbmd0aDsKCiAgICAgICAgaWYgKG4pIHsKICAgICAgICAgIHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh4WzBdLCB5WzBdKSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHhbMF0sIHlbMF0pOwogICAgICAgICAgaWYgKG4gPT09IDIpIHsKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5saW5lVG8oeFsxXSwgeVsxXSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB2YXIgcHggPSBjb250cm9sUG9pbnRzJDEoeCksCiAgICAgICAgICAgICAgICBweSA9IGNvbnRyb2xQb2ludHMkMSh5KTsKICAgICAgICAgICAgZm9yICh2YXIgaTAgPSAwLCBpMSA9IDE7IGkxIDwgbjsgKytpMCwgKytpMSkgewogICAgICAgICAgICAgIHRoaXMuX2NvbnRleHQuYmV6aWVyQ3VydmVUbyhweFswXVtpMF0sIHB5WzBdW2kwXSwgcHhbMV1baTBdLCBweVsxXVtpMF0sIHhbaTFdLCB5W2kxXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmICh0aGlzLl9saW5lIHx8ICh0aGlzLl9saW5lICE9PSAwICYmIG4gPT09IDEpKSB0aGlzLl9jb250ZXh0LmNsb3NlUGF0aCgpOwogICAgICAgIHRoaXMuX2xpbmUgPSAxIC0gdGhpcy5fbGluZTsKICAgICAgICB0aGlzLl94ID0gdGhpcy5feSA9IG51bGw7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgdGhpcy5feC5wdXNoKCt4KTsKICAgICAgICB0aGlzLl95LnB1c2goK3kpOwogICAgICB9CiAgICB9OwoKICAgIC8vIFNlZSBodHRwczovL3d3dy5wYXJ0aWNsZWluY2VsbC5jb20vMjAxMi9iZXppZXItc3BsaW5lcy8gZm9yIGRlcml2YXRpb24uCiAgICBmdW5jdGlvbiBjb250cm9sUG9pbnRzJDEoeCkgewogICAgICB2YXIgaSwKICAgICAgICAgIG4gPSB4Lmxlbmd0aCAtIDEsCiAgICAgICAgICBtLAogICAgICAgICAgYSA9IG5ldyBBcnJheShuKSwKICAgICAgICAgIGIgPSBuZXcgQXJyYXkobiksCiAgICAgICAgICByID0gbmV3IEFycmF5KG4pOwogICAgICBhWzBdID0gMCwgYlswXSA9IDIsIHJbMF0gPSB4WzBdICsgMiAqIHhbMV07CiAgICAgIGZvciAoaSA9IDE7IGkgPCBuIC0gMTsgKytpKSBhW2ldID0gMSwgYltpXSA9IDQsIHJbaV0gPSA0ICogeFtpXSArIDIgKiB4W2kgKyAxXTsKICAgICAgYVtuIC0gMV0gPSAyLCBiW24gLSAxXSA9IDcsIHJbbiAtIDFdID0gOCAqIHhbbiAtIDFdICsgeFtuXTsKICAgICAgZm9yIChpID0gMTsgaSA8IG47ICsraSkgbSA9IGFbaV0gLyBiW2kgLSAxXSwgYltpXSAtPSBtLCByW2ldIC09IG0gKiByW2kgLSAxXTsKICAgICAgYVtuIC0gMV0gPSByW24gLSAxXSAvIGJbbiAtIDFdOwogICAgICBmb3IgKGkgPSBuIC0gMjsgaSA+PSAwOyAtLWkpIGFbaV0gPSAocltpXSAtIGFbaSArIDFdKSAvIGJbaV07CiAgICAgIGJbbiAtIDFdID0gKHhbbl0gKyBhW24gLSAxXSkgLyAyOwogICAgICBmb3IgKGkgPSAwOyBpIDwgbiAtIDE7ICsraSkgYltpXSA9IDIgKiB4W2kgKyAxXSAtIGFbaSArIDFdOwogICAgICByZXR1cm4gW2EsIGJdOwogICAgfQoKICAgIGZ1bmN0aW9uIG5hdHVyYWwkMShjb250ZXh0KSB7CiAgICAgIHJldHVybiBuZXcgTmF0dXJhbCQxKGNvbnRleHQpOwogICAgfQoKICAgIGZ1bmN0aW9uIFN0ZXAkMShjb250ZXh0LCB0KSB7CiAgICAgIHRoaXMuX2NvbnRleHQgPSBjb250ZXh0OwogICAgICB0aGlzLl90ID0gdDsKICAgIH0KCiAgICBTdGVwJDEucHJvdG90eXBlID0gewogICAgICBhcmVhU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2xpbmUgPSAwOwogICAgICB9LAogICAgICBhcmVhRW5kOiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLl9saW5lID0gTmFOOwogICAgICB9LAogICAgICBsaW5lU3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX3ggPSB0aGlzLl95ID0gTmFOOwogICAgICAgIHRoaXMuX3BvaW50ID0gMDsKICAgICAgfSwKICAgICAgbGluZUVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgaWYgKDAgPCB0aGlzLl90ICYmIHRoaXMuX3QgPCAxICYmIHRoaXMuX3BvaW50ID09PSAyKSB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94LCB0aGlzLl95KTsKICAgICAgICBpZiAodGhpcy5fbGluZSB8fCAodGhpcy5fbGluZSAhPT0gMCAmJiB0aGlzLl9wb2ludCA9PT0gMSkpIHRoaXMuX2NvbnRleHQuY2xvc2VQYXRoKCk7CiAgICAgICAgaWYgKHRoaXMuX2xpbmUgPj0gMCkgdGhpcy5fdCA9IDEgLSB0aGlzLl90LCB0aGlzLl9saW5lID0gMSAtIHRoaXMuX2xpbmU7CiAgICAgIH0sCiAgICAgIHBvaW50OiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgeCA9ICt4LCB5ID0gK3k7CiAgICAgICAgc3dpdGNoICh0aGlzLl9wb2ludCkgewogICAgICAgICAgY2FzZSAwOiB0aGlzLl9wb2ludCA9IDE7IHRoaXMuX2xpbmUgPyB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KSA6IHRoaXMuX2NvbnRleHQubW92ZVRvKHgsIHkpOyBicmVhazsKICAgICAgICAgIGNhc2UgMTogdGhpcy5fcG9pbnQgPSAyOyAvLyBwcm9jZWVkCiAgICAgICAgICBkZWZhdWx0OiB7CiAgICAgICAgICAgIGlmICh0aGlzLl90IDw9IDApIHsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh0aGlzLl94LCB5KTsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4LCB5KTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICB2YXIgeDEgPSB0aGlzLl94ICogKDEgLSB0aGlzLl90KSArIHggKiB0aGlzLl90OwogICAgICAgICAgICAgIHRoaXMuX2NvbnRleHQubGluZVRvKHgxLCB0aGlzLl95KTsKICAgICAgICAgICAgICB0aGlzLl9jb250ZXh0LmxpbmVUbyh4MSwgeSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuX3ggPSB4LCB0aGlzLl95ID0geTsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBzdGVwJDEoY29udGV4dCkgewogICAgICByZXR1cm4gbmV3IFN0ZXAkMShjb250ZXh0LCAwLjUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0ZXBCZWZvcmUkMShjb250ZXh0KSB7CiAgICAgIHJldHVybiBuZXcgU3RlcCQxKGNvbnRleHQsIDApOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0ZXBBZnRlciQxKGNvbnRleHQpIHsKICAgICAgcmV0dXJuIG5ldyBTdGVwJDEoY29udGV4dCwgMSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9uZSQ2KHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDEpKSByZXR1cm47CiAgICAgIGZvciAodmFyIGkgPSAxLCBqLCBzMCwgczEgPSBzZXJpZXNbb3JkZXJbMF1dLCBuLCBtID0gczEubGVuZ3RoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgczAgPSBzMSwgczEgPSBzZXJpZXNbb3JkZXJbaV1dOwogICAgICAgIGZvciAoaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICAgIHMxW2pdWzFdICs9IHMxW2pdWzBdID0gaXNOYU4oczBbal1bMV0pID8gczBbal1bMF0gOiBzMFtqXVsxXTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBub25lJDcoc2VyaWVzKSB7CiAgICAgIHZhciBuID0gc2VyaWVzLmxlbmd0aCwgbyA9IG5ldyBBcnJheShuKTsKICAgICAgd2hpbGUgKC0tbiA+PSAwKSBvW25dID0gbjsKICAgICAgcmV0dXJuIG87CiAgICB9CgogICAgZnVuY3Rpb24gc3RhY2tWYWx1ZSQxKGQsIGtleSkgewogICAgICByZXR1cm4gZFtrZXldOwogICAgfQoKICAgIGZ1bmN0aW9uIHN0YWNrJDEoKSB7CiAgICAgIHZhciBrZXlzID0gY29uc3RhbnQkcyhbXSksCiAgICAgICAgICBvcmRlciA9IG5vbmUkNywKICAgICAgICAgIG9mZnNldCA9IG5vbmUkNiwKICAgICAgICAgIHZhbHVlID0gc3RhY2tWYWx1ZSQxOwoKICAgICAgZnVuY3Rpb24gc3RhY2soZGF0YSkgewogICAgICAgIHZhciBreiA9IGtleXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgaSwKICAgICAgICAgICAgbSA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBuID0ga3oubGVuZ3RoLAogICAgICAgICAgICBzeiA9IG5ldyBBcnJheShuKSwKICAgICAgICAgICAgb3o7CgogICAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGZvciAodmFyIGtpID0ga3pbaV0sIHNpID0gc3pbaV0gPSBuZXcgQXJyYXkobSksIGogPSAwLCBzaWo7IGogPCBtOyArK2opIHsKICAgICAgICAgICAgc2lbal0gPSBzaWogPSBbMCwgK3ZhbHVlKGRhdGFbal0sIGtpLCBqLCBkYXRhKV07CiAgICAgICAgICAgIHNpai5kYXRhID0gZGF0YVtqXTsKICAgICAgICAgIH0KICAgICAgICAgIHNpLmtleSA9IGtpOwogICAgICAgIH0KCiAgICAgICAgZm9yIChpID0gMCwgb3ogPSBvcmRlcihzeik7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIHN6W296W2ldXS5pbmRleCA9IGk7CiAgICAgICAgfQoKICAgICAgICBvZmZzZXQoc3osIG96KTsKICAgICAgICByZXR1cm4gc3o7CiAgICAgIH0KCiAgICAgIHN0YWNrLmtleXMgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoa2V5cyA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHMoc2xpY2UkZC5jYWxsKF8pKSwgc3RhY2spIDoga2V5czsKICAgICAgfTsKCiAgICAgIHN0YWNrLnZhbHVlID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHZhbHVlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkcygrXyksIHN0YWNrKSA6IHZhbHVlOwogICAgICB9OwoKICAgICAgc3RhY2sub3JkZXIgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAob3JkZXIgPSBfID09IG51bGwgPyBub25lJDcgOiB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCRzKHNsaWNlJGQuY2FsbChfKSksIHN0YWNrKSA6IG9yZGVyOwogICAgICB9OwoKICAgICAgc3RhY2sub2Zmc2V0ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKG9mZnNldCA9IF8gPT0gbnVsbCA/IG5vbmUkNiA6IF8sIHN0YWNrKSA6IG9mZnNldDsKICAgICAgfTsKCiAgICAgIHJldHVybiBzdGFjazsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBhbmQkMShzZXJpZXMsIG9yZGVyKSB7CiAgICAgIGlmICghKChuID0gc2VyaWVzLmxlbmd0aCkgPiAwKSkgcmV0dXJuOwogICAgICBmb3IgKHZhciBpLCBuLCBqID0gMCwgbSA9IHNlcmllc1swXS5sZW5ndGgsIHk7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHkgPSBpID0gMDsgaSA8IG47ICsraSkgeSArPSBzZXJpZXNbaV1bal1bMV0gfHwgMDsKICAgICAgICBpZiAoeSkgZm9yIChpID0gMDsgaSA8IG47ICsraSkgc2VyaWVzW2ldW2pdWzFdIC89IHk7CiAgICAgIH0KICAgICAgbm9uZSQ2KHNlcmllcywgb3JkZXIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRpdmVyZ2luZyQyKHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDEpKSByZXR1cm47CiAgICAgIGZvciAodmFyIGksIGogPSAwLCBkLCBkeSwgeXAsIHluLCBuLCBtID0gc2VyaWVzW29yZGVyWzBdXS5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHlwID0geW4gPSAwLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChkeSA9IChkID0gc2VyaWVzW29yZGVyW2ldXVtqXSlbMV0gLSBkWzBdKSA+PSAwKSB7CiAgICAgICAgICAgIGRbMF0gPSB5cCwgZFsxXSA9IHlwICs9IGR5OwogICAgICAgICAgfSBlbHNlIGlmIChkeSA8IDApIHsKICAgICAgICAgICAgZFsxXSA9IHluLCBkWzBdID0geW4gKz0gZHk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBkWzBdID0geXA7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc2lsaG91ZXR0ZSQxKHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDApKSByZXR1cm47CiAgICAgIGZvciAodmFyIGogPSAwLCBzMCA9IHNlcmllc1tvcmRlclswXV0sIG4sIG0gPSBzMC5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBpID0gMCwgeSA9IDA7IGkgPCBuOyArK2kpIHkgKz0gc2VyaWVzW2ldW2pdWzFdIHx8IDA7CiAgICAgICAgczBbal1bMV0gKz0gczBbal1bMF0gPSAteSAvIDI7CiAgICAgIH0KICAgICAgbm9uZSQ2KHNlcmllcywgb3JkZXIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHdpZ2dsZSQxKHNlcmllcywgb3JkZXIpIHsKICAgICAgaWYgKCEoKG4gPSBzZXJpZXMubGVuZ3RoKSA+IDApIHx8ICEoKG0gPSAoczAgPSBzZXJpZXNbb3JkZXJbMF1dKS5sZW5ndGgpID4gMCkpIHJldHVybjsKICAgICAgZm9yICh2YXIgeSA9IDAsIGogPSAxLCBzMCwgbSwgbjsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBzMSA9IDAsIHMyID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdmFyIHNpID0gc2VyaWVzW29yZGVyW2ldXSwKICAgICAgICAgICAgICBzaWowID0gc2lbal1bMV0gfHwgMCwKICAgICAgICAgICAgICBzaWoxID0gc2lbaiAtIDFdWzFdIHx8IDAsCiAgICAgICAgICAgICAgczMgPSAoc2lqMCAtIHNpajEpIC8gMjsKICAgICAgICAgIGZvciAodmFyIGsgPSAwOyBrIDwgaTsgKytrKSB7CiAgICAgICAgICAgIHZhciBzayA9IHNlcmllc1tvcmRlcltrXV0sCiAgICAgICAgICAgICAgICBza2owID0gc2tbal1bMV0gfHwgMCwKICAgICAgICAgICAgICAgIHNrajEgPSBza1tqIC0gMV1bMV0gfHwgMDsKICAgICAgICAgICAgczMgKz0gc2tqMCAtIHNrajE7CiAgICAgICAgICB9CiAgICAgICAgICBzMSArPSBzaWowLCBzMiArPSBzMyAqIHNpajA7CiAgICAgICAgfQogICAgICAgIHMwW2ogLSAxXVsxXSArPSBzMFtqIC0gMV1bMF0gPSB5OwogICAgICAgIGlmIChzMSkgeSAtPSBzMiAvIHMxOwogICAgICB9CiAgICAgIHMwW2ogLSAxXVsxXSArPSBzMFtqIC0gMV1bMF0gPSB5OwogICAgICBub25lJDYoc2VyaWVzLCBvcmRlcik7CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nJGIoc2VyaWVzKSB7CiAgICAgIHZhciBzdW1zID0gc2VyaWVzLm1hcChzdW0kNSk7CiAgICAgIHJldHVybiBub25lJDcoc2VyaWVzKS5zb3J0KGZ1bmN0aW9uKGEsIGIpIHsgcmV0dXJuIHN1bXNbYV0gLSBzdW1zW2JdOyB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdW0kNShzZXJpZXMpIHsKICAgICAgdmFyIHMgPSAwLCBpID0gLTEsIG4gPSBzZXJpZXMubGVuZ3RoLCB2OwogICAgICB3aGlsZSAoKytpIDwgbikgaWYgKHYgPSArc2VyaWVzW2ldWzFdKSBzICs9IHY7CiAgICAgIHJldHVybiBzOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlc2NlbmRpbmckNShzZXJpZXMpIHsKICAgICAgcmV0dXJuIGFzY2VuZGluZyRiKHNlcmllcykucmV2ZXJzZSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGluc2lkZU91dCQxKHNlcmllcykgewogICAgICB2YXIgbiA9IHNlcmllcy5sZW5ndGgsCiAgICAgICAgICBpLAogICAgICAgICAgaiwKICAgICAgICAgIHN1bXMgPSBzZXJpZXMubWFwKHN1bSQ1KSwKICAgICAgICAgIG9yZGVyID0gbm9uZSQ3KHNlcmllcykuc29ydChmdW5jdGlvbihhLCBiKSB7IHJldHVybiBzdW1zW2JdIC0gc3Vtc1thXTsgfSksCiAgICAgICAgICB0b3AgPSAwLAogICAgICAgICAgYm90dG9tID0gMCwKICAgICAgICAgIHRvcHMgPSBbXSwKICAgICAgICAgIGJvdHRvbXMgPSBbXTsKCiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICBqID0gb3JkZXJbaV07CiAgICAgICAgaWYgKHRvcCA8IGJvdHRvbSkgewogICAgICAgICAgdG9wICs9IHN1bXNbal07CiAgICAgICAgICB0b3BzLnB1c2goaik7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGJvdHRvbSArPSBzdW1zW2pdOwogICAgICAgICAgYm90dG9tcy5wdXNoKGopOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIGJvdHRvbXMucmV2ZXJzZSgpLmNvbmNhdCh0b3BzKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXZlcnNlJDEoc2VyaWVzKSB7CiAgICAgIHJldHVybiBub25lJDcoc2VyaWVzKS5yZXZlcnNlKCk7CiAgICB9CgogICAgdmFyIHQwJDUgPSBuZXcgRGF0ZSwKICAgICAgICB0MSQ1ID0gbmV3IERhdGU7CgogICAgZnVuY3Rpb24gbmV3SW50ZXJ2YWwkMihmbG9vcmksIG9mZnNldGksIGNvdW50LCBmaWVsZCkgewoKICAgICAgZnVuY3Rpb24gaW50ZXJ2YWwoZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSksIGRhdGU7CiAgICAgIH0KCiAgICAgIGludGVydmFsLmZsb29yID0gaW50ZXJ2YWw7CgogICAgICBpbnRlcnZhbC5jZWlsID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKGRhdGUgLSAxKSksIG9mZnNldGkoZGF0ZSwgMSksIGZsb29yaShkYXRlKSwgZGF0ZTsKICAgICAgfTsKCiAgICAgIGludGVydmFsLnJvdW5kID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHZhciBkMCA9IGludGVydmFsKGRhdGUpLAogICAgICAgICAgICBkMSA9IGludGVydmFsLmNlaWwoZGF0ZSk7CiAgICAgICAgcmV0dXJuIGRhdGUgLSBkMCA8IGQxIC0gZGF0ZSA/IGQwIDogZDE7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5vZmZzZXQgPSBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgcmV0dXJuIG9mZnNldGkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSwgc3RlcCA9PSBudWxsID8gMSA6IE1hdGguZmxvb3Ioc3RlcCkpLCBkYXRlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwucmFuZ2UgPSBmdW5jdGlvbihzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICAgIHZhciByYW5nZSA9IFtdLCBwcmV2aW91czsKICAgICAgICBzdGFydCA9IGludGVydmFsLmNlaWwoc3RhcnQpOwogICAgICAgIHN0ZXAgPSBzdGVwID09IG51bGwgPyAxIDogTWF0aC5mbG9vcihzdGVwKTsKICAgICAgICBpZiAoIShzdGFydCA8IHN0b3ApIHx8ICEoc3RlcCA+IDApKSByZXR1cm4gcmFuZ2U7IC8vIGFsc28gaGFuZGxlcyBJbnZhbGlkIERhdGUKICAgICAgICBkbyByYW5nZS5wdXNoKHByZXZpb3VzID0gbmV3IERhdGUoK3N0YXJ0KSksIG9mZnNldGkoc3RhcnQsIHN0ZXApLCBmbG9vcmkoc3RhcnQpOwogICAgICAgIHdoaWxlIChwcmV2aW91cyA8IHN0YXJ0ICYmIHN0YXJ0IDwgc3RvcCk7CiAgICAgICAgcmV0dXJuIHJhbmdlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwuZmlsdGVyID0gZnVuY3Rpb24odGVzdCkgewogICAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHdoaWxlIChmbG9vcmkoZGF0ZSksICF0ZXN0KGRhdGUpKSBkYXRlLnNldFRpbWUoZGF0ZSAtIDEpOwogICAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHsKICAgICAgICAgICAgaWYgKHN0ZXAgPCAwKSB3aGlsZSAoKytzdGVwIDw9IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCAtMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0gZWxzZSB3aGlsZSAoLS1zdGVwID49IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCArMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIGlmIChjb3VudCkgewogICAgICAgIGludGVydmFsLmNvdW50ID0gZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgICAgdDAkNS5zZXRUaW1lKCtzdGFydCksIHQxJDUuc2V0VGltZSgrZW5kKTsKICAgICAgICAgIGZsb29yaSh0MCQ1KSwgZmxvb3JpKHQxJDUpOwogICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IoY291bnQodDAkNSwgdDEkNSkpOwogICAgICAgIH07CgogICAgICAgIGludGVydmFsLmV2ZXJ5ID0gZnVuY3Rpb24oc3RlcCkgewogICAgICAgICAgc3RlcCA9IE1hdGguZmxvb3Ioc3RlcCk7CiAgICAgICAgICByZXR1cm4gIWlzRmluaXRlKHN0ZXApIHx8ICEoc3RlcCA+IDApID8gbnVsbAogICAgICAgICAgICAgIDogIShzdGVwID4gMSkgPyBpbnRlcnZhbAogICAgICAgICAgICAgIDogaW50ZXJ2YWwuZmlsdGVyKGZpZWxkCiAgICAgICAgICAgICAgICAgID8gZnVuY3Rpb24oZCkgeyByZXR1cm4gZmllbGQoZCkgJSBzdGVwID09PSAwOyB9CiAgICAgICAgICAgICAgICAgIDogZnVuY3Rpb24oZCkgeyByZXR1cm4gaW50ZXJ2YWwuY291bnQoMCwgZCkgJSBzdGVwID09PSAwOyB9KTsKICAgICAgICB9OwogICAgICB9CgogICAgICByZXR1cm4gaW50ZXJ2YWw7CiAgICB9CgogICAgdmFyIG1pbGxpc2Vjb25kJDIgPSBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKCkgewogICAgICAvLyBub29wCiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0VGltZSgrZGF0ZSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kIC0gc3RhcnQ7CiAgICB9KTsKCiAgICAvLyBBbiBvcHRpbWl6ZWQgaW1wbGVtZW50YXRpb24gZm9yIHRoaXMgc2ltcGxlIGNhc2UuCiAgICBtaWxsaXNlY29uZCQyLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICBrID0gTWF0aC5mbG9vcihrKTsKICAgICAgaWYgKCFpc0Zpbml0ZShrKSB8fCAhKGsgPiAwKSkgcmV0dXJuIG51bGw7CiAgICAgIGlmICghKGsgPiAxKSkgcmV0dXJuIG1pbGxpc2Vjb25kJDI7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFRpbWUoTWF0aC5mbG9vcihkYXRlIC8gaykgKiBrKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0VGltZSgrZGF0ZSArIHN0ZXAgKiBrKTsKICAgICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gazsKICAgICAgfSk7CiAgICB9OwogICAgdmFyIG1pbGxpc2Vjb25kcyQxID0gbWlsbGlzZWNvbmQkMi5yYW5nZTsKCiAgICB2YXIgZHVyYXRpb25TZWNvbmQkNCA9IDFlMzsKICAgIHZhciBkdXJhdGlvbk1pbnV0ZSQ0ID0gNmU0OwogICAgdmFyIGR1cmF0aW9uSG91ciQ0ID0gMzZlNTsKICAgIHZhciBkdXJhdGlvbkRheSQ0ID0gODY0ZTU7CiAgICB2YXIgZHVyYXRpb25XZWVrJDQgPSA2MDQ4ZTU7CgogICAgdmFyIHNlY29uZCQyID0gbmV3SW50ZXJ2YWwkMihmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VGltZShNYXRoLmZsb29yKGRhdGUgLyBkdXJhdGlvblNlY29uZCQ0KSAqIGR1cmF0aW9uU2Vjb25kJDQpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25TZWNvbmQkNCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25TZWNvbmQkNDsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDU2Vjb25kcygpOwogICAgfSk7CiAgICB2YXIgc2Vjb25kcyQxID0gc2Vjb25kJDIucmFuZ2U7CgogICAgdmFyIG1pbnV0ZSQyID0gbmV3SW50ZXJ2YWwkMihmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VGltZShNYXRoLmZsb29yKGRhdGUgLyBkdXJhdGlvbk1pbnV0ZSQ0KSAqIGR1cmF0aW9uTWludXRlJDQpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25NaW51dGUkNCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25NaW51dGUkNDsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0TWludXRlcygpOwogICAgfSk7CiAgICB2YXIgbWludXRlcyQxID0gbWludXRlJDIucmFuZ2U7CgogICAgdmFyIGhvdXIkMiA9IG5ld0ludGVydmFsJDIoZnVuY3Rpb24oZGF0ZSkgewogICAgICB2YXIgb2Zmc2V0ID0gZGF0ZS5nZXRUaW1lem9uZU9mZnNldCgpICogZHVyYXRpb25NaW51dGUkNCAlIGR1cmF0aW9uSG91ciQ0OwogICAgICBpZiAob2Zmc2V0IDwgMCkgb2Zmc2V0ICs9IGR1cmF0aW9uSG91ciQ0OwogICAgICBkYXRlLnNldFRpbWUoTWF0aC5mbG9vcigoK2RhdGUgLSBvZmZzZXQpIC8gZHVyYXRpb25Ib3VyJDQpICogZHVyYXRpb25Ib3VyJDQgKyBvZmZzZXQpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25Ib3VyJDQpOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uSG91ciQ0OwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRIb3VycygpOwogICAgfSk7CiAgICB2YXIgaG91cnMkMSA9IGhvdXIkMi5yYW5nZTsKCiAgICB2YXIgZGF5JDIgPSBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXREYXRlKGRhdGUuZ2V0RGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQgLSAoZW5kLmdldFRpbWV6b25lT2Zmc2V0KCkgLSBzdGFydC5nZXRUaW1lem9uZU9mZnNldCgpKSAqIGR1cmF0aW9uTWludXRlJDQpIC8gZHVyYXRpb25EYXkkNDsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0RGF0ZSgpIC0gMTsKICAgIH0pOwogICAgdmFyIGRheXMkMSA9IGRheSQyLnJhbmdlOwoKICAgIGZ1bmN0aW9uIHdlZWtkYXkkMihpKSB7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldERhdGUoZGF0ZS5nZXREYXRlKCkgLSAoZGF0ZS5nZXREYXkoKSArIDcgLSBpKSAlIDcpOwogICAgICAgIGRhdGUuc2V0SG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldERhdGUoZGF0ZS5nZXREYXRlKCkgKyBzdGVwICogNyk7CiAgICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0IC0gKGVuZC5nZXRUaW1lem9uZU9mZnNldCgpIC0gc3RhcnQuZ2V0VGltZXpvbmVPZmZzZXQoKSkgKiBkdXJhdGlvbk1pbnV0ZSQ0KSAvIGR1cmF0aW9uV2VlayQ0OwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgc3VuZGF5JDIgPSB3ZWVrZGF5JDIoMCk7CiAgICB2YXIgbW9uZGF5JDIgPSB3ZWVrZGF5JDIoMSk7CiAgICB2YXIgdHVlc2RheSQyID0gd2Vla2RheSQyKDIpOwogICAgdmFyIHdlZG5lc2RheSQyID0gd2Vla2RheSQyKDMpOwogICAgdmFyIHRodXJzZGF5JDIgPSB3ZWVrZGF5JDIoNCk7CiAgICB2YXIgZnJpZGF5JDIgPSB3ZWVrZGF5JDIoNSk7CiAgICB2YXIgc2F0dXJkYXkkMiA9IHdlZWtkYXkkMig2KTsKCiAgICB2YXIgc3VuZGF5cyQxID0gc3VuZGF5JDIucmFuZ2U7CiAgICB2YXIgbW9uZGF5cyQxID0gbW9uZGF5JDIucmFuZ2U7CiAgICB2YXIgdHVlc2RheXMkMSA9IHR1ZXNkYXkkMi5yYW5nZTsKICAgIHZhciB3ZWRuZXNkYXlzJDEgPSB3ZWRuZXNkYXkkMi5yYW5nZTsKICAgIHZhciB0aHVyc2RheXMkMSA9IHRodXJzZGF5JDIucmFuZ2U7CiAgICB2YXIgZnJpZGF5cyQxID0gZnJpZGF5JDIucmFuZ2U7CiAgICB2YXIgc2F0dXJkYXlzJDEgPSBzYXR1cmRheSQyLnJhbmdlOwoKICAgIHZhciBtb250aCQyID0gbmV3SW50ZXJ2YWwkMihmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0RGF0ZSgxKTsKICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRNb250aChkYXRlLmdldE1vbnRoKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRNb250aCgpIC0gc3RhcnQuZ2V0TW9udGgoKSArIChlbmQuZ2V0RnVsbFllYXIoKSAtIHN0YXJ0LmdldEZ1bGxZZWFyKCkpICogMTI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldE1vbnRoKCk7CiAgICB9KTsKICAgIHZhciBtb250aHMkMSA9IG1vbnRoJDIucmFuZ2U7CgogICAgdmFyIHllYXIkMiA9IG5ld0ludGVydmFsJDIoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldE1vbnRoKDAsIDEpOwogICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldEZ1bGxZZWFyKGRhdGUuZ2V0RnVsbFllYXIoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldEZ1bGxZZWFyKCkgLSBzdGFydC5nZXRGdWxsWWVhcigpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRGdWxsWWVhcigpOwogICAgfSk7CgogICAgLy8gQW4gb3B0aW1pemVkIGltcGxlbWVudGF0aW9uIGZvciB0aGlzIHNpbXBsZSBjYXNlLgogICAgeWVhciQyLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICByZXR1cm4gIWlzRmluaXRlKGsgPSBNYXRoLmZsb29yKGspKSB8fCAhKGsgPiAwKSA/IG51bGwgOiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldEZ1bGxZZWFyKE1hdGguZmxvb3IoZGF0ZS5nZXRGdWxsWWVhcigpIC8gaykgKiBrKTsKICAgICAgICBkYXRlLnNldE1vbnRoKDAsIDEpOwogICAgICAgIGRhdGUuc2V0SG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldEZ1bGxZZWFyKGRhdGUuZ2V0RnVsbFllYXIoKSArIHN0ZXAgKiBrKTsKICAgICAgfSk7CiAgICB9OwogICAgdmFyIHllYXJzJDEgPSB5ZWFyJDIucmFuZ2U7CgogICAgdmFyIHV0Y01pbnV0ZSQyID0gbmV3SW50ZXJ2YWwkMihmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VVRDU2Vjb25kcygwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRUaW1lKCtkYXRlICsgc3RlcCAqIGR1cmF0aW9uTWludXRlJDQpOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uTWludXRlJDQ7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ01pbnV0ZXMoKTsKICAgIH0pOwogICAgdmFyIHV0Y01pbnV0ZXMkMSA9IHV0Y01pbnV0ZSQyLnJhbmdlOwoKICAgIHZhciB1dGNIb3VyJDIgPSBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENNaW51dGVzKDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFRpbWUoK2RhdGUgKyBzdGVwICogZHVyYXRpb25Ib3VyJDQpOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uSG91ciQ0OwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRVVENIb3VycygpOwogICAgfSk7CiAgICB2YXIgdXRjSG91cnMkMSA9IHV0Y0hvdXIkMi5yYW5nZTsKCiAgICB2YXIgdXRjRGF5JDIgPSBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENEYXRlKGRhdGUuZ2V0VVRDRGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25EYXkkNDsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDRGF0ZSgpIC0gMTsKICAgIH0pOwogICAgdmFyIHV0Y0RheXMkMSA9IHV0Y0RheSQyLnJhbmdlOwoKICAgIGZ1bmN0aW9uIHV0Y1dlZWtkYXkkMihpKSB7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgLSAoZGF0ZS5nZXRVVENEYXkoKSArIDcgLSBpKSAlIDcpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgKyBzdGVwICogNyk7CiAgICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uV2VlayQ0OwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgdXRjU3VuZGF5JDIgPSB1dGNXZWVrZGF5JDIoMCk7CiAgICB2YXIgdXRjTW9uZGF5JDIgPSB1dGNXZWVrZGF5JDIoMSk7CiAgICB2YXIgdXRjVHVlc2RheSQyID0gdXRjV2Vla2RheSQyKDIpOwogICAgdmFyIHV0Y1dlZG5lc2RheSQyID0gdXRjV2Vla2RheSQyKDMpOwogICAgdmFyIHV0Y1RodXJzZGF5JDIgPSB1dGNXZWVrZGF5JDIoNCk7CiAgICB2YXIgdXRjRnJpZGF5JDIgPSB1dGNXZWVrZGF5JDIoNSk7CiAgICB2YXIgdXRjU2F0dXJkYXkkMiA9IHV0Y1dlZWtkYXkkMig2KTsKCiAgICB2YXIgdXRjU3VuZGF5cyQxID0gdXRjU3VuZGF5JDIucmFuZ2U7CiAgICB2YXIgdXRjTW9uZGF5cyQxID0gdXRjTW9uZGF5JDIucmFuZ2U7CiAgICB2YXIgdXRjVHVlc2RheXMkMSA9IHV0Y1R1ZXNkYXkkMi5yYW5nZTsKICAgIHZhciB1dGNXZWRuZXNkYXlzJDEgPSB1dGNXZWRuZXNkYXkkMi5yYW5nZTsKICAgIHZhciB1dGNUaHVyc2RheXMkMSA9IHV0Y1RodXJzZGF5JDIucmFuZ2U7CiAgICB2YXIgdXRjRnJpZGF5cyQxID0gdXRjRnJpZGF5JDIucmFuZ2U7CiAgICB2YXIgdXRjU2F0dXJkYXlzJDEgPSB1dGNTYXR1cmRheSQyLnJhbmdlOwoKICAgIHZhciB1dGNNb250aCQyID0gbmV3SW50ZXJ2YWwkMihmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VVRDRGF0ZSgxKTsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENNb250aChkYXRlLmdldFVUQ01vbnRoKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRVVENNb250aCgpIC0gc3RhcnQuZ2V0VVRDTW9udGgoKSArIChlbmQuZ2V0VVRDRnVsbFllYXIoKSAtIHN0YXJ0LmdldFVUQ0Z1bGxZZWFyKCkpICogMTI7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ01vbnRoKCk7CiAgICB9KTsKICAgIHZhciB1dGNNb250aHMkMSA9IHV0Y01vbnRoJDIucmFuZ2U7CgogICAgdmFyIHV0Y1llYXIkMiA9IG5ld0ludGVydmFsJDIoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldFVUQ01vbnRoKDAsIDEpOwogICAgICBkYXRlLnNldFVUQ0hvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSArIHN0ZXApOwogICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICByZXR1cm4gZW5kLmdldFVUQ0Z1bGxZZWFyKCkgLSBzdGFydC5nZXRVVENGdWxsWWVhcigpOwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXRVVENGdWxsWWVhcigpOwogICAgfSk7CgogICAgLy8gQW4gb3B0aW1pemVkIGltcGxlbWVudGF0aW9uIGZvciB0aGlzIHNpbXBsZSBjYXNlLgogICAgdXRjWWVhciQyLmV2ZXJ5ID0gZnVuY3Rpb24oaykgewogICAgICByZXR1cm4gIWlzRmluaXRlKGsgPSBNYXRoLmZsb29yKGspKSB8fCAhKGsgPiAwKSA/IG51bGwgOiBuZXdJbnRlcnZhbCQyKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKE1hdGguZmxvb3IoZGF0ZS5nZXRVVENGdWxsWWVhcigpIC8gaykgKiBrKTsKICAgICAgICBkYXRlLnNldFVUQ01vbnRoKDAsIDEpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0Z1bGxZZWFyKGRhdGUuZ2V0VVRDRnVsbFllYXIoKSArIHN0ZXAgKiBrKTsKICAgICAgfSk7CiAgICB9OwogICAgdmFyIHV0Y1llYXJzJDEgPSB1dGNZZWFyJDIucmFuZ2U7CgogICAgdmFyIHQwJDYgPSBuZXcgRGF0ZSwKICAgICAgICB0MSQ2ID0gbmV3IERhdGU7CgogICAgZnVuY3Rpb24gbmV3SW50ZXJ2YWwkMyhmbG9vcmksIG9mZnNldGksIGNvdW50LCBmaWVsZCkgewoKICAgICAgZnVuY3Rpb24gaW50ZXJ2YWwoZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IGFyZ3VtZW50cy5sZW5ndGggPT09IDAgPyBuZXcgRGF0ZSA6IG5ldyBEYXRlKCtkYXRlKSksIGRhdGU7CiAgICAgIH0KCiAgICAgIGludGVydmFsLmZsb29yID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSksIGRhdGU7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5jZWlsID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHJldHVybiBmbG9vcmkoZGF0ZSA9IG5ldyBEYXRlKGRhdGUgLSAxKSksIG9mZnNldGkoZGF0ZSwgMSksIGZsb29yaShkYXRlKSwgZGF0ZTsKICAgICAgfTsKCiAgICAgIGludGVydmFsLnJvdW5kID0gZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIHZhciBkMCA9IGludGVydmFsKGRhdGUpLAogICAgICAgICAgICBkMSA9IGludGVydmFsLmNlaWwoZGF0ZSk7CiAgICAgICAgcmV0dXJuIGRhdGUgLSBkMCA8IGQxIC0gZGF0ZSA/IGQwIDogZDE7CiAgICAgIH07CgogICAgICBpbnRlcnZhbC5vZmZzZXQgPSBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgcmV0dXJuIG9mZnNldGkoZGF0ZSA9IG5ldyBEYXRlKCtkYXRlKSwgc3RlcCA9PSBudWxsID8gMSA6IE1hdGguZmxvb3Ioc3RlcCkpLCBkYXRlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwucmFuZ2UgPSBmdW5jdGlvbihzdGFydCwgc3RvcCwgc3RlcCkgewogICAgICAgIHZhciByYW5nZSA9IFtdLCBwcmV2aW91czsKICAgICAgICBzdGFydCA9IGludGVydmFsLmNlaWwoc3RhcnQpOwogICAgICAgIHN0ZXAgPSBzdGVwID09IG51bGwgPyAxIDogTWF0aC5mbG9vcihzdGVwKTsKICAgICAgICBpZiAoIShzdGFydCA8IHN0b3ApIHx8ICEoc3RlcCA+IDApKSByZXR1cm4gcmFuZ2U7IC8vIGFsc28gaGFuZGxlcyBJbnZhbGlkIERhdGUKICAgICAgICBkbyByYW5nZS5wdXNoKHByZXZpb3VzID0gbmV3IERhdGUoK3N0YXJ0KSksIG9mZnNldGkoc3RhcnQsIHN0ZXApLCBmbG9vcmkoc3RhcnQpOwogICAgICAgIHdoaWxlIChwcmV2aW91cyA8IHN0YXJ0ICYmIHN0YXJ0IDwgc3RvcCk7CiAgICAgICAgcmV0dXJuIHJhbmdlOwogICAgICB9OwoKICAgICAgaW50ZXJ2YWwuZmlsdGVyID0gZnVuY3Rpb24odGVzdCkgewogICAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQzKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHdoaWxlIChmbG9vcmkoZGF0ZSksICF0ZXN0KGRhdGUpKSBkYXRlLnNldFRpbWUoZGF0ZSAtIDEpOwogICAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICAgIGlmIChkYXRlID49IGRhdGUpIHsKICAgICAgICAgICAgaWYgKHN0ZXAgPCAwKSB3aGlsZSAoKytzdGVwIDw9IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCAtMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0gZWxzZSB3aGlsZSAoLS1zdGVwID49IDApIHsKICAgICAgICAgICAgICB3aGlsZSAob2Zmc2V0aShkYXRlLCArMSksICF0ZXN0KGRhdGUpKSB7fSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLWVtcHR5CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIGlmIChjb3VudCkgewogICAgICAgIGludGVydmFsLmNvdW50ID0gZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgICAgdDAkNi5zZXRUaW1lKCtzdGFydCksIHQxJDYuc2V0VGltZSgrZW5kKTsKICAgICAgICAgIGZsb29yaSh0MCQ2KSwgZmxvb3JpKHQxJDYpOwogICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IoY291bnQodDAkNiwgdDEkNikpOwogICAgICAgIH07CgogICAgICAgIGludGVydmFsLmV2ZXJ5ID0gZnVuY3Rpb24oc3RlcCkgewogICAgICAgICAgc3RlcCA9IE1hdGguZmxvb3Ioc3RlcCk7CiAgICAgICAgICByZXR1cm4gIWlzRmluaXRlKHN0ZXApIHx8ICEoc3RlcCA+IDApID8gbnVsbAogICAgICAgICAgICAgIDogIShzdGVwID4gMSkgPyBpbnRlcnZhbAogICAgICAgICAgICAgIDogaW50ZXJ2YWwuZmlsdGVyKGZpZWxkCiAgICAgICAgICAgICAgICAgID8gZnVuY3Rpb24oZCkgeyByZXR1cm4gZmllbGQoZCkgJSBzdGVwID09PSAwOyB9CiAgICAgICAgICAgICAgICAgIDogZnVuY3Rpb24oZCkgeyByZXR1cm4gaW50ZXJ2YWwuY291bnQoMCwgZCkgJSBzdGVwID09PSAwOyB9KTsKICAgICAgICB9OwogICAgICB9CgogICAgICByZXR1cm4gaW50ZXJ2YWw7CiAgICB9CgogICAgdmFyIGR1cmF0aW9uTWludXRlJDUgPSA2ZTQ7CiAgICB2YXIgZHVyYXRpb25EYXkkNSA9IDg2NGU1OwogICAgdmFyIGR1cmF0aW9uV2VlayQ1ID0gNjA0OGU1OwoKICAgIHZhciBkYXkkMyA9IG5ld0ludGVydmFsJDMoZnVuY3Rpb24oZGF0ZSkgewogICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICBkYXRlLnNldERhdGUoZGF0ZS5nZXREYXRlKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIChlbmQgLSBzdGFydCAtIChlbmQuZ2V0VGltZXpvbmVPZmZzZXQoKSAtIHN0YXJ0LmdldFRpbWV6b25lT2Zmc2V0KCkpICogZHVyYXRpb25NaW51dGUkNSkgLyBkdXJhdGlvbkRheSQ1OwogICAgfSwgZnVuY3Rpb24oZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS5nZXREYXRlKCkgLSAxOwogICAgfSk7CgogICAgZnVuY3Rpb24gd2Vla2RheSQzKGkpIHsKICAgICAgcmV0dXJuIG5ld0ludGVydmFsJDMoZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIGRhdGUuc2V0RGF0ZShkYXRlLmdldERhdGUoKSAtIChkYXRlLmdldERheSgpICsgNyAtIGkpICUgNyk7CiAgICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0RGF0ZShkYXRlLmdldERhdGUoKSArIHN0ZXAgKiA3KTsKICAgICAgfSwgZnVuY3Rpb24oc3RhcnQsIGVuZCkgewogICAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQgLSAoZW5kLmdldFRpbWV6b25lT2Zmc2V0KCkgLSBzdGFydC5nZXRUaW1lem9uZU9mZnNldCgpKSAqIGR1cmF0aW9uTWludXRlJDUpIC8gZHVyYXRpb25XZWVrJDU7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBzdW5kYXkkMyA9IHdlZWtkYXkkMygwKTsKICAgIHZhciBtb25kYXkkMyA9IHdlZWtkYXkkMygxKTsKICAgIHZhciB0dWVzZGF5JDMgPSB3ZWVrZGF5JDMoMik7CiAgICB2YXIgd2VkbmVzZGF5JDMgPSB3ZWVrZGF5JDMoMyk7CiAgICB2YXIgdGh1cnNkYXkkMyA9IHdlZWtkYXkkMyg0KTsKICAgIHZhciBmcmlkYXkkMyA9IHdlZWtkYXkkMyg1KTsKICAgIHZhciBzYXR1cmRheSQzID0gd2Vla2RheSQzKDYpOwoKICAgIHZhciB5ZWFyJDMgPSBuZXdJbnRlcnZhbCQzKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRNb250aCgwLCAxKTsKICAgICAgZGF0ZS5zZXRIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkYXRlLmdldEZ1bGxZZWFyKCkgKyBzdGVwKTsKICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgcmV0dXJuIGVuZC5nZXRGdWxsWWVhcigpIC0gc3RhcnQuZ2V0RnVsbFllYXIoKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0RnVsbFllYXIoKTsKICAgIH0pOwoKICAgIC8vIEFuIG9wdGltaXplZCBpbXBsZW1lbnRhdGlvbiBmb3IgdGhpcyBzaW1wbGUgY2FzZS4KICAgIHllYXIkMy5ldmVyeSA9IGZ1bmN0aW9uKGspIHsKICAgICAgcmV0dXJuICFpc0Zpbml0ZShrID0gTWF0aC5mbG9vcihrKSkgfHwgIShrID4gMCkgPyBudWxsIDogbmV3SW50ZXJ2YWwkMyhmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihNYXRoLmZsb29yKGRhdGUuZ2V0RnVsbFllYXIoKSAvIGspICogayk7CiAgICAgICAgZGF0ZS5zZXRNb250aCgwLCAxKTsKICAgICAgICBkYXRlLnNldEhvdXJzKDAsIDAsIDAsIDApOwogICAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkYXRlLmdldEZ1bGxZZWFyKCkgKyBzdGVwICogayk7CiAgICAgIH0pOwogICAgfTsKCiAgICB2YXIgdXRjRGF5JDMgPSBuZXdJbnRlcnZhbCQzKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgZGF0ZS5zZXRVVENEYXRlKGRhdGUuZ2V0VVRDRGF0ZSgpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiAoZW5kIC0gc3RhcnQpIC8gZHVyYXRpb25EYXkkNTsKICAgIH0sIGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgcmV0dXJuIGRhdGUuZ2V0VVRDRGF0ZSgpIC0gMTsKICAgIH0pOwoKICAgIGZ1bmN0aW9uIHV0Y1dlZWtkYXkkMyhpKSB7CiAgICAgIHJldHVybiBuZXdJbnRlcnZhbCQzKGZ1bmN0aW9uKGRhdGUpIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgLSAoZGF0ZS5nZXRVVENEYXkoKSArIDcgLSBpKSAlIDcpOwogICAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICAgIH0sIGZ1bmN0aW9uKGRhdGUsIHN0ZXApIHsKICAgICAgICBkYXRlLnNldFVUQ0RhdGUoZGF0ZS5nZXRVVENEYXRlKCkgKyBzdGVwICogNyk7CiAgICAgIH0sIGZ1bmN0aW9uKHN0YXJ0LCBlbmQpIHsKICAgICAgICByZXR1cm4gKGVuZCAtIHN0YXJ0KSAvIGR1cmF0aW9uV2VlayQ1OwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgdXRjU3VuZGF5JDMgPSB1dGNXZWVrZGF5JDMoMCk7CiAgICB2YXIgdXRjTW9uZGF5JDMgPSB1dGNXZWVrZGF5JDMoMSk7CiAgICB2YXIgdXRjVHVlc2RheSQzID0gdXRjV2Vla2RheSQzKDIpOwogICAgdmFyIHV0Y1dlZG5lc2RheSQzID0gdXRjV2Vla2RheSQzKDMpOwogICAgdmFyIHV0Y1RodXJzZGF5JDMgPSB1dGNXZWVrZGF5JDMoNCk7CiAgICB2YXIgdXRjRnJpZGF5JDMgPSB1dGNXZWVrZGF5JDMoNSk7CiAgICB2YXIgdXRjU2F0dXJkYXkkMyA9IHV0Y1dlZWtkYXkkMyg2KTsKCiAgICB2YXIgdXRjWWVhciQzID0gbmV3SW50ZXJ2YWwkMyhmdW5jdGlvbihkYXRlKSB7CiAgICAgIGRhdGUuc2V0VVRDTW9udGgoMCwgMSk7CiAgICAgIGRhdGUuc2V0VVRDSG91cnMoMCwgMCwgMCwgMCk7CiAgICB9LCBmdW5jdGlvbihkYXRlLCBzdGVwKSB7CiAgICAgIGRhdGUuc2V0VVRDRnVsbFllYXIoZGF0ZS5nZXRVVENGdWxsWWVhcigpICsgc3RlcCk7CiAgICB9LCBmdW5jdGlvbihzdGFydCwgZW5kKSB7CiAgICAgIHJldHVybiBlbmQuZ2V0VVRDRnVsbFllYXIoKSAtIHN0YXJ0LmdldFVUQ0Z1bGxZZWFyKCk7CiAgICB9LCBmdW5jdGlvbihkYXRlKSB7CiAgICAgIHJldHVybiBkYXRlLmdldFVUQ0Z1bGxZZWFyKCk7CiAgICB9KTsKCiAgICAvLyBBbiBvcHRpbWl6ZWQgaW1wbGVtZW50YXRpb24gZm9yIHRoaXMgc2ltcGxlIGNhc2UuCiAgICB1dGNZZWFyJDMuZXZlcnkgPSBmdW5jdGlvbihrKSB7CiAgICAgIHJldHVybiAhaXNGaW5pdGUoayA9IE1hdGguZmxvb3IoaykpIHx8ICEoayA+IDApID8gbnVsbCA6IG5ld0ludGVydmFsJDMoZnVuY3Rpb24oZGF0ZSkgewogICAgICAgIGRhdGUuc2V0VVRDRnVsbFllYXIoTWF0aC5mbG9vcihkYXRlLmdldFVUQ0Z1bGxZZWFyKCkgLyBrKSAqIGspOwogICAgICAgIGRhdGUuc2V0VVRDTW9udGgoMCwgMSk7CiAgICAgICAgZGF0ZS5zZXRVVENIb3VycygwLCAwLCAwLCAwKTsKICAgICAgfSwgZnVuY3Rpb24oZGF0ZSwgc3RlcCkgewogICAgICAgIGRhdGUuc2V0VVRDRnVsbFllYXIoZGF0ZS5nZXRVVENGdWxsWWVhcigpICsgc3RlcCAqIGspOwogICAgICB9KTsKICAgIH07CgogICAgZnVuY3Rpb24gbG9jYWxEYXRlJDIoZCkgewogICAgICBpZiAoMCA8PSBkLnkgJiYgZC55IDwgMTAwKSB7CiAgICAgICAgdmFyIGRhdGUgPSBuZXcgRGF0ZSgtMSwgZC5tLCBkLmQsIGQuSCwgZC5NLCBkLlMsIGQuTCk7CiAgICAgICAgZGF0ZS5zZXRGdWxsWWVhcihkLnkpOwogICAgICAgIHJldHVybiBkYXRlOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgRGF0ZShkLnksIGQubSwgZC5kLCBkLkgsIGQuTSwgZC5TLCBkLkwpOwogICAgfQoKICAgIGZ1bmN0aW9uIHV0Y0RhdGUkMihkKSB7CiAgICAgIGlmICgwIDw9IGQueSAmJiBkLnkgPCAxMDApIHsKICAgICAgICB2YXIgZGF0ZSA9IG5ldyBEYXRlKERhdGUuVVRDKC0xLCBkLm0sIGQuZCwgZC5ILCBkLk0sIGQuUywgZC5MKSk7CiAgICAgICAgZGF0ZS5zZXRVVENGdWxsWWVhcihkLnkpOwogICAgICAgIHJldHVybiBkYXRlOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgRGF0ZShEYXRlLlVUQyhkLnksIGQubSwgZC5kLCBkLkgsIGQuTSwgZC5TLCBkLkwpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBuZXdZZWFyKHkpIHsKICAgICAgcmV0dXJuIHt5OiB5LCBtOiAwLCBkOiAxLCBIOiAwLCBNOiAwLCBTOiAwLCBMOiAwfTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRMb2NhbGUkNShsb2NhbGUpIHsKICAgICAgdmFyIGxvY2FsZV9kYXRlVGltZSA9IGxvY2FsZS5kYXRlVGltZSwKICAgICAgICAgIGxvY2FsZV9kYXRlID0gbG9jYWxlLmRhdGUsCiAgICAgICAgICBsb2NhbGVfdGltZSA9IGxvY2FsZS50aW1lLAogICAgICAgICAgbG9jYWxlX3BlcmlvZHMgPSBsb2NhbGUucGVyaW9kcywKICAgICAgICAgIGxvY2FsZV93ZWVrZGF5cyA9IGxvY2FsZS5kYXlzLAogICAgICAgICAgbG9jYWxlX3Nob3J0V2Vla2RheXMgPSBsb2NhbGUuc2hvcnREYXlzLAogICAgICAgICAgbG9jYWxlX21vbnRocyA9IGxvY2FsZS5tb250aHMsCiAgICAgICAgICBsb2NhbGVfc2hvcnRNb250aHMgPSBsb2NhbGUuc2hvcnRNb250aHM7CgogICAgICB2YXIgcGVyaW9kUmUgPSBmb3JtYXRSZSQyKGxvY2FsZV9wZXJpb2RzKSwKICAgICAgICAgIHBlcmlvZExvb2t1cCA9IGZvcm1hdExvb2t1cCQyKGxvY2FsZV9wZXJpb2RzKSwKICAgICAgICAgIHdlZWtkYXlSZSA9IGZvcm1hdFJlJDIobG9jYWxlX3dlZWtkYXlzKSwKICAgICAgICAgIHdlZWtkYXlMb29rdXAgPSBmb3JtYXRMb29rdXAkMihsb2NhbGVfd2Vla2RheXMpLAogICAgICAgICAgc2hvcnRXZWVrZGF5UmUgPSBmb3JtYXRSZSQyKGxvY2FsZV9zaG9ydFdlZWtkYXlzKSwKICAgICAgICAgIHNob3J0V2Vla2RheUxvb2t1cCA9IGZvcm1hdExvb2t1cCQyKGxvY2FsZV9zaG9ydFdlZWtkYXlzKSwKICAgICAgICAgIG1vbnRoUmUgPSBmb3JtYXRSZSQyKGxvY2FsZV9tb250aHMpLAogICAgICAgICAgbW9udGhMb29rdXAgPSBmb3JtYXRMb29rdXAkMihsb2NhbGVfbW9udGhzKSwKICAgICAgICAgIHNob3J0TW9udGhSZSA9IGZvcm1hdFJlJDIobG9jYWxlX3Nob3J0TW9udGhzKSwKICAgICAgICAgIHNob3J0TW9udGhMb29rdXAgPSBmb3JtYXRMb29rdXAkMihsb2NhbGVfc2hvcnRNb250aHMpOwoKICAgICAgdmFyIGZvcm1hdHMgPSB7CiAgICAgICAgImEiOiBmb3JtYXRTaG9ydFdlZWtkYXksCiAgICAgICAgIkEiOiBmb3JtYXRXZWVrZGF5LAogICAgICAgICJiIjogZm9ybWF0U2hvcnRNb250aCwKICAgICAgICAiQiI6IGZvcm1hdE1vbnRoLAogICAgICAgICJjIjogbnVsbCwKICAgICAgICAiZCI6IGZvcm1hdERheU9mTW9udGgkMiwKICAgICAgICAiZSI6IGZvcm1hdERheU9mTW9udGgkMiwKICAgICAgICAiZiI6IGZvcm1hdE1pY3Jvc2Vjb25kcyQyLAogICAgICAgICJIIjogZm9ybWF0SG91cjI0JDIsCiAgICAgICAgIkkiOiBmb3JtYXRIb3VyMTIkMiwKICAgICAgICAiaiI6IGZvcm1hdERheU9mWWVhciQyLAogICAgICAgICJMIjogZm9ybWF0TWlsbGlzZWNvbmRzJDIsCiAgICAgICAgIm0iOiBmb3JtYXRNb250aE51bWJlciQyLAogICAgICAgICJNIjogZm9ybWF0TWludXRlcyQyLAogICAgICAgICJwIjogZm9ybWF0UGVyaW9kLAogICAgICAgICJRIjogZm9ybWF0VW5peFRpbWVzdGFtcCQyLAogICAgICAgICJzIjogZm9ybWF0VW5peFRpbWVzdGFtcFNlY29uZHMkMiwKICAgICAgICAiUyI6IGZvcm1hdFNlY29uZHMkMiwKICAgICAgICAidSI6IGZvcm1hdFdlZWtkYXlOdW1iZXJNb25kYXkkMiwKICAgICAgICAiVSI6IGZvcm1hdFdlZWtOdW1iZXJTdW5kYXkkMiwKICAgICAgICAiViI6IGZvcm1hdFdlZWtOdW1iZXJJU08kMiwKICAgICAgICAidyI6IGZvcm1hdFdlZWtkYXlOdW1iZXJTdW5kYXkkMiwKICAgICAgICAiVyI6IGZvcm1hdFdlZWtOdW1iZXJNb25kYXkkMiwKICAgICAgICAieCI6IG51bGwsCiAgICAgICAgIlgiOiBudWxsLAogICAgICAgICJ5IjogZm9ybWF0WWVhciQzLAogICAgICAgICJZIjogZm9ybWF0RnVsbFllYXIkMiwKICAgICAgICAiWiI6IGZvcm1hdFpvbmUkMiwKICAgICAgICAiJSI6IGZvcm1hdExpdGVyYWxQZXJjZW50JDIKICAgICAgfTsKCiAgICAgIHZhciB1dGNGb3JtYXRzID0gewogICAgICAgICJhIjogZm9ybWF0VVRDU2hvcnRXZWVrZGF5LAogICAgICAgICJBIjogZm9ybWF0VVRDV2Vla2RheSwKICAgICAgICAiYiI6IGZvcm1hdFVUQ1Nob3J0TW9udGgsCiAgICAgICAgIkIiOiBmb3JtYXRVVENNb250aCwKICAgICAgICAiYyI6IG51bGwsCiAgICAgICAgImQiOiBmb3JtYXRVVENEYXlPZk1vbnRoJDIsCiAgICAgICAgImUiOiBmb3JtYXRVVENEYXlPZk1vbnRoJDIsCiAgICAgICAgImYiOiBmb3JtYXRVVENNaWNyb3NlY29uZHMkMiwKICAgICAgICAiSCI6IGZvcm1hdFVUQ0hvdXIyNCQyLAogICAgICAgICJJIjogZm9ybWF0VVRDSG91cjEyJDIsCiAgICAgICAgImoiOiBmb3JtYXRVVENEYXlPZlllYXIkMiwKICAgICAgICAiTCI6IGZvcm1hdFVUQ01pbGxpc2Vjb25kcyQyLAogICAgICAgICJtIjogZm9ybWF0VVRDTW9udGhOdW1iZXIkMiwKICAgICAgICAiTSI6IGZvcm1hdFVUQ01pbnV0ZXMkMiwKICAgICAgICAicCI6IGZvcm1hdFVUQ1BlcmlvZCwKICAgICAgICAiUSI6IGZvcm1hdFVuaXhUaW1lc3RhbXAkMiwKICAgICAgICAicyI6IGZvcm1hdFVuaXhUaW1lc3RhbXBTZWNvbmRzJDIsCiAgICAgICAgIlMiOiBmb3JtYXRVVENTZWNvbmRzJDIsCiAgICAgICAgInUiOiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyTW9uZGF5JDIsCiAgICAgICAgIlUiOiBmb3JtYXRVVENXZWVrTnVtYmVyU3VuZGF5JDIsCiAgICAgICAgIlYiOiBmb3JtYXRVVENXZWVrTnVtYmVySVNPJDIsCiAgICAgICAgInciOiBmb3JtYXRVVENXZWVrZGF5TnVtYmVyU3VuZGF5JDIsCiAgICAgICAgIlciOiBmb3JtYXRVVENXZWVrTnVtYmVyTW9uZGF5JDIsCiAgICAgICAgIngiOiBudWxsLAogICAgICAgICJYIjogbnVsbCwKICAgICAgICAieSI6IGZvcm1hdFVUQ1llYXIkMiwKICAgICAgICAiWSI6IGZvcm1hdFVUQ0Z1bGxZZWFyJDIsCiAgICAgICAgIloiOiBmb3JtYXRVVENab25lJDIsCiAgICAgICAgIiUiOiBmb3JtYXRMaXRlcmFsUGVyY2VudCQyCiAgICAgIH07CgogICAgICB2YXIgcGFyc2VzID0gewogICAgICAgICJhIjogcGFyc2VTaG9ydFdlZWtkYXksCiAgICAgICAgIkEiOiBwYXJzZVdlZWtkYXksCiAgICAgICAgImIiOiBwYXJzZVNob3J0TW9udGgsCiAgICAgICAgIkIiOiBwYXJzZU1vbnRoLAogICAgICAgICJjIjogcGFyc2VMb2NhbGVEYXRlVGltZSwKICAgICAgICAiZCI6IHBhcnNlRGF5T2ZNb250aCQyLAogICAgICAgICJlIjogcGFyc2VEYXlPZk1vbnRoJDIsCiAgICAgICAgImYiOiBwYXJzZU1pY3Jvc2Vjb25kcyQyLAogICAgICAgICJIIjogcGFyc2VIb3VyMjQkMiwKICAgICAgICAiSSI6IHBhcnNlSG91cjI0JDIsCiAgICAgICAgImoiOiBwYXJzZURheU9mWWVhciQyLAogICAgICAgICJMIjogcGFyc2VNaWxsaXNlY29uZHMkMiwKICAgICAgICAibSI6IHBhcnNlTW9udGhOdW1iZXIkMiwKICAgICAgICAiTSI6IHBhcnNlTWludXRlcyQyLAogICAgICAgICJwIjogcGFyc2VQZXJpb2QsCiAgICAgICAgIlEiOiBwYXJzZVVuaXhUaW1lc3RhbXAkMiwKICAgICAgICAicyI6IHBhcnNlVW5peFRpbWVzdGFtcFNlY29uZHMkMiwKICAgICAgICAiUyI6IHBhcnNlU2Vjb25kcyQyLAogICAgICAgICJ1IjogcGFyc2VXZWVrZGF5TnVtYmVyTW9uZGF5JDIsCiAgICAgICAgIlUiOiBwYXJzZVdlZWtOdW1iZXJTdW5kYXkkMiwKICAgICAgICAiViI6IHBhcnNlV2Vla051bWJlcklTTyQyLAogICAgICAgICJ3IjogcGFyc2VXZWVrZGF5TnVtYmVyU3VuZGF5JDIsCiAgICAgICAgIlciOiBwYXJzZVdlZWtOdW1iZXJNb25kYXkkMiwKICAgICAgICAieCI6IHBhcnNlTG9jYWxlRGF0ZSwKICAgICAgICAiWCI6IHBhcnNlTG9jYWxlVGltZSwKICAgICAgICAieSI6IHBhcnNlWWVhciQyLAogICAgICAgICJZIjogcGFyc2VGdWxsWWVhciQyLAogICAgICAgICJaIjogcGFyc2Vab25lJDIsCiAgICAgICAgIiUiOiBwYXJzZUxpdGVyYWxQZXJjZW50JDIKICAgICAgfTsKCiAgICAgIC8vIFRoZXNlIHJlY3Vyc2l2ZSBkaXJlY3RpdmUgZGVmaW5pdGlvbnMgbXVzdCBiZSBkZWZlcnJlZC4KICAgICAgZm9ybWF0cy54ID0gbmV3Rm9ybWF0KGxvY2FsZV9kYXRlLCBmb3JtYXRzKTsKICAgICAgZm9ybWF0cy5YID0gbmV3Rm9ybWF0KGxvY2FsZV90aW1lLCBmb3JtYXRzKTsKICAgICAgZm9ybWF0cy5jID0gbmV3Rm9ybWF0KGxvY2FsZV9kYXRlVGltZSwgZm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMueCA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZSwgdXRjRm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMuWCA9IG5ld0Zvcm1hdChsb2NhbGVfdGltZSwgdXRjRm9ybWF0cyk7CiAgICAgIHV0Y0Zvcm1hdHMuYyA9IG5ld0Zvcm1hdChsb2NhbGVfZGF0ZVRpbWUsIHV0Y0Zvcm1hdHMpOwoKICAgICAgZnVuY3Rpb24gbmV3Rm9ybWF0KHNwZWNpZmllciwgZm9ybWF0cykgewogICAgICAgIHJldHVybiBmdW5jdGlvbihkYXRlKSB7CiAgICAgICAgICB2YXIgc3RyaW5nID0gW10sCiAgICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICAgIGogPSAwLAogICAgICAgICAgICAgIG4gPSBzcGVjaWZpZXIubGVuZ3RoLAogICAgICAgICAgICAgIGMsCiAgICAgICAgICAgICAgcGFkLAogICAgICAgICAgICAgIGZvcm1hdDsKCiAgICAgICAgICBpZiAoIShkYXRlIGluc3RhbmNlb2YgRGF0ZSkpIGRhdGUgPSBuZXcgRGF0ZSgrZGF0ZSk7CgogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgICAgaWYgKHNwZWNpZmllci5jaGFyQ29kZUF0KGkpID09PSAzNykgewogICAgICAgICAgICAgIHN0cmluZy5wdXNoKHNwZWNpZmllci5zbGljZShqLCBpKSk7CiAgICAgICAgICAgICAgaWYgKChwYWQgPSBwYWRzJDJbYyA9IHNwZWNpZmllci5jaGFyQXQoKytpKV0pICE9IG51bGwpIGMgPSBzcGVjaWZpZXIuY2hhckF0KCsraSk7CiAgICAgICAgICAgICAgZWxzZSBwYWQgPSBjID09PSAiZSIgPyAiICIgOiAiMCI7CiAgICAgICAgICAgICAgaWYgKGZvcm1hdCA9IGZvcm1hdHNbY10pIGMgPSBmb3JtYXQoZGF0ZSwgcGFkKTsKICAgICAgICAgICAgICBzdHJpbmcucHVzaChjKTsKICAgICAgICAgICAgICBqID0gaSArIDE7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KCiAgICAgICAgICBzdHJpbmcucHVzaChzcGVjaWZpZXIuc2xpY2UoaiwgaSkpOwogICAgICAgICAgcmV0dXJuIHN0cmluZy5qb2luKCIiKTsKICAgICAgICB9OwogICAgICB9CgogICAgICBmdW5jdGlvbiBuZXdQYXJzZShzcGVjaWZpZXIsIG5ld0RhdGUpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oc3RyaW5nKSB7CiAgICAgICAgICB2YXIgZCA9IG5ld1llYXIoMTkwMCksCiAgICAgICAgICAgICAgaSA9IHBhcnNlU3BlY2lmaWVyKGQsIHNwZWNpZmllciwgc3RyaW5nICs9ICIiLCAwKSwKICAgICAgICAgICAgICB3ZWVrLCBkYXk7CiAgICAgICAgICBpZiAoaSAhPSBzdHJpbmcubGVuZ3RoKSByZXR1cm4gbnVsbDsKCiAgICAgICAgICAvLyBJZiBhIFVOSVggdGltZXN0YW1wIGlzIHNwZWNpZmllZCwgcmV0dXJuIGl0LgogICAgICAgICAgaWYgKCJRIiBpbiBkKSByZXR1cm4gbmV3IERhdGUoZC5RKTsKCiAgICAgICAgICAvLyBUaGUgYW0tcG0gZmxhZyBpcyAwIGZvciBBTSwgYW5kIDEgZm9yIFBNLgogICAgICAgICAgaWYgKCJwIiBpbiBkKSBkLkggPSBkLkggJSAxMiArIGQucCAqIDEyOwoKICAgICAgICAgIC8vIENvbnZlcnQgZGF5LW9mLXdlZWsgYW5kIHdlZWstb2YteWVhciB0byBkYXktb2YteWVhci4KICAgICAgICAgIGlmICgiViIgaW4gZCkgewogICAgICAgICAgICBpZiAoZC5WIDwgMSB8fCBkLlYgPiA1MykgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIGlmICghKCJ3IiBpbiBkKSkgZC53ID0gMTsKICAgICAgICAgICAgaWYgKCJaIiBpbiBkKSB7CiAgICAgICAgICAgICAgd2VlayA9IHV0Y0RhdGUkMihuZXdZZWFyKGQueSkpLCBkYXkgPSB3ZWVrLmdldFVUQ0RheSgpOwogICAgICAgICAgICAgIHdlZWsgPSBkYXkgPiA0IHx8IGRheSA9PT0gMCA/IHV0Y01vbmRheSQzLmNlaWwod2VlaykgOiB1dGNNb25kYXkkMyh3ZWVrKTsKICAgICAgICAgICAgICB3ZWVrID0gdXRjRGF5JDMub2Zmc2V0KHdlZWssIChkLlYgLSAxKSAqIDcpOwogICAgICAgICAgICAgIGQueSA9IHdlZWsuZ2V0VVRDRnVsbFllYXIoKTsKICAgICAgICAgICAgICBkLm0gPSB3ZWVrLmdldFVUQ01vbnRoKCk7CiAgICAgICAgICAgICAgZC5kID0gd2Vlay5nZXRVVENEYXRlKCkgKyAoZC53ICsgNikgJSA3OwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIHdlZWsgPSBuZXdEYXRlKG5ld1llYXIoZC55KSksIGRheSA9IHdlZWsuZ2V0RGF5KCk7CiAgICAgICAgICAgICAgd2VlayA9IGRheSA+IDQgfHwgZGF5ID09PSAwID8gbW9uZGF5JDMuY2VpbCh3ZWVrKSA6IG1vbmRheSQzKHdlZWspOwogICAgICAgICAgICAgIHdlZWsgPSBkYXkkMy5vZmZzZXQod2VlaywgKGQuViAtIDEpICogNyk7CiAgICAgICAgICAgICAgZC55ID0gd2Vlay5nZXRGdWxsWWVhcigpOwogICAgICAgICAgICAgIGQubSA9IHdlZWsuZ2V0TW9udGgoKTsKICAgICAgICAgICAgICBkLmQgPSB3ZWVrLmdldERhdGUoKSArIChkLncgKyA2KSAlIDc7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAoIlciIGluIGQgfHwgIlUiIGluIGQpIHsKICAgICAgICAgICAgaWYgKCEoInciIGluIGQpKSBkLncgPSAidSIgaW4gZCA/IGQudSAlIDcgOiAiVyIgaW4gZCA/IDEgOiAwOwogICAgICAgICAgICBkYXkgPSAiWiIgaW4gZCA/IHV0Y0RhdGUkMihuZXdZZWFyKGQueSkpLmdldFVUQ0RheSgpIDogbmV3RGF0ZShuZXdZZWFyKGQueSkpLmdldERheSgpOwogICAgICAgICAgICBkLm0gPSAwOwogICAgICAgICAgICBkLmQgPSAiVyIgaW4gZCA/IChkLncgKyA2KSAlIDcgKyBkLlcgKiA3IC0gKGRheSArIDUpICUgNyA6IGQudyArIGQuVSAqIDcgLSAoZGF5ICsgNikgJSA3OwogICAgICAgICAgfQoKICAgICAgICAgIC8vIElmIGEgdGltZSB6b25lIGlzIHNwZWNpZmllZCwgYWxsIGZpZWxkcyBhcmUgaW50ZXJwcmV0ZWQgYXMgVVRDIGFuZCB0aGVuCiAgICAgICAgICAvLyBvZmZzZXQgYWNjb3JkaW5nIHRvIHRoZSBzcGVjaWZpZWQgdGltZSB6b25lLgogICAgICAgICAgaWYgKCJaIiBpbiBkKSB7CiAgICAgICAgICAgIGQuSCArPSBkLlogLyAxMDAgfCAwOwogICAgICAgICAgICBkLk0gKz0gZC5aICUgMTAwOwogICAgICAgICAgICByZXR1cm4gdXRjRGF0ZSQyKGQpOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIE90aGVyd2lzZSwgYWxsIGZpZWxkcyBhcmUgaW4gbG9jYWwgdGltZS4KICAgICAgICAgIHJldHVybiBuZXdEYXRlKGQpOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlU3BlY2lmaWVyKGQsIHNwZWNpZmllciwgc3RyaW5nLCBqKSB7CiAgICAgICAgdmFyIGkgPSAwLAogICAgICAgICAgICBuID0gc3BlY2lmaWVyLmxlbmd0aCwKICAgICAgICAgICAgbSA9IHN0cmluZy5sZW5ndGgsCiAgICAgICAgICAgIGMsCiAgICAgICAgICAgIHBhcnNlOwoKICAgICAgICB3aGlsZSAoaSA8IG4pIHsKICAgICAgICAgIGlmIChqID49IG0pIHJldHVybiAtMTsKICAgICAgICAgIGMgPSBzcGVjaWZpZXIuY2hhckNvZGVBdChpKyspOwogICAgICAgICAgaWYgKGMgPT09IDM3KSB7CiAgICAgICAgICAgIGMgPSBzcGVjaWZpZXIuY2hhckF0KGkrKyk7CiAgICAgICAgICAgIHBhcnNlID0gcGFyc2VzW2MgaW4gcGFkcyQyID8gc3BlY2lmaWVyLmNoYXJBdChpKyspIDogY107CiAgICAgICAgICAgIGlmICghcGFyc2UgfHwgKChqID0gcGFyc2UoZCwgc3RyaW5nLCBqKSkgPCAwKSkgcmV0dXJuIC0xOwogICAgICAgICAgfSBlbHNlIGlmIChjICE9IHN0cmluZy5jaGFyQ29kZUF0KGorKykpIHsKICAgICAgICAgICAgcmV0dXJuIC0xOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIGo7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlUGVyaW9kKGQsIHN0cmluZywgaSkgewogICAgICAgIHZhciBuID0gcGVyaW9kUmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICAgIHJldHVybiBuID8gKGQucCA9IHBlcmlvZExvb2t1cFtuWzBdLnRvTG93ZXJDYXNlKCldLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlU2hvcnRXZWVrZGF5KGQsIHN0cmluZywgaSkgewogICAgICAgIHZhciBuID0gc2hvcnRXZWVrZGF5UmUuZXhlYyhzdHJpbmcuc2xpY2UoaSkpOwogICAgICAgIHJldHVybiBuID8gKGQudyA9IHNob3J0V2Vla2RheUxvb2t1cFtuWzBdLnRvTG93ZXJDYXNlKCldLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlV2Vla2RheShkLCBzdHJpbmcsIGkpIHsKICAgICAgICB2YXIgbiA9IHdlZWtkYXlSZS5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgICAgcmV0dXJuIG4gPyAoZC53ID0gd2Vla2RheUxvb2t1cFtuWzBdLnRvTG93ZXJDYXNlKCldLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlU2hvcnRNb250aChkLCBzdHJpbmcsIGkpIHsKICAgICAgICB2YXIgbiA9IHNob3J0TW9udGhSZS5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgICAgcmV0dXJuIG4gPyAoZC5tID0gc2hvcnRNb250aExvb2t1cFtuWzBdLnRvTG93ZXJDYXNlKCldLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlTW9udGgoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgdmFyIG4gPSBtb250aFJlLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgICByZXR1cm4gbiA/IChkLm0gPSBtb250aExvb2t1cFtuWzBdLnRvTG93ZXJDYXNlKCldLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHBhcnNlTG9jYWxlRGF0ZVRpbWUoZCwgc3RyaW5nLCBpKSB7CiAgICAgICAgcmV0dXJuIHBhcnNlU3BlY2lmaWVyKGQsIGxvY2FsZV9kYXRlVGltZSwgc3RyaW5nLCBpKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VMb2NhbGVEYXRlKGQsIHN0cmluZywgaSkgewogICAgICAgIHJldHVybiBwYXJzZVNwZWNpZmllcihkLCBsb2NhbGVfZGF0ZSwgc3RyaW5nLCBpKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gcGFyc2VMb2NhbGVUaW1lKGQsIHN0cmluZywgaSkgewogICAgICAgIHJldHVybiBwYXJzZVNwZWNpZmllcihkLCBsb2NhbGVfdGltZSwgc3RyaW5nLCBpKTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0U2hvcnRXZWVrZGF5KGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3Nob3J0V2Vla2RheXNbZC5nZXREYXkoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtkYXkoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfd2Vla2RheXNbZC5nZXREYXkoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFNob3J0TW9udGgoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfc2hvcnRNb250aHNbZC5nZXRNb250aCgpXTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gZm9ybWF0TW9udGgoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfbW9udGhzW2QuZ2V0TW9udGgoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFBlcmlvZChkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9wZXJpb2RzWysoZC5nZXRIb3VycygpID49IDEyKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1Nob3J0V2Vla2RheShkKSB7CiAgICAgICAgcmV0dXJuIGxvY2FsZV9zaG9ydFdlZWtkYXlzW2QuZ2V0VVRDRGF5KCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrZGF5KGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3dlZWtkYXlzW2QuZ2V0VVRDRGF5KCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRVVENTaG9ydE1vbnRoKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX3Nob3J0TW9udGhzW2QuZ2V0VVRDTW9udGgoKV07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ01vbnRoKGQpIHsKICAgICAgICByZXR1cm4gbG9jYWxlX21vbnRoc1tkLmdldFVUQ01vbnRoKCldOwogICAgICB9CgogICAgICBmdW5jdGlvbiBmb3JtYXRVVENQZXJpb2QoZCkgewogICAgICAgIHJldHVybiBsb2NhbGVfcGVyaW9kc1srKGQuZ2V0VVRDSG91cnMoKSA+PSAxMildOwogICAgICB9CgogICAgICByZXR1cm4gewogICAgICAgIGZvcm1hdDogZnVuY3Rpb24oc3BlY2lmaWVyKSB7CiAgICAgICAgICB2YXIgZiA9IG5ld0Zvcm1hdChzcGVjaWZpZXIgKz0gIiIsIGZvcm1hdHMpOwogICAgICAgICAgZi50b1N0cmluZyA9IGZ1bmN0aW9uKCkgeyByZXR1cm4gc3BlY2lmaWVyOyB9OwogICAgICAgICAgcmV0dXJuIGY7CiAgICAgICAgfSwKICAgICAgICBwYXJzZTogZnVuY3Rpb24oc3BlY2lmaWVyKSB7CiAgICAgICAgICB2YXIgcCA9IG5ld1BhcnNlKHNwZWNpZmllciArPSAiIiwgbG9jYWxEYXRlJDIpOwogICAgICAgICAgcC50b1N0cmluZyA9IGZ1bmN0aW9uKCkgeyByZXR1cm4gc3BlY2lmaWVyOyB9OwogICAgICAgICAgcmV0dXJuIHA7CiAgICAgICAgfSwKICAgICAgICB1dGNGb3JtYXQ6IGZ1bmN0aW9uKHNwZWNpZmllcikgewogICAgICAgICAgdmFyIGYgPSBuZXdGb3JtYXQoc3BlY2lmaWVyICs9ICIiLCB1dGNGb3JtYXRzKTsKICAgICAgICAgIGYudG9TdHJpbmcgPSBmdW5jdGlvbigpIHsgcmV0dXJuIHNwZWNpZmllcjsgfTsKICAgICAgICAgIHJldHVybiBmOwogICAgICAgIH0sCiAgICAgICAgdXRjUGFyc2U6IGZ1bmN0aW9uKHNwZWNpZmllcikgewogICAgICAgICAgdmFyIHAgPSBuZXdQYXJzZShzcGVjaWZpZXIsIHV0Y0RhdGUkMik7CiAgICAgICAgICBwLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7IHJldHVybiBzcGVjaWZpZXI7IH07CiAgICAgICAgICByZXR1cm4gcDsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgdmFyIHBhZHMkMiA9IHsiLSI6ICIiLCAiXyI6ICIgIiwgIjAiOiAiMCJ9LAogICAgICAgIG51bWJlclJlJDIgPSAvXlxzKlxkKy8sIC8vIG5vdGU6IGlnbm9yZXMgbmV4dCBkaXJlY3RpdmUKICAgICAgICBwZXJjZW50UmUkMiA9IC9eJS8sCiAgICAgICAgcmVxdW90ZVJlJDIgPSAvW1xcXiQqKz98W1xdKCkue31dL2c7CgogICAgZnVuY3Rpb24gcGFkJDModmFsdWUsIGZpbGwsIHdpZHRoKSB7CiAgICAgIHZhciBzaWduID0gdmFsdWUgPCAwID8gIi0iIDogIiIsCiAgICAgICAgICBzdHJpbmcgPSAoc2lnbiA/IC12YWx1ZSA6IHZhbHVlKSArICIiLAogICAgICAgICAgbGVuZ3RoID0gc3RyaW5nLmxlbmd0aDsKICAgICAgcmV0dXJuIHNpZ24gKyAobGVuZ3RoIDwgd2lkdGggPyBuZXcgQXJyYXkod2lkdGggLSBsZW5ndGggKyAxKS5qb2luKGZpbGwpICsgc3RyaW5nIDogc3RyaW5nKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXF1b3RlJDIocykgewogICAgICByZXR1cm4gcy5yZXBsYWNlKHJlcXVvdGVSZSQyLCAiXFwkJiIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFJlJDIobmFtZXMpIHsKICAgICAgcmV0dXJuIG5ldyBSZWdFeHAoIl4oPzoiICsgbmFtZXMubWFwKHJlcXVvdGUkMikuam9pbigifCIpICsgIikiLCAiaSIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdExvb2t1cCQyKG5hbWVzKSB7CiAgICAgIHZhciBtYXAgPSB7fSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbWFwW25hbWVzW2ldLnRvTG93ZXJDYXNlKCldID0gaTsKICAgICAgcmV0dXJuIG1hcDsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVdlZWtkYXlOdW1iZXJTdW5kYXkkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAxKSk7CiAgICAgIHJldHVybiBuID8gKGQudyA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VXZWVrZGF5TnVtYmVyTW9uZGF5JDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMi5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMSkpOwogICAgICByZXR1cm4gbiA/IChkLnUgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlV2Vla051bWJlclN1bmRheSQyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5VID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVdlZWtOdW1iZXJJU08kMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAyKSk7CiAgICAgIHJldHVybiBuID8gKGQuViA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VXZWVrTnVtYmVyTW9uZGF5JDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMi5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLlcgPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlRnVsbFllYXIkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyA0KSk7CiAgICAgIHJldHVybiBuID8gKGQueSA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VZZWFyJDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMi5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLnkgPSArblswXSArICgrblswXSA+IDY4ID8gMTkwMCA6IDIwMDApLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2Vab25lJDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gL14oWil8KFsrLV1cZFxkKSg/Ojo/KFxkXGQpKT8vLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyA2KSk7CiAgICAgIHJldHVybiBuID8gKGQuWiA9IG5bMV0gPyAwIDogLShuWzJdICsgKG5bM10gfHwgIjAwIikpLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VNb250aE51bWJlciQyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5tID0gblswXSAtIDEsIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZURheU9mTW9udGgkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAyKSk7CiAgICAgIHJldHVybiBuID8gKGQuZCA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VEYXlPZlllYXIkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAzKSk7CiAgICAgIHJldHVybiBuID8gKGQubSA9IDAsIGQuZCA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VIb3VyMjQkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGksIGkgKyAyKSk7CiAgICAgIHJldHVybiBuID8gKGQuSCA9ICtuWzBdLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VNaW51dGVzJDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMi5leGVjKHN0cmluZy5zbGljZShpLCBpICsgMikpOwogICAgICByZXR1cm4gbiA/IChkLk0gPSArblswXSwgaSArIG5bMF0ubGVuZ3RoKSA6IC0xOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlU2Vjb25kcyQyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDIpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5TID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1pbGxpc2Vjb25kcyQyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDMpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5MID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZU1pY3Jvc2Vjb25kcyQyKGQsIHN0cmluZywgaSkgewogICAgICB2YXIgbiA9IG51bWJlclJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDYpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5MID0gTWF0aC5mbG9vcihuWzBdIC8gMTAwMCksIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZUxpdGVyYWxQZXJjZW50JDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gcGVyY2VudFJlJDIuZXhlYyhzdHJpbmcuc2xpY2UoaSwgaSArIDEpKTsKICAgICAgcmV0dXJuIG4gPyBpICsgblswXS5sZW5ndGggOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVVuaXhUaW1lc3RhbXAkMihkLCBzdHJpbmcsIGkpIHsKICAgICAgdmFyIG4gPSBudW1iZXJSZSQyLmV4ZWMoc3RyaW5nLnNsaWNlKGkpKTsKICAgICAgcmV0dXJuIG4gPyAoZC5RID0gK25bMF0sIGkgKyBuWzBdLmxlbmd0aCkgOiAtMTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVVuaXhUaW1lc3RhbXBTZWNvbmRzJDIoZCwgc3RyaW5nLCBpKSB7CiAgICAgIHZhciBuID0gbnVtYmVyUmUkMi5leGVjKHN0cmluZy5zbGljZShpKSk7CiAgICAgIHJldHVybiBuID8gKGQuUSA9ICgrblswXSkgKiAxMDAwLCBpICsgblswXS5sZW5ndGgpIDogLTE7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0RGF5T2ZNb250aCQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0RGF0ZSgpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRIb3VyMjQkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMyhkLmdldEhvdXJzKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdEhvdXIxMiQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0SG91cnMoKSAlIDEyIHx8IDEyLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXREYXlPZlllYXIkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMygxICsgZGF5JDMuY291bnQoeWVhciQzKGQpLCBkKSwgcCwgMyk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TWlsbGlzZWNvbmRzJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRNaWxsaXNlY29uZHMoKSwgcCwgMyk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TWljcm9zZWNvbmRzJDIoZCwgcCkgewogICAgICByZXR1cm4gZm9ybWF0TWlsbGlzZWNvbmRzJDIoZCwgcCkgKyAiMDAwIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRNb250aE51bWJlciQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0TW9udGgoKSArIDEsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdE1pbnV0ZXMkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMyhkLmdldE1pbnV0ZXMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0U2Vjb25kcyQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0U2Vjb25kcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRXZWVrZGF5TnVtYmVyTW9uZGF5JDIoZCkgewogICAgICB2YXIgZGF5ID0gZC5nZXREYXkoKTsKICAgICAgcmV0dXJuIGRheSA9PT0gMCA/IDcgOiBkYXk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0V2Vla051bWJlclN1bmRheSQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKHN1bmRheSQzLmNvdW50KHllYXIkMyhkKSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtOdW1iZXJJU08kMihkLCBwKSB7CiAgICAgIHZhciBkYXkgPSBkLmdldERheSgpOwogICAgICBkID0gKGRheSA+PSA0IHx8IGRheSA9PT0gMCkgPyB0aHVyc2RheSQzKGQpIDogdGh1cnNkYXkkMy5jZWlsKGQpOwogICAgICByZXR1cm4gcGFkJDModGh1cnNkYXkkMy5jb3VudCh5ZWFyJDMoZCksIGQpICsgKHllYXIkMyhkKS5nZXREYXkoKSA9PT0gNCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtkYXlOdW1iZXJTdW5kYXkkMihkKSB7CiAgICAgIHJldHVybiBkLmdldERheSgpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFdlZWtOdW1iZXJNb25kYXkkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMyhtb25kYXkkMy5jb3VudCh5ZWFyJDMoZCksIGQpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRZZWFyJDMoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRGdWxsWWVhcigpICUgMTAwLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRGdWxsWWVhciQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0RnVsbFllYXIoKSAlIDEwMDAwLCBwLCA0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRab25lJDIoZCkgewogICAgICB2YXIgeiA9IGQuZ2V0VGltZXpvbmVPZmZzZXQoKTsKICAgICAgcmV0dXJuICh6ID4gMCA/ICItIiA6ICh6ICo9IC0xLCAiKyIpKQogICAgICAgICAgKyBwYWQkMyh6IC8gNjAgfCAwLCAiMCIsIDIpCiAgICAgICAgICArIHBhZCQzKHogJSA2MCwgIjAiLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENEYXlPZk1vbnRoJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRVVENEYXRlKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0hvdXIyNCQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0VVRDSG91cnMoKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDSG91cjEyJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRVVENIb3VycygpICUgMTIgfHwgMTIsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0RheU9mWWVhciQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKDEgKyB1dGNEYXkkMy5jb3VudCh1dGNZZWFyJDMoZCksIGQpLCBwLCAzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENNaWxsaXNlY29uZHMkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMyhkLmdldFVUQ01pbGxpc2Vjb25kcygpLCBwLCAzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENNaWNyb3NlY29uZHMkMihkLCBwKSB7CiAgICAgIHJldHVybiBmb3JtYXRVVENNaWxsaXNlY29uZHMkMihkLCBwKSArICIwMDAiOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ01vbnRoTnVtYmVyJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRVVENNb250aCgpICsgMSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDTWludXRlcyQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKGQuZ2V0VVRDTWludXRlcygpLCBwLCAyKTsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENTZWNvbmRzJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRVVENTZWNvbmRzKCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1dlZWtkYXlOdW1iZXJNb25kYXkkMihkKSB7CiAgICAgIHZhciBkb3cgPSBkLmdldFVUQ0RheSgpOwogICAgICByZXR1cm4gZG93ID09PSAwID8gNyA6IGRvdzsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVVENXZWVrTnVtYmVyU3VuZGF5JDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDModXRjU3VuZGF5JDMuY291bnQodXRjWWVhciQzKGQpLCBkKSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla051bWJlcklTTyQyKGQsIHApIHsKICAgICAgdmFyIGRheSA9IGQuZ2V0VVRDRGF5KCk7CiAgICAgIGQgPSAoZGF5ID49IDQgfHwgZGF5ID09PSAwKSA/IHV0Y1RodXJzZGF5JDMoZCkgOiB1dGNUaHVyc2RheSQzLmNlaWwoZCk7CiAgICAgIHJldHVybiBwYWQkMyh1dGNUaHVyc2RheSQzLmNvdW50KHV0Y1llYXIkMyhkKSwgZCkgKyAodXRjWWVhciQzKGQpLmdldFVUQ0RheSgpID09PSA0KSwgcCwgMik7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla2RheU51bWJlclN1bmRheSQyKGQpIHsKICAgICAgcmV0dXJuIGQuZ2V0VVRDRGF5KCk7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VVRDV2Vla051bWJlck1vbmRheSQyKGQsIHApIHsKICAgICAgcmV0dXJuIHBhZCQzKHV0Y01vbmRheSQzLmNvdW50KHV0Y1llYXIkMyhkKSwgZCksIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1llYXIkMihkLCBwKSB7CiAgICAgIHJldHVybiBwYWQkMyhkLmdldFVUQ0Z1bGxZZWFyKCkgJSAxMDAsIHAsIDIpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ0Z1bGxZZWFyJDIoZCwgcCkgewogICAgICByZXR1cm4gcGFkJDMoZC5nZXRVVENGdWxsWWVhcigpICUgMTAwMDAsIHAsIDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGZvcm1hdFVUQ1pvbmUkMigpIHsKICAgICAgcmV0dXJuICIrMDAwMCI7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0TGl0ZXJhbFBlcmNlbnQkMigpIHsKICAgICAgcmV0dXJuICIlIjsKICAgIH0KCiAgICBmdW5jdGlvbiBmb3JtYXRVbml4VGltZXN0YW1wJDIoZCkgewogICAgICByZXR1cm4gK2Q7CiAgICB9CgogICAgZnVuY3Rpb24gZm9ybWF0VW5peFRpbWVzdGFtcFNlY29uZHMkMihkKSB7CiAgICAgIHJldHVybiBNYXRoLmZsb29yKCtkIC8gMTAwMCk7CiAgICB9CgogICAgdmFyIGxvY2FsZSQ1OwogICAgdmFyIHRpbWVGb3JtYXQkMjsKICAgIHZhciB0aW1lUGFyc2UkMjsKICAgIHZhciB1dGNGb3JtYXQkMjsKICAgIHZhciB1dGNQYXJzZSQyOwoKICAgIGRlZmF1bHRMb2NhbGUkNSh7CiAgICAgIGRhdGVUaW1lOiAiJXgsICVYIiwKICAgICAgZGF0ZTogIiUtbS8lLWQvJVkiLAogICAgICB0aW1lOiAiJS1JOiVNOiVTICVwIiwKICAgICAgcGVyaW9kczogWyJBTSIsICJQTSJdLAogICAgICBkYXlzOiBbIlN1bmRheSIsICJNb25kYXkiLCAiVHVlc2RheSIsICJXZWRuZXNkYXkiLCAiVGh1cnNkYXkiLCAiRnJpZGF5IiwgIlNhdHVyZGF5Il0sCiAgICAgIHNob3J0RGF5czogWyJTdW4iLCAiTW9uIiwgIlR1ZSIsICJXZWQiLCAiVGh1IiwgIkZyaSIsICJTYXQiXSwKICAgICAgbW9udGhzOiBbIkphbnVhcnkiLCAiRmVicnVhcnkiLCAiTWFyY2giLCAiQXByaWwiLCAiTWF5IiwgIkp1bmUiLCAiSnVseSIsICJBdWd1c3QiLCAiU2VwdGVtYmVyIiwgIk9jdG9iZXIiLCAiTm92ZW1iZXIiLCAiRGVjZW1iZXIiXSwKICAgICAgc2hvcnRNb250aHM6IFsiSmFuIiwgIkZlYiIsICJNYXIiLCAiQXByIiwgIk1heSIsICJKdW4iLCAiSnVsIiwgIkF1ZyIsICJTZXAiLCAiT2N0IiwgIk5vdiIsICJEZWMiXQogICAgfSk7CgogICAgZnVuY3Rpb24gZGVmYXVsdExvY2FsZSQ1KGRlZmluaXRpb24pIHsKICAgICAgbG9jYWxlJDUgPSBmb3JtYXRMb2NhbGUkNShkZWZpbml0aW9uKTsKICAgICAgdGltZUZvcm1hdCQyID0gbG9jYWxlJDUuZm9ybWF0OwogICAgICB0aW1lUGFyc2UkMiA9IGxvY2FsZSQ1LnBhcnNlOwogICAgICB1dGNGb3JtYXQkMiA9IGxvY2FsZSQ1LnV0Y0Zvcm1hdDsKICAgICAgdXRjUGFyc2UkMiA9IGxvY2FsZSQ1LnV0Y1BhcnNlOwogICAgICByZXR1cm4gbG9jYWxlJDU7CiAgICB9CgogICAgdmFyIGlzb1NwZWNpZmllciQxID0gIiVZLSVtLSVkVCVIOiVNOiVTLiVMWiI7CgogICAgZnVuY3Rpb24gZm9ybWF0SXNvTmF0aXZlJDEoZGF0ZSkgewogICAgICByZXR1cm4gZGF0ZS50b0lTT1N0cmluZygpOwogICAgfQoKICAgIHZhciBmb3JtYXRJc28kMSA9IERhdGUucHJvdG90eXBlLnRvSVNPU3RyaW5nCiAgICAgICAgPyBmb3JtYXRJc29OYXRpdmUkMQogICAgICAgIDogdXRjRm9ybWF0JDIoaXNvU3BlY2lmaWVyJDEpOwoKICAgIGZ1bmN0aW9uIHBhcnNlSXNvTmF0aXZlJDEoc3RyaW5nKSB7CiAgICAgIHZhciBkYXRlID0gbmV3IERhdGUoc3RyaW5nKTsKICAgICAgcmV0dXJuIGlzTmFOKGRhdGUpID8gbnVsbCA6IGRhdGU7CiAgICB9CgogICAgdmFyIHBhcnNlSXNvJDEgPSArbmV3IERhdGUoIjIwMDAtMDEtMDFUMDA6MDA6MDAuMDAwWiIpCiAgICAgICAgPyBwYXJzZUlzb05hdGl2ZSQxCiAgICAgICAgOiB1dGNQYXJzZSQyKGlzb1NwZWNpZmllciQxKTsKCiAgICB2YXIgZnJhbWUkMyA9IDAsIC8vIGlzIGFuIGFuaW1hdGlvbiBmcmFtZSBwZW5kaW5nPwogICAgICAgIHRpbWVvdXQkNSA9IDAsIC8vIGlzIGEgdGltZW91dCBwZW5kaW5nPwogICAgICAgIGludGVydmFsJDQgPSAwLCAvLyBhcmUgYW55IHRpbWVycyBhY3RpdmU/CiAgICAgICAgcG9rZURlbGF5JDMgPSAxMDAwLCAvLyBob3cgZnJlcXVlbnRseSB3ZSBjaGVjayBmb3IgY2xvY2sgc2tldwogICAgICAgIHRhc2tIZWFkJDMsCiAgICAgICAgdGFza1RhaWwkMywKICAgICAgICBjbG9ja0xhc3QkMyA9IDAsCiAgICAgICAgY2xvY2tOb3ckMyA9IDAsCiAgICAgICAgY2xvY2tTa2V3JDMgPSAwLAogICAgICAgIGNsb2NrJDMgPSB0eXBlb2YgcGVyZm9ybWFuY2UgPT09ICJvYmplY3QiICYmIHBlcmZvcm1hbmNlLm5vdyA/IHBlcmZvcm1hbmNlIDogRGF0ZSwKICAgICAgICBzZXRGcmFtZSQzID0gdHlwZW9mIHdpbmRvdyA9PT0gIm9iamVjdCIgJiYgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSA/IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUuYmluZCh3aW5kb3cpIDogZnVuY3Rpb24oZikgeyBzZXRUaW1lb3V0KGYsIDE3KTsgfTsKCiAgICBmdW5jdGlvbiBub3ckMygpIHsKICAgICAgcmV0dXJuIGNsb2NrTm93JDMgfHwgKHNldEZyYW1lJDMoY2xlYXJOb3ckMyksIGNsb2NrTm93JDMgPSBjbG9jayQzLm5vdygpICsgY2xvY2tTa2V3JDMpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsZWFyTm93JDMoKSB7CiAgICAgIGNsb2NrTm93JDMgPSAwOwogICAgfQoKICAgIGZ1bmN0aW9uIFRpbWVyJDMoKSB7CiAgICAgIHRoaXMuX2NhbGwgPQogICAgICB0aGlzLl90aW1lID0KICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICB9CgogICAgVGltZXIkMy5wcm90b3R5cGUgPSB0aW1lciQzLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRpbWVyJDMsCiAgICAgIHJlc3RhcnQ6IGZ1bmN0aW9uKGNhbGxiYWNrLCBkZWxheSwgdGltZSkgewogICAgICAgIGlmICh0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBUeXBlRXJyb3IoImNhbGxiYWNrIGlzIG5vdCBhIGZ1bmN0aW9uIik7CiAgICAgICAgdGltZSA9ICh0aW1lID09IG51bGwgPyBub3ckMygpIDogK3RpbWUpICsgKGRlbGF5ID09IG51bGwgPyAwIDogK2RlbGF5KTsKICAgICAgICBpZiAoIXRoaXMuX25leHQgJiYgdGFza1RhaWwkMyAhPT0gdGhpcykgewogICAgICAgICAgaWYgKHRhc2tUYWlsJDMpIHRhc2tUYWlsJDMuX25leHQgPSB0aGlzOwogICAgICAgICAgZWxzZSB0YXNrSGVhZCQzID0gdGhpczsKICAgICAgICAgIHRhc2tUYWlsJDMgPSB0aGlzOwogICAgICAgIH0KICAgICAgICB0aGlzLl9jYWxsID0gY2FsbGJhY2s7CiAgICAgICAgdGhpcy5fdGltZSA9IHRpbWU7CiAgICAgICAgc2xlZXAkMygpOwogICAgICB9LAogICAgICBzdG9wOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fY2FsbCkgewogICAgICAgICAgdGhpcy5fY2FsbCA9IG51bGw7CiAgICAgICAgICB0aGlzLl90aW1lID0gSW5maW5pdHk7CiAgICAgICAgICBzbGVlcCQzKCk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHRpbWVyJDMoY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgIHZhciB0ID0gbmV3IFRpbWVyJDM7CiAgICAgIHQucmVzdGFydChjYWxsYmFjaywgZGVsYXksIHRpbWUpOwogICAgICByZXR1cm4gdDsKICAgIH0KCiAgICBmdW5jdGlvbiB0aW1lckZsdXNoJDMoKSB7CiAgICAgIG5vdyQzKCk7IC8vIEdldCB0aGUgY3VycmVudCB0aW1lLCBpZiBub3QgYWxyZWFkeSBzZXQuCiAgICAgICsrZnJhbWUkMzsgLy8gUHJldGVuZCB3ZeKAmXZlIHNldCBhbiBhbGFybSwgaWYgd2UgaGF2ZW7igJl0IGFscmVhZHkuCiAgICAgIHZhciB0ID0gdGFza0hlYWQkMywgZTsKICAgICAgd2hpbGUgKHQpIHsKICAgICAgICBpZiAoKGUgPSBjbG9ja05vdyQzIC0gdC5fdGltZSkgPj0gMCkgdC5fY2FsbC5jYWxsKG51bGwsIGUpOwogICAgICAgIHQgPSB0Ll9uZXh0OwogICAgICB9CiAgICAgIC0tZnJhbWUkMzsKICAgIH0KCiAgICBmdW5jdGlvbiB3YWtlJDMoKSB7CiAgICAgIGNsb2NrTm93JDMgPSAoY2xvY2tMYXN0JDMgPSBjbG9jayQzLm5vdygpKSArIGNsb2NrU2tldyQzOwogICAgICBmcmFtZSQzID0gdGltZW91dCQ1ID0gMDsKICAgICAgdHJ5IHsKICAgICAgICB0aW1lckZsdXNoJDMoKTsKICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBmcmFtZSQzID0gMDsKICAgICAgICBuYXAkMygpOwogICAgICAgIGNsb2NrTm93JDMgPSAwOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcG9rZSQ0KCkgewogICAgICB2YXIgbm93ID0gY2xvY2skMy5ub3coKSwgZGVsYXkgPSBub3cgLSBjbG9ja0xhc3QkMzsKICAgICAgaWYgKGRlbGF5ID4gcG9rZURlbGF5JDMpIGNsb2NrU2tldyQzIC09IGRlbGF5LCBjbG9ja0xhc3QkMyA9IG5vdzsKICAgIH0KCiAgICBmdW5jdGlvbiBuYXAkMygpIHsKICAgICAgdmFyIHQwLCB0MSA9IHRhc2tIZWFkJDMsIHQyLCB0aW1lID0gSW5maW5pdHk7CiAgICAgIHdoaWxlICh0MSkgewogICAgICAgIGlmICh0MS5fY2FsbCkgewogICAgICAgICAgaWYgKHRpbWUgPiB0MS5fdGltZSkgdGltZSA9IHQxLl90aW1lOwogICAgICAgICAgdDAgPSB0MSwgdDEgPSB0MS5fbmV4dDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdDIgPSB0MS5fbmV4dCwgdDEuX25leHQgPSBudWxsOwogICAgICAgICAgdDEgPSB0MCA/IHQwLl9uZXh0ID0gdDIgOiB0YXNrSGVhZCQzID0gdDI7CiAgICAgICAgfQogICAgICB9CiAgICAgIHRhc2tUYWlsJDMgPSB0MDsKICAgICAgc2xlZXAkMyh0aW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzbGVlcCQzKHRpbWUpIHsKICAgICAgaWYgKGZyYW1lJDMpIHJldHVybjsgLy8gU29vbmVzdCBhbGFybSBhbHJlYWR5IHNldCwgb3Igd2lsbCBiZS4KICAgICAgaWYgKHRpbWVvdXQkNSkgdGltZW91dCQ1ID0gY2xlYXJUaW1lb3V0KHRpbWVvdXQkNSk7CiAgICAgIHZhciBkZWxheSA9IHRpbWUgLSBjbG9ja05vdyQzOyAvLyBTdHJpY3RseSBsZXNzIHRoYW4gaWYgd2UgcmVjb21wdXRlZCBjbG9ja05vdy4KICAgICAgaWYgKGRlbGF5ID4gMjQpIHsKICAgICAgICBpZiAodGltZSA8IEluZmluaXR5KSB0aW1lb3V0JDUgPSBzZXRUaW1lb3V0KHdha2UkMywgdGltZSAtIGNsb2NrJDMubm93KCkgLSBjbG9ja1NrZXckMyk7CiAgICAgICAgaWYgKGludGVydmFsJDQpIGludGVydmFsJDQgPSBjbGVhckludGVydmFsKGludGVydmFsJDQpOwogICAgICB9IGVsc2UgewogICAgICAgIGlmICghaW50ZXJ2YWwkNCkgY2xvY2tMYXN0JDMgPSBjbG9jayQzLm5vdygpLCBpbnRlcnZhbCQ0ID0gc2V0SW50ZXJ2YWwocG9rZSQ0LCBwb2tlRGVsYXkkMyk7CiAgICAgICAgZnJhbWUkMyA9IDEsIHNldEZyYW1lJDMod2FrZSQzKTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVvdXQkNihjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIkMzsKICAgICAgZGVsYXkgPSBkZWxheSA9PSBudWxsID8gMCA6ICtkZWxheTsKICAgICAgdC5yZXN0YXJ0KGZ1bmN0aW9uKGVsYXBzZWQpIHsKICAgICAgICB0LnN0b3AoKTsKICAgICAgICBjYWxsYmFjayhlbGFwc2VkICsgZGVsYXkpOwogICAgICB9LCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVydmFsJDUoY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgIHZhciB0ID0gbmV3IFRpbWVyJDMsIHRvdGFsID0gZGVsYXk7CiAgICAgIGlmIChkZWxheSA9PSBudWxsKSByZXR1cm4gdC5yZXN0YXJ0KGNhbGxiYWNrLCBkZWxheSwgdGltZSksIHQ7CiAgICAgIGRlbGF5ID0gK2RlbGF5LCB0aW1lID0gdGltZSA9PSBudWxsID8gbm93JDMoKSA6ICt0aW1lOwogICAgICB0LnJlc3RhcnQoZnVuY3Rpb24gdGljayhlbGFwc2VkKSB7CiAgICAgICAgZWxhcHNlZCArPSB0b3RhbDsKICAgICAgICB0LnJlc3RhcnQodGljaywgdG90YWwgKz0gZGVsYXksIHRpbWUpOwogICAgICAgIGNhbGxiYWNrKGVsYXBzZWQpOwogICAgICB9LCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIHZhciB4aHRtbCQ0ID0gImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGh0bWwiOwoKICAgIHZhciBuYW1lc3BhY2VzJDQgPSB7CiAgICAgIHN2ZzogImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiwKICAgICAgeGh0bWw6IHhodG1sJDQsCiAgICAgIHhsaW5rOiAiaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIsCiAgICAgIHhtbDogImh0dHA6Ly93d3cudzMub3JnL1hNTC8xOTk4L25hbWVzcGFjZSIsCiAgICAgIHhtbG5zOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC94bWxucy8iCiAgICB9OwoKICAgIGZ1bmN0aW9uIG5hbWVzcGFjZSQ0KG5hbWUpIHsKICAgICAgdmFyIHByZWZpeCA9IG5hbWUgKz0gIiIsIGkgPSBwcmVmaXguaW5kZXhPZigiOiIpOwogICAgICBpZiAoaSA+PSAwICYmIChwcmVmaXggPSBuYW1lLnNsaWNlKDAsIGkpKSAhPT0gInhtbG5zIikgbmFtZSA9IG5hbWUuc2xpY2UoaSArIDEpOwogICAgICByZXR1cm4gbmFtZXNwYWNlcyQ0Lmhhc093blByb3BlcnR5KHByZWZpeCkgPyB7c3BhY2U6IG5hbWVzcGFjZXMkNFtwcmVmaXhdLCBsb2NhbDogbmFtZX0gOiBuYW1lOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3JJbmhlcml0JDQobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGRvY3VtZW50ID0gdGhpcy5vd25lckRvY3VtZW50LAogICAgICAgICAgICB1cmkgPSB0aGlzLm5hbWVzcGFjZVVSSTsKICAgICAgICByZXR1cm4gdXJpID09PSB4aHRtbCQ0ICYmIGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5uYW1lc3BhY2VVUkkgPT09IHhodG1sJDQKICAgICAgICAgICAgPyBkb2N1bWVudC5jcmVhdGVFbGVtZW50KG5hbWUpCiAgICAgICAgICAgIDogZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKHVyaSwgbmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvckZpeGVkJDQoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLm93bmVyRG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvciQ0KG5hbWUpIHsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlJDQobmFtZSk7CiAgICAgIHJldHVybiAoZnVsbG5hbWUubG9jYWwKICAgICAgICAgID8gY3JlYXRvckZpeGVkJDQKICAgICAgICAgIDogY3JlYXRvckluaGVyaXQkNCkoZnVsbG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vbmUkOCgpIHt9CgogICAgZnVuY3Rpb24gc2VsZWN0b3IkNChzZWxlY3RvcikgewogICAgICByZXR1cm4gc2VsZWN0b3IgPT0gbnVsbCA/IG5vbmUkOCA6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zZWxlY3QkNChzZWxlY3QpIHsKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yJDQoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIHN1Ym5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKHN1Ym5vZGUgPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpKSB7CiAgICAgICAgICAgIGlmICgiX19kYXRhX18iIGluIG5vZGUpIHN1Ym5vZGUuX19kYXRhX18gPSBub2RlLl9fZGF0YV9fOwogICAgICAgICAgICBzdWJncm91cFtpXSA9IHN1Ym5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ2KHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gZW1wdHkkNigpIHsKICAgICAgcmV0dXJuIFtdOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdG9yQWxsJDQoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHNlbGVjdG9yID09IG51bGwgPyBlbXB0eSQ2IDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucXVlcnlTZWxlY3RvckFsbChzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NlbGVjdEFsbCQ0KHNlbGVjdCkgewogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3JBbGwkNChzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gW10sIHBhcmVudHMgPSBbXSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc3ViZ3JvdXBzLnB1c2goc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKTsKICAgICAgICAgICAgcGFyZW50cy5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNihzdWJncm91cHMsIHBhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1hdGNoZXIkNShzZWxlY3RvcikgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubWF0Y2hlcyhzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2ZpbHRlciQ0KG1hdGNoKSB7CiAgICAgIGlmICh0eXBlb2YgbWF0Y2ggIT09ICJmdW5jdGlvbiIpIG1hdGNoID0gbWF0Y2hlciQ1KG1hdGNoKTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBbXSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiBtYXRjaC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkgewogICAgICAgICAgICBzdWJncm91cC5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNihzdWJncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNwYXJzZSQ0KHVwZGF0ZSkgewogICAgICByZXR1cm4gbmV3IEFycmF5KHVwZGF0ZS5sZW5ndGgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9lbnRlciQ0KCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ2KHRoaXMuX2VudGVyIHx8IHRoaXMuX2dyb3Vwcy5tYXAoc3BhcnNlJDQpLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBFbnRlck5vZGUkNChwYXJlbnQsIGRhdHVtKSB7CiAgICAgIHRoaXMub3duZXJEb2N1bWVudCA9IHBhcmVudC5vd25lckRvY3VtZW50OwogICAgICB0aGlzLm5hbWVzcGFjZVVSSSA9IHBhcmVudC5uYW1lc3BhY2VVUkk7CiAgICAgIHRoaXMuX25leHQgPSBudWxsOwogICAgICB0aGlzLl9wYXJlbnQgPSBwYXJlbnQ7CiAgICAgIHRoaXMuX19kYXRhX18gPSBkYXR1bTsKICAgIH0KCiAgICBFbnRlck5vZGUkNC5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBFbnRlck5vZGUkNCwKICAgICAgYXBwZW5kQ2hpbGQ6IGZ1bmN0aW9uKGNoaWxkKSB7IHJldHVybiB0aGlzLl9wYXJlbnQuaW5zZXJ0QmVmb3JlKGNoaWxkLCB0aGlzLl9uZXh0KTsgfSwKICAgICAgaW5zZXJ0QmVmb3JlOiBmdW5jdGlvbihjaGlsZCwgbmV4dCkgeyByZXR1cm4gdGhpcy5fcGFyZW50Lmluc2VydEJlZm9yZShjaGlsZCwgbmV4dCk7IH0sCiAgICAgIHF1ZXJ5U2VsZWN0b3I6IGZ1bmN0aW9uKHNlbGVjdG9yKSB7IHJldHVybiB0aGlzLl9wYXJlbnQucXVlcnlTZWxlY3RvcihzZWxlY3Rvcik7IH0sCiAgICAgIHF1ZXJ5U2VsZWN0b3JBbGw6IGZ1bmN0aW9uKHNlbGVjdG9yKSB7IHJldHVybiB0aGlzLl9wYXJlbnQucXVlcnlTZWxlY3RvckFsbChzZWxlY3Rvcik7IH0KICAgIH07CgogICAgZnVuY3Rpb24gY29uc3RhbnQkdCh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIga2V5UHJlZml4JDYgPSAiJCI7IC8vIFByb3RlY3QgYWdhaW5zdCBrZXlzIGxpa2Ug4oCcX19wcm90b19f4oCdLgoKICAgIGZ1bmN0aW9uIGJpbmRJbmRleCQ0KHBhcmVudCwgZ3JvdXAsIGVudGVyLCB1cGRhdGUsIGV4aXQsIGRhdGEpIHsKICAgICAgdmFyIGkgPSAwLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoOwoKICAgICAgLy8gUHV0IGFueSBub24tbnVsbCBub2RlcyB0aGF0IGZpdCBpbnRvIHVwZGF0ZS4KICAgICAgLy8gUHV0IGFueSBudWxsIG5vZGVzIGludG8gZW50ZXIuCiAgICAgIC8vIFB1dCBhbnkgcmVtYWluaW5nIGRhdGEgaW50byBlbnRlci4KICAgICAgZm9yICg7IGkgPCBkYXRhTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBub2RlLl9fZGF0YV9fID0gZGF0YVtpXTsKICAgICAgICAgIHVwZGF0ZVtpXSA9IG5vZGU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVudGVyW2ldID0gbmV3IEVudGVyTm9kZSQ0KHBhcmVudCwgZGF0YVtpXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBQdXQgYW55IG5vbi1udWxsIG5vZGVzIHRoYXQgZG9u4oCZdCBmaXQgaW50byBleGl0LgogICAgICBmb3IgKDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBiaW5kS2V5JDQocGFyZW50LCBncm91cCwgZW50ZXIsIHVwZGF0ZSwgZXhpdCwgZGF0YSwga2V5KSB7CiAgICAgIHZhciBpLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIG5vZGVCeUtleVZhbHVlID0ge30sCiAgICAgICAgICBncm91cExlbmd0aCA9IGdyb3VwLmxlbmd0aCwKICAgICAgICAgIGRhdGFMZW5ndGggPSBkYXRhLmxlbmd0aCwKICAgICAgICAgIGtleVZhbHVlcyA9IG5ldyBBcnJheShncm91cExlbmd0aCksCiAgICAgICAgICBrZXlWYWx1ZTsKCiAgICAgIC8vIENvbXB1dGUgdGhlIGtleSBmb3IgZWFjaCBub2RlLgogICAgICAvLyBJZiBtdWx0aXBsZSBub2RlcyBoYXZlIHRoZSBzYW1lIGtleSwgdGhlIGR1cGxpY2F0ZXMgYXJlIGFkZGVkIHRvIGV4aXQuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAga2V5VmFsdWVzW2ldID0ga2V5VmFsdWUgPSBrZXlQcmVmaXgkNiArIGtleS5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKTsKICAgICAgICAgIGlmIChrZXlWYWx1ZSBpbiBub2RlQnlLZXlWYWx1ZSkgewogICAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBDb21wdXRlIHRoZSBrZXkgZm9yIGVhY2ggZGF0dW0uCiAgICAgIC8vIElmIHRoZXJlIGEgbm9kZSBhc3NvY2lhdGVkIHdpdGggdGhpcyBrZXksIGpvaW4gYW5kIGFkZCBpdCB0byB1cGRhdGUuCiAgICAgIC8vIElmIHRoZXJlIGlzIG5vdCAob3IgdGhlIGtleSBpcyBhIGR1cGxpY2F0ZSksIGFkZCBpdCB0byBlbnRlci4KICAgICAgZm9yIChpID0gMDsgaSA8IGRhdGFMZW5ndGg7ICsraSkgewogICAgICAgIGtleVZhbHVlID0ga2V5UHJlZml4JDYgKyBrZXkuY2FsbChwYXJlbnQsIGRhdGFbaV0sIGksIGRhdGEpOwogICAgICAgIGlmIChub2RlID0gbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdKSB7CiAgICAgICAgICB1cGRhdGVbaV0gPSBub2RlOwogICAgICAgICAgbm9kZS5fX2RhdGFfXyA9IGRhdGFbaV07CiAgICAgICAgICBub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZV0gPSBudWxsOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlbnRlcltpXSA9IG5ldyBFbnRlck5vZGUkNChwYXJlbnQsIGRhdGFbaV0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gQWRkIGFueSByZW1haW5pbmcgbm9kZXMgdGhhdCB3ZXJlIG5vdCBib3VuZCB0byBkYXRhIHRvIGV4aXQuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZXNbaV1dID09PSBub2RlKSkgewogICAgICAgICAgZXhpdFtpXSA9IG5vZGU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2RhdGEkNCh2YWx1ZSwga2V5KSB7CiAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICBkYXRhID0gbmV3IEFycmF5KHRoaXMuc2l6ZSgpKSwgaiA9IC0xOwogICAgICAgIHRoaXMuZWFjaChmdW5jdGlvbihkKSB7IGRhdGFbKytqXSA9IGQ7IH0pOwogICAgICAgIHJldHVybiBkYXRhOwogICAgICB9CgogICAgICB2YXIgYmluZCA9IGtleSA/IGJpbmRLZXkkNCA6IGJpbmRJbmRleCQ0LAogICAgICAgICAgcGFyZW50cyA9IHRoaXMuX3BhcmVudHMsCiAgICAgICAgICBncm91cHMgPSB0aGlzLl9ncm91cHM7CgogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB2YWx1ZSA9IGNvbnN0YW50JHQodmFsdWUpOwoKICAgICAgZm9yICh2YXIgbSA9IGdyb3Vwcy5sZW5ndGgsIHVwZGF0ZSA9IG5ldyBBcnJheShtKSwgZW50ZXIgPSBuZXcgQXJyYXkobSksIGV4aXQgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHBhcmVudHNbal0sCiAgICAgICAgICAgIGdyb3VwID0gZ3JvdXBzW2pdLAogICAgICAgICAgICBncm91cExlbmd0aCA9IGdyb3VwLmxlbmd0aCwKICAgICAgICAgICAgZGF0YSA9IHZhbHVlLmNhbGwocGFyZW50LCBwYXJlbnQgJiYgcGFyZW50Ll9fZGF0YV9fLCBqLCBwYXJlbnRzKSwKICAgICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBlbnRlckdyb3VwID0gZW50ZXJbal0gPSBuZXcgQXJyYXkoZGF0YUxlbmd0aCksCiAgICAgICAgICAgIHVwZGF0ZUdyb3VwID0gdXBkYXRlW2pdID0gbmV3IEFycmF5KGRhdGFMZW5ndGgpLAogICAgICAgICAgICBleGl0R3JvdXAgPSBleGl0W2pdID0gbmV3IEFycmF5KGdyb3VwTGVuZ3RoKTsKCiAgICAgICAgYmluZChwYXJlbnQsIGdyb3VwLCBlbnRlckdyb3VwLCB1cGRhdGVHcm91cCwgZXhpdEdyb3VwLCBkYXRhLCBrZXkpOwoKICAgICAgICAvLyBOb3cgY29ubmVjdCB0aGUgZW50ZXIgbm9kZXMgdG8gdGhlaXIgZm9sbG93aW5nIHVwZGF0ZSBub2RlLCBzdWNoIHRoYXQKICAgICAgICAvLyBhcHBlbmRDaGlsZCBjYW4gaW5zZXJ0IHRoZSBtYXRlcmlhbGl6ZWQgZW50ZXIgbm9kZSBiZWZvcmUgdGhpcyBub2RlLAogICAgICAgIC8vIHJhdGhlciB0aGFuIGF0IHRoZSBlbmQgb2YgdGhlIHBhcmVudCBub2RlLgogICAgICAgIGZvciAodmFyIGkwID0gMCwgaTEgPSAwLCBwcmV2aW91cywgbmV4dDsgaTAgPCBkYXRhTGVuZ3RoOyArK2kwKSB7CiAgICAgICAgICBpZiAocHJldmlvdXMgPSBlbnRlckdyb3VwW2kwXSkgewogICAgICAgICAgICBpZiAoaTAgPj0gaTEpIGkxID0gaTAgKyAxOwogICAgICAgICAgICB3aGlsZSAoIShuZXh0ID0gdXBkYXRlR3JvdXBbaTFdKSAmJiArK2kxIDwgZGF0YUxlbmd0aCk7CiAgICAgICAgICAgIHByZXZpb3VzLl9uZXh0ID0gbmV4dCB8fCBudWxsOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgdXBkYXRlID0gbmV3IFNlbGVjdGlvbiQ2KHVwZGF0ZSwgcGFyZW50cyk7CiAgICAgIHVwZGF0ZS5fZW50ZXIgPSBlbnRlcjsKICAgICAgdXBkYXRlLl9leGl0ID0gZXhpdDsKICAgICAgcmV0dXJuIHVwZGF0ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZXhpdCQ0KCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ2KHRoaXMuX2V4aXQgfHwgdGhpcy5fZ3JvdXBzLm1hcChzcGFyc2UkNCksIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9qb2luJDMob25lbnRlciwgb251cGRhdGUsIG9uZXhpdCkgewogICAgICB2YXIgZW50ZXIgPSB0aGlzLmVudGVyKCksIHVwZGF0ZSA9IHRoaXMsIGV4aXQgPSB0aGlzLmV4aXQoKTsKICAgICAgZW50ZXIgPSB0eXBlb2Ygb25lbnRlciA9PT0gImZ1bmN0aW9uIiA/IG9uZW50ZXIoZW50ZXIpIDogZW50ZXIuYXBwZW5kKG9uZW50ZXIgKyAiIik7CiAgICAgIGlmIChvbnVwZGF0ZSAhPSBudWxsKSB1cGRhdGUgPSBvbnVwZGF0ZSh1cGRhdGUpOwogICAgICBpZiAob25leGl0ID09IG51bGwpIGV4aXQucmVtb3ZlKCk7IGVsc2Ugb25leGl0KGV4aXQpOwogICAgICByZXR1cm4gZW50ZXIgJiYgdXBkYXRlID8gZW50ZXIubWVyZ2UodXBkYXRlKS5vcmRlcigpIDogdXBkYXRlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9tZXJnZSQ0KHNlbGVjdGlvbikgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzMCA9IHRoaXMuX2dyb3VwcywgZ3JvdXBzMSA9IHNlbGVjdGlvbi5fZ3JvdXBzLCBtMCA9IGdyb3VwczAubGVuZ3RoLCBtMSA9IGdyb3VwczEubGVuZ3RoLCBtID0gTWF0aC5taW4obTAsIG0xKSwgbWVyZ2VzID0gbmV3IEFycmF5KG0wKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cDAgPSBncm91cHMwW2pdLCBncm91cDEgPSBncm91cHMxW2pdLCBuID0gZ3JvdXAwLmxlbmd0aCwgbWVyZ2UgPSBtZXJnZXNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwMFtpXSB8fCBncm91cDFbaV0pIHsKICAgICAgICAgICAgbWVyZ2VbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yICg7IGogPCBtMDsgKytqKSB7CiAgICAgICAgbWVyZ2VzW2pdID0gZ3JvdXBzMFtqXTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNihtZXJnZXMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9vcmRlciQ0KCkgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gLTEsIG0gPSBncm91cHMubGVuZ3RoOyArK2ogPCBtOykgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gZ3JvdXAubGVuZ3RoIC0gMSwgbmV4dCA9IGdyb3VwW2ldLCBub2RlOyAtLWkgPj0gMDspIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgaWYgKG5leHQgJiYgbm9kZS5jb21wYXJlRG9jdW1lbnRQb3NpdGlvbihuZXh0KSBeIDQpIG5leHQucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUobm9kZSwgbmV4dCk7CiAgICAgICAgICAgIG5leHQgPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NvcnQkNChjb21wYXJlKSB7CiAgICAgIGlmICghY29tcGFyZSkgY29tcGFyZSA9IGFzY2VuZGluZyRjOwoKICAgICAgZnVuY3Rpb24gY29tcGFyZU5vZGUoYSwgYikgewogICAgICAgIHJldHVybiBhICYmIGIgPyBjb21wYXJlKGEuX19kYXRhX18sIGIuX19kYXRhX18pIDogIWEgLSAhYjsKICAgICAgfQoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc29ydGdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc29ydGdyb3VwID0gc29ydGdyb3Vwc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc29ydGdyb3VwW2ldID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgc29ydGdyb3VwLnNvcnQoY29tcGFyZU5vZGUpOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ2KHNvcnRncm91cHMsIHRoaXMuX3BhcmVudHMpLm9yZGVyKCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nJGMoYSwgYikgewogICAgICByZXR1cm4gYSA8IGIgPyAtMSA6IGEgPiBiID8gMSA6IGEgPj0gYiA/IDAgOiBOYU47CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2NhbGwkNCgpIHsKICAgICAgdmFyIGNhbGxiYWNrID0gYXJndW1lbnRzWzBdOwogICAgICBhcmd1bWVudHNbMF0gPSB0aGlzOwogICAgICBjYWxsYmFjay5hcHBseShudWxsLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbm9kZXMkNCgpIHsKICAgICAgdmFyIG5vZGVzID0gbmV3IEFycmF5KHRoaXMuc2l6ZSgpKSwgaSA9IC0xOwogICAgICB0aGlzLmVhY2goZnVuY3Rpb24oKSB7IG5vZGVzWysraV0gPSB0aGlzOyB9KTsKICAgICAgcmV0dXJuIG5vZGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9ub2RlJDQoKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgdmFyIG5vZGUgPSBncm91cFtpXTsKICAgICAgICAgIGlmIChub2RlKSByZXR1cm4gbm9kZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zaXplJDQoKSB7CiAgICAgIHZhciBzaXplID0gMDsKICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKCkgeyArK3NpemU7IH0pOwogICAgICByZXR1cm4gc2l6ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZW1wdHkkNCgpIHsKICAgICAgcmV0dXJuICF0aGlzLm5vZGUoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZWFjaCQ0KGNhbGxiYWNrKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZTsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgY2FsbGJhY2suY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlJDYobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZU5TJDYoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnQkNihuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgdmFsdWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudE5TJDYoZnVsbG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCwgdmFsdWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbiQ2KG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgZWxzZSB0aGlzLnNldEF0dHJpYnV0ZShuYW1lLCB2KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb25OUyQ2KGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBlbHNlIHRoaXMuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCB2KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fYXR0ciQ0KG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQ0KG5hbWUpOwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIG5vZGUgPSB0aGlzLm5vZGUoKTsKICAgICAgICByZXR1cm4gZnVsbG5hbWUubG9jYWwKICAgICAgICAgICAgPyBub2RlLmdldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCkKICAgICAgICAgICAgOiBub2RlLmdldEF0dHJpYnV0ZShmdWxsbmFtZSk7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHZhbHVlID09IG51bGwKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0clJlbW92ZU5TJDYgOiBhdHRyUmVtb3ZlJDYpIDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyRnVuY3Rpb25OUyQ2IDogYXR0ckZ1bmN0aW9uJDYpCiAgICAgICAgICA6IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJDb25zdGFudE5TJDYgOiBhdHRyQ29uc3RhbnQkNikpKShmdWxsbmFtZSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0VmlldyQ0KG5vZGUpIHsKICAgICAgcmV0dXJuIChub2RlLm93bmVyRG9jdW1lbnQgJiYgbm9kZS5vd25lckRvY3VtZW50LmRlZmF1bHRWaWV3KSAvLyBub2RlIGlzIGEgTm9kZQogICAgICAgICAgfHwgKG5vZGUuZG9jdW1lbnQgJiYgbm9kZSkgLy8gbm9kZSBpcyBhIFdpbmRvdwogICAgICAgICAgfHwgbm9kZS5kZWZhdWx0VmlldzsgLy8gbm9kZSBpcyBhIERvY3VtZW50CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVSZW1vdmUkNihuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLnJlbW92ZVByb3BlcnR5KG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlQ29uc3RhbnQkNihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgdmFsdWUsIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUZ1bmN0aW9uJDYobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgICBlbHNlIHRoaXMuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgdiwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zdHlsZSQ0KG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA+IDEKICAgICAgICAgID8gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgICA/IHN0eWxlUmVtb3ZlJDYgOiB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICAgID8gc3R5bGVGdW5jdGlvbiQ2CiAgICAgICAgICAgICAgICA6IHN0eWxlQ29uc3RhbnQkNikobmFtZSwgdmFsdWUsIHByaW9yaXR5ID09IG51bGwgPyAiIiA6IHByaW9yaXR5KSkKICAgICAgICAgIDogc3R5bGVWYWx1ZSQ0KHRoaXMubm9kZSgpLCBuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVZhbHVlJDQobm9kZSwgbmFtZSkgewogICAgICByZXR1cm4gbm9kZS5zdHlsZS5nZXRQcm9wZXJ0eVZhbHVlKG5hbWUpCiAgICAgICAgICB8fCBkZWZhdWx0VmlldyQ0KG5vZGUpLmdldENvbXB1dGVkU3R5bGUobm9kZSwgbnVsbCkuZ2V0UHJvcGVydHlWYWx1ZShuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eVJlbW92ZSQ0KG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGRlbGV0ZSB0aGlzW25hbWVdOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5Q29uc3RhbnQkNChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpc1tuYW1lXSA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5RnVuY3Rpb24kNChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIGRlbGV0ZSB0aGlzW25hbWVdOwogICAgICAgIGVsc2UgdGhpc1tuYW1lXSA9IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3Byb3BlcnR5JDQobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPiAxCiAgICAgICAgICA/IHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgID8gcHJvcGVydHlSZW1vdmUkNCA6IHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gcHJvcGVydHlGdW5jdGlvbiQ0CiAgICAgICAgICAgICAgOiBwcm9wZXJ0eUNvbnN0YW50JDQpKG5hbWUsIHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKClbbmFtZV07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NBcnJheSQ0KHN0cmluZykgewogICAgICByZXR1cm4gc3RyaW5nLnRyaW0oKS5zcGxpdCgvXnxccysvKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc0xpc3QkNChub2RlKSB7CiAgICAgIHJldHVybiBub2RlLmNsYXNzTGlzdCB8fCBuZXcgQ2xhc3NMaXN0JDQobm9kZSk7CiAgICB9CgogICAgZnVuY3Rpb24gQ2xhc3NMaXN0JDQobm9kZSkgewogICAgICB0aGlzLl9ub2RlID0gbm9kZTsKICAgICAgdGhpcy5fbmFtZXMgPSBjbGFzc0FycmF5JDQobm9kZS5nZXRBdHRyaWJ1dGUoImNsYXNzIikgfHwgIiIpOwogICAgfQoKICAgIENsYXNzTGlzdCQ0LnByb3RvdHlwZSA9IHsKICAgICAgYWRkOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpOwogICAgICAgIGlmIChpIDwgMCkgewogICAgICAgICAgdGhpcy5fbmFtZXMucHVzaChuYW1lKTsKICAgICAgICAgIHRoaXMuX25vZGUuc2V0QXR0cmlidXRlKCJjbGFzcyIsIHRoaXMuX25hbWVzLmpvaW4oIiAiKSk7CiAgICAgICAgfQogICAgICB9LAogICAgICByZW1vdmU6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICB2YXIgaSA9IHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSk7CiAgICAgICAgaWYgKGkgPj0gMCkgewogICAgICAgICAgdGhpcy5fbmFtZXMuc3BsaWNlKGksIDEpOwogICAgICAgICAgdGhpcy5fbm9kZS5zZXRBdHRyaWJ1dGUoImNsYXNzIiwgdGhpcy5fbmFtZXMuam9pbigiICIpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGNvbnRhaW5zOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSkgPj0gMDsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjbGFzc2VkQWRkJDQobm9kZSwgbmFtZXMpIHsKICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3QkNChub2RlKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbGlzdC5hZGQobmFtZXNbaV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRSZW1vdmUkNChub2RlLCBuYW1lcykgewogICAgICB2YXIgbGlzdCA9IGNsYXNzTGlzdCQ0KG5vZGUpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBsaXN0LnJlbW92ZShuYW1lc1tpXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZFRydWUkNChuYW1lcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgY2xhc3NlZEFkZCQ0KHRoaXMsIG5hbWVzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkRmFsc2UkNChuYW1lcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgY2xhc3NlZFJlbW92ZSQ0KHRoaXMsIG5hbWVzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkRnVuY3Rpb24kNChuYW1lcywgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICh2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpID8gY2xhc3NlZEFkZCQ0IDogY2xhc3NlZFJlbW92ZSQ0KSh0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2NsYXNzZWQkNChuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgbmFtZXMgPSBjbGFzc0FycmF5JDQobmFtZSArICIiKTsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0JDQodGhpcy5ub2RlKCkpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICghbGlzdC5jb250YWlucyhuYW1lc1tpXSkpIHJldHVybiBmYWxzZTsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXMuZWFjaCgodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IGNsYXNzZWRGdW5jdGlvbiQ0IDogdmFsdWUKICAgICAgICAgID8gY2xhc3NlZFRydWUkNAogICAgICAgICAgOiBjbGFzc2VkRmFsc2UkNCkobmFtZXMsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dFJlbW92ZSQ0KCkgewogICAgICB0aGlzLnRleHRDb250ZW50ID0gIiI7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dENvbnN0YW50JDYodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0RnVuY3Rpb24kNih2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2ID09IG51bGwgPyAiIiA6IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3RleHQkNCh2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2godmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgID8gdGV4dFJlbW92ZSQ0IDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gdGV4dEZ1bmN0aW9uJDYKICAgICAgICAgICAgICA6IHRleHRDb25zdGFudCQ2KSh2YWx1ZSkpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLnRleHRDb250ZW50OwogICAgfQoKICAgIGZ1bmN0aW9uIGh0bWxSZW1vdmUkNCgpIHsKICAgICAgdGhpcy5pbm5lckhUTUwgPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sQ29uc3RhbnQkNCh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5pbm5lckhUTUwgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sRnVuY3Rpb24kNCh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHRoaXMuaW5uZXJIVE1MID0gdiA9PSBudWxsID8gIiIgOiB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9odG1sJDQodmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IGh0bWxSZW1vdmUkNCA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IGh0bWxGdW5jdGlvbiQ0CiAgICAgICAgICAgICAgOiBodG1sQ29uc3RhbnQkNCkodmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS5pbm5lckhUTUw7CiAgICB9CgogICAgZnVuY3Rpb24gcmFpc2UkNSgpIHsKICAgICAgaWYgKHRoaXMubmV4dFNpYmxpbmcpIHRoaXMucGFyZW50Tm9kZS5hcHBlbmRDaGlsZCh0aGlzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fcmFpc2UkNCgpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChyYWlzZSQ1KTsKICAgIH0KCiAgICBmdW5jdGlvbiBsb3dlciQ0KCkgewogICAgICBpZiAodGhpcy5wcmV2aW91c1NpYmxpbmcpIHRoaXMucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUodGhpcywgdGhpcy5wYXJlbnROb2RlLmZpcnN0Q2hpbGQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9sb3dlciQ0KCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKGxvd2VyJDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9hcHBlbmQkNChuYW1lKSB7CiAgICAgIHZhciBjcmVhdGUgPSB0eXBlb2YgbmFtZSA9PT0gImZ1bmN0aW9uIiA/IG5hbWUgOiBjcmVhdG9yJDQobmFtZSk7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5hcHBlbmRDaGlsZChjcmVhdGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50TnVsbCQ0KCkgewogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25faW5zZXJ0JDQobmFtZSwgYmVmb3JlKSB7CiAgICAgIHZhciBjcmVhdGUgPSB0eXBlb2YgbmFtZSA9PT0gImZ1bmN0aW9uIiA/IG5hbWUgOiBjcmVhdG9yJDQobmFtZSksCiAgICAgICAgICBzZWxlY3QgPSBiZWZvcmUgPT0gbnVsbCA/IGNvbnN0YW50TnVsbCQ0IDogdHlwZW9mIGJlZm9yZSA9PT0gImZ1bmN0aW9uIiA/IGJlZm9yZSA6IHNlbGVjdG9yJDQoYmVmb3JlKTsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLmluc2VydEJlZm9yZShjcmVhdGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSwgc2VsZWN0LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgbnVsbCk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHJlbW92ZSQ0KCkgewogICAgICB2YXIgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICBpZiAocGFyZW50KSBwYXJlbnQucmVtb3ZlQ2hpbGQodGhpcyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3JlbW92ZSQ0KCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKHJlbW92ZSQ0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xvbmVTaGFsbG93JDQoKSB7CiAgICAgIHZhciBjbG9uZSA9IHRoaXMuY2xvbmVOb2RlKGZhbHNlKSwgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICByZXR1cm4gcGFyZW50ID8gcGFyZW50Lmluc2VydEJlZm9yZShjbG9uZSwgdGhpcy5uZXh0U2libGluZykgOiBjbG9uZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xvbmVEZWVwJDQoKSB7CiAgICAgIHZhciBjbG9uZSA9IHRoaXMuY2xvbmVOb2RlKHRydWUpLCBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIHJldHVybiBwYXJlbnQgPyBwYXJlbnQuaW5zZXJ0QmVmb3JlKGNsb25lLCB0aGlzLm5leHRTaWJsaW5nKSA6IGNsb25lOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZSQ0KGRlZXApIHsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGRlZXAgPyBzZWxlY3Rpb25fY2xvbmVEZWVwJDQgOiBzZWxlY3Rpb25fY2xvbmVTaGFsbG93JDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kYXR1bSQ0KHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMucHJvcGVydHkoIl9fZGF0YV9fIiwgdmFsdWUpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLl9fZGF0YV9fOwogICAgfQoKICAgIHZhciBmaWx0ZXJFdmVudHMkNCA9IHt9OwoKICAgIGlmICh0eXBlb2YgZG9jdW1lbnQgIT09ICJ1bmRlZmluZWQiKSB7CiAgICAgIHZhciBlbGVtZW50JDUgPSBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQ7CiAgICAgIGlmICghKCJvbm1vdXNlZW50ZXIiIGluIGVsZW1lbnQkNSkpIHsKICAgICAgICBmaWx0ZXJFdmVudHMkNCA9IHttb3VzZWVudGVyOiAibW91c2VvdmVyIiwgbW91c2VsZWF2ZTogIm1vdXNlb3V0In07CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBmaWx0ZXJDb250ZXh0TGlzdGVuZXIkNChsaXN0ZW5lciwgaW5kZXgsIGdyb3VwKSB7CiAgICAgIGxpc3RlbmVyID0gY29udGV4dExpc3RlbmVyJDQobGlzdGVuZXIsIGluZGV4LCBncm91cCk7CiAgICAgIHJldHVybiBmdW5jdGlvbihldmVudCkgewogICAgICAgIHZhciByZWxhdGVkID0gZXZlbnQucmVsYXRlZFRhcmdldDsKICAgICAgICBpZiAoIXJlbGF0ZWQgfHwgKHJlbGF0ZWQgIT09IHRoaXMgJiYgIShyZWxhdGVkLmNvbXBhcmVEb2N1bWVudFBvc2l0aW9uKHRoaXMpICYgOCkpKSB7CiAgICAgICAgICBsaXN0ZW5lci5jYWxsKHRoaXMsIGV2ZW50KTsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY29udGV4dExpc3RlbmVyJDQobGlzdGVuZXIsIGluZGV4LCBncm91cCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oZXZlbnQxKSB7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIGxpc3RlbmVyLmNhbGwodGhpcywgdGhpcy5fX2RhdGFfXywgaW5kZXgsIGdyb3VwKTsKICAgICAgICB9IGZpbmFsbHkgewogICAgICAgIH0KICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVR5cGVuYW1lcyQ5KHR5cGVuYW1lcykgewogICAgICByZXR1cm4gdHlwZW5hbWVzLnRyaW0oKS5zcGxpdCgvXnxccysvKS5tYXAoZnVuY3Rpb24odCkgewogICAgICAgIHZhciBuYW1lID0gIiIsIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSBuYW1lID0gdC5zbGljZShpICsgMSksIHQgPSB0LnNsaWNlKDAsIGkpOwogICAgICAgIHJldHVybiB7dHlwZTogdCwgbmFtZTogbmFtZX07CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIG9uUmVtb3ZlJDQodHlwZW5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBvbiA9IHRoaXMuX19vbjsKICAgICAgICBpZiAoIW9uKSByZXR1cm47CiAgICAgICAgZm9yICh2YXIgaiA9IDAsIGkgPSAtMSwgbSA9IG9uLmxlbmd0aCwgbzsgaiA8IG07ICsraikgewogICAgICAgICAgaWYgKG8gPSBvbltqXSwgKCF0eXBlbmFtZS50eXBlIHx8IG8udHlwZSA9PT0gdHlwZW5hbWUudHlwZSkgJiYgby5uYW1lID09PSB0eXBlbmFtZS5uYW1lKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIsIG8uY2FwdHVyZSk7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBvblsrK2ldID0gbzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKCsraSkgb24ubGVuZ3RoID0gaTsKICAgICAgICBlbHNlIGRlbGV0ZSB0aGlzLl9fb247CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb25BZGQkNCh0eXBlbmFtZSwgdmFsdWUsIGNhcHR1cmUpIHsKICAgICAgdmFyIHdyYXAgPSBmaWx0ZXJFdmVudHMkNC5oYXNPd25Qcm9wZXJ0eSh0eXBlbmFtZS50eXBlKSA/IGZpbHRlckNvbnRleHRMaXN0ZW5lciQ0IDogY29udGV4dExpc3RlbmVyJDQ7CiAgICAgIHJldHVybiBmdW5jdGlvbihkLCBpLCBncm91cCkgewogICAgICAgIHZhciBvbiA9IHRoaXMuX19vbiwgbywgbGlzdGVuZXIgPSB3cmFwKHZhbHVlLCBpLCBncm91cCk7CiAgICAgICAgaWYgKG9uKSBmb3IgKHZhciBqID0gMCwgbSA9IG9uLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgICAgaWYgKChvID0gb25bal0pLnR5cGUgPT09IHR5cGVuYW1lLnR5cGUgJiYgby5uYW1lID09PSB0eXBlbmFtZS5uYW1lKSB7CiAgICAgICAgICAgIHRoaXMucmVtb3ZlRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIsIG8uY2FwdHVyZSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcihvLnR5cGUsIG8ubGlzdGVuZXIgPSBsaXN0ZW5lciwgby5jYXB0dXJlID0gY2FwdHVyZSk7CiAgICAgICAgICAgIG8udmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIodHlwZW5hbWUudHlwZSwgbGlzdGVuZXIsIGNhcHR1cmUpOwogICAgICAgIG8gPSB7dHlwZTogdHlwZW5hbWUudHlwZSwgbmFtZTogdHlwZW5hbWUubmFtZSwgdmFsdWU6IHZhbHVlLCBsaXN0ZW5lcjogbGlzdGVuZXIsIGNhcHR1cmU6IGNhcHR1cmV9OwogICAgICAgIGlmICghb24pIHRoaXMuX19vbiA9IFtvXTsKICAgICAgICBlbHNlIG9uLnB1c2gobyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX29uJDQodHlwZW5hbWUsIHZhbHVlLCBjYXB0dXJlKSB7CiAgICAgIHZhciB0eXBlbmFtZXMgPSBwYXJzZVR5cGVuYW1lcyQ5KHR5cGVuYW1lICsgIiIpLCBpLCBuID0gdHlwZW5hbWVzLmxlbmd0aCwgdDsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBvbiA9IHRoaXMubm9kZSgpLl9fb247CiAgICAgICAgaWYgKG9uKSBmb3IgKHZhciBqID0gMCwgbSA9IG9uLmxlbmd0aCwgbzsgaiA8IG07ICsraikgewogICAgICAgICAgZm9yIChpID0gMCwgbyA9IG9uW2pdOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICAgIGlmICgodCA9IHR5cGVuYW1lc1tpXSkudHlwZSA9PT0gby50eXBlICYmIHQubmFtZSA9PT0gby5uYW1lKSB7CiAgICAgICAgICAgICAgcmV0dXJuIG8udmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBvbiA9IHZhbHVlID8gb25BZGQkNCA6IG9uUmVtb3ZlJDQ7CiAgICAgIGlmIChjYXB0dXJlID09IG51bGwpIGNhcHR1cmUgPSBmYWxzZTsKICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgdGhpcy5lYWNoKG9uKHR5cGVuYW1lc1tpXSwgdmFsdWUsIGNhcHR1cmUpKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hFdmVudCQ0KG5vZGUsIHR5cGUsIHBhcmFtcykgewogICAgICB2YXIgd2luZG93ID0gZGVmYXVsdFZpZXckNChub2RlKSwKICAgICAgICAgIGV2ZW50ID0gd2luZG93LkN1c3RvbUV2ZW50OwoKICAgICAgaWYgKHR5cGVvZiBldmVudCA9PT0gImZ1bmN0aW9uIikgewogICAgICAgIGV2ZW50ID0gbmV3IGV2ZW50KHR5cGUsIHBhcmFtcyk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgZXZlbnQgPSB3aW5kb3cuZG9jdW1lbnQuY3JlYXRlRXZlbnQoIkV2ZW50Iik7CiAgICAgICAgaWYgKHBhcmFtcykgZXZlbnQuaW5pdEV2ZW50KHR5cGUsIHBhcmFtcy5idWJibGVzLCBwYXJhbXMuY2FuY2VsYWJsZSksIGV2ZW50LmRldGFpbCA9IHBhcmFtcy5kZXRhaWw7CiAgICAgICAgZWxzZSBldmVudC5pbml0RXZlbnQodHlwZSwgZmFsc2UsIGZhbHNlKTsKICAgICAgfQoKICAgICAgbm9kZS5kaXNwYXRjaEV2ZW50KGV2ZW50KTsKICAgIH0KCiAgICBmdW5jdGlvbiBkaXNwYXRjaENvbnN0YW50JDQodHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gZGlzcGF0Y2hFdmVudCQ0KHRoaXMsIHR5cGUsIHBhcmFtcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hGdW5jdGlvbiQ0KHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRpc3BhdGNoRXZlbnQkNCh0aGlzLCB0eXBlLCBwYXJhbXMuYXBwbHkodGhpcywgYXJndW1lbnRzKSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2Rpc3BhdGNoJDQodHlwZSwgcGFyYW1zKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2goKHR5cGVvZiBwYXJhbXMgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gZGlzcGF0Y2hGdW5jdGlvbiQ0CiAgICAgICAgICA6IGRpc3BhdGNoQ29uc3RhbnQkNCkodHlwZSwgcGFyYW1zKSk7CiAgICB9CgogICAgdmFyIHJvb3QkNiA9IFtudWxsXTsKCiAgICBmdW5jdGlvbiBTZWxlY3Rpb24kNihncm91cHMsIHBhcmVudHMpIHsKICAgICAgdGhpcy5fZ3JvdXBzID0gZ3JvdXBzOwogICAgICB0aGlzLl9wYXJlbnRzID0gcGFyZW50czsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb24kNCgpIHsKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kNihbW2RvY3VtZW50LmRvY3VtZW50RWxlbWVudF1dLCByb290JDYpOwogICAgfQoKICAgIFNlbGVjdGlvbiQ2LnByb3RvdHlwZSA9IHNlbGVjdGlvbiQ0LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFNlbGVjdGlvbiQ2LAogICAgICBzZWxlY3Q6IHNlbGVjdGlvbl9zZWxlY3QkNCwKICAgICAgc2VsZWN0QWxsOiBzZWxlY3Rpb25fc2VsZWN0QWxsJDQsCiAgICAgIGZpbHRlcjogc2VsZWN0aW9uX2ZpbHRlciQ0LAogICAgICBkYXRhOiBzZWxlY3Rpb25fZGF0YSQ0LAogICAgICBlbnRlcjogc2VsZWN0aW9uX2VudGVyJDQsCiAgICAgIGV4aXQ6IHNlbGVjdGlvbl9leGl0JDQsCiAgICAgIGpvaW46IHNlbGVjdGlvbl9qb2luJDMsCiAgICAgIG1lcmdlOiBzZWxlY3Rpb25fbWVyZ2UkNCwKICAgICAgb3JkZXI6IHNlbGVjdGlvbl9vcmRlciQ0LAogICAgICBzb3J0OiBzZWxlY3Rpb25fc29ydCQ0LAogICAgICBjYWxsOiBzZWxlY3Rpb25fY2FsbCQ0LAogICAgICBub2Rlczogc2VsZWN0aW9uX25vZGVzJDQsCiAgICAgIG5vZGU6IHNlbGVjdGlvbl9ub2RlJDQsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9zaXplJDQsCiAgICAgIGVtcHR5OiBzZWxlY3Rpb25fZW1wdHkkNCwKICAgICAgZWFjaDogc2VsZWN0aW9uX2VhY2gkNCwKICAgICAgYXR0cjogc2VsZWN0aW9uX2F0dHIkNCwKICAgICAgc3R5bGU6IHNlbGVjdGlvbl9zdHlsZSQ0LAogICAgICBwcm9wZXJ0eTogc2VsZWN0aW9uX3Byb3BlcnR5JDQsCiAgICAgIGNsYXNzZWQ6IHNlbGVjdGlvbl9jbGFzc2VkJDQsCiAgICAgIHRleHQ6IHNlbGVjdGlvbl90ZXh0JDQsCiAgICAgIGh0bWw6IHNlbGVjdGlvbl9odG1sJDQsCiAgICAgIHJhaXNlOiBzZWxlY3Rpb25fcmFpc2UkNCwKICAgICAgbG93ZXI6IHNlbGVjdGlvbl9sb3dlciQ0LAogICAgICBhcHBlbmQ6IHNlbGVjdGlvbl9hcHBlbmQkNCwKICAgICAgaW5zZXJ0OiBzZWxlY3Rpb25faW5zZXJ0JDQsCiAgICAgIHJlbW92ZTogc2VsZWN0aW9uX3JlbW92ZSQ0LAogICAgICBjbG9uZTogc2VsZWN0aW9uX2Nsb25lJDQsCiAgICAgIGRhdHVtOiBzZWxlY3Rpb25fZGF0dW0kNCwKICAgICAgb246IHNlbGVjdGlvbl9vbiQ0LAogICAgICBkaXNwYXRjaDogc2VsZWN0aW9uX2Rpc3BhdGNoJDQKICAgIH07CgogICAgdmFyIG5vb3AkYSA9IHt2YWx1ZTogZnVuY3Rpb24oKSB7fX07CgogICAgZnVuY3Rpb24gZGlzcGF0Y2gkNSgpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSBhcmd1bWVudHMubGVuZ3RoLCBfID0ge30sIHQ7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoISh0ID0gYXJndW1lbnRzW2ldICsgIiIpIHx8ICh0IGluIF8pIHx8IC9bXHMuXS8udGVzdCh0KSkgdGhyb3cgbmV3IEVycm9yKCJpbGxlZ2FsIHR5cGU6ICIgKyB0KTsKICAgICAgICBfW3RdID0gW107CiAgICAgIH0KICAgICAgcmV0dXJuIG5ldyBEaXNwYXRjaCQ1KF8pOwogICAgfQoKICAgIGZ1bmN0aW9uIERpc3BhdGNoJDUoXykgewogICAgICB0aGlzLl8gPSBfOwogICAgfQoKICAgIGZ1bmN0aW9uIHBhcnNlVHlwZW5hbWVzJGEodHlwZW5hbWVzLCB0eXBlcykgewogICAgICByZXR1cm4gdHlwZW5hbWVzLnRyaW0oKS5zcGxpdCgvXnxccysvKS5tYXAoZnVuY3Rpb24odCkgewogICAgICAgIHZhciBuYW1lID0gIiIsIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSBuYW1lID0gdC5zbGljZShpICsgMSksIHQgPSB0LnNsaWNlKDAsIGkpOwogICAgICAgIGlmICh0ICYmICF0eXBlcy5oYXNPd25Qcm9wZXJ0eSh0KSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0KTsKICAgICAgICByZXR1cm4ge3R5cGU6IHQsIG5hbWU6IG5hbWV9OwogICAgICB9KTsKICAgIH0KCiAgICBEaXNwYXRjaCQ1LnByb3RvdHlwZSA9IGRpc3BhdGNoJDUucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogRGlzcGF0Y2gkNSwKICAgICAgb246IGZ1bmN0aW9uKHR5cGVuYW1lLCBjYWxsYmFjaykgewogICAgICAgIHZhciBfID0gdGhpcy5fLAogICAgICAgICAgICBUID0gcGFyc2VUeXBlbmFtZXMkYSh0eXBlbmFtZSArICIiLCBfKSwKICAgICAgICAgICAgdCwKICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICBuID0gVC5sZW5ndGg7CgogICAgICAgIC8vIElmIG5vIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJldHVybiB0aGUgY2FsbGJhY2sgb2YgdGhlIGdpdmVuIHR5cGUgYW5kIG5hbWUuCiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgaWYgKCh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgJiYgKHQgPSBnZXQkOChfW3RdLCB0eXBlbmFtZS5uYW1lKSkpIHJldHVybiB0OwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gSWYgYSB0eXBlIHdhcyBzcGVjaWZpZWQsIHNldCB0aGUgY2FsbGJhY2sgZm9yIHRoZSBnaXZlbiB0eXBlIGFuZCBuYW1lLgogICAgICAgIC8vIE90aGVyd2lzZSwgaWYgYSBudWxsIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQsIHJlbW92ZSBjYWxsYmFja3Mgb2YgdGhlIGdpdmVuIG5hbWUuCiAgICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwgJiYgdHlwZW9mIGNhbGxiYWNrICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3IoImludmFsaWQgY2FsbGJhY2s6ICIgKyBjYWxsYmFjayk7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIHsKICAgICAgICAgIGlmICh0ID0gKHR5cGVuYW1lID0gVFtpXSkudHlwZSkgX1t0XSA9IHNldCRjKF9bdF0sIHR5cGVuYW1lLm5hbWUsIGNhbGxiYWNrKTsKICAgICAgICAgIGVsc2UgaWYgKGNhbGxiYWNrID09IG51bGwpIGZvciAodCBpbiBfKSBfW3RdID0gc2V0JGMoX1t0XSwgdHlwZW5hbWUubmFtZSwgbnVsbCk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgY29weTogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGNvcHkgPSB7fSwgXyA9IHRoaXMuXzsKICAgICAgICBmb3IgKHZhciB0IGluIF8pIGNvcHlbdF0gPSBfW3RdLnNsaWNlKCk7CiAgICAgICAgcmV0dXJuIG5ldyBEaXNwYXRjaCQ1KGNvcHkpOwogICAgICB9LAogICAgICBjYWxsOiBmdW5jdGlvbih0eXBlLCB0aGF0KSB7CiAgICAgICAgaWYgKChuID0gYXJndW1lbnRzLmxlbmd0aCAtIDIpID4gMCkgZm9yICh2YXIgYXJncyA9IG5ldyBBcnJheShuKSwgaSA9IDAsIG4sIHQ7IGkgPCBuOyArK2kpIGFyZ3NbaV0gPSBhcmd1bWVudHNbaSArIDJdOwogICAgICAgIGlmICghdGhpcy5fLmhhc093blByb3BlcnR5KHR5cGUpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHR5cGUpOwogICAgICAgIGZvciAodCA9IHRoaXMuX1t0eXBlXSwgaSA9IDAsIG4gPSB0Lmxlbmd0aDsgaSA8IG47ICsraSkgdFtpXS52YWx1ZS5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfSwKICAgICAgYXBwbHk6IGZ1bmN0aW9uKHR5cGUsIHRoYXQsIGFyZ3MpIHsKICAgICAgICBpZiAoIXRoaXMuXy5oYXNPd25Qcm9wZXJ0eSh0eXBlKSkgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIHR5cGU6ICIgKyB0eXBlKTsKICAgICAgICBmb3IgKHZhciB0ID0gdGhpcy5fW3R5cGVdLCBpID0gMCwgbiA9IHQubGVuZ3RoOyBpIDwgbjsgKytpKSB0W2ldLnZhbHVlLmFwcGx5KHRoYXQsIGFyZ3MpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGdldCQ4KHR5cGUsIG5hbWUpIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0eXBlLmxlbmd0aCwgYzsgaSA8IG47ICsraSkgewogICAgICAgIGlmICgoYyA9IHR5cGVbaV0pLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgIHJldHVybiBjLnZhbHVlOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHNldCRjKHR5cGUsIG5hbWUsIGNhbGxiYWNrKSB7CiAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHlwZS5sZW5ndGg7IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAodHlwZVtpXS5uYW1lID09PSBuYW1lKSB7CiAgICAgICAgICB0eXBlW2ldID0gbm9vcCRhLCB0eXBlID0gdHlwZS5zbGljZSgwLCBpKS5jb25jYXQodHlwZS5zbGljZShpICsgMSkpOwogICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmIChjYWxsYmFjayAhPSBudWxsKSB0eXBlLnB1c2goe25hbWU6IG5hbWUsIHZhbHVlOiBjYWxsYmFja30pOwogICAgICByZXR1cm4gdHlwZTsKICAgIH0KCiAgICB2YXIgZnJhbWUkNCA9IDAsIC8vIGlzIGFuIGFuaW1hdGlvbiBmcmFtZSBwZW5kaW5nPwogICAgICAgIHRpbWVvdXQkNyA9IDAsIC8vIGlzIGEgdGltZW91dCBwZW5kaW5nPwogICAgICAgIGludGVydmFsJDYgPSAwLCAvLyBhcmUgYW55IHRpbWVycyBhY3RpdmU/CiAgICAgICAgcG9rZURlbGF5JDQgPSAxMDAwLCAvLyBob3cgZnJlcXVlbnRseSB3ZSBjaGVjayBmb3IgY2xvY2sgc2tldwogICAgICAgIHRhc2tIZWFkJDQsCiAgICAgICAgdGFza1RhaWwkNCwKICAgICAgICBjbG9ja0xhc3QkNCA9IDAsCiAgICAgICAgY2xvY2tOb3ckNCA9IDAsCiAgICAgICAgY2xvY2tTa2V3JDQgPSAwLAogICAgICAgIGNsb2NrJDQgPSB0eXBlb2YgcGVyZm9ybWFuY2UgPT09ICJvYmplY3QiICYmIHBlcmZvcm1hbmNlLm5vdyA/IHBlcmZvcm1hbmNlIDogRGF0ZSwKICAgICAgICBzZXRGcmFtZSQ0ID0gdHlwZW9mIHdpbmRvdyA9PT0gIm9iamVjdCIgJiYgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSA/IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUuYmluZCh3aW5kb3cpIDogZnVuY3Rpb24oZikgeyBzZXRUaW1lb3V0KGYsIDE3KTsgfTsKCiAgICBmdW5jdGlvbiBub3ckNCgpIHsKICAgICAgcmV0dXJuIGNsb2NrTm93JDQgfHwgKHNldEZyYW1lJDQoY2xlYXJOb3ckNCksIGNsb2NrTm93JDQgPSBjbG9jayQ0Lm5vdygpICsgY2xvY2tTa2V3JDQpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsZWFyTm93JDQoKSB7CiAgICAgIGNsb2NrTm93JDQgPSAwOwogICAgfQoKICAgIGZ1bmN0aW9uIFRpbWVyJDQoKSB7CiAgICAgIHRoaXMuX2NhbGwgPQogICAgICB0aGlzLl90aW1lID0KICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICB9CgogICAgVGltZXIkNC5wcm90b3R5cGUgPSB0aW1lciQ0LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRpbWVyJDQsCiAgICAgIHJlc3RhcnQ6IGZ1bmN0aW9uKGNhbGxiYWNrLCBkZWxheSwgdGltZSkgewogICAgICAgIGlmICh0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBUeXBlRXJyb3IoImNhbGxiYWNrIGlzIG5vdCBhIGZ1bmN0aW9uIik7CiAgICAgICAgdGltZSA9ICh0aW1lID09IG51bGwgPyBub3ckNCgpIDogK3RpbWUpICsgKGRlbGF5ID09IG51bGwgPyAwIDogK2RlbGF5KTsKICAgICAgICBpZiAoIXRoaXMuX25leHQgJiYgdGFza1RhaWwkNCAhPT0gdGhpcykgewogICAgICAgICAgaWYgKHRhc2tUYWlsJDQpIHRhc2tUYWlsJDQuX25leHQgPSB0aGlzOwogICAgICAgICAgZWxzZSB0YXNrSGVhZCQ0ID0gdGhpczsKICAgICAgICAgIHRhc2tUYWlsJDQgPSB0aGlzOwogICAgICAgIH0KICAgICAgICB0aGlzLl9jYWxsID0gY2FsbGJhY2s7CiAgICAgICAgdGhpcy5fdGltZSA9IHRpbWU7CiAgICAgICAgc2xlZXAkNCgpOwogICAgICB9LAogICAgICBzdG9wOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fY2FsbCkgewogICAgICAgICAgdGhpcy5fY2FsbCA9IG51bGw7CiAgICAgICAgICB0aGlzLl90aW1lID0gSW5maW5pdHk7CiAgICAgICAgICBzbGVlcCQ0KCk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHRpbWVyJDQoY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgIHZhciB0ID0gbmV3IFRpbWVyJDQ7CiAgICAgIHQucmVzdGFydChjYWxsYmFjaywgZGVsYXksIHRpbWUpOwogICAgICByZXR1cm4gdDsKICAgIH0KCiAgICBmdW5jdGlvbiB0aW1lckZsdXNoJDQoKSB7CiAgICAgIG5vdyQ0KCk7IC8vIEdldCB0aGUgY3VycmVudCB0aW1lLCBpZiBub3QgYWxyZWFkeSBzZXQuCiAgICAgICsrZnJhbWUkNDsgLy8gUHJldGVuZCB3ZeKAmXZlIHNldCBhbiBhbGFybSwgaWYgd2UgaGF2ZW7igJl0IGFscmVhZHkuCiAgICAgIHZhciB0ID0gdGFza0hlYWQkNCwgZTsKICAgICAgd2hpbGUgKHQpIHsKICAgICAgICBpZiAoKGUgPSBjbG9ja05vdyQ0IC0gdC5fdGltZSkgPj0gMCkgdC5fY2FsbC5jYWxsKG51bGwsIGUpOwogICAgICAgIHQgPSB0Ll9uZXh0OwogICAgICB9CiAgICAgIC0tZnJhbWUkNDsKICAgIH0KCiAgICBmdW5jdGlvbiB3YWtlJDQoKSB7CiAgICAgIGNsb2NrTm93JDQgPSAoY2xvY2tMYXN0JDQgPSBjbG9jayQ0Lm5vdygpKSArIGNsb2NrU2tldyQ0OwogICAgICBmcmFtZSQ0ID0gdGltZW91dCQ3ID0gMDsKICAgICAgdHJ5IHsKICAgICAgICB0aW1lckZsdXNoJDQoKTsKICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBmcmFtZSQ0ID0gMDsKICAgICAgICBuYXAkNCgpOwogICAgICAgIGNsb2NrTm93JDQgPSAwOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcG9rZSQ1KCkgewogICAgICB2YXIgbm93ID0gY2xvY2skNC5ub3coKSwgZGVsYXkgPSBub3cgLSBjbG9ja0xhc3QkNDsKICAgICAgaWYgKGRlbGF5ID4gcG9rZURlbGF5JDQpIGNsb2NrU2tldyQ0IC09IGRlbGF5LCBjbG9ja0xhc3QkNCA9IG5vdzsKICAgIH0KCiAgICBmdW5jdGlvbiBuYXAkNCgpIHsKICAgICAgdmFyIHQwLCB0MSA9IHRhc2tIZWFkJDQsIHQyLCB0aW1lID0gSW5maW5pdHk7CiAgICAgIHdoaWxlICh0MSkgewogICAgICAgIGlmICh0MS5fY2FsbCkgewogICAgICAgICAgaWYgKHRpbWUgPiB0MS5fdGltZSkgdGltZSA9IHQxLl90aW1lOwogICAgICAgICAgdDAgPSB0MSwgdDEgPSB0MS5fbmV4dDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdDIgPSB0MS5fbmV4dCwgdDEuX25leHQgPSBudWxsOwogICAgICAgICAgdDEgPSB0MCA/IHQwLl9uZXh0ID0gdDIgOiB0YXNrSGVhZCQ0ID0gdDI7CiAgICAgICAgfQogICAgICB9CiAgICAgIHRhc2tUYWlsJDQgPSB0MDsKICAgICAgc2xlZXAkNCh0aW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzbGVlcCQ0KHRpbWUpIHsKICAgICAgaWYgKGZyYW1lJDQpIHJldHVybjsgLy8gU29vbmVzdCBhbGFybSBhbHJlYWR5IHNldCwgb3Igd2lsbCBiZS4KICAgICAgaWYgKHRpbWVvdXQkNykgdGltZW91dCQ3ID0gY2xlYXJUaW1lb3V0KHRpbWVvdXQkNyk7CiAgICAgIHZhciBkZWxheSA9IHRpbWUgLSBjbG9ja05vdyQ0OyAvLyBTdHJpY3RseSBsZXNzIHRoYW4gaWYgd2UgcmVjb21wdXRlZCBjbG9ja05vdy4KICAgICAgaWYgKGRlbGF5ID4gMjQpIHsKICAgICAgICBpZiAodGltZSA8IEluZmluaXR5KSB0aW1lb3V0JDcgPSBzZXRUaW1lb3V0KHdha2UkNCwgdGltZSAtIGNsb2NrJDQubm93KCkgLSBjbG9ja1NrZXckNCk7CiAgICAgICAgaWYgKGludGVydmFsJDYpIGludGVydmFsJDYgPSBjbGVhckludGVydmFsKGludGVydmFsJDYpOwogICAgICB9IGVsc2UgewogICAgICAgIGlmICghaW50ZXJ2YWwkNikgY2xvY2tMYXN0JDQgPSBjbG9jayQ0Lm5vdygpLCBpbnRlcnZhbCQ2ID0gc2V0SW50ZXJ2YWwocG9rZSQ1LCBwb2tlRGVsYXkkNCk7CiAgICAgICAgZnJhbWUkNCA9IDEsIHNldEZyYW1lJDQod2FrZSQ0KTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVvdXQkOChjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIkNDsKICAgICAgZGVsYXkgPSBkZWxheSA9PSBudWxsID8gMCA6ICtkZWxheTsKICAgICAgdC5yZXN0YXJ0KGZ1bmN0aW9uKGVsYXBzZWQpIHsKICAgICAgICB0LnN0b3AoKTsKICAgICAgICBjYWxsYmFjayhlbGFwc2VkICsgZGVsYXkpOwogICAgICB9LCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIHZhciBlbXB0eU9uJDIgPSBkaXNwYXRjaCQ1KCJzdGFydCIsICJlbmQiLCAiaW50ZXJydXB0Iik7CiAgICB2YXIgZW1wdHlUd2VlbiQyID0gW107CgogICAgdmFyIENSRUFURUQkMiA9IDA7CiAgICB2YXIgU0NIRURVTEVEJDIgPSAxOwogICAgdmFyIFNUQVJUSU5HJDIgPSAyOwogICAgdmFyIFNUQVJURUQkMiA9IDM7CiAgICB2YXIgUlVOTklORyQyID0gNDsKICAgIHZhciBFTkRJTkckMiA9IDU7CiAgICB2YXIgRU5ERUQkMiA9IDY7CgogICAgZnVuY3Rpb24gc2NoZWR1bGUkMyhub2RlLCBuYW1lLCBpZCwgaW5kZXgsIGdyb3VwLCB0aW1pbmcpIHsKICAgICAgdmFyIHNjaGVkdWxlcyA9IG5vZGUuX190cmFuc2l0aW9uOwogICAgICBpZiAoIXNjaGVkdWxlcykgbm9kZS5fX3RyYW5zaXRpb24gPSB7fTsKICAgICAgZWxzZSBpZiAoaWQgaW4gc2NoZWR1bGVzKSByZXR1cm47CiAgICAgIGNyZWF0ZSQ0KG5vZGUsIGlkLCB7CiAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICBpbmRleDogaW5kZXgsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBncm91cDogZ3JvdXAsIC8vIEZvciBjb250ZXh0IGR1cmluZyBjYWxsYmFjay4KICAgICAgICBvbjogZW1wdHlPbiQyLAogICAgICAgIHR3ZWVuOiBlbXB0eVR3ZWVuJDIsCiAgICAgICAgdGltZTogdGltaW5nLnRpbWUsCiAgICAgICAgZGVsYXk6IHRpbWluZy5kZWxheSwKICAgICAgICBkdXJhdGlvbjogdGltaW5nLmR1cmF0aW9uLAogICAgICAgIGVhc2U6IHRpbWluZy5lYXNlLAogICAgICAgIHRpbWVyOiBudWxsLAogICAgICAgIHN0YXRlOiBDUkVBVEVEJDIKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gaW5pdCQyKG5vZGUsIGlkKSB7CiAgICAgIHZhciBzY2hlZHVsZSA9IGdldCQ5KG5vZGUsIGlkKTsKICAgICAgaWYgKHNjaGVkdWxlLnN0YXRlID4gQ1JFQVRFRCQyKSB0aHJvdyBuZXcgRXJyb3IoInRvbyBsYXRlOyBhbHJlYWR5IHNjaGVkdWxlZCIpOwogICAgICByZXR1cm4gc2NoZWR1bGU7CiAgICB9CgogICAgZnVuY3Rpb24gc2V0JGQobm9kZSwgaWQpIHsKICAgICAgdmFyIHNjaGVkdWxlID0gZ2V0JDkobm9kZSwgaWQpOwogICAgICBpZiAoc2NoZWR1bGUuc3RhdGUgPiBTVEFSVElORyQyKSB0aHJvdyBuZXcgRXJyb3IoInRvbyBsYXRlOyBhbHJlYWR5IHN0YXJ0ZWQiKTsKICAgICAgcmV0dXJuIHNjaGVkdWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGdldCQ5KG5vZGUsIGlkKSB7CiAgICAgIHZhciBzY2hlZHVsZSA9IG5vZGUuX190cmFuc2l0aW9uOwogICAgICBpZiAoIXNjaGVkdWxlIHx8ICEoc2NoZWR1bGUgPSBzY2hlZHVsZVtpZF0pKSB0aHJvdyBuZXcgRXJyb3IoInRyYW5zaXRpb24gbm90IGZvdW5kIik7CiAgICAgIHJldHVybiBzY2hlZHVsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdGUkNChub2RlLCBpZCwgc2VsZikgewogICAgICB2YXIgc2NoZWR1bGVzID0gbm9kZS5fX3RyYW5zaXRpb24sCiAgICAgICAgICB0d2VlbjsKCiAgICAgIC8vIEluaXRpYWxpemUgdGhlIHNlbGYgdGltZXIgd2hlbiB0aGUgdHJhbnNpdGlvbiBpcyBjcmVhdGVkLgogICAgICAvLyBOb3RlIHRoZSBhY3R1YWwgZGVsYXkgaXMgbm90IGtub3duIHVudGlsIHRoZSBmaXJzdCBjYWxsYmFjayEKICAgICAgc2NoZWR1bGVzW2lkXSA9IHNlbGY7CiAgICAgIHNlbGYudGltZXIgPSB0aW1lciQ0KHNjaGVkdWxlLCAwLCBzZWxmLnRpbWUpOwoKICAgICAgZnVuY3Rpb24gc2NoZWR1bGUoZWxhcHNlZCkgewogICAgICAgIHNlbGYuc3RhdGUgPSBTQ0hFRFVMRUQkMjsKICAgICAgICBzZWxmLnRpbWVyLnJlc3RhcnQoc3RhcnQsIHNlbGYuZGVsYXksIHNlbGYudGltZSk7CgogICAgICAgIC8vIElmIHRoZSBlbGFwc2VkIGRlbGF5IGlzIGxlc3MgdGhhbiBvdXIgZmlyc3Qgc2xlZXAsIHN0YXJ0IGltbWVkaWF0ZWx5LgogICAgICAgIGlmIChzZWxmLmRlbGF5IDw9IGVsYXBzZWQpIHN0YXJ0KGVsYXBzZWQgLSBzZWxmLmRlbGF5KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gc3RhcnQoZWxhcHNlZCkgewogICAgICAgIHZhciBpLCBqLCBuLCBvOwoKICAgICAgICAvLyBJZiB0aGUgc3RhdGUgaXMgbm90IFNDSEVEVUxFRCwgdGhlbiB3ZSBwcmV2aW91c2x5IGVycm9yZWQgb24gc3RhcnQuCiAgICAgICAgaWYgKHNlbGYuc3RhdGUgIT09IFNDSEVEVUxFRCQyKSByZXR1cm4gc3RvcCgpOwoKICAgICAgICBmb3IgKGkgaW4gc2NoZWR1bGVzKSB7CiAgICAgICAgICBvID0gc2NoZWR1bGVzW2ldOwogICAgICAgICAgaWYgKG8ubmFtZSAhPT0gc2VsZi5uYW1lKSBjb250aW51ZTsKCiAgICAgICAgICAvLyBXaGlsZSB0aGlzIGVsZW1lbnQgYWxyZWFkeSBoYXMgYSBzdGFydGluZyB0cmFuc2l0aW9uIGR1cmluZyB0aGlzIGZyYW1lLAogICAgICAgICAgLy8gZGVmZXIgc3RhcnRpbmcgYW4gaW50ZXJydXB0aW5nIHRyYW5zaXRpb24gdW50aWwgdGhhdCB0cmFuc2l0aW9uIGhhcyBhCiAgICAgICAgICAvLyBjaGFuY2UgdG8gdGljayAoYW5kIHBvc3NpYmx5IGVuZCk7IHNlZSBkMy9kMy10cmFuc2l0aW9uIzU0IQogICAgICAgICAgaWYgKG8uc3RhdGUgPT09IFNUQVJURUQkMikgcmV0dXJuIHRpbWVvdXQkOChzdGFydCk7CgogICAgICAgICAgLy8gSW50ZXJydXB0IHRoZSBhY3RpdmUgdHJhbnNpdGlvbiwgaWYgYW55LgogICAgICAgICAgLy8gRGlzcGF0Y2ggdGhlIGludGVycnVwdCBldmVudC4KICAgICAgICAgIGlmIChvLnN0YXRlID09PSBSVU5OSU5HJDIpIHsKICAgICAgICAgICAgby5zdGF0ZSA9IEVOREVEJDI7CiAgICAgICAgICAgIG8udGltZXIuc3RvcCgpOwogICAgICAgICAgICBvLm9uLmNhbGwoImludGVycnVwdCIsIG5vZGUsIG5vZGUuX19kYXRhX18sIG8uaW5kZXgsIG8uZ3JvdXApOwogICAgICAgICAgICBkZWxldGUgc2NoZWR1bGVzW2ldOwogICAgICAgICAgfQoKICAgICAgICAgIC8vIENhbmNlbCBhbnkgcHJlLWVtcHRlZCB0cmFuc2l0aW9ucy4gTm8gaW50ZXJydXB0IGV2ZW50IGlzIGRpc3BhdGNoZWQKICAgICAgICAgIC8vIGJlY2F1c2UgdGhlIGNhbmNlbGxlZCB0cmFuc2l0aW9ucyBuZXZlciBzdGFydGVkLiBOb3RlIHRoYXQgdGhpcyBhbHNvCiAgICAgICAgICAvLyByZW1vdmVzIHRoaXMgdHJhbnNpdGlvbiBmcm9tIHRoZSBwZW5kaW5nIGxpc3QhCiAgICAgICAgICBlbHNlIGlmICgraSA8IGlkKSB7CiAgICAgICAgICAgIG8uc3RhdGUgPSBFTkRFRCQyOwogICAgICAgICAgICBvLnRpbWVyLnN0b3AoKTsKICAgICAgICAgICAgZGVsZXRlIHNjaGVkdWxlc1tpXTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIERlZmVyIHRoZSBmaXJzdCB0aWNrIHRvIGVuZCBvZiB0aGUgY3VycmVudCBmcmFtZTsgc2VlIGQzL2QzIzE1NzYuCiAgICAgICAgLy8gTm90ZSB0aGUgdHJhbnNpdGlvbiBtYXkgYmUgY2FuY2VsZWQgYWZ0ZXIgc3RhcnQgYW5kIGJlZm9yZSB0aGUgZmlyc3QgdGljayEKICAgICAgICAvLyBOb3RlIHRoaXMgbXVzdCBiZSBzY2hlZHVsZWQgYmVmb3JlIHRoZSBzdGFydCBldmVudDsgc2VlIGQzL2QzLXRyYW5zaXRpb24jMTYhCiAgICAgICAgLy8gQXNzdW1pbmcgdGhpcyBpcyBzdWNjZXNzZnVsLCBzdWJzZXF1ZW50IGNhbGxiYWNrcyBnbyBzdHJhaWdodCB0byB0aWNrLgogICAgICAgIHRpbWVvdXQkOChmdW5jdGlvbigpIHsKICAgICAgICAgIGlmIChzZWxmLnN0YXRlID09PSBTVEFSVEVEJDIpIHsKICAgICAgICAgICAgc2VsZi5zdGF0ZSA9IFJVTk5JTkckMjsKICAgICAgICAgICAgc2VsZi50aW1lci5yZXN0YXJ0KHRpY2ssIHNlbGYuZGVsYXksIHNlbGYudGltZSk7CiAgICAgICAgICAgIHRpY2soZWxhcHNlZCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIC8vIERpc3BhdGNoIHRoZSBzdGFydCBldmVudC4KICAgICAgICAvLyBOb3RlIHRoaXMgbXVzdCBiZSBkb25lIGJlZm9yZSB0aGUgdHdlZW4gYXJlIGluaXRpYWxpemVkLgogICAgICAgIHNlbGYuc3RhdGUgPSBTVEFSVElORyQyOwogICAgICAgIHNlbGYub24uY2FsbCgic3RhcnQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKTsKICAgICAgICBpZiAoc2VsZi5zdGF0ZSAhPT0gU1RBUlRJTkckMikgcmV0dXJuOyAvLyBpbnRlcnJ1cHRlZAogICAgICAgIHNlbGYuc3RhdGUgPSBTVEFSVEVEJDI7CgogICAgICAgIC8vIEluaXRpYWxpemUgdGhlIHR3ZWVuLCBkZWxldGluZyBudWxsIHR3ZWVuLgogICAgICAgIHR3ZWVuID0gbmV3IEFycmF5KG4gPSBzZWxmLnR3ZWVuLmxlbmd0aCk7CiAgICAgICAgZm9yIChpID0gMCwgaiA9IC0xOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobyA9IHNlbGYudHdlZW5baV0udmFsdWUuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBzZWxmLmluZGV4LCBzZWxmLmdyb3VwKSkgewogICAgICAgICAgICB0d2VlblsrK2pdID0gbzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdHdlZW4ubGVuZ3RoID0gaiArIDE7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRpY2soZWxhcHNlZCkgewogICAgICAgIHZhciB0ID0gZWxhcHNlZCA8IHNlbGYuZHVyYXRpb24gPyBzZWxmLmVhc2UuY2FsbChudWxsLCBlbGFwc2VkIC8gc2VsZi5kdXJhdGlvbikgOiAoc2VsZi50aW1lci5yZXN0YXJ0KHN0b3ApLCBzZWxmLnN0YXRlID0gRU5ESU5HJDIsIDEpLAogICAgICAgICAgICBpID0gLTEsCiAgICAgICAgICAgIG4gPSB0d2Vlbi5sZW5ndGg7CgogICAgICAgIHdoaWxlICgrK2kgPCBuKSB7CiAgICAgICAgICB0d2VlbltpXS5jYWxsKG51bGwsIHQpOwogICAgICAgIH0KCiAgICAgICAgLy8gRGlzcGF0Y2ggdGhlIGVuZCBldmVudC4KICAgICAgICBpZiAoc2VsZi5zdGF0ZSA9PT0gRU5ESU5HJDIpIHsKICAgICAgICAgIHNlbGYub24uY2FsbCgiZW5kIiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgc2VsZi5pbmRleCwgc2VsZi5ncm91cCk7CiAgICAgICAgICBzdG9wKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBzdG9wKCkgewogICAgICAgIHNlbGYuc3RhdGUgPSBFTkRFRCQyOwogICAgICAgIHNlbGYudGltZXIuc3RvcCgpOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaWRdOwogICAgICAgIGZvciAodmFyIGkgaW4gc2NoZWR1bGVzKSByZXR1cm47IC8vIGVzbGludC1kaXNhYmxlLWxpbmUgbm8tdW51c2VkLXZhcnMKICAgICAgICBkZWxldGUgbm9kZS5fX3RyYW5zaXRpb247CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnJ1cHQkMihub2RlLCBuYW1lKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbiwKICAgICAgICAgIHNjaGVkdWxlLAogICAgICAgICAgYWN0aXZlLAogICAgICAgICAgZW1wdHkgPSB0cnVlLAogICAgICAgICAgaTsKCiAgICAgIGlmICghc2NoZWR1bGVzKSByZXR1cm47CgogICAgICBuYW1lID0gbmFtZSA9PSBudWxsID8gbnVsbCA6IG5hbWUgKyAiIjsKCiAgICAgIGZvciAoaSBpbiBzY2hlZHVsZXMpIHsKICAgICAgICBpZiAoKHNjaGVkdWxlID0gc2NoZWR1bGVzW2ldKS5uYW1lICE9PSBuYW1lKSB7IGVtcHR5ID0gZmFsc2U7IGNvbnRpbnVlOyB9CiAgICAgICAgYWN0aXZlID0gc2NoZWR1bGUuc3RhdGUgPiBTVEFSVElORyQyICYmIHNjaGVkdWxlLnN0YXRlIDwgRU5ESU5HJDI7CiAgICAgICAgc2NoZWR1bGUuc3RhdGUgPSBFTkRFRCQyOwogICAgICAgIHNjaGVkdWxlLnRpbWVyLnN0b3AoKTsKICAgICAgICBpZiAoYWN0aXZlKSBzY2hlZHVsZS5vbi5jYWxsKCJpbnRlcnJ1cHQiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzY2hlZHVsZS5pbmRleCwgc2NoZWR1bGUuZ3JvdXApOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgIH0KCiAgICAgIGlmIChlbXB0eSkgZGVsZXRlIG5vZGUuX190cmFuc2l0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9pbnRlcnJ1cHQkMihuYW1lKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgaW50ZXJydXB0JDIodGhpcywgbmFtZSk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGRlZmluZSQ1KGNvbnN0cnVjdG9yLCBmYWN0b3J5LCBwcm90b3R5cGUpIHsKICAgICAgY29uc3RydWN0b3IucHJvdG90eXBlID0gZmFjdG9yeS5wcm90b3R5cGUgPSBwcm90b3R5cGU7CiAgICAgIHByb3RvdHlwZS5jb25zdHJ1Y3RvciA9IGNvbnN0cnVjdG9yOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4dGVuZCQ1KHBhcmVudCwgZGVmaW5pdGlvbikgewogICAgICB2YXIgcHJvdG90eXBlID0gT2JqZWN0LmNyZWF0ZShwYXJlbnQucHJvdG90eXBlKTsKICAgICAgZm9yICh2YXIga2V5IGluIGRlZmluaXRpb24pIHByb3RvdHlwZVtrZXldID0gZGVmaW5pdGlvbltrZXldOwogICAgICByZXR1cm4gcHJvdG90eXBlOwogICAgfQoKICAgIGZ1bmN0aW9uIENvbG9yJDUoKSB7fQoKICAgIHZhciBkYXJrZXIkNSA9IDAuNzsKICAgIHZhciBicmlnaHRlciQ1ID0gMSAvIGRhcmtlciQ1OwoKICAgIHZhciByZUkkNSA9ICJcXHMqKFsrLV0/XFxkKylcXHMqIiwKICAgICAgICByZU4kNSA9ICJcXHMqKFsrLV0/XFxkKlxcLj9cXGQrKD86W2VFXVsrLV0/XFxkKyk/KVxccyoiLAogICAgICAgIHJlUCQ1ID0gIlxccyooWystXT9cXGQqXFwuP1xcZCsoPzpbZUVdWystXT9cXGQrKT8pJVxccyoiLAogICAgICAgIHJlSGV4JDQgPSAvXiMoWzAtOWEtZl17Myw4fSkkLywKICAgICAgICByZVJnYkludGVnZXIkNSA9IG5ldyBSZWdFeHAoIl5yZ2JcXCgiICsgW3JlSSQ1LCByZUkkNSwgcmVJJDVdICsgIlxcKSQiKSwKICAgICAgICByZVJnYlBlcmNlbnQkNSA9IG5ldyBSZWdFeHAoIl5yZ2JcXCgiICsgW3JlUCQ1LCByZVAkNSwgcmVQJDVdICsgIlxcKSQiKSwKICAgICAgICByZVJnYmFJbnRlZ2VyJDUgPSBuZXcgUmVnRXhwKCJecmdiYVxcKCIgKyBbcmVJJDUsIHJlSSQ1LCByZUkkNSwgcmVOJDVdICsgIlxcKSQiKSwKICAgICAgICByZVJnYmFQZXJjZW50JDUgPSBuZXcgUmVnRXhwKCJecmdiYVxcKCIgKyBbcmVQJDUsIHJlUCQ1LCByZVAkNSwgcmVOJDVdICsgIlxcKSQiKSwKICAgICAgICByZUhzbFBlcmNlbnQkNSA9IG5ldyBSZWdFeHAoIl5oc2xcXCgiICsgW3JlTiQ1LCByZVAkNSwgcmVQJDVdICsgIlxcKSQiKSwKICAgICAgICByZUhzbGFQZXJjZW50JDUgPSBuZXcgUmVnRXhwKCJeaHNsYVxcKCIgKyBbcmVOJDUsIHJlUCQ1LCByZVAkNSwgcmVOJDVdICsgIlxcKSQiKTsKCiAgICB2YXIgbmFtZWQkNSA9IHsKICAgICAgYWxpY2VibHVlOiAweGYwZjhmZiwKICAgICAgYW50aXF1ZXdoaXRlOiAweGZhZWJkNywKICAgICAgYXF1YTogMHgwMGZmZmYsCiAgICAgIGFxdWFtYXJpbmU6IDB4N2ZmZmQ0LAogICAgICBhenVyZTogMHhmMGZmZmYsCiAgICAgIGJlaWdlOiAweGY1ZjVkYywKICAgICAgYmlzcXVlOiAweGZmZTRjNCwKICAgICAgYmxhY2s6IDB4MDAwMDAwLAogICAgICBibGFuY2hlZGFsbW9uZDogMHhmZmViY2QsCiAgICAgIGJsdWU6IDB4MDAwMGZmLAogICAgICBibHVldmlvbGV0OiAweDhhMmJlMiwKICAgICAgYnJvd246IDB4YTUyYTJhLAogICAgICBidXJseXdvb2Q6IDB4ZGViODg3LAogICAgICBjYWRldGJsdWU6IDB4NWY5ZWEwLAogICAgICBjaGFydHJldXNlOiAweDdmZmYwMCwKICAgICAgY2hvY29sYXRlOiAweGQyNjkxZSwKICAgICAgY29yYWw6IDB4ZmY3ZjUwLAogICAgICBjb3JuZmxvd2VyYmx1ZTogMHg2NDk1ZWQsCiAgICAgIGNvcm5zaWxrOiAweGZmZjhkYywKICAgICAgY3JpbXNvbjogMHhkYzE0M2MsCiAgICAgIGN5YW46IDB4MDBmZmZmLAogICAgICBkYXJrYmx1ZTogMHgwMDAwOGIsCiAgICAgIGRhcmtjeWFuOiAweDAwOGI4YiwKICAgICAgZGFya2dvbGRlbnJvZDogMHhiODg2MGIsCiAgICAgIGRhcmtncmF5OiAweGE5YTlhOSwKICAgICAgZGFya2dyZWVuOiAweDAwNjQwMCwKICAgICAgZGFya2dyZXk6IDB4YTlhOWE5LAogICAgICBkYXJra2hha2k6IDB4YmRiNzZiLAogICAgICBkYXJrbWFnZW50YTogMHg4YjAwOGIsCiAgICAgIGRhcmtvbGl2ZWdyZWVuOiAweDU1NmIyZiwKICAgICAgZGFya29yYW5nZTogMHhmZjhjMDAsCiAgICAgIGRhcmtvcmNoaWQ6IDB4OTkzMmNjLAogICAgICBkYXJrcmVkOiAweDhiMDAwMCwKICAgICAgZGFya3NhbG1vbjogMHhlOTk2N2EsCiAgICAgIGRhcmtzZWFncmVlbjogMHg4ZmJjOGYsCiAgICAgIGRhcmtzbGF0ZWJsdWU6IDB4NDgzZDhiLAogICAgICBkYXJrc2xhdGVncmF5OiAweDJmNGY0ZiwKICAgICAgZGFya3NsYXRlZ3JleTogMHgyZjRmNGYsCiAgICAgIGRhcmt0dXJxdW9pc2U6IDB4MDBjZWQxLAogICAgICBkYXJrdmlvbGV0OiAweDk0MDBkMywKICAgICAgZGVlcHBpbms6IDB4ZmYxNDkzLAogICAgICBkZWVwc2t5Ymx1ZTogMHgwMGJmZmYsCiAgICAgIGRpbWdyYXk6IDB4Njk2OTY5LAogICAgICBkaW1ncmV5OiAweDY5Njk2OSwKICAgICAgZG9kZ2VyYmx1ZTogMHgxZTkwZmYsCiAgICAgIGZpcmVicmljazogMHhiMjIyMjIsCiAgICAgIGZsb3JhbHdoaXRlOiAweGZmZmFmMCwKICAgICAgZm9yZXN0Z3JlZW46IDB4MjI4YjIyLAogICAgICBmdWNoc2lhOiAweGZmMDBmZiwKICAgICAgZ2FpbnNib3JvOiAweGRjZGNkYywKICAgICAgZ2hvc3R3aGl0ZTogMHhmOGY4ZmYsCiAgICAgIGdvbGQ6IDB4ZmZkNzAwLAogICAgICBnb2xkZW5yb2Q6IDB4ZGFhNTIwLAogICAgICBncmF5OiAweDgwODA4MCwKICAgICAgZ3JlZW46IDB4MDA4MDAwLAogICAgICBncmVlbnllbGxvdzogMHhhZGZmMmYsCiAgICAgIGdyZXk6IDB4ODA4MDgwLAogICAgICBob25leWRldzogMHhmMGZmZjAsCiAgICAgIGhvdHBpbms6IDB4ZmY2OWI0LAogICAgICBpbmRpYW5yZWQ6IDB4Y2Q1YzVjLAogICAgICBpbmRpZ286IDB4NGIwMDgyLAogICAgICBpdm9yeTogMHhmZmZmZjAsCiAgICAgIGtoYWtpOiAweGYwZTY4YywKICAgICAgbGF2ZW5kZXI6IDB4ZTZlNmZhLAogICAgICBsYXZlbmRlcmJsdXNoOiAweGZmZjBmNSwKICAgICAgbGF3bmdyZWVuOiAweDdjZmMwMCwKICAgICAgbGVtb25jaGlmZm9uOiAweGZmZmFjZCwKICAgICAgbGlnaHRibHVlOiAweGFkZDhlNiwKICAgICAgbGlnaHRjb3JhbDogMHhmMDgwODAsCiAgICAgIGxpZ2h0Y3lhbjogMHhlMGZmZmYsCiAgICAgIGxpZ2h0Z29sZGVucm9keWVsbG93OiAweGZhZmFkMiwKICAgICAgbGlnaHRncmF5OiAweGQzZDNkMywKICAgICAgbGlnaHRncmVlbjogMHg5MGVlOTAsCiAgICAgIGxpZ2h0Z3JleTogMHhkM2QzZDMsCiAgICAgIGxpZ2h0cGluazogMHhmZmI2YzEsCiAgICAgIGxpZ2h0c2FsbW9uOiAweGZmYTA3YSwKICAgICAgbGlnaHRzZWFncmVlbjogMHgyMGIyYWEsCiAgICAgIGxpZ2h0c2t5Ymx1ZTogMHg4N2NlZmEsCiAgICAgIGxpZ2h0c2xhdGVncmF5OiAweDc3ODg5OSwKICAgICAgbGlnaHRzbGF0ZWdyZXk6IDB4Nzc4ODk5LAogICAgICBsaWdodHN0ZWVsYmx1ZTogMHhiMGM0ZGUsCiAgICAgIGxpZ2h0eWVsbG93OiAweGZmZmZlMCwKICAgICAgbGltZTogMHgwMGZmMDAsCiAgICAgIGxpbWVncmVlbjogMHgzMmNkMzIsCiAgICAgIGxpbmVuOiAweGZhZjBlNiwKICAgICAgbWFnZW50YTogMHhmZjAwZmYsCiAgICAgIG1hcm9vbjogMHg4MDAwMDAsCiAgICAgIG1lZGl1bWFxdWFtYXJpbmU6IDB4NjZjZGFhLAogICAgICBtZWRpdW1ibHVlOiAweDAwMDBjZCwKICAgICAgbWVkaXVtb3JjaGlkOiAweGJhNTVkMywKICAgICAgbWVkaXVtcHVycGxlOiAweDkzNzBkYiwKICAgICAgbWVkaXVtc2VhZ3JlZW46IDB4M2NiMzcxLAogICAgICBtZWRpdW1zbGF0ZWJsdWU6IDB4N2I2OGVlLAogICAgICBtZWRpdW1zcHJpbmdncmVlbjogMHgwMGZhOWEsCiAgICAgIG1lZGl1bXR1cnF1b2lzZTogMHg0OGQxY2MsCiAgICAgIG1lZGl1bXZpb2xldHJlZDogMHhjNzE1ODUsCiAgICAgIG1pZG5pZ2h0Ymx1ZTogMHgxOTE5NzAsCiAgICAgIG1pbnRjcmVhbTogMHhmNWZmZmEsCiAgICAgIG1pc3R5cm9zZTogMHhmZmU0ZTEsCiAgICAgIG1vY2Nhc2luOiAweGZmZTRiNSwKICAgICAgbmF2YWpvd2hpdGU6IDB4ZmZkZWFkLAogICAgICBuYXZ5OiAweDAwMDA4MCwKICAgICAgb2xkbGFjZTogMHhmZGY1ZTYsCiAgICAgIG9saXZlOiAweDgwODAwMCwKICAgICAgb2xpdmVkcmFiOiAweDZiOGUyMywKICAgICAgb3JhbmdlOiAweGZmYTUwMCwKICAgICAgb3JhbmdlcmVkOiAweGZmNDUwMCwKICAgICAgb3JjaGlkOiAweGRhNzBkNiwKICAgICAgcGFsZWdvbGRlbnJvZDogMHhlZWU4YWEsCiAgICAgIHBhbGVncmVlbjogMHg5OGZiOTgsCiAgICAgIHBhbGV0dXJxdW9pc2U6IDB4YWZlZWVlLAogICAgICBwYWxldmlvbGV0cmVkOiAweGRiNzA5MywKICAgICAgcGFwYXlhd2hpcDogMHhmZmVmZDUsCiAgICAgIHBlYWNocHVmZjogMHhmZmRhYjksCiAgICAgIHBlcnU6IDB4Y2Q4NTNmLAogICAgICBwaW5rOiAweGZmYzBjYiwKICAgICAgcGx1bTogMHhkZGEwZGQsCiAgICAgIHBvd2RlcmJsdWU6IDB4YjBlMGU2LAogICAgICBwdXJwbGU6IDB4ODAwMDgwLAogICAgICByZWJlY2NhcHVycGxlOiAweDY2MzM5OSwKICAgICAgcmVkOiAweGZmMDAwMCwKICAgICAgcm9zeWJyb3duOiAweGJjOGY4ZiwKICAgICAgcm95YWxibHVlOiAweDQxNjllMSwKICAgICAgc2FkZGxlYnJvd246IDB4OGI0NTEzLAogICAgICBzYWxtb246IDB4ZmE4MDcyLAogICAgICBzYW5keWJyb3duOiAweGY0YTQ2MCwKICAgICAgc2VhZ3JlZW46IDB4MmU4YjU3LAogICAgICBzZWFzaGVsbDogMHhmZmY1ZWUsCiAgICAgIHNpZW5uYTogMHhhMDUyMmQsCiAgICAgIHNpbHZlcjogMHhjMGMwYzAsCiAgICAgIHNreWJsdWU6IDB4ODdjZWViLAogICAgICBzbGF0ZWJsdWU6IDB4NmE1YWNkLAogICAgICBzbGF0ZWdyYXk6IDB4NzA4MDkwLAogICAgICBzbGF0ZWdyZXk6IDB4NzA4MDkwLAogICAgICBzbm93OiAweGZmZmFmYSwKICAgICAgc3ByaW5nZ3JlZW46IDB4MDBmZjdmLAogICAgICBzdGVlbGJsdWU6IDB4NDY4MmI0LAogICAgICB0YW46IDB4ZDJiNDhjLAogICAgICB0ZWFsOiAweDAwODA4MCwKICAgICAgdGhpc3RsZTogMHhkOGJmZDgsCiAgICAgIHRvbWF0bzogMHhmZjYzNDcsCiAgICAgIHR1cnF1b2lzZTogMHg0MGUwZDAsCiAgICAgIHZpb2xldDogMHhlZTgyZWUsCiAgICAgIHdoZWF0OiAweGY1ZGViMywKICAgICAgd2hpdGU6IDB4ZmZmZmZmLAogICAgICB3aGl0ZXNtb2tlOiAweGY1ZjVmNSwKICAgICAgeWVsbG93OiAweGZmZmYwMCwKICAgICAgeWVsbG93Z3JlZW46IDB4OWFjZDMyCiAgICB9OwoKICAgIGRlZmluZSQ1KENvbG9yJDUsIGNvbG9yJDUsIHsKICAgICAgY29weTogZnVuY3Rpb24oY2hhbm5lbHMpIHsKICAgICAgICByZXR1cm4gT2JqZWN0LmFzc2lnbihuZXcgdGhpcy5jb25zdHJ1Y3RvciwgdGhpcywgY2hhbm5lbHMpOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZGlzcGxheWFibGUoKTsKICAgICAgfSwKICAgICAgaGV4OiBjb2xvcl9mb3JtYXRIZXgkNCwgLy8gRGVwcmVjYXRlZCEgVXNlIGNvbG9yLmZvcm1hdEhleC4KICAgICAgZm9ybWF0SGV4OiBjb2xvcl9mb3JtYXRIZXgkNCwKICAgICAgZm9ybWF0SHNsOiBjb2xvcl9mb3JtYXRIc2wkNCwKICAgICAgZm9ybWF0UmdiOiBjb2xvcl9mb3JtYXRSZ2IkNCwKICAgICAgdG9TdHJpbmc6IGNvbG9yX2Zvcm1hdFJnYiQ0CiAgICB9KTsKCiAgICBmdW5jdGlvbiBjb2xvcl9mb3JtYXRIZXgkNCgpIHsKICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZm9ybWF0SGV4KCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0SHNsJDQoKSB7CiAgICAgIHJldHVybiBoc2xDb252ZXJ0JDUodGhpcykuZm9ybWF0SHNsKCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3JfZm9ybWF0UmdiJDQoKSB7CiAgICAgIHJldHVybiB0aGlzLnJnYigpLmZvcm1hdFJnYigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbG9yJDUoZm9ybWF0KSB7CiAgICAgIHZhciBtLCBsOwogICAgICBmb3JtYXQgPSAoZm9ybWF0ICsgIiIpLnRyaW0oKS50b0xvd2VyQ2FzZSgpOwogICAgICByZXR1cm4gKG0gPSByZUhleCQ0LmV4ZWMoZm9ybWF0KSkgPyAobCA9IG1bMV0ubGVuZ3RoLCBtID0gcGFyc2VJbnQobVsxXSwgMTYpLCBsID09PSA2ID8gcmdibiQ1KG0pIC8vICNmZjAwMDAKICAgICAgICAgIDogbCA9PT0gMyA/IG5ldyBSZ2IkNSgobSA+PiA4ICYgMHhmKSB8IChtID4+IDQgJiAweGYwKSwgKG0gPj4gNCAmIDB4ZikgfCAobSAmIDB4ZjApLCAoKG0gJiAweGYpIDw8IDQpIHwgKG0gJiAweGYpLCAxKSAvLyAjZjAwCiAgICAgICAgICA6IGwgPT09IDggPyByZ2JhJDUobSA+PiAyNCAmIDB4ZmYsIG0gPj4gMTYgJiAweGZmLCBtID4+IDggJiAweGZmLCAobSAmIDB4ZmYpIC8gMHhmZikgLy8gI2ZmMDAwMDAwCiAgICAgICAgICA6IGwgPT09IDQgPyByZ2JhJDUoKG0gPj4gMTIgJiAweGYpIHwgKG0gPj4gOCAmIDB4ZjApLCAobSA+PiA4ICYgMHhmKSB8IChtID4+IDQgJiAweGYwKSwgKG0gPj4gNCAmIDB4ZikgfCAobSAmIDB4ZjApLCAoKChtICYgMHhmKSA8PCA0KSB8IChtICYgMHhmKSkgLyAweGZmKSAvLyAjZjAwMAogICAgICAgICAgOiBudWxsKSAvLyBpbnZhbGlkIGhleAogICAgICAgICAgOiAobSA9IHJlUmdiSW50ZWdlciQ1LmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiJDUobVsxXSwgbVsyXSwgbVszXSwgMSkgLy8gcmdiKDI1NSwgMCwgMCkKICAgICAgICAgIDogKG0gPSByZVJnYlBlcmNlbnQkNS5leGVjKGZvcm1hdCkpID8gbmV3IFJnYiQ1KG1bMV0gKiAyNTUgLyAxMDAsIG1bMl0gKiAyNTUgLyAxMDAsIG1bM10gKiAyNTUgLyAxMDAsIDEpIC8vIHJnYigxMDAlLCAwJSwgMCUpCiAgICAgICAgICA6IChtID0gcmVSZ2JhSW50ZWdlciQ1LmV4ZWMoZm9ybWF0KSkgPyByZ2JhJDUobVsxXSwgbVsyXSwgbVszXSwgbVs0XSkgLy8gcmdiYSgyNTUsIDAsIDAsIDEpCiAgICAgICAgICA6IChtID0gcmVSZ2JhUGVyY2VudCQ1LmV4ZWMoZm9ybWF0KSkgPyByZ2JhJDUobVsxXSAqIDI1NSAvIDEwMCwgbVsyXSAqIDI1NSAvIDEwMCwgbVszXSAqIDI1NSAvIDEwMCwgbVs0XSkgLy8gcmdiKDEwMCUsIDAlLCAwJSwgMSkKICAgICAgICAgIDogKG0gPSByZUhzbFBlcmNlbnQkNS5leGVjKGZvcm1hdCkpID8gaHNsYSQ1KG1bMV0sIG1bMl0gLyAxMDAsIG1bM10gLyAxMDAsIDEpIC8vIGhzbCgxMjAsIDUwJSwgNTAlKQogICAgICAgICAgOiAobSA9IHJlSHNsYVBlcmNlbnQkNS5leGVjKGZvcm1hdCkpID8gaHNsYSQ1KG1bMV0sIG1bMl0gLyAxMDAsIG1bM10gLyAxMDAsIG1bNF0pIC8vIGhzbGEoMTIwLCA1MCUsIDUwJSwgMSkKICAgICAgICAgIDogbmFtZWQkNS5oYXNPd25Qcm9wZXJ0eShmb3JtYXQpID8gcmdibiQ1KG5hbWVkJDVbZm9ybWF0XSkgLy8gZXNsaW50LWRpc2FibGUtbGluZSBuby1wcm90b3R5cGUtYnVpbHRpbnMKICAgICAgICAgIDogZm9ybWF0ID09PSAidHJhbnNwYXJlbnQiID8gbmV3IFJnYiQ1KE5hTiwgTmFOLCBOYU4sIDApCiAgICAgICAgICA6IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gcmdibiQ1KG4pIHsKICAgICAgcmV0dXJuIG5ldyBSZ2IkNShuID4+IDE2ICYgMHhmZiwgbiA+PiA4ICYgMHhmZiwgbiAmIDB4ZmYsIDEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYmEkNShyLCBnLCBiLCBhKSB7CiAgICAgIGlmIChhIDw9IDApIHIgPSBnID0gYiA9IE5hTjsKICAgICAgcmV0dXJuIG5ldyBSZ2IkNShyLCBnLCBiLCBhKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JDb252ZXJ0JDUobykgewogICAgICBpZiAoIShvIGluc3RhbmNlb2YgQ29sb3IkNSkpIG8gPSBjb2xvciQ1KG8pOwogICAgICBpZiAoIW8pIHJldHVybiBuZXcgUmdiJDU7CiAgICAgIG8gPSBvLnJnYigpOwogICAgICByZXR1cm4gbmV3IFJnYiQ1KG8uciwgby5nLCBvLmIsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiJDcociwgZywgYiwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IHJnYkNvbnZlcnQkNShyKSA6IG5ldyBSZ2IkNShyLCBnLCBiLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gUmdiJDUociwgZywgYiwgb3BhY2l0eSkgewogICAgICB0aGlzLnIgPSArcjsKICAgICAgdGhpcy5nID0gK2c7CiAgICAgIHRoaXMuYiA9ICtiOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkNShSZ2IkNSwgcmdiJDcsIGV4dGVuZCQ1KENvbG9yJDUsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIkNSA6IE1hdGgucG93KGJyaWdodGVyJDUsIGspOwogICAgICAgIHJldHVybiBuZXcgUmdiJDUodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciQ1IDogTWF0aC5wb3coZGFya2VyJDUsIGspOwogICAgICAgIHJldHVybiBuZXcgUmdiJDUodGhpcy5yICogaywgdGhpcy5nICogaywgdGhpcy5iICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgcmdiOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfSwKICAgICAgZGlzcGxheWFibGU6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAoLTAuNSA8PSB0aGlzLnIgJiYgdGhpcy5yIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgtMC41IDw9IHRoaXMuZyAmJiB0aGlzLmcgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKC0wLjUgPD0gdGhpcy5iICYmIHRoaXMuYiA8IDI1NS41KQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLm9wYWNpdHkgJiYgdGhpcy5vcGFjaXR5IDw9IDEpOwogICAgICB9LAogICAgICBoZXg6IHJnYl9mb3JtYXRIZXgkNCwgLy8gRGVwcmVjYXRlZCEgVXNlIGNvbG9yLmZvcm1hdEhleC4KICAgICAgZm9ybWF0SGV4OiByZ2JfZm9ybWF0SGV4JDQsCiAgICAgIGZvcm1hdFJnYjogcmdiX2Zvcm1hdFJnYiQ0LAogICAgICB0b1N0cmluZzogcmdiX2Zvcm1hdFJnYiQ0CiAgICB9KSk7CgogICAgZnVuY3Rpb24gcmdiX2Zvcm1hdEhleCQ0KCkgewogICAgICByZXR1cm4gIiMiICsgaGV4JDQodGhpcy5yKSArIGhleCQ0KHRoaXMuZykgKyBoZXgkNCh0aGlzLmIpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYl9mb3JtYXRSZ2IkNCgpIHsKICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgIHJldHVybiAoYSA9PT0gMSA/ICJyZ2IoIiA6ICJyZ2JhKCIpCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLnIpIHx8IDApKSArICIsICIKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMuZykgfHwgMCkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5iKSB8fCAwKSkKICAgICAgICAgICsgKGEgPT09IDEgPyAiKSIgOiAiLCAiICsgYSArICIpIik7CiAgICB9CgogICAgZnVuY3Rpb24gaGV4JDQodmFsdWUpIHsKICAgICAgdmFsdWUgPSBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodmFsdWUpIHx8IDApKTsKICAgICAgcmV0dXJuICh2YWx1ZSA8IDE2ID8gIjAiIDogIiIpICsgdmFsdWUudG9TdHJpbmcoMTYpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbGEkNShoLCBzLCBsLCBhKSB7CiAgICAgIGlmIChhIDw9IDApIGggPSBzID0gbCA9IE5hTjsKICAgICAgZWxzZSBpZiAobCA8PSAwIHx8IGwgPj0gMSkgaCA9IHMgPSBOYU47CiAgICAgIGVsc2UgaWYgKHMgPD0gMCkgaCA9IE5hTjsKICAgICAgcmV0dXJuIG5ldyBIc2wkNShoLCBzLCBsLCBhKTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2xDb252ZXJ0JDUobykgewogICAgICBpZiAobyBpbnN0YW5jZW9mIEhzbCQ1KSByZXR1cm4gbmV3IEhzbCQ1KG8uaCwgby5zLCBvLmwsIG8ub3BhY2l0eSk7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvciQ1KSkgbyA9IGNvbG9yJDUobyk7CiAgICAgIGlmICghbykgcmV0dXJuIG5ldyBIc2wkNTsKICAgICAgaWYgKG8gaW5zdGFuY2VvZiBIc2wkNSkgcmV0dXJuIG87CiAgICAgIG8gPSBvLnJnYigpOwogICAgICB2YXIgciA9IG8uciAvIDI1NSwKICAgICAgICAgIGcgPSBvLmcgLyAyNTUsCiAgICAgICAgICBiID0gby5iIC8gMjU1LAogICAgICAgICAgbWluID0gTWF0aC5taW4ociwgZywgYiksCiAgICAgICAgICBtYXggPSBNYXRoLm1heChyLCBnLCBiKSwKICAgICAgICAgIGggPSBOYU4sCiAgICAgICAgICBzID0gbWF4IC0gbWluLAogICAgICAgICAgbCA9IChtYXggKyBtaW4pIC8gMjsKICAgICAgaWYgKHMpIHsKICAgICAgICBpZiAociA9PT0gbWF4KSBoID0gKGcgLSBiKSAvIHMgKyAoZyA8IGIpICogNjsKICAgICAgICBlbHNlIGlmIChnID09PSBtYXgpIGggPSAoYiAtIHIpIC8gcyArIDI7CiAgICAgICAgZWxzZSBoID0gKHIgLSBnKSAvIHMgKyA0OwogICAgICAgIHMgLz0gbCA8IDAuNSA/IG1heCArIG1pbiA6IDIgLSBtYXggLSBtaW47CiAgICAgICAgaCAqPSA2MDsKICAgICAgfSBlbHNlIHsKICAgICAgICBzID0gbCA+IDAgJiYgbCA8IDEgPyAwIDogaDsKICAgICAgfQogICAgICByZXR1cm4gbmV3IEhzbCQ1KGgsIHMsIGwsIG8ub3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsJDkoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA9PT0gMSA/IGhzbENvbnZlcnQkNShoKSA6IG5ldyBIc2wkNShoLCBzLCBsLCBvcGFjaXR5ID09IG51bGwgPyAxIDogb3BhY2l0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gSHNsJDUoaCwgcywgbCwgb3BhY2l0eSkgewogICAgICB0aGlzLmggPSAraDsKICAgICAgdGhpcy5zID0gK3M7CiAgICAgIHRoaXMubCA9ICtsOwogICAgICB0aGlzLm9wYWNpdHkgPSArb3BhY2l0eTsKICAgIH0KCiAgICBkZWZpbmUkNShIc2wkNSwgaHNsJDksIGV4dGVuZCQ1KENvbG9yJDUsIHsKICAgICAgYnJpZ2h0ZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gYnJpZ2h0ZXIkNSA6IE1hdGgucG93KGJyaWdodGVyJDUsIGspOwogICAgICAgIHJldHVybiBuZXcgSHNsJDUodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIGRhcmtlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBkYXJrZXIkNSA6IE1hdGgucG93KGRhcmtlciQ1LCBrKTsKICAgICAgICByZXR1cm4gbmV3IEhzbCQ1KHRoaXMuaCwgdGhpcy5zLCB0aGlzLmwgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBoID0gdGhpcy5oICUgMzYwICsgKHRoaXMuaCA8IDApICogMzYwLAogICAgICAgICAgICBzID0gaXNOYU4oaCkgfHwgaXNOYU4odGhpcy5zKSA/IDAgOiB0aGlzLnMsCiAgICAgICAgICAgIGwgPSB0aGlzLmwsCiAgICAgICAgICAgIG0yID0gbCArIChsIDwgMC41ID8gbCA6IDEgLSBsKSAqIHMsCiAgICAgICAgICAgIG0xID0gMiAqIGwgLSBtMjsKICAgICAgICByZXR1cm4gbmV3IFJnYiQ1KAogICAgICAgICAgaHNsMnJnYiQ1KGggPj0gMjQwID8gaCAtIDI0MCA6IGggKyAxMjAsIG0xLCBtMiksCiAgICAgICAgICBoc2wycmdiJDUoaCwgbTEsIG0yKSwKICAgICAgICAgIGhzbDJyZ2IkNShoIDwgMTIwID8gaCArIDI0MCA6IGggLSAxMjAsIG0xLCBtMiksCiAgICAgICAgICB0aGlzLm9wYWNpdHkKICAgICAgICApOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuICgwIDw9IHRoaXMucyAmJiB0aGlzLnMgPD0gMSB8fCBpc05hTih0aGlzLnMpKQogICAgICAgICAgICAmJiAoMCA8PSB0aGlzLmwgJiYgdGhpcy5sIDw9IDEpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMub3BhY2l0eSAmJiB0aGlzLm9wYWNpdHkgPD0gMSk7CiAgICAgIH0sCiAgICAgIGZvcm1hdEhzbDogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGEgPSB0aGlzLm9wYWNpdHk7IGEgPSBpc05hTihhKSA/IDEgOiBNYXRoLm1heCgwLCBNYXRoLm1pbigxLCBhKSk7CiAgICAgICAgcmV0dXJuIChhID09PSAxID8gImhzbCgiIDogImhzbGEoIikKICAgICAgICAgICAgKyAodGhpcy5oIHx8IDApICsgIiwgIgogICAgICAgICAgICArICh0aGlzLnMgfHwgMCkgKiAxMDAgKyAiJSwgIgogICAgICAgICAgICArICh0aGlzLmwgfHwgMCkgKiAxMDAgKyAiJSIKICAgICAgICAgICAgKyAoYSA9PT0gMSA/ICIpIiA6ICIsICIgKyBhICsgIikiKTsKICAgICAgfQogICAgfSkpOwoKICAgIC8qIEZyb20gRnZEIDEzLjM3LCBDU1MgQ29sb3IgTW9kdWxlIExldmVsIDMgKi8KICAgIGZ1bmN0aW9uIGhzbDJyZ2IkNShoLCBtMSwgbTIpIHsKICAgICAgcmV0dXJuIChoIDwgNjAgPyBtMSArIChtMiAtIG0xKSAqIGggLyA2MAogICAgICAgICAgOiBoIDwgMTgwID8gbTIKICAgICAgICAgIDogaCA8IDI0MCA/IG0xICsgKG0yIC0gbTEpICogKDI0MCAtIGgpIC8gNjAKICAgICAgICAgIDogbTEpICogMjU1OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50JHUoeCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHg7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbGluZWFyJDgoYSwgZCkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBhICsgdCAqIGQ7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZXhwb25lbnRpYWwkNihhLCBiLCB5KSB7CiAgICAgIHJldHVybiBhID0gTWF0aC5wb3coYSwgeSksIGIgPSBNYXRoLnBvdyhiLCB5KSAtIGEsIHkgPSAxIC8geSwgZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBNYXRoLnBvdyhhICsgdCAqIGIsIHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGdhbW1hJDQoeSkgewogICAgICByZXR1cm4gKHkgPSAreSkgPT09IDEgPyBub2dhbW1hJDQgOiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgcmV0dXJuIGIgLSBhID8gZXhwb25lbnRpYWwkNihhLCBiLCB5KSA6IGNvbnN0YW50JHUoaXNOYU4oYSkgPyBiIDogYSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gbm9nYW1tYSQ0KGEsIGIpIHsKICAgICAgdmFyIGQgPSBiIC0gYTsKICAgICAgcmV0dXJuIGQgPyBsaW5lYXIkOChhLCBkKSA6IGNvbnN0YW50JHUoaXNOYU4oYSkgPyBiIDogYSk7CiAgICB9CgogICAgdmFyIGludGVycG9sYXRlUmdiJDIgPSAoZnVuY3Rpb24gcmdiR2FtbWEoeSkgewogICAgICB2YXIgY29sb3IgPSBnYW1tYSQ0KHkpOwoKICAgICAgZnVuY3Rpb24gcmdiKHN0YXJ0LCBlbmQpIHsKICAgICAgICB2YXIgciA9IGNvbG9yKChzdGFydCA9IHJnYiQ3KHN0YXJ0KSkuciwgKGVuZCA9IHJnYiQ3KGVuZCkpLnIpLAogICAgICAgICAgICBnID0gY29sb3Ioc3RhcnQuZywgZW5kLmcpLAogICAgICAgICAgICBiID0gY29sb3Ioc3RhcnQuYiwgZW5kLmIpLAogICAgICAgICAgICBvcGFjaXR5ID0gbm9nYW1tYSQ0KHN0YXJ0Lm9wYWNpdHksIGVuZC5vcGFjaXR5KTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgc3RhcnQuciA9IHIodCk7CiAgICAgICAgICBzdGFydC5nID0gZyh0KTsKICAgICAgICAgIHN0YXJ0LmIgPSBiKHQpOwogICAgICAgICAgc3RhcnQub3BhY2l0eSA9IG9wYWNpdHkodCk7CiAgICAgICAgICByZXR1cm4gc3RhcnQgKyAiIjsKICAgICAgICB9OwogICAgICB9CgogICAgICByZ2IuZ2FtbWEgPSByZ2JHYW1tYTsKCiAgICAgIHJldHVybiByZ2I7CiAgICB9KSgxKTsKCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZU51bWJlciQyKGEsIGIpIHsKICAgICAgcmV0dXJuIGEgPSArYSwgYiA9ICtiLCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGEgKiAoMSAtIHQpICsgYiAqIHQ7CiAgICAgIH07CiAgICB9CgogICAgdmFyIHJlQSQ0ID0gL1stK10/KD86XGQrXC4/XGQqfFwuP1xkKykoPzpbZUVdWy0rXT9cZCspPy9nLAogICAgICAgIHJlQiQ0ID0gbmV3IFJlZ0V4cChyZUEkNC5zb3VyY2UsICJnIik7CgogICAgZnVuY3Rpb24gemVybyQ0KGIpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBiOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9uZSQ0KGIpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHQpIHsKICAgICAgICByZXR1cm4gYih0KSArICIiOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlU3RyaW5nJDIoYSwgYikgewogICAgICB2YXIgYmkgPSByZUEkNC5sYXN0SW5kZXggPSByZUIkNC5sYXN0SW5kZXggPSAwLCAvLyBzY2FuIGluZGV4IGZvciBuZXh0IG51bWJlciBpbiBiCiAgICAgICAgICBhbSwgLy8gY3VycmVudCBtYXRjaCBpbiBhCiAgICAgICAgICBibSwgLy8gY3VycmVudCBtYXRjaCBpbiBiCiAgICAgICAgICBicywgLy8gc3RyaW5nIHByZWNlZGluZyBjdXJyZW50IG51bWJlciBpbiBiLCBpZiBhbnkKICAgICAgICAgIGkgPSAtMSwgLy8gaW5kZXggaW4gcwogICAgICAgICAgcyA9IFtdLCAvLyBzdHJpbmcgY29uc3RhbnRzIGFuZCBwbGFjZWhvbGRlcnMKICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKCiAgICAgIC8vIENvZXJjZSBpbnB1dHMgdG8gc3RyaW5ncy4KICAgICAgYSA9IGEgKyAiIiwgYiA9IGIgKyAiIjsKCiAgICAgIC8vIEludGVycG9sYXRlIHBhaXJzIG9mIG51bWJlcnMgaW4gYSAmIGIuCiAgICAgIHdoaWxlICgoYW0gPSByZUEkNC5leGVjKGEpKQogICAgICAgICAgJiYgKGJtID0gcmVCJDQuZXhlYyhiKSkpIHsKICAgICAgICBpZiAoKGJzID0gYm0uaW5kZXgpID4gYmkpIHsgLy8gYSBzdHJpbmcgcHJlY2VkZXMgdGhlIG5leHQgbnVtYmVyIGluIGIKICAgICAgICAgIGJzID0gYi5zbGljZShiaSwgYnMpOwogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYnM7IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICAgIH0KICAgICAgICBpZiAoKGFtID0gYW1bMF0pID09PSAoYm0gPSBibVswXSkpIHsgLy8gbnVtYmVycyBpbiBhICYgYiBtYXRjaAogICAgICAgICAgaWYgKHNbaV0pIHNbaV0gKz0gYm07IC8vIGNvYWxlc2NlIHdpdGggcHJldmlvdXMgc3RyaW5nCiAgICAgICAgICBlbHNlIHNbKytpXSA9IGJtOwogICAgICAgIH0gZWxzZSB7IC8vIGludGVycG9sYXRlIG5vbi1tYXRjaGluZyBudW1iZXJzCiAgICAgICAgICBzWysraV0gPSBudWxsOwogICAgICAgICAgcS5wdXNoKHtpOiBpLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQyKGFtLCBibSl9KTsKICAgICAgICB9CiAgICAgICAgYmkgPSByZUIkNC5sYXN0SW5kZXg7CiAgICAgIH0KCiAgICAgIC8vIEFkZCByZW1haW5zIG9mIGIuCiAgICAgIGlmIChiaSA8IGIubGVuZ3RoKSB7CiAgICAgICAgYnMgPSBiLnNsaWNlKGJpKTsKICAgICAgICBpZiAoc1tpXSkgc1tpXSArPSBiczsgLy8gY29hbGVzY2Ugd2l0aCBwcmV2aW91cyBzdHJpbmcKICAgICAgICBlbHNlIHNbKytpXSA9IGJzOwogICAgICB9CgogICAgICAvLyBTcGVjaWFsIG9wdGltaXphdGlvbiBmb3Igb25seSBhIHNpbmdsZSBtYXRjaC4KICAgICAgLy8gT3RoZXJ3aXNlLCBpbnRlcnBvbGF0ZSBlYWNoIG9mIHRoZSBudW1iZXJzIGFuZCByZWpvaW4gdGhlIHN0cmluZy4KICAgICAgcmV0dXJuIHMubGVuZ3RoIDwgMiA/IChxWzBdCiAgICAgICAgICA/IG9uZSQ0KHFbMF0ueCkKICAgICAgICAgIDogemVybyQ0KGIpKQogICAgICAgICAgOiAoYiA9IHEubGVuZ3RoLCBmdW5jdGlvbih0KSB7CiAgICAgICAgICAgICAgZm9yICh2YXIgaSA9IDAsIG87IGkgPCBiOyArK2kpIHNbKG8gPSBxW2ldKS5pXSA9IG8ueCh0KTsKICAgICAgICAgICAgICByZXR1cm4gcy5qb2luKCIiKTsKICAgICAgICAgICAgfSk7CiAgICB9CgogICAgdmFyIGRlZ3JlZXMkNSA9IDE4MCAvIE1hdGguUEk7CgogICAgdmFyIGlkZW50aXR5JGsgPSB7CiAgICAgIHRyYW5zbGF0ZVg6IDAsCiAgICAgIHRyYW5zbGF0ZVk6IDAsCiAgICAgIHJvdGF0ZTogMCwKICAgICAgc2tld1g6IDAsCiAgICAgIHNjYWxlWDogMSwKICAgICAgc2NhbGVZOiAxCiAgICB9OwoKICAgIGZ1bmN0aW9uIGRlY29tcG9zZSQzKGEsIGIsIGMsIGQsIGUsIGYpIHsKICAgICAgdmFyIHNjYWxlWCwgc2NhbGVZLCBza2V3WDsKICAgICAgaWYgKHNjYWxlWCA9IE1hdGguc3FydChhICogYSArIGIgKiBiKSkgYSAvPSBzY2FsZVgsIGIgLz0gc2NhbGVYOwogICAgICBpZiAoc2tld1ggPSBhICogYyArIGIgKiBkKSBjIC09IGEgKiBza2V3WCwgZCAtPSBiICogc2tld1g7CiAgICAgIGlmIChzY2FsZVkgPSBNYXRoLnNxcnQoYyAqIGMgKyBkICogZCkpIGMgLz0gc2NhbGVZLCBkIC89IHNjYWxlWSwgc2tld1ggLz0gc2NhbGVZOwogICAgICBpZiAoYSAqIGQgPCBiICogYykgYSA9IC1hLCBiID0gLWIsIHNrZXdYID0gLXNrZXdYLCBzY2FsZVggPSAtc2NhbGVYOwogICAgICByZXR1cm4gewogICAgICAgIHRyYW5zbGF0ZVg6IGUsCiAgICAgICAgdHJhbnNsYXRlWTogZiwKICAgICAgICByb3RhdGU6IE1hdGguYXRhbjIoYiwgYSkgKiBkZWdyZWVzJDUsCiAgICAgICAgc2tld1g6IE1hdGguYXRhbihza2V3WCkgKiBkZWdyZWVzJDUsCiAgICAgICAgc2NhbGVYOiBzY2FsZVgsCiAgICAgICAgc2NhbGVZOiBzY2FsZVkKICAgICAgfTsKICAgIH0KCiAgICB2YXIgY3NzTm9kZSQzLAogICAgICAgIGNzc1Jvb3QkMywKICAgICAgICBjc3NWaWV3JDMsCiAgICAgICAgc3ZnTm9kZSQzOwoKICAgIGZ1bmN0aW9uIHBhcnNlQ3NzJDQodmFsdWUpIHsKICAgICAgaWYgKHZhbHVlID09PSAibm9uZSIpIHJldHVybiBpZGVudGl0eSRrOwogICAgICBpZiAoIWNzc05vZGUkMykgY3NzTm9kZSQzID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgiRElWIiksIGNzc1Jvb3QkMyA9IGRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwgY3NzVmlldyQzID0gZG9jdW1lbnQuZGVmYXVsdFZpZXc7CiAgICAgIGNzc05vZGUkMy5zdHlsZS50cmFuc2Zvcm0gPSB2YWx1ZTsKICAgICAgdmFsdWUgPSBjc3NWaWV3JDMuZ2V0Q29tcHV0ZWRTdHlsZShjc3NSb290JDMuYXBwZW5kQ2hpbGQoY3NzTm9kZSQzKSwgbnVsbCkuZ2V0UHJvcGVydHlWYWx1ZSgidHJhbnNmb3JtIik7CiAgICAgIGNzc1Jvb3QkMy5yZW1vdmVDaGlsZChjc3NOb2RlJDMpOwogICAgICB2YWx1ZSA9IHZhbHVlLnNsaWNlKDcsIC0xKS5zcGxpdCgiLCIpOwogICAgICByZXR1cm4gZGVjb21wb3NlJDMoK3ZhbHVlWzBdLCArdmFsdWVbMV0sICt2YWx1ZVsyXSwgK3ZhbHVlWzNdLCArdmFsdWVbNF0sICt2YWx1ZVs1XSk7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VTdmckMyh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIGlkZW50aXR5JGs7CiAgICAgIGlmICghc3ZnTm9kZSQzKSBzdmdOb2RlJDMgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiwgImciKTsKICAgICAgc3ZnTm9kZSQzLnNldEF0dHJpYnV0ZSgidHJhbnNmb3JtIiwgdmFsdWUpOwogICAgICBpZiAoISh2YWx1ZSA9IHN2Z05vZGUkMy50cmFuc2Zvcm0uYmFzZVZhbC5jb25zb2xpZGF0ZSgpKSkgcmV0dXJuIGlkZW50aXR5JGs7CiAgICAgIHZhbHVlID0gdmFsdWUubWF0cml4OwogICAgICByZXR1cm4gZGVjb21wb3NlJDModmFsdWUuYSwgdmFsdWUuYiwgdmFsdWUuYywgdmFsdWUuZCwgdmFsdWUuZSwgdmFsdWUuZik7CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGVUcmFuc2Zvcm0kMyhwYXJzZSwgcHhDb21tYSwgcHhQYXJlbiwgZGVnUGFyZW4pIHsKCiAgICAgIGZ1bmN0aW9uIHBvcChzKSB7CiAgICAgICAgcmV0dXJuIHMubGVuZ3RoID8gcy5wb3AoKSArICIgIiA6ICIiOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2xhdGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2goInRyYW5zbGF0ZSgiLCBudWxsLCBweENvbW1hLCBudWxsLCBweFBhcmVuKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IGludGVycG9sYXRlTnVtYmVyJDIoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMih5YSwgeWIpfSk7CiAgICAgICAgfSBlbHNlIGlmICh4YiB8fCB5YikgewogICAgICAgICAgcy5wdXNoKCJ0cmFuc2xhdGUoIiArIHhiICsgcHhDb21tYSArIHliICsgcHhQYXJlbik7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiByb3RhdGUoYSwgYiwgcywgcSkgewogICAgICAgIGlmIChhICE9PSBiKSB7CiAgICAgICAgICBpZiAoYSAtIGIgPiAxODApIGIgKz0gMzYwOyBlbHNlIGlmIChiIC0gYSA+IDE4MCkgYSArPSAzNjA7IC8vIHNob3J0ZXN0IHBhdGgKICAgICAgICAgIHEucHVzaCh7aTogcy5wdXNoKHBvcChzKSArICJyb3RhdGUoIiwgbnVsbCwgZGVnUGFyZW4pIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMihhLCBiKX0pOwogICAgICAgIH0gZWxzZSBpZiAoYikgewogICAgICAgICAgcy5wdXNoKHBvcChzKSArICJyb3RhdGUoIiArIGIgKyBkZWdQYXJlbik7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBza2V3WChhLCBiLCBzLCBxKSB7CiAgICAgICAgaWYgKGEgIT09IGIpIHsKICAgICAgICAgIHEucHVzaCh7aTogcy5wdXNoKHBvcChzKSArICJza2V3WCgiLCBudWxsLCBkZWdQYXJlbikgLSAyLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQyKGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIgKyBiICsgZGVnUGFyZW4pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gc2NhbGUoeGEsIHlhLCB4YiwgeWIsIHMsIHEpIHsKICAgICAgICBpZiAoeGEgIT09IHhiIHx8IHlhICE9PSB5YikgewogICAgICAgICAgdmFyIGkgPSBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIsIG51bGwsICIsIiwgbnVsbCwgIikiKTsKICAgICAgICAgIHEucHVzaCh7aTogaSAtIDQsIHg6IGludGVycG9sYXRlTnVtYmVyJDIoeGEsIHhiKX0sIHtpOiBpIC0gMiwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMih5YSwgeWIpfSk7CiAgICAgICAgfSBlbHNlIGlmICh4YiAhPT0gMSB8fCB5YiAhPT0gMSkgewogICAgICAgICAgcy5wdXNoKHBvcChzKSArICJzY2FsZSgiICsgeGIgKyAiLCIgKyB5YiArICIpIik7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24oYSwgYikgewogICAgICAgIHZhciBzID0gW10sIC8vIHN0cmluZyBjb25zdGFudHMgYW5kIHBsYWNlaG9sZGVycwogICAgICAgICAgICBxID0gW107IC8vIG51bWJlciBpbnRlcnBvbGF0b3JzCiAgICAgICAgYSA9IHBhcnNlKGEpLCBiID0gcGFyc2UoYik7CiAgICAgICAgdHJhbnNsYXRlKGEudHJhbnNsYXRlWCwgYS50cmFuc2xhdGVZLCBiLnRyYW5zbGF0ZVgsIGIudHJhbnNsYXRlWSwgcywgcSk7CiAgICAgICAgcm90YXRlKGEucm90YXRlLCBiLnJvdGF0ZSwgcywgcSk7CiAgICAgICAgc2tld1goYS5za2V3WCwgYi5za2V3WCwgcywgcSk7CiAgICAgICAgc2NhbGUoYS5zY2FsZVgsIGEuc2NhbGVZLCBiLnNjYWxlWCwgYi5zY2FsZVksIHMsIHEpOwogICAgICAgIGEgPSBiID0gbnVsbDsgLy8gZ2MKICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgdmFyIGkgPSAtMSwgbiA9IHEubGVuZ3RoLCBvOwogICAgICAgICAgd2hpbGUgKCsraSA8IG4pIHNbKG8gPSBxW2ldKS5pXSA9IG8ueCh0KTsKICAgICAgICAgIHJldHVybiBzLmpvaW4oIiIpOwogICAgICAgIH07CiAgICAgIH07CiAgICB9CgogICAgdmFyIGludGVycG9sYXRlVHJhbnNmb3JtQ3NzJDMgPSBpbnRlcnBvbGF0ZVRyYW5zZm9ybSQzKHBhcnNlQ3NzJDQsICJweCwgIiwgInB4KSIsICJkZWcpIik7CiAgICB2YXIgaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmckMyA9IGludGVycG9sYXRlVHJhbnNmb3JtJDMocGFyc2VTdmckMywgIiwgIiwgIikiLCAiKSIpOwoKICAgIGZ1bmN0aW9uIHR3ZWVuUmVtb3ZlJDIoaWQsIG5hbWUpIHsKICAgICAgdmFyIHR3ZWVuMCwgdHdlZW4xOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JGQodGhpcywgaWQpLAogICAgICAgICAgICB0d2VlbiA9IHNjaGVkdWxlLnR3ZWVuOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIHR3ZWVuIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIHR3ZWVuIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmICh0d2VlbiAhPT0gdHdlZW4wKSB7CiAgICAgICAgICB0d2VlbjEgPSB0d2VlbjAgPSB0d2VlbjsKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHdlZW4xLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAodHdlZW4xW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgICB0d2VlbjEgPSB0d2VlbjEuc2xpY2UoKTsKICAgICAgICAgICAgICB0d2VlbjEuc3BsaWNlKGksIDEpOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBzY2hlZHVsZS50d2VlbiA9IHR3ZWVuMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0d2VlbkZ1bmN0aW9uJDIoaWQsIG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciB0d2VlbjAsIHR3ZWVuMTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JGQodGhpcywgaWQpLAogICAgICAgICAgICB0d2VlbiA9IHNjaGVkdWxlLnR3ZWVuOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIHR3ZWVuIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIHR3ZWVuIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmICh0d2VlbiAhPT0gdHdlZW4wKSB7CiAgICAgICAgICB0d2VlbjEgPSAodHdlZW4wID0gdHdlZW4pLnNsaWNlKCk7CiAgICAgICAgICBmb3IgKHZhciB0ID0ge25hbWU6IG5hbWUsIHZhbHVlOiB2YWx1ZX0sIGkgPSAwLCBuID0gdHdlZW4xLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAodHdlZW4xW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgICB0d2VlbjFbaV0gPSB0OwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaSA9PT0gbikgdHdlZW4xLnB1c2godCk7CiAgICAgICAgfQoKICAgICAgICBzY2hlZHVsZS50d2VlbiA9IHR3ZWVuMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3R3ZWVuJDIobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICBuYW1lICs9ICIiOwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIHR3ZWVuID0gZ2V0JDkodGhpcy5ub2RlKCksIGlkKS50d2VlbjsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR3ZWVuLmxlbmd0aCwgdDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKCh0ID0gdHdlZW5baV0pLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIHQudmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CgogICAgICByZXR1cm4gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsID8gdHdlZW5SZW1vdmUkMiA6IHR3ZWVuRnVuY3Rpb24kMikoaWQsIG5hbWUsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHdlZW5WYWx1ZSQyKHRyYW5zaXRpb24sIG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRyYW5zaXRpb24uX2lkOwoKICAgICAgdHJhbnNpdGlvbi5lYWNoKGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCRkKHRoaXMsIGlkKTsKICAgICAgICAoc2NoZWR1bGUudmFsdWUgfHwgKHNjaGVkdWxlLnZhbHVlID0ge30pKVtuYW1lXSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICByZXR1cm4gZ2V0JDkobm9kZSwgaWQpLnZhbHVlW25hbWVdOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlJDUoYSwgYikgewogICAgICB2YXIgYzsKICAgICAgcmV0dXJuICh0eXBlb2YgYiA9PT0gIm51bWJlciIgPyBpbnRlcnBvbGF0ZU51bWJlciQyCiAgICAgICAgICA6IGIgaW5zdGFuY2VvZiBjb2xvciQ1ID8gaW50ZXJwb2xhdGVSZ2IkMgogICAgICAgICAgOiAoYyA9IGNvbG9yJDUoYikpID8gKGIgPSBjLCBpbnRlcnBvbGF0ZVJnYiQyKQogICAgICAgICAgOiBpbnRlcnBvbGF0ZVN0cmluZyQyKShhLCBiKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlJDcobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZU5TJDcoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnQkNyhuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUxKSB7CiAgICAgIHZhciB2YWx1ZTAwLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHZhbHVlMCA9IHRoaXMuZ2V0QXR0cmlidXRlKG5hbWUpOwogICAgICAgIHJldHVybiB2YWx1ZTAgPT09IHZhbHVlMSA/IG51bGwKICAgICAgICAgICAgOiB2YWx1ZTAgPT09IHZhbHVlMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZSh2YWx1ZTAwID0gdmFsdWUwLCB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudE5TJDcoZnVsbG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZTEpIHsKICAgICAgdmFyIHZhbHVlMDAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUwID0gdGhpcy5nZXRBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICAgIHJldHVybiB2YWx1ZTAgPT09IHZhbHVlMSA/IG51bGwKICAgICAgICAgICAgOiB2YWx1ZTAgPT09IHZhbHVlMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZSh2YWx1ZTAwID0gdmFsdWUwLCB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbiQ3KG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZSkgewogICAgICB2YXIgdmFsdWUwMCwKICAgICAgICAgIHZhbHVlMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUwLCB2YWx1ZTEgPSB2YWx1ZSh0aGlzKTsKICAgICAgICBpZiAodmFsdWUxID09IG51bGwpIHJldHVybiB2b2lkIHRoaXMucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgIHZhbHVlMCA9IHRoaXMuZ2V0QXR0cmlidXRlKG5hbWUpOwogICAgICAgIHJldHVybiB2YWx1ZTAgPT09IHZhbHVlMSA/IG51bGwKICAgICAgICAgICAgOiB2YWx1ZTAgPT09IHZhbHVlMDAgJiYgdmFsdWUxID09PSB2YWx1ZTEwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUodmFsdWUwMCA9IHZhbHVlMCwgdmFsdWUxMCA9IHZhbHVlMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckZ1bmN0aW9uTlMkNyhmdWxsbmFtZSwgaW50ZXJwb2xhdGUsIHZhbHVlKSB7CiAgICAgIHZhciB2YWx1ZTAwLAogICAgICAgICAgdmFsdWUxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciB2YWx1ZTAsIHZhbHVlMSA9IHZhbHVlKHRoaXMpOwogICAgICAgIGlmICh2YWx1ZTEgPT0gbnVsbCkgcmV0dXJuIHZvaWQgdGhpcy5yZW1vdmVBdHRyaWJ1dGVOUyhmdWxsbmFtZS5zcGFjZSwgZnVsbG5hbWUubG9jYWwpOwogICAgICAgIHZhbHVlMCA9IHRoaXMuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICByZXR1cm4gdmFsdWUwID09PSB2YWx1ZTEgPyBudWxsCiAgICAgICAgICAgIDogdmFsdWUwID09PSB2YWx1ZTAwICYmIHZhbHVlMSA9PT0gdmFsdWUxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHZhbHVlMDAgPSB2YWx1ZTAsIHZhbHVlMTAgPSB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0ciQyKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQ0KG5hbWUpLCBpID0gZnVsbG5hbWUgPT09ICJ0cmFuc2Zvcm0iID8gaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmckMyA6IGludGVycG9sYXRlJDU7CiAgICAgIHJldHVybiB0aGlzLmF0dHJUd2VlbihuYW1lLCB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckZ1bmN0aW9uTlMkNyA6IGF0dHJGdW5jdGlvbiQ3KShmdWxsbmFtZSwgaSwgdHdlZW5WYWx1ZSQyKHRoaXMsICJhdHRyLiIgKyBuYW1lLCB2YWx1ZSkpCiAgICAgICAgICA6IHZhbHVlID09IG51bGwgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyUmVtb3ZlTlMkNyA6IGF0dHJSZW1vdmUkNykoZnVsbG5hbWUpCiAgICAgICAgICA6IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJDb25zdGFudE5TJDcgOiBhdHRyQ29uc3RhbnQkNykoZnVsbG5hbWUsIGksIHZhbHVlICsgIiIpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyVHdlZW5OUyQyKGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgbm9kZSA9IHRoaXMsIGkgPSB2YWx1ZS5hcHBseShub2RlLCBhcmd1bWVudHMpOwogICAgICAgIHJldHVybiBpICYmIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIG5vZGUuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCBpKHQpKTsKICAgICAgICB9OwogICAgICB9CiAgICAgIHR3ZWVuLl92YWx1ZSA9IHZhbHVlOwogICAgICByZXR1cm4gdHdlZW47CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clR3ZWVuJDIobmFtZSwgdmFsdWUpIHsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIG5vZGUgPSB0aGlzLCBpID0gdmFsdWUuYXBwbHkobm9kZSwgYXJndW1lbnRzKTsKICAgICAgICByZXR1cm4gaSAmJiBmdW5jdGlvbih0KSB7CiAgICAgICAgICBub2RlLnNldEF0dHJpYnV0ZShuYW1lLCBpKHQpKTsKICAgICAgICB9OwogICAgICB9CiAgICAgIHR3ZWVuLl92YWx1ZSA9IHZhbHVlOwogICAgICByZXR1cm4gdHdlZW47CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9hdHRyVHdlZW4kMihuYW1lLCB2YWx1ZSkgewogICAgICB2YXIga2V5ID0gImF0dHIuIiArIG5hbWU7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgcmV0dXJuIChrZXkgPSB0aGlzLnR3ZWVuKGtleSkpICYmIGtleS5fdmFsdWU7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gdGhpcy50d2VlbihrZXksIG51bGwpOwogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3I7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQ0KG5hbWUpOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIChmdWxsbmFtZS5sb2NhbCA/IGF0dHJUd2Vlbk5TJDIgOiBhdHRyVHdlZW4kMikoZnVsbG5hbWUsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gZGVsYXlGdW5jdGlvbiQyKGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgaW5pdCQyKHRoaXMsIGlkKS5kZWxheSA9ICt2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRlbGF5Q29uc3RhbnQkMihpZCwgdmFsdWUpIHsKICAgICAgcmV0dXJuIHZhbHVlID0gK3ZhbHVlLCBmdW5jdGlvbigpIHsKICAgICAgICBpbml0JDIodGhpcywgaWQpLmRlbGF5ID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9kZWxheSQyKHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRoaXMuX2lkOwoKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKCh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IGRlbGF5RnVuY3Rpb24kMgogICAgICAgICAgICAgIDogZGVsYXlDb25zdGFudCQyKShpZCwgdmFsdWUpKQogICAgICAgICAgOiBnZXQkOSh0aGlzLm5vZGUoKSwgaWQpLmRlbGF5OwogICAgfQoKICAgIGZ1bmN0aW9uIGR1cmF0aW9uRnVuY3Rpb24kMihpZCwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHNldCRkKHRoaXMsIGlkKS5kdXJhdGlvbiA9ICt2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGR1cmF0aW9uQ29uc3RhbnQkMihpZCwgdmFsdWUpIHsKICAgICAgcmV0dXJuIHZhbHVlID0gK3ZhbHVlLCBmdW5jdGlvbigpIHsKICAgICAgICBzZXQkZCh0aGlzLCBpZCkuZHVyYXRpb24gPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2R1cmF0aW9uJDIodmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gZHVyYXRpb25GdW5jdGlvbiQyCiAgICAgICAgICAgICAgOiBkdXJhdGlvbkNvbnN0YW50JDIpKGlkLCB2YWx1ZSkpCiAgICAgICAgICA6IGdldCQ5KHRoaXMubm9kZSgpLCBpZCkuZHVyYXRpb247CiAgICB9CgogICAgZnVuY3Rpb24gZWFzZUNvbnN0YW50JDIoaWQsIHZhbHVlKSB7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHNldCRkKHRoaXMsIGlkKS5lYXNlID0gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9lYXNlJDIodmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2goZWFzZUNvbnN0YW50JDIoaWQsIHZhbHVlKSkKICAgICAgICAgIDogZ2V0JDkodGhpcy5ub2RlKCksIGlkKS5lYXNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZmlsdGVyJDIobWF0Y2gpIHsKICAgICAgaWYgKHR5cGVvZiBtYXRjaCAhPT0gImZ1bmN0aW9uIikgbWF0Y2ggPSBtYXRjaGVyJDUobWF0Y2gpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IFtdLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIG1hdGNoLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKSB7CiAgICAgICAgICAgIHN1Ymdyb3VwLnB1c2gobm9kZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMihzdWJncm91cHMsIHRoaXMuX3BhcmVudHMsIHRoaXMuX25hbWUsIHRoaXMuX2lkKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX21lcmdlJDIodHJhbnNpdGlvbikgewogICAgICBpZiAodHJhbnNpdGlvbi5faWQgIT09IHRoaXMuX2lkKSB0aHJvdyBuZXcgRXJyb3I7CgogICAgICBmb3IgKHZhciBncm91cHMwID0gdGhpcy5fZ3JvdXBzLCBncm91cHMxID0gdHJhbnNpdGlvbi5fZ3JvdXBzLCBtMCA9IGdyb3VwczAubGVuZ3RoLCBtMSA9IGdyb3VwczEubGVuZ3RoLCBtID0gTWF0aC5taW4obTAsIG0xKSwgbWVyZ2VzID0gbmV3IEFycmF5KG0wKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cDAgPSBncm91cHMwW2pdLCBncm91cDEgPSBncm91cHMxW2pdLCBuID0gZ3JvdXAwLmxlbmd0aCwgbWVyZ2UgPSBtZXJnZXNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwMFtpXSB8fCBncm91cDFbaV0pIHsKICAgICAgICAgICAgbWVyZ2VbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yICg7IGogPCBtMDsgKytqKSB7CiAgICAgICAgbWVyZ2VzW2pdID0gZ3JvdXBzMFtqXTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDIobWVyZ2VzLCB0aGlzLl9wYXJlbnRzLCB0aGlzLl9uYW1lLCB0aGlzLl9pZCk7CiAgICB9CgogICAgZnVuY3Rpb24gc3RhcnQkMyhuYW1lKSB7CiAgICAgIHJldHVybiAobmFtZSArICIiKS50cmltKCkuc3BsaXQoL158XHMrLykuZXZlcnkoZnVuY3Rpb24odCkgewogICAgICAgIHZhciBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgdCA9IHQuc2xpY2UoMCwgaSk7CiAgICAgICAgcmV0dXJuICF0IHx8IHQgPT09ICJzdGFydCI7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIG9uRnVuY3Rpb24kMihpZCwgbmFtZSwgbGlzdGVuZXIpIHsKICAgICAgdmFyIG9uMCwgb24xLCBzaXQgPSBzdGFydCQzKG5hbWUpID8gaW5pdCQyIDogc2V0JGQ7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2NoZWR1bGUgPSBzaXQodGhpcywgaWQpLAogICAgICAgICAgICBvbiA9IHNjaGVkdWxlLm9uOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIGEgZGlzcGF0Y2ggd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAvLyBqdXN0IGFzc2lnbiB0aGUgdXBkYXRlZCBzaGFyZWQgZGlzcGF0Y2ggYW5kIHdl4oCZcmUgZG9uZSEKICAgICAgICAvLyBPdGhlcndpc2UsIGNvcHktb24td3JpdGUuCiAgICAgICAgaWYgKG9uICE9PSBvbjApIChvbjEgPSAob24wID0gb24pLmNvcHkoKSkub24obmFtZSwgbGlzdGVuZXIpOwoKICAgICAgICBzY2hlZHVsZS5vbiA9IG9uMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX29uJDIobmFtZSwgbGlzdGVuZXIpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA8IDIKICAgICAgICAgID8gZ2V0JDkodGhpcy5ub2RlKCksIGlkKS5vbi5vbihuYW1lKQogICAgICAgICAgOiB0aGlzLmVhY2gob25GdW5jdGlvbiQyKGlkLCBuYW1lLCBsaXN0ZW5lcikpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJlbW92ZUZ1bmN0aW9uJDIoaWQpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgICAgZm9yICh2YXIgaSBpbiB0aGlzLl9fdHJhbnNpdGlvbikgaWYgKCtpICE9PSBpZCkgcmV0dXJuOwogICAgICAgIGlmIChwYXJlbnQpIHBhcmVudC5yZW1vdmVDaGlsZCh0aGlzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3JlbW92ZSQyKCkgewogICAgICByZXR1cm4gdGhpcy5vbigiZW5kLnJlbW92ZSIsIHJlbW92ZUZ1bmN0aW9uJDIodGhpcy5faWQpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3NlbGVjdCQyKHNlbGVjdCkgewogICAgICB2YXIgbmFtZSA9IHRoaXMuX25hbWUsCiAgICAgICAgICBpZCA9IHRoaXMuX2lkOwoKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yJDQoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIHN1Ym5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKHN1Ym5vZGUgPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpKSB7CiAgICAgICAgICAgIGlmICgiX19kYXRhX18iIGluIG5vZGUpIHN1Ym5vZGUuX19kYXRhX18gPSBub2RlLl9fZGF0YV9fOwogICAgICAgICAgICBzdWJncm91cFtpXSA9IHN1Ym5vZGU7CiAgICAgICAgICAgIHNjaGVkdWxlJDMoc3ViZ3JvdXBbaV0sIG5hbWUsIGlkLCBpLCBzdWJncm91cCwgZ2V0JDkobm9kZSwgaWQpKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQyKHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cywgbmFtZSwgaWQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc2VsZWN0QWxsJDIoc2VsZWN0KSB7CiAgICAgIHZhciBuYW1lID0gdGhpcy5fbmFtZSwKICAgICAgICAgIGlkID0gdGhpcy5faWQ7CgogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3JBbGwkNChzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gW10sIHBhcmVudHMgPSBbXSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgZm9yICh2YXIgY2hpbGRyZW4gPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCksIGNoaWxkLCBpbmhlcml0ID0gZ2V0JDkobm9kZSwgaWQpLCBrID0gMCwgbCA9IGNoaWxkcmVuLmxlbmd0aDsgayA8IGw7ICsraykgewogICAgICAgICAgICAgIGlmIChjaGlsZCA9IGNoaWxkcmVuW2tdKSB7CiAgICAgICAgICAgICAgICBzY2hlZHVsZSQzKGNoaWxkLCBuYW1lLCBpZCwgaywgY2hpbGRyZW4sIGluaGVyaXQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBzdWJncm91cHMucHVzaChjaGlsZHJlbik7CiAgICAgICAgICAgIHBhcmVudHMucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQyKHN1Ymdyb3VwcywgcGFyZW50cywgbmFtZSwgaWQpOwogICAgfQoKICAgIHZhciBTZWxlY3Rpb24kNyA9IHNlbGVjdGlvbiQ0LnByb3RvdHlwZS5jb25zdHJ1Y3RvcjsKCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3NlbGVjdGlvbiQyKCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ3KHRoaXMuX2dyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVSZW1vdmUkNyhuYW1lLCBpbnRlcnBvbGF0ZSkgewogICAgICB2YXIgdmFsdWUwMCwKICAgICAgICAgIHZhbHVlMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUwID0gc3R5bGVWYWx1ZSQ0KHRoaXMsIG5hbWUpLAogICAgICAgICAgICB2YWx1ZTEgPSAodGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKSwgc3R5bGVWYWx1ZSQ0KHRoaXMsIG5hbWUpKTsKICAgICAgICByZXR1cm4gdmFsdWUwID09PSB2YWx1ZTEgPyBudWxsCiAgICAgICAgICAgIDogdmFsdWUwID09PSB2YWx1ZTAwICYmIHZhbHVlMSA9PT0gdmFsdWUxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHZhbHVlMDAgPSB2YWx1ZTAsIHZhbHVlMTAgPSB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlUmVtb3ZlRW5kKG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVDb25zdGFudCQ3KG5hbWUsIGludGVycG9sYXRlLCB2YWx1ZTEpIHsKICAgICAgdmFyIHZhbHVlMDAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUwID0gc3R5bGVWYWx1ZSQ0KHRoaXMsIG5hbWUpOwogICAgICAgIHJldHVybiB2YWx1ZTAgPT09IHZhbHVlMSA/IG51bGwKICAgICAgICAgICAgOiB2YWx1ZTAgPT09IHZhbHVlMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZSh2YWx1ZTAwID0gdmFsdWUwLCB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlRnVuY3Rpb24kNyhuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHZhbHVlMDAsCiAgICAgICAgICB2YWx1ZTEwLAogICAgICAgICAgaW50ZXJwb2xhdGUwOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHZhbHVlMCA9IHN0eWxlVmFsdWUkNCh0aGlzLCBuYW1lKSwKICAgICAgICAgICAgdmFsdWUxID0gdmFsdWUodGhpcyk7CiAgICAgICAgaWYgKHZhbHVlMSA9PSBudWxsKSB2YWx1ZTEgPSAodGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKSwgc3R5bGVWYWx1ZSQ0KHRoaXMsIG5hbWUpKTsKICAgICAgICByZXR1cm4gdmFsdWUwID09PSB2YWx1ZTEgPyBudWxsCiAgICAgICAgICAgIDogdmFsdWUwID09PSB2YWx1ZTAwICYmIHZhbHVlMSA9PT0gdmFsdWUxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHZhbHVlMDAgPSB2YWx1ZTAsIHZhbHVlMTAgPSB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc3R5bGUkMihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIGkgPSAobmFtZSArPSAiIikgPT09ICJ0cmFuc2Zvcm0iID8gaW50ZXJwb2xhdGVUcmFuc2Zvcm1Dc3MkMyA6IGludGVycG9sYXRlJDU7CiAgICAgIHJldHVybiB2YWx1ZSA9PSBudWxsID8gdGhpcwogICAgICAgICAgICAgIC5zdHlsZVR3ZWVuKG5hbWUsIHN0eWxlUmVtb3ZlJDcobmFtZSwgaSkpCiAgICAgICAgICAgICAgLm9uKCJlbmQuc3R5bGUuIiArIG5hbWUsIHN0eWxlUmVtb3ZlRW5kKG5hbWUpKQogICAgICAgICAgOiB0aGlzLnN0eWxlVHdlZW4obmFtZSwgdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBzdHlsZUZ1bmN0aW9uJDcobmFtZSwgaSwgdHdlZW5WYWx1ZSQyKHRoaXMsICJzdHlsZS4iICsgbmFtZSwgdmFsdWUpKQogICAgICAgICAgICAgIDogc3R5bGVDb25zdGFudCQ3KG5hbWUsIGksIHZhbHVlICsgIiIpLCBwcmlvcml0eSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVUd2VlbiQyKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICBmdW5jdGlvbiB0d2VlbigpIHsKICAgICAgICB2YXIgbm9kZSA9IHRoaXMsIGkgPSB2YWx1ZS5hcHBseShub2RlLCBhcmd1bWVudHMpOwogICAgICAgIHJldHVybiBpICYmIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIG5vZGUuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgaSh0KSwgcHJpb3JpdHkpOwogICAgICAgIH07CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3N0eWxlVHdlZW4kMihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIGtleSA9ICJzdHlsZS4iICsgKG5hbWUgKz0gIiIpOwogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHJldHVybiAoa2V5ID0gdGhpcy50d2VlbihrZXkpKSAmJiBrZXkuX3ZhbHVlOwogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCBudWxsKTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIHN0eWxlVHdlZW4kMihuYW1lLCB2YWx1ZSwgcHJpb3JpdHkgPT0gbnVsbCA/ICIiIDogcHJpb3JpdHkpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0Q29uc3RhbnQkNyh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRGdW5jdGlvbiQ3KHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUxID0gdmFsdWUodGhpcyk7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHZhbHVlMSA9PSBudWxsID8gIiIgOiB2YWx1ZTE7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl90ZXh0JDIodmFsdWUpIHsKICAgICAgcmV0dXJuIHRoaXMudHdlZW4oInRleHQiLCB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gdGV4dEZ1bmN0aW9uJDcodHdlZW5WYWx1ZSQyKHRoaXMsICJ0ZXh0IiwgdmFsdWUpKQogICAgICAgICAgOiB0ZXh0Q29uc3RhbnQkNyh2YWx1ZSA9PSBudWxsID8gIiIgOiB2YWx1ZSArICIiKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl90cmFuc2l0aW9uJDIoKSB7CiAgICAgIHZhciBuYW1lID0gdGhpcy5fbmFtZSwKICAgICAgICAgIGlkMCA9IHRoaXMuX2lkLAogICAgICAgICAgaWQxID0gbmV3SWQkMigpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgdmFyIGluaGVyaXQgPSBnZXQkOShub2RlLCBpZDApOwogICAgICAgICAgICBzY2hlZHVsZSQzKG5vZGUsIG5hbWUsIGlkMSwgaSwgZ3JvdXAsIHsKICAgICAgICAgICAgICB0aW1lOiBpbmhlcml0LnRpbWUgKyBpbmhlcml0LmRlbGF5ICsgaW5oZXJpdC5kdXJhdGlvbiwKICAgICAgICAgICAgICBkZWxheTogMCwKICAgICAgICAgICAgICBkdXJhdGlvbjogaW5oZXJpdC5kdXJhdGlvbiwKICAgICAgICAgICAgICBlYXNlOiBpbmhlcml0LmVhc2UKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMihncm91cHMsIHRoaXMuX3BhcmVudHMsIG5hbWUsIGlkMSk7CiAgICB9CgogICAgdmFyIGlkJDIgPSAwOwoKICAgIGZ1bmN0aW9uIFRyYW5zaXRpb24kMihncm91cHMsIHBhcmVudHMsIG5hbWUsIGlkKSB7CiAgICAgIHRoaXMuX2dyb3VwcyA9IGdyb3VwczsKICAgICAgdGhpcy5fcGFyZW50cyA9IHBhcmVudHM7CiAgICAgIHRoaXMuX25hbWUgPSBuYW1lOwogICAgICB0aGlzLl9pZCA9IGlkOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb24kMihuYW1lKSB7CiAgICAgIHJldHVybiBzZWxlY3Rpb24kNCgpLnRyYW5zaXRpb24obmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gbmV3SWQkMigpIHsKICAgICAgcmV0dXJuICsraWQkMjsKICAgIH0KCiAgICB2YXIgc2VsZWN0aW9uX3Byb3RvdHlwZSQyID0gc2VsZWN0aW9uJDQucHJvdG90eXBlOwoKICAgIFRyYW5zaXRpb24kMi5wcm90b3R5cGUgPSB0cmFuc2l0aW9uJDIucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVHJhbnNpdGlvbiQyLAogICAgICBzZWxlY3Q6IHRyYW5zaXRpb25fc2VsZWN0JDIsCiAgICAgIHNlbGVjdEFsbDogdHJhbnNpdGlvbl9zZWxlY3RBbGwkMiwKICAgICAgZmlsdGVyOiB0cmFuc2l0aW9uX2ZpbHRlciQyLAogICAgICBtZXJnZTogdHJhbnNpdGlvbl9tZXJnZSQyLAogICAgICBzZWxlY3Rpb246IHRyYW5zaXRpb25fc2VsZWN0aW9uJDIsCiAgICAgIHRyYW5zaXRpb246IHRyYW5zaXRpb25fdHJhbnNpdGlvbiQyLAogICAgICBjYWxsOiBzZWxlY3Rpb25fcHJvdG90eXBlJDIuY2FsbCwKICAgICAgbm9kZXM6IHNlbGVjdGlvbl9wcm90b3R5cGUkMi5ub2RlcywKICAgICAgbm9kZTogc2VsZWN0aW9uX3Byb3RvdHlwZSQyLm5vZGUsCiAgICAgIHNpemU6IHNlbGVjdGlvbl9wcm90b3R5cGUkMi5zaXplLAogICAgICBlbXB0eTogc2VsZWN0aW9uX3Byb3RvdHlwZSQyLmVtcHR5LAogICAgICBlYWNoOiBzZWxlY3Rpb25fcHJvdG90eXBlJDIuZWFjaCwKICAgICAgb246IHRyYW5zaXRpb25fb24kMiwKICAgICAgYXR0cjogdHJhbnNpdGlvbl9hdHRyJDIsCiAgICAgIGF0dHJUd2VlbjogdHJhbnNpdGlvbl9hdHRyVHdlZW4kMiwKICAgICAgc3R5bGU6IHRyYW5zaXRpb25fc3R5bGUkMiwKICAgICAgc3R5bGVUd2VlbjogdHJhbnNpdGlvbl9zdHlsZVR3ZWVuJDIsCiAgICAgIHRleHQ6IHRyYW5zaXRpb25fdGV4dCQyLAogICAgICByZW1vdmU6IHRyYW5zaXRpb25fcmVtb3ZlJDIsCiAgICAgIHR3ZWVuOiB0cmFuc2l0aW9uX3R3ZWVuJDIsCiAgICAgIGRlbGF5OiB0cmFuc2l0aW9uX2RlbGF5JDIsCiAgICAgIGR1cmF0aW9uOiB0cmFuc2l0aW9uX2R1cmF0aW9uJDIsCiAgICAgIGVhc2U6IHRyYW5zaXRpb25fZWFzZSQyCiAgICB9OwoKICAgIHZhciBkZWZhdWx0VGltaW5nJDIgPSB7CiAgICAgIHRpbWU6IG51bGwsIC8vIFNldCBvbiB1c2UuCiAgICAgIGRlbGF5OiAwLAogICAgICBkdXJhdGlvbjogMjUwLAogICAgICBlYXNlOiBjdWJpY0luT3V0CiAgICB9OwoKICAgIGZ1bmN0aW9uIGluaGVyaXQkMihub2RlLCBpZCkgewogICAgICB2YXIgdGltaW5nOwogICAgICB3aGlsZSAoISh0aW1pbmcgPSBub2RlLl9fdHJhbnNpdGlvbikgfHwgISh0aW1pbmcgPSB0aW1pbmdbaWRdKSkgewogICAgICAgIGlmICghKG5vZGUgPSBub2RlLnBhcmVudE5vZGUpKSB7CiAgICAgICAgICByZXR1cm4gZGVmYXVsdFRpbWluZyQyLnRpbWUgPSBub3ckNCgpLCBkZWZhdWx0VGltaW5nJDI7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0aW1pbmc7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3RyYW5zaXRpb24kMihuYW1lKSB7CiAgICAgIHZhciBpZCwKICAgICAgICAgIHRpbWluZzsKCiAgICAgIGlmIChuYW1lIGluc3RhbmNlb2YgVHJhbnNpdGlvbiQyKSB7CiAgICAgICAgaWQgPSBuYW1lLl9pZCwgbmFtZSA9IG5hbWUuX25hbWU7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgaWQgPSBuZXdJZCQyKCksICh0aW1pbmcgPSBkZWZhdWx0VGltaW5nJDIpLnRpbWUgPSBub3ckNCgpLCBuYW1lID0gbmFtZSA9PSBudWxsID8gbnVsbCA6IG5hbWUgKyAiIjsKICAgICAgfQoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc2NoZWR1bGUkMyhub2RlLCBuYW1lLCBpZCwgaSwgZ3JvdXAsIHRpbWluZyB8fCBpbmhlcml0JDIobm9kZSwgaWQpKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQyKGdyb3VwcywgdGhpcy5fcGFyZW50cywgbmFtZSwgaWQpOwogICAgfQoKICAgIHNlbGVjdGlvbiQ0LnByb3RvdHlwZS5pbnRlcnJ1cHQgPSBzZWxlY3Rpb25faW50ZXJydXB0JDI7CiAgICBzZWxlY3Rpb24kNC5wcm90b3R5cGUudHJhbnNpdGlvbiA9IHNlbGVjdGlvbl90cmFuc2l0aW9uJDI7CgogICAgdmFyIHJvb3QkNyA9IFtudWxsXTsKCiAgICBmdW5jdGlvbiBhY3RpdmUkMShub2RlLCBuYW1lKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbiwKICAgICAgICAgIHNjaGVkdWxlLAogICAgICAgICAgaTsKCiAgICAgIGlmIChzY2hlZHVsZXMpIHsKICAgICAgICBuYW1lID0gbmFtZSA9PSBudWxsID8gbnVsbCA6IG5hbWUgKyAiIjsKICAgICAgICBmb3IgKGkgaW4gc2NoZWR1bGVzKSB7CiAgICAgICAgICBpZiAoKHNjaGVkdWxlID0gc2NoZWR1bGVzW2ldKS5zdGF0ZSA+IFNDSEVEVUxFRCQyICYmIHNjaGVkdWxlLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDIoW1tub2RlXV0sIHJvb3QkNywgbmFtZSwgK2kpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkdih4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB4JDkoZCkgewogICAgICByZXR1cm4gZFswXTsKICAgIH0KCiAgICBmdW5jdGlvbiB5JDkoZCkgewogICAgICByZXR1cm4gZFsxXTsKICAgIH0KCiAgICBmdW5jdGlvbiBSZWRCbGFja1RyZWUkMSgpIHsKICAgICAgdGhpcy5fID0gbnVsbDsgLy8gcm9vdCBub2RlCiAgICB9CgogICAgZnVuY3Rpb24gUmVkQmxhY2tOb2RlJDEobm9kZSkgewogICAgICBub2RlLlUgPSAvLyBwYXJlbnQgbm9kZQogICAgICBub2RlLkMgPSAvLyBjb2xvciAtIHRydWUgZm9yIHJlZCwgZmFsc2UgZm9yIGJsYWNrCiAgICAgIG5vZGUuTCA9IC8vIGxlZnQgbm9kZQogICAgICBub2RlLlIgPSAvLyByaWdodCBub2RlCiAgICAgIG5vZGUuUCA9IC8vIHByZXZpb3VzIG5vZGUKICAgICAgbm9kZS5OID0gbnVsbDsgLy8gbmV4dCBub2RlCiAgICB9CgogICAgUmVkQmxhY2tUcmVlJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogUmVkQmxhY2tUcmVlJDEsCgogICAgICBpbnNlcnQ6IGZ1bmN0aW9uKGFmdGVyLCBub2RlKSB7CiAgICAgICAgdmFyIHBhcmVudCwgZ3JhbmRwYSwgdW5jbGU7CgogICAgICAgIGlmIChhZnRlcikgewogICAgICAgICAgbm9kZS5QID0gYWZ0ZXI7CiAgICAgICAgICBub2RlLk4gPSBhZnRlci5OOwogICAgICAgICAgaWYgKGFmdGVyLk4pIGFmdGVyLk4uUCA9IG5vZGU7CiAgICAgICAgICBhZnRlci5OID0gbm9kZTsKICAgICAgICAgIGlmIChhZnRlci5SKSB7CiAgICAgICAgICAgIGFmdGVyID0gYWZ0ZXIuUjsKICAgICAgICAgICAgd2hpbGUgKGFmdGVyLkwpIGFmdGVyID0gYWZ0ZXIuTDsKICAgICAgICAgICAgYWZ0ZXIuTCA9IG5vZGU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBhZnRlci5SID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICAgIHBhcmVudCA9IGFmdGVyOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5fKSB7CiAgICAgICAgICBhZnRlciA9IFJlZEJsYWNrRmlyc3QkMSh0aGlzLl8pOwogICAgICAgICAgbm9kZS5QID0gbnVsbDsKICAgICAgICAgIG5vZGUuTiA9IGFmdGVyOwogICAgICAgICAgYWZ0ZXIuUCA9IGFmdGVyLkwgPSBub2RlOwogICAgICAgICAgcGFyZW50ID0gYWZ0ZXI7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIG5vZGUuUCA9IG5vZGUuTiA9IG51bGw7CiAgICAgICAgICB0aGlzLl8gPSBub2RlOwogICAgICAgICAgcGFyZW50ID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgbm9kZS5MID0gbm9kZS5SID0gbnVsbDsKICAgICAgICBub2RlLlUgPSBwYXJlbnQ7CiAgICAgICAgbm9kZS5DID0gdHJ1ZTsKCiAgICAgICAgYWZ0ZXIgPSBub2RlOwogICAgICAgIHdoaWxlIChwYXJlbnQgJiYgcGFyZW50LkMpIHsKICAgICAgICAgIGdyYW5kcGEgPSBwYXJlbnQuVTsKICAgICAgICAgIGlmIChwYXJlbnQgPT09IGdyYW5kcGEuTCkgewogICAgICAgICAgICB1bmNsZSA9IGdyYW5kcGEuUjsKICAgICAgICAgICAgaWYgKHVuY2xlICYmIHVuY2xlLkMpIHsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHVuY2xlLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIGFmdGVyID0gZ3JhbmRwYTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpZiAoYWZ0ZXIgPT09IHBhcmVudC5SKSB7CiAgICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZUxlZnQkMSh0aGlzLCBwYXJlbnQpOwogICAgICAgICAgICAgICAgYWZ0ZXIgPSBwYXJlbnQ7CiAgICAgICAgICAgICAgICBwYXJlbnQgPSBhZnRlci5VOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBwYXJlbnQuQyA9IGZhbHNlOwogICAgICAgICAgICAgIGdyYW5kcGEuQyA9IHRydWU7CiAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVSaWdodCQxKHRoaXMsIGdyYW5kcGEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB1bmNsZSA9IGdyYW5kcGEuTDsKICAgICAgICAgICAgaWYgKHVuY2xlICYmIHVuY2xlLkMpIHsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHVuY2xlLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIGFmdGVyID0gZ3JhbmRwYTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBpZiAoYWZ0ZXIgPT09IHBhcmVudC5MKSB7CiAgICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZVJpZ2h0JDEodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICAgIGFmdGVyID0gcGFyZW50OwogICAgICAgICAgICAgICAgcGFyZW50ID0gYWZ0ZXIuVTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgcGFyZW50LkMgPSBmYWxzZTsKICAgICAgICAgICAgICBncmFuZHBhLkMgPSB0cnVlOwogICAgICAgICAgICAgIFJlZEJsYWNrUm90YXRlTGVmdCQxKHRoaXMsIGdyYW5kcGEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBwYXJlbnQgPSBhZnRlci5VOwogICAgICAgIH0KICAgICAgICB0aGlzLl8uQyA9IGZhbHNlOwogICAgICB9LAoKICAgICAgcmVtb3ZlOiBmdW5jdGlvbihub2RlKSB7CiAgICAgICAgaWYgKG5vZGUuTikgbm9kZS5OLlAgPSBub2RlLlA7CiAgICAgICAgaWYgKG5vZGUuUCkgbm9kZS5QLk4gPSBub2RlLk47CiAgICAgICAgbm9kZS5OID0gbm9kZS5QID0gbnVsbDsKCiAgICAgICAgdmFyIHBhcmVudCA9IG5vZGUuVSwKICAgICAgICAgICAgc2libGluZywKICAgICAgICAgICAgbGVmdCA9IG5vZGUuTCwKICAgICAgICAgICAgcmlnaHQgPSBub2RlLlIsCiAgICAgICAgICAgIG5leHQsCiAgICAgICAgICAgIHJlZDsKCiAgICAgICAgaWYgKCFsZWZ0KSBuZXh0ID0gcmlnaHQ7CiAgICAgICAgZWxzZSBpZiAoIXJpZ2h0KSBuZXh0ID0gbGVmdDsKICAgICAgICBlbHNlIG5leHQgPSBSZWRCbGFja0ZpcnN0JDEocmlnaHQpOwoKICAgICAgICBpZiAocGFyZW50KSB7CiAgICAgICAgICBpZiAocGFyZW50LkwgPT09IG5vZGUpIHBhcmVudC5MID0gbmV4dDsKICAgICAgICAgIGVsc2UgcGFyZW50LlIgPSBuZXh0OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLl8gPSBuZXh0OwogICAgICAgIH0KCiAgICAgICAgaWYgKGxlZnQgJiYgcmlnaHQpIHsKICAgICAgICAgIHJlZCA9IG5leHQuQzsKICAgICAgICAgIG5leHQuQyA9IG5vZGUuQzsKICAgICAgICAgIG5leHQuTCA9IGxlZnQ7CiAgICAgICAgICBsZWZ0LlUgPSBuZXh0OwogICAgICAgICAgaWYgKG5leHQgIT09IHJpZ2h0KSB7CiAgICAgICAgICAgIHBhcmVudCA9IG5leHQuVTsKICAgICAgICAgICAgbmV4dC5VID0gbm9kZS5VOwogICAgICAgICAgICBub2RlID0gbmV4dC5SOwogICAgICAgICAgICBwYXJlbnQuTCA9IG5vZGU7CiAgICAgICAgICAgIG5leHQuUiA9IHJpZ2h0OwogICAgICAgICAgICByaWdodC5VID0gbmV4dDsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5leHQuVSA9IHBhcmVudDsKICAgICAgICAgICAgcGFyZW50ID0gbmV4dDsKICAgICAgICAgICAgbm9kZSA9IG5leHQuUjsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmVkID0gbm9kZS5DOwogICAgICAgICAgbm9kZSA9IG5leHQ7CiAgICAgICAgfQoKICAgICAgICBpZiAobm9kZSkgbm9kZS5VID0gcGFyZW50OwogICAgICAgIGlmIChyZWQpIHJldHVybjsKICAgICAgICBpZiAobm9kZSAmJiBub2RlLkMpIHsgbm9kZS5DID0gZmFsc2U7IHJldHVybjsgfQoKICAgICAgICBkbyB7CiAgICAgICAgICBpZiAobm9kZSA9PT0gdGhpcy5fKSBicmVhazsKICAgICAgICAgIGlmIChub2RlID09PSBwYXJlbnQuTCkgewogICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50LlI7CiAgICAgICAgICAgIGlmIChzaWJsaW5nLkMpIHsKICAgICAgICAgICAgICBzaWJsaW5nLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBwYXJlbnQuQyA9IHRydWU7CiAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVMZWZ0JDEodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50LlI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKChzaWJsaW5nLkwgJiYgc2libGluZy5MLkMpCiAgICAgICAgICAgICAgICB8fCAoc2libGluZy5SICYmIHNpYmxpbmcuUi5DKSkgewogICAgICAgICAgICAgIGlmICghc2libGluZy5SIHx8ICFzaWJsaW5nLlIuQykgewogICAgICAgICAgICAgICAgc2libGluZy5MLkMgPSBmYWxzZTsKICAgICAgICAgICAgICAgIHNpYmxpbmcuQyA9IHRydWU7CiAgICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZVJpZ2h0JDEodGhpcywgc2libGluZyk7CiAgICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50LlI7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHNpYmxpbmcuQyA9IHBhcmVudC5DOwogICAgICAgICAgICAgIHBhcmVudC5DID0gc2libGluZy5SLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZUxlZnQkMSh0aGlzLCBwYXJlbnQpOwogICAgICAgICAgICAgIG5vZGUgPSB0aGlzLl87CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIHNpYmxpbmcgPSBwYXJlbnQuTDsKICAgICAgICAgICAgaWYgKHNpYmxpbmcuQykgewogICAgICAgICAgICAgIHNpYmxpbmcuQyA9IGZhbHNlOwogICAgICAgICAgICAgIHBhcmVudC5DID0gdHJ1ZTsKICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZVJpZ2h0JDEodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50Lkw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKChzaWJsaW5nLkwgJiYgc2libGluZy5MLkMpCiAgICAgICAgICAgICAgfHwgKHNpYmxpbmcuUiAmJiBzaWJsaW5nLlIuQykpIHsKICAgICAgICAgICAgICBpZiAoIXNpYmxpbmcuTCB8fCAhc2libGluZy5MLkMpIHsKICAgICAgICAgICAgICAgIHNpYmxpbmcuUi5DID0gZmFsc2U7CiAgICAgICAgICAgICAgICBzaWJsaW5nLkMgPSB0cnVlOwogICAgICAgICAgICAgICAgUmVkQmxhY2tSb3RhdGVMZWZ0JDEodGhpcywgc2libGluZyk7CiAgICAgICAgICAgICAgICBzaWJsaW5nID0gcGFyZW50Lkw7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIHNpYmxpbmcuQyA9IHBhcmVudC5DOwogICAgICAgICAgICAgIHBhcmVudC5DID0gc2libGluZy5MLkMgPSBmYWxzZTsKICAgICAgICAgICAgICBSZWRCbGFja1JvdGF0ZVJpZ2h0JDEodGhpcywgcGFyZW50KTsKICAgICAgICAgICAgICBub2RlID0gdGhpcy5fOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBzaWJsaW5nLkMgPSB0cnVlOwogICAgICAgICAgbm9kZSA9IHBhcmVudDsKICAgICAgICAgIHBhcmVudCA9IHBhcmVudC5VOwogICAgICAgIH0gd2hpbGUgKCFub2RlLkMpOwoKICAgICAgICBpZiAobm9kZSkgbm9kZS5DID0gZmFsc2U7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gUmVkQmxhY2tSb3RhdGVMZWZ0JDEodHJlZSwgbm9kZSkgewogICAgICB2YXIgcCA9IG5vZGUsCiAgICAgICAgICBxID0gbm9kZS5SLAogICAgICAgICAgcGFyZW50ID0gcC5VOwoKICAgICAgaWYgKHBhcmVudCkgewogICAgICAgIGlmIChwYXJlbnQuTCA9PT0gcCkgcGFyZW50LkwgPSBxOwogICAgICAgIGVsc2UgcGFyZW50LlIgPSBxOwogICAgICB9IGVsc2UgewogICAgICAgIHRyZWUuXyA9IHE7CiAgICAgIH0KCiAgICAgIHEuVSA9IHBhcmVudDsKICAgICAgcC5VID0gcTsKICAgICAgcC5SID0gcS5MOwogICAgICBpZiAocC5SKSBwLlIuVSA9IHA7CiAgICAgIHEuTCA9IHA7CiAgICB9CgogICAgZnVuY3Rpb24gUmVkQmxhY2tSb3RhdGVSaWdodCQxKHRyZWUsIG5vZGUpIHsKICAgICAgdmFyIHAgPSBub2RlLAogICAgICAgICAgcSA9IG5vZGUuTCwKICAgICAgICAgIHBhcmVudCA9IHAuVTsKCiAgICAgIGlmIChwYXJlbnQpIHsKICAgICAgICBpZiAocGFyZW50LkwgPT09IHApIHBhcmVudC5MID0gcTsKICAgICAgICBlbHNlIHBhcmVudC5SID0gcTsKICAgICAgfSBlbHNlIHsKICAgICAgICB0cmVlLl8gPSBxOwogICAgICB9CgogICAgICBxLlUgPSBwYXJlbnQ7CiAgICAgIHAuVSA9IHE7CiAgICAgIHAuTCA9IHEuUjsKICAgICAgaWYgKHAuTCkgcC5MLlUgPSBwOwogICAgICBxLlIgPSBwOwogICAgfQoKICAgIGZ1bmN0aW9uIFJlZEJsYWNrRmlyc3QkMShub2RlKSB7CiAgICAgIHdoaWxlIChub2RlLkwpIG5vZGUgPSBub2RlLkw7CiAgICAgIHJldHVybiBub2RlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZUVkZ2UkMShsZWZ0LCByaWdodCwgdjAsIHYxKSB7CiAgICAgIHZhciBlZGdlID0gW251bGwsIG51bGxdLAogICAgICAgICAgaW5kZXggPSBlZGdlcyQxLnB1c2goZWRnZSkgLSAxOwogICAgICBlZGdlLmxlZnQgPSBsZWZ0OwogICAgICBlZGdlLnJpZ2h0ID0gcmlnaHQ7CiAgICAgIGlmICh2MCkgc2V0RWRnZUVuZCQxKGVkZ2UsIGxlZnQsIHJpZ2h0LCB2MCk7CiAgICAgIGlmICh2MSkgc2V0RWRnZUVuZCQxKGVkZ2UsIHJpZ2h0LCBsZWZ0LCB2MSk7CiAgICAgIGNlbGxzJDFbbGVmdC5pbmRleF0uaGFsZmVkZ2VzLnB1c2goaW5kZXgpOwogICAgICBjZWxscyQxW3JpZ2h0LmluZGV4XS5oYWxmZWRnZXMucHVzaChpbmRleCk7CiAgICAgIHJldHVybiBlZGdlOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZUJvcmRlckVkZ2UkMShsZWZ0LCB2MCwgdjEpIHsKICAgICAgdmFyIGVkZ2UgPSBbdjAsIHYxXTsKICAgICAgZWRnZS5sZWZ0ID0gbGVmdDsKICAgICAgcmV0dXJuIGVkZ2U7CiAgICB9CgogICAgZnVuY3Rpb24gc2V0RWRnZUVuZCQxKGVkZ2UsIGxlZnQsIHJpZ2h0LCB2ZXJ0ZXgpIHsKICAgICAgaWYgKCFlZGdlWzBdICYmICFlZGdlWzFdKSB7CiAgICAgICAgZWRnZVswXSA9IHZlcnRleDsKICAgICAgICBlZGdlLmxlZnQgPSBsZWZ0OwogICAgICAgIGVkZ2UucmlnaHQgPSByaWdodDsKICAgICAgfSBlbHNlIGlmIChlZGdlLmxlZnQgPT09IHJpZ2h0KSB7CiAgICAgICAgZWRnZVsxXSA9IHZlcnRleDsKICAgICAgfSBlbHNlIHsKICAgICAgICBlZGdlWzBdID0gdmVydGV4OwogICAgICB9CiAgICB9CgogICAgLy8gTGlhbmfigJNCYXJza3kgbGluZSBjbGlwcGluZy4KICAgIGZ1bmN0aW9uIGNsaXBFZGdlJDEoZWRnZSwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgdmFyIGEgPSBlZGdlWzBdLAogICAgICAgICAgYiA9IGVkZ2VbMV0sCiAgICAgICAgICBheCA9IGFbMF0sCiAgICAgICAgICBheSA9IGFbMV0sCiAgICAgICAgICBieCA9IGJbMF0sCiAgICAgICAgICBieSA9IGJbMV0sCiAgICAgICAgICB0MCA9IDAsCiAgICAgICAgICB0MSA9IDEsCiAgICAgICAgICBkeCA9IGJ4IC0gYXgsCiAgICAgICAgICBkeSA9IGJ5IC0gYXksCiAgICAgICAgICByOwoKICAgICAgciA9IHgwIC0gYXg7CiAgICAgIGlmICghZHggJiYgciA+IDApIHJldHVybjsKICAgICAgciAvPSBkeDsKICAgICAgaWYgKGR4IDwgMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0gZWxzZSBpZiAoZHggPiAwKSB7CiAgICAgICAgaWYgKHIgPiB0MSkgcmV0dXJuOwogICAgICAgIGlmIChyID4gdDApIHQwID0gcjsKICAgICAgfQoKICAgICAgciA9IHgxIC0gYXg7CiAgICAgIGlmICghZHggJiYgciA8IDApIHJldHVybjsKICAgICAgciAvPSBkeDsKICAgICAgaWYgKGR4IDwgMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0gZWxzZSBpZiAoZHggPiAwKSB7CiAgICAgICAgaWYgKHIgPCB0MCkgcmV0dXJuOwogICAgICAgIGlmIChyIDwgdDEpIHQxID0gcjsKICAgICAgfQoKICAgICAgciA9IHkwIC0gYXk7CiAgICAgIGlmICghZHkgJiYgciA+IDApIHJldHVybjsKICAgICAgciAvPSBkeTsKICAgICAgaWYgKGR5IDwgMCkgewogICAgICAgIGlmIChyIDwgdDApIHJldHVybjsKICAgICAgICBpZiAociA8IHQxKSB0MSA9IHI7CiAgICAgIH0gZWxzZSBpZiAoZHkgPiAwKSB7CiAgICAgICAgaWYgKHIgPiB0MSkgcmV0dXJuOwogICAgICAgIGlmIChyID4gdDApIHQwID0gcjsKICAgICAgfQoKICAgICAgciA9IHkxIC0gYXk7CiAgICAgIGlmICghZHkgJiYgciA8IDApIHJldHVybjsKICAgICAgciAvPSBkeTsKICAgICAgaWYgKGR5IDwgMCkgewogICAgICAgIGlmIChyID4gdDEpIHJldHVybjsKICAgICAgICBpZiAociA+IHQwKSB0MCA9IHI7CiAgICAgIH0gZWxzZSBpZiAoZHkgPiAwKSB7CiAgICAgICAgaWYgKHIgPCB0MCkgcmV0dXJuOwogICAgICAgIGlmIChyIDwgdDEpIHQxID0gcjsKICAgICAgfQoKICAgICAgaWYgKCEodDAgPiAwKSAmJiAhKHQxIDwgMSkpIHJldHVybiB0cnVlOyAvLyBUT0RPIEJldHRlciBjaGVjaz8KCiAgICAgIGlmICh0MCA+IDApIGVkZ2VbMF0gPSBbYXggKyB0MCAqIGR4LCBheSArIHQwICogZHldOwogICAgICBpZiAodDEgPCAxKSBlZGdlWzFdID0gW2F4ICsgdDEgKiBkeCwgYXkgKyB0MSAqIGR5XTsKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CgogICAgZnVuY3Rpb24gY29ubmVjdEVkZ2UkMShlZGdlLCB4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgdjEgPSBlZGdlWzFdOwogICAgICBpZiAodjEpIHJldHVybiB0cnVlOwoKICAgICAgdmFyIHYwID0gZWRnZVswXSwKICAgICAgICAgIGxlZnQgPSBlZGdlLmxlZnQsCiAgICAgICAgICByaWdodCA9IGVkZ2UucmlnaHQsCiAgICAgICAgICBseCA9IGxlZnRbMF0sCiAgICAgICAgICBseSA9IGxlZnRbMV0sCiAgICAgICAgICByeCA9IHJpZ2h0WzBdLAogICAgICAgICAgcnkgPSByaWdodFsxXSwKICAgICAgICAgIGZ4ID0gKGx4ICsgcngpIC8gMiwKICAgICAgICAgIGZ5ID0gKGx5ICsgcnkpIC8gMiwKICAgICAgICAgIGZtLAogICAgICAgICAgZmI7CgogICAgICBpZiAocnkgPT09IGx5KSB7CiAgICAgICAgaWYgKGZ4IDwgeDAgfHwgZnggPj0geDEpIHJldHVybjsKICAgICAgICBpZiAobHggPiByeCkgewogICAgICAgICAgaWYgKCF2MCkgdjAgPSBbZngsIHkwXTsKICAgICAgICAgIGVsc2UgaWYgKHYwWzFdID49IHkxKSByZXR1cm47CiAgICAgICAgICB2MSA9IFtmeCwgeTFdOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAoIXYwKSB2MCA9IFtmeCwgeTFdOwogICAgICAgICAgZWxzZSBpZiAodjBbMV0gPCB5MCkgcmV0dXJuOwogICAgICAgICAgdjEgPSBbZngsIHkwXTsKICAgICAgICB9CiAgICAgIH0gZWxzZSB7CiAgICAgICAgZm0gPSAobHggLSByeCkgLyAocnkgLSBseSk7CiAgICAgICAgZmIgPSBmeSAtIGZtICogZng7CiAgICAgICAgaWYgKGZtIDwgLTEgfHwgZm0gPiAxKSB7CiAgICAgICAgICBpZiAobHggPiByeCkgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFsoeTAgLSBmYikgLyBmbSwgeTBdOwogICAgICAgICAgICBlbHNlIGlmICh2MFsxXSA+PSB5MSkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFsoeTEgLSBmYikgLyBmbSwgeTFdOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKCF2MCkgdjAgPSBbKHkxIC0gZmIpIC8gZm0sIHkxXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMV0gPCB5MCkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFsoeTAgLSBmYikgLyBmbSwgeTBdOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAobHkgPCByeSkgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFt4MCwgZm0gKiB4MCArIGZiXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMF0gPj0geDEpIHJldHVybjsKICAgICAgICAgICAgdjEgPSBbeDEsIGZtICogeDEgKyBmYl07CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoIXYwKSB2MCA9IFt4MSwgZm0gKiB4MSArIGZiXTsKICAgICAgICAgICAgZWxzZSBpZiAodjBbMF0gPCB4MCkgcmV0dXJuOwogICAgICAgICAgICB2MSA9IFt4MCwgZm0gKiB4MCArIGZiXTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGVkZ2VbMF0gPSB2MDsKICAgICAgZWRnZVsxXSA9IHYxOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwRWRnZXMkMSh4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgaSA9IGVkZ2VzJDEubGVuZ3RoLAogICAgICAgICAgZWRnZTsKCiAgICAgIHdoaWxlIChpLS0pIHsKICAgICAgICBpZiAoIWNvbm5lY3RFZGdlJDEoZWRnZSA9IGVkZ2VzJDFbaV0sIHgwLCB5MCwgeDEsIHkxKQogICAgICAgICAgICB8fCAhY2xpcEVkZ2UkMShlZGdlLCB4MCwgeTAsIHgxLCB5MSkKICAgICAgICAgICAgfHwgIShNYXRoLmFicyhlZGdlWzBdWzBdIC0gZWRnZVsxXVswXSkgPiBlcHNpbG9uJGIKICAgICAgICAgICAgICAgIHx8IE1hdGguYWJzKGVkZ2VbMF1bMV0gLSBlZGdlWzFdWzFdKSA+IGVwc2lsb24kYikpIHsKICAgICAgICAgIGRlbGV0ZSBlZGdlcyQxW2ldOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZUNlbGwkMShzaXRlKSB7CiAgICAgIHJldHVybiBjZWxscyQxW3NpdGUuaW5kZXhdID0gewogICAgICAgIHNpdGU6IHNpdGUsCiAgICAgICAgaGFsZmVkZ2VzOiBbXQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNlbGxIYWxmZWRnZUFuZ2xlJDEoY2VsbCwgZWRnZSkgewogICAgICB2YXIgc2l0ZSA9IGNlbGwuc2l0ZSwKICAgICAgICAgIHZhID0gZWRnZS5sZWZ0LAogICAgICAgICAgdmIgPSBlZGdlLnJpZ2h0OwogICAgICBpZiAoc2l0ZSA9PT0gdmIpIHZiID0gdmEsIHZhID0gc2l0ZTsKICAgICAgaWYgKHZiKSByZXR1cm4gTWF0aC5hdGFuMih2YlsxXSAtIHZhWzFdLCB2YlswXSAtIHZhWzBdKTsKICAgICAgaWYgKHNpdGUgPT09IHZhKSB2YSA9IGVkZ2VbMV0sIHZiID0gZWRnZVswXTsKICAgICAgZWxzZSB2YSA9IGVkZ2VbMF0sIHZiID0gZWRnZVsxXTsKICAgICAgcmV0dXJuIE1hdGguYXRhbjIodmFbMF0gLSB2YlswXSwgdmJbMV0gLSB2YVsxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2VsbEhhbGZlZGdlU3RhcnQkMShjZWxsLCBlZGdlKSB7CiAgICAgIHJldHVybiBlZGdlWysoZWRnZS5sZWZ0ICE9PSBjZWxsLnNpdGUpXTsKICAgIH0KCiAgICBmdW5jdGlvbiBjZWxsSGFsZmVkZ2VFbmQkMShjZWxsLCBlZGdlKSB7CiAgICAgIHJldHVybiBlZGdlWysoZWRnZS5sZWZ0ID09PSBjZWxsLnNpdGUpXTsKICAgIH0KCiAgICBmdW5jdGlvbiBzb3J0Q2VsbEhhbGZlZGdlcyQxKCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGNlbGxzJDEubGVuZ3RoLCBjZWxsLCBoYWxmZWRnZXMsIGosIG07IGkgPCBuOyArK2kpIHsKICAgICAgICBpZiAoKGNlbGwgPSBjZWxscyQxW2ldKSAmJiAobSA9IChoYWxmZWRnZXMgPSBjZWxsLmhhbGZlZGdlcykubGVuZ3RoKSkgewogICAgICAgICAgdmFyIGluZGV4ID0gbmV3IEFycmF5KG0pLAogICAgICAgICAgICAgIGFycmF5ID0gbmV3IEFycmF5KG0pOwogICAgICAgICAgZm9yIChqID0gMDsgaiA8IG07ICsraikgaW5kZXhbal0gPSBqLCBhcnJheVtqXSA9IGNlbGxIYWxmZWRnZUFuZ2xlJDEoY2VsbCwgZWRnZXMkMVtoYWxmZWRnZXNbal1dKTsKICAgICAgICAgIGluZGV4LnNvcnQoZnVuY3Rpb24oaSwgaikgeyByZXR1cm4gYXJyYXlbal0gLSBhcnJheVtpXTsgfSk7CiAgICAgICAgICBmb3IgKGogPSAwOyBqIDwgbTsgKytqKSBhcnJheVtqXSA9IGhhbGZlZGdlc1tpbmRleFtqXV07CiAgICAgICAgICBmb3IgKGogPSAwOyBqIDwgbTsgKytqKSBoYWxmZWRnZXNbal0gPSBhcnJheVtqXTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBjbGlwQ2VsbHMkMSh4MCwgeTAsIHgxLCB5MSkgewogICAgICB2YXIgbkNlbGxzID0gY2VsbHMkMS5sZW5ndGgsCiAgICAgICAgICBpQ2VsbCwKICAgICAgICAgIGNlbGwsCiAgICAgICAgICBzaXRlLAogICAgICAgICAgaUhhbGZlZGdlLAogICAgICAgICAgaGFsZmVkZ2VzLAogICAgICAgICAgbkhhbGZlZGdlcywKICAgICAgICAgIHN0YXJ0LAogICAgICAgICAgc3RhcnRYLAogICAgICAgICAgc3RhcnRZLAogICAgICAgICAgZW5kLAogICAgICAgICAgZW5kWCwKICAgICAgICAgIGVuZFksCiAgICAgICAgICBjb3ZlciA9IHRydWU7CgogICAgICBmb3IgKGlDZWxsID0gMDsgaUNlbGwgPCBuQ2VsbHM7ICsraUNlbGwpIHsKICAgICAgICBpZiAoY2VsbCA9IGNlbGxzJDFbaUNlbGxdKSB7CiAgICAgICAgICBzaXRlID0gY2VsbC5zaXRlOwogICAgICAgICAgaGFsZmVkZ2VzID0gY2VsbC5oYWxmZWRnZXM7CiAgICAgICAgICBpSGFsZmVkZ2UgPSBoYWxmZWRnZXMubGVuZ3RoOwoKICAgICAgICAgIC8vIFJlbW92ZSBhbnkgZGFuZ2xpbmcgY2xpcHBlZCBlZGdlcy4KICAgICAgICAgIHdoaWxlIChpSGFsZmVkZ2UtLSkgewogICAgICAgICAgICBpZiAoIWVkZ2VzJDFbaGFsZmVkZ2VzW2lIYWxmZWRnZV1dKSB7CiAgICAgICAgICAgICAgaGFsZmVkZ2VzLnNwbGljZShpSGFsZmVkZ2UsIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgLy8gSW5zZXJ0IGFueSBib3JkZXIgZWRnZXMgYXMgbmVjZXNzYXJ5LgogICAgICAgICAgaUhhbGZlZGdlID0gMCwgbkhhbGZlZGdlcyA9IGhhbGZlZGdlcy5sZW5ndGg7CiAgICAgICAgICB3aGlsZSAoaUhhbGZlZGdlIDwgbkhhbGZlZGdlcykgewogICAgICAgICAgICBlbmQgPSBjZWxsSGFsZmVkZ2VFbmQkMShjZWxsLCBlZGdlcyQxW2hhbGZlZGdlc1tpSGFsZmVkZ2VdXSksIGVuZFggPSBlbmRbMF0sIGVuZFkgPSBlbmRbMV07CiAgICAgICAgICAgIHN0YXJ0ID0gY2VsbEhhbGZlZGdlU3RhcnQkMShjZWxsLCBlZGdlcyQxW2hhbGZlZGdlc1srK2lIYWxmZWRnZSAlIG5IYWxmZWRnZXNdXSksIHN0YXJ0WCA9IHN0YXJ0WzBdLCBzdGFydFkgPSBzdGFydFsxXTsKICAgICAgICAgICAgaWYgKE1hdGguYWJzKGVuZFggLSBzdGFydFgpID4gZXBzaWxvbiRiIHx8IE1hdGguYWJzKGVuZFkgLSBzdGFydFkpID4gZXBzaWxvbiRiKSB7CiAgICAgICAgICAgICAgaGFsZmVkZ2VzLnNwbGljZShpSGFsZmVkZ2UsIDAsIGVkZ2VzJDEucHVzaChjcmVhdGVCb3JkZXJFZGdlJDEoc2l0ZSwgZW5kLAogICAgICAgICAgICAgICAgICBNYXRoLmFicyhlbmRYIC0geDApIDwgZXBzaWxvbiRiICYmIHkxIC0gZW5kWSA+IGVwc2lsb24kYiA/IFt4MCwgTWF0aC5hYnMoc3RhcnRYIC0geDApIDwgZXBzaWxvbiRiID8gc3RhcnRZIDogeTFdCiAgICAgICAgICAgICAgICAgIDogTWF0aC5hYnMoZW5kWSAtIHkxKSA8IGVwc2lsb24kYiAmJiB4MSAtIGVuZFggPiBlcHNpbG9uJGIgPyBbTWF0aC5hYnMoc3RhcnRZIC0geTEpIDwgZXBzaWxvbiRiID8gc3RhcnRYIDogeDEsIHkxXQogICAgICAgICAgICAgICAgICA6IE1hdGguYWJzKGVuZFggLSB4MSkgPCBlcHNpbG9uJGIgJiYgZW5kWSAtIHkwID4gZXBzaWxvbiRiID8gW3gxLCBNYXRoLmFicyhzdGFydFggLSB4MSkgPCBlcHNpbG9uJGIgPyBzdGFydFkgOiB5MF0KICAgICAgICAgICAgICAgICAgOiBNYXRoLmFicyhlbmRZIC0geTApIDwgZXBzaWxvbiRiICYmIGVuZFggLSB4MCA+IGVwc2lsb24kYiA/IFtNYXRoLmFicyhzdGFydFkgLSB5MCkgPCBlcHNpbG9uJGIgPyBzdGFydFggOiB4MCwgeTBdCiAgICAgICAgICAgICAgICAgIDogbnVsbCkpIC0gMSk7CiAgICAgICAgICAgICAgKytuSGFsZmVkZ2VzOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKG5IYWxmZWRnZXMpIGNvdmVyID0gZmFsc2U7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBJZiB0aGVyZSB3ZXJlbuKAmXQgYW55IGVkZ2VzLCBoYXZlIHRoZSBjbG9zZXN0IHNpdGUgY292ZXIgdGhlIGV4dGVudC4KICAgICAgLy8gSXQgZG9lc27igJl0IG1hdHRlciB3aGljaCBjb3JuZXIgb2YgdGhlIGV4dGVudCB3ZSBtZWFzdXJlIQogICAgICBpZiAoY292ZXIpIHsKICAgICAgICB2YXIgZHgsIGR5LCBkMiwgZGMgPSBJbmZpbml0eTsKCiAgICAgICAgZm9yIChpQ2VsbCA9IDAsIGNvdmVyID0gbnVsbDsgaUNlbGwgPCBuQ2VsbHM7ICsraUNlbGwpIHsKICAgICAgICAgIGlmIChjZWxsID0gY2VsbHMkMVtpQ2VsbF0pIHsKICAgICAgICAgICAgc2l0ZSA9IGNlbGwuc2l0ZTsKICAgICAgICAgICAgZHggPSBzaXRlWzBdIC0geDA7CiAgICAgICAgICAgIGR5ID0gc2l0ZVsxXSAtIHkwOwogICAgICAgICAgICBkMiA9IGR4ICogZHggKyBkeSAqIGR5OwogICAgICAgICAgICBpZiAoZDIgPCBkYykgZGMgPSBkMiwgY292ZXIgPSBjZWxsOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgaWYgKGNvdmVyKSB7CiAgICAgICAgICB2YXIgdjAwID0gW3gwLCB5MF0sIHYwMSA9IFt4MCwgeTFdLCB2MTEgPSBbeDEsIHkxXSwgdjEwID0gW3gxLCB5MF07CiAgICAgICAgICBjb3Zlci5oYWxmZWRnZXMucHVzaCgKICAgICAgICAgICAgZWRnZXMkMS5wdXNoKGNyZWF0ZUJvcmRlckVkZ2UkMShzaXRlID0gY292ZXIuc2l0ZSwgdjAwLCB2MDEpKSAtIDEsCiAgICAgICAgICAgIGVkZ2VzJDEucHVzaChjcmVhdGVCb3JkZXJFZGdlJDEoc2l0ZSwgdjAxLCB2MTEpKSAtIDEsCiAgICAgICAgICAgIGVkZ2VzJDEucHVzaChjcmVhdGVCb3JkZXJFZGdlJDEoc2l0ZSwgdjExLCB2MTApKSAtIDEsCiAgICAgICAgICAgIGVkZ2VzJDEucHVzaChjcmVhdGVCb3JkZXJFZGdlJDEoc2l0ZSwgdjEwLCB2MDApKSAtIDEKICAgICAgICAgICk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBMYXN0bHkgZGVsZXRlIGFueSBjZWxscyB3aXRoIG5vIGVkZ2VzOyB0aGVzZSB3ZXJlIGVudGlyZWx5IGNsaXBwZWQuCiAgICAgIGZvciAoaUNlbGwgPSAwOyBpQ2VsbCA8IG5DZWxsczsgKytpQ2VsbCkgewogICAgICAgIGlmIChjZWxsID0gY2VsbHMkMVtpQ2VsbF0pIHsKICAgICAgICAgIGlmICghY2VsbC5oYWxmZWRnZXMubGVuZ3RoKSB7CiAgICAgICAgICAgIGRlbGV0ZSBjZWxscyQxW2lDZWxsXTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICB2YXIgY2lyY2xlUG9vbCQxID0gW107CgogICAgdmFyIGZpcnN0Q2lyY2xlJDE7CgogICAgZnVuY3Rpb24gQ2lyY2xlJDEoKSB7CiAgICAgIFJlZEJsYWNrTm9kZSQxKHRoaXMpOwogICAgICB0aGlzLnggPQogICAgICB0aGlzLnkgPQogICAgICB0aGlzLmFyYyA9CiAgICAgIHRoaXMuc2l0ZSA9CiAgICAgIHRoaXMuY3kgPSBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dGFjaENpcmNsZSQxKGFyYykgewogICAgICB2YXIgbEFyYyA9IGFyYy5QLAogICAgICAgICAgckFyYyA9IGFyYy5OOwoKICAgICAgaWYgKCFsQXJjIHx8ICFyQXJjKSByZXR1cm47CgogICAgICB2YXIgbFNpdGUgPSBsQXJjLnNpdGUsCiAgICAgICAgICBjU2l0ZSA9IGFyYy5zaXRlLAogICAgICAgICAgclNpdGUgPSByQXJjLnNpdGU7CgogICAgICBpZiAobFNpdGUgPT09IHJTaXRlKSByZXR1cm47CgogICAgICB2YXIgYnggPSBjU2l0ZVswXSwKICAgICAgICAgIGJ5ID0gY1NpdGVbMV0sCiAgICAgICAgICBheCA9IGxTaXRlWzBdIC0gYngsCiAgICAgICAgICBheSA9IGxTaXRlWzFdIC0gYnksCiAgICAgICAgICBjeCA9IHJTaXRlWzBdIC0gYngsCiAgICAgICAgICBjeSA9IHJTaXRlWzFdIC0gYnk7CgogICAgICB2YXIgZCA9IDIgKiAoYXggKiBjeSAtIGF5ICogY3gpOwogICAgICBpZiAoZCA+PSAtZXBzaWxvbjIkNSkgcmV0dXJuOwoKICAgICAgdmFyIGhhID0gYXggKiBheCArIGF5ICogYXksCiAgICAgICAgICBoYyA9IGN4ICogY3ggKyBjeSAqIGN5LAogICAgICAgICAgeCA9IChjeSAqIGhhIC0gYXkgKiBoYykgLyBkLAogICAgICAgICAgeSA9IChheCAqIGhjIC0gY3ggKiBoYSkgLyBkOwoKICAgICAgdmFyIGNpcmNsZSA9IGNpcmNsZVBvb2wkMS5wb3AoKSB8fCBuZXcgQ2lyY2xlJDE7CiAgICAgIGNpcmNsZS5hcmMgPSBhcmM7CiAgICAgIGNpcmNsZS5zaXRlID0gY1NpdGU7CiAgICAgIGNpcmNsZS54ID0geCArIGJ4OwogICAgICBjaXJjbGUueSA9IChjaXJjbGUuY3kgPSB5ICsgYnkpICsgTWF0aC5zcXJ0KHggKiB4ICsgeSAqIHkpOyAvLyB5IGJvdHRvbQoKICAgICAgYXJjLmNpcmNsZSA9IGNpcmNsZTsKCiAgICAgIHZhciBiZWZvcmUgPSBudWxsLAogICAgICAgICAgbm9kZSA9IGNpcmNsZXMkMS5fOwoKICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICBpZiAoY2lyY2xlLnkgPCBub2RlLnkgfHwgKGNpcmNsZS55ID09PSBub2RlLnkgJiYgY2lyY2xlLnggPD0gbm9kZS54KSkgewogICAgICAgICAgaWYgKG5vZGUuTCkgbm9kZSA9IG5vZGUuTDsKICAgICAgICAgIGVsc2UgeyBiZWZvcmUgPSBub2RlLlA7IGJyZWFrOyB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChub2RlLlIpIG5vZGUgPSBub2RlLlI7CiAgICAgICAgICBlbHNlIHsgYmVmb3JlID0gbm9kZTsgYnJlYWs7IH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIGNpcmNsZXMkMS5pbnNlcnQoYmVmb3JlLCBjaXJjbGUpOwogICAgICBpZiAoIWJlZm9yZSkgZmlyc3RDaXJjbGUkMSA9IGNpcmNsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZXRhY2hDaXJjbGUkMShhcmMpIHsKICAgICAgdmFyIGNpcmNsZSA9IGFyYy5jaXJjbGU7CiAgICAgIGlmIChjaXJjbGUpIHsKICAgICAgICBpZiAoIWNpcmNsZS5QKSBmaXJzdENpcmNsZSQxID0gY2lyY2xlLk47CiAgICAgICAgY2lyY2xlcyQxLnJlbW92ZShjaXJjbGUpOwogICAgICAgIGNpcmNsZVBvb2wkMS5wdXNoKGNpcmNsZSk7CiAgICAgICAgUmVkQmxhY2tOb2RlJDEoY2lyY2xlKTsKICAgICAgICBhcmMuY2lyY2xlID0gbnVsbDsKICAgICAgfQogICAgfQoKICAgIHZhciBiZWFjaFBvb2wkMSA9IFtdOwoKICAgIGZ1bmN0aW9uIEJlYWNoJDEoKSB7CiAgICAgIFJlZEJsYWNrTm9kZSQxKHRoaXMpOwogICAgICB0aGlzLmVkZ2UgPQogICAgICB0aGlzLnNpdGUgPQogICAgICB0aGlzLmNpcmNsZSA9IG51bGw7CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRlQmVhY2gkMShzaXRlKSB7CiAgICAgIHZhciBiZWFjaCA9IGJlYWNoUG9vbCQxLnBvcCgpIHx8IG5ldyBCZWFjaCQxOwogICAgICBiZWFjaC5zaXRlID0gc2l0ZTsKICAgICAgcmV0dXJuIGJlYWNoOwogICAgfQoKICAgIGZ1bmN0aW9uIGRldGFjaEJlYWNoJDEoYmVhY2gpIHsKICAgICAgZGV0YWNoQ2lyY2xlJDEoYmVhY2gpOwogICAgICBiZWFjaGVzJDEucmVtb3ZlKGJlYWNoKTsKICAgICAgYmVhY2hQb29sJDEucHVzaChiZWFjaCk7CiAgICAgIFJlZEJsYWNrTm9kZSQxKGJlYWNoKTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVCZWFjaCQxKGJlYWNoKSB7CiAgICAgIHZhciBjaXJjbGUgPSBiZWFjaC5jaXJjbGUsCiAgICAgICAgICB4ID0gY2lyY2xlLngsCiAgICAgICAgICB5ID0gY2lyY2xlLmN5LAogICAgICAgICAgdmVydGV4ID0gW3gsIHldLAogICAgICAgICAgcHJldmlvdXMgPSBiZWFjaC5QLAogICAgICAgICAgbmV4dCA9IGJlYWNoLk4sCiAgICAgICAgICBkaXNhcHBlYXJpbmcgPSBbYmVhY2hdOwoKICAgICAgZGV0YWNoQmVhY2gkMShiZWFjaCk7CgogICAgICB2YXIgbEFyYyA9IHByZXZpb3VzOwogICAgICB3aGlsZSAobEFyYy5jaXJjbGUKICAgICAgICAgICYmIE1hdGguYWJzKHggLSBsQXJjLmNpcmNsZS54KSA8IGVwc2lsb24kYgogICAgICAgICAgJiYgTWF0aC5hYnMoeSAtIGxBcmMuY2lyY2xlLmN5KSA8IGVwc2lsb24kYikgewogICAgICAgIHByZXZpb3VzID0gbEFyYy5QOwogICAgICAgIGRpc2FwcGVhcmluZy51bnNoaWZ0KGxBcmMpOwogICAgICAgIGRldGFjaEJlYWNoJDEobEFyYyk7CiAgICAgICAgbEFyYyA9IHByZXZpb3VzOwogICAgICB9CgogICAgICBkaXNhcHBlYXJpbmcudW5zaGlmdChsQXJjKTsKICAgICAgZGV0YWNoQ2lyY2xlJDEobEFyYyk7CgogICAgICB2YXIgckFyYyA9IG5leHQ7CiAgICAgIHdoaWxlIChyQXJjLmNpcmNsZQogICAgICAgICAgJiYgTWF0aC5hYnMoeCAtIHJBcmMuY2lyY2xlLngpIDwgZXBzaWxvbiRiCiAgICAgICAgICAmJiBNYXRoLmFicyh5IC0gckFyYy5jaXJjbGUuY3kpIDwgZXBzaWxvbiRiKSB7CiAgICAgICAgbmV4dCA9IHJBcmMuTjsKICAgICAgICBkaXNhcHBlYXJpbmcucHVzaChyQXJjKTsKICAgICAgICBkZXRhY2hCZWFjaCQxKHJBcmMpOwogICAgICAgIHJBcmMgPSBuZXh0OwogICAgICB9CgogICAgICBkaXNhcHBlYXJpbmcucHVzaChyQXJjKTsKICAgICAgZGV0YWNoQ2lyY2xlJDEockFyYyk7CgogICAgICB2YXIgbkFyY3MgPSBkaXNhcHBlYXJpbmcubGVuZ3RoLAogICAgICAgICAgaUFyYzsKICAgICAgZm9yIChpQXJjID0gMTsgaUFyYyA8IG5BcmNzOyArK2lBcmMpIHsKICAgICAgICByQXJjID0gZGlzYXBwZWFyaW5nW2lBcmNdOwogICAgICAgIGxBcmMgPSBkaXNhcHBlYXJpbmdbaUFyYyAtIDFdOwogICAgICAgIHNldEVkZ2VFbmQkMShyQXJjLmVkZ2UsIGxBcmMuc2l0ZSwgckFyYy5zaXRlLCB2ZXJ0ZXgpOwogICAgICB9CgogICAgICBsQXJjID0gZGlzYXBwZWFyaW5nWzBdOwogICAgICByQXJjID0gZGlzYXBwZWFyaW5nW25BcmNzIC0gMV07CiAgICAgIHJBcmMuZWRnZSA9IGNyZWF0ZUVkZ2UkMShsQXJjLnNpdGUsIHJBcmMuc2l0ZSwgbnVsbCwgdmVydGV4KTsKCiAgICAgIGF0dGFjaENpcmNsZSQxKGxBcmMpOwogICAgICBhdHRhY2hDaXJjbGUkMShyQXJjKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhZGRCZWFjaCQxKHNpdGUpIHsKICAgICAgdmFyIHggPSBzaXRlWzBdLAogICAgICAgICAgZGlyZWN0cml4ID0gc2l0ZVsxXSwKICAgICAgICAgIGxBcmMsCiAgICAgICAgICByQXJjLAogICAgICAgICAgZHhsLAogICAgICAgICAgZHhyLAogICAgICAgICAgbm9kZSA9IGJlYWNoZXMkMS5fOwoKICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICBkeGwgPSBsZWZ0QnJlYWtQb2ludCQxKG5vZGUsIGRpcmVjdHJpeCkgLSB4OwogICAgICAgIGlmIChkeGwgPiBlcHNpbG9uJGIpIG5vZGUgPSBub2RlLkw7IGVsc2UgewogICAgICAgICAgZHhyID0geCAtIHJpZ2h0QnJlYWtQb2ludCQxKG5vZGUsIGRpcmVjdHJpeCk7CiAgICAgICAgICBpZiAoZHhyID4gZXBzaWxvbiRiKSB7CiAgICAgICAgICAgIGlmICghbm9kZS5SKSB7CiAgICAgICAgICAgICAgbEFyYyA9IG5vZGU7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbm9kZSA9IG5vZGUuUjsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGlmIChkeGwgPiAtZXBzaWxvbiRiKSB7CiAgICAgICAgICAgICAgbEFyYyA9IG5vZGUuUDsKICAgICAgICAgICAgICByQXJjID0gbm9kZTsKICAgICAgICAgICAgfSBlbHNlIGlmIChkeHIgPiAtZXBzaWxvbiRiKSB7CiAgICAgICAgICAgICAgbEFyYyA9IG5vZGU7CiAgICAgICAgICAgICAgckFyYyA9IG5vZGUuTjsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBsQXJjID0gckFyYyA9IG5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBjcmVhdGVDZWxsJDEoc2l0ZSk7CiAgICAgIHZhciBuZXdBcmMgPSBjcmVhdGVCZWFjaCQxKHNpdGUpOwogICAgICBiZWFjaGVzJDEuaW5zZXJ0KGxBcmMsIG5ld0FyYyk7CgogICAgICBpZiAoIWxBcmMgJiYgIXJBcmMpIHJldHVybjsKCiAgICAgIGlmIChsQXJjID09PSByQXJjKSB7CiAgICAgICAgZGV0YWNoQ2lyY2xlJDEobEFyYyk7CiAgICAgICAgckFyYyA9IGNyZWF0ZUJlYWNoJDEobEFyYy5zaXRlKTsKICAgICAgICBiZWFjaGVzJDEuaW5zZXJ0KG5ld0FyYywgckFyYyk7CiAgICAgICAgbmV3QXJjLmVkZ2UgPSByQXJjLmVkZ2UgPSBjcmVhdGVFZGdlJDEobEFyYy5zaXRlLCBuZXdBcmMuc2l0ZSk7CiAgICAgICAgYXR0YWNoQ2lyY2xlJDEobEFyYyk7CiAgICAgICAgYXR0YWNoQ2lyY2xlJDEockFyYyk7CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBpZiAoIXJBcmMpIHsgLy8gJiYgbEFyYwogICAgICAgIG5ld0FyYy5lZGdlID0gY3JlYXRlRWRnZSQxKGxBcmMuc2l0ZSwgbmV3QXJjLnNpdGUpOwogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgLy8gZWxzZSBsQXJjICE9PSByQXJjCiAgICAgIGRldGFjaENpcmNsZSQxKGxBcmMpOwogICAgICBkZXRhY2hDaXJjbGUkMShyQXJjKTsKCiAgICAgIHZhciBsU2l0ZSA9IGxBcmMuc2l0ZSwKICAgICAgICAgIGF4ID0gbFNpdGVbMF0sCiAgICAgICAgICBheSA9IGxTaXRlWzFdLAogICAgICAgICAgYnggPSBzaXRlWzBdIC0gYXgsCiAgICAgICAgICBieSA9IHNpdGVbMV0gLSBheSwKICAgICAgICAgIHJTaXRlID0gckFyYy5zaXRlLAogICAgICAgICAgY3ggPSByU2l0ZVswXSAtIGF4LAogICAgICAgICAgY3kgPSByU2l0ZVsxXSAtIGF5LAogICAgICAgICAgZCA9IDIgKiAoYnggKiBjeSAtIGJ5ICogY3gpLAogICAgICAgICAgaGIgPSBieCAqIGJ4ICsgYnkgKiBieSwKICAgICAgICAgIGhjID0gY3ggKiBjeCArIGN5ICogY3ksCiAgICAgICAgICB2ZXJ0ZXggPSBbKGN5ICogaGIgLSBieSAqIGhjKSAvIGQgKyBheCwgKGJ4ICogaGMgLSBjeCAqIGhiKSAvIGQgKyBheV07CgogICAgICBzZXRFZGdlRW5kJDEockFyYy5lZGdlLCBsU2l0ZSwgclNpdGUsIHZlcnRleCk7CiAgICAgIG5ld0FyYy5lZGdlID0gY3JlYXRlRWRnZSQxKGxTaXRlLCBzaXRlLCBudWxsLCB2ZXJ0ZXgpOwogICAgICByQXJjLmVkZ2UgPSBjcmVhdGVFZGdlJDEoc2l0ZSwgclNpdGUsIG51bGwsIHZlcnRleCk7CiAgICAgIGF0dGFjaENpcmNsZSQxKGxBcmMpOwogICAgICBhdHRhY2hDaXJjbGUkMShyQXJjKTsKICAgIH0KCiAgICBmdW5jdGlvbiBsZWZ0QnJlYWtQb2ludCQxKGFyYywgZGlyZWN0cml4KSB7CiAgICAgIHZhciBzaXRlID0gYXJjLnNpdGUsCiAgICAgICAgICByZm9jeCA9IHNpdGVbMF0sCiAgICAgICAgICByZm9jeSA9IHNpdGVbMV0sCiAgICAgICAgICBwYnkyID0gcmZvY3kgLSBkaXJlY3RyaXg7CgogICAgICBpZiAoIXBieTIpIHJldHVybiByZm9jeDsKCiAgICAgIHZhciBsQXJjID0gYXJjLlA7CiAgICAgIGlmICghbEFyYykgcmV0dXJuIC1JbmZpbml0eTsKCiAgICAgIHNpdGUgPSBsQXJjLnNpdGU7CiAgICAgIHZhciBsZm9jeCA9IHNpdGVbMF0sCiAgICAgICAgICBsZm9jeSA9IHNpdGVbMV0sCiAgICAgICAgICBwbGJ5MiA9IGxmb2N5IC0gZGlyZWN0cml4OwoKICAgICAgaWYgKCFwbGJ5MikgcmV0dXJuIGxmb2N4OwoKICAgICAgdmFyIGhsID0gbGZvY3ggLSByZm9jeCwKICAgICAgICAgIGFieTIgPSAxIC8gcGJ5MiAtIDEgLyBwbGJ5MiwKICAgICAgICAgIGIgPSBobCAvIHBsYnkyOwoKICAgICAgaWYgKGFieTIpIHJldHVybiAoLWIgKyBNYXRoLnNxcnQoYiAqIGIgLSAyICogYWJ5MiAqIChobCAqIGhsIC8gKC0yICogcGxieTIpIC0gbGZvY3kgKyBwbGJ5MiAvIDIgKyByZm9jeSAtIHBieTIgLyAyKSkpIC8gYWJ5MiArIHJmb2N4OwoKICAgICAgcmV0dXJuIChyZm9jeCArIGxmb2N4KSAvIDI7CiAgICB9CgogICAgZnVuY3Rpb24gcmlnaHRCcmVha1BvaW50JDEoYXJjLCBkaXJlY3RyaXgpIHsKICAgICAgdmFyIHJBcmMgPSBhcmMuTjsKICAgICAgaWYgKHJBcmMpIHJldHVybiBsZWZ0QnJlYWtQb2ludCQxKHJBcmMsIGRpcmVjdHJpeCk7CiAgICAgIHZhciBzaXRlID0gYXJjLnNpdGU7CiAgICAgIHJldHVybiBzaXRlWzFdID09PSBkaXJlY3RyaXggPyBzaXRlWzBdIDogSW5maW5pdHk7CiAgICB9CgogICAgdmFyIGVwc2lsb24kYiA9IDFlLTY7CiAgICB2YXIgZXBzaWxvbjIkNSA9IDFlLTEyOwogICAgdmFyIGJlYWNoZXMkMTsKICAgIHZhciBjZWxscyQxOwogICAgdmFyIGNpcmNsZXMkMTsKICAgIHZhciBlZGdlcyQxOwoKICAgIGZ1bmN0aW9uIHRyaWFuZ2xlQXJlYSQxKGEsIGIsIGMpIHsKICAgICAgcmV0dXJuIChhWzBdIC0gY1swXSkgKiAoYlsxXSAtIGFbMV0pIC0gKGFbMF0gLSBiWzBdKSAqIChjWzFdIC0gYVsxXSk7CiAgICB9CgogICAgZnVuY3Rpb24gbGV4aWNvZ3JhcGhpYyQxKGEsIGIpIHsKICAgICAgcmV0dXJuIGJbMV0gLSBhWzFdCiAgICAgICAgICB8fCBiWzBdIC0gYVswXTsKICAgIH0KCiAgICBmdW5jdGlvbiBEaWFncmFtJDEoc2l0ZXMsIGV4dGVudCkgewogICAgICB2YXIgc2l0ZSA9IHNpdGVzLnNvcnQobGV4aWNvZ3JhcGhpYyQxKS5wb3AoKSwKICAgICAgICAgIHgsCiAgICAgICAgICB5LAogICAgICAgICAgY2lyY2xlOwoKICAgICAgZWRnZXMkMSA9IFtdOwogICAgICBjZWxscyQxID0gbmV3IEFycmF5KHNpdGVzLmxlbmd0aCk7CiAgICAgIGJlYWNoZXMkMSA9IG5ldyBSZWRCbGFja1RyZWUkMTsKICAgICAgY2lyY2xlcyQxID0gbmV3IFJlZEJsYWNrVHJlZSQxOwoKICAgICAgd2hpbGUgKHRydWUpIHsKICAgICAgICBjaXJjbGUgPSBmaXJzdENpcmNsZSQxOwogICAgICAgIGlmIChzaXRlICYmICghY2lyY2xlIHx8IHNpdGVbMV0gPCBjaXJjbGUueSB8fCAoc2l0ZVsxXSA9PT0gY2lyY2xlLnkgJiYgc2l0ZVswXSA8IGNpcmNsZS54KSkpIHsKICAgICAgICAgIGlmIChzaXRlWzBdICE9PSB4IHx8IHNpdGVbMV0gIT09IHkpIHsKICAgICAgICAgICAgYWRkQmVhY2gkMShzaXRlKTsKICAgICAgICAgICAgeCA9IHNpdGVbMF0sIHkgPSBzaXRlWzFdOwogICAgICAgICAgfQogICAgICAgICAgc2l0ZSA9IHNpdGVzLnBvcCgpOwogICAgICAgIH0gZWxzZSBpZiAoY2lyY2xlKSB7CiAgICAgICAgICByZW1vdmVCZWFjaCQxKGNpcmNsZS5hcmMpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHNvcnRDZWxsSGFsZmVkZ2VzJDEoKTsKCiAgICAgIGlmIChleHRlbnQpIHsKICAgICAgICB2YXIgeDAgPSArZXh0ZW50WzBdWzBdLAogICAgICAgICAgICB5MCA9ICtleHRlbnRbMF1bMV0sCiAgICAgICAgICAgIHgxID0gK2V4dGVudFsxXVswXSwKICAgICAgICAgICAgeTEgPSArZXh0ZW50WzFdWzFdOwogICAgICAgIGNsaXBFZGdlcyQxKHgwLCB5MCwgeDEsIHkxKTsKICAgICAgICBjbGlwQ2VsbHMkMSh4MCwgeTAsIHgxLCB5MSk7CiAgICAgIH0KCiAgICAgIHRoaXMuZWRnZXMgPSBlZGdlcyQxOwogICAgICB0aGlzLmNlbGxzID0gY2VsbHMkMTsKCiAgICAgIGJlYWNoZXMkMSA9CiAgICAgIGNpcmNsZXMkMSA9CiAgICAgIGVkZ2VzJDEgPQogICAgICBjZWxscyQxID0gbnVsbDsKICAgIH0KCiAgICBEaWFncmFtJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogRGlhZ3JhbSQxLAoKICAgICAgcG9seWdvbnM6IGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBlZGdlcyA9IHRoaXMuZWRnZXM7CgogICAgICAgIHJldHVybiB0aGlzLmNlbGxzLm1hcChmdW5jdGlvbihjZWxsKSB7CiAgICAgICAgICB2YXIgcG9seWdvbiA9IGNlbGwuaGFsZmVkZ2VzLm1hcChmdW5jdGlvbihpKSB7IHJldHVybiBjZWxsSGFsZmVkZ2VTdGFydCQxKGNlbGwsIGVkZ2VzW2ldKTsgfSk7CiAgICAgICAgICBwb2x5Z29uLmRhdGEgPSBjZWxsLnNpdGUuZGF0YTsKICAgICAgICAgIHJldHVybiBwb2x5Z29uOwogICAgICAgIH0pOwogICAgICB9LAoKICAgICAgdHJpYW5nbGVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdHJpYW5nbGVzID0gW10sCiAgICAgICAgICAgIGVkZ2VzID0gdGhpcy5lZGdlczsKCiAgICAgICAgdGhpcy5jZWxscy5mb3JFYWNoKGZ1bmN0aW9uKGNlbGwsIGkpIHsKICAgICAgICAgIGlmICghKG0gPSAoaGFsZmVkZ2VzID0gY2VsbC5oYWxmZWRnZXMpLmxlbmd0aCkpIHJldHVybjsKICAgICAgICAgIHZhciBzaXRlID0gY2VsbC5zaXRlLAogICAgICAgICAgICAgIGhhbGZlZGdlcywKICAgICAgICAgICAgICBqID0gLTEsCiAgICAgICAgICAgICAgbSwKICAgICAgICAgICAgICBzMCwKICAgICAgICAgICAgICBlMSA9IGVkZ2VzW2hhbGZlZGdlc1ttIC0gMV1dLAogICAgICAgICAgICAgIHMxID0gZTEubGVmdCA9PT0gc2l0ZSA/IGUxLnJpZ2h0IDogZTEubGVmdDsKCiAgICAgICAgICB3aGlsZSAoKytqIDwgbSkgewogICAgICAgICAgICBzMCA9IHMxOwogICAgICAgICAgICBlMSA9IGVkZ2VzW2hhbGZlZGdlc1tqXV07CiAgICAgICAgICAgIHMxID0gZTEubGVmdCA9PT0gc2l0ZSA/IGUxLnJpZ2h0IDogZTEubGVmdDsKICAgICAgICAgICAgaWYgKHMwICYmIHMxICYmIGkgPCBzMC5pbmRleCAmJiBpIDwgczEuaW5kZXggJiYgdHJpYW5nbGVBcmVhJDEoc2l0ZSwgczAsIHMxKSA8IDApIHsKICAgICAgICAgICAgICB0cmlhbmdsZXMucHVzaChbc2l0ZS5kYXRhLCBzMC5kYXRhLCBzMS5kYXRhXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgcmV0dXJuIHRyaWFuZ2xlczsKICAgICAgfSwKCiAgICAgIGxpbmtzOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5lZGdlcy5maWx0ZXIoZnVuY3Rpb24oZWRnZSkgewogICAgICAgICAgcmV0dXJuIGVkZ2UucmlnaHQ7CiAgICAgICAgfSkubWFwKGZ1bmN0aW9uKGVkZ2UpIHsKICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIHNvdXJjZTogZWRnZS5sZWZ0LmRhdGEsCiAgICAgICAgICAgIHRhcmdldDogZWRnZS5yaWdodC5kYXRhCiAgICAgICAgICB9OwogICAgICAgIH0pOwogICAgICB9LAoKICAgICAgZmluZDogZnVuY3Rpb24oeCwgeSwgcmFkaXVzKSB7CiAgICAgICAgdmFyIHRoYXQgPSB0aGlzLCBpMCwgaTEgPSB0aGF0Ll9mb3VuZCB8fCAwLCBuID0gdGhhdC5jZWxscy5sZW5ndGgsIGNlbGw7CgogICAgICAgIC8vIFVzZSB0aGUgcHJldmlvdXNseS1mb3VuZCBjZWxsLCBvciBzdGFydCB3aXRoIGFuIGFyYml0cmFyeSBvbmUuCiAgICAgICAgd2hpbGUgKCEoY2VsbCA9IHRoYXQuY2VsbHNbaTFdKSkgaWYgKCsraTEgPj0gbikgcmV0dXJuIG51bGw7CiAgICAgICAgdmFyIGR4ID0geCAtIGNlbGwuc2l0ZVswXSwgZHkgPSB5IC0gY2VsbC5zaXRlWzFdLCBkMiA9IGR4ICogZHggKyBkeSAqIGR5OwoKICAgICAgICAvLyBUcmF2ZXJzZSB0aGUgaGFsZi1lZGdlcyB0byBmaW5kIGEgY2xvc2VyIGNlbGwsIGlmIGFueS4KICAgICAgICBkbyB7CiAgICAgICAgICBjZWxsID0gdGhhdC5jZWxsc1tpMCA9IGkxXSwgaTEgPSBudWxsOwogICAgICAgICAgY2VsbC5oYWxmZWRnZXMuZm9yRWFjaChmdW5jdGlvbihlKSB7CiAgICAgICAgICAgIHZhciBlZGdlID0gdGhhdC5lZGdlc1tlXSwgdiA9IGVkZ2UubGVmdDsKICAgICAgICAgICAgaWYgKCh2ID09PSBjZWxsLnNpdGUgfHwgIXYpICYmICEodiA9IGVkZ2UucmlnaHQpKSByZXR1cm47CiAgICAgICAgICAgIHZhciB2eCA9IHggLSB2WzBdLCB2eSA9IHkgLSB2WzFdLCB2MiA9IHZ4ICogdnggKyB2eSAqIHZ5OwogICAgICAgICAgICBpZiAodjIgPCBkMikgZDIgPSB2MiwgaTEgPSB2LmluZGV4OwogICAgICAgICAgfSk7CiAgICAgICAgfSB3aGlsZSAoaTEgIT09IG51bGwpOwoKICAgICAgICB0aGF0Ll9mb3VuZCA9IGkwOwoKICAgICAgICByZXR1cm4gcmFkaXVzID09IG51bGwgfHwgZDIgPD0gcmFkaXVzICogcmFkaXVzID8gY2VsbC5zaXRlIDogbnVsbDsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiB2b3Jvbm9pJDEoKSB7CiAgICAgIHZhciB4ID0geCQ5LAogICAgICAgICAgeSA9IHkkOSwKICAgICAgICAgIGV4dGVudCA9IG51bGw7CgogICAgICBmdW5jdGlvbiB2b3Jvbm9pKGRhdGEpIHsKICAgICAgICByZXR1cm4gbmV3IERpYWdyYW0kMShkYXRhLm1hcChmdW5jdGlvbihkLCBpKSB7CiAgICAgICAgICB2YXIgcyA9IFtNYXRoLnJvdW5kKHgoZCwgaSwgZGF0YSkgLyBlcHNpbG9uJGIpICogZXBzaWxvbiRiLCBNYXRoLnJvdW5kKHkoZCwgaSwgZGF0YSkgLyBlcHNpbG9uJGIpICogZXBzaWxvbiRiXTsKICAgICAgICAgIHMuaW5kZXggPSBpOwogICAgICAgICAgcy5kYXRhID0gZDsKICAgICAgICAgIHJldHVybiBzOwogICAgICAgIH0pLCBleHRlbnQpOwogICAgICB9CgogICAgICB2b3Jvbm9pLnBvbHlnb25zID0gZnVuY3Rpb24oZGF0YSkgewogICAgICAgIHJldHVybiB2b3Jvbm9pKGRhdGEpLnBvbHlnb25zKCk7CiAgICAgIH07CgogICAgICB2b3Jvbm9pLmxpbmtzID0gZnVuY3Rpb24oZGF0YSkgewogICAgICAgIHJldHVybiB2b3Jvbm9pKGRhdGEpLmxpbmtzKCk7CiAgICAgIH07CgogICAgICB2b3Jvbm9pLnRyaWFuZ2xlcyA9IGZ1bmN0aW9uKGRhdGEpIHsKICAgICAgICByZXR1cm4gdm9yb25vaShkYXRhKS50cmlhbmdsZXMoKTsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kueCA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh4ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkdigrXyksIHZvcm9ub2kpIDogeDsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kueSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/ICh5ID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkdigrXyksIHZvcm9ub2kpIDogeTsKICAgICAgfTsKCiAgICAgIHZvcm9ub2kuZXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGV4dGVudCA9IF8gPT0gbnVsbCA/IG51bGwgOiBbWytfWzBdWzBdLCArX1swXVsxXV0sIFsrX1sxXVswXSwgK19bMV1bMV1dXSwgdm9yb25vaSkgOiBleHRlbnQgJiYgW1tleHRlbnRbMF1bMF0sIGV4dGVudFswXVsxXV0sIFtleHRlbnRbMV1bMF0sIGV4dGVudFsxXVsxXV1dOwogICAgICB9OwoKICAgICAgdm9yb25vaS5zaXplID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGV4dGVudCA9IF8gPT0gbnVsbCA/IG51bGwgOiBbWzAsIDBdLCBbK19bMF0sICtfWzFdXV0sIHZvcm9ub2kpIDogZXh0ZW50ICYmIFtleHRlbnRbMV1bMF0gLSBleHRlbnRbMF1bMF0sIGV4dGVudFsxXVsxXSAtIGV4dGVudFswXVsxXV07CiAgICAgIH07CgogICAgICByZXR1cm4gdm9yb25vaTsKICAgIH0KCiAgICB2YXIgbm9vcCRiID0ge3ZhbHVlOiBmdW5jdGlvbigpIHt9fTsKCiAgICBmdW5jdGlvbiBkaXNwYXRjaCQ2KCkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IGFyZ3VtZW50cy5sZW5ndGgsIF8gPSB7fSwgdDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICghKHQgPSBhcmd1bWVudHNbaV0gKyAiIikgfHwgKHQgaW4gXykgfHwgL1tccy5dLy50ZXN0KHQpKSB0aHJvdyBuZXcgRXJyb3IoImlsbGVnYWwgdHlwZTogIiArIHQpOwogICAgICAgIF9bdF0gPSBbXTsKICAgICAgfQogICAgICByZXR1cm4gbmV3IERpc3BhdGNoJDYoXyk7CiAgICB9CgogICAgZnVuY3Rpb24gRGlzcGF0Y2gkNihfKSB7CiAgICAgIHRoaXMuXyA9IF87CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VUeXBlbmFtZXMkYih0eXBlbmFtZXMsIHR5cGVzKSB7CiAgICAgIHJldHVybiB0eXBlbmFtZXMudHJpbSgpLnNwbGl0KC9efFxzKy8pLm1hcChmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIG5hbWUgPSAiIiwgaSA9IHQuaW5kZXhPZigiLiIpOwogICAgICAgIGlmIChpID49IDApIG5hbWUgPSB0LnNsaWNlKGkgKyAxKSwgdCA9IHQuc2xpY2UoMCwgaSk7CiAgICAgICAgaWYgKHQgJiYgIXR5cGVzLmhhc093blByb3BlcnR5KHQpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHQpOwogICAgICAgIHJldHVybiB7dHlwZTogdCwgbmFtZTogbmFtZX07CiAgICAgIH0pOwogICAgfQoKICAgIERpc3BhdGNoJDYucHJvdG90eXBlID0gZGlzcGF0Y2gkNi5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBEaXNwYXRjaCQ2LAogICAgICBvbjogZnVuY3Rpb24odHlwZW5hbWUsIGNhbGxiYWNrKSB7CiAgICAgICAgdmFyIF8gPSB0aGlzLl8sCiAgICAgICAgICAgIFQgPSBwYXJzZVR5cGVuYW1lcyRiKHR5cGVuYW1lICsgIiIsIF8pLAogICAgICAgICAgICB0LAogICAgICAgICAgICBpID0gLTEsCiAgICAgICAgICAgIG4gPSBULmxlbmd0aDsKCiAgICAgICAgLy8gSWYgbm8gY2FsbGJhY2sgd2FzIHNwZWNpZmllZCwgcmV0dXJuIHRoZSBjYWxsYmFjayBvZiB0aGUgZ2l2ZW4gdHlwZSBhbmQgbmFtZS4KICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICAgIHdoaWxlICgrK2kgPCBuKSBpZiAoKHQgPSAodHlwZW5hbWUgPSBUW2ldKS50eXBlKSAmJiAodCA9IGdldCRhKF9bdF0sIHR5cGVuYW1lLm5hbWUpKSkgcmV0dXJuIHQ7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBJZiBhIHR5cGUgd2FzIHNwZWNpZmllZCwgc2V0IHRoZSBjYWxsYmFjayBmb3IgdGhlIGdpdmVuIHR5cGUgYW5kIG5hbWUuCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBpZiBhIG51bGwgY2FsbGJhY2sgd2FzIHNwZWNpZmllZCwgcmVtb3ZlIGNhbGxiYWNrcyBvZiB0aGUgZ2l2ZW4gbmFtZS4KICAgICAgICBpZiAoY2FsbGJhY2sgIT0gbnVsbCAmJiB0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcigiaW52YWxpZCBjYWxsYmFjazogIiArIGNhbGxiYWNrKTsKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgaWYgKHQgPSAodHlwZW5hbWUgPSBUW2ldKS50eXBlKSBfW3RdID0gc2V0JGUoX1t0XSwgdHlwZW5hbWUubmFtZSwgY2FsbGJhY2spOwogICAgICAgICAgZWxzZSBpZiAoY2FsbGJhY2sgPT0gbnVsbCkgZm9yICh0IGluIF8pIF9bdF0gPSBzZXQkZShfW3RdLCB0eXBlbmFtZS5uYW1lLCBudWxsKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICBjb3B5OiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgY29weSA9IHt9LCBfID0gdGhpcy5fOwogICAgICAgIGZvciAodmFyIHQgaW4gXykgY29weVt0XSA9IF9bdF0uc2xpY2UoKTsKICAgICAgICByZXR1cm4gbmV3IERpc3BhdGNoJDYoY29weSk7CiAgICAgIH0sCiAgICAgIGNhbGw6IGZ1bmN0aW9uKHR5cGUsIHRoYXQpIHsKICAgICAgICBpZiAoKG4gPSBhcmd1bWVudHMubGVuZ3RoIC0gMikgPiAwKSBmb3IgKHZhciBhcmdzID0gbmV3IEFycmF5KG4pLCBpID0gMCwgbiwgdDsgaSA8IG47ICsraSkgYXJnc1tpXSA9IGFyZ3VtZW50c1tpICsgMl07CiAgICAgICAgaWYgKCF0aGlzLl8uaGFzT3duUHJvcGVydHkodHlwZSkpIHRocm93IG5ldyBFcnJvcigidW5rbm93biB0eXBlOiAiICsgdHlwZSk7CiAgICAgICAgZm9yICh0ID0gdGhpcy5fW3R5cGVdLCBpID0gMCwgbiA9IHQubGVuZ3RoOyBpIDwgbjsgKytpKSB0W2ldLnZhbHVlLmFwcGx5KHRoYXQsIGFyZ3MpOwogICAgICB9LAogICAgICBhcHBseTogZnVuY3Rpb24odHlwZSwgdGhhdCwgYXJncykgewogICAgICAgIGlmICghdGhpcy5fLmhhc093blByb3BlcnR5KHR5cGUpKSB0aHJvdyBuZXcgRXJyb3IoInVua25vd24gdHlwZTogIiArIHR5cGUpOwogICAgICAgIGZvciAodmFyIHQgPSB0aGlzLl9bdHlwZV0sIGkgPSAwLCBuID0gdC5sZW5ndGg7IGkgPCBuOyArK2kpIHRbaV0udmFsdWUuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0KICAgIH07CgogICAgZnVuY3Rpb24gZ2V0JGEodHlwZSwgbmFtZSkgewogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR5cGUubGVuZ3RoLCBjOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKChjID0gdHlwZVtpXSkubmFtZSA9PT0gbmFtZSkgewogICAgICAgICAgcmV0dXJuIGMudmFsdWU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc2V0JGUodHlwZSwgbmFtZSwgY2FsbGJhY2spIHsKICAgICAgZm9yICh2YXIgaSA9IDAsIG4gPSB0eXBlLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgIGlmICh0eXBlW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgIHR5cGVbaV0gPSBub29wJGIsIHR5cGUgPSB0eXBlLnNsaWNlKDAsIGkpLmNvbmNhdCh0eXBlLnNsaWNlKGkgKyAxKSk7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKGNhbGxiYWNrICE9IG51bGwpIHR5cGUucHVzaCh7bmFtZTogbmFtZSwgdmFsdWU6IGNhbGxiYWNrfSk7CiAgICAgIHJldHVybiB0eXBlOwogICAgfQoKICAgIHZhciB4aHRtbCQ1ID0gImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGh0bWwiOwoKICAgIHZhciBuYW1lc3BhY2VzJDUgPSB7CiAgICAgIHN2ZzogImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiwKICAgICAgeGh0bWw6IHhodG1sJDUsCiAgICAgIHhsaW5rOiAiaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIsCiAgICAgIHhtbDogImh0dHA6Ly93d3cudzMub3JnL1hNTC8xOTk4L25hbWVzcGFjZSIsCiAgICAgIHhtbG5zOiAiaHR0cDovL3d3dy53My5vcmcvMjAwMC94bWxucy8iCiAgICB9OwoKICAgIGZ1bmN0aW9uIG5hbWVzcGFjZSQ1KG5hbWUpIHsKICAgICAgdmFyIHByZWZpeCA9IG5hbWUgKz0gIiIsIGkgPSBwcmVmaXguaW5kZXhPZigiOiIpOwogICAgICBpZiAoaSA+PSAwICYmIChwcmVmaXggPSBuYW1lLnNsaWNlKDAsIGkpKSAhPT0gInhtbG5zIikgbmFtZSA9IG5hbWUuc2xpY2UoaSArIDEpOwogICAgICByZXR1cm4gbmFtZXNwYWNlcyQ1Lmhhc093blByb3BlcnR5KHByZWZpeCkgPyB7c3BhY2U6IG5hbWVzcGFjZXMkNVtwcmVmaXhdLCBsb2NhbDogbmFtZX0gOiBuYW1lOwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0b3JJbmhlcml0JDUobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGRvY3VtZW50ID0gdGhpcy5vd25lckRvY3VtZW50LAogICAgICAgICAgICB1cmkgPSB0aGlzLm5hbWVzcGFjZVVSSTsKICAgICAgICByZXR1cm4gdXJpID09PSB4aHRtbCQ1ICYmIGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5uYW1lc3BhY2VVUkkgPT09IHhodG1sJDUKICAgICAgICAgICAgPyBkb2N1bWVudC5jcmVhdGVFbGVtZW50KG5hbWUpCiAgICAgICAgICAgIDogZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKHVyaSwgbmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvckZpeGVkJDUoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLm93bmVyRG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gY3JlYXRvciQ1KG5hbWUpIHsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlJDUobmFtZSk7CiAgICAgIHJldHVybiAoZnVsbG5hbWUubG9jYWwKICAgICAgICAgID8gY3JlYXRvckZpeGVkJDUKICAgICAgICAgIDogY3JlYXRvckluaGVyaXQkNSkoZnVsbG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vbmUkOSgpIHt9CgogICAgZnVuY3Rpb24gc2VsZWN0b3IkNShzZWxlY3RvcikgewogICAgICByZXR1cm4gc2VsZWN0b3IgPT0gbnVsbCA/IG5vbmUkOSA6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zZWxlY3QkNShzZWxlY3QpIHsKICAgICAgaWYgKHR5cGVvZiBzZWxlY3QgIT09ICJmdW5jdGlvbiIpIHNlbGVjdCA9IHNlbGVjdG9yJDUoc2VsZWN0KTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIHN1Ym5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgKHN1Ym5vZGUgPSBzZWxlY3QuY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpKSB7CiAgICAgICAgICAgIGlmICgiX19kYXRhX18iIGluIG5vZGUpIHN1Ym5vZGUuX19kYXRhX18gPSBub2RlLl9fZGF0YV9fOwogICAgICAgICAgICBzdWJncm91cFtpXSA9IHN1Ym5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ4KHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cyk7CiAgICB9CgogICAgZnVuY3Rpb24gZW1wdHkkNygpIHsKICAgICAgcmV0dXJuIFtdOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdG9yQWxsJDUoc2VsZWN0b3IpIHsKICAgICAgcmV0dXJuIHNlbGVjdG9yID09IG51bGwgPyBlbXB0eSQ3IDogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMucXVlcnlTZWxlY3RvckFsbChzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NlbGVjdEFsbCQ1KHNlbGVjdCkgewogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3JBbGwkNShzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gW10sIHBhcmVudHMgPSBbXSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc3ViZ3JvdXBzLnB1c2goc2VsZWN0LmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgaSwgZ3JvdXApKTsKICAgICAgICAgICAgcGFyZW50cy5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kOChzdWJncm91cHMsIHBhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1hdGNoZXIkNihzZWxlY3RvcikgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubWF0Y2hlcyhzZWxlY3Rvcik7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2ZpbHRlciQ1KG1hdGNoKSB7CiAgICAgIGlmICh0eXBlb2YgbWF0Y2ggIT09ICJmdW5jdGlvbiIpIG1hdGNoID0gbWF0Y2hlciQ2KG1hdGNoKTsKCiAgICAgIGZvciAodmFyIGdyb3VwcyA9IHRoaXMuX2dyb3VwcywgbSA9IGdyb3Vwcy5sZW5ndGgsIHN1Ymdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc3ViZ3JvdXAgPSBzdWJncm91cHNbal0gPSBbXSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiBtYXRjaC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkgewogICAgICAgICAgICBzdWJncm91cC5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kOChzdWJncm91cHMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNwYXJzZSQ1KHVwZGF0ZSkgewogICAgICByZXR1cm4gbmV3IEFycmF5KHVwZGF0ZS5sZW5ndGgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9lbnRlciQ1KCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ4KHRoaXMuX2VudGVyIHx8IHRoaXMuX2dyb3Vwcy5tYXAoc3BhcnNlJDUpLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBFbnRlck5vZGUkNShwYXJlbnQsIGRhdHVtKSB7CiAgICAgIHRoaXMub3duZXJEb2N1bWVudCA9IHBhcmVudC5vd25lckRvY3VtZW50OwogICAgICB0aGlzLm5hbWVzcGFjZVVSSSA9IHBhcmVudC5uYW1lc3BhY2VVUkk7CiAgICAgIHRoaXMuX25leHQgPSBudWxsOwogICAgICB0aGlzLl9wYXJlbnQgPSBwYXJlbnQ7CiAgICAgIHRoaXMuX19kYXRhX18gPSBkYXR1bTsKICAgIH0KCiAgICBFbnRlck5vZGUkNS5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBFbnRlck5vZGUkNSwKICAgICAgYXBwZW5kQ2hpbGQ6IGZ1bmN0aW9uKGNoaWxkKSB7IHJldHVybiB0aGlzLl9wYXJlbnQuaW5zZXJ0QmVmb3JlKGNoaWxkLCB0aGlzLl9uZXh0KTsgfSwKICAgICAgaW5zZXJ0QmVmb3JlOiBmdW5jdGlvbihjaGlsZCwgbmV4dCkgeyByZXR1cm4gdGhpcy5fcGFyZW50Lmluc2VydEJlZm9yZShjaGlsZCwgbmV4dCk7IH0sCiAgICAgIHF1ZXJ5U2VsZWN0b3I6IGZ1bmN0aW9uKHNlbGVjdG9yKSB7IHJldHVybiB0aGlzLl9wYXJlbnQucXVlcnlTZWxlY3RvcihzZWxlY3Rvcik7IH0sCiAgICAgIHF1ZXJ5U2VsZWN0b3JBbGw6IGZ1bmN0aW9uKHNlbGVjdG9yKSB7IHJldHVybiB0aGlzLl9wYXJlbnQucXVlcnlTZWxlY3RvckFsbChzZWxlY3Rvcik7IH0KICAgIH07CgogICAgZnVuY3Rpb24gY29uc3RhbnQkdyh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIga2V5UHJlZml4JDcgPSAiJCI7IC8vIFByb3RlY3QgYWdhaW5zdCBrZXlzIGxpa2Ug4oCcX19wcm90b19f4oCdLgoKICAgIGZ1bmN0aW9uIGJpbmRJbmRleCQ1KHBhcmVudCwgZ3JvdXAsIGVudGVyLCB1cGRhdGUsIGV4aXQsIGRhdGEpIHsKICAgICAgdmFyIGkgPSAwLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIGdyb3VwTGVuZ3RoID0gZ3JvdXAubGVuZ3RoLAogICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoOwoKICAgICAgLy8gUHV0IGFueSBub24tbnVsbCBub2RlcyB0aGF0IGZpdCBpbnRvIHVwZGF0ZS4KICAgICAgLy8gUHV0IGFueSBudWxsIG5vZGVzIGludG8gZW50ZXIuCiAgICAgIC8vIFB1dCBhbnkgcmVtYWluaW5nIGRhdGEgaW50byBlbnRlci4KICAgICAgZm9yICg7IGkgPCBkYXRhTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBub2RlLl9fZGF0YV9fID0gZGF0YVtpXTsKICAgICAgICAgIHVwZGF0ZVtpXSA9IG5vZGU7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVudGVyW2ldID0gbmV3IEVudGVyTm9kZSQ1KHBhcmVudCwgZGF0YVtpXSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBQdXQgYW55IG5vbi1udWxsIG5vZGVzIHRoYXQgZG9u4oCZdCBmaXQgaW50byBleGl0LgogICAgICBmb3IgKDsgaSA8IGdyb3VwTGVuZ3RoOyArK2kpIHsKICAgICAgICBpZiAobm9kZSA9IGdyb3VwW2ldKSB7CiAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICB9CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBiaW5kS2V5JDUocGFyZW50LCBncm91cCwgZW50ZXIsIHVwZGF0ZSwgZXhpdCwgZGF0YSwga2V5KSB7CiAgICAgIHZhciBpLAogICAgICAgICAgbm9kZSwKICAgICAgICAgIG5vZGVCeUtleVZhbHVlID0ge30sCiAgICAgICAgICBncm91cExlbmd0aCA9IGdyb3VwLmxlbmd0aCwKICAgICAgICAgIGRhdGFMZW5ndGggPSBkYXRhLmxlbmd0aCwKICAgICAgICAgIGtleVZhbHVlcyA9IG5ldyBBcnJheShncm91cExlbmd0aCksCiAgICAgICAgICBrZXlWYWx1ZTsKCiAgICAgIC8vIENvbXB1dGUgdGhlIGtleSBmb3IgZWFjaCBub2RlLgogICAgICAvLyBJZiBtdWx0aXBsZSBub2RlcyBoYXZlIHRoZSBzYW1lIGtleSwgdGhlIGR1cGxpY2F0ZXMgYXJlIGFkZGVkIHRvIGV4aXQuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAga2V5VmFsdWVzW2ldID0ga2V5VmFsdWUgPSBrZXlQcmVmaXgkNyArIGtleS5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKTsKICAgICAgICAgIGlmIChrZXlWYWx1ZSBpbiBub2RlQnlLZXlWYWx1ZSkgewogICAgICAgICAgICBleGl0W2ldID0gbm9kZTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vZGVCeUtleVZhbHVlW2tleVZhbHVlXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICAvLyBDb21wdXRlIHRoZSBrZXkgZm9yIGVhY2ggZGF0dW0uCiAgICAgIC8vIElmIHRoZXJlIGEgbm9kZSBhc3NvY2lhdGVkIHdpdGggdGhpcyBrZXksIGpvaW4gYW5kIGFkZCBpdCB0byB1cGRhdGUuCiAgICAgIC8vIElmIHRoZXJlIGlzIG5vdCAob3IgdGhlIGtleSBpcyBhIGR1cGxpY2F0ZSksIGFkZCBpdCB0byBlbnRlci4KICAgICAgZm9yIChpID0gMDsgaSA8IGRhdGFMZW5ndGg7ICsraSkgewogICAgICAgIGtleVZhbHVlID0ga2V5UHJlZml4JDcgKyBrZXkuY2FsbChwYXJlbnQsIGRhdGFbaV0sIGksIGRhdGEpOwogICAgICAgIGlmIChub2RlID0gbm9kZUJ5S2V5VmFsdWVba2V5VmFsdWVdKSB7CiAgICAgICAgICB1cGRhdGVbaV0gPSBub2RlOwogICAgICAgICAgbm9kZS5fX2RhdGFfXyA9IGRhdGFbaV07CiAgICAgICAgICBub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZV0gPSBudWxsOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlbnRlcltpXSA9IG5ldyBFbnRlck5vZGUkNShwYXJlbnQsIGRhdGFbaV0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gQWRkIGFueSByZW1haW5pbmcgbm9kZXMgdGhhdCB3ZXJlIG5vdCBib3VuZCB0byBkYXRhIHRvIGV4aXQuCiAgICAgIGZvciAoaSA9IDA7IGkgPCBncm91cExlbmd0aDsgKytpKSB7CiAgICAgICAgaWYgKChub2RlID0gZ3JvdXBbaV0pICYmIChub2RlQnlLZXlWYWx1ZVtrZXlWYWx1ZXNbaV1dID09PSBub2RlKSkgewogICAgICAgICAgZXhpdFtpXSA9IG5vZGU7CiAgICAgICAgfQogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2RhdGEkNSh2YWx1ZSwga2V5KSB7CiAgICAgIGlmICghdmFsdWUpIHsKICAgICAgICBkYXRhID0gbmV3IEFycmF5KHRoaXMuc2l6ZSgpKSwgaiA9IC0xOwogICAgICAgIHRoaXMuZWFjaChmdW5jdGlvbihkKSB7IGRhdGFbKytqXSA9IGQ7IH0pOwogICAgICAgIHJldHVybiBkYXRhOwogICAgICB9CgogICAgICB2YXIgYmluZCA9IGtleSA/IGJpbmRLZXkkNSA6IGJpbmRJbmRleCQ1LAogICAgICAgICAgcGFyZW50cyA9IHRoaXMuX3BhcmVudHMsCiAgICAgICAgICBncm91cHMgPSB0aGlzLl9ncm91cHM7CgogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB2YWx1ZSA9IGNvbnN0YW50JHcodmFsdWUpOwoKICAgICAgZm9yICh2YXIgbSA9IGdyb3Vwcy5sZW5ndGgsIHVwZGF0ZSA9IG5ldyBBcnJheShtKSwgZW50ZXIgPSBuZXcgQXJyYXkobSksIGV4aXQgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHBhcmVudHNbal0sCiAgICAgICAgICAgIGdyb3VwID0gZ3JvdXBzW2pdLAogICAgICAgICAgICBncm91cExlbmd0aCA9IGdyb3VwLmxlbmd0aCwKICAgICAgICAgICAgZGF0YSA9IHZhbHVlLmNhbGwocGFyZW50LCBwYXJlbnQgJiYgcGFyZW50Ll9fZGF0YV9fLCBqLCBwYXJlbnRzKSwKICAgICAgICAgICAgZGF0YUxlbmd0aCA9IGRhdGEubGVuZ3RoLAogICAgICAgICAgICBlbnRlckdyb3VwID0gZW50ZXJbal0gPSBuZXcgQXJyYXkoZGF0YUxlbmd0aCksCiAgICAgICAgICAgIHVwZGF0ZUdyb3VwID0gdXBkYXRlW2pdID0gbmV3IEFycmF5KGRhdGFMZW5ndGgpLAogICAgICAgICAgICBleGl0R3JvdXAgPSBleGl0W2pdID0gbmV3IEFycmF5KGdyb3VwTGVuZ3RoKTsKCiAgICAgICAgYmluZChwYXJlbnQsIGdyb3VwLCBlbnRlckdyb3VwLCB1cGRhdGVHcm91cCwgZXhpdEdyb3VwLCBkYXRhLCBrZXkpOwoKICAgICAgICAvLyBOb3cgY29ubmVjdCB0aGUgZW50ZXIgbm9kZXMgdG8gdGhlaXIgZm9sbG93aW5nIHVwZGF0ZSBub2RlLCBzdWNoIHRoYXQKICAgICAgICAvLyBhcHBlbmRDaGlsZCBjYW4gaW5zZXJ0IHRoZSBtYXRlcmlhbGl6ZWQgZW50ZXIgbm9kZSBiZWZvcmUgdGhpcyBub2RlLAogICAgICAgIC8vIHJhdGhlciB0aGFuIGF0IHRoZSBlbmQgb2YgdGhlIHBhcmVudCBub2RlLgogICAgICAgIGZvciAodmFyIGkwID0gMCwgaTEgPSAwLCBwcmV2aW91cywgbmV4dDsgaTAgPCBkYXRhTGVuZ3RoOyArK2kwKSB7CiAgICAgICAgICBpZiAocHJldmlvdXMgPSBlbnRlckdyb3VwW2kwXSkgewogICAgICAgICAgICBpZiAoaTAgPj0gaTEpIGkxID0gaTAgKyAxOwogICAgICAgICAgICB3aGlsZSAoIShuZXh0ID0gdXBkYXRlR3JvdXBbaTFdKSAmJiArK2kxIDwgZGF0YUxlbmd0aCk7CiAgICAgICAgICAgIHByZXZpb3VzLl9uZXh0ID0gbmV4dCB8fCBudWxsOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgdXBkYXRlID0gbmV3IFNlbGVjdGlvbiQ4KHVwZGF0ZSwgcGFyZW50cyk7CiAgICAgIHVwZGF0ZS5fZW50ZXIgPSBlbnRlcjsKICAgICAgdXBkYXRlLl9leGl0ID0gZXhpdDsKICAgICAgcmV0dXJuIHVwZGF0ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZXhpdCQ1KCkgewogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ4KHRoaXMuX2V4aXQgfHwgdGhpcy5fZ3JvdXBzLm1hcChzcGFyc2UkNSksIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9qb2luJDQob25lbnRlciwgb251cGRhdGUsIG9uZXhpdCkgewogICAgICB2YXIgZW50ZXIgPSB0aGlzLmVudGVyKCksIHVwZGF0ZSA9IHRoaXMsIGV4aXQgPSB0aGlzLmV4aXQoKTsKICAgICAgZW50ZXIgPSB0eXBlb2Ygb25lbnRlciA9PT0gImZ1bmN0aW9uIiA/IG9uZW50ZXIoZW50ZXIpIDogZW50ZXIuYXBwZW5kKG9uZW50ZXIgKyAiIik7CiAgICAgIGlmIChvbnVwZGF0ZSAhPSBudWxsKSB1cGRhdGUgPSBvbnVwZGF0ZSh1cGRhdGUpOwogICAgICBpZiAob25leGl0ID09IG51bGwpIGV4aXQucmVtb3ZlKCk7IGVsc2Ugb25leGl0KGV4aXQpOwogICAgICByZXR1cm4gZW50ZXIgJiYgdXBkYXRlID8gZW50ZXIubWVyZ2UodXBkYXRlKS5vcmRlcigpIDogdXBkYXRlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9tZXJnZSQ1KHNlbGVjdGlvbikgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzMCA9IHRoaXMuX2dyb3VwcywgZ3JvdXBzMSA9IHNlbGVjdGlvbi5fZ3JvdXBzLCBtMCA9IGdyb3VwczAubGVuZ3RoLCBtMSA9IGdyb3VwczEubGVuZ3RoLCBtID0gTWF0aC5taW4obTAsIG0xKSwgbWVyZ2VzID0gbmV3IEFycmF5KG0wKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cDAgPSBncm91cHMwW2pdLCBncm91cDEgPSBncm91cHMxW2pdLCBuID0gZ3JvdXAwLmxlbmd0aCwgbWVyZ2UgPSBtZXJnZXNbal0gPSBuZXcgQXJyYXkobiksIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAobm9kZSA9IGdyb3VwMFtpXSB8fCBncm91cDFbaV0pIHsKICAgICAgICAgICAgbWVyZ2VbaV0gPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgZm9yICg7IGogPCBtMDsgKytqKSB7CiAgICAgICAgbWVyZ2VzW2pdID0gZ3JvdXBzMFtqXTsKICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBTZWxlY3Rpb24kOChtZXJnZXMsIHRoaXMuX3BhcmVudHMpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9vcmRlciQ1KCkgewoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBqID0gLTEsIG0gPSBncm91cHMubGVuZ3RoOyArK2ogPCBtOykgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gZ3JvdXAubGVuZ3RoIC0gMSwgbmV4dCA9IGdyb3VwW2ldLCBub2RlOyAtLWkgPj0gMDspIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgaWYgKG5leHQgJiYgbm9kZS5jb21wYXJlRG9jdW1lbnRQb3NpdGlvbihuZXh0KSBeIDQpIG5leHQucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUobm9kZSwgbmV4dCk7CiAgICAgICAgICAgIG5leHQgPSBub2RlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3NvcnQkNShjb21wYXJlKSB7CiAgICAgIGlmICghY29tcGFyZSkgY29tcGFyZSA9IGFzY2VuZGluZyRkOwoKICAgICAgZnVuY3Rpb24gY29tcGFyZU5vZGUoYSwgYikgewogICAgICAgIHJldHVybiBhICYmIGIgPyBjb21wYXJlKGEuX19kYXRhX18sIGIuX19kYXRhX18pIDogIWEgLSAhYjsKICAgICAgfQoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc29ydGdyb3VwcyA9IG5ldyBBcnJheShtKSwgaiA9IDA7IGogPCBtOyArK2opIHsKICAgICAgICBmb3IgKHZhciBncm91cCA9IGdyb3Vwc1tqXSwgbiA9IGdyb3VwLmxlbmd0aCwgc29ydGdyb3VwID0gc29ydGdyb3Vwc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXBbaV0pIHsKICAgICAgICAgICAgc29ydGdyb3VwW2ldID0gbm9kZTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgc29ydGdyb3VwLnNvcnQoY29tcGFyZU5vZGUpOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFNlbGVjdGlvbiQ4KHNvcnRncm91cHMsIHRoaXMuX3BhcmVudHMpLm9yZGVyKCk7CiAgICB9CgogICAgZnVuY3Rpb24gYXNjZW5kaW5nJGQoYSwgYikgewogICAgICByZXR1cm4gYSA8IGIgPyAtMSA6IGEgPiBiID8gMSA6IGEgPj0gYiA/IDAgOiBOYU47CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2NhbGwkNSgpIHsKICAgICAgdmFyIGNhbGxiYWNrID0gYXJndW1lbnRzWzBdOwogICAgICBhcmd1bWVudHNbMF0gPSB0aGlzOwogICAgICBjYWxsYmFjay5hcHBseShudWxsLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fbm9kZXMkNSgpIHsKICAgICAgdmFyIG5vZGVzID0gbmV3IEFycmF5KHRoaXMuc2l6ZSgpKSwgaSA9IC0xOwogICAgICB0aGlzLmVhY2goZnVuY3Rpb24oKSB7IG5vZGVzWysraV0gPSB0aGlzOyB9KTsKICAgICAgcmV0dXJuIG5vZGVzOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9ub2RlJDUoKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgdmFyIG5vZGUgPSBncm91cFtpXTsKICAgICAgICAgIGlmIChub2RlKSByZXR1cm4gbm9kZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zaXplJDUoKSB7CiAgICAgIHZhciBzaXplID0gMDsKICAgICAgdGhpcy5lYWNoKGZ1bmN0aW9uKCkgeyArK3NpemU7IH0pOwogICAgICByZXR1cm4gc2l6ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZW1wdHkkNSgpIHsKICAgICAgcmV0dXJuICF0aGlzLm5vZGUoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fZWFjaCQ1KGNhbGxiYWNrKSB7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIGogPSAwLCBtID0gZ3JvdXBzLmxlbmd0aDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBpID0gMCwgbiA9IGdyb3VwLmxlbmd0aCwgbm9kZTsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgY2FsbGJhY2suY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCk7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlJDgobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZU5TJDgoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnQkOChuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUobmFtZSwgdmFsdWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJDb25zdGFudE5TJDgoZnVsbG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCwgdmFsdWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJGdW5jdGlvbiQ4KG5hbWUsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgZWxzZSB0aGlzLnNldEF0dHJpYnV0ZShuYW1lLCB2KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb25OUyQ4KGZ1bGxuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBlbHNlIHRoaXMuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCB2KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fYXR0ciQ1KG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQ1KG5hbWUpOwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIG5vZGUgPSB0aGlzLm5vZGUoKTsKICAgICAgICByZXR1cm4gZnVsbG5hbWUubG9jYWwKICAgICAgICAgICAgPyBub2RlLmdldEF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCkKICAgICAgICAgICAgOiBub2RlLmdldEF0dHJpYnV0ZShmdWxsbmFtZSk7CiAgICAgIH0KCiAgICAgIHJldHVybiB0aGlzLmVhY2goKHZhbHVlID09IG51bGwKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0clJlbW92ZU5TJDggOiBhdHRyUmVtb3ZlJDgpIDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyRnVuY3Rpb25OUyQ4IDogYXR0ckZ1bmN0aW9uJDgpCiAgICAgICAgICA6IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJDb25zdGFudE5TJDggOiBhdHRyQ29uc3RhbnQkOCkpKShmdWxsbmFtZSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0VmlldyQ1KG5vZGUpIHsKICAgICAgcmV0dXJuIChub2RlLm93bmVyRG9jdW1lbnQgJiYgbm9kZS5vd25lckRvY3VtZW50LmRlZmF1bHRWaWV3KSAvLyBub2RlIGlzIGEgTm9kZQogICAgICAgICAgfHwgKG5vZGUuZG9jdW1lbnQgJiYgbm9kZSkgLy8gbm9kZSBpcyBhIFdpbmRvdwogICAgICAgICAgfHwgbm9kZS5kZWZhdWx0VmlldzsgLy8gbm9kZSBpcyBhIERvY3VtZW50CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVSZW1vdmUkOChuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLnJlbW92ZVByb3BlcnR5KG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlQ29uc3RhbnQkOChuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgdmFsdWUsIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZUZ1bmN0aW9uJDgobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdiA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgICAgaWYgKHYgPT0gbnVsbCkgdGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKTsKICAgICAgICBlbHNlIHRoaXMuc3R5bGUuc2V0UHJvcGVydHkobmFtZSwgdiwgcHJpb3JpdHkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9zdHlsZSQ1KG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA+IDEKICAgICAgICAgID8gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsCiAgICAgICAgICAgICAgICA/IHN0eWxlUmVtb3ZlJDggOiB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICAgID8gc3R5bGVGdW5jdGlvbiQ4CiAgICAgICAgICAgICAgICA6IHN0eWxlQ29uc3RhbnQkOCkobmFtZSwgdmFsdWUsIHByaW9yaXR5ID09IG51bGwgPyAiIiA6IHByaW9yaXR5KSkKICAgICAgICAgIDogc3R5bGVWYWx1ZSQ1KHRoaXMubm9kZSgpLCBuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVZhbHVlJDUobm9kZSwgbmFtZSkgewogICAgICByZXR1cm4gbm9kZS5zdHlsZS5nZXRQcm9wZXJ0eVZhbHVlKG5hbWUpCiAgICAgICAgICB8fCBkZWZhdWx0VmlldyQ1KG5vZGUpLmdldENvbXB1dGVkU3R5bGUobm9kZSwgbnVsbCkuZ2V0UHJvcGVydHlWYWx1ZShuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwcm9wZXJ0eVJlbW92ZSQ1KG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIGRlbGV0ZSB0aGlzW25hbWVdOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5Q29uc3RhbnQkNShuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpc1tuYW1lXSA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHByb3BlcnR5RnVuY3Rpb24kNShuYW1lLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmICh2ID09IG51bGwpIGRlbGV0ZSB0aGlzW25hbWVdOwogICAgICAgIGVsc2UgdGhpc1tuYW1lXSA9IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3Byb3BlcnR5JDUobmFtZSwgdmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPiAxCiAgICAgICAgICA/IHRoaXMuZWFjaCgodmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgID8gcHJvcGVydHlSZW1vdmUkNSA6IHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gcHJvcGVydHlGdW5jdGlvbiQ1CiAgICAgICAgICAgICAgOiBwcm9wZXJ0eUNvbnN0YW50JDUpKG5hbWUsIHZhbHVlKSkKICAgICAgICAgIDogdGhpcy5ub2RlKClbbmFtZV07CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NBcnJheSQ1KHN0cmluZykgewogICAgICByZXR1cm4gc3RyaW5nLnRyaW0oKS5zcGxpdCgvXnxccysvKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc0xpc3QkNShub2RlKSB7CiAgICAgIHJldHVybiBub2RlLmNsYXNzTGlzdCB8fCBuZXcgQ2xhc3NMaXN0JDUobm9kZSk7CiAgICB9CgogICAgZnVuY3Rpb24gQ2xhc3NMaXN0JDUobm9kZSkgewogICAgICB0aGlzLl9ub2RlID0gbm9kZTsKICAgICAgdGhpcy5fbmFtZXMgPSBjbGFzc0FycmF5JDUobm9kZS5nZXRBdHRyaWJ1dGUoImNsYXNzIikgfHwgIiIpOwogICAgfQoKICAgIENsYXNzTGlzdCQ1LnByb3RvdHlwZSA9IHsKICAgICAgYWRkOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgdmFyIGkgPSB0aGlzLl9uYW1lcy5pbmRleE9mKG5hbWUpOwogICAgICAgIGlmIChpIDwgMCkgewogICAgICAgICAgdGhpcy5fbmFtZXMucHVzaChuYW1lKTsKICAgICAgICAgIHRoaXMuX25vZGUuc2V0QXR0cmlidXRlKCJjbGFzcyIsIHRoaXMuX25hbWVzLmpvaW4oIiAiKSk7CiAgICAgICAgfQogICAgICB9LAogICAgICByZW1vdmU6IGZ1bmN0aW9uKG5hbWUpIHsKICAgICAgICB2YXIgaSA9IHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSk7CiAgICAgICAgaWYgKGkgPj0gMCkgewogICAgICAgICAgdGhpcy5fbmFtZXMuc3BsaWNlKGksIDEpOwogICAgICAgICAgdGhpcy5fbm9kZS5zZXRBdHRyaWJ1dGUoImNsYXNzIiwgdGhpcy5fbmFtZXMuam9pbigiICIpKTsKICAgICAgICB9CiAgICAgIH0sCiAgICAgIGNvbnRhaW5zOiBmdW5jdGlvbihuYW1lKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX25hbWVzLmluZGV4T2YobmFtZSkgPj0gMDsKICAgICAgfQogICAgfTsKCiAgICBmdW5jdGlvbiBjbGFzc2VkQWRkJDUobm9kZSwgbmFtZXMpIHsKICAgICAgdmFyIGxpc3QgPSBjbGFzc0xpc3QkNShub2RlKSwgaSA9IC0xLCBuID0gbmFtZXMubGVuZ3RoOwogICAgICB3aGlsZSAoKytpIDwgbikgbGlzdC5hZGQobmFtZXNbaV0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsYXNzZWRSZW1vdmUkNShub2RlLCBuYW1lcykgewogICAgICB2YXIgbGlzdCA9IGNsYXNzTGlzdCQ1KG5vZGUpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgIHdoaWxlICgrK2kgPCBuKSBsaXN0LnJlbW92ZShuYW1lc1tpXSk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xhc3NlZFRydWUkNShuYW1lcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgY2xhc3NlZEFkZCQ1KHRoaXMsIG5hbWVzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkRmFsc2UkNShuYW1lcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgY2xhc3NlZFJlbW92ZSQ1KHRoaXMsIG5hbWVzKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBjbGFzc2VkRnVuY3Rpb24kNShuYW1lcywgdmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgICh2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpID8gY2xhc3NlZEFkZCQ1IDogY2xhc3NlZFJlbW92ZSQ1KSh0aGlzLCBuYW1lcyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX2NsYXNzZWQkNShuYW1lLCB2YWx1ZSkgewogICAgICB2YXIgbmFtZXMgPSBjbGFzc0FycmF5JDUobmFtZSArICIiKTsKCiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMikgewogICAgICAgIHZhciBsaXN0ID0gY2xhc3NMaXN0JDUodGhpcy5ub2RlKCkpLCBpID0gLTEsIG4gPSBuYW1lcy5sZW5ndGg7CiAgICAgICAgd2hpbGUgKCsraSA8IG4pIGlmICghbGlzdC5jb250YWlucyhuYW1lc1tpXSkpIHJldHVybiBmYWxzZTsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQoKICAgICAgcmV0dXJuIHRoaXMuZWFjaCgodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IGNsYXNzZWRGdW5jdGlvbiQ1IDogdmFsdWUKICAgICAgICAgID8gY2xhc3NlZFRydWUkNQogICAgICAgICAgOiBjbGFzc2VkRmFsc2UkNSkobmFtZXMsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dFJlbW92ZSQ1KCkgewogICAgICB0aGlzLnRleHRDb250ZW50ID0gIiI7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dENvbnN0YW50JDgodmFsdWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0RnVuY3Rpb24kOCh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSB2ID09IG51bGwgPyAiIiA6IHY7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3RleHQkNSh2YWx1ZSkgewogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2godmFsdWUgPT0gbnVsbAogICAgICAgICAgICAgID8gdGV4dFJlbW92ZSQ1IDogKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gdGV4dEZ1bmN0aW9uJDgKICAgICAgICAgICAgICA6IHRleHRDb25zdGFudCQ4KSh2YWx1ZSkpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLnRleHRDb250ZW50OwogICAgfQoKICAgIGZ1bmN0aW9uIGh0bWxSZW1vdmUkNSgpIHsKICAgICAgdGhpcy5pbm5lckhUTUwgPSAiIjsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sQ29uc3RhbnQkNSh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5pbm5lckhUTUwgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBodG1sRnVuY3Rpb24kNSh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHYgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIHRoaXMuaW5uZXJIVE1MID0gdiA9PSBudWxsID8gIiIgOiB2OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9odG1sJDUodmFsdWUpIHsKICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGgKICAgICAgICAgID8gdGhpcy5lYWNoKHZhbHVlID09IG51bGwKICAgICAgICAgICAgICA/IGh0bWxSZW1vdmUkNSA6ICh0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgICAgICA/IGh0bWxGdW5jdGlvbiQ1CiAgICAgICAgICAgICAgOiBodG1sQ29uc3RhbnQkNSkodmFsdWUpKQogICAgICAgICAgOiB0aGlzLm5vZGUoKS5pbm5lckhUTUw7CiAgICB9CgogICAgZnVuY3Rpb24gcmFpc2UkNigpIHsKICAgICAgaWYgKHRoaXMubmV4dFNpYmxpbmcpIHRoaXMucGFyZW50Tm9kZS5hcHBlbmRDaGlsZCh0aGlzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fcmFpc2UkNSgpIHsKICAgICAgcmV0dXJuIHRoaXMuZWFjaChyYWlzZSQ2KTsKICAgIH0KCiAgICBmdW5jdGlvbiBsb3dlciQ1KCkgewogICAgICBpZiAodGhpcy5wcmV2aW91c1NpYmxpbmcpIHRoaXMucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUodGhpcywgdGhpcy5wYXJlbnROb2RlLmZpcnN0Q2hpbGQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9sb3dlciQ1KCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKGxvd2VyJDUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9hcHBlbmQkNShuYW1lKSB7CiAgICAgIHZhciBjcmVhdGUgPSB0eXBlb2YgbmFtZSA9PT0gImZ1bmN0aW9uIiA/IG5hbWUgOiBjcmVhdG9yJDUobmFtZSk7CiAgICAgIHJldHVybiB0aGlzLnNlbGVjdChmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5hcHBlbmRDaGlsZChjcmVhdGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnN0YW50TnVsbCQ1KCkgewogICAgICByZXR1cm4gbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25faW5zZXJ0JDUobmFtZSwgYmVmb3JlKSB7CiAgICAgIHZhciBjcmVhdGUgPSB0eXBlb2YgbmFtZSA9PT0gImZ1bmN0aW9uIiA/IG5hbWUgOiBjcmVhdG9yJDUobmFtZSksCiAgICAgICAgICBzZWxlY3QgPSBiZWZvcmUgPT0gbnVsbCA/IGNvbnN0YW50TnVsbCQ1IDogdHlwZW9mIGJlZm9yZSA9PT0gImZ1bmN0aW9uIiA/IGJlZm9yZSA6IHNlbGVjdG9yJDUoYmVmb3JlKTsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLmluc2VydEJlZm9yZShjcmVhdGUuYXBwbHkodGhpcywgYXJndW1lbnRzKSwgc2VsZWN0LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgbnVsbCk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHJlbW92ZSQ1KCkgewogICAgICB2YXIgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICBpZiAocGFyZW50KSBwYXJlbnQucmVtb3ZlQ2hpbGQodGhpcyk7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3JlbW92ZSQ1KCkgewogICAgICByZXR1cm4gdGhpcy5lYWNoKHJlbW92ZSQ1KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xvbmVTaGFsbG93JDUoKSB7CiAgICAgIHZhciBjbG9uZSA9IHRoaXMuY2xvbmVOb2RlKGZhbHNlKSwgcGFyZW50ID0gdGhpcy5wYXJlbnROb2RlOwogICAgICByZXR1cm4gcGFyZW50ID8gcGFyZW50Lmluc2VydEJlZm9yZShjbG9uZSwgdGhpcy5uZXh0U2libGluZykgOiBjbG9uZTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fY2xvbmVEZWVwJDUoKSB7CiAgICAgIHZhciBjbG9uZSA9IHRoaXMuY2xvbmVOb2RlKHRydWUpLCBwYXJlbnQgPSB0aGlzLnBhcmVudE5vZGU7CiAgICAgIHJldHVybiBwYXJlbnQgPyBwYXJlbnQuaW5zZXJ0QmVmb3JlKGNsb25lLCB0aGlzLm5leHRTaWJsaW5nKSA6IGNsb25lOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9jbG9uZSQ1KGRlZXApIHsKICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0KGRlZXAgPyBzZWxlY3Rpb25fY2xvbmVEZWVwJDUgOiBzZWxlY3Rpb25fY2xvbmVTaGFsbG93JDUpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kYXR1bSQ1KHZhbHVlKSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMucHJvcGVydHkoIl9fZGF0YV9fIiwgdmFsdWUpCiAgICAgICAgICA6IHRoaXMubm9kZSgpLl9fZGF0YV9fOwogICAgfQoKICAgIHZhciBmaWx0ZXJFdmVudHMkNSA9IHt9OwoKICAgIHZhciBldmVudCQ0ID0gbnVsbDsKCiAgICBpZiAodHlwZW9mIGRvY3VtZW50ICE9PSAidW5kZWZpbmVkIikgewogICAgICB2YXIgZWxlbWVudCQ2ID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50OwogICAgICBpZiAoISgib25tb3VzZWVudGVyIiBpbiBlbGVtZW50JDYpKSB7CiAgICAgICAgZmlsdGVyRXZlbnRzJDUgPSB7bW91c2VlbnRlcjogIm1vdXNlb3ZlciIsIG1vdXNlbGVhdmU6ICJtb3VzZW91dCJ9OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZmlsdGVyQ29udGV4dExpc3RlbmVyJDUobGlzdGVuZXIsIGluZGV4LCBncm91cCkgewogICAgICBsaXN0ZW5lciA9IGNvbnRleHRMaXN0ZW5lciQ1KGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApOwogICAgICByZXR1cm4gZnVuY3Rpb24oZXZlbnQpIHsKICAgICAgICB2YXIgcmVsYXRlZCA9IGV2ZW50LnJlbGF0ZWRUYXJnZXQ7CiAgICAgICAgaWYgKCFyZWxhdGVkIHx8IChyZWxhdGVkICE9PSB0aGlzICYmICEocmVsYXRlZC5jb21wYXJlRG9jdW1lbnRQb3NpdGlvbih0aGlzKSAmIDgpKSkgewogICAgICAgICAgbGlzdGVuZXIuY2FsbCh0aGlzLCBldmVudCk7CiAgICAgICAgfQogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGNvbnRleHRMaXN0ZW5lciQ1KGxpc3RlbmVyLCBpbmRleCwgZ3JvdXApIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGV2ZW50MSkgewogICAgICAgIHZhciBldmVudDAgPSBldmVudCQ0OyAvLyBFdmVudHMgY2FuIGJlIHJlZW50cmFudCAoZS5nLiwgZm9jdXMpLgogICAgICAgIGV2ZW50JDQgPSBldmVudDE7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIGxpc3RlbmVyLmNhbGwodGhpcywgdGhpcy5fX2RhdGFfXywgaW5kZXgsIGdyb3VwKTsKICAgICAgICB9IGZpbmFsbHkgewogICAgICAgICAgZXZlbnQkNCA9IGV2ZW50MDsKICAgICAgICB9CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VUeXBlbmFtZXMkYyh0eXBlbmFtZXMpIHsKICAgICAgcmV0dXJuIHR5cGVuYW1lcy50cmltKCkuc3BsaXQoL158XHMrLykubWFwKGZ1bmN0aW9uKHQpIHsKICAgICAgICB2YXIgbmFtZSA9ICIiLCBpID0gdC5pbmRleE9mKCIuIik7CiAgICAgICAgaWYgKGkgPj0gMCkgbmFtZSA9IHQuc2xpY2UoaSArIDEpLCB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICByZXR1cm4ge3R5cGU6IHQsIG5hbWU6IG5hbWV9OwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBvblJlbW92ZSQ1KHR5cGVuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgb24gPSB0aGlzLl9fb247CiAgICAgICAgaWYgKCFvbikgcmV0dXJuOwogICAgICAgIGZvciAodmFyIGogPSAwLCBpID0gLTEsIG0gPSBvbi5sZW5ndGgsIG87IGogPCBtOyArK2opIHsKICAgICAgICAgIGlmIChvID0gb25bal0sICghdHlwZW5hbWUudHlwZSB8fCBvLnR5cGUgPT09IHR5cGVuYW1lLnR5cGUpICYmIG8ubmFtZSA9PT0gdHlwZW5hbWUubmFtZSkgewogICAgICAgICAgICB0aGlzLnJlbW92ZUV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyLCBvLmNhcHR1cmUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgb25bKytpXSA9IG87CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGlmICgrK2kpIG9uLmxlbmd0aCA9IGk7CiAgICAgICAgZWxzZSBkZWxldGUgdGhpcy5fX29uOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIG9uQWRkJDUodHlwZW5hbWUsIHZhbHVlLCBjYXB0dXJlKSB7CiAgICAgIHZhciB3cmFwID0gZmlsdGVyRXZlbnRzJDUuaGFzT3duUHJvcGVydHkodHlwZW5hbWUudHlwZSkgPyBmaWx0ZXJDb250ZXh0TGlzdGVuZXIkNSA6IGNvbnRleHRMaXN0ZW5lciQ1OwogICAgICByZXR1cm4gZnVuY3Rpb24oZCwgaSwgZ3JvdXApIHsKICAgICAgICB2YXIgb24gPSB0aGlzLl9fb24sIG8sIGxpc3RlbmVyID0gd3JhcCh2YWx1ZSwgaSwgZ3JvdXApOwogICAgICAgIGlmIChvbikgZm9yICh2YXIgaiA9IDAsIG0gPSBvbi5sZW5ndGg7IGogPCBtOyArK2opIHsKICAgICAgICAgIGlmICgobyA9IG9uW2pdKS50eXBlID09PSB0eXBlbmFtZS50eXBlICYmIG8ubmFtZSA9PT0gdHlwZW5hbWUubmFtZSkgewogICAgICAgICAgICB0aGlzLnJlbW92ZUV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyLCBvLmNhcHR1cmUpOwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoby50eXBlLCBvLmxpc3RlbmVyID0gbGlzdGVuZXIsIG8uY2FwdHVyZSA9IGNhcHR1cmUpOwogICAgICAgICAgICBvLnZhbHVlID0gdmFsdWU7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKHR5cGVuYW1lLnR5cGUsIGxpc3RlbmVyLCBjYXB0dXJlKTsKICAgICAgICBvID0ge3R5cGU6IHR5cGVuYW1lLnR5cGUsIG5hbWU6IHR5cGVuYW1lLm5hbWUsIHZhbHVlOiB2YWx1ZSwgbGlzdGVuZXI6IGxpc3RlbmVyLCBjYXB0dXJlOiBjYXB0dXJlfTsKICAgICAgICBpZiAoIW9uKSB0aGlzLl9fb24gPSBbb107CiAgICAgICAgZWxzZSBvbi5wdXNoKG8pOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9vbiQ1KHR5cGVuYW1lLCB2YWx1ZSwgY2FwdHVyZSkgewogICAgICB2YXIgdHlwZW5hbWVzID0gcGFyc2VUeXBlbmFtZXMkYyh0eXBlbmFtZSArICIiKSwgaSwgbiA9IHR5cGVuYW1lcy5sZW5ndGgsIHQ7CgogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHsKICAgICAgICB2YXIgb24gPSB0aGlzLm5vZGUoKS5fX29uOwogICAgICAgIGlmIChvbikgZm9yICh2YXIgaiA9IDAsIG0gPSBvbi5sZW5ndGgsIG87IGogPCBtOyArK2opIHsKICAgICAgICAgIGZvciAoaSA9IDAsIG8gPSBvbltqXTsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAoKHQgPSB0eXBlbmFtZXNbaV0pLnR5cGUgPT09IG8udHlwZSAmJiB0Lm5hbWUgPT09IG8ubmFtZSkgewogICAgICAgICAgICAgIHJldHVybiBvLnZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybjsKICAgICAgfQoKICAgICAgb24gPSB2YWx1ZSA/IG9uQWRkJDUgOiBvblJlbW92ZSQ1OwogICAgICBpZiAoY2FwdHVyZSA9PSBudWxsKSBjYXB0dXJlID0gZmFsc2U7CiAgICAgIGZvciAoaSA9IDA7IGkgPCBuOyArK2kpIHRoaXMuZWFjaChvbih0eXBlbmFtZXNbaV0sIHZhbHVlLCBjYXB0dXJlKSk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIGZ1bmN0aW9uIGN1c3RvbUV2ZW50JDQoZXZlbnQxLCBsaXN0ZW5lciwgdGhhdCwgYXJncykgewogICAgICB2YXIgZXZlbnQwID0gZXZlbnQkNDsKICAgICAgZXZlbnQxLnNvdXJjZUV2ZW50ID0gZXZlbnQkNDsKICAgICAgZXZlbnQkNCA9IGV2ZW50MTsKICAgICAgdHJ5IHsKICAgICAgICByZXR1cm4gbGlzdGVuZXIuYXBwbHkodGhhdCwgYXJncyk7CiAgICAgIH0gZmluYWxseSB7CiAgICAgICAgZXZlbnQkNCA9IGV2ZW50MDsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoRXZlbnQkNShub2RlLCB0eXBlLCBwYXJhbXMpIHsKICAgICAgdmFyIHdpbmRvdyA9IGRlZmF1bHRWaWV3JDUobm9kZSksCiAgICAgICAgICBldmVudCA9IHdpbmRvdy5DdXN0b21FdmVudDsKCiAgICAgIGlmICh0eXBlb2YgZXZlbnQgPT09ICJmdW5jdGlvbiIpIHsKICAgICAgICBldmVudCA9IG5ldyBldmVudCh0eXBlLCBwYXJhbXMpOwogICAgICB9IGVsc2UgewogICAgICAgIGV2ZW50ID0gd2luZG93LmRvY3VtZW50LmNyZWF0ZUV2ZW50KCJFdmVudCIpOwogICAgICAgIGlmIChwYXJhbXMpIGV2ZW50LmluaXRFdmVudCh0eXBlLCBwYXJhbXMuYnViYmxlcywgcGFyYW1zLmNhbmNlbGFibGUpLCBldmVudC5kZXRhaWwgPSBwYXJhbXMuZGV0YWlsOwogICAgICAgIGVsc2UgZXZlbnQuaW5pdEV2ZW50KHR5cGUsIGZhbHNlLCBmYWxzZSk7CiAgICAgIH0KCiAgICAgIG5vZGUuZGlzcGF0Y2hFdmVudChldmVudCk7CiAgICB9CgogICAgZnVuY3Rpb24gZGlzcGF0Y2hDb25zdGFudCQ1KHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGRpc3BhdGNoRXZlbnQkNSh0aGlzLCB0eXBlLCBwYXJhbXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGRpc3BhdGNoRnVuY3Rpb24kNSh0eXBlLCBwYXJhbXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiBkaXNwYXRjaEV2ZW50JDUodGhpcywgdHlwZSwgcGFyYW1zLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9kaXNwYXRjaCQ1KHR5cGUsIHBhcmFtcykgewogICAgICByZXR1cm4gdGhpcy5lYWNoKCh0eXBlb2YgcGFyYW1zID09PSAiZnVuY3Rpb24iCiAgICAgICAgICA/IGRpc3BhdGNoRnVuY3Rpb24kNQogICAgICAgICAgOiBkaXNwYXRjaENvbnN0YW50JDUpKHR5cGUsIHBhcmFtcykpOwogICAgfQoKICAgIHZhciByb290JDggPSBbbnVsbF07CgogICAgZnVuY3Rpb24gU2VsZWN0aW9uJDgoZ3JvdXBzLCBwYXJlbnRzKSB7CiAgICAgIHRoaXMuX2dyb3VwcyA9IGdyb3VwczsKICAgICAgdGhpcy5fcGFyZW50cyA9IHBhcmVudHM7CiAgICB9CgogICAgZnVuY3Rpb24gc2VsZWN0aW9uJDUoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDgoW1tkb2N1bWVudC5kb2N1bWVudEVsZW1lbnRdXSwgcm9vdCQ4KTsKICAgIH0KCiAgICBTZWxlY3Rpb24kOC5wcm90b3R5cGUgPSBzZWxlY3Rpb24kNS5wcm90b3R5cGUgPSB7CiAgICAgIGNvbnN0cnVjdG9yOiBTZWxlY3Rpb24kOCwKICAgICAgc2VsZWN0OiBzZWxlY3Rpb25fc2VsZWN0JDUsCiAgICAgIHNlbGVjdEFsbDogc2VsZWN0aW9uX3NlbGVjdEFsbCQ1LAogICAgICBmaWx0ZXI6IHNlbGVjdGlvbl9maWx0ZXIkNSwKICAgICAgZGF0YTogc2VsZWN0aW9uX2RhdGEkNSwKICAgICAgZW50ZXI6IHNlbGVjdGlvbl9lbnRlciQ1LAogICAgICBleGl0OiBzZWxlY3Rpb25fZXhpdCQ1LAogICAgICBqb2luOiBzZWxlY3Rpb25fam9pbiQ0LAogICAgICBtZXJnZTogc2VsZWN0aW9uX21lcmdlJDUsCiAgICAgIG9yZGVyOiBzZWxlY3Rpb25fb3JkZXIkNSwKICAgICAgc29ydDogc2VsZWN0aW9uX3NvcnQkNSwKICAgICAgY2FsbDogc2VsZWN0aW9uX2NhbGwkNSwKICAgICAgbm9kZXM6IHNlbGVjdGlvbl9ub2RlcyQ1LAogICAgICBub2RlOiBzZWxlY3Rpb25fbm9kZSQ1LAogICAgICBzaXplOiBzZWxlY3Rpb25fc2l6ZSQ1LAogICAgICBlbXB0eTogc2VsZWN0aW9uX2VtcHR5JDUsCiAgICAgIGVhY2g6IHNlbGVjdGlvbl9lYWNoJDUsCiAgICAgIGF0dHI6IHNlbGVjdGlvbl9hdHRyJDUsCiAgICAgIHN0eWxlOiBzZWxlY3Rpb25fc3R5bGUkNSwKICAgICAgcHJvcGVydHk6IHNlbGVjdGlvbl9wcm9wZXJ0eSQ1LAogICAgICBjbGFzc2VkOiBzZWxlY3Rpb25fY2xhc3NlZCQ1LAogICAgICB0ZXh0OiBzZWxlY3Rpb25fdGV4dCQ1LAogICAgICBodG1sOiBzZWxlY3Rpb25faHRtbCQ1LAogICAgICByYWlzZTogc2VsZWN0aW9uX3JhaXNlJDUsCiAgICAgIGxvd2VyOiBzZWxlY3Rpb25fbG93ZXIkNSwKICAgICAgYXBwZW5kOiBzZWxlY3Rpb25fYXBwZW5kJDUsCiAgICAgIGluc2VydDogc2VsZWN0aW9uX2luc2VydCQ1LAogICAgICByZW1vdmU6IHNlbGVjdGlvbl9yZW1vdmUkNSwKICAgICAgY2xvbmU6IHNlbGVjdGlvbl9jbG9uZSQ1LAogICAgICBkYXR1bTogc2VsZWN0aW9uX2RhdHVtJDUsCiAgICAgIG9uOiBzZWxlY3Rpb25fb24kNSwKICAgICAgZGlzcGF0Y2g6IHNlbGVjdGlvbl9kaXNwYXRjaCQ1CiAgICB9OwoKICAgIGZ1bmN0aW9uIHNlbGVjdCQ0KHNlbGVjdG9yKSB7CiAgICAgIHJldHVybiB0eXBlb2Ygc2VsZWN0b3IgPT09ICJzdHJpbmciCiAgICAgICAgICA/IG5ldyBTZWxlY3Rpb24kOChbW2RvY3VtZW50LnF1ZXJ5U2VsZWN0b3Ioc2VsZWN0b3IpXV0sIFtkb2N1bWVudC5kb2N1bWVudEVsZW1lbnRdKQogICAgICAgICAgOiBuZXcgU2VsZWN0aW9uJDgoW1tzZWxlY3Rvcl1dLCByb290JDgpOwogICAgfQoKICAgIGZ1bmN0aW9uIHNvdXJjZUV2ZW50JDQoKSB7CiAgICAgIHZhciBjdXJyZW50ID0gZXZlbnQkNCwgc291cmNlOwogICAgICB3aGlsZSAoc291cmNlID0gY3VycmVudC5zb3VyY2VFdmVudCkgY3VycmVudCA9IHNvdXJjZTsKICAgICAgcmV0dXJuIGN1cnJlbnQ7CiAgICB9CgogICAgZnVuY3Rpb24gcG9pbnQkZShub2RlLCBldmVudCkgewogICAgICB2YXIgc3ZnID0gbm9kZS5vd25lclNWR0VsZW1lbnQgfHwgbm9kZTsKCiAgICAgIGlmIChzdmcuY3JlYXRlU1ZHUG9pbnQpIHsKICAgICAgICB2YXIgcG9pbnQgPSBzdmcuY3JlYXRlU1ZHUG9pbnQoKTsKICAgICAgICBwb2ludC54ID0gZXZlbnQuY2xpZW50WCwgcG9pbnQueSA9IGV2ZW50LmNsaWVudFk7CiAgICAgICAgcG9pbnQgPSBwb2ludC5tYXRyaXhUcmFuc2Zvcm0obm9kZS5nZXRTY3JlZW5DVE0oKS5pbnZlcnNlKCkpOwogICAgICAgIHJldHVybiBbcG9pbnQueCwgcG9pbnQueV07CiAgICAgIH0KCiAgICAgIHZhciByZWN0ID0gbm9kZS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgcmV0dXJuIFtldmVudC5jbGllbnRYIC0gcmVjdC5sZWZ0IC0gbm9kZS5jbGllbnRMZWZ0LCBldmVudC5jbGllbnRZIC0gcmVjdC50b3AgLSBub2RlLmNsaWVudFRvcF07CiAgICB9CgogICAgZnVuY3Rpb24gbW91c2UkNChub2RlKSB7CiAgICAgIHZhciBldmVudCA9IHNvdXJjZUV2ZW50JDQoKTsKICAgICAgaWYgKGV2ZW50LmNoYW5nZWRUb3VjaGVzKSBldmVudCA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzWzBdOwogICAgICByZXR1cm4gcG9pbnQkZShub2RlLCBldmVudCk7CiAgICB9CgogICAgZnVuY3Rpb24gdG91Y2gkMyhub2RlLCB0b3VjaGVzLCBpZGVudGlmaWVyKSB7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMykgaWRlbnRpZmllciA9IHRvdWNoZXMsIHRvdWNoZXMgPSBzb3VyY2VFdmVudCQ0KCkuY2hhbmdlZFRvdWNoZXM7CgogICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHRvdWNoZXMgPyB0b3VjaGVzLmxlbmd0aCA6IDAsIHRvdWNoOyBpIDwgbjsgKytpKSB7CiAgICAgICAgaWYgKCh0b3VjaCA9IHRvdWNoZXNbaV0pLmlkZW50aWZpZXIgPT09IGlkZW50aWZpZXIpIHsKICAgICAgICAgIHJldHVybiBwb2ludCRlKG5vZGUsIHRvdWNoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBudWxsOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vZXZlbnQkNigpIHsKICAgICAgZXZlbnQkNC5wcmV2ZW50RGVmYXVsdCgpOwogICAgICBldmVudCQ0LnN0b3BJbW1lZGlhdGVQcm9wYWdhdGlvbigpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRyYWdEaXNhYmxlJDIodmlldykgewogICAgICB2YXIgcm9vdCA9IHZpZXcuZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LAogICAgICAgICAgc2VsZWN0aW9uID0gc2VsZWN0JDQodmlldykub24oImRyYWdzdGFydC5kcmFnIiwgbm9ldmVudCQ2LCB0cnVlKTsKICAgICAgaWYgKCJvbnNlbGVjdHN0YXJ0IiBpbiByb290KSB7CiAgICAgICAgc2VsZWN0aW9uLm9uKCJzZWxlY3RzdGFydC5kcmFnIiwgbm9ldmVudCQ2LCB0cnVlKTsKICAgICAgfSBlbHNlIHsKICAgICAgICByb290Ll9fbm9zZWxlY3QgPSByb290LnN0eWxlLk1velVzZXJTZWxlY3Q7CiAgICAgICAgcm9vdC5zdHlsZS5Nb3pVc2VyU2VsZWN0ID0gIm5vbmUiOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24geWVzZHJhZyQzKHZpZXcsIG5vY2xpY2spIHsKICAgICAgdmFyIHJvb3QgPSB2aWV3LmRvY3VtZW50LmRvY3VtZW50RWxlbWVudCwKICAgICAgICAgIHNlbGVjdGlvbiA9IHNlbGVjdCQ0KHZpZXcpLm9uKCJkcmFnc3RhcnQuZHJhZyIsIG51bGwpOwogICAgICBpZiAobm9jbGljaykgewogICAgICAgIHNlbGVjdGlvbi5vbigiY2xpY2suZHJhZyIsIG5vZXZlbnQkNiwgdHJ1ZSk7CiAgICAgICAgc2V0VGltZW91dChmdW5jdGlvbigpIHsgc2VsZWN0aW9uLm9uKCJjbGljay5kcmFnIiwgbnVsbCk7IH0sIDApOwogICAgICB9CiAgICAgIGlmICgib25zZWxlY3RzdGFydCIgaW4gcm9vdCkgewogICAgICAgIHNlbGVjdGlvbi5vbigic2VsZWN0c3RhcnQuZHJhZyIsIG51bGwpOwogICAgICB9IGVsc2UgewogICAgICAgIHJvb3Quc3R5bGUuTW96VXNlclNlbGVjdCA9IHJvb3QuX19ub3NlbGVjdDsKICAgICAgICBkZWxldGUgcm9vdC5fX25vc2VsZWN0OwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gZGVmaW5lJDYoY29uc3RydWN0b3IsIGZhY3RvcnksIHByb3RvdHlwZSkgewogICAgICBjb25zdHJ1Y3Rvci5wcm90b3R5cGUgPSBmYWN0b3J5LnByb3RvdHlwZSA9IHByb3RvdHlwZTsKICAgICAgcHJvdG90eXBlLmNvbnN0cnVjdG9yID0gY29uc3RydWN0b3I7CiAgICB9CgogICAgZnVuY3Rpb24gZXh0ZW5kJDYocGFyZW50LCBkZWZpbml0aW9uKSB7CiAgICAgIHZhciBwcm90b3R5cGUgPSBPYmplY3QuY3JlYXRlKHBhcmVudC5wcm90b3R5cGUpOwogICAgICBmb3IgKHZhciBrZXkgaW4gZGVmaW5pdGlvbikgcHJvdG90eXBlW2tleV0gPSBkZWZpbml0aW9uW2tleV07CiAgICAgIHJldHVybiBwcm90b3R5cGU7CiAgICB9CgogICAgZnVuY3Rpb24gQ29sb3IkNigpIHt9CgogICAgdmFyIGRhcmtlciQ2ID0gMC43OwogICAgdmFyIGJyaWdodGVyJDYgPSAxIC8gZGFya2VyJDY7CgogICAgdmFyIHJlSSQ2ID0gIlxccyooWystXT9cXGQrKVxccyoiLAogICAgICAgIHJlTiQ2ID0gIlxccyooWystXT9cXGQqXFwuP1xcZCsoPzpbZUVdWystXT9cXGQrKT8pXFxzKiIsCiAgICAgICAgcmVQJDYgPSAiXFxzKihbKy1dP1xcZCpcXC4/XFxkKyg/OltlRV1bKy1dP1xcZCspPyklXFxzKiIsCiAgICAgICAgcmVIZXgkNSA9IC9eIyhbMC05YS1mXXszLDh9KSQvLAogICAgICAgIHJlUmdiSW50ZWdlciQ2ID0gbmV3IFJlZ0V4cCgiXnJnYlxcKCIgKyBbcmVJJDYsIHJlSSQ2LCByZUkkNl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiUGVyY2VudCQ2ID0gbmV3IFJlZ0V4cCgiXnJnYlxcKCIgKyBbcmVQJDYsIHJlUCQ2LCByZVAkNl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiYUludGVnZXIkNiA9IG5ldyBSZWdFeHAoIl5yZ2JhXFwoIiArIFtyZUkkNiwgcmVJJDYsIHJlSSQ2LCByZU4kNl0gKyAiXFwpJCIpLAogICAgICAgIHJlUmdiYVBlcmNlbnQkNiA9IG5ldyBSZWdFeHAoIl5yZ2JhXFwoIiArIFtyZVAkNiwgcmVQJDYsIHJlUCQ2LCByZU4kNl0gKyAiXFwpJCIpLAogICAgICAgIHJlSHNsUGVyY2VudCQ2ID0gbmV3IFJlZ0V4cCgiXmhzbFxcKCIgKyBbcmVOJDYsIHJlUCQ2LCByZVAkNl0gKyAiXFwpJCIpLAogICAgICAgIHJlSHNsYVBlcmNlbnQkNiA9IG5ldyBSZWdFeHAoIl5oc2xhXFwoIiArIFtyZU4kNiwgcmVQJDYsIHJlUCQ2LCByZU4kNl0gKyAiXFwpJCIpOwoKICAgIHZhciBuYW1lZCQ2ID0gewogICAgICBhbGljZWJsdWU6IDB4ZjBmOGZmLAogICAgICBhbnRpcXVld2hpdGU6IDB4ZmFlYmQ3LAogICAgICBhcXVhOiAweDAwZmZmZiwKICAgICAgYXF1YW1hcmluZTogMHg3ZmZmZDQsCiAgICAgIGF6dXJlOiAweGYwZmZmZiwKICAgICAgYmVpZ2U6IDB4ZjVmNWRjLAogICAgICBiaXNxdWU6IDB4ZmZlNGM0LAogICAgICBibGFjazogMHgwMDAwMDAsCiAgICAgIGJsYW5jaGVkYWxtb25kOiAweGZmZWJjZCwKICAgICAgYmx1ZTogMHgwMDAwZmYsCiAgICAgIGJsdWV2aW9sZXQ6IDB4OGEyYmUyLAogICAgICBicm93bjogMHhhNTJhMmEsCiAgICAgIGJ1cmx5d29vZDogMHhkZWI4ODcsCiAgICAgIGNhZGV0Ymx1ZTogMHg1ZjllYTAsCiAgICAgIGNoYXJ0cmV1c2U6IDB4N2ZmZjAwLAogICAgICBjaG9jb2xhdGU6IDB4ZDI2OTFlLAogICAgICBjb3JhbDogMHhmZjdmNTAsCiAgICAgIGNvcm5mbG93ZXJibHVlOiAweDY0OTVlZCwKICAgICAgY29ybnNpbGs6IDB4ZmZmOGRjLAogICAgICBjcmltc29uOiAweGRjMTQzYywKICAgICAgY3lhbjogMHgwMGZmZmYsCiAgICAgIGRhcmtibHVlOiAweDAwMDA4YiwKICAgICAgZGFya2N5YW46IDB4MDA4YjhiLAogICAgICBkYXJrZ29sZGVucm9kOiAweGI4ODYwYiwKICAgICAgZGFya2dyYXk6IDB4YTlhOWE5LAogICAgICBkYXJrZ3JlZW46IDB4MDA2NDAwLAogICAgICBkYXJrZ3JleTogMHhhOWE5YTksCiAgICAgIGRhcmtraGFraTogMHhiZGI3NmIsCiAgICAgIGRhcmttYWdlbnRhOiAweDhiMDA4YiwKICAgICAgZGFya29saXZlZ3JlZW46IDB4NTU2YjJmLAogICAgICBkYXJrb3JhbmdlOiAweGZmOGMwMCwKICAgICAgZGFya29yY2hpZDogMHg5OTMyY2MsCiAgICAgIGRhcmtyZWQ6IDB4OGIwMDAwLAogICAgICBkYXJrc2FsbW9uOiAweGU5OTY3YSwKICAgICAgZGFya3NlYWdyZWVuOiAweDhmYmM4ZiwKICAgICAgZGFya3NsYXRlYmx1ZTogMHg0ODNkOGIsCiAgICAgIGRhcmtzbGF0ZWdyYXk6IDB4MmY0ZjRmLAogICAgICBkYXJrc2xhdGVncmV5OiAweDJmNGY0ZiwKICAgICAgZGFya3R1cnF1b2lzZTogMHgwMGNlZDEsCiAgICAgIGRhcmt2aW9sZXQ6IDB4OTQwMGQzLAogICAgICBkZWVwcGluazogMHhmZjE0OTMsCiAgICAgIGRlZXBza3libHVlOiAweDAwYmZmZiwKICAgICAgZGltZ3JheTogMHg2OTY5NjksCiAgICAgIGRpbWdyZXk6IDB4Njk2OTY5LAogICAgICBkb2RnZXJibHVlOiAweDFlOTBmZiwKICAgICAgZmlyZWJyaWNrOiAweGIyMjIyMiwKICAgICAgZmxvcmFsd2hpdGU6IDB4ZmZmYWYwLAogICAgICBmb3Jlc3RncmVlbjogMHgyMjhiMjIsCiAgICAgIGZ1Y2hzaWE6IDB4ZmYwMGZmLAogICAgICBnYWluc2Jvcm86IDB4ZGNkY2RjLAogICAgICBnaG9zdHdoaXRlOiAweGY4ZjhmZiwKICAgICAgZ29sZDogMHhmZmQ3MDAsCiAgICAgIGdvbGRlbnJvZDogMHhkYWE1MjAsCiAgICAgIGdyYXk6IDB4ODA4MDgwLAogICAgICBncmVlbjogMHgwMDgwMDAsCiAgICAgIGdyZWVueWVsbG93OiAweGFkZmYyZiwKICAgICAgZ3JleTogMHg4MDgwODAsCiAgICAgIGhvbmV5ZGV3OiAweGYwZmZmMCwKICAgICAgaG90cGluazogMHhmZjY5YjQsCiAgICAgIGluZGlhbnJlZDogMHhjZDVjNWMsCiAgICAgIGluZGlnbzogMHg0YjAwODIsCiAgICAgIGl2b3J5OiAweGZmZmZmMCwKICAgICAga2hha2k6IDB4ZjBlNjhjLAogICAgICBsYXZlbmRlcjogMHhlNmU2ZmEsCiAgICAgIGxhdmVuZGVyYmx1c2g6IDB4ZmZmMGY1LAogICAgICBsYXduZ3JlZW46IDB4N2NmYzAwLAogICAgICBsZW1vbmNoaWZmb246IDB4ZmZmYWNkLAogICAgICBsaWdodGJsdWU6IDB4YWRkOGU2LAogICAgICBsaWdodGNvcmFsOiAweGYwODA4MCwKICAgICAgbGlnaHRjeWFuOiAweGUwZmZmZiwKICAgICAgbGlnaHRnb2xkZW5yb2R5ZWxsb3c6IDB4ZmFmYWQyLAogICAgICBsaWdodGdyYXk6IDB4ZDNkM2QzLAogICAgICBsaWdodGdyZWVuOiAweDkwZWU5MCwKICAgICAgbGlnaHRncmV5OiAweGQzZDNkMywKICAgICAgbGlnaHRwaW5rOiAweGZmYjZjMSwKICAgICAgbGlnaHRzYWxtb246IDB4ZmZhMDdhLAogICAgICBsaWdodHNlYWdyZWVuOiAweDIwYjJhYSwKICAgICAgbGlnaHRza3libHVlOiAweDg3Y2VmYSwKICAgICAgbGlnaHRzbGF0ZWdyYXk6IDB4Nzc4ODk5LAogICAgICBsaWdodHNsYXRlZ3JleTogMHg3Nzg4OTksCiAgICAgIGxpZ2h0c3RlZWxibHVlOiAweGIwYzRkZSwKICAgICAgbGlnaHR5ZWxsb3c6IDB4ZmZmZmUwLAogICAgICBsaW1lOiAweDAwZmYwMCwKICAgICAgbGltZWdyZWVuOiAweDMyY2QzMiwKICAgICAgbGluZW46IDB4ZmFmMGU2LAogICAgICBtYWdlbnRhOiAweGZmMDBmZiwKICAgICAgbWFyb29uOiAweDgwMDAwMCwKICAgICAgbWVkaXVtYXF1YW1hcmluZTogMHg2NmNkYWEsCiAgICAgIG1lZGl1bWJsdWU6IDB4MDAwMGNkLAogICAgICBtZWRpdW1vcmNoaWQ6IDB4YmE1NWQzLAogICAgICBtZWRpdW1wdXJwbGU6IDB4OTM3MGRiLAogICAgICBtZWRpdW1zZWFncmVlbjogMHgzY2IzNzEsCiAgICAgIG1lZGl1bXNsYXRlYmx1ZTogMHg3YjY4ZWUsCiAgICAgIG1lZGl1bXNwcmluZ2dyZWVuOiAweDAwZmE5YSwKICAgICAgbWVkaXVtdHVycXVvaXNlOiAweDQ4ZDFjYywKICAgICAgbWVkaXVtdmlvbGV0cmVkOiAweGM3MTU4NSwKICAgICAgbWlkbmlnaHRibHVlOiAweDE5MTk3MCwKICAgICAgbWludGNyZWFtOiAweGY1ZmZmYSwKICAgICAgbWlzdHlyb3NlOiAweGZmZTRlMSwKICAgICAgbW9jY2FzaW46IDB4ZmZlNGI1LAogICAgICBuYXZham93aGl0ZTogMHhmZmRlYWQsCiAgICAgIG5hdnk6IDB4MDAwMDgwLAogICAgICBvbGRsYWNlOiAweGZkZjVlNiwKICAgICAgb2xpdmU6IDB4ODA4MDAwLAogICAgICBvbGl2ZWRyYWI6IDB4NmI4ZTIzLAogICAgICBvcmFuZ2U6IDB4ZmZhNTAwLAogICAgICBvcmFuZ2VyZWQ6IDB4ZmY0NTAwLAogICAgICBvcmNoaWQ6IDB4ZGE3MGQ2LAogICAgICBwYWxlZ29sZGVucm9kOiAweGVlZThhYSwKICAgICAgcGFsZWdyZWVuOiAweDk4ZmI5OCwKICAgICAgcGFsZXR1cnF1b2lzZTogMHhhZmVlZWUsCiAgICAgIHBhbGV2aW9sZXRyZWQ6IDB4ZGI3MDkzLAogICAgICBwYXBheWF3aGlwOiAweGZmZWZkNSwKICAgICAgcGVhY2hwdWZmOiAweGZmZGFiOSwKICAgICAgcGVydTogMHhjZDg1M2YsCiAgICAgIHBpbms6IDB4ZmZjMGNiLAogICAgICBwbHVtOiAweGRkYTBkZCwKICAgICAgcG93ZGVyYmx1ZTogMHhiMGUwZTYsCiAgICAgIHB1cnBsZTogMHg4MDAwODAsCiAgICAgIHJlYmVjY2FwdXJwbGU6IDB4NjYzMzk5LAogICAgICByZWQ6IDB4ZmYwMDAwLAogICAgICByb3N5YnJvd246IDB4YmM4ZjhmLAogICAgICByb3lhbGJsdWU6IDB4NDE2OWUxLAogICAgICBzYWRkbGVicm93bjogMHg4YjQ1MTMsCiAgICAgIHNhbG1vbjogMHhmYTgwNzIsCiAgICAgIHNhbmR5YnJvd246IDB4ZjRhNDYwLAogICAgICBzZWFncmVlbjogMHgyZThiNTcsCiAgICAgIHNlYXNoZWxsOiAweGZmZjVlZSwKICAgICAgc2llbm5hOiAweGEwNTIyZCwKICAgICAgc2lsdmVyOiAweGMwYzBjMCwKICAgICAgc2t5Ymx1ZTogMHg4N2NlZWIsCiAgICAgIHNsYXRlYmx1ZTogMHg2YTVhY2QsCiAgICAgIHNsYXRlZ3JheTogMHg3MDgwOTAsCiAgICAgIHNsYXRlZ3JleTogMHg3MDgwOTAsCiAgICAgIHNub3c6IDB4ZmZmYWZhLAogICAgICBzcHJpbmdncmVlbjogMHgwMGZmN2YsCiAgICAgIHN0ZWVsYmx1ZTogMHg0NjgyYjQsCiAgICAgIHRhbjogMHhkMmI0OGMsCiAgICAgIHRlYWw6IDB4MDA4MDgwLAogICAgICB0aGlzdGxlOiAweGQ4YmZkOCwKICAgICAgdG9tYXRvOiAweGZmNjM0NywKICAgICAgdHVycXVvaXNlOiAweDQwZTBkMCwKICAgICAgdmlvbGV0OiAweGVlODJlZSwKICAgICAgd2hlYXQ6IDB4ZjVkZWIzLAogICAgICB3aGl0ZTogMHhmZmZmZmYsCiAgICAgIHdoaXRlc21va2U6IDB4ZjVmNWY1LAogICAgICB5ZWxsb3c6IDB4ZmZmZjAwLAogICAgICB5ZWxsb3dncmVlbjogMHg5YWNkMzIKICAgIH07CgogICAgZGVmaW5lJDYoQ29sb3IkNiwgY29sb3IkNiwgewogICAgICBjb3B5OiBmdW5jdGlvbihjaGFubmVscykgewogICAgICAgIHJldHVybiBPYmplY3QuYXNzaWduKG5ldyB0aGlzLmNvbnN0cnVjdG9yLCB0aGlzLCBjaGFubmVscyk7CiAgICAgIH0sCiAgICAgIGRpc3BsYXlhYmxlOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdGhpcy5yZ2IoKS5kaXNwbGF5YWJsZSgpOwogICAgICB9LAogICAgICBoZXg6IGNvbG9yX2Zvcm1hdEhleCQ1LCAvLyBEZXByZWNhdGVkISBVc2UgY29sb3IuZm9ybWF0SGV4LgogICAgICBmb3JtYXRIZXg6IGNvbG9yX2Zvcm1hdEhleCQ1LAogICAgICBmb3JtYXRIc2w6IGNvbG9yX2Zvcm1hdEhzbCQ1LAogICAgICBmb3JtYXRSZ2I6IGNvbG9yX2Zvcm1hdFJnYiQ1LAogICAgICB0b1N0cmluZzogY29sb3JfZm9ybWF0UmdiJDUKICAgIH0pOwoKICAgIGZ1bmN0aW9uIGNvbG9yX2Zvcm1hdEhleCQ1KCkgewogICAgICByZXR1cm4gdGhpcy5yZ2IoKS5mb3JtYXRIZXgoKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvcl9mb3JtYXRIc2wkNSgpIHsKICAgICAgcmV0dXJuIGhzbENvbnZlcnQkNih0aGlzKS5mb3JtYXRIc2woKTsKICAgIH0KCiAgICBmdW5jdGlvbiBjb2xvcl9mb3JtYXRSZ2IkNSgpIHsKICAgICAgcmV0dXJuIHRoaXMucmdiKCkuZm9ybWF0UmdiKCk7CiAgICB9CgogICAgZnVuY3Rpb24gY29sb3IkNihmb3JtYXQpIHsKICAgICAgdmFyIG0sIGw7CiAgICAgIGZvcm1hdCA9IChmb3JtYXQgKyAiIikudHJpbSgpLnRvTG93ZXJDYXNlKCk7CiAgICAgIHJldHVybiAobSA9IHJlSGV4JDUuZXhlYyhmb3JtYXQpKSA/IChsID0gbVsxXS5sZW5ndGgsIG0gPSBwYXJzZUludChtWzFdLCAxNiksIGwgPT09IDYgPyByZ2JuJDYobSkgLy8gI2ZmMDAwMAogICAgICAgICAgOiBsID09PSAzID8gbmV3IFJnYiQ2KChtID4+IDggJiAweGYpIHwgKG0gPj4gNCAmIDB4ZjApLCAobSA+PiA0ICYgMHhmKSB8IChtICYgMHhmMCksICgobSAmIDB4ZikgPDwgNCkgfCAobSAmIDB4ZiksIDEpIC8vICNmMDAKICAgICAgICAgIDogbCA9PT0gOCA/IHJnYmEkNihtID4+IDI0ICYgMHhmZiwgbSA+PiAxNiAmIDB4ZmYsIG0gPj4gOCAmIDB4ZmYsIChtICYgMHhmZikgLyAweGZmKSAvLyAjZmYwMDAwMDAKICAgICAgICAgIDogbCA9PT0gNCA/IHJnYmEkNigobSA+PiAxMiAmIDB4ZikgfCAobSA+PiA4ICYgMHhmMCksIChtID4+IDggJiAweGYpIHwgKG0gPj4gNCAmIDB4ZjApLCAobSA+PiA0ICYgMHhmKSB8IChtICYgMHhmMCksICgoKG0gJiAweGYpIDw8IDQpIHwgKG0gJiAweGYpKSAvIDB4ZmYpIC8vICNmMDAwCiAgICAgICAgICA6IG51bGwpIC8vIGludmFsaWQgaGV4CiAgICAgICAgICA6IChtID0gcmVSZ2JJbnRlZ2VyJDYuZXhlYyhmb3JtYXQpKSA/IG5ldyBSZ2IkNihtWzFdLCBtWzJdLCBtWzNdLCAxKSAvLyByZ2IoMjU1LCAwLCAwKQogICAgICAgICAgOiAobSA9IHJlUmdiUGVyY2VudCQ2LmV4ZWMoZm9ybWF0KSkgPyBuZXcgUmdiJDYobVsxXSAqIDI1NSAvIDEwMCwgbVsyXSAqIDI1NSAvIDEwMCwgbVszXSAqIDI1NSAvIDEwMCwgMSkgLy8gcmdiKDEwMCUsIDAlLCAwJSkKICAgICAgICAgIDogKG0gPSByZVJnYmFJbnRlZ2VyJDYuZXhlYyhmb3JtYXQpKSA/IHJnYmEkNihtWzFdLCBtWzJdLCBtWzNdLCBtWzRdKSAvLyByZ2JhKDI1NSwgMCwgMCwgMSkKICAgICAgICAgIDogKG0gPSByZVJnYmFQZXJjZW50JDYuZXhlYyhmb3JtYXQpKSA/IHJnYmEkNihtWzFdICogMjU1IC8gMTAwLCBtWzJdICogMjU1IC8gMTAwLCBtWzNdICogMjU1IC8gMTAwLCBtWzRdKSAvLyByZ2IoMTAwJSwgMCUsIDAlLCAxKQogICAgICAgICAgOiAobSA9IHJlSHNsUGVyY2VudCQ2LmV4ZWMoZm9ybWF0KSkgPyBoc2xhJDYobVsxXSwgbVsyXSAvIDEwMCwgbVszXSAvIDEwMCwgMSkgLy8gaHNsKDEyMCwgNTAlLCA1MCUpCiAgICAgICAgICA6IChtID0gcmVIc2xhUGVyY2VudCQ2LmV4ZWMoZm9ybWF0KSkgPyBoc2xhJDYobVsxXSwgbVsyXSAvIDEwMCwgbVszXSAvIDEwMCwgbVs0XSkgLy8gaHNsYSgxMjAsIDUwJSwgNTAlLCAxKQogICAgICAgICAgOiBuYW1lZCQ2Lmhhc093blByb3BlcnR5KGZvcm1hdCkgPyByZ2JuJDYobmFtZWQkNltmb3JtYXRdKSAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXByb3RvdHlwZS1idWlsdGlucwogICAgICAgICAgOiBmb3JtYXQgPT09ICJ0cmFuc3BhcmVudCIgPyBuZXcgUmdiJDYoTmFOLCBOYU4sIE5hTiwgMCkKICAgICAgICAgIDogbnVsbDsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2JuJDYobikgewogICAgICByZXR1cm4gbmV3IFJnYiQ2KG4gPj4gMTYgJiAweGZmLCBuID4+IDggJiAweGZmLCBuICYgMHhmZiwgMSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiYSQ2KHIsIGcsIGIsIGEpIHsKICAgICAgaWYgKGEgPD0gMCkgciA9IGcgPSBiID0gTmFOOwogICAgICByZXR1cm4gbmV3IFJnYiQ2KHIsIGcsIGIsIGEpOwogICAgfQoKICAgIGZ1bmN0aW9uIHJnYkNvbnZlcnQkNihvKSB7CiAgICAgIGlmICghKG8gaW5zdGFuY2VvZiBDb2xvciQ2KSkgbyA9IGNvbG9yJDYobyk7CiAgICAgIGlmICghbykgcmV0dXJuIG5ldyBSZ2IkNjsKICAgICAgbyA9IG8ucmdiKCk7CiAgICAgIHJldHVybiBuZXcgUmdiJDYoby5yLCBvLmcsIG8uYiwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZ2IkOChyLCBnLCBiLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gcmdiQ29udmVydCQ2KHIpIDogbmV3IFJnYiQ2KHIsIGcsIGIsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBSZ2IkNihyLCBnLCBiLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuciA9ICtyOwogICAgICB0aGlzLmcgPSArZzsKICAgICAgdGhpcy5iID0gK2I7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGRlZmluZSQ2KFJnYiQ2LCByZ2IkOCwgZXh0ZW5kJDYoQ29sb3IkNiwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBicmlnaHRlciQ2IDogTWF0aC5wb3coYnJpZ2h0ZXIkNiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkNih0aGlzLnIgKiBrLCB0aGlzLmcgKiBrLCB0aGlzLmIgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICBkYXJrZXI6IGZ1bmN0aW9uKGspIHsKICAgICAgICBrID0gayA9PSBudWxsID8gZGFya2VyJDYgOiBNYXRoLnBvdyhkYXJrZXIkNiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBSZ2IkNih0aGlzLnIgKiBrLCB0aGlzLmcgKiBrLCB0aGlzLmIgKiBrLCB0aGlzLm9wYWNpdHkpOwogICAgICB9LAogICAgICByZ2I6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9LAogICAgICBkaXNwbGF5YWJsZTogZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuICgtMC41IDw9IHRoaXMuciAmJiB0aGlzLnIgPCAyNTUuNSkKICAgICAgICAgICAgJiYgKC0wLjUgPD0gdGhpcy5nICYmIHRoaXMuZyA8IDI1NS41KQogICAgICAgICAgICAmJiAoLTAuNSA8PSB0aGlzLmIgJiYgdGhpcy5iIDwgMjU1LjUpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMub3BhY2l0eSAmJiB0aGlzLm9wYWNpdHkgPD0gMSk7CiAgICAgIH0sCiAgICAgIGhleDogcmdiX2Zvcm1hdEhleCQ1LCAvLyBEZXByZWNhdGVkISBVc2UgY29sb3IuZm9ybWF0SGV4LgogICAgICBmb3JtYXRIZXg6IHJnYl9mb3JtYXRIZXgkNSwKICAgICAgZm9ybWF0UmdiOiByZ2JfZm9ybWF0UmdiJDUsCiAgICAgIHRvU3RyaW5nOiByZ2JfZm9ybWF0UmdiJDUKICAgIH0pKTsKCiAgICBmdW5jdGlvbiByZ2JfZm9ybWF0SGV4JDUoKSB7CiAgICAgIHJldHVybiAiIyIgKyBoZXgkNSh0aGlzLnIpICsgaGV4JDUodGhpcy5nKSArIGhleCQ1KHRoaXMuYik7CiAgICB9CgogICAgZnVuY3Rpb24gcmdiX2Zvcm1hdFJnYiQ1KCkgewogICAgICB2YXIgYSA9IHRoaXMub3BhY2l0eTsgYSA9IGlzTmFOKGEpID8gMSA6IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIGEpKTsKICAgICAgcmV0dXJuIChhID09PSAxID8gInJnYigiIDogInJnYmEoIikKICAgICAgICAgICsgTWF0aC5tYXgoMCwgTWF0aC5taW4oMjU1LCBNYXRoLnJvdW5kKHRoaXMucikgfHwgMCkpICsgIiwgIgogICAgICAgICAgKyBNYXRoLm1heCgwLCBNYXRoLm1pbigyNTUsIE1hdGgucm91bmQodGhpcy5nKSB8fCAwKSkgKyAiLCAiCiAgICAgICAgICArIE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh0aGlzLmIpIHx8IDApKQogICAgICAgICAgKyAoYSA9PT0gMSA/ICIpIiA6ICIsICIgKyBhICsgIikiKTsKICAgIH0KCiAgICBmdW5jdGlvbiBoZXgkNSh2YWx1ZSkgewogICAgICB2YWx1ZSA9IE1hdGgubWF4KDAsIE1hdGgubWluKDI1NSwgTWF0aC5yb3VuZCh2YWx1ZSkgfHwgMCkpOwogICAgICByZXR1cm4gKHZhbHVlIDwgMTYgPyAiMCIgOiAiIikgKyB2YWx1ZS50b1N0cmluZygxNik7CiAgICB9CgogICAgZnVuY3Rpb24gaHNsYSQ2KGgsIHMsIGwsIGEpIHsKICAgICAgaWYgKGEgPD0gMCkgaCA9IHMgPSBsID0gTmFOOwogICAgICBlbHNlIGlmIChsIDw9IDAgfHwgbCA+PSAxKSBoID0gcyA9IE5hTjsKICAgICAgZWxzZSBpZiAocyA8PSAwKSBoID0gTmFOOwogICAgICByZXR1cm4gbmV3IEhzbCQ2KGgsIHMsIGwsIGEpOwogICAgfQoKICAgIGZ1bmN0aW9uIGhzbENvbnZlcnQkNihvKSB7CiAgICAgIGlmIChvIGluc3RhbmNlb2YgSHNsJDYpIHJldHVybiBuZXcgSHNsJDYoby5oLCBvLnMsIG8ubCwgby5vcGFjaXR5KTsKICAgICAgaWYgKCEobyBpbnN0YW5jZW9mIENvbG9yJDYpKSBvID0gY29sb3IkNihvKTsKICAgICAgaWYgKCFvKSByZXR1cm4gbmV3IEhzbCQ2OwogICAgICBpZiAobyBpbnN0YW5jZW9mIEhzbCQ2KSByZXR1cm4gbzsKICAgICAgbyA9IG8ucmdiKCk7CiAgICAgIHZhciByID0gby5yIC8gMjU1LAogICAgICAgICAgZyA9IG8uZyAvIDI1NSwKICAgICAgICAgIGIgPSBvLmIgLyAyNTUsCiAgICAgICAgICBtaW4gPSBNYXRoLm1pbihyLCBnLCBiKSwKICAgICAgICAgIG1heCA9IE1hdGgubWF4KHIsIGcsIGIpLAogICAgICAgICAgaCA9IE5hTiwKICAgICAgICAgIHMgPSBtYXggLSBtaW4sCiAgICAgICAgICBsID0gKG1heCArIG1pbikgLyAyOwogICAgICBpZiAocykgewogICAgICAgIGlmIChyID09PSBtYXgpIGggPSAoZyAtIGIpIC8gcyArIChnIDwgYikgKiA2OwogICAgICAgIGVsc2UgaWYgKGcgPT09IG1heCkgaCA9IChiIC0gcikgLyBzICsgMjsKICAgICAgICBlbHNlIGggPSAociAtIGcpIC8gcyArIDQ7CiAgICAgICAgcyAvPSBsIDwgMC41ID8gbWF4ICsgbWluIDogMiAtIG1heCAtIG1pbjsKICAgICAgICBoICo9IDYwOwogICAgICB9IGVsc2UgewogICAgICAgIHMgPSBsID4gMCAmJiBsIDwgMSA/IDAgOiBoOwogICAgICB9CiAgICAgIHJldHVybiBuZXcgSHNsJDYoaCwgcywgbCwgby5vcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBoc2wkYShoLCBzLCBsLCBvcGFjaXR5KSB7CiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID09PSAxID8gaHNsQ29udmVydCQ2KGgpIDogbmV3IEhzbCQ2KGgsIHMsIGwsIG9wYWNpdHkgPT0gbnVsbCA/IDEgOiBvcGFjaXR5KTsKICAgIH0KCiAgICBmdW5jdGlvbiBIc2wkNihoLCBzLCBsLCBvcGFjaXR5KSB7CiAgICAgIHRoaXMuaCA9ICtoOwogICAgICB0aGlzLnMgPSArczsKICAgICAgdGhpcy5sID0gK2w7CiAgICAgIHRoaXMub3BhY2l0eSA9ICtvcGFjaXR5OwogICAgfQoKICAgIGRlZmluZSQ2KEhzbCQ2LCBoc2wkYSwgZXh0ZW5kJDYoQ29sb3IkNiwgewogICAgICBicmlnaHRlcjogZnVuY3Rpb24oaykgewogICAgICAgIGsgPSBrID09IG51bGwgPyBicmlnaHRlciQ2IDogTWF0aC5wb3coYnJpZ2h0ZXIkNiwgayk7CiAgICAgICAgcmV0dXJuIG5ldyBIc2wkNih0aGlzLmgsIHRoaXMucywgdGhpcy5sICogaywgdGhpcy5vcGFjaXR5KTsKICAgICAgfSwKICAgICAgZGFya2VyOiBmdW5jdGlvbihrKSB7CiAgICAgICAgayA9IGsgPT0gbnVsbCA/IGRhcmtlciQ2IDogTWF0aC5wb3coZGFya2VyJDYsIGspOwogICAgICAgIHJldHVybiBuZXcgSHNsJDYodGhpcy5oLCB0aGlzLnMsIHRoaXMubCAqIGssIHRoaXMub3BhY2l0eSk7CiAgICAgIH0sCiAgICAgIHJnYjogZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGggPSB0aGlzLmggJSAzNjAgKyAodGhpcy5oIDwgMCkgKiAzNjAsCiAgICAgICAgICAgIHMgPSBpc05hTihoKSB8fCBpc05hTih0aGlzLnMpID8gMCA6IHRoaXMucywKICAgICAgICAgICAgbCA9IHRoaXMubCwKICAgICAgICAgICAgbTIgPSBsICsgKGwgPCAwLjUgPyBsIDogMSAtIGwpICogcywKICAgICAgICAgICAgbTEgPSAyICogbCAtIG0yOwogICAgICAgIHJldHVybiBuZXcgUmdiJDYoCiAgICAgICAgICBoc2wycmdiJDYoaCA+PSAyNDAgPyBoIC0gMjQwIDogaCArIDEyMCwgbTEsIG0yKSwKICAgICAgICAgIGhzbDJyZ2IkNihoLCBtMSwgbTIpLAogICAgICAgICAgaHNsMnJnYiQ2KGggPCAxMjAgPyBoICsgMjQwIDogaCAtIDEyMCwgbTEsIG0yKSwKICAgICAgICAgIHRoaXMub3BhY2l0eQogICAgICAgICk7CiAgICAgIH0sCiAgICAgIGRpc3BsYXlhYmxlOiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gKDAgPD0gdGhpcy5zICYmIHRoaXMucyA8PSAxIHx8IGlzTmFOKHRoaXMucykpCiAgICAgICAgICAgICYmICgwIDw9IHRoaXMubCAmJiB0aGlzLmwgPD0gMSkKICAgICAgICAgICAgJiYgKDAgPD0gdGhpcy5vcGFjaXR5ICYmIHRoaXMub3BhY2l0eSA8PSAxKTsKICAgICAgfSwKICAgICAgZm9ybWF0SHNsOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYSA9IHRoaXMub3BhY2l0eTsgYSA9IGlzTmFOKGEpID8gMSA6IE1hdGgubWF4KDAsIE1hdGgubWluKDEsIGEpKTsKICAgICAgICByZXR1cm4gKGEgPT09IDEgPyAiaHNsKCIgOiAiaHNsYSgiKQogICAgICAgICAgICArICh0aGlzLmggfHwgMCkgKyAiLCAiCiAgICAgICAgICAgICsgKHRoaXMucyB8fCAwKSAqIDEwMCArICIlLCAiCiAgICAgICAgICAgICsgKHRoaXMubCB8fCAwKSAqIDEwMCArICIlIgogICAgICAgICAgICArIChhID09PSAxID8gIikiIDogIiwgIiArIGEgKyAiKSIpOwogICAgICB9CiAgICB9KSk7CgogICAgLyogRnJvbSBGdkQgMTMuMzcsIENTUyBDb2xvciBNb2R1bGUgTGV2ZWwgMyAqLwogICAgZnVuY3Rpb24gaHNsMnJnYiQ2KGgsIG0xLCBtMikgewogICAgICByZXR1cm4gKGggPCA2MCA/IG0xICsgKG0yIC0gbTEpICogaCAvIDYwCiAgICAgICAgICA6IGggPCAxODAgPyBtMgogICAgICAgICAgOiBoIDwgMjQwID8gbTEgKyAobTIgLSBtMSkgKiAoMjQwIC0gaCkgLyA2MAogICAgICAgICAgOiBtMSkgKiAyNTU7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3RhbnQkeCh4KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4geDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBsaW5lYXIkOShhLCBkKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIGEgKyB0ICogZDsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBleHBvbmVudGlhbCQ3KGEsIGIsIHkpIHsKICAgICAgcmV0dXJuIGEgPSBNYXRoLnBvdyhhLCB5KSwgYiA9IE1hdGgucG93KGIsIHkpIC0gYSwgeSA9IDEgLyB5LCBmdW5jdGlvbih0KSB7CiAgICAgICAgcmV0dXJuIE1hdGgucG93KGEgKyB0ICogYiwgeSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZ2FtbWEkNSh5KSB7CiAgICAgIHJldHVybiAoeSA9ICt5KSA9PT0gMSA/IG5vZ2FtbWEkNSA6IGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICByZXR1cm4gYiAtIGEgPyBleHBvbmVudGlhbCQ3KGEsIGIsIHkpIDogY29uc3RhbnQkeChpc05hTihhKSA/IGIgOiBhKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2dhbW1hJDUoYSwgYikgewogICAgICB2YXIgZCA9IGIgLSBhOwogICAgICByZXR1cm4gZCA/IGxpbmVhciQ5KGEsIGQpIDogY29uc3RhbnQkeChpc05hTihhKSA/IGIgOiBhKTsKICAgIH0KCiAgICB2YXIgaW50ZXJwb2xhdGVSZ2IkMyA9IChmdW5jdGlvbiByZ2JHYW1tYSh5KSB7CiAgICAgIHZhciBjb2xvciA9IGdhbW1hJDUoeSk7CgogICAgICBmdW5jdGlvbiByZ2Ioc3RhcnQsIGVuZCkgewogICAgICAgIHZhciByID0gY29sb3IoKHN0YXJ0ID0gcmdiJDgoc3RhcnQpKS5yLCAoZW5kID0gcmdiJDgoZW5kKSkuciksCiAgICAgICAgICAgIGcgPSBjb2xvcihzdGFydC5nLCBlbmQuZyksCiAgICAgICAgICAgIGIgPSBjb2xvcihzdGFydC5iLCBlbmQuYiksCiAgICAgICAgICAgIG9wYWNpdHkgPSBub2dhbW1hJDUoc3RhcnQub3BhY2l0eSwgZW5kLm9wYWNpdHkpOwogICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICBzdGFydC5yID0gcih0KTsKICAgICAgICAgIHN0YXJ0LmcgPSBnKHQpOwogICAgICAgICAgc3RhcnQuYiA9IGIodCk7CiAgICAgICAgICBzdGFydC5vcGFjaXR5ID0gb3BhY2l0eSh0KTsKICAgICAgICAgIHJldHVybiBzdGFydCArICIiOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJnYi5nYW1tYSA9IHJnYkdhbW1hOwoKICAgICAgcmV0dXJuIHJnYjsKICAgIH0pKDEpOwoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlTnVtYmVyJDMoYSwgYikgewogICAgICByZXR1cm4gYSA9ICthLCBiID0gK2IsIGZ1bmN0aW9uKHQpIHsKICAgICAgICByZXR1cm4gYSAqICgxIC0gdCkgKyBiICogdDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgcmVBJDUgPSAvWy0rXT8oPzpcZCtcLj9cZCp8XC4/XGQrKSg/OltlRV1bLStdP1xkKyk/L2csCiAgICAgICAgcmVCJDUgPSBuZXcgUmVnRXhwKHJlQSQ1LnNvdXJjZSwgImciKTsKCiAgICBmdW5jdGlvbiB6ZXJvJDUoYikgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIGI7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gb25lJDUoYikgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHJldHVybiBiKHQpICsgIiI7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJwb2xhdGVTdHJpbmckMyhhLCBiKSB7CiAgICAgIHZhciBiaSA9IHJlQSQ1Lmxhc3RJbmRleCA9IHJlQiQ1Lmxhc3RJbmRleCA9IDAsIC8vIHNjYW4gaW5kZXggZm9yIG5leHQgbnVtYmVyIGluIGIKICAgICAgICAgIGFtLCAvLyBjdXJyZW50IG1hdGNoIGluIGEKICAgICAgICAgIGJtLCAvLyBjdXJyZW50IG1hdGNoIGluIGIKICAgICAgICAgIGJzLCAvLyBzdHJpbmcgcHJlY2VkaW5nIGN1cnJlbnQgbnVtYmVyIGluIGIsIGlmIGFueQogICAgICAgICAgaSA9IC0xLCAvLyBpbmRleCBpbiBzCiAgICAgICAgICBzID0gW10sIC8vIHN0cmluZyBjb25zdGFudHMgYW5kIHBsYWNlaG9sZGVycwogICAgICAgICAgcSA9IFtdOyAvLyBudW1iZXIgaW50ZXJwb2xhdG9ycwoKICAgICAgLy8gQ29lcmNlIGlucHV0cyB0byBzdHJpbmdzLgogICAgICBhID0gYSArICIiLCBiID0gYiArICIiOwoKICAgICAgLy8gSW50ZXJwb2xhdGUgcGFpcnMgb2YgbnVtYmVycyBpbiBhICYgYi4KICAgICAgd2hpbGUgKChhbSA9IHJlQSQ1LmV4ZWMoYSkpCiAgICAgICAgICAmJiAoYm0gPSByZUIkNS5leGVjKGIpKSkgewogICAgICAgIGlmICgoYnMgPSBibS5pbmRleCkgPiBiaSkgeyAvLyBhIHN0cmluZyBwcmVjZWRlcyB0aGUgbmV4dCBudW1iZXIgaW4gYgogICAgICAgICAgYnMgPSBiLnNsaWNlKGJpLCBicyk7CiAgICAgICAgICBpZiAoc1tpXSkgc1tpXSArPSBiczsgLy8gY29hbGVzY2Ugd2l0aCBwcmV2aW91cyBzdHJpbmcKICAgICAgICAgIGVsc2Ugc1srK2ldID0gYnM7CiAgICAgICAgfQogICAgICAgIGlmICgoYW0gPSBhbVswXSkgPT09IChibSA9IGJtWzBdKSkgeyAvLyBudW1iZXJzIGluIGEgJiBiIG1hdGNoCiAgICAgICAgICBpZiAoc1tpXSkgc1tpXSArPSBibTsgLy8gY29hbGVzY2Ugd2l0aCBwcmV2aW91cyBzdHJpbmcKICAgICAgICAgIGVsc2Ugc1srK2ldID0gYm07CiAgICAgICAgfSBlbHNlIHsgLy8gaW50ZXJwb2xhdGUgbm9uLW1hdGNoaW5nIG51bWJlcnMKICAgICAgICAgIHNbKytpXSA9IG51bGw7CiAgICAgICAgICBxLnB1c2goe2k6IGksIHg6IGludGVycG9sYXRlTnVtYmVyJDMoYW0sIGJtKX0pOwogICAgICAgIH0KICAgICAgICBiaSA9IHJlQiQ1Lmxhc3RJbmRleDsKICAgICAgfQoKICAgICAgLy8gQWRkIHJlbWFpbnMgb2YgYi4KICAgICAgaWYgKGJpIDwgYi5sZW5ndGgpIHsKICAgICAgICBicyA9IGIuc2xpY2UoYmkpOwogICAgICAgIGlmIChzW2ldKSBzW2ldICs9IGJzOyAvLyBjb2FsZXNjZSB3aXRoIHByZXZpb3VzIHN0cmluZwogICAgICAgIGVsc2Ugc1srK2ldID0gYnM7CiAgICAgIH0KCiAgICAgIC8vIFNwZWNpYWwgb3B0aW1pemF0aW9uIGZvciBvbmx5IGEgc2luZ2xlIG1hdGNoLgogICAgICAvLyBPdGhlcndpc2UsIGludGVycG9sYXRlIGVhY2ggb2YgdGhlIG51bWJlcnMgYW5kIHJlam9pbiB0aGUgc3RyaW5nLgogICAgICByZXR1cm4gcy5sZW5ndGggPCAyID8gKHFbMF0KICAgICAgICAgID8gb25lJDUocVswXS54KQogICAgICAgICAgOiB6ZXJvJDUoYikpCiAgICAgICAgICA6IChiID0gcS5sZW5ndGgsIGZ1bmN0aW9uKHQpIHsKICAgICAgICAgICAgICBmb3IgKHZhciBpID0gMCwgbzsgaSA8IGI7ICsraSkgc1sobyA9IHFbaV0pLmldID0gby54KHQpOwogICAgICAgICAgICAgIHJldHVybiBzLmpvaW4oIiIpOwogICAgICAgICAgICB9KTsKICAgIH0KCiAgICB2YXIgZGVncmVlcyQ2ID0gMTgwIC8gTWF0aC5QSTsKCiAgICB2YXIgaWRlbnRpdHkkbCA9IHsKICAgICAgdHJhbnNsYXRlWDogMCwKICAgICAgdHJhbnNsYXRlWTogMCwKICAgICAgcm90YXRlOiAwLAogICAgICBza2V3WDogMCwKICAgICAgc2NhbGVYOiAxLAogICAgICBzY2FsZVk6IDEKICAgIH07CgogICAgZnVuY3Rpb24gZGVjb21wb3NlJDQoYSwgYiwgYywgZCwgZSwgZikgewogICAgICB2YXIgc2NhbGVYLCBzY2FsZVksIHNrZXdYOwogICAgICBpZiAoc2NhbGVYID0gTWF0aC5zcXJ0KGEgKiBhICsgYiAqIGIpKSBhIC89IHNjYWxlWCwgYiAvPSBzY2FsZVg7CiAgICAgIGlmIChza2V3WCA9IGEgKiBjICsgYiAqIGQpIGMgLT0gYSAqIHNrZXdYLCBkIC09IGIgKiBza2V3WDsKICAgICAgaWYgKHNjYWxlWSA9IE1hdGguc3FydChjICogYyArIGQgKiBkKSkgYyAvPSBzY2FsZVksIGQgLz0gc2NhbGVZLCBza2V3WCAvPSBzY2FsZVk7CiAgICAgIGlmIChhICogZCA8IGIgKiBjKSBhID0gLWEsIGIgPSAtYiwgc2tld1ggPSAtc2tld1gsIHNjYWxlWCA9IC1zY2FsZVg7CiAgICAgIHJldHVybiB7CiAgICAgICAgdHJhbnNsYXRlWDogZSwKICAgICAgICB0cmFuc2xhdGVZOiBmLAogICAgICAgIHJvdGF0ZTogTWF0aC5hdGFuMihiLCBhKSAqIGRlZ3JlZXMkNiwKICAgICAgICBza2V3WDogTWF0aC5hdGFuKHNrZXdYKSAqIGRlZ3JlZXMkNiwKICAgICAgICBzY2FsZVg6IHNjYWxlWCwKICAgICAgICBzY2FsZVk6IHNjYWxlWQogICAgICB9OwogICAgfQoKICAgIHZhciBjc3NOb2RlJDQsCiAgICAgICAgY3NzUm9vdCQ0LAogICAgICAgIGNzc1ZpZXckNCwKICAgICAgICBzdmdOb2RlJDQ7CgogICAgZnVuY3Rpb24gcGFyc2VDc3MkNSh2YWx1ZSkgewogICAgICBpZiAodmFsdWUgPT09ICJub25lIikgcmV0dXJuIGlkZW50aXR5JGw7CiAgICAgIGlmICghY3NzTm9kZSQ0KSBjc3NOb2RlJDQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCJESVYiKSwgY3NzUm9vdCQ0ID0gZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LCBjc3NWaWV3JDQgPSBkb2N1bWVudC5kZWZhdWx0VmlldzsKICAgICAgY3NzTm9kZSQ0LnN0eWxlLnRyYW5zZm9ybSA9IHZhbHVlOwogICAgICB2YWx1ZSA9IGNzc1ZpZXckNC5nZXRDb21wdXRlZFN0eWxlKGNzc1Jvb3QkNC5hcHBlbmRDaGlsZChjc3NOb2RlJDQpLCBudWxsKS5nZXRQcm9wZXJ0eVZhbHVlKCJ0cmFuc2Zvcm0iKTsKICAgICAgY3NzUm9vdCQ0LnJlbW92ZUNoaWxkKGNzc05vZGUkNCk7CiAgICAgIHZhbHVlID0gdmFsdWUuc2xpY2UoNywgLTEpLnNwbGl0KCIsIik7CiAgICAgIHJldHVybiBkZWNvbXBvc2UkNCgrdmFsdWVbMF0sICt2YWx1ZVsxXSwgK3ZhbHVlWzJdLCArdmFsdWVbM10sICt2YWx1ZVs0XSwgK3ZhbHVlWzVdKTsKICAgIH0KCiAgICBmdW5jdGlvbiBwYXJzZVN2ZyQ0KHZhbHVlKSB7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gaWRlbnRpdHkkbDsKICAgICAgaWYgKCFzdmdOb2RlJDQpIHN2Z05vZGUkNCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciLCAiZyIpOwogICAgICBzdmdOb2RlJDQuc2V0QXR0cmlidXRlKCJ0cmFuc2Zvcm0iLCB2YWx1ZSk7CiAgICAgIGlmICghKHZhbHVlID0gc3ZnTm9kZSQ0LnRyYW5zZm9ybS5iYXNlVmFsLmNvbnNvbGlkYXRlKCkpKSByZXR1cm4gaWRlbnRpdHkkbDsKICAgICAgdmFsdWUgPSB2YWx1ZS5tYXRyaXg7CiAgICAgIHJldHVybiBkZWNvbXBvc2UkNCh2YWx1ZS5hLCB2YWx1ZS5iLCB2YWx1ZS5jLCB2YWx1ZS5kLCB2YWx1ZS5lLCB2YWx1ZS5mKTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnRlcnBvbGF0ZVRyYW5zZm9ybSQ0KHBhcnNlLCBweENvbW1hLCBweFBhcmVuLCBkZWdQYXJlbikgewoKICAgICAgZnVuY3Rpb24gcG9wKHMpIHsKICAgICAgICByZXR1cm4gcy5sZW5ndGggPyBzLnBvcCgpICsgIiAiIDogIiI7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRyYW5zbGF0ZSh4YSwgeWEsIHhiLCB5YiwgcywgcSkgewogICAgICAgIGlmICh4YSAhPT0geGIgfHwgeWEgIT09IHliKSB7CiAgICAgICAgICB2YXIgaSA9IHMucHVzaCgidHJhbnNsYXRlKCIsIG51bGwsIHB4Q29tbWEsIG51bGwsIHB4UGFyZW4pOwogICAgICAgICAgcS5wdXNoKHtpOiBpIC0gNCwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMyh4YSwgeGIpfSwge2k6IGkgLSAyLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQzKHlhLCB5Yil9KTsKICAgICAgICB9IGVsc2UgaWYgKHhiIHx8IHliKSB7CiAgICAgICAgICBzLnB1c2goInRyYW5zbGF0ZSgiICsgeGIgKyBweENvbW1hICsgeWIgKyBweFBhcmVuKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHJvdGF0ZShhLCBiLCBzLCBxKSB7CiAgICAgICAgaWYgKGEgIT09IGIpIHsKICAgICAgICAgIGlmIChhIC0gYiA+IDE4MCkgYiArPSAzNjA7IGVsc2UgaWYgKGIgLSBhID4gMTgwKSBhICs9IDM2MDsgLy8gc2hvcnRlc3QgcGF0aAogICAgICAgICAgcS5wdXNoKHtpOiBzLnB1c2gocG9wKHMpICsgInJvdGF0ZSgiLCBudWxsLCBkZWdQYXJlbikgLSAyLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQzKGEsIGIpfSk7CiAgICAgICAgfSBlbHNlIGlmIChiKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInJvdGF0ZSgiICsgYiArIGRlZ1BhcmVuKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNrZXdYKGEsIGIsIHMsIHEpIHsKICAgICAgICBpZiAoYSAhPT0gYikgewogICAgICAgICAgcS5wdXNoKHtpOiBzLnB1c2gocG9wKHMpICsgInNrZXdYKCIsIG51bGwsIGRlZ1BhcmVuKSAtIDIsIHg6IGludGVycG9sYXRlTnVtYmVyJDMoYSwgYil9KTsKICAgICAgICB9IGVsc2UgaWYgKGIpIHsKICAgICAgICAgIHMucHVzaChwb3AocykgKyAic2tld1goIiArIGIgKyBkZWdQYXJlbik7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBzY2FsZSh4YSwgeWEsIHhiLCB5YiwgcywgcSkgewogICAgICAgIGlmICh4YSAhPT0geGIgfHwgeWEgIT09IHliKSB7CiAgICAgICAgICB2YXIgaSA9IHMucHVzaChwb3AocykgKyAic2NhbGUoIiwgbnVsbCwgIiwiLCBudWxsLCAiKSIpOwogICAgICAgICAgcS5wdXNoKHtpOiBpIC0gNCwgeDogaW50ZXJwb2xhdGVOdW1iZXIkMyh4YSwgeGIpfSwge2k6IGkgLSAyLCB4OiBpbnRlcnBvbGF0ZU51bWJlciQzKHlhLCB5Yil9KTsKICAgICAgICB9IGVsc2UgaWYgKHhiICE9PSAxIHx8IHliICE9PSAxKSB7CiAgICAgICAgICBzLnB1c2gocG9wKHMpICsgInNjYWxlKCIgKyB4YiArICIsIiArIHliICsgIikiKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgdmFyIHMgPSBbXSwgLy8gc3RyaW5nIGNvbnN0YW50cyBhbmQgcGxhY2Vob2xkZXJzCiAgICAgICAgICAgIHEgPSBbXTsgLy8gbnVtYmVyIGludGVycG9sYXRvcnMKICAgICAgICBhID0gcGFyc2UoYSksIGIgPSBwYXJzZShiKTsKICAgICAgICB0cmFuc2xhdGUoYS50cmFuc2xhdGVYLCBhLnRyYW5zbGF0ZVksIGIudHJhbnNsYXRlWCwgYi50cmFuc2xhdGVZLCBzLCBxKTsKICAgICAgICByb3RhdGUoYS5yb3RhdGUsIGIucm90YXRlLCBzLCBxKTsKICAgICAgICBza2V3WChhLnNrZXdYLCBiLnNrZXdYLCBzLCBxKTsKICAgICAgICBzY2FsZShhLnNjYWxlWCwgYS5zY2FsZVksIGIuc2NhbGVYLCBiLnNjYWxlWSwgcywgcSk7CiAgICAgICAgYSA9IGIgPSBudWxsOyAvLyBnYwogICAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgICB2YXIgaSA9IC0xLCBuID0gcS5sZW5ndGgsIG87CiAgICAgICAgICB3aGlsZSAoKytpIDwgbikgc1sobyA9IHFbaV0pLmldID0gby54KHQpOwogICAgICAgICAgcmV0dXJuIHMuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgaW50ZXJwb2xhdGVUcmFuc2Zvcm1Dc3MkNCA9IGludGVycG9sYXRlVHJhbnNmb3JtJDQocGFyc2VDc3MkNSwgInB4LCAiLCAicHgpIiwgImRlZykiKTsKICAgIHZhciBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZyQ0ID0gaW50ZXJwb2xhdGVUcmFuc2Zvcm0kNChwYXJzZVN2ZyQ0LCAiLCAiLCAiKSIsICIpIik7CgogICAgdmFyIHJobyQyID0gTWF0aC5TUVJUMiwKICAgICAgICByaG8yJDIgPSAyLAogICAgICAgIHJobzQkMiA9IDQsCiAgICAgICAgZXBzaWxvbjIkNiA9IDFlLTEyOwoKICAgIGZ1bmN0aW9uIGNvc2gkMih4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCh4KSkgKyAxIC8geCkgLyAyOwogICAgfQoKICAgIGZ1bmN0aW9uIHNpbmgkMih4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCh4KSkgLSAxIC8geCkgLyAyOwogICAgfQoKICAgIGZ1bmN0aW9uIHRhbmgkMih4KSB7CiAgICAgIHJldHVybiAoKHggPSBNYXRoLmV4cCgyICogeCkpIC0gMSkgLyAoeCArIDEpOwogICAgfQoKICAgIC8vIHAwID0gW3V4MCwgdXkwLCB3MF0KICAgIC8vIHAxID0gW3V4MSwgdXkxLCB3MV0KICAgIGZ1bmN0aW9uIGludGVycG9sYXRlWm9vbSQxKHAwLCBwMSkgewogICAgICB2YXIgdXgwID0gcDBbMF0sIHV5MCA9IHAwWzFdLCB3MCA9IHAwWzJdLAogICAgICAgICAgdXgxID0gcDFbMF0sIHV5MSA9IHAxWzFdLCB3MSA9IHAxWzJdLAogICAgICAgICAgZHggPSB1eDEgLSB1eDAsCiAgICAgICAgICBkeSA9IHV5MSAtIHV5MCwKICAgICAgICAgIGQyID0gZHggKiBkeCArIGR5ICogZHksCiAgICAgICAgICBpLAogICAgICAgICAgUzsKCiAgICAgIC8vIFNwZWNpYWwgY2FzZSBmb3IgdTAg4omFIHUxLgogICAgICBpZiAoZDIgPCBlcHNpbG9uMiQ2KSB7CiAgICAgICAgUyA9IE1hdGgubG9nKHcxIC8gdzApIC8gcmhvJDI7CiAgICAgICAgaSA9IGZ1bmN0aW9uKHQpIHsKICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgIHV4MCArIHQgKiBkeCwKICAgICAgICAgICAgdXkwICsgdCAqIGR5LAogICAgICAgICAgICB3MCAqIE1hdGguZXhwKHJobyQyICogdCAqIFMpCiAgICAgICAgICBdOwogICAgICAgIH07CiAgICAgIH0KCiAgICAgIC8vIEdlbmVyYWwgY2FzZS4KICAgICAgZWxzZSB7CiAgICAgICAgdmFyIGQxID0gTWF0aC5zcXJ0KGQyKSwKICAgICAgICAgICAgYjAgPSAodzEgKiB3MSAtIHcwICogdzAgKyByaG80JDIgKiBkMikgLyAoMiAqIHcwICogcmhvMiQyICogZDEpLAogICAgICAgICAgICBiMSA9ICh3MSAqIHcxIC0gdzAgKiB3MCAtIHJobzQkMiAqIGQyKSAvICgyICogdzEgKiByaG8yJDIgKiBkMSksCiAgICAgICAgICAgIHIwID0gTWF0aC5sb2coTWF0aC5zcXJ0KGIwICogYjAgKyAxKSAtIGIwKSwKICAgICAgICAgICAgcjEgPSBNYXRoLmxvZyhNYXRoLnNxcnQoYjEgKiBiMSArIDEpIC0gYjEpOwogICAgICAgIFMgPSAocjEgLSByMCkgLyByaG8kMjsKICAgICAgICBpID0gZnVuY3Rpb24odCkgewogICAgICAgICAgdmFyIHMgPSB0ICogUywKICAgICAgICAgICAgICBjb3NocjAgPSBjb3NoJDIocjApLAogICAgICAgICAgICAgIHUgPSB3MCAvIChyaG8yJDIgKiBkMSkgKiAoY29zaHIwICogdGFuaCQyKHJobyQyICogcyArIHIwKSAtIHNpbmgkMihyMCkpOwogICAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgdXgwICsgdSAqIGR4LAogICAgICAgICAgICB1eTAgKyB1ICogZHksCiAgICAgICAgICAgIHcwICogY29zaHIwIC8gY29zaCQyKHJobyQyICogcyArIHIwKQogICAgICAgICAgXTsKICAgICAgICB9OwogICAgICB9CgogICAgICBpLmR1cmF0aW9uID0gUyAqIDEwMDA7CgogICAgICByZXR1cm4gaTsKICAgIH0KCiAgICB2YXIgZnJhbWUkNSA9IDAsIC8vIGlzIGFuIGFuaW1hdGlvbiBmcmFtZSBwZW5kaW5nPwogICAgICAgIHRpbWVvdXQkOSA9IDAsIC8vIGlzIGEgdGltZW91dCBwZW5kaW5nPwogICAgICAgIGludGVydmFsJDcgPSAwLCAvLyBhcmUgYW55IHRpbWVycyBhY3RpdmU/CiAgICAgICAgcG9rZURlbGF5JDUgPSAxMDAwLCAvLyBob3cgZnJlcXVlbnRseSB3ZSBjaGVjayBmb3IgY2xvY2sgc2tldwogICAgICAgIHRhc2tIZWFkJDUsCiAgICAgICAgdGFza1RhaWwkNSwKICAgICAgICBjbG9ja0xhc3QkNSA9IDAsCiAgICAgICAgY2xvY2tOb3ckNSA9IDAsCiAgICAgICAgY2xvY2tTa2V3JDUgPSAwLAogICAgICAgIGNsb2NrJDUgPSB0eXBlb2YgcGVyZm9ybWFuY2UgPT09ICJvYmplY3QiICYmIHBlcmZvcm1hbmNlLm5vdyA/IHBlcmZvcm1hbmNlIDogRGF0ZSwKICAgICAgICBzZXRGcmFtZSQ1ID0gdHlwZW9mIHdpbmRvdyA9PT0gIm9iamVjdCIgJiYgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSA/IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUuYmluZCh3aW5kb3cpIDogZnVuY3Rpb24oZikgeyBzZXRUaW1lb3V0KGYsIDE3KTsgfTsKCiAgICBmdW5jdGlvbiBub3ckNSgpIHsKICAgICAgcmV0dXJuIGNsb2NrTm93JDUgfHwgKHNldEZyYW1lJDUoY2xlYXJOb3ckNSksIGNsb2NrTm93JDUgPSBjbG9jayQ1Lm5vdygpICsgY2xvY2tTa2V3JDUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGNsZWFyTm93JDUoKSB7CiAgICAgIGNsb2NrTm93JDUgPSAwOwogICAgfQoKICAgIGZ1bmN0aW9uIFRpbWVyJDUoKSB7CiAgICAgIHRoaXMuX2NhbGwgPQogICAgICB0aGlzLl90aW1lID0KICAgICAgdGhpcy5fbmV4dCA9IG51bGw7CiAgICB9CgogICAgVGltZXIkNS5wcm90b3R5cGUgPSB0aW1lciQ1LnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRpbWVyJDUsCiAgICAgIHJlc3RhcnQ6IGZ1bmN0aW9uKGNhbGxiYWNrLCBkZWxheSwgdGltZSkgewogICAgICAgIGlmICh0eXBlb2YgY2FsbGJhY2sgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBUeXBlRXJyb3IoImNhbGxiYWNrIGlzIG5vdCBhIGZ1bmN0aW9uIik7CiAgICAgICAgdGltZSA9ICh0aW1lID09IG51bGwgPyBub3ckNSgpIDogK3RpbWUpICsgKGRlbGF5ID09IG51bGwgPyAwIDogK2RlbGF5KTsKICAgICAgICBpZiAoIXRoaXMuX25leHQgJiYgdGFza1RhaWwkNSAhPT0gdGhpcykgewogICAgICAgICAgaWYgKHRhc2tUYWlsJDUpIHRhc2tUYWlsJDUuX25leHQgPSB0aGlzOwogICAgICAgICAgZWxzZSB0YXNrSGVhZCQ1ID0gdGhpczsKICAgICAgICAgIHRhc2tUYWlsJDUgPSB0aGlzOwogICAgICAgIH0KICAgICAgICB0aGlzLl9jYWxsID0gY2FsbGJhY2s7CiAgICAgICAgdGhpcy5fdGltZSA9IHRpbWU7CiAgICAgICAgc2xlZXAkNSgpOwogICAgICB9LAogICAgICBzdG9wOiBmdW5jdGlvbigpIHsKICAgICAgICBpZiAodGhpcy5fY2FsbCkgewogICAgICAgICAgdGhpcy5fY2FsbCA9IG51bGw7CiAgICAgICAgICB0aGlzLl90aW1lID0gSW5maW5pdHk7CiAgICAgICAgICBzbGVlcCQ1KCk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIHRpbWVyJDUoY2FsbGJhY2ssIGRlbGF5LCB0aW1lKSB7CiAgICAgIHZhciB0ID0gbmV3IFRpbWVyJDU7CiAgICAgIHQucmVzdGFydChjYWxsYmFjaywgZGVsYXksIHRpbWUpOwogICAgICByZXR1cm4gdDsKICAgIH0KCiAgICBmdW5jdGlvbiB0aW1lckZsdXNoJDUoKSB7CiAgICAgIG5vdyQ1KCk7IC8vIEdldCB0aGUgY3VycmVudCB0aW1lLCBpZiBub3QgYWxyZWFkeSBzZXQuCiAgICAgICsrZnJhbWUkNTsgLy8gUHJldGVuZCB3ZeKAmXZlIHNldCBhbiBhbGFybSwgaWYgd2UgaGF2ZW7igJl0IGFscmVhZHkuCiAgICAgIHZhciB0ID0gdGFza0hlYWQkNSwgZTsKICAgICAgd2hpbGUgKHQpIHsKICAgICAgICBpZiAoKGUgPSBjbG9ja05vdyQ1IC0gdC5fdGltZSkgPj0gMCkgdC5fY2FsbC5jYWxsKG51bGwsIGUpOwogICAgICAgIHQgPSB0Ll9uZXh0OwogICAgICB9CiAgICAgIC0tZnJhbWUkNTsKICAgIH0KCiAgICBmdW5jdGlvbiB3YWtlJDUoKSB7CiAgICAgIGNsb2NrTm93JDUgPSAoY2xvY2tMYXN0JDUgPSBjbG9jayQ1Lm5vdygpKSArIGNsb2NrU2tldyQ1OwogICAgICBmcmFtZSQ1ID0gdGltZW91dCQ5ID0gMDsKICAgICAgdHJ5IHsKICAgICAgICB0aW1lckZsdXNoJDUoKTsKICAgICAgfSBmaW5hbGx5IHsKICAgICAgICBmcmFtZSQ1ID0gMDsKICAgICAgICBuYXAkNSgpOwogICAgICAgIGNsb2NrTm93JDUgPSAwOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gcG9rZSQ2KCkgewogICAgICB2YXIgbm93ID0gY2xvY2skNS5ub3coKSwgZGVsYXkgPSBub3cgLSBjbG9ja0xhc3QkNTsKICAgICAgaWYgKGRlbGF5ID4gcG9rZURlbGF5JDUpIGNsb2NrU2tldyQ1IC09IGRlbGF5LCBjbG9ja0xhc3QkNSA9IG5vdzsKICAgIH0KCiAgICBmdW5jdGlvbiBuYXAkNSgpIHsKICAgICAgdmFyIHQwLCB0MSA9IHRhc2tIZWFkJDUsIHQyLCB0aW1lID0gSW5maW5pdHk7CiAgICAgIHdoaWxlICh0MSkgewogICAgICAgIGlmICh0MS5fY2FsbCkgewogICAgICAgICAgaWYgKHRpbWUgPiB0MS5fdGltZSkgdGltZSA9IHQxLl90aW1lOwogICAgICAgICAgdDAgPSB0MSwgdDEgPSB0MS5fbmV4dDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdDIgPSB0MS5fbmV4dCwgdDEuX25leHQgPSBudWxsOwogICAgICAgICAgdDEgPSB0MCA/IHQwLl9uZXh0ID0gdDIgOiB0YXNrSGVhZCQ1ID0gdDI7CiAgICAgICAgfQogICAgICB9CiAgICAgIHRhc2tUYWlsJDUgPSB0MDsKICAgICAgc2xlZXAkNSh0aW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzbGVlcCQ1KHRpbWUpIHsKICAgICAgaWYgKGZyYW1lJDUpIHJldHVybjsgLy8gU29vbmVzdCBhbGFybSBhbHJlYWR5IHNldCwgb3Igd2lsbCBiZS4KICAgICAgaWYgKHRpbWVvdXQkOSkgdGltZW91dCQ5ID0gY2xlYXJUaW1lb3V0KHRpbWVvdXQkOSk7CiAgICAgIHZhciBkZWxheSA9IHRpbWUgLSBjbG9ja05vdyQ1OyAvLyBTdHJpY3RseSBsZXNzIHRoYW4gaWYgd2UgcmVjb21wdXRlZCBjbG9ja05vdy4KICAgICAgaWYgKGRlbGF5ID4gMjQpIHsKICAgICAgICBpZiAodGltZSA8IEluZmluaXR5KSB0aW1lb3V0JDkgPSBzZXRUaW1lb3V0KHdha2UkNSwgdGltZSAtIGNsb2NrJDUubm93KCkgLSBjbG9ja1NrZXckNSk7CiAgICAgICAgaWYgKGludGVydmFsJDcpIGludGVydmFsJDcgPSBjbGVhckludGVydmFsKGludGVydmFsJDcpOwogICAgICB9IGVsc2UgewogICAgICAgIGlmICghaW50ZXJ2YWwkNykgY2xvY2tMYXN0JDUgPSBjbG9jayQ1Lm5vdygpLCBpbnRlcnZhbCQ3ID0gc2V0SW50ZXJ2YWwocG9rZSQ2LCBwb2tlRGVsYXkkNSk7CiAgICAgICAgZnJhbWUkNSA9IDEsIHNldEZyYW1lJDUod2FrZSQ1KTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHRpbWVvdXQkYShjYWxsYmFjaywgZGVsYXksIHRpbWUpIHsKICAgICAgdmFyIHQgPSBuZXcgVGltZXIkNTsKICAgICAgZGVsYXkgPSBkZWxheSA9PSBudWxsID8gMCA6ICtkZWxheTsKICAgICAgdC5yZXN0YXJ0KGZ1bmN0aW9uKGVsYXBzZWQpIHsKICAgICAgICB0LnN0b3AoKTsKICAgICAgICBjYWxsYmFjayhlbGFwc2VkICsgZGVsYXkpOwogICAgICB9LCBkZWxheSwgdGltZSk7CiAgICAgIHJldHVybiB0OwogICAgfQoKICAgIHZhciBlbXB0eU9uJDMgPSBkaXNwYXRjaCQ2KCJzdGFydCIsICJlbmQiLCAiY2FuY2VsIiwgImludGVycnVwdCIpOwogICAgdmFyIGVtcHR5VHdlZW4kMyA9IFtdOwoKICAgIHZhciBDUkVBVEVEJDMgPSAwOwogICAgdmFyIFNDSEVEVUxFRCQzID0gMTsKICAgIHZhciBTVEFSVElORyQzID0gMjsKICAgIHZhciBTVEFSVEVEJDMgPSAzOwogICAgdmFyIFJVTk5JTkckMyA9IDQ7CiAgICB2YXIgRU5ESU5HJDMgPSA1OwogICAgdmFyIEVOREVEJDMgPSA2OwoKICAgIGZ1bmN0aW9uIHNjaGVkdWxlJDQobm9kZSwgbmFtZSwgaWQsIGluZGV4LCBncm91cCwgdGltaW5nKSB7CiAgICAgIHZhciBzY2hlZHVsZXMgPSBub2RlLl9fdHJhbnNpdGlvbjsKICAgICAgaWYgKCFzY2hlZHVsZXMpIG5vZGUuX190cmFuc2l0aW9uID0ge307CiAgICAgIGVsc2UgaWYgKGlkIGluIHNjaGVkdWxlcykgcmV0dXJuOwogICAgICBjcmVhdGUkNShub2RlLCBpZCwgewogICAgICAgIG5hbWU6IG5hbWUsCiAgICAgICAgaW5kZXg6IGluZGV4LCAvLyBGb3IgY29udGV4dCBkdXJpbmcgY2FsbGJhY2suCiAgICAgICAgZ3JvdXA6IGdyb3VwLCAvLyBGb3IgY29udGV4dCBkdXJpbmcgY2FsbGJhY2suCiAgICAgICAgb246IGVtcHR5T24kMywKICAgICAgICB0d2VlbjogZW1wdHlUd2VlbiQzLAogICAgICAgIHRpbWU6IHRpbWluZy50aW1lLAogICAgICAgIGRlbGF5OiB0aW1pbmcuZGVsYXksCiAgICAgICAgZHVyYXRpb246IHRpbWluZy5kdXJhdGlvbiwKICAgICAgICBlYXNlOiB0aW1pbmcuZWFzZSwKICAgICAgICB0aW1lcjogbnVsbCwKICAgICAgICBzdGF0ZTogQ1JFQVRFRCQzCiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGluaXQkMyhub2RlLCBpZCkgewogICAgICB2YXIgc2NoZWR1bGUgPSBnZXQkYihub2RlLCBpZCk7CiAgICAgIGlmIChzY2hlZHVsZS5zdGF0ZSA+IENSRUFURUQkMykgdGhyb3cgbmV3IEVycm9yKCJ0b28gbGF0ZTsgYWxyZWFkeSBzY2hlZHVsZWQiKTsKICAgICAgcmV0dXJuIHNjaGVkdWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIHNldCRmKG5vZGUsIGlkKSB7CiAgICAgIHZhciBzY2hlZHVsZSA9IGdldCRiKG5vZGUsIGlkKTsKICAgICAgaWYgKHNjaGVkdWxlLnN0YXRlID4gU1RBUlRFRCQzKSB0aHJvdyBuZXcgRXJyb3IoInRvbyBsYXRlOyBhbHJlYWR5IHJ1bm5pbmciKTsKICAgICAgcmV0dXJuIHNjaGVkdWxlOwogICAgfQoKICAgIGZ1bmN0aW9uIGdldCRiKG5vZGUsIGlkKSB7CiAgICAgIHZhciBzY2hlZHVsZSA9IG5vZGUuX190cmFuc2l0aW9uOwogICAgICBpZiAoIXNjaGVkdWxlIHx8ICEoc2NoZWR1bGUgPSBzY2hlZHVsZVtpZF0pKSB0aHJvdyBuZXcgRXJyb3IoInRyYW5zaXRpb24gbm90IGZvdW5kIik7CiAgICAgIHJldHVybiBzY2hlZHVsZTsKICAgIH0KCiAgICBmdW5jdGlvbiBjcmVhdGUkNShub2RlLCBpZCwgc2VsZikgewogICAgICB2YXIgc2NoZWR1bGVzID0gbm9kZS5fX3RyYW5zaXRpb24sCiAgICAgICAgICB0d2VlbjsKCiAgICAgIC8vIEluaXRpYWxpemUgdGhlIHNlbGYgdGltZXIgd2hlbiB0aGUgdHJhbnNpdGlvbiBpcyBjcmVhdGVkLgogICAgICAvLyBOb3RlIHRoZSBhY3R1YWwgZGVsYXkgaXMgbm90IGtub3duIHVudGlsIHRoZSBmaXJzdCBjYWxsYmFjayEKICAgICAgc2NoZWR1bGVzW2lkXSA9IHNlbGY7CiAgICAgIHNlbGYudGltZXIgPSB0aW1lciQ1KHNjaGVkdWxlLCAwLCBzZWxmLnRpbWUpOwoKICAgICAgZnVuY3Rpb24gc2NoZWR1bGUoZWxhcHNlZCkgewogICAgICAgIHNlbGYuc3RhdGUgPSBTQ0hFRFVMRUQkMzsKICAgICAgICBzZWxmLnRpbWVyLnJlc3RhcnQoc3RhcnQsIHNlbGYuZGVsYXksIHNlbGYudGltZSk7CgogICAgICAgIC8vIElmIHRoZSBlbGFwc2VkIGRlbGF5IGlzIGxlc3MgdGhhbiBvdXIgZmlyc3Qgc2xlZXAsIHN0YXJ0IGltbWVkaWF0ZWx5LgogICAgICAgIGlmIChzZWxmLmRlbGF5IDw9IGVsYXBzZWQpIHN0YXJ0KGVsYXBzZWQgLSBzZWxmLmRlbGF5KTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gc3RhcnQoZWxhcHNlZCkgewogICAgICAgIHZhciBpLCBqLCBuLCBvOwoKICAgICAgICAvLyBJZiB0aGUgc3RhdGUgaXMgbm90IFNDSEVEVUxFRCwgdGhlbiB3ZSBwcmV2aW91c2x5IGVycm9yZWQgb24gc3RhcnQuCiAgICAgICAgaWYgKHNlbGYuc3RhdGUgIT09IFNDSEVEVUxFRCQzKSByZXR1cm4gc3RvcCgpOwoKICAgICAgICBmb3IgKGkgaW4gc2NoZWR1bGVzKSB7CiAgICAgICAgICBvID0gc2NoZWR1bGVzW2ldOwogICAgICAgICAgaWYgKG8ubmFtZSAhPT0gc2VsZi5uYW1lKSBjb250aW51ZTsKCiAgICAgICAgICAvLyBXaGlsZSB0aGlzIGVsZW1lbnQgYWxyZWFkeSBoYXMgYSBzdGFydGluZyB0cmFuc2l0aW9uIGR1cmluZyB0aGlzIGZyYW1lLAogICAgICAgICAgLy8gZGVmZXIgc3RhcnRpbmcgYW4gaW50ZXJydXB0aW5nIHRyYW5zaXRpb24gdW50aWwgdGhhdCB0cmFuc2l0aW9uIGhhcyBhCiAgICAgICAgICAvLyBjaGFuY2UgdG8gdGljayAoYW5kIHBvc3NpYmx5IGVuZCk7IHNlZSBkMy9kMy10cmFuc2l0aW9uIzU0IQogICAgICAgICAgaWYgKG8uc3RhdGUgPT09IFNUQVJURUQkMykgcmV0dXJuIHRpbWVvdXQkYShzdGFydCk7CgogICAgICAgICAgLy8gSW50ZXJydXB0IHRoZSBhY3RpdmUgdHJhbnNpdGlvbiwgaWYgYW55LgogICAgICAgICAgaWYgKG8uc3RhdGUgPT09IFJVTk5JTkckMykgewogICAgICAgICAgICBvLnN0YXRlID0gRU5ERUQkMzsKICAgICAgICAgICAgby50aW1lci5zdG9wKCk7CiAgICAgICAgICAgIG8ub24uY2FsbCgiaW50ZXJydXB0Iiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgby5pbmRleCwgby5ncm91cCk7CiAgICAgICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgICAgICB9CgogICAgICAgICAgLy8gQ2FuY2VsIGFueSBwcmUtZW1wdGVkIHRyYW5zaXRpb25zLgogICAgICAgICAgZWxzZSBpZiAoK2kgPCBpZCkgewogICAgICAgICAgICBvLnN0YXRlID0gRU5ERUQkMzsKICAgICAgICAgICAgby50aW1lci5zdG9wKCk7CiAgICAgICAgICAgIG8ub24uY2FsbCgiY2FuY2VsIiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgby5pbmRleCwgby5ncm91cCk7CiAgICAgICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBEZWZlciB0aGUgZmlyc3QgdGljayB0byBlbmQgb2YgdGhlIGN1cnJlbnQgZnJhbWU7IHNlZSBkMy9kMyMxNTc2LgogICAgICAgIC8vIE5vdGUgdGhlIHRyYW5zaXRpb24gbWF5IGJlIGNhbmNlbGVkIGFmdGVyIHN0YXJ0IGFuZCBiZWZvcmUgdGhlIGZpcnN0IHRpY2shCiAgICAgICAgLy8gTm90ZSB0aGlzIG11c3QgYmUgc2NoZWR1bGVkIGJlZm9yZSB0aGUgc3RhcnQgZXZlbnQ7IHNlZSBkMy9kMy10cmFuc2l0aW9uIzE2IQogICAgICAgIC8vIEFzc3VtaW5nIHRoaXMgaXMgc3VjY2Vzc2Z1bCwgc3Vic2VxdWVudCBjYWxsYmFja3MgZ28gc3RyYWlnaHQgdG8gdGljay4KICAgICAgICB0aW1lb3V0JGEoZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoc2VsZi5zdGF0ZSA9PT0gU1RBUlRFRCQzKSB7CiAgICAgICAgICAgIHNlbGYuc3RhdGUgPSBSVU5OSU5HJDM7CiAgICAgICAgICAgIHNlbGYudGltZXIucmVzdGFydCh0aWNrLCBzZWxmLmRlbGF5LCBzZWxmLnRpbWUpOwogICAgICAgICAgICB0aWNrKGVsYXBzZWQpOwogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICAvLyBEaXNwYXRjaCB0aGUgc3RhcnQgZXZlbnQuCiAgICAgICAgLy8gTm90ZSB0aGlzIG11c3QgYmUgZG9uZSBiZWZvcmUgdGhlIHR3ZWVuIGFyZSBpbml0aWFsaXplZC4KICAgICAgICBzZWxmLnN0YXRlID0gU1RBUlRJTkckMzsKICAgICAgICBzZWxmLm9uLmNhbGwoInN0YXJ0Iiwgbm9kZSwgbm9kZS5fX2RhdGFfXywgc2VsZi5pbmRleCwgc2VsZi5ncm91cCk7CiAgICAgICAgaWYgKHNlbGYuc3RhdGUgIT09IFNUQVJUSU5HJDMpIHJldHVybjsgLy8gaW50ZXJydXB0ZWQKICAgICAgICBzZWxmLnN0YXRlID0gU1RBUlRFRCQzOwoKICAgICAgICAvLyBJbml0aWFsaXplIHRoZSB0d2VlbiwgZGVsZXRpbmcgbnVsbCB0d2Vlbi4KICAgICAgICB0d2VlbiA9IG5ldyBBcnJheShuID0gc2VsZi50d2Vlbi5sZW5ndGgpOwogICAgICAgIGZvciAoaSA9IDAsIGogPSAtMTsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG8gPSBzZWxmLnR3ZWVuW2ldLnZhbHVlLmNhbGwobm9kZSwgbm9kZS5fX2RhdGFfXywgc2VsZi5pbmRleCwgc2VsZi5ncm91cCkpIHsKICAgICAgICAgICAgdHdlZW5bKytqXSA9IG87CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHR3ZWVuLmxlbmd0aCA9IGogKyAxOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0aWNrKGVsYXBzZWQpIHsKICAgICAgICB2YXIgdCA9IGVsYXBzZWQgPCBzZWxmLmR1cmF0aW9uID8gc2VsZi5lYXNlLmNhbGwobnVsbCwgZWxhcHNlZCAvIHNlbGYuZHVyYXRpb24pIDogKHNlbGYudGltZXIucmVzdGFydChzdG9wKSwgc2VsZi5zdGF0ZSA9IEVORElORyQzLCAxKSwKICAgICAgICAgICAgaSA9IC0xLAogICAgICAgICAgICBuID0gdHdlZW4ubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytpIDwgbikgewogICAgICAgICAgdHdlZW5baV0uY2FsbChub2RlLCB0KTsKICAgICAgICB9CgogICAgICAgIC8vIERpc3BhdGNoIHRoZSBlbmQgZXZlbnQuCiAgICAgICAgaWYgKHNlbGYuc3RhdGUgPT09IEVORElORyQzKSB7CiAgICAgICAgICBzZWxmLm9uLmNhbGwoImVuZCIsIG5vZGUsIG5vZGUuX19kYXRhX18sIHNlbGYuaW5kZXgsIHNlbGYuZ3JvdXApOwogICAgICAgICAgc3RvcCgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gc3RvcCgpIHsKICAgICAgICBzZWxmLnN0YXRlID0gRU5ERUQkMzsKICAgICAgICBzZWxmLnRpbWVyLnN0b3AoKTsKICAgICAgICBkZWxldGUgc2NoZWR1bGVzW2lkXTsKICAgICAgICBmb3IgKHZhciBpIGluIHNjaGVkdWxlcykgcmV0dXJuOyAvLyBlc2xpbnQtZGlzYWJsZS1saW5lIG5vLXVudXNlZC12YXJzCiAgICAgICAgZGVsZXRlIG5vZGUuX190cmFuc2l0aW9uOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gaW50ZXJydXB0JDMobm9kZSwgbmFtZSkgewogICAgICB2YXIgc2NoZWR1bGVzID0gbm9kZS5fX3RyYW5zaXRpb24sCiAgICAgICAgICBzY2hlZHVsZSwKICAgICAgICAgIGFjdGl2ZSwKICAgICAgICAgIGVtcHR5ID0gdHJ1ZSwKICAgICAgICAgIGk7CgogICAgICBpZiAoIXNjaGVkdWxlcykgcmV0dXJuOwoKICAgICAgbmFtZSA9IG5hbWUgPT0gbnVsbCA/IG51bGwgOiBuYW1lICsgIiI7CgogICAgICBmb3IgKGkgaW4gc2NoZWR1bGVzKSB7CiAgICAgICAgaWYgKChzY2hlZHVsZSA9IHNjaGVkdWxlc1tpXSkubmFtZSAhPT0gbmFtZSkgeyBlbXB0eSA9IGZhbHNlOyBjb250aW51ZTsgfQogICAgICAgIGFjdGl2ZSA9IHNjaGVkdWxlLnN0YXRlID4gU1RBUlRJTkckMyAmJiBzY2hlZHVsZS5zdGF0ZSA8IEVORElORyQzOwogICAgICAgIHNjaGVkdWxlLnN0YXRlID0gRU5ERUQkMzsKICAgICAgICBzY2hlZHVsZS50aW1lci5zdG9wKCk7CiAgICAgICAgc2NoZWR1bGUub24uY2FsbChhY3RpdmUgPyAiaW50ZXJydXB0IiA6ICJjYW5jZWwiLCBub2RlLCBub2RlLl9fZGF0YV9fLCBzY2hlZHVsZS5pbmRleCwgc2NoZWR1bGUuZ3JvdXApOwogICAgICAgIGRlbGV0ZSBzY2hlZHVsZXNbaV07CiAgICAgIH0KCiAgICAgIGlmIChlbXB0eSkgZGVsZXRlIG5vZGUuX190cmFuc2l0aW9uOwogICAgfQoKICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9pbnRlcnJ1cHQkMyhuYW1lKSB7CiAgICAgIHJldHVybiB0aGlzLmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgaW50ZXJydXB0JDModGhpcywgbmFtZSk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHR3ZWVuUmVtb3ZlJDMoaWQsIG5hbWUpIHsKICAgICAgdmFyIHR3ZWVuMCwgdHdlZW4xOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JGYodGhpcywgaWQpLAogICAgICAgICAgICB0d2VlbiA9IHNjaGVkdWxlLnR3ZWVuOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIHR3ZWVuIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIHR3ZWVuIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmICh0d2VlbiAhPT0gdHdlZW4wKSB7CiAgICAgICAgICB0d2VlbjEgPSB0d2VlbjAgPSB0d2VlbjsKICAgICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gdHdlZW4xLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAodHdlZW4xW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgICB0d2VlbjEgPSB0d2VlbjEuc2xpY2UoKTsKICAgICAgICAgICAgICB0d2VlbjEuc3BsaWNlKGksIDEpOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBzY2hlZHVsZS50d2VlbiA9IHR3ZWVuMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0d2VlbkZ1bmN0aW9uJDMoaWQsIG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciB0d2VlbjAsIHR3ZWVuMTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHNjaGVkdWxlID0gc2V0JGYodGhpcywgaWQpLAogICAgICAgICAgICB0d2VlbiA9IHNjaGVkdWxlLnR3ZWVuOwoKICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIHR3ZWVuIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIHR3ZWVuIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmICh0d2VlbiAhPT0gdHdlZW4wKSB7CiAgICAgICAgICB0d2VlbjEgPSAodHdlZW4wID0gdHdlZW4pLnNsaWNlKCk7CiAgICAgICAgICBmb3IgKHZhciB0ID0ge25hbWU6IG5hbWUsIHZhbHVlOiB2YWx1ZX0sIGkgPSAwLCBuID0gdHdlZW4xLmxlbmd0aDsgaSA8IG47ICsraSkgewogICAgICAgICAgICBpZiAodHdlZW4xW2ldLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgICB0d2VlbjFbaV0gPSB0OwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaSA9PT0gbikgdHdlZW4xLnB1c2godCk7CiAgICAgICAgfQoKICAgICAgICBzY2hlZHVsZS50d2VlbiA9IHR3ZWVuMTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3R3ZWVuJDMobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICBuYW1lICs9ICIiOwoKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgdmFyIHR3ZWVuID0gZ2V0JGIodGhpcy5ub2RlKCksIGlkKS50d2VlbjsKICAgICAgICBmb3IgKHZhciBpID0gMCwgbiA9IHR3ZWVuLmxlbmd0aCwgdDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKCh0ID0gdHdlZW5baV0pLm5hbWUgPT09IG5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIHQudmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBudWxsOwogICAgICB9CgogICAgICByZXR1cm4gdGhpcy5lYWNoKCh2YWx1ZSA9PSBudWxsID8gdHdlZW5SZW1vdmUkMyA6IHR3ZWVuRnVuY3Rpb24kMykoaWQsIG5hbWUsIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdHdlZW5WYWx1ZSQzKHRyYW5zaXRpb24sIG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBpZCA9IHRyYW5zaXRpb24uX2lkOwoKICAgICAgdHJhbnNpdGlvbi5lYWNoKGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNldCRmKHRoaXMsIGlkKTsKICAgICAgICAoc2NoZWR1bGUudmFsdWUgfHwgKHNjaGVkdWxlLnZhbHVlID0ge30pKVtuYW1lXSA9IHZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICByZXR1cm4gZ2V0JGIobm9kZSwgaWQpLnZhbHVlW25hbWVdOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGludGVycG9sYXRlJDYoYSwgYikgewogICAgICB2YXIgYzsKICAgICAgcmV0dXJuICh0eXBlb2YgYiA9PT0gIm51bWJlciIgPyBpbnRlcnBvbGF0ZU51bWJlciQzCiAgICAgICAgICA6IGIgaW5zdGFuY2VvZiBjb2xvciQ2ID8gaW50ZXJwb2xhdGVSZ2IkMwogICAgICAgICAgOiAoYyA9IGNvbG9yJDYoYikpID8gKGIgPSBjLCBpbnRlcnBvbGF0ZVJnYiQzKQogICAgICAgICAgOiBpbnRlcnBvbGF0ZVN0cmluZyQzKShhLCBiKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyUmVtb3ZlJDkobmFtZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clJlbW92ZU5TJDkoZnVsbG5hbWUpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyQ29uc3RhbnQkOShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUxKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIiwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckNvbnN0YW50TlMkOShmdWxsbmFtZSwgaW50ZXJwb2xhdGUsIHZhbHVlMSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiIsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCA9IHRoaXMuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgdmFsdWUxKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb24kOShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCwgdmFsdWUxID0gdmFsdWUodGhpcyksIHN0cmluZzE7CiAgICAgICAgaWYgKHZhbHVlMSA9PSBudWxsKSByZXR1cm4gdm9pZCB0aGlzLnJlbW92ZUF0dHJpYnV0ZShuYW1lKTsKICAgICAgICBzdHJpbmcwID0gdGhpcy5nZXRBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgc3RyaW5nMSA9IHZhbHVlMSArICIiOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwICYmIHN0cmluZzEgPT09IHN0cmluZzEwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogKHN0cmluZzEwID0gc3RyaW5nMSwgaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCB2YWx1ZTEpKTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBhdHRyRnVuY3Rpb25OUyQ5KGZ1bGxuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCwgdmFsdWUxID0gdmFsdWUodGhpcyksIHN0cmluZzE7CiAgICAgICAgaWYgKHZhbHVlMSA9PSBudWxsKSByZXR1cm4gdm9pZCB0aGlzLnJlbW92ZUF0dHJpYnV0ZU5TKGZ1bGxuYW1lLnNwYWNlLCBmdWxsbmFtZS5sb2NhbCk7CiAgICAgICAgc3RyaW5nMCA9IHRoaXMuZ2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsKTsKICAgICAgICBzdHJpbmcxID0gdmFsdWUxICsgIiI7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgJiYgc3RyaW5nMSA9PT0gc3RyaW5nMTAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiAoc3RyaW5nMTAgPSBzdHJpbmcxLCBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHZhbHVlMSkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0ciQzKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBmdWxsbmFtZSA9IG5hbWVzcGFjZSQ1KG5hbWUpLCBpID0gZnVsbG5hbWUgPT09ICJ0cmFuc2Zvcm0iID8gaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmckNCA6IGludGVycG9sYXRlJDY7CiAgICAgIHJldHVybiB0aGlzLmF0dHJUd2VlbihuYW1lLCB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gKGZ1bGxuYW1lLmxvY2FsID8gYXR0ckZ1bmN0aW9uTlMkOSA6IGF0dHJGdW5jdGlvbiQ5KShmdWxsbmFtZSwgaSwgdHdlZW5WYWx1ZSQzKHRoaXMsICJhdHRyLiIgKyBuYW1lLCB2YWx1ZSkpCiAgICAgICAgICA6IHZhbHVlID09IG51bGwgPyAoZnVsbG5hbWUubG9jYWwgPyBhdHRyUmVtb3ZlTlMkOSA6IGF0dHJSZW1vdmUkOSkoZnVsbG5hbWUpCiAgICAgICAgICA6IChmdWxsbmFtZS5sb2NhbCA/IGF0dHJDb25zdGFudE5TJDkgOiBhdHRyQ29uc3RhbnQkOSkoZnVsbG5hbWUsIGksIHZhbHVlKSk7CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckludGVycG9sYXRlJDIobmFtZSwgaSkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKG5hbWUsIGkuY2FsbCh0aGlzLCB0KSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gYXR0ckludGVycG9sYXRlTlMkMihmdWxsbmFtZSwgaSkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHRoaXMuc2V0QXR0cmlidXRlTlMoZnVsbG5hbWUuc3BhY2UsIGZ1bGxuYW1lLmxvY2FsLCBpLmNhbGwodGhpcywgdCkpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGF0dHJUd2Vlbk5TJDMoZnVsbG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciB0MCwgaTA7CiAgICAgIGZ1bmN0aW9uIHR3ZWVuKCkgewogICAgICAgIHZhciBpID0gdmFsdWUuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgICBpZiAoaSAhPT0gaTApIHQwID0gKGkwID0gaSkgJiYgYXR0ckludGVycG9sYXRlTlMkMihmdWxsbmFtZSwgaSk7CiAgICAgICAgcmV0dXJuIHQwOwogICAgICB9CiAgICAgIHR3ZWVuLl92YWx1ZSA9IHZhbHVlOwogICAgICByZXR1cm4gdHdlZW47CiAgICB9CgogICAgZnVuY3Rpb24gYXR0clR3ZWVuJDMobmFtZSwgdmFsdWUpIHsKICAgICAgdmFyIHQwLCBpMDsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChpICE9PSBpMCkgdDAgPSAoaTAgPSBpKSAmJiBhdHRySW50ZXJwb2xhdGUkMihuYW1lLCBpKTsKICAgICAgICByZXR1cm4gdDA7CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2F0dHJUd2VlbiQzKG5hbWUsIHZhbHVlKSB7CiAgICAgIHZhciBrZXkgPSAiYXR0ci4iICsgbmFtZTsKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSByZXR1cm4gKGtleSA9IHRoaXMudHdlZW4oa2V5KSkgJiYga2V5Ll92YWx1ZTsKICAgICAgaWYgKHZhbHVlID09IG51bGwpIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgbnVsbCk7CiAgICAgIGlmICh0eXBlb2YgdmFsdWUgIT09ICJmdW5jdGlvbiIpIHRocm93IG5ldyBFcnJvcjsKICAgICAgdmFyIGZ1bGxuYW1lID0gbmFtZXNwYWNlJDUobmFtZSk7CiAgICAgIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgKGZ1bGxuYW1lLmxvY2FsID8gYXR0clR3ZWVuTlMkMyA6IGF0dHJUd2VlbiQzKShmdWxsbmFtZSwgdmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWxheUZ1bmN0aW9uJDMoaWQsIHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICBpbml0JDModGhpcywgaWQpLmRlbGF5ID0gK3ZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZGVsYXlDb25zdGFudCQzKGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPSArdmFsdWUsIGZ1bmN0aW9uKCkgewogICAgICAgIGluaXQkMyh0aGlzLCBpZCkuZGVsYXkgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2RlbGF5JDModmFsdWUpIHsKICAgICAgdmFyIGlkID0gdGhpcy5faWQ7CgogICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aAogICAgICAgICAgPyB0aGlzLmVhY2goKHR5cGVvZiB2YWx1ZSA9PT0gImZ1bmN0aW9uIgogICAgICAgICAgICAgID8gZGVsYXlGdW5jdGlvbiQzCiAgICAgICAgICAgICAgOiBkZWxheUNvbnN0YW50JDMpKGlkLCB2YWx1ZSkpCiAgICAgICAgICA6IGdldCRiKHRoaXMubm9kZSgpLCBpZCkuZGVsYXk7CiAgICB9CgogICAgZnVuY3Rpb24gZHVyYXRpb25GdW5jdGlvbiQzKGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgc2V0JGYodGhpcywgaWQpLmR1cmF0aW9uID0gK3ZhbHVlLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gZHVyYXRpb25Db25zdGFudCQzKGlkLCB2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPSArdmFsdWUsIGZ1bmN0aW9uKCkgewogICAgICAgIHNldCRmKHRoaXMsIGlkKS5kdXJhdGlvbiA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fZHVyYXRpb24kMyh2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaCgodHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iCiAgICAgICAgICAgICAgPyBkdXJhdGlvbkZ1bmN0aW9uJDMKICAgICAgICAgICAgICA6IGR1cmF0aW9uQ29uc3RhbnQkMykoaWQsIHZhbHVlKSkKICAgICAgICAgIDogZ2V0JGIodGhpcy5ub2RlKCksIGlkKS5kdXJhdGlvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBlYXNlQ29uc3RhbnQkMyhpZCwgdmFsdWUpIHsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgc2V0JGYodGhpcywgaWQpLmVhc2UgPSB2YWx1ZTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2Vhc2UkMyh2YWx1ZSkgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoCiAgICAgICAgICA/IHRoaXMuZWFjaChlYXNlQ29uc3RhbnQkMyhpZCwgdmFsdWUpKQogICAgICAgICAgOiBnZXQkYih0aGlzLm5vZGUoKSwgaWQpLmVhc2U7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9maWx0ZXIkMyhtYXRjaCkgewogICAgICBpZiAodHlwZW9mIG1hdGNoICE9PSAiZnVuY3Rpb24iKSBtYXRjaCA9IG1hdGNoZXIkNihtYXRjaCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBuZXcgQXJyYXkobSksIGogPSAwOyBqIDwgbTsgKytqKSB7CiAgICAgICAgZm9yICh2YXIgZ3JvdXAgPSBncm91cHNbal0sIG4gPSBncm91cC5sZW5ndGgsIHN1Ymdyb3VwID0gc3ViZ3JvdXBzW2pdID0gW10sIG5vZGUsIGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKG5vZGUgPSBncm91cFtpXSkgJiYgbWF0Y2guY2FsbChub2RlLCBub2RlLl9fZGF0YV9fLCBpLCBncm91cCkpIHsKICAgICAgICAgICAgc3ViZ3JvdXAucHVzaChub2RlKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQzKHN1Ymdyb3VwcywgdGhpcy5fcGFyZW50cywgdGhpcy5fbmFtZSwgdGhpcy5faWQpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fbWVyZ2UkMyh0cmFuc2l0aW9uKSB7CiAgICAgIGlmICh0cmFuc2l0aW9uLl9pZCAhPT0gdGhpcy5faWQpIHRocm93IG5ldyBFcnJvcjsKCiAgICAgIGZvciAodmFyIGdyb3VwczAgPSB0aGlzLl9ncm91cHMsIGdyb3VwczEgPSB0cmFuc2l0aW9uLl9ncm91cHMsIG0wID0gZ3JvdXBzMC5sZW5ndGgsIG0xID0gZ3JvdXBzMS5sZW5ndGgsIG0gPSBNYXRoLm1pbihtMCwgbTEpLCBtZXJnZXMgPSBuZXcgQXJyYXkobTApLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwMCA9IGdyb3VwczBbal0sIGdyb3VwMSA9IGdyb3VwczFbal0sIG4gPSBncm91cDAubGVuZ3RoLCBtZXJnZSA9IG1lcmdlc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmIChub2RlID0gZ3JvdXAwW2ldIHx8IGdyb3VwMVtpXSkgewogICAgICAgICAgICBtZXJnZVtpXSA9IG5vZGU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBmb3IgKDsgaiA8IG0wOyArK2opIHsKICAgICAgICBtZXJnZXNbal0gPSBncm91cHMwW2pdOwogICAgICB9CgogICAgICByZXR1cm4gbmV3IFRyYW5zaXRpb24kMyhtZXJnZXMsIHRoaXMuX3BhcmVudHMsIHRoaXMuX25hbWUsIHRoaXMuX2lkKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdGFydCQ0KG5hbWUpIHsKICAgICAgcmV0dXJuIChuYW1lICsgIiIpLnRyaW0oKS5zcGxpdCgvXnxccysvKS5ldmVyeShmdW5jdGlvbih0KSB7CiAgICAgICAgdmFyIGkgPSB0LmluZGV4T2YoIi4iKTsKICAgICAgICBpZiAoaSA+PSAwKSB0ID0gdC5zbGljZSgwLCBpKTsKICAgICAgICByZXR1cm4gIXQgfHwgdCA9PT0gInN0YXJ0IjsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gb25GdW5jdGlvbiQzKGlkLCBuYW1lLCBsaXN0ZW5lcikgewogICAgICB2YXIgb24wLCBvbjEsIHNpdCA9IHN0YXJ0JDQobmFtZSkgPyBpbml0JDMgOiBzZXQkZjsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzY2hlZHVsZSA9IHNpdCh0aGlzLCBpZCksCiAgICAgICAgICAgIG9uID0gc2NoZWR1bGUub247CgogICAgICAgIC8vIElmIHRoaXMgbm9kZSBzaGFyZWQgYSBkaXNwYXRjaCB3aXRoIHRoZSBwcmV2aW91cyBub2RlLAogICAgICAgIC8vIGp1c3QgYXNzaWduIHRoZSB1cGRhdGVkIHNoYXJlZCBkaXNwYXRjaCBhbmQgd2XigJlyZSBkb25lIQogICAgICAgIC8vIE90aGVyd2lzZSwgY29weS1vbi13cml0ZS4KICAgICAgICBpZiAob24gIT09IG9uMCkgKG9uMSA9IChvbjAgPSBvbikuY29weSgpKS5vbihuYW1lLCBsaXN0ZW5lcik7CgogICAgICAgIHNjaGVkdWxlLm9uID0gb24xOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fb24kMyhuYW1lLCBsaXN0ZW5lcikgewogICAgICB2YXIgaWQgPSB0aGlzLl9pZDsKCiAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoIDwgMgogICAgICAgICAgPyBnZXQkYih0aGlzLm5vZGUoKSwgaWQpLm9uLm9uKG5hbWUpCiAgICAgICAgICA6IHRoaXMuZWFjaChvbkZ1bmN0aW9uJDMoaWQsIG5hbWUsIGxpc3RlbmVyKSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlRnVuY3Rpb24kMyhpZCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgICBmb3IgKHZhciBpIGluIHRoaXMuX190cmFuc2l0aW9uKSBpZiAoK2kgIT09IGlkKSByZXR1cm47CiAgICAgICAgaWYgKHBhcmVudCkgcGFyZW50LnJlbW92ZUNoaWxkKHRoaXMpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fcmVtb3ZlJDMoKSB7CiAgICAgIHJldHVybiB0aGlzLm9uKCJlbmQucmVtb3ZlIiwgcmVtb3ZlRnVuY3Rpb24kMyh0aGlzLl9pZCkpOwogICAgfQoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc2VsZWN0JDMoc2VsZWN0KSB7CiAgICAgIHZhciBuYW1lID0gdGhpcy5fbmFtZSwKICAgICAgICAgIGlkID0gdGhpcy5faWQ7CgogICAgICBpZiAodHlwZW9mIHNlbGVjdCAhPT0gImZ1bmN0aW9uIikgc2VsZWN0ID0gc2VsZWN0b3IkNShzZWxlY3QpOwoKICAgICAgZm9yICh2YXIgZ3JvdXBzID0gdGhpcy5fZ3JvdXBzLCBtID0gZ3JvdXBzLmxlbmd0aCwgc3ViZ3JvdXBzID0gbmV3IEFycmF5KG0pLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBzdWJncm91cCA9IHN1Ymdyb3Vwc1tqXSA9IG5ldyBBcnJheShuKSwgbm9kZSwgc3Vibm9kZSwgaSA9IDA7IGkgPCBuOyArK2kpIHsKICAgICAgICAgIGlmICgobm9kZSA9IGdyb3VwW2ldKSAmJiAoc3Vibm9kZSA9IHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSkpIHsKICAgICAgICAgICAgaWYgKCJfX2RhdGFfXyIgaW4gbm9kZSkgc3Vibm9kZS5fX2RhdGFfXyA9IG5vZGUuX19kYXRhX187CiAgICAgICAgICAgIHN1Ymdyb3VwW2ldID0gc3Vibm9kZTsKICAgICAgICAgICAgc2NoZWR1bGUkNChzdWJncm91cFtpXSwgbmFtZSwgaWQsIGksIHN1Ymdyb3VwLCBnZXQkYihub2RlLCBpZCkpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDMoc3ViZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCBuYW1lLCBpZCk7CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zZWxlY3RBbGwkMyhzZWxlY3QpIHsKICAgICAgdmFyIG5hbWUgPSB0aGlzLl9uYW1lLAogICAgICAgICAgaWQgPSB0aGlzLl9pZDsKCiAgICAgIGlmICh0eXBlb2Ygc2VsZWN0ICE9PSAiZnVuY3Rpb24iKSBzZWxlY3QgPSBzZWxlY3RvckFsbCQ1KHNlbGVjdCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBzdWJncm91cHMgPSBbXSwgcGFyZW50cyA9IFtdLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBmb3IgKHZhciBjaGlsZHJlbiA9IHNlbGVjdC5jYWxsKG5vZGUsIG5vZGUuX19kYXRhX18sIGksIGdyb3VwKSwgY2hpbGQsIGluaGVyaXQgPSBnZXQkYihub2RlLCBpZCksIGsgPSAwLCBsID0gY2hpbGRyZW4ubGVuZ3RoOyBrIDwgbDsgKytrKSB7CiAgICAgICAgICAgICAgaWYgKGNoaWxkID0gY2hpbGRyZW5ba10pIHsKICAgICAgICAgICAgICAgIHNjaGVkdWxlJDQoY2hpbGQsIG5hbWUsIGlkLCBrLCBjaGlsZHJlbiwgaW5oZXJpdCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHN1Ymdyb3Vwcy5wdXNoKGNoaWxkcmVuKTsKICAgICAgICAgICAgcGFyZW50cy5wdXNoKG5vZGUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDMoc3ViZ3JvdXBzLCBwYXJlbnRzLCBuYW1lLCBpZCk7CiAgICB9CgogICAgdmFyIFNlbGVjdGlvbiQ5ID0gc2VsZWN0aW9uJDUucHJvdG90eXBlLmNvbnN0cnVjdG9yOwoKICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fc2VsZWN0aW9uJDMoKSB7CiAgICAgIHJldHVybiBuZXcgU2VsZWN0aW9uJDkodGhpcy5fZ3JvdXBzLCB0aGlzLl9wYXJlbnRzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZU51bGwkMihuYW1lLCBpbnRlcnBvbGF0ZSkgewogICAgICB2YXIgc3RyaW5nMDAsCiAgICAgICAgICBzdHJpbmcxMCwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gc3R5bGVWYWx1ZSQ1KHRoaXMsIG5hbWUpLAogICAgICAgICAgICBzdHJpbmcxID0gKHRoaXMuc3R5bGUucmVtb3ZlUHJvcGVydHkobmFtZSksIHN0eWxlVmFsdWUkNSh0aGlzLCBuYW1lKSk7CiAgICAgICAgcmV0dXJuIHN0cmluZzAgPT09IHN0cmluZzEgPyBudWxsCiAgICAgICAgICAgIDogc3RyaW5nMCA9PT0gc3RyaW5nMDAgJiYgc3RyaW5nMSA9PT0gc3RyaW5nMTAgPyBpbnRlcnBvbGF0ZTAKICAgICAgICAgICAgOiBpbnRlcnBvbGF0ZTAgPSBpbnRlcnBvbGF0ZShzdHJpbmcwMCA9IHN0cmluZzAsIHN0cmluZzEwID0gc3RyaW5nMSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVSZW1vdmUkOShuYW1lKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB0aGlzLnN0eWxlLnJlbW92ZVByb3BlcnR5KG5hbWUpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlQ29uc3RhbnQkOShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUxKSB7CiAgICAgIHZhciBzdHJpbmcwMCwKICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIiwKICAgICAgICAgIGludGVycG9sYXRlMDsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBzdHJpbmcwID0gc3R5bGVWYWx1ZSQ1KHRoaXMsIG5hbWUpOwogICAgICAgIHJldHVybiBzdHJpbmcwID09PSBzdHJpbmcxID8gbnVsbAogICAgICAgICAgICA6IHN0cmluZzAgPT09IHN0cmluZzAwID8gaW50ZXJwb2xhdGUwCiAgICAgICAgICAgIDogaW50ZXJwb2xhdGUwID0gaW50ZXJwb2xhdGUoc3RyaW5nMDAgPSBzdHJpbmcwLCB2YWx1ZTEpOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHN0eWxlRnVuY3Rpb24kOShuYW1lLCBpbnRlcnBvbGF0ZSwgdmFsdWUpIHsKICAgICAgdmFyIHN0cmluZzAwLAogICAgICAgICAgc3RyaW5nMTAsCiAgICAgICAgICBpbnRlcnBvbGF0ZTA7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RyaW5nMCA9IHN0eWxlVmFsdWUkNSh0aGlzLCBuYW1lKSwKICAgICAgICAgICAgdmFsdWUxID0gdmFsdWUodGhpcyksCiAgICAgICAgICAgIHN0cmluZzEgPSB2YWx1ZTEgKyAiIjsKICAgICAgICBpZiAodmFsdWUxID09IG51bGwpIHN0cmluZzEgPSB2YWx1ZTEgPSAodGhpcy5zdHlsZS5yZW1vdmVQcm9wZXJ0eShuYW1lKSwgc3R5bGVWYWx1ZSQ1KHRoaXMsIG5hbWUpKTsKICAgICAgICByZXR1cm4gc3RyaW5nMCA9PT0gc3RyaW5nMSA/IG51bGwKICAgICAgICAgICAgOiBzdHJpbmcwID09PSBzdHJpbmcwMCAmJiBzdHJpbmcxID09PSBzdHJpbmcxMCA/IGludGVycG9sYXRlMAogICAgICAgICAgICA6IChzdHJpbmcxMCA9IHN0cmluZzEsIGludGVycG9sYXRlMCA9IGludGVycG9sYXRlKHN0cmluZzAwID0gc3RyaW5nMCwgdmFsdWUxKSk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVNYXliZVJlbW92ZSQyKGlkLCBuYW1lKSB7CiAgICAgIHZhciBvbjAsIG9uMSwgbGlzdGVuZXIwLCBrZXkgPSAic3R5bGUuIiArIG5hbWUsIGV2ZW50ID0gImVuZC4iICsga2V5LCByZW1vdmU7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2NoZWR1bGUgPSBzZXQkZih0aGlzLCBpZCksCiAgICAgICAgICAgIG9uID0gc2NoZWR1bGUub24sCiAgICAgICAgICAgIGxpc3RlbmVyID0gc2NoZWR1bGUudmFsdWVba2V5XSA9PSBudWxsID8gcmVtb3ZlIHx8IChyZW1vdmUgPSBzdHlsZVJlbW92ZSQ5KG5hbWUpKSA6IHVuZGVmaW5lZDsKCiAgICAgICAgLy8gSWYgdGhpcyBub2RlIHNoYXJlZCBhIGRpc3BhdGNoIHdpdGggdGhlIHByZXZpb3VzIG5vZGUsCiAgICAgICAgLy8ganVzdCBhc3NpZ24gdGhlIHVwZGF0ZWQgc2hhcmVkIGRpc3BhdGNoIGFuZCB3ZeKAmXJlIGRvbmUhCiAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgIGlmIChvbiAhPT0gb24wIHx8IGxpc3RlbmVyMCAhPT0gbGlzdGVuZXIpIChvbjEgPSAob24wID0gb24pLmNvcHkoKSkub24oZXZlbnQsIGxpc3RlbmVyMCA9IGxpc3RlbmVyKTsKCiAgICAgICAgc2NoZWR1bGUub24gPSBvbjE7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zdHlsZSQzKG5hbWUsIHZhbHVlLCBwcmlvcml0eSkgewogICAgICB2YXIgaSA9IChuYW1lICs9ICIiKSA9PT0gInRyYW5zZm9ybSIgPyBpbnRlcnBvbGF0ZVRyYW5zZm9ybUNzcyQ0IDogaW50ZXJwb2xhdGUkNjsKICAgICAgcmV0dXJuIHZhbHVlID09IG51bGwgPyB0aGlzCiAgICAgICAgICAuc3R5bGVUd2VlbihuYW1lLCBzdHlsZU51bGwkMihuYW1lLCBpKSkKICAgICAgICAgIC5vbigiZW5kLnN0eWxlLiIgKyBuYW1lLCBzdHlsZVJlbW92ZSQ5KG5hbWUpKQogICAgICAgIDogdHlwZW9mIHZhbHVlID09PSAiZnVuY3Rpb24iID8gdGhpcwogICAgICAgICAgLnN0eWxlVHdlZW4obmFtZSwgc3R5bGVGdW5jdGlvbiQ5KG5hbWUsIGksIHR3ZWVuVmFsdWUkMyh0aGlzLCAic3R5bGUuIiArIG5hbWUsIHZhbHVlKSkpCiAgICAgICAgICAuZWFjaChzdHlsZU1heWJlUmVtb3ZlJDIodGhpcy5faWQsIG5hbWUpKQogICAgICAgIDogdGhpcwogICAgICAgICAgLnN0eWxlVHdlZW4obmFtZSwgc3R5bGVDb25zdGFudCQ5KG5hbWUsIGksIHZhbHVlKSwgcHJpb3JpdHkpCiAgICAgICAgICAub24oImVuZC5zdHlsZS4iICsgbmFtZSwgbnVsbCk7CiAgICB9CgogICAgZnVuY3Rpb24gc3R5bGVJbnRlcnBvbGF0ZSQyKG5hbWUsIGksIHByaW9yaXR5KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbih0KSB7CiAgICAgICAgdGhpcy5zdHlsZS5zZXRQcm9wZXJ0eShuYW1lLCBpLmNhbGwodGhpcywgdCksIHByaW9yaXR5KTsKICAgICAgfTsKICAgIH0KCiAgICBmdW5jdGlvbiBzdHlsZVR3ZWVuJDMobmFtZSwgdmFsdWUsIHByaW9yaXR5KSB7CiAgICAgIHZhciB0LCBpMDsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChpICE9PSBpMCkgdCA9IChpMCA9IGkpICYmIHN0eWxlSW50ZXJwb2xhdGUkMihuYW1lLCBpLCBwcmlvcml0eSk7CiAgICAgICAgcmV0dXJuIHQ7CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3N0eWxlVHdlZW4kMyhuYW1lLCB2YWx1ZSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIGtleSA9ICJzdHlsZS4iICsgKG5hbWUgKz0gIiIpOwogICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA8IDIpIHJldHVybiAoa2V5ID0gdGhpcy50d2VlbihrZXkpKSAmJiBrZXkuX3ZhbHVlOwogICAgICBpZiAodmFsdWUgPT0gbnVsbCkgcmV0dXJuIHRoaXMudHdlZW4oa2V5LCBudWxsKTsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPT0gImZ1bmN0aW9uIikgdGhyb3cgbmV3IEVycm9yOwogICAgICByZXR1cm4gdGhpcy50d2VlbihrZXksIHN0eWxlVHdlZW4kMyhuYW1lLCB2YWx1ZSwgcHJpb3JpdHkgPT0gbnVsbCA/ICIiIDogcHJpb3JpdHkpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0ZXh0Q29uc3RhbnQkOSh2YWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHZhbHVlOwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHRleHRGdW5jdGlvbiQ5KHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgdmFsdWUxID0gdmFsdWUodGhpcyk7CiAgICAgICAgdGhpcy50ZXh0Q29udGVudCA9IHZhbHVlMSA9PSBudWxsID8gIiIgOiB2YWx1ZTE7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl90ZXh0JDModmFsdWUpIHsKICAgICAgcmV0dXJuIHRoaXMudHdlZW4oInRleHQiLCB0eXBlb2YgdmFsdWUgPT09ICJmdW5jdGlvbiIKICAgICAgICAgID8gdGV4dEZ1bmN0aW9uJDkodHdlZW5WYWx1ZSQzKHRoaXMsICJ0ZXh0IiwgdmFsdWUpKQogICAgICAgICAgOiB0ZXh0Q29uc3RhbnQkOSh2YWx1ZSA9PSBudWxsID8gIiIgOiB2YWx1ZSArICIiKSk7CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dEludGVycG9sYXRlJDIoaSkgewogICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgIHRoaXMudGV4dENvbnRlbnQgPSBpLmNhbGwodGhpcywgdCk7CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gdGV4dFR3ZWVuJDIodmFsdWUpIHsKICAgICAgdmFyIHQwLCBpMDsKICAgICAgZnVuY3Rpb24gdHdlZW4oKSB7CiAgICAgICAgdmFyIGkgPSB2YWx1ZS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgIGlmIChpICE9PSBpMCkgdDAgPSAoaTAgPSBpKSAmJiB0ZXh0SW50ZXJwb2xhdGUkMihpKTsKICAgICAgICByZXR1cm4gdDA7CiAgICAgIH0KICAgICAgdHdlZW4uX3ZhbHVlID0gdmFsdWU7CiAgICAgIHJldHVybiB0d2VlbjsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3RleHRUd2VlbiQyKHZhbHVlKSB7CiAgICAgIHZhciBrZXkgPSAidGV4dCI7CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoIDwgMSkgcmV0dXJuIChrZXkgPSB0aGlzLnR3ZWVuKGtleSkpICYmIGtleS5fdmFsdWU7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSByZXR1cm4gdGhpcy50d2VlbihrZXksIG51bGwpOwogICAgICBpZiAodHlwZW9mIHZhbHVlICE9PSAiZnVuY3Rpb24iKSB0aHJvdyBuZXcgRXJyb3I7CiAgICAgIHJldHVybiB0aGlzLnR3ZWVuKGtleSwgdGV4dFR3ZWVuJDIodmFsdWUpKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX3RyYW5zaXRpb24kMygpIHsKICAgICAgdmFyIG5hbWUgPSB0aGlzLl9uYW1lLAogICAgICAgICAgaWQwID0gdGhpcy5faWQsCiAgICAgICAgICBpZDEgPSBuZXdJZCQzKCk7CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICB2YXIgaW5oZXJpdCA9IGdldCRiKG5vZGUsIGlkMCk7CiAgICAgICAgICAgIHNjaGVkdWxlJDQobm9kZSwgbmFtZSwgaWQxLCBpLCBncm91cCwgewogICAgICAgICAgICAgIHRpbWU6IGluaGVyaXQudGltZSArIGluaGVyaXQuZGVsYXkgKyBpbmhlcml0LmR1cmF0aW9uLAogICAgICAgICAgICAgIGRlbGF5OiAwLAogICAgICAgICAgICAgIGR1cmF0aW9uOiBpbmhlcml0LmR1cmF0aW9uLAogICAgICAgICAgICAgIGVhc2U6IGluaGVyaXQuZWFzZQogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXcgVHJhbnNpdGlvbiQzKGdyb3VwcywgdGhpcy5fcGFyZW50cywgbmFtZSwgaWQxKTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uX2VuZCQyKCkgewogICAgICB2YXIgb24wLCBvbjEsIHRoYXQgPSB0aGlzLCBpZCA9IHRoYXQuX2lkLCBzaXplID0gdGhhdC5zaXplKCk7CiAgICAgIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLCByZWplY3QpIHsKICAgICAgICB2YXIgY2FuY2VsID0ge3ZhbHVlOiByZWplY3R9LAogICAgICAgICAgICBlbmQgPSB7dmFsdWU6IGZ1bmN0aW9uKCkgeyBpZiAoLS1zaXplID09PSAwKSByZXNvbHZlKCk7IH19OwoKICAgICAgICB0aGF0LmVhY2goZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgc2NoZWR1bGUgPSBzZXQkZih0aGlzLCBpZCksCiAgICAgICAgICAgICAgb24gPSBzY2hlZHVsZS5vbjsKCiAgICAgICAgICAvLyBJZiB0aGlzIG5vZGUgc2hhcmVkIGEgZGlzcGF0Y2ggd2l0aCB0aGUgcHJldmlvdXMgbm9kZSwKICAgICAgICAgIC8vIGp1c3QgYXNzaWduIHRoZSB1cGRhdGVkIHNoYXJlZCBkaXNwYXRjaCBhbmQgd2XigJlyZSBkb25lIQogICAgICAgICAgLy8gT3RoZXJ3aXNlLCBjb3B5LW9uLXdyaXRlLgogICAgICAgICAgaWYgKG9uICE9PSBvbjApIHsKICAgICAgICAgICAgb24xID0gKG9uMCA9IG9uKS5jb3B5KCk7CiAgICAgICAgICAgIG9uMS5fLmNhbmNlbC5wdXNoKGNhbmNlbCk7CiAgICAgICAgICAgIG9uMS5fLmludGVycnVwdC5wdXNoKGNhbmNlbCk7CiAgICAgICAgICAgIG9uMS5fLmVuZC5wdXNoKGVuZCk7CiAgICAgICAgICB9CgogICAgICAgICAgc2NoZWR1bGUub24gPSBvbjE7CiAgICAgICAgfSk7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBpZCQzID0gMDsKCiAgICBmdW5jdGlvbiBUcmFuc2l0aW9uJDMoZ3JvdXBzLCBwYXJlbnRzLCBuYW1lLCBpZCkgewogICAgICB0aGlzLl9ncm91cHMgPSBncm91cHM7CiAgICAgIHRoaXMuX3BhcmVudHMgPSBwYXJlbnRzOwogICAgICB0aGlzLl9uYW1lID0gbmFtZTsKICAgICAgdGhpcy5faWQgPSBpZDsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2l0aW9uJDMobmFtZSkgewogICAgICByZXR1cm4gc2VsZWN0aW9uJDUoKS50cmFuc2l0aW9uKG5hbWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5ld0lkJDMoKSB7CiAgICAgIHJldHVybiArK2lkJDM7CiAgICB9CgogICAgdmFyIHNlbGVjdGlvbl9wcm90b3R5cGUkMyA9IHNlbGVjdGlvbiQ1LnByb3RvdHlwZTsKCiAgICBUcmFuc2l0aW9uJDMucHJvdG90eXBlID0gdHJhbnNpdGlvbiQzLnByb3RvdHlwZSA9IHsKICAgICAgY29uc3RydWN0b3I6IFRyYW5zaXRpb24kMywKICAgICAgc2VsZWN0OiB0cmFuc2l0aW9uX3NlbGVjdCQzLAogICAgICBzZWxlY3RBbGw6IHRyYW5zaXRpb25fc2VsZWN0QWxsJDMsCiAgICAgIGZpbHRlcjogdHJhbnNpdGlvbl9maWx0ZXIkMywKICAgICAgbWVyZ2U6IHRyYW5zaXRpb25fbWVyZ2UkMywKICAgICAgc2VsZWN0aW9uOiB0cmFuc2l0aW9uX3NlbGVjdGlvbiQzLAogICAgICB0cmFuc2l0aW9uOiB0cmFuc2l0aW9uX3RyYW5zaXRpb24kMywKICAgICAgY2FsbDogc2VsZWN0aW9uX3Byb3RvdHlwZSQzLmNhbGwsCiAgICAgIG5vZGVzOiBzZWxlY3Rpb25fcHJvdG90eXBlJDMubm9kZXMsCiAgICAgIG5vZGU6IHNlbGVjdGlvbl9wcm90b3R5cGUkMy5ub2RlLAogICAgICBzaXplOiBzZWxlY3Rpb25fcHJvdG90eXBlJDMuc2l6ZSwKICAgICAgZW1wdHk6IHNlbGVjdGlvbl9wcm90b3R5cGUkMy5lbXB0eSwKICAgICAgZWFjaDogc2VsZWN0aW9uX3Byb3RvdHlwZSQzLmVhY2gsCiAgICAgIG9uOiB0cmFuc2l0aW9uX29uJDMsCiAgICAgIGF0dHI6IHRyYW5zaXRpb25fYXR0ciQzLAogICAgICBhdHRyVHdlZW46IHRyYW5zaXRpb25fYXR0clR3ZWVuJDMsCiAgICAgIHN0eWxlOiB0cmFuc2l0aW9uX3N0eWxlJDMsCiAgICAgIHN0eWxlVHdlZW46IHRyYW5zaXRpb25fc3R5bGVUd2VlbiQzLAogICAgICB0ZXh0OiB0cmFuc2l0aW9uX3RleHQkMywKICAgICAgdGV4dFR3ZWVuOiB0cmFuc2l0aW9uX3RleHRUd2VlbiQyLAogICAgICByZW1vdmU6IHRyYW5zaXRpb25fcmVtb3ZlJDMsCiAgICAgIHR3ZWVuOiB0cmFuc2l0aW9uX3R3ZWVuJDMsCiAgICAgIGRlbGF5OiB0cmFuc2l0aW9uX2RlbGF5JDMsCiAgICAgIGR1cmF0aW9uOiB0cmFuc2l0aW9uX2R1cmF0aW9uJDMsCiAgICAgIGVhc2U6IHRyYW5zaXRpb25fZWFzZSQzLAogICAgICBlbmQ6IHRyYW5zaXRpb25fZW5kJDIKICAgIH07CgogICAgdmFyIGRlZmF1bHRUaW1pbmckMyA9IHsKICAgICAgdGltZTogbnVsbCwgLy8gU2V0IG9uIHVzZS4KICAgICAgZGVsYXk6IDAsCiAgICAgIGR1cmF0aW9uOiAyNTAsCiAgICAgIGVhc2U6IGN1YmljSW5PdXQKICAgIH07CgogICAgZnVuY3Rpb24gaW5oZXJpdCQzKG5vZGUsIGlkKSB7CiAgICAgIHZhciB0aW1pbmc7CiAgICAgIHdoaWxlICghKHRpbWluZyA9IG5vZGUuX190cmFuc2l0aW9uKSB8fCAhKHRpbWluZyA9IHRpbWluZ1tpZF0pKSB7CiAgICAgICAgaWYgKCEobm9kZSA9IG5vZGUucGFyZW50Tm9kZSkpIHsKICAgICAgICAgIHJldHVybiBkZWZhdWx0VGltaW5nJDMudGltZSA9IG5vdyQ1KCksIGRlZmF1bHRUaW1pbmckMzsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHRpbWluZzsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fdHJhbnNpdGlvbiQzKG5hbWUpIHsKICAgICAgdmFyIGlkLAogICAgICAgICAgdGltaW5nOwoKICAgICAgaWYgKG5hbWUgaW5zdGFuY2VvZiBUcmFuc2l0aW9uJDMpIHsKICAgICAgICBpZCA9IG5hbWUuX2lkLCBuYW1lID0gbmFtZS5fbmFtZTsKICAgICAgfSBlbHNlIHsKICAgICAgICBpZCA9IG5ld0lkJDMoKSwgKHRpbWluZyA9IGRlZmF1bHRUaW1pbmckMykudGltZSA9IG5vdyQ1KCksIG5hbWUgPSBuYW1lID09IG51bGwgPyBudWxsIDogbmFtZSArICIiOwogICAgICB9CgogICAgICBmb3IgKHZhciBncm91cHMgPSB0aGlzLl9ncm91cHMsIG0gPSBncm91cHMubGVuZ3RoLCBqID0gMDsgaiA8IG07ICsraikgewogICAgICAgIGZvciAodmFyIGdyb3VwID0gZ3JvdXBzW2pdLCBuID0gZ3JvdXAubGVuZ3RoLCBub2RlLCBpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgaWYgKG5vZGUgPSBncm91cFtpXSkgewogICAgICAgICAgICBzY2hlZHVsZSQ0KG5vZGUsIG5hbWUsIGlkLCBpLCBncm91cCwgdGltaW5nIHx8IGluaGVyaXQkMyhub2RlLCBpZCkpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIG5ldyBUcmFuc2l0aW9uJDMoZ3JvdXBzLCB0aGlzLl9wYXJlbnRzLCBuYW1lLCBpZCk7CiAgICB9CgogICAgc2VsZWN0aW9uJDUucHJvdG90eXBlLmludGVycnVwdCA9IHNlbGVjdGlvbl9pbnRlcnJ1cHQkMzsKICAgIHNlbGVjdGlvbiQ1LnByb3RvdHlwZS50cmFuc2l0aW9uID0gc2VsZWN0aW9uX3RyYW5zaXRpb24kMzsKCiAgICBmdW5jdGlvbiBjb25zdGFudCR5KHgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB4OwogICAgICB9OwogICAgfQoKICAgIGZ1bmN0aW9uIFpvb21FdmVudCQxKHRhcmdldCwgdHlwZSwgdHJhbnNmb3JtKSB7CiAgICAgIHRoaXMudGFyZ2V0ID0gdGFyZ2V0OwogICAgICB0aGlzLnR5cGUgPSB0eXBlOwogICAgICB0aGlzLnRyYW5zZm9ybSA9IHRyYW5zZm9ybTsKICAgIH0KCiAgICBmdW5jdGlvbiBUcmFuc2Zvcm0kMShrLCB4LCB5KSB7CiAgICAgIHRoaXMuayA9IGs7CiAgICAgIHRoaXMueCA9IHg7CiAgICAgIHRoaXMueSA9IHk7CiAgICB9CgogICAgVHJhbnNmb3JtJDEucHJvdG90eXBlID0gewogICAgICBjb25zdHJ1Y3RvcjogVHJhbnNmb3JtJDEsCiAgICAgIHNjYWxlOiBmdW5jdGlvbihrKSB7CiAgICAgICAgcmV0dXJuIGsgPT09IDEgPyB0aGlzIDogbmV3IFRyYW5zZm9ybSQxKHRoaXMuayAqIGssIHRoaXMueCwgdGhpcy55KTsKICAgICAgfSwKICAgICAgdHJhbnNsYXRlOiBmdW5jdGlvbih4LCB5KSB7CiAgICAgICAgcmV0dXJuIHggPT09IDAgJiB5ID09PSAwID8gdGhpcyA6IG5ldyBUcmFuc2Zvcm0kMSh0aGlzLmssIHRoaXMueCArIHRoaXMuayAqIHgsIHRoaXMueSArIHRoaXMuayAqIHkpOwogICAgICB9LAogICAgICBhcHBseTogZnVuY3Rpb24ocG9pbnQpIHsKICAgICAgICByZXR1cm4gW3BvaW50WzBdICogdGhpcy5rICsgdGhpcy54LCBwb2ludFsxXSAqIHRoaXMuayArIHRoaXMueV07CiAgICAgIH0sCiAgICAgIGFwcGx5WDogZnVuY3Rpb24oeCkgewogICAgICAgIHJldHVybiB4ICogdGhpcy5rICsgdGhpcy54OwogICAgICB9LAogICAgICBhcHBseVk6IGZ1bmN0aW9uKHkpIHsKICAgICAgICByZXR1cm4geSAqIHRoaXMuayArIHRoaXMueTsKICAgICAgfSwKICAgICAgaW52ZXJ0OiBmdW5jdGlvbihsb2NhdGlvbikgewogICAgICAgIHJldHVybiBbKGxvY2F0aW9uWzBdIC0gdGhpcy54KSAvIHRoaXMuaywgKGxvY2F0aW9uWzFdIC0gdGhpcy55KSAvIHRoaXMua107CiAgICAgIH0sCiAgICAgIGludmVydFg6IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4gKHggLSB0aGlzLngpIC8gdGhpcy5rOwogICAgICB9LAogICAgICBpbnZlcnRZOiBmdW5jdGlvbih5KSB7CiAgICAgICAgcmV0dXJuICh5IC0gdGhpcy55KSAvIHRoaXMuazsKICAgICAgfSwKICAgICAgcmVzY2FsZVg6IGZ1bmN0aW9uKHgpIHsKICAgICAgICByZXR1cm4geC5jb3B5KCkuZG9tYWluKHgucmFuZ2UoKS5tYXAodGhpcy5pbnZlcnRYLCB0aGlzKS5tYXAoeC5pbnZlcnQsIHgpKTsKICAgICAgfSwKICAgICAgcmVzY2FsZVk6IGZ1bmN0aW9uKHkpIHsKICAgICAgICByZXR1cm4geS5jb3B5KCkuZG9tYWluKHkucmFuZ2UoKS5tYXAodGhpcy5pbnZlcnRZLCB0aGlzKS5tYXAoeS5pbnZlcnQsIHkpKTsKICAgICAgfSwKICAgICAgdG9TdHJpbmc6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiAidHJhbnNsYXRlKCIgKyB0aGlzLnggKyAiLCIgKyB0aGlzLnkgKyAiKSBzY2FsZSgiICsgdGhpcy5rICsgIikiOwogICAgICB9CiAgICB9OwoKICAgIHZhciBpZGVudGl0eSRtID0gbmV3IFRyYW5zZm9ybSQxKDEsIDAsIDApOwoKICAgIHRyYW5zZm9ybSQzLnByb3RvdHlwZSA9IFRyYW5zZm9ybSQxLnByb3RvdHlwZTsKCiAgICBmdW5jdGlvbiB0cmFuc2Zvcm0kMyhub2RlKSB7CiAgICAgIHJldHVybiBub2RlLl9fem9vbSB8fCBpZGVudGl0eSRtOwogICAgfQoKICAgIGZ1bmN0aW9uIG5vcHJvcGFnYXRpb24kNSgpIHsKICAgICAgZXZlbnQkNC5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTsKICAgIH0KCiAgICBmdW5jdGlvbiBub2V2ZW50JDcoKSB7CiAgICAgIGV2ZW50JDQucHJldmVudERlZmF1bHQoKTsKICAgICAgZXZlbnQkNC5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTsKICAgIH0KCiAgICAvLyBJZ25vcmUgcmlnaHQtY2xpY2ssIHNpbmNlIHRoYXQgc2hvdWxkIG9wZW4gdGhlIGNvbnRleHQgbWVudS4KICAgIGZ1bmN0aW9uIGRlZmF1bHRGaWx0ZXIkNSgpIHsKICAgICAgcmV0dXJuICFldmVudCQ0LmJ1dHRvbjsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0RXh0ZW50JDMoKSB7CiAgICAgIHZhciBlID0gdGhpcywgdywgaDsKICAgICAgaWYgKGUgaW5zdGFuY2VvZiBTVkdFbGVtZW50KSB7CiAgICAgICAgZSA9IGUub3duZXJTVkdFbGVtZW50IHx8IGU7CiAgICAgICAgdyA9IGUud2lkdGguYmFzZVZhbC52YWx1ZTsKICAgICAgICBoID0gZS5oZWlnaHQuYmFzZVZhbC52YWx1ZTsKICAgICAgfSBlbHNlIHsKICAgICAgICB3ID0gZS5jbGllbnRXaWR0aDsKICAgICAgICBoID0gZS5jbGllbnRIZWlnaHQ7CiAgICAgIH0KICAgICAgcmV0dXJuIFtbMCwgMF0sIFt3LCBoXV07CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFRyYW5zZm9ybSQxKCkgewogICAgICByZXR1cm4gdGhpcy5fX3pvb20gfHwgaWRlbnRpdHkkbTsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0V2hlZWxEZWx0YSQxKCkgewogICAgICByZXR1cm4gLWV2ZW50JDQuZGVsdGFZICogKGV2ZW50JDQuZGVsdGFNb2RlID8gMTIwIDogMSkgLyA1MDA7CiAgICB9CgogICAgZnVuY3Rpb24gZGVmYXVsdFRvdWNoYWJsZSQ0KCkgewogICAgICByZXR1cm4gIm9udG91Y2hzdGFydCIgaW4gdGhpczsKICAgIH0KCiAgICBmdW5jdGlvbiBkZWZhdWx0Q29uc3RyYWluJDEodHJhbnNmb3JtLCBleHRlbnQsIHRyYW5zbGF0ZUV4dGVudCkgewogICAgICB2YXIgZHgwID0gdHJhbnNmb3JtLmludmVydFgoZXh0ZW50WzBdWzBdKSAtIHRyYW5zbGF0ZUV4dGVudFswXVswXSwKICAgICAgICAgIGR4MSA9IHRyYW5zZm9ybS5pbnZlcnRYKGV4dGVudFsxXVswXSkgLSB0cmFuc2xhdGVFeHRlbnRbMV1bMF0sCiAgICAgICAgICBkeTAgPSB0cmFuc2Zvcm0uaW52ZXJ0WShleHRlbnRbMF1bMV0pIC0gdHJhbnNsYXRlRXh0ZW50WzBdWzFdLAogICAgICAgICAgZHkxID0gdHJhbnNmb3JtLmludmVydFkoZXh0ZW50WzFdWzFdKSAtIHRyYW5zbGF0ZUV4dGVudFsxXVsxXTsKICAgICAgcmV0dXJuIHRyYW5zZm9ybS50cmFuc2xhdGUoCiAgICAgICAgZHgxID4gZHgwID8gKGR4MCArIGR4MSkgLyAyIDogTWF0aC5taW4oMCwgZHgwKSB8fCBNYXRoLm1heCgwLCBkeDEpLAogICAgICAgIGR5MSA+IGR5MCA/IChkeTAgKyBkeTEpIC8gMiA6IE1hdGgubWluKDAsIGR5MCkgfHwgTWF0aC5tYXgoMCwgZHkxKQogICAgICApOwogICAgfQoKICAgIGZ1bmN0aW9uIHpvb20kMigpIHsKICAgICAgdmFyIGZpbHRlciA9IGRlZmF1bHRGaWx0ZXIkNSwKICAgICAgICAgIGV4dGVudCA9IGRlZmF1bHRFeHRlbnQkMywKICAgICAgICAgIGNvbnN0cmFpbiA9IGRlZmF1bHRDb25zdHJhaW4kMSwKICAgICAgICAgIHdoZWVsRGVsdGEgPSBkZWZhdWx0V2hlZWxEZWx0YSQxLAogICAgICAgICAgdG91Y2hhYmxlID0gZGVmYXVsdFRvdWNoYWJsZSQ0LAogICAgICAgICAgc2NhbGVFeHRlbnQgPSBbMCwgSW5maW5pdHldLAogICAgICAgICAgdHJhbnNsYXRlRXh0ZW50ID0gW1stSW5maW5pdHksIC1JbmZpbml0eV0sIFtJbmZpbml0eSwgSW5maW5pdHldXSwKICAgICAgICAgIGR1cmF0aW9uID0gMjUwLAogICAgICAgICAgaW50ZXJwb2xhdGUgPSBpbnRlcnBvbGF0ZVpvb20kMSwKICAgICAgICAgIGdlc3R1cmVzID0gW10sCiAgICAgICAgICBsaXN0ZW5lcnMgPSBkaXNwYXRjaCQ2KCJzdGFydCIsICJ6b29tIiwgImVuZCIpLAogICAgICAgICAgdG91Y2hzdGFydGluZywKICAgICAgICAgIHRvdWNoZW5kaW5nLAogICAgICAgICAgdG91Y2hEZWxheSA9IDUwMCwKICAgICAgICAgIHdoZWVsRGVsYXkgPSAxNTAsCiAgICAgICAgICBjbGlja0Rpc3RhbmNlMiA9IDA7CgogICAgICBmdW5jdGlvbiB6b29tKHNlbGVjdGlvbikgewogICAgICAgIHNlbGVjdGlvbgogICAgICAgICAgICAucHJvcGVydHkoIl9fem9vbSIsIGRlZmF1bHRUcmFuc2Zvcm0kMSkKICAgICAgICAgICAgLm9uKCJ3aGVlbC56b29tIiwgd2hlZWxlZCkKICAgICAgICAgICAgLm9uKCJtb3VzZWRvd24uem9vbSIsIG1vdXNlZG93bmVkKQogICAgICAgICAgICAub24oImRibGNsaWNrLnpvb20iLCBkYmxjbGlja2VkKQogICAgICAgICAgLmZpbHRlcih0b3VjaGFibGUpCiAgICAgICAgICAgIC5vbigidG91Y2hzdGFydC56b29tIiwgdG91Y2hzdGFydGVkKQogICAgICAgICAgICAub24oInRvdWNobW92ZS56b29tIiwgdG91Y2htb3ZlZCkKICAgICAgICAgICAgLm9uKCJ0b3VjaGVuZC56b29tIHRvdWNoY2FuY2VsLnpvb20iLCB0b3VjaGVuZGVkKQogICAgICAgICAgICAuc3R5bGUoInRvdWNoLWFjdGlvbiIsICJub25lIikKICAgICAgICAgICAgLnN0eWxlKCItd2Via2l0LXRhcC1oaWdobGlnaHQtY29sb3IiLCAicmdiYSgwLDAsMCwwKSIpOwogICAgICB9CgogICAgICB6b29tLnRyYW5zZm9ybSA9IGZ1bmN0aW9uKGNvbGxlY3Rpb24sIHRyYW5zZm9ybSkgewogICAgICAgIHZhciBzZWxlY3Rpb24gPSBjb2xsZWN0aW9uLnNlbGVjdGlvbiA/IGNvbGxlY3Rpb24uc2VsZWN0aW9uKCkgOiBjb2xsZWN0aW9uOwogICAgICAgIHNlbGVjdGlvbi5wcm9wZXJ0eSgiX196b29tIiwgZGVmYXVsdFRyYW5zZm9ybSQxKTsKICAgICAgICBpZiAoY29sbGVjdGlvbiAhPT0gc2VsZWN0aW9uKSB7CiAgICAgICAgICBzY2hlZHVsZShjb2xsZWN0aW9uLCB0cmFuc2Zvcm0pOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBzZWxlY3Rpb24uaW50ZXJydXB0KCkuZWFjaChmdW5jdGlvbigpIHsKICAgICAgICAgICAgZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpCiAgICAgICAgICAgICAgICAuc3RhcnQoKQogICAgICAgICAgICAgICAgLnpvb20obnVsbCwgdHlwZW9mIHRyYW5zZm9ybSA9PT0gImZ1bmN0aW9uIiA/IHRyYW5zZm9ybS5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogdHJhbnNmb3JtKQogICAgICAgICAgICAgICAgLmVuZCgpOwogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9OwoKICAgICAgem9vbS5zY2FsZUJ5ID0gZnVuY3Rpb24oc2VsZWN0aW9uLCBrKSB7CiAgICAgICAgem9vbS5zY2FsZVRvKHNlbGVjdGlvbiwgZnVuY3Rpb24oKSB7CiAgICAgICAgICB2YXIgazAgPSB0aGlzLl9fem9vbS5rLAogICAgICAgICAgICAgIGsxID0gdHlwZW9mIGsgPT09ICJmdW5jdGlvbiIgPyBrLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiBrOwogICAgICAgICAgcmV0dXJuIGswICogazE7CiAgICAgICAgfSk7CiAgICAgIH07CgogICAgICB6b29tLnNjYWxlVG8gPSBmdW5jdGlvbihzZWxlY3Rpb24sIGspIHsKICAgICAgICB6b29tLnRyYW5zZm9ybShzZWxlY3Rpb24sIGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIGUgPSBleHRlbnQuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgICB0MCA9IHRoaXMuX196b29tLAogICAgICAgICAgICAgIHAwID0gY2VudHJvaWQoZSksCiAgICAgICAgICAgICAgcDEgPSB0MC5pbnZlcnQocDApLAogICAgICAgICAgICAgIGsxID0gdHlwZW9mIGsgPT09ICJmdW5jdGlvbiIgPyBrLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiBrOwogICAgICAgICAgcmV0dXJuIGNvbnN0cmFpbih0cmFuc2xhdGUoc2NhbGUodDAsIGsxKSwgcDAsIHAxKSwgZSwgdHJhbnNsYXRlRXh0ZW50KTsKICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIHpvb20udHJhbnNsYXRlQnkgPSBmdW5jdGlvbihzZWxlY3Rpb24sIHgsIHkpIHsKICAgICAgICB6b29tLnRyYW5zZm9ybShzZWxlY3Rpb24sIGZ1bmN0aW9uKCkgewogICAgICAgICAgcmV0dXJuIGNvbnN0cmFpbih0aGlzLl9fem9vbS50cmFuc2xhdGUoCiAgICAgICAgICAgIHR5cGVvZiB4ID09PSAiZnVuY3Rpb24iID8geC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogeCwKICAgICAgICAgICAgdHlwZW9mIHkgPT09ICJmdW5jdGlvbiIgPyB5LmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgOiB5CiAgICAgICAgICApLCBleHRlbnQuYXBwbHkodGhpcywgYXJndW1lbnRzKSwgdHJhbnNsYXRlRXh0ZW50KTsKICAgICAgICB9KTsKICAgICAgfTsKCiAgICAgIHpvb20udHJhbnNsYXRlVG8gPSBmdW5jdGlvbihzZWxlY3Rpb24sIHgsIHkpIHsKICAgICAgICB6b29tLnRyYW5zZm9ybShzZWxlY3Rpb24sIGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIGUgPSBleHRlbnQuYXBwbHkodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgICB0ID0gdGhpcy5fX3pvb20sCiAgICAgICAgICAgICAgcCA9IGNlbnRyb2lkKGUpOwogICAgICAgICAgcmV0dXJuIGNvbnN0cmFpbihpZGVudGl0eSRtLnRyYW5zbGF0ZShwWzBdLCBwWzFdKS5zY2FsZSh0LmspLnRyYW5zbGF0ZSgKICAgICAgICAgICAgdHlwZW9mIHggPT09ICJmdW5jdGlvbiIgPyAteC5hcHBseSh0aGlzLCBhcmd1bWVudHMpIDogLXgsCiAgICAgICAgICAgIHR5cGVvZiB5ID09PSAiZnVuY3Rpb24iID8gLXkuYXBwbHkodGhpcywgYXJndW1lbnRzKSA6IC15CiAgICAgICAgICApLCBlLCB0cmFuc2xhdGVFeHRlbnQpOwogICAgICAgIH0pOwogICAgICB9OwoKICAgICAgZnVuY3Rpb24gc2NhbGUodHJhbnNmb3JtLCBrKSB7CiAgICAgICAgayA9IE1hdGgubWF4KHNjYWxlRXh0ZW50WzBdLCBNYXRoLm1pbihzY2FsZUV4dGVudFsxXSwgaykpOwogICAgICAgIHJldHVybiBrID09PSB0cmFuc2Zvcm0uayA/IHRyYW5zZm9ybSA6IG5ldyBUcmFuc2Zvcm0kMShrLCB0cmFuc2Zvcm0ueCwgdHJhbnNmb3JtLnkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0cmFuc2xhdGUodHJhbnNmb3JtLCBwMCwgcDEpIHsKICAgICAgICB2YXIgeCA9IHAwWzBdIC0gcDFbMF0gKiB0cmFuc2Zvcm0uaywgeSA9IHAwWzFdIC0gcDFbMV0gKiB0cmFuc2Zvcm0uazsKICAgICAgICByZXR1cm4geCA9PT0gdHJhbnNmb3JtLnggJiYgeSA9PT0gdHJhbnNmb3JtLnkgPyB0cmFuc2Zvcm0gOiBuZXcgVHJhbnNmb3JtJDEodHJhbnNmb3JtLmssIHgsIHkpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBjZW50cm9pZChleHRlbnQpIHsKICAgICAgICByZXR1cm4gWygrZXh0ZW50WzBdWzBdICsgK2V4dGVudFsxXVswXSkgLyAyLCAoK2V4dGVudFswXVsxXSArICtleHRlbnRbMV1bMV0pIC8gMl07CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHNjaGVkdWxlKHRyYW5zaXRpb24sIHRyYW5zZm9ybSwgY2VudGVyKSB7CiAgICAgICAgdHJhbnNpdGlvbgogICAgICAgICAgICAub24oInN0YXJ0Lnpvb20iLCBmdW5jdGlvbigpIHsgZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpLnN0YXJ0KCk7IH0pCiAgICAgICAgICAgIC5vbigiaW50ZXJydXB0Lnpvb20gZW5kLnpvb20iLCBmdW5jdGlvbigpIHsgZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpLmVuZCgpOyB9KQogICAgICAgICAgICAudHdlZW4oInpvb20iLCBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICB2YXIgdGhhdCA9IHRoaXMsCiAgICAgICAgICAgICAgICAgIGFyZ3MgPSBhcmd1bWVudHMsCiAgICAgICAgICAgICAgICAgIGcgPSBnZXN0dXJlKHRoYXQsIGFyZ3MpLAogICAgICAgICAgICAgICAgICBlID0gZXh0ZW50LmFwcGx5KHRoYXQsIGFyZ3MpLAogICAgICAgICAgICAgICAgICBwID0gY2VudGVyIHx8IGNlbnRyb2lkKGUpLAogICAgICAgICAgICAgICAgICB3ID0gTWF0aC5tYXgoZVsxXVswXSAtIGVbMF1bMF0sIGVbMV1bMV0gLSBlWzBdWzFdKSwKICAgICAgICAgICAgICAgICAgYSA9IHRoYXQuX196b29tLAogICAgICAgICAgICAgICAgICBiID0gdHlwZW9mIHRyYW5zZm9ybSA9PT0gImZ1bmN0aW9uIiA/IHRyYW5zZm9ybS5hcHBseSh0aGF0LCBhcmdzKSA6IHRyYW5zZm9ybSwKICAgICAgICAgICAgICAgICAgaSA9IGludGVycG9sYXRlKGEuaW52ZXJ0KHApLmNvbmNhdCh3IC8gYS5rKSwgYi5pbnZlcnQocCkuY29uY2F0KHcgLyBiLmspKTsKICAgICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24odCkgewogICAgICAgICAgICAgICAgaWYgKHQgPT09IDEpIHQgPSBiOyAvLyBBdm9pZCByb3VuZGluZyBlcnJvciBvbiBlbmQuCiAgICAgICAgICAgICAgICBlbHNlIHsgdmFyIGwgPSBpKHQpLCBrID0gdyAvIGxbMl07IHQgPSBuZXcgVHJhbnNmb3JtJDEoaywgcFswXSAtIGxbMF0gKiBrLCBwWzFdIC0gbFsxXSAqIGspOyB9CiAgICAgICAgICAgICAgICBnLnpvb20obnVsbCwgdCk7CiAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIGdlc3R1cmUodGhhdCwgYXJncykgewogICAgICAgIGZvciAodmFyIGkgPSAwLCBuID0gZ2VzdHVyZXMubGVuZ3RoLCBnOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICBpZiAoKGcgPSBnZXN0dXJlc1tpXSkudGhhdCA9PT0gdGhhdCkgewogICAgICAgICAgICByZXR1cm4gZzsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIG5ldyBHZXN0dXJlKHRoYXQsIGFyZ3MpOwogICAgICB9CgogICAgICBmdW5jdGlvbiBHZXN0dXJlKHRoYXQsIGFyZ3MpIHsKICAgICAgICB0aGlzLnRoYXQgPSB0aGF0OwogICAgICAgIHRoaXMuYXJncyA9IGFyZ3M7CiAgICAgICAgdGhpcy5pbmRleCA9IC0xOwogICAgICAgIHRoaXMuYWN0aXZlID0gMDsKICAgICAgICB0aGlzLmV4dGVudCA9IGV4dGVudC5hcHBseSh0aGF0LCBhcmdzKTsKICAgICAgfQoKICAgICAgR2VzdHVyZS5wcm90b3R5cGUgPSB7CiAgICAgICAgc3RhcnQ6IGZ1bmN0aW9uKCkgewogICAgICAgICAgaWYgKCsrdGhpcy5hY3RpdmUgPT09IDEpIHsKICAgICAgICAgICAgdGhpcy5pbmRleCA9IGdlc3R1cmVzLnB1c2godGhpcykgLSAxOwogICAgICAgICAgICB0aGlzLmVtaXQoInN0YXJ0Iik7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIHpvb206IGZ1bmN0aW9uKGtleSwgdHJhbnNmb3JtKSB7CiAgICAgICAgICBpZiAodGhpcy5tb3VzZSAmJiBrZXkgIT09ICJtb3VzZSIpIHRoaXMubW91c2VbMV0gPSB0cmFuc2Zvcm0uaW52ZXJ0KHRoaXMubW91c2VbMF0pOwogICAgICAgICAgaWYgKHRoaXMudG91Y2gwICYmIGtleSAhPT0gInRvdWNoIikgdGhpcy50b3VjaDBbMV0gPSB0cmFuc2Zvcm0uaW52ZXJ0KHRoaXMudG91Y2gwWzBdKTsKICAgICAgICAgIGlmICh0aGlzLnRvdWNoMSAmJiBrZXkgIT09ICJ0b3VjaCIpIHRoaXMudG91Y2gxWzFdID0gdHJhbnNmb3JtLmludmVydCh0aGlzLnRvdWNoMVswXSk7CiAgICAgICAgICB0aGlzLnRoYXQuX196b29tID0gdHJhbnNmb3JtOwogICAgICAgICAgdGhpcy5lbWl0KCJ6b29tIik7CiAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9LAogICAgICAgIGVuZDogZnVuY3Rpb24oKSB7CiAgICAgICAgICBpZiAoLS10aGlzLmFjdGl2ZSA9PT0gMCkgewogICAgICAgICAgICBnZXN0dXJlcy5zcGxpY2UodGhpcy5pbmRleCwgMSk7CiAgICAgICAgICAgIHRoaXMuaW5kZXggPSAtMTsKICAgICAgICAgICAgdGhpcy5lbWl0KCJlbmQiKTsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0sCiAgICAgICAgZW1pdDogZnVuY3Rpb24odHlwZSkgewogICAgICAgICAgY3VzdG9tRXZlbnQkNChuZXcgWm9vbUV2ZW50JDEoem9vbSwgdHlwZSwgdGhpcy50aGF0Ll9fem9vbSksIGxpc3RlbmVycy5hcHBseSwgbGlzdGVuZXJzLCBbdHlwZSwgdGhpcy50aGF0LCB0aGlzLmFyZ3NdKTsKICAgICAgICB9CiAgICAgIH07CgogICAgICBmdW5jdGlvbiB3aGVlbGVkKCkgewogICAgICAgIGlmICghZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgdCA9IHRoaXMuX196b29tLAogICAgICAgICAgICBrID0gTWF0aC5tYXgoc2NhbGVFeHRlbnRbMF0sIE1hdGgubWluKHNjYWxlRXh0ZW50WzFdLCB0LmsgKiBNYXRoLnBvdygyLCB3aGVlbERlbHRhLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpKSksCiAgICAgICAgICAgIHAgPSBtb3VzZSQ0KHRoaXMpOwoKICAgICAgICAvLyBJZiB0aGUgbW91c2UgaXMgaW4gdGhlIHNhbWUgbG9jYXRpb24gYXMgYmVmb3JlLCByZXVzZSBpdC4KICAgICAgICAvLyBJZiB0aGVyZSB3ZXJlIHJlY2VudCB3aGVlbCBldmVudHMsIHJlc2V0IHRoZSB3aGVlbCBpZGxlIHRpbWVvdXQuCiAgICAgICAgaWYgKGcud2hlZWwpIHsKICAgICAgICAgIGlmIChnLm1vdXNlWzBdWzBdICE9PSBwWzBdIHx8IGcubW91c2VbMF1bMV0gIT09IHBbMV0pIHsKICAgICAgICAgICAgZy5tb3VzZVsxXSA9IHQuaW52ZXJ0KGcubW91c2VbMF0gPSBwKTsKICAgICAgICAgIH0KICAgICAgICAgIGNsZWFyVGltZW91dChnLndoZWVsKTsKICAgICAgICB9CgogICAgICAgIC8vIElmIHRoaXMgd2hlZWwgZXZlbnQgd29u4oCZdCB0cmlnZ2VyIGEgdHJhbnNmb3JtIGNoYW5nZSwgaWdub3JlIGl0LgogICAgICAgIGVsc2UgaWYgKHQuayA9PT0gaykgcmV0dXJuOwoKICAgICAgICAvLyBPdGhlcndpc2UsIGNhcHR1cmUgdGhlIG1vdXNlIHBvaW50IGFuZCBsb2NhdGlvbiBhdCB0aGUgc3RhcnQuCiAgICAgICAgZWxzZSB7CiAgICAgICAgICBnLm1vdXNlID0gW3AsIHQuaW52ZXJ0KHApXTsKICAgICAgICAgIGludGVycnVwdCQzKHRoaXMpOwogICAgICAgICAgZy5zdGFydCgpOwogICAgICAgIH0KCiAgICAgICAgbm9ldmVudCQ3KCk7CiAgICAgICAgZy53aGVlbCA9IHNldFRpbWVvdXQod2hlZWxpZGxlZCwgd2hlZWxEZWxheSk7CiAgICAgICAgZy56b29tKCJtb3VzZSIsIGNvbnN0cmFpbih0cmFuc2xhdGUoc2NhbGUodCwgayksIGcubW91c2VbMF0sIGcubW91c2VbMV0pLCBnLmV4dGVudCwgdHJhbnNsYXRlRXh0ZW50KSk7CgogICAgICAgIGZ1bmN0aW9uIHdoZWVsaWRsZWQoKSB7CiAgICAgICAgICBnLndoZWVsID0gbnVsbDsKICAgICAgICAgIGcuZW5kKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBtb3VzZWRvd25lZCgpIHsKICAgICAgICBpZiAodG91Y2hlbmRpbmcgfHwgIWZpbHRlci5hcHBseSh0aGlzLCBhcmd1bWVudHMpKSByZXR1cm47CiAgICAgICAgdmFyIGcgPSBnZXN0dXJlKHRoaXMsIGFyZ3VtZW50cyksCiAgICAgICAgICAgIHYgPSBzZWxlY3QkNChldmVudCQ0LnZpZXcpLm9uKCJtb3VzZW1vdmUuem9vbSIsIG1vdXNlbW92ZWQsIHRydWUpLm9uKCJtb3VzZXVwLnpvb20iLCBtb3VzZXVwcGVkLCB0cnVlKSwKICAgICAgICAgICAgcCA9IG1vdXNlJDQodGhpcyksCiAgICAgICAgICAgIHgwID0gZXZlbnQkNC5jbGllbnRYLAogICAgICAgICAgICB5MCA9IGV2ZW50JDQuY2xpZW50WTsKCiAgICAgICAgZHJhZ0Rpc2FibGUkMihldmVudCQ0LnZpZXcpOwogICAgICAgIG5vcHJvcGFnYXRpb24kNSgpOwogICAgICAgIGcubW91c2UgPSBbcCwgdGhpcy5fX3pvb20uaW52ZXJ0KHApXTsKICAgICAgICBpbnRlcnJ1cHQkMyh0aGlzKTsKICAgICAgICBnLnN0YXJ0KCk7CgogICAgICAgIGZ1bmN0aW9uIG1vdXNlbW92ZWQoKSB7CiAgICAgICAgICBub2V2ZW50JDcoKTsKICAgICAgICAgIGlmICghZy5tb3ZlZCkgewogICAgICAgICAgICB2YXIgZHggPSBldmVudCQ0LmNsaWVudFggLSB4MCwgZHkgPSBldmVudCQ0LmNsaWVudFkgLSB5MDsKICAgICAgICAgICAgZy5tb3ZlZCA9IGR4ICogZHggKyBkeSAqIGR5ID4gY2xpY2tEaXN0YW5jZTI7CiAgICAgICAgICB9CiAgICAgICAgICBnLnpvb20oIm1vdXNlIiwgY29uc3RyYWluKHRyYW5zbGF0ZShnLnRoYXQuX196b29tLCBnLm1vdXNlWzBdID0gbW91c2UkNChnLnRoYXQpLCBnLm1vdXNlWzFdKSwgZy5leHRlbnQsIHRyYW5zbGF0ZUV4dGVudCkpOwogICAgICAgIH0KCiAgICAgICAgZnVuY3Rpb24gbW91c2V1cHBlZCgpIHsKICAgICAgICAgIHYub24oIm1vdXNlbW92ZS56b29tIG1vdXNldXAuem9vbSIsIG51bGwpOwogICAgICAgICAgeWVzZHJhZyQzKGV2ZW50JDQudmlldywgZy5tb3ZlZCk7CiAgICAgICAgICBub2V2ZW50JDcoKTsKICAgICAgICAgIGcuZW5kKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBmdW5jdGlvbiBkYmxjbGlja2VkKCkgewogICAgICAgIGlmICghZmlsdGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykpIHJldHVybjsKICAgICAgICB2YXIgdDAgPSB0aGlzLl9fem9vbSwKICAgICAgICAgICAgcDAgPSBtb3VzZSQ0KHRoaXMpLAogICAgICAgICAgICBwMSA9IHQwLmludmVydChwMCksCiAgICAgICAgICAgIGsxID0gdDAuayAqIChldmVudCQ0LnNoaWZ0S2V5ID8gMC41IDogMiksCiAgICAgICAgICAgIHQxID0gY29uc3RyYWluKHRyYW5zbGF0ZShzY2FsZSh0MCwgazEpLCBwMCwgcDEpLCBleHRlbnQuYXBwbHkodGhpcywgYXJndW1lbnRzKSwgdHJhbnNsYXRlRXh0ZW50KTsKCiAgICAgICAgbm9ldmVudCQ3KCk7CiAgICAgICAgaWYgKGR1cmF0aW9uID4gMCkgc2VsZWN0JDQodGhpcykudHJhbnNpdGlvbigpLmR1cmF0aW9uKGR1cmF0aW9uKS5jYWxsKHNjaGVkdWxlLCB0MSwgcDApOwogICAgICAgIGVsc2Ugc2VsZWN0JDQodGhpcykuY2FsbCh6b29tLnRyYW5zZm9ybSwgdDEpOwogICAgICB9CgogICAgICBmdW5jdGlvbiB0b3VjaHN0YXJ0ZWQoKSB7CiAgICAgICAgaWYgKCFmaWx0ZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSkgcmV0dXJuOwogICAgICAgIHZhciBnID0gZ2VzdHVyZSh0aGlzLCBhcmd1bWVudHMpLAogICAgICAgICAgICB0b3VjaGVzID0gZXZlbnQkNC5jaGFuZ2VkVG91Y2hlcywKICAgICAgICAgICAgc3RhcnRlZCwKICAgICAgICAgICAgbiA9IHRvdWNoZXMubGVuZ3RoLCBpLCB0LCBwOwoKICAgICAgICBub3Byb3BhZ2F0aW9uJDUoKTsKICAgICAgICBmb3IgKGkgPSAwOyBpIDwgbjsgKytpKSB7CiAgICAgICAgICB0ID0gdG91Y2hlc1tpXSwgcCA9IHRvdWNoJDModGhpcywgdG91Y2hlcywgdC5pZGVudGlmaWVyKTsKICAgICAgICAgIHAgPSBbcCwgdGhpcy5fX3pvb20uaW52ZXJ0KHApLCB0LmlkZW50aWZpZXJdOwogICAgICAgICAgaWYgKCFnLnRvdWNoMCkgZy50b3VjaDAgPSBwLCBzdGFydGVkID0gdHJ1ZTsKICAgICAgICAgIGVsc2UgaWYgKCFnLnRvdWNoMSkgZy50b3VjaDEgPSBwOwogICAgICAgIH0KCiAgICAgICAgLy8gSWYgdGhpcyBpcyBhIGRibHRhcCwgcmVyb3V0ZSB0byB0aGUgKG9wdGlvbmFsKSBkYmxjbGljay56b29tIGhhbmRsZXIuCiAgICAgICAgaWYgKHRvdWNoc3RhcnRpbmcpIHsKICAgICAgICAgIHRvdWNoc3RhcnRpbmcgPSBjbGVhclRpbWVvdXQodG91Y2hzdGFydGluZyk7CiAgICAgICAgICBpZiAoIWcudG91Y2gxKSB7CiAgICAgICAgICAgIGcuZW5kKCk7CiAgICAgICAgICAgIHAgPSBzZWxlY3QkNCh0aGlzKS5vbigiZGJsY2xpY2suem9vbSIpOwogICAgICAgICAgICBpZiAocCkgcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAoc3RhcnRlZCkgewogICAgICAgICAgdG91Y2hzdGFydGluZyA9IHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHRvdWNoc3RhcnRpbmcgPSBudWxsOyB9LCB0b3VjaERlbGF5KTsKICAgICAgICAgIGludGVycnVwdCQzKHRoaXMpOwogICAgICAgICAgZy5zdGFydCgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZnVuY3Rpb24gdG91Y2htb3ZlZCgpIHsKICAgICAgICB2YXIgZyA9IGdlc3R1cmUodGhpcywgYXJndW1lbnRzKSwKICAgICAgICAgICAgdG91Y2hlcyA9IGV2ZW50JDQuY2hhbmdlZFRvdWNoZXMsCiAgICAgICAgICAgIG4gPSB0b3VjaGVzLmxlbmd0aCwgaSwgdCwgcCwgbDsKCiAgICAgICAgbm9ldmVudCQ3KCk7CiAgICAgICAgaWYgKHRvdWNoc3RhcnRpbmcpIHRvdWNoc3RhcnRpbmcgPSBjbGVhclRpbWVvdXQodG91Y2hzdGFydGluZyk7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdCA9IHRvdWNoZXNbaV0sIHAgPSB0b3VjaCQzKHRoaXMsIHRvdWNoZXMsIHQuaWRlbnRpZmllcik7CiAgICAgICAgICBpZiAoZy50b3VjaDAgJiYgZy50b3VjaDBbMl0gPT09IHQuaWRlbnRpZmllcikgZy50b3VjaDBbMF0gPSBwOwogICAgICAgICAgZWxzZSBpZiAoZy50b3VjaDEgJiYgZy50b3VjaDFbMl0gPT09IHQuaWRlbnRpZmllcikgZy50b3VjaDFbMF0gPSBwOwogICAgICAgIH0KICAgICAgICB0ID0gZy50aGF0Ll9fem9vbTsKICAgICAgICBpZiAoZy50b3VjaDEpIHsKICAgICAgICAgIHZhciBwMCA9IGcudG91Y2gwWzBdLCBsMCA9IGcudG91Y2gwWzFdLAogICAgICAgICAgICAgIHAxID0gZy50b3VjaDFbMF0sIGwxID0gZy50b3VjaDFbMV0sCiAgICAgICAgICAgICAgZHAgPSAoZHAgPSBwMVswXSAtIHAwWzBdKSAqIGRwICsgKGRwID0gcDFbMV0gLSBwMFsxXSkgKiBkcCwKICAgICAgICAgICAgICBkbCA9IChkbCA9IGwxWzBdIC0gbDBbMF0pICogZGwgKyAoZGwgPSBsMVsxXSAtIGwwWzFdKSAqIGRsOwogICAgICAgICAgdCA9IHNjYWxlKHQsIE1hdGguc3FydChkcCAvIGRsKSk7CiAgICAgICAgICBwID0gWyhwMFswXSArIHAxWzBdKSAvIDIsIChwMFsxXSArIHAxWzFdKSAvIDJdOwogICAgICAgICAgbCA9IFsobDBbMF0gKyBsMVswXSkgLyAyLCAobDBbMV0gKyBsMVsxXSkgLyAyXTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoZy50b3VjaDApIHAgPSBnLnRvdWNoMFswXSwgbCA9IGcudG91Y2gwWzFdOwogICAgICAgIGVsc2UgcmV0dXJuOwogICAgICAgIGcuem9vbSgidG91Y2giLCBjb25zdHJhaW4odHJhbnNsYXRlKHQsIHAsIGwpLCBnLmV4dGVudCwgdHJhbnNsYXRlRXh0ZW50KSk7CiAgICAgIH0KCiAgICAgIGZ1bmN0aW9uIHRvdWNoZW5kZWQoKSB7CiAgICAgICAgdmFyIGcgPSBnZXN0dXJlKHRoaXMsIGFyZ3VtZW50cyksCiAgICAgICAgICAgIHRvdWNoZXMgPSBldmVudCQ0LmNoYW5nZWRUb3VjaGVzLAogICAgICAgICAgICBuID0gdG91Y2hlcy5sZW5ndGgsIGksIHQ7CgogICAgICAgIG5vcHJvcGFnYXRpb24kNSgpOwogICAgICAgIGlmICh0b3VjaGVuZGluZykgY2xlYXJUaW1lb3V0KHRvdWNoZW5kaW5nKTsKICAgICAgICB0b3VjaGVuZGluZyA9IHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7IHRvdWNoZW5kaW5nID0gbnVsbDsgfSwgdG91Y2hEZWxheSk7CiAgICAgICAgZm9yIChpID0gMDsgaSA8IG47ICsraSkgewogICAgICAgICAgdCA9IHRvdWNoZXNbaV07CiAgICAgICAgICBpZiAoZy50b3VjaDAgJiYgZy50b3VjaDBbMl0gPT09IHQuaWRlbnRpZmllcikgZGVsZXRlIGcudG91Y2gwOwogICAgICAgICAgZWxzZSBpZiAoZy50b3VjaDEgJiYgZy50b3VjaDFbMl0gPT09IHQuaWRlbnRpZmllcikgZGVsZXRlIGcudG91Y2gxOwogICAgICAgIH0KICAgICAgICBpZiAoZy50b3VjaDEgJiYgIWcudG91Y2gwKSBnLnRvdWNoMCA9IGcudG91Y2gxLCBkZWxldGUgZy50b3VjaDE7CiAgICAgICAgaWYgKGcudG91Y2gwKSBnLnRvdWNoMFsxXSA9IHRoaXMuX196b29tLmludmVydChnLnRvdWNoMFswXSk7CiAgICAgICAgZWxzZSBnLmVuZCgpOwogICAgICB9CgogICAgICB6b29tLndoZWVsRGVsdGEgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAod2hlZWxEZWx0YSA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHkoK18pLCB6b29tKSA6IHdoZWVsRGVsdGE7CiAgICAgIH07CgogICAgICB6b29tLmZpbHRlciA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChmaWx0ZXIgPSB0eXBlb2YgXyA9PT0gImZ1bmN0aW9uIiA/IF8gOiBjb25zdGFudCR5KCEhXyksIHpvb20pIDogZmlsdGVyOwogICAgICB9OwoKICAgICAgem9vbS50b3VjaGFibGUgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAodG91Y2hhYmxlID0gdHlwZW9mIF8gPT09ICJmdW5jdGlvbiIgPyBfIDogY29uc3RhbnQkeSghIV8pLCB6b29tKSA6IHRvdWNoYWJsZTsKICAgICAgfTsKCiAgICAgIHpvb20uZXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGV4dGVudCA9IHR5cGVvZiBfID09PSAiZnVuY3Rpb24iID8gXyA6IGNvbnN0YW50JHkoW1srX1swXVswXSwgK19bMF1bMV1dLCBbK19bMV1bMF0sICtfWzFdWzFdXV0pLCB6b29tKSA6IGV4dGVudDsKICAgICAgfTsKCiAgICAgIHpvb20uc2NhbGVFeHRlbnQgPSBmdW5jdGlvbihfKSB7CiAgICAgICAgcmV0dXJuIGFyZ3VtZW50cy5sZW5ndGggPyAoc2NhbGVFeHRlbnRbMF0gPSArX1swXSwgc2NhbGVFeHRlbnRbMV0gPSArX1sxXSwgem9vbSkgOiBbc2NhbGVFeHRlbnRbMF0sIHNjYWxlRXh0ZW50WzFdXTsKICAgICAgfTsKCiAgICAgIHpvb20udHJhbnNsYXRlRXh0ZW50ID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKHRyYW5zbGF0ZUV4dGVudFswXVswXSA9ICtfWzBdWzBdLCB0cmFuc2xhdGVFeHRlbnRbMV1bMF0gPSArX1sxXVswXSwgdHJhbnNsYXRlRXh0ZW50WzBdWzFdID0gK19bMF1bMV0sIHRyYW5zbGF0ZUV4dGVudFsxXVsxXSA9ICtfWzFdWzFdLCB6b29tKSA6IFtbdHJhbnNsYXRlRXh0ZW50WzBdWzBdLCB0cmFuc2xhdGVFeHRlbnRbMF1bMV1dLCBbdHJhbnNsYXRlRXh0ZW50WzFdWzBdLCB0cmFuc2xhdGVFeHRlbnRbMV1bMV1dXTsKICAgICAgfTsKCiAgICAgIHpvb20uY29uc3RyYWluID0gZnVuY3Rpb24oXykgewogICAgICAgIHJldHVybiBhcmd1bWVudHMubGVuZ3RoID8gKGNvbnN0cmFpbiA9IF8sIHpvb20pIDogY29uc3RyYWluOwogICAgICB9OwoKICAgICAgem9vbS5kdXJhdGlvbiA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChkdXJhdGlvbiA9ICtfLCB6b29tKSA6IGR1cmF0aW9uOwogICAgICB9OwoKICAgICAgem9vbS5pbnRlcnBvbGF0ZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChpbnRlcnBvbGF0ZSA9IF8sIHpvb20pIDogaW50ZXJwb2xhdGU7CiAgICAgIH07CgogICAgICB6b29tLm9uID0gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIHZhbHVlID0gbGlzdGVuZXJzLm9uLmFwcGx5KGxpc3RlbmVycywgYXJndW1lbnRzKTsKICAgICAgICByZXR1cm4gdmFsdWUgPT09IGxpc3RlbmVycyA/IHpvb20gOiB2YWx1ZTsKICAgICAgfTsKCiAgICAgIHpvb20uY2xpY2tEaXN0YW5jZSA9IGZ1bmN0aW9uKF8pIHsKICAgICAgICByZXR1cm4gYXJndW1lbnRzLmxlbmd0aCA/IChjbGlja0Rpc3RhbmNlMiA9IChfID0gK18pICogXywgem9vbSkgOiBNYXRoLnNxcnQoY2xpY2tEaXN0YW5jZTIpOwogICAgICB9OwoKICAgICAgcmV0dXJuIHpvb207CiAgICB9CgogICAgdmFyIGQzID0gLyojX19QVVJFX18qL09iamVjdC5mcmVlemUoewogICAgICAgIF9fcHJvdG9fXzogbnVsbCwKICAgICAgICB2ZXJzaW9uOiB2ZXJzaW9uJDIsCiAgICAgICAgYmlzZWN0OiBiaXNlY3RSaWdodCQxLAogICAgICAgIGJpc2VjdFJpZ2h0OiBiaXNlY3RSaWdodCQxLAogICAgICAgIGJpc2VjdExlZnQ6IGJpc2VjdExlZnQkMSwKICAgICAgICBhc2NlbmRpbmc6IGFzY2VuZGluZyQ0LAogICAgICAgIGJpc2VjdG9yOiBiaXNlY3RvciQxLAogICAgICAgIGNyb3NzOiBjcm9zcyQzLAogICAgICAgIGRlc2NlbmRpbmc6IGRlc2NlbmRpbmckMywKICAgICAgICBkZXZpYXRpb246IGRldmlhdGlvbiQxLAogICAgICAgIGV4dGVudDogZXh0ZW50JDIsCiAgICAgICAgaGlzdG9ncmFtOiBoaXN0b2dyYW0kMSwKICAgICAgICB0aHJlc2hvbGRGcmVlZG1hbkRpYWNvbmlzOiBmcmVlZG1hbkRpYWNvbmlzJDEsCiAgICAgICAgdGhyZXNob2xkU2NvdHQ6IHNjb3R0JDEsCiAgICAgICAgdGhyZXNob2xkU3R1cmdlczogc3R1cmdlcywKICAgICAgICBtYXg6IG1heCQzLAogICAgICAgIG1lYW46IG1lYW4kMSwKICAgICAgICBtZWRpYW46IG1lZGlhbiQxLAogICAgICAgIG1lcmdlOiBtZXJnZSQxLAogICAgICAgIG1pbjogbWluJDIsCiAgICAgICAgcGFpcnM6IHBhaXJzJDEsCiAgICAgICAgcGVybXV0ZTogcGVybXV0ZSQxLAogICAgICAgIHF1YW50aWxlOiBxdWFudGlsZSQxLAogICAgICAgIHJhbmdlOiByYW5nZSQxLAogICAgICAgIHNjYW46IHNjYW4kMSwKICAgICAgICBzaHVmZmxlOiBzaHVmZmxlJDIsCiAgICAgICAgc3VtOiBzdW0kMywKICAgICAgICB0aWNrczogdGlja3MkMSwKICAgICAgICB0aWNrSW5jcmVtZW50OiB0aWNrSW5jcmVtZW50JDEsCiAgICAgICAgdGlja1N0ZXA6IHRpY2tTdGVwJDEsCiAgICAgICAgdHJhbnNwb3NlOiB0cmFuc3Bvc2UkMSwKICAgICAgICB2YXJpYW5jZTogdmFyaWFuY2UkMSwKICAgICAgICB6aXA6IHppcCQxLAogICAgICAgIGF4aXNUb3A6IGF4aXNUb3AkMSwKICAgICAgICBheGlzUmlnaHQ6IGF4aXNSaWdodCQxLAogICAgICAgIGF4aXNCb3R0b206IGF4aXNCb3R0b20kMSwKICAgICAgICBheGlzTGVmdDogYXhpc0xlZnQkMSwKICAgICAgICBicnVzaDogYnJ1c2gkMiwKICAgICAgICBicnVzaFg6IGJydXNoWCQxLAogICAgICAgIGJydXNoWTogYnJ1c2hZJDEsCiAgICAgICAgYnJ1c2hTZWxlY3Rpb246IGJydXNoU2VsZWN0aW9uJDEsCiAgICAgICAgY2hvcmQ6IGNob3JkJDEsCiAgICAgICAgcmliYm9uOiByaWJib24kMSwKICAgICAgICBuZXN0OiBuZXN0JDEsCiAgICAgICAgc2V0OiBzZXQkNiwKICAgICAgICBtYXA6IG1hcCQ1LAogICAgICAgIGtleXM6IGtleXMkMSwKICAgICAgICB2YWx1ZXM6IHZhbHVlcyQxLAogICAgICAgIGVudHJpZXM6IGVudHJpZXMkMSwKICAgICAgICBjb2xvcjogY29sb3IkMiwKICAgICAgICByZ2I6IHJnYiQyLAogICAgICAgIGhzbDogaHNsJDQsCiAgICAgICAgbGFiOiBsYWIkMiwKICAgICAgICBoY2w6IGhjbCQzLAogICAgICAgIGN1YmVoZWxpeDogY3ViZWhlbGl4JDQsCiAgICAgICAgZGlzcGF0Y2g6IGRpc3BhdGNoJDIsCiAgICAgICAgZHJhZzogZHJhZyQxLAogICAgICAgIGRyYWdEaXNhYmxlOiBub2RyYWcsCiAgICAgICAgZHJhZ0VuYWJsZTogeWVzZHJhZyQyLAogICAgICAgIGRzdkZvcm1hdDogZHN2JDEsCiAgICAgICAgY3N2UGFyc2U6IGNzdlBhcnNlJDEsCiAgICAgICAgY3N2UGFyc2VSb3dzOiBjc3ZQYXJzZVJvd3MkMSwKICAgICAgICBjc3ZGb3JtYXQ6IGNzdkZvcm1hdCQxLAogICAgICAgIGNzdkZvcm1hdFJvd3M6IGNzdkZvcm1hdFJvd3MkMSwKICAgICAgICB0c3ZQYXJzZTogdHN2UGFyc2UkMSwKICAgICAgICB0c3ZQYXJzZVJvd3M6IHRzdlBhcnNlUm93cyQxLAogICAgICAgIHRzdkZvcm1hdDogdHN2Rm9ybWF0JDEsCiAgICAgICAgdHN2Rm9ybWF0Um93czogdHN2Rm9ybWF0Um93cyQxLAogICAgICAgIGVhc2VMaW5lYXI6IGxpbmVhciQ0LAogICAgICAgIGVhc2VRdWFkOiBxdWFkSW5PdXQkMSwKICAgICAgICBlYXNlUXVhZEluOiBxdWFkSW4kMSwKICAgICAgICBlYXNlUXVhZE91dDogcXVhZE91dCQxLAogICAgICAgIGVhc2VRdWFkSW5PdXQ6IHF1YWRJbk91dCQxLAogICAgICAgIGVhc2VDdWJpYzogY3ViaWNJbk91dCQxLAogICAgICAgIGVhc2VDdWJpY0luOiBjdWJpY0luJDEsCiAgICAgICAgZWFzZUN1YmljT3V0OiBjdWJpY091dCQxLAogICAgICAgIGVhc2VDdWJpY0luT3V0OiBjdWJpY0luT3V0JDEsCiAgICAgICAgZWFzZVBvbHk6IHBvbHlJbk91dCQxLAogICAgICAgIGVhc2VQb2x5SW46IHBvbHlJbiQxLAogICAgICAgIGVhc2VQb2x5T3V0OiBwb2x5T3V0JDEsCiAgICAgICAgZWFzZVBvbHlJbk91dDogcG9seUluT3V0JDEsCiAgICAgICAgZWFzZVNpbjogc2luSW5PdXQkMSwKICAgICAgICBlYXNlU2luSW46IHNpbkluJDEsCiAgICAgICAgZWFzZVNpbk91dDogc2luT3V0JDEsCiAgICAgICAgZWFzZVNpbkluT3V0OiBzaW5Jbk91dCQxLAogICAgICAgIGVhc2VFeHA6IGV4cEluT3V0JDEsCiAgICAgICAgZWFzZUV4cEluOiBleHBJbiQxLAogICAgICAgIGVhc2VFeHBPdXQ6IGV4cE91dCQxLAogICAgICAgIGVhc2VFeHBJbk91dDogZXhwSW5PdXQkMSwKICAgICAgICBlYXNlQ2lyY2xlOiBjaXJjbGVJbk91dCQxLAogICAgICAgIGVhc2VDaXJjbGVJbjogY2lyY2xlSW4kMSwKICAgICAgICBlYXNlQ2lyY2xlT3V0OiBjaXJjbGVPdXQkMSwKICAgICAgICBlYXNlQ2lyY2xlSW5PdXQ6IGNpcmNsZUluT3V0JDEsCiAgICAgICAgZWFzZUJvdW5jZTogYm91bmNlT3V0JDEsCiAgICAgICAgZWFzZUJvdW5jZUluOiBib3VuY2VJbiQxLAogICAgICAgIGVhc2VCb3VuY2VPdXQ6IGJvdW5jZU91dCQxLAogICAgICAgIGVhc2VCb3VuY2VJbk91dDogYm91bmNlSW5PdXQkMSwKICAgICAgICBlYXNlQmFjazogYmFja0luT3V0JDEsCiAgICAgICAgZWFzZUJhY2tJbjogYmFja0luJDEsCiAgICAgICAgZWFzZUJhY2tPdXQ6IGJhY2tPdXQkMSwKICAgICAgICBlYXNlQmFja0luT3V0OiBiYWNrSW5PdXQkMSwKICAgICAgICBlYXNlRWxhc3RpYzogZWxhc3RpY091dCQxLAogICAgICAgIGVhc2VFbGFzdGljSW46IGVsYXN0aWNJbiQxLAogICAgICAgIGVhc2VFbGFzdGljT3V0OiBlbGFzdGljT3V0JDEsCiAgICAgICAgZWFzZUVsYXN0aWNJbk91dDogZWxhc3RpY0luT3V0JDEsCiAgICAgICAgZm9yY2VDZW50ZXI6IGNlbnRlciQzLAogICAgICAgIGZvcmNlQ29sbGlkZTogY29sbGlkZSQxLAogICAgICAgIGZvcmNlTGluazogbGluayQzLAogICAgICAgIGZvcmNlTWFueUJvZHk6IG1hbnlCb2R5JDEsCiAgICAgICAgZm9yY2VSYWRpYWw6IHJhZGlhbCQxLAogICAgICAgIGZvcmNlU2ltdWxhdGlvbjogc2ltdWxhdGlvbiQxLAogICAgICAgIGZvcmNlWDogeCQ3LAogICAgICAgIGZvcmNlWTogeSQ3LAogICAgICAgIGZvcm1hdERlZmF1bHRMb2NhbGU6IGRlZmF1bHRMb2NhbGUkMiwKICAgICAgICBnZXQgZm9ybWF0ICgpIHsgcmV0dXJuIGZvcm1hdCQxOyB9LAogICAgICAgIGdldCBmb3JtYXRQcmVmaXggKCkgeyByZXR1cm4gZm9ybWF0UHJlZml4JDE7IH0sCiAgICAgICAgZm9ybWF0TG9jYWxlOiBmb3JtYXRMb2NhbGUkMiwKICAgICAgICBmb3JtYXRTcGVjaWZpZXI6IGZvcm1hdFNwZWNpZmllciQxLAogICAgICAgIHByZWNpc2lvbkZpeGVkOiBwcmVjaXNpb25GaXhlZCQxLAogICAgICAgIHByZWNpc2lvblByZWZpeDogcHJlY2lzaW9uUHJlZml4JDEsCiAgICAgICAgcHJlY2lzaW9uUm91bmQ6IHByZWNpc2lvblJvdW5kJDEsCiAgICAgICAgZ2VvQXJlYTogYXJlYSQ0LAogICAgICAgIGdlb0JvdW5kczogYm91bmRzJDEsCiAgICAgICAgZ2VvQ2VudHJvaWQ6IGNlbnRyb2lkJDIsCiAgICAgICAgZ2VvQ2lyY2xlOiBjaXJjbGUkMywKICAgICAgICBnZW9DbGlwQW50aW1lcmlkaWFuOiBjbGlwQW50aW1lcmlkaWFuJDEsCiAgICAgICAgZ2VvQ2xpcENpcmNsZTogY2xpcENpcmNsZSQxLAogICAgICAgIGdlb0NsaXBFeHRlbnQ6IGV4dGVudCQzLAogICAgICAgIGdlb0NsaXBSZWN0YW5nbGU6IGNsaXBSZWN0YW5nbGUkMSwKICAgICAgICBnZW9Db250YWluczogY29udGFpbnMkMywKICAgICAgICBnZW9EaXN0YW5jZTogZGlzdGFuY2UkMSwKICAgICAgICBnZW9HcmF0aWN1bGU6IGdyYXRpY3VsZSQxLAogICAgICAgIGdlb0dyYXRpY3VsZTEwOiBncmF0aWN1bGUxMCQxLAogICAgICAgIGdlb0ludGVycG9sYXRlOiBpbnRlcnBvbGF0ZSQ0LAogICAgICAgIGdlb0xlbmd0aDogbGVuZ3RoJDQsCiAgICAgICAgZ2VvUGF0aDogaW5kZXgkNSwKICAgICAgICBnZW9BbGJlcnM6IGFsYmVycyQxLAogICAgICAgIGdlb0FsYmVyc1VzYTogYWxiZXJzVXNhJDEsCiAgICAgICAgZ2VvQXppbXV0aGFsRXF1YWxBcmVhOiBhemltdXRoYWxFcXVhbEFyZWEkMSwKICAgICAgICBnZW9BemltdXRoYWxFcXVhbEFyZWFSYXc6IGF6aW11dGhhbEVxdWFsQXJlYVJhdyQxLAogICAgICAgIGdlb0F6aW11dGhhbEVxdWlkaXN0YW50OiBhemltdXRoYWxFcXVpZGlzdGFudCQxLAogICAgICAgIGdlb0F6aW11dGhhbEVxdWlkaXN0YW50UmF3OiBhemltdXRoYWxFcXVpZGlzdGFudFJhdyQxLAogICAgICAgIGdlb0NvbmljQ29uZm9ybWFsOiBjb25pY0NvbmZvcm1hbCQxLAogICAgICAgIGdlb0NvbmljQ29uZm9ybWFsUmF3OiBjb25pY0NvbmZvcm1hbFJhdyQxLAogICAgICAgIGdlb0NvbmljRXF1YWxBcmVhOiBjb25pY0VxdWFsQXJlYSQxLAogICAgICAgIGdlb0NvbmljRXF1YWxBcmVhUmF3OiBjb25pY0VxdWFsQXJlYVJhdyQxLAogICAgICAgIGdlb0NvbmljRXF1aWRpc3RhbnQ6IGNvbmljRXF1aWRpc3RhbnQkMSwKICAgICAgICBnZW9Db25pY0VxdWlkaXN0YW50UmF3OiBjb25pY0VxdWlkaXN0YW50UmF3JDEsCiAgICAgICAgZ2VvRXF1aXJlY3Rhbmd1bGFyOiBlcXVpcmVjdGFuZ3VsYXIkMSwKICAgICAgICBnZW9FcXVpcmVjdGFuZ3VsYXJSYXc6IGVxdWlyZWN0YW5ndWxhclJhdyQxLAogICAgICAgIGdlb0dub21vbmljOiBnbm9tb25pYyQxLAogICAgICAgIGdlb0dub21vbmljUmF3OiBnbm9tb25pY1JhdyQxLAogICAgICAgIGdlb0lkZW50aXR5OiBpZGVudGl0eSRmLAogICAgICAgIGdlb1Byb2plY3Rpb246IHByb2plY3Rpb24kMSwKICAgICAgICBnZW9Qcm9qZWN0aW9uTXV0YXRvcjogcHJvamVjdGlvbk11dGF0b3IkMSwKICAgICAgICBnZW9NZXJjYXRvcjogbWVyY2F0b3IkMSwKICAgICAgICBnZW9NZXJjYXRvclJhdzogbWVyY2F0b3JSYXckMSwKICAgICAgICBnZW9OYXR1cmFsRWFydGgxOiBuYXR1cmFsRWFydGgxJDEsCiAgICAgICAgZ2VvTmF0dXJhbEVhcnRoMVJhdzogbmF0dXJhbEVhcnRoMVJhdyQxLAogICAgICAgIGdlb09ydGhvZ3JhcGhpYzogb3J0aG9ncmFwaGljJDEsCiAgICAgICAgZ2VvT3J0aG9ncmFwaGljUmF3OiBvcnRob2dyYXBoaWNSYXckMSwKICAgICAgICBnZW9TdGVyZW9ncmFwaGljOiBzdGVyZW9ncmFwaGljJDEsCiAgICAgICAgZ2VvU3RlcmVvZ3JhcGhpY1Jhdzogc3RlcmVvZ3JhcGhpY1JhdyQxLAogICAgICAgIGdlb1RyYW5zdmVyc2VNZXJjYXRvcjogdHJhbnN2ZXJzZU1lcmNhdG9yJDEsCiAgICAgICAgZ2VvVHJhbnN2ZXJzZU1lcmNhdG9yUmF3OiB0cmFuc3ZlcnNlTWVyY2F0b3JSYXckMSwKICAgICAgICBnZW9Sb3RhdGlvbjogcm90YXRpb24kMSwKICAgICAgICBnZW9TdHJlYW06IGdlb1N0cmVhbSQxLAogICAgICAgIGdlb1RyYW5zZm9ybTogdHJhbnNmb3JtJDIsCiAgICAgICAgY2x1c3RlcjogY2x1c3RlciQxLAogICAgICAgIGhpZXJhcmNoeTogaGllcmFyY2h5JDEsCiAgICAgICAgcGFjazogaW5kZXgkNiwKICAgICAgICBwYWNrU2libGluZ3M6IHNpYmxpbmdzJDEsCiAgICAgICAgcGFja0VuY2xvc2U6IGVuY2xvc2UkMSwKICAgICAgICBwYXJ0aXRpb246IHBhcnRpdGlvbiQxLAogICAgICAgIHN0cmF0aWZ5OiBzdHJhdGlmeSQxLAogICAgICAgIHRyZWU6IHRyZWUkMSwKICAgICAgICB0cmVlbWFwOiBpbmRleCQ3LAogICAgICAgIHRyZWVtYXBCaW5hcnk6IGJpbmFyeSQxLAogICAgICAgIHRyZWVtYXBEaWNlOiB0cmVlbWFwRGljZSQxLAogICAgICAgIHRyZWVtYXBTbGljZTogdHJlZW1hcFNsaWNlJDEsCiAgICAgICAgdHJlZW1hcFNsaWNlRGljZTogc2xpY2VEaWNlJDEsCiAgICAgICAgdHJlZW1hcFNxdWFyaWZ5OiBzcXVhcmlmeSQxLAogICAgICAgIHRyZWVtYXBSZXNxdWFyaWZ5OiByZXNxdWFyaWZ5JDEsCiAgICAgICAgaW50ZXJwb2xhdGU6IHZhbHVlLAogICAgICAgIGludGVycG9sYXRlQXJyYXk6IGFycmF5JDUsCiAgICAgICAgaW50ZXJwb2xhdGVCYXNpczogYmFzaXMkNCwKICAgICAgICBpbnRlcnBvbGF0ZUJhc2lzQ2xvc2VkOiBiYXNpc0Nsb3NlZCQyLAogICAgICAgIGludGVycG9sYXRlRGF0ZTogZGF0ZSQzLAogICAgICAgIGludGVycG9sYXRlTnVtYmVyOiBudW1iZXIkNiwKICAgICAgICBpbnRlcnBvbGF0ZU9iamVjdDogb2JqZWN0JDQsCiAgICAgICAgaW50ZXJwb2xhdGVSb3VuZDogcm91bmQsCiAgICAgICAgaW50ZXJwb2xhdGVTdHJpbmc6IHN0cmluZywKICAgICAgICBpbnRlcnBvbGF0ZVRyYW5zZm9ybUNzczogaW50ZXJwb2xhdGVUcmFuc2Zvcm1Dc3MkMiwKICAgICAgICBpbnRlcnBvbGF0ZVRyYW5zZm9ybVN2ZzogaW50ZXJwb2xhdGVUcmFuc2Zvcm1TdmckMiwKICAgICAgICBpbnRlcnBvbGF0ZVpvb206IHpvb20kMSwKICAgICAgICBpbnRlcnBvbGF0ZVJnYjogcmdiJDQsCiAgICAgICAgaW50ZXJwb2xhdGVSZ2JCYXNpczogcmdiQmFzaXMkMSwKICAgICAgICBpbnRlcnBvbGF0ZVJnYkJhc2lzQ2xvc2VkOiByZ2JCYXNpc0Nsb3NlZCQxLAogICAgICAgIGludGVycG9sYXRlSHNsOiBoc2wkNywKICAgICAgICBpbnRlcnBvbGF0ZUhzbExvbmc6IGhzbExvbmckMSwKICAgICAgICBpbnRlcnBvbGF0ZUxhYjogbGFiJDQsCiAgICAgICAgaW50ZXJwb2xhdGVIY2w6IGhjbCQ2LAogICAgICAgIGludGVycG9sYXRlSGNsTG9uZzogaGNsTG9uZyQxLAogICAgICAgIGludGVycG9sYXRlQ3ViZWhlbGl4OiBjdWJlaGVsaXgkNywKICAgICAgICBpbnRlcnBvbGF0ZUN1YmVoZWxpeExvbmc6IGN1YmVoZWxpeExvbmckMSwKICAgICAgICBxdWFudGl6ZTogcXVhbnRpemUkMiwKICAgICAgICBwYXRoOiBwYXRoJDIsCiAgICAgICAgcG9seWdvbkFyZWE6IGFyZWEkNSwKICAgICAgICBwb2x5Z29uQ2VudHJvaWQ6IGNlbnRyb2lkJDMsCiAgICAgICAgcG9seWdvbkh1bGw6IGh1bGwkMSwKICAgICAgICBwb2x5Z29uQ29udGFpbnM6IGNvbnRhaW5zJDQsCiAgICAgICAgcG9seWdvbkxlbmd0aDogbGVuZ3RoJDUsCiAgICAgICAgcXVhZHRyZWU6IHF1YWR0cmVlJDIsCiAgICAgICAgcXVldWU6IHF1ZXVlLAogICAgICAgIHJhbmRvbVVuaWZvcm06IHVuaWZvcm0kMSwKICAgICAgICByYW5kb21Ob3JtYWw6IG5vcm1hbCQxLAogICAgICAgIHJhbmRvbUxvZ05vcm1hbDogbG9nTm9ybWFsJDEsCiAgICAgICAgcmFuZG9tQmF0ZXM6IGJhdGVzJDEsCiAgICAgICAgcmFuZG9tSXJ3aW5IYWxsOiBpcndpbkhhbGwkMSwKICAgICAgICByYW5kb21FeHBvbmVudGlhbDogZXhwb25lbnRpYWwkNCwKICAgICAgICByZXF1ZXN0OiByZXF1ZXN0LAogICAgICAgIGh0bWw6IGh0bWwkMiwKICAgICAgICBqc29uOiBqc29uJDEsCiAgICAgICAgdGV4dDogdGV4dCQxLAogICAgICAgIHhtbDogeG1sJDEsCiAgICAgICAgY3N2OiBjc3YkMywKICAgICAgICB0c3Y6IHRzdiQzLAogICAgICAgIHNjYWxlQmFuZDogYmFuZCQxLAogICAgICAgIHNjYWxlUG9pbnQ6IHBvaW50JDgsCiAgICAgICAgc2NhbGVJZGVudGl0eTogaWRlbnRpdHkkaSwKICAgICAgICBzY2FsZUxpbmVhcjogbGluZWFyJDcsCiAgICAgICAgc2NhbGVMb2c6IGxvZyQzLAogICAgICAgIHNjYWxlT3JkaW5hbDogb3JkaW5hbCQxLAogICAgICAgIHNjYWxlSW1wbGljaXQ6IGltcGxpY2l0JDEsCiAgICAgICAgc2NhbGVQb3c6IHBvdyQzLAogICAgICAgIHNjYWxlU3FydDogc3FydCQ0LAogICAgICAgIHNjYWxlUXVhbnRpbGU6IHF1YW50aWxlJDIsCiAgICAgICAgc2NhbGVRdWFudGl6ZTogcXVhbnRpemUkMywKICAgICAgICBzY2FsZVRocmVzaG9sZDogdGhyZXNob2xkJDMsCiAgICAgICAgc2NhbGVUaW1lOiB0aW1lJDEsCiAgICAgICAgc2NhbGVVdGM6IHV0Y1RpbWUkMSwKICAgICAgICBzY2hlbWVDYXRlZ29yeTEwOiBjYXRlZ29yeTEwJDEsCiAgICAgICAgc2NoZW1lQ2F0ZWdvcnkyMGI6IGNhdGVnb3J5MjBiLAogICAgICAgIHNjaGVtZUNhdGVnb3J5MjBjOiBjYXRlZ29yeTIwYywKICAgICAgICBzY2hlbWVDYXRlZ29yeTIwOiBjYXRlZ29yeTIwLAogICAgICAgIGludGVycG9sYXRlQ3ViZWhlbGl4RGVmYXVsdDogY3ViZWhlbGl4JGEsCiAgICAgICAgaW50ZXJwb2xhdGVSYWluYm93OiByYWluYm93JDIsCiAgICAgICAgaW50ZXJwb2xhdGVXYXJtOiB3YXJtJDEsCiAgICAgICAgaW50ZXJwb2xhdGVDb29sOiBjb29sJDEsCiAgICAgICAgaW50ZXJwb2xhdGVWaXJpZGlzOiB2aXJpZGlzJDEsCiAgICAgICAgaW50ZXJwb2xhdGVNYWdtYTogbWFnbWEkMSwKICAgICAgICBpbnRlcnBvbGF0ZUluZmVybm86IGluZmVybm8kMSwKICAgICAgICBpbnRlcnBvbGF0ZVBsYXNtYTogcGxhc21hJDEsCiAgICAgICAgc2NhbGVTZXF1ZW50aWFsOiBzZXF1ZW50aWFsJDEsCiAgICAgICAgY3JlYXRlOiBjcmVhdGUkMywKICAgICAgICBjcmVhdG9yOiBjcmVhdG9yJDMsCiAgICAgICAgbG9jYWw6IGxvY2FsJDMsCiAgICAgICAgbWF0Y2hlcjogbWF0Y2hlciQ0LAogICAgICAgIG1vdXNlOiBtb3VzZSQzLAogICAgICAgIG5hbWVzcGFjZTogbmFtZXNwYWNlJDMsCiAgICAgICAgbmFtZXNwYWNlczogbmFtZXNwYWNlcyQzLAogICAgICAgIGNsaWVudFBvaW50OiBwb2ludCQ5LAogICAgICAgIHNlbGVjdDogc2VsZWN0JDMsCiAgICAgICAgc2VsZWN0QWxsOiBzZWxlY3RBbGwkMSwKICAgICAgICBzZWxlY3Rpb246IHNlbGVjdGlvbiQzLAogICAgICAgIHNlbGVjdG9yOiBzZWxlY3RvciQzLAogICAgICAgIHNlbGVjdG9yQWxsOiBzZWxlY3RvckFsbCQzLAogICAgICAgIHN0eWxlOiBzdHlsZVZhbHVlJDMsCiAgICAgICAgdG91Y2g6IHRvdWNoJDIsCiAgICAgICAgdG91Y2hlczogdG91Y2hlcyQxLAogICAgICAgIHdpbmRvdzogZGVmYXVsdFZpZXckMywKICAgICAgICBnZXQgZXZlbnQgKCkgeyByZXR1cm4gZXZlbnQkMzsgfSwKICAgICAgICBjdXN0b21FdmVudDogY3VzdG9tRXZlbnQkMywKICAgICAgICBhcmM6IGFyYyQxLAogICAgICAgIGFyZWE6IGFyZWEkNiwKICAgICAgICBsaW5lOiBsaW5lJDEsCiAgICAgICAgcGllOiBwaWUkMSwKICAgICAgICBhcmVhUmFkaWFsOiBhcmVhUmFkaWFsJDEsCiAgICAgICAgcmFkaWFsQXJlYTogYXJlYVJhZGlhbCQxLAogICAgICAgIGxpbmVSYWRpYWw6IGxpbmVSYWRpYWwkMywKICAgICAgICByYWRpYWxMaW5lOiBsaW5lUmFkaWFsJDMsCiAgICAgICAgcG9pbnRSYWRpYWw6IHBvaW50UmFkaWFsJDEsCiAgICAgICAgbGlua0hvcml6b250YWw6IGxpbmtIb3Jpem9udGFsJDEsCiAgICAgICAgbGlua1ZlcnRpY2FsOiBsaW5rVmVydGljYWwkMSwKICAgICAgICBsaW5rUmFkaWFsOiBsaW5rUmFkaWFsJDEsCiAgICAgICAgc3ltYm9sOiBzeW1ib2wkMSwKICAgICAgICBzeW1ib2xzOiBzeW1ib2xzJDEsCiAgICAgICAgc3ltYm9sQ2lyY2xlOiBjaXJjbGUkNSwKICAgICAgICBzeW1ib2xDcm9zczogY3Jvc3MkNSwKICAgICAgICBzeW1ib2xEaWFtb25kOiBkaWFtb25kJDEsCiAgICAgICAgc3ltYm9sU3F1YXJlOiBzcXVhcmUkMSwKICAgICAgICBzeW1ib2xTdGFyOiBzdGFyJDEsCiAgICAgICAgc3ltYm9sVHJpYW5nbGU6IHRyaWFuZ2xlJDEsCiAgICAgICAgc3ltYm9sV3llOiB3eWUkMSwKICAgICAgICBjdXJ2ZUJhc2lzQ2xvc2VkOiBiYXNpc0Nsb3NlZCQzLAogICAgICAgIGN1cnZlQmFzaXNPcGVuOiBiYXNpc09wZW4kMSwKICAgICAgICBjdXJ2ZUJhc2lzOiBiYXNpcyQ1LAogICAgICAgIGN1cnZlQnVuZGxlOiBidW5kbGUkMSwKICAgICAgICBjdXJ2ZUNhcmRpbmFsQ2xvc2VkOiBjYXJkaW5hbENsb3NlZCQxLAogICAgICAgIGN1cnZlQ2FyZGluYWxPcGVuOiBjYXJkaW5hbE9wZW4kMSwKICAgICAgICBjdXJ2ZUNhcmRpbmFsOiBjYXJkaW5hbCQxLAogICAgICAgIGN1cnZlQ2F0bXVsbFJvbUNsb3NlZDogY2F0bXVsbFJvbUNsb3NlZCQxLAogICAgICAgIGN1cnZlQ2F0bXVsbFJvbU9wZW46IGNhdG11bGxSb21PcGVuJDEsCiAgICAgICAgY3VydmVDYXRtdWxsUm9tOiBjYXRtdWxsUm9tJDEsCiAgICAgICAgY3VydmVMaW5lYXJDbG9zZWQ6IGxpbmVhckNsb3NlZCQxLAogICAgICAgIGN1cnZlTGluZWFyOiBjdXJ2ZUxpbmVhciQxLAogICAgICAgIGN1cnZlTW9ub3RvbmVYOiBtb25vdG9uZVgkMSwKICAgICAgICBjdXJ2ZU1vbm90b25lWTogbW9ub3RvbmVZJDEsCiAgICAgICAgY3VydmVOYXR1cmFsOiBuYXR1cmFsJDEsCiAgICAgICAgY3VydmVTdGVwOiBzdGVwJDEsCiAgICAgICAgY3VydmVTdGVwQWZ0ZXI6IHN0ZXBBZnRlciQxLAogICAgICAgIGN1cnZlU3RlcEJlZm9yZTogc3RlcEJlZm9yZSQxLAogICAgICAgIHN0YWNrOiBzdGFjayQxLAogICAgICAgIHN0YWNrT2Zmc2V0RXhwYW5kOiBleHBhbmQkMSwKICAgICAgICBzdGFja09mZnNldERpdmVyZ2luZzogZGl2ZXJnaW5nJDIsCiAgICAgICAgc3RhY2tPZmZzZXROb25lOiBub25lJDYsCiAgICAgICAgc3RhY2tPZmZzZXRTaWxob3VldHRlOiBzaWxob3VldHRlJDEsCiAgICAgICAgc3RhY2tPZmZzZXRXaWdnbGU6IHdpZ2dsZSQxLAogICAgICAgIHN0YWNrT3JkZXJBc2NlbmRpbmc6IGFzY2VuZGluZyRiLAogICAgICAgIHN0YWNrT3JkZXJEZXNjZW5kaW5nOiBkZXNjZW5kaW5nJDUsCiAgICAgICAgc3RhY2tPcmRlckluc2lkZU91dDogaW5zaWRlT3V0JDEsCiAgICAgICAgc3RhY2tPcmRlck5vbmU6IG5vbmUkNywKICAgICAgICBzdGFja09yZGVyUmV2ZXJzZTogcmV2ZXJzZSQxLAogICAgICAgIHRpbWVJbnRlcnZhbDogbmV3SW50ZXJ2YWwkMiwKICAgICAgICB0aW1lTWlsbGlzZWNvbmQ6IG1pbGxpc2Vjb25kJDIsCiAgICAgICAgdGltZU1pbGxpc2Vjb25kczogbWlsbGlzZWNvbmRzJDEsCiAgICAgICAgdXRjTWlsbGlzZWNvbmQ6IG1pbGxpc2Vjb25kJDIsCiAgICAgICAgdXRjTWlsbGlzZWNvbmRzOiBtaWxsaXNlY29uZHMkMSwKICAgICAgICB0aW1lU2Vjb25kOiBzZWNvbmQkMiwKICAgICAgICB0aW1lU2Vjb25kczogc2Vjb25kcyQxLAogICAgICAgIHV0Y1NlY29uZDogc2Vjb25kJDIsCiAgICAgICAgdXRjU2Vjb25kczogc2Vjb25kcyQxLAogICAgICAgIHRpbWVNaW51dGU6IG1pbnV0ZSQyLAogICAgICAgIHRpbWVNaW51dGVzOiBtaW51dGVzJDEsCiAgICAgICAgdGltZUhvdXI6IGhvdXIkMiwKICAgICAgICB0aW1lSG91cnM6IGhvdXJzJDEsCiAgICAgICAgdGltZURheTogZGF5JDIsCiAgICAgICAgdGltZURheXM6IGRheXMkMSwKICAgICAgICB0aW1lV2Vlazogc3VuZGF5JDIsCiAgICAgICAgdGltZVdlZWtzOiBzdW5kYXlzJDEsCiAgICAgICAgdGltZVN1bmRheTogc3VuZGF5JDIsCiAgICAgICAgdGltZVN1bmRheXM6IHN1bmRheXMkMSwKICAgICAgICB0aW1lTW9uZGF5OiBtb25kYXkkMiwKICAgICAgICB0aW1lTW9uZGF5czogbW9uZGF5cyQxLAogICAgICAgIHRpbWVUdWVzZGF5OiB0dWVzZGF5JDIsCiAgICAgICAgdGltZVR1ZXNkYXlzOiB0dWVzZGF5cyQxLAogICAgICAgIHRpbWVXZWRuZXNkYXk6IHdlZG5lc2RheSQyLAogICAgICAgIHRpbWVXZWRuZXNkYXlzOiB3ZWRuZXNkYXlzJDEsCiAgICAgICAgdGltZVRodXJzZGF5OiB0aHVyc2RheSQyLAogICAgICAgIHRpbWVUaHVyc2RheXM6IHRodXJzZGF5cyQxLAogICAgICAgIHRpbWVGcmlkYXk6IGZyaWRheSQyLAogICAgICAgIHRpbWVGcmlkYXlzOiBmcmlkYXlzJDEsCiAgICAgICAgdGltZVNhdHVyZGF5OiBzYXR1cmRheSQyLAogICAgICAgIHRpbWVTYXR1cmRheXM6IHNhdHVyZGF5cyQxLAogICAgICAgIHRpbWVNb250aDogbW9udGgkMiwKICAgICAgICB0aW1lTW9udGhzOiBtb250aHMkMSwKICAgICAgICB0aW1lWWVhcjogeWVhciQyLAogICAgICAgIHRpbWVZZWFyczogeWVhcnMkMSwKICAgICAgICB1dGNNaW51dGU6IHV0Y01pbnV0ZSQyLAogICAgICAgIHV0Y01pbnV0ZXM6IHV0Y01pbnV0ZXMkMSwKICAgICAgICB1dGNIb3VyOiB1dGNIb3VyJDIsCiAgICAgICAgdXRjSG91cnM6IHV0Y0hvdXJzJDEsCiAgICAgICAgdXRjRGF5OiB1dGNEYXkkMiwKICAgICAgICB1dGNEYXlzOiB1dGNEYXlzJDEsCiAgICAgICAgdXRjV2VlazogdXRjU3VuZGF5JDIsCiAgICAgICAgdXRjV2Vla3M6IHV0Y1N1bmRheXMkMSwKICAgICAgICB1dGNTdW5kYXk6IHV0Y1N1bmRheSQyLAogICAgICAgIHV0Y1N1bmRheXM6IHV0Y1N1bmRheXMkMSwKICAgICAgICB1dGNNb25kYXk6IHV0Y01vbmRheSQyLAogICAgICAgIHV0Y01vbmRheXM6IHV0Y01vbmRheXMkMSwKICAgICAgICB1dGNUdWVzZGF5OiB1dGNUdWVzZGF5JDIsCiAgICAgICAgdXRjVHVlc2RheXM6IHV0Y1R1ZXNkYXlzJDEsCiAgICAgICAgdXRjV2VkbmVzZGF5OiB1dGNXZWRuZXNkYXkkMiwKICAgICAgICB1dGNXZWRuZXNkYXlzOiB1dGNXZWRuZXNkYXlzJDEsCiAgICAgICAgdXRjVGh1cnNkYXk6IHV0Y1RodXJzZGF5JDIsCiAgICAgICAgdXRjVGh1cnNkYXlzOiB1dGNUaHVyc2RheXMkMSwKICAgICAgICB1dGNGcmlkYXk6IHV0Y0ZyaWRheSQyLAogICAgICAgIHV0Y0ZyaWRheXM6IHV0Y0ZyaWRheXMkMSwKICAgICAgICB1dGNTYXR1cmRheTogdXRjU2F0dXJkYXkkMiwKICAgICAgICB1dGNTYXR1cmRheXM6IHV0Y1NhdHVyZGF5cyQxLAogICAgICAgIHV0Y01vbnRoOiB1dGNNb250aCQyLAogICAgICAgIHV0Y01vbnRoczogdXRjTW9udGhzJDEsCiAgICAgICAgdXRjWWVhcjogdXRjWWVhciQyLAogICAgICAgIHV0Y1llYXJzOiB1dGNZZWFycyQxLAogICAgICAgIHRpbWVGb3JtYXREZWZhdWx0TG9jYWxlOiBkZWZhdWx0TG9jYWxlJDUsCiAgICAgICAgZ2V0IHRpbWVGb3JtYXQgKCkgeyByZXR1cm4gdGltZUZvcm1hdCQyOyB9LAogICAgICAgIGdldCB0aW1lUGFyc2UgKCkgeyByZXR1cm4gdGltZVBhcnNlJDI7IH0sCiAgICAgICAgZ2V0IHV0Y0Zvcm1hdCAoKSB7IHJldHVybiB1dGNGb3JtYXQkMjsgfSwKICAgICAgICBnZXQgdXRjUGFyc2UgKCkgeyByZXR1cm4gdXRjUGFyc2UkMjsgfSwKICAgICAgICB0aW1lRm9ybWF0TG9jYWxlOiBmb3JtYXRMb2NhbGUkNSwKICAgICAgICBpc29Gb3JtYXQ6IGZvcm1hdElzbyQxLAogICAgICAgIGlzb1BhcnNlOiBwYXJzZUlzbyQxLAogICAgICAgIG5vdzogbm93JDMsCiAgICAgICAgdGltZXI6IHRpbWVyJDMsCiAgICAgICAgdGltZXJGbHVzaDogdGltZXJGbHVzaCQzLAogICAgICAgIHRpbWVvdXQ6IHRpbWVvdXQkNiwKICAgICAgICBpbnRlcnZhbDogaW50ZXJ2YWwkNSwKICAgICAgICB0cmFuc2l0aW9uOiB0cmFuc2l0aW9uJDIsCiAgICAgICAgYWN0aXZlOiBhY3RpdmUkMSwKICAgICAgICBpbnRlcnJ1cHQ6IGludGVycnVwdCQyLAogICAgICAgIHZvcm9ub2k6IHZvcm9ub2kkMSwKICAgICAgICB6b29tOiB6b29tJDIsCiAgICAgICAgem9vbVRyYW5zZm9ybTogdHJhbnNmb3JtJDMsCiAgICAgICAgem9vbUlkZW50aXR5OiBpZGVudGl0eSRtCiAgICB9KTsKCiAgICB2YXIgYWRkRDNTZWxlY3Rpb25NdWx0aSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICoKICAgICAqIEBmaWxlb3ZlcnZpZXcgbWFudWFsbHkgYWRkIGQzLXNlbGVjdGlvbi1tdWx0aSB0byBkMyBkZWZhdWx0IGJ1bmRsZS4gTW9zdCBvZiB0aGlzIGNvZGUgaXMKICAgICAqIGNvcGllZCBmcm9tIGQzLXNlbGVjdGlvbi1tdWx0aUAxLjAuMC4KICAgICAqIFNlZSBodHRwczovL2dpdGh1Yi5jb20vZDMvZDMtc2VsZWN0aW9uLW11bHRpL2lzc3Vlcy8xMSBmb3Igd2h5IHdlIGhhdmUgdG8gZG8gdGhpcwogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBkM1NlbGVjdGlvbiA9IGQzOwogICAgdmFyIGQzVHJhbnNpdGlvbiA9IGQzOwogICAgZnVuY3Rpb24gYXR0cnNGdW5jdGlvbihzZWxlY3Rpb24sIG1hcCkgewogICAgICAgIHJldHVybiBzZWxlY3Rpb24uZWFjaChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciB4ID0gbWFwLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyksIHMgPSBkM1NlbGVjdGlvbi5zZWxlY3QodGhpcyk7CiAgICAgICAgICAgIGZvciAodmFyIG5hbWVfMSBpbiB4KQogICAgICAgICAgICAgICAgcy5hdHRyKG5hbWVfMSwgeFtuYW1lXzFdKTsKICAgICAgICB9KTsKICAgIH0KICAgIGZ1bmN0aW9uIGF0dHJzT2JqZWN0KHNlbGVjdGlvbiwgbWFwKSB7CiAgICAgICAgZm9yICh2YXIgbmFtZV8yIGluIG1hcCkKICAgICAgICAgICAgc2VsZWN0aW9uLmF0dHIobmFtZV8yLCBtYXBbbmFtZV8yXSk7CiAgICAgICAgcmV0dXJuIHNlbGVjdGlvbjsKICAgIH0KICAgIGZ1bmN0aW9uIHNlbGVjdGlvbl9hdHRycyhtYXApIHsKICAgICAgICByZXR1cm4gKHR5cGVvZiBtYXAgPT09ICJmdW5jdGlvbiIgPyBhdHRyc0Z1bmN0aW9uIDogYXR0cnNPYmplY3QpKHRoaXMsIG1hcCk7CiAgICB9CiAgICBmdW5jdGlvbiBzdHlsZXNGdW5jdGlvbihzZWxlY3Rpb24sIG1hcCwgcHJpb3JpdHkpIHsKICAgICAgICByZXR1cm4gc2VsZWN0aW9uLmVhY2goZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgeCA9IG1hcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCBzID0gZDNTZWxlY3Rpb24uc2VsZWN0KHRoaXMpOwogICAgICAgICAgICBmb3IgKHZhciBuYW1lXzMgaW4geCkKICAgICAgICAgICAgICAgIHMuc3R5bGUobmFtZV8zLCB4W25hbWVfM10sIHByaW9yaXR5KTsKICAgICAgICB9KTsKICAgIH0KICAgIGZ1bmN0aW9uIHN0eWxlc09iamVjdChzZWxlY3Rpb24sIG1hcCwgcHJpb3JpdHkpIHsKICAgICAgICBmb3IgKHZhciBuYW1lXzQgaW4gbWFwKQogICAgICAgICAgICBzZWxlY3Rpb24uc3R5bGUobmFtZV80LCBtYXBbbmFtZV80XSwgcHJpb3JpdHkpOwogICAgICAgIHJldHVybiBzZWxlY3Rpb247CiAgICB9CiAgICBmdW5jdGlvbiBzZWxlY3Rpb25fc3R5bGVzKG1hcCwgcHJpb3JpdHkpIHsKICAgICAgICByZXR1cm4gKHR5cGVvZiBtYXAgPT09ICJmdW5jdGlvbiIgPyBzdHlsZXNGdW5jdGlvbiA6IHN0eWxlc09iamVjdCkodGhpcywgbWFwLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSk7CiAgICB9CiAgICBmdW5jdGlvbiBwcm9wZXJ0aWVzRnVuY3Rpb24oc2VsZWN0aW9uLCBtYXApIHsKICAgICAgICByZXR1cm4gc2VsZWN0aW9uLmVhY2goZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgeCA9IG1hcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCBzID0gZDNTZWxlY3Rpb24uc2VsZWN0KHRoaXMpOwogICAgICAgICAgICBmb3IgKHZhciBuYW1lXzUgaW4geCkKICAgICAgICAgICAgICAgIHMucHJvcGVydHkobmFtZV81LCB4W25hbWVfNV0pOwogICAgICAgIH0pOwogICAgfQogICAgZnVuY3Rpb24gcHJvcGVydGllc09iamVjdChzZWxlY3Rpb24sIG1hcCkgewogICAgICAgIGZvciAodmFyIG5hbWVfNiBpbiBtYXApCiAgICAgICAgICAgIHNlbGVjdGlvbi5wcm9wZXJ0eShuYW1lXzYsIG1hcFtuYW1lXzZdKTsKICAgICAgICByZXR1cm4gc2VsZWN0aW9uOwogICAgfQogICAgZnVuY3Rpb24gc2VsZWN0aW9uX3Byb3BlcnRpZXMobWFwKSB7CiAgICAgICAgcmV0dXJuICh0eXBlb2YgbWFwID09PSAiZnVuY3Rpb24iID8gcHJvcGVydGllc0Z1bmN0aW9uIDogcHJvcGVydGllc09iamVjdCkodGhpcywgbWFwKTsKICAgIH0KICAgIGZ1bmN0aW9uIGF0dHJzRnVuY3Rpb24kMSh0cmFuc2l0aW9uLCBtYXApIHsKICAgICAgICByZXR1cm4gdHJhbnNpdGlvbi5lYWNoKGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHggPSBtYXAuYXBwbHkodGhpcywgYXJndW1lbnRzKSwgdCA9IGQzU2VsZWN0aW9uLnNlbGVjdCh0aGlzKS50cmFuc2l0aW9uKHRyYW5zaXRpb24pOwogICAgICAgICAgICBmb3IgKHZhciBuYW1lXzcgaW4geCkKICAgICAgICAgICAgICAgIHQuYXR0cihuYW1lXzcsIHhbbmFtZV83XSk7CiAgICAgICAgfSk7CiAgICB9CiAgICBmdW5jdGlvbiBhdHRyc09iamVjdCQxKHRyYW5zaXRpb24sIG1hcCkgewogICAgICAgIGZvciAodmFyIG5hbWVfOCBpbiBtYXApCiAgICAgICAgICAgIHRyYW5zaXRpb24uYXR0cihuYW1lXzgsIG1hcFtuYW1lXzhdKTsKICAgICAgICByZXR1cm4gdHJhbnNpdGlvbjsKICAgIH0KICAgIGZ1bmN0aW9uIHRyYW5zaXRpb25fYXR0cnMobWFwKSB7CiAgICAgICAgcmV0dXJuICh0eXBlb2YgbWFwID09PSAiZnVuY3Rpb24iID8gYXR0cnNGdW5jdGlvbiQxIDogYXR0cnNPYmplY3QkMSkodGhpcywgbWFwKTsKICAgIH0KICAgIGZ1bmN0aW9uIHN0eWxlc0Z1bmN0aW9uJDEodHJhbnNpdGlvbiwgbWFwLCBwcmlvcml0eSkgewogICAgICAgIHJldHVybiB0cmFuc2l0aW9uLmVhY2goZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgeCA9IG1hcC5hcHBseSh0aGlzLCBhcmd1bWVudHMpLCB0ID0gZDNTZWxlY3Rpb24uc2VsZWN0KHRoaXMpLnRyYW5zaXRpb24odHJhbnNpdGlvbik7CiAgICAgICAgICAgIGZvciAodmFyIG5hbWVfOSBpbiB4KQogICAgICAgICAgICAgICAgdC5zdHlsZShuYW1lXzksIHhbbmFtZV85XSwgcHJpb3JpdHkpOwogICAgICAgIH0pOwogICAgfQogICAgZnVuY3Rpb24gc3R5bGVzT2JqZWN0JDEodHJhbnNpdGlvbiwgbWFwLCBwcmlvcml0eSkgewogICAgICAgIGZvciAodmFyIG5hbWVfMTAgaW4gbWFwKQogICAgICAgICAgICB0cmFuc2l0aW9uLnN0eWxlKG5hbWVfMTAsIG1hcFtuYW1lXzEwXSwgcHJpb3JpdHkpOwogICAgICAgIHJldHVybiB0cmFuc2l0aW9uOwogICAgfQogICAgZnVuY3Rpb24gdHJhbnNpdGlvbl9zdHlsZXMobWFwLCBwcmlvcml0eSkgewogICAgICAgIHJldHVybiAodHlwZW9mIG1hcCA9PT0gImZ1bmN0aW9uIiA/IHN0eWxlc0Z1bmN0aW9uJDEgOiBzdHlsZXNPYmplY3QkMSkodGhpcywgbWFwLCBwcmlvcml0eSA9PSBudWxsID8gIiIgOiBwcmlvcml0eSk7CiAgICB9CiAgICBkM1NlbGVjdGlvbi5zZWxlY3Rpb24ucHJvdG90eXBlLmF0dHJzID0gc2VsZWN0aW9uX2F0dHJzOwogICAgZDNTZWxlY3Rpb24uc2VsZWN0aW9uLnByb3RvdHlwZS5zdHlsZXMgPSBzZWxlY3Rpb25fc3R5bGVzOwogICAgZDNTZWxlY3Rpb24uc2VsZWN0aW9uLnByb3RvdHlwZS5wcm9wZXJ0aWVzID0gc2VsZWN0aW9uX3Byb3BlcnRpZXM7CiAgICBkM1RyYW5zaXRpb24udHJhbnNpdGlvbi5wcm90b3R5cGUuYXR0cnMgPSB0cmFuc2l0aW9uX2F0dHJzOwogICAgZDNUcmFuc2l0aW9uLnRyYW5zaXRpb24ucHJvdG90eXBlLnN0eWxlcyA9IHRyYW5zaXRpb25fc3R5bGVzOwogICAgfSk7CgogICAgdmFyIGNvZXJjZUQzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvKioKICAgICAqIENvZXJjZSBwb3NzaWJseSBleHRlcm5hbCBkMyBpbnN0YW5jZSBpbnRvIG91ciBvd24gaW5zdGFuY2Ugb2YgZDMgc28gd2UgY2FuIHVzZSBkMy1zZWxlY3Rpb24tbXVsdGkuCiAgICAgKiBTZWUgaHR0cHM6Ly9naXRodWIuY29tL2QzL2QzLXNlbGVjdGlvbi1tdWx0aS9pc3N1ZXMvMTEgZm9yIHdoeSB3ZSBoYXZlIHRvIGRvIHRoaXMuCiAgICAgKgogICAgICogQW55IHB1YmxpYyBmYWNpbmcgQVBJIHRoYXQgYWNjZXB0cyBhIGQzIHNlbGVjdGlvbiBzaG91bGQgZmlyc3QgcGFzcyB0aGF0IHVzZXItc3VwcGxpZWQgc2VsZWN0aW9uCiAgICAgKiB0aHJvdWdoIGhlcmUgLSB0aGlzIGVuc3VyZXMgYWxsIHNlbGVjdGlvbiBvYmplY3RzIHRoYXQgZ28gdGhyb3VnaCB0aGUgUGxvdHRhYmxlIGNvZGViYXNlIGFyZSAidmV0dGVkIi4KICAgICAqLwogICAgZnVuY3Rpb24gY29lcmNlRXh0ZXJuYWxEMyhleHRlcm5hbEQzU2VsZWN0aW9uKSB7CiAgICAgICAgLy8gaWYgLmF0dHJzIGlzbid0IGRlZmluZWQ7IGNvbnZlcnQgdGhlIHNlbGVjdGlvbgogICAgICAgIGlmIChleHRlcm5hbEQzU2VsZWN0aW9uLmF0dHJzID09IG51bGwpIHsKICAgICAgICAgICAgaWYgKGV4dGVybmFsRDNTZWxlY3Rpb24ubm9kZXMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgLy8gbm9kZXMgaXNuJ3QgZGVmaW5lZDsgdGhpcyBpcyBwcm9iYWJseSBhIGQzdjMgc2VsZWN0aW9uLiBoYW5kbGUgaXQgYWNjb3JkaW5nbHkKICAgICAgICAgICAgICAgIHZhciBub2Rlc18xID0gW107CiAgICAgICAgICAgICAgICBleHRlcm5hbEQzU2VsZWN0aW9uLmVhY2goZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIG5vZGVzXzEucHVzaCh0aGlzKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgcmV0dXJuIGQzLnNlbGVjdEFsbChub2Rlc18xKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBkMy5zZWxlY3RBbGwoZXh0ZXJuYWxEM1NlbGVjdGlvbi5ub2RlcygpKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgcmV0dXJuIGV4dGVybmFsRDNTZWxlY3Rpb247CiAgICAgICAgfQogICAgfQogICAgZXhwb3J0cy5jb2VyY2VFeHRlcm5hbEQzID0gY29lcmNlRXh0ZXJuYWxEMzsKICAgIH0pOwoKICAgIHZhciBtYWtlRW51bV8xID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICBmdW5jdGlvbiBtYWtlRW51bSh2YWx1ZXMpIHsKICAgICAgICByZXR1cm4gdmFsdWVzLnJlZHVjZShmdW5jdGlvbiAob2JqLCB2KSB7CiAgICAgICAgICAgIG9ialt2XSA9IHY7CiAgICAgICAgICAgIHJldHVybiBvYmo7CiAgICAgICAgfSwge30pOwogICAgfQogICAgZXhwb3J0cy5tYWtlRW51bSA9IG1ha2VFbnVtOwogICAgfSk7CgogICAgdmFyIGVhc2luZ0FuaW1hdG9yID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICB2YXIgRUFTRV9OQU1FX01BUFBJTkcgPSB7CiAgICAgICAgbGluZWFyOiBzcmMuZWFzZUxpbmVhciwKICAgICAgICBxdWFkOiBzcmMuZWFzZVF1YWQsCiAgICAgICAgcXVhZEluOiBzcmMuZWFzZVF1YWRJbiwKICAgICAgICBxdWFkT3V0OiBzcmMuZWFzZVF1YWRPdXQsCiAgICAgICAgcXVhZEluT3V0OiBzcmMuZWFzZVF1YWRJbk91dCwKICAgICAgICBjdWJpYzogc3JjLmVhc2VDdWJpYywKICAgICAgICBjdWJpY0luOiBzcmMuZWFzZUN1YmljSW4sCiAgICAgICAgY3ViaWNPdXQ6IHNyYy5lYXNlQ3ViaWNPdXQsCiAgICAgICAgY3ViaWNJbk91dDogc3JjLmVhc2VDdWJpY0luT3V0LAogICAgICAgIHBvbHk6IHNyYy5lYXNlUG9seSwKICAgICAgICBwb2x5SW46IHNyYy5lYXNlUG9seUluLAogICAgICAgIHBvbHlPdXQ6IHNyYy5lYXNlUG9seU91dCwKICAgICAgICBwb2x5SW5PdXQ6IHNyYy5lYXNlUG9seUluT3V0LAogICAgICAgIHNpbjogc3JjLmVhc2VTaW4sCiAgICAgICAgc2luSW46IHNyYy5lYXNlU2luSW4sCiAgICAgICAgc2luT3V0OiBzcmMuZWFzZVNpbk91dCwKICAgICAgICBzaW5Jbk91dDogc3JjLmVhc2VTaW5Jbk91dCwKICAgICAgICBleHA6IHNyYy5lYXNlRXhwLAogICAgICAgIGV4cEluOiBzcmMuZWFzZUV4cEluLAogICAgICAgIGV4cE91dDogc3JjLmVhc2VFeHBPdXQsCiAgICAgICAgZXhwSW5PdXQ6IHNyYy5lYXNlRXhwSW5PdXQsCiAgICAgICAgY2lyY2xlOiBzcmMuZWFzZUNpcmNsZSwKICAgICAgICBjaXJjbGVJbjogc3JjLmVhc2VDaXJjbGVJbiwKICAgICAgICBjaXJjbGVPdXQ6IHNyYy5lYXNlQ2lyY2xlT3V0LAogICAgICAgIGNpcmNsZUluT3V0OiBzcmMuZWFzZUNpcmNsZUluT3V0LAogICAgICAgIGJvdW5jZTogc3JjLmVhc2VCb3VuY2UsCiAgICAgICAgYm91bmNlSW46IHNyYy5lYXNlQm91bmNlSW4sCiAgICAgICAgYm91bmNlT3V0OiBzcmMuZWFzZUJvdW5jZU91dCwKICAgICAgICBib3VuY2VJbk91dDogc3JjLmVhc2VCb3VuY2VJbk91dCwKICAgICAgICBiYWNrOiBzcmMuZWFzZUJhY2ssCiAgICAgICAgYmFja0luOiBzcmMuZWFzZUJhY2tJbiwKICAgICAgICBiYWNrT3V0OiBzcmMuZWFzZUJhY2tPdXQsCiAgICAgICAgYmFja0luT3V0OiBzcmMuZWFzZUJhY2tJbk91dCwKICAgICAgICBlbGFzdGljOiBzcmMuZWFzZUVsYXN0aWMsCiAgICAgICAgZWxhc3RpY0luOiBzcmMuZWFzZUVsYXN0aWNJbiwKICAgICAgICBlbGFzdGljT3V0OiBzcmMuZWFzZUVsYXN0aWNPdXQsCiAgICAgICAgZWxhc3RpY0luT3V0OiBzcmMuZWFzZUVsYXN0aWNJbk91dCwKICAgIH07CiAgICBleHBvcnRzLkVhc2VOYW1lID0gbWFrZUVudW1fMS5tYWtlRW51bShbCiAgICAgICAgImxpbmVhciIsCiAgICAgICAgInF1YWQiLAogICAgICAgICJxdWFkSW4iLAogICAgICAgICJxdWFkT3V0IiwKICAgICAgICAicXVhZEluT3V0IiwKICAgICAgICAiY3ViaWMiLAogICAgICAgICJjdWJpY0luIiwKICAgICAgICAiY3ViaWNPdXQiLAogICAgICAgICJjdWJpY0luT3V0IiwKICAgICAgICAicG9seSIsCiAgICAgICAgInBvbHlJbiIsCiAgICAgICAgInBvbHlPdXQiLAogICAgICAgICJwb2x5SW5PdXQiLAogICAgICAgICJzaW4iLAogICAgICAgICJzaW5JbiIsCiAgICAgICAgInNpbk91dCIsCiAgICAgICAgInNpbkluT3V0IiwKICAgICAgICAiZXhwIiwKICAgICAgICAiZXhwSW4iLAogICAgICAgICJleHBPdXQiLAogICAgICAgICJleHBJbk91dCIsCiAgICAgICAgImNpcmNsZSIsCiAgICAgICAgImNpcmNsZUluIiwKICAgICAgICAiY2lyY2xlT3V0IiwKICAgICAgICAiY2lyY2xlSW5PdXQiLAogICAgICAgICJib3VuY2UiLAogICAgICAgICJib3VuY2VJbiIsCiAgICAgICAgImJvdW5jZU91dCIsCiAgICAgICAgImJvdW5jZUluT3V0IiwKICAgICAgICAiYmFjayIsCiAgICAgICAgImJhY2tJbiIsCiAgICAgICAgImJhY2tPdXQiLAogICAgICAgICJiYWNrSW5PdXQiLAogICAgICAgICJlbGFzdGljIiwKICAgICAgICAiZWxhc3RpY0luIiwKICAgICAgICAiZWxhc3RpY091dCIsCiAgICAgICAgImVsYXN0aWNJbk91dCIsCiAgICBdKTsKICAgIC8qKgogICAgICogQW4gQW5pbWF0b3Igd2l0aCBlYXNpbmcgYW5kIGNvbmZpZ3VyYWJsZSBkdXJhdGlvbnMgYW5kIGRlbGF5cy4KICAgICAqLwogICAgdmFyIEVhc2luZyA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIHRoZSBkZWZhdWx0IGFuaW1hdG9yCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBFYXNpbmcoKSB7CiAgICAgICAgICAgIHRoaXMuX3N0YXJ0RGVsYXkgPSBFYXNpbmcuX0RFRkFVTFRfU1RBUlRfREVMQVlfTUlMTElTRUNPTkRTOwogICAgICAgICAgICB0aGlzLl9zdGVwRHVyYXRpb24gPSBFYXNpbmcuX0RFRkFVTFRfU1RFUF9EVVJBVElPTl9NSUxMSVNFQ09ORFM7CiAgICAgICAgICAgIHRoaXMuX3N0ZXBEZWxheSA9IEVhc2luZy5fREVGQVVMVF9JVEVSQVRJVkVfREVMQVlfTUlMTElTRUNPTkRTOwogICAgICAgICAgICB0aGlzLl9tYXhUb3RhbER1cmF0aW9uID0gRWFzaW5nLl9ERUZBVUxUX01BWF9UT1RBTF9EVVJBVElPTl9NSUxMSVNFQ09ORFM7CiAgICAgICAgICAgIHRoaXMuX2Vhc2luZ01vZGUgPSBFYXNpbmcuX0RFRkFVTFRfRUFTSU5HX01PREU7CiAgICAgICAgfQogICAgICAgIEVhc2luZy5wcm90b3R5cGUudG90YWxUaW1lID0gZnVuY3Rpb24gKG51bWJlck9mU3RlcHMpIHsKICAgICAgICAgICAgdmFyIGFkanVzdGVkSXRlcmF0aXZlRGVsYXkgPSB0aGlzLl9nZXRBZGp1c3RlZEl0ZXJhdGl2ZURlbGF5KG51bWJlck9mU3RlcHMpOwogICAgICAgICAgICByZXR1cm4gdGhpcy5zdGFydERlbGF5KCkgKyBhZGp1c3RlZEl0ZXJhdGl2ZURlbGF5ICogKE1hdGgubWF4KG51bWJlck9mU3RlcHMgLSAxLCAwKSkgKyB0aGlzLnN0ZXBEdXJhdGlvbigpOwogICAgICAgIH07CiAgICAgICAgRWFzaW5nLnByb3RvdHlwZS5hbmltYXRlID0gZnVuY3Rpb24gKHNlbGVjdGlvbiwgYXR0clRvQXBwbGllZFByb2plY3RvcikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBzZWxlY3Rpb24gPSBjb2VyY2VEMy5jb2VyY2VFeHRlcm5hbEQzKHNlbGVjdGlvbik7CiAgICAgICAgICAgIHZhciBudW1iZXJPZlN0ZXBzID0gc2VsZWN0aW9uLnNpemUoKTsKICAgICAgICAgICAgdmFyIGFkanVzdGVkSXRlcmF0aXZlRGVsYXkgPSB0aGlzLl9nZXRBZGp1c3RlZEl0ZXJhdGl2ZURlbGF5KG51bWJlck9mU3RlcHMpOwogICAgICAgICAgICByZXR1cm4gc2VsZWN0aW9uLnRyYW5zaXRpb24oKQogICAgICAgICAgICAgICAgLmVhc2UodGhpcy5fZ2V0RWFzZUZhY3RvcnkoKSkKICAgICAgICAgICAgICAgIC5kdXJhdGlvbih0aGlzLnN0ZXBEdXJhdGlvbigpKQogICAgICAgICAgICAgICAgLmRlbGF5KGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBfdGhpcy5zdGFydERlbGF5KCkgKyBhZGp1c3RlZEl0ZXJhdGl2ZURlbGF5ICogaTsgfSkKICAgICAgICAgICAgICAgIC5hdHRycyhhdHRyVG9BcHBsaWVkUHJvamVjdG9yKTsKICAgICAgICB9OwogICAgICAgIEVhc2luZy5wcm90b3R5cGUuc3RhcnREZWxheSA9IGZ1bmN0aW9uIChzdGFydERlbGF5KSB7CiAgICAgICAgICAgIGlmIChzdGFydERlbGF5ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9zdGFydERlbGF5OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fc3RhcnREZWxheSA9IHN0YXJ0RGVsYXk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgRWFzaW5nLnByb3RvdHlwZS5zdGVwRHVyYXRpb24gPSBmdW5jdGlvbiAoc3RlcER1cmF0aW9uKSB7CiAgICAgICAgICAgIGlmIChzdGVwRHVyYXRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIE1hdGgubWluKHRoaXMuX3N0ZXBEdXJhdGlvbiwgdGhpcy5fbWF4VG90YWxEdXJhdGlvbik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9zdGVwRHVyYXRpb24gPSBzdGVwRHVyYXRpb247CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgRWFzaW5nLnByb3RvdHlwZS5zdGVwRGVsYXkgPSBmdW5jdGlvbiAoc3RlcERlbGF5KSB7CiAgICAgICAgICAgIGlmIChzdGVwRGVsYXkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3N0ZXBEZWxheTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3N0ZXBEZWxheSA9IHN0ZXBEZWxheTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBFYXNpbmcucHJvdG90eXBlLm1heFRvdGFsRHVyYXRpb24gPSBmdW5jdGlvbiAobWF4VG90YWxEdXJhdGlvbikgewogICAgICAgICAgICBpZiAobWF4VG90YWxEdXJhdGlvbiA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWF4VG90YWxEdXJhdGlvbjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heFRvdGFsRHVyYXRpb24gPSBtYXhUb3RhbER1cmF0aW9uOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEVhc2luZy5wcm90b3R5cGUuZWFzaW5nTW9kZSA9IGZ1bmN0aW9uIChlYXNpbmdNb2RlKSB7CiAgICAgICAgICAgIGlmIChlYXNpbmdNb2RlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9lYXNpbmdNb2RlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZWFzaW5nTW9kZSA9IGVhc2luZ01vZGU7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgRWFzaW5nLnByb3RvdHlwZS5fZ2V0RWFzZUZhY3RvcnkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBlYXNlID0gdGhpcy5lYXNpbmdNb2RlKCk7CiAgICAgICAgICAgIGlmICh0eXBlb2YgZWFzZSA9PT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgIHZhciBtYXliZUVhc2VGdW5jdGlvbiA9IEVBU0VfTkFNRV9NQVBQSU5HW2Vhc2VdOwogICAgICAgICAgICAgICAgaWYgKG1heWJlRWFzZUZ1bmN0aW9uID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAvLyBvb3BzOyBuYW1lIGlzIHdyb25nIC0gZGVmYXVsdCB0byBsaW5lYXIgaW5zdGVhZAogICAgICAgICAgICAgICAgICAgIHJldHVybiBFQVNFX05BTUVfTUFQUElOR1sibGluZWFyIl07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbWF5YmVFYXNlRnVuY3Rpb247CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZWFzZTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRqdXN0IHRoZSBpdGVyYXRpdmUgZGVsYXksIHN1Y2ggdGhhdCBpdCB0YWtlcyBpbnRvIGFjY291bnQgdGhlIG1heFRvdGFsRHVyYXRpb24gY29uc3RyYWludAogICAgICAgICAqLwogICAgICAgIEVhc2luZy5wcm90b3R5cGUuX2dldEFkanVzdGVkSXRlcmF0aXZlRGVsYXkgPSBmdW5jdGlvbiAobnVtYmVyT2ZTdGVwcykgewogICAgICAgICAgICB2YXIgc3RlcFN0YXJ0VGltZUludGVydmFsID0gdGhpcy5tYXhUb3RhbER1cmF0aW9uKCkgLSB0aGlzLnN0ZXBEdXJhdGlvbigpOwogICAgICAgICAgICBzdGVwU3RhcnRUaW1lSW50ZXJ2YWwgPSBNYXRoLm1heChzdGVwU3RhcnRUaW1lSW50ZXJ2YWwsIDApOwogICAgICAgICAgICB2YXIgbWF4UG9zc2libGVJdGVyYXRpdmVEZWxheSA9IHN0ZXBTdGFydFRpbWVJbnRlcnZhbCAvIE1hdGgubWF4KG51bWJlck9mU3RlcHMgLSAxLCAxKTsKICAgICAgICAgICAgcmV0dXJuIE1hdGgubWluKHRoaXMuc3RlcERlbGF5KCksIG1heFBvc3NpYmxlSXRlcmF0aXZlRGVsYXkpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGRlZmF1bHQgc3RhcnRpbmcgZGVsYXkgb2YgdGhlIGFuaW1hdGlvbiBpbiBtaWxsaXNlY29uZHMKICAgICAgICAgKi8KICAgICAgICBFYXNpbmcuX0RFRkFVTFRfU1RBUlRfREVMQVlfTUlMTElTRUNPTkRTID0gMDsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGVmYXVsdCBkdXJhdGlvbiBvZiBvbmUgYW5pbWF0aW9uIHN0ZXAgaW4gbWlsbGlzZWNvbmRzCiAgICAgICAgICovCiAgICAgICAgRWFzaW5nLl9ERUZBVUxUX1NURVBfRFVSQVRJT05fTUlMTElTRUNPTkRTID0gMzAwOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBkZWZhdWx0IG1heGltdW0gc3RhcnQgZGVsYXkgYmV0d2VlbiBlYWNoIHN0ZXAgb2YgYW4gYW5pbWF0aW9uCiAgICAgICAgICovCiAgICAgICAgRWFzaW5nLl9ERUZBVUxUX0lURVJBVElWRV9ERUxBWV9NSUxMSVNFQ09ORFMgPSAxNTsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgZGVmYXVsdCBtYXhpbXVtIHRvdGFsIGFuaW1hdGlvbiBkdXJhdGlvbgogICAgICAgICAqLwogICAgICAgIEVhc2luZy5fREVGQVVMVF9NQVhfVE9UQUxfRFVSQVRJT05fTUlMTElTRUNPTkRTID0gSW5maW5pdHk7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGRlZmF1bHQgZWFzaW5nIG9mIHRoZSBhbmltYXRpb24KICAgICAgICAgKi8KICAgICAgICBFYXNpbmcuX0RFRkFVTFRfRUFTSU5HX01PREUgPSAiZXhwT3V0IjsKICAgICAgICByZXR1cm4gRWFzaW5nOwogICAgfSgpKTsKICAgIGV4cG9ydHMuRWFzaW5nID0gRWFzaW5nOwogICAgfSk7CgogICAgdmFyIG51bGxBbmltYXRvciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIC8qKgogICAgICogQW4gYW5pbWF0b3IgaW1wbGVtZW50YXRpb24gd2l0aCBubyBhbmltYXRpb24uIFRoZSBhdHRyaWJ1dGVzIGFyZQogICAgICogaW1tZWRpYXRlbHkgc2V0IG9uIHRoZSBzZWxlY3Rpb24uCiAgICAgKi8KICAgIHZhciBOdWxsID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIE51bGwoKSB7CiAgICAgICAgfQogICAgICAgIE51bGwucHJvdG90eXBlLnRvdGFsVGltZSA9IGZ1bmN0aW9uIChzZWxlY3Rpb24pIHsKICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfTsKICAgICAgICBOdWxsLnByb3RvdHlwZS5hbmltYXRlID0gZnVuY3Rpb24gKHNlbGVjdGlvbiwgYXR0clRvQXBwbGllZFByb2plY3RvcikgewogICAgICAgICAgICBzZWxlY3Rpb24gPSBjb2VyY2VEMy5jb2VyY2VFeHRlcm5hbEQzKHNlbGVjdGlvbik7CiAgICAgICAgICAgIHJldHVybiBzZWxlY3Rpb24uYXR0cnMoYXR0clRvQXBwbGllZFByb2plY3Rvcik7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gTnVsbDsKICAgIH0oKSk7CiAgICBleHBvcnRzLk51bGwgPSBOdWxsOwogICAgfSk7CgogICAgdmFyIGFuaW1hdG9ycyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZWFzaW5nQW5pbWF0b3IsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihudWxsQW5pbWF0b3IsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIGNhY2hlID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgQ2FjaGUgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIC8qKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGNvbXB1dGUgVGhlIGZ1bmN0aW9uIHdob3NlIHJlc3VsdHMgd2lsbCBiZSBjYWNoZWQuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gQ2FjaGUoY29tcHV0ZSkgewogICAgICAgICAgICB0aGlzLmNhY2hlID0ge307CiAgICAgICAgICAgIHRoaXMuY29tcHV0ZSA9IGNvbXB1dGU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEF0dGVtcHQgdG8gbG9vayB1cCBrIGluIHRoZSBjYWNoZSwgY29tcHV0aW5nIHRoZSByZXN1bHQgaWYgaXQgaXNuJ3QKICAgICAgICAgKiBmb3VuZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrIFRoZSBrZXkgdG8gbG9vayB1cCBpbiB0aGUgY2FjaGUuCiAgICAgICAgICogQHJldHVybiB7VH0gVGhlIHZhbHVlIGFzc29jaWF0ZWQgd2l0aCBrOyB0aGUgcmVzdWx0IG9mIGNvbXB1dGUoaykuCiAgICAgICAgICovCiAgICAgICAgQ2FjaGUucHJvdG90eXBlLmdldCA9IGZ1bmN0aW9uIChrKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5jYWNoZS5oYXNPd25Qcm9wZXJ0eShrKSkgewogICAgICAgICAgICAgICAgdGhpcy5jYWNoZVtrXSA9IHRoaXMuY29tcHV0ZShrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5jYWNoZVtrXTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlc2V0IHRoZSBjYWNoZSBlbXB0eS4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge0NhY2hlPFQ+fSBUaGUgY2FsbGluZyBDYWNoZS4KICAgICAgICAgKi8KICAgICAgICBDYWNoZS5wcm90b3R5cGUuY2xlYXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuY2FjaGUgPSB7fTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ2FjaGU7CiAgICB9KCkpOwogICAgZXhwb3J0cy5DYWNoZSA9IENhY2hlOwoKICAgIH0pOwoKICAgIHZhciBtZXRob2RzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgTWV0aG9kcyA9IChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gTWV0aG9kcygpIHsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2sgaWYgdHdvIGFycmF5cyBhcmUgZXF1YWwgYnkgc3RyaWN0IGVxdWFsaXR5LgogICAgICAgICAqLwogICAgICAgIE1ldGhvZHMuYXJyYXlFcSA9IGZ1bmN0aW9uIChhLCBiKSB7CiAgICAgICAgICAgIC8vIFRlY2huaWNhbGx5LCBudWxsIGFuZCB1bmRlZmluZWQgYXJlIGFycmF5cyB0b28KICAgICAgICAgICAgaWYgKGEgPT0gbnVsbCB8fCBiID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBhID09PSBiOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChhLmxlbmd0aCAhPT0gYi5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGEubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGlmIChhW2ldICE9PSBiW2ldKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHthbnl9IGEgT2JqZWN0IHRvIGNoZWNrIGFnYWluc3QgYiBmb3IgZXF1YWxpdHkuCiAgICAgICAgICogQHBhcmFtIHthbnl9IGIgT2JqZWN0IHRvIGNoZWNrIGFnYWluc3QgYSBmb3IgZXF1YWxpdHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gd2hldGhlciBvciBub3QgdHdvIG9iamVjdHMgc2hhcmUgdGhlIHNhbWUga2V5cywgYW5kCiAgICAgICAgICogICAgICAgICAgdmFsdWVzIGFzc29jaWF0ZWQgd2l0aCB0aG9zZSBrZXlzLiBWYWx1ZXMgd2lsbCBiZSBjb21wYXJlZAogICAgICAgICAqICAgICAgICAgIHdpdGggPT09LgogICAgICAgICAqLwogICAgICAgIE1ldGhvZHMub2JqRXEgPSBmdW5jdGlvbiAoYSwgYikgewogICAgICAgICAgICBpZiAoYSA9PSBudWxsIHx8IGIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGEgPT09IGI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGtleXNBID0gT2JqZWN0LmtleXMoYSkuc29ydCgpOwogICAgICAgICAgICB2YXIga2V5c0IgPSBPYmplY3Qua2V5cyhiKS5zb3J0KCk7CiAgICAgICAgICAgIHZhciB2YWx1ZXNBID0ga2V5c0EubWFwKGZ1bmN0aW9uIChrKSB7IHJldHVybiBhW2tdOyB9KTsKICAgICAgICAgICAgdmFyIHZhbHVlc0IgPSBrZXlzQi5tYXAoZnVuY3Rpb24gKGspIHsgcmV0dXJuIGJba107IH0pOwogICAgICAgICAgICByZXR1cm4gTWV0aG9kcy5hcnJheUVxKGtleXNBLCBrZXlzQikgJiYgTWV0aG9kcy5hcnJheUVxKHZhbHVlc0EsIHZhbHVlc0IpOwogICAgICAgIH07CiAgICAgICAgTWV0aG9kcy5zdHJpY3RFcSA9IGZ1bmN0aW9uIChhLCBiKSB7CiAgICAgICAgICAgIHJldHVybiBhID09PSBiOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogU2hpbSBmb3IgXy5kZWZhdWx0cwogICAgICAgICAqLwogICAgICAgIE1ldGhvZHMuZGVmYXVsdHMgPSBmdW5jdGlvbiAodGFyZ2V0KSB7CiAgICAgICAgICAgIHZhciBvYmplY3RzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIF9pID0gMTsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgICAgICBvYmplY3RzW19pIC0gMV0gPSBhcmd1bWVudHNbX2ldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0YXJnZXQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcigiQ2Fubm90IGNvbnZlcnQgdW5kZWZpbmVkIG9yIG51bGwgdG8gb2JqZWN0Iik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHJlc3VsdCA9IE9iamVjdCh0YXJnZXQpOwogICAgICAgICAgICBvYmplY3RzLmZvckVhY2goZnVuY3Rpb24gKG9iaikgewogICAgICAgICAgICAgICAgaWYgKG9iaiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgZm9yICh2YXIga2V5IGluIG9iaikgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKG9iaiwga2V5KSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzdWx0W2tleV0gPSBvYmpba2V5XTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gTWV0aG9kczsKICAgIH0oKSk7CiAgICBleHBvcnRzLk1ldGhvZHMgPSBNZXRob2RzOwoKICAgIH0pOwoKICAgIHZhciBzdHJpbmdNZXRob2RzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgU3RyaW5nTWV0aG9kcyA9IChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gU3RyaW5nTWV0aG9kcygpIHsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogVHJlYXQgYWxsIHNlcXVlbmNlcyBvZiBjb25zZWN1dGl2ZSBzcGFjZXMgYXMgYSBzaW5nbGUgIiAiLgogICAgICAgICAqLwogICAgICAgIFN0cmluZ01ldGhvZHMuY29tYmluZVdoaXRlc3BhY2UgPSBmdW5jdGlvbiAoc3RyKSB7CiAgICAgICAgICAgIHJldHVybiBzdHIucmVwbGFjZSgvWyBcdF0rL2csICIgIik7CiAgICAgICAgfTsKICAgICAgICBTdHJpbmdNZXRob2RzLmlzTm90RW1wdHlTdHJpbmcgPSBmdW5jdGlvbiAoc3RyKSB7CiAgICAgICAgICAgIHJldHVybiBzdHIgJiYgc3RyLnRyaW0oKSAhPT0gIiI7CiAgICAgICAgfTsKICAgICAgICBTdHJpbmdNZXRob2RzLnRyaW1TdGFydCA9IGZ1bmN0aW9uIChzdHIsIHNwbGl0dGVyKSB7CiAgICAgICAgICAgIGlmICghc3RyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gc3RyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBjaGFycyA9IHN0ci5zcGxpdCgiIik7CiAgICAgICAgICAgIHZhciByZWR1Y2VGdW5jdGlvbiA9IHNwbGl0dGVyID8gZnVuY3Rpb24gKHMpIHsgcmV0dXJuIHMuc3BsaXQoc3BsaXR0ZXIpLnNvbWUoU3RyaW5nTWV0aG9kcy5pc05vdEVtcHR5U3RyaW5nKTsgfQogICAgICAgICAgICAgICAgOiBTdHJpbmdNZXRob2RzLmlzTm90RW1wdHlTdHJpbmc7CiAgICAgICAgICAgIHJldHVybiBjaGFycy5yZWR1Y2UoZnVuY3Rpb24gKHMsIGMpIHsgcmV0dXJuIHJlZHVjZUZ1bmN0aW9uKHMgKyBjKSA/IHMgKyBjIDogczsgfSwgIiIpOwogICAgICAgIH07CiAgICAgICAgU3RyaW5nTWV0aG9kcy50cmltRW5kID0gZnVuY3Rpb24gKHN0ciwgYykgewogICAgICAgICAgICBpZiAoIXN0cikgewogICAgICAgICAgICAgICAgcmV0dXJuIHN0cjsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgcmV2ZXJzZWRDaGFycyA9IHN0ci5zcGxpdCgiIik7CiAgICAgICAgICAgIHJldmVyc2VkQ2hhcnMucmV2ZXJzZSgpOwogICAgICAgICAgICByZXZlcnNlZENoYXJzID0gU3RyaW5nTWV0aG9kcy50cmltU3RhcnQocmV2ZXJzZWRDaGFycy5qb2luKCIiKSwgYykuc3BsaXQoIiIpOwogICAgICAgICAgICByZXZlcnNlZENoYXJzLnJldmVyc2UoKTsKICAgICAgICAgICAgcmV0dXJuIHJldmVyc2VkQ2hhcnMuam9pbigiIik7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gU3RyaW5nTWV0aG9kczsKICAgIH0oKSk7CiAgICBleHBvcnRzLlN0cmluZ01ldGhvZHMgPSBTdHJpbmdNZXRob2RzOwoKICAgIH0pOwoKICAgIHZhciB0b2tlbml6ZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIExpY2Vuc2UgKHRoZSAiTGljZW5zZSIpOyB5b3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlCiAgICAgKiBsaWNlbnNlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci90eXBlc2V0dGFibGUvYmxvYi9kZXZlbG9wL0xJQ0VOU0UKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIHZhciBUb2tlbml6ZXIgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFRva2VuaXplcigpIHsKICAgICAgICAgICAgdGhpcy5Xb3JkRGl2aWRlclJlZ0V4cCA9IG5ldyBSZWdFeHAoIlxcVyIpOwogICAgICAgICAgICB0aGlzLldoaXRlc3BhY2VSZWdFeHAgPSBuZXcgUmVnRXhwKCJcXHMiKTsKICAgICAgICB9CiAgICAgICAgVG9rZW5pemVyLnByb3RvdHlwZS50b2tlbml6ZSA9IGZ1bmN0aW9uIChsaW5lKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHJldHVybiBsaW5lLnNwbGl0KCIiKS5yZWR1Y2UoZnVuY3Rpb24gKHRva2VucywgYykgewogICAgICAgICAgICAgICAgcmV0dXJuIHRva2Vucy5zbGljZSgwLCAtMSkuY29uY2F0KF90aGlzLnNob3VsZENyZWF0ZU5ld1Rva2VuKHRva2Vuc1t0b2tlbnMubGVuZ3RoIC0gMV0sIGMpKTsKICAgICAgICAgICAgfSwgWyIiXSk7CiAgICAgICAgfTsKICAgICAgICBUb2tlbml6ZXIucHJvdG90eXBlLnNob3VsZENyZWF0ZU5ld1Rva2VuID0gZnVuY3Rpb24gKHRva2VuLCBuZXdDaGFyYWN0ZXIpIHsKICAgICAgICAgICAgaWYgKCF0b2tlbikgewogICAgICAgICAgICAgICAgcmV0dXJuIFtuZXdDaGFyYWN0ZXJdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBsYXN0Q2hhcmFjdGVyID0gdG9rZW5bdG9rZW4ubGVuZ3RoIC0gMV07CiAgICAgICAgICAgIGlmICh0aGlzLldoaXRlc3BhY2VSZWdFeHAudGVzdChsYXN0Q2hhcmFjdGVyKSAmJiB0aGlzLldoaXRlc3BhY2VSZWdFeHAudGVzdChuZXdDaGFyYWN0ZXIpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW3Rva2VuICsgbmV3Q2hhcmFjdGVyXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0aGlzLldoaXRlc3BhY2VSZWdFeHAudGVzdChsYXN0Q2hhcmFjdGVyKSB8fCB0aGlzLldoaXRlc3BhY2VSZWdFeHAudGVzdChuZXdDaGFyYWN0ZXIpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW3Rva2VuLCBuZXdDaGFyYWN0ZXJdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKCEodGhpcy5Xb3JkRGl2aWRlclJlZ0V4cC50ZXN0KGxhc3RDaGFyYWN0ZXIpKSkgewogICAgICAgICAgICAgICAgcmV0dXJuIFt0b2tlbiArIG5ld0NoYXJhY3Rlcl07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAobGFzdENoYXJhY3RlciA9PT0gbmV3Q2hhcmFjdGVyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW3Rva2VuICsgbmV3Q2hhcmFjdGVyXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBbdG9rZW4sIG5ld0NoYXJhY3Rlcl07CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBUb2tlbml6ZXI7CiAgICB9KCkpOwogICAgZXhwb3J0cy5Ub2tlbml6ZXIgPSBUb2tlbml6ZXI7CgogICAgfSk7CgogICAgdmFyIHV0aWxzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIGZ1bmN0aW9uIF9fZXhwb3J0KG0pIHsKICAgICAgICBmb3IgKHZhciBwIGluIG0pIGlmICghZXhwb3J0cy5oYXNPd25Qcm9wZXJ0eShwKSkgZXhwb3J0c1twXSA9IG1bcF07CiAgICB9CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgX19leHBvcnQoY2FjaGUpOwogICAgX19leHBvcnQobWV0aG9kcyk7CiAgICBfX2V4cG9ydChzdHJpbmdNZXRob2RzKTsKICAgIF9fZXhwb3J0KHRva2VuaXplcik7CgogICAgfSk7CgogICAgdmFyIHdyaXRlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMsIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgICAqIExpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgTGljZW5zZSAodGhlICJMaWNlbnNlIik7IHlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUKICAgICAqIGxpY2Vuc2UgYXQgaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3R5cGVzZXR0YWJsZS9ibG9iL2RldmVsb3AvTElDRU5TRQogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBERUZBVUxUX1dSSVRFX09QVElPTlMgPSB7CiAgICAgICAgdGV4dFJvdGF0aW9uOiAwLAogICAgICAgIHRleHRTaGVhcjogMCwKICAgICAgICB4QWxpZ246ICJsZWZ0IiwKICAgICAgICB5QWxpZ246ICJ0b3AiLAogICAgfTsKICAgIHZhciBXcml0ZXIgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFdyaXRlcihfbWVhc3VyZXIsIF9wZW5GYWN0b3J5LCBfd3JhcHBlcikgewogICAgICAgICAgICB0aGlzLl9tZWFzdXJlciA9IF9tZWFzdXJlcjsKICAgICAgICAgICAgdGhpcy5fcGVuRmFjdG9yeSA9IF9wZW5GYWN0b3J5OwogICAgICAgICAgICB0aGlzLl93cmFwcGVyID0gX3dyYXBwZXI7CiAgICAgICAgfQogICAgICAgIFdyaXRlci5wcm90b3R5cGUubWVhc3VyZXIgPSBmdW5jdGlvbiAobmV3TWVhc3VyZXIpIHsKICAgICAgICAgICAgdGhpcy5fbWVhc3VyZXIgPSBuZXdNZWFzdXJlcjsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBXcml0ZXIucHJvdG90eXBlLndyYXBwZXIgPSBmdW5jdGlvbiAobmV3V3JhcHBlcikgewogICAgICAgICAgICB0aGlzLl93cmFwcGVyID0gbmV3V3JhcHBlcjsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBXcml0ZXIucHJvdG90eXBlLnBlbkZhY3RvcnkgPSBmdW5jdGlvbiAobmV3UGVuRmFjdG9yeSkgewogICAgICAgICAgICB0aGlzLl9wZW5GYWN0b3J5ID0gbmV3UGVuRmFjdG9yeTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBXcml0ZXMgdGhlIHRleHQgaW50byB0aGUgY29udGFpbmVyLiBJZiBubyBjb250YWluZXIgaXMgc3BlY2lmaWVkLCB0aGUgcGVuJ3MKICAgICAgICAgKiBkZWZhdWx0IGNvbnRhaW5lciB3aWxsIGJlIHVzZWQuCiAgICAgICAgICovCiAgICAgICAgV3JpdGVyLnByb3RvdHlwZS53cml0ZSA9IGZ1bmN0aW9uICh0ZXh0LCB3aWR0aCwgaGVpZ2h0LCBvcHRpb25zLCBjb250YWluZXIpIHsKICAgICAgICAgICAgaWYgKG9wdGlvbnMgPT09IHZvaWQgMCkgeyBvcHRpb25zID0ge307IH0KICAgICAgICAgICAgLy8gYXBwbHkgZGVmYXVsdCBvcHRpb25zCiAgICAgICAgICAgIG9wdGlvbnMgPSB1dGlscy5NZXRob2RzLmRlZmF1bHRzKHt9LCBERUZBVUxUX1dSSVRFX09QVElPTlMsIG9wdGlvbnMpOwogICAgICAgICAgICAvLyB2YWxpZGF0ZSBpbnB1dAogICAgICAgICAgICBpZiAoV3JpdGVyLlN1cHBvcnRlZFJvdGF0aW9uLmluZGV4T2Yob3B0aW9ucy50ZXh0Um90YXRpb24pID09PSAtMSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJ1bnN1cHBvcnRlZCByb3RhdGlvbiAtICIgKyBvcHRpb25zLnRleHRSb3RhdGlvbiArCiAgICAgICAgICAgICAgICAgICAgIi4gU3VwcG9ydGVkIHJvdGF0aW9ucyBhcmUgIiArIFdyaXRlci5TdXBwb3J0ZWRSb3RhdGlvbi5qb2luKCIsICIpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob3B0aW9ucy50ZXh0U2hlYXIgIT0gbnVsbCAmJiBvcHRpb25zLnRleHRTaGVhciA8IC04MCB8fCBvcHRpb25zLnRleHRTaGVhciA+IDgwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoInVuc3VwcG9ydGVkIHNoZWFyIGFuZ2xlIC0gIiArIG9wdGlvbnMudGV4dFNoZWFyICsgIi4gTXVzdCBiZSBiZXR3ZWVuIC04MCBhbmQgODAiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgb3JpZW50SG9yaXpvbnRhbGx5ID0gTWF0aC5hYnMoTWF0aC5hYnMob3B0aW9ucy50ZXh0Um90YXRpb24pIC0gOTApID4gNDU7CiAgICAgICAgICAgIHZhciBwcmltYXJ5RGltZW5zaW9uID0gb3JpZW50SG9yaXpvbnRhbGx5ID8gd2lkdGggOiBoZWlnaHQ7CiAgICAgICAgICAgIHZhciBzZWNvbmRhcnlEaW1lbnNpb24gPSBvcmllbnRIb3Jpem9udGFsbHkgPyBoZWlnaHQgOiB3aWR0aDsKICAgICAgICAgICAgLy8gY29tcHV0ZSBzaGVhciBwYXJhbWV0ZXJzCiAgICAgICAgICAgIHZhciBzaGVhckRlZ3JlZXMgPSBvcHRpb25zLnRleHRTaGVhcjsKICAgICAgICAgICAgdmFyIHNoZWFyUmFkaWFucyA9IHNoZWFyRGVncmVlcyAqIE1hdGguUEkgLyAxODA7CiAgICAgICAgICAgIHZhciBsaW5lSGVpZ2h0ID0gdGhpcy5fbWVhc3VyZXIubWVhc3VyZSgpLmhlaWdodDsKICAgICAgICAgICAgdmFyIHNoZWFyU2hpZnQgPSBsaW5lSGVpZ2h0ICogTWF0aC50YW4oc2hlYXJSYWRpYW5zKTsKICAgICAgICAgICAgLy8gV2hlbiB3ZSBhcHBseSB0ZXh0IHNoZWFyLCB0aGUgcHJpbWFyeSBheGlzIGdyb3dzIGFuZCB0aGUgc2Vjb25kYXJ5IGF4aXMKICAgICAgICAgICAgLy8gc2hyaW5rcywgZHVlIHRvIHRyaWdvbm9tZXRyeS4gVGhlIHRleHQgc2hlYXIgZmVhdHVyZSB1c2VzIHRoZSBub3JtYWwKICAgICAgICAgICAgLy8gd3JhcHBpbmcgbG9naWMgd2l0aCBhIHN1YnNpdHV0ZWQgYm91bmRpbmcgYm94IG9mIHRoZSBjb3JyZWN0ZWQgc2l6ZQogICAgICAgICAgICAvLyAoY29tcHV0ZWQgYmVsb3cpLiBXaGVuIHJlbmRlcmluZyB0aGUgd3JhcHBlZCBsaW5lcywgd2Ugcm90YXRlIHRoZSB0ZXh0CiAgICAgICAgICAgIC8vIGNvbnRhaW5lciBieSB0aGUgdGV4dCByb3RhdGlvbiBhbmdsZSBBTkQgdGhlIHNoZWFyIGFuZ2xlIHRoZW4gY2FyZWZ1bGx5CiAgICAgICAgICAgIC8vIG9mZnNldCBlYWNoIG9uZSBzbyB0aGF0IHRoZXkgYXJlIHN0aWxsIGFsaWduZWQgdG8gdGhlIHByaW1hcnkgYWxpZ25tZW50CiAgICAgICAgICAgIC8vIG9wdGlvbi4KICAgICAgICAgICAgdmFyIHNoZWFyQ29ycmVjdGVkUHJpbWFyeURpbWVuc2lvbiA9IHByaW1hcnlEaW1lbnNpb24gLyBNYXRoLmNvcyhzaGVhclJhZGlhbnMpIC0gTWF0aC5hYnMoc2hlYXJTaGlmdCk7CiAgICAgICAgICAgIHZhciBzaGVhckNvcnJlY3RlZFNlY29uZGFyeURpbWVuc2lvbiA9IHNlY29uZGFyeURpbWVuc2lvbiAqIE1hdGguY29zKHNoZWFyUmFkaWFucyk7CiAgICAgICAgICAgIC8vIG5vcm1hbGl6ZSBhbmQgd3JhcCB0ZXh0CiAgICAgICAgICAgIHZhciBub3JtYWxpemVkVGV4dCA9IHV0aWxzLlN0cmluZ01ldGhvZHMuY29tYmluZVdoaXRlc3BhY2UodGV4dCk7CiAgICAgICAgICAgIHZhciB3cmFwcGVkVGV4dCA9IHRoaXMuX3dyYXBwZXIgPwogICAgICAgICAgICAgICAgdGhpcy5fd3JhcHBlci53cmFwKG5vcm1hbGl6ZWRUZXh0LCB0aGlzLl9tZWFzdXJlciwgc2hlYXJDb3JyZWN0ZWRQcmltYXJ5RGltZW5zaW9uLCBzaGVhckNvcnJlY3RlZFNlY29uZGFyeURpbWVuc2lvbikud3JhcHBlZFRleHQgOiBub3JtYWxpemVkVGV4dDsKICAgICAgICAgICAgdmFyIGxpbmVzID0gd3JhcHBlZFRleHQuc3BsaXQoIlxuIik7CiAgICAgICAgICAgIC8vIGNvcnJlY3QgdGhlIGludGlhbCB4L3kgb2Zmc2V0IG9mIHRoZSB0ZXh0IGNvbnRhaW5lciBhY2NvdW50aW5nIHNoZWFyIGFuZCBhbGlnbm1lbnQKICAgICAgICAgICAgdmFyIHNoZWFyQ29ycmVjdGVkWE9mZnNldCA9IFdyaXRlci5YT2Zmc2V0RmFjdG9yW29wdGlvbnMueEFsaWduXSAqCiAgICAgICAgICAgICAgICBzaGVhckNvcnJlY3RlZFByaW1hcnlEaW1lbnNpb24gKiBNYXRoLnNpbihzaGVhclJhZGlhbnMpOwogICAgICAgICAgICB2YXIgc2hlYXJDb3JyZWN0ZWRZT2Zmc2V0ID0gV3JpdGVyLllPZmZzZXRGYWN0b3Jbb3B0aW9ucy55QWxpZ25dICoKICAgICAgICAgICAgICAgIChzaGVhckNvcnJlY3RlZFNlY29uZGFyeURpbWVuc2lvbiAtIGxpbmVzLmxlbmd0aCAqIGxpbmVIZWlnaHQpOwogICAgICAgICAgICB2YXIgc2hlYXJDb3JyZWN0aW9uID0gc2hlYXJDb3JyZWN0ZWRYT2Zmc2V0IC0gc2hlYXJDb3JyZWN0ZWRZT2Zmc2V0OwogICAgICAgICAgICAvLyBjb21wdXRlIHRyYW5zZm9ybQogICAgICAgICAgICB2YXIgdHJhbnNsYXRlID0gWzAsIDBdOwogICAgICAgICAgICB2YXIgcm90YXRlID0gb3B0aW9ucy50ZXh0Um90YXRpb24gKyBzaGVhckRlZ3JlZXM7CiAgICAgICAgICAgIHN3aXRjaCAob3B0aW9ucy50ZXh0Um90YXRpb24pIHsKICAgICAgICAgICAgICAgIGNhc2UgOTA6CiAgICAgICAgICAgICAgICAgICAgdHJhbnNsYXRlID0gW3dpZHRoICsgc2hlYXJDb3JyZWN0aW9uLCAwXTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgLTkwOgogICAgICAgICAgICAgICAgICAgIHRyYW5zbGF0ZSA9IFstc2hlYXJDb3JyZWN0aW9uLCBoZWlnaHRdOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAxODA6CiAgICAgICAgICAgICAgICAgICAgdHJhbnNsYXRlID0gW3dpZHRoLCBoZWlnaHQgKyBzaGVhckNvcnJlY3Rpb25dOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICB0cmFuc2xhdGUgPSBbMCwgLXNoZWFyQ29ycmVjdGlvbl07CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gY3JlYXRlIGEgbmV3IHBlbiBhbmQgd3JpdGUgdGhlIGxpbmVzCiAgICAgICAgICAgIHZhciBsaW5lUGVuID0gdGhpcy5fcGVuRmFjdG9yeS5jcmVhdGVQZW4odGV4dCwgeyB0cmFuc2xhdGU6IHRyYW5zbGF0ZSwgcm90YXRlOiByb3RhdGUgfSwgY29udGFpbmVyKTsKICAgICAgICAgICAgdGhpcy53cml0ZUxpbmVzKGxpbmVzLCBsaW5lUGVuLCBzaGVhckNvcnJlY3RlZFByaW1hcnlEaW1lbnNpb24sIGxpbmVIZWlnaHQsIHNoZWFyU2hpZnQsIG9wdGlvbnMueEFsaWduKTsKICAgICAgICAgICAgaWYgKGxpbmVQZW4uZGVzdHJveSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBsaW5lUGVuLmRlc3Ryb3koKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgV3JpdGVyLnByb3RvdHlwZS53cml0ZUxpbmVzID0gZnVuY3Rpb24gKGxpbmVzLCBsaW5lUGVuLCB3aWR0aCwgbGluZUhlaWdodCwgc2hlYXJTaGlmdCwgeEFsaWduKSB7CiAgICAgICAgICAgIGxpbmVzLmZvckVhY2goZnVuY3Rpb24gKGxpbmUsIGkpIHsKICAgICAgICAgICAgICAgIHZhciB4U2hlYXJPZmZzZXQgPSAoc2hlYXJTaGlmdCA+IDApID8gKGkgKyAxKSAqIHNoZWFyU2hpZnQgOiAoaSkgKiBzaGVhclNoaWZ0OwogICAgICAgICAgICAgICAgbGluZVBlbi53cml0ZShsaW5lLCB3aWR0aCwgeEFsaWduLCB4U2hlYXJPZmZzZXQsIChpICsgMSkgKiBsaW5lSGVpZ2h0KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gV3JpdGVyOwogICAgfSgpKTsKICAgIFdyaXRlci5YT2Zmc2V0RmFjdG9yID0gewogICAgICAgIGNlbnRlcjogMC41LAogICAgICAgIGxlZnQ6IDAsCiAgICAgICAgcmlnaHQ6IDEsCiAgICB9OwogICAgV3JpdGVyLllPZmZzZXRGYWN0b3IgPSB7CiAgICAgICAgYm90dG9tOiAxLAogICAgICAgIGNlbnRlcjogMC41LAogICAgICAgIHRvcDogMCwKICAgIH07CiAgICBXcml0ZXIuU3VwcG9ydGVkUm90YXRpb24gPSBbLTkwLCAwLCAxODAsIDkwXTsKICAgIGV4cG9ydHMuV3JpdGVyID0gV3JpdGVyOwoKICAgIH0pOwoKICAgIHZhciB3cml0ZXJzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIGZ1bmN0aW9uIF9fZXhwb3J0KG0pIHsKICAgICAgICBmb3IgKHZhciBwIGluIG0pIGlmICghZXhwb3J0cy5oYXNPd25Qcm9wZXJ0eShwKSkgZXhwb3J0c1twXSA9IG1bcF07CiAgICB9CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgX19leHBvcnQod3JpdGVyKTsKCiAgICB9KTsKCiAgICB2YXIgaHRtbCQzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgSHRtbFV0aWxzID0gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBIdG1sVXRpbHMoKSB7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEFwcGVuZHMgYW4gSFRNTCBlbGVtZW50IHdpdGggdGhlIHNwZWNpZmllZCB0YWcgbmFtZSB0byB0aGUgcHJvdmlkZWQgZWxlbWVudC4KICAgICAgICAgKiBUaGUgdmFyaWFkaWMgY2xhc3NuYW1lcyBhcmUgYWRkZWQgdG8gdGhlIG5ldyBlbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogUmV0dXJucyB0aGUgbmV3IGVsZW1lbnQuCiAgICAgICAgICovCiAgICAgICAgSHRtbFV0aWxzLmFwcGVuZCA9IGZ1bmN0aW9uIChlbGVtZW50LCB0YWdOYW1lKSB7CiAgICAgICAgICAgIHZhciBjbGFzc05hbWVzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIF9pID0gMjsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgICAgICBjbGFzc05hbWVzW19pIC0gMl0gPSBhcmd1bWVudHNbX2ldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBjaGlsZCA9IEh0bWxVdGlscy5jcmVhdGUuYXBwbHkoSHRtbFV0aWxzLCBbdGFnTmFtZV0uY29uY2F0KGNsYXNzTmFtZXMpKTsKICAgICAgICAgICAgZWxlbWVudC5hcHBlbmRDaGlsZChjaGlsZCk7CiAgICAgICAgICAgIHJldHVybiBjaGlsZDsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW5kIHJldHVybnMgYSBuZXcgSFRNTEVsZW1lbnQgd2l0aCB0aGUgYXR0YWNoZWQgY2xhc3NuYW1lcy4KICAgICAgICAgKi8KICAgICAgICBIdG1sVXRpbHMuY3JlYXRlID0gZnVuY3Rpb24gKHRhZ05hbWUpIHsKICAgICAgICAgICAgdmFyIGNsYXNzTmFtZXMgPSBbXTsKICAgICAgICAgICAgZm9yICh2YXIgX2kgPSAxOyBfaSA8IGFyZ3VtZW50cy5sZW5ndGg7IF9pKyspIHsKICAgICAgICAgICAgICAgIGNsYXNzTmFtZXNbX2kgLSAxXSA9IGFyZ3VtZW50c1tfaV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KHRhZ05hbWUpOwogICAgICAgICAgICBIdG1sVXRpbHMuYWRkQ2xhc3Nlcy5hcHBseShIdG1sVXRpbHMsIFtlbGVtZW50XS5jb25jYXQoY2xhc3NOYW1lcykpOwogICAgICAgICAgICByZXR1cm4gZWxlbWVudDsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgdGhlIHZhcmlhZGljIGNsYXNzbmFtZXMgdG8gdGhlIEVsZW1lbnQKICAgICAgICAgKi8KICAgICAgICBIdG1sVXRpbHMuYWRkQ2xhc3NlcyA9IGZ1bmN0aW9uIChlbGVtZW50KSB7CiAgICAgICAgICAgIHZhciBjbGFzc05hbWVzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIF9pID0gMTsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgICAgICBjbGFzc05hbWVzW19pIC0gMV0gPSBhcmd1bWVudHNbX2ldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNsYXNzTmFtZXMgPSBjbGFzc05hbWVzLmZpbHRlcihmdW5jdGlvbiAoYykgeyByZXR1cm4gYyAhPSBudWxsOyB9KTsKICAgICAgICAgICAgaWYgKGVsZW1lbnQuY2xhc3NMaXN0ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGNsYXNzTmFtZXMuZm9yRWFjaChmdW5jdGlvbiAoY2xhc3NOYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgZWxlbWVudC5jbGFzc0xpc3QuYWRkKGNsYXNzTmFtZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIElFIDExIGRvZXMgbm90IHN1cHBvcnQgY2xhc3NMaXN0CiAgICAgICAgICAgICAgICBlbGVtZW50LnNldEF0dHJpYnV0ZSgiY2xhc3MiLCBjbGFzc05hbWVzLmpvaW4oIiAiKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIHdpZHRoL2hlaWdodCBvZiBIVE1MRWxlbWVudCdzIGJvdW5kaW5nIGJveAogICAgICAgICAqLwogICAgICAgIEh0bWxVdGlscy5nZXREaW1lbnNpb25zID0gZnVuY3Rpb24gKGVsZW1lbnQpIHsKICAgICAgICAgICAgLy8gdXNpbmcgZmVhdHVyZSBkZXRlY3Rpb24sIHNhZmVseSByZXR1cm4gdGhlIGJvdW5kaW5nIGJveCBkaW1lbnNpb25zIG9mIHRoZQogICAgICAgICAgICAvLyBwcm92aWRlZCBodG1sIGVsZW1lbnQKICAgICAgICAgICAgaWYgKGVsZW1lbnQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KSB7CiAgICAgICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgICAgIHZhciBfYSA9IGVsZW1lbnQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCksIHdpZHRoID0gX2Eud2lkdGgsIGhlaWdodCA9IF9hLmhlaWdodDsKICAgICAgICAgICAgICAgICAgICAvLyBjb3B5IHRvIHByZXZlbnQgTm9Nb2RpZmljYXRpb25BbGxvd2VkRXJyb3IKICAgICAgICAgICAgICAgICAgICByZXR1cm4geyB3aWR0aDogd2lkdGgsIGhlaWdodDogaGVpZ2h0IH07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXRjaCAoZXJyKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gc3dhbGxvdyBhbnkgZXJyb3JzIHRoYXQgb2NjdXIgKEZpcmVmb3ggTGludXgpCiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gaWYgY2FuJ3QgZ2V0IHZhbGlkIGJib3gsIHJldHVybiAwLDAKICAgICAgICAgICAgcmV0dXJuIHsgaGVpZ2h0OiAwLCB3aWR0aDogMCB9OwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEh0bWxVdGlsczsKICAgIH0oKSk7CiAgICBleHBvcnRzLkh0bWxVdGlscyA9IEh0bWxVdGlsczsKICAgIC8qKgogICAgICogQSB0eXBlc2V0dGVyIGNvbnRleHQgZm9yIEhUTUwuCiAgICAgKi8KICAgIHZhciBIdG1sQ29udGV4dCA9IChmdW5jdGlvbiAoKSB7CiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIGVsZW1lbnQgLSBUaGUgQ1NTIGZvbnQgc3R5bGVzIGFwcGxpZWQgdG8gYGVsZW1lbnRgIHdpbGwgZGV0ZXJtaW5lIHRoZQogICAgICAgICAqIHNpemUgb2YgdGV4dCBtZWFzdXJlbWVudHMuIEFsc28gdGhlIGRlZmF1bHQgdGV4dCBibG9jayBjb250YWluZXIuCiAgICAgICAgICogQHBhcmFtIGNsYXNzTmFtZSAtIGFkZGVkIHRvIG5ldyB0ZXh0IGJsb2NrcwogICAgICAgICAqIEBwYXJhbSBhZGRUaXRsZSAtIGVuYWJsZSB0aXRsZSBhdHRyaWJ1dGUgdG8gYmUgYWRkZWQgdG8gbmV3IHRleHQgYmxvY2tzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIEh0bWxDb250ZXh0KGVsZW1lbnQsIGNsYXNzTmFtZSwgYWRkVGl0bGUpIHsKICAgICAgICAgICAgaWYgKGFkZFRpdGxlID09PSB2b2lkIDApIHsgYWRkVGl0bGUgPSBmYWxzZTsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB0aGlzLmVsZW1lbnQgPSBlbGVtZW50OwogICAgICAgICAgICB0aGlzLmNsYXNzTmFtZSA9IGNsYXNzTmFtZTsKICAgICAgICAgICAgdGhpcy5hZGRUaXRsZSA9IGFkZFRpdGxlOwogICAgICAgICAgICB0aGlzLmNyZWF0ZVJ1bGVyID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICh0ZXh0KSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHRleHRFbGVtZW50ID0gSHRtbFV0aWxzLmFwcGVuZChfdGhpcy5lbGVtZW50LCAic3BhbiIsICJ0ZXh0LXRtcCIsIF90aGlzLmNsYXNzTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgdGV4dEVsZW1lbnQudGV4dENvbnRlbnQgPSB0ZXh0OwogICAgICAgICAgICAgICAgICAgIHZhciBkaW1lbnNpb25zID0gSHRtbFV0aWxzLmdldERpbWVuc2lvbnModGV4dEVsZW1lbnQpOwogICAgICAgICAgICAgICAgICAgIF90aGlzLmVsZW1lbnQucmVtb3ZlQ2hpbGQodGV4dEVsZW1lbnQpOyAvLyBlbGVtZW50LnJlbW92ZSgpIGRvZXNuJ3Qgd29yayBpbiBJRTExCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGRpbWVuc2lvbnM7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLmNyZWF0ZVBlbiA9IGZ1bmN0aW9uICh0ZXh0LCB0cmFuc2Zvcm0sIGVsZW1lbnQpIHsKICAgICAgICAgICAgICAgIGlmIChlbGVtZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBlbGVtZW50ID0gX3RoaXMuZWxlbWVudDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciB0ZXh0QmxvY2sgPSBIdG1sVXRpbHMuYXBwZW5kKGVsZW1lbnQsICJkaXYiLCAidGV4dC1ibG9jayIsIF90aGlzLmNsYXNzTmFtZSk7CiAgICAgICAgICAgICAgICB0ZXh0QmxvY2suc3R5bGUucG9zaXRpb24gPSAicmVsYXRpdmUiOwogICAgICAgICAgICAgICAgdGV4dEJsb2NrLnN0eWxlLnRyYW5zZm9ybSA9CiAgICAgICAgICAgICAgICAgICAgInRyYW5zbGF0ZSgwLCAtMWVtKSAiICsKICAgICAgICAgICAgICAgICAgICAgICAgKCJ0cmFuc2xhdGUoIiArIHRyYW5zZm9ybS50cmFuc2xhdGVbMF0gKyAicHgsICIgKyB0cmFuc2Zvcm0udHJhbnNsYXRlWzFdICsgInB4KSAiKSArCiAgICAgICAgICAgICAgICAgICAgICAgICgicm90YXRlKCIgKyB0cmFuc2Zvcm0ucm90YXRlICsgImRlZykiKTsKICAgICAgICAgICAgICAgIC8vIFRoaXMgYXdrd2FyZCB0cmFuc2Zvcm0gb3JpZ2luIG1hdGNoZXMgdGhlIFNWRyBvcmlnaW4KICAgICAgICAgICAgICAgIHRleHRCbG9jay5zdHlsZS50cmFuc2Zvcm1PcmlnaW4gPSAiMCAxLjJlbSI7CiAgICAgICAgICAgICAgICAvLyBhdHRhY2ggb3B0aW9uYWwgdGl0bGUKICAgICAgICAgICAgICAgIGlmIChfdGhpcy5hZGRUaXRsZSkgewogICAgICAgICAgICAgICAgICAgIHRleHRCbG9jay5zZXRBdHRyaWJ1dGUoInRpdGxlIiwgdGV4dCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuY3JlYXRlSHRtbExpbmVQZW4odGV4dEJsb2NrKTsKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgSHRtbENvbnRleHQucHJvdG90eXBlLnNldEFkZFRpdGxlID0gZnVuY3Rpb24gKGFkZFRpdGxlKSB7CiAgICAgICAgICAgIHRoaXMuYWRkVGl0bGUgPSBhZGRUaXRsZTsKICAgICAgICB9OwogICAgICAgIEh0bWxDb250ZXh0LnByb3RvdHlwZS5jcmVhdGVIdG1sTGluZVBlbiA9IGZ1bmN0aW9uICh0ZXh0QmxvY2spIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHdyaXRlOiBmdW5jdGlvbiAobGluZSwgd2lkdGgsIHhBbGlnbiwgeE9mZnNldCwgeU9mZnNldCkgewogICAgICAgICAgICAgICAgICAgIHZhciB0ZXh0TGluZSA9IEh0bWxVdGlscy5hcHBlbmQodGV4dEJsb2NrLCAiZGl2IiwgInRleHQtbGluZSIpOwogICAgICAgICAgICAgICAgICAgIHRleHRMaW5lLnRleHRDb250ZW50ID0gbGluZTsKICAgICAgICAgICAgICAgICAgICB0ZXh0TGluZS5zdHlsZS53aWR0aCA9IHdpZHRoICsgInB4IjsKICAgICAgICAgICAgICAgICAgICB0ZXh0TGluZS5zdHlsZS50ZXh0QWxpZ24gPSB4QWxpZ247CiAgICAgICAgICAgICAgICAgICAgdGV4dExpbmUuc3R5bGUucG9zaXRpb24gPSAiYWJzb2x1dGUiOwogICAgICAgICAgICAgICAgICAgIHRleHRMaW5lLnN0eWxlLndoaXRlU3BhY2UgPSAibm93cmFwIjsKICAgICAgICAgICAgICAgICAgICB0ZXh0TGluZS5zdHlsZS50b3AgPSB5T2Zmc2V0ICsgInB4IjsKICAgICAgICAgICAgICAgICAgICB0ZXh0TGluZS5zdHlsZS5sZWZ0ID0geE9mZnNldCArICJweCI7CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEh0bWxDb250ZXh0OwogICAgfSgpKTsKICAgIGV4cG9ydHMuSHRtbENvbnRleHQgPSBIdG1sQ29udGV4dDsKCiAgICB9KTsKCiAgICB2YXIgc3ZnJDEgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIExpY2Vuc2UgKHRoZSAiTGljZW5zZSIpOyB5b3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlCiAgICAgKiBsaWNlbnNlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci90eXBlc2V0dGFibGUvYmxvYi9kZXZlbG9wL0xJQ0VOU0UKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgdmFyIFN2Z1V0aWxzID0gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBTdmdVdGlscygpIHsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQXBwZW5kcyBhbiBTVkcgZWxlbWVudCB3aXRoIHRoZSBzcGVjaWZpZWQgdGFnIG5hbWUgdG8gdGhlIHByb3ZpZGVkIGVsZW1lbnQuCiAgICAgICAgICogVGhlIHZhcmlhZGljIGNsYXNzbmFtZXMgYXJlIGFkZGVkIHRvIHRoZSBuZXcgZWxlbWVudC4KICAgICAgICAgKgogICAgICAgICAqIFJldHVybnMgdGhlIG5ldyBlbGVtZW50LgogICAgICAgICAqLwogICAgICAgIFN2Z1V0aWxzLmFwcGVuZCA9IGZ1bmN0aW9uIChlbGVtZW50LCB0YWdOYW1lKSB7CiAgICAgICAgICAgIHZhciBjbGFzc05hbWVzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIF9pID0gMjsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgICAgICBjbGFzc05hbWVzW19pIC0gMl0gPSBhcmd1bWVudHNbX2ldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBjaGlsZCA9IFN2Z1V0aWxzLmNyZWF0ZS5hcHBseShTdmdVdGlscywgW3RhZ05hbWVdLmNvbmNhdChjbGFzc05hbWVzKSk7CiAgICAgICAgICAgIGVsZW1lbnQuYXBwZW5kQ2hpbGQoY2hpbGQpOwogICAgICAgICAgICByZXR1cm4gY2hpbGQ7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGFuZCByZXR1cm5zIGEgbmV3IFNWR0VsZW1lbnQgd2l0aCB0aGUgYXR0YWNoZWQgY2xhc3NuYW1lcy4KICAgICAgICAgKi8KICAgICAgICBTdmdVdGlscy5jcmVhdGUgPSBmdW5jdGlvbiAodGFnTmFtZSkgewogICAgICAgICAgICB2YXIgY2xhc3NOYW1lcyA9IFtdOwogICAgICAgICAgICBmb3IgKHZhciBfaSA9IDE7IF9pIDwgYXJndW1lbnRzLmxlbmd0aDsgX2krKykgewogICAgICAgICAgICAgICAgY2xhc3NOYW1lc1tfaSAtIDFdID0gYXJndW1lbnRzW19pXTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgZWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTdmdVdGlscy5TVkdfTlMsIHRhZ05hbWUpOwogICAgICAgICAgICBodG1sJDMuSHRtbFV0aWxzLmFkZENsYXNzZXMuYXBwbHkoaHRtbCQzLkh0bWxVdGlscywgW2VsZW1lbnRdLmNvbmNhdChjbGFzc05hbWVzKSk7CiAgICAgICAgICAgIHJldHVybiBlbGVtZW50OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgd2lkdGgvaGVpZ2h0IG9mIHN2ZyBlbGVtZW50J3MgYm91bmRpbmcgYm94CiAgICAgICAgICovCiAgICAgICAgU3ZnVXRpbHMuZ2V0RGltZW5zaW9ucyA9IGZ1bmN0aW9uIChlbGVtZW50KSB7CiAgICAgICAgICAgIC8vIHVzaW5nIGZlYXR1cmUgZGV0ZWN0aW9uLCBzYWZlbHkgcmV0dXJuIHRoZSBib3VuZGluZyBib3ggZGltZW5zaW9ucyBvZiB0aGUKICAgICAgICAgICAgLy8gcHJvdmlkZWQgc3ZnIGVsZW1lbnQKICAgICAgICAgICAgaWYgKGVsZW1lbnQuZ2V0QkJveCkgewogICAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgICAgICB2YXIgX2EgPSBlbGVtZW50LmdldEJCb3goKSwgd2lkdGggPSBfYS53aWR0aCwgaGVpZ2h0ID0gX2EuaGVpZ2h0OwogICAgICAgICAgICAgICAgICAgIC8vIGNvcHkgdG8gcHJldmVudCBOb01vZGlmaWNhdGlvbkFsbG93ZWRFcnJvcgogICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHdpZHRoOiB3aWR0aCwgaGVpZ2h0OiBoZWlnaHQgfTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNhdGNoIChlcnIpIHsKICAgICAgICAgICAgICAgICAgICAvLyBzd2FsbG93IGFueSBlcnJvcnMgdGhhdCBvY2N1ciAoRmlyZWZveCBMaW51eCkKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBpZiBjYW4ndCBnZXQgdmFsaWQgYmJveCwgcmV0dXJuIDAsMAogICAgICAgICAgICByZXR1cm4geyBoZWlnaHQ6IDAsIHdpZHRoOiAwIH07CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gU3ZnVXRpbHM7CiAgICB9KCkpOwogICAgU3ZnVXRpbHMuU1ZHX05TID0gImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIjsKICAgIGV4cG9ydHMuU3ZnVXRpbHMgPSBTdmdVdGlsczsKICAgIC8qKgogICAgICogQSB0eXBlc2V0dGVyIGNvbnRleHQgZm9yIFNWRy4KICAgICAqCiAgICAgKiBAcGFyYW0gZWxlbWVudCAtIFRoZSBDU1MgZm9udCBzdHlsZXMgYXBwbGllZCB0byBgZWxlbWVudGAgd2lsbCBkZXRlcm1pbmUgdGhlCiAgICAgKiBzaXplIG9mIHRleHQgbWVhc3VyZW1lbnRzLiBBbHNvIHRoZSBkZWZhdWx0IHRleHQgYmxvY2sgY29udGFpbmVyLgogICAgICogQHBhcmFtIGNsYXNzTmFtZSAtIGFkZGVkIHRvIG5ldyB0ZXh0IGJsb2NrcwogICAgICogQHBhcmFtIGFkZFRpdGxlRWxlbWVudCAtIGVuYWJsZSB0aXRsZSB0YWdzIHRvIGJlIGFkZGVkIHRvIG5ldyB0ZXh0IGJsb2Nrcy4KICAgICAqLwogICAgdmFyIFN2Z0NvbnRleHQgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFN2Z0NvbnRleHQoZWxlbWVudCwgY2xhc3NOYW1lLCBhZGRUaXRsZUVsZW1lbnQpIHsKICAgICAgICAgICAgaWYgKGFkZFRpdGxlRWxlbWVudCA9PT0gdm9pZCAwKSB7IGFkZFRpdGxlRWxlbWVudCA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuZWxlbWVudCA9IGVsZW1lbnQ7CiAgICAgICAgICAgIHRoaXMuY2xhc3NOYW1lID0gY2xhc3NOYW1lOwogICAgICAgICAgICB0aGlzLmFkZFRpdGxlRWxlbWVudCA9IGFkZFRpdGxlRWxlbWVudDsKICAgICAgICAgICAgdGhpcy5jcmVhdGVSdWxlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHZhciBfYSA9IF90aGlzLmdldFRleHRFbGVtZW50cyhfdGhpcy5lbGVtZW50KSwgcGFyZW50RWxlbWVudCA9IF9hLnBhcmVudEVsZW1lbnQsIGNvbnRhaW5lckVsZW1lbnQgPSBfYS5jb250YWluZXJFbGVtZW50LCB0ZXh0RWxlbWVudCA9IF9hLnRleHRFbGVtZW50OwogICAgICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICh0ZXh0KSB7CiAgICAgICAgICAgICAgICAgICAgcGFyZW50RWxlbWVudC5hcHBlbmRDaGlsZChjb250YWluZXJFbGVtZW50KTsKICAgICAgICAgICAgICAgICAgICB0ZXh0RWxlbWVudC50ZXh0Q29udGVudCA9IHRleHQ7CiAgICAgICAgICAgICAgICAgICAgdmFyIGRpbWVuc2lvbnMgPSBTdmdVdGlscy5nZXREaW1lbnNpb25zKHRleHRFbGVtZW50KTsKICAgICAgICAgICAgICAgICAgICBwYXJlbnRFbGVtZW50LnJlbW92ZUNoaWxkKGNvbnRhaW5lckVsZW1lbnQpOyAvLyBlbGVtZW50LnJlbW92ZSgpIGRvZXNuJ3Qgd29yayBpbiBJRTExCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGRpbWVuc2lvbnM7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLmNyZWF0ZVBlbiA9IGZ1bmN0aW9uICh0ZXh0LCB0cmFuc2Zvcm0sIGVsZW1lbnQpIHsKICAgICAgICAgICAgICAgIGlmIChlbGVtZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBlbGVtZW50ID0gX3RoaXMuZWxlbWVudDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciB0ZXh0Q29udGFpbmVyID0gU3ZnVXRpbHMuYXBwZW5kKGVsZW1lbnQsICJnIiwgInRleHQtY29udGFpbmVyIiwgX3RoaXMuY2xhc3NOYW1lKTsKICAgICAgICAgICAgICAgIC8vIGF0dGFjaCBvcHRpb25hbCB0aXRsZQogICAgICAgICAgICAgICAgaWYgKF90aGlzLmFkZFRpdGxlRWxlbWVudCkgewogICAgICAgICAgICAgICAgICAgIFN2Z1V0aWxzLmFwcGVuZCh0ZXh0Q29udGFpbmVyLCAidGl0bGUiKS50ZXh0Q29udGVudCA9IHRleHQ7CiAgICAgICAgICAgICAgICAgICAgdGV4dENvbnRhaW5lci5zZXRBdHRyaWJ1dGUoInRpdGxlIiwgdGV4dCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBjcmVhdGUgYW5kIHRyYW5zZm9ybSB0ZXh0IGJsb2NrIGdyb3VwCiAgICAgICAgICAgICAgICB2YXIgdGV4dEJsb2NrR3JvdXAgPSBTdmdVdGlscy5hcHBlbmQodGV4dENvbnRhaW5lciwgImciLCAidGV4dC1hcmVhIik7CiAgICAgICAgICAgICAgICB0ZXh0QmxvY2tHcm91cC5zZXRBdHRyaWJ1dGUoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIHRyYW5zZm9ybS50cmFuc2xhdGVbMF0gKyAiLCIgKyB0cmFuc2Zvcm0udHJhbnNsYXRlWzFdICsgIikiICsKICAgICAgICAgICAgICAgICAgICAoInJvdGF0ZSgiICsgdHJhbnNmb3JtLnJvdGF0ZSArICIpIikpOwogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLmNyZWF0ZVN2Z0xpbmVQZW4odGV4dEJsb2NrR3JvdXApOwogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBTdmdDb250ZXh0LnByb3RvdHlwZS5zZXRBZGRUaXRsZUVsZW1lbnQgPSBmdW5jdGlvbiAoYWRkVGl0bGVFbGVtZW50KSB7CiAgICAgICAgICAgIHRoaXMuYWRkVGl0bGVFbGVtZW50ID0gYWRkVGl0bGVFbGVtZW50OwogICAgICAgIH07CiAgICAgICAgU3ZnQ29udGV4dC5wcm90b3R5cGUuY3JlYXRlU3ZnTGluZVBlbiA9IGZ1bmN0aW9uICh0ZXh0QmxvY2tHcm91cCkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgd3JpdGU6IGZ1bmN0aW9uIChsaW5lLCB3aWR0aCwgeEFsaWduLCB4T2Zmc2V0LCB5T2Zmc2V0KSB7CiAgICAgICAgICAgICAgICAgICAgeE9mZnNldCArPSB3aWR0aCAqIHdyaXRlcnMuV3JpdGVyLlhPZmZzZXRGYWN0b3JbeEFsaWduXTsKICAgICAgICAgICAgICAgICAgICB2YXIgZWxlbWVudCA9IFN2Z1V0aWxzLmFwcGVuZCh0ZXh0QmxvY2tHcm91cCwgInRleHQiLCAidGV4dC1saW5lIik7CiAgICAgICAgICAgICAgICAgICAgZWxlbWVudC50ZXh0Q29udGVudCA9IGxpbmU7CiAgICAgICAgICAgICAgICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoInRleHQtYW5jaG9yIiwgU3ZnQ29udGV4dC5BbmNob3JNYXBbeEFsaWduXSk7CiAgICAgICAgICAgICAgICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIHhPZmZzZXQgKyAiLCIgKyB5T2Zmc2V0ICsgIikiKTsKICAgICAgICAgICAgICAgICAgICBlbGVtZW50LnNldEF0dHJpYnV0ZSgieSIsICItMC4yNWVtIik7CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgU3ZnQ29udGV4dC5wcm90b3R5cGUuZ2V0VGV4dEVsZW1lbnRzID0gZnVuY3Rpb24gKGVsZW1lbnQpIHsKICAgICAgICAgICAgLy8gaWYgZWxlbWVudCBpcyBhbHJlYWR5IGEgdGV4dCBlbGVtZW50LCByZXR1cm4gaXQKICAgICAgICAgICAgaWYgKGVsZW1lbnQudGFnTmFtZSA9PT0gInRleHQiKSB7CiAgICAgICAgICAgICAgICB2YXIgcGFyZW50RWxlbWVudCA9IGVsZW1lbnQucGFyZW50RWxlbWVudDsKICAgICAgICAgICAgICAgIGlmIChwYXJlbnRFbGVtZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBwYXJlbnRFbGVtZW50ID0gZWxlbWVudC5wYXJlbnROb2RlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gbXVzdCBiZSByZW1vdmVkIGZyb20gcGFyZW50IHNpbmNlIHdlIHJlLWFkZCBpdCBvbiBldmVyeSBtZWFzdXJlbWVudAogICAgICAgICAgICAgICAgcGFyZW50RWxlbWVudC5yZW1vdmVDaGlsZChlbGVtZW50KTsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgY29udGFpbmVyRWxlbWVudDogZWxlbWVudCwKICAgICAgICAgICAgICAgICAgICBwYXJlbnRFbGVtZW50OiBwYXJlbnRFbGVtZW50LAogICAgICAgICAgICAgICAgICAgIHRleHRFbGVtZW50OiBlbGVtZW50LAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBpZiBlbGVtZW50IGhhcyBhIHRleHQgZWxlbWVudCBkZXNjZW5kZW50LCBzZWxlY3QgaXQgYW5kIHJldHVybiBpdAogICAgICAgICAgICB2YXIgc2VsZWN0ZWQgPSBlbGVtZW50LnF1ZXJ5U2VsZWN0b3IoInRleHQiKTsKICAgICAgICAgICAgaWYgKHNlbGVjdGVkICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHZhciBwYXJlbnRFbGVtZW50ID0gc2VsZWN0ZWQucGFyZW50RWxlbWVudDsKICAgICAgICAgICAgICAgIGlmIChwYXJlbnRFbGVtZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBwYXJlbnRFbGVtZW50ID0gc2VsZWN0ZWQucGFyZW50Tm9kZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIG11c3QgYmUgcmVtb3ZlZCBmcm9tIHBhcmVudCBzaW5jZSB3ZSByZS1hZGQgaXQgb24gZXZlcnkgbWVhc3VyZW1lbnQKICAgICAgICAgICAgICAgIHBhcmVudEVsZW1lbnQucmVtb3ZlQ2hpbGQoc2VsZWN0ZWQpOwogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBjb250YWluZXJFbGVtZW50OiBzZWxlY3RlZCwKICAgICAgICAgICAgICAgICAgICBwYXJlbnRFbGVtZW50OiBwYXJlbnRFbGVtZW50LAogICAgICAgICAgICAgICAgICAgIHRleHRFbGVtZW50OiBzZWxlY3RlZCwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gb3RoZXJ3aXNlIGNyZWF0ZSBhIG5ldyB0ZXh0IGVsZW1lbnQKICAgICAgICAgICAgdmFyIGNyZWF0ZWQgPSBTdmdVdGlscy5jcmVhdGUoInRleHQiLCB0aGlzLmNsYXNzTmFtZSk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBjb250YWluZXJFbGVtZW50OiBjcmVhdGVkLAogICAgICAgICAgICAgICAgcGFyZW50RWxlbWVudDogZWxlbWVudCwKICAgICAgICAgICAgICAgIHRleHRFbGVtZW50OiBjcmVhdGVkLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFN2Z0NvbnRleHQ7CiAgICB9KCkpOwogICAgU3ZnQ29udGV4dC5BbmNob3JNYXAgPSB7CiAgICAgICAgY2VudGVyOiAibWlkZGxlIiwKICAgICAgICBsZWZ0OiAic3RhcnQiLAogICAgICAgIHJpZ2h0OiAiZW5kIiwKICAgIH07CiAgICBleHBvcnRzLlN2Z0NvbnRleHQgPSBTdmdDb250ZXh0OwoKICAgIH0pOwoKICAgIHZhciBjYW52YXMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIExpY2Vuc2UgKHRoZSAiTGljZW5zZSIpOyB5b3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlCiAgICAgKiBsaWNlbnNlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci90eXBlc2V0dGFibGUvYmxvYi9kZXZlbG9wL0xJQ0VOU0UKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgREVGQVVMVF9GSUxMX0NPTE9SID0gIiM0NDQiOwogICAgLyoqCiAgICAgKiBBIHR5cGVzZXR0ZXIgY29udGV4dCBmb3IgSFRNTDUgQ2FudmFzLgogICAgICoKICAgICAqIER1ZSB0byB0aGUgQ2FudmFzIEFQSSwgeW91IG11c3QgZXhwbGljaXRseSBkZWZpbmUgdGhlIGxpbmUgaGVpZ2h0LCBhbmQgYW55CiAgICAgKiBzdHlsaW5nIGZvciB0aGUgZm9udCBtdXN0IGFsc28gYmUgZXhwbGljaXRseSBkZWZpbmVkIGluIHRoZSBvcHRpb25hbAogICAgICogYElDYW52YXNGb250U3R5bGVgIG9iamVjdC4KICAgICAqLwogICAgdmFyIENhbnZhc0NvbnRleHQgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIENhbnZhc0NvbnRleHQoY3R4LCBsaW5lSGVpZ2h0LCBzdHlsZSkgewogICAgICAgICAgICBpZiAobGluZUhlaWdodCA9PT0gdm9pZCAwKSB7IGxpbmVIZWlnaHQgPSAxMDsgfQogICAgICAgICAgICBpZiAoc3R5bGUgPT09IHZvaWQgMCkgeyBzdHlsZSA9IHt9OyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuY3R4ID0gY3R4OwogICAgICAgICAgICB0aGlzLmxpbmVIZWlnaHQgPSBsaW5lSGVpZ2h0OwogICAgICAgICAgICB0aGlzLnN0eWxlID0gc3R5bGU7CiAgICAgICAgICAgIHRoaXMuY3JlYXRlUnVsZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKHRleHQpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5jdHguZm9udCA9IF90aGlzLnN0eWxlLmZvbnQ7CiAgICAgICAgICAgICAgICAgICAgdmFyIHdpZHRoID0gX3RoaXMuY3R4Lm1lYXN1cmVUZXh0KHRleHQpLndpZHRoOwogICAgICAgICAgICAgICAgICAgIHJldHVybiB7IHdpZHRoOiB3aWR0aCwgaGVpZ2h0OiBfdGhpcy5saW5lSGVpZ2h0IH07CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLmNyZWF0ZVBlbiA9IGZ1bmN0aW9uIChfdGV4dCwgdHJhbnNmb3JtLCBjdHgpIHsKICAgICAgICAgICAgICAgIGlmIChjdHggPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGN0eCA9IF90aGlzLmN0eDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGN0eC5zYXZlKCk7CiAgICAgICAgICAgICAgICBjdHgudHJhbnNsYXRlKHRyYW5zZm9ybS50cmFuc2xhdGVbMF0sIHRyYW5zZm9ybS50cmFuc2xhdGVbMV0pOwogICAgICAgICAgICAgICAgY3R4LnJvdGF0ZSh0cmFuc2Zvcm0ucm90YXRlICogTWF0aC5QSSAvIDE4MC4wKTsKICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5jcmVhdGVDYW52YXNQZW4oY3R4KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgaWYgKHRoaXMuc3R5bGUuZmlsbCA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLnN0eWxlLmZpbGwgPSBERUZBVUxUX0ZJTExfQ09MT1I7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgQ2FudmFzQ29udGV4dC5wcm90b3R5cGUuY3JlYXRlQ2FudmFzUGVuID0gZnVuY3Rpb24gKGN0eCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgZGVzdHJveTogZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIGN0eC5yZXN0b3JlKCk7CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgd3JpdGU6IGZ1bmN0aW9uIChsaW5lLCB3aWR0aCwgeEFsaWduLCB4T2Zmc2V0LCB5T2Zmc2V0KSB7CiAgICAgICAgICAgICAgICAgICAgeE9mZnNldCArPSB3aWR0aCAqIHdyaXRlcnMuV3JpdGVyLlhPZmZzZXRGYWN0b3JbeEFsaWduXTsKICAgICAgICAgICAgICAgICAgICBjdHgudGV4dEFsaWduID0geEFsaWduOwogICAgICAgICAgICAgICAgICAgIGlmIChfdGhpcy5zdHlsZS5mb250ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY3R4LmZvbnQgPSBfdGhpcy5zdHlsZS5mb250OwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpZiAoX3RoaXMuc3R5bGUuZmlsbCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGN0eC5maWxsU3R5bGUgPSBfdGhpcy5zdHlsZS5maWxsOwogICAgICAgICAgICAgICAgICAgICAgICBjdHguZmlsbFRleHQobGluZSwgeE9mZnNldCwgeU9mZnNldCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmIChfdGhpcy5zdHlsZS5zdHJva2UgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgICAgICBjdHguc3Ryb2tlU3R5bGUgPSBfdGhpcy5zdHlsZS5maWxsOwogICAgICAgICAgICAgICAgICAgICAgICBjdHguc3Ryb2tlVGV4dChsaW5lLCB4T2Zmc2V0LCB5T2Zmc2V0KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIENhbnZhc0NvbnRleHQ7CiAgICB9KCkpOwogICAgZXhwb3J0cy5DYW52YXNDb250ZXh0ID0gQ2FudmFzQ29udGV4dDsKCiAgICB9KTsKCiAgICB2YXIgY29udGV4dHMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIExpY2Vuc2UgKHRoZSAiTGljZW5zZSIpOyB5b3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlCiAgICAgKiBsaWNlbnNlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci90eXBlc2V0dGFibGUvYmxvYi9kZXZlbG9wL0xJQ0VOU0UKICAgICAqLwogICAgZnVuY3Rpb24gX19leHBvcnQobSkgewogICAgICAgIGZvciAodmFyIHAgaW4gbSkgaWYgKCFleHBvcnRzLmhhc093blByb3BlcnR5KHApKSBleHBvcnRzW3BdID0gbVtwXTsKICAgIH0KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICBfX2V4cG9ydChzdmckMSk7CiAgICBfX2V4cG9ydChjYW52YXMpOwogICAgX19leHBvcnQoaHRtbCQzKTsKCiAgICB9KTsKCiAgICB2YXIgYWJzdHJhY3RNZWFzdXJlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMsIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgICAqIExpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgTGljZW5zZSAodGhlICJMaWNlbnNlIik7IHlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUKICAgICAqIGxpY2Vuc2UgYXQgaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3R5cGVzZXR0YWJsZS9ibG9iL2RldmVsb3AvTElDRU5TRQogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgdmFyIEFic3RyYWN0TWVhc3VyZXIgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIEFic3RyYWN0TWVhc3VyZXIocnVsZXIpIHsKICAgICAgICAgICAgaWYgKHJ1bGVyLmNyZWF0ZVJ1bGVyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMucnVsZXIgPSBydWxlci5jcmVhdGVSdWxlcigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5ydWxlciA9IHJ1bGVyOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIEFic3RyYWN0TWVhc3VyZXIucHJvdG90eXBlLm1lYXN1cmUgPSBmdW5jdGlvbiAodGV4dCkgewogICAgICAgICAgICBpZiAodGV4dCA9PT0gdm9pZCAwKSB7IHRleHQgPSBBYnN0cmFjdE1lYXN1cmVyLkhFSUdIVF9URVhUOyB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJ1bGVyKHRleHQpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEFic3RyYWN0TWVhc3VyZXI7CiAgICB9KCkpOwogICAgLyoqCiAgICAgKiBBIHN0cmluZyByZXByZXNlbnRpbmcgdGhlIGZ1bGwgYXNjZW5kZXIvZGVzY2VuZGVyIHJhbmdlIG9mIHlvdXIgdGV4dC4KICAgICAqCiAgICAgKiBOb3RlIHRoYXQgdGhpcyBpcyByZWFsbHkgb25seSBhcHBsaWNhYmxlIHRvIHdlc3Rlcm4gYWxwaGFiZXRzLiBJZiB5b3UgYXJlCiAgICAgKiB1c2luZyBhIGRpZmZlcmVudCBsb2NhbGUgbGFuZ3VhZ2Ugc3VjaCBhcyBhcmFiaWMgb3IgY2hpbmVzZSwgeW91IG1heSB3YW50CiAgICAgKiB0byBvdmVycmlkZSB0aGlzLgogICAgICovCiAgICBBYnN0cmFjdE1lYXN1cmVyLkhFSUdIVF9URVhUID0gImJkcHFsIjsKICAgIGV4cG9ydHMuQWJzdHJhY3RNZWFzdXJlciA9IEFic3RyYWN0TWVhc3VyZXI7CgogICAgfSk7CgogICAgdmFyIG1lYXN1cmVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIHZhciBfX2V4dGVuZHMgPSAoY29tbW9uanNHbG9iYWwgJiYgY29tbW9uanNHbG9iYWwuX19leHRlbmRzKSB8fCAoZnVuY3Rpb24gKCkgewogICAgICAgIHZhciBleHRlbmRTdGF0aWNzID0gT2JqZWN0LnNldFByb3RvdHlwZU9mIHx8CiAgICAgICAgICAgICh7IF9fcHJvdG9fXzogW10gfSBpbnN0YW5jZW9mIEFycmF5ICYmIGZ1bmN0aW9uIChkLCBiKSB7IGQuX19wcm90b19fID0gYjsgfSkgfHwKICAgICAgICAgICAgZnVuY3Rpb24gKGQsIGIpIHsgZm9yICh2YXIgcCBpbiBiKSBpZiAoYi5oYXNPd25Qcm9wZXJ0eShwKSkgZFtwXSA9IGJbcF07IH07CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkLCBiKSB7CiAgICAgICAgICAgIGV4dGVuZFN0YXRpY3MoZCwgYik7CiAgICAgICAgICAgIGZ1bmN0aW9uIF9fKCkgeyB0aGlzLmNvbnN0cnVjdG9yID0gZDsgfQogICAgICAgICAgICBkLnByb3RvdHlwZSA9IGIgPT09IG51bGwgPyBPYmplY3QuY3JlYXRlKGIpIDogKF9fLnByb3RvdHlwZSA9IGIucHJvdG90eXBlLCBuZXcgX18oKSk7CiAgICAgICAgfTsKICAgIH0pKCk7CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBNZWFzdXJlciA9IChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgX19leHRlbmRzKE1lYXN1cmVyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIE1lYXN1cmVyKHJ1bGVyLCB1c2VHdWFyZHMpIHsKICAgICAgICAgICAgaWYgKHVzZUd1YXJkcyA9PT0gdm9pZCAwKSB7IHVzZUd1YXJkcyA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMsIHJ1bGVyKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy51c2VHdWFyZHMgPSB1c2VHdWFyZHM7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgLy8gR3VhcmRzIGFzc3VyZXMgc2FtZSBsaW5lIGhlaWdodCBhbmQgd2lkdGggb2Ygd2hpdGVzcGFjZXMgb24gYm90aCBlbmRzLgogICAgICAgIE1lYXN1cmVyLnByb3RvdHlwZS5fYWRkR3VhcmRzID0gZnVuY3Rpb24gKHRleHQpIHsKICAgICAgICAgICAgcmV0dXJuIGFic3RyYWN0TWVhc3VyZXIuQWJzdHJhY3RNZWFzdXJlci5IRUlHSFRfVEVYVCArIHRleHQgKyBhYnN0cmFjdE1lYXN1cmVyLkFic3RyYWN0TWVhc3VyZXIuSEVJR0hUX1RFWFQ7CiAgICAgICAgfTsKICAgICAgICBNZWFzdXJlci5wcm90b3R5cGUuX21lYXN1cmVMaW5lID0gZnVuY3Rpb24gKGxpbmUsIGZvcmNlR3VhcmRzKSB7CiAgICAgICAgICAgIGlmIChmb3JjZUd1YXJkcyA9PT0gdm9pZCAwKSB7IGZvcmNlR3VhcmRzID0gZmFsc2U7IH0KICAgICAgICAgICAgdmFyIHVzZUd1YXJkcyA9IHRoaXMudXNlR3VhcmRzIHx8IGZvcmNlR3VhcmRzIHx8IC9eW1x0IF0kLy50ZXN0KGxpbmUpOwogICAgICAgICAgICB2YXIgbWVhc3VyZWRMaW5lID0gdXNlR3VhcmRzID8gdGhpcy5fYWRkR3VhcmRzKGxpbmUpIDogbGluZTsKICAgICAgICAgICAgdmFyIG1lYXN1cmVkTGluZURpbWVuc2lvbnMgPSBfc3VwZXIucHJvdG90eXBlLm1lYXN1cmUuY2FsbCh0aGlzLCBtZWFzdXJlZExpbmUpOwogICAgICAgICAgICBtZWFzdXJlZExpbmVEaW1lbnNpb25zLndpZHRoIC09IHVzZUd1YXJkcyA/ICgyICogdGhpcy5nZXRHdWFyZFdpZHRoKCkpIDogMDsKICAgICAgICAgICAgcmV0dXJuIG1lYXN1cmVkTGluZURpbWVuc2lvbnM7CiAgICAgICAgfTsKICAgICAgICBNZWFzdXJlci5wcm90b3R5cGUubWVhc3VyZSA9IGZ1bmN0aW9uICh0ZXh0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmICh0ZXh0ID09PSB2b2lkIDApIHsgdGV4dCA9IGFic3RyYWN0TWVhc3VyZXIuQWJzdHJhY3RNZWFzdXJlci5IRUlHSFRfVEVYVDsgfQogICAgICAgICAgICBpZiAodGV4dC50cmltKCkgPT09ICIiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4geyB3aWR0aDogMCwgaGVpZ2h0OiAwIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGxpbmVzRGltZW5zaW9ucyA9IHRleHQudHJpbSgpLnNwbGl0KCJcbiIpLm1hcChmdW5jdGlvbiAobGluZSkgeyByZXR1cm4gX3RoaXMuX21lYXN1cmVMaW5lKGxpbmUpOyB9KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGhlaWdodDogbGluZXNEaW1lbnNpb25zLnJlZHVjZShmdW5jdGlvbiAoYWNjLCBkaW0pIHsgcmV0dXJuIGFjYyArIGRpbS5oZWlnaHQ7IH0sIDApLAogICAgICAgICAgICAgICAgd2lkdGg6IGxpbmVzRGltZW5zaW9ucy5yZWR1Y2UoZnVuY3Rpb24gKGFjYywgZGltKSB7IHJldHVybiBNYXRoLm1heChhY2MsIGRpbS53aWR0aCk7IH0sIDApLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgTWVhc3VyZXIucHJvdG90eXBlLmdldEd1YXJkV2lkdGggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLmd1YXJkV2lkdGggPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5ndWFyZFdpZHRoID0gX3N1cGVyLnByb3RvdHlwZS5tZWFzdXJlLmNhbGwodGhpcykud2lkdGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuZ3VhcmRXaWR0aDsKICAgICAgICB9OwogICAgICAgIHJldHVybiBNZWFzdXJlcjsKICAgIH0oYWJzdHJhY3RNZWFzdXJlci5BYnN0cmFjdE1lYXN1cmVyKSk7CiAgICBleHBvcnRzLk1lYXN1cmVyID0gTWVhc3VyZXI7CgogICAgfSk7CgogICAgdmFyIGNoYXJhY3Rlck1lYXN1cmVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIC8qIGlzdGFuYnVsIGlnbm9yZSBuZXh0ICovCiAgICB2YXIgX19leHRlbmRzID0gKGNvbW1vbmpzR2xvYmFsICYmIGNvbW1vbmpzR2xvYmFsLl9fZXh0ZW5kcykgfHwgKGZ1bmN0aW9uICgpIHsKICAgICAgICB2YXIgZXh0ZW5kU3RhdGljcyA9IE9iamVjdC5zZXRQcm90b3R5cGVPZiB8fAogICAgICAgICAgICAoeyBfX3Byb3RvX186IFtdIH0gaW5zdGFuY2VvZiBBcnJheSAmJiBmdW5jdGlvbiAoZCwgYikgeyBkLl9fcHJvdG9fXyA9IGI7IH0pIHx8CiAgICAgICAgICAgIGZ1bmN0aW9uIChkLCBiKSB7IGZvciAodmFyIHAgaW4gYikgaWYgKGIuaGFzT3duUHJvcGVydHkocCkpIGRbcF0gPSBiW3BdOyB9OwogICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCwgYikgewogICAgICAgICAgICBleHRlbmRTdGF0aWNzKGQsIGIpOwogICAgICAgICAgICBmdW5jdGlvbiBfXygpIHsgdGhpcy5jb25zdHJ1Y3RvciA9IGQ7IH0KICAgICAgICAgICAgZC5wcm90b3R5cGUgPSBiID09PSBudWxsID8gT2JqZWN0LmNyZWF0ZShiKSA6IChfXy5wcm90b3R5cGUgPSBiLnByb3RvdHlwZSwgbmV3IF9fKCkpOwogICAgICAgIH07CiAgICB9KSgpOwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgQ2hhcmFjdGVyTWVhc3VyZXIgPSAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIF9fZXh0ZW5kcyhDaGFyYWN0ZXJNZWFzdXJlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBDaGFyYWN0ZXJNZWFzdXJlcigpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlciAhPT0gbnVsbCAmJiBfc3VwZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSB8fCB0aGlzOwogICAgICAgIH0KICAgICAgICBDaGFyYWN0ZXJNZWFzdXJlci5wcm90b3R5cGUuX21lYXN1cmVDaGFyYWN0ZXIgPSBmdW5jdGlvbiAoYykgewogICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5fbWVhc3VyZUxpbmUuY2FsbCh0aGlzLCBjKTsKICAgICAgICB9OwogICAgICAgIENoYXJhY3Rlck1lYXN1cmVyLnByb3RvdHlwZS5fbWVhc3VyZUxpbmUgPSBmdW5jdGlvbiAobGluZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgY2hhcmFjdGVyc0RpbWVuc2lvbnMgPSBsaW5lLnNwbGl0KCIiKS5tYXAoZnVuY3Rpb24gKGMpIHsgcmV0dXJuIF90aGlzLl9tZWFzdXJlQ2hhcmFjdGVyKGMpOyB9KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGhlaWdodDogY2hhcmFjdGVyc0RpbWVuc2lvbnMucmVkdWNlKGZ1bmN0aW9uIChhY2MsIGRpbSkgeyByZXR1cm4gTWF0aC5tYXgoYWNjLCBkaW0uaGVpZ2h0KTsgfSwgMCksCiAgICAgICAgICAgICAgICB3aWR0aDogY2hhcmFjdGVyc0RpbWVuc2lvbnMucmVkdWNlKGZ1bmN0aW9uIChhY2MsIGRpbSkgeyByZXR1cm4gYWNjICsgZGltLndpZHRoOyB9LCAwKSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBDaGFyYWN0ZXJNZWFzdXJlcjsKICAgIH0obWVhc3VyZXIuTWVhc3VyZXIpKTsKICAgIGV4cG9ydHMuQ2hhcmFjdGVyTWVhc3VyZXIgPSBDaGFyYWN0ZXJNZWFzdXJlcjsKCiAgICB9KTsKCiAgICB2YXIgY2FjaGVDaGFyYWN0ZXJNZWFzdXJlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMsIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgICAqIExpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgTGljZW5zZSAodGhlICJMaWNlbnNlIik7IHlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUKICAgICAqIGxpY2Vuc2UgYXQgaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3R5cGVzZXR0YWJsZS9ibG9iL2RldmVsb3AvTElDRU5TRQogICAgICovCiAgICAvKiBpc3RhbmJ1bCBpZ25vcmUgbmV4dCAqLwogICAgdmFyIF9fZXh0ZW5kcyA9IChjb21tb25qc0dsb2JhbCAmJiBjb21tb25qc0dsb2JhbC5fX2V4dGVuZHMpIHx8IChmdW5jdGlvbiAoKSB7CiAgICAgICAgdmFyIGV4dGVuZFN0YXRpY3MgPSBPYmplY3Quc2V0UHJvdG90eXBlT2YgfHwKICAgICAgICAgICAgKHsgX19wcm90b19fOiBbXSB9IGluc3RhbmNlb2YgQXJyYXkgJiYgZnVuY3Rpb24gKGQsIGIpIHsgZC5fX3Byb3RvX18gPSBiOyB9KSB8fAogICAgICAgICAgICBmdW5jdGlvbiAoZCwgYikgeyBmb3IgKHZhciBwIGluIGIpIGlmIChiLmhhc093blByb3BlcnR5KHApKSBkW3BdID0gYltwXTsgfTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGQsIGIpIHsKICAgICAgICAgICAgZXh0ZW5kU3RhdGljcyhkLCBiKTsKICAgICAgICAgICAgZnVuY3Rpb24gX18oKSB7IHRoaXMuY29uc3RydWN0b3IgPSBkOyB9CiAgICAgICAgICAgIGQucHJvdG90eXBlID0gYiA9PT0gbnVsbCA/IE9iamVjdC5jcmVhdGUoYikgOiAoX18ucHJvdG90eXBlID0gYi5wcm90b3R5cGUsIG5ldyBfXygpKTsKICAgICAgICB9OwogICAgfSkoKTsKICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKICAgIHZhciBDYWNoZUNoYXJhY3Rlck1lYXN1cmVyID0gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICBfX2V4dGVuZHMoQ2FjaGVDaGFyYWN0ZXJNZWFzdXJlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBDYWNoZUNoYXJhY3Rlck1lYXN1cmVyKHJ1bGVyLCB1c2VHdWFyZHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcywgcnVsZXIsIHVzZUd1YXJkcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuY2FjaGUgPSBuZXcgdXRpbHMuQ2FjaGUoZnVuY3Rpb24gKGMpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5fbWVhc3VyZUNoYXJhY3Rlck5vdEZyb21DYWNoZShjKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgQ2FjaGVDaGFyYWN0ZXJNZWFzdXJlci5wcm90b3R5cGUuX21lYXN1cmVDaGFyYWN0ZXJOb3RGcm9tQ2FjaGUgPSBmdW5jdGlvbiAoYykgewogICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5fbWVhc3VyZUNoYXJhY3Rlci5jYWxsKHRoaXMsIGMpOwogICAgICAgIH07CiAgICAgICAgQ2FjaGVDaGFyYWN0ZXJNZWFzdXJlci5wcm90b3R5cGUuX21lYXN1cmVDaGFyYWN0ZXIgPSBmdW5jdGlvbiAoYykgewogICAgICAgICAgICByZXR1cm4gdGhpcy5jYWNoZS5nZXQoYyk7CiAgICAgICAgfTsKICAgICAgICBDYWNoZUNoYXJhY3Rlck1lYXN1cmVyLnByb3RvdHlwZS5yZXNldCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5jYWNoZS5jbGVhcigpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIENhY2hlQ2hhcmFjdGVyTWVhc3VyZXI7CiAgICB9KGNoYXJhY3Rlck1lYXN1cmVyLkNoYXJhY3Rlck1lYXN1cmVyKSk7CiAgICBleHBvcnRzLkNhY2hlQ2hhcmFjdGVyTWVhc3VyZXIgPSBDYWNoZUNoYXJhY3Rlck1lYXN1cmVyOwoKICAgIH0pOwoKICAgIHZhciBjYWNoZU1lYXN1cmVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIC8qIGlzdGFuYnVsIGlnbm9yZSBuZXh0ICovCiAgICB2YXIgX19leHRlbmRzID0gKGNvbW1vbmpzR2xvYmFsICYmIGNvbW1vbmpzR2xvYmFsLl9fZXh0ZW5kcykgfHwgKGZ1bmN0aW9uICgpIHsKICAgICAgICB2YXIgZXh0ZW5kU3RhdGljcyA9IE9iamVjdC5zZXRQcm90b3R5cGVPZiB8fAogICAgICAgICAgICAoeyBfX3Byb3RvX186IFtdIH0gaW5zdGFuY2VvZiBBcnJheSAmJiBmdW5jdGlvbiAoZCwgYikgeyBkLl9fcHJvdG9fXyA9IGI7IH0pIHx8CiAgICAgICAgICAgIGZ1bmN0aW9uIChkLCBiKSB7IGZvciAodmFyIHAgaW4gYikgaWYgKGIuaGFzT3duUHJvcGVydHkocCkpIGRbcF0gPSBiW3BdOyB9OwogICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCwgYikgewogICAgICAgICAgICBleHRlbmRTdGF0aWNzKGQsIGIpOwogICAgICAgICAgICBmdW5jdGlvbiBfXygpIHsgdGhpcy5jb25zdHJ1Y3RvciA9IGQ7IH0KICAgICAgICAgICAgZC5wcm90b3R5cGUgPSBiID09PSBudWxsID8gT2JqZWN0LmNyZWF0ZShiKSA6IChfXy5wcm90b3R5cGUgPSBiLnByb3RvdHlwZSwgbmV3IF9fKCkpOwogICAgICAgIH07CiAgICB9KSgpOwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKICAgIHZhciBDYWNoZU1lYXN1cmVyID0gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICBfX2V4dGVuZHMoQ2FjaGVNZWFzdXJlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBDYWNoZU1lYXN1cmVyKHJ1bGVyKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMsIHJ1bGVyKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5kaW1DYWNoZSA9IG5ldyB1dGlscy5DYWNoZShmdW5jdGlvbiAocykgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9tZWFzdXJlTm90RnJvbUNhY2hlKHMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBDYWNoZU1lYXN1cmVyLnByb3RvdHlwZS5fbWVhc3VyZU5vdEZyb21DYWNoZSA9IGZ1bmN0aW9uIChzKSB7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLm1lYXN1cmUuY2FsbCh0aGlzLCBzKTsKICAgICAgICB9OwogICAgICAgIENhY2hlTWVhc3VyZXIucHJvdG90eXBlLm1lYXN1cmUgPSBmdW5jdGlvbiAocykgewogICAgICAgICAgICBpZiAocyA9PT0gdm9pZCAwKSB7IHMgPSBhYnN0cmFjdE1lYXN1cmVyLkFic3RyYWN0TWVhc3VyZXIuSEVJR0hUX1RFWFQ7IH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuZGltQ2FjaGUuZ2V0KHMpOwogICAgICAgIH07CiAgICAgICAgQ2FjaGVNZWFzdXJlci5wcm90b3R5cGUucmVzZXQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuZGltQ2FjaGUuY2xlYXIoKTsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZXNldC5jYWxsKHRoaXMpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIENhY2hlTWVhc3VyZXI7CiAgICB9KGNhY2hlQ2hhcmFjdGVyTWVhc3VyZXIuQ2FjaGVDaGFyYWN0ZXJNZWFzdXJlcikpOwogICAgZXhwb3J0cy5DYWNoZU1lYXN1cmVyID0gQ2FjaGVNZWFzdXJlcjsKCiAgICB9KTsKCiAgICB2YXIgbWVhc3VyZXJzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIGZ1bmN0aW9uIF9fZXhwb3J0KG0pIHsKICAgICAgICBmb3IgKHZhciBwIGluIG0pIGlmICghZXhwb3J0cy5oYXNPd25Qcm9wZXJ0eShwKSkgZXhwb3J0c1twXSA9IG1bcF07CiAgICB9CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgX19leHBvcnQoYWJzdHJhY3RNZWFzdXJlcik7CiAgICBfX2V4cG9ydChjYWNoZUNoYXJhY3Rlck1lYXN1cmVyKTsKICAgIF9fZXhwb3J0KGNhY2hlTWVhc3VyZXIpOwogICAgX19leHBvcnQoY2hhcmFjdGVyTWVhc3VyZXIpOwogICAgX19leHBvcnQobWVhc3VyZXIpOwoKICAgIH0pOwoKICAgIHZhciB3cmFwcGVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgdmFyIFdyYXBwZXIgPSAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFdyYXBwZXIoKSB7CiAgICAgICAgICAgIHRoaXMubWF4TGluZXMoSW5maW5pdHkpOwogICAgICAgICAgICB0aGlzLnRleHRUcmltbWluZygiZWxsaXBzaXMiKTsKICAgICAgICAgICAgdGhpcy5hbGxvd0JyZWFraW5nV29yZHMoZmFsc2UpOwogICAgICAgICAgICB0aGlzLl90b2tlbml6ZXIgPSBuZXcgdXRpbHMuVG9rZW5pemVyKCk7CiAgICAgICAgICAgIHRoaXMuX2JyZWFraW5nQ2hhcmFjdGVyID0gIi0iOwogICAgICAgIH0KICAgICAgICBXcmFwcGVyLnByb3RvdHlwZS5tYXhMaW5lcyA9IGZ1bmN0aW9uIChub0xpbmVzKSB7CiAgICAgICAgICAgIGlmIChub0xpbmVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhMaW5lczsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heExpbmVzID0gbm9MaW5lczsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBXcmFwcGVyLnByb3RvdHlwZS50ZXh0VHJpbW1pbmcgPSBmdW5jdGlvbiAob3B0aW9uKSB7CiAgICAgICAgICAgIGlmIChvcHRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3RleHRUcmltbWluZzsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGlmIChvcHRpb24gIT09ICJlbGxpcHNpcyIgJiYgb3B0aW9uICE9PSAibm9uZSIpIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3Iob3B0aW9uICsgIiAtIHVuc3VwcG9ydGVkIHRleHQgdHJpbW1pbmcgb3B0aW9uLiIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5fdGV4dFRyaW1taW5nID0gb3B0aW9uOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFdyYXBwZXIucHJvdG90eXBlLmFsbG93QnJlYWtpbmdXb3JkcyA9IGZ1bmN0aW9uIChhbGxvdykgewogICAgICAgICAgICBpZiAoYWxsb3cgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2FsbG93QnJlYWtpbmdXb3JkczsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2FsbG93QnJlYWtpbmdXb3JkcyA9IGFsbG93OwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFdyYXBwZXIucHJvdG90eXBlLndyYXAgPSBmdW5jdGlvbiAodGV4dCwgbWVhc3VyZXIsIHdpZHRoLCBoZWlnaHQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKGhlaWdodCA9PT0gdm9pZCAwKSB7IGhlaWdodCA9IEluZmluaXR5OyB9CiAgICAgICAgICAgIHZhciBpbml0aWFsV3JhcHBpbmdSZXN1bHQgPSB7CiAgICAgICAgICAgICAgICBub0Jyb2tlV29yZHM6IDAsCiAgICAgICAgICAgICAgICBub0xpbmVzOiAwLAogICAgICAgICAgICAgICAgb3JpZ2luYWxUZXh0OiB0ZXh0LAogICAgICAgICAgICAgICAgdHJ1bmNhdGVkVGV4dDogIiIsCiAgICAgICAgICAgICAgICB3cmFwcGVkVGV4dDogIiIsCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBzdGF0ZSA9IHsKICAgICAgICAgICAgICAgIGF2YWlsYWJsZUxpbmVzOiBNYXRoLm1pbihNYXRoLmZsb29yKGhlaWdodCAvIG1lYXN1cmVyLm1lYXN1cmUoKS5oZWlnaHQpLCB0aGlzLl9tYXhMaW5lcyksCiAgICAgICAgICAgICAgICBhdmFpbGFibGVXaWR0aDogd2lkdGgsCiAgICAgICAgICAgICAgICBjYW5GaXRUZXh0OiB0cnVlLAogICAgICAgICAgICAgICAgY3VycmVudExpbmU6ICIiLAogICAgICAgICAgICAgICAgd3JhcHBpbmc6IGluaXRpYWxXcmFwcGluZ1Jlc3VsdCwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIGxpbmVzID0gdGV4dC5zcGxpdCgiXG4iKTsKICAgICAgICAgICAgcmV0dXJuIGxpbmVzLnJlZHVjZShmdW5jdGlvbiAocywgbGluZSwgaSkgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLmJyZWFrTGluZVRvRml0V2lkdGgocywgbGluZSwgaSAhPT0gbGluZXMubGVuZ3RoIC0gMSwgbWVhc3VyZXIpOwogICAgICAgICAgICB9LCBzdGF0ZSkud3JhcHBpbmc7CiAgICAgICAgfTsKICAgICAgICBXcmFwcGVyLnByb3RvdHlwZS5icmVha0xpbmVUb0ZpdFdpZHRoID0gZnVuY3Rpb24gKHN0YXRlLCBsaW5lLCBoYXNOZXh0TGluZSwgbWVhc3VyZXIpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKCFzdGF0ZS5jYW5GaXRUZXh0ICYmIHN0YXRlLndyYXBwaW5nLnRydW5jYXRlZFRleHQgIT09ICIiKSB7CiAgICAgICAgICAgICAgICBzdGF0ZS53cmFwcGluZy50cnVuY2F0ZWRUZXh0ICs9ICJcbiI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRva2VucyA9IHRoaXMuX3Rva2VuaXplci50b2tlbml6ZShsaW5lKTsKICAgICAgICAgICAgc3RhdGUgPSB0b2tlbnMucmVkdWNlKGZ1bmN0aW9uIChzLCB0b2tlbikgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLndyYXBOZXh0VG9rZW4odG9rZW4sIHMsIG1lYXN1cmVyKTsKICAgICAgICAgICAgfSwgc3RhdGUpOwogICAgICAgICAgICB2YXIgd3JhcHBlZFRleHQgPSB1dGlscy5TdHJpbmdNZXRob2RzLnRyaW1FbmQoc3RhdGUuY3VycmVudExpbmUpOwogICAgICAgICAgICBzdGF0ZS53cmFwcGluZy5ub0xpbmVzICs9ICsod3JhcHBlZFRleHQgIT09ICIiKTsKICAgICAgICAgICAgaWYgKHN0YXRlLndyYXBwaW5nLm5vTGluZXMgPT09IHN0YXRlLmF2YWlsYWJsZUxpbmVzICYmIHRoaXMuX3RleHRUcmltbWluZyAhPT0gIm5vbmUiICYmIGhhc05leHRMaW5lKSB7CiAgICAgICAgICAgICAgICAvLyBOb3RlOiBubyBuZWVkIHRvIGFkZCBtb3JlIGVsbGlwc2VzLCB0aGV5IHdlcmUgYWRkZWQgaW4gYHdyYXBOZXh0VG9rZW5gCiAgICAgICAgICAgICAgICBzdGF0ZS5jYW5GaXRUZXh0ID0gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBzdGF0ZS53cmFwcGluZy53cmFwcGVkVGV4dCArPSB3cmFwcGVkVGV4dDsKICAgICAgICAgICAgfQogICAgICAgICAgICBzdGF0ZS5jdXJyZW50TGluZSA9ICJcbiI7CiAgICAgICAgICAgIHJldHVybiBzdGF0ZTsKICAgICAgICB9OwogICAgICAgIFdyYXBwZXIucHJvdG90eXBlLmNhbkZpdFRva2VuID0gZnVuY3Rpb24gKHRva2VuLCB3aWR0aCwgbWVhc3VyZXIpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHBvc3NpYmxlQnJlYWtzID0gdG9rZW4uc3BsaXQoIiIpLm1hcChmdW5jdGlvbiAoYywgaSkgeyByZXR1cm4gKGkgIT09IHRva2VuLmxlbmd0aCAtIDEpID8gYyArIF90aGlzLl9icmVha2luZ0NoYXJhY3RlciA6IGM7IH0pOwogICAgICAgICAgICByZXR1cm4gKG1lYXN1cmVyLm1lYXN1cmUodG9rZW4pLndpZHRoIDw9IHdpZHRoKSB8fCBwb3NzaWJsZUJyZWFrcy5ldmVyeShmdW5jdGlvbiAoYykgeyByZXR1cm4gbWVhc3VyZXIubWVhc3VyZShjKS53aWR0aCA8PSB3aWR0aDsgfSk7CiAgICAgICAgfTsKICAgICAgICBXcmFwcGVyLnByb3RvdHlwZS5hZGRFbGxpcHNpcyA9IGZ1bmN0aW9uIChsaW5lLCB3aWR0aCwgbWVhc3VyZXIpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX3RleHRUcmltbWluZyA9PT0gIm5vbmUiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIHJlbWFpbmluZ1Rva2VuOiAiIiwKICAgICAgICAgICAgICAgICAgICB3cmFwcGVkVG9rZW46IGxpbmUsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB0cnVuY2F0ZWRMaW5lID0gbGluZS5zdWJzdHJpbmcoMCkudHJpbSgpOwogICAgICAgICAgICB2YXIgbGluZVdpZHRoID0gbWVhc3VyZXIubWVhc3VyZSh0cnVuY2F0ZWRMaW5lKS53aWR0aDsKICAgICAgICAgICAgdmFyIGVsbGlwc2VzV2lkdGggPSBtZWFzdXJlci5tZWFzdXJlKCIuLi4iKS53aWR0aDsKICAgICAgICAgICAgdmFyIHByZWZpeCA9IChsaW5lLmxlbmd0aCA+IDAgJiYgbGluZVswXSA9PT0gIlxuIikgPyAiXG4iIDogIiI7CiAgICAgICAgICAgIGlmICh3aWR0aCA8PSBlbGxpcHNlc1dpZHRoKSB7CiAgICAgICAgICAgICAgICB2YXIgcGVyaW9kV2lkdGggPSBlbGxpcHNlc1dpZHRoIC8gMzsKICAgICAgICAgICAgICAgIHZhciBudW1QZXJpb2RzVGhhdEZpdCA9IE1hdGguZmxvb3Iod2lkdGggLyBwZXJpb2RXaWR0aCk7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIHJlbWFpbmluZ1Rva2VuOiBsaW5lLAogICAgICAgICAgICAgICAgICAgIHdyYXBwZWRUb2tlbjogcHJlZml4ICsgIi4uLiIuc3Vic3RyKDAsIG51bVBlcmlvZHNUaGF0Rml0KSwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgd2hpbGUgKGxpbmVXaWR0aCArIGVsbGlwc2VzV2lkdGggPiB3aWR0aCkgewogICAgICAgICAgICAgICAgdHJ1bmNhdGVkTGluZSA9IHV0aWxzLlN0cmluZ01ldGhvZHMudHJpbUVuZCh0cnVuY2F0ZWRMaW5lLnN1YnN0cigwLCB0cnVuY2F0ZWRMaW5lLmxlbmd0aCAtIDEpKTsKICAgICAgICAgICAgICAgIGxpbmVXaWR0aCA9IG1lYXN1cmVyLm1lYXN1cmUodHJ1bmNhdGVkTGluZSkud2lkdGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHJlbWFpbmluZ1Rva2VuOiB1dGlscy5TdHJpbmdNZXRob2RzLnRyaW1FbmQobGluZS5zdWJzdHJpbmcodHJ1bmNhdGVkTGluZS5sZW5ndGgpLCAiLSIpLnRyaW0oKSwKICAgICAgICAgICAgICAgIHdyYXBwZWRUb2tlbjogcHJlZml4ICsgdHJ1bmNhdGVkTGluZSArICIuLi4iLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgV3JhcHBlci5wcm90b3R5cGUud3JhcE5leHRUb2tlbiA9IGZ1bmN0aW9uICh0b2tlbiwgc3RhdGUsIG1lYXN1cmVyKSB7CiAgICAgICAgICAgIGlmICghc3RhdGUuY2FuRml0VGV4dCB8fAogICAgICAgICAgICAgICAgc3RhdGUuYXZhaWxhYmxlTGluZXMgPT09IHN0YXRlLndyYXBwaW5nLm5vTGluZXMgfHwKICAgICAgICAgICAgICAgICF0aGlzLmNhbkZpdFRva2VuKHRva2VuLCBzdGF0ZS5hdmFpbGFibGVXaWR0aCwgbWVhc3VyZXIpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5maW5pc2hXcmFwcGluZyh0b2tlbiwgc3RhdGUsIG1lYXN1cmVyKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgcmVtYWluaW5nVG9rZW4gPSB0b2tlbjsKICAgICAgICAgICAgd2hpbGUgKHJlbWFpbmluZ1Rva2VuKSB7CiAgICAgICAgICAgICAgICB2YXIgcmVzdWx0ID0gdGhpcy5icmVha1Rva2VuVG9GaXRJbldpZHRoKHJlbWFpbmluZ1Rva2VuLCBzdGF0ZS5jdXJyZW50TGluZSwgc3RhdGUuYXZhaWxhYmxlV2lkdGgsIG1lYXN1cmVyKTsKICAgICAgICAgICAgICAgIHN0YXRlLmN1cnJlbnRMaW5lID0gcmVzdWx0LmxpbmU7CiAgICAgICAgICAgICAgICByZW1haW5pbmdUb2tlbiA9IHJlc3VsdC5yZW1haW5pbmdUb2tlbjsKICAgICAgICAgICAgICAgIGlmIChyZW1haW5pbmdUb2tlbiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgc3RhdGUud3JhcHBpbmcubm9Ccm9rZVdvcmRzICs9ICtyZXN1bHQuYnJlYWtXb3JkOwogICAgICAgICAgICAgICAgICAgICsrc3RhdGUud3JhcHBpbmcubm9MaW5lczsKICAgICAgICAgICAgICAgICAgICBpZiAoc3RhdGUuYXZhaWxhYmxlTGluZXMgPT09IHN0YXRlLndyYXBwaW5nLm5vTGluZXMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIGVsbGlwc2lzUmVzdWx0ID0gdGhpcy5hZGRFbGxpcHNpcyhzdGF0ZS5jdXJyZW50TGluZSwgc3RhdGUuYXZhaWxhYmxlV2lkdGgsIG1lYXN1cmVyKTsKICAgICAgICAgICAgICAgICAgICAgICAgc3RhdGUud3JhcHBpbmcud3JhcHBlZFRleHQgKz0gZWxsaXBzaXNSZXN1bHQud3JhcHBlZFRva2VuOwogICAgICAgICAgICAgICAgICAgICAgICBzdGF0ZS53cmFwcGluZy50cnVuY2F0ZWRUZXh0ICs9IGVsbGlwc2lzUmVzdWx0LnJlbWFpbmluZ1Rva2VuICsgcmVtYWluaW5nVG9rZW47CiAgICAgICAgICAgICAgICAgICAgICAgIHN0YXRlLmN1cnJlbnRMaW5lID0gIlxuIjsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHN0YXRlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgc3RhdGUud3JhcHBpbmcud3JhcHBlZFRleHQgKz0gdXRpbHMuU3RyaW5nTWV0aG9kcy50cmltRW5kKHN0YXRlLmN1cnJlbnRMaW5lKTsKICAgICAgICAgICAgICAgICAgICAgICAgc3RhdGUuY3VycmVudExpbmUgPSAiXG4iOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gc3RhdGU7CiAgICAgICAgfTsKICAgICAgICBXcmFwcGVyLnByb3RvdHlwZS5maW5pc2hXcmFwcGluZyA9IGZ1bmN0aW9uICh0b2tlbiwgc3RhdGUsIG1lYXN1cmVyKSB7CiAgICAgICAgICAgIC8vIFRva2VuIGlzIHJlYWxseSBsb25nLCBidXQgd2UgaGF2ZSBhIHNwYWNlIHRvIHB1dCBwYXJ0IG9mIHRoZSB3b3JkLgogICAgICAgICAgICBpZiAoc3RhdGUuY2FuRml0VGV4dCAmJgogICAgICAgICAgICAgICAgc3RhdGUuYXZhaWxhYmxlTGluZXMgIT09IHN0YXRlLndyYXBwaW5nLm5vTGluZXMgJiYKICAgICAgICAgICAgICAgIHRoaXMuX3RleHRUcmltbWluZyAhPT0gIm5vbmUiKSB7CiAgICAgICAgICAgICAgICB2YXIgcmVzID0gdGhpcy5hZGRFbGxpcHNpcyhzdGF0ZS5jdXJyZW50TGluZSArIHRva2VuLCBzdGF0ZS5hdmFpbGFibGVXaWR0aCwgbWVhc3VyZXIpOwogICAgICAgICAgICAgICAgc3RhdGUud3JhcHBpbmcud3JhcHBlZFRleHQgKz0gcmVzLndyYXBwZWRUb2tlbjsKICAgICAgICAgICAgICAgIHN0YXRlLndyYXBwaW5nLnRydW5jYXRlZFRleHQgKz0gcmVzLnJlbWFpbmluZ1Rva2VuOwogICAgICAgICAgICAgICAgc3RhdGUud3JhcHBpbmcubm9Ccm9rZVdvcmRzICs9ICsocmVzLnJlbWFpbmluZ1Rva2VuLmxlbmd0aCA8IHRva2VuLmxlbmd0aCk7CiAgICAgICAgICAgICAgICBzdGF0ZS53cmFwcGluZy5ub0xpbmVzICs9ICsocmVzLndyYXBwZWRUb2tlbi5sZW5ndGggPiAwKTsKICAgICAgICAgICAgICAgIHN0YXRlLmN1cnJlbnRMaW5lID0gIiI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBzdGF0ZS53cmFwcGluZy50cnVuY2F0ZWRUZXh0ICs9IHRva2VuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHN0YXRlLmNhbkZpdFRleHQgPSBmYWxzZTsKICAgICAgICAgICAgcmV0dXJuIHN0YXRlOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQnJlYWtzIHNpbmdsZSB0b2tlbiB0byBmaXQgY3VycmVudCBsaW5lLgogICAgICAgICAqIElmIHRva2VuIGNvbnRhaW5zIG9ubHkgd2hpdGVzcGFjZXMgdGhlbiB0aGV5IHdpbGwgbm90IGJlIHBvcHVsYXRlZCB0byBuZXh0IGxpbmUuCiAgICAgICAgICovCiAgICAgICAgV3JhcHBlci5wcm90b3R5cGUuYnJlYWtUb2tlblRvRml0SW5XaWR0aCA9IGZ1bmN0aW9uICh0b2tlbiwgbGluZSwgYXZhaWxhYmxlV2lkdGgsIG1lYXN1cmVyLCBicmVha2luZ0NoYXJhY3RlcikgewogICAgICAgICAgICBpZiAoYnJlYWtpbmdDaGFyYWN0ZXIgPT09IHZvaWQgMCkgeyBicmVha2luZ0NoYXJhY3RlciA9IHRoaXMuX2JyZWFraW5nQ2hhcmFjdGVyOyB9CiAgICAgICAgICAgIGlmIChtZWFzdXJlci5tZWFzdXJlKGxpbmUgKyB0b2tlbikud2lkdGggPD0gYXZhaWxhYmxlV2lkdGgpIHsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWtXb3JkOiBmYWxzZSwKICAgICAgICAgICAgICAgICAgICBsaW5lOiBsaW5lICsgdG9rZW4sCiAgICAgICAgICAgICAgICAgICAgcmVtYWluaW5nVG9rZW46IG51bGwsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0b2tlbi50cmltKCkgPT09ICIiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIGJyZWFrV29yZDogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgbGluZTogbGluZSwKICAgICAgICAgICAgICAgICAgICByZW1haW5pbmdUb2tlbjogIiIsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIGlmIHdlIGRvbid0IGFsbG93IGJyZWFraW5nIHdvcmRzIEFORCB0aGUgdG9rZW4gaXNuJ3QgdGhlIG9ubHkgdGhpbmcgb24gdGhlIGN1cnJlbnQgbGluZS4KICAgICAgICAgICAgaWYgKCF0aGlzLl9hbGxvd0JyZWFraW5nV29yZHMgJiYgbGluZS50cmltKCkgIT09ICIiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIGJyZWFrV29yZDogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgbGluZTogbGluZSwKICAgICAgICAgICAgICAgICAgICByZW1haW5pbmdUb2tlbjogdG9rZW4sCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBmaXRUb2tlbkxlbmd0aCA9IDA7CiAgICAgICAgICAgIHdoaWxlIChmaXRUb2tlbkxlbmd0aCA8IHRva2VuLmxlbmd0aCkgewogICAgICAgICAgICAgICAgaWYgKG1lYXN1cmVyLm1lYXN1cmUobGluZSArIHRva2VuLnN1YnN0cmluZygwLCBmaXRUb2tlbkxlbmd0aCArIDEpICsgYnJlYWtpbmdDaGFyYWN0ZXIpLndpZHRoIDw9IGF2YWlsYWJsZVdpZHRoKSB7CiAgICAgICAgICAgICAgICAgICAgKytmaXRUb2tlbkxlbmd0aDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBzdWZmaXggPSAiIjsKICAgICAgICAgICAgaWYgKGZpdFRva2VuTGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgc3VmZml4ID0gYnJlYWtpbmdDaGFyYWN0ZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGJyZWFrV29yZDogZml0VG9rZW5MZW5ndGggPiAwLAogICAgICAgICAgICAgICAgbGluZTogbGluZSArIHRva2VuLnN1YnN0cmluZygwLCBmaXRUb2tlbkxlbmd0aCkgKyBzdWZmaXgsCiAgICAgICAgICAgICAgICByZW1haW5pbmdUb2tlbjogdG9rZW4uc3Vic3RyaW5nKGZpdFRva2VuTGVuZ3RoKSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBXcmFwcGVyOwogICAgfSgpKTsKICAgIGV4cG9ydHMuV3JhcHBlciA9IFdyYXBwZXI7CgogICAgfSk7CgogICAgdmFyIHNpbmdsZUxpbmVXcmFwcGVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcywgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICogTGljZW5zZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlICh0aGUgIkxpY2Vuc2UiKTsgeW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZQogICAgICogbGljZW5zZSBhdCBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvdHlwZXNldHRhYmxlL2Jsb2IvZGV2ZWxvcC9MSUNFTlNFCiAgICAgKi8KICAgIHZhciBfX2V4dGVuZHMgPSAoY29tbW9uanNHbG9iYWwgJiYgY29tbW9uanNHbG9iYWwuX19leHRlbmRzKSB8fCAoZnVuY3Rpb24gKCkgewogICAgICAgIHZhciBleHRlbmRTdGF0aWNzID0gT2JqZWN0LnNldFByb3RvdHlwZU9mIHx8CiAgICAgICAgICAgICh7IF9fcHJvdG9fXzogW10gfSBpbnN0YW5jZW9mIEFycmF5ICYmIGZ1bmN0aW9uIChkLCBiKSB7IGQuX19wcm90b19fID0gYjsgfSkgfHwKICAgICAgICAgICAgZnVuY3Rpb24gKGQsIGIpIHsgZm9yICh2YXIgcCBpbiBiKSBpZiAoYi5oYXNPd25Qcm9wZXJ0eShwKSkgZFtwXSA9IGJbcF07IH07CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkLCBiKSB7CiAgICAgICAgICAgIGV4dGVuZFN0YXRpY3MoZCwgYik7CiAgICAgICAgICAgIGZ1bmN0aW9uIF9fKCkgeyB0aGlzLmNvbnN0cnVjdG9yID0gZDsgfQogICAgICAgICAgICBkLnByb3RvdHlwZSA9IGIgPT09IG51bGwgPyBPYmplY3QuY3JlYXRlKGIpIDogKF9fLnByb3RvdHlwZSA9IGIucHJvdG90eXBlLCBuZXcgX18oKSk7CiAgICAgICAgfTsKICAgIH0pKCk7CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBTaW5nbGVMaW5lV3JhcHBlciA9IChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgX19leHRlbmRzKFNpbmdsZUxpbmVXcmFwcGVyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFNpbmdsZUxpbmVXcmFwcGVyKCkgewogICAgICAgICAgICByZXR1cm4gX3N1cGVyICE9PSBudWxsICYmIF9zdXBlci5hcHBseSh0aGlzLCBhcmd1bWVudHMpIHx8IHRoaXM7CiAgICAgICAgfQogICAgICAgIFNpbmdsZUxpbmVXcmFwcGVyLnByb3RvdHlwZS53cmFwID0gZnVuY3Rpb24gKHRleHQsIG1lYXN1cmVyLCB3aWR0aCwgaGVpZ2h0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmIChoZWlnaHQgPT09IHZvaWQgMCkgeyBoZWlnaHQgPSBJbmZpbml0eTsgfQogICAgICAgICAgICB2YXIgbGluZXMgPSB0ZXh0LnNwbGl0KCJcbiIpOwogICAgICAgICAgICBpZiAobGluZXMubGVuZ3RoID4gMSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTaW5nbGVMaW5lV3JhcHBlciBpcyBkZXNpZ25lZCB0byB3b3JrIG9ubHkgb24gc2luZ2xlIGxpbmUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgd3JhcEZOID0gZnVuY3Rpb24gKHcpIHsgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUud3JhcC5jYWxsKF90aGlzLCB0ZXh0LCBtZWFzdXJlciwgdywgaGVpZ2h0KTsgfTsKICAgICAgICAgICAgdmFyIHJlc3VsdCA9IHdyYXBGTih3aWR0aCk7CiAgICAgICAgICAgIGlmIChyZXN1bHQubm9MaW5lcyA8IDIpIHsKICAgICAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGxlZnQgPSAwOwogICAgICAgICAgICB2YXIgcmlnaHQgPSB3aWR0aDsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBTaW5nbGVMaW5lV3JhcHBlci5OT19XUkFQX0lURVJBVElPTlMgJiYgcmlnaHQgPiBsZWZ0OyArK2kpIHsKICAgICAgICAgICAgICAgIHZhciBjdXJyZW50V2lkdGggPSAocmlnaHQgKyBsZWZ0KSAvIDI7CiAgICAgICAgICAgICAgICB2YXIgY3VycmVudFJlc3VsdCA9IHdyYXBGTihjdXJyZW50V2lkdGgpOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuYXJlU2FtZVJlc3VsdHMocmVzdWx0LCBjdXJyZW50UmVzdWx0KSkgewogICAgICAgICAgICAgICAgICAgIHJpZ2h0ID0gY3VycmVudFdpZHRoOwogICAgICAgICAgICAgICAgICAgIHJlc3VsdCA9IGN1cnJlbnRSZXN1bHQ7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBsZWZ0ID0gY3VycmVudFdpZHRoOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfTsKICAgICAgICBTaW5nbGVMaW5lV3JhcHBlci5wcm90b3R5cGUuYXJlU2FtZVJlc3VsdHMgPSBmdW5jdGlvbiAob25lLCB0d28pIHsKICAgICAgICAgICAgcmV0dXJuIG9uZS5ub0xpbmVzID09PSB0d28ubm9MaW5lcyAmJiBvbmUudHJ1bmNhdGVkVGV4dCA9PT0gdHdvLnRydW5jYXRlZFRleHQ7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gU2luZ2xlTGluZVdyYXBwZXI7CiAgICB9KHdyYXBwZXIuV3JhcHBlcikpOwogICAgU2luZ2xlTGluZVdyYXBwZXIuTk9fV1JBUF9JVEVSQVRJT05TID0gNTsKICAgIGV4cG9ydHMuU2luZ2xlTGluZVdyYXBwZXIgPSBTaW5nbGVMaW5lV3JhcHBlcjsKCiAgICB9KTsKCiAgICB2YXIgd3JhcHBlcnMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzLCBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCiAgICAgKiBMaWNlbnNlZCB1bmRlciB0aGUgTUlUIExpY2Vuc2UgKHRoZSAiTGljZW5zZSIpOyB5b3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlCiAgICAgKiBsaWNlbnNlIGF0IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci90eXBlc2V0dGFibGUvYmxvYi9kZXZlbG9wL0xJQ0VOU0UKICAgICAqLwogICAgZnVuY3Rpb24gX19leHBvcnQobSkgewogICAgICAgIGZvciAodmFyIHAgaW4gbSkgaWYgKCFleHBvcnRzLmhhc093blByb3BlcnR5KHApKSBleHBvcnRzW3BdID0gbVtwXTsKICAgIH0KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICBfX2V4cG9ydChzaW5nbGVMaW5lV3JhcHBlcik7CiAgICBfX2V4cG9ydCh3cmFwcGVyKTsKCiAgICB9KTsKCiAgICB2YXIgdHlwZXNldHRlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMsIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgICAqIExpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgTGljZW5zZSAodGhlICJMaWNlbnNlIik7IHlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUKICAgICAqIGxpY2Vuc2UgYXQgaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3R5cGVzZXR0YWJsZS9ibG9iL2RldmVsb3AvTElDRU5TRQogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIC8qKgogICAgICogVGhpcyBpcyBhIGNvbnZlbmllbmNlIGludGVyZmFjZSBmb3IgdHlwZXNldHRpbmcgc3RyaW5ncyB1c2luZyB0aGUgZGVmYXVsdAogICAgICogbWVhc3VyZXIvd3JhcHBlci93cml0ZXIgc2V0dXAuCiAgICAgKi8KICAgIHZhciBUeXBlc2V0dGVyID0gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBUeXBlc2V0dGVyKGNvbnRleHQpIHsKICAgICAgICAgICAgdGhpcy5jb250ZXh0ID0gY29udGV4dDsKICAgICAgICAgICAgdGhpcy5tZWFzdXJlciA9IG5ldyBtZWFzdXJlcnMuQ2FjaGVNZWFzdXJlcih0aGlzLmNvbnRleHQpOwogICAgICAgICAgICB0aGlzLndyYXBwZXIgPSBuZXcgd3JhcHBlcnMuV3JhcHBlcigpOwogICAgICAgICAgICB0aGlzLndyaXRlciA9IG5ldyB3cml0ZXJzLldyaXRlcih0aGlzLm1lYXN1cmVyLCB0aGlzLmNvbnRleHQsIHRoaXMud3JhcHBlcik7CiAgICAgICAgfQogICAgICAgIFR5cGVzZXR0ZXIuc3ZnID0gZnVuY3Rpb24gKGVsZW1lbnQsIGNsYXNzTmFtZSwgYWRkVGl0bGVFbGVtZW50KSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgVHlwZXNldHRlcihuZXcgY29udGV4dHMuU3ZnQ29udGV4dChlbGVtZW50LCBjbGFzc05hbWUsIGFkZFRpdGxlRWxlbWVudCkpOwogICAgICAgIH07CiAgICAgICAgVHlwZXNldHRlci5jYW52YXMgPSBmdW5jdGlvbiAoY3R4LCBsaW5lSGVpZ2h0LCBzdHlsZSkgewogICAgICAgICAgICByZXR1cm4gbmV3IFR5cGVzZXR0ZXIobmV3IGNvbnRleHRzLkNhbnZhc0NvbnRleHQoY3R4LCBsaW5lSGVpZ2h0LCBzdHlsZSkpOwogICAgICAgIH07CiAgICAgICAgVHlwZXNldHRlci5odG1sID0gZnVuY3Rpb24gKGVsZW1lbnQsIGNsYXNzTmFtZSwgYWRkVGl0bGUpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBUeXBlc2V0dGVyKG5ldyBjb250ZXh0cy5IdG1sQ29udGV4dChlbGVtZW50LCBjbGFzc05hbWUsIGFkZFRpdGxlKSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBXcmFwcyB0aGUgZ2l2ZW4gc3RyaW5nIGludG8gdGhlIHdpZHRoL2hlaWdodCBhbmQgd3JpdGVzIGl0IGludG8gdGhlCiAgICAgICAgICogY2FudmFzIG9yIFNWRyAoZGVwZW5kaW5nIG9uIGNvbnRleHQpLgogICAgICAgICAqCiAgICAgICAgICogRGVsZWdhdGVzIHRvIGBXcml0ZXIud3JpdGVgIHVzaW5nIHRoZSBpbnRlcm5hbCBgSVR5cGVzZXR0ZXJDb250ZXh0YC4KICAgICAgICAgKi8KICAgICAgICBUeXBlc2V0dGVyLnByb3RvdHlwZS53cml0ZSA9IGZ1bmN0aW9uICh0ZXh0LCB3aWR0aCwgaGVpZ2h0LCBvcHRpb25zLCBpbnRvKSB7CiAgICAgICAgICAgIHRoaXMud3JpdGVyLndyaXRlKHRleHQsIHdpZHRoLCBoZWlnaHQsIG9wdGlvbnMsIGludG8pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQ2xlYXJzIHRoZSBgTWVhc3VyZXJgJ3MgQ2FjaGVNZWFzdXJlci4KICAgICAgICAgKgogICAgICAgICAqIENhbGwgdGhpcyBpZiB5b3VyIGZvbnQgc3R5bGUgY2hhbmdlZSBpbiBTVkcuCiAgICAgICAgICovCiAgICAgICAgVHlwZXNldHRlci5wcm90b3R5cGUuY2xlYXJNZWFzdXJlckNhY2hlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLm1lYXN1cmVyLnJlc2V0KCk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gVHlwZXNldHRlcjsKICAgIH0oKSk7CiAgICBleHBvcnRzLlR5cGVzZXR0ZXIgPSBUeXBlc2V0dGVyOwoKICAgIH0pOwoKICAgIHZhciBzcmMkMSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMsIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgICAqIExpY2Vuc2VkIHVuZGVyIHRoZSBNSVQgTGljZW5zZSAodGhlICJMaWNlbnNlIik7IHlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUKICAgICAqIGxpY2Vuc2UgYXQgaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3R5cGVzZXR0YWJsZS9ibG9iL2RldmVsb3AvTElDRU5TRQogICAgICovCiAgICBmdW5jdGlvbiBfX2V4cG9ydChtKSB7CiAgICAgICAgZm9yICh2YXIgcCBpbiBtKSBpZiAoIWV4cG9ydHMuaGFzT3duUHJvcGVydHkocCkpIGV4cG9ydHNbcF0gPSBtW3BdOwogICAgfQogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIF9fZXhwb3J0KGNvbnRleHRzKTsKICAgIF9fZXhwb3J0KG1lYXN1cmVycyk7CiAgICBfX2V4cG9ydCh0eXBlc2V0dGVyKTsKICAgIF9fZXhwb3J0KHV0aWxzKTsKICAgIF9fZXhwb3J0KHdyYXBwZXJzKTsKICAgIF9fZXhwb3J0KHdyaXRlcnMpOwoKICAgIH0pOwoKICAgIHZhciBhcnJheVV0aWxzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgdmFyIG5hdGl2ZUFycmF5ID0gd2luZG93LkFycmF5OwogICAgLyoqCiAgICAgKiBUYWtlcyB0d28gYXJyYXlzIG9mIG51bWJlcnMgYW5kIGFkZHMgdGhlbSB0b2dldGhlcgogICAgICoKICAgICAqIEBwYXJhbSB7bnVtYmVyW119IGFMaXN0IFRoZSBmaXJzdCBhcnJheSBvZiBudW1iZXJzCiAgICAgKiBAcGFyYW0ge251bWJlcltdfSBiTGlzdCBUaGUgc2Vjb25kIGFycmF5IG9mIG51bWJlcnMKICAgICAqIEByZXR1cm4ge251bWJlcltdfSBBbiBhcnJheSBvZiBudW1iZXJzIHdoZXJlIHhbaV0gPSBhTGlzdFtpXSArIGJMaXN0W2ldCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFkZChhTGlzdCwgYkxpc3QpIHsKICAgICAgICBpZiAoYUxpc3QubGVuZ3RoICE9PSBiTGlzdC5sZW5ndGgpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJhdHRlbXB0ZWQgdG8gYWRkIGFycmF5cyBvZiB1bmVxdWFsIGxlbmd0aCIpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gYUxpc3QubWFwKGZ1bmN0aW9uIChfLCBpKSB7IHJldHVybiBhTGlzdFtpXSArIGJMaXN0W2ldOyB9KTsKICAgIH0KICAgIGV4cG9ydHMuYWRkID0gYWRkOwogICAgLyoqCiAgICAgKiBUYWtlIGFuIGFycmF5IG9mIHZhbHVlcywgYW5kIHJldHVybiB0aGUgdW5pcXVlIHZhbHVlcy4KICAgICAqIFdpbGwgd29yayBpZmYg4oiAIGEsIGIsIGEudG9TdHJpbmcoKSA9PSBiLnRvU3RyaW5nKCkgPT4gYSA9PSBiOyB3aWxsIGJyZWFrIG9uIE9iamVjdCBpbnB1dHMKICAgICAqCiAgICAgKiBAcGFyYW0ge1RbXX0gdmFsdWVzIFRoZSB2YWx1ZXMgdG8gZmluZCB1bmlxdWVuZXNzIGZvcgogICAgICogQHJldHVybiB7VFtdfSBUaGUgdW5pcXVlIHZhbHVlcwogICAgICovCiAgICBmdW5jdGlvbiB1bmlxKGFycikgewogICAgICAgIHZhciBzZWVuID0gZDMuc2V0KCk7CiAgICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICAgIGFyci5mb3JFYWNoKGZ1bmN0aW9uICh4KSB7CiAgICAgICAgICAgIGlmICghc2Vlbi5oYXMoU3RyaW5nKHgpKSkgewogICAgICAgICAgICAgICAgc2Vlbi5hZGQoU3RyaW5nKHgpKTsKICAgICAgICAgICAgICAgIHJlc3VsdC5wdXNoKHgpOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KICAgIGV4cG9ydHMudW5pcSA9IHVuaXE7CiAgICAvKioKICAgICAqIEBwYXJhbSB7VFtdW119IGEgVGhlIDJEIGFycmF5IHRoYXQgd2lsbCBoYXZlIGl0cyBlbGVtZW50cyBqb2luZWQgdG9nZXRoZXIuCiAgICAgKiBAcmV0dXJuIHtUW119IEV2ZXJ5IGFycmF5IGluIGEsIGNvbmNhdGVuYXRlZCB0b2dldGhlciBpbiB0aGUgb3JkZXIgdGhleSBhcHBlYXIuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZsYXR0ZW4oYSkgewogICAgICAgIHJldHVybiBuYXRpdmVBcnJheS5wcm90b3R5cGUuY29uY2F0LmFwcGx5KFtdLCBhKTsKICAgIH0KICAgIGV4cG9ydHMuZmxhdHRlbiA9IGZsYXR0ZW47CiAgICAvKioKICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgbGVuZ3RoIGBjb3VudGAsIGZpbGxlZCB3aXRoIHZhbHVlIG9yIChpZiB2YWx1ZSBpcyBhIGZ1bmN0aW9uKSwgdmFsdWUoKQogICAgICoKICAgICAqIEBwYXJhbSB7VCB8ICgoaW5kZXg/OiBudW1iZXIpID0+IFQpfSB2YWx1ZSBUaGUgdmFsdWUgdG8gZmlsbCB0aGUgYXJyYXkgd2l0aCBvciBhIHZhbHVlIGdlbmVyYXRvciAoY2FsbGVkIHdpdGggaW5kZXggYXMgYXJnKQogICAgICogQHBhcmFtIHtudW1iZXJ9IGNvdW50IFRoZSBsZW5ndGggb2YgdGhlIGFycmF5IHRvIGdlbmVyYXRlCiAgICAgKiBAcmV0dXJuIHthbnlbXX0KICAgICAqLwogICAgZnVuY3Rpb24gY3JlYXRlRmlsbGVkQXJyYXkodmFsdWUsIGNvdW50KSB7CiAgICAgICAgdmFyIG91dCA9IFtdOwogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgY291bnQ7IGkrKykgewogICAgICAgICAgICBvdXRbaV0gPSB0eXBlb2YgKHZhbHVlKSA9PT0gImZ1bmN0aW9uIiA/IHZhbHVlKGkpIDogdmFsdWU7CiAgICAgICAgfQogICAgICAgIHJldHVybiBvdXQ7CiAgICB9CiAgICBleHBvcnRzLmNyZWF0ZUZpbGxlZEFycmF5ID0gY3JlYXRlRmlsbGVkQXJyYXk7CiAgICB9KTsKCiAgICB2YXIgY29sb3JVdGlscyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBuYXRpdmVNYXRoID0gd2luZG93Lk1hdGg7CiAgICAvKioKICAgICAqIFJldHVybiBjb250cmFzdCByYXRpbyBiZXR3ZWVuIHR3byBjb2xvcnMKICAgICAqIEJhc2VkIG9uIGltcGxlbWVudGF0aW9uIGZyb20gY2hyb21hLmpzIGJ5IEdyZWdvciBBaXNjaCAoZ2thKSAobGljZW5zZWQgdW5kZXIgQlNEKQogICAgICogY2hyb21hLmpzIG1heSBiZSBmb3VuZCBoZXJlOiBodHRwczovL2dpdGh1Yi5jb20vZ2thL2Nocm9tYS5qcwogICAgICogTGljZW5zZSBtYXkgYmUgZm91bmQgaGVyZTogaHR0cHM6Ly9naXRodWIuY29tL2drYS9jaHJvbWEuanMvYmxvYi9tYXN0ZXIvTElDRU5TRQogICAgICogc2VlIGh0dHA6Ly93d3cudzMub3JnL1RSLzIwMDgvUkVDLVdDQUcyMC0yMDA4MTIxMS8jY29udHJhc3QtcmF0aW9kZWYKICAgICAqLwogICAgZnVuY3Rpb24gY29udHJhc3QoYSwgYikgewogICAgICAgIHZhciBsMSA9IGx1bWluYW5jZShhKSArIDAuMDU7CiAgICAgICAgdmFyIGwyID0gbHVtaW5hbmNlKGIpICsgMC4wNTsKICAgICAgICByZXR1cm4gbDEgPiBsMiA/IGwxIC8gbDIgOiBsMiAvIGwxOwogICAgfQogICAgZXhwb3J0cy5jb250cmFzdCA9IGNvbnRyYXN0OwogICAgLyoqCiAgICAgKiBSZXR1cm5zIGEgYnJpZ2h0ZXIgY29weSBvZiB0aGlzIGNvbG9yLiBFYWNoIGNoYW5uZWwgaXMgbXVsdGlwbGllZCBieSAwLjcgXiAtZmFjdG9yLgogICAgICogQ2hhbm5lbCB2YWx1ZXMgYXJlIGNhcHBlZCBhdCB0aGUgbWF4aW11bSB2YWx1ZSBvZiAyNTUsIGFuZCB0aGUgbWluaW11bSB2YWx1ZSBvZiAzMC4KICAgICAqLwogICAgZnVuY3Rpb24gbGlnaHRlbkNvbG9yKGNvbG9yLCBmYWN0b3IpIHsKICAgICAgICB2YXIgYnJpZ2h0ZW5lZCA9IGQzLmNvbG9yKGNvbG9yKS5icmlnaHRlcihmYWN0b3IpOwogICAgICAgIHJldHVybiBicmlnaHRlbmVkLnJnYigpLnRvU3RyaW5nKCk7CiAgICB9CiAgICBleHBvcnRzLmxpZ2h0ZW5Db2xvciA9IGxpZ2h0ZW5Db2xvcjsKICAgIC8qKgogICAgICogR2V0cyB0aGUgSGV4IENvZGUgb2YgdGhlIGNvbG9yIHJlc3VsdGluZyBieSBhcHBseWluZyB0aGUgY2xhc3NOYW1lIENTUyBjbGFzcyB0byB0aGUKICAgICAqIGNvbG9yVGVzdGVyIHNlbGVjdGlvbi4gUmV0dXJucyBudWxsIGlmIHRoZSB0ZXN0ZXIgaXMgdHJhbnNwYXJlbnQuCiAgICAgKgogICAgICogQHBhcmFtIHtkMy5TZWxlY3Rpb248dm9pZD59IGNvbG9yVGVzdGVyIFRoZSBkMyBzZWxlY3Rpb24gdG8gYXBwbHkgdGhlIENTUyBjbGFzcyB0bwogICAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gYmUgYXBwbGllZAogICAgICogQHJldHVybiB7c3RyaW5nfSBUaGUgaGV4IGNvZGUgb2YgdGhlIGNvbXB1dGVkIGNvbG9yCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbG9yVGVzdChjb2xvclRlc3RlciwgY2xhc3NOYW1lKSB7CiAgICAgICAgY29sb3JUZXN0ZXIuY2xhc3NlZChjbGFzc05hbWUsIHRydWUpOwogICAgICAgIC8vIFVzZSByZWdleCB0byBnZXQgdGhlIHRleHQgaW5zaWRlIHRoZSByZ2IgcGFyZW50aGVzZXMKICAgICAgICB2YXIgY29sb3JTdHlsZSA9IGNvbG9yVGVzdGVyLnN0eWxlKCJiYWNrZ3JvdW5kLWNvbG9yIik7CiAgICAgICAgaWYgKGNvbG9yU3R5bGUgPT09ICJ0cmFuc3BhcmVudCIpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIHZhciBtYXRjaCA9IC9cKCguKylcKS8uZXhlYyhjb2xvclN0eWxlKTsKICAgICAgICBpZiAoIW1hdGNoKSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICB2YXIgcmdiID0gbWF0Y2hbMV0KICAgICAgICAgICAgLnNwbGl0KCIsIikKICAgICAgICAgICAgLm1hcChmdW5jdGlvbiAoY29sb3JWYWx1ZSkgewogICAgICAgICAgICB2YXIgY29sb3JOdW1iZXIgPSArY29sb3JWYWx1ZTsKICAgICAgICAgICAgdmFyIGhleFZhbHVlID0gY29sb3JOdW1iZXIudG9TdHJpbmcoMTYpOwogICAgICAgICAgICByZXR1cm4gY29sb3JOdW1iZXIgPCAxNiA/ICIwIiArIGhleFZhbHVlIDogaGV4VmFsdWU7CiAgICAgICAgfSk7CiAgICAgICAgaWYgKHJnYi5sZW5ndGggPT09IDQgJiYgcmdiWzNdID09PSAiMDAiKSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICB2YXIgaGV4Q29kZSA9ICIjIiArIHJnYi5qb2luKCIiKTsKICAgICAgICBjb2xvclRlc3Rlci5jbGFzc2VkKGNsYXNzTmFtZSwgZmFsc2UpOwogICAgICAgIHJldHVybiBoZXhDb2RlOwogICAgfQogICAgZXhwb3J0cy5jb2xvclRlc3QgPSBjb2xvclRlc3Q7CiAgICAvKioKICAgICAqIFJldHVybiByZWxhdGl2ZSBsdW1pbmFuY2UgKGRlZmluZWQgaGVyZTogaHR0cDovL3d3dy53My5vcmcvVFIvMjAwOC9SRUMtV0NBRzIwLTIwMDgxMjExLyNyZWxhdGl2ZWx1bWluYW5jZWRlZikKICAgICAqIEJhc2VkIG9uIGltcGxlbWVudGF0aW9uIGZyb20gY2hyb21hLmpzIGJ5IEdyZWdvciBBaXNjaCAoZ2thKSAobGljZW5zZWQgdW5kZXIgQlNEKQogICAgICogY2hyb21hLmpzIG1heSBiZSBmb3VuZCBoZXJlOiBodHRwczovL2dpdGh1Yi5jb20vZ2thL2Nocm9tYS5qcwogICAgICogTGljZW5zZSBtYXkgYmUgZm91bmQgaGVyZTogaHR0cHM6Ly9naXRodWIuY29tL2drYS9jaHJvbWEuanMvYmxvYi9tYXN0ZXIvTElDRU5TRQogICAgICovCiAgICBmdW5jdGlvbiBsdW1pbmFuY2UoY29sb3IpIHsKICAgICAgICB2YXIgcmdiID0gZDMucmdiKGNvbG9yKTsKICAgICAgICB2YXIgbHVtID0gZnVuY3Rpb24gKHgpIHsKICAgICAgICAgICAgeCA9IHggLyAyNTU7CiAgICAgICAgICAgIHJldHVybiB4IDw9IDAuMDM5MjggPyB4IC8gMTIuOTIgOiBuYXRpdmVNYXRoLnBvdygoeCArIDAuMDU1KSAvIDEuMDU1LCAyLjQpOwogICAgICAgIH07CiAgICAgICAgdmFyIHIgPSBsdW0ocmdiLnIpOwogICAgICAgIHZhciBnID0gbHVtKHJnYi5nKTsKICAgICAgICB2YXIgYiA9IGx1bShyZ2IuYik7CiAgICAgICAgcmV0dXJuIDAuMjEyNiAqIHIgKyAwLjcxNTIgKiBnICsgMC4wNzIyICogYjsKICAgIH0KICAgIH0pOwoKICAgIHZhciBkb21VdGlscyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHZhciBuYXRpdmVNYXRoID0gd2luZG93Lk1hdGg7CiAgICAvKioKICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgY2hpbGQgaXMgaW4gZmFjdCBhIGNoaWxkIG9mIHRoZSBwYXJlbnQKICAgICAqLwogICAgZnVuY3Rpb24gY29udGFpbnMocGFyZW50LCBjaGlsZCkgewogICAgICAgIHZhciBtYXliZVBhcmVudCA9IGNoaWxkOwogICAgICAgIHdoaWxlIChtYXliZVBhcmVudCAhPSBudWxsICYmIG1heWJlUGFyZW50ICE9PSBwYXJlbnQpIHsKICAgICAgICAgICAgbWF5YmVQYXJlbnQgPSBtYXliZVBhcmVudC5wYXJlbnROb2RlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gbWF5YmVQYXJlbnQgPT09IHBhcmVudDsKICAgIH0KICAgIGV4cG9ydHMuY29udGFpbnMgPSBjb250YWluczsKICAgIC8qKgogICAgICogR2V0cyB0aGUgYm91bmRpbmcgYm94IG9mIGFuIGVsZW1lbnQuCiAgICAgKiBAcGFyYW0ge2QzLlNlbGVjdGlvbn0gZWxlbWVudAogICAgICogQHJldHVybnMge1NWR1JlZH0gVGhlIGJvdW5kaW5nIGJveC4KICAgICAqLwogICAgZnVuY3Rpb24gZWxlbWVudEJCb3goZWxlbWVudCkgewogICAgICAgIHZhciBiYm94OwogICAgICAgIC8vIEhBQ0tIQUNLOiBGaXJlZm94IHdvbid0IGNvcnJlY3RseSBtZWFzdXJlIG5vZGVzIHdpdGggc3R5bGUgImRpc3BsYXk6IG5vbmUiIG9yIHRoZWlyIGRlc2NlbmRlbnRzIChGRiBCdWcgNjEyMTE4KS4KICAgICAgICB0cnkgewogICAgICAgICAgICBiYm94ID0gZWxlbWVudC5ub2RlKCkuZ2V0QkJveCgpOwogICAgICAgIH0KICAgICAgICBjYXRjaCAoZXJyKSB7CiAgICAgICAgICAgIGJib3ggPSB7IHg6IDAsIHk6IDAsIHdpZHRoOiAwLCBoZWlnaHQ6IDAgfTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGJib3g7CiAgICB9CiAgICBleHBvcnRzLmVsZW1lbnRCQm94ID0gZWxlbWVudEJCb3g7CiAgICBmdW5jdGlvbiBlbnRpdHlCb3VuZHMoZWxlbWVudCkgewogICAgICAgIGlmIChlbGVtZW50IGluc3RhbmNlb2YgU1ZHRWxlbWVudCkgewogICAgICAgICAgICByZXR1cm4gZWxlbWVudEJCb3goZDMuc2VsZWN0KGVsZW1lbnQpKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoZWxlbWVudCBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7CiAgICAgICAgICAgIHZhciByZWN0ID0gZWxlbWVudC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAgICAgcmV0dXJuIHsgeDogcmVjdC5sZWZ0LCB5OiByZWN0LnRvcCwgd2lkdGg6IHJlY3Qud2lkdGgsIGhlaWdodDogcmVjdC5oZWlnaHQgfTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHJldHVybiB7IHg6IDAsIHk6IDAsIHdpZHRoOiAwLCBoZWlnaHQ6IDAgfTsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLmVudGl0eUJvdW5kcyA9IGVudGl0eUJvdW5kczsKICAgIC8qKgogICAgICogU2NyZWVuIHJlZnJlc2ggcmF0ZSB3aGljaCBpcyBhc3N1bWVkIHRvIGJlIDYwZnBzCiAgICAgKi8KICAgIGV4cG9ydHMuU0NSRUVOX1JFRlJFU0hfUkFURV9NSUxMSVNFQ09ORFMgPSAxMDAwIC8gNjA7CiAgICAvKioKICAgICAqIFBvbHlmaWxsIGZvciBgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZWAuCiAgICAgKiBJZiB0aGUgZnVuY3Rpb24gZXhpc3RzLCB0aGVuIHdlIHVzZSB0aGUgZnVuY3Rpb24gZGlyZWN0bHkuCiAgICAgKiBPdGhlcndpc2UsIHdlIHNldCBhIHRpbWVvdXQgb24gYFNDUkVFTl9SRUZSRVNIX1JBVEVfTUlMTElTRUNPTkRTYCBhbmQgdGhlbiBwZXJmb3JtIHRoZSBmdW5jdGlvbi4KICAgICAqCiAgICAgKiBAcGFyYW0geygpID0+IHZvaWR9IGNhbGxiYWNrIFRoZSBjYWxsYmFjayB0byBjYWxsIGluIHRoZSBuZXh0IGFuaW1hdGlvbiBmcmFtZQogICAgICovCiAgICBmdW5jdGlvbiByZXF1ZXN0QW5pbWF0aW9uRnJhbWVQb2x5ZmlsbChjYWxsYmFjaykgewogICAgICAgIGlmICh3aW5kb3cucmVxdWVzdEFuaW1hdGlvbkZyYW1lICE9IG51bGwpIHsKICAgICAgICAgICAgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZShjYWxsYmFjayk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBzZXRUaW1lb3V0KGNhbGxiYWNrLCBleHBvcnRzLlNDUkVFTl9SRUZSRVNIX1JBVEVfTUlMTElTRUNPTkRTKTsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLnJlcXVlc3RBbmltYXRpb25GcmFtZVBvbHlmaWxsID0gcmVxdWVzdEFuaW1hdGlvbkZyYW1lUG9seWZpbGw7CiAgICAvKioKICAgICAqIENhbGN1bGF0ZXMgdGhlIHdpZHRoIG9mIHRoZSBlbGVtZW50LgogICAgICogVGhlIHdpZHRoIGluY2x1ZGVzIHRoZSBwYWRkaW5nIGFuZCB0aGUgYm9yZGVyIG9uIHRoZSBlbGVtZW50J3MgbGVmdCBhbmQgcmlnaHQgc2lkZXMuCiAgICAgKgogICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50IFRoZSBlbGVtZW50IHRvIHF1ZXJ5CiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBUaGUgd2lkdGggb2YgdGhlIGVsZW1lbnQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVsZW1lbnRXaWR0aChlbGVtZW50T3JTZWxlY3Rpb24pIHsKICAgICAgICB2YXIgZWxlbWVudCA9IGVsZW1lbnRPclNlbGVjdGlvbiBpbnN0YW5jZW9mIGQzLnNlbGVjdGlvbgogICAgICAgICAgICA/IGVsZW1lbnRPclNlbGVjdGlvbi5ub2RlKCkKICAgICAgICAgICAgOiBlbGVtZW50T3JTZWxlY3Rpb247CiAgICAgICAgdmFyIHN0eWxlID0gd2luZG93LmdldENvbXB1dGVkU3R5bGUoZWxlbWVudCk7CiAgICAgICAgcmV0dXJuIF9wYXJzZVN0eWxlVmFsdWUoc3R5bGUsICJ3aWR0aCIpCiAgICAgICAgICAgICsgX3BhcnNlU3R5bGVWYWx1ZShzdHlsZSwgInBhZGRpbmctbGVmdCIpCiAgICAgICAgICAgICsgX3BhcnNlU3R5bGVWYWx1ZShzdHlsZSwgInBhZGRpbmctcmlnaHQiKQogICAgICAgICAgICArIF9wYXJzZVN0eWxlVmFsdWUoc3R5bGUsICJib3JkZXItbGVmdC13aWR0aCIpCiAgICAgICAgICAgICsgX3BhcnNlU3R5bGVWYWx1ZShzdHlsZSwgImJvcmRlci1yaWdodC13aWR0aCIpOwogICAgfQogICAgZXhwb3J0cy5lbGVtZW50V2lkdGggPSBlbGVtZW50V2lkdGg7CiAgICAvKioKICAgICAqIENhbGN1bGF0ZXMgdGhlIGhlaWdodCBvZiB0aGUgZWxlbWVudC4KICAgICAqIFRoZSBoZWlnaHQgaW5jbHVkZXMgdGhlIHBhZGRpbmcgdGhlIGFuZCB0aGUgYm9yZGVyIG9uIHRoZSBlbGVtZW50J3MgdG9wIGFuZCBib3R0b20gc2lkZXMuCiAgICAgKgogICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50IFRoZSBlbGVtZW50IHRvIHF1ZXJ5CiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBUaGUgaGVpZ2h0IG9mIHRoZSBlbGVtZW50CiAgICAgKi8KICAgIGZ1bmN0aW9uIGVsZW1lbnRIZWlnaHQoZWxlbWVudE9yU2VsZWN0aW9uKSB7CiAgICAgICAgdmFyIGVsZW1lbnQgPSBlbGVtZW50T3JTZWxlY3Rpb24gaW5zdGFuY2VvZiBkMy5zZWxlY3Rpb24KICAgICAgICAgICAgPyBlbGVtZW50T3JTZWxlY3Rpb24ubm9kZSgpCiAgICAgICAgICAgIDogZWxlbWVudE9yU2VsZWN0aW9uOwogICAgICAgIHZhciBzdHlsZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKGVsZW1lbnQpOwogICAgICAgIHJldHVybiBfcGFyc2VTdHlsZVZhbHVlKHN0eWxlLCAiaGVpZ2h0IikKICAgICAgICAgICAgKyBfcGFyc2VTdHlsZVZhbHVlKHN0eWxlLCAicGFkZGluZy10b3AiKQogICAgICAgICAgICArIF9wYXJzZVN0eWxlVmFsdWUoc3R5bGUsICJwYWRkaW5nLWJvdHRvbSIpCiAgICAgICAgICAgICsgX3BhcnNlU3R5bGVWYWx1ZShzdHlsZSwgImJvcmRlci10b3Atd2lkdGgiKQogICAgICAgICAgICArIF9wYXJzZVN0eWxlVmFsdWUoc3R5bGUsICJib3JkZXItYm90dG9tLXdpZHRoIik7CiAgICB9CiAgICBleHBvcnRzLmVsZW1lbnRIZWlnaHQgPSBlbGVtZW50SGVpZ2h0OwogICAgLy8gdGFrZW4gZnJvbSB0aGUgQk5GIGF0IGh0dHBzOi8vd3d3LnczLm9yZy9UUi9TVkcvY29vcmRzLmh0bWwKICAgIHZhciBXU1AgPSAiXFxzIjsKICAgIHZhciBOVU1CRVIgPSAiKD86Wy0rXT9bMC05XSpcXC4/WzAtOV0rKSI7CiAgICB2YXIgQ09NTUFfV1NQID0gIig/Oig/OiIgKyBXU1AgKyAiKyw/IiArIFdTUCArICIqKXwoPzosIiArIFdTUCArICIqKSkiOwogICAgdmFyIFRSQU5TTEFURV9SRUdFWCA9IG5ldyBSZWdFeHAoInRyYW5zbGF0ZSIgKyBXU1AgKyAiKlxcKCIgKyBXU1AgKyAiKigiICsgTlVNQkVSICsgIikoPzoiICsgQ09NTUFfV1NQICsgIigiICsgTlVNQkVSICsgIikpPyIgKyBXU1AgKyAiKlxcKSIpOwogICAgdmFyIFJPVEFURV9SRUdFWCA9IG5ldyBSZWdFeHAoInJvdGF0ZSIgKyBXU1AgKyAiKlxcKCIgKyBXU1AgKyAiKigiICsgTlVNQkVSICsgIikiICsgV1NQICsgIipcXCkiKTsKICAgIHZhciBTQ0FMRV9SRUdFWCA9IG5ldyBSZWdFeHAoInNjYWxlIiArIFdTUCArICIqXFwoIiArIFdTUCArICIqKCIgKyBOVU1CRVIgKyAiKSg/OiIgKyBDT01NQV9XU1AgKyAiKCIgKyBOVU1CRVIgKyAiKSk/IiArIFdTUCArICIqXFwpIik7CiAgICAvKioKICAgICAqIEFjY2VwdHMgc2VsZWN0aW9ucyB3aG9zZSAudHJhbnNmb3JtIGNvbnRhaW4gYSAidHJhbnNsYXRlKGEsIGIpIiBhbmQgZXh0cmFjdHMgdGhlIGEgYW5kIGIKICAgICAqLwogICAgZnVuY3Rpb24gZ2V0VHJhbnNsYXRlVmFsdWVzKGVsKSB7CiAgICAgICAgdmFyIG1hdGNoID0gVFJBTlNMQVRFX1JFR0VYLmV4ZWMoZWwuYXR0cigidHJhbnNmb3JtIikpOwogICAgICAgIGlmIChtYXRjaCAhPSBudWxsKSB7CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVYID0gbWF0Y2hbMV0sIF9hID0gbWF0Y2hbMl0sIHRyYW5zbGF0ZVkgPSBfYSA9PT0gdm9pZCAwID8gMCA6IF9hOwogICAgICAgICAgICByZXR1cm4gWyt0cmFuc2xhdGVYLCArdHJhbnNsYXRlWV07CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICByZXR1cm4gWzAsIDBdOwogICAgICAgIH0KICAgIH0KICAgIGV4cG9ydHMuZ2V0VHJhbnNsYXRlVmFsdWVzID0gZ2V0VHJhbnNsYXRlVmFsdWVzOwogICAgLyoqCiAgICAgKiBBY2NlcHRzIHNlbGVjdGlvbnMgd2hvc2UgLnRyYW5zZm9ybSBjb250YWluIGEgInJvdGF0ZShhbmdsZSkiIGFuZCByZXR1cm5zIHRoZSBhbmdsZQogICAgICovCiAgICBmdW5jdGlvbiBnZXRSb3RhdGUoZWwpIHsKICAgICAgICB2YXIgbWF0Y2ggPSBST1RBVEVfUkVHRVguZXhlYyhlbC5hdHRyKCJ0cmFuc2Zvcm0iKSk7CiAgICAgICAgaWYgKG1hdGNoICE9IG51bGwpIHsKICAgICAgICAgICAgdmFyIHJvdGF0aW9uID0gbWF0Y2hbMV07CiAgICAgICAgICAgIHJldHVybiArcm90YXRpb247CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLmdldFJvdGF0ZSA9IGdldFJvdGF0ZTsKICAgIGZ1bmN0aW9uIGdldFNjYWxlVmFsdWVzKGVsKSB7CiAgICAgICAgdmFyIG1hdGNoID0gU0NBTEVfUkVHRVguZXhlYyhlbC5hdHRyKCJ0cmFuc2Zvcm0iKSk7CiAgICAgICAgaWYgKG1hdGNoICE9IG51bGwpIHsKICAgICAgICAgICAgdmFyIHNjYWxlWCA9IG1hdGNoWzFdLCBzY2FsZVkgPSBtYXRjaFsyXTsKICAgICAgICAgICAgcmV0dXJuIFsrc2NhbGVYLCBzY2FsZVkgPT0gbnVsbCA/ICtzY2FsZVggOiArc2NhbGVZXTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHJldHVybiBbMCwgMF07CiAgICAgICAgfQogICAgfQogICAgZXhwb3J0cy5nZXRTY2FsZVZhbHVlcyA9IGdldFNjYWxlVmFsdWVzOwogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgdGhlIGZpcnN0IENsaWVudFJlY3Qgb3ZlcmxhcHMgdGhlIHNlY29uZC4KICAgICAqCiAgICAgKiBAcGFyYW0ge0NsaWVudFJlY3R9IGNsaWVudFJlY3RBIFRoZSBmaXJzdCBDbGllbnRSZWN0CiAgICAgKiBAcGFyYW0ge0NsaWVudFJlY3R9IGNsaWVudFJlY3RCIFRoZSBzZWNvbmQgQ2xpZW50UmVjdAogICAgICogQHJldHVybnMge2Jvb2xlYW59IElmIHRoZSBDbGllbnRSZWN0cyBvdmVybGFwIGVhY2ggb3RoZXIuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNsaWVudFJlY3RzT3ZlcmxhcChjbGllbnRSZWN0QSwgY2xpZW50UmVjdEIpIHsKICAgICAgICBpZiAobmF0aXZlTWF0aC5mbG9vcihjbGllbnRSZWN0QS5yaWdodCkgPD0gbmF0aXZlTWF0aC5jZWlsKGNsaWVudFJlY3RCLmxlZnQpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgICAgaWYgKG5hdGl2ZU1hdGguY2VpbChjbGllbnRSZWN0QS5sZWZ0KSA+PSBuYXRpdmVNYXRoLmZsb29yKGNsaWVudFJlY3RCLnJpZ2h0KSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIGlmIChuYXRpdmVNYXRoLmZsb29yKGNsaWVudFJlY3RBLmJvdHRvbSkgPD0gbmF0aXZlTWF0aC5jZWlsKGNsaWVudFJlY3RCLnRvcCkpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICBpZiAobmF0aXZlTWF0aC5jZWlsKGNsaWVudFJlY3RBLnRvcCkgPj0gbmF0aXZlTWF0aC5mbG9vcihjbGllbnRSZWN0Qi5ib3R0b20pKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICBleHBvcnRzLmNsaWVudFJlY3RzT3ZlcmxhcCA9IGNsaWVudFJlY3RzT3ZlcmxhcDsKICAgIC8qKgogICAgICogUmV0dXJuIGEgbmV3IENsaWVudFJlY3QgdGhhdCBpcyB0aGUgb2xkIENsaWVudFJlY3QgZXhwYW5kZWQgYnkgYW1vdW50IGluIGFsbCBkaXJlY3Rpb25zLgogICAgICogQHBhcmFtIHJlY3QKICAgICAqIEBwYXJhbSBhbW91bnQKICAgICAqLwogICAgZnVuY3Rpb24gZXhwYW5kUmVjdChyZWN0LCBhbW91bnQpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgICBsZWZ0OiByZWN0LmxlZnQgLSBhbW91bnQsCiAgICAgICAgICAgIHRvcDogcmVjdC50b3AgLSBhbW91bnQsCiAgICAgICAgICAgIHJpZ2h0OiByZWN0LnJpZ2h0ICsgYW1vdW50LAogICAgICAgICAgICBib3R0b206IHJlY3QuYm90dG9tICsgYW1vdW50LAogICAgICAgICAgICB3aWR0aDogcmVjdC53aWR0aCArIGFtb3VudCAqIDIsCiAgICAgICAgICAgIGhlaWdodDogcmVjdC5oZWlnaHQgKyBhbW91bnQgKiAyLAogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLmV4cGFuZFJlY3QgPSBleHBhbmRSZWN0OwogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRydWUgaWYgYW5kIG9ubHkgaWYgaW5uZXJDbGllbnRSZWN0IGlzIGluc2lkZSBvdXRlckNsaWVudFJlY3QuCiAgICAgKgogICAgICogQHBhcmFtIHtDbGllbnRSZWN0fSBpbm5lckNsaWVudFJlY3QgVGhlIGZpcnN0IENsaWVudFJlY3QKICAgICAqIEBwYXJhbSB7Q2xpZW50UmVjdH0gb3V0ZXJDbGllbnRSZWN0IFRoZSBzZWNvbmQgQ2xpZW50UmVjdAogICAgICogQHJldHVybnMge2Jvb2xlYW59IElmIGFuZCBvbmx5IGlmIHRoZSBpbm5lckNsaWVudFJlY3QgaXMgaW5zaWRlIG91dGVyQ2xpZW50UmVjdC4KICAgICAqLwogICAgZnVuY3Rpb24gY2xpZW50UmVjdEluc2lkZShpbm5lckNsaWVudFJlY3QsIG91dGVyQ2xpZW50UmVjdCkgewogICAgICAgIHJldHVybiAobmF0aXZlTWF0aC5mbG9vcihvdXRlckNsaWVudFJlY3QubGVmdCkgPD0gbmF0aXZlTWF0aC5jZWlsKGlubmVyQ2xpZW50UmVjdC5sZWZ0KSAmJgogICAgICAgICAgICBuYXRpdmVNYXRoLmZsb29yKG91dGVyQ2xpZW50UmVjdC50b3ApIDw9IG5hdGl2ZU1hdGguY2VpbChpbm5lckNsaWVudFJlY3QudG9wKSAmJgogICAgICAgICAgICBuYXRpdmVNYXRoLmZsb29yKGlubmVyQ2xpZW50UmVjdC5yaWdodCkgPD0gbmF0aXZlTWF0aC5jZWlsKG91dGVyQ2xpZW50UmVjdC5yaWdodCkgJiYKICAgICAgICAgICAgbmF0aXZlTWF0aC5mbG9vcihpbm5lckNsaWVudFJlY3QuYm90dG9tKSA8PSBuYXRpdmVNYXRoLmNlaWwob3V0ZXJDbGllbnRSZWN0LmJvdHRvbSkpOwogICAgfQogICAgZXhwb3J0cy5jbGllbnRSZWN0SW5zaWRlID0gY2xpZW50UmVjdEluc2lkZTsKICAgIC8qKgogICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBzdXBwbGllZCBjb29yZGluYXRlcyBvciBSYW5nZXMgaW50ZXJzZWN0IG9yIGFyZSBjb250YWluZWQgYnkgYmJveC4KICAgICAqCiAgICAgKiBAcGFyYW0ge251bWJlciB8IFJhbmdlfSB4VmFsT3JSYW5nZSBUaGUgeCBjb29yZGluYXRlIG9yIFJhbmdlIHRvIHRlc3QKICAgICAqIEBwYXJhbSB7bnVtYmVyIHwgUmFuZ2V9IHlWYWxPclJhbmdlIFRoZSB5IGNvb3JkaW5hdGUgb3IgUmFuZ2UgdG8gdGVzdAogICAgICogQHBhcmFtIHtTVkdSZWN0fSBiYm94IFRoZSBiYm94CiAgICAgKiBAcGFyYW0ge251bWJlcn0gdG9sZXJhbmNlIEFtb3VudCBieSB3aGljaCB0byBleHBhbmQgYmJveCwgaW4gZWFjaCBkaW1lbnNpb24sIGJlZm9yZQogICAgICogdGVzdGluZyBpbnRlcnNlY3Rpb24KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB0aGUgc3VwcGxpZWQgY29vcmRpbmF0ZXMgb3IgUmFuZ2VzIGludGVyc2VjdCBvciBhcmUKICAgICAqIGNvbnRhaW5lZCBieSBiYm94LCBmYWxzZSBvdGhlcndpc2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGludGVyc2VjdHNCQm94KHhWYWxPclJhbmdlLCB5VmFsT3JSYW5nZSwgYmJveCwgdG9sZXJhbmNlKSB7CiAgICAgICAgaWYgKHRvbGVyYW5jZSA9PT0gdm9pZCAwKSB7IHRvbGVyYW5jZSA9IDAuNTsgfQogICAgICAgIHZhciB4UmFuZ2UgPSBfcGFyc2VSYW5nZSh4VmFsT3JSYW5nZSk7CiAgICAgICAgdmFyIHlSYW5nZSA9IF9wYXJzZVJhbmdlKHlWYWxPclJhbmdlKTsKICAgICAgICAvLyBTVkdSZWN0cyBhcmUgcG9zaXRpb25lZCB3aXRoIHN1Yi1waXhlbCBhY2N1cmFjeSAodGhlIGRlZmF1bHQgdW5pdAogICAgICAgIC8vIGZvciB0aGUgeCwgeSwgaGVpZ2h0ICYgd2lkdGggYXR0cmlidXRlcyksIGJ1dCB1c2VyIHNlbGVjdGlvbnMgKGUuZy4gdmlhCiAgICAgICAgLy8gbW91c2UgZXZlbnRzKSB1c3VhbGx5IGhhdmUgcGl4ZWwgYWNjdXJhY3kuIEEgdG9sZXJhbmNlIG9mIGhhbGYtYS1waXhlbAogICAgICAgIC8vIHNlZW1zIGFwcHJvcHJpYXRlLgogICAgICAgIHJldHVybiBiYm94LnggKyBiYm94LndpZHRoID49IHhSYW5nZS5taW4gLSB0b2xlcmFuY2UgJiYKICAgICAgICAgICAgYmJveC54IDw9IHhSYW5nZS5tYXggKyB0b2xlcmFuY2UgJiYKICAgICAgICAgICAgYmJveC55ICsgYmJveC5oZWlnaHQgPj0geVJhbmdlLm1pbiAtIHRvbGVyYW5jZSAmJgogICAgICAgICAgICBiYm94LnkgPD0geVJhbmdlLm1heCArIHRvbGVyYW5jZTsKICAgIH0KICAgIGV4cG9ydHMuaW50ZXJzZWN0c0JCb3ggPSBpbnRlcnNlY3RzQkJveDsKICAgIC8qKgogICAgICogQ3JlYXRlIGEgUmFuZ2UgZnJvbSBhIG51bWJlciBvciBhbiBvYmplY3Qgd2l0aCAibWluIiBhbmQgIm1heCIgZGVmaW5lZC4KICAgICAqCiAgICAgKiBAcGFyYW0ge2FueX0gaW5wdXQgVGhlIG9iamVjdCB0byBwYXJzZQogICAgICoKICAgICAqIEByZXR1cm5zIHtSYW5nZX0gVGhlIGdlbmVyYXRlZCBSYW5nZQogICAgICovCiAgICBmdW5jdGlvbiBfcGFyc2VSYW5nZShpbnB1dCkgewogICAgICAgIGlmICh0eXBlb2YgKGlucHV0KSA9PT0gIm51bWJlciIpIHsKICAgICAgICAgICAgdmFyIHZhbHVlID0gaW5wdXQ7CiAgICAgICAgICAgIHJldHVybiB7IG1pbjogdmFsdWUsIG1heDogdmFsdWUgfTsKICAgICAgICB9CiAgICAgICAgdmFyIHJhbmdlID0gaW5wdXQ7CiAgICAgICAgaWYgKHJhbmdlIGluc3RhbmNlb2YgT2JqZWN0ICYmICJtaW4iIGluIHJhbmdlICYmICJtYXgiIGluIHJhbmdlKSB7CiAgICAgICAgICAgIHJldHVybiByYW5nZTsKICAgICAgICB9CiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJpbnB1dCAnIiArIGlucHV0ICsgIicgY2FuJ3QgYmUgcGFyc2VkIGFzIGFuIFJhbmdlIik7CiAgICB9CiAgICBmdW5jdGlvbiBfcGFyc2VTdHlsZVZhbHVlKHN0eWxlLCBwcm9wZXJ0eSkgewogICAgICAgIHZhciB2YWx1ZSA9IHN0eWxlLmdldFByb3BlcnR5VmFsdWUocHJvcGVydHkpOwogICAgICAgIHZhciBwYXJzZWRWYWx1ZSA9IHBhcnNlRmxvYXQodmFsdWUpOwogICAgICAgIHJldHVybiBwYXJzZWRWYWx1ZSB8fCAwOwogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm5zIGFuIGFycmF5IGNvbnRhaW5pbmcgYWxsIGFuY2VzdG9yIGBIVE1MRWxlbWVudGBzLCBzdGFydGluZyBhdCB0aGUKICAgICAqIHByb3ZpZGVkIGVsZW1lbnQgYW5kIHVzdWFsbHkgZW5kaW5nIHdpdGggdGhlIGA8Ym9keT5gIGVsZW1lbnQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldEh0bWxFbGVtZW50QW5jZXN0b3JzKGVsZW0pIHsKICAgICAgICB2YXIgZWxlbXMgPSBbXTsKICAgICAgICB3aGlsZSAoZWxlbSAmJiBlbGVtIGluc3RhbmNlb2YgSFRNTEVsZW1lbnQpIHsKICAgICAgICAgICAgZWxlbXMucHVzaChlbGVtKTsKICAgICAgICAgICAgZWxlbSA9IGVsZW0ucGFyZW50RWxlbWVudDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGVsZW1zOwogICAgfQogICAgZXhwb3J0cy5nZXRIdG1sRWxlbWVudEFuY2VzdG9ycyA9IGdldEh0bWxFbGVtZW50QW5jZXN0b3JzOwogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRoZSBgSUNzc1RyYW5zZm9ybU1hdHJpeGAgb2YgYW4gZWxlbWVudCwgaWYgZGVmaW5lZCBpbiBpdHMgY29tcHV0ZWQKICAgICAqIHN0eWxlLiBSZXR1cm5zIGBudWxsYCBpZiB0aGVyZSBpcyBubyB0cmFuc2Zvcm0gb24gdGhlIGVsZW1lbnQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldEVsZW1lbnRUcmFuc2Zvcm0oZWxlbSkgewogICAgICAgIHZhciBzdHlsZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKGVsZW0sIG51bGwpOwogICAgICAgIHZhciB0cmFuc2Zvcm0gPSBzdHlsZS5nZXRQcm9wZXJ0eVZhbHVlKCItd2Via2l0LXRyYW5zZm9ybSIpIHx8CiAgICAgICAgICAgIHN0eWxlLmdldFByb3BlcnR5VmFsdWUoIi1tb3otdHJhbnNmb3JtIikgfHwKICAgICAgICAgICAgc3R5bGUuZ2V0UHJvcGVydHlWYWx1ZSgiLW1zLXRyYW5zZm9ybSIpIHx8CiAgICAgICAgICAgIHN0eWxlLmdldFByb3BlcnR5VmFsdWUoIi1vLXRyYW5zZm9ybSIpIHx8CiAgICAgICAgICAgIHN0eWxlLmdldFByb3BlcnR5VmFsdWUoInRyYW5zZm9ybSIpOwogICAgICAgIHJldHVybiBwYXJzZVRyYW5zZm9ybU1hdHJpeCh0cmFuc2Zvcm0pOwogICAgfQogICAgZXhwb3J0cy5nZXRFbGVtZW50VHJhbnNmb3JtID0gZ2V0RWxlbWVudFRyYW5zZm9ybTsKICAgIHZhciBfTUFUUklYX1JFR0VYID0gL15tYXRyaXhcKChbXildKylcKSQvOwogICAgdmFyIF9TUExJVF9SRUdFWCA9IC9bLCBdKy87CiAgICAvKioKICAgICAqIEF0dGVtcHRzIHRvIHBhcnNlIGEgc3RyaW5nIHN1Y2ggYXMgYCJtYXRyaXgoMSwgMCwgMSwgMSwgMTAwLCAwKSJgIGludG8gYW4KICAgICAqIGFycmF5IHN1Y2ggYXMgYFsxLCAwLCAxLCAxLCAxMDAsIDBdYC4KICAgICAqCiAgICAgKiBJZiB1bmFibGUgdG8gZG8gc28sIGBudWxsYCBpcyByZXR1cm5lZC4KICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2VUcmFuc2Zvcm1NYXRyaXgodHJhbnNmb3JtKSB7CiAgICAgICAgaWYgKHRyYW5zZm9ybSA9PSBudWxsIHx8IHRyYW5zZm9ybSA9PT0gIm5vbmUiKSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICB2YXIgbWF0cml4U3RyaW5ncyA9IHRyYW5zZm9ybS5tYXRjaChfTUFUUklYX1JFR0VYKTsKICAgICAgICBpZiAobWF0cml4U3RyaW5ncyA9PSBudWxsIHx8IG1hdHJpeFN0cmluZ3MubGVuZ3RoIDwgMikgewogICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgICAgdmFyIG1hdHJpeCA9IG1hdHJpeFN0cmluZ3NbMV0uc3BsaXQoX1NQTElUX1JFR0VYKS5tYXAoZnVuY3Rpb24gKHYpIHsgcmV0dXJuIHBhcnNlRmxvYXQodik7IH0pOwogICAgICAgIGlmIChtYXRyaXgubGVuZ3RoICE9IDYpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIHJldHVybiBtYXRyaXg7CiAgICB9CiAgICB9KTsKCiAgICB2YXIgbWF0aFV0aWxzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKICAgIHZhciBuYXRpdmVNYXRoID0gd2luZG93Lk1hdGg7CiAgICB2YXIgX0lERU5USVRZX1RSQU5TRk9STSA9IFsxLCAwLCAwLCAxLCAwLCAwXTsKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIHggaXMgYmV0d2VlbiBhIGFuZCBiLgogICAgICoKICAgICAqIEBwYXJhbSB7bnVtYmVyfSB4IFRoZSB2YWx1ZSB0byB0ZXN0IGlmIGluIHJhbmdlCiAgICAgKiBAcGFyYW0ge251bWJlcn0gYSBUaGUgYmVnaW5uaW5nIG9mIHRoZSAoaW5jbHVzaXZlKSByYW5nZQogICAgICogQHBhcmFtIHtudW1iZXJ9IGIgVGhlIGVuZGluZyBvZiB0aGUgKGluY2x1c2l2ZSkgcmFuZ2UKICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IFdoZXRoZXIgeCBpcyBpbiBbYSwgYl0KICAgICAqLwogICAgZnVuY3Rpb24gaW5SYW5nZSh4LCBhLCBiKSB7CiAgICAgICAgcmV0dXJuIChuYXRpdmVNYXRoLm1pbihhLCBiKSA8PSB4ICYmIHggPD0gbmF0aXZlTWF0aC5tYXgoYSwgYikpOwogICAgfQogICAgZXhwb3J0cy5pblJhbmdlID0gaW5SYW5nZTsKICAgIC8qKgogICAgICogQ2xhbXBzIHggdG8gdGhlIHJhbmdlIFttaW4sIG1heF0uCiAgICAgKgogICAgICogQHBhcmFtIHtudW1iZXJ9IHggVGhlIHZhbHVlIHRvIGJlIGNsYW1wZWQuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gbWluIFRoZSBtaW5pbXVtIHZhbHVlLgogICAgICogQHBhcmFtIHtudW1iZXJ9IG1heCBUaGUgbWF4aW11bSB2YWx1ZS4KICAgICAqIEByZXR1cm4ge251bWJlcn0gQSBjbGFtcGVkIHZhbHVlIGluIHRoZSByYW5nZSBbbWluLCBtYXhdLgogICAgICovCiAgICBmdW5jdGlvbiBjbGFtcCh4LCBtaW4sIG1heCkgewogICAgICAgIHJldHVybiBuYXRpdmVNYXRoLm1pbihuYXRpdmVNYXRoLm1heChtaW4sIHgpLCBtYXgpOwogICAgfQogICAgZXhwb3J0cy5jbGFtcCA9IGNsYW1wOwogICAgZnVuY3Rpb24gbWF4KGFycmF5LCBmaXJzdEFyZywgc2Vjb25kQXJnKSB7CiAgICAgICAgdmFyIGFjY2Vzc29yID0gdHlwZW9mIChmaXJzdEFyZykgPT09ICJmdW5jdGlvbiIgPyBmaXJzdEFyZyA6IG51bGw7CiAgICAgICAgdmFyIGRlZmF1bHRWYWx1ZSA9IGFjY2Vzc29yID09IG51bGwgPyBmaXJzdEFyZyA6IHNlY29uZEFyZzsKICAgICAgICB2YXIgbWF4VmFsdWUgPSBhY2Nlc3NvciA9PSBudWxsID8gZDMubWF4KGFycmF5KSA6IGQzLm1heChhcnJheSwgYWNjZXNzb3IpOwogICAgICAgIHJldHVybiBtYXhWYWx1ZSAhPT0gdW5kZWZpbmVkID8gbWF4VmFsdWUgOiBkZWZhdWx0VmFsdWU7CiAgICB9CiAgICBleHBvcnRzLm1heCA9IG1heDsKICAgIGZ1bmN0aW9uIG1pbihhcnJheSwgZmlyc3RBcmcsIHNlY29uZEFyZykgewogICAgICAgIHZhciBhY2Nlc3NvciA9IHR5cGVvZiAoZmlyc3RBcmcpID09PSAiZnVuY3Rpb24iID8gZmlyc3RBcmcgOiBudWxsOwogICAgICAgIHZhciBkZWZhdWx0VmFsdWUgPSBhY2Nlc3NvciA9PSBudWxsID8gZmlyc3RBcmcgOiBzZWNvbmRBcmc7CiAgICAgICAgdmFyIG1pblZhbHVlID0gYWNjZXNzb3IgPT0gbnVsbCA/IGQzLm1pbihhcnJheSkgOiBkMy5taW4oYXJyYXksIGFjY2Vzc29yKTsKICAgICAgICByZXR1cm4gbWluVmFsdWUgIT09IHVuZGVmaW5lZCA/IG1pblZhbHVlIDogZGVmYXVsdFZhbHVlOwogICAgfQogICAgZXhwb3J0cy5taW4gPSBtaW47CiAgICAvKioKICAgICAqIFJldHVybnMgdHJ1ZSAqKm9ubHkqKiBpZiB4IGlzIE5hTgogICAgICovCiAgICBmdW5jdGlvbiBpc05hTihuKSB7CiAgICAgICAgcmV0dXJuIG4gIT09IG47CiAgICB9CiAgICBleHBvcnRzLmlzTmFOID0gaXNOYU47CiAgICAvKioKICAgICAqIFJldHVybnMgdHJ1ZSBpZiB0aGUgYXJndW1lbnQgaXMgYSBudW1iZXIsIHdoaWNoIGlzIG5vdCBOYU4KICAgICAqIE51bWJlcnMgcmVwcmVzZW50ZWQgYXMgc3RyaW5ncyBkbyBub3QgcGFzcyB0aGlzIGZ1bmN0aW9uCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzVmFsaWROdW1iZXIobikgewogICAgICAgIHJldHVybiB0eXBlb2YgbiA9PT0gIm51bWJlciIgJiYgbiAtIG4gPCAxOwogICAgfQogICAgZXhwb3J0cy5pc1ZhbGlkTnVtYmVyID0gaXNWYWxpZE51bWJlcjsKICAgIC8qKgogICAgICogR2VuZXJhdGVzIGFuIGFycmF5IG9mIGNvbnNlY3V0aXZlLCBzdHJpY3RseSBpbmNyZWFzaW5nIG51bWJlcnMKICAgICAqIGluIHRoZSByYW5nZSBbc3RhcnQsIHN0b3ApIHNlcGFyZXRlZCBieSBzdGVwCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJhbmdlKHN0YXJ0LCBzdG9wLCBzdGVwKSB7CiAgICAgICAgaWYgKHN0ZXAgPT09IHZvaWQgMCkgeyBzdGVwID0gMTsgfQogICAgICAgIGlmIChzdGVwID09PSAwKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigic3RlcCBjYW5ub3QgYmUgMCIpOwogICAgICAgIH0KICAgICAgICB2YXIgbGVuZ3RoID0gbmF0aXZlTWF0aC5tYXgobmF0aXZlTWF0aC5jZWlsKChzdG9wIC0gc3RhcnQpIC8gc3RlcCksIDApOwogICAgICAgIHZhciByYW5nZSA9IFtdOwogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgbGVuZ3RoOyArK2kpIHsKICAgICAgICAgICAgcmFuZ2VbaV0gPSBzdGFydCArIHN0ZXAgKiBpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gcmFuZ2U7CiAgICB9CiAgICBleHBvcnRzLnJhbmdlID0gcmFuZ2U7CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIHNxdWFyZSBvZiB0aGUgZGlzdGFuY2UgYmV0d2VlbiB0d28gcG9pbnRzCiAgICAgKgogICAgICogQHBhcmFtIHtQb2ludH0gcDEKICAgICAqIEBwYXJhbSB7UG9pbnR9IHAyCiAgICAgKiBAcmV0dXJuIHtudW1iZXJ9IGRpc3QocDEsIHAyKV4yCiAgICAgKi8KICAgIGZ1bmN0aW9uIGRpc3RhbmNlU3F1YXJlZChwMSwgcDIpIHsKICAgICAgICByZXR1cm4gbmF0aXZlTWF0aC5wb3cocDIueSAtIHAxLnksIDIpICsgbmF0aXZlTWF0aC5wb3cocDIueCAtIHAxLngsIDIpOwogICAgfQogICAgZXhwb3J0cy5kaXN0YW5jZVNxdWFyZWQgPSBkaXN0YW5jZVNxdWFyZWQ7CiAgICBmdW5jdGlvbiBkZWdyZWVzVG9SYWRpYW5zKGRlZ3JlZSkgewogICAgICAgIHJldHVybiBkZWdyZWUgLyAzNjAgKiBuYXRpdmVNYXRoLlBJICogMjsKICAgIH0KICAgIGV4cG9ydHMuZGVncmVlc1RvUmFkaWFucyA9IGRlZ3JlZXNUb1JhZGlhbnM7CiAgICAvKioKICAgICAqIFJldHVybnMgaWYgdGhlIHBvaW50IGlzIHdpdGhpbiB0aGUgYm91bmRzLiBQb2ludHMgYWxvbmcKICAgICAqIHRoZSBib3VuZHMgYXJlIGNvbnNpZGVyZWQgIndpdGhpbiIgYXMgd2VsbC4KICAgICAqIEBwYXJhbSB7UG9pbnR9IHAgUG9pbnQgaW4gY29uc2lkZXJhdGlvbnMuCiAgICAgKiBAcGFyYW0ge0JvdW5kc30gYm91bmRzIEJvdW5kcyB3aXRoaW4gd2hpY2ggdG8gY2hlY2sgZm9yIGluY2x1c2lvbi4KICAgICAqLwogICAgZnVuY3Rpb24gd2l0aGluKHAsIGJvdW5kcykgewogICAgICAgIHJldHVybiBib3VuZHMudG9wTGVmdC54IDw9IHAueAogICAgICAgICAgICAmJiBib3VuZHMuYm90dG9tUmlnaHQueCA+PSBwLngKICAgICAgICAgICAgJiYgYm91bmRzLnRvcExlZnQueSA8PSBwLnkKICAgICAgICAgICAgJiYgYm91bmRzLmJvdHRvbVJpZ2h0LnkgPj0gcC55OwogICAgfQogICAgZXhwb3J0cy53aXRoaW4gPSB3aXRoaW47CiAgICAvKioKICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgZmlyc3QgYm91bmRzIGludGVyc2VjdHMgdGhlIHNlY29uZCBib3VuZHMuCiAgICAgKiBQYXNzIHByaW1pdGl2ZSBudW1iZXJzIGRpcmVjdGx5IGZvciBwZXJmb3JtYW5jZS4KICAgICAqCiAgICAgKiBBc3N1bWVzIHdpZHRoIGFuZCBoZWlnaHRzIGFyZSBwb3NpdGl2ZS4KICAgICAqLwogICAgZnVuY3Rpb24gYm91bmRzSW50ZXJzZWN0cyhhWCwgYVksIGFXaWR0aCwgYUhlaWdodCwgYlgsIGJZLCBiV2lkdGgsIGJIZWlnaHQpIHsKICAgICAgICByZXR1cm4gYVggPD0gYlggKyBiV2lkdGggJiYKICAgICAgICAgICAgYlggPD0gYVggKyBhV2lkdGggJiYKICAgICAgICAgICAgYVkgPD0gYlkgKyBiSGVpZ2h0ICYmCiAgICAgICAgICAgIGJZIDw9IGFZICsgYUhlaWdodDsKICAgIH0KICAgIGV4cG9ydHMuYm91bmRzSW50ZXJzZWN0cyA9IGJvdW5kc0ludGVyc2VjdHM7CiAgICAvKioKICAgICAqIFJldHVybnMgYSBgSUNzc1RyYW5zZm9ybU1hdHJpeGAgcmVwcmVzZW50aW5nIHRoZSBjdW11bGF0aXZlIHRyYW5zZm9ybWF0aW9uIG9mCiAgICAgKiB0aGUgZWxlbWVudCBhbmQgYWxsIGl0cyBwYXJlbnRzLiBUaGlzIHRyYW5zZm9ybSBjb252ZXJ0cyBmcm9tIHRvcC1sZXZlbAogICAgICogY2xpZW50WC9jbGllbnRZIGNvb3JkaW5hdGVzIChzdWNoIGFzIGRvY3VtZW50IG1vdXNlIGV2ZW50cykgdG8gaW50ZXJuYWwKICAgICAqIGNvbXBvbmVudCBvZmZzZXRYL29mZnNldFkgY29vcmRpbmF0ZXMuCiAgICAgKgogICAgICogVXNlIGBhcHBseVRyYW5zZm9ybWAgdG8gY29udmVydCBmcm9tIGNsaWVudCBjb29yZGluYXRlcyB0byBlbGVtZW50CiAgICAgKiBjb29yZGluYXRlcywgYWNjb3VudGluZyBmb3IgYWxsIENTUyB0cmFuc2Zvcm1zIGFwcGxpZWQgdG8gdGhhdCBlbGVtZW50LgogICAgICoKICAgICAqIE5vdGUgdGhhdCB0aGlzIGhhbmRsZXMgY3NzIGB0cmFuc2Zvcm1gIGJ1dCBkb2VzIG5vdCBoYW5kbGUgY3NzCiAgICAgKiBgdHJhbnNmb3JtLW9yaWdpbmAgdmFsdWVzIG90aGVyIHRoYW4gZGVmYXVsdCAoIjUwJSA1MCUiKS4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Q3VtdWxhdGl2ZVRyYW5zZm9ybShlbGVtZW50KSB7CiAgICAgICAgdmFyIGVsZW1zID0gZG9tVXRpbHMuZ2V0SHRtbEVsZW1lbnRBbmNlc3RvcnMoZWxlbWVudCk7CiAgICAgICAgdmFyIHRyYW5zZm9ybSA9IF9JREVOVElUWV9UUkFOU0ZPUk07CiAgICAgICAgdmFyIG9mZnNldFBhcmVudCA9IG51bGw7CiAgICAgICAgZm9yICh2YXIgX2kgPSAwLCBlbGVtc18xID0gZWxlbXM7IF9pIDwgZWxlbXNfMS5sZW5ndGg7IF9pKyspIHsKICAgICAgICAgICAgdmFyIGVsZW0gPSBlbGVtc18xW19pXTsKICAgICAgICAgICAgLy8gYXBwbHkgY3NzIHRyYW5zZm9ybSBmcm9tIGFueSBhbmNlc3RvciBlbGVtZW50CiAgICAgICAgICAgIHZhciBlbGVtZW50VHJhbnNmb3JtID0gZG9tVXRpbHMuZ2V0RWxlbWVudFRyYW5zZm9ybShlbGVtKTsKICAgICAgICAgICAgaWYgKGVsZW1lbnRUcmFuc2Zvcm0gIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIG1pZFggPSBlbGVtLmNsaWVudFdpZHRoIC8gMjsKICAgICAgICAgICAgICAgIHZhciBtaWRZID0gZWxlbS5jbGllbnRIZWlnaHQgLyAyOwogICAgICAgICAgICAgICAgdHJhbnNmb3JtID0gbXVsdGlwbHlUcmFuc2xhdGUodHJhbnNmb3JtLCBbbWlkWCwgbWlkWV0pOwogICAgICAgICAgICAgICAgdHJhbnNmb3JtID0gbXVsdGlwbHlNYXRyaXgodHJhbnNmb3JtLCBpbnZlcnRNYXRyaXgoZWxlbWVudFRyYW5zZm9ybSkpOwogICAgICAgICAgICAgICAgdHJhbnNmb3JtID0gbXVsdGlwbHlUcmFuc2xhdGUodHJhbnNmb3JtLCBbLW1pZFgsIC1taWRZXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gYXBwbHkgc2Nyb2xsIG9mZnNldHMgZnJvbSBhbnkgYW5jZXN0b3IgZWxlbWVudAogICAgICAgICAgICB2YXIgb2Zmc2V0WCA9IGVsZW0uc2Nyb2xsTGVmdDsKICAgICAgICAgICAgdmFyIG9mZnNldFkgPSBlbGVtLnNjcm9sbFRvcDsKICAgICAgICAgICAgLy8gYXBwbHkgY2xpZW50K29mZnNldCBmcm9tIG9ubHkgYWNlbnN0b3IgIm9mZnNldFBhcmVudCIKICAgICAgICAgICAgaWYgKG9mZnNldFBhcmVudCA9PT0gbnVsbCB8fCBlbGVtID09PSBvZmZzZXRQYXJlbnQpIHsKICAgICAgICAgICAgICAgIG9mZnNldFggLT0gZWxlbS5vZmZzZXRMZWZ0ICsgZWxlbS5jbGllbnRMZWZ0OwogICAgICAgICAgICAgICAgb2Zmc2V0WSAtPSBlbGVtLm9mZnNldFRvcCArIGVsZW0uY2xpZW50VG9wOwogICAgICAgICAgICAgICAgb2Zmc2V0UGFyZW50ID0gZWxlbS5vZmZzZXRQYXJlbnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdHJhbnNmb3JtID0gbXVsdGlwbHlUcmFuc2xhdGUodHJhbnNmb3JtLCBbb2Zmc2V0WCwgb2Zmc2V0WV0pOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJhbnNmb3JtOwogICAgfQogICAgZXhwb3J0cy5nZXRDdW11bGF0aXZlVHJhbnNmb3JtID0gZ2V0Q3VtdWxhdGl2ZVRyYW5zZm9ybTsKICAgIC8qKgogICAgICogU3RyYWlnaHRmb3J3YXJkIG1hdHJpeCBtdWx0aXBsaWNhdGlvbiBvZiBob21vZ2VuaXplZCBjc3MgdHJhbnNmb3JtIG1hdHJpY2VzLgogICAgICovCiAgICBmdW5jdGlvbiBtdWx0aXBseU1hdHJpeChhLCBiKSB7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgYVswXSAqIGJbMF0gKyBhWzJdICogYlsxXSwKICAgICAgICAgICAgYVsxXSAqIGJbMF0gKyBhWzNdICogYlsxXSwKICAgICAgICAgICAgYVswXSAqIGJbMl0gKyBhWzJdICogYlszXSwKICAgICAgICAgICAgYVsxXSAqIGJbMl0gKyBhWzNdICogYlszXSwKICAgICAgICAgICAgYVswXSAqIGJbNF0gKyBhWzJdICogYls1XSArIGFbNF0sCiAgICAgICAgICAgIGFbMV0gKiBiWzRdICsgYVszXSAqIGJbNV0gKyBhWzVdLAogICAgICAgIF07CiAgICB9CiAgICBleHBvcnRzLm11bHRpcGx5TWF0cml4ID0gbXVsdGlwbHlNYXRyaXg7CiAgICAvKioKICAgICAqIFByZXBlbmRzIHRyYW5zbGF0aW9uIHRvIHRyYW5zZm9ybWF0aW9uIG1hdHJpeC4KICAgICAqCiAgICAgKiBFcXVpdmFsZW50IHRvIGBtdWx0aXBseU1hdHJpeChbMSwgMCwgMCwgMSwgLi4udl0sIGIpYAogICAgICovCiAgICBmdW5jdGlvbiBwcmVtdWx0aXBseVRyYW5zbGF0ZSh2LCBiKSB7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgYlswXSwgYlsxXSwgYlsyXSwgYlszXSwKICAgICAgICAgICAgYls0XSArIHZbMF0sCiAgICAgICAgICAgIGJbNV0gKyB2WzFdLAogICAgICAgIF07CiAgICB9CiAgICBleHBvcnRzLnByZW11bHRpcGx5VHJhbnNsYXRlID0gcHJlbXVsdGlwbHlUcmFuc2xhdGU7CiAgICAvKioKICAgICAqIEFwcGVuZHMgdHJhbnNsYXRpb24gdG8gdHJhbnNmb3JtYXRpb24gbWF0cml4LgogICAgICoKICAgICAqIEVxdWl2YWxlbnQgdG8gYG11bHRpcGx5TWF0cml4KGEsIFsxLCAwLCAwLCAxLCAuLi52XSlgCiAgICAgKi8KICAgIGZ1bmN0aW9uIG11bHRpcGx5VHJhbnNsYXRlKGEsIHYpIHsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgICBhWzBdLCBhWzFdLCBhWzJdLCBhWzNdLAogICAgICAgICAgICBhWzBdICogdlswXSArIGFbMl0gKiB2WzFdICsgYVs0XSwKICAgICAgICAgICAgYVsxXSAqIHZbMF0gKyBhWzNdICogdlsxXSArIGFbNV0sCiAgICAgICAgXTsKICAgIH0KICAgIGV4cG9ydHMubXVsdGlwbHlUcmFuc2xhdGUgPSBtdWx0aXBseVRyYW5zbGF0ZTsKICAgIC8qKgogICAgICogQW5hbHl0aWNhbCBpbnZlcnNlIG9mIGEgYElDc3NUcmFuc2Zvcm1NYXRyaXhgIGFuYWxvZ291cyB0byBhIG5vbi1zaW5ndWxhcgogICAgICogaG9tb2dlbm91cyAzeDMgbWF0cml4LgogICAgICoKICAgICAqIGh0dHA6Ly9tYXRod29ybGQud29sZnJhbS5jb20vTWF0cml4SW52ZXJzZS5odG1sCiAgICAgKiBodHRwczovL3N0YWNrb3ZlcmZsb3cuY29tL3F1ZXN0aW9ucy8yNjI0NDIyL2VmZmljaWVudC00eDQtbWF0cml4LWludmVyc2UtYWZmaW5lLXRyYW5zZm9ybQogICAgICovCiAgICBmdW5jdGlvbiBpbnZlcnRNYXRyaXgoYSkgewogICAgICAgIHZhciBkZXRlcm1pbmFudCA9IGFbMF0gKiBhWzNdIC0gYVsxXSAqIGFbMl07CiAgICAgICAgaWYgKGRldGVybWluYW50ID09PSAwKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigic2luZ3VsYXIgbWF0cml4Iik7CiAgICAgICAgfQogICAgICAgIHZhciBpbnZlcnNlRGV0ZXJtaW5hbnQgPSAxIC8gZGV0ZXJtaW5hbnQ7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgaW52ZXJzZURldGVybWluYW50ICogYVszXSwKICAgICAgICAgICAgaW52ZXJzZURldGVybWluYW50ICogLWFbMV0sCiAgICAgICAgICAgIGludmVyc2VEZXRlcm1pbmFudCAqIC1hWzJdLAogICAgICAgICAgICBpbnZlcnNlRGV0ZXJtaW5hbnQgKiBhWzBdLAogICAgICAgICAgICBpbnZlcnNlRGV0ZXJtaW5hbnQgKiAoLWFbM10gKiBhWzRdICsgYVsyXSAqIGFbNV0pLAogICAgICAgICAgICBpbnZlcnNlRGV0ZXJtaW5hbnQgKiAoYVsxXSAqIGFbNF0gKyAtYVswXSAqIGFbNV0pLAogICAgICAgIF07CiAgICB9CiAgICBleHBvcnRzLmludmVydE1hdHJpeCA9IGludmVydE1hdHJpeDsKICAgIC8qKgogICAgICogQXBwbGllcyB0aGUgYElDc3NUcmFuc2Zvcm1NYXRyaXhgIHRvIHRoZSBgUG9pbnRgLgogICAgICoKICAgICAqIFJldHVybnMgYSBuZXcgYFBvaW50YC4KICAgICAqLwogICAgZnVuY3Rpb24gYXBwbHlUcmFuc2Zvcm0oYSwgcCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIHg6IGFbMF0gKiBwLnggKyBhWzJdICogcC55ICsgYVs0XSwKICAgICAgICAgICAgeTogYVsxXSAqIHAueCArIGFbM10gKiBwLnkgKyBhWzVdLAogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLmFwcGx5VHJhbnNmb3JtID0gYXBwbHlUcmFuc2Zvcm07CiAgICB9KTsKCiAgICB2YXIgclRyZWVTcGxpdFN0cmF0ZWdpZXMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIHZhciBTcGxpdFN0cmF0ZWd5VHJpdmlhbCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBTcGxpdFN0cmF0ZWd5VHJpdmlhbCgpIHsKICAgICAgICB9CiAgICAgICAgU3BsaXRTdHJhdGVneVRyaXZpYWwucHJvdG90eXBlLnNwbGl0ID0gZnVuY3Rpb24gKGVudHJpZXMsIG5vZGVzKSB7CiAgICAgICAgICAgIC8vIENyZWF0ZSBzaW1wbGUgbWlkZGxlIHNwbGl0CiAgICAgICAgICAgIHZhciBtaWQgPSBNYXRoLmNlaWwoZW50cmllcy5sZW5ndGggLyAyKTsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBtaWQ7IGkrKykgewogICAgICAgICAgICAgICAgbm9kZXNbMF0uaW5zZXJ0KGVudHJpZXNbaV0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGZvciAodmFyIGkgPSBtaWQ7IGkgPCBlbnRyaWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBub2Rlc1sxXS5pbnNlcnQoZW50cmllc1tpXSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBTcGxpdFN0cmF0ZWd5VHJpdmlhbDsKICAgIH0oKSk7CiAgICBleHBvcnRzLlNwbGl0U3RyYXRlZ3lUcml2aWFsID0gU3BsaXRTdHJhdGVneVRyaXZpYWw7CiAgICAvLyBMaW5lYXIgc3BsaXQgbWV0aG9kIGFkYXB0ZWQgZnJvbSBodHRwczovL2dpdGh1Yi5jb20vaW1iY21kdGgvUlRyZWUvYmxvYi9tYXN0ZXIvc3JjL3J0cmVlLmpzCiAgICB2YXIgU3BsaXRTdHJhdGVneUxpbmVhciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBTcGxpdFN0cmF0ZWd5TGluZWFyKCkgewogICAgICAgIH0KICAgICAgICBTcGxpdFN0cmF0ZWd5TGluZWFyLnByb3RvdHlwZS5zcGxpdCA9IGZ1bmN0aW9uIChlbnRyaWVzLCBub2RlcykgewogICAgICAgICAgICAvLyBjb3B5IGVudHJpZXMgYmVmb3JlIHdlIG11dGF0ZSBpdAogICAgICAgICAgICBlbnRyaWVzID0gZW50cmllcy5zbGljZSgpOwogICAgICAgICAgICB0aGlzLmNob29zZUZpcnN0U3BsaXQoZW50cmllcywgbm9kZXMpOwogICAgICAgICAgICB3aGlsZSAoZW50cmllcy5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFkZE5leHQoZW50cmllcywgbm9kZXMpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDaG9vc2UgdGhlIHR3byBmYXJ0aGVzdC1hcGFydCBlbnRyaWVzIHRvIGJlZ2luIHRoZSBzcGxpdC4KICAgICAgICAgKi8KICAgICAgICBTcGxpdFN0cmF0ZWd5TGluZWFyLnByb3RvdHlwZS5jaG9vc2VGaXJzdFNwbGl0ID0gZnVuY3Rpb24gKGVudHJpZXMsIG5vZGVzKSB7CiAgICAgICAgICAgIC8vIERldGVybWluZSBlbnRyeSBpbmRpY2VzIHRoYXQgaGF2ZSBtaW4vbWF4IHgveSBjb29yZGluYXRlcwogICAgICAgICAgICB2YXIgbWluWEggPSAwOwogICAgICAgICAgICB2YXIgbWluWUggPSAwOwogICAgICAgICAgICB2YXIgbWF4WEwgPSBlbnRyaWVzLmxlbmd0aCAtIDE7CiAgICAgICAgICAgIHZhciBtYXhZTCA9IGVudHJpZXMubGVuZ3RoIC0gMTsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDE7IGkgPCBlbnRyaWVzLmxlbmd0aCAtIDE7IGkrKykgewogICAgICAgICAgICAgICAgdmFyIGVudHJ5ID0gZW50cmllc1tpXTsKICAgICAgICAgICAgICAgIGlmIChlbnRyeS5ib3VuZHMueGwgPiBlbnRyaWVzW21heFhMXS5ib3VuZHMueGwpIHsKICAgICAgICAgICAgICAgICAgICBtYXhYTCA9IGk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChlbnRyeS5ib3VuZHMueGggPCBlbnRyaWVzW21pblhIXS5ib3VuZHMueGgpIHsKICAgICAgICAgICAgICAgICAgICBtaW5YSCA9IGk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoZW50cnkuYm91bmRzLnlsID4gZW50cmllc1ttYXhZTF0uYm91bmRzLnlsKSB7CiAgICAgICAgICAgICAgICAgICAgbWF4WUwgPSBpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoZW50cnkuYm91bmRzLnloIDwgZW50cmllc1ttaW5ZSF0uYm91bmRzLnloKSB7CiAgICAgICAgICAgICAgICAgICAgbWluWUggPSBpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENob29zZSB0byBzcGxpdCB4IG9yIHkgYmFzZWQgb24gZ3JlYXRlc3QgZGlmZmVyZW5jZQogICAgICAgICAgICB2YXIgZHggPSBNYXRoLmFicyhlbnRyaWVzW21pblhIXS5ib3VuZHMueGggLSBlbnRyaWVzW21heFhMXS5ib3VuZHMueGwpOwogICAgICAgICAgICB2YXIgZHkgPSBNYXRoLmFicyhlbnRyaWVzW21pbllIXS5ib3VuZHMueWggLSBlbnRyaWVzW21heFlMXS5ib3VuZHMueWwpOwogICAgICAgICAgICB2YXIgX2EgPSBkeCA+IGR5ID8gW21pblhILCBtYXhYTF0gOiBbbWluWUgsIG1heFlMXSwgaTAgPSBfYVswXSwgaTEgPSBfYVsxXTsKICAgICAgICAgICAgLy8gaWYgbm8gZGV0ZWN0YWJsZSBzcGxpdCwganVzdCB1c2UgZmlyc3QvbGFzdCBlbnRyaWVzCiAgICAgICAgICAgIGlmIChpMCA9PT0gaTEpIHsKICAgICAgICAgICAgICAgIGkwID0gMDsKICAgICAgICAgICAgICAgIGkxID0gZW50cmllcy5sZW5ndGggLSAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFNwbGl0IG9mZiBub2Rlcy4gV2Ugc3BsaWNlIHdpdGggdGhlIG1heCBpbmRleCBmaXJzdCB0byBtYWtlIHN1cmUgd2UKICAgICAgICAgICAgLy8gZG9uJ3QgY2hhbmdlIHRoZSBpbmRleCBvZiB0aGUgc2Vjb25kIHNwbGljZSBjYWxsCiAgICAgICAgICAgIG5vZGVzWzBdLmluc2VydChlbnRyaWVzLnNwbGljZShNYXRoLm1heChpMCwgaTEpLCAxKVswXSk7CiAgICAgICAgICAgIG5vZGVzWzFdLmluc2VydChlbnRyaWVzLnNwbGljZShNYXRoLm1pbihpMCwgaTEpLCAxKVswXSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBTcGxpdCB0aGUgbmV4dCBlbnRyeS4gQ2hvb3NlIHRoZSBlbnRyeSB0aGF0IGV4cGFuZHMgaXRzIHBhcmVudCBub2RlJ3MKICAgICAgICAgKiBhcmVhIHRoZSBsZWFzdC4KICAgICAgICAgKi8KICAgICAgICBTcGxpdFN0cmF0ZWd5TGluZWFyLnByb3RvdHlwZS5hZGROZXh0ID0gZnVuY3Rpb24gKGVudHJpZXMsIG5vZGVzKSB7CiAgICAgICAgICAgIHZhciBpbmRleCA9IG51bGw7CiAgICAgICAgICAgIHZhciBtaW5EaWZmID0gbnVsbDsKICAgICAgICAgICAgdmFyIG1pbkRpZmZOb2RlID0gbnVsbDsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBlbnRyaWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICB2YXIgZW50cnkgPSBlbnRyaWVzW2ldOwogICAgICAgICAgICAgICAgdmFyIGFyZWFEaWZmMCA9IG5vZGVzWzBdLnVuaW9uQXJlYURpZmZlcmVuY2UoZW50cnkuYm91bmRzKTsKICAgICAgICAgICAgICAgIHZhciBhcmVhRGlmZjEgPSBub2Rlc1sxXS51bmlvbkFyZWFEaWZmZXJlbmNlKGVudHJ5LmJvdW5kcyk7CiAgICAgICAgICAgICAgICBpZiAoYXJlYURpZmYwIDwgbWluRGlmZiB8fCBpbmRleCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgaW5kZXggPSBpOwogICAgICAgICAgICAgICAgICAgIG1pbkRpZmYgPSBhcmVhRGlmZjA7CiAgICAgICAgICAgICAgICAgICAgbWluRGlmZk5vZGUgPSBub2Rlc1swXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChhcmVhRGlmZjEgPCBtaW5EaWZmKSB7CiAgICAgICAgICAgICAgICAgICAgaW5kZXggPSBpOwogICAgICAgICAgICAgICAgICAgIG1pbkRpZmYgPSBhcmVhRGlmZjE7CiAgICAgICAgICAgICAgICAgICAgbWluRGlmZk5vZGUgPSBub2Rlc1sxXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBtaW5EaWZmTm9kZS5pbnNlcnQoZW50cmllcy5zcGxpY2UoaW5kZXgsIDEpWzBdKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBTcGxpdFN0cmF0ZWd5TGluZWFyOwogICAgfSgpKTsKICAgIGV4cG9ydHMuU3BsaXRTdHJhdGVneUxpbmVhciA9IFNwbGl0U3RyYXRlZ3lMaW5lYXI7CiAgICB9KTsKCiAgICB2YXIgclRyZWUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvKioKICAgICAqIFRoZSBtYXhpbXVtIG51bWJlciBvZiBjaGlsZHJlbiBpbiBhbiByLXRyZWUgbm9kZSBiZWZvcmUgd2UgYXR0ZW1wdCB0byBzcGxpdC4KICAgICAqIFRoaXMgbXVzdCBiZSA+PSAyLgogICAgICovCiAgICB2YXIgREVGQVVMVF9NQVhfTk9ERV9DSElMRFJFTiA9IDU7CiAgICAvKioKICAgICAqIFRoZXJlIGFyZSBzZXZlcmFsIHN0cmF0ZWdpZXMgZm9yIHNwbGl0dGluZyBub2RlcyB0aGF0IGNvbnRhaW4gb3ZlcmxhcHBpbmcKICAgICAqIHJlZ2lvbnMuIEJ5IGRlZmF1bHQgd2UgdXNlIGBTcGxpdFN0cmF0ZWd5TGluZWFyYCB3aGljaCBtaW5pbWl6ZXMgdGhlIGNoYW5nZQogICAgICogaW4gbm9kZSBib3VuZGluZyBib3ggYXJlYS4KICAgICAqLwogICAgdmFyIERFRkFVTFRfU1BMSVRfU1RSQVRFR1kgPSBuZXcgclRyZWVTcGxpdFN0cmF0ZWdpZXMuU3BsaXRTdHJhdGVneUxpbmVhcigpOwogICAgLyoqCiAgICAgKiBUaGUgcmV0dXJuIHJlc3VsdCBvZiBwcmVkaWNhdGVzIHVzZWQgd2l0aCBgUlRyZWUucXVlcnlOb2Rlc2AuCiAgICAgKgogICAgICogVGhlIGBQQVNTX0FORF9PVkVSV1JJVEVgIHZhbHVlIHdpbGwgb3ZlcndyaXRlIHByZXZpb3VzIHJlc3VsdHMKICAgICAqIHdoZW4gdGhlIHByZWRpY2F0ZSBmaW5kcyBhIG1vcmUgb3B0aW1hbCByZXN1bHQuCiAgICAgKi8KICAgIHZhciBRdWVyeVByZWRpY2F0ZVJlc3VsdDsKICAgIChmdW5jdGlvbiAoUXVlcnlQcmVkaWNhdGVSZXN1bHQpIHsKICAgICAgICBRdWVyeVByZWRpY2F0ZVJlc3VsdFtRdWVyeVByZWRpY2F0ZVJlc3VsdFsiUEFTUyJdID0gMF0gPSAiUEFTUyI7CiAgICAgICAgUXVlcnlQcmVkaWNhdGVSZXN1bHRbUXVlcnlQcmVkaWNhdGVSZXN1bHRbIkZBSUwiXSA9IDFdID0gIkZBSUwiOwogICAgICAgIFF1ZXJ5UHJlZGljYXRlUmVzdWx0W1F1ZXJ5UHJlZGljYXRlUmVzdWx0WyJQQVNTX0FORF9PVkVSV1JJVEUiXSA9IDJdID0gIlBBU1NfQU5EX09WRVJXUklURSI7CiAgICB9KShRdWVyeVByZWRpY2F0ZVJlc3VsdCA9IGV4cG9ydHMuUXVlcnlQcmVkaWNhdGVSZXN1bHQgfHwgKGV4cG9ydHMuUXVlcnlQcmVkaWNhdGVSZXN1bHQgPSB7fSkpOwogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgbm9kZSBwcmVkaWNhdGUgZm9yIHVzZSB3aXRoIGBSVHJlZS5xdWVyeU5vZGVzYAogICAgICoKICAgICAqIEBwYXJhbSBwb2ludCAtIHRoZSBxdWVyeSBwb2ludAogICAgICogQHBhcmFtIG5lYXJGbiAtIGFuIGBJRGlzdGFuY2VGdW5jdGlvbmAgZnJvbSB0aGUgcXVlcnkgcG9pbnQgdG8gdGhlIG5lYXJlc3QKICAgICAqIHBvaW50IG9uIHRoZSBub2RlIGJvdW5kcwogICAgICogQHBhcmFtIGZhckZuIC0gYW4gYElEaXN0YW5jZUZ1bmN0aW9uYCBmcm9tIHRoZSBxdWVyeSBwb2ludCB0byB0aGUgZmFydGhlc3QKICAgICAqIHBvaW50IG9uIHRoZSBub2RlIGJvdW5kcwogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVNaW5pbWl6aW5nTm9kZVByZWRpY2F0ZShwb2ludCwgbmVhckZuLCBmYXJGbikgewogICAgICAgIHZhciBuZWFyZXN0TGVhZkRpc3RhbmNlID0gSW5maW5pdHk7CiAgICAgICAgdmFyIGZhcnRoZXN0QnJhbmNoRGlzdGFuY2UgPSBJbmZpbml0eTsKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKG5vZGUpIHsKICAgICAgICAgICAgdmFyIG5lYXIgPSBuZWFyRm4obm9kZS5ib3VuZHMsIHBvaW50KTsKICAgICAgICAgICAgdmFyIGZhciA9IGZhckZuKG5vZGUuYm91bmRzLCBwb2ludCk7CiAgICAgICAgICAgIC8vIGFzc3VtcHRpb246IG5vZGUudmFsdWUgaW5kaWNhdGVzIHRoYXQgcGFyZW50IGlzIGEgbGVhZgogICAgICAgICAgICBpZiAobm9kZS52YWx1ZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBpZiAobmVhciA8IG5lYXJlc3RMZWFmRGlzdGFuY2UpIHsKICAgICAgICAgICAgICAgICAgICBuZWFyZXN0TGVhZkRpc3RhbmNlID0gbmVhcjsKICAgICAgICAgICAgICAgICAgICBmYXJ0aGVzdEJyYW5jaERpc3RhbmNlID0gZmFyOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBRdWVyeVByZWRpY2F0ZVJlc3VsdC5QQVNTX0FORF9PVkVSV1JJVEU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChuZWFyID09PSBuZWFyZXN0TGVhZkRpc3RhbmNlKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFF1ZXJ5UHJlZGljYXRlUmVzdWx0LlBBU1M7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gUXVlcnlQcmVkaWNhdGVSZXN1bHQuRkFJTDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGlmIChuZWFyID4gZmFydGhlc3RCcmFuY2hEaXN0YW5jZSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBRdWVyeVByZWRpY2F0ZVJlc3VsdC5GQUlMOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgZmFydGhlc3RCcmFuY2hEaXN0YW5jZSA9IE1hdGgubWF4KGZhciwgZmFydGhlc3RCcmFuY2hEaXN0YW5jZSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFF1ZXJ5UHJlZGljYXRlUmVzdWx0LlBBU1M7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5jcmVhdGVNaW5pbWl6aW5nTm9kZVByZWRpY2F0ZSA9IGNyZWF0ZU1pbmltaXppbmdOb2RlUHJlZGljYXRlOwogICAgLyoqCiAgICAgKiBDcmVhdGUgYSBgQXJyYXkuc29ydGAgZnVuY3Rpb24gZnJvbSBhIHF1ZXJ5IHBvaW50IGFuZCBhIGRpc3RhbmNlIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVOb2RlU29ydChwb2ludCwgZGlzdGFuY2VGbikgewogICAgICAgIHJldHVybiBmdW5jdGlvbiAoYSwgYikgewogICAgICAgICAgICByZXR1cm4gZGlzdGFuY2VGbihiLmJvdW5kcywgcG9pbnQpIC0gZGlzdGFuY2VGbihhLmJvdW5kcywgcG9pbnQpOwogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLmNyZWF0ZU5vZGVTb3J0ID0gY3JlYXRlTm9kZVNvcnQ7CiAgICAvKioKICAgICAqIFItVHJlZSBpcyBhIG11bHRpZGltZW5zaW9uYWwgc3BhdGlhbCByZWdpb24gdHJlZS4gSXQgc3RvcmVzIGVudHJpZXMgdGhhdCBoYXZlCiAgICAgKiBhcmJpdHJhcmlseSBvdmVybGFwcGluZyBib3VuZGluZyBib3hlcyBhbmQgc3VwcG9ydHMgZWZmaWNpZW50IHBvaW50IGFuZAogICAgICogYm91bmRpbmcgYm94IG92ZXJsYXAgcXVlcmllcy4KICAgICAqCiAgICAgKiBBdmVyYWdlIHNlYXJjaCB0aW1lIGNvbXBsZXhpdHkgaXMgTyhsb2dfTShOKSkgd2hlcmUgTSA9IG1heCBjaGlsZHJlbiBwZXIgbm9kZQogICAgICogYW5kIE4gaXMgbnVtYmVyIG9mIHZhbHVlcyBzdG9yZWQgaW4gdHJlZS4KICAgICAqCiAgICAgKiBJdCBpcyBzaW1pbGFyIGluIHB1cnBvc2UgdG8gYSBxdWFkdHJlZSBleGNlcHQgcXVhZHRyZWVzIGNhbiBvbmx5IHN0b3JlIGEKICAgICAqIHNpbmdsZSBwb2ludCBwZXIgZW50cnkuIEFsc28sIHRoZSBzcGFjZS1wYXJ0aXRpb25pbmcgc3RydWN0dXJlIG9mIHF1YWR0cmVlcwogICAgICogcHJvdmlkZXMgZ3VhcmFudGVlcyB0aGF0IGFueSBnaXZlbiB2YWx1ZSBoYXMgbm8gbmVpZ2hib3JzIGNsb3NlciB0aGFuIGl0cwogICAgICogbm9kZSdzIGJvdW5kcywgd2hlcmVhcyByLXRyZWVzIHByb3ZpZGUgbm8gc3VjaCBndWFyYW50ZWVzLgogICAgICovCiAgICB2YXIgUlRyZWUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gUlRyZWUobWF4Tm9kZUNoaWxkcmVuLCBzcGxpdFN0cmF0ZWd5KSB7CiAgICAgICAgICAgIGlmIChtYXhOb2RlQ2hpbGRyZW4gPT09IHZvaWQgMCkgeyBtYXhOb2RlQ2hpbGRyZW4gPSBERUZBVUxUX01BWF9OT0RFX0NISUxEUkVOOyB9CiAgICAgICAgICAgIGlmIChzcGxpdFN0cmF0ZWd5ID09PSB2b2lkIDApIHsgc3BsaXRTdHJhdGVneSA9IERFRkFVTFRfU1BMSVRfU1RSQVRFR1k7IH0KICAgICAgICAgICAgdGhpcy5tYXhOb2RlQ2hpbGRyZW4gPSBtYXhOb2RlQ2hpbGRyZW47CiAgICAgICAgICAgIHRoaXMuc3BsaXRTdHJhdGVneSA9IHNwbGl0U3RyYXRlZ3k7CiAgICAgICAgICAgIHRoaXMucm9vdCA9IG5ldyBSVHJlZU5vZGUodHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuc2l6ZSA9IDA7CiAgICAgICAgfQogICAgICAgIFJUcmVlLnByb3RvdHlwZS5nZXRSb290ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5yb290OwogICAgICAgIH07CiAgICAgICAgUlRyZWUucHJvdG90eXBlLmNsZWFyID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLnJvb3QgPSBuZXcgUlRyZWVOb2RlKHRydWUpOwogICAgICAgICAgICB0aGlzLnNpemUgPSAwOwogICAgICAgIH07CiAgICAgICAgUlRyZWUucHJvdG90eXBlLmluc2VydCA9IGZ1bmN0aW9uIChib3VuZHMsIHZhbHVlKSB7CiAgICAgICAgICAgIHZhciBub2RlID0gdGhpcy5yb290OwogICAgICAgICAgICAvLyBDaG9vc2Ugc3VidHJlZSB1bnRpbCB3ZSBmaW5kIGEgbGVhZgogICAgICAgICAgICB3aGlsZSAoIW5vZGUubGVhZikgewogICAgICAgICAgICAgICAgbm9kZSA9IG5vZGUuc3VidHJlZShib3VuZHMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEluc2VydCBuZXcgdmFsdWUgbm9kZSBpbnRvIGxlYWYgbm9kZQogICAgICAgICAgICB2YXIgdmFsdWVOb2RlID0gUlRyZWVOb2RlLnZhbHVlTm9kZShib3VuZHMsIHZhbHVlKTsKICAgICAgICAgICAgbm9kZS5pbnNlcnQodmFsdWVOb2RlKTsKICAgICAgICAgICAgdGhpcy5zaXplICs9IDE7CiAgICAgICAgICAgIC8vIFdoaWxlIG5vZGUgb3ZlcmZsb3dzLCBzcGxpdCBhbmQgd2FsayB1cAogICAgICAgICAgICB3aGlsZSAobm9kZS5vdmVyZmxvdyh0aGlzLm1heE5vZGVDaGlsZHJlbikpIHsKICAgICAgICAgICAgICAgIG5vZGUgPSBub2RlLnNwbGl0KHRoaXMuc3BsaXRTdHJhdGVneSk7CiAgICAgICAgICAgICAgICBpZiAobm9kZS5wYXJlbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMucm9vdCA9IG5vZGU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHZhbHVlTm9kZTsKICAgICAgICB9OwogICAgICAgIFJUcmVlLnByb3RvdHlwZS5sb2NhdGUgPSBmdW5jdGlvbiAoeHkpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucXVlcnkoZnVuY3Rpb24gKGIpIHsgcmV0dXJuIGIuY29udGFpbnMoeHkpOyB9KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYW4gYXJyYXkgb2YgYFRgIHZhbHVlcyB0aGF0IGFyZSB0aGUgIm5lYXJlc3QiIHRvIHRoZSBxdWVyeSBwb2ludC4KICAgICAgICAgKgogICAgICAgICAqIE5lYXJuZXNzIGlzIG1lYXN1cmVkIGFzIHRoZSBhYnNvbHV0ZSBkaXN0YW5jZSBmcm9tIHRoZSBxdWVyeSBwb2ludCB0byB0aGUKICAgICAgICAgKiBuZWFyZXN0IGVkZ2Ugb2YgdGhlIG5vZGUgYm91bmRzLiBJZiB0aGUgbm9kZSBib3VuZHMgY29udGFpbnMgdGhlIHF1ZXJ5CiAgICAgICAgICogcG9pbnQsIHRoZSBkaXN0YW5jZSBpcyAwLgogICAgICAgICAqLwogICAgICAgIFJUcmVlLnByb3RvdHlwZS5sb2NhdGVOZWFyZXN0ID0gZnVuY3Rpb24gKHh5KSB7CiAgICAgICAgICAgIHZhciBwcmVkaWNhdGUgPSBjcmVhdGVNaW5pbWl6aW5nTm9kZVByZWRpY2F0ZSh4eSwgUlRyZWVCb3VuZHMuZGlzdGFuY2VTcXVhcmVkVG9OZWFyRWRnZSwgUlRyZWVCb3VuZHMuZGlzdGFuY2VTcXVhcmVkVG9GYXJFZGdlKTsKICAgICAgICAgICAgdmFyIG5vZGVzID0gdGhpcy5xdWVyeU5vZGVzKHByZWRpY2F0ZSk7CiAgICAgICAgICAgIHJldHVybiBub2Rlcy5tYXAoZnVuY3Rpb24gKG5vZGUpIHsgcmV0dXJuIG5vZGUudmFsdWU7IH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBhbiBhcnJheSBvZiBgVGAgdmFsdWVzIHRoYXQgYXJlIHRoZSAibmVhcmVzdCIgdG8gdGhlIHF1ZXJ5IHBvaW50LgogICAgICAgICAqCiAgICAgICAgICogTmVhcm5lc3MgaXMgbWVhc3VyZWQgYXMgdGhlIDEtZGltZW5zaW9uYWwgYWJzb2x1dGUgZGlzdGFuY2UgZnJvbSB0aGUKICAgICAgICAgKiBxdWVyeSdzIHggcG9pbnQgdG8gdGhlIG5lYXJlc3QgZWRnZSBvZiB0aGUgbm9kZSBib3VuZHMuIElmIHRoZSBub2RlCiAgICAgICAgICogYm91bmRzIGNvbnRhaW5zIHRoZSBxdWVyeSBwb2ludCwgdGhlIGRpc3RhbmNlIGlzIDAuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgcmVzdWx0cyBhcmUgc29ydGVkIGJ5IHktY29vcmRpbmF0ZSBuZWFybmVzcy4KICAgICAgICAgKi8KICAgICAgICBSVHJlZS5wcm90b3R5cGUubG9jYXRlTmVhcmVzdFggPSBmdW5jdGlvbiAoeHkpIHsKICAgICAgICAgICAgdmFyIHByZWRpY2F0ZSA9IGNyZWF0ZU1pbmltaXppbmdOb2RlUHJlZGljYXRlKHh5LCBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9OZWFyRWRnZVgsIFJUcmVlQm91bmRzLmFic29sdXRlRGlzdGFuY2VUb0ZhckVkZ2VYKTsKICAgICAgICAgICAgdmFyIG5vZGVzID0gdGhpcy5xdWVyeU5vZGVzKHByZWRpY2F0ZSk7CiAgICAgICAgICAgIG5vZGVzLnNvcnQoY3JlYXRlTm9kZVNvcnQoeHksIFJUcmVlQm91bmRzLmFic29sdXRlRGlzdGFuY2VUb05lYXJFZGdlWSkpOwogICAgICAgICAgICByZXR1cm4gbm9kZXMubWFwKGZ1bmN0aW9uIChub2RlKSB7IHJldHVybiBub2RlLnZhbHVlOyB9KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgYW4gYXJyYXkgb2YgYFRgIHZhbHVlcyB0aGF0IGFyZSB0aGUgIm5lYXJlc3QiIHRvIHRoZSBxdWVyeSBwb2ludC4KICAgICAgICAgKgogICAgICAgICAqIE5lYXJuZXNzIGlzIG1lYXN1cmVkIGFzIHRoZSAxLWRpbWVuc2lvbmFsIGFic29sdXRlIGRpc3RhbmNlIGZyb20gdGhlCiAgICAgICAgICogcXVlcnkncyB5IHBvaW50IHRvIHRoZSBuZWFyZXN0IGVkZ2Ugb2YgdGhlIG5vZGUgYm91bmRzLiBJZiB0aGUgbm9kZQogICAgICAgICAqIGJvdW5kcyBjb250YWlucyB0aGUgcXVlcnkgcG9pbnQsIHRoZSBkaXN0YW5jZSBpcyAwLgogICAgICAgICAqCiAgICAgICAgICogVGhlIHJlc3VsdHMgYXJlIHNvcnRlZCBieSB4LWNvb3JkaW5hdGUgbmVhcm5lc3MuCiAgICAgICAgICovCiAgICAgICAgUlRyZWUucHJvdG90eXBlLmxvY2F0ZU5lYXJlc3RZID0gZnVuY3Rpb24gKHh5KSB7CiAgICAgICAgICAgIHZhciBwcmVkaWNhdGUgPSBjcmVhdGVNaW5pbWl6aW5nTm9kZVByZWRpY2F0ZSh4eSwgUlRyZWVCb3VuZHMuYWJzb2x1dGVEaXN0YW5jZVRvTmVhckVkZ2VZLCBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9GYXJFZGdlWSk7CiAgICAgICAgICAgIHZhciBub2RlcyA9IHRoaXMucXVlcnlOb2RlcyhwcmVkaWNhdGUpOwogICAgICAgICAgICBub2Rlcy5zb3J0KGNyZWF0ZU5vZGVTb3J0KHh5LCBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9OZWFyRWRnZVgpKTsKICAgICAgICAgICAgcmV0dXJuIG5vZGVzLm1hcChmdW5jdGlvbiAobm9kZSkgeyByZXR1cm4gbm9kZS52YWx1ZTsgfSk7CiAgICAgICAgfTsKICAgICAgICBSVHJlZS5wcm90b3R5cGUuaW50ZXJzZWN0ID0gZnVuY3Rpb24gKGJvdW5kcykgewogICAgICAgICAgICByZXR1cm4gdGhpcy5xdWVyeShmdW5jdGlvbiAoYikgeyByZXR1cm4gUlRyZWVCb3VuZHMuaXNCb3VuZHNPdmVybGFwQm91bmRzKGIsIGJvdW5kcyk7IH0pOwogICAgICAgIH07CiAgICAgICAgUlRyZWUucHJvdG90eXBlLmludGVyc2VjdFggPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5KGZ1bmN0aW9uIChiKSB7IHJldHVybiBSVHJlZUJvdW5kcy5pc0JvdW5kc092ZXJsYXBYKGIsIGJvdW5kcyk7IH0pOwogICAgICAgIH07CiAgICAgICAgUlRyZWUucHJvdG90eXBlLmludGVyc2VjdFkgPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnF1ZXJ5KGZ1bmN0aW9uIChiKSB7IHJldHVybiBSVHJlZUJvdW5kcy5pc0JvdW5kc092ZXJsYXBZKGIsIGJvdW5kcyk7IH0pOwogICAgICAgIH07CiAgICAgICAgUlRyZWUucHJvdG90eXBlLnF1ZXJ5ID0gZnVuY3Rpb24gKHByZWRpY2F0ZSkgewogICAgICAgICAgICB2YXIgcmVzdWx0cyA9IFtdOwogICAgICAgICAgICBpZiAodGhpcy5yb290LmJvdW5kcyAhPSBudWxsICYmICFwcmVkaWNhdGUodGhpcy5yb290LmJvdW5kcykpIHsKICAgICAgICAgICAgICAgIHJldHVybiByZXN1bHRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBjYW5kaWRhdGVzID0gW3RoaXMucm9vdF07CiAgICAgICAgICAgIHdoaWxlIChjYW5kaWRhdGVzLmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgICAgIHZhciBjYW5kaWRhdGUgPSBjYW5kaWRhdGVzLnNoaWZ0KCk7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGNhbmRpZGF0ZS5lbnRyaWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGVudHJ5ID0gY2FuZGlkYXRlLmVudHJpZXNbaV07CiAgICAgICAgICAgICAgICAgICAgaWYgKHByZWRpY2F0ZShlbnRyeS5ib3VuZHMpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChjYW5kaWRhdGUubGVhZikgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmVzdWx0cy5wdXNoKGVudHJ5LnZhbHVlKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNhbmRpZGF0ZXMucHVzaChlbnRyeSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHJlc3VsdHM7CiAgICAgICAgfTsKICAgICAgICBSVHJlZS5wcm90b3R5cGUucXVlcnlOb2RlcyA9IGZ1bmN0aW9uIChwcmVkaWNhdGUpIHsKICAgICAgICAgICAgdmFyIHJlc3VsdHMgPSBbXTsKICAgICAgICAgICAgaWYgKHRoaXMucm9vdC5ib3VuZHMgIT0gbnVsbCAmJiBwcmVkaWNhdGUodGhpcy5yb290KSA9PT0gUXVlcnlQcmVkaWNhdGVSZXN1bHQuRkFJTCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHJlc3VsdHM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGNhbmRpZGF0ZXMgPSBbdGhpcy5yb290XTsKICAgICAgICAgICAgd2hpbGUgKGNhbmRpZGF0ZXMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgdmFyIGNhbmRpZGF0ZSA9IGNhbmRpZGF0ZXMuc2hpZnQoKTsKICAgICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgY2FuZGlkYXRlLmVudHJpZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgICAgICB2YXIgZW50cnkgPSBjYW5kaWRhdGUuZW50cmllc1tpXTsKICAgICAgICAgICAgICAgICAgICB2YXIgcCA9IHByZWRpY2F0ZShlbnRyeSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHAgPT09IFF1ZXJ5UHJlZGljYXRlUmVzdWx0LlBBU1NfQU5EX09WRVJXUklURSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXN1bHRzID0gW107CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmIChwID09PSBRdWVyeVByZWRpY2F0ZVJlc3VsdC5QQVNTIHx8IHAgPT09IFF1ZXJ5UHJlZGljYXRlUmVzdWx0LlBBU1NfQU5EX09WRVJXUklURSkgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoY2FuZGlkYXRlLmxlYWYpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlc3VsdHMucHVzaChlbnRyeSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjYW5kaWRhdGVzLnB1c2goZW50cnkpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHRzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFJUcmVlOwogICAgfSgpKTsKICAgIGV4cG9ydHMuUlRyZWUgPSBSVHJlZTsKICAgIHZhciBSVHJlZU5vZGUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gUlRyZWVOb2RlKGxlYWYpIHsKICAgICAgICAgICAgdGhpcy5sZWFmID0gbGVhZjsKICAgICAgICAgICAgdGhpcy5ib3VuZHMgPSBudWxsOwogICAgICAgICAgICB0aGlzLmVudHJpZXMgPSBbXTsKICAgICAgICAgICAgdGhpcy5wYXJlbnQgPSBudWxsOwogICAgICAgICAgICB0aGlzLnZhbHVlID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgUlRyZWVOb2RlLnZhbHVlTm9kZSA9IGZ1bmN0aW9uIChib3VuZHMsIHZhbHVlKSB7CiAgICAgICAgICAgIHZhciBub2RlID0gbmV3IFJUcmVlTm9kZSh0cnVlKTsKICAgICAgICAgICAgbm9kZS5ib3VuZHMgPSBib3VuZHM7CiAgICAgICAgICAgIG5vZGUudmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgcmV0dXJuIG5vZGU7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGB0cnVlYCBpZmYgdGhpcyBub2RlIGhhcyBtb3JlIGNoaWxkcmVuIHRoYW4gdGhlIGBtYXhOb2RlQ2hpbGRyZW5gCiAgICAgICAgICogcGFyYW1ldGVyLgogICAgICAgICAqLwogICAgICAgIFJUcmVlTm9kZS5wcm90b3R5cGUub3ZlcmZsb3cgPSBmdW5jdGlvbiAobWF4Tm9kZUNoaWxkcmVuKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmVudHJpZXMubGVuZ3RoID4gbWF4Tm9kZUNoaWxkcmVuOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogSW5zZXJ0cyBhIGNoaWxkIG5vZGUgYW5kIHVwZGF0ZXMgdGhlIGFuY2VzdHJ5IGJvdW5kcy4KICAgICAgICAgKi8KICAgICAgICBSVHJlZU5vZGUucHJvdG90eXBlLmluc2VydCA9IGZ1bmN0aW9uIChub2RlKSB7CiAgICAgICAgICAgIHRoaXMuZW50cmllcy5wdXNoKG5vZGUpOwogICAgICAgICAgICBub2RlLnBhcmVudCA9IHRoaXM7CiAgICAgICAgICAgIC8vIFVwZGF0ZSBhbmNlc3RvciBib3VuZHMKICAgICAgICAgICAgdmFyIGFuY2VzdG9yID0gdGhpczsKICAgICAgICAgICAgd2hpbGUgKGFuY2VzdG9yICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGFuY2VzdG9yLmJvdW5kcyA9IFJUcmVlQm91bmRzLnVuaW9uQWxsKFthbmNlc3Rvci5ib3VuZHMsIG5vZGUuYm91bmRzXSk7CiAgICAgICAgICAgICAgICBhbmNlc3RvciA9IGFuY2VzdG9yLnBhcmVudDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjaGlsZCBub2RlIGFuZCB1cGRhdGVzIHRoZSBhbmNlc3RyeSBib3VuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBJZiB0aGUgbm9kZSBhcmd1bWVudCBpcyBub3QgYSBjaGlsZCwgZG8gbm90aGluZy4KICAgICAgICAgKi8KICAgICAgICBSVHJlZU5vZGUucHJvdG90eXBlLnJlbW92ZSA9IGZ1bmN0aW9uIChub2RlKSB7CiAgICAgICAgICAgIHZhciBpID0gdGhpcy5lbnRyaWVzLmluZGV4T2Yobm9kZSk7CiAgICAgICAgICAgIGlmIChpID49IDApIHsKICAgICAgICAgICAgICAgIHRoaXMuZW50cmllcy5zcGxpY2UoaSwgMSk7CiAgICAgICAgICAgICAgICAvLyBVcGRhdGUgYW5jZXN0b3IgYm91bmRzCiAgICAgICAgICAgICAgICB2YXIgYW5jZXN0b3IgPSB0aGlzOwogICAgICAgICAgICAgICAgd2hpbGUgKGFuY2VzdG9yICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBhbmNlc3Rvci5ib3VuZHMgPSBSVHJlZUJvdW5kcy51bmlvbkFsbChhbmNlc3Rvci5lbnRyaWVzLm1hcChmdW5jdGlvbiAoZSkgeyByZXR1cm4gZS5ib3VuZHM7IH0pKTsKICAgICAgICAgICAgICAgICAgICBhbmNlc3RvciA9IGFuY2VzdG9yLnBhcmVudDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENob29zZXMgYW4gbm9kZSBmcm9tIHRoZW4gZW50cmllcyB0aGF0IG1pbmltaXplcyB0aGUgYXJlYSBkaWZmZXJlbmNlIHRoYXQKICAgICAgICAgKiBhZGRpbmcgdGhlIGJvdW5kcyB0aGUgZWFjaCBlbnRyeSB3b3VsZCBjYXVzZS4KICAgICAgICAgKi8KICAgICAgICBSVHJlZU5vZGUucHJvdG90eXBlLnN1YnRyZWUgPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHZhciBtaW5EaWZmID0gSW5maW5pdHk7CiAgICAgICAgICAgIHZhciBtaW5FbnRyeSA9IG51bGw7CiAgICAgICAgICAgIC8vIGNob29zZSBlbnRyeSBmb3Igd2hpY2ggdGhlIGFkZGl0aW9uIGxlYXN0IGluY3JlYXNlcyB0aGUgZW50cnkncyBhcmVhCiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGhpcy5lbnRyaWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICB2YXIgZW50cnkgPSB0aGlzLmVudHJpZXNbaV07CiAgICAgICAgICAgICAgICB2YXIgZGlmZkFyZWEgPSBlbnRyeS51bmlvbkFyZWFEaWZmZXJlbmNlKGJvdW5kcyk7CiAgICAgICAgICAgICAgICBpZiAoZGlmZkFyZWEgPCBtaW5EaWZmIHx8ICgKICAgICAgICAgICAgICAgIC8vIGJyZWFrIHRpZXMgdG8gbm9kZSB3aXRoIGZld2VzdCBjaGlsZHJlbgogICAgICAgICAgICAgICAgZGlmZkFyZWEgPT09IG1pbkRpZmYgJiYKICAgICAgICAgICAgICAgICAgICBtaW5FbnRyeSAhPSBudWxsICYmCiAgICAgICAgICAgICAgICAgICAgZW50cnkuZW50cmllcy5sZW5ndGggPCBtaW5FbnRyeS5lbnRyaWVzLmxlbmd0aCkpIHsKICAgICAgICAgICAgICAgICAgICBtaW5FbnRyeSA9IGVudHJ5OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBtaW5FbnRyeTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFNwbGl0cyB0aGlzIG5vZGUgYnkgY3JlYXRpbmcgdHdvIG5ldyBub2RlcyBhbmQgZGl2aWRpbmcgdGhlIHRoaXMgbm9kZSdzCiAgICAgICAgICogY2hpbGRyZW4gYmV0d2VlbiB0aGVtLiBUaGlzIG5vZGUgaXMgcmVtb3ZlZCBmcm9tIGl0cyBwYXJlbnQgYW5kIHRoZSB0d28KICAgICAgICAgKiBuZXcgbm9kZXMgYXJlIGFkZGVkLgogICAgICAgICAqCiAgICAgICAgICogSWYgdGhpcyBub2RlIGlzIHRoZSByb290LCBhIG5ldyBwYXJlbnQgbm9kZSBpcyBjcmVhdGVkLgogICAgICAgICAqCiAgICAgICAgICogUmV0dXJucyB0aGUgcGFyZW50IG5vZGUuCiAgICAgICAgICovCiAgICAgICAgUlRyZWVOb2RlLnByb3RvdHlwZS5zcGxpdCA9IGZ1bmN0aW9uIChzdHJhdGVneSkgewogICAgICAgICAgICAvLyBSZW1vdmUgc2VsZiBmcm9tIHBhcmVudC4KICAgICAgICAgICAgaWYgKHRoaXMucGFyZW50ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMucGFyZW50LnJlbW92ZSh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDcmVhdGUgY2hpbGRyZW4gZnJvbSBzcGxpdAogICAgICAgICAgICB2YXIgY2hpbGRyZW4gPSBbCiAgICAgICAgICAgICAgICBuZXcgUlRyZWVOb2RlKHRoaXMubGVhZiksCiAgICAgICAgICAgICAgICBuZXcgUlRyZWVOb2RlKHRoaXMubGVhZiksCiAgICAgICAgICAgIF07CiAgICAgICAgICAgIHN0cmF0ZWd5LnNwbGl0KHRoaXMuZW50cmllcywgY2hpbGRyZW4pOwogICAgICAgICAgICAvLyBBZGQgbmV3IG5vZGVzIHRvIHBhcmVudAogICAgICAgICAgICAvLyBJZiByb290LCBjcmVhdGUgbmV3IG5vbi1sZWFmIG5vZGUgYXMgcGFyZW50LgogICAgICAgICAgICB2YXIgcGFyZW50ID0gdGhpcy5wYXJlbnQgIT0gbnVsbCA/IHRoaXMucGFyZW50IDogbmV3IFJUcmVlTm9kZShmYWxzZSk7CiAgICAgICAgICAgIHBhcmVudC5pbnNlcnQoY2hpbGRyZW5bMF0pOwogICAgICAgICAgICBwYXJlbnQuaW5zZXJ0KGNoaWxkcmVuWzFdKTsKICAgICAgICAgICAgLy8gQWx3YXlzIG1ha2UgdGhlIHBhcmVudCBhIG5vbi1sZWFmIGFmdGVyIHNwbGl0CiAgICAgICAgICAgIHBhcmVudC5sZWFmID0gZmFsc2U7CiAgICAgICAgICAgIHJldHVybiBwYXJlbnQ7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBkaWZmZXJlbmNlIGluIGFyZWEgdGhhdCBhZGRpbmcgYW4gZW50cnkgYGJvdW5kc2AgdG8gdGhlIG5vZGUKICAgICAgICAgKiB3b3VsZCBjYXVzZS4KICAgICAgICAgKi8KICAgICAgICBSVHJlZU5vZGUucHJvdG90eXBlLnVuaW9uQXJlYURpZmZlcmVuY2UgPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHJldHVybiBNYXRoLmFicyhSVHJlZUJvdW5kcy51bmlvbih0aGlzLmJvdW5kcywgYm91bmRzKS5hcmVhKCkgLSB0aGlzLmJvdW5kcy5hcmVhKCkpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgZGVwdGggZnJvbSB0aGlzIG5vZGUgdG8gdGhlIGRlZXBlc3QgbGVhZiBkZXNjZW5kYW50LgogICAgICAgICAqLwogICAgICAgIFJUcmVlTm9kZS5wcm90b3R5cGUubWF4RGVwdGggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLmxlYWYpCiAgICAgICAgICAgICAgICByZXR1cm4gMTsKICAgICAgICAgICAgcmV0dXJuIDEgKyB0aGlzLmVudHJpZXMubWFwKGZ1bmN0aW9uIChlKSB7IHJldHVybiBlLm1heERlcHRoKCk7IH0pLnJlZHVjZShmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gTWF0aC5tYXgoYSwgYik7IH0pOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFJUcmVlTm9kZTsKICAgIH0oKSk7CiAgICBleHBvcnRzLlJUcmVlTm9kZSA9IFJUcmVlTm9kZTsKICAgIHZhciBSVHJlZUJvdW5kcyA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBSVHJlZUJvdW5kcyh4bCwgeWwsIHhoLCB5aCkgewogICAgICAgICAgICB0aGlzLnhsID0geGw7CiAgICAgICAgICAgIHRoaXMueWwgPSB5bDsKICAgICAgICAgICAgdGhpcy54aCA9IHhoOwogICAgICAgICAgICB0aGlzLnloID0geWg7CiAgICAgICAgICAgIHRoaXMud2lkdGggPSB0aGlzLnhoIC0gdGhpcy54bDsKICAgICAgICAgICAgdGhpcy5oZWlnaHQgPSB0aGlzLnloIC0gdGhpcy55bDsKICAgICAgICB9CiAgICAgICAgUlRyZWVCb3VuZHMueHl3aCA9IGZ1bmN0aW9uICh4LCB5LCB3LCBoKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgUlRyZWVCb3VuZHMoeCwgeSwgeCArIHcsIHkgKyBoKTsKICAgICAgICB9OwogICAgICAgIFJUcmVlQm91bmRzLmVudGl0eUJvdW5kcyA9IGZ1bmN0aW9uIChib3VuZHMpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBSVHJlZUJvdW5kcyhib3VuZHMueCwgYm91bmRzLnksIGJvdW5kcy54ICsgYm91bmRzLndpZHRoLCBib3VuZHMueSArIGJvdW5kcy5oZWlnaHQpOwogICAgICAgIH07CiAgICAgICAgUlRyZWVCb3VuZHMuYm91bmRzID0gZnVuY3Rpb24gKGJvdW5kcykgewogICAgICAgICAgICByZXR1cm4gUlRyZWVCb3VuZHMucG9pbnRQYWlyKGJvdW5kcy50b3BMZWZ0LCBib3VuZHMuYm90dG9tUmlnaHQpOwogICAgICAgIH07CiAgICAgICAgUlRyZWVCb3VuZHMucG9pbnRQYWlyID0gZnVuY3Rpb24gKHAwLCBwMSkgewogICAgICAgICAgICByZXR1cm4gbmV3IFJUcmVlQm91bmRzKE1hdGgubWluKHAwLngsIHAxLngpLCBNYXRoLm1pbihwMC55LCBwMS55KSwgTWF0aC5tYXgocDAueCwgcDEueCksIE1hdGgubWF4KHAwLnksIHAxLnkpKTsKICAgICAgICB9OwogICAgICAgIFJUcmVlQm91bmRzLnBvaW50cyA9IGZ1bmN0aW9uIChwb2ludHMpIHsKICAgICAgICAgICAgaWYgKHBvaW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIm5lZWQgYXQgbGVhc3QgMiBwb2ludHMgdG8gY3JlYXRlIGJvdW5kcyIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB4cyA9IHBvaW50cy5tYXAoZnVuY3Rpb24gKHApIHsgcmV0dXJuIHAueDsgfSk7CiAgICAgICAgICAgIHZhciB5cyA9IHBvaW50cy5tYXAoZnVuY3Rpb24gKHApIHsgcmV0dXJuIHAueTsgfSk7CiAgICAgICAgICAgIHJldHVybiBuZXcgUlRyZWVCb3VuZHMoeHMucmVkdWNlKGZ1bmN0aW9uIChhLCBiKSB7IHJldHVybiBNYXRoLm1pbihhLCBiKTsgfSksIHlzLnJlZHVjZShmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gTWF0aC5taW4oYSwgYik7IH0pLCB4cy5yZWR1Y2UoZnVuY3Rpb24gKGEsIGIpIHsgcmV0dXJuIE1hdGgubWF4KGEsIGIpOyB9KSwgeXMucmVkdWNlKGZ1bmN0aW9uIChhLCBiKSB7IHJldHVybiBNYXRoLm1heChhLCBiKTsgfSkpOwogICAgICAgIH07CiAgICAgICAgUlRyZWVCb3VuZHMudW5pb24gPSBmdW5jdGlvbiAoYjAsIGIxKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgUlRyZWVCb3VuZHMoTWF0aC5taW4oYjAueGwsIGIxLnhsKSwgTWF0aC5taW4oYjAueWwsIGIxLnlsKSwgTWF0aC5tYXgoYjAueGgsIGIxLnhoKSwgTWF0aC5tYXgoYjAueWgsIGIxLnloKSk7CiAgICAgICAgfTsKICAgICAgICBSVHJlZUJvdW5kcy51bmlvbkFsbCA9IGZ1bmN0aW9uIChib3VuZHMpIHsKICAgICAgICAgICAgYm91bmRzID0gYm91bmRzLmZpbHRlcihmdW5jdGlvbiAoYikgeyByZXR1cm4gYiAhPSBudWxsOyB9KTsKICAgICAgICAgICAgaWYgKGJvdW5kcy5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBib3VuZHMucmVkdWNlKGZ1bmN0aW9uIChiMCwgYjEpIHsgcmV0dXJuIFJUcmVlQm91bmRzLnVuaW9uKGIwLCBiMSk7IH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0cnVlIGlmIGBhYCBvdmVybGFwcyBgYmAgaW4gdGhlIHggYW5kIHkgYXhlcy4KICAgICAgICAgKgogICAgICAgICAqIFRvdWNoaW5nIGNvdW50cyBhcyBvdmVybGFwLgogICAgICAgICAqLwogICAgICAgIFJUcmVlQm91bmRzLmlzQm91bmRzT3ZlcmxhcEJvdW5kcyA9IGZ1bmN0aW9uIChhLCBiKSB7CiAgICAgICAgICAgIHJldHVybiBSVHJlZUJvdW5kcy5pc0JvdW5kc092ZXJsYXBYKGEsIGIpICYmIFJUcmVlQm91bmRzLmlzQm91bmRzT3ZlcmxhcFkoYSwgYik7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRydWUgaWYgYGFgIG92ZXJsYXBzIGBiYCBpbiB0aGUgeCBheGlzIG9ubHkuCiAgICAgICAgICoKICAgICAgICAgKiBUb3VjaGluZyBjb3VudHMgYXMgb3ZlcmxhcC4KICAgICAgICAgKi8KICAgICAgICBSVHJlZUJvdW5kcy5pc0JvdW5kc092ZXJsYXBYID0gZnVuY3Rpb24gKGEsIGIpIHsKICAgICAgICAgICAgcmV0dXJuICEoYS54aCA8IGIueGwpICYmICEoYS54bCA+IGIueGgpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0cnVlIGlmIGBhYCBvdmVybGFwcyBgYmAgaW4gdGhlIHkgYXhpcyBvbmx5LgogICAgICAgICAqCiAgICAgICAgICogVG91Y2hpbmcgY291bnRzIGFzIG92ZXJsYXAuCiAgICAgICAgICovCiAgICAgICAgUlRyZWVCb3VuZHMuaXNCb3VuZHNPdmVybGFwWSA9IGZ1bmN0aW9uIChhLCBiKSB7CiAgICAgICAgICAgIHJldHVybiAhKGEueWggPCBiLnlsKSAmJiAhKGEueWwgPiBiLnloKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIG9ydGhvZ29uYWwgYWJzb2x1dGUgZGlzdGFuY2UgaW4gdGhlIHgtZGltZW5zaW9uIGZyb20gcG9pbnQKICAgICAgICAgKiBgcGAgdG8gdGhlIG5lYXJlc3QgZWRnZSBvZiBgYm91bmRzYC4KICAgICAgICAgKgogICAgICAgICAqIElmIGBwLnhgIGlzIGluc2lkZSB0aGUgYm91bmRzIHJldHVybnMgYDBgLgogICAgICAgICAqLwogICAgICAgIFJUcmVlQm91bmRzLmFic29sdXRlRGlzdGFuY2VUb05lYXJFZGdlWCA9IGZ1bmN0aW9uIChib3VuZHMsIHApIHsKICAgICAgICAgICAgdmFyIGhhbGYgPSBib3VuZHMud2lkdGggLyAyOwogICAgICAgICAgICB2YXIgbWlkID0gYm91bmRzLnhsICsgaGFsZjsKICAgICAgICAgICAgcmV0dXJuIE1hdGgubWF4KE1hdGguYWJzKHAueCAtIG1pZCkgLSBoYWxmLCAwKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIG9ydGhvZ29uYWwgYWJzb2x1dGUgZGlzdGFuY2UgaW4gdGhlIHktZGltZW5zaW9uIGZyb20gcG9pbnQKICAgICAgICAgKiBgcGAgdG8gdGhlIG5lYXJlc3QgZWRnZSBvZiBgYm91bmRzYC4KICAgICAgICAgKgogICAgICAgICAqIElmIGBwLnlgIGlzIGluc2lkZSB0aGUgYm91bmRzIHJldHVybnMgYDBgLgogICAgICAgICAqLwogICAgICAgIFJUcmVlQm91bmRzLmFic29sdXRlRGlzdGFuY2VUb05lYXJFZGdlWSA9IGZ1bmN0aW9uIChib3VuZHMsIHApIHsKICAgICAgICAgICAgdmFyIGhhbGYgPSBib3VuZHMuaGVpZ2h0IC8gMjsKICAgICAgICAgICAgdmFyIG1pZCA9IGJvdW5kcy55bCArIGhhbGY7CiAgICAgICAgICAgIHJldHVybiBNYXRoLm1heChNYXRoLmFicyhwLnkgLSBtaWQpIC0gaGFsZiwgMCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBvcnRob2dvbmFsIGFic29sdXRlIGRpc3RhbmNlIGluIHRoZSB4LWRpbWVuc2lvbiBmcm9tIHBvaW50CiAgICAgICAgICogYHBgIHRvIHRoZSBmYXJ0aGVzdCBlZGdlIG9mIGBib3VuZHNgLgogICAgICAgICAqCiAgICAgICAgICogSWYgYHAueGAgaXMgaW5zaWRlIHRoZSBib3VuZHMgcmV0dXJucyBgMGAuCiAgICAgICAgICovCiAgICAgICAgUlRyZWVCb3VuZHMuYWJzb2x1dGVEaXN0YW5jZVRvRmFyRWRnZVggPSBmdW5jdGlvbiAoYm91bmRzLCBwKSB7CiAgICAgICAgICAgIHZhciBuZWFyID0gUlRyZWVCb3VuZHMuYWJzb2x1dGVEaXN0YW5jZVRvTmVhckVkZ2VYKGJvdW5kcywgcCk7CiAgICAgICAgICAgIHJldHVybiBuZWFyID09PSAwID8gMCA6IG5lYXIgKyBib3VuZHMud2lkdGg7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBvcnRob2dvbmFsIGFic29sdXRlIGRpc3RhbmNlIGluIHRoZSB5LWRpbWVuc2lvbiBmcm9tIHBvaW50CiAgICAgICAgICogYHBgIHRvIHRoZSBmYXJ0aGVzdCBlZGdlIG9mIGBib3VuZHNgLgogICAgICAgICAqCiAgICAgICAgICogSWYgYHAueWAgaXMgaW5zaWRlIHRoZSBib3VuZHMgcmV0dXJucyBgMGAuCiAgICAgICAgICovCiAgICAgICAgUlRyZWVCb3VuZHMuYWJzb2x1dGVEaXN0YW5jZVRvRmFyRWRnZVkgPSBmdW5jdGlvbiAoYm91bmRzLCBwKSB7CiAgICAgICAgICAgIHZhciBuZWFyID0gUlRyZWVCb3VuZHMuYWJzb2x1dGVEaXN0YW5jZVRvTmVhckVkZ2VZKGJvdW5kcywgcCk7CiAgICAgICAgICAgIHJldHVybiBuZWFyID09PSAwID8gMCA6IG5lYXIgKyBib3VuZHMuaGVpZ2h0OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgZGlzdGFuY2Ugc3F1YXJlZCBmcm9tIGBwYCB0byB0aGUgbmVhcmVzdCBlZGdlIG9mIGBib3VuZHNgLiBJZgogICAgICAgICAqIHRoZSBwb2ludCB0b3VjaGVzIG9yIGlzIGluc2lkZSB0aGUgYm91bmRzLCByZXR1cm5zIGAwYDsKICAgICAgICAgKgogICAgICAgICAqIGh0dHBzOi8vZ2FtZWRldi5zdGFja2V4Y2hhbmdlLmNvbS9xdWVzdGlvbnMvNDQ0ODMvaG93LWRvLWktY2FsY3VsYXRlLWRpc3RhbmNlLWJldHdlZW4tYS1wb2ludC1hbmQtYW4tYXhpcy1hbGlnbmVkLXJlY3RhbmdsZQogICAgICAgICAqLwogICAgICAgIFJUcmVlQm91bmRzLmRpc3RhbmNlU3F1YXJlZFRvTmVhckVkZ2UgPSBmdW5jdGlvbiAoYm91bmRzLCBwKSB7CiAgICAgICAgICAgIHZhciBkeCA9IFJUcmVlQm91bmRzLmFic29sdXRlRGlzdGFuY2VUb05lYXJFZGdlWChib3VuZHMsIHApOwogICAgICAgICAgICB2YXIgZHkgPSBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9OZWFyRWRnZVkoYm91bmRzLCBwKTsKICAgICAgICAgICAgcmV0dXJuIGR4ICogZHggKyBkeSAqIGR5OwogICAgICAgIH07CiAgICAgICAgUlRyZWVCb3VuZHMuZGlzdGFuY2VTcXVhcmVkVG9GYXJFZGdlID0gZnVuY3Rpb24gKGJvdW5kcywgcCkgewogICAgICAgICAgICB2YXIgZHggPSBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9GYXJFZGdlWChib3VuZHMsIHApOwogICAgICAgICAgICB2YXIgZHkgPSBSVHJlZUJvdW5kcy5hYnNvbHV0ZURpc3RhbmNlVG9GYXJFZGdlWShib3VuZHMsIHApOwogICAgICAgICAgICByZXR1cm4gZHggKiBkeCArIGR5ICogZHk7CiAgICAgICAgfTsKICAgICAgICBSVHJlZUJvdW5kcy5wcm90b3R5cGUuYXJlYSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuYXJlYUNhY2hlZCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFyZWFDYWNoZWQgPSAodGhpcy54aCAtIHRoaXMueGwpICogKHRoaXMueWggLSB0aGlzLnlsKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5hcmVhQ2FjaGVkOwogICAgICAgIH07CiAgICAgICAgUlRyZWVCb3VuZHMucHJvdG90eXBlLmNvbnRhaW5zID0gZnVuY3Rpb24gKHh5KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnhsIDw9IHh5LnggJiYgdGhpcy54aCA+PSB4eS54ICYmIHRoaXMueWwgPD0geHkueSAmJiB0aGlzLnloID49IHh5Lnk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gUlRyZWVCb3VuZHM7CiAgICB9KCkpOwogICAgZXhwb3J0cy5SVHJlZUJvdW5kcyA9IFJUcmVlQm91bmRzOwogICAgfSk7CgogICAgdmFyIHN0YWNraW5nVXRpbHMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCiAgICAvKioKICAgICAqIE9wdGlvbiB0eXBlIGZvciBzdGFja2luZyBkaXJlY3Rpb24uIEJ5IGRlZmF1bHQsIHN0YWNrZWQgYmFyIGFuZCBhcmVhIGNoYXJ0cwogICAgICogcHV0IHRoZSBmaXJzdCBkYXRhIHNlcmllcyBhdCB0aGUgYm90dG9tIG9mIHRoZSBheGlzICgiYm90dG9tdXAiKSwgYnV0IHRoaXMKICAgICAqIGNhbiBiZSByZXZlcnNlZCB3aXRoIHRoZSAidG9wZG93biIgb3B0aW9uLCB3aGljaCBwcm9kdWNlcyBhIHN0YWNraW5nIG9yZGVyCiAgICAgKiB0aGF0IG1hdGNoZXMgdGhlIG9yZGVyIG9mIHNlcmllcyBpbiB0aGUgbGVnZW5kLgogICAgICovCiAgICBleHBvcnRzLklTdGFja2luZ09yZGVyID0gbWFrZUVudW1fMS5tYWtlRW51bShbInRvcGRvd24iLCAiYm90dG9tdXAiXSk7CiAgICB2YXIgbmF0aXZlTWF0aCA9IHdpbmRvdy5NYXRoOwogICAgLyoqCiAgICAgKiBDb21wdXRlcyB0aGUgU3RhY2tpbmdSZXN1bHQgKHZhbHVlIGFuZCBvZmZzZXQpIGZvciBlYWNoIGRhdGEgcG9pbnQgaW4gZWFjaCBEYXRhc2V0LgogICAgICoKICAgICAqIEBwYXJhbSB7RGF0YXNldFtdfSBkYXRhc2V0cyBUaGUgRGF0YXNldHMgdG8gYmUgc3RhY2tlZCBvbiB0b3Agb2YgZWFjaCBvdGhlciBpbiB0aGUgb3JkZXIgb2Ygc3RhY2tpbmcKICAgICAqIEBwYXJhbSB7QWNjZXNzb3I8YW55Pn0ga2V5QWNjZXNzb3IgQWNjZXNzb3IgZm9yIHRoZSBrZXkgb2YgdGhlIGRhdGEKICAgICAqIEBwYXJhbSB7QWNjZXNzb3I8bnVtYmVyPn0gdmFsdWVBY2Nlc3NvciBBY2Nlc3NvciBmb3IgdGhlIHZhbHVlIG9mIHRoZSBkYXRhCiAgICAgKiBAcGFyYW0ge0lTdGFja2luZ09yZGVyfSBzdGFja2luZ09yZGVyIFRoZSBvcmRlciBvZiBzdGFja2luZyAoZGVmYXVsdCAiYm90dG9tdXAiKQogICAgICogQHJldHVybiB7U3RhY2tpbmdSZXN1bHR9IHZhbHVlIGFuZCBvZmZzZXQgZm9yIGVhY2ggZGF0YXBvaW50IGluIGVhY2ggRGF0YXNldAogICAgICovCiAgICBmdW5jdGlvbiBzdGFjayhkYXRhc2V0cywga2V5QWNjZXNzb3IsIHZhbHVlQWNjZXNzb3IsIHN0YWNraW5nT3JkZXIpIHsKICAgICAgICBpZiAoc3RhY2tpbmdPcmRlciA9PT0gdm9pZCAwKSB7IHN0YWNraW5nT3JkZXIgPSAiYm90dG9tdXAiOyB9CiAgICAgICAgdmFyIHBvc2l0aXZlT2Zmc2V0cyA9IGQzLm1hcCgpOwogICAgICAgIHZhciBuZWdhdGl2ZU9mZnNldHMgPSBkMy5tYXAoKTsKICAgICAgICB2YXIgZGF0YXNldFRvS2V5VG9TdGFja2VkRGF0dW0gPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICBpZiAoc3RhY2tpbmdPcmRlciA9PT0gInRvcGRvd24iKSB7CiAgICAgICAgICAgIGRhdGFzZXRzID0gZGF0YXNldHMuc2xpY2UoKTsKICAgICAgICAgICAgZGF0YXNldHMucmV2ZXJzZSgpOwogICAgICAgIH0KICAgICAgICBmb3IgKHZhciBfaSA9IDAsIGRhdGFzZXRzXzEgPSBkYXRhc2V0czsgX2kgPCBkYXRhc2V0c18xLmxlbmd0aDsgX2krKykgewogICAgICAgICAgICB2YXIgZGF0YXNldCA9IGRhdGFzZXRzXzFbX2ldOwogICAgICAgICAgICB2YXIga2V5VG9TdGFja2VkRGF0dW0gPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKTsKICAgICAgICAgICAgdmFyIGRhdGFMZW4gPSBkYXRhLmxlbmd0aDsKICAgICAgICAgICAgZm9yICh2YXIgaW5kZXggPSAwOyBpbmRleCA8IGRhdGFMZW47IGluZGV4KyspIHsKICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGRhdGFbaW5kZXhdOwogICAgICAgICAgICAgICAgdmFyIGFjY2Vzc2VkS2V5ID0ga2V5QWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBrZXkgPSBleHBvcnRzLm5vcm1hbGl6ZUtleShhY2Nlc3NlZEtleSk7CiAgICAgICAgICAgICAgICB2YXIgdmFsdWUgPSArdmFsdWVBY2Nlc3NvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIG9mZnNldCA9IHZvaWQgMDsKICAgICAgICAgICAgICAgIHZhciBvZmZzZXRNYXAgPSAodmFsdWUgPj0gMCkgPyBwb3NpdGl2ZU9mZnNldHMgOiBuZWdhdGl2ZU9mZnNldHM7CiAgICAgICAgICAgICAgICBpZiAob2Zmc2V0TWFwLmhhcyhrZXkpKSB7CiAgICAgICAgICAgICAgICAgICAgb2Zmc2V0ID0gb2Zmc2V0TWFwLmdldChrZXkpOwogICAgICAgICAgICAgICAgICAgIG9mZnNldE1hcC5zZXQoa2V5LCBvZmZzZXQgKyB2YWx1ZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBvZmZzZXQgPSAwOwogICAgICAgICAgICAgICAgICAgIG9mZnNldE1hcC5zZXQoa2V5LCB2YWx1ZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBrZXlUb1N0YWNrZWREYXR1bS5zZXQoa2V5LCB7CiAgICAgICAgICAgICAgICAgICAgb2Zmc2V0OiBvZmZzZXQsCiAgICAgICAgICAgICAgICAgICAgdmFsdWU6IHZhbHVlLAogICAgICAgICAgICAgICAgICAgIGF4aXNWYWx1ZTogYWNjZXNzZWRLZXksCiAgICAgICAgICAgICAgICAgICAgb3JpZ2luYWxEYXR1bTogZGF0dW0sCiAgICAgICAgICAgICAgICAgICAgb3JpZ2luYWxEYXRhc2V0OiBkYXRhc2V0LAogICAgICAgICAgICAgICAgICAgIG9yaWdpbmFsSW5kZXg6IGluZGV4LAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZGF0YXNldFRvS2V5VG9TdGFja2VkRGF0dW0uc2V0KGRhdGFzZXQsIGtleVRvU3RhY2tlZERhdHVtKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGRhdGFzZXRUb0tleVRvU3RhY2tlZERhdHVtOwogICAgfQogICAgZXhwb3J0cy5zdGFjayA9IHN0YWNrOwogICAgLyoqCiAgICAgKiBDb21wdXRlcyB0aGUgbWF4aW11bSBhbmQgbWluaW11bSBleHRlbnRzIG9mIGVhY2ggc3RhY2sgaW5kaXZpZHVhbGx5LgogICAgICoKICAgICAqIEBwYXJhbSB7R2VuZXJpY1N0YWNraW5nUmVzdWx0fSBzdGFja2luZ1Jlc3VsdCBUaGUgdmFsdWUgYW5kIG9mZnNldCBpbmZvcm1hdGlvbiBmb3IgZWFjaCBkYXRhcG9pbnQgaW4gZWFjaCBkYXRhc2V0CiAgICAgKiBAcmV0dXJuIHsgeyBtYXhpbXVtRXh0ZW50czogVXRpbHMuTWFwPEQsIG51bWJlcj4sIG1pbmltdW1FeHRlbnRzOiBVdGlscy5NYXA8RCwgbnVtYmVyPiB9IH0gVGhlIG1heGltdW0gYW5kIG1pbmltdW0gZXh0ZW50cwogICAgICogb2YgZWFjaCBpbmRpdmlkdWFsIHN0YWNrLgogICAgICovCiAgICBmdW5jdGlvbiBzdGFja2VkRXh0ZW50cyhzdGFja2luZ1Jlc3VsdCkgewogICAgICAgIHZhciBtYXhpbXVtRXh0ZW50cyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgIHZhciBtaW5pbXVtRXh0ZW50cyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgIHN0YWNraW5nUmVzdWx0LmZvckVhY2goZnVuY3Rpb24gKHN0YWNrKSB7CiAgICAgICAgICAgIHN0YWNrLmZvckVhY2goZnVuY3Rpb24gKGRhdHVtLCBrZXkpIHsKICAgICAgICAgICAgICAgIC8vIGNvcnJlY3RseSBoYW5kbGUgbmVnYXRpdmUgYmFyIHN0YWNrcwogICAgICAgICAgICAgICAgdmFyIG9mZnNldFZhbHVlID0gZGF0dW0ub2Zmc2V0ICsgZGF0dW0udmFsdWU7CiAgICAgICAgICAgICAgICB2YXIgbWF4aW1hbFZhbHVlID0gdXRpbHMkMS5NYXRoLm1heChbb2Zmc2V0VmFsdWUsIGRhdHVtLm9mZnNldF0sIGRhdHVtLm9mZnNldCk7CiAgICAgICAgICAgICAgICB2YXIgbWluaW1hbFZhbHVlID0gdXRpbHMkMS5NYXRoLm1pbihbb2Zmc2V0VmFsdWUsIGRhdHVtLm9mZnNldF0sIGRhdHVtLm9mZnNldCk7CiAgICAgICAgICAgICAgICB2YXIgYXhpc1ZhbHVlID0gZGF0dW0uYXhpc1ZhbHVlOwogICAgICAgICAgICAgICAgaWYgKCFtYXhpbXVtRXh0ZW50cy5oYXMoa2V5KSkgewogICAgICAgICAgICAgICAgICAgIG1heGltdW1FeHRlbnRzLnNldChrZXksIHsgZXh0ZW50OiBtYXhpbWFsVmFsdWUsIGF4aXNWYWx1ZTogYXhpc1ZhbHVlLCBzdGFja2VkRGF0dW06IGRhdHVtIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAobWF4aW11bUV4dGVudHMuZ2V0KGtleSkuZXh0ZW50IDwgbWF4aW1hbFZhbHVlKSB7CiAgICAgICAgICAgICAgICAgICAgbWF4aW11bUV4dGVudHMuc2V0KGtleSwgeyBleHRlbnQ6IG1heGltYWxWYWx1ZSwgYXhpc1ZhbHVlOiBheGlzVmFsdWUsIHN0YWNrZWREYXR1bTogZGF0dW0gfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoIW1pbmltdW1FeHRlbnRzLmhhcyhrZXkpKSB7CiAgICAgICAgICAgICAgICAgICAgbWluaW11bUV4dGVudHMuc2V0KGtleSwgeyBleHRlbnQ6IG1pbmltYWxWYWx1ZSwgYXhpc1ZhbHVlOiBheGlzVmFsdWUsIHN0YWNrZWREYXR1bTogZGF0dW0gfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChtaW5pbXVtRXh0ZW50cy5nZXQoa2V5KS5leHRlbnQgPiAobWluaW1hbFZhbHVlKSkgewogICAgICAgICAgICAgICAgICAgIG1pbmltdW1FeHRlbnRzLnNldChrZXksIHsgZXh0ZW50OiBtaW5pbWFsVmFsdWUsIGF4aXNWYWx1ZTogYXhpc1ZhbHVlLCBzdGFja2VkRGF0dW06IGRhdHVtIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4geyBtYXhpbXVtRXh0ZW50czogbWF4aW11bUV4dGVudHMsIG1pbmltdW1FeHRlbnRzOiBtaW5pbXVtRXh0ZW50cyB9OwogICAgfQogICAgZXhwb3J0cy5zdGFja2VkRXh0ZW50cyA9IHN0YWNrZWRFeHRlbnRzOwogICAgLyoqCiAgICAgKiBDb21wdXRlcyB0aGUgdG90YWwgZXh0ZW50IG92ZXIgYWxsIGRhdGEgcG9pbnRzIGluIGFsbCBEYXRhc2V0cywgdGFraW5nIHN0YWNraW5nIGludG8gY29uc2lkZXJhdGlvbi4KICAgICAqCiAgICAgKiBAcGFyYW0ge1N0YWNraW5nUmVzdWx0fSBzdGFja2luZ1Jlc3VsdCBUaGUgdmFsdWUgYW5kIG9mZnNldCBpbmZvcm1hdGlvbiBmb3IgZWFjaCBkYXRhcG9pbnQgaW4gZWFjaCBkYXRhc2V0CiAgICAgKiBAcGFyYW0ge0FjY2Vzc29yPGFueT59IGtleUFjY2Vzc29yIEFjY2Vzc29yIGZvciB0aGUga2V5IG9mIHRoZSBkYXRhIGV4aXN0ZW50IGluIHRoZSBzdGFja2luZ1Jlc3VsdAogICAgICogQHBhcmFtIHtBY2Nlc3Nvcjxib29sZWFuPn0gZmlsdGVyIEEgZmlsdGVyIGZvciBkYXRhIHRvIGJlIGNvbnNpZGVyZWQgd2hlbiBjb21wdXRpbmcgdGhlIHRvdGFsIGV4dGVudAogICAgICogQHJldHVybiB7W251bWJlciwgbnVtYmVyXX0gVGhlIHRvdGFsIGV4dGVudAogICAgICovCiAgICBmdW5jdGlvbiBzdGFja2VkRXh0ZW50KHN0YWNraW5nUmVzdWx0LCBrZXlBY2Nlc3NvciwgZmlsdGVyKSB7CiAgICAgICAgdmFyIGV4dGVudHMgPSBbXTsKICAgICAgICBzdGFja2luZ1Jlc3VsdC5mb3JFYWNoKGZ1bmN0aW9uIChzdGFja2VkRGF0dW1NYXAsIGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKTsKICAgICAgICAgICAgdmFyIGRhdGFMZW4gPSBkYXRhLmxlbmd0aDsKICAgICAgICAgICAgZm9yICh2YXIgaW5kZXggPSAwOyBpbmRleCA8IGRhdGFMZW47IGluZGV4KyspIHsKICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGRhdGFbaW5kZXhdOwogICAgICAgICAgICAgICAgaWYgKGZpbHRlciAhPSBudWxsICYmICFmaWx0ZXIoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSkgewogICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIHN0YWNrZWREYXR1bSA9IHN0YWNrZWREYXR1bU1hcC5nZXQoZXhwb3J0cy5ub3JtYWxpemVLZXkoa2V5QWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSkpOwogICAgICAgICAgICAgICAgZXh0ZW50cy5wdXNoKHN0YWNrZWREYXR1bS52YWx1ZSArIHN0YWNrZWREYXR1bS5vZmZzZXQpOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgdmFyIG1heFN0YWNrRXh0ZW50ID0gdXRpbHMkMS5NYXRoLm1heChleHRlbnRzLCAwKTsKICAgICAgICB2YXIgbWluU3RhY2tFeHRlbnQgPSB1dGlscyQxLk1hdGgubWluKGV4dGVudHMsIDApOwogICAgICAgIHJldHVybiBbbmF0aXZlTWF0aC5taW4obWluU3RhY2tFeHRlbnQsIDApLCBuYXRpdmVNYXRoLm1heCgwLCBtYXhTdGFja0V4dGVudCldOwogICAgfQogICAgZXhwb3J0cy5zdGFja2VkRXh0ZW50ID0gc3RhY2tlZEV4dGVudDsKICAgIC8qKgogICAgICogTm9ybWFsaXplcyBhIGtleSB1c2VkIGZvciBzdGFja2luZwogICAgICoKICAgICAqIEBwYXJhbSB7YW55fSBrZXkgVGhlIGtleSB0byBiZSBub3JtYWxpemVkCiAgICAgKiBAcmV0dXJuIHtzdHJpbmd9IFRoZSBzdHJpbmdpZmllZCBrZXkKICAgICAqLwogICAgZXhwb3J0cy5ub3JtYWxpemVLZXkgPSBsb2Rhc2gubWVtb2l6ZShmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgcmV0dXJuIFN0cmluZyhrZXkpOwogICAgfSk7CiAgICB9KTsKCiAgICB2YXIgY29uZmlnJDEgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIC8qKgogICAgICogU3BlY2lmaWVzIGlmIFBsb3R0YWJsZSBzaG91bGQgc2hvdyB3YXJuaW5ncy4KICAgICAqLwogICAgZXhwb3J0cy5TSE9XX1dBUk5JTkdTID0gdHJ1ZTsKICAgIC8qKgogICAgICogU3BlY2lmaWVzIGlmIFBsb3R0YWJsZSBzaG91bGQgYWRkIDx0aXRsZT4gZWxlbWVudHMgdG8gdGV4dC4KICAgICAqLwogICAgZXhwb3J0cy5BRERfVElUTEVfRUxFTUVOVFMgPSB0cnVlOwogICAgfSk7CgogICAgdmFyIHdpbmRvd1V0aWxzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgLyoqCiAgICAgKiBQcmludCBhIHdhcm5pbmcgbWVzc2FnZSB0byB0aGUgY29uc29sZSwgaWYgaXQgaXMgYXZhaWxhYmxlLgogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBUaGUgd2FybmluZ3MgdG8gcHJpbnQKICAgICAqLwogICAgZnVuY3Rpb24gd2Fybih3YXJuaW5nKSB7CiAgICAgICAgaWYgKCFjb25maWckMS5TSE9XX1dBUk5JTkdTKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLWNvbnNvbGUKICAgICAgICBjb25zb2xlLndhcm4od2FybmluZyk7CiAgICB9CiAgICBleHBvcnRzLndhcm4gPSB3YXJuOwogICAgLyoqCiAgICAgKiBJcyBsaWtlIHNldFRpbWVvdXQsIGJ1dCBhY3RpdmF0ZXMgc3luY2hyb25vdXNseSBpZiB0aW1lPTAKICAgICAqIFdlIHNwZWNpYWwgY2FzZSAwIGJlY2F1c2Ugb2YgYW4gb2JzZXJ2ZWQgaXNzdWUgd2hlcmUgY2FsbGluZyBzZXRUaW1lb3V0IGNhdXNlcyB2aXNpYmxlIGZsaWNrZXJpbmcuCiAgICAgKiBXZSBiZWxpZXZlIHRoaXMgaXMgYmVjYXVzZSB3aGVuIHJlcXVlc3RBbmltYXRpb25GcmFtZSBjYWxscyBpbnRvIHRoZSBwYWludCBmdW5jdGlvbiwgYXMgc29vbiBhcyB0aGF0IGZ1bmN0aW9uIGZpbmlzaGVzCiAgICAgKiBldmFsdWF0aW5nLCB0aGUgcmVzdWx0cyBhcmUgcGFpbnRlZCB0byB0aGUgc2NyZWVuLiBBcyBhIHJlc3VsdCwgaWYgd2Ugd2FudCBzb21ldGhpbmcgdG8gb2NjdXIgaW1tZWRpYXRlbHkgYnV0IGNhbGwgc2V0VGltZW91dAogICAgICogd2l0aCB0aW1lPTAsIHRoZW4gaXQgaXMgcHVzaGVkIHRvIHRoZSBjYWxsIHN0YWNrIGFuZCByZW5kZXJlZCBpbiB0aGUgbmV4dCBmcmFtZSwgc28gdGhlIGNvbXBvbmVudCB0aGF0IHdhcyByZW5kZXJlZCB2aWEKICAgICAqIHNldFRpbWVvdXQgYXBwZWFycyBvdXQtb2Ytc3luYyB3aXRoIHRoZSByZXN0IG9mIHRoZSBwbG90LgogICAgICovCiAgICBmdW5jdGlvbiBzZXRUaW1lb3V0KGYsIHRpbWUpIHsKICAgICAgICB2YXIgYXJncyA9IFtdOwogICAgICAgIGZvciAodmFyIF9pID0gMjsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgIGFyZ3NbX2kgLSAyXSA9IGFyZ3VtZW50c1tfaV07CiAgICAgICAgfQogICAgICAgIGlmICh0aW1lID09PSAwKSB7CiAgICAgICAgICAgIGYoYXJncyk7CiAgICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHJldHVybiB3aW5kb3cuc2V0VGltZW91dChmLCB0aW1lLCBhcmdzKTsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLnNldFRpbWVvdXQgPSBzZXRUaW1lb3V0OwogICAgLyoqCiAgICAgKiBEZWJvdW5jZXMgdGhlIHN1cHBsaWVkIGNhbGxiYWNrIGFuZCByZXR1cm5zIGEgZnVuY3Rpb24gd2l0aCB0aGUgc2FtZQogICAgICogYXJndW1lbnRzLgogICAgICoKICAgICAqIFRoZSBjYWxsYmFjayBpcyBzY2hlZHVsZSBmb3IgaW52b2NhdGlvbiBldmVyeSB0aW1lIHRoZSByZXR1cm5lZCBmdW5jdGlvbiBpcwogICAgICogaW52b2tlZC4gSWYgdGhlIHJldHVybmVkIGZ1bmN0aW9uIGlzIGNhbGxlZCB3aXRoaW4gdGhlIGRlYm91bmNlIHRpbWUsIHRoZQogICAgICogcHJldmlvdXNseSBzY2hlZHVsZWQgY2FsbCBpcyBjYW5jZWxlZCBhbmQgdGhlIGNhbGxiYWNrIGlzIHNjaGVkdWxlIGFnYWluLgogICAgICoKICAgICAqIElmIGRlYm91bmNlZCwgdGhlIGNhbGxiYWNrIHdpbGwgYmUgY2FsbGVkIHdpdGggdGhlIG1vc3QgcmVjZW50IGFyZ3VtZW50cy4KICAgICAqCiAgICAgKiBAcGFyYW0ge251bWJlcn0gbXNlYyAtIHRoZSBkZWJvdW5jZSB0aW1lIGluIG1pbGxpc2Vjb25kcwogICAgICogQHBhcmFtIHtUfSBjYWxsYmFjayAtIHRoZSBjYWxsYmFjayBpbnZva2VkIGFmdGVyIHRoZSBkZWJvdW5jZSB0aW1lCiAgICAgKiBAcGFyYW0ge2FueX0gY29udGV4dCAgLSB0aGUgYHRoaXNgIGFyZ3VtZW50IHVzZWQgdG8gaW52b2tlIHRoZSBjYWxsYmFjawogICAgICovCiAgICBmdW5jdGlvbiBkZWJvdW5jZShtc2VjLCBjYWxsYmFjaywgY29udGV4dCkgewogICAgICAgIHZhciB0aW1lb3V0VG9rZW4gPSBudWxsOwogICAgICAgIHZhciBhcmdzID0gW107CiAgICAgICAgdmFyIGRlZmVycmVkQ2FsbGJhY2sgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGNhbGxiYWNrLmFwcGx5KGNvbnRleHQsIGFyZ3MpOwogICAgICAgIH07CiAgICAgICAgLy8gY29lcmNlIHRvIFQKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBhcmdzID0gQXJyYXkucHJvdG90eXBlLnNsaWNlLmNhbGwoYXJndW1lbnRzKTsKICAgICAgICAgICAgY2xlYXJUaW1lb3V0KHRpbWVvdXRUb2tlbik7CiAgICAgICAgICAgIHRpbWVvdXRUb2tlbiA9IHNldFRpbWVvdXQoZGVmZXJyZWRDYWxsYmFjaywgbXNlYyk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuZGVib3VuY2UgPSBkZWJvdW5jZTsKICAgIC8qKgogICAgICogU2VuZHMgYSBkZXByZWNhdGlvbiB3YXJuaW5nIHRvIHRoZSBjb25zb2xlLiBUaGUgd2FybmluZyBpbmNsdWRlcyB0aGUgbmFtZSBvZiB0aGUgZGVwcmVjYXRlZCBtZXRob2QsCiAgICAgKiB2ZXJzaW9uIG51bWJlciBvZiB0aGUgZGVwcmVjYXRpb24sIGFuZCBhbiBvcHRpb25hbCBtZXNzYWdlLgogICAgICoKICAgICAqIFRvIGJlIHVzZWQgaW4gdGhlIGZpcnN0IGxpbmUgb2YgYSBkZXByZWNhdGVkIG1ldGhvZC4KICAgICAqCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2FsbGluZ01ldGhvZCBUaGUgbmFtZSBvZiB0aGUgbWV0aG9kIGJlaW5nIGRlcHJlY2F0ZWQKICAgICAqIEBwYXJhbSB7c3RyaW5nfSB2ZXJzaW9uIFRoZSB2ZXJzaW9uIHdoZW4gdGhlIHRhZ2dlZCBtZXRob2QgYmVjYW1lIG9ic29sZXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZz99IG1lc3NhZ2UgT3B0aW9uYWwgbWVzc2FnZSB0byBiZSBzaG93biB3aXRoIHRoZSB3YXJuaW5nCiAgICAgKi8KICAgIGZ1bmN0aW9uIGRlcHJlY2F0ZWQoY2FsbGluZ01ldGhvZCwgdmVyc2lvbiwgbWVzc2FnZSkgewogICAgICAgIGlmIChtZXNzYWdlID09PSB2b2lkIDApIHsgbWVzc2FnZSA9ICIiOyB9CiAgICAgICAgd2FybigiTWV0aG9kICIgKyBjYWxsaW5nTWV0aG9kICsgIiBoYXMgYmVlbiBkZXByZWNhdGVkIGluIHZlcnNpb24gIiArIHZlcnNpb24gKwogICAgICAgICAgICAiLiBQbGVhc2UgcmVmZXIgdG8gdGhlIHJlbGVhc2Ugbm90ZXMuICIgKyBtZXNzYWdlKTsKICAgIH0KICAgIGV4cG9ydHMuZGVwcmVjYXRlZCA9IGRlcHJlY2F0ZWQ7CiAgICB9KTsKCiAgICB2YXIgYnVja2V0ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNy1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICAvKioKICAgICAqIFRoaXMgY2xhc3Mga2VlcHMgdHJhY2sgb2YgYnVja2V0aW5nIHN0YXRlIHdoaWxlIGNvbGxhcHNpbmcgZGVuc2UgbGluZQogICAgICogZ2VvbWV0cnkgaW4gYSBsaW5lIGFuZCBhcmVhIHBsb3RzLgogICAgICovCiAgICB2YXIgQnVja2V0ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIEJ1Y2tldChpbmRleCwgeFZhbHVlLCB5VmFsdWUpIHsKICAgICAgICAgICAgdGhpcy5lbnRyeUluZGV4ID0gaW5kZXg7CiAgICAgICAgICAgIHRoaXMuZXhpdEluZGV4ID0gaW5kZXg7CiAgICAgICAgICAgIHRoaXMubWluSW5kZXggPSBpbmRleDsKICAgICAgICAgICAgdGhpcy5tYXhJbmRleCA9IGluZGV4OwogICAgICAgICAgICB0aGlzLmJ1Y2tldFZhbHVlID0geFZhbHVlOwogICAgICAgICAgICB0aGlzLm1pblZhbHVlID0geVZhbHVlOwogICAgICAgICAgICB0aGlzLm1heFZhbHVlID0geVZhbHVlOwogICAgICAgIH0KICAgICAgICBCdWNrZXQucHJvdG90eXBlLmlzSW5CdWNrZXQgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHZhbHVlID09IHRoaXMuYnVja2V0VmFsdWU7CiAgICAgICAgfTsKICAgICAgICBCdWNrZXQucHJvdG90eXBlLmFkZFRvQnVja2V0ID0gZnVuY3Rpb24gKHZhbHVlLCBpbmRleCkgewogICAgICAgICAgICBpZiAodmFsdWUgPCB0aGlzLm1pblZhbHVlKSB7CiAgICAgICAgICAgICAgICB0aGlzLm1pblZhbHVlID0gdmFsdWU7CiAgICAgICAgICAgICAgICB0aGlzLm1pbkluZGV4ID0gaW5kZXg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHZhbHVlID4gdGhpcy5tYXhWYWx1ZSkgewogICAgICAgICAgICAgICAgdGhpcy5tYXhWYWx1ZSA9IHZhbHVlOwogICAgICAgICAgICAgICAgdGhpcy5tYXhJbmRleCA9IGluZGV4OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuZXhpdEluZGV4ID0gaW5kZXg7CiAgICAgICAgfTsKICAgICAgICBCdWNrZXQucHJvdG90eXBlLmdldFVuaXF1ZUluZGljZXMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBpZHhzID0gW3RoaXMuZW50cnlJbmRleCwgdGhpcy5tYXhJbmRleCwgdGhpcy5taW5JbmRleCwgdGhpcy5leGl0SW5kZXhdOwogICAgICAgICAgICByZXR1cm4gaWR4cy5maWx0ZXIoZnVuY3Rpb24gKGlkeCwgaSkgeyByZXR1cm4gaSA9PSAwIHx8IGlkeCAhPSBpZHhzW2kgLSAxXTsgfSk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQnVja2V0OwogICAgfSgpKTsKICAgIGV4cG9ydHMuQnVja2V0ID0gQnVja2V0OwogICAgfSk7CgogICAgdmFyIHNldCRnID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICAvKioKICAgICAqIFNoaW0gZm9yIEVTNiBzZXQuCiAgICAgKiBodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9TZXQKICAgICAqLwogICAgdmFyIFNldCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBTZXQoKSB7CiAgICAgICAgICAgIGlmICh0eXBlb2Ygd2luZG93LlNldCA9PT0gImZ1bmN0aW9uIikgewogICAgICAgICAgICAgICAgdGhpcy5fZXM2U2V0ID0gbmV3IHdpbmRvdy5TZXQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3ZhbHVlcyA9IFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuc2l6ZSA9IDA7CiAgICAgICAgfQogICAgICAgIFNldC5wcm90b3R5cGUuYWRkID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZTZXQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fZXM2U2V0LmFkZCh2YWx1ZSk7CiAgICAgICAgICAgICAgICB0aGlzLnNpemUgPSB0aGlzLl9lczZTZXQuc2l6ZTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghdGhpcy5oYXModmFsdWUpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl92YWx1ZXMucHVzaCh2YWx1ZSk7CiAgICAgICAgICAgICAgICB0aGlzLnNpemUgPSB0aGlzLl92YWx1ZXMubGVuZ3RoOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU2V0LnByb3RvdHlwZS5kZWxldGUgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2VzNlNldCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgZGVsZXRlZCA9IHRoaXMuX2VzNlNldC5kZWxldGUodmFsdWUpOwogICAgICAgICAgICAgICAgdGhpcy5zaXplID0gdGhpcy5fZXM2U2V0LnNpemU7CiAgICAgICAgICAgICAgICByZXR1cm4gZGVsZXRlZDsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgaW5kZXggPSB0aGlzLl92YWx1ZXMuaW5kZXhPZih2YWx1ZSk7CiAgICAgICAgICAgIGlmIChpbmRleCAhPT0gLTEpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3ZhbHVlcy5zcGxpY2UoaW5kZXgsIDEpOwogICAgICAgICAgICAgICAgdGhpcy5zaXplID0gdGhpcy5fdmFsdWVzLmxlbmd0aDsKICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9OwogICAgICAgIFNldC5wcm90b3R5cGUuaGFzID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZTZXQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VzNlNldC5oYXModmFsdWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl92YWx1ZXMuaW5kZXhPZih2YWx1ZSkgIT09IC0xOwogICAgICAgIH07CiAgICAgICAgU2V0LnByb3RvdHlwZS5mb3JFYWNoID0gZnVuY3Rpb24gKGNhbGxiYWNrLCB0aGlzQXJnKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZTZXQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIGNhbGxiYWNrV3JhcHBlciA9IGZ1bmN0aW9uICh2YWx1ZSwgdmFsdWUyKSB7IHJldHVybiBjYWxsYmFjay5jYWxsKHRoaXNBcmcsIHZhbHVlLCB2YWx1ZTIsIF90aGlzKTsgfTsKICAgICAgICAgICAgICAgIHRoaXMuX2VzNlNldC5mb3JFYWNoKGNhbGxiYWNrV3JhcHBlciwgdGhpc0FyZyk7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdmFsdWVzLmZvckVhY2goZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgICAgICBjYWxsYmFjay5jYWxsKHRoaXNBcmcsIHZhbHVlLCB2YWx1ZSwgX3RoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBTZXQ7CiAgICB9KCkpOwogICAgZXhwb3J0cy5TZXQgPSBTZXQ7CiAgICB9KTsKCiAgICB2YXIgY2FsbGJhY2tTZXQgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgLyoqCiAgICAgKiBBIHNldCBvZiBjYWxsYmFja3Mgd2hpY2ggY2FuIGJlIGFsbCBpbnZva2VkIGF0IG9uY2UuCiAgICAgKiBFYWNoIGNhbGxiYWNrIGV4aXN0cyBhdCBtb3N0IG9uY2UgaW4gdGhlIHNldCAoYmFzZWQgb24gcmVmZXJlbmNlIGVxdWFsaXR5KS4KICAgICAqIEFsbCBjYWxsYmFja3Mgc2hvdWxkIGhhdmUgdGhlIHNhbWUgc2lnbmF0dXJlLgogICAgICovCiAgICB2YXIgQ2FsbGJhY2tTZXQgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhDYWxsYmFja1NldCwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBDYWxsYmFja1NldCgpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlciAhPT0gbnVsbCAmJiBfc3VwZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSB8fCB0aGlzOwogICAgICAgIH0KICAgICAgICBDYWxsYmFja1NldC5wcm90b3R5cGUuY2FsbENhbGxiYWNrcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBbXTsKICAgICAgICAgICAgZm9yICh2YXIgX2kgPSAwOyBfaSA8IGFyZ3VtZW50cy5sZW5ndGg7IF9pKyspIHsKICAgICAgICAgICAgICAgIGFyZ3NbX2ldID0gYXJndW1lbnRzW19pXTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLmZvckVhY2goZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgICAgICBjYWxsYmFjay5hcHBseShfdGhpcywgYXJncyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIHJldHVybiBDYWxsYmFja1NldDsKICAgIH0oc2V0JGcuU2V0KSk7CiAgICBleHBvcnRzLkNhbGxiYWNrU2V0ID0gQ2FsbGJhY2tTZXQ7CiAgICB9KTsKCiAgICB2YXIgZW50aXR5U3RvcmUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvKioKICAgICAqIEltcGxlbWVudGF0aW9uIG9mIHtJRW50aXR5U3RvcmV9IHRoYXQgdXNlcyBhbiBhcnJheSBmb3IgZWFzeSBpdGVyYXRpb24gYXMKICAgICAqIHdlbGwgYXMgYSBxdWFkIHRyZWUgZm9yIGZhc3QgbmVhcmVzdC1wb2ludCBxdWVyaWVzLgogICAgICoKICAgICAqIE5vdGUgdGhhdCBpZiB0aGUgcG9zaXRpb24gb2YgeW91ciBlbnRpdGllcyBjaGFuZ2VzLCB5b3UgTVVTVCByZWJ1aWxkIHRoZQogICAgICogZW50aXR5IHN0b3JlIGZvciB0aGUgYGVudGl0eU5lYXJlc3RgIG1ldGhvZCB0byB3b3JrIHNpbmNlIHRoZSBxdWFkdHJlZSBkb2VzCiAgICAgKiBub3Qga25vdyB0aGF0IGl0cyBub2RlcyBoYXZlIG1vdmVkLgogICAgICovCiAgICB2YXIgRW50aXR5U3RvcmUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gRW50aXR5U3RvcmUoKSB7CiAgICAgICAgICAgIHRoaXMuX2VudGl0aWVzID0gW107CiAgICAgICAgICAgIHRoaXMuX3J0cmVlID0gbmV3IHJUcmVlLlJUcmVlKCk7CiAgICAgICAgfQogICAgICAgIEVudGl0eVN0b3JlLnByb3RvdHlwZS5hZGRBbGwgPSBmdW5jdGlvbiAoZW50aXRpZXMsIGVudGl0eUJvdW5kc0ZhY3RvcnksIGJvdW5kcykgewogICAgICAgICAgICB0aGlzLl9lbnRpdGllcyA9IHRoaXMuX2VudGl0aWVzLmNvbmNhdChlbnRpdGllcyk7CiAgICAgICAgICAgIC8vIGZpbHRlciBvdXQgb2YgYm91bmRzIGVudGl0aWVzIGlmIGJvdW5kcyBpcyBkZWZpbmVkCiAgICAgICAgICAgIGlmIChib3VuZHMgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgdmFyIGZpbHRlckJvdW5kcyA9IHJUcmVlLlJUcmVlQm91bmRzLmJvdW5kcyhib3VuZHMpOwogICAgICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBlbnRpdGllcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgICAgIHZhciBlbnRpdHkgPSBlbnRpdGllc1tpXTsKICAgICAgICAgICAgICAgICAgICB2YXIgZW50aXR5Qm91bmRzID0gclRyZWUuUlRyZWVCb3VuZHMuZW50aXR5Qm91bmRzKGVudGl0eUJvdW5kc0ZhY3RvcnkoZW50aXR5KSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHJUcmVlLlJUcmVlQm91bmRzLmlzQm91bmRzT3ZlcmxhcEJvdW5kcyhmaWx0ZXJCb3VuZHMsIGVudGl0eUJvdW5kcykpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fcnRyZWUuaW5zZXJ0KGVudGl0eUJvdW5kcywgZW50aXR5KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGVudGl0aWVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGVudGl0eSA9IGVudGl0aWVzW2ldOwogICAgICAgICAgICAgICAgICAgIHZhciBlbnRpdHlCb3VuZHMgPSByVHJlZS5SVHJlZUJvdW5kcy5lbnRpdHlCb3VuZHMoZW50aXR5Qm91bmRzRmFjdG9yeShlbnRpdHkpKTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9ydHJlZS5pbnNlcnQoZW50aXR5Qm91bmRzLCBlbnRpdHkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBFbnRpdHlTdG9yZS5wcm90b3R5cGUuZW50aXR5TmVhcmVzdCA9IGZ1bmN0aW9uIChxdWVyeVBvaW50KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9ydHJlZS5sb2NhdGVOZWFyZXN0KHF1ZXJ5UG9pbnQpLnBvcCgpOwogICAgICAgIH07CiAgICAgICAgRW50aXR5U3RvcmUucHJvdG90eXBlLmVudGl0eU5lYXJlc3RYID0gZnVuY3Rpb24gKHF1ZXJ5UG9pbnQpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3J0cmVlLmxvY2F0ZU5lYXJlc3RYKHF1ZXJ5UG9pbnQpLnBvcCgpOwogICAgICAgIH07CiAgICAgICAgRW50aXR5U3RvcmUucHJvdG90eXBlLmVudGl0eU5lYXJlc3RZID0gZnVuY3Rpb24gKHF1ZXJ5UG9pbnQpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3J0cmVlLmxvY2F0ZU5lYXJlc3RZKHF1ZXJ5UG9pbnQpLnBvcCgpOwogICAgICAgIH07CiAgICAgICAgRW50aXR5U3RvcmUucHJvdG90eXBlLmVudGl0aWVzSW5Cb3VuZHMgPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9ydHJlZS5pbnRlcnNlY3QoclRyZWUuUlRyZWVCb3VuZHMuZW50aXR5Qm91bmRzKGJvdW5kcykpOwogICAgICAgIH07CiAgICAgICAgRW50aXR5U3RvcmUucHJvdG90eXBlLmVudGl0aWVzSW5YQm91bmRzID0gZnVuY3Rpb24gKGJvdW5kcykgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fcnRyZWUuaW50ZXJzZWN0WChyVHJlZS5SVHJlZUJvdW5kcy5lbnRpdHlCb3VuZHMoYm91bmRzKSk7CiAgICAgICAgfTsKICAgICAgICBFbnRpdHlTdG9yZS5wcm90b3R5cGUuZW50aXRpZXNJbllCb3VuZHMgPSBmdW5jdGlvbiAoYm91bmRzKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9ydHJlZS5pbnRlcnNlY3RZKHJUcmVlLlJUcmVlQm91bmRzLmVudGl0eUJvdW5kcyhib3VuZHMpKTsKICAgICAgICB9OwogICAgICAgIEVudGl0eVN0b3JlLnByb3RvdHlwZS5lbnRpdGllcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VudGl0aWVzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEVudGl0eVN0b3JlOwogICAgfSgpKTsKICAgIGV4cG9ydHMuRW50aXR5U3RvcmUgPSBFbnRpdHlTdG9yZTsKICAgIH0pOwoKICAgIHZhciBtYXAkYSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIC8qKgogICAgICogU2hpbSBmb3IgRVM2IG1hcC4KICAgICAqIGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0phdmFTY3JpcHQvUmVmZXJlbmNlL0dsb2JhbF9PYmplY3RzL01hcAogICAgICovCiAgICB2YXIgTWFwID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIE1hcCgpIHsKICAgICAgICAgICAgaWYgKHR5cGVvZiB3aW5kb3cuTWFwID09PSAiZnVuY3Rpb24iKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9lczZNYXAgPSBuZXcgd2luZG93Lk1hcCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fa2V5VmFsdWVQYWlycyA9IFtdOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIE1hcC5wcm90b3R5cGUuc2V0ID0gZnVuY3Rpb24gKGtleSwgdmFsdWUpIHsKICAgICAgICAgICAgaWYgKG1hdGhVdGlscy5pc05hTihrZXkpKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIk5hTiBtYXkgbm90IGJlIHVzZWQgYXMgYSBrZXkgdG8gdGhlIE1hcCIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZNYXAgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fZXM2TWFwLnNldChrZXksIHZhbHVlKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGhpcy5fa2V5VmFsdWVQYWlycy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2tleVZhbHVlUGFpcnNbaV0ua2V5ID09PSBrZXkpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9rZXlWYWx1ZVBhaXJzW2ldLnZhbHVlID0gdmFsdWU7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fa2V5VmFsdWVQYWlycy5wdXNoKHsga2V5OiBrZXksIHZhbHVlOiB2YWx1ZSB9KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBNYXAucHJvdG90eXBlLmdldCA9IGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2VzNk1hcCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZXM2TWFwLmdldChrZXkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGhpcy5fa2V5VmFsdWVQYWlycy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2tleVZhbHVlUGFpcnNbaV0ua2V5ID09PSBrZXkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fa2V5VmFsdWVQYWlyc1tpXS52YWx1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgICAgIH07CiAgICAgICAgTWFwLnByb3RvdHlwZS5oYXMgPSBmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZNYXAgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VzNk1hcC5oYXMoa2V5KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHRoaXMuX2tleVZhbHVlUGFpcnMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9rZXlWYWx1ZVBhaXJzW2ldLmtleSA9PT0ga2V5KSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH07CiAgICAgICAgTWFwLnByb3RvdHlwZS5mb3JFYWNoID0gZnVuY3Rpb24gKGNhbGxiYWNrRm4sIHRoaXNBcmcpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKHRoaXMuX2VzNk1hcCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgY2FsbGJhY2tXcmFwcGVyID0gZnVuY3Rpb24gKHZhbHVlLCBrZXkpIHsgcmV0dXJuIGNhbGxiYWNrRm4uY2FsbCh0aGlzQXJnLCB2YWx1ZSwga2V5LCBfdGhpcyk7IH07CiAgICAgICAgICAgICAgICB0aGlzLl9lczZNYXAuZm9yRWFjaChjYWxsYmFja1dyYXBwZXIsIHRoaXNBcmcpOwogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2tleVZhbHVlUGFpcnMuZm9yRWFjaChmdW5jdGlvbiAoa2V5VmFsdWVQYWlyKSB7CiAgICAgICAgICAgICAgICBjYWxsYmFja0ZuLmNhbGwodGhpc0FyZywga2V5VmFsdWVQYWlyLnZhbHVlLCBrZXlWYWx1ZVBhaXIua2V5LCBfdGhpcyk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgTWFwLnByb3RvdHlwZS5kZWxldGUgPSBmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9lczZNYXAgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VzNk1hcC5kZWxldGUoa2V5KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHRoaXMuX2tleVZhbHVlUGFpcnMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9rZXlWYWx1ZVBhaXJzW2ldLmtleSA9PT0ga2V5KSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fa2V5VmFsdWVQYWlycy5zcGxpY2UoaSwgMSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIE1hcDsKICAgIH0oKSk7CiAgICBleHBvcnRzLk1hcCA9IE1hcDsKICAgIH0pOwoKICAgIHZhciBvYmplY3RVdGlscyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgLyoqCiAgICAgKiBQb2x5ZmlsbCBmb3IgT2JqZWN0LmFzc2lnbgogICAgICovCiAgICBmdW5jdGlvbiBhc3NpZ24oKSB7CiAgICAgICAgdmFyIG9ianMgPSBbXTsKICAgICAgICBmb3IgKHZhciBfaSA9IDA7IF9pIDwgYXJndW1lbnRzLmxlbmd0aDsgX2krKykgewogICAgICAgICAgICBvYmpzW19pXSA9IGFyZ3VtZW50c1tfaV07CiAgICAgICAgfQogICAgICAgIHZhciByZXN1bHQgPSB7fTsKICAgICAgICBmb3IgKHZhciBfYSA9IDAsIG9ianNfMSA9IG9ianM7IF9hIDwgb2Jqc18xLmxlbmd0aDsgX2ErKykgewogICAgICAgICAgICB2YXIgb2JqID0gb2Jqc18xW19hXTsKICAgICAgICAgICAgdmFyIGtleXMgPSBPYmplY3Qua2V5cyhvYmopOwogICAgICAgICAgICBmb3IgKHZhciBfYiA9IDAsIGtleXNfMSA9IGtleXM7IF9iIDwga2V5c18xLmxlbmd0aDsgX2IrKykgewogICAgICAgICAgICAgICAgdmFyIGtleSA9IGtleXNfMVtfYl07CiAgICAgICAgICAgICAgICByZXN1bHRba2V5XSA9IG9ialtrZXldOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICBleHBvcnRzLmFzc2lnbiA9IGFzc2lnbjsKICAgIH0pOwoKICAgIHZhciB0cmFuc2Zvcm1Bd2FyZVRyYW5zbGF0b3IgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgX1RSQU5TTEFUT1JfS0VZID0gIl9fUGxvdHRhYmxlX0NsaWVudFRyYW5zbGF0b3IiOwogICAgLyoqCiAgICAgKiBSZXR1cm5zIGEgc2luZ2xldG9uLWl6ZWQgYFRyYW5zbGF0b3JgIGluc3RhbmNlIGFzc29jaWF0ZWQgd2l0aCB0aGUgY29tcG9uZW50LgogICAgICovCiAgICBmdW5jdGlvbiBnZXRUcmFuc2xhdG9yKGNvbXBvbmVudCkgewogICAgICAgIHZhciByb290RWxlbWVudCA9IGNvbXBvbmVudC5yb290KCkucm9vdEVsZW1lbnQoKS5ub2RlKCk7CiAgICAgICAgdmFyIHRyYW5zbGF0b3IgPSByb290RWxlbWVudFtfVFJBTlNMQVRPUl9LRVldOwogICAgICAgIGlmICh0cmFuc2xhdG9yID09IG51bGwpIHsKICAgICAgICAgICAgdHJhbnNsYXRvciA9IG5ldyBUcmFuc2xhdG9yKHJvb3RFbGVtZW50KTsKICAgICAgICAgICAgcm9vdEVsZW1lbnRbX1RSQU5TTEFUT1JfS0VZXSA9IHRyYW5zbGF0b3I7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0cmFuc2xhdG9yOwogICAgfQogICAgZXhwb3J0cy5nZXRUcmFuc2xhdG9yID0gZ2V0VHJhbnNsYXRvcjsKICAgIC8qKgogICAgICogVGhlIHRyYW5zbGF0b3IgaW1wbGVtZW50cyBDU1MgdHJhbnNmb3JtIGF3YXJlIHBvc2l0aW9uIG1lYXN1cmluZy4gV2UgbWFudWFsbHkKICAgICAqIGNvbXB1dGUgYSBjdW11bGF0aXZlIENTUzMgb2YgdGhlIHJvb3QgZWxlbWVudCBhbmNlc3RvcnMgdXAgdG8gYDxib2R5PmAuCiAgICAgKi8KICAgIHZhciBUcmFuc2xhdG9yID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFRyYW5zbGF0b3IoX3Jvb3RFbGVtZW50KSB7CiAgICAgICAgICAgIHRoaXMuX3Jvb3RFbGVtZW50ID0gX3Jvb3RFbGVtZW50OwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHaXZlbiBgZG9jdW1lbnRgIGNsaWVudCBjb29yZGluYXRlcywgY29tcHV0ZXMgdGhlIHBvc2l0aW9uIHJlbGF0aXZlIHRvIHRoZQogICAgICAgICAqIGBDb21wb25lbnRgJ3Mgcm9vdCBlbGVtZW50LCB0YWtpbmcgaW50byBhY2NvdW50IHRoZSBjdW11bGF0aXZlIENTUzMKICAgICAgICAgKiB0cmFuc2Zvcm1zIG9mIHRoZSByb290IGVsZW1lbnQgYW5jZXN0b3JzIHVwIHRvIGA8Ym9keT5gLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyB0cmlnZ2VycyBhIGxheW91dCBidXQgZG9lc24ndCBmdXJ0aGVyIG1vZGlmeSB0aGUgRE9NLCBzbyBjYXVzZXMgYQogICAgICAgICAqIG1heGltdW0gb2Ygb25lIGxheW91dCBwZXIgZnJhbWUuCiAgICAgICAgICoKICAgICAgICAgKiBEb2VzIG5vdCBzdXBwb3J0IGB0cmFuc2Zvcm0tb3JpZ2luYCBDU1MgcHJvcGVydHkgb3RoZXIgdGhhbiB0aGUgZGVmYXVsdC4KICAgICAgICAgKi8KICAgICAgICBUcmFuc2xhdG9yLnByb3RvdHlwZS5jb21wdXRlUG9zaXRpb24gPSBmdW5jdGlvbiAoY2xpZW50WCwgY2xpZW50WSkgewogICAgICAgICAgICB2YXIgY2xpZW50UG9zaXRpb24gPSB7CiAgICAgICAgICAgICAgICB4OiBjbGllbnRYLAogICAgICAgICAgICAgICAgeTogY2xpZW50WSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIHRyYW5zZm9ybSA9IHV0aWxzJDEuTWF0aC5nZXRDdW11bGF0aXZlVHJhbnNmb3JtKHRoaXMuX3Jvb3RFbGVtZW50KTsKICAgICAgICAgICAgaWYgKHRyYW5zZm9ybSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY2xpZW50UG9zaXRpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRyYW5zZm9ybWVkID0gdXRpbHMkMS5NYXRoLmFwcGx5VHJhbnNmb3JtKHRyYW5zZm9ybSwgY2xpZW50UG9zaXRpb24pOwogICAgICAgICAgICByZXR1cm4gdHJhbnNmb3JtZWQ7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBJcyB0aGUgZXZlbnQncyB0YXJnZXQgcGFydCBvZiB0aGUgZ2l2ZW4gY29tcG9uZW50J3MgRE9NIHRyZWU/CiAgICAgICAgICovCiAgICAgICAgVHJhbnNsYXRvci5pc0V2ZW50SW5zaWRlID0gZnVuY3Rpb24gKGNvbXBvbmVudCwgZSkgewogICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5ET00uY29udGFpbnMoY29tcG9uZW50LnJvb3QoKS5yb290RWxlbWVudCgpLm5vZGUoKSwgZS50YXJnZXQpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFRyYW5zbGF0b3I7CiAgICB9KCkpOwogICAgZXhwb3J0cy5UcmFuc2xhdG9yID0gVHJhbnNsYXRvcjsKICAgIH0pOwoKICAgIHZhciB1dGlscyQxID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKICAgIGV4cG9ydHMuQXJyYXkgPSBhcnJheVV0aWxzOwoKICAgIGV4cG9ydHMuQ29sb3IgPSBjb2xvclV0aWxzOwoKICAgIGV4cG9ydHMuRE9NID0gZG9tVXRpbHM7CgogICAgZXhwb3J0cy5NYXRoID0gbWF0aFV0aWxzOwoKICAgIGV4cG9ydHMuUlRyZWUgPSByVHJlZTsKCiAgICBleHBvcnRzLlN0YWNraW5nID0gc3RhY2tpbmdVdGlsczsKCiAgICBleHBvcnRzLldpbmRvdyA9IHdpbmRvd1V0aWxzOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihidWNrZXQsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihjYWxsYmFja1NldCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGNvZXJjZUQzLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZW50aXR5U3RvcmUsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihtYXAkYSwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKG9iamVjdFV0aWxzLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoc2V0JGcsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3Rhcih0cmFuc2Zvcm1Bd2FyZVRyYW5zbGF0b3IsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIHJlbmRlclBvbGljeSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCiAgICAvKioKICAgICAqIFJlbmRlcnMgQ29tcG9uZW50cyBpbW1lZGlhdGVseSBhZnRlciB0aGV5IGFyZSBlbnF1ZXVlZC4KICAgICAqIFVzZWZ1bCBmb3IgZGVidWdnaW5nLCBob3JyaWJsZSBmb3IgcGVyZm9ybWFuY2UuCiAgICAgKi8KICAgIHZhciBJbW1lZGlhdGUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gSW1tZWRpYXRlKCkgewogICAgICAgIH0KICAgICAgICBJbW1lZGlhdGUucHJvdG90eXBlLnJlbmRlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmVuZGVyQ29udHJvbGxlci5mbHVzaCgpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEltbWVkaWF0ZTsKICAgIH0oKSk7CiAgICBleHBvcnRzLkltbWVkaWF0ZSA9IEltbWVkaWF0ZTsKICAgIC8qKgogICAgICogVGhlIGRlZmF1bHQgd2F5IHRvIHJlbmRlciwgd2hpY2ggb25seSB0cmllcyB0byByZW5kZXIgZXZlcnkgZnJhbWUKICAgICAqICh1c3VhbGx5LCAxLzYwdGggb2YgYSBzZWNvbmQpLgogICAgICovCiAgICB2YXIgQW5pbWF0aW9uRnJhbWUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gQW5pbWF0aW9uRnJhbWUoKSB7CiAgICAgICAgfQogICAgICAgIEFuaW1hdGlvbkZyYW1lLnByb3RvdHlwZS5yZW5kZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHV0aWxzJDEuRE9NLnJlcXVlc3RBbmltYXRpb25GcmFtZVBvbHlmaWxsKHJlbmRlckNvbnRyb2xsZXIuZmx1c2gpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEFuaW1hdGlvbkZyYW1lOwogICAgfSgpKTsKICAgIGV4cG9ydHMuQW5pbWF0aW9uRnJhbWUgPSBBbmltYXRpb25GcmFtZTsKICAgIC8qKgogICAgICogUmVuZGVycyB3aXRoIGBzZXRUaW1lb3V0KClgLgogICAgICogR2VuZXJhbGx5IGFuIGluZmVyaW9yIHdheSB0byByZW5kZXIgY29tcGFyZWQgdG8gYHJlcXVlc3RBbmltYXRpb25GcmFtZWAsCiAgICAgKiBidXQgdXNlZnVsIGZvciBicm93c2VycyB0aGF0IGRvbid0IHN1cHBvb3J0IGByZXF1ZXN0QW5pbWF0aW9uRnJhbWVgLgogICAgICovCiAgICB2YXIgVGltZW91dCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBUaW1lb3V0KCkgewogICAgICAgICAgICB0aGlzLl90aW1lb3V0TXNlYyA9IHV0aWxzJDEuRE9NLlNDUkVFTl9SRUZSRVNIX1JBVEVfTUlMTElTRUNPTkRTOwogICAgICAgIH0KICAgICAgICBUaW1lb3V0LnByb3RvdHlwZS5yZW5kZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHNldFRpbWVvdXQocmVuZGVyQ29udHJvbGxlci5mbHVzaCwgdGhpcy5fdGltZW91dE1zZWMpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFRpbWVvdXQ7CiAgICB9KCkpOwogICAgZXhwb3J0cy5UaW1lb3V0ID0gVGltZW91dDsKICAgIH0pOwoKICAgIHZhciByZW5kZXJDb250cm9sbGVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICAvKioKICAgICAqIFRoZSBSZW5kZXJDb250cm9sbGVyIGlzIHJlc3BvbnNpYmxlIGZvciBlbnF1ZXVlaW5nIGFuZCBzeW5jaHJvbml6aW5nCiAgICAgKiBsYXlvdXQgYW5kIHJlbmRlciBjYWxscyBmb3IgQ29tcG9uZW50cy4KICAgICAqCiAgICAgKiBMYXlvdXQgYW5kIHJlbmRlciBjYWxscyBvY2N1ciBpbnNpZGUgYW4gYW5pbWF0aW9uIGNhbGxiYWNrCiAgICAgKiAod2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSBpZiBhdmFpbGFibGUpLgogICAgICoKICAgICAqIFJlbmRlckNvbnRyb2xsZXIuZmx1c2goKSBpbW1lZGlhdGVseSBsYXlzIG91dCBhbmQgcmVuZGVycyBhbGwgQ29tcG9uZW50cyBjdXJyZW50bHkgZW5xdWV1ZWQuCiAgICAgKgogICAgICogVG8gYWx3YXlzIGhhdmUgaW1tZWRpYXRlIHJlbmRlcmluZyAodXNlZnVsIGZvciBkZWJ1Z2dpbmcpLCBjYWxsCiAgICAgKiBgYGB0eXBlc2NyaXB0CiAgICAgKiBQbG90dGFibGUuUmVuZGVyQ29udHJvbGxlci5zZXRSZW5kZXJQb2xpY3koCiAgICAgKiAgIG5ldyBQbG90dGFibGUuUmVuZGVyUG9saWNpZXMuSW1tZWRpYXRlKCkKICAgICAqICk7CiAgICAgKiBgYGAKICAgICAqLwogICAgdmFyIF9jb21wb25lbnRzTmVlZGluZ1JlbmRlciA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgdmFyIF9jb21wb25lbnRzTmVlZGluZ0NvbXB1dGVMYXlvdXQgPSBuZXcgdXRpbHMkMS5TZXQoKTsKICAgIHZhciBfYW5pbWF0aW9uUmVxdWVzdGVkID0gZmFsc2U7CiAgICB2YXIgX2lzQ3VycmVudGx5Rmx1c2hpbmcgPSBmYWxzZTsKICAgIGV4cG9ydHMuUG9saWN5ID0gbWFrZUVudW1fMS5tYWtlRW51bShbImltbWVkaWF0ZSIsICJhbmltYXRpb25GcmFtZSIsICJ0aW1lb3V0Il0pOwogICAgdmFyIF9yZW5kZXJQb2xpY3kgPSBuZXcgcmVuZGVyUG9saWN5LkFuaW1hdGlvbkZyYW1lKCk7CiAgICBmdW5jdGlvbiByZW5kZXJQb2xpY3kkMShyZW5kZXJQb2xpY3kkMSkgewogICAgICAgIGlmIChyZW5kZXJQb2xpY3kkMSA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiBfcmVuZGVyUG9saWN5OwogICAgICAgIH0KICAgICAgICBzd2l0Y2ggKHJlbmRlclBvbGljeSQxKSB7CiAgICAgICAgICAgIGNhc2UgZXhwb3J0cy5Qb2xpY3kuaW1tZWRpYXRlOgogICAgICAgICAgICAgICAgX3JlbmRlclBvbGljeSA9IG5ldyByZW5kZXJQb2xpY3kuSW1tZWRpYXRlKCk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBleHBvcnRzLlBvbGljeS5hbmltYXRpb25GcmFtZToKICAgICAgICAgICAgICAgIF9yZW5kZXJQb2xpY3kgPSBuZXcgcmVuZGVyUG9saWN5LkFuaW1hdGlvbkZyYW1lKCk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgY2FzZSBleHBvcnRzLlBvbGljeS50aW1lb3V0OgogICAgICAgICAgICAgICAgX3JlbmRlclBvbGljeSA9IG5ldyByZW5kZXJQb2xpY3kuVGltZW91dCgpOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICB1dGlscyQxLldpbmRvdy53YXJuKCJVbnJlY29nbml6ZWQgcmVuZGVyUG9saWN5OiAiICsgcmVuZGVyUG9saWN5JDEpOwogICAgICAgIH0KICAgIH0KICAgIGV4cG9ydHMucmVuZGVyUG9saWN5ID0gcmVuZGVyUG9saWN5JDE7CiAgICAvKioKICAgICAqIEVucXVldWVzIHRoZSBDb21wb25lbnQgZm9yIHJlbmRlcmluZy4KICAgICAqCiAgICAgKiBAcGFyYW0ge0NvbXBvbmVudH0gY29tcG9uZW50CiAgICAgKi8KICAgIGZ1bmN0aW9uIHJlZ2lzdGVyVG9SZW5kZXIoY29tcG9uZW50KSB7CiAgICAgICAgaWYgKF9pc0N1cnJlbnRseUZsdXNoaW5nKSB7CiAgICAgICAgICAgIHV0aWxzJDEuV2luZG93Lndhcm4oIlJlZ2lzdGVyZWQgdG8gcmVuZGVyIHdoaWxlIG90aGVyIGNvbXBvbmVudHMgYXJlIGZsdXNoaW5nOiByZXF1ZXN0IG1heSBiZSBpZ25vcmVkIik7CiAgICAgICAgfQogICAgICAgIF9jb21wb25lbnRzTmVlZGluZ1JlbmRlci5hZGQoY29tcG9uZW50KTsKICAgICAgICByZXF1ZXN0UmVuZGVyKCk7CiAgICB9CiAgICBleHBvcnRzLnJlZ2lzdGVyVG9SZW5kZXIgPSByZWdpc3RlclRvUmVuZGVyOwogICAgLyoqCiAgICAgKiBFbnF1ZXVlcyB0aGUgQ29tcG9uZW50IGZvciBsYXlvdXQgYW5kIHJlbmRlcmluZy4KICAgICAqCiAgICAgKiBAcGFyYW0ge0NvbXBvbmVudH0gY29tcG9uZW50CiAgICAgKi8KICAgIGZ1bmN0aW9uIHJlZ2lzdGVyVG9Db21wdXRlTGF5b3V0QW5kUmVuZGVyKGNvbXBvbmVudCkgewogICAgICAgIF9jb21wb25lbnRzTmVlZGluZ0NvbXB1dGVMYXlvdXQuYWRkKGNvbXBvbmVudCk7CiAgICAgICAgX2NvbXBvbmVudHNOZWVkaW5nUmVuZGVyLmFkZChjb21wb25lbnQpOwogICAgICAgIHJlcXVlc3RSZW5kZXIoKTsKICAgIH0KICAgIGV4cG9ydHMucmVnaXN0ZXJUb0NvbXB1dGVMYXlvdXRBbmRSZW5kZXIgPSByZWdpc3RlclRvQ29tcHV0ZUxheW91dEFuZFJlbmRlcjsKICAgIC8qKgogICAgICogRW5xdWV1ZXMgdGhlIENvbXBvbmVudCBmb3IgbGF5b3V0IGFuZCByZW5kZXJpbmcuCiAgICAgKgogICAgICogQHBhcmFtIHtDb21wb25lbnR9IGNvbXBvbmVudAogICAgICogQGRlcHJlY2F0ZWQgVGhpcyBtZXRob2QgaGFzIGJlZW4gcmVuYW1lZCB0byBgUmVuZGVyQ29udHJvbGxlci5yZWdpc3RlclRvQ29tcHV0ZUxheW91dEFuZFJlbmRlcigpYC4KICAgICAqLwogICAgZnVuY3Rpb24gcmVnaXN0ZXJUb0NvbXB1dGVMYXlvdXQoY29tcG9uZW50KSB7CiAgICAgICAgcmVnaXN0ZXJUb0NvbXB1dGVMYXlvdXRBbmRSZW5kZXIoY29tcG9uZW50KTsKICAgIH0KICAgIGV4cG9ydHMucmVnaXN0ZXJUb0NvbXB1dGVMYXlvdXQgPSByZWdpc3RlclRvQ29tcHV0ZUxheW91dDsKICAgIGZ1bmN0aW9uIHJlcXVlc3RSZW5kZXIoKSB7CiAgICAgICAgLy8gT25seSBydW4gb3IgZW5xdWV1ZSBmbHVzaCBvbiBmaXJzdCByZXF1ZXN0LgogICAgICAgIGlmICghX2FuaW1hdGlvblJlcXVlc3RlZCkgewogICAgICAgICAgICBfYW5pbWF0aW9uUmVxdWVzdGVkID0gdHJ1ZTsKICAgICAgICAgICAgX3JlbmRlclBvbGljeS5yZW5kZXIoKTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIFJlbmRlcnMgYWxsIENvbXBvbmVudHMgd2FpdGluZyB0byBiZSByZW5kZXJlZCBpbW1lZGlhdGVseQogICAgICogaW5zdGVhZCBvZiB3YWl0aW5nIHVudGlsIHRoZSBuZXh0IGZyYW1lLiBGbHVzaCBpcyBpZGVtcG90ZW50IChnaXZlbiB0aGVyZSBhcmUgbm8gaW50ZXJtZWRpYXRlIHJlZ2lzdHJhdGlvbnMpLgogICAgICoKICAgICAqIFVzZWZ1bCB0byBjYWxsIHdoZW4gZGVidWdnaW5nLgogICAgICovCiAgICBmdW5jdGlvbiBmbHVzaCgpIHsKICAgICAgICBpZiAoX2FuaW1hdGlvblJlcXVlc3RlZCkgewogICAgICAgICAgICAvLyBMYXlvdXQKICAgICAgICAgICAgX2NvbXBvbmVudHNOZWVkaW5nQ29tcHV0ZUxheW91dC5mb3JFYWNoKGZ1bmN0aW9uIChjb21wb25lbnQpIHsgcmV0dXJuIGNvbXBvbmVudC5jb21wdXRlTGF5b3V0KCk7IH0pOwogICAgICAgICAgICAvLyBUb3AgbGV2ZWwgcmVuZGVyOyBDb250YWluZXJzIHdpbGwgcHV0IHRoZWlyIGNoaWxkcmVuIGluIHRoZSB0b1JlbmRlciBxdWV1ZQogICAgICAgICAgICBfY29tcG9uZW50c05lZWRpbmdSZW5kZXIuZm9yRWFjaChmdW5jdGlvbiAoY29tcG9uZW50KSB7IHJldHVybiBjb21wb25lbnQucmVuZGVyKCk7IH0pOwogICAgICAgICAgICBfaXNDdXJyZW50bHlGbHVzaGluZyA9IHRydWU7CiAgICAgICAgICAgIHZhciBmYWlsZWRfMSA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgICAgICAgICBfY29tcG9uZW50c05lZWRpbmdSZW5kZXIuZm9yRWFjaChmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgICAgIGNvbXBvbmVudC5yZW5kZXJJbW1lZGlhdGVseSgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY2F0Y2ggKGVycikgewogICAgICAgICAgICAgICAgICAgIC8vIHRocm93IGVycm9yIHdpdGggdGltZW91dCB0byBhdm9pZCBpbnRlcnJ1cHRpbmcgZnVydGhlciByZW5kZXJzCiAgICAgICAgICAgICAgICAgICAgd2luZG93LnNldFRpbWVvdXQoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgICAgICB0aHJvdyBlcnI7CiAgICAgICAgICAgICAgICAgICAgfSwgMCk7CiAgICAgICAgICAgICAgICAgICAgZmFpbGVkXzEuYWRkKGNvbXBvbmVudCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBfY29tcG9uZW50c05lZWRpbmdDb21wdXRlTGF5b3V0ID0gbmV3IHV0aWxzJDEuU2V0KCk7CiAgICAgICAgICAgIF9jb21wb25lbnRzTmVlZGluZ1JlbmRlciA9IGZhaWxlZF8xOwogICAgICAgICAgICBfYW5pbWF0aW9uUmVxdWVzdGVkID0gZmFsc2U7CiAgICAgICAgICAgIF9pc0N1cnJlbnRseUZsdXNoaW5nID0gZmFsc2U7CiAgICAgICAgfQogICAgfQogICAgZXhwb3J0cy5mbHVzaCA9IGZsdXNoOwogICAgfSk7CgogICAgdmFyIGNvbXBvbmVudCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgogICAgZXhwb3J0cy5YQWxpZ25tZW50ID0gbWFrZUVudW1fMS5tYWtlRW51bShbImxlZnQiLCAiY2VudGVyIiwgInJpZ2h0Il0pOwogICAgZXhwb3J0cy5ZQWxpZ25tZW50ID0gbWFrZUVudW1fMS5tYWtlRW51bShbInRvcCIsICJjZW50ZXIiLCAiYm90dG9tIl0pOwogICAgLyoqCiAgICAgKiBDb21wb25lbnRzIGFyZSB0aGUgY29yZSBsb2dpY2FsIHVuaXRzIHRoYXQgYnVpbGQgUGxvdHRhYmxlIHZpc3VhbGl6YXRpb25zLgogICAgICoKICAgICAqIFRoaXMgY2xhc3MgZGVhbHMgd2l0aCBDb21wb25lbnQgbGlmZWN5Y2xlIChhbmNob3JpbmcsIGdldHRpbmcgYSBzaXplLCBhbmQgcmVuZGVyaW5nCiAgICAgKiBpbmZyYXN0cnVjdHVyZSksIGFzIHdlbGwgYXMgYnVpbGRpbmcgdGhlIGZyYW1ld29yayBvZiBET00gZWxlbWVudHMgZm9yIGFsbCBDb21wb25lbnRzLgogICAgICovCiAgICB2YXIgQ29tcG9uZW50ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIENvbXBvbmVudCgpIHsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFN1YmNsYXNzZXMgc2hvdWxkIHNldCB0aGlzIHRvIHRydWUgaW4gdGhlaXIgY29uc3RydWN0b3IgdG8gcHJldmVudCBjb250ZW50IGZyb20gb3ZlcmZsb3dpbmcuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9vdmVyZmxvd0hpZGRlbiA9IGZhbHNlOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogT3JpZ2luIG9mIHRoaXMgQ29tcG9uZW50IHJlbGF0aXZlIHRvIGl0cyBwYXJlbnQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9vcmlnaW4gPSB7IHg6IDAsIHk6IDAgfTsKICAgICAgICAgICAgdGhpcy5feEFsaWdubWVudCA9ICJsZWZ0IjsKICAgICAgICAgICAgdGhpcy5feUFsaWdubWVudCA9ICJ0b3AiOwogICAgICAgICAgICB0aGlzLl9pc1NldHVwID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuX2lzQW5jaG9yZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fY3NzQ2xhc3NlcyA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogSWYgLmRlc3Ryb3koKSBoYXMgYmVlbiBjYWxsZWQgb24gdGhpcyBDb21wb25lbnQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9kZXN0cm95ZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fb25BbmNob3JDYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICB0aGlzLl9vbkRldGFjaENhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIHRoaXMuX2Nzc0NsYXNzZXMuYWRkKCJjb21wb25lbnQiKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQXR0YWNoZXMgdGhlIENvbXBvbmVudCBhcyBhIGNoaWxkIG9mIGEgZ2l2ZW4gZDMgU2VsZWN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtkMy5TZWxlY3Rpb259IHNlbGVjdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7Q29tcG9uZW50fSBUaGUgY2FsbGluZyBDb21wb25lbnQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5hbmNob3IgPSBmdW5jdGlvbiAoc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbiA9IGNvZXJjZUQzLmNvZXJjZUV4dGVybmFsRDMoc2VsZWN0aW9uKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2Rlc3Ryb3llZCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJDYW4ndCByZXVzZSBkZXN0cm95KCktZWQgQ29tcG9uZW50cyEiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5pc1Jvb3QoKSkgewogICAgICAgICAgICAgICAgdGhpcy5fcm9vdEVsZW1lbnQgPSBzZWxlY3Rpb247CiAgICAgICAgICAgICAgICAvLyByb290RWxlbWVudCBnZXRzIHRoZSAicGxvdHRhYmxlIiBDU1MgY2xhc3MKICAgICAgICAgICAgICAgIHRoaXMuX3Jvb3RFbGVtZW50LmNsYXNzZWQoInBsb3R0YWJsZSIsIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl9lbGVtZW50ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIC8vIHJlYXR0YWNoIGV4aXN0aW5nIGVsZW1lbnQKICAgICAgICAgICAgICAgIHNlbGVjdGlvbi5ub2RlKCkuYXBwZW5kQ2hpbGQodGhpcy5fZWxlbWVudC5ub2RlKCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZWxlbWVudCA9IHNlbGVjdGlvbi5hcHBlbmQoImRpdiIpOwogICAgICAgICAgICAgICAgdGhpcy5fc2V0dXAoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9pc0FuY2hvcmVkID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fb25BbmNob3JDYWxsYmFja3MuY2FsbENhbGxiYWNrcyh0aGlzKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIG9uIGFuY2hvcmluZyB0aGUgQ29tcG9uZW50IHRvIHRoZSBET00uCiAgICAgICAgICogSWYgdGhlIENvbXBvbmVudCBpcyBhbHJlYWR5IGFuY2hvcmVkLCB0aGUgY2FsbGJhY2sgaXMgY2FsbGVkIGltbWVkaWF0ZWx5LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDb21wb25lbnRDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtDb21wb25lbnR9CiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5vbkFuY2hvciA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICBpZiAodGhpcy5faXNBbmNob3JlZCkgewogICAgICAgICAgICAgICAgY2FsbGJhY2sodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fb25BbmNob3JDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgb24gYW5jaG9yaW5nIHRoZSBDb21wb25lbnQgdG8gdGhlIERPTS4KICAgICAgICAgKiBUaGUgY2FsbGJhY2sgaXMgaWRlbnRpZmllZCBieSByZWZlcmVuY2UgZXF1YWxpdHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0NvbXBvbmVudENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0NvbXBvbmVudH0KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLm9mZkFuY2hvciA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9vbkFuY2hvckNhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYWRkaXRpb25hbCBlbGVtZW50cyBhcyBuZWNlc3NhcnkgZm9yIHRoZSBDb21wb25lbnQgdG8gZnVuY3Rpb24uCiAgICAgICAgICogQ2FsbGVkIGR1cmluZyBhbmNob3IoKSBpZiB0aGUgQ29tcG9uZW50J3MgZWxlbWVudCBoYXMgbm90IGJlZW4gY3JlYXRlZCB5ZXQuCiAgICAgICAgICogT3ZlcnJpZGUgaW4gc3ViY2xhc3NlcyB0byBwcm92aWRlIGFkZGl0aW9uYWwgZnVuY3Rpb25hbGl0eS4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLl9zZXR1cCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzU2V0dXApIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jc3NDbGFzc2VzLmZvckVhY2goZnVuY3Rpb24gKGNzc0NsYXNzKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5fZWxlbWVudC5jbGFzc2VkKGNzc0NsYXNzLCB0cnVlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX2Nzc0NsYXNzZXMgPSBuZXcgdXRpbHMkMS5TZXQoKTsKICAgICAgICAgICAgdGhpcy5fYmFja2dyb3VuZENvbnRhaW5lciA9IHRoaXMuX2VsZW1lbnQuYXBwZW5kKCJzdmciKS5jbGFzc2VkKCJiYWNrZ3JvdW5kLWNvbnRhaW5lciIsIHRydWUpOwogICAgICAgICAgICB0aGlzLl9jb250ZW50ID0gdGhpcy5fZWxlbWVudC5hcHBlbmQoInN2ZyIpLmNsYXNzZWQoImNvbnRlbnQiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5fZm9yZWdyb3VuZENvbnRhaW5lciA9IHRoaXMuX2VsZW1lbnQuYXBwZW5kKCJzdmciKS5jbGFzc2VkKCJmb3JlZ3JvdW5kLWNvbnRhaW5lciIsIHRydWUpOwogICAgICAgICAgICBpZiAodGhpcy5fb3ZlcmZsb3dIaWRkZW4pIHsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbnRlbnQuY2xhc3NlZCgiY29tcG9uZW50LW92ZXJmbG93LWhpZGRlbiIsIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fY29udGVudC5jbGFzc2VkKCJjb21wb25lbnQtb3ZlcmZsb3ctdmlzaWJsZSIsIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2lzU2V0dXAgPSB0cnVlOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2l2ZW4gYXZhaWxhYmxlIHNwYWNlIGluIHBpeGVscywgcmV0dXJucyB0aGUgbWluaW11bSB3aWR0aCBhbmQgaGVpZ2h0IHRoaXMgQ29tcG9uZW50IHdpbGwgbmVlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBhdmFpbGFibGVXaWR0aAogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBhdmFpbGFibGVIZWlnaHQKICAgICAgICAgKiBAcmV0dXJucyB7U3BhY2VSZXF1ZXN0fQogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUucmVxdWVzdGVkU3BhY2UgPSBmdW5jdGlvbiAoYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbWluV2lkdGg6IDAsCiAgICAgICAgICAgICAgICBtaW5IZWlnaHQ6IDAsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyBhbmQgc2V0cyB0aGUgc2l6ZSwgcG9zaXRpb24sIGFuZCBhbGlnbm1lbnQgb2YgdGhlIENvbXBvbmVudCBmcm9tIHRoZSBzcGVjaWZpZWQgdmFsdWVzLgogICAgICAgICAqIElmIG5vIHBhcmFtZXRlcnMgYXJlIHN1cHBsaWVkIGFuZCB0aGUgQ29tcG9uZW50IGlzIGEgcm9vdCBub2RlLAogICAgICAgICAqIHRoZXkgYXJlIGluZmVycmVkIGZyb20gdGhlIHNpemUgb2YgdGhlIENvbXBvbmVudCdzIGVsZW1lbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBbb3JpZ2luXSBPcmlnaW4gb2YgdGhlIHNwYWNlIG9mZmVyZWQgdG8gdGhlIENvbXBvbmVudC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2F2YWlsYWJsZVdpZHRoXSBBdmFpbGFibGUgd2lkdGggaW4gcGl4ZWxzLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbYXZhaWxhYmxlSGVpZ2h0XSBBdmFpbGFibGUgaGVpZ2h0IGluIHBpeGVscy4KICAgICAgICAgKiBAcmV0dXJucyB7Q29tcG9uZW50fSBUaGUgY2FsbGluZyBDb21wb25lbnQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBpZiAob3JpZ2luID09IG51bGwgfHwgYXZhaWxhYmxlV2lkdGggPT0gbnVsbCB8fCBhdmFpbGFibGVIZWlnaHQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2VsZW1lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiYW5jaG9yKCkgbXVzdCBiZSBjYWxsZWQgYmVmb3JlIGNvbXB1dGVMYXlvdXQoKSIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAodGhpcy5fcm9vdEVsZW1lbnQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIC8vIHJldHJpZXZlIGhlaWdodC93aWR0aCBmcm9tIHJvb3RFbGVtZW50CiAgICAgICAgICAgICAgICAgICAgb3JpZ2luID0geyB4OiAwLCB5OiAwIH07CiAgICAgICAgICAgICAgICAgICAgdmFyIGVsZW0gPSB0aGlzLl9yb290RWxlbWVudC5ub2RlKCk7CiAgICAgICAgICAgICAgICAgICAgYXZhaWxhYmxlV2lkdGggPSB1dGlscyQxLkRPTS5lbGVtZW50V2lkdGgoZWxlbSk7CiAgICAgICAgICAgICAgICAgICAgYXZhaWxhYmxlSGVpZ2h0ID0gdXRpbHMkMS5ET00uZWxlbWVudEhlaWdodChlbGVtKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigibnVsbCBhcmd1bWVudHMgY2Fubm90IGJlIHBhc3NlZCB0byBjb21wdXRlTGF5b3V0KCkgb24gYSBub24tcm9vdCwgdW5hbmNob3JlZCBub2RlIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIF9hID0gdGhpcy5fc2l6ZUZyb21PZmZlcihhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSwgaGVpZ2h0ID0gX2EuaGVpZ2h0LCB3aWR0aCA9IF9hLndpZHRoOwogICAgICAgICAgICB2YXIgeEFsaWduUHJvcG9ydGlvbiA9IENvbXBvbmVudC5feEFsaWduVG9Qcm9wb3J0aW9uW3RoaXMuX3hBbGlnbm1lbnRdOwogICAgICAgICAgICB2YXIgeUFsaWduUHJvcG9ydGlvbiA9IENvbXBvbmVudC5feUFsaWduVG9Qcm9wb3J0aW9uW3RoaXMuX3lBbGlnbm1lbnRdOwogICAgICAgICAgICB2YXIgb3JpZ2luWCA9IG9yaWdpbi54ICsgKGF2YWlsYWJsZVdpZHRoIC0gd2lkdGgpICogeEFsaWduUHJvcG9ydGlvbjsKICAgICAgICAgICAgdmFyIG9yaWdpblkgPSBvcmlnaW4ueSArIChhdmFpbGFibGVIZWlnaHQgLSBoZWlnaHQpICogeUFsaWduUHJvcG9ydGlvbjsKICAgICAgICAgICAgdGhpcy5zZXRCb3VuZHMod2lkdGgsIGhlaWdodCwgb3JpZ2luWCwgb3JpZ2luWSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogRGlyZWN0bHkgc2V0cyBjb21wb25lbnQgc2l6ZSBhbmQsIG9wdGlvbmFsbHksIGl0cyBvcmlnaW4uCiAgICAgICAgICoKICAgICAgICAgKiBQcmVmZXJhYmx5LCBsYXlvdXQgaXMgYWNjb21wbGlzaGVkIGJ5IHBsYWNpbmcgY29tcG9uZW50cyBpbiBhIHRhYmxlLgogICAgICAgICAqIEhvd2V2ZXIsIGlmIHlvdSBuZWVkIHRvIGRpcmVjdGx5IG92ZXJyaWRlIHRoZSBjb21wb25lbnQgc2l6ZSwgeW91IG1heSBjYWxsCiAgICAgICAgICogdGhpcyBtZXRob2QuCiAgICAgICAgICoKICAgICAgICAgKiBOb3RlIHRoYXQgdGhpcyBtZXRob2Qgc3R5bGVzIHRoZSBhbmNob3JlZCBlbGVtZW50LCBzbyB0aGlzIGlzIHVzdWFsbHkgb25seQogICAgICAgICAqIHVzZWZ1bCBhZnRlciB0aGUgY29tcG9uZW50IGhhcyBiZWVuIGFuY2hvcmVkLiBJZiB0aGUgY29tcG9uZW50IGhhcyBub3QgYmVlbgogICAgICAgICAqIGFuY2hvcmVkIHRvIGFuIGVsZW1lbnQsIHRoZSBpbnRlcm5hbCBwcm9wZXJ0aWVzIHdpbGwgYmUgc2V0IGJ1dCBubyBzdHlsZXMKICAgICAgICAgKiB3aWxsIGJlIGFwcGxpZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW3dpZHRoXSB3aWR0aCBpbiBwaXhlbHMKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2hlaWdodF0gaGVpZ2h0IGluIHBpeGVscwogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbb3JpZ2luWF0gbGVmdCBvZmZzZXQgaW4gcGl4ZWxzCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IFtvcmlnaW5ZXSB0b3Agb2Zmc2V0IGluIHBpeGVscwogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUuc2V0Qm91bmRzID0gZnVuY3Rpb24gKHdpZHRoLCBoZWlnaHQsIG9yaWdpblgsIG9yaWdpblkpIHsKICAgICAgICAgICAgaWYgKG9yaWdpblggPT09IHZvaWQgMCkgeyBvcmlnaW5YID0gMDsgfQogICAgICAgICAgICBpZiAob3JpZ2luWSA9PT0gdm9pZCAwKSB7IG9yaWdpblkgPSAwOyB9CiAgICAgICAgICAgIHRoaXMuX3dpZHRoID0gd2lkdGg7CiAgICAgICAgICAgIHRoaXMuX2hlaWdodCA9IGhlaWdodDsKICAgICAgICAgICAgdGhpcy5fb3JpZ2luID0gewogICAgICAgICAgICAgICAgeDogb3JpZ2luWCwKICAgICAgICAgICAgICAgIHk6IG9yaWdpblksCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGlmICh0aGlzLl9lbGVtZW50ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2VsZW1lbnQuc3R5bGVzKHsKICAgICAgICAgICAgICAgICAgICBsZWZ0OiBvcmlnaW5YICsgInB4IiwKICAgICAgICAgICAgICAgICAgICBoZWlnaHQ6IGhlaWdodCArICJweCIsCiAgICAgICAgICAgICAgICAgICAgdG9wOiBvcmlnaW5ZICsgInB4IiwKICAgICAgICAgICAgICAgICAgICB3aWR0aDogd2lkdGggKyAicHgiLAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX3Jlc2l6ZUhhbmRsZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fcmVzaXplSGFuZGxlcih7IHdpZHRoOiB3aWR0aCwgaGVpZ2h0OiBoZWlnaHQgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLl9zaXplRnJvbU9mZmVyID0gZnVuY3Rpb24gKGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpIHsKICAgICAgICAgICAgdmFyIHJlcXVlc3RlZFNwYWNlID0gdGhpcy5yZXF1ZXN0ZWRTcGFjZShhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHdpZHRoOiB0aGlzLmZpeGVkV2lkdGgoKSA/IE1hdGgubWluKGF2YWlsYWJsZVdpZHRoLCByZXF1ZXN0ZWRTcGFjZS5taW5XaWR0aCkgOiBhdmFpbGFibGVXaWR0aCwKICAgICAgICAgICAgICAgIGhlaWdodDogdGhpcy5maXhlZEhlaWdodCgpID8gTWF0aC5taW4oYXZhaWxhYmxlSGVpZ2h0LCByZXF1ZXN0ZWRTcGFjZS5taW5IZWlnaHQpIDogYXZhaWxhYmxlSGVpZ2h0LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUXVldWVzIHRoZSBDb21wb25lbnQgZm9yIHJlbmRlcmluZy4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtDb21wb25lbnR9IFRoZSBjYWxsaW5nIENvbXBvbmVudC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLnJlbmRlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzQW5jaG9yZWQgJiYgdGhpcy5faXNTZXR1cCAmJiB0aGlzLndpZHRoKCkgPj0gMCAmJiB0aGlzLmhlaWdodCgpID49IDApIHsKICAgICAgICAgICAgICAgIHJlbmRlckNvbnRyb2xsZXIucmVnaXN0ZXJUb1JlbmRlcih0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUucmVuZGVyTG93UHJpb3JpdHkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJlbmRlcigpOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5fc2NoZWR1bGVDb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5faXNBbmNob3JlZCAmJiB0aGlzLl9pc1NldHVwKSB7CiAgICAgICAgICAgICAgICByZW5kZXJDb250cm9sbGVyLnJlZ2lzdGVyVG9Db21wdXRlTGF5b3V0QW5kUmVuZGVyKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIGEgY2FsbGJhY2sgdGhhdCBnZXRzIGNhbGxlZCB3aGVuIHRoZSBjb21wb25lbnQgcmVzaXplcy4gVGhlIHNpemUgY2hhbmdlCiAgICAgICAgICogaXMgbm90IGd1YXJhbnRlZWQgdG8gYmUgcmVmbGVjdGVkIGJ5IHRoZSBET00gYXQgdGhlIHRpbWUgdGhlIGNhbGxiYWNrIGlzIGZpcmVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtJUmVzaXplSGFuZGxlcn0gW3Jlc2l6ZUhhbmRsZXJdIENhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGNvbXBvbmVudCByZXNpemVzCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5vblJlc2l6ZSA9IGZ1bmN0aW9uIChyZXNpemVIYW5kbGVyKSB7CiAgICAgICAgICAgIHRoaXMuX3Jlc2l6ZUhhbmRsZXIgPSByZXNpemVIYW5kbGVyOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbmRlcnMgdGhlIENvbXBvbmVudCB3aXRob3V0IHdhaXRpbmcgZm9yIHRoZSBuZXh0IGZyYW1lLiBUaGlzIG1ldGhvZCBpcyBhIG5vLW9wIG9uCiAgICAgICAgICogQ29tcG9uZW50LCBUYWJsZSwgYW5kIEdyb3VwOyByZW5kZXIgdGhlbSBpbW1lZGlhdGVseSB3aXRoIC5yZW5kZXJUbygpIGluc3RlYWQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDYXVzZXMgdGhlIENvbXBvbmVudCB0byByZS1sYXlvdXQgYW5kIHJlbmRlci4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtDb21wb25lbnR9IFRoZSBjYWxsaW5nIENvbXBvbmVudC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLnJlZHJhdyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzQW5jaG9yZWQgJiYgdGhpcy5faXNTZXR1cCkgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuaXNSb290KCkpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9zY2hlZHVsZUNvbXB1dGVMYXlvdXQoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHRoaXMucGFyZW50KCkucmVkcmF3KCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUZWxsIHRoaXMgY29tcG9uZW50IHRvIGludmFsaWRhdGUgYW55IGNhY2hpbmcuIFRoaXMgZnVuY3Rpb24gc2hvdWxkIGJlCiAgICAgICAgICogY2FsbGVkIHdoZW4gYSBDU1MgY2hhbmdlIGhhcyBvY2N1cnJlZCB0aGF0IGNvdWxkIGluZmx1ZW5jZSB0aGUgbGF5b3V0CiAgICAgICAgICogb2YgdGhlIENvbXBvbmVudCwgc3VjaCBhcyBjaGFuZ2luZyB0aGUgZm9udCBzaXplLgogICAgICAgICAqCiAgICAgICAgICogU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5pbnZhbGlkYXRlQ2FjaGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIC8vIENvcmUgY29tcG9uZW50IGhhcyBubyBjYWNoaW5nLgogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVuZGVycyB0aGUgQ29tcG9uZW50IHRvIGEgZ2l2ZW4gSFRNTCBFbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtTdHJpbmd8ZDMuU2VsZWN0aW9ufSBlbGVtZW50IFRoZSBlbGVtZW50LCBhIHNlbGVjdG9yIHN0cmluZyBmb3IgdGhlIGVsZW1lbnQsIG9yIGEgZDMuU2VsZWN0aW9uIGZvciB0aGUgZWxlbWVudC4KICAgICAgICAgKiBAcmV0dXJucyB7Q29tcG9uZW50fSBUaGUgY2FsbGluZyBDb21wb25lbnQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5yZW5kZXJUbyA9IGZ1bmN0aW9uIChlbGVtZW50KSB7CiAgICAgICAgICAgIHRoaXMuZGV0YWNoKCk7CiAgICAgICAgICAgIGlmIChlbGVtZW50ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHZhciBzZWxlY3Rpb24gPSB2b2lkIDA7CiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIChlbGVtZW50KSA9PT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgICAgICBzZWxlY3Rpb24gPSBkMy5zZWxlY3QoZWxlbWVudCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChsb2Rhc2guaXNFbGVtZW50KGVsZW1lbnQpKSB7CiAgICAgICAgICAgICAgICAgICAgc2VsZWN0aW9uID0gZDMuc2VsZWN0KGVsZW1lbnQpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgc2VsZWN0aW9uID0gY29lcmNlRDMuY29lcmNlRXh0ZXJuYWxEMyhlbGVtZW50KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICghc2VsZWN0aW9uLm5vZGUoKSB8fCBzZWxlY3Rpb24ubm9kZSgpLm5vZGVOYW1lID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlBsb3R0YWJsZSByZXF1aXJlcyBhIHZhbGlkIEVsZW1lbnQgdG8gcmVuZGVyVG8iKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChzZWxlY3Rpb24ubm9kZSgpLm5vZGVOYW1lID09PSAic3ZnIikgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiUGxvdHRhYmxlIDMueCBhbmQgbGF0ZXIgY2FuIG9ubHkgcmVuZGVyVG8gYW4gSFRNTCBjb21wb25lbnQ7IHBhc3MgYSBkaXYgaW5zdGVhZCEiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuYW5jaG9yKHNlbGVjdGlvbik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX2VsZW1lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJJZiBhIENvbXBvbmVudCBoYXMgbmV2ZXIgYmVlbiByZW5kZXJlZCBiZWZvcmUsIHRoZW4gcmVuZGVyVG8gbXVzdCBiZSBnaXZlbiBhIG5vZGUgdG8gcmVuZGVyIHRvLCAiICsKICAgICAgICAgICAgICAgICAgICAib3IgYSBkMy5TZWxlY3Rpb24sIG9yIGEgc2VsZWN0b3Igc3RyaW5nIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmVuZGVyQ29udHJvbGxlci5yZWdpc3RlclRvQ29tcHV0ZUxheW91dEFuZFJlbmRlcih0aGlzKTsKICAgICAgICAgICAgLy8gZmx1c2ggc28gdGhhdCBjb25zdW1lcnMgY2FuIGltbWVkaWF0ZWx5IGF0dGFjaCB0byBzdHVmZiB3ZSBjcmVhdGUgaW4gdGhlIERPTQogICAgICAgICAgICByZW5kZXJDb250cm9sbGVyLmZsdXNoKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS54QWxpZ25tZW50ID0gZnVuY3Rpb24gKHhBbGlnbm1lbnQpIHsKICAgICAgICAgICAgaWYgKHhBbGlnbm1lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3hBbGlnbm1lbnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgeEFsaWdubWVudCA9IHhBbGlnbm1lbnQudG9Mb3dlckNhc2UoKTsKICAgICAgICAgICAgaWYgKENvbXBvbmVudC5feEFsaWduVG9Qcm9wb3J0aW9uW3hBbGlnbm1lbnRdID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiVW5zdXBwb3J0ZWQgYWxpZ25tZW50OiAiICsgeEFsaWdubWVudCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5feEFsaWdubWVudCA9IHhBbGlnbm1lbnQ7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS55QWxpZ25tZW50ID0gZnVuY3Rpb24gKHlBbGlnbm1lbnQpIHsKICAgICAgICAgICAgaWYgKHlBbGlnbm1lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3lBbGlnbm1lbnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgeUFsaWdubWVudCA9IHlBbGlnbm1lbnQudG9Mb3dlckNhc2UoKTsKICAgICAgICAgICAgaWYgKENvbXBvbmVudC5feUFsaWduVG9Qcm9wb3J0aW9uW3lBbGlnbm1lbnRdID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiVW5zdXBwb3J0ZWQgYWxpZ25tZW50OiAiICsgeUFsaWdubWVudCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5feUFsaWdubWVudCA9IHlBbGlnbm1lbnQ7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIGlmIHRoZSBDb21wb25lbnQgaGFzIGEgZ2l2ZW4gQ1NTIGNsYXNzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGNzc0NsYXNzIFRoZSBDU1MgY2xhc3MgdG8gY2hlY2sgZm9yLgogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUuaGFzQ2xhc3MgPSBmdW5jdGlvbiAoY3NzQ2xhc3MpIHsKICAgICAgICAgICAgaWYgKGNzc0NsYXNzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fZWxlbWVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fY3NzQ2xhc3Nlcy5oYXMoY3NzQ2xhc3MpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VsZW1lbnQuY2xhc3NlZChjc3NDbGFzcyk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBnaXZlbiBDU1MgY2xhc3MgdG8gdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjc3NDbGFzcyBUaGUgQ1NTIGNsYXNzIHRvIGFkZC4KICAgICAgICAgKiBAcmV0dXJucyB7Q29tcG9uZW50fSBUaGUgY2FsbGluZyBDb21wb25lbnQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5hZGRDbGFzcyA9IGZ1bmN0aW9uIChjc3NDbGFzcykgewogICAgICAgICAgICBpZiAoY3NzQ2xhc3MgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX2VsZW1lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fY3NzQ2xhc3Nlcy5hZGQoY3NzQ2xhc3MpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZWxlbWVudC5jbGFzc2VkKGNzc0NsYXNzLCB0cnVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBnaXZlbiBDU1MgY2xhc3MgZnJvbSB0aGUgQ29tcG9uZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IGNzc0NsYXNzIFRoZSBDU1MgY2xhc3MgdG8gcmVtb3ZlLgogICAgICAgICAqIEByZXR1cm5zIHtDb21wb25lbnR9IFRoZSBjYWxsaW5nIENvbXBvbmVudC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLnJlbW92ZUNsYXNzID0gZnVuY3Rpb24gKGNzc0NsYXNzKSB7CiAgICAgICAgICAgIGlmIChjc3NDbGFzcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fZWxlbWVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jc3NDbGFzc2VzLmRlbGV0ZShjc3NDbGFzcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9lbGVtZW50LmNsYXNzZWQoY3NzQ2xhc3MsIGZhbHNlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyBpZiB0aGUgQ29tcG9uZW50IGhhcyBhIGZpeGVkIHdpZHRoIG9yIGlmIGl0IGdyb3dzIHRvIGZpbGwgYXZhaWxhYmxlIHNwYWNlLgogICAgICAgICAqIFJldHVybnMgZmFsc2UgYnkgZGVmYXVsdCBvbiB0aGUgYmFzZSBDb21wb25lbnQgY2xhc3MuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5maXhlZFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3MgaWYgdGhlIENvbXBvbmVudCBoYXMgYSBmaXhlZCBoZWlnaHQgb3IgaWYgaXQgZ3Jvd3MgdG8gZmlsbCBhdmFpbGFibGUgc3BhY2UuCiAgICAgICAgICogUmV0dXJucyBmYWxzZSBieSBkZWZhdWx0IG9uIHRoZSBiYXNlIENvbXBvbmVudCBjbGFzcy4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLmZpeGVkSGVpZ2h0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBEZXRhY2hlcyBhIENvbXBvbmVudCBmcm9tIHRoZSBET00uIFRoZSBDb21wb25lbnQgY2FuIGJlIHJldXNlZC4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgc2hvdWxkIG9ubHkgYmUgdXNlZCBpZiB5b3UgcGxhbiBvbiByZXVzaW5nIHRoZSBjYWxsaW5nIENvbXBvbmVudC4gT3RoZXJ3aXNlLCB1c2UgZGVzdHJveSgpLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybnMgVGhlIGNhbGxpbmcgQ29tcG9uZW50LgogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUuZGV0YWNoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLnBhcmVudChudWxsKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzQW5jaG9yZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2VsZW1lbnQucmVtb3ZlKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5faXNBbmNob3JlZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9vbkRldGFjaENhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKHRoaXMpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUgQ29tcG9uZW50IGlzIGRldGFjaCgpLWVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDb21wb25lbnRDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtDb21wb25lbnR9IFRoZSBjYWxsaW5nIENvbXBvbmVudC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLm9uRGV0YWNoID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX29uRGV0YWNoQ2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIHRoZSBDb21wb25lbnQgaXMgZGV0YWNoKCktZWQuCiAgICAgICAgICogVGhlIGNhbGxiYWNrIGlzIGlkZW50aWZpZWQgYnkgcmVmZXJlbmNlIGVxdWFsaXR5LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDb21wb25lbnRDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtDb21wb25lbnR9IFRoZSBjYWxsaW5nIENvbXBvbmVudC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLm9mZkRldGFjaCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9vbkRldGFjaENhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUucGFyZW50ID0gZnVuY3Rpb24gKHBhcmVudCkgewogICAgICAgICAgICBpZiAocGFyZW50ID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wYXJlbnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHBhcmVudCAhPT0gbnVsbCAmJiAhcGFyZW50Lmhhcyh0aGlzKSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJQYXNzZWQgaW52YWxpZCBwYXJlbnQiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9wYXJlbnQgPSBwYXJlbnQ7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybnMge0JvdW5kc30gZm9yIHRoZSBjb21wb25lbnQgaW4gcGl4ZWwgc3BhY2UsIHdoZXJlIHRoZSB0b3BMZWZ0CiAgICAgICAgICogcmVwcmVzZW50cyB0aGUgY29tcG9uZW50J3MgbWluaW11bSB4IGFuZCB5IHZhbHVlcyBhbmQgdGhlIGJvdHRvbVJpZ2h0IHJlcHJlc2VudHMKICAgICAgICAgKiB0aGUgY29tcG9uZW50J3MgbWF4aW11bSB4IGFuZCB5IHZhbHVlcy4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLmJvdW5kcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHRvcExlZnQgPSB0aGlzLm9yaWdpbigpOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgdG9wTGVmdDogdG9wTGVmdCwKICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiB7CiAgICAgICAgICAgICAgICAgICAgeDogdG9wTGVmdC54ICsgdGhpcy53aWR0aCgpLAogICAgICAgICAgICAgICAgICAgIHk6IHRvcExlZnQueSArIHRoaXMuaGVpZ2h0KCksCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIENvbXBvbmVudCBmcm9tIHRoZSBET00gYW5kIGRpc2Nvbm5lY3RzIGFsbCBsaXN0ZW5lcnMuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5kZXN0cm95ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl9kZXN0cm95ZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLmRldGFjaCgpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgd2lkdGggb2YgdGhlIENvbXBvbmVudCBpbiBwaXhlbHMuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS53aWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3dpZHRoOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgaGVpZ2h0IG9mIHRoZSBDb21wb25lbnQgaW4gcGl4ZWxzLgogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUuaGVpZ2h0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5faGVpZ2h0OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgb3JpZ2luIG9mIHRoZSBDb21wb25lbnQgcmVsYXRpdmUgdG8gaXRzIHBhcmVudC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge1BvaW50fQogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUub3JpZ2luID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgeDogdGhpcy5fb3JpZ2luLngsCiAgICAgICAgICAgICAgICB5OiB0aGlzLl9vcmlnaW4ueSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIG9yaWdpbiBvZiB0aGUgQ29tcG9uZW50IHJlbGF0aXZlIHRvIHRoZSByb290IENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge1BvaW50fQogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUub3JpZ2luVG9Sb290ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgb3JpZ2luID0gdGhpcy5vcmlnaW4oKTsKICAgICAgICAgICAgdmFyIGFuY2VzdG9yID0gdGhpcy5wYXJlbnQoKTsKICAgICAgICAgICAgd2hpbGUgKGFuY2VzdG9yICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHZhciBhbmNlc3Rvck9yaWdpbiA9IGFuY2VzdG9yLm9yaWdpbigpOwogICAgICAgICAgICAgICAgb3JpZ2luLnggKz0gYW5jZXN0b3JPcmlnaW4ueDsKICAgICAgICAgICAgICAgIG9yaWdpbi55ICs9IGFuY2VzdG9yT3JpZ2luLnk7CiAgICAgICAgICAgICAgICBhbmNlc3RvciA9IGFuY2VzdG9yLnBhcmVudCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBvcmlnaW47CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSByb290IGNvbXBvbmVudCBvZiB0aGUgaGllcmFyY2h5LiBJZiB0aGUgcHJvdmlkZWQKICAgICAgICAgKiBjb21wb25lbnQgaXMgdGhlIHJvb3QsIHRoYXQgY29tcG9uZW50IHdpbGwgYmUgcmV0dXJuZWQuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5yb290ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgY29tcG9uZW50ID0gdGhpczsKICAgICAgICAgICAgd2hpbGUgKCFjb21wb25lbnQuaXNSb290KCkpIHsKICAgICAgICAgICAgICAgIGNvbXBvbmVudCA9IGNvbXBvbmVudC5wYXJlbnQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gY29tcG9uZW50OwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5pc1Jvb3QgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnBhcmVudCgpID09IG51bGw7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBTZWxlY3Rpb24gY29udGFpbmluZyB0aGUgPGc+IGluIGZyb250IG9mIHRoZSB2aXN1YWwgZWxlbWVudHMgb2YgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIFdpbGwgcmV0dXJuIHVuZGVmaW5lZCBpZiB0aGUgQ29tcG9uZW50IGhhcyBub3QgYmVlbiBhbmNob3JlZC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge2QzLlNlbGVjdGlvbn0KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLmZvcmVncm91bmQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9mb3JlZ3JvdW5kQ29udGFpbmVyOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgU1ZHIHRoYXQgaG9sZHMgdGhlIHZpc3VhbCBlbGVtZW50cyBvZiB0aGUgQ29tcG9uZW50LgogICAgICAgICAqCiAgICAgICAgICogV2lsbCByZXR1cm4gdW5kZWZpbmVkIGlmIHRoZSBDb21wb25lbnQgaGFzIG5vdCBiZWVuIGFuY2hvcmVkLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7ZDMuU2VsZWN0aW9ufSBjb250ZW50IHNlbGVjdGlvbiBmb3IgdGhlIENvbXBvbmVudAogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudC5wcm90b3R5cGUuY29udGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbnRlbnQ7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBIVE1MIEVsZW1lbnQgYXQgdGhlIHJvb3Qgb2YgdGhpcyBjb21wb25lbnQncyBET00gdHJlZS4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLmVsZW1lbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9lbGVtZW50OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgdG9wLWxldmVsIHVzZXIgc3VwcGxpZWQgZWxlbWVudCB0aGF0IHJvb3RzIHRoZSB0cmVlIHRoYXQgdGhpcyBDb21wb25lbnQgbGl2ZXMgaW4uCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50LnByb3RvdHlwZS5yb290RWxlbWVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucm9vdCgpLl9yb290RWxlbWVudDsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIFNlbGVjdGlvbiBjb250YWluaW5nIHRoZSA8Zz4gYmVoaW5kIHRoZSB2aXN1YWwgZWxlbWVudHMgb2YgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIFdpbGwgcmV0dXJuIHVuZGVmaW5lZCBpZiB0aGUgQ29tcG9uZW50IGhhcyBub3QgYmVlbiBhbmNob3JlZC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge2QzLlNlbGVjdGlvbn0gYmFja2dyb3VuZCBzZWxlY3Rpb24gZm9yIHRoZSBDb21wb25lbnQKICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnQucHJvdG90eXBlLmJhY2tncm91bmQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9iYWNrZ3JvdW5kQ29udGFpbmVyOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50Ll94QWxpZ25Ub1Byb3BvcnRpb24gPSB7CiAgICAgICAgICAgIGxlZnQ6IDAsCiAgICAgICAgICAgIGNlbnRlcjogMC41LAogICAgICAgICAgICByaWdodDogMSwKICAgICAgICB9OwogICAgICAgIENvbXBvbmVudC5feUFsaWduVG9Qcm9wb3J0aW9uID0gewogICAgICAgICAgICB0b3A6IDAsCiAgICAgICAgICAgIGNlbnRlcjogMC41LAogICAgICAgICAgICBib3R0b206IDEsCiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ29tcG9uZW50OwogICAgfSgpKTsKICAgIGV4cG9ydHMuQ29tcG9uZW50ID0gQ29tcG9uZW50OwogICAgfSk7CgogICAgdmFyIGZvcm1hdHRlcnMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvLyBEbyBub3QgdXNlIHV0YyBieSBkZWZhdWx0CiAgICB2YXIgREVGQVVMVF9VU0VfVVRDID0gZmFsc2U7CiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBmb3JtYXR0ZXIgZm9yIGN1cnJlbmN5IHZhbHVlcy4KICAgICAqCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW3ByZWNpc2lvbl0gVGhlIG51bWJlciBvZiBkZWNpbWFsIHBsYWNlcyB0byBzaG93IChkZWZhdWx0IDIpLgogICAgICogQHBhcmFtIHtzdHJpbmd9IFtzeW1ib2xdIFRoZSBjdXJyZW5jeSBzeW1ib2wgdG8gdXNlIChkZWZhdWx0ICIkIikuCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtwcmVmaXhdIFdoZXRoZXIgdG8gcHJlcGVuZCBvciBhcHBlbmQgdGhlIGN1cnJlbmN5IHN5bWJvbCAoZGVmYXVsdCB0cnVlKS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciBmb3IgY3VycmVuY3kgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBjdXJyZW5jeShwcmVjaXNpb24sIHN5bWJvbCwgcHJlZml4KSB7CiAgICAgICAgaWYgKHByZWNpc2lvbiA9PT0gdm9pZCAwKSB7IHByZWNpc2lvbiA9IDI7IH0KICAgICAgICBpZiAoc3ltYm9sID09PSB2b2lkIDApIHsgc3ltYm9sID0gIiQiOyB9CiAgICAgICAgaWYgKHByZWZpeCA9PT0gdm9pZCAwKSB7IHByZWZpeCA9IHRydWU7IH0KICAgICAgICB2YXIgZml4ZWRGb3JtYXR0ZXIgPSBmaXhlZChwcmVjaXNpb24pOwogICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICB2YXIgZm9ybWF0dGVkVmFsdWUgPSBmaXhlZEZvcm1hdHRlcihNYXRoLmFicyhkKSk7CiAgICAgICAgICAgIGlmIChmb3JtYXR0ZWRWYWx1ZSAhPT0gIiIpIHsKICAgICAgICAgICAgICAgIGlmIChwcmVmaXgpIHsKICAgICAgICAgICAgICAgICAgICBmb3JtYXR0ZWRWYWx1ZSA9IHN5bWJvbCArIGZvcm1hdHRlZFZhbHVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgZm9ybWF0dGVkVmFsdWUgKz0gc3ltYm9sOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGQgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgZm9ybWF0dGVkVmFsdWUgPSAiLSIgKyBmb3JtYXR0ZWRWYWx1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZm9ybWF0dGVkVmFsdWU7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuY3VycmVuY3kgPSBjdXJyZW5jeTsKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGZvcm1hdHRlciB0aGF0IGRpc3BsYXlzIGV4YWN0bHkgW3ByZWNpc2lvbl0gZGVjaW1hbCBwbGFjZXMuCiAgICAgKgogICAgICogQHBhcmFtIHtudW1iZXJ9IFtwcmVjaXNpb25dIFRoZSBudW1iZXIgb2YgZGVjaW1hbCBwbGFjZXMgdG8gc2hvdyAoZGVmYXVsdCAzKS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciB0aGF0IGRpc3BsYXlzIGV4YWN0bHkgW3ByZWNpc2lvbl0gZGVjaW1hbCBwbGFjZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZpeGVkKHByZWNpc2lvbikgewogICAgICAgIGlmIChwcmVjaXNpb24gPT09IHZvaWQgMCkgeyBwcmVjaXNpb24gPSAzOyB9CiAgICAgICAgdmVyaWZ5UHJlY2lzaW9uKHByZWNpc2lvbik7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkKSB7IHJldHVybiBkLnRvRml4ZWQocHJlY2lzaW9uKTsgfTsKICAgIH0KICAgIGV4cG9ydHMuZml4ZWQgPSBmaXhlZDsKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGZvcm1hdHRlciB0aGF0IGZvcm1hdHMgbnVtYmVycyB0byBzaG93IG5vIG1vcmUgdGhhbgogICAgICogW21heE51bWJlck9mRGVjaW1hbFBsYWNlc10gZGVjaW1hbCBwbGFjZXMuIEFsbCBvdGhlciB2YWx1ZXMgYXJlIHN0cmluZ2lmaWVkLgogICAgICoKICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbbWF4TnVtYmVyT2ZEZWNpbWFsUGxhY2VzXSBUaGUgbnVtYmVyIG9mIGRlY2ltYWwgcGxhY2VzIHRvIHNob3cgKGRlZmF1bHQgMykuCiAgICAgKgogICAgICogQHJldHVybnMge0Zvcm1hdHRlcn0gQSBmb3JtYXR0ZXIgZm9yIGdlbmVyYWwgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBnZW5lcmFsKG1heE51bWJlck9mRGVjaW1hbFBsYWNlcykgewogICAgICAgIGlmIChtYXhOdW1iZXJPZkRlY2ltYWxQbGFjZXMgPT09IHZvaWQgMCkgeyBtYXhOdW1iZXJPZkRlY2ltYWxQbGFjZXMgPSAzOyB9CiAgICAgICAgdmVyaWZ5UHJlY2lzaW9uKG1heE51bWJlck9mRGVjaW1hbFBsYWNlcyk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgIGlmICh0eXBlb2YgZCA9PT0gIm51bWJlciIpIHsKICAgICAgICAgICAgICAgIHZhciBtdWx0aXBsaWVyID0gTWF0aC5wb3coMTAsIG1heE51bWJlck9mRGVjaW1hbFBsYWNlcyk7CiAgICAgICAgICAgICAgICByZXR1cm4gU3RyaW5nKE1hdGgucm91bmQoZCAqIG11bHRpcGxpZXIpIC8gbXVsdGlwbGllcik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gU3RyaW5nKGQpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuZ2VuZXJhbCA9IGdlbmVyYWw7CiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBmb3JtYXR0ZXIgdGhhdCBzdHJpbmdpZmllcyBpdHMgaW5wdXQuCiAgICAgKgogICAgICogQHJldHVybnMge0Zvcm1hdHRlcn0gQSBmb3JtYXR0ZXIgdGhhdCBzdHJpbmdpZmllcyBpdHMgaW5wdXQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlkZW50aXR5KCkgewogICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCkgeyByZXR1cm4gU3RyaW5nKGQpOyB9OwogICAgfQogICAgZXhwb3J0cy5pZGVudGl0eSA9IGlkZW50aXR5OwogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgZm9ybWF0dGVyIGZvciBwZXJjZW50YWdlIHZhbHVlcy4KICAgICAqIE11bHRpcGxpZXMgdGhlIGlucHV0IGJ5IDEwMCBhbmQgYXBwZW5kcyAiJSIuCiAgICAgKgogICAgICogQHBhcmFtIHtudW1iZXJ9IFtwcmVjaXNpb25dIFRoZSBudW1iZXIgb2YgZGVjaW1hbCBwbGFjZXMgdG8gc2hvdyAoZGVmYXVsdCAwKS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciBmb3IgcGVyY2VudGFnZSB2YWx1ZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBlcmNlbnRhZ2UocHJlY2lzaW9uKSB7CiAgICAgICAgaWYgKHByZWNpc2lvbiA9PT0gdm9pZCAwKSB7IHByZWNpc2lvbiA9IDA7IH0KICAgICAgICB2YXIgZml4ZWRGb3JtYXR0ZXIgPSBmaXhlZChwcmVjaXNpb24pOwogICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICB2YXIgdmFsVG9Gb3JtYXQgPSBkICogMTAwOwogICAgICAgICAgICAvLyBBY2NvdW50IGZvciBmbG9hdCBpbXByZWNpc2lvbgogICAgICAgICAgICB2YXIgdmFsU3RyaW5nID0gZC50b1N0cmluZygpOwogICAgICAgICAgICB2YXIgaW50ZWdlclBvd2VyVGVuID0gTWF0aC5wb3coMTAsIHZhbFN0cmluZy5sZW5ndGggLSAodmFsU3RyaW5nLmluZGV4T2YoIi4iKSArIDEpKTsKICAgICAgICAgICAgdmFsVG9Gb3JtYXQgPSBwYXJzZUludCgodmFsVG9Gb3JtYXQgKiBpbnRlZ2VyUG93ZXJUZW4pLnRvU3RyaW5nKCksIDEwKSAvIGludGVnZXJQb3dlclRlbjsKICAgICAgICAgICAgcmV0dXJuIGZpeGVkRm9ybWF0dGVyKHZhbFRvRm9ybWF0KSArICIlIjsKICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5wZXJjZW50YWdlID0gcGVyY2VudGFnZTsKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGZvcm1hdHRlciBmb3IgdmFsdWVzIHRoYXQgZGlzcGxheXMgW251bWJlck9mU2lnbmlmaWNhbnRGaWd1cmVzXSBzaWduaWZpY2FudCBmaWd1cmVzCiAgICAgKiBhbmQgcHV0cyBTSSBub3RhdGlvbi4KICAgICAqCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW251bWJlck9mU2lnbmlmaWNhbnRGaWd1cmVzXSBUaGUgbnVtYmVyIG9mIHNpZ25pZmljYW50IGZpZ3VyZXMgdG8gc2hvdyAoZGVmYXVsdCAzKS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciBmb3IgU0kgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBzaVN1ZmZpeChudW1iZXJPZlNpZ25pZmljYW50RmlndXJlcykgewogICAgICAgIGlmIChudW1iZXJPZlNpZ25pZmljYW50RmlndXJlcyA9PT0gdm9pZCAwKSB7IG51bWJlck9mU2lnbmlmaWNhbnRGaWd1cmVzID0gMzsgfQogICAgICAgIHZlcmlmeVByZWNpc2lvbihudW1iZXJPZlNpZ25pZmljYW50RmlndXJlcyk7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkKSB7IHJldHVybiBkMy5mb3JtYXQoIi4iICsgbnVtYmVyT2ZTaWduaWZpY2FudEZpZ3VyZXMgKyAicyIpKGQpOyB9OwogICAgfQogICAgZXhwb3J0cy5zaVN1ZmZpeCA9IHNpU3VmZml4OwogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgZm9ybWF0dGVyIGZvciB2YWx1ZXMgdGhhdCBkaXNwbGF5cyBhYmJyZXZpYXRlZCB2YWx1ZXMKICAgICAqIGFuZCB1c2VzIHN0YW5kYXJkIHNob3J0IHNjYWxlIHN1ZmZpeGVzCiAgICAgKiAtIEsgLSB0aG91c2FuZHMgLSAxMCBeIDMKICAgICAqIC0gTSAtIG1pbGxpb25zIC0gMTAgXiA2CiAgICAgKiAtIEIgLSBiaWxsaW9ucyAtIDEwIF4gOQogICAgICogLSBUIC0gdHJpbGxpb25zIC0gMTAgXiAxMgogICAgICogLSBRIC0gcXVhZHJpbGxpb25zIC0gMTAgXiAxNQogICAgICoKICAgICAqIE51bWJlcnMgd2l0aCBhIG1hZ25pdHVkZSBvdXRzaWRlIG9mICgxMCBeICgtcHJlY2lzaW9uKSwgMTAgXiAxNSkgYXJlIHNob3duIHVzaW5nCiAgICAgKiBzY2llbnRpZmljIG5vdGF0aW9uIHRvIGF2b2lkIGNyZWF0aW5nIGV4dHJlbWVseSBsb25nIGRlY2ltYWwgc3RyaW5ncy4KICAgICAqCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW3ByZWNpc2lvbl0gdGhlIG51bWJlciBvZiBkZWNpbWFsIHBsYWNlcyB0byBzaG93IChkZWZhdWx0IDMpCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciB3aXRoIHNob3J0IHNjYWxlIGZvcm1hdHRpbmcKICAgICAqLwogICAgZnVuY3Rpb24gc2hvcnRTY2FsZShwcmVjaXNpb24pIHsKICAgICAgICBpZiAocHJlY2lzaW9uID09PSB2b2lkIDApIHsgcHJlY2lzaW9uID0gMzsgfQogICAgICAgIHZlcmlmeVByZWNpc2lvbihwcmVjaXNpb24pOwogICAgICAgIHZhciBzdWZmaXhlcyA9ICJLTUJUUSI7CiAgICAgICAgdmFyIGV4cG9uZW50Rm9ybWF0dGVyID0gZDMuZm9ybWF0KCIuIiArIHByZWNpc2lvbiArICJlIik7CiAgICAgICAgdmFyIGZpeGVkRm9ybWF0dGVyID0gZDMuZm9ybWF0KCIuIiArIHByZWNpc2lvbiArICJmIik7CiAgICAgICAgdmFyIG1heCA9IE1hdGgucG93KDEwLCAoMyAqIChzdWZmaXhlcy5sZW5ndGggKyAxKSkpOwogICAgICAgIHZhciBtaW4gPSBNYXRoLnBvdygxMCwgLXByZWNpc2lvbik7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChudW0pIHsKICAgICAgICAgICAgdmFyIGFic051bSA9IE1hdGguYWJzKG51bSk7CiAgICAgICAgICAgIGlmICgoYWJzTnVtIDwgbWluIHx8IGFic051bSA+PSBtYXgpICYmIGFic051bSAhPT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGV4cG9uZW50Rm9ybWF0dGVyKG51bSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGlkeCA9IC0xOwogICAgICAgICAgICB3aGlsZSAoYWJzTnVtID49IE1hdGgucG93KDEwMDAsIGlkeCArIDIpICYmIGlkeCA8IChzdWZmaXhlcy5sZW5ndGggLSAxKSkgewogICAgICAgICAgICAgICAgaWR4Kys7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIG91dHB1dCA9ICIiOwogICAgICAgICAgICBpZiAoaWR4ID09PSAtMSkgewogICAgICAgICAgICAgICAgb3V0cHV0ID0gZml4ZWRGb3JtYXR0ZXIobnVtKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIG91dHB1dCA9IGZpeGVkRm9ybWF0dGVyKG51bSAvIE1hdGgucG93KDEwMDAsIGlkeCArIDEpKSArIHN1ZmZpeGVzW2lkeF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gY2F0Y2ggcm91bmRpbmcgYnkgdGhlIHVuZGVybHlpbmcgZDMgZm9ybWF0dGVyCiAgICAgICAgICAgIGlmICgobnVtID4gMCAmJiBvdXRwdXQuc3Vic3RyKDAsIDQpID09PSAiMTAwMCIpIHx8IChudW0gPCAwICYmIG91dHB1dC5zdWJzdHIoMCwgNSkgPT09ICItMTAwMCIpKSB7CiAgICAgICAgICAgICAgICBpZiAoaWR4IDwgc3VmZml4ZXMubGVuZ3RoIC0gMSkgewogICAgICAgICAgICAgICAgICAgIGlkeCsrOwogICAgICAgICAgICAgICAgICAgIG91dHB1dCA9IGZpeGVkRm9ybWF0dGVyKG51bSAvIE1hdGgucG93KDEwMDAsIGlkeCArIDEpKSArIHN1ZmZpeGVzW2lkeF07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBvdXRwdXQgPSBleHBvbmVudEZvcm1hdHRlcihudW0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBvdXRwdXQ7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuc2hvcnRTY2FsZSA9IHNob3J0U2NhbGU7CiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBtdWx0aSB0aW1lIGZvcm1hdHRlciB0aGF0IGRpc3BsYXlzIGRhdGVzLgogICAgICoKICAgICAqIEByZXR1cm5zIHtGb3JtYXR0ZXJ9IEEgZm9ybWF0dGVyIGZvciB0aW1lL2RhdGUgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBtdWx0aVRpbWUoKSB7CiAgICAgICAgLy8gRm9ybWF0dGVyIHRpZXJzIGdvaW5nIGZyb20gc2hvcnRlc3QgdGltZSBzY2FsZSB0byBsYXJnZXN0IC0gdGhlc2Ugd2VyZSB0YWtlbiBmcm9tIGQzCiAgICAgICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL21ib3N0b2NrL2QzL3dpa2kvVGltZS1Gb3JtYXR0aW5nI2Zvcm1hdF9tdWx0aQogICAgICAgIHZhciBjYW5kaWRhdGVGb3JtYXRzID0gWwogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBzcGVjaWZpZXI6ICIuJUwiLAogICAgICAgICAgICAgICAgcHJlZGljYXRlOiBmdW5jdGlvbiAoZCkgeyByZXR1cm4gZC5nZXRNaWxsaXNlY29uZHMoKSAhPT0gMDsgfSwKICAgICAgICAgICAgfSwKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgc3BlY2lmaWVyOiAiOiVTIiwKICAgICAgICAgICAgICAgIHByZWRpY2F0ZTogZnVuY3Rpb24gKGQpIHsgcmV0dXJuIGQuZ2V0U2Vjb25kcygpICE9PSAwOyB9LAogICAgICAgICAgICB9LAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBzcGVjaWZpZXI6ICIlSTolTSIsCiAgICAgICAgICAgICAgICBwcmVkaWNhdGU6IGZ1bmN0aW9uIChkKSB7IHJldHVybiBkLmdldE1pbnV0ZXMoKSAhPT0gMDsgfSwKICAgICAgICAgICAgfSwKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgc3BlY2lmaWVyOiAiJUkgJXAiLAogICAgICAgICAgICAgICAgcHJlZGljYXRlOiBmdW5jdGlvbiAoZCkgeyByZXR1cm4gZC5nZXRIb3VycygpICE9PSAwOyB9LAogICAgICAgICAgICB9LAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBzcGVjaWZpZXI6ICIlYSAlZCIsCiAgICAgICAgICAgICAgICBwcmVkaWNhdGU6IGZ1bmN0aW9uIChkKSB7IHJldHVybiBkLmdldERheSgpICE9PSAwICYmIGQuZ2V0RGF0ZSgpICE9PSAxOyB9LAogICAgICAgICAgICB9LAogICAgICAgICAgICB7CiAgICAgICAgICAgICAgICBzcGVjaWZpZXI6ICIlYiAlZCIsCiAgICAgICAgICAgICAgICBwcmVkaWNhdGU6IGZ1bmN0aW9uIChkKSB7IHJldHVybiBkLmdldERhdGUoKSAhPT0gMTsgfSwKICAgICAgICAgICAgfSwKICAgICAgICAgICAgewogICAgICAgICAgICAgICAgc3BlY2lmaWVyOiAiJWIiLAogICAgICAgICAgICAgICAgcHJlZGljYXRlOiBmdW5jdGlvbiAoZCkgeyByZXR1cm4gZC5nZXRNb250aCgpICE9PSAwOyB9LAogICAgICAgICAgICB9LAogICAgICAgIF07CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgIHZhciBhY2NlcHRhYmxlRm9ybWF0cyA9IGNhbmRpZGF0ZUZvcm1hdHMuZmlsdGVyKGZ1bmN0aW9uIChjYW5kaWRhdGUpIHsgcmV0dXJuIGNhbmRpZGF0ZS5wcmVkaWNhdGUoZCk7IH0pOwogICAgICAgICAgICB2YXIgc3BlY2lmaWVyID0gYWNjZXB0YWJsZUZvcm1hdHMubGVuZ3RoID4gMAogICAgICAgICAgICAgICAgPyBhY2NlcHRhYmxlRm9ybWF0c1swXS5zcGVjaWZpZXIKICAgICAgICAgICAgICAgIDogIiVZIjsKICAgICAgICAgICAgcmV0dXJuIGQzLnRpbWVGb3JtYXQoc3BlY2lmaWVyKShkKTsKICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5tdWx0aVRpbWUgPSBtdWx0aVRpbWU7CiAgICAvKioKICAgICAqIENyZWF0ZXMgYSB0aW1lIGZvcm1hdHRlciB0aGF0IGRpc3BsYXlzIHRpbWUvZGF0ZSB1c2luZyBnaXZlbiBzcGVjaWZpZXIuCiAgICAgKgogICAgICogTGlzdCBvZiBkaXJlY3RpdmVzIGNhbiBiZSBmb3VuZCBvbjogaHR0cHM6Ly9naXRodWIuY29tL21ib3N0b2NrL2QzL3dpa2kvVGltZS1Gb3JtYXR0aW5nI2Zvcm1hdAogICAgICoKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbc3BlY2lmaWVyXSBUaGUgc3BlY2lmaWVyIGZvciB0aGUgZm9ybWF0dGVyLgogICAgICogQHBhcmFtIHtib29sZWFufSBbdXNlVVRDXSBEaXNwbGF5cyB0aW1lIGluIFVUQyBpZiB0cnVlLCBsb2NhbCB0aW1lIGlmIGZhbHNlLiBEZWZhdWx0cyB0byBmYWxzZS4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7Rm9ybWF0dGVyfSBBIGZvcm1hdHRlciBmb3IgdGltZS9kYXRlIHZhbHVlcy4KICAgICAqLwogICAgZnVuY3Rpb24gdGltZShzcGVjaWZpZXIsIHVzZVVUQykgewogICAgICAgIGlmICh1c2VVVEMgPT09IHZvaWQgMCkgeyB1c2VVVEMgPSBERUZBVUxUX1VTRV9VVEM7IH0KICAgICAgICBpZiAodXNlVVRDKSB7CiAgICAgICAgICAgIHJldHVybiBkMy51dGNGb3JtYXQoc3BlY2lmaWVyKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGQzLnRpbWVGb3JtYXQoc3BlY2lmaWVyKTsKICAgIH0KICAgIGV4cG9ydHMudGltZSA9IHRpbWU7CiAgICBmdW5jdGlvbiB2ZXJpZnlQcmVjaXNpb24ocHJlY2lzaW9uKSB7CiAgICAgICAgaWYgKHByZWNpc2lvbiA8IDAgfHwgcHJlY2lzaW9uID4gMjApIHsKICAgICAgICAgICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoIkZvcm1hdHRlciBwcmVjaXNpb24gbXVzdCBiZSBiZXR3ZWVuIDAgYW5kIDIwIik7CiAgICAgICAgfQogICAgICAgIGlmIChwcmVjaXNpb24gIT09IE1hdGguZmxvb3IocHJlY2lzaW9uKSkgewogICAgICAgICAgICB0aHJvdyBuZXcgUmFuZ2VFcnJvcigiRm9ybWF0dGVyIHByZWNpc2lvbiBtdXN0IGJlIGFuIGludGVnZXIiKTsKICAgICAgICB9CiAgICB9CiAgICB9KTsKCiAgICB2YXIgYXhpcyQyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCgogICAgZXhwb3J0cy5BeGlzT3JpZW50YXRpb24gPSBtYWtlRW51bV8xLm1ha2VFbnVtKFsiYm90dG9tIiwgImxlZnQiLCAicmlnaHQiLCAidG9wIl0pOwogICAgdmFyIEF4aXMgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhBeGlzLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIENvbnN0cnVjdHMgYW4gQXhpcy4KICAgICAgICAgKiBBbiBBeGlzIGlzIGEgdmlzdWFsIHJlcHJlc2VudGF0aW9uIG9mIGEgU2NhbGUuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlfSBzY2FsZQogICAgICAgICAqIEBwYXJhbSB7QXhpc09yaWVudGF0aW9ufSBvcmllbnRhdGlvbiBPcmllbnRhdGlvbiBvZiB0aGlzIEF4aXMuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gQXhpcyhzY2FsZSwgb3JpZW50YXRpb24pIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2VuZFRpY2tMZW5ndGggPSA1OwogICAgICAgICAgICBfdGhpcy5faW5uZXJUaWNrTGVuZ3RoID0gNTsKICAgICAgICAgICAgX3RoaXMuX3RpY2tMYWJlbFBhZGRpbmcgPSAxMDsKICAgICAgICAgICAgX3RoaXMuX21hcmdpbiA9IDE1OwogICAgICAgICAgICBfdGhpcy5fc2hvd0VuZFRpY2tMYWJlbHMgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuX2Fubm90YXRpb25zRW5hYmxlZCA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fYW5ub3RhdGlvblRpZXJDb3VudCA9IDE7CiAgICAgICAgICAgIGlmIChzY2FsZSA9PSBudWxsIHx8IG9yaWVudGF0aW9uID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiQXhpcyByZXF1aXJlcyBhIHNjYWxlIGFuZCBvcmllbnRhdGlvbiIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF90aGlzLl9zY2FsZSA9IHNjYWxlOwogICAgICAgICAgICBfdGhpcy5vcmllbnRhdGlvbihvcmllbnRhdGlvbik7CiAgICAgICAgICAgIF90aGlzLl9zZXREZWZhdWx0QWxpZ25tZW50KCk7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJheGlzIik7CiAgICAgICAgICAgIGlmIChfdGhpcy5pc0hvcml6b250YWwoKSkgewogICAgICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoIngtYXhpcyIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoInktYXhpcyIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF90aGlzLmZvcm1hdHRlcihmb3JtYXR0ZXJzLmlkZW50aXR5KCkpOwogICAgICAgICAgICBfdGhpcy5fcmVzY2FsZUNhbGxiYWNrID0gZnVuY3Rpb24gKG5ld1NjYWxlKSB7IHJldHVybiBfdGhpcy5fcmVzY2FsZSgpOyB9OwogICAgICAgICAgICBfdGhpcy5fc2NhbGUub25VcGRhdGUoX3RoaXMuX3Jlc2NhbGVDYWxsYmFjayk7CiAgICAgICAgICAgIF90aGlzLl9hbm5vdGF0ZWRUaWNrcyA9IFtdOwogICAgICAgICAgICBfdGhpcy5fYW5ub3RhdGlvbkZvcm1hdHRlciA9IGZvcm1hdHRlcnMuaWRlbnRpdHkoKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBBeGlzLnByb3RvdHlwZS5kZXN0cm95ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmRlc3Ryb3kuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fc2NhbGUub2ZmVXBkYXRlKHRoaXMuX3Jlc2NhbGVDYWxsYmFjayk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSB0aWNrIGxhYmVsIGRhdGEgb24gYSBlbGVtZW50LiBFbGVtZW50IGluIGFyZ3VtZW50IG11c3QgYmUgYSBkZXNjZW5kZW50IG9mIGEgdGljayBsYWJlbCBlbGVtZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgICAgICovCiAgICAgICAgQXhpcy5wcm90b3R5cGUudGlja0xhYmVsRGF0YU9uRWxlbWVudCA9IGZ1bmN0aW9uIChlbGVtZW50KSB7CiAgICAgICAgICAgIGlmIChlbGVtZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRpY2tMYWJlbDsKICAgICAgICAgICAgLy8gZ28gdXAgRE9NIHRyZWUgdG8gZmluZCB0aWNrIGxhYmVsIGVsZW1lbnQgaW4gYW5jZXN0b3IgZWxlbWVudHMKICAgICAgICAgICAgd2hpbGUgKChlbGVtZW50ICE9IG51bGwpICYmIChlbGVtZW50LmNsYXNzTGlzdCkgJiYgKHRpY2tMYWJlbCA9PT0gdW5kZWZpbmVkKSkgewogICAgICAgICAgICAgICAgaWYgKGVsZW1lbnQuY2xhc3NMaXN0LmNvbnRhaW5zKEF4aXMuVElDS19MQUJFTF9DTEFTUykpIHsKICAgICAgICAgICAgICAgICAgICB0aWNrTGFiZWwgPSBlbGVtZW50OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgZWxlbWVudCA9IGVsZW1lbnQucGFyZW50Tm9kZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZWxlbWVudCA9PT0gdW5kZWZpbmVkID8gdW5kZWZpbmVkIDogZDMuc2VsZWN0KGVsZW1lbnQpLmRhdHVtKCk7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fY29tcHV0ZVdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAvLyB0byBiZSBvdmVycmlkZGVuIGJ5IHN1YmNsYXNzIGxvZ2ljCiAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKTsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLl9jb21wdXRlSGVpZ2h0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAvLyB0byBiZSBvdmVycmlkZGVuIGJ5IHN1YmNsYXNzIGxvZ2ljCiAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKTsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLnJlcXVlc3RlZFNwYWNlID0gZnVuY3Rpb24gKG9mZmVyZWRXaWR0aCwgb2ZmZXJlZEhlaWdodCkgewogICAgICAgICAgICB2YXIgcmVxdWVzdGVkV2lkdGggPSAwOwogICAgICAgICAgICB2YXIgcmVxdWVzdGVkSGVpZ2h0ID0gMDsKICAgICAgICAgICAgaWYgKHRoaXMuaXNIb3Jpem9udGFsKCkpIHsKICAgICAgICAgICAgICAgIHJlcXVlc3RlZEhlaWdodCA9IHRoaXMuX2NvbXB1dGVIZWlnaHQoKSArIHRoaXMuX21hcmdpbjsKICAgICAgICAgICAgICAgIGlmICh0aGlzLmFubm90YXRpb25zRW5hYmxlZCgpKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHRpZXJIZWlnaHQgPSB0aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIubWVhc3VyZSgpLmhlaWdodCArIDIgKiBBeGlzLl9BTk5PVEFUSU9OX0xBQkVMX1BBRERJTkc7CiAgICAgICAgICAgICAgICAgICAgcmVxdWVzdGVkSGVpZ2h0ICs9IHRpZXJIZWlnaHQgKiB0aGlzLmFubm90YXRpb25UaWVyQ291bnQoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJlcXVlc3RlZFdpZHRoID0gdGhpcy5fY29tcHV0ZVdpZHRoKCkgKyB0aGlzLl9tYXJnaW47CiAgICAgICAgICAgICAgICBpZiAodGhpcy5hbm5vdGF0aW9uc0VuYWJsZWQoKSkgewogICAgICAgICAgICAgICAgICAgIHZhciB0aWVySGVpZ2h0ID0gdGhpcy5fYW5ub3RhdGlvbk1lYXN1cmVyLm1lYXN1cmUoKS5oZWlnaHQgKyAyICogQXhpcy5fQU5OT1RBVElPTl9MQUJFTF9QQURESU5HOwogICAgICAgICAgICAgICAgICAgIHJlcXVlc3RlZFdpZHRoICs9IHRpZXJIZWlnaHQgKiB0aGlzLmFubm90YXRpb25UaWVyQ291bnQoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbWluV2lkdGg6IHJlcXVlc3RlZFdpZHRoLAogICAgICAgICAgICAgICAgbWluSGVpZ2h0OiByZXF1ZXN0ZWRIZWlnaHQsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5maXhlZEhlaWdodCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaXNIb3Jpem9udGFsKCk7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5maXhlZFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gIXRoaXMuaXNIb3Jpem9udGFsKCk7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fcmVzY2FsZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgLy8gZGVmYXVsdCBpbXBsZW1lbnRhdGlvbjsgc3ViY2xhc3NlcyBtYXkgY2FsbCByZWRyYXcoKSBoZXJlCiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICBpZiAodGhpcy5pc0hvcml6b250YWwoKSkgewogICAgICAgICAgICAgICAgdGhpcy5fc2NhbGUucmFuZ2UoWzAsIHRoaXMud2lkdGgoKV0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fc2NhbGUucmFuZ2UoW3RoaXMuaGVpZ2h0KCksIDBdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLl9zaXplRnJvbU9mZmVyID0gZnVuY3Rpb24gKGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpIHsKICAgICAgICAgICAgdmFyIHJlcXVlc3RlZFNwYWNlID0gdGhpcy5yZXF1ZXN0ZWRTcGFjZShhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KTsKICAgICAgICAgICAgaWYgKHRoaXMuaXNIb3Jpem9udGFsKCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgd2lkdGg6IGF2YWlsYWJsZVdpZHRoLAogICAgICAgICAgICAgICAgICAgIC8vIGFsd2F5cyBrZWVwIHRoZSBoZWlnaHQgdG8gYmUgd2hhdCB3ZSByZXF1ZXN0OyBBeGVzIHRlbGwgdGhlIG91dHNpZGUgd2hhdCBoZWlnaHQgdGhleSBhcmUuCiAgICAgICAgICAgICAgICAgICAgLy8gdGhpcyBhbGxvd3MgYmx1ZXByaW50LWNoYXJ0IHRvIHB1dCB0aGUgQXhpcyBpbiBkb2N1bWVudCBmbG93IGJ5IHJlbW92aW5nIGFic29sdXRlIHBvc2l0aW9uaW5nCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0OiByZXF1ZXN0ZWRTcGFjZS5taW5IZWlnaHQsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBoZWlnaHQ6IGF2YWlsYWJsZUhlaWdodCwKICAgICAgICAgICAgICAgICAgICB3aWR0aDogcmVxdWVzdGVkU3BhY2UubWluV2lkdGgsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3RpY2tNYXJrQ29udGFpbmVyID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikKICAgICAgICAgICAgICAgIC5jbGFzc2VkKEF4aXMuVElDS19NQVJLX0NMQVNTICsgIi1jb250YWluZXIiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5fdGlja0xhYmVsQ29udGFpbmVyID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikKICAgICAgICAgICAgICAgIC5jbGFzc2VkKEF4aXMuVElDS19MQUJFTF9DTEFTUyArICItY29udGFpbmVyIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX2Jhc2VsaW5lID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJsaW5lIikuY2xhc3NlZCgiYmFzZWxpbmUiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvbkNvbnRhaW5lciA9IHRoaXMuY29udGVudCgpLmFwcGVuZCgiZyIpCiAgICAgICAgICAgICAgICAuY2xhc3NlZCgiYW5ub3RhdGlvbi1jb250YWluZXIiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvbkNvbnRhaW5lci5hcHBlbmQoImciKS5jbGFzc2VkKCJhbm5vdGF0aW9uLWxpbmUtY29udGFpbmVyIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25Db250YWluZXIuYXBwZW5kKCJnIikuY2xhc3NlZCgiYW5ub3RhdGlvbi1jaXJjbGUtY29udGFpbmVyIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25Db250YWluZXIuYXBwZW5kKCJnIikuY2xhc3NlZCgiYW5ub3RhdGlvbi1yZWN0LWNvbnRhaW5lciIsIHRydWUpOwogICAgICAgICAgICB2YXIgYW5ub3RhdGlvbkxhYmVsQ29udGFpbmVyID0gdGhpcy5fYW5ub3RhdGlvbkNvbnRhaW5lci5hcHBlbmQoImciKS5jbGFzc2VkKCJhbm5vdGF0aW9uLWxhYmVsLWNvbnRhaW5lciIsIHRydWUpOwogICAgICAgICAgICB2YXIgdHlwZXNldHRlckNvbnRleHQgPSBuZXcgc3JjJDEuU3ZnQ29udGV4dChhbm5vdGF0aW9uTGFiZWxDb250YWluZXIubm9kZSgpKTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvbk1lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIodHlwZXNldHRlckNvbnRleHQpOwogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uV3JpdGVyID0gbmV3IHNyYyQxLldyaXRlcih0aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIsIHR5cGVzZXR0ZXJDb250ZXh0KTsKICAgICAgICB9OwogICAgICAgIC8qCiAgICAgICAgICogRnVuY3Rpb24gZm9yIGdlbmVyYXRpbmcgdGljayB2YWx1ZXMgaW4gZGF0YS1zcGFjZSAoYXMgb3Bwb3NlZCB0byBwaXhlbCB2YWx1ZXMpLgogICAgICAgICAqIFRvIGJlIGltcGxlbWVudGVkIGJ5IHN1YmNsYXNzZXMuCiAgICAgICAgICovCiAgICAgICAgQXhpcy5wcm90b3R5cGUuX2dldFRpY2tWYWx1ZXMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbmRlciB0aWNrIG1hcmtzLCBiYXNlbGluZSwgYW5kIGFubm90YXRpb25zLiBTaG91bGQgYmUgc3VwZXIgY2FsbGVkIGJ5IHN1YmNsYXNzZXMgYW5kIHRoZW4gb3ZlcnJpZGRlbiB0byBkcmF3CiAgICAgICAgICogb3RoZXIgcmVsZXZhbnQgYXNwZWN0cyBvZiB0aGlzIEF4aXMuCiAgICAgICAgICovCiAgICAgICAgQXhpcy5wcm90b3R5cGUucmVuZGVySW1tZWRpYXRlbHkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciB0aWNrTWFya1ZhbHVlcyA9IHRoaXMuX2dldFRpY2tWYWx1ZXMoKTsKICAgICAgICAgICAgdmFyIHRpY2tNYXJrc1VwZGF0ZSA9IHRoaXMuX3RpY2tNYXJrQ29udGFpbmVyLnNlbGVjdEFsbCgiLiIgKyBBeGlzLlRJQ0tfTUFSS19DTEFTUykuZGF0YSh0aWNrTWFya1ZhbHVlcyk7CiAgICAgICAgICAgIHZhciB0aWNrTWFya3MgPSB0aWNrTWFya3NVcGRhdGUKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCJsaW5lIikKICAgICAgICAgICAgICAgIC5jbGFzc2VkKEF4aXMuVElDS19NQVJLX0NMQVNTLCB0cnVlKQogICAgICAgICAgICAgICAgLm1lcmdlKHRpY2tNYXJrc1VwZGF0ZSk7CiAgICAgICAgICAgIHRpY2tNYXJrcy5hdHRycyh0aGlzLl9nZW5lcmF0ZVRpY2tNYXJrQXR0ckhhc2goKSk7CiAgICAgICAgICAgIGQzLnNlbGVjdCh0aWNrTWFya3Mubm9kZXMoKVswXSkuY2xhc3NlZChBeGlzLkVORF9USUNLX01BUktfQ0xBU1MsIHRydWUpCiAgICAgICAgICAgICAgICAuYXR0cnModGhpcy5fZ2VuZXJhdGVUaWNrTWFya0F0dHJIYXNoKHRydWUpKTsKICAgICAgICAgICAgZDMuc2VsZWN0KHRpY2tNYXJrcy5ub2RlcygpW3RpY2tNYXJrVmFsdWVzLmxlbmd0aCAtIDFdKS5jbGFzc2VkKEF4aXMuRU5EX1RJQ0tfTUFSS19DTEFTUywgdHJ1ZSkKICAgICAgICAgICAgICAgIC5hdHRycyh0aGlzLl9nZW5lcmF0ZVRpY2tNYXJrQXR0ckhhc2godHJ1ZSkpOwogICAgICAgICAgICB0aWNrTWFya3NVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9iYXNlbGluZS5hdHRycyh0aGlzLl9nZW5lcmF0ZUJhc2VsaW5lQXR0ckhhc2goKSk7CiAgICAgICAgICAgIGlmICh0aGlzLmFubm90YXRpb25zRW5hYmxlZCgpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmF3QW5ub3RhdGlvbnMoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3JlbW92ZUFubm90YXRpb25zKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5hbm5vdGF0ZWRUaWNrcyA9IGZ1bmN0aW9uIChhbm5vdGF0ZWRUaWNrcykgewogICAgICAgICAgICBpZiAoYW5ub3RhdGVkVGlja3MgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Fubm90YXRlZFRpY2tzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRlZFRpY2tzID0gYW5ub3RhdGVkVGlja3M7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuYW5ub3RhdGlvbkZvcm1hdHRlciA9IGZ1bmN0aW9uIChhbm5vdGF0aW9uRm9ybWF0dGVyKSB7CiAgICAgICAgICAgIGlmIChhbm5vdGF0aW9uRm9ybWF0dGVyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9hbm5vdGF0aW9uRm9ybWF0dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25Gb3JtYXR0ZXIgPSBhbm5vdGF0aW9uRm9ybWF0dGVyOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLmFubm90YXRpb25zRW5hYmxlZCA9IGZ1bmN0aW9uIChhbm5vdGF0aW9uc0VuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKGFubm90YXRpb25zRW5hYmxlZCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5ub3RhdGlvbnNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25zRW5hYmxlZCA9IGFubm90YXRpb25zRW5hYmxlZDsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5hbm5vdGF0aW9uVGllckNvdW50ID0gZnVuY3Rpb24gKGFubm90YXRpb25UaWVyQ291bnQpIHsKICAgICAgICAgICAgaWYgKGFubm90YXRpb25UaWVyQ291bnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Fubm90YXRpb25UaWVyQ291bnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGFubm90YXRpb25UaWVyQ291bnQgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoImFubm90YXRpb25UaWVyQ291bnQgY2Fubm90IGJlIG5lZ2F0aXZlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvblRpZXJDb3VudCA9IGFubm90YXRpb25UaWVyQ291bnQ7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuX2RyYXdBbm5vdGF0aW9ucyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGxhYmVsUGFkZGluZyA9IEF4aXMuX0FOTk9UQVRJT05fTEFCRUxfUEFERElORzsKICAgICAgICAgICAgdmFyIG1lYXN1cmVtZW50cyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgICAgICB2YXIgYW5ub3RhdGVkVGlja3MgPSB0aGlzLl9hbm5vdGF0ZWRUaWNrc1RvUmVuZGVyKCk7CiAgICAgICAgICAgIGFubm90YXRlZFRpY2tzLmZvckVhY2goZnVuY3Rpb24gKGFubm90YXRlZFRpY2spIHsKICAgICAgICAgICAgICAgIHZhciBtZWFzdXJlbWVudCA9IF90aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIubWVhc3VyZShfdGhpcy5hbm5vdGF0aW9uRm9ybWF0dGVyKCkoYW5ub3RhdGVkVGljaykpOwogICAgICAgICAgICAgICAgdmFyIHBhZGRlZE1lYXN1cmVtZW50ID0gewogICAgICAgICAgICAgICAgICAgIHdpZHRoOiBtZWFzdXJlbWVudC53aWR0aCArIDIgKiBsYWJlbFBhZGRpbmcsCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0OiBtZWFzdXJlbWVudC5oZWlnaHQgKyAyICogbGFiZWxQYWRkaW5nLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIG1lYXN1cmVtZW50cy5zZXQoYW5ub3RhdGVkVGljaywgcGFkZGVkTWVhc3VyZW1lbnQpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIHRpZXJIZWlnaHQgPSB0aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIubWVhc3VyZSgpLmhlaWdodCArIDIgKiBsYWJlbFBhZGRpbmc7CiAgICAgICAgICAgIHZhciBhbm5vdGF0aW9uVG9UaWVyID0gdGhpcy5fYW5ub3RhdGlvblRvVGllcihtZWFzdXJlbWVudHMpOwogICAgICAgICAgICB2YXIgaGlkZGVuQW5ub3RhdGlvbnMgPSBuZXcgdXRpbHMkMS5TZXQoKTsKICAgICAgICAgICAgdmFyIGF4aXNIZWlnaHQgPSB0aGlzLmlzSG9yaXpvbnRhbCgpID8gdGhpcy5oZWlnaHQoKSA6IHRoaXMud2lkdGgoKTsKICAgICAgICAgICAgdmFyIGF4aXNIZWlnaHRXaXRob3V0TWFyZ2luQW5kQW5ub3RhdGlvbnMgPSB0aGlzLl9jb3JlU2l6ZSgpOwogICAgICAgICAgICB2YXIgbnVtVGllcnMgPSBNYXRoLm1pbih0aGlzLmFubm90YXRpb25UaWVyQ291bnQoKSwgTWF0aC5mbG9vcigoYXhpc0hlaWdodCAtIGF4aXNIZWlnaHRXaXRob3V0TWFyZ2luQW5kQW5ub3RhdGlvbnMpIC8gdGllckhlaWdodCkpOwogICAgICAgICAgICBhbm5vdGF0aW9uVG9UaWVyLmZvckVhY2goZnVuY3Rpb24gKHRpZXIsIGFubm90YXRpb24pIHsKICAgICAgICAgICAgICAgIGlmICh0aWVyID09PSAtMSB8fCB0aWVyID49IG51bVRpZXJzKSB7CiAgICAgICAgICAgICAgICAgICAgaGlkZGVuQW5ub3RhdGlvbnMuYWRkKGFubm90YXRpb24pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIGJpbmRFbGVtZW50cyA9IGZ1bmN0aW9uIChzZWxlY3Rpb24sIGVsZW1lbnROYW1lLCBjbGFzc05hbWUpIHsKICAgICAgICAgICAgICAgIHZhciBlbGVtZW50c1VwZGF0ZSA9IHNlbGVjdGlvbi5zZWxlY3RBbGwoIi4iICsgY2xhc3NOYW1lKS5kYXRhKGFubm90YXRlZFRpY2tzKTsKICAgICAgICAgICAgICAgIHZhciBlbGVtZW50cyA9IGVsZW1lbnRzVXBkYXRlCiAgICAgICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgICAgICAuYXBwZW5kKGVsZW1lbnROYW1lKQogICAgICAgICAgICAgICAgICAgIC5jbGFzc2VkKGNsYXNzTmFtZSwgdHJ1ZSkKICAgICAgICAgICAgICAgICAgICAubWVyZ2UoZWxlbWVudHNVcGRhdGUpOwogICAgICAgICAgICAgICAgZWxlbWVudHNVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICAgICAgcmV0dXJuIGVsZW1lbnRzOwogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgb2Zmc2V0RiA9IGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICBzd2l0Y2ggKF90aGlzLm9yaWVudGF0aW9uKCkpIHsKICAgICAgICAgICAgICAgICAgICBjYXNlICJib3R0b20iOgogICAgICAgICAgICAgICAgICAgIGNhc2UgInJpZ2h0IjoKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGFubm90YXRpb25Ub1RpZXIuZ2V0KGQpICogdGllckhlaWdodCArIGF4aXNIZWlnaHRXaXRob3V0TWFyZ2luQW5kQW5ub3RhdGlvbnM7CiAgICAgICAgICAgICAgICAgICAgY2FzZSAidG9wIjoKICAgICAgICAgICAgICAgICAgICBjYXNlICJsZWZ0IjoKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGF4aXNIZWlnaHQgLSBheGlzSGVpZ2h0V2l0aG91dE1hcmdpbkFuZEFubm90YXRpb25zIC0gYW5ub3RhdGlvblRvVGllci5nZXQoZCkgKiB0aWVySGVpZ2h0OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgcG9zaXRpb25GID0gZnVuY3Rpb24gKGQpIHsgcmV0dXJuIF90aGlzLl9zY2FsZS5zY2FsZShkKTsgfTsKICAgICAgICAgICAgdmFyIHZpc2liaWxpdHlGID0gZnVuY3Rpb24gKGQpIHsgcmV0dXJuIGhpZGRlbkFubm90YXRpb25zLmhhcyhkKSA/ICJoaWRkZW4iIDogInZpc2libGUiOyB9OwogICAgICAgICAgICB2YXIgc2Vjb25kYXJ5UG9zaXRpb247CiAgICAgICAgICAgIHN3aXRjaCAodGhpcy5vcmllbnRhdGlvbigpKSB7CiAgICAgICAgICAgICAgICBjYXNlICJib3R0b20iOgogICAgICAgICAgICAgICAgY2FzZSAicmlnaHQiOgogICAgICAgICAgICAgICAgICAgIHNlY29uZGFyeVBvc2l0aW9uID0gMDsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgInRvcCI6CiAgICAgICAgICAgICAgICAgICAgc2Vjb25kYXJ5UG9zaXRpb24gPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAibGVmdCI6CiAgICAgICAgICAgICAgICAgICAgc2Vjb25kYXJ5UG9zaXRpb24gPSB0aGlzLndpZHRoKCk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGlzSG9yaXpvbnRhbCA9IHRoaXMuaXNIb3Jpem9udGFsKCk7CiAgICAgICAgICAgIGJpbmRFbGVtZW50cyh0aGlzLl9hbm5vdGF0aW9uQ29udGFpbmVyLnNlbGVjdCgiLmFubm90YXRpb24tbGluZS1jb250YWluZXIiKSwgImxpbmUiLCBBeGlzLkFOTk9UQVRJT05fTElORV9DTEFTUykKICAgICAgICAgICAgICAgIC5hdHRycyh7CiAgICAgICAgICAgICAgICB4MTogaXNIb3Jpem9udGFsID8gcG9zaXRpb25GIDogc2Vjb25kYXJ5UG9zaXRpb24sCiAgICAgICAgICAgICAgICB4MjogaXNIb3Jpem9udGFsID8gcG9zaXRpb25GIDogb2Zmc2V0RiwKICAgICAgICAgICAgICAgIHkxOiBpc0hvcml6b250YWwgPyBzZWNvbmRhcnlQb3NpdGlvbiA6IHBvc2l0aW9uRiwKICAgICAgICAgICAgICAgIHkyOiBpc0hvcml6b250YWwgPyBvZmZzZXRGIDogcG9zaXRpb25GLAogICAgICAgICAgICAgICAgdmlzaWJpbGl0eTogdmlzaWJpbGl0eUYsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBiaW5kRWxlbWVudHModGhpcy5fYW5ub3RhdGlvbkNvbnRhaW5lci5zZWxlY3QoIi5hbm5vdGF0aW9uLWNpcmNsZS1jb250YWluZXIiKSwgImNpcmNsZSIsIEF4aXMuQU5OT1RBVElPTl9DSVJDTEVfQ0xBU1MpCiAgICAgICAgICAgICAgICAuYXR0cnMoewogICAgICAgICAgICAgICAgY3g6IGlzSG9yaXpvbnRhbCA/IHBvc2l0aW9uRiA6IHNlY29uZGFyeVBvc2l0aW9uLAogICAgICAgICAgICAgICAgY3k6IGlzSG9yaXpvbnRhbCA/IHNlY29uZGFyeVBvc2l0aW9uIDogcG9zaXRpb25GLAogICAgICAgICAgICAgICAgcjogMywKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciByZWN0YW5nbGVPZmZzZXRGID0gZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHN3aXRjaCAoX3RoaXMub3JpZW50YXRpb24oKSkgewogICAgICAgICAgICAgICAgICAgIGNhc2UgImJvdHRvbSI6CiAgICAgICAgICAgICAgICAgICAgY2FzZSAicmlnaHQiOgogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gb2Zmc2V0RihkKTsKICAgICAgICAgICAgICAgICAgICBjYXNlICJ0b3AiOgogICAgICAgICAgICAgICAgICAgIGNhc2UgImxlZnQiOgogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gb2Zmc2V0RihkKSAtIG1lYXN1cmVtZW50cy5nZXQoZCkuaGVpZ2h0OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBiaW5kRWxlbWVudHModGhpcy5fYW5ub3RhdGlvbkNvbnRhaW5lci5zZWxlY3QoIi5hbm5vdGF0aW9uLXJlY3QtY29udGFpbmVyIiksICJyZWN0IiwgQXhpcy5BTk5PVEFUSU9OX1JFQ1RfQ0xBU1MpCiAgICAgICAgICAgICAgICAuYXR0cnMoewogICAgICAgICAgICAgICAgeDogaXNIb3Jpem9udGFsID8gcG9zaXRpb25GIDogcmVjdGFuZ2xlT2Zmc2V0RiwKICAgICAgICAgICAgICAgIHk6IGlzSG9yaXpvbnRhbCA/IHJlY3RhbmdsZU9mZnNldEYgOiBwb3NpdGlvbkYsCiAgICAgICAgICAgICAgICB3aWR0aDogaXNIb3Jpem9udGFsID8gZnVuY3Rpb24gKGQpIHsgcmV0dXJuIG1lYXN1cmVtZW50cy5nZXQoZCkud2lkdGg7IH0gOiBmdW5jdGlvbiAoZCkgeyByZXR1cm4gbWVhc3VyZW1lbnRzLmdldChkKS5oZWlnaHQ7IH0sCiAgICAgICAgICAgICAgICBoZWlnaHQ6IGlzSG9yaXpvbnRhbCA/IGZ1bmN0aW9uIChkKSB7IHJldHVybiBtZWFzdXJlbWVudHMuZ2V0KGQpLmhlaWdodDsgfSA6IGZ1bmN0aW9uIChkKSB7IHJldHVybiBtZWFzdXJlbWVudHMuZ2V0KGQpLndpZHRoOyB9LAogICAgICAgICAgICAgICAgdmlzaWJpbGl0eTogdmlzaWJpbGl0eUYsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgYW5ub3RhdGlvbldyaXRlciA9IHRoaXMuX2Fubm90YXRpb25Xcml0ZXI7CiAgICAgICAgICAgIHZhciBhbm5vdGF0aW9uRm9ybWF0dGVyID0gdGhpcy5hbm5vdGF0aW9uRm9ybWF0dGVyKCk7CiAgICAgICAgICAgIHZhciBhbm5vdGF0aW9uTGFiZWxzID0gYmluZEVsZW1lbnRzKHRoaXMuX2Fubm90YXRpb25Db250YWluZXIuc2VsZWN0KCIuYW5ub3RhdGlvbi1sYWJlbC1jb250YWluZXIiKSwgImciLCBBeGlzLkFOTk9UQVRJT05fTEFCRUxfQ0xBU1MpOwogICAgICAgICAgICBhbm5vdGF0aW9uTGFiZWxzLnNlbGVjdEFsbCgiLnRleHQtY29udGFpbmVyIikucmVtb3ZlKCk7CiAgICAgICAgICAgIGFubm90YXRpb25MYWJlbHMuYXR0cnMoewogICAgICAgICAgICAgICAgdHJhbnNmb3JtOiBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHZhciB4VHJhbnNsYXRlID0gaXNIb3Jpem9udGFsID8gcG9zaXRpb25GKGQpIDogcmVjdGFuZ2xlT2Zmc2V0RihkKTsKICAgICAgICAgICAgICAgICAgICB2YXIgeVRyYW5zbGF0ZSA9IGlzSG9yaXpvbnRhbCA/IHJlY3RhbmdsZU9mZnNldEYoZCkgOiBwb3NpdGlvbkYoZCk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICJ0cmFuc2xhdGUoIiArIHhUcmFuc2xhdGUgKyAiLCIgKyB5VHJhbnNsYXRlICsgIikiOwogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIHZpc2liaWxpdHk6IHZpc2liaWxpdHlGLAogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKGFubm90YXRpb25MYWJlbCkgewogICAgICAgICAgICAgICAgYW5ub3RhdGlvbldyaXRlci53cml0ZShhbm5vdGF0aW9uRm9ybWF0dGVyKGFubm90YXRpb25MYWJlbCksIGlzSG9yaXpvbnRhbCA/IG1lYXN1cmVtZW50cy5nZXQoYW5ub3RhdGlvbkxhYmVsKS53aWR0aCA6IG1lYXN1cmVtZW50cy5nZXQoYW5ub3RhdGlvbkxhYmVsKS5oZWlnaHQsIGlzSG9yaXpvbnRhbCA/IG1lYXN1cmVtZW50cy5nZXQoYW5ub3RhdGlvbkxhYmVsKS5oZWlnaHQgOiBtZWFzdXJlbWVudHMuZ2V0KGFubm90YXRpb25MYWJlbCkud2lkdGgsIHsKICAgICAgICAgICAgICAgICAgICB4QWxpZ246ICJjZW50ZXIiLAogICAgICAgICAgICAgICAgICAgIHlBbGlnbjogImNlbnRlciIsCiAgICAgICAgICAgICAgICAgICAgdGV4dFJvdGF0aW9uOiBpc0hvcml6b250YWwgPyAwIDogOTAsCiAgICAgICAgICAgICAgICB9LCBkMy5zZWxlY3QodGhpcykubm9kZSgpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fYW5ub3RhdGVkVGlja3NUb1JlbmRlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHNjYWxlUmFuZ2UgPSB0aGlzLl9zY2FsZS5yYW5nZSgpOwogICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5BcnJheS51bmlxKHRoaXMuYW5ub3RhdGVkVGlja3MoKS5maWx0ZXIoZnVuY3Rpb24gKHRpY2spIHsKICAgICAgICAgICAgICAgIGlmICh0aWNrID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5NYXRoLmluUmFuZ2UoX3RoaXMuX3NjYWxlLnNjYWxlKHRpY2spLCBzY2FsZVJhbmdlWzBdLCBzY2FsZVJhbmdlWzFdKTsKICAgICAgICAgICAgfSkpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0cmlldmVzIHRoZSBzaXplIG9mIHRoZSBjb3JlIHBpZWNlcy4KICAgICAgICAgKgogICAgICAgICAqIFRoZSBjb3JlIHBpZWNlcyBpbmNsdWRlIHRoZSBsYWJlbHMsIHRoZSBlbmQgdGljayBtYXJrcywgdGhlIGlubmVyIHRpY2sgbWFya3MsIGFuZCB0aGUgdGljayBsYWJlbCBwYWRkaW5nLgogICAgICAgICAqLwogICAgICAgIEF4aXMucHJvdG90eXBlLl9jb3JlU2l6ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHJlbGV2YW50RGltZW5zaW9uID0gdGhpcy5pc0hvcml6b250YWwoKSA/IHRoaXMuaGVpZ2h0KCkgOiB0aGlzLndpZHRoKCk7CiAgICAgICAgICAgIHZhciBheGlzSGVpZ2h0V2l0aG91dE1hcmdpbiA9IHRoaXMuaXNIb3Jpem9udGFsKCkgPyB0aGlzLl9jb21wdXRlSGVpZ2h0KCkgOiB0aGlzLl9jb21wdXRlV2lkdGgoKTsKICAgICAgICAgICAgcmV0dXJuIE1hdGgubWluKGF4aXNIZWlnaHRXaXRob3V0TWFyZ2luLCByZWxldmFudERpbWVuc2lvbik7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fYW5ub3RhdGlvblRpZXJIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIubWVhc3VyZSgpLmhlaWdodCArIDIgKiBBeGlzLl9BTk5PVEFUSU9OX0xBQkVMX1BBRERJTkc7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5fYW5ub3RhdGlvblRvVGllciA9IGZ1bmN0aW9uIChtZWFzdXJlbWVudHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGFubm90YXRpb25UaWVycyA9IFtbXV07CiAgICAgICAgICAgIHZhciBhbm5vdGF0aW9uVG9UaWVyID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHZhciBkaW1lbnNpb24gPSB0aGlzLmlzSG9yaXpvbnRhbCgpID8gdGhpcy53aWR0aCgpIDogdGhpcy5oZWlnaHQoKTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGVkVGlja3NUb1JlbmRlcigpLmZvckVhY2goZnVuY3Rpb24gKGFubm90YXRlZFRpY2spIHsKICAgICAgICAgICAgICAgIHZhciBwb3NpdGlvbiA9IF90aGlzLl9zY2FsZS5zY2FsZShhbm5vdGF0ZWRUaWNrKTsKICAgICAgICAgICAgICAgIHZhciBsZW5ndGggPSBtZWFzdXJlbWVudHMuZ2V0KGFubm90YXRlZFRpY2spLndpZHRoOwogICAgICAgICAgICAgICAgaWYgKHBvc2l0aW9uIDwgMCB8fCBwb3NpdGlvbiArIGxlbmd0aCA+IGRpbWVuc2lvbikgewogICAgICAgICAgICAgICAgICAgIGFubm90YXRpb25Ub1RpZXIuc2V0KGFubm90YXRlZFRpY2ssIC0xKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgdGllckhhc0NvbGxpc2lvbiA9IGZ1bmN0aW9uICh0ZXN0VGllcikgeyByZXR1cm4gYW5ub3RhdGlvblRpZXJzW3Rlc3RUaWVyXS5zb21lKGZ1bmN0aW9uICh0ZXN0VGljaykgewogICAgICAgICAgICAgICAgICAgIHZhciB0ZXN0UG9zaXRpb24gPSBfdGhpcy5fc2NhbGUuc2NhbGUodGVzdFRpY2spOwogICAgICAgICAgICAgICAgICAgIHZhciB0ZXN0TGVuZ3RoID0gbWVhc3VyZW1lbnRzLmdldCh0ZXN0VGljaykud2lkdGg7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHBvc2l0aW9uICsgbGVuZ3RoID49IHRlc3RQb3NpdGlvbiAmJiBwb3NpdGlvbiA8PSB0ZXN0UG9zaXRpb24gKyB0ZXN0TGVuZ3RoOwogICAgICAgICAgICAgICAgfSk7IH07CiAgICAgICAgICAgICAgICB2YXIgdGllciA9IDA7CiAgICAgICAgICAgICAgICB3aGlsZSAodGllckhhc0NvbGxpc2lvbih0aWVyKSkgewogICAgICAgICAgICAgICAgICAgIHRpZXIrKzsKICAgICAgICAgICAgICAgICAgICBpZiAoYW5ub3RhdGlvblRpZXJzLmxlbmd0aCA9PT0gdGllcikgewogICAgICAgICAgICAgICAgICAgICAgICBhbm5vdGF0aW9uVGllcnMucHVzaChbXSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgYW5ub3RhdGlvblRpZXJzW3RpZXJdLnB1c2goYW5ub3RhdGVkVGljayk7CiAgICAgICAgICAgICAgICBhbm5vdGF0aW9uVG9UaWVyLnNldChhbm5vdGF0ZWRUaWNrLCB0aWVyKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBhbm5vdGF0aW9uVG9UaWVyOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuX3JlbW92ZUFubm90YXRpb25zID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uQ29udGFpbmVyLnNlbGVjdEFsbCgiLmFubm90YXRpb24tbGluZSIpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uQ29udGFpbmVyLnNlbGVjdEFsbCgiLmFubm90YXRpb24tY2lyY2xlIikucmVtb3ZlKCk7CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25Db250YWluZXIuc2VsZWN0QWxsKCIuYW5ub3RhdGlvbi1yZWN0IikucmVtb3ZlKCk7CiAgICAgICAgICAgIHRoaXMuX2Fubm90YXRpb25Db250YWluZXIuc2VsZWN0QWxsKCIuYW5ub3RhdGlvbi1sYWJlbCIpLnJlbW92ZSgpOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuX2dlbmVyYXRlQmFzZWxpbmVBdHRySGFzaCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGJhc2VsaW5lQXR0ckhhc2ggPSB7CiAgICAgICAgICAgICAgICB4MTogMCwKICAgICAgICAgICAgICAgIHkxOiAwLAogICAgICAgICAgICAgICAgeDI6IDAsCiAgICAgICAgICAgICAgICB5MjogMCwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgc3dpdGNoICh0aGlzLl9vcmllbnRhdGlvbikgewogICAgICAgICAgICAgICAgY2FzZSAiYm90dG9tIjoKICAgICAgICAgICAgICAgICAgICBiYXNlbGluZUF0dHJIYXNoWyJ4MiJdID0gdGhpcy53aWR0aCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAidG9wIjoKICAgICAgICAgICAgICAgICAgICBiYXNlbGluZUF0dHJIYXNoWyJ4MiJdID0gdGhpcy53aWR0aCgpOwogICAgICAgICAgICAgICAgICAgIGJhc2VsaW5lQXR0ckhhc2hbInkxIl0gPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICAgICAgICAgIGJhc2VsaW5lQXR0ckhhc2hbInkyIl0gPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAibGVmdCI6CiAgICAgICAgICAgICAgICAgICAgYmFzZWxpbmVBdHRySGFzaFsieDEiXSA9IHRoaXMud2lkdGgoKTsKICAgICAgICAgICAgICAgICAgICBiYXNlbGluZUF0dHJIYXNoWyJ4MiJdID0gdGhpcy53aWR0aCgpOwogICAgICAgICAgICAgICAgICAgIGJhc2VsaW5lQXR0ckhhc2hbInkyIl0gPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAicmlnaHQiOgogICAgICAgICAgICAgICAgICAgIGJhc2VsaW5lQXR0ckhhc2hbInkyIl0gPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBiYXNlbGluZUF0dHJIYXNoOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuX2dlbmVyYXRlVGlja01hcmtBdHRySGFzaCA9IGZ1bmN0aW9uIChpc0VuZFRpY2tNYXJrKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmIChpc0VuZFRpY2tNYXJrID09PSB2b2lkIDApIHsgaXNFbmRUaWNrTWFyayA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciB0aWNrTWFya0F0dHJIYXNoID0gewogICAgICAgICAgICAgICAgeDE6IDAsCiAgICAgICAgICAgICAgICB5MTogMCwKICAgICAgICAgICAgICAgIHgyOiAwLAogICAgICAgICAgICAgICAgeTI6IDAsCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBzY2FsaW5nRnVuY3Rpb24gPSBmdW5jdGlvbiAoZCkgeyByZXR1cm4gX3RoaXMuX3NjYWxlLnNjYWxlKGQpOyB9OwogICAgICAgICAgICBpZiAodGhpcy5pc0hvcml6b250YWwoKSkgewogICAgICAgICAgICAgICAgdGlja01hcmtBdHRySGFzaFsieDEiXSA9IHNjYWxpbmdGdW5jdGlvbjsKICAgICAgICAgICAgICAgIHRpY2tNYXJrQXR0ckhhc2hbIngyIl0gPSBzY2FsaW5nRnVuY3Rpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aWNrTWFya0F0dHJIYXNoWyJ5MSJdID0gc2NhbGluZ0Z1bmN0aW9uOwogICAgICAgICAgICAgICAgdGlja01hcmtBdHRySGFzaFsieTIiXSA9IHNjYWxpbmdGdW5jdGlvbjsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgdGlja0xlbmd0aCA9IGlzRW5kVGlja01hcmsgPyB0aGlzLl9lbmRUaWNrTGVuZ3RoIDogdGhpcy5faW5uZXJUaWNrTGVuZ3RoOwogICAgICAgICAgICBzd2l0Y2ggKHRoaXMuX29yaWVudGF0aW9uKSB7CiAgICAgICAgICAgICAgICBjYXNlICJib3R0b20iOgogICAgICAgICAgICAgICAgICAgIHRpY2tNYXJrQXR0ckhhc2hbInkyIl0gPSB0aWNrTGVuZ3RoOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAidG9wIjoKICAgICAgICAgICAgICAgICAgICB0aWNrTWFya0F0dHJIYXNoWyJ5MSJdID0gdGhpcy5oZWlnaHQoKTsKICAgICAgICAgICAgICAgICAgICB0aWNrTWFya0F0dHJIYXNoWyJ5MiJdID0gdGhpcy5oZWlnaHQoKSAtIHRpY2tMZW5ndGg7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlICJsZWZ0IjoKICAgICAgICAgICAgICAgICAgICB0aWNrTWFya0F0dHJIYXNoWyJ4MSJdID0gdGhpcy53aWR0aCgpOwogICAgICAgICAgICAgICAgICAgIHRpY2tNYXJrQXR0ckhhc2hbIngyIl0gPSB0aGlzLndpZHRoKCkgLSB0aWNrTGVuZ3RoOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAicmlnaHQiOgogICAgICAgICAgICAgICAgICAgIHRpY2tNYXJrQXR0ckhhc2hbIngyIl0gPSB0aWNrTGVuZ3RoOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aWNrTWFya0F0dHJIYXNoOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuX3NldERlZmF1bHRBbGlnbm1lbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHN3aXRjaCAodGhpcy5fb3JpZW50YXRpb24pIHsKICAgICAgICAgICAgICAgIGNhc2UgImJvdHRvbSI6CiAgICAgICAgICAgICAgICAgICAgdGhpcy55QWxpZ25tZW50KCJ0b3AiKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgInRvcCI6CiAgICAgICAgICAgICAgICAgICAgdGhpcy55QWxpZ25tZW50KCJib3R0b20iKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgImxlZnQiOgogICAgICAgICAgICAgICAgICAgIHRoaXMueEFsaWdubWVudCgicmlnaHQiKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgInJpZ2h0IjoKICAgICAgICAgICAgICAgICAgICB0aGlzLnhBbGlnbm1lbnQoImxlZnQiKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0IHdoZXRoZXIgdGhpcyBheGlzIGlzIGhvcml6b250YWwgKG9yaWVudGF0aW9uIGlzICJ0b3AiIG9yICJib3R0b20iKSBvciB2ZXJ0aWNhbC4KICAgICAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gLSB0cnVlIGZvciBob3Jpem9udGFsLCBmYWxzZSBmb3IgdmVydGljYWwuCiAgICAgICAgICovCiAgICAgICAgQXhpcy5wcm90b3R5cGUuaXNIb3Jpem9udGFsID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fb3JpZW50YXRpb24gPT09ICJ0b3AiIHx8IHRoaXMuX29yaWVudGF0aW9uID09PSAiYm90dG9tIjsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldCB0aGUgc2NhbGUgdGhhdCB0aGlzIGF4aXMgaXMgYXNzb2NpYXRlZCB3aXRoLgogICAgICAgICAqIEByZXR1cm5zIHtTY2FsZTxELCBudW1iZXI+fQogICAgICAgICAqLwogICAgICAgIEF4aXMucHJvdG90eXBlLmdldFNjYWxlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc2NhbGU7CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5mb3JtYXR0ZXIgPSBmdW5jdGlvbiAoZm9ybWF0dGVyKSB7CiAgICAgICAgICAgIGlmIChmb3JtYXR0ZXIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Zvcm1hdHRlcjsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9mb3JtYXR0ZXIgPSBmb3JtYXR0ZXI7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuaW5uZXJUaWNrTGVuZ3RoID0gZnVuY3Rpb24gKGxlbmd0aCkgewogICAgICAgICAgICBpZiAobGVuZ3RoID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9pbm5lclRpY2tMZW5ndGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBpZiAobGVuZ3RoIDwgMCkgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiaW5uZXIgdGljayBsZW5ndGggbXVzdCBiZSBwb3NpdGl2ZSIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5faW5uZXJUaWNrTGVuZ3RoID0gbGVuZ3RoOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5lbmRUaWNrTGVuZ3RoID0gZnVuY3Rpb24gKGxlbmd0aCkgewogICAgICAgICAgICBpZiAobGVuZ3RoID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9lbmRUaWNrTGVuZ3RoOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgaWYgKGxlbmd0aCA8IDApIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoImVuZCB0aWNrIGxlbmd0aCBtdXN0IGJlIHBvc2l0aXZlIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9lbmRUaWNrTGVuZ3RoID0gbGVuZ3RoOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBtYXhpbXVtIHBpeGVsIGxlbmd0aCBvdmVyIGFsbCB0aWNrcyBvbiB0aGlzIGF4aXMuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0KICAgICAgICAgKi8KICAgICAgICBBeGlzLnByb3RvdHlwZS5fbWF4TGFiZWxUaWNrTGVuZ3RoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5zaG93RW5kVGlja0xhYmVscygpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5tYXgodGhpcy5pbm5lclRpY2tMZW5ndGgoKSwgdGhpcy5lbmRUaWNrTGVuZ3RoKCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW5uZXJUaWNrTGVuZ3RoKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLnRpY2tMYWJlbFBhZGRpbmcgPSBmdW5jdGlvbiAocGFkZGluZykgewogICAgICAgICAgICBpZiAocGFkZGluZyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fdGlja0xhYmVsUGFkZGluZzsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGlmIChwYWRkaW5nIDwgMCkgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigidGljayBsYWJlbCBwYWRkaW5nIG11c3QgYmUgcG9zaXRpdmUiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3RpY2tMYWJlbFBhZGRpbmcgPSBwYWRkaW5nOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5tYXJnaW4gPSBmdW5jdGlvbiAoc2l6ZSkgewogICAgICAgICAgICBpZiAoc2l6ZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWFyZ2luOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgaWYgKHNpemUgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJtYXJnaW4gc2l6ZSBtdXN0IGJlIHBvc2l0aXZlIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9tYXJnaW4gPSBzaXplOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBBeGlzLnByb3RvdHlwZS5vcmllbnRhdGlvbiA9IGZ1bmN0aW9uIChvcmllbnRhdGlvbikgewogICAgICAgICAgICBpZiAob3JpZW50YXRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX29yaWVudGF0aW9uOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgLy8gZW5zdXJlIGJhY2t3YXJkcyBjb21wYXRpYmlsaXR5IGZvciBvbGRlciB2ZXJzaW9ucyB0aGF0IHN1cHBseSBvcmllbnRhdGlvbiBpbiBkaWZmZXJlbnQgY2FzZXMKICAgICAgICAgICAgICAgIHZhciBuZXdPcmllbnRhdGlvbkxDID0gb3JpZW50YXRpb24udG9Mb3dlckNhc2UoKTsKICAgICAgICAgICAgICAgIGlmIChuZXdPcmllbnRhdGlvbkxDICE9PSAidG9wIiAmJgogICAgICAgICAgICAgICAgICAgIG5ld09yaWVudGF0aW9uTEMgIT09ICJib3R0b20iICYmCiAgICAgICAgICAgICAgICAgICAgbmV3T3JpZW50YXRpb25MQyAhPT0gImxlZnQiICYmCiAgICAgICAgICAgICAgICAgICAgbmV3T3JpZW50YXRpb25MQyAhPT0gInJpZ2h0IikgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigidW5zdXBwb3J0ZWQgb3JpZW50YXRpb24iKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX29yaWVudGF0aW9uID0gbmV3T3JpZW50YXRpb25MQzsKICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuc2hvd0VuZFRpY2tMYWJlbHMgPSBmdW5jdGlvbiAoc2hvdykgewogICAgICAgICAgICBpZiAoc2hvdyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fc2hvd0VuZFRpY2tMYWJlbHM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fc2hvd0VuZFRpY2tMYWJlbHMgPSBzaG93OwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLl9zaG93QWxsVGlja01hcmtzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl90aWNrTWFya0NvbnRhaW5lci5zZWxlY3RBbGwoIi4iICsgQXhpcy5USUNLX01BUktfQ0xBU1MpCiAgICAgICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBkMy5zZWxlY3QodGhpcykuc3R5bGUoInZpc2liaWxpdHkiLCAiaW5oZXJpdCIpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIEF4aXMucHJvdG90eXBlLl9zaG93QWxsVGlja0xhYmVscyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLnNlbGVjdEFsbCgiLiIgKyBBeGlzLlRJQ0tfTEFCRUxfQ0xBU1MpCiAgICAgICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBkMy5zZWxlY3QodGhpcykuc3R5bGUoInZpc2liaWxpdHkiLCAiaW5oZXJpdCIpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlc3BvbnNpYmxlIGZvciBoaWRpbmcgYW55IHRpY2sgbGFiZWxzIHRoYXQgYnJlYWsgb3V0IG9mIHRoZSBib3VuZGluZwogICAgICAgICAqIGNvbnRhaW5lci4KICAgICAgICAgKi8KICAgICAgICBBeGlzLnByb3RvdHlwZS5faGlkZU92ZXJmbG93aW5nVGlja0xhYmVscyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGJvdW5kaW5nQm94ID0gdGhpcy5lbGVtZW50KCkubm9kZSgpLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgICAgICB2YXIgdGlja0xhYmVscyA9IHRoaXMuX3RpY2tMYWJlbENvbnRhaW5lci5zZWxlY3RBbGwoIi4iICsgQXhpcy5USUNLX0xBQkVMX0NMQVNTKTsKICAgICAgICAgICAgaWYgKHRpY2tMYWJlbHMuZW1wdHkoKSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRpY2tMYWJlbHMuZWFjaChmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgaWYgKCF1dGlscyQxLkRPTS5jbGllbnRSZWN0SW5zaWRlKHRoaXMuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCksIGJvdW5kaW5nQm94KSkgewogICAgICAgICAgICAgICAgICAgIGQzLnNlbGVjdCh0aGlzKS5zdHlsZSgidmlzaWJpbGl0eSIsICJoaWRkZW4iKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBIaWRlcyB0aGUgVGljayBNYXJrcyB3aGljaCBoYXZlIG5vIGNvcnJlc3BvbmRpbmcgVGljayBMYWJlbHMKICAgICAgICAgKi8KICAgICAgICBBeGlzLnByb3RvdHlwZS5faGlkZVRpY2tNYXJrc1dpdGhvdXRMYWJlbCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHZpc2libGVUaWNrTWFya3MgPSB0aGlzLl90aWNrTWFya0NvbnRhaW5lci5zZWxlY3RBbGwoIi4iICsgQXhpcy5USUNLX01BUktfQ0xBU1MpOwogICAgICAgICAgICB2YXIgdmlzaWJsZVRpY2tMYWJlbHMgPSB0aGlzLl90aWNrTGFiZWxDb250YWluZXIKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoIi4iICsgQXhpcy5USUNLX0xBQkVMX0NMQVNTKQogICAgICAgICAgICAgICAgLmZpbHRlcihmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgdmFyIHZpc2liaWxpdHkgPSBkMy5zZWxlY3QodGhpcykuc3R5bGUoInZpc2liaWxpdHkiKTsKICAgICAgICAgICAgICAgIHJldHVybiAodmlzaWJpbGl0eSA9PT0gImluaGVyaXQiKSB8fCAodmlzaWJpbGl0eSA9PT0gInZpc2libGUiKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciBsYWJlbE51bWJlcnNTaG93biA9IHZpc2libGVUaWNrTGFiZWxzLmRhdGEoKTsKICAgICAgICAgICAgdmlzaWJsZVRpY2tNYXJrcy5lYWNoKGZ1bmN0aW9uIChlLCBpKSB7CiAgICAgICAgICAgICAgICBpZiAobGFiZWxOdW1iZXJzU2hvd24uaW5kZXhPZihlKSA9PT0gLTEpIHsKICAgICAgICAgICAgICAgICAgICBkMy5zZWxlY3QodGhpcykuc3R5bGUoInZpc2liaWxpdHkiLCAiaGlkZGVuIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgQXhpcy5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uTWVhc3VyZXIucmVzZXQoKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byBlYWNoIGVuZCB0aWNrIG1hcmsgKHRoZSBsaW5lIG9uIHRoZSBlbmQgdGljaykuCiAgICAgICAgICovCiAgICAgICAgQXhpcy5FTkRfVElDS19NQVJLX0NMQVNTID0gImVuZC10aWNrLW1hcmsiOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byBlYWNoIHRpY2sgbWFyayAodGhlIGxpbmUgb24gdGhlIHRpY2spLgogICAgICAgICAqLwogICAgICAgIEF4aXMuVElDS19NQVJLX0NMQVNTID0gInRpY2stbWFyayI7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGNzcyBjbGFzcyBhcHBsaWVkIHRvIGVhY2ggdGljayBsYWJlbCAodGhlIHRleHQgYXNzb2NpYXRlZCB3aXRoIHRoZSB0aWNrKS4KICAgICAgICAgKi8KICAgICAgICBBeGlzLlRJQ0tfTEFCRUxfQ0xBU1MgPSAidGljay1sYWJlbCI7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGNzcyBjbGFzcyBhcHBsaWVkIHRvIGVhY2ggYW5ub3RhdGlvbiBsaW5lLCB3aGljaCBleHRlbmRzIGZyb20gdGhlIGF4aXMgdG8gdGhlIHJlY3QuCiAgICAgICAgICovCiAgICAgICAgQXhpcy5BTk5PVEFUSU9OX0xJTkVfQ0xBU1MgPSAiYW5ub3RhdGlvbi1saW5lIjsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgY3NzIGNsYXNzIGFwcGxpZWQgdG8gZWFjaCBhbm5vdGF0aW9uIHJlY3QsIHdoaWNoIHN1cnJvdW5kcyB0aGUgYW5ub3RhdGlvbiBsYWJlbC4KICAgICAgICAgKi8KICAgICAgICBBeGlzLkFOTk9UQVRJT05fUkVDVF9DTEFTUyA9ICJhbm5vdGF0aW9uLXJlY3QiOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byBlYWNoIGFubm90YXRpb24gY2lyY2xlLCB3aGljaCBkZW5vdGVzIHdoaWNoIHRpY2sgaXMgYmVpbmcgYW5ub3RhdGVkLgogICAgICAgICAqLwogICAgICAgIEF4aXMuQU5OT1RBVElPTl9DSVJDTEVfQ0xBU1MgPSAiYW5ub3RhdGlvbi1jaXJjbGUiOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byBlYWNoIGFubm90YXRpb24gbGFiZWwsIHdoaWNoIHNob3dzIHRoZSBmb3JtYXR0ZWQgYW5ub3RhdGlvbiB0ZXh0LgogICAgICAgICAqLwogICAgICAgIEF4aXMuQU5OT1RBVElPTl9MQUJFTF9DTEFTUyA9ICJhbm5vdGF0aW9uLWxhYmVsIjsKICAgICAgICBBeGlzLl9BTk5PVEFUSU9OX0xBQkVMX1BBRERJTkcgPSA0OwogICAgICAgIHJldHVybiBBeGlzOwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLkF4aXMgPSBBeGlzOwogICAgfSk7CgogICAgdmFyIGNhdGVnb3J5QXhpcyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgogICAgdmFyIENhdGVnb3J5ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQ2F0ZWdvcnksIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29uc3RydWN0cyBhIENhdGVnb3J5IEF4aXMuCiAgICAgICAgICoKICAgICAgICAgKiBBIENhdGVnb3J5IEF4aXMgaXMgYSB2aXN1YWwgcmVwcmVzZW50YXRpb24gb2YgYSBDYXRlZ29yeSBTY2FsZS4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7U2NhbGVzLkNhdGVnb3J5fSBzY2FsZQogICAgICAgICAqIEBwYXJhbSB7QXhpc09yaWVudGF0aW9ufSBbb3JpZW50YXRpb249ImJvdHRvbSJdIE9yaWVudGF0aW9uIG9mIHRoaXMgQ2F0ZWdvcnkgQXhpcy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBDYXRlZ29yeShzY2FsZSwgb3JpZW50YXRpb24pIHsKICAgICAgICAgICAgaWYgKG9yaWVudGF0aW9uID09PSB2b2lkIDApIHsgb3JpZW50YXRpb24gPSAiYm90dG9tIjsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzLCBzY2FsZSwgb3JpZW50YXRpb24pIHx8IHRoaXM7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBUaGUgcm90YXRpb24gYW5nbGUgb2YgdGljayBsYWJlbCB0ZXh0LiBPbmx5IDAsIDkwLCAtOTAgYXJlIHN1cHBvcnRlZAogICAgICAgICAgICAgKi8KICAgICAgICAgICAgX3RoaXMuX3RpY2tMYWJlbEFuZ2xlID0gMDsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFRoZSBzaGVhciBhbmdsZSBvZiB0aGUgdGljayBsYWJlbCB0ZXh0LiBPbmx5IHZhbHVlcyAtODAgPD0geCA8PSA4MCBhcmUgc3VwcG9ydGVkCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBfdGhpcy5fdGlja0xhYmVsU2hlYXJBbmdsZSA9IDA7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJjYXRlZ29yeS1heGlzIik7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KENhdGVnb3J5LnByb3RvdHlwZSwgIl93cmFwcGVyIiwgewogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQSBXcmFwcGVyIGNvbmZpZ3VyZWQgYWNjb3JkaW5nIHRvIHRoZSBvdGhlciBwcm9wZXJ0aWVzIG9uIHRoaXMgYXhpcy4KICAgICAgICAgICAgICogQHJldHVybnMge1R5cGVzZXR0YWJsZS5XcmFwcGVyfQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgZ2V0OiBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB2YXIgd3JhcHBlciA9IG5ldyBzcmMkMS5XcmFwcGVyKCk7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fdGlja0xhYmVsTWF4TGluZXMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHdyYXBwZXIubWF4TGluZXModGhpcy5fdGlja0xhYmVsTWF4TGluZXMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIHdyYXBwZXI7CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIGVudW1lcmFibGU6IHRydWUsCiAgICAgICAgICAgIGNvbmZpZ3VyYWJsZTogdHJ1ZQogICAgICAgIH0pOwogICAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShDYXRlZ29yeS5wcm90b3R5cGUsICJfd3JpdGVyIiwgewogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQSBXcml0ZXIgYXR0YWNoZWQgdG8gdGhpcyBtZWFzdXJlciBhbmQgd3JhcHBlci4KICAgICAgICAgICAgICogQHJldHVybnMge1R5cGVzZXR0YWJsZS5Xcml0ZXJ9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICBnZXQ6IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHJldHVybiBuZXcgc3JjJDEuV3JpdGVyKHRoaXMuX21lYXN1cmVyLCB0aGlzLl90eXBlc2V0dGVyQ29udGV4dCwgdGhpcy5fd3JhcHBlcik7CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIGVudW1lcmFibGU6IHRydWUsCiAgICAgICAgICAgIGNvbmZpZ3VyYWJsZTogdHJ1ZQogICAgICAgIH0pOwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3R5cGVzZXR0ZXJDb250ZXh0ID0gbmV3IHNyYyQxLlN2Z0NvbnRleHQodGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLm5vZGUoKSk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIodGhpcy5fdHlwZXNldHRlckNvbnRleHQpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLl9yZXNjYWxlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5yZWRyYXcoKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENvbXB1dGUgc3BhY2UgcmVxdWlyZW1lbnRzIGZvciB0aGlzIENhdGVnb3J5IEF4aXMuIENhdGVnb3J5IEF4ZXMgaGF2ZSB0d28gcHJpbWFyeSBzcGFjZSByZXF1aXJlbWVudHM6CiAgICAgICAgICoKICAgICAgICAgKiAxKSB3aWR0aC9oZWlnaHQgbmVlZGVkIGJ5IHRoZSB0aWNrIGxpbmVzIChpbmNsdWRpbmcgYW5ub3RhdGlvbnMsIHBhZGRpbmcsIGFuZCBtYXJnaW5zKS4KICAgICAgICAgKiAyKSB3aWR0aC9oZWlnaHQgbmVlZGVkIGJ5IHRoZSB0aWNrIHRleHQuCiAgICAgICAgICoKICAgICAgICAgKiBXZSByZXF1ZXN0ZWQgc3BhY2UgaXMgdGhlIHN1bSBvZiB0aGUgbGluZXMgYW5kIHRleHQuCiAgICAgICAgICogQHBhcmFtIG9mZmVyZWRXaWR0aAogICAgICAgICAqIEBwYXJhbSBvZmZlcmVkSGVpZ2h0CiAgICAgICAgICogQHJldHVybnMge2FueX0KICAgICAgICAgKi8KICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUucmVxdWVzdGVkU3BhY2UgPSBmdW5jdGlvbiAob2ZmZXJlZFdpZHRoLCBvZmZlcmVkSGVpZ2h0KSB7CiAgICAgICAgICAgIHZhciB3aWR0aFJlcXVpcmVkQnlUaWNrcyA9IHRoaXMuaXNIb3Jpem9udGFsKCkgPyAwIDogdGhpcy5fdGlja1NwYWNlUmVxdWlyZWQoKSArIHRoaXMubWFyZ2luKCk7CiAgICAgICAgICAgIHZhciBoZWlnaHRSZXF1aXJlZEJ5VGlja3MgPSB0aGlzLmlzSG9yaXpvbnRhbCgpID8gdGhpcy5fdGlja1NwYWNlUmVxdWlyZWQoKSArIHRoaXMubWFyZ2luKCkgOiAwOwogICAgICAgICAgICBpZiAodGhpcy5fc2NhbGUuZG9tYWluKCkubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIG1pbldpZHRoOiAwLAogICAgICAgICAgICAgICAgICAgIG1pbkhlaWdodDogMCwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuYW5ub3RhdGlvbnNFbmFibGVkKCkpIHsKICAgICAgICAgICAgICAgIHZhciB0aWVyVG90YWxIZWlnaHQgPSB0aGlzLl9hbm5vdGF0aW9uVGllckhlaWdodCgpICogdGhpcy5hbm5vdGF0aW9uVGllckNvdW50KCk7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5pc0hvcml6b250YWwoKSkgewogICAgICAgICAgICAgICAgICAgIGhlaWdodFJlcXVpcmVkQnlUaWNrcyArPSB0aWVyVG90YWxIZWlnaHQ7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB3aWR0aFJlcXVpcmVkQnlUaWNrcyArPSB0aWVyVG90YWxIZWlnaHQ7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIG1lYXN1cmVSZXN1bHQgPSB0aGlzLl9tZWFzdXJlVGlja0xhYmVscyhvZmZlcmVkV2lkdGgsIG9mZmVyZWRIZWlnaHQpOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbWluV2lkdGg6IG1lYXN1cmVSZXN1bHQudXNlZFdpZHRoICsgd2lkdGhSZXF1aXJlZEJ5VGlja3MsCiAgICAgICAgICAgICAgICBtaW5IZWlnaHQ6IG1lYXN1cmVSZXN1bHQudXNlZEhlaWdodCArIGhlaWdodFJlcXVpcmVkQnlUaWNrcywKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fY29yZVNpemUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciByZWxldmFudERpbWVuc2lvbiA9IHRoaXMuaXNIb3Jpem9udGFsKCkgPyB0aGlzLmhlaWdodCgpIDogdGhpcy53aWR0aCgpOwogICAgICAgICAgICB2YXIgcmVsZXZhbnRSZXF1ZXN0ZWRTcGFjZURpbWVuc2lvbiA9IHRoaXMuaXNIb3Jpem9udGFsKCkgPwogICAgICAgICAgICAgICAgdGhpcy5yZXF1ZXN0ZWRTcGFjZSh0aGlzLndpZHRoKCksIHRoaXMuaGVpZ2h0KCkpLm1pbkhlaWdodCA6CiAgICAgICAgICAgICAgICB0aGlzLnJlcXVlc3RlZFNwYWNlKHRoaXMud2lkdGgoKSwgdGhpcy5oZWlnaHQoKSkubWluV2lkdGg7CiAgICAgICAgICAgIHZhciBtYXJnaW5BbmRBbm5vdGF0aW9uU2l6ZSA9IHRoaXMubWFyZ2luKCkgKyB0aGlzLl9hbm5vdGF0aW9uVGllckhlaWdodCgpOwogICAgICAgICAgICB2YXIgYXhpc0hlaWdodFdpdGhvdXRNYXJnaW4gPSByZWxldmFudFJlcXVlc3RlZFNwYWNlRGltZW5zaW9uIC0gbWFyZ2luQW5kQW5ub3RhdGlvblNpemU7CiAgICAgICAgICAgIHJldHVybiBNYXRoLm1pbihheGlzSGVpZ2h0V2l0aG91dE1hcmdpbiwgcmVsZXZhbnREaW1lbnNpb24pOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLl9nZXRUaWNrVmFsdWVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5nZXREb3duc2FtcGxlSW5mbygpLmRvbWFpbjsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fc2l6ZUZyb21PZmZlciA9IGZ1bmN0aW9uIChhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIC8vIGhhY2s6IGNvbnRpbnVlIHVzaW5nIENvbXBvbmVudC5fc2l6ZUZyb21PZmZlciB0byBwcmV2ZW50IGFuZ2xlZCBheGlzIHRpY2tzCiAgICAgICAgICAgIC8vIGZyb20gb3ZlcmZsb3dpbmcgdGhlaXIgY29udGFpbmVyCiAgICAgICAgICAgIHJldHVybiBjb21wb25lbnQuQ29tcG9uZW50LnByb3RvdHlwZS5fc2l6ZUZyb21PZmZlci5jYWxsKHRoaXMsIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVGFrZSB0aGUgc2NhbGUgYW5kIGRyb3AgdGlja3MgYXQgcmVndWxhciBpbnRlcnZhbHMgc3VjaCB0aGF0IHRoZSByZXN1bHRhbnQgdGlja3MgYXJlIGFsbCBhIHJlYXNvbmFibGUgbWluaW11bQogICAgICAgICAqIGRpc3RhbmNlIGFwYXJ0LiBSZXR1cm4gdGhlIHJlc3VsdGFudCB0aWNrcyB0byByZW5kZXIsIGFzIHdlbGwgYXMgdGhlIG5ldyBzdGVwV2lkdGggYmV0d2VlbiB0aGVtLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtTY2FsZXMuQ2F0ZWdvcnl9IHNjYWxlIC0gVGhlIHNjYWxlIGJlaW5nIGRvd25zYW1wbGVkLiBEZWZhdWx0cyB0byB0aGlzIEF4aXMnIHNjYWxlLgogICAgICAgICAqIEByZXR1cm4ge0Rvd25zYW1wbGVJbmZvfSBhbiBvYmplY3QgaG9sZGluZyB0aGUgcmVzdWx0YW50IGRvbWFpbiBhbmQgbmV3IHN0ZXBXaWR0aC4KICAgICAgICAgKi8KICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuZ2V0RG93bnNhbXBsZUluZm8gPSBmdW5jdGlvbiAoc2NhbGUsIGRvbWFpbikgewogICAgICAgICAgICBpZiAoc2NhbGUgPT09IHZvaWQgMCkgeyBzY2FsZSA9IHRoaXMuX3NjYWxlOyB9CiAgICAgICAgICAgIGlmIChkb21haW4gPT09IHZvaWQgMCkgeyBkb21haW4gPSBzY2FsZS5pbnZlcnRSYW5nZSgpOyB9CiAgICAgICAgICAgIC8vIGFjY291bnQgZm9yIGhvdyBzaGVhcmluZyB0aWdodGVucyB0aGUgc3BhY2UgYmV0d2VlbiB2ZXJ0aWNhbGx5IG9yaWVudGVkIHRpY2tzCiAgICAgICAgICAgIHZhciBzaGVhckZhY3RvciA9IHRoaXMuX3RpY2tMYWJlbEFuZ2xlID09PSAwID8gMSA6IDEgLyBNYXRoLmNvcyh0aGlzLl90aWNrTGFiZWxTaGVhckFuZ2xlIC8gMTgwICogTWF0aC5QSSk7CiAgICAgICAgICAgIHZhciBzaGVhcmVkTWluaW11bVdpZHRoID0gQ2F0ZWdvcnkuX01JTklNVU1fV0lEVEhfUEVSX0xBQkVMX1BYICogc2hlYXJGYWN0b3I7CiAgICAgICAgICAgIHZhciBkb3duc2FtcGxlUmF0aW8gPSBNYXRoLmNlaWwoc2hlYXJlZE1pbmltdW1XaWR0aCAvIHNjYWxlLnN0ZXBXaWR0aCgpKTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGRvbWFpbjogZG9tYWluLmZpbHRlcihmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gaSAlIGRvd25zYW1wbGVSYXRpbyA9PT0gMDsgfSksCiAgICAgICAgICAgICAgICBzdGVwV2lkdGg6IGRvd25zYW1wbGVSYXRpbyAqIHNjYWxlLnN0ZXBXaWR0aCgpLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnRpY2tMYWJlbEFuZ2xlID0gZnVuY3Rpb24gKGFuZ2xlKSB7CiAgICAgICAgICAgIGlmIChhbmdsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fdGlja0xhYmVsQW5nbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGFuZ2xlICE9PSAwICYmIGFuZ2xlICE9PSA5MCAmJiBhbmdsZSAhPT0gLTkwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIkFuZ2xlICIgKyBhbmdsZSArICIgbm90IHN1cHBvcnRlZDsgb25seSAwLCA5MCwgYW5kIC05MCBhcmUgdmFsaWQgdmFsdWVzIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdGlja0xhYmVsQW5nbGUgPSBhbmdsZTsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUudGlja0xhYmVsU2hlYXJBbmdsZSA9IGZ1bmN0aW9uIChhbmdsZSkgewogICAgICAgICAgICBpZiAoYW5nbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3RpY2tMYWJlbFNoZWFyQW5nbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGFuZ2xlIDwgLTgwIHx8IGFuZ2xlID4gODApIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiQW5nbGUgIiArIGFuZ2xlICsgIiBub3Qgc3VwcG9ydGVkOyBNdXN0IGJlIGJldHdlZW4gWy04MCwgODBdIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdGlja0xhYmVsU2hlYXJBbmdsZSA9IGFuZ2xlOwogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS50aWNrTGFiZWxNYXhXaWR0aCA9IGZ1bmN0aW9uIChtYXhXaWR0aCkgewogICAgICAgICAgICAvLyBhbGxvdyB1c2VyIHRvIHVuLXNldCB0aWNrTGFiZWxNYXhXaWR0aCBieSBwYXNzaW5nIGluIG51bGwgb3IgdW5kZWZpbmVkIGV4cGxpY2l0bHkKICAgICAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl90aWNrTGFiZWxNYXhXaWR0aDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl90aWNrTGFiZWxNYXhXaWR0aCA9IG1heFdpZHRoOwogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS50aWNrTGFiZWxNYXhMaW5lcyA9IGZ1bmN0aW9uIChtYXhMaW5lcykgewogICAgICAgICAgICAvLyBhbGxvdyB1c2VyIHRvIHVuLXNldCB0aWNrTGFiZWxNYXhMaW5lcyBieSBwYXNzaW5nIGluIG51bGwgb3IgdW5kZWZpbmVkIGV4cGxpY2l0bHkKICAgICAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl90aWNrTGFiZWxNYXhMaW5lczsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl90aWNrTGFiZWxNYXhMaW5lcyA9IG1heExpbmVzOwogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiB0aGUgc3BhY2UgcmVxdWlyZWQgYnkgdGhlIHRpY2tzLCBwYWRkaW5nIGluY2x1ZGVkLgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9CiAgICAgICAgICovCiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLl90aWNrU3BhY2VSZXF1aXJlZCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21heExhYmVsVGlja0xlbmd0aCgpICsgdGhpcy50aWNrTGFiZWxQYWRkaW5nKCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBXcml0ZSB0aWNrcyB0byB0aGUgRE9NLgogICAgICAgICAqIEBwYXJhbSB7UGxvdHRhYmxlLlNjYWxlcy5DYXRlZ29yeX0gc2NhbGUgVGhlIHNjYWxlIHRoaXMgYXhpcyBpcyByZXByZXNlbnRpbmcuCiAgICAgICAgICogQHBhcmFtIHtkMy5TZWxlY3Rpb259IHRpY2tzIFRoZSB0aWNrIGVsZW1lbnRzIHRvIHdyaXRlLgogICAgICAgICAqLwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fZHJhd1RpY2tzID0gZnVuY3Rpb24gKHN0ZXBXaWR0aCwgdGlja3MpIHsKICAgICAgICAgICAgdmFyIHNlbGYgPSB0aGlzOwogICAgICAgICAgICB2YXIgeEFsaWduOwogICAgICAgICAgICB2YXIgeUFsaWduOwogICAgICAgICAgICBzd2l0Y2ggKHRoaXMudGlja0xhYmVsQW5nbGUoKSkgewogICAgICAgICAgICAgICAgY2FzZSAwOgogICAgICAgICAgICAgICAgICAgIHhBbGlnbiA9IHsgbGVmdDogInJpZ2h0IiwgcmlnaHQ6ICJsZWZ0IiwgdG9wOiAiY2VudGVyIiwgYm90dG9tOiAiY2VudGVyIiB9OwogICAgICAgICAgICAgICAgICAgIHlBbGlnbiA9IHsgbGVmdDogImNlbnRlciIsIHJpZ2h0OiAiY2VudGVyIiwgdG9wOiAiYm90dG9tIiwgYm90dG9tOiAidG9wIiB9OwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSA5MDoKICAgICAgICAgICAgICAgICAgICB4QWxpZ24gPSB7IGxlZnQ6ICJjZW50ZXIiLCByaWdodDogImNlbnRlciIsIHRvcDogInJpZ2h0IiwgYm90dG9tOiAibGVmdCIgfTsKICAgICAgICAgICAgICAgICAgICB5QWxpZ24gPSB7IGxlZnQ6ICJ0b3AiLCByaWdodDogImJvdHRvbSIsIHRvcDogImNlbnRlciIsIGJvdHRvbTogImNlbnRlciIgfTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgLTkwOgogICAgICAgICAgICAgICAgICAgIHhBbGlnbiA9IHsgbGVmdDogImNlbnRlciIsIHJpZ2h0OiAiY2VudGVyIiwgdG9wOiAibGVmdCIsIGJvdHRvbTogInJpZ2h0IiB9OwogICAgICAgICAgICAgICAgICAgIHlBbGlnbiA9IHsgbGVmdDogImJvdHRvbSIsIHJpZ2h0OiAidG9wIiwgdG9wOiAiY2VudGVyIiwgYm90dG9tOiAiY2VudGVyIiB9OwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRpY2tzLmVhY2goZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHZhciBjb250YWluZXIgPSBkMy5zZWxlY3QodGhpcyk7CiAgICAgICAgICAgICAgICB2YXIgd2lkdGggPSBzZWxmLmlzSG9yaXpvbnRhbCgpID8gc3RlcFdpZHRoIDogc2VsZi53aWR0aCgpIC0gc2VsZi5fdGlja1NwYWNlUmVxdWlyZWQoKTsKICAgICAgICAgICAgICAgIHZhciBoZWlnaHQgPSBzZWxmLmlzSG9yaXpvbnRhbCgpID8gc2VsZi5oZWlnaHQoKSAtIHNlbGYuX3RpY2tTcGFjZVJlcXVpcmVkKCkgOiBzdGVwV2lkdGg7CiAgICAgICAgICAgICAgICB2YXIgd3JpdGVPcHRpb25zID0gewogICAgICAgICAgICAgICAgICAgIHhBbGlnbjogeEFsaWduW3NlbGYub3JpZW50YXRpb24oKV0sCiAgICAgICAgICAgICAgICAgICAgeUFsaWduOiB5QWxpZ25bc2VsZi5vcmllbnRhdGlvbigpXSwKICAgICAgICAgICAgICAgICAgICB0ZXh0Um90YXRpb246IHNlbGYudGlja0xhYmVsQW5nbGUoKSwKICAgICAgICAgICAgICAgICAgICB0ZXh0U2hlYXI6IHNlbGYudGlja0xhYmVsU2hlYXJBbmdsZSgpLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGlmIChzZWxmLl90aWNrTGFiZWxNYXhXaWR0aCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gZm9yIGxlZnQtb3JpZW50ZWQgYXhlcywgd2UgbXVzdCBtb3ZlIHRoZSB0aWNrcyBieSB0aGUgYW1vdW50IHdlJ3ZlIGN1dCBvZmYgaW4gb3JkZXIgdG8ga2VlcCB0aGUgdGV4dAogICAgICAgICAgICAgICAgICAgIC8vIGFsaWduZWQgd2l0aCB0aGUgc2lkZSBvZiB0aGUgdGlja3MKICAgICAgICAgICAgICAgICAgICBpZiAoc2VsZi5vcmllbnRhdGlvbigpID09PSAibGVmdCIgJiYgd2lkdGggPiBzZWxmLl90aWNrTGFiZWxNYXhXaWR0aCkgewogICAgICAgICAgICAgICAgICAgICAgICB2YXIgY3V0T2ZmV2lkdGggPSB3aWR0aCAtIHNlbGYuX3RpY2tMYWJlbE1heFdpZHRoOwogICAgICAgICAgICAgICAgICAgICAgICB2YXIgbmV3VHJhbnNmb3JtID0gY29udGFpbmVyLmF0dHIoInRyYW5zZm9ybSIpICsgIiB0cmFuc2xhdGUoIiArIGN1dE9mZldpZHRoICsgIiwgMCkiOwogICAgICAgICAgICAgICAgICAgICAgICBjb250YWluZXIuYXR0cigidHJhbnNmb3JtIiwgbmV3VHJhbnNmb3JtKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgd2lkdGggPSBNYXRoLm1pbih3aWR0aCwgc2VsZi5fdGlja0xhYmVsTWF4V2lkdGgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgc2VsZi5fd3JpdGVyLndyaXRlKHNlbGYuZm9ybWF0dGVyKCkoZCksIHdpZHRoLCBoZWlnaHQsIHdyaXRlT3B0aW9ucywgY29udGFpbmVyLm5vZGUoKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogTWVhc3VyZXMgdGhlIHNpemUgb2YgdGhlIHRpY2sgbGFiZWxzIHdpdGhvdXQgbWFraW5nIGFueSAocGVybWFuZW50KSBET00gY2hhbmdlcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBheGlzV2lkdGggV2lkdGggYXZhaWxhYmxlIGZvciB0aGlzIGF4aXMuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGF4aXNIZWlnaHQgSGVpZ2h0IGF2YWlsYWJsZSBmb3IgdGhpcyBheGlzLgogICAgICAgICAqIEBwYXJhbSB7UGxvdHRhYmxlLlNjYWxlcy5DYXRlZ29yeX0gc2NhbGUgVGhlIHNjYWxlIHRoaXMgYXhpcyBpcyByZXByZXNlbnRpbmcuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmdbXX0gdGlja3MgVGhlIHN0cmluZ3MgdGhhdCB3aWxsIGJlIHByaW50ZWQgb24gdGhlIHRpY2tzLgogICAgICAgICAqLwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fbWVhc3VyZVRpY2tMYWJlbHMgPSBmdW5jdGlvbiAoYXhpc1dpZHRoLCBheGlzSGVpZ2h0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciB0aGlzU2NhbGUgPSB0aGlzLl9zY2FsZTsKICAgICAgICAgICAgLy8gc2V0IHVwIGEgdGVzdCBzY2FsZSB0byBzaW11bGF0ZSByZW5kZXJpbmcgdGlja3Mgd2l0aCB0aGUgZ2l2ZW4gd2lkdGggYW5kIGhlaWdodC4KICAgICAgICAgICAgdmFyIHNjYWxlID0gdGhpc1NjYWxlLmNsb25lV2l0aG91dFByb3ZpZGVycygpCiAgICAgICAgICAgICAgICAucmFuZ2UoWzAsIHRoaXMuaXNIb3Jpem9udGFsKCkgPyBheGlzV2lkdGggOiBheGlzSGVpZ2h0XSk7CiAgICAgICAgICAgIHZhciBfYSA9IHRoaXMuZ2V0RG93bnNhbXBsZUluZm8oc2NhbGUpLCBkb21haW4gPSBfYS5kb21haW4sIHN0ZXBXaWR0aCA9IF9hLnN0ZXBXaWR0aDsKICAgICAgICAgICAgLy8gSEFDS0hBQ0s6IGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci9zdmctdHlwZXdyaXRlci9pc3N1ZXMvMjUKICAgICAgICAgICAgLy8gdGhlIHdpZHRoICh4LWF4aXMgc3BlY2lmaWMpIGF2YWlsYWJsZSB0byBhIHNpbmdsZSB0aWNrIGxhYmVsLgogICAgICAgICAgICB2YXIgd2lkdGggPSBheGlzV2lkdGggLSB0aGlzLl90aWNrU3BhY2VSZXF1aXJlZCgpOyAvLyBkZWZhdWx0IGZvciBsZWZ0L3JpZ2h0CiAgICAgICAgICAgIGlmICh0aGlzLmlzSG9yaXpvbnRhbCgpKSB7CiAgICAgICAgICAgICAgICB3aWR0aCA9IHN0ZXBXaWR0aDsgLy8gZGVmYXVsdHMgdG8gdGhlIGJhbmQgd2lkdGgKICAgICAgICAgICAgICAgIGlmICh0aGlzLl90aWNrTGFiZWxBbmdsZSAhPT0gMCkgewogICAgICAgICAgICAgICAgICAgIHdpZHRoID0gYXhpc0hlaWdodCAtIHRoaXMuX3RpY2tTcGFjZVJlcXVpcmVkKCk7IC8vIHVzZSB0aGUgYXhpcyBoZWlnaHQKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEhBQ0tIQUNLOiBXcmFwcGVyIGZhaWxzIHVuZGVyIG5lZ2F0aXZlIGNpcmN1bXN0YW5jZXMKICAgICAgICAgICAgICAgIHdpZHRoID0gTWF0aC5tYXgod2lkdGgsIDApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEhBQ0tIQUNLOiBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvc3ZnLXR5cGV3cml0ZXIvaXNzdWVzLzI1CiAgICAgICAgICAgIC8vIHRoZSBoZWlnaHQgKHktYXhpcyBzcGVjaWZpYykgYXZhaWxhYmxlIHRvIGEgc2luZ2xlIHRpY2sgbGFiZWwuCiAgICAgICAgICAgIHZhciBoZWlnaHQgPSBzdGVwV2lkdGg7IC8vIGRlZmF1bHQgZm9yIGxlZnQvcmlnaHQKICAgICAgICAgICAgaWYgKHRoaXMuaXNIb3Jpem9udGFsKCkpIHsKICAgICAgICAgICAgICAgIGhlaWdodCA9IGF4aXNIZWlnaHQgLSB0aGlzLl90aWNrU3BhY2VSZXF1aXJlZCgpOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuX3RpY2tMYWJlbEFuZ2xlICE9PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0ID0gYXhpc1dpZHRoIC0gdGhpcy5fdGlja1NwYWNlUmVxdWlyZWQoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEhBQ0tIQUNLOiBXcmFwcGVyIGZhaWxzIHVuZGVyIG5lZ2F0aXZlIGNpcmN1bXN0YW5jZXMKICAgICAgICAgICAgICAgIGhlaWdodCA9IE1hdGgubWF4KGhlaWdodCwgMCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX3RpY2tMYWJlbE1heFdpZHRoICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHdpZHRoID0gTWF0aC5taW4od2lkdGgsIHRoaXMuX3RpY2tMYWJlbE1heFdpZHRoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgd3JhcHBpbmdSZXN1bHRzID0gZG9tYWluLm1hcChmdW5jdGlvbiAocykgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl93cmFwcGVyLndyYXAoX3RoaXMuZm9ybWF0dGVyKCkocyksIF90aGlzLl9tZWFzdXJlciwgd2lkdGgsIGhlaWdodCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBIQUNLSEFDSzogaHR0cHM6Ly9naXRodWIuY29tL3BhbGFudGlyL3N2Zy10eXBld3JpdGVyL2lzc3Vlcy8yNQogICAgICAgICAgICB2YXIgd2lkdGhGbiA9ICh0aGlzLmlzSG9yaXpvbnRhbCgpICYmIHRoaXMuX3RpY2tMYWJlbEFuZ2xlID09PSAwKSA/IGQzLnN1bSA6IHV0aWxzJDEuTWF0aC5tYXg7CiAgICAgICAgICAgIHZhciBoZWlnaHRGbiA9ICh0aGlzLmlzSG9yaXpvbnRhbCgpICYmIHRoaXMuX3RpY2tMYWJlbEFuZ2xlID09PSAwKSA/IHV0aWxzJDEuTWF0aC5tYXggOiBkMy5zdW07CiAgICAgICAgICAgIHZhciB1c2VkV2lkdGggPSB3aWR0aEZuKHdyYXBwaW5nUmVzdWx0cywgZnVuY3Rpb24gKHQpIHsgcmV0dXJuIF90aGlzLl9tZWFzdXJlci5tZWFzdXJlKHQud3JhcHBlZFRleHQpLndpZHRoOyB9LCAwKTsKICAgICAgICAgICAgdmFyIHVzZWRIZWlnaHQgPSBoZWlnaHRGbih3cmFwcGluZ1Jlc3VsdHMsIGZ1bmN0aW9uICh0KSB7IHJldHVybiBfdGhpcy5fbWVhc3VyZXIubWVhc3VyZSh0LndyYXBwZWRUZXh0KS5oZWlnaHQ7IH0sIDApOwogICAgICAgICAgICAvLyBJZiB0aGUgdGljayBsYWJlbHMgYXJlIHJvdGF0ZWQsIHJldmVyc2UgdXNlZFdpZHRoIGFuZCB1c2VkSGVpZ2h0CiAgICAgICAgICAgIC8vIEhBQ0tIQUNLOiBodHRwczovL2dpdGh1Yi5jb20vcGFsYW50aXIvc3ZnLXR5cGV3cml0ZXIvaXNzdWVzLzI1CiAgICAgICAgICAgIGlmICh0aGlzLl90aWNrTGFiZWxBbmdsZSAhPT0gMCkgewogICAgICAgICAgICAgICAgX2IgPSBbdXNlZEhlaWdodCwgdXNlZFdpZHRoXSwgdXNlZFdpZHRoID0gX2JbMF0sIHVzZWRIZWlnaHQgPSBfYlsxXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgdXNlZFdpZHRoOiB1c2VkV2lkdGgsCiAgICAgICAgICAgICAgICB1c2VkSGVpZ2h0OiB1c2VkSGVpZ2h0LAogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgX2I7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUucmVuZGVySW1tZWRpYXRlbHkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUucmVuZGVySW1tZWRpYXRlbHkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdmFyIGNhdFNjYWxlID0gdGhpcy5fc2NhbGU7CiAgICAgICAgICAgIHZhciBfYSA9IHRoaXMuZ2V0RG93bnNhbXBsZUluZm8oY2F0U2NhbGUpLCBkb21haW4gPSBfYS5kb21haW4sIHN0ZXBXaWR0aCA9IF9hLnN0ZXBXaWR0aDsKICAgICAgICAgICAgLy8gR2l2ZSBlYWNoIHRpY2sgYSBzdGVwV2lkdGggb2Ygc3BhY2Ugd2hpY2ggd2lsbCBwYXJ0aXRpb24gdGhlIGVudGlyZSBheGlzIGV2ZW5seQogICAgICAgICAgICB2YXIgYXZhaWxhYmxlVGV4dFNwYWNlID0gc3RlcFdpZHRoOwogICAgICAgICAgICBpZiAodGhpcy5pc0hvcml6b250YWwoKSAmJiB0aGlzLl90aWNrTGFiZWxNYXhXaWR0aCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBhdmFpbGFibGVUZXh0U3BhY2UgPSBNYXRoLm1pbihhdmFpbGFibGVUZXh0U3BhY2UsIHRoaXMuX3RpY2tMYWJlbE1heFdpZHRoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgZ2V0VGlja0xhYmVsVHJhbnNmb3JtID0gZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgIC8vIHNjYWxlKGQpIHdpbGwgZ2l2ZSB0aGUgY2VudGVyIG9mIHRoZSBiYW5kLCBzbyBzdWJ0cmFjdCBoYWxmIG9mIHRoZSB0ZXh0IHdpZHRoIHRvIGdldCB0aGUgbGVmdCAodG9wLW1vc3QpCiAgICAgICAgICAgICAgICAvLyBjb29yZGluYXRlIHRoYXQgdGhlIHRpY2sgbGFiZWwgc2hvdWxkIGJlIHRyYW5zZm9ybWVkIHRvLgogICAgICAgICAgICAgICAgdmFyIHRpY2tMYWJlbEVkZ2UgPSBjYXRTY2FsZS5zY2FsZShkKSAtIGF2YWlsYWJsZVRleHRTcGFjZSAvIDI7CiAgICAgICAgICAgICAgICB2YXIgeCA9IF90aGlzLmlzSG9yaXpvbnRhbCgpID8gdGlja0xhYmVsRWRnZSA6IDA7CiAgICAgICAgICAgICAgICB2YXIgeSA9IF90aGlzLmlzSG9yaXpvbnRhbCgpID8gMCA6IHRpY2tMYWJlbEVkZ2U7CiAgICAgICAgICAgICAgICByZXR1cm4gInRyYW5zbGF0ZSgiICsgeCArICIsIiArIHkgKyAiKSI7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzVXBkYXRlID0gdGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTKS5kYXRhKGRvbWFpbik7CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzID0gdGlja0xhYmVsc1VwZGF0ZQogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoImciKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoYXhpcyQyLkF4aXMuVElDS19MQUJFTF9DTEFTUywgdHJ1ZSkKICAgICAgICAgICAgICAgIC5tZXJnZSh0aWNrTGFiZWxzVXBkYXRlKTsKICAgICAgICAgICAgdGlja0xhYmVsc1VwZGF0ZS5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgIHRpY2tMYWJlbHMuYXR0cigidHJhbnNmb3JtIiwgZ2V0VGlja0xhYmVsVHJhbnNmb3JtKTsKICAgICAgICAgICAgLy8gZXJhc2UgYWxsIHRleHQgZmlyc3QsIHRoZW4gcmV3cml0ZQogICAgICAgICAgICB0aWNrTGFiZWxzLnRleHQoIiIpOwogICAgICAgICAgICB0aGlzLl9kcmF3VGlja3Moc3RlcFdpZHRoLCB0aWNrTGFiZWxzKTsKICAgICAgICAgICAgdmFyIHhUcmFuc2xhdGUgPSB0aGlzLm9yaWVudGF0aW9uKCkgPT09ICJyaWdodCIgPyB0aGlzLl90aWNrU3BhY2VSZXF1aXJlZCgpIDogMDsKICAgICAgICAgICAgdmFyIHlUcmFuc2xhdGUgPSB0aGlzLm9yaWVudGF0aW9uKCkgPT09ICJib3R0b20iID8gdGhpcy5fdGlja1NwYWNlUmVxdWlyZWQoKSA6IDA7CiAgICAgICAgICAgIHRoaXMuX3RpY2tMYWJlbENvbnRhaW5lci5hdHRyKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyB4VHJhbnNsYXRlICsgIiwiICsgeVRyYW5zbGF0ZSArICIpIik7CiAgICAgICAgICAgIC8vIGhpZGUgdGlja3MgYW5kIGxhYmVscyB0aGF0IG92ZXJmbG93IHRoZSBheGlzCiAgICAgICAgICAgIHRoaXMuX3Nob3dBbGxUaWNrTWFya3MoKTsKICAgICAgICAgICAgdGhpcy5fc2hvd0FsbFRpY2tMYWJlbHMoKTsKICAgICAgICAgICAgdGhpcy5faGlkZVRpY2tNYXJrc1dpdGhvdXRMYWJlbCgpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICBpZiAoIXRoaXMuaXNIb3Jpem9udGFsKCkpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3NjYWxlLnJhbmdlKFswLCB0aGlzLmhlaWdodCgpXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9tZWFzdXJlci5yZXNldCgpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogSG93IG1hbnkgcGl4ZWxzIHRvIGdpdmUgbGFiZWxzIGF0IG1pbmltdW0gYmVmb3JlIGRvd25zYW1wbGluZyB0YWtlcyBlZmZlY3QuCiAgICAgICAgICovCiAgICAgICAgQ2F0ZWdvcnkuX01JTklNVU1fV0lEVEhfUEVSX0xBQkVMX1BYID0gMTU7CiAgICAgICAgcmV0dXJuIENhdGVnb3J5OwogICAgfShheGlzJDIuQXhpcykpOwogICAgZXhwb3J0cy5DYXRlZ29yeSA9IENhdGVnb3J5OwogICAgfSk7CgogICAgdmFyIG51bWVyaWNBeGlzID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCiAgICB2YXIgTnVtZXJpYyA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKE51bWVyaWMsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29uc3RydWN0cyBhIE51bWVyaWMgQXhpcy4KICAgICAgICAgKgogICAgICAgICAqIEEgTnVtZXJpYyBBeGlzIGlzIGEgdmlzdWFsIHJlcHJlc2VudGF0aW9uIG9mIGEgUXVhbnRpdGF0aXZlU2NhbGUuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1F1YW50aXRhdGl2ZVNjYWxlfSBzY2FsZQogICAgICAgICAqIEBwYXJhbSB7QXhpc09yaWVudGF0aW9ufSBvcmllbnRhdGlvbiBPcmllbnRhdGlvbiBvZiB0aGlzIE51bWVyaWMgQXhpcy4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBOdW1lcmljKHNjYWxlLCBvcmllbnRhdGlvbikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzLCBzY2FsZSwgb3JpZW50YXRpb24pIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl90aWNrTGFiZWxQb3NpdGlvbmluZyA9ICJjZW50ZXIiOwogICAgICAgICAgICBfdGhpcy5fdXNlc1RleHRXaWR0aEFwcHJveGltYXRpb24gPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuZm9ybWF0dGVyKGZvcm1hdHRlcnMuZ2VuZXJhbCgpKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBOdW1lcmljLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHZhciBjb250ZXh0ID0gbmV3IHNyYyQxLlN2Z0NvbnRleHQodGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLm5vZGUoKSwgYXhpcyQyLkF4aXMuVElDS19MQUJFTF9DTEFTUyk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIoY29udGV4dCk7CiAgICAgICAgICAgIHRoaXMuX3dyYXBwZXIgPSBuZXcgc3JjJDEuV3JhcHBlcigpLm1heExpbmVzKDEpOwogICAgICAgIH07CiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUuX2NvbXB1dGVXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIG1heFRleHRXaWR0aCA9IHRoaXMuX3VzZXNUZXh0V2lkdGhBcHByb3hpbWF0aW9uID8gdGhpcy5fY29tcHV0ZUFwcHJveGltYXRlVGV4dFdpZHRoKCkgOiB0aGlzLl9jb21wdXRlRXhhY3RUZXh0V2lkdGgoKTsKICAgICAgICAgICAgaWYgKHRoaXMuX3RpY2tMYWJlbFBvc2l0aW9uaW5nID09PSAiY2VudGVyIikgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21heExhYmVsVGlja0xlbmd0aCgpICsgdGhpcy50aWNrTGFiZWxQYWRkaW5nKCkgKyBtYXhUZXh0V2lkdGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5tYXgodGhpcy5fbWF4TGFiZWxUaWNrTGVuZ3RoKCksIHRoaXMudGlja0xhYmVsUGFkZGluZygpICsgbWF4VGV4dFdpZHRoKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUuX2NvbXB1dGVFeGFjdFRleHRXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHRpY2tWYWx1ZXMgPSB0aGlzLl9nZXRUaWNrVmFsdWVzKCk7CiAgICAgICAgICAgIHZhciB0ZXh0TGVuZ3RocyA9IHRpY2tWYWx1ZXMubWFwKGZ1bmN0aW9uICh2KSB7CiAgICAgICAgICAgICAgICB2YXIgZm9ybWF0dGVkVmFsdWUgPSBfdGhpcy5mb3JtYXR0ZXIoKSh2KTsKICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5fbWVhc3VyZXIubWVhc3VyZShmb3JtYXR0ZWRWYWx1ZSkud2lkdGg7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5NYXRoLm1heCh0ZXh0TGVuZ3RocywgMCk7CiAgICAgICAgfTsKICAgICAgICBOdW1lcmljLnByb3RvdHlwZS5fY29tcHV0ZUFwcHJveGltYXRlVGV4dFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgdGlja1ZhbHVlcyA9IHRoaXMuX2dldFRpY2tWYWx1ZXMoKTsKICAgICAgICAgICAgdmFyIG1XaWR0aCA9IHRoaXMuX21lYXN1cmVyLm1lYXN1cmUoIk0iKS53aWR0aDsKICAgICAgICAgICAgdmFyIHRleHRMZW5ndGhzID0gdGlja1ZhbHVlcy5tYXAoZnVuY3Rpb24gKHYpIHsKICAgICAgICAgICAgICAgIHZhciBmb3JtYXR0ZWRWYWx1ZSA9IF90aGlzLmZvcm1hdHRlcigpKHYpOwogICAgICAgICAgICAgICAgcmV0dXJuIGZvcm1hdHRlZFZhbHVlLmxlbmd0aCAqIG1XaWR0aDsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGgubWF4KHRleHRMZW5ndGhzLCAwKTsKICAgICAgICB9OwogICAgICAgIE51bWVyaWMucHJvdG90eXBlLl9jb21wdXRlSGVpZ2h0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgdGV4dEhlaWdodCA9IHRoaXMuX21lYXN1cmVyLm1lYXN1cmUoKS5oZWlnaHQ7CiAgICAgICAgICAgIGlmICh0aGlzLl90aWNrTGFiZWxQb3NpdGlvbmluZyA9PT0gImNlbnRlciIpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKSArIHRoaXMudGlja0xhYmVsUGFkZGluZygpICsgdGV4dEhlaWdodDsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLm1heCh0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKSwgdGhpcy50aWNrTGFiZWxQYWRkaW5nKCkgKyB0ZXh0SGVpZ2h0KTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUuX2dldFRpY2tWYWx1ZXMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBzY2FsZSA9IHRoaXMuX3NjYWxlOwogICAgICAgICAgICB2YXIgZG9tYWluID0gc2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIHZhciBtaW4gPSBkb21haW5bMF0gPD0gZG9tYWluWzFdID8gZG9tYWluWzBdIDogZG9tYWluWzFdOwogICAgICAgICAgICB2YXIgbWF4ID0gZG9tYWluWzBdID49IGRvbWFpblsxXSA/IGRvbWFpblswXSA6IGRvbWFpblsxXTsKICAgICAgICAgICAgcmV0dXJuIHNjYWxlLnRpY2tzKCkuZmlsdGVyKGZ1bmN0aW9uIChpKSB7IHJldHVybiBpID49IG1pbiAmJiBpIDw9IG1heDsgfSk7CiAgICAgICAgfTsKICAgICAgICBOdW1lcmljLnByb3RvdHlwZS5fcmVzY2FsZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9pc1NldHVwKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCF0aGlzLmlzSG9yaXpvbnRhbCgpKSB7CiAgICAgICAgICAgICAgICB2YXIgcmVDb21wdXRlZFdpZHRoID0gdGhpcy5fY29tcHV0ZVdpZHRoKCk7CiAgICAgICAgICAgICAgICBpZiAocmVDb21wdXRlZFdpZHRoID4gdGhpcy53aWR0aCgpIHx8IHJlQ29tcHV0ZWRXaWR0aCA8ICh0aGlzLndpZHRoKCkgLSB0aGlzLm1hcmdpbigpKSkgewogICAgICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgfTsKICAgICAgICBOdW1lcmljLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseS5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgdGlja0xhYmVsQXR0ckhhc2ggPSB7CiAgICAgICAgICAgICAgICB4OiAwLAogICAgICAgICAgICAgICAgeTogMCwKICAgICAgICAgICAgICAgIGR4OiAiMGVtIiwKICAgICAgICAgICAgICAgIGR5OiAiMC4zZW0iLAogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgdGlja01hcmtMZW5ndGggPSB0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKTsKICAgICAgICAgICAgdmFyIHRpY2tMYWJlbFBhZGRpbmcgPSB0aGlzLnRpY2tMYWJlbFBhZGRpbmcoKTsKICAgICAgICAgICAgdmFyIHRpY2tMYWJlbFRleHRBbmNob3IgPSAibWlkZGxlIjsKICAgICAgICAgICAgdmFyIGxhYmVsR3JvdXBUcmFuc2Zvcm1YID0gMDsKICAgICAgICAgICAgdmFyIGxhYmVsR3JvdXBUcmFuc2Zvcm1ZID0gMDsKICAgICAgICAgICAgdmFyIGxhYmVsR3JvdXBTaGlmdFggPSAwOwogICAgICAgICAgICB2YXIgbGFiZWxHcm91cFNoaWZ0WSA9IDA7CiAgICAgICAgICAgIGlmICh0aGlzLmlzSG9yaXpvbnRhbCgpKSB7CiAgICAgICAgICAgICAgICBzd2l0Y2ggKHRoaXMuX3RpY2tMYWJlbFBvc2l0aW9uaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgY2FzZSAibGVmdCI6CiAgICAgICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbFRleHRBbmNob3IgPSAiZW5kIjsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxHcm91cFRyYW5zZm9ybVggPSAtdGlja0xhYmVsUGFkZGluZzsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxHcm91cFNoaWZ0WSA9IHRpY2tMYWJlbFBhZGRpbmc7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGNhc2UgImNlbnRlciI6CiAgICAgICAgICAgICAgICAgICAgICAgIGxhYmVsR3JvdXBTaGlmdFkgPSB0aWNrTWFya0xlbmd0aCArIHRpY2tMYWJlbFBhZGRpbmc7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGNhc2UgInJpZ2h0IjoKICAgICAgICAgICAgICAgICAgICAgICAgdGlja0xhYmVsVGV4dEFuY2hvciA9ICJzdGFydCI7CiAgICAgICAgICAgICAgICAgICAgICAgIGxhYmVsR3JvdXBUcmFuc2Zvcm1YID0gdGlja0xhYmVsUGFkZGluZzsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxHcm91cFNoaWZ0WSA9IHRpY2tMYWJlbFBhZGRpbmc7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgc3dpdGNoICh0aGlzLl90aWNrTGFiZWxQb3NpdGlvbmluZykgewogICAgICAgICAgICAgICAgICAgIGNhc2UgInRvcCI6CiAgICAgICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbEF0dHJIYXNoWyJkeSJdID0gIi0wLjNlbSI7CiAgICAgICAgICAgICAgICAgICAgICAgIGxhYmVsR3JvdXBTaGlmdFggPSB0aWNrTGFiZWxQYWRkaW5nOwogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbEdyb3VwVHJhbnNmb3JtWSA9IC10aWNrTGFiZWxQYWRkaW5nOwogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICBjYXNlICJjZW50ZXIiOgogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbEdyb3VwU2hpZnRYID0gdGlja01hcmtMZW5ndGggKyB0aWNrTGFiZWxQYWRkaW5nOwogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICBjYXNlICJib3R0b20iOgogICAgICAgICAgICAgICAgICAgICAgICB0aWNrTGFiZWxBdHRySGFzaFsiZHkiXSA9ICIxZW0iOwogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbEdyb3VwU2hpZnRYID0gdGlja0xhYmVsUGFkZGluZzsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxHcm91cFRyYW5zZm9ybVkgPSB0aWNrTGFiZWxQYWRkaW5nOwogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgdGlja01hcmtBdHRySGFzaCA9IHRoaXMuX2dlbmVyYXRlVGlja01hcmtBdHRySGFzaCgpOwogICAgICAgICAgICBzd2l0Y2ggKHRoaXMub3JpZW50YXRpb24oKSkgewogICAgICAgICAgICAgICAgY2FzZSAiYm90dG9tIjoKICAgICAgICAgICAgICAgICAgICB0aWNrTGFiZWxBdHRySGFzaFsieCJdID0gdGlja01hcmtBdHRySGFzaFsieDEiXTsKICAgICAgICAgICAgICAgICAgICB0aWNrTGFiZWxBdHRySGFzaFsiZHkiXSA9ICIwLjk1ZW0iOwogICAgICAgICAgICAgICAgICAgIGxhYmVsR3JvdXBUcmFuc2Zvcm1ZID0gdGlja01hcmtBdHRySGFzaFsieTEiXSArIGxhYmVsR3JvdXBTaGlmdFk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlICJ0b3AiOgogICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbEF0dHJIYXNoWyJ4Il0gPSB0aWNrTWFya0F0dHJIYXNoWyJ4MSJdOwogICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbEF0dHJIYXNoWyJkeSJdID0gIi0uMjVlbSI7CiAgICAgICAgICAgICAgICAgICAgbGFiZWxHcm91cFRyYW5zZm9ybVkgPSB0aWNrTWFya0F0dHJIYXNoWyJ5MSJdIC0gbGFiZWxHcm91cFNoaWZ0WTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgImxlZnQiOgogICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbFRleHRBbmNob3IgPSAiZW5kIjsKICAgICAgICAgICAgICAgICAgICBsYWJlbEdyb3VwVHJhbnNmb3JtWCA9IHRpY2tNYXJrQXR0ckhhc2hbIngxIl0gLSBsYWJlbEdyb3VwU2hpZnRYOwogICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbEF0dHJIYXNoWyJ5Il0gPSB0aWNrTWFya0F0dHJIYXNoWyJ5MSJdOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAicmlnaHQiOgogICAgICAgICAgICAgICAgICAgIHRpY2tMYWJlbFRleHRBbmNob3IgPSAic3RhcnQiOwogICAgICAgICAgICAgICAgICAgIGxhYmVsR3JvdXBUcmFuc2Zvcm1YID0gdGlja01hcmtBdHRySGFzaFsieDEiXSArIGxhYmVsR3JvdXBTaGlmdFg7CiAgICAgICAgICAgICAgICAgICAgdGlja0xhYmVsQXR0ckhhc2hbInkiXSA9IHRpY2tNYXJrQXR0ckhhc2hbInkxIl07CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRpY2tMYWJlbFZhbHVlcyA9IHRoaXMuX2dldFRpY2tWYWx1ZXMoKTsKICAgICAgICAgICAgdmFyIHRpY2tMYWJlbHNVcGRhdGUgPSB0aGlzLl90aWNrTGFiZWxDb250YWluZXIuc2VsZWN0QWxsKCIuIiArIGF4aXMkMi5BeGlzLlRJQ0tfTEFCRUxfQ0xBU1MpLmRhdGEodGlja0xhYmVsVmFsdWVzKTsKICAgICAgICAgICAgdGlja0xhYmVsc1VwZGF0ZS5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzID0gdGlja0xhYmVsc1VwZGF0ZQogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoInRleHQiKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoYXhpcyQyLkF4aXMuVElDS19MQUJFTF9DTEFTUywgdHJ1ZSkKICAgICAgICAgICAgICAgIC5tZXJnZSh0aWNrTGFiZWxzVXBkYXRlKTsKICAgICAgICAgICAgdGlja0xhYmVscy5zdHlsZSgidGV4dC1hbmNob3IiLCB0aWNrTGFiZWxUZXh0QW5jaG9yKQogICAgICAgICAgICAgICAgLnN0eWxlKCJ2aXNpYmlsaXR5IiwgImluaGVyaXQiKQogICAgICAgICAgICAgICAgLmF0dHJzKHRpY2tMYWJlbEF0dHJIYXNoKQogICAgICAgICAgICAgICAgLnRleHQoZnVuY3Rpb24gKHMpIHsgcmV0dXJuIF90aGlzLmZvcm1hdHRlcigpKHMpOyB9KTsKICAgICAgICAgICAgdmFyIGxhYmVsR3JvdXBUcmFuc2Zvcm0gPSAidHJhbnNsYXRlKCIgKyBsYWJlbEdyb3VwVHJhbnNmb3JtWCArICIsICIgKyBsYWJlbEdyb3VwVHJhbnNmb3JtWSArICIpIjsKICAgICAgICAgICAgdGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLmF0dHIoInRyYW5zZm9ybSIsIGxhYmVsR3JvdXBUcmFuc2Zvcm0pOwogICAgICAgICAgICB0aGlzLl9zaG93QWxsVGlja01hcmtzKCk7CiAgICAgICAgICAgIGlmICghdGhpcy5zaG93RW5kVGlja0xhYmVscygpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9oaWRlRW5kVGlja0xhYmVscygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2hpZGVPdmVyZmxvd2luZ1RpY2tMYWJlbHMoKTsKICAgICAgICAgICAgdGhpcy5faGlkZU92ZXJsYXBwaW5nVGlja0xhYmVscygpOwogICAgICAgICAgICBpZiAodGhpcy5fdGlja0xhYmVsUG9zaXRpb25pbmcgIT09ICJjZW50ZXIiKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9oaWRlVGlja01hcmtzV2l0aG91dExhYmVsKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBOdW1lcmljLnByb3RvdHlwZS50aWNrTGFiZWxQb3NpdGlvbiA9IGZ1bmN0aW9uIChwb3NpdGlvbikgewogICAgICAgICAgICBpZiAocG9zaXRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3RpY2tMYWJlbFBvc2l0aW9uaW5nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdmFyIHBvc2l0aW9uTEMgPSBwb3NpdGlvbi50b0xvd2VyQ2FzZSgpOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuaXNIb3Jpem9udGFsKCkpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoIShwb3NpdGlvbkxDID09PSAibGVmdCIgfHwgcG9zaXRpb25MQyA9PT0gImNlbnRlciIgfHwgcG9zaXRpb25MQyA9PT0gInJpZ2h0IikpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKHBvc2l0aW9uTEMgKyAiIGlzIG5vdCBhIHZhbGlkIHRpY2sgbGFiZWwgcG9zaXRpb24gZm9yIGEgaG9yaXpvbnRhbCBOdW1lcmljQXhpcyIpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGlmICghKHBvc2l0aW9uTEMgPT09ICJ0b3AiIHx8IHBvc2l0aW9uTEMgPT09ICJjZW50ZXIiIHx8IHBvc2l0aW9uTEMgPT09ICJib3R0b20iKSkgewogICAgICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IocG9zaXRpb25MQyArICIgaXMgbm90IGEgdmFsaWQgdGljayBsYWJlbCBwb3NpdGlvbiBmb3IgYSB2ZXJ0aWNhbCBOdW1lcmljQXhpcyIpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3RpY2tMYWJlbFBvc2l0aW9uaW5nID0gcG9zaXRpb25MQzsKICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUudXNlc1RleHRXaWR0aEFwcHJveGltYXRpb24gPSBmdW5jdGlvbiAoZW5hYmxlKSB7CiAgICAgICAgICAgIGlmIChlbmFibGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3VzZXNUZXh0V2lkdGhBcHByb3hpbWF0aW9uOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fdXNlc1RleHRXaWR0aEFwcHJveGltYXRpb24gPSBlbmFibGU7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUuX2hpZGVFbmRUaWNrTGFiZWxzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgYm91bmRpbmdCb3ggPSB0aGlzLmVsZW1lbnQoKS5ub2RlKCkuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzID0gdGhpcy5fdGlja0xhYmVsQ29udGFpbmVyLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTKTsKICAgICAgICAgICAgaWYgKHRpY2tMYWJlbHMuc2l6ZSgpID09PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGZpcnN0VGlja0xhYmVsID0gdGlja0xhYmVscy5ub2RlcygpWzBdOwogICAgICAgICAgICBpZiAoIXV0aWxzJDEuRE9NLmNsaWVudFJlY3RJbnNpZGUoZmlyc3RUaWNrTGFiZWwuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCksIGJvdW5kaW5nQm94KSkgewogICAgICAgICAgICAgICAgZDMuc2VsZWN0KGZpcnN0VGlja0xhYmVsKS5zdHlsZSgidmlzaWJpbGl0eSIsICJoaWRkZW4iKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgbGFzdFRpY2tMYWJlbCA9IHRpY2tMYWJlbHMubm9kZXMoKVt0aWNrTGFiZWxzLnNpemUoKSAtIDFdOwogICAgICAgICAgICBpZiAoIXV0aWxzJDEuRE9NLmNsaWVudFJlY3RJbnNpZGUobGFzdFRpY2tMYWJlbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKSwgYm91bmRpbmdCb3gpKSB7CiAgICAgICAgICAgICAgICBkMy5zZWxlY3QobGFzdFRpY2tMYWJlbCkuc3R5bGUoInZpc2liaWxpdHkiLCAiaGlkZGVuIik7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIE51bWVyaWMucHJvdG90eXBlLl9oaWRlT3ZlcmxhcHBpbmdUaWNrTGFiZWxzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgdmlzaWJsZVRpY2tMYWJlbHMgPSB0aGlzLl90aWNrTGFiZWxDb250YWluZXIKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoIi4iICsgYXhpcyQyLkF4aXMuVElDS19MQUJFTF9DTEFTUykKICAgICAgICAgICAgICAgIC5maWx0ZXIoZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgIHZhciB2aXNpYmlsaXR5ID0gZDMuc2VsZWN0KHRoaXMpLnN0eWxlKCJ2aXNpYmlsaXR5Iik7CiAgICAgICAgICAgICAgICByZXR1cm4gKHZpc2liaWxpdHkgPT09ICJpbmhlcml0IikgfHwgKHZpc2liaWxpdHkgPT09ICJ2aXNpYmxlIik7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgdmlzaWJsZVRpY2tMYWJlbFJlY3RzID0gdmlzaWJsZVRpY2tMYWJlbHMubm9kZXMoKS5tYXAoZnVuY3Rpb24gKGxhYmVsKSB7IHJldHVybiBsYWJlbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsgfSk7CiAgICAgICAgICAgIHZhciBpbnRlcnZhbCA9IDE7CiAgICAgICAgICAgIHdoaWxlICghdGhpcy5faGFzT3ZlcmxhcFdpdGhJbnRlcnZhbChpbnRlcnZhbCwgdmlzaWJsZVRpY2tMYWJlbFJlY3RzKSAmJiBpbnRlcnZhbCA8IHZpc2libGVUaWNrTGFiZWxSZWN0cy5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIGludGVydmFsICs9IDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmlzaWJsZVRpY2tMYWJlbHMuZWFjaChmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgdmFyIHRpY2tMYWJlbCA9IGQzLnNlbGVjdCh0aGlzKTsKICAgICAgICAgICAgICAgIGlmIChpICUgaW50ZXJ2YWwgIT09IDApIHsKICAgICAgICAgICAgICAgICAgICB0aWNrTGFiZWwuc3R5bGUoInZpc2liaWxpdHkiLCAiaGlkZGVuIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG1ldGhvZCBpcyByZXNwb25zaWJsZSBmb3IgZXZlbmx5IHNwYWNpbmcgdGhlIGxhYmVscyBvbiB0aGUgYXhpcy4KICAgICAgICAgKiBAcmV0dXJuIHRlc3QgdG8gc2VlIGlmIHRha2luZyBldmVyeSBgaW50ZXJ2YWxgIHJlY3JhbmdsZSBmcm9tIGByZWN0c2AKICAgICAgICAgKiAgICAgICAgIHdpbGwgcmVzdWx0IGluIGxhYmVscyBub3Qgb3ZlcmxhcHBpbmcKICAgICAgICAgKgogICAgICAgICAqIEZvciB0b3AsIGJvdHRvbSwgbGVmdCwgcmlnaHQgcG9zaXRpb25pbmcgb2YgdGhlIHRoaWNrcywgd2Ugd2FudCB0aGUgcGFkZGluZwogICAgICAgICAqIGJldHdlZW4gdGhlIGxhYmVscyB0byBiZSAzeCwgc3VjaCB0aGF0IHRoZSBsYWJlbCB3aWxsIGJlICBgcGFkZGluZ2AgZGlzdGFuY2UKICAgICAgICAgKiBmcm9tIHRoZSB0aWNrIGFuZCAyICogYHBhZGRpbmdgIGRpc3RhbmNlIChvciBtb3JlKSBmcm9tIHRoZSBuZXh0IHRpY2s6CiAgICAgICAgICogc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci9wbG90dGFibGUvcHVsbC8xODEyCiAgICAgICAgICovCiAgICAgICAgTnVtZXJpYy5wcm90b3R5cGUuX2hhc092ZXJsYXBXaXRoSW50ZXJ2YWwgPSBmdW5jdGlvbiAoaW50ZXJ2YWwsIHJlY3RzKSB7CiAgICAgICAgICAgIHZhciBwYWRkaW5nID0gKHRoaXMuX3RpY2tMYWJlbFBvc2l0aW9uaW5nID09PSAiY2VudGVyIikKICAgICAgICAgICAgICAgID8gdGhpcy50aWNrTGFiZWxQYWRkaW5nKCkKICAgICAgICAgICAgICAgIDogdGhpcy50aWNrTGFiZWxQYWRkaW5nKCkgKiAzOwogICAgICAgICAgICB2YXIgcmVjdHNXaXRoUGFkZGluZyA9IHJlY3RzLm1hcChmdW5jdGlvbiAocmVjdCkgeyByZXR1cm4gdXRpbHMkMS5ET00uZXhwYW5kUmVjdChyZWN0LCBwYWRkaW5nKTsgfSk7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcmVjdHNXaXRoUGFkZGluZy5sZW5ndGggLSBpbnRlcnZhbDsgaSArPSBpbnRlcnZhbCkgewogICAgICAgICAgICAgICAgdmFyIGN1cnJSZWN0ID0gcmVjdHNXaXRoUGFkZGluZ1tpXTsKICAgICAgICAgICAgICAgIHZhciBuZXh0UmVjdCA9IHJlY3RzV2l0aFBhZGRpbmdbaSArIGludGVydmFsXTsKICAgICAgICAgICAgICAgIGlmICh1dGlscyQxLkRPTS5jbGllbnRSZWN0c092ZXJsYXAoY3VyclJlY3QsIG5leHRSZWN0KSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9OwogICAgICAgIE51bWVyaWMucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5pbnZhbGlkYXRlQ2FjaGUuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fbWVhc3VyZXIucmVzZXQoKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBOdW1lcmljOwogICAgfShheGlzJDIuQXhpcykpOwogICAgZXhwb3J0cy5OdW1lcmljID0gTnVtZXJpYzsKICAgIH0pOwoKICAgIHZhciB0aWNrR2VuZXJhdG9ycyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIFRpY2tHZW5lcmF0b3IgdXNpbmcgdGhlIHNwZWNpZmllZCBpbnRlcnZhbC4KICAgICAqCiAgICAgKiBHZW5lcmF0ZXMgdGlja3MgYXQgbXVsdGlwbGVzIG9mIHRoZSBpbnRlcnZhbCB3aGlsZSBhbHNvIGluY2x1ZGluZyB0aGUgZG9tYWluIGJvdW5kYXJpZXMuCiAgICAgKgogICAgICogQHBhcmFtIHtudW1iZXJ9IGludGVydmFsCiAgICAgKiBAcmV0dXJucyB7VGlja0dlbmVyYXRvcn0KICAgICAqLwogICAgZnVuY3Rpb24gaW50ZXJ2YWxUaWNrR2VuZXJhdG9yKGludGVydmFsKSB7CiAgICAgICAgaWYgKGludGVydmFsIDw9IDApIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJpbnRlcnZhbCBtdXN0IGJlIHBvc2l0aXZlIG51bWJlciIpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZnVuY3Rpb24gKHMpIHsKICAgICAgICAgICAgdmFyIGRvbWFpbiA9IHMuZG9tYWluKCk7CiAgICAgICAgICAgIHZhciBsb3cgPSBNYXRoLm1pbihkb21haW5bMF0sIGRvbWFpblsxXSk7CiAgICAgICAgICAgIHZhciBoaWdoID0gTWF0aC5tYXgoZG9tYWluWzBdLCBkb21haW5bMV0pOwogICAgICAgICAgICB2YXIgZmlyc3RUaWNrID0gTWF0aC5jZWlsKGxvdyAvIGludGVydmFsKSAqIGludGVydmFsOwogICAgICAgICAgICB2YXIgbnVtVGlja3MgPSBNYXRoLmZsb29yKChoaWdoIC0gZmlyc3RUaWNrKSAvIGludGVydmFsKSArIDE7CiAgICAgICAgICAgIHZhciBsb3dUaWNrcyA9IGxvdyAlIGludGVydmFsID09PSAwID8gW10gOiBbbG93XTsKICAgICAgICAgICAgdmFyIG1pZGRsZVRpY2tzID0gdXRpbHMkMS5NYXRoLnJhbmdlKDAsIG51bVRpY2tzKS5tYXAoZnVuY3Rpb24gKHQpIHsgcmV0dXJuIGZpcnN0VGljayArIHQgKiBpbnRlcnZhbDsgfSk7CiAgICAgICAgICAgIHZhciBoaWdoVGlja3MgPSBoaWdoICUgaW50ZXJ2YWwgPT09IDAgPyBbXSA6IFtoaWdoXTsKICAgICAgICAgICAgcmV0dXJuIGxvd1RpY2tzLmNvbmNhdChtaWRkbGVUaWNrcykuY29uY2F0KGhpZ2hUaWNrcyk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuaW50ZXJ2YWxUaWNrR2VuZXJhdG9yID0gaW50ZXJ2YWxUaWNrR2VuZXJhdG9yOwogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgVGlja0dlbmVyYXRvciByZXR1cm5zIG9ubHkgaW50ZWdlciB0aWNrIHZhbHVlcy4KICAgICAqCiAgICAgKiBAcmV0dXJucyB7VGlja0dlbmVyYXRvcn0KICAgICAqLwogICAgZnVuY3Rpb24gaW50ZWdlclRpY2tHZW5lcmF0b3IoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzKSB7CiAgICAgICAgICAgIHZhciBkZWZhdWx0VGlja3MgPSBzLmRlZmF1bHRUaWNrcygpOwogICAgICAgICAgICByZXR1cm4gZGVmYXVsdFRpY2tzLmZpbHRlcihmdW5jdGlvbiAodGljaywgaSkgeyByZXR1cm4gKHRpY2sgJSAxID09PSAwKSB8fCAoaSA9PT0gMCkgfHwgKGkgPT09IGRlZmF1bHRUaWNrcy5sZW5ndGggLSAxKTsgfSk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuaW50ZWdlclRpY2tHZW5lcmF0b3IgPSBpbnRlZ2VyVGlja0dlbmVyYXRvcjsKICAgIH0pOwoKICAgIHZhciBwYW5ab29tQ29uc3RyYWludHMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIC8qKgogICAgICogUmV0dXJuIGB2YWx1ZWAgaWYgaXRzIGRpc3RhbmNlIHRvIGBjZW50ZXJgIHdhcyBzY2FsZWQgYnkgYHpvb21gLgogICAgICoKICAgICAqIGUuZy4gem9vbU91dCgxMDAsIDIsIDUwKSAtPiAxNTAKICAgICAqIGUuZy4gem9vbU91dCgwLCAyLCA1MCkgLT4gLTUwCiAgICAgKiBlLmcuIHpvb21PdXQoMTAwLCAwLjUsIDUwKSAtPiA3NQogICAgICogZS5nLiB6b29tT3V0KDAsIDAuNSwgNTApIC0+IDI1CiAgICAgKi8KICAgIGZ1bmN0aW9uIHpvb21PdXQodmFsdWUsIHpvb20sIGNlbnRlcikgewogICAgICAgIHJldHVybiBjZW50ZXIgLSAoY2VudGVyIC0gdmFsdWUpICogem9vbTsKICAgIH0KICAgIGV4cG9ydHMuem9vbU91dCA9IHpvb21PdXQ7CiAgICAvKioKICAgICAqIFRoaXMgaXMgdGhlIHpvb21PdXQgbWV0aG9kIGFsZ2VicmEtZWQgdG8gc29sdmUgZm9yIHRoZSBgY2VudGVyYCB2YWx1ZQogICAgICogZ2l2ZW4gdGhlIG90aGVyIHRocmVlLiBUaGUgInRhcmdldCIgaXMgdGhlIHJldHVybiB2YWx1ZSBvZiB6b29tT3V0LgogICAgICovCiAgICBmdW5jdGlvbiBnZXRab29tT3V0Q2VudGVyKHZhbHVlLCB6b29tLCB0YXJnZXQpIHsKICAgICAgICByZXR1cm4gKHZhbHVlICogem9vbSAtIHRhcmdldCkgLyAoem9vbSAtIDEpOwogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm4gcG9zc2libHkgZGlmZmVyZW50IHpvb21BbW91bnQgYW5kIGNlbnRlclBvaW50IHZhbHVlcyBzdWNoIHRoYXQgYXBwbHlpbmcgdGhlIHpvb20KICAgICAqIHRvIHRoZSBzY2FsZSByZXNwZWN0cyB0aGUgZ2l2ZW4gbWluL21heCBleHRlbnRzIGFuZCB2YWx1ZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbnN0cmFpbmVkWm9vbShzY2FsZSwgem9vbUFtb3VudCwgY2VudGVyUG9pbnQsIG1pbkRvbWFpbkV4dGVudCwgbWF4RG9tYWluRXh0ZW50LCBtaW5Eb21haW5WYWx1ZSwgbWF4RG9tYWluVmFsdWUpIHsKICAgICAgICB6b29tQW1vdW50ID0gY29uc3RyYWluWm9vbUV4dGVudHMoc2NhbGUsIHpvb21BbW91bnQsIG1pbkRvbWFpbkV4dGVudCwgbWF4RG9tYWluRXh0ZW50KTsKICAgICAgICByZXR1cm4gY29uc3RyYWluWm9vbVZhbHVlcyhzY2FsZSwgem9vbUFtb3VudCwgY2VudGVyUG9pbnQsIG1pbkRvbWFpblZhbHVlLCBtYXhEb21haW5WYWx1ZSk7CiAgICB9CiAgICBleHBvcnRzLmNvbnN0cmFpbmVkWm9vbSA9IGNvbnN0cmFpbmVkWm9vbTsKICAgIGZ1bmN0aW9uIGNvbnN0cmFpblpvb21FeHRlbnRzKHNjYWxlLCB6b29tQW1vdW50LCBtaW5Eb21haW5FeHRlbnQsIG1heERvbWFpbkV4dGVudCkgewogICAgICAgIHZhciBleHRlbnRJbmNyZWFzaW5nID0gem9vbUFtb3VudCA+IDE7CiAgICAgICAgdmFyIGJvdW5kaW5nRG9tYWluRXh0ZW50ID0gZXh0ZW50SW5jcmVhc2luZyA/IG1heERvbWFpbkV4dGVudCA6IG1pbkRvbWFpbkV4dGVudDsKICAgICAgICBpZiAoYm91bmRpbmdEb21haW5FeHRlbnQgPT0gbnVsbCkgewogICAgICAgICAgICByZXR1cm4gem9vbUFtb3VudDsKICAgICAgICB9CiAgICAgICAgdmFyIF9hID0gc2NhbGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4oKSwgc2NhbGVEb21haW5NaW4gPSBfYVswXSwgc2NhbGVEb21haW5NYXggPSBfYVsxXTsKICAgICAgICB2YXIgZG9tYWluRXh0ZW50ID0gTWF0aC5hYnMoc2NhbGVEb21haW5NYXggLSBzY2FsZURvbWFpbk1pbik7CiAgICAgICAgdmFyIGNvbXBhcmVGID0gZXh0ZW50SW5jcmVhc2luZyA/IE1hdGgubWluIDogTWF0aC5tYXg7CiAgICAgICAgcmV0dXJuIGNvbXBhcmVGKHpvb21BbW91bnQsIGJvdW5kaW5nRG9tYWluRXh0ZW50IC8gZG9tYWluRXh0ZW50KTsKICAgIH0KICAgIGV4cG9ydHMuY29uc3RyYWluWm9vbUV4dGVudHMgPSBjb25zdHJhaW5ab29tRXh0ZW50czsKICAgIC8qKgogICAgICogTW9kaWZ5IHpvb21BbW91bnQgYW5kIGNlbnRlclBvaW50IHN1Y2ggdGhhdCBhIHBhbnpvb20gd2lsbCBzdGF5IGluc2lkZQogICAgICogdGhlIGJvdW5kcyBkZWZpbmVkIGJ5IG1pbkRvbWFpblZhbHVlIGFuZCBtYXhEb21haW5WYWx1ZS4KICAgICAqLwogICAgZnVuY3Rpb24gY29uc3RyYWluWm9vbVZhbHVlcyhzY2FsZSwgem9vbUFtb3VudCwgY2VudGVyUG9pbnQsIG1pbkRvbWFpblZhbHVlLCBtYXhEb21haW5WYWx1ZSkgewogICAgICAgIC8vIHdoZW4gem9vbWluZyBpbiwgd2UgZG9uJ3QgaGF2ZSB0byB3b3JyeSBhYm91dCBvdmVyZmxvd2luZyBkb21haW4KICAgICAgICBpZiAoem9vbUFtb3VudCA8PSAxKSB7CiAgICAgICAgICAgIHJldHVybiB7IGNlbnRlclBvaW50OiBjZW50ZXJQb2ludCwgem9vbUFtb3VudDogem9vbUFtb3VudCB9OwogICAgICAgIH0KICAgICAgICAvLyBpZiBubyBjb25zdHJhaW50cyBzZXQsIHdlJ3JlIGRvbmUKICAgICAgICBpZiAobWluRG9tYWluVmFsdWUgPT0gbnVsbCAmJiBtYXhEb21haW5WYWx1ZSA9PSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiB7IGNlbnRlclBvaW50OiBjZW50ZXJQb2ludCwgem9vbUFtb3VudDogem9vbUFtb3VudCB9OwogICAgICAgIH0KICAgICAgICB2YXIgcmFuZ2VSZXZlcnNlZCA9IGlzUmFuZ2VSZXZlcnNlZChzY2FsZSk7CiAgICAgICAgdmFyIGRvbWFpblJldmVyc2VkID0gaXNEb21haW5SZXZlcnNlZChzY2FsZSk7CiAgICAgICAgdmFyIGRlZmF1bHREb21haW5NaW4gPSBkb21haW5SZXZlcnNlZCA/IEluZmluaXR5IDogLUluZmluaXR5OwogICAgICAgIHZhciBkZWZhdWx0RG9tYWluTWF4ID0gZG9tYWluUmV2ZXJzZWQgPyAtSW5maW5pdHkgOiBJbmZpbml0eTsKICAgICAgICBtaW5Eb21haW5WYWx1ZSA9IG1pbkRvbWFpblZhbHVlID09IG51bGwgPyBkZWZhdWx0RG9tYWluTWluIDogbWluRG9tYWluVmFsdWU7CiAgICAgICAgbWF4RG9tYWluVmFsdWUgPSBtYXhEb21haW5WYWx1ZSA9PSBudWxsID8gZGVmYXVsdERvbWFpbk1heCA6IG1heERvbWFpblZhbHVlOwogICAgICAgIHZhciBfYSA9IHNjYWxlLmdldFRyYW5zZm9ybWF0aW9uRG9tYWluKCksIHNjYWxlRG9tYWluTWluID0gX2FbMF0sIHNjYWxlRG9tYWluTWF4ID0gX2FbMV07CiAgICAgICAgdmFyIG1heFJhbmdlID0gc2NhbGUuc2NhbGVUcmFuc2Zvcm1hdGlvbihtYXhEb21haW5WYWx1ZSk7CiAgICAgICAgdmFyIGN1cnJlbnRNYXhSYW5nZSA9IHNjYWxlLnNjYWxlVHJhbnNmb3JtYXRpb24oc2NhbGVEb21haW5NYXgpOwogICAgICAgIHZhciBuZXdNYXhSYW5nZSA9IHpvb21PdXQoY3VycmVudE1heFJhbmdlLCB6b29tQW1vdW50LCBjZW50ZXJQb2ludCk7CiAgICAgICAgdmFyIG1pblJhbmdlID0gc2NhbGUuc2NhbGVUcmFuc2Zvcm1hdGlvbihtaW5Eb21haW5WYWx1ZSk7CiAgICAgICAgdmFyIGN1cnJlbnRNaW5SYW5nZSA9IHNjYWxlLnNjYWxlVHJhbnNmb3JtYXRpb24oc2NhbGVEb21haW5NaW4pOwogICAgICAgIHZhciBuZXdNaW5SYW5nZSA9IHpvb21PdXQoY3VycmVudE1pblJhbmdlLCB6b29tQW1vdW50LCBjZW50ZXJQb2ludCk7CiAgICAgICAgdmFyIG1pbk1heExlbmd0aCA9IE1hdGguYWJzKG1heFJhbmdlIC0gbWluUmFuZ2UpOwogICAgICAgIHZhciBuZXdSYW5nZUxlbmd0aCA9IE1hdGguYWJzKG5ld01heFJhbmdlIC0gbmV3TWluUmFuZ2UpOwogICAgICAgIGlmIChuZXdSYW5nZUxlbmd0aCA+IG1pbk1heExlbmd0aCkgewogICAgICAgICAgICAvLyBUaGUgbmV3IHpvb20gc2ltcGx5IHdvbid0IGZpdC4gSW5zdGVhZCBqdXN0IHNldCB0aGUgem9vbSBhbW91bnQgdG8gYSBmdWxsIHpvb20gb3V0LgogICAgICAgICAgICB2YXIgd2FudGVkWm9vbUFtb3VudCA9IChtYXhSYW5nZSAtIG1pblJhbmdlKSAvIChjdXJyZW50TWF4UmFuZ2UgLSBjdXJyZW50TWluUmFuZ2UpOwogICAgICAgICAgICBpZiAod2FudGVkWm9vbUFtb3VudCAhPT0gMSkgewogICAgICAgICAgICAgICAgLy8gb25seSBzb2x2ZSBmb3IgY2VudGVyUG9pbnQgaWYgd2FudGVkWm9vbUFtb3VudCBpc24ndCAxIHRvIHByZXZlbnQgTmFOLgogICAgICAgICAgICAgICAgdmFyIHdhbnRlZENlbnRlclBvaW50ID0gZ2V0Wm9vbU91dENlbnRlcihjdXJyZW50TWF4UmFuZ2UsIHdhbnRlZFpvb21BbW91bnQsIG1heFJhbmdlKTsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgY2VudGVyUG9pbnQ6IHdhbnRlZENlbnRlclBvaW50LAogICAgICAgICAgICAgICAgICAgIHpvb21BbW91bnQ6IHdhbnRlZFpvb21BbW91bnQsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgLy8gdGhlIGNlbnRlclBvaW50IGRvZXNuJ3QgbWF0dGVyIGF0IGFsbCBoZXJlIGJ1dCB3ZSBtdXN0IGluY2x1ZGUgaXQKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgY2VudGVyUG9pbnQ6IGNlbnRlclBvaW50LAogICAgICAgICAgICAgICAgICAgIHpvb21BbW91bnQ6IHdhbnRlZFpvb21BbW91bnQsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICAvLyB0aGUgem9vbSBkb2VzIGZpdCwgYnV0IG9uZSBlbmQgaXMgb3V0c2lkZS4gSW4gdGhpcyBjYXNlIGp1c3QgbnVkZ2UgdGhlIGVkZ2UgaW4KICAgICAgICAgICAgaWYgKG5ld01heFJhbmdlID4gbWF4UmFuZ2UgIT0gcmFuZ2VSZXZlcnNlZCkgewogICAgICAgICAgICAgICAgLy8gcHJldmVudCBvdXQgb2YgYm91bmRzIG9uIG1heCBlZGdlLgogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBjZW50ZXJQb2ludDogZ2V0Wm9vbU91dENlbnRlcihjdXJyZW50TWF4UmFuZ2UsIHpvb21BbW91bnQsIG1heFJhbmdlKSwKICAgICAgICAgICAgICAgICAgICB6b29tQW1vdW50OiB6b29tQW1vdW50LAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmIChuZXdNaW5SYW5nZSA8IG1pblJhbmdlICE9IHJhbmdlUmV2ZXJzZWQpIHsKICAgICAgICAgICAgICAgIC8vIHByZXZlbnQgb3V0IG9mIGJvdW5kcyBvbiBtaW4gZWRnZS4KICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgY2VudGVyUG9pbnQ6IGdldFpvb21PdXRDZW50ZXIoY3VycmVudE1pblJhbmdlLCB6b29tQW1vdW50LCBtaW5SYW5nZSksCiAgICAgICAgICAgICAgICAgICAgem9vbUFtb3VudDogem9vbUFtb3VudCwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4geyBjZW50ZXJQb2ludDogY2VudGVyUG9pbnQsIHpvb21BbW91bnQ6IHpvb21BbW91bnQgfTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KICAgIGV4cG9ydHMuY29uc3RyYWluWm9vbVZhbHVlcyA9IGNvbnN0cmFpblpvb21WYWx1ZXM7CiAgICAvKioKICAgICAqIFJldHVybnMgYSBuZXcgdHJhbnNsYXRpb24gdmFsdWUgdGhhdCByZXNwZWN0cyBkb21haW4gbWluL21heCB2YWx1ZQogICAgICogY29uc3RyYWludHMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbnN0cmFpbmVkVHJhbnNsYXRpb24oc2NhbGUsIHRyYW5zbGF0aW9uLCBtaW5Eb21haW5WYWx1ZSwgbWF4RG9tYWluVmFsdWUpIHsKICAgICAgICB2YXIgX2EgPSBzY2FsZS5nZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbigpLCBzY2FsZURvbWFpbk1pbiA9IF9hWzBdLCBzY2FsZURvbWFpbk1heCA9IF9hWzFdOwogICAgICAgIHZhciByZXZlcnNlZCA9IGlzUmFuZ2VSZXZlcnNlZChzY2FsZSk7CiAgICAgICAgaWYgKHRyYW5zbGF0aW9uID4gMCAhPT0gcmV2ZXJzZWQpIHsKICAgICAgICAgICAgdmFyIGJvdW5kID0gbWF4RG9tYWluVmFsdWU7CiAgICAgICAgICAgIGlmIChib3VuZCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgY3VycmVudE1heFJhbmdlID0gc2NhbGUuc2NhbGVUcmFuc2Zvcm1hdGlvbihzY2FsZURvbWFpbk1heCk7CiAgICAgICAgICAgICAgICB2YXIgbWF4UmFuZ2UgPSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKGJvdW5kKTsKICAgICAgICAgICAgICAgIHRyYW5zbGF0aW9uID0gKHJldmVyc2VkID8gTWF0aC5tYXggOiBNYXRoLm1pbikoY3VycmVudE1heFJhbmdlICsgdHJhbnNsYXRpb24sIG1heFJhbmdlKSAtIGN1cnJlbnRNYXhSYW5nZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgdmFyIGJvdW5kID0gbWluRG9tYWluVmFsdWU7CiAgICAgICAgICAgIGlmIChib3VuZCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgY3VycmVudE1pblJhbmdlID0gc2NhbGUuc2NhbGVUcmFuc2Zvcm1hdGlvbihzY2FsZURvbWFpbk1pbik7CiAgICAgICAgICAgICAgICB2YXIgbWluUmFuZ2UgPSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKGJvdW5kKTsKICAgICAgICAgICAgICAgIHRyYW5zbGF0aW9uID0gKHJldmVyc2VkID8gTWF0aC5taW4gOiBNYXRoLm1heCkoY3VycmVudE1pblJhbmdlICsgdHJhbnNsYXRpb24sIG1pblJhbmdlKSAtIGN1cnJlbnRNaW5SYW5nZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJhbnNsYXRpb247CiAgICB9CiAgICBleHBvcnRzLmNvbnN0cmFpbmVkVHJhbnNsYXRpb24gPSBjb25zdHJhaW5lZFRyYW5zbGF0aW9uOwogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRydWUgaWZmIHRoZSBzY2FsZS5yYW5nZVsxXSA8IHNjYWxlLnJhbmdlWzBdLgogICAgICovCiAgICBmdW5jdGlvbiBpc1JhbmdlUmV2ZXJzZWQoc2NhbGUpIHsKICAgICAgICB2YXIgcmFuZ2UgPSBzY2FsZS5yYW5nZSgpOwogICAgICAgIHJldHVybiByYW5nZVsxXSA8IHJhbmdlWzBdOwogICAgfQogICAgZnVuY3Rpb24gaXNEb21haW5SZXZlcnNlZChzY2FsZSkgewogICAgICAgIHZhciBkb21haW4gPSBzY2FsZS5nZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbigpOwogICAgICAgIHJldHVybiBkb21haW5bMV0gPCBkb21haW5bMF07CiAgICB9CiAgICB9KTsKCiAgICB2YXIgc2NhbGUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgU2NhbGUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBTY2FsZSBpcyBhIGZ1bmN0aW9uIChpbiB0aGUgbWF0aGVtYXRpY2FsIHNlbnNlKSB0aGF0IG1hcHMgdmFsdWVzIGZyb20gYSBkb21haW4gdG8gYSByYW5nZS4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFNjYWxlKCkgewogICAgICAgICAgICB0aGlzLl9hdXRvRG9tYWluQXV0b21hdGljYWxseSA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX2RvbWFpbk1vZGlmaWNhdGlvbkluUHJvZ3Jlc3MgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlSWQgPSAwOwogICAgICAgICAgICB0aGlzLl9jYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICB0aGlzLl9pbmNsdWRlZFZhbHVlc1Byb3ZpZGVycyA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHaXZlbiBhbiBhcnJheSBvZiBwb3RlbnRpYWwgZG9tYWluIHZhbHVlcywgY29tcHV0ZXMgdGhlIGV4dGVudCBvZiB0aG9zZSB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RbXX0gdmFsdWVzCiAgICAgICAgICogQHJldHVybnMge0RbXX0gVGhlIGV4dGVudCBvZiB0aGUgaW5wdXQgdmFsdWVzLgogICAgICAgICAqLwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5leHRlbnRPZlZhbHVlcyA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOyAvLyB0aGlzIHNob3VsZCBiZSBvdmVyd3JpdHRlbgogICAgICAgIH07CiAgICAgICAgU2NhbGUucHJvdG90eXBlLl9nZXRBbGxJbmNsdWRlZFZhbHVlcyA9IGZ1bmN0aW9uIChpZ25vcmVBdHRhY2hTdGF0ZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAoaWdub3JlQXR0YWNoU3RhdGUgPT09IHZvaWQgMCkgeyBpZ25vcmVBdHRhY2hTdGF0ZSA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciBwcm92aWRlckFycmF5ID0gW107CiAgICAgICAgICAgIHRoaXMuX2luY2x1ZGVkVmFsdWVzUHJvdmlkZXJzLmZvckVhY2goZnVuY3Rpb24gKHByb3ZpZGVyKSB7CiAgICAgICAgICAgICAgICB2YXIgZXh0ZW50cyA9IHByb3ZpZGVyKF90aGlzLCBpZ25vcmVBdHRhY2hTdGF0ZSk7CiAgICAgICAgICAgICAgICBwcm92aWRlckFycmF5ID0gcHJvdmlkZXJBcnJheS5jb25jYXQoZXh0ZW50cyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gcHJvdmlkZXJBcnJheTsKICAgICAgICB9OwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5fZ2V0RXh0ZW50ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gW107IC8vIHRoaXMgc2hvdWxkIGJlIG92ZXJ3cml0dGVuCiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIFNjYWxlIHVwZGF0ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlQ2FsbGJhY2t9IGNhbGxiYWNrLgogICAgICAgICAqIEByZXR1cm5zIHtTY2FsZX0gVGhlIGNhbGxpbmcgU2NhbGUuCiAgICAgICAgICovCiAgICAgICAgU2NhbGUucHJvdG90eXBlLm9uVXBkYXRlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2NhbGxiYWNrcy5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIHRoZSBTY2FsZSB1cGRhdGVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtTY2FsZUNhbGxiYWNrfSBjYWxsYmFjay4KICAgICAgICAgKiBAcmV0dXJucyB7U2NhbGV9IFRoZSBjYWxsaW5nIFNjYWxlLgogICAgICAgICAqLwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5vZmZVcGRhdGUgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fY2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU2NhbGUucHJvdG90eXBlLl9kaXNwYXRjaFVwZGF0ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlSWQrKzsKICAgICAgICAgICAgdGhpcy5fY2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModGhpcyk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBTY2FsZSdzIGRvbWFpbiBzbyB0aGF0IGl0IHNwYW5zIHRoZSBFeHRlbnRzIG9mIGFsbCBpdHMgRXh0ZW50c1Byb3ZpZGVycy4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtTY2FsZX0gVGhlIGNhbGxpbmcgU2NhbGUuCiAgICAgICAgICovCiAgICAgICAgU2NhbGUucHJvdG90eXBlLmF1dG9Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuX2F1dG9Eb21haW5BdXRvbWF0aWNhbGx5ID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fc2V0RG9tYWluKHRoaXMuX2dldEV4dGVudCgpKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUcmlnZ2VycyBgLmF1dG9Eb21haW4oKWAgaWYgdGhlIGRvbWFpbiBpcyBub3QgZXhwbGljaXRseSBzZXQuCiAgICAgICAgICovCiAgICAgICAgU2NhbGUucHJvdG90eXBlLmF1dG9Eb21haW5JZkF1dG9tYXRpY01vZGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9hdXRvRG9tYWluQXV0b21hdGljYWxseSkgewogICAgICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENvbXB1dGVzIHRoZSByYW5nZSB2YWx1ZSBjb3JyZXNwb25kaW5nIHRvIGEgZ2l2ZW4gZG9tYWluIHZhbHVlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEfSB2YWx1ZQogICAgICAgICAqIEByZXR1cm5zIHtSfSBUaGUgcmFuZ2UgdmFsdWUgY29ycmVzcG9uZGluZyB0byB0aGUgc3VwcGxpZWQgZG9tYWluIHZhbHVlLgogICAgICAgICAqLwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5zY2FsZSA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlN1YmNsYXNzZXMgc2hvdWxkIG92ZXJyaWRlIHNjYWxlIik7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIGFuIGFycmF5IG9mIHRpY2sgdmFsdWVzIHNwYW5uaW5nIHRoZSBkb21haW4uCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJucyB7RFtdfQogICAgICAgICAqLwogICAgICAgIFNjYWxlLnByb3RvdHlwZS50aWNrcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuZG9tYWluKCk7CiAgICAgICAgfTsKICAgICAgICBTY2FsZS5wcm90b3R5cGUuZG9tYWluID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICBpZiAodmFsdWVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXREb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2F1dG9Eb21haW5BdXRvbWF0aWNhbGx5ID0gZmFsc2U7CiAgICAgICAgICAgICAgICB0aGlzLl9zZXREb21haW4odmFsdWVzKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTY2FsZS5wcm90b3R5cGUuX2dldERvbWFpbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTdWJjbGFzc2VzIHNob3VsZCBvdmVycmlkZSBfZ2V0RG9tYWluIik7CiAgICAgICAgfTsKICAgICAgICBTY2FsZS5wcm90b3R5cGUuX3NldERvbWFpbiA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9kb21haW5Nb2RpZmljYXRpb25JblByb2dyZXNzKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kb21haW5Nb2RpZmljYXRpb25JblByb2dyZXNzID0gdHJ1ZTsKICAgICAgICAgICAgICAgIHRoaXMuX2JhY2tpbmdTY2FsZURvbWFpbih2YWx1ZXMpOwogICAgICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2RvbWFpbk1vZGlmaWNhdGlvbkluUHJvZ3Jlc3MgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgU2NhbGUucHJvdG90eXBlLl9iYWNraW5nU2NhbGVEb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUgX2JhY2tpbmdEb21haW4iKTsKICAgICAgICB9OwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5yYW5nZSA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgaWYgKHZhbHVlcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZ2V0UmFuZ2UoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3NldFJhbmdlKHZhbHVlcyk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgU2NhbGUucHJvdG90eXBlLl9nZXRSYW5nZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTdWJjbGFzc2VzIHNob3VsZCBvdmVycmlkZSBfZ2V0UmFuZ2UiKTsKICAgICAgICB9OwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5fc2V0UmFuZ2UgPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUgX3NldFJhbmdlIik7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGFuIEluY2x1ZGVkVmFsdWVzUHJvdmlkZXIgdG8gdGhlIFNjYWxlLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtTY2FsZXMuSW5jbHVkZWRWYWx1ZXNQcm92aWRlcn0gcHJvdmlkZXIKICAgICAgICAgKiBAcmV0dXJucyB7U2NhbGV9IFRoZSBjYWxsaW5nIFNjYWxlLgogICAgICAgICAqLwogICAgICAgIFNjYWxlLnByb3RvdHlwZS5hZGRJbmNsdWRlZFZhbHVlc1Byb3ZpZGVyID0gZnVuY3Rpb24gKHByb3ZpZGVyKSB7CiAgICAgICAgICAgIHRoaXMuX2luY2x1ZGVkVmFsdWVzUHJvdmlkZXJzLmFkZChwcm92aWRlcik7CiAgICAgICAgICAgIHRoaXMuYXV0b0RvbWFpbklmQXV0b21hdGljTW9kZSgpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgdGhlIEluY2x1ZGVkVmFsdWVzUHJvdmlkZXIgZnJvbSB0aGUgU2NhbGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlcy5JbmNsdWRlZFZhbHVlc1Byb3ZpZGVyfSBwcm92aWRlcgogICAgICAgICAqIEByZXR1cm5zIHtTY2FsZX0gVGhlIGNhbGxpbmcgU2NhbGUuCiAgICAgICAgICovCiAgICAgICAgU2NhbGUucHJvdG90eXBlLnJlbW92ZUluY2x1ZGVkVmFsdWVzUHJvdmlkZXIgPSBmdW5jdGlvbiAocHJvdmlkZXIpIHsKICAgICAgICAgICAgdGhpcy5faW5jbHVkZWRWYWx1ZXNQcm92aWRlcnMuZGVsZXRlKHByb3ZpZGVyKTsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU2NhbGUucHJvdG90eXBlLnVwZGF0ZUlkID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fdXBkYXRlSWQ7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gU2NhbGU7CiAgICB9KCkpOwogICAgZXhwb3J0cy5TY2FsZSA9IFNjYWxlOwogICAgfSk7CgogICAgdmFyIGNhdGVnb3J5U2NhbGUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgogICAgdmFyIFRSQU5TRk9STUFUSU9OX1NQQUNFID0gWzAsIDFdOwogICAgdmFyIENhdGVnb3J5ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQ2F0ZWdvcnksIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBDYXRlZ29yeSBTY2FsZSBtYXBzIHN0cmluZ3MgdG8gbnVtYmVycy4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIENhdGVnb3J5KCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fcmFuZ2UgPSBbMCwgMV07CiAgICAgICAgICAgIF90aGlzLl9kM1NjYWxlID0gZDMuc2NhbGVCYW5kKCk7CiAgICAgICAgICAgIF90aGlzLl9kM1NjYWxlLnJhbmdlKFRSQU5TRk9STUFUSU9OX1NQQUNFKTsKICAgICAgICAgICAgX3RoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZSA9IGQzLnNjYWxlTGluZWFyKCk7CiAgICAgICAgICAgIF90aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuZG9tYWluKFRSQU5TRk9STUFUSU9OX1NQQUNFKTsKICAgICAgICAgICAgdmFyIGQzSW5uZXJQYWRkaW5nID0gMC4zOwogICAgICAgICAgICBfdGhpcy5faW5uZXJQYWRkaW5nID0gQ2F0ZWdvcnkuX2NvbnZlcnRUb1Bsb3R0YWJsZUlubmVyUGFkZGluZyhkM0lubmVyUGFkZGluZyk7CiAgICAgICAgICAgIF90aGlzLl9vdXRlclBhZGRpbmcgPSBDYXRlZ29yeS5fY29udmVydFRvUGxvdHRhYmxlT3V0ZXJQYWRkaW5nKDAuNSwgZDNJbm5lclBhZGRpbmcpOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiBhIGNsb25lIG9mIHRoaXMgY2F0ZWdvcnkgc2NhbGUgdGhhdCBob2xkcyB0aGUgc2FtZSBwYW4vem9vbSwgcGFkZGluZywgZG9tYWluIGFuZCByYW5nZSwgYnV0CiAgICAgICAgICogd2l0aG91dCBhbnkgaW5jbHVkZWQgdmFsdWVzIHByb3ZpZGVycy4KICAgICAgICAgKi8KICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuY2xvbmVXaXRob3V0UHJvdmlkZXJzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgc2NhbGUgPSBuZXcgQ2F0ZWdvcnkoKQogICAgICAgICAgICAgICAgLmRvbWFpbih0aGlzLmRvbWFpbigpKQogICAgICAgICAgICAgICAgLnJhbmdlKHRoaXMucmFuZ2UoKSkKICAgICAgICAgICAgICAgIC5pbm5lclBhZGRpbmcodGhpcy5pbm5lclBhZGRpbmcoKSkKICAgICAgICAgICAgICAgIC5vdXRlclBhZGRpbmcodGhpcy5vdXRlclBhZGRpbmcoKSk7CiAgICAgICAgICAgIHNjYWxlLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuZG9tYWluKHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZS5kb21haW4oKSk7CiAgICAgICAgICAgIHJldHVybiBzY2FsZTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5leHRlbnRPZlZhbHVlcyA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuQXJyYXkudW5pcSh2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLl9nZXRFeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB1dGlscyQxLkFycmF5LnVuaXEodGhpcy5fZ2V0QWxsSW5jbHVkZWRWYWx1ZXMoKSk7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuZG9tYWluID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5kb21haW4uY2FsbCh0aGlzLCB2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBkb21haW4gdmFsdWVzIHRoYXQgbGllIGluc2lkZSB0aGUgZ2l2ZW4gcmFuZ2UuCiAgICAgICAgICogQHBhcmFtIHJhbmdlCiAgICAgICAgICogQHJldHVybnMge3N0cmluZ1tdfQogICAgICAgICAqLwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5pbnZlcnRSYW5nZSA9IGZ1bmN0aW9uIChyYW5nZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAocmFuZ2UgPT09IHZvaWQgMCkgeyByYW5nZSA9IHRoaXMucmFuZ2UoKTsgfQogICAgICAgICAgICB2YXIgcmFuZ2VCYW5kID0gdGhpcy5fZDNTY2FsZS5iYW5kd2lkdGgoKTsKICAgICAgICAgICAgdmFyIGRvbWFpblN0YXJ0Tm9ybWFsaXplZCA9IHRoaXMuaW52ZXJ0ZWRUcmFuc2Zvcm1hdGlvbihyYW5nZVswXSk7CiAgICAgICAgICAgIHZhciBkb21haW5FbmROb3JtYWxpemVkID0gdGhpcy5pbnZlcnRlZFRyYW5zZm9ybWF0aW9uKHJhbmdlWzFdKTsKICAgICAgICAgICAgdmFyIGRvbWFpbiA9IHRoaXMuX2QzU2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIC8vIG1hcCBbImEiLCAiYiIsICJjIl0gdG8gdGhlIG5vcm1hbGl6ZWQgY2VudGVyIHBvc2l0aW9uIChlLmcuIFswLjI1LCAuNSwgMC43NV0pLiBXZSBhZGQKICAgICAgICAgICAgLy8gaGFsZiB0aGUgcmFuZ2VCYW5kIHRvIGNvbnNpZGVyIHRoZSBjZW50ZXIgb2YgdGhlIGJhcnMKICAgICAgICAgICAgdmFyIG5vcm1hbGl6ZWREb21haW4gPSBkb21haW4ubWFwKGZ1bmN0aW9uIChkKSB7IHJldHVybiBfdGhpcy5fZDNTY2FsZShkKSArIHJhbmdlQmFuZCAvIDI7IH0pOwogICAgICAgICAgICB2YXIgZG9tYWluU3RhcnQgPSBkMy5iaXNlY3Qobm9ybWFsaXplZERvbWFpbiwgZG9tYWluU3RhcnROb3JtYWxpemVkKTsKICAgICAgICAgICAgdmFyIGRvbWFpbkVuZCA9IGQzLmJpc2VjdChub3JtYWxpemVkRG9tYWluLCBkb21haW5FbmROb3JtYWxpemVkKTsKICAgICAgICAgICAgcmV0dXJuIGRvbWFpbi5zbGljZShkb21haW5TdGFydCwgZG9tYWluRW5kKTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5yYW5nZSA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUucmFuZ2UuY2FsbCh0aGlzLCB2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkuX2NvbnZlcnRUb1Bsb3R0YWJsZUlubmVyUGFkZGluZyA9IGZ1bmN0aW9uIChkM0lubmVyUGFkZGluZykgewogICAgICAgICAgICByZXR1cm4gMSAvICgxIC0gZDNJbm5lclBhZGRpbmcpIC0gMTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5Ll9jb252ZXJ0VG9QbG90dGFibGVPdXRlclBhZGRpbmcgPSBmdW5jdGlvbiAoZDNPdXRlclBhZGRpbmcsIGQzSW5uZXJQYWRkaW5nKSB7CiAgICAgICAgICAgIHJldHVybiBkM091dGVyUGFkZGluZyAvICgxIC0gZDNJbm5lclBhZGRpbmcpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLl9zZXRCYW5kcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGQzSW5uZXJQYWRkaW5nID0gMSAtIDEgLyAoMSArIHRoaXMuaW5uZXJQYWRkaW5nKCkpOwogICAgICAgICAgICB2YXIgZDNPdXRlclBhZGRpbmcgPSB0aGlzLm91dGVyUGFkZGluZygpIC8gKDEgKyB0aGlzLmlubmVyUGFkZGluZygpKTsKICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5wYWRkaW5nSW5uZXIoZDNJbm5lclBhZGRpbmcpOwogICAgICAgICAgICB0aGlzLl9kM1NjYWxlLnBhZGRpbmdPdXRlcihkM091dGVyUGFkZGluZyk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSB3aWR0aCBvZiB0aGUgcmFuZ2UgYmFuZC4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFRoZSByYW5nZSBiYW5kIHdpZHRoCiAgICAgICAgICovCiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnJhbmdlQmFuZCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Jlc2NhbGVCYW5kKHRoaXMuX2QzU2NhbGUuYmFuZHdpZHRoKCkpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgc3RlcCB3aWR0aCBvZiB0aGUgc2NhbGUuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgc3RlcCB3aWR0aCBpcyB0aGUgcGl4ZWwgZGlzdGFuY2UgYmV0d2VlbiBhZGphY2VudCB2YWx1ZXMgaW4gdGhlIGRvbWFpbi4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9CiAgICAgICAgICovCiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnN0ZXBXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgLy8gdG9kbyBjb25zaWRlciByZXBsYWNpbmcgdGhpcyB3aXRoIF9kM1NjYWxlLnN0ZXAoKQogICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVzY2FsZUJhbmQodGhpcy5fZDNTY2FsZS5iYW5kd2lkdGgoKSAqICgxICsgdGhpcy5pbm5lclBhZGRpbmcoKSkpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnRpY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5kb21haW4oKTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5pbm5lclBhZGRpbmcgPSBmdW5jdGlvbiAoaW5uZXJQYWRkaW5nKSB7CiAgICAgICAgICAgIGlmIChpbm5lclBhZGRpbmcgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2lubmVyUGFkZGluZzsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9pbm5lclBhZGRpbmcgPSBpbm5lclBhZGRpbmc7CiAgICAgICAgICAgIHRoaXMucmFuZ2UodGhpcy5yYW5nZSgpKTsKICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUub3V0ZXJQYWRkaW5nID0gZnVuY3Rpb24gKG91dGVyUGFkZGluZykgewogICAgICAgICAgICBpZiAob3V0ZXJQYWRkaW5nID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9vdXRlclBhZGRpbmc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fb3V0ZXJQYWRkaW5nID0gb3V0ZXJQYWRkaW5nOwogICAgICAgICAgICB0aGlzLnJhbmdlKHRoaXMucmFuZ2UoKSk7CiAgICAgICAgICAgIHRoaXMuX2Rpc3BhdGNoVXBkYXRlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnNjYWxlID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIC8vIERldGVybWluZSB0aGUgbWlkZGxlIG9mIHRoZSByYW5nZSBiYW5kIGZvciB0aGUgdmFsdWUKICAgICAgICAgICAgdmFyIHVudHJhbnNmb3JtZWQgPSB0aGlzLl9kM1NjYWxlKHZhbHVlKSArIHRoaXMuX2QzU2NhbGUuYmFuZHdpZHRoKCkgLyAyOwogICAgICAgICAgICAvLyBDb252ZXJ0IHRvIHNjcmVlbiBzcGFjZQogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNUcmFuc2Zvcm1hdGlvblNjYWxlKHVudHJhbnNmb3JtZWQpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLnpvb20gPSBmdW5jdGlvbiAobWFnbmlmeUFtb3VudCwgY2VudGVyVmFsdWUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIG1hZ25pZnlUcmFuc2Zvcm0gPSBmdW5jdGlvbiAocmFuZ2VWYWx1ZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuaW52ZXJ0KHBhblpvb21Db25zdHJhaW50cy56b29tT3V0KHJhbmdlVmFsdWUsIG1hZ25pZnlBbW91bnQsIGNlbnRlclZhbHVlKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZS5kb21haW4odGhpcy5fZDNUcmFuc2Zvcm1hdGlvblNjYWxlLnJhbmdlKCkubWFwKG1hZ25pZnlUcmFuc2Zvcm0pKTsKICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5wYW4gPSBmdW5jdGlvbiAodHJhbnNsYXRlQW1vdW50KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVUcmFuc2Zvcm0gPSBmdW5jdGlvbiAocmFuZ2VWYWx1ZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuaW52ZXJ0KHJhbmdlVmFsdWUgKyB0cmFuc2xhdGVBbW91bnQpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuZG9tYWluKHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZS5yYW5nZSgpLm1hcCh0cmFuc2xhdGVUcmFuc2Zvcm0pKTsKICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5zY2FsZVRyYW5zZm9ybWF0aW9uID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLmludmVydGVkVHJhbnNmb3JtYXRpb24gPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZS5pbnZlcnQodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgQ2F0ZWdvcnkucHJvdG90eXBlLmdldFRyYW5zZm9ybWF0aW9uRXh0ZW50ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gVFJBTlNGT1JNQVRJT05fU1BBQ0U7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUuZG9tYWluKCk7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuc2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoZG9tYWluKSB7CiAgICAgICAgICAgIHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZS5kb21haW4oZG9tYWluKTsKICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fZ2V0RG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fYmFja2luZ1NjYWxlRG9tYWluKCk7CiAgICAgICAgfTsKICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuX2JhY2tpbmdTY2FsZURvbWFpbiA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgaWYgKHZhbHVlcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5kb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2QzU2NhbGUuZG9tYWluKHZhbHVlcyk7CiAgICAgICAgICAgICAgICB0aGlzLl9zZXRCYW5kcygpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fZ2V0UmFuZ2UgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9yYW5nZTsKICAgICAgICB9OwogICAgICAgIENhdGVnb3J5LnByb3RvdHlwZS5fc2V0UmFuZ2UgPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRoaXMuX3JhbmdlID0gdmFsdWVzOwogICAgICAgICAgICB0aGlzLl9kM1RyYW5zZm9ybWF0aW9uU2NhbGUucmFuZ2UodmFsdWVzKTsKICAgICAgICAgICAgdGhpcy5fc2V0QmFuZHMoKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENvbnZlcnRzIGEgd2lkdGggb3IgaGVpZ2h0IGluICpUcmFuc2Zvcm1hdGlvbiBTcGFjZSogaW50byAqU2NyZWVuIFNwYWNlKi4KICAgICAgICAgKi8KICAgICAgICBDYXRlZ29yeS5wcm90b3R5cGUuX3Jlc2NhbGVCYW5kID0gZnVuY3Rpb24gKGJhbmQpIHsKICAgICAgICAgICAgcmV0dXJuIE1hdGguYWJzKHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZShiYW5kKSAtIHRoaXMuX2QzVHJhbnNmb3JtYXRpb25TY2FsZSgwKSk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ2F0ZWdvcnk7CiAgICB9KHNjYWxlLlNjYWxlKSk7CiAgICBleHBvcnRzLkNhdGVnb3J5ID0gQ2F0ZWdvcnk7CiAgICB9KTsKCiAgICB2YXIgY29sb3JTY2FsZSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIC8qKgogICAgICogV29ya2Fyb3VuZCBmb3IgYmFkIGQzIGJlaGF2aW9yLgogICAgICoKICAgICAqIGQzJ3MgY29sb3Igc2NhbGVzLCB3aGljaCBhcmUgb3JpZGluYWwgc2NhbGVzLCBoYXZlIHNpZGUtZWZmZWN0cyB3aGVuIGludm9rZWQuCiAgICAgKiBXaGVuIHlvdSBjYWxsIHRoZSBgc2NhbGUodmFsdWUpYCBhcyBhIGZ1bmN0aW9uLCBpdCB3aWxsIGltcGxpY2l0bHkgYWRkIG5ldwogICAgICogdmFsdWVzIHRvIHRoZSBkb21haW4uCiAgICAgKgogICAgICogVGhlc2Ugc2lkZS1lZmZlY3RzIGNhdXNlIHVzIHRvIHJlbHkgb24gbG9va2luZyB1cCB0aGUgY3VycmVudCBzY2FsZSBzdGF0ZQogICAgICogd2l0aCB0aGUgYC5kb21haW4oKWAgYW5kIGAucmFuZ2UoKWAgbWV0aG9kcy4gSG93ZXZlciwgdGhlc2UgbWV0aG9kcyBoYXZlIHBvb3IKICAgICAqIHBlcmZvcm1hbmNlIGltcGxpY2F0aW9ucyBzaW5jZSB0aGV5IHdpbGwgYWx3YXlzIHNsaWNlIHRoZWlyIGludGVybmFsIHZhbHVlcwogICAgICogYmVmb3JlIHJldHVybmluZy4gSW5zaWRlIHRoZSBpbm5lciByZW5kZXIgbG9vcCBvZiBjb2xvciBzY2F0dGVyIHBsb3QgcG9pbnRzLAogICAgICogdGhlc2Ugc2xpY2VzIGFkZCB1cC4KICAgICAqLwogICAgdmFyIEltcGxpY2l0U2VyaWVzVHJhY2tlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBJbXBsaWNpdFNlcmllc1RyYWNrZXIoKSB7CiAgICAgICAgICAgIHRoaXMuY291bnQgPSAwOwogICAgICAgICAgICB0aGlzLnRyYWNrZXIgPSB7fTsKICAgICAgICB9CiAgICAgICAgSW1wbGljaXRTZXJpZXNUcmFja2VyLnByb3RvdHlwZS5nZXRJbmRleCA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICBpZiAodGhpcy50cmFja2VyW3ZhbHVlXSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy50cmFja2VyW3ZhbHVlXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHZhciBpZHggPSB0aGlzLmNvdW50OwogICAgICAgICAgICAgICAgdGhpcy50cmFja2VyW3ZhbHVlXSA9IGlkeDsKICAgICAgICAgICAgICAgIHRoaXMuY291bnQgKz0gMTsKICAgICAgICAgICAgICAgIHJldHVybiBpZHg7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEltcGxpY2l0U2VyaWVzVHJhY2tlci5wcm90b3R5cGUuY2xlYXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuY291bnQgPSAwOwogICAgICAgICAgICB0aGlzLnRyYWNrZXIgPSB7fTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBJbXBsaWNpdFNlcmllc1RyYWNrZXI7CiAgICB9KCkpOwogICAgdmFyIENvbG9yID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQ29sb3IsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBDb2xvciBTY2FsZSBtYXBzIHN0cmluZyB2YWx1ZXMgdG8gY29sb3IgaGV4IHZhbHVlcyBleHByZXNzZWQgYXMgYSBzdHJpbmcuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW3NjYWxlVHlwZV0gT25lIG9mICJDYXRlZ29yeTEwIi8iQ2F0ZWdvcnkyMCIvIkNhdGVnb3J5MjBiIi8iQ2F0ZWdvcnkyMGMiLgogICAgICAgICAqICAgKHNlZSBodHRwczovL2dpdGh1Yi5jb20vbWJvc3RvY2svZDMvd2lraS9PcmRpbmFsLVNjYWxlcyNjYXRlZ29yaWNhbC1jb2xvcnMpCiAgICAgICAgICogICBJZiBub3Qgc3VwcGxpZWQsIHJlYWRzIHRoZSBjb2xvcnMgZGVmaW5lZCB1c2luZyBDU1MgLS0gc2VlIHBsb3R0YWJsZS5jc3MuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gQ29sb3Ioc2NhbGVUeXBlKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIC8vIENhY2hlIHRoZSBudW1iZXIgb2YgcmFuZ2UgdmFsdWUgdG8gYXZvaWQgY2FsbGluZyBgc2NhbGUucmFuZ2UoKS5sZW5ndGhgCiAgICAgICAgICAgIF90aGlzLl9yYW5nZUxlbmd0aCA9IDE7CiAgICAgICAgICAgIF90aGlzLl90cmFja2VyID0gbmV3IEltcGxpY2l0U2VyaWVzVHJhY2tlcigpOwogICAgICAgICAgICB2YXIgc2NhbGU7CiAgICAgICAgICAgIHN3aXRjaCAoc2NhbGVUeXBlKSB7CiAgICAgICAgICAgICAgICBjYXNlIG51bGw6CiAgICAgICAgICAgICAgICBjYXNlIHVuZGVmaW5lZDoKICAgICAgICAgICAgICAgICAgICBpZiAoQ29sb3IuX3Bsb3R0YWJsZUNvbG9yQ2FjaGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgICAgICBDb2xvci5fcGxvdHRhYmxlQ29sb3JDYWNoZSA9IENvbG9yLl9nZXRQbG90dGFibGVDb2xvcnMoKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgc2NhbGUgPSBkMy5zY2FsZU9yZGluYWwoKS5yYW5nZShDb2xvci5fcGxvdHRhYmxlQ29sb3JDYWNoZSk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlICJDYXRlZ29yeTEwIjoKICAgICAgICAgICAgICAgIGNhc2UgImNhdGVnb3J5MTAiOgogICAgICAgICAgICAgICAgY2FzZSAiMTAiOgogICAgICAgICAgICAgICAgICAgIHNjYWxlID0gZDMuc2NhbGVPcmRpbmFsKGQzLnNjaGVtZUNhdGVnb3J5MTApOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAiQ2F0ZWdvcnkyMCI6CiAgICAgICAgICAgICAgICBjYXNlICJjYXRlZ29yeTIwIjoKICAgICAgICAgICAgICAgIGNhc2UgIjIwIjoKICAgICAgICAgICAgICAgICAgICBzY2FsZSA9IGQzLnNjYWxlT3JkaW5hbChkMy5zY2hlbWVDYXRlZ29yeTIwKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgIkNhdGVnb3J5MjBiIjoKICAgICAgICAgICAgICAgIGNhc2UgImNhdGVnb3J5MjBiIjoKICAgICAgICAgICAgICAgIGNhc2UgIjIwYiI6CiAgICAgICAgICAgICAgICAgICAgc2NhbGUgPSBkMy5zY2FsZU9yZGluYWwoZDMuc2NoZW1lQ2F0ZWdvcnkyMGIpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAiQ2F0ZWdvcnkyMGMiOgogICAgICAgICAgICAgICAgY2FzZSAiY2F0ZWdvcnkyMGMiOgogICAgICAgICAgICAgICAgY2FzZSAiMjBjIjoKICAgICAgICAgICAgICAgICAgICBzY2FsZSA9IGQzLnNjYWxlT3JkaW5hbChkMy5zY2hlbWVDYXRlZ29yeTIwYyk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiVW5zdXBwb3J0ZWQgQ29sb3JTY2FsZSB0eXBlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgX3RoaXMuX2QzU2NhbGUgPSBzY2FsZTsKICAgICAgICAgICAgX3RoaXMuX3JhbmdlTGVuZ3RoID0gX3RoaXMuX2QzU2NhbGUucmFuZ2UoKS5sZW5ndGg7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgQ29sb3IucHJvdG90eXBlLmV4dGVudE9mVmFsdWVzID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5BcnJheS51bmlxKHZhbHVlcyk7CiAgICAgICAgfTsKICAgICAgICAvLyBEdXBsaWNhdGVkIGZyb20gT3JkaW5hbFNjYWxlLl9nZXRFeHRlbnQgLSBzaG91bGQgYmUgcmVtb3ZlZCBpbiAjMzg4CiAgICAgICAgQ29sb3IucHJvdG90eXBlLl9nZXRFeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB1dGlscyQxLkFycmF5LnVuaXEodGhpcy5fZ2V0QWxsSW5jbHVkZWRWYWx1ZXMoKSk7CiAgICAgICAgfTsKICAgICAgICBDb2xvci5pbnZhbGlkYXRlQ29sb3JDYWNoZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgQ29sb3IuX3Bsb3R0YWJsZUNvbG9yQ2FjaGUgPSBudWxsOwogICAgICAgIH07CiAgICAgICAgQ29sb3IuX2dldFBsb3R0YWJsZUNvbG9ycyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHBsb3R0YWJsZURlZmF1bHRDb2xvcnMgPSBbXTsKICAgICAgICAgICAgdmFyIGNvbG9yVGVzdGVyID0gZDMuc2VsZWN0KCJib2R5IikuYXBwZW5kKCJwbG90dGFibGUtY29sb3ItdGVzdGVyIik7CiAgICAgICAgICAgIHZhciBkZWZhdWx0Q29sb3JIZXggPSB1dGlscyQxLkNvbG9yLmNvbG9yVGVzdChjb2xvclRlc3RlciwgIiIpOwogICAgICAgICAgICB2YXIgaSA9IDA7CiAgICAgICAgICAgIHZhciBjb2xvckhleCA9IHV0aWxzJDEuQ29sb3IuY29sb3JUZXN0KGNvbG9yVGVzdGVyLCAicGxvdHRhYmxlLWNvbG9ycy0wIik7CiAgICAgICAgICAgIHdoaWxlIChjb2xvckhleCAhPSBudWxsICYmIGkgPCB0aGlzLl9NQVhJTVVNX0NPTE9SU19GUk9NX0NTUykgewogICAgICAgICAgICAgICAgaWYgKGNvbG9ySGV4ID09PSBkZWZhdWx0Q29sb3JIZXggJiYgY29sb3JIZXggPT09IHBsb3R0YWJsZURlZmF1bHRDb2xvcnNbcGxvdHRhYmxlRGVmYXVsdENvbG9ycy5sZW5ndGggLSAxXSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcGxvdHRhYmxlRGVmYXVsdENvbG9ycy5wdXNoKGNvbG9ySGV4KTsKICAgICAgICAgICAgICAgIGkrKzsKICAgICAgICAgICAgICAgIGNvbG9ySGV4ID0gdXRpbHMkMS5Db2xvci5jb2xvclRlc3QoY29sb3JUZXN0ZXIsICJwbG90dGFibGUtY29sb3JzLSIgKyBpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb2xvclRlc3Rlci5yZW1vdmUoKTsKICAgICAgICAgICAgcmV0dXJuIHBsb3R0YWJsZURlZmF1bHRDb2xvcnM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBjb2xvci1zdHJpbmcgY29ycmVzcG9uZGluZyB0byBhIGdpdmVuIHN0cmluZy4KICAgICAgICAgKgogICAgICAgICAqIElmIHRoZXJlIGFyZSBub3QgZW5vdWdoIGNvbG9ycyBpbiB0aGUgcmFuZ2UoKSwgYSBsaWdodGVuZWQgdmVyc2lvbiBvZiBhbgogICAgICAgICAqIGV4aXN0aW5nIGNvbG9yIHdpbGwgYmUgdXNlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB2YWx1ZQogICAgICAgICAqIEByZXR1cm5zIHtzdHJpbmd9CiAgICAgICAgICovCiAgICAgICAgQ29sb3IucHJvdG90eXBlLnNjYWxlID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHZhciBjb2xvciA9IHRoaXMuX2QzU2NhbGUodmFsdWUpOwogICAgICAgICAgICB2YXIgaW5kZXggPSB0aGlzLl90cmFja2VyLmdldEluZGV4KHZhbHVlKTsKICAgICAgICAgICAgdmFyIG51bUxvb3BlZCA9IE1hdGguZmxvb3IoaW5kZXggLyB0aGlzLl9yYW5nZUxlbmd0aCk7CiAgICAgICAgICAgIGlmIChudW1Mb29wZWQgPT09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiBjb2xvcjsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgbW9kaWZ5RmFjdG9yID0gTWF0aC5sb2cobnVtTG9vcGVkICogQ29sb3IuX0xPT1BfTElHSFRFTl9GQUNUT1IgKyAxKTsKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuQ29sb3IubGlnaHRlbkNvbG9yKGNvbG9yLCBtb2RpZnlGYWN0b3IpOwogICAgICAgIH07CiAgICAgICAgQ29sb3IucHJvdG90eXBlLl9nZXREb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9iYWNraW5nU2NhbGVEb21haW4oKTsKICAgICAgICB9OwogICAgICAgIENvbG9yLnByb3RvdHlwZS5fYmFja2luZ1NjYWxlRG9tYWluID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICBpZiAodmFsdWVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLmRvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5kb21haW4odmFsdWVzKTsKICAgICAgICAgICAgICAgIHRoaXMuX3RyYWNrZXIuY2xlYXIoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBDb2xvci5wcm90b3R5cGUuX2dldFJhbmdlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5yYW5nZSgpOwogICAgICAgIH07CiAgICAgICAgQ29sb3IucHJvdG90eXBlLl9zZXRSYW5nZSA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5yYW5nZSh2YWx1ZXMpOwogICAgICAgICAgICB0aGlzLl9yYW5nZUxlbmd0aCA9IHZhbHVlcy5sZW5ndGg7CiAgICAgICAgfTsKICAgICAgICBDb2xvci5fTE9PUF9MSUdIVEVOX0ZBQ1RPUiA9IDEuNjsKICAgICAgICAvLyBUaGUgbWF4aW11bSBudW1iZXIgb2YgY29sb3JzIHdlIGFyZSBnZXR0aW5nIGZyb20gQ1NTIHN0eWxlc2hlZXRzCiAgICAgICAgQ29sb3IuX01BWElNVU1fQ09MT1JTX0ZST01fQ1NTID0gMjU2OwogICAgICAgIHJldHVybiBDb2xvcjsKICAgIH0oc2NhbGUuU2NhbGUpKTsKICAgIGV4cG9ydHMuQ29sb3IgPSBDb2xvcjsKICAgIH0pOwoKICAgIHZhciBpbnRlcnBvbGF0ZWRDb2xvclNjYWxlID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgogICAgdmFyIEludGVycG9sYXRlZENvbG9yID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoSW50ZXJwb2xhdGVkQ29sb3IsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQW4gSW50ZXJwb2xhdGVkQ29sb3IgU2NhbGUgbWFwcyBudW1iZXJzIHRvIGNvbG9yIGhleCB2YWx1ZXMsIGV4cHJlc3NlZCBhcyBzdHJpbmdzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtzY2FsZVR5cGU9ImxpbmVhciJdIE9uZSBvZiAibGluZWFyIi8ibG9nIi8ic3FydCIvInBvdyIuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gSW50ZXJwb2xhdGVkQ29sb3Ioc2NhbGVUeXBlKSB7CiAgICAgICAgICAgIGlmIChzY2FsZVR5cGUgPT09IHZvaWQgMCkgeyBzY2FsZVR5cGUgPSAibGluZWFyIjsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBzd2l0Y2ggKHNjYWxlVHlwZSkgewogICAgICAgICAgICAgICAgY2FzZSAibGluZWFyIjoKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fY29sb3JTY2FsZSA9IGQzLnNjYWxlTGluZWFyKCk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlICJsb2ciOgogICAgICAgICAgICAgICAgICAgIF90aGlzLl9jb2xvclNjYWxlID0gZDMuc2NhbGVMb2coKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgInNxcnQiOgogICAgICAgICAgICAgICAgICAgIF90aGlzLl9jb2xvclNjYWxlID0gZDMuc2NhbGVTcXJ0KCk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlICJwb3ciOgogICAgICAgICAgICAgICAgICAgIF90aGlzLl9jb2xvclNjYWxlID0gZDMuc2NhbGVQb3coKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoX3RoaXMuX2NvbG9yU2NhbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJ1bmtub3duIFF1YW50aXRhdGl2ZVNjYWxlIHNjYWxlIHR5cGUgIiArIHNjYWxlVHlwZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgX3RoaXMucmFuZ2UoSW50ZXJwb2xhdGVkQ29sb3IuUkVEUyk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3IucHJvdG90eXBlLmV4dGVudE9mVmFsdWVzID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICB2YXIgZXh0ZW50ID0gZDMuZXh0ZW50KHZhbHVlcyk7CiAgICAgICAgICAgIGlmIChleHRlbnRbMF0gPT0gbnVsbCB8fCBleHRlbnRbMV0gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIGV4dGVudDsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2VuZXJhdGVzIHRoZSBjb252ZXJ0ZWQgUXVhbnRpdGF0aXZlU2NhbGUuCiAgICAgICAgICovCiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3IucHJvdG90eXBlLl9kM0ludGVycG9sYXRlZFNjYWxlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fY29sb3JTY2FsZS5yYW5nZShbMCwgMV0pLmludGVycG9sYXRlKHRoaXMuX2ludGVycG9sYXRlQ29sb3JzKCkpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2VuZXJhdGVzIHRoZSBkMyBpbnRlcnBvbGF0b3IgZm9yIGNvbG9ycy4KICAgICAgICAgKi8KICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvci5wcm90b3R5cGUuX2ludGVycG9sYXRlQ29sb3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgY29sb3JzID0gdGhpcy5fY29sb3JSYW5nZTsKICAgICAgICAgICAgaWYgKGNvbG9ycy5sZW5ndGggPCAyKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIkNvbG9yIHNjYWxlIGFycmF5cyBtdXN0IGhhdmUgYXQgbGVhc3QgdHdvIGVsZW1lbnRzLiIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbiAoYSwgYikgewogICAgICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uICh0KSB7CiAgICAgICAgICAgICAgICAgICAgLy8gQ2xhbXAgdCBwYXJhbWV0ZXIgdG8gWzAsMV0KICAgICAgICAgICAgICAgICAgICB0ID0gTWF0aC5tYXgoMCwgTWF0aC5taW4oMSwgdCkpOwogICAgICAgICAgICAgICAgICAgIC8vIERldGVybWluZSBpbmRpY2VzIGZvciBjb2xvcnMKICAgICAgICAgICAgICAgICAgICB2YXIgdFNjYWxlZCA9IHQgKiAoY29sb3JzLmxlbmd0aCAtIDEpOwogICAgICAgICAgICAgICAgICAgIHZhciBpMCA9IE1hdGguZmxvb3IodFNjYWxlZCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGkxID0gTWF0aC5jZWlsKHRTY2FsZWQpOwogICAgICAgICAgICAgICAgICAgIHZhciBmcmFjID0gKHRTY2FsZWQgLSBpMCk7CiAgICAgICAgICAgICAgICAgICAgLy8gSW50ZXJwb2xhdGUgaW4gdGhlIEwqYSpiIGNvbG9yIHNwYWNlCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGQzLmludGVycG9sYXRlTGFiKGNvbG9yc1tpMF0sIGNvbG9yc1tpMV0pKGZyYWMpOwogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yLnByb3RvdHlwZS5fcmVzZXRTY2FsZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fZDNTY2FsZSA9IHRoaXMuX2QzSW50ZXJwb2xhdGVkU2NhbGUoKTsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHRoaXMuX2Rpc3BhdGNoVXBkYXRlKCk7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvci5wcm90b3R5cGUuYXV0b0RvbWFpbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgLy8gSW50ZXJwb2xhdGVkQ29sb3JTY2FsZXMgZG8gbm90IHBhZAogICAgICAgICAgICB2YXIgaW5jbHVkZWRWYWx1ZXMgPSB0aGlzLl9nZXRBbGxJbmNsdWRlZFZhbHVlcygpOwogICAgICAgICAgICBpZiAoaW5jbHVkZWRWYWx1ZXMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fc2V0RG9tYWluKFt1dGlscyQxLk1hdGgubWluKGluY2x1ZGVkVmFsdWVzLCAwKSwgdXRpbHMkMS5NYXRoLm1heChpbmNsdWRlZFZhbHVlcywgMCldKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yLnByb3RvdHlwZS5zY2FsZSA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZSh2YWx1ZSk7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvci5wcm90b3R5cGUuX2dldERvbWFpbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2JhY2tpbmdTY2FsZURvbWFpbigpOwogICAgICAgIH07CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3IucHJvdG90eXBlLl9iYWNraW5nU2NhbGVEb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIGlmICh2YWx1ZXMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kM1NjYWxlLmRvbWFpbih2YWx1ZXMpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yLnByb3RvdHlwZS5fZ2V0UmFuZ2UgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb2xvclJhbmdlOwogICAgICAgIH07CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3IucHJvdG90eXBlLl9zZXRSYW5nZSA9IGZ1bmN0aW9uIChyYW5nZSkgewogICAgICAgICAgICB0aGlzLl9jb2xvclJhbmdlID0gcmFuZ2U7CiAgICAgICAgICAgIHRoaXMuX3Jlc2V0U2NhbGUoKTsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yLlJFRFMgPSBbCiAgICAgICAgICAgICIjRkZGRkZGIiwKICAgICAgICAgICAgIiNGRkY2RTEiLAogICAgICAgICAgICAiI0ZFRjRDMCIsCiAgICAgICAgICAgICIjRkVEOTc2IiwKICAgICAgICAgICAgIiNGRUIyNEMiLAogICAgICAgICAgICAiI0ZEOEQzQyIsCiAgICAgICAgICAgICIjRkM0RTJBIiwKICAgICAgICAgICAgIiNFMzFBMUMiLAogICAgICAgICAgICAiI0IxMDAyNiIsCiAgICAgICAgXTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvci5CTFVFUyA9IFsKICAgICAgICAgICAgIiNGRkZGRkYiLAogICAgICAgICAgICAiI0NDRkZGRiIsCiAgICAgICAgICAgICIjQTVGRkZEIiwKICAgICAgICAgICAgIiM4NUY3RkIiLAogICAgICAgICAgICAiIzZFRDNFRiIsCiAgICAgICAgICAgICIjNTVBN0UwIiwKICAgICAgICAgICAgIiM0MTdGRDAiLAogICAgICAgICAgICAiIzI1NDVEMyIsCiAgICAgICAgICAgICIjMEIwMkUxIiwKICAgICAgICBdOwogICAgICAgIEludGVycG9sYXRlZENvbG9yLlBPU05FRyA9IFsKICAgICAgICAgICAgIiMwQjAyRTEiLAogICAgICAgICAgICAiIzI1NDVEMyIsCiAgICAgICAgICAgICIjNDE3RkQwIiwKICAgICAgICAgICAgIiM1NUE3RTAiLAogICAgICAgICAgICAiIzZFRDNFRiIsCiAgICAgICAgICAgICIjODVGN0ZCIiwKICAgICAgICAgICAgIiNBNUZGRkQiLAogICAgICAgICAgICAiI0NDRkZGRiIsCiAgICAgICAgICAgICIjRkZGRkZGIiwKICAgICAgICAgICAgIiNGRkY2RTEiLAogICAgICAgICAgICAiI0ZFRjRDMCIsCiAgICAgICAgICAgICIjRkVEOTc2IiwKICAgICAgICAgICAgIiNGRUIyNEMiLAogICAgICAgICAgICAiI0ZEOEQzQyIsCiAgICAgICAgICAgICIjRkM0RTJBIiwKICAgICAgICAgICAgIiNFMzFBMUMiLAogICAgICAgICAgICAiI0IxMDAyNiIsCiAgICAgICAgXTsKICAgICAgICByZXR1cm4gSW50ZXJwb2xhdGVkQ29sb3I7CiAgICB9KHNjYWxlLlNjYWxlKSk7CiAgICBleHBvcnRzLkludGVycG9sYXRlZENvbG9yID0gSW50ZXJwb2xhdGVkQ29sb3I7CiAgICB9KTsKCiAgICB2YXIgcXVhbnRpdGF0aXZlU2NhbGUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgogICAgdmFyIFF1YW50aXRhdGl2ZVNjYWxlID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUXVhbnRpdGF0aXZlU2NhbGUsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBRdWFudGl0YXRpdmVTY2FsZSBpcyBhIFNjYWxlIHRoYXQgbWFwcyBudW1iZXItbGlrZSB2YWx1ZXMgdG8gbnVtYmVycy4KICAgICAgICAgKiBJdCBpcyBpbnZlcnRpYmxlIGFuZCBjb250aW51b3VzLgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gUXVhbnRpdGF0aXZlU2NhbGUoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl90aWNrR2VuZXJhdG9yID0gZnVuY3Rpb24gKHNjYWxlKSB7IHJldHVybiBzY2FsZS5kZWZhdWx0VGlja3MoKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3BhZFByb3BvcnRpb24gPSAwLjA1OwogICAgICAgICAgICBfdGhpcy5fc25hcHBpbmdEb21haW5FbmFibGVkID0gdHJ1ZTsKICAgICAgICAgICAgX3RoaXMuX3BhZGRpbmdFeGNlcHRpb25zUHJvdmlkZXJzID0gbmV3IHV0aWxzJDEuU2V0KCk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLmF1dG9Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuX2RvbWFpbk1pbiA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX2RvbWFpbk1heCA9IG51bGw7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuYXV0b0RvbWFpbi5jYWxsKHRoaXMpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5fZG9tYWluTWluICE9IG51bGwgJiYgdGhpcy5fZG9tYWluTWF4ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3NldERvbWFpbihbdGhpcy5fZG9tYWluTWluLCB0aGlzLl9kb21haW5NYXhdKTsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgY29tcHV0ZWRFeHRlbnQgPSB0aGlzLl9nZXRFeHRlbnQoKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2RvbWFpbk1pbiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgbWF4VmFsdWUgPSBjb21wdXRlZEV4dGVudFsxXTsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9kb21haW5NaW4gPj0gbWF4VmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICBtYXhWYWx1ZSA9IHRoaXMuX2V4cGFuZFNpbmdsZVZhbHVlRG9tYWluKFt0aGlzLl9kb21haW5NaW4sIHRoaXMuX2RvbWFpbk1pbl0pWzFdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5fc2V0RG9tYWluKFt0aGlzLl9kb21haW5NaW4sIG1heFZhbHVlXSk7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX2RvbWFpbk1heCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgbWluVmFsdWUgPSBjb21wdXRlZEV4dGVudFswXTsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9kb21haW5NYXggPD0gbWluVmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICBtaW5WYWx1ZSA9IHRoaXMuX2V4cGFuZFNpbmdsZVZhbHVlRG9tYWluKFt0aGlzLl9kb21haW5NYXgsIHRoaXMuX2RvbWFpbk1heF0pWzBdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5fc2V0RG9tYWluKFttaW5WYWx1ZSwgdGhpcy5fZG9tYWluTWF4XSk7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlLmNhbGwodGhpcyk7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuX2dldFVuYm91bmRlZEV4dGVudCA9IGZ1bmN0aW9uIChpZ25vcmVBdHRhY2hTdGF0ZSkgewogICAgICAgICAgICBpZiAoaWdub3JlQXR0YWNoU3RhdGUgPT09IHZvaWQgMCkgeyBpZ25vcmVBdHRhY2hTdGF0ZSA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciBpbmNsdWRlZFZhbHVlcyA9IHRoaXMuX2dldEFsbEluY2x1ZGVkVmFsdWVzKGlnbm9yZUF0dGFjaFN0YXRlKTsKICAgICAgICAgICAgdmFyIGV4dGVudCA9IHRoaXMuX2RlZmF1bHRFeHRlbnQoKTsKICAgICAgICAgICAgaWYgKGluY2x1ZGVkVmFsdWVzLmxlbmd0aCAhPT0gMCkgewogICAgICAgICAgICAgICAgdmFyIGNvbWJpbmVkRXh0ZW50ID0gWwogICAgICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5taW4oaW5jbHVkZWRWYWx1ZXMsIGV4dGVudFswXSksCiAgICAgICAgICAgICAgICAgICAgdXRpbHMkMS5NYXRoLm1heChpbmNsdWRlZFZhbHVlcywgZXh0ZW50WzFdKSwKICAgICAgICAgICAgICAgIF07CiAgICAgICAgICAgICAgICBleHRlbnQgPSB0aGlzLl9wYWREb21haW4oY29tYmluZWRFeHRlbnQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBleHRlbnQ7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuX2dldEV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGV4dGVudCA9IHRoaXMuX2dldFVuYm91bmRlZEV4dGVudCgpOwogICAgICAgICAgICBpZiAodGhpcy5fZG9tYWluTWluICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGV4dGVudFswXSA9IHRoaXMuX2RvbWFpbk1pbjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fZG9tYWluTWF4ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGV4dGVudFsxXSA9IHRoaXMuX2RvbWFpbk1heDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZXh0ZW50OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIHBhZGRpbmcgZXhjZXB0aW9uIHByb3ZpZGVyLgogICAgICAgICAqIElmIG9uZSBlbmQgb2YgdGhlIGRvbWFpbiBpcyBzZXQgdG8gYW4gZXhjZXB0ZWQgdmFsdWUgYXMgYSByZXN1bHQgb2YgYXV0b0RvbWFpbigpLWluZywKICAgICAgICAgKiB0aGF0IGVuZCBvZiB0aGUgZG9tYWluIHdpbGwgbm90IGJlIHBhZGRlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7U2NhbGVzLlBhZGRpbmdFeGNlcHRpb25Qcm92aWRlcjxEPn0gcHJvdmlkZXIgVGhlIHByb3ZpZGVyIGZ1bmN0aW9uLgogICAgICAgICAqIEByZXR1cm5zIHtRdWFudGl0YXRpdmVTY2FsZX0gVGhlIGNhbGxpbmcgUXVhbnRpdGF0aXZlU2NhbGUuCiAgICAgICAgICovCiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLmFkZFBhZGRpbmdFeGNlcHRpb25zUHJvdmlkZXIgPSBmdW5jdGlvbiAocHJvdmlkZXIpIHsKICAgICAgICAgICAgdGhpcy5fcGFkZGluZ0V4Y2VwdGlvbnNQcm92aWRlcnMuYWRkKHByb3ZpZGVyKTsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyB0aGUgcGFkZGluZyBleGNlcHRpb24gcHJvdmlkZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlcy5QYWRkaW5nRXhjZXB0aW9uUHJvdmlkZXI8RD59IHByb3ZpZGVyIFRoZSBwcm92aWRlciBmdW5jdGlvbi4KICAgICAgICAgKiBAcmV0dXJucyB7UXVhbnRpdGF0aXZlU2NhbGV9IFRoZSBjYWxsaW5nIFF1YW50aXRhdGl2ZVNjYWxlLgogICAgICAgICAqLwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5yZW1vdmVQYWRkaW5nRXhjZXB0aW9uc1Byb3ZpZGVyID0gZnVuY3Rpb24gKHByb3ZpZGVyKSB7CiAgICAgICAgICAgIHRoaXMuX3BhZGRpbmdFeGNlcHRpb25zUHJvdmlkZXJzLmRlbGV0ZShwcm92aWRlcik7CiAgICAgICAgICAgIHRoaXMuYXV0b0RvbWFpbklmQXV0b21hdGljTW9kZSgpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5wYWRQcm9wb3J0aW9uID0gZnVuY3Rpb24gKHBhZFByb3BvcnRpb24pIHsKICAgICAgICAgICAgaWYgKHBhZFByb3BvcnRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3BhZFByb3BvcnRpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHBhZFByb3BvcnRpb24gPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoInBhZFByb3BvcnRpb24gbXVzdCBiZSBub24tbmVnYXRpdmUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9wYWRQcm9wb3J0aW9uID0gcGFkUHJvcG9ydGlvbjsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLl9wYWREb21haW4gPSBmdW5jdGlvbiAoZG9tYWluKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmIChkb21haW5bMF0udmFsdWVPZigpID09PSBkb21haW5bMV0udmFsdWVPZigpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZXhwYW5kU2luZ2xlVmFsdWVEb21haW4oZG9tYWluKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fcGFkUHJvcG9ydGlvbiA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGRvbWFpbjsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgcCA9IHRoaXMuX3BhZFByb3BvcnRpb24gLyAyOwogICAgICAgICAgICB2YXIgbWluID0gZG9tYWluWzBdOwogICAgICAgICAgICB2YXIgbWF4ID0gZG9tYWluWzFdOwogICAgICAgICAgICB2YXIgbWluRXhpc3RzSW5FeGNlcHRpb25zID0gZmFsc2U7CiAgICAgICAgICAgIHZhciBtYXhFeGlzdHNJbkV4Y2VwdGlvbnMgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fcGFkZGluZ0V4Y2VwdGlvbnNQcm92aWRlcnMuZm9yRWFjaChmdW5jdGlvbiAocHJvdmlkZXIpIHsKICAgICAgICAgICAgICAgIHZhciB2YWx1ZXMgPSBwcm92aWRlcihfdGhpcyk7CiAgICAgICAgICAgICAgICB2YWx1ZXMuZm9yRWFjaChmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICBpZiAodmFsdWUudmFsdWVPZigpID09PSBtaW4udmFsdWVPZigpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIG1pbkV4aXN0c0luRXhjZXB0aW9ucyA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmICh2YWx1ZS52YWx1ZU9mKCkgPT09IG1heC52YWx1ZU9mKCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgbWF4RXhpc3RzSW5FeGNlcHRpb25zID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciBvcmlnaW5hbERvbWFpbiA9IHRoaXMuX2JhY2tpbmdTY2FsZURvbWFpbigpOwogICAgICAgICAgICB0aGlzLl9iYWNraW5nU2NhbGVEb21haW4oZG9tYWluKTsKICAgICAgICAgICAgdmFyIG5ld01pbiA9IG1pbkV4aXN0c0luRXhjZXB0aW9ucyA/IG1pbiA6IHRoaXMuaW52ZXJ0KHRoaXMuc2NhbGUobWluKSAtICh0aGlzLnNjYWxlKG1heCkgLSB0aGlzLnNjYWxlKG1pbikpICogcCk7CiAgICAgICAgICAgIHZhciBuZXdNYXggPSBtYXhFeGlzdHNJbkV4Y2VwdGlvbnMgPyBtYXggOiB0aGlzLmludmVydCh0aGlzLnNjYWxlKG1heCkgKyAodGhpcy5zY2FsZShtYXgpIC0gdGhpcy5zY2FsZShtaW4pKSAqIHApOwogICAgICAgICAgICB0aGlzLl9iYWNraW5nU2NhbGVEb21haW4ob3JpZ2luYWxEb21haW4pOwogICAgICAgICAgICBpZiAodGhpcy5fc25hcHBpbmdEb21haW5FbmFibGVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbmljZURvbWFpbihbbmV3TWluLCBuZXdNYXhdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gKFtuZXdNaW4sIG5ld01heF0pOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLnNuYXBwaW5nRG9tYWluRW5hYmxlZCA9IGZ1bmN0aW9uIChzbmFwcGluZ0RvbWFpbkVuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKHNuYXBwaW5nRG9tYWluRW5hYmxlZCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fc25hcHBpbmdEb21haW5FbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NuYXBwaW5nRG9tYWluRW5hYmxlZCA9IHNuYXBwaW5nRG9tYWluRW5hYmxlZDsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLl9leHBhbmRTaW5nbGVWYWx1ZURvbWFpbiA9IGZ1bmN0aW9uIChzaW5nbGVWYWx1ZURvbWFpbikgewogICAgICAgICAgICByZXR1cm4gc2luZ2xlVmFsdWVEb21haW47CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgZG9tYWluIHZhbHVlIGNvcnJlc3BvbmRpbmcgdG8gYSBzdXBwbGllZCByYW5nZSB2YWx1ZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSB2YWx1ZTogQSB2YWx1ZSBmcm9tIHRoZSBTY2FsZSdzIHJhbmdlLgogICAgICAgICAqIEByZXR1cm5zIHtEfSBUaGUgZG9tYWluIHZhbHVlIGNvcnJlc3BvbmRpbmcgdG8gdGhlIHN1cHBsaWVkIHJhbmdlIHZhbHVlLgogICAgICAgICAqLwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5pbnZlcnQgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTdWJjbGFzc2VzIHNob3VsZCBvdmVycmlkZSBpbnZlcnQiKTsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5kb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIGlmICh2YWx1ZXMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fZG9tYWluTWluID0gdmFsdWVzWzBdOwogICAgICAgICAgICAgICAgdGhpcy5fZG9tYWluTWF4ID0gdmFsdWVzWzFdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLmRvbWFpbi5jYWxsKHRoaXMsIHZhbHVlcyk7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuZG9tYWluTWluID0gZnVuY3Rpb24gKGRvbWFpbk1pbikgewogICAgICAgICAgICBpZiAoZG9tYWluTWluID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLmRvbWFpbigpWzBdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2RvbWFpbk1pbiA9IGRvbWFpbk1pbjsKICAgICAgICAgICAgdGhpcy5hdXRvRG9tYWluSWZBdXRvbWF0aWNNb2RlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLmRvbWFpbk1heCA9IGZ1bmN0aW9uIChkb21haW5NYXgpIHsKICAgICAgICAgICAgaWYgKGRvbWFpbk1heCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5kb21haW4oKVsxXTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9kb21haW5NYXggPSBkb21haW5NYXg7CiAgICAgICAgICAgIHRoaXMuYXV0b0RvbWFpbklmQXV0b21hdGljTW9kZSgpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5leHRlbnRPZlZhbHVlcyA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgLy8gSEFDS0hBQ0s6IFRTMS40IGRvZXNuJ3QgY29uc2lkZXIgbnVtYmVycyB0byBiZSBOdW1iZXItbGlrZSAodmFsdWVPZigpIHJldHVybmluZyBudW1iZXIpLCBzbyBEIGNhbid0IGJlIHR5cGVkIGNvcnJlY3RseQogICAgICAgICAgICB2YXIgZXh0ZW50ID0gZDMuZXh0ZW50KHZhbHVlcy5maWx0ZXIoZnVuY3Rpb24gKHZhbHVlKSB7IHJldHVybiB1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcigrdmFsdWUpOyB9KSk7CiAgICAgICAgICAgIGlmIChleHRlbnRbMF0gPT0gbnVsbCB8fCBleHRlbnRbMV0gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIGV4dGVudDsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLnpvb20gPSBmdW5jdGlvbiAobWFnbmlmeUFtb3VudCwgY2VudGVyVmFsdWUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIG1hZ25pZnlUcmFuc2Zvcm0gPSBmdW5jdGlvbiAocmFuZ2VWYWx1ZSkgeyByZXR1cm4gX3RoaXMuaW52ZXJ0KHBhblpvb21Db25zdHJhaW50cy56b29tT3V0KHJhbmdlVmFsdWUsIG1hZ25pZnlBbW91bnQsIGNlbnRlclZhbHVlKSk7IH07CiAgICAgICAgICAgIHRoaXMuZG9tYWluKHRoaXMucmFuZ2UoKS5tYXAobWFnbmlmeVRyYW5zZm9ybSkpOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLnBhbiA9IGZ1bmN0aW9uICh0cmFuc2xhdGVBbW91bnQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHRyYW5zbGF0ZVRyYW5zZm9ybSA9IGZ1bmN0aW9uIChyYW5nZVZhbHVlKSB7IHJldHVybiBfdGhpcy5pbnZlcnQocmFuZ2VWYWx1ZSArIHRyYW5zbGF0ZUFtb3VudCk7IH07CiAgICAgICAgICAgIHRoaXMuZG9tYWluKHRoaXMucmFuZ2UoKS5tYXAodHJhbnNsYXRlVHJhbnNmb3JtKSk7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuc2NhbGVUcmFuc2Zvcm1hdGlvbiA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlN1YmNsYXNzZXMgc2hvdWxkIG92ZXJyaWRlIHNjYWxlVHJhbnNmb3JtYXRpb24iKTsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5pbnZlcnRlZFRyYW5zZm9ybWF0aW9uID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUgaW52ZXJ0ZWRUcmFuc2Zvcm1hdGlvbiIpOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLmdldFRyYW5zZm9ybWF0aW9uRXh0ZW50ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlN1YmNsYXNzZXMgc2hvdWxkIG92ZXJyaWRlIGdldFRyYW5zZm9ybWF0aW9uRXh0ZW50Iik7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUgZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4iKTsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS5zZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbiA9IGZ1bmN0aW9uIChkb21haW4pIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTdWJjbGFzc2VzIHNob3VsZCBvdmVycmlkZSBzZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbiIpOwogICAgICAgIH07CiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLl9zZXREb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHZhciBpc05hTk9ySW5maW5pdHkgPSBmdW5jdGlvbiAoeCkgeyByZXR1cm4gdXRpbHMkMS5NYXRoLmlzTmFOKHgpIHx8IHggPT09IEluZmluaXR5IHx8IHggPT09IC1JbmZpbml0eTsgfTsKICAgICAgICAgICAgaWYgKGlzTmFOT3JJbmZpbml0eSh2YWx1ZXNbMF0pIHx8IGlzTmFOT3JJbmZpbml0eSh2YWx1ZXNbMV0pKSB7CiAgICAgICAgICAgICAgICB1dGlscyQxLldpbmRvdy53YXJuKCJXYXJuaW5nOiBRdWFudGl0YXRpdmVTY2FsZXMgY2Fubm90IHRha2UgTmFOIG9yIEluZmluaXR5IGFzIGEgZG9tYWluIHZhbHVlLiBJZ25vcmluZy4iKTsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXREb21haW4uY2FsbCh0aGlzLCB2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgYXJyYXkgb2YgdGljayB2YWx1ZXMgZ2VuZXJhdGVkIGJ5IHRoZSBkZWZhdWx0IGFsZ29yaXRobS4KICAgICAgICAgKi8KICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuZGVmYXVsdFRpY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlN1YmNsYXNzZXMgc2hvdWxkIG92ZXJyaWRlIF9nZXREZWZhdWx0VGlja3MiKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgYW4gYXJyYXkgb2YgdGljayB2YWx1ZXMgc3Bhbm5pbmcgdGhlIGRvbWFpbi4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtEW119CiAgICAgICAgICovCiAgICAgICAgUXVhbnRpdGF0aXZlU2NhbGUucHJvdG90eXBlLnRpY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fdGlja0dlbmVyYXRvcih0aGlzKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdpdmVuIGEgZG9tYWluLCBleHBhbmRzIGl0cyBkb21haW4gb250byAibmljZSIgdmFsdWVzLCBlLmcuIHdob2xlCiAgICAgICAgICogbnVtYmVycy4KICAgICAgICAgKi8KICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuX25pY2VEb21haW4gPSBmdW5jdGlvbiAoZG9tYWluLCBjb3VudCkgewogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlN1YmNsYXNzZXMgc2hvdWxkIG92ZXJyaWRlIF9uaWNlRG9tYWluIik7CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5wcm90b3R5cGUuX2RlZmF1bHRFeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU3ViY2xhc3NlcyBzaG91bGQgb3ZlcnJpZGUgX2RlZmF1bHRFeHRlbnQiKTsKICAgICAgICB9OwogICAgICAgIFF1YW50aXRhdGl2ZVNjYWxlLnByb3RvdHlwZS50aWNrR2VuZXJhdG9yID0gZnVuY3Rpb24gKGdlbmVyYXRvcikgewogICAgICAgICAgICBpZiAoZ2VuZXJhdG9yID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl90aWNrR2VuZXJhdG9yOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fdGlja0dlbmVyYXRvciA9IGdlbmVyYXRvcjsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBRdWFudGl0YXRpdmVTY2FsZS5fREVGQVVMVF9OVU1fVElDS1MgPSAxMDsKICAgICAgICByZXR1cm4gUXVhbnRpdGF0aXZlU2NhbGU7CiAgICB9KHNjYWxlLlNjYWxlKSk7CiAgICBleHBvcnRzLlF1YW50aXRhdGl2ZVNjYWxlID0gUXVhbnRpdGF0aXZlU2NhbGU7CiAgICB9KTsKCiAgICB2YXIgbGluZWFyU2NhbGUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKICAgIHZhciBMaW5lYXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhMaW5lYXIsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gTGluZWFyKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fZDNTY2FsZSA9IGQzLnNjYWxlTGluZWFyKCk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5fZGVmYXVsdEV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIFswLCAxXTsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuX2V4cGFuZFNpbmdsZVZhbHVlRG9tYWluID0gZnVuY3Rpb24gKHNpbmdsZVZhbHVlRG9tYWluKSB7CiAgICAgICAgICAgIGlmIChzaW5nbGVWYWx1ZURvbWFpblswXSA9PT0gc2luZ2xlVmFsdWVEb21haW5bMV0pIHsKICAgICAgICAgICAgICAgIHJldHVybiBbc2luZ2xlVmFsdWVEb21haW5bMF0gLSAxLCBzaW5nbGVWYWx1ZURvbWFpblsxXSArIDFdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBzaW5nbGVWYWx1ZURvbWFpbjsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuc2NhbGUgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5zY2FsZVRyYW5zZm9ybWF0aW9uID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnNjYWxlKHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuaW52ZXJ0ZWRUcmFuc2Zvcm1hdGlvbiA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5pbnZlcnQodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5nZXRUcmFuc2Zvcm1hdGlvbkV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2dldFVuYm91bmRlZEV4dGVudCh0cnVlKTsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmRvbWFpbigpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5zZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbiA9IGZ1bmN0aW9uIChkb21haW4pIHsKICAgICAgICAgICAgdGhpcy5kb21haW4oZG9tYWluKTsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuX2dldERvbWFpbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2JhY2tpbmdTY2FsZURvbWFpbigpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5fYmFja2luZ1NjYWxlRG9tYWluID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICBpZiAodmFsdWVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLmRvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5kb21haW4odmFsdWVzKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMaW5lYXIucHJvdG90eXBlLl9nZXRSYW5nZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUucmFuZ2UoKTsKICAgICAgICB9OwogICAgICAgIExpbmVhci5wcm90b3R5cGUuX3NldFJhbmdlID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICB0aGlzLl9kM1NjYWxlLnJhbmdlKHZhbHVlcyk7CiAgICAgICAgfTsKICAgICAgICBMaW5lYXIucHJvdG90eXBlLmludmVydCA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5pbnZlcnQodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5kZWZhdWx0VGlja3MgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLnRpY2tzKExpbmVhci5fREVGQVVMVF9OVU1fVElDS1MpOwogICAgICAgIH07CiAgICAgICAgTGluZWFyLnByb3RvdHlwZS5fbmljZURvbWFpbiA9IGZ1bmN0aW9uIChkb21haW4sIGNvdW50KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLmNvcHkoKS5kb21haW4oZG9tYWluKS5uaWNlKGNvdW50KS5kb21haW4oKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBMaW5lYXI7CiAgICB9KHF1YW50aXRhdGl2ZVNjYWxlLlF1YW50aXRhdGl2ZVNjYWxlKSk7CiAgICBleHBvcnRzLkxpbmVhciA9IExpbmVhcjsKICAgIH0pOwoKICAgIHZhciBsb2dTY2FsZSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIExvZyA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKExvZywgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBMb2coYmFzZSkgewogICAgICAgICAgICBpZiAoYmFzZSA9PT0gdm9pZCAwKSB7IGJhc2UgPSAxMDsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fZDNTY2FsZSA9IGQzLnNjYWxlTG9nKCkuYmFzZShiYXNlKTsKICAgICAgICAgICAgX3RoaXMuX3NldERvbWFpbihfdGhpcy5fZGVmYXVsdEV4dGVudCgpKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBMb2cucHJvdG90eXBlLl9kZWZhdWx0RXh0ZW50ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gWzEsIHRoaXMuX2QzU2NhbGUuYmFzZSgpXTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuX2V4cGFuZFNpbmdsZVZhbHVlRG9tYWluID0gZnVuY3Rpb24gKHNpbmdsZVZhbHVlRG9tYWluKSB7CiAgICAgICAgICAgIGlmIChzaW5nbGVWYWx1ZURvbWFpblswXSA9PT0gc2luZ2xlVmFsdWVEb21haW5bMV0pIHsKICAgICAgICAgICAgICAgIHJldHVybiBbc2luZ2xlVmFsdWVEb21haW5bMF0gLyB0aGlzLl9kM1NjYWxlLmJhc2UoKSwKICAgICAgICAgICAgICAgICAgICBzaW5nbGVWYWx1ZURvbWFpblsxXSAqIHRoaXMuX2QzU2NhbGUuYmFzZSgpXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gc2luZ2xlVmFsdWVEb21haW47CiAgICAgICAgfTsKICAgICAgICBMb2cucHJvdG90eXBlLnNjYWxlID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlKHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuc2NhbGVUcmFuc2Zvcm1hdGlvbiA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5zY2FsZSh2YWx1ZSk7CiAgICAgICAgfTsKICAgICAgICBMb2cucHJvdG90eXBlLmludmVydGVkVHJhbnNmb3JtYXRpb24gPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW52ZXJ0KHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25FeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXRVbmJvdW5kZWRFeHRlbnQodHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBMb2cucHJvdG90eXBlLmdldFRyYW5zZm9ybWF0aW9uRG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5kb21haW4oKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuc2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoZG9tYWluKSB7CiAgICAgICAgICAgIHRoaXMuZG9tYWluKGRvbWFpbik7CiAgICAgICAgfTsKICAgICAgICBMb2cucHJvdG90eXBlLl9nZXREb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9iYWNraW5nU2NhbGVEb21haW4oKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuX2JhY2tpbmdTY2FsZURvbWFpbiA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgaWYgKHZhbHVlcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5kb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2QzU2NhbGUuZG9tYWluKHZhbHVlcyk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTG9nLnByb3RvdHlwZS5fZ2V0UmFuZ2UgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLnJhbmdlKCk7CiAgICAgICAgfTsKICAgICAgICBMb2cucHJvdG90eXBlLl9zZXRSYW5nZSA9IGZ1bmN0aW9uICh2YWx1ZXMpIHsKICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5yYW5nZSh2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgTG9nLnByb3RvdHlwZS5pbnZlcnQgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUuaW52ZXJ0KHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuZGVmYXVsdFRpY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS50aWNrcyhMb2cuX0RFRkFVTFRfTlVNX1RJQ0tTKTsKICAgICAgICB9OwogICAgICAgIExvZy5wcm90b3R5cGUuX25pY2VEb21haW4gPSBmdW5jdGlvbiAoZG9tYWluLCBjb3VudCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5jb3B5KCkuZG9tYWluKGRvbWFpbikubmljZSgpLmRvbWFpbigpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIExvZzsKICAgIH0ocXVhbnRpdGF0aXZlU2NhbGUuUXVhbnRpdGF0aXZlU2NhbGUpKTsKICAgIGV4cG9ydHMuTG9nID0gTG9nOwogICAgfSk7CgogICAgdmFyIG1vZGlmaWVkTG9nU2NhbGUgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgogICAgdmFyIE1vZGlmaWVkTG9nID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoTW9kaWZpZWRMb2csIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBNb2RpZmllZExvZyBTY2FsZSBhY3RzIGFzIGEgcmVndWxhciBsb2cgc2NhbGUgZm9yIGxhcmdlIG51bWJlcnMuCiAgICAgICAgICogQXMgaXQgYXBwcm9hY2hlcyAwLCBpdCBncmFkdWFsbHkgYmVjb21lcyBsaW5lYXIuCiAgICAgICAgICogQ29uc2VxdWVudGx5LCBhIE1vZGlmaWVkTG9nIFNjYWxlIGNhbiBwcm9jZXNzIDAgYW5kIG5lZ2F0aXZlIG51bWJlcnMuCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgeCA+PSBiYXNlLCBzY2FsZSh4KSA9IGxvZyh4KS4KICAgICAgICAgKgogICAgICAgICAqIEZvciAwIDwgeCA8IGJhc2UsIHNjYWxlKHgpIHdpbGwgYmVjb21lIG1vcmUgYW5kIG1vcmUKICAgICAgICAgKiBsaW5lYXIgYXMgaXQgYXBwcm9hY2hlcyAwLgogICAgICAgICAqCiAgICAgICAgICogQXQgeCA9PSAwLCBzY2FsZSh4KSA9PSAwLgogICAgICAgICAqCiAgICAgICAgICogRm9yIG5lZ2F0aXZlIHZhbHVlcywgc2NhbGUoLXgpID0gLXNjYWxlKHgpLgogICAgICAgICAqCiAgICAgICAgICogVGhlIHJhbmdlIGFuZCBkb21haW4gZm9yIHRoZSBzY2FsZSBzaG91bGQgYWxzbyBiZSBzZXQsIHVzaW5nIHRoZQogICAgICAgICAqIHJhbmdlKCkgYW5kIGRvbWFpbigpIGFjY2Vzc29ycywgcmVzcGVjdGl2ZWx5LgogICAgICAgICAqCiAgICAgICAgICogRm9yIGByYW5nZWAsIHByb3ZpZGUgYSB0d28tZWxlbWVudCBhcnJheSBnaXZpbmcgdGhlIG1pbmltdW0gYW5kCiAgICAgICAgICogbWF4aW11bSBvZiB2YWx1ZXMgcHJvZHVjZWQgd2hlbiBzY2FsaW5nLgogICAgICAgICAqCiAgICAgICAgICogRm9yIGBkb21haW5gIHByb3ZpZGUgYSB0d28tZWxlbWVudCBhcnJheSBnaXZpbmcgdGhlIG1pbmltdW0gYW5kCiAgICAgICAgICogbWF4aW11bSBvZiB0aGUgdmFsdWVzIHRoYXQgd2lsbCBiZSBzY2FsZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2Jhc2U9MTBdCiAgICAgICAgICogICAgICAgIFRoZSBiYXNlIG9mIHRoZSBsb2cuIE11c3QgYmUgPiAxLgogICAgICAgICAqCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gTW9kaWZpZWRMb2coYmFzZSkgewogICAgICAgICAgICBpZiAoYmFzZSA9PT0gdm9pZCAwKSB7IGJhc2UgPSAxMDsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbG9nVGlja0dlbmVyYXRvciA9IGZ1bmN0aW9uIChzY2FsZSkgewogICAgICAgICAgICAgICAgLy8gU2F5IHlvdXIgZG9tYWluIGlzIFstMTAwLCAxMDBdIGFuZCB5b3VyIHBpdm90IGlzIDEwLgogICAgICAgICAgICAgICAgLy8gdGhlbiB3ZSdyZSBnb2luZyB0byBkcmF3IG5lZ2F0aXZlIGxvZyB0aWNrcyBmcm9tIC0xMDAgdG8gLTEwLAogICAgICAgICAgICAgICAgLy8gbGluZWFyIHRpY2tzIGZyb20gLTEwIHRvIDEwLCBhbmQgcG9zaXRpdmUgbG9nIHRpY2tzIGZyb20gMTAgdG8gMTAwLgogICAgICAgICAgICAgICAgdmFyIG1pZGRsZSA9IGZ1bmN0aW9uICh4LCB5LCB6KSB7IHJldHVybiBbeCwgeSwgel0uc29ydChmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gYSAtIGI7IH0pWzFdOyB9OwogICAgICAgICAgICAgICAgdmFyIG1pbiA9IHV0aWxzJDEuTWF0aC5taW4oX3RoaXMuX3VudHJhbnNmb3JtZWREb21haW4sIDApOwogICAgICAgICAgICAgICAgdmFyIG1heCA9IHV0aWxzJDEuTWF0aC5tYXgoX3RoaXMuX3VudHJhbnNmb3JtZWREb21haW4sIDApOwogICAgICAgICAgICAgICAgdmFyIG5lZ2F0aXZlTG93ZXIgPSBtaW47CiAgICAgICAgICAgICAgICB2YXIgbmVnYXRpdmVVcHBlciA9IG1pZGRsZShtaW4sIG1heCwgLV90aGlzLl9waXZvdCk7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpdmVMb3dlciA9IG1pZGRsZShtaW4sIG1heCwgX3RoaXMuX3Bpdm90KTsKICAgICAgICAgICAgICAgIHZhciBwb3NpdGl2ZVVwcGVyID0gbWF4OwogICAgICAgICAgICAgICAgdmFyIG5lZ2F0aXZlTG9nVGlja3MgPSBfdGhpcy5fbG9nVGlja3MoLW5lZ2F0aXZlVXBwZXIsIC1uZWdhdGl2ZUxvd2VyKS5tYXAoZnVuY3Rpb24gKHgpIHsgcmV0dXJuIC14OyB9KS5yZXZlcnNlKCk7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpdmVMb2dUaWNrcyA9IF90aGlzLl9sb2dUaWNrcyhwb3NpdGl2ZUxvd2VyLCBwb3NpdGl2ZVVwcGVyKTsKICAgICAgICAgICAgICAgIHZhciBsaW5lYXJNaW4gPSBNYXRoLm1heChtaW4sIC1fdGhpcy5fcGl2b3QpOwogICAgICAgICAgICAgICAgdmFyIGxpbmVhck1heCA9IE1hdGgubWluKG1heCwgX3RoaXMuX3Bpdm90KTsKICAgICAgICAgICAgICAgIHZhciBsaW5lYXJUaWNrcyA9IGQzLnNjYWxlTGluZWFyKCkuZG9tYWluKFtsaW5lYXJNaW4sIGxpbmVhck1heF0pLnRpY2tzKF90aGlzLl9ob3dNYW55VGlja3MobGluZWFyTWluLCBsaW5lYXJNYXgpKTsKICAgICAgICAgICAgICAgIHZhciB0aWNrcyA9IG5lZ2F0aXZlTG9nVGlja3MuY29uY2F0KGxpbmVhclRpY2tzKS5jb25jYXQocG9zaXRpdmVMb2dUaWNrcyk7CiAgICAgICAgICAgICAgICAvLyBJZiB5b3Ugb25seSBoYXZlIDEgdGljaywgeW91IGNhbid0IHRlbGwgaG93IGJpZyB0aGUgc2NhbGUgaXMuCiAgICAgICAgICAgICAgICBpZiAodGlja3MubGVuZ3RoIDw9IDEpIHsKICAgICAgICAgICAgICAgICAgICB0aWNrcyA9IGQzLnNjYWxlTGluZWFyKCkuZG9tYWluKFttaW4sIG1heF0pLnRpY2tzKHNjYWxlcy5Nb2RpZmllZExvZy5fREVGQVVMVF9OVU1fVElDS1MpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIHRpY2tzOwogICAgICAgICAgICB9OwogICAgICAgICAgICBfdGhpcy5fZDNTY2FsZSA9IGQzLnNjYWxlTGluZWFyKCk7CiAgICAgICAgICAgIF90aGlzLl9iYXNlID0gYmFzZTsKICAgICAgICAgICAgX3RoaXMuX3Bpdm90ID0gX3RoaXMuX2Jhc2U7CiAgICAgICAgICAgIF90aGlzLl9zZXREb21haW4oX3RoaXMuX2RlZmF1bHRFeHRlbnQoKSk7CiAgICAgICAgICAgIF90aGlzLnRpY2tHZW5lcmF0b3IoX3RoaXMuX2xvZ1RpY2tHZW5lcmF0b3IpOwogICAgICAgICAgICBpZiAoYmFzZSA8PSAxKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIk1vZGlmaWVkTG9nU2NhbGU6IFRoZSBiYXNlIG11c3QgYmUgPiAxIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGFuIGFkanVzdGVkIGxvZzEwIHZhbHVlIGZvciBncmFwaGluZyBwdXJwb3Nlcy4gIFRoZSBmaXJzdAogICAgICAgICAqIGFkanVzdG1lbnQgaXMgdGhhdCBuZWdhdGl2ZSB2YWx1ZXMgYXJlIGNoYW5nZWQgdG8gcG9zaXRpdmUgZHVyaW5nCiAgICAgICAgICogdGhlIGNhbGN1bGF0aW9ucywgYW5kIHRoZW4gdGhlIGFuc3dlciBpcyBuZWdhdGVkIGF0IHRoZSBlbmQuICBUaGUKICAgICAgICAgKiBzZWNvbmQgaXMgdGhhdCwgZm9yIHZhbHVlcyBsZXNzIHRoYW4gMTAsIGFuIGluY3JlYXNpbmdseSBsYXJnZQogICAgICAgICAqICgwIHRvIDEpIHNjYWxpbmcgZmFjdG9yIGlzIGFkZGVkIHN1Y2ggdGhhdCBhdCAwIHRoZSB2YWx1ZSBpcwogICAgICAgICAqIGFkanVzdGVkIHRvIDEsIHJlc3VsdGluZyBpbiBhIHJldHVybmVkIHJlc3VsdCBvZiAwLgogICAgICAgICAqLwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5fYWRqdXN0ZWRMb2cgPSBmdW5jdGlvbiAoeCkgewogICAgICAgICAgICB2YXIgbmVnYXRpb25GYWN0b3IgPSB4IDwgMCA/IC0xIDogMTsKICAgICAgICAgICAgeCAqPSBuZWdhdGlvbkZhY3RvcjsKICAgICAgICAgICAgaWYgKHggPCB0aGlzLl9waXZvdCkgewogICAgICAgICAgICAgICAgeCArPSAodGhpcy5fcGl2b3QgLSB4KSAvIHRoaXMuX3Bpdm90OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHggPSBNYXRoLmxvZyh4KSAvIE1hdGgubG9nKHRoaXMuX2Jhc2UpOwogICAgICAgICAgICB4ICo9IG5lZ2F0aW9uRmFjdG9yOwogICAgICAgICAgICByZXR1cm4geDsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5faW52ZXJ0ZWRBZGp1c3RlZExvZyA9IGZ1bmN0aW9uICh4KSB7CiAgICAgICAgICAgIHZhciBuZWdhdGlvbkZhY3RvciA9IHggPCAwID8gLTEgOiAxOwogICAgICAgICAgICB4ICo9IG5lZ2F0aW9uRmFjdG9yOwogICAgICAgICAgICB4ID0gTWF0aC5wb3codGhpcy5fYmFzZSwgeCk7CiAgICAgICAgICAgIGlmICh4IDwgdGhpcy5fcGl2b3QpIHsKICAgICAgICAgICAgICAgIHggPSAodGhpcy5fcGl2b3QgKiAoeCAtIDEpKSAvICh0aGlzLl9waXZvdCAtIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHggKj0gbmVnYXRpb25GYWN0b3I7CiAgICAgICAgICAgIHJldHVybiB4OwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLnNjYWxlID0gZnVuY3Rpb24gKHgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUodGhpcy5fYWRqdXN0ZWRMb2coeCkpOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLmludmVydCA9IGZ1bmN0aW9uICh4KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9pbnZlcnRlZEFkanVzdGVkTG9nKHRoaXMuX2QzU2NhbGUuaW52ZXJ0KHgpKTsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5zY2FsZVRyYW5zZm9ybWF0aW9uID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnNjYWxlKHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5pbnZlcnRlZFRyYW5zZm9ybWF0aW9uID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmludmVydCh2YWx1ZSk7CiAgICAgICAgfTsKICAgICAgICBNb2RpZmllZExvZy5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25FeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXRVbmJvdW5kZWRFeHRlbnQodHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBNb2RpZmllZExvZy5wcm90b3R5cGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmRvbWFpbigpOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLnNldFRyYW5zZm9ybWF0aW9uRG9tYWluID0gZnVuY3Rpb24gKGRvbWFpbikgewogICAgICAgICAgICB0aGlzLmRvbWFpbihkb21haW4pOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLl9nZXREb21haW4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl91bnRyYW5zZm9ybWVkRG9tYWluOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLl9zZXREb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRoaXMuX3VudHJhbnNmb3JtZWREb21haW4gPSB2YWx1ZXM7CiAgICAgICAgICAgIHZhciB0cmFuc2Zvcm1lZERvbWFpbiA9IFt0aGlzLl9hZGp1c3RlZExvZyh2YWx1ZXNbMF0pLCB0aGlzLl9hZGp1c3RlZExvZyh2YWx1ZXNbMV0pXTsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fc2V0RG9tYWluLmNhbGwodGhpcywgdHJhbnNmb3JtZWREb21haW4pOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLl9iYWNraW5nU2NhbGVEb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIGlmICh2YWx1ZXMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kM1NjYWxlLmRvbWFpbih2YWx1ZXMpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiBhbiBhcHByb3ByaWF0ZSBudW1iZXIgb2YgdGlja3MgZnJvbSBsb3dlciB0byB1cHBlci4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgd2lsbCBmaXJzdCB0cnkgdG8gZml0IGFzIG1hbnkgcG93ZXJzIG9mIHRoaXMuYmFzZSBhcyBpdCBjYW4gZnJvbQogICAgICAgICAqIGxvd2VyIHRvIHVwcGVyLgogICAgICAgICAqCiAgICAgICAgICogSWYgaXQgc3RpbGwgaGFzIHRpY2tzIGFmdGVyIHRoYXQsIGl0IHdpbGwgZ2VuZXJhdGUgdGlja3MgaW4gImNsdXN0ZXJzIiwKICAgICAgICAgKiBlLmcuIFsyMCwgMzAsIC4uLiA5MCwgMTAwXSB3b3VsZCBiZSBhIGNsdXN0ZXIsIFsyMDAsIDMwMCwgLi4uIDkwMCwgMTAwMF0KICAgICAgICAgKiB3b3VsZCBiZSBhbm90aGVyIGNsdXN0ZXIuCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIGZ1bmN0aW9uIHdpbGwgZ2VuZXJhdGUgY2x1c3RlcnMgYXMgbGFyZ2UgYXMgaXQgY2FuIHdoaWxlIG5vdAogICAgICAgICAqIGRyYXN0aWNhbGx5IGV4Y2VlZGluZyBpdHMgbnVtYmVyIG9mIHRpY2tzLgogICAgICAgICAqLwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5fbG9nVGlja3MgPSBmdW5jdGlvbiAobG93ZXIsIHVwcGVyKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBuVGlja3MgPSB0aGlzLl9ob3dNYW55VGlja3MobG93ZXIsIHVwcGVyKTsKICAgICAgICAgICAgaWYgKG5UaWNrcyA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBzdGFydExvZ2dlZCA9IE1hdGguZmxvb3IoTWF0aC5sb2cobG93ZXIpIC8gTWF0aC5sb2codGhpcy5fYmFzZSkpOwogICAgICAgICAgICB2YXIgZW5kTG9nZ2VkID0gTWF0aC5jZWlsKE1hdGgubG9nKHVwcGVyKSAvIE1hdGgubG9nKHRoaXMuX2Jhc2UpKTsKICAgICAgICAgICAgdmFyIGJhc2VzID0gZDMucmFuZ2UoZW5kTG9nZ2VkLCBzdGFydExvZ2dlZCwgLU1hdGguY2VpbCgoZW5kTG9nZ2VkIC0gc3RhcnRMb2dnZWQpIC8gblRpY2tzKSk7CiAgICAgICAgICAgIHZhciBtdWx0aXBsZXMgPSBkMy5yYW5nZSh0aGlzLl9iYXNlLCAxLCAtKHRoaXMuX2Jhc2UgLSAxKSkubWFwKE1hdGguZmxvb3IpOwogICAgICAgICAgICB2YXIgdW5pcU11bHRpcGxlcyA9IHV0aWxzJDEuQXJyYXkudW5pcShtdWx0aXBsZXMpOwogICAgICAgICAgICB2YXIgY2x1c3RlcnMgPSBiYXNlcy5tYXAoZnVuY3Rpb24gKGIpIHsgcmV0dXJuIHVuaXFNdWx0aXBsZXMubWFwKGZ1bmN0aW9uICh4KSB7IHJldHVybiBNYXRoLnBvdyhfdGhpcy5fYmFzZSwgYiAtIDEpICogeDsgfSk7IH0pOwogICAgICAgICAgICB2YXIgZmxhdHRlbmVkID0gdXRpbHMkMS5BcnJheS5mbGF0dGVuKGNsdXN0ZXJzKTsKICAgICAgICAgICAgdmFyIGZpbHRlcmVkID0gZmxhdHRlbmVkLmZpbHRlcihmdW5jdGlvbiAoeCkgeyByZXR1cm4gbG93ZXIgPD0geCAmJiB4IDw9IHVwcGVyOyB9KTsKICAgICAgICAgICAgdmFyIHNvcnRlZCA9IGZpbHRlcmVkLnNvcnQoZnVuY3Rpb24gKHgsIHkpIHsgcmV0dXJuIHggLSB5OyB9KTsKICAgICAgICAgICAgcmV0dXJuIHNvcnRlZDsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEhvdyBtYW55IHRpY2tzIGRvZXMgdGhlIHJhbmdlIFtsb3dlciwgdXBwZXJdIGRlc2VydmU/CiAgICAgICAgICoKICAgICAgICAgKiBlLmcuIGlmIHlvdXIgZG9tYWluIHdhcyBbMTAsIDEwMDBdIGFuZCBJIGFza2VkIF9ob3dNYW55VGlja3MoMTAsIDEwMCksCiAgICAgICAgICogSSB3b3VsZCBnZXQgMS8yIG9mIHRoZSB0aWNrcy4gVGhlIHJhbmdlIDEwLCAxMDAgdGFrZXMgdXAgMS8yIG9mIHRoZQogICAgICAgICAqIGRpc3RhbmNlIHdoZW4gcGxvdHRlZC4KICAgICAgICAgKi8KICAgICAgICBNb2RpZmllZExvZy5wcm90b3R5cGUuX2hvd01hbnlUaWNrcyA9IGZ1bmN0aW9uIChsb3dlciwgdXBwZXIpIHsKICAgICAgICAgICAgdmFyIGFkanVzdGVkTWluID0gdGhpcy5fYWRqdXN0ZWRMb2codXRpbHMkMS5NYXRoLm1pbih0aGlzLl91bnRyYW5zZm9ybWVkRG9tYWluLCAwKSk7CiAgICAgICAgICAgIHZhciBhZGp1c3RlZE1heCA9IHRoaXMuX2FkanVzdGVkTG9nKHV0aWxzJDEuTWF0aC5tYXgodGhpcy5fdW50cmFuc2Zvcm1lZERvbWFpbiwgMCkpOwogICAgICAgICAgICB2YXIgYWRqdXN0ZWRMb3dlciA9IHRoaXMuX2FkanVzdGVkTG9nKGxvd2VyKTsKICAgICAgICAgICAgdmFyIGFkanVzdGVkVXBwZXIgPSB0aGlzLl9hZGp1c3RlZExvZyh1cHBlcik7CiAgICAgICAgICAgIHZhciBwcm9wb3J0aW9uID0gKGFkanVzdGVkVXBwZXIgLSBhZGp1c3RlZExvd2VyKSAvIChhZGp1c3RlZE1heCAtIGFkanVzdGVkTWluKTsKICAgICAgICAgICAgdmFyIHRpY2tzID0gTWF0aC5jZWlsKHByb3BvcnRpb24gKiBzY2FsZXMuTW9kaWZpZWRMb2cuX0RFRkFVTFRfTlVNX1RJQ0tTKTsKICAgICAgICAgICAgcmV0dXJuIHRpY2tzOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLl9uaWNlRG9tYWluID0gZnVuY3Rpb24gKGRvbWFpbiwgY291bnQpIHsKICAgICAgICAgICAgcmV0dXJuIGRvbWFpbjsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5fZGVmYXVsdEV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIFswLCB0aGlzLl9iYXNlXTsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5fZXhwYW5kU2luZ2xlVmFsdWVEb21haW4gPSBmdW5jdGlvbiAoc2luZ2xlVmFsdWVEb21haW4pIHsKICAgICAgICAgICAgaWYgKHNpbmdsZVZhbHVlRG9tYWluWzBdID09PSBzaW5nbGVWYWx1ZURvbWFpblsxXSkgewogICAgICAgICAgICAgICAgdmFyIHNpbmdsZVZhbHVlID0gc2luZ2xlVmFsdWVEb21haW5bMF07CiAgICAgICAgICAgICAgICBpZiAoc2luZ2xlVmFsdWUgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFtzaW5nbGVWYWx1ZSAvIHRoaXMuX2Jhc2UsIHNpbmdsZVZhbHVlICogdGhpcy5fYmFzZV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChzaW5nbGVWYWx1ZSA9PT0gMCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBbLXRoaXMuX2Jhc2UsIHRoaXMuX2Jhc2VdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFtzaW5nbGVWYWx1ZSAqIHRoaXMuX2Jhc2UsIHNpbmdsZVZhbHVlIC8gdGhpcy5fYmFzZV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHNpbmdsZVZhbHVlRG9tYWluOwogICAgICAgIH07CiAgICAgICAgTW9kaWZpZWRMb2cucHJvdG90eXBlLl9nZXRSYW5nZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUucmFuZ2UoKTsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5fc2V0UmFuZ2UgPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRoaXMuX2QzU2NhbGUucmFuZ2UodmFsdWVzKTsKICAgICAgICB9OwogICAgICAgIE1vZGlmaWVkTG9nLnByb3RvdHlwZS5kZWZhdWx0VGlja3MgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLnRpY2tzKHNjYWxlcy5Nb2RpZmllZExvZy5fREVGQVVMVF9OVU1fVElDS1MpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIE1vZGlmaWVkTG9nOwogICAgfShxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSkpOwogICAgZXhwb3J0cy5Nb2RpZmllZExvZyA9IE1vZGlmaWVkTG9nOwogICAgfSk7CgogICAgdmFyIHRpbWVTY2FsZSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIHZhciBUaW1lID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoVGltZSwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBIFRpbWUgU2NhbGUgbWFwcyBEYXRlIG9iamVjdHMgdG8gbnVtYmVycy4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFRpbWUoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9kM1NjYWxlID0gZDMuc2NhbGVUaW1lKCk7CiAgICAgICAgICAgIF90aGlzLmF1dG9Eb21haW4oKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGFuIGFycmF5IG9mIHRpY2tzIHZhbHVlcyBzZXBhcmF0ZWQgYnkgdGhlIHNwZWNpZmllZCBpbnRlcnZhbC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBpbnRlcnZhbCBBIHN0cmluZyBzcGVjaWZ5aW5nIHRoZSBpbnRlcnZhbCB1bml0LgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyP30gW3N0ZXBdIFRoZSBudW1iZXIgb2YgbXVsdGlwbGVzIG9mIHRoZSBpbnRlcnZhbCBiZXR3ZWVuIGNvbnNlY3V0aXZlIHRpY2tzLgogICAgICAgICAqIEByZXR1cm4ge0RhdGVbXX0KICAgICAgICAgKi8KICAgICAgICBUaW1lLnByb3RvdHlwZS50aWNrSW50ZXJ2YWwgPSBmdW5jdGlvbiAoaW50ZXJ2YWwsIHN0ZXAsIHVzZVVUQykgewogICAgICAgICAgICBpZiAoc3RlcCA9PT0gdm9pZCAwKSB7IHN0ZXAgPSAxOyB9CiAgICAgICAgICAgIGlmICh1c2VVVEMgPT09IHZvaWQgMCkgeyB1c2VVVEMgPSBmYWxzZTsgfQogICAgICAgICAgICAvLyB0ZW1wb3JhcmlseSBjcmVhdHMgYSB0aW1lIHNjYWxlIGZyb20gb3VyIGxpbmVhciBzY2FsZSBpbnRvIGEgdGltZSBzY2FsZSBzbyB3ZSBjYW4gZ2V0IGFjY2VzcyB0byBpdHMgYXBpCiAgICAgICAgICAgIHZhciB0ZW1wU2NhbGUgPSBkMy5zY2FsZVRpbWUoKTsKICAgICAgICAgICAgdmFyIGQzSW50ZXJ2YWwgPSBUaW1lLnRpbWVJbnRlcnZhbFRvRDNUaW1lKGludGVydmFsLCB1c2VVVEMpLmV2ZXJ5KHN0ZXApOwogICAgICAgICAgICB0ZW1wU2NhbGUuZG9tYWluKHRoaXMuZG9tYWluKCkpOwogICAgICAgICAgICB0ZW1wU2NhbGUucmFuZ2UodGhpcy5yYW5nZSgpKTsKICAgICAgICAgICAgcmV0dXJuIHRlbXBTY2FsZS50aWNrcyhkM0ludGVydmFsKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9zZXREb21haW4gPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIGlmICh2YWx1ZXNbMV0gPCB2YWx1ZXNbMF0pIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiU2NhbGUuVGltZSBkb21haW4gdmFsdWVzIG11c3QgYmUgaW4gY2hyb25vbG9naWNhbCBvcmRlciIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLl9zZXREb21haW4uY2FsbCh0aGlzLCB2YWx1ZXMpOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX2RlZmF1bHRFeHRlbnQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBbbmV3IERhdGUoIjE5NzAtMDEtMDEiKSwgbmV3IERhdGUoIjE5NzAtMDEtMDIiKV07CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fZXhwYW5kU2luZ2xlVmFsdWVEb21haW4gPSBmdW5jdGlvbiAoc2luZ2xlVmFsdWVEb21haW4pIHsKICAgICAgICAgICAgdmFyIHN0YXJ0VGltZSA9IHNpbmdsZVZhbHVlRG9tYWluWzBdLmdldFRpbWUoKTsKICAgICAgICAgICAgdmFyIGVuZFRpbWUgPSBzaW5nbGVWYWx1ZURvbWFpblsxXS5nZXRUaW1lKCk7CiAgICAgICAgICAgIGlmIChzdGFydFRpbWUgPT09IGVuZFRpbWUpIHsKICAgICAgICAgICAgICAgIHZhciBzdGFydERhdGUgPSBuZXcgRGF0ZShzdGFydFRpbWUpOwogICAgICAgICAgICAgICAgc3RhcnREYXRlLnNldERhdGUoc3RhcnREYXRlLmdldERhdGUoKSAtIDEpOwogICAgICAgICAgICAgICAgdmFyIGVuZERhdGUgPSBuZXcgRGF0ZShlbmRUaW1lKTsKICAgICAgICAgICAgICAgIGVuZERhdGUuc2V0RGF0ZShlbmREYXRlLmdldERhdGUoKSArIDEpOwogICAgICAgICAgICAgICAgcmV0dXJuIFtzdGFydERhdGUsIGVuZERhdGVdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBzaW5nbGVWYWx1ZURvbWFpbjsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLnNjYWxlID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlKHZhbHVlKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLnNjYWxlVHJhbnNmb3JtYXRpb24gPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuc2NhbGUobmV3IERhdGUodmFsdWUpKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLmludmVydGVkVHJhbnNmb3JtYXRpb24gPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW52ZXJ0KHZhbHVlKS5nZXRUaW1lKCk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5nZXRUcmFuc2Zvcm1hdGlvbkV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGV4dGVudCA9IHRoaXMuX2dldFVuYm91bmRlZEV4dGVudCh0cnVlKTsKICAgICAgICAgICAgcmV0dXJuIFtleHRlbnRbMF0udmFsdWVPZigpLCBleHRlbnRbMV0udmFsdWVPZigpXTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLmdldFRyYW5zZm9ybWF0aW9uRG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgZGF0ZXMgPSB0aGlzLmRvbWFpbigpOwogICAgICAgICAgICByZXR1cm4gW2RhdGVzWzBdLnZhbHVlT2YoKSwgZGF0ZXNbMV0udmFsdWVPZigpXTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLnNldFRyYW5zZm9ybWF0aW9uRG9tYWluID0gZnVuY3Rpb24gKF9hKSB7CiAgICAgICAgICAgIHZhciBkb21haW5NaW4gPSBfYVswXSwgZG9tYWluTWF4ID0gX2FbMV07CiAgICAgICAgICAgIHRoaXMuZG9tYWluKFtuZXcgRGF0ZShkb21haW5NaW4pLCBuZXcgRGF0ZShkb21haW5NYXgpXSk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fZ2V0RG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fYmFja2luZ1NjYWxlRG9tYWluKCk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fYmFja2luZ1NjYWxlRG9tYWluID0gZnVuY3Rpb24gKHZhbHVlcykgewogICAgICAgICAgICBpZiAodmFsdWVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLmRvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZDNTY2FsZS5kb21haW4odmFsdWVzKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fZ2V0UmFuZ2UgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM1NjYWxlLnJhbmdlKCk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fc2V0UmFuZ2UgPSBmdW5jdGlvbiAodmFsdWVzKSB7CiAgICAgICAgICAgIHRoaXMuX2QzU2NhbGUucmFuZ2UodmFsdWVzKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLmludmVydCA9IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS5pbnZlcnQodmFsdWUpOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuZGVmYXVsdFRpY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNTY2FsZS50aWNrcyhUaW1lLl9ERUZBVUxUX05VTV9USUNLUyk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fbmljZURvbWFpbiA9IGZ1bmN0aW9uIChkb21haW4pIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzU2NhbGUuY29weSgpLmRvbWFpbihkb21haW4pLm5pY2UoKS5kb21haW4oKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFRyYW5zZm9ybXMgdGhlIFBsb3R0YWJsZSBUaW1lSW50ZXJ2YWwgc3RyaW5nIGludG8gYSBkMyB0aW1lIGludGVydmFsIGVxdWl2YWxlbnQuCiAgICAgICAgICogSWYgdGhlIHByb3ZpZGVkIFRpbWVJbnRlcnZhbCBpcyBpbmNvcnJlY3QsIHRoZSBkZWZhdWx0IGlzIGQzLnRpbWVZZWFyCiAgICAgICAgICovCiAgICAgICAgVGltZS50aW1lSW50ZXJ2YWxUb0QzVGltZSA9IGZ1bmN0aW9uICh0aW1lSW50ZXJ2YWwsIHVzZVVUQykgewogICAgICAgICAgICBzd2l0Y2ggKHRpbWVJbnRlcnZhbCkgewogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwuc2Vjb25kOgogICAgICAgICAgICAgICAgICAgIHJldHVybiB1c2VVVEMgPyBkMy51dGNTZWNvbmQgOiBkMy50aW1lU2Vjb25kOwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwubWludXRlOgogICAgICAgICAgICAgICAgICAgIHJldHVybiB1c2VVVEMgPyBkMy51dGNNaW51dGUgOiBkMy50aW1lTWludXRlOwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwuaG91cjoKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdXNlVVRDID8gZDMudXRjSG91ciA6IGQzLnRpbWVIb3VyOwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwuZGF5OgogICAgICAgICAgICAgICAgICAgIHJldHVybiB1c2VVVEMgPyBkMy51dGNEYXkgOiBkMy50aW1lRGF5OwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwud2VlazoKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdXNlVVRDID8gZDMudXRjV2VlayA6IGQzLnRpbWVXZWVrOwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwubW9udGg6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHVzZVVUQyA/IGQzLnV0Y01vbnRoIDogZDMudGltZU1vbnRoOwogICAgICAgICAgICAgICAgY2FzZSB0aW1lQXhpcy5UaW1lSW50ZXJ2YWwueWVhcjoKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdXNlVVRDID8gZDMudXRjWWVhciA6IGQzLnRpbWVZZWFyOwogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICB0aHJvdyBFcnJvcigiVGltZUludGVydmFsIHNwZWNpZmllZCBkb2VzIG5vdCBleGlzdDogIiArIHRpbWVJbnRlcnZhbCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBUaW1lOwogICAgfShxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSkpOwogICAgZXhwb3J0cy5UaW1lID0gVGltZTsKICAgIH0pOwoKICAgIHZhciBzY2FsZXMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgZXhwb3J0cy5UaWNrR2VuZXJhdG9ycyA9IHRpY2tHZW5lcmF0b3JzOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihjYXRlZ29yeVNjYWxlLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoY29sb3JTY2FsZSwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGludGVycG9sYXRlZENvbG9yU2NhbGUsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihsaW5lYXJTY2FsZSwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGxvZ1NjYWxlLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIobW9kaWZpZWRMb2dTY2FsZSwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHRpbWVTY2FsZSwgZXhwb3J0cyk7CiAgICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIHZhciBjYXRlZ29yeVNjYWxlXzEgPSBjYXRlZ29yeVNjYWxlOwoKICAgIC8qKgogICAgICogVHlwZSBndWFyZGVkIGZ1bmN0aW9uIHRvIGNoZWNrIGlmIHRoZSBzY2FsZSBpbXBsZW1lbnRzIHRoZQogICAgICogYFRyYW5zZm9ybWFibGVTY2FsZWAgaW50ZXJmYWNlLiBVbmZvcnR1bmF0ZWx5LCB0aGVyZSBpcyBubyB3YXkgdG8gZG8KICAgICAqIHJ1bnRpbWUgaW50ZXJmYWNlIHR5cGVjaGVja2luZywgc28gd2UgaGF2ZSB0byBleHBsaWNpdGx5IGxpc3QgYWxsIGNsYXNzZXMKICAgICAqIHRoYXQgaW1wbGVtZW50IHRoZSBpbnRlcmZhY2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzVHJhbnNmb3JtYWJsZShzY2FsZSkgewogICAgICAgIHJldHVybiAoc2NhbGUgaW5zdGFuY2VvZiBxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSB8fAogICAgICAgICAgICBzY2FsZSBpbnN0YW5jZW9mIGNhdGVnb3J5U2NhbGVfMS5DYXRlZ29yeSk7CiAgICB9CiAgICBleHBvcnRzLmlzVHJhbnNmb3JtYWJsZSA9IGlzVHJhbnNmb3JtYWJsZTsKICAgIH0pOwoKICAgIHZhciB0aW1lQXhpcyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgoKCiAgICBleHBvcnRzLlRpbWVJbnRlcnZhbCA9IG1ha2VFbnVtXzEubWFrZUVudW0oWwogICAgICAgICJzZWNvbmQiLAogICAgICAgICJtaW51dGUiLAogICAgICAgICJob3VyIiwKICAgICAgICAiZGF5IiwKICAgICAgICAid2VlayIsCiAgICAgICAgIm1vbnRoIiwKICAgICAgICAieWVhciIsCiAgICBdKTsKICAgIC8qKgogICAgICogUG9zc2libGUgb3JpZW50YXRpb25zIGZvciBhIFRpbWUgQXhpcy4KICAgICAqLwogICAgZXhwb3J0cy5UaW1lQXhpc09yaWVudGF0aW9uID0gbWFrZUVudW1fMS5tYWtlRW51bShbInRvcCIsICJib3R0b20iXSk7CiAgICBleHBvcnRzLlRpZXJMYWJlbFBvc2l0aW9uID0gbWFrZUVudW1fMS5tYWtlRW51bShbImJldHdlZW4iLCAiY2VudGVyIl0pOwogICAgdmFyIFRpbWUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhUaW1lLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIENvbnN0cnVjdHMgYSBUaW1lIEF4aXMuCiAgICAgICAgICoKICAgICAgICAgKiBBIFRpbWUgQXhpcyBpcyBhIHZpc3VhbCByZXByZXNlbnRhdGlvbiBvZiBhIFRpbWUgU2NhbGUuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlcy5UaW1lfSBzY2FsZQogICAgICAgICAqIEBwYXJhbSB7QXhpc09yaWVudGF0aW9ufSBvcmllbnRhdGlvbiBPcmllbnRhdGlvbiBvZiB0aGlzIFRpbWUgQXhpcy4gVGltZSBBeGVzIGNhbiBvbmx5IGhhdmUgInRvcCIgb3IgImJvdHRvbSIKICAgICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IHVzZVVUQyBEaXNwbGF5cyBkYXRlIG9iamVjdCBpbiBVVEMgaWYgdHJ1ZSwgbG9jYWwgdGltZSBpZiBmYWxzZS4gRGVmYXVsdHMgdG8gZmFsc2UuCiAgICAgICAgICogb3JpZW50YXRpb25zLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFRpbWUoc2NhbGUsIG9yaWVudGF0aW9uLCB1c2VVVEMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcywgc2NhbGUsIG9yaWVudGF0aW9uKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbWF4VGltZUludGVydmFsUHJlY2lzaW9uID0gbnVsbDsKICAgICAgICAgICAgX3RoaXMuX3RpZXJMYWJlbFBvc2l0aW9ucyA9IFtdOwogICAgICAgICAgICBfdGhpcy5fdXNlVVRDID0gdXNlVVRDOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygidGltZS1heGlzIik7CiAgICAgICAgICAgIF90aGlzLnRpY2tMYWJlbFBhZGRpbmcoNSk7CiAgICAgICAgICAgIF90aGlzLmF4aXNDb25maWd1cmF0aW9ucyhUaW1lLl9ERUZBVUxUX1RJTUVfQVhJU19DT05GSUdVUkFUSU9OUyhfdGhpcy5fdXNlVVRDKSk7CiAgICAgICAgICAgIF90aGlzLmFubm90YXRpb25Gb3JtYXR0ZXIoZm9ybWF0dGVycy50aW1lKCIlYSAlYiAlZCwgJVkiLCBfdGhpcy5fdXNlVVRDKSk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgVGltZS5wcm90b3R5cGUudGllckxhYmVsUG9zaXRpb25zID0gZnVuY3Rpb24gKG5ld1Bvc2l0aW9ucykgewogICAgICAgICAgICBpZiAobmV3UG9zaXRpb25zID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl90aWVyTGFiZWxQb3NpdGlvbnM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBpZiAoIW5ld1Bvc2l0aW9ucy5ldmVyeShmdW5jdGlvbiAocG9zKSB7IHJldHVybiBwb3MudG9Mb3dlckNhc2UoKSA9PT0gImJldHdlZW4iIHx8IHBvcy50b0xvd2VyQ2FzZSgpID09PSAiY2VudGVyIjsgfSkpIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIlVuc3VwcG9ydGVkIHBvc2l0aW9uIGZvciB0aWVyIGxhYmVscyIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdGhpcy5fdGllckxhYmVsUG9zaXRpb25zID0gbmV3UG9zaXRpb25zOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5tYXhUaW1lSW50ZXJ2YWxQcmVjaXNpb24gPSBmdW5jdGlvbiAobmV3UHJlY2lzaW9uKSB7CiAgICAgICAgICAgIGlmIChuZXdQcmVjaXNpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21heFRpbWVJbnRlcnZhbFByZWNpc2lvbjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heFRpbWVJbnRlcnZhbFByZWNpc2lvbiA9IG5ld1ByZWNpc2lvbjsKICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgY3VycmVudCBgVGltZUF4aXNDb25maWd1cmF0aW9uYCB1c2VkIHRvIHJlbmRlciB0aGUgYXhlcy4KICAgICAgICAgKgogICAgICAgICAqIE5vdGUgdGhhdCB0aGlzIGlzIG9ubHkgdmFsaWQgYWZ0ZXIgdGhlIGF4aXMgaGFkIGJlZW4gcmVuZGVyZWQgYW5kIHRoZQogICAgICAgICAqIG1vc3QgcHJlY2lzZSB2YWxpZCBjb25maWd1cmF0aW9uIGlzIGRldGVybWluZWQgZnJvbSB0aGUgYXZhaWxhYmxlIHNwYWNlCiAgICAgICAgICogYW5kIG1heGltdW0gcHJlY2lzaW9uIGNvbnN0cmFpbnRzLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybnMge1RpbWVBeGlzQ29uZmlndXJhdGlvbn0gVGhlIGN1cnJlbnRseSB1c2VkIGBUaW1lQXhpc0NvbmZpZ3VyYXRpb25gIG9yIGB1bmRlZmluZWRgLgogICAgICAgICAqLwogICAgICAgIFRpbWUucHJvdG90eXBlLmN1cnJlbnRBeGlzQ29uZmlndXJhdGlvbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Bvc3NpYmxlVGltZUF4aXNDb25maWd1cmF0aW9uc1t0aGlzLl9tb3N0UHJlY2lzZUNvbmZpZ0luZGV4XTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLmF4aXNDb25maWd1cmF0aW9ucyA9IGZ1bmN0aW9uIChjb25maWd1cmF0aW9ucykgewogICAgICAgICAgICBpZiAoY29uZmlndXJhdGlvbnMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Bvc3NpYmxlVGltZUF4aXNDb25maWd1cmF0aW9uczsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9wb3NzaWJsZVRpbWVBeGlzQ29uZmlndXJhdGlvbnMgPSBjb25maWd1cmF0aW9uczsKICAgICAgICAgICAgdGhpcy5fbnVtVGllcnMgPSB1dGlscyQxLk1hdGgubWF4KHRoaXMuX3Bvc3NpYmxlVGltZUF4aXNDb25maWd1cmF0aW9ucy5tYXAoZnVuY3Rpb24gKGNvbmZpZykgeyByZXR1cm4gY29uZmlnLmxlbmd0aDsgfSksIDApOwogICAgICAgICAgICBpZiAodGhpcy5faXNBbmNob3JlZCkgewogICAgICAgICAgICAgICAgdGhpcy5fc2V0dXBEb21FbGVtZW50cygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBvbGRMYWJlbFBvc2l0aW9ucyA9IHRoaXMudGllckxhYmVsUG9zaXRpb25zKCk7CiAgICAgICAgICAgIHZhciBuZXdMYWJlbFBvc2l0aW9ucyA9IFtdOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHRoaXMuX251bVRpZXJzOyBpKyspIHsKICAgICAgICAgICAgICAgIG5ld0xhYmVsUG9zaXRpb25zLnB1c2gob2xkTGFiZWxQb3NpdGlvbnNbaV0gfHwgImJldHdlZW4iKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLnRpZXJMYWJlbFBvc2l0aW9ucyhuZXdMYWJlbFBvc2l0aW9ucyk7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgaW5kZXggb2YgdGhlIG1vc3QgcHJlY2lzZSBUaW1lQXhpc0NvbmZpZ3VyYXRpb24gdGhhdCB3aWxsIGZpdCBpbiB0aGUgY3VycmVudCB3aWR0aC4KICAgICAgICAgKi8KICAgICAgICBUaW1lLnByb3RvdHlwZS5fZ2V0TW9zdFByZWNpc2VDb25maWd1cmF0aW9uSW5kZXggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBtb3N0UHJlY2lzZUluZGV4ID0gdGhpcy5fcG9zc2libGVUaW1lQXhpc0NvbmZpZ3VyYXRpb25zLmxlbmd0aDsKICAgICAgICAgICAgdGhpcy5fcG9zc2libGVUaW1lQXhpc0NvbmZpZ3VyYXRpb25zLmZvckVhY2goZnVuY3Rpb24gKGludGVydmFsLCBpbmRleCkgewogICAgICAgICAgICAgICAgaWYgKGluZGV4IDwgbW9zdFByZWNpc2VJbmRleCAmJiBpbnRlcnZhbC5ldmVyeShmdW5jdGlvbiAodGllcikgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5fY2hlY2tUaW1lQXhpc1RpZXJDb25maWd1cmF0aW9uKHRpZXIpOwogICAgICAgICAgICAgICAgfSkpIHsKICAgICAgICAgICAgICAgICAgICBtb3N0UHJlY2lzZUluZGV4ID0gaW5kZXg7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBpZiAobW9zdFByZWNpc2VJbmRleCA9PT0gdGhpcy5fcG9zc2libGVUaW1lQXhpc0NvbmZpZ3VyYXRpb25zLmxlbmd0aCkgewogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cud2Fybigiem9vbWVkIG91dCB0b28gZmFyOiBjb3VsZCBub3QgZmluZCBzdWl0YWJsZSBpbnRlcnZhbCB0byBkaXNwbGF5IGxhYmVscyIpOwogICAgICAgICAgICAgICAgLS1tb3N0UHJlY2lzZUluZGV4OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBtb3N0UHJlY2lzZUluZGV4OwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUub3JpZW50YXRpb24gPSBmdW5jdGlvbiAob3JpZW50YXRpb24pIHsKICAgICAgICAgICAgaWYgKG9yaWVudGF0aW9uICYmIChvcmllbnRhdGlvbi50b0xvd2VyQ2FzZSgpID09PSAicmlnaHQiIHx8IG9yaWVudGF0aW9uLnRvTG93ZXJDYXNlKCkgPT09ICJsZWZ0IikpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihvcmllbnRhdGlvbiArICIgaXMgbm90IGEgc3VwcG9ydGVkIG9yaWVudGF0aW9uIGZvciBUaW1lQXhpcyAtIG9ubHkgaG9yaXpvbnRhbCBvcmllbnRhdGlvbnMgYXJlIHN1cHBvcnRlZCIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLm9yaWVudGF0aW9uLmNhbGwodGhpcywgb3JpZW50YXRpb24pOyAvLyBtYWludGFpbnMgZ2V0dGVyLXNldHRlciBmdW5jdGlvbmFsaXR5CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fY29tcHV0ZUhlaWdodCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHRleHRIZWlnaHQgPSB0aGlzLl9tZWFzdXJlci5tZWFzdXJlKCkuaGVpZ2h0OwogICAgICAgICAgICB0aGlzLl90aWVySGVpZ2h0cyA9IFtdOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHRoaXMuX251bVRpZXJzOyBpKyspIHsKICAgICAgICAgICAgICAgIHRoaXMuX3RpZXJIZWlnaHRzLnB1c2godGV4dEhlaWdodCArIHRoaXMudGlja0xhYmVsUGFkZGluZygpICsKICAgICAgICAgICAgICAgICAgICAoKHRoaXMuX3RpZXJMYWJlbFBvc2l0aW9uc1tpXSkgPT09ICJiZXR3ZWVuIiA/IDAgOiB0aGlzLl9tYXhMYWJlbFRpY2tMZW5ndGgoKSkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBkMy5zdW0odGhpcy5fdGllckhlaWdodHMpOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX2dldEludGVydmFsTGVuZ3RoID0gZnVuY3Rpb24gKGNvbmZpZykgewogICAgICAgICAgICB2YXIgc3RhcnREYXRlID0gdGhpcy5fc2NhbGUuZG9tYWluKClbMF07CiAgICAgICAgICAgIHZhciBkM0ludGVydmFsID0gc2NhbGVzLlRpbWUudGltZUludGVydmFsVG9EM1RpbWUoY29uZmlnLmludGVydmFsLCB0aGlzLl91c2VVVEMpOwogICAgICAgICAgICB2YXIgZW5kRGF0ZSA9IGQzSW50ZXJ2YWwub2Zmc2V0KHN0YXJ0RGF0ZSwgY29uZmlnLnN0ZXApOwogICAgICAgICAgICBpZiAoZW5kRGF0ZSA+IHRoaXMuX3NjYWxlLmRvbWFpbigpWzFdKSB7CiAgICAgICAgICAgICAgICAvLyB0aGlzIG9mZnNldCBpcyB0b28gbGFyZ2UsIHNvIGp1c3QgcmV0dXJuIGF2YWlsYWJsZSB3aWR0aAogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMud2lkdGgoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBtZWFzdXJlIGhvdyBtdWNoIHNwYWNlIG9uZSBkYXRlIGNhbiBnZXQKICAgICAgICAgICAgdmFyIHN0ZXBMZW5ndGggPSBNYXRoLmFicyh0aGlzLl9zY2FsZS5zY2FsZShlbmREYXRlKSAtIHRoaXMuX3NjYWxlLnNjYWxlKHN0YXJ0RGF0ZSkpOwogICAgICAgICAgICByZXR1cm4gc3RlcExlbmd0aDsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9tYXhXaWR0aEZvckludGVydmFsID0gZnVuY3Rpb24gKGNvbmZpZykgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fbWVhc3VyZXIubWVhc3VyZShjb25maWcuZm9ybWF0dGVyKFRpbWUuX0xPTkdfREFURSkpLndpZHRoOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2sgaWYgdGllciBjb25maWd1cmF0aW9uIGZpdHMgaW4gdGhlIGN1cnJlbnQgd2lkdGggYW5kIHNhdGlzZmllZCB0aGUKICAgICAgICAgKiBtYXggVGltZUludGVydmFsIHByZWNpc2lvbiBsaW1pdC4KICAgICAgICAgKi8KICAgICAgICBUaW1lLnByb3RvdHlwZS5fY2hlY2tUaW1lQXhpc1RpZXJDb25maWd1cmF0aW9uID0gZnVuY3Rpb24gKGNvbmZpZykgewogICAgICAgICAgICAvLyBVc2UgdGhlIHNvcnRlZCBpbmRleCB0byBkZXRlcm1pbmUgaWYgdGhlIHRlaXIgY29uZmlndXJhdGlvbiBjb250YWlucyBhCiAgICAgICAgICAgIC8vIHRpbWUgaW50ZXJ2YWwgdGhhdCBpcyB0b28gcHJlY2lzZSBmb3IgdGhlIG1heFRpbWVJbnRlcnZhbFByZWNpc2lvbgogICAgICAgICAgICAvLyBzZXR0aW5nIChpZiBzZXQpLgogICAgICAgICAgICBpZiAodGhpcy5fbWF4VGltZUludGVydmFsUHJlY2lzaW9uICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHZhciBwcmVjaXNpb25MaW1pdCA9IFRpbWUuX1NPUlRFRF9USU1FX0lOVEVSVkFMX0lOREVYW3RoaXMuX21heFRpbWVJbnRlcnZhbFByZWNpc2lvbl07CiAgICAgICAgICAgICAgICB2YXIgY29uZmlnUHJlY2lzaW9uID0gVGltZS5fU09SVEVEX1RJTUVfSU5URVJWQUxfSU5ERVhbY29uZmlnLmludGVydmFsXTsKICAgICAgICAgICAgICAgIGlmIChwcmVjaXNpb25MaW1pdCAhPSBudWxsICYmIGNvbmZpZ1ByZWNpc2lvbiAhPSBudWxsICYmIGNvbmZpZ1ByZWNpc2lvbiA8IHByZWNpc2lvbkxpbWl0KSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB3b3JzdFdpZHRoID0gdGhpcy5fbWF4V2lkdGhGb3JJbnRlcnZhbChjb25maWcpICsgMiAqIHRoaXMudGlja0xhYmVsUGFkZGluZygpOwogICAgICAgICAgICByZXR1cm4gTWF0aC5taW4odGhpcy5fZ2V0SW50ZXJ2YWxMZW5ndGgoY29uZmlnKSwgdGhpcy53aWR0aCgpKSA+PSB3b3JzdFdpZHRoOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX3NpemVGcm9tT2ZmZXIgPSBmdW5jdGlvbiAoYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICAvLyBNYWtlcyBzdXJlIHRoYXQgdGhlIHNpemUgaXQgcmVxdWlyZXMgaXMgYSBtdWx0aXBsZSBvZiB0aWVyIHNpemVzLCBzdWNoIHRoYXQKICAgICAgICAgICAgLy8gd2UgaGF2ZSBubyBsZWZ0b3ZlciB0aWVycwogICAgICAgICAgICB2YXIgc2l6ZSA9IF9zdXBlci5wcm90b3R5cGUuX3NpemVGcm9tT2ZmZXIuY2FsbCh0aGlzLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KTsKICAgICAgICAgICAgdmFyIHRpZXJIZWlnaHRzID0gdGhpcy5fdGllckhlaWdodHMucmVkdWNlKGZ1bmN0aW9uIChwcmV2VmFsdWUsIGN1cnJWYWx1ZSwgaW5kZXgsIGFycikgewogICAgICAgICAgICAgICAgcmV0dXJuIChwcmV2VmFsdWUgKyBjdXJyVmFsdWUgPiBzaXplLmhlaWdodCkgPyBwcmV2VmFsdWUgOiAocHJldlZhbHVlICsgY3VyclZhbHVlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciBub25Db3JlSGVpZ2h0ID0gdGhpcy5tYXJnaW4oKSArICh0aGlzLmFubm90YXRpb25zRW5hYmxlZCgpID8gdGhpcy5hbm5vdGF0aW9uVGllckNvdW50KCkgKiB0aGlzLl9hbm5vdGF0aW9uVGllckhlaWdodCgpIDogMCk7CiAgICAgICAgICAgIHNpemUuaGVpZ2h0ID0gTWF0aC5taW4oc2l6ZS5oZWlnaHQsIHRpZXJIZWlnaHRzICsgbm9uQ29yZUhlaWdodCk7CiAgICAgICAgICAgIHJldHVybiBzaXplOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX3NldHVwID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9zZXR1cERvbUVsZW1lbnRzKCk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fc2V0dXBEb21FbGVtZW50cyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5jb250ZW50KCkuc2VsZWN0QWxsKCIuIiArIFRpbWUuVElNRV9BWElTX1RJRVJfQ0xBU1MpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl90aWVyTGFiZWxDb250YWluZXJzID0gW107CiAgICAgICAgICAgIHRoaXMuX3RpZXJNYXJrQ29udGFpbmVycyA9IFtdOwogICAgICAgICAgICB0aGlzLl90aWVyQmFzZWxpbmVzID0gW107CiAgICAgICAgICAgIHRoaXMuX3RpY2tMYWJlbENvbnRhaW5lci5yZW1vdmUoKTsKICAgICAgICAgICAgdGhpcy5fYmFzZWxpbmUucmVtb3ZlKCk7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGhpcy5fbnVtVGllcnM7ICsraSkgewogICAgICAgICAgICAgICAgdmFyIHRpZXJDb250YWluZXIgPSB0aGlzLmNvbnRlbnQoKS5hcHBlbmQoImciKS5jbGFzc2VkKFRpbWUuVElNRV9BWElTX1RJRVJfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICAgICAgdGhpcy5fdGllckxhYmVsQ29udGFpbmVycy5wdXNoKHRpZXJDb250YWluZXIuYXBwZW5kKCJnIikuY2xhc3NlZChheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTICsgIi1jb250YWluZXIiLCB0cnVlKSk7CiAgICAgICAgICAgICAgICB0aGlzLl90aWVyTWFya0NvbnRhaW5lcnMucHVzaCh0aWVyQ29udGFpbmVyLmFwcGVuZCgiZyIpLmNsYXNzZWQoYXhpcyQyLkF4aXMuVElDS19NQVJLX0NMQVNTICsgIi1jb250YWluZXIiLCB0cnVlKSk7CiAgICAgICAgICAgICAgICB0aGlzLl90aWVyQmFzZWxpbmVzLnB1c2godGllckNvbnRhaW5lci5hcHBlbmQoImxpbmUiKS5jbGFzc2VkKCJiYXNlbGluZSIsIHRydWUpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgY29udGV4dCA9IG5ldyBzcmMkMS5TdmdDb250ZXh0KHRoaXMuX3RpZXJMYWJlbENvbnRhaW5lcnNbMF0ubm9kZSgpKTsKICAgICAgICAgICAgdGhpcy5fbWVhc3VyZXIgPSBuZXcgc3JjJDEuQ2FjaGVNZWFzdXJlcihjb250ZXh0KTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9nZXRUaWNrSW50ZXJ2YWxWYWx1ZXMgPSBmdW5jdGlvbiAoY29uZmlnKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9zY2FsZS50aWNrSW50ZXJ2YWwoY29uZmlnLmludGVydmFsLCBjb25maWcuc3RlcCwgdGhpcy5fdXNlVVRDKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9nZXRUaWNrVmFsdWVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fcG9zc2libGVUaW1lQXhpc0NvbmZpZ3VyYXRpb25zW3RoaXMuX21vc3RQcmVjaXNlQ29uZmlnSW5kZXhdLnJlZHVjZShmdW5jdGlvbiAodGlja3MsIGNvbmZpZykgeyByZXR1cm4gdGlja3MuY29uY2F0KF90aGlzLl9nZXRUaWNrSW50ZXJ2YWxWYWx1ZXMoY29uZmlnKSk7IH0sIFtdKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9jbGVhblRpZXJzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBmb3IgKHZhciBpbmRleCA9IDA7IGluZGV4IDwgdGhpcy5fdGllckxhYmVsQ29udGFpbmVycy5sZW5ndGg7IGluZGV4KyspIHsKICAgICAgICAgICAgICAgIHRoaXMuX3RpZXJMYWJlbENvbnRhaW5lcnNbaW5kZXhdLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTKS5yZW1vdmUoKTsKICAgICAgICAgICAgICAgIHRoaXMuX3RpZXJNYXJrQ29udGFpbmVyc1tpbmRleF0uc2VsZWN0QWxsKCIuIiArIGF4aXMkMi5BeGlzLlRJQ0tfTUFSS19DTEFTUykucmVtb3ZlKCk7CiAgICAgICAgICAgICAgICB0aGlzLl90aWVyQmFzZWxpbmVzW2luZGV4XS5zdHlsZSgidmlzaWJpbGl0eSIsICJoaWRkZW4iKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX2dldFRpY2tWYWx1ZXNGb3JDb25maWd1cmF0aW9uID0gZnVuY3Rpb24gKGNvbmZpZykgewogICAgICAgICAgICB2YXIgdGlja1BvcyA9IHRoaXMuX3NjYWxlLnRpY2tJbnRlcnZhbChjb25maWcuaW50ZXJ2YWwsIGNvbmZpZy5zdGVwLCB0aGlzLl91c2VVVEMpOwogICAgICAgICAgICB2YXIgZG9tYWluID0gdGhpcy5fc2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIHZhciB0aWNrUG9zVmFsdWVzID0gdGlja1Bvcy5tYXAoZnVuY3Rpb24gKGQpIHsgcmV0dXJuIGQudmFsdWVPZigpOyB9KTsgLy8gY2FuJ3QgaW5kZXhPZiB3aXRoIG9iamVjdHMKICAgICAgICAgICAgaWYgKHRpY2tQb3NWYWx1ZXMuaW5kZXhPZihkb21haW5bMF0udmFsdWVPZigpKSA9PT0gLTEpIHsKICAgICAgICAgICAgICAgIHRpY2tQb3MudW5zaGlmdChkb21haW5bMF0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aWNrUG9zVmFsdWVzLmluZGV4T2YoZG9tYWluWzFdLnZhbHVlT2YoKSkgPT09IC0xKSB7CiAgICAgICAgICAgICAgICB0aWNrUG9zLnB1c2goZG9tYWluWzFdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGlja1BvczsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9yZW5kZXJUaWVyTGFiZWxzID0gZnVuY3Rpb24gKGNvbnRhaW5lciwgY29uZmlnLCBpbmRleCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgdGlja1BvcyA9IHRoaXMuX2dldFRpY2tWYWx1ZXNGb3JDb25maWd1cmF0aW9uKGNvbmZpZyk7CiAgICAgICAgICAgIHZhciBsYWJlbFBvcyA9IFtdOwogICAgICAgICAgICBpZiAodGhpcy5fdGllckxhYmVsUG9zaXRpb25zW2luZGV4XSA9PT0gImJldHdlZW4iICYmIGNvbmZpZy5zdGVwID09PSAxKSB7CiAgICAgICAgICAgICAgICB0aWNrUG9zLm1hcChmdW5jdGlvbiAoZGF0dW0sIGkpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoaSArIDEgPj0gdGlja1Bvcy5sZW5ndGgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBsYWJlbFBvcy5wdXNoKG5ldyBEYXRlKCh0aWNrUG9zW2kgKyAxXS52YWx1ZU9mKCkgLSB0aWNrUG9zW2ldLnZhbHVlT2YoKSkgLyAyICsgdGlja1Bvc1tpXS52YWx1ZU9mKCkpKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgbGFiZWxQb3MgPSB0aWNrUG9zOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzVXBkYXRlID0gY29udGFpbmVyLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTKS5kYXRhKGxhYmVsUG9zLCBmdW5jdGlvbiAoZCkgeyByZXR1cm4gU3RyaW5nKGQudmFsdWVPZigpKTsgfSk7CiAgICAgICAgICAgIHZhciB0aWNrTGFiZWxzRW50ZXIgPSB0aWNrTGFiZWxzVXBkYXRlCiAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgLmFwcGVuZCgiZyIpCiAgICAgICAgICAgICAgICAuY2xhc3NlZChheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTLCB0cnVlKTsKICAgICAgICAgICAgdGlja0xhYmVsc0VudGVyLmFwcGVuZCgidGV4dCIpOwogICAgICAgICAgICB2YXIgeFRyYW5zbGF0ZSA9ICh0aGlzLl90aWVyTGFiZWxQb3NpdGlvbnNbaW5kZXhdID09PSAiY2VudGVyIiB8fCBjb25maWcuc3RlcCA9PT0gMSkgPyAwIDogdGhpcy50aWNrTGFiZWxQYWRkaW5nKCk7CiAgICAgICAgICAgIHZhciB5VHJhbnNsYXRlOwogICAgICAgICAgICBpZiAodGhpcy5vcmllbnRhdGlvbigpID09PSAiYm90dG9tIikgewogICAgICAgICAgICAgICAgeVRyYW5zbGF0ZSA9IGQzLnN1bSh0aGlzLl90aWVySGVpZ2h0cy5zbGljZSgwLCBpbmRleCArIDEpKSAtIHRoaXMudGlja0xhYmVsUGFkZGluZygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX3RpZXJMYWJlbFBvc2l0aW9uc1tpbmRleF0gPT09ICJjZW50ZXIiKSB7CiAgICAgICAgICAgICAgICAgICAgeVRyYW5zbGF0ZSA9IHRoaXMuaGVpZ2h0KCkgLSBkMy5zdW0odGhpcy5fdGllckhlaWdodHMuc2xpY2UoMCwgaW5kZXgpKSAtIHRoaXMudGlja0xhYmVsUGFkZGluZygpIC0gdGhpcy5fbWF4TGFiZWxUaWNrTGVuZ3RoKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB5VHJhbnNsYXRlID0gdGhpcy5oZWlnaHQoKSAtIGQzLnN1bSh0aGlzLl90aWVySGVpZ2h0cy5zbGljZSgwLCBpbmRleCkpIC0gdGhpcy50aWNrTGFiZWxQYWRkaW5nKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRpY2tMYWJlbHMgPSB0aWNrTGFiZWxzVXBkYXRlLm1lcmdlKHRpY2tMYWJlbHNFbnRlcik7CiAgICAgICAgICAgIHZhciB0ZXh0U2VsZWN0aW9uID0gdGlja0xhYmVscy5zZWxlY3RBbGwoInRleHQiKTsKICAgICAgICAgICAgaWYgKHRleHRTZWxlY3Rpb24uc2l6ZSgpID4gMCkgewogICAgICAgICAgICAgICAgdGV4dFNlbGVjdGlvbi5hdHRyKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyB4VHJhbnNsYXRlICsgIiwiICsgeVRyYW5zbGF0ZSArICIpIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGlja0xhYmVsc1VwZGF0ZS5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgIHRpY2tMYWJlbHMuYXR0cigidHJhbnNmb3JtIiwgZnVuY3Rpb24gKGQpIHsgcmV0dXJuICJ0cmFuc2xhdGUoIiArIF90aGlzLl9zY2FsZS5zY2FsZShkKSArICIsMCkiOyB9KTsKICAgICAgICAgICAgdmFyIGFuY2hvciA9ICh0aGlzLl90aWVyTGFiZWxQb3NpdGlvbnNbaW5kZXhdID09PSAiY2VudGVyIiB8fCBjb25maWcuc3RlcCA9PT0gMSkgPyAibWlkZGxlIiA6ICJzdGFydCI7CiAgICAgICAgICAgIHRpY2tMYWJlbHMuc2VsZWN0QWxsKCJ0ZXh0IikudGV4dChjb25maWcuZm9ybWF0dGVyKS5zdHlsZSgidGV4dC1hbmNob3IiLCBhbmNob3IpOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX3JlbmRlclRpY2tNYXJrcyA9IGZ1bmN0aW9uICh0aWNrVmFsdWVzLCBpbmRleCkgewogICAgICAgICAgICB2YXIgdGlja01hcmtzVXBkYXRlID0gdGhpcy5fdGllck1hcmtDb250YWluZXJzW2luZGV4XS5zZWxlY3RBbGwoIi4iICsgYXhpcyQyLkF4aXMuVElDS19NQVJLX0NMQVNTKS5kYXRhKHRpY2tWYWx1ZXMpOwogICAgICAgICAgICB2YXIgdGlja01hcmtzID0gdGlja01hcmtzVXBkYXRlCiAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgLmFwcGVuZCgibGluZSIpCiAgICAgICAgICAgICAgICAuY2xhc3NlZChheGlzJDIuQXhpcy5USUNLX01BUktfQ0xBU1MsIHRydWUpCiAgICAgICAgICAgICAgICAubWVyZ2UodGlja01hcmtzVXBkYXRlKTsKICAgICAgICAgICAgdmFyIGF0dHIgPSB0aGlzLl9nZW5lcmF0ZVRpY2tNYXJrQXR0ckhhc2goKTsKICAgICAgICAgICAgdmFyIG9mZnNldCA9IHRoaXMuX3RpZXJIZWlnaHRzLnNsaWNlKDAsIGluZGV4KS5yZWR1Y2UoZnVuY3Rpb24gKHRyYW5zbGF0ZSwgaGVpZ2h0KSB7IHJldHVybiB0cmFuc2xhdGUgKyBoZWlnaHQ7IH0sIDApOwogICAgICAgICAgICBpZiAodGhpcy5vcmllbnRhdGlvbigpID09PSAiYm90dG9tIikgewogICAgICAgICAgICAgICAgYXR0clsieTEiXSA9IG9mZnNldDsKICAgICAgICAgICAgICAgIGF0dHJbInkyIl0gPSBvZmZzZXQgKyAodGhpcy5fdGllckxhYmVsUG9zaXRpb25zW2luZGV4XSA9PT0gImNlbnRlciIgPyB0aGlzLmlubmVyVGlja0xlbmd0aCgpIDogdGhpcy5fdGllckhlaWdodHNbaW5kZXhdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGF0dHJbInkxIl0gPSB0aGlzLmhlaWdodCgpIC0gb2Zmc2V0OwogICAgICAgICAgICAgICAgYXR0clsieTIiXSA9IHRoaXMuaGVpZ2h0KCkgLSAob2Zmc2V0ICsgKHRoaXMuX3RpZXJMYWJlbFBvc2l0aW9uc1tpbmRleF0gPT09ICJjZW50ZXIiID8KICAgICAgICAgICAgICAgICAgICB0aGlzLmlubmVyVGlja0xlbmd0aCgpIDogdGhpcy5fdGllckhlaWdodHNbaW5kZXhdKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGlja01hcmtzLmF0dHJzKGF0dHIpOwogICAgICAgICAgICBpZiAodGhpcy5vcmllbnRhdGlvbigpID09PSAiYm90dG9tIikgewogICAgICAgICAgICAgICAgYXR0clsieTEiXSA9IG9mZnNldDsKICAgICAgICAgICAgICAgIGF0dHJbInkyIl0gPSBvZmZzZXQgKyAodGhpcy5fdGllckxhYmVsUG9zaXRpb25zW2luZGV4XSA9PT0gImNlbnRlciIgPyB0aGlzLmVuZFRpY2tMZW5ndGgoKSA6IHRoaXMuX3RpZXJIZWlnaHRzW2luZGV4XSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBhdHRyWyJ5MSJdID0gdGhpcy5oZWlnaHQoKSAtIG9mZnNldDsKICAgICAgICAgICAgICAgIGF0dHJbInkyIl0gPSB0aGlzLmhlaWdodCgpIC0gKG9mZnNldCArICh0aGlzLl90aWVyTGFiZWxQb3NpdGlvbnNbaW5kZXhdID09PSAiY2VudGVyIiA/CiAgICAgICAgICAgICAgICAgICAgdGhpcy5lbmRUaWNrTGVuZ3RoKCkgOiB0aGlzLl90aWVySGVpZ2h0c1tpbmRleF0pKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBkMy5zZWxlY3QodGlja01hcmtzLm5vZGVzKClbMF0pLmF0dHJzKGF0dHIpOwogICAgICAgICAgICBkMy5zZWxlY3QodGlja01hcmtzLm5vZGVzKClbdGlja01hcmtzLnNpemUoKSAtIDFdKS5hdHRycyhhdHRyKTsKICAgICAgICAgICAgLy8gQWRkIGVuZC10aWNrIGNsYXNzZXMgdG8gZmlyc3QgYW5kIGxhc3QgdGljayBmb3IgQ1NTIGN1c3RvbWl6YXRpb24gcHVycG9zZXMKICAgICAgICAgICAgZDMuc2VsZWN0KHRpY2tNYXJrcy5ub2RlcygpWzBdKS5jbGFzc2VkKGF4aXMkMi5BeGlzLkVORF9USUNLX01BUktfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICBkMy5zZWxlY3QodGlja01hcmtzLm5vZGVzKClbdGlja01hcmtzLnNpemUoKSAtIDFdKS5jbGFzc2VkKGF4aXMkMi5BeGlzLkVORF9USUNLX01BUktfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB0aWNrTWFya3NVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgIH07CiAgICAgICAgVGltZS5wcm90b3R5cGUuX3JlbmRlckxhYmVsbGVzc1RpY2tNYXJrcyA9IGZ1bmN0aW9uICh0aWNrVmFsdWVzKSB7CiAgICAgICAgICAgIHZhciB0aWNrTWFya3NVcGRhdGUgPSB0aGlzLl90aWNrTWFya0NvbnRhaW5lci5zZWxlY3RBbGwoIi4iICsgYXhpcyQyLkF4aXMuVElDS19NQVJLX0NMQVNTKS5kYXRhKHRpY2tWYWx1ZXMpOwogICAgICAgICAgICB2YXIgdGlja01hcmtzID0gdGlja01hcmtzVXBkYXRlCiAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgLmFwcGVuZCgibGluZSIpCiAgICAgICAgICAgICAgICAuY2xhc3NlZChheGlzJDIuQXhpcy5USUNLX01BUktfQ0xBU1MsIHRydWUpCiAgICAgICAgICAgICAgICAubWVyZ2UodGlja01hcmtzVXBkYXRlKTsKICAgICAgICAgICAgdmFyIGF0dHIgPSB0aGlzLl9nZW5lcmF0ZVRpY2tNYXJrQXR0ckhhc2goKTsKICAgICAgICAgICAgYXR0clsieTIiXSA9ICh0aGlzLm9yaWVudGF0aW9uKCkgPT09ICJib3R0b20iKSA/IHRoaXMudGlja0xhYmVsUGFkZGluZygpIDogdGhpcy5oZWlnaHQoKSAtIHRoaXMudGlja0xhYmVsUGFkZGluZygpOwogICAgICAgICAgICB0aWNrTWFya3MuYXR0cnMoYXR0cik7CiAgICAgICAgICAgIHRpY2tNYXJrc1VwZGF0ZS5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5fZ2VuZXJhdGVMYWJlbGxlc3NUaWNrcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX21vc3RQcmVjaXNlQ29uZmlnSW5kZXggPCAxKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2dldFRpY2tJbnRlcnZhbFZhbHVlcyh0aGlzLl9wb3NzaWJsZVRpbWVBeGlzQ29uZmlndXJhdGlvbnNbdGhpcy5fbW9zdFByZWNpc2VDb25maWdJbmRleCAtIDFdWzBdKTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB0aGlzLl9tb3N0UHJlY2lzZUNvbmZpZ0luZGV4ID0gdGhpcy5fZ2V0TW9zdFByZWNpc2VDb25maWd1cmF0aW9uSW5kZXgoKTsKICAgICAgICAgICAgdmFyIHRpZXJDb25maWdzID0gdGhpcy5fcG9zc2libGVUaW1lQXhpc0NvbmZpZ3VyYXRpb25zW3RoaXMuX21vc3RQcmVjaXNlQ29uZmlnSW5kZXhdOwogICAgICAgICAgICB0aGlzLl9jbGVhblRpZXJzKCk7CiAgICAgICAgICAgIHRpZXJDb25maWdzLmZvckVhY2goZnVuY3Rpb24gKGNvbmZpZywgaSkgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9yZW5kZXJUaWVyTGFiZWxzKF90aGlzLl90aWVyTGFiZWxDb250YWluZXJzW2ldLCBjb25maWcsIGkpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIHRpZXJUaWNrcyA9IHRpZXJDb25maWdzLm1hcChmdW5jdGlvbiAoY29uZmlnLCBpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2dldFRpY2tWYWx1ZXNGb3JDb25maWd1cmF0aW9uKGNvbmZpZyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgYmFzZWxpbmVPZmZzZXQgPSAwOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IE1hdGgubWF4KHRpZXJDb25maWdzLmxlbmd0aCwgMSk7ICsraSkgewogICAgICAgICAgICAgICAgdmFyIGF0dHIgPSB0aGlzLl9nZW5lcmF0ZUJhc2VsaW5lQXR0ckhhc2goKTsKICAgICAgICAgICAgICAgIGF0dHJbInkxIl0gKz0gKHRoaXMub3JpZW50YXRpb24oKSA9PT0gImJvdHRvbSIpID8gYmFzZWxpbmVPZmZzZXQgOiAtYmFzZWxpbmVPZmZzZXQ7CiAgICAgICAgICAgICAgICBhdHRyWyJ5MiJdID0gYXR0clsieTEiXTsKICAgICAgICAgICAgICAgIHRoaXMuX3RpZXJCYXNlbGluZXNbaV0uYXR0cnMoYXR0cikuc3R5bGUoInZpc2liaWxpdHkiLCAiaW5oZXJpdCIpOwogICAgICAgICAgICAgICAgYmFzZWxpbmVPZmZzZXQgKz0gdGhpcy5fdGllckhlaWdodHNbaV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGxhYmVsTGVzc1RpY2tzID0gW107CiAgICAgICAgICAgIHZhciBkb21haW4gPSB0aGlzLl9zY2FsZS5kb21haW4oKTsKICAgICAgICAgICAgdmFyIHRvdGFsTGVuZ3RoID0gdGhpcy5fc2NhbGUuc2NhbGUoZG9tYWluWzFdKSAtIHRoaXMuX3NjYWxlLnNjYWxlKGRvbWFpblswXSk7CiAgICAgICAgICAgIGlmICh0aGlzLl9nZXRJbnRlcnZhbExlbmd0aCh0aWVyQ29uZmlnc1swXSkgKiAxLjUgPj0gdG90YWxMZW5ndGgpIHsKICAgICAgICAgICAgICAgIGxhYmVsTGVzc1RpY2tzID0gdGhpcy5fZ2VuZXJhdGVMYWJlbGxlc3NUaWNrcygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3JlbmRlckxhYmVsbGVzc1RpY2tNYXJrcyhsYWJlbExlc3NUaWNrcyk7CiAgICAgICAgICAgIHRoaXMuX2hpZGVPdmVyZmxvd2luZ1RpZXJzKCk7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGllckNvbmZpZ3MubGVuZ3RoOyArK2kpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3JlbmRlclRpY2tNYXJrcyh0aWVyVGlja3NbaV0sIGkpOwogICAgICAgICAgICAgICAgdGhpcy5faGlkZU92ZXJsYXBwaW5nQW5kQ3V0T2ZmTGFiZWxzKGkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLmFubm90YXRpb25zRW5hYmxlZCgpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmF3QW5ub3RhdGlvbnMoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3JlbW92ZUFubm90YXRpb25zKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5faGlkZU92ZXJmbG93aW5nVGllcnMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBhdmFpbGFibGVIZWlnaHQgPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICB2YXIgdXNlZEhlaWdodCA9IDA7CiAgICAgICAgICAgIHRoaXMuY29udGVudCgpCiAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCIuIiArIFRpbWUuVElNRV9BWElTX1RJRVJfQ0xBU1MpCiAgICAgICAgICAgICAgICAuYXR0cigidmlzaWJpbGl0eSIsIGZ1bmN0aW9uIChkLCBpKSB7CiAgICAgICAgICAgICAgICB1c2VkSGVpZ2h0ICs9IF90aGlzLl90aWVySGVpZ2h0c1tpXTsKICAgICAgICAgICAgICAgIHJldHVybiB1c2VkSGVpZ2h0IDw9IGF2YWlsYWJsZUhlaWdodCA/ICJpbmhlcml0IiA6ICJoaWRkZW4iOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIFRpbWUucHJvdG90eXBlLl9oaWRlT3ZlcmxhcHBpbmdBbmRDdXRPZmZMYWJlbHMgPSBmdW5jdGlvbiAoaW5kZXgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGJvdW5kaW5nQm94ID0gdGhpcy5lbGVtZW50KCkubm9kZSgpLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgICAgICB2YXIgaXNJbnNpZGVCQm94ID0gZnVuY3Rpb24gKHRpY2tCb3gpIHsKICAgICAgICAgICAgICAgIHJldHVybiAoTWF0aC5mbG9vcihib3VuZGluZ0JveC5sZWZ0KSA8PSBNYXRoLmNlaWwodGlja0JveC5sZWZ0KSAmJgogICAgICAgICAgICAgICAgICAgIE1hdGguZmxvb3IoYm91bmRpbmdCb3gudG9wKSA8PSBNYXRoLmNlaWwodGlja0JveC50b3ApICYmCiAgICAgICAgICAgICAgICAgICAgTWF0aC5mbG9vcih0aWNrQm94LnJpZ2h0KSA8PSBNYXRoLmNlaWwoYm91bmRpbmdCb3gubGVmdCArIF90aGlzLndpZHRoKCkpICYmCiAgICAgICAgICAgICAgICAgICAgTWF0aC5mbG9vcih0aWNrQm94LmJvdHRvbSkgPD0gTWF0aC5jZWlsKGJvdW5kaW5nQm94LnRvcCArIF90aGlzLmhlaWdodCgpKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB2aXNpYmxlVGlja01hcmtzID0gdGhpcy5fdGllck1hcmtDb250YWluZXJzW2luZGV4XQogICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX01BUktfQ0xBU1MpCiAgICAgICAgICAgICAgICAuZmlsdGVyKGZ1bmN0aW9uIChkLCBpKSB7CiAgICAgICAgICAgICAgICB2YXIgdmlzaWJpbGl0eSA9IGQzLnNlbGVjdCh0aGlzKS5zdHlsZSgidmlzaWJpbGl0eSIpOwogICAgICAgICAgICAgICAgcmV0dXJuIHZpc2liaWxpdHkgPT09ICJ2aXNpYmxlIiB8fCB2aXNpYmlsaXR5ID09PSAiaW5oZXJpdCI7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBXZSB1c2UgdGhlIENsaWVudFJlY3RzIGJlY2F1c2UgeDEveDIgYXR0cmlidXRlcyBhcmUgbm90IGNvbXBhcmFibGUgdG8gQ2xpZW50UmVjdHMgb2YgbGFiZWxzCiAgICAgICAgICAgIHZhciB2aXNpYmxlVGlja01hcmtSZWN0cyA9IHZpc2libGVUaWNrTWFya3Mubm9kZXMoKS5tYXAoZnVuY3Rpb24gKG1hcmspIHsgcmV0dXJuIG1hcmsuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7IH0pOwogICAgICAgICAgICB2YXIgdmlzaWJsZVRpY2tMYWJlbHMgPSB0aGlzLl90aWVyTGFiZWxDb250YWluZXJzW2luZGV4XQogICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgiLiIgKyBheGlzJDIuQXhpcy5USUNLX0xBQkVMX0NMQVNTKQogICAgICAgICAgICAgICAgLmZpbHRlcihmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgdmFyIHZpc2liaWxpdHkgPSBkMy5zZWxlY3QodGhpcykuc3R5bGUoInZpc2liaWxpdHkiKTsKICAgICAgICAgICAgICAgIHJldHVybiB2aXNpYmlsaXR5ID09PSAidmlzaWJsZSIgfHwgdmlzaWJpbGl0eSA9PT0gImluaGVyaXQiOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIGxhc3RMYWJlbENsaWVudFJlY3Q7CiAgICAgICAgICAgIHZpc2libGVUaWNrTGFiZWxzLmVhY2goZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgIHZhciBjbGllbnRSZWN0ID0gdGhpcy5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAgICAgICAgIHZhciB0aWNrTGFiZWwgPSBkMy5zZWxlY3QodGhpcyk7CiAgICAgICAgICAgICAgICB2YXIgbGVhZGluZ1RpY2tNYXJrID0gdmlzaWJsZVRpY2tNYXJrUmVjdHNbaV07CiAgICAgICAgICAgICAgICB2YXIgdHJhaWxpbmdUaWNrTWFyayA9IHZpc2libGVUaWNrTWFya1JlY3RzW2kgKyAxXTsKICAgICAgICAgICAgICAgIHZhciBpc092ZXJsYXBwaW5nTGFzdExhYmVsID0gKGxhc3RMYWJlbENsaWVudFJlY3QgIT0gbnVsbCAmJiB1dGlscyQxLkRPTS5jbGllbnRSZWN0c092ZXJsYXAoY2xpZW50UmVjdCwgbGFzdExhYmVsQ2xpZW50UmVjdCkpOwogICAgICAgICAgICAgICAgdmFyIGlzT3ZlcmxhcHBpbmdMZWFkaW5nVGlja01hcmsgPSAobGVhZGluZ1RpY2tNYXJrICE9IG51bGwgJiYgdXRpbHMkMS5ET00uY2xpZW50UmVjdHNPdmVybGFwKGNsaWVudFJlY3QsIGxlYWRpbmdUaWNrTWFyaykpOwogICAgICAgICAgICAgICAgdmFyIGlzT3ZlcmxhcHBpbmdUcmFpbGluZ1RpY2tNYXJrID0gKHRyYWlsaW5nVGlja01hcmsgIT0gbnVsbCAmJiB1dGlscyQxLkRPTS5jbGllbnRSZWN0c092ZXJsYXAoY2xpZW50UmVjdCwgdHJhaWxpbmdUaWNrTWFyaykpOwogICAgICAgICAgICAgICAgaWYgKCFpc0luc2lkZUJCb3goY2xpZW50UmVjdCkgfHwgaXNPdmVybGFwcGluZ0xhc3RMYWJlbCB8fCBpc092ZXJsYXBwaW5nTGVhZGluZ1RpY2tNYXJrIHx8IGlzT3ZlcmxhcHBpbmdUcmFpbGluZ1RpY2tNYXJrKSB7CiAgICAgICAgICAgICAgICAgICAgdGlja0xhYmVsLnN0eWxlKCJ2aXNpYmlsaXR5IiwgImhpZGRlbiIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgbGFzdExhYmVsQ2xpZW50UmVjdCA9IGNsaWVudFJlY3Q7CiAgICAgICAgICAgICAgICAgICAgdGlja0xhYmVsLnN0eWxlKCJ2aXNpYmlsaXR5IiwgImluaGVyaXQiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBUaW1lLnByb3RvdHlwZS5pbnZhbGlkYXRlQ2FjaGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyLnJlc2V0KCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgQ1NTIGNsYXNzIGFwcGxpZWQgdG8gZWFjaCBUaW1lIEF4aXMgdGllcgogICAgICAgICAqLwogICAgICAgIFRpbWUuVElNRV9BWElTX1RJRVJfQ0xBU1MgPSAidGltZS1heGlzLXRpZXIiOwogICAgICAgIFRpbWUuX1NPUlRFRF9USU1FX0lOVEVSVkFMX0lOREVYID0gKF9hID0ge30sCiAgICAgICAgICAgIF9hW2V4cG9ydHMuVGltZUludGVydmFsLnNlY29uZF0gPSAwLAogICAgICAgICAgICBfYVtleHBvcnRzLlRpbWVJbnRlcnZhbC5taW51dGVdID0gMSwKICAgICAgICAgICAgX2FbZXhwb3J0cy5UaW1lSW50ZXJ2YWwuaG91cl0gPSAyLAogICAgICAgICAgICBfYVtleHBvcnRzLlRpbWVJbnRlcnZhbC5kYXldID0gMywKICAgICAgICAgICAgX2FbZXhwb3J0cy5UaW1lSW50ZXJ2YWwud2Vla10gPSA0LAogICAgICAgICAgICBfYVtleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aF0gPSA1LAogICAgICAgICAgICBfYVtleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyXSA9IDYsCiAgICAgICAgICAgIF9hKTsKICAgICAgICBUaW1lLl9ERUZBVUxUX1RJTUVfQVhJU19DT05GSUdVUkFUSU9OUyA9IGZ1bmN0aW9uICh1c2VVVEMpIHsKICAgICAgICAgICAgdmFyIGZvcm1hdHRlciA9IGZ1bmN0aW9uIChzcGVjaWZpZXIpIHsgcmV0dXJuIGZvcm1hdHRlcnMudGltZShzcGVjaWZpZXIsIHVzZVVUQyk7IH07CiAgICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuc2Vjb25kLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUk6JU06JVMgJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLnNlY29uZCwgc3RlcDogNSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVJOiVNOiVTICVwIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5kYXksIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlQiAlZSwgJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5zZWNvbmQsIHN0ZXA6IDEwLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUk6JU06JVMgJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLnNlY29uZCwgc3RlcDogMTUsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlSTolTTolUyAlcCIpIH0sCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuZGF5LCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUIgJWUsICVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuc2Vjb25kLCBzdGVwOiAzMCwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVJOiVNOiVTICVwIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5kYXksIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlQiAlZSwgJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5taW51dGUsIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlSTolTSAlcCIpIH0sCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuZGF5LCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUIgJWUsICVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwubWludXRlLCBzdGVwOiA1LCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUk6JU0gJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLm1pbnV0ZSwgc3RlcDogMTAsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlSTolTSAlcCIpIH0sCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuZGF5LCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUIgJWUsICVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwubWludXRlLCBzdGVwOiAxNSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVJOiVNICVwIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5kYXksIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlQiAlZSwgJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5taW51dGUsIHN0ZXA6IDMwLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUk6JU0gJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmhvdXIsIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlSSAlcCIpIH0sCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuZGF5LCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUIgJWUsICVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuaG91ciwgc3RlcDogMywgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVJICVwIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5kYXksIHN0ZXA6IDEsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlQiAlZSwgJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5ob3VyLCBzdGVwOiA2LCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUkgJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmhvdXIsIHN0ZXA6IDEyLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUkgJXAiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVlLCAlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLmRheSwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVhICVlIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aCwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCICVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwuZGF5LCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJWUiKSB9LAogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLm1vbnRoLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJUIgJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aCwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVCIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aCwgc3RlcDogMSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiViIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aCwgc3RlcDogMywgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiViIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC5tb250aCwgc3RlcDogNiwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiViIikgfSwKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAxLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJXkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiA1LCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiAyNSwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwueWVhciwgc3RlcDogNTAsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLnllYXIsIHN0ZXA6IDEwMCwgZm9ybWF0dGVyOiBmb3JtYXR0ZXIoIiVZIikgfSwKICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICBbCiAgICAgICAgICAgICAgICAgICAgeyBpbnRlcnZhbDogZXhwb3J0cy5UaW1lSW50ZXJ2YWwueWVhciwgc3RlcDogMjAwLCBmb3JtYXR0ZXI6IGZvcm1hdHRlcigiJVkiKSB9LAogICAgICAgICAgICAgICAgXSwKICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICB7IGludGVydmFsOiBleHBvcnRzLlRpbWVJbnRlcnZhbC55ZWFyLCBzdGVwOiA1MDAsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICAgWwogICAgICAgICAgICAgICAgICAgIHsgaW50ZXJ2YWw6IGV4cG9ydHMuVGltZUludGVydmFsLnllYXIsIHN0ZXA6IDEwMDAsIGZvcm1hdHRlcjogZm9ybWF0dGVyKCIlWSIpIH0sCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICBdOwogICAgICAgIH07CiAgICAgICAgVGltZS5fTE9OR19EQVRFID0gbmV3IERhdGUoOTk5OSwgOCwgMjksIDEyLCA1OSwgOTk5OSk7CiAgICAgICAgcmV0dXJuIFRpbWU7CiAgICB9KGF4aXMkMi5BeGlzKSk7CiAgICBleHBvcnRzLlRpbWUgPSBUaW1lOwogICAgdmFyIF9hOwogICAgfSk7CgogICAgdmFyIGF4ZXMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGNhdGVnb3J5QXhpcywgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKG51bWVyaWNBeGlzLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIodGltZUF4aXMsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIGRpc3BhdGNoZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgRGlzcGF0Y2hlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBEaXNwYXRjaGVyKCkgewogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogU3ViY2xhc3NlcyBzZXQgdGhlc2UgaW4gY29uc3RydWN0b3IuIFRoZW4sIHRoZXNlIGdldCBhdHRhY2hlZCB0byB0aGUgZXZlbnQKICAgICAgICAgICAgICogdGFyZ2V0IGluIF9jb25uZWN0CiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIGV2ZW50bmFtZSBpcyBhIERPTSBldmVudCBuYW1lIGxpa2UgIm1vdXNldXAiLCAidG91Y2hzdGFydCIsIGV0Yy4gVGhlCiAgICAgICAgICAgICAqIGNhbGxiYWNrIGlzIHNpbXBseSByZWdpc3RlcmVkIHRvIHRoZSBldmVudCBjYWxsYmFjayB3aXRoIGJ1YmJsaW5nLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5fZXZlbnRUb1Byb2Nlc3NpbmdGdW5jdGlvbiA9IHt9OwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQWxsIGxpc3RlbmVycyBhcmUgcmVnaXN0ZXJlZCB0byB0aGlzIGBFdmVudFRhcmdldGAgYW5kIGV2ZW50cyBhcmUgdGhlbgogICAgICAgICAgICAgKiBkaXNwYXRjaGVkIHRvIGNhbGxiYWNrcyBmcm9tIGBfZXZlbnROYW1lVG9DYWxsYmFja1NldGAgbWFudWFsbHkuCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIFN1YmNsYXNzZXMgc2V0IHRoZWlyIG93biBldmVudCB0YXJnZXQgaW5zdGVhZCBvZiBgZG9jdW1lbnRgLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5fZXZlbnRUYXJnZXQgPSBkb2N1bWVudDsKICAgICAgICAgICAgdGhpcy5fZXZlbnROYW1lVG9DYWxsYmFja1NldCA9IHt9OwogICAgICAgICAgICB0aGlzLl9jb25uZWN0ZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgRGlzcGF0Y2hlci5wcm90b3R5cGUuX2hhc05vQ2FsbGJhY2tzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgZXZlbnROYW1lcyA9IE9iamVjdC5rZXlzKHRoaXMuX2V2ZW50TmFtZVRvQ2FsbGJhY2tTZXQpOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGV2ZW50TmFtZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9ldmVudE5hbWVUb0NhbGxiYWNrU2V0W2V2ZW50TmFtZXNbaV1dLnNpemUgIT09IDApIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfTsKICAgICAgICBEaXNwYXRjaGVyLnByb3RvdHlwZS5fY29ubmVjdCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKHRoaXMuX2Nvbm5lY3RlZCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIE9iamVjdC5rZXlzKHRoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb24pLmZvckVhY2goZnVuY3Rpb24gKGV2ZW50KSB7CiAgICAgICAgICAgICAgICB2YXIgcHJvY2Vzc2luZ0Z1bmN0aW9uID0gX3RoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb25bZXZlbnRdOwogICAgICAgICAgICAgICAgLy8gQWRkIGB7IHBhc3NpdmU6IGZhbHNlIH1gIG9wdGlvbiBiZWNhdXNlIENocm9tZSA3MyBicm9rZSB0aGlzLgogICAgICAgICAgICAgICAgdmFyIG9wdGlvbnMgPSBldmVudCA9PT0gIndoZWVsIiA/IHsgcGFzc2l2ZTogZmFsc2UgfSA6IHVuZGVmaW5lZDsKICAgICAgICAgICAgICAgIF90aGlzLl9ldmVudFRhcmdldC5hZGRFdmVudExpc3RlbmVyKGV2ZW50LCBwcm9jZXNzaW5nRnVuY3Rpb24sIG9wdGlvbnMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fY29ubmVjdGVkID0gdHJ1ZTsKICAgICAgICB9OwogICAgICAgIERpc3BhdGNoZXIucHJvdG90eXBlLl9kaXNjb25uZWN0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAodGhpcy5fY29ubmVjdGVkICYmIHRoaXMuX2hhc05vQ2FsbGJhY2tzKCkpIHsKICAgICAgICAgICAgICAgIE9iamVjdC5rZXlzKHRoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb24pLmZvckVhY2goZnVuY3Rpb24gKGV2ZW50KSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHByb2Nlc3NpbmdGdW5jdGlvbiA9IF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW2V2ZW50XTsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZXZlbnRUYXJnZXQucmVtb3ZlRXZlbnRMaXN0ZW5lcihldmVudCwgcHJvY2Vzc2luZ0Z1bmN0aW9uKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fY29ubmVjdGVkID0gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIERpc3BhdGNoZXIucHJvdG90eXBlLl9hZGRDYWxsYmFja0ZvckV2ZW50ID0gZnVuY3Rpb24gKGV2ZW50TmFtZSwgY2FsbGJhY2spIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2V2ZW50TmFtZVRvQ2FsbGJhY2tTZXRbZXZlbnROYW1lXSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9ldmVudE5hbWVUb0NhbGxiYWNrU2V0W2V2ZW50TmFtZV0gPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2V2ZW50TmFtZVRvQ2FsbGJhY2tTZXRbZXZlbnROYW1lXS5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9jb25uZWN0KCk7CiAgICAgICAgfTsKICAgICAgICBEaXNwYXRjaGVyLnByb3RvdHlwZS5fcmVtb3ZlQ2FsbGJhY2tGb3JFdmVudCA9IGZ1bmN0aW9uIChldmVudE5hbWUsIGNhbGxiYWNrKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9ldmVudE5hbWVUb0NhbGxiYWNrU2V0W2V2ZW50TmFtZV0gIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fZXZlbnROYW1lVG9DYWxsYmFja1NldFtldmVudE5hbWVdLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZGlzY29ubmVjdCgpOwogICAgICAgIH07CiAgICAgICAgRGlzcGF0Y2hlci5wcm90b3R5cGUuX2NhbGxDYWxsYmFja3NGb3JFdmVudCA9IGZ1bmN0aW9uIChldmVudE5hbWUpIHsKICAgICAgICAgICAgdmFyIGFyZ3MgPSBbXTsKICAgICAgICAgICAgZm9yICh2YXIgX2kgPSAxOyBfaSA8IGFyZ3VtZW50cy5sZW5ndGg7IF9pKyspIHsKICAgICAgICAgICAgICAgIGFyZ3NbX2kgLSAxXSA9IGFyZ3VtZW50c1tfaV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGNhbGxiYWNrU2V0ID0gdGhpcy5fZXZlbnROYW1lVG9DYWxsYmFja1NldFtldmVudE5hbWVdOwogICAgICAgICAgICBpZiAoY2FsbGJhY2tTZXQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgY2FsbGJhY2tTZXQuY2FsbENhbGxiYWNrcy5hcHBseShjYWxsYmFja1NldCwgYXJncyk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBEaXNwYXRjaGVyOwogICAgfSgpKTsKICAgIGV4cG9ydHMuRGlzcGF0Y2hlciA9IERpc3BhdGNoZXI7CiAgICB9KTsKCiAgICB2YXIga2V5RGlzcGF0Y2hlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCiAgICB2YXIgS2V5ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoS2V5LCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIFRoaXMgY29uc3RydWN0b3Igc2hvdWxkIG5vdCBiZSBpbnZva2VkIGRpcmVjdGx5LgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gS2V5KCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fZXZlbnRUb1Byb2Nlc3NpbmdGdW5jdGlvbltLZXkuX0tFWURPV05fRVZFTlRfTkFNRV0gPSBmdW5jdGlvbiAoZSkgeyByZXR1cm4gX3RoaXMuX3Byb2Nlc3NLZXlkb3duKGUpOyB9OwogICAgICAgICAgICBfdGhpcy5fZXZlbnRUb1Byb2Nlc3NpbmdGdW5jdGlvbltLZXkuX0tFWVVQX0VWRU5UX05BTUVdID0gZnVuY3Rpb24gKGUpIHsgcmV0dXJuIF90aGlzLl9wcm9jZXNzS2V5dXAoZSk7IH07CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyBhIEtleSBEaXNwYXRjaGVyLiBJZiBvbmUgYWxyZWFkeSBleGlzdHMgaXQgd2lsbCBiZSByZXR1cm5lZDsKICAgICAgICAgKiBvdGhlcndpc2UsIGEgbmV3IG9uZSB3aWxsIGJlIGNyZWF0ZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5LZXl9CiAgICAgICAgICovCiAgICAgICAgS2V5LmdldERpc3BhdGNoZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBkaXNwYXRjaGVyID0gZG9jdW1lbnRbS2V5Ll9ESVNQQVRDSEVSX0tFWV07CiAgICAgICAgICAgIGlmIChkaXNwYXRjaGVyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIGRpc3BhdGNoZXIgPSBuZXcgS2V5KCk7CiAgICAgICAgICAgICAgICBkb2N1bWVudFtLZXkuX0RJU1BBVENIRVJfS0VZXSA9IGRpc3BhdGNoZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGRpc3BhdGNoZXI7CiAgICAgICAgfTsKICAgICAgICBLZXkucHJvdG90eXBlLl9wcm9jZXNzS2V5ZG93biA9IGZ1bmN0aW9uIChldmVudCkgewogICAgICAgICAgICB0aGlzLl9jYWxsQ2FsbGJhY2tzRm9yRXZlbnQoS2V5Ll9LRVlET1dOX0VWRU5UX05BTUUsIGV2ZW50LmtleUNvZGUsIGV2ZW50KTsKICAgICAgICB9OwogICAgICAgIEtleS5wcm90b3R5cGUuX3Byb2Nlc3NLZXl1cCA9IGZ1bmN0aW9uIChldmVudCkgewogICAgICAgICAgICB0aGlzLl9jYWxsQ2FsbGJhY2tzRm9yRXZlbnQoS2V5Ll9LRVlVUF9FVkVOVF9OQU1FLCBldmVudC5rZXlDb2RlLCBldmVudCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZWdpc3RlcnMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbmV2ZXIgYSBrZXkgaXMgcHJlc3NlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7S2V5Q2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuS2V5fSBUaGUgY2FsbGluZyBLZXkgRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBLZXkucHJvdG90eXBlLm9uS2V5RG93biA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9hZGRDYWxsYmFja0ZvckV2ZW50KEtleS5fS0VZRE9XTl9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyB0aGUgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW5ldmVyIGEga2V5IGlzIHByZXNzZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0tleUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLktleX0gVGhlIGNhbGxpbmcgS2V5IERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgS2V5LnByb3RvdHlwZS5vZmZLZXlEb3duID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3JlbW92ZUNhbGxiYWNrRm9yRXZlbnQoS2V5Ll9LRVlET1dOX0VWRU5UX05BTUUsIGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKiogUmVnaXN0ZXJzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW5ldmVyIGEga2V5IGlzIHJlbGVhc2VkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtLZXlDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5LZXl9IFRoZSBjYWxsaW5nIEtleSBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIEtleS5wcm90b3R5cGUub25LZXlVcCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9hZGRDYWxsYmFja0ZvckV2ZW50KEtleS5fS0VZVVBfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgdGhlIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuZXZlciBhIGtleSBpcyByZWxlYXNlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7S2V5Q2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuS2V5fSBUaGUgY2FsbGluZyBLZXkgRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBLZXkucHJvdG90eXBlLm9mZktleVVwID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3JlbW92ZUNhbGxiYWNrRm9yRXZlbnQoS2V5Ll9LRVlVUF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgS2V5Ll9ESVNQQVRDSEVSX0tFWSA9ICJfX1Bsb3R0YWJsZV9EaXNwYXRjaGVyX0tleSI7CiAgICAgICAgS2V5Ll9LRVlET1dOX0VWRU5UX05BTUUgPSAia2V5ZG93biI7CiAgICAgICAgS2V5Ll9LRVlVUF9FVkVOVF9OQU1FID0gImtleXVwIjsKICAgICAgICByZXR1cm4gS2V5OwogICAgfShkaXNwYXRjaGVyLkRpc3BhdGNoZXIpKTsKICAgIGV4cG9ydHMuS2V5ID0gS2V5OwogICAgfSk7CgogICAgdmFyIG1vdXNlRGlzcGF0Y2hlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIE1vdXNlID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoTW91c2UsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBjb25zdHJ1Y3RvciBub3QgYmUgaW52b2tlZCBkaXJlY3RseS4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIE1vdXNlKGNvbXBvbmVudCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbGFzdE1vdXNlUG9zaXRpb24gPSB7IHg6IC0xLCB5OiAtMSB9OwogICAgICAgICAgICBfdGhpcy5fdHJhbnNsYXRvciA9IHV0aWxzJDEuZ2V0VHJhbnNsYXRvcihjb21wb25lbnQpOwogICAgICAgICAgICB2YXIgcHJvY2Vzc01vdmVDYWxsYmFjayA9IGZ1bmN0aW9uIChlKSB7IHJldHVybiBfdGhpcy5fbWVhc3VyZUFuZERpc3BhdGNoKGNvbXBvbmVudCwgZSwgTW91c2UuX01PVVNFTU9WRV9FVkVOVF9OQU1FLCAicGFnZSIpOyB9OwogICAgICAgICAgICBfdGhpcy5fZXZlbnRUb1Byb2Nlc3NpbmdGdW5jdGlvbltNb3VzZS5fTU9VU0VPVkVSX0VWRU5UX05BTUVdID0gcHJvY2Vzc01vdmVDYWxsYmFjazsKICAgICAgICAgICAgX3RoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb25bTW91c2UuX01PVVNFTU9WRV9FVkVOVF9OQU1FXSA9IHByb2Nlc3NNb3ZlQ2FsbGJhY2s7CiAgICAgICAgICAgIF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW01vdXNlLl9NT1VTRU9VVF9FVkVOVF9OQU1FXSA9IHByb2Nlc3NNb3ZlQ2FsbGJhY2s7CiAgICAgICAgICAgIF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW01vdXNlLl9NT1VTRURPV05fRVZFTlRfTkFNRV0gPQogICAgICAgICAgICAgICAgZnVuY3Rpb24gKGUpIHsgcmV0dXJuIF90aGlzLl9tZWFzdXJlQW5kRGlzcGF0Y2goY29tcG9uZW50LCBlLCBNb3VzZS5fTU9VU0VET1dOX0VWRU5UX05BTUUpOyB9OwogICAgICAgICAgICBfdGhpcy5fZXZlbnRUb1Byb2Nlc3NpbmdGdW5jdGlvbltNb3VzZS5fTU9VU0VVUF9FVkVOVF9OQU1FXSA9CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZSkgeyByZXR1cm4gX3RoaXMuX21lYXN1cmVBbmREaXNwYXRjaChjb21wb25lbnQsIGUsIE1vdXNlLl9NT1VTRVVQX0VWRU5UX05BTUUsICJwYWdlIik7IH07CiAgICAgICAgICAgIF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW01vdXNlLl9XSEVFTF9FVkVOVF9OQU1FXSA9CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZSkgeyByZXR1cm4gX3RoaXMuX21lYXN1cmVBbmREaXNwYXRjaChjb21wb25lbnQsIGUsIE1vdXNlLl9XSEVFTF9FVkVOVF9OQU1FKTsgfTsKICAgICAgICAgICAgX3RoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb25bTW91c2UuX0RCTENMSUNLX0VWRU5UX05BTUVdID0KICAgICAgICAgICAgICAgIGZ1bmN0aW9uIChlKSB7IHJldHVybiBfdGhpcy5fbWVhc3VyZUFuZERpc3BhdGNoKGNvbXBvbmVudCwgZSwgTW91c2UuX0RCTENMSUNLX0VWRU5UX05BTUUpOyB9OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdldCBhIE1vdXNlIERpc3BhdGNoZXIgZm9yIHRoZSBjb21wb25lbnQgdHJlZS4KICAgICAgICAgKiBJZiBvbmUgYWxyZWFkeSBleGlzdHMgb24gdGhhdCA8c3ZnPiwgaXQgd2lsbCBiZSByZXR1cm5lZDsgb3RoZXJ3aXNlLCBhIG5ldyBvbmUgd2lsbCBiZSBjcmVhdGVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtTVkdFbGVtZW50fSBlbGVtCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuTW91c2V9CiAgICAgICAgICovCiAgICAgICAgTW91c2UuZ2V0RGlzcGF0Y2hlciA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgdmFyIGVsZW1lbnQgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCk7CiAgICAgICAgICAgIHZhciBkaXNwYXRjaGVyID0gZWxlbWVudFtNb3VzZS5fRElTUEFUQ0hFUl9LRVldOwogICAgICAgICAgICBpZiAoZGlzcGF0Y2hlciA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICBkaXNwYXRjaGVyID0gbmV3IE1vdXNlKGNvbXBvbmVudCk7CiAgICAgICAgICAgICAgICBlbGVtZW50W01vdXNlLl9ESVNQQVRDSEVSX0tFWV0gPSBkaXNwYXRjaGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBkaXNwYXRjaGVyOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVnaXN0ZXJzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIG1vdXNlIHBvc2l0aW9uIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge01vdXNlQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuTW91c2V9IFRoZSBjYWxsaW5nIE1vdXNlIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLm9uTW91c2VNb3ZlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZENhbGxiYWNrRm9yRXZlbnQoTW91c2UuX01PVVNFTU9WRV9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gdGhlIG1vdXNlIHBvc2l0aW9uIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge01vdXNlQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuTW91c2V9IFRoZSBjYWxsaW5nIE1vdXNlIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLm9mZk1vdXNlTW92ZSA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVDYWxsYmFja0ZvckV2ZW50KE1vdXNlLl9NT1VTRU1PVkVfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgbW91c2Vkb3duIG9jY3Vycy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7TW91c2VDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5Nb3VzZX0gVGhlIGNhbGxpbmcgTW91c2UgRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBNb3VzZS5wcm90b3R5cGUub25Nb3VzZURvd24gPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fYWRkQ2FsbGJhY2tGb3JFdmVudChNb3VzZS5fTU9VU0VET1dOX0VWRU5UX05BTUUsIGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBhIG1vdXNlZG93biBvY2N1cnMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge01vdXNlQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuTW91c2V9IFRoZSBjYWxsaW5nIE1vdXNlIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLm9mZk1vdXNlRG93biA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVDYWxsYmFja0ZvckV2ZW50KE1vdXNlLl9NT1VTRURPV05fRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgbW91c2V1cCBvY2N1cnMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge01vdXNlQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuTW91c2V9IFRoZSBjYWxsaW5nIE1vdXNlIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLm9uTW91c2VVcCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9hZGRDYWxsYmFja0ZvckV2ZW50KE1vdXNlLl9NT1VTRVVQX0VWRU5UX05BTUUsIGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBhIG1vdXNldXAgb2NjdXJzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtNb3VzZUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLk1vdXNlfSBUaGUgY2FsbGluZyBNb3VzZSBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIE1vdXNlLnByb3RvdHlwZS5vZmZNb3VzZVVwID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3JlbW92ZUNhbGxiYWNrRm9yRXZlbnQoTW91c2UuX01PVVNFVVBfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgd2hlZWwgZXZlbnQgb2NjdXJzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtNb3VzZUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLk1vdXNlfSBUaGUgY2FsbGluZyBNb3VzZSBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIE1vdXNlLnByb3RvdHlwZS5vbldoZWVsID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZENhbGxiYWNrRm9yRXZlbnQoTW91c2UuX1dIRUVMX0VWRU5UX05BTUUsIGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBhIHdoZWVsIGV2ZW50IG9jY3Vycy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7TW91c2VDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5Nb3VzZX0gVGhlIGNhbGxpbmcgTW91c2UgRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBNb3VzZS5wcm90b3R5cGUub2ZmV2hlZWwgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fcmVtb3ZlQ2FsbGJhY2tGb3JFdmVudChNb3VzZS5fV0hFRUxfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgZGJsQ2xpY2sgb2NjdXJzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtNb3VzZUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLk1vdXNlfSBUaGUgY2FsbGluZyBNb3VzZSBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIE1vdXNlLnByb3RvdHlwZS5vbkRibENsaWNrID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZENhbGxiYWNrRm9yRXZlbnQoTW91c2UuX0RCTENMSUNLX0VWRU5UX05BTUUsIGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBhIGRibENsaWNrIG9jY3Vycy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7TW91c2VDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5Nb3VzZX0gVGhlIGNhbGxpbmcgTW91c2UgRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBNb3VzZS5wcm90b3R5cGUub2ZmRGJsQ2xpY2sgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fcmVtb3ZlQ2FsbGJhY2tGb3JFdmVudChNb3VzZS5fREJMQ0xJQ0tfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENvbXB1dGVzIHRoZSBtb3VzZSBwb3NpdGlvbiBmcm9tIHRoZSBnaXZlbiBldmVudCwgYW5kIGlmIHN1Y2Nlc3NmdWwKICAgICAgICAgKiBjYWxscyBhbGwgdGhlIGNhbGxiYWNrcyBpbiB0aGUgcHJvdmlkZWQgY2FsbGJhY2tTZXQuCiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLl9tZWFzdXJlQW5kRGlzcGF0Y2ggPSBmdW5jdGlvbiAoY29tcG9uZW50LCBldmVudCwgZXZlbnROYW1lLCBzY29wZSkgewogICAgICAgICAgICBpZiAoc2NvcGUgPT09IHZvaWQgMCkgeyBzY29wZSA9ICJlbGVtZW50IjsgfQogICAgICAgICAgICBpZiAoc2NvcGUgIT09ICJwYWdlIiAmJiBzY29wZSAhPT0gImVsZW1lbnQiKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIkludmFsaWQgc2NvcGUgJyIgKyBzY29wZSArICInLCBtdXN0IGJlICdlbGVtZW50JyBvciAncGFnZSciKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc2NvcGUgPT09ICJwYWdlIiB8fCB0aGlzLmV2ZW50SW5zaWRlKGNvbXBvbmVudCwgZXZlbnQpKSB7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpb24gPSB0aGlzLl90cmFuc2xhdG9yLmNvbXB1dGVQb3NpdGlvbihldmVudC5jbGllbnRYLCBldmVudC5jbGllbnRZKTsKICAgICAgICAgICAgICAgIHRoaXMuX2xhc3RNb3VzZVBvc2l0aW9uID0gcG9zaXRpb247CiAgICAgICAgICAgICAgICB0aGlzLl9jYWxsQ2FsbGJhY2tzRm9yRXZlbnQoZXZlbnROYW1lLCB0aGlzLmxhc3RNb3VzZVBvc2l0aW9uKCksIGV2ZW50KTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTW91c2UucHJvdG90eXBlLmV2ZW50SW5zaWRlID0gZnVuY3Rpb24gKGNvbXBvbmVudCwgZXZlbnQpIHsKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuVHJhbnNsYXRvci5pc0V2ZW50SW5zaWRlKGNvbXBvbmVudCwgZXZlbnQpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgbGFzdCBjb21wdXRlZCBtb3VzZSBwb3NpdGlvbiBpbiA8c3ZnPiBjb29yZGluYXRlIHNwYWNlLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybiB7UG9pbnR9CiAgICAgICAgICovCiAgICAgICAgTW91c2UucHJvdG90eXBlLmxhc3RNb3VzZVBvc2l0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fbGFzdE1vdXNlUG9zaXRpb247CiAgICAgICAgfTsKICAgICAgICBNb3VzZS5fRElTUEFUQ0hFUl9LRVkgPSAiX19QbG90dGFibGVfRGlzcGF0Y2hlcl9Nb3VzZSI7CiAgICAgICAgTW91c2UuX01PVVNFT1ZFUl9FVkVOVF9OQU1FID0gIm1vdXNlb3ZlciI7CiAgICAgICAgTW91c2UuX01PVVNFTU9WRV9FVkVOVF9OQU1FID0gIm1vdXNlbW92ZSI7CiAgICAgICAgTW91c2UuX01PVVNFT1VUX0VWRU5UX05BTUUgPSAibW91c2VvdXQiOwogICAgICAgIE1vdXNlLl9NT1VTRURPV05fRVZFTlRfTkFNRSA9ICJtb3VzZWRvd24iOwogICAgICAgIE1vdXNlLl9NT1VTRVVQX0VWRU5UX05BTUUgPSAibW91c2V1cCI7CiAgICAgICAgTW91c2UuX1dIRUVMX0VWRU5UX05BTUUgPSAid2hlZWwiOwogICAgICAgIE1vdXNlLl9EQkxDTElDS19FVkVOVF9OQU1FID0gImRibGNsaWNrIjsKICAgICAgICByZXR1cm4gTW91c2U7CiAgICB9KGRpc3BhdGNoZXIuRGlzcGF0Y2hlcikpOwogICAgZXhwb3J0cy5Nb3VzZSA9IE1vdXNlOwogICAgfSk7CgogICAgdmFyIHRvdWNoRGlzcGF0Y2hlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIFRvdWNoID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoVG91Y2gsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBjb25zdHJ1Y3RvciBzaG91bGQgbm90IGJlIGludm9rZWQgZGlyZWN0bHkuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1NWR0VsZW1lbnR9IHN2ZyBUaGUgcm9vdCA8c3ZnPiB0byBhdHRhY2ggdG8uCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gVG91Y2goY29tcG9uZW50KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl90cmFuc2xhdG9yID0gdXRpbHMkMS5nZXRUcmFuc2xhdG9yKGNvbXBvbmVudCk7CiAgICAgICAgICAgIF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW1RvdWNoLl9UT1VDSFNUQVJUX0VWRU5UX05BTUVdID0KICAgICAgICAgICAgICAgIGZ1bmN0aW9uIChlKSB7IHJldHVybiBfdGhpcy5fbWVhc3VyZUFuZERpc3BhdGNoKGNvbXBvbmVudCwgZSwgVG91Y2guX1RPVUNIU1RBUlRfRVZFTlRfTkFNRSwgInBhZ2UiKTsgfTsKICAgICAgICAgICAgX3RoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb25bVG91Y2guX1RPVUNITU9WRV9FVkVOVF9OQU1FXSA9CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZSkgeyByZXR1cm4gX3RoaXMuX21lYXN1cmVBbmREaXNwYXRjaChjb21wb25lbnQsIGUsIFRvdWNoLl9UT1VDSE1PVkVfRVZFTlRfTkFNRSwgInBhZ2UiKTsgfTsKICAgICAgICAgICAgX3RoaXMuX2V2ZW50VG9Qcm9jZXNzaW5nRnVuY3Rpb25bVG91Y2guX1RPVUNIRU5EX0VWRU5UX05BTUVdID0KICAgICAgICAgICAgICAgIGZ1bmN0aW9uIChlKSB7IHJldHVybiBfdGhpcy5fbWVhc3VyZUFuZERpc3BhdGNoKGNvbXBvbmVudCwgZSwgVG91Y2guX1RPVUNIRU5EX0VWRU5UX05BTUUsICJwYWdlIik7IH07CiAgICAgICAgICAgIF90aGlzLl9ldmVudFRvUHJvY2Vzc2luZ0Z1bmN0aW9uW1RvdWNoLl9UT1VDSENBTkNFTF9FVkVOVF9OQU1FXSA9CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZSkgeyByZXR1cm4gX3RoaXMuX21lYXN1cmVBbmREaXNwYXRjaChjb21wb25lbnQsIGUsIFRvdWNoLl9UT1VDSENBTkNFTF9FVkVOVF9OQU1FLCAicGFnZSIpOyB9OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgYSBUb3VjaCBEaXNwYXRjaGVyIGZvciB0aGUgY29tcG9uZW50LgogICAgICAgICAqIElmIG9uZSBhbHJlYWR5IGV4aXN0cywgaXQgd2lsbCBiZSByZXR1cm5lZDsgb3RoZXJ3aXNlLCBhIG5ldyBvbmUgd2lsbCBiZSBjcmVhdGVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIGNvbXBvbmVudAogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLlRvdWNofQogICAgICAgICAqLwogICAgICAgIFRvdWNoLmdldERpc3BhdGNoZXIgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIHZhciBzdmcgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCk7CiAgICAgICAgICAgIHZhciBkaXNwYXRjaGVyID0gc3ZnW1RvdWNoLl9ESVNQQVRDSEVSX0tFWV07CiAgICAgICAgICAgIGlmIChkaXNwYXRjaGVyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIGRpc3BhdGNoZXIgPSBuZXcgVG91Y2goY29tcG9uZW50KTsKICAgICAgICAgICAgICAgIHN2Z1tUb3VjaC5fRElTUEFUQ0hFUl9LRVldID0gZGlzcGF0Y2hlcjsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZGlzcGF0Y2hlcjsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgdG91Y2ggc3RhcnRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtUb3VjaENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLlRvdWNofSBUaGUgY2FsbGluZyBUb3VjaCBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIFRvdWNoLnByb3RvdHlwZS5vblRvdWNoU3RhcnQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fYWRkQ2FsbGJhY2tGb3JFdmVudChUb3VjaC5fVE9VQ0hTVEFSVF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gYSB0b3VjaCBzdGFydHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1RvdWNoQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuVG91Y2h9IFRoZSBjYWxsaW5nIFRvdWNoIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgVG91Y2gucHJvdG90eXBlLm9mZlRvdWNoU3RhcnQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fcmVtb3ZlQ2FsbGJhY2tGb3JFdmVudChUb3VjaC5fVE9VQ0hTVEFSVF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVnaXN0ZXJzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIHRvdWNoIHBvc2l0aW9uIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1RvdWNoQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuVG91Y2h9IFRoZSBjYWxsaW5nIFRvdWNoIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgVG91Y2gucHJvdG90eXBlLm9uVG91Y2hNb3ZlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2FkZENhbGxiYWNrRm9yRXZlbnQoVG91Y2guX1RPVUNITU9WRV9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gdGhlIHRvdWNoIHBvc2l0aW9uIGNoYW5nZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1RvdWNoQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuVG91Y2h9IFRoZSBjYWxsaW5nIFRvdWNoIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgVG91Y2gucHJvdG90eXBlLm9mZlRvdWNoTW92ZSA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVDYWxsYmFja0ZvckV2ZW50KFRvdWNoLl9UT1VDSE1PVkVfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlZ2lzdGVycyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGEgdG91Y2ggZW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7VG91Y2hDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtEaXNwYXRjaGVycy5Ub3VjaH0gVGhlIGNhbGxpbmcgVG91Y2ggRGlzcGF0Y2hlci4KICAgICAgICAgKi8KICAgICAgICBUb3VjaC5wcm90b3R5cGUub25Ub3VjaEVuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9hZGRDYWxsYmFja0ZvckV2ZW50KFRvdWNoLl9UT1VDSEVORF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gYSB0b3VjaCBlbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtUb3VjaENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLlRvdWNofSBUaGUgY2FsbGluZyBUb3VjaCBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIFRvdWNoLnByb3RvdHlwZS5vZmZUb3VjaEVuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVDYWxsYmFja0ZvckV2ZW50KFRvdWNoLl9UT1VDSEVORF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVnaXN0ZXJzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gYSB0b3VjaCBpcyBjYW5jZWxsZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1RvdWNoQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7RGlzcGF0Y2hlcnMuVG91Y2h9IFRoZSBjYWxsaW5nIFRvdWNoIERpc3BhdGNoZXIuCiAgICAgICAgICovCiAgICAgICAgVG91Y2gucHJvdG90eXBlLm9uVG91Y2hDYW5jZWwgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fYWRkQ2FsbGJhY2tGb3JFdmVudChUb3VjaC5fVE9VQ0hDQU5DRUxfRVZFTlRfTkFNRSwgY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIGEgdG91Y2ggaXMgY2FuY2VsbGVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtUb3VjaENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0Rpc3BhdGNoZXJzLlRvdWNofSBUaGUgY2FsbGluZyBUb3VjaCBEaXNwYXRjaGVyLgogICAgICAgICAqLwogICAgICAgIFRvdWNoLnByb3RvdHlwZS5vZmZUb3VjaENhbmNlbCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVDYWxsYmFja0ZvckV2ZW50KFRvdWNoLl9UT1VDSENBTkNFTF9FVkVOVF9OQU1FLCBjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQ29tcHV0ZXMgdGhlIFRvdWNoIHBvc2l0aW9uIGZyb20gdGhlIGdpdmVuIGV2ZW50LCBhbmQgaWYgc3VjY2Vzc2Z1bAogICAgICAgICAqIGNhbGxzIGFsbCB0aGUgY2FsbGJhY2tzIGluIHRoZSBwcm92aWRlZCBjYWxsYmFja1NldC4KICAgICAgICAgKi8KICAgICAgICBUb3VjaC5wcm90b3R5cGUuX21lYXN1cmVBbmREaXNwYXRjaCA9IGZ1bmN0aW9uIChjb21wb25lbnQsIGV2ZW50LCBldmVudE5hbWUsIHNjb3BlKSB7CiAgICAgICAgICAgIGlmIChzY29wZSA9PT0gdm9pZCAwKSB7IHNjb3BlID0gImVsZW1lbnQiOyB9CiAgICAgICAgICAgIGlmIChzY29wZSAhPT0gInBhZ2UiICYmIHNjb3BlICE9PSAiZWxlbWVudCIpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiSW52YWxpZCBzY29wZSAnIiArIHNjb3BlICsgIicsIG11c3QgYmUgJ2VsZW1lbnQnIG9yICdwYWdlJyIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChzY29wZSA9PT0gImVsZW1lbnQiICYmICF0aGlzLmV2ZW50SW5zaWRlKGNvbXBvbmVudCwgZXZlbnQpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRvdWNoZXMgPSBldmVudC5jaGFuZ2VkVG91Y2hlczsKICAgICAgICAgICAgdmFyIHRvdWNoUG9zaXRpb25zID0ge307CiAgICAgICAgICAgIHZhciB0b3VjaElkZW50aWZpZXJzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdG91Y2hlcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgdmFyIHRvdWNoID0gdG91Y2hlc1tpXTsKICAgICAgICAgICAgICAgIHZhciB0b3VjaElEID0gdG91Y2guaWRlbnRpZmllcjsKICAgICAgICAgICAgICAgIHZhciBuZXdUb3VjaFBvc2l0aW9uID0gdGhpcy5fdHJhbnNsYXRvci5jb21wdXRlUG9zaXRpb24odG91Y2guY2xpZW50WCwgdG91Y2guY2xpZW50WSk7CiAgICAgICAgICAgICAgICBpZiAobmV3VG91Y2hQb3NpdGlvbiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgdG91Y2hQb3NpdGlvbnNbdG91Y2hJRF0gPSBuZXdUb3VjaFBvc2l0aW9uOwogICAgICAgICAgICAgICAgICAgIHRvdWNoSWRlbnRpZmllcnMucHVzaCh0b3VjaElEKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodG91Y2hJZGVudGlmaWVycy5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jYWxsQ2FsbGJhY2tzRm9yRXZlbnQoZXZlbnROYW1lLCB0b3VjaElkZW50aWZpZXJzLCB0b3VjaFBvc2l0aW9ucywgZXZlbnQpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBUb3VjaC5wcm90b3R5cGUuZXZlbnRJbnNpZGUgPSBmdW5jdGlvbiAoY29tcG9uZW50LCBldmVudCkgewogICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5UcmFuc2xhdG9yLmlzRXZlbnRJbnNpZGUoY29tcG9uZW50LCBldmVudCk7CiAgICAgICAgfTsKICAgICAgICBUb3VjaC5fRElTUEFUQ0hFUl9LRVkgPSAiX19QbG90dGFibGVfRGlzcGF0Y2hlcl9Ub3VjaCI7CiAgICAgICAgVG91Y2guX1RPVUNIU1RBUlRfRVZFTlRfTkFNRSA9ICJ0b3VjaHN0YXJ0IjsKICAgICAgICBUb3VjaC5fVE9VQ0hNT1ZFX0VWRU5UX05BTUUgPSAidG91Y2htb3ZlIjsKICAgICAgICBUb3VjaC5fVE9VQ0hFTkRfRVZFTlRfTkFNRSA9ICJ0b3VjaGVuZCI7CiAgICAgICAgVG91Y2guX1RPVUNIQ0FOQ0VMX0VWRU5UX05BTUUgPSAidG91Y2hjYW5jZWwiOwogICAgICAgIHJldHVybiBUb3VjaDsKICAgIH0oZGlzcGF0Y2hlci5EaXNwYXRjaGVyKSk7CiAgICBleHBvcnRzLlRvdWNoID0gVG91Y2g7CiAgICB9KTsKCiAgICB2YXIgZGlzcGF0Y2hlcnMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGtleURpc3BhdGNoZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3Rhcihtb3VzZURpc3BhdGNoZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3Rhcih0b3VjaERpc3BhdGNoZXIsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIGludGVyYWN0aW9uID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgSW50ZXJhY3Rpb24gPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gSW50ZXJhY3Rpb24oKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuX2FuY2hvckNhbGxiYWNrID0gZnVuY3Rpb24gKGNvbXBvbmVudCkgeyByZXR1cm4gX3RoaXMuX2FuY2hvcihjb21wb25lbnQpOyB9OwogICAgICAgICAgICB0aGlzLl9lbmFibGVkID0gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQXR0YWNoZXMgdGhpcyBJbnRlcmFjdGlvbiB0byBhIENvbXBvbmVudC4KICAgICAgICAgKiBJZiB0aGUgSW50ZXJhY3Rpb24gd2FzIGFscmVhZHkgYXR0YWNoZWQgdG8gYSBDb21wb25lbnQsIGl0IGZpcnN0IGRldGFjaGVzIGl0c2VsZiBmcm9tIHRoZSBvbGQgQ29tcG9uZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDb21wb25lbnR9IGNvbXBvbmVudAogICAgICAgICAqIEByZXR1cm5zIHtJbnRlcmFjdGlvbn0gVGhlIGNhbGxpbmcgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgSW50ZXJhY3Rpb24ucHJvdG90eXBlLmF0dGFjaFRvID0gZnVuY3Rpb24gKGNvbXBvbmVudCkgewogICAgICAgICAgICB0aGlzLl9kaXNjb25uZWN0KCk7CiAgICAgICAgICAgIHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8gPSBjb21wb25lbnQ7CiAgICAgICAgICAgIHRoaXMuX2Nvbm5lY3QoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBAZGVwcmVjYXRlZCByZW5hbWVkIHRvIC5kZXRhY2goKS4KICAgICAgICAgKi8KICAgICAgICBJbnRlcmFjdGlvbi5wcm90b3R5cGUuZGV0YWNoRnJvbSA9IGZ1bmN0aW9uIChfY29tcG9uZW50KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmRldGFjaCgpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogRGV0YWNoZXMgdGhpcyBJbnRlcmFjdGlvbiBmcm9tIHdoYXRldmVyIGNvbXBvbmVudCBpdCB3YXMgYXR0YWNoZWQgdG8uCiAgICAgICAgICogVGhpcyBJbnRlcmFjdGlvbiBjYW4gYmUgcmV1c2VkLgogICAgICAgICAqCiAgICAgICAgICogQHJldHVybnMge0ludGVyYWN0aW9ufSBUaGUgY2FsbGluZyBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBJbnRlcmFjdGlvbi5wcm90b3R5cGUuZGV0YWNoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl9kaXNjb25uZWN0KCk7CiAgICAgICAgICAgIHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8gPSBudWxsOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEludGVyYWN0aW9uLnByb3RvdHlwZS5lbmFibGVkID0gZnVuY3Rpb24gKGVuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKGVuYWJsZWQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VuYWJsZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZW5hYmxlZCA9IGVuYWJsZWQ7CiAgICAgICAgICAgIGlmICh0aGlzLl9lbmFibGVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jb25uZWN0KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kaXNjb25uZWN0KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBJbnRlcmFjdGlvbi5wcm90b3R5cGUuX2FuY2hvciA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgdGhpcy5faXNBbmNob3JlZCA9IHRydWU7CiAgICAgICAgfTsKICAgICAgICBJbnRlcmFjdGlvbi5wcm90b3R5cGUuX3VuYW5jaG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl9pc0FuY2hvcmVkID0gZmFsc2U7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUcmFuc2xhdGVzIGFuIDxzdmc+LWNvb3JkaW5hdGUtc3BhY2UgcG9pbnQgdG8gQ29tcG9uZW50LXNwYWNlIGNvb3JkaW5hdGVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQb2ludH0gcCBBIFBvaW50IGluIDxzdmc+LXNwYWNlIGNvb3JkaW5hdGVzLgogICAgICAgICAqIEByZXR1cm4ge1BvaW50fSBUaGUgc2FtZSBsb2NhdGlvbiBpbiBDb21wb25lbnQtc3BhY2UgY29vcmRpbmF0ZXMuCiAgICAgICAgICovCiAgICAgICAgSW50ZXJhY3Rpb24ucHJvdG90eXBlLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIG9yaWdpbiA9IHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8ub3JpZ2luVG9Sb290KCk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICB4OiBwLnggLSBvcmlnaW4ueCwKICAgICAgICAgICAgICAgIHk6IHAueSAtIG9yaWdpbi55LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQ2hlY2tzIHdoZXRoZXIgYSBDb21wb25lbnQtY29vcmRpbmF0ZS1zcGFjZSBQb2ludCBpcyBpbnNpZGUgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnR9IHAgQSBQb2ludCBpbiBDb21wb2VubnQtc3BhY2UgY29vcmRpbmF0ZXMuCiAgICAgICAgICogQHJldHVybiB7Ym9vbGVhbn0gV2hldGhlciBvciBub3QgdGhlIHBvaW50IGlzIGluc2lkZSB0aGUgQ29tcG9uZW50LgogICAgICAgICAqLwogICAgICAgIEludGVyYWN0aW9uLnByb3RvdHlwZS5faXNJbnNpZGVDb21wb25lbnQgPSBmdW5jdGlvbiAocCkgewogICAgICAgICAgICByZXR1cm4gMCA8PSBwLnggJiYgMCA8PSBwLnkKICAgICAgICAgICAgICAgICYmIHAueCA8PSB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLndpZHRoKCkKICAgICAgICAgICAgICAgICYmIHAueSA8PSB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLmhlaWdodCgpOwogICAgICAgIH07CiAgICAgICAgSW50ZXJhY3Rpb24ucHJvdG90eXBlLl9jb25uZWN0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5lbmFibGVkKCkgJiYgdGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyAhPSBudWxsICYmICF0aGlzLl9pc0FuY2hvcmVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLm9uQW5jaG9yKHRoaXMuX2FuY2hvckNhbGxiYWNrKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgSW50ZXJhY3Rpb24ucHJvdG90eXBlLl9kaXNjb25uZWN0ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5faXNBbmNob3JlZCkgewogICAgICAgICAgICAgICAgdGhpcy5fdW5hbmNob3IoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLm9mZkFuY2hvcih0aGlzLl9hbmNob3JDYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBJbnRlcmFjdGlvbjsKICAgIH0oKSk7CiAgICBleHBvcnRzLkludGVyYWN0aW9uID0gSW50ZXJhY3Rpb247CiAgICB9KTsKCiAgICB2YXIgY2xpY2tJbnRlcmFjdGlvbiA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIHZhciBDbGljayA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKENsaWNrLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIENsaWNrKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIgIT09IG51bGwgJiYgX3N1cGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2NsaWNrZWREb3duID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLl9kb3VibGVDbGlja2luZyA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fb25DbGlja0NhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9vbkRvdWJsZUNsaWNrQ2FsbGJhY2tzID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIE5vdGU6IHdlIGJpbmQgdG8gbW91c2Vkb3duLCBtb3VzZXVwLCB0b3VjaHN0YXJ0IGFuZCB0b3VjaGVuZCBiZWNhdXNlIGJyb3dzZXJzCiAgICAgICAgICAgICAqIGhhdmUgYSAzMDBtcyBkZWxheSBiZXR3ZWVuIHRvdWNoc3RhcnQgYW5kIGNsaWNrIHRvIGFsbG93IGZvciBzY3JvbGxpbmcgY2FuY2VsbGluZyBldGMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBfdGhpcy5fbW91c2VEb3duQ2FsbGJhY2sgPSBmdW5jdGlvbiAocCwgZXZlbnQpIHsgcmV0dXJuIF90aGlzLl9oYW5kbGVDbGlja0Rvd24ocCwgZXZlbnQpOyB9OwogICAgICAgICAgICBfdGhpcy5fbW91c2VVcENhbGxiYWNrID0gZnVuY3Rpb24gKHAsIGV2ZW50KSB7IHJldHVybiBfdGhpcy5faGFuZGxlQ2xpY2tVcChwLCBldmVudCk7IH07CiAgICAgICAgICAgIF90aGlzLl9kYmxDbGlja0NhbGxiYWNrID0gZnVuY3Rpb24gKHAsIGV2ZW50KSB7IHJldHVybiBfdGhpcy5faGFuZGxlRGJsQ2xpY2socCwgZXZlbnQpOyB9OwogICAgICAgICAgICBfdGhpcy5fdG91Y2hTdGFydENhbGxiYWNrID0gZnVuY3Rpb24gKGlkcywgaWRUb1BvaW50LCBldmVudCkgeyByZXR1cm4gX3RoaXMuX2hhbmRsZUNsaWNrRG93bihpZFRvUG9pbnRbaWRzWzBdXSwgZXZlbnQpOyB9OwogICAgICAgICAgICBfdGhpcy5fdG91Y2hFbmRDYWxsYmFjayA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZXZlbnQpIHsgcmV0dXJuIF90aGlzLl9oYW5kbGVDbGlja1VwKGlkVG9Qb2ludFtpZHNbMF1dLCBldmVudCk7IH07CiAgICAgICAgICAgIF90aGlzLl90b3VjaENhbmNlbENhbGxiYWNrID0gZnVuY3Rpb24gKGlkcywgaWRUb1BvaW50KSB7IHJldHVybiBfdGhpcy5fY2xpY2tlZERvd24gPSBmYWxzZTsgfTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBDbGljay5wcm90b3R5cGUuX2FuY2hvciA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fYW5jaG9yLmNhbGwodGhpcywgY29tcG9uZW50KTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyID0gZGlzcGF0Y2hlcnMuTW91c2UuZ2V0RGlzcGF0Y2hlcihjb21wb25lbnQpOwogICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIub25Nb3VzZURvd24odGhpcy5fbW91c2VEb3duQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIub25Nb3VzZVVwKHRoaXMuX21vdXNlVXBDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vbkRibENsaWNrKHRoaXMuX2RibENsaWNrQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIgPSBkaXNwYXRjaGVycy5Ub3VjaC5nZXREaXNwYXRjaGVyKGNvbXBvbmVudCk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoU3RhcnQodGhpcy5fdG91Y2hTdGFydENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9uVG91Y2hFbmQodGhpcy5fdG91Y2hFbmRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoQ2FuY2VsKHRoaXMuX3RvdWNoQ2FuY2VsQ2FsbGJhY2spOwogICAgICAgIH07CiAgICAgICAgQ2xpY2sucHJvdG90eXBlLl91bmFuY2hvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fdW5hbmNob3IuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9mZk1vdXNlRG93bih0aGlzLl9tb3VzZURvd25DYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vZmZNb3VzZVVwKHRoaXMuX21vdXNlVXBDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vZmZEYmxDbGljayh0aGlzLl9kYmxDbGlja0NhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9mZlRvdWNoU3RhcnQodGhpcy5fdG91Y2hTdGFydENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9mZlRvdWNoRW5kKHRoaXMuX3RvdWNoRW5kQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIub2ZmVG91Y2hDYW5jZWwodGhpcy5fdG91Y2hDYW5jZWxDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgfTsKICAgICAgICBDbGljay5wcm90b3R5cGUuX2hhbmRsZUNsaWNrRG93biA9IGZ1bmN0aW9uIChwLCBldmVudCkgewogICAgICAgICAgICB2YXIgdHJhbnNsYXRlZFAgPSB0aGlzLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlKHApOwogICAgICAgICAgICBpZiAodGhpcy5faXNJbnNpZGVDb21wb25lbnQodHJhbnNsYXRlZFApKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jbGlja2VkRG93biA9IHRydWU7CiAgICAgICAgICAgICAgICB0aGlzLl9jbGlja2VkUG9pbnQgPSB0cmFuc2xhdGVkUDsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgQ2xpY2sucHJvdG90eXBlLl9oYW5kbGVDbGlja1VwID0gZnVuY3Rpb24gKHAsIGV2ZW50KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVkUCA9IHRoaXMuX3RyYW5zbGF0ZVRvQ29tcG9uZW50U3BhY2UocCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9jbGlja2VkRG93biAmJiBDbGljay5fcG9pbnRzRXF1YWwodHJhbnNsYXRlZFAsIHRoaXMuX2NsaWNrZWRQb2ludCkpIHsKICAgICAgICAgICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIGlmICghX3RoaXMuX2RvdWJsZUNsaWNraW5nKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIF90aGlzLl9vbkNsaWNrQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModHJhbnNsYXRlZFAsIGV2ZW50KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9LCAwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jbGlja2VkRG93biA9IGZhbHNlOwogICAgICAgIH07CiAgICAgICAgQ2xpY2sucHJvdG90eXBlLl9oYW5kbGVEYmxDbGljayA9IGZ1bmN0aW9uIChwLCBldmVudCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgdHJhbnNsYXRlZFAgPSB0aGlzLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlKHApOwogICAgICAgICAgICB0aGlzLl9kb3VibGVDbGlja2luZyA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX29uRG91YmxlQ2xpY2tDYWxsYmFja3MuY2FsbENhbGxiYWNrcyh0cmFuc2xhdGVkUCwgZXZlbnQpOwogICAgICAgICAgICBzZXRUaW1lb3V0KGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9kb3VibGVDbGlja2luZyA9IGZhbHNlOyB9LCAwKTsKICAgICAgICB9OwogICAgICAgIENsaWNrLl9wb2ludHNFcXVhbCA9IGZ1bmN0aW9uIChwMSwgcDIpIHsKICAgICAgICAgICAgcmV0dXJuIHAxLnggPT09IHAyLnggJiYgcDEueSA9PT0gcDIueTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUgQ29tcG9uZW50IGlzIGNsaWNrZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0NsaWNrQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7SW50ZXJhY3Rpb25zLkNsaWNrfSBUaGUgY2FsbGluZyBDbGljayBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBDbGljay5wcm90b3R5cGUub25DbGljayA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9vbkNsaWNrQ2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gdGhlIENvbXBvbmVudCBpcyBjbGlja2VkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDbGlja0NhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5DbGlja30gVGhlIGNhbGxpbmcgQ2xpY2sgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgQ2xpY2sucHJvdG90eXBlLm9mZkNsaWNrID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX29uQ2xpY2tDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIENvbXBvbmVudCBpcyBkb3VibGUtY2xpY2tlZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7Q2xpY2tDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtJbnRlcmFjdGlvbnMuQ2xpY2t9IFRoZSBjYWxsaW5nIENsaWNrIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIENsaWNrLnByb3RvdHlwZS5vbkRvdWJsZUNsaWNrID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX29uRG91YmxlQ2xpY2tDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiB0aGUgQ29tcG9uZW50IGlzIGRvdWJsZS1jbGlja2VkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtDbGlja0NhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5DbGlja30gVGhlIGNhbGxpbmcgQ2xpY2sgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgQ2xpY2sucHJvdG90eXBlLm9mZkRvdWJsZUNsaWNrID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX29uRG91YmxlQ2xpY2tDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ2xpY2s7CiAgICB9KGludGVyYWN0aW9uLkludGVyYWN0aW9uKSk7CiAgICBleHBvcnRzLkNsaWNrID0gQ2xpY2s7CiAgICB9KTsKCiAgICB2YXIgZHJhZ0ludGVyYWN0aW9uID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgogICAgdmFyIERyYWcgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhEcmFnLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIERyYWcobW91c2VCdXR0b24pIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2RyYWdnaW5nID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLl9jb25zdHJhaW5lZFRvQ29tcG9uZW50ID0gdHJ1ZTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIE9ubHkgZW1pdCBldmVudHMgd2hlbiB0aGUgbW91c2VGaWx0ZXIgaXMgdHJ1ZSBmb3IgdGhlIHNvdXJjZSBtb3VzZQogICAgICAgICAgICAgKiBldmVudHMuIFVzZSB0aGlzIHRvIGRlZmluZSBjdXN0b20gZmlsdGVycyAoZS5nLiBvbmx5IHJpZ2h0IGNsaWNrLAogICAgICAgICAgICAgKiByZXF1aXJlIHNoaWZ0IHRvIGJlIGhlbGQgZG93biwgZXRjLikKICAgICAgICAgICAgICovCiAgICAgICAgICAgIF90aGlzLl9tb3VzZUZpbHRlciA9IERyYWcuX0RFRkFVTFRfTU9VU0VfRklMVEVSOwogICAgICAgICAgICBfdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdDYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICBfdGhpcy5fZHJhZ0VuZENhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9tb3VzZURvd25DYWxsYmFjayA9IGZ1bmN0aW9uIChwLCBlKSB7IHJldHVybiBfdGhpcy5fc3RhcnREcmFnKHAsIGUpOyB9OwogICAgICAgICAgICBfdGhpcy5fbW91c2VNb3ZlQ2FsbGJhY2sgPSBmdW5jdGlvbiAocCwgZSkgeyByZXR1cm4gX3RoaXMuX2RvRHJhZyhwLCBlKTsgfTsKICAgICAgICAgICAgX3RoaXMuX21vdXNlVXBDYWxsYmFjayA9IGZ1bmN0aW9uIChwLCBlKSB7IHJldHVybiBfdGhpcy5fZW5kRHJhZyhwLCBlKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3RvdWNoU3RhcnRDYWxsYmFjayA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgeyByZXR1cm4gX3RoaXMuX3N0YXJ0RHJhZyhpZFRvUG9pbnRbaWRzWzBdXSwgZSk7IH07CiAgICAgICAgICAgIF90aGlzLl90b3VjaE1vdmVDYWxsYmFjayA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgeyByZXR1cm4gX3RoaXMuX2RvRHJhZyhpZFRvUG9pbnRbaWRzWzBdXSwgZSk7IH07CiAgICAgICAgICAgIF90aGlzLl90b3VjaEVuZENhbGxiYWNrID0gZnVuY3Rpb24gKGlkcywgaWRUb1BvaW50LCBlKSB7IHJldHVybiBfdGhpcy5fZW5kRHJhZyhpZFRvUG9pbnRbaWRzWzBdXSwgZSk7IH07CiAgICAgICAgICAgIF90aGlzLl9tb3VzZUJ1dHRvbiA9IG1vdXNlQnV0dG9uICE9PSB1bmRlZmluZWQgPyBtb3VzZUJ1dHRvbiA6IDA7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgRHJhZy5wcm90b3R5cGUuX2FuY2hvciA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fYW5jaG9yLmNhbGwodGhpcywgY29tcG9uZW50KTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyID0gZGlzcGF0Y2hlcnMuTW91c2UuZ2V0RGlzcGF0Y2hlcih0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9uTW91c2VEb3duKHRoaXMuX21vdXNlRG93bkNhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9uTW91c2VNb3ZlKHRoaXMuX21vdXNlTW92ZUNhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9uTW91c2VVcCh0aGlzLl9tb3VzZVVwQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIgPSBkaXNwYXRjaGVycy5Ub3VjaC5nZXREaXNwYXRjaGVyKHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8pOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIub25Ub3VjaFN0YXJ0KHRoaXMuX3RvdWNoU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoTW92ZSh0aGlzLl90b3VjaE1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoRW5kKHRoaXMuX3RvdWNoRW5kQ2FsbGJhY2spOwogICAgICAgIH07CiAgICAgICAgRHJhZy5wcm90b3R5cGUuX3VuYW5jaG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl91bmFuY2hvci5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIub2ZmTW91c2VEb3duKHRoaXMuX21vdXNlRG93bkNhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9mZk1vdXNlTW92ZSh0aGlzLl9tb3VzZU1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vZmZNb3VzZVVwKHRoaXMuX21vdXNlVXBDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vZmZUb3VjaFN0YXJ0KHRoaXMuX3RvdWNoU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vZmZUb3VjaE1vdmUodGhpcy5fdG91Y2hNb3ZlQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIub2ZmVG91Y2hFbmQodGhpcy5fdG91Y2hFbmRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgfTsKICAgICAgICBEcmFnLnByb3RvdHlwZS5fdHJhbnNsYXRlQW5kQ29uc3RyYWluID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIHRyYW5zbGF0ZWRQID0gdGhpcy5fdHJhbnNsYXRlVG9Db21wb25lbnRTcGFjZShwKTsKICAgICAgICAgICAgaWYgKCF0aGlzLl9jb25zdHJhaW5lZFRvQ29tcG9uZW50KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJhbnNsYXRlZFA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHg6IHV0aWxzJDEuTWF0aC5jbGFtcCh0cmFuc2xhdGVkUC54LCAwLCB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLndpZHRoKCkpLAogICAgICAgICAgICAgICAgeTogdXRpbHMkMS5NYXRoLmNsYW1wKHRyYW5zbGF0ZWRQLnksIDAsIHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8uaGVpZ2h0KCkpLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgRHJhZy5wcm90b3R5cGUuX3N0YXJ0RHJhZyA9IGZ1bmN0aW9uIChwb2ludCwgZXZlbnQpIHsKICAgICAgICAgICAgaWYgKGV2ZW50IGluc3RhbmNlb2YgTW91c2VFdmVudCAmJiAhdGhpcy5fbW91c2VGaWx0ZXIoZXZlbnQpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRyYW5zbGF0ZWRQID0gdGhpcy5fdHJhbnNsYXRlVG9Db21wb25lbnRTcGFjZShwb2ludCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc0luc2lkZUNvbXBvbmVudCh0cmFuc2xhdGVkUCkpIHsKICAgICAgICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnZ2luZyA9IHRydWU7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnT3JpZ2luID0gdHJhbnNsYXRlZFA7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnU3RhcnRDYWxsYmFja3MuY2FsbENhbGxiYWNrcyh0aGlzLl9kcmFnT3JpZ2luKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgRHJhZy5wcm90b3R5cGUuX2RvRHJhZyA9IGZ1bmN0aW9uIChwb2ludCwgZXZlbnQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2RyYWdnaW5nKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModGhpcy5fZHJhZ09yaWdpbiwgdGhpcy5fdHJhbnNsYXRlQW5kQ29uc3RyYWluKHBvaW50KSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIERyYWcucHJvdG90eXBlLl9lbmREcmFnID0gZnVuY3Rpb24gKHBvaW50LCBldmVudCkgewogICAgICAgICAgICBpZiAoZXZlbnQgaW5zdGFuY2VvZiBNb3VzZUV2ZW50ICYmIGV2ZW50LmJ1dHRvbiAhPT0gdGhpcy5fbW91c2VCdXR0b24pIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fZHJhZ2dpbmcpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2RyYWdnaW5nID0gZmFsc2U7CiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnRW5kQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModGhpcy5fZHJhZ09yaWdpbiwgdGhpcy5fdHJhbnNsYXRlQW5kQ29uc3RyYWluKHBvaW50KSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIERyYWcucHJvdG90eXBlLmNvbnN0cmFpbmVkVG9Db21wb25lbnQgPSBmdW5jdGlvbiAoY29uc3RyYWluZWRUb0NvbXBvbmVudCkgewogICAgICAgICAgICBpZiAoY29uc3RyYWluZWRUb0NvbXBvbmVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fY29uc3RyYWluZWRUb0NvbXBvbmVudDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jb25zdHJhaW5lZFRvQ29tcG9uZW50ID0gY29uc3RyYWluZWRUb0NvbXBvbmVudDsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBEcmFnLnByb3RvdHlwZS5tb3VzZUZpbHRlciA9IGZ1bmN0aW9uIChmaWx0ZXIpIHsKICAgICAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9tb3VzZUZpbHRlcjsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9tb3VzZUZpbHRlciA9IGZpbHRlcjsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgc3RhcnRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWd9IFRoZSBjYWxsaW5nIERyYWcgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgRHJhZy5wcm90b3R5cGUub25EcmFnU3RhcnQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgc3RhcnRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWd9IFRoZSBjYWxsaW5nIERyYWcgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgRHJhZy5wcm90b3R5cGUub2ZmRHJhZ1N0YXJ0ID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdTdGFydENhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgZHVyaW5nIGRyYWdnaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWd9IFRoZSBjYWxsaW5nIERyYWcgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgRHJhZy5wcm90b3R5cGUub25EcmFnID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgZHVyaW5nIGRyYWdnaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWd9IFRoZSBjYWxsaW5nIERyYWcgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgRHJhZy5wcm90b3R5cGUub2ZmRHJhZyA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9kcmFnQ2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGRyYWdnaW5nIGVuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RyYWdDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ30gVGhlIGNhbGxpbmcgRHJhZyBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBEcmFnLnByb3RvdHlwZS5vbkRyYWdFbmQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ0VuZENhbGxiYWNrcy5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIGRyYWdnaW5nIGVuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RyYWdDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ30gVGhlIGNhbGxpbmcgRHJhZyBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBEcmFnLnByb3RvdHlwZS5vZmZEcmFnRW5kID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdFbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBEcmFnLl9ERUZBVUxUX01PVVNFX0ZJTFRFUiA9IGZ1bmN0aW9uIChldmVudCkgeyByZXR1cm4gZXZlbnQuYnV0dG9uID09PSAwOyB9OwogICAgICAgIHJldHVybiBEcmFnOwogICAgfShpbnRlcmFjdGlvbi5JbnRlcmFjdGlvbikpOwogICAgZXhwb3J0cy5EcmFnID0gRHJhZzsKICAgIH0pOwoKICAgIHZhciBrZXlJbnRlcmFjdGlvbiA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIHZhciBLZXkgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhLZXksIF9zdXBlcik7CiAgICAgICAgZnVuY3Rpb24gS2V5KCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIgIT09IG51bGwgJiYgX3N1cGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2tleVByZXNzQ2FsbGJhY2tzID0ge307CiAgICAgICAgICAgIF90aGlzLl9rZXlSZWxlYXNlQ2FsbGJhY2tzID0ge307CiAgICAgICAgICAgIF90aGlzLl9tb3VzZU1vdmVDYWxsYmFjayA9IGZ1bmN0aW9uIChwb2ludCkgeyByZXR1cm4gZmFsc2U7IH07IC8vIEhBQ0tIQUNLOiByZWdpc3RlcmluZyBhIGxpc3RlbmVyCiAgICAgICAgICAgIF90aGlzLl9kb3duZWRLZXlzID0gbmV3IHV0aWxzJDEuU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9rZXlEb3duQ2FsbGJhY2sgPSBmdW5jdGlvbiAoa2V5Q29kZSwgZXZlbnQpIHsgcmV0dXJuIF90aGlzLl9oYW5kbGVLZXlEb3duRXZlbnQoa2V5Q29kZSwgZXZlbnQpOyB9OwogICAgICAgICAgICBfdGhpcy5fa2V5VXBDYWxsYmFjayA9IGZ1bmN0aW9uIChrZXlDb2RlKSB7IHJldHVybiBfdGhpcy5faGFuZGxlS2V5VXBFdmVudChrZXlDb2RlKTsgfTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBLZXkucHJvdG90eXBlLl9hbmNob3IgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX2FuY2hvci5jYWxsKHRoaXMsIGNvbXBvbmVudCk7CiAgICAgICAgICAgIHRoaXMuX3Bvc2l0aW9uRGlzcGF0Y2hlciA9IGRpc3BhdGNoZXJzLk1vdXNlLmdldERpc3BhdGNoZXIodGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyk7CiAgICAgICAgICAgIHRoaXMuX3Bvc2l0aW9uRGlzcGF0Y2hlci5vbk1vdXNlTW92ZSh0aGlzLl9tb3VzZU1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX2tleURpc3BhdGNoZXIgPSBkaXNwYXRjaGVycy5LZXkuZ2V0RGlzcGF0Y2hlcigpOwogICAgICAgICAgICB0aGlzLl9rZXlEaXNwYXRjaGVyLm9uS2V5RG93bih0aGlzLl9rZXlEb3duQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9rZXlEaXNwYXRjaGVyLm9uS2V5VXAodGhpcy5fa2V5VXBDYWxsYmFjayk7CiAgICAgICAgfTsKICAgICAgICBLZXkucHJvdG90eXBlLl91bmFuY2hvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fdW5hbmNob3IuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fcG9zaXRpb25EaXNwYXRjaGVyLm9mZk1vdXNlTW92ZSh0aGlzLl9tb3VzZU1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3Bvc2l0aW9uRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX2tleURpc3BhdGNoZXIub2ZmS2V5RG93bih0aGlzLl9rZXlEb3duQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9rZXlEaXNwYXRjaGVyLm9mZktleVVwKHRoaXMuX2tleVVwQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9rZXlEaXNwYXRjaGVyID0gbnVsbDsKICAgICAgICB9OwogICAgICAgIEtleS5wcm90b3R5cGUuX2hhbmRsZUtleURvd25FdmVudCA9IGZ1bmN0aW9uIChrZXlDb2RlLCBldmVudCkgewogICAgICAgICAgICB2YXIgcCA9IHRoaXMuX3RyYW5zbGF0ZVRvQ29tcG9uZW50U3BhY2UodGhpcy5fcG9zaXRpb25EaXNwYXRjaGVyLmxhc3RNb3VzZVBvc2l0aW9uKCkpOwogICAgICAgICAgICBpZiAodGhpcy5faXNJbnNpZGVDb21wb25lbnQocCkgJiYgIWV2ZW50LnJlcGVhdCkgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2tleVByZXNzQ2FsbGJhY2tzW2tleUNvZGVdKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fa2V5UHJlc3NDYWxsYmFja3Nba2V5Q29kZV0uY2FsbENhbGxiYWNrcyhrZXlDb2RlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2Rvd25lZEtleXMuYWRkKGtleUNvZGUpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBLZXkucHJvdG90eXBlLl9oYW5kbGVLZXlVcEV2ZW50ID0gZnVuY3Rpb24gKGtleUNvZGUpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2Rvd25lZEtleXMuaGFzKGtleUNvZGUpICYmIHRoaXMuX2tleVJlbGVhc2VDYWxsYmFja3Nba2V5Q29kZV0pIHsKICAgICAgICAgICAgICAgIHRoaXMuX2tleVJlbGVhc2VDYWxsYmFja3Nba2V5Q29kZV0uY2FsbENhbGxiYWNrcyhrZXlDb2RlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9kb3duZWRLZXlzLmRlbGV0ZShrZXlDb2RlKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUga2V5IHdpdGggdGhlIGdpdmVuIGtleUNvZGUgaXMKICAgICAgICAgKiBwcmVzc2VkIGFuZCB0aGUgdXNlciBpcyBtb3VzZWQgb3ZlciB0aGUgQ29tcG9uZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGtleUNvZGUKICAgICAgICAgKiBAcGFyYW0ge0tleUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtJbnRlcmFjdGlvbnMuS2V5fSBUaGUgY2FsbGluZyBLZXkgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgS2V5LnByb3RvdHlwZS5vbktleVByZXNzID0gZnVuY3Rpb24gKGtleUNvZGUsIGNhbGxiYWNrKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fa2V5UHJlc3NDYWxsYmFja3Nba2V5Q29kZV0pIHsKICAgICAgICAgICAgICAgIHRoaXMuX2tleVByZXNzQ2FsbGJhY2tzW2tleUNvZGVdID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9rZXlQcmVzc0NhbGxiYWNrc1trZXlDb2RlXS5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIHRoZSBrZXkgd2l0aCB0aGUgZ2l2ZW4ga2V5Q29kZSBpcwogICAgICAgICAqIHByZXNzZWQgYW5kIHRoZSB1c2VyIGlzIG1vdXNlZCBvdmVyIHRoZSBDb21wb25lbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0ga2V5Q29kZQogICAgICAgICAqIEBwYXJhbSB7S2V5Q2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0ludGVyYWN0aW9ucy5LZXl9IFRoZSBjYWxsaW5nIEtleSBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBLZXkucHJvdG90eXBlLm9mZktleVByZXNzID0gZnVuY3Rpb24gKGtleUNvZGUsIGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2tleVByZXNzQ2FsbGJhY2tzW2tleUNvZGVdLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIGlmICh0aGlzLl9rZXlQcmVzc0NhbGxiYWNrc1trZXlDb2RlXS5zaXplID09PSAwKSB7CiAgICAgICAgICAgICAgICBkZWxldGUgdGhpcy5fa2V5UHJlc3NDYWxsYmFja3Nba2V5Q29kZV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gdGhlIGtleSB3aXRoIHRoZSBnaXZlbiBrZXlDb2RlIGlzCiAgICAgICAgICogcmVsZWFzZWQgaWYgdGhlIGtleSB3YXMgcHJlc3NlZCB3aXRoIHRoZSBtb3VzZSBpbnNpZGUgb2YgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBrZXlDb2RlCiAgICAgICAgICogQHBhcmFtIHtLZXlDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7SW50ZXJhY3Rpb25zLktleX0gVGhlIGNhbGxpbmcgS2V5IEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIEtleS5wcm90b3R5cGUub25LZXlSZWxlYXNlID0gZnVuY3Rpb24gKGtleUNvZGUsIGNhbGxiYWNrKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXSkgewogICAgICAgICAgICAgICAgdGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXSA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXS5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIHRoZSBrZXkgd2l0aCB0aGUgZ2l2ZW4ga2V5Q29kZSBpcwogICAgICAgICAqIHJlbGVhc2VkIGlmIHRoZSBrZXkgd2FzIHByZXNzZWQgd2l0aCB0aGUgbW91c2UgaW5zaWRlIG9mIHRoZSBDb21wb25lbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0ga2V5Q29kZQogICAgICAgICAqIEBwYXJhbSB7S2V5Q2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0ludGVyYWN0aW9ucy5LZXl9IFRoZSBjYWxsaW5nIEtleSBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBLZXkucHJvdG90eXBlLm9mZktleVJlbGVhc2UgPSBmdW5jdGlvbiAoa2V5Q29kZSwgY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXS5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICBpZiAodGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXS5zaXplID09PSAwKSB7CiAgICAgICAgICAgICAgICBkZWxldGUgdGhpcy5fa2V5UmVsZWFzZUNhbGxiYWNrc1trZXlDb2RlXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIHJldHVybiBLZXk7CiAgICB9KGludGVyYWN0aW9uLkludGVyYWN0aW9uKSk7CiAgICBleHBvcnRzLktleSA9IEtleTsKICAgIH0pOwoKICAgIHZhciBwYW5ab29tSW50ZXJhY3Rpb24gPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgoKCgogICAgdmFyIFBhblpvb20gPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhQYW5ab29tLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEEgUGFuWm9vbSBJbnRlcmFjdGlvbiB1cGRhdGVzIHRoZSBkb21haW5zIG9mIGFuIHgtc2NhbGUgYW5kL29yIGEgeS1zY2FsZQogICAgICAgICAqIGluIHJlc3BvbnNlIHRvIHRoZSB1c2VyIHBhbm5pbmcgb3Igem9vbWluZy4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7VHJhbnNmb3JtYWJsZVNjYWxlfSBbeFNjYWxlXSBUaGUgeC1zY2FsZSB0byB1cGRhdGUgb24gcGFubmluZy96b29taW5nLgogICAgICAgICAqIEBwYXJhbSB7VHJhbnNmb3JtYWJsZVNjYWxlfSBbeVNjYWxlXSBUaGUgeS1zY2FsZSB0byB1cGRhdGUgb24gcGFubmluZy96b29taW5nLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFBhblpvb20oeFNjYWxlLCB5U2NhbGUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX3doZWVsRmlsdGVyID0gZnVuY3Rpb24gKGUpIHsgcmV0dXJuIHRydWU7IH07CiAgICAgICAgICAgIF90aGlzLl93aGVlbENhbGxiYWNrID0gZnVuY3Rpb24gKHAsIGUpIHsgcmV0dXJuIF90aGlzLl9oYW5kbGVXaGVlbEV2ZW50KHAsIGUpOyB9OwogICAgICAgICAgICBfdGhpcy5fdG91Y2hTdGFydENhbGxiYWNrID0gZnVuY3Rpb24gKGlkcywgaWRUb1BvaW50LCBlKSB7IHJldHVybiBfdGhpcy5faGFuZGxlVG91Y2hTdGFydChpZHMsIGlkVG9Qb2ludCwgZSk7IH07CiAgICAgICAgICAgIF90aGlzLl90b3VjaE1vdmVDYWxsYmFjayA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgeyByZXR1cm4gX3RoaXMuX2hhbmRsZVBpbmNoKGlkcywgaWRUb1BvaW50LCBlKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3RvdWNoRW5kQ2FsbGJhY2sgPSBmdW5jdGlvbiAoaWRzLCBpZFRvUG9pbnQsIGUpIHsgcmV0dXJuIF90aGlzLl9oYW5kbGVUb3VjaEVuZChpZHMsIGlkVG9Qb2ludCwgZSk7IH07CiAgICAgICAgICAgIF90aGlzLl90b3VjaENhbmNlbENhbGxiYWNrID0gZnVuY3Rpb24gKGlkcywgaWRUb1BvaW50LCBlKSB7IHJldHVybiBfdGhpcy5faGFuZGxlVG91Y2hFbmQoaWRzLCBpZFRvUG9pbnQsIGUpOyB9OwogICAgICAgICAgICBfdGhpcy5fcGFuRW5kQ2FsbGJhY2tzID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgX3RoaXMuX3pvb21FbmRDYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICBfdGhpcy5fcGFuWm9vbVVwZGF0ZUNhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl94U2NhbGVzID0gbmV3IHV0aWxzJDEuU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl95U2NhbGVzID0gbmV3IHV0aWxzJDEuU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9kcmFnSW50ZXJhY3Rpb24gPSBuZXcgaW50ZXJhY3Rpb25zLkRyYWcoKTsKICAgICAgICAgICAgX3RoaXMuX3NldHVwRHJhZ0ludGVyYWN0aW9uKCk7CiAgICAgICAgICAgIF90aGlzLl90b3VjaElkcyA9IGQzLm1hcCgpOwogICAgICAgICAgICBfdGhpcy5fbWluRG9tYWluRXh0ZW50cyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgICAgICBfdGhpcy5fbWF4RG9tYWluRXh0ZW50cyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgICAgICBfdGhpcy5fbWluRG9tYWluVmFsdWVzID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIF90aGlzLl9tYXhEb21haW5WYWx1ZXMgPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICAgICAgaWYgKHhTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5hZGRYU2NhbGUoeFNjYWxlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoeVNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIF90aGlzLmFkZFlTY2FsZSh5U2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0IHRoZSBiYWNraW5nIGRyYWcgaW50ZXJhY3Rpb24uIFVzZWZ1bCB0byBjdXN0b21pemUgdGhlIHBhbnpvb20gaW50ZXJhY3Rpb24uCiAgICAgICAgICogQHJldHVybnMge0RyYWd9CiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUuZHJhZ0ludGVyYWN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZHJhZ0ludGVyYWN0aW9uOwogICAgICAgIH07CiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUud2hlZWxGaWx0ZXIgPSBmdW5jdGlvbiAoZmlsdGVyKSB7CiAgICAgICAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fd2hlZWxGaWx0ZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fd2hlZWxGaWx0ZXIgPSBmaWx0ZXI7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUGFucyB0aGUgY2hhcnQgYnkgYSBzcGVjaWZpZWQgYW1vdW50CiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1Bsb3R0YWJsZS5Qb2ludH0gW3RyYW5zbGF0ZUFtb3VudF0gVGhlIGFtb3VudCBieSB3aGljaCB0byB0cmFuc2xhdGUgdGhlIHggYW5kIHkgc2NhbGVzLgogICAgICAgICAqLwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLnBhbiA9IGZ1bmN0aW9uICh0cmFuc2xhdGVBbW91bnQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdGhpcy54U2NhbGVzKCkuZm9yRWFjaChmdW5jdGlvbiAoeFNjYWxlKSB7CiAgICAgICAgICAgICAgICB4U2NhbGUucGFuKF90aGlzLl9jb25zdHJhaW5lZFRyYW5zbGF0aW9uKHhTY2FsZSwgdHJhbnNsYXRlQW1vdW50LngpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMueVNjYWxlcygpLmZvckVhY2goZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICAgICAgeVNjYWxlLnBhbihfdGhpcy5fY29uc3RyYWluZWRUcmFuc2xhdGlvbih5U2NhbGUsIHRyYW5zbGF0ZUFtb3VudC55KSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9wYW5ab29tVXBkYXRlQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3MoKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFpvb21zIHRoZSBjaGFydCBieSBhIHNwZWNpZmllZCBhbW91bnQgYXJvdW5kIGEgc3BlY2lmaWMgcG9pbnQKICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbem9vbUFtb3VudF0gVGhlIHBlcmNlbnRhZ2UgYnkgd2hpY2ggdG8gem9vbSB0aGUgeCBhbmQgeSBzY2FsZS4KICAgICAgICAgKiBBIHZhbHVlIG9mIDAuOSB6b29tcyBpbiBieSAxMCUuIEEgdmFsdWUgb2YgMS4xIHpvb21zIG91dCBieSAxMCUuIEEgdmFsdWUgb2YgMSBoYXMKICAgICAgICAgKiBubyBlZmZlY3QuCiAgICAgICAgICogQHBhcmFtIHtQbG90dGFibGUuUG9pbnR9IFtjZW50ZXJWYWx1ZV0gVGhlIGNlbnRlciBpbiBwaXhlbHMgYXJvdW5kIHdoaWNoIHRvIHpvb20uCiAgICAgICAgICogQnkgZGVmYXVsdCwgYGNlbnRlclZhbHVlYCBpcyB0aGUgY2VudGVyIG9mIHRoZSB4IGFuZCB5IHJhbmdlIG9mIGVhY2ggc2NhbGUuCiAgICAgICAgICogQHBhcmFtIHtib29sZWFufSBbY29uc3RyYWluZWRdIFdoZXRoZXIgdG8gcmVzcGVjdCB0aGUgem9vbSBleHRlbnRzIGFuZCBtaW4vbWF4CiAgICAgICAgICogdmFsdWVzLiBEZWZhdWx0IHRydWUuCiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUuem9vbSA9IGZ1bmN0aW9uICh6b29tQW1vdW50LCBjZW50ZXJWYWx1ZSwgY29uc3RyYWluZWQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKGNvbnN0cmFpbmVkID09PSB2b2lkIDApIHsgY29uc3RyYWluZWQgPSB0cnVlOyB9CiAgICAgICAgICAgIHZhciBjZW50ZXJYOwogICAgICAgICAgICB2YXIgY2VudGVyWTsKICAgICAgICAgICAgaWYgKGNlbnRlclZhbHVlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGNlbnRlclggPSBjZW50ZXJWYWx1ZS54OwogICAgICAgICAgICAgICAgY2VudGVyWSA9IGNlbnRlclZhbHVlLnk7CiAgICAgICAgICAgICAgICBpZiAoY29uc3RyYWluZWQpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnhTY2FsZXMoKS5mb3JFYWNoKGZ1bmN0aW9uICh4U2NhbGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIGNvbnN0cmFpbmVkID0gX3RoaXMuX2NvbnN0cmFpbmVkWm9vbSh4U2NhbGUsIHpvb21BbW91bnQsIGNlbnRlclgpOwogICAgICAgICAgICAgICAgICAgICAgICBjZW50ZXJYID0gY29uc3RyYWluZWQuY2VudGVyUG9pbnQ7CiAgICAgICAgICAgICAgICAgICAgICAgIHpvb21BbW91bnQgPSBjb25zdHJhaW5lZC56b29tQW1vdW50OwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIHRoaXMueVNjYWxlcygpLmZvckVhY2goZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICAgICAgICAgICAgICB2YXIgY29uc3RyYWluZWQgPSBfdGhpcy5fY29uc3RyYWluZWRab29tKHlTY2FsZSwgem9vbUFtb3VudCwgY2VudGVyWSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNlbnRlclkgPSBjb25zdHJhaW5lZC5jZW50ZXJQb2ludDsKICAgICAgICAgICAgICAgICAgICAgICAgem9vbUFtb3VudCA9IGNvbnN0cmFpbmVkLnpvb21BbW91bnQ7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy54U2NhbGVzKCkuZm9yRWFjaChmdW5jdGlvbiAoeFNjYWxlKSB7CiAgICAgICAgICAgICAgICB2YXIgcmFuZ2UgPSB4U2NhbGUucmFuZ2UoKTsKICAgICAgICAgICAgICAgIHZhciB4Q2VudGVyID0gY2VudGVyWCA9PSBudWxsCiAgICAgICAgICAgICAgICAgICAgPyAocmFuZ2VbMV0gKyByYW5nZVswXSkgLyAyCiAgICAgICAgICAgICAgICAgICAgOiBjZW50ZXJYOwogICAgICAgICAgICAgICAgeFNjYWxlLnpvb20oem9vbUFtb3VudCwgeENlbnRlcik7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLnlTY2FsZXMoKS5mb3JFYWNoKGZ1bmN0aW9uICh5U2NhbGUpIHsKICAgICAgICAgICAgICAgIHZhciByYW5nZSA9IHlTY2FsZS5yYW5nZSgpOwogICAgICAgICAgICAgICAgdmFyIHlDZW50ZXIgPSBjZW50ZXJZID09IG51bGwKICAgICAgICAgICAgICAgICAgICA/IChyYW5nZVsxXSArIHJhbmdlWzBdKSAvIDIKICAgICAgICAgICAgICAgICAgICA6IGNlbnRlclk7CiAgICAgICAgICAgICAgICB5U2NhbGUuem9vbSh6b29tQW1vdW50LCB5Q2VudGVyKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX3Bhblpvb21VcGRhdGVDYWxsYmFja3MuY2FsbENhbGxiYWNrcygpOwogICAgICAgICAgICByZXR1cm4geyB6b29tQW1vdW50OiB6b29tQW1vdW50LCBjZW50ZXJWYWx1ZTogeyBjZW50ZXJYOiBjZW50ZXJYLCBjZW50ZXJZOiBjZW50ZXJZIH0gfTsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9hbmNob3IgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX2FuY2hvci5jYWxsKHRoaXMsIGNvbXBvbmVudCk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdJbnRlcmFjdGlvbi5hdHRhY2hUbyhjb21wb25lbnQpOwogICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIgPSBkaXNwYXRjaGVycy5Nb3VzZS5nZXREaXNwYXRjaGVyKHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8pOwogICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIub25XaGVlbCh0aGlzLl93aGVlbENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyID0gZGlzcGF0Y2hlcnMuVG91Y2guZ2V0RGlzcGF0Y2hlcih0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9uVG91Y2hTdGFydCh0aGlzLl90b3VjaFN0YXJ0Q2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIub25Ub3VjaE1vdmUodGhpcy5fdG91Y2hNb3ZlQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIub25Ub3VjaEVuZCh0aGlzLl90b3VjaEVuZENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9uVG91Y2hDYW5jZWwodGhpcy5fdG91Y2hDYW5jZWxDYWxsYmFjayk7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5fdW5hbmNob3IgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3VuYW5jaG9yLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vZmZXaGVlbCh0aGlzLl93aGVlbENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9mZlRvdWNoU3RhcnQodGhpcy5fdG91Y2hTdGFydENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9mZlRvdWNoTW92ZSh0aGlzLl90b3VjaE1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vZmZUb3VjaEVuZCh0aGlzLl90b3VjaEVuZENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fdG91Y2hEaXNwYXRjaGVyLm9mZlRvdWNoQ2FuY2VsKHRoaXMuX3RvdWNoQ2FuY2VsQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl90b3VjaERpc3BhdGNoZXIgPSBudWxsOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24uZGV0YWNoKCk7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5faGFuZGxlVG91Y2hTdGFydCA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgewogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGlkcy5sZW5ndGggJiYgdGhpcy5fdG91Y2hJZHMuc2l6ZSgpIDwgMjsgaSsrKSB7CiAgICAgICAgICAgICAgICB2YXIgaWQgPSBpZHNbaV07CiAgICAgICAgICAgICAgICB0aGlzLl90b3VjaElkcy5zZXQoaWQudG9TdHJpbmcoKSwgdGhpcy5fdHJhbnNsYXRlVG9Db21wb25lbnRTcGFjZShpZFRvUG9pbnRbaWRdKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9oYW5kbGVQaW5jaCA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAodGhpcy5fdG91Y2hJZHMuc2l6ZSgpIDwgMikgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBvbGRQb2ludHMgPSB0aGlzLl90b3VjaElkcy52YWx1ZXMoKTsKICAgICAgICAgICAgaWYgKCF0aGlzLl9pc0luc2lkZUNvbXBvbmVudCh0aGlzLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlKG9sZFBvaW50c1swXSkpIHx8ICF0aGlzLl9pc0luc2lkZUNvbXBvbmVudCh0aGlzLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlKG9sZFBvaW50c1sxXSkpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIG9sZENvcm5lckRpc3RhbmNlID0gUGFuWm9vbS5fcG9pbnREaXN0YW5jZShvbGRQb2ludHNbMF0sIG9sZFBvaW50c1sxXSk7CiAgICAgICAgICAgIGlmIChvbGRDb3JuZXJEaXN0YW5jZSA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlkcy5mb3JFYWNoKGZ1bmN0aW9uIChpZCkgewogICAgICAgICAgICAgICAgaWYgKF90aGlzLl90b3VjaElkcy5oYXMoaWQudG9TdHJpbmcoKSkpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fdG91Y2hJZHMuc2V0KGlkLnRvU3RyaW5nKCksIF90aGlzLl90cmFuc2xhdGVUb0NvbXBvbmVudFNwYWNlKGlkVG9Qb2ludFtpZF0pKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciBwb2ludHMgPSB0aGlzLl90b3VjaElkcy52YWx1ZXMoKTsKICAgICAgICAgICAgdmFyIG5ld0Nvcm5lckRpc3RhbmNlID0gUGFuWm9vbS5fcG9pbnREaXN0YW5jZShwb2ludHNbMF0sIHBvaW50c1sxXSk7CiAgICAgICAgICAgIGlmIChuZXdDb3JuZXJEaXN0YW5jZSA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBpbml0TWFnbmlmeUFtb3VudCA9IG9sZENvcm5lckRpc3RhbmNlIC8gbmV3Q29ybmVyRGlzdGFuY2U7CiAgICAgICAgICAgIHZhciBub3JtYWxpemVkUG9pbnREaWZmcyA9IHBvaW50cy5tYXAoZnVuY3Rpb24gKHBvaW50LCBpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIHg6IChwb2ludC54IC0gb2xkUG9pbnRzW2ldLngpIC8gaW5pdE1hZ25pZnlBbW91bnQsCiAgICAgICAgICAgICAgICAgICAgeTogKHBvaW50LnkgLSBvbGRQb2ludHNbaV0ueSkgLyBpbml0TWFnbmlmeUFtb3VudCwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgb2xkQ2VudGVyUG9pbnQgPSBQYW5ab29tLmNlbnRlclBvaW50KG9sZFBvaW50c1swXSwgb2xkUG9pbnRzWzFdKTsKICAgICAgICAgICAgdmFyIF9hID0gdGhpcy56b29tKGluaXRNYWduaWZ5QW1vdW50LCBvbGRDZW50ZXJQb2ludCksIGNlbnRlclZhbHVlID0gX2EuY2VudGVyVmFsdWUsIHpvb21BbW91bnQgPSBfYS56b29tQW1vdW50OwogICAgICAgICAgICB2YXIgY2VudGVyWCA9IGNlbnRlclZhbHVlLmNlbnRlclgsIGNlbnRlclkgPSBjZW50ZXJWYWx1ZS5jZW50ZXJZOwogICAgICAgICAgICB2YXIgY29uc3RyYWluZWRQb2ludHMgPSBvbGRQb2ludHMubWFwKGZ1bmN0aW9uIChvbGRQb2ludCwgaSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICB4OiBub3JtYWxpemVkUG9pbnREaWZmc1tpXS54ICogem9vbUFtb3VudCArIG9sZFBvaW50LngsCiAgICAgICAgICAgICAgICAgICAgeTogbm9ybWFsaXplZFBvaW50RGlmZnNbaV0ueSAqIHpvb21BbW91bnQgKyBvbGRQb2ludC55LAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVBbW91bnQgPSB7CiAgICAgICAgICAgICAgICB4OiBjZW50ZXJYIC0gKChjb25zdHJhaW5lZFBvaW50c1swXS54ICsgY29uc3RyYWluZWRQb2ludHNbMV0ueCkgLyAyKSwKICAgICAgICAgICAgICAgIHk6IGNlbnRlclkgLSAoKGNvbnN0cmFpbmVkUG9pbnRzWzBdLnkgKyBjb25zdHJhaW5lZFBvaW50c1sxXS55KSAvIDIpLAogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLnBhbih0cmFuc2xhdGVBbW91bnQpOwogICAgICAgIH07CiAgICAgICAgUGFuWm9vbS5jZW50ZXJQb2ludCA9IGZ1bmN0aW9uIChwb2ludDEsIHBvaW50MikgewogICAgICAgICAgICB2YXIgbGVmdFggPSBNYXRoLm1pbihwb2ludDEueCwgcG9pbnQyLngpOwogICAgICAgICAgICB2YXIgcmlnaHRYID0gTWF0aC5tYXgocG9pbnQxLngsIHBvaW50Mi54KTsKICAgICAgICAgICAgdmFyIHRvcFkgPSBNYXRoLm1pbihwb2ludDEueSwgcG9pbnQyLnkpOwogICAgICAgICAgICB2YXIgYm90dG9tWSA9IE1hdGgubWF4KHBvaW50MS55LCBwb2ludDIueSk7CiAgICAgICAgICAgIHJldHVybiB7IHg6IChsZWZ0WCArIHJpZ2h0WCkgLyAyLCB5OiAoYm90dG9tWSArIHRvcFkpIC8gMiB9OwogICAgICAgIH07CiAgICAgICAgUGFuWm9vbS5fcG9pbnREaXN0YW5jZSA9IGZ1bmN0aW9uIChwb2ludDEsIHBvaW50MikgewogICAgICAgICAgICB2YXIgbGVmdFggPSBNYXRoLm1pbihwb2ludDEueCwgcG9pbnQyLngpOwogICAgICAgICAgICB2YXIgcmlnaHRYID0gTWF0aC5tYXgocG9pbnQxLngsIHBvaW50Mi54KTsKICAgICAgICAgICAgdmFyIHRvcFkgPSBNYXRoLm1pbihwb2ludDEueSwgcG9pbnQyLnkpOwogICAgICAgICAgICB2YXIgYm90dG9tWSA9IE1hdGgubWF4KHBvaW50MS55LCBwb2ludDIueSk7CiAgICAgICAgICAgIHJldHVybiBNYXRoLnNxcnQoTWF0aC5wb3cocmlnaHRYIC0gbGVmdFgsIDIpICsgTWF0aC5wb3coYm90dG9tWSAtIHRvcFksIDIpKTsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9oYW5kbGVUb3VjaEVuZCA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZHMuZm9yRWFjaChmdW5jdGlvbiAoaWQpIHsKICAgICAgICAgICAgICAgIF90aGlzLl90b3VjaElkcy5yZW1vdmUoaWQudG9TdHJpbmcoKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBpZiAodGhpcy5fdG91Y2hJZHMuc2l6ZSgpID4gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fem9vbUVuZENhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9oYW5kbGVXaGVlbEV2ZW50ID0gZnVuY3Rpb24gKHAsIGUpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl93aGVlbEZpbHRlcihlKSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVkUCA9IHRoaXMuX3RyYW5zbGF0ZVRvQ29tcG9uZW50U3BhY2UocCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc0luc2lkZUNvbXBvbmVudCh0cmFuc2xhdGVkUCkpIHsKICAgICAgICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgICAgICAgIC8vIGluIGNhc2VzIHdoZXJlIG9ubHkgaG9yaXpvbnRhbCBzY3JvbGwgaXMgcHJlc2VudCwgdXNlIHRoYXQgaW4gbGlldSBvZiBub3RoaW5nLgogICAgICAgICAgICAgICAgdmFyIGRlbHRhQW1vdW50ID0gZS5kZWx0YVkgIT09IDAgPyBlLmRlbHRhWSA6IGUuZGVsdGFYOwogICAgICAgICAgICAgICAgdmFyIGRlbHRhUGl4ZWxBbW91bnQgPSBkZWx0YUFtb3VudCAqIChlLmRlbHRhTW9kZSA/IFBhblpvb20uX1BJWEVMU19QRVJfTElORSA6IDEpOwogICAgICAgICAgICAgICAgdmFyIHpvb21BbW91bnQgPSBNYXRoLnBvdygyLCBkZWx0YVBpeGVsQW1vdW50ICogLjAwMik7CiAgICAgICAgICAgICAgICB0aGlzLnpvb20oem9vbUFtb3VudCwgdHJhbnNsYXRlZFApOwogICAgICAgICAgICAgICAgdGhpcy5fem9vbUVuZENhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9jb25zdHJhaW5lZFpvb20gPSBmdW5jdGlvbiAoc2NhbGUsIHpvb21BbW91bnQsIGNlbnRlclBvaW50KSB7CiAgICAgICAgICAgIHJldHVybiBwYW5ab29tQ29uc3RyYWludHMuY29uc3RyYWluZWRab29tKHNjYWxlLCB6b29tQW1vdW50LCBjZW50ZXJQb2ludCwgdGhpcy5taW5Eb21haW5FeHRlbnQoc2NhbGUpLCB0aGlzLm1heERvbWFpbkV4dGVudChzY2FsZSksIHRoaXMubWluRG9tYWluVmFsdWUoc2NhbGUpLCB0aGlzLm1heERvbWFpblZhbHVlKHNjYWxlKSk7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5fY29uc3RyYWluZWRUcmFuc2xhdGlvbiA9IGZ1bmN0aW9uIChzY2FsZSwgdHJhbnNsYXRpb24pIHsKICAgICAgICAgICAgcmV0dXJuIHBhblpvb21Db25zdHJhaW50cy5jb25zdHJhaW5lZFRyYW5zbGF0aW9uKHNjYWxlLCB0cmFuc2xhdGlvbiwgdGhpcy5taW5Eb21haW5WYWx1ZShzY2FsZSksIHRoaXMubWF4RG9tYWluVmFsdWUoc2NhbGUpKTsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9zZXR1cERyYWdJbnRlcmFjdGlvbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmNvbnN0cmFpbmVkVG9Db21wb25lbnQoZmFsc2UpOwogICAgICAgICAgICB2YXIgbGFzdERyYWdQb2ludDsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9uRHJhZ1N0YXJ0KGZ1bmN0aW9uICgpIHsgcmV0dXJuIGxhc3REcmFnUG9pbnQgPSBudWxsOyB9KTsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9uRHJhZyhmdW5jdGlvbiAoc3RhcnRQb2ludCwgZW5kUG9pbnQpIHsKICAgICAgICAgICAgICAgIGlmIChfdGhpcy5fdG91Y2hJZHMuc2l6ZSgpID49IDIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgdHJhbnNsYXRlQW1vdW50ID0gewogICAgICAgICAgICAgICAgICAgIHg6IChsYXN0RHJhZ1BvaW50ID09IG51bGwgPyBzdGFydFBvaW50LnggOiBsYXN0RHJhZ1BvaW50LngpIC0gZW5kUG9pbnQueCwKICAgICAgICAgICAgICAgICAgICB5OiAobGFzdERyYWdQb2ludCA9PSBudWxsID8gc3RhcnRQb2ludC55IDogbGFzdERyYWdQb2ludC55KSAtIGVuZFBvaW50LnksCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgX3RoaXMucGFuKHRyYW5zbGF0ZUFtb3VudCk7CiAgICAgICAgICAgICAgICBsYXN0RHJhZ1BvaW50ID0gZW5kUG9pbnQ7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24ub25EcmFnRW5kKGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9wYW5FbmRDYWxsYmFja3MuY2FsbENhbGxiYWNrcygpOyB9KTsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLl9ub25MaW5lYXJTY2FsZVdpdGhFeHRlbnRzID0gZnVuY3Rpb24gKHNjYWxlKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLm1pbkRvbWFpbkV4dGVudChzY2FsZSkgIT0gbnVsbCAmJiB0aGlzLm1heERvbWFpbkV4dGVudChzY2FsZSkgIT0gbnVsbCAmJiAhKHNjYWxlIGluc3RhbmNlb2Ygc2NhbGVzLkxpbmVhcikgJiYgIShzY2FsZSBpbnN0YW5jZW9mIHNjYWxlcy5UaW1lKTsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLnhTY2FsZXMgPSBmdW5jdGlvbiAoeFNjYWxlcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAoeFNjYWxlcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgc2NhbGVzXzEgPSBbXTsKICAgICAgICAgICAgICAgIHRoaXMuX3hTY2FsZXMuZm9yRWFjaChmdW5jdGlvbiAoeFNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgc2NhbGVzXzEucHVzaCh4U2NhbGUpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICByZXR1cm4gc2NhbGVzXzE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5feFNjYWxlcyA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgICAgICAgICB4U2NhbGVzLmZvckVhY2goZnVuY3Rpb24gKHhTY2FsZSkgewogICAgICAgICAgICAgICAgX3RoaXMuYWRkWFNjYWxlKHhTY2FsZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLnlTY2FsZXMgPSBmdW5jdGlvbiAoeVNjYWxlcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAoeVNjYWxlcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgc2NhbGVzXzIgPSBbXTsKICAgICAgICAgICAgICAgIHRoaXMuX3lTY2FsZXMuZm9yRWFjaChmdW5jdGlvbiAoeVNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgc2NhbGVzXzIucHVzaCh5U2NhbGUpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICByZXR1cm4gc2NhbGVzXzI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5feVNjYWxlcyA9IG5ldyB1dGlscyQxLlNldCgpOwogICAgICAgICAgICB5U2NhbGVzLmZvckVhY2goZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICAgICAgX3RoaXMuYWRkWVNjYWxlKHlTY2FsZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYW4geCBzY2FsZSB0byB0aGlzIFBhblpvb20gSW50ZXJhY3Rpb24KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7VHJhbnNmb3JtYWJsZVNjYWxlfSBBbiB4IHNjYWxlIHRvIGFkZAogICAgICAgICAqIEByZXR1cm5zIHtJbnRlcmFjdGlvbnMuUGFuWm9vbX0gVGhlIGNhbGxpbmcgUGFuWm9vbSBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5hZGRYU2NhbGUgPSBmdW5jdGlvbiAoeFNjYWxlKSB7CiAgICAgICAgICAgIHRoaXMuX3hTY2FsZXMuYWRkKHhTY2FsZSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhbiB4IHNjYWxlIGZyb20gdGhpcyBQYW5ab29tIEludGVyYWN0aW9uCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1RyYW5zZm9ybWFibGVTY2FsZX0gQW4geCBzY2FsZSB0byByZW1vdmUKICAgICAgICAgKiBAcmV0dXJucyB7SW50ZXJhY3Rpb25zLlBhblpvb219IFRoZSBjYWxsaW5nIFBhblpvb20gSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUucmVtb3ZlWFNjYWxlID0gZnVuY3Rpb24gKHhTY2FsZSkgewogICAgICAgICAgICB0aGlzLl94U2NhbGVzLmRlbGV0ZSh4U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5FeHRlbnRzLmRlbGV0ZSh4U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9tYXhEb21haW5FeHRlbnRzLmRlbGV0ZSh4U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5WYWx1ZXMuZGVsZXRlKHhTY2FsZSk7CiAgICAgICAgICAgIHRoaXMuX21heERvbWFpblZhbHVlcy5kZWxldGUoeFNjYWxlKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgeSBzY2FsZSB0byB0aGlzIFBhblpvb20gSW50ZXJhY3Rpb24KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7VHJhbnNmb3JtYWJsZVNjYWxlfSBBIHkgc2NhbGUgdG8gYWRkCiAgICAgICAgICogQHJldHVybnMge0ludGVyYWN0aW9ucy5QYW5ab29tfSBUaGUgY2FsbGluZyBQYW5ab29tIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLmFkZFlTY2FsZSA9IGZ1bmN0aW9uICh5U2NhbGUpIHsKICAgICAgICAgICAgdGhpcy5feVNjYWxlcy5hZGQoeVNjYWxlKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgeSBzY2FsZSBmcm9tIHRoaXMgUGFuWm9vbSBJbnRlcmFjdGlvbgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtUcmFuc2Zvcm1hYmxlU2NhbGV9IEEgeSBzY2FsZSB0byByZW1vdmUKICAgICAgICAgKiBAcmV0dXJucyB7SW50ZXJhY3Rpb25zLlBhblpvb219IFRoZSBjYWxsaW5nIFBhblpvb20gSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUucmVtb3ZlWVNjYWxlID0gZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICB0aGlzLl95U2NhbGVzLmRlbGV0ZSh5U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5FeHRlbnRzLmRlbGV0ZSh5U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9tYXhEb21haW5FeHRlbnRzLmRlbGV0ZSh5U2NhbGUpOwogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5WYWx1ZXMuZGVsZXRlKHlTY2FsZSk7CiAgICAgICAgICAgIHRoaXMuX21heERvbWFpblZhbHVlcy5kZWxldGUoeVNjYWxlKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5taW5Eb21haW5FeHRlbnQgPSBmdW5jdGlvbiAoc2NhbGUsIG1pbkRvbWFpbkV4dGVudCkgewogICAgICAgICAgICBpZiAobWluRG9tYWluRXh0ZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9taW5Eb21haW5FeHRlbnRzLmdldChzY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG1pbkRvbWFpbkV4dGVudC52YWx1ZU9mKCkgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoImV4dGVudCBtdXN0IGJlIG5vbi1uZWdhdGl2ZSIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBtYXhFeHRlbnRGb3JTY2FsZSA9IHRoaXMubWF4RG9tYWluRXh0ZW50KHNjYWxlKTsKICAgICAgICAgICAgaWYgKG1heEV4dGVudEZvclNjYWxlICE9IG51bGwgJiYgbWF4RXh0ZW50Rm9yU2NhbGUudmFsdWVPZigpIDwgbWluRG9tYWluRXh0ZW50LnZhbHVlT2YoKSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJtaW5Eb21haW5FeHRlbnQgbXVzdCBiZSBzbWFsbGVyIHRoYW4gbWF4RG9tYWluRXh0ZW50IGZvciB0aGUgc2FtZSBTY2FsZSIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl9ub25MaW5lYXJTY2FsZVdpdGhFeHRlbnRzKHNjYWxlKSkgewogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cud2FybigiUGFubmluZyBhbmQgem9vbWluZyB3aXRoIGV4dGVudHMgb24gYSBub25saW5lYXIgc2NhbGUgbWF5IGhhdmUgdW5pbnRlbmRlZCBiZWhhdmlvci4iKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5FeHRlbnRzLnNldChzY2FsZSwgbWluRG9tYWluRXh0ZW50KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5tYXhEb21haW5FeHRlbnQgPSBmdW5jdGlvbiAoc2NhbGUsIG1heERvbWFpbkV4dGVudCkgewogICAgICAgICAgICBpZiAobWF4RG9tYWluRXh0ZW50ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhEb21haW5FeHRlbnRzLmdldChzY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG1heERvbWFpbkV4dGVudC52YWx1ZU9mKCkgPD0gMCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJleHRlbnQgbXVzdCBiZSBwb3NpdGl2ZSIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBtaW5FeHRlbnRGb3JTY2FsZSA9IHRoaXMubWluRG9tYWluRXh0ZW50KHNjYWxlKTsKICAgICAgICAgICAgaWYgKG1pbkV4dGVudEZvclNjYWxlICE9IG51bGwgJiYgbWF4RG9tYWluRXh0ZW50LnZhbHVlT2YoKSA8IG1pbkV4dGVudEZvclNjYWxlLnZhbHVlT2YoKSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJtYXhEb21haW5FeHRlbnQgbXVzdCBiZSBsYXJnZXIgdGhhbiBtaW5Eb21haW5FeHRlbnQgZm9yIHRoZSBzYW1lIFNjYWxlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX25vbkxpbmVhclNjYWxlV2l0aEV4dGVudHMoc2NhbGUpKSB7CiAgICAgICAgICAgICAgICB1dGlscyQxLldpbmRvdy53YXJuKCJQYW5uaW5nIGFuZCB6b29taW5nIHdpdGggZXh0ZW50cyBvbiBhIG5vbmxpbmVhciBzY2FsZSBtYXkgaGF2ZSB1bmludGVuZGVkIGJlaGF2aW9yLiIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX21heERvbWFpbkV4dGVudHMuc2V0KHNjYWxlLCBtYXhEb21haW5FeHRlbnQpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLm1pbkRvbWFpblZhbHVlID0gZnVuY3Rpb24gKHNjYWxlLCBtaW5Eb21haW5WYWx1ZSkgewogICAgICAgICAgICBpZiAobWluRG9tYWluVmFsdWUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21pbkRvbWFpblZhbHVlcy5nZXQoc2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX21pbkRvbWFpblZhbHVlcy5zZXQoc2NhbGUsIG1pbkRvbWFpblZhbHVlKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5tYXhEb21haW5WYWx1ZSA9IGZ1bmN0aW9uIChzY2FsZSwgbWF4RG9tYWluVmFsdWUpIHsKICAgICAgICAgICAgaWYgKG1heERvbWFpblZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9tYXhEb21haW5WYWx1ZXMuZ2V0KHNjYWxlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9tYXhEb21haW5WYWx1ZXMuc2V0KHNjYWxlLCBtYXhEb21haW5WYWx1ZSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVXNlcyB0aGUgY3VycmVudCBkb21haW4gb2YgdGhlIHNjYWxlIHRvIGFwcGx5IGEgbWluaW11bSBhbmQgbWF4aW11bQogICAgICAgICAqIGRvbWFpbiB2YWx1ZSBmb3IgdGhhdCBzY2FsZS4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgY29uc3RyYWlucyB0aGUgcGFuL3pvb20gaW50ZXJhY3Rpb24gdG8gc2hvdyBubyBtb3JlIHRoYW4gdGhlIGRvbWFpbgogICAgICAgICAqIG9mIHRoZSBzY2FsZS4KICAgICAgICAgKi8KICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5zZXRNaW5NYXhEb21haW5WYWx1ZXNUbyA9IGZ1bmN0aW9uIChzY2FsZSkgewogICAgICAgICAgICB0aGlzLl9taW5Eb21haW5WYWx1ZXMuZGVsZXRlKHNjYWxlKTsKICAgICAgICAgICAgdGhpcy5fbWF4RG9tYWluVmFsdWVzLmRlbGV0ZShzY2FsZSk7CiAgICAgICAgICAgIHZhciBfYSA9IHNjYWxlLmdldFRyYW5zZm9ybWF0aW9uRG9tYWluKCksIGRvbWFpbk1pbiA9IF9hWzBdLCBkb21haW5NYXggPSBfYVsxXTsKICAgICAgICAgICAgdGhpcy5taW5Eb21haW5WYWx1ZShzY2FsZSwgZG9tYWluTWluKTsKICAgICAgICAgICAgdGhpcy5tYXhEb21haW5WYWx1ZShzY2FsZSwgZG9tYWluTWF4KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gcGFubmluZyBlbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQYW5DYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7dGhpc30gVGhlIGNhbGxpbmcgUGFuWm9vbSBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5vblBhbkVuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9wYW5FbmRDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBwYW5uaW5nIGVuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BhbkNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHt0aGlzfSBUaGUgY2FsbGluZyBQYW5ab29tIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLm9mZlBhbkVuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9wYW5FbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gem9vbWluZyBlbmRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtab29tQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge3RoaXN9IFRoZSBjYWxsaW5nIFBhblpvb20gSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUub25ab29tRW5kID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3pvb21FbmRDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiB6b29taW5nIGVuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1pvb21DYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7dGhpc30gVGhlIGNhbGxpbmcgUGFuWm9vbSBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBQYW5ab29tLnByb3RvdHlwZS5vZmZab29tRW5kID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3pvb21FbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gYW55IHBhbiBvciB6b29tIHVwZGF0ZSBvY2N1cnMuIFRoaXMgaXMKICAgICAgICAgKiBjYWxsZWQgb24gZXZlcnkgZnJhbWUsIHNvIGJlIHN1cmUgeW91ciBjYWxsYmFjayBpcyBmYXN0LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQYW5ab29tVXBkYXRlQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge3RoaXN9IFRoZSBjYWxsaW5nIFBhblpvb20gSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgUGFuWm9vbS5wcm90b3R5cGUub25QYW5ab29tVXBkYXRlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3Bhblpvb21VcGRhdGVDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiBhbnkgcGFuIG9yIHpvb20gdXBkYXRlIG9jY3Vycy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UGFuWm9vbVVwZGF0ZUNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHt0aGlzfSBUaGUgY2FsbGluZyBQYW5ab29tIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBhblpvb20ucHJvdG90eXBlLm9mZlBhblpvb21VcGRhdGUgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fcGFuWm9vbVVwZGF0ZUNhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBudW1iZXIgb2YgcGl4ZWxzIG9jY3VwaWVkIGluIGEgbGluZS4KICAgICAgICAgKi8KICAgICAgICBQYW5ab29tLl9QSVhFTFNfUEVSX0xJTkUgPSAxMjA7CiAgICAgICAgcmV0dXJuIFBhblpvb207CiAgICB9KGludGVyYWN0aW9uLkludGVyYWN0aW9uKSk7CiAgICBleHBvcnRzLlBhblpvb20gPSBQYW5ab29tOwogICAgfSk7CgogICAgdmFyIHBvaW50ZXJJbnRlcmFjdGlvbiA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIHZhciBQb2ludGVyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUG9pbnRlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBQb2ludGVyKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIgIT09IG51bGwgJiYgX3N1cGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX292ZXJDb21wb25lbnQgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuX3BvaW50ZXJFbnRlckNhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9wb2ludGVyTW92ZUNhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9wb2ludGVyRXhpdENhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9tb3VzZU1vdmVDYWxsYmFjayA9IGZ1bmN0aW9uIChwLCBlKSB7IHJldHVybiBfdGhpcy5faGFuZGxlTW91c2VFdmVudChwLCBlKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3RvdWNoU3RhcnRDYWxsYmFjayA9IGZ1bmN0aW9uIChpZHMsIGlkVG9Qb2ludCwgZSkgeyByZXR1cm4gX3RoaXMuX2hhbmRsZVRvdWNoRXZlbnQoaWRUb1BvaW50W2lkc1swXV0sIGUpOyB9OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLl9hbmNob3IgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX2FuY2hvci5jYWxsKHRoaXMsIGNvbXBvbmVudCk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlciA9IGRpc3BhdGNoZXJzLk1vdXNlLmdldERpc3BhdGNoZXIodGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vbk1vdXNlTW92ZSh0aGlzLl9tb3VzZU1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlciA9IGRpc3BhdGNoZXJzLlRvdWNoLmdldERpc3BhdGNoZXIodGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoU3RhcnQodGhpcy5fdG91Y2hTdGFydENhbGxiYWNrKTsKICAgICAgICB9OwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLl91bmFuY2hvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fdW5hbmNob3IuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyLm9mZk1vdXNlTW92ZSh0aGlzLl9tb3VzZU1vdmVDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vZmZUb3VjaFN0YXJ0KHRoaXMuX3RvdWNoU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX3RvdWNoRGlzcGF0Y2hlciA9IG51bGw7CiAgICAgICAgfTsKICAgICAgICBQb2ludGVyLnByb3RvdHlwZS5faGFuZGxlTW91c2VFdmVudCA9IGZ1bmN0aW9uIChwLCBlKSB7CiAgICAgICAgICAgIHZhciBpbnNpZGVTVkcgPSB0aGlzLl9tb3VzZURpc3BhdGNoZXIuZXZlbnRJbnNpZGUodGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbywgZSk7CiAgICAgICAgICAgIHRoaXMuX2hhbmRsZVBvaW50ZXJFdmVudChwLCBpbnNpZGVTVkcpOwogICAgICAgIH07CiAgICAgICAgUG9pbnRlci5wcm90b3R5cGUuX2hhbmRsZVRvdWNoRXZlbnQgPSBmdW5jdGlvbiAocCwgZSkgewogICAgICAgICAgICB2YXIgaW5zaWRlU1ZHID0gdGhpcy5fdG91Y2hEaXNwYXRjaGVyLmV2ZW50SW5zaWRlKHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8sIGUpOwogICAgICAgICAgICB0aGlzLl9oYW5kbGVQb2ludGVyRXZlbnQocCwgaW5zaWRlU1ZHKTsKICAgICAgICB9OwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLl9oYW5kbGVQb2ludGVyRXZlbnQgPSBmdW5jdGlvbiAocCwgaW5zaWRlU1ZHKSB7CiAgICAgICAgICAgIHZhciB0cmFuc2xhdGVkUCA9IHRoaXMuX3RyYW5zbGF0ZVRvQ29tcG9uZW50U3BhY2UocCk7CiAgICAgICAgICAgIHZhciBvdmVyQ29tcG9uZW50ID0gdGhpcy5faXNJbnNpZGVDb21wb25lbnQodHJhbnNsYXRlZFApOwogICAgICAgICAgICBpZiAob3ZlckNvbXBvbmVudCAmJiBpbnNpZGVTVkcpIHsKICAgICAgICAgICAgICAgIGlmICghdGhpcy5fb3ZlckNvbXBvbmVudCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFbnRlckNhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKHRyYW5zbGF0ZWRQKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJNb3ZlQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModHJhbnNsYXRlZFApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHRoaXMuX292ZXJDb21wb25lbnQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFeGl0Q2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModHJhbnNsYXRlZFApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX292ZXJDb21wb25lbnQgPSBvdmVyQ29tcG9uZW50ICYmIGluc2lkZVNWRzsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUgcG9pbnRlciBlbnRlcnMgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnRlckNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5Qb2ludGVyfSBUaGUgY2FsbGluZyBQb2ludGVyIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLm9uUG9pbnRlckVudGVyID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFbnRlckNhbGxiYWNrcy5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIHRoZSBwb2ludGVyIGVudGVycyB0aGUgQ29tcG9uZW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQb2ludGVyQ2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybiB7SW50ZXJhY3Rpb25zLlBvaW50ZXJ9IFRoZSBjYWxsaW5nIFBvaW50ZXIgSW50ZXJhY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgUG9pbnRlci5wcm90b3R5cGUub2ZmUG9pbnRlckVudGVyID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFbnRlckNhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUgcG9pbnRlciBtb3ZlcyB3aXRoaW4gdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnRlckNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5Qb2ludGVyfSBUaGUgY2FsbGluZyBQb2ludGVyIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLm9uUG9pbnRlck1vdmUgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fcG9pbnRlck1vdmVDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgd2hlbiB0aGUgcG9pbnRlciBtb3ZlcyB3aXRoaW4gdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnRlckNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5Qb2ludGVyfSBUaGUgY2FsbGluZyBQb2ludGVyIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLm9mZlBvaW50ZXJNb3ZlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJNb3ZlQ2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIHRoZSBwb2ludGVyIGV4aXRzIHRoZSBDb21wb25lbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50ZXJDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJuIHtJbnRlcmFjdGlvbnMuUG9pbnRlcn0gVGhlIGNhbGxpbmcgUG9pbnRlciBJbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBQb2ludGVyLnByb3RvdHlwZS5vblBvaW50ZXJFeGl0ID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFeGl0Q2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gdGhlIHBvaW50ZXIgZXhpdHMgdGhlIENvbXBvbmVudC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnRlckNhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm4ge0ludGVyYWN0aW9ucy5Qb2ludGVyfSBUaGUgY2FsbGluZyBQb2ludGVyIEludGVyYWN0aW9uLgogICAgICAgICAqLwogICAgICAgIFBvaW50ZXIucHJvdG90eXBlLm9mZlBvaW50ZXJFeGl0ID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX3BvaW50ZXJFeGl0Q2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFBvaW50ZXI7CiAgICB9KGludGVyYWN0aW9uLkludGVyYWN0aW9uKSk7CiAgICBleHBvcnRzLlBvaW50ZXIgPSBQb2ludGVyOwogICAgfSk7CgogICAgdmFyIGludGVyYWN0aW9ucyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoY2xpY2tJbnRlcmFjdGlvbiwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGRyYWdJbnRlcmFjdGlvbiwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGtleUludGVyYWN0aW9uLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIocGFuWm9vbUludGVyYWN0aW9uLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIocG9pbnRlckludGVyYWN0aW9uLCBleHBvcnRzKTsKCiAgICBleHBvcnRzLnpvb21PdXQgPSBwYW5ab29tQ29uc3RyYWludHMuem9vbU91dDsKICAgIH0pOwoKICAgIHZhciBzZWxlY3Rpb25Cb3hMYXllciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIFByb3BlcnR5TW9kZTsKICAgIChmdW5jdGlvbiAoUHJvcGVydHlNb2RlKSB7CiAgICAgICAgUHJvcGVydHlNb2RlW1Byb3BlcnR5TW9kZVsiVkFMVUUiXSA9IDBdID0gIlZBTFVFIjsKICAgICAgICBQcm9wZXJ0eU1vZGVbUHJvcGVydHlNb2RlWyJQSVhFTCJdID0gMV0gPSAiUElYRUwiOwogICAgfSkoUHJvcGVydHlNb2RlID0gZXhwb3J0cy5Qcm9wZXJ0eU1vZGUgfHwgKGV4cG9ydHMuUHJvcGVydHlNb2RlID0ge30pKTsKICAgIHZhciBTZWxlY3Rpb25Cb3hMYXllciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFNlbGVjdGlvbkJveExheWVyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFNlbGVjdGlvbkJveExheWVyKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fYm94VmlzaWJsZSA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fYm94Qm91bmRzID0gewogICAgICAgICAgICAgICAgdG9wTGVmdDogeyB4OiAwLCB5OiAwIH0sCiAgICAgICAgICAgICAgICBib3R0b21SaWdodDogeyB4OiAwLCB5OiAwIH0sCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIF90aGlzLl94Qm91bmRzTW9kZSA9IFByb3BlcnR5TW9kZS5QSVhFTDsKICAgICAgICAgICAgX3RoaXMuX3lCb3VuZHNNb2RlID0gUHJvcGVydHlNb2RlLlBJWEVMOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygic2VsZWN0aW9uLWJveC1sYXllciIpOwogICAgICAgICAgICBfdGhpcy5fYWRqdXN0Qm91bmRzQ2FsbGJhY2sgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgX3RoaXMuX292ZXJmbG93SGlkZGVuID0gdHJ1ZTsKICAgICAgICAgICAgX3RoaXMuX3hFeHRlbnQgPSBbdW5kZWZpbmVkLCB1bmRlZmluZWRdOwogICAgICAgICAgICBfdGhpcy5feUV4dGVudCA9IFt1bmRlZmluZWQsIHVuZGVmaW5lZF07CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgU2VsZWN0aW9uQm94TGF5ZXIucHJvdG90eXBlLl9zZXR1cCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fc2V0dXAuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fYm94ID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikuY2xhc3NlZCgic2VsZWN0aW9uLWJveCIsIHRydWUpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9ib3hBcmVhID0gdGhpcy5fYm94LmFwcGVuZCgicmVjdCIpLmNsYXNzZWQoInNlbGVjdGlvbi1hcmVhIiwgdHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuX3NpemVGcm9tT2ZmZXIgPSBmdW5jdGlvbiAoYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgd2lkdGg6IGF2YWlsYWJsZVdpZHRoLAogICAgICAgICAgICAgICAgaGVpZ2h0OiBhdmFpbGFibGVIZWlnaHQsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuYm91bmRzID0gZnVuY3Rpb24gKG5ld0JvdW5kcykgewogICAgICAgICAgICBpZiAobmV3Qm91bmRzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXRCb3VuZHMoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9zZXRCb3VuZHMobmV3Qm91bmRzKTsKICAgICAgICAgICAgdGhpcy5feEJvdW5kc01vZGUgPSBQcm9wZXJ0eU1vZGUuUElYRUw7CiAgICAgICAgICAgIHRoaXMuX3lCb3VuZHNNb2RlID0gUHJvcGVydHlNb2RlLlBJWEVMOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS5fc2V0Qm91bmRzID0gZnVuY3Rpb24gKG5ld0JvdW5kcykgewogICAgICAgICAgICB2YXIgdG9wTGVmdCA9IHsKICAgICAgICAgICAgICAgIHg6IE1hdGgubWluKG5ld0JvdW5kcy50b3BMZWZ0LngsIG5ld0JvdW5kcy5ib3R0b21SaWdodC54KSwKICAgICAgICAgICAgICAgIHk6IE1hdGgubWluKG5ld0JvdW5kcy50b3BMZWZ0LnksIG5ld0JvdW5kcy5ib3R0b21SaWdodC55KSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIGJvdHRvbVJpZ2h0ID0gewogICAgICAgICAgICAgICAgeDogTWF0aC5tYXgobmV3Qm91bmRzLnRvcExlZnQueCwgbmV3Qm91bmRzLmJvdHRvbVJpZ2h0LngpLAogICAgICAgICAgICAgICAgeTogTWF0aC5tYXgobmV3Qm91bmRzLnRvcExlZnQueSwgbmV3Qm91bmRzLmJvdHRvbVJpZ2h0LnkpLAogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLl9ib3hCb3VuZHMgPSB7CiAgICAgICAgICAgICAgICB0b3BMZWZ0OiB0b3BMZWZ0LAogICAgICAgICAgICAgICAgYm90dG9tUmlnaHQ6IGJvdHRvbVJpZ2h0LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgU2VsZWN0aW9uQm94TGF5ZXIucHJvdG90eXBlLl9nZXRCb3VuZHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICB0b3BMZWZ0OiB7CiAgICAgICAgICAgICAgICAgICAgeDogdGhpcy5feEJvdW5kc01vZGUgPT09IFByb3BlcnR5TW9kZS5QSVhFTCA/CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2JveEJvdW5kcy50b3BMZWZ0LnggOgogICAgICAgICAgICAgICAgICAgICAgICAodGhpcy5feFNjYWxlID09IG51bGwgPwogICAgICAgICAgICAgICAgICAgICAgICAgICAgMCA6CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBNYXRoLm1pbih0aGlzLnhTY2FsZSgpLnNjYWxlKHRoaXMueEV4dGVudCgpWzBdKSwgdGhpcy54U2NhbGUoKS5zY2FsZSh0aGlzLnhFeHRlbnQoKVsxXSkpKSwKICAgICAgICAgICAgICAgICAgICB5OiB0aGlzLl95Qm91bmRzTW9kZSA9PT0gUHJvcGVydHlNb2RlLlBJWEVMID8KICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fYm94Qm91bmRzLnRvcExlZnQueSA6CiAgICAgICAgICAgICAgICAgICAgICAgICh0aGlzLl95U2NhbGUgPT0gbnVsbCA/CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAwIDoKICAgICAgICAgICAgICAgICAgICAgICAgICAgIE1hdGgubWluKHRoaXMueVNjYWxlKCkuc2NhbGUodGhpcy55RXh0ZW50KClbMF0pLCB0aGlzLnlTY2FsZSgpLnNjYWxlKHRoaXMueUV4dGVudCgpWzFdKSkpLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiB7CiAgICAgICAgICAgICAgICAgICAgeDogdGhpcy5feEJvdW5kc01vZGUgPT09IFByb3BlcnR5TW9kZS5QSVhFTCA/CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2JveEJvdW5kcy5ib3R0b21SaWdodC54IDoKICAgICAgICAgICAgICAgICAgICAgICAgKHRoaXMuX3hTY2FsZSA9PSBudWxsID8KICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgTWF0aC5tYXgodGhpcy54U2NhbGUoKS5zY2FsZSh0aGlzLnhFeHRlbnQoKVswXSksIHRoaXMueFNjYWxlKCkuc2NhbGUodGhpcy54RXh0ZW50KClbMV0pKSksCiAgICAgICAgICAgICAgICAgICAgeTogdGhpcy5feUJvdW5kc01vZGUgPT09IFByb3BlcnR5TW9kZS5QSVhFTCA/CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2JveEJvdW5kcy5ib3R0b21SaWdodC55IDoKICAgICAgICAgICAgICAgICAgICAgICAgKHRoaXMuX3lTY2FsZSA9PSBudWxsID8KICAgICAgICAgICAgICAgICAgICAgICAgICAgIDAgOgogICAgICAgICAgICAgICAgICAgICAgICAgICAgTWF0aC5tYXgodGhpcy55U2NhbGUoKS5zY2FsZSh0aGlzLnlFeHRlbnQoKVswXSksIHRoaXMueVNjYWxlKCkuc2NhbGUodGhpcy55RXh0ZW50KClbMV0pKSksCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgU2VsZWN0aW9uQm94TGF5ZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLl9ib3hWaXNpYmxlKSB7CiAgICAgICAgICAgICAgICB2YXIgYm91bmRzID0gdGhpcy5ib3VuZHMoKTsKICAgICAgICAgICAgICAgIHZhciB0ID0gYm91bmRzLnRvcExlZnQueTsKICAgICAgICAgICAgICAgIHZhciBiID0gYm91bmRzLmJvdHRvbVJpZ2h0Lnk7CiAgICAgICAgICAgICAgICB2YXIgbCA9IGJvdW5kcy50b3BMZWZ0Lng7CiAgICAgICAgICAgICAgICB2YXIgciA9IGJvdW5kcy5ib3R0b21SaWdodC54OwogICAgICAgICAgICAgICAgaWYgKCEodXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIodCkgJiYKICAgICAgICAgICAgICAgICAgICB1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihiKSAmJgogICAgICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKGwpICYmCiAgICAgICAgICAgICAgICAgICAgdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIocikpKSB7CiAgICAgICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJib3VuZHMgaGF2ZSBub3QgYmVlbiBwcm9wZXJseSBzZXQiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2JveEFyZWEuYXR0cnMoewogICAgICAgICAgICAgICAgICAgIHg6IGwsIHk6IHQsIHdpZHRoOiByIC0gbCwgaGVpZ2h0OiBiIC0gdCwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5jb250ZW50KCkubm9kZSgpLmFwcGVuZENoaWxkKHRoaXMuX2JveC5ub2RlKCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fYm94LnJlbW92ZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU2VsZWN0aW9uQm94TGF5ZXIucHJvdG90eXBlLmJveFZpc2libGUgPSBmdW5jdGlvbiAoc2hvdykgewogICAgICAgICAgICBpZiAoc2hvdyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYm94VmlzaWJsZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9ib3hWaXNpYmxlID0gc2hvdzsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuZml4ZWRXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgU2VsZWN0aW9uQm94TGF5ZXIucHJvdG90eXBlLnhTY2FsZSA9IGZ1bmN0aW9uICh4U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHhTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5feFNjYWxlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl94U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5feFNjYWxlLm9mZlVwZGF0ZSh0aGlzLl9hZGp1c3RCb3VuZHNDYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5feFNjYWxlID0geFNjYWxlOwogICAgICAgICAgICB0aGlzLl94Qm91bmRzTW9kZSA9IFByb3BlcnR5TW9kZS5WQUxVRTsKICAgICAgICAgICAgdGhpcy5feFNjYWxlLm9uVXBkYXRlKHRoaXMuX2FkanVzdEJvdW5kc0NhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUueVNjYWxlID0gZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICBpZiAoeVNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl95U2NhbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX3lTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl95U2NhbGUub2ZmVXBkYXRlKHRoaXMuX2FkanVzdEJvdW5kc0NhbGxiYWNrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl95U2NhbGUgPSB5U2NhbGU7CiAgICAgICAgICAgIHRoaXMuX3lCb3VuZHNNb2RlID0gUHJvcGVydHlNb2RlLlZBTFVFOwogICAgICAgICAgICB0aGlzLl95U2NhbGUub25VcGRhdGUodGhpcy5fYWRqdXN0Qm91bmRzQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS54RXh0ZW50ID0gZnVuY3Rpb24gKHhFeHRlbnQpIHsKICAgICAgICAgICAgLy8gRXhwbGljaXQgdHlwaW5nIGZvciBUeXBlc2NyaXB0IDEuNAogICAgICAgICAgICBpZiAoeEV4dGVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZ2V0WEV4dGVudCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NldFhFeHRlbnQoeEV4dGVudCk7CiAgICAgICAgICAgIHRoaXMuX3hCb3VuZHNNb2RlID0gUHJvcGVydHlNb2RlLlZBTFVFOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS5fZ2V0WEV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3hCb3VuZHNNb2RlID09PSBQcm9wZXJ0eU1vZGUuVkFMVUUgPwogICAgICAgICAgICAgICAgdGhpcy5feEV4dGVudCA6CiAgICAgICAgICAgICAgICAodGhpcy5feFNjYWxlID09IG51bGwgPwogICAgICAgICAgICAgICAgICAgIFt1bmRlZmluZWQsIHVuZGVmaW5lZF0gOgogICAgICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5feFNjYWxlLmludmVydCh0aGlzLl9ib3hCb3VuZHMudG9wTGVmdC54KSwKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5feFNjYWxlLmludmVydCh0aGlzLl9ib3hCb3VuZHMuYm90dG9tUmlnaHQueCksCiAgICAgICAgICAgICAgICAgICAgXSk7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuX3NldFhFeHRlbnQgPSBmdW5jdGlvbiAoeEV4dGVudCkgewogICAgICAgICAgICB0aGlzLl94RXh0ZW50ID0geEV4dGVudDsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS55RXh0ZW50ID0gZnVuY3Rpb24gKHlFeHRlbnQpIHsKICAgICAgICAgICAgLy8gRXhwbGljaXQgdHlwaW5nIGZvciBUeXBlc2NyaXB0IDEuNAogICAgICAgICAgICBpZiAoeUV4dGVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZ2V0WUV4dGVudCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NldFlFeHRlbnQoeUV4dGVudCk7CiAgICAgICAgICAgIHRoaXMuX3lCb3VuZHNNb2RlID0gUHJvcGVydHlNb2RlLlZBTFVFOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS5fZ2V0WUV4dGVudCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3lCb3VuZHNNb2RlID09PSBQcm9wZXJ0eU1vZGUuVkFMVUUgPwogICAgICAgICAgICAgICAgdGhpcy5feUV4dGVudCA6CiAgICAgICAgICAgICAgICAodGhpcy5feVNjYWxlID09IG51bGwgPwogICAgICAgICAgICAgICAgICAgIFt1bmRlZmluZWQsIHVuZGVmaW5lZF0gOgogICAgICAgICAgICAgICAgICAgIFsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5feVNjYWxlLmludmVydCh0aGlzLl9ib3hCb3VuZHMudG9wTGVmdC55KSwKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5feVNjYWxlLmludmVydCh0aGlzLl9ib3hCb3VuZHMuYm90dG9tUmlnaHQueSksCiAgICAgICAgICAgICAgICAgICAgXSk7CiAgICAgICAgfTsKICAgICAgICBTZWxlY3Rpb25Cb3hMYXllci5wcm90b3R5cGUuX3NldFlFeHRlbnQgPSBmdW5jdGlvbiAoeUV4dGVudCkgewogICAgICAgICAgICB0aGlzLl95RXh0ZW50ID0geUV4dGVudDsKICAgICAgICB9OwogICAgICAgIFNlbGVjdGlvbkJveExheWVyLnByb3RvdHlwZS5kZXN0cm95ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmRlc3Ryb3kuY2FsbCh0aGlzKTsKICAgICAgICAgICAgaWYgKHRoaXMuX3hTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLnhTY2FsZSgpLm9mZlVwZGF0ZSh0aGlzLl9hZGp1c3RCb3VuZHNDYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX3lTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLnlTY2FsZSgpLm9mZlVwZGF0ZSh0aGlzLl9hZGp1c3RCb3VuZHNDYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBTZWxlY3Rpb25Cb3hMYXllcjsKICAgIH0oY29tcG9uZW50LkNvbXBvbmVudCkpOwogICAgZXhwb3J0cy5TZWxlY3Rpb25Cb3hMYXllciA9IFNlbGVjdGlvbkJveExheWVyOwogICAgfSk7CgogICAgdmFyIGRyYWdCb3hMYXllciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgogICAgdmFyIERyYWdCb3hMYXllciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKERyYWdCb3hMYXllciwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgRHJhZ0JveExheWVyLgogICAgICAgICAqCiAgICAgICAgICogQSBEcmFnQm94TGF5ZXIgaXMgYSBTZWxlY3Rpb25Cb3hMYXllciB3aXRoIGEgYnVpbHQtaW4gRHJhZyBJbnRlcmFjdGlvbi4KICAgICAgICAgKiBBIGRyYWcgZ2VzdHVyZSB3aWxsIHNldCB0aGUgQm91bmRzIG9mIHRoZSBib3guCiAgICAgICAgICogSWYgcmVzaXppbmcgaXMgZW5hYmxlZCB1c2luZyByZXNpemFibGUodHJ1ZSksIHRoZSBlZGdlcyBvZiBib3ggY2FuIGJlIHJlcG9zaXRpb25lZC4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIERyYWdCb3hMYXllcigpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2RldGVjdGlvblJhZGl1cyA9IDM7CiAgICAgICAgICAgIF90aGlzLl9yZXNpemFibGUgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuX21vdmFibGUgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuX2hhc0Nvcm5lcnMgPSB0cnVlOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygiZHJhZy1ib3gtbGF5ZXIiKTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbiA9IG5ldyBpbnRlcmFjdGlvbnMuRHJhZygpOwogICAgICAgICAgICBfdGhpcy5fc2V0VXBDYWxsYmFja3MoKTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5hdHRhY2hUbyhfdGhpcyk7CiAgICAgICAgICAgIF90aGlzLl9kcmFnU3RhcnRDYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICBfdGhpcy5fZHJhZ0NhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9kcmFnRW5kQ2FsbGJhY2tzID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLl9zZXRVcENhbGxiYWNrcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHJlc2l6aW5nRWRnZXM7CiAgICAgICAgICAgIHZhciB0b3BMZWZ0OwogICAgICAgICAgICB2YXIgYm90dG9tUmlnaHQ7CiAgICAgICAgICAgIHZhciBsYXN0RW5kUG9pbnQ7CiAgICAgICAgICAgIHZhciBEUkFHX01PREVTID0gewogICAgICAgICAgICAgICAgbmV3Qm94OiAwLAogICAgICAgICAgICAgICAgcmVzaXplOiAxLAogICAgICAgICAgICAgICAgbW92ZTogMiwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIG1vZGUgPSBEUkFHX01PREVTLm5ld0JveDsKICAgICAgICAgICAgdmFyIG9uRHJhZ1N0YXJ0Q2FsbGJhY2sgPSBmdW5jdGlvbiAoc3RhcnRQb2ludCkgewogICAgICAgICAgICAgICAgcmVzaXppbmdFZGdlcyA9IF90aGlzLl9nZXRSZXNpemluZ0VkZ2VzKHN0YXJ0UG9pbnQpOwogICAgICAgICAgICAgICAgdmFyIGJvdW5kcyA9IF90aGlzLmJvdW5kcygpOwogICAgICAgICAgICAgICAgdmFyIGlzSW5zaWRlQm94ID0gYm91bmRzLnRvcExlZnQueCA8PSBzdGFydFBvaW50LnggJiYgc3RhcnRQb2ludC54IDw9IGJvdW5kcy5ib3R0b21SaWdodC54ICYmCiAgICAgICAgICAgICAgICAgICAgYm91bmRzLnRvcExlZnQueSA8PSBzdGFydFBvaW50LnkgJiYgc3RhcnRQb2ludC55IDw9IGJvdW5kcy5ib3R0b21SaWdodC55OwogICAgICAgICAgICAgICAgaWYgKF90aGlzLmJveFZpc2libGUoKSAmJiAocmVzaXppbmdFZGdlcy50b3AgfHwgcmVzaXppbmdFZGdlcy5ib3R0b20gfHwgcmVzaXppbmdFZGdlcy5sZWZ0IHx8IHJlc2l6aW5nRWRnZXMucmlnaHQpKSB7CiAgICAgICAgICAgICAgICAgICAgbW9kZSA9IERSQUdfTU9ERVMucmVzaXplOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoX3RoaXMuYm94VmlzaWJsZSgpICYmIF90aGlzLm1vdmFibGUoKSAmJiBpc0luc2lkZUJveCkgewogICAgICAgICAgICAgICAgICAgIG1vZGUgPSBEUkFHX01PREVTLm1vdmU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBtb2RlID0gRFJBR19NT0RFUy5uZXdCb3g7CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuX3NldEJvdW5kcyh7CiAgICAgICAgICAgICAgICAgICAgICAgIHRvcExlZnQ6IHN0YXJ0UG9pbnQsCiAgICAgICAgICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiBzdGFydFBvaW50LAogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIGlmIChfdGhpcy5feEJvdW5kc01vZGUgPT09IGNvbXBvbmVudHMuUHJvcGVydHlNb2RlLlZBTFVFICYmIF90aGlzLnhTY2FsZSgpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgX3RoaXMuX3NldFhFeHRlbnQoW190aGlzLnhTY2FsZSgpLmludmVydChzdGFydFBvaW50LngpLCBfdGhpcy54U2NhbGUoKS5pbnZlcnQoc3RhcnRQb2ludC54KV0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpZiAoX3RoaXMuX3lCb3VuZHNNb2RlID09PSBjb21wb25lbnRzLlByb3BlcnR5TW9kZS5WQUxVRSAmJiBfdGhpcy55U2NhbGUoKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIF90aGlzLl9zZXRZRXh0ZW50KFtfdGhpcy55U2NhbGUoKS5pbnZlcnQoc3RhcnRQb2ludC55KSwgX3RoaXMueVNjYWxlKCkuaW52ZXJ0KHN0YXJ0UG9pbnQueSldKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgX3RoaXMucmVuZGVyKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBfdGhpcy5ib3hWaXNpYmxlKHRydWUpOwogICAgICAgICAgICAgICAgYm91bmRzID0gX3RoaXMuYm91bmRzKCk7CiAgICAgICAgICAgICAgICAvLyBjb3B5IHBvaW50cyBzbyBjaGFuZ2VzIHRvIHRvcExlZnQgYW5kIGJvdHRvbVJpZ2h0IGRvbid0IG11dGF0ZSBib3VuZHMKICAgICAgICAgICAgICAgIHRvcExlZnQgPSB7IHg6IGJvdW5kcy50b3BMZWZ0LngsIHk6IGJvdW5kcy50b3BMZWZ0LnkgfTsKICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0ID0geyB4OiBib3VuZHMuYm90dG9tUmlnaHQueCwgeTogYm91bmRzLmJvdHRvbVJpZ2h0LnkgfTsKICAgICAgICAgICAgICAgIGxhc3RFbmRQb2ludCA9IHN0YXJ0UG9pbnQ7CiAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmNhbGxDYWxsYmFja3MoYm91bmRzKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIG9uRHJhZ0NhbGxiYWNrID0gZnVuY3Rpb24gKHN0YXJ0UG9pbnQsIGVuZFBvaW50KSB7CiAgICAgICAgICAgICAgICBzd2l0Y2ggKG1vZGUpIHsKICAgICAgICAgICAgICAgICAgICBjYXNlIERSQUdfTU9ERVMubmV3Qm94OgogICAgICAgICAgICAgICAgICAgICAgICBib3R0b21SaWdodC54ID0gZW5kUG9pbnQueDsKICAgICAgICAgICAgICAgICAgICAgICAgYm90dG9tUmlnaHQueSA9IGVuZFBvaW50Lnk7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGNhc2UgRFJBR19NT0RFUy5yZXNpemU6CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChyZXNpemluZ0VkZ2VzLmJvdHRvbSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgYm90dG9tUmlnaHQueSA9IGVuZFBvaW50Lnk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSBpZiAocmVzaXppbmdFZGdlcy50b3ApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRvcExlZnQueSA9IGVuZFBvaW50Lnk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHJlc2l6aW5nRWRnZXMucmlnaHQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0LnggPSBlbmRQb2ludC54OwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgaWYgKHJlc2l6aW5nRWRnZXMubGVmdCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgdG9wTGVmdC54ID0gZW5kUG9pbnQueDsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICBjYXNlIERSQUdfTU9ERVMubW92ZToKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIGR4ID0gZW5kUG9pbnQueCAtIGxhc3RFbmRQb2ludC54OwogICAgICAgICAgICAgICAgICAgICAgICB2YXIgZHkgPSBlbmRQb2ludC55IC0gbGFzdEVuZFBvaW50Lnk7CiAgICAgICAgICAgICAgICAgICAgICAgIHRvcExlZnQueCArPSBkeDsKICAgICAgICAgICAgICAgICAgICAgICAgdG9wTGVmdC55ICs9IGR5OwogICAgICAgICAgICAgICAgICAgICAgICBib3R0b21SaWdodC54ICs9IGR4OwogICAgICAgICAgICAgICAgICAgICAgICBib3R0b21SaWdodC55ICs9IGR5OwogICAgICAgICAgICAgICAgICAgICAgICBsYXN0RW5kUG9pbnQgPSBlbmRQb2ludDsKICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBfdGhpcy5fc2V0Qm91bmRzKHsKICAgICAgICAgICAgICAgICAgICB0b3BMZWZ0OiB0b3BMZWZ0LAogICAgICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiBib3R0b21SaWdodCwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgaWYgKF90aGlzLl94Qm91bmRzTW9kZSA9PT0gY29tcG9uZW50cy5Qcm9wZXJ0eU1vZGUuVkFMVUUgJiYgX3RoaXMueFNjYWxlKCkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIF90aGlzLl9zZXRYRXh0ZW50KFtfdGhpcy54U2NhbGUoKS5pbnZlcnQodG9wTGVmdC54KSwgX3RoaXMueFNjYWxlKCkuaW52ZXJ0KGJvdHRvbVJpZ2h0LngpXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoX3RoaXMuX3lCb3VuZHNNb2RlID09PSBjb21wb25lbnRzLlByb3BlcnR5TW9kZS5WQUxVRSAmJiBfdGhpcy55U2NhbGUoKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuX3NldFlFeHRlbnQoW190aGlzLnlTY2FsZSgpLmludmVydCh0b3BMZWZ0LnkpLCBfdGhpcy55U2NhbGUoKS5pbnZlcnQoYm90dG9tUmlnaHQueSldKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIF90aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgX3RoaXMuX2RyYWdDYWxsYmFja3MuY2FsbENhbGxiYWNrcyhfdGhpcy5ib3VuZHMoKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBvbkRyYWdFbmRDYWxsYmFjayA9IGZ1bmN0aW9uIChzdGFydFBvaW50LCBlbmRQb2ludCkgewogICAgICAgICAgICAgICAgaWYgKG1vZGUgPT09IERSQUdfTU9ERVMubmV3Qm94ICYmIHN0YXJ0UG9pbnQueCA9PT0gZW5kUG9pbnQueCAmJiBzdGFydFBvaW50LnkgPT09IGVuZFBvaW50LnkpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5ib3hWaXNpYmxlKGZhbHNlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIF90aGlzLl9kcmFnRW5kQ2FsbGJhY2tzLmNhbGxDYWxsYmFja3MoX3RoaXMuYm91bmRzKCkpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24ub25EcmFnU3RhcnQob25EcmFnU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdJbnRlcmFjdGlvbi5vbkRyYWcob25EcmFnQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24ub25EcmFnRW5kKG9uRHJhZ0VuZENhbGxiYWNrKTsKICAgICAgICAgICAgdGhpcy5fZGlzY29ubmVjdEludGVyYWN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vZmZEcmFnU3RhcnQob25EcmFnU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9mZkRyYWcob25EcmFnQ2FsbGJhY2spOwogICAgICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vZmZEcmFnRW5kKG9uRHJhZ0VuZENhbGxiYWNrKTsKICAgICAgICAgICAgICAgIF90aGlzLl9kcmFnSW50ZXJhY3Rpb24uZGV0YWNoKCk7CiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLl9zZXR1cCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fc2V0dXAuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdmFyIGNyZWF0ZUxpbmUgPSBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fYm94LmFwcGVuZCgibGluZSIpLnN0eWxlcyh7CiAgICAgICAgICAgICAgICBvcGFjaXR5OiAwLAogICAgICAgICAgICAgICAgc3Ryb2tlOiAicGluayIsCiAgICAgICAgICAgICAgICAicG9pbnRlci1ldmVudHMiOiAidmlzaWJsZVN0cm9rZSIsCiAgICAgICAgICAgIH0pOyB9OwogICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25FZGdlVCA9IGNyZWF0ZUxpbmUoKS5jbGFzc2VkKCJkcmFnLWVkZ2UtdGIiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5fZGV0ZWN0aW9uRWRnZUIgPSBjcmVhdGVMaW5lKCkuY2xhc3NlZCgiZHJhZy1lZGdlLXRiIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkVkZ2VMID0gY3JlYXRlTGluZSgpLmNsYXNzZWQoImRyYWctZWRnZS1sciIsIHRydWUpOwogICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25FZGdlUiA9IGNyZWF0ZUxpbmUoKS5jbGFzc2VkKCJkcmFnLWVkZ2UtbHIiLCB0cnVlKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2hhc0Nvcm5lcnMpIHsKICAgICAgICAgICAgICAgIHZhciBjcmVhdGVDb3JuZXIgPSBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fYm94LmFwcGVuZCgiY2lyY2xlIikKICAgICAgICAgICAgICAgICAgICAuc3R5bGVzKHsKICAgICAgICAgICAgICAgICAgICBvcGFjaXR5OiAwLAogICAgICAgICAgICAgICAgICAgIGZpbGw6ICJwaW5rIiwKICAgICAgICAgICAgICAgICAgICAicG9pbnRlci1ldmVudHMiOiAidmlzaWJsZUZpbGwiLAogICAgICAgICAgICAgICAgfSk7IH07CiAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJUTCA9IGNyZWF0ZUNvcm5lcigpLmNsYXNzZWQoImRyYWctY29ybmVyLXRsIiwgdHJ1ZSk7CiAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJUUiA9IGNyZWF0ZUNvcm5lcigpLmNsYXNzZWQoImRyYWctY29ybmVyLXRyIiwgdHJ1ZSk7CiAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJCTCA9IGNyZWF0ZUNvcm5lcigpLmNsYXNzZWQoImRyYWctY29ybmVyLWJsIiwgdHJ1ZSk7CiAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJCUiA9IGNyZWF0ZUNvcm5lcigpLmNsYXNzZWQoImRyYWctY29ybmVyLWJyIiwgdHJ1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIERyYWdCb3hMYXllci5wcm90b3R5cGUuX2dldFJlc2l6aW5nRWRnZXMgPSBmdW5jdGlvbiAocCkgewogICAgICAgICAgICB2YXIgZWRnZXMgPSB7CiAgICAgICAgICAgICAgICB0b3A6IGZhbHNlLAogICAgICAgICAgICAgICAgYm90dG9tOiBmYWxzZSwKICAgICAgICAgICAgICAgIGxlZnQ6IGZhbHNlLAogICAgICAgICAgICAgICAgcmlnaHQ6IGZhbHNlLAogICAgICAgICAgICB9OwogICAgICAgICAgICBpZiAoIXRoaXMucmVzaXphYmxlKCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBlZGdlczsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgYm91bmRzID0gdGhpcy5ib3VuZHMoKTsKICAgICAgICAgICAgdmFyIHQgPSBib3VuZHMudG9wTGVmdC55OwogICAgICAgICAgICB2YXIgYiA9IGJvdW5kcy5ib3R0b21SaWdodC55OwogICAgICAgICAgICB2YXIgbCA9IGJvdW5kcy50b3BMZWZ0Lng7CiAgICAgICAgICAgIHZhciByID0gYm91bmRzLmJvdHRvbVJpZ2h0Lng7CiAgICAgICAgICAgIHZhciByYWQgPSB0aGlzLl9kZXRlY3Rpb25SYWRpdXM7CiAgICAgICAgICAgIGlmIChsIC0gcmFkIDw9IHAueCAmJiBwLnggPD0gciArIHJhZCkgewogICAgICAgICAgICAgICAgZWRnZXMudG9wID0gKHQgLSByYWQgPD0gcC55ICYmIHAueSA8PSB0ICsgcmFkKTsKICAgICAgICAgICAgICAgIGVkZ2VzLmJvdHRvbSA9IChiIC0gcmFkIDw9IHAueSAmJiBwLnkgPD0gYiArIHJhZCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHQgLSByYWQgPD0gcC55ICYmIHAueSA8PSBiICsgcmFkKSB7CiAgICAgICAgICAgICAgICBlZGdlcy5sZWZ0ID0gKGwgLSByYWQgPD0gcC54ICYmIHAueCA8PSBsICsgcmFkKTsKICAgICAgICAgICAgICAgIGVkZ2VzLnJpZ2h0ID0gKHIgLSByYWQgPD0gcC54ICYmIHAueCA8PSByICsgcmFkKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZWRnZXM7CiAgICAgICAgfTsKICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLmJveFZpc2libGUoKSkgewogICAgICAgICAgICAgICAgdmFyIGJvdW5kcyA9IHRoaXMuYm91bmRzKCk7CiAgICAgICAgICAgICAgICB2YXIgdCA9IGJvdW5kcy50b3BMZWZ0Lnk7CiAgICAgICAgICAgICAgICB2YXIgYiA9IGJvdW5kcy5ib3R0b21SaWdodC55OwogICAgICAgICAgICAgICAgdmFyIGwgPSBib3VuZHMudG9wTGVmdC54OwogICAgICAgICAgICAgICAgdmFyIHIgPSBib3VuZHMuYm90dG9tUmlnaHQueDsKICAgICAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkVkZ2VULmF0dHJzKHsKICAgICAgICAgICAgICAgICAgICB4MTogbCwgeTE6IHQsIHgyOiByLCB5MjogdCwKICAgICAgICAgICAgICAgICAgICAic3Ryb2tlLXdpZHRoIjogdGhpcy5fZGV0ZWN0aW9uUmFkaXVzICogMiwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fZGV0ZWN0aW9uRWRnZUIuYXR0cnMoewogICAgICAgICAgICAgICAgICAgIHgxOiBsLCB5MTogYiwgeDI6IHIsIHkyOiBiLAogICAgICAgICAgICAgICAgICAgICJzdHJva2Utd2lkdGgiOiB0aGlzLl9kZXRlY3Rpb25SYWRpdXMgKiAyLAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25FZGdlTC5hdHRycyh7CiAgICAgICAgICAgICAgICAgICAgeDE6IGwsIHkxOiB0LCB4MjogbCwgeTI6IGIsCiAgICAgICAgICAgICAgICAgICAgInN0cm9rZS13aWR0aCI6IHRoaXMuX2RldGVjdGlvblJhZGl1cyAqIDIsCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkVkZ2VSLmF0dHJzKHsKICAgICAgICAgICAgICAgICAgICB4MTogciwgeTE6IHQsIHgyOiByLCB5MjogYiwKICAgICAgICAgICAgICAgICAgICAic3Ryb2tlLXdpZHRoIjogdGhpcy5fZGV0ZWN0aW9uUmFkaXVzICogMiwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2hhc0Nvcm5lcnMpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJUTC5hdHRycyh7IGN4OiBsLCBjeTogdCwgcjogdGhpcy5fZGV0ZWN0aW9uUmFkaXVzIH0pOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkNvcm5lclRSLmF0dHJzKHsgY3g6IHIsIGN5OiB0LCByOiB0aGlzLl9kZXRlY3Rpb25SYWRpdXMgfSk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fZGV0ZWN0aW9uQ29ybmVyQkwuYXR0cnMoeyBjeDogbCwgY3k6IGIsIHI6IHRoaXMuX2RldGVjdGlvblJhZGl1cyB9KTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25Db3JuZXJCUi5hdHRycyh7IGN4OiByLCBjeTogYiwgcjogdGhpcy5fZGV0ZWN0aW9uUmFkaXVzIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5kZXRlY3Rpb25SYWRpdXMgPSBmdW5jdGlvbiAocikgewogICAgICAgICAgICBpZiAociA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZGV0ZWN0aW9uUmFkaXVzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChyIDwgMCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJkZXRlY3Rpb24gcmFkaXVzIGNhbm5vdCBiZSBuZWdhdGl2ZS4iKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9kZXRlY3Rpb25SYWRpdXMgPSByOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIERyYWdCb3hMYXllci5wcm90b3R5cGUucmVzaXphYmxlID0gZnVuY3Rpb24gKGNhblJlc2l6ZSkgewogICAgICAgICAgICBpZiAoY2FuUmVzaXplID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9yZXNpemFibGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fcmVzaXphYmxlID0gY2FuUmVzaXplOwogICAgICAgICAgICB0aGlzLl9zZXRSZXNpemFibGVDbGFzc2VzKGNhblJlc2l6ZSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLy8gU2V0cyByZXNpemFibGUgY2xhc3Nlcy4gT3ZlcnJpZGRlbiBieSBzdWJjbGFzc2VzIHRoYXQgb25seSByZXNpemUgaW4gb25lIGRpbWVuc2lvbi4KICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLl9zZXRSZXNpemFibGVDbGFzc2VzID0gZnVuY3Rpb24gKGNhblJlc2l6ZSkgewogICAgICAgICAgICBpZiAoY2FuUmVzaXplICYmIHRoaXMuZW5hYmxlZCgpKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFkZENsYXNzKCJ4LXJlc2l6YWJsZSIpOwogICAgICAgICAgICAgICAgdGhpcy5hZGRDbGFzcygieS1yZXNpemFibGUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMucmVtb3ZlQ2xhc3MoIngtcmVzaXphYmxlIik7CiAgICAgICAgICAgICAgICB0aGlzLnJlbW92ZUNsYXNzKCJ5LXJlc2l6YWJsZSIpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLm1vdmFibGUgPSBmdW5jdGlvbiAobW92YWJsZSkgewogICAgICAgICAgICBpZiAobW92YWJsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbW92YWJsZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9tb3ZhYmxlID0gbW92YWJsZTsKICAgICAgICAgICAgdGhpcy5fc2V0TW92YWJsZUNsYXNzKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5fc2V0TW92YWJsZUNsYXNzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5tb3ZhYmxlKCkgJiYgdGhpcy5lbmFibGVkKCkpIHsKICAgICAgICAgICAgICAgIHRoaXMuYWRkQ2xhc3MoIm1vdmFibGUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMucmVtb3ZlQ2xhc3MoIm1vdmFibGUiKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyB0aGUgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgc3RhcnRzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnQm94Q2FsbGJhY2t9IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWdCb3hMYXllcn0gVGhlIGNhbGxpbmcgRHJhZ0JveExheWVyLgogICAgICAgICAqLwogICAgICAgIERyYWdCb3hMYXllci5wcm90b3R5cGUub25EcmFnU3RhcnQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGRyYWdnaW5nIHN0YXJ0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RHJhZ0JveENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnQm94TGF5ZXJ9IFRoZSBjYWxsaW5nIERyYWdCb3hMYXllci4KICAgICAgICAgKi8KICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLm9mZkRyYWdTdGFydCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9kcmFnU3RhcnRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIGR1cmluZyBkcmFnZ2luZy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RHJhZ0JveENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnQm94TGF5ZXJ9IFRoZSBjYWxsaW5nIERyYWdCb3hMYXllci4KICAgICAgICAgKi8KICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLm9uRHJhZyA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9kcmFnQ2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCBkdXJpbmcgZHJhZ2dpbmcuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RyYWdCb3hDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ0JveExheWVyfSBUaGUgY2FsbGluZyBEcmFnQm94TGF5ZXIuCiAgICAgICAgICovCiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5vZmZEcmFnID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIGEgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgZW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RHJhZ0JveENhbGxiYWNrfSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnQm94TGF5ZXJ9IFRoZSBjYWxsaW5nIERyYWdCb3hMYXllci4KICAgICAgICAgKi8KICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLm9uRHJhZ0VuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9kcmFnRW5kQ2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCB3aGVuIGRyYWdnaW5nIGVuZHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RyYWdCb3hDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ0JveExheWVyfSBUaGUgY2FsbGluZyBEcmFnQm94TGF5ZXIuCiAgICAgICAgICovCiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5vZmZEcmFnRW5kID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdFbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBpbnRlcm5hbCBJbnRlcmFjdGlvbnMuRHJhZyBvZiB0aGUgRHJhZ0JveExheWVyLgogICAgICAgICAqLwogICAgICAgIERyYWdCb3hMYXllci5wcm90b3R5cGUuZHJhZ0ludGVyYWN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZHJhZ0ludGVyYWN0aW9uOwogICAgICAgIH07CiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5lbmFibGVkID0gZnVuY3Rpb24gKGVuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKGVuYWJsZWQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2RyYWdJbnRlcmFjdGlvbi5lbmFibGVkKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmVuYWJsZWQoZW5hYmxlZCk7CiAgICAgICAgICAgIHRoaXMuX3NldFJlc2l6YWJsZUNsYXNzZXModGhpcy5yZXNpemFibGUoKSk7CiAgICAgICAgICAgIHRoaXMuX3NldE1vdmFibGVDbGFzcygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIERyYWdCb3hMYXllci5wcm90b3R5cGUuZGVzdHJveSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5kZXN0cm95LmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdTdGFydENhbGxiYWNrcy5mb3JFYWNoKGZ1bmN0aW9uIChjYWxsYmFjaykgeyByZXR1cm4gX3RoaXMuX2RyYWdDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsgfSk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdDYWxsYmFja3MuZm9yRWFjaChmdW5jdGlvbiAoY2FsbGJhY2spIHsgcmV0dXJuIF90aGlzLl9kcmFnQ2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7IH0pOwogICAgICAgICAgICB0aGlzLl9kcmFnRW5kQ2FsbGJhY2tzLmZvckVhY2goZnVuY3Rpb24gKGNhbGxiYWNrKSB7IHJldHVybiBfdGhpcy5fZHJhZ0VuZENhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOyB9KTsKICAgICAgICAgICAgdGhpcy5fZGlzY29ubmVjdEludGVyYWN0aW9uKCk7CiAgICAgICAgfTsKICAgICAgICBEcmFnQm94TGF5ZXIucHJvdG90eXBlLmRldGFjaCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fcmVzZXRTdGF0ZSgpOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24uZGV0YWNoKCk7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGV0YWNoLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5hbmNob3IgPSBmdW5jdGlvbiAoc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbiA9IGNvZXJjZUQzLmNvZXJjZUV4dGVybmFsRDMoc2VsZWN0aW9uKTsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmF0dGFjaFRvKHRoaXMpOwogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmFuY2hvci5jYWxsKHRoaXMsIHNlbGVjdGlvbik7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgRHJhZ0JveExheWVyLnByb3RvdHlwZS5fcmVzZXRTdGF0ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5ib3VuZHMoewogICAgICAgICAgICAgICAgdG9wTGVmdDogeyB4OiAwLCB5OiAwIH0sCiAgICAgICAgICAgICAgICBib3R0b21SaWdodDogeyB4OiAwLCB5OiAwIH0sCiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIERyYWdCb3hMYXllcjsKICAgIH0oc2VsZWN0aW9uQm94TGF5ZXIuU2VsZWN0aW9uQm94TGF5ZXIpKTsKICAgIGV4cG9ydHMuRHJhZ0JveExheWVyID0gRHJhZ0JveExheWVyOwogICAgfSk7CgogICAgdmFyIGd1aWRlTGluZUxheWVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICB2YXIgUHJvcGVydHlNb2RlOwogICAgKGZ1bmN0aW9uIChQcm9wZXJ0eU1vZGUpIHsKICAgICAgICBQcm9wZXJ0eU1vZGVbUHJvcGVydHlNb2RlWyJWQUxVRSJdID0gMF0gPSAiVkFMVUUiOwogICAgICAgIFByb3BlcnR5TW9kZVtQcm9wZXJ0eU1vZGVbIlBJWEVMIl0gPSAxXSA9ICJQSVhFTCI7CiAgICB9KShQcm9wZXJ0eU1vZGUgfHwgKFByb3BlcnR5TW9kZSA9IHt9KSk7CiAgICB2YXIgR3VpZGVMaW5lTGF5ZXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhHdWlkZUxpbmVMYXllciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBHdWlkZUxpbmVMYXllcihvcmllbnRhdGlvbikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbW9kZSA9IFByb3BlcnR5TW9kZS5WQUxVRTsKICAgICAgICAgICAgaWYgKG9yaWVudGF0aW9uICE9PSBHdWlkZUxpbmVMYXllci5PUklFTlRBVElPTl9WRVJUSUNBTCAmJiBvcmllbnRhdGlvbiAhPT0gR3VpZGVMaW5lTGF5ZXIuT1JJRU5UQVRJT05fSE9SSVpPTlRBTCkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKG9yaWVudGF0aW9uICsgIiBpcyBub3QgYSB2YWxpZCBvcmllbnRhdGlvbiBmb3IgR3VpZGVMaW5lTGF5ZXIiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBfdGhpcy5fb3JpZW50YXRpb24gPSBvcmllbnRhdGlvbjsKICAgICAgICAgICAgX3RoaXMuX292ZXJmbG93SGlkZGVuID0gdHJ1ZTsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoImd1aWRlLWxpbmUtbGF5ZXIiKTsKICAgICAgICAgICAgaWYgKF90aGlzLl9pc1ZlcnRpY2FsKCkpIHsKICAgICAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJ2ZXJ0aWNhbCIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoImhvcml6b250YWwiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBfdGhpcy5fc2NhbGVVcGRhdGVDYWxsYmFjayA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIF90aGlzLl9zeW5jUGl4ZWxQb3NpdGlvbkFuZFZhbHVlKCk7CiAgICAgICAgICAgICAgICBfdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuX3NldHVwID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9ndWlkZUxpbmUgPSB0aGlzLmNvbnRlbnQoKS5hcHBlbmQoImxpbmUiKS5jbGFzc2VkKCJndWlkZS1saW5lIiwgdHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuX3NpemVGcm9tT2ZmZXIgPSBmdW5jdGlvbiAoYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgd2lkdGg6IGF2YWlsYWJsZVdpZHRoLAogICAgICAgICAgICAgICAgaGVpZ2h0OiBhdmFpbGFibGVIZWlnaHQsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuX2lzVmVydGljYWwgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9vcmllbnRhdGlvbiA9PT0gR3VpZGVMaW5lTGF5ZXIuT1JJRU5UQVRJT05fVkVSVElDQUw7CiAgICAgICAgfTsKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuZml4ZWRXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfTsKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgR3VpZGVMaW5lTGF5ZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQgPSBmdW5jdGlvbiAob3JpZ2luLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuY29tcHV0ZUxheW91dC5jYWxsKHRoaXMsIG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCk7CiAgICAgICAgICAgIGlmICh0aGlzLnNjYWxlKCkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2lzVmVydGljYWwoKSkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuc2NhbGUoKS5yYW5nZShbMCwgdGhpcy53aWR0aCgpXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnNjYWxlKCkucmFuZ2UoW3RoaXMuaGVpZ2h0KCksIDBdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEd1aWRlTGluZUxheWVyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9zeW5jUGl4ZWxQb3NpdGlvbkFuZFZhbHVlKCk7CiAgICAgICAgICAgIHRoaXMuX2d1aWRlTGluZS5hdHRycyh7CiAgICAgICAgICAgICAgICB4MTogdGhpcy5faXNWZXJ0aWNhbCgpID8gdGhpcy5waXhlbFBvc2l0aW9uKCkgOiAwLAogICAgICAgICAgICAgICAgeTE6IHRoaXMuX2lzVmVydGljYWwoKSA/IDAgOiB0aGlzLnBpeGVsUG9zaXRpb24oKSwKICAgICAgICAgICAgICAgIHgyOiB0aGlzLl9pc1ZlcnRpY2FsKCkgPyB0aGlzLnBpeGVsUG9zaXRpb24oKSA6IHRoaXMud2lkdGgoKSwKICAgICAgICAgICAgICAgIHkyOiB0aGlzLl9pc1ZlcnRpY2FsKCkgPyB0aGlzLmhlaWdodCgpIDogdGhpcy5waXhlbFBvc2l0aW9uKCksCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8vIHNldHMgcGl4ZWxQb3NpdGlvbigpIG9yIHZhbHVlKCkgYmFzZWQgb24gdGhlIG90aGVyLCBkZXBlbmRpbmcgb24gd2hpY2ggd2FzIHRoZSBsYXN0IG9uZSBzZXQKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuX3N5bmNQaXhlbFBvc2l0aW9uQW5kVmFsdWUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnNjYWxlKCkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl9tb2RlID09PSBQcm9wZXJ0eU1vZGUuVkFMVUUgJiYgdGhpcy52YWx1ZSgpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3BpeGVsUG9zaXRpb24gPSB0aGlzLnNjYWxlKCkuc2NhbGUodGhpcy52YWx1ZSgpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0aGlzLl9tb2RlID09PSBQcm9wZXJ0eU1vZGUuUElYRUwgJiYgdGhpcy5waXhlbFBvc2l0aW9uKCkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fdmFsdWUgPSB0aGlzLnNjYWxlKCkuaW52ZXJ0KHRoaXMucGl4ZWxQb3NpdGlvbigpKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgR3VpZGVMaW5lTGF5ZXIucHJvdG90eXBlLl9zZXRQaXhlbFBvc2l0aW9uV2l0aG91dENoYW5naW5nTW9kZSA9IGZ1bmN0aW9uIChwaXhlbFBvc2l0aW9uKSB7CiAgICAgICAgICAgIHRoaXMuX3BpeGVsUG9zaXRpb24gPSBwaXhlbFBvc2l0aW9uOwogICAgICAgICAgICBpZiAodGhpcy5zY2FsZSgpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3ZhbHVlID0gdGhpcy5zY2FsZSgpLmludmVydCh0aGlzLnBpeGVsUG9zaXRpb24oKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICB9OwogICAgICAgIEd1aWRlTGluZUxheWVyLnByb3RvdHlwZS5zY2FsZSA9IGZ1bmN0aW9uIChzY2FsZSkgewogICAgICAgICAgICBpZiAoc2NhbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NjYWxlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBwcmV2aW91c1NjYWxlID0gdGhpcy5fc2NhbGU7CiAgICAgICAgICAgIGlmIChwcmV2aW91c1NjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHByZXZpb3VzU2NhbGUub2ZmVXBkYXRlKHRoaXMuX3NjYWxlVXBkYXRlQ2FsbGJhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NjYWxlID0gc2NhbGU7CiAgICAgICAgICAgIHRoaXMuX3NjYWxlLm9uVXBkYXRlKHRoaXMuX3NjYWxlVXBkYXRlQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9zeW5jUGl4ZWxQb3NpdGlvbkFuZFZhbHVlKCk7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3VpZGVMaW5lTGF5ZXIucHJvdG90eXBlLnZhbHVlID0gZnVuY3Rpb24gKHZhbHVlKSB7CiAgICAgICAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fdmFsdWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgdGhpcy5fbW9kZSA9IFByb3BlcnR5TW9kZS5WQUxVRTsKICAgICAgICAgICAgdGhpcy5fc3luY1BpeGVsUG9zaXRpb25BbmRWYWx1ZSgpOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEd1aWRlTGluZUxheWVyLnByb3RvdHlwZS5waXhlbFBvc2l0aW9uID0gZnVuY3Rpb24gKHBpeGVsUG9zaXRpb24pIHsKICAgICAgICAgICAgaWYgKHBpeGVsUG9zaXRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3BpeGVsUG9zaXRpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCF1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihwaXhlbFBvc2l0aW9uKSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJwaXhlbFBvc2l0aW9uIG11c3QgYmUgYSBmaW5pdGUgbnVtYmVyIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fcGl4ZWxQb3NpdGlvbiA9IHBpeGVsUG9zaXRpb247CiAgICAgICAgICAgIHRoaXMuX21vZGUgPSBQcm9wZXJ0eU1vZGUuUElYRUw7CiAgICAgICAgICAgIHRoaXMuX3N5bmNQaXhlbFBvc2l0aW9uQW5kVmFsdWUoKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBHdWlkZUxpbmVMYXllci5wcm90b3R5cGUuZGVzdHJveSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5kZXN0cm95LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLnNjYWxlKCkgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5zY2FsZSgpLm9mZlVwZGF0ZSh0aGlzLl9zY2FsZVVwZGF0ZUNhbGxiYWNrKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgR3VpZGVMaW5lTGF5ZXIuT1JJRU5UQVRJT05fVkVSVElDQUwgPSAidmVydGljYWwiOwogICAgICAgIEd1aWRlTGluZUxheWVyLk9SSUVOVEFUSU9OX0hPUklaT05UQUwgPSAiaG9yaXpvbnRhbCI7CiAgICAgICAgcmV0dXJuIEd1aWRlTGluZUxheWVyOwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLkd1aWRlTGluZUxheWVyID0gR3VpZGVMaW5lTGF5ZXI7CiAgICB9KTsKCiAgICB2YXIgZHJhZ0xpbmVMYXllciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKICAgIHZhciBEcmFnTGluZUxheWVyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoRHJhZ0xpbmVMYXllciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBEcmFnTGluZUxheWVyKG9yaWVudGF0aW9uKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMsIG9yaWVudGF0aW9uKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fZGV0ZWN0aW9uUmFkaXVzID0gMzsKICAgICAgICAgICAgX3RoaXMuX2VuYWJsZWQgPSB0cnVlOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygiZHJhZy1saW5lLWxheWVyIik7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJlbmFibGVkIik7CiAgICAgICAgICAgIF90aGlzLl9kcmFnSW50ZXJhY3Rpb24gPSBuZXcgaW50ZXJhY3Rpb25zLkRyYWcoKTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5hdHRhY2hUbyhfdGhpcyk7CiAgICAgICAgICAgIHZhciBvbkxpbmUgPSBmdW5jdGlvbiAocCkgewogICAgICAgICAgICAgICAgcmV0dXJuIChfdGhpcy5faXNWZXJ0aWNhbCgpICYmCiAgICAgICAgICAgICAgICAgICAgX3RoaXMucGl4ZWxQb3NpdGlvbigpIC0gX3RoaXMuZGV0ZWN0aW9uUmFkaXVzKCkgPD0gcC54ICYmCiAgICAgICAgICAgICAgICAgICAgcC54IDw9IF90aGlzLnBpeGVsUG9zaXRpb24oKSArIF90aGlzLmRldGVjdGlvblJhZGl1cygpKSB8fAogICAgICAgICAgICAgICAgICAgICghX3RoaXMuX2lzVmVydGljYWwoKSAmJgogICAgICAgICAgICAgICAgICAgICAgICBfdGhpcy5waXhlbFBvc2l0aW9uKCkgLSBfdGhpcy5kZXRlY3Rpb25SYWRpdXMoKSA8PSBwLnkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgcC55IDw9IF90aGlzLnBpeGVsUG9zaXRpb24oKSArIF90aGlzLmRldGVjdGlvblJhZGl1cygpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIGRyYWdnaW5nID0gZmFsc2U7CiAgICAgICAgICAgIHZhciBpbnRlcmFjdGlvbkRyYWdTdGFydENhbGxiYWNrID0gZnVuY3Rpb24gKHN0YXJ0KSB7CiAgICAgICAgICAgICAgICBpZiAob25MaW5lKHN0YXJ0KSkgewogICAgICAgICAgICAgICAgICAgIGRyYWdnaW5nID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmNhbGxDYWxsYmFja3MoX3RoaXMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBfdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9uRHJhZ1N0YXJ0KGludGVyYWN0aW9uRHJhZ1N0YXJ0Q2FsbGJhY2spOwogICAgICAgICAgICB2YXIgaW50ZXJhY3Rpb25EcmFnQ2FsbGJhY2sgPSBmdW5jdGlvbiAoc3RhcnQsIGVuZCkgewogICAgICAgICAgICAgICAgaWYgKGRyYWdnaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuX3NldFBpeGVsUG9zaXRpb25XaXRob3V0Q2hhbmdpbmdNb2RlKF90aGlzLl9pc1ZlcnRpY2FsKCkgPyBlbmQueCA6IGVuZC55KTsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ0NhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKF90aGlzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vbkRyYWcoaW50ZXJhY3Rpb25EcmFnQ2FsbGJhY2spOwogICAgICAgICAgICB2YXIgaW50ZXJhY3Rpb25EcmFnRW5kQ2FsbGJhY2sgPSBmdW5jdGlvbiAoc3RhcnQsIGVuZCkgewogICAgICAgICAgICAgICAgaWYgKGRyYWdnaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgZHJhZ2dpbmcgPSBmYWxzZTsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ0VuZENhbGxiYWNrcy5jYWxsQ2FsbGJhY2tzKF90aGlzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfTsKICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vbkRyYWdFbmQoaW50ZXJhY3Rpb25EcmFnRW5kQ2FsbGJhY2spOwogICAgICAgICAgICBfdGhpcy5fZGlzY29ubmVjdEludGVyYWN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vZmZEcmFnU3RhcnQoaW50ZXJhY3Rpb25EcmFnU3RhcnRDYWxsYmFjayk7CiAgICAgICAgICAgICAgICBfdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9mZkRyYWcoaW50ZXJhY3Rpb25EcmFnQ2FsbGJhY2spOwogICAgICAgICAgICAgICAgX3RoaXMuX2RyYWdJbnRlcmFjdGlvbi5vZmZEcmFnRW5kKGludGVyYWN0aW9uRHJhZ0VuZENhbGxiYWNrKTsKICAgICAgICAgICAgICAgIF90aGlzLl9kcmFnSW50ZXJhY3Rpb24uZGV0YWNoKCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIF90aGlzLl9kcmFnU3RhcnRDYWxsYmFja3MgPSBuZXcgdXRpbHMkMS5DYWxsYmFja1NldCgpOwogICAgICAgICAgICBfdGhpcy5fZHJhZ0NhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIF90aGlzLl9kcmFnRW5kQ2FsbGJhY2tzID0gbmV3IHV0aWxzJDEuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBEcmFnTGluZUxheWVyLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkVkZ2UgPSB0aGlzLmNvbnRlbnQoKS5hcHBlbmQoImxpbmUiKS5zdHlsZXMoewogICAgICAgICAgICAgICAgb3BhY2l0eTogMCwKICAgICAgICAgICAgICAgIHN0cm9rZTogInBpbmsiLAogICAgICAgICAgICAgICAgInBvaW50ZXItZXZlbnRzIjogInZpc2libGVTdHJva2UiLAogICAgICAgICAgICB9KS5jbGFzc2VkKCJkcmFnLWVkZ2UiLCB0cnVlKTsKICAgICAgICB9OwogICAgICAgIERyYWdMaW5lTGF5ZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvbkVkZ2UuYXR0cnMoewogICAgICAgICAgICAgICAgeDE6IHRoaXMuX2lzVmVydGljYWwoKSA/IHRoaXMucGl4ZWxQb3NpdGlvbigpIDogMCwKICAgICAgICAgICAgICAgIHkxOiB0aGlzLl9pc1ZlcnRpY2FsKCkgPyAwIDogdGhpcy5waXhlbFBvc2l0aW9uKCksCiAgICAgICAgICAgICAgICB4MjogdGhpcy5faXNWZXJ0aWNhbCgpID8gdGhpcy5waXhlbFBvc2l0aW9uKCkgOiB0aGlzLndpZHRoKCksCiAgICAgICAgICAgICAgICB5MjogdGhpcy5faXNWZXJ0aWNhbCgpID8gdGhpcy5oZWlnaHQoKSA6IHRoaXMucGl4ZWxQb3NpdGlvbigpLAogICAgICAgICAgICAgICAgInN0cm9rZS13aWR0aCI6IHRoaXMuX2RldGVjdGlvblJhZGl1cyAqIDIsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIERyYWdMaW5lTGF5ZXIucHJvdG90eXBlLmRldGVjdGlvblJhZGl1cyA9IGZ1bmN0aW9uIChkZXRlY3Rpb25SYWRpdXMpIHsKICAgICAgICAgICAgaWYgKGRldGVjdGlvblJhZGl1cyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZGV0ZWN0aW9uUmFkaXVzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChkZXRlY3Rpb25SYWRpdXMgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoImRldGVjdGlvbiByYWRpdXMgY2Fubm90IGJlIG5lZ2F0aXZlLiIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2RldGVjdGlvblJhZGl1cyA9IGRldGVjdGlvblJhZGl1czsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBEcmFnTGluZUxheWVyLnByb3RvdHlwZS5lbmFibGVkID0gZnVuY3Rpb24gKGVuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKGVuYWJsZWQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VuYWJsZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZW5hYmxlZCA9IGVuYWJsZWQ7CiAgICAgICAgICAgIGlmIChlbmFibGVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFkZENsYXNzKCJlbmFibGVkIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLnJlbW92ZUNsYXNzKCJlbmFibGVkIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmVuYWJsZWQoZW5hYmxlZCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyB0aGUgY2FsbGJhY2sgdG8gYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgc3RhcnRzLgogICAgICAgICAqIFRoZSBjYWxsYmFjayB3aWxsIGJlIHBhc3NlZCB0aGUgY2FsbGluZyBEcmFnTGluZUxheWVyLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnTGluZUNhbGxiYWNrPEQ+fSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnTGluZUxheWVyPEQ+fSBUaGUgY2FsbGluZyBEcmFnTGluZUxheWVyLgogICAgICAgICAqLwogICAgICAgIERyYWdMaW5lTGF5ZXIucHJvdG90eXBlLm9uRHJhZ1N0YXJ0ID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdTdGFydENhbGxiYWNrcy5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIGRyYWdnaW5nIHN0YXJ0cy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RHJhZ0xpbmVDYWxsYmFjazxEPn0gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ0xpbmVMYXllcjxEPn0gVGhlIGNhbGxpbmcgRHJhZ0xpbmVMYXllci4KICAgICAgICAgKi8KICAgICAgICBEcmFnTGluZUxheWVyLnByb3RvdHlwZS5vZmZEcmFnU3RhcnQgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyBhIGNhbGxiYWNrIHRvIGJlIGNhbGxlZCBkdXJpbmcgZHJhZ2dpbmcuCiAgICAgICAgICogVGhlIGNhbGxiYWNrIHdpbGwgYmUgcGFzc2VkIHRoZSBjYWxsaW5nIERyYWdMaW5lTGF5ZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RyYWdMaW5lQ2FsbGJhY2s8RD59IGNhbGxiYWNrCiAgICAgICAgICogQHJldHVybnMge0RyYWdMaW5lTGF5ZXI8RD59IFRoZSBjYWxsaW5nIERyYWdMaW5lTGF5ZXIuCiAgICAgICAgICovCiAgICAgICAgRHJhZ0xpbmVMYXllci5wcm90b3R5cGUub25EcmFnID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdDYWxsYmFja3MuYWRkKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIGEgY2FsbGJhY2sgdGhhdCB3b3VsZCBiZSBjYWxsZWQgZHVyaW5nIGRyYWdnaW5nLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnTGluZUNhbGxiYWNrPEQ+fSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnTGluZUxheWVyPEQ+fSBUaGUgY2FsbGluZyBEcmFnTGluZUxheWVyLgogICAgICAgICAqLwogICAgICAgIERyYWdMaW5lTGF5ZXIucHJvdG90eXBlLm9mZkRyYWcgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ0NhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiBkcmFnZ2luZyBlbmRzLgogICAgICAgICAqIFRoZSBjYWxsYmFjayB3aWxsIGJlIHBhc3NlZCB0aGUgY2FsbGluZyBEcmFnTGluZUxheWVyLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEcmFnTGluZUNhbGxiYWNrPEQ+fSBjYWxsYmFjawogICAgICAgICAqIEByZXR1cm5zIHtEcmFnTGluZUxheWVyPEQ+fSBUaGUgY2FsbGluZyBEcmFnTGluZUxheWVyLgogICAgICAgICAqLwogICAgICAgIERyYWdMaW5lTGF5ZXIucHJvdG90eXBlLm9uRHJhZ0VuZCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLl9kcmFnRW5kQ2FsbGJhY2tzLmFkZChjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIGNhbGxiYWNrIHRoYXQgd291bGQgYmUgY2FsbGVkIHdoZW4gZHJhZ2dpbmcgZW5kcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RHJhZ0xpbmVDYWxsYmFjazxEPn0gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RHJhZ0xpbmVMYXllcjxEPn0gVGhlIGNhbGxpbmcgRHJhZ0xpbmVMYXllci4KICAgICAgICAgKi8KICAgICAgICBEcmFnTGluZUxheWVyLnByb3RvdHlwZS5vZmZEcmFnRW5kID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2RyYWdFbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBEcmFnTGluZUxheWVyLnByb3RvdHlwZS5kZXN0cm95ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmRlc3Ryb3kuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmZvckVhY2goZnVuY3Rpb24gKGNhbGxiYWNrKSB7IHJldHVybiBfdGhpcy5fZHJhZ1N0YXJ0Q2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7IH0pOwogICAgICAgICAgICB0aGlzLl9kcmFnQ2FsbGJhY2tzLmZvckVhY2goZnVuY3Rpb24gKGNhbGxiYWNrKSB7IHJldHVybiBfdGhpcy5fZHJhZ0NhbGxiYWNrcy5kZWxldGUoY2FsbGJhY2spOyB9KTsKICAgICAgICAgICAgdGhpcy5fZHJhZ0VuZENhbGxiYWNrcy5mb3JFYWNoKGZ1bmN0aW9uIChjYWxsYmFjaykgeyByZXR1cm4gX3RoaXMuX2RyYWdFbmRDYWxsYmFja3MuZGVsZXRlKGNhbGxiYWNrKTsgfSk7CiAgICAgICAgICAgIHRoaXMuX2Rpc2Nvbm5lY3RJbnRlcmFjdGlvbigpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIERyYWdMaW5lTGF5ZXI7CiAgICB9KGd1aWRlTGluZUxheWVyLkd1aWRlTGluZUxheWVyKSk7CiAgICBleHBvcnRzLkRyYWdMaW5lTGF5ZXIgPSBEcmFnTGluZUxheWVyOwogICAgfSk7CgogICAgdmFyIGdyaWRsaW5lcyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCiAgICAvKioKICAgICAqIFJldHVybnMgbmV4dCBncmlkIHBvc2l0aW9uIGJhc2VkIG9uIHRpY2sgdmFsdWUKICAgICAqCiAgICAgKiBAcGFyYW0gc2NhbGUgU2NhbGUgdXNlZCBieSB0aGUgZ3JpZAogICAgICogQHBhcmFtIGJldHdlZW4gVmFsdWUgZGVub3Rpbmcgd2hldGhlciB0aGUgZ3JpZCByZW5kZXJzIGJldHdlZW4gdGlja3Mgb3Igb24gdGlja3MKICAgICAqIEBwYXJhbSBvcmRlcmVkVGlja3MgQWxsIHRpY2tzIGluIG9yZGVyLiBvbmx5IG5lZWRlZCB3aGVuIHJlbmRlcmluZyBsaW5lcyBiZXR3ZWVuIHRpY2tzCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdyaWRQb3NpdGlvbkZhY3Rvcnkoc2NhbGUsIGJldHdlZW4sIG9yZGVyZWRUaWNrcykgewogICAgICAgIHZhciBwcmV2aW91c1RpY2sgPSB7fTsKICAgICAgICBpZiAob3JkZXJlZFRpY2tzICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBvcmRlcmVkVGlja3MubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIHZhciBwcmV2aW91cyA9IG9yZGVyZWRUaWNrc1tpIC0gMV07CiAgICAgICAgICAgICAgICB2YXIgY3VycmVudCA9IG9yZGVyZWRUaWNrc1tpXTsKICAgICAgICAgICAgICAgIHByZXZpb3VzVGlja1tjdXJyZW50XSA9IHByZXZpb3VzOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBmdW5jdGlvbiAodGlja1ZhbCkgewogICAgICAgICAgICB2YXIgcG9zaXRpb24gPSBzY2FsZS5zY2FsZSh0aWNrVmFsKTsKICAgICAgICAgICAgaWYgKCFiZXR3ZWVuKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gcG9zaXRpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGdyaWRQb3NpdGlvbjsKICAgICAgICAgICAgdmFyIHByZXZpb3VzUG9zaXRpb24gPSBwcmV2aW91c1RpY2tbdGlja1ZhbF0gPT09IHVuZGVmaW5lZAogICAgICAgICAgICAgICAgPyB1bmRlZmluZWQKICAgICAgICAgICAgICAgIDogc2NhbGUuc2NhbGUocHJldmlvdXNUaWNrW3RpY2tWYWxdKTsKICAgICAgICAgICAgaWYgKHByZXZpb3VzUG9zaXRpb24gIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgZ3JpZFBvc2l0aW9uID0gcHJldmlvdXNQb3NpdGlvbiArIChwb3NpdGlvbiAtIHByZXZpb3VzUG9zaXRpb24pIC8gMjsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZ3JpZFBvc2l0aW9uOwogICAgICAgIH07CiAgICB9CiAgICB2YXIgR3JpZGxpbmVzID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoR3JpZGxpbmVzLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7U2NhbGV9IHhTY2FsZSBUaGUgc2NhbGUgdG8gYmFzZSB0aGUgeCBncmlkbGluZXMgb24uIFBhc3MgbnVsbCBpZiBubyBncmlkbGluZXMgYXJlIGRlc2lyZWQuCiAgICAgICAgICogQHBhcmFtIHtTY2FsZX0geVNjYWxlIFRoZSBzY2FsZSB0byBiYXNlIHRoZSB5IGdyaWRsaW5lcyBvbi4gUGFzcyBudWxsIGlmIG5vIGdyaWRsaW5lcyBhcmUgZGVzaXJlZC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBHcmlkbGluZXMoeFNjYWxlLCB5U2NhbGUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoImdyaWRsaW5lcyIpOwogICAgICAgICAgICBfdGhpcy5feFNjYWxlID0geFNjYWxlOwogICAgICAgICAgICBfdGhpcy5feVNjYWxlID0geVNjYWxlOwogICAgICAgICAgICBfdGhpcy5fcmVuZGVyQ2FsbGJhY2sgPSBmdW5jdGlvbiAoc2NhbGUpIHsgcmV0dXJuIF90aGlzLnJlbmRlcigpOyB9OwogICAgICAgICAgICBpZiAoX3RoaXMuX3hTY2FsZSkgewogICAgICAgICAgICAgICAgX3RoaXMuX3hTY2FsZS5vblVwZGF0ZShfdGhpcy5fcmVuZGVyQ2FsbGJhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChfdGhpcy5feVNjYWxlKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5feVNjYWxlLm9uVXBkYXRlKF90aGlzLl9yZW5kZXJDYWxsYmFjayk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBHcmlkbGluZXMucHJvdG90eXBlLmJldHdlZW5YID0gZnVuY3Rpb24gKF9iZXR3ZWVuWCkgewogICAgICAgICAgICBpZiAoX2JldHdlZW5YID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9iZXR3ZWVuWDsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoX2JldHdlZW5YICE9PSB0aGlzLl9iZXR3ZWVuWCkgewogICAgICAgICAgICAgICAgdGhpcy5fYmV0d2VlblggPSBfYmV0d2Vlblg7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3JpZGxpbmVzLnByb3RvdHlwZS5iZXR3ZWVuWSA9IGZ1bmN0aW9uIChfYmV0d2VlblkpIHsKICAgICAgICAgICAgaWYgKF9iZXR3ZWVuWSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYmV0d2Vlblk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKF9iZXR3ZWVuWSAhPT0gdGhpcy5fYmV0d2VlblkpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2JldHdlZW5ZID0gX2JldHdlZW5ZOwogICAgICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEdyaWRsaW5lcy5wcm90b3R5cGUuZGVzdHJveSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5kZXN0cm95LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLl94U2NhbGUpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3hTY2FsZS5vZmZVcGRhdGUodGhpcy5fcmVuZGVyQ2FsbGJhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl95U2NhbGUpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3lTY2FsZS5vZmZVcGRhdGUodGhpcy5fcmVuZGVyQ2FsbGJhY2spOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3JpZGxpbmVzLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3hMaW5lc0NvbnRhaW5lciA9IHRoaXMuY29udGVudCgpLmFwcGVuZCgiZyIpLmNsYXNzZWQoIngtZ3JpZGxpbmVzIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX3lMaW5lc0NvbnRhaW5lciA9IHRoaXMuY29udGVudCgpLmFwcGVuZCgiZyIpLmNsYXNzZWQoInktZ3JpZGxpbmVzIiwgdHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBHcmlkbGluZXMucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3JlZHJhd1hMaW5lcygpOwogICAgICAgICAgICB0aGlzLl9yZWRyYXdZTGluZXMoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBHcmlkbGluZXMucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQgPSBmdW5jdGlvbiAob3JpZ2luLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuY29tcHV0ZUxheW91dC5jYWxsKHRoaXMsIG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCk7CiAgICAgICAgICAgIGlmICh0aGlzLl94U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5feFNjYWxlLnJhbmdlKFswLCB0aGlzLndpZHRoKCldKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5feVNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3lTY2FsZS5yYW5nZShbdGhpcy5oZWlnaHQoKSwgMF0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3JpZGxpbmVzLnByb3RvdHlwZS5fcmVkcmF3WExpbmVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5feFNjYWxlKSB7CiAgICAgICAgICAgICAgICB2YXIgYmV0d2VlbiA9IHRoaXMuYmV0d2VlblgoKTsKICAgICAgICAgICAgICAgIHZhciB4VGlja3MgPSB0aGlzLl94U2NhbGUudGlja3MoKS5zbGljZShiZXR3ZWVuID8gMSA6IDApOwogICAgICAgICAgICAgICAgdmFyIHhMaW5lc1VwZGF0ZSA9IHRoaXMuX3hMaW5lc0NvbnRhaW5lci5zZWxlY3RBbGwoImxpbmUiKS5kYXRhKHhUaWNrcyk7CiAgICAgICAgICAgICAgICB2YXIgeExpbmVzID0geExpbmVzVXBkYXRlLmVudGVyKCkuYXBwZW5kKCJsaW5lIikubWVyZ2UoeExpbmVzVXBkYXRlKTsKICAgICAgICAgICAgICAgIHhMaW5lcy5hdHRyKCJ4MSIsIGdyaWRQb3NpdGlvbkZhY3RvcnkodGhpcy5feFNjYWxlLCBiZXR3ZWVuLCB0aGlzLl94U2NhbGUudGlja3MoKSkpCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoInkxIiwgMCkKICAgICAgICAgICAgICAgICAgICAuYXR0cigieDIiLCBncmlkUG9zaXRpb25GYWN0b3J5KHRoaXMuX3hTY2FsZSwgYmV0d2VlbiwgdGhpcy5feFNjYWxlLnRpY2tzKCkpKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCJ5MiIsIHRoaXMuaGVpZ2h0KCkpCiAgICAgICAgICAgICAgICAgICAgLmNsYXNzZWQoImJldHdlZW5saW5lIiwgYmV0d2VlbikKICAgICAgICAgICAgICAgICAgICAuY2xhc3NlZCgiemVyb2xpbmUiLCBmdW5jdGlvbiAodCkgeyByZXR1cm4gdCA9PT0gMDsgfSk7CiAgICAgICAgICAgICAgICB4TGluZXNVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBHcmlkbGluZXMucHJvdG90eXBlLl9yZWRyYXdZTGluZXMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl95U2NhbGUpIHsKICAgICAgICAgICAgICAgIHZhciBiZXR3ZWVuID0gdGhpcy5iZXR3ZWVuWSgpOwogICAgICAgICAgICAgICAgdmFyIHlUaWNrcyA9IHRoaXMuX3lTY2FsZS50aWNrcygpLnNsaWNlKGJldHdlZW4gPyAxIDogMCk7CiAgICAgICAgICAgICAgICB2YXIgeUxpbmVzVXBkYXRlID0gdGhpcy5feUxpbmVzQ29udGFpbmVyLnNlbGVjdEFsbCgibGluZSIpLmRhdGEoeVRpY2tzKTsKICAgICAgICAgICAgICAgIHZhciB5TGluZXMgPSB5TGluZXNVcGRhdGUuZW50ZXIoKS5hcHBlbmQoImxpbmUiKS5tZXJnZSh5TGluZXNVcGRhdGUpOwogICAgICAgICAgICAgICAgeUxpbmVzLmF0dHIoIngxIiwgMCkKICAgICAgICAgICAgICAgICAgICAuYXR0cigieTEiLCBncmlkUG9zaXRpb25GYWN0b3J5KHRoaXMuX3lTY2FsZSwgYmV0d2VlbiwgdGhpcy5feVNjYWxlLnRpY2tzKCkpKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCJ4MiIsIHRoaXMud2lkdGgoKSkKICAgICAgICAgICAgICAgICAgICAuYXR0cigieTIiLCBncmlkUG9zaXRpb25GYWN0b3J5KHRoaXMuX3lTY2FsZSwgYmV0d2VlbiwgdGhpcy5feVNjYWxlLnRpY2tzKCkpKQogICAgICAgICAgICAgICAgICAgIC5jbGFzc2VkKCJiZXR3ZWVubGluZSIsIGJldHdlZW4pCiAgICAgICAgICAgICAgICAgICAgLmNsYXNzZWQoInplcm9saW5lIiwgZnVuY3Rpb24gKHQpIHsgcmV0dXJuIHQgPT09IDA7IH0pOwogICAgICAgICAgICAgICAgeUxpbmVzVXBkYXRlLmV4aXQoKS5yZW1vdmUoKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEdyaWRsaW5lczsKICAgIH0oY29tcG9uZW50LkNvbXBvbmVudCkpOwogICAgZXhwb3J0cy5HcmlkbGluZXMgPSBHcmlkbGluZXM7CiAgICB9KTsKCiAgICB2YXIgY29tcG9uZW50Q29udGFpbmVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICAvKgogICAgICogQ29tcG9uZW50Q29udGFpbmVyIGNsYXNzIGVuY2Fwc3VsYXRlcyBUYWJsZSBhbmQgQ29tcG9uZW50R3JvdXAncyBzaGFyZWQgZnVuY3Rpb25hbGl0eS4KICAgICAqIEl0IHdpbGwgbm90IGRvIGFueXRoaW5nIGlmIGluc3RhbnRpYXRlZCBkaXJlY3RseS4KICAgICAqLwogICAgdmFyIENvbXBvbmVudENvbnRhaW5lciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKENvbXBvbmVudENvbnRhaW5lciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBDb21wb25lbnRDb250YWluZXIoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9kZXRhY2hDYWxsYmFjayA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsgcmV0dXJuIF90aGlzLnJlbW92ZShjb21wb25lbnQpOyB9OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIENvbXBvbmVudENvbnRhaW5lci5wcm90b3R5cGUuYW5jaG9yID0gZnVuY3Rpb24gKHNlbGVjdGlvbikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBzZWxlY3Rpb24gPSBjb2VyY2VEMy5jb2VyY2VFeHRlcm5hbEQzKHNlbGVjdGlvbik7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuYW5jaG9yLmNhbGwodGhpcywgc2VsZWN0aW9uKTsKICAgICAgICAgICAgdGhpcy5fZm9yRWFjaChmdW5jdGlvbiAoYykgeyByZXR1cm4gYy5hbmNob3IoX3RoaXMuZWxlbWVudCgpKTsgfSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50Q29udGFpbmVyLnByb3RvdHlwZS5yZW5kZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuX2ZvckVhY2goZnVuY3Rpb24gKGMpIHsgcmV0dXJuIGMucmVuZGVyKCk7IH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyB3aGV0aGVyIHRoZSBzcGVjaWZpZWQgQ29tcG9uZW50IGlzIGluIHRoZSBDb21wb25lbnRDb250YWluZXIuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50Q29udGFpbmVyLnByb3RvdHlwZS5oYXMgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiaGFzKCkgaXMgbm90IGltcGxlbWVudGVkIG9uIENvbXBvbmVudENvbnRhaW5lciIpOwogICAgICAgIH07CiAgICAgICAgQ29tcG9uZW50Q29udGFpbmVyLnByb3RvdHlwZS5fYWRvcHRBbmRBbmNob3IgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIGNvbXBvbmVudC5wYXJlbnQodGhpcyk7CiAgICAgICAgICAgIGNvbXBvbmVudC5vbkRldGFjaCh0aGlzLl9kZXRhY2hDYWxsYmFjayk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc0FuY2hvcmVkKSB7CiAgICAgICAgICAgICAgICBjb21wb25lbnQuYW5jaG9yKHRoaXMuZWxlbWVudCgpKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyB0aGUgc3BlY2lmaWVkIENvbXBvbmVudCBmcm9tIHRoZSBDb21wb25lbnRDb250YWluZXIuCiAgICAgICAgICovCiAgICAgICAgQ29tcG9uZW50Q29udGFpbmVyLnByb3RvdHlwZS5yZW1vdmUgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIGlmICh0aGlzLmhhcyhjb21wb25lbnQpKSB7CiAgICAgICAgICAgICAgICBjb21wb25lbnQub2ZmRGV0YWNoKHRoaXMuX2RldGFjaENhbGxiYWNrKTsKICAgICAgICAgICAgICAgIHRoaXMuX3JlbW92ZShjb21wb25lbnQpOwogICAgICAgICAgICAgICAgY29tcG9uZW50LmRldGFjaCgpOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENhcnJ5IG91dCB0aGUgYWN0dWFsIHJlbW92YWwgb2YgYSBDb21wb25lbnQuCiAgICAgICAgICogSW1wbGVtZW50YXRpb24gZGVwZW5kZW50IG9uIHRoZSB0eXBlIG9mIGNvbnRhaW5lci4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IHRydWUgaWYgdGhlIENvbXBvbmVudCB3YXMgc3VjY2Vzc2Z1bGx5IHJlbW92ZWQsIGZhbHNlIG90aGVyd2lzZS4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnRDb250YWluZXIucHJvdG90eXBlLl9yZW1vdmUgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEludm9rZXMgYSBjYWxsYmFjayBvbiBlYWNoIENvbXBvbmVudCBpbiB0aGUgQ29tcG9uZW50Q29udGFpbmVyLgogICAgICAgICAqLwogICAgICAgIENvbXBvbmVudENvbnRhaW5lci5wcm90b3R5cGUuX2ZvckVhY2ggPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJfZm9yRWFjaCgpIGlzIG5vdCBpbXBsZW1lbnRlZCBvbiBDb21wb25lbnRDb250YWluZXIiKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIERlc3Ryb3lzIHRoZSBDb21wb25lbnRDb250YWluZXIgYW5kIGFsbCBDb21wb25lbnRzIHdpdGhpbiBpdC4KICAgICAgICAgKi8KICAgICAgICBDb21wb25lbnRDb250YWluZXIucHJvdG90eXBlLmRlc3Ryb3kgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGVzdHJveS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9mb3JFYWNoKGZ1bmN0aW9uIChjKSB7IHJldHVybiBjLmRlc3Ryb3koKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBDb21wb25lbnRDb250YWluZXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fZm9yRWFjaChmdW5jdGlvbiAoYykgeyByZXR1cm4gYy5pbnZhbGlkYXRlQ2FjaGUoKTsgfSk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ29tcG9uZW50Q29udGFpbmVyOwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLkNvbXBvbmVudENvbnRhaW5lciA9IENvbXBvbmVudENvbnRhaW5lcjsKICAgIH0pOwoKICAgIHZhciBncm91cCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIEdyb3VwID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoR3JvdXAsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29uc3RydWN0cyBhIEdyb3VwLgogICAgICAgICAqCiAgICAgICAgICogQSBHcm91cCBjb250YWlucyBDb21wb25lbnRzIHRoYXQgd2lsbCBiZSByZW5kZXJlZCBvbiB0b3Agb2YgZWFjaCBvdGhlci4KICAgICAgICAgKiBDb21wb25lbnRzIGFkZGVkIGxhdGVyIHdpbGwgYmUgcmVuZGVyZWQgYWJvdmUgQ29tcG9uZW50cyBhbHJlYWR5IGluIHRoZSBHcm91cC4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7Q29tcG9uZW50W119IFtjb21wb25lbnRzPVtdXSBDb21wb25lbnRzIHRvIGJlIGFkZGVkIHRvIHRoZSBHcm91cC4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBHcm91cChjb21wb25lbnRzKSB7CiAgICAgICAgICAgIGlmIChjb21wb25lbnRzID09PSB2b2lkIDApIHsgY29tcG9uZW50cyA9IFtdOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9jb21wb25lbnRzID0gW107CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJjb21wb25lbnQtZ3JvdXAiKTsKICAgICAgICAgICAgY29tcG9uZW50cy5mb3JFYWNoKGZ1bmN0aW9uIChjKSB7IHJldHVybiBfdGhpcy5hcHBlbmQoYyk7IH0pOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIEdyb3VwLnByb3RvdHlwZS5fZm9yRWFjaCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICB0aGlzLmNvbXBvbmVudHMoKS5mb3JFYWNoKGNhbGxiYWNrKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENoZWNrcyB3aGV0aGVyIHRoZSBzcGVjaWZpZWQgQ29tcG9uZW50IGlzIGluIHRoZSBHcm91cC4KICAgICAgICAgKi8KICAgICAgICBHcm91cC5wcm90b3R5cGUuaGFzID0gZnVuY3Rpb24gKGNvbXBvbmVudCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fY29tcG9uZW50cy5pbmRleE9mKGNvbXBvbmVudCkgPj0gMDsKICAgICAgICB9OwogICAgICAgIEdyb3VwLnByb3RvdHlwZS5yZXF1ZXN0ZWRTcGFjZSA9IGZ1bmN0aW9uIChvZmZlcmVkV2lkdGgsIG9mZmVyZWRIZWlnaHQpIHsKICAgICAgICAgICAgdmFyIHJlcXVlc3RzID0gdGhpcy5fY29tcG9uZW50cy5tYXAoZnVuY3Rpb24gKGMpIHsgcmV0dXJuIGMucmVxdWVzdGVkU3BhY2Uob2ZmZXJlZFdpZHRoLCBvZmZlcmVkSGVpZ2h0KTsgfSk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBtaW5XaWR0aDogdXRpbHMkMS5NYXRoLm1heChyZXF1ZXN0cywgZnVuY3Rpb24gKHJlcXVlc3QpIHsgcmV0dXJuIHJlcXVlc3QubWluV2lkdGg7IH0sIDApLAogICAgICAgICAgICAgICAgbWluSGVpZ2h0OiB1dGlscyQxLk1hdGgubWF4KHJlcXVlc3RzLCBmdW5jdGlvbiAocmVxdWVzdCkgeyByZXR1cm4gcmVxdWVzdC5taW5IZWlnaHQ7IH0sIDApLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgR3JvdXAucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQgPSBmdW5jdGlvbiAob3JpZ2luLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuY29tcHV0ZUxheW91dC5jYWxsKHRoaXMsIG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCk7CiAgICAgICAgICAgIHRoaXMuX2ZvckVhY2goZnVuY3Rpb24gKGNvbXBvbmVudCkgewogICAgICAgICAgICAgICAgY29tcG9uZW50LmNvbXB1dGVMYXlvdXQoeyB4OiAwLCB5OiAwIH0sIF90aGlzLndpZHRoKCksIF90aGlzLmhlaWdodCgpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3JvdXAucHJvdG90eXBlLl9zaXplRnJvbU9mZmVyID0gZnVuY3Rpb24gKGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHdpZHRoOiBhdmFpbGFibGVXaWR0aCwKICAgICAgICAgICAgICAgIGhlaWdodDogYXZhaWxhYmxlSGVpZ2h0LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgR3JvdXAucHJvdG90eXBlLmZpeGVkV2lkdGggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb21wb25lbnRzLmV2ZXJ5KGZ1bmN0aW9uIChjKSB7IHJldHVybiBjLmZpeGVkV2lkdGgoKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBHcm91cC5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb21wb25lbnRzLmV2ZXJ5KGZ1bmN0aW9uIChjKSB7IHJldHVybiBjLmZpeGVkSGVpZ2h0KCk7IH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB7Q29tcG9uZW50W119IFRoZSBDb21wb25lbnRzIGluIHRoaXMgR3JvdXAuCiAgICAgICAgICovCiAgICAgICAgR3JvdXAucHJvdG90eXBlLmNvbXBvbmVudHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb21wb25lbnRzLnNsaWNlKCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgQ29tcG9uZW50IHRvIHRoaXMgR3JvdXAuCiAgICAgICAgICogVGhlIGFkZGVkIENvbXBvbmVudCB3aWxsIGJlIHJlbmRlcmVkIGFib3ZlIENvbXBvbmVudHMgYWxyZWFkeSBpbiB0aGUgR3JvdXAuCiAgICAgICAgICovCiAgICAgICAgR3JvdXAucHJvdG90eXBlLmFwcGVuZCA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgaWYgKGNvbXBvbmVudCAhPSBudWxsICYmICF0aGlzLmhhcyhjb21wb25lbnQpKSB7CiAgICAgICAgICAgICAgICBjb21wb25lbnQuZGV0YWNoKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9jb21wb25lbnRzLnB1c2goY29tcG9uZW50KTsKICAgICAgICAgICAgICAgIHRoaXMuX2Fkb3B0QW5kQW5jaG9yKGNvbXBvbmVudCk7CiAgICAgICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgR3JvdXAucHJvdG90eXBlLl9yZW1vdmUgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIHZhciByZW1vdmVJbmRleCA9IHRoaXMuX2NvbXBvbmVudHMuaW5kZXhPZihjb21wb25lbnQpOwogICAgICAgICAgICBpZiAocmVtb3ZlSW5kZXggPj0gMCkgewogICAgICAgICAgICAgICAgdGhpcy5fY29tcG9uZW50cy5zcGxpY2UocmVtb3ZlSW5kZXgsIDEpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEdyb3VwOwogICAgfShjb21wb25lbnRDb250YWluZXIuQ29tcG9uZW50Q29udGFpbmVyKSk7CiAgICBleHBvcnRzLkdyb3VwID0gR3JvdXA7CiAgICB9KTsKCiAgICB2YXIgaW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgoKICAgIHZhciBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKEludGVycG9sYXRlZENvbG9yTGVnZW5kLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYW4gSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQgY29uc2lzdHMgb2YgYSBzZXF1ZW5jZSBvZiBzd2F0Y2hlcyB0aGF0IHNob3cgdGhlCiAgICAgICAgICogYXNzb2NpYXRlZCBJbnRlcnBvbGF0ZWRDb2xvciBTY2FsZSBzYW1wbGVkIGF0IHZhcmlvdXMgcG9pbnRzLgogICAgICAgICAqIFR3byBsYWJlbHMgc2hvdyB0aGUgbWF4aW11bSBhbmQgbWluaW11bSB2YWx1ZXMgb2YgdGhlIEludGVycG9sYXRlZENvbG9yIFNjYWxlLgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtTY2FsZXMuSW50ZXJwb2xhdGVkQ29sb3J9IGludGVycG9sYXRlZENvbG9yU2NhbGUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZChpbnRlcnBvbGF0ZWRDb2xvclNjYWxlKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl90ZXh0UGFkZGluZyA9IDU7CiAgICAgICAgICAgIGlmIChpbnRlcnBvbGF0ZWRDb2xvclNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQgcmVxdWlyZXMgYSBpbnRlcnBvbGF0ZWRDb2xvclNjYWxlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgX3RoaXMuX3NjYWxlID0gaW50ZXJwb2xhdGVkQ29sb3JTY2FsZTsKICAgICAgICAgICAgX3RoaXMuX3JlZHJhd0NhbGxiYWNrID0gZnVuY3Rpb24gKHNjYWxlKSB7IHJldHVybiBfdGhpcy5yZWRyYXcoKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3NjYWxlLm9uVXBkYXRlKF90aGlzLl9yZWRyYXdDYWxsYmFjayk7CiAgICAgICAgICAgIF90aGlzLl9mb3JtYXR0ZXIgPSBmb3JtYXR0ZXJzLmdlbmVyYWwoKTsKICAgICAgICAgICAgX3RoaXMuX29yaWVudGF0aW9uID0gImhvcml6b250YWwiOwogICAgICAgICAgICBfdGhpcy5fZXhwYW5kcyA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygibGVnZW5kIik7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJpbnRlcnBvbGF0ZWQtY29sb3ItbGVnZW5kIik7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQucHJvdG90eXBlLmRlc3Ryb3kgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGVzdHJveS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9zY2FsZS5vZmZVcGRhdGUodGhpcy5fcmVkcmF3Q2FsbGJhY2spOwogICAgICAgIH07CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQucHJvdG90eXBlLmZvcm1hdHRlciA9IGZ1bmN0aW9uIChmb3JtYXR0ZXIpIHsKICAgICAgICAgICAgaWYgKGZvcm1hdHRlciA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZm9ybWF0dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Zvcm1hdHRlciA9IGZvcm1hdHRlcjsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5wcm90b3R5cGUuZXhwYW5kcyA9IGZ1bmN0aW9uIChleHBhbmRzKSB7CiAgICAgICAgICAgIGlmIChleHBhbmRzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9leHBhbmRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2V4cGFuZHMgPSBleHBhbmRzOwogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yTGVnZW5kLl9lbnN1cmVPcmllbnRhdGlvbiA9IGZ1bmN0aW9uIChvcmllbnRhdGlvbikgewogICAgICAgICAgICBvcmllbnRhdGlvbiA9IG9yaWVudGF0aW9uLnRvTG93ZXJDYXNlKCk7CiAgICAgICAgICAgIGlmIChvcmllbnRhdGlvbiA9PT0gImhvcml6b250YWwiIHx8IG9yaWVudGF0aW9uID09PSAibGVmdCIgfHwgb3JpZW50YXRpb24gPT09ICJyaWdodCIpIHsKICAgICAgICAgICAgICAgIHJldHVybiBvcmllbnRhdGlvbjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiXCIiICsgb3JpZW50YXRpb24gKyAiXCIgaXMgbm90IGEgdmFsaWQgb3JpZW50YXRpb24gZm9yIEludGVycG9sYXRlZENvbG9yTGVnZW5kIik7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yTGVnZW5kLnByb3RvdHlwZS5vcmllbnRhdGlvbiA9IGZ1bmN0aW9uIChvcmllbnRhdGlvbikgewogICAgICAgICAgICBpZiAob3JpZW50YXRpb24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX29yaWVudGF0aW9uOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fb3JpZW50YXRpb24gPSBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5fZW5zdXJlT3JpZW50YXRpb24ob3JpZW50YXRpb24pOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5wcm90b3R5cGUuZml4ZWRXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuICF0aGlzLmV4cGFuZHMoKSB8fCB0aGlzLl9pc1ZlcnRpY2FsKCk7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiAhdGhpcy5leHBhbmRzKCkgfHwgIXRoaXMuX2lzVmVydGljYWwoKTsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yTGVnZW5kLnByb3RvdHlwZS5fZ2VuZXJhdGVUaWNrcyA9IGZ1bmN0aW9uIChudW1Td2F0Y2hlcykgewogICAgICAgICAgICBpZiAobnVtU3dhdGNoZXMgPT09IHZvaWQgMCkgeyBudW1Td2F0Y2hlcyA9IEludGVycG9sYXRlZENvbG9yTGVnZW5kLl9ERUZBVUxUX05VTV9TV0FUQ0hFUzsgfQogICAgICAgICAgICB2YXIgZG9tYWluID0gdGhpcy5fc2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIGlmIChudW1Td2F0Y2hlcyA9PT0gMSkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtkb21haW5bMF1dOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBzbG9wZSA9IChkb21haW5bMV0gLSBkb21haW5bMF0pIC8gKG51bVN3YXRjaGVzIC0gMSk7CiAgICAgICAgICAgIHZhciB0aWNrcyA9IFtdOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IG51bVN3YXRjaGVzOyBpKyspIHsKICAgICAgICAgICAgICAgIHRpY2tzLnB1c2goZG9tYWluWzBdICsgc2xvcGUgKiBpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGlja3M7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5wcm90b3R5cGUuX3NldHVwID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9zd2F0Y2hDb250YWluZXIgPSB0aGlzLmNvbnRlbnQoKS5hcHBlbmQoImciKS5jbGFzc2VkKCJzd2F0Y2gtY29udGFpbmVyIiwgdHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX3N3YXRjaEJvdW5kaW5nQm94ID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJyZWN0IikuY2xhc3NlZCgic3dhdGNoLWJvdW5kaW5nLWJveCIsIHRydWUpOwogICAgICAgICAgICB0aGlzLl9sb3dlckxhYmVsID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikuY2xhc3NlZChJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5MRUdFTkRfTEFCRUxfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB0aGlzLl91cHBlckxhYmVsID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikuY2xhc3NlZChJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5MRUdFTkRfTEFCRUxfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB2YXIgY29udGV4dCA9IG5ldyBzcmMkMS5TdmdDb250ZXh0KHRoaXMuY29udGVudCgpLm5vZGUoKSk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLk1lYXN1cmVyKGNvbnRleHQpOwogICAgICAgICAgICB0aGlzLl93cmFwcGVyID0gbmV3IHNyYyQxLldyYXBwZXIoKTsKICAgICAgICAgICAgdGhpcy5fd3JpdGVyID0gbmV3IHNyYyQxLldyaXRlcih0aGlzLl9tZWFzdXJlciwgY29udGV4dCwgdGhpcy5fd3JhcHBlcik7CiAgICAgICAgfTsKICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5wcm90b3R5cGUucmVxdWVzdGVkU3BhY2UgPSBmdW5jdGlvbiAob2ZmZXJlZFdpZHRoLCBvZmZlcmVkSGVpZ2h0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciB0ZXh0SGVpZ2h0ID0gdGhpcy5fbWVhc3VyZXIubWVhc3VyZSgpLmhlaWdodDsKICAgICAgICAgICAgdmFyIHBhZGRpbmcgPSB0ZXh0SGVpZ2h0OwogICAgICAgICAgICB2YXIgZG9tYWluID0gdGhpcy5fc2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIHZhciBsYWJlbFdpZHRocyA9IGRvbWFpbi5tYXAoZnVuY3Rpb24gKGQpIHsgcmV0dXJuIF90aGlzLl9tZWFzdXJlci5tZWFzdXJlKF90aGlzLl9mb3JtYXR0ZXIoZCkpLndpZHRoOyB9KTsKICAgICAgICAgICAgdmFyIGRlc2lyZWRIZWlnaHQ7CiAgICAgICAgICAgIHZhciBkZXNpcmVkV2lkdGg7CiAgICAgICAgICAgIHZhciBudW1Td2F0Y2hlcyA9IEludGVycG9sYXRlZENvbG9yTGVnZW5kLl9ERUZBVUxUX05VTV9TV0FUQ0hFUzsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzVmVydGljYWwoKSkgewogICAgICAgICAgICAgICAgdmFyIGxvbmdlc3RXaWR0aCA9IHV0aWxzJDEuTWF0aC5tYXgobGFiZWxXaWR0aHMsIDApOwogICAgICAgICAgICAgICAgZGVzaXJlZFdpZHRoID0gcGFkZGluZyArIHRleHRIZWlnaHQgKyB0aGlzLl90ZXh0UGFkZGluZyArIGxvbmdlc3RXaWR0aCArIHRoaXMuX3RleHRQYWRkaW5nOwogICAgICAgICAgICAgICAgZGVzaXJlZEhlaWdodCA9IG51bVN3YXRjaGVzICogdGV4dEhlaWdodDsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGRlc2lyZWRIZWlnaHQgPSBwYWRkaW5nICsgdGV4dEhlaWdodCArIHBhZGRpbmc7CiAgICAgICAgICAgICAgICBkZXNpcmVkV2lkdGggPSB0aGlzLl90ZXh0UGFkZGluZyArIGxhYmVsV2lkdGhzWzBdICsgbnVtU3dhdGNoZXMgKiB0ZXh0SGVpZ2h0CiAgICAgICAgICAgICAgICAgICAgKyBsYWJlbFdpZHRoc1sxXSArIHRoaXMuX3RleHRQYWRkaW5nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBtaW5XaWR0aDogZGVzaXJlZFdpZHRoLAogICAgICAgICAgICAgICAgbWluSGVpZ2h0OiBkZXNpcmVkSGVpZ2h0LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQucHJvdG90eXBlLl9pc1ZlcnRpY2FsID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fb3JpZW50YXRpb24gIT09ICJob3Jpem9udGFsIjsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yTGVnZW5kLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseS5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgZG9tYWluID0gdGhpcy5fc2NhbGUuZG9tYWluKCk7CiAgICAgICAgICAgIHZhciB0ZXh0MCA9IHRoaXMuX2Zvcm1hdHRlcihkb21haW5bMF0pOwogICAgICAgICAgICB2YXIgdGV4dDBXaWR0aCA9IHRoaXMuX21lYXN1cmVyLm1lYXN1cmUodGV4dDApLndpZHRoOwogICAgICAgICAgICB2YXIgdGV4dDEgPSB0aGlzLl9mb3JtYXR0ZXIoZG9tYWluWzFdKTsKICAgICAgICAgICAgdmFyIHRleHQxV2lkdGggPSB0aGlzLl9tZWFzdXJlci5tZWFzdXJlKHRleHQxKS53aWR0aDsKICAgICAgICAgICAgdmFyIHRleHRIZWlnaHQgPSB0aGlzLl9tZWFzdXJlci5tZWFzdXJlKCkuaGVpZ2h0OwogICAgICAgICAgICB2YXIgdGV4dFBhZGRpbmcgPSB0aGlzLl90ZXh0UGFkZGluZzsKICAgICAgICAgICAgdmFyIHVwcGVyTGFiZWxTaGlmdCA9IHsgeDogMCwgeTogMCB9OwogICAgICAgICAgICB2YXIgbG93ZXJMYWJlbFNoaWZ0ID0geyB4OiAwLCB5OiAwIH07CiAgICAgICAgICAgIHZhciBsb3dlcldyaXRlT3B0aW9ucyA9IHsKICAgICAgICAgICAgICAgIHhBbGlnbjogImNlbnRlciIsCiAgICAgICAgICAgICAgICB5QWxpZ246ICJjZW50ZXIiLAogICAgICAgICAgICAgICAgdGV4dFJvdGF0aW9uOiAwLAogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgdXBwZXJXcml0ZU9wdGlvbnMgPSB7CiAgICAgICAgICAgICAgICB4QWxpZ246ICJjZW50ZXIiLAogICAgICAgICAgICAgICAgeUFsaWduOiAiY2VudGVyIiwKICAgICAgICAgICAgICAgIHRleHRSb3RhdGlvbjogMCwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIHN3YXRjaFdpZHRoOwogICAgICAgICAgICB2YXIgc3dhdGNoSGVpZ2h0OwogICAgICAgICAgICB2YXIgc3dhdGNoWDsKICAgICAgICAgICAgdmFyIHN3YXRjaFk7CiAgICAgICAgICAgIHZhciBib3VuZGluZ0JveEF0dHIgPSB7CiAgICAgICAgICAgICAgICB4OiAwLAogICAgICAgICAgICAgICAgeTogMCwKICAgICAgICAgICAgICAgIHdpZHRoOiAwLAogICAgICAgICAgICAgICAgaGVpZ2h0OiAwLAogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgcGFkZGluZzsKICAgICAgICAgICAgdmFyIG51bVN3YXRjaGVzOwogICAgICAgICAgICBpZiAodGhpcy5faXNWZXJ0aWNhbCgpKSB7CiAgICAgICAgICAgICAgICBudW1Td2F0Y2hlcyA9IE1hdGguZmxvb3IodGhpcy5oZWlnaHQoKSk7CiAgICAgICAgICAgICAgICB2YXIgbG9uZ2VzdFRleHRXaWR0aF8xID0gTWF0aC5tYXgodGV4dDBXaWR0aCwgdGV4dDFXaWR0aCk7CiAgICAgICAgICAgICAgICBwYWRkaW5nID0gKHRoaXMud2lkdGgoKSAtIGxvbmdlc3RUZXh0V2lkdGhfMSAtIDIgKiB0aGlzLl90ZXh0UGFkZGluZykgLyAyOwogICAgICAgICAgICAgICAgc3dhdGNoV2lkdGggPSBNYXRoLm1heCh0aGlzLndpZHRoKCkgLSBwYWRkaW5nIC0gMiAqIHRleHRQYWRkaW5nIC0gbG9uZ2VzdFRleHRXaWR0aF8xLCAwKTsKICAgICAgICAgICAgICAgIHN3YXRjaEhlaWdodCA9IDE7CiAgICAgICAgICAgICAgICBzd2F0Y2hZID0gZnVuY3Rpb24gKGQsIGkpIHsgcmV0dXJuIF90aGlzLmhlaWdodCgpIC0gKGkgKyAxKTsgfTsKICAgICAgICAgICAgICAgIHVwcGVyV3JpdGVPcHRpb25zLnlBbGlnbiA9ICJ0b3AiOwogICAgICAgICAgICAgICAgdXBwZXJMYWJlbFNoaWZ0LnkgPSAwOwogICAgICAgICAgICAgICAgbG93ZXJXcml0ZU9wdGlvbnMueUFsaWduID0gImJvdHRvbSI7CiAgICAgICAgICAgICAgICBsb3dlckxhYmVsU2hpZnQueSA9IDA7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fb3JpZW50YXRpb24gPT09ICJsZWZ0IikgewogICAgICAgICAgICAgICAgICAgIHN3YXRjaFggPSBmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gdGV4dFBhZGRpbmcgKyBsb25nZXN0VGV4dFdpZHRoXzEgKyB0ZXh0UGFkZGluZzsgfTsKICAgICAgICAgICAgICAgICAgICB1cHBlcldyaXRlT3B0aW9ucy54QWxpZ24gPSAicmlnaHQiOwogICAgICAgICAgICAgICAgICAgIHVwcGVyTGFiZWxTaGlmdC54ID0gLShwYWRkaW5nICsgc3dhdGNoV2lkdGggKyB0ZXh0UGFkZGluZyk7CiAgICAgICAgICAgICAgICAgICAgbG93ZXJXcml0ZU9wdGlvbnMueEFsaWduID0gInJpZ2h0IjsKICAgICAgICAgICAgICAgICAgICBsb3dlckxhYmVsU2hpZnQueCA9IC0ocGFkZGluZyArIHN3YXRjaFdpZHRoICsgdGV4dFBhZGRpbmcpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgc3dhdGNoWCA9IGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBwYWRkaW5nOyB9OwogICAgICAgICAgICAgICAgICAgIHVwcGVyV3JpdGVPcHRpb25zLnhBbGlnbiA9ICJsZWZ0IjsKICAgICAgICAgICAgICAgICAgICB1cHBlckxhYmVsU2hpZnQueCA9IHBhZGRpbmcgKyBzd2F0Y2hXaWR0aCArIHRleHRQYWRkaW5nOwogICAgICAgICAgICAgICAgICAgIGxvd2VyV3JpdGVPcHRpb25zLnhBbGlnbiA9ICJsZWZ0IjsKICAgICAgICAgICAgICAgICAgICBsb3dlckxhYmVsU2hpZnQueCA9IHBhZGRpbmcgKyBzd2F0Y2hXaWR0aCArIHRleHRQYWRkaW5nOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgYm91bmRpbmdCb3hBdHRyWyJ3aWR0aCJdID0gc3dhdGNoV2lkdGg7CiAgICAgICAgICAgICAgICBib3VuZGluZ0JveEF0dHJbImhlaWdodCJdID0gbnVtU3dhdGNoZXMgKiBzd2F0Y2hIZWlnaHQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBwYWRkaW5nID0gTWF0aC5tYXgodGV4dFBhZGRpbmcsICh0aGlzLmhlaWdodCgpIC0gdGV4dEhlaWdodCkgLyAyKTsKICAgICAgICAgICAgICAgIG51bVN3YXRjaGVzID0gTWF0aC5tYXgoTWF0aC5mbG9vcih0aGlzLndpZHRoKCkgLSB0ZXh0UGFkZGluZyAqIDQgLSB0ZXh0MFdpZHRoIC0gdGV4dDFXaWR0aCksIDApOwogICAgICAgICAgICAgICAgc3dhdGNoV2lkdGggPSAxOwogICAgICAgICAgICAgICAgc3dhdGNoSGVpZ2h0ID0gTWF0aC5tYXgoKHRoaXMuaGVpZ2h0KCkgLSAyICogcGFkZGluZyksIDApOwogICAgICAgICAgICAgICAgc3dhdGNoWCA9IGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBNYXRoLmZsb29yKHRleHQwV2lkdGggKyAyICogdGV4dFBhZGRpbmcpICsgaTsgfTsKICAgICAgICAgICAgICAgIHN3YXRjaFkgPSBmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gcGFkZGluZzsgfTsKICAgICAgICAgICAgICAgIHVwcGVyV3JpdGVPcHRpb25zLnhBbGlnbiA9ICJyaWdodCI7CiAgICAgICAgICAgICAgICB1cHBlckxhYmVsU2hpZnQueCA9IC10ZXh0UGFkZGluZzsKICAgICAgICAgICAgICAgIGxvd2VyV3JpdGVPcHRpb25zLnhBbGlnbiA9ICJsZWZ0IjsKICAgICAgICAgICAgICAgIGxvd2VyTGFiZWxTaGlmdC54ID0gdGV4dFBhZGRpbmc7CiAgICAgICAgICAgICAgICBib3VuZGluZ0JveEF0dHJbInkiXSA9IHBhZGRpbmc7CiAgICAgICAgICAgICAgICBib3VuZGluZ0JveEF0dHJbIndpZHRoIl0gPSBudW1Td2F0Y2hlcyAqIHN3YXRjaFdpZHRoOwogICAgICAgICAgICAgICAgYm91bmRpbmdCb3hBdHRyWyJoZWlnaHQiXSA9IHN3YXRjaEhlaWdodDsKICAgICAgICAgICAgfQogICAgICAgICAgICBib3VuZGluZ0JveEF0dHJbIngiXSA9IHN3YXRjaFgobnVsbCwgMCk7IC8vIHBvc2l0aW9uIG9mIHRoZSBmaXJzdCBzd2F0Y2gKICAgICAgICAgICAgdGhpcy5fdXBwZXJMYWJlbC50ZXh0KCIiKTsgLy8gY2xlYXIgdGhlIHVwcGVyIGxhYmVsCiAgICAgICAgICAgIHRoaXMuX3dyaXRlci53cml0ZSh0ZXh0MSwgdGhpcy53aWR0aCgpLCB0aGlzLmhlaWdodCgpLCB1cHBlcldyaXRlT3B0aW9ucywgdGhpcy5fdXBwZXJMYWJlbC5ub2RlKCkpOwogICAgICAgICAgICB2YXIgdXBwZXJUcmFuc2xhdGVTdHJpbmcgPSAidHJhbnNsYXRlKCIgKyB1cHBlckxhYmVsU2hpZnQueCArICIsICIgKyB1cHBlckxhYmVsU2hpZnQueSArICIpIjsKICAgICAgICAgICAgdGhpcy5fdXBwZXJMYWJlbC5hdHRyKCJ0cmFuc2Zvcm0iLCB1cHBlclRyYW5zbGF0ZVN0cmluZyk7CiAgICAgICAgICAgIHRoaXMuX2xvd2VyTGFiZWwudGV4dCgiIik7IC8vIGNsZWFyIHRoZSBsb3dlciBsYWJlbAogICAgICAgICAgICB0aGlzLl93cml0ZXIud3JpdGUodGV4dDAsIHRoaXMud2lkdGgoKSwgdGhpcy5oZWlnaHQoKSwgbG93ZXJXcml0ZU9wdGlvbnMsIHRoaXMuX2xvd2VyTGFiZWwubm9kZSgpKTsKICAgICAgICAgICAgdmFyIGxvd2VyVHJhbnNsYXRlU3RyaW5nID0gInRyYW5zbGF0ZSgiICsgbG93ZXJMYWJlbFNoaWZ0LnggKyAiLCAiICsgbG93ZXJMYWJlbFNoaWZ0LnkgKyAiKSI7CiAgICAgICAgICAgIHRoaXMuX2xvd2VyTGFiZWwuYXR0cigidHJhbnNmb3JtIiwgbG93ZXJUcmFuc2xhdGVTdHJpbmcpOwogICAgICAgICAgICB0aGlzLl9zd2F0Y2hCb3VuZGluZ0JveC5hdHRycyhib3VuZGluZ0JveEF0dHIpOwogICAgICAgICAgICB2YXIgdGlja3MgPSB0aGlzLl9nZW5lcmF0ZVRpY2tzKG51bVN3YXRjaGVzKTsKICAgICAgICAgICAgdmFyIHN3YXRjaGVzVXBkYXRlID0gdGhpcy5fc3dhdGNoQ29udGFpbmVyLnNlbGVjdEFsbCgicmVjdC5zd2F0Y2giKS5kYXRhKHRpY2tzKTsKICAgICAgICAgICAgdmFyIHJlY3RzID0gc3dhdGNoZXNVcGRhdGUuZW50ZXIoKS5hcHBlbmQoInJlY3QiKS5jbGFzc2VkKCJzd2F0Y2giLCB0cnVlKTsKICAgICAgICAgICAgdmFyIHN3YXRjaGVzID0gc3dhdGNoZXNVcGRhdGUubWVyZ2UocmVjdHMpOwogICAgICAgICAgICBzd2F0Y2hlc1VwZGF0ZS5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgIHN3YXRjaGVzLmF0dHJzKHsKICAgICAgICAgICAgICAgIGZpbGw6IGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBfdGhpcy5fc2NhbGUuc2NhbGUoZCk7IH0sCiAgICAgICAgICAgICAgICB3aWR0aDogc3dhdGNoV2lkdGgsCiAgICAgICAgICAgICAgICBoZWlnaHQ6IHN3YXRjaEhlaWdodCwKICAgICAgICAgICAgICAgIHg6IHN3YXRjaFgsCiAgICAgICAgICAgICAgICB5OiBzd2F0Y2hZLAogICAgICAgICAgICAgICAgInNoYXBlLXJlbmRlcmluZyI6ICJjcmlzcEVkZ2VzIiwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGlmIChjb25maWckMS5BRERfVElUTEVfRUxFTUVOVFMpIHsKICAgICAgICAgICAgICAgIHJlY3RzLmFwcGVuZCgidGl0bGUiKS50ZXh0KGZ1bmN0aW9uIChkKSB7IHJldHVybiBfdGhpcy5fZm9ybWF0dGVyKGQpOyB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEludGVycG9sYXRlZENvbG9yTGVnZW5kLl9ERUZBVUxUX05VTV9TV0FUQ0hFUyA9IDExOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byB0aGUgbGVnZW5kIGxhYmVscy4KICAgICAgICAgKi8KICAgICAgICBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZC5MRUdFTkRfTEFCRUxfQ0xBU1MgPSAibGVnZW5kLWxhYmVsIjsKICAgICAgICByZXR1cm4gSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQ7CiAgICB9KGNvbXBvbmVudC5Db21wb25lbnQpKTsKICAgIGV4cG9ydHMuSW50ZXJwb2xhdGVkQ29sb3JMZWdlbmQgPSBJbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZDsKICAgIH0pOwoKICAgIHZhciBsYWJlbCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIExhYmVsID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoTGFiZWwsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBMYWJlbCBpcyBhIENvbXBvbmVudCB0aGF0IGRpc3BsYXlzIGEgc2luZ2xlIGxpbmUgb2YgdGV4dC4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbZGlzcGxheVRleHQ9IiJdIFRoZSB0ZXh0IG9mIHRoZSBMYWJlbC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gW2FuZ2xlPTBdIFRoZSBhbmdsZSBvZiB0aGUgTGFiZWwgaW4gZGVncmVlcyAoLTkwLzAvOTApLiAwIGlzIGhvcml6b250YWwuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gTGFiZWwoZGlzcGxheVRleHQsIGFuZ2xlKSB7CiAgICAgICAgICAgIGlmIChkaXNwbGF5VGV4dCA9PT0gdm9pZCAwKSB7IGRpc3BsYXlUZXh0ID0gIiI7IH0KICAgICAgICAgICAgaWYgKGFuZ2xlID09PSB2b2lkIDApIHsgYW5nbGUgPSAwOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJsYWJlbCIpOwogICAgICAgICAgICBfdGhpcy50ZXh0KGRpc3BsYXlUZXh0KTsKICAgICAgICAgICAgX3RoaXMuYW5nbGUoYW5nbGUpOwogICAgICAgICAgICBfdGhpcy54QWxpZ25tZW50KCJjZW50ZXIiKS55QWxpZ25tZW50KCJjZW50ZXIiKTsKICAgICAgICAgICAgX3RoaXMuX3BhZGRpbmcgPSAwOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIExhYmVsLnByb3RvdHlwZS5yZXF1ZXN0ZWRTcGFjZSA9IGZ1bmN0aW9uIChvZmZlcmVkV2lkdGgsIG9mZmVyZWRIZWlnaHQpIHsKICAgICAgICAgICAgdmFyIGRlc2lyZWRXSCA9IHRoaXMuX21lYXN1cmVyLm1lYXN1cmUodGhpcy5fdGV4dCk7CiAgICAgICAgICAgIHZhciBkZXNpcmVkV2lkdGggPSAodGhpcy5hbmdsZSgpID09PSAwID8gZGVzaXJlZFdILndpZHRoIDogZGVzaXJlZFdILmhlaWdodCkgKyAyICogdGhpcy5wYWRkaW5nKCk7CiAgICAgICAgICAgIHZhciBkZXNpcmVkSGVpZ2h0ID0gKHRoaXMuYW5nbGUoKSA9PT0gMCA/IGRlc2lyZWRXSC5oZWlnaHQgOiBkZXNpcmVkV0gud2lkdGgpICsgMiAqIHRoaXMucGFkZGluZygpOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbWluV2lkdGg6IGRlc2lyZWRXaWR0aCwKICAgICAgICAgICAgICAgIG1pbkhlaWdodDogZGVzaXJlZEhlaWdodCwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIExhYmVsLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3RleHRDb250YWluZXIgPSB0aGlzLmNvbnRlbnQoKS5hcHBlbmQoImciKTsKICAgICAgICAgICAgdmFyIGNvbnRleHQgPSBuZXcgc3JjJDEuU3ZnQ29udGV4dCh0aGlzLl90ZXh0Q29udGFpbmVyLm5vZGUoKSk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIoY29udGV4dCk7CiAgICAgICAgICAgIHRoaXMuX3dyYXBwZXIgPSBuZXcgc3JjJDEuV3JhcHBlcigpOwogICAgICAgICAgICB0aGlzLl93cml0ZXIgPSBuZXcgc3JjJDEuV3JpdGVyKHRoaXMuX21lYXN1cmVyLCBjb250ZXh0LCB0aGlzLl93cmFwcGVyKTsKICAgICAgICAgICAgdGhpcy50ZXh0KHRoaXMuX3RleHQpOwogICAgICAgIH07CiAgICAgICAgTGFiZWwucHJvdG90eXBlLnRleHQgPSBmdW5jdGlvbiAoZGlzcGxheVRleHQpIHsKICAgICAgICAgICAgaWYgKGRpc3BsYXlUZXh0ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl90ZXh0OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgaWYgKHR5cGVvZiBkaXNwbGF5VGV4dCAhPT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIkxhYmVsLnRleHQoKSBvbmx5IHRha2VzIHN0cmluZ3MgYXMgaW5wdXQiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3RleHQgPSBkaXNwbGF5VGV4dDsKICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTGFiZWwucHJvdG90eXBlLmFuZ2xlID0gZnVuY3Rpb24gKGFuZ2xlKSB7CiAgICAgICAgICAgIGlmIChhbmdsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5nbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBhbmdsZSAlPSAzNjA7CiAgICAgICAgICAgICAgICBpZiAoYW5nbGUgPiAxODApIHsKICAgICAgICAgICAgICAgICAgICBhbmdsZSAtPSAzNjA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChhbmdsZSA8IC0xODApIHsKICAgICAgICAgICAgICAgICAgICBhbmdsZSArPSAzNjA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoYW5nbGUgPT09IC05MCB8fCBhbmdsZSA9PT0gMCB8fCBhbmdsZSA9PT0gOTApIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9hbmdsZSA9IGFuZ2xlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKGFuZ2xlICsgIiBpcyBub3QgYSB2YWxpZCBhbmdsZSBmb3IgTGFiZWwiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTGFiZWwucHJvdG90eXBlLnBhZGRpbmcgPSBmdW5jdGlvbiAocGFkQW1vdW50KSB7CiAgICAgICAgICAgIGlmIChwYWRBbW91bnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3BhZGRpbmc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBwYWRBbW91bnQgPSArcGFkQW1vdW50OwogICAgICAgICAgICAgICAgaWYgKHBhZEFtb3VudCA8IDApIHsKICAgICAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IocGFkQW1vdW50ICsgIiBpcyBub3QgYSB2YWxpZCBwYWRkaW5nIHZhbHVlLiBDYW5ub3QgYmUgbGVzcyB0aGFuIDAuIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9wYWRkaW5nID0gcGFkQW1vdW50OwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMYWJlbC5wcm90b3R5cGUuZml4ZWRXaWR0aCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfTsKICAgICAgICBMYWJlbC5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgTGFiZWwucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIC8vIEhBQ0tIQUNLIFR5cGVzZXR0YWJsZS5yZW1vdmUgZXhpc3RpbmcgY29udGVudCAtICMyMSBvbiBUeXBlc2V0dGFibGUuCiAgICAgICAgICAgIHRoaXMuX3RleHRDb250YWluZXIuc2VsZWN0QWxsKCJnIikucmVtb3ZlKCk7CiAgICAgICAgICAgIHZhciB0ZXh0TWVhc3VyZW1lbnQgPSB0aGlzLl9tZWFzdXJlci5tZWFzdXJlKHRoaXMuX3RleHQpOwogICAgICAgICAgICB2YXIgaGVpZ2h0UGFkZGluZyA9IE1hdGgubWF4KE1hdGgubWluKCh0aGlzLmhlaWdodCgpIC0gdGV4dE1lYXN1cmVtZW50LmhlaWdodCkgLyAyLCB0aGlzLnBhZGRpbmcoKSksIDApOwogICAgICAgICAgICB2YXIgd2lkdGhQYWRkaW5nID0gTWF0aC5tYXgoTWF0aC5taW4oKHRoaXMud2lkdGgoKSAtIHRleHRNZWFzdXJlbWVudC53aWR0aCkgLyAyLCB0aGlzLnBhZGRpbmcoKSksIDApOwogICAgICAgICAgICB0aGlzLl90ZXh0Q29udGFpbmVyLmF0dHIoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIHdpZHRoUGFkZGluZyArICIsIiArIGhlaWdodFBhZGRpbmcgKyAiKSIpOwogICAgICAgICAgICB2YXIgd3JpdGVXaWR0aCA9IHRoaXMud2lkdGgoKSAtIDIgKiB3aWR0aFBhZGRpbmc7CiAgICAgICAgICAgIHZhciB3cml0ZUhlaWdodCA9IHRoaXMuaGVpZ2h0KCkgLSAyICogaGVpZ2h0UGFkZGluZzsKICAgICAgICAgICAgdmFyIHdyaXRlT3B0aW9ucyA9IHsKICAgICAgICAgICAgICAgIHhBbGlnbjogdGhpcy54QWxpZ25tZW50KCksCiAgICAgICAgICAgICAgICB5QWxpZ246IHRoaXMueUFsaWdubWVudCgpLAogICAgICAgICAgICAgICAgdGV4dFJvdGF0aW9uOiB0aGlzLmFuZ2xlKCksCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX3dyaXRlci53cml0ZSh0aGlzLl90ZXh0LCB3cml0ZVdpZHRoLCB3cml0ZUhlaWdodCwgd3JpdGVPcHRpb25zKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBMYWJlbC5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9tZWFzdXJlci5yZXNldCgpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIExhYmVsOwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLkxhYmVsID0gTGFiZWw7CiAgICB2YXIgVGl0bGVMYWJlbCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFRpdGxlTGFiZWwsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFt0ZXh0XQogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbYW5nbGVdIE9uZSBvZiAtOTAvMC85MC4gMCBpcyBob3Jpem9udGFsLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFRpdGxlTGFiZWwodGV4dCwgYW5nbGUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcywgdGV4dCwgYW5nbGUpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKFRpdGxlTGFiZWwuVElUTEVfTEFCRUxfQ0xBU1MpOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFRpdGxlTGFiZWwuVElUTEVfTEFCRUxfQ0xBU1MgPSAidGl0bGUtbGFiZWwiOwogICAgICAgIHJldHVybiBUaXRsZUxhYmVsOwogICAgfShMYWJlbCkpOwogICAgZXhwb3J0cy5UaXRsZUxhYmVsID0gVGl0bGVMYWJlbDsKICAgIHZhciBBeGlzTGFiZWwgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhBeGlzTGFiZWwsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFt0ZXh0XQogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbYW5nbGVdIE9uZSBvZiAtOTAvMC85MC4gMCBpcyBob3Jpem9udGFsLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIEF4aXNMYWJlbCh0ZXh0LCBhbmdsZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzLCB0ZXh0LCBhbmdsZSkgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoQXhpc0xhYmVsLkFYSVNfTEFCRUxfQ0xBU1MpOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIEF4aXNMYWJlbC5BWElTX0xBQkVMX0NMQVNTID0gImF4aXMtbGFiZWwiOwogICAgICAgIHJldHVybiBBeGlzTGFiZWw7CiAgICB9KExhYmVsKSk7CiAgICBleHBvcnRzLkF4aXNMYWJlbCA9IEF4aXNMYWJlbDsKICAgIH0pOwoKICAgIHZhciBzeW1ib2xGYWN0b3JpZXMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICBmdW5jdGlvbiBjaXJjbGUoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbENpcmNsZSkuc2l6ZShNYXRoLlBJICogTWF0aC5wb3coc3ltYm9sU2l6ZSAvIDIsIDIpKTsKICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5jaXJjbGUgPSBjaXJjbGU7CiAgICBmdW5jdGlvbiBzcXVhcmUoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbFNxdWFyZSkuc2l6ZShNYXRoLnBvdyhzeW1ib2xTaXplLCAyKSk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuc3F1YXJlID0gc3F1YXJlOwogICAgZnVuY3Rpb24gY3Jvc3MoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbENyb3NzKS5zaXplKCg1IC8gOSkgKiBNYXRoLnBvdyhzeW1ib2xTaXplLCAyKSk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMuY3Jvc3MgPSBjcm9zczsKICAgIGZ1bmN0aW9uIGRpYW1vbmQoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbERpYW1vbmQpLnNpemUoTWF0aC50YW4oTWF0aC5QSSAvIDYpICogTWF0aC5wb3coc3ltYm9sU2l6ZSwgMikgLyAyKTsKICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5kaWFtb25kID0gZGlhbW9uZDsKICAgIGZ1bmN0aW9uIHRyaWFuZ2xlKCkgewogICAgICAgIHJldHVybiBmdW5jdGlvbiAoc3ltYm9sU2l6ZSkgewogICAgICAgICAgICByZXR1cm4gZDMuc3ltYm9sKCkudHlwZShkMy5zeW1ib2xUcmlhbmdsZSkuc2l6ZShNYXRoLnNxcnQoMykgKiBNYXRoLnBvdyhzeW1ib2xTaXplIC8gMiwgMikpOwogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLnRyaWFuZ2xlID0gdHJpYW5nbGU7CiAgICAvLyBjb3BpZWQgZnJvbSBodHRwczovL2dpdGh1Yi5jb20vZDMvZDMtc2hhcGUvYmxvYi9lMmU1NzcyMjAwNGFjYmE3NTRlZDllZGZmMDIwMjgyNjgyNDUwYzVjL3NyYy9zeW1ib2wvc3Rhci5qcyNMMwogICAgdmFyIGthID0gMC44OTA4MTMwOTE1MjkyODUyMjgxMDsKICAgIGZ1bmN0aW9uIHN0YXIoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbFN0YXIpLnNpemUoa2EgKiBNYXRoLnBvdyhzeW1ib2xTaXplIC8gMiwgMikpOwogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLnN0YXIgPSBzdGFyOwogICAgLy8gY29waWVkIGZyb20gaHR0cHM6Ly9naXRodWIuY29tL2QzL2QzLXNoYXBlL2Jsb2IvYzM1YjIzMDNlYjQ4MzZhYmEzMTcxNjQyZjAxYzI2NTNlNDIyOGI5Yy9zcmMvc3ltYm9sL3d5ZS5qcyNMMgogICAgdmFyIGEgPSAoKDEgLyBNYXRoLnNxcnQoMTIpKSAvIDIgKyAxKSAqIDM7CiAgICBmdW5jdGlvbiB3eWUoKSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChzeW1ib2xTaXplKSB7CiAgICAgICAgICAgIHJldHVybiBkMy5zeW1ib2woKS50eXBlKGQzLnN5bWJvbFd5ZSkuc2l6ZShhICogTWF0aC5wb3coc3ltYm9sU2l6ZSAvIDIuNCwgMikpOwogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLnd5ZSA9IHd5ZTsKICAgIH0pOwoKICAgIHZhciBsZWdlbmQgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgoKCgogICAgLyoqCiAgICAgKiBUaGUgTGVnZW5kJ3Mgcm93IHJlcHJlc2VudGF0aW9ucy4gU3RvcmVzIHBvc2l0aW9uaW5nIGluZm9ybWF0aW9uCiAgICAgKiBhbmQgY29sdW1uIGRhdGEuCiAgICAgKi8KICAgIHZhciBMZWdlbmRSb3cgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gTGVnZW5kUm93KAogICAgICAgIC8qKgogICAgICAgICAqIENvbHVtbnMgd2l0aGluIHRoZSByb3cKICAgICAgICAgKiBAcGFyYW0ge0xlZ2VuZENvbHVtbjxhbnk+W119IGNvbHVtbnMKICAgICAgICAgKi8KICAgICAgICBjb2x1bW5zLCAKICAgICAgICAvKioKICAgICAgICAgKiBQYWRkaW5nIGFwcGxpZWQgYmVsb3cgdGhlIHJvdy4gQWZmZWN0cyB0aGUgc3BhY2luZyBiZXR3ZWVuIHJvd3MuIERlZmF1bHRzIHRvIDAuCiAgICAgICAgICogQHBhcmFtIHtib3R0b21QYWRkaW5nfSBudW1iZXIKICAgICAgICAgKi8KICAgICAgICBib3R0b21QYWRkaW5nLCAKICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBtYXhpbXVtIGFsbG93YWJsZSB3aWR0aCBvZiB0aGlzIGNvbHVtbi4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gbWF4V2lkdGgKICAgICAgICAgKi8KICAgICAgICBtYXhXaWR0aCkgewogICAgICAgICAgICBpZiAoY29sdW1ucyA9PT0gdm9pZCAwKSB7IGNvbHVtbnMgPSBbXTsgfQogICAgICAgICAgICBpZiAoYm90dG9tUGFkZGluZyA9PT0gdm9pZCAwKSB7IGJvdHRvbVBhZGRpbmcgPSAwOyB9CiAgICAgICAgICAgIGlmIChtYXhXaWR0aCA9PT0gdm9pZCAwKSB7IG1heFdpZHRoID0gSW5maW5pdHk7IH0KICAgICAgICAgICAgdGhpcy5jb2x1bW5zID0gY29sdW1uczsKICAgICAgICAgICAgdGhpcy5ib3R0b21QYWRkaW5nID0gYm90dG9tUGFkZGluZzsKICAgICAgICAgICAgdGhpcy5tYXhXaWR0aCA9IG1heFdpZHRoOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBBZGRzIGEgY29sdW1uIHRvIHRoZSBsaXN0IG9mIGNvbHVtbnMgd2l0aGluIHRoZSByb3cuIE1heSByZWFkanVzdCB0aGUgc2l6ZSBvZiB0aGUKICAgICAgICAgKiBjb2x1bW4gdG8gZml0IHdpdGhpbiB0aGUgcm93CiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0xlZ2VuZENvbHVtbjxhbnk+fSBjb2x1bW4KICAgICAgICAgKi8KICAgICAgICBMZWdlbmRSb3cucHJvdG90eXBlLmFkZENvbHVtbiA9IGZ1bmN0aW9uIChjb2x1bW4pIHsKICAgICAgICAgICAgdmFyIGRlc2lyZWRDb2x1bW5XaWR0aCA9IGNvbHVtbi53aWR0aDsKICAgICAgICAgICAgLy8gY2hvb3NlIHRoZSBzbWFsbGVyIG9mIDEpIHJlbWFpbmluZyBzcGFjZSwgMikgZGVzaXJlZCB3aWR0aAogICAgICAgICAgICB2YXIgd2lkdGhSZW1haW5pbmcgPSB0aGlzLmdldFdpZHRoQXZhaWxhYmxlKCk7CiAgICAgICAgICAgIGNvbHVtbi53aWR0aCA9IE1hdGgubWluKHdpZHRoUmVtYWluaW5nLCBkZXNpcmVkQ29sdW1uV2lkdGgpOwogICAgICAgICAgICB0aGlzLmNvbHVtbnMucHVzaChjb2x1bW4pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgYm91bmRzIHRoZSBjb2x1bW4sIHJlbGF0aXZlIHRvIHRoZSByb3cuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGNvbHVtbkluZGV4IFRoZSBpbmRleCBvZiB0aGUgY29sdW1uIGluIHF1ZXN0aW9uCiAgICAgICAgICogQHJldHVybnMge0JvdW5kc30gYm91bmRzCiAgICAgICAgICovCiAgICAgICAgTGVnZW5kUm93LnByb3RvdHlwZS5nZXRCb3VuZHMgPSBmdW5jdGlvbiAoY29sdW1uSW5kZXgpIHsKICAgICAgICAgICAgdmFyIGNvbHVtbiA9IHRoaXMuY29sdW1uc1tjb2x1bW5JbmRleF07CiAgICAgICAgICAgIHZhciBjb2x1bW5YT2Zmc2V0ID0gMDsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBjb2x1bW5JbmRleDsgaSsrKSB7CiAgICAgICAgICAgICAgICBjb2x1bW5YT2Zmc2V0ICs9IHRoaXMuY29sdW1uc1tpXS53aWR0aDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgdG9wTGVmdDogeyB4OiBjb2x1bW5YT2Zmc2V0LCB5OiAwIH0sCiAgICAgICAgICAgICAgICBib3R0b21SaWdodDogewogICAgICAgICAgICAgICAgICAgIHg6IGNvbHVtblhPZmZzZXQgKyBjb2x1bW4ud2lkdGgsCiAgICAgICAgICAgICAgICAgICAgeTogY29sdW1uLmhlaWdodCwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBoZWlnaHQgb2YgdGhlIHJvdywgaW5jbHVkaW5nIHRoZSBib3R0b21QYWRkaW5nLgogICAgICAgICAqIEByZXR1cm4ge251bWJlcn0gaGVpZ2h0CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kUm93LnByb3RvdHlwZS5nZXRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGgubWF4KHRoaXMuY29sdW1ucy5tYXAoZnVuY3Rpb24gKF9hKSB7CiAgICAgICAgICAgICAgICB2YXIgaGVpZ2h0ID0gX2EuaGVpZ2h0OwogICAgICAgICAgICAgICAgcmV0dXJuIGhlaWdodDsKICAgICAgICAgICAgfSksIDApICsgdGhpcy5ib3R0b21QYWRkaW5nOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgY3VycmVudCB3aWR0aCBvZiB0aGUgcm93IGNvbnN0cmFpbmVkIGJ5IG1heFdpZHRoLCBpZiBzZXQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gd2lkdGgKICAgICAgICAgKi8KICAgICAgICBMZWdlbmRSb3cucHJvdG90eXBlLmdldFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gTWF0aC5taW4odGhpcy5jb2x1bW5zLnJlZHVjZShmdW5jdGlvbiAoc3VtLCBfYSkgewogICAgICAgICAgICAgICAgdmFyIHdpZHRoID0gX2Eud2lkdGg7CiAgICAgICAgICAgICAgICByZXR1cm4gc3VtICsgd2lkdGg7CiAgICAgICAgICAgIH0sIDApLCB0aGlzLm1heFdpZHRoKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIHJlbWFpbmluZyB3aWR0aCBhdmFpbGFibGUgaW4gdGhlIHJvdyBiYXNlZCBvbiB0aGUgbWF4aW11bQogICAgICAgICAqIHdpZHRoIG9mIHRoaXMgcm93LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IHdpZHRoUmVtYWluaW5nCiAgICAgICAgICovCiAgICAgICAgTGVnZW5kUm93LnByb3RvdHlwZS5nZXRXaWR0aEF2YWlsYWJsZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHdpZHRoQ29uc3VtZWQgPSB0aGlzLmdldFdpZHRoKCk7CiAgICAgICAgICAgIHJldHVybiBNYXRoLm1heCh0aGlzLm1heFdpZHRoIC0gd2lkdGhDb25zdW1lZCwgMCk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gTGVnZW5kUm93OwogICAgfSgpKTsKICAgIC8qKgogICAgICogU3RvcmVzIExlZ2VuZFJvd3MuIFVzZWZ1bCBmb3IgY2FsY3VsYXRpbmcgYW5kIG1haW50YWluaW5nCiAgICAgKiBwb3NpdGlvbmluZyBpbmZvcm1hdGlvbiBhYm91dCB0aGUgTGVnZW5kLgogICAgICovCiAgICB2YXIgTGVnZW5kVGFibGUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gTGVnZW5kVGFibGUobWF4V2lkdGgsIG1heEhlaWdodCwgcGFkZGluZywgcm93cykgewogICAgICAgICAgICBpZiAobWF4V2lkdGggPT09IHZvaWQgMCkgeyBtYXhXaWR0aCA9IEluZmluaXR5OyB9CiAgICAgICAgICAgIGlmIChtYXhIZWlnaHQgPT09IHZvaWQgMCkgeyBtYXhIZWlnaHQgPSBJbmZpbml0eTsgfQogICAgICAgICAgICBpZiAocGFkZGluZyA9PT0gdm9pZCAwKSB7IHBhZGRpbmcgPSAwOyB9CiAgICAgICAgICAgIGlmIChyb3dzID09PSB2b2lkIDApIHsgcm93cyA9IFtdOyB9CiAgICAgICAgICAgIHRoaXMubWF4V2lkdGggPSBtYXhXaWR0aDsKICAgICAgICAgICAgdGhpcy5tYXhIZWlnaHQgPSBtYXhIZWlnaHQ7CiAgICAgICAgICAgIHRoaXMucGFkZGluZyA9IHBhZGRpbmc7CiAgICAgICAgICAgIHRoaXMucm93cyA9IHJvd3M7CiAgICAgICAgfQogICAgICAgIExlZ2VuZFRhYmxlLnByb3RvdHlwZS5hZGRSb3cgPSBmdW5jdGlvbiAocm93KSB7CiAgICAgICAgICAgIHJvdy5tYXhXaWR0aCA9IHRoaXMubWF4V2lkdGggLSB0aGlzLnBhZGRpbmcgKiAyOwogICAgICAgICAgICB0aGlzLnJvd3MucHVzaChyb3cpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgYm91bmRzIG9mIHRoZSBjb2x1bW4gcmVsYXRpdmUgdG8gdGhlIHBhcmVudCBhbmQgc2libGluZ3Mgb2YgdGhlCiAgICAgICAgICogY29sdW1uLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHJvd0luZGV4IFRoZSBwYXJlbnQgcm93IGNvbnRhaW5pbmcgdGhlIGRlc2lyZWQgY29sdW1uLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBjb2x1bW5JbmRleCBUaGUgY29sdW1uIHRvIGNhbGN1bGF0ZSBib3VuZHMuCiAgICAgICAgICogQHJldHVybnMge0JvdW5kc30KICAgICAgICAgKi8KICAgICAgICBMZWdlbmRUYWJsZS5wcm90b3R5cGUuZ2V0Q29sdW1uQm91bmRzID0gZnVuY3Rpb24gKHJvd0luZGV4LCBjb2x1bW5JbmRleCkgewogICAgICAgICAgICB2YXIgcm93Qm91bmRzID0gdGhpcy5nZXRSb3dCb3VuZHMocm93SW5kZXgpOwogICAgICAgICAgICB2YXIgY29sdW1uQm91bmRzID0gdGhpcy5yb3dzW3Jvd0luZGV4XS5nZXRCb3VuZHMoY29sdW1uSW5kZXgpOwogICAgICAgICAgICBjb2x1bW5Cb3VuZHMudG9wTGVmdC54ICs9IHJvd0JvdW5kcy50b3BMZWZ0Lng7CiAgICAgICAgICAgIGNvbHVtbkJvdW5kcy5ib3R0b21SaWdodC54ICs9IHJvd0JvdW5kcy50b3BMZWZ0Lng7CiAgICAgICAgICAgIGNvbHVtbkJvdW5kcy50b3BMZWZ0LnkgKz0gcm93Qm91bmRzLnRvcExlZnQueTsKICAgICAgICAgICAgY29sdW1uQm91bmRzLmJvdHRvbVJpZ2h0LnkgKz0gcm93Qm91bmRzLnRvcExlZnQueTsKICAgICAgICAgICAgcmV0dXJuIGNvbHVtbkJvdW5kczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIGJvdW5kcyByZWxhdGl2ZSB0byB0aGUgcGFyZW50IGFuZCBzaWJsaW5ncyBvZiB0aGUgcm93LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHJvd0luZGV4IFRoZSByb3cgdG8gY2FsY3VsYXRlIGJvdW5kcwogICAgICAgICAqIEByZXR1cm5zIHtCb3VuZHN9CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kVGFibGUucHJvdG90eXBlLmdldFJvd0JvdW5kcyA9IGZ1bmN0aW9uIChyb3dJbmRleCkgewogICAgICAgICAgICB2YXIgcm93WE9mZnNldCA9IHRoaXMucGFkZGluZzsKICAgICAgICAgICAgdmFyIHJvd1lPZmZzZXQgPSB0aGlzLnBhZGRpbmc7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcm93SW5kZXg7IGkrKykgewogICAgICAgICAgICAgICAgcm93WU9mZnNldCArPSB0aGlzLnJvd3NbaV0uZ2V0SGVpZ2h0KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHJvd0JvdW5kcyA9IHsKICAgICAgICAgICAgICAgIHRvcExlZnQ6IHsgeDogcm93WE9mZnNldCwgeTogcm93WU9mZnNldCB9LAogICAgICAgICAgICAgICAgYm90dG9tUmlnaHQ6IHsKICAgICAgICAgICAgICAgICAgICB4OiByb3dYT2Zmc2V0ICsgdGhpcy5yb3dzW3Jvd0luZGV4XS5nZXRXaWR0aCgpLAogICAgICAgICAgICAgICAgICAgIHk6IHJvd1lPZmZzZXQgKyB0aGlzLnJvd3Nbcm93SW5kZXhdLmdldEhlaWdodCgpLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIHJvd0JvdW5kczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIGhlaWdodCBvZiB0aGUgVGFibGUsIGNvbnN0cmFpbmVkIGJ5IGEgbWF4aW11bSBoZWlnaHQsIGlmIHNldC4KICAgICAgICAgKiBUaGUgaGVpZ2h0IGluY2x1ZGVzIHRoZSBwYWRkaW5nLCBpZiBzZXQuCiAgICAgICAgICogQHJldHVybnMge251bWJlcn0gaGVpZ2h0CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kVGFibGUucHJvdG90eXBlLmdldEhlaWdodCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIE1hdGgubWluKHRoaXMucm93cy5yZWR1Y2UoZnVuY3Rpb24gKHN1bSwgcm93KSB7IHJldHVybiBzdW0gKyByb3cuZ2V0SGVpZ2h0KCk7IH0sIDApICsgdGhpcy5wYWRkaW5nICogMiwgdGhpcy5tYXhIZWlnaHQpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgd2lkdGggb2YgdGhlIHRhYmxlLCBjb25zdHJhaW5lZCBieSB0aGUgbWF4aW11bSB3aWR0aCwgaWYgc2V0LgogICAgICAgICAqIFRoZSB3aWR0aCBpbmNsdWRlcyB0aGUgcGFkZGluZywgaWYgc2V0LgogICAgICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IHdpZHRoCiAgICAgICAgICovCiAgICAgICAgTGVnZW5kVGFibGUucHJvdG90eXBlLmdldFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gTWF0aC5taW4odXRpbHMkMS5NYXRoLm1heCh0aGlzLnJvd3MubWFwKGZ1bmN0aW9uIChyb3cpIHsgcmV0dXJuIHJvdy5nZXRXaWR0aCgpOyB9KSwgMCkgKyB0aGlzLnBhZGRpbmcgKiAyLCB0aGlzLm1heFdpZHRoKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBMZWdlbmRUYWJsZTsKICAgIH0oKSk7CiAgICB2YXIgTGVnZW5kID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoTGVnZW5kLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBMZWdlbmQgY29uc2lzdHMgb2YgYSBzZXJpZXMgb2YgZW50cmllcywgZWFjaCB3aXRoIGEgY29sb3IgYW5kIGxhYmVsIHRha2VuIGZyb20gdGhlIENvbG9yIFNjYWxlLgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtTY2FsZS5Db2xvcn0gc2NhbGUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBMZWdlbmQoY29sb3JTY2FsZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fcGFkZGluZyA9IDU7CiAgICAgICAgICAgIF90aGlzLl9yb3dCb3R0b21QYWRkaW5nID0gMzsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoImxlZ2VuZCIpOwogICAgICAgICAgICBfdGhpcy5tYXhFbnRyaWVzUGVyUm93KDEpOwogICAgICAgICAgICBpZiAoY29sb3JTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIkxlZ2VuZCByZXF1aXJlcyBhIGNvbG9yU2NhbGUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBfdGhpcy5fY29sb3JTY2FsZSA9IGNvbG9yU2NhbGU7CiAgICAgICAgICAgIF90aGlzLl9yZWRyYXdDYWxsYmFjayA9IGZ1bmN0aW9uIChzY2FsZSkgeyByZXR1cm4gX3RoaXMucmVkcmF3KCk7IH07CiAgICAgICAgICAgIF90aGlzLl9jb2xvclNjYWxlLm9uVXBkYXRlKF90aGlzLl9yZWRyYXdDYWxsYmFjayk7CiAgICAgICAgICAgIF90aGlzLl9mb3JtYXR0ZXIgPSBmb3JtYXR0ZXJzLmlkZW50aXR5KCk7CiAgICAgICAgICAgIF90aGlzLm1heExpbmVzUGVyRW50cnkoMSk7CiAgICAgICAgICAgIF90aGlzLnhBbGlnbm1lbnQoInJpZ2h0IikueUFsaWdubWVudCgidG9wIik7CiAgICAgICAgICAgIF90aGlzLmNvbXBhcmF0b3IoZnVuY3Rpb24gKGEsIGIpIHsKICAgICAgICAgICAgICAgIHZhciBmb3JtYXR0ZWRUZXh0ID0gX3RoaXMuX2NvbG9yU2NhbGUuZG9tYWluKCkuc2xpY2UoKS5tYXAoZnVuY3Rpb24gKGQpIHsgcmV0dXJuIF90aGlzLl9mb3JtYXR0ZXIoZCk7IH0pOwogICAgICAgICAgICAgICAgcmV0dXJuIGZvcm1hdHRlZFRleHQuaW5kZXhPZihhKSAtIGZvcm1hdHRlZFRleHQuaW5kZXhPZihiKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIF90aGlzLl9zeW1ib2xGYWN0b3J5QWNjZXNzb3IgPSBmdW5jdGlvbiAoKSB7IHJldHVybiBzeW1ib2xGYWN0b3JpZXMuY2lyY2xlKCk7IH07CiAgICAgICAgICAgIF90aGlzLl9zeW1ib2xPcGFjaXR5QWNjZXNzb3IgPSBmdW5jdGlvbiAoKSB7IHJldHVybiAxOyB9OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIExlZ2VuZC5wcm90b3R5cGUuX3NldHVwID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgZmFrZUxlZ2VuZFJvdyA9IHRoaXMuY29udGVudCgpLmFwcGVuZCgiZyIpLmNsYXNzZWQoTGVnZW5kLkxFR0VORF9ST1dfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB2YXIgZmFrZUxlZ2VuZEVudHJ5ID0gZmFrZUxlZ2VuZFJvdy5hcHBlbmQoImciKS5jbGFzc2VkKExlZ2VuZC5MRUdFTkRfRU5UUllfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICBmYWtlTGVnZW5kRW50cnkuYXBwZW5kKCJ0ZXh0Iik7CiAgICAgICAgICAgIHZhciBjb250ZXh0ID0gbmV3IHNyYyQxLlN2Z0NvbnRleHQoZmFrZUxlZ2VuZFJvdy5ub2RlKCksIG51bGwsIGNvbmZpZyQxLkFERF9USVRMRV9FTEVNRU5UUyk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIoY29udGV4dCk7CiAgICAgICAgICAgIHRoaXMuX3dyYXBwZXIgPSBuZXcgc3JjJDEuV3JhcHBlcigpLm1heExpbmVzKHRoaXMubWF4TGluZXNQZXJFbnRyeSgpKTsKICAgICAgICAgICAgdGhpcy5fd3JpdGVyID0gbmV3IHNyYyQxLldyaXRlcih0aGlzLl9tZWFzdXJlciwgY29udGV4dCwgdGhpcy5fd3JhcHBlcik7CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLmZvcm1hdHRlciA9IGZ1bmN0aW9uIChmb3JtYXR0ZXIpIHsKICAgICAgICAgICAgaWYgKGZvcm1hdHRlciA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZm9ybWF0dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Zvcm1hdHRlciA9IGZvcm1hdHRlcjsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLm1heEVudHJpZXNQZXJSb3cgPSBmdW5jdGlvbiAobWF4RW50cmllc1BlclJvdykgewogICAgICAgICAgICBpZiAobWF4RW50cmllc1BlclJvdyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWF4RW50cmllc1BlclJvdzsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heEVudHJpZXNQZXJSb3cgPSBtYXhFbnRyaWVzUGVyUm93OwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLm1heExpbmVzUGVyRW50cnkgPSBmdW5jdGlvbiAobWF4TGluZXNQZXJFbnRyeSkgewogICAgICAgICAgICBpZiAobWF4TGluZXNQZXJFbnRyeSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWF4TGluZXNQZXJFbnRyeTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heExpbmVzUGVyRW50cnkgPSBtYXhMaW5lc1BlckVudHJ5OwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLm1heFdpZHRoID0gZnVuY3Rpb24gKG1heFdpZHRoKSB7CiAgICAgICAgICAgIGlmIChtYXhXaWR0aCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWF4V2lkdGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9tYXhXaWR0aCA9IG1heFdpZHRoOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLmNvbXBhcmF0b3IgPSBmdW5jdGlvbiAoY29tcGFyYXRvcikgewogICAgICAgICAgICBpZiAoY29tcGFyYXRvciA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fY29tcGFyYXRvcjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbXBhcmF0b3IgPSBjb21wYXJhdG9yOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMZWdlbmQucHJvdG90eXBlLmNvbG9yU2NhbGUgPSBmdW5jdGlvbiAoY29sb3JTY2FsZSkgewogICAgICAgICAgICBpZiAoY29sb3JTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jb2xvclNjYWxlLm9mZlVwZGF0ZSh0aGlzLl9yZWRyYXdDYWxsYmFjayk7CiAgICAgICAgICAgICAgICB0aGlzLl9jb2xvclNjYWxlID0gY29sb3JTY2FsZTsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbG9yU2NhbGUub25VcGRhdGUodGhpcy5fcmVkcmF3Q2FsbGJhY2spOwogICAgICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbG9yU2NhbGU7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIExlZ2VuZC5wcm90b3R5cGUuZGVzdHJveSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5kZXN0cm95LmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2NvbG9yU2NhbGUub2ZmVXBkYXRlKHRoaXMuX3JlZHJhd0NhbGxiYWNrKTsKICAgICAgICB9OwogICAgICAgIExlZ2VuZC5wcm90b3R5cGUuX2J1aWxkTGVnZW5kVGFibGUgPSBmdW5jdGlvbiAod2lkdGgsIGhlaWdodCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgdGV4dEhlaWdodCA9IHRoaXMuX21lYXN1cmVyLm1lYXN1cmUoKS5oZWlnaHQ7CiAgICAgICAgICAgIHZhciB0YWJsZSA9IG5ldyBMZWdlbmRUYWJsZSh3aWR0aCwgaGVpZ2h0LCB0aGlzLl9wYWRkaW5nKTsKICAgICAgICAgICAgdmFyIGVudHJ5TmFtZXMgPSB0aGlzLl9jb2xvclNjYWxlLmRvbWFpbigpLnNsaWNlKCkuc29ydChmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gX3RoaXMuX2NvbXBhcmF0b3IoX3RoaXMuX2Zvcm1hdHRlcihhKSwgX3RoaXMuX2Zvcm1hdHRlcihiKSk7IH0pOwogICAgICAgICAgICB2YXIgcm93ID0gbmV3IExlZ2VuZFJvdygpOwogICAgICAgICAgICB0YWJsZS5hZGRSb3cocm93KTsKICAgICAgICAgICAgcm93LmJvdHRvbVBhZGRpbmcgPSB0aGlzLl9yb3dCb3R0b21QYWRkaW5nOwogICAgICAgICAgICBlbnRyeU5hbWVzLmZvckVhY2goZnVuY3Rpb24gKG5hbWUsIGluZGV4KSB7CiAgICAgICAgICAgICAgICBpZiAocm93LmNvbHVtbnMubGVuZ3RoIC8gMiA9PT0gX3RoaXMubWF4RW50cmllc1BlclJvdygpKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gd2UgYWRkIHR3byBjb2x1bW5zIHBlciBlbnRyeSwgYSBzeW1ib2wgY29sdW1uIGFuZCBhIG5hbWUgY29sdW1uCiAgICAgICAgICAgICAgICAgICAgLy8gaWYgdGhlIGN1cnJlbnQgcm93IGlzIGZ1bGwsIGFjY29yZGluZyB0byB0aGUgbnVtYmVyIG9mIGVudHJpZXMKICAgICAgICAgICAgICAgICAgICAvLyB3ZSdyZSBhbGxvd2VkIHRvIGhhdmUgcGVyIHJvdywgd2UgbmVlZCB0byBhbGxvY2F0ZSBuZXcgc3BhY2UKICAgICAgICAgICAgICAgICAgICByb3cgPSBuZXcgTGVnZW5kUm93KCk7CiAgICAgICAgICAgICAgICAgICAgcm93LmJvdHRvbVBhZGRpbmcgPSBfdGhpcy5fcm93Qm90dG9tUGFkZGluZzsKICAgICAgICAgICAgICAgICAgICB0YWJsZS5hZGRSb3cocm93KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBhdmFpbGFibGVXaWR0aCA9IHJvdy5nZXRXaWR0aEF2YWlsYWJsZSgpOwogICAgICAgICAgICAgICAgdmFyIGZvcm1hdHRlZE5hbWUgPSBfdGhpcy5fZm9ybWF0dGVyKG5hbWUpOwogICAgICAgICAgICAgICAgLy8gdGhpcyBpcyB0aGUgd2lkdGggb2YgdGhlIHNlcmllcyBuYW1lIHdpdGhvdXQgYW55IGxpbmUgd3JhcHBpbmcKICAgICAgICAgICAgICAgIC8vIGl0IGlzIHRoZSBtb3N0IG9wdGltYWwgcHJlc2VudGF0aW9uIG9mIHRoZSBuYW1lCiAgICAgICAgICAgICAgICB2YXIgdW53cmFwcGVkTmFtZVdpZHRoID0gX3RoaXMuX21lYXN1cmVyLm1lYXN1cmUoZm9ybWF0dGVkTmFtZSkud2lkdGg7CiAgICAgICAgICAgICAgICB2YXIgd2lsbEJlU3F1aXNoZWQgPSAoYXZhaWxhYmxlV2lkdGggLSB0ZXh0SGVpZ2h0IC0gdW53cmFwcGVkTmFtZVdpZHRoKSA8IDA7CiAgICAgICAgICAgICAgICBpZiAod2lsbEJlU3F1aXNoZWQgJiYgcm93LmNvbHVtbnMubGVuZ3RoID4gMSkgewogICAgICAgICAgICAgICAgICAgIC8vIGFkZGluZyB0aGUgZW50cnkgdG8gdGhpcyByb3cgd2lsbCBzcXVpc2ggdGhpcwogICAgICAgICAgICAgICAgICAgIC8vIGVudHJ5LiBUaGUgcm93IGFscmVhZHkgY29udGFpbnMgZW50cmllcyBzbyBjcmVhdGUKICAgICAgICAgICAgICAgICAgICAvLyBhIG5ldyByb3cgdG8gYWRkIHRoaXMgZW50cnkgdG8gZm9yIG9wdGltYWwgZGlzcGxheQogICAgICAgICAgICAgICAgICAgIHJvdyA9IG5ldyBMZWdlbmRSb3coKTsKICAgICAgICAgICAgICAgICAgICByb3cuYm90dG9tUGFkZGluZyA9IF90aGlzLl9yb3dCb3R0b21QYWRkaW5nOwogICAgICAgICAgICAgICAgICAgIHRhYmxlLmFkZFJvdyhyb3cpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIHN5bWJvbENvbHVtbiA9IHsgd2lkdGg6IHRleHRIZWlnaHQsIGhlaWdodDogdGV4dEhlaWdodCwgZGF0YTogeyBuYW1lOiBuYW1lLCB0eXBlOiAic3ltYm9sIiB9IH07CiAgICAgICAgICAgICAgICByb3cuYWRkQ29sdW1uKHN5bWJvbENvbHVtbik7CiAgICAgICAgICAgICAgICAvLyB0aGUgc3BhY2UgY29uc3VtZWQgYnkgdGhlIG5hbWUgZmllbGQgaXMgdGhlIG1pbmltdW0gb2YgdGhlIHNwYWNlIGF2YWlsYWJsZSBpbiB0aGUgdGFibGUKICAgICAgICAgICAgICAgIC8vIGFuZCB0aGUgYWN0dWFsIHdpZHRoIGNvbnN1bWVkIGJ5IHRoZSBuYW1lCiAgICAgICAgICAgICAgICBhdmFpbGFibGVXaWR0aCA9IHJvdy5nZXRXaWR0aEF2YWlsYWJsZSgpOwogICAgICAgICAgICAgICAgdmFyIHVzZWROYW1lV2lkdGggPSBNYXRoLm1pbihhdmFpbGFibGVXaWR0aCwgdW53cmFwcGVkTmFtZVdpZHRoKTsKICAgICAgICAgICAgICAgIF90aGlzLl93cmFwcGVyLm1heExpbmVzKF90aGlzLm1heExpbmVzUGVyRW50cnkoKSk7CiAgICAgICAgICAgICAgICB2YXIgbnVtYmVyT2ZSb3dzID0gX3RoaXMuX3dyYXBwZXIud3JhcChmb3JtYXR0ZWROYW1lLCBfdGhpcy5fbWVhc3VyZXIsIHVzZWROYW1lV2lkdGgpLm5vTGluZXM7CiAgICAgICAgICAgICAgICB2YXIgbmFtZUNvbHVtbkhlaWdodCA9IG51bWJlck9mUm93cyAqIHRleHRIZWlnaHQ7CiAgICAgICAgICAgICAgICB2YXIgbmFtZUNvbHVtbiA9IHsgd2lkdGg6IHVzZWROYW1lV2lkdGgsIGhlaWdodDogbmFtZUNvbHVtbkhlaWdodCwgZGF0YTogeyBuYW1lOiBuYW1lLCB0eXBlOiAidGV4dCIgfSB9OwogICAgICAgICAgICAgICAgcm93LmFkZENvbHVtbihuYW1lQ29sdW1uKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB0YWJsZTsKICAgICAgICB9OwogICAgICAgIExlZ2VuZC5wcm90b3R5cGUucmVxdWVzdGVkU3BhY2UgPSBmdW5jdGlvbiAob2ZmZXJlZFdpZHRoLCBvZmZlcmVkSGVpZ2h0KSB7CiAgICAgICAgICAgIC8vIGlmIG1heCB3aWR0aCBpcyBzZXQsIHRoZSB0YWJsZSBpcyBndWFyYW50ZWVkIHRvIGJlIGF0IG1vc3QgbWF4V2lkdGggd2lkZS4KICAgICAgICAgICAgLy8gaWYgbWF4IHdpZHRoIGlzIG5vdCBzZXQsIHRoZSB0YWJsZSB3aWxsIGJlIGFzIHdpZGUgYXMgdGhlIGxvbmdlc3QgdW50cnVuY2F0ZWQgcm93CiAgICAgICAgICAgIHZhciB0YWJsZSA9IHRoaXMuX2J1aWxkTGVnZW5kVGFibGUodXRpbHMkMS5NYXRoLm1pbihbdGhpcy5tYXhXaWR0aCgpLCBvZmZlcmVkV2lkdGhdLCBvZmZlcmVkV2lkdGgpLCBvZmZlcmVkSGVpZ2h0KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIG1pbkhlaWdodDogdGFibGUuZ2V0SGVpZ2h0KCksCiAgICAgICAgICAgICAgICBtaW5XaWR0aDogdGFibGUuZ2V0V2lkdGgoKSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIEVudGl0aWVzIChyZXByZXNlbnRpbmcgTGVnZW5kIGVudHJpZXMpIGF0IGEgcGFydGljdWxhciBwb2ludC4KICAgICAgICAgKiBSZXR1cm5zIGFuIGVtcHR5IGFycmF5IGlmIG5vIEVudGl0aWVzIGFyZSBwcmVzZW50IGF0IHRoYXQgbG9jYXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBwCiAgICAgICAgICogQHJldHVybnMge0VudGl0eTxMZWdlbmQ+W119CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5lbnRpdGllc0F0ID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKCF0aGlzLl9pc1NldHVwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHRhYmxlID0gdGhpcy5fYnVpbGRMZWdlbmRUYWJsZSh0aGlzLndpZHRoKCksIHRoaXMuaGVpZ2h0KCkpOwogICAgICAgICAgICByZXR1cm4gdGFibGUucm93cy5yZWR1Y2UoZnVuY3Rpb24gKGVudGl0eSwgcm93LCByb3dJbmRleCkgewogICAgICAgICAgICAgICAgaWYgKGVudGl0eS5sZW5ndGggIT09IDApIHsKICAgICAgICAgICAgICAgICAgICAvLyB3ZSd2ZSBhbHJlYWR5IGZvdW5kIHRoZSBuZWFyZXN0IGVudGl0eTsganVzdCByZXR1cm4gaXQuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGVudGl0eTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciByb3dCb3VuZHMgPSB0YWJsZS5nZXRSb3dCb3VuZHMocm93SW5kZXgpOwogICAgICAgICAgICAgICAgdmFyIHdpdGhpblJvdyA9IHV0aWxzJDEuTWF0aC53aXRoaW4ocCwgcm93Qm91bmRzKTsKICAgICAgICAgICAgICAgIGlmICghd2l0aGluUm93KSB7CiAgICAgICAgICAgICAgICAgICAgLy8gdGhlIG5lYXJlc3QgZW50aXR5IGlzbid0IHdpdGhpbiB0aGlzIHJvdywgY29udGludWU7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGVudGl0eTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiByb3cuY29sdW1ucy5yZWR1Y2UoZnVuY3Rpb24gKGVudGl0eSwgY29sdW1uLCBjb2x1bW5JbmRleCkgewogICAgICAgICAgICAgICAgICAgIHZhciBjb2x1bW5Cb3VuZHMgPSB0YWJsZS5nZXRDb2x1bW5Cb3VuZHMocm93SW5kZXgsIGNvbHVtbkluZGV4KTsKICAgICAgICAgICAgICAgICAgICB2YXIgd2l0aGluQ29sdW1uID0gdXRpbHMkMS5NYXRoLndpdGhpbihwLCBjb2x1bW5Cb3VuZHMpOwogICAgICAgICAgICAgICAgICAgIGlmICh3aXRoaW5Db2x1bW4pIHsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHJvd0VsZW1lbnQgPSBfdGhpcy5jb250ZW50KCkuc2VsZWN0QWxsKCIuIiArIExlZ2VuZC5MRUdFTkRfUk9XX0NMQVNTKS5ub2RlcygpW3Jvd0luZGV4XTsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gSEFDS0hBQ0sgVGhlIDIueCBBUEkgY2hvb3NlcyB0aGUgc3ltYm9sIGVsZW1lbnQgYXMgdGhlICJzZWxlY3Rpb24iIHRvIHJldHVybiwgcmVnYXJkbGVzcyBvZiB3aGF0CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIHdhcyBhY3R1YWxseSBzZWxlY3RlZAogICAgICAgICAgICAgICAgICAgICAgICB2YXIgZW50cnlFbGVtZW50ID0gZDMuc2VsZWN0KHJvd0VsZW1lbnQpCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCIuIiArIExlZ2VuZC5MRUdFTkRfRU5UUllfQ0xBU1MpLm5vZGVzKClbTWF0aC5mbG9vcihjb2x1bW5JbmRleCAvIDIpXTsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHN5bWJvbEVsZW1lbnQgPSBkMy5zZWxlY3QoZW50cnlFbGVtZW50KS5zZWxlY3QoIi4iICsgTGVnZW5kLkxFR0VORF9TWU1CT0xfQ0xBU1MpOwogICAgICAgICAgICAgICAgICAgICAgICAvLyBIQUNLSEFDSyBUaGUgMi54IEFQSSByZXR1cm5zIHRoZSBjZW50ZXIge3gsIHl9IG9mIHRoZSBzeW1ib2wgYXMgdGhlIHBvc2l0aW9uLgogICAgICAgICAgICAgICAgICAgICAgICB2YXIgcm93VHJhbnNsYXRlID0gdXRpbHMkMS5ET00uZ2V0VHJhbnNsYXRlVmFsdWVzKGQzLnNlbGVjdChyb3dFbGVtZW50KSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBzeW1ib2xUcmFuc2xhdGUgPSB1dGlscyQxLkRPTS5nZXRUcmFuc2xhdGVWYWx1ZXMoc3ltYm9sRWxlbWVudCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBbewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJvdW5kczogdXRpbHMkMS5ET00uZWxlbWVudEJCb3goZDMuc2VsZWN0KHJvd0VsZW1lbnQpKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkYXR1bTogY29sdW1uLmRhdGEubmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbjogewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB4OiByb3dUcmFuc2xhdGVbMF0gKyBzeW1ib2xUcmFuc2xhdGVbMF0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHk6IHJvd1RyYW5zbGF0ZVsxXSArIHN5bWJvbFRyYW5zbGF0ZVsxXSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNlbGVjdGlvbjogZDMuc2VsZWN0KGVudHJ5RWxlbWVudCksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29tcG9uZW50OiBfdGhpcywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH1dOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gZW50aXR5OwogICAgICAgICAgICAgICAgfSwgZW50aXR5KTsKICAgICAgICAgICAgfSwgW10pOwogICAgICAgIH07CiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseS5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgdGFibGUgPSB0aGlzLl9idWlsZExlZ2VuZFRhYmxlKHRoaXMud2lkdGgoKSwgdGhpcy5oZWlnaHQoKSk7CiAgICAgICAgICAgIC8vIGNsZWFyIGNvbnRlbnQgZnJvbSBwcmV2aW91cyByZW5kZXJzCiAgICAgICAgICAgIHRoaXMuY29udGVudCgpLnNlbGVjdEFsbCgiKiIpLnJlbW92ZSgpOwogICAgICAgICAgICB2YXIgcm93c1VwZGF0ZSA9IHRoaXMuY29udGVudCgpLnNlbGVjdEFsbCgiZy4iICsgTGVnZW5kLkxFR0VORF9ST1dfQ0xBU1MpLmRhdGEodGFibGUucm93cyk7CiAgICAgICAgICAgIHZhciByb3dzID0gcm93c1VwZGF0ZQogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoImciKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoTGVnZW5kLkxFR0VORF9ST1dfQ0xBU1MsIHRydWUpCiAgICAgICAgICAgICAgICAubWVyZ2Uocm93c1VwZGF0ZSk7CiAgICAgICAgICAgIHJvd3NVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICByb3dzLmF0dHIoInRyYW5zZm9ybSIsIGZ1bmN0aW9uIChyb3csIHJvd0luZGV4KSB7CiAgICAgICAgICAgICAgICB2YXIgcm93Qm91bmRzID0gdGFibGUuZ2V0Um93Qm91bmRzKHJvd0luZGV4KTsKICAgICAgICAgICAgICAgIHJldHVybiAidHJhbnNsYXRlKCIgKyByb3dCb3VuZHMudG9wTGVmdC54ICsgIiwgIiArIHJvd0JvdW5kcy50b3BMZWZ0LnkgKyAiKSI7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgc2VsZiA9IHRoaXM7CiAgICAgICAgICAgIHJvd3MuZWFjaChmdW5jdGlvbiAocm93LCByb3dJbmRleCkgewogICAgICAgICAgICAgICAgdmFyIHN5bWJvbEVudHJ5UGFpcnMgPSBbXTsKICAgICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgcm93LmNvbHVtbnMubGVuZ3RoOyBpICs9IDIpIHsKICAgICAgICAgICAgICAgICAgICBzeW1ib2xFbnRyeVBhaXJzLnB1c2goW3Jvdy5jb2x1bW5zW2ldLCByb3cuY29sdW1uc1tpICsgMV1dKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBlbnRyaWVzVXBkYXRlID0gZDMuc2VsZWN0KHRoaXMpLnNlbGVjdEFsbCgiZy4iICsgTGVnZW5kLkxFR0VORF9FTlRSWV9DTEFTUykuZGF0YShzeW1ib2xFbnRyeVBhaXJzKTsKICAgICAgICAgICAgICAgIHZhciBlbnRyaWVzRW50ZXIgPSBlbnRyaWVzVXBkYXRlCiAgICAgICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgICAgICAuYXBwZW5kKCJnIikKICAgICAgICAgICAgICAgICAgICAuY2xhc3NlZChMZWdlbmQuTEVHRU5EX0VOVFJZX0NMQVNTLCB0cnVlKQogICAgICAgICAgICAgICAgICAgIC5tZXJnZShlbnRyaWVzVXBkYXRlKTsKICAgICAgICAgICAgICAgIGVudHJpZXNFbnRlci5hcHBlbmQoInBhdGgiKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCJkIiwgZnVuY3Rpb24gKHN5bWJvbEVudHJ5UGFpciwgY29sdW1uSW5kZXgpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgc3ltYm9sID0gc3ltYm9sRW50cnlQYWlyWzBdOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBzZWxmLnN5bWJvbCgpKHN5bWJvbC5kYXRhLm5hbWUsIHJvd0luZGV4KShzeW1ib2wuaGVpZ2h0ICogMC42KShudWxsKTsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoInRyYW5zZm9ybSIsIGZ1bmN0aW9uIChzeW1ib2xFbnRyeVBhaXIsIGkpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgc3ltYm9sID0gc3ltYm9sRW50cnlQYWlyWzBdOwogICAgICAgICAgICAgICAgICAgIHZhciBjb2x1bW5JbmRleCA9IHRhYmxlLnJvd3Nbcm93SW5kZXhdLmNvbHVtbnMuaW5kZXhPZihzeW1ib2wpOwogICAgICAgICAgICAgICAgICAgIHZhciBjb2x1bW5Cb3VuZHMgPSB0YWJsZS5nZXRDb2x1bW5Cb3VuZHMocm93SW5kZXgsIGNvbHVtbkluZGV4KTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gInRyYW5zbGF0ZSgiICsgKGNvbHVtbkJvdW5kcy50b3BMZWZ0LnggKyBzeW1ib2wud2lkdGggLyAyKSArICIsICIgKyBzeW1ib2wuaGVpZ2h0IC8gMiArICIpIjsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoImZpbGwiLCBmdW5jdGlvbiAoc3ltYm9sRW50cnlQYWlyKSB7IHJldHVybiBzZWxmLl9jb2xvclNjYWxlLnNjYWxlKHN5bWJvbEVudHJ5UGFpclswXS5kYXRhLm5hbWUpOyB9KQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCJvcGFjaXR5IiwgZnVuY3Rpb24gKHN5bWJvbEVudHJ5UGFpciwgX2NvbHVtbkluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHNlbGYuc3ltYm9sT3BhY2l0eSgpKHN5bWJvbEVudHJ5UGFpclswXS5kYXRhLm5hbWUsIHJvd0luZGV4KTsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLmNsYXNzZWQoTGVnZW5kLkxFR0VORF9TWU1CT0xfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICAgICAgZW50cmllc0VudGVyLmFwcGVuZCgiZyIpLmNsYXNzZWQoInRleHQtY29udGFpbmVyIiwgdHJ1ZSkKICAgICAgICAgICAgICAgICAgICAuYXR0cigidHJhbnNmb3JtIiwgZnVuY3Rpb24gKHN5bWJvbEVudHJ5UGFpciwgaSkgewogICAgICAgICAgICAgICAgICAgIHZhciBlbnRyeSA9IHN5bWJvbEVudHJ5UGFpclsxXTsKICAgICAgICAgICAgICAgICAgICB2YXIgY29sdW1uSW5kZXggPSB0YWJsZS5yb3dzW3Jvd0luZGV4XS5jb2x1bW5zLmluZGV4T2YoZW50cnkpOwogICAgICAgICAgICAgICAgICAgIHZhciBjb2x1bW5Cb3VuZHMgPSB0YWJsZS5nZXRDb2x1bW5Cb3VuZHMocm93SW5kZXgsIGNvbHVtbkluZGV4KTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gInRyYW5zbGF0ZSgiICsgY29sdW1uQm91bmRzLnRvcExlZnQueCArICIsIDApIjsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKHN5bWJvbEVudHJ5UGFpciwgaSwgcm93SW5kZXgpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgdGV4dENvbnRhaW5lciA9IGQzLnNlbGVjdCh0aGlzKTsKICAgICAgICAgICAgICAgICAgICB2YXIgY29sdW1uID0gc3ltYm9sRW50cnlQYWlyWzFdOwogICAgICAgICAgICAgICAgICAgIHZhciB3cml0ZU9wdGlvbnMgPSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHhBbGlnbjogImxlZnQiLAogICAgICAgICAgICAgICAgICAgICAgICB5QWxpZ246ICJ0b3AiLAogICAgICAgICAgICAgICAgICAgICAgICB0ZXh0Um90YXRpb246IDAsCiAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICBzZWxmLl93cml0ZXIud3JpdGUoc2VsZi5fZm9ybWF0dGVyKGNvbHVtbi5kYXRhLm5hbWUpLCBjb2x1bW4ud2lkdGgsIHNlbGYuaGVpZ2h0KCksIHdyaXRlT3B0aW9ucywgdGV4dENvbnRhaW5lci5ub2RlKCkpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBlbnRyaWVzVXBkYXRlLmV4aXQoKS5yZW1vdmUoKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5zeW1ib2wgPSBmdW5jdGlvbiAoc3ltYm9sKSB7CiAgICAgICAgICAgIGlmIChzeW1ib2wgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3N5bWJvbEZhY3RvcnlBY2Nlc3NvcjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3N5bWJvbEZhY3RvcnlBY2Nlc3NvciA9IHN5bWJvbDsKICAgICAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5zeW1ib2xPcGFjaXR5ID0gZnVuY3Rpb24gKHN5bWJvbE9wYWNpdHkpIHsKICAgICAgICAgICAgaWYgKHN5bWJvbE9wYWNpdHkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3N5bWJvbE9wYWNpdHlBY2Nlc3NvcjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0eXBlb2Ygc3ltYm9sT3BhY2l0eSA9PT0gIm51bWJlciIpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3N5bWJvbE9wYWNpdHlBY2Nlc3NvciA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIHN5bWJvbE9wYWNpdHk7IH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9zeW1ib2xPcGFjaXR5QWNjZXNzb3IgPSBzeW1ib2xPcGFjaXR5OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5maXhlZFdpZHRoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9OwogICAgICAgIExlZ2VuZC5wcm90b3R5cGUuZml4ZWRIZWlnaHQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgTGVnZW5kLnByb3RvdHlwZS5pbnZhbGlkYXRlQ2FjaGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyLnJlc2V0KCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgY3NzIGNsYXNzIGFwcGxpZWQgdG8gZWFjaCBsZWdlbmQgcm93CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kLkxFR0VORF9ST1dfQ0xBU1MgPSAibGVnZW5kLXJvdyI7CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGNzcyBjbGFzcyBhcHBsaWVkIHRvIGVhY2ggbGVnZW5kIGVudHJ5CiAgICAgICAgICovCiAgICAgICAgTGVnZW5kLkxFR0VORF9FTlRSWV9DTEFTUyA9ICJsZWdlbmQtZW50cnkiOwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBjc3MgY2xhc3MgYXBwbGllZCB0byBlYWNoIGxlZ2VuZCBzeW1ib2wKICAgICAgICAgKi8KICAgICAgICBMZWdlbmQuTEVHRU5EX1NZTUJPTF9DTEFTUyA9ICJsZWdlbmQtc3ltYm9sIjsKICAgICAgICByZXR1cm4gTGVnZW5kOwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLkxlZ2VuZCA9IExlZ2VuZDsKICAgIH0pOwoKICAgIHZhciBjb21tb25zID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CiAgICB2YXIgQW5pbWF0b3I7CiAgICAoZnVuY3Rpb24gKEFuaW1hdG9yKSB7CiAgICAgICAgQW5pbWF0b3IuTUFJTiA9ICJtYWluIjsKICAgICAgICBBbmltYXRvci5SRVNFVCA9ICJyZXNldCI7CiAgICB9KShBbmltYXRvciA9IGV4cG9ydHMuQW5pbWF0b3IgfHwgKGV4cG9ydHMuQW5pbWF0b3IgPSB7fSkpOwogICAgfSk7CgogICAgLyohCiAgICAgKiBpc29iamVjdCA8aHR0cHM6Ly9naXRodWIuY29tL2pvbnNjaGxpbmtlcnQvaXNvYmplY3Q+CiAgICAgKgogICAgICogQ29weXJpZ2h0IChjKSAyMDE0LTIwMTcsIEpvbiBTY2hsaW5rZXJ0LgogICAgICogUmVsZWFzZWQgdW5kZXIgdGhlIE1JVCBMaWNlbnNlLgogICAgICovCgogICAgdmFyIGlzb2JqZWN0ID0gZnVuY3Rpb24gaXNPYmplY3QodmFsKSB7CiAgICAgIHJldHVybiB2YWwgIT0gbnVsbCAmJiB0eXBlb2YgdmFsID09PSAnb2JqZWN0JyAmJiBBcnJheS5pc0FycmF5KHZhbCkgPT09IGZhbHNlOwogICAgfTsKCiAgICBmdW5jdGlvbiBpc09iamVjdE9iamVjdChvKSB7CiAgICAgIHJldHVybiBpc29iamVjdChvKSA9PT0gdHJ1ZQogICAgICAgICYmIE9iamVjdC5wcm90b3R5cGUudG9TdHJpbmcuY2FsbChvKSA9PT0gJ1tvYmplY3QgT2JqZWN0XSc7CiAgICB9CgogICAgdmFyIGlzUGxhaW5PYmplY3QgPSBmdW5jdGlvbiBpc1BsYWluT2JqZWN0KG8pIHsKICAgICAgdmFyIGN0b3IscHJvdDsKCiAgICAgIGlmIChpc09iamVjdE9iamVjdChvKSA9PT0gZmFsc2UpIHJldHVybiBmYWxzZTsKCiAgICAgIC8vIElmIGhhcyBtb2RpZmllZCBjb25zdHJ1Y3RvcgogICAgICBjdG9yID0gby5jb25zdHJ1Y3RvcjsKICAgICAgaWYgKHR5cGVvZiBjdG9yICE9PSAnZnVuY3Rpb24nKSByZXR1cm4gZmFsc2U7CgogICAgICAvLyBJZiBoYXMgbW9kaWZpZWQgcHJvdG90eXBlCiAgICAgIHByb3QgPSBjdG9yLnByb3RvdHlwZTsKICAgICAgaWYgKGlzT2JqZWN0T2JqZWN0KHByb3QpID09PSBmYWxzZSkgcmV0dXJuIGZhbHNlOwoKICAgICAgLy8gSWYgY29uc3RydWN0b3IgZG9lcyBub3QgaGF2ZSBhbiBPYmplY3Qtc3BlY2lmaWMgbWV0aG9kCiAgICAgIGlmIChwcm90Lmhhc093blByb3BlcnR5KCdpc1Byb3RvdHlwZU9mJykgPT09IGZhbHNlKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CgogICAgICAvLyBNb3N0IGxpa2VseSBhIHBsYWluIE9iamVjdAogICAgICByZXR1cm4gdHJ1ZTsKICAgIH07CgogICAgdmFyIGRhdGFzZXQgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB2YXIgVVBEQVRFX01PTk9UT05JQyA9IDA7CiAgICB2YXIgRGF0YXNldCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICAvKioKICAgICAgICAgKiBBIERhdGFzZXQgY29udGFpbnMgYW4gYXJyYXkgb2YgZGF0YSBhbmQgc29tZSBtZXRhZGF0YS4KICAgICAgICAgKiBDaGFuZ2VzIHRvIHRoZSBkYXRhIG9yIG1ldGFkYXRhIHdpbGwgY2F1c2UgYW55dGhpbmcgc3Vic2NyaWJlZCB0byB0aGUgRGF0YXNldCB0byB1cGRhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge2FueVtdfSBbZGF0YT1bXV0gVGhlIGRhdGEgZm9yIHRoaXMgRGF0YXNldC4KICAgICAgICAgKiBAcGFyYW0ge2FueX0gW21ldGFkYXRhPXt9XSBBbiBvYmplY3QgY29udGFpbmluZyBhZGRpdGlvbmFsIGluZm9ybWF0aW9uLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIERhdGFzZXQoZGF0YSwgbWV0YWRhdGEpIHsKICAgICAgICAgICAgaWYgKGRhdGEgPT09IHZvaWQgMCkgeyBkYXRhID0gW107IH0KICAgICAgICAgICAgaWYgKG1ldGFkYXRhID09PSB2b2lkIDApIHsgbWV0YWRhdGEgPSB7fTsgfQogICAgICAgICAgICB0aGlzLl91cGRhdGVJZCA9IFVQREFURV9NT05PVE9OSUMrKzsKICAgICAgICAgICAgdGhpcy5fZGF0YSA9IGRhdGE7CiAgICAgICAgICAgIHRoaXMuX21ldGFkYXRhID0gbWV0YWRhdGE7CiAgICAgICAgICAgIHRoaXMuX2NhbGxiYWNrcyA9IG5ldyB1dGlscyQxLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBjYWxsYmFjayB0byBiZSBjYWxsZWQgd2hlbiB0aGUgRGF0YXNldCB1cGRhdGVzLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEYXRhc2V0Q2FsbGJhY2t9IGNhbGxiYWNrLgogICAgICAgICAqIEByZXR1cm5zIHtEYXRhc2V0fSBUaGUgY2FsbGluZyBEYXRhc2V0LgogICAgICAgICAqLwogICAgICAgIERhdGFzZXQucHJvdG90eXBlLm9uVXBkYXRlID0gZnVuY3Rpb24gKGNhbGxiYWNrKSB7CiAgICAgICAgICAgIHRoaXMuX2NhbGxiYWNrcy5hZGQoY2FsbGJhY2spOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZXMgYSBjYWxsYmFjayB0aGF0IHdvdWxkIGJlIGNhbGxlZCB3aGVuIHRoZSBEYXRhc2V0IHVwZGF0ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RhdGFzZXRDYWxsYmFja30gY2FsbGJhY2sKICAgICAgICAgKiBAcmV0dXJucyB7RGF0YXNldH0gVGhlIGNhbGxpbmcgRGF0YXNldC4KICAgICAgICAgKi8KICAgICAgICBEYXRhc2V0LnByb3RvdHlwZS5vZmZVcGRhdGUgPSBmdW5jdGlvbiAoY2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fY2FsbGJhY2tzLmRlbGV0ZShjYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgRGF0YXNldC5wcm90b3R5cGUuZGF0YSA9IGZ1bmN0aW9uIChkYXRhKSB7CiAgICAgICAgICAgIGlmIChkYXRhID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kYXRhOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZGF0YSA9IGRhdGE7CiAgICAgICAgICAgICAgICB0aGlzLl9kaXNwYXRjaFVwZGF0ZSgpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIERhdGFzZXQucHJvdG90eXBlLm1ldGFkYXRhID0gZnVuY3Rpb24gKG1ldGFkYXRhKSB7CiAgICAgICAgICAgIGlmIChtZXRhZGF0YSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWV0YWRhdGE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9tZXRhZGF0YSA9IG1ldGFkYXRhOwogICAgICAgICAgICAgICAgdGhpcy5fZGlzcGF0Y2hVcGRhdGUoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBEYXRhc2V0LnByb3RvdHlwZS51cGRhdGVJZCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3VwZGF0ZUlkOwogICAgICAgIH07CiAgICAgICAgRGF0YXNldC5wcm90b3R5cGUuX2Rpc3BhdGNoVXBkYXRlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl91cGRhdGVJZCA9IFVQREFURV9NT05PVE9OSUMrKzsKICAgICAgICAgICAgdGhpcy5fY2FsbGJhY2tzLmNhbGxDYWxsYmFja3ModGhpcyk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gRGF0YXNldDsKICAgIH0oKSk7CiAgICBleHBvcnRzLkRhdGFzZXQgPSBEYXRhc2V0OwogICAgfSk7CgogICAgdmFyIHNpZ25hdHVyZSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICogQGZpbGVvdmVydmlldyBJbXBsZW1lbnRzIHRoZSBTaWduYXR1cmUgQVBJIHRvIGhlbHAgaW4gY29tcGFyaW5nIHdoZW4gdHdvCiAgICAgKiBQbG90dGFibGUgb2JqZWN0cyBoYXZlICJjaGFuZ2VkIi4KICAgICAqCiAgICAgKiBNZW1vaXphdGlvbiBpbiBQbG90dGFibGUgaXMgY29tcGxpY2F0ZWQgYnkgbXV0YWJsZSBzY2FsZXMgYW5kIGRhdGFzZXRzLiBXZSBjYW5ub3Qgc2ltcGx5CiAgICAgKiByZWZlcmVuY2UgY29tcGFyZSB0d28gZS5nLiBzY2FsZXMgc2luY2UgaXQgbWF5IGhhdmUgaW50ZXJuYWxseSBtdXRhdGVkLiBUbyByZXNvbHZlIHRoaXMsCiAgICAgKiB3ZSB3cml0ZSBhIHJlY3Vyc2l2ZSBTaWduYXR1cmUgaW50ZXJmYWNlIHRoYXQgaG9sZHMgYW4gaW1tdXRhYmxlIHNuYXBzaG90IG9mIHdoYXRldmVyCiAgICAgKiBzdGF0ZSB0aGUgc2NhbGUvZGF0YSB3YXMgaW4gYXQgdGhlIHRpbWUuIFRoZW4gb24gbWVtb2l6ZWQgZnVuY3Rpb24gaW52b2NhdGlvbiB3ZSBzaWduIHRoZQogICAgICogbmV3IGlucHV0cyBhbmQgY29tcGFyZSB0aGUgc2lnbmF0dXJlcyB0byBkZWNpZGUgaWYgd2Ugc2hvdWxkIHJlY29tcHV0ZS4KICAgICAqCiAgICAgKiBXZSBtdXN0IGhhbmQtd3JpdGUgYSBzaWduYXR1cmUgZm9yIGVhY2ggY3VzdG9tIGNsYXNzIHdlIHdpc2ggdG8gc3VwcG9ydC4KICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCiAgICAvKioKICAgICAqIEdlbmVyaWMgc2lnbmF0dXJlIGZhY3RvcnkgLSBwYXNzIGFueSB2YWx1ZSBhbmQgZ2V0IGEgc2lnbmF0dXJlIGZvciBpdC4KICAgICAqCiAgICAgKiBEYXRhc2V0cyBhbmQgU2NhbGVzIGFyZSBoYW5kbGVkIHNwZWNpYWxseSAtIHNlZSB0aGVpciByZXNwZWN0aXZlIHNpZ25pbmcgbWV0aG9kcy4KICAgICAqCiAgICAgKiBJZiB0aGUgaW5wdXQgaXMgYWxyZWFkeSBhIHNpZ25hdHVyZSwgc2ltcGx5IHJldHVybiBpdC4KICAgICAqCiAgICAgKiBAcGFyYW0gYQogICAgICogQHJldHVybnMge1NpZ25hdHVyZX0KICAgICAqLwogICAgZnVuY3Rpb24gc2lnbihhKSB7CiAgICAgICAgaWYgKGEgaW5zdGFuY2VvZiBTaWduYXR1cmUpIHsKICAgICAgICAgICAgcmV0dXJuIGE7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKGEgaW5zdGFuY2VvZiBEYXRlKSB7CiAgICAgICAgICAgIHJldHVybiBzaWduUmVmKGEudmFsdWVPZigpKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoYSBpbnN0YW5jZW9mIHNjYWxlLlNjYWxlKSB7CiAgICAgICAgICAgIHJldHVybiBzaWduU2NhbGUoYSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKGEgaW5zdGFuY2VvZiBkYXRhc2V0LkRhdGFzZXQpIHsKICAgICAgICAgICAgcmV0dXJuIHNpZ25EYXRhc2V0KGEpOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmIChpc1BsYWluT2JqZWN0KGEpKSB7CiAgICAgICAgICAgIHJldHVybiBzaWduT2JqKGEpOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmIChBcnJheS5pc0FycmF5KGEpKSB7CiAgICAgICAgICAgIHJldHVybiBzaWduQXJyYXkoYSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICByZXR1cm4gc2lnblJlZihhKTsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLnNpZ24gPSBzaWduOwogICAgZnVuY3Rpb24gc2lnblNjYWxlKHNjYWxlKSB7CiAgICAgICAgdmFyIHNjYWxlT2JqID0gewogICAgICAgICAgICAvLyByZXF1aXJlZCBpbiBjYXNlIHRoZSBkb21haW4gaGFzIGNoYW5nZWQgd2l0aG91dCB0aGUgdXBkYXRlSWQgY2hhbmdpbmcKICAgICAgICAgICAgZG9tYWluOiBzY2FsZS5kb21haW4oKSwKICAgICAgICAgICAgLy8gcmVxdWlyZWQgaW4gY2FzZSB0aGUgcmFuZ2UgaGFzIGNoYW5nZWQgd2l0aG91dCB0aGUgdXBkYXRlSWQgY2hhbmdpbmcKICAgICAgICAgICAgcmFuZ2U6IHNjYWxlLnJhbmdlKCksCiAgICAgICAgICAgIC8vIGdlbmVyaWMgY2F0Y2gtYWxsIGZvciBzY2FsZSB1cGRhdGVzIChleGlzdGluZyBjb2RlIGRvZXNuJ3QgZnVsbHkgY2F0Y2ggYWxsCiAgICAgICAgICAgIC8vIHVwZGF0ZXMsIGJ1dCBpdCdzIGdvb2QgZm9yIHNvbWV0aGluZykKICAgICAgICAgICAgdXBkYXRlSWQ6IHNjYWxlLnVwZGF0ZUlkKCksCiAgICAgICAgICAgIC8vIGtlZXAgYSByZWYgdG8gdGhlIHNjYWxlIGluIGNhc2UgdGhlIHJlZiBjaGFuZ2VzCiAgICAgICAgICAgIHJlZjogc2lnblJlZihzY2FsZSksCiAgICAgICAgfTsKICAgICAgICByZXR1cm4gc2lnbk9iaihzY2FsZU9iaik7CiAgICB9CiAgICBleHBvcnRzLnNpZ25TY2FsZSA9IHNpZ25TY2FsZTsKICAgIGZ1bmN0aW9uIHNpZ25EYXRhc2V0KGRhdGFzZXQpIHsKICAgICAgICB2YXIgZGF0YXNldE9iaiA9IHsKICAgICAgICAgICAgcmVmOiBzaWduUmVmKGRhdGFzZXQpLAogICAgICAgICAgICAvLyBvbmx5IHNpZ24gdXBkYXRlSWQgc2luY2Ugb25seSBkYXRhKCkgYW5kIG1ldGFkYXRhKCkgZXhpc3QgYXMgcHJvcGVydGllcwogICAgICAgICAgICAvLyBhbmQgYm90aCB1cGRhdGUgdXBkYXRlSWQKICAgICAgICAgICAgdXBkYXRlSWQ6IGRhdGFzZXQudXBkYXRlSWQoKSwKICAgICAgICB9OwogICAgICAgIHJldHVybiBzaWduT2JqKGRhdGFzZXRPYmopOwogICAgfQogICAgZXhwb3J0cy5zaWduRGF0YXNldCA9IHNpZ25EYXRhc2V0OwogICAgZnVuY3Rpb24gc2lnblJlZihhKSB7CiAgICAgICAgcmV0dXJuIG5ldyBSZWZlcmVuY2VTaWduYXR1cmUoYSk7CiAgICB9CiAgICBleHBvcnRzLnNpZ25SZWYgPSBzaWduUmVmOwogICAgZnVuY3Rpb24gc2lnbkFycmF5KGEpIHsKICAgICAgICByZXR1cm4gbmV3IEFycmF5U2lnbmF0dXJlKGEubWFwKGZ1bmN0aW9uIChlbGVtZW50KSB7IHJldHVybiBzaWduKGVsZW1lbnQpOyB9KSk7CiAgICB9CiAgICBleHBvcnRzLnNpZ25BcnJheSA9IHNpZ25BcnJheTsKICAgIGZ1bmN0aW9uIHNpZ25PYmoob2JqKSB7CiAgICAgICAgdmFyIHNpZ25hdHVyZVJlY29yZCA9IHt9OwogICAgICAgIGZvciAodmFyIGtleSBpbiBvYmopIHsKICAgICAgICAgICAgaWYgKG9iai5oYXNPd25Qcm9wZXJ0eShrZXkpKSB7CiAgICAgICAgICAgICAgICBzaWduYXR1cmVSZWNvcmRba2V5XSA9IHNpZ24ob2JqW2tleV0pOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBuZXcgT2JqZWN0U2lnbmF0dXJlKHNpZ25hdHVyZVJlY29yZCk7CiAgICB9CiAgICBleHBvcnRzLnNpZ25PYmogPSBzaWduT2JqOwogICAgLyoqCiAgICAgKiBCYXNlIHNpZ25hdHVyZS4gU3ViY2xhc3NlcyBzaG91bGQgaW1wbGVtZW50IGlzU2lnbmF0dXJlRGlmZmVyZW50LiBBbGwgY2xhc3NlcwogICAgICogc2hvdWxkIGJlIGltbXV0YWJsZS4KICAgICAqCiAgICAgKiBVc2VycyBzaG91bGQgb25seSBjYWxsIGBpc0RpZmZlcmVudGAsIG5vdCBgaXNTaWduYXR1cmVEaWZmZXJlbnRgLgogICAgICovCiAgICB2YXIgU2lnbmF0dXJlID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIGZ1bmN0aW9uIFNpZ25hdHVyZSgpIHsKICAgICAgICB9CiAgICAgICAgU2lnbmF0dXJlLnByb3RvdHlwZS5pc0RpZmZlcmVudCA9IGZ1bmN0aW9uIChvdGhlcikgewogICAgICAgICAgICBpZiAob3RoZXIgaW5zdGFuY2VvZiB0aGlzLmNvbnN0cnVjdG9yKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5pc1NpZ25hdHVyZURpZmZlcmVudChvdGhlcik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFNpZ25hdHVyZTsKICAgIH0oKSk7CiAgICBleHBvcnRzLlNpZ25hdHVyZSA9IFNpZ25hdHVyZTsKICAgIC8qKgogICAgICogQSBzaWduYXR1cmUgZm9yIGFuIGFycmF5LgogICAgICovCiAgICB2YXIgQXJyYXlTaWduYXR1cmUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhBcnJheVNpZ25hdHVyZSwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBBcnJheVNpZ25hdHVyZShhcnJheSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5hcnJheSA9IGFycmF5OwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEFuIGFycmF5IG9mIHNpZ25hdHVyZXMgaXMgZGlmZmVyZW50IGlmIGFueSBvZiB0aGUgZWxlbWVudHMgaXNEaWZmZXJlbnQuCiAgICAgICAgICovCiAgICAgICAgQXJyYXlTaWduYXR1cmUucHJvdG90eXBlLmlzU2lnbmF0dXJlRGlmZmVyZW50ID0gZnVuY3Rpb24gKG90aGVyKSB7CiAgICAgICAgICAgIGlmIChvdGhlci5hcnJheS5sZW5ndGggIT09IHRoaXMuYXJyYXkubGVuZ3RoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgdGhpcy5hcnJheS5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLmFycmF5W2ldLmlzRGlmZmVyZW50KG90aGVyLmFycmF5W2ldKSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIHJldHVybiBBcnJheVNpZ25hdHVyZTsKICAgIH0oU2lnbmF0dXJlKSk7CiAgICBleHBvcnRzLkFycmF5U2lnbmF0dXJlID0gQXJyYXlTaWduYXR1cmU7CiAgICB2YXIgUmVmZXJlbmNlU2lnbmF0dXJlID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUmVmZXJlbmNlU2lnbmF0dXJlLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFJlZmVyZW5jZVNpZ25hdHVyZShyZWYpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMucmVmID0gcmVmOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFJlZmVyZW5jZVNpZ25hdHVyZS5wcm90b3R5cGUuaXNTaWduYXR1cmVEaWZmZXJlbnQgPSBmdW5jdGlvbiAob3RoZXIpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVmICE9PSBvdGhlci5yZWY7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gUmVmZXJlbmNlU2lnbmF0dXJlOwogICAgfShTaWduYXR1cmUpKTsKICAgIGV4cG9ydHMuUmVmZXJlbmNlU2lnbmF0dXJlID0gUmVmZXJlbmNlU2lnbmF0dXJlOwogICAgLyoqCiAgICAgKiBBIHNpZ25hdHVyZSBmb3IgYSBwbGFpbiBqcyBvYmplY3QuCiAgICAgKi8KICAgIHZhciBPYmplY3RTaWduYXR1cmUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhPYmplY3RTaWduYXR1cmUsIF9zdXBlcik7CiAgICAgICAgZnVuY3Rpb24gT2JqZWN0U2lnbmF0dXJlKG9iaikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5vYmogPSBvYmo7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQW4gb2JqZWN0IHNpZ25hdHVyZSBpcyBkaWZmZXJlbnQgaWYgYW55IG9mIHRoZSBlbGVtZW50cyBpc0RpZmZlcmVudC4KICAgICAgICAgKi8KICAgICAgICBPYmplY3RTaWduYXR1cmUucHJvdG90eXBlLmlzU2lnbmF0dXJlRGlmZmVyZW50ID0gZnVuY3Rpb24gKG90aGVyKSB7CiAgICAgICAgICAgIHZhciBteUtleXMgPSBPYmplY3Qua2V5cyh0aGlzLm9iaik7CiAgICAgICAgICAgIHZhciBvdGhlcktleXMgPSBPYmplY3Qua2V5cyhvdGhlci5vYmopOwogICAgICAgICAgICBpZiAobXlLZXlzLmxlbmd0aCAhPT0gb3RoZXJLZXlzLmxlbmd0aCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZm9yICh2YXIgX2kgPSAwLCBteUtleXNfMSA9IG15S2V5czsgX2kgPCBteUtleXNfMS5sZW5ndGg7IF9pKyspIHsKICAgICAgICAgICAgICAgIHZhciBrZXkgPSBteUtleXNfMVtfaV07CiAgICAgICAgICAgICAgICBpZiAoIW90aGVyLm9iai5oYXNPd25Qcm9wZXJ0eShrZXkpKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAodGhpcy5vYmpba2V5XS5pc0RpZmZlcmVudChvdGhlci5vYmpba2V5XSkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gT2JqZWN0U2lnbmF0dXJlOwogICAgfShTaWduYXR1cmUpKTsKICAgIGV4cG9ydHMuT2JqZWN0U2lnbmF0dXJlID0gT2JqZWN0U2lnbmF0dXJlOwogICAgfSk7CgogICAgdmFyIG1lbW9pemVfMSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICogQGZpbGVvdmVydmlldyBJbXBsZW1lbnRzIGEgZnVuY3Rpb24gbWVtb2l6ZXIgdXNpbmcgdGhlIFNpZ25hdHVyZSBBUEkuCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgLyoqCiAgICAgKiBSZXR1cm4gYSBtZW1vaXplZCB2ZXJzaW9uIG9mIHRoZSBpbnB1dCBmdW5jdGlvbi4gVGhlIG1lbW9pemVkIGZ1bmN0aW9uCiAgICAgKiByZWR1Y2VzIHVubmVjZXNzYXJ5IGludm9jYXRpb25zIG9mIHRoZSBpbnB1dCBieSBrZWVwaW5nIGEgY2FjaGUgb2YgdGhlCiAgICAgKiByZXR1cm4gdmFsdWUgb2YgY29tcHV0ZToKICAgICAqCiAgICAgKiA8cHJlPgogICAgICogZnVuY3Rpb24gY29tcHV0ZShhLCBiKSB7IHJldHVybiBhICsgYiB9CiAgICAgKiBjb25zdCBtZW1vaXplZENvbXB1dGUgPSBtZW1vaXplKGNvbXB1dGUpOwogICAgICoKICAgICAqIGNvbXB1dGUoMywgNykgPT0gMTAKICAgICAqIGNvbXB1dGUoMywgNykgPT0gMTAgLy8gY2FjaGUgaGl0CiAgICAgKiA8L3ByZT4KICAgICAqCiAgICAgKiBDYWNoZSBpbnZhbGlkYXRpb24gaXMgY29tcGxpY2F0ZWQgYnkgbXV0YWJsZSBjbGFzc2VzIChTY2FsZXMgYW5kIERhdGFzZXRzKS4KICAgICAqIFRoZSBTaWduYXR1cmUgQVBJIGlzIGJ1aWx0IHRvIHNvbHZlIHRoaXMgaXNzdWUgYnkgY29uc3RydWN0aW5nIGFuIGltbXV0YWJsZQogICAgICogc25hcHNob3Qgb2YgU2NhbGVzL0RhdGFzZXRzIG9uIG1lbW9pemVkIGZ1bmN0aW9uIGludm9jYXRpb24sIHdoaWNoIGlzIGl0c2VsZgogICAgICogYSBwZXJmb3JtYW5jZSBoaXQuIFRodXMgd2UgaW50cm9kdWNlIGEgImRvTG9ja2VkIiBtZXRob2QgdGhhdCBtb21lbnRhcmlseQogICAgICogYnlwYXNzZXMgc2lnbi9jb21wYXJpc29uIGxvZ2ljIGFuZCBzaW1wbHkgcmV0dXJucyB0aGUgY2FjaGVkIHZhbHVlLgogICAgICoKICAgICAqIFNlZSB0aGUgU2lnbmF0dXJlIEFQSSBmb3IgbW9yZSBpbmZvcm1hdGlvbi4KICAgICAqCiAgICAgKiBAcGFyYW0ge0Z9IGNvbXB1dGUKICAgICAqIEByZXR1cm5zIHtNZW1vaXplZEZ1bmN0aW9uPEYgZXh0ZW5kcyBGdW5jdGlvbj59CiAgICAgKi8KICAgIGZ1bmN0aW9uIG1lbW9pemUoY29tcHV0ZSkgewogICAgICAgIHZhciBsYXN0U2lnbmF0dXJlID0gdW5kZWZpbmVkOwogICAgICAgIHZhciBsYXN0VmFsdWU7CiAgICAgICAgdmFyIGxvY2tlZCA9IGZhbHNlOwogICAgICAgIHZhciBsb2dQZXJmb3JtYW5jZSA9IGZhbHNlOwogICAgICAgIHZhciBtZW1vaXplRm4gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBhcmdzID0gW107CiAgICAgICAgICAgIGZvciAodmFyIF9pID0gMDsgX2kgPCBhcmd1bWVudHMubGVuZ3RoOyBfaSsrKSB7CiAgICAgICAgICAgICAgICBhcmdzW19pXSA9IGFyZ3VtZW50c1tfaV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGxvY2tlZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGxhc3RWYWx1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgaW5wdXRTaWduYXR1cmUgPSBzaWduYXR1cmUuc2lnbkFycmF5KGFyZ3MpOwogICAgICAgICAgICBpZiAobGFzdFNpZ25hdHVyZSA9PT0gdW5kZWZpbmVkCiAgICAgICAgICAgICAgICB8fCBsYXN0U2lnbmF0dXJlLmlzRGlmZmVyZW50KGlucHV0U2lnbmF0dXJlKSkgewogICAgICAgICAgICAgICAgaWYgKGxvZ1BlcmZvcm1hbmNlKSB7CiAgICAgICAgICAgICAgICAgICAgY29uc29sZS53YXJuKCJjYWNoZSBtaXNzISBjb21wdXRpbmciKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGxhc3RTaWduYXR1cmUgPSBpbnB1dFNpZ25hdHVyZTsKICAgICAgICAgICAgICAgIGxhc3RWYWx1ZSA9IGNvbXB1dGUuYXBwbHkodGhpcywgYXJncyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBpZiAobG9nUGVyZm9ybWFuY2UpIHsKICAgICAgICAgICAgICAgICAgICBjb25zb2xlLndhcm4oImNhY2hlIGhpdCEiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gbGFzdFZhbHVlOwogICAgICAgIH07CiAgICAgICAgbWVtb2l6ZUZuLmRvTG9ja2VkID0gZnVuY3Rpb24gKGNiKSB7CiAgICAgICAgICAgIGlmIChsb2NrZWQpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiTG9ja2luZyBhbiBhbHJlYWR5IGxvY2tlZCBtZW1vaXplIGZ1bmN0aW9uISIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxvY2tlZCA9IHRydWU7CiAgICAgICAgICAgIHZhciByZXRWYWwgPSBjYi5hcHBseSh0aGlzKTsKICAgICAgICAgICAgbG9ja2VkID0gZmFsc2U7CiAgICAgICAgICAgIHJldHVybiByZXRWYWw7CiAgICAgICAgfTsKICAgICAgICBtZW1vaXplRm4ubG9nUGVyZm9ybWFuY2UgPSBmdW5jdGlvbiAobG9nKSB7CiAgICAgICAgICAgIGlmIChsb2cgPT09IHZvaWQgMCkgeyBsb2cgPSB0cnVlOyB9CiAgICAgICAgICAgIGxvZ1BlcmZvcm1hbmNlID0gbG9nOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIHJldHVybiBtZW1vaXplRm47CiAgICB9CiAgICBleHBvcnRzLm1lbW9pemUgPSBtZW1vaXplOwogICAgfSk7CgogICAgdmFyIG1lbW9pemVQcm9qZWN0b3JzXzEgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIC8qKgogICAgICogQW4gaW5kZXggdGhhdCBzdG9yZXMgdmFsdWVzIGJ5IG51bWVyaWMga2V5LgogICAgICoKICAgICAqIEludGVybmFsbHkgdGhpcyB1c2VzIHByb3RvdHlwZS1sZXNzIG9iamVjdHMgYXMga2V5IGxvb2t1cHMgYXJlIG1hcmdpbmFsbHkKICAgICAqIGZhc3RlciB0aGFuIGB7fWBzLgogICAgICovCiAgICB2YXIgSW5kZXhNYXAgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gSW5kZXhNYXAoKSB7CiAgICAgICAgICAgIHRoaXMubWFwID0gT2JqZWN0LmNyZWF0ZShudWxsKTsKICAgICAgICAgICAgdGhpcy5leGlzdHMgPSBPYmplY3QuY3JlYXRlKG51bGwpOwogICAgICAgIH0KICAgICAgICBJbmRleE1hcC5wcm90b3R5cGUuZGVsZXRlID0gZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICBkZWxldGUgdGhpcy5tYXBba2V5XTsKICAgICAgICAgICAgZGVsZXRlIHRoaXMuZXhpc3RzW2tleV07CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH07CiAgICAgICAgSW5kZXhNYXAucHJvdG90eXBlLmdldCA9IGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMubWFwW2tleV07CiAgICAgICAgfTsKICAgICAgICBJbmRleE1hcC5wcm90b3R5cGUuaGFzID0gZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICByZXR1cm4gISF0aGlzLmV4aXN0c1trZXldOwogICAgICAgIH07CiAgICAgICAgSW5kZXhNYXAucHJvdG90eXBlLnNldCA9IGZ1bmN0aW9uIChrZXksIHZhbHVlKSB7CiAgICAgICAgICAgIHRoaXMubWFwW2tleV0gPSB2YWx1ZTsKICAgICAgICAgICAgdGhpcy5leGlzdHNba2V5XSA9IHRydWU7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEluZGV4TWFwOwogICAgfSgpKTsKICAgIC8qKgogICAgICogQSBsb2Rhc2gtc3R5bGUgYE1hcENhY2hlYCB0aGF0IHV0aWxpemVzIGEgW251bWJlciwgbnVtYmVyXSBrZXkgdG8gY3JlYXRlIGEKICAgICAqIGZhc3QtbG9va3VwIDJEIGluZGV4LiBUaGlzIGlzIG11Y2ggZmFzdGVyIHRoYW4gc3RyaW5naWZ5aW5nIHRoZSBrZXkuCiAgICAgKi8KICAgIHZhciBEYXRhc2V0SW5kZXhDYWNoZSA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBEYXRhc2V0SW5kZXhDYWNoZSgpIHsKICAgICAgICAgICAgdGhpcy5tYXAgPSBuZXcgSW5kZXhNYXAoKTsKICAgICAgICB9CiAgICAgICAgRGF0YXNldEluZGV4Q2FjaGUucHJvdG90eXBlLmdldCA9IGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMubWFwLmdldChrZXlbMF0pLmdldChrZXlbMV0pOwogICAgICAgIH07CiAgICAgICAgRGF0YXNldEluZGV4Q2FjaGUucHJvdG90eXBlLmhhcyA9IGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMubWFwLmhhcyhrZXlbMF0pICYmIHRoaXMubWFwLmdldChrZXlbMF0pLmhhcyhrZXlbMV0pOwogICAgICAgIH07CiAgICAgICAgRGF0YXNldEluZGV4Q2FjaGUucHJvdG90eXBlLnNldCA9IGZ1bmN0aW9uIChrZXksIHZhbHVlKSB7CiAgICAgICAgICAgIHRoaXMubWFwLmhhcyhrZXlbMF0pIHx8IHRoaXMubWFwLnNldChrZXlbMF0sIG5ldyBJbmRleE1hcCgpKTsKICAgICAgICAgICAgdGhpcy5tYXAuZ2V0KGtleVswXSkuc2V0KGtleVsxXSwgdmFsdWUpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIERhdGFzZXRJbmRleENhY2hlLnByb3RvdHlwZS5kZWxldGUgPSBmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgICAgIC8vIE5PVEU6IHRoaXMgY2FuIHBvdGVudGlhbGx5IGxlYXZlIGRhbmdsaW5nIGBJbmRleE1hcGBzIGlmIHdlIGRlbGV0ZQogICAgICAgICAgICAvLyBhbGwgdGhlIGtleXMgZnJvbSB0aGUgaW5kZXggaW5zdGVhZCBvZiB1c2luZyBgY2xlYXJgLiBUaGUgb3ZlcmhlYWQgaXMKICAgICAgICAgICAgLy8gbWluaW1hbCwgc28gdGhpcyBpcyBmaW5lLgogICAgICAgICAgICB0aGlzLm1hcC5oYXMoa2V5WzBdKSAmJiB0aGlzLm1hcC5nZXQoa2V5WzBdKS5kZWxldGUoa2V5WzFdKTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfTsKICAgICAgICBEYXRhc2V0SW5kZXhDYWNoZS5wcm90b3R5cGUuY2xlYXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMubWFwID0gbmV3IEluZGV4TWFwKCk7CiAgICAgICAgfTsKICAgICAgICBEYXRhc2V0SW5kZXhDYWNoZS5yZXNvbHZlciA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBbZGF0YXNldC51cGRhdGVJZCgpLCBpXTsgfTsKICAgICAgICByZXR1cm4gRGF0YXNldEluZGV4Q2FjaGU7CiAgICB9KCkpOwogICAgZnVuY3Rpb24gbWVtb2l6ZVByb2plY3Rvcihwcm9qZWN0b3IpIHsKICAgICAgICB2YXIgbWVtbyA9IGxvZGFzaC5tZW1vaXplKHByb2plY3RvciwgRGF0YXNldEluZGV4Q2FjaGUucmVzb2x2ZXIpOwogICAgICAgIG1lbW8uY2FjaGUgPSBuZXcgRGF0YXNldEluZGV4Q2FjaGUoKTsKICAgICAgICByZXR1cm4gbWVtbzsKICAgIH0KICAgIGV4cG9ydHMubWVtb2l6ZVByb2plY3RvciA9IG1lbW9pemVQcm9qZWN0b3I7CiAgICBmdW5jdGlvbiBtZW1vaXplUHJvamVjdG9ycyhhdHRyVG9Qcm9qZWN0b3IpIHsKICAgICAgICBPYmplY3Qua2V5cyhhdHRyVG9Qcm9qZWN0b3IpLmZvckVhY2goZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3Jba2V5XSA9IG1lbW9pemVQcm9qZWN0b3IoYXR0clRvUHJvamVjdG9yW2tleV0pOwogICAgICAgIH0pOwogICAgICAgIHJldHVybiBhdHRyVG9Qcm9qZWN0b3I7CiAgICB9CiAgICBleHBvcnRzLm1lbW9pemVQcm9qZWN0b3JzID0gbWVtb2l6ZVByb2plY3RvcnM7CiAgICB9KTsKCiAgICB2YXIgbWVtVGh1bmtfMSA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICogQGZpbGVvdmVydmlldyBJbXBsZW1lbnRzIGEgY29udmVuaWVudCB0aHVuayBmdW5jdGlvbiB0byBoYW5kbGUgdGhlIGNvbW1vbiBjYXNlCiAgICAgKiBvZiBjcmVhdGluZyBhIG1lbW9pemVkIGZ1bmN0aW9uIHRoYXQgdGFrZXMgaXRzIGlucHV0cyBmcm9tIG11dGFibGUgY2xhc3MgcHJvcGVydGllcy4KICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvKioKICAgICAqIEZpcnN0IHBhc3MgYXJndW1lbnQgdGh1bmtzIHRoYXQgd2lsbCBiZSBldmFsdWF0ZWQgd2hlbmV2ZXIgdGhlIG1lbVRodW5rCiAgICAgKiBpcyBhY2Nlc3NlZC4gVGhpcyBzaG91bGQgYmUgZmFzdCBhbmQgc2ltcGxlLgogICAgICoKICAgICAqIFRoZW4gcGFzcyBhIHB1cmUgZnVuY3Rpb24gdGhhdCwgd2hlbiBnaXZlbiB0aGUgYXJndW1lbnQgdGh1bmtzJyB2YWx1ZXMsCiAgICAgKiB3aWxsIG91dHB1dCBzb21lIGNvbXB1dGVkIHZhbHVlLiBJdCBzaG91bGQgbm90IHVzZSBgdGhpc2AgaW4gdGhlIGJvZHkuCiAgICAgKgogICAgICogV2UgbWVtb2l6ZSBhbmQgcmV0dXJuIHRoaXMgcHVyZSBmdW5jdGlvbi4KICAgICAqCiAgICAgKiBUaGlzIHdheSwgbWVtVGh1bmsgbGV0cyB5b3UgaW1wbGVtZW50IGEgcGVyZm9ybWFudCwgYWx3YXlzLXVwLXRvLWRhdGUgImNvbXB1dGVkIgogICAgICogdmFsdWUgZ2V0dGVyLgogICAgICovCiAgICBmdW5jdGlvbiBtZW1UaHVuaygpIHsKICAgICAgICB2YXIgYXJnc0FuZENvbXB1dGUgPSBbXTsKICAgICAgICBmb3IgKHZhciBfaSA9IDA7IF9pIDwgYXJndW1lbnRzLmxlbmd0aDsgX2krKykgewogICAgICAgICAgICBhcmdzQW5kQ29tcHV0ZVtfaV0gPSBhcmd1bWVudHNbX2ldOwogICAgICAgIH0KICAgICAgICB2YXIgaW5wdXRzID0gYXJnc0FuZENvbXB1dGUuc2xpY2UoMCwgLTEpOwogICAgICAgIHZhciBjb21wdXRlID0gYXJnc0FuZENvbXB1dGVbYXJnc0FuZENvbXB1dGUubGVuZ3RoIC0gMV07CiAgICAgICAgdmFyIG1lbW9pemVkQ29tcHV0ZSA9IG1lbW9pemUubWVtb2l6ZShjb21wdXRlKTsKICAgICAgICB2YXIgbWVtb2l6ZWRUaHVuayA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGlucHV0RXZhbCA9IGlucHV0cy5tYXAoZnVuY3Rpb24gKGlucHV0Rm4pIHsgcmV0dXJuIGlucHV0Rm4uYXBwbHkoX3RoaXMpOyB9KTsKICAgICAgICAgICAgcmV0dXJuIG1lbW9pemVkQ29tcHV0ZS5hcHBseSh1bmRlZmluZWQsIGlucHV0RXZhbCk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gbWVtb2l6ZWRUaHVuazsKICAgIH0KICAgIGV4cG9ydHMubWVtVGh1bmsgPSBtZW1UaHVuazsKICAgIH0pOwoKICAgIHZhciBtZW1vaXplID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihtZW1vaXplXzEsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihtZW1vaXplUHJvamVjdG9yc18xLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIobWVtVGh1bmtfMSwgZXhwb3J0cyk7CgogICAgZXhwb3J0cy5zaWduID0gc2lnbmF0dXJlLnNpZ247CiAgICB9KTsKCiAgICB2YXIgY2FudmFzRHJhd2VyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgogICAgLyoqCiAgICAgKiBBIENhbnZhc0RyYXdlciBkcmF3cyBkYXRhIG9udG8gYSBzdXBwbGllZCBDYW52YXMgQ29udGV4dC4KICAgICAqCiAgICAgKiBUaGlzIGNsYXNzIGlzIGltbXV0YWJsZSAoYnV0IGhhcyBpbnRlcm5hbCBzdGF0ZSkgYW5kIHNob3VsZG4ndCBiZSBleHRlbmRlZC4KICAgICAqLwogICAgdmFyIENhbnZhc0RyYXdlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICAvKioKICAgICAgICAgKiBAcGFyYW0gX2NvbnRleHQgVGhlIGNvbnRleHQgZm9yIGEgY2FudmFzIHRoYXQgdGhpcyBkcmF3ZXIgd2lsbCBkcmF3IHRvLgogICAgICAgICAqIEBwYXJhbSBfZHJhd1N0ZXAgVGhlIGRyYXcgc3RlcCBsb2dpYyB0aGF0IGFjdHVhbGx5IGRyYXdzLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIENhbnZhc0RyYXdlcihfY29udGV4dCwgX2RyYXdTdGVwKSB7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQgPSBfY29udGV4dDsKICAgICAgICAgICAgdGhpcy5fZHJhd1N0ZXAgPSBfZHJhd1N0ZXA7CiAgICAgICAgfQogICAgICAgIC8vIHB1YmxpYyBmb3IgdGVzdGluZwogICAgICAgIENhbnZhc0RyYXdlci5wcm90b3R5cGUuZ2V0RHJhd1N0ZXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kcmF3U3RlcDsKICAgICAgICB9OwogICAgICAgIENhbnZhc0RyYXdlci5wcm90b3R5cGUuZHJhdyA9IGZ1bmN0aW9uIChkYXRhLCBhcHBsaWVkRHJhd1N0ZXBzKSB7CiAgICAgICAgICAgIHZhciBwcm9qZWN0b3IgPSBhcHBsaWVkRHJhd1N0ZXBzW2FwcGxpZWREcmF3U3RlcHMubGVuZ3RoIC0gMV0uYXR0clRvQXBwbGllZFByb2plY3RvcjsKICAgICAgICAgICAgLy8gZG9uJ3Qgc3VwcG9ydCBhbmltYXRpb25zIGZvciBub3c7IGp1c3QgZHJhdyB0aGUgbGFzdCBkcmF3IHN0ZXAgaW1tZWRpYXRlbHkKICAgICAgICAgICAgdGhpcy5fY29udGV4dC5zYXZlKCk7CiAgICAgICAgICAgIHRoaXMuX2RyYXdTdGVwKHRoaXMuX2NvbnRleHQsIGRhdGEsIHByb2plY3Rvcik7CiAgICAgICAgICAgIHRoaXMuX2NvbnRleHQucmVzdG9yZSgpOwogICAgICAgIH07CiAgICAgICAgQ2FudmFzRHJhd2VyLnByb3RvdHlwZS5nZXRWaXN1YWxQcmltaXRpdmVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgfTsKICAgICAgICBDYW52YXNEcmF3ZXIucHJvdG90eXBlLmdldFZpc3VhbFByaW1pdGl2ZUF0SW5kZXggPSBmdW5jdGlvbiAoaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfTsKICAgICAgICBDYW52YXNEcmF3ZXIucHJvdG90eXBlLnJlbW92ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgLy8gTk8gb3AgLSBjYW52YXMgZWxlbWVudCBvd25zIHRoZSBjYW52YXM7IGNvbnRleHQgaXMgZnJlZQogICAgICAgIH07CiAgICAgICAgcmV0dXJuIENhbnZhc0RyYXdlcjsKICAgIH0oKSk7CiAgICBleHBvcnRzLkNhbnZhc0RyYXdlciA9IENhbnZhc0RyYXdlcjsKICAgIGV4cG9ydHMuQ29udGV4dFN0eWxlQXR0cnMgPSBbCiAgICAgICAgImZpbGwtb3BhY2l0eSIsCiAgICAgICAgImZpbGwiLAogICAgICAgICJvcGFjaXR5IiwKICAgICAgICAic3Ryb2tlLW9wYWNpdHkiLAogICAgICAgICJzdHJva2Utd2lkdGgiLAogICAgICAgICJzdHJva2UiLAogICAgICAgICJzdHJva2UtZGFzaGFycmF5IiwKICAgIF07CiAgICAvKioKICAgICAqIERFUFJFQ0FURUQuIFByZWNvbXB1dGUgdGhlIGNvbmNhdHRlZCBhcnJheSBhbmQgdXNlIGByZXNvbHZlQXR0cmlidXRlc2AKICAgICAqIGluc3RlYWQgb2YgdXNpbmcgdGhpcyBpbiB0aGUgaW5uZXIgbG9vcC4KICAgICAqLwogICAgZnVuY3Rpb24gcmVzb2x2ZUF0dHJpYnV0ZXNTdWJzZXRXaXRoU3R5bGVzKHByb2plY3RvciwgZXh0cmFLZXlzLCBkYXR1bSwgaW5kZXgpIHsKICAgICAgICB2YXIgYXR0cktleXMgPSBleHBvcnRzLkNvbnRleHRTdHlsZUF0dHJzLmNvbmNhdChleHRyYUtleXMpOwogICAgICAgIHJldHVybiByZXNvbHZlQXR0cmlidXRlcyhwcm9qZWN0b3IsIGF0dHJLZXlzLCBkYXR1bSwgaW5kZXgpOwogICAgfQogICAgZXhwb3J0cy5yZXNvbHZlQXR0cmlidXRlc1N1YnNldFdpdGhTdHlsZXMgPSByZXNvbHZlQXR0cmlidXRlc1N1YnNldFdpdGhTdHlsZXM7CiAgICBmdW5jdGlvbiByZXNvbHZlQXR0cmlidXRlcyhwcm9qZWN0b3IsIGF0dHJLZXlzLCBkYXR1bSwgaW5kZXgpIHsKICAgICAgICB2YXIgYXR0cnMgPSB7fTsKICAgICAgICBmb3IgKHZhciBfaSA9IDAsIGF0dHJLZXlzXzEgPSBhdHRyS2V5czsgX2kgPCBhdHRyS2V5c18xLmxlbmd0aDsgX2krKykgewogICAgICAgICAgICB2YXIgYXR0cktleSA9IGF0dHJLZXlzXzFbX2ldOwogICAgICAgICAgICBpZiAocHJvamVjdG9yLmhhc093blByb3BlcnR5KGF0dHJLZXkpKSB7CiAgICAgICAgICAgICAgICBhdHRyc1thdHRyS2V5XSA9IHByb2plY3RvclthdHRyS2V5XShkYXR1bSwgaW5kZXgpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBhdHRyczsKICAgIH0KICAgIGV4cG9ydHMucmVzb2x2ZUF0dHJpYnV0ZXMgPSByZXNvbHZlQXR0cmlidXRlczsKICAgIGZ1bmN0aW9uIGdldFN0cm9rZU9wYWNpdHkoc3R5bGUpIHsKICAgICAgICB2YXIgYmFzZU9wYWNpdHkgPSBzdHlsZVsib3BhY2l0eSJdICE9IG51bGwgPyBwYXJzZUZsb2F0KHN0eWxlWyJvcGFjaXR5Il0pIDogMTsKICAgICAgICB2YXIgc3Ryb2tlT3BhY2l0eSA9IHN0eWxlWyJzdHJva2Utb3BhY2l0eSJdICE9IG51bGwgPyBwYXJzZUZsb2F0KHN0eWxlWyJzdHJva2Utb3BhY2l0eSJdKSA6IDE7CiAgICAgICAgcmV0dXJuIHN0cm9rZU9wYWNpdHkgKiBiYXNlT3BhY2l0eTsKICAgIH0KICAgIGZ1bmN0aW9uIGdldEZpbGxPcGFjaXR5KHN0eWxlKSB7CiAgICAgICAgdmFyIGJhc2VPcGFjaXR5ID0gc3R5bGVbIm9wYWNpdHkiXSAhPSBudWxsID8gcGFyc2VGbG9hdChzdHlsZVsib3BhY2l0eSJdKSA6IDE7CiAgICAgICAgdmFyIGZpbGxPcGFjaXR5ID0gc3R5bGVbImZpbGwtb3BhY2l0eSJdICE9IG51bGwgPyBwYXJzZUZsb2F0KHN0eWxlWyJmaWxsLW9wYWNpdHkiXSkgOiAxOwogICAgICAgIHJldHVybiBmaWxsT3BhY2l0eSAqIGJhc2VPcGFjaXR5OwogICAgfQogICAgZnVuY3Rpb24gZ2V0U3Ryb2tlV2lkdGgoc3R5bGUpIHsKICAgICAgICByZXR1cm4gc3R5bGVbInN0cm9rZS13aWR0aCJdICE9IG51bGwgPyBwYXJzZUZsb2F0KHN0eWxlWyJzdHJva2Utd2lkdGgiXSkgOiAxOwogICAgfQogICAgZXhwb3J0cy5nZXRTdHJva2VXaWR0aCA9IGdldFN0cm9rZVdpZHRoOwogICAgZnVuY3Rpb24gZ2V0U3Ryb2tlRGFzaEFycmF5KHN0eWxlKSB7CiAgICAgICAgdmFyIHJhd1ZhbHVlID0gc3R5bGVbInN0cm9rZS1kYXNoYXJyYXkiXTsKICAgICAgICBpZiAocmF3VmFsdWUgIT0gbnVsbCkgewogICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgcmV0dXJuIHJhd1ZhbHVlLnNwbGl0KC9bICxdKy8pLm1hcChmdW5jdGlvbiAoeCkgeyByZXR1cm4gcGFyc2VJbnQoeCwgMTApOyB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjYXRjaCAoZSkgewogICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcigiZ2V0U3Ryb2tlRGFzaEFycmF5IGZhaWxlZCB3aXRoOiAiICsgZSk7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIFtdOwogICAgfQogICAgZXhwb3J0cy5nZXRTdHJva2VEYXNoQXJyYXkgPSBnZXRTdHJva2VEYXNoQXJyYXk7CiAgICBmdW5jdGlvbiByZW5kZXJBcmVhKGNvbnRleHQsIGQzQXJlYSwgZGF0YSwgc3R5bGUpIHsKICAgICAgICBjb250ZXh0LnNhdmUoKTsKICAgICAgICBjb250ZXh0LmJlZ2luUGF0aCgpOwogICAgICAgIGQzQXJlYS5jb250ZXh0KGNvbnRleHQpOwogICAgICAgIGQzQXJlYShkYXRhKTsKICAgICAgICBjb250ZXh0LmxpbmVKb2luID0gInJvdW5kIjsKICAgICAgICByZW5kZXJQYXRoV2l0aFN0eWxlKGNvbnRleHQsIHN0eWxlKTsKICAgICAgICBjb250ZXh0LnJlc3RvcmUoKTsKICAgIH0KICAgIGV4cG9ydHMucmVuZGVyQXJlYSA9IHJlbmRlckFyZWE7CiAgICBmdW5jdGlvbiByZW5kZXJMaW5lKGNvbnRleHQsIGQzTGluZSwgZGF0YSwgc3R5bGUpIHsKICAgICAgICBjb250ZXh0LnNhdmUoKTsKICAgICAgICBjb250ZXh0LmJlZ2luUGF0aCgpOwogICAgICAgIGQzTGluZS5jb250ZXh0KGNvbnRleHQpOwogICAgICAgIGQzTGluZShkYXRhKTsKICAgICAgICBjb250ZXh0LmxpbmVKb2luID0gInJvdW5kIjsKICAgICAgICByZW5kZXJQYXRoV2l0aFN0eWxlKGNvbnRleHQsIHN0eWxlKTsKICAgICAgICBjb250ZXh0LnJlc3RvcmUoKTsKICAgIH0KICAgIGV4cG9ydHMucmVuZGVyTGluZSA9IHJlbmRlckxpbmU7CiAgICBmdW5jdGlvbiByZW5kZXJQYXRoV2l0aFN0eWxlKGNvbnRleHQsIHN0eWxlKSB7CiAgICAgICAgaWYgKHN0eWxlWyJzdHJva2UiXSkgewogICAgICAgICAgICBjb250ZXh0LmxpbmVXaWR0aCA9IGdldFN0cm9rZVdpZHRoKHN0eWxlKTsKICAgICAgICAgICAgdmFyIHN0cm9rZUNvbG9yID0gZDMuY29sb3Ioc3R5bGVbInN0cm9rZSJdKTsKICAgICAgICAgICAgdmFyIHN0cm9rZURhc2hBcnJheSA9IGdldFN0cm9rZURhc2hBcnJheShzdHlsZSk7CiAgICAgICAgICAgIGNvbnRleHQuc2V0TGluZURhc2goc3Ryb2tlRGFzaEFycmF5KTsKICAgICAgICAgICAgc3Ryb2tlQ29sb3Iub3BhY2l0eSAqPSBnZXRTdHJva2VPcGFjaXR5KHN0eWxlKTsKICAgICAgICAgICAgY29udGV4dC5zdHJva2VTdHlsZSA9IHN0cm9rZUNvbG9yLnRvU3RyaW5nKCk7CiAgICAgICAgICAgIGNvbnRleHQuc3Ryb2tlKCk7CiAgICAgICAgfQogICAgICAgIGlmIChzdHlsZVsiZmlsbCJdKSB7CiAgICAgICAgICAgIHZhciBmaWxsQ29sb3IgPSBkMy5jb2xvcihzdHlsZVsiZmlsbCJdKTsKICAgICAgICAgICAgZmlsbENvbG9yLm9wYWNpdHkgKj0gZ2V0RmlsbE9wYWNpdHkoc3R5bGUpOwogICAgICAgICAgICBjb250ZXh0LmZpbGxTdHlsZSA9IGZpbGxDb2xvci50b1N0cmluZygpOwogICAgICAgICAgICBjb250ZXh0LmZpbGwoKTsKICAgICAgICB9CiAgICB9CiAgICBleHBvcnRzLnJlbmRlclBhdGhXaXRoU3R5bGUgPSByZW5kZXJQYXRoV2l0aFN0eWxlOwogICAgfSk7CgogICAgdmFyIGRyYXdlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgLyoqCiAgICAgKiBBIERyYXdlciBpcyBhIHN0YXRlZnVsIGNsYXNzIHRoYXQgaG9sZHMgb25lIFNWR0RyYXdlciBhbmQgb25lIENhbnZhc0RyYXdlciwgYW5kIGNhbiBzd2l0Y2ggYmV0d2VlbgogICAgICogdGhlIHR3by4KICAgICAqLwogICAgdmFyIFByb3h5RHJhd2VyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKCkgewogICAgICAgIC8qKgogICAgICAgICAqIEEgRHJhd2VyIGRyYXdzIHN2ZyBlbGVtZW50cyBiYXNlZCBvbiB0aGUgaW5wdXQgRGF0YXNldC4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSBfc3ZnRHJhd2VyRmFjdG9yeSBBIGZhY3RvcnkgdGhhdCB3aWxsIGJlIGludm9rZWQgdG8gY3JlYXRlIGFuIFNWR0RyYXdlciB3aGVuZXZlciB1c2VTVkcgaXMgY2FsbGVkCiAgICAgICAgICogQHBhcmFtIF9jYW52YXNEcmF3U3RlcCBUaGUgRHJhd1N0ZXAgdG8gYmUgZmVkIGludG8gYSBuZXcgQ2FudmFzRHJhd2VyIHdoZW5ldmVyIHVzZUNhbnZhcyBpcyBjYWxsZWQKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBQcm94eURyYXdlcihfc3ZnRHJhd2VyRmFjdG9yeSwgX2NhbnZhc0RyYXdlckZhY3RvcnkpIHsKICAgICAgICAgICAgdGhpcy5fc3ZnRHJhd2VyRmFjdG9yeSA9IF9zdmdEcmF3ZXJGYWN0b3J5OwogICAgICAgICAgICB0aGlzLl9jYW52YXNEcmF3ZXJGYWN0b3J5ID0gX2NhbnZhc0RyYXdlckZhY3Rvcnk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZSB0aGUgb2xkIGRyYXdlciBhbmQgdXNlIFNWRyByZW5kZXJpbmcgZnJvbSBub3cgb24uCiAgICAgICAgICovCiAgICAgICAgUHJveHlEcmF3ZXIucHJvdG90eXBlLnVzZVNWRyA9IGZ1bmN0aW9uIChwYXJlbnQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2N1cnJlbnREcmF3ZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fY3VycmVudERyYXdlci5yZW1vdmUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgc3ZnRHJhd2VyID0gdGhpcy5fc3ZnRHJhd2VyRmFjdG9yeSgpOwogICAgICAgICAgICBzdmdEcmF3ZXIuYXR0YWNoVG8ocGFyZW50KTsKICAgICAgICAgICAgdGhpcy5fY3VycmVudERyYXdlciA9IHN2Z0RyYXdlcjsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJlbW92ZSB0aGUgb2xkIGRyYXdlciBhbmQgdXNlIENhbnZhcyByZW5kZXJpbmcgZnJvbSBub3cgb24uCiAgICAgICAgICovCiAgICAgICAgUHJveHlEcmF3ZXIucHJvdG90eXBlLnVzZUNhbnZhcyA9IGZ1bmN0aW9uIChjYW52YXMpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2N1cnJlbnREcmF3ZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fY3VycmVudERyYXdlci5yZW1vdmUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jdXJyZW50RHJhd2VyID0gdGhpcy5fY2FudmFzRHJhd2VyRmFjdG9yeShjYW52YXMubm9kZSgpLmdldENvbnRleHQoIjJkIikpOwogICAgICAgIH07CiAgICAgICAgLy8gcHVibGljIGZvciB0ZXN0aW5nCiAgICAgICAgUHJveHlEcmF3ZXIucHJvdG90eXBlLmdldERyYXdlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2N1cnJlbnREcmF3ZXI7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZW1vdmVzIHRoaXMgRHJhd2VyJ3MgcmVuZGVyQXJlYQogICAgICAgICAqLwogICAgICAgIFByb3h5RHJhd2VyLnByb3RvdHlwZS5yZW1vdmUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9jdXJyZW50RHJhd2VyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2N1cnJlbnREcmF3ZXIucmVtb3ZlKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFByb3h5RHJhd2VyLnByb3RvdHlwZS5kcmF3ID0gZnVuY3Rpb24gKGRhdGEsIGRyYXdTdGVwcykgewogICAgICAgICAgICB0aGlzLl9jdXJyZW50RHJhd2VyLmRyYXcoZGF0YSwgZHJhd1N0ZXBzKTsKICAgICAgICB9OwogICAgICAgIFByb3h5RHJhd2VyLnByb3RvdHlwZS5nZXRWaXN1YWxQcmltaXRpdmVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fY3VycmVudERyYXdlci5nZXRWaXN1YWxQcmltaXRpdmVzKCk7CiAgICAgICAgfTsKICAgICAgICBQcm94eURyYXdlci5wcm90b3R5cGUuZ2V0VmlzdWFsUHJpbWl0aXZlQXRJbmRleCA9IGZ1bmN0aW9uIChpbmRleCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fY3VycmVudERyYXdlci5nZXRWaXN1YWxQcmltaXRpdmVBdEluZGV4KGluZGV4KTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBQcm94eURyYXdlcjsKICAgIH0oKSk7CiAgICBleHBvcnRzLlByb3h5RHJhd2VyID0gUHJveHlEcmF3ZXI7CiAgICB9KTsKCiAgICB2YXIgc3ZnRHJhd2VyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKICAgIC8qKgogICAgICogQW4gU1ZHRHJhd2VyIGRyYXdzIGRhdGEgYnkgY3JlYXRpbmcgRE9NIGVsZW1lbnRzIGFuZCBzZXR0aW5nIHNwZWNpZmljIGF0dHJpYnV0ZXMgb24gdGhlbQogICAgICogdG8gYWNjdXJhdGVseSByZWZsZWN0IHRoZSBkYXRhIGJlaW5nIHBhc3NlZCBpbi4KICAgICAqCiAgICAgKiBUaGlzIGNsYXNzIGlzIGltbXV0YWJsZSAoYnV0IGhhcyBpbnRlcm5hbCBzdGF0ZSkuCiAgICAgKi8KICAgIHZhciBTVkdEcmF3ZXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgLyoqCiAgICAgICAgICogQHBhcmFtIHN2Z0VsZW1lbnROYW1lIGFuIEhUTUwvU1ZHIHRhZyBuYW1lIHRvIGJlIGNyZWF0ZWQsIG9uZSBwZXIgZGF0dW0uCiAgICAgICAgICogQHBhcmFtIGNsYXNzTmFtZSBDU1MgY2xhc3NlcyB0byBiZSBhcHBsaWVkIHRvIHRoZSBkcmF3biBwcmltaXRpdmVzLgogICAgICAgICAqIEBwYXJhbSBhcHBseURlZmF1bHRBdHRyaWJ1dGVzCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gU1ZHRHJhd2VyKHN2Z0VsZW1lbnROYW1lLCBjbGFzc05hbWUpIHsKICAgICAgICAgICAgdGhpcy5fcm9vdCA9IGQzLnNlbGVjdChkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiwgImciKSk7CiAgICAgICAgICAgIHRoaXMuX2NsYXNzTmFtZSA9IGNsYXNzTmFtZTsKICAgICAgICAgICAgdGhpcy5fc3ZnRWxlbWVudE5hbWUgPSBzdmdFbGVtZW50TmFtZTsKICAgICAgICB9CiAgICAgICAgU1ZHRHJhd2VyLnByb3RvdHlwZS5kcmF3ID0gZnVuY3Rpb24gKGRhdGEsIGFwcGxpZWREcmF3U3RlcHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgLyoKICAgICAgICAgICAgICogRHJhdyB0byB0aGUgRE9NIGJ5IGNsZWFyaW5nIG9sZCBET00gZWxlbWVudHMsIGFkZGluZyBuZXcgRE9NIGVsZW1lbnRzLAogICAgICAgICAgICAgKiBhbmQgdGhlbiBwYXNzaW5nIHRob3NlIERPTSBlbGVtZW50cyB0byB0aGUgYW5pbWF0b3IsIHdoaWNoIHdpbGwgc2V0IHRoZQogICAgICAgICAgICAgKiBhcHByb3ByaWF0ZSBhdHRyaWJ1dGVzIG9uIHRoZSBET00uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9jcmVhdGVBbmREZXN0cm95RE9NRWxlbWVudHMoZGF0YSk7CiAgICAgICAgICAgIHZhciBkZWxheSA9IDA7CiAgICAgICAgICAgIHZhciBkcmF3TGVuZ3RoID0gYXBwbGllZERyYXdTdGVwcy5sZW5ndGg7CiAgICAgICAgICAgIHZhciBfbG9vcF8xID0gZnVuY3Rpb24gKGkpIHsKICAgICAgICAgICAgICAgIHZhciBkcmF3U3RlcCA9IGFwcGxpZWREcmF3U3RlcHNbaV07CiAgICAgICAgICAgICAgICB1dGlscyQxLldpbmRvdy5zZXRUaW1lb3V0KGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9kcmF3U3RlcChkcmF3U3RlcCk7IH0sIGRlbGF5KTsKICAgICAgICAgICAgICAgIGRlbGF5ICs9IGRyYXdTdGVwLmFuaW1hdG9yLnRvdGFsVGltZShkYXRhLmxlbmd0aCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgZHJhd0xlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBfbG9vcF8xKGkpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTVkdEcmF3ZXIucHJvdG90eXBlLmdldFZpc3VhbFByaW1pdGl2ZXMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9jYWNoZWRWaXN1YWxQcmltaXRpdmVzTm9kZXMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2FjaGVkVmlzdWFsUHJpbWl0aXZlc05vZGVzID0gdGhpcy5fc2VsZWN0aW9uLm5vZGVzKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NhY2hlZFZpc3VhbFByaW1pdGl2ZXNOb2RlczsKICAgICAgICB9OwogICAgICAgIFNWR0RyYXdlci5wcm90b3R5cGUuZ2V0VmlzdWFsUHJpbWl0aXZlQXRJbmRleCA9IGZ1bmN0aW9uIChpbmRleCkgewogICAgICAgICAgICBpZiAodGhpcy5fY2FjaGVkVmlzdWFsUHJpbWl0aXZlc05vZGVNYXAgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NhY2hlZFZpc3VhbFByaW1pdGl2ZXNOb2RlTWFwLmdldChpbmRleCk7CiAgICAgICAgfTsKICAgICAgICBTVkdEcmF3ZXIucHJvdG90eXBlLnJlbW92ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fcm9vdC5yZW1vdmUoKTsKICAgICAgICB9OwogICAgICAgIFNWR0RyYXdlci5wcm90b3R5cGUuYXR0YWNoVG8gPSBmdW5jdGlvbiAocGFyZW50KSB7CiAgICAgICAgICAgIHBhcmVudC5ub2RlKCkuYXBwZW5kQ2hpbGQodGhpcy5fcm9vdC5ub2RlKCkpOwogICAgICAgIH07CiAgICAgICAgLy8gcHVibGljIGZvciB0ZXN0aW5nCiAgICAgICAgU1ZHRHJhd2VyLnByb3RvdHlwZS5nZXRSb290ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fcm9vdDsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIENTUyBzZWxlY3RvciBmb3IgdGhpcyBEcmF3ZXIncyB2aXN1YWwgZWxlbWVudHMuCiAgICAgICAgICovCiAgICAgICAgU1ZHRHJhd2VyLnByb3RvdHlwZS5zZWxlY3RvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3N2Z0VsZW1lbnROYW1lOwogICAgICAgIH07CiAgICAgICAgU1ZHRHJhd2VyLnByb3RvdHlwZS5fYXBwbHlEZWZhdWx0QXR0cmlidXRlcyA9IGZ1bmN0aW9uIChzZWxlY3Rpb24pIHsKICAgICAgICAgICAgLy8gc3ViY2xhc3NlcyBtYXkgb3ZlcnJpZGUKICAgICAgICB9OwogICAgICAgIFNWR0RyYXdlci5wcm90b3R5cGUuX2NyZWF0ZUFuZERlc3Ryb3lET01FbGVtZW50cyA9IGZ1bmN0aW9uIChkYXRhKSB7CiAgICAgICAgICAgIC8vIGZpcnN0IHN0b3JlIHNvdXJjZSBkYXRhIGluZGV4IGJlZm9yZSBhbnkgZmlsdGVyaW5nIHRha2VzIHBsYWNlCiAgICAgICAgICAgIHZhciBtYXBwZWREYXRhID0gZGF0YS5tYXAoZnVuY3Rpb24gKGQsIGkpIHsgcmV0dXJuIGQgIT0gbnVsbCA/IHsgZDogZCwgaTogaSB9IDogbnVsbDsgfSk7CiAgICAgICAgICAgIC8vIFdoZXJlYXMgY2FudmFzIHJlbmRlcnMgY2FuIGNvcGUgd2l0aCBudWxsIGRhdGEgdmFsdWVzLCBzdmcgcmVuZGVyZXIKICAgICAgICAgICAgLy8gYXR0cmlidXRlIGFjY2Vzc29ycyBhc3N1bWUgbm9uLW51bGwgZGF0YSB2YWx1ZXMsIHNvIHdlIG11c3QgZmlsdGVyIHRoZW0KICAgICAgICAgICAgLy8gb3V0LiBVbmZvcnR1bmF0ZWx5LCB0aGlzIG1lYW5zIHRoZSBpbmRleCBwYXNzZWQgdG8gZWFjaCBhY2Nlc3NvciB3aWxsCiAgICAgICAgICAgIC8vIG5vdCBuZWNlc3NhcmlseSBtYXRjaCB0aGUgaW5kZXggb2YgdGhlIGRhdHVtIGluIHRoZSBkYXRhc2V0LgogICAgICAgICAgICB2YXIgZmlsdGVyZWREYXRhID0gbWFwcGVkRGF0YS5maWx0ZXIoZnVuY3Rpb24gKGQpIHsgcmV0dXJuIGQgIT0gbnVsbDsgfSk7CiAgICAgICAgICAgIHZhciBkYXRhRWxlbWVudHNVcGRhdGUgPSB0aGlzLl9yb290LnNlbGVjdEFsbCh0aGlzLnNlbGVjdG9yKCkpLmRhdGEoZmlsdGVyZWREYXRhKTsKICAgICAgICAgICAgdGhpcy5fc2VsZWN0aW9uID0gZGF0YUVsZW1lbnRzVXBkYXRlCiAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgLmFwcGVuZCh0aGlzLl9zdmdFbGVtZW50TmFtZSkKICAgICAgICAgICAgICAgIC5tZXJnZShkYXRhRWxlbWVudHNVcGRhdGUpOwogICAgICAgICAgICBkYXRhRWxlbWVudHNVcGRhdGUuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICAvLyBidWlsZCBtYXAgb2Ygc291cmNlIGRhdGEgaW5kZXggdG8gRWxlbWVudAogICAgICAgICAgICB2YXIgbmV3TWFwID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGlvbi5lYWNoKGZ1bmN0aW9uIChkYXRhQW5kSW5kZXgpIHsKICAgICAgICAgICAgICAgIC8vIFRPRE8gb3B0aW9uYWxseSBhdHRhY2ggZGF0YSBhdHRyaWJ1dGVzIHRvIEVsZW1lbnQKICAgICAgICAgICAgICAgIC8vIHRoaXMuc2V0QXR0cmlidXRlKCJkYXRhLXNvdXJjZS1kYXRhIiwgZGF0YUFuZEluZGV4LmQpOwogICAgICAgICAgICAgICAgLy8gdGhpcy5zZXRBdHRyaWJ1dGUoImRhdGEtc291cmNlLWluZGV4IiwgZGF0YUFuZEluZGV4LmkpOwogICAgICAgICAgICAgICAgbmV3TWFwLnNldChkYXRhQW5kSW5kZXguaSwgdGhpcyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9jYWNoZWRWaXN1YWxQcmltaXRpdmVzTm9kZU1hcCA9IG5ld01hcDsKICAgICAgICAgICAgdGhpcy5fY2FjaGVkVmlzdWFsUHJpbWl0aXZlc05vZGVzID0gbnVsbDsKICAgICAgICAgICAgLy8gdW53cmFwIGRhdGEgbm93IHRoYXQgZWxlbWVudHMgbWF0Y2ggdGhlaXIgb3JpZ2luYWwgZGF0YSBpbmRleAogICAgICAgICAgICB0aGlzLl9zZWxlY3Rpb24uZGF0YSh0aGlzLl9zZWxlY3Rpb24uZGF0YSgpLm1hcChmdW5jdGlvbiAoX2EpIHsKICAgICAgICAgICAgICAgIHZhciBkID0gX2EuZDsKICAgICAgICAgICAgICAgIHJldHVybiBkOwogICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIGlmICh0aGlzLl9jbGFzc05hbWUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5fc2VsZWN0aW9uLmNsYXNzZWQodGhpcy5fY2xhc3NOYW1lLCB0cnVlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9hcHBseURlZmF1bHRBdHRyaWJ1dGVzKHRoaXMuX3NlbGVjdGlvbik7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBEcmF3cyBkYXRhIHVzaW5nIG9uZSBzdGVwCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW17QXBwbGllZERyYXdTdGVwfSBzdGVwIFRoZSBzdGVwLCBob3cgZGF0YSBzaG91bGQgYmUgZHJhd24uCiAgICAgICAgICovCiAgICAgICAgU1ZHRHJhd2VyLnByb3RvdHlwZS5fZHJhd1N0ZXAgPSBmdW5jdGlvbiAoc3RlcCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgY29sb3JBdHRyaWJ1dGVzID0gWyJmaWxsIiwgInN0cm9rZSJdOwogICAgICAgICAgICBjb2xvckF0dHJpYnV0ZXMuZm9yRWFjaChmdW5jdGlvbiAoY29sb3JBdHRyaWJ1dGUpIHsKICAgICAgICAgICAgICAgIGlmIChzdGVwLmF0dHJUb0FwcGxpZWRQcm9qZWN0b3JbY29sb3JBdHRyaWJ1dGVdICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fc2VsZWN0aW9uLmF0dHIoY29sb3JBdHRyaWJ1dGUsIHN0ZXAuYXR0clRvQXBwbGllZFByb2plY3Rvcltjb2xvckF0dHJpYnV0ZV0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgc3RlcC5hbmltYXRvci5hbmltYXRlKHRoaXMuX3NlbGVjdGlvbiwgc3RlcC5hdHRyVG9BcHBsaWVkUHJvamVjdG9yKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2NsYXNzTmFtZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9zZWxlY3Rpb24uY2xhc3NlZCh0aGlzLl9jbGFzc05hbWUsIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gU1ZHRHJhd2VyOwogICAgfSgpKTsKICAgIGV4cG9ydHMuU1ZHRHJhd2VyID0gU1ZHRHJhd2VyOwogICAgfSk7CgogICAgdmFyIGRlZmVycmVkUmVuZGVyZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE3LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKICAgIC8qKgogICAgICogU3RvcmVzIHRoZSBkZWZlcnJlZCB0cmFuc2Zvcm1hdGlvbiBzdGF0ZSBmb3IgYSBzaW5nbGUgc2NhbGUuCiAgICAgKi8KICAgIHZhciBEb21haW5UcmFuc2Zvcm0gPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoKSB7CiAgICAgICAgZnVuY3Rpb24gRG9tYWluVHJhbnNmb3JtKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB0aGlzLnNjYWxlID0gMDsKICAgICAgICAgICAgdGhpcy50cmFuc2xhdGUgPSAwOwogICAgICAgICAgICB0aGlzLmNhY2hlZERvbWFpbiA9IFtudWxsLCBudWxsXTsKICAgICAgICAgICAgdGhpcy5sYXN0U2VlbkRvbWFpbiA9IFtudWxsLCBudWxsXTsKICAgICAgICAgICAgdGhpcy51cGRhdGVEb21haW4gPSBmdW5jdGlvbiAoc2NhbGUpIHsKICAgICAgICAgICAgICAgIF90aGlzLmxhc3RTZWVuRG9tYWluID0gc2NhbGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4oKTsKICAgICAgICAgICAgICAgIHZhciBjYWNoZWRMZW5ndGggPSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKF90aGlzLmNhY2hlZERvbWFpblsxXSkgLSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKF90aGlzLmNhY2hlZERvbWFpblswXSk7CiAgICAgICAgICAgICAgICB2YXIgbGFzdFNlZW5MZW5ndGggPSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKF90aGlzLmxhc3RTZWVuRG9tYWluWzFdKSAtIHNjYWxlLnNjYWxlVHJhbnNmb3JtYXRpb24oX3RoaXMubGFzdFNlZW5Eb21haW5bMF0pOwogICAgICAgICAgICAgICAgX3RoaXMuc2NhbGUgPSAoY2FjaGVkTGVuZ3RoIC8gbGFzdFNlZW5MZW5ndGgpIHx8IDE7CiAgICAgICAgICAgICAgICBfdGhpcy50cmFuc2xhdGUgPSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKF90aGlzLmNhY2hlZERvbWFpblswXSkgLSBzY2FsZS5zY2FsZVRyYW5zZm9ybWF0aW9uKF90aGlzLmxhc3RTZWVuRG9tYWluWzBdKSAqIF90aGlzLnNjYWxlIHx8IDA7CiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIERvbWFpblRyYW5zZm9ybS5wcm90b3R5cGUucmVzZXQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuc2NhbGUgPSAxOwogICAgICAgICAgICB0aGlzLnRyYW5zbGF0ZSA9IDA7CiAgICAgICAgICAgIHRoaXMuY2FjaGVkRG9tYWluID0gdGhpcy5sYXN0U2VlbkRvbWFpbjsKICAgICAgICB9OwogICAgICAgIERvbWFpblRyYW5zZm9ybS5wcm90b3R5cGUuc2V0RG9tYWluID0gZnVuY3Rpb24gKHNjYWxlKSB7CiAgICAgICAgICAgIHRoaXMuY2FjaGVkRG9tYWluID0gc2NhbGUuZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4oKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBEb21haW5UcmFuc2Zvcm07CiAgICB9KCkpOwogICAgLyoqCiAgICAgKiBNYW5hZ2VzIGRlZmVycmVkIHJlbmRlcmluZyBjYWxsYmFja3MuCiAgICAgKgogICAgICogQ2FsbCBgc2V0RG9tYWluc2Agd2hlbiBkZWZlcnJlZCByZW5kZXJpbmcgaXMgaW5pdGlhbGx5IGVuYWJsZWQgdG8gZml4IHRoZQogICAgICogY3VycmVudCBkb21haW4gdmFsdWVzLgogICAgICoKICAgICAqIENhbGwgYHVwZGF0ZURvbWFpbnNgIHdoZW4gc2NhbGUgZG9tYWlucyBjaGFuZ2UsIHdoaWNoIHVzZXMgdGhlIGRvbWFpbiB0bwogICAgICogY29tcHV0ZSBDU1MtdHlsZSB0cmFuc2Zvcm0gcGFyYW1ldGVycyBwYXNzZWQgdG8gYGFwcGx5VHJhbnNmb3JtQ2FsbGJhY2tgLAogICAgICogbWltaWNraW5nIHRoZSByZXN1bHQgb2YgYSBmdWxsIHJlLXJlbmRlci4gQWZ0ZXIgYSBkZWZlcnJlZCB0aW1lb3V0LCBpbnZva2UKICAgICAqIGBhcHBseVRyYW5zZm9ybUNhbGxiYWNrYCBhZ2FpbiB3aXRoIGFuIGlkZW50aXR5IHRyYW5zZm9ybSBhbmQgZmluYWxseSBpbnZva2UKICAgICAqIGByZW5kZXJDYWxsYmFja2AsIHdoaWNoIHNob3VsZCBhY3R1YWxseSByZWRyYXcgdGhlIHBsb3QuCiAgICAgKgogICAgICogQ2FsbCBgcmVzZXRUcmFuc2Zvcm1zYCBqdXN0IHByaW9yIHRvIHJlLXJlbmRlcmluZyBpbnRvIHRoZSBjYW52YXMuIFRoaXMKICAgICAqIGVuc3VyZXMgdGhhdCB0aGUgY2FudmFzIGlzIGF0IDE6MSBzY2FsaW5nLgogICAgICovCiAgICB2YXIgRGVmZXJyZWRSZW5kZXJlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBEZWZlcnJlZFJlbmRlcmVyKHJlbmRlckNhbGxiYWNrLCBhcHBseVRyYW5zZm9ybUNhbGxiYWNrKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMucmVuZGVyQ2FsbGJhY2sgPSByZW5kZXJDYWxsYmFjazsKICAgICAgICAgICAgdGhpcy5hcHBseVRyYW5zZm9ybUNhbGxiYWNrID0gYXBwbHlUcmFuc2Zvcm1DYWxsYmFjazsKICAgICAgICAgICAgdGhpcy5kb21haW5UcmFuc2Zvcm1YID0gbmV3IERvbWFpblRyYW5zZm9ybSgpOwogICAgICAgICAgICB0aGlzLmRvbWFpblRyYW5zZm9ybVkgPSBuZXcgRG9tYWluVHJhbnNmb3JtKCk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyRGVmZXJyZWQgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5hcHBseVRyYW5zZm9ybSgpOwogICAgICAgICAgICAgICAgY2xlYXJUaW1lb3V0KF90aGlzLnRpbWVvdXRUb2tlbik7CiAgICAgICAgICAgICAgICBfdGhpcy50aW1lb3V0VG9rZW4gPSBzZXRUaW1lb3V0KGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5yZW5kZXJDYWxsYmFjaygpOwogICAgICAgICAgICAgICAgfSwgRGVmZXJyZWRSZW5kZXJlci5ERUZFUlJFRF9SRU5ERVJJTkdfREVMQVkpOwogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBEZWZlcnJlZFJlbmRlcmVyLnByb3RvdHlwZS5zZXREb21haW5zID0gZnVuY3Rpb24gKHNjYWxlWCwgc2NhbGVZKSB7CiAgICAgICAgICAgIGlmIChzY2FsZVgpIHsKICAgICAgICAgICAgICAgIHRoaXMuZG9tYWluVHJhbnNmb3JtWC5zZXREb21haW4oc2NhbGVYKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc2NhbGVZKSB7CiAgICAgICAgICAgICAgICB0aGlzLmRvbWFpblRyYW5zZm9ybVkuc2V0RG9tYWluKHNjYWxlWSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZW5kZXJEZWZlcnJlZCgpOwogICAgICAgIH07CiAgICAgICAgRGVmZXJyZWRSZW5kZXJlci5wcm90b3R5cGUudXBkYXRlRG9tYWlucyA9IGZ1bmN0aW9uIChzY2FsZVgsIHNjYWxlWSkgewogICAgICAgICAgICBpZiAoc2NhbGVYKSB7CiAgICAgICAgICAgICAgICB0aGlzLmRvbWFpblRyYW5zZm9ybVgudXBkYXRlRG9tYWluKHNjYWxlWCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHNjYWxlWSkgewogICAgICAgICAgICAgICAgdGhpcy5kb21haW5UcmFuc2Zvcm1ZLnVwZGF0ZURvbWFpbihzY2FsZVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMucmVuZGVyRGVmZXJyZWQoKTsKICAgICAgICB9OwogICAgICAgIERlZmVycmVkUmVuZGVyZXIucHJvdG90eXBlLnJlc2V0VHJhbnNmb3JtcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5kb21haW5UcmFuc2Zvcm1YLnJlc2V0KCk7CiAgICAgICAgICAgIHRoaXMuZG9tYWluVHJhbnNmb3JtWS5yZXNldCgpOwogICAgICAgICAgICB0aGlzLmFwcGx5VHJhbnNmb3JtKCk7CiAgICAgICAgfTsKICAgICAgICBEZWZlcnJlZFJlbmRlcmVyLnByb3RvdHlwZS5hcHBseVRyYW5zZm9ybSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5hcHBseVRyYW5zZm9ybUNhbGxiYWNrKHRoaXMuZG9tYWluVHJhbnNmb3JtWC50cmFuc2xhdGUsIHRoaXMuZG9tYWluVHJhbnNmb3JtWS50cmFuc2xhdGUsIHRoaXMuZG9tYWluVHJhbnNmb3JtWC5zY2FsZSwgdGhpcy5kb21haW5UcmFuc2Zvcm1ZLnNjYWxlKTsKICAgICAgICB9OwogICAgICAgIERlZmVycmVkUmVuZGVyZXIuREVGRVJSRURfUkVOREVSSU5HX0RFTEFZID0gMjAwOwogICAgICAgIHJldHVybiBEZWZlcnJlZFJlbmRlcmVyOwogICAgfSgpKTsKICAgIGV4cG9ydHMuRGVmZXJyZWRSZW5kZXJlciA9IERlZmVycmVkUmVuZGVyZXI7CiAgICB9KTsKCiAgICB2YXIgcGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgoKCgoKCgoKICAgIGV4cG9ydHMuUmVuZGVyZXIgPSBtYWtlRW51bV8xLm1ha2VFbnVtKFsic3ZnIiwgImNhbnZhcyJdKTsKICAgIHZhciBQbG90ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUGxvdCwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBIFBsb3QgZHJhd3Mgc29tZSB2aXN1YWxpemF0aW9uIG9mIHRoZSBpbnB1dHRlZCBEYXRhc2V0cy4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFBsb3QoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBXaGV0aGVyIHRoZSBiYWNraW5nIGRhdGFzZXRzIGhhdmUgY2hhbmdlZCBzaW5jZSB0aGlzIHBsb3QncyBsYXN0IHJlbmRlci4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIF90aGlzLl9kYXRhQ2hhbmdlZCA9IGZhbHNlOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogTWFwcGluZyBmcm9tIGF0dHJpYnV0ZSBuYW1lcyB0byB0aGUgZXh0ZW50cyAoW21pbiwgbWF4XSkgdmFsdWVzIHRoYXQgdGhhdCBhdHRyaWJ1dGUgdGFrZXMgb24uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBfdGhpcy5fYXR0ckV4dGVudHMgPSB7fTsKICAgICAgICAgICAgX3RoaXMuX2FuaW1hdGUgPSBmYWxzZTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFRoZSBBbmltYXRvcnMgZm9yIHRoaXMgcGxvdC4gRWFjaCBwbG90IGV4cG9zZXMgYSBzZXQgb2YgImFuaW1hdG9yIGtleSIgc3RyaW5ncyB0aGF0CiAgICAgICAgICAgICAqIGRlZmluZSBob3cgZGlmZmVyZW50IHBhcnRzIG9mIHRoYXQgcGFydGljdWxhciBQbG90IGFuaW1hdGVzLiBGb3IgaW5zdGFuY2UsIFJlY3RhbmdsZQogICAgICAgICAgICAgKiBQbG90cyBoYXZlIGEgInJlY3RhbmdsZXMiIGFuaW1hdG9yIGtleSB3aGljaCBjb250cm9scyBob3cgdGhlIDxyZWN0PnMgYXJlIGFuaW1hdGVkLgogICAgICAgICAgICAgKiBAc2VlIGFuaW1hdG9yKCkKICAgICAgICAgICAgICoKICAgICAgICAgICAgICogVGhlcmUgYXJlIHR3byBjb21tb24gYW5pbWF0b3JzIHRoYXQgbW9zdCBQbG90cyByZXNwZWN0OiAibWFpbiIgYW5kICJyZXNldCIuIEluIGdlbmVyYWwsCiAgICAgICAgICAgICAqIFBsb3RzIGRyYXcgaW4gdHdvIHN0ZXBzOiBmaXJzdCB0aGV5ICJyZXNldCIgdGhlaXIgdmlzdWFsIGVsZW1lbnRzIChlLmcuIHNjYXR0ZXIgcGxvdHMgc2V0CiAgICAgICAgICAgICAqIGFsbCB0aGUgZG90cyB0byBzaXplIDApLCBhbmQgdGhlbiB0aGV5IGRvIHRoZSAibWFpbiIgYW5pbWF0aW9uIGludG8gdGhlIGNvcnJlY3QgdmlzdWFsaXphdGlvbgogICAgICAgICAgICAgKiAoZS5nLiBzY2F0dGVyIHBsb3QgZG90cyBncm93IHRvIHRoZWlyIHNwZWNpZmllZCBzaXplKS4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIF90aGlzLl9hbmltYXRvcnMgPSB7fTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIE1hcHBpbmcgZnJvbSBwcm9wZXJ0eSBuYW1lcyB0byB0aGUgZXh0ZW50cyAoW21pbiwgbWF4XSkgdmFsdWVzIHRoYXQgdGhhdAogICAgICAgICAgICAgKiBwcm9wZXJ0eSB0YWtlcyBvbi4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIF90aGlzLl9wcm9wZXJ0eUV4dGVudHMgPSB7fTsKICAgICAgICAgICAgX3RoaXMuX3Jlc2V0RW50aXR5U3RvcmUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBfdGhpcy5fY2FjaGVkRW50aXR5U3RvcmUgPSB1bmRlZmluZWQ7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIF90aGlzLl9vdmVyZmxvd0hpZGRlbiA9IHRydWU7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJwbG90Iik7CiAgICAgICAgICAgIF90aGlzLl9kYXRhc2V0VG9EcmF3ZXIgPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICAgICAgX3RoaXMuX2F0dHJCaW5kaW5ncyA9IGQzLm1hcCgpOwogICAgICAgICAgICBfdGhpcy5faW5jbHVkZWRWYWx1ZXNQcm92aWRlciA9IGZ1bmN0aW9uIChzY2FsZSwgaWdub3JlQW5jaG9yU3RhdGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5faW5jbHVkZWRWYWx1ZXNGb3JTY2FsZShzY2FsZSwgaWdub3JlQW5jaG9yU3RhdGUpOwogICAgICAgICAgICB9OwogICAgICAgICAgICBfdGhpcy5fcmVuZGVyQ2FsbGJhY2sgPSBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5yZW5kZXIoKTsgfTsKICAgICAgICAgICAgX3RoaXMuX29uRGF0YXNldFVwZGF0ZUNhbGxiYWNrID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX29uRGF0YXNldFVwZGF0ZSgpOyB9OwogICAgICAgICAgICBfdGhpcy5fcHJvcGVydHlCaW5kaW5ncyA9IGQzLm1hcCgpOwogICAgICAgICAgICB2YXIgbWFpbkFuaW1hdG9yID0gbmV3IGFuaW1hdG9ycy5FYXNpbmcoKS5tYXhUb3RhbER1cmF0aW9uKFBsb3QuX0FOSU1BVElPTl9NQVhfRFVSQVRJT04pOwogICAgICAgICAgICBfdGhpcy5hbmltYXRvcihjb21tb25zLkFuaW1hdG9yLk1BSU4sIG1haW5BbmltYXRvcik7CiAgICAgICAgICAgIF90aGlzLmFuaW1hdG9yKGNvbW1vbnMuQW5pbWF0b3IuUkVTRVQsIG5ldyBhbmltYXRvcnMuTnVsbCgpKTsKICAgICAgICAgICAgX3RoaXMuX2RlZmVycmVkUmVzZXRFbnRpdHlTdG9yZSA9IHV0aWxzJDEuV2luZG93LmRlYm91bmNlKGRlZmVycmVkUmVuZGVyZXIuRGVmZXJyZWRSZW5kZXJlci5ERUZFUlJFRF9SRU5ERVJJTkdfREVMQVksIF90aGlzLl9yZXNldEVudGl0eVN0b3JlKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBQbG90LmdldFRvdGFsRHJhd1RpbWUgPSBmdW5jdGlvbiAoZGF0YSwgZHJhd1N0ZXBzKSB7CiAgICAgICAgICAgIHJldHVybiBkcmF3U3RlcHMucmVkdWNlKGZ1bmN0aW9uICh0aW1lLCBkcmF3U3RlcCkgeyByZXR1cm4gdGltZSArIGRyYXdTdGVwLmFuaW1hdG9yLnRvdGFsVGltZShkYXRhLmxlbmd0aCk7IH0sIDApOwogICAgICAgIH07CiAgICAgICAgUGxvdC5hcHBseURyYXdTdGVwcyA9IGZ1bmN0aW9uIChkcmF3U3RlcHMsIGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIGFwcGxpZWREcmF3U3RlcHMgPSBkcmF3U3RlcHMubWFwKGZ1bmN0aW9uIChkcmF3U3RlcCkgewogICAgICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IGRyYXdTdGVwLmF0dHJUb1Byb2plY3RvcjsKICAgICAgICAgICAgICAgIHZhciBhdHRyVG9BcHBsaWVkUHJvamVjdG9yID0ge307CiAgICAgICAgICAgICAgICBPYmplY3Qua2V5cyhhdHRyVG9Qcm9qZWN0b3IpLmZvckVhY2goZnVuY3Rpb24gKGF0dHIpIHsKICAgICAgICAgICAgICAgICAgICBhdHRyVG9BcHBsaWVkUHJvamVjdG9yW2F0dHJdID0KICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24gKGRhdHVtLCBpbmRleCkgeyByZXR1cm4gYXR0clRvUHJvamVjdG9yW2F0dHJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7IH07CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgYXR0clRvQXBwbGllZFByb2plY3RvcjogYXR0clRvQXBwbGllZFByb2plY3RvciwKICAgICAgICAgICAgICAgICAgICBhbmltYXRvcjogZHJhd1N0ZXAuYW5pbWF0b3IsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGFwcGxpZWREcmF3U3RlcHM7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5hbmNob3IgPSBmdW5jdGlvbiAoc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbiA9IGNvZXJjZUQzLmNvZXJjZUV4dGVybmFsRDMoc2VsZWN0aW9uKTsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5hbmNob3IuY2FsbCh0aGlzLCBzZWxlY3Rpb24pOwogICAgICAgICAgICB0aGlzLl9kYXRhQ2hhbmdlZCA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX3Jlc2V0RW50aXR5U3RvcmUoKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlRXh0ZW50cygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9zZXR1cCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzU2V0dXApIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICBpZiAodGhpcy5fY2FudmFzICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2FwcGVuZENhbnZhc05vZGUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9yZW5kZXJBcmVhID0gdGhpcy5jb250ZW50KCkuYXBwZW5kKCJnIikuY2xhc3NlZCgicmVuZGVyLWFyZWEiLCB0cnVlKTsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQoZGF0YXNldCk7IH0pOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2FwcGVuZENhbnZhc05vZGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBjYW52YXNDb250YWluZXIgPSB0aGlzLmVsZW1lbnQoKS5zZWxlY3QoIi5wbG90LWNhbnZhcy1jb250YWluZXIiKTsKICAgICAgICAgICAgaWYgKGNhbnZhc0NvbnRhaW5lci5lbXB0eSgpKSB7CiAgICAgICAgICAgICAgICBjYW52YXNDb250YWluZXIgPSB0aGlzLmVsZW1lbnQoKS5hcHBlbmQoImRpdiIpLmNsYXNzZWQoInBsb3QtY2FudmFzLWNvbnRhaW5lciIsIHRydWUpOwogICAgICAgICAgICAgICAgY2FudmFzQ29udGFpbmVyLm5vZGUoKS5hcHBlbmRDaGlsZCh0aGlzLl9jYW52YXMubm9kZSgpKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuc2V0Qm91bmRzID0gZnVuY3Rpb24gKHdpZHRoLCBoZWlnaHQsIG9yaWdpblgsIG9yaWdpblkpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5zZXRCb3VuZHMuY2FsbCh0aGlzLCB3aWR0aCwgaGVpZ2h0LCBvcmlnaW5YLCBvcmlnaW5ZKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlRXh0ZW50cygpOwogICAgICAgICAgICBpZiAodGhpcy5fY2FudmFzICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9idWZmZXJDYW52YXMgJiYgIXRoaXMuX2J1ZmZlckNhbnZhc1ZhbGlkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gY29weSBjdXJyZW50IGNhbnZhcyB0byBidWZmZXIgMToxCiAgICAgICAgICAgICAgICAgICAgLy8KICAgICAgICAgICAgICAgICAgICAvLyBXaHkgdXNlIGEgYnVmZmVyIGNhbnZhcz8KICAgICAgICAgICAgICAgICAgICAvLyBBcyBzb29uIGFzIHdlIGNoYW5nZSB0aGUgc2l6ZSBvZiBhIGNhbnZhcyB3aXRoIGNzcyBvciBhdHRyaWJ1dGVzLCBpdAogICAgICAgICAgICAgICAgICAgIC8vIGNsZWFycyB0aGUgY29udGVudHMuIFdpdGhvdXQgYSBidWZmZXIgY2FudmFzLCB0aGlzIHJlcXVpcmVzCiAgICAgICAgICAgICAgICAgICAgLy8gZHJhZy1yZXNpemFibGUgY2hhcnRzIHRvIGltbWVkaWF0ZWx5IGRvIGEgZnVsbCByZWRyYXcgd2hpbGUgeW91CiAgICAgICAgICAgICAgICAgICAgLy8gZHJhZy1yZXNpemUsIHdoaWNoIGNhbiBjYXVzZSBqYW5rLiBUbyBhdm9pZCB0aGF0LCB0aGlzIGJ1ZmZlciBjYW52YXMKICAgICAgICAgICAgICAgICAgICAvLyBzdG9yZXMgdGhlIGN1cnJlbnQgY2FudmFzIGNvbnRlbnRzIHdoZW4gdGhlIHJlc2l6ZSBzdGFydHMgYW5kIHJlZHJhd3MKICAgICAgICAgICAgICAgICAgICAvLyBpdCBpbnRvIHRoZSByZXNpemVkIGNhbnZhcy4gRXZlbnR1YWxseSwgdGhlIGRlZmVycmVkIHJlbmRlcmluZwogICAgICAgICAgICAgICAgICAgIC8vIGNhbGxiYWNrIHdpbGwgdHJpZ2dlciBhbmQgZG8gYSBmdWxsLXJleiByZWRyYXcuIElmIGRlZmVycmVkIHJlbmRlcmluZwogICAgICAgICAgICAgICAgICAgIC8vIGlzIGRpc2FibGVkLCB0aGUgYnVmZmVyIGNvcHkgd2lsbCBiZSBvdmVyd3JpdHRlbiBpbW1lZGlhdGVseSBieSBhCiAgICAgICAgICAgICAgICAgICAgLy8gZnVsbCByZWRyYXcuCiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYnVmZmVyQ2FudmFzLmF0dHIoIndpZHRoIiwgdGhpcy5fY2FudmFzLmF0dHIoIndpZHRoIikpOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2J1ZmZlckNhbnZhcy5hdHRyKCJoZWlnaHQiLCB0aGlzLl9jYW52YXMuYXR0cigiaGVpZ2h0IikpOwogICAgICAgICAgICAgICAgICAgIHZhciBidHggPSB0aGlzLl9idWZmZXJDYW52YXMubm9kZSgpLmdldENvbnRleHQoIjJkIik7CiAgICAgICAgICAgICAgICAgICAgLy8gZm9yIGhlYWRsZXNzIHRlc3QgY29tcGF0IChqZXN0KQogICAgICAgICAgICAgICAgICAgIGlmIChidHgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIG9yaWdpbmFsQ2FudmFzID0gdGhpcy5fY2FudmFzLm5vZGUoKTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG9yaWdpbmFsQ2FudmFzLndpZHRoID4gMCAmJiBvcmlnaW5hbENhbnZhcy5oZWlnaHQgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoYnR4LmNhbnZhcy53aWR0aCA+IDAgJiYgYnR4LmNhbnZhcy5oZWlnaHQgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYnR4LmRyYXdJbWFnZShvcmlnaW5hbENhbnZhcywgMCwgMCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zb2xlLndhcm4oIkZhaWxlZCB0byBmaWxsIGJ1ZmZlciBjYW52YXMgd2l0aCB3aXRoIDB4MCBjYW52YXMiKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB0aGlzLl9idWZmZXJDYW52YXNWYWxpZCA9IHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyB1cGRhdGUgY2FudmFzIHNpemUKICAgICAgICAgICAgICAgIHZhciByYXRpbyA9ICh3aW5kb3cuZGV2aWNlUGl4ZWxSYXRpbyAhPSBudWxsKSA/IHdpbmRvdy5kZXZpY2VQaXhlbFJhdGlvIDogMTsKICAgICAgICAgICAgICAgIC8vIHVwZGF0ZSBjYW52YXMgd2lkdGgvaGVpZ2h0IHRha2luZyBpbnRvIGFjY291bnQgcmV0aW5hIGRpc3BsYXlzLgogICAgICAgICAgICAgICAgLy8gVGhpcyB3aWxsIGFsc28gY2xlYXIgdGhlIGNhbnZhcyBvZiBhbnkgZHJhd24gZWxlbWVudHMgc28gd2Ugc2hvdWxkCiAgICAgICAgICAgICAgICAvLyBiZSBzdXJlIG5vdCB0byBjb21wdXRlTGF5b3V0KCkgd2l0aG91dCBhIHJlbmRlcigpIGluIHRoZSBmdXR1cmUuCiAgICAgICAgICAgICAgICB0aGlzLl9jYW52YXMuYXR0cigid2lkdGgiLCB3aWR0aCAqIHJhdGlvKTsKICAgICAgICAgICAgICAgIHRoaXMuX2NhbnZhcy5hdHRyKCJoZWlnaHQiLCBoZWlnaHQgKiByYXRpbyk7CiAgICAgICAgICAgICAgICAvLyByZXNldCB0aGUgdHJhbnNmb3JtIHRoZW4gc2V0IHRoZSBzY2FsZSBmYWN0b3IKICAgICAgICAgICAgICAgIHZhciBjdHggPSB0aGlzLl9jYW52YXMubm9kZSgpLmdldENvbnRleHQoIjJkIik7CiAgICAgICAgICAgICAgICAvLyBudWxsIGNoZWNrIGZvciBoZWFkbGVzcyB0ZXN0IGNvbXBhdCAoamVzdCkKICAgICAgICAgICAgICAgIGlmIChjdHgpIHsKICAgICAgICAgICAgICAgICAgICBjdHguc2V0VHJhbnNmb3JtKHJhdGlvLCAwLCAwLCByYXRpbywgMCwgMCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuX2J1ZmZlckNhbnZhcykgewogICAgICAgICAgICAgICAgICAgICAgICB2YXIgYnVmZmVyQ2FudmFzID0gdGhpcy5fYnVmZmVyQ2FudmFzLm5vZGUoKTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGJ1ZmZlckNhbnZhcy53aWR0aCA+IDAgJiYgYnVmZmVyQ2FudmFzLmhlaWdodCA+IDApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChjdHguY2FudmFzLndpZHRoID4gMCAmJiBjdHguY2FudmFzLmhlaWdodCA+IDApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBkcmF3IGJ1ZmZlciB0byBjdXJyZW50IGNhbnZhcyBhdCBuZXcgc2l6ZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGN0eC5kcmF3SW1hZ2UoYnVmZmVyQ2FudmFzLCAwLCAwLCB3aWR0aCwgaGVpZ2h0KTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnNvbGUud2FybigiRmFpbGVkIHRvIGZpbGwgY2FudmFzIHdpdGggMHgwIGJ1ZmZlciBjYW52YXMiKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLmRlc3Ryb3kgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGVzdHJveS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9zY2FsZXMoKS5mb3JFYWNoKGZ1bmN0aW9uIChzY2FsZSkgeyByZXR1cm4gc2NhbGUub2ZmVXBkYXRlKF90aGlzLl9yZW5kZXJDYWxsYmFjayk7IH0pOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKFtdKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFNldHVwIHRoZSBET00gbm9kZXMgZm9yIHRoZSBnaXZlbiBkYXRhc2V0LiBUaGlzIGlzIGEgc2VwYXJhdGUKICAgICAgICAgKiBzdGVwIGZyb20gImNyZWF0aW5nIHRoZSBEcmF3ZXIiIHNpbmNlIHRoZSBlbGVtZW50IG1heSBub3QgYmUgc2V0dXAgeWV0CiAgICAgICAgICogKGluIHdoaWNoIGNhc2UgdGhlIF9yZW5kZXJBcmVhIGlzIG51bGwgYmVjYXVzZSB0aGUgLmVsZW1lbnQoKSBhbmQgLmNvbnRlbnQoKQogICAgICAgICAqIGFyZSBudWxsKS4gQWxzbyBiZWNhdXNlIHN1YmNsYXNzZXMgbWF5IGRvIG1vcmUgdGhhbiBqdXN0IGNvbmZpZ3VyZSBvbmUKICAgICAgICAgKiBzaW5nbGUgZHJhd2VyIChlLmcuIGFkZGluZyB0ZXh0IGRyYXdpbmcgY2FwYWJpbGl0aWVzKS4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fY3JlYXRlTm9kZXNGb3JEYXRhc2V0ID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIGRyYXdlciA9IHRoaXMuX2RhdGFzZXRUb0RyYXdlci5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgIGlmICh0aGlzLnJlbmRlcmVyKCkgPT09ICJzdmciKSB7CiAgICAgICAgICAgICAgICBkcmF3ZXIudXNlU1ZHKHRoaXMuX3JlbmRlckFyZWEpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgZHJhd2VyLnVzZUNhbnZhcyh0aGlzLl9jYW52YXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBkcmF3ZXI7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGUgYSBuZXcgRHJhd2VyLiBTdWJjbGFzc2VzIHNob3VsZCBvdmVycmlkZSB0aGlzIHRvIHJldHVybgogICAgICAgICAqIGEgRHJhd2VyIHRoYXQgZHJhd3MgdGhlIGNvcnJlY3Qgc2hhcGVzIGZvciB0aGlzIHBsb3QuCiAgICAgICAgICovCiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2NyZWF0ZURyYXdlciA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgZHJhd2VyLlByb3h5RHJhd2VyKGZ1bmN0aW9uICgpIHsgcmV0dXJuIG5ldyBzdmdEcmF3ZXIuU1ZHRHJhd2VyKCJwYXRoIiwgIiIpOyB9LCBmdW5jdGlvbiAoY3R4KSB7IHJldHVybiBuZXcgY2FudmFzRHJhd2VyLkNhbnZhc0RyYXdlcihjdHgsIGZ1bmN0aW9uICgpIHsgfSk7IH0pOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2dldEFuaW1hdG9yID0gZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICBpZiAodGhpcy5fYW5pbWF0ZU9uTmV4dFJlbmRlcigpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5pbWF0b3JzW2tleV0gfHwgbmV3IGFuaW1hdG9ycy5OdWxsKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IGFuaW1hdG9ycy5OdWxsKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9vbkRhdGFzZXRVcGRhdGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZUV4dGVudHMoKTsKICAgICAgICAgICAgdGhpcy5fZGF0YUNoYW5nZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9yZXNldEVudGl0eVN0b3JlKCk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyTG93UHJpb3JpdHkoKTsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLmF0dHIgPSBmdW5jdGlvbiAoYXR0ciwgYXR0clZhbHVlLCBzY2FsZSkgewogICAgICAgICAgICBpZiAoYXR0clZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9hdHRyQmluZGluZ3MuZ2V0KGF0dHIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRBdHRyKGF0dHIsIGF0dHJWYWx1ZSwgc2NhbGUpOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOyAvLyBxdWV1ZSBhIHJlLXJlbmRlciB1cG9uIGNoYW5naW5nIHByb2plY3RvcgogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9iaW5kUHJvcGVydHkgPSBmdW5jdGlvbiAocHJvcGVydHksIHZhbHVlT3JGbiwgc2NhbGUsIHBvc3RTY2FsZSkgewogICAgICAgICAgICB2YXIgYmluZGluZyA9IHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KHByb3BlcnR5KTsKICAgICAgICAgICAgdmFyIG9sZFNjYWxlID0gYmluZGluZyAhPSBudWxsID8gYmluZGluZy5zY2FsZSA6IG51bGw7CiAgICAgICAgICAgIHZhciBhY2Nlc3NvciA9IHR5cGVvZiB2YWx1ZU9yRm4gPT09ICJmdW5jdGlvbiIgPyB2YWx1ZU9yRm4gOiBmdW5jdGlvbiAoKSB7IHJldHVybiB2YWx1ZU9yRm47IH07CiAgICAgICAgICAgIHRoaXMuX3Byb3BlcnR5QmluZGluZ3Muc2V0KHByb3BlcnR5LCB7IGFjY2Vzc29yOiBhY2Nlc3Nvciwgc2NhbGU6IHNjYWxlLCBwb3N0U2NhbGU6IHBvc3RTY2FsZSB9KTsKICAgICAgICAgICAgaWYgKG9sZFNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3VuaW5zdGFsbFNjYWxlRm9yS2V5KG9sZFNjYWxlLCBwcm9wZXJ0eSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2luc3RhbGxTY2FsZUZvcktleShzY2FsZSwgcHJvcGVydHkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2NsZWFyQXR0clRvUHJvamVjdG9yQ2FjaGUoKTsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9iaW5kQXR0ciA9IGZ1bmN0aW9uIChhdHRyLCB2YWx1ZU9yRm4sIHNjYWxlKSB7CiAgICAgICAgICAgIHZhciBiaW5kaW5nID0gdGhpcy5fYXR0ckJpbmRpbmdzLmdldChhdHRyKTsKICAgICAgICAgICAgdmFyIG9sZFNjYWxlID0gYmluZGluZyAhPSBudWxsID8gYmluZGluZy5zY2FsZSA6IG51bGw7CiAgICAgICAgICAgIHZhciBhY2Nlc3NvciA9IHR5cGVvZiB2YWx1ZU9yRm4gPT09ICJmdW5jdGlvbiIgPyB2YWx1ZU9yRm4gOiBmdW5jdGlvbiAoKSB7IHJldHVybiB2YWx1ZU9yRm47IH07CiAgICAgICAgICAgIHRoaXMuX2F0dHJCaW5kaW5ncy5zZXQoYXR0ciwgeyBhY2Nlc3NvcjogYWNjZXNzb3IsIHNjYWxlOiBzY2FsZSB9KTsKICAgICAgICAgICAgaWYgKG9sZFNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3VuaW5zdGFsbFNjYWxlRm9yS2V5KG9sZFNjYWxlLCBhdHRyKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5faW5zdGFsbFNjYWxlRm9yS2V5KHNjYWxlLCBhdHRyKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jbGVhckF0dHJUb1Byb2plY3RvckNhY2hlKCk7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5fY2xlYXJBdHRyVG9Qcm9qZWN0b3JDYWNoZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgZGVsZXRlIHRoaXMuX2NhY2hlZEF0dHJUb1Byb2plY3RvcjsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9nZXRBdHRyVG9Qcm9qZWN0b3IgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9jYWNoZWRBdHRyVG9Qcm9qZWN0b3IgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIHByb2plY3RvcnMgPSB0aGlzLl9nZW5lcmF0ZUF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICAgICAgaWYgKFBsb3QuT1BUSU1JWkVfTUVNT0laRV9QUk9KRUNUT1JTKSB7CiAgICAgICAgICAgICAgICAgICAgcHJvamVjdG9ycyA9IG1lbW9pemUubWVtb2l6ZVByb2plY3RvcnMocHJvamVjdG9ycyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9jYWNoZWRBdHRyVG9Qcm9qZWN0b3IgPSBwcm9qZWN0b3JzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIHJldHVybiBzaGFsbG93IGNsb25lIG9mIGNhY2hlZCBwcm9qZWN0b3IKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuYXNzaWduKHt9LCB0aGlzLl9jYWNoZWRBdHRyVG9Qcm9qZWN0b3IpOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgaCA9IHt9OwogICAgICAgICAgICB0aGlzLl9hdHRyQmluZGluZ3MuZWFjaChmdW5jdGlvbiAoYmluZGluZywgYXR0cikgewogICAgICAgICAgICAgICAgaFthdHRyXSA9IFBsb3QuX3NjYWxlZEFjY2Vzc29yKGJpbmRpbmcpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIHByb3BlcnR5UHJvamVjdG9ycyA9IHRoaXMuX3Byb3BlcnR5UHJvamVjdG9ycygpOwogICAgICAgICAgICBPYmplY3Qua2V5cyhwcm9wZXJ0eVByb2plY3RvcnMpLmZvckVhY2goZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICAgICAgaWYgKGhba2V5XSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgaFtrZXldID0gcHJvcGVydHlQcm9qZWN0b3JzW2tleV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gaDsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnJlbmRlckltbWVkaWF0ZWx5LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc0FuY2hvcmVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9wYWludCgpOwogICAgICAgICAgICAgICAgdGhpcy5fZGF0YUNoYW5nZWQgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLnJlbmRlckxvd1ByaW9yaXR5ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl9yZW5kZXJDYWxsYmFjaygpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLmFuaW1hdGVkID0gZnVuY3Rpb24gKHdpbGxBbmltYXRlKSB7CiAgICAgICAgICAgIGlmICh3aWxsQW5pbWF0ZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5pbWF0ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9hbmltYXRlID0gd2lsbEFuaW1hdGU7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuZGV0YWNoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmRldGFjaC5jYWxsKHRoaXMpOwogICAgICAgICAgICAvLyBtYWtlIHRoZSBkb21haW4gcmVzaXplCiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZUV4dGVudHMoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBAcmV0dXJucyB7U2NhbGVbXX0gQSB1bmlxdWUgYXJyYXkgb2YgYWxsIHNjYWxlcyBjdXJyZW50bHkgdXNlZCBieSB0aGUgUGxvdC4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fc2NhbGVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgc2NhbGVzID0gW107CiAgICAgICAgICAgIHRoaXMuX2F0dHJCaW5kaW5ncy5lYWNoKGZ1bmN0aW9uIChiaW5kaW5nLCBhdHRyKSB7CiAgICAgICAgICAgICAgICB2YXIgc2NhbGUgPSBiaW5kaW5nLnNjYWxlOwogICAgICAgICAgICAgICAgaWYgKHNjYWxlICE9IG51bGwgJiYgc2NhbGVzLmluZGV4T2Yoc2NhbGUpID09PSAtMSkgewogICAgICAgICAgICAgICAgICAgIHNjYWxlcy5wdXNoKHNjYWxlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZWFjaChmdW5jdGlvbiAoYmluZGluZywgcHJvcGVydHkpIHsKICAgICAgICAgICAgICAgIHZhciBzY2FsZSA9IGJpbmRpbmcuc2NhbGU7CiAgICAgICAgICAgICAgICBpZiAoc2NhbGUgIT0gbnVsbCAmJiBzY2FsZXMuaW5kZXhPZihzY2FsZSkgPT09IC0xKSB7CiAgICAgICAgICAgICAgICAgICAgc2NhbGVzLnB1c2goc2NhbGUpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIHNjYWxlczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFVwZGF0ZXMgdGhlIGV4dGVudHMgYXNzb2NpYXRlZCB3aXRoIGVhY2ggYXR0cmlidXRlLCB0aGVuIGF1dG9kb21haW5zIGFsbCBzY2FsZXMgdGhlIFBsb3QgdXNlcy4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fdXBkYXRlRXh0ZW50cyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdGhpcy5fcmVzZXRFbnRpdHlTdG9yZSgpOwogICAgICAgICAgICB0aGlzLl9zY2FsZXMoKS5mb3JFYWNoKGZ1bmN0aW9uIChzY2FsZSkgeyByZXR1cm4gc2NhbGUuYWRkSW5jbHVkZWRWYWx1ZXNQcm92aWRlcihfdGhpcy5faW5jbHVkZWRWYWx1ZXNQcm92aWRlcik7IH0pOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2ZpbHRlckZvclByb3BlcnR5ID0gZnVuY3Rpb24gKHByb3BlcnR5KSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuZ2V0RXh0ZW50c0ZvckF0dHIgPSBmdW5jdGlvbiAoYXR0cikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAodGhpcy5fYXR0ckV4dGVudHNbYXR0cl0gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIHRodW5rID0gbWVtb2l6ZS5tZW1UaHVuayhmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5kYXRhc2V0cygpOyB9LCBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fYXR0ckJpbmRpbmdzLmdldChhdHRyKTsgfSwgZnVuY3Rpb24gKGRhdGFzZXRzLCBhY2NTY2FsZUJpbmRpbmcpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoYWNjU2NhbGVCaW5kaW5nID09IG51bGwgfHwgYWNjU2NhbGVCaW5kaW5nLmFjY2Vzc29yID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIHJldHVybiBkYXRhc2V0cy5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIGNvbXB1dGVFeHRlbnQoZGF0YXNldCwgYWNjU2NhbGVCaW5kaW5nLCBudWxsKTsgfSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHRoaXMuX2F0dHJFeHRlbnRzW2F0dHJdID0gdGh1bms7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2F0dHJFeHRlbnRzW2F0dHJdKCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBPdmVycmlkZSBpbiBzdWJjbGFzcyB0byBhZGQgc3BlY2lhbCBleHRlbnRzLCBzdWNoIGFzIGluY2x1ZGVkIHZhbHVlcwogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLmdldEV4dGVudHNGb3JQcm9wZXJ0eSA9IGZ1bmN0aW9uIChwcm9wZXJ0eSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAodGhpcy5fcHJvcGVydHlFeHRlbnRzW3Byb3BlcnR5XSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgdGh1bmsgPSBtZW1vaXplLm1lbVRodW5rKGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLmRhdGFzZXRzKCk7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChwcm9wZXJ0eSk7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9maWx0ZXJGb3JQcm9wZXJ0eShwcm9wZXJ0eSk7IH0sIGZ1bmN0aW9uIChkYXRhc2V0cywgYWNjU2NhbGVCaW5kaW5nLCBmaWx0ZXIpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoYWNjU2NhbGVCaW5kaW5nID09IG51bGwgfHwgYWNjU2NhbGVCaW5kaW5nLmFjY2Vzc29yID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIHJldHVybiBkYXRhc2V0cy5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIGNvbXB1dGVFeHRlbnQoZGF0YXNldCwgYWNjU2NhbGVCaW5kaW5nLCBmaWx0ZXIpOyB9KTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fcHJvcGVydHlFeHRlbnRzW3Byb3BlcnR5XSA9IHRodW5rOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUV4dGVudHNbcHJvcGVydHldKCk7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5faW5jbHVkZWRWYWx1ZXNGb3JTY2FsZSA9IGZ1bmN0aW9uIChzY2FsZSwgaWdub3JlQXR0YWNoU3RhdGUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKCF0aGlzLl9pc0FuY2hvcmVkICYmICFpZ25vcmVBdHRhY2hTdGF0ZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBpbmNsdWRlZFZhbHVlcyA9IFtdOwogICAgICAgICAgICB0aGlzLl9hdHRyQmluZGluZ3MuZWFjaChmdW5jdGlvbiAoYmluZGluZywgYXR0cikgewogICAgICAgICAgICAgICAgaWYgKGJpbmRpbmcuc2NhbGUgPT09IHNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGV4dGVudHMgPSBfdGhpcy5nZXRFeHRlbnRzRm9yQXR0cihhdHRyKTsKICAgICAgICAgICAgICAgICAgICBpZiAoZXh0ZW50cyAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGluY2x1ZGVkVmFsdWVzID0gaW5jbHVkZWRWYWx1ZXMuY29uY2F0KGQzLm1lcmdlKGV4dGVudHMpKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmVhY2goZnVuY3Rpb24gKGJpbmRpbmcsIHByb3BlcnR5KSB7CiAgICAgICAgICAgICAgICBpZiAoYmluZGluZy5zY2FsZSA9PT0gc2NhbGUpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgZXh0ZW50cyA9IF90aGlzLmdldEV4dGVudHNGb3JQcm9wZXJ0eShwcm9wZXJ0eSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKGV4dGVudHMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgICAgICBpbmNsdWRlZFZhbHVlcyA9IGluY2x1ZGVkVmFsdWVzLmNvbmNhdChkMy5tZXJnZShleHRlbnRzKSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGluY2x1ZGVkVmFsdWVzOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuYW5pbWF0b3IgPSBmdW5jdGlvbiAoYW5pbWF0b3JLZXksIGFuaW1hdG9yKSB7CiAgICAgICAgICAgIGlmIChhbmltYXRvciA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5pbWF0b3JzW2FuaW1hdG9yS2V5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2FuaW1hdG9yc1thbmltYXRvcktleV0gPSBhbmltYXRvcjsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5yZW5kZXJlciA9IGZ1bmN0aW9uIChyZW5kZXJlcikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBpZiAocmVuZGVyZXIgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NhbnZhcyA9PSBudWxsID8gInN2ZyIgOiAiY2FudmFzIjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9jYW52YXMgPT0gbnVsbCAmJiByZW5kZXJlciA9PT0gImNhbnZhcyIpIHsKICAgICAgICAgICAgICAgICAgICAvLyBjb25zdHJ1Y3QgdGhlIGNhbnZhcywgcmVtb3ZlIGRyYXdlcidzIHJlbmRlckFyZWFzLCBzZXQgZHJhd2VyJ3MgY2FudmFzCiAgICAgICAgICAgICAgICAgICAgdGhpcy5fY2FudmFzID0gZDMuc2VsZWN0KGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoImNhbnZhcyIpKS5jbGFzc2VkKCJwbG90LWNhbnZhcyIsIHRydWUpOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2J1ZmZlckNhbnZhcyA9IGQzLnNlbGVjdChkb2N1bWVudC5jcmVhdGVFbGVtZW50KCJjYW52YXMiKSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuZWxlbWVudCgpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fYXBwZW5kQ2FudmFzTm9kZSgpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB0aGlzLl9kYXRhc2V0VG9EcmF3ZXIuZm9yRWFjaChmdW5jdGlvbiAoZHJhd2VyKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGRyYXdlci51c2VDYW52YXMoX3RoaXMuX2NhbnZhcyk7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKHRoaXMuX2NhbnZhcyAhPSBudWxsICYmIHJlbmRlcmVyID09ICJzdmciKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fY2FudmFzLnJlbW92ZSgpOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2NhbnZhcyA9IG51bGw7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYnVmZmVyQ2FudmFzID0gbnVsbDsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9kYXRhc2V0VG9EcmF3ZXIuZm9yRWFjaChmdW5jdGlvbiAoZHJhd2VyKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGRyYXdlci51c2VTVkcoX3RoaXMuX3JlbmRlckFyZWEpOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIERhdGFzZXQgdG8gdGhlIFBsb3QuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RhdGFzZXR9IGRhdGFzZXQKICAgICAgICAgKiBAcmV0dXJucyB7UGxvdH0gVGhlIGNhbGxpbmcgUGxvdC4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5hZGREYXRhc2V0ID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgdGhpcy5fYWRkRGF0YXNldChkYXRhc2V0KTsKICAgICAgICAgICAgdGhpcy5fb25EYXRhc2V0VXBkYXRlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2FkZERhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVEYXRhc2V0KGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgZHJhd2VyID0gdGhpcy5fY3JlYXRlRHJhd2VyKGRhdGFzZXQpOwogICAgICAgICAgICB0aGlzLl9kYXRhc2V0VG9EcmF3ZXIuc2V0KGRhdGFzZXQsIGRyYXdlcik7CiAgICAgICAgICAgIGlmICh0aGlzLl9pc1NldHVwKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQoZGF0YXNldCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZGF0YXNldC5vblVwZGF0ZSh0aGlzLl9vbkRhdGFzZXRVcGRhdGVDYWxsYmFjayk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmVtb3ZlcyBhIERhdGFzZXQgZnJvbSB0aGUgUGxvdC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RGF0YXNldH0gZGF0YXNldAogICAgICAgICAqIEByZXR1cm5zIHtQbG90fSBUaGUgY2FsbGluZyBQbG90LgogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLnJlbW92ZURhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICB0aGlzLl9yZW1vdmVEYXRhc2V0KGRhdGFzZXQpOwogICAgICAgICAgICB0aGlzLl9vbkRhdGFzZXRVcGRhdGUoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5fcmVtb3ZlRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIGlmICh0aGlzLmRhdGFzZXRzKCkuaW5kZXhPZihkYXRhc2V0KSA9PT0gLTEpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3JlbW92ZURhdGFzZXROb2RlcyhkYXRhc2V0KTsKICAgICAgICAgICAgZGF0YXNldC5vZmZVcGRhdGUodGhpcy5fb25EYXRhc2V0VXBkYXRlQ2FsbGJhY2spOwogICAgICAgICAgICB0aGlzLl9kYXRhc2V0VG9EcmF3ZXIuZGVsZXRlKGRhdGFzZXQpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0Tm9kZXMgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICB2YXIgZHJhd2VyID0gdGhpcy5fZGF0YXNldFRvRHJhd2VyLmdldChkYXRhc2V0KTsKICAgICAgICAgICAgZHJhd2VyLnJlbW92ZSgpOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuZGF0YXNldHMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGN1cnJlbnREYXRhc2V0cyA9IFtdOwogICAgICAgICAgICB0aGlzLl9kYXRhc2V0VG9EcmF3ZXIuZm9yRWFjaChmdW5jdGlvbiAoZHJhd2VyLCBkYXRhc2V0KSB7IHJldHVybiBjdXJyZW50RGF0YXNldHMucHVzaChkYXRhc2V0KTsgfSk7CiAgICAgICAgICAgIGlmIChkYXRhc2V0cyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY3VycmVudERhdGFzZXRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGN1cnJlbnREYXRhc2V0cy5mb3JFYWNoKGZ1bmN0aW9uIChkYXRhc2V0KSB7IHJldHVybiBfdGhpcy5fcmVtb3ZlRGF0YXNldChkYXRhc2V0KTsgfSk7CiAgICAgICAgICAgIGRhdGFzZXRzLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9hZGREYXRhc2V0KGRhdGFzZXQpOyB9KTsKICAgICAgICAgICAgdGhpcy5fb25EYXRhc2V0VXBkYXRlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2dlbmVyYXRlRHJhd1N0ZXBzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gW3sgYXR0clRvUHJvamVjdG9yOiB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKSwgYW5pbWF0b3I6IG5ldyBhbmltYXRvcnMuTnVsbCgpIH1dOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2FkZGl0aW9uYWxQYWludCA9IGZ1bmN0aW9uICh0aW1lKSB7CiAgICAgICAgICAgIC8vIG5vLW9wCiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBfYnVpbGRMaWdodHdlaWdodFBsb3RFbnRpdGllcyBjb25zdHVjdHMge0xpZ2h0d2VpZ2h0UGxvdEVudGl0eVtdfSBmcm9tCiAgICAgICAgICogYWxsIHRoZSBlbnRpdGllcyBpbiB0aGUgcGxvdAogICAgICAgICAqIEBwYXJhbSB7RGF0YXNldFtdfSBbZGF0YXNldHNdIC0gZGF0YXNldHMgY29tcHJpc2luZyB0aGlzIHBsb3QKICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fYnVpbGRMaWdodHdlaWdodFBsb3RFbnRpdGllcyA9IGZ1bmN0aW9uIChkYXRhc2V0cykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgbGlnaHR3ZWlnaHRQbG90RW50aXRpZXMgPSBbXTsKICAgICAgICAgICAgZGF0YXNldHMuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCwgZGF0YXNldEluZGV4KSB7CiAgICAgICAgICAgICAgICB2YXIgZHJhd2VyID0gX3RoaXMuX2RhdGFzZXRUb0RyYXdlci5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgdmFsaWREYXR1bUluZGV4ID0gMDsKICAgICAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YXNldC5kYXRhKCk7CiAgICAgICAgICAgICAgICB2YXIgZGF0YUxlbiA9IGRhdGEubGVuZ3RoOwogICAgICAgICAgICAgICAgdmFyIF9sb29wXzEgPSBmdW5jdGlvbiAoZGF0dW1JbmRleCkgewogICAgICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGRhdGFbZGF0dW1JbmRleF07CiAgICAgICAgICAgICAgICAgICAgdmFyIHBvc2l0aW9uID0gX3RoaXMuX3BpeGVsUG9pbnQoZGF0dW0sIGRhdHVtSW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIGlmICh1dGlscyQxLk1hdGguaXNOYU4ocG9zaXRpb24ueCkgfHwgdXRpbHMkMS5NYXRoLmlzTmFOKHBvc2l0aW9uLnkpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAiY29udGludWUiOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB2YXIgcGxvdCA9IF90aGlzOwogICAgICAgICAgICAgICAgICAgIGxpZ2h0d2VpZ2h0UGxvdEVudGl0aWVzLnB1c2goewogICAgICAgICAgICAgICAgICAgICAgICBkYXR1bTogZGF0dW0sCiAgICAgICAgICAgICAgICAgICAgICAgIGdldCBwb3NpdGlvbigpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIG9ubHkgY2FsY3VsYXRlIHBvc2l0aW9uIHdoZW4gbmVlZGluZyB0byBpbXByb3ZlIHBhbiB6b29tIHBlcmZvcm1hbmNlICMzMTU5CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gcGxvdC5fcGl4ZWxQb2ludC5jYWxsKHBsb3QsIGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICAgICAgaW5kZXg6IGRhdHVtSW5kZXgsCiAgICAgICAgICAgICAgICAgICAgICAgIGRhdGFzZXQ6IGRhdGFzZXQsCiAgICAgICAgICAgICAgICAgICAgICAgIGRhdGFzZXRJbmRleDogZGF0YXNldEluZGV4LAogICAgICAgICAgICAgICAgICAgICAgICBjb21wb25lbnQ6IF90aGlzLAogICAgICAgICAgICAgICAgICAgICAgICBkcmF3ZXI6IGRyYXdlciwKICAgICAgICAgICAgICAgICAgICAgICAgdmFsaWREYXR1bUluZGV4OiB2YWxpZERhdHVtSW5kZXgsCiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgdmFsaWREYXR1bUluZGV4Kys7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgZm9yICh2YXIgZGF0dW1JbmRleCA9IDA7IGRhdHVtSW5kZXggPCBkYXRhTGVuOyBkYXR1bUluZGV4KyspIHsKICAgICAgICAgICAgICAgICAgICBfbG9vcF8xKGRhdHVtSW5kZXgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGxpZ2h0d2VpZ2h0UGxvdEVudGl0aWVzOwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2dldERhdGFUb0RyYXcgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBkYXRhVG9EcmF3ID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHRoaXMuZGF0YXNldHMoKS5mb3JFYWNoKGZ1bmN0aW9uIChkYXRhc2V0KSB7IHJldHVybiBkYXRhVG9EcmF3LnNldChkYXRhc2V0LCBkYXRhc2V0LmRhdGEoKSk7IH0pOwogICAgICAgICAgICByZXR1cm4gZGF0YVRvRHJhdzsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9wYWludCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgZGVsZXRlIHRoaXMuX2NhY2hlZEF0dHJUb1Byb2plY3RvcjsKICAgICAgICAgICAgdmFyIGRyYXdTdGVwcyA9IHRoaXMuX2dlbmVyYXRlRHJhd1N0ZXBzKCk7CiAgICAgICAgICAgIHZhciBkYXRhVG9EcmF3ID0gdGhpcy5fZ2V0RGF0YVRvRHJhdygpOwogICAgICAgICAgICB2YXIgZHJhd2VycyA9IHRoaXMuZGF0YXNldHMoKS5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9kYXRhc2V0VG9EcmF3ZXIuZ2V0KGRhdGFzZXQpOyB9KTsKICAgICAgICAgICAgaWYgKHRoaXMucmVuZGVyZXIoKSA9PT0gImNhbnZhcyIpIHsKICAgICAgICAgICAgICAgIHZhciBjYW52YXMgPSB0aGlzLl9jYW52YXMubm9kZSgpOwogICAgICAgICAgICAgICAgdmFyIGNvbnRleHRfMSA9IGNhbnZhcy5nZXRDb250ZXh0KCIyZCIpOwogICAgICAgICAgICAgICAgY29udGV4dF8xLmNsZWFyUmVjdCgwLCAwLCBjYW52YXMuY2xpZW50V2lkdGgsIGNhbnZhcy5jbGllbnRIZWlnaHQpOwogICAgICAgICAgICAgICAgdGhpcy5fYnVmZmVyQ2FudmFzVmFsaWQgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZHMsIGkpIHsKICAgICAgICAgICAgICAgIHZhciBhcHBsaWVkRHJhd1N0ZXBzID0gUGxvdC5hcHBseURyYXdTdGVwcyhkcmF3U3RlcHMsIGRzKTsKICAgICAgICAgICAgICAgIGRyYXdlcnNbaV0uZHJhdyhkYXRhVG9EcmF3LmdldChkcyksIGFwcGxpZWREcmF3U3RlcHMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIHRpbWVzID0gdGhpcy5kYXRhc2V0cygpLm1hcChmdW5jdGlvbiAoZHMsIGkpIHsgcmV0dXJuIFBsb3QuZ2V0VG90YWxEcmF3VGltZShkYXRhVG9EcmF3LmdldChkcyksIGRyYXdTdGVwcyk7IH0pOwogICAgICAgICAgICB2YXIgbWF4VGltZSA9IHV0aWxzJDEuTWF0aC5tYXgodGltZXMsIDApOwogICAgICAgICAgICB0aGlzLl9hZGRpdGlvbmFsUGFpbnQobWF4VGltZSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXRyaWV2ZXMgdGhlIGRyYXduIHZpc3VhbCBlbGVtZW50cyBmb3IgdGhlIHNwZWNpZmllZCBEYXRhc2V0cyBhcyBhIGQzIFNlbGVjdGlvbi4KICAgICAgICAgKiBOb3Qgc3VwcG9ydGVkIG9uIGNhbnZhcyByZW5kZXJlci4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7RGF0YXNldFtdfSBbZGF0YXNldHNdIFRoZSBEYXRhc2V0cyB0byByZXRyaWV2ZSB0aGUgU2VsZWN0aW9ucyBmb3IuCiAgICAgICAgICogICBJZiBub3QgcHJvdmlkZWQsIFNlbGVjdGlvbnMgd2lsbCBiZSByZXRyaWV2ZWQgZm9yIGFsbCBEYXRhc2V0cyBvbiB0aGUgUGxvdC4KICAgICAgICAgKiBAcmV0dXJucyB7ZDMuU2VsZWN0aW9ufQogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLnNlbGVjdGlvbnMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKGRhdGFzZXRzID09PSB2b2lkIDApIHsgZGF0YXNldHMgPSB0aGlzLmRhdGFzZXRzKCk7IH0KICAgICAgICAgICAgaWYgKHRoaXMucmVuZGVyZXIoKSA9PT0gImNhbnZhcyIpIHsKICAgICAgICAgICAgICAgIC8vIHJldHVybiBlbXB0eSBzZWxlY3Rpb24KICAgICAgICAgICAgICAgIHJldHVybiBkMy5zZWxlY3RBbGwoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHZhciBzZWxlY3Rpb25zXzEgPSBbXTsKICAgICAgICAgICAgICAgIGRhdGFzZXRzLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgZHJhd2VyID0gX3RoaXMuX2RhdGFzZXRUb0RyYXdlci5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKGRyYXdlciA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgdmFyIHZpc3VhbFByaW1pdGl2ZXMgPSBkcmF3ZXIuZ2V0VmlzdWFsUHJpbWl0aXZlcygpOwogICAgICAgICAgICAgICAgICAgIHNlbGVjdGlvbnNfMS5wdXNoLmFwcGx5KHNlbGVjdGlvbnNfMSwgdmlzdWFsUHJpbWl0aXZlcyk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHJldHVybiBkMy5zZWxlY3RBbGwoc2VsZWN0aW9uc18xKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgRW50aXRpZXMgYXNzb2NpYXRlZCB3aXRoIHRoZSBzcGVjaWZpZWQgRGF0YXNldHMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge0RhdGFzZXRbXX0gZGF0YXNldHMgVGhlIERhdGFzZXRzIHRvIHJldHJpZXZlIHRoZSBFbnRpdGllcyBmb3IuCiAgICAgICAgICogICBJZiBub3QgcHJvdmlkZWQsIHJldHVybnMgZGVmYXVsdHMgdG8gYWxsIERhdGFzZXRzIG9uIHRoZSBQbG90LgogICAgICAgICAqIEByZXR1cm4ge1Bsb3RzLlBsb3RFbnRpdHlbXX0KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5lbnRpdGllcyA9IGZ1bmN0aW9uIChkYXRhc2V0cykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fZ2V0RW50aXR5U3RvcmUoZGF0YXNldHMpLmVudGl0aWVzKCkubWFwKGZ1bmN0aW9uIChlbnRpdHkpIHsgcmV0dXJuIF90aGlzLl9saWdodHdlaWdodFBsb3RFbnRpdHlUb1Bsb3RFbnRpdHkoZW50aXR5KTsgfSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBgUGxvdHMuUGxvdEVudGl0eWBzIGluIHRoZSBwbG90LCB3aGVyZWJ5IHRoZQogICAgICAgICAqIGBQbG90cy5JTGlnaHR3ZWlnaHRQbG90RW50aXR5YHMgYXJlIGZpbHRlcmVkIGJ5IHRoZSBwcm92aWRlZCBwcmVkaWNhdGUuCiAgICAgICAgICogU2luY2UgYF9saWdodHdlaWdodFBsb3RFbnRpdHlUb1Bsb3RFbnRpdHlgIGNhbiBiZSBleHBlbnNpdmUsIHRoaXMgbWV0aG9kCiAgICAgICAgICogY2FuIGJlIHVzZWZ1bCBmb3IgcGVyZm9ybWFuY2Ugb3B0aW1pemF0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHdoZXJlIEEgZmlsdGVyIHByZWRpY2F0ZSB0aGF0IGlzIGFwcGxpZWQgdG8gbGlnaHR3ZWlnaHQgZW50aXRpZXMKICAgICAgICAgKiBiZWZvcmUgdXBjb252ZXJ0aW5nIHRoZW0gdG8gZnVsbCBwbG90IGVudGl0aWVzCiAgICAgICAgICogQHJldHVybiB7UGxvdHMuUGxvdEVudGl0eVtdfQogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLmZpbHRlckVudGl0aWVzID0gZnVuY3Rpb24gKHdoZXJlKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXRFbnRpdHlTdG9yZSgpCiAgICAgICAgICAgICAgICAuZW50aXRpZXMoKQogICAgICAgICAgICAgICAgLmZpbHRlcih3aGVyZSkKICAgICAgICAgICAgICAgIC5tYXAoZnVuY3Rpb24gKGVudGl0eSkgeyByZXR1cm4gX3RoaXMuX2xpZ2h0d2VpZ2h0UGxvdEVudGl0eVRvUGxvdEVudGl0eShlbnRpdHkpOyB9KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIF9nZXRFbnRpdHlTdG9yZSByZXR1cm5zIHRoZSBzdG9yZSBvZiBhbGwgRW50aXRpZXMgYXNzb2NpYXRlZCB3aXRoIHRoZSBzcGVjaWZpZWQgZGF0YXNldAogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEYXRhc2V0W119IFtkYXRhc2V0c10gLSBUaGUgZGF0YXNldHMgd2l0aCB3aGljaCB0byBjb25zdHJ1Y3QgdGhlIHN0b3JlLiBJZiBubyBkYXRhc2V0cwogICAgICAgICAqIGFyZSBzcGVjaWZpZWQgYWxsIGRhdGFzZXRzIHdpbGwgYmUgdXNlZC4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fZ2V0RW50aXR5U3RvcmUgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGVudGl0eUJvdW5kc0ZhY3RvcnkgPSBmdW5jdGlvbiAoZW50aXR5KSB7IHJldHVybiBfdGhpcy5fZW50aXR5Qm91bmRzKGVudGl0eSk7IH07CiAgICAgICAgICAgIGlmIChkYXRhc2V0cyAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICB2YXIgZW50aXR5U3RvcmUgPSBuZXcgdXRpbHMkMS5FbnRpdHlTdG9yZSgpOwogICAgICAgICAgICAgICAgZW50aXR5U3RvcmUuYWRkQWxsKHRoaXMuX2J1aWxkTGlnaHR3ZWlnaHRQbG90RW50aXRpZXMoZGF0YXNldHMpLCBlbnRpdHlCb3VuZHNGYWN0b3J5LCB0aGlzLl9sb2NhbE9yaWdpbkJvdW5kcygpKTsKICAgICAgICAgICAgICAgIHJldHVybiBlbnRpdHlTdG9yZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0aGlzLl9jYWNoZWRFbnRpdHlTdG9yZSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICB2YXIgZW50aXR5U3RvcmUgPSBuZXcgdXRpbHMkMS5FbnRpdHlTdG9yZSgpOwogICAgICAgICAgICAgICAgZW50aXR5U3RvcmUuYWRkQWxsKHRoaXMuX2J1aWxkTGlnaHR3ZWlnaHRQbG90RW50aXRpZXModGhpcy5kYXRhc2V0cygpKSwgZW50aXR5Qm91bmRzRmFjdG9yeSwgdGhpcy5fbG9jYWxPcmlnaW5Cb3VuZHMoKSk7CiAgICAgICAgICAgICAgICB0aGlzLl9jYWNoZWRFbnRpdHlTdG9yZSA9IGVudGl0eVN0b3JlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jYWNoZWRFbnRpdHlTdG9yZTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIF9sb2NhbE9yaWdpbkJvdW5kcyByZXR1cm5zIGJvdW5kcyBvZiB0aGUgcGxvdCBmcm9tIGl0cyBvd24gb3JpZ2luLCByYXRoZXIgdGhhbiBmcm9tIHBhcmVudCBvcmlnaW4gKGFzIHByb3ZpZGVkIGJ5IGB0aGlzLmJvdW5kcygpYCkKICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm4ge0JvdW5kc30KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5fbG9jYWxPcmlnaW5Cb3VuZHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICB0b3BMZWZ0OiB7IHg6IDAsIHk6IDAgfSwKICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiB7IHg6IHRoaXMud2lkdGgoKSwgeTogdGhpcy5oZWlnaHQoKSB9LAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2VudGl0eUJvdW5kcyA9IGZ1bmN0aW9uIChlbnRpdHkpIHsKICAgICAgICAgICAgdmFyIGRhdHVtID0gZW50aXR5LmRhdHVtLCBpbmRleCA9IGVudGl0eS5pbmRleCwgZGF0YXNldCA9IGVudGl0eS5kYXRhc2V0OwogICAgICAgICAgICB2YXIgX2EgPSB0aGlzLl9waXhlbFBvaW50KGRhdHVtLCBpbmRleCwgZGF0YXNldCksIHggPSBfYS54LCB5ID0gX2EueTsKICAgICAgICAgICAgcmV0dXJuIHsgeDogeCwgeTogeSwgd2lkdGg6IDAsIGhlaWdodDogMCB9OwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2xpZ2h0d2VpZ2h0UGxvdEVudGl0eVRvUGxvdEVudGl0eSA9IGZ1bmN0aW9uIChlbnRpdHkpIHsKICAgICAgICAgICAgdmFyIHBsb3RFbnRpdHkgPSB7CiAgICAgICAgICAgICAgICBib3VuZHM6IHRoaXMuX2VudGl0eUJvdW5kcyhlbnRpdHkpLAogICAgICAgICAgICAgICAgY29tcG9uZW50OiBlbnRpdHkuY29tcG9uZW50LAogICAgICAgICAgICAgICAgZGF0YXNldDogZW50aXR5LmRhdGFzZXQsCiAgICAgICAgICAgICAgICBkYXRhc2V0SW5kZXg6IGVudGl0eS5kYXRhc2V0SW5kZXgsCiAgICAgICAgICAgICAgICBkYXR1bTogZW50aXR5LmRhdHVtLAogICAgICAgICAgICAgICAgaW5kZXg6IGVudGl0eS5pbmRleCwKICAgICAgICAgICAgICAgIHBvc2l0aW9uOiBlbnRpdHkucG9zaXRpb24sCiAgICAgICAgICAgICAgICBzZWxlY3Rpb246IGQzLnNlbGVjdChlbnRpdHkuZHJhd2VyLmdldFZpc3VhbFByaW1pdGl2ZUF0SW5kZXgoZW50aXR5LnZhbGlkRGF0dW1JbmRleCkpLAogICAgICAgICAgICB9OwogICAgICAgICAgICByZXR1cm4gcGxvdEVudGl0eTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIFBsb3RFbnRpdGllcyBhdCBhIHBhcnRpY3VsYXIgUG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBFYWNoIHBsb3QgdHlwZSBkZXRlcm1pbmVzIGhvdyB0byBsb2NhdGUgZW50aXRpZXMgYXQgb3IgbmVhciB0aGUgcXVlcnkKICAgICAgICAgKiBwb2ludC4gRm9yIGV4YW1wbGUsIGxpbmUgYW5kIGFyZWEgY2hhcnRzIHdpbGwgcmV0dXJuIHRoZSBuZWFyZXN0IGVudGl0eSwKICAgICAgICAgKiBidXQgYmFyIGNoYXJ0cyB3aWxsIG9ubHkgcmV0dXJuIHRoZSBlbnRpdGllcyB0aGF0IGZ1bGx5IGNvbnRhaW4gdGhlIHF1ZXJ5CiAgICAgICAgICogcG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBwb2ludCBUaGUgcG9pbnQgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge1Bsb3RFbnRpdHlbXX0gVGhlIFBsb3RFbnRpdGllcyBhdCB0aGUgcGFydGljdWxhciBwb2ludAogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLmVudGl0aWVzQXQgPSBmdW5jdGlvbiAocG9pbnQpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJwbG90cyBtdXN0IGltcGxlbWVudCBlbnRpdGllc0F0Iik7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSB7UGxvdHMuUGxvdEVudGl0eX0gbmVhcmVzdCB0byB0aGUgcXVlcnkgcG9pbnQsCiAgICAgICAgICogb3IgdW5kZWZpbmVkIGlmIG5vIHtQbG90cy5QbG90RW50aXR5fSBjYW4gYmUgZm91bmQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBxdWVyeVBvaW50CiAgICAgICAgICogQHJldHVybnMge1Bsb3RzLlBsb3RFbnRpdHl9IFRoZSBuZWFyZXN0IFBsb3RFbnRpdHksIG9yIHVuZGVmaW5lZCBpZiBubyB7UGxvdHMuUGxvdEVudGl0eX0gY2FuIGJlIGZvdW5kLgogICAgICAgICAqLwogICAgICAgIFBsb3QucHJvdG90eXBlLmVudGl0eU5lYXJlc3QgPSBmdW5jdGlvbiAocXVlcnlQb2ludCkgewogICAgICAgICAgICB2YXIgbmVhcmVzdCA9IHRoaXMuX2dldEVudGl0eVN0b3JlKCkuZW50aXR5TmVhcmVzdChxdWVyeVBvaW50KTsKICAgICAgICAgICAgcmV0dXJuIG5lYXJlc3QgPT09IHVuZGVmaW5lZCA/IHVuZGVmaW5lZCA6IHRoaXMuX2xpZ2h0d2VpZ2h0UGxvdEVudGl0eVRvUGxvdEVudGl0eShuZWFyZXN0KTsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLmVudGl0aWVzSW4gPSBmdW5jdGlvbiAoeFJhbmdlT3JCb3VuZHMsIHlSYW5nZSkgewogICAgICAgICAgICB2YXIgcXVlcnlCb3VuZHM7CiAgICAgICAgICAgIGlmICh5UmFuZ2UgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIGJvdW5kcyA9IHhSYW5nZU9yQm91bmRzOwogICAgICAgICAgICAgICAgcXVlcnlCb3VuZHMgPSB7CiAgICAgICAgICAgICAgICAgICAgeDogYm91bmRzLnRvcExlZnQueCwKICAgICAgICAgICAgICAgICAgICB5OiBib3VuZHMudG9wTGVmdC55LAogICAgICAgICAgICAgICAgICAgIHdpZHRoOiBib3VuZHMuYm90dG9tUmlnaHQueCAtIGJvdW5kcy50b3BMZWZ0LngsCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0OiBib3VuZHMuYm90dG9tUmlnaHQueSAtIGJvdW5kcy50b3BMZWZ0LnksCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdmFyIHhSYW5nZSA9IHhSYW5nZU9yQm91bmRzOwogICAgICAgICAgICAgICAgcXVlcnlCb3VuZHMgPSB7CiAgICAgICAgICAgICAgICAgICAgeDogeFJhbmdlLm1pbiwKICAgICAgICAgICAgICAgICAgICB5OiB5UmFuZ2UubWluLAogICAgICAgICAgICAgICAgICAgIHdpZHRoOiB4UmFuZ2UubWF4IC0geFJhbmdlLm1pbiwKICAgICAgICAgICAgICAgICAgICBoZWlnaHQ6IHlSYW5nZS5tYXggLSB5UmFuZ2UubWluLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5lbnRpdGllc0luQm91bmRzKHF1ZXJ5Qm91bmRzKTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIGVudGl0ZXMgd2hvc2UgYm91bmRpbmcgYm94ZXMgb3ZlcmxhcCB0aGUgcGFyYW1ldGVyLgogICAgICAgICAqCiAgICAgICAgICogYHF1ZXJ5Qm91bmRzYCBhcmUgaW4gcGl4ZWwgc3BhY2UsIG1lYXN1cmVkIGZyb20gdGhlIG9yaWdpbiBvZiB0aGlzIHBsb3QuCiAgICAgICAgICovCiAgICAgICAgUGxvdC5wcm90b3R5cGUuZW50aXRpZXNJbkJvdW5kcyA9IGZ1bmN0aW9uIChxdWVyeUJvdW5kcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgZm91bmQgPSB0aGlzLl9nZXRFbnRpdHlTdG9yZSgpLmVudGl0aWVzSW5Cb3VuZHMocXVlcnlCb3VuZHMpOwogICAgICAgICAgICBpZiAoIWZvdW5kKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmb3VuZC5tYXAoZnVuY3Rpb24gKGVudGl0eSkgeyByZXR1cm4gX3RoaXMuX2xpZ2h0d2VpZ2h0UGxvdEVudGl0eVRvUGxvdEVudGl0eShlbnRpdHkpOyB9KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIGVudGl0ZXMgd2hvc2UgYm91bmRpbmcgYm94ZXMgb3ZlcmxhcCB0aGUgYHF1ZXJ5Qm91bmRzYAogICAgICAgICAqIHBhcmFtZXRlciBvbiB0aGUgeC1heGlzLgogICAgICAgICAqCiAgICAgICAgICogYHF1ZXJ5Qm91bmRzYCBhcmUgaW4gcGl4ZWwgc3BhY2UsIG1lYXN1cmVkIGZyb20gdGhlIG9yaWdpbiBvZiB0aGlzIHBsb3QuCiAgICAgICAgICovCiAgICAgICAgUGxvdC5wcm90b3R5cGUuZW50aXRpZXNJblhCb3VuZHMgPSBmdW5jdGlvbiAocXVlcnlCb3VuZHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGZvdW5kID0gdGhpcy5fZ2V0RW50aXR5U3RvcmUoKS5lbnRpdGllc0luWEJvdW5kcyhxdWVyeUJvdW5kcyk7CiAgICAgICAgICAgIGlmICghZm91bmQpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZvdW5kLm1hcChmdW5jdGlvbiAoZW50aXR5KSB7IHJldHVybiBfdGhpcy5fbGlnaHR3ZWlnaHRQbG90RW50aXR5VG9QbG90RW50aXR5KGVudGl0eSk7IH0pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgZW50aXRlcyB3aG9zZSBib3VuZGluZyBib3hlcyBvdmVybGFwIHRoZSBgcXVlcnlCb3VuZHNgCiAgICAgICAgICogcGFyYW1ldGVyIG9uIHRoZSB5LWF4aXMuCiAgICAgICAgICoKICAgICAgICAgKiBgcXVlcnlCb3VuZHNgIGFyZSBpbiBwaXhlbCBzcGFjZSwgbWVhc3VyZWQgZnJvbSB0aGUgb3JpZ2luIG9mIHRoaXMgcGxvdC4KICAgICAgICAgKi8KICAgICAgICBQbG90LnByb3RvdHlwZS5lbnRpdGllc0luWUJvdW5kcyA9IGZ1bmN0aW9uIChxdWVyeUJvdW5kcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgZm91bmQgPSB0aGlzLl9nZXRFbnRpdHlTdG9yZSgpLmVudGl0aWVzSW5ZQm91bmRzKHF1ZXJ5Qm91bmRzKTsKICAgICAgICAgICAgaWYgKCFmb3VuZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZm91bmQubWFwKGZ1bmN0aW9uIChlbnRpdHkpIHsgcmV0dXJuIF90aGlzLl9saWdodHdlaWdodFBsb3RFbnRpdHlUb1Bsb3RFbnRpdHkoZW50aXR5KTsgfSk7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5fdW5pbnN0YWxsU2NhbGVGb3JLZXkgPSBmdW5jdGlvbiAoc2NhbGUsIGtleSkgewogICAgICAgICAgICBzY2FsZS5vZmZVcGRhdGUodGhpcy5fcmVuZGVyQ2FsbGJhY2spOwogICAgICAgICAgICBzY2FsZS5vZmZVcGRhdGUodGhpcy5fZGVmZXJyZWRSZXNldEVudGl0eVN0b3JlKTsKICAgICAgICAgICAgc2NhbGUucmVtb3ZlSW5jbHVkZWRWYWx1ZXNQcm92aWRlcih0aGlzLl9pbmNsdWRlZFZhbHVlc1Byb3ZpZGVyKTsKICAgICAgICB9OwogICAgICAgIFBsb3QucHJvdG90eXBlLl9pbnN0YWxsU2NhbGVGb3JLZXkgPSBmdW5jdGlvbiAoc2NhbGUsIGtleSkgewogICAgICAgICAgICBzY2FsZS5vblVwZGF0ZSh0aGlzLl9yZW5kZXJDYWxsYmFjayk7CiAgICAgICAgICAgIHNjYWxlLm9uVXBkYXRlKHRoaXMuX2RlZmVycmVkUmVzZXRFbnRpdHlTdG9yZSk7CiAgICAgICAgICAgIHNjYWxlLmFkZEluY2x1ZGVkVmFsdWVzUHJvdmlkZXIodGhpcy5faW5jbHVkZWRWYWx1ZXNQcm92aWRlcik7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5fcHJvcGVydHlQcm9qZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4ge307CiAgICAgICAgfTsKICAgICAgICBQbG90Ll9zY2FsZWRBY2Nlc3NvciA9IGZ1bmN0aW9uIChiaW5kaW5nKSB7CiAgICAgICAgICAgIHZhciBzY2FsZSA9IGJpbmRpbmcuc2NhbGUsIGFjY2Vzc29yID0gYmluZGluZy5hY2Nlc3NvciwgcG9zdFNjYWxlID0gYmluZGluZy5wb3N0U2NhbGU7CiAgICAgICAgICAgIC8vIGlmIHByb3ZpZGVkLCBhcHBseSBzY2FsZQogICAgICAgICAgICB2YXIgc2NhbGVkQWNjZXNvciA9IHNjYWxlID09IG51bGwgPyBhY2Nlc3NvciA6CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZCwgaSwgZHMpIHsgcmV0dXJuIHNjYWxlLnNjYWxlKGFjY2Vzc29yKGQsIGksIGRzKSk7IH07CiAgICAgICAgICAgIC8vIGlmIHByb3ZpZGVkLCBhcHBseSBwb3N0IHNjYWxlCiAgICAgICAgICAgIHZhciBwb3N0U2NhbGVkQWNjZXNvciA9IHBvc3RTY2FsZSA9PSBudWxsID8gc2NhbGVkQWNjZXNvciA6CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZCwgaSwgZHMpIHsgcmV0dXJuIHBvc3RTY2FsZShzY2FsZWRBY2Nlc29yKGQsIGksIGRzKSwgZCwgaSwgZHMpOyB9OwogICAgICAgICAgICByZXR1cm4gcG9zdFNjYWxlZEFjY2Vzb3I7CiAgICAgICAgfTsKICAgICAgICBQbG90LnByb3RvdHlwZS5fcGl4ZWxQb2ludCA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQpIHsKICAgICAgICAgICAgcmV0dXJuIHsgeDogMCwgeTogMCB9OwogICAgICAgIH07CiAgICAgICAgUGxvdC5wcm90b3R5cGUuX2FuaW1hdGVPbk5leHRSZW5kZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9hbmltYXRlICYmIHRoaXMuX2RhdGFDaGFuZ2VkOwogICAgICAgIH07CiAgICAgICAgUGxvdC5PUFRJTUlaRV9NRU1PSVpFX1BST0pFQ1RPUlMgPSBmYWxzZTsKICAgICAgICBQbG90Ll9BTklNQVRJT05fTUFYX0RVUkFUSU9OID0gNjAwOwogICAgICAgIHJldHVybiBQbG90OwogICAgfShjb21wb25lbnQuQ29tcG9uZW50KSk7CiAgICBleHBvcnRzLlBsb3QgPSBQbG90OwogICAgZnVuY3Rpb24gY29tcHV0ZUV4dGVudChkYXRhc2V0LCBhY2NTY2FsZUJpbmRpbmcsIGZpbHRlcikgewogICAgICAgIHZhciBhY2Nlc3NvciA9IGFjY1NjYWxlQmluZGluZy5hY2Nlc3NvcjsKICAgICAgICB2YXIgc2NhbGUgPSBhY2NTY2FsZUJpbmRpbmcuc2NhbGU7CiAgICAgICAgaWYgKHNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgIH0KICAgICAgICB2YXIgZGF0YSA9IGRhdGFzZXQuZGF0YSgpOwogICAgICAgIGlmIChmaWx0ZXIgIT0gbnVsbCkgewogICAgICAgICAgICBkYXRhID0gZGF0YS5maWx0ZXIoZnVuY3Rpb24gKGQsIGkpIHsgcmV0dXJuIGZpbHRlcihkLCBpLCBkYXRhc2V0KTsgfSk7CiAgICAgICAgfQogICAgICAgIHZhciBhcHBsaWVkQWNjZXNzb3IgPSBmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gYWNjZXNzb3IoZCwgaSwgZGF0YXNldCk7IH07CiAgICAgICAgdmFyIG1hcHBlZERhdGEgPSBkYXRhLm1hcChhcHBsaWVkQWNjZXNzb3IpOwogICAgICAgIHJldHVybiBzY2FsZS5leHRlbnRPZlZhbHVlcyhtYXBwZWREYXRhKTsKICAgIH0KICAgIH0pOwoKICAgIHZhciBwbG90R3JvdXAgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCiAgICB2YXIgUGxvdEdyb3VwID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUGxvdEdyb3VwLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFBsb3RHcm91cCgpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlciAhPT0gbnVsbCAmJiBfc3VwZXIuYXBwbHkodGhpcywgYXJndW1lbnRzKSB8fCB0aGlzOwogICAgICAgIH0KICAgICAgICBQbG90R3JvdXAucHJvdG90eXBlLmVudGl0eU5lYXJlc3QgPSBmdW5jdGlvbiAocG9pbnQpIHsKICAgICAgICAgICAgdmFyIGNsb3Nlc3RQbG90RW50aXR5OwogICAgICAgICAgICB2YXIgbWluRGlzdFNxdWFyZWQgPSBJbmZpbml0eTsKICAgICAgICAgICAgdGhpcy5jb21wb25lbnRzKCkuZm9yRWFjaChmdW5jdGlvbiAocGxvdENvbXBvbmVudCkgewogICAgICAgICAgICAgICAgLy8gd2Uga25vdyBpdCdzIGEgUGxvdCBzaW5jZSAuYXBwZW5kKCkgdGhyb3dzIGEgcnVudGltZSBlcnJvciBvdGhlcndpc2UKICAgICAgICAgICAgICAgIHZhciBwbG90ID0gcGxvdENvbXBvbmVudDsKICAgICAgICAgICAgICAgIHZhciBjYW5kaWRhdGVQbG90RW50aXR5ID0gcGxvdC5lbnRpdHlOZWFyZXN0KHBvaW50KTsKICAgICAgICAgICAgICAgIGlmIChjYW5kaWRhdGVQbG90RW50aXR5ID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgZGlzdFNxdWFyZWQgPSB1dGlscyQxLk1hdGguZGlzdGFuY2VTcXVhcmVkKGNhbmRpZGF0ZVBsb3RFbnRpdHkucG9zaXRpb24sIHBvaW50KTsKICAgICAgICAgICAgICAgIGlmIChkaXN0U3F1YXJlZCA8PSBtaW5EaXN0U3F1YXJlZCkgewogICAgICAgICAgICAgICAgICAgIG1pbkRpc3RTcXVhcmVkID0gZGlzdFNxdWFyZWQ7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdFBsb3RFbnRpdHkgPSBjYW5kaWRhdGVQbG90RW50aXR5OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGNsb3Nlc3RQbG90RW50aXR5OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIFBsb3QgdG8gdGhpcyBQbG90IEdyb3VwLgogICAgICAgICAqIFRoZSBhZGRlZCBQbG90IHdpbGwgYmUgcmVuZGVyZWQgYWJvdmUgUGxvdHMgYWxyZWFkeSBpbiB0aGUgR3JvdXAuCiAgICAgICAgICovCiAgICAgICAgUGxvdEdyb3VwLnByb3RvdHlwZS5hcHBlbmQgPSBmdW5jdGlvbiAocGxvdCQxKSB7CiAgICAgICAgICAgIGlmIChwbG90JDEgIT0gbnVsbCAmJiAhKHBsb3QkMSBpbnN0YW5jZW9mIHBsb3QuUGxvdCkpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiUGxvdCBHcm91cCBvbmx5IGFjY2VwdHMgcGxvdHMiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmFwcGVuZC5jYWxsKHRoaXMsIHBsb3QkMSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFBsb3RHcm91cDsKICAgIH0oZ3JvdXAuR3JvdXApKTsKICAgIGV4cG9ydHMuUGxvdEdyb3VwID0gUGxvdEdyb3VwOwogICAgfSk7CgogICAgdmFyIHRhYmxlID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgogICAgdmFyIFRhYmxlID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoVGFibGUsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBUYWJsZSBjb21iaW5lcyBDb21wb25lbnRzIGluIHRoZSBmb3JtIG9mIGEgZ3JpZC4gQQogICAgICAgICAqIGNvbW1vbiBjYXNlIGlzIGNvbWJpbmluZyBhIHktYXhpcywgeC1heGlzLCBhbmQgdGhlIHBsb3R0ZWQgZGF0YSB2aWEKICAgICAgICAgKiBgYGB0eXBlc2NyaXB0CiAgICAgICAgICogbmV3IFRhYmxlKFtbeUF4aXMsIHBsb3RdLAogICAgICAgICAqICAgICAgICAgICAgW251bGwsICB4QXhpc11dKTsKICAgICAgICAgKiBgYGAKICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqIEBwYXJhbSB7KENvbXBvbmVudHxudWxsfHVuZGVmaW5lZClbXVtdfSBbcm93cz1bXV0gQSAyLUQgYXJyYXkgb2YgQ29tcG9uZW50cyB0byBiZSBhZGRlZCB0byB0aGUgVGFibGUuCiAgICAgICAgICogICBudWxsIGNhbiBiZSB1c2VkIGlmIGEgY2VsbCBpcyBlbXB0eS4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBUYWJsZShyb3dzKSB7CiAgICAgICAgICAgIGlmIChyb3dzID09PSB2b2lkIDApIHsgcm93cyA9IFtdOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9yb3dQYWRkaW5nID0gMDsKICAgICAgICAgICAgX3RoaXMuX2NvbHVtblBhZGRpbmcgPSAwOwogICAgICAgICAgICBfdGhpcy5fcm93cyA9IFtdOwogICAgICAgICAgICBfdGhpcy5fcm93V2VpZ2h0cyA9IFtdOwogICAgICAgICAgICBfdGhpcy5fY29sdW1uV2VpZ2h0cyA9IFtdOwogICAgICAgICAgICBfdGhpcy5fblJvd3MgPSAwOwogICAgICAgICAgICBfdGhpcy5fbkNvbHMgPSAwOwogICAgICAgICAgICBfdGhpcy5fY2FsY3VsYXRlZExheW91dCA9IG51bGw7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJ0YWJsZSIpOwogICAgICAgICAgICByb3dzLmZvckVhY2goZnVuY3Rpb24gKHJvdywgcm93SW5kZXgpIHsKICAgICAgICAgICAgICAgIHJvdy5mb3JFYWNoKGZ1bmN0aW9uIChjb21wb25lbnQsIGNvbEluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKGNvbXBvbmVudCAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIF90aGlzLmFkZChjb21wb25lbnQsIHJvd0luZGV4LCBjb2xJbmRleCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFRhYmxlLnByb3RvdHlwZS5fZm9yRWFjaCA9IGZ1bmN0aW9uIChjYWxsYmFjaykgewogICAgICAgICAgICBmb3IgKHZhciByID0gMDsgciA8IHRoaXMuX25Sb3dzOyByKyspIHsKICAgICAgICAgICAgICAgIGZvciAodmFyIGMgPSAwOyBjIDwgdGhpcy5fbkNvbHM7IGMrKykgewogICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLl9yb3dzW3JdW2NdICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY2FsbGJhY2sodGhpcy5fcm93c1tyXVtjXSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDaGVja3Mgd2hldGhlciB0aGUgc3BlY2lmaWVkIENvbXBvbmVudCBpcyBpbiB0aGUgVGFibGUuCiAgICAgICAgICovCiAgICAgICAgVGFibGUucHJvdG90eXBlLmhhcyA9IGZ1bmN0aW9uIChjb21wb25lbnQpIHsKICAgICAgICAgICAgZm9yICh2YXIgciA9IDA7IHIgPCB0aGlzLl9uUm93czsgcisrKSB7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBjID0gMDsgYyA8IHRoaXMuX25Db2xzOyBjKyspIHsKICAgICAgICAgICAgICAgICAgICBpZiAodGhpcy5fcm93c1tyXVtjXSA9PT0gY29tcG9uZW50KSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBDb21wb25lbnQgYXQgdGhlIHNwZWNpZmllZCByb3cgYW5kIGNvbHVtbiBpbmRleC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSByb3dJbmRleAogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBjb2x1bW5JbmRleAogICAgICAgICAqIEByZXR1cm5zIHtDb21wb25lbnR9IFRoZSBDb21wb25lbnQgYXQgdGhlIHNwZWNpZmllZCBwb3NpdGlvbiwgb3IgbnVsbCBpZiBubyBDb21wb25lbnQgaXMgdGhlcmUuCiAgICAgICAgICovCiAgICAgICAgVGFibGUucHJvdG90eXBlLmNvbXBvbmVudEF0ID0gZnVuY3Rpb24gKHJvd0luZGV4LCBjb2x1bW5JbmRleCkgewogICAgICAgICAgICBpZiAocm93SW5kZXggPCAwIHx8IHJvd0luZGV4ID49IHRoaXMuX25Sb3dzIHx8IGNvbHVtbkluZGV4IDwgMCB8fCBjb2x1bW5JbmRleCA+PSB0aGlzLl9uQ29scykgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Jvd3Nbcm93SW5kZXhdW2NvbHVtbkluZGV4XTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEFkZHMgYSBDb21wb25lbnQgaW4gdGhlIHNwZWNpZmllZCByb3cgYW5kIGNvbHVtbiBwb3NpdGlvbi4KICAgICAgICAgKgogICAgICAgICAqIEZvciBleGFtcGxlLCBpbnN0ZWFkIG9mIGNhbGxpbmcgYG5ldyBUYWJsZShbW2EsIGJdLCBbbnVsbCwgY11dKWAsIHlvdQogICAgICAgICAqIGNvdWxkIGNhbGwKICAgICAgICAgKiB2YXIgdGFibGUgPSBuZXcgUGxvdHRhYmxlLkNvbXBvbmVudHMuVGFibGUoKTsKICAgICAgICAgKiB0YWJsZS5hZGQoYSwgMCwgMCk7CiAgICAgICAgICogdGFibGUuYWRkKGIsIDAsIDEpOwogICAgICAgICAqIHRhYmxlLmFkZChjLCAxLCAxKTsKICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7Q29tcG9uZW50fSBjb21wb25lbnQgVGhlIENvbXBvbmVudCB0byBiZSBhZGRlZC4KICAgICAgICAgKiBAcGFyYW0ge251bWJlcn0gcm93CiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGNvbAogICAgICAgICAqIEByZXR1cm5zIHtUYWJsZX0gVGhlIGNhbGxpbmcgVGFibGUuCiAgICAgICAgICovCiAgICAgICAgVGFibGUucHJvdG90eXBlLmFkZCA9IGZ1bmN0aW9uIChjb21wb25lbnQsIHJvdywgY29sKSB7CiAgICAgICAgICAgIGlmIChjb21wb25lbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoIkNhbm5vdCBhZGQgbnVsbCB0byBhIHRhYmxlIGNlbGwiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoIXRoaXMuaGFzKGNvbXBvbmVudCkpIHsKICAgICAgICAgICAgICAgIHZhciBjdXJyZW50Q29tcG9uZW50ID0gdGhpcy5fcm93c1tyb3ddICYmIHRoaXMuX3Jvd3Nbcm93XVtjb2xdOwogICAgICAgICAgICAgICAgaWYgKGN1cnJlbnRDb21wb25lbnQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiY2VsbCBpcyBvY2N1cGllZCIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29tcG9uZW50LmRldGFjaCgpOwogICAgICAgICAgICAgICAgdGhpcy5fblJvd3MgPSBNYXRoLm1heChyb3cgKyAxLCB0aGlzLl9uUm93cyk7CiAgICAgICAgICAgICAgICB0aGlzLl9uQ29scyA9IE1hdGgubWF4KGNvbCArIDEsIHRoaXMuX25Db2xzKTsKICAgICAgICAgICAgICAgIHRoaXMuX3BhZFRhYmxlVG9TaXplKHRoaXMuX25Sb3dzLCB0aGlzLl9uQ29scyk7CiAgICAgICAgICAgICAgICB0aGlzLl9yb3dzW3Jvd11bY29sXSA9IGNvbXBvbmVudDsKICAgICAgICAgICAgICAgIHRoaXMuX2Fkb3B0QW5kQW5jaG9yKGNvbXBvbmVudCk7CiAgICAgICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgVGFibGUucHJvdG90eXBlLl9yZW1vdmUgPSBmdW5jdGlvbiAoY29tcG9uZW50KSB7CiAgICAgICAgICAgIGZvciAodmFyIHIgPSAwOyByIDwgdGhpcy5fblJvd3M7IHIrKykgewogICAgICAgICAgICAgICAgZm9yICh2YXIgYyA9IDA7IGMgPCB0aGlzLl9uQ29sczsgYysrKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuX3Jvd3Nbcl1bY10gPT09IGNvbXBvbmVudCkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9yb3dzW3JdW2NdID0gbnVsbDsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9OwogICAgICAgIFRhYmxlLnByb3RvdHlwZS5faXRlcmF0ZUxheW91dCA9IGZ1bmN0aW9uIChhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0LCBpc0ZpbmFsT2ZmZXIpIHsKICAgICAgICAgICAgaWYgKGlzRmluYWxPZmZlciA9PT0gdm9pZCAwKSB7IGlzRmluYWxPZmZlciA9IGZhbHNlOyB9CiAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAqIEdpdmVuIGF2YWlsYWJsZVdpZHRoIGFuZCBhdmFpbGFibGVIZWlnaHQsIGZpZ3VyZSBvdXQgaG93IHRvIGFsbG9jYXRlIGl0IGJldHdlZW4gcm93cyBhbmQgY29sdW1ucyB1c2luZyBhbiBpdGVyYXRpdmUgYWxnb3JpdGhtLgogICAgICAgICAgICAgKgogICAgICAgICAgICAgKiBGb3IgYm90aCBkaW1lbnNpb25zLCBrZWVwcyB0cmFjayBvZiAiZ3VhcmFudGVlZFNwYWNlIiwgd2hpY2ggdGhlIGZpeGVkLXNpemUgY29tcG9uZW50cyBoYXZlIHJlcXVlc3RlZCwgYW5kCiAgICAgICAgICAgICAqICJwcm9wb3J0aW9uYWxTcGFjZSIsIHdoaWNoIGlzIGJlaW5nIGdpdmVuIHRvIHByb3BvcnRpb25hbGx5LWdyb3dpbmcgY29tcG9uZW50cyBhY2NvcmRpbmcgdG8gdGhlIHdlaWdodHMgb24gdGhlIHRhYmxlLgogICAgICAgICAgICAgKiBIZXJlIGlzIGhvdyBpdCB3b3JrcyAoZXhhbXBsZSB1c2VzIHdpZHRoIGJ1dCBpdCBpcyB0aGUgc2FtZSBmb3IgaGVpZ2h0KS4gRmlyc3QsIGNvbHVtbnMgYXJlIGd1YXJhbnRlZWQgbm8gd2lkdGgsIGFuZAogICAgICAgICAgICAgKiB0aGUgZnJlZSB3aWR0aCBpcyBhbGxvY2F0ZWQgdG8gY29sdW1ucyBiYXNlZCBvbiB0aGVpciBjb2xXZWlnaHRzLiBUaGVuLCBpbiBkZXRlcm1pbmVHdWFyYW50ZWVzLCBldmVyeSBjb21wb25lbnQgaXMKICAgICAgICAgICAgICogb2ZmZXJlZCBpdHMgY29sdW1uJ3Mgd2lkdGggYW5kIG1heSByZXF1ZXN0IHNvbWUgYW1vdW50IG9mIGl0LCB3aGljaCBpbmNyZWFzZXMgdGhhdCBjb2x1bW4ncyBndWFyYW50ZWVkCiAgICAgICAgICAgICAqIHdpZHRoLiBJZiB0aGVyZSBhcmUgc29tZSBjb21wb25lbnRzIHRoYXQgd2VyZSBub3Qgc2F0aXNmaWVkIHdpdGggdGhlIHdpZHRoIHRoZXkgd2VyZSBvZmZlcmVkLCBhbmQgdGhlcmUgaXMgZnJlZQogICAgICAgICAgICAgKiB3aWR0aCB0aGF0IGhhcyBub3QgYWxyZWFkeSBiZWVuIGd1YXJhbnRlZWQsIHRoZW4gdGhlIHJlbWFpbmluZyB3aWR0aCBpcyBhbGxvY2F0ZWQgdG8gdGhlIHVuc2F0aXNmaWVkIGNvbHVtbnMgYW5kIHRoZQogICAgICAgICAgICAgKiBhbGdvcml0aG0gcnVucyBhZ2Fpbi4gSWYgYWxsIGNvbXBvbmVudHMgYXJlIHNhdGlzZmllZCwgdGhlbiB0aGUgcmVtYWluaW5nIHdpZHRoIGlzIGFsbG9jYXRlZCBhcyBwcm9wb3J0aW9uYWwgc3BhY2UKICAgICAgICAgICAgICogYWNjb3JkaW5nIHRvIHRoZSBjb2xXZWlnaHRzLgogICAgICAgICAgICAgKgogICAgICAgICAgICAgKiBUaGUgZ3VhcmFudGVlZCB3aWR0aCBmb3IgZWFjaCBjb2x1bW4gaXMgbW9ub3RvbmljYWxseSBpbmNyZWFzaW5nIGFzIHRoZSBhbGdvcml0aG0gaXRlcmF0ZXMuIFNpbmNlIGl0IGlzIGRldGVybWluaXN0aWMKICAgICAgICAgICAgICogYW5kIG1vbm90b25pY2FsbHkgaW5jcmVhc2luZywgaWYgdGhlIGZyZWVXaWR0aCBkb2VzIG5vdCBjaGFuZ2UgZHVyaW5nIGFuIGl0ZXJhdGlvbiBpdCBpbXBsaWVzIHRoYXQgbm8gZnVydGhlciBwcm9ncmVzcwogICAgICAgICAgICAgKiBpcyBwb3NzaWJsZSwgc28gdGhlIGFsZ29yaXRobSB3aWxsIG5vdCBjb250aW51ZSBpdGVyYXRpbmcgb24gdGhhdCBkaW1lbnNpb24ncyBhY2NvdW50LgogICAgICAgICAgICAgKgogICAgICAgICAgICAgKiBJZiB0aGUgYWxnb3JpdGhtIHJ1bnMgbW9yZSB0aGFuIDUgdGltZXMsIHdlIHN0b3AgYW5kIGp1c3QgdXNlIHdoYXRldmVyIHdlIGFycml2ZWQgYXQuIEl0J3Mgbm90IGNsZWFyIHVuZGVyIHdoYXQKICAgICAgICAgICAgICogY2lyY3Vtc3RhbmNlcyB0aGlzIHdpbGwgaGFwcGVuIG9yIGlmIGl0IHdpbGwgaGFwcGVuIGF0IGFsbC4gQSBtZXNzYWdlIHdpbGwgYmUgcHJpbnRlZCB0byB0aGUgY29uc29sZSBpZiB0aGlzIG9jY3Vycy4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICovCiAgICAgICAgICAgIHZhciByb3dzID0gdGhpcy5fcm93czsKICAgICAgICAgICAgdmFyIGNvbHMgPSBkMy50cmFuc3Bvc2UodGhpcy5fcm93cyk7CiAgICAgICAgICAgIHZhciBhdmFpbGFibGVXaWR0aEFmdGVyUGFkZGluZyA9IGF2YWlsYWJsZVdpZHRoIC0gdGhpcy5fY29sdW1uUGFkZGluZyAqICh0aGlzLl9uQ29scyAtIDEpOwogICAgICAgICAgICB2YXIgYXZhaWxhYmxlSGVpZ2h0QWZ0ZXJQYWRkaW5nID0gYXZhaWxhYmxlSGVpZ2h0IC0gdGhpcy5fcm93UGFkZGluZyAqICh0aGlzLl9uUm93cyAtIDEpOwogICAgICAgICAgICB2YXIgcm93V2VpZ2h0cyA9IFRhYmxlLl9jYWxjQ29tcG9uZW50V2VpZ2h0cyh0aGlzLl9yb3dXZWlnaHRzLCByb3dzLCBmdW5jdGlvbiAoYykgeyByZXR1cm4gKGMgPT0gbnVsbCkgfHwgYy5maXhlZEhlaWdodCgpOyB9KTsKICAgICAgICAgICAgdmFyIGNvbFdlaWdodHMgPSBUYWJsZS5fY2FsY0NvbXBvbmVudFdlaWdodHModGhpcy5fY29sdW1uV2VpZ2h0cywgY29scywgZnVuY3Rpb24gKGMpIHsgcmV0dXJuIChjID09IG51bGwpIHx8IGMuZml4ZWRXaWR0aCgpOyB9KTsKICAgICAgICAgICAgLy8gVG8gZ2l2ZSB0aGUgdGFibGUgYSBnb29kIHN0YXJ0aW5nIHBvc2l0aW9uIHRvIGl0ZXJhdGUgZnJvbSwgd2UgZ2l2ZSB0aGUgZml4ZWQtd2lkdGggY29tcG9uZW50cyBoYWxmLXdlaWdodAogICAgICAgICAgICAvLyBzbyB0aGF0IHRoZXkgd2lsbCBnZXQgc29tZSBpbml0aWFsIHNwYWNlIGFsbG9jYXRlZCB0byB3b3JrIHdpdGgKICAgICAgICAgICAgdmFyIGhldXJpc3RpY0NvbFdlaWdodHMgPSBjb2xXZWlnaHRzLm1hcChmdW5jdGlvbiAoYykgeyByZXR1cm4gYyA9PT0gMCA/IDAuNSA6IGM7IH0pOwogICAgICAgICAgICB2YXIgaGV1cmlzdGljUm93V2VpZ2h0cyA9IHJvd1dlaWdodHMubWFwKGZ1bmN0aW9uIChjKSB7IHJldHVybiBjID09PSAwID8gMC41IDogYzsgfSk7CiAgICAgICAgICAgIHZhciBjb2xQcm9wb3J0aW9uYWxTcGFjZSA9IFRhYmxlLl9jYWxjUHJvcG9ydGlvbmFsU3BhY2UoaGV1cmlzdGljQ29sV2VpZ2h0cywgYXZhaWxhYmxlV2lkdGhBZnRlclBhZGRpbmcpOwogICAgICAgICAgICB2YXIgcm93UHJvcG9ydGlvbmFsU3BhY2UgPSBUYWJsZS5fY2FsY1Byb3BvcnRpb25hbFNwYWNlKGhldXJpc3RpY1Jvd1dlaWdodHMsIGF2YWlsYWJsZUhlaWdodEFmdGVyUGFkZGluZyk7CiAgICAgICAgICAgIHZhciBndWFyYW50ZWVkV2lkdGhzID0gdXRpbHMkMS5BcnJheS5jcmVhdGVGaWxsZWRBcnJheSgwLCB0aGlzLl9uQ29scyk7CiAgICAgICAgICAgIHZhciBndWFyYW50ZWVkSGVpZ2h0cyA9IHV0aWxzJDEuQXJyYXkuY3JlYXRlRmlsbGVkQXJyYXkoMCwgdGhpcy5fblJvd3MpOwogICAgICAgICAgICB2YXIgZnJlZVdpZHRoOwogICAgICAgICAgICB2YXIgZnJlZUhlaWdodDsKICAgICAgICAgICAgdmFyIG5JdGVyYXRpb25zID0gMDsKICAgICAgICAgICAgdmFyIGd1YXJhbnRlZXM7CiAgICAgICAgICAgIHZhciB3YW50c1dpZHRoOwogICAgICAgICAgICB2YXIgd2FudHNIZWlnaHQ7CiAgICAgICAgICAgIHdoaWxlICh0cnVlKSB7CiAgICAgICAgICAgICAgICB2YXIgb2ZmZXJlZEhlaWdodHMgPSB1dGlscyQxLkFycmF5LmFkZChndWFyYW50ZWVkSGVpZ2h0cywgcm93UHJvcG9ydGlvbmFsU3BhY2UpOwogICAgICAgICAgICAgICAgdmFyIG9mZmVyZWRXaWR0aHMgPSB1dGlscyQxLkFycmF5LmFkZChndWFyYW50ZWVkV2lkdGhzLCBjb2xQcm9wb3J0aW9uYWxTcGFjZSk7CiAgICAgICAgICAgICAgICBndWFyYW50ZWVzID0gdGhpcy5fZGV0ZXJtaW5lR3VhcmFudGVlcyhvZmZlcmVkV2lkdGhzLCBvZmZlcmVkSGVpZ2h0cywgaXNGaW5hbE9mZmVyKTsKICAgICAgICAgICAgICAgIGd1YXJhbnRlZWRXaWR0aHMgPSBndWFyYW50ZWVzLmd1YXJhbnRlZWRXaWR0aHM7CiAgICAgICAgICAgICAgICBndWFyYW50ZWVkSGVpZ2h0cyA9IGd1YXJhbnRlZXMuZ3VhcmFudGVlZEhlaWdodHM7CiAgICAgICAgICAgICAgICB3YW50c1dpZHRoID0gZ3VhcmFudGVlcy53YW50c1dpZHRoQXJyLnNvbWUoZnVuY3Rpb24gKHgpIHsgcmV0dXJuIHg7IH0pOwogICAgICAgICAgICAgICAgd2FudHNIZWlnaHQgPSBndWFyYW50ZWVzLndhbnRzSGVpZ2h0QXJyLnNvbWUoZnVuY3Rpb24gKHgpIHsgcmV0dXJuIHg7IH0pOwogICAgICAgICAgICAgICAgdmFyIGxhc3RGcmVlV2lkdGggPSBmcmVlV2lkdGg7CiAgICAgICAgICAgICAgICB2YXIgbGFzdEZyZWVIZWlnaHQgPSBmcmVlSGVpZ2h0OwogICAgICAgICAgICAgICAgZnJlZVdpZHRoID0gYXZhaWxhYmxlV2lkdGhBZnRlclBhZGRpbmcgLSBkMy5zdW0oZ3VhcmFudGVlcy5ndWFyYW50ZWVkV2lkdGhzKTsKICAgICAgICAgICAgICAgIGZyZWVIZWlnaHQgPSBhdmFpbGFibGVIZWlnaHRBZnRlclBhZGRpbmcgLSBkMy5zdW0oZ3VhcmFudGVlcy5ndWFyYW50ZWVkSGVpZ2h0cyk7CiAgICAgICAgICAgICAgICB2YXIgeFdlaWdodHMgPSB2b2lkIDA7CiAgICAgICAgICAgICAgICBpZiAod2FudHNXaWR0aCkgewogICAgICAgICAgICAgICAgICAgIHhXZWlnaHRzID0gZ3VhcmFudGVlcy53YW50c1dpZHRoQXJyLm1hcChmdW5jdGlvbiAoeCkgeyByZXR1cm4geCA/IDAuMSA6IDA7IH0pOwogICAgICAgICAgICAgICAgICAgIHhXZWlnaHRzID0gdXRpbHMkMS5BcnJheS5hZGQoeFdlaWdodHMsIGNvbFdlaWdodHMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgeFdlaWdodHMgPSBjb2xXZWlnaHRzOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIHlXZWlnaHRzID0gdm9pZCAwOwogICAgICAgICAgICAgICAgaWYgKHdhbnRzSGVpZ2h0KSB7CiAgICAgICAgICAgICAgICAgICAgeVdlaWdodHMgPSBndWFyYW50ZWVzLndhbnRzSGVpZ2h0QXJyLm1hcChmdW5jdGlvbiAoeCkgeyByZXR1cm4geCA/IDAuMSA6IDA7IH0pOwogICAgICAgICAgICAgICAgICAgIHlXZWlnaHRzID0gdXRpbHMkMS5BcnJheS5hZGQoeVdlaWdodHMsIHJvd1dlaWdodHMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgeVdlaWdodHMgPSByb3dXZWlnaHRzOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29sUHJvcG9ydGlvbmFsU3BhY2UgPSBUYWJsZS5fY2FsY1Byb3BvcnRpb25hbFNwYWNlKHhXZWlnaHRzLCBmcmVlV2lkdGgpOwogICAgICAgICAgICAgICAgcm93UHJvcG9ydGlvbmFsU3BhY2UgPSBUYWJsZS5fY2FsY1Byb3BvcnRpb25hbFNwYWNlKHlXZWlnaHRzLCBmcmVlSGVpZ2h0KTsKICAgICAgICAgICAgICAgIG5JdGVyYXRpb25zKys7CiAgICAgICAgICAgICAgICB2YXIgY2FuSW1wcm92ZVdpZHRoQWxsb2NhdGlvbiA9IGZyZWVXaWR0aCA+IDAgJiYgZnJlZVdpZHRoICE9PSBsYXN0RnJlZVdpZHRoOwogICAgICAgICAgICAgICAgdmFyIGNhbkltcHJvdmVIZWlnaHRBbGxvY2F0aW9uID0gZnJlZUhlaWdodCA+IDAgJiYgZnJlZUhlaWdodCAhPT0gbGFzdEZyZWVIZWlnaHQ7CiAgICAgICAgICAgICAgICBpZiAoIShjYW5JbXByb3ZlV2lkdGhBbGxvY2F0aW9uIHx8IGNhbkltcHJvdmVIZWlnaHRBbGxvY2F0aW9uKSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKG5JdGVyYXRpb25zID4gNSkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFJlZG8gdGhlIHByb3BvcnRpb25hbCBzcGFjZSBvbmUgbGFzdCB0aW1lLCB0byBlbnN1cmUgd2UgdXNlIHRoZSByZWFsIHdlaWdodHMgbm90IHRoZSB3YW50c1dpZHRoL0hlaWdodCB3ZWlnaHRzCiAgICAgICAgICAgIGZyZWVXaWR0aCA9IGF2YWlsYWJsZVdpZHRoQWZ0ZXJQYWRkaW5nIC0gZDMuc3VtKGd1YXJhbnRlZXMuZ3VhcmFudGVlZFdpZHRocyk7CiAgICAgICAgICAgIGZyZWVIZWlnaHQgPSBhdmFpbGFibGVIZWlnaHRBZnRlclBhZGRpbmcgLSBkMy5zdW0oZ3VhcmFudGVlcy5ndWFyYW50ZWVkSGVpZ2h0cyk7CiAgICAgICAgICAgIGNvbFByb3BvcnRpb25hbFNwYWNlID0gVGFibGUuX2NhbGNQcm9wb3J0aW9uYWxTcGFjZShjb2xXZWlnaHRzLCBmcmVlV2lkdGgpOwogICAgICAgICAgICByb3dQcm9wb3J0aW9uYWxTcGFjZSA9IFRhYmxlLl9jYWxjUHJvcG9ydGlvbmFsU3BhY2Uocm93V2VpZ2h0cywgZnJlZUhlaWdodCk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBjb2xQcm9wb3J0aW9uYWxTcGFjZTogY29sUHJvcG9ydGlvbmFsU3BhY2UsCiAgICAgICAgICAgICAgICByb3dQcm9wb3J0aW9uYWxTcGFjZTogcm93UHJvcG9ydGlvbmFsU3BhY2UsCiAgICAgICAgICAgICAgICBndWFyYW50ZWVkV2lkdGhzOiBndWFyYW50ZWVzLmd1YXJhbnRlZWRXaWR0aHMsCiAgICAgICAgICAgICAgICBndWFyYW50ZWVkSGVpZ2h0czogZ3VhcmFudGVlcy5ndWFyYW50ZWVkSGVpZ2h0cywKICAgICAgICAgICAgICAgIHdhbnRzV2lkdGg6IHdhbnRzV2lkdGgsCiAgICAgICAgICAgICAgICB3YW50c0hlaWdodDogd2FudHNIZWlnaHQsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBUYWJsZS5wcm90b3R5cGUuX2RldGVybWluZUd1YXJhbnRlZXMgPSBmdW5jdGlvbiAob2ZmZXJlZFdpZHRocywgb2ZmZXJlZEhlaWdodHMsIGlzRmluYWxPZmZlcikgewogICAgICAgICAgICBpZiAoaXNGaW5hbE9mZmVyID09PSB2b2lkIDApIHsgaXNGaW5hbE9mZmVyID0gZmFsc2U7IH0KICAgICAgICAgICAgdmFyIHJlcXVlc3RlZFdpZHRocyA9IHV0aWxzJDEuQXJyYXkuY3JlYXRlRmlsbGVkQXJyYXkoMCwgdGhpcy5fbkNvbHMpOwogICAgICAgICAgICB2YXIgcmVxdWVzdGVkSGVpZ2h0cyA9IHV0aWxzJDEuQXJyYXkuY3JlYXRlRmlsbGVkQXJyYXkoMCwgdGhpcy5fblJvd3MpOwogICAgICAgICAgICB2YXIgY29sdW1uTmVlZHNXaWR0aCA9IHV0aWxzJDEuQXJyYXkuY3JlYXRlRmlsbGVkQXJyYXkoZmFsc2UsIHRoaXMuX25Db2xzKTsKICAgICAgICAgICAgdmFyIHJvd05lZWRzSGVpZ2h0ID0gdXRpbHMkMS5BcnJheS5jcmVhdGVGaWxsZWRBcnJheShmYWxzZSwgdGhpcy5fblJvd3MpOwogICAgICAgICAgICB0aGlzLl9yb3dzLmZvckVhY2goZnVuY3Rpb24gKHJvdywgcm93SW5kZXgpIHsKICAgICAgICAgICAgICAgIHJvdy5mb3JFYWNoKGZ1bmN0aW9uIChjb21wb25lbnQsIGNvbEluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIHNwYWNlUmVxdWVzdDsKICAgICAgICAgICAgICAgICAgICBpZiAoY29tcG9uZW50ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgc3BhY2VSZXF1ZXN0ID0gY29tcG9uZW50LnJlcXVlc3RlZFNwYWNlKG9mZmVyZWRXaWR0aHNbY29sSW5kZXhdLCBvZmZlcmVkSGVpZ2h0c1tyb3dJbmRleF0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgc3BhY2VSZXF1ZXN0ID0gewogICAgICAgICAgICAgICAgICAgICAgICAgICAgbWluV2lkdGg6IDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtaW5IZWlnaHQ6IDAsCiAgICAgICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIHZhciBjb2x1bW5XaWR0aCA9IGlzRmluYWxPZmZlciA/IE1hdGgubWluKHNwYWNlUmVxdWVzdC5taW5XaWR0aCwgb2ZmZXJlZFdpZHRoc1tjb2xJbmRleF0pIDogc3BhY2VSZXF1ZXN0Lm1pbldpZHRoOwogICAgICAgICAgICAgICAgICAgIHJlcXVlc3RlZFdpZHRoc1tjb2xJbmRleF0gPSBNYXRoLm1heChyZXF1ZXN0ZWRXaWR0aHNbY29sSW5kZXhdLCBjb2x1bW5XaWR0aCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIHJvd0hlaWdodCA9IGlzRmluYWxPZmZlciA/IE1hdGgubWluKHNwYWNlUmVxdWVzdC5taW5IZWlnaHQsIG9mZmVyZWRIZWlnaHRzW3Jvd0luZGV4XSkgOiBzcGFjZVJlcXVlc3QubWluSGVpZ2h0OwogICAgICAgICAgICAgICAgICAgIHJlcXVlc3RlZEhlaWdodHNbcm93SW5kZXhdID0gTWF0aC5tYXgocmVxdWVzdGVkSGVpZ2h0c1tyb3dJbmRleF0sIHJvd0hlaWdodCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGNvbXBvbmVudE5lZWRzV2lkdGggPSBzcGFjZVJlcXVlc3QubWluV2lkdGggPiBvZmZlcmVkV2lkdGhzW2NvbEluZGV4XTsKICAgICAgICAgICAgICAgICAgICBjb2x1bW5OZWVkc1dpZHRoW2NvbEluZGV4XSA9IGNvbHVtbk5lZWRzV2lkdGhbY29sSW5kZXhdIHx8IGNvbXBvbmVudE5lZWRzV2lkdGg7CiAgICAgICAgICAgICAgICAgICAgdmFyIGNvbXBvbmVudE5lZWRzSGVpZ2h0ID0gc3BhY2VSZXF1ZXN0Lm1pbkhlaWdodCA+IG9mZmVyZWRIZWlnaHRzW3Jvd0luZGV4XTsKICAgICAgICAgICAgICAgICAgICByb3dOZWVkc0hlaWdodFtyb3dJbmRleF0gPSByb3dOZWVkc0hlaWdodFtyb3dJbmRleF0gfHwgY29tcG9uZW50TmVlZHNIZWlnaHQ7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBndWFyYW50ZWVkV2lkdGhzOiByZXF1ZXN0ZWRXaWR0aHMsCiAgICAgICAgICAgICAgICBndWFyYW50ZWVkSGVpZ2h0czogcmVxdWVzdGVkSGVpZ2h0cywKICAgICAgICAgICAgICAgIHdhbnRzV2lkdGhBcnI6IGNvbHVtbk5lZWRzV2lkdGgsCiAgICAgICAgICAgICAgICB3YW50c0hlaWdodEFycjogcm93TmVlZHNIZWlnaHQsCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBUYWJsZS5wcm90b3R5cGUucmVxdWVzdGVkU3BhY2UgPSBmdW5jdGlvbiAob2ZmZXJlZFdpZHRoLCBvZmZlcmVkSGVpZ2h0KSB7CiAgICAgICAgICAgIHRoaXMuX2NhbGN1bGF0ZWRMYXlvdXQgPSB0aGlzLl9pdGVyYXRlTGF5b3V0KG9mZmVyZWRXaWR0aCwgb2ZmZXJlZEhlaWdodCk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBtaW5XaWR0aDogZDMuc3VtKHRoaXMuX2NhbGN1bGF0ZWRMYXlvdXQuZ3VhcmFudGVlZFdpZHRocyksCiAgICAgICAgICAgICAgICBtaW5IZWlnaHQ6IGQzLnN1bSh0aGlzLl9jYWxjdWxhdGVkTGF5b3V0Lmd1YXJhbnRlZWRIZWlnaHRzKSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIFRhYmxlLnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICB2YXIgbGFzdExheW91dFdpZHRoID0gZDMuc3VtKHRoaXMuX2NhbGN1bGF0ZWRMYXlvdXQuZ3VhcmFudGVlZFdpZHRocyk7CiAgICAgICAgICAgIHZhciBsYXN0TGF5b3V0SGVpZ2h0ID0gZDMuc3VtKHRoaXMuX2NhbGN1bGF0ZWRMYXlvdXQuZ3VhcmFudGVlZEhlaWdodHMpOwogICAgICAgICAgICB2YXIgbGF5b3V0ID0gdGhpcy5fY2FsY3VsYXRlZExheW91dDsKICAgICAgICAgICAgaWYgKGxhc3RMYXlvdXRXaWR0aCA+IHRoaXMud2lkdGgoKSB8fCBsYXN0TGF5b3V0SGVpZ2h0ID4gdGhpcy5oZWlnaHQoKSkgewogICAgICAgICAgICAgICAgbGF5b3V0ID0gdGhpcy5faXRlcmF0ZUxheW91dCh0aGlzLndpZHRoKCksIHRoaXMuaGVpZ2h0KCksIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBjaGlsZFlPcmlnaW4gPSAwOwogICAgICAgICAgICB2YXIgcm93SGVpZ2h0cyA9IHV0aWxzJDEuQXJyYXkuYWRkKGxheW91dC5yb3dQcm9wb3J0aW9uYWxTcGFjZSwgbGF5b3V0Lmd1YXJhbnRlZWRIZWlnaHRzKTsKICAgICAgICAgICAgdmFyIGNvbFdpZHRocyA9IHV0aWxzJDEuQXJyYXkuYWRkKGxheW91dC5jb2xQcm9wb3J0aW9uYWxTcGFjZSwgbGF5b3V0Lmd1YXJhbnRlZWRXaWR0aHMpOwogICAgICAgICAgICB0aGlzLl9yb3dzLmZvckVhY2goZnVuY3Rpb24gKHJvdywgcm93SW5kZXgpIHsKICAgICAgICAgICAgICAgIHZhciBjaGlsZFhPcmlnaW4gPSAwOwogICAgICAgICAgICAgICAgcm93LmZvckVhY2goZnVuY3Rpb24gKGNvbXBvbmVudCwgY29sSW5kZXgpIHsKICAgICAgICAgICAgICAgICAgICAvLyByZWN1cnNpdmVseSBjb21wdXRlIGxheW91dAogICAgICAgICAgICAgICAgICAgIGlmIChjb21wb25lbnQgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgICAgICBjb21wb25lbnQuY29tcHV0ZUxheW91dCh7IHg6IGNoaWxkWE9yaWdpbiwgeTogY2hpbGRZT3JpZ2luIH0sIGNvbFdpZHRoc1tjb2xJbmRleF0sIHJvd0hlaWdodHNbcm93SW5kZXhdKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgY2hpbGRYT3JpZ2luICs9IGNvbFdpZHRoc1tjb2xJbmRleF0gKyBfdGhpcy5fY29sdW1uUGFkZGluZzsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgY2hpbGRZT3JpZ2luICs9IHJvd0hlaWdodHNbcm93SW5kZXhdICsgX3RoaXMuX3Jvd1BhZGRpbmc7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFRhYmxlLnByb3RvdHlwZS5yb3dQYWRkaW5nID0gZnVuY3Rpb24gKHJvd1BhZGRpbmcpIHsKICAgICAgICAgICAgaWYgKHJvd1BhZGRpbmcgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Jvd1BhZGRpbmc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCF1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihyb3dQYWRkaW5nKSB8fCByb3dQYWRkaW5nIDwgMCkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoInJvd1BhZGRpbmcgbXVzdCBiZSBhIG5vbi1uZWdhdGl2ZSBmaW5pdGUgdmFsdWUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9yb3dQYWRkaW5nID0gcm93UGFkZGluZzsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBUYWJsZS5wcm90b3R5cGUuY29sdW1uUGFkZGluZyA9IGZ1bmN0aW9uIChjb2x1bW5QYWRkaW5nKSB7CiAgICAgICAgICAgIGlmIChjb2x1bW5QYWRkaW5nID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb2x1bW5QYWRkaW5nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIoY29sdW1uUGFkZGluZykgfHwgY29sdW1uUGFkZGluZyA8IDApIHsKICAgICAgICAgICAgICAgIHRocm93IEVycm9yKCJjb2x1bW5QYWRkaW5nIG11c3QgYmUgYSBub24tbmVnYXRpdmUgZmluaXRlIHZhbHVlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fY29sdW1uUGFkZGluZyA9IGNvbHVtblBhZGRpbmc7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgVGFibGUucHJvdG90eXBlLnJvd1dlaWdodCA9IGZ1bmN0aW9uIChpbmRleCwgd2VpZ2h0KSB7CiAgICAgICAgICAgIGlmICh3ZWlnaHQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Jvd1dlaWdodHNbaW5kZXhdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIod2VpZ2h0KSB8fCB3ZWlnaHQgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBFcnJvcigicm93V2VpZ2h0IG11c3QgYmUgYSBub24tbmVnYXRpdmUgZmluaXRlIHZhbHVlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fcm93V2VpZ2h0c1tpbmRleF0gPSB3ZWlnaHQ7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgVGFibGUucHJvdG90eXBlLmNvbHVtbldlaWdodCA9IGZ1bmN0aW9uIChpbmRleCwgd2VpZ2h0KSB7CiAgICAgICAgICAgIGlmICh3ZWlnaHQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbHVtbldlaWdodHNbaW5kZXhdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIod2VpZ2h0KSB8fCB3ZWlnaHQgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBFcnJvcigiY29sdW1uV2VpZ2h0IG11c3QgYmUgYSBub24tbmVnYXRpdmUgZmluaXRlIHZhbHVlIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fY29sdW1uV2VpZ2h0c1tpbmRleF0gPSB3ZWlnaHQ7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgVGFibGUucHJvdG90eXBlLmZpeGVkV2lkdGggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBjb2xzID0gZDMudHJhbnNwb3NlKHRoaXMuX3Jvd3MpOwogICAgICAgICAgICByZXR1cm4gVGFibGUuX2ZpeGVkU3BhY2UoY29scywgZnVuY3Rpb24gKGMpIHsgcmV0dXJuIChjID09IG51bGwpIHx8IGMuZml4ZWRXaWR0aCgpOyB9KTsKICAgICAgICB9OwogICAgICAgIFRhYmxlLnByb3RvdHlwZS5maXhlZEhlaWdodCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIFRhYmxlLl9maXhlZFNwYWNlKHRoaXMuX3Jvd3MsIGZ1bmN0aW9uIChjKSB7IHJldHVybiAoYyA9PSBudWxsKSB8fCBjLmZpeGVkSGVpZ2h0KCk7IH0pOwogICAgICAgIH07CiAgICAgICAgVGFibGUucHJvdG90eXBlLl9wYWRUYWJsZVRvU2l6ZSA9IGZ1bmN0aW9uIChuUm93cywgbkNvbHMpIHsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBuUm93czsgaSsrKSB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fcm93c1tpXSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fcm93c1tpXSA9IFtdOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX3Jvd1dlaWdodHNbaV0gPSBudWxsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZm9yICh2YXIgaiA9IDA7IGogPCBuQ29sczsgaisrKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHRoaXMuX3Jvd3NbaV1bal0gPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9yb3dzW2ldW2pdID0gbnVsbDsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZm9yICh2YXIgaiA9IDA7IGogPCBuQ29sczsgaisrKSB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fY29sdW1uV2VpZ2h0c1tqXSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fY29sdW1uV2VpZ2h0c1tqXSA9IG51bGw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFRhYmxlLl9jYWxjQ29tcG9uZW50V2VpZ2h0cyA9IGZ1bmN0aW9uIChzZXRXZWlnaHRzLCBjb21wb25lbnRHcm91cHMsIGZpeGl0eUFjY2Vzc29yKSB7CiAgICAgICAgICAgIC8vIElmIHRoZSByb3cvY29sIHdlaWdodCB3YXMgZXhwbGljaXRseSBzZXQsIHRoZW4gcmV0dXJuIGl0IG91dHJpZ2h0CiAgICAgICAgICAgIC8vIElmIHRoZSB3ZWlnaHQgd2FzIG5vdCBleHBsaWNpdGx5IHNldCwgdGhlbiBndWVzcyBpdCB1c2luZyB0aGUgaGV1cmlzdGljIHRoYXQgaWYgYWxsIGNvbXBvbmVudHMgYXJlIGZpeGVkLXNwYWNlCiAgICAgICAgICAgIC8vIHRoZW4gd2VpZ2h0IGlzIDAsIG90aGVyd2lzZSB3ZWlnaHQgaXMgMQogICAgICAgICAgICByZXR1cm4gc2V0V2VpZ2h0cy5tYXAoZnVuY3Rpb24gKHcsIGkpIHsKICAgICAgICAgICAgICAgIGlmICh3ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBmaXhpdGllcyA9IGNvbXBvbmVudEdyb3Vwc1tpXS5tYXAoZml4aXR5QWNjZXNzb3IpOwogICAgICAgICAgICAgICAgdmFyIGFsbEZpeGVkID0gZml4aXRpZXMucmVkdWNlKGZ1bmN0aW9uIChhLCBiKSB7IHJldHVybiBhICYmIGI7IH0sIHRydWUpOwogICAgICAgICAgICAgICAgcmV0dXJuIGFsbEZpeGVkID8gMCA6IDE7CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgVGFibGUuX2NhbGNQcm9wb3J0aW9uYWxTcGFjZSA9IGZ1bmN0aW9uICh3ZWlnaHRzLCBmcmVlU3BhY2UpIHsKICAgICAgICAgICAgdmFyIHdlaWdodFN1bSA9IGQzLnN1bSh3ZWlnaHRzKTsKICAgICAgICAgICAgaWYgKHdlaWdodFN1bSA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuQXJyYXkuY3JlYXRlRmlsbGVkQXJyYXkoMCwgd2VpZ2h0cy5sZW5ndGgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIHdlaWdodHMubWFwKGZ1bmN0aW9uICh3KSB7IHJldHVybiBmcmVlU3BhY2UgKiB3IC8gd2VpZ2h0U3VtOyB9KTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgVGFibGUuX2ZpeGVkU3BhY2UgPSBmdW5jdGlvbiAoY29tcG9uZW50R3JvdXAsIGZpeGl0eUFjY2Vzc29yKSB7CiAgICAgICAgICAgIHZhciBhbGwgPSBmdW5jdGlvbiAoYm9vbHMpIHsgcmV0dXJuIGJvb2xzLnJlZHVjZShmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gYSAmJiBiOyB9LCB0cnVlKTsgfTsKICAgICAgICAgICAgdmFyIGdyb3VwSXNGaXhlZCA9IGZ1bmN0aW9uIChjb21wb25lbnRzKSB7IHJldHVybiBhbGwoY29tcG9uZW50cy5tYXAoZml4aXR5QWNjZXNzb3IpKTsgfTsKICAgICAgICAgICAgcmV0dXJuIGFsbChjb21wb25lbnRHcm91cC5tYXAoZ3JvdXBJc0ZpeGVkKSk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gVGFibGU7CiAgICB9KGNvbXBvbmVudENvbnRhaW5lci5Db21wb25lbnRDb250YWluZXIpKTsKICAgIGV4cG9ydHMuVGFibGUgPSBUYWJsZTsKICAgIH0pOwoKICAgIHZhciB3cmFwcGVkTGFiZWwgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgdmFyIERFRkFVTFRfTUFYX0xJTkVTID0gMjsKICAgIHZhciBXcmFwcGVkTGFiZWwgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhXcmFwcGVkTGFiZWwsIF9zdXBlcik7CiAgICAgICAgZnVuY3Rpb24gV3JhcHBlZExhYmVsKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIgIT09IG51bGwgJiYgX3N1cGVyLmFwcGx5KHRoaXMsIGFyZ3VtZW50cykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX21heExpbmVzID0gREVGQVVMVF9NQVhfTElORVM7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgV3JhcHBlZExhYmVsLnByb3RvdHlwZS5yZXF1ZXN0ZWRTcGFjZSA9IGZ1bmN0aW9uIChvZmZlcmVkV2lkdGgsIG9mZmVyZWRIZWlnaHQpIHsKICAgICAgICAgICAgdGhpcy5fd3JhcHBlci5tYXhMaW5lcyh0aGlzLl9tYXhMaW5lcyk7CiAgICAgICAgICAgIHZhciBvZmZlcmVkTGluZUxlbmd0aCA9IHRoaXMuYW5nbGUoKSA9PT0gMCA/IG9mZmVyZWRXaWR0aCA6IG9mZmVyZWRIZWlnaHQ7CiAgICAgICAgICAgIGlmIChvZmZlcmVkTGluZUxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgb2ZmZXJlZExpbmVMZW5ndGggPSBJbmZpbml0eTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgd3JhcHBlZCA9IHRoaXMuX3dyYXBwZXIud3JhcCh0aGlzLl90ZXh0LCB0aGlzLl9tZWFzdXJlciwgb2ZmZXJlZExpbmVMZW5ndGgpOwogICAgICAgICAgICB2YXIgbWVhc3VyZWRXcmFwID0gdGhpcy5fbWVhc3VyZXIubWVhc3VyZSh3cmFwcGVkLndyYXBwZWRUZXh0KTsKICAgICAgICAgICAgdmFyIG1pbldpZHRoID0gKHRoaXMuYW5nbGUoKSA9PT0gMCA/IG1lYXN1cmVkV3JhcC53aWR0aCA6IG1lYXN1cmVkV3JhcC5oZWlnaHQpICsgMiAqIHRoaXMucGFkZGluZygpOwogICAgICAgICAgICB2YXIgbWluSGVpZ2h0ID0gKHRoaXMuYW5nbGUoKSA9PT0gMCA/IG1lYXN1cmVkV3JhcC5oZWlnaHQgOiBtZWFzdXJlZFdyYXAud2lkdGgpICsgMiAqIHRoaXMucGFkZGluZygpOwogICAgICAgICAgICByZXR1cm4geyBtaW5XaWR0aDogbWluV2lkdGgsIG1pbkhlaWdodDogbWluSGVpZ2h0IH07CiAgICAgICAgfTsKICAgICAgICBXcmFwcGVkTGFiZWwucHJvdG90eXBlLm1heExpbmVzID0gZnVuY3Rpb24gKG1heExpbmVzKSB7CiAgICAgICAgICAgIC8vIGFsbG93IHVzZXIgdG8gdW4tc2V0IGJ5IHBhc3NpbmcgaW4gbnVsbCBvciB1bmRlZmluZWQgZXhwbGljaXRseQogICAgICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21heExpbmVzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX21heExpbmVzID0gbWF4TGluZXM7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFdyYXBwZWRMYWJlbDsKICAgIH0obGFiZWwuTGFiZWwpKTsKICAgIGV4cG9ydHMuV3JhcHBlZExhYmVsID0gV3JhcHBlZExhYmVsOwogICAgfSk7CgogICAgdmFyIHhEcmFnQm94TGF5ZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgdmFyIFhEcmFnQm94TGF5ZXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhYRHJhZ0JveExheWVyLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEFuIFhEcmFnQm94TGF5ZXIgaXMgYSBEcmFnQm94TGF5ZXIgd2hvc2Ugc2l6ZSBjYW4gb25seSBiZSBzZXQgaW4gdGhlIFgtZGlyZWN0aW9uLgogICAgICAgICAqIFRoZSB5LXZhbHVlcyBvZiB0aGUgYm91bmRzKCkgYXJlIGFsd2F5cyBzZXQgdG8gMCBhbmQgdGhlIGhlaWdodCgpIG9mIHRoZSBYRHJhZ0JveExheWVyLgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gWERyYWdCb3hMYXllcigpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoIngtZHJhZy1ib3gtbGF5ZXIiKTsKICAgICAgICAgICAgX3RoaXMuX2hhc0Nvcm5lcnMgPSBmYWxzZTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBYRHJhZ0JveExheWVyLnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICAvLyBzZXQgY29ycmVjdCBib3VuZHMgd2hlbiB3aWR0aC9oZWlnaHQgY2hhbmdlcwogICAgICAgICAgICB0aGlzLl9zZXRCb3VuZHModGhpcy5ib3VuZHMoKSk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgWERyYWdCb3hMYXllci5wcm90b3R5cGUuX3NldEJvdW5kcyA9IGZ1bmN0aW9uIChuZXdCb3VuZHMpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fc2V0Qm91bmRzLmNhbGwodGhpcywgewogICAgICAgICAgICAgICAgdG9wTGVmdDogeyB4OiBuZXdCb3VuZHMudG9wTGVmdC54LCB5OiAwIH0sCiAgICAgICAgICAgICAgICBib3R0b21SaWdodDogeyB4OiBuZXdCb3VuZHMuYm90dG9tUmlnaHQueCwgeTogdGhpcy5oZWlnaHQoKSB9LAogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIFhEcmFnQm94TGF5ZXIucHJvdG90eXBlLl9zZXRSZXNpemFibGVDbGFzc2VzID0gZnVuY3Rpb24gKGNhblJlc2l6ZSkgewogICAgICAgICAgICBpZiAoY2FuUmVzaXplICYmIHRoaXMuZW5hYmxlZCgpKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFkZENsYXNzKCJ4LXJlc2l6YWJsZSIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5yZW1vdmVDbGFzcygieC1yZXNpemFibGUiKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgWERyYWdCb3hMYXllci5wcm90b3R5cGUueVNjYWxlID0gZnVuY3Rpb24gKHlTY2FsZSkgewogICAgICAgICAgICBpZiAoeVNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnlTY2FsZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigieVNjYWxlcyBjYW5ub3QgYmUgc2V0IG9uIGFuIFhEcmFnQm94TGF5ZXIiKTsKICAgICAgICB9OwogICAgICAgIFhEcmFnQm94TGF5ZXIucHJvdG90eXBlLnlFeHRlbnQgPSBmdW5jdGlvbiAoeUV4dGVudCkgewogICAgICAgICAgICBpZiAoeUV4dGVudCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS55RXh0ZW50LmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJYRHJhZ0JveExheWVyIGhhcyBubyB5RXh0ZW50Iik7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gWERyYWdCb3hMYXllcjsKICAgIH0oZHJhZ0JveExheWVyLkRyYWdCb3hMYXllcikpOwogICAgZXhwb3J0cy5YRHJhZ0JveExheWVyID0gWERyYWdCb3hMYXllcjsKICAgIH0pOwoKICAgIHZhciB5RHJhZ0JveExheWVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKICAgIHZhciBZRHJhZ0JveExheWVyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoWURyYWdCb3hMYXllciwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBIFlEcmFnQm94TGF5ZXIgaXMgYSBEcmFnQm94TGF5ZXIgd2hvc2Ugc2l6ZSBjYW4gb25seSBiZSBzZXQgaW4gdGhlIFktZGlyZWN0aW9uLgogICAgICAgICAqIFRoZSB4LXZhbHVlcyBvZiB0aGUgYm91bmRzKCkgYXJlIGFsd2F5cyBzZXQgdG8gMCBhbmQgdGhlIHdpZHRoKCkgb2YgdGhlIFlEcmFnQm94TGF5ZXIuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBZRHJhZ0JveExheWVyKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygieS1kcmFnLWJveC1sYXllciIpOwogICAgICAgICAgICBfdGhpcy5faGFzQ29ybmVycyA9IGZhbHNlOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFlEcmFnQm94TGF5ZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQgPSBmdW5jdGlvbiAob3JpZ2luLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuY29tcHV0ZUxheW91dC5jYWxsKHRoaXMsIG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCk7CiAgICAgICAgICAgIC8vIHNldCBjb3JyZWN0IGJvdW5kcyB3aGVuIHdpZHRoL2hlaWdodCBjaGFuZ2VzCiAgICAgICAgICAgIHRoaXMuX3NldEJvdW5kcyh0aGlzLmJvdW5kcygpKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBZRHJhZ0JveExheWVyLnByb3RvdHlwZS5fc2V0Qm91bmRzID0gZnVuY3Rpb24gKG5ld0JvdW5kcykgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXRCb3VuZHMuY2FsbCh0aGlzLCB7CiAgICAgICAgICAgICAgICB0b3BMZWZ0OiB7IHg6IDAsIHk6IG5ld0JvdW5kcy50b3BMZWZ0LnkgfSwKICAgICAgICAgICAgICAgIGJvdHRvbVJpZ2h0OiB7IHg6IHRoaXMud2lkdGgoKSwgeTogbmV3Qm91bmRzLmJvdHRvbVJpZ2h0LnkgfSwKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBZRHJhZ0JveExheWVyLnByb3RvdHlwZS5fc2V0UmVzaXphYmxlQ2xhc3NlcyA9IGZ1bmN0aW9uIChjYW5SZXNpemUpIHsKICAgICAgICAgICAgaWYgKGNhblJlc2l6ZSAmJiB0aGlzLmVuYWJsZWQoKSkgewogICAgICAgICAgICAgICAgdGhpcy5hZGRDbGFzcygieS1yZXNpemFibGUiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMucmVtb3ZlQ2xhc3MoInktcmVzaXphYmxlIik7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFlEcmFnQm94TGF5ZXIucHJvdG90eXBlLnhTY2FsZSA9IGZ1bmN0aW9uICh4U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHhTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS54U2NhbGUuY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoInhTY2FsZXMgY2Fubm90IGJlIHNldCBvbiBhbiBZRHJhZ0JveExheWVyIik7CiAgICAgICAgfTsKICAgICAgICBZRHJhZ0JveExheWVyLnByb3RvdHlwZS54RXh0ZW50ID0gZnVuY3Rpb24gKHhFeHRlbnQpIHsKICAgICAgICAgICAgaWYgKHhFeHRlbnQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUueEV4dGVudC5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiWURyYWdCb3hMYXllciBoYXMgbm8geEV4dGVudCIpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIFlEcmFnQm94TGF5ZXI7CiAgICB9KGRyYWdCb3hMYXllci5EcmFnQm94TGF5ZXIpKTsKICAgIGV4cG9ydHMuWURyYWdCb3hMYXllciA9IFlEcmFnQm94TGF5ZXI7CiAgICB9KTsKCiAgICB2YXIgY29tcG9uZW50cyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZHJhZ0JveExheWVyLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZHJhZ0xpbmVMYXllciwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGdyaWRsaW5lcywgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGdyb3VwLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZ3VpZGVMaW5lTGF5ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihpbnRlcnBvbGF0ZWRDb2xvckxlZ2VuZCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGxhYmVsLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIobGVnZW5kLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIocGxvdEdyb3VwLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoc2VsZWN0aW9uQm94TGF5ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3Rhcih0YWJsZSwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHdyYXBwZWRMYWJlbCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHhEcmFnQm94TGF5ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3Rhcih5RHJhZ0JveExheWVyLCBleHBvcnRzKTsKICAgIH0pOwoKICAgIHZhciBhcmNEcmF3ZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgdmFyIEFyY1NWR0RyYXdlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKEFyY1NWR0RyYXdlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBBcmNTVkdEcmF3ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIuY2FsbCh0aGlzLCAicGF0aCIsICJhcmMgZmlsbCIpIHx8IHRoaXM7CiAgICAgICAgfQogICAgICAgIEFyY1NWR0RyYXdlci5wcm90b3R5cGUuX2FwcGx5RGVmYXVsdEF0dHJpYnV0ZXMgPSBmdW5jdGlvbiAoc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbi5zdHlsZSgic3Ryb2tlIiwgIm5vbmUiKTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBBcmNTVkdEcmF3ZXI7CiAgICB9KHN2Z0RyYXdlci5TVkdEcmF3ZXIpKTsKICAgIGV4cG9ydHMuQXJjU1ZHRHJhd2VyID0gQXJjU1ZHRHJhd2VyOwogICAgfSk7CgogICAgdmFyIGFyY091dGxpbmVEcmF3ZXIgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgogICAgdmFyIEFyY091dGxpbmVTVkdEcmF3ZXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhBcmNPdXRsaW5lU1ZHRHJhd2VyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIEFyY091dGxpbmVTVkdEcmF3ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIuY2FsbCh0aGlzLCAicGF0aCIsICJhcmMgb3V0bGluZSIpIHx8IHRoaXM7CiAgICAgICAgfQogICAgICAgIEFyY091dGxpbmVTVkdEcmF3ZXIucHJvdG90eXBlLl9hcHBseURlZmF1bHRBdHRyaWJ1dGVzID0gZnVuY3Rpb24gKHNlbGVjdGlvbikgewogICAgICAgICAgICBzZWxlY3Rpb24uc3R5bGUoImZpbGwiLCAibm9uZSIpOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEFyY091dGxpbmVTVkdEcmF3ZXI7CiAgICB9KHN2Z0RyYXdlci5TVkdEcmF3ZXIpKTsKICAgIGV4cG9ydHMuQXJjT3V0bGluZVNWR0RyYXdlciA9IEFyY091dGxpbmVTVkdEcmF3ZXI7CiAgICB9KTsKCiAgICB2YXIgYXJlYURyYXdlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgogICAgdmFyIEFyZWFTVkdEcmF3ZXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhBcmVhU1ZHRHJhd2VyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIEFyZWFTVkdEcmF3ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIuY2FsbCh0aGlzLCAicGF0aCIsICJhcmVhIikgfHwgdGhpczsKICAgICAgICB9CiAgICAgICAgQXJlYVNWR0RyYXdlci5wcm90b3R5cGUuX2FwcGx5RGVmYXVsdEF0dHJpYnV0ZXMgPSBmdW5jdGlvbiAoc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbi5zdHlsZSgic3Ryb2tlIiwgIm5vbmUiKTsKICAgICAgICB9OwogICAgICAgIEFyZWFTVkdEcmF3ZXIucHJvdG90eXBlLmdldFZpc3VhbFByaW1pdGl2ZUF0SW5kZXggPSBmdW5jdGlvbiAoaW5kZXgpIHsKICAgICAgICAgICAgLy8gYXJlYXMgYXJlIHJlcHJlc2VudGVkIGJ5IG9uZSBzaW5nbGUgZWxlbWVudDsgYWx3YXlzIGdldCB0aGF0IGVsZW1lbnQKICAgICAgICAgICAgLy8gcmVnYXJkbGVzcyBvZiB0aGUgZGF0YSBpbmRleC4KICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuZ2V0VmlzdWFsUHJpbWl0aXZlQXRJbmRleC5jYWxsKHRoaXMsIDApOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIEFyZWFTVkdEcmF3ZXI7CiAgICB9KHN2Z0RyYXdlci5TVkdEcmF3ZXIpKTsKICAgIGV4cG9ydHMuQXJlYVNWR0RyYXdlciA9IEFyZWFTVkdEcmF3ZXI7CiAgICB2YXIgQVJFQV9GSUxMX0FUVFJTID0gWyJvcGFjaXR5IiwgImZpbGwiLCAiZmlsbC1vcGFjaXR5Il07CiAgICB2YXIgQVJFQV9TVFJPS0VfQVRUUlMgPSBbIm9wYWNpdHkiLCAic3Ryb2tlIiwgInN0cm9rZS13aWR0aCJdOwogICAgZnVuY3Rpb24gbWFrZUFyZWFDYW52YXNEcmF3U3RlcChkM0FyZWFGYWN0b3J5LCBkM0xpbmVGYWN0b3J5KSB7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChjb250ZXh0LCBkYXRhLCBwcm9qZWN0b3IpIHsKICAgICAgICAgICAgdmFyIGZpbGxBdHRycyA9IGNhbnZhc0RyYXdlci5yZXNvbHZlQXR0cmlidXRlcyhwcm9qZWN0b3IsIEFSRUFfRklMTF9BVFRSUywgZGF0YVswXSwgMCk7CiAgICAgICAgICAgIGNhbnZhc0RyYXdlci5yZW5kZXJBcmVhKGNvbnRleHQsIGQzQXJlYUZhY3RvcnkoKSwgZGF0YVswXSwgZmlsbEF0dHJzKTsKICAgICAgICAgICAgdmFyIHN0cm9rZUF0dHJzID0gY2FudmFzRHJhd2VyLnJlc29sdmVBdHRyaWJ1dGVzKHByb2plY3RvciwgQVJFQV9TVFJPS0VfQVRUUlMsIGRhdGFbMF0sIDApOwogICAgICAgICAgICBjYW52YXNEcmF3ZXIucmVuZGVyTGluZShjb250ZXh0LCBkM0xpbmVGYWN0b3J5KCksIGRhdGFbMF0sIHN0cm9rZUF0dHJzKTsKICAgICAgICB9OwogICAgfQogICAgZXhwb3J0cy5tYWtlQXJlYUNhbnZhc0RyYXdTdGVwID0gbWFrZUFyZWFDYW52YXNEcmF3U3RlcDsKICAgIH0pOwoKICAgIHZhciBsaW5lRHJhd2VyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICB2YXIgTGluZVNWR0RyYXdlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKExpbmVTVkdEcmF3ZXIsIF9zdXBlcik7CiAgICAgICAgZnVuY3Rpb24gTGluZVNWR0RyYXdlcigpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5jYWxsKHRoaXMsICJwYXRoIiwgImxpbmUiKSB8fCB0aGlzOwogICAgICAgIH0KICAgICAgICBMaW5lU1ZHRHJhd2VyLnByb3RvdHlwZS5fYXBwbHlEZWZhdWx0QXR0cmlidXRlcyA9IGZ1bmN0aW9uIChzZWxlY3Rpb24pIHsKICAgICAgICAgICAgc2VsZWN0aW9uLnN0eWxlKCJmaWxsIiwgIm5vbmUiKTsKICAgICAgICB9OwogICAgICAgIExpbmVTVkdEcmF3ZXIucHJvdG90eXBlLmdldFZpc3VhbFByaW1pdGl2ZUF0SW5kZXggPSBmdW5jdGlvbiAoaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuZ2V0VmlzdWFsUHJpbWl0aXZlQXRJbmRleC5jYWxsKHRoaXMsIDApOwogICAgICAgIH07CiAgICAgICAgcmV0dXJuIExpbmVTVkdEcmF3ZXI7CiAgICB9KHN2Z0RyYXdlci5TVkdEcmF3ZXIpKTsKICAgIGV4cG9ydHMuTGluZVNWR0RyYXdlciA9IExpbmVTVkdEcmF3ZXI7CiAgICB2YXIgTElORV9BVFRSSUJVVEVTID0gWwogICAgICAgICJvcGFjaXR5IiwKICAgICAgICAic3Ryb2tlLW9wYWNpdHkiLAogICAgICAgICJzdHJva2Utd2lkdGgiLAogICAgICAgICJzdHJva2UiLAogICAgICAgICJzdHJva2UtZGFzaGFycmF5IiwKICAgIF07CiAgICAvKioKICAgICAqIEBwYXJhbSBkM0xpbmVGYWN0b3J5IEEgY2FsbGJhY2sgdGhhdCBnaXZlcyB0aGlzIExpbmUgRHJhd2VyIGEgZDMuTGluZSBvYmplY3Qgd2hpY2ggd2lsbCBiZQogICAgICogdXNlZCB0byBkcmF3IHdpdGguCiAgICAgKgogICAgICogVE9ETyBwdXQgdGhlIGQzLkxpbmUgaW50byB0aGUgYXR0clRvQXBwbGllZFByb2plY3RvciBkaXJlY3RseQogICAgICovCiAgICBmdW5jdGlvbiBtYWtlTGluZUNhbnZhc0RyYXdTdGVwKGQzTGluZUZhY3RvcnkpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGNvbnRleHQsIGRhdGEsIGF0dHJUb0FwcGxpZWRQcm9qZWN0b3IpIHsKICAgICAgICAgICAgdmFyIGxpbmVTdHlsZSA9IGNhbnZhc0RyYXdlci5yZXNvbHZlQXR0cmlidXRlcyhhdHRyVG9BcHBsaWVkUHJvamVjdG9yLCBMSU5FX0FUVFJJQlVURVMsIGRhdGFbMF0sIDApOwogICAgICAgICAgICBjYW52YXNEcmF3ZXIucmVuZGVyTGluZShjb250ZXh0LCBkM0xpbmVGYWN0b3J5KCksIGRhdGFbMF0sIGxpbmVTdHlsZSk7CiAgICAgICAgfTsKICAgIH0KICAgIGV4cG9ydHMubWFrZUxpbmVDYW52YXNEcmF3U3RlcCA9IG1ha2VMaW5lQ2FudmFzRHJhd1N0ZXA7CiAgICB9KTsKCiAgICB2YXIgcmVjdGFuZ2xlRHJhd2VyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCiAgICB2YXIgUmVjdGFuZ2xlU1ZHRHJhd2VyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUmVjdGFuZ2xlU1ZHRHJhd2VyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFJlY3RhbmdsZVNWR0RyYXdlcihfcm9vdENsYXNzTmFtZSkgewogICAgICAgICAgICBpZiAoX3Jvb3RDbGFzc05hbWUgPT09IHZvaWQgMCkgeyBfcm9vdENsYXNzTmFtZSA9ICIiOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMsICJyZWN0IiwgIiIpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9yb290Q2xhc3NOYW1lID0gX3Jvb3RDbGFzc05hbWU7CiAgICAgICAgICAgIF90aGlzLl9yb290LmNsYXNzZWQoX3RoaXMuX3Jvb3RDbGFzc05hbWUsIHRydWUpOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIHJldHVybiBSZWN0YW5nbGVTVkdEcmF3ZXI7CiAgICB9KHN2Z0RyYXdlci5TVkdEcmF3ZXIpKTsKICAgIGV4cG9ydHMuUmVjdGFuZ2xlU1ZHRHJhd2VyID0gUmVjdGFuZ2xlU1ZHRHJhd2VyOwogICAgdmFyIFJFQ1RfQVRUUlMgPSBjYW52YXNEcmF3ZXIuQ29udGV4dFN0eWxlQXR0cnMuY29uY2F0KFsieCIsICJ5IiwgIndpZHRoIiwgImhlaWdodCJdKTsKICAgIGV4cG9ydHMuUmVjdGFuZ2xlQ2FudmFzRHJhd1N0ZXAgPSBmdW5jdGlvbiAoY29udGV4dCwgZGF0YSwgcHJvamVjdG9yKSB7CiAgICAgICAgY29udGV4dC5zYXZlKCk7CiAgICAgICAgdmFyIGRhdGFMZW4gPSBkYXRhLmxlbmd0aDsKICAgICAgICBmb3IgKHZhciBpbmRleCA9IDA7IGluZGV4IDwgZGF0YUxlbjsgaW5kZXgrKykgewogICAgICAgICAgICB2YXIgZGF0dW0gPSBkYXRhW2luZGV4XTsKICAgICAgICAgICAgaWYgKGRhdHVtID09IG51bGwpIHsKICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBhdHRycyA9IGNhbnZhc0RyYXdlci5yZXNvbHZlQXR0cmlidXRlcyhwcm9qZWN0b3IsIFJFQ1RfQVRUUlMsIGRhdHVtLCBpbmRleCk7CiAgICAgICAgICAgIGNvbnRleHQuYmVnaW5QYXRoKCk7CiAgICAgICAgICAgIGNvbnRleHQucmVjdChhdHRyc1sieCJdLCBhdHRyc1sieSJdLCBhdHRyc1sid2lkdGgiXSwgYXR0cnNbImhlaWdodCJdKTsKICAgICAgICAgICAgY2FudmFzRHJhd2VyLnJlbmRlclBhdGhXaXRoU3R5bGUoY29udGV4dCwgYXR0cnMpOwogICAgICAgIH0KICAgICAgICBjb250ZXh0LnJlc3RvcmUoKTsKICAgIH07CiAgICB2YXIgUmVjdGFuZ2xlQ2FudmFzRHJhd2VyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoUmVjdGFuZ2xlQ2FudmFzRHJhd2VyLCBfc3VwZXIpOwogICAgICAgIGZ1bmN0aW9uIFJlY3RhbmdsZUNhbnZhc0RyYXdlcihjdHgpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5jYWxsKHRoaXMsIGN0eCwgZXhwb3J0cy5SZWN0YW5nbGVDYW52YXNEcmF3U3RlcCkgfHwgdGhpczsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIFJlY3RhbmdsZUNhbnZhc0RyYXdlcjsKICAgIH0oY2FudmFzRHJhd2VyLkNhbnZhc0RyYXdlcikpOwogICAgZXhwb3J0cy5SZWN0YW5nbGVDYW52YXNEcmF3ZXIgPSBSZWN0YW5nbGVDYW52YXNEcmF3ZXI7CiAgICB9KTsKCiAgICB2YXIgc2VnbWVudERyYXdlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCiAgICB2YXIgU2VnbWVudFNWR0RyYXdlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFNlZ21lbnRTVkdEcmF3ZXIsIF9zdXBlcik7CiAgICAgICAgZnVuY3Rpb24gU2VnbWVudFNWR0RyYXdlcigpIHsKICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5jYWxsKHRoaXMsICJsaW5lIiwgIiIpIHx8IHRoaXM7CiAgICAgICAgfQogICAgICAgIHJldHVybiBTZWdtZW50U1ZHRHJhd2VyOwogICAgfShzdmdEcmF3ZXIuU1ZHRHJhd2VyKSk7CiAgICBleHBvcnRzLlNlZ21lbnRTVkdEcmF3ZXIgPSBTZWdtZW50U1ZHRHJhd2VyOwogICAgfSk7CgogICAgdmFyIGNhbnZhc0J1ZmZlciA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTctcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgdmFyIENhbnZhc0J1ZmZlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uICgpIHsKICAgICAgICBmdW5jdGlvbiBDYW52YXNCdWZmZXIoc2NyZWVuV2lkdGgsIHNjcmVlbkhlaWdodCwgZGV2aWNlUGl4ZWxSYXRpbykgewogICAgICAgICAgICBpZiAoZGV2aWNlUGl4ZWxSYXRpbyA9PT0gdm9pZCAwKSB7IGRldmljZVBpeGVsUmF0aW8gPSB3aW5kb3cuZGV2aWNlUGl4ZWxSYXRpbzsgfQogICAgICAgICAgICB0aGlzLnNjcmVlbldpZHRoID0gc2NyZWVuV2lkdGg7CiAgICAgICAgICAgIHRoaXMuc2NyZWVuSGVpZ2h0ID0gc2NyZWVuSGVpZ2h0OwogICAgICAgICAgICB0aGlzLmRldmljZVBpeGVsUmF0aW8gPSBkZXZpY2VQaXhlbFJhdGlvOwogICAgICAgICAgICB0aGlzLnBpeGVsV2lkdGggPSBzY3JlZW5XaWR0aCAqIGRldmljZVBpeGVsUmF0aW87CiAgICAgICAgICAgIHRoaXMucGl4ZWxIZWlnaHQgPSBzY3JlZW5IZWlnaHQgKiBkZXZpY2VQaXhlbFJhdGlvOwogICAgICAgICAgICB0aGlzLmNhbnZhcyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoImNhbnZhcyIpOwogICAgICAgICAgICB0aGlzLmN0eCA9IHRoaXMuY2FudmFzLmdldENvbnRleHQoIjJkIik7CiAgICAgICAgICAgIENhbnZhc0J1ZmZlci5zaXplUGl4ZWxzKHRoaXMuY3R4LCBzY3JlZW5XaWR0aCwgc2NyZWVuSGVpZ2h0LCBkZXZpY2VQaXhlbFJhdGlvKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmVzaXplcyB0aGUgY2FudmFzJyBpbnRlcm5hbCBwaXhlbCBidWZmZXIgdG8gbWF0Y2ggdGhlIGRldmljZVBpeGVsUmF0aW8KICAgICAgICAgKi8KICAgICAgICBDYW52YXNCdWZmZXIuc2l6ZVBpeGVscyA9IGZ1bmN0aW9uIChjdHgsIHNjcmVlbldpZHRoLCBzY3JlZW5IZWlnaHQsIGRldmljZVBpeGVsUmF0aW8pIHsKICAgICAgICAgICAgdmFyIGNhbnZhcyA9IGN0eC5jYW52YXM7CiAgICAgICAgICAgIGNhbnZhcy53aWR0aCA9IHNjcmVlbldpZHRoICogZGV2aWNlUGl4ZWxSYXRpbzsKICAgICAgICAgICAgY2FudmFzLmhlaWdodCA9IHNjcmVlbkhlaWdodCAqIGRldmljZVBpeGVsUmF0aW87CiAgICAgICAgICAgIGNhbnZhcy5zdHlsZS53aWR0aCA9IHNjcmVlbldpZHRoICsgInB4IjsKICAgICAgICAgICAgY2FudmFzLnN0eWxlLmhlaWdodCA9IHNjcmVlbkhlaWdodCArICJweCI7CiAgICAgICAgICAgIGN0eC5zZXRUcmFuc2Zvcm0oMSwgMCwgMCwgMSwgMCwgMCk7CiAgICAgICAgICAgIGN0eC5zY2FsZShkZXZpY2VQaXhlbFJhdGlvLCBkZXZpY2VQaXhlbFJhdGlvKTsKICAgICAgICB9OwogICAgICAgIENhbnZhc0J1ZmZlci5wcm90b3R5cGUuYmxpdCA9IGZ1bmN0aW9uIChjdHgsIHgsIHkpIHsKICAgICAgICAgICAgaWYgKHggPT09IHZvaWQgMCkgeyB4ID0gMDsgfQogICAgICAgICAgICBpZiAoeSA9PT0gdm9pZCAwKSB7IHkgPSAwOyB9CiAgICAgICAgICAgIGN0eC5kcmF3SW1hZ2UodGhpcy5jYW52YXMsIHgsIHksIHRoaXMuc2NyZWVuV2lkdGgsIHRoaXMuc2NyZWVuSGVpZ2h0KTsKICAgICAgICB9OwogICAgICAgIENhbnZhc0J1ZmZlci5wcm90b3R5cGUuYmxpdENlbnRlciA9IGZ1bmN0aW9uIChjdHgsIHgsIHkpIHsKICAgICAgICAgICAgaWYgKHggPT09IHZvaWQgMCkgeyB4ID0gMDsgfQogICAgICAgICAgICBpZiAoeSA9PT0gdm9pZCAwKSB7IHkgPSAwOyB9CiAgICAgICAgICAgIHRoaXMuYmxpdChjdHgsIE1hdGguZmxvb3IoeCAtIHRoaXMuc2NyZWVuV2lkdGggLyAyKSwgTWF0aC5mbG9vcih5IC0gdGhpcy5zY3JlZW5IZWlnaHQgLyAyKSk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBDaGFuZ2VzIHRoZSBzaXplIG9mIHRoZSB1bmRlcmx5aW5nIGNhbnZhcyBpbiBzY3JlZW4gc3BhY2UsIHJlc3BlY3RpbmcgdGhlCiAgICAgICAgICogY3VycmVudCBkZXZpY2VQaXhlbFJhdGlvLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIGNlbnRlciAtIG9wdGlvbmFsbHkgZW5hYmxlIGEgdHJhbnNsYXRlIHRyYW5zZm9ybWF0aW9uIG1vdmluZyB0aGUKICAgICAgICAgKiAgICAgICAgICAgICAgICAgb3JpZ2luIHRvIHRoZSBjZW50ZXIgb2YgdGhlIGNhbnZhcy4KICAgICAgICAgKi8KICAgICAgICBDYW52YXNCdWZmZXIucHJvdG90eXBlLnJlc2l6ZSA9IGZ1bmN0aW9uIChzY3JlZW5XaWR0aCwgc2NyZWVuSGVpZ2h0LCBjZW50ZXIpIHsKICAgICAgICAgICAgaWYgKGNlbnRlciA9PT0gdm9pZCAwKSB7IGNlbnRlciA9IGZhbHNlOyB9CiAgICAgICAgICAgIHZhciBkZXZpY2VQaXhlbFJhdGlvID0gdGhpcy5kZXZpY2VQaXhlbFJhdGlvOwogICAgICAgICAgICB0aGlzLnNjcmVlbldpZHRoID0gc2NyZWVuV2lkdGg7CiAgICAgICAgICAgIHRoaXMuc2NyZWVuSGVpZ2h0ID0gc2NyZWVuSGVpZ2h0OwogICAgICAgICAgICB0aGlzLnBpeGVsV2lkdGggPSBzY3JlZW5XaWR0aCAqIGRldmljZVBpeGVsUmF0aW87CiAgICAgICAgICAgIHRoaXMucGl4ZWxIZWlnaHQgPSBzY3JlZW5IZWlnaHQgKiBkZXZpY2VQaXhlbFJhdGlvOwogICAgICAgICAgICBDYW52YXNCdWZmZXIuc2l6ZVBpeGVscyh0aGlzLmN0eCwgc2NyZWVuV2lkdGgsIHNjcmVlbkhlaWdodCwgZGV2aWNlUGl4ZWxSYXRpbyk7CiAgICAgICAgICAgIGlmIChjZW50ZXIpIHsKICAgICAgICAgICAgICAgIHRoaXMuY3R4LnRyYW5zbGF0ZShzY3JlZW5XaWR0aCAvIDIsIHNjcmVlbldpZHRoIC8gMik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUZW1wb3JhcmlseSByZXNldHMgdGhlIGN1cnJlbnQgY29udGV4dCB0cmFuc2Zvcm1hdGlvbiBhbmQgZmlsbHMgdGhlCiAgICAgICAgICogZW50aXJlIGNhbnZhcyB3aXRoIHRoZSBwcm92aWRlZCBjb2xvci4gSWYgbm8gY29sb3IgaXMgcHJvdmlkZWQsIHRoZQogICAgICAgICAqIGNhbnZhcyBpcyBjbGVhcmVkIGluc3RlYWQuCiAgICAgICAgICovCiAgICAgICAgQ2FudmFzQnVmZmVyLnByb3RvdHlwZS5jbGVhciA9IGZ1bmN0aW9uIChjb2xvcikgewogICAgICAgICAgICB2YXIgX2EgPSB0aGlzLCBwaXhlbFdpZHRoID0gX2EucGl4ZWxXaWR0aCwgcGl4ZWxIZWlnaHQgPSBfYS5waXhlbEhlaWdodCwgY3R4ID0gX2EuY3R4OwogICAgICAgICAgICBjdHguc2F2ZSgpOwogICAgICAgICAgICBjdHguc2V0VHJhbnNmb3JtKDEsIDAsIDAsIDEsIDAsIDApOwogICAgICAgICAgICBpZiAoY29sb3IgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgY3R4LmNsZWFyUmVjdCgwLCAwLCBwaXhlbFdpZHRoLCBwaXhlbEhlaWdodCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBjdHguZmlsbFN0eWxlID0gY29sb3I7CiAgICAgICAgICAgICAgICBjdHguZmlsbFJlY3QoMCwgMCwgcGl4ZWxXaWR0aCwgcGl4ZWxIZWlnaHQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGN0eC5yZXN0b3JlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQ2FudmFzQnVmZmVyLnByb3RvdHlwZS5nZXRJbWFnZURhdGEgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmN0eC5nZXRJbWFnZURhdGEoMCwgMCwgdGhpcy5waXhlbFdpZHRoLCB0aGlzLnBpeGVsSGVpZ2h0KTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBDYW52YXNCdWZmZXI7CiAgICB9KCkpOwogICAgZXhwb3J0cy5DYW52YXNCdWZmZXIgPSBDYW52YXNCdWZmZXI7CiAgICB9KTsKCiAgICB2YXIgc3ltYm9sRHJhd2VyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgogICAgdmFyIFN5bWJvbFNWR0RyYXdlciA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFN5bWJvbFNWR0RyYXdlciwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBTeW1ib2xTVkdEcmF3ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIuY2FsbCh0aGlzLCAicGF0aCIsICJzeW1ib2wiKSB8fCB0aGlzOwogICAgICAgIH0KICAgICAgICByZXR1cm4gU3ltYm9sU1ZHRHJhd2VyOwogICAgfShzdmdEcmF3ZXIuU1ZHRHJhd2VyKSk7CiAgICBleHBvcnRzLlN5bWJvbFNWR0RyYXdlciA9IFN5bWJvbFNWR0RyYXdlcjsKICAgIHZhciBTWU1CT0xfQVRUUlMgPSBjYW52YXNEcmF3ZXIuQ29udGV4dFN0eWxlQXR0cnMuY29uY2F0KFsieCIsICJ5Il0pOwogICAgZnVuY3Rpb24gbWFrZVN5bWJvbENhbnZhc0RyYXdTdGVwKGRhdGFzZXQsIHN5bWJvbFByb2plY3Rvciwgc2l6ZVByb2plY3Rvciwgc3RlcEJ1ZmZlcikgewogICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChjb250ZXh0LCBkYXRhLCBhdHRyVG9BcHBsaWVkUHJvamVjdG9yKSB7CiAgICAgICAgICAgIHZhciBfYSA9IGNvbnRleHQuY2FudmFzLCBjbGllbnRXaWR0aCA9IF9hLmNsaWVudFdpZHRoLCBjbGllbnRIZWlnaHQgPSBfYS5jbGllbnRIZWlnaHQ7CiAgICAgICAgICAgIHZhciBidWZmZXIgPSAoc3RlcEJ1ZmZlciA9PT0gdW5kZWZpbmVkKSA/IG5ldyBjYW52YXNCdWZmZXIuQ2FudmFzQnVmZmVyKDAsIDApIDogc3RlcEJ1ZmZlcjsKICAgICAgICAgICAgdmFyIHN5bWJvbEFjY2Vzc29yID0gc3ltYm9sUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHZhciBzaXplQWNjZXNzb3IgPSBzaXplUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHZhciBwcmV2QXR0cnMgPSBudWxsOwogICAgICAgICAgICB2YXIgcHJldlN5bWJvbEdlbmVyYXRvciA9IG51bGw7CiAgICAgICAgICAgIHZhciBwcmV2U3ltYm9sU2l6ZSA9IG51bGw7CiAgICAgICAgICAgIGZvciAodmFyIGluZGV4ID0gMDsgaW5kZXggPCBkYXRhLmxlbmd0aDsgaW5kZXgrKykgewogICAgICAgICAgICAgICAgdmFyIGRhdHVtID0gZGF0YVtpbmRleF07CiAgICAgICAgICAgICAgICBpZiAoZGF0dW0gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gY2hlY2sgc3ltYm9sIGlzIGluIHZpZXdwb3J0CiAgICAgICAgICAgICAgICB2YXIgYXR0cnMgPSBjYW52YXNEcmF3ZXIucmVzb2x2ZUF0dHJpYnV0ZXMoYXR0clRvQXBwbGllZFByb2plY3RvciwgU1lNQk9MX0FUVFJTLCBkYXR1bSwgaW5kZXgpOwogICAgICAgICAgICAgICAgdmFyIHN5bWJvbFNpemUgPSBzaXplQWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmICghc3F1YXJlT3ZlcmxhcHNCb3VuZHMoY2xpZW50V2lkdGgsIGNsaWVudEhlaWdodCwgYXR0cnNbIngiXSwgYXR0cnNbInkiXSwgc3ltYm9sU2l6ZSkpIHsKICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIGNoZWNrIGF0dHJpYnV0ZXMgYW5kIHN5bWJvbCB0eXBlCiAgICAgICAgICAgICAgICB2YXIgYXR0cnNTYW1lID0gaXNBdHRyaWJ1dGVWYWx1ZXNFcXVhbChwcmV2QXR0cnMsIGF0dHJzLCBjYW52YXNEcmF3ZXIuQ29udGV4dFN0eWxlQXR0cnMpOwogICAgICAgICAgICAgICAgdmFyIHN5bWJvbEdlbmVyYXRvciA9IHN5bWJvbEFjY2Vzc29yKGRhdHVtLCBpbmRleCwgX3RoaXMuX2RhdGFzZXQpOwogICAgICAgICAgICAgICAgaWYgKGF0dHJzU2FtZSAmJiBwcmV2U3ltYm9sU2l6ZSA9PSBzeW1ib2xTaXplICYmIHByZXZTeW1ib2xHZW5lcmF0b3IgPT0gc3ltYm9sR2VuZXJhdG9yKSA7CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAvLyBtYWtlIHJvb20gZm9yIGJpZ2dlciBzeW1ib2wgaWYgbmVlZGVkCiAgICAgICAgICAgICAgICAgICAgdmFyIHN0cm9rZVdpZHRoID0gY2FudmFzRHJhd2VyLmdldFN0cm9rZVdpZHRoKGF0dHJzKTsKICAgICAgICAgICAgICAgICAgICAvLyArMSB0byBhY2NvdW50IGZvciBzdWJwaXhlbCBhbGlhc2luZwogICAgICAgICAgICAgICAgICAgIHZhciB3YW50ZWRCdWZmZXJTaXplID0gc3ltYm9sU2l6ZSArIHN0cm9rZVdpZHRoICsgMTsKICAgICAgICAgICAgICAgICAgICBpZiAod2FudGVkQnVmZmVyU2l6ZSA+IGJ1ZmZlci5zY3JlZW5XaWR0aCB8fCB3YW50ZWRCdWZmZXJTaXplID4gYnVmZmVyLnNjcmVlbkhlaWdodCkgewogICAgICAgICAgICAgICAgICAgICAgICBidWZmZXIucmVzaXplKHdhbnRlZEJ1ZmZlclNpemUsIHdhbnRlZEJ1ZmZlclNpemUsIHRydWUpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBkcmF3IGFjdHVhbCBzeW1ib2wgaW50byBidWZmZXIKICAgICAgICAgICAgICAgICAgICBidWZmZXIuY2xlYXIoKTsKICAgICAgICAgICAgICAgICAgICB2YXIgYnVmZmVyQ3R4ID0gYnVmZmVyLmN0eDsKICAgICAgICAgICAgICAgICAgICBidWZmZXJDdHguYmVnaW5QYXRoKCk7CiAgICAgICAgICAgICAgICAgICAgc3ltYm9sR2VuZXJhdG9yKHN5bWJvbFNpemUpLmNvbnRleHQoYnVmZmVyQ3R4KShudWxsKTsKICAgICAgICAgICAgICAgICAgICBidWZmZXJDdHguY2xvc2VQYXRoKCk7CiAgICAgICAgICAgICAgICAgICAgY2FudmFzRHJhd2VyLnJlbmRlclBhdGhXaXRoU3R5bGUoYnVmZmVyQ3R4LCBhdHRycyk7CiAgICAgICAgICAgICAgICAgICAgLy8gc2F2ZSB0aGUgdmFsdWVzIHRoYXQgYXJlIGluIHRoZSBidWZmZXIKICAgICAgICAgICAgICAgICAgICBwcmV2U3ltYm9sR2VuZXJhdG9yID0gc3ltYm9sR2VuZXJhdG9yOwogICAgICAgICAgICAgICAgICAgIHByZXZTeW1ib2xTaXplID0gc3ltYm9sU2l6ZTsKICAgICAgICAgICAgICAgICAgICBwcmV2QXR0cnMgPSBhdHRyczsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIGJsaXQgdGhlIGJ1ZmZlciB0byB0aGUgY2FudmFzCiAgICAgICAgICAgICAgICBidWZmZXIuYmxpdENlbnRlcihjb250ZXh0LCBhdHRyc1sieCJdLCBhdHRyc1sieSJdKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICB9CiAgICBleHBvcnRzLm1ha2VTeW1ib2xDYW52YXNEcmF3U3RlcCA9IG1ha2VTeW1ib2xDYW52YXNEcmF3U3RlcDsKICAgIGZ1bmN0aW9uIHNxdWFyZU92ZXJsYXBzQm91bmRzKHdpZHRoLCBoZWlnaHQsIHgsIHksIHNpemUpIHsKICAgICAgICByZXR1cm4gKHggKyBzaXplID49IDAgJiYgeCAtIHNpemUgPD0gd2lkdGggJiYKICAgICAgICAgICAgeSArIHNpemUgPj0gMCAmJiB5IC0gc2l6ZSA8PSBoZWlnaHQpOwogICAgfQogICAgZnVuY3Rpb24gaXNBdHRyaWJ1dGVWYWx1ZXNFcXVhbChwcmV2QXR0cnMsIGF0dHJzLCBhdHRyS2V5cykgewogICAgICAgIGlmIChwcmV2QXR0cnMgPT0gbnVsbCkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgYXR0cktleXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgdmFyIGF0dHJLZXkgPSBhdHRyS2V5c1tpXTsKICAgICAgICAgICAgaWYgKHByZXZBdHRyc1thdHRyS2V5XSAhPSBhdHRyc1thdHRyS2V5XSkgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiB0cnVlOwogICAgfQogICAgfSk7CgogICAgdmFyIGRyYXdlcnMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGFyY0RyYXdlciwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGFyY091dGxpbmVEcmF3ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihhcmVhRHJhd2VyLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoY2FudmFzRHJhd2VyLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZHJhd2VyLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIobGluZURyYXdlciwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHJlY3RhbmdsZURyYXdlciwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHNlZ21lbnREcmF3ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihzdmdEcmF3ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihzeW1ib2xEcmF3ZXIsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIHh5UGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCiAgICB2YXIgWFlQbG90ID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoWFlQbG90LCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEFuIFhZUGxvdCBpcyBhIFBsb3QgdGhhdCBkaXNwbGF5cyBkYXRhIGFsb25nIHR3byBwcmltYXJ5IGRpcmVjdGlvbnMsIFggYW5kIFkuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlfSB4U2NhbGUgVGhlIHggc2NhbGUgdG8gdXNlLgogICAgICAgICAqIEBwYXJhbSB7U2NhbGV9IHlTY2FsZSBUaGUgeSBzY2FsZSB0byB1c2UuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gWFlQbG90KCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fYXV0b0FkanVzdFhTY2FsZURvbWFpbiA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fYXV0b0FkanVzdFlTY2FsZURvbWFpbiA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fZGVmZXJyZWRSZW5kZXJpbmcgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuX2FwcGx5RGVmZXJyZWRSZW5kZXJpbmdUcmFuc2Zvcm0gPSBmdW5jdGlvbiAodHgsIHR5LCBzeCwgc3kpIHsKICAgICAgICAgICAgICAgIGlmICghX3RoaXMuX2lzQW5jaG9yZWQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoX3RoaXMuX3JlbmRlckFyZWEgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIF90aGlzLl9yZW5kZXJBcmVhLmF0dHIoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIHR4ICsgIiwgIiArIHR5ICsgIikgc2NhbGUoIiArIHN4ICsgIiwgIiArIHN5ICsgIikiKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChfdGhpcy5fY2FudmFzICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fY2FudmFzLnN0eWxlKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyB0eCArICJweCwgIiArIHR5ICsgInB4KSBzY2FsZSgiICsgc3ggKyAiLCAiICsgc3kgKyAiKSIpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygieHktcGxvdCIpOwogICAgICAgICAgICBfdGhpcy5fYWRqdXN0WURvbWFpbk9uQ2hhbmdlRnJvbVhDYWxsYmFjayA9IGZ1bmN0aW9uIChzY2FsZSkgeyByZXR1cm4gX3RoaXMuX2FkanVzdFlEb21haW5PbkNoYW5nZUZyb21YKCk7IH07CiAgICAgICAgICAgIF90aGlzLl9hZGp1c3RYRG9tYWluT25DaGFuZ2VGcm9tWUNhbGxiYWNrID0gZnVuY3Rpb24gKHNjYWxlKSB7IHJldHVybiBfdGhpcy5fYWRqdXN0WERvbWFpbk9uQ2hhbmdlRnJvbVkoKTsgfTsKICAgICAgICAgICAgX3RoaXMuX3JlbmRlckNhbGxiYWNrID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgaWYgKF90aGlzLmRlZmVycmVkUmVuZGVyaW5nKCkpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgc2NhbGVYID0gX3RoaXMueCgpICYmIF90aGlzLngoKS5zY2FsZTsKICAgICAgICAgICAgICAgICAgICB2YXIgc2NhbGVZID0gX3RoaXMueSgpICYmIF90aGlzLnkoKS5zY2FsZTsKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZGVmZXJyZWRSZW5kZXJlci51cGRhdGVEb21haW5zKHNjYWxlWCwgc2NhbGVZKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIF90aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBfdGhpcy5fZGVmZXJyZWRSZW5kZXJlciA9IG5ldyBkZWZlcnJlZFJlbmRlcmVyLkRlZmVycmVkUmVuZGVyZXIoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMucmVuZGVyKCk7IH0sIF90aGlzLl9hcHBseURlZmVycmVkUmVuZGVyaW5nVHJhbnNmb3JtKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBYWVBsb3QucHJvdG90eXBlLnJlbmRlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuZGVmZXJyZWRSZW5kZXJpbmcoKSkgewogICAgICAgICAgICAgICAgdGhpcy5fZGVmZXJyZWRSZW5kZXJlci5yZXNldFRyYW5zZm9ybXMoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5yZW5kZXIuY2FsbCh0aGlzKTsKICAgICAgICB9OwogICAgICAgIFhZUGxvdC5wcm90b3R5cGUuZGVmZXJyZWRSZW5kZXJpbmcgPSBmdW5jdGlvbiAoZGVmZXJyZWRSZW5kZXJpbmcpIHsKICAgICAgICAgICAgaWYgKGRlZmVycmVkUmVuZGVyaW5nID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kZWZlcnJlZFJlbmRlcmluZzsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoZGVmZXJyZWRSZW5kZXJpbmcpIHsKICAgICAgICAgICAgICAgIHZhciBzY2FsZVggPSB0aGlzLngoKSAmJiB0aGlzLngoKS5zY2FsZTsKICAgICAgICAgICAgICAgIHZhciBzY2FsZVkgPSB0aGlzLnkoKSAmJiB0aGlzLnkoKS5zY2FsZTsKICAgICAgICAgICAgICAgIHRoaXMuX2RlZmVycmVkUmVuZGVyZXIuc2V0RG9tYWlucyhzY2FsZVgsIHNjYWxlWSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZGVmZXJyZWRSZW5kZXJpbmcgPSBkZWZlcnJlZFJlbmRlcmluZzsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLnggPSBmdW5jdGlvbiAoeCwgeFNjYWxlLCBwb3N0U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHggPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFhZUGxvdC5fWF9LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShYWVBsb3QuX1hfS0VZLCB4LCB4U2NhbGUsIHBvc3RTY2FsZSk7CiAgICAgICAgICAgIHZhciB3aWR0aCA9IHRoaXMud2lkdGgoKTsKICAgICAgICAgICAgaWYgKHhTY2FsZSAhPSBudWxsICYmIHdpZHRoICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHhTY2FsZS5yYW5nZShbMCwgd2lkdGhdKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fYXV0b0FkanVzdFlTY2FsZURvbWFpbikgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlWUV4dGVudHNBbmRBdXRvZG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLnkgPSBmdW5jdGlvbiAoeSwgeVNjYWxlLCBwb3N0U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFhZUGxvdC5fWV9LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShYWVBsb3QuX1lfS0VZLCB5LCB5U2NhbGUsIHBvc3RTY2FsZSk7CiAgICAgICAgICAgIHZhciBoZWlnaHQgPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICBpZiAoeVNjYWxlICE9IG51bGwgJiYgaGVpZ2h0ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmICh5U2NhbGUgaW5zdGFuY2VvZiBzY2FsZXMuQ2F0ZWdvcnkpIHsKICAgICAgICAgICAgICAgICAgICB5U2NhbGUucmFuZ2UoWzAsIGhlaWdodF0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgeVNjYWxlLnJhbmdlKFtoZWlnaHQsIDBdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fYXV0b0FkanVzdFhTY2FsZURvbWFpbikgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlWEV4dGVudHNBbmRBdXRvZG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLl9maWx0ZXJGb3JQcm9wZXJ0eSA9IGZ1bmN0aW9uIChwcm9wZXJ0eSkgewogICAgICAgICAgICBpZiAocHJvcGVydHkgPT09ICJ4IiAmJiB0aGlzLl9hdXRvQWRqdXN0WFNjYWxlRG9tYWluKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbWFrZUZpbHRlckJ5UHJvcGVydHkoInkiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICgocHJvcGVydHkgPT09ICJ5IiB8fCBwcm9wZXJ0eSA9PT0gInkwIikgJiYgdGhpcy5fYXV0b0FkanVzdFlTY2FsZURvbWFpbikgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX21ha2VGaWx0ZXJCeVByb3BlcnR5KCJ4Iik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLl9tYWtlRmlsdGVyQnlQcm9wZXJ0eSA9IGZ1bmN0aW9uIChwcm9wZXJ0eSkgewogICAgICAgICAgICB2YXIgYmluZGluZyA9IHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KHByb3BlcnR5KTsKICAgICAgICAgICAgaWYgKGJpbmRpbmcgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIGFjY2Vzc29yXzEgPSBiaW5kaW5nLmFjY2Vzc29yOwogICAgICAgICAgICAgICAgdmFyIHNjYWxlXzEgPSBiaW5kaW5nLnNjYWxlOwogICAgICAgICAgICAgICAgaWYgKHNjYWxlXzEgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbiAoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciByYW5nZSA9IHNjYWxlXzEucmFuZ2UoKTsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuTWF0aC5pblJhbmdlKHNjYWxlXzEuc2NhbGUoYWNjZXNzb3JfMShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpKSwgcmFuZ2VbMF0sIHJhbmdlWzFdKTsKICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH07CiAgICAgICAgWFlQbG90LnByb3RvdHlwZS5fdW5pbnN0YWxsU2NhbGVGb3JLZXkgPSBmdW5jdGlvbiAoc2NhbGUsIGtleSkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl91bmluc3RhbGxTY2FsZUZvcktleS5jYWxsKHRoaXMsIHNjYWxlLCBrZXkpOwogICAgICAgICAgICB2YXIgYWRqdXN0Q2FsbGJhY2sgPSBrZXkgPT09IFhZUGxvdC5fWF9LRVkgPyB0aGlzLl9hZGp1c3RZRG9tYWluT25DaGFuZ2VGcm9tWENhbGxiYWNrCiAgICAgICAgICAgICAgICA6IHRoaXMuX2FkanVzdFhEb21haW5PbkNoYW5nZUZyb21ZQ2FsbGJhY2s7CiAgICAgICAgICAgIHNjYWxlLm9mZlVwZGF0ZShhZGp1c3RDYWxsYmFjayk7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLl9pbnN0YWxsU2NhbGVGb3JLZXkgPSBmdW5jdGlvbiAoc2NhbGUsIGtleSkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9pbnN0YWxsU2NhbGVGb3JLZXkuY2FsbCh0aGlzLCBzY2FsZSwga2V5KTsKICAgICAgICAgICAgdmFyIGFkanVzdENhbGxiYWNrID0ga2V5ID09PSBYWVBsb3QuX1hfS0VZID8gdGhpcy5fYWRqdXN0WURvbWFpbk9uQ2hhbmdlRnJvbVhDYWxsYmFjawogICAgICAgICAgICAgICAgOiB0aGlzLl9hZGp1c3RYRG9tYWluT25DaGFuZ2VGcm9tWUNhbGxiYWNrOwogICAgICAgICAgICBzY2FsZS5vblVwZGF0ZShhZGp1c3RDYWxsYmFjayk7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLmRlc3Ryb3kgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGVzdHJveS5jYWxsKHRoaXMpOwogICAgICAgICAgICBpZiAodGhpcy54KCkuc2NhbGUpIHsKICAgICAgICAgICAgICAgIHRoaXMueCgpLnNjYWxlLm9mZlVwZGF0ZSh0aGlzLl9hZGp1c3RZRG9tYWluT25DaGFuZ2VGcm9tWENhbGxiYWNrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy55KCkuc2NhbGUpIHsKICAgICAgICAgICAgICAgIHRoaXMueSgpLnNjYWxlLm9mZlVwZGF0ZSh0aGlzLl9hZGp1c3RYRG9tYWluT25DaGFuZ2VGcm9tWUNhbGxiYWNrKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFhZUGxvdC5wcm90b3R5cGUuYXV0b3JhbmdlTW9kZSA9IGZ1bmN0aW9uIChhdXRvcmFuZ2VNb2RlKSB7CiAgICAgICAgICAgIGlmIChhdXRvcmFuZ2VNb2RlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9hdXRvQWRqdXN0WFNjYWxlRG9tYWluKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICJ4IjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICh0aGlzLl9hdXRvQWRqdXN0WVNjYWxlRG9tYWluKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICJ5IjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiAibm9uZSI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc3dpdGNoIChhdXRvcmFuZ2VNb2RlKSB7CiAgICAgICAgICAgICAgICBjYXNlICJ4IjoKICAgICAgICAgICAgICAgICAgICB0aGlzLl9hdXRvQWRqdXN0WFNjYWxlRG9tYWluID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9hdXRvQWRqdXN0WVNjYWxlRG9tYWluID0gZmFsc2U7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYWRqdXN0WERvbWFpbk9uQ2hhbmdlRnJvbVkoKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgInkiOgogICAgICAgICAgICAgICAgICAgIHRoaXMuX2F1dG9BZGp1c3RYU2NhbGVEb21haW4gPSBmYWxzZTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9hdXRvQWRqdXN0WVNjYWxlRG9tYWluID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9hZGp1c3RZRG9tYWluT25DaGFuZ2VGcm9tWCgpOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAibm9uZSI6CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYXV0b0FkanVzdFhTY2FsZURvbWFpbiA9IGZhbHNlOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2F1dG9BZGp1c3RZU2NhbGVEb21haW4gPSBmYWxzZTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJJbnZhbGlkIHNjYWxlIG5hbWUgJyIgKyBhdXRvcmFuZ2VNb2RlICsgIicsIG11c3QgYmUgJ3gnLCAneScgb3IgJ25vbmUnIik7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQgPSBmdW5jdGlvbiAob3JpZ2luLCBhdmFpbGFibGVXaWR0aCwgYXZhaWxhYmxlSGVpZ2h0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuY29tcHV0ZUxheW91dC5jYWxsKHRoaXMsIG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCk7CiAgICAgICAgICAgIHZhciB4QmluZGluZyA9IHRoaXMueCgpOwogICAgICAgICAgICB2YXIgeFNjYWxlID0geEJpbmRpbmcgJiYgeEJpbmRpbmcuc2NhbGU7CiAgICAgICAgICAgIGlmICh4U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgeFNjYWxlLnJhbmdlKFswLCB0aGlzLndpZHRoKCldKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgeUJpbmRpbmcgPSB0aGlzLnkoKTsKICAgICAgICAgICAgdmFyIHlTY2FsZSA9IHlCaW5kaW5nICYmIHlCaW5kaW5nLnNjYWxlOwogICAgICAgICAgICBpZiAoeVNjYWxlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmICh5U2NhbGUgaW5zdGFuY2VvZiBzY2FsZXMuQ2F0ZWdvcnkpIHsKICAgICAgICAgICAgICAgICAgICB5U2NhbGUucmFuZ2UoWzAsIHRoaXMuaGVpZ2h0KCldKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHlTY2FsZS5yYW5nZShbdGhpcy5oZWlnaHQoKSwgMF0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgWFlQbG90LnByb3RvdHlwZS5fdXBkYXRlWEV4dGVudHNBbmRBdXRvZG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgeFNjYWxlID0gdGhpcy54KCkuc2NhbGU7CiAgICAgICAgICAgIGlmICh4U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgeFNjYWxlLmF1dG9Eb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgWFlQbG90LnByb3RvdHlwZS5fdXBkYXRlWUV4dGVudHNBbmRBdXRvZG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgeVNjYWxlID0gdGhpcy55KCkuc2NhbGU7CiAgICAgICAgICAgIGlmICh5U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgeVNjYWxlLmF1dG9Eb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogQWRqdXN0cyB0aGUgZG9tYWlucyBvZiBib3RoIFggYW5kIFkgc2NhbGVzIHRvIHNob3cgYWxsIGRhdGEuCiAgICAgICAgICogVGhpcyBjYWxsIGRvZXMgbm90IG92ZXJyaWRlIHRoZSBhdXRvcmFuZ2UoKSBiZWhhdmlvci4KICAgICAgICAgKgogICAgICAgICAqIEByZXR1cm5zIHtYWVBsb3R9IFRoZSBjYWxsaW5nIFhZUGxvdC4KICAgICAgICAgKi8KICAgICAgICBYWVBsb3QucHJvdG90eXBlLnNob3dBbGxEYXRhID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB0aGlzLl91cGRhdGVYRXh0ZW50c0FuZEF1dG9kb21haW4oKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlWUV4dGVudHNBbmRBdXRvZG9tYWluKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgWFlQbG90LnByb3RvdHlwZS5fYWRqdXN0WURvbWFpbk9uQ2hhbmdlRnJvbVggPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fcHJvamVjdG9yc1JlYWR5KCkpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fYXV0b0FkanVzdFlTY2FsZURvbWFpbikgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlWUV4dGVudHNBbmRBdXRvZG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFhZUGxvdC5wcm90b3R5cGUuX2FkanVzdFhEb21haW5PbkNoYW5nZUZyb21ZID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX3Byb2plY3RvcnNSZWFkeSgpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX2F1dG9BZGp1c3RYU2NhbGVEb21haW4pIHsKICAgICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVhFeHRlbnRzQW5kQXV0b2RvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLl9wcm9qZWN0b3JzUmVhZHkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciB4QmluZGluZyA9IHRoaXMueCgpOwogICAgICAgICAgICB2YXIgeUJpbmRpbmcgPSB0aGlzLnkoKTsKICAgICAgICAgICAgcmV0dXJuIHhCaW5kaW5nICE9IG51bGwgJiYKICAgICAgICAgICAgICAgIHhCaW5kaW5nLmFjY2Vzc29yICE9IG51bGwgJiYKICAgICAgICAgICAgICAgIHlCaW5kaW5nICE9IG51bGwgJiYKICAgICAgICAgICAgICAgIHlCaW5kaW5nLmFjY2Vzc29yICE9IG51bGw7CiAgICAgICAgfTsKICAgICAgICBYWVBsb3QucHJvdG90eXBlLl9waXhlbFBvaW50ID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICB2YXIgeFByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpOwogICAgICAgICAgICB2YXIgeVByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55KCkpOwogICAgICAgICAgICByZXR1cm4geyB4OiB4UHJvamVjdG9yKGRhdHVtLCBpbmRleCwgZGF0YXNldCksIHk6IHlQcm9qZWN0b3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB9OwogICAgICAgIH07CiAgICAgICAgWFlQbG90LnByb3RvdHlwZS5fZ2V0RGF0YVRvRHJhdyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGRhdGFUb0RyYXcgPSBfc3VwZXIucHJvdG90eXBlLl9nZXREYXRhVG9EcmF3LmNhbGwodGhpcyk7CiAgICAgICAgICAgIHZhciBkZWZpbmVkQXR0ciA9IHRoaXMuYXR0cigiZGVmaW5lZCIpOwogICAgICAgICAgICB2YXIgZGVmaW5lZEZ1bmN0aW9uID0gZnVuY3Rpb24gKGQsIGksIGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIHZhciBwb3NpdGlvblggPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKF90aGlzLngoKSkoZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpb25ZID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3NvcihfdGhpcy55KCkpKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgaWYgKGRlZmluZWRBdHRyICYmIGRlZmluZWRBdHRyLmFjY2Vzc29yKGQsIGksIGRhdGFzZXQpID09PSBmYWxzZSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihwb3NpdGlvblgpICYmCiAgICAgICAgICAgICAgICAgICAgdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIocG9zaXRpb25ZKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRhdGFzZXQsIGRhdGFUb0RyYXcuZ2V0KGRhdGFzZXQpLmZpbHRlcihmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gZGVmaW5lZEZ1bmN0aW9uKGQsIGksIGRhdGFzZXQpOyB9KSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gZGF0YVRvRHJhdzsKICAgICAgICB9OwogICAgICAgIFhZUGxvdC5fWF9LRVkgPSAieCI7CiAgICAgICAgWFlQbG90Ll9ZX0tFWSA9ICJ5IjsKICAgICAgICByZXR1cm4gWFlQbG90OwogICAgfShwbG90LlBsb3QpKTsKICAgIGV4cG9ydHMuWFlQbG90ID0gWFlQbG90OwogICAgfSk7CgogICAgdmFyIGxpbmVQbG90ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCgoKCgoKCgogICAgdmFyIENVUlZFX05BTUVfTUFQUElORyA9IHsKICAgICAgICBsaW5lYXI6IGQzLmN1cnZlTGluZWFyLAogICAgICAgIGxpbmVhckNsb3NlZDogZDMuY3VydmVMaW5lYXJDbG9zZWQsCiAgICAgICAgc3RlcDogZDMuY3VydmVTdGVwLAogICAgICAgIHN0ZXBCZWZvcmU6IGQzLmN1cnZlU3RlcEJlZm9yZSwKICAgICAgICBzdGVwQWZ0ZXI6IGQzLmN1cnZlU3RlcEFmdGVyLAogICAgICAgIGJhc2lzOiBkMy5jdXJ2ZUJhc2lzLAogICAgICAgIGJhc2lzT3BlbjogZDMuY3VydmVCYXNpc09wZW4sCiAgICAgICAgYmFzaXNDbG9zZWQ6IGQzLmN1cnZlQmFzaXNDbG9zZWQsCiAgICAgICAgYnVuZGxlOiBkMy5jdXJ2ZUJ1bmRsZSwKICAgICAgICBjYXJkaW5hbDogZDMuY3VydmVDYXJkaW5hbCwKICAgICAgICBjYXJkaW5hbE9wZW46IGQzLmN1cnZlQ2FyZGluYWxPcGVuLAogICAgICAgIGNhcmRpbmFsQ2xvc2VkOiBkMy5jdXJ2ZUNhcmRpbmFsQ2xvc2VkLAogICAgICAgIG1vbm90b25lOiBkMy5jdXJ2ZU1vbm90b25lWCwKICAgIH07CiAgICAvKioKICAgICAqIEtub3duIGN1cnZlIHR5cGVzIHRoYXQgbGluZSBhbmQgYXJlYSBwbG90J3MgLmN1cnZlKCkgbWV0aG9kcyB1bmRlcnN0YW5kCiAgICAgKi8KICAgIGV4cG9ydHMuQ3VydmVOYW1lID0gbWFrZUVudW1fMS5tYWtlRW51bShbCiAgICAgICAgImxpbmVhciIsCiAgICAgICAgImxpbmVhckNsb3NlZCIsCiAgICAgICAgInN0ZXAiLAogICAgICAgICJzdGVwQmVmb3JlIiwKICAgICAgICAic3RlcEFmdGVyIiwKICAgICAgICAiYmFzaXMiLAogICAgICAgICJiYXNpc09wZW4iLAogICAgICAgICJiYXNpc0Nsb3NlZCIsCiAgICAgICAgImJ1bmRsZSIsCiAgICAgICAgImNhcmRpbmFsIiwKICAgICAgICAiY2FyZGluYWxPcGVuIiwKICAgICAgICAiY2FyZGluYWxDbG9zZWQiLAogICAgICAgICJtb25vdG9uZSIsCiAgICBdKTsKICAgIHZhciBMaW5lID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoTGluZSwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBIExpbmUgUGxvdCBkcmF3cyBsaW5lIHNlZ21lbnRzIHN0YXJ0aW5nIGZyb20gdGhlIGZpcnN0IGRhdGEgcG9pbnQgdG8gdGhlIG5leHQuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBMaW5lKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fY3VydmUgPSAibGluZWFyIjsKICAgICAgICAgICAgX3RoaXMuX2F1dG9yYW5nZVNtb290aCA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5fY3JvcHBlZFJlbmRlcmluZ0VuYWJsZWQgPSB0cnVlOwogICAgICAgICAgICBfdGhpcy5fY29sbGFwc2VEZW5zZVZlcnRpY2FsTGluZXNFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLl9kb3duc2FtcGxpbmdFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJsaW5lLXBsb3QiKTsKICAgICAgICAgICAgdmFyIGFuaW1hdG9yID0gbmV3IGFuaW1hdG9ycy5FYXNpbmcoKTsKICAgICAgICAgICAgYW5pbWF0b3Iuc3RlcER1cmF0aW9uKHBsb3QuUGxvdC5fQU5JTUFUSU9OX01BWF9EVVJBVElPTik7CiAgICAgICAgICAgIGFuaW1hdG9yLmVhc2luZ01vZGUoImV4cEluT3V0Iik7CiAgICAgICAgICAgIGFuaW1hdG9yLm1heFRvdGFsRHVyYXRpb24ocGxvdC5QbG90Ll9BTklNQVRJT05fTUFYX0RVUkFUSU9OKTsKICAgICAgICAgICAgX3RoaXMuYW5pbWF0b3IocGxvdHMuQW5pbWF0b3IuTUFJTiwgYW5pbWF0b3IpOwogICAgICAgICAgICBfdGhpcy5hdHRyKCJzdHJva2UiLCBuZXcgc2NhbGVzLkNvbG9yKCkucmFuZ2UoKVswXSk7CiAgICAgICAgICAgIF90aGlzLmF0dHIoInN0cm9rZS13aWR0aCIsICIycHgiKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBMaW5lLnByb3RvdHlwZS54ID0gZnVuY3Rpb24gKHgsIHhTY2FsZSwgcG9zdFNjYWxlKSB7CiAgICAgICAgICAgIGlmICh4ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnguY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueC5jYWxsKHRoaXMsIHgsIHhTY2FsZSwgcG9zdFNjYWxlKTsKICAgICAgICAgICAgICAgIHRoaXMuX3NldFNjYWxlU25hcHBpbmcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS55ID0gZnVuY3Rpb24gKHksIHlTY2FsZSwgcG9zdFNjYWxlKSB7CiAgICAgICAgICAgIGlmICh5ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMsIHksIHlTY2FsZSwgcG9zdFNjYWxlKTsKICAgICAgICAgICAgICAgIHRoaXMuX3NldFNjYWxlU25hcHBpbmcoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5hdXRvcmFuZ2VNb2RlID0gZnVuY3Rpb24gKGF1dG9yYW5nZU1vZGUpIHsKICAgICAgICAgICAgaWYgKGF1dG9yYW5nZU1vZGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuYXV0b3JhbmdlTW9kZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuYXV0b3JhbmdlTW9kZS5jYWxsKHRoaXMsIGF1dG9yYW5nZU1vZGUpOwogICAgICAgICAgICB0aGlzLl9zZXRTY2FsZVNuYXBwaW5nKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuYXV0b3JhbmdlU21vb3RoID0gZnVuY3Rpb24gKGF1dG9yYW5nZVNtb290aCkgewogICAgICAgICAgICBpZiAoYXV0b3JhbmdlU21vb3RoID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9hdXRvcmFuZ2VTbW9vdGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fYXV0b3JhbmdlU21vb3RoID0gYXV0b3JhbmdlU21vb3RoOwogICAgICAgICAgICB0aGlzLl9zZXRTY2FsZVNuYXBwaW5nKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX3NldFNjYWxlU25hcHBpbmcgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLmF1dG9yYW5nZU1vZGUoKSA9PT0gIngiICYmIHRoaXMueCgpICYmIHRoaXMueCgpLnNjYWxlICYmIHRoaXMueCgpLnNjYWxlIGluc3RhbmNlb2YgcXVhbnRpdGF0aXZlU2NhbGUuUXVhbnRpdGF0aXZlU2NhbGUpIHsKICAgICAgICAgICAgICAgIHRoaXMueCgpLnNjYWxlLnNuYXBwaW5nRG9tYWluRW5hYmxlZCghdGhpcy5hdXRvcmFuZ2VTbW9vdGgoKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuYXV0b3JhbmdlTW9kZSgpID09PSAieSIgJiYgdGhpcy55KCkgJiYgdGhpcy55KCkuc2NhbGUgJiYgdGhpcy55KCkuc2NhbGUgaW5zdGFuY2VvZiBxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSkgewogICAgICAgICAgICAgICAgdGhpcy55KCkuc2NhbGUuc25hcHBpbmdEb21haW5FbmFibGVkKCF0aGlzLmF1dG9yYW5nZVNtb290aCgpKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuY3VydmUgPSBmdW5jdGlvbiAoY3VydmUpIHsKICAgICAgICAgICAgaWYgKGN1cnZlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9jdXJ2ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jdXJ2ZSA9IGN1cnZlOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIExpbmUucHJvdG90eXBlLmRvd25zYW1wbGluZ0VuYWJsZWQgPSBmdW5jdGlvbiAoZG93bnNhbXBsaW5nKSB7CiAgICAgICAgICAgIGlmIChkb3duc2FtcGxpbmcgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Rvd25zYW1wbGluZ0VuYWJsZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZG93bnNhbXBsaW5nRW5hYmxlZCA9IGRvd25zYW1wbGluZzsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5jcm9wcGVkUmVuZGVyaW5nRW5hYmxlZCA9IGZ1bmN0aW9uIChjcm9wcGVkUmVuZGVyaW5nKSB7CiAgICAgICAgICAgIGlmIChjcm9wcGVkUmVuZGVyaW5nID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9jcm9wcGVkUmVuZGVyaW5nRW5hYmxlZDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jcm9wcGVkUmVuZGVyaW5nRW5hYmxlZCA9IGNyb3BwZWRSZW5kZXJpbmc7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuY29sbGFwc2VEZW5zZUxpbmVzRW5hYmxlZCA9IGZ1bmN0aW9uIChjb2xsYXBzZURlbnNlTGluZXMpIHsKICAgICAgICAgICAgaWYgKGNvbGxhcHNlRGVuc2VMaW5lcyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fY29sbGFwc2VEZW5zZVZlcnRpY2FsTGluZXNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2NvbGxhcHNlRGVuc2VWZXJ0aWNhbExpbmVzRW5hYmxlZCA9IGNvbGxhcHNlRGVuc2VMaW5lczsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5fY3JlYXRlRHJhd2VyID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXIuUHJveHlEcmF3ZXIoZnVuY3Rpb24gKCkgeyByZXR1cm4gbmV3IGxpbmVEcmF3ZXIuTGluZVNWR0RyYXdlcigpOyB9LCBmdW5jdGlvbiAoY3R4KSB7IHJldHVybiBuZXcgZHJhd2Vycy5DYW52YXNEcmF3ZXIoY3R4LCBsaW5lRHJhd2VyLm1ha2VMaW5lQ2FudmFzRHJhd1N0ZXAoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2QzTGluZUZhY3RvcnkoZGF0YXNldCk7IH0pKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5nZXRFeHRlbnRzRm9yUHJvcGVydHkgPSBmdW5jdGlvbiAocHJvcGVydHkpIHsKICAgICAgICAgICAgdmFyIGV4dGVudHMgPSBfc3VwZXIucHJvdG90eXBlLmdldEV4dGVudHNGb3JQcm9wZXJ0eS5jYWxsKHRoaXMsIHByb3BlcnR5KTsKICAgICAgICAgICAgaWYgKCF0aGlzLl9hdXRvcmFuZ2VTbW9vdGgpIHsKICAgICAgICAgICAgICAgIHJldHVybiBleHRlbnRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLmF1dG9yYW5nZU1vZGUoKSAhPT0gcHJvcGVydHkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBleHRlbnRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLmF1dG9yYW5nZU1vZGUoKSAhPT0gIngiICYmIHRoaXMuYXV0b3JhbmdlTW9kZSgpICE9PSAieSIpIHsKICAgICAgICAgICAgICAgIHJldHVybiBleHRlbnRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBlZGdlSW50ZXJzZWN0aW9uUG9pbnRzID0gdGhpcy5fZ2V0RWRnZUludGVyc2VjdGlvblBvaW50cygpOwogICAgICAgICAgICB2YXIgaW5jbHVkZWRWYWx1ZXM7CiAgICAgICAgICAgIGlmICh0aGlzLmF1dG9yYW5nZU1vZGUoKSA9PT0gInkiKSB7CiAgICAgICAgICAgICAgICBpbmNsdWRlZFZhbHVlcyA9IGVkZ2VJbnRlcnNlY3Rpb25Qb2ludHMubGVmdC5jb25jYXQoZWRnZUludGVyc2VjdGlvblBvaW50cy5yaWdodCkubWFwKGZ1bmN0aW9uIChwb2ludCkgeyByZXR1cm4gcG9pbnQueTsgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBpbmNsdWRlZFZhbHVlcyA9IGVkZ2VJbnRlcnNlY3Rpb25Qb2ludHMudG9wLmNvbmNhdChlZGdlSW50ZXJzZWN0aW9uUG9pbnRzLmJvdHRvbSkubWFwKGZ1bmN0aW9uIChwb2ludCkgeyByZXR1cm4gcG9pbnQueDsgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGV4dGVudHMubWFwKGZ1bmN0aW9uIChleHRlbnQpIHsgcmV0dXJuIGQzLmV4dGVudChkMy5tZXJnZShbZXh0ZW50LCBpbmNsdWRlZFZhbHVlc10pKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5fZ2V0RWRnZUludGVyc2VjdGlvblBvaW50cyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKCEodGhpcy55KCkuc2NhbGUgaW5zdGFuY2VvZiBxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSAmJiB0aGlzLngoKS5zY2FsZSBpbnN0YW5jZW9mIHF1YW50aXRhdGl2ZVNjYWxlLlF1YW50aXRhdGl2ZVNjYWxlKSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBsZWZ0OiBbXSwKICAgICAgICAgICAgICAgICAgICByaWdodDogW10sCiAgICAgICAgICAgICAgICAgICAgdG9wOiBbXSwKICAgICAgICAgICAgICAgICAgICBib3R0b206IFtdLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgeVNjYWxlID0gdGhpcy55KCkuc2NhbGU7CiAgICAgICAgICAgIHZhciB4U2NhbGUgPSB0aGlzLngoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIGludGVyc2VjdGlvblBvaW50cyA9IHsKICAgICAgICAgICAgICAgIGxlZnQ6IFtdLAogICAgICAgICAgICAgICAgcmlnaHQ6IFtdLAogICAgICAgICAgICAgICAgdG9wOiBbXSwKICAgICAgICAgICAgICAgIGJvdHRvbTogW10sCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBsZWZ0WCA9IHhTY2FsZS5zY2FsZSh4U2NhbGUuZG9tYWluKClbMF0pOwogICAgICAgICAgICB2YXIgcmlnaHRYID0geFNjYWxlLnNjYWxlKHhTY2FsZS5kb21haW4oKVsxXSk7CiAgICAgICAgICAgIHZhciBib3R0b21ZID0geVNjYWxlLnNjYWxlKHlTY2FsZS5kb21haW4oKVswXSk7CiAgICAgICAgICAgIHZhciB0b3BZID0geVNjYWxlLnNjYWxlKHlTY2FsZS5kb21haW4oKVsxXSk7CiAgICAgICAgICAgIHRoaXMuZGF0YXNldHMoKS5mb3JFYWNoKGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgZGF0YSA9IGRhdGFzZXQuZGF0YSgpOwogICAgICAgICAgICAgICAgdmFyIHgxLCB4MiwgeTEsIHkyOwogICAgICAgICAgICAgICAgdmFyIHByZXZYLCBwcmV2WSwgY3VyclgsIGN1cnJZOwogICAgICAgICAgICAgICAgZm9yICh2YXIgaSA9IDE7IGkgPCBkYXRhLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgcHJldlggPSBjdXJyWCB8fCB4U2NhbGUuc2NhbGUoX3RoaXMueCgpLmFjY2Vzc29yKGRhdGFbaSAtIDFdLCBpIC0gMSwgZGF0YXNldCkpOwogICAgICAgICAgICAgICAgICAgIHByZXZZID0gY3VyclkgfHwgeVNjYWxlLnNjYWxlKF90aGlzLnkoKS5hY2Nlc3NvcihkYXRhW2kgLSAxXSwgaSAtIDEsIGRhdGFzZXQpKTsKICAgICAgICAgICAgICAgICAgICBjdXJyWCA9IHhTY2FsZS5zY2FsZShfdGhpcy54KCkuYWNjZXNzb3IoZGF0YVtpXSwgaSwgZGF0YXNldCkpOwogICAgICAgICAgICAgICAgICAgIGN1cnJZID0geVNjYWxlLnNjYWxlKF90aGlzLnkoKS5hY2Nlc3NvcihkYXRhW2ldLCBpLCBkYXRhc2V0KSk7CiAgICAgICAgICAgICAgICAgICAgLy8gSWYgdmFsdWVzIGNyb3NzZWQgbGVmdCBlZGdlCiAgICAgICAgICAgICAgICAgICAgaWYgKChwcmV2WCA8IGxlZnRYKSA9PT0gKGxlZnRYIDw9IGN1cnJYKSkgewogICAgICAgICAgICAgICAgICAgICAgICB4MSA9IGxlZnRYIC0gcHJldlg7CiAgICAgICAgICAgICAgICAgICAgICAgIHgyID0gY3VyclggLSBwcmV2WDsKICAgICAgICAgICAgICAgICAgICAgICAgeTIgPSBjdXJyWSAtIHByZXZZOwogICAgICAgICAgICAgICAgICAgICAgICB5MSA9IHgxICogeTIgLyB4MjsKICAgICAgICAgICAgICAgICAgICAgICAgaW50ZXJzZWN0aW9uUG9pbnRzLmxlZnQucHVzaCh7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB4OiBsZWZ0WCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHk6IHlTY2FsZS5pbnZlcnQocHJldlkgKyB5MSksCiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBJZiB2YWx1ZXMgY3Jvc3NlZCByaWdodCBlZGdlCiAgICAgICAgICAgICAgICAgICAgaWYgKChwcmV2WCA8IHJpZ2h0WCkgPT09IChyaWdodFggPD0gY3VyclgpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHgxID0gcmlnaHRYIC0gcHJldlg7CiAgICAgICAgICAgICAgICAgICAgICAgIHgyID0gY3VyclggLSBwcmV2WDsKICAgICAgICAgICAgICAgICAgICAgICAgeTIgPSBjdXJyWSAtIHByZXZZOwogICAgICAgICAgICAgICAgICAgICAgICB5MSA9IHgxICogeTIgLyB4MjsKICAgICAgICAgICAgICAgICAgICAgICAgaW50ZXJzZWN0aW9uUG9pbnRzLnJpZ2h0LnB1c2goewogICAgICAgICAgICAgICAgICAgICAgICAgICAgeDogcmlnaHRYLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgeTogeVNjYWxlLmludmVydChwcmV2WSArIHkxKSwKICAgICAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIC8vIElmIHZhbHVlcyBjcm9zc2VkIHVwcGVyIGVkZ2UKICAgICAgICAgICAgICAgICAgICBpZiAoKHByZXZZIDwgdG9wWSkgPT09ICh0b3BZIDw9IGN1cnJZKSkgewogICAgICAgICAgICAgICAgICAgICAgICB4MiA9IGN1cnJYIC0gcHJldlg7CiAgICAgICAgICAgICAgICAgICAgICAgIHkxID0gdG9wWSAtIHByZXZZOwogICAgICAgICAgICAgICAgICAgICAgICB5MiA9IGN1cnJZIC0gcHJldlk7CiAgICAgICAgICAgICAgICAgICAgICAgIHgxID0geTEgKiB4MiAvIHkyOwogICAgICAgICAgICAgICAgICAgICAgICBpbnRlcnNlY3Rpb25Qb2ludHMudG9wLnB1c2goewogICAgICAgICAgICAgICAgICAgICAgICAgICAgeDogeFNjYWxlLmludmVydChwcmV2WCArIHgxKSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHk6IHRvcFksCiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBJZiB2YWx1ZXMgY3Jvc3NlZCBsb3dlciBlZGdlCiAgICAgICAgICAgICAgICAgICAgaWYgKChwcmV2WSA8IGJvdHRvbVkpID09PSAoYm90dG9tWSA8PSBjdXJyWSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgeDIgPSBjdXJyWCAtIHByZXZYOwogICAgICAgICAgICAgICAgICAgICAgICB5MSA9IGJvdHRvbVkgLSBwcmV2WTsKICAgICAgICAgICAgICAgICAgICAgICAgeTIgPSBjdXJyWSAtIHByZXZZOwogICAgICAgICAgICAgICAgICAgICAgICB4MSA9IHkxICogeDIgLyB5MjsKICAgICAgICAgICAgICAgICAgICAgICAgaW50ZXJzZWN0aW9uUG9pbnRzLmJvdHRvbS5wdXNoKHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHg6IHhTY2FsZS5pbnZlcnQocHJldlggKyB4MSksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB5OiBib3R0b21ZLAogICAgICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gaW50ZXJzZWN0aW9uUG9pbnRzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX2dldFJlc2V0WUZ1bmN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAvLyBnZXRzIHRoZSB5LXZhbHVlIGdlbmVyYXRvciBmb3IgdGhlIGFuaW1hdGlvbiBzdGFydCBwb2ludAogICAgICAgICAgICB2YXIgeURvbWFpbiA9IHRoaXMueSgpLnNjYWxlLmRvbWFpbigpOwogICAgICAgICAgICB2YXIgZG9tYWluTWF4ID0gTWF0aC5tYXgoeURvbWFpblswXSwgeURvbWFpblsxXSk7CiAgICAgICAgICAgIHZhciBkb21haW5NaW4gPSBNYXRoLm1pbih5RG9tYWluWzBdLCB5RG9tYWluWzFdKTsKICAgICAgICAgICAgLy8gc3RhcnQgZnJvbSB6ZXJvLCBvciB0aGUgY2xvc2VzdCBkb21haW4gdmFsdWUgdG8gemVybwogICAgICAgICAgICAvLyBhdm9pZHMgbGluZXMgem9vbWluZyBvbiBmcm9tIG9mZnNjcmVlbi4KICAgICAgICAgICAgdmFyIHN0YXJ0VmFsdWUgPSAoZG9tYWluTWF4IDwgMCAmJiBkb21haW5NYXgpIHx8IChkb21haW5NaW4gPiAwICYmIGRvbWFpbk1pbikgfHwgMDsKICAgICAgICAgICAgdmFyIHNjYWxlZFN0YXJ0VmFsdWUgPSB0aGlzLnkoKS5zY2FsZS5zY2FsZShzdGFydFZhbHVlKTsKICAgICAgICAgICAgcmV0dXJuIGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBzY2FsZWRTdGFydFZhbHVlOyB9OwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX2dlbmVyYXRlRHJhd1N0ZXBzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgZHJhd1N0ZXBzID0gW107CiAgICAgICAgICAgIGlmICh0aGlzLl9hbmltYXRlT25OZXh0UmVuZGVyKCkpIHsKICAgICAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsiZCJdID0gdGhpcy5fY29uc3RydWN0TGluZVByb2plY3RvcihwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKSwgdGhpcy5fZ2V0UmVzZXRZRnVuY3Rpb24oKSk7CiAgICAgICAgICAgICAgICBkcmF3U3RlcHMucHVzaCh7IGF0dHJUb1Byb2plY3RvcjogYXR0clRvUHJvamVjdG9yLCBhbmltYXRvcjogdGhpcy5fZ2V0QW5pbWF0b3IocGxvdHMuQW5pbWF0b3IuUkVTRVQpIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGRyYXdTdGVwcy5wdXNoKHsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvcjogdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCksCiAgICAgICAgICAgICAgICBhbmltYXRvcjogdGhpcy5fZ2V0QW5pbWF0b3IocGxvdHMuQW5pbWF0b3IuTUFJTiksCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gZHJhd1N0ZXBzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gX3N1cGVyLnByb3RvdHlwZS5fZ2VuZXJhdGVBdHRyVG9Qcm9qZWN0b3IuY2FsbCh0aGlzKTsKICAgICAgICAgICAgT2JqZWN0LmtleXMoYXR0clRvUHJvamVjdG9yKS5mb3JFYWNoKGZ1bmN0aW9uIChhdHRyaWJ1dGUpIHsKICAgICAgICAgICAgICAgIGlmIChhdHRyaWJ1dGUgPT09ICJkIikgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBwcm9qZWN0b3IgPSBhdHRyVG9Qcm9qZWN0b3JbYXR0cmlidXRlXTsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclthdHRyaWJ1dGVdID0gZnVuY3Rpb24gKGRhdGEsIGksIGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZGF0YS5sZW5ndGggPiAwID8gcHJvamVjdG9yKGRhdGFbMF0sIGksIGRhdGFzZXQpIDogbnVsbDsKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuZW50aXRpZXNBdCA9IGZ1bmN0aW9uIChwb2ludCkgewogICAgICAgICAgICB2YXIgZW50aXR5ID0gdGhpcy5lbnRpdHlOZWFyZXN0QnlYVGhlblkocG9pbnQpOwogICAgICAgICAgICBpZiAoZW50aXR5ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBbZW50aXR5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0aGUgUGxvdEVudGl0eSBuZWFyZXN0IHRvIHRoZSBxdWVyeSBwb2ludCBieSBYIHRoZW4gYnkgWSwgb3IgdW5kZWZpbmVkIGlmIG5vIFBsb3RFbnRpdHkgY2FuIGJlIGZvdW5kLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQb2ludH0gcXVlcnlQb2ludAogICAgICAgICAqIEByZXR1cm5zIHtQbG90RW50aXR5fSBUaGUgbmVhcmVzdCBQbG90RW50aXR5LCBvciB1bmRlZmluZWQgaWYgbm8gUGxvdEVudGl0eSBjYW4gYmUgZm91bmQuCiAgICAgICAgICovCiAgICAgICAgTGluZS5wcm90b3R5cGUuZW50aXR5TmVhcmVzdEJ5WFRoZW5ZID0gZnVuY3Rpb24gKHF1ZXJ5UG9pbnQpIHsKICAgICAgICAgICAgdmFyIG1pblhEaXN0ID0gSW5maW5pdHk7CiAgICAgICAgICAgIHZhciBtaW5ZRGlzdCA9IEluZmluaXR5OwogICAgICAgICAgICB2YXIgY2xvc2VzdDsKICAgICAgICAgICAgdmFyIGNoYXJ0Qm91bmRzID0gdGhpcy5ib3VuZHMoKTsKICAgICAgICAgICAgdmFyIGVudGl0aWVzID0gdGhpcy5lbnRpdGllcygpOwogICAgICAgICAgICB2YXIgZW50aXR5TGVuID0gZW50aXRpZXMubGVuZ3RoOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGVudGl0eUxlbjsgaSsrKSB7CiAgICAgICAgICAgICAgICB2YXIgZW50aXR5ID0gZW50aXRpZXNbaV07CiAgICAgICAgICAgICAgICBpZiAoIXV0aWxzJDEuTWF0aC53aXRoaW4oZW50aXR5LnBvc2l0aW9uLCBjaGFydEJvdW5kcykpIHsKICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciB4RGlzdCA9IE1hdGguYWJzKHF1ZXJ5UG9pbnQueCAtIGVudGl0eS5wb3NpdGlvbi54KTsKICAgICAgICAgICAgICAgIHZhciB5RGlzdCA9IE1hdGguYWJzKHF1ZXJ5UG9pbnQueSAtIGVudGl0eS5wb3NpdGlvbi55KTsKICAgICAgICAgICAgICAgIGlmICh4RGlzdCA8IG1pblhEaXN0IHx8IHhEaXN0ID09PSBtaW5YRGlzdCAmJiB5RGlzdCA8IG1pbllEaXN0KSB7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdCA9IGVudGl0eTsKICAgICAgICAgICAgICAgICAgICBtaW5YRGlzdCA9IHhEaXN0OwogICAgICAgICAgICAgICAgICAgIG1pbllEaXN0ID0geURpc3Q7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGNsb3Nlc3Q7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5fcHJvcGVydHlQcm9qZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgcHJvcGVydHlUb1Byb2plY3RvcnMgPSBfc3VwZXIucHJvdG90eXBlLl9wcm9wZXJ0eVByb2plY3RvcnMuY2FsbCh0aGlzKTsKICAgICAgICAgICAgcHJvcGVydHlUb1Byb2plY3RvcnNbImQiXSA9IHRoaXMuX2NvbnN0cnVjdExpbmVQcm9qZWN0b3IocGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLngoKSksIHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55KCkpKTsKICAgICAgICAgICAgcmV0dXJuIHByb3BlcnR5VG9Qcm9qZWN0b3JzOwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX2NvbnN0cnVjdExpbmVQcm9qZWN0b3IgPSBmdW5jdGlvbiAoeFByb2plY3RvciwgeVByb2plY3RvcikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9kM0xpbmVGYWN0b3J5KGRhdGFzZXQsIHhQcm9qZWN0b3IsIHlQcm9qZWN0b3IpKGRhdHVtKTsKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiBhIGQzLkxpbmUgd2hvc2UgLngsIC55LCBhbmQgLmRlZmluZWQgYWNjZXNzb3JzIGFyZSBob29rZWQgdXAgdG8gdGhlIHhQcm9qZWN0b3IgYW5kIHlQcm9qZWN0b3IKICAgICAgICAgKiBhZnRlciB0aGV5J3ZlIGJlZW4gZmVkIHRoZSBkYXRhc2V0LCBhbmQgd2hvc2UgY3VydmUgaXMgY29uZmlndXJlZCB0byB0aGlzIHBsb3QncyBjdXJ2ZS4KICAgICAgICAgKiBAcGFyYW0gZGF0YXNldAogICAgICAgICAqIEBwYXJhbSB4UHJvamVjdG9yCiAgICAgICAgICogQHBhcmFtIHlQcm9qZWN0b3IKICAgICAgICAgKiBAcmV0dXJucyB7TGluZTxbbnVtYmVyLG51bWJlcl0+fQogICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICovCiAgICAgICAgTGluZS5wcm90b3R5cGUuX2QzTGluZUZhY3RvcnkgPSBmdW5jdGlvbiAoZGF0YXNldCwgeFByb2plY3RvciwgeVByb2plY3RvcikgewogICAgICAgICAgICBpZiAoeFByb2plY3RvciA9PT0gdm9pZCAwKSB7IHhQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsgfQogICAgICAgICAgICBpZiAoeVByb2plY3RvciA9PT0gdm9pZCAwKSB7IHlQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKTsgfQogICAgICAgICAgICB2YXIgZGVmaW5lZFByb2plY3RvciA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpb25YID0geFByb2plY3RvcihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBwb3NpdGlvblkgPSB5UHJvamVjdG9yKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHBvc2l0aW9uWCkgJiYgdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIocG9zaXRpb25ZKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIGQzLmxpbmUoKQogICAgICAgICAgICAgICAgLngoZnVuY3Rpb24gKGlubmVyRGF0dW0sIGlubmVySW5kZXgpIHsgcmV0dXJuIHhQcm9qZWN0b3IoaW5uZXJEYXR1bSwgaW5uZXJJbmRleCwgZGF0YXNldCk7IH0pCiAgICAgICAgICAgICAgICAueShmdW5jdGlvbiAoaW5uZXJEYXR1bSwgaW5uZXJJbmRleCkgeyByZXR1cm4geVByb2plY3Rvcihpbm5lckRhdHVtLCBpbm5lckluZGV4LCBkYXRhc2V0KTsgfSkKICAgICAgICAgICAgICAgIC5jdXJ2ZSh0aGlzLl9nZXRDdXJ2ZUZhY3RvcnkoKSkKICAgICAgICAgICAgICAgIC5kZWZpbmVkKGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiBkZWZpbmVkUHJvamVjdG9yKGlubmVyRGF0dW0sIGlubmVySW5kZXgsIGRhdGFzZXQpOyB9KTsKICAgICAgICB9OwogICAgICAgIExpbmUucHJvdG90eXBlLl9nZXRDdXJ2ZUZhY3RvcnkgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBjdXJ2ZSA9IHRoaXMuY3VydmUoKTsKICAgICAgICAgICAgaWYgKHR5cGVvZiBjdXJ2ZSA9PT0gInN0cmluZyIpIHsKICAgICAgICAgICAgICAgIHZhciBtYXliZUN1cnZlRnVuY3Rpb24gPSBDVVJWRV9OQU1FX01BUFBJTkdbY3VydmVdOwogICAgICAgICAgICAgICAgaWYgKG1heWJlQ3VydmVGdW5jdGlvbiA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gb29wczsgbmFtZSBpcyB3cm9uZyAtIGRlZmF1bHQgdG8gbGluZWFyIGluc3RlYWQKICAgICAgICAgICAgICAgICAgICByZXR1cm4gQ1VSVkVfTkFNRV9NQVBQSU5HWyJsaW5lYXIiXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBtYXliZUN1cnZlRnVuY3Rpb247CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY3VydmU7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIExpbmUgcGxvdHMgcmVwcmVzZW50IGVhY2ggZGF0YXNldCB3aXRoIGEgc2luZ2xlIDxwYXRoPiBlbGVtZW50LCBzbyB3ZSB3cmFwIHRoZSBkYXRhc2V0IGRhdGEgaW4gYSBzaW5nbGUgZWxlbWVudCBhcnJheS4KICAgICAgICAgKiBAcmV0dXJucyB7TWFwPERhdGFzZXQsIGFueVtdPn0KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIExpbmUucHJvdG90eXBlLl9nZXREYXRhVG9EcmF3ID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgZGF0YVRvRHJhdyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKTsKICAgICAgICAgICAgICAgIGlmICghX3RoaXMuX2Nyb3BwZWRSZW5kZXJpbmdFbmFibGVkICYmICFfdGhpcy5fZG93bnNhbXBsaW5nRW5hYmxlZCkgewogICAgICAgICAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRhdGFzZXQsIFtkYXRhXSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIGZpbHRlcmVkRGF0YUluZGljZXMgPSBbXTsKICAgICAgICAgICAgICAgIHZhciBkYXRhTGVuID0gZGF0YS5sZW5ndGg7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGRhdGFMZW47IGkrKykgewogICAgICAgICAgICAgICAgICAgIGZpbHRlcmVkRGF0YUluZGljZXNbaV0gPSBpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKF90aGlzLl9jcm9wcGVkUmVuZGVyaW5nRW5hYmxlZCkgewogICAgICAgICAgICAgICAgICAgIGZpbHRlcmVkRGF0YUluZGljZXMgPSBfdGhpcy5fZmlsdGVyQ3JvcHBlZFJlbmRlcmluZyhkYXRhc2V0LCBmaWx0ZXJlZERhdGFJbmRpY2VzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChfdGhpcy5fZG93bnNhbXBsaW5nRW5hYmxlZCkgewogICAgICAgICAgICAgICAgICAgIGZpbHRlcmVkRGF0YUluZGljZXMgPSBfdGhpcy5fZmlsdGVyRG93bnNhbXBsaW5nKGRhdGFzZXQsIGZpbHRlcmVkRGF0YUluZGljZXMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKF90aGlzLl9jb2xsYXBzZURlbnNlVmVydGljYWxMaW5lc0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJlZERhdGFJbmRpY2VzID0gX3RoaXMuX2ZpbHRlckRlbnNlTGluZXMoZGF0YXNldCwgZmlsdGVyZWREYXRhSW5kaWNlcyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgZmlsdGVyZWREYXRhID0gW107CiAgICAgICAgICAgICAgICB2YXIgZmlsdGVyZWRJbmRpY2VzTGVuID0gZmlsdGVyZWREYXRhSW5kaWNlcy5sZW5ndGg7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGZpbHRlcmVkSW5kaWNlc0xlbjsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGluZGV4ID0gZmlsdGVyZWREYXRhSW5kaWNlc1tpXTsKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJlZERhdGFbaV0gPSBkYXRhW2luZGV4XTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRhdGFzZXQsIFtmaWx0ZXJlZERhdGFdKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkYXRhVG9EcmF3OwogICAgICAgIH07CiAgICAgICAgTGluZS5wcm90b3R5cGUuX2ZpbHRlckNyb3BwZWRSZW5kZXJpbmcgPSBmdW5jdGlvbiAoZGF0YXNldCwgaW5kaWNlcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgeFByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpOwogICAgICAgICAgICB2YXIgeVByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55KCkpOwogICAgICAgICAgICB2YXIgZGF0YSA9IGRhdGFzZXQuZGF0YSgpOwogICAgICAgICAgICB2YXIgZmlsdGVyZWREYXRhSW5kaWNlcyA9IFtdOwogICAgICAgICAgICB2YXIgcG9pbnRJblZpZXdwb3J0ID0gZnVuY3Rpb24gKHgsIHkpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGguaW5SYW5nZSh4LCAwLCBfdGhpcy53aWR0aCgpKSAmJgogICAgICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5pblJhbmdlKHksIDAsIF90aGlzLmhlaWdodCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBpbmRpY2VzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICB2YXIgY3VyclhQb2ludCA9IHhQcm9qZWN0b3IoZGF0YVtpbmRpY2VzW2ldXSwgaW5kaWNlc1tpXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgY3VycllQb2ludCA9IHlQcm9qZWN0b3IoZGF0YVtpbmRpY2VzW2ldXSwgaW5kaWNlc1tpXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgc2hvdWxkU2hvdyA9IHBvaW50SW5WaWV3cG9ydChjdXJyWFBvaW50LCBjdXJyWVBvaW50KTsKICAgICAgICAgICAgICAgIGlmICghc2hvdWxkU2hvdyAmJiBpbmRpY2VzW2kgLSAxXSAhPSBudWxsICYmIGRhdGFbaW5kaWNlc1tpIC0gMV1dICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgcHJldlhQb2ludCA9IHhQcm9qZWN0b3IoZGF0YVtpbmRpY2VzW2kgLSAxXV0sIGluZGljZXNbaSAtIDFdLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgICAgICB2YXIgcHJldllQb2ludCA9IHlQcm9qZWN0b3IoZGF0YVtpbmRpY2VzW2kgLSAxXV0sIGluZGljZXNbaSAtIDFdLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgICAgICBzaG91bGRTaG93ID0gc2hvdWxkU2hvdyB8fCBwb2ludEluVmlld3BvcnQocHJldlhQb2ludCwgcHJldllQb2ludCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoIXNob3VsZFNob3cgJiYgaW5kaWNlc1tpICsgMV0gIT0gbnVsbCAmJiBkYXRhW2luZGljZXNbaSArIDFdXSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIG5leHRYUG9pbnQgPSB4UHJvamVjdG9yKGRhdGFbaW5kaWNlc1tpICsgMV1dLCBpbmRpY2VzW2kgKyAxXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIG5leHRZUG9pbnQgPSB5UHJvamVjdG9yKGRhdGFbaW5kaWNlc1tpICsgMV1dLCBpbmRpY2VzW2kgKyAxXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgc2hvdWxkU2hvdyA9IHNob3VsZFNob3cgfHwgcG9pbnRJblZpZXdwb3J0KG5leHRYUG9pbnQsIG5leHRZUG9pbnQpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKHNob3VsZFNob3cpIHsKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJlZERhdGFJbmRpY2VzLnB1c2goaW5kaWNlc1tpXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZpbHRlcmVkRGF0YUluZGljZXM7CiAgICAgICAgfTsKICAgICAgICBMaW5lLnByb3RvdHlwZS5fZmlsdGVyRG93bnNhbXBsaW5nID0gZnVuY3Rpb24gKGRhdGFzZXQsIGluZGljZXMpIHsKICAgICAgICAgICAgaWYgKGluZGljZXMubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKTsKICAgICAgICAgICAgdmFyIHNjYWxlZFhBY2Nlc3NvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpOwogICAgICAgICAgICB2YXIgc2NhbGVkWUFjY2Vzc29yID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkoKSk7CiAgICAgICAgICAgIHZhciBmaWx0ZXJlZEluZGljZXMgPSBbaW5kaWNlc1swXV07CiAgICAgICAgICAgIHZhciBpbmRleE9uQ3VycmVudFNsb3BlID0gZnVuY3Rpb24gKGksIGN1cnJlbnRTbG9wZSkgewogICAgICAgICAgICAgICAgdmFyIHAxeCA9IHNjYWxlZFhBY2Nlc3NvcihkYXRhW2luZGljZXNbaV1dLCBpbmRpY2VzW2ldLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBwMXkgPSBzY2FsZWRZQWNjZXNzb3IoZGF0YVtpbmRpY2VzW2ldXSwgaW5kaWNlc1tpXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgcDJ4ID0gc2NhbGVkWEFjY2Vzc29yKGRhdGFbaW5kaWNlc1tpICsgMV1dLCBpbmRpY2VzW2kgKyAxXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgcDJ5ID0gc2NhbGVkWUFjY2Vzc29yKGRhdGFbaW5kaWNlc1tpICsgMV1dLCBpbmRpY2VzW2kgKyAxXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICBpZiAoY3VycmVudFNsb3BlID09PSBJbmZpbml0eSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLmZsb29yKHAxeCkgPT09IE1hdGguZmxvb3IocDJ4KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHZhciBleHBlY3RlZFAyeSA9IHAxeSArIChwMnggLSBwMXgpICogY3VycmVudFNsb3BlOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLmZsb29yKHAyeSkgPT09IE1hdGguZmxvb3IoZXhwZWN0ZWRQMnkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGluZGljZXMubGVuZ3RoIC0gMTspIHsKICAgICAgICAgICAgICAgIHZhciBpbmRleEZpcnN0ID0gaW5kaWNlc1tpXTsKICAgICAgICAgICAgICAgIHZhciBwMXggPSBzY2FsZWRYQWNjZXNzb3IoZGF0YVtpbmRpY2VzW2ldXSwgaW5kaWNlc1tpXSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgcDF5ID0gc2NhbGVkWUFjY2Vzc29yKGRhdGFbaW5kaWNlc1tpXV0sIGluZGljZXNbaV0sIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIHAyeCA9IHNjYWxlZFhBY2Nlc3NvcihkYXRhW2luZGljZXNbaSArIDFdXSwgaW5kaWNlc1tpICsgMV0sIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIHAyeSA9IHNjYWxlZFlBY2Nlc3NvcihkYXRhW2luZGljZXNbaSArIDFdXSwgaW5kaWNlc1tpICsgMV0sIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIGN1cnJlbnRTbG9wZSA9IChNYXRoLmZsb29yKHAxeCkgPT09IE1hdGguZmxvb3IocDJ4KSkgPyBJbmZpbml0eSA6IChwMnkgLSBwMXkpIC8gKHAyeCAtIHAxeCk7CiAgICAgICAgICAgICAgICB2YXIgaW5kZXhNaW4gPSBpbmRpY2VzW2ldOwogICAgICAgICAgICAgICAgdmFyIG1pblNjYWxlZFZhbHVlID0gKGN1cnJlbnRTbG9wZSA9PT0gSW5maW5pdHkpID8gcDF5IDogcDF4OwogICAgICAgICAgICAgICAgdmFyIGluZGV4TWF4ID0gaW5kZXhNaW47CiAgICAgICAgICAgICAgICB2YXIgbWF4U2NhbGVkVmFsdWUgPSBtaW5TY2FsZWRWYWx1ZTsKICAgICAgICAgICAgICAgIHZhciBmaXJzdEluZGV4T25DdXJyZW50U2xvcGUgPSB0cnVlOwogICAgICAgICAgICAgICAgd2hpbGUgKGkgPCBpbmRpY2VzLmxlbmd0aCAtIDEgJiYgKGZpcnN0SW5kZXhPbkN1cnJlbnRTbG9wZSB8fCBpbmRleE9uQ3VycmVudFNsb3BlKGksIGN1cnJlbnRTbG9wZSkpKSB7CiAgICAgICAgICAgICAgICAgICAgaSsrOwogICAgICAgICAgICAgICAgICAgIGZpcnN0SW5kZXhPbkN1cnJlbnRTbG9wZSA9IGZhbHNlOwogICAgICAgICAgICAgICAgICAgIHZhciBjdXJyU2NhbGVkVmFsdWUgPSBjdXJyZW50U2xvcGUgPT09IEluZmluaXR5ID8gc2NhbGVkWUFjY2Vzc29yKGRhdGFbaW5kaWNlc1tpXV0sIGluZGljZXNbaV0sIGRhdGFzZXQpIDoKICAgICAgICAgICAgICAgICAgICAgICAgc2NhbGVkWEFjY2Vzc29yKGRhdGFbaW5kaWNlc1tpXV0sIGluZGljZXNbaV0sIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIGlmIChjdXJyU2NhbGVkVmFsdWUgPiBtYXhTY2FsZWRWYWx1ZSkgewogICAgICAgICAgICAgICAgICAgICAgICBtYXhTY2FsZWRWYWx1ZSA9IGN1cnJTY2FsZWRWYWx1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgaW5kZXhNYXggPSBpbmRpY2VzW2ldOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpZiAoY3VyclNjYWxlZFZhbHVlIDwgbWluU2NhbGVkVmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgbWluU2NhbGVkVmFsdWUgPSBjdXJyU2NhbGVkVmFsdWU7CiAgICAgICAgICAgICAgICAgICAgICAgIGluZGV4TWluID0gaW5kaWNlc1tpXTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgaW5kZXhMYXN0ID0gaW5kaWNlc1tpXTsKICAgICAgICAgICAgICAgIGlmIChpbmRleE1pbiAhPT0gaW5kZXhGaXJzdCkgewogICAgICAgICAgICAgICAgICAgIGZpbHRlcmVkSW5kaWNlcy5wdXNoKGluZGV4TWluKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChpbmRleE1heCAhPT0gaW5kZXhNaW4gJiYgaW5kZXhNYXggIT09IGluZGV4Rmlyc3QpIHsKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJlZEluZGljZXMucHVzaChpbmRleE1heCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoaW5kZXhMYXN0ICE9PSBpbmRleEZpcnN0ICYmIGluZGV4TGFzdCAhPT0gaW5kZXhNaW4gJiYgaW5kZXhMYXN0ICE9PSBpbmRleE1heCkgewogICAgICAgICAgICAgICAgICAgIGZpbHRlcmVkSW5kaWNlcy5wdXNoKGluZGV4TGFzdCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZpbHRlcmVkSW5kaWNlczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIENvbGxhcHNlIGxpbmUgZ2VvbWV0cnkKICAgICAgICAgKgogICAgICAgICAqIEFzc3VtaW5nIHRoYXQgdGhlcmUgYXJlIG1hbnkgcG9pbnRzIHRoYXQgYXJlIGRyYXduIG9uIHRoZSBzYW1lIGNvb3JkaW5hdGUsCiAgICAgICAgICogd2UgY2FuIHNhdmUgYSBsb3Qgb2YgcmVuZGVyIHRpbWUgYnkganVzdCBkcmF3aW5nIG9uZSBsaW5lIGZyb20gdGhlIG1pbiB0bwogICAgICAgICAqIG1heCB5LWNvb3JkaW5hdGUgb2YgYWxsIHRob3NlIHBvaW50cy4KICAgICAgICAgKi8KICAgICAgICBMaW5lLnByb3RvdHlwZS5fZmlsdGVyRGVuc2VMaW5lcyA9IGZ1bmN0aW9uIChkYXRhc2V0LCBpbmRpY2VzKSB7CiAgICAgICAgICAgIGlmIChpbmRpY2VzLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YXNldC5kYXRhKCk7CiAgICAgICAgICAgIHZhciBzY2FsZWRYQWNjZXNzb3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsKICAgICAgICAgICAgdmFyIHNjYWxlZFlBY2Nlc3NvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55KCkpOwogICAgICAgICAgICB2YXIgeEZuID0gZnVuY3Rpb24gKGkpIHsgcmV0dXJuIHNjYWxlZFhBY2Nlc3NvcihkYXRhW2ldLCBpLCBkYXRhc2V0KTsgfTsKICAgICAgICAgICAgdmFyIHlGbiA9IGZ1bmN0aW9uIChpKSB7IHJldHVybiBzY2FsZWRZQWNjZXNzb3IoZGF0YVtpXSwgaSwgZGF0YXNldCk7IH07CiAgICAgICAgICAgIC8vIFRPRE8gZGV0ZXJtaW5lIGlmIHdlIHNob3VsZCBjb2xsYXBzZSB4IG9yIHkgb3Igbm90IGNvbGxhcHNlIGF0IGFsbC4KICAgICAgICAgICAgLy8gRm9yIG5vdywgd2UgYXNzdW1lIGxpbmUgY2hhcnRzIGFyZSBhbHdheXMgYSBmdW5jdGlvbiBvZiB4CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9idWNrZXRCeVgoZGF0YXNldCwgaW5kaWNlcywgeEZuLCB5Rm4pOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogSXRlcmF0ZXMgb3ZlciB0aGUgbGluZSBwb2ludHMgY29sbGFwc2luZyBwb2ludHMgdGhhdCBmYWxsIG9uIHRoZSBzYW1lCiAgICAgICAgICogZmxvb3JlZCB4IGNvb3JkaW5hdGUuCiAgICAgICAgICoKICAgICAgICAgKiBPbmNlIGFsbCB0aGUgcG9pbnRzIHdpdGggdGhlIHNhbWUgeCBjb29yZGluYXRlIGFyZSBkZXRlY3RlZCwgd2UgZHJhdyBhCiAgICAgICAgICogc2luZ2xlIGxpbmUgZnJvbSB0aGUgbWluIHRvIG1heCB5IGNvb3JpbmRhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgImVudHJhbmNlIiBhbmQgImV4aXQiIGxpbmVzIHRvL2Zyb20gdGhpcyBjb2xsYXBzZWQgdmVydGljYWwgbGluZSBhcmUKICAgICAgICAgKiBhbHNvIGRyYXduLiBUaGlzIGFsbG93cyBsaW5lcyB3aXRoIG5vIGNvbGxhcHNlZCBzZWdtZW50cyB0byByZW5kZXIKICAgICAgICAgKiBjb3JyZWN0bHkuCiAgICAgICAgICovCiAgICAgICAgTGluZS5wcm90b3R5cGUuX2J1Y2tldEJ5WCA9IGZ1bmN0aW9uIChkYXRhc2V0LCBpbmRpY2VzLCB4Rm4sIHlGbikgewogICAgICAgICAgICB2YXIgZmlsdGVyZWRJbmRpY2VzID0gW107CiAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YXNldC5kYXRhKCk7CiAgICAgICAgICAgIHZhciBidWNrZXQgPSBudWxsOwogICAgICAgICAgICB2YXIgaW5kaWNlc0xlbmd0aCA9IGluZGljZXMubGVuZ3RoOwogICAgICAgICAgICBmb3IgKHZhciBpaSA9IDA7IGlpIDw9IGluZGljZXNMZW5ndGg7ICsraWkpIHsKICAgICAgICAgICAgICAgIHZhciBpID0gaW5kaWNlc1tpaV07CiAgICAgICAgICAgICAgICBpZiAoZGF0YVtpXSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgeCA9IE1hdGguZmxvb3IoeEZuKGkpKTsKICAgICAgICAgICAgICAgIHZhciB5ID0geUZuKGkpOwogICAgICAgICAgICAgICAgaWYgKGJ1Y2tldCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgYnVja2V0ID0gbmV3IHV0aWxzJDEuQnVja2V0KGksIHgsIHkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoYnVja2V0LmlzSW5CdWNrZXQoeCkpIHsKICAgICAgICAgICAgICAgICAgICBidWNrZXQuYWRkVG9CdWNrZXQoeSwgaSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJlZEluZGljZXMucHVzaC5hcHBseShmaWx0ZXJlZEluZGljZXMsIGJ1Y2tldC5nZXRVbmlxdWVJbmRpY2VzKCkpOwogICAgICAgICAgICAgICAgICAgIGJ1Y2tldCA9IG5ldyB1dGlscyQxLkJ1Y2tldChpLCB4LCB5KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoYnVja2V0ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGZpbHRlcmVkSW5kaWNlcy5wdXNoLmFwcGx5KGZpbHRlcmVkSW5kaWNlcywgYnVja2V0LmdldFVuaXF1ZUluZGljZXMoKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZpbHRlcmVkSW5kaWNlczsKICAgICAgICB9OwogICAgICAgIHJldHVybiBMaW5lOwogICAgfSh4eVBsb3QuWFlQbG90KSk7CiAgICBleHBvcnRzLkxpbmUgPSBMaW5lOwogICAgfSk7CgogICAgdmFyIGFyZWFQbG90ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCgoKCgoKICAgIHZhciBBcmVhID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQXJlYSwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBbiBBcmVhIFBsb3QgZHJhd3MgYSBmaWxsZWQgcmVnaW9uIChhcmVhKSBiZXR3ZWVuIFkgYW5kIFkwLgogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gQXJlYSgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuYWRkQ2xhc3MoImFyZWEtcGxvdCIpOwogICAgICAgICAgICBfdGhpcy55MCgwKTsgLy8gZGVmYXVsdAogICAgICAgICAgICBfdGhpcy5hdHRyKCJmaWxsLW9wYWNpdHkiLCAwLjI1KTsKICAgICAgICAgICAgX3RoaXMuYXR0cigiZmlsbCIsIG5ldyBzY2FsZXMuQ29sb3IoKS5yYW5nZSgpWzBdKTsKICAgICAgICAgICAgX3RoaXMuX2xpbmVEcmF3ZXJzID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgQXJlYS5wcm90b3R5cGUueSA9IGZ1bmN0aW9uICh5LCB5U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh5U2NhbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS55LmNhbGwodGhpcywgeSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzLCB5LCB5U2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh5U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIHkwID0gdGhpcy55MCgpLmFjY2Vzc29yOwogICAgICAgICAgICAgICAgaWYgKHkwICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoQXJlYS5fWTBfS0VZLCB5MCwgeVNjYWxlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVlTY2FsZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUueTAgPSBmdW5jdGlvbiAoeTApIHsKICAgICAgICAgICAgaWYgKHkwID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChBcmVhLl9ZMF9LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciB5QmluZGluZyA9IHRoaXMueSgpOwogICAgICAgICAgICB2YXIgeVNjYWxlID0geUJpbmRpbmcgJiYgeUJpbmRpbmcuc2NhbGU7CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShBcmVhLl9ZMF9LRVksIHkwLCB5U2NhbGUpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVZU2NhbGUoKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fb25EYXRhc2V0VXBkYXRlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9vbkRhdGFzZXRVcGRhdGUuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlWVNjYWxlKCk7CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fYWRkRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuX2xpbmVEcmF3ZXJzLnNldChkYXRhc2V0LCBuZXcgZHJhd2Vycy5Qcm94eURyYXdlcihmdW5jdGlvbiAoKSB7IHJldHVybiBuZXcgbGluZURyYXdlci5MaW5lU1ZHRHJhd2VyKCk7IH0sIGZ1bmN0aW9uIChjdHgpIHsgcmV0dXJuIG5ldyBkcmF3ZXJzLkNhbnZhc0RyYXdlcihjdHgsIGxpbmVEcmF3ZXIubWFrZUxpbmVDYW52YXNEcmF3U3RlcChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB2YXIgeFByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IoX3RoaXMueCgpKTsKICAgICAgICAgICAgICAgIHZhciB5UHJvamVjdG9yID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3NvcihfdGhpcy55KCkpOwogICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9kM0xpbmVGYWN0b3J5KGRhdGFzZXQsIHhQcm9qZWN0b3IsIHlQcm9qZWN0b3IpOwogICAgICAgICAgICB9KSk7IH0pKTsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fYWRkRGF0YXNldC5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGRyYXdlciA9IHRoaXMuX2xpbmVEcmF3ZXJzLmdldChkYXRhc2V0KTsKICAgICAgICAgICAgaWYgKHRoaXMucmVuZGVyZXIoKSA9PT0gInN2ZyIpIHsKICAgICAgICAgICAgICAgIGRyYXdlci51c2VTVkcodGhpcy5fcmVuZGVyQXJlYSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBkcmF3ZXIudXNlQ2FudmFzKHRoaXMuX2NhbnZhcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGRyYXdlcjsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0Tm9kZXMgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0Tm9kZXMuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdGhpcy5fbGluZURyYXdlcnMuZ2V0KGRhdGFzZXQpLnJlbW92ZSgpOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2FkZGl0aW9uYWxQYWludCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGRyYXdTdGVwcyA9IHRoaXMuX2dlbmVyYXRlTGluZURyYXdTdGVwcygpOwogICAgICAgICAgICB2YXIgZGF0YVRvRHJhdyA9IHRoaXMuX2dldERhdGFUb0RyYXcoKTsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIHZhciBhcHBsaWVkRHJhd1N0ZXBzID0gcGxvdC5QbG90LmFwcGx5RHJhd1N0ZXBzKGRyYXdTdGVwcywgZGF0YXNldCk7CiAgICAgICAgICAgICAgICBfdGhpcy5fbGluZURyYXdlcnMuZ2V0KGRhdGFzZXQpLmRyYXcoZGF0YVRvRHJhdy5nZXQoZGF0YXNldCksIGFwcGxpZWREcmF3U3RlcHMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLl9nZW5lcmF0ZUxpbmVEcmF3U3RlcHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBkcmF3U3RlcHMgPSBbXTsKICAgICAgICAgICAgaWYgKHRoaXMuX2FuaW1hdGVPbk5leHRSZW5kZXIoKSkgewogICAgICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dlbmVyYXRlTGluZUF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJkIl0gPSB0aGlzLl9jb25zdHJ1Y3RMaW5lUHJvamVjdG9yKHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpLCB0aGlzLl9nZXRSZXNldFlGdW5jdGlvbigpKTsKICAgICAgICAgICAgICAgIGRyYXdTdGVwcy5wdXNoKHsgYXR0clRvUHJvamVjdG9yOiBhdHRyVG9Qcm9qZWN0b3IsIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5SRVNFVCkgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZHJhd1N0ZXBzLnB1c2goewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yOiB0aGlzLl9nZW5lcmF0ZUxpbmVBdHRyVG9Qcm9qZWN0b3IoKSwKICAgICAgICAgICAgICAgIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5NQUlOKSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkcmF3U3RlcHM7CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fZ2VuZXJhdGVMaW5lQXR0clRvUHJvamVjdG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgbGluZUF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICBsaW5lQXR0clRvUHJvamVjdG9yWyJkIl0gPSB0aGlzLl9jb25zdHJ1Y3RMaW5lUHJvamVjdG9yKHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpLCBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKSk7CiAgICAgICAgICAgIHJldHVybiBsaW5lQXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2NyZWF0ZURyYXdlciA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHJldHVybiBuZXcgZHJhd2VyLlByb3h5RHJhd2VyKGZ1bmN0aW9uICgpIHsgcmV0dXJuIG5ldyBhcmVhRHJhd2VyLkFyZWFTVkdEcmF3ZXIoKTsgfSwgZnVuY3Rpb24gKGN0eCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXJzLkNhbnZhc0RyYXdlcihjdHgsIGFyZWFEcmF3ZXIubWFrZUFyZWFDYW52YXNEcmF3U3RlcChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIF9hID0gX3RoaXMuX2Nvb3JkaW5hdGVQcm9qZWN0b3JzKCksIHhQcm9qZWN0b3IgPSBfYVswXSwgeVByb2plY3RvciA9IF9hWzFdLCB5MFByb2plY3RvciA9IF9hWzJdOwogICAgICAgICAgICAgICAgICAgIHZhciBkZWZpbmVkUHJvamVjdG9yID0gX3RoaXMuX2NyZWF0ZURlZmluZWRQcm9qZWN0b3IoeFByb2plY3RvciwgeVByb2plY3Rvcik7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIF90aGlzLl9jcmVhdGVBcmVhR2VuZXJhdG9yKHhQcm9qZWN0b3IsIHlQcm9qZWN0b3IsIHkwUHJvamVjdG9yLCBkZWZpbmVkUHJvamVjdG9yLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIH0sIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgX2EgPSBfdGhpcy5fY29vcmRpbmF0ZVByb2plY3RvcnMoKSwgeFByb2plY3RvciA9IF9hWzBdLCB5UHJvamVjdG9yID0gX2FbMV07CiAgICAgICAgICAgICAgICAgICAgdmFyIGRlZmluZWRQcm9qZWN0b3IgPSBfdGhpcy5fY3JlYXRlRGVmaW5lZFByb2plY3Rvcih4UHJvamVjdG9yLCB5UHJvamVjdG9yKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2NyZWF0ZVRvcExpbmVHZW5lcmF0b3IoeFByb2plY3RvciwgeVByb2plY3RvciwgZGVmaW5lZFByb2plY3RvciwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2dlbmVyYXRlRHJhd1N0ZXBzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgZHJhd1N0ZXBzID0gW107CiAgICAgICAgICAgIGlmICh0aGlzLl9hbmltYXRlT25OZXh0UmVuZGVyKCkpIHsKICAgICAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsiZCJdID0gdGhpcy5fY29uc3RydWN0QXJlYVByb2plY3RvcihwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKSwgdGhpcy5fZ2V0UmVzZXRZRnVuY3Rpb24oKSwgcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkwKCkpKTsKICAgICAgICAgICAgICAgIGRyYXdTdGVwcy5wdXNoKHsgYXR0clRvUHJvamVjdG9yOiBhdHRyVG9Qcm9qZWN0b3IsIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5SRVNFVCkgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZHJhd1N0ZXBzLnB1c2goewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yOiB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKSwKICAgICAgICAgICAgICAgIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5NQUlOKSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkcmF3U3RlcHM7CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fdXBkYXRlWVNjYWxlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgZXh0ZW50cyA9IHRoaXMuZ2V0RXh0ZW50c0ZvclByb3BlcnR5KCJ5MCIpOwogICAgICAgICAgICB2YXIgZXh0ZW50ID0gdXRpbHMkMS5BcnJheS5mbGF0dGVuKGV4dGVudHMpOwogICAgICAgICAgICB2YXIgdW5pcUV4dGVudFZhbHMgPSB1dGlscyQxLkFycmF5LnVuaXEoZXh0ZW50KTsKICAgICAgICAgICAgdmFyIGNvbnN0YW50QmFzZWxpbmUgPSB1bmlxRXh0ZW50VmFscy5sZW5ndGggPT09IDEgPyB1bmlxRXh0ZW50VmFsc1swXSA6IG51bGw7CiAgICAgICAgICAgIHZhciB5QmluZGluZyA9IHRoaXMueSgpOwogICAgICAgICAgICB2YXIgeVNjYWxlID0gKHlCaW5kaW5nICYmIHlCaW5kaW5nLnNjYWxlKTsKICAgICAgICAgICAgaWYgKHlTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMuX2NvbnN0YW50QmFzZWxpbmVWYWx1ZVByb3ZpZGVyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHlTY2FsZS5yZW1vdmVQYWRkaW5nRXhjZXB0aW9uc1Byb3ZpZGVyKHRoaXMuX2NvbnN0YW50QmFzZWxpbmVWYWx1ZVByb3ZpZGVyKTsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbnN0YW50QmFzZWxpbmVWYWx1ZVByb3ZpZGVyID0gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoY29uc3RhbnRCYXNlbGluZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jb25zdGFudEJhc2VsaW5lVmFsdWVQcm92aWRlciA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIFtjb25zdGFudEJhc2VsaW5lXTsgfTsKICAgICAgICAgICAgICAgIHlTY2FsZS5hZGRQYWRkaW5nRXhjZXB0aW9uc1Byb3ZpZGVyKHRoaXMuX2NvbnN0YW50QmFzZWxpbmVWYWx1ZVByb3ZpZGVyKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2dldFJlc2V0WUZ1bmN0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkwKCkpOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2Nvb3JkaW5hdGVQcm9qZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gWwogICAgICAgICAgICAgICAgcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLngoKSksCiAgICAgICAgICAgICAgICBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKSwKICAgICAgICAgICAgICAgIHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55MCgpKSwKICAgICAgICAgICAgXTsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLl9wcm9wZXJ0eVByb2plY3RvcnMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBwcm9wZXJ0eVRvUHJvamVjdG9ycyA9IF9zdXBlci5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycy5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgX2EgPSB0aGlzLl9jb29yZGluYXRlUHJvamVjdG9ycygpLCB4UHJvamVjdCA9IF9hWzBdLCB5UHJvamVjdG9yID0gX2FbMV0sIHkwUHJvamVjdG9yID0gX2FbMl07CiAgICAgICAgICAgIHByb3BlcnR5VG9Qcm9qZWN0b3JzWyJkIl0gPSB0aGlzLl9jb25zdHJ1Y3RBcmVhUHJvamVjdG9yKHhQcm9qZWN0LCB5UHJvamVjdG9yLCB5MFByb2plY3Rvcik7CiAgICAgICAgICAgIHJldHVybiBwcm9wZXJ0eVRvUHJvamVjdG9yczsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLnNlbGVjdGlvbnMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKGRhdGFzZXRzID09PSB2b2lkIDApIHsgZGF0YXNldHMgPSB0aGlzLmRhdGFzZXRzKCk7IH0KICAgICAgICAgICAgaWYgKHRoaXMucmVuZGVyZXIoKSA9PT0gImNhbnZhcyIpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkMy5zZWxlY3RBbGwoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgYWxsU2VsZWN0aW9ucyA9IF9zdXBlci5wcm90b3R5cGUuc2VsZWN0aW9ucy5jYWxsKHRoaXMsIGRhdGFzZXRzKS5ub2RlcygpOwogICAgICAgICAgICB2YXIgbGluZURyYXdlcnMgPSBkYXRhc2V0cy5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9saW5lRHJhd2Vycy5nZXQoZGF0YXNldCk7IH0pCiAgICAgICAgICAgICAgICAuZmlsdGVyKGZ1bmN0aW9uIChkcmF3ZXIpIHsgcmV0dXJuIGRyYXdlciAhPSBudWxsOyB9KTsKICAgICAgICAgICAgbGluZURyYXdlcnMuZm9yRWFjaChmdW5jdGlvbiAobGQpIHsgcmV0dXJuIGFsbFNlbGVjdGlvbnMucHVzaC5hcHBseShhbGxTZWxlY3Rpb25zLCBsZC5nZXRWaXN1YWxQcmltaXRpdmVzKCkpOyB9KTsKICAgICAgICAgICAgcmV0dXJuIGQzLnNlbGVjdEFsbChhbGxTZWxlY3Rpb25zKTsKICAgICAgICB9OwogICAgICAgIEFyZWEucHJvdG90eXBlLl9jb25zdHJ1Y3RBcmVhUHJvamVjdG9yID0gZnVuY3Rpb24gKHhQcm9qZWN0b3IsIHlQcm9qZWN0b3IsIHkwUHJvamVjdG9yKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBkZWZpbmVkUHJvamVjdG9yID0gdGhpcy5fY3JlYXRlRGVmaW5lZFByb2plY3RvcihwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKSwgcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkoKSkpOwogICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGFyZWFHZW5lcmF0b3IgPSBfdGhpcy5fY3JlYXRlQXJlYUdlbmVyYXRvcih4UHJvamVjdG9yLCB5UHJvamVjdG9yLCB5MFByb2plY3RvciwgZGVmaW5lZFByb2plY3RvciwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICByZXR1cm4gYXJlYUdlbmVyYXRvcihkYXR1bSk7CiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fY3JlYXRlRGVmaW5lZFByb2plY3RvciA9IGZ1bmN0aW9uICh4UHJvamVjdG9yLCB5UHJvamVjdG9yKSB7CiAgICAgICAgICAgIHJldHVybiBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIHBvc2l0aW9uWCA9IHhQcm9qZWN0b3IoZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgcG9zaXRpb25ZID0geVByb2plY3RvcihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihwb3NpdGlvblgpICYmIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHBvc2l0aW9uWSk7CiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBBcmVhLnByb3RvdHlwZS5fY3JlYXRlQXJlYUdlbmVyYXRvciA9IGZ1bmN0aW9uICh4UHJvamVjdG9yLCB5UHJvamVjdG9yLCB5MFByb2plY3RvciwgZGVmaW5lZFByb2plY3RvciwgZGF0YXNldCkgewogICAgICAgICAgICAvLyBqdXN0IHJ1bnRpbWUgZXJyb3IgaWYgdXNlciBwYXNzZXMgY3VydmVCdW5kbGUgdG8gYXJlYSBwbG90CiAgICAgICAgICAgIHZhciBjdXJ2ZUZhY3RvcnkgPSB0aGlzLl9nZXRDdXJ2ZUZhY3RvcnkoKTsKICAgICAgICAgICAgdmFyIGFyZWFHZW5lcmF0b3IgPSBkMy5hcmVhKCkKICAgICAgICAgICAgICAgIC54KGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiB4UHJvamVjdG9yKGlubmVyRGF0dW0sIGlubmVySW5kZXgsIGRhdGFzZXQpOyB9KQogICAgICAgICAgICAgICAgLnkxKGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiB5UHJvamVjdG9yKGlubmVyRGF0dW0sIGlubmVySW5kZXgsIGRhdGFzZXQpOyB9KQogICAgICAgICAgICAgICAgLnkwKGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiB5MFByb2plY3Rvcihpbm5lckRhdHVtLCBpbm5lckluZGV4LCBkYXRhc2V0KTsgfSkKICAgICAgICAgICAgICAgIC5jdXJ2ZShjdXJ2ZUZhY3RvcnkpCiAgICAgICAgICAgICAgICAuZGVmaW5lZChmdW5jdGlvbiAoaW5uZXJEYXR1bSwgaW5uZXJJbmRleCkgeyByZXR1cm4gZGVmaW5lZFByb2plY3Rvcihpbm5lckRhdHVtLCBpbm5lckluZGV4LCBkYXRhc2V0KTsgfSk7CiAgICAgICAgICAgIHJldHVybiBhcmVhR2VuZXJhdG9yOwogICAgICAgIH07CiAgICAgICAgQXJlYS5wcm90b3R5cGUuX2NyZWF0ZVRvcExpbmVHZW5lcmF0b3IgPSBmdW5jdGlvbiAoeFByb2plY3RvciwgeVByb2plY3RvciwgZGVmaW5lZFByb2plY3RvciwgZGF0YXNldCkgewogICAgICAgICAgICB2YXIgY3VydmVGYWN0b3J5ID0gdGhpcy5fZ2V0Q3VydmVGYWN0b3J5KCk7CiAgICAgICAgICAgIHZhciBhcmVhR2VuZXJhdG9yID0gZDMubGluZSgpCiAgICAgICAgICAgICAgICAueChmdW5jdGlvbiAoaW5uZXJEYXR1bSwgaW5uZXJJbmRleCkgeyByZXR1cm4geFByb2plY3Rvcihpbm5lckRhdHVtLCBpbm5lckluZGV4LCBkYXRhc2V0KTsgfSkKICAgICAgICAgICAgICAgIC55KGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiB5UHJvamVjdG9yKGlubmVyRGF0dW0sIGlubmVySW5kZXgsIGRhdGFzZXQpOyB9KQogICAgICAgICAgICAgICAgLmN1cnZlKGN1cnZlRmFjdG9yeSkKICAgICAgICAgICAgICAgIC5kZWZpbmVkKGZ1bmN0aW9uIChpbm5lckRhdHVtLCBpbm5lckluZGV4KSB7IHJldHVybiBkZWZpbmVkUHJvamVjdG9yKGlubmVyRGF0dW0sIGlubmVySW5kZXgsIGRhdGFzZXQpOyB9KTsKICAgICAgICAgICAgcmV0dXJuIGFyZWFHZW5lcmF0b3I7CiAgICAgICAgfTsKICAgICAgICBBcmVhLl9ZMF9LRVkgPSAieTAiOwogICAgICAgIHJldHVybiBBcmVhOwogICAgfShsaW5lUGxvdC5MaW5lKSk7CiAgICBleHBvcnRzLkFyZWEgPSBBcmVhOwogICAgfSk7CgogICAgdmFyIGJhclBsb3QgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgoKCgoKCgoKCgoKCiAgICBleHBvcnRzLkJhck9yaWVudGF0aW9uID0gbWFrZUVudW1fMS5tYWtlRW51bShbInZlcnRpY2FsIiwgImhvcml6b250YWwiXSk7CiAgICBleHBvcnRzLkxhYmVsc1Bvc2l0aW9uID0gbWFrZUVudW1fMS5tYWtlRW51bShbInN0YXJ0IiwgIm1pZGRsZSIsICJlbmQiLCAib3V0c2lkZSJdKTsKICAgIGV4cG9ydHMuQmFyQWxpZ25tZW50ID0gbWFrZUVudW1fMS5tYWtlRW51bShbInN0YXJ0IiwgIm1pZGRsZSIsICJlbmQiXSk7CiAgICB2YXIgQmFyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQmFyLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEEgQmFyIFBsb3QgZHJhd3MgYmFycyBncm93aW5nIG91dCBmcm9tIGEgYmFzZWxpbmUgdG8gc29tZSB2YWx1ZQogICAgICAgICAqCiAgICAgICAgICogQGNvbnN0cnVjdG9yCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IFtvcmllbnRhdGlvbj0idmVydGljYWwiXSBPbmUgb2YgInZlcnRpY2FsIi8iaG9yaXpvbnRhbCIuCiAgICAgICAgICovCiAgICAgICAgZnVuY3Rpb24gQmFyKG9yaWVudGF0aW9uKSB7CiAgICAgICAgICAgIGlmIChvcmllbnRhdGlvbiA9PT0gdm9pZCAwKSB7IG9yaWVudGF0aW9uID0gInZlcnRpY2FsIjsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbGFiZWxGb3JtYXR0ZXIgPSBmb3JtYXR0ZXJzLmlkZW50aXR5KCk7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbHNFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbHNQb3NpdGlvbiA9IGV4cG9ydHMuTGFiZWxzUG9zaXRpb24uZW5kOwogICAgICAgICAgICBfdGhpcy5faGlkZUJhcnNJZkFueUFyZVRvb1dpZGUgPSB0cnVlOwogICAgICAgICAgICBfdGhpcy5fYmFyQWxpZ25tZW50ID0gIm1pZGRsZSI7CiAgICAgICAgICAgIF90aGlzLl9jb21wdXRlQmFyUGl4ZWxUaGlja25lc3MgPSBtZW1vaXplLm1lbW9pemUoY29tcHV0ZUJhclBpeGVsVGhpY2tuZXNzKTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdoZXRoZXIgYWxsIHRoZSBiYXJzIGluIHRoaXMgYmFyUGxvdCBoYXZlIHRoZSBzYW1lIHBpeGVsIHRoaWNrbmVzcy4KICAgICAgICAgICAgICogSWYgc28sIHVzZSB0aGUgX2JhclBpeGVsVGhpY2tuZXNzIHByb3BlcnR5IHRvIGFjY2VzcyB0aGUgdGhpY2tuZXNzLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgX3RoaXMuX2ZpeGVkQmFyUGl4ZWxUaGlja25lc3MgPSB0cnVlOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygiYmFyLXBsb3QiKTsKICAgICAgICAgICAgaWYgKG9yaWVudGF0aW9uICE9PSAidmVydGljYWwiICYmIG9yaWVudGF0aW9uICE9PSAiaG9yaXpvbnRhbCIpIHsKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcihvcmllbnRhdGlvbiArICIgaXMgbm90IGEgdmFsaWQgb3JpZW50YXRpb24gZm9yIFBsb3RzLkJhciIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF90aGlzLl9pc1ZlcnRpY2FsID0gb3JpZW50YXRpb24gPT09ICJ2ZXJ0aWNhbCI7CiAgICAgICAgICAgIF90aGlzLmFuaW1hdG9yKCJiYXNlbGluZSIsIG5ldyBhbmltYXRvcnMuTnVsbCgpKTsKICAgICAgICAgICAgX3RoaXMuYXR0cigiZmlsbCIsIG5ldyBzY2FsZXMuQ29sb3IoKS5yYW5nZSgpWzBdKTsKICAgICAgICAgICAgX3RoaXMuYXR0cihCYXIuX0JBUl9USElDS05FU1NfS0VZLCBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fYmFyUGl4ZWxUaGlja25lc3MoKTsgfSk7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbENvbmZpZyA9IG5ldyB1dGlscyQxLk1hcCgpOwogICAgICAgICAgICBfdGhpcy5fYmFzZWxpbmVWYWx1ZVByb3ZpZGVyID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gW190aGlzLmJhc2VsaW5lVmFsdWUoKV07IH07CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgQmFyLnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVFeHRlbnRzKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS54ID0gZnVuY3Rpb24gKHgsIHhTY2FsZSkgewogICAgICAgICAgICBpZiAoeCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS54LmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHhTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnguY2FsbCh0aGlzLCB4KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueC5jYWxsKHRoaXMsIHgsIHhTY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdXBkYXRlVGhpY2tuZXNzQXR0cigpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVMZW5ndGhTY2FsZSgpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUueSA9IGZ1bmN0aW9uICh5LCB5U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHkgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh5U2NhbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS55LmNhbGwodGhpcywgeSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzLCB5LCB5U2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZUxlbmd0aFNjYWxlKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIGJpbmRpbmcgYXNzb2NpYXRlZCB3aXRoIGJhciBsZW5ndGguIExlbmd0aCBpcyB0aGUgY291bnQgb3IgdmFsdWUgdGhlIGJhciBpcyB0cnlpbmcgdG8gc2hvdy4KICAgICAgICAgKiBUaGlzIGlzIHRoZSAueSgpIGZvciBhIHZlcnRpY2FsIHBsb3QgYW5kIC54KCkgZm9yIGEgaG9yaXpvbnRhbCBwbG90LgogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUubGVuZ3RoID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5faXNWZXJ0aWNhbCA/IHRoaXMueSgpIDogdGhpcy54KCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBUaGUgYmluZGluZyBhc3NvY2lhdGVkIHdpdGggYmFyIHBvc2l0aW9uLiBQb3NpdGlvbiBzZXBhcmF0ZXMgdGhlIGRpZmZlcmVudCBiYXIgY2F0ZWdvcmllcy4KICAgICAgICAgKiBUaGlzIGlzIHRoZSAueCgpIGZvciBhIHZlcnRpY2FsIHBsb3QgYW5kIC55KCkgZm9yIGEgaG9yaXpvbnRhbCBwbG90LgogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUucG9zaXRpb24gPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9pc1ZlcnRpY2FsID8gdGhpcy54KCkgOiB0aGlzLnkoKTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuYmFyRW5kID0gZnVuY3Rpb24gKGVuZCkgewogICAgICAgICAgICBpZiAoZW5kID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChCYXIuX0JBUl9FTkRfS0VZKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgYmluZGluZyA9IHRoaXMucG9zaXRpb24oKTsKICAgICAgICAgICAgdmFyIHNjYWxlID0gYmluZGluZyAmJiBiaW5kaW5nLnNjYWxlOwogICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoQmFyLl9CQVJfRU5EX0tFWSwgZW5kLCBzY2FsZSk7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVRoaWNrbmVzc0F0dHIoKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlTGVuZ3RoU2NhbGUoKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLmJhckFsaWdubWVudCA9IGZ1bmN0aW9uIChhbGlnbikgewogICAgICAgICAgICBpZiAoYWxpZ24gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2JhckFsaWdubWVudDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9iYXJBbGlnbm1lbnQgPSBhbGlnbjsKICAgICAgICAgICAgdGhpcy5fY2xlYXJBdHRyVG9Qcm9qZWN0b3JDYWNoZSgpOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIG9yaWVudGF0aW9uIG9mIHRoZSBwbG90CiAgICAgICAgICoKICAgICAgICAgKiBAcmV0dXJuICJ2ZXJ0aWNhbCIgfCAiaG9yaXpvbnRhbCIKICAgICAgICAgKi8KICAgICAgICBCYXIucHJvdG90eXBlLm9yaWVudGF0aW9uID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5faXNWZXJ0aWNhbCA/ICJ2ZXJ0aWNhbCIgOiAiaG9yaXpvbnRhbCI7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9jcmVhdGVEcmF3ZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgZHJhd2VyLlByb3h5RHJhd2VyKGZ1bmN0aW9uICgpIHsgcmV0dXJuIG5ldyByZWN0YW5nbGVEcmF3ZXIuUmVjdGFuZ2xlU1ZHRHJhd2VyKEJhci5fQkFSX0FSRUFfQ0xBU1MpOyB9LCBmdW5jdGlvbiAoY3R4KSB7IHJldHVybiBuZXcgZHJhd2Vycy5SZWN0YW5nbGVDYW52YXNEcmF3ZXIoY3R4KTsgfSk7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9zZXR1cCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fc2V0dXAuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fYmFzZWxpbmUgPSB0aGlzLl9yZW5kZXJBcmVhLmFwcGVuZCgibGluZSIpLmNsYXNzZWQoImJhc2VsaW5lIiwgdHJ1ZSk7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLmJhc2VsaW5lVmFsdWUgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgaWYgKHZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9iYXNlbGluZVZhbHVlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fYmFzZWxpbmVWYWx1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICghdGhpcy5fcHJvamVjdG9yc1JlYWR5KCkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBsZW5ndGhTY2FsZSA9IHRoaXMubGVuZ3RoKCkuc2NhbGU7CiAgICAgICAgICAgICAgICBpZiAoIWxlbmd0aFNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAobGVuZ3RoU2NhbGUgaW5zdGFuY2VvZiBzY2FsZXMuVGltZSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBuZXcgRGF0ZSgwKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Jhc2VsaW5lVmFsdWUgPSB2YWx1ZTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlTGVuZ3RoU2NhbGUoKTsKICAgICAgICAgICAgdGhpcy5fY2xlYXJBdHRyVG9Qcm9qZWN0b3JDYWNoZSgpOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuYWRkRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuYWRkRGF0YXNldC5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2FkZERhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9hZGREYXRhc2V0LmNhbGwodGhpcywgZGF0YXNldCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5yZW1vdmVEYXRhc2V0ID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5yZW1vdmVEYXRhc2V0LmNhbGwodGhpcywgZGF0YXNldCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fcmVtb3ZlRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLmRhdGFzZXRzID0gZnVuY3Rpb24gKGRhdGFzZXRzKSB7CiAgICAgICAgICAgIGlmIChkYXRhc2V0cyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5kYXRhc2V0cy5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuZGF0YXNldHMuY2FsbCh0aGlzLCBkYXRhc2V0cyk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5sYWJlbHNFbmFibGVkID0gZnVuY3Rpb24gKGVuYWJsZWQsIGxhYmVsc1Bvc2l0aW9uKSB7CiAgICAgICAgICAgIGlmIChlbmFibGVkID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9sYWJlbHNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxzRW5hYmxlZCA9IGVuYWJsZWQ7CiAgICAgICAgICAgICAgICBpZiAobGFiZWxzUG9zaXRpb24gIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX2xhYmVsc1Bvc2l0aW9uID0gbGFiZWxzUG9zaXRpb247CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9jbGVhckF0dHJUb1Byb2plY3RvckNhY2hlKCk7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUubGFiZWxGb3JtYXR0ZXIgPSBmdW5jdGlvbiAoZm9ybWF0dGVyKSB7CiAgICAgICAgICAgIGlmIChmb3JtYXR0ZXIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2xhYmVsRm9ybWF0dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxGb3JtYXR0ZXIgPSBmb3JtYXR0ZXI7CiAgICAgICAgICAgICAgICB0aGlzLl9jbGVhckF0dHJUb1Byb2plY3RvckNhY2hlKCk7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2NyZWF0ZU5vZGVzRm9yRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIHZhciBkcmF3ZXIgPSBfc3VwZXIucHJvdG90eXBlLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGxhYmVsQXJlYSA9IHRoaXMuX3JlbmRlckFyZWEuYXBwZW5kKCJnIikuY2xhc3NlZChCYXIuX0xBQkVMX0FSRUFfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB2YXIgY29udGV4dCA9IG5ldyBzcmMkMS5TdmdDb250ZXh0KGxhYmVsQXJlYS5ub2RlKCkpOwogICAgICAgICAgICB2YXIgbWVhc3VyZXIgPSBuZXcgc3JjJDEuQ2FjaGVNZWFzdXJlcihjb250ZXh0KTsKICAgICAgICAgICAgdmFyIHdyaXRlciA9IG5ldyBzcmMkMS5Xcml0ZXIobWVhc3VyZXIsIGNvbnRleHQpOwogICAgICAgICAgICB0aGlzLl9sYWJlbENvbmZpZy5zZXQoZGF0YXNldCwgeyBsYWJlbEFyZWE6IGxhYmVsQXJlYSwgbWVhc3VyZXI6IG1lYXN1cmVyLCB3cml0ZXI6IHdyaXRlciB9KTsKICAgICAgICAgICAgcmV0dXJuIGRyYXdlcjsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXROb2RlcyA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXROb2Rlcy5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgbGFiZWxDb25maWcgPSB0aGlzLl9sYWJlbENvbmZpZy5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgIGlmIChsYWJlbENvbmZpZyAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBsYWJlbENvbmZpZy5sYWJlbEFyZWEucmVtb3ZlKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9sYWJlbENvbmZpZy5kZWxldGUoZGF0YXNldCk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgdGhlIFBsb3RFbnRpdHkgbmVhcmVzdCB0byB0aGUgcXVlcnkgcG9pbnQgYWNjb3JkaW5nIHRvIHRoZSBmb2xsb3dpbmcgYWxnb3JpdGhtOgogICAgICAgICAqICAgLSBJZiB0aGUgcXVlcnkgcG9pbnQgaXMgaW5zaWRlIGEgYmFyLCByZXR1cm5zIHRoZSBQbG90RW50aXR5IGZvciB0aGF0IGJhci4KICAgICAgICAgKiAgIC0gT3RoZXJ3aXNlLCBnZXRzIHRoZSBuZWFyZXN0IFBsb3RFbnRpdHkgYnkgdGhlIHBvc2l0aW9uYWwgZGlyZWN0aW9uIChYIGZvciB2ZXJ0aWNhbCwgWSBmb3IgaG9yaXpvbnRhbCksCiAgICAgICAgICogICAgIGJyZWFraW5nIHRpZXMgd2l0aCB0aGUgc2Vjb25kYXJ5IGRpcmVjdGlvbi4KICAgICAgICAgKiBSZXR1cm5zIHVuZGVmaW5lZCBpZiBubyBQbG90RW50aXR5IGNhbiBiZSBmb3VuZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7UG9pbnR9IHF1ZXJ5UG9pbnQKICAgICAgICAgKiBAcmV0dXJucyB7UGxvdEVudGl0eX0gVGhlIG5lYXJlc3QgUGxvdEVudGl0eSwgb3IgdW5kZWZpbmVkIGlmIG5vIFBsb3RFbnRpdHkgY2FuIGJlIGZvdW5kLgogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUuZW50aXR5TmVhcmVzdCA9IGZ1bmN0aW9uIChxdWVyeVBvaW50KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciB3b3JrZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB2YXIgbmVhcmVzdCA9IF90aGlzLl9pc1ZlcnRpY2FsID8KICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZ2V0RW50aXR5U3RvcmUoKS5lbnRpdHlOZWFyZXN0WChxdWVyeVBvaW50KSA6CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuX2dldEVudGl0eVN0b3JlKCkuZW50aXR5TmVhcmVzdFkocXVlcnlQb2ludCk7CiAgICAgICAgICAgICAgICByZXR1cm4gbmVhcmVzdCA9PT0gdW5kZWZpbmVkID8gdW5kZWZpbmVkIDogX3RoaXMuX2xpZ2h0d2VpZ2h0UGxvdEVudGl0eVRvUGxvdEVudGl0eShuZWFyZXN0KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2ZpeGVkQmFyUGl4ZWxUaGlja25lc3MgPyB0aGlzLl9jb21wdXRlQmFyUGl4ZWxUaGlja25lc3MuZG9Mb2NrZWQod29ya2VyKSA6IHdvcmtlcigpOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogR2V0cyB0aGUgRW50aXRpZXMgYXQgYSBwYXJ0aWN1bGFyIFBvaW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQb2ludH0gcAogICAgICAgICAqIEByZXR1cm5zIHtQbG90RW50aXR5W119CiAgICAgICAgICovCiAgICAgICAgQmFyLnByb3RvdHlwZS5lbnRpdGllc0F0ID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHdvcmtlciA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9lbnRpdGllc0ludGVyc2VjdGluZyhwLngsIHAueSk7IH07CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9maXhlZEJhclBpeGVsVGhpY2tuZXNzID8gdGhpcy5fY29tcHV0ZUJhclBpeGVsVGhpY2tuZXNzLmRvTG9ja2VkKHdvcmtlcikgOiB3b3JrZXIoKTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuZW50aXRpZXNJbkJvdW5kcyA9IGZ1bmN0aW9uIChxdWVyeUJvdW5kcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgd29ya2VyID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5lbnRpdGllc0luQm91bmRzLmNhbGwoX3RoaXMsIHF1ZXJ5Qm91bmRzKTsgfTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2ZpeGVkQmFyUGl4ZWxUaGlja25lc3MgPyB0aGlzLl9jb21wdXRlQmFyUGl4ZWxUaGlja25lc3MuZG9Mb2NrZWQod29ya2VyKSA6IHdvcmtlcigpOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5lbnRpdGllc0luWEJvdW5kcyA9IGZ1bmN0aW9uIChxdWVyeUJvdW5kcykgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgd29ya2VyID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5lbnRpdGllc0luWEJvdW5kcy5jYWxsKF90aGlzLCBxdWVyeUJvdW5kcyk7IH07CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9maXhlZEJhclBpeGVsVGhpY2tuZXNzID8gdGhpcy5fY29tcHV0ZUJhclBpeGVsVGhpY2tuZXNzLmRvTG9ja2VkKHdvcmtlcikgOiB3b3JrZXIoKTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuZW50aXRpZXNJbllCb3VuZHMgPSBmdW5jdGlvbiAocXVlcnlCb3VuZHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHdvcmtlciA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuZW50aXRpZXNJbllCb3VuZHMuY2FsbChfdGhpcywgcXVlcnlCb3VuZHMpOyB9OwogICAgICAgICAgICByZXR1cm4gdGhpcy5fZml4ZWRCYXJQaXhlbFRoaWNrbmVzcyA/IHRoaXMuX2NvbXB1dGVCYXJQaXhlbFRoaWNrbmVzcy5kb0xvY2tlZCh3b3JrZXIpIDogd29ya2VyKCk7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9lbnRpdGllc0ludGVyc2VjdGluZyA9IGZ1bmN0aW9uICh4VmFsT3JSYW5nZSwgeVZhbE9yUmFuZ2UpIHsKICAgICAgICAgICAgdmFyIGludGVyc2VjdGVkID0gW107CiAgICAgICAgICAgIHZhciBlbnRpdGllcyA9IHRoaXMuX2dldEVudGl0eVN0b3JlKCkuZW50aXRpZXMoKTsKICAgICAgICAgICAgdmFyIGVudGl0aWVzTGVuID0gZW50aXRpZXMubGVuZ3RoOwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGVudGl0aWVzTGVuOyBpKyspIHsKICAgICAgICAgICAgICAgIHZhciBlbnRpdHkgPSBlbnRpdGllc1tpXTsKICAgICAgICAgICAgICAgIGlmICh1dGlscyQxLkRPTS5pbnRlcnNlY3RzQkJveCh4VmFsT3JSYW5nZSwgeVZhbE9yUmFuZ2UsIHRoaXMuX2VudGl0eUJvdW5kcyhlbnRpdHkpKSkgewogICAgICAgICAgICAgICAgICAgIGludGVyc2VjdGVkLnB1c2godGhpcy5fbGlnaHR3ZWlnaHRQbG90RW50aXR5VG9QbG90RW50aXR5KGVudGl0eSkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBpbnRlcnNlY3RlZDsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX3VwZGF0ZUxlbmd0aFNjYWxlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX3Byb2plY3RvcnNSZWFkeSgpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGxlbmd0aFNjYWxlID0gdGhpcy5sZW5ndGgoKS5zY2FsZTsKICAgICAgICAgICAgaWYgKGxlbmd0aFNjYWxlIGluc3RhbmNlb2YgcXVhbnRpdGF0aXZlU2NhbGUuUXVhbnRpdGF0aXZlU2NhbGUpIHsKICAgICAgICAgICAgICAgIGxlbmd0aFNjYWxlLmFkZFBhZGRpbmdFeGNlcHRpb25zUHJvdmlkZXIodGhpcy5fYmFzZWxpbmVWYWx1ZVByb3ZpZGVyKTsKICAgICAgICAgICAgICAgIGxlbmd0aFNjYWxlLmFkZEluY2x1ZGVkVmFsdWVzUHJvdmlkZXIodGhpcy5fYmFzZWxpbmVWYWx1ZVByb3ZpZGVyKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5yZW5kZXJJbW1lZGlhdGVseSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgLy8gSEFDSyB1cGRhdGUgYmFyIHBpeGVsIHRoaWNrbmVzcwogICAgICAgICAgICB0aGlzLl9iYXJQaXhlbFRoaWNrbmVzcygpOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fY29tcHV0ZUJhclBpeGVsVGhpY2tuZXNzLmRvTG9ja2VkKGZ1bmN0aW9uICgpIHsgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUucmVuZGVySW1tZWRpYXRlbHkuY2FsbChfdGhpcyk7IH0pOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fYWRkaXRpb25hbFBhaW50ID0gZnVuY3Rpb24gKHRpbWUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGxlbmd0aFNjYWxlID0gdGhpcy5sZW5ndGgoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIHNjYWxlZEJhc2VsaW5lID0gbGVuZ3RoU2NhbGUuc2NhbGUodGhpcy5iYXNlbGluZVZhbHVlKCkpOwogICAgICAgICAgICB2YXIgYmFzZWxpbmVBdHRyID0gewogICAgICAgICAgICAgICAgeDE6IHRoaXMuX2lzVmVydGljYWwgPyAwIDogc2NhbGVkQmFzZWxpbmUsCiAgICAgICAgICAgICAgICB5MTogdGhpcy5faXNWZXJ0aWNhbCA/IHNjYWxlZEJhc2VsaW5lIDogMCwKICAgICAgICAgICAgICAgIHgyOiB0aGlzLl9pc1ZlcnRpY2FsID8gdGhpcy53aWR0aCgpIDogc2NhbGVkQmFzZWxpbmUsCiAgICAgICAgICAgICAgICB5MjogdGhpcy5faXNWZXJ0aWNhbCA/IHNjYWxlZEJhc2VsaW5lIDogdGhpcy5oZWlnaHQoKSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5fZ2V0QW5pbWF0b3IoImJhc2VsaW5lIikuYW5pbWF0ZSh0aGlzLl9iYXNlbGluZSwgYmFzZWxpbmVBdHRyKTsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9sYWJlbENvbmZpZy5nZXQoZGF0YXNldCkubGFiZWxBcmVhLnNlbGVjdEFsbCgiZyIpLnJlbW92ZSgpOyB9KTsKICAgICAgICAgICAgaWYgKHRoaXMuX2xhYmVsc0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgIHV0aWxzJDEuV2luZG93LnNldFRpbWVvdXQoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2RyYXdMYWJlbHMoKTsgfSwgdGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIE1ha2VzIHN1cmUgdGhlIGV4dGVudCB0YWtlcyBpbnRvIGFjY291bnQgdGhlIHdpZHRocyBvZiB0aGUgYmFycwogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUuZ2V0RXh0ZW50c0ZvclByb3BlcnR5ID0gZnVuY3Rpb24gKHByb3BlcnR5KSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBleHRlbnRzID0gX3N1cGVyLnByb3RvdHlwZS5nZXRFeHRlbnRzRm9yUHJvcGVydHkuY2FsbCh0aGlzLCBwcm9wZXJ0eSk7CiAgICAgICAgICAgIHZhciBhY2NTY2FsZUJpbmRpbmc7CiAgICAgICAgICAgIGlmIChwcm9wZXJ0eSA9PT0gIngiICYmIHRoaXMuX2lzVmVydGljYWwpIHsKICAgICAgICAgICAgICAgIGFjY1NjYWxlQmluZGluZyA9IHRoaXMueCgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHByb3BlcnR5ID09PSAieSIgJiYgIXRoaXMuX2lzVmVydGljYWwpIHsKICAgICAgICAgICAgICAgIGFjY1NjYWxlQmluZGluZyA9IHRoaXMueSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIGV4dGVudHM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCEoYWNjU2NhbGVCaW5kaW5nICYmIGFjY1NjYWxlQmluZGluZy5zY2FsZSAmJiBhY2NTY2FsZUJpbmRpbmcuc2NhbGUgaW5zdGFuY2VvZiBxdWFudGl0YXRpdmVTY2FsZS5RdWFudGl0YXRpdmVTY2FsZSkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBleHRlbnRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBzY2FsZSA9IGFjY1NjYWxlQmluZGluZy5zY2FsZTsKICAgICAgICAgICAgdmFyIHdpZHRoID0gdGhpcy5fYmFyUGl4ZWxUaGlja25lc3MoKTsKICAgICAgICAgICAgLy8gVG8gYWNjb3VudCBmb3IgaW52ZXJ0ZWQgZG9tYWlucwogICAgICAgICAgICBleHRlbnRzID0gZXh0ZW50cy5tYXAoZnVuY3Rpb24gKGV4dGVudCkgeyByZXR1cm4gZDMuZXh0ZW50KFsKICAgICAgICAgICAgICAgIHNjYWxlLmludmVydChfdGhpcy5fZ2V0UG9zaXRpb25BdHRyKHNjYWxlLnNjYWxlKGV4dGVudFswXSksIHdpZHRoKSksCiAgICAgICAgICAgICAgICBzY2FsZS5pbnZlcnQoX3RoaXMuX2dldFBvc2l0aW9uQXR0cihzY2FsZS5zY2FsZShleHRlbnRbMF0pLCB3aWR0aCkgKyB3aWR0aCksCiAgICAgICAgICAgICAgICBzY2FsZS5pbnZlcnQoX3RoaXMuX2dldFBvc2l0aW9uQXR0cihzY2FsZS5zY2FsZShleHRlbnRbMV0pLCB3aWR0aCkpLAogICAgICAgICAgICAgICAgc2NhbGUuaW52ZXJ0KF90aGlzLl9nZXRQb3NpdGlvbkF0dHIoc2NhbGUuc2NhbGUoZXh0ZW50WzFdKSwgd2lkdGgpICsgd2lkdGgpLAogICAgICAgICAgICBdKTsgfSk7CiAgICAgICAgICAgIHJldHVybiBleHRlbnRzOwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJuIHRoZSA8cmVjdD4ncyB4IG9yIHkgYXR0ciB2YWx1ZSBnaXZlbiB0aGUgcG9zaXRpb24gYW5kIHRoaWNrbmVzcyBvZgogICAgICAgICAqIHRoYXQgYmFyLiBUaGlzIG1ldGhvZCBpcyByZXNwb25zaWJsZSBmb3IgYWNjb3VudCBmb3IgYmFyQWxpZ25tZW50LCBpbiBwYXJ0aWN1bGFyLgogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUuX2dldFBvc2l0aW9uQXR0ciA9IGZ1bmN0aW9uIChwb3NpdGlvbiwgdGhpY2tuZXNzKSB7CiAgICAgICAgICAgIC8vIGFjY291bnQgZm9yIGZsaXBwZWQgdmVydGljYWwgYXhpcwogICAgICAgICAgICBpZiAoIXRoaXMuX2lzVmVydGljYWwpIHsKICAgICAgICAgICAgICAgIHBvc2l0aW9uIC09IHRoaWNrbmVzczsKICAgICAgICAgICAgICAgIHRoaWNrbmVzcyAqPSAtMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzd2l0Y2ggKHRoaXMuX2JhckFsaWdubWVudCkgewogICAgICAgICAgICAgICAgY2FzZSAic3RhcnQiOgogICAgICAgICAgICAgICAgICAgIHJldHVybiBwb3NpdGlvbjsKICAgICAgICAgICAgICAgIGNhc2UgImVuZCI6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHBvc2l0aW9uIC0gdGhpY2tuZXNzOwogICAgICAgICAgICAgICAgY2FzZSAibWlkZGxlIjoKICAgICAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHBvc2l0aW9uIC0gdGhpY2tuZXNzIC8gMjsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fZHJhd0xhYmVscyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGRhdGFUb0RyYXcgPSB0aGlzLl9nZXREYXRhVG9EcmF3KCk7CiAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgdmFyIGFueUxhYmVsVG9vV2lkZSA9IHRoaXMuZGF0YXNldHMoKS5zb21lKGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZGF0YVRvRHJhdy5nZXQoZGF0YXNldCkuc29tZShmdW5jdGlvbiAoZGF0dW0sIGluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKGRhdHVtID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2RyYXdMYWJlbChkYXR1bSwgaW5kZXgsIGRhdGFzZXQsIGF0dHJUb1Byb2plY3Rvcik7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGlmICh0aGlzLl9oaWRlQmFyc0lmQW55QXJlVG9vV2lkZSAmJiBhbnlMYWJlbFRvb1dpZGUpIHsKICAgICAgICAgICAgICAgIHRoaXMuZGF0YXNldHMoKS5mb3JFYWNoKGZ1bmN0aW9uIChkYXRhc2V0KSB7IHJldHVybiBfdGhpcy5fbGFiZWxDb25maWcuZ2V0KGRhdGFzZXQpLmxhYmVsQXJlYS5zZWxlY3RBbGwoImciKS5yZW1vdmUoKTsgfSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2RyYXdMYWJlbCA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQsIGF0dHJUb1Byb2plY3RvcikgewogICAgICAgICAgICB2YXIgX2EgPSB0aGlzLl9sYWJlbENvbmZpZy5nZXQoZGF0YXNldCksIGxhYmVsQXJlYSA9IF9hLmxhYmVsQXJlYSwgbWVhc3VyZXIgPSBfYS5tZWFzdXJlciwgd3JpdGVyID0gX2Eud3JpdGVyOwogICAgICAgICAgICB2YXIgbGVuZ3RoQWNjZXNzb3IgPSB0aGlzLmxlbmd0aCgpLmFjY2Vzc29yOwogICAgICAgICAgICB2YXIgbGVuZ3RoID0gbGVuZ3RoQWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGxlbmd0aFNjYWxlID0gdGhpcy5sZW5ndGgoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIHNjYWxlZExlbmd0aCA9IGxlbmd0aFNjYWxlICE9IG51bGwgPyBsZW5ndGhTY2FsZS5zY2FsZShsZW5ndGgpIDogbGVuZ3RoOwogICAgICAgICAgICB2YXIgc2NhbGVkQmFzZWxpbmUgPSBsZW5ndGhTY2FsZSAhPSBudWxsID8gbGVuZ3RoU2NhbGUuc2NhbGUodGhpcy5iYXNlbGluZVZhbHVlKCkpIDogdGhpcy5iYXNlbGluZVZhbHVlKCk7CiAgICAgICAgICAgIHZhciBiYXJDb29yZGluYXRlcyA9IHsgeDogYXR0clRvUHJvamVjdG9yWyJ4Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwgeTogYXR0clRvUHJvamVjdG9yWyJ5Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB9OwogICAgICAgICAgICB2YXIgYmFyRGltZW5zaW9ucyA9IHsgd2lkdGg6IGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpLCBoZWlnaHQ6IGF0dHJUb1Byb2plY3RvclsiaGVpZ2h0Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB9OwogICAgICAgICAgICB2YXIgdGV4dCA9IHRoaXMuX2xhYmVsRm9ybWF0dGVyKGxlbmd0aCwgZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIG1lYXN1cmVtZW50ID0gbWVhc3VyZXIubWVhc3VyZSh0ZXh0KTsKICAgICAgICAgICAgdmFyIHNob3dMYWJlbE9uQmFyID0gdGhpcy5fc2hvdWxkU2hvd0xhYmVsT25CYXIoYmFyQ29vcmRpbmF0ZXMsIGJhckRpbWVuc2lvbnMsIG1lYXN1cmVtZW50KTsKICAgICAgICAgICAgLy8gc2hvdyBsYWJlbCBvbiByaWdodCB3aGVuIHZhbHVlID09PSBiYXNlbGluZSBmb3IgaG9yaXpvbnRhbCBwbG90cwogICAgICAgICAgICB2YXIgYWJvdmVPckxlZnRPZkJhc2VsaW5lID0gdGhpcy5faXNWZXJ0aWNhbCA/IHNjYWxlZExlbmd0aCA8PSBzY2FsZWRCYXNlbGluZSA6IHNjYWxlZExlbmd0aCA8IHNjYWxlZEJhc2VsaW5lOwogICAgICAgICAgICB2YXIgX2IgPSB0aGlzLl9jYWxjdWxhdGVMYWJlbFByb3BlcnRpZXMoYmFyQ29vcmRpbmF0ZXMsIGJhckRpbWVuc2lvbnMsIG1lYXN1cmVtZW50LCBzaG93TGFiZWxPbkJhciwgYWJvdmVPckxlZnRPZkJhc2VsaW5lKSwgY29udGFpbmVyRGltZW5zaW9ucyA9IF9iLmNvbnRhaW5lckRpbWVuc2lvbnMsIGxhYmVsQ29udGFpbmVyT3JpZ2luID0gX2IubGFiZWxDb250YWluZXJPcmlnaW4sIGxhYmVsT3JpZ2luID0gX2IubGFiZWxPcmlnaW4sIGFsaWdubWVudCA9IF9iLmFsaWdubWVudDsKICAgICAgICAgICAgdmFyIGNvbG9yID0gYXR0clRvUHJvamVjdG9yWyJmaWxsIl0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGxhYmVsQ29udGFpbmVyID0gdGhpcy5fY3JlYXRlTGFiZWxDb250YWluZXIobGFiZWxBcmVhLCBsYWJlbENvbnRhaW5lck9yaWdpbiwgbGFiZWxPcmlnaW4sIG1lYXN1cmVtZW50LCBzaG93TGFiZWxPbkJhciwgY29sb3IpOwogICAgICAgICAgICB2YXIgd3JpdGVPcHRpb25zID0geyB4QWxpZ246IGFsaWdubWVudC54LCB5QWxpZ246IGFsaWdubWVudC55IH07CiAgICAgICAgICAgIHdyaXRlci53cml0ZSh0ZXh0LCBjb250YWluZXJEaW1lbnNpb25zLndpZHRoLCBjb250YWluZXJEaW1lbnNpb25zLmhlaWdodCwgd3JpdGVPcHRpb25zLCBsYWJlbENvbnRhaW5lci5ub2RlKCkpOwogICAgICAgICAgICB2YXIgdG9vV2lkZSA9IHRoaXMuX2lzVmVydGljYWwKICAgICAgICAgICAgICAgID8gYmFyRGltZW5zaW9ucy53aWR0aCA8IChtZWFzdXJlbWVudC53aWR0aCkKICAgICAgICAgICAgICAgIDogYmFyRGltZW5zaW9ucy5oZWlnaHQgPCAobWVhc3VyZW1lbnQuaGVpZ2h0KTsKICAgICAgICAgICAgcmV0dXJuIHRvb1dpZGU7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBMYWJlbHMgYXJlICJvbi1iYXIiIGJ5IGRlZmF1bHQsIGJ1dCBpZiB0aGUgYmFyIGlzIG5vdCBsb25nIGVub3VnaCB0byBmaXQgdGhlIHRleHQsCiAgICAgICAgICogd2UgY2FuIHRyeSBwdXR0aW5nIHRoZSBsYWJlbCAib2ZmLWJhciIsIGlmIHRoZXJlJ3MgZW5vdWdoIHNwYWNlIG91dHNpZGUgb2YgdGhlIGJhcgogICAgICAgICAqIHRvIGZpdCBpdC4KICAgICAgICAgKi8KICAgICAgICBCYXIucHJvdG90eXBlLl9zaG91bGRTaG93TGFiZWxPbkJhciA9IGZ1bmN0aW9uIChiYXJDb29yZGluYXRlcywgYmFyRGltZW5zaW9ucywgbGFiZWxEaW1lbnNpb25zKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9sYWJlbHNQb3NpdGlvbiA9PT0gZXhwb3J0cy5MYWJlbHNQb3NpdGlvbi5vdXRzaWRlKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGJhclN0YXJ0ID0gdGhpcy5faXNWZXJ0aWNhbCA/IGJhckNvb3JkaW5hdGVzLnkgOiBiYXJDb29yZGluYXRlcy54OwogICAgICAgICAgICB2YXIgYmFyTGVuZ3RoID0gdGhpcy5faXNWZXJ0aWNhbCA/IGJhckRpbWVuc2lvbnMuaGVpZ2h0IDogYmFyRGltZW5zaW9ucy53aWR0aDsKICAgICAgICAgICAgdmFyIHRvdGFsTGVuZ3RoID0gdGhpcy5faXNWZXJ0aWNhbCA/IHRoaXMuaGVpZ2h0KCkgOiB0aGlzLndpZHRoKCk7CiAgICAgICAgICAgIHZhciBsYWJlbExlbmd0aCA9IHRoaXMuX2lzVmVydGljYWwgPyBsYWJlbERpbWVuc2lvbnMuaGVpZ2h0IDogbGFiZWxEaW1lbnNpb25zLndpZHRoOwogICAgICAgICAgICB2YXIgYmFyRW5kID0gYmFyU3RhcnQgKyBiYXJMZW5ndGg7CiAgICAgICAgICAgIHZhciBiYXJMZW5ndGhWaXNpYmxlT25TY3JlZW4gPSBiYXJMZW5ndGg7CiAgICAgICAgICAgIGlmIChiYXJFbmQgPiB0b3RhbExlbmd0aCkgewogICAgICAgICAgICAgICAgYmFyTGVuZ3RoVmlzaWJsZU9uU2NyZWVuID0gdG90YWxMZW5ndGggLSBiYXJTdGFydDsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmIChiYXJTdGFydCA8IDApIHsKICAgICAgICAgICAgICAgIGJhckxlbmd0aFZpc2libGVPblNjcmVlbiA9IGJhckVuZDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gKGxhYmVsTGVuZ3RoICsgQmFyLl9MQUJFTF9NQVJHSU5fSU5TSURFX0JBUiA8PSBiYXJMZW5ndGhWaXNpYmxlT25TY3JlZW4pOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fY2FsY3VsYXRlTGFiZWxQcm9wZXJ0aWVzID0gZnVuY3Rpb24gKGJhckNvb3JkaW5hdGVzLCBiYXJEaW1lbnNpb25zLCBtZWFzdXJlbWVudCwgc2hvd0xhYmVsT25CYXIsIGFib3ZlT3JMZWZ0T2ZCYXNlbGluZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgYmFyQ29vcmRpbmF0ZSA9IHRoaXMuX2lzVmVydGljYWwgPyBiYXJDb29yZGluYXRlcy55IDogYmFyQ29vcmRpbmF0ZXMueDsKICAgICAgICAgICAgdmFyIGJhckRpbWVuc2lvbiA9IHRoaXMuX2lzVmVydGljYWwgPyBiYXJEaW1lbnNpb25zLmhlaWdodCA6IGJhckRpbWVuc2lvbnMud2lkdGg7CiAgICAgICAgICAgIHZhciBtZWFzdXJlbWVudERpbWVuc2lvbiA9IHRoaXMuX2lzVmVydGljYWwgPyBtZWFzdXJlbWVudC5oZWlnaHQgOiBtZWFzdXJlbWVudC53aWR0aDsKICAgICAgICAgICAgdmFyIGFsaWdubWVudERpbWVuc2lvbiA9ICJjZW50ZXIiOwogICAgICAgICAgICB2YXIgY29udGFpbmVyRGltZW5zaW9uID0gYmFyRGltZW5zaW9uOwogICAgICAgICAgICB2YXIgbGFiZWxDb250YWluZXJPcmlnaW5Db29yZGluYXRlID0gYmFyQ29vcmRpbmF0ZTsKICAgICAgICAgICAgdmFyIGxhYmVsT3JpZ2luQ29vcmRpbmF0ZSA9IGJhckNvb3JkaW5hdGU7CiAgICAgICAgICAgIHZhciB1cGRhdGVDb29yZGluYXRlcyA9IGZ1bmN0aW9uIChwb3NpdGlvbikgewogICAgICAgICAgICAgICAgc3dpdGNoIChwb3NpdGlvbikgewogICAgICAgICAgICAgICAgICAgIGNhc2UgInRvcExlZnQiOgogICAgICAgICAgICAgICAgICAgICAgICBhbGlnbm1lbnREaW1lbnNpb24gPSBfdGhpcy5faXNWZXJ0aWNhbCA/ICJ0b3AiIDogImxlZnQiOwogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbENvbnRhaW5lck9yaWdpbkNvb3JkaW5hdGUgKz0gQmFyLl9MQUJFTF9NQVJHSU5fSU5TSURFX0JBUjsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxPcmlnaW5Db29yZGluYXRlICs9IEJhci5fTEFCRUxfTUFSR0lOX0lOU0lERV9CQVI7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICBjYXNlICJjZW50ZXIiOgogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbE9yaWdpbkNvb3JkaW5hdGUgKz0gKGJhckRpbWVuc2lvbiArIG1lYXN1cmVtZW50RGltZW5zaW9uKSAvIDI7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICBjYXNlICJib3R0b21SaWdodCI6CiAgICAgICAgICAgICAgICAgICAgICAgIGFsaWdubWVudERpbWVuc2lvbiA9IF90aGlzLl9pc1ZlcnRpY2FsID8gImJvdHRvbSIgOiAicmlnaHQiOwogICAgICAgICAgICAgICAgICAgICAgICBsYWJlbENvbnRhaW5lck9yaWdpbkNvb3JkaW5hdGUgLT0gQmFyLl9MQUJFTF9NQVJHSU5fSU5TSURFX0JBUjsKICAgICAgICAgICAgICAgICAgICAgICAgbGFiZWxPcmlnaW5Db29yZGluYXRlICs9IGNvbnRhaW5lckRpbWVuc2lvbiAtIEJhci5fTEFCRUxfTUFSR0lOX0lOU0lERV9CQVIgLSBtZWFzdXJlbWVudERpbWVuc2lvbjsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgICAgICBpZiAoc2hvd0xhYmVsT25CYXIpIHsKICAgICAgICAgICAgICAgIHN3aXRjaCAodGhpcy5fbGFiZWxzUG9zaXRpb24pIHsKICAgICAgICAgICAgICAgICAgICBjYXNlIGV4cG9ydHMuTGFiZWxzUG9zaXRpb24uc3RhcnQ6CiAgICAgICAgICAgICAgICAgICAgICAgIGFib3ZlT3JMZWZ0T2ZCYXNlbGluZSA/IHVwZGF0ZUNvb3JkaW5hdGVzKCJib3R0b21SaWdodCIpIDogdXBkYXRlQ29vcmRpbmF0ZXMoInRvcExlZnQiKTsKICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgY2FzZSBleHBvcnRzLkxhYmVsc1Bvc2l0aW9uLm1pZGRsZToKICAgICAgICAgICAgICAgICAgICAgICAgdXBkYXRlQ29vcmRpbmF0ZXMoImNlbnRlciIpOwogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICBjYXNlIGV4cG9ydHMuTGFiZWxzUG9zaXRpb24uZW5kOgogICAgICAgICAgICAgICAgICAgICAgICBhYm92ZU9yTGVmdE9mQmFzZWxpbmUgPyB1cGRhdGVDb29yZGluYXRlcygidG9wTGVmdCIpIDogdXBkYXRlQ29vcmRpbmF0ZXMoImJvdHRvbVJpZ2h0Iik7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgaWYgKGFib3ZlT3JMZWZ0T2ZCYXNlbGluZSkgewogICAgICAgICAgICAgICAgICAgIGFsaWdubWVudERpbWVuc2lvbiA9IHRoaXMuX2lzVmVydGljYWwgPyAidG9wIiA6ICJsZWZ0IjsKICAgICAgICAgICAgICAgICAgICBjb250YWluZXJEaW1lbnNpb24gPSBiYXJEaW1lbnNpb24gKyBCYXIuX0xBQkVMX01BUkdJTl9JTlNJREVfQkFSICsgbWVhc3VyZW1lbnREaW1lbnNpb247CiAgICAgICAgICAgICAgICAgICAgbGFiZWxDb250YWluZXJPcmlnaW5Db29yZGluYXRlIC09IEJhci5fTEFCRUxfTUFSR0lOX0lOU0lERV9CQVIgKyBtZWFzdXJlbWVudERpbWVuc2lvbjsKICAgICAgICAgICAgICAgICAgICBsYWJlbE9yaWdpbkNvb3JkaW5hdGUgLT0gQmFyLl9MQUJFTF9NQVJHSU5fSU5TSURFX0JBUiArIG1lYXN1cmVtZW50RGltZW5zaW9uOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgYWxpZ25tZW50RGltZW5zaW9uID0gdGhpcy5faXNWZXJ0aWNhbCA/ICJib3R0b20iIDogInJpZ2h0IjsKICAgICAgICAgICAgICAgICAgICBjb250YWluZXJEaW1lbnNpb24gPSBiYXJEaW1lbnNpb24gKyBCYXIuX0xBQkVMX01BUkdJTl9JTlNJREVfQkFSICsgbWVhc3VyZW1lbnREaW1lbnNpb247CiAgICAgICAgICAgICAgICAgICAgbGFiZWxPcmlnaW5Db29yZGluYXRlICs9IGJhckRpbWVuc2lvbiArIEJhci5fTEFCRUxfTUFSR0lOX0lOU0lERV9CQVI7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGNvbnRhaW5lckRpbWVuc2lvbnM6IHsKICAgICAgICAgICAgICAgICAgICB3aWR0aDogdGhpcy5faXNWZXJ0aWNhbCA/IGJhckRpbWVuc2lvbnMud2lkdGggOiBjb250YWluZXJEaW1lbnNpb24sCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0OiB0aGlzLl9pc1ZlcnRpY2FsID8gY29udGFpbmVyRGltZW5zaW9uIDogYmFyRGltZW5zaW9ucy5oZWlnaHQsCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgbGFiZWxDb250YWluZXJPcmlnaW46IHsKICAgICAgICAgICAgICAgICAgICB4OiB0aGlzLl9pc1ZlcnRpY2FsID8gYmFyQ29vcmRpbmF0ZXMueCA6IGxhYmVsQ29udGFpbmVyT3JpZ2luQ29vcmRpbmF0ZSwKICAgICAgICAgICAgICAgICAgICB5OiB0aGlzLl9pc1ZlcnRpY2FsID8gbGFiZWxDb250YWluZXJPcmlnaW5Db29yZGluYXRlIDogYmFyQ29vcmRpbmF0ZXMueSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICBsYWJlbE9yaWdpbjogewogICAgICAgICAgICAgICAgICAgIHg6IHRoaXMuX2lzVmVydGljYWwgPyAoYmFyQ29vcmRpbmF0ZXMueCArIGJhckRpbWVuc2lvbnMud2lkdGggLyAyIC0gbWVhc3VyZW1lbnQud2lkdGggLyAyKSA6IGxhYmVsT3JpZ2luQ29vcmRpbmF0ZSwKICAgICAgICAgICAgICAgICAgICB5OiB0aGlzLl9pc1ZlcnRpY2FsID8gbGFiZWxPcmlnaW5Db29yZGluYXRlIDogKGJhckNvb3JkaW5hdGVzLnkgKyBiYXJEaW1lbnNpb25zLmhlaWdodCAvIDIgLSBtZWFzdXJlbWVudC5oZWlnaHQgLyAyKSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICBhbGlnbm1lbnQ6IHsKICAgICAgICAgICAgICAgICAgICB4OiB0aGlzLl9pc1ZlcnRpY2FsID8gImNlbnRlciIgOiBhbGlnbm1lbnREaW1lbnNpb24sCiAgICAgICAgICAgICAgICAgICAgeTogdGhpcy5faXNWZXJ0aWNhbCA/IGFsaWdubWVudERpbWVuc2lvbiA6ICJjZW50ZXIiLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2NyZWF0ZUxhYmVsQ29udGFpbmVyID0gZnVuY3Rpb24gKGxhYmVsQXJlYSwgbGFiZWxDb250YWluZXJPcmlnaW4sIGxhYmVsT3JpZ2luLCBtZWFzdXJlbWVudCwgc2hvd0xhYmVsT25CYXIsIGNvbG9yKSB7CiAgICAgICAgICAgIHZhciBsYWJlbENvbnRhaW5lciA9IGxhYmVsQXJlYS5hcHBlbmQoImciKS5hdHRyKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyBsYWJlbENvbnRhaW5lck9yaWdpbi54ICsgIiwgIiArIGxhYmVsQ29udGFpbmVyT3JpZ2luLnkgKyAiKSIpOwogICAgICAgICAgICBpZiAoc2hvd0xhYmVsT25CYXIpIHsKICAgICAgICAgICAgICAgIGxhYmVsQ29udGFpbmVyLmNsYXNzZWQoIm9uLWJhci1sYWJlbCIsIHRydWUpOwogICAgICAgICAgICAgICAgdmFyIGRhcmsgPSB1dGlscyQxLkNvbG9yLmNvbnRyYXN0KCJ3aGl0ZSIsIGNvbG9yKSAqIDEuNiA8IHV0aWxzJDEuQ29sb3IuY29udHJhc3QoImJsYWNrIiwgY29sb3IpOwogICAgICAgICAgICAgICAgbGFiZWxDb250YWluZXIuY2xhc3NlZChkYXJrID8gImRhcmstbGFiZWwiIDogImxpZ2h0LWxhYmVsIiwgdHJ1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBsYWJlbENvbnRhaW5lci5jbGFzc2VkKCJvZmYtYmFyLWxhYmVsIiwgdHJ1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGxhYmVsQ29udGFpbmVyOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fZ2VuZXJhdGVEcmF3U3RlcHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBkcmF3U3RlcHMgPSBbXTsKICAgICAgICAgICAgaWYgKHRoaXMuX2FuaW1hdGVPbk5leHRSZW5kZXIoKSkgewogICAgICAgICAgICAgICAgdmFyIHJlc2V0QXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgICAgICB2YXIgbGVuZ3RoU2NhbGUgPSB0aGlzLmxlbmd0aCgpLnNjYWxlOwogICAgICAgICAgICAgICAgdmFyIHNjYWxlZEJhc2VsaW5lXzEgPSBsZW5ndGhTY2FsZS5zY2FsZSh0aGlzLmJhc2VsaW5lVmFsdWUoKSk7CiAgICAgICAgICAgICAgICB2YXIgbGVuZ3RoQXR0ciA9IHRoaXMuX2lzVmVydGljYWwgPyAieSIgOiAieCI7CiAgICAgICAgICAgICAgICB2YXIgdGhpY2tuZXNzQXR0ciA9IHRoaXMuX2lzVmVydGljYWwgPyAiaGVpZ2h0IiA6ICJ3aWR0aCI7CiAgICAgICAgICAgICAgICByZXNldEF0dHJUb1Byb2plY3RvcltsZW5ndGhBdHRyXSA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIHNjYWxlZEJhc2VsaW5lXzE7IH07CiAgICAgICAgICAgICAgICByZXNldEF0dHJUb1Byb2plY3Rvclt0aGlja25lc3NBdHRyXSA9IGZ1bmN0aW9uICgpIHsgcmV0dXJuIDA7IH07CiAgICAgICAgICAgICAgICBkcmF3U3RlcHMucHVzaCh7IGF0dHJUb1Byb2plY3RvcjogcmVzZXRBdHRyVG9Qcm9qZWN0b3IsIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5SRVNFVCkgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZHJhd1N0ZXBzLnB1c2goewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yOiB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKSwKICAgICAgICAgICAgICAgIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5NQUlOKSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkcmF3U3RlcHM7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9nZW5lcmF0ZUF0dHJUb1Byb2plY3RvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHZhciBsZW5ndGhTY2FsZSA9IHRoaXMubGVuZ3RoKCkuc2NhbGU7CiAgICAgICAgICAgIHZhciBzY2FsZWRCYXNlbGluZSA9IGxlbmd0aFNjYWxlLnNjYWxlKHRoaXMuYmFzZWxpbmVWYWx1ZSgpKTsKICAgICAgICAgICAgdmFyIGxlbmd0aEF0dHIgPSB0aGlzLl9pc1ZlcnRpY2FsID8gInkiIDogIngiOwogICAgICAgICAgICB2YXIgcG9zaXRpb25BdHRyID0gdGhpcy5faXNWZXJ0aWNhbCA/ICJ4IiA6ICJ5IjsKICAgICAgICAgICAgdmFyIHBvc2l0aW9uRiA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5wb3NpdGlvbigpKTsKICAgICAgICAgICAgdmFyIG9yaWdpbmFsTGVuZ3RoRm4gPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMubGVuZ3RoKCkpOwogICAgICAgICAgICB2YXIgbGVuZ3RoRm4gPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIE1hdGguYWJzKHNjYWxlZEJhc2VsaW5lIC0gb3JpZ2luYWxMZW5ndGhGbihkLCBpLCBkYXRhc2V0KSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB0aGlja25lc3NGID0gYXR0clRvUHJvamVjdG9yW0Jhci5fQkFSX1RISUNLTkVTU19LRVldOwogICAgICAgICAgICB2YXIgZ2FwRiA9IGF0dHJUb1Byb2plY3RvclsiZ2FwIl07CiAgICAgICAgICAgIHZhciB0aGlja25lc3NNaW51c0dhcCA9IGdhcEYgPT0gbnVsbCA/IHRoaWNrbmVzc0YgOiBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIHRoaWNrID0gdGhpY2tuZXNzRihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIC8vIG9ubHkgc3VidHJhY3QgZ2FwIGlmIGJhcnMgYXJlIGF0IGxlYXN0IDIgcGl4ZWxzIHdpZGUsIG90aGVyd2lzZSBjYW52YXMKICAgICAgICAgICAgICAgIC8vIGludGVycG9sYXRpb24gY2FuIGNhdXNlIGJhcnMgdG8gYmVjb21lIGludmlzaWJsZSBkdWUgdG8gc3VicGl4ZWwKICAgICAgICAgICAgICAgIC8vIHNhbXBsaW5nCiAgICAgICAgICAgICAgICByZXR1cm4gdGhpY2sgPCBCYXIuX0JBUl9HQVBMRVNTX1RIUkVTSE9MRF9QWCA/IHRoaWNrIDogdGhpY2sgLSBnYXBGKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyByZS1pbnRlcnByZXQgIndpZHRoIiBhdHRyIGZyb20gcmVwcmVzZW50aW5nICJ0aGlja25lc3MiIHRvIGFjdHVhbGx5IG1lYW5pbmcKICAgICAgICAgICAgLy8gd2lkdGggKHRoYXQgaXMsIHgtZGlyZWN0aW9uIHNwZWNpZmljKSBhZ2FpbgogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbIndpZHRoIl0gPSB0aGlzLl9pc1ZlcnRpY2FsID8gdGhpY2tuZXNzTWludXNHYXAgOiBsZW5ndGhGbjsKICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXSA9IHRoaXMuX2lzVmVydGljYWwgPyBsZW5ndGhGbiA6IHRoaWNrbmVzc01pbnVzR2FwOwogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbbGVuZ3RoQXR0cl0gPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIG9yaWdpbmFsTGVuZ3RoID0gb3JpZ2luYWxMZW5ndGhGbihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIC8vIElmIGl0IGlzIHBhc3QgdGhlIGJhc2VsaW5lLCBpdCBzaG91bGQgc3RhcnQgYXQgdGhlIGJhc2VsaW5lIHRoZW4gd2lkdGgvaGVpZ2h0CiAgICAgICAgICAgICAgICAvLyBjYXJyaWVzIGl0IG92ZXIuIElmIGl0J3Mgbm90IHBhc3QgdGhlIGJhc2VsaW5lLCBsZWF2ZSBpdCBhdCBvcmlnaW5hbCBwb3NpdGlvbiBhbmQKICAgICAgICAgICAgICAgIC8vIHRoZW4gd2lkdGgvaGVpZ2h0IGNhcnJpZXMgaXQgdG8gYmFzZWxpbmUKICAgICAgICAgICAgICAgIHJldHVybiAob3JpZ2luYWxMZW5ndGggPiBzY2FsZWRCYXNlbGluZSkgPyBzY2FsZWRCYXNlbGluZSA6IG9yaWdpbmFsTGVuZ3RoOwogICAgICAgICAgICB9OwogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbcG9zaXRpb25BdHRyXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2dldFBvc2l0aW9uQXR0cihwb3NpdGlvbkYoZCwgaSwgZGF0YXNldCksIHRoaWNrbmVzc0YoZCwgaSwgZGF0YXNldCkpOwogICAgICAgICAgICB9OwogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fdXBkYXRlVGhpY2tuZXNzQXR0ciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHN0YXJ0UHJvaiA9IHRoaXMucG9zaXRpb24oKTsKICAgICAgICAgICAgdmFyIGVuZFByb2ogPSB0aGlzLmJhckVuZCgpOwogICAgICAgICAgICBpZiAoc3RhcnRQcm9qICE9IG51bGwgJiYgZW5kUHJvaiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9maXhlZEJhclBpeGVsVGhpY2tuZXNzID0gZmFsc2U7CiAgICAgICAgICAgICAgICB0aGlzLmF0dHIoQmFyLl9CQVJfVEhJQ0tORVNTX0tFWSwgZnVuY3Rpb24gKGQsIGksIGRhdGEpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgdjEgPSBzdGFydFByb2ouYWNjZXNzb3IoZCwgaSwgZGF0YSk7CiAgICAgICAgICAgICAgICAgICAgdmFyIHYyID0gZW5kUHJvai5hY2Nlc3NvcihkLCBpLCBkYXRhKTsKICAgICAgICAgICAgICAgICAgICB2MSA9IHN0YXJ0UHJvai5zY2FsZSA/IHN0YXJ0UHJvai5zY2FsZS5zY2FsZSh2MSkgOiB2MTsKICAgICAgICAgICAgICAgICAgICB2MiA9IGVuZFByb2ouc2NhbGUgPyBlbmRQcm9qLnNjYWxlLnNjYWxlKHYyKSA6IHYyOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLmFicyh2MiAtIHYxKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZml4ZWRCYXJQaXhlbFRoaWNrbmVzcyA9IHRydWU7CiAgICAgICAgICAgICAgICB0aGlzLmF0dHIoQmFyLl9CQVJfVEhJQ0tORVNTX0tFWSwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2JhclBpeGVsVGhpY2tuZXNzKCk7IH0pOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9iYXJQaXhlbFRoaWNrbmVzcyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2ZpeGVkQmFyUGl4ZWxUaGlja25lc3MpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9wcm9qZWN0b3JzUmVhZHkoKSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb21wdXRlQmFyUGl4ZWxUaGlja25lc3ModGhpcy5wb3NpdGlvbigpLCB0aGlzLmRhdGFzZXRzKCksIHRoaXMuX2lzVmVydGljYWwgPyB0aGlzLndpZHRoKCkgOiB0aGlzLmhlaWdodCgpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuZW50aXRpZXMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgaWYgKGRhdGFzZXRzID09PSB2b2lkIDApIHsgZGF0YXNldHMgPSB0aGlzLmRhdGFzZXRzKCk7IH0KICAgICAgICAgICAgaWYgKCF0aGlzLl9wcm9qZWN0b3JzUmVhZHkoKSkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBlbnRpdGllcyA9IF9zdXBlci5wcm90b3R5cGUuZW50aXRpZXMuY2FsbCh0aGlzLCBkYXRhc2V0cyk7CiAgICAgICAgICAgIHJldHVybiBlbnRpdGllczsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2VudGl0eUJvdW5kcyA9IGZ1bmN0aW9uIChlbnRpdHkpIHsKICAgICAgICAgICAgdmFyIGRhdHVtID0gZW50aXR5LmRhdHVtLCBpbmRleCA9IGVudGl0eS5pbmRleCwgZGF0YXNldCA9IGVudGl0eS5kYXRhc2V0OwogICAgICAgICAgICByZXR1cm4gdGhpcy5fcGl4ZWxCb3VuZHMoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIFRoZSByZWN0YW5ndWxhciBib3VuZHMgb2YgYSBiYXIuIE5vdGUgdGhhdCB0aGUgeC95IGNvb3JkaW5hdGVzIGFyZSBub3QgdGhlCiAgICAgICAgICogc2FtZSBhcyB0aGUgInBpeGVsIHBvaW50IiBiZWNhdXNlIHRoZXkgYXJlIGFsd2F5cyBhdCB0aGUgdG9wL2xlZnQgb2YgdGhlCiAgICAgICAgICogYmFyLgogICAgICAgICAqLwogICAgICAgIEJhci5wcm90b3R5cGUuX3BpeGVsQm91bmRzID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICB4OiBhdHRyVG9Qcm9qZWN0b3JbIngiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpLAogICAgICAgICAgICAgICAgeTogYXR0clRvUHJvamVjdG9yWyJ5Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwKICAgICAgICAgICAgICAgIHdpZHRoOiBhdHRyVG9Qcm9qZWN0b3JbIndpZHRoIl0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwKICAgICAgICAgICAgICAgIGhlaWdodDogYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgLyoqCiAgICAgICAgICogVGhlICJwaXhlbCBwb2ludCIgb2YgYSBiYXIgaXMgdGhlIGZhcnRoZXN0IHBvaW50IGZyb20gdGhlIGJhc2VsaW5lLgogICAgICAgICAqCiAgICAgICAgICogRm9yIGV4YW1wbGUsIGluIGEgdmVydGljYWwgYmFyIGNoYXJ0IHdpdGggcG9zaXRpdmUgYmFyIHZhbHVlcywgdGhlIHBpeGVsCiAgICAgICAgICogcG9pbnQgd2lsbCBiZSBhdCB0aGUgdG9wIG9mIHRoZSBiYXIuIEZvciBuZWdhdGl2ZSBiYXIgdmFsdWVzLCB0aGUgcGl4ZWwKICAgICAgICAgKiBwb2ludCB3aWxsIGJlIGF0IHRoZSBib3R0b20gb2YgdGhlIGJhci4KICAgICAgICAgKi8KICAgICAgICBCYXIucHJvdG90eXBlLl9waXhlbFBvaW50ID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICB2YXIgcmVjdCA9IHRoaXMuX3BpeGVsQm91bmRzKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgIHZhciBvcmlnaW5hbFBvc2l0aW9uID0gKHRoaXMuX2lzVmVydGljYWwgPyBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKSA6IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54KCkpKShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgc2NhbGVkQmFzZWxpbmUgPSAodGhpcy5faXNWZXJ0aWNhbCA/IHRoaXMueSgpLnNjYWxlIDogdGhpcy54KCkuc2NhbGUpLnNjYWxlKHRoaXMuYmFzZWxpbmVWYWx1ZSgpKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3BpeGVsUG9pbnRCYXIob3JpZ2luYWxQb3NpdGlvbiwgc2NhbGVkQmFzZWxpbmUsIHJlY3QpOwogICAgICAgIH07CiAgICAgICAgQmFyLnByb3RvdHlwZS5fcGl4ZWxQb2ludEJhciA9IGZ1bmN0aW9uIChvcmlnaW5hbFBvc2l0aW9uLCBzY2FsZWRCYXNlbGluZSwgcmVjdCkgewogICAgICAgICAgICB2YXIgeCwgeTsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzVmVydGljYWwpIHsKICAgICAgICAgICAgICAgIHggPSByZWN0LnggKyByZWN0LndpZHRoIC8gMjsKICAgICAgICAgICAgICAgIHkgPSBvcmlnaW5hbFBvc2l0aW9uIDw9IHNjYWxlZEJhc2VsaW5lID8gcmVjdC55IDogcmVjdC55ICsgcmVjdC5oZWlnaHQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB4ID0gb3JpZ2luYWxQb3NpdGlvbiA+PSBzY2FsZWRCYXNlbGluZSA/IHJlY3QueCArIHJlY3Qud2lkdGggOiByZWN0Lng7CiAgICAgICAgICAgICAgICB5ID0gcmVjdC55ICsgcmVjdC5oZWlnaHQgLyAyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB7IHg6IHgsIHk6IHkgfTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX3VuaW5zdGFsbFNjYWxlRm9yS2V5ID0gZnVuY3Rpb24gKHNjYWxlLCBrZXkpIHsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5fdW5pbnN0YWxsU2NhbGVGb3JLZXkuY2FsbCh0aGlzLCBzY2FsZSwga2V5KTsKICAgICAgICB9OwogICAgICAgIEJhci5wcm90b3R5cGUuX2dldERhdGFUb0RyYXcgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBkYXRhVG9EcmF3ID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgdmFyIHBsb3RXaWR0aCA9IHRoaXMud2lkdGgoKTsKICAgICAgICAgICAgdmFyIHBsb3RIZWlnaHQgPSB0aGlzLmhlaWdodCgpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKS5tYXAoZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgaXNWYWxpZCA9IF90aGlzLl9pc0RhdHVtT25TY3JlZW4oYXR0clRvUHJvamVjdG9yLCBwbG90V2lkdGgsIHBsb3RIZWlnaHQsIGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBpc1ZhbGlkID8gZCA6IG51bGw7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRhdGFzZXQsIGRhdGEpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGRhdGFUb0RyYXc7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLl9pc0RhdHVtT25TY3JlZW4gPSBmdW5jdGlvbiAoYXR0clRvUHJvamVjdG9yLCBwbG90V2lkdGgsIHBsb3RIZWlnaHQsIGQsIGksIGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIHBpeGVsWCA9IGF0dHJUb1Byb2plY3RvclsieCJdKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgcGl4ZWxZID0gYXR0clRvUHJvamVjdG9yWyJ5Il0oZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgIHZhciBwaXhlbFdpZHRoID0gYXR0clRvUHJvamVjdG9yWyJ3aWR0aCJdKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgcGl4ZWxIZWlnaHQgPSBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgaXNWYWxpZCA9IHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHBpeGVsWCkgJiYKICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHBpeGVsWSkgJiYKICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHBpeGVsV2lkdGgpICYmCiAgICAgICAgICAgICAgICB1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihwaXhlbEhlaWdodCk7CiAgICAgICAgICAgIGlmICghaXNWYWxpZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB1dGlscyQxLk1hdGguYm91bmRzSW50ZXJzZWN0cyhwaXhlbFgsIHBpeGVsWSwgcGl4ZWxXaWR0aCwgcGl4ZWxIZWlnaHQsIDAsIDAsIHBsb3RXaWR0aCwgcGxvdEhlaWdodCk7CiAgICAgICAgfTsKICAgICAgICBCYXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS5pbnZhbGlkYXRlQ2FjaGUuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9sYWJlbENvbmZpZy5nZXQoZGF0YXNldCkubWVhc3VyZXIucmVzZXQoKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBCYXIuX0JBUl9USElDS05FU1NfUkFUSU8gPSAwLjk1OwogICAgICAgIEJhci5fQkFSX0dBUExFU1NfVEhSRVNIT0xEX1BYID0gMzsKICAgICAgICBCYXIuX1NJTkdMRV9CQVJfRElNRU5TSU9OX1JBVElPID0gMC40OwogICAgICAgIEJhci5fQkFSX0FSRUFfQ0xBU1MgPSAiYmFyLWFyZWEiOwogICAgICAgIEJhci5fQkFSX0VORF9LRVkgPSAiYmFyRW5kIjsKICAgICAgICAvLyB3ZSBzcGVjaWFsIGNhc2UgdGhlICJ3aWR0aCIgcHJvcGVydHkgdG8gcmVwcmVzZW50IHRoZSBiYXIgdGhpY2tuZXNzCiAgICAgICAgLy8gKGFrYSB0aGUgZGlzdGFuY2UgYmV0d2VlbiBhZGphY2VudCBiYXIgcG9zaXRpb25zKTsgaW4gX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yCiAgICAgICAgLy8gd2UgcmUtYXNzaWduICJ3aWR0aCIgdG8gc3BlY2lmaWNhbGx5IHJlZmVyIHRvIDxyZWN0PidzIHdpZHRoIGF0dHJpYnV0ZQogICAgICAgIEJhci5fQkFSX1RISUNLTkVTU19LRVkgPSAid2lkdGgiOwogICAgICAgIEJhci5fTEFCRUxfQVJFQV9DTEFTUyA9ICJiYXItbGFiZWwtdGV4dC1hcmVhIjsKICAgICAgICAvKioKICAgICAgICAgKiBJbiB0aGUgY2FzZSBvZiAic3RhcnQiIG9yICJlbmQiIExhYmVsUG9zaXRpb25zLCBwdXQgdGhlIGxhYmVsIHRoaXMgbWFueSBweCBhd2F5CiAgICAgICAgICogZnJvbSB0aGUgYmFyJ3MgbGVuZ3RoIGRpc3RhbmNlIGVkZ2UKICAgICAgICAgKi8KICAgICAgICBCYXIuX0xBQkVMX01BUkdJTl9JTlNJREVfQkFSID0gMTA7CiAgICAgICAgcmV0dXJuIEJhcjsKICAgIH0oeHlQbG90LlhZUGxvdCkpOwogICAgZXhwb3J0cy5CYXIgPSBCYXI7CiAgICAvKioKICAgICAqIENvbXB1dGVzIHRoZSBiYXJQaXhlbFRoaWNrbmVzcyBvZiBhbGwgdGhlIGJhcnMgaW4gdGhlIHBsb3QuCiAgICAgKgogICAgICogSWYgdGhlIHBvc2l0aW9uIHNjYWxlIG9mIHRoZSBwbG90IGlzIGEgQ2F0ZWdvcnlTY2FsZSBhbmQgaW4gYmFuZHMgbW9kZSwgdGhlbiB0aGUgcmFuZ2VCYW5kcyBmdW5jdGlvbiB3aWxsIGJlIHVzZWQuCiAgICAgKiBJZiB0aGUgcG9zaXRpb24gc2NhbGUgb2YgdGhlIHBsb3QgaXMgYSBRdWFudGl0YXRpdmVTY2FsZSwgdGhlbiB0aGUgYmFyIHRoaWNrbmVzcyBpcyBlcXVhbCB0byB0aGUgc21hbGxlc3QgZGlzdGFuY2UgYmV0d2VlbgogICAgICogdHdvIGFkamFjZW50IGRhdGEgcG9pbnRzLCBwYWRkZWQgZm9yIHZpc3VhbGlzYXRpb24uCiAgICAgKgogICAgICogVGhpcyBpcyBpZ25vcmVkIHdoZW4gZXhwbGljaXRseSBzZXR0aW5nIHRoZSBiYXJFbmQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbXB1dGVCYXJQaXhlbFRoaWNrbmVzcyhwb3NpdGlvbkJpbmRpbmcsIGRhdGFzZXRzLCBwbG90UG9zaXRpb25EaW1lbnNpb25MZW5ndGgpIHsKICAgICAgICB2YXIgYmFyUGl4ZWxUaGlja25lc3M7CiAgICAgICAgdmFyIHBvc2l0aW9uU2NhbGUgPSBwb3NpdGlvbkJpbmRpbmcuc2NhbGU7CiAgICAgICAgaWYgKHBvc2l0aW9uU2NhbGUgaW5zdGFuY2VvZiBzY2FsZXMuQ2F0ZWdvcnkpIHsKICAgICAgICAgICAgYmFyUGl4ZWxUaGlja25lc3MgPSBwb3NpdGlvblNjYWxlLnJhbmdlQmFuZCgpOwogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgdmFyIHBvc2l0aW9uQWNjZXNzb3JfMSA9IHBvc2l0aW9uQmluZGluZy5hY2Nlc3NvcjsKICAgICAgICAgICAgdmFyIG51bWJlckJhckFjY2Vzc29yRGF0YSA9IGQzLnNldCh1dGlscyQxLkFycmF5LmZsYXR0ZW4oZGF0YXNldHMubWFwKGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZGF0YXNldC5kYXRhKCkubWFwKGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBwb3NpdGlvbkFjY2Vzc29yXzEoZCwgaSwgZGF0YXNldCk7IH0pCiAgICAgICAgICAgICAgICAgICAgLmZpbHRlcihmdW5jdGlvbiAoZCkgeyByZXR1cm4gZCAhPSBudWxsOyB9KQogICAgICAgICAgICAgICAgICAgIC5tYXAoZnVuY3Rpb24gKGQpIHsgcmV0dXJuIGQudmFsdWVPZigpOyB9KTsKICAgICAgICAgICAgfSkpKS52YWx1ZXMoKS5tYXAoZnVuY3Rpb24gKHZhbHVlKSB7IHJldHVybiArdmFsdWU7IH0pOwogICAgICAgICAgICBudW1iZXJCYXJBY2Nlc3NvckRhdGEuc29ydChmdW5jdGlvbiAoYSwgYikgeyByZXR1cm4gYSAtIGI7IH0pOwogICAgICAgICAgICB2YXIgc2NhbGVkRGF0YSA9IG51bWJlckJhckFjY2Vzc29yRGF0YS5tYXAoZnVuY3Rpb24gKGRhdHVtKSB7IHJldHVybiBwb3NpdGlvblNjYWxlLnNjYWxlKGRhdHVtKTsgfSk7CiAgICAgICAgICAgIHZhciBiYXJBY2Nlc3NvckRhdGFQYWlycyA9IGQzLnBhaXJzKHNjYWxlZERhdGEpOwogICAgICAgICAgICBiYXJQaXhlbFRoaWNrbmVzcyA9IHV0aWxzJDEuTWF0aC5taW4oYmFyQWNjZXNzb3JEYXRhUGFpcnMsIGZ1bmN0aW9uIChwYWlyLCBpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5hYnMocGFpclsxXSAtIHBhaXJbMF0pOwogICAgICAgICAgICB9LCBwbG90UG9zaXRpb25EaW1lbnNpb25MZW5ndGggKiBCYXIuX1NJTkdMRV9CQVJfRElNRU5TSU9OX1JBVElPKTsKICAgICAgICAgICAgYmFyUGl4ZWxUaGlja25lc3MgKj0gQmFyLl9CQVJfVEhJQ0tORVNTX1JBVElPOwogICAgICAgIH0KICAgICAgICByZXR1cm4gYmFyUGl4ZWxUaGlja25lc3M7CiAgICB9CiAgICB9KTsKCiAgICB2YXIgY2x1c3RlcmVkQmFyUGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCiAgICB2YXIgQ2x1c3RlcmVkQmFyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoQ2x1c3RlcmVkQmFyLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEEgQ2x1c3RlcmVkQmFyIFBsb3QgZ3JvdXBzIGJhcnMgYWNyb3NzIERhdGFzZXRzIGJhc2VkIG9uIHRoZSBwcmltYXJ5IHZhbHVlIG9mIHRoZSBiYXJzLgogICAgICAgICAqICAgT24gYSB2ZXJ0aWNhbCBDbHVzdGVyZWRCYXIgUGxvdCwgdGhlIGJhcnMgd2l0aCB0aGUgc2FtZSBYIHZhbHVlIGFyZSBncm91cGVkLgogICAgICAgICAqICAgT24gYSBob3Jpem9udGFsIENsdXN0ZXJlZEJhciBQbG90LCB0aGUgYmFycyB3aXRoIHRoZSBzYW1lIFkgdmFsdWUgYXJlIGdyb3VwZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW29yaWVudGF0aW9uPSJ2ZXJ0aWNhbCJdIE9uZSBvZiAidmVydGljYWwiLyJob3Jpem9udGFsIi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBDbHVzdGVyZWRCYXIob3JpZW50YXRpb24pIHsKICAgICAgICAgICAgaWYgKG9yaWVudGF0aW9uID09PSB2b2lkIDApIHsgb3JpZW50YXRpb24gPSAidmVydGljYWwiOyB9CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMsIG9yaWVudGF0aW9uKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fY2x1c3Rlck9mZnNldHMgPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBDbHVzdGVyZWRCYXIucHJvdG90eXBlLl9nZW5lcmF0ZUF0dHJUb1Byb2plY3RvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yLmNhbGwodGhpcyk7CiAgICAgICAgICAgIC8vIHRoZSB3aWR0aCBpcyBjb25zdGFudCwgc28gc2V0IHRoZSBpbm5lciBzY2FsZSByYW5nZSB0byB0aGF0CiAgICAgICAgICAgIHZhciBpbm5lclNjYWxlID0gdGhpcy5fbWFrZUlubmVyU2NhbGUoKTsKICAgICAgICAgICAgdmFyIGlubmVyV2lkdGhGID0gZnVuY3Rpb24gKGQsIGkpIHsgcmV0dXJuIGlubmVyU2NhbGUucmFuZ2VCYW5kKCk7IH07CiAgICAgICAgICAgIGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXSA9IHRoaXMuX2lzVmVydGljYWwgPyBpbm5lcldpZHRoRiA6IGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXTsKICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXSA9ICF0aGlzLl9pc1ZlcnRpY2FsID8gaW5uZXJXaWR0aEYgOiBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdOwogICAgICAgICAgICB2YXIgeEF0dHIgPSBhdHRyVG9Qcm9qZWN0b3JbIngiXTsKICAgICAgICAgICAgdmFyIHlBdHRyID0gYXR0clRvUHJvamVjdG9yWyJ5Il07CiAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsieCJdID0gdGhpcy5faXNWZXJ0aWNhbCA/CiAgICAgICAgICAgICAgICBmdW5jdGlvbiAoZCwgaSwgZHMpIHsgcmV0dXJuIHhBdHRyKGQsIGksIGRzKSArIF90aGlzLl9jbHVzdGVyT2Zmc2V0cy5nZXQoZHMpOyB9IDoKICAgICAgICAgICAgICAgIGZ1bmN0aW9uIChkLCBpLCBkcykgeyByZXR1cm4geEF0dHIoZCwgaSwgZHMpOyB9OwogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbInkiXSA9IHRoaXMuX2lzVmVydGljYWwgPwogICAgICAgICAgICAgICAgZnVuY3Rpb24gKGQsIGksIGRzKSB7IHJldHVybiB5QXR0cihkLCBpLCBkcyk7IH0gOgogICAgICAgICAgICAgICAgZnVuY3Rpb24gKGQsIGksIGRzKSB7IHJldHVybiB5QXR0cihkLCBpLCBkcykgKyBfdGhpcy5fY2x1c3Rlck9mZnNldHMuZ2V0KGRzKTsgfTsKICAgICAgICAgICAgcmV0dXJuIGF0dHJUb1Byb2plY3RvcjsKICAgICAgICB9OwogICAgICAgIENsdXN0ZXJlZEJhci5wcm90b3R5cGUuX3VwZGF0ZUNsdXN0ZXJQb3NpdGlvbiA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGlubmVyU2NhbGUgPSB0aGlzLl9tYWtlSW5uZXJTY2FsZSgpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZCwgaSkgeyByZXR1cm4gX3RoaXMuX2NsdXN0ZXJPZmZzZXRzLnNldChkLCBpbm5lclNjYWxlLnNjYWxlKFN0cmluZyhpKSkgLSBpbm5lclNjYWxlLnJhbmdlQmFuZCgpIC8gMik7IH0pOwogICAgICAgIH07CiAgICAgICAgQ2x1c3RlcmVkQmFyLnByb3RvdHlwZS5fbWFrZUlubmVyU2NhbGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBpbm5lclNjYWxlID0gbmV3IHNjYWxlcy5DYXRlZ29yeSgpOwogICAgICAgICAgICBpbm5lclNjYWxlLmRvbWFpbih0aGlzLmRhdGFzZXRzKCkubWFwKGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBTdHJpbmcoaSk7IH0pKTsKICAgICAgICAgICAgdmFyIHdpZHRoUHJvamVjdG9yID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLmF0dHIoYmFyUGxvdC5CYXIuX0JBUl9USElDS05FU1NfS0VZKSk7CiAgICAgICAgICAgIGlubmVyU2NhbGUucmFuZ2UoWzAsIHdpZHRoUHJvamVjdG9yKG51bGwsIDAsIG51bGwpXSk7CiAgICAgICAgICAgIHJldHVybiBpbm5lclNjYWxlOwogICAgICAgIH07CiAgICAgICAgQ2x1c3RlcmVkQmFyLnByb3RvdHlwZS5fZ2V0RGF0YVRvRHJhdyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlQ2x1c3RlclBvc2l0aW9uKCk7CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLl9nZXREYXRhVG9EcmF3LmNhbGwodGhpcyk7CiAgICAgICAgfTsKICAgICAgICByZXR1cm4gQ2x1c3RlcmVkQmFyOwogICAgfShiYXJQbG90LkJhcikpOwogICAgZXhwb3J0cy5DbHVzdGVyZWRCYXIgPSBDbHVzdGVyZWRCYXI7CiAgICB9KTsKCiAgICB2YXIgcGllUGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgoKCgoKCgogICAgdmFyIFBpZSA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFBpZSwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBQaWUoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9zdGFydEFuZ2xlID0gMDsKICAgICAgICAgICAgX3RoaXMuX2VuZEFuZ2xlID0gMiAqIE1hdGguUEk7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbEZvcm1hdHRlciA9IGZvcm1hdHRlcnMuaWRlbnRpdHkoKTsKICAgICAgICAgICAgX3RoaXMuX2xhYmVsc0VuYWJsZWQgPSBmYWxzZTsKICAgICAgICAgICAgX3RoaXMuaW5uZXJSYWRpdXMoMCk7CiAgICAgICAgICAgIF90aGlzLm91dGVyUmFkaXVzKGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHZhciBwaWVDZW50ZXIgPSBfdGhpcy5fcGllQ2VudGVyKCk7CiAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5taW4oTWF0aC5tYXgoX3RoaXMud2lkdGgoKSAtIHBpZUNlbnRlci54LCBwaWVDZW50ZXIueCksIE1hdGgubWF4KF90aGlzLmhlaWdodCgpIC0gcGllQ2VudGVyLnksIHBpZUNlbnRlci55KSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygicGllLXBsb3QiKTsKICAgICAgICAgICAgX3RoaXMuYXR0cigiZmlsbCIsIGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBTdHJpbmcoaSk7IH0sIG5ldyBzY2FsZXMuQ29sb3IoKSk7CiAgICAgICAgICAgIF90aGlzLl9zdHJva2VEcmF3ZXJzID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgUGllLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX3N0cm9rZURyYXdlcnMuZm9yRWFjaChmdW5jdGlvbiAoZCkgeyByZXR1cm4gZC5hdHRhY2hUbyhfdGhpcy5fcmVuZGVyQXJlYSk7IH0pOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5jb21wdXRlTGF5b3V0ID0gZnVuY3Rpb24gKG9yaWdpbiwgYXZhaWxhYmxlV2lkdGgsIGF2YWlsYWJsZUhlaWdodCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmNvbXB1dGVMYXlvdXQuY2FsbCh0aGlzLCBvcmlnaW4sIGF2YWlsYWJsZVdpZHRoLCBhdmFpbGFibGVIZWlnaHQpOwogICAgICAgICAgICB2YXIgcGllQ2VudGVyID0gdGhpcy5fcGllQ2VudGVyKCk7CiAgICAgICAgICAgIHRoaXMuX3JlbmRlckFyZWEuYXR0cigidHJhbnNmb3JtIiwgInRyYW5zbGF0ZSgiICsgcGllQ2VudGVyLnggKyAiLCIgKyBwaWVDZW50ZXIueSArICIpIik7CiAgICAgICAgICAgIHZhciByYWRpdXNMaW1pdCA9IE1hdGgubWluKE1hdGgubWF4KHRoaXMud2lkdGgoKSAtIHBpZUNlbnRlci54LCBwaWVDZW50ZXIueCksIE1hdGgubWF4KHRoaXMuaGVpZ2h0KCkgLSBwaWVDZW50ZXIueSwgcGllQ2VudGVyLnkpKTsKICAgICAgICAgICAgaWYgKHRoaXMuaW5uZXJSYWRpdXMoKS5zY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLmlubmVyUmFkaXVzKCkuc2NhbGUucmFuZ2UoWzAsIHJhZGl1c0xpbWl0XSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMub3V0ZXJSYWRpdXMoKS5zY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLm91dGVyUmFkaXVzKCkuc2NhbGUucmFuZ2UoWzAsIHJhZGl1c0xpbWl0XSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLmFkZERhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmFkZERhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLl9hZGREYXRhc2V0ID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuZGF0YXNldHMoKS5sZW5ndGggPT09IDEpIHsKICAgICAgICAgICAgICAgIHV0aWxzJDEuV2luZG93Lndhcm4oIk9ubHkgb25lIGRhdGFzZXQgaXMgc3VwcG9ydGVkIGluIFBpZSBwbG90cyIpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fdXBkYXRlUGllQW5nbGVzKCk7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX2FkZERhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIHN0cm9rZURyYXdlciA9IG5ldyBhcmNPdXRsaW5lRHJhd2VyLkFyY091dGxpbmVTVkdEcmF3ZXIoKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2lzU2V0dXApIHsKICAgICAgICAgICAgICAgIHN0cm9rZURyYXdlci5hdHRhY2hUbyh0aGlzLl9yZW5kZXJBcmVhKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9zdHJva2VEcmF3ZXJzLnNldChkYXRhc2V0LCBzdHJva2VEcmF3ZXIpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUucmVtb3ZlRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUucmVtb3ZlRGF0YXNldC5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXROb2RlcyA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXROb2Rlcy5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICB0aGlzLl9zdHJva2VEcmF3ZXJzLmdldChkYXRhc2V0KS5yZW1vdmUoKTsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX3JlbW92ZURhdGFzZXQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0LmNhbGwodGhpcywgZGF0YXNldCk7CiAgICAgICAgICAgIHRoaXMuX3N0cm9rZURyYXdlcnMuZGVsZXRlKGRhdGFzZXQpOwogICAgICAgICAgICB0aGlzLl9zdGFydEFuZ2xlcyA9IFtdOwogICAgICAgICAgICB0aGlzLl9lbmRBbmdsZXMgPSBbXTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLnNlbGVjdGlvbnMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgaWYgKGRhdGFzZXRzID09PSB2b2lkIDApIHsgZGF0YXNldHMgPSB0aGlzLmRhdGFzZXRzKCk7IH0KICAgICAgICAgICAgdmFyIGFsbFNlbGVjdGlvbnMgPSBfc3VwZXIucHJvdG90eXBlLnNlbGVjdGlvbnMuY2FsbCh0aGlzLCBkYXRhc2V0cykubm9kZXMoKTsKICAgICAgICAgICAgZGF0YXNldHMuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGRyYXdlciA9IF90aGlzLl9zdHJva2VEcmF3ZXJzLmdldChkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmIChkcmF3ZXIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGFsbFNlbGVjdGlvbnMucHVzaC5hcHBseShhbGxTZWxlY3Rpb25zLCBkcmF3ZXIuZ2V0VmlzdWFsUHJpbWl0aXZlcygpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkMy5zZWxlY3RBbGwoYWxsU2VsZWN0aW9ucyk7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLl9vbkRhdGFzZXRVcGRhdGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX29uRGF0YXNldFVwZGF0ZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVQaWVBbmdsZXMoKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX2NyZWF0ZURyYXdlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXIuUHJveHlEcmF3ZXIoZnVuY3Rpb24gKCkgeyByZXR1cm4gbmV3IGFyY0RyYXdlci5BcmNTVkdEcmF3ZXIoKTsgfSwgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgd2luZG93VXRpbHMud2FybigiY2FudmFzIHJlbmRlcmVyIGlzIG5vdCBzdXBwb3J0ZWQgb24gUGllIFBsb3QhIik7CiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLmVudGl0aWVzID0gZnVuY3Rpb24gKGRhdGFzZXRzKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmIChkYXRhc2V0cyA9PT0gdm9pZCAwKSB7IGRhdGFzZXRzID0gdGhpcy5kYXRhc2V0cygpOyB9CiAgICAgICAgICAgIHZhciBlbnRpdGllcyA9IF9zdXBlci5wcm90b3R5cGUuZW50aXRpZXMuY2FsbCh0aGlzLCBkYXRhc2V0cyk7CiAgICAgICAgICAgIHJldHVybiBlbnRpdGllcy5tYXAoZnVuY3Rpb24gKGVudGl0eSkgewogICAgICAgICAgICAgICAgZW50aXR5LnBvc2l0aW9uLnggKz0gX3RoaXMud2lkdGgoKSAvIDI7CiAgICAgICAgICAgICAgICBlbnRpdHkucG9zaXRpb24ueSArPSBfdGhpcy5oZWlnaHQoKSAvIDI7CiAgICAgICAgICAgICAgICB2YXIgc3Ryb2tlID0gZDMuc2VsZWN0KF90aGlzLl9zdHJva2VEcmF3ZXJzLmdldChlbnRpdHkuZGF0YXNldCkuZ2V0VmlzdWFsUHJpbWl0aXZlQXRJbmRleChlbnRpdHkuaW5kZXgpKTsKICAgICAgICAgICAgICAgIHZhciBwaWVQbG90RW50aXR5ID0gZW50aXR5OwogICAgICAgICAgICAgICAgcGllUGxvdEVudGl0eS5zdHJva2VTZWxlY3Rpb24gPSBzdHJva2U7CiAgICAgICAgICAgICAgICByZXR1cm4gcGllUGxvdEVudGl0eTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLnNlY3RvclZhbHVlID0gZnVuY3Rpb24gKHNlY3RvclZhbHVlLCBzY2FsZSkgewogICAgICAgICAgICBpZiAoc2VjdG9yVmFsdWUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFBpZS5fU0VDVE9SX1ZBTFVFX0tFWSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fYmluZFByb3BlcnR5KFBpZS5fU0VDVE9SX1ZBTFVFX0tFWSwgc2VjdG9yVmFsdWUsIHNjYWxlKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlUGllQW5nbGVzKCk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5pbm5lclJhZGl1cyA9IGZ1bmN0aW9uIChpbm5lclJhZGl1cywgc2NhbGUpIHsKICAgICAgICAgICAgaWYgKGlubmVyUmFkaXVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChQaWUuX0lOTkVSX1JBRElVU19LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShQaWUuX0lOTkVSX1JBRElVU19LRVksIGlubmVyUmFkaXVzLCBzY2FsZSk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5vdXRlclJhZGl1cyA9IGZ1bmN0aW9uIChvdXRlclJhZGl1cywgc2NhbGUpIHsKICAgICAgICAgICAgaWYgKG91dGVyUmFkaXVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChQaWUuX09VVEVSX1JBRElVU19LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShQaWUuX09VVEVSX1JBRElVU19LRVksIG91dGVyUmFkaXVzLCBzY2FsZSk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5zdGFydEFuZ2xlID0gZnVuY3Rpb24gKGFuZ2xlKSB7CiAgICAgICAgICAgIGlmIChhbmdsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fc3RhcnRBbmdsZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX3N0YXJ0QW5nbGUgPSBhbmdsZTsKICAgICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVBpZUFuZ2xlcygpOwogICAgICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLmVuZEFuZ2xlID0gZnVuY3Rpb24gKGFuZ2xlKSB7CiAgICAgICAgICAgIGlmIChhbmdsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fZW5kQW5nbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9lbmRBbmdsZSA9IGFuZ2xlOwogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlUGllQW5nbGVzKCk7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUubGFiZWxzRW5hYmxlZCA9IGZ1bmN0aW9uIChlbmFibGVkKSB7CiAgICAgICAgICAgIGlmIChlbmFibGVkID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9sYWJlbHNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxzRW5hYmxlZCA9IGVuYWJsZWQ7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUubGFiZWxGb3JtYXR0ZXIgPSBmdW5jdGlvbiAoZm9ybWF0dGVyKSB7CiAgICAgICAgICAgIGlmIChmb3JtYXR0ZXIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2xhYmVsRm9ybWF0dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxGb3JtYXR0ZXIgPSBmb3JtYXR0ZXI7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qCiAgICAgICAgICogR2V0cyB0aGUgRW50aXRpZXMgYXQgYSBwYXJ0aWN1bGFyIFBvaW50LgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtQb2ludH0gcAogICAgICAgICAqIEBwYXJhbSB7UGxvdEVudGl0eVtdfQogICAgICAgICAqLwogICAgICAgIFBpZS5wcm90b3R5cGUuZW50aXRpZXNBdCA9IGZ1bmN0aW9uIChxdWVyeVBvaW50KSB7CiAgICAgICAgICAgIHZhciBjZW50ZXIgPSB7IHg6IHRoaXMud2lkdGgoKSAvIDIsIHk6IHRoaXMuaGVpZ2h0KCkgLyAyIH07CiAgICAgICAgICAgIHZhciBhZGp1c3RlZFF1ZXJ5UG9pbnQgPSB7IHg6IHF1ZXJ5UG9pbnQueCAtIGNlbnRlci54LCB5OiBxdWVyeVBvaW50LnkgLSBjZW50ZXIueSB9OwogICAgICAgICAgICB2YXIgaW5kZXggPSB0aGlzLl9zbGljZUluZGV4Rm9yUG9pbnQoYWRqdXN0ZWRRdWVyeVBvaW50KTsKICAgICAgICAgICAgcmV0dXJuIGluZGV4ID09IG51bGwgPyBbXSA6IFt0aGlzLmVudGl0aWVzKClbaW5kZXhdXTsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycy5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgaW5uZXJSYWRpdXNBY2Nlc3NvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5pbm5lclJhZGl1cygpKTsKICAgICAgICAgICAgdmFyIG91dGVyUmFkaXVzQWNjZXNzb3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMub3V0ZXJSYWRpdXMoKSk7CiAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsiZCJdID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZHMpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkMy5hcmMoKS5pbm5lclJhZGl1cyhpbm5lclJhZGl1c0FjY2Vzc29yKGRhdHVtLCBpbmRleCwgZHMpKQogICAgICAgICAgICAgICAgICAgIC5vdXRlclJhZGl1cyhvdXRlclJhZGl1c0FjY2Vzc29yKGRhdHVtLCBpbmRleCwgZHMpKQogICAgICAgICAgICAgICAgICAgIC5zdGFydEFuZ2xlKF90aGlzLl9zdGFydEFuZ2xlc1tpbmRleF0pCiAgICAgICAgICAgICAgICAgICAgLmVuZEFuZ2xlKF90aGlzLl9lbmRBbmdsZXNbaW5kZXhdKShkYXR1bSwgaW5kZXgpOwogICAgICAgICAgICB9OwogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5fdXBkYXRlUGllQW5nbGVzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAodGhpcy5zZWN0b3JWYWx1ZSgpID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5kYXRhc2V0cygpLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBzZWN0b3JWYWx1ZUFjY2Vzc29yID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnNlY3RvclZhbHVlKCkpOwogICAgICAgICAgICB2YXIgZGF0YXNldCA9IHRoaXMuZGF0YXNldHMoKVswXTsKICAgICAgICAgICAgdmFyIGRhdGEgPSB0aGlzLl9nZXREYXRhVG9EcmF3KCkuZ2V0KGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgcGllID0gZDMucGllKCkuc29ydChudWxsKS5zdGFydEFuZ2xlKHRoaXMuX3N0YXJ0QW5nbGUpLmVuZEFuZ2xlKHRoaXMuX2VuZEFuZ2xlKQogICAgICAgICAgICAgICAgLnZhbHVlKGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBzZWN0b3JWYWx1ZUFjY2Vzc29yKGQsIGksIGRhdGFzZXQpOyB9KShkYXRhKTsKICAgICAgICAgICAgdGhpcy5fc3RhcnRBbmdsZXMgPSBwaWUubWFwKGZ1bmN0aW9uIChzbGljZSkgeyByZXR1cm4gc2xpY2Uuc3RhcnRBbmdsZTsgfSk7CiAgICAgICAgICAgIHRoaXMuX2VuZEFuZ2xlcyA9IHBpZS5tYXAoZnVuY3Rpb24gKHNsaWNlKSB7IHJldHVybiBzbGljZS5lbmRBbmdsZTsgfSk7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLl9waWVDZW50ZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBhID0gdGhpcy5fc3RhcnRBbmdsZSA8IHRoaXMuX2VuZEFuZ2xlID8gdGhpcy5fc3RhcnRBbmdsZSA6IHRoaXMuX2VuZEFuZ2xlOwogICAgICAgICAgICB2YXIgYiA9IHRoaXMuX3N0YXJ0QW5nbGUgPCB0aGlzLl9lbmRBbmdsZSA/IHRoaXMuX2VuZEFuZ2xlIDogdGhpcy5fc3RhcnRBbmdsZTsKICAgICAgICAgICAgdmFyIHNpbkEgPSBNYXRoLnNpbihhKTsKICAgICAgICAgICAgdmFyIGNvc0EgPSBNYXRoLmNvcyhhKTsKICAgICAgICAgICAgdmFyIHNpbkIgPSBNYXRoLnNpbihiKTsKICAgICAgICAgICAgdmFyIGNvc0IgPSBNYXRoLmNvcyhiKTsKICAgICAgICAgICAgdmFyIGhUb3A7CiAgICAgICAgICAgIHZhciBoQm90dG9tOwogICAgICAgICAgICB2YXIgd1JpZ2h0OwogICAgICAgICAgICB2YXIgd0xlZnQ7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiAgVGhlIGNlbnRlciBvZiB0aGUgcGllIGlzIGNvbXB1dGVkIHVzaW5nIHRoZSBzaW5lIGFuZCBjb3NpbmUgb2YgdGhlIHN0YXJ0IGFuZ2xlIGFuZCB0aGUgZW5kIGFuZ2xlCiAgICAgICAgICAgICAqICBUaGUgc2luZSBpbmRpY2F0ZXMgd2hldGhlciB0aGUgc3RhcnQgYW5kIGVuZCBmYWxsIG9uIHRoZSByaWdodCBoYWxmIG9yIHRoZSBsZWZ0IGhhbGYgb2YgdGhlIHBpZQogICAgICAgICAgICAgKiAgVGhlIGNvc2luZSBpbmRpY2F0ZXMgd2hldGhlciB0aGUgc3RhcnQgYW5kIGVuZCBmYWxsIG9uIHRoZSB0b3Agb3IgdGhlIGJvdHRvbSBoYWxmIG9mIHRoZSBwaWUKICAgICAgICAgICAgICogIERpZmZlcmVudCBjb21iaW5hdGlvbnMgcHJvdmlkZSB0aGUgZGlmZmVyZW50IGhlaWdodHMgYW5kIHdpZHRocyB0aGUgcGllIG5lZWRzIGZyb20gdGhlIGNlbnRlciB0byB0aGUgc2lkZXMKICAgICAgICAgICAgICovCiAgICAgICAgICAgIGlmIChzaW5BID49IDAgJiYgc2luQiA+PSAwKSB7CiAgICAgICAgICAgICAgICBpZiAoY29zQSA+PSAwICYmIGNvc0IgPj0gMCkgewogICAgICAgICAgICAgICAgICAgIGhUb3AgPSBjb3NBOwogICAgICAgICAgICAgICAgICAgIGhCb3R0b20gPSAwOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gMDsKICAgICAgICAgICAgICAgICAgICB3UmlnaHQgPSBzaW5COwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoY29zQSA8IDAgJiYgY29zQiA8IDApIHsKICAgICAgICAgICAgICAgICAgICBoVG9wID0gMDsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gLWNvc0I7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAwOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IHNpbkE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChjb3NBID49IDAgJiYgY29zQiA8IDApIHsKICAgICAgICAgICAgICAgICAgICBoVG9wID0gY29zQTsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gLWNvc0I7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAwOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IHNpbkE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChjb3NBIDwgMCAmJiBjb3NCID49IDApIHsKICAgICAgICAgICAgICAgICAgICBoVG9wID0gMTsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gMTsKICAgICAgICAgICAgICAgICAgICB3TGVmdCA9IDE7CiAgICAgICAgICAgICAgICAgICAgd1JpZ2h0ID0gTWF0aC5tYXgoc2luQSwgc2luQik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoc2luQSA+PSAwICYmIHNpbkIgPCAwKSB7CiAgICAgICAgICAgICAgICBpZiAoY29zQSA+PSAwICYmIGNvc0IgPj0gMCkgewogICAgICAgICAgICAgICAgICAgIGhUb3AgPSBNYXRoLm1heChjb3NBLCBjb3NCKTsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gMTsKICAgICAgICAgICAgICAgICAgICB3TGVmdCA9IDE7CiAgICAgICAgICAgICAgICAgICAgd1JpZ2h0ID0gMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGNvc0EgPCAwICYmIGNvc0IgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IDA7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IDE7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAtc2luQjsKICAgICAgICAgICAgICAgICAgICB3UmlnaHQgPSBzaW5BOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoY29zQSA+PSAwICYmIGNvc0IgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IGNvc0E7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IDE7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAtc2luQjsKICAgICAgICAgICAgICAgICAgICB3UmlnaHQgPSAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoY29zQSA8IDAgJiYgY29zQiA+PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IGNvc0I7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IDE7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAxOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IHNpbkE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoc2luQSA8IDAgJiYgc2luQiA+PSAwKSB7CiAgICAgICAgICAgICAgICBpZiAoY29zQSA+PSAwICYmIGNvc0IgPj0gMCkgewogICAgICAgICAgICAgICAgICAgIGhUb3AgPSAxOwogICAgICAgICAgICAgICAgICAgIGhCb3R0b20gPSAwOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gLXNpbkE7CiAgICAgICAgICAgICAgICAgICAgd1JpZ2h0ID0gc2luQjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGNvc0EgPCAwICYmIGNvc0IgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IDE7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IE1hdGgubWF4KC1jb3NBLCAtY29zQik7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAxOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IDE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChjb3NBID49IDAgJiYgY29zQiA8IDApIHsKICAgICAgICAgICAgICAgICAgICBoVG9wID0gMTsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gLWNvc0I7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAtc2luQTsKICAgICAgICAgICAgICAgICAgICB3UmlnaHQgPSAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoY29zQSA8IDAgJiYgY29zQiA+PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IDE7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IC1jb3NBOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gMTsKICAgICAgICAgICAgICAgICAgICB3UmlnaHQgPSBzaW5COwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHNpbkEgPCAwICYmIHNpbkIgPCAwKSB7CiAgICAgICAgICAgICAgICBpZiAoY29zQSA+PSAwICYmIGNvc0IgPj0gMCkgewogICAgICAgICAgICAgICAgICAgIGhUb3AgPSBjb3NCOwogICAgICAgICAgICAgICAgICAgIGhCb3R0b20gPSAwOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gLXNpbkE7CiAgICAgICAgICAgICAgICAgICAgd1JpZ2h0ID0gMDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGNvc0EgPCAwICYmIGNvc0IgPCAwKSB7CiAgICAgICAgICAgICAgICAgICAgaFRvcCA9IDA7CiAgICAgICAgICAgICAgICAgICAgaEJvdHRvbSA9IC1jb3NBOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gLXNpbkI7CiAgICAgICAgICAgICAgICAgICAgd1JpZ2h0ID0gMDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGNvc0EgPj0gMCAmJiBjb3NCIDwgMCkgewogICAgICAgICAgICAgICAgICAgIGhUb3AgPSAxOwogICAgICAgICAgICAgICAgICAgIGhCb3R0b20gPSAxOwogICAgICAgICAgICAgICAgICAgIHdMZWZ0ID0gTWF0aC5tYXgoY29zQSwgLWNvc0IpOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IDE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChjb3NBIDwgMCAmJiBjb3NCID49IDApIHsKICAgICAgICAgICAgICAgICAgICBoVG9wID0gY29zQjsKICAgICAgICAgICAgICAgICAgICBoQm90dG9tID0gLWNvc0E7CiAgICAgICAgICAgICAgICAgICAgd0xlZnQgPSAxOwogICAgICAgICAgICAgICAgICAgIHdSaWdodCA9IDA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHg6IHdMZWZ0ICsgd1JpZ2h0ID09IDAgPyAwIDogKHdMZWZ0IC8gKHdMZWZ0ICsgd1JpZ2h0KSkgKiB0aGlzLndpZHRoKCksCiAgICAgICAgICAgICAgICB5OiBoVG9wICsgaEJvdHRvbSA9PSAwID8gMCA6IChoVG9wIC8gKGhUb3AgKyBoQm90dG9tKSkgKiB0aGlzLmhlaWdodCgpLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5fZ2V0RGF0YVRvRHJhdyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGRhdGFUb0RyYXcgPSBfc3VwZXIucHJvdG90eXBlLl9nZXREYXRhVG9EcmF3LmNhbGwodGhpcyk7CiAgICAgICAgICAgIGlmICh0aGlzLmRhdGFzZXRzKCkubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZGF0YVRvRHJhdzsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgc2VjdG9yVmFsdWVBY2Nlc3NvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5zZWN0b3JWYWx1ZSgpKTsKICAgICAgICAgICAgdmFyIGRzID0gdGhpcy5kYXRhc2V0cygpWzBdOwogICAgICAgICAgICB2YXIgZGF0YSA9IGRhdGFUb0RyYXcuZ2V0KGRzKTsKICAgICAgICAgICAgdmFyIGZpbHRlcmVkRGF0YSA9IGRhdGEuZmlsdGVyKGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBQaWUuX2lzVmFsaWREYXRhKHNlY3RvclZhbHVlQWNjZXNzb3IoZCwgaSwgZHMpKTsgfSk7CiAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRzLCBmaWx0ZXJlZERhdGEpOwogICAgICAgICAgICByZXR1cm4gZGF0YVRvRHJhdzsKICAgICAgICB9OwogICAgICAgIFBpZS5faXNWYWxpZERhdGEgPSBmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKHZhbHVlKSAmJiB2YWx1ZSA+PSAwOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5fcGl4ZWxQb2ludCA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIHNjYWxlZFZhbHVlQWNjZXNzb3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMuc2VjdG9yVmFsdWUoKSk7CiAgICAgICAgICAgIGlmICghUGllLl9pc1ZhbGlkRGF0YShzY2FsZWRWYWx1ZUFjY2Vzc29yKGRhdHVtLCBpbmRleCwgZGF0YXNldCkpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4geyB4OiBOYU4sIHk6IE5hTiB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBpbm5lclJhZGl1cyA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5pbm5lclJhZGl1cygpKShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgb3V0ZXJSYWRpdXMgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMub3V0ZXJSYWRpdXMoKSkoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGF2Z1JhZGl1cyA9IChpbm5lclJhZGl1cyArIG91dGVyUmFkaXVzKSAvIDI7CiAgICAgICAgICAgIHZhciBwaWUgPSBkMy5waWUoKQogICAgICAgICAgICAgICAgLnNvcnQobnVsbCkKICAgICAgICAgICAgICAgIC52YWx1ZShmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgdmFyIHZhbHVlID0gc2NhbGVkVmFsdWVBY2Nlc3NvcihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHJldHVybiBQaWUuX2lzVmFsaWREYXRhKHZhbHVlKSA/IHZhbHVlIDogMDsKICAgICAgICAgICAgfSkuc3RhcnRBbmdsZSh0aGlzLl9zdGFydEFuZ2xlKS5lbmRBbmdsZSh0aGlzLl9lbmRBbmdsZSkoZGF0YXNldC5kYXRhKCkpOwogICAgICAgICAgICB2YXIgc3RhcnRBbmdsZSA9IHBpZVtpbmRleF0uc3RhcnRBbmdsZTsKICAgICAgICAgICAgdmFyIGVuZEFuZ2xlID0gcGllW2luZGV4XS5lbmRBbmdsZTsKICAgICAgICAgICAgdmFyIGF2Z0FuZ2xlID0gKHN0YXJ0QW5nbGUgKyBlbmRBbmdsZSkgLyAyOwogICAgICAgICAgICByZXR1cm4geyB4OiBhdmdSYWRpdXMgKiBNYXRoLnNpbihhdmdBbmdsZSksIHk6IC1hdmdSYWRpdXMgKiBNYXRoLmNvcyhhdmdBbmdsZSkgfTsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX2FkZGl0aW9uYWxQYWludCA9IGZ1bmN0aW9uICh0aW1lKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuX3JlbmRlckFyZWEuc2VsZWN0KCIubGFiZWwtYXJlYSIpLnJlbW92ZSgpOwogICAgICAgICAgICBpZiAodGhpcy5fbGFiZWxzRW5hYmxlZCkgewogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cuc2V0VGltZW91dChmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fZHJhd0xhYmVscygpOyB9LCB0aW1lKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgZHJhd1N0ZXBzID0gdGhpcy5fZ2VuZXJhdGVTdHJva2VEcmF3U3RlcHMoKTsKICAgICAgICAgICAgdmFyIGRhdGFUb0RyYXcgPSB0aGlzLl9nZXREYXRhVG9EcmF3KCk7CiAgICAgICAgICAgIHRoaXMuZGF0YXNldHMoKS5mb3JFYWNoKGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgYXBwbGllZERyYXdTdGVwcyA9IHBsb3QuUGxvdC5hcHBseURyYXdTdGVwcyhkcmF3U3RlcHMsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgX3RoaXMuX3N0cm9rZURyYXdlcnMuZ2V0KGRhdGFzZXQpLmRyYXcoZGF0YVRvRHJhdy5nZXQoZGF0YXNldCksIGFwcGxpZWREcmF3U3RlcHMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIFBpZS5wcm90b3R5cGUuX2dlbmVyYXRlU3Ryb2tlRHJhd1N0ZXBzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHJldHVybiBbeyBhdHRyVG9Qcm9qZWN0b3I6IGF0dHJUb1Byb2plY3RvciwgYW5pbWF0b3I6IG5ldyBhbmltYXRvcnMuTnVsbCgpIH1dOwogICAgICAgIH07CiAgICAgICAgUGllLnByb3RvdHlwZS5fc2xpY2VJbmRleEZvclBvaW50ID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIHBvaW50UmFkaXVzID0gTWF0aC5zcXJ0KE1hdGgucG93KHAueCwgMikgKyBNYXRoLnBvdyhwLnksIDIpKTsKICAgICAgICAgICAgdmFyIHBvaW50QW5nbGUgPSBNYXRoLmFjb3MoLXAueSAvIHBvaW50UmFkaXVzKTsKICAgICAgICAgICAgaWYgKHAueCA8IDApIHsKICAgICAgICAgICAgICAgIHBvaW50QW5nbGUgPSBNYXRoLlBJICogMiAtIHBvaW50QW5nbGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGluZGV4OwogICAgICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHRoaXMuX3N0YXJ0QW5nbGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fc3RhcnRBbmdsZXNbaV0gPCBwb2ludEFuZ2xlICYmIHRoaXMuX2VuZEFuZ2xlc1tpXSA+IHBvaW50QW5nbGUpIHsKICAgICAgICAgICAgICAgICAgICBpbmRleCA9IGk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGluZGV4ICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHZhciBkYXRhc2V0ID0gdGhpcy5kYXRhc2V0cygpWzBdOwogICAgICAgICAgICAgICAgdmFyIGRhdHVtID0gZGF0YXNldC5kYXRhKClbaW5kZXhdOwogICAgICAgICAgICAgICAgdmFyIGlubmVyUmFkaXVzID0gdGhpcy5pbm5lclJhZGl1cygpLmFjY2Vzc29yKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgb3V0ZXJSYWRpdXMgPSB0aGlzLm91dGVyUmFkaXVzKCkuYWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmIChwb2ludFJhZGl1cyA+IGlubmVyUmFkaXVzICYmIHBvaW50UmFkaXVzIDwgb3V0ZXJSYWRpdXMpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gaW5kZXg7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfTsKICAgICAgICBQaWUucHJvdG90eXBlLl9kcmF3TGFiZWxzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHZhciBsYWJlbEFyZWEgPSB0aGlzLl9yZW5kZXJBcmVhLmFwcGVuZCgiZyIpLmNsYXNzZWQoImxhYmVsLWFyZWEiLCB0cnVlKTsKICAgICAgICAgICAgdmFyIGNvbnRleHQgPSBuZXcgc3JjJDEuU3ZnQ29udGV4dChsYWJlbEFyZWEubm9kZSgpKTsKICAgICAgICAgICAgdmFyIG1lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIoY29udGV4dCk7CiAgICAgICAgICAgIHZhciB3cml0ZXIgPSBuZXcgc3JjJDEuV3JpdGVyKG1lYXN1cmVyLCBjb250ZXh0KTsKICAgICAgICAgICAgdmFyIGRhdGFzZXQgPSB0aGlzLmRhdGFzZXRzKClbMF07CiAgICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5fZ2V0RGF0YVRvRHJhdygpLmdldChkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGRhdGFMZW4gPSBkYXRhLmxlbmd0aDsKICAgICAgICAgICAgdmFyIF9sb29wXzEgPSBmdW5jdGlvbiAoZGF0dW1JbmRleCkgewogICAgICAgICAgICAgICAgdmFyIGRhdHVtID0gZGF0YVtkYXR1bUluZGV4XTsKICAgICAgICAgICAgICAgIHZhciB2YWx1ZSA9IHRoaXNfMS5zZWN0b3JWYWx1ZSgpLmFjY2Vzc29yKGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmICghdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIodmFsdWUpKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICJjb250aW51ZSI7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YWx1ZSA9IHRoaXNfMS5fbGFiZWxGb3JtYXR0ZXIodmFsdWUsIGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBtZWFzdXJlbWVudCA9IG1lYXN1cmVyLm1lYXN1cmUodmFsdWUpOwogICAgICAgICAgICAgICAgdmFyIHRoZXRhID0gKHRoaXNfMS5fZW5kQW5nbGVzW2RhdHVtSW5kZXhdICsgdGhpc18xLl9zdGFydEFuZ2xlc1tkYXR1bUluZGV4XSkgLyAyOwogICAgICAgICAgICAgICAgdmFyIG91dGVyUmFkaXVzID0gdGhpc18xLm91dGVyUmFkaXVzKCkuYWNjZXNzb3IoZGF0dW0sIGRhdHVtSW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgaWYgKHRoaXNfMS5vdXRlclJhZGl1cygpLnNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgb3V0ZXJSYWRpdXMgPSB0aGlzXzEub3V0ZXJSYWRpdXMoKS5zY2FsZS5zY2FsZShvdXRlclJhZGl1cyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgaW5uZXJSYWRpdXMgPSB0aGlzXzEuaW5uZXJSYWRpdXMoKS5hY2Nlc3NvcihkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICBpZiAodGhpc18xLmlubmVyUmFkaXVzKCkuc2NhbGUpIHsKICAgICAgICAgICAgICAgICAgICBpbm5lclJhZGl1cyA9IHRoaXNfMS5pbm5lclJhZGl1cygpLnNjYWxlLnNjYWxlKGlubmVyUmFkaXVzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBsYWJlbFJhZGl1cyA9IChvdXRlclJhZGl1cyArIGlubmVyUmFkaXVzKSAvIDI7CiAgICAgICAgICAgICAgICB2YXIgeCA9IE1hdGguc2luKHRoZXRhKSAqIGxhYmVsUmFkaXVzIC0gbWVhc3VyZW1lbnQud2lkdGggLyAyOwogICAgICAgICAgICAgICAgdmFyIHkgPSAtTWF0aC5jb3ModGhldGEpICogbGFiZWxSYWRpdXMgLSBtZWFzdXJlbWVudC5oZWlnaHQgLyAyOwogICAgICAgICAgICAgICAgdmFyIGNvcm5lcnMgPSBbCiAgICAgICAgICAgICAgICAgICAgeyB4OiB4LCB5OiB5IH0sCiAgICAgICAgICAgICAgICAgICAgeyB4OiB4LCB5OiB5ICsgbWVhc3VyZW1lbnQuaGVpZ2h0IH0sCiAgICAgICAgICAgICAgICAgICAgeyB4OiB4ICsgbWVhc3VyZW1lbnQud2lkdGgsIHk6IHkgfSwKICAgICAgICAgICAgICAgICAgICB7IHg6IHggKyBtZWFzdXJlbWVudC53aWR0aCwgeTogeSArIG1lYXN1cmVtZW50LmhlaWdodCB9LAogICAgICAgICAgICAgICAgXTsKICAgICAgICAgICAgICAgIHZhciBzaG93TGFiZWwgPSBjb3JuZXJzLmV2ZXJ5KGZ1bmN0aW9uIChjb3JuZXIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5hYnMoY29ybmVyLngpIDw9IF90aGlzLndpZHRoKCkgLyAyICYmIE1hdGguYWJzKGNvcm5lci55KSA8PSBfdGhpcy5oZWlnaHQoKSAvIDI7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGlmIChzaG93TGFiZWwpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgc2xpY2VJbmRpY2VzID0gY29ybmVycy5tYXAoZnVuY3Rpb24gKGNvcm5lcikgeyByZXR1cm4gX3RoaXMuX3NsaWNlSW5kZXhGb3JQb2ludChjb3JuZXIpOyB9KTsKICAgICAgICAgICAgICAgICAgICBzaG93TGFiZWwgPSBzbGljZUluZGljZXMuZXZlcnkoZnVuY3Rpb24gKGluZGV4KSB7IHJldHVybiBpbmRleCA9PT0gZGF0dW1JbmRleDsgfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgY29sb3IgPSBhdHRyVG9Qcm9qZWN0b3JbImZpbGwiXShkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgZGFyayA9IHV0aWxzJDEuQ29sb3IuY29udHJhc3QoIndoaXRlIiwgY29sb3IpICogMS42IDwgdXRpbHMkMS5Db2xvci5jb250cmFzdCgiYmxhY2siLCBjb2xvcik7CiAgICAgICAgICAgICAgICB2YXIgZyA9IGxhYmVsQXJlYS5hcHBlbmQoImciKS5hdHRyKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyB4ICsgIiwiICsgeSArICIpIik7CiAgICAgICAgICAgICAgICB2YXIgY2xhc3NOYW1lID0gZGFyayA/ICJkYXJrLWxhYmVsIiA6ICJsaWdodC1sYWJlbCI7CiAgICAgICAgICAgICAgICBnLmNsYXNzZWQoY2xhc3NOYW1lLCB0cnVlKTsKICAgICAgICAgICAgICAgIGcuc3R5bGUoInZpc2liaWxpdHkiLCBzaG93TGFiZWwgPyAiaW5oZXJpdCIgOiAiaGlkZGVuIik7CiAgICAgICAgICAgICAgICB3cml0ZXIud3JpdGUodmFsdWUsIG1lYXN1cmVtZW50LndpZHRoLCBtZWFzdXJlbWVudC5oZWlnaHQsIHsKICAgICAgICAgICAgICAgICAgICB4QWxpZ246ICJjZW50ZXIiLAogICAgICAgICAgICAgICAgICAgIHlBbGlnbjogImNlbnRlciIsCiAgICAgICAgICAgICAgICB9LCBnLm5vZGUoKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB0aGlzXzEgPSB0aGlzOwogICAgICAgICAgICBmb3IgKHZhciBkYXR1bUluZGV4ID0gMDsgZGF0dW1JbmRleCA8IGRhdGFMZW47IGRhdHVtSW5kZXgrKykgewogICAgICAgICAgICAgICAgX2xvb3BfMShkYXR1bUluZGV4KTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgUGllLl9JTk5FUl9SQURJVVNfS0VZID0gImlubmVyLXJhZGl1cyI7CiAgICAgICAgUGllLl9PVVRFUl9SQURJVVNfS0VZID0gIm91dGVyLXJhZGl1cyI7CiAgICAgICAgUGllLl9TRUNUT1JfVkFMVUVfS0VZID0gInNlY3Rvci12YWx1ZSI7CiAgICAgICAgcmV0dXJuIFBpZTsKICAgIH0ocGxvdC5QbG90KSk7CiAgICBleHBvcnRzLlBpZSA9IFBpZTsKICAgIH0pOwoKICAgIHZhciByZWN0YW5nbGVQbG90ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCgoKCgoKICAgIHZhciBSZWN0YW5nbGUgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhSZWN0YW5nbGUsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBSZWN0YW5nbGUgUGxvdCBkaXNwbGF5cyByZWN0YW5nbGVzIGJhc2VkIG9uIHRoZSBkYXRhLgogICAgICAgICAqIFRoZSBsZWZ0IGFuZCByaWdodCBlZGdlcyBvZiBlYWNoIHJlY3RhbmdsZSBjYW4gYmUgc2V0IHdpdGggeCgpIGFuZCB4MigpLgogICAgICAgICAqICAgSWYgb25seSB4KCkgaXMgc2V0IHRoZSBSZWN0YW5nbGUgUGxvdCB3aWxsIGF0dGVtcHQgdG8gY29tcHV0ZSB0aGUgY29ycmVjdCBsZWZ0IGFuZCByaWdodCBlZGdlIHBvc2l0aW9ucy4KICAgICAgICAgKiBUaGUgdG9wIGFuZCBib3R0b20gZWRnZXMgb2YgZWFjaCByZWN0YW5nbGUgY2FuIGJlIHNldCB3aXRoIHkoKSBhbmQgeTIoKS4KICAgICAgICAgKiAgIElmIG9ubHkgeSgpIGlzIHNldCB0aGUgUmVjdGFuZ2xlIFBsb3Qgd2lsbCBhdHRlbXB0IHRvIGNvbXB1dGUgdGhlIGNvcnJlY3QgdG9wIGFuZCBib3R0b20gZWRnZSBwb3NpdGlvbnMuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlLlNjYWxlfSB4U2NhbGUKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlLlNjYWxlfSB5U2NhbGUKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBSZWN0YW5nbGUoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbHNFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbCA9IG51bGw7CiAgICAgICAgICAgIF90aGlzLmFuaW1hdG9yKCJyZWN0YW5nbGVzIiwgbmV3IGFuaW1hdG9ycy5OdWxsKCkpOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygicmVjdGFuZ2xlLXBsb3QiKTsKICAgICAgICAgICAgX3RoaXMuYXR0cigiZmlsbCIsIG5ldyBzY2FsZXMuQ29sb3IoKS5yYW5nZSgpWzBdKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLl9jcmVhdGVEcmF3ZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgZHJhd2VyLlByb3h5RHJhd2VyKGZ1bmN0aW9uICgpIHsgcmV0dXJuIG5ldyByZWN0YW5nbGVEcmF3ZXIuUmVjdGFuZ2xlU1ZHRHJhd2VyKCk7IH0sIGZ1bmN0aW9uIChjdHgpIHsgcmV0dXJuIG5ldyBkcmF3ZXJzLlJlY3RhbmdsZUNhbnZhc0RyYXdlcihjdHgpOyB9KTsKICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gX3N1cGVyLnByb3RvdHlwZS5fZ2VuZXJhdGVBdHRyVG9Qcm9qZWN0b3IuY2FsbCh0aGlzKTsKICAgICAgICAgICAgLy8gQ29weSBlYWNoIG9mIHRoZSBkaWZmZXJlbnQgcHJvamVjdG9ycy4KICAgICAgICAgICAgdmFyIHhBdHRyID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLngoKSk7CiAgICAgICAgICAgIHZhciB4MkF0dHIgPSBhdHRyVG9Qcm9qZWN0b3JbUmVjdGFuZ2xlLl9YMl9LRVldOwogICAgICAgICAgICB2YXIgeUF0dHIgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKTsKICAgICAgICAgICAgdmFyIHkyQXR0ciA9IGF0dHJUb1Byb2plY3RvcltSZWN0YW5nbGUuX1kyX0tFWV07CiAgICAgICAgICAgIHZhciB4U2NhbGUgPSB0aGlzLngoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIHlTY2FsZSA9IHRoaXMueSgpLnNjYWxlOwogICAgICAgICAgICBpZiAoeDJBdHRyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBNYXRoLmFicyh4MkF0dHIoZCwgaSwgZGF0YXNldCkgLSB4QXR0cihkLCBpLCBkYXRhc2V0KSk7IH07CiAgICAgICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbIngiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBNYXRoLm1pbih4MkF0dHIoZCwgaSwgZGF0YXNldCksIHhBdHRyKGQsIGksIGRhdGFzZXQpKTsgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBfdGhpcy5fcmVjdGFuZ2xlV2lkdGgoeFNjYWxlKTsgfTsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsieCJdID0gZnVuY3Rpb24gKGQsIGksIGRhdGFzZXQpIHsgcmV0dXJuIHhBdHRyKGQsIGksIGRhdGFzZXQpIC0gMC41ICogYXR0clRvUHJvamVjdG9yWyJ3aWR0aCJdKGQsIGksIGRhdGFzZXQpOyB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh5MkF0dHIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7IHJldHVybiBNYXRoLmFicyh5MkF0dHIoZCwgaSwgZGF0YXNldCkgLSB5QXR0cihkLCBpLCBkYXRhc2V0KSk7IH07CiAgICAgICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbInkiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIE1hdGgubWF4KHkyQXR0cihkLCBpLCBkYXRhc2V0KSwgeUF0dHIoZCwgaSwgZGF0YXNldCkpIC0gYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXShkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdID0gZnVuY3Rpb24gKGQsIGksIGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9yZWN0YW5nbGVXaWR0aCh5U2NhbGUpOyB9OwogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJ5Il0gPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgeyByZXR1cm4geUF0dHIoZCwgaSwgZGF0YXNldCkgLSAwLjUgKiBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdKGQsIGksIGRhdGFzZXQpOyB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENsZWFuIHVwIHRoZSBhdHRyaWJ1dGVzIHByb2plY3RlZCBvbnRvIHRoZSBTVkcgZWxlbWVudHMKICAgICAgICAgICAgZGVsZXRlIGF0dHJUb1Byb2plY3RvcltSZWN0YW5nbGUuX1gyX0tFWV07CiAgICAgICAgICAgIGRlbGV0ZSBhdHRyVG9Qcm9qZWN0b3JbUmVjdGFuZ2xlLl9ZMl9LRVldOwogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS5fZ2VuZXJhdGVEcmF3U3RlcHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBbeyBhdHRyVG9Qcm9qZWN0b3I6IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpLCBhbmltYXRvcjogdGhpcy5fZ2V0QW5pbWF0b3IoInJlY3RhbmdsZXMiKSB9XTsKICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUuX2ZpbHRlckZvclByb3BlcnR5ID0gZnVuY3Rpb24gKHByb3BlcnR5KSB7CiAgICAgICAgICAgIGlmIChwcm9wZXJ0eSA9PT0gIngyIikgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuX2ZpbHRlckZvclByb3BlcnR5LmNhbGwodGhpcywgIngiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmIChwcm9wZXJ0eSA9PT0gInkyIikgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuX2ZpbHRlckZvclByb3BlcnR5LmNhbGwodGhpcywgInkiKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5fZmlsdGVyRm9yUHJvcGVydHkuY2FsbCh0aGlzLCBwcm9wZXJ0eSk7CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLnggPSBmdW5jdGlvbiAoeCwgeFNjYWxlLCBwb3N0U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHggPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUueC5jYWxsKHRoaXMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh4U2NhbGUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS54LmNhbGwodGhpcywgeCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnguY2FsbCh0aGlzLCB4LCB4U2NhbGUsIHBvc3RTY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHhTY2FsZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgeDJCaW5kaW5nID0gdGhpcy54MigpOwogICAgICAgICAgICAgICAgdmFyIHgyID0geDJCaW5kaW5nICYmIHgyQmluZGluZy5hY2Nlc3NvcjsKICAgICAgICAgICAgICAgIGlmICh4MiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYmluZFByb3BlcnR5KFJlY3RhbmdsZS5fWDJfS0VZLCB4MiwgeFNjYWxlLCB4MkJpbmRpbmcucG9zdFNjYWxlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBUaGUgeCBhbmQgeSBzY2FsZXMgc2hvdWxkIHJlbmRlciBpbiBiYW5kcyB3aXRoIG5vIHBhZGRpbmcgZm9yIGNhdGVnb3J5IHNjYWxlcwogICAgICAgICAgICBpZiAoeFNjYWxlIGluc3RhbmNlb2Ygc2NhbGVzLkNhdGVnb3J5KSB7CiAgICAgICAgICAgICAgICB4U2NhbGUuaW5uZXJQYWRkaW5nKDApLm91dGVyUGFkZGluZygwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUueDIgPSBmdW5jdGlvbiAoeDIsIHBvc3RTY2FsZSkgewogICAgICAgICAgICBpZiAoeDIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFJlY3RhbmdsZS5fWDJfS0VZKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgeEJpbmRpbmcgPSB0aGlzLngoKTsKICAgICAgICAgICAgdmFyIHhTY2FsZSA9IHhCaW5kaW5nICYmIHhCaW5kaW5nLnNjYWxlOwogICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoUmVjdGFuZ2xlLl9YMl9LRVksIHgyLCB4U2NhbGUsIHBvc3RTY2FsZSk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS55ID0gZnVuY3Rpb24gKHksIHlTY2FsZSwgcG9zdFNjYWxlKSB7CiAgICAgICAgICAgIGlmICh5ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoeVNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMsIHkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS55LmNhbGwodGhpcywgeSwgeVNjYWxlLCBwb3N0U2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh5U2NhbGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdmFyIHkyQmluZGluZyA9IHRoaXMueTIoKTsKICAgICAgICAgICAgICAgIHZhciB5MiA9IHkyQmluZGluZyAmJiB5MkJpbmRpbmcuYWNjZXNzb3I7CiAgICAgICAgICAgICAgICBpZiAoeTIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShSZWN0YW5nbGUuX1kyX0tFWSwgeTIsIHlTY2FsZSwgeTJCaW5kaW5nLnBvc3RTY2FsZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVGhlIHggYW5kIHkgc2NhbGVzIHNob3VsZCByZW5kZXIgaW4gYmFuZHMgd2l0aCBubyBwYWRkaW5nIGZvciBjYXRlZ29yeSBzY2FsZXMKICAgICAgICAgICAgaWYgKHlTY2FsZSBpbnN0YW5jZW9mIHNjYWxlcy5DYXRlZ29yeSkgewogICAgICAgICAgICAgICAgeVNjYWxlLmlubmVyUGFkZGluZygwKS5vdXRlclBhZGRpbmcoMCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLnkyID0gZnVuY3Rpb24gKHkyLCBwb3N0U2NhbGUpIHsKICAgICAgICAgICAgaWYgKHkyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9wcm9wZXJ0eUJpbmRpbmdzLmdldChSZWN0YW5nbGUuX1kyX0tFWSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHlCaW5kaW5nID0gdGhpcy55KCk7CiAgICAgICAgICAgIHZhciB5U2NhbGUgPSB5QmluZGluZyAmJiB5QmluZGluZy5zY2FsZTsKICAgICAgICAgICAgdGhpcy5fYmluZFByb3BlcnR5KFJlY3RhbmdsZS5fWTJfS0VZLCB5MiwgeVNjYWxlLCBwb3N0U2NhbGUpOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdldHMgdGhlIFBsb3RFbnRpdGllcyBhdCBhIHBhcnRpY3VsYXIgUG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBwb2ludCBUaGUgcG9pbnQgdG8gcXVlcnkuCiAgICAgICAgICogQHJldHVybnMge1Bsb3RFbnRpdHlbXX0gVGhlIFBsb3RFbnRpdGllcyBhdCB0aGUgcGFydGljdWxhciBwb2ludAogICAgICAgICAqLwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUuZW50aXRpZXNBdCA9IGZ1bmN0aW9uIChwb2ludCkgewogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmVudGl0aWVzKCkuZmlsdGVyKGZ1bmN0aW9uIChlbnRpdHkpIHsKICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGVudGl0eS5kYXR1bTsKICAgICAgICAgICAgICAgIHZhciBpbmRleCA9IGVudGl0eS5pbmRleDsKICAgICAgICAgICAgICAgIHZhciBkYXRhc2V0ID0gZW50aXR5LmRhdGFzZXQ7CiAgICAgICAgICAgICAgICB2YXIgeCA9IGF0dHJUb1Byb2plY3RvclsieCJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgeSA9IGF0dHJUb1Byb2plY3RvclsieSJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgd2lkdGggPSBhdHRyVG9Qcm9qZWN0b3JbIndpZHRoIl0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBoZWlnaHQgPSBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICByZXR1cm4geCA8PSBwb2ludC54ICYmIHBvaW50LnggPD0geCArIHdpZHRoICYmIHkgPD0gcG9pbnQueSAmJiBwb2ludC55IDw9IHkgKyBoZWlnaHQ7CiAgICAgICAgICAgIH0pOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS5fZW50aXR5Qm91bmRzID0gZnVuY3Rpb24gKGVudGl0eSkgewogICAgICAgICAgICB2YXIgZGF0dW0gPSBlbnRpdHkuZGF0dW0sIGluZGV4ID0gZW50aXR5LmluZGV4LCBkYXRhc2V0ID0gZW50aXR5LmRhdGFzZXQ7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9lbnRpdHlCQm94KGRhdHVtLCBpbmRleCwgZGF0YXNldCwgdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCkpOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS5fZW50aXR5QkJveCA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQsIGF0dHJUb1Byb2plY3RvcikgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgeDogYXR0clRvUHJvamVjdG9yWyJ4Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwKICAgICAgICAgICAgICAgIHk6IGF0dHJUb1Byb2plY3RvclsieSJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCksCiAgICAgICAgICAgICAgICB3aWR0aDogYXR0clRvUHJvamVjdG9yWyJ3aWR0aCJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCksCiAgICAgICAgICAgICAgICBoZWlnaHQ6IGF0dHJUb1Byb2plY3RvclsiaGVpZ2h0Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwKICAgICAgICAgICAgfTsKICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUubGFiZWwgPSBmdW5jdGlvbiAobGFiZWwpIHsKICAgICAgICAgICAgaWYgKGxhYmVsID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9sYWJlbDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9sYWJlbCA9IGxhYmVsOwogICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUubGFiZWxzRW5hYmxlZCA9IGZ1bmN0aW9uIChlbmFibGVkKSB7CiAgICAgICAgICAgIGlmIChlbmFibGVkID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9sYWJlbHNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxzRW5hYmxlZCA9IGVuYWJsZWQ7CiAgICAgICAgICAgICAgICB0aGlzLnJlbmRlcigpOwogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycy5jYWxsKHRoaXMpOwogICAgICAgICAgICBpZiAodGhpcy54MigpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsieDIiXSA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54MigpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy55MigpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsieTIiXSA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy55MigpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS5fcGl4ZWxQb2ludCA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICB2YXIgcmVjdFggPSBhdHRyVG9Qcm9qZWN0b3JbIngiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgcmVjdFkgPSBhdHRyVG9Qcm9qZWN0b3JbInkiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgcmVjdFdpZHRoID0gYXR0clRvUHJvamVjdG9yWyJ3aWR0aCJdKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgIHZhciByZWN0SGVpZ2h0ID0gYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXShkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgeCA9IHJlY3RYICsgcmVjdFdpZHRoIC8gMjsKICAgICAgICAgICAgdmFyIHkgPSByZWN0WSArIHJlY3RIZWlnaHQgLyAyOwogICAgICAgICAgICByZXR1cm4geyB4OiB4LCB5OiB5IH07CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLl9yZWN0YW5nbGVXaWR0aCA9IGZ1bmN0aW9uIChzY2FsZSkgewogICAgICAgICAgICBpZiAoc2NhbGUgaW5zdGFuY2VvZiBzY2FsZXMuQ2F0ZWdvcnkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBzY2FsZS5yYW5nZUJhbmQoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHZhciBhY2Nlc3Nvcl8xID0gc2NhbGUgPT09IHRoaXMueCgpLnNjYWxlID8gdGhpcy54KCkuYWNjZXNzb3IgOiB0aGlzLnkoKS5hY2Nlc3NvcjsKICAgICAgICAgICAgICAgIHZhciBhY2Nlc3NvckRhdGEgPSBkMy5zZXQodXRpbHMkMS5BcnJheS5mbGF0dGVuKHRoaXMuZGF0YXNldHMoKS5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZGF0YXNldC5kYXRhKCkubWFwKGZ1bmN0aW9uIChkLCBpKSB7IHJldHVybiBhY2Nlc3Nvcl8xKGQsIGksIGRhdGFzZXQpLnZhbHVlT2YoKTsgfSk7CiAgICAgICAgICAgICAgICB9KSkpLnZhbHVlcygpLm1hcChmdW5jdGlvbiAodmFsdWUpIHsgcmV0dXJuICt2YWx1ZTsgfSk7CiAgICAgICAgICAgICAgICAvLyBHZXQgdGhlIGFic29sdXRlIGRpZmZlcmVuY2UgYmV0d2VlbiBtaW4gYW5kIG1heAogICAgICAgICAgICAgICAgdmFyIG1pbiA9IHV0aWxzJDEuTWF0aC5taW4oYWNjZXNzb3JEYXRhLCAwKTsKICAgICAgICAgICAgICAgIHZhciBtYXggPSB1dGlscyQxLk1hdGgubWF4KGFjY2Vzc29yRGF0YSwgMCk7CiAgICAgICAgICAgICAgICB2YXIgc2NhbGVkTWluID0gc2NhbGUuc2NhbGUobWluKTsKICAgICAgICAgICAgICAgIHZhciBzY2FsZWRNYXggPSBzY2FsZS5zY2FsZShtYXgpOwogICAgICAgICAgICAgICAgcmV0dXJuIChzY2FsZWRNYXggLSBzY2FsZWRNaW4pIC8gTWF0aC5hYnMobWF4IC0gbWluKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLnByb3RvdHlwZS5fZ2V0RGF0YVRvRHJhdyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGRhdGFUb0RyYXcgPSBuZXcgdXRpbHMkMS5NYXAoKTsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhc2V0LmRhdGEoKS5tYXAoZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgaXNWYWxpZCA9ICh1dGlscyQxLk1hdGguaXNWYWxpZE51bWJlcihhdHRyVG9Qcm9qZWN0b3JbIngiXShkLCBpLCBkYXRhc2V0KSkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIoYXR0clRvUHJvamVjdG9yWyJ5Il0oZCwgaSwgZGF0YXNldCkpICYmCiAgICAgICAgICAgICAgICAgICAgICAgIHV0aWxzJDEuTWF0aC5pc1ZhbGlkTnVtYmVyKGF0dHJUb1Byb2plY3Rvclsid2lkdGgiXShkLCBpLCBkYXRhc2V0KSkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgdXRpbHMkMS5NYXRoLmlzVmFsaWROdW1iZXIoYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXShkLCBpLCBkYXRhc2V0KSkpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBpc1ZhbGlkID8gZCA6IG51bGw7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGRhdGFUb0RyYXcuc2V0KGRhdGFzZXQsIGRhdGEpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGRhdGFUb0RyYXc7CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLl9hZGRpdGlvbmFsUGFpbnQgPSBmdW5jdGlvbiAodGltZSkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB0aGlzLl9yZW5kZXJBcmVhLnNlbGVjdEFsbCgiLmxhYmVsLWFyZWEiKS5yZW1vdmUoKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2xhYmVsc0VuYWJsZWQgJiYgdGhpcy5sYWJlbCgpICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHV0aWxzJDEuV2luZG93LnNldFRpbWVvdXQoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2RyYXdMYWJlbHMoKTsgfSwgdGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFJlY3RhbmdsZS5wcm90b3R5cGUuX2RyYXdMYWJlbHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBkYXRhVG9EcmF3ID0gdGhpcy5fZ2V0RGF0YVRvRHJhdygpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCwgaSkgeyByZXR1cm4gX3RoaXMuX2RyYXdMYWJlbChkYXRhVG9EcmF3LCBkYXRhc2V0LCBpKTsgfSk7CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLl9kcmF3TGFiZWwgPSBmdW5jdGlvbiAoZGF0YVRvRHJhdywgZGF0YXNldCwgZGF0YXNldEluZGV4KSB7CiAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgdmFyIGxhYmVsQXJlYSA9IHRoaXMuX3JlbmRlckFyZWEuYXBwZW5kKCJnIikuY2xhc3NlZCgibGFiZWwtYXJlYSIsIHRydWUpOwogICAgICAgICAgICB2YXIgY29udGV4dCA9IG5ldyBzcmMkMS5TdmdDb250ZXh0KGxhYmVsQXJlYS5ub2RlKCkpOwogICAgICAgICAgICB2YXIgbWVhc3VyZXIgPSBuZXcgc3JjJDEuQ2FjaGVNZWFzdXJlcihjb250ZXh0KTsKICAgICAgICAgICAgdmFyIHdyaXRlciA9IG5ldyBzcmMkMS5Xcml0ZXIobWVhc3VyZXIsIGNvbnRleHQpOwogICAgICAgICAgICB2YXIgeFJhbmdlID0gdGhpcy54KCkuc2NhbGUucmFuZ2UoKTsKICAgICAgICAgICAgdmFyIHlSYW5nZSA9IHRoaXMueSgpLnNjYWxlLnJhbmdlKCk7CiAgICAgICAgICAgIHZhciB4TWluID0gTWF0aC5taW4uYXBwbHkobnVsbCwgeFJhbmdlKTsKICAgICAgICAgICAgdmFyIHhNYXggPSBNYXRoLm1heC5hcHBseShudWxsLCB4UmFuZ2UpOwogICAgICAgICAgICB2YXIgeU1pbiA9IE1hdGgubWluLmFwcGx5KG51bGwsIHlSYW5nZSk7CiAgICAgICAgICAgIHZhciB5TWF4ID0gTWF0aC5tYXguYXBwbHkobnVsbCwgeVJhbmdlKTsKICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhVG9EcmF3LmdldChkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGRhdGFMZW5ndGggPSBkYXRhLmxlbmd0aDsKICAgICAgICAgICAgZm9yICh2YXIgZGF0dW1JbmRleCA9IDA7IGRhdHVtSW5kZXggPCBkYXRhTGVuZ3RoOyBkYXR1bUluZGV4KyspIHsKICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGRhdGFbZGF0dW1JbmRleF07CiAgICAgICAgICAgICAgICBpZiAoZGF0dW0gPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIGxhYmVsID0gIiIgKyB0aGlzLmxhYmVsKCkoZGF0dW0sIGRhdHVtSW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIG1lYXN1cmVtZW50ID0gbWVhc3VyZXIubWVhc3VyZShsYWJlbCk7CiAgICAgICAgICAgICAgICB2YXIgeCA9IGF0dHJUb1Byb2plY3RvclsieCJdKGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciB5ID0gYXR0clRvUHJvamVjdG9yWyJ5Il0oZGF0dW0sIGRhdHVtSW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIHdpZHRoID0gYXR0clRvUHJvamVjdG9yWyJ3aWR0aCJdKGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBoZWlnaHQgPSBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdKGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmIChtZWFzdXJlbWVudC5oZWlnaHQgPD0gaGVpZ2h0ICYmIG1lYXN1cmVtZW50LndpZHRoIDw9IHdpZHRoKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGhvcml6b250YWxPZmZzZXQgPSAod2lkdGggLSBtZWFzdXJlbWVudC53aWR0aCkgLyAyOwogICAgICAgICAgICAgICAgICAgIHZhciB2ZXJ0aWNhbE9mZnNldCA9IChoZWlnaHQgLSBtZWFzdXJlbWVudC5oZWlnaHQpIC8gMjsKICAgICAgICAgICAgICAgICAgICB4ICs9IGhvcml6b250YWxPZmZzZXQ7CiAgICAgICAgICAgICAgICAgICAgeSArPSB2ZXJ0aWNhbE9mZnNldDsKICAgICAgICAgICAgICAgICAgICB2YXIgeExhYmVsUmFuZ2UgPSB7IG1pbjogeCwgbWF4OiB4ICsgbWVhc3VyZW1lbnQud2lkdGggfTsKICAgICAgICAgICAgICAgICAgICB2YXIgeUxhYmVsUmFuZ2UgPSB7IG1pbjogeSwgbWF4OiB5ICsgbWVhc3VyZW1lbnQuaGVpZ2h0IH07CiAgICAgICAgICAgICAgICAgICAgaWYgKHhMYWJlbFJhbmdlLm1pbiA8IHhNaW4gfHwgeExhYmVsUmFuZ2UubWF4ID4geE1heCB8fCB5TGFiZWxSYW5nZS5taW4gPCB5TWluIHx8IHlMYWJlbFJhbmdlLm1heCA+IHlNYXgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmICh0aGlzLl9vdmVybGF5TGFiZWwoeExhYmVsUmFuZ2UsIHlMYWJlbFJhbmdlLCBkYXR1bUluZGV4LCBkYXRhc2V0SW5kZXgsIGRhdGFUb0RyYXcpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB2YXIgY29sb3IgPSBhdHRyVG9Qcm9qZWN0b3JbImZpbGwiXShkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGRhcmsgPSB1dGlscyQxLkNvbG9yLmNvbnRyYXN0KCJ3aGl0ZSIsIGNvbG9yKSAqIDEuNiA8IHV0aWxzJDEuQ29sb3IuY29udHJhc3QoImJsYWNrIiwgY29sb3IpOwogICAgICAgICAgICAgICAgICAgIHZhciBnID0gbGFiZWxBcmVhLmFwcGVuZCgiZyIpLmF0dHIoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIHggKyAiLCIgKyB5ICsgIikiKTsKICAgICAgICAgICAgICAgICAgICB2YXIgY2xhc3NOYW1lID0gZGFyayA/ICJkYXJrLWxhYmVsIiA6ICJsaWdodC1sYWJlbCI7CiAgICAgICAgICAgICAgICAgICAgZy5jbGFzc2VkKGNsYXNzTmFtZSwgdHJ1ZSk7CiAgICAgICAgICAgICAgICAgICAgd3JpdGVyLndyaXRlKGxhYmVsLCBtZWFzdXJlbWVudC53aWR0aCwgbWVhc3VyZW1lbnQuaGVpZ2h0LCB7CiAgICAgICAgICAgICAgICAgICAgICAgIHhBbGlnbjogImNlbnRlciIsCiAgICAgICAgICAgICAgICAgICAgICAgIHlBbGlnbjogImNlbnRlciIsCiAgICAgICAgICAgICAgICAgICAgfSwgZy5ub2RlKCkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBSZWN0YW5nbGUucHJvdG90eXBlLl9vdmVybGF5TGFiZWwgPSBmdW5jdGlvbiAobGFiZWxYUmFuZ2UsIGxhYmVsWVJhbmdlLCBkYXR1bUluZGV4LCBkYXRhc2V0SW5kZXgsIGRhdGFUb0RyYXcpIHsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICB2YXIgZGF0YXNldHMgPSB0aGlzLmRhdGFzZXRzKCk7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSBkYXRhc2V0SW5kZXg7IGkgPCBkYXRhc2V0cy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgdmFyIGRhdGFzZXQgPSBkYXRhc2V0c1tpXTsKICAgICAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YVRvRHJhdy5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgZGF0YUxlbiA9IGRhdGEubGVuZ3RoOwogICAgICAgICAgICAgICAgZm9yICh2YXIgaiA9IChpID09PSBkYXRhc2V0SW5kZXggPyBkYXR1bUluZGV4ICsgMSA6IDApOyBqIDwgZGF0YUxlbjsgaisrKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHV0aWxzJDEuRE9NLmludGVyc2VjdHNCQm94KGxhYmVsWFJhbmdlLCBsYWJlbFlSYW5nZSwgdGhpcy5fZW50aXR5QkJveChkYXRhW2pdLCBqLCBkYXRhc2V0LCBhdHRyVG9Qcm9qZWN0b3IpKSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH07CiAgICAgICAgUmVjdGFuZ2xlLl9YMl9LRVkgPSAieDIiOwogICAgICAgIFJlY3RhbmdsZS5fWTJfS0VZID0gInkyIjsKICAgICAgICByZXR1cm4gUmVjdGFuZ2xlOwogICAgfSh4eVBsb3QuWFlQbG90KSk7CiAgICBleHBvcnRzLlJlY3RhbmdsZSA9IFJlY3RhbmdsZTsKICAgIH0pOwoKICAgIHZhciBzY2F0dGVyUGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgoKCgoKCgoKICAgIHZhciBTY2F0dGVyID0gLyoqIEBjbGFzcyAqLyAoZnVuY3Rpb24gKF9zdXBlcikgewogICAgICAgIHRzbGliX2VzNi5fX2V4dGVuZHMoU2NhdHRlciwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBBIFNjYXR0ZXIgUGxvdCBkcmF3cyBhIHN5bWJvbCBhdCBlYWNoIGRhdGEgcG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBTY2F0dGVyKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzKSB8fCB0aGlzOwogICAgICAgICAgICBfdGhpcy5fbGFiZWxGb3JtYXR0ZXIgPSBmb3JtYXR0ZXJzLmlkZW50aXR5KCk7CiAgICAgICAgICAgIF90aGlzLl9sYWJlbHNFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJzY2F0dGVyLXBsb3QiKTsKICAgICAgICAgICAgdmFyIGFuaW1hdG9yID0gbmV3IGFuaW1hdG9ycy5FYXNpbmcoKTsKICAgICAgICAgICAgYW5pbWF0b3Iuc3RhcnREZWxheSg1KTsKICAgICAgICAgICAgYW5pbWF0b3Iuc3RlcER1cmF0aW9uKDI1MCk7CiAgICAgICAgICAgIGFuaW1hdG9yLm1heFRvdGFsRHVyYXRpb24ocGxvdC5QbG90Ll9BTklNQVRJT05fTUFYX0RVUkFUSU9OKTsKICAgICAgICAgICAgX3RoaXMuYW5pbWF0b3IocGxvdHMuQW5pbWF0b3IuTUFJTiwgYW5pbWF0b3IpOwogICAgICAgICAgICBfdGhpcy5hdHRyKCJvcGFjaXR5IiwgMC42KTsKICAgICAgICAgICAgX3RoaXMuYXR0cigiZmlsbCIsIG5ldyBzY2FsZXMuQ29sb3IoKS5yYW5nZSgpWzBdKTsKICAgICAgICAgICAgX3RoaXMuc2l6ZSg2KTsKICAgICAgICAgICAgdmFyIGNpcmNsZVN5bWJvbEZhY3RvcnkgPSBzeW1ib2xGYWN0b3JpZXMuY2lyY2xlKCk7CiAgICAgICAgICAgIF90aGlzLnN5bWJvbChmdW5jdGlvbiAoKSB7IHJldHVybiBjaXJjbGVTeW1ib2xGYWN0b3J5OyB9KTsKICAgICAgICAgICAgX3RoaXMuX2xhYmVsQ29uZmlnID0gbmV3IHV0aWxzJDEuTWFwKCk7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgU2NhdHRlci5wcm90b3R5cGUuX2J1aWxkTGlnaHR3ZWlnaHRQbG90RW50aXRpZXMgPSBmdW5jdGlvbiAoZGF0YXNldHMpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGxpZ2h0d2VpZ2h0UGxvdEVudGl0aWVzID0gX3N1cGVyLnByb3RvdHlwZS5fYnVpbGRMaWdodHdlaWdodFBsb3RFbnRpdGllcy5jYWxsKHRoaXMsIGRhdGFzZXRzKTsKICAgICAgICAgICAgcmV0dXJuIGxpZ2h0d2VpZ2h0UGxvdEVudGl0aWVzLm1hcChmdW5jdGlvbiAobGlnaHR3ZWlnaHRQbG90RW50aXR5KSB7CiAgICAgICAgICAgICAgICB2YXIgZGlhbWV0ZXIgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKF90aGlzLnNpemUoKSkobGlnaHR3ZWlnaHRQbG90RW50aXR5LmRhdHVtLCBsaWdodHdlaWdodFBsb3RFbnRpdHkuaW5kZXgsIGxpZ2h0d2VpZ2h0UGxvdEVudGl0eS5kYXRhc2V0KTsKICAgICAgICAgICAgICAgIGxpZ2h0d2VpZ2h0UGxvdEVudGl0eS5kaWFtZXRlciA9IGRpYW1ldGVyOwogICAgICAgICAgICAgICAgcmV0dXJuIGxpZ2h0d2VpZ2h0UGxvdEVudGl0eTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fY3JlYXRlRHJhd2VyID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXIuUHJveHlEcmF3ZXIoZnVuY3Rpb24gKCkgeyByZXR1cm4gbmV3IHN5bWJvbERyYXdlci5TeW1ib2xTVkdEcmF3ZXIoKTsgfSwgZnVuY3Rpb24gKGN0eCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXJzLkNhbnZhc0RyYXdlcihjdHgsIHN5bWJvbERyYXdlci5tYWtlU3ltYm9sQ2FudmFzRHJhd1N0ZXAoZGF0YXNldCwgZnVuY3Rpb24gKCkgeyByZXR1cm4gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3NvcihfdGhpcy5zeW1ib2woKSk7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IoX3RoaXMuc2l6ZSgpKTsgfSkpOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIFNjYXR0ZXIucHJvdG90eXBlLnNpemUgPSBmdW5jdGlvbiAoc2l6ZSwgc2NhbGUpIHsKICAgICAgICAgICAgaWYgKHNpemUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFNjYXR0ZXIuX1NJWkVfS0VZKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoU2NhdHRlci5fU0laRV9LRVksIHNpemUsIHNjYWxlKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5zeW1ib2wgPSBmdW5jdGlvbiAoc3ltYm9sKSB7CiAgICAgICAgICAgIGlmIChzeW1ib2wgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFNjYXR0ZXIuX1NZTUJPTF9LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3Byb3BlcnR5QmluZGluZ3Muc2V0KFNjYXR0ZXIuX1NZTUJPTF9LRVksIHsgYWNjZXNzb3I6IHN5bWJvbCB9KTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fZ2VuZXJhdGVEcmF3U3RlcHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBkcmF3U3RlcHMgPSBbXTsKICAgICAgICAgICAgaWYgKHRoaXMuX2FuaW1hdGVPbk5leHRSZW5kZXIoKSkgewogICAgICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICAgICAgdmFyIHN5bWJvbFByb2plY3Rvcl8xID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnN5bWJvbCgpKTsKICAgICAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsiZCJdID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgeyByZXR1cm4gc3ltYm9sUHJvamVjdG9yXzEoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSgwKShudWxsKTsgfTsKICAgICAgICAgICAgICAgIGRyYXdTdGVwcy5wdXNoKHsgYXR0clRvUHJvamVjdG9yOiBhdHRyVG9Qcm9qZWN0b3IsIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5SRVNFVCkgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZHJhd1N0ZXBzLnB1c2goewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yOiB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKSwKICAgICAgICAgICAgICAgIGFuaW1hdG9yOiB0aGlzLl9nZXRBbmltYXRvcihwbG90cy5BbmltYXRvci5NQUlOKSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkcmF3U3RlcHM7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fcHJvcGVydHlQcm9qZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgcHJvcGVydHlUb1Byb2plY3RvcnMgPSBfc3VwZXIucHJvdG90eXBlLl9wcm9wZXJ0eVByb2plY3RvcnMuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdmFyIHhQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsKICAgICAgICAgICAgdmFyIHlQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKTsKICAgICAgICAgICAgcHJvcGVydHlUb1Byb2plY3RvcnNbIngiXSA9IHhQcm9qZWN0b3I7CiAgICAgICAgICAgIHByb3BlcnR5VG9Qcm9qZWN0b3JzWyJ5Il0gPSB5UHJvamVjdG9yOwogICAgICAgICAgICBwcm9wZXJ0eVRvUHJvamVjdG9yc1sidHJhbnNmb3JtIl0gPSBmdW5jdGlvbiAoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gInRyYW5zbGF0ZSgiICsgeFByb2plY3RvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpICsgIiwiICsgeVByb2plY3RvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpICsgIikiOwogICAgICAgICAgICB9OwogICAgICAgICAgICBwcm9wZXJ0eVRvUHJvamVjdG9yc1siZCJdID0gdGhpcy5fY29uc3RydWN0U3ltYm9sR2VuZXJhdG9yKCk7CiAgICAgICAgICAgIHJldHVybiBwcm9wZXJ0eVRvUHJvamVjdG9yczsKICAgICAgICB9OwogICAgICAgIFNjYXR0ZXIucHJvdG90eXBlLl9jb25zdHJ1Y3RTeW1ib2xHZW5lcmF0b3IgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBzeW1ib2xQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMuc3ltYm9sKCkpOwogICAgICAgICAgICB2YXIgc2l6ZVByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5zaXplKCkpOwogICAgICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHN5bWJvbFByb2plY3RvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpKHNpemVQcm9qZWN0b3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSkobnVsbCk7CiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fZW50aXR5Qm91bmRzID0gZnVuY3Rpb24gKGVudGl0eSkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgeDogZW50aXR5LnBvc2l0aW9uLnggLSBlbnRpdHkuZGlhbWV0ZXIgLyAyLAogICAgICAgICAgICAgICAgeTogZW50aXR5LnBvc2l0aW9uLnkgLSBlbnRpdHkuZGlhbWV0ZXIgLyAyLAogICAgICAgICAgICAgICAgd2lkdGg6IGVudGl0eS5kaWFtZXRlciwKICAgICAgICAgICAgICAgIGhlaWdodDogZW50aXR5LmRpYW1ldGVyLAogICAgICAgICAgICB9OwogICAgICAgIH07CiAgICAgICAgU2NhdHRlci5wcm90b3R5cGUuX2VudGl0eVZpc2libGVPblBsb3QgPSBmdW5jdGlvbiAoZW50aXR5LCBib3VuZHMpIHsKICAgICAgICAgICAgdmFyIHhSYW5nZSA9IHsgbWluOiBib3VuZHMudG9wTGVmdC54LCBtYXg6IGJvdW5kcy5ib3R0b21SaWdodC54IH07CiAgICAgICAgICAgIHZhciB5UmFuZ2UgPSB7IG1pbjogYm91bmRzLnRvcExlZnQueSwgbWF4OiBib3VuZHMuYm90dG9tUmlnaHQueSB9OwogICAgICAgICAgICB2YXIgdHJhbnNsYXRlZEJib3ggPSB0aGlzLl9lbnRpdHlCb3VuZHMoZW50aXR5KTsKICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuRE9NLmludGVyc2VjdHNCQm94KHhSYW5nZSwgeVJhbmdlLCB0cmFuc2xhdGVkQmJveCk7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBFbnRpdGllcyBhdCBhIHBhcnRpY3VsYXIgUG9pbnQuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0ge1BvaW50fSBwCiAgICAgICAgICogQHJldHVybnMge1Bsb3RFbnRpdHlbXX0KICAgICAgICAgKi8KICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5lbnRpdGllc0F0ID0gZnVuY3Rpb24gKHApIHsKICAgICAgICAgICAgdmFyIHhQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsKICAgICAgICAgICAgdmFyIHlQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueSgpKTsKICAgICAgICAgICAgdmFyIHNpemVQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMuc2l6ZSgpKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuZW50aXRpZXMoKS5maWx0ZXIoZnVuY3Rpb24gKGVudGl0eSkgewogICAgICAgICAgICAgICAgdmFyIGRhdHVtID0gZW50aXR5LmRhdHVtOwogICAgICAgICAgICAgICAgdmFyIGluZGV4ID0gZW50aXR5LmluZGV4OwogICAgICAgICAgICAgICAgdmFyIGRhdGFzZXQgPSBlbnRpdHkuZGF0YXNldDsKICAgICAgICAgICAgICAgIHZhciB4ID0geFByb2plY3RvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIHkgPSB5UHJvamVjdG9yKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgc2l6ZSA9IHNpemVQcm9qZWN0b3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHJldHVybiB4IC0gc2l6ZSAvIDIgPD0gcC54ICYmIHAueCA8PSB4ICsgc2l6ZSAvIDIgJiYgeSAtIHNpemUgLyAyIDw9IHAueSAmJiBwLnkgPD0geSArIHNpemUgLyAyOwogICAgICAgICAgICB9KTsKICAgICAgICB9OwogICAgICAgIFNjYXR0ZXIucHJvdG90eXBlLmxhYmVsc0VuYWJsZWQgPSBmdW5jdGlvbiAoZW5hYmxlZCkgewogICAgICAgICAgICBpZiAoZW5hYmxlZCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fbGFiZWxzRW5hYmxlZDsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2xhYmVsc0VuYWJsZWQgPSBlbmFibGVkOwogICAgICAgICAgICAgICAgdGhpcy5fY2xlYXJBdHRyVG9Qcm9qZWN0b3JDYWNoZSgpOwogICAgICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fY3JlYXRlTm9kZXNGb3JEYXRhc2V0ID0gZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgdmFyIGRyYXdlciA9IF9zdXBlci5wcm90b3R5cGUuX2NyZWF0ZU5vZGVzRm9yRGF0YXNldC5jYWxsKHRoaXMsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgbGFiZWxBcmVhID0gdGhpcy5fcmVuZGVyQXJlYS5hcHBlbmQoImciKS5jbGFzc2VkKFNjYXR0ZXIuX0xBQkVMX0FSRUFfQ0xBU1MsIHRydWUpOwogICAgICAgICAgICB2YXIgY29udGV4dCA9IG5ldyBzcmMkMS5TdmdDb250ZXh0KGxhYmVsQXJlYS5ub2RlKCkpOwogICAgICAgICAgICB2YXIgbWVhc3VyZXIgPSBuZXcgc3JjJDEuQ2FjaGVNZWFzdXJlcihjb250ZXh0KTsKICAgICAgICAgICAgdmFyIHdyaXRlciA9IG5ldyBzcmMkMS5Xcml0ZXIobWVhc3VyZXIsIGNvbnRleHQpOwogICAgICAgICAgICB0aGlzLl9sYWJlbENvbmZpZy5zZXQoZGF0YXNldCwgeyBsYWJlbEFyZWE6IGxhYmVsQXJlYSwgbWVhc3VyZXI6IG1lYXN1cmVyLCB3cml0ZXI6IHdyaXRlciB9KTsKICAgICAgICAgICAgcmV0dXJuIGRyYXdlcjsKICAgICAgICB9OwogICAgICAgIFNjYXR0ZXIucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0Tm9kZXMgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9yZW1vdmVEYXRhc2V0Tm9kZXMuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIGxhYmVsQ29uZmlnID0gdGhpcy5fbGFiZWxDb25maWcuZ2V0KGRhdGFzZXQpOwogICAgICAgICAgICBpZiAobGFiZWxDb25maWcgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgbGFiZWxDb25maWcubGFiZWxBcmVhLnJlbW92ZSgpOwogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxDb25maWcuZGVsZXRlKGRhdGFzZXQpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fYWRkaXRpb25hbFBhaW50ID0gZnVuY3Rpb24gKHRpbWUpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdGhpcy5kYXRhc2V0cygpLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsgcmV0dXJuIF90aGlzLl9sYWJlbENvbmZpZy5nZXQoZGF0YXNldCkubGFiZWxBcmVhLnNlbGVjdEFsbCgiZyIpLnJlbW92ZSgpOyB9KTsKICAgICAgICAgICAgaWYgKHRoaXMuX2xhYmVsc0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgIHV0aWxzJDEuV2luZG93LnNldFRpbWVvdXQoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2RyYXdMYWJlbHMoKTsgfSwgdGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFNjYXR0ZXIucHJvdG90eXBlLl9kcmF3TGFiZWxzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgZGF0YVRvRHJhdyA9IHRoaXMuX2dldERhdGFUb0RyYXcoKTsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzKCkuZm9yRWFjaChmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICAgICAgdmFyIGRhdGEgPSBkYXRhVG9EcmF3LmdldChkYXRhc2V0KTsKICAgICAgICAgICAgICAgIHZhciBkYXRhTGVuID0gZGF0YS5sZW5ndGg7CiAgICAgICAgICAgICAgICBmb3IgKHZhciBpbmRleCA9IDA7IGluZGV4IDwgZGF0YUxlbjsgaW5kZXgrKykgewogICAgICAgICAgICAgICAgICAgIHZhciBkYXR1bSA9IGRhdGFbaW5kZXhdOwogICAgICAgICAgICAgICAgICAgIGlmIChkYXR1bSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBfdGhpcy5fZHJhd0xhYmVsKGRhdHVtLCBpbmRleCwgZGF0YXNldCwgYXR0clRvUHJvamVjdG9yKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fZHJhd0xhYmVsID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCwgYXR0clRvUHJvamVjdG9yKSB7CiAgICAgICAgICAgIGlmIChkYXR1bS5sYWJlbCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIF9hID0gdGhpcy5fbGFiZWxDb25maWcuZ2V0KGRhdGFzZXQpLCBsYWJlbEFyZWEgPSBfYS5sYWJlbEFyZWEsIG1lYXN1cmVyID0gX2EubWVhc3VyZXIsIHdyaXRlciA9IF9hLndyaXRlcjsKICAgICAgICAgICAgdmFyIHNjYXR0ZXJDb29yZGluYXRlcyA9IHsgeDogYXR0clRvUHJvamVjdG9yWyJ4Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSwgeTogYXR0clRvUHJvamVjdG9yWyJ5Il0oZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB9OwogICAgICAgICAgICB2YXIgc2l6ZVByb2plY3RvciA9IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy5zaXplKCkpOwogICAgICAgICAgICB2YXIgZGlhbWV0ZXIgPSBzaXplUHJvamVjdG9yKGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgIHZhciBsYWJlbCA9IHRoaXMuX2xhYmVsRm9ybWF0dGVyKGRhdHVtLmxhYmVsLCBkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgbWVhc3VyZW1lbnQgPSBtZWFzdXJlci5tZWFzdXJlKGxhYmVsKTsKICAgICAgICAgICAgdmFyIF9iID0gdGhpcy5fY2FsY3VsYXRlTGFiZWxQcm9wZXJ0aWVzKHNjYXR0ZXJDb29yZGluYXRlcywgZGlhbWV0ZXIsIG1lYXN1cmVtZW50KSwgY29udGFpbmVyRGltZW5zaW9ucyA9IF9iLmNvbnRhaW5lckRpbWVuc2lvbnMsIGxhYmVsQ29udGFpbmVyT3JpZ2luID0gX2IubGFiZWxDb250YWluZXJPcmlnaW4sIGxhYmVsT3JpZ2luID0gX2IubGFiZWxPcmlnaW4sIGFsaWdubWVudCA9IF9iLmFsaWdubWVudDsKICAgICAgICAgICAgdmFyIGxhYmVsQ29udGFpbmVyID0gdGhpcy5fY3JlYXRlTGFiZWxDb250YWluZXIobGFiZWxBcmVhLCBsYWJlbENvbnRhaW5lck9yaWdpbiwgbGFiZWxPcmlnaW4sIG1lYXN1cmVtZW50KTsKICAgICAgICAgICAgdmFyIHdyaXRlT3B0aW9ucyA9IHsgeEFsaWduOiBhbGlnbm1lbnQueCwgeUFsaWduOiBhbGlnbm1lbnQueSB9OwogICAgICAgICAgICB3cml0ZXIud3JpdGUobGFiZWwsIGNvbnRhaW5lckRpbWVuc2lvbnMud2lkdGgsIGNvbnRhaW5lckRpbWVuc2lvbnMuaGVpZ2h0LCB3cml0ZU9wdGlvbnMsIGxhYmVsQ29udGFpbmVyLm5vZGUoKSk7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fY2FsY3VsYXRlTGFiZWxQcm9wZXJ0aWVzID0gZnVuY3Rpb24gKHBvaW50Q29vcmRpbmF0ZXMsIGRpYW1ldGVyLCBtZWFzdXJlbWVudCkgewogICAgICAgICAgICAvLyBJZiBkaWFtZXRlciBpcyBzbWFsbGVyIHRoYW4gZm9udCBzaXplLCBwdXQgbGFiZWwgYWJvdmUKICAgICAgICAgICAgdmFyIGxhYmVsU2hpZnQgPSBkaWFtZXRlciA8IG1lYXN1cmVtZW50LmhlaWdodCA/IGRpYW1ldGVyIC8gMiArIFNjYXR0ZXIuX0xBQkVMX01BUkdJTl9GUk9NX0JVQkJMRSA6IDA7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBjb250YWluZXJEaW1lbnNpb25zOiB7CiAgICAgICAgICAgICAgICAgICAgd2lkdGg6IG1lYXN1cmVtZW50LndpZHRoLAogICAgICAgICAgICAgICAgICAgIGhlaWdodDogbWVhc3VyZW1lbnQuaGVpZ2h0LAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGxhYmVsQ29udGFpbmVyT3JpZ2luOiB7CiAgICAgICAgICAgICAgICAgICAgeDogcG9pbnRDb29yZGluYXRlcy54IC0gbWVhc3VyZW1lbnQud2lkdGggLyAyLAogICAgICAgICAgICAgICAgICAgIHk6IHBvaW50Q29vcmRpbmF0ZXMueSAtIG1lYXN1cmVtZW50LmhlaWdodCAvIDIgKyBsYWJlbFNoaWZ0LAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGxhYmVsT3JpZ2luOiB7CiAgICAgICAgICAgICAgICAgICAgeDogcG9pbnRDb29yZGluYXRlcy54LAogICAgICAgICAgICAgICAgICAgIHk6IHBvaW50Q29vcmRpbmF0ZXMueSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICBhbGlnbm1lbnQ6IHsKICAgICAgICAgICAgICAgICAgICB4OiAiY2VudGVyIiwKICAgICAgICAgICAgICAgICAgICB5OiAiY2VudGVyIiwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgIH07CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLnByb3RvdHlwZS5fY3JlYXRlTGFiZWxDb250YWluZXIgPSBmdW5jdGlvbiAobGFiZWxBcmVhLCBsYWJlbENvbnRhaW5lck9yaWdpbiwgbGFiZWxPcmlnaW4sIG1lYXN1cmVtZW50KSB7CiAgICAgICAgICAgIHZhciBsYWJlbENvbnRhaW5lciA9IGxhYmVsQXJlYS5hcHBlbmQoImciKQogICAgICAgICAgICAgICAgLmF0dHIoInRyYW5zZm9ybSIsICJ0cmFuc2xhdGUoIiArIGxhYmVsQ29udGFpbmVyT3JpZ2luLnggKyAiLCAiICsgbGFiZWxDb250YWluZXJPcmlnaW4ueSArICIpIik7CiAgICAgICAgICAgIGxhYmVsQ29udGFpbmVyLmNsYXNzZWQoIm9uLWJhci1sYWJlbCIsIHRydWUpOwogICAgICAgICAgICByZXR1cm4gbGFiZWxDb250YWluZXI7CiAgICAgICAgfTsKICAgICAgICBTY2F0dGVyLl9TSVpFX0tFWSA9ICJzaXplIjsKICAgICAgICBTY2F0dGVyLl9TWU1CT0xfS0VZID0gInN5bWJvbCI7CiAgICAgICAgLy8gbGFiZWwgc3R1ZmYKICAgICAgICBTY2F0dGVyLl9MQUJFTF9BUkVBX0NMQVNTID0gInNjYXR0ZXItbGFiZWwtdGV4dC1hcmVhIjsKICAgICAgICBTY2F0dGVyLl9MQUJFTF9NQVJHSU5fRlJPTV9CVUJCTEUgPSAxNTsKICAgICAgICByZXR1cm4gU2NhdHRlcjsKICAgIH0oeHlQbG90LlhZUGxvdCkpOwogICAgZXhwb3J0cy5TY2F0dGVyID0gU2NhdHRlcjsKICAgIH0pOwoKICAgIHZhciBzZWdtZW50UGxvdCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwoKCgoKCgoKCiAgICB2YXIgU2VnbWVudCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFNlZ21lbnQsIF9zdXBlcik7CiAgICAgICAgLyoqCiAgICAgICAgICogQSBTZWdtZW50IFBsb3QgZGlzcGxheXMgbGluZSBzZWdtZW50cyBiYXNlZCBvbiB0aGUgZGF0YS4KICAgICAgICAgKgogICAgICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIFNlZ21lbnQoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJzZWdtZW50LXBsb3QiKTsKICAgICAgICAgICAgX3RoaXMuYXR0cigic3Ryb2tlIiwgbmV3IHNjYWxlcy5Db2xvcigpLnJhbmdlKClbMF0pOwogICAgICAgICAgICBfdGhpcy5hdHRyKCJzdHJva2Utd2lkdGgiLCAiMnB4Iik7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgU2VnbWVudC5wcm90b3R5cGUuX2NyZWF0ZURyYXdlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcmV0dXJuIG5ldyBkcmF3ZXIuUHJveHlEcmF3ZXIoZnVuY3Rpb24gKCkgeyByZXR1cm4gbmV3IHNlZ21lbnREcmF3ZXIuU2VnbWVudFNWR0RyYXdlcigpOyB9LCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB3aW5kb3dVdGlscy53YXJuKCJjYW52YXMgcmVuZGVyZXIgaXMgbm90IHN1cHBvcnRlZCBvbiBTZWdtZW50IFBsb3QhIik7CiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS5fZ2VuZXJhdGVEcmF3U3RlcHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiBbeyBhdHRyVG9Qcm9qZWN0b3I6IHRoaXMuX2dldEF0dHJUb1Byb2plY3RvcigpLCBhbmltYXRvcjogbmV3IGFuaW1hdG9ycy5OdWxsKCkgfV07CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS5fZmlsdGVyRm9yUHJvcGVydHkgPSBmdW5jdGlvbiAocHJvcGVydHkpIHsKICAgICAgICAgICAgaWYgKHByb3BlcnR5ID09PSAieDIiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5fZmlsdGVyRm9yUHJvcGVydHkuY2FsbCh0aGlzLCAieCIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHByb3BlcnR5ID09PSAieTIiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5fZmlsdGVyRm9yUHJvcGVydHkuY2FsbCh0aGlzLCAieSIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLl9maWx0ZXJGb3JQcm9wZXJ0eS5jYWxsKHRoaXMsIHByb3BlcnR5KTsKICAgICAgICB9OwogICAgICAgIFNlZ21lbnQucHJvdG90eXBlLnggPSBmdW5jdGlvbiAoeCwgeFNjYWxlKSB7CiAgICAgICAgICAgIGlmICh4ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnguY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoeFNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueC5jYWxsKHRoaXMsIHgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS54LmNhbGwodGhpcywgeCwgeFNjYWxlKTsKICAgICAgICAgICAgICAgIHZhciB4MkJpbmRpbmcgPSB0aGlzLngyKCk7CiAgICAgICAgICAgICAgICB2YXIgeDIgPSB4MkJpbmRpbmcgJiYgeDJCaW5kaW5nLmFjY2Vzc29yOwogICAgICAgICAgICAgICAgaWYgKHgyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoU2VnbWVudC5fWDJfS0VZLCB4MiwgeFNjYWxlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFNlZ21lbnQucHJvdG90eXBlLngyID0gZnVuY3Rpb24gKHgyKSB7CiAgICAgICAgICAgIGlmICh4MiA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fcHJvcGVydHlCaW5kaW5ncy5nZXQoU2VnbWVudC5fWDJfS0VZKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgeEJpbmRpbmcgPSB0aGlzLngoKTsKICAgICAgICAgICAgdmFyIHhTY2FsZSA9IHhCaW5kaW5nICYmIHhCaW5kaW5nLnNjYWxlOwogICAgICAgICAgICB0aGlzLl9iaW5kUHJvcGVydHkoU2VnbWVudC5fWDJfS0VZLCB4MiwgeFNjYWxlKTsKICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS55ID0gZnVuY3Rpb24gKHksIHlTY2FsZSkgewogICAgICAgICAgICBpZiAoeSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS55LmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHlTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzLCB5KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMsIHksIHlTY2FsZSk7CiAgICAgICAgICAgICAgICB2YXIgeTJCaW5kaW5nID0gdGhpcy55MigpOwogICAgICAgICAgICAgICAgdmFyIHkyID0geTJCaW5kaW5nICYmIHkyQmluZGluZy5hY2Nlc3NvcjsKICAgICAgICAgICAgICAgIGlmICh5MiAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fYmluZFByb3BlcnR5KFNlZ21lbnQuX1kyX0tFWSwgeTIsIHlTY2FsZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS55MiA9IGZ1bmN0aW9uICh5MikgewogICAgICAgICAgICBpZiAoeTIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3Byb3BlcnR5QmluZGluZ3MuZ2V0KFNlZ21lbnQuX1kyX0tFWSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHlCaW5kaW5nID0gdGhpcy55KCk7CiAgICAgICAgICAgIHZhciB5U2NhbGUgPSB5QmluZGluZyAmJiB5QmluZGluZy5zY2FsZTsKICAgICAgICAgICAgdGhpcy5fYmluZFByb3BlcnR5KFNlZ21lbnQuX1kyX0tFWSwgeTIsIHlTY2FsZSk7CiAgICAgICAgICAgIHRoaXMucmVuZGVyKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU2VnbWVudC5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX3Byb3BlcnR5UHJvamVjdG9ycy5jYWxsKHRoaXMpOwogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbIngxIl0gPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsKICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJ4MiJdID0gdGhpcy54MigpID09IG51bGwgPyBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKSA6IHBsb3QuUGxvdC5fc2NhbGVkQWNjZXNzb3IodGhpcy54MigpKTsKICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJ5MSJdID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkoKSk7CiAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsieTIiXSA9IHRoaXMueTIoKSA9PSBudWxsID8gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3Nvcih0aGlzLnkoKSkgOiBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueTIoKSk7CiAgICAgICAgICAgIHJldHVybiBhdHRyVG9Qcm9qZWN0b3I7CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS5lbnRpdGllc0F0ID0gZnVuY3Rpb24gKHBvaW50KSB7CiAgICAgICAgICAgIHZhciBlbnRpdHkgPSB0aGlzLmVudGl0eU5lYXJlc3QocG9pbnQpOwogICAgICAgICAgICBpZiAoZW50aXR5ICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBbZW50aXR5XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgU2VnbWVudC5wcm90b3R5cGUuZW50aXRpZXNJbiA9IGZ1bmN0aW9uICh4UmFuZ2VPckJvdW5kcywgeVJhbmdlKSB7CiAgICAgICAgICAgIHZhciBkYXRhWFJhbmdlOwogICAgICAgICAgICB2YXIgZGF0YVlSYW5nZTsKICAgICAgICAgICAgaWYgKHlSYW5nZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICB2YXIgYm91bmRzID0geFJhbmdlT3JCb3VuZHM7CiAgICAgICAgICAgICAgICBkYXRhWFJhbmdlID0geyBtaW46IGJvdW5kcy50b3BMZWZ0LngsIG1heDogYm91bmRzLmJvdHRvbVJpZ2h0LnggfTsKICAgICAgICAgICAgICAgIGRhdGFZUmFuZ2UgPSB7IG1pbjogYm91bmRzLnRvcExlZnQueSwgbWF4OiBib3VuZHMuYm90dG9tUmlnaHQueSB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgZGF0YVhSYW5nZSA9IHhSYW5nZU9yQm91bmRzOwogICAgICAgICAgICAgICAgZGF0YVlSYW5nZSA9IHlSYW5nZTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5fZW50aXRpZXNJbnRlcnNlY3RpbmcoZGF0YVhSYW5nZSwgZGF0YVlSYW5nZSk7CiAgICAgICAgfTsKICAgICAgICBTZWdtZW50LnByb3RvdHlwZS5fZW50aXRpZXNJbnRlcnNlY3RpbmcgPSBmdW5jdGlvbiAoeFJhbmdlLCB5UmFuZ2UpIHsKICAgICAgICAgICAgdmFyIGludGVyc2VjdGVkID0gW107CiAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSB0aGlzLl9nZXRBdHRyVG9Qcm9qZWN0b3IoKTsKICAgICAgICAgICAgdmFyIGVudGl0aWVzID0gdGhpcy5lbnRpdGllcygpOwogICAgICAgICAgICB2YXIgZW50aXRpZXNMZW4gPSBlbnRpdGllcy5sZW5ndGg7CiAgICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgZW50aXRpZXNMZW47IGkrKykgewogICAgICAgICAgICAgICAgdmFyIGVudGl0eSA9IGVudGl0aWVzW2ldOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2xpbmVJbnRlcnNlY3RzQm94KGVudGl0eSwgeFJhbmdlLCB5UmFuZ2UsIGF0dHJUb1Byb2plY3RvcikpIHsKICAgICAgICAgICAgICAgICAgICBpbnRlcnNlY3RlZC5wdXNoKGVudGl0eSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGludGVyc2VjdGVkOwogICAgICAgIH07CiAgICAgICAgU2VnbWVudC5wcm90b3R5cGUuX2xpbmVJbnRlcnNlY3RzQm94ID0gZnVuY3Rpb24gKGVudGl0eSwgeFJhbmdlLCB5UmFuZ2UsIGF0dHJUb1Byb2plY3RvcikgewogICAgICAgICAgICB2YXIgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB2YXIgeDEgPSBhdHRyVG9Qcm9qZWN0b3JbIngxIl0oZW50aXR5LmRhdHVtLCBlbnRpdHkuaW5kZXgsIGVudGl0eS5kYXRhc2V0KTsKICAgICAgICAgICAgdmFyIHgyID0gYXR0clRvUHJvamVjdG9yWyJ4MiJdKGVudGl0eS5kYXR1bSwgZW50aXR5LmluZGV4LCBlbnRpdHkuZGF0YXNldCk7CiAgICAgICAgICAgIHZhciB5MSA9IGF0dHJUb1Byb2plY3RvclsieTEiXShlbnRpdHkuZGF0dW0sIGVudGl0eS5pbmRleCwgZW50aXR5LmRhdGFzZXQpOwogICAgICAgICAgICB2YXIgeTIgPSBhdHRyVG9Qcm9qZWN0b3JbInkyIl0oZW50aXR5LmRhdHVtLCBlbnRpdHkuaW5kZXgsIGVudGl0eS5kYXRhc2V0KTsKICAgICAgICAgICAgLy8gY2hlY2sgaWYgYW55IG9mIGVuZCBwb2ludHMgb2YgdGhlIHNlZ21lbnQgaXMgaW5zaWRlIHRoZSBib3gKICAgICAgICAgICAgaWYgKCh4UmFuZ2UubWluIDw9IHgxICYmIHgxIDw9IHhSYW5nZS5tYXggJiYgeVJhbmdlLm1pbiA8PSB5MSAmJiB5MSA8PSB5UmFuZ2UubWF4KSB8fAogICAgICAgICAgICAgICAgKHhSYW5nZS5taW4gPD0geDIgJiYgeDIgPD0geFJhbmdlLm1heCAmJiB5UmFuZ2UubWluIDw9IHkyICYmIHkyIDw9IHlSYW5nZS5tYXgpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgc3RhcnRQb2ludCA9IHsgeDogeDEsIHk6IHkxIH07CiAgICAgICAgICAgIHZhciBlbmRQb2ludCA9IHsgeDogeDIsIHk6IHkyIH07CiAgICAgICAgICAgIHZhciBjb3JuZXJzID0gWwogICAgICAgICAgICAgICAgeyB4OiB4UmFuZ2UubWluLCB5OiB5UmFuZ2UubWluIH0sCiAgICAgICAgICAgICAgICB7IHg6IHhSYW5nZS5taW4sIHk6IHlSYW5nZS5tYXggfSwKICAgICAgICAgICAgICAgIHsgeDogeFJhbmdlLm1heCwgeTogeVJhbmdlLm1heCB9LAogICAgICAgICAgICAgICAgeyB4OiB4UmFuZ2UubWF4LCB5OiB5UmFuZ2UubWluIH0sCiAgICAgICAgICAgIF07CiAgICAgICAgICAgIHZhciBpbnRlcnNlY3Rpb25zID0gY29ybmVycy5maWx0ZXIoZnVuY3Rpb24gKHBvaW50LCBpbmRleCkgewogICAgICAgICAgICAgICAgaWYgKGluZGV4ICE9PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gcmV0dXJuIHRydWUgaWYgYm9yZGVyIGZvcm1lZCBieSBjb25lY3RpbmcgY3VycmVudCBjb3JuZXIgYW5kIHByZXZpb3VzIGNvcm5lciBpbnRlcnNlY3RzIHdpdGggdGhlIHNlZ21lbnQKICAgICAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2xpbmVJbnRlcnNlY3RzU2VnbWVudChzdGFydFBvaW50LCBlbmRQb2ludCwgcG9pbnQsIGNvcm5lcnNbaW5kZXggLSAxXSkgJiYKICAgICAgICAgICAgICAgICAgICAgICAgX3RoaXMuX2xpbmVJbnRlcnNlY3RzU2VnbWVudChwb2ludCwgY29ybmVyc1tpbmRleCAtIDFdLCBzdGFydFBvaW50LCBlbmRQb2ludCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gaW50ZXJzZWN0aW9ucy5sZW5ndGggPiAwOwogICAgICAgIH07CiAgICAgICAgU2VnbWVudC5wcm90b3R5cGUuX2xpbmVJbnRlcnNlY3RzU2VnbWVudCA9IGZ1bmN0aW9uIChwb2ludDEsIHBvaW50MiwgcG9pbnQzLCBwb2ludDQpIHsKICAgICAgICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLXNoYWRvd2VkLXZhcmlhYmxlCiAgICAgICAgICAgIHZhciBjYWxjT3JpZW50YXRpb24gPSBmdW5jdGlvbiAocG9pbnQxLCBwb2ludDIsIHBvaW50KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gKHBvaW50Mi54IC0gcG9pbnQxLngpICogKHBvaW50LnkgLSBwb2ludDIueSkgLSAocG9pbnQyLnkgLSBwb2ludDEueSkgKiAocG9pbnQueCAtIHBvaW50Mi54KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgLy8gcG9pbnQzIGFuZCBwb2ludDQgYXJlIG9uIGRpZmZlcmVudCBzaWRlcyBvZiBsaW5lIGZvcm1lZCBieSBwb2ludDEgYW5kIHBvaW50MgogICAgICAgICAgICByZXR1cm4gY2FsY09yaWVudGF0aW9uKHBvaW50MSwgcG9pbnQyLCBwb2ludDMpICogY2FsY09yaWVudGF0aW9uKHBvaW50MSwgcG9pbnQyLCBwb2ludDQpIDwgMDsKICAgICAgICB9OwogICAgICAgIFNlZ21lbnQuX1gyX0tFWSA9ICJ4MiI7CiAgICAgICAgU2VnbWVudC5fWTJfS0VZID0gInkyIjsKICAgICAgICByZXR1cm4gU2VnbWVudDsKICAgIH0oeHlQbG90LlhZUGxvdCkpOwogICAgZXhwb3J0cy5TZWdtZW50ID0gU2VnbWVudDsKICAgIH0pOwoKICAgIHZhciBzdGFja2VkQXJlYVBsb3QgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCgoKCgoKCiAgICB2YXIgU3RhY2tlZEFyZWEgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhTdGFja2VkQXJlYSwgX3N1cGVyKTsKICAgICAgICAvKioKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBTdGFja2VkQXJlYSgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gX3N1cGVyLmNhbGwodGhpcykgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX3N0YWNraW5nUmVzdWx0ID0gbWVtb2l6ZS5tZW1UaHVuayhmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5kYXRhc2V0cygpOyB9LCBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy54KCkuYWNjZXNzb3I7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLnkoKS5hY2Nlc3NvcjsgfSwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX3N0YWNraW5nT3JkZXI7IH0sIGZ1bmN0aW9uIChkYXRhc2V0cywga2V5QWNjZXNzb3IsIHZhbHVlQWNjZXNzb3IsIHN0YWNraW5nT3JkZXIpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLlN0YWNraW5nLnN0YWNrKGRhdGFzZXRzLCBrZXlBY2Nlc3NvciwgdmFsdWVBY2Nlc3Nvciwgc3RhY2tpbmdPcmRlcik7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBfdGhpcy5fc3RhY2tlZEV4dGVudCA9IG1lbW9pemUubWVtVGh1bmsoX3RoaXMuX3N0YWNraW5nUmVzdWx0LCBmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy54KCkuYWNjZXNzb3I7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9maWx0ZXJGb3JQcm9wZXJ0eSgieSIpOyB9LCBmdW5jdGlvbiAoc3RhY2tpbmdSZXN1bHQsIGtleUFjY2Vzc29yLCBmaWx0ZXIpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLlN0YWNraW5nLnN0YWNrZWRFeHRlbnQoc3RhY2tpbmdSZXN1bHQsIGtleUFjY2Vzc29yLCBmaWx0ZXIpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgX3RoaXMuX2Jhc2VsaW5lVmFsdWUgPSAwOwogICAgICAgICAgICBfdGhpcy5fc3RhY2tpbmdPcmRlciA9ICJib3R0b211cCI7CiAgICAgICAgICAgIF90aGlzLmFkZENsYXNzKCJzdGFja2VkLWFyZWEtcGxvdCIpOwogICAgICAgICAgICBfdGhpcy5fYmFzZWxpbmVWYWx1ZVByb3ZpZGVyID0gZnVuY3Rpb24gKCkgeyByZXR1cm4gW190aGlzLl9iYXNlbGluZVZhbHVlXTsgfTsKICAgICAgICAgICAgX3RoaXMuY3JvcHBlZFJlbmRlcmluZ0VuYWJsZWQoZmFsc2UpOwogICAgICAgICAgICByZXR1cm4gX3RoaXM7CiAgICAgICAgfQogICAgICAgIFN0YWNrZWRBcmVhLnByb3RvdHlwZS5jcm9wcGVkUmVuZGVyaW5nRW5hYmxlZCA9IGZ1bmN0aW9uIChjcm9wcGVkUmVuZGVyaW5nKSB7CiAgICAgICAgICAgIGlmIChjcm9wcGVkUmVuZGVyaW5nID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLmNyb3BwZWRSZW5kZXJpbmdFbmFibGVkLmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGNyb3BwZWRSZW5kZXJpbmcpIHsKICAgICAgICAgICAgICAgIC8vIEhBQ0tIQUNLICMzMDMyOiBjcm9wcGVkIHJlbmRlcmluZyBkb2Vzbid0IGN1cnJlbnRseSB3b3JrIGNvcnJlY3RseSBvbiBTdGFja2VkQXJlYQogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cud2FybigiV2FybmluZzogU3RhY2tlZCBBcmVhIFBsb3QgZG9lcyBub3Qgc3VwcG9ydCBjcm9wcGVkIHJlbmRlcmluZy4iKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLmNyb3BwZWRSZW5kZXJpbmdFbmFibGVkLmNhbGwodGhpcywgY3JvcHBlZFJlbmRlcmluZyk7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX2dldEFuaW1hdG9yID0gZnVuY3Rpb24gKGtleSkgewogICAgICAgICAgICByZXR1cm4gbmV3IGFuaW1hdG9ycy5OdWxsKCk7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX3NldHVwID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9zZXR1cC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9iYXNlbGluZSA9IHRoaXMuX3JlbmRlckFyZWEuYXBwZW5kKCJsaW5lIikuY2xhc3NlZCgiYmFzZWxpbmUiLCB0cnVlKTsKICAgICAgICB9OwogICAgICAgIFN0YWNrZWRBcmVhLnByb3RvdHlwZS54ID0gZnVuY3Rpb24gKHgsIHhTY2FsZSkgewogICAgICAgICAgICBpZiAoeCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS54LmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHhTY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLnguY2FsbCh0aGlzLCB4KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueC5jYWxsKHRoaXMsIHgsIHhTY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fY2hlY2tTYW1lRG9tYWluKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEFyZWEucHJvdG90eXBlLnkgPSBmdW5jdGlvbiAoeSwgeVNjYWxlKSB7CiAgICAgICAgICAgIGlmICh5ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLnkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoeVNjYWxlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUueS5jYWxsKHRoaXMsIHkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgX3N1cGVyLnByb3RvdHlwZS55LmNhbGwodGhpcywgeSwgeVNjYWxlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9jaGVja1NhbWVEb21haW4oKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICAvKioKICAgICAgICAgKiBHZXRzIHRoZSBvZmZzZXQgb2YgdGhlIHkgdmFsdWUgY29ycmVzcG9uZGluZyB0byBhbiB4IHZhbHVlIG9mIGEgZ2l2ZW4gZGF0YXNldC4gVGhpcyBhbGxvd3Mgb3RoZXIgcGxvdHMgdG8gcGxvdAogICAgICAgICAqIHBvaW50cyBjb3JyZXNwb25kaW5nIHRvIHRoZWlyIHN0YWNrZWQgdmFsdWUgaW4gdGhlIGdyYXBoLgogICAgICAgICAqIEBwYXJhbSBkYXRhc2V0IFRoZSBkYXRhc2V0IGZyb20gd2hpY2ggdG8gcmV0cmlldmUgdGhlIHkgdmFsdWUgb2Zmc2V0CiAgICAgICAgICogQHBhcmFtIHggVGhlIHggdmFsdWUgY29ycmVzcG9uZGluZyB0byB0aGUgeS12YWx1ZSBvZiBpbnRlcmVzdC4KICAgICAgICAgKi8KICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUueU9mZnNldCA9IGZ1bmN0aW9uIChkYXRhc2V0LCB4KSB7CiAgICAgICAgICAgIHZhciBzdGFja2luZ1Jlc3VsdCA9IHRoaXMuX3N0YWNraW5nUmVzdWx0KCk7CiAgICAgICAgICAgIGlmIChzdGFja2luZ1Jlc3VsdCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBkYXRhc2V0U3RhY2tpbmdSZXN1bHQgPSBzdGFja2luZ1Jlc3VsdC5nZXQoZGF0YXNldCk7CiAgICAgICAgICAgIGlmIChkYXRhc2V0U3RhY2tpbmdSZXN1bHQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgcmVzdWx0ID0gZGF0YXNldFN0YWNraW5nUmVzdWx0LmdldChTdHJpbmcoeCkpOwogICAgICAgICAgICBpZiAocmVzdWx0ID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1bmRlZmluZWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHJlc3VsdC5vZmZzZXQ7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuc3RhY2tpbmdPcmRlciA9IGZ1bmN0aW9uIChzdGFja2luZ09yZGVyKSB7CiAgICAgICAgICAgIGlmIChzdGFja2luZ09yZGVyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9zdGFja2luZ09yZGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3N0YWNraW5nT3JkZXIgPSBzdGFja2luZ09yZGVyOwogICAgICAgICAgICB0aGlzLl9vbkRhdGFzZXRVcGRhdGUoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuZG93bnNhbXBsaW5nRW5hYmxlZCA9IGZ1bmN0aW9uIChkb3duc2FtcGxpbmcpIHsKICAgICAgICAgICAgaWYgKGRvd25zYW1wbGluZyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5kb3duc2FtcGxpbmdFbmFibGVkLmNhbGwodGhpcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cud2FybigiV2FybmluZzogU3RhY2tlZCBBcmVhIFBsb3QgZG9lcyBub3Qgc3VwcG9ydCBkb3duc2FtcGxpbmciKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX2FkZGl0aW9uYWxQYWludCA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHNjYWxlZEJhc2VsaW5lID0gdGhpcy55KCkuc2NhbGUuc2NhbGUodGhpcy5fYmFzZWxpbmVWYWx1ZSk7CiAgICAgICAgICAgIHZhciBiYXNlbGluZUF0dHIgPSB7CiAgICAgICAgICAgICAgICB4MTogMCwKICAgICAgICAgICAgICAgIHkxOiBzY2FsZWRCYXNlbGluZSwKICAgICAgICAgICAgICAgIHgyOiB0aGlzLndpZHRoKCksCiAgICAgICAgICAgICAgICB5Mjogc2NhbGVkQmFzZWxpbmUsCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX2dldEFuaW1hdG9yKCJiYXNlbGluZSIpLmFuaW1hdGUodGhpcy5fYmFzZWxpbmUsIGJhc2VsaW5lQXR0cik7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX3VwZGF0ZVlTY2FsZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIHlCaW5kaW5nID0gdGhpcy55KCk7CiAgICAgICAgICAgIHZhciBzY2FsZSA9ICh5QmluZGluZyAmJiB5QmluZGluZy5zY2FsZSk7CiAgICAgICAgICAgIGlmIChzY2FsZSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc2NhbGUuYWRkUGFkZGluZ0V4Y2VwdGlvbnNQcm92aWRlcih0aGlzLl9iYXNlbGluZVZhbHVlUHJvdmlkZXIpOwogICAgICAgICAgICBzY2FsZS5hZGRJbmNsdWRlZFZhbHVlc1Byb3ZpZGVyKHRoaXMuX2Jhc2VsaW5lVmFsdWVQcm92aWRlcik7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX29uRGF0YXNldFVwZGF0ZSA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdGhpcy5fY2hlY2tTYW1lRG9tYWluKCk7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX29uRGF0YXNldFVwZGF0ZS5jYWxsKHRoaXMpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFN0YWNrZWRBcmVhLnByb3RvdHlwZS5nZXRFeHRlbnRzRm9yUHJvcGVydHkgPSBmdW5jdGlvbiAoYXR0cikgewogICAgICAgICAgICB2YXIgcHJpbWFyeUF0dHIgPSAieSI7CiAgICAgICAgICAgIGlmIChhdHRyID09PSBwcmltYXJ5QXR0cikgewogICAgICAgICAgICAgICAgcmV0dXJuIFt0aGlzLl9zdGFja2VkRXh0ZW50KCldOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIF9zdXBlci5wcm90b3R5cGUuZ2V0RXh0ZW50c0ZvclByb3BlcnR5LmNhbGwodGhpcywgYXR0cik7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFN0YWNrZWRBcmVhLnByb3RvdHlwZS5fY2hlY2tTYW1lRG9tYWluID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX3Byb2plY3RvcnNSZWFkeSgpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGRhdGFzZXRzID0gdGhpcy5kYXRhc2V0cygpOwogICAgICAgICAgICB2YXIga2V5QWNjZXNzb3IgPSB0aGlzLngoKS5hY2Nlc3NvcjsKICAgICAgICAgICAgdmFyIGtleVNldHMgPSBkYXRhc2V0cy5tYXAoZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkMy5zZXQoZGF0YXNldC5kYXRhKCkubWFwKGZ1bmN0aW9uIChkYXR1bSwgaSkgeyByZXR1cm4gdXRpbHMkMS5TdGFja2luZy5ub3JtYWxpemVLZXkoa2V5QWNjZXNzb3IoZGF0dW0sIGksIGRhdGFzZXQpKTsgfSkpLnZhbHVlcygpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIGRvbWFpbktleXMgPSBTdGFja2VkQXJlYS5fZG9tYWluS2V5cyhkYXRhc2V0cywga2V5QWNjZXNzb3IpOwogICAgICAgICAgICBpZiAoa2V5U2V0cy5zb21lKGZ1bmN0aW9uIChrZXlTZXQpIHsgcmV0dXJuIGtleVNldC5sZW5ndGggIT09IGRvbWFpbktleXMubGVuZ3RoOyB9KSkgewogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cud2FybigidGhlIGRvbWFpbnMgYWNyb3NzIHRoZSBkYXRhc2V0cyBhcmUgbm90IHRoZSBzYW1lLiBQbG90IG1heSBwcm9kdWNlIHVuaW50ZW5kZWQgYmVoYXZpb3IuIik7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIC8qKgogICAgICAgICAqIEdpdmVuIGFuIGFycmF5IG9mIERhdGFzZXRzIGFuZCB0aGUgYWNjZXNzb3IgZnVuY3Rpb24gZm9yIHRoZSBrZXksIGNvbXB1dGVzIHRoZQogICAgICAgICAqIHNldCByZXVuaW9uIChubyBkdXBsaWNhdGVzKSBvZiB0aGUgZG9tYWluIG9mIGVhY2ggRGF0YXNldC4gVGhlIGtleXMgYXJlIHN0cmluZ2lmaWVkCiAgICAgICAgICogYmVmb3JlIGJlaW5nIHJldHVybmVkLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIHtEYXRhc2V0W119IGRhdGFzZXRzIFRoZSBEYXRhc2V0cyBmb3Igd2hpY2ggd2UgZXh0cmFjdCB0aGUgZG9tYWluIGtleXMKICAgICAgICAgKiBAcGFyYW0ge0FjY2Vzc29yPGFueT59IGtleUFjY2Vzc29yIFRoZSBhY2Nlc3NvciBmb3IgdGhlIGtleSBvZiB0aGUgZGF0YQogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ1tdfSBBbiBhcnJheSBvZiBzdHJpbmdpZmllZCBrZXlzCiAgICAgICAgICovCiAgICAgICAgU3RhY2tlZEFyZWEuX2RvbWFpbktleXMgPSBmdW5jdGlvbiAoZGF0YXNldHMsIGtleUFjY2Vzc29yKSB7CiAgICAgICAgICAgIHZhciBkb21haW5LZXlzID0gZDMuc2V0KCk7CiAgICAgICAgICAgIGRhdGFzZXRzLmZvckVhY2goZnVuY3Rpb24gKGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YXNldC5kYXRhKCk7CiAgICAgICAgICAgICAgICB2YXIgZGF0YUxlbiA9IGRhdGEubGVuZ3RoOwogICAgICAgICAgICAgICAgZm9yICh2YXIgaW5kZXggPSAwOyBpbmRleCA8IGRhdGFMZW47IGluZGV4KyspIHsKICAgICAgICAgICAgICAgICAgICB2YXIgZGF0dW0gPSBkYXRhW2luZGV4XTsKICAgICAgICAgICAgICAgICAgICBkb21haW5LZXlzLmFkZChrZXlBY2Nlc3NvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBkb21haW5LZXlzLnZhbHVlcygpOwogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEFyZWEucHJvdG90eXBlLl9jb29yZGluYXRlUHJvamVjdG9ycyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIHhQcm9qZWN0b3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMueCgpKTsKICAgICAgICAgICAgdmFyIHlBY2Nlc3NvciA9IHRoaXMueSgpLmFjY2Vzc29yOwogICAgICAgICAgICB2YXIgeEFjY2Vzc29yID0gdGhpcy54KCkuYWNjZXNzb3I7CiAgICAgICAgICAgIHZhciBub3JtYWxpemVkWEFjY2Vzc29yID0gZnVuY3Rpb24gKGRhdHVtLCBpbmRleCwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHV0aWxzJDEuU3RhY2tpbmcubm9ybWFsaXplS2V5KHhBY2Nlc3NvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIHN0YWNraW5nUmVzdWx0ID0gdGhpcy5fc3RhY2tpbmdSZXN1bHQoKTsKICAgICAgICAgICAgdmFyIHN0YWNrWVByb2plY3RvciA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgeSA9ICt5QWNjZXNzb3IoZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgb2Zmc2V0ID0gc3RhY2tpbmdSZXN1bHQuZ2V0KGRhdGFzZXQpLmdldChub3JtYWxpemVkWEFjY2Vzc29yKGQsIGksIGRhdGFzZXQpKS5vZmZzZXQ7CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMueSgpLnNjYWxlLnNjYWxlKHkgKyBvZmZzZXQpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgc3RhY2tZMFByb2plY3RvciA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgb2Zmc2V0ID0gc3RhY2tpbmdSZXN1bHQuZ2V0KGRhdGFzZXQpLmdldChub3JtYWxpemVkWEFjY2Vzc29yKGQsIGksIGRhdGFzZXQpKS5vZmZzZXQ7CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMueSgpLnNjYWxlLnNjYWxlKG9mZnNldCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHJldHVybiBbCiAgICAgICAgICAgICAgICB4UHJvamVjdG9yLAogICAgICAgICAgICAgICAgc3RhY2tZUHJvamVjdG9yLAogICAgICAgICAgICAgICAgc3RhY2tZMFByb2plY3RvciwKICAgICAgICAgICAgXTsKICAgICAgICB9OwogICAgICAgIFN0YWNrZWRBcmVhLnByb3RvdHlwZS5fcHJvcGVydHlQcm9qZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgcHJvcGVydHlUb1Byb2plY3RvcnMgPSBfc3VwZXIucHJvdG90eXBlLl9wcm9wZXJ0eVByb2plY3RvcnMuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdmFyIF9hID0gdGhpcy5fY29vcmRpbmF0ZVByb2plY3RvcnMoKSwgeFByb2plY3RvciA9IF9hWzBdLCBzdGFja1lQcm9qZWN0b3IgPSBfYVsxXSwgc3RhY2tZMFByb2plY3RvciA9IF9hWzJdOwogICAgICAgICAgICBwcm9wZXJ0eVRvUHJvamVjdG9yc1siZCJdID0gdGhpcy5fY29uc3RydWN0QXJlYVByb2plY3Rvcih4UHJvamVjdG9yLCBzdGFja1lQcm9qZWN0b3IsIHN0YWNrWTBQcm9qZWN0b3IpOwogICAgICAgICAgICByZXR1cm4gcHJvcGVydHlUb1Byb2plY3RvcnM7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQXJlYS5wcm90b3R5cGUuX3BpeGVsUG9pbnQgPSBmdW5jdGlvbiAoZGF0dW0sIGluZGV4LCBkYXRhc2V0KSB7CiAgICAgICAgICAgIHZhciBwaXhlbFBvaW50ID0gX3N1cGVyLnByb3RvdHlwZS5fcGl4ZWxQb2ludC5jYWxsKHRoaXMsIGRhdHVtLCBpbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgIHZhciB4VmFsdWUgPSB0aGlzLngoKS5hY2Nlc3NvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICB2YXIgeVZhbHVlID0gdGhpcy55KCkuYWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgdmFyIHNjYWxlZFlWYWx1ZSA9IHRoaXMueSgpLnNjYWxlLnNjYWxlKCt5VmFsdWUgKyB0aGlzLl9zdGFja2luZ1Jlc3VsdCgpLmdldChkYXRhc2V0KS5nZXQodXRpbHMkMS5TdGFja2luZy5ub3JtYWxpemVLZXkoeFZhbHVlKSkub2Zmc2V0KTsKICAgICAgICAgICAgcmV0dXJuIHsgeDogcGl4ZWxQb2ludC54LCB5OiBzY2FsZWRZVmFsdWUgfTsKICAgICAgICB9OwogICAgICAgIHJldHVybiBTdGFja2VkQXJlYTsKICAgIH0oYXJlYVBsb3QuQXJlYSkpOwogICAgZXhwb3J0cy5TdGFja2VkQXJlYSA9IFN0YWNrZWRBcmVhOwogICAgfSk7CgogICAgdmFyIHN0YWNrZWRCYXJQbG90ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgoKCgogICAgdmFyIFN0YWNrZWRCYXIgPSAvKiogQGNsYXNzICovIChmdW5jdGlvbiAoX3N1cGVyKSB7CiAgICAgICAgdHNsaWJfZXM2Ll9fZXh0ZW5kcyhTdGFja2VkQmFyLCBfc3VwZXIpOwogICAgICAgIC8qKgogICAgICAgICAqIEEgU3RhY2tlZEJhciBQbG90IHN0YWNrcyBiYXJzIGFjcm9zcyBEYXRhc2V0cyBiYXNlZCBvbiB0aGUgcHJpbWFyeSB2YWx1ZSBvZiB0aGUgYmFycy4KICAgICAgICAgKiAgIE9uIGEgdmVydGljYWwgU3RhY2tlZEJhciBQbG90LCB0aGUgYmFycyB3aXRoIHRoZSBzYW1lIFggdmFsdWUgYXJlIHN0YWNrZWQuCiAgICAgICAgICogICBPbiBhIGhvcml6b250YWwgU3RhY2tlZEJhciBQbG90LCB0aGUgYmFycyB3aXRoIHRoZSBzYW1lIFkgdmFsdWUgYXJlIHN0YWNrZWQuCiAgICAgICAgICoKICAgICAgICAgKiBAY29uc3RydWN0b3IKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlfSB4U2NhbGUKICAgICAgICAgKiBAcGFyYW0ge1NjYWxlfSB5U2NhbGUKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gW29yaWVudGF0aW9uPSJ2ZXJ0aWNhbCJdIE9uZSBvZiAidmVydGljYWwiLyJob3Jpem9udGFsIi4KICAgICAgICAgKi8KICAgICAgICBmdW5jdGlvbiBTdGFja2VkQmFyKG9yaWVudGF0aW9uKSB7CiAgICAgICAgICAgIGlmIChvcmllbnRhdGlvbiA9PT0gdm9pZCAwKSB7IG9yaWVudGF0aW9uID0gInZlcnRpY2FsIjsgfQogICAgICAgICAgICB2YXIgX3RoaXMgPSBfc3VwZXIuY2FsbCh0aGlzLCBvcmllbnRhdGlvbikgfHwgdGhpczsKICAgICAgICAgICAgX3RoaXMuX2V4dHJlbWFGb3JtYXR0ZXIgPSBmb3JtYXR0ZXJzLmlkZW50aXR5KCk7CiAgICAgICAgICAgIF90aGlzLl9zdGFja2luZ1Jlc3VsdCA9IG1lbW9pemUubWVtVGh1bmsoZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuZGF0YXNldHMoKTsgfSwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMucG9zaXRpb24oKS5hY2Nlc3NvcjsgfSwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMubGVuZ3RoKCkuYWNjZXNzb3I7IH0sIGZ1bmN0aW9uICgpIHsgcmV0dXJuIF90aGlzLl9zdGFja2luZ09yZGVyOyB9LCBmdW5jdGlvbiAoZGF0YXNldHMsIHBvc2l0aW9uQWNjZXNzb3IsIGxlbmd0aEFjY2Vzc29yLCBzdGFja2luZ09yZGVyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdXRpbHMkMS5TdGFja2luZy5zdGFjayhkYXRhc2V0cywgcG9zaXRpb25BY2Nlc3NvciwgbGVuZ3RoQWNjZXNzb3IsIHN0YWNraW5nT3JkZXIpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgX3RoaXMuX3N0YWNrZWRFeHRlbnQgPSBtZW1vaXplLm1lbVRodW5rKF90aGlzLl9zdGFja2luZ1Jlc3VsdCwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMucG9zaXRpb24oKS5hY2Nlc3NvcjsgfSwgZnVuY3Rpb24gKCkgeyByZXR1cm4gX3RoaXMuX2ZpbHRlckZvclByb3BlcnR5KF90aGlzLl9pc1ZlcnRpY2FsID8gInkiIDogIngiKTsgfSwgZnVuY3Rpb24gKHN0YWNraW5nUmVzdWx0LCBwb3NpdGlvbkFjY2Vzc29yLCBmaWx0ZXIpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLlN0YWNraW5nLnN0YWNrZWRFeHRlbnQoc3RhY2tpbmdSZXN1bHQsIHBvc2l0aW9uQWNjZXNzb3IsIGZpbHRlcik7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygic3RhY2tlZC1iYXItcGxvdCIpOwogICAgICAgICAgICBfdGhpcy5fc3RhY2tpbmdPcmRlciA9ICJib3R0b211cCI7CiAgICAgICAgICAgIHJldHVybiBfdGhpczsKICAgICAgICB9CiAgICAgICAgU3RhY2tlZEJhci5wcm90b3R5cGUuc3RhY2tpbmdPcmRlciA9IGZ1bmN0aW9uIChzdGFja2luZ09yZGVyKSB7CiAgICAgICAgICAgIGlmIChzdGFja2luZ09yZGVyID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9zdGFja2luZ09yZGVyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3N0YWNraW5nT3JkZXIgPSBzdGFja2luZ09yZGVyOwogICAgICAgICAgICB0aGlzLl9vbkRhdGFzZXRVcGRhdGUoKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQmFyLnByb3RvdHlwZS5leHRyZW1hRm9ybWF0dGVyID0gZnVuY3Rpb24gKGZvcm1hdHRlcikgewogICAgICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2V4dHJlbWFGb3JtYXR0ZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9leHRyZW1hRm9ybWF0dGVyID0gZm9ybWF0dGVyOwogICAgICAgICAgICAgICAgdGhpcy5yZW5kZXIoKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQmFyLnByb3RvdHlwZS5fc2V0dXAgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX3NldHVwLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2xhYmVsQXJlYSA9IHRoaXMuX3JlbmRlckFyZWEuYXBwZW5kKCJnIikuY2xhc3NlZChiYXJQbG90LkJhci5fTEFCRUxfQVJFQV9DTEFTUywgdHJ1ZSk7CiAgICAgICAgICAgIHZhciBjb250ZXh0ID0gbmV3IHNyYyQxLlN2Z0NvbnRleHQodGhpcy5fbGFiZWxBcmVhLm5vZGUoKSk7CiAgICAgICAgICAgIHRoaXMuX21lYXN1cmVyID0gbmV3IHNyYyQxLkNhY2hlTWVhc3VyZXIoY29udGV4dCk7CiAgICAgICAgICAgIHRoaXMuX3dyaXRlciA9IG5ldyBzcmMkMS5Xcml0ZXIodGhpcy5fbWVhc3VyZXIsIGNvbnRleHQpOwogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEJhci5wcm90b3R5cGUuX2RyYXdMYWJlbHMgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIF9zdXBlci5wcm90b3R5cGUuX2RyYXdMYWJlbHMuY2FsbCh0aGlzKTsKICAgICAgICAgICAgLy8gcmVtb3ZlIGFsbCBjdXJyZW50IGxhYmVscyBiZWZvcmUgcmVkcmF3aW5nCiAgICAgICAgICAgIHRoaXMuX2xhYmVsQXJlYS5zZWxlY3RBbGwoImciKS5yZW1vdmUoKTsKICAgICAgICAgICAgdmFyIGJhc2VsaW5lVmFsdWUgPSArdGhpcy5iYXNlbGluZVZhbHVlKCk7CiAgICAgICAgICAgIHZhciBwb3NpdGlvblNjYWxlID0gdGhpcy5wb3NpdGlvbigpLnNjYWxlOwogICAgICAgICAgICB2YXIgbGVuZ3RoU2NhbGUgPSB0aGlzLmxlbmd0aCgpLnNjYWxlOwogICAgICAgICAgICB2YXIgX2EgPSB1dGlscyQxLlN0YWNraW5nLnN0YWNrZWRFeHRlbnRzKHRoaXMuX3N0YWNraW5nUmVzdWx0KCkpLCBtYXhpbXVtRXh0ZW50cyA9IF9hLm1heGltdW1FeHRlbnRzLCBtaW5pbXVtRXh0ZW50cyA9IF9hLm1pbmltdW1FeHRlbnRzOwogICAgICAgICAgICB2YXIgYW55VG9vV2lkZSA9IFtdOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogVHJ5IGRyYXdpbmcgdGhlIHRleHQgYXQgdGhlIGNlbnRlciBvZiB0aGUgYm91bmRzLiBUaGlzIG1ldGhvZCBkb2VzIG5vdCBkcmF3CiAgICAgICAgICAgICAqIHRoZSB0ZXh0IGlmIHRoZSB0ZXh0IHdvdWxkIG92ZXJmbG93IG91dHNpZGUgb2YgdGhlIHBsb3QuCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIEBwYXJhbSB0ZXh0CiAgICAgICAgICAgICAqIEBwYXJhbSBib3VuZHMKICAgICAgICAgICAgICogQHJldHVybnMge2Jvb2xlYW59CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB2YXIgbWF5YmVEcmF3TGFiZWwgPSBmdW5jdGlvbiAodGV4dCwgYm91bmRzLCBiYXJUaGlja25lc3MpIHsKICAgICAgICAgICAgICAgIHZhciBfYSA9IGJvdW5kcy50b3BMZWZ0LCB4ID0gX2EueCwgeSA9IF9hLnk7CiAgICAgICAgICAgICAgICB2YXIgd2lkdGggPSBib3VuZHMuYm90dG9tUmlnaHQueCAtIGJvdW5kcy50b3BMZWZ0Lng7CiAgICAgICAgICAgICAgICB2YXIgaGVpZ2h0ID0gYm91bmRzLmJvdHRvbVJpZ2h0LnkgLSBib3VuZHMudG9wTGVmdC55OwogICAgICAgICAgICAgICAgdmFyIHRleHRUb29Mb25nID0gX3RoaXMuX2lzVmVydGljYWwKICAgICAgICAgICAgICAgICAgICA/IHdpZHRoID4gYmFyVGhpY2tuZXNzCiAgICAgICAgICAgICAgICAgICAgOiBoZWlnaHQgPiBiYXJUaGlja25lc3M7CiAgICAgICAgICAgICAgICBpZiAoIXRleHRUb29Mb25nKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGxhYmVsQ29udGFpbmVyID0gX3RoaXMuX2xhYmVsQXJlYS5hcHBlbmQoImciKS5hdHRyKCJ0cmFuc2Zvcm0iLCAidHJhbnNsYXRlKCIgKyB4ICsgIiwgIiArIHkgKyAiKSIpOwogICAgICAgICAgICAgICAgICAgIGxhYmVsQ29udGFpbmVyLmNsYXNzZWQoInN0YWNrZWQtYmFyLWxhYmVsIiwgdHJ1ZSk7CiAgICAgICAgICAgICAgICAgICAgdmFyIHdyaXRlT3B0aW9ucyA9IHsKICAgICAgICAgICAgICAgICAgICAgICAgeEFsaWduOiAiY2VudGVyIiwKICAgICAgICAgICAgICAgICAgICAgICAgeUFsaWduOiAiY2VudGVyIiwKICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgICAgIF90aGlzLl93cml0ZXIud3JpdGUodGV4dCwgd2lkdGgsIGhlaWdodCwgd3JpdGVPcHRpb25zLCBsYWJlbENvbnRhaW5lci5ub2RlKCkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIHRleHRUb29Mb25nOwogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgZHJhd0xhYmVsc0ZvckV4dGVudHMgPSBmdW5jdGlvbiAoc3RhY2tzLCBjb21wdXRlTGFiZWxUb3BMZWZ0KSB7CiAgICAgICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gX3RoaXMuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgICAgICB2YXIgcGxvdFdpZHRoID0gX3RoaXMud2lkdGgoKTsKICAgICAgICAgICAgICAgIHZhciBwbG90SGVpZ2h0ID0gX3RoaXMuaGVpZ2h0KCk7CiAgICAgICAgICAgICAgICBzdGFja3MuZm9yRWFjaChmdW5jdGlvbiAoc3RhY2spIHsKICAgICAgICAgICAgICAgICAgICBpZiAoc3RhY2suZXh0ZW50ICE9PSBiYXNlbGluZVZhbHVlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIG9ubHkgZHJhdyBzdW1zIGZvciB2YWx1ZXMgbm90IGF0IHRoZSBiYXNlbGluZQogICAgICAgICAgICAgICAgICAgICAgICB2YXIgdGV4dCA9IF90aGlzLmV4dHJlbWFGb3JtYXR0ZXIoKShzdGFjay5leHRlbnQpOwogICAgICAgICAgICAgICAgICAgICAgICB2YXIgdGV4dERpbWVuc2lvbnMgPSBfdGhpcy5fbWVhc3VyZXIubWVhc3VyZSh0ZXh0KTsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHN0YWNrZWREYXR1bSA9IHN0YWNrLnN0YWNrZWREYXR1bTsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIG9yaWdpbmFsRGF0dW0gPSBzdGFja2VkRGF0dW0ub3JpZ2luYWxEYXR1bSwgb3JpZ2luYWxJbmRleCA9IHN0YWNrZWREYXR1bS5vcmlnaW5hbEluZGV4LCBvcmlnaW5hbERhdGFzZXQgPSBzdGFja2VkRGF0dW0ub3JpZ2luYWxEYXRhc2V0OwogICAgICAgICAgICAgICAgICAgICAgICAvLyBvbmx5IGNvbnNpZGVyIHN0YWNrIGV4dGVudHMgdGhhdCBhcmUgb24gdGhlIHNjcmVlbgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoIV90aGlzLl9pc0RhdHVtT25TY3JlZW4oYXR0clRvUHJvamVjdG9yLCBwbG90V2lkdGgsIHBsb3RIZWlnaHQsIG9yaWdpbmFsRGF0dW0sIG9yaWdpbmFsSW5kZXgsIG9yaWdpbmFsRGF0YXNldCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICB2YXIgYmFyVGhpY2tuZXNzID0gcGxvdC5QbG90Ll9zY2FsZWRBY2Nlc3NvcihfdGhpcy5hdHRyKGJhclBsb3QuQmFyLl9CQVJfVEhJQ0tORVNTX0tFWSkpKG9yaWdpbmFsRGF0dW0sIG9yaWdpbmFsSW5kZXgsIG9yaWdpbmFsRGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8qCiAgICAgICAgICAgICAgICAgICAgICAgICAqIFRoZSBzdGFja0VkZ2UgaXMgYWxpZ25lZCBhdCB0aGUgZWRnZSBvZiB0aGUgc3RhY2sgaW4gdGhlIGxlbmd0aCBkaW1lbnNpb24sCiAgICAgICAgICAgICAgICAgICAgICAgICAqIGFuZCBpbiB0aGUgY2VudGVyIG9mIHRoZSBzdGFjayBpbiB0aGUgdGhpY2tuZXNzIGRpbWVuc2lvbi4KICAgICAgICAgICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBzdGFja0VkZ2VMZW5ndGggPSBsZW5ndGhTY2FsZS5zY2FsZShzdGFjay5leHRlbnQpOwogICAgICAgICAgICAgICAgICAgICAgICB2YXIgc3RhY2tDZW50ZXJQb3NpdGlvbiA9IF90aGlzLl9nZXRQb3NpdGlvbkF0dHIocG9zaXRpb25TY2FsZS5zY2FsZShzdGFjay5heGlzVmFsdWUpLCBiYXJUaGlja25lc3MpICsgYmFyVGhpY2tuZXNzIC8gMjsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHN0YWNrRWRnZSA9IF90aGlzLl9pc1ZlcnRpY2FsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICA/IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB4OiBzdGFja0NlbnRlclBvc2l0aW9uLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHk6IHN0YWNrRWRnZUxlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIDogewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHg6IHN0YWNrRWRnZUxlbmd0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB5OiBzdGFja0NlbnRlclBvc2l0aW9uLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHRvcExlZnQgPSBjb21wdXRlTGFiZWxUb3BMZWZ0KHN0YWNrRWRnZSwgdGV4dERpbWVuc2lvbnMsIGJhclRoaWNrbmVzcyk7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBpc1Rvb1dpZGUgPSBtYXliZURyYXdMYWJlbCh0ZXh0LCB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0b3BMZWZ0OiB0b3BMZWZ0LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgYm90dG9tUmlnaHQ6IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB4OiB0b3BMZWZ0LnggKyB0ZXh0RGltZW5zaW9ucy53aWR0aCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB5OiB0b3BMZWZ0LnkgKyB0ZXh0RGltZW5zaW9ucy5oZWlnaHQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICB9LCBiYXJUaGlja25lc3MpOwogICAgICAgICAgICAgICAgICAgICAgICBhbnlUb29XaWRlLnB1c2goaXNUb29XaWRlKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgZHJhd0xhYmVsc0ZvckV4dGVudHMobWF4aW11bUV4dGVudHMsIGZ1bmN0aW9uIChzdGFja0VkZ2UsIG1lYXN1cmVtZW50LCB0aGlja25lc3MpIHsKICAgICAgICAgICAgICAgIHZhciBwcmltYXJ5VGV4dE1lYXN1cmVtZW50ID0gX3RoaXMuX2lzVmVydGljYWwgPyBtZWFzdXJlbWVudC53aWR0aCA6IG1lYXN1cmVtZW50LmhlaWdodDsKICAgICAgICAgICAgICAgIHZhciBzZWNvbmRhcnlUZXh0TWVhc3VyZW1lbnQgPSBfdGhpcy5faXNWZXJ0aWNhbCA/IG1lYXN1cmVtZW50LmhlaWdodCA6IG1lYXN1cmVtZW50LndpZHRoOwogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICB4OiBfdGhpcy5faXNWZXJ0aWNhbAogICAgICAgICAgICAgICAgICAgICAgICA/IHN0YWNrRWRnZS54IC0gcHJpbWFyeVRleHRNZWFzdXJlbWVudCAvIDIKICAgICAgICAgICAgICAgICAgICAgICAgOiBzdGFja0VkZ2UueCArIFN0YWNrZWRCYXIuX0VYVFJFTUFfTEFCRUxfTUFSR0lOX0ZST01fQkFSLAogICAgICAgICAgICAgICAgICAgIHk6IF90aGlzLl9pc1ZlcnRpY2FsCiAgICAgICAgICAgICAgICAgICAgICAgID8gc3RhY2tFZGdlLnkgLSBzZWNvbmRhcnlUZXh0TWVhc3VyZW1lbnQKICAgICAgICAgICAgICAgICAgICAgICAgOiBzdGFja0VkZ2UueSAtIHByaW1hcnlUZXh0TWVhc3VyZW1lbnQgLyAyLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGRyYXdMYWJlbHNGb3JFeHRlbnRzKG1pbmltdW1FeHRlbnRzLCBmdW5jdGlvbiAoc3RhY2tFZGdlLCBtZWFzdXJlbWVudCwgdGhpY2tuZXNzKSB7CiAgICAgICAgICAgICAgICB2YXIgcHJpbWFyeVRleHRNZWFzdXJlbWVudCA9IF90aGlzLl9pc1ZlcnRpY2FsID8gbWVhc3VyZW1lbnQud2lkdGggOiBtZWFzdXJlbWVudC5oZWlnaHQ7CiAgICAgICAgICAgICAgICB2YXIgc2Vjb25kYXJ5VGV4dE1lYXN1cmVtZW50ID0gX3RoaXMuX2lzVmVydGljYWwgPyBtZWFzdXJlbWVudC5oZWlnaHQgOiBtZWFzdXJlbWVudC53aWR0aDsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgeDogX3RoaXMuX2lzVmVydGljYWwKICAgICAgICAgICAgICAgICAgICAgICAgPyBzdGFja0VkZ2UueCAtIHByaW1hcnlUZXh0TWVhc3VyZW1lbnQgLyAyCiAgICAgICAgICAgICAgICAgICAgICAgIDogc3RhY2tFZGdlLnggLSBzZWNvbmRhcnlUZXh0TWVhc3VyZW1lbnQsCiAgICAgICAgICAgICAgICAgICAgeTogX3RoaXMuX2lzVmVydGljYWwKICAgICAgICAgICAgICAgICAgICAgICAgPyBzdGFja0VkZ2UueSArIFN0YWNrZWRCYXIuX0VYVFJFTUFfTEFCRUxfTUFSR0lOX0ZST01fQkFSCiAgICAgICAgICAgICAgICAgICAgICAgIDogc3RhY2tFZGdlLnkgLSBwcmltYXJ5VGV4dE1lYXN1cmVtZW50IC8gMiwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBpZiAoYW55VG9vV2lkZS5zb21lKGZ1bmN0aW9uIChkKSB7IHJldHVybiBkOyB9KSkgewogICAgICAgICAgICAgICAgdGhpcy5fbGFiZWxBcmVhLnNlbGVjdEFsbCgiZyIpLnJlbW92ZSgpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBTdGFja2VkQmFyLnByb3RvdHlwZS5fZ2VuZXJhdGVBdHRyVG9Qcm9qZWN0b3IgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHZhciBhdHRyVG9Qcm9qZWN0b3IgPSBfc3VwZXIucHJvdG90eXBlLl9nZW5lcmF0ZUF0dHJUb1Byb2plY3Rvci5jYWxsKHRoaXMpOwogICAgICAgICAgICB2YXIgdmFsdWVBdHRyID0gdGhpcy5faXNWZXJ0aWNhbCA/ICJ5IiA6ICJ4IjsKICAgICAgICAgICAgdmFyIGxlbmd0aFNjYWxlID0gdGhpcy5sZW5ndGgoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIGxlbmd0aEFjY2Vzc29yID0gdGhpcy5sZW5ndGgoKS5hY2Nlc3NvcjsKICAgICAgICAgICAgdmFyIHBvc2l0aW9uQWNjZXNzb3IgPSB0aGlzLnBvc2l0aW9uKCkuYWNjZXNzb3I7CiAgICAgICAgICAgIHZhciBub3JtYWxpemVkUG9zaXRpb25BY2Nlc3NvciA9IGZ1bmN0aW9uIChkYXR1bSwgaW5kZXgsIGRhdGFzZXQpIHsKICAgICAgICAgICAgICAgIHJldHVybiB1dGlscyQxLlN0YWNraW5nLm5vcm1hbGl6ZUtleShwb3NpdGlvbkFjY2Vzc29yKGRhdHVtLCBpbmRleCwgZGF0YXNldCkpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB2YXIgc3RhY2tpbmdSZXN1bHQgPSB0aGlzLl9zdGFja2luZ1Jlc3VsdCgpOwogICAgICAgICAgICB2YXIgZ2V0U3RhcnQgPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGxlbmd0aFNjYWxlLnNjYWxlKHN0YWNraW5nUmVzdWx0LmdldChkYXRhc2V0KS5nZXQobm9ybWFsaXplZFBvc2l0aW9uQWNjZXNzb3IoZCwgaSwgZGF0YXNldCkpLm9mZnNldCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBnZXRFbmQgPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGxlbmd0aFNjYWxlLnNjYWxlKCtsZW5ndGhBY2Nlc3NvcihkLCBpLCBkYXRhc2V0KSArCiAgICAgICAgICAgICAgICAgICAgc3RhY2tpbmdSZXN1bHQuZ2V0KGRhdGFzZXQpLmdldChub3JtYWxpemVkUG9zaXRpb25BY2Nlc3NvcihkLCBpLCBkYXRhc2V0KSkub2Zmc2V0KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIGhlaWdodEYgPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgcmV0dXJuIE1hdGguYWJzKGdldEVuZChkLCBpLCBkYXRhc2V0KSAtIGdldFN0YXJ0KGQsIGksIGRhdGFzZXQpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yW3RoaXMuX2lzVmVydGljYWwgPyAiaGVpZ2h0IiA6ICJ3aWR0aCJdID0gaGVpZ2h0RjsKICAgICAgICAgICAgdmFyIGF0dHJGdW5jdGlvbiA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gK2xlbmd0aEFjY2Vzc29yKGQsIGksIGRhdGFzZXQpIDwgMCA/IGdldFN0YXJ0KGQsIGksIGRhdGFzZXQpIDogZ2V0RW5kKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB9OwogICAgICAgICAgICBhdHRyVG9Qcm9qZWN0b3JbdmFsdWVBdHRyXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3RoaXMuX2lzVmVydGljYWwgPyBhdHRyRnVuY3Rpb24oZCwgaSwgZGF0YXNldCkgOiBhdHRyRnVuY3Rpb24oZCwgaSwgZGF0YXNldCkgLSBoZWlnaHRGKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICB9OwogICAgICAgICAgICByZXR1cm4gYXR0clRvUHJvamVjdG9yOwogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEJhci5wcm90b3R5cGUuZ2V0RXh0ZW50c0ZvclByb3BlcnR5ID0gZnVuY3Rpb24gKGF0dHIpIHsKICAgICAgICAgICAgdmFyIHByaW1hcnlBdHRyID0gdGhpcy5faXNWZXJ0aWNhbCA/ICJ5IiA6ICJ4IjsKICAgICAgICAgICAgaWYgKGF0dHIgPT09IHByaW1hcnlBdHRyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW3RoaXMuX3N0YWNrZWRFeHRlbnQoKV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX3N1cGVyLnByb3RvdHlwZS5nZXRFeHRlbnRzRm9yUHJvcGVydHkuY2FsbCh0aGlzLCBhdHRyKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEJhci5wcm90b3R5cGUuaW52YWxpZGF0ZUNhY2hlID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLmludmFsaWRhdGVDYWNoZS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9tZWFzdXJlci5yZXNldCgpOwogICAgICAgIH07CiAgICAgICAgU3RhY2tlZEJhci5fRVhUUkVNQV9MQUJFTF9NQVJHSU5fRlJPTV9CQVIgPSA1OwogICAgICAgIHJldHVybiBTdGFja2VkQmFyOwogICAgfShiYXJQbG90LkJhcikpOwogICAgZXhwb3J0cy5TdGFja2VkQmFyID0gU3RhY2tlZEJhcjsKICAgIH0pOwoKICAgIHZhciB3YXRlcmZhbGxQbG90ID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqCiAgICAgKiBDb3B5cmlnaHQgMjAxNC1wcmVzZW50IFBhbGFudGlyIFRlY2hub2xvZ2llcwogICAgICogQGxpY2Vuc2UgTUlUCiAgICAgKi8KICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShleHBvcnRzLCAiX19lc01vZHVsZSIsIHsgdmFsdWU6IHRydWUgfSk7CgoKCgogICAgdmFyIFdhdGVyZmFsbCA9IC8qKiBAY2xhc3MgKi8gKGZ1bmN0aW9uIChfc3VwZXIpIHsKICAgICAgICB0c2xpYl9lczYuX19leHRlbmRzKFdhdGVyZmFsbCwgX3N1cGVyKTsKICAgICAgICBmdW5jdGlvbiBXYXRlcmZhbGwoKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IF9zdXBlci5jYWxsKHRoaXMpIHx8IHRoaXM7CiAgICAgICAgICAgIF90aGlzLl9jb25uZWN0b3JzRW5hYmxlZCA9IGZhbHNlOwogICAgICAgICAgICBfdGhpcy5hZGRDbGFzcygid2F0ZXJmYWxsLXBsb3QiKTsKICAgICAgICAgICAgcmV0dXJuIF90aGlzOwogICAgICAgIH0KICAgICAgICBXYXRlcmZhbGwucHJvdG90eXBlLmNvbm5lY3RvcnNFbmFibGVkID0gZnVuY3Rpb24gKGVuYWJsZWQpIHsKICAgICAgICAgICAgaWYgKGVuYWJsZWQgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Nvbm5lY3RvcnNFbmFibGVkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2Nvbm5lY3RvcnNFbmFibGVkID0gZW5hYmxlZDsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBXYXRlcmZhbGwucHJvdG90eXBlLnRvdGFsID0gZnVuY3Rpb24gKHRvdGFsKSB7CiAgICAgICAgICAgIGlmICh0b3RhbCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fcHJvcGVydHlCaW5kaW5ncy5nZXQoV2F0ZXJmYWxsLl9UT1RBTF9LRVkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2JpbmRQcm9wZXJ0eShXYXRlcmZhbGwuX1RPVEFMX0tFWSwgdG90YWwsIG51bGwpOwogICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICB9OwogICAgICAgIFdhdGVyZmFsbC5wcm90b3R5cGUuX2FkZGl0aW9uYWxQYWludCA9IGZ1bmN0aW9uICh0aW1lKSB7CiAgICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIHRoaXMuX2Nvbm5lY3RvckFyZWEuc2VsZWN0QWxsKCJsaW5lIikucmVtb3ZlKCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9jb25uZWN0b3JzRW5hYmxlZCkgewogICAgICAgICAgICAgICAgdXRpbHMkMS5XaW5kb3cuc2V0VGltZW91dChmdW5jdGlvbiAoKSB7IHJldHVybiBfdGhpcy5fZHJhd0Nvbm5lY3RvcnMoKTsgfSwgdGltZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFdhdGVyZmFsbC5wcm90b3R5cGUuX2NyZWF0ZU5vZGVzRm9yRGF0YXNldCA9IGZ1bmN0aW9uIChkYXRhc2V0KSB7CiAgICAgICAgICAgIHZhciBkcmF3ZXIgPSBfc3VwZXIucHJvdG90eXBlLl9jcmVhdGVOb2Rlc0ZvckRhdGFzZXQuY2FsbCh0aGlzLCBkYXRhc2V0KTsKICAgICAgICAgICAgdGhpcy5fY29ubmVjdG9yQXJlYSA9IHRoaXMuX3JlbmRlckFyZWEuYXBwZW5kKCJnIikuY2xhc3NlZChXYXRlcmZhbGwuX0NPTk5FQ1RPUl9BUkVBX0NMQVNTLCB0cnVlKTsKICAgICAgICAgICAgcmV0dXJuIGRyYXdlcjsKICAgICAgICB9OwogICAgICAgIFdhdGVyZmFsbC5wcm90b3R5cGUuZ2V0RXh0ZW50c0ZvclByb3BlcnR5ID0gZnVuY3Rpb24gKGF0dHIpIHsKICAgICAgICAgICAgdmFyIHByaW1hcnlBdHRyID0gInkiOwogICAgICAgICAgICBpZiAoYXR0ciA9PT0gcHJpbWFyeUF0dHIpIHsKICAgICAgICAgICAgICAgIHJldHVybiBbdGhpcy5fZXh0ZW50XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBfc3VwZXIucHJvdG90eXBlLmdldEV4dGVudHNGb3JQcm9wZXJ0eS5jYWxsKHRoaXMsIGF0dHIpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBXYXRlcmZhbGwucHJvdG90eXBlLl9nZW5lcmF0ZUF0dHJUb1Byb2plY3RvciA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIF90aGlzID0gdGhpczsKICAgICAgICAgICAgdmFyIGF0dHJUb1Byb2plY3RvciA9IF9zdXBlci5wcm90b3R5cGUuX2dlbmVyYXRlQXR0clRvUHJvamVjdG9yLmNhbGwodGhpcyk7CiAgICAgICAgICAgIHZhciB5U2NhbGUgPSB0aGlzLnkoKS5zY2FsZTsKICAgICAgICAgICAgdmFyIHRvdGFsQWNjZXNzb3IgPSBwbG90LlBsb3QuX3NjYWxlZEFjY2Vzc29yKHRoaXMudG90YWwoKSk7CiAgICAgICAgICAgIHZhciB5QXR0ciA9IHRoaXMuYXR0cigieSIpOwogICAgICAgICAgICBpZiAoeUF0dHIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJ5Il0gPSBmdW5jdGlvbiAoZCwgaSwgZGF0YXNldCkgewogICAgICAgICAgICAgICAgICAgIHZhciBjdXJyZW50VmFsdWUgPSBfdGhpcy55KCkuYWNjZXNzb3IoZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGlzVG90YWwgPSB0b3RhbEFjY2Vzc29yKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIGlmIChpc1RvdGFsKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLm1pbih5U2NhbGUuc2NhbGUoY3VycmVudFZhbHVlKSwgeVNjYWxlLnNjYWxlKDApKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBjdXJyZW50U3VidG90YWwgPSBfdGhpcy5fc3VidG90YWxzW2ldOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaSA9PT0gMCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGN1cnJlbnRWYWx1ZSA8IDApIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geVNjYWxlLnNjYWxlKGN1cnJlbnRTdWJ0b3RhbCAtIGN1cnJlbnRWYWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4geVNjYWxlLnNjYWxlKGN1cnJlbnRTdWJ0b3RhbCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHByaW9yU3VidG90YWwgPSBfdGhpcy5fc3VidG90YWxzW2kgLSAxXTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGN1cnJlbnRTdWJ0b3RhbCA+IHByaW9yU3VidG90YWwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB5U2NhbGUuc2NhbGUoY3VycmVudFN1YnRvdGFsKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB5U2NhbGUuc2NhbGUocHJpb3JTdWJ0b3RhbCk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBoZWlnaHRBdHRyID0gdGhpcy5hdHRyKCJoZWlnaHQiKTsKICAgICAgICAgICAgaWYgKGhlaWdodEF0dHIgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgYXR0clRvUHJvamVjdG9yWyJoZWlnaHQiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGlzVG90YWwgPSB0b3RhbEFjY2Vzc29yKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIHZhciBjdXJyZW50VmFsdWUgPSBfdGhpcy55KCkuYWNjZXNzb3IoZCwgaSwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKGlzVG90YWwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIE1hdGguYWJzKHlTY2FsZS5zY2FsZShjdXJyZW50VmFsdWUpIC0geVNjYWxlLnNjYWxlKDApKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHZhciBjdXJyZW50U3VidG90YWwgPSBfdGhpcy5fc3VidG90YWxzW2ldOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAoaSA9PT0gMCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIE1hdGguYWJzKHlTY2FsZS5zY2FsZShjdXJyZW50U3VidG90YWwpIC0geVNjYWxlLnNjYWxlKGN1cnJlbnRTdWJ0b3RhbCAtIGN1cnJlbnRWYWx1ZSkpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgdmFyIHByaW9yU3VidG90YWwgPSBfdGhpcy5fc3VidG90YWxzW2kgLSAxXTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLmFicyh5U2NhbGUuc2NhbGUoY3VycmVudFN1YnRvdGFsKSAtIHlTY2FsZS5zY2FsZShwcmlvclN1YnRvdGFsKSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGF0dHJUb1Byb2plY3RvclsiY2xhc3MiXSA9IGZ1bmN0aW9uIChkLCBpLCBkYXRhc2V0KSB7CiAgICAgICAgICAgICAgICB2YXIgYmFzZUNsYXNzID0gIiI7CiAgICAgICAgICAgICAgICBpZiAoX3RoaXMuYXR0cigiY2xhc3MiKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgYmFzZUNsYXNzID0gX3RoaXMuYXR0cigiY2xhc3MiKS5hY2Nlc3NvcihkLCBpLCBkYXRhc2V0KSArICIgIjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHZhciBpc1RvdGFsID0gdG90YWxBY2Nlc3NvcihkLCBpLCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmIChpc1RvdGFsKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGJhc2VDbGFzcyArIFdhdGVyZmFsbC5fQkFSX1RPVEFMX0NMQVNTOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGRlbHRhID0gX3RoaXMueSgpLmFjY2Vzc29yKGQsIGksIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBiYXNlQ2xhc3MgKyAoZGVsdGEgPiAwID8gV2F0ZXJmYWxsLl9CQVJfR1JPV1RIX0NMQVNTIDogV2F0ZXJmYWxsLl9CQVJfREVDTElORV9DTEFTUyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHJldHVybiBhdHRyVG9Qcm9qZWN0b3I7CiAgICAgICAgfTsKICAgICAgICBXYXRlcmZhbGwucHJvdG90eXBlLl9vbkRhdGFzZXRVcGRhdGUgPSBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVN1YnRvdGFscygpOwogICAgICAgICAgICBfc3VwZXIucHJvdG90eXBlLl9vbkRhdGFzZXRVcGRhdGUuY2FsbCh0aGlzKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfTsKICAgICAgICBXYXRlcmZhbGwucHJvdG90eXBlLl9jYWxjdWxhdGVTdWJ0b3RhbHNBbmRFeHRlbnQgPSBmdW5jdGlvbiAoZGF0YXNldCkgewogICAgICAgICAgICB2YXIgbWluID0gTnVtYmVyLk1BWF9WQUxVRTsKICAgICAgICAgICAgdmFyIG1heCA9IE51bWJlci5NSU5fVkFMVUU7CiAgICAgICAgICAgIHZhciB0b3RhbCA9IDA7CiAgICAgICAgICAgIHZhciBoYXNTdGFydGVkID0gZmFsc2U7CiAgICAgICAgICAgIHZhciBkYXRhID0gZGF0YXNldC5kYXRhKCk7CiAgICAgICAgICAgIHZhciBkYXRhTGVuID0gZGF0YS5sZW5ndGg7CiAgICAgICAgICAgIGZvciAodmFyIGluZGV4ID0gMDsgaW5kZXggPCBkYXRhTGVuOyBpbmRleCsrKSB7CiAgICAgICAgICAgICAgICB2YXIgZGF0dW0gPSBkYXRhW2luZGV4XTsKICAgICAgICAgICAgICAgIHZhciBjdXJyZW50VmFsdWUgPSB0aGlzLnkoKS5hY2Nlc3NvcihkYXR1bSwgaW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIGlzVG90YWwgPSB0aGlzLnRvdGFsKCkuYWNjZXNzb3IoZGF0dW0sIGluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIGlmICghaXNUb3RhbCB8fCBpbmRleCA9PT0gMCkgewogICAgICAgICAgICAgICAgICAgIHRvdGFsICs9IGN1cnJlbnRWYWx1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3N1YnRvdGFscy5wdXNoKHRvdGFsKTsKICAgICAgICAgICAgICAgIGlmICh0b3RhbCA8IG1pbikgewogICAgICAgICAgICAgICAgICAgIG1pbiA9IHRvdGFsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKHRvdGFsID4gbWF4KSB7CiAgICAgICAgICAgICAgICAgICAgbWF4ID0gdG90YWw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoaXNUb3RhbCkgewogICAgICAgICAgICAgICAgICAgIGlmIChjdXJyZW50VmFsdWUgPCBtaW4pIHsKICAgICAgICAgICAgICAgICAgICAgICAgbWluID0gY3VycmVudFZhbHVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpZiAoY3VycmVudFZhbHVlID4gbWF4KSB7CiAgICAgICAgICAgICAgICAgICAgICAgIG1heCA9IGN1cnJlbnRWYWx1ZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoIWhhc1N0YXJ0ZWQgJiYgaXNUb3RhbCkgewogICAgICAgICAgICAgICAgICAgIHZhciBzdGFydFRvdGFsID0gY3VycmVudFZhbHVlIC0gdG90YWw7CiAgICAgICAgICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLl9zdWJ0b3RhbHMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fc3VidG90YWxzW2ldICs9IHN0YXJ0VG90YWw7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGhhc1N0YXJ0ZWQgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgIHRvdGFsICs9IHN0YXJ0VG90YWw7CiAgICAgICAgICAgICAgICAgICAgbWluICs9IHN0YXJ0VG90YWw7CiAgICAgICAgICAgICAgICAgICAgbWF4ICs9IHN0YXJ0VG90YWw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fZXh0ZW50ID0gW21pbiwgbWF4XTsKICAgICAgICB9OwogICAgICAgIFdhdGVyZmFsbC5wcm90b3R5cGUuX2RyYXdDb25uZWN0b3JzID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICB2YXIgYXR0clRvUHJvamVjdG9yID0gdGhpcy5fZ2V0QXR0clRvUHJvamVjdG9yKCk7CiAgICAgICAgICAgIHZhciBkYXRhc2V0ID0gdGhpcy5kYXRhc2V0cygpWzBdOwogICAgICAgICAgICBmb3IgKHZhciBkYXR1bUluZGV4ID0gMTsgZGF0dW1JbmRleCA8IGRhdGFzZXQuZGF0YSgpLmxlbmd0aDsgZGF0dW1JbmRleCsrKSB7CiAgICAgICAgICAgICAgICB2YXIgcHJldkluZGV4ID0gZGF0dW1JbmRleCAtIDE7CiAgICAgICAgICAgICAgICB2YXIgZGF0dW0gPSBkYXRhc2V0LmRhdGEoKVtkYXR1bUluZGV4XTsKICAgICAgICAgICAgICAgIHZhciBwcmV2RGF0dW0gPSBkYXRhc2V0LmRhdGEoKVtwcmV2SW5kZXhdOwogICAgICAgICAgICAgICAgdmFyIHggPSBhdHRyVG9Qcm9qZWN0b3JbIngiXShwcmV2RGF0dW0sIHByZXZJbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICB2YXIgeDIgPSBhdHRyVG9Qcm9qZWN0b3JbIngiXShkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCkgKyBhdHRyVG9Qcm9qZWN0b3JbIndpZHRoIl0oZGF0dW0sIGRhdHVtSW5kZXgsIGRhdGFzZXQpOwogICAgICAgICAgICAgICAgdmFyIHkgPSBhdHRyVG9Qcm9qZWN0b3JbInkiXShkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCk7CiAgICAgICAgICAgICAgICBpZiAoKHRoaXMuX3N1YnRvdGFsc1tkYXR1bUluZGV4XSA+IDAgJiYgdGhpcy5fc3VidG90YWxzW2RhdHVtSW5kZXhdID4gdGhpcy5fc3VidG90YWxzW3ByZXZJbmRleF0pIHx8CiAgICAgICAgICAgICAgICAgICAgKHRoaXMuX3N1YnRvdGFsc1tkYXR1bUluZGV4XSA8IDAgJiYgdGhpcy5fc3VidG90YWxzW2RhdHVtSW5kZXhdID49IHRoaXMuX3N1YnRvdGFsc1twcmV2SW5kZXhdKSkgewogICAgICAgICAgICAgICAgICAgIHkgPSBhdHRyVG9Qcm9qZWN0b3JbInkiXShkYXR1bSwgZGF0dW1JbmRleCwgZGF0YXNldCkgKyBhdHRyVG9Qcm9qZWN0b3JbImhlaWdodCJdKGRhdHVtLCBkYXR1bUluZGV4LCBkYXRhc2V0KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2Nvbm5lY3RvckFyZWEuYXBwZW5kKCJsaW5lIikuY2xhc3NlZChXYXRlcmZhbGwuX0NPTk5FQ1RPUl9DTEFTUywgdHJ1ZSkKICAgICAgICAgICAgICAgICAgICAuYXR0cigieDEiLCB4KS5hdHRyKCJ4MiIsIHgyKS5hdHRyKCJ5MSIsIHkpLmF0dHIoInkyIiwgeSk7CiAgICAgICAgICAgIH0KICAgICAgICB9OwogICAgICAgIFdhdGVyZmFsbC5wcm90b3R5cGUuX3VwZGF0ZVN1YnRvdGFscyA9IGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgdmFyIGRhdGFzZXRzID0gdGhpcy5kYXRhc2V0cygpOwogICAgICAgICAgICBpZiAoZGF0YXNldHMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgdmFyIGRhdGFzZXQgPSBkYXRhc2V0c1tkYXRhc2V0cy5sZW5ndGggLSAxXTsKICAgICAgICAgICAgICAgIHRoaXMuX3N1YnRvdGFscyA9IG5ldyBBcnJheSgpOwogICAgICAgICAgICAgICAgdGhpcy5fY2FsY3VsYXRlU3VidG90YWxzQW5kRXh0ZW50KGRhdGFzZXQpOwogICAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgICBXYXRlcmZhbGwuX0JBUl9ERUNMSU5FX0NMQVNTID0gIndhdGVyZmFsbC1kZWNsaW5lIjsKICAgICAgICBXYXRlcmZhbGwuX0JBUl9HUk9XVEhfQ0xBU1MgPSAid2F0ZXJmYWxsLWdyb3d0aCI7CiAgICAgICAgV2F0ZXJmYWxsLl9CQVJfVE9UQUxfQ0xBU1MgPSAid2F0ZXJmYWxsLXRvdGFsIjsKICAgICAgICBXYXRlcmZhbGwuX0NPTk5FQ1RPUl9DTEFTUyA9ICJjb25uZWN0b3IiOwogICAgICAgIFdhdGVyZmFsbC5fQ09OTkVDVE9SX0FSRUFfQ0xBU1MgPSAiY29ubmVjdG9yLWFyZWEiOwogICAgICAgIFdhdGVyZmFsbC5fVE9UQUxfS0VZID0gInRvdGFsIjsKICAgICAgICByZXR1cm4gV2F0ZXJmYWxsOwogICAgfShiYXJQbG90LkJhcikpOwogICAgZXhwb3J0cy5XYXRlcmZhbGwgPSBXYXRlcmZhbGw7CiAgICB9KTsKCiAgICB2YXIgcGxvdHMgPSBjcmVhdGVDb21tb25qc01vZHVsZShmdW5jdGlvbiAobW9kdWxlLCBleHBvcnRzKSB7CiAgICAvKioKICAgICAqIENvcHlyaWdodCAyMDE0LXByZXNlbnQgUGFsYW50aXIgVGVjaG5vbG9naWVzCiAgICAgKiBAbGljZW5zZSBNSVQKICAgICAqLwogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGFyZWFQbG90LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoYmFyUGxvdCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGNvbW1vbnMsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihjbHVzdGVyZWRCYXJQbG90LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIobGluZVBsb3QsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihwaWVQbG90LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIocmVjdGFuZ2xlUGxvdCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHNjYXR0ZXJQbG90LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoc2VnbWVudFBsb3QsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihzdGFja2VkQXJlYVBsb3QsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihzdGFja2VkQmFyUGxvdCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHdhdGVyZmFsbFBsb3QsIGV4cG9ydHMpOwogICAgfSk7CgogICAgdmFyIHZlcnNpb24kMyA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKgogICAgICogQ29weXJpZ2h0IDIwMTQtcHJlc2VudCBQYWxhbnRpciBUZWNobm9sb2dpZXMKICAgICAqIEBsaWNlbnNlIE1JVAogICAgICovCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoZXhwb3J0cywgIl9fZXNNb2R1bGUiLCB7IHZhbHVlOiB0cnVlIH0pOwogICAgLyoKICAgICAqIFdBUk5JTkc6IFRoZSBqcyBvdXRwdXQgb2YgdGhpcyBleHByZXNzaW9uIGlzIHNlYXJjaGVkIGJ5IHN0cmluZyAoeWVzLCBJIGtub3cpIGFuZCByZXBsYWNlZCB3aXRoIGEKICAgICAqIHJlYWwgdmVyc2lvbiBudW1iZXIgZHVyaW5nIHRoZSBkaXN0IHBoYXNlIGZvciBmb3IgbnBtIG1vZHVsZSBwdWJsaXNoaW5nLiBNb2RpZnlpbmcgdGhpcyBsaW5lIHNob3VsZAogICAgICogYmUgYWNjb21wYW5pZWQgYnkgbW9kaWZ5aW5nIHRoZSAic2VkLXZlcnNpb24iIHRhc2sgaW4gcGFja2FnZS5qc29uIGFjY29yZGluZ2x5LgogICAgICovCiAgICBleHBvcnRzLnZlcnNpb24gPSAiMy45LjAiOwogICAgfSk7CgogICAgdmFyIHNyYyQyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KGV4cG9ydHMsICJfX2VzTW9kdWxlIiwgeyB2YWx1ZTogdHJ1ZSB9KTsKCiAgICAvLyBIQUNLSEFDSyBkMy1zZWxlY3Rpb24tbXVsdGkgZG9lc24ndCBwbGF5IHdlbGwgd2l0aCBkZWZhdWx0ICJkMyIgcGFja2FnZSBpbiBhCiAgICAvLyBidW5kbGVyIGVudmlyb25tZW50IChlLmcuIHdlYnBhY2spIC0gc2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9kMy9kMy1zZWxlY3Rpb24tbXVsdGkvaXNzdWVzLzExCiAgICAvLyB3ZSBhZGQgaXQgbWFudWFsbHkgdG8gdGhlIGRlZmF1bHQgImQzIiBidW5kbGUKCgogICAgZXhwb3J0cy5BbmltYXRvcnMgPSBhbmltYXRvcnM7CgogICAgZXhwb3J0cy5BeGVzID0gYXhlczsKCiAgICBleHBvcnRzLkNvbXBvbmVudHMgPSBjb21wb25lbnRzOwoKICAgIGV4cG9ydHMuQ29uZmlncyA9IGNvbmZpZyQxOwoKICAgIGV4cG9ydHMuRm9ybWF0dGVycyA9IGZvcm1hdHRlcnM7CgogICAgZXhwb3J0cy5SZW5kZXJDb250cm9sbGVyID0gcmVuZGVyQ29udHJvbGxlcjsKCiAgICBleHBvcnRzLlJlbmRlclBvbGljaWVzID0gcmVuZGVyUG9saWN5OwoKICAgIGV4cG9ydHMuU3ltYm9sRmFjdG9yaWVzID0gc3ltYm9sRmFjdG9yaWVzOwoKICAgIGV4cG9ydHMuRGlzcGF0Y2hlcnMgPSBkaXNwYXRjaGVyczsKCiAgICBleHBvcnRzLkRyYXdlcnMgPSBkcmF3ZXJzOwoKICAgIGV4cG9ydHMuSW50ZXJhY3Rpb25zID0gaW50ZXJhY3Rpb25zOwoKICAgIGV4cG9ydHMuUGxvdHMgPSBwbG90czsKCiAgICBleHBvcnRzLlNjYWxlcyA9IHNjYWxlczsKCiAgICBleHBvcnRzLlV0aWxzID0gdXRpbHMkMTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoYXhpcyQyLCBleHBvcnRzKTsKCiAgICBleHBvcnRzLlRpbWVJbnRlcnZhbCA9IHRpbWVBeGlzLlRpbWVJbnRlcnZhbDsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoY29tcG9uZW50LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoY29tcG9uZW50Q29udGFpbmVyLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoZGF0YXNldCwgZXhwb3J0cyk7CgogICAgZXhwb3J0cy52ZXJzaW9uID0gdmVyc2lvbiQzLnZlcnNpb247CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGRpc3BhdGNoZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihkcmF3ZXIsIGV4cG9ydHMpOwogICAgdHNsaWJfZXM2Ll9fZXhwb3J0U3RhcihpbnRlcmFjdGlvbiwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKGtleUludGVyYWN0aW9uLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoeHlQbG90LCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIocGxvdCwgZXhwb3J0cyk7CiAgICB0c2xpYl9lczYuX19leHBvcnRTdGFyKHF1YW50aXRhdGl2ZVNjYWxlLCBleHBvcnRzKTsKICAgIHRzbGliX2VzNi5fX2V4cG9ydFN0YXIoc2NhbGUsIGV4cG9ydHMpOwogICAgfSk7CgogICAgLyogQ29weXJpZ2h0IDIwMTUgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIEEgbGlzdCBvZiBzeW1ib2xzIHRoYXQgbGluZSBjaGFydHMgY2FuIGN5Y2xlIHRocm91Z2ggcGVyIGRhdGEgc2VyaWVzLgogICAgICovCiAgICBjb25zdCBTWU1CT0xTX0xJU1QgPSBbCiAgICAgICAgewogICAgICAgICAgICBjaGFyYWN0ZXI6ICdcdTI1RkMnLAogICAgICAgICAgICBtZXRob2Q6IHNyYyQyLlN5bWJvbEZhY3Rvcmllcy5zcXVhcmUsCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIGNoYXJhY3RlcjogJ1x1MjVDNicsCiAgICAgICAgICAgIG1ldGhvZDogc3JjJDIuU3ltYm9sRmFjdG9yaWVzLmRpYW1vbmQsCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIGNoYXJhY3RlcjogJ1x1MjVCMicsCiAgICAgICAgICAgIG1ldGhvZDogc3JjJDIuU3ltYm9sRmFjdG9yaWVzLnRyaWFuZ2xlLAogICAgICAgIH0sCiAgICAgICAgewogICAgICAgICAgICBjaGFyYWN0ZXI6ICdcdTI2MDUnLAogICAgICAgICAgICBtZXRob2Q6IHNyYyQyLlN5bWJvbEZhY3Rvcmllcy5zdGFyLAogICAgICAgIH0sCiAgICAgICAgewogICAgICAgICAgICBjaGFyYWN0ZXI6ICdcdTI3MUEnLAogICAgICAgICAgICBtZXRob2Q6IHNyYyQyLlN5bWJvbEZhY3Rvcmllcy5jcm9zcywKICAgICAgICB9LAogICAgXTsKICAgIC8qKiBYIGF4aXMgY2hvaWNlcyBmb3IgVGVuc29yQm9hcmQgY2hhcnRzLiAqLwogICAgdmFyIFhUeXBlOwogICAgKGZ1bmN0aW9uIChYVHlwZSkgewogICAgICAgIC8qKiBMaW5lYXIgc2NhbGUgdXNpbmcgdGhlICJzdGVwIiBwcm9wZXJ0eSBvZiB0aGUgZGF0dW0uICovCiAgICAgICAgWFR5cGVbIlNURVAiXSA9ICJzdGVwIjsKICAgICAgICAvKiogVGVtcG9yYWwgc2NhbGUgdXNpbmcgdGhlICJ3YWxsX3RpbWUiIHByb3BlcnR5IG9mIHRoZSBkYXR1bS4gKi8KICAgICAgICBYVHlwZVsiUkVMQVRJVkUiXSA9ICJyZWxhdGl2ZSI7CiAgICAgICAgLyoqCiAgICAgICAgICogVGVtcG9yYWwgc2NhbGUgdXNpbmcgdGhlICJyZWxhdGl2ZSIgcHJvcGVydHkgb2YgdGhlIGRhdHVtIGlmIGl0IGlzIHByZXNlbnQKICAgICAgICAgKiBvciBjYWxjdWxhdGluZyBmcm9tICJ3YWxsX3RpbWUiIGlmIGl0IGlzbid0LgogICAgICAgICAqLwogICAgICAgIFhUeXBlWyJXQUxMX1RJTUUiXSA9ICJ3YWxsX3RpbWUiOwogICAgfSkoWFR5cGUgfHwgKFhUeXBlID0ge30pKTsKICAgIGxldCBZX1RPT0xUSVBfRk9STUFUVEVSX1BSRUNJU0lPTiA9IDQ7CiAgICBsZXQgU1RFUF9GT1JNQVRURVJfUFJFQ0lTSU9OID0gNDsKICAgIGxldCBZX0FYSVNfRk9STUFUVEVSX1BSRUNJU0lPTiA9IDM7CiAgICBsZXQgVE9PTFRJUF9ZX1BJWEVMX09GRlNFVCA9IDIwOwogICAgbGV0IFRPT0xUSVBfQ0lSQ0xFX1NJWkUgPSA0OwogICAgbGV0IE5BTl9TWU1CT0xfU0laRSA9IDY7CiAgICAvKiBDcmVhdGUgYSBmb3JtYXR0ZXIgZnVuY3Rpb24gdGhhdCB3aWxsIHN3aXRjaCBiZXR3ZWVuIGV4cG9uZW50aWFsIGFuZAogICAgICogcmVndWxhciBkaXNwbGF5IGRlcGVuZGluZyBvbiB0aGUgc2NhbGUgb2YgdGhlIG51bWJlciBiZWluZyBmb3JtYXR0ZWQsCiAgICAgKiBhbmQgc2hvdyBgZGlnaXRzYCBzaWduaWZpY2FudCBkaWdpdHMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG11bHRpc2NhbGVGb3JtYXR0ZXIoZGlnaXRzKSB7CiAgICAgICAgcmV0dXJuICh2KSA9PiB7CiAgICAgICAgICAgIGxldCBhYnN2ID0gTWF0aC5hYnModik7CiAgICAgICAgICAgIGlmIChhYnN2IDwgMWUtMTUpIHsKICAgICAgICAgICAgICAgIC8vIFNvbWV0aW1lcyB6ZXJvLWxpa2UgdmFsdWVzIGdldCBhbiBhbm5veWluZyByZXByZXNlbnRhdGlvbgogICAgICAgICAgICAgICAgYWJzdiA9IDA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IGY7CiAgICAgICAgICAgIGlmIChhYnN2ID49IDEwMDAwKSB7CiAgICAgICAgICAgICAgICBmID0gZm9ybWF0KCcuJyArIGRpZ2l0cyArICd+ZScpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGFic3YgPiAwICYmIGFic3YgPCAwLjAxKSB7CiAgICAgICAgICAgICAgICBmID0gZm9ybWF0KCcuJyArIGRpZ2l0cyArICd+ZScpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgZiA9IGZvcm1hdCgnLicgKyBkaWdpdHMgKyAnfmcnKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZih2KTsKICAgICAgICB9OwogICAgfQogICAgY29uc3Qgc3RlcEZvcm1hdHRlciA9IGZvcm1hdChgLiR7U1RFUF9GT1JNQVRURVJfUFJFQ0lTSU9OfX5zYCk7CiAgICBmdW5jdGlvbiBzdGVwWCgpIHsKICAgICAgICBsZXQgc2NhbGUgPSBuZXcgc3JjJDIuU2NhbGVzLkxpbmVhcigpOwogICAgICAgIHNjYWxlLnRpY2tHZW5lcmF0b3Ioc3JjJDIuU2NhbGVzLlRpY2tHZW5lcmF0b3JzLmludGVnZXJUaWNrR2VuZXJhdG9yKCkpOwogICAgICAgIGxldCBheGlzID0gbmV3IHNyYyQyLkF4ZXMuTnVtZXJpYyhzY2FsZSwgJ2JvdHRvbScpOwogICAgICAgIGF4aXMuZm9ybWF0dGVyKHN0ZXBGb3JtYXR0ZXIpOwogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIHNjYWxlOiBzY2FsZSwKICAgICAgICAgICAgYXhpczogYXhpcywKICAgICAgICAgICAgYWNjZXNzb3I6IChkKSA9PiBkLnN0ZXAsCiAgICAgICAgfTsKICAgIH0KICAgIGxldCB0aW1lRm9ybWF0dGVyID0gc3JjJDIuRm9ybWF0dGVycy50aW1lKCclYSAlYiAlZSwgJUg6JU06JVMnKTsKICAgIGZ1bmN0aW9uIHdhbGxYKCkgewogICAgICAgIGxldCBzY2FsZSA9IG5ldyBzcmMkMi5TY2FsZXMuVGltZSgpOwogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIHNjYWxlOiBzY2FsZSwKICAgICAgICAgICAgYXhpczogbmV3IHNyYyQyLkF4ZXMuVGltZShzY2FsZSwgJ2JvdHRvbScpLAogICAgICAgICAgICBhY2Nlc3NvcjogKGQpID0+IGQud2FsbF90aW1lLAogICAgICAgIH07CiAgICB9CiAgICBsZXQgcmVsYXRpdmVBY2Nlc3NvciA9IAogICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLWFueSBiZSBxdWlldCB0c2MKICAgIChkLCBpbmRleCwgZGF0YXNldCkgPT4gewogICAgICAgIC8vIFdlIG1heSBiZSByZW5kZXJpbmcgdGhlIGZpbmFsLXBvaW50IGRhdHVtIGZvciBzY2F0dGVycGxvdC4KICAgICAgICAvLyBJZiBzbywgd2Ugd2lsbCBoYXZlIGFscmVhZHkgcHJvdmlkZWQgdGhlICdyZWxhdGl2ZScgcHJvcGVydHkKICAgICAgICBpZiAoZC5yZWxhdGl2ZSAhPSBudWxsKSB7CiAgICAgICAgICAgIHJldHVybiBkLnJlbGF0aXZlOwogICAgICAgIH0KICAgICAgICBsZXQgZGF0YSA9IGRhdGFzZXQuZGF0YSgpOwogICAgICAgIC8vIEkgY2FuJ3QgaW1hZ2luZSBob3cgdGhpcyBmdW5jdGlvbiB3b3VsZCBiZSBjYWxsZWQgd2hlbiB0aGUgZGF0YSBpcwogICAgICAgIC8vIGVtcHR5IChhZnRlciBhbGwsIGl0IGl0ZXJhdGVzIG92ZXIgdGhlIGRhdGEpLCBidXQgbGV0cyBndWFyZCBqdXN0CiAgICAgICAgLy8gdG8gYmUgc2FmZS4KICAgICAgICBsZXQgZmlyc3QgPSBkYXRhLmxlbmd0aCA+IDAgPyArZGF0YVswXS53YWxsX3RpbWUgOiAwOwogICAgICAgIHJldHVybiAoK2Qud2FsbF90aW1lIC0gZmlyc3QpIC8gKDYwICogNjAgKiAxMDAwKTsgLy8gbXMgdG8gaG91cnMKICAgIH07CiAgICBsZXQgcmVsYXRpdmVGb3JtYXR0ZXIgPSAobikgPT4gewogICAgICAgIC8vIHdlIHdpbGwgYWx3YXlzIHNob3cgMiB1bml0cyBvZiBwcmVjaXNpb24sIGUuZyBkYXlzIGFuZCBob3Vycywgb3IKICAgICAgICAvLyBtaW51dGVzIGFuZCBzZWNvbmRzLCBidXQgbm90IGhvdXJzIGFuZCBtaW51dGVzIGFuZCBzZWNvbmRzCiAgICAgICAgbGV0IHJldCA9ICcnOwogICAgICAgIGxldCBkYXlzID0gTWF0aC5mbG9vcihuIC8gMjQpOwogICAgICAgIG4gLT0gZGF5cyAqIDI0OwogICAgICAgIGlmIChkYXlzKSB7CiAgICAgICAgICAgIHJldCArPSBkYXlzICsgJ2QgJzsKICAgICAgICB9CiAgICAgICAgbGV0IGhvdXJzID0gTWF0aC5mbG9vcihuKTsKICAgICAgICBuIC09IGhvdXJzOwogICAgICAgIG4gKj0gNjA7CiAgICAgICAgaWYgKGhvdXJzIHx8IGRheXMpIHsKICAgICAgICAgICAgcmV0ICs9IGhvdXJzICsgJ2ggJzsKICAgICAgICB9CiAgICAgICAgbGV0IG1pbnV0ZXMgPSBNYXRoLmZsb29yKG4pOwogICAgICAgIG4gLT0gbWludXRlczsKICAgICAgICBuICo9IDYwOwogICAgICAgIGlmIChtaW51dGVzIHx8IGhvdXJzIHx8IGRheXMpIHsKICAgICAgICAgICAgcmV0ICs9IG1pbnV0ZXMgKyAnbSAnOwogICAgICAgIH0KICAgICAgICBsZXQgc2Vjb25kcyA9IE1hdGguZmxvb3Iobik7CiAgICAgICAgcmV0dXJuIHJldCArIHNlY29uZHMgKyAncyc7CiAgICB9OwogICAgZnVuY3Rpb24gcmVsYXRpdmVYKCkgewogICAgICAgIGxldCBzY2FsZSA9IG5ldyBzcmMkMi5TY2FsZXMuTGluZWFyKCk7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgc2NhbGU6IHNjYWxlLAogICAgICAgICAgICBheGlzOiBuZXcgc3JjJDIuQXhlcy5OdW1lcmljKHNjYWxlLCAnYm90dG9tJyksCiAgICAgICAgICAgIGFjY2Vzc29yOiByZWxhdGl2ZUFjY2Vzc29yLAogICAgICAgIH07CiAgICB9CiAgICBmdW5jdGlvbiBnZXRYQ29tcG9uZW50cyh4VHlwZSkgewogICAgICAgIHN3aXRjaCAoeFR5cGUpIHsKICAgICAgICAgICAgY2FzZSBYVHlwZS5TVEVQOgogICAgICAgICAgICAgICAgcmV0dXJuIHN0ZXBYKCk7CiAgICAgICAgICAgIGNhc2UgWFR5cGUuV0FMTF9USU1FOgogICAgICAgICAgICAgICAgcmV0dXJuIHdhbGxYKCk7CiAgICAgICAgICAgIGNhc2UgWFR5cGUuUkVMQVRJVkU6CiAgICAgICAgICAgICAgICByZXR1cm4gcmVsYXRpdmVYKCk7CiAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2ludmFsaWQgeFR5cGU6ICcgKyB4VHlwZSk7CiAgICAgICAgfQogICAgfQoKICAgIC8vIE5PVF9MT0FERUQgaXMgaW1wbGljaXQKICAgIHZhciBMb2FkU3RhdGU7CiAgICAoZnVuY3Rpb24gKExvYWRTdGF0ZSkgewogICAgICAgIExvYWRTdGF0ZVtMb2FkU3RhdGVbIkxPQURJTkciXSA9IDBdID0gIkxPQURJTkciOwogICAgICAgIExvYWRTdGF0ZVtMb2FkU3RhdGVbIkxPQURFRCJdID0gMV0gPSAiTE9BREVEIjsKICAgIH0pKExvYWRTdGF0ZSB8fCAoTG9hZFN0YXRlID0ge30pKTsKICAgIGZ1bmN0aW9uIERhdGFMb2FkZXJCZWhhdmlvcihzdXBlckNsYXNzKSB7CiAgICAgICAgcmV0dXJuIGNsYXNzIERhdGFMb2FkZXJCZWhhdmlvckltcGwgZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBBIHVuaXF1ZSBpZGVudGlmaWFibGUgc3RyaW5nLiBXaGVuIGNoYW5nZXMsIGl0IGV4cHVuZ2VzIHRoZSBkYXRhCiAgICAgICAgICAgICAgICAgKiBjYWNoZS4KICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgdGhpcy5sb2FkS2V5ID0gJyc7CiAgICAgICAgICAgICAgICAvLyBMaXN0IG9mIGl0ZW1zIHRvIGJlIGxvYWRlZC4gQnkgZGVmYXVsdCwgaXRlbXMgYXJlIHBhc3NlZCB0bwogICAgICAgICAgICAgICAgLy8gYHJlcXVlc3REYXRhYCB0byBmZXRjaCBkYXRhLiBXaGVuIHRoZSByZXF1ZXN0IHJlc29sdmVzLCBpbnZva2VzCiAgICAgICAgICAgICAgICAvLyBgbG9hZERhdGFDYWxsYmFja2Agd2l0aCB0aGUgZGF0dW0gYW5kIGl0cyByZXNwb25zZS4KICAgICAgICAgICAgICAgIHRoaXMuZGF0YVRvTG9hZCA9IFtdOwogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBBIGZ1bmN0aW9uIHRoYXQgdGFrZXMgYW4gaXRlbSBhcyBhbiBpbnB1dCBhbmQgcmV0dXJucyBhIHVuaXF1ZQogICAgICAgICAgICAgICAgICogaWRlbnRpZmlhYmxlIHN0cmluZy4gVXNlZCBmb3IgY2FjaGluZyBwdXJwb3Nlcy4KICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgdGhpcy5nZXREYXRhTG9hZE5hbWUgPSAoaXRlbSkgPT4gU3RyaW5nKGl0ZW0pOwogICAgICAgICAgICAgICAgdGhpcy5kYXRhTG9hZGluZyA9IGZhbHNlOwogICAgICAgICAgICAgICAgLy8gVGhlIHN0YW5kYXJkIE5vZGUuaXNDb25uZWN0ZWQgZG9lc24ndCBzZWVtIHRvIGJlIHNldCByZWxpYWJseSwgc28gd2UKICAgICAgICAgICAgICAgIC8vIHdpcmUgdXAgb3VyIG93biBwcm9wZXJ0eSBtYW51YWxseS4KICAgICAgICAgICAgICAgIHRoaXMuX2lzQ29ubmVjdGVkID0gZmFsc2U7CiAgICAgICAgICAgICAgICAvKgogICAgICAgICAgICAgICAgICogQSBtYXAgb2YgYSBjYWNoZSBrZXkgdG8gTG9hZFN0YXRlLiBJZiBhIGNhY2hlS2V5IGRvZXMgbm90IGV4aXN0IGluIHRoZQogICAgICAgICAgICAgICAgICogbWFwLCBpdCBpcyBjb25zaWRlcmVkIE5PVF9MT0FERUQuCiAgICAgICAgICAgICAgICAgKiBJbnZva2luZyBgcmVsb2FkYCBvciBhIGNoYW5nZSBpbiBgbG9hZEtleWAgY2xlYXJzIHRoZSBjYWNoZS4KICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgdGhpcy5fZGF0YUxvYWRTdGF0ZSA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2NhbmNlbGxlciA9IG5ldyBDYW5jZWxsZXIoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2xvYWREYXRhQXN5bmMgPSBudWxsOwogICAgICAgICAgICAgICAgdGhpcy5fbG9hZERhdGEgPSBsb2Rhc2gudGhyb3R0bGUodGhpcy5fbG9hZERhdGFJbXBsLCAxMDAsIHsKICAgICAgICAgICAgICAgICAgICBsZWFkaW5nOiB0cnVlLAogICAgICAgICAgICAgICAgICAgIHRyYWlsaW5nOiB0cnVlLAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgICAgICAgICAgdGhpcy5faXNDb25uZWN0ZWQgPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGRpc2Nvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgICAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICAgICAgICAgIHRoaXMuX2lzQ29ubmVjdGVkID0gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBhY3RpdmU6IHsKICAgICAgICAgICAgICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfbG9hZERhdGFJZkFjdGl2ZScsCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICBfaXNDb25uZWN0ZWQ6IHsgdHlwZTogQm9vbGVhbiB9LAogICAgICAgICAgICAgICAgICAgIGxvYWRLZXk6IHsgdHlwZTogU3RyaW5nIH0sCiAgICAgICAgICAgICAgICAgICAgZGF0YVRvTG9hZDogeyB0eXBlOiBBcnJheSB9LAogICAgICAgICAgICAgICAgICAgIGdldERhdGFMb2FkTmFtZTogeyB0eXBlOiBPYmplY3QgfSwKICAgICAgICAgICAgICAgICAgICBsb2FkRGF0YUNhbGxiYWNrOiB7IHR5cGU6IE9iamVjdCB9LAogICAgICAgICAgICAgICAgICAgIHJlcXVlc3REYXRhOiB7IHR5cGU6IE9iamVjdCB9LAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzdGF0aWMgZ2V0IG9ic2VydmVycygpIHsKICAgICAgICAgICAgICAgIHJldHVybiBbJ19kYXRhVG9Mb2FkQ2hhbmdlZChfaXNDb25uZWN0ZWQsIGRhdGFUb0xvYWQuKiknXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBvbkxvYWRGaW5pc2goKSB7CiAgICAgICAgICAgICAgICAvLyBPdmVycmlkZSB0byBkbyBzb21ldGhpbmcgdXNlZnVsLgogICAgICAgICAgICB9CiAgICAgICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2RhdGFMb2FkU3RhdGUuY2xlYXIoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2xvYWREYXRhKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmVzZXQoKSB7CiAgICAgICAgICAgICAgICAvLyBodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9pc3N1ZXMvMTQ5OQogICAgICAgICAgICAgICAgLy8gQ2Fubm90IHVzZSB0aGUgb2JzZXJ2ZXIgdG8gb2JzZXJ2ZSBgbG9hZEtleWAgY2hhbmdlcyBkaXJlY3RseS4KICAgICAgICAgICAgICAgIGlmICh0aGlzLl9sb2FkRGF0YUFzeW5jICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQodGhpcy5fbG9hZERhdGFBc3luYyk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fbG9hZERhdGFBc3luYyA9IG51bGw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fY2FuY2VsbGVyKQogICAgICAgICAgICAgICAgICAgIHRoaXMuX2NhbmNlbGxlci5jYW5jZWxBbGwoKTsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9kYXRhTG9hZFN0YXRlKQogICAgICAgICAgICAgICAgICAgIHRoaXMuX2RhdGFMb2FkU3RhdGUuY2xlYXIoKTsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9pc0Nvbm5lY3RlZCkKICAgICAgICAgICAgICAgICAgICB0aGlzLl9sb2FkRGF0YSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIF9kYXRhVG9Mb2FkQ2hhbmdlZCgpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9pc0Nvbm5lY3RlZCkKICAgICAgICAgICAgICAgICAgICB0aGlzLl9sb2FkRGF0YSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGRldGFjaGVkKCkgewogICAgICAgICAgICAgICAgLy8gTm90ZTogQ2Fubm90IGNhbGwgY2FuY2VsbGVyLmNhbmNlbEFsbCBzaW5jZSBpdCB3aWxsIHBvaXNvbiB0aGUgY2FjaGUuCiAgICAgICAgICAgICAgICAvLyBkZXRhY2hlZCBnZXRzIGNhbGxlZCB3aGVuIGEgY29tcG9uZW50IGdldHMgdW5tb3VudGVkIGZyb20gdGhlIGRvY3VtZW50CiAgICAgICAgICAgICAgICAvLyBidXQgaXQgY2FuIGJlIHJlLW1vdW50ZWQuIFdoZW4gcmVtb3VudGVkLCBwb2lzb25lZCBjYWNoZSB3aWxsIG1hbmlmZXN0LgogICAgICAgICAgICAgICAgLy8gdD0wOiBkYXRhTG9hZFN0YXRlOiAnYScgPSBsb2FkaW5nCiAgICAgICAgICAgICAgICAvLyB0PTEwOiB1bm1vdW50CiAgICAgICAgICAgICAgICAvLyB0PTIwOiByZXF1ZXN0IGZvciAnYScgcmVzb2x2ZXMgYnV0IHdlIGRvIG5vdCBjaGFuZ2UgdGhlIGxvYWRTdGF0ZQogICAgICAgICAgICAgICAgLy8gYmVjYXVzZSB3ZSBkbyBub3Qgd2FudCB0byBzZXQgb25lIGlmLCBpbnN0ZWFkLCBpdCB3YXMgcmVzZXR0ZWQgYXQgdD0xMC4KICAgICAgICAgICAgICAgIGlmICh0aGlzLl9sb2FkRGF0YUFzeW5jICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBjbGVhclRpbWVvdXQodGhpcy5fbG9hZERhdGFBc3luYyk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fbG9hZERhdGFBc3luYyA9IG51bGw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgX2xvYWREYXRhSWZBY3RpdmUoKSB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5hY3RpdmUpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9sb2FkRGF0YSgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIF9sb2FkRGF0YUltcGwoKSB7CiAgICAgICAgICAgICAgICBpZiAoIXRoaXMuYWN0aXZlKQogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9sb2FkRGF0YUFzeW5jICE9PSBudWxsKQogICAgICAgICAgICAgICAgICAgIGNsZWFyVGltZW91dCh0aGlzLl9sb2FkRGF0YUFzeW5jKTsKICAgICAgICAgICAgICAgIHRoaXMuX2xvYWREYXRhQXN5bmMgPSBzZXRUaW1lb3V0KHRoaXMuX2NhbmNlbGxlci5jYW5jZWxsYWJsZSgocmVzdWx0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHJlc3VsdC5jYW5jZWxsZWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB0aGlzLmRhdGFMb2FkaW5nID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBkaXJ0eUl0ZW1zID0gdGhpcy5kYXRhVG9Mb2FkLmZpbHRlcigoZGF0dW0pID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgY2FjaGVLZXkgPSB0aGlzLmdldERhdGFMb2FkTmFtZShkYXR1bSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAhdGhpcy5fZGF0YUxvYWRTdGF0ZS5oYXMoY2FjaGVLZXkpOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIGZvciAoY29uc3QgaXRlbSBvZiBkaXJ0eUl0ZW1zKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGNhY2hlS2V5ID0gdGhpcy5nZXREYXRhTG9hZE5hbWUoaXRlbSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2RhdGFMb2FkU3RhdGUuc2V0KGNhY2hlS2V5LCBMb2FkU3RhdGUuTE9BRElORyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9uTG9hZCA9IHRoaXMuX2NhbmNlbGxlci5jYW5jZWxsYWJsZSgocmVzdWx0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChyZXN1bHQuY2FuY2VsbGVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgeyBpdGVtLCBkYXRhIH0gPSByZXN1bHQudmFsdWU7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGNhY2hlS2V5ID0gdGhpcy5nZXREYXRhTG9hZE5hbWUoaXRlbSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2RhdGFMb2FkU3RhdGUuc2V0KGNhY2hlS2V5LCBMb2FkU3RhdGUuTE9BREVEKTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5sb2FkRGF0YUNhbGxiYWNrKHRoaXMsIGl0ZW0sIGRhdGEpOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9uRmluaXNoID0gdGhpcy5fY2FuY2VsbGVyLmNhbmNlbGxhYmxlKChyZXN1bHQpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gT25seSBub3RpZnkgb2YgZGF0YSBsb2FkIGlmIHRoZSBsb2FkIHdhcyBub3QgY2FuY2VsbGVkLgogICAgICAgICAgICAgICAgICAgICAgICBpZiAoIXJlc3VsdC5jYW5jZWxsZWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGtleXNGZXRjaGVkID0gcmVzdWx0LnZhbHVlOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZmV0Y2hlZCA9IG5ldyBTZXQoZGlydHlJdGVtcy5tYXAoKGl0ZW0pID0+IHRoaXMuZ2V0RGF0YUxvYWROYW1lKGl0ZW0pKSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzaG91bGROb3RpZnkgPSB0aGlzLmRhdGFUb0xvYWQuc29tZSgoZGF0dW0pID0+IGZldGNoZWQuaGFzKHRoaXMuZ2V0RGF0YUxvYWROYW1lKGRhdHVtKSkpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHNob3VsZE5vdGlmeSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMub25Mb2FkRmluaXNoKCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9sb2FkRGF0YUFzeW5jID0gbnVsbDsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBpc0RhdGFGZXRjaFBlbmRpbmcgPSBBcnJheS5mcm9tKHRoaXMuX2RhdGFMb2FkU3RhdGUudmFsdWVzKCkpLmluY2x1ZGVzKExvYWRTdGF0ZS5MT0FESU5HKTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFpc0RhdGFGZXRjaFBlbmRpbmcpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuZGF0YUxvYWRpbmcgPSBmYWxzZTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIHRoaXMucmVxdWVzdERhdGEoZGlydHlJdGVtcywgb25Mb2FkLCAoKSA9PiBvbkZpbmlzaCh1bmRlZmluZWQpKTsKICAgICAgICAgICAgICAgIH0pKTsKICAgICAgICAgICAgfQogICAgICAgIH07CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICByZWdpc3RlclN0eWxlRG9tTW9kdWxlKHsKICAgICAgICBtb2R1bGVOYW1lOiAncGxvdHRhYmxlLXN0eWxlJywKICAgICAgICBzdHlsZUNvbnRlbnQ6IGAKICAgIAoucGxvdHRhYmxlLWNvbG9ycy0wIHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjNTI3OWM3OyAvKiBJTkRJR08gKi8KfQoKLnBsb3R0YWJsZS1jb2xvcnMtMSB7CiAgYmFja2dyb3VuZC1jb2xvcjogI2ZkMzczZTsgLyogQ09SQUxfUkVEICovCn0KCi5wbG90dGFibGUtY29sb3JzLTIgewogIGJhY2tncm91bmQtY29sb3I6ICM2M2MyNjE7IC8qIEZFUk4gKi8KfQoKLnBsb3R0YWJsZS1jb2xvcnMtMyB7CiAgYmFja2dyb3VuZC1jb2xvcjogI2ZhZDQxOTsgLyogQlJJR0hUX1NVTiAqLwp9CgoucGxvdHRhYmxlLWNvbG9ycy00IHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjMmMyYjZmOyAvKiBKQUNBUlRBICovCn0KCi5wbG90dGFibGUtY29sb3JzLTUgewogIGJhY2tncm91bmQtY29sb3I6ICNmZjc5Mzk7IC8qIEJVUk5JTkdfT1JBTkdFICovCn0KCi5wbG90dGFibGUtY29sb3JzLTYgewogIGJhY2tncm91bmQtY29sb3I6ICNkYjJlNjU7IC8qIENFUklTRV9SRUQgKi8KfQoKLnBsb3R0YWJsZS1jb2xvcnMtNyB7CiAgYmFja2dyb3VuZC1jb2xvcjogIzk5Y2U1MDsgLyogQ09OSUZFUiAqLwp9CgoucGxvdHRhYmxlLWNvbG9ycy04IHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjOTYyNTY1OyAvKiBST1lBTF9IRUFUSCAqLwp9CgoucGxvdHRhYmxlLWNvbG9ycy05IHsKICBiYWNrZ3JvdW5kLWNvbG9yOiAjMDZjY2NjOyAvKiBST0JJTlNfRUdHX0JMVUUgKi8KfQoKLyoqCiAqIFVzZXItc3VwcGxpZWQgcmVuZGVyVG8gZWxlbWVudC4KICovCi5wbG90dGFibGUgewogIGRpc3BsYXk6IGJsb2NrOyAvKiBtdXN0IGJlIGJsb2NrIGVsZW1lbnRzIGZvciB3aWR0aC9oZWlnaHQgY2FsY3VsYXRpb25zIHRvIHdvcmsgaW4gRmlyZWZveC4gKi8KICBwb2ludGVyLWV2ZW50czogdmlzaWJsZUZpbGw7CiAgcG9zaXRpb246IHJlbGF0aXZlOwogIC8qKgogICAqIFByZSAzLjAsIHVzZXJzIGNvdWxkIHNldCB0aGUgZGltZW5zaW9uIG9mIHRoZSByb290IGVsZW1lbnQgaW4gdHdvIHdheXM6IGVpdGhlciB1c2luZyBDU1MKICAgKiAoaW5saW5lIG9yIHRocm91Z2ggYSBzdHlsZXNoZWV0KSwgb3IgdXNpbmcgdGhlIFNWRyB3aWR0aC9oZWlnaHQgYXR0cmlidXRlcy4gQnkgZGVmYXVsdCwgd2UKICAgKiBzZXQgdGhlIFNWRyB3aWR0aC9oZWlnaHQgYXR0cmlidXRlcyB0byAxMDAlLgogICAqCiAgICogUG9zdCAzLjAgdGhlIHJvb3QgZWxlbWVudCBpcyBhbHdheXMgYSBub3JtYWwgZGl2IGFuZCB0aGUgb25seSB3YXkgdG8gc2V0IHRoZSBkaW1lbnNpb25zIGlzCiAgICogdG8gdXNlIENTUy4gVG8gcmVwbGljYXRlIHRoZSAiMTAwJS1ieS1kZWZhdWx0IiBiZWhhdmlvciwgd2UgYXBwbHkgd2lkdGgvaGVpZ2h0IDEwMCUuCiAgICovCiAgd2lkdGg6IDEwMCU7CiAgaGVpZ2h0OiAxMDAlOwp9CgovKioKICogVGhlIF9lbGVtZW50IHRoYXQgcm9vdHMgZWFjaCBDb21wb25lbnQncyBET00uCiAqLwoucGxvdHRhYmxlIC5jb21wb25lbnQgewogIC8qIEFsbG93IGNvbXBvbmVudHMgdG8gYmUgcG9zaXRpb25lZCB3aXRoIGV4cGxpY2l0IGxlZnQvdG9wL3dpZHRoL2hlaWdodCBzdHlsZXMgKi8KICBwb3NpdGlvbjogYWJzb2x1dGU7Cn0KCi5wbG90dGFibGUgLmJhY2tncm91bmQtY29udGFpbmVyLAoucGxvdHRhYmxlIC5jb250ZW50LAoucGxvdHRhYmxlIC5mb3JlZ3JvdW5kLWNvbnRhaW5lciB7CiAgcG9zaXRpb246IGFic29sdXRlOwogIHdpZHRoOiAxMDAlOwogIGhlaWdodDogMTAwJTsKfQoKLyoqCiAqIERvbid0IGFsbG93IHN2ZyBlbGVtZW50cyBhYm92ZSB0aGUgY29udGVudCB0byBzdGVhbCBldmVudHMKICovCi5wbG90dGFibGUgLmZvcmVncm91bmQtY29udGFpbmVyIHsKICBwb2ludGVyLWV2ZW50czogbm9uZTsKfQoKLnBsb3R0YWJsZSAuY29tcG9uZW50LW92ZXJmbG93LWhpZGRlbiB7CiAgb3ZlcmZsb3c6IGhpZGRlbjsKfQoKLnBsb3R0YWJsZSAuY29tcG9uZW50LW92ZXJmbG93LXZpc2libGUgewogIG92ZXJmbG93OiB2aXNpYmxlOwp9CgoucGxvdHRhYmxlIC5wbG90LWNhbnZhcy1jb250YWluZXIgewogIHdpZHRoOiAxMDAlOwogIGhlaWdodDogMTAwJTsKICBvdmVyZmxvdzogaGlkZGVuOwp9CgoucGxvdHRhYmxlIC5wbG90LWNhbnZhcyB7CiAgd2lkdGg6IDEwMCU7CiAgaGVpZ2h0OiAxMDAlOwogIC8qKgogICAqIFBsYXkgd2VsbCB3aXRoIGRlZmVycmVkIHJlbmRlcmluZy4KICAgKi8KICB0cmFuc2Zvcm0tb3JpZ2luOiAwcHggMHB4IDBweDsKfQoKLnBsb3R0YWJsZSB0ZXh0IHsKICB0ZXh0LXJlbmRlcmluZzogZ2VvbWV0cmljUHJlY2lzaW9uOwp9CgoucGxvdHRhYmxlIC5sYWJlbCB0ZXh0IHsKICBmaWxsOiAjMzIzMTNGOwp9CgoucGxvdHRhYmxlIC5iYXItbGFiZWwtdGV4dC1hcmVhIHRleHQsCi5wbG90dGFibGUgLnNjYXR0ZXItbGFiZWwtdGV4dC1hcmVhIHRleHQgewogIGZvbnQtc2l6ZTogMTJweDsKfQoKLnBsb3R0YWJsZSAubGFiZWwtYXJlYSB0ZXh0IHsKICBmaWxsOiAjMzIzMTNGOwogIGZvbnQtc2l6ZTogMTRweDsKfQoKLnBsb3R0YWJsZSAubGlnaHQtbGFiZWwgdGV4dCB7CiAgZmlsbDogd2hpdGU7Cn0KCi5wbG90dGFibGUgLmRhcmstbGFiZWwgdGV4dCB7CiAgZmlsbDogIzMyMzEzRjsKfQoKLnBsb3R0YWJsZSAub2ZmLWJhci1sYWJlbCB0ZXh0IHsKICBmaWxsOiAjMzIzMTNGOwp9CgoucGxvdHRhYmxlIC5zdGFja2VkLWJhci1sYWJlbCB0ZXh0IHsKICBmaWxsOiAjMzIzMTNGOwogIGZvbnQtc3R5bGU6IG5vcm1hbDsKfQoKLnBsb3R0YWJsZSAuc3RhY2tlZC1iYXItcGxvdCAub2ZmLWJhci1sYWJlbCB7CiAgLyogSEFDS0hBQ0sgIzI3OTU6IGNvcnJlY3Qgb2ZmLWJhciBsYWJlbCBsb2dpYyB0byBiZSBpbXBsZW1lbnRlZCBvbiBTdGFja2VkQmFyICovCiAgdmlzaWJpbGl0eTogaGlkZGVuICFpbXBvcnRhbnQ7Cn0KCi5wbG90dGFibGUgLmF4aXMtbGFiZWwgdGV4dCB7CiAgZm9udC1zaXplOiAxMHB4OwogIGZvbnQtd2VpZ2h0OiBib2xkOwogIGxldHRlci1zcGFjaW5nOiAxcHg7CiAgbGluZS1oZWlnaHQ6IG5vcm1hbDsKICB0ZXh0LXRyYW5zZm9ybTogdXBwZXJjYXNlOwp9CgoucGxvdHRhYmxlIC50aXRsZS1sYWJlbCB0ZXh0IHsKICBmb250LXNpemU6IDIwcHg7CiAgZm9udC13ZWlnaHQ6IGJvbGQ7Cn0KCi5wbG90dGFibGUgLmF4aXMgbGluZS5iYXNlbGluZSB7CiAgc3Ryb2tlOiAjQ0NDOwogIHN0cm9rZS13aWR0aDogMXB4Owp9CgoucGxvdHRhYmxlIC5heGlzIGxpbmUudGljay1tYXJrIHsKICBzdHJva2U6ICNDQ0M7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7Cn0KCi5wbG90dGFibGUgLmF4aXMgdGV4dCB7CiAgZmlsbDogIzMyMzEzRjsKICBmb250LXNpemU6IDEycHg7CiAgZm9udC13ZWlnaHQ6IDIwMDsKICBsaW5lLWhlaWdodDogbm9ybWFsOwp9CgoucGxvdHRhYmxlIC5heGlzIC5hbm5vdGF0aW9uLWNpcmNsZSB7CiAgZmlsbDogd2hpdGU7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7CiAgc3Ryb2tlOiAjQ0NDOwp9CgoucGxvdHRhYmxlIC5heGlzIC5hbm5vdGF0aW9uLWxpbmUgewogIHN0cm9rZTogI0NDQzsKICBzdHJva2Utd2lkdGg6IDFweDsKfQoKLnBsb3R0YWJsZSAuYXhpcyAuYW5ub3RhdGlvbi1yZWN0IHsKICBzdHJva2U6ICNDQ0M7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7CiAgZmlsbDogd2hpdGU7Cn0KCi5wbG90dGFibGUgLmJhci1wbG90IC5iYXNlbGluZSB7CiAgc3Ryb2tlOiAjOTk5Owp9CgoucGxvdHRhYmxlIC5ncmlkbGluZXMgbGluZSB7CiAgc3Ryb2tlOiAjM0MzQzNDOyAvKiBoYWNraGFjazogZ3JpZGxpbmVzIHNob3VsZCBiZSBzb2xpZDsgc2VlICM4MjAgKi8KICBvcGFjaXR5OiAwLjI1OwogIHN0cm9rZS13aWR0aDogMXB4Owp9CgoucGxvdHRhYmxlIC5zZWxlY3Rpb24tYm94LWxheWVyIC5zZWxlY3Rpb24tYXJlYSB7CiAgZmlsbDogYmxhY2s7CiAgZmlsbC1vcGFjaXR5OiAwLjAzOwogIHN0cm9rZTogI0NDQzsKfQovKiBEcmFnQm94TGF5ZXIgKi8KLnBsb3R0YWJsZSAuZHJhZy1ib3gtbGF5ZXIueC1yZXNpemFibGUgLmRyYWctZWRnZS1sciB7CiAgY3Vyc29yOiBldy1yZXNpemU7Cn0KLnBsb3R0YWJsZSAuZHJhZy1ib3gtbGF5ZXIueS1yZXNpemFibGUgLmRyYWctZWRnZS10YiB7CiAgY3Vyc29yOiBucy1yZXNpemU7Cn0KCi5wbG90dGFibGUgLmRyYWctYm94LWxheWVyLngtcmVzaXphYmxlLnktcmVzaXphYmxlIC5kcmFnLWNvcm5lci10bCB7CiAgY3Vyc29yOiBud3NlLXJlc2l6ZTsKfQoucGxvdHRhYmxlIC5kcmFnLWJveC1sYXllci54LXJlc2l6YWJsZS55LXJlc2l6YWJsZSAuZHJhZy1jb3JuZXItdHIgewogIGN1cnNvcjogbmVzdy1yZXNpemU7Cn0KLnBsb3R0YWJsZSAuZHJhZy1ib3gtbGF5ZXIueC1yZXNpemFibGUueS1yZXNpemFibGUgLmRyYWctY29ybmVyLWJsIHsKICBjdXJzb3I6IG5lc3ctcmVzaXplOwp9Ci5wbG90dGFibGUgLmRyYWctYm94LWxheWVyLngtcmVzaXphYmxlLnktcmVzaXphYmxlIC5kcmFnLWNvcm5lci1iciB7CiAgY3Vyc29yOiBud3NlLXJlc2l6ZTsKfQoKLnBsb3R0YWJsZSAuZHJhZy1ib3gtbGF5ZXIubW92YWJsZSAuc2VsZWN0aW9uLWFyZWEgewogIGN1cnNvcjogbW92ZTsgLyogSUUgZmFsbGJhY2sgKi8KICBjdXJzb3I6IC1tb3otZ3JhYjsKICBjdXJzb3I6IC13ZWJraXQtZ3JhYjsKICBjdXJzb3I6IGdyYWI7Cn0KCi5wbG90dGFibGUgLmRyYWctYm94LWxheWVyLm1vdmFibGUgLnNlbGVjdGlvbi1hcmVhOmFjdGl2ZSB7CiAgY3Vyc29yOiAtbW96LWdyYWJiaW5nOwogIGN1cnNvcjogLXdlYmtpdC1ncmFiYmluZzsKICBjdXJzb3I6IGdyYWJiaW5nOwp9Ci8qIC9EcmFnQm94TGF5ZXIgKi8KCi5wbG90dGFibGUgLmd1aWRlLWxpbmUtbGF5ZXIgbGluZS5ndWlkZS1saW5lIHsKICBzdHJva2U6ICNDQ0M7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7Cn0KCi5wbG90dGFibGUgLmRyYWctbGluZS1sYXllci5lbmFibGVkLnZlcnRpY2FsIGxpbmUuZHJhZy1lZGdlIHsKICBjdXJzb3I6IGV3LXJlc2l6ZTsKfQoKLnBsb3R0YWJsZSAuZHJhZy1saW5lLWxheWVyLmVuYWJsZWQuaG9yaXpvbnRhbCBsaW5lLmRyYWctZWRnZSB7CiAgY3Vyc29yOiBucy1yZXNpemU7Cn0KCi5wbG90dGFibGUgLmxlZ2VuZCB0ZXh0IHsKICBmaWxsOiAjMzIzMTNGOwogIGZvbnQtc2l6ZTogMTJweDsKICBmb250LXdlaWdodDogYm9sZDsKICBsaW5lLWhlaWdodDogbm9ybWFsOwp9CgoucGxvdHRhYmxlIC5pbnRlcnBvbGF0ZWQtY29sb3ItbGVnZW5kIHJlY3Quc3dhdGNoLWJvdW5kaW5nLWJveCB7CiAgZmlsbDogbm9uZTsKICBzdHJva2U6ICNDQ0M7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7CiAgcG9pbnRlci1ldmVudHM6IG5vbmU7Cn0KCi5wbG90dGFibGUgLndhdGVyZmFsbC1wbG90IGxpbmUuY29ubmVjdG9yIHsKICBzdHJva2U6ICNDQ0M7CiAgc3Ryb2tlLXdpZHRoOiAxcHg7Cn0KCi5wbG90dGFibGUgLnBpZS1wbG90IC5hcmMub3V0bGluZSB7CiAgc3Ryb2tlLWxpbmVqb2luOiByb3VuZDsKfQoKYCwKICAgIH0pOwoKICAgIC8qIENvcHlyaWdodCAyMDE5IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgZnVuY3Rpb24gZ2V0SHRtbEVsZW1lbnRBbmNlc3RvcnMoZWxlbSkgewogICAgICAgIGNvbnN0IGVsZW1zID0gW107CiAgICAgICAgd2hpbGUgKGVsZW0gJiYgZWxlbSBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7CiAgICAgICAgICAgIGVsZW1zLnB1c2goZWxlbSk7CiAgICAgICAgICAgIGlmIChlbGVtLmFzc2lnbmVkU2xvdCkgewogICAgICAgICAgICAgICAgZWxlbSA9IGVsZW0uYXNzaWduZWRTbG90OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKCFlbGVtLnBhcmVudEVsZW1lbnQpIHsKICAgICAgICAgICAgICAgIGNvbnN0IHBhcmVudE5vZGUgPSBlbGVtLnBhcmVudE5vZGU7CiAgICAgICAgICAgICAgICBpZiAocGFyZW50Tm9kZSBpbnN0YW5jZW9mIERvY3VtZW50RnJhZ21lbnQpIHsKICAgICAgICAgICAgICAgICAgICBlbGVtID0gcGFyZW50Tm9kZS5ob3N0OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgLy8gPGh0bWw+LnBhcmVudE5vZGUgPT0gPGh0bWw+CiAgICAgICAgICAgICAgICAgICAgZWxlbSA9IHBhcmVudE5vZGUgIT09IGVsZW0gPyBwYXJlbnROb2RlIDogbnVsbDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGVsZW0gPSBlbGVtLnBhcmVudEVsZW1lbnQ7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGVsZW1zOwogICAgfQogICAgY29uc3QgX0lERU5USVRZX1RSQU5TRk9STSA9IFsxLCAwLCAwLCAxLCAwLCAwXTsKICAgIC8vIEZvcmtlZCBmcm9tIGh0dHBzOi8vZ2l0aHViLmNvbS9wYWxhbnRpci9wbG90dGFibGUvYmxvYi9iNmUzNmZiZDRkOGQ3Y2JhNTc5ZDg1M2I5ZjM1Y2MyNjBkMTI0M2JmL3NyYy91dGlscy9tYXRoVXRpbHMudHMjTDE3My1MMjAyCiAgICAvLyBUaGUgb25seSBkaWZmZXJlbmNlIGlzIHRoZSBpbXBsZW1lbnRhdGlvbiBvZiB0aGUgZ2V0SHRtbEVsZW1lbnRBbmNlc3RvcnMuCiAgICBmdW5jdGlvbiBnZXRDdW11bGF0aXZlVHJhbnNmb3JtKGVsZW1lbnQpIHsKICAgICAgICBjb25zdCBlbGVtcyA9IGdldEh0bWxFbGVtZW50QW5jZXN0b3JzKGVsZW1lbnQpOwogICAgICAgIGxldCB0cmFuc2Zvcm0gPSBfSURFTlRJVFlfVFJBTlNGT1JNOwogICAgICAgIGxldCBvZmZzZXRQYXJlbnQgPSBudWxsOwogICAgICAgIGZvciAoY29uc3QgZWxlbSBvZiBlbGVtcykgewogICAgICAgICAgICAvLyBhcHBseSBjc3MgdHJhbnNmb3JtIGZyb20gYW55IGFuY2VzdG9yIGVsZW1lbnQKICAgICAgICAgICAgY29uc3QgZWxlbWVudFRyYW5zZm9ybSA9IHNyYyQyLlV0aWxzLkRPTS5nZXRFbGVtZW50VHJhbnNmb3JtKGVsZW0pOwogICAgICAgICAgICBpZiAoZWxlbWVudFRyYW5zZm9ybSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBjb25zdCBtaWRYID0gZWxlbS5jbGllbnRXaWR0aCAvIDI7CiAgICAgICAgICAgICAgICBjb25zdCBtaWRZID0gZWxlbS5jbGllbnRIZWlnaHQgLyAyOwogICAgICAgICAgICAgICAgdHJhbnNmb3JtID0gc3JjJDIuVXRpbHMuTWF0aC5tdWx0aXBseVRyYW5zbGF0ZSh0cmFuc2Zvcm0sIFsKICAgICAgICAgICAgICAgICAgICBtaWRYLAogICAgICAgICAgICAgICAgICAgIG1pZFksCiAgICAgICAgICAgICAgICBdKTsKICAgICAgICAgICAgICAgIHRyYW5zZm9ybSA9IHNyYyQyLlV0aWxzLk1hdGgubXVsdGlwbHlNYXRyaXgodHJhbnNmb3JtLCBzcmMkMi5VdGlscy5NYXRoLmludmVydE1hdHJpeChlbGVtZW50VHJhbnNmb3JtKSk7CiAgICAgICAgICAgICAgICB0cmFuc2Zvcm0gPSBzcmMkMi5VdGlscy5NYXRoLm11bHRpcGx5VHJhbnNsYXRlKHRyYW5zZm9ybSwgWwogICAgICAgICAgICAgICAgICAgIC1taWRYLAogICAgICAgICAgICAgICAgICAgIC1taWRZLAogICAgICAgICAgICAgICAgXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gYXBwbHkgc2Nyb2xsIG9mZnNldHMgZnJvbSBhbnkgYW5jZXN0b3IgZWxlbWVudAogICAgICAgICAgICBsZXQgb2Zmc2V0WCA9IGVsZW0uc2Nyb2xsTGVmdDsKICAgICAgICAgICAgbGV0IG9mZnNldFkgPSBlbGVtLnNjcm9sbFRvcDsKICAgICAgICAgICAgLy8gYXBwbHkgY2xpZW50K29mZnNldCBmcm9tIG9ubHkgYWNlbnN0b3IgIm9mZnNldFBhcmVudCIKICAgICAgICAgICAgaWYgKG9mZnNldFBhcmVudCA9PT0gbnVsbCB8fCBlbGVtID09PSBvZmZzZXRQYXJlbnQpIHsKICAgICAgICAgICAgICAgIG9mZnNldFggLT0gZWxlbS5vZmZzZXRMZWZ0ICsgZWxlbS5jbGllbnRMZWZ0OwogICAgICAgICAgICAgICAgb2Zmc2V0WSAtPSBlbGVtLm9mZnNldFRvcCArIGVsZW0uY2xpZW50VG9wOwogICAgICAgICAgICAgICAgb2Zmc2V0UGFyZW50ID0gZWxlbS5vZmZzZXRQYXJlbnQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdHJhbnNmb3JtID0gc3JjJDIuVXRpbHMuTWF0aC5tdWx0aXBseVRyYW5zbGF0ZSh0cmFuc2Zvcm0sIFsKICAgICAgICAgICAgICAgIG9mZnNldFgsCiAgICAgICAgICAgICAgICBvZmZzZXRZLAogICAgICAgICAgICBdKTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRyYW5zZm9ybTsKICAgIH0KICAgIGNsYXNzIEN1c3RvbVRyYW5zbGF0b3IgZXh0ZW5kcyBzcmMkMi5VdGlscy5UcmFuc2xhdG9yIHsKICAgICAgICBjb21wdXRlUG9zaXRpb24oY2xpZW50WCwgY2xpZW50WSkgewogICAgICAgICAgICBjb25zdCBjbGllbnRQb3NpdGlvbiA9IHsKICAgICAgICAgICAgICAgIHg6IGNsaWVudFgsCiAgICAgICAgICAgICAgICB5OiBjbGllbnRZLAogICAgICAgICAgICB9OwogICAgICAgICAgICBjb25zdCB0cmFuc2Zvcm0gPSBnZXRDdW11bGF0aXZlVHJhbnNmb3JtKHRoaXMuX3Jvb3RFbGVtZW50KTsKICAgICAgICAgICAgaWYgKHRyYW5zZm9ybSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY2xpZW50UG9zaXRpb247CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgdHJhbnNmb3JtZWQgPSBzcmMkMi5VdGlscy5NYXRoLmFwcGx5VHJhbnNmb3JtKHRyYW5zZm9ybSwgY2xpZW50UG9zaXRpb24pOwogICAgICAgICAgICByZXR1cm4gdHJhbnNmb3JtZWQ7CiAgICAgICAgfQogICAgfQogICAgY2xhc3MgTW91c2VEaXNwYXRjaGVyIGV4dGVuZHMgc3JjJDIuRGlzcGF0Y2hlcnMuTW91c2UgewogICAgICAgIGNvbnN0cnVjdG9yKGNvbXBvbmVudCkgewogICAgICAgICAgICBzdXBlcihjb21wb25lbnQpOwogICAgICAgICAgICAvLyBldmVudFRhcmdldCBpcyBgZG9jdW1lbnRgIGJ5IGRlZmF1bHQuIENoYW5nZSBpdCB0byB0aGUgcm9vdCBvZiBjaGFydC4KICAgICAgICAgICAgdGhpcy5fZXZlbnRUYXJnZXQgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCkubm9kZSgpOwogICAgICAgICAgICAvLyBSZXF1aXJlcyBjdXN0b20gdHJhbnNsYXRvciB0aGF0IHVzZXMgY29ycmVjdCBET00gdHJhdmVyc2FsICh3aXRoCiAgICAgICAgICAgIC8vIFdlYkNvbXBvbmVudHMpIHRvIGNoYW5nZSBwb2ludGVyIHBvc2l0aW9uIHRvIHJlbGF0aXZlIHRvIHRoZSByb290IG5vZGUuCiAgICAgICAgICAgIHRoaXMuX3RyYW5zbGF0b3IgPSBuZXcgQ3VzdG9tVHJhbnNsYXRvcihjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCkubm9kZSgpKTsKICAgICAgICB9CiAgICAgICAgc3RhdGljIGdldERpc3BhdGNoZXIoY29tcG9uZW50KSB7CiAgICAgICAgICAgIGNvbnN0IGVsZW1lbnQgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCk7CiAgICAgICAgICAgIGxldCBkaXNwYXRjaGVyID0gZWxlbWVudFtNb3VzZURpc3BhdGNoZXIuX0RJU1BBVENIRVJfS0VZXTsKICAgICAgICAgICAgaWYgKCFkaXNwYXRjaGVyKSB7CiAgICAgICAgICAgICAgICBkaXNwYXRjaGVyID0gbmV3IE1vdXNlRGlzcGF0Y2hlcihjb21wb25lbnQpOwogICAgICAgICAgICAgICAgZWxlbWVudFtNb3VzZURpc3BhdGNoZXIuX0RJU1BBVENIRVJfS0VZXSA9IGRpc3BhdGNoZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGRpc3BhdGNoZXI7CiAgICAgICAgfQogICAgfQogICAgY2xhc3MgVG91Y2hEaXNwYXRjaGVyIGV4dGVuZHMgc3JjJDIuRGlzcGF0Y2hlcnMuVG91Y2ggewogICAgICAgIGNvbnN0cnVjdG9yKGNvbXBvbmVudCkgewogICAgICAgICAgICBzdXBlcihjb21wb25lbnQpOwogICAgICAgICAgICAvLyBldmVudFRhcmdldCBpcyBgZG9jdW1lbnRgIGJ5IGRlZmF1bHQuIENoYW5nZSBpdCB0byB0aGUgcm9vdCBvZiBjaGFydC4KICAgICAgICAgICAgdGhpcy5fZXZlbnRUYXJnZXQgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCkubm9kZSgpOwogICAgICAgICAgICAvLyBSZXF1aXJlcyBjdXN0b20gdHJhbnNsYXRvciB0aGF0IHVzZXMgY29ycmVjdCBET00gdHJhdmVyc2FsICh3aXRoCiAgICAgICAgICAgIC8vIFdlYkNvbXBvbmVudHMpIHRvIGNoYW5nZSBwb2ludGVyIHBvc2l0aW9uIHRvIHJlbGF0aXZlIHRvIHRoZSByb290IG5vZGUuCiAgICAgICAgICAgIHRoaXMuX3RyYW5zbGF0b3IgPSBuZXcgQ3VzdG9tVHJhbnNsYXRvcihjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCkubm9kZSgpKTsKICAgICAgICB9CiAgICAgICAgc3RhdGljIGdldERpc3BhdGNoZXIoY29tcG9uZW50KSB7CiAgICAgICAgICAgIGNvbnN0IGVsZW1lbnQgPSBjb21wb25lbnQucm9vdCgpLnJvb3RFbGVtZW50KCk7CiAgICAgICAgICAgIGxldCBkaXNwYXRjaGVyID0gZWxlbWVudFtUb3VjaERpc3BhdGNoZXIuX0RJU1BBVENIRVJfS0VZXTsKICAgICAgICAgICAgaWYgKCFkaXNwYXRjaGVyKSB7CiAgICAgICAgICAgICAgICBkaXNwYXRjaGVyID0gbmV3IFRvdWNoRGlzcGF0Y2hlcihjb21wb25lbnQpOwogICAgICAgICAgICAgICAgZWxlbWVudFtUb3VjaERpc3BhdGNoZXIuX0RJU1BBVENIRVJfS0VZXSA9IGRpc3BhdGNoZXI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGRpc3BhdGNoZXI7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBGaXhlcyAjMzI4Mi4KICAgICAqCiAgICAgKiBSZXBybzogd2hlbiB0b29sdGlwIGlzIHNob3duLCBzbG93bHkgbW92ZSB0aGUgbW91c2UgdG8gYW4gZWRnZSBvZiBhIGNoYXJ0LgogICAgICogV2UgZXhwZWN0IHRoZSB0b29sdGlwIHRoZSBkaXNhcHBlYXIgd2hlbiB0aGUgY3Vyc29yIGlzIG9uIHRoZSBlZGdlIG9mIHRoZQogICAgICogY2hhcnQuCiAgICAgKgogICAgICogQ2F1c2U6CiAgICAgKiAxLiBGb3IgUG9seW1lciAyIGFuZCBpdHMgU2hhZG93IERPTSBjb21wYXRpYmlsaXR5LCBUZW5zb3JCb2FyZCBvcHRlZCBvdXQgb2YKICAgICAqIHRoZSBldmVudCBkZWxlZ2F0aW9uIG9mIFBsb3R0YWJsZS4gUGxvdHRhYmxlLCBieSBkZWZhdWx0LCBhdHRhY2hlcyBhIHNldCBvZgogICAgICogZXZlbnQgbGlzdGVuZXJzIG9uIGRvY3VtZW50LmJvZHkgYW5kIGludm9rZXMgYXBwcm9wcmlhdGUgY2FsbGJhY2tzCiAgICAgKiBkZXBlbmRpbmcgb24gdGhlIGNpcmN1bXN0YW5jZXMuIEhvd2V2ZXIsIHdpdGggdGhlIFNoYWRvdyBET00sIHRoZSBldmVudAogICAgICogcmUtdGFyZ2V0dGluZyBicm9rZSAoaGFyZGVyIHRvIGlkZW50aWZ5IGBldmVudC50YXJnZXRgKSwgc28gVGVuc29yQm9hcmQsCiAgICAgKiBpbnN0ZWFkLCBhdHRhY2hlcyB0aGUgZXZlbnQgbGlzdGVuZXJzIG9uIGV2ZXJ5IFBsb3R0YWJsZSBjb250YWluZXIsIFNWR3MuCiAgICAgKgogICAgICogMi4gV2hlbiBtb3VzZSBsZWF2ZXMgKG1vdXNlb3V0KSB0aGUgY29udGFpbmVyLCBQbG90dGFibGUgcmVtYXBzIHRoZSBldmVudAogICAgICogYXMgbW91c2UgbW92ZSBhbmQgY2FsY3VsYXRlIHdoZXRoZXIgdGhlIGN1cnNvciBpcyBpbnNpZGUgYSBjb21wb25lbnQKICAgICAqIChJbnRlcmFjdGlvbi5wcm90b3R5cGUuX2lzSW5zaWRlQ29tcG9uZW50LCBzcGVjaWZpY2FsbHkpIHRvIHRyaWdnZXIKICAgICAqIGFwcHJvcHJpYXRlIGNhbGxiYWNrLiBUaGUgbWV0aG9kLCBob3dldmVyIGlzIGZsYXdlZCBzaW5jZSBpdCByZXR1cm5zLCBmb3IgYQogICAgICogY29tcG9uZW50IHRoYXQgaXMsIGZvciBpbnN0YW5jZSwgYXQgPDAsIDA+IHdpdGggc2l6ZSBvZiA8MTAwLCAxMDA+LCB0cnVlCiAgICAgKiB3aGVuIHBvaW50ZXIgaXMgYXQgPDEwMCwgMTAwPi4gSXQgc2hvdWxkIG9ubHkgcmV0dXJuIHRydWUgZm9yIFswLCAxMDApIGZvcgogICAgICogYSBnaXZlbiBkaW1lbnNpb24sIGluc3RlYWQuICBBcyBhIHJlc3VsdCwgdGhlIG1vdXNlb3V0IGV2ZW50IG9jY3VycmVkIGF0CiAgICAgKiA8MTAwLCAxMDA+IHdhcyB0cmVhdGVkIGFzIGFuIGV2ZW50IGluc2lkZSB0aGUgY29tcG9uZW50IGJ1dCBhbGwgdGhlCiAgICAgKiBzdWJzZXF1ZW50IG1vdXNlIG1vdmVtZW50cyBhcmUgbm90IGNhcHR1cmVkIHNpbmNlIHRoZXkgYXJlIGV2ZW50cyB0aGF0CiAgICAgKiBvY2N1cnJlZCBvdXRzaWRlIG9mIHRoZSBldmVudCB0YXJnZXQuIEluIHZhbmlsbGEgUGxvdHRhYmxlLCB0aGlzIGJ1ZyBkbyBub3QKICAgICAqIG1hbmlmZXN0IHNpbmNlIGV2ZW50IGRlbGVnYXRpb24gb24gdGhlIGVudGlyZSBkb2N1bWVudCB3aWxsIGV2ZW50dWFsbHkKICAgICAqIHRyaWdnZXIgbW91c2Ugb3V0IHdoZW4gY3Vyc29yIGlzIGF0LCBmb3IgaW5zdGFuY2UsIDwxMDEsIDEwMD4uCiAgICAgKi8KICAgIHNyYyQyLkludGVyYWN0aW9uLnByb3RvdHlwZS5faXNJbnNpZGVDb21wb25lbnQgPSBmdW5jdGlvbiAocCkgewogICAgICAgIHJldHVybiAoMCA8PSBwLnggJiYKICAgICAgICAgICAgMCA8PSBwLnkgJiYKICAgICAgICAgICAgLy8gRGVsdGE6IGA8YCBpbnN0ZWFkIG9mIGA8PWAgaGVyZSBhbmQgYmVsb3cuCiAgICAgICAgICAgIHAueCA8IHRoaXMuX2NvbXBvbmVudEF0dGFjaGVkVG8ud2lkdGgoKSAmJgogICAgICAgICAgICBwLnkgPCB0aGlzLl9jb21wb25lbnRBdHRhY2hlZFRvLmhlaWdodCgpKTsKICAgIH07CiAgICBjbGFzcyBQb2ludGVySW50ZXJhY3Rpb24gZXh0ZW5kcyBzcmMkMi5JbnRlcmFjdGlvbnMuUG9pbnRlciB7CiAgICAgICAgX2FuY2hvcihjb21wb25lbnQpIHsKICAgICAgICAgICAgY29uc3QgYW55VGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGFueVRoaXMuX2lzQW5jaG9yZWQgPSB0cnVlOwogICAgICAgICAgICBhbnlUaGlzLl9tb3VzZURpc3BhdGNoZXIgPSBNb3VzZURpc3BhdGNoZXIuZ2V0RGlzcGF0Y2hlcihhbnlUaGlzLl9jb21wb25lbnRBdHRhY2hlZFRvKTsKICAgICAgICAgICAgYW55VGhpcy5fbW91c2VEaXNwYXRjaGVyLm9uTW91c2VNb3ZlKGFueVRoaXMuX21vdXNlTW92ZUNhbGxiYWNrKTsKICAgICAgICAgICAgYW55VGhpcy5fdG91Y2hEaXNwYXRjaGVyID0gVG91Y2hEaXNwYXRjaGVyLmdldERpc3BhdGNoZXIoYW55VGhpcy5fY29tcG9uZW50QXR0YWNoZWRUbyk7CiAgICAgICAgICAgIGFueVRoaXMuX3RvdWNoRGlzcGF0Y2hlci5vblRvdWNoU3RhcnQoYW55VGhpcy5fdG91Y2hTdGFydENhbGxiYWNrKTsKICAgICAgICB9CiAgICB9CgogICAgdmFyIFRvb2x0aXBQb3NpdGlvbjsKICAgIChmdW5jdGlvbiAoVG9vbHRpcFBvc2l0aW9uKSB7CiAgICAgICAgLyoqCiAgICAgICAgICogUG9zaXRpb25zIHRoZSB0b29sdGlwIHRvIHRoZSBib3R0b20gb2YgdGhlIGNoYXJ0IGluIG1vc3QgY2FzZS4gUG9zaXRpb25zCiAgICAgICAgICogdGhlIHRvb2x0aXAgYWJvdmUgdGhlIGNoYXJ0IGlmIHRoZXJlIGlzbid0IHN1ZmZpY2llbnQgc3BhY2UgYmVsb3cuCiAgICAgICAgICovCiAgICAgICAgVG9vbHRpcFBvc2l0aW9uWyJBVVRPIl0gPSAiYXV0byI7CiAgICAgICAgLyoqCiAgICAgICAgICogUG9zaXRpb24gdGhlIHRvb2x0aXAgb24gdGhlIGJvdHRvbSBvZiB0aGUgY2hhcnQuCiAgICAgICAgICovCiAgICAgICAgVG9vbHRpcFBvc2l0aW9uWyJCT1RUT00iXSA9ICJib3R0b20iOwogICAgICAgIC8qKgogICAgICAgICAqIFBvc2l0aW9ucyB0aGUgdG9vbHRpcCB0byB0aGUgcmlnaHQgb2YgdGhlIGNoYXJ0LgogICAgICAgICAqLwogICAgICAgIFRvb2x0aXBQb3NpdGlvblsiUklHSFQiXSA9ICJyaWdodCI7CiAgICB9KShUb29sdGlwUG9zaXRpb24gfHwgKFRvb2x0aXBQb3NpdGlvbiA9IHt9KSk7CiAgICBjb25zdCBERUZBVUxUX1RPT0xUSVBfU1RZTEUgPSB7CiAgICAgICAgYm94U2hhZG93OiAnMCAxcHggNHB4IHJnYmEoMCwgMCwgMCwgLjMpJywKICAgICAgICBvcGFjaXR5OiAwLAogICAgICAgIHBvc2l0aW9uOiAnZml4ZWQnLAogICAgICAgIHdpbGxDaGFuZ2U6ICd0cmFuc2Zvcm0nLAogICAgICAgIHpJbmRleDogNSwKICAgIH07CiAgICBsZXQgVnpDaGFydFRvb2x0aXAgPSBjbGFzcyBWekNoYXJ0VG9vbHRpcCBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLnBvc2l0aW9uID0gVG9vbHRpcFBvc2l0aW9uLkFVVE87CiAgICAgICAgICAgIHRoaXMubWluRGlzdEZyb21FZGdlID0gMTU7CiAgICAgICAgICAgIHRoaXMuX3N0eWxlQ2FjaGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLl9yYWYgPSBudWxsOwogICAgICAgICAgICB0aGlzLl90dW5uZWwgPSBudWxsOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgdGhpcy5fc3R5bGVDYWNoZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX3JhZiA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX3R1bm5lbCA9IG51bGw7CiAgICAgICAgfQogICAgICAgIGF0dGFjaGVkKCkgewogICAgICAgICAgICB0aGlzLl90dW5uZWwgPSB0aGlzLl9jcmVhdGVUdW5uZWwoKTsKICAgICAgICAgICAgdGhpcy5faGlkZU9uQmx1ciA9ICgpID0+IHsKICAgICAgICAgICAgICAgIGlmIChkb2N1bWVudC5oaWRkZW4pCiAgICAgICAgICAgICAgICAgICAgdGhpcy5oaWRlKCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHdpbmRvdy5hZGRFdmVudExpc3RlbmVyKCd2aXNpYmlsaXR5Y2hhbmdlJywgdGhpcy5faGlkZU9uQmx1cik7CiAgICAgICAgfQogICAgICAgIGRldGFjaGVkKCkgewogICAgICAgICAgICB0aGlzLmhpZGUoKTsKICAgICAgICAgICAgdGhpcy5fcmVtb3ZlVHVubmVsKHRoaXMuX3R1bm5lbCk7CiAgICAgICAgICAgIHRoaXMuX3R1bm5lbCA9IG51bGw7CiAgICAgICAgICAgIHdpbmRvdy5yZW1vdmVFdmVudExpc3RlbmVyKCd2aXNpYmlsaXR5Y2hhbmdlJywgdGhpcy5faGlkZU9uQmx1cik7CiAgICAgICAgfQogICAgICAgIGNvbnRlbnQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl90dW5uZWwuc2hhZG93Um9vdDsKICAgICAgICB9CiAgICAgICAgaGlkZSgpIHsKICAgICAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX3JhZik7CiAgICAgICAgICAgIHRoaXMuX3N0eWxlQ2FjaGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLl90dW5uZWwuc3R5bGUub3BhY2l0eSA9IDA7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIENTUyBTY29wZXMgdGhlIG5ld2x5IGFkZGVkIERPTSAoaW4gbW9zdCB0b29sdGlwIHdoZXJlIGNvbHVtbnMgYXJlCiAgICAgICAgICogaW52YXJpYWJsZSwgb25seSBuZXdseSBhZGRlZCByb3dzIGFyZSBuZWNlc3NhcnkgdG8gYmUgc2NvcGVkKSBhbmQgcG9zaXRpb25zCiAgICAgICAgICogdGhlIHRvb2x0aXAgd2l0aCByZXNwZWN0IHRvIHRoZSBhbmNob3JOb2RlLgogICAgICAgICAqLwogICAgICAgIHVwZGF0ZUFuZFBvc2l0aW9uKGFuY2hvck5vZGUpIHsKICAgICAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX3JhZik7CiAgICAgICAgICAgIHRoaXMuX3JhZiA9IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gewogICAgICAgICAgICAgICAgaWYgKCF0aGlzLmlzQXR0YWNoZWQpCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgdGhpcy5fcmVwb3NpdGlvbkltcGwoYW5jaG9yTm9kZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfcmVwb3NpdGlvbkltcGwoYW5jaG9yTm9kZSkgewogICAgICAgICAgICBjb25zdCB0b29sdGlwQ29udGVudCA9IHRoaXMuX3R1bm5lbDsKICAgICAgICAgICAgY29uc3Qgbm9kZVJlY3QgPSBhbmNob3JOb2RlLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgICAgICBjb25zdCB0b29sdGlwUmVjdCA9IHRvb2x0aXBDb250ZW50LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgICAgICBjb25zdCB2aWV3cG9ydEhlaWdodCA9IHdpbmRvdy5pbm5lckhlaWdodDsKICAgICAgICAgICAgY29uc3QgZG9jdW1lbnRXaWR0aCA9IGRvY3VtZW50LmJvZHkuY2xpZW50V2lkdGg7CiAgICAgICAgICAgIGNvbnN0IGFuY2hvclRvcCA9IG5vZGVSZWN0LnRvcDsKICAgICAgICAgICAgY29uc3QgYW5jaG9yQm90dG9tID0gYW5jaG9yVG9wICsgbm9kZVJlY3QuaGVpZ2h0OwogICAgICAgICAgICBjb25zdCBlZmZlY3RpdmVUb29sdGlwSGVpZ2h0ID0gdG9vbHRpcFJlY3QuaGVpZ2h0ICsgVE9PTFRJUF9ZX1BJWEVMX09GRlNFVDsKICAgICAgICAgICAgbGV0IGJvdHRvbSA9IG51bGw7CiAgICAgICAgICAgIGxldCBsZWZ0ID0gTWF0aC5tYXgodGhpcy5taW5EaXN0RnJvbUVkZ2UsIG5vZGVSZWN0LmxlZnQpOwogICAgICAgICAgICBsZXQgcmlnaHQgPSBudWxsOwogICAgICAgICAgICBsZXQgdG9wID0gYW5jaG9yVG9wOwogICAgICAgICAgICBpZiAodGhpcy5wb3NpdGlvbiA9PSBUb29sdGlwUG9zaXRpb24uUklHSFQpIHsKICAgICAgICAgICAgICAgIGxlZnQgPSBub2RlUmVjdC5yaWdodDsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRvcCA9IGFuY2hvckJvdHRvbSArIFRPT0xUSVBfWV9QSVhFTF9PRkZTRVQ7CiAgICAgICAgICAgICAgICAvLyBwcmV2ZW50IGl0IGZyb20gZmFsbGluZyBvZmYgdGhlIHJpZ2h0IHNpZGUgb2YgdGhlIHNjcmVlbi4KICAgICAgICAgICAgICAgIGlmIChkb2N1bWVudFdpZHRoIDwgbGVmdCArIHRvb2x0aXBSZWN0LndpZHRoICsgdGhpcy5taW5EaXN0RnJvbUVkZ2UpIHsKICAgICAgICAgICAgICAgICAgICBsZWZ0ID0gbnVsbDsKICAgICAgICAgICAgICAgICAgICByaWdodCA9IHRoaXMubWluRGlzdEZyb21FZGdlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIElmIHRoZXJlIGlzIG5vdCBlbm91Z2ggc3BhY2UgdG8gcmVuZGVyIHRvb2x0aXAgYmVsb3cgdGhlIGFuY2hvck5vZGUgaW4KICAgICAgICAgICAgLy8gdGhlIHZpZXdwb3J0IGFuZCB0aGVyZSBpcyBlbm91Z2ggc3BhY2UgYWJvdmUsIHBsYWNlIGl0IGFib3ZlIHRoZQogICAgICAgICAgICAvLyBhbmNob3JOb2RlLgogICAgICAgICAgICBpZiAodGhpcy5wb3NpdGlvbiA9PSBUb29sdGlwUG9zaXRpb24uQVVUTyAmJgogICAgICAgICAgICAgICAgbm9kZVJlY3QudG9wIC0gZWZmZWN0aXZlVG9vbHRpcEhlaWdodCA+IDAgJiYKICAgICAgICAgICAgICAgIHZpZXdwb3J0SGVpZ2h0IDwgbm9kZVJlY3QudG9wICsgbm9kZVJlY3QuaGVpZ2h0ICsgZWZmZWN0aXZlVG9vbHRpcEhlaWdodCkgewogICAgICAgICAgICAgICAgdG9wID0gbnVsbDsKICAgICAgICAgICAgICAgIGJvdHRvbSA9IHZpZXdwb3J0SGVpZ2h0IC0gYW5jaG9yVG9wICsgVE9PTFRJUF9ZX1BJWEVMX09GRlNFVDsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBuZXdTdHlsZSA9IHsKICAgICAgICAgICAgICAgIGNvbnRhaW46ICdjb250ZW50JywKICAgICAgICAgICAgICAgIG9wYWNpdHk6IDEsCiAgICAgICAgICAgICAgICBsZWZ0OiBsZWZ0ID8gYCR7bGVmdH1weGAgOiBudWxsLAogICAgICAgICAgICAgICAgcmlnaHQ6IHJpZ2h0ID8gYCR7cmlnaHR9cHhgIDogbnVsbCwKICAgICAgICAgICAgICAgIHRvcDogdG9wID8gYCR7dG9wfXB4YCA6IG51bGwsCiAgICAgICAgICAgICAgICBib3R0b206IGJvdHRvbSA/IGAke2JvdHRvbX1weGAgOiBudWxsLAogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyBEbyBub3QgdXBkYXRlIHRoZSBzdHlsZSAod2hpY2ggY2FuIGNhdXNlIHJlLWxheW91dCkgaWYgaXQgaGFzIG5vdAogICAgICAgICAgICAvLyBjaGFuZ2VkLgogICAgICAgICAgICBpZiAoIWxvZGFzaC5pc0VxdWFsKHRoaXMuX3N0eWxlQ2FjaGUsIG5ld1N0eWxlKSkgewogICAgICAgICAgICAgICAgT2JqZWN0LmFzc2lnbih0b29sdGlwQ29udGVudC5zdHlsZSwgbmV3U3R5bGUpOwogICAgICAgICAgICAgICAgdGhpcy5fc3R5bGVDYWNoZSA9IG5ld1N0eWxlOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVUdW5uZWwoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5jb250ZW50Q29tcG9uZW50TmFtZSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoJ1JlcXVpcmUgYGNvbnRlbnRDb21wb25lbnROYW1lYCB0byBiZSBhIG5hbWUgb2YgYSBQb2x5bWVyIGNvbXBvbmVudCcpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHR1bm5lbCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQodGhpcy5jb250ZW50Q29tcG9uZW50TmFtZSk7CiAgICAgICAgICAgIE9iamVjdC5hc3NpZ24odHVubmVsLnN0eWxlLCBERUZBVUxUX1RPT0xUSVBfU1RZTEUpOwogICAgICAgICAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKHR1bm5lbCk7CiAgICAgICAgICAgIHJldHVybiB0dW5uZWw7CiAgICAgICAgfQogICAgICAgIF9yZW1vdmVUdW5uZWwodHVubmVsKSB7CiAgICAgICAgICAgIGRvY3VtZW50LmJvZHkucmVtb3ZlQ2hpbGQodHVubmVsKTsKICAgICAgICB9CiAgICB9OwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBWekNoYXJ0VG9vbHRpcC5wcm90b3R5cGUsICJjb250ZW50Q29tcG9uZW50TmFtZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFZ6Q2hhcnRUb29sdGlwLnByb3RvdHlwZSwgInBvc2l0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVnpDaGFydFRvb2x0aXAucHJvdG90eXBlLCAibWluRGlzdEZyb21FZGdlIiwgdm9pZCAwKTsKICAgIFZ6Q2hhcnRUb29sdGlwID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndnotY2hhcnQtdG9vbHRpcCcpCiAgICBdLCBWekNoYXJ0VG9vbHRpcCk7CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjbGFzcyBMaW5lYXJTY2FsZSBleHRlbmRzIHNyYyQyLlNjYWxlcy5MaW5lYXIgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgICB0aGlzLl9pZ25vcmVPdXRsaWVyID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMucGFkUHJvcG9ydGlvbigwLjIpOwogICAgICAgIH0KICAgICAgICBzZXRWYWx1ZVByb3ZpZGVyRm9yRG9tYWluKHByb3ZpZGVyKSB7CiAgICAgICAgICAgIHRoaXMuX3ZhbHVlUHJvdmlkZXJGb3JEb21haW4gPSBwcm92aWRlcjsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFRPRE8obmlja2ZlbHQpOiBFeGFtaW5lIHdoZXRoZXIgd2UgdHJ1bHkgcmVxdWlyZSBgY2AuCiAgICAgICAgICogQWRkcyBzb21lIHBhZGRpbmcgdG8gYSBnaXZlbiBkb21haW4uIFNwZWNpZmljYWxseSwgaXQ6CiAgICAgICAgICogLSByZXR1cm5zIGFib3V0IFstMC4xYSAtIGMsIDIuMWEgKyBjXSB3aGVuIGEgPSBiIGFuZCBhID49IDAuCiAgICAgICAgICogLSByZXR1cm5zIGFib3V0IFstMi4xfGF8IC0gYywgLTAuMXxhfCArIGNdIHdoZW4gYSA9IGIgYW5kIGEgPCAwLgogICAgICAgICAqIC0gcmV0dXJucyBbLTAuMWIsIGIgKyBwYWRQcm9wb3J0aW9uICogKGItYSldIGlmIGIgPiAyYSBhbmQgYSA+IDAKICAgICAgICAgKiAtIGVsc2UsIHBhZHMgYnkgYHBhZFByb3BvcnRpb25gCiAgICAgICAgICogTm90ZSB0aGF0IGBjYCBpcyBhIGNvbnN0YW50IG9mZnNldCB3aGljaCBzcGVjaWZpY2FsbHkgaXMgMS4xLiBQbGVhc2UgcmVmZXIKICAgICAgICAgKiB0byBbMV0gZm9yIGl0cyByYXRpb25hbGUuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX25pY2VEb21haW4oZG9tYWluLCBjb3VudCkgewogICAgICAgICAgICBjb25zdCBbYSwgYl0gPSBkb21haW47CiAgICAgICAgICAgIGxldCBwYWRkaW5nOwogICAgICAgICAgICBjb25zdCBzcGFuID0gYiAtIGE7CiAgICAgICAgICAgIGlmIChzcGFuID09PSAwKSB7CiAgICAgICAgICAgICAgICAvLyBJZiBiPT09YSwgd2Ugd291bGQgY3JlYXRlIGFuIGVtcHR5IHJhbmdlLiBXZSBpbnN0ZWFkIHNlbGVjdCB0aGUgcmFuZ2UKICAgICAgICAgICAgICAgIC8vIFswLCAyKmFdIGlmIGEgPiAwLCBvciBbLTIqYSwgMF0gaWYgYSA8IDAsIHBsdXMgYSBsaXR0bGUgYml0IG9mCiAgICAgICAgICAgICAgICAvLyBleHRyYSBwYWRkaW5nIG9uIHRoZSB0b3AgYW5kIGJvdHRvbSBvZiB0aGUgcGxvdC4KICAgICAgICAgICAgICAgIHBhZGRpbmcgPSBNYXRoLmFicyhhKSAqIDEuMSArIDEuMTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHBhZGRpbmcgPSBzcGFuICogdGhpcy5wYWRQcm9wb3J0aW9uKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IGxvd2VyOwogICAgICAgICAgICBpZiAoYSA+PSAwICYmIGEgPCBzcGFuKSB7CiAgICAgICAgICAgICAgICAvLyBbMV06IFdlIGluY2x1ZGUgdGhlIGludGVyY2VwdCAoeSA9IDApIGlmIGRvaW5nIHNvIGxlc3MgdGhhbiBkb3VibGVzIHRoZQogICAgICAgICAgICAgICAgLy8gc3BhbiBvZiB0aGUgeS1heGlzLiAoV2UgYWN0dWFsbHkgc2VsZWN0IGEgbG93ZXIgYm91bmQgdGhhdCdzIHNsaWdodGx5CiAgICAgICAgICAgICAgICAvLyBsZXNzIHRoYW4gMCBzbyB0aGF0IDAuMDAgd2lsbCBjbGVhcmx5IGJlIHdyaXR0ZW4gb24gdGhlIGxvd2VyIGVkZ2Ugb2YKICAgICAgICAgICAgICAgIC8vIHRoZSBjaGFydC4gVGhlIGxhYmVsIG9uIHRoZSBsb3dlc3QgdGljayBpcyBvZnRlbiBmaWx0ZXJlZCBvdXQuKQogICAgICAgICAgICAgICAgbG93ZXIgPSAtMC4xICogYjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGxvd2VyID0gYSAtIHBhZGRpbmc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHN1cGVyLl9uaWNlRG9tYWluKFtsb3dlciwgYiArIHBhZGRpbmddLCBjb3VudCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEBvdmVycmlkZSB0byByZW1vdmUgZGVmYXVsdCBwYWRkaW5nIGxvZ2ljLgogICAgICAgICAqLwogICAgICAgIF9nZXRVbmJvdW5kZWRFeHRlbnQoaWdub3JlQXR0YWNoU3RhdGUpIHsKICAgICAgICAgICAgY29uc3QgaW5jbHVkZWRWYWx1ZXMgPSB0aGlzLl9nZXRBbGxJbmNsdWRlZFZhbHVlcyhpZ25vcmVBdHRhY2hTdGF0ZSk7CiAgICAgICAgICAgIGxldCBleHRlbnQgPSB0aGlzLl9kZWZhdWx0RXh0ZW50KCk7CiAgICAgICAgICAgIGlmIChpbmNsdWRlZFZhbHVlcy5sZW5ndGggIT09IDApIHsKICAgICAgICAgICAgICAgIGNvbnN0IGNvbWJpbmVkRXh0ZW50ID0gWwogICAgICAgICAgICAgICAgICAgIHNyYyQyLlV0aWxzLk1hdGgubWluKGluY2x1ZGVkVmFsdWVzLCBleHRlbnRbMF0pLAogICAgICAgICAgICAgICAgICAgIHNyYyQyLlV0aWxzLk1hdGgubWF4KGluY2x1ZGVkVmFsdWVzLCBleHRlbnRbMV0pLAogICAgICAgICAgICAgICAgXTsKICAgICAgICAgICAgICAgIGV4dGVudCA9IHRoaXMuX25pY2VEb21haW4oY29tYmluZWRFeHRlbnQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBleHRlbnQ7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEBvdmVycmlkZQogICAgICAgICAqLwogICAgICAgIF9nZXRBbGxJbmNsdWRlZFZhbHVlcyhpZ25vcmVBdHRhY2hTdGF0ZSA9IGZhbHNlKSB7CiAgICAgICAgICAgIGNvbnN0IHZhbHVlcyA9IHRoaXMuX3ZhbHVlUHJvdmlkZXJGb3JEb21haW4KICAgICAgICAgICAgICAgID8gdGhpcy5fdmFsdWVQcm92aWRlckZvckRvbWFpbigpCiAgICAgICAgICAgICAgICA6IFtdOwogICAgICAgICAgICByZXR1cm4gdGhpcy5leHRlbnRPZlZhbHVlcyh2YWx1ZXMpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBAb3ZlcnJpZGUgdG8gYXBwbHkgdGhlIG91dGxpZXIgbG9naWMuCiAgICAgICAgICovCiAgICAgICAgZXh0ZW50T2ZWYWx1ZXModmFsdWVzKSB7CiAgICAgICAgICAgIGNvbnN0IGxlZ2FsVmFsdWVzID0gdmFsdWVzLmZpbHRlcigoeCkgPT4gc3JjJDIuVXRpbHMuTWF0aC5pc1ZhbGlkTnVtYmVyKHgpKTsKICAgICAgICAgICAgbGV0IGZpbHRlcmVkVmFsdWVzID0gbGVnYWxWYWx1ZXM7CiAgICAgICAgICAgIGlmICh0aGlzLmlnbm9yZU91dGxpZXIoKSkgewogICAgICAgICAgICAgICAgY29uc3Qgc29ydGVkVmFsdWVzID0gbGVnYWxWYWx1ZXMuc29ydCgoYSwgYikgPT4gYSAtIGIpOwogICAgICAgICAgICAgICAgY29uc3QgYSA9IHRocmVzaG9sZChzb3J0ZWRWYWx1ZXMsIDAuMDUpOwogICAgICAgICAgICAgICAgY29uc3QgYiA9IHRocmVzaG9sZChzb3J0ZWRWYWx1ZXMsIDAuOTUpOwogICAgICAgICAgICAgICAgZmlsdGVyZWRWYWx1ZXMgPSBsZWdhbFZhbHVlcy5maWx0ZXIoKHgpID0+IHggPj0gYSAmJiB4IDw9IGIpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGV4dGVudCQxID0gZXh0ZW50KGZpbHRlcmVkVmFsdWVzKTsKICAgICAgICAgICAgcmV0dXJuIGV4dGVudCQxWzBdID09IG51bGwgfHwgZXh0ZW50JDFbMV0gPT0gbnVsbCA/IFtdIDogZXh0ZW50JDE7CiAgICAgICAgfQogICAgICAgIGlnbm9yZU91dGxpZXIoaWdub3JlKSB7CiAgICAgICAgICAgIGlmICh0eXBlb2YgaWdub3JlID09ICdib29sZWFuJykgewogICAgICAgICAgICAgICAgdGhpcy5faWdub3JlT3V0bGllciA9IGlnbm9yZTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9pZ25vcmVPdXRsaWVyOwogICAgICAgIH0KICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxOCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNsYXNzIFRmU2NhbGUgZXh0ZW5kcyBzcmMkMi5RdWFudGl0YXRpdmVTY2FsZSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX2lnbm9yZU91dGxpZXIgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgc2V0VmFsdWVQcm92aWRlckZvckRvbWFpbihwcm92aWRlcikgewogICAgICAgICAgICB0aGlzLl92YWx1ZVByb3ZpZGVyRm9yRG9tYWluID0gcHJvdmlkZXI7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KICAgICAgICBpZ25vcmVPdXRsaWVyKGlnbm9yZSkgewogICAgICAgICAgICBpZiAodHlwZW9mIGlnbm9yZSA9PSAnYm9vbGVhbicpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2lnbm9yZU91dGxpZXIgPSBpZ25vcmU7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpczsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5faWdub3JlT3V0bGllcjsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBwb3NzaWJsZSBgZXh0ZW50YHMgZm9yIGEgZGF0YXNldC4gTm90ZSB0aGF0IGEgZGF0YXNldCBjYW4gY29udGFpbgogICAgICAgICAqIG11bHRpcGxlIHNlcmllcy4gVW5saWtlIHRoZSBtZXRob2QgbmFtZSBzdWdnZXN0cywgaXQgdXNlcyB2YWx1ZXMgZnJvbSBlYWNoCiAgICAgICAgICogc2VyaWVzIHRvIHJldHVybiBgZXh0ZW50YHMuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgX2dldEFsbEluY2x1ZGVkVmFsdWVzKGlnbm9yZUF0dGFjaFN0YXRlID0gZmFsc2UpIHsKICAgICAgICAgICAgY29uc3QgdmFsdWVzID0gdGhpcy5fdmFsdWVQcm92aWRlckZvckRvbWFpbgogICAgICAgICAgICAgICAgPyB0aGlzLl92YWx1ZVByb3ZpZGVyRm9yRG9tYWluKCkKICAgICAgICAgICAgICAgIDogW107CiAgICAgICAgICAgIHJldHVybiB0aGlzLmV4dGVudE9mVmFsdWVzKHZhbHVlcyk7CiAgICAgICAgfQogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE4IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gU21hbGxlc3QgcG9zaXRpdmUgbm9uLXplcm8gdmFsdWUgcmVwcmVzZW50ZWQgYnkgSUVFRSA3NTQgYmluYXJ5ICg2NCBiaXQpCWltcG9ydCAqIGFzIGQzIGZyb20gJ2QzJzsKICAgIC8vIGZsb2F0aW5nLXBvaW50IG51bWJlci4KICAgIC8vIGh0dHBzOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNS4xLyNzZWMtOC41CiAgICBjb25zdCBNSU5fUE9TSVRJVkVfVkFMVUUgPSBNYXRoLnBvdygyLCAtMTA3NCk7CiAgICBmdW5jdGlvbiBsb2ckNCh4KSB7CiAgICAgICAgcmV0dXJuIE1hdGgubG9nMTAoeCk7CiAgICB9CiAgICBmdW5jdGlvbiBwb3ckNCh4KSB7CiAgICAgICAgcmV0dXJuIE1hdGgucG93KDEwLCB4KTsKICAgIH0KICAgIC8qKgogICAgICogQSBsb2dhcml0aG1pYyBzY2FsZSB0aGF0IHJldHVybnMgTmFOIGZvciBhbGwgbm9uLXBvc2l0aXZlIHZhbHVlcyBhcyBpdAogICAgICogbWF0aGVtYXRpY2FsbHkgaXMgc3VwcG9zZWQgdG8gYmUgLUluZmluaXR5LiBBbHNvLCBkdWUgdG8gdGhlIGZsb2F0aW5nIHBvaW50CiAgICAgKiBwcmVjaXNpb24gaXNzdWUsIGl0IHRyZWF0cyBhbGwgdmFsdWVzIHNtYWxsZXIgdGhhbiBNSU5fUE9TSVRJVkVfVkFMVUUgYXMKICAgICAqIG5vbi1wb3NpdGl2ZS4gTGFzdGx5LCBpZiB1c2luZyBhdXRvRG9tYWluIGZlYXR1cmUgYW5kIGlmIGFsbCB2YWx1ZXMgYXJlIHRoZQogICAgICogc2FtZSB2YWx1ZSwgaXQgcGFkcyAxMCUgb2YgdGhlIHZhbHVlLgogICAgICovCiAgICBjbGFzcyBMb2dTY2FsZSBleHRlbmRzIFRmU2NhbGUgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgICB0aGlzLl9kM0xvZ1NjYWxlID0gbG9nJDEoKTsKICAgICAgICAgICAgdGhpcy5wYWRQcm9wb3J0aW9uKDAuMik7CiAgICAgICAgfQogICAgICAgIHNjYWxlKHgpIHsKICAgICAgICAgICAgLy8gUmV0dXJuaW5nIE5hTiBtYWtlcyBzdXJlIGxpbmUgcGxvdCBkb2VzIG5vdCBwbG90IGlsbGVnYWwgdmFsdWVzLgogICAgICAgICAgICBpZiAoeCA8PSAwKQogICAgICAgICAgICAgICAgcmV0dXJuIE5hTjsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzTG9nU2NhbGUoeCk7CiAgICAgICAgfQogICAgICAgIGludmVydCh4KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM0xvZ1NjYWxlLmludmVydCh4KTsKICAgICAgICB9CiAgICAgICAgc2NhbGVUcmFuc2Zvcm1hdGlvbih2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5zY2FsZSh2YWx1ZSk7CiAgICAgICAgfQogICAgICAgIGludmVydGVkVHJhbnNmb3JtYXRpb24odmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW52ZXJ0KHZhbHVlKTsKICAgICAgICB9CiAgICAgICAgZ2V0VHJhbnNmb3JtYXRpb25Eb21haW4oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmRvbWFpbigpOwogICAgICAgIH0KICAgICAgICBzZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbihkb21haW4pIHsKICAgICAgICAgICAgdGhpcy5kb21haW4oZG9tYWluKTsKICAgICAgICB9CiAgICAgICAgZ2V0VHJhbnNmb3JtYXRpb25FeHRlbnQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9nZXRVbmJvdW5kZWRFeHRlbnQodHJ1ZSk7CiAgICAgICAgfQogICAgICAgIF9nZXREb21haW4oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl91bnRyYW5zZm9ybWVkRG9tYWluOwogICAgICAgIH0KICAgICAgICBfc2V0RG9tYWluKHZhbHVlcykgewogICAgICAgICAgICB0aGlzLl91bnRyYW5zZm9ybWVkRG9tYWluID0gdmFsdWVzOwogICAgICAgICAgICBjb25zdCBbbWluLCBtYXhdID0gdmFsdWVzOwogICAgICAgICAgICBzdXBlci5fc2V0RG9tYWluKFtNYXRoLm1heChNSU5fUE9TSVRJVkVfVkFMVUUsIG1pbiksIG1heF0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHaXZlbiBhIGRvbWFpbiwgcGFkIGl0IGFuZCBjbGlwIHRoZSBsb3dlciBib3VuZCB0byBNSU5fUE9TSVRJVkVfVkFMVUUuCiAgICAgICAgICovCiAgICAgICAgX25pY2VEb21haW4oZG9tYWluLCBjb3VudCkgewogICAgICAgICAgICBjb25zdCBbbG93LCBoaWdoXSA9IGRvbWFpbjsKICAgICAgICAgICAgY29uc3QgYWRqdXN0ZWRMb2dMb3cgPSBNYXRoLm1heChsb2ckNChNSU5fUE9TSVRJVkVfVkFMVUUpLCBsb2ckNChsb3cpKTsKICAgICAgICAgICAgY29uc3QgbG9nSGlnaCA9IGxvZyQ0KGhpZ2gpOwogICAgICAgICAgICBjb25zdCBzcHJlYWQgPSBsb2dIaWdoIC0gYWRqdXN0ZWRMb2dMb3c7CiAgICAgICAgICAgIGNvbnN0IHBhZCA9IHNwcmVhZCA/IHNwcmVhZCAqIHRoaXMucGFkUHJvcG9ydGlvbigpIDogMTsKICAgICAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICAgICAgIHBvdyQ0KE1hdGgubWF4KGxvZyQ0KE1JTl9QT1NJVElWRV9WQUxVRSksIGFkanVzdGVkTG9nTG93IC0gcGFkKSksCiAgICAgICAgICAgICAgICBwb3ckNChsb2dIaWdoICsgcGFkKSwKICAgICAgICAgICAgXTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogR2VuZXJhdGVzIGEgcG9zc2libGUgZXh0ZW50IGJhc2VkIG9uIGRhdGEgZnJvbSBhbGwgcGxvdHMgdGhlIHNjYWxlIGlzCiAgICAgICAgICogY29ubmVjdGVkIHRvIGJ5IHRha2luZyB0aGUgbWluaW11bSBhbmQgbWF4aW11bSB2YWx1ZXMgb2YgYWxsIGV4dGVudHMgZm9yCiAgICAgICAgICogbG93ZXIgYW5kIHVwcGVyIGJvdW5kLCByZXNwZWN0aXZlbHkuCiAgICAgICAgICogQG92ZXJyaWRlIHRvIHJlbW92ZSBkZWZhdWx0IHBhZGRpbmcgbG9naWMuCiAgICAgICAgICovCiAgICAgICAgX2dldFVuYm91bmRlZEV4dGVudChpZ25vcmVBdHRhY2hTdGF0ZSkgewogICAgICAgICAgICBjb25zdCBpbmNsdWRlZFZhbHVlcyA9IHRoaXMuX2dldEFsbEluY2x1ZGVkVmFsdWVzKGlnbm9yZUF0dGFjaFN0YXRlKTsKICAgICAgICAgICAgbGV0IGV4dGVudCA9IHRoaXMuX2RlZmF1bHRFeHRlbnQoKTsKICAgICAgICAgICAgaWYgKGluY2x1ZGVkVmFsdWVzLmxlbmd0aCAhPT0gMCkgewogICAgICAgICAgICAgICAgY29uc3QgY29tYmluZWRFeHRlbnQgPSBbCiAgICAgICAgICAgICAgICAgICAgc3JjJDIuVXRpbHMuTWF0aC5taW4oaW5jbHVkZWRWYWx1ZXMsIGV4dGVudFswXSksCiAgICAgICAgICAgICAgICAgICAgc3JjJDIuVXRpbHMuTWF0aC5tYXgoaW5jbHVkZWRWYWx1ZXMsIGV4dGVudFsxXSksCiAgICAgICAgICAgICAgICBdOwogICAgICAgICAgICAgICAgZXh0ZW50ID0gdGhpcy5fbmljZURvbWFpbihjb21iaW5lZEV4dGVudCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGV4dGVudDsKICAgICAgICB9CiAgICAgICAgX2dldEFsbEluY2x1ZGVkVmFsdWVzKGlnbm9yZUF0dGFjaFN0YXRlID0gZmFsc2UpIHsKICAgICAgICAgICAgY29uc3QgdmFsdWVzID0gc3VwZXIuX2dldEFsbEluY2x1ZGVkVmFsdWVzKCk7CiAgICAgICAgICAgIC8vIEZvciBsb2cgc2NhbGUsIHRoZSB2YWx1ZSBjYW5ub3QgYmUgc21hbGxlciBvciBlcXVhbCB0byAwLiBUaGV5IGFyZQogICAgICAgICAgICAvLyBuZWdhdGl2ZSBpbmZpbml0eS4KICAgICAgICAgICAgcmV0dXJuIHZhbHVlcy5tYXAoKHgpID0+ICh4ID4gMCA/IHggOiBNSU5fUE9TSVRJVkVfVkFMVUUpKTsKICAgICAgICB9CiAgICAgICAgX2RlZmF1bHRFeHRlbnQoKSB7CiAgICAgICAgICAgIHJldHVybiBbMSwgMTBdOwogICAgICAgIH0KICAgICAgICBfYmFja2luZ1NjYWxlRG9tYWluKHZhbHVlcykgewogICAgICAgICAgICBpZiAodmFsdWVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLl9kM0xvZ1NjYWxlLmRvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fZDNMb2dTY2FsZS5kb21haW4odmFsdWVzKTsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9nZXRSYW5nZSgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzTG9nU2NhbGUucmFuZ2UoKTsKICAgICAgICB9CiAgICAgICAgX3NldFJhbmdlKHZhbHVlcykgewogICAgICAgICAgICB0aGlzLl9kM0xvZ1NjYWxlLnJhbmdlKHZhbHVlcyk7CiAgICAgICAgfQogICAgICAgIGRlZmF1bHRUaWNrcygpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzTG9nU2NhbGUudGlja3MoMSk7CiAgICAgICAgfQogICAgICAgIHRpY2tzKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZDNMb2dTY2FsZS50aWNrcygpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGFuIGBleHRlbnRgIGZvciBhIGRhdGEgc2VyaWVzLiBJbiBsb2ctc2NhbGUsIHdlIG11c3Qgb21pdCBhbGwKICAgICAgICAgKiBub24tcG9zaXRpdmUgdmFsdWVzIHdoZW4gY29tcHV0aW5nIGEgYGRvbWFpbmAuCiAgICAgICAgICogQG92ZXJyaWRlCiAgICAgICAgICovCiAgICAgICAgZXh0ZW50T2ZWYWx1ZXModmFsdWVzKSB7CiAgICAgICAgICAgIC8vIExvZyBjYW4gb25seSB0YWtlIHBvc2l0aXZlIHZhbHVlcy4KICAgICAgICAgICAgY29uc3QgbGVnYWxWYWx1ZXMgPSB2YWx1ZXMuZmlsdGVyKCh4KSA9PiBzcmMkMi5VdGlscy5NYXRoLmlzVmFsaWROdW1iZXIoeCkgJiYgeCA+IDApOwogICAgICAgICAgICBsZXQgZmlsdGVyZWRWYWx1ZXMgPSBsZWdhbFZhbHVlczsKICAgICAgICAgICAgaWYgKHRoaXMuaWdub3JlT3V0bGllcigpKSB7CiAgICAgICAgICAgICAgICBjb25zdCBsb2dWYWx1ZXMgPSBsZWdhbFZhbHVlcy5tYXAobG9nJDQpOwogICAgICAgICAgICAgICAgY29uc3Qgc29ydGVkTG9nVmFsdWVzID0gbG9nVmFsdWVzLnNvcnQoKGEsIGIpID0+IGEgLSBiKTsKICAgICAgICAgICAgICAgIGNvbnN0IGEgPSB0aHJlc2hvbGQoc29ydGVkTG9nVmFsdWVzLCAwLjA1KTsKICAgICAgICAgICAgICAgIGNvbnN0IGIgPSB0aHJlc2hvbGQoc29ydGVkTG9nVmFsdWVzLCAwLjk1KTsKICAgICAgICAgICAgICAgIGZpbHRlcmVkVmFsdWVzID0gc29ydGVkTG9nVmFsdWVzLmZpbHRlcigoeCkgPT4geCA+PSBhICYmIHggPD0gYikubWFwKHBvdyQ0KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBleHRlbnQkMSA9IGV4dGVudChmaWx0ZXJlZFZhbHVlcyk7CiAgICAgICAgICAgIHJldHVybiBleHRlbnQkMVswXSA9PSBudWxsIHx8IGV4dGVudCQxWzFdID09IG51bGwgPyBbXSA6IGV4dGVudCQxOwogICAgICAgIH0KICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNsYXNzIERyYWdab29tTGF5ZXIgZXh0ZW5kcyBzcmMkMi5Db21wb25lbnRzLlNlbGVjdGlvbkJveExheWVyIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgU2VsZWN0aW9uQm94TGF5ZXIgd2l0aCBhbiBhdHRhY2hlZCBEcmFnSW50ZXJhY3Rpb24gYW5kCiAgICAgICAgICogQ2xpY2tJbnRlcmFjdGlvbi4gT24gZHJhZywgaXQgdHJpZ2dlcnMgYW4gYW5pbWF0ZWQgem9vbSBpbnRvIHRoZSBib3gKICAgICAgICAgKiB0aGF0IHdhcyBkcmFnZ2VkLiBPbiBkb3VibGUgY2xpY2ssIGl0IHpvb21zIGJhY2sgb3V0IHRvIHRoZSBvcmlnaW5hbAogICAgICAgICAqIHZpZXcsIGJlZm9yZSBhbnkgem9vbWluZy4KICAgICAgICAgKiBUaGUgem9vbSBhbmltYXRpb24gdXNlcyBhbiBlYXNpbmcgZnVuY3Rpb24gKGRlZmF1bHQKICAgICAgICAgKiBkMy5lYXNlKCdjdWJpYy1pbi1vdXQnKSkgYW5kIGlzIGN1c3RvbWl6YWJsZS4KICAgICAgICAgKiBVc2FnZTogQ29uc3RydWN0IHRoZSBzZWxlY3Rpb24gYm94IGxheWVyIGFuZCBhdHRhY2ggeCBhbmQgeSBzY2FsZXMsCiAgICAgICAgICogYW5kIHRoZW4gYWRkIHRoZSBsYXllciBvdmVyIHRoZSBwbG90IHlvdSBhcmUgem9vbWluZyBvbiB1c2luZyBhCiAgICAgICAgICogQ29tcG9uZW50IEdyb3VwLgogICAgICAgICAqIFRPRE8oQGRlY2VudHJhbGlvbikgLSBtZXJnZSB0aGlzIGludG8gUGxvdHRhYmxlCiAgICAgICAgICovCiAgICAgICAgY29uc3RydWN0b3IoeFNjYWxlLCB5U2NhbGUsIHVuem9vbU1ldGhvZCkgewogICAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgICB0aGlzLmVhc2VGbiA9IGN1YmljSW5PdXQ7CiAgICAgICAgICAgIHRoaXMuX2FuaW1hdGlvblRpbWUgPSA3NTA7CiAgICAgICAgICAgIHRoaXMueFNjYWxlKHhTY2FsZSk7CiAgICAgICAgICAgIHRoaXMueVNjYWxlKHlTY2FsZSk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdJbnRlcmFjdGlvbiA9IG5ldyBzcmMkMi5JbnRlcmFjdGlvbnMuRHJhZygpOwogICAgICAgICAgICB0aGlzLl9kb3VibGVDbGlja0ludGVyYWN0aW9uID0gbmV3IHNyYyQyLkludGVyYWN0aW9ucy5DbGljaygpOwogICAgICAgICAgICB0aGlzLnNldHVwQ2FsbGJhY2tzKCk7CiAgICAgICAgICAgIHRoaXMudW56b29tTWV0aG9kID0gdW56b29tTWV0aG9kOwogICAgICAgICAgICAvLyBBY3RpdmF0ZSBpbnRlcmFjdGlvbiBvbmx5IHdoZW4gdGhlIGNvbXBvbmVudCBpcyBtb3VudGVkIG9udG8gRE9NLgogICAgICAgICAgICB0aGlzLm9uRGV0YWNoKCgpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuX2RvdWJsZUNsaWNrSW50ZXJhY3Rpb24uZGV0YWNoRnJvbSh0aGlzKTsKICAgICAgICAgICAgICAgIHRoaXMuX2RyYWdJbnRlcmFjdGlvbi5kZXRhY2hGcm9tKHRoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5vbkFuY2hvcigoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9kb3VibGVDbGlja0ludGVyYWN0aW9uLmF0dGFjaFRvKHRoaXMpOwogICAgICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmF0dGFjaFRvKHRoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmVnaXN0ZXIgYSBtZXRob2QgdGhhdCBjYWxscyB3aGVuIHRoZSBEcmFnWm9vbSBpbnRlcmFjdGlvbiBzdGFydHMuCiAgICAgICAgICovCiAgICAgICAgaW50ZXJhY3Rpb25TdGFydChjYikgewogICAgICAgICAgICB0aGlzLm9uU3RhcnQgPSBjYjsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmVnaXN0ZXIgYSBtZXRob2QgdGhhdCBjYWxscyB3aGVuIHRoZSBEcmFnWm9vbSBpbnRlcmFjdGlvbiBlbmRzLgogICAgICAgICAqLwogICAgICAgIGludGVyYWN0aW9uRW5kKGNiKSB7CiAgICAgICAgICAgIHRoaXMub25FbmQgPSBjYjsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBiYWNraW5nIGRyYWcgaW50ZXJhY3Rpb24uIFVzZWZ1bCBmb3IgY3VzdG9taXphdGlvbiB0byB0aGUKICAgICAgICAgKiBpbnRlcmFjdGlvbi4KICAgICAgICAgKi8KICAgICAgICBkcmFnSW50ZXJhY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9kcmFnSW50ZXJhY3Rpb247CiAgICAgICAgfQogICAgICAgIHNldHVwQ2FsbGJhY2tzKCkgewogICAgICAgICAgICBsZXQgZHJhZ2dpbmcgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLm9uRHJhZ1N0YXJ0KChzdGFydFBvaW50KSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLmJvdW5kcyh7CiAgICAgICAgICAgICAgICAgICAgdG9wTGVmdDogc3RhcnRQb2ludCwKICAgICAgICAgICAgICAgICAgICBib3R0b21SaWdodDogc3RhcnRQb2ludCwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5vblN0YXJ0KCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24ub25EcmFnKChzdGFydFBvaW50LCBlbmRQb2ludCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5ib3VuZHMoeyB0b3BMZWZ0OiBzdGFydFBvaW50LCBib3R0b21SaWdodDogZW5kUG9pbnQgfSk7CiAgICAgICAgICAgICAgICB0aGlzLmJveFZpc2libGUodHJ1ZSk7CiAgICAgICAgICAgICAgICBkcmFnZ2luZyA9IHRydWU7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9kcmFnSW50ZXJhY3Rpb24ub25EcmFnRW5kKChzdGFydFBvaW50LCBlbmRQb2ludCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5ib3hWaXNpYmxlKGZhbHNlKTsKICAgICAgICAgICAgICAgIHRoaXMuYm91bmRzKHsgdG9wTGVmdDogc3RhcnRQb2ludCwgYm90dG9tUmlnaHQ6IGVuZFBvaW50IH0pOwogICAgICAgICAgICAgICAgaWYgKGRyYWdnaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgdGhpcy56b29tKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLm9uRW5kKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBkcmFnZ2luZyA9IGZhbHNlOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fZG91YmxlQ2xpY2tJbnRlcmFjdGlvbi5vbkRvdWJsZUNsaWNrKHRoaXMudW56b29tLmJpbmQodGhpcykpOwogICAgICAgIH0KICAgICAgICBhbmltYXRpb25UaW1lKGFuaW1hdGlvblRpbWUpIHsKICAgICAgICAgICAgaWYgKGFuaW1hdGlvblRpbWUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2FuaW1hdGlvblRpbWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGFuaW1hdGlvblRpbWUgPCAwKSB7CiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ2FuaW1hdGlvblRpbWUgY2Fubm90IGJlIG5lZ2F0aXZlJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fYW5pbWF0aW9uVGltZSA9IGFuaW1hdGlvblRpbWU7CiAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdGhlIGVhc2luZyBmdW5jdGlvbiwgd2hpY2ggZGV0ZXJtaW5lcyBob3cgdGhlIHpvb20gaW50ZXJwb2xhdGVzCiAgICAgICAgICogb3ZlciB0aW1lLgogICAgICAgICAqLwogICAgICAgIGVhc2UoZm4pIHsKICAgICAgICAgICAgaWYgKHR5cGVvZiBmbiAhPT0gJ2Z1bmN0aW9uJykgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdlYXNlIGZ1bmN0aW9uIG11c3QgYmUgYSBmdW5jdGlvbicpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChmbigwKSAhPT0gMCB8fCBmbigxKSAhPT0gMSkgewogICAgICAgICAgICAgICAgc3JjJDIuVXRpbHMuV2luZG93Lndhcm4oJ0Vhc2luZyBmdW5jdGlvbiBkb2VzIG5vdCBtYWludGFpbiBpbnZhcmlhbnQgJyArCiAgICAgICAgICAgICAgICAgICAgJ2YoMCk9PTAgJiYgZigxKT09MS4gQmFkIGJlaGF2aW9yIG1heSByZXN1bHQuJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5lYXNlRm4gPSBmbjsKICAgICAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgICAgfQogICAgICAgIC8vIFpvb20gaW50byBleHRlbnQgb2YgdGhlIHNlbGVjdGlvbiBib3ggYm91bmRzCiAgICAgICAgem9vbSgpIHsKICAgICAgICAgICAgbGV0IHgwID0gdGhpcy54RXh0ZW50KClbMF0udmFsdWVPZigpOwogICAgICAgICAgICBsZXQgeDEgPSB0aGlzLnhFeHRlbnQoKVsxXS52YWx1ZU9mKCk7CiAgICAgICAgICAgIGxldCB5MCA9IHRoaXMueUV4dGVudCgpWzFdLnZhbHVlT2YoKTsKICAgICAgICAgICAgbGV0IHkxID0gdGhpcy55RXh0ZW50KClbMF0udmFsdWVPZigpOwogICAgICAgICAgICBpZiAoeDAgPT09IHgxIHx8IHkwID09PSB5MSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuaW50ZXJwb2xhdGVab29tKHgwLCB4MSwgeTAsIHkxKTsKICAgICAgICB9CiAgICAgICAgLy8gUmVzdG9yZSB0aGUgc2NhbGVzIHRvIHRoZWlyIHN0YXRlIGJlZm9yZSBhbnkgem9vbQogICAgICAgIHVuem9vbSgpIHsKICAgICAgICAgICAgLy8gV2UgbmVlZCB0byByZXNldCB0aGUgem9vbSBkb21haW4gdW5jb25kaXRpb25hbGx5LCBhcyB0aGUgZGF0YSBvciB0aGUKICAgICAgICAgICAgLy8gc21vb3RoaW5nIG1heSBoYXZlIHVwZGF0ZWQsIHN1Y2ggdGhhdCB3ZSBhcmUgbm90IGxvbmdlciBmdWxseSB6b29tZWQgb3V0LgogICAgICAgICAgICBsZXQgeFNjYWxlID0gdGhpcy54U2NhbGUoKTsKICAgICAgICAgICAgeFNjYWxlLl9kb21haW5NaW4gPSBudWxsOwogICAgICAgICAgICB4U2NhbGUuX2RvbWFpbk1heCA9IG51bGw7CiAgICAgICAgICAgIGxldCB4RG9tYWluID0geFNjYWxlLl9nZXRFeHRlbnQoKTsKICAgICAgICAgICAgdGhpcy54U2NhbGUoKS5kb21haW4oeERvbWFpbik7CiAgICAgICAgICAgIHRoaXMudW56b29tTWV0aG9kKCk7CiAgICAgICAgfQogICAgICAgIC8vIElmIHdlIGFyZSB6b29taW5nLCBkaXNhYmxlIGludGVyYWN0aW9ucywgdG8gYXZvaWQgY29udGVudGlvbgogICAgICAgIGlzWm9vbWluZyhpc1pvb21pbmcpIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ0ludGVyYWN0aW9uLmVuYWJsZWQoIWlzWm9vbWluZyk7CiAgICAgICAgICAgIHRoaXMuX2RvdWJsZUNsaWNrSW50ZXJhY3Rpb24uZW5hYmxlZCghaXNab29taW5nKTsKICAgICAgICB9CiAgICAgICAgaW50ZXJwb2xhdGVab29tKHgwZiwgeDFmLCB5MGYsIHkxZikgewogICAgICAgICAgICBsZXQgeDBzID0gdGhpcy54U2NhbGUoKS5kb21haW4oKVswXS52YWx1ZU9mKCk7CiAgICAgICAgICAgIGxldCB4MXMgPSB0aGlzLnhTY2FsZSgpLmRvbWFpbigpWzFdLnZhbHVlT2YoKTsKICAgICAgICAgICAgbGV0IHkwcyA9IHRoaXMueVNjYWxlKCkuZG9tYWluKClbMF0udmFsdWVPZigpOwogICAgICAgICAgICBsZXQgeTFzID0gdGhpcy55U2NhbGUoKS5kb21haW4oKVsxXS52YWx1ZU9mKCk7CiAgICAgICAgICAgIC8vIENvcHkgYSByZWYgdG8gdGhlIGVhc2UgZm4sIHNvIHRoYXQgY2hhbmdpbmcgZWFzZSB3b250IGFmZmVjdCB6b29tcyBpbgogICAgICAgICAgICAvLyBwcm9ncmVzcy4KICAgICAgICAgICAgbGV0IGVhc2UgPSB0aGlzLmVhc2VGbjsKICAgICAgICAgICAgbGV0IGludGVycG9sYXRvciA9IChhLCBiLCBwKSA9PiBpbnRlcnBvbGF0ZU51bWJlcihhLCBiKShlYXNlKHApKTsKICAgICAgICAgICAgdGhpcy5pc1pvb21pbmcodHJ1ZSk7CiAgICAgICAgICAgIGxldCBzdGFydCA9IERhdGUubm93KCk7CiAgICAgICAgICAgIGxldCBkcmF3ID0gKCkgPT4gewogICAgICAgICAgICAgICAgbGV0IG5vdyA9IERhdGUubm93KCk7CiAgICAgICAgICAgICAgICBsZXQgcGFzc2VkID0gbm93IC0gc3RhcnQ7CiAgICAgICAgICAgICAgICBsZXQgcCA9IHRoaXMuX2FuaW1hdGlvblRpbWUgPT09IDAKICAgICAgICAgICAgICAgICAgICA/IDEKICAgICAgICAgICAgICAgICAgICA6IE1hdGgubWluKDEsIHBhc3NlZCAvIHRoaXMuX2FuaW1hdGlvblRpbWUpOwogICAgICAgICAgICAgICAgbGV0IHgwID0gaW50ZXJwb2xhdG9yKHgwcywgeDBmLCBwKTsKICAgICAgICAgICAgICAgIGxldCB4MSA9IGludGVycG9sYXRvcih4MXMsIHgxZiwgcCk7CiAgICAgICAgICAgICAgICBsZXQgeTAgPSBpbnRlcnBvbGF0b3IoeTBzLCB5MGYsIHApOwogICAgICAgICAgICAgICAgbGV0IHkxID0gaW50ZXJwb2xhdG9yKHkxcywgeTFmLCBwKTsKICAgICAgICAgICAgICAgIHRoaXMueFNjYWxlKCkuZG9tYWluKFt4MCwgeDFdKTsKICAgICAgICAgICAgICAgIHRoaXMueVNjYWxlKCkuZG9tYWluKFt5MCwgeTFdKTsKICAgICAgICAgICAgICAgIGlmIChwIDwgMSkgewogICAgICAgICAgICAgICAgICAgIHNyYyQyLlV0aWxzLkRPTS5yZXF1ZXN0QW5pbWF0aW9uRnJhbWVQb2x5ZmlsbChkcmF3KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHRoaXMub25FbmQoKTsKICAgICAgICAgICAgICAgICAgICB0aGlzLmlzWm9vbWluZyhmYWxzZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGRyYXcoKTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTggVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICB2YXIgU3RhdGU7CiAgICAoZnVuY3Rpb24gKFN0YXRlKSB7CiAgICAgICAgU3RhdGVbU3RhdGVbIk5PTkUiXSA9IDBdID0gIk5PTkUiOwogICAgICAgIFN0YXRlW1N0YXRlWyJEUkFHX1pPT01JTkciXSA9IDFdID0gIkRSQUdfWk9PTUlORyI7CiAgICAgICAgU3RhdGVbU3RhdGVbIlBBTk5JTkciXSA9IDJdID0gIlBBTk5JTkciOwogICAgfSkoU3RhdGUgfHwgKFN0YXRlID0ge30pKTsKICAgIGNsYXNzIFBhblpvb21EcmFnTGF5ZXIgZXh0ZW5kcyBzcmMkMi5Db21wb25lbnRzLkdyb3VwIHsKICAgICAgICAvKioKICAgICAgICAgKiBBIFBsb3R0YWJsZSBjb21wb25lbnQvbGF5ZXIgd2l0aCBhIGNvbXBsZXggaW50ZXJhY3Rpb24gZm9yIHRoZSBsaW5lIGNoYXJ0LgogICAgICAgICAqIFdoZW4gbm90IHByZXNzaW5nIGFsdC1rZXksIGl0IGJlaGF2ZXMgbGlrZSBEcmFnWm9vbUxheWVyIC0tIGRyYWdnaW5nIGEKICAgICAgICAgKiByZWdpb24gem9vbXMgdGhlIGFyZWEgdW5kZXIgdGhlIGdyYXkgYm94IGFuZCBkb3VibGUgY2xpY2tpbmcgcmVzZXRzIHRoZQogICAgICAgICAqIHpvb20uIFdoZW4gcHJlc3NpbmcgYWx0LWtleSwgaXQgbGV0cyB1c2VyIHBhbiBhcm91bmQgd2hpbGUgaGF2aW5nIG1vdXNlZG93bgogICAgICAgICAqIG9uIHRoZSBjaGFydCBhbmQgbGV0IHVzZXIgem9vbS1pbi9vdXQgb2YgY3Vyc29yIHdoZW4gc2Nyb2xsIHdpdGggYWx0IGtleQogICAgICAgICAqIHByZXNzZWQuCiAgICAgICAgICovCiAgICAgICAgY29uc3RydWN0b3IoeFNjYWxlLCB5U2NhbGUsIHVuem9vbU1ldGhvZCkgewogICAgICAgICAgICBzdXBlcigpOwogICAgICAgICAgICB0aGlzLnN0YXRlID0gU3RhdGUuTk9ORTsKICAgICAgICAgICAgdGhpcy5wYW5TdGFydENhbGxiYWNrID0gbmV3IHNyYyQyLlV0aWxzLkNhbGxiYWNrU2V0KCk7CiAgICAgICAgICAgIHRoaXMucGFuRW5kQ2FsbGJhY2sgPSBuZXcgc3JjJDIuVXRpbHMuQ2FsbGJhY2tTZXQoKTsKICAgICAgICAgICAgdGhpcy5wYW5ab29tID0gbmV3IHNyYyQyLkludGVyYWN0aW9ucy5QYW5ab29tKHhTY2FsZSwgeVNjYWxlKTsKICAgICAgICAgICAgdGhpcy5wYW5ab29tLmRyYWdJbnRlcmFjdGlvbigpLm1vdXNlRmlsdGVyKChldmVudCkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuIFBhblpvb21EcmFnTGF5ZXIuaXNQYW5LZXkoZXZlbnQpICYmIGV2ZW50LmJ1dHRvbiA9PT0gMDsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMucGFuWm9vbS53aGVlbEZpbHRlcih0aGlzLmNhblNjcm9sbFpvb20pOwogICAgICAgICAgICB0aGlzLmRyYWdab29tTGF5ZXIgPSBuZXcgRHJhZ1pvb21MYXllcih4U2NhbGUsIHlTY2FsZSwgdW56b29tTWV0aG9kKTsKICAgICAgICAgICAgdGhpcy5kcmFnWm9vbUxheWVyLmRyYWdJbnRlcmFjdGlvbigpLm1vdXNlRmlsdGVyKChldmVudCkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuICFQYW5ab29tRHJhZ0xheWVyLmlzUGFuS2V5KGV2ZW50KSAmJiBldmVudC5idXR0b24gPT09IDA7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLmFwcGVuZCh0aGlzLmRyYWdab29tTGF5ZXIpOwogICAgICAgICAgICBjb25zdCBvbldoZWVsID0gdGhpcy5vbldoZWVsLmJpbmQodGhpcyk7CiAgICAgICAgICAgIHRoaXMub25BbmNob3IoKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5fbW91c2VEaXNwYXRjaGVyID0gc3JjJDIuRGlzcGF0Y2hlcnMuTW91c2UuZ2V0RGlzcGF0Y2hlcih0aGlzKTsKICAgICAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vbldoZWVsKG9uV2hlZWwpOwogICAgICAgICAgICAgICAgdGhpcy5wYW5ab29tLmF0dGFjaFRvKHRoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5vbkRldGFjaCgoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLnBhblpvb20uZGV0YWNoRnJvbSh0aGlzKTsKICAgICAgICAgICAgICAgIC8vIG9uRGV0YWNoIGNhbiBiZSBpbnZva2VkIGJlZm9yZSBvbkFuY2hvcgogICAgICAgICAgICAgICAgaWYgKHRoaXMuX21vdXNlRGlzcGF0Y2hlcikgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX21vdXNlRGlzcGF0Y2hlci5vZmZXaGVlbChvbldoZWVsKTsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9tb3VzZURpc3BhdGNoZXIgPSBudWxsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5wYW5ab29tLmRyYWdJbnRlcmFjdGlvbigpLm9uRHJhZ1N0YXJ0KCgpID0+IHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLnN0YXRlID09IFN0YXRlLk5PTkUpCiAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXRTdGF0ZShTdGF0ZS5QQU5OSU5HKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMucGFuWm9vbS5kcmFnSW50ZXJhY3Rpb24oKS5vbkRyYWdFbmQoKCkgPT4gewogICAgICAgICAgICAgICAgaWYgKHRoaXMuc3RhdGUgPT0gU3RhdGUuUEFOTklORykKICAgICAgICAgICAgICAgICAgICB0aGlzLnNldFN0YXRlKFN0YXRlLk5PTkUpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5kcmFnWm9vbUxheWVyLmRyYWdJbnRlcmFjdGlvbigpLm9uRHJhZ1N0YXJ0KCgpID0+IHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLnN0YXRlID09IFN0YXRlLk5PTkUpCiAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXRTdGF0ZShTdGF0ZS5EUkFHX1pPT01JTkcpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5kcmFnWm9vbUxheWVyLmRyYWdJbnRlcmFjdGlvbigpLm9uRHJhZ0VuZCgoKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5zdGF0ZSA9PSBTdGF0ZS5EUkFHX1pPT01JTkcpCiAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXRTdGF0ZShTdGF0ZS5OT05FKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIG9uV2hlZWwoXywgZXZlbnQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuY2FuU2Nyb2xsWm9vbShldmVudCkpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIGNvbnN0IGhlbHBDb250YWluZXIgPSB0aGlzLmVsZW1lbnQoKTsKICAgICAgICAgICAgaWYgKCFoZWxwQ29udGFpbmVyLnNlbGVjdCgnLmhlbHAnKS5lbXB0eSgpKQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICBjb25zdCBoZWxwID0gaGVscENvbnRhaW5lci5hcHBlbmQoJ2RpdicpLmNsYXNzZWQoJ2hlbHAnLCB0cnVlKTsKICAgICAgICAgICAgaGVscC5hcHBlbmQoJ3NwYW4nKS50ZXh0KCdBbHQgKyBTY3JvbGwgdG8gWm9vbScpOwogICAgICAgICAgICAvLyBQbGVhc2Ugc2VlIHZ6LXBhbi16b29tLXN0eWxlIGZvciB0aGUgZGVmaW5pdGlvbiBvZiB0aGUgYW5pbWF0aW9uLgogICAgICAgICAgICBoZWxwLm9uKCdhbmltYXRpb25lbmQnLCAoKSA9PiB2b2lkIGhlbHAucmVtb3ZlKCkpOwogICAgICAgIH0KICAgICAgICBzdGF0aWMgaXNQYW5LZXkoZXZlbnQpIHsKICAgICAgICAgICAgcmV0dXJuIEJvb2xlYW4oZXZlbnQuYWx0S2V5KSB8fCBCb29sZWFuKGV2ZW50LnNoaWZ0S2V5KTsKICAgICAgICB9CiAgICAgICAgY2FuU2Nyb2xsWm9vbShldmVudCkgewogICAgICAgICAgICByZXR1cm4gZXZlbnQuYWx0S2V5OwogICAgICAgIH0KICAgICAgICBzZXRTdGF0ZShuZXh0U3RhdGUpIHsKICAgICAgICAgICAgaWYgKHRoaXMuc3RhdGUgPT0gbmV4dFN0YXRlKQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICBjb25zdCBwcmV2U3RhdGUgPSB0aGlzLnN0YXRlOwogICAgICAgICAgICB0aGlzLnN0YXRlID0gbmV4dFN0YXRlOwogICAgICAgICAgICB0aGlzLnJvb3QoKS5yZW1vdmVDbGFzcyh0aGlzLnN0YXRlQ2xhc3NOYW1lKHByZXZTdGF0ZSkpOwogICAgICAgICAgICB0aGlzLnJvb3QoKS5hZGRDbGFzcyh0aGlzLnN0YXRlQ2xhc3NOYW1lKG5leHRTdGF0ZSkpOwogICAgICAgICAgICBpZiAocHJldlN0YXRlID09IFN0YXRlLlBBTk5JTkcpIHsKICAgICAgICAgICAgICAgIHRoaXMucGFuRW5kQ2FsbGJhY2suY2FsbENhbGxiYWNrcygpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChuZXh0U3RhdGUgPT0gU3RhdGUuUEFOTklORykgewogICAgICAgICAgICAgICAgdGhpcy5wYW5TdGFydENhbGxiYWNrLmNhbGxDYWxsYmFja3MoKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBzdGF0ZUNsYXNzTmFtZShzdGF0ZSkgewogICAgICAgICAgICBzd2l0Y2ggKHN0YXRlKSB7CiAgICAgICAgICAgICAgICBjYXNlIFN0YXRlLlBBTk5JTkc6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICdwYW5uaW5nJzsKICAgICAgICAgICAgICAgIGNhc2UgU3RhdGUuRFJBR19aT09NSU5HOgogICAgICAgICAgICAgICAgICAgIHJldHVybiAnZHJhZy16b29taW5nJzsKICAgICAgICAgICAgICAgIGNhc2UgU3RhdGUuTk9ORToKICAgICAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIG9uUGFuU3RhcnQoY2IpIHsKICAgICAgICAgICAgdGhpcy5wYW5TdGFydENhbGxiYWNrLmFkZChjYik7CiAgICAgICAgfQogICAgICAgIG9uUGFuRW5kKGNiKSB7CiAgICAgICAgICAgIHRoaXMucGFuRW5kQ2FsbGJhY2suYWRkKGNiKTsKICAgICAgICB9CiAgICAgICAgb25TY3JvbGxab29tKGNiKSB7CiAgICAgICAgICAgIHRoaXMucGFuWm9vbS5vblpvb21FbmQoY2IpOwogICAgICAgIH0KICAgICAgICBvbkRyYWdab29tU3RhcnQoY2IpIHsKICAgICAgICAgICAgdGhpcy5kcmFnWm9vbUxheWVyLmludGVyYWN0aW9uU3RhcnQoY2IpOwogICAgICAgIH0KICAgICAgICBvbkRyYWdab29tRW5kKGNiKSB7CiAgICAgICAgICAgIHRoaXMuZHJhZ1pvb21MYXllci5pbnRlcmFjdGlvbkVuZChjYik7CiAgICAgICAgfQogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE4IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgdmFyIFRvb2x0aXBDb2x1bW5FdmFsVHlwZTsKICAgIChmdW5jdGlvbiAoVG9vbHRpcENvbHVtbkV2YWxUeXBlKSB7CiAgICAgICAgVG9vbHRpcENvbHVtbkV2YWxUeXBlW1Rvb2x0aXBDb2x1bW5FdmFsVHlwZVsiVEVYVCJdID0gMF0gPSAiVEVYVCI7CiAgICAgICAgVG9vbHRpcENvbHVtbkV2YWxUeXBlW1Rvb2x0aXBDb2x1bW5FdmFsVHlwZVsiRE9NIl0gPSAxXSA9ICJET00iOwogICAgfSkoVG9vbHRpcENvbHVtbkV2YWxUeXBlIHx8IChUb29sdGlwQ29sdW1uRXZhbFR5cGUgPSB7fSkpOwogICAgdmFyIFlTY2FsZVR5cGU7CiAgICAoZnVuY3Rpb24gKFlTY2FsZVR5cGUpIHsKICAgICAgICBZU2NhbGVUeXBlWyJMT0ciXSA9ICJsb2ciOwogICAgICAgIFlTY2FsZVR5cGVbIkxJTkVBUiJdID0gImxpbmVhciI7CiAgICB9KShZU2NhbGVUeXBlIHx8IChZU2NhbGVUeXBlID0ge30pKTsKICAgIC8qKgogICAgICogVGhlIG1heGltdW0gbnVtYmVyIG9mIG1hcmtlciBzeW1ib2xzIHdpdGhpbiBhbnkgbGluZSBmb3IgYSBkYXRhIHNlcmllcy4gVG9vCiAgICAgKiBtYW55IG1hcmtlcnMgY2x1dHRlciB0aGUgY2hhcnQuCiAgICAgKi8KICAgIGNvbnN0IF9NQVhfTUFSS0VSUyA9IDIwOwogICAgY2xhc3MgTGluZUNoYXJ0IHsKICAgICAgICBjb25zdHJ1Y3Rvcih4Q29tcG9uZW50c0NyZWF0aW9uTWV0aG9kLCB5VmFsdWVBY2Nlc3NvciwgeVNjYWxlVHlwZSwgY29sb3JTY2FsZSwgdG9vbHRpcCwgLy8gVnpDaGFydFRvb2x0aXAKICAgICAgICB0b29sdGlwQ29sdW1ucywgZmlsbEFyZWEsIGRlZmF1bHRYUmFuZ2UsIGRlZmF1bHRZUmFuZ2UsIHN5bWJvbEZ1bmN0aW9uLCB4QXhpc0Zvcm1hdHRlcikgewogICAgICAgICAgICB0aGlzLmRpcnR5RGF0YXNldHMgPSBuZXcgU2V0KCk7CiAgICAgICAgICAgIHRoaXMuc2VyaWVzTmFtZXMgPSBbXTsKICAgICAgICAgICAgdGhpcy5uYW1lMmRhdGFzZXRzID0ge307CiAgICAgICAgICAgIHRoaXMuY29sb3JTY2FsZSA9IGNvbG9yU2NhbGU7CiAgICAgICAgICAgIHRoaXMudG9vbHRpcCA9IHRvb2x0aXA7CiAgICAgICAgICAgIHRoaXMuZGF0YXNldHMgPSBbXTsKICAgICAgICAgICAgdGhpcy5faWdub3JlWU91dGxpZXJzID0gZmFsc2U7CiAgICAgICAgICAgIC8vIGxhc3RQb2ludERhdGFzZXQgaXMgYSBkYXRhc2V0IHRoYXQgY29udGFpbnMganVzdCB0aGUgbGFzdCBwb2ludCBvZgogICAgICAgICAgICAvLyBldmVyeSBkYXRhc2V0IHdlJ3JlIGN1cnJlbnRseSBkcmF3aW5nLgogICAgICAgICAgICB0aGlzLmxhc3RQb2ludHNEYXRhc2V0ID0gbmV3IHNyYyQyLkRhdGFzZXQoKTsKICAgICAgICAgICAgdGhpcy5uYW5EYXRhc2V0ID0gbmV3IHNyYyQyLkRhdGFzZXQoKTsKICAgICAgICAgICAgdGhpcy55VmFsdWVBY2Nlc3NvciA9IHlWYWx1ZUFjY2Vzc29yOwogICAgICAgICAgICAvLyBUaGUgc3ltYm9sIGZ1bmN0aW9uIG1hcHMgc2VyaWVzIHRvIG1hcmtlci4gSXQgdXNlcyBhIHNwZWNpYWwgZGF0YXNldCB0aGF0CiAgICAgICAgICAgIC8vIHZhcmllcyBiYXNlZCBvbiB3aGV0aGVyIHNtb290aGluZyBpcyBlbmFibGVkLgogICAgICAgICAgICB0aGlzLnN5bWJvbEZ1bmN0aW9uID0gc3ltYm9sRnVuY3Rpb247CiAgICAgICAgICAgIHRoaXMuX2RlZmF1bHRYUmFuZ2UgPSBkZWZhdWx0WFJhbmdlOwogICAgICAgICAgICB0aGlzLl9kZWZhdWx0WVJhbmdlID0gZGVmYXVsdFlSYW5nZTsKICAgICAgICAgICAgdGhpcy50b29sdGlwQ29sdW1ucyA9IHRvb2x0aXBDb2x1bW5zOwogICAgICAgICAgICB0aGlzLmJ1aWxkQ2hhcnQoeENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZCwgeVZhbHVlQWNjZXNzb3IsIHlTY2FsZVR5cGUsIGZpbGxBcmVhLCB4QXhpc0Zvcm1hdHRlcik7CiAgICAgICAgfQogICAgICAgIGJ1aWxkQ2hhcnQoeENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZCwgeVZhbHVlQWNjZXNzb3IsIHlTY2FsZVR5cGUsIGZpbGxBcmVhLCB4QXhpc0Zvcm1hdHRlcikgewogICAgICAgICAgICB0aGlzLmRlc3Ryb3koKTsKICAgICAgICAgICAgY29uc3QgeENvbXBvbmVudHMgPSB4Q29tcG9uZW50c0NyZWF0aW9uTWV0aG9kKCk7CiAgICAgICAgICAgIHRoaXMueEFjY2Vzc29yID0geENvbXBvbmVudHMuYWNjZXNzb3I7CiAgICAgICAgICAgIHRoaXMueFNjYWxlID0geENvbXBvbmVudHMuc2NhbGU7CiAgICAgICAgICAgIHRoaXMueEF4aXMgPSB4Q29tcG9uZW50cy5heGlzOwogICAgICAgICAgICB0aGlzLnhBeGlzLm1hcmdpbigwKS50aWNrTGFiZWxQYWRkaW5nKDMpOwogICAgICAgICAgICBpZiAoeEF4aXNGb3JtYXR0ZXIpIHsKICAgICAgICAgICAgICAgIHRoaXMueEF4aXMuZm9ybWF0dGVyKHhBeGlzRm9ybWF0dGVyKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLnlTY2FsZSA9IExpbmVDaGFydC5nZXRZU2NhbGVGcm9tVHlwZSh5U2NhbGVUeXBlKTsKICAgICAgICAgICAgdGhpcy55U2NhbGUuc2V0VmFsdWVQcm92aWRlckZvckRvbWFpbigoKSA9PiB0aGlzLmdldFZhbHVlc0ZvcllBeGlzRG9tYWluQ29tcHV0ZSgpKTsKICAgICAgICAgICAgdGhpcy55QXhpcyA9IG5ldyBzcmMkMi5BeGVzLk51bWVyaWModGhpcy55U2NhbGUsICdsZWZ0Jyk7CiAgICAgICAgICAgIGxldCB5Rm9ybWF0dGVyID0gbXVsdGlzY2FsZUZvcm1hdHRlcihZX0FYSVNfRk9STUFUVEVSX1BSRUNJU0lPTik7CiAgICAgICAgICAgIHRoaXMueUF4aXMubWFyZ2luKDApCiAgICAgICAgICAgICAgICAudGlja0xhYmVsUGFkZGluZyg1KQogICAgICAgICAgICAgICAgLmZvcm1hdHRlcih5Rm9ybWF0dGVyKTsKICAgICAgICAgICAgdGhpcy55QXhpcy51c2VzVGV4dFdpZHRoQXBwcm94aW1hdGlvbih0cnVlKTsKICAgICAgICAgICAgdGhpcy5maWxsQXJlYSA9IGZpbGxBcmVhOwogICAgICAgICAgICBjb25zdCBwYW5ab29tTGF5ZXIgPSBuZXcgUGFuWm9vbURyYWdMYXllcih0aGlzLnhTY2FsZSwgdGhpcy55U2NhbGUsICgpID0+IHRoaXMucmVzZXREb21haW4oKSk7CiAgICAgICAgICAgIHRoaXMudG9vbHRpcEludGVyYWN0aW9uID0gdGhpcy5jcmVhdGVUb29sdGlwSW50ZXJhY3Rpb24ocGFuWm9vbUxheWVyKTsKICAgICAgICAgICAgdGhpcy50b29sdGlwUG9pbnRzQ29tcG9uZW50ID0gbmV3IHNyYyQyLkNvbXBvbmVudCgpOwogICAgICAgICAgICBjb25zdCBwbG90ID0gdGhpcy5idWlsZFBsb3QodGhpcy54U2NhbGUsIHRoaXMueVNjYWxlLCBmaWxsQXJlYSk7CiAgICAgICAgICAgIHRoaXMuZ3JpZGxpbmVzID0gbmV3IHNyYyQyLkNvbXBvbmVudHMuR3JpZGxpbmVzKHRoaXMueFNjYWxlLCB0aGlzLnlTY2FsZSk7CiAgICAgICAgICAgIGxldCB4WmVyb0xpbmUgPSBudWxsOwogICAgICAgICAgICBpZiAoeVNjYWxlVHlwZSAhPT0gWVNjYWxlVHlwZS5MT0cpIHsKICAgICAgICAgICAgICAgIHhaZXJvTGluZSA9IG5ldyBzcmMkMi5Db21wb25lbnRzLkd1aWRlTGluZUxheWVyKCdob3Jpem9udGFsJyk7CiAgICAgICAgICAgICAgICB4WmVyb0xpbmUuc2NhbGUodGhpcy55U2NhbGUpLnZhbHVlKDApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCB5WmVyb0xpbmUgPSBuZXcgc3JjJDIuQ29tcG9uZW50cy5HdWlkZUxpbmVMYXllcigndmVydGljYWwnKTsKICAgICAgICAgICAgeVplcm9MaW5lLnNjYWxlKHRoaXMueFNjYWxlKS52YWx1ZSgwKTsKICAgICAgICAgICAgdGhpcy5jZW50ZXIgPSBuZXcgc3JjJDIuQ29tcG9uZW50cy5Hcm91cChbCiAgICAgICAgICAgICAgICB0aGlzLmdyaWRsaW5lcywKICAgICAgICAgICAgICAgIHhaZXJvTGluZSwKICAgICAgICAgICAgICAgIHlaZXJvTGluZSwKICAgICAgICAgICAgICAgIHBsb3QsCiAgICAgICAgICAgICAgICB0aGlzLnRvb2x0aXBQb2ludHNDb21wb25lbnQsCiAgICAgICAgICAgICAgICBwYW5ab29tTGF5ZXIsCiAgICAgICAgICAgIF0pOwogICAgICAgICAgICB0aGlzLmNlbnRlci5hZGRDbGFzcygnbWFpbicpOwogICAgICAgICAgICB0aGlzLm91dGVyID0gbmV3IHNyYyQyLkNvbXBvbmVudHMuVGFibGUoWwogICAgICAgICAgICAgICAgW3RoaXMueUF4aXMsIHRoaXMuY2VudGVyXSwKICAgICAgICAgICAgICAgIFtudWxsLCB0aGlzLnhBeGlzXSwKICAgICAgICAgICAgXSk7CiAgICAgICAgfQogICAgICAgIGJ1aWxkUGxvdCh4U2NhbGUsIHlTY2FsZSwgZmlsbEFyZWEpIHsKICAgICAgICAgICAgaWYgKGZpbGxBcmVhKSB7CiAgICAgICAgICAgICAgICB0aGlzLm1hcmdpbkFyZWFQbG90ID0gbmV3IHNyYyQyLlBsb3RzLkFyZWEoKTsKICAgICAgICAgICAgICAgIHRoaXMubWFyZ2luQXJlYVBsb3QueCh0aGlzLnhBY2Nlc3NvciwgeFNjYWxlKTsKICAgICAgICAgICAgICAgIHRoaXMubWFyZ2luQXJlYVBsb3QueShmaWxsQXJlYS5oaWdoZXJBY2Nlc3NvciwgeVNjYWxlKTsKICAgICAgICAgICAgICAgIHRoaXMubWFyZ2luQXJlYVBsb3QueTAoZmlsbEFyZWEubG93ZXJBY2Nlc3Nvcik7CiAgICAgICAgICAgICAgICB0aGlzLm1hcmdpbkFyZWFQbG90LmF0dHIoJ2ZpbGwnLCAoZCwgaSwgZGF0YXNldCkgPT4gdGhpcy5jb2xvclNjYWxlLnNjYWxlKGRhdGFzZXQubWV0YWRhdGEoKS5uYW1lKSk7CiAgICAgICAgICAgICAgICB0aGlzLm1hcmdpbkFyZWFQbG90LmF0dHIoJ2ZpbGwtb3BhY2l0eScsIDAuMyk7CiAgICAgICAgICAgICAgICB0aGlzLm1hcmdpbkFyZWFQbG90LmF0dHIoJ3N0cm9rZS13aWR0aCcsIDApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuc21vb3RoZWRBY2Nlc3NvciA9IChkKSA9PiBkLnNtb290aGVkOwogICAgICAgICAgICBsZXQgbGluZVBsb3QgPSBuZXcgc3JjJDIuUGxvdHMuTGluZSgpOwogICAgICAgICAgICBsaW5lUGxvdC54KHRoaXMueEFjY2Vzc29yLCB4U2NhbGUpOwogICAgICAgICAgICBsaW5lUGxvdC55KHRoaXMueVZhbHVlQWNjZXNzb3IsIHlTY2FsZSk7CiAgICAgICAgICAgIGxpbmVQbG90LmF0dHIoJ3N0cm9rZScsIChkLCBpLCBkYXRhc2V0KSA9PiB0aGlzLmNvbG9yU2NhbGUuc2NhbGUoZGF0YXNldC5tZXRhZGF0YSgpLm5hbWUpKTsKICAgICAgICAgICAgdGhpcy5saW5lUGxvdCA9IGxpbmVQbG90OwogICAgICAgICAgICB0aGlzLnNldHVwVG9vbHRpcHMobGluZVBsb3QpOwogICAgICAgICAgICBsZXQgc21vb3RoTGluZVBsb3QgPSBuZXcgc3JjJDIuUGxvdHMuTGluZSgpOwogICAgICAgICAgICBzbW9vdGhMaW5lUGxvdC54KHRoaXMueEFjY2Vzc29yLCB4U2NhbGUpOwogICAgICAgICAgICBzbW9vdGhMaW5lUGxvdC55KHRoaXMuc21vb3RoZWRBY2Nlc3NvciwgeVNjYWxlKTsKICAgICAgICAgICAgc21vb3RoTGluZVBsb3QuYXR0cignc3Ryb2tlJywgKGQsIGksIGRhdGFzZXQpID0+IHRoaXMuY29sb3JTY2FsZS5zY2FsZShkYXRhc2V0Lm1ldGFkYXRhKCkubmFtZSkpOwogICAgICAgICAgICB0aGlzLnNtb290aExpbmVQbG90ID0gc21vb3RoTGluZVBsb3Q7CiAgICAgICAgICAgIGlmICh0aGlzLnN5bWJvbEZ1bmN0aW9uKSB7CiAgICAgICAgICAgICAgICBjb25zdCBtYXJrZXJzU2NhdHRlclBsb3QgPSBuZXcgc3JjJDIuUGxvdHMuU2NhdHRlcigpOwogICAgICAgICAgICAgICAgbWFya2Vyc1NjYXR0ZXJQbG90LngodGhpcy54QWNjZXNzb3IsIHhTY2FsZSk7CiAgICAgICAgICAgICAgICBtYXJrZXJzU2NhdHRlclBsb3QueSh0aGlzLnlWYWx1ZUFjY2Vzc29yLCB5U2NhbGUpOwogICAgICAgICAgICAgICAgbWFya2Vyc1NjYXR0ZXJQbG90LmF0dHIoJ2ZpbGwnLCAoZCwgaSwgZGF0YXNldCkgPT4gdGhpcy5jb2xvclNjYWxlLnNjYWxlKGRhdGFzZXQubWV0YWRhdGEoKS5uYW1lKSk7CiAgICAgICAgICAgICAgICBtYXJrZXJzU2NhdHRlclBsb3QuYXR0cignb3BhY2l0eScsIDEpOwogICAgICAgICAgICAgICAgbWFya2Vyc1NjYXR0ZXJQbG90LnNpemUoVE9PTFRJUF9DSVJDTEVfU0laRSAqIDIpOwogICAgICAgICAgICAgICAgbWFya2Vyc1NjYXR0ZXJQbG90LnN5bWJvbCgoZCwgaSwgZGF0YXNldCkgPT4gewogICAgICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLnN5bWJvbEZ1bmN0aW9uKGRhdGFzZXQubWV0YWRhdGEoKS5uYW1lKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgLy8gVXNlIGEgc3BlY2lhbCBkYXRhc2V0IGJlY2F1c2UgdGhpcyBzY2F0dGVyIHBsb3Qgc2hvdWxkIHVzZSB0aGUgYWNjZXNvcgogICAgICAgICAgICAgICAgLy8gdGhhdCBkZXBlbmRzIG9uIHdoZXRoZXIgc21vb3RoaW5nIGlzIGVuYWJsZWQuCiAgICAgICAgICAgICAgICB0aGlzLm1hcmtlcnNTY2F0dGVyUGxvdCA9IG1hcmtlcnNTY2F0dGVyUGxvdDsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBUaGUgc2NhdHRlclBsb3Qgd2lsbCBkaXNwbGF5IHRoZSBsYXN0IHBvaW50IGZvciBlYWNoIGRhdGFzZXQuCiAgICAgICAgICAgIC8vIFRoaXMgd2F5LCBpZiB0aGVyZSBpcyBvbmx5IG9uZSBkYXR1bSBmb3IgdGhlIHNlcmllcywgaXQgaXMgc3RpbGwKICAgICAgICAgICAgLy8gdmlzaWJsZS4gV2UgaGlkZSBpdCB3aGVuIHRvb2x0aXBzIGFyZSBhY3RpdmUgdG8ga2VlcCB0aGluZ3MgY2xlYW4uCiAgICAgICAgICAgIGxldCBzY2F0dGVyUGxvdCA9IG5ldyBzcmMkMi5QbG90cy5TY2F0dGVyKCk7CiAgICAgICAgICAgIHNjYXR0ZXJQbG90LngodGhpcy54QWNjZXNzb3IsIHhTY2FsZSk7CiAgICAgICAgICAgIHNjYXR0ZXJQbG90LnkodGhpcy55VmFsdWVBY2Nlc3NvciwgeVNjYWxlKTsKICAgICAgICAgICAgc2NhdHRlclBsb3QuYXR0cignZmlsbCcsIChkKSA9PiB0aGlzLmNvbG9yU2NhbGUuc2NhbGUoZC5uYW1lKSk7CiAgICAgICAgICAgIHNjYXR0ZXJQbG90LmF0dHIoJ29wYWNpdHknLCAxKTsKICAgICAgICAgICAgc2NhdHRlclBsb3Quc2l6ZShUT09MVElQX0NJUkNMRV9TSVpFICogMik7CiAgICAgICAgICAgIHNjYXR0ZXJQbG90LmRhdGFzZXRzKFt0aGlzLmxhc3RQb2ludHNEYXRhc2V0XSk7CiAgICAgICAgICAgIHRoaXMuc2NhdHRlclBsb3QgPSBzY2F0dGVyUGxvdDsKICAgICAgICAgICAgbGV0IG5hbkRpc3BsYXkgPSBuZXcgc3JjJDIuUGxvdHMuU2NhdHRlcigpOwogICAgICAgICAgICBuYW5EaXNwbGF5LngodGhpcy54QWNjZXNzb3IsIHhTY2FsZSk7CiAgICAgICAgICAgIG5hbkRpc3BsYXkueSgoeCkgPT4geC5kaXNwbGF5WSwgeVNjYWxlKTsKICAgICAgICAgICAgbmFuRGlzcGxheS5hdHRyKCdmaWxsJywgKGQpID0+IHRoaXMuY29sb3JTY2FsZS5zY2FsZShkLm5hbWUpKTsKICAgICAgICAgICAgbmFuRGlzcGxheS5hdHRyKCdvcGFjaXR5JywgMSk7CiAgICAgICAgICAgIG5hbkRpc3BsYXkuc2l6ZShOQU5fU1lNQk9MX1NJWkUgKiAyKTsKICAgICAgICAgICAgbmFuRGlzcGxheS5kYXRhc2V0cyhbdGhpcy5uYW5EYXRhc2V0XSk7CiAgICAgICAgICAgIG5hbkRpc3BsYXkuc3ltYm9sKHNyYyQyLlN5bWJvbEZhY3Rvcmllcy50cmlhbmdsZSk7CiAgICAgICAgICAgIHRoaXMubmFuRGlzcGxheSA9IG5hbkRpc3BsYXk7CiAgICAgICAgICAgIGNvbnN0IGdyb3VwcyA9IFtuYW5EaXNwbGF5LCBzY2F0dGVyUGxvdCwgc21vb3RoTGluZVBsb3QsIGxpbmVQbG90XTsKICAgICAgICAgICAgaWYgKHRoaXMubWFyZ2luQXJlYVBsb3QpIHsKICAgICAgICAgICAgICAgIGdyb3Vwcy5wdXNoKHRoaXMubWFyZ2luQXJlYVBsb3QpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLm1hcmtlcnNTY2F0dGVyUGxvdCkgewogICAgICAgICAgICAgICAgZ3JvdXBzLnB1c2godGhpcy5tYXJrZXJzU2NhdHRlclBsb3QpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBuZXcgc3JjJDIuQ29tcG9uZW50cy5Hcm91cChncm91cHMpOwogICAgICAgIH0KICAgICAgICBpZ25vcmVZT3V0bGllcnMoaWdub3JlWU91dGxpZXJzKSB7CiAgICAgICAgICAgIGlmIChpZ25vcmVZT3V0bGllcnMgIT09IHRoaXMuX2lnbm9yZVlPdXRsaWVycykgewogICAgICAgICAgICAgICAgdGhpcy5faWdub3JlWU91dGxpZXJzID0gaWdub3JlWU91dGxpZXJzOwogICAgICAgICAgICAgICAgdGhpcy51cGRhdGVTcGVjaWFsRGF0YXNldHMoKTsKICAgICAgICAgICAgICAgIHRoaXMueVNjYWxlLmlnbm9yZU91dGxpZXIoaWdub3JlWU91dGxpZXJzKTsKICAgICAgICAgICAgICAgIHRoaXMucmVzZXRZRG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgZ2V0VmFsdWVzRm9yWUF4aXNEb21haW5Db21wdXRlKCkgewogICAgICAgICAgICBjb25zdCBhY2Nlc3NvcnMgPSB0aGlzLmdldEFjY2Vzc29yc0ZvckNvbXB1dGluZ1lSYW5nZSgpOwogICAgICAgICAgICBsZXQgZGF0YXNldFRvVmFsdWVzID0gKGQpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBhY2Nlc3NvcnMubWFwKChhY2Nlc3NvcikgPT4gZC5kYXRhKCkubWFwKCh4KSA9PiBhY2Nlc3Nvcih4LCAtMSwgZCkpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIGxvZGFzaC5mbGF0dGVuRGVlcCh0aGlzLmRhdGFzZXRzLm1hcChkYXRhc2V0VG9WYWx1ZXMpKS5maWx0ZXIoaXNGaW5pdGUpOwogICAgICAgIH0KICAgICAgICAvKiogQ29uc3RydWN0cyBzcGVjaWFsIGRhdGFzZXRzLiBFYWNoIHNwZWNpYWwgZGF0YXNldCBjb250YWlucyBleGNlcHRpb25hbAogICAgICAgICAqIHZhbHVlcyBmcm9tIGFsbCBvZiB0aGUgcmVndWxhciBkYXRhc2V0cywgZS5nLiBsYXN0IHBvaW50cyBpbiBzZXJpZXMsIG9yCiAgICAgICAgICogTmFOIHZhbHVlcy4gVGhvc2UgcG9pbnRzIHdpbGwgaGF2ZSBhIGBuYW1lYCBhbmQgYHJlbGF0aXZlYCBwcm9wZXJ0eSBhZGRlZAogICAgICAgICAqIChzaW5jZSB1c3VhbGx5IHRob3NlIGFyZSBjb250ZXh0IGluIHRoZSBzdXJyb3VuZGluZyBkYXRhc2V0KS4KICAgICAgICAgKi8KICAgICAgICB1cGRhdGVTcGVjaWFsRGF0YXNldHMoKSB7CiAgICAgICAgICAgIGNvbnN0IGFjY2Vzc29yID0gdGhpcy5nZXRZQXhpc0FjY2Vzc29yKCk7CiAgICAgICAgICAgIGxldCBsYXN0UG9pbnRzRGF0YSA9IHRoaXMuZGF0YXNldHMKICAgICAgICAgICAgICAgIC5tYXAoKGQpID0+IHsKICAgICAgICAgICAgICAgIGxldCBkYXR1bSA9IG51bGw7CiAgICAgICAgICAgICAgICAvLyBmaWx0ZXIgb3V0IE5hTnMgdG8gZW5zdXJlIGxhc3QgcG9pbnQgaXMgYSBjbGVhbiBvbmUKICAgICAgICAgICAgICAgIGxldCBub25OYW5EYXRhID0gZC5kYXRhKCkuZmlsdGVyKCh4KSA9PiAhaXNOYU4oYWNjZXNzb3IoeCwgLTEsIGQpKSk7CiAgICAgICAgICAgICAgICBpZiAobm9uTmFuRGF0YS5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IGlkeCA9IG5vbk5hbkRhdGEubGVuZ3RoIC0gMTsKICAgICAgICAgICAgICAgICAgICBkYXR1bSA9IG5vbk5hbkRhdGFbaWR4XTsKICAgICAgICAgICAgICAgICAgICBkYXR1bS5uYW1lID0gZC5tZXRhZGF0YSgpLm5hbWU7CiAgICAgICAgICAgICAgICAgICAgZGF0dW0ucmVsYXRpdmUgPSByZWxhdGl2ZUFjY2Vzc29yKGRhdHVtLCAtMSwgZCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gZGF0dW07CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAuZmlsdGVyKCh4KSA9PiB4ICE9IG51bGwpOwogICAgICAgICAgICB0aGlzLmxhc3RQb2ludHNEYXRhc2V0LmRhdGEobGFzdFBvaW50c0RhdGEpOwogICAgICAgICAgICBpZiAodGhpcy5tYXJrZXJzU2NhdHRlclBsb3QpIHsKICAgICAgICAgICAgICAgIHRoaXMubWFya2Vyc1NjYXR0ZXJQbG90LmRhdGFzZXRzKHRoaXMuZGF0YXNldHMubWFwKHRoaXMuY3JlYXRlU2FtcGxlZERhdGFzZXRGb3JNYXJrZXJzKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVGFrZSBhIGRhdGFzZXQsIHJldHVybiBhbiBhcnJheSBvZiBOYU4gZGF0YSBwb2ludHMKICAgICAgICAgICAgLy8gdGhlIE5hTiBwb2ludHMgd2lsbCBoYXZlIGEgImRpc3BsYXlZIiBwcm9wZXJ0eSB3aGljaCBpcyB0aGUKICAgICAgICAgICAgLy8geS12YWx1ZSBvZiBhIG5lYXJieSBwb2ludCB0aGF0IHdhcyBub3QgTmFOICgwIGlmIGFsbCBwb2ludHMgYXJlIE5hTikKICAgICAgICAgICAgbGV0IGRhdGFzZXRUb05hTkRhdGEgPSAoZCkgPT4gewogICAgICAgICAgICAgICAgbGV0IGRpc3BsYXlZID0gbnVsbDsKICAgICAgICAgICAgICAgIGxldCBkYXRhID0gZC5kYXRhKCk7CiAgICAgICAgICAgICAgICBsZXQgaSA9IDA7CiAgICAgICAgICAgICAgICB3aGlsZSAoaSA8IGRhdGEubGVuZ3RoICYmIGRpc3BsYXlZID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoIWlzTmFOKGFjY2Vzc29yKGRhdGFbaV0sIC0xLCBkKSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgZGlzcGxheVkgPSBhY2Nlc3NvcihkYXRhW2ldLCAtMSwgZCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGkrKzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChkaXNwbGF5WSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgZGlzcGxheVkgPSAwOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IG5hbkRhdGEgPSBbXTsKICAgICAgICAgICAgICAgIGZvciAoaSA9IDA7IGkgPCBkYXRhLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKCFpc05hTihhY2Nlc3NvcihkYXRhW2ldLCAtMSwgZCkpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGRpc3BsYXlZID0gYWNjZXNzb3IoZGF0YVtpXSwgLTEsIGQpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgZGF0YVtpXS5uYW1lID0gZC5tZXRhZGF0YSgpLm5hbWU7CiAgICAgICAgICAgICAgICAgICAgICAgIGRhdGFbaV0uZGlzcGxheVkgPSBkaXNwbGF5WTsKICAgICAgICAgICAgICAgICAgICAgICAgZGF0YVtpXS5yZWxhdGl2ZSA9IHJlbGF0aXZlQWNjZXNzb3IoZGF0YVtpXSwgLTEsIGQpOwogICAgICAgICAgICAgICAgICAgICAgICBuYW5EYXRhLnB1c2goZGF0YVtpXSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIG5hbkRhdGE7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGxldCBuYW5EYXRhID0gbG9kYXNoLmZsYXR0ZW4odGhpcy5kYXRhc2V0cy5tYXAoZGF0YXNldFRvTmFORGF0YSkpOwogICAgICAgICAgICB0aGlzLm5hbkRhdGFzZXQuZGF0YShuYW5EYXRhKTsKICAgICAgICB9CiAgICAgICAgcmVzZXREb21haW4oKSB7CiAgICAgICAgICAgIHRoaXMucmVzZXRYRG9tYWluKCk7CiAgICAgICAgICAgIHRoaXMucmVzZXRZRG9tYWluKCk7CiAgICAgICAgfQogICAgICAgIHJlc2V0WERvbWFpbigpIHsKICAgICAgICAgICAgbGV0IHhEb21haW47CiAgICAgICAgICAgIGlmICh0aGlzLl9kZWZhdWx0WFJhbmdlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIC8vIFVzZSB0aGUgcmFuZ2Ugc3BlY2lmaWVkIGJ5IHRoZSBjYWxsZXIuCiAgICAgICAgICAgICAgICB4RG9tYWluID0gdGhpcy5fZGVmYXVsdFhSYW5nZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIChDb3BpZWQgZnJvbSB2el9saW5lX2NoYXJ0LkRyYWdab29tTGF5ZXIudW56b29tLikKICAgICAgICAgICAgICAgIGNvbnN0IHhTY2FsZSA9IHRoaXMueFNjYWxlOwogICAgICAgICAgICAgICAgeFNjYWxlLl9kb21haW5NaW4gPSBudWxsOwogICAgICAgICAgICAgICAgeFNjYWxlLl9kb21haW5NYXggPSBudWxsOwogICAgICAgICAgICAgICAgeERvbWFpbiA9IHhTY2FsZS5fZ2V0RXh0ZW50KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy54U2NhbGUuZG9tYWluKHhEb21haW4pOwogICAgICAgIH0KICAgICAgICByZXNldFlEb21haW4oKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9kZWZhdWx0WVJhbmdlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIC8vIFVzZSB0aGUgcmFuZ2Ugc3BlY2lmaWVkIGJ5IHRoZSBjYWxsZXIuCiAgICAgICAgICAgICAgICB0aGlzLnlTY2FsZS5kb21haW4odGhpcy5fZGVmYXVsdFlSYW5nZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAvLyBUZlNjYWxlIGhhcyBhbGwgdGhlIGxvZ2ljcyBmb3Igc2NhbGluZyBhbmQgd2UgbWFudWFsbHkgdHJpZ2dlciBpdCB3aXRoCiAgICAgICAgICAgICAgICAvLyBgYXV0b0RvbWFpbmAuIEhvd2V2ZXIsIHRoaXMgZW5hYmxlcyB0aGUgYXV0b0RvbWFpbiBtb2RlIHdoaWNoIHVwZGF0ZXMKICAgICAgICAgICAgICAgIC8vIHRoZSBkb21haW4gb24gYW55IGRhdGFzZXQgY2hhbmdlIGFuZCB0aGlzIGlzIG5vdCBkZXNpcmFibHkgZXNwZWNpYWxseQogICAgICAgICAgICAgICAgLy8gd2hlbiBhIHJ1biBpcyBub3QgZmluaXNoZWQgeWV0OyB3ZSBkb24ndCB3YW50IHRoZSBncmFwaCB0byBjaGFuZ2UgaW4KICAgICAgICAgICAgICAgIC8vIHNjYWxlIHdoaWxlIHVzZXIgaXMgaW5zcGVjdGluZyB0aGUgZ3JhcGguIEJ5IHNldHRpbmcgdGhlIGBkb21haW5gCiAgICAgICAgICAgICAgICAvLyBleHBsaWNpdGx5LCB3ZSBjYW4gdHVybiB0aGUgZmVhdHVyZSBvZmYuCiAgICAgICAgICAgICAgICB0aGlzLnlTY2FsZS5hdXRvRG9tYWluKCk7CiAgICAgICAgICAgICAgICB0aGlzLnlTY2FsZS5kb21haW4odGhpcy55U2NhbGUuZG9tYWluKCkpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGdldEFjY2Vzc29yc0ZvckNvbXB1dGluZ1lSYW5nZSgpIHsKICAgICAgICAgICAgY29uc3QgYWNjZXNzb3JzID0gW3RoaXMuZ2V0WUF4aXNBY2Nlc3NvcigpXTsKICAgICAgICAgICAgaWYgKHRoaXMuZmlsbEFyZWEpIHsKICAgICAgICAgICAgICAgIC8vIE1ha2UgdGhlIFkgZG9tYWluIHRha2UgbWFyZ2lucyBpbnRvIGFjY291bnQuCiAgICAgICAgICAgICAgICBhY2Nlc3NvcnMucHVzaCh0aGlzLmZpbGxBcmVhLmxvd2VyQWNjZXNzb3IsIHRoaXMuZmlsbEFyZWEuaGlnaGVyQWNjZXNzb3IpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBhY2Nlc3NvcnM7CiAgICAgICAgfQogICAgICAgIGdldFlBeGlzQWNjZXNzb3IoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnNtb290aGluZ0VuYWJsZWQgPyB0aGlzLnNtb290aGVkQWNjZXNzb3IgOiB0aGlzLnlWYWx1ZUFjY2Vzc29yOwogICAgICAgIH0KICAgICAgICBjcmVhdGVUb29sdGlwSW50ZXJhY3Rpb24ocHpkbCkgewogICAgICAgICAgICBjb25zdCBwaSA9IG5ldyBQb2ludGVySW50ZXJhY3Rpb24oKTsKICAgICAgICAgICAgLy8gRGlzYWJsZSBpbnRlcmFjdGlvbiB3aGlsZSBkcmFnIHpvb21pbmcuCiAgICAgICAgICAgIGNvbnN0IGRpc2FibGVUb29sdGlwVXBkYXRlID0gKCkgPT4gewogICAgICAgICAgICAgICAgcGkuZW5hYmxlZChmYWxzZSk7CiAgICAgICAgICAgICAgICB0aGlzLmhpZGVUb29sdGlwcygpOwogICAgICAgICAgICB9OwogICAgICAgICAgICBjb25zdCBlbmFibGVUb29sdGlwVXBkYXRlID0gKCkgPT4gcGkuZW5hYmxlZCh0cnVlKTsKICAgICAgICAgICAgcHpkbC5vblBhblN0YXJ0KGRpc2FibGVUb29sdGlwVXBkYXRlKTsKICAgICAgICAgICAgcHpkbC5vbkRyYWdab29tU3RhcnQoZGlzYWJsZVRvb2x0aXBVcGRhdGUpOwogICAgICAgICAgICBwemRsLm9uUGFuRW5kKGVuYWJsZVRvb2x0aXBVcGRhdGUpOwogICAgICAgICAgICBwemRsLm9uRHJhZ1pvb21FbmQoZW5hYmxlVG9vbHRpcFVwZGF0ZSk7CiAgICAgICAgICAgIC8vIFdoZW4gdXNpbmcgd2hlZWwsIGN1cnNvciBwb3NpdGlvbiBkb2VzIG5vdCBjaGFuZ2UuIFJlZHJhdyB0aGUgdG9vbHRpcAogICAgICAgICAgICAvLyB1c2luZyB0aGUgbGFzdCBrbm93biBtb3VzZSBwb3NpdGlvbi4KICAgICAgICAgICAgcHpkbC5vblNjcm9sbFpvb20oKCkgPT4gdGhpcy51cGRhdGVUb29sdGlwQ29udGVudCh0aGlzLl9sYXN0TW91c2VQb3NpdGlvbikpOwogICAgICAgICAgICBwaS5vblBvaW50ZXJNb3ZlKChwKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9sYXN0TW91c2VQb3NpdGlvbiA9IHA7CiAgICAgICAgICAgICAgICB0aGlzLnVwZGF0ZVRvb2x0aXBDb250ZW50KHApOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcGkub25Qb2ludGVyRXhpdCgoKSA9PiB0aGlzLmhpZGVUb29sdGlwcygpKTsKICAgICAgICAgICAgcmV0dXJuIHBpOwogICAgICAgIH0KICAgICAgICB1cGRhdGVUb29sdGlwQ29udGVudChwKSB7CiAgICAgICAgICAgIC8vIExpbmUgcGxvdCBtdXN0IGJlIGluaXRpYWxpemVkIHRvIGRyYXcuCiAgICAgICAgICAgIGlmICghdGhpcy5saW5lUGxvdCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX3Rvb2x0aXBVcGRhdGVBbmltYXRpb25GcmFtZSk7CiAgICAgICAgICAgIHRoaXMuX3Rvb2x0aXBVcGRhdGVBbmltYXRpb25GcmFtZSA9IHdpbmRvdy5yZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gewogICAgICAgICAgICAgICAgbGV0IHRhcmdldCA9IHsKICAgICAgICAgICAgICAgICAgICB4OiBwLngsCiAgICAgICAgICAgICAgICAgICAgeTogcC55LAogICAgICAgICAgICAgICAgICAgIGRhdHVtOiBudWxsLAogICAgICAgICAgICAgICAgICAgIGRhdGFzZXQ6IG51bGwsCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgbGV0IGJib3ggPSB0aGlzLmdyaWRsaW5lcy5jb250ZW50KCkubm9kZSgpLmdldEJCb3goKTsKICAgICAgICAgICAgICAgIC8vIHB0cyBpcyB0aGUgY2xvc2V0cyBwb2ludCB0byB0aGUgdG9vbHRpcCBmb3IgZWFjaCBkYXRhc2V0CiAgICAgICAgICAgICAgICBsZXQgcHRzID0gdGhpcy5saW5lUGxvdAogICAgICAgICAgICAgICAgICAgIC5kYXRhc2V0cygpCiAgICAgICAgICAgICAgICAgICAgLm1hcCgoZGF0YXNldCkgPT4gdGhpcy5maW5kQ2xvc2VzdFBvaW50KHRhcmdldCwgZGF0YXNldCkpCiAgICAgICAgICAgICAgICAgICAgLmZpbHRlcihCb29sZWFuKTsKICAgICAgICAgICAgICAgIGxldCBpbnRlcnNlY3RzQkJveCA9IHNyYyQyLlV0aWxzLkRPTS5pbnRlcnNlY3RzQkJveDsKICAgICAgICAgICAgICAgIC8vIFdlIGRyYXcgdG9vbHRpcHMgZm9yIHBvaW50cyB0aGF0IGFyZSBOYU4sIG9yIGFyZSBjdXJyZW50bHkgdmlzaWJsZQogICAgICAgICAgICAgICAgbGV0IHB0c0ZvclRvb2x0aXBzID0gcHRzLmZpbHRlcigocCkgPT4gaW50ZXJzZWN0c0JCb3gocC54LCBwLnksIGJib3gpIHx8CiAgICAgICAgICAgICAgICAgICAgaXNOYU4odGhpcy55VmFsdWVBY2Nlc3NvcihwLmRhdHVtLCAwLCBwLmRhdGFzZXQpKSk7CiAgICAgICAgICAgICAgICAvLyBPbmx5IGRyYXcgbGl0dGxlIGluZGljYXRvciBjaXJjbGVzIGZvciB0aGUgbm9uLU5hTiBwb2ludHMKICAgICAgICAgICAgICAgIGxldCBwdHNUb0NpcmNsZSA9IHB0c0ZvclRvb2x0aXBzLmZpbHRlcigocCkgPT4gIWlzTmFOKHRoaXMueVZhbHVlQWNjZXNzb3IocC5kYXR1bSwgMCwgcC5kYXRhc2V0KSkpOwogICAgICAgICAgICAgICAgaWYgKHB0cy5sZW5ndGggIT09IDApIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnNjYXR0ZXJQbG90LmF0dHIoJ2Rpc3BsYXknLCAnbm9uZScpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHB0c1NlbGVjdGlvbiA9IHRoaXMudG9vbHRpcFBvaW50c0NvbXBvbmVudAogICAgICAgICAgICAgICAgICAgICAgICAuY29udGVudCgpCiAgICAgICAgICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJy5wb2ludCcpCiAgICAgICAgICAgICAgICAgICAgICAgIC5kYXRhKHB0c1RvQ2lyY2xlLCAocCkgPT4gcC5kYXRhc2V0Lm1ldGFkYXRhKCkubmFtZSk7CiAgICAgICAgICAgICAgICAgICAgcHRzU2VsZWN0aW9uLmVudGVyKCkuYXBwZW5kKCdjaXJjbGUnKS5jbGFzc2VkKCdwb2ludCcsIHRydWUpOwogICAgICAgICAgICAgICAgICAgIHB0c1NlbGVjdGlvbgogICAgICAgICAgICAgICAgICAgICAgICAuYXR0cigncicsIFRPT0xUSVBfQ0lSQ0xFX1NJWkUpCiAgICAgICAgICAgICAgICAgICAgICAgIC5hdHRyKCdjeCcsIChwKSA9PiBwLngpCiAgICAgICAgICAgICAgICAgICAgICAgIC5hdHRyKCdjeScsIChwKSA9PiBwLnkpCiAgICAgICAgICAgICAgICAgICAgICAgIC5zdHlsZSgnc3Ryb2tlJywgJ25vbmUnKQogICAgICAgICAgICAgICAgICAgICAgICAuYXR0cignZmlsbCcsIChwKSA9PiB0aGlzLmNvbG9yU2NhbGUuc2NhbGUocC5kYXRhc2V0Lm1ldGFkYXRhKCkubmFtZSkpOwogICAgICAgICAgICAgICAgICAgIHB0c1NlbGVjdGlvbi5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5kcmF3VG9vbHRpcHMocHRzRm9yVG9vbHRpcHMsIHRhcmdldCwgdGhpcy50b29sdGlwQ29sdW1ucyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLmhpZGVUb29sdGlwcygpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgaGlkZVRvb2x0aXBzKCkgewogICAgICAgICAgICB3aW5kb3cuY2FuY2VsQW5pbWF0aW9uRnJhbWUodGhpcy5fdG9vbHRpcFVwZGF0ZUFuaW1hdGlvbkZyYW1lKTsKICAgICAgICAgICAgdGhpcy50b29sdGlwLmhpZGUoKTsKICAgICAgICAgICAgdGhpcy5zY2F0dGVyUGxvdC5hdHRyKCdkaXNwbGF5JywgJ2Jsb2NrJyk7CiAgICAgICAgICAgIHRoaXMudG9vbHRpcFBvaW50c0NvbXBvbmVudC5jb250ZW50KCkuc2VsZWN0QWxsKCcucG9pbnQnKS5yZW1vdmUoKTsKICAgICAgICB9CiAgICAgICAgc2V0dXBUb29sdGlwcyhwbG90KSB7CiAgICAgICAgICAgIHBsb3Qub25EZXRhY2goKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy50b29sdGlwSW50ZXJhY3Rpb24uZGV0YWNoRnJvbShwbG90KTsKICAgICAgICAgICAgICAgIHRoaXMudG9vbHRpcEludGVyYWN0aW9uLmVuYWJsZWQoZmFsc2UpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcGxvdC5vbkFuY2hvcigoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLnRvb2x0aXBJbnRlcmFjdGlvbi5hdHRhY2hUbyhwbG90KTsKICAgICAgICAgICAgICAgIHRoaXMudG9vbHRpcEludGVyYWN0aW9uLmVuYWJsZWQodHJ1ZSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBkcmF3VG9vbHRpcHMocG9pbnRzLCB0YXJnZXQsIHRvb2x0aXBDb2x1bW5zKSB7CiAgICAgICAgICAgIGlmICghcG9pbnRzLmxlbmd0aCkgewogICAgICAgICAgICAgICAgdGhpcy50b29sdGlwLmhpZGUoKTsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCB7IGNvbG9yU2NhbGUgfSA9IHRoaXM7CiAgICAgICAgICAgIGNvbnN0IHN3YXRjaENvbCA9IHsKICAgICAgICAgICAgICAgIHRpdGxlOiAnJywKICAgICAgICAgICAgICAgIHN0YXRpYzogZmFsc2UsCiAgICAgICAgICAgICAgICBldmFsVHlwZTogVG9vbHRpcENvbHVtbkV2YWxUeXBlLkRPTSwKICAgICAgICAgICAgICAgIGV2YWx1YXRlKGQpIHsKICAgICAgICAgICAgICAgICAgICBzZWxlY3QodGhpcykKICAgICAgICAgICAgICAgICAgICAgICAgLnNlbGVjdCgnc3BhbicpCiAgICAgICAgICAgICAgICAgICAgICAgIC5zdHlsZSgnYmFja2dyb3VuZC1jb2xvcicsICgpID0+IGNvbG9yU2NhbGUuc2NhbGUoZC5kYXRhc2V0Lm1ldGFkYXRhKCkubmFtZSkpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICBlbnRlcihkKSB7CiAgICAgICAgICAgICAgICAgICAgc2VsZWN0KHRoaXMpCiAgICAgICAgICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3NwYW4nKQogICAgICAgICAgICAgICAgICAgICAgICAuY2xhc3NlZCgnc3dhdGNoJywgdHJ1ZSkKICAgICAgICAgICAgICAgICAgICAgICAgLnN0eWxlKCdiYWNrZ3JvdW5kLWNvbG9yJywgKCkgPT4gY29sb3JTY2FsZS5zY2FsZShkLmRhdGFzZXQubWV0YWRhdGEoKS5uYW1lKSk7CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9OwogICAgICAgICAgICB0b29sdGlwQ29sdW1ucyA9IFtzd2F0Y2hDb2wsIC4uLnRvb2x0aXBDb2x1bW5zXTsKICAgICAgICAgICAgY29uc3QgZGlzdCA9IChwKSA9PiBNYXRoLnBvdyhwLnggLSB0YXJnZXQueCwgMikgKyBNYXRoLnBvdyhwLnkgLSB0YXJnZXQueSwgMik7CiAgICAgICAgICAgIGNvbnN0IGNsb3Nlc3REaXN0ID0gbG9kYXNoLm1pbihwb2ludHMubWFwKGRpc3QpKTsKICAgICAgICAgICAgY29uc3QgdmFsdWVTb3J0TWV0aG9kID0gdGhpcy5zbW9vdGhpbmdFbmFibGVkCiAgICAgICAgICAgICAgICA/IHRoaXMuc21vb3RoZWRBY2Nlc3NvcgogICAgICAgICAgICAgICAgOiB0aGlzLnlWYWx1ZUFjY2Vzc29yOwogICAgICAgICAgICBpZiAodGhpcy50b29sdGlwU29ydGluZ01ldGhvZCA9PT0gJ2FzY2VuZGluZycpIHsKICAgICAgICAgICAgICAgIHBvaW50cyA9IGxvZGFzaC5zb3J0QnkocG9pbnRzLCAoZCkgPT4gdmFsdWVTb3J0TWV0aG9kKGQuZGF0dW0sIC0xLCBkLmRhdGFzZXQpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0aGlzLnRvb2x0aXBTb3J0aW5nTWV0aG9kID09PSAnZGVzY2VuZGluZycpIHsKICAgICAgICAgICAgICAgIHBvaW50cyA9IGxvZGFzaC5zb3J0QnkocG9pbnRzLCAoZCkgPT4gdmFsdWVTb3J0TWV0aG9kKGQuZGF0dW0sIC0xLCBkLmRhdGFzZXQpKS5yZXZlcnNlKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAodGhpcy50b29sdGlwU29ydGluZ01ldGhvZCA9PT0gJ25lYXJlc3QnKSB7CiAgICAgICAgICAgICAgICBwb2ludHMgPSBsb2Rhc2guc29ydEJ5KHBvaW50cywgZGlzdCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgJ2RlZmF1bHQnIHNvcnRpbmcgbWV0aG9kIG1haW50YWlucyB0aGUgb3JkZXIgb2YgbmFtZXMgcGFzc2VkIHRvCiAgICAgICAgICAgICAgICAvLyBzZXRWaXNpYmxlU2VyaWVzKCkuIEhvd2V2ZXIgd2UgcmV2ZXJzZSB0aGF0IG9yZGVyIHdoZW4gZGVmaW5pbmcgdGhlCiAgICAgICAgICAgICAgICAvLyBkYXRhc2V0cy4gU28gd2UgbXVzdCBjYWxsIHJldmVyc2UgYWdhaW4gdG8gcmVzdG9yZSB0aGUgb3JkZXIuCiAgICAgICAgICAgICAgICBwb2ludHMgPSBwb2ludHMuc2xpY2UoMCkucmV2ZXJzZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHNlbGYgPSB0aGlzOwogICAgICAgICAgICBjb25zdCB0YWJsZSA9IHNlbGVjdCh0aGlzLnRvb2x0aXAuY29udGVudCgpKS5zZWxlY3QoJ3RhYmxlJyk7CiAgICAgICAgICAgIGNvbnN0IGhlYWRlciA9IHRhYmxlCiAgICAgICAgICAgICAgICAuc2VsZWN0KCd0aGVhZCcpCiAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCd0aCcpCiAgICAgICAgICAgICAgICAuZGF0YSh0b29sdGlwQ29sdW1ucywgKGNvbHVtbiwgXywgX18pID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBjb2x1bW4udGl0bGU7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBoZWFkZXIKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCd0aCcpCiAgICAgICAgICAgICAgICAudGV4dCgoY29sKSA9PiBjb2wudGl0bGUpCiAgICAgICAgICAgICAgICAubm9kZXMoKTsKICAgICAgICAgICAgaGVhZGVyLmV4aXQoKS5yZW1vdmUoKTsKICAgICAgICAgICAgY29uc3Qgcm93cyA9IHRhYmxlCiAgICAgICAgICAgICAgICAuc2VsZWN0KCd0Ym9keScpCiAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCd0cicpCiAgICAgICAgICAgICAgICAuZGF0YShwb2ludHMsIChwdCwgXywgX18pID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBwdC5kYXRhc2V0Lm1ldGFkYXRhKCkubmFtZTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJvd3MKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCdkaXN0YW50JywgKGQpID0+IHsKICAgICAgICAgICAgICAgIC8vIEdyZXkgb3V0IHRoZSBwb2ludCBpZiBhbnkgb2YgdGhlIGZvbGxvd2luZyBhcmUgdHJ1ZToKICAgICAgICAgICAgICAgIC8vIC0gVGhlIGN1cnNvciBpcyBvdXRzaWRlIG9mIHRoZSB4LWV4dGVudCBvZiB0aGUgZGF0YXNldAogICAgICAgICAgICAgICAgLy8gLSBUaGUgcG9pbnQncyB5IHZhbHVlIGlzIE5hTgogICAgICAgICAgICAgICAgbGV0IGZpcnN0UG9pbnQgPSBkLmRhdGFzZXQuZGF0YSgpWzBdOwogICAgICAgICAgICAgICAgbGV0IGxhc3RQb2ludCA9IGxvZGFzaC5sYXN0KGQuZGF0YXNldC5kYXRhKCkpOwogICAgICAgICAgICAgICAgbGV0IGZpcnN0WCA9IHRoaXMueFNjYWxlLnNjYWxlKHRoaXMueEFjY2Vzc29yKGZpcnN0UG9pbnQsIDAsIGQuZGF0YXNldCkpOwogICAgICAgICAgICAgICAgbGV0IGxhc3RYID0gdGhpcy54U2NhbGUuc2NhbGUodGhpcy54QWNjZXNzb3IobGFzdFBvaW50LCAwLCBkLmRhdGFzZXQpKTsKICAgICAgICAgICAgICAgIGxldCBzID0gdGhpcy5zbW9vdGhpbmdFbmFibGVkCiAgICAgICAgICAgICAgICAgICAgPyBkLmRhdHVtLnNtb290aGVkCiAgICAgICAgICAgICAgICAgICAgOiB0aGlzLnlWYWx1ZUFjY2Vzc29yKGQuZGF0dW0sIDAsIGQuZGF0YXNldCk7CiAgICAgICAgICAgICAgICByZXR1cm4gdGFyZ2V0LnggPCBmaXJzdFggfHwgdGFyZ2V0LnggPiBsYXN0WCB8fCBpc05hTihzKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCdjbG9zZXN0JywgKHApID0+IGRpc3QocCkgPT09IGNsb3Nlc3REaXN0KQogICAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKHBvaW50KSB7CiAgICAgICAgICAgICAgICBzZWxmLmRyYXdUb29sdGlwUm93KHRoaXMsIHRvb2x0aXBDb2x1bW5zLCBwb2ludCk7CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAvLyByZW9yZGVycyBET00gdG8gbWF0Y2ggdGhlIG9yZGVyaW5nIG9mIHRoZSBgZGF0YWAuCiAgICAgICAgICAgICAgICAub3JkZXIoKTsKICAgICAgICAgICAgcm93cy5leGl0KCkucmVtb3ZlKCk7CiAgICAgICAgICAgIHJvd3MKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCd0cicpCiAgICAgICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAocG9pbnQpIHsKICAgICAgICAgICAgICAgIHNlbGYuZHJhd1Rvb2x0aXBSb3codGhpcywgdG9vbHRpcENvbHVtbnMsIHBvaW50KTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5ub2RlcygpOwogICAgICAgICAgICB0aGlzLnRvb2x0aXAudXBkYXRlQW5kUG9zaXRpb24odGhpcy50YXJnZXRTVkcubm9kZSgpKTsKICAgICAgICB9CiAgICAgICAgZHJhd1Rvb2x0aXBSb3cocm93LCB0b29sdGlwQ29sdW1ucywgcG9pbnQpIHsKICAgICAgICAgICAgY29uc3Qgc2VsZiA9IHRoaXM7CiAgICAgICAgICAgIGNvbnN0IGNvbHVtbnMgPSBzZWxlY3Qocm93KS5zZWxlY3RBbGwoJ3RkJykuZGF0YSh0b29sdGlwQ29sdW1ucyk7CiAgICAgICAgICAgIGNvbHVtbnMuZWFjaChmdW5jdGlvbiAoY29sKSB7CiAgICAgICAgICAgICAgICAvLyBTa2lwIGNvbHVtbiB2YWx1ZSB1cGRhdGUgd2hlbiB0aGUgY29sdW1uIGlzIHN0YXRpYy4KICAgICAgICAgICAgICAgIGlmIChjb2wuc3RhdGljKQogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIHNlbGYuZHJhd1Rvb2x0aXBDb2x1bW4uY2FsbChzZWxmLCB0aGlzLCBjb2wsIHBvaW50KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGNvbHVtbnMuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICBjb2x1bW5zCiAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgLmFwcGVuZCgndGQnKQogICAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKGNvbCkgewogICAgICAgICAgICAgICAgaWYgKCdlbnRlcicgaW4gY29sICYmIGNvbC5lbnRlcikgewogICAgICAgICAgICAgICAgICAgIGNvbnN0IGN1c3RvbVRvb2x0aXAgPSBjb2w7CiAgICAgICAgICAgICAgICAgICAgY3VzdG9tVG9vbHRpcC5lbnRlci5jYWxsKHRoaXMsIHBvaW50KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHNlbGYuZHJhd1Rvb2x0aXBDb2x1bW4uY2FsbChzZWxmLCB0aGlzLCBjb2wsIHBvaW50KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIGRyYXdUb29sdGlwQ29sdW1uKGNvbHVtbiwgdG9vbHRpcENvbCwgcG9pbnQpIHsKICAgICAgICAgICAgY29uc3QgeyBzbW9vdGhpbmdFbmFibGVkIH0gPSB0aGlzOwogICAgICAgICAgICBpZiAoJ2V2YWxUeXBlJyBpbiB0b29sdGlwQ29sICYmCiAgICAgICAgICAgICAgICB0b29sdGlwQ29sLmV2YWxUeXBlID09IFRvb2x0aXBDb2x1bW5FdmFsVHlwZS5ET00pIHsKICAgICAgICAgICAgICAgIHRvb2x0aXBDb2wuZXZhbHVhdGUuY2FsbChjb2x1bW4sIHBvaW50LCB7IHNtb290aGluZ0VuYWJsZWQgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBzZWxlY3QoY29sdW1uKS50ZXh0KHRvb2x0aXBDb2wuZXZhbHVhdGUuY2FsbChjb2x1bW4sIHBvaW50LCB7IHNtb290aGluZ0VuYWJsZWQgfSkpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGZpbmRDbG9zZXN0UG9pbnQodGFyZ2V0LCBkYXRhc2V0KSB7CiAgICAgICAgICAgIGNvbnN0IHhQb2ludHMgPSBkYXRhc2V0CiAgICAgICAgICAgICAgICAuZGF0YSgpCiAgICAgICAgICAgICAgICAubWFwKChkLCBpKSA9PiB0aGlzLnhTY2FsZS5zY2FsZSh0aGlzLnhBY2Nlc3NvcihkLCBpLCBkYXRhc2V0KSkpOwogICAgICAgICAgICBsZXQgaWR4ID0gbG9kYXNoLnNvcnRlZEluZGV4KHhQb2ludHMsIHRhcmdldC54KTsKICAgICAgICAgICAgaWYgKHhQb2ludHMubGVuZ3RoID09IDApCiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgaWYgKGlkeCA9PT0geFBvaW50cy5sZW5ndGgpIHsKICAgICAgICAgICAgICAgIGlkeCA9IGlkeCAtIDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAoaWR4ICE9PSAwKSB7CiAgICAgICAgICAgICAgICBjb25zdCBwcmV2RGlzdCA9IE1hdGguYWJzKHhQb2ludHNbaWR4IC0gMV0gLSB0YXJnZXQueCk7CiAgICAgICAgICAgICAgICBjb25zdCBuZXh0RGlzdCA9IE1hdGguYWJzKHhQb2ludHNbaWR4XSAtIHRhcmdldC54KTsKICAgICAgICAgICAgICAgIGlkeCA9IHByZXZEaXN0IDwgbmV4dERpc3QgPyBpZHggLSAxIDogaWR4OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGRhdHVtID0gZGF0YXNldC5kYXRhKClbaWR4XTsKICAgICAgICAgICAgY29uc3QgeSA9IHRoaXMuc21vb3RoaW5nRW5hYmxlZAogICAgICAgICAgICAgICAgPyB0aGlzLnNtb290aGVkQWNjZXNzb3IoZGF0dW0sIGlkeCwgZGF0YXNldCkKICAgICAgICAgICAgICAgIDogdGhpcy55VmFsdWVBY2Nlc3NvcihkYXR1bSwgaWR4LCBkYXRhc2V0KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHg6IHhQb2ludHNbaWR4XSwKICAgICAgICAgICAgICAgIHk6IHRoaXMueVNjYWxlLnNjYWxlKHkpLAogICAgICAgICAgICAgICAgZGF0dW0sCiAgICAgICAgICAgICAgICBkYXRhc2V0LAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICByZXNtb290aERhdGFzZXQoZGF0YXNldCkgewogICAgICAgICAgICBsZXQgZGF0YSA9IGRhdGFzZXQuZGF0YSgpOwogICAgICAgICAgICBjb25zdCBzbW9vdGhpbmdXZWlnaHQgPSB0aGlzLnNtb290aGluZ1dlaWdodDsKICAgICAgICAgICAgLy8gMXN0LW9yZGVyIElJUiBsb3ctcGFzcyBmaWx0ZXIgdG8gYXR0ZW51YXRlIHRoZSBoaWdoZXItCiAgICAgICAgICAgIC8vIGZyZXF1ZW5jeSBjb21wb25lbnRzIG9mIHRoZSB0aW1lLXNlcmllcy4KICAgICAgICAgICAgbGV0IGxhc3QgPSBkYXRhLmxlbmd0aCA+IDAgPyAwIDogTmFOOwogICAgICAgICAgICBsZXQgbnVtQWNjdW0gPSAwOwogICAgICAgICAgICBjb25zdCB5VmFsdWVzID0gZGF0YS5tYXAoKGQsIGkpID0+IHRoaXMueVZhbHVlQWNjZXNzb3IoZCwgaSwgZGF0YXNldCkpOwogICAgICAgICAgICAvLyBTZWUgIzc4Ni4KICAgICAgICAgICAgY29uc3QgaXNDb25zdGFudCA9IHlWYWx1ZXMuZXZlcnkoKHYpID0+IHYgPT0geVZhbHVlc1swXSk7CiAgICAgICAgICAgIGRhdGEuZm9yRWFjaCgoZCwgaSkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgbmV4dFZhbCA9IHlWYWx1ZXNbaV07CiAgICAgICAgICAgICAgICBpZiAoaXNDb25zdGFudCB8fCAhTnVtYmVyLmlzRmluaXRlKG5leHRWYWwpKSB7CiAgICAgICAgICAgICAgICAgICAgZC5zbW9vdGhlZCA9IG5leHRWYWw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBsYXN0ID0gbGFzdCAqIHNtb290aGluZ1dlaWdodCArICgxIC0gc21vb3RoaW5nV2VpZ2h0KSAqIG5leHRWYWw7CiAgICAgICAgICAgICAgICAgICAgbnVtQWNjdW0rKzsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgdW5jb3JyZWN0ZWQgbW92aW5nIGF2ZXJhZ2UgaXMgYmlhc2VkIHRvd2FyZHMgdGhlIGluaXRpYWwgdmFsdWUuCiAgICAgICAgICAgICAgICAgICAgLy8gRm9yIGV4YW1wbGUsIGlmIGluaXRpYWxpemVkIHdpdGggYDBgLCB3aXRoIHNtb290aGluZ1dlaWdodCBgc2AsIHdoZXJlCiAgICAgICAgICAgICAgICAgICAgLy8gZXZlcnkgZGF0YSBwb2ludCBpcyBgY2AsIGFmdGVyIGB0YCBzdGVwcyB0aGUgbW92aW5nIGF2ZXJhZ2UgaXMKICAgICAgICAgICAgICAgICAgICAvLyBgYGAKICAgICAgICAgICAgICAgICAgICAvLyAgIEVNQSA9IDAqc14odCkgKyBjKigxIC0gcykqc14odC0xKSArIGMqKDEgLSBzKSpzXih0LTIpICsgLi4uCiAgICAgICAgICAgICAgICAgICAgLy8gICAgICAgPSBjKigxIC0gc150KQogICAgICAgICAgICAgICAgICAgIC8vIGBgYAogICAgICAgICAgICAgICAgICAgIC8vIElmIGluaXRpYWxpemVkIHdpdGggYDBgLCBkaXZpZGluZyBieSAoMSAtIHNedCkgaXMgZW5vdWdoIHRvIGRlYmlhcwogICAgICAgICAgICAgICAgICAgIC8vIHRoZSBtb3ZpbmcgYXZlcmFnZS4gV2UgY291bnQgdGhlIG51bWJlciBvZiBmaW5pdGUgZGF0YSBwb2ludHMgYW5kCiAgICAgICAgICAgICAgICAgICAgLy8gZGl2aWRlIGFwcHJvcHJpYXRlbHkgYmVmb3JlIHN0b3JpbmcgdGhlIGRhdGEuCiAgICAgICAgICAgICAgICAgICAgbGV0IGRlYmlhc1dlaWdodCA9IDE7CiAgICAgICAgICAgICAgICAgICAgaWYgKHNtb290aGluZ1dlaWdodCAhPT0gMSkgewogICAgICAgICAgICAgICAgICAgICAgICBkZWJpYXNXZWlnaHQgPSAxIC0gTWF0aC5wb3coc21vb3RoaW5nV2VpZ2h0LCBudW1BY2N1bSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGQuc21vb3RoZWQgPSBsYXN0IC8gZGViaWFzV2VpZ2h0OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgZ2V0RGF0YXNldChuYW1lKSB7CiAgICAgICAgICAgIGlmICh0aGlzLm5hbWUyZGF0YXNldHNbbmFtZV0gPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgdGhpcy5uYW1lMmRhdGFzZXRzW25hbWVdID0gbmV3IHNyYyQyLkRhdGFzZXQoW10sIHsKICAgICAgICAgICAgICAgICAgICBuYW1lLAogICAgICAgICAgICAgICAgICAgIG1ldGE6IG51bGwsCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5uYW1lMmRhdGFzZXRzW25hbWVdOwogICAgICAgIH0KICAgICAgICBzdGF0aWMgZ2V0WVNjYWxlRnJvbVR5cGUoeVNjYWxlVHlwZSkgewogICAgICAgICAgICBpZiAoeVNjYWxlVHlwZSA9PT0gWVNjYWxlVHlwZS5MT0cpIHsKICAgICAgICAgICAgICAgIHJldHVybiBuZXcgTG9nU2NhbGUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh5U2NhbGVUeXBlID09PSBZU2NhbGVUeXBlLkxJTkVBUikgewogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBMaW5lYXJTY2FsZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdVbnJlY29nbml6ZWQgeVNjYWxlIHR5cGUgJyArIHlTY2FsZVR5cGUpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFN0YWdlcyB1cGRhdGUgb2YgdmlzaWJsZSBzZXJpZXMgb24gdGhlIGNoYXJ0LgogICAgICAgICAqCiAgICAgICAgICogUGxlYXNlIGNhbGwgYGNvbW1pdENoYW5nZXNgIGZvciB0aGUgY2hhbmdlcyB0byBiZSByZWZsZWN0ZWQgb24gdGhlIGNoYXJ0CiAgICAgICAgICogYWZ0ZXIgbWFraW5nIGFsbCB0aGUgY2hhbmdlcy4KICAgICAgICAgKi8KICAgICAgICBzZXRWaXNpYmxlU2VyaWVzKG5hbWVzKSB7CiAgICAgICAgICAgIHRoaXMuZGlzYWJsZUNoYW5nZXMoKTsKICAgICAgICAgICAgbmFtZXMgPSBuYW1lcy5zb3J0KCk7CiAgICAgICAgICAgIG5hbWVzLnJldmVyc2UoKTsgLy8gZHJhdyBmaXJzdCBzZXJpZXMgb24gdG9wCiAgICAgICAgICAgIHRoaXMuc2VyaWVzTmFtZXMgPSBuYW1lczsKICAgICAgICB9CiAgICAgICAgZGlzYWJsZUNoYW5nZXMoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5kaXJ0eURhdGFzZXRzLnNpemUpIHsKICAgICAgICAgICAgICAgIC8vIFByZXZlbnQgcGxvdHMgZnJvbSByZWFjdGluZyB0byB0aGUgZGF0YXNldCBjaGFuZ2VzLgogICAgICAgICAgICAgICAgdGhpcy5saW5lUGxvdC5kYXRhc2V0cyhbXSk7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5zbW9vdGhMaW5lUGxvdCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuc21vb3RoTGluZVBsb3QuZGF0YXNldHMoW10pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKHRoaXMubWFyZ2luQXJlYVBsb3QpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLm1hcmdpbkFyZWFQbG90LmRhdGFzZXRzKFtdKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBjb21taXRDaGFuZ2VzKCkgewogICAgICAgICAgICB0aGlzLmRhdGFzZXRzID0gdGhpcy5zZXJpZXNOYW1lcy5tYXAoKHIpID0+IHRoaXMuZ2V0RGF0YXNldChyKSk7CiAgICAgICAgICAgIFsuLi50aGlzLmRpcnR5RGF0YXNldHNdLmZvckVhY2goKGQpID0+IHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLnNtb290aGluZ0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnJlc21vb3RoRGF0YXNldCh0aGlzLmdldERhdGFzZXQoZCkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy51cGRhdGVTcGVjaWFsRGF0YXNldHMoKTsKICAgICAgICAgICAgdGhpcy5saW5lUGxvdC5kYXRhc2V0cyh0aGlzLmRhdGFzZXRzKTsKICAgICAgICAgICAgaWYgKHRoaXMuc21vb3RoaW5nRW5hYmxlZCkgewogICAgICAgICAgICAgICAgdGhpcy5zbW9vdGhMaW5lUGxvdC5kYXRhc2V0cyh0aGlzLmRhdGFzZXRzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5tYXJnaW5BcmVhUGxvdCkgewogICAgICAgICAgICAgICAgdGhpcy5tYXJnaW5BcmVhUGxvdC5kYXRhc2V0cyh0aGlzLmRhdGFzZXRzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLm1lYXN1cmVCQm94QW5kTWF5YmVJbnZhbGlkYXRlTGF5b3V0SW5SYWYoKTsKICAgICAgICAgICAgdGhpcy5kaXJ0eURhdGFzZXRzLmNsZWFyKCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFNhbXBsZXMgYSBkYXRhc2V0IHNvIHRoYXQgaXQgY29udGFpbnMgbm8gbW9yZSB0aGFuIF9NQVhfTUFSS0VSUyBudW1iZXIgb2YKICAgICAgICAgKiBkYXRhIHBvaW50cy4gVGhpcyBmdW5jdGlvbiByZXR1cm5zIHRoZSBvcmlnaW5hbCBkYXRhc2V0IGlmIGl0IGRvZXMgbm90CiAgICAgICAgICogZXhjZWVkIHRoYXQgbWFueSBwb2ludHMuCiAgICAgICAgICovCiAgICAgICAgY3JlYXRlU2FtcGxlZERhdGFzZXRGb3JNYXJrZXJzKG9yaWdpbmFsKSB7CiAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsRGF0YSA9IG9yaWdpbmFsLmRhdGEoKTsKICAgICAgICAgICAgaWYgKG9yaWdpbmFsRGF0YS5sZW5ndGggPD0gX01BWF9NQVJLRVJTKSB7CiAgICAgICAgICAgICAgICAvLyBUaGlzIGRhdGFzZXQgaXMgc21hbGwgZW5vdWdoLiBEbyBub3Qgc2FtcGxlLgogICAgICAgICAgICAgICAgcmV0dXJuIG9yaWdpbmFsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIERvd25zYW1wbGUgdGhlIGRhdGEuIE90aGVyd2lzZSwgdG9vIG1hbnkgbWFya2VycyBjbHV0dGVyIHRoZSBjaGFydC4KICAgICAgICAgICAgY29uc3Qgc2tpcExlbmd0aCA9IE1hdGguY2VpbChvcmlnaW5hbERhdGEubGVuZ3RoIC8gX01BWF9NQVJLRVJTKTsKICAgICAgICAgICAgY29uc3QgZGF0YSA9IG5ldyBBcnJheShNYXRoLmZsb29yKG9yaWdpbmFsRGF0YS5sZW5ndGggLyBza2lwTGVuZ3RoKSk7CiAgICAgICAgICAgIGZvciAobGV0IGkgPSAwLCBqID0gMDsgaSA8IGRhdGEubGVuZ3RoOyBpKyssIGogKz0gc2tpcExlbmd0aCkgewogICAgICAgICAgICAgICAgZGF0YVtpXSA9IG9yaWdpbmFsRGF0YVtqXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gbmV3IHNyYyQyLkRhdGFzZXQoZGF0YSwgb3JpZ2luYWwubWV0YWRhdGEoKSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFN0YWdlcyBhIGRhdGEgY2hhbmdlIG9mIGEgc2VyaWVzIG9uIHRoZSBjaGFydC4KICAgICAgICAgKgogICAgICAgICAqIFBsZWFzZSBjYWxsIGBjb21taXRDaGFuZ2VzYCBmb3IgdGhlIGNoYW5nZXMgdG8gYmUgcmVmbGVjdGVkIG9uIHRoZSBjaGFydAogICAgICAgICAqIGFmdGVyIG1ha2luZyBhbGwgdGhlIGNoYW5nZXMuCiAgICAgICAgICovCiAgICAgICAgc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKSB7CiAgICAgICAgICAgIHRoaXMuZGlzYWJsZUNoYW5nZXMoKTsKICAgICAgICAgICAgdGhpcy5nZXREYXRhc2V0KG5hbWUpLmRhdGEoZGF0YSk7CiAgICAgICAgICAgIHRoaXMuZGlydHlEYXRhc2V0cy5hZGQobmFtZSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgYSBtZXRhZGF0YSBjaGFuZ2Ugb2YgYSBzZXJpZXMgb24gdGhlIGNoYXJ0LgogICAgICAgICAqCiAgICAgICAgICogUGxlYXNlIGNhbGwgYGNvbW1pdENoYW5nZXNgIGZvciB0aGUgY2hhbmdlcyB0byBiZSByZWZsZWN0ZWQgb24gdGhlIGNoYXJ0CiAgICAgICAgICogYWZ0ZXIgbWFraW5nIGFsbCB0aGUgY2hhbmdlcy4KICAgICAgICAgKi8KICAgICAgICBzZXRTZXJpZXNNZXRhZGF0YShuYW1lLCBtZXRhKSB7CiAgICAgICAgICAgIHRoaXMuZGlzYWJsZUNoYW5nZXMoKTsKICAgICAgICAgICAgdGhpcy5nZXREYXRhc2V0KG5hbWUpLm1ldGFkYXRhKE9iamVjdC5hc3NpZ24oT2JqZWN0LmFzc2lnbih7fSwgdGhpcy5nZXREYXRhc2V0KG5hbWUpLm1ldGFkYXRhKCkpLCB7IG1ldGEgfSkpOwogICAgICAgICAgICB0aGlzLmRpcnR5RGF0YXNldHMuYWRkKG5hbWUpOwogICAgICAgIH0KICAgICAgICBzbW9vdGhpbmdVcGRhdGUod2VpZ2h0KSB7CiAgICAgICAgICAgIHRoaXMuc21vb3RoaW5nV2VpZ2h0ID0gd2VpZ2h0OwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzLmZvckVhY2goKGQpID0+IHRoaXMucmVzbW9vdGhEYXRhc2V0KGQpKTsKICAgICAgICAgICAgaWYgKCF0aGlzLnNtb290aGluZ0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMubGluZVBsb3QuYWRkQ2xhc3MoJ2dob3N0Jyk7CiAgICAgICAgICAgICAgICB0aGlzLnNjYXR0ZXJQbG90LnkodGhpcy5zbW9vdGhlZEFjY2Vzc29yLCB0aGlzLnlTY2FsZSk7CiAgICAgICAgICAgICAgICB0aGlzLnNtb290aGluZ0VuYWJsZWQgPSB0cnVlOwogICAgICAgICAgICAgICAgdGhpcy5zbW9vdGhMaW5lUGxvdC5kYXRhc2V0cyh0aGlzLmRhdGFzZXRzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5tYXJrZXJzU2NhdHRlclBsb3QpIHsKICAgICAgICAgICAgICAgIC8vIFVzZSB0aGUgY29ycmVjdCBhY2Nlc3NvciBmb3IgbWFya2VyIHBvc2l0aW9uaW5nLgogICAgICAgICAgICAgICAgdGhpcy5tYXJrZXJzU2NhdHRlclBsb3QueSh0aGlzLmdldFlBeGlzQWNjZXNzb3IoKSwgdGhpcy55U2NhbGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMudXBkYXRlU3BlY2lhbERhdGFzZXRzKCk7CiAgICAgICAgfQogICAgICAgIHNtb290aGluZ0Rpc2FibGUoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnNtb290aGluZ0VuYWJsZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMubGluZVBsb3QucmVtb3ZlQ2xhc3MoJ2dob3N0Jyk7CiAgICAgICAgICAgICAgICB0aGlzLnNjYXR0ZXJQbG90LnkodGhpcy55VmFsdWVBY2Nlc3NvciwgdGhpcy55U2NhbGUpOwogICAgICAgICAgICAgICAgdGhpcy5zbW9vdGhMaW5lUGxvdC5kYXRhc2V0cyhbXSk7CiAgICAgICAgICAgICAgICB0aGlzLnNtb290aGluZ0VuYWJsZWQgPSBmYWxzZTsKICAgICAgICAgICAgICAgIHRoaXMudXBkYXRlU3BlY2lhbERhdGFzZXRzKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRoaXMubWFya2Vyc1NjYXR0ZXJQbG90KSB7CiAgICAgICAgICAgICAgICAvLyBVc2UgdGhlIGNvcnJlY3QgYWNjZXNzb3IgKHdoaWNoIGRlcGVuZHMgb24gd2hldGhlciBzbW9vdGhpbmcgaXMKICAgICAgICAgICAgICAgIC8vIGVuYWJsZWQpIGZvciBtYXJrZXIgcG9zaXRpb25pbmcuCiAgICAgICAgICAgICAgICB0aGlzLm1hcmtlcnNTY2F0dGVyUGxvdC55KHRoaXMuZ2V0WUF4aXNBY2Nlc3NvcigpLCB0aGlzLnlTY2FsZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgc2V0Q29sb3JTY2FsZShjb2xvclNjYWxlKSB7CiAgICAgICAgICAgIHRoaXMuY29sb3JTY2FsZSA9IGNvbG9yU2NhbGU7CiAgICAgICAgfQogICAgICAgIHNldFRvb2x0aXBDb2x1bW5zKHRvb2x0aXBDb2x1bW5zKSB7CiAgICAgICAgICAgIHRoaXMudG9vbHRpcENvbHVtbnMgPSB0b29sdGlwQ29sdW1uczsKICAgICAgICB9CiAgICAgICAgc2V0VG9vbHRpcFNvcnRpbmdNZXRob2QobWV0aG9kKSB7CiAgICAgICAgICAgIHRoaXMudG9vbHRpcFNvcnRpbmdNZXRob2QgPSBtZXRob2Q7CiAgICAgICAgfQogICAgICAgIHJlbmRlclRvKHRhcmdldFNWRykgewogICAgICAgICAgICB0aGlzLnRhcmdldFNWRyA9IHRhcmdldFNWRzsKICAgICAgICAgICAgdGhpcy5vdXRlci5yZW5kZXJUbyh0YXJnZXRTVkcpOwogICAgICAgICAgICBpZiAodGhpcy5fZGVmYXVsdFhSYW5nZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBBIGhpZ2hlci1sZXZlbCBjb21wb25lbnQgcHJvdmlkZWQgYSBkZWZhdWx0IHJhbmdlIGZvciB0aGUgWCBheGlzLgogICAgICAgICAgICAgICAgLy8gU3RhcnQgd2l0aCB0aGF0IHJhbmdlLgogICAgICAgICAgICAgICAgdGhpcy5yZXNldFhEb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fZGVmYXVsdFlSYW5nZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBBIGhpZ2hlci1sZXZlbCBjb21wb25lbnQgcHJvdmlkZWQgYSBkZWZhdWx0IHJhbmdlIGZvciB0aGUgWSBheGlzLgogICAgICAgICAgICAgICAgLy8gU3RhcnQgd2l0aCB0aGF0IHJhbmdlLgogICAgICAgICAgICAgICAgdGhpcy5yZXNldFlEb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLm1lYXN1cmVCQm94QW5kTWF5YmVJbnZhbGlkYXRlTGF5b3V0SW5SYWYoKTsKICAgICAgICB9CiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICB3aW5kb3cuY2FuY2VsQW5pbWF0aW9uRnJhbWUodGhpcy5fcmVkcmF3UmFmKTsKICAgICAgICAgICAgdGhpcy5fcmVkcmF3UmFmID0gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLm1lYXN1cmVCQm94QW5kTWF5YmVJbnZhbGlkYXRlTGF5b3V0KCk7CiAgICAgICAgICAgICAgICB0aGlzLm91dGVyLnJlZHJhdygpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgbWVhc3VyZUJCb3hBbmRNYXliZUludmFsaWRhdGVMYXlvdXRJblJhZigpIHsKICAgICAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHRoaXMuX2ludmFsaWRhdGVMYXlvdXRSYWYpOwogICAgICAgICAgICB0aGlzLl9pbnZhbGlkYXRlTGF5b3V0UmFmID0gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLm1lYXN1cmVCQm94QW5kTWF5YmVJbnZhbGlkYXRlTGF5b3V0KCk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBNZWFzdXJlcyBib3VuZGluZyBib3ggb2YgdGhlIGFuY2hvciBub2RlIGFuZCBkZXRlcm1pbmVzIHdoZXRoZXIgdGhlIGxheW91dAogICAgICAgICAqIG5lZWRzIHRvIGJlIHJlLWRvbmUgd2l0aCBtZWFzdXJlbWVudCBjYWNoZSBpbnZhbGlkYXRlZC4gUGxvdHRhYmxlIGltcHJvdmVkCiAgICAgICAgICogcGVyZm9ybWFuY2Ugb2YgcmVuZGVyaW5nIGJ5IGNhY2hpbmcgZXhwZW5zaXZlIERPTSBtZWFzdXJlbWVudCBidXQgdGhpcwogICAgICAgICAqIGNhY2hlIGNhbiBiZSBwb2lzb25lZCBpbiBjYXNlIHRoZSBhbmNob3Igbm9kZSBpcyBpbiBhIHdyb25nIHN0YXRlIC0tIG5hbWVseQogICAgICAgICAqIGBkaXNwbGF5OiBub25lYCB3aGVyZSBhbGwgZGltZW5zaW9ucyBhcmUgMC4KICAgICAgICAgKi8KICAgICAgICBtZWFzdXJlQkJveEFuZE1heWJlSW52YWxpZGF0ZUxheW91dCgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2xhc3REcmF3QkJveCkgewogICAgICAgICAgICAgICAgY29uc3QgeyB3aWR0aDogcHJldldpZHRoIH0gPSB0aGlzLl9sYXN0RHJhd0JCb3g7CiAgICAgICAgICAgICAgICBjb25zdCB7IHdpZHRoIH0gPSB0aGlzLnRhcmdldFNWRy5ub2RlKCkuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgICAgICAgICBpZiAocHJldldpZHRoID09IDAgJiYgcHJldldpZHRoIDwgd2lkdGgpCiAgICAgICAgICAgICAgICAgICAgdGhpcy5vdXRlci5pbnZhbGlkYXRlQ2FjaGUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9sYXN0RHJhd0JCb3ggPSB0aGlzLnRhcmdldFNWRy5ub2RlKCkuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgfQogICAgICAgIGRlc3Ryb3koKSB7CiAgICAgICAgICAgIC8vIERlc3Ryb3lpbmcgb3V0ZXIgZGVzdHJveXMgYWxsIHN1YmNvbXBvbmVudHMgcmVjdXJzaXZlbHkuCiAgICAgICAgICAgIHdpbmRvdy5jYW5jZWxBbmltYXRpb25GcmFtZSh0aGlzLl9yZWRyYXdSYWYpOwogICAgICAgICAgICB3aW5kb3cuY2FuY2VsQW5pbWF0aW9uRnJhbWUodGhpcy5faW52YWxpZGF0ZUxheW91dFJhZik7CiAgICAgICAgICAgIGlmICh0aGlzLm91dGVyKQogICAgICAgICAgICAgICAgdGhpcy5vdXRlci5kZXN0cm95KCk7CiAgICAgICAgfQogICAgICAgIG9uQW5jaG9yKGZuKSB7CiAgICAgICAgICAgIGlmICh0aGlzLm91dGVyKQogICAgICAgICAgICAgICAgdGhpcy5vdXRlci5vbkFuY2hvcihmbik7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgZXh0ZW50IG9mIHJlbmRlcmVkIGRhdGEgdmFsdWVzIGZpdHMgdGhlIGN1cnJlbnQKICAgICAgICAgKiBjaGFydCB2aWV3cG9ydCBkb21haW4gKGluY2x1ZGVzIHNtb290aGluZyBhbmQgb3V0bGllciBkZXRlY3Rpb24pLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBpcyB0cnVlIHdoZW4gdGhlcmUgaXMgbm8gZGF0YSwgYW5kIGZhbHNlIHdoZW4gdGhlIGRvbWFpbiBoYXMgYmVlbgogICAgICAgICAqIHRyYW5zZm9ybWVkIGZyb20gdGhlIGV4dGVudCB2aWEgdHJhbnNmb3JtYXRpb25zIChwYW4sIHpvb20pLgogICAgICAgICAqLwogICAgICAgIGlzRGF0YUZpdFRvRG9tYWluKCkgewogICAgICAgICAgICByZXR1cm4gKGlzRGF0YUZpdFRvRG9tYWluKHRoaXMueEF4aXMuZ2V0U2NhbGUoKSkgJiYKICAgICAgICAgICAgICAgIGlzRGF0YUZpdFRvRG9tYWluKHRoaXMueUF4aXMuZ2V0U2NhbGUoKSkpOwogICAgICAgICAgICBmdW5jdGlvbiBpc0RhdGFGaXRUb0RvbWFpbihzY2FsZSkgewogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBEb21haW4gcmVwcmVzZW50cyB0aGUgY3VycmVudGx5IGRpc3BsYXllZCByZWdpb24sIHBvc3NpYmx5IGEgem9vbWVkCiAgICAgICAgICAgICAgICAgKiBpbiBvciB6b29tZWQgb3V0IHZpZXcgb2YgdGhlIGRhdGEuCiAgICAgICAgICAgICAgICAgKgogICAgICAgICAgICAgICAgICogRXh0ZW50IHJlcHJlc2VudHMgdGhlIGV4dGVudCBvZiB0aGUgZGF0YSwgdGhlIHJhbmdlIG9mIGFsbCBwcm92aWRlZAogICAgICAgICAgICAgICAgICogZGF0dW0gdmFsdWVzLgogICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICBjb25zdCBkb21haW4gPSBzY2FsZS5nZXRUcmFuc2Zvcm1hdGlvbkRvbWFpbigpOwogICAgICAgICAgICAgICAgY29uc3QgZXh0ZW50ID0gc2NhbGUuZ2V0VHJhbnNmb3JtYXRpb25FeHRlbnQoKTsKICAgICAgICAgICAgICAgIHJldHVybiBleHRlbnRbMF0gPT09IGRvbWFpblswXSAmJiBleHRlbnRbMV0gPT09IGRvbWFpblsxXTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxOCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHZhciBOb2RlTmFtZTsKICAgIChmdW5jdGlvbiAoTm9kZU5hbWUpIHsKICAgICAgICBOb2RlTmFtZVsiR1JPVVAiXSA9ICJHIjsKICAgICAgICBOb2RlTmFtZVsiRElWIl0gPSAiRElWIjsKICAgICAgICBOb2RlTmFtZVsiU1ZHIl0gPSAiU1ZHIjsKICAgICAgICBOb2RlTmFtZVsiVEVYVCJdID0gIlRFWFQiOwogICAgfSkoTm9kZU5hbWUgfHwgKE5vZGVOYW1lID0ge30pKTsKICAgIGNsYXNzIFBsb3R0YWJsZUV4cG9ydGVyIHsKICAgICAgICBjb25zdHJ1Y3Rvcihyb290RWwpIHsKICAgICAgICAgICAgdGhpcy51bmlxdWVJZCA9IDA7CiAgICAgICAgICAgIHRoaXMucm9vdCA9IHJvb3RFbDsKICAgICAgICB9CiAgICAgICAgZXhwb3J0QXNTdHJpbmcoKSB7CiAgICAgICAgICAgIGNvbnN0IGNvbnZlcnRlZE5vZGVzID0gdGhpcy5jb252ZXJ0KHRoaXMucm9vdCk7CiAgICAgICAgICAgIGlmICghY29udmVydGVkTm9kZXMpCiAgICAgICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgICAgIGNvbnN0IHN2ZyA9IHRoaXMuY3JlYXRlUm9vdFN2ZygpOwogICAgICAgICAgICBzdmcuYXBwZW5kQ2hpbGQoY29udmVydGVkTm9kZXMpOwogICAgICAgICAgICByZXR1cm4gc3ZnLm91dGVySFRNTDsKICAgICAgICB9CiAgICAgICAgY3JlYXRlVW5pcXVlSWQocHJlZml4KSB7CiAgICAgICAgICAgIHJldHVybiBgJHtwcmVmaXh9XyR7dGhpcy51bmlxdWVJZCsrfWA7CiAgICAgICAgfQogICAgICAgIGdldFNpemUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJvb3QuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgfQogICAgICAgIGNyZWF0ZVJvb3RTdmcoKSB7CiAgICAgICAgICAgIGNvbnN0IHN2ZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3N2ZycpOwogICAgICAgICAgICBjb25zdCByZWN0ID0gdGhpcy5nZXRTaXplKCk7CiAgICAgICAgICAgIC8vIGNhc2Ugb24gYHZpZXdCb3hgIGlzIHNlbnNpdGl2ZS4KICAgICAgICAgICAgc3ZnLnNldEF0dHJpYnV0ZU5TKCdzdmcnLCAndmlld0JveCcsIGAwIDAgJHtyZWN0LndpZHRofSAke3JlY3QuaGVpZ2h0fWApOwogICAgICAgICAgICBzdmcuc2V0QXR0cmlidXRlKCd4bWxucycsICdodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZycpOwogICAgICAgICAgICByZXR1cm4gc3ZnOwogICAgICAgIH0KICAgICAgICBjb252ZXJ0KG5vZGUpIHsKICAgICAgICAgICAgbGV0IG5ld05vZGUgPSBudWxsOwogICAgICAgICAgICBjb25zdCBub2RlTmFtZSA9IG5vZGUubm9kZU5hbWUudG9VcHBlckNhc2UoKTsKICAgICAgICAgICAgaWYgKG5vZGUubm9kZVR5cGUgPT0gTm9kZS5FTEVNRU5UX05PREUgJiYKICAgICAgICAgICAgICAgIChub2RlTmFtZSA9PSBOb2RlTmFtZS5ESVYgfHwgbm9kZU5hbWUgPT0gTm9kZU5hbWUuU1ZHKSkgewogICAgICAgICAgICAgICAgbmV3Tm9kZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoTm9kZU5hbWUuR1JPVVApOwogICAgICAgICAgICAgICAgY29uc3Qgc3R5bGUgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZShub2RlKTsKICAgICAgICAgICAgICAgIGNvbnN0IGxlZnQgPSBwYXJzZUludChzdHlsZS5sZWZ0LCAxMCk7CiAgICAgICAgICAgICAgICBjb25zdCB0b3AgPSBwYXJzZUludChzdHlsZS50b3AsIDEwKTsKICAgICAgICAgICAgICAgIGlmIChsZWZ0IHx8IHRvcCkgewogICAgICAgICAgICAgICAgICAgIGNvbnN0IGNsaXBJZCA9IHRoaXMuY3JlYXRlVW5pcXVlSWQoJ2NsaXAnKTsKICAgICAgICAgICAgICAgICAgICBuZXdOb2RlLnNldEF0dHJpYnV0ZSgndHJhbnNmb3JtJywgYHRyYW5zbGF0ZSgke2xlZnR9LCAke3RvcH0pYCk7CiAgICAgICAgICAgICAgICAgICAgbmV3Tm9kZS5zZXRBdHRyaWJ1dGUoJ2NsaXAtcGF0aCcsIGB1cmwoIyR7Y2xpcElkfSlgKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCB3aWR0aCA9IHBhcnNlSW50KHN0eWxlLndpZHRoLCAxMCk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgaGVpZ2h0ID0gcGFyc2VJbnQoc3R5bGUuaGVpZ2h0LCAxMCk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcmVjdCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3JlY3QnKTsKICAgICAgICAgICAgICAgICAgICByZWN0LnNldEF0dHJpYnV0ZSgnd2lkdGgnLCBTdHJpbmcod2lkdGgpKTsKICAgICAgICAgICAgICAgICAgICByZWN0LnNldEF0dHJpYnV0ZSgnaGVpZ2h0JywgU3RyaW5nKGhlaWdodCkpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IGNsaXBQYXRoID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCdzdmcnLCAnY2xpcFBhdGgnKTsKICAgICAgICAgICAgICAgICAgICBjbGlwUGF0aC5pZCA9IGNsaXBJZDsKICAgICAgICAgICAgICAgICAgICBjbGlwUGF0aC5hcHBlbmRDaGlsZChyZWN0KTsKICAgICAgICAgICAgICAgICAgICBuZXdOb2RlLmFwcGVuZENoaWxkKGNsaXBQYXRoKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIG5ld05vZGUgPSBub2RlLmNsb25lTm9kZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIEFycmF5LmZyb20obm9kZS5jaGlsZE5vZGVzKQogICAgICAgICAgICAgICAgLm1hcCgobm9kZSkgPT4gdGhpcy5jb252ZXJ0KG5vZGUpKQogICAgICAgICAgICAgICAgLmZpbHRlcihCb29sZWFuKQogICAgICAgICAgICAgICAgLmZvckVhY2goKGVsKSA9PiBuZXdOb2RlLmFwcGVuZENoaWxkKGVsKSk7CiAgICAgICAgICAgIC8vIFJlbW92ZSBlbXB0eSBncm91cGluZy4gVGhleSBhZGQgdG9vIG11Y2ggbm9pc2UuCiAgICAgICAgICAgIGNvbnN0IHNob3VsZE9taXQgPSAobmV3Tm9kZS5ub2RlTmFtZS50b1VwcGVyQ2FzZSgpID09IE5vZGVOYW1lLkdST1VQICYmCiAgICAgICAgICAgICAgICAhbmV3Tm9kZS5oYXNDaGlsZE5vZGVzKCkpIHx8CiAgICAgICAgICAgICAgICB0aGlzLnNob3VsZE9taXROb2RlKG5vZGUpOwogICAgICAgICAgICBpZiAoc2hvdWxkT21pdCkKICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICByZXR1cm4gdGhpcy5zdHJpcENsYXNzKHRoaXMudHJhbnNmZXJTdHlsZShub2RlLCBuZXdOb2RlKSk7CiAgICAgICAgfQogICAgICAgIHN0cmlwQ2xhc3Mobm9kZSkgewogICAgICAgICAgICBpZiAobm9kZS5ub2RlVHlwZSA9PSBOb2RlLkVMRU1FTlRfTk9ERSkgewogICAgICAgICAgICAgICAgbm9kZS5yZW1vdmVBdHRyaWJ1dGUoJ2NsYXNzJyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG5vZGU7CiAgICAgICAgfQogICAgICAgIHRyYW5zZmVyU3R5bGUob3JpZ05vZGUsIG5vZGUpIHsKICAgICAgICAgICAgaWYgKG5vZGUubm9kZVR5cGUgIT0gTm9kZS5FTEVNRU5UX05PREUpCiAgICAgICAgICAgICAgICByZXR1cm4gbm9kZTsKICAgICAgICAgICAgY29uc3QgZWwgPSBub2RlOwogICAgICAgICAgICBjb25zdCBub2RlTmFtZSA9IG5vZGUubm9kZU5hbWUudG9VcHBlckNhc2UoKTsKICAgICAgICAgICAgY29uc3Qgc3R5bGUgPSB3aW5kb3cuZ2V0Q29tcHV0ZWRTdHlsZShvcmlnTm9kZSk7CiAgICAgICAgICAgIGlmIChub2RlTmFtZSA9PSBOb2RlTmFtZS5URVhUKSB7CiAgICAgICAgICAgICAgICBPYmplY3QuYXNzaWduKGVsLnN0eWxlLCB7CiAgICAgICAgICAgICAgICAgICAgZm9udEZhbWlseTogc3R5bGUuZm9udEZhbWlseSwKICAgICAgICAgICAgICAgICAgICBmb250U2l6ZTogc3R5bGUuZm9udFNpemUsCiAgICAgICAgICAgICAgICAgICAgZm9udFdlaWdodDogc3R5bGUuZm9udFdlaWdodCwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChub2RlTmFtZSAhPSBOb2RlTmFtZS5HUk9VUCkgewogICAgICAgICAgICAgICAgZWwuc2V0QXR0cmlidXRlKCdmaWxsJywgc3R5bGUuZmlsbCk7CiAgICAgICAgICAgICAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZScsIHN0eWxlLnN0cm9rZSk7CiAgICAgICAgICAgICAgICBlbC5zZXRBdHRyaWJ1dGUoJ3N0cm9rZS13aWR0aCcsIHN0eWxlLnN0cm9rZVdpZHRoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc3R5bGUub3BhY2l0eSAhPSAnMScpCiAgICAgICAgICAgICAgICBlbC5zZXRBdHRyaWJ1dGUoJ29wYWNpdHknLCBzdHlsZS5vcGFjaXR5KTsKICAgICAgICAgICAgcmV0dXJuIG5vZGU7CiAgICAgICAgfQogICAgICAgIHNob3VsZE9taXROb2RlKG5vZGUpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgIH0KICAgIGNsYXNzIExpbmVDaGFydEV4cG9ydGVyIGV4dGVuZHMgUGxvdHRhYmxlRXhwb3J0ZXIgewogICAgICAgIHNob3VsZE9taXROb2RlKG5vZGUpIHsKICAgICAgICAgICAgLy8gU2NhdHRlciBwbG90IGlzIHVzZWZ1bCBmb3IgdG9vbHRpcC4gVG9vbHRpcCBpcyBtZWFuaW5nbGVzcyBpbiB0aGUKICAgICAgICAgICAgLy8gZXhwb3J0ZWQgc3ZnLgogICAgICAgICAgICBpZiAobm9kZS5ub2RlVHlwZSA9PSBOb2RlLkVMRU1FTlRfTk9ERSkgewogICAgICAgICAgICAgICAgcmV0dXJuIG5vZGUuY2xhc3NMaXN0LmNvbnRhaW5zKCdzY2F0dGVyLXBsb3QnKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE2IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgcmVnaXN0ZXJTdHlsZURvbU1vZHVsZSh7CiAgICAgICAgbW9kdWxlTmFtZTogJ3Z6LXBhbi16b29tLXN0eWxlJywKICAgICAgICBzdHlsZUNvbnRlbnQ6IGAKICAgIC5oZWxwIHsKICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgYW5pbWF0aW9uLWRlbGF5OiAxczsKICAgICAgYW5pbWF0aW9uLWR1cmF0aW9uOiAxczsKICAgICAgYW5pbWF0aW9uLW5hbWU6IGZhZGUtb3V0OwogICAgICBiYWNrZ3JvdW5kOiByZ2JhKDMwLCAzMCwgMzAsIDAuNik7CiAgICAgIGJvdHRvbTogMDsKICAgICAgY29sb3I6ICNmZmY7CiAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyOwogICAgICBsZWZ0OiAwOwogICAgICBvcGFjaXR5OiAxOwogICAgICBwYWRkaW5nOiAyMHB4OwogICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICByaWdodDogMDsKICAgICAgdG9wOiAwOwogICAgfQoKICAgIC5oZWxwID4gc3BhbiB7CiAgICAgIHdoaXRlLXNwYWNlOiBub3JtYWw7CiAgICB9CgogICAgQGtleWZyYW1lcyBmYWRlLW91dCB7CiAgICAgIDAlIHsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICB9CgogICAgICAxMDAlIHsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICB9CiAgICB9CiAgYCwKICAgIH0pOwoKICAgIGNvbnN0IHZhbHVlRm9ybWF0dGVyID0gbXVsdGlzY2FsZUZvcm1hdHRlcihZX1RPT0xUSVBfRk9STUFUVEVSX1BSRUNJU0lPTik7CiAgICBjb25zdCBmb3JtYXRWYWx1ZU9yTmFOID0gKHgpID0+IChpc05hTih4KSA/ICdOYU4nIDogdmFsdWVGb3JtYXR0ZXIoeCkpOwogICAgY29uc3QgREVGQVVMVF9UT09MVElQX0NPTFVNTlMgPSBbCiAgICAgICAgewogICAgICAgICAgICB0aXRsZTogJ05hbWUnLAogICAgICAgICAgICBldmFsdWF0ZTogKGQpID0+IGQuZGF0YXNldC5tZXRhZGF0YSgpLm5hbWUsCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIHRpdGxlOiAnU21vb3RoZWQnLAogICAgICAgICAgICBldmFsdWF0ZShkLCBzdGF0dXNPYmplY3QpIHsKICAgICAgICAgICAgICAgIGNvbnN0IHsgc21vb3RoaW5nRW5hYmxlZCB9ID0gc3RhdHVzT2JqZWN0OwogICAgICAgICAgICAgICAgcmV0dXJuIGZvcm1hdFZhbHVlT3JOYU4oc21vb3RoaW5nRW5hYmxlZCA/IGQuZGF0dW0uc21vb3RoZWQgOiBkLmRhdHVtLnNjYWxhcik7CiAgICAgICAgICAgIH0sCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIHRpdGxlOiAnVmFsdWUnLAogICAgICAgICAgICBldmFsdWF0ZTogKGQpID0+IGZvcm1hdFZhbHVlT3JOYU4oZC5kYXR1bS5zY2FsYXIpLAogICAgICAgIH0sCiAgICAgICAgewogICAgICAgICAgICB0aXRsZTogJ1N0ZXAnLAogICAgICAgICAgICBldmFsdWF0ZTogKGQpID0+IHN0ZXBGb3JtYXR0ZXIoZC5kYXR1bS5zdGVwKSwKICAgICAgICB9LAogICAgICAgIHsKICAgICAgICAgICAgdGl0bGU6ICdUaW1lJywKICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiB0aW1lRm9ybWF0dGVyKGQuZGF0dW0ud2FsbF90aW1lKSwKICAgICAgICB9LAogICAgICAgIHsKICAgICAgICAgICAgdGl0bGU6ICdSZWxhdGl2ZScsCiAgICAgICAgICAgIGV2YWx1YXRlOiAoZCkgPT4gcmVsYXRpdmVGb3JtYXR0ZXIocmVsYXRpdmVBY2Nlc3NvcihkLmRhdHVtLCAtMSwgZC5kYXRhc2V0KSksCiAgICAgICAgfSwKICAgIF07CiAgICBsZXQgVnpMaW5lQ2hhcnQyID0gY2xhc3MgVnpMaW5lQ2hhcnQyIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBTY2FsZSB0aGF0IG1hcHMgc2VyaWVzIG5hbWVzIHRvIGNvbG9ycy4gVGhlIGRlZmF1bHQgY29sb3JzIGFyZSBmcm9tCiAgICAgICAgICAgICAqIGQzLnNjaGVtZUNhdGVnb3J5MTAuIFVzZSB0aGlzIHByb3BlcnR5IHRvIHJlcGxhY2UgdGhlIGRlZmF1bHQgbGluZQogICAgICAgICAgICAgKiBjb2xvcnMgd2l0aCBjb2xvcnMgb2YgeW91ciBvd24gY2hvaWNlLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5jb2xvclNjYWxlID0gbmV3IHNyYyQyLlNjYWxlcy5Db2xvcigpLnJhbmdlKGNhdGVnb3J5MTAuc2xpY2UoMCkpOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogV2hldGhlciBzbW9vdGhpbmcgaXMgZW5hYmxlZCBvciBub3QuIElmIHRydWUsIHNtb290aGVkIGxpbmVzIHdpbGwgYmUKICAgICAgICAgICAgICogcGxvdHRlZCBpbiB0aGUgY2hhcnQgd2hpbGUgdGhlIHVuc21vb3RoZWQgbGluZXMgd2lsbCBiZSBnaG9zdGVkIGluCiAgICAgICAgICAgICAqIHRoZSBiYWNrZ3JvdW5kLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5zbW9vdGhpbmdFbmFibGVkID0gZmFsc2U7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBXZWlnaHQgKGJldHdlZW4gMC4wIGFuZCAxLjApIG9mIHRoZSBzbW9vdGhpbmcuIEEgdmFsdWUgb2YgMC4wCiAgICAgICAgICAgICAqIG1lYW5zIHZlcnkgbGl0dGxlIHNtb290aGluZywgcG9zc2libHkgbm8gc21vb3RoaW5nIGF0IGFsbC4gQQogICAgICAgICAgICAgKiB2YWx1ZSBvZiAxLjAgbWVhbnMgYSB3aG9sZSBsb3Qgb2Ygc21vb3RoaW5nLCBwb3NzaWJseSBzbyBtdWNoIGFzCiAgICAgICAgICAgICAqIHRvIG1ha2UgdGhlIHdob2xlIHBsb3QgYXBwZWFyIGFzIGEgY29uc3RhbnQgZnVuY3Rpb24uCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIEhhcyBubyBlZmZlY3Qgd2hlbiBgc21vb3RoaW5nRW5hYmxlZGAgaXMgYGZhbHNlYC4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMuc21vb3RoaW5nV2VpZ2h0ID0gMC42OwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogVGhpcyBpcyBhIGhlbHBlciBmaWVsZCBmb3IgYXV0b21hdGljYWxseSBnZW5lcmF0aW5nIGNvbW1vbmx5IHVzZWQKICAgICAgICAgICAgICogZnVuY3Rpb25zIGZvciB4Q29tcG9uZW50c0NyZWF0aW9uTWV0aG9kLiBWYWxpZCB2YWx1ZXMgYXJlIHdoYXQgY2FuCiAgICAgICAgICAgICAqIGJlIHByb2Nlc3NlZCBieSB2el9jaGFydF9oZWxwZXJzLmdldFhDb21wb25lbnRzKCkgYW5kIGluY2x1ZGUKICAgICAgICAgICAgICogInN0ZXAiLCAid2FsbF90aW1lIiwgYW5kICJyZWxhdGl2ZSIuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnhUeXBlID0gbnVsbDsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFdlIGFjY2VwdCBhIGZ1bmN0aW9uIGZvciBjcmVhdGluZyBhbiBYQ29tcG9uZW50cyBvYmplY3QgaW5zdGVhZCBvZiBzdWNoCiAgICAgICAgICAgICAqIGFuIG9iamVjdCBpdHNlbGYgYmVjYXVzZSB0aGUgQXhpcyBtdXN0IGJlIG1hZGUgcmlnaHQgd2hlbiB3ZSBtYWtlIHRoZQogICAgICAgICAgICAgKiBMaW5lQ2hhcnQgb2JqZWN0LCBsZXN0IHdlIHVzZSBhIHByZXZpb3VzbHkgZGVzdHJveWVkIEF4aXMuIFNlZSB0aGUgYXN5bmMKICAgICAgICAgICAgICogbG9naWMgYmVsb3cgdGhhdCB1c2VzIHRoaXMgcHJvcGVydHkuCiAgICAgICAgICAgICAqCiAgICAgICAgICAgICAqIE5vdGUgdGhhdCB0aGlzIGZ1bmN0aW9uIHJldHVybnMgYSBmdW5jdGlvbiBiZWNhdXNlIHBvbHltZXIgY2FsbHMgdGhlCiAgICAgICAgICAgICAqIG91dGVyIGZ1bmN0aW9uIHRvIGNvbXB1dGUgdGhlIHZhbHVlLiBXZSBhY3R1YWxseSB3YW50IHRoZSB2YWx1ZSBvZiB0aGlzCiAgICAgICAgICAgICAqIHByb3BlcnR5IHRvIGJlIHRoZSBpbm5lciBmdW5jdGlvbi4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMueENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZCA9IG51bGw7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBBIG1ldGhvZCB0aGF0IGltcGxlbWVudHMgdGhlIFBsb3R0YWJsZS5JQWNjZXNzb3I8bnVtYmVyPiBpbnRlcmZhY2UuIFVzZWQKICAgICAgICAgICAgICogZm9yIGFjY2Vzc2luZyB0aGUgeSB2YWx1ZSBmcm9tIGEgZGF0YSBwb2ludC4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICogTm90ZSB0aGF0IHRoaXMgZnVuY3Rpb24gcmV0dXJucyBhIGZ1bmN0aW9uIGJlY2F1c2UgcG9seW1lciBjYWxscyB0aGUKICAgICAgICAgICAgICogb3V0ZXIgZnVuY3Rpb24gdG8gY29tcHV0ZSB0aGUgdmFsdWUuIFdlIGFjdHVhbGx5IHdhbnQgdGhlIHZhbHVlIG9mIHRoaXMKICAgICAgICAgICAgICogcHJvcGVydHkgdG8gYmUgdGhlIGlubmVyIGZ1bmN0aW9uLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy55VmFsdWVBY2Nlc3NvciA9IChkKSA9PiBkLnNjYWxhcjsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEFuIGFycmF5IG9mIENoYXJ0SGVscGVyLlRvb2x0aXBDb2x1bW4gb2JqZWN0cy4gVXNlZCB0byBwb3B1bGF0ZSB0aGUgdGFibGUKICAgICAgICAgICAgICogd2l0aGluIHRoZSB0b29sdGlwLiBUaGUgdGFibGUgY29udGFpbnMgMSByb3cgcGVyIHJ1bi4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICogTm90ZSB0aGF0IHRoaXMgZnVuY3Rpb24gcmV0dXJucyBhIGZ1bmN0aW9uIGJlY2F1c2UgcG9seW1lciBjYWxscyB0aGUKICAgICAgICAgICAgICogb3V0ZXIgZnVuY3Rpb24gdG8gY29tcHV0ZSB0aGUgdmFsdWUuIFdlIGFjdHVhbGx5IHdhbnQgdGhlIHZhbHVlIG9mIHRoaXMKICAgICAgICAgICAgICogcHJvcGVydHkgdG8gYmUgdGhlIGlubmVyIGZ1bmN0aW9uLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy50b29sdGlwQ29sdW1ucyA9IERFRkFVTFRfVE9PTFRJUF9DT0xVTU5TOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogVGhlIHNjYWxlIGZvciB0aGUgeS1heGlzLiBBbGxvd3M6CiAgICAgICAgICAgICAqIC0gImxpbmVhciIgLSBsaW5lYXIgc2NhbGUgKFBsb3R0YWJsZS5TY2FsZXMuTGluZWFyKQogICAgICAgICAgICAgKiAtICJsb2ciIC0gbW9kaWZpZWQtbG9nIHNjYWxlIChQbG90dGFibGUuU2NhbGVzLk1vZGlmaWVkTG9nKQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy55U2NhbGVUeXBlID0gWVNjYWxlVHlwZS5MSU5FQVI7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBXaGV0aGVyIHRvIGlnbm9yZSBvdXRsaWVyIGRhdGEgd2hlbiBjb21wdXRpbmcgdGhlIHlTY2FsZSBkb21haW4uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmlnbm9yZVlPdXRsaWVycyA9IGZhbHNlOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQ2hhbmdlIGhvdyB0aGUgdG9vbHRpcCBpcyBzb3J0ZWQuIEFsbG93czoKICAgICAgICAgICAgICogLSAiZGVmYXVsdCIgLSBTb3J0IHRoZSB0b29sdGlwIGJ5IGlucHV0IG9yZGVyLgogICAgICAgICAgICAgKiAtICJhc2NlbmRpbmciIC0gU29ydCB0aGUgdG9vbHRpcCBieSBhc2NlbmRpbmcgdmFsdWUuCiAgICAgICAgICAgICAqIC0gImRlc2NlbmRpbmciIC0gU29ydCB0aGUgdG9vbHRpcCBieSBkZXNjZW5kaW5nIHZhbHVlLgogICAgICAgICAgICAgKiAtICJuZWFyZXN0IiAtIFNvcnQgdGhlIHRvb2x0aXAgYnkgY2xvc2VzdCB0byBjdXJzb3IuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnRvb2x0aXBTb3J0aW5nTWV0aG9kID0gJ2RlZmF1bHQnOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQ2hhbmdlcyBob3cgdGhlIHRvb2x0aXAgaXMgcG9zaXRpb25lZC4gQWxsb3dzOgogICAgICAgICAgICAgKiAtICJib3R0b20iIC0gUG9zaXRpb24gdGhlIHRvb2x0aXAgb24gdGhlIGJvdHRvbSBvZiB0aGUgY2hhcnQuCiAgICAgICAgICAgICAqIC0gInJpZ2h0IiAtIFBvc2l0aW9uIHRoZSB0b29sdGlwIHRvIHRoZSByaWdodCBvZiB0aGUgY2hhcnQuCiAgICAgICAgICAgICAqIC0gImF1dG8iIC0gUG9zaXRpb24gdGhlIHRvb2x0aXAgdG8gdGhlIGJvdHRvbSBvZiB0aGUgY2hhcnQgaW4gbW9zdCBjYXNlLgogICAgICAgICAgICAgKiAgICAgICAgICAgIFBvc2l0aW9uIHRoZSB0b29sdGlwIGFib3ZlIHRoZSBjaGFydCBpZiB0aGVyZSBpc24ndCBzdWZmaWNpZW50CiAgICAgICAgICAgICAqICAgICAgICAgICAgc3BhY2UgYmVsb3cuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnRvb2x0aXBQb3NpdGlvbiA9IFRvb2x0aXBQb3NpdGlvbi5CT1RUT007CiAgICAgICAgICAgIHRoaXMuX3Zpc2libGVTZXJpZXNDYWNoZSA9IFtdOwogICAgICAgICAgICB0aGlzLl9zZXJpZXNEYXRhQ2FjaGUgPSB7fTsKICAgICAgICAgICAgdGhpcy5fc2VyaWVzTWV0YWRhdGFDYWNoZSA9IHt9OwogICAgICAgICAgICB0aGlzLl9tYWtlQ2hhcnRBc3luY0NhbGxiYWNrSWQgPSBudWxsOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgdGhpcy5zY29wZVN1YnRyZWUodGhpcy4kLmNoYXJ0ZGl2LCB0cnVlKTsKICAgICAgICB9CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIC8vIGBjYXB0dXJlYCBlbnN1cmVzIHRoYXQgbm8gaGFuZGxlciBjYW4gc3RvcCBwcm9wYWdhdGlvbiBhbmQgYnJlYWsgdGhlCiAgICAgICAgICAgIC8vIGhhbmRsZXIuIGBwYXNzaXZlYCBlbnN1cmVzIHRoYXQgYnJvd3NlciBkb2VzIG5vdCB3YWl0IHJlbmRlcmVyIHRocmVhZAogICAgICAgICAgICAvLyBvbiBKUyBoYW5kbGVyICh3aGljaCBjYW4gcHJldmVudCBkZWZhdWx0IGFuZCBpbXBhY3QgcmVuZGVyaW5nKS4KICAgICAgICAgICAgY29uc3Qgb3B0aW9uID0geyBjYXB0dXJlOiB0cnVlLCBwYXNzaXZlOiB0cnVlIH07CiAgICAgICAgICAgIHRoaXMuX2xpc3Rlbih0aGlzLCAnbW91c2Vkb3duJywgdGhpcy5fb25Nb3VzZURvd24uYmluZCh0aGlzKSwgb3B0aW9uKTsKICAgICAgICAgICAgdGhpcy5fbGlzdGVuKHRoaXMsICdtb3VzZXVwJywgdGhpcy5fb25Nb3VzZVVwLmJpbmQodGhpcyksIG9wdGlvbik7CiAgICAgICAgICAgIHRoaXMuX2xpc3Rlbih3aW5kb3csICdrZXlkb3duJywgdGhpcy5fb25LZXlEb3duLmJpbmQodGhpcyksIG9wdGlvbik7CiAgICAgICAgICAgIHRoaXMuX2xpc3Rlbih3aW5kb3csICdrZXl1cCcsIHRoaXMuX29uS2V5VXAuYmluZCh0aGlzKSwgb3B0aW9uKTsKICAgICAgICB9CiAgICAgICAgZGV0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuY2FuY2VsQXN5bmModGhpcy5fbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkKTsKICAgICAgICAgICAgaWYgKHRoaXMuX2NoYXJ0KSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydC5kZXN0cm95KCk7CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydCA9IHVuZGVmaW5lZDsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5fbGlzdGVuZXJzKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9saXN0ZW5lcnMuZm9yRWFjaCgoeyBub2RlLCBldmVudE5hbWUsIGZ1bmMsIG9wdGlvbiB9KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgbm9kZS5yZW1vdmVFdmVudExpc3RlbmVyKGV2ZW50TmFtZSwgZnVuYywgb3B0aW9uKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fbGlzdGVuZXJzLmNsZWFyKCk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgX2xpc3Rlbihub2RlLCBldmVudE5hbWUsIGZ1bmMsIG9wdGlvbiA9IHt9KSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fbGlzdGVuZXJzKQogICAgICAgICAgICAgICAgdGhpcy5fbGlzdGVuZXJzID0gbmV3IFNldCgpOwogICAgICAgICAgICB0aGlzLl9saXN0ZW5lcnMuYWRkKHsgbm9kZSwgZXZlbnROYW1lLCBmdW5jLCBvcHRpb24gfSk7CiAgICAgICAgICAgIG5vZGUuYWRkRXZlbnRMaXN0ZW5lcihldmVudE5hbWUsIGZ1bmMsIG9wdGlvbik7CiAgICAgICAgfQogICAgICAgIF9vbktleURvd24oZXZlbnQpIHsKICAgICAgICAgICAgdGhpcy50b2dnbGVDbGFzcygncGFua2V5JywgUGFuWm9vbURyYWdMYXllci5pc1BhbktleShldmVudCkpOwogICAgICAgIH0KICAgICAgICBfb25LZXlVcChldmVudCkgewogICAgICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdwYW5rZXknLCBQYW5ab29tRHJhZ0xheWVyLmlzUGFuS2V5KGV2ZW50KSk7CiAgICAgICAgfQogICAgICAgIF9vbk1vdXNlRG93bihldmVudCkgewogICAgICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdtb3VzZWRvd24nLCB0cnVlKTsKICAgICAgICB9CiAgICAgICAgX29uTW91c2VVcChldmVudCkgewogICAgICAgICAgICB0aGlzLnRvZ2dsZUNsYXNzKCdtb3VzZWRvd24nLCBmYWxzZSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgd2hldGhlciB0aGUgZXh0ZW50IG9mIHJlbmRlcmVkIGRhdGEgdmFsdWVzIGZpdHMgdGhlIGN1cnJlbnQKICAgICAgICAgKiBjaGFydCB2aWV3cG9ydCBkb21haW4gKGluY2x1ZGVzIHNtb290aGluZyBhbmQgb3V0bGllciBkZXRlY3Rpb24pLgogICAgICAgICAqCiAgICAgICAgICogVGhpcyBpcyB0cnVlIHdoZW4gdGhlcmUgaXMgbm8gZGF0YSwgYW5kIGZhbHNlIHdoZW4gdGhlIGRvbWFpbiBoYXMgYmVlbgogICAgICAgICAqIHRyYW5zZm9ybWVkIGZyb20gdGhlIGV4dGVudCB2aWEgdHJhbnNmb3JtYXRpb25zIChwYW4sIHpvb20pLgogICAgICAgICAqLwogICAgICAgIGlzRGF0YUZpdFRvRG9tYWluKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fY2hhcnQgPyB0aGlzLl9jaGFydC5pc0RhdGFGaXRUb0RvbWFpbigpIDogdHJ1ZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyB0aGUgc2VyaWVzIHRoYXQgdGhlIGNoYXJ0IGRpc3BsYXlzLiBTZXJpZXMgd2l0aCBvdGhlciBuYW1lcyB3aWxsCiAgICAgICAgICogbm90IGJlIGRpc3BsYXllZC4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7QXJyYXk8U3RyaW5nPn0gbmFtZXMgQXJyYXkgd2l0aCB0aGUgbmFtZXMgb2YgdGhlIHNlcmllcyB0bwogICAgICAgICAqIGRpc3BsYXkuCiAgICAgICAgICovCiAgICAgICAgc2V0VmlzaWJsZVNlcmllcyhuYW1lcykgewogICAgICAgICAgICBpZiAobG9kYXNoLmlzRXF1YWwodGhpcy5fdmlzaWJsZVNlcmllc0NhY2hlLCBuYW1lcykpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIHRoaXMuX3Zpc2libGVTZXJpZXNDYWNoZSA9IG5hbWVzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBkYXRhIG9mIG9uZSBvZiB0aGUgc2VyaWVzLiBOb3RlIHRoYXQgdG8gZGlzcGxheSB0aGlzIHNlcmllcwogICAgICAgICAqIGl0cyBuYW1lIG11c3QgYmUgaW4gdGhlIHNldFZpc2libGVTZXJpZXMoKSBhcnJheS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgdGhlIHNlcmllcy4KICAgICAgICAgKiBAcGFyYW0ge0FycmF5PCF2el9jaGFydF9oZWxwZXJzLlNjYWxhckRhdHVtPn0gZGF0YSBEYXRhIG9mIHRoZSBzZXJpZXMuCiAgICAgICAgICogVGhpcyBpcyBhbiBhcnJheSBvZiBvYmplY3RzIHdpdGggYXQgbGVhc3QgdGhlIGZvbGxvd2luZyBwcm9wZXJ0aWVzOgogICAgICAgICAqIC0gc3RlcDogKE51bWJlcikgLSBpbmRleCBvZiB0aGUgZGF0dW0uCiAgICAgICAgICogLSB3YWxsX3RpbWU6IChEYXRlKSAtIERhdGUgb2JqZWN0IHdpdGggdGhlIGRhdHVtJ3MgdGltZS4KICAgICAgICAgKiAtIHNjYWxhcjogKE51bWJlcikgLSBWYWx1ZSBvZiB0aGUgZGF0dW0uCiAgICAgICAgICovCiAgICAgICAgc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKSB7CiAgICAgICAgICAgIHRoaXMuX3Nlcmllc0RhdGFDYWNoZVtuYW1lXSA9IGRhdGE7CiAgICAgICAgICAgIGlmICh0aGlzLl9jaGFydCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQuc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBTZXRzIHRoZSBtZXRhZGF0YSBvZiBvbmUgb2YgdGhlIHNlcmllcy4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIE5hbWUgb2YgdGhlIHNlcmllcy4KICAgICAgICAgKiBAcGFyYW0geyp9IG1ldGEgTWV0YWRhdGEgb2YgdGhlIGRhdGFzZXQgdXNlZCBmb3IgbGF0ZXIKICAgICAgICAgKi8KICAgICAgICBzZXRTZXJpZXNNZXRhZGF0YShuYW1lLCBtZXRhKSB7CiAgICAgICAgICAgIHRoaXMuX3Nlcmllc01ldGFkYXRhQ2FjaGVbbmFtZV0gPSBtZXRhOwogICAgICAgICAgICBpZiAodGhpcy5fY2hhcnQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldFNlcmllc01ldGFkYXRhKG5hbWUsIG1ldGEpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGNvbW1pdENoYW5nZXMoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fY2hhcnQpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIHRoaXMuX2NoYXJ0LmNvbW1pdENoYW5nZXMoKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmVzZXQgdGhlIGNoYXJ0IGRvbWFpbi4gSWYgdGhlIGNoYXJ0IGhhcyBub3QgcmVuZGVyZWQgeWV0LCBhIGNhbGwgdG8gdGhpcwogICAgICAgICAqIG1ldGhvZCBuby1vcHMuCiAgICAgICAgICovCiAgICAgICAgcmVzZXREb21haW4oKSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9jaGFydCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQucmVzZXREb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZS1yZW5kZXJzIHRoZSBjaGFydC4gVXNlZnVsIGlmIGUuZy4gdGhlIGNvbnRhaW5lciBzaXplIGNoYW5nZWQuCiAgICAgICAgICovCiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICBpZiAodGhpcy5fY2hhcnQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnJlZHJhdygpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIENyZWF0ZXMgYSBjaGFydCwgYW5kIGFzeW5jaHJvbm91c2x5IHJlbmRlcnMgaXQuIEZpcmVzIGEgY2hhcnQtcmVuZGVyZWQKICAgICAgICAgKiBldmVudCBhZnRlciB0aGUgY2hhcnQgaXMgcmVuZGVyZWQuCiAgICAgICAgICovCiAgICAgICAgX21ha2VDaGFydCgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX21ha2VDaGFydEFzeW5jQ2FsbGJhY2tJZCAhPT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5jYW5jZWxBc3luYyh0aGlzLl9tYWtlQ2hhcnRBc3luY0NhbGxiYWNrSWQpOwogICAgICAgICAgICAgICAgdGhpcy5fbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkID0gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9tYWtlQ2hhcnRBc3luY0NhbGxiYWNrSWQgPSB0aGlzLmFzeW5jKGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIHRoaXMuX21ha2VDaGFydEFzeW5jQ2FsbGJhY2tJZCA9IG51bGw7CiAgICAgICAgICAgICAgICAvLyBGaW5kIHRoZSBhY3R1YWwgeENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZC4KICAgICAgICAgICAgICAgIGxldCBub3JtYWxYQ29tcG9uZW50c0NyZWF0aW9uTWV0aG9kID0gdGhpcy54Q29tcG9uZW50c0NyZWF0aW9uTWV0aG9kOwogICAgICAgICAgICAgICAgaWYgKCF0aGlzLnhUeXBlICYmICFub3JtYWxYQ29tcG9uZW50c0NyZWF0aW9uTWV0aG9kKSB7CiAgICAgICAgICAgICAgICAgICAgbm9ybWFsWENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZCA9IHN0ZXBYOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAodGhpcy54VHlwZSkgewogICAgICAgICAgICAgICAgICAgIG5vcm1hbFhDb21wb25lbnRzQ3JlYXRpb25NZXRob2QgPSAoKSA9PiBnZXRYQ29tcG9uZW50cyh0aGlzLnhUeXBlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICghbm9ybWFsWENvbXBvbmVudHNDcmVhdGlvbk1ldGhvZCB8fAogICAgICAgICAgICAgICAgICAgICF0aGlzLnlWYWx1ZUFjY2Vzc29yIHx8CiAgICAgICAgICAgICAgICAgICAgIXRoaXMudG9vbHRpcENvbHVtbnMpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBXZSBkaXJlY3RseSByZWZlcmVuY2UgcHJvcGVydGllcyBvZiBgdGhpc2AgYmVjYXVzZSB0aGlzIGNhbGwgaXMKICAgICAgICAgICAgICAgIC8vIGFzeW5jaHJvbm91cywgYW5kIHZhbHVlcyBtYXkgaGF2ZSBjaGFuZ2VkIGluIGJldHdlZW4gdGhlIGNhbGwgYmVpbmcKICAgICAgICAgICAgICAgIC8vIGluaXRpYXRlZCBhbmQgYWN0dWFsbHkgYmVpbmcgcnVuLgogICAgICAgICAgICAgICAgdmFyIGNoYXJ0ID0gbmV3IExpbmVDaGFydChub3JtYWxYQ29tcG9uZW50c0NyZWF0aW9uTWV0aG9kLCB0aGlzLnlWYWx1ZUFjY2Vzc29yLCB0aGlzLnlTY2FsZVR5cGUsIHRoaXMuY29sb3JTY2FsZSwgdGhpcy4kLnRvb2x0aXAsIHRoaXMudG9vbHRpcENvbHVtbnMsIHRoaXMuZmlsbEFyZWEsIHRoaXMuZGVmYXVsdFhSYW5nZSwgdGhpcy5kZWZhdWx0WVJhbmdlLCB0aGlzLnN5bWJvbEZ1bmN0aW9uLCB0aGlzLnhBeGlzRm9ybWF0dGVyKTsKICAgICAgICAgICAgICAgIHZhciBkaXYgPSBzZWxlY3QodGhpcy4kLmNoYXJ0ZGl2KTsKICAgICAgICAgICAgICAgIGNoYXJ0LnJlbmRlclRvKGRpdik7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5fY2hhcnQpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLl9jaGFydC5kZXN0cm95KCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydCA9IGNoYXJ0OwogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQub25BbmNob3IoKCkgPT4gdGhpcy5maXJlKCdjaGFydC1hdHRhY2hlZCcpKTsKICAgICAgICAgICAgfSwgMzUwKTsKICAgICAgICB9CiAgICAgICAgX3JlbG9hZEZyb21DYWNoZSgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9jaGFydCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgdGhpcy5fdmlzaWJsZVNlcmllc0NhY2hlLmZvckVhY2goKG5hbWUpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldFNlcmllc0RhdGEobmFtZSwgdGhpcy5fc2VyaWVzRGF0YUNhY2hlW25hbWVdIHx8IFtdKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX3Zpc2libGVTZXJpZXNDYWNoZQogICAgICAgICAgICAgICAgLmZpbHRlcigobmFtZSkgPT4gdGhpcy5fc2VyaWVzTWV0YWRhdGFDYWNoZVtuYW1lXSkKICAgICAgICAgICAgICAgIC5mb3JFYWNoKChuYW1lKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydC5zZXRTZXJpZXNNZXRhZGF0YShuYW1lLCB0aGlzLl9zZXJpZXNNZXRhZGF0YUNhY2hlW25hbWVdKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldFZpc2libGVTZXJpZXModGhpcy5fdmlzaWJsZVNlcmllc0NhY2hlKTsKICAgICAgICAgICAgdGhpcy5fY2hhcnQuY29tbWl0Q2hhbmdlcygpOwogICAgICAgIH0KICAgICAgICBfc21vb3RoaW5nQ2hhbmdlZCgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9jaGFydCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgaWYgKHRoaXMuc21vb3RoaW5nRW5hYmxlZCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQuc21vb3RoaW5nVXBkYXRlKHRoaXMuc21vb3RoaW5nV2VpZ2h0KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNtb290aGluZ0Rpc2FibGUoKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfb3V0bGllcnNDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX2NoYXJ0KQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB0aGlzLl9jaGFydC5pZ25vcmVZT3V0bGllcnModGhpcy5pZ25vcmVZT3V0bGllcnMpOwogICAgICAgIH0KICAgICAgICBfY29sb3JTY2FsZUNoYW5nZWQoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fY2hhcnQpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldENvbG9yU2NhbGUodGhpcy5jb2xvclNjYWxlKTsKICAgICAgICAgICAgdGhpcy5fY2hhcnQucmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIF90b29sdGlwQ29sdW1uc0NoYW5nZWQoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fY2hhcnQpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldFRvb2x0aXBDb2x1bW5zKHRoaXMudG9vbHRpcENvbHVtbnMpOwogICAgICAgIH0KICAgICAgICBfdG9vbHRpcFNvcnRpbmdNZXRob2RDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX2NoYXJ0KQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB0aGlzLl9jaGFydC5zZXRUb29sdGlwU29ydGluZ01ldGhvZCh0aGlzLnRvb2x0aXBTb3J0aW5nTWV0aG9kKTsKICAgICAgICB9CiAgICAgICAgZ2V0RXhwb3J0ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgTGluZUNoYXJ0RXhwb3J0ZXIodGhpcy4kLmNoYXJ0ZGl2KTsKICAgICAgICB9CiAgICB9OwogICAgVnpMaW5lQ2hhcnQyLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJjaGFydGRpdiI+PC9kaXY+CiAgICA8dnotY2hhcnQtdG9vbHRpcAogICAgICBpZD0idG9vbHRpcCIKICAgICAgcG9zaXRpb249IltbdG9vbHRpcFBvc2l0aW9uXV0iCiAgICAgIGNvbnRlbnQtY29tcG9uZW50LW5hbWU9InZ6LWxpbmUtY2hhcnQtdG9vbHRpcCIKICAgID48L3Z6LWNoYXJ0LXRvb2x0aXA+CiAgICA8c3R5bGUgaW5jbHVkZT0icGxvdHRhYmxlLXN0eWxlIj48L3N0eWxlPgogICAgPHN0eWxlIGluY2x1ZGU9InZ6LXBhbi16b29tLXN0eWxlIj48L3N0eWxlPgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgLW1vei11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgb3V0bGluZTogbm9uZTsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgICAgfQogICAgICBkaXYgewogICAgICAgIC13ZWJraXQtdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLW1vei11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgIH0KCiAgICAgICNjaGFydGRpdiAubWFpbiB7CiAgICAgICAgY29udGFpbjogc3RyaWN0OwogICAgICAgIGN1cnNvcjogY3Jvc3NoYWlyOwogICAgICB9CgogICAgICA6aG9zdCgucGFua2V5KSAjY2hhcnRkaXYgOm5vdCguZHJhZy16b29taW5nKSAubWFpbiB7CiAgICAgICAgY3Vyc29yOiAtd2Via2l0LWdyYWI7CiAgICAgICAgY3Vyc29yOiBncmFiOwogICAgICB9CgogICAgICA6aG9zdCgubW91c2Vkb3duKSAjY2hhcnRkaXYgLnBhbm5pbmcgLm1haW4gewogICAgICAgIGN1cnNvcjogLXdlYmtpdC1ncmFiYmluZzsKICAgICAgICBjdXJzb3I6IGdyYWJiaW5nOwogICAgICB9CgogICAgICAjY2hhcnRkaXYgewogICAgICAgIGNvbnRhaW46IHN0cmljdDsKICAgICAgfQoKICAgICAgI2NoYXJ0ZGl2IGxpbmUuZ3VpZGUtbGluZSB7CiAgICAgICAgc3Ryb2tlOiAjOTk5OwogICAgICAgIHN0cm9rZS13aWR0aDogMS41cHg7CiAgICAgIH0KICAgICAgI2NoYXJ0ZGl2OmhvdmVyIC5tYWluIHsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CgogICAgICAuZ2hvc3QgewogICAgICAgIG9wYWNpdHk6IDAuMjsKICAgICAgICBzdHJva2Utd2lkdGg6IDFweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBzcmMkMi5TY2FsZXMuQ29sb3IpCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiY29sb3JTY2FsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInN5bWJvbEZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJzbW9vdGhpbmdFbmFibGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInNtb290aGluZ1dlaWdodCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJ4VHlwZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInhDb21wb25lbnRzQ3JlYXRpb25NZXRob2QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbikKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJ4QXhpc0Zvcm1hdHRlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInlWYWx1ZUFjY2Vzc29yIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJ0b29sdGlwQ29sdW1ucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJmaWxsQXJlYSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiZGVmYXVsdFhSYW5nZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiZGVmYXVsdFlSYW5nZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJ5U2NhbGVUeXBlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiaWdub3JlWU91dGxpZXJzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInRvb2x0aXBTb3J0aW5nTWV0aG9kIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgInRvb2x0aXBQb3NpdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfY2hhcnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgIl92aXNpYmxlU2VyaWVzQ2FjaGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiX3Nlcmllc0RhdGFDYWNoZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfc2VyaWVzTWV0YWRhdGFDYWNoZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3hDb21wb25lbnRzQ3JlYXRpb25NZXRob2QnLCAneFR5cGUnLCAneVZhbHVlQWNjZXNzb3InLCAneVNjYWxlVHlwZScsICdpc0F0dGFjaGVkJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiX21ha2VDaGFydCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX2NoYXJ0JywgJ192aXNpYmxlU2VyaWVzQ2FjaGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfcmVsb2FkRnJvbUNhY2hlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdzbW9vdGhpbmdFbmFibGVkJywgJ3Ntb290aGluZ1dlaWdodCcsICdfY2hhcnQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfc21vb3RoaW5nQ2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnaWdub3JlWU91dGxpZXJzJywgJ19jaGFydCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVnpMaW5lQ2hhcnQyLnByb3RvdHlwZSwgIl9vdXRsaWVyc0NoYW5nZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ2NvbG9yU2NhbGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFZ6TGluZUNoYXJ0Mi5wcm90b3R5cGUsICJfY29sb3JTY2FsZUNoYW5nZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3Rvb2x0aXBDb2x1bW5zJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiX3Rvb2x0aXBDb2x1bW5zQ2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgndG9vbHRpcFNvcnRpbmdNZXRob2QnLCAnX2NoYXJ0JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBWekxpbmVDaGFydDIucHJvdG90eXBlLCAiX3Rvb2x0aXBTb3J0aW5nTWV0aG9kQ2hhbmdlZCIsIG51bGwpOwogICAgVnpMaW5lQ2hhcnQyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndnotbGluZS1jaGFydDInKQogICAgXSwgVnpMaW5lQ2hhcnQyKTsKICAgIGxldCBWekxpbmVDaGFydFRvb2x0aXAgPSBjbGFzcyBWekxpbmVDaGFydFRvb2x0aXAgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICB9OwogICAgVnpMaW5lQ2hhcnRUb29sdGlwLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGNsYXNzPSJjb250ZW50Ij4KICAgICAgPHRhYmxlPgogICAgICAgIDx0aGVhZD48L3RoZWFkPgogICAgICAgIDx0Ym9keT48L3Rib2R5PgogICAgICA8L3RhYmxlPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQoKICAgICAgLmNvbnRlbnQgewogICAgICAgIGJhY2tncm91bmQ6IHJnYmEoMCwgMCwgMCwgMC44KTsKICAgICAgICBib3JkZXItcmFkaXVzOiA0cHg7CiAgICAgICAgY29sb3I6ICNmZmY7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQoKICAgICAgdGFibGUgewogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBsaW5lLWhlaWdodDogMS40ZW07CiAgICAgICAgbWFyZ2luLXRvcDogMTBweDsKICAgICAgICBwYWRkaW5nOiA4cHg7CiAgICAgIH0KCiAgICAgIHRoZWFkIHsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgIH0KCiAgICAgIHRib2R5IHsKICAgICAgICBmb250LXNpemU6IDEzcHg7CiAgICAgICAgbGluZS1oZWlnaHQ6IDIxcHg7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgICAgfQoKICAgICAgdGQgewogICAgICAgIHBhZGRpbmc6IDAgNXB4OwogICAgICB9CgogICAgICAuc3dhdGNoIHsKICAgICAgICBib3JkZXItcmFkaXVzOiA1MCU7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgaGVpZ2h0OiAxOHB4OwogICAgICAgIHdpZHRoOiAxOHB4OwogICAgICB9CgogICAgICAuY2xvc2VzdCAuc3dhdGNoIHsKICAgICAgICBib3gtc2hhZG93OiBpbnNldCAwIDAgMCAycHggI2ZmZjsKICAgICAgfQoKICAgICAgdGggewogICAgICAgIHBhZGRpbmc6IDAgNXB4OwogICAgICAgIHRleHQtYWxpZ246IGxlZnQ7CiAgICAgIH0KCiAgICAgIC5kaXN0YW50IHRkOm5vdCguc3dhdGNoKSB7CiAgICAgICAgb3BhY2l0eTogMC44OwogICAgICB9CgogICAgICAuZ2hvc3QgewogICAgICAgIG9wYWNpdHk6IDAuMjsKICAgICAgICBzdHJva2Utd2lkdGg6IDFweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgVnpMaW5lQ2hhcnRUb29sdGlwID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndnotbGluZS1jaGFydC10b29sdGlwJykKICAgIF0sIFZ6TGluZUNoYXJ0VG9vbHRpcCk7CgogICAgLy8gVGhlIGNoYXJ0IGNhbiBzb21ldGltZXMgZ2V0IGluIGEgYmFkIHN0YXRlLCB3aGVuIGl0IHJlZHJhd3Mgd2hpbGUKICAgIC8vIGl0IGlzIGRpc3BsYXk6IG5vbmUgZHVlIHRvIHRoZSB1c2VyIGhhdmluZyBzd2l0Y2hlZCB0byBhIGRpZmZlcmVudAogICAgLy8gcGFnZS4gVGhpcyBjb2RlIGltcGxlbWVudHMgYSBjYXNjYWRpbmcgcXVldWUgdG8gcmVkcmF3IHRoZSBiYWQgY2hhcnRzCiAgICAvLyBvbmUtYnktb25lIG9uY2UgdGhleSBhcmUgYWN0aXZlIGFnYWluLgogICAgLy8gV2UgdXNlIGEgY2FzY2FkaW5nIHF1ZXVlIGJlY3Vhc2Ugd2UgZG9uJ3Qgd2FudCB0byBibG9jayB0aGUgVUkgLyBtYWtlIHRoZQogICAgLy8gcmlwcGxlcyB2ZXJ5IHNsb3cgd2hpbGUgZXZlcnl0aGluZyBzeW5jaHJvbm91c2x5IHJlZHJhd3MuCiAgICBjb25zdCByZWRyYXdRdWV1ZSA9IFtdOwogICAgbGV0IHJlZHJhd1JhZiA9IDA7CiAgICBjb25zdCBjYXNjYWRpbmdSZWRyYXcgPSBsb2Rhc2gudGhyb3R0bGUoZnVuY3Rpb24gaW50ZXJuYWxSZWRyYXcoKSB7CiAgICAgICAgaWYgKHJlZHJhd1F1ZXVlLmxlbmd0aCA9PSAwKQogICAgICAgICAgICByZXR1cm47CiAgICAgICAgY29uc3QgeCA9IHJlZHJhd1F1ZXVlLnNoaWZ0KCk7CiAgICAgICAgaWYgKHggJiYgeC5hY3RpdmUpIHsKICAgICAgICAgICAgeC5yZWRyYXcoKTsKICAgICAgICAgICAgeC5fbWF5YmVSZW5kZXJlZEluQmFkU3RhdGUgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgd2luZG93LmNhbmNlbEFuaW1hdGlvbkZyYW1lKHJlZHJhd1JhZik7CiAgICAgICAgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZShpbnRlcm5hbFJlZHJhdyk7CiAgICB9LCAxMDApOwogICAgLy8gQSBjb21wb25lbnQgdGhhdCBmZXRjaGVzIGRhdGEgZnJvbSB0aGUgVGVuc29yQm9hcmQgc2VydmVyIGFuZCByZW5kZXJzIGl0IGludG8KICAgIC8vIGEgdnotbGluZS1jaGFydC4KICAgIGxldCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyID0gY2xhc3MgX1RmTGluZUNoYXJ0RGF0YUxvYWRlciBleHRlbmRzIERhdGFMb2FkZXJCZWhhdmlvcihMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpKSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX3JlZHJhd1JhZiA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuYWN0aXZlID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMubG9nU2NhbGVBY3RpdmUgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5jb2xvclNjYWxlID0geyBzY2FsZTogcnVuc0NvbG9yU2NhbGUgfTsKICAgICAgICAgICAgdGhpcy5fcmVzZXREb21haW5Pbk5leHRMb2FkID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fbWF5YmVSZW5kZXJlZEluQmFkU3RhdGUgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgb25Mb2FkRmluaXNoKCkgewogICAgICAgICAgICB0aGlzLmNvbW1pdENoYW5nZXMoKTsKICAgICAgICAgICAgaWYgKHRoaXMuZGF0YVRvTG9hZC5sZW5ndGggPiAwICYmIHRoaXMuX3Jlc2V0RG9tYWluT25OZXh0TG9hZCkgewogICAgICAgICAgICAgICAgLy8gKERvbid0IHVuc2V0IF9yZXNldERvbWFpbk9uTmV4dExvYWQgd2hlbiB3ZSBkaWRuJ3QKICAgICAgICAgICAgICAgIC8vIGxvYWQgYW55IHJ1bnM6IHRoaXMgaGFzIHRoZSBlZmZlY3QgdGhhdCBpZiBhbGwgb3VyCiAgICAgICAgICAgICAgICAvLyBydW5zIGFyZSBkZXNlbGVjdGVkLCB0aGVuIHdlIHRvZ2dsZSB0aGVtIGFsbCBvbiwgd2UKICAgICAgICAgICAgICAgIC8vIHByb3Blcmx5IHNpemUgdGhlIGRvbWFpbiBvbmNlIGFsbCB0aGUgZGF0YSBpcyBsb2FkZWQKICAgICAgICAgICAgICAgIC8vIGluc3RlYWQgb2YganVzdCB3aGVuIHdlJ3JlIGZpcnN0IHJlbmRlcmVkLikKICAgICAgICAgICAgICAgIHRoaXMuX3Jlc2V0RG9tYWluT25OZXh0TG9hZCA9IGZhbHNlOwogICAgICAgICAgICAgICAgdGhpcy5nZXRDaGFydCgpLnJlc2V0RG9tYWluKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgICAgIHN1cGVyLmRpc2Nvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgICAgICAgIGlmICh0aGlzLl9yZWRyYXdSYWYgIT09IG51bGwpCiAgICAgICAgICAgICAgICBjYW5jZWxBbmltYXRpb25GcmFtZSh0aGlzLl9yZWRyYXdSYWYpOwogICAgICAgIH0KICAgICAgICBleHBvcnRBc1N2Z1N0cmluZygpIHsKICAgICAgICAgICAgY29uc3QgZXhwb3J0ZXIgPSB0aGlzLmdldENoYXJ0KCkuZ2V0RXhwb3J0ZXIoKTsKICAgICAgICAgICAgcmV0dXJuIGV4cG9ydGVyLmV4cG9ydEFzU3RyaW5nKCk7CiAgICAgICAgfQogICAgICAgIGdldENoYXJ0KCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy4kLmNoYXJ0OwogICAgICAgIH0KICAgICAgICByZXNldERvbWFpbigpIHsKICAgICAgICAgICAgdGhpcy5nZXRDaGFydCgpLnJlc2V0RG9tYWluKCk7CiAgICAgICAgfQogICAgICAgIHNldFNlcmllc0RhdGEobmFtZSwgZGF0YSkgewogICAgICAgICAgICB0aGlzLmdldENoYXJ0KCkuc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKTsKICAgICAgICB9CiAgICAgICAgc2V0U2VyaWVzTWV0YWRhdGEobmFtZSwgbWV0YWRhdGEpIHsKICAgICAgICAgICAgdGhpcy5nZXRDaGFydCgpLnNldFNlcmllc01ldGFkYXRhKG5hbWUsIG1ldGFkYXRhKTsKICAgICAgICB9CiAgICAgICAgY29tbWl0Q2hhbmdlcygpIHsKICAgICAgICAgICAgdGhpcy5nZXRDaGFydCgpLmNvbW1pdENoYW5nZXMoKTsKICAgICAgICB9CiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICBpZiAodGhpcy5fcmVkcmF3UmFmICE9PSBudWxsKQogICAgICAgICAgICAgICAgY2FuY2VsQW5pbWF0aW9uRnJhbWUodGhpcy5fcmVkcmF3UmFmKTsKICAgICAgICAgICAgdGhpcy5fcmVkcmF3UmFmID0gd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAodGhpcy5hY3RpdmUpIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLmdldENoYXJ0KCkucmVkcmF3KCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAvLyBJZiB3ZSByZWFjaGVkIGEgcG9pbnQgd2hlcmUgd2Ugc2hvdWxkIHJlbmRlciB3aGlsZSB0aGUgcGFnZQogICAgICAgICAgICAgICAgICAgIC8vIGlzIG5vdCBhY3RpdmUsIHdlJ3ZlIGdvdHRlbiBpbnRvIGEgYmFkIHN0YXRlLgogICAgICAgICAgICAgICAgICAgIHRoaXMuX21heWJlUmVuZGVyZWRJbkJhZFN0YXRlID0gdHJ1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9sb2FkS2V5Q2hhbmdlZCgpIHsKICAgICAgICAgICAgdGhpcy5yZXNldCgpOwogICAgICAgICAgICB0aGlzLl9yZXNldERvbWFpbk9uTmV4dExvYWQgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBfZGF0YVNlcmllc0NoYW5nZWQoKSB7CiAgICAgICAgICAgIC8vIFNldHRpbmcgdmlzaWJsZSBzZXJpZXMgcmVkcmF3cyB0aGUgY2hhcnQuCiAgICAgICAgICAgIHRoaXMuZ2V0Q2hhcnQoKS5zZXRWaXNpYmxlU2VyaWVzKHRoaXMuZGF0YVNlcmllcyk7CiAgICAgICAgfQogICAgICAgIF9sb2dTY2FsZUNoYW5nZWQobG9nU2NhbGVBY3RpdmUpIHsKICAgICAgICAgICAgY29uc3QgY2hhcnQgPSB0aGlzLmdldENoYXJ0KCk7CiAgICAgICAgICAgIGNoYXJ0LnlTY2FsZVR5cGUgPSBsb2dTY2FsZUFjdGl2ZSA/IFlTY2FsZVR5cGUuTE9HIDogWVNjYWxlVHlwZS5MSU5FQVI7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIF9maXhCYWRTdGF0ZVdoZW5BY3RpdmUoKSB7CiAgICAgICAgICAgIC8vIFdoZW4gdGhlIGNoYXJ0IGVudGVycyBhIHBvdGVudGlhbGx5IGJhZCBzdGF0ZSAoYmVjYXVzZSBpdCBzaG91bGQKICAgICAgICAgICAgLy8gcmVkcmF3LCBidXQgdGhlIHBhZ2UgaXMgbm90IGN1cnJlbnRseSBhY3RpdmUpLCB3ZSBzZXQgdGhlCiAgICAgICAgICAgIC8vIF9tYXliZVJlbmRlcmVkSW5CYWRTdGF0ZSBmbGFnLiBXaGVuZXZlciB0aGUgY2hhcnQgYmVjb21lcyBhY3RpdmUsCiAgICAgICAgICAgIC8vIHdlIHRlc3QgdGhpcyBhbmQgc2NoZWR1bGUgYSByZWRyYXcgb2YgdGhlIGJhZCBjaGFydHMuCiAgICAgICAgICAgIGlmICh0aGlzLmFjdGl2ZSAmJiB0aGlzLl9tYXliZVJlbmRlcmVkSW5CYWRTdGF0ZSkgewogICAgICAgICAgICAgICAgcmVkcmF3UXVldWUucHVzaCh0aGlzKTsKICAgICAgICAgICAgICAgIGNhc2NhZGluZ1JlZHJhdygpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9vbkNoYXJ0QXR0YWNoZWQoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5hY3RpdmUpIHsKICAgICAgICAgICAgICAgIHRoaXMuX21heWJlUmVuZGVyZWRJbkJhZFN0YXRlID0gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH07CiAgICBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJjaGFydC1hbmQtc3Bpbm5lci1jb250YWluZXIiPgogICAgICA8dnotbGluZS1jaGFydDIKICAgICAgICBpZD0iY2hhcnQiCiAgICAgICAgZGF0YS1sb2FkaW5nJD0iW1tkYXRhTG9hZGluZ11dIgogICAgICAgIGNvbG9yLXNjYWxlPSJbW2NvbG9yU2NhbGVdXSIKICAgICAgICBkZWZhdWx0LXgtcmFuZ2U9IltbZGVmYXVsdFhSYW5nZV1dIgogICAgICAgIGRlZmF1bHQteS1yYW5nZT0iW1tkZWZhdWx0WVJhbmdlXV0iCiAgICAgICAgZmlsbC1hcmVhPSJbW2ZpbGxBcmVhXV0iCiAgICAgICAgaWdub3JlLXktb3V0bGllcnM9IltbaWdub3JlWU91dGxpZXJzXV0iCiAgICAgICAgb24tY2hhcnQtYXR0YWNoZWQ9Il9vbkNoYXJ0QXR0YWNoZWQiCiAgICAgICAgc21vb3RoaW5nLWVuYWJsZWQ9Iltbc21vb3RoaW5nRW5hYmxlZF1dIgogICAgICAgIHNtb290aGluZy13ZWlnaHQ9Iltbc21vb3RoaW5nV2VpZ2h0XV0iCiAgICAgICAgc3ltYm9sLWZ1bmN0aW9uPSJbW3N5bWJvbEZ1bmN0aW9uXV0iCiAgICAgICAgdG9vbHRpcC1jb2x1bW5zPSJbW3Rvb2x0aXBDb2x1bW5zXV0iCiAgICAgICAgdG9vbHRpcC1wb3NpdGlvbj0iW1t0b29sdGlwUG9zaXRpb25dXSIKICAgICAgICB0b29sdGlwLXNvcnRpbmctbWV0aG9kPSJbW3Rvb2x0aXBTb3J0aW5nTWV0aG9kXV0iCiAgICAgICAgeC1jb21wb25lbnRzLWNyZWF0aW9uLW1ldGhvZD0iW1t4Q29tcG9uZW50c0NyZWF0aW9uTWV0aG9kXV0iCiAgICAgICAgeC10eXBlPSJbW3hUeXBlXV0iCiAgICAgICAgeS12YWx1ZS1hY2Nlc3Nvcj0iW1t5VmFsdWVBY2Nlc3Nvcl1dIgogICAgICA+PC92ei1saW5lLWNoYXJ0Mj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW2RhdGFMb2FkaW5nXV0iPgogICAgICAgIDxkaXYgaWQ9ImxvYWRpbmctc3Bpbm5lci1jb250YWluZXIiPgogICAgICAgICAgPHBhcGVyLXNwaW5uZXItbGl0ZSBhY3RpdmU9IiI+PC9wYXBlci1zcGlubmVyLWxpdGU+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L2Rpdj4KICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgIH0KCiAgICAgIDpob3N0KFtfbWF5YmUtcmVuZGVyZWQtaW4tYmFkLXN0YXRlXSkgdnotbGluZS1jaGFydCB7CiAgICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgICB9CgogICAgICAjY2hhcnQtYW5kLXNwaW5uZXItY29udGFpbmVyIHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZ3JvdzogMTsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgICNsb2FkaW5nLXNwaW5uZXItY29udGFpbmVyIHsKICAgICAgICBhbGlnbi1pdGVtczogY2VudGVyOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7CiAgICAgICAgbGVmdDogMDsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgcmlnaHQ6IDA7CiAgICAgICAgdG9wOiAwOwogICAgICB9CgogICAgICB2ei1saW5lLWNoYXJ0MiB7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICB9CgogICAgICB2ei1saW5lLWNoYXJ0MltkYXRhLWxvYWRpbmddIHsKICAgICAgICBvcGFjaXR5OiAwLjM7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZml4QmFkU3RhdGVXaGVuQWN0aXZlJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgImFjdGl2ZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgImRhdGFTZXJpZXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBSZXF1ZXN0TWFuYWdlcikKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAicmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBvYnNlcnZlcjogJ19sb2dTY2FsZUNoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAibG9nU2NhbGVBY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgInhDb21wb25lbnRzQ3JlYXRpb25NZXRob2QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgInhUeXBlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgInlWYWx1ZUFjY2Vzc29yIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJmaWxsQXJlYSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJzbW9vdGhpbmdFbmFibGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJzbW9vdGhpbmdXZWlnaHQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJ0b29sdGlwQ29sdW1ucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAidG9vbHRpcFNvcnRpbmdNZXRob2QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyLnByb3RvdHlwZSwgInRvb2x0aXBQb3NpdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJpZ25vcmVZT3V0bGllcnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJkZWZhdWx0WFJhbmdlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAiZGVmYXVsdFlSYW5nZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJzeW1ib2xGdW5jdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAiY29sb3JTY2FsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmTGluZUNoYXJ0RGF0YUxvYWRlci5wcm90b3R5cGUsICJfcmVzZXREb21haW5Pbk5leHRMb2FkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAiX21heWJlUmVuZGVyZWRJbkJhZFN0YXRlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ2xvYWRLZXknKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAiX2xvYWRLZXlDaGFuZ2VkIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdkYXRhU2VyaWVzLionKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIF9UZkxpbmVDaGFydERhdGFMb2FkZXIucHJvdG90eXBlLCAiX2RhdGFTZXJpZXNDaGFuZ2VkIiwgbnVsbCk7CiAgICBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtbGluZS1jaGFydC1kYXRhLWxvYWRlcicpCiAgICBdLCBfVGZMaW5lQ2hhcnREYXRhTG9hZGVyKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHJlZ2lzdGVyU3R5bGVEb21Nb2R1bGUoewogICAgICAgIG1vZHVsZU5hbWU6ICd0Zi1jdXN0b20tc2NhbGFyLWNhcmQtc3R5bGUnLAogICAgICAgIHN0eWxlQ29udGVudDogYAogICAgOmhvc3QgewogICAgICBtYXJnaW46IDVweCAxMHB4OwogICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgIHdpZHRoOiAzMzBweDsKICAgICAgdmVydGljYWwtYWxpZ246IHRleHQtdG9wOwogICAgfQoKICAgIDpob3N0KFtfZXhwYW5kZWRdKSB7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgfQoKICAgIDpob3N0KFtfZXhwYW5kZWRdKSAjdGYtbGluZS1jaGFydC1kYXRhLWxvYWRlci1jb250YWluZXIgewogICAgICBoZWlnaHQ6IDQwMHB4OwogICAgfQoKICAgIGgxIHsKICAgICAgZm9udC1zaXplOiAxOXB4OwogICAgICBmb250LXdlaWdodDogbm9ybWFsOwogICAgfQoKICAgICN0Zi1saW5lLWNoYXJ0LWRhdGEtbG9hZGVyLWNvbnRhaW5lciB7CiAgICAgIGhlaWdodDogMjAwcHg7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgfQoKICAgICNidXR0b25zIHsKICAgICAgZGlzcGxheTogZmxleDsKICAgICAgZmxleC1kaXJlY3Rpb246IHJvdzsKICAgIH0KCiAgICBwYXBlci1pY29uLWJ1dHRvbiB7CiAgICAgIGNvbG9yOiAjMjE5NmYzOwogICAgICBib3JkZXItcmFkaXVzOiAxMDAlOwogICAgICB3aWR0aDogMzJweDsKICAgICAgaGVpZ2h0OiAzMnB4OwogICAgICBwYWRkaW5nOiA0cHg7CiAgICB9CgogICAgcGFwZXItaWNvbi1idXR0b25bc2VsZWN0ZWRdIHsKICAgICAgYmFja2dyb3VuZDogdmFyKC0tdGItdWktbGlnaHQtYWNjZW50KTsKICAgIH0KCiAgICAuZG93bmxvYWQtbGlua3MgewogICAgICBkaXNwbGF5OiBmbGV4OwogICAgICBoZWlnaHQ6IDMycHg7CiAgICB9CgogICAgLmRvd25sb2FkLWxpbmtzIGEgewogICAgICBmb250LXNpemU6IDEwcHg7CiAgICAgIGFsaWduLXNlbGY6IGNlbnRlcjsKICAgICAgbWFyZ2luOiAycHg7CiAgICB9CgogICAgLmRvd25sb2FkLWxpbmtzIHBhcGVyLWRyb3Bkb3duLW1lbnUgewogICAgICB3aWR0aDogMTAwcHg7CiAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsOiB7CiAgICAgICAgZm9udC1zaXplOiAxMHB4OwogICAgICB9CiAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0OiB7CiAgICAgICAgZm9udC1zaXplOiAxMHB4OwogICAgICB9CiAgICB9CiAgYCwKICAgIH0pOwoKICAgIC8qIENvcHlyaWdodCAyMDE3IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBBIGNsYXNzIHRoYXQgcmVwcmVzZW50cyBhIGRhdGEgc2VyaWVzIGZvciBhIGN1c3RvbSBzY2FsYXJzIGNoYXJ0LgogICAgICovCiAgICBjbGFzcyBEYXRhU2VyaWVzIHsKICAgICAgICBjb25zdHJ1Y3RvcihydW4sIHRhZywgbmFtZSwgc2NhbGFyRGF0YSwgc3ltYm9sKSB7CiAgICAgICAgICAgIHRoaXMucnVuID0gcnVuOwogICAgICAgICAgICB0aGlzLnRhZyA9IHRhZzsKICAgICAgICAgICAgdGhpcy5uYW1lID0gbmFtZTsKICAgICAgICAgICAgdGhpcy5zY2FsYXJEYXRhID0gc2NhbGFyRGF0YTsKICAgICAgICAgICAgdGhpcy5zeW1ib2wgPSBzeW1ib2w7CiAgICAgICAgfQogICAgICAgIGdldE5hbWUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLm5hbWU7CiAgICAgICAgfQogICAgICAgIHNldERhdGEoc2NhbGFyRGF0YSkgewogICAgICAgICAgICB0aGlzLnNjYWxhckRhdGEgPSBzY2FsYXJEYXRhOwogICAgICAgIH0KICAgICAgICBnZXREYXRhKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5zY2FsYXJEYXRhOwogICAgICAgIH0KICAgICAgICBnZXRSdW4oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnJ1bjsKICAgICAgICB9CiAgICAgICAgZ2V0VGFnKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy50YWc7CiAgICAgICAgfQogICAgICAgIGdldFN5bWJvbCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuc3ltYm9sOwogICAgICAgIH0KICAgIH0KICAgIGZ1bmN0aW9uIGdlbmVyYXRlRGF0YVNlcmllc05hbWUocnVuLCB0YWcpIHsKICAgICAgICByZXR1cm4gYCR7dGFnfSAoJHtydW59KWA7CiAgICB9CiAgICAvKioKICAgICAqIEEgY29sb3Igc2NhbGUgdGhhdCB3cmFwcyB0aGUgdXN1YWwgY29sb3Igc2NhbGUgdGhhdCByZWxpZXMgb24gcnVucy4gVGhpcwogICAgICogcGFydGljdWxhciBjb2xvciBzY2FsZSBwYXJzZXMgdGhlIHJ1biBmcm9tIGEgc2VyaWVzIG5hbWUgYW5kIGRlZmVycyB0byB0aGF0CiAgICAgKiBmb3JtZXIgY29sb3Igc2NhbGUuCiAgICAgKi8KICAgIGNsYXNzIERhdGFTZXJpZXNDb2xvclNjYWxlIHsKICAgICAgICBjb25zdHJ1Y3RvcihydW5CYXNlZENvbG9yU2NhbGUpIHsKICAgICAgICAgICAgdGhpcy5ydW5CYXNlZENvbG9yU2NhbGUgPSBydW5CYXNlZENvbG9yU2NhbGU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIE9idGFpbnMgdGhlIGNvcnJlY3QgY29sb3IgYmFzZWQgb24gdGhlIHJ1bi4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZGF0YVNlcmllcwogICAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gVGhlIGNvbG9yLgogICAgICAgICAqLwogICAgICAgIHNjYWxlKGRhdGFTZXJpZXMpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucnVuQmFzZWRDb2xvclNjYWxlLnNjYWxlKHRoaXMucGFyc2VSdW5OYW1lKGRhdGFTZXJpZXMpKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUGFyc2VzIHRoZSBydW4gbmFtZSBmcm9tIGEgZGF0YSBzZXJpZXMgc3RyaW5nLiBSZXR1cm5zIHRoZSBlbXB0eSBzdHJpbmcgaWYKICAgICAgICAgKiBwYXJzaW5nIGZhaWxzLgogICAgICAgICAqLwogICAgICAgIHBhcnNlUnVuTmFtZShkYXRhU2VyaWVzKSB7CiAgICAgICAgICAgIGNvbnN0IG1hdGNoID0gZGF0YVNlcmllcy5tYXRjaCgvXCgoLiopXCkkLyk7CiAgICAgICAgICAgIGlmICghbWF0Y2gpIHsKICAgICAgICAgICAgICAgIC8vIE5vIG1hdGNoIGZvdW5kLgogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBtYXRjaFsxXTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkID0gY2xhc3MgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuYWN0aXZlID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fY29sb3JTY2FsZSA9IG5ldyBEYXRhU2VyaWVzQ29sb3JTY2FsZSh7CiAgICAgICAgICAgICAgICBzY2FsZTogcnVuc0NvbG9yU2NhbGUsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl9uYW1lVG9EYXRhU2VyaWVzID0ge307CiAgICAgICAgICAgIHRoaXMuX2V4cGFuZGVkID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3REYXRhID0gKGl0ZW1zLCBvbkxvYWQsIG9uRmluaXNoKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCByb3V0ZXIgPSBnZXRSb3V0ZXIoKTsKICAgICAgICAgICAgICAgIGNvbnN0IGJhc2VVcmwgPSByb3V0ZXIucGx1Z2luUm91dGUoJ2N1c3RvbV9zY2FsYXJzJywgJy9zY2FsYXJzJyk7CiAgICAgICAgICAgICAgICBQcm9taXNlLmFsbChpdGVtcy5tYXAoKGl0ZW0pID0+IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBydW4gPSBpdGVtOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHRhZyA9IHRoaXMuX3RhZ0ZpbHRlcjsKICAgICAgICAgICAgICAgICAgICBjb25zdCB1cmwgPSBhZGRQYXJhbXMoYmFzZVVybCwgeyB0YWcsIHJ1biB9KTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5yZXF1ZXN0TWFuYWdlcgogICAgICAgICAgICAgICAgICAgICAgICAucmVxdWVzdCh1cmwpCiAgICAgICAgICAgICAgICAgICAgICAgIC50aGVuKChkYXRhKSA9PiB2b2lkIG9uTG9hZCh7IGl0ZW0sIGRhdGEgfSkpOwogICAgICAgICAgICAgICAgfSkpLmZpbmFsbHkoKCkgPT4gdm9pZCBvbkZpbmlzaCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5fcnVuVG9OZXh0QXZhaWxhYmxlU3ltYm9sSW5kZXggPSB7fTsKICAgICAgICAgICAgdGhpcy5fbWF0Y2hlc0xpc3RPcGVuZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fZmlsbEFyZWEgPSB7CiAgICAgICAgICAgICAgICBsb3dlckFjY2Vzc29yOiAoZCkgPT4gZC5sb3dlciwKICAgICAgICAgICAgICAgIGhpZ2hlckFjY2Vzc29yOiAoZCkgPT4gZC51cHBlciwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5fdG9vbHRpcENvbHVtbnMgPSAoKCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgdmFsdWVGb3JtYXR0ZXIgPSBtdWx0aXNjYWxlRm9ybWF0dGVyKFlfVE9PTFRJUF9GT1JNQVRURVJfUFJFQ0lTSU9OKTsKICAgICAgICAgICAgICAgIGNvbnN0IGZvcm1hdFZhbHVlT3JOYU4gPSAoeCkgPT4gKGlzTmFOKHgpID8gJ05hTicgOiB2YWx1ZUZvcm1hdHRlcih4KSk7CiAgICAgICAgICAgICAgICByZXR1cm4gWwogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdOYW1lJywKICAgICAgICAgICAgICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiBkLmRhdGFzZXQubWV0YWRhdGEoKS5uYW1lLAogICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICB0aXRsZTogJ1ZhbHVlJywKICAgICAgICAgICAgICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiBmb3JtYXRWYWx1ZU9yTmFOKGQuZGF0dW0uc2NhbGFyKSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdMb3dlciBNYXJnaW4nLAogICAgICAgICAgICAgICAgICAgICAgICBldmFsdWF0ZTogKGQpID0+IGZvcm1hdFZhbHVlT3JOYU4oZC5kYXR1bS5sb3dlciksCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRpdGxlOiAnVXBwZXIgTWFyZ2luJywKICAgICAgICAgICAgICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiBmb3JtYXRWYWx1ZU9yTmFOKGQuZGF0dW0udXBwZXIpLAogICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICB0aXRsZTogJ1N0ZXAnLAogICAgICAgICAgICAgICAgICAgICAgICBldmFsdWF0ZTogKGQpID0+IHN0ZXBGb3JtYXR0ZXIoZC5kYXR1bS5zdGVwKSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdUaW1lJywKICAgICAgICAgICAgICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiB0aW1lRm9ybWF0dGVyKGQuZGF0dW0ud2FsbF90aW1lKSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdSZWxhdGl2ZScsCiAgICAgICAgICAgICAgICAgICAgICAgIGV2YWx1YXRlOiAoZCkgPT4gcmVsYXRpdmVGb3JtYXR0ZXIocmVsYXRpdmVBY2Nlc3NvcihkLmRhdHVtLCAtMSwgZC5kYXRhc2V0KSksCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIF07CiAgICAgICAgICAgIH0pKCk7CiAgICAgICAgICAgIHRoaXMuX21pc3NpbmdUYWdzID0gW107CiAgICAgICAgICAgIHRoaXMuX21pc3NpbmdUYWdzQ29sbGFwc2libGVPcGVuZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgcmVsb2FkKCkgewogICAgICAgICAgICB0aGlzLiQubG9hZGVyLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICByZWRyYXcoKSB7CiAgICAgICAgICAgIHRoaXMuJC5sb2FkZXIucmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIF90b2dnbGVFeHBhbmRlZChlKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfZXhwYW5kZWQnLCAhdGhpcy5fZXhwYW5kZWQpOwogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlTG9nU2NhbGUoKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfbG9nU2NhbGVBY3RpdmUnLCAhdGhpcy5fbG9nU2NhbGVBY3RpdmUpOwogICAgICAgIH0KICAgICAgICBfcmVzZXREb21haW4oKSB7CiAgICAgICAgICAgIGNvbnN0IGNoYXJ0ID0gdGhpcy4kLmxvYWRlcjsKICAgICAgICAgICAgaWYgKGNoYXJ0KSB7CiAgICAgICAgICAgICAgICBjaGFydC5yZXNldERvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9jc3ZVcmwoX25hbWVUb0RhdGFTZXJpZXMsIGRhdGFTZXJpZXNOYW1lKSB7CiAgICAgICAgICAgIGlmICghZGF0YVNlcmllc05hbWUpCiAgICAgICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgICAgIGNvbnN0IGJhc2VVcmwgPSB0aGlzLl9kb3dubG9hZERhdGFVcmwoX25hbWVUb0RhdGFTZXJpZXMsIGRhdGFTZXJpZXNOYW1lKTsKICAgICAgICAgICAgcmV0dXJuIGFkZFBhcmFtcyhiYXNlVXJsLCB7IGZvcm1hdDogJ2NzdicgfSk7CiAgICAgICAgfQogICAgICAgIF9qc29uVXJsKF9uYW1lVG9EYXRhU2VyaWVzLCBkYXRhU2VyaWVzTmFtZSkgewogICAgICAgICAgICBpZiAoIWRhdGFTZXJpZXNOYW1lKQogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICBjb25zdCBiYXNlVXJsID0gdGhpcy5fZG93bmxvYWREYXRhVXJsKF9uYW1lVG9EYXRhU2VyaWVzLCBkYXRhU2VyaWVzTmFtZSk7CiAgICAgICAgICAgIHJldHVybiBhZGRQYXJhbXMoYmFzZVVybCwgeyBmb3JtYXQ6ICdqc29uJyB9KTsKICAgICAgICB9CiAgICAgICAgX2Rvd25sb2FkRGF0YVVybChfbmFtZVRvRGF0YVNlcmllcywgZGF0YVNlcmllc05hbWUpIHsKICAgICAgICAgICAgY29uc3QgZGF0YVNlcmllcyA9IF9uYW1lVG9EYXRhU2VyaWVzW2RhdGFTZXJpZXNOYW1lXTsKICAgICAgICAgICAgY29uc3QgZ2V0VmFycyA9IHsKICAgICAgICAgICAgICAgIHRhZzogZGF0YVNlcmllcy5nZXRUYWcoKSwKICAgICAgICAgICAgICAgIHJ1bjogZGF0YVNlcmllcy5nZXRSdW4oKSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgcmV0dXJuIGFkZFBhcmFtcyhnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnY3VzdG9tX3NjYWxhcnMnLCAnL2Rvd25sb2FkX2RhdGEnKSwgZ2V0VmFycyk7CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVQcm9jZXNzRGF0YUZ1bmN0aW9uKG1hcmdpbkNoYXJ0U2VyaWVzKSB7CiAgICAgICAgICAgIC8vIFRoaXMgZnVuY3Rpb24gaXMgY2FsbGVkIHdoZW4gZGF0YSBpcyByZWNlaXZlZCBmcm9tIHRoZSBiYWNrZW5kLgogICAgICAgICAgICByZXR1cm4gKHNjYWxhckNoYXJ0LCBydW4sIGRhdGEpID0+IHsKICAgICAgICAgICAgICAgIGlmICghZGF0YS5yZWdleF92YWxpZCkgewogICAgICAgICAgICAgICAgICAgIC8vIFRoZSByZWd1bGFyIGV4cHJlc3Npb24gaXMgY29uc3RydWN0ZWQgZnJvbSBmcm9udGVuZCBsb2dpYyB0aGF0CiAgICAgICAgICAgICAgICAgICAgLy8gcGllY2VzIHRvZ2V0aGVyIGRpZmZlcmVudCB0YWdzLiBIZW5jZSwgdGhpcyBjYXNlIHNob3VsZCBuZXZlciBiZQogICAgICAgICAgICAgICAgICAgIC8vIHJlYWNoZWQgaWYgdGhlIGRhc2hib2FyZCBiZWhhdmVzIGNvcnJlY3RseS4KICAgICAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3RhZ0ZpbHRlckludmFsaWQnLCB0cnVlKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBUaGUgdXNlcidzIHJlZ3VsYXIgZXhwcmVzc2lvbiB3YXMgdmFsaWQuCiAgICAgICAgICAgICAgICAvLyBJbmNvcnBvcmF0ZSB0aGVzZSBuZXdseSBsb2FkZWQgdmFsdWVzLgogICAgICAgICAgICAgICAgY29uc3QgbmV3TWFwcGluZyA9IGxvZGFzaC5jbG9uZSh0aGlzLl9uYW1lVG9EYXRhU2VyaWVzKTsKICAgICAgICAgICAgICAgIGNvbnN0IHRhZ3NOb3RGb3VuZCA9IFtdOwogICAgICAgICAgICAgICAgbG9kYXNoLmZvckVhY2gobWFyZ2luQ2hhcnRTZXJpZXMsICh0YWdzT2JqZWN0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgbGV0IHRhZ05vdEZvdW5kID0gZmFsc2U7CiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2NhbGFyRXZlbnRzID0gZGF0YS50YWdfdG9fZXZlbnRzW3RhZ3NPYmplY3QudmFsdWVdOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IGxvd2VyQm91bmRzID0gZGF0YS50YWdfdG9fZXZlbnRzW3RhZ3NPYmplY3QubG93ZXJdOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHVwcGVyQm91bmRzID0gZGF0YS50YWdfdG9fZXZlbnRzW3RhZ3NPYmplY3QudXBwZXJdOwogICAgICAgICAgICAgICAgICAgIC8vIE1ha2Ugc3VyZSB0aGF0IGRhdGEgaXMgZm91bmQgZm9yIGVhY2ggb2YgdGhlIHRhZ3MuCiAgICAgICAgICAgICAgICAgICAgaWYgKGxvZGFzaC5pc1VuZGVmaW5lZChzY2FsYXJFdmVudHMpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRhZ3NOb3RGb3VuZC5wdXNoKHRhZ3NPYmplY3QudmFsdWUpOwogICAgICAgICAgICAgICAgICAgICAgICB0YWdOb3RGb3VuZCA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNVbmRlZmluZWQobG93ZXJCb3VuZHMpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRhZ3NOb3RGb3VuZC5wdXNoKHRhZ3NPYmplY3QubG93ZXIpOwogICAgICAgICAgICAgICAgICAgICAgICB0YWdOb3RGb3VuZCA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNVbmRlZmluZWQodXBwZXJCb3VuZHMpKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRhZ3NOb3RGb3VuZC5wdXNoKHRhZ3NPYmplY3QudXBwZXIpOwogICAgICAgICAgICAgICAgICAgICAgICB0YWdOb3RGb3VuZCA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIC8vIEF0IGxlYXN0IG9uZSBvZiB0aGUgdGFncyBsYWNrcyBkYXRhLiBXZSB0ZXJtaW5hdGUgZWFybHkgYmVjYXVzZQogICAgICAgICAgICAgICAgICAgIC8vIHRoZSBsaW5lIGNoYXJ0IHJlcXVpcmVzIGFsbCAzIHBpZWNlcyBvZiBkYXRhICh2YWx1ZSwgbG93ZXIgYm91bmQsCiAgICAgICAgICAgICAgICAgICAgLy8gYW5kIHVwcGVyIGJvdW5kKS4KICAgICAgICAgICAgICAgICAgICBpZiAodGFnTm90Rm91bmQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBNYWtlIHN1cmUgdGhhdCBzdGVwcyBmb3IgYWxsIHRoZSBsaXN0cyBjb3JyZXNwb25kIHdpdGggZWFjaAogICAgICAgICAgICAgICAgICAgIC8vIG90aGVyLiBPdGhlcndpc2UsIGRpc3BsYXkgYW4gZXJyb3IgbWVzc2FnZS4KICAgICAgICAgICAgICAgICAgICBjb25zdCBvYnRhaW5TdGVwID0gKGRhdHVtKSA9PiBkYXR1bVsxXTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBzdGVwc01pc21hdGNoID0gdGhpcy5fZmluZFN0ZXBNaXNtYXRjaCh0YWdzT2JqZWN0LCBzY2FsYXJFdmVudHMubWFwKG9idGFpblN0ZXApLCBsb3dlckJvdW5kcy5tYXAob2J0YWluU3RlcCksIHVwcGVyQm91bmRzLm1hcChvYnRhaW5TdGVwKSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHN0ZXBzTWlzbWF0Y2gpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19zdGVwc01pc21hdGNoJywgc3RlcHNNaXNtYXRjaCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgLy8gQ3JlYXRlIGRhdGEgcG9pbnRzIHRoYXQgdGhlIGxpbmUgY2hhcnQgY2FuIHBhcnNlLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9idGFpbk51bWJlciA9IChkYXR1bSkgPT4gZGF0dW1bMl07CiAgICAgICAgICAgICAgICAgICAgY29uc3QgZGF0YVBvaW50cyA9IHNjYWxhckV2ZW50cy5tYXAoKGRhdHVtLCBpKSA9PiAoewogICAgICAgICAgICAgICAgICAgICAgICB3YWxsX3RpbWU6IG5ldyBEYXRlKGRhdHVtWzBdICogMTAwMCksCiAgICAgICAgICAgICAgICAgICAgICAgIHN0ZXA6IG9idGFpblN0ZXAoZGF0dW0pLAogICAgICAgICAgICAgICAgICAgICAgICBzY2FsYXI6IG9idGFpbk51bWJlcihkYXR1bSksCiAgICAgICAgICAgICAgICAgICAgICAgIGxvd2VyOiBvYnRhaW5OdW1iZXIobG93ZXJCb3VuZHNbaV0pLAogICAgICAgICAgICAgICAgICAgICAgICB1cHBlcjogb2J0YWluTnVtYmVyKHVwcGVyQm91bmRzW2ldKSwKICAgICAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgICAgICAgICAgLy8gQ29tcHV0ZSB0aGUgc2VyaWVzIG5hbWUsIHdoaWNoIGlzIGJhc2VkIG9uIGJvdGggdGhlIHJ1biBhbmQgdGhlCiAgICAgICAgICAgICAgICAgICAgLy8gdGFnIG9mIHRoZSB2YWx1ZS4KICAgICAgICAgICAgICAgICAgICBjb25zdCBzZXJpZXNOYW1lID0gZ2VuZXJhdGVEYXRhU2VyaWVzTmFtZShydW4sIHRhZ3NPYmplY3QudmFsdWUpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlcmllcyA9IG5ld01hcHBpbmdbc2VyaWVzTmFtZV07CiAgICAgICAgICAgICAgICAgICAgaWYgKHNlcmllcykgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIHNlcmllcyBhbHJlYWR5IGV4aXN0cy4KICAgICAgICAgICAgICAgICAgICAgICAgc2VyaWVzLnNldERhdGEoZGF0YVBvaW50cyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBzZXJpZXMgPSB0aGlzLl9jcmVhdGVOZXdEYXRhU2VyaWVzKHJ1biwgdGFnc09iamVjdC52YWx1ZSwgc2VyaWVzTmFtZSwgZGF0YVBvaW50cyk7CiAgICAgICAgICAgICAgICAgICAgICAgIG5ld01hcHBpbmdbc2VyaWVzTmFtZV0gPSBzZXJpZXM7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX25hbWVUb0RhdGFTZXJpZXMnLCBuZXdNYXBwaW5nKTsKICAgICAgICAgICAgICAgIGNvbnN0IGVudHJ5SW5kZXggPSBsb2Rhc2guZmluZEluZGV4KHRoaXMuX21pc3NpbmdUYWdzLCAoZW50cnkpID0+IHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZW50cnkucnVuID09PSBydW47CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGlmICh0YWdzTm90Rm91bmQubGVuZ3RoICYmIHRhZ3NOb3RGb3VuZC5sZW5ndGggIT0gMykgewogICAgICAgICAgICAgICAgICAgIC8vIFNvbWUgYnV0IG5vdCBhbGwgdGFncyB3ZXJlIGZvdW5kLiBTaG93IGEgd2FybmluZyBtZXNzYWdlLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IGVudHJ5ID0gewogICAgICAgICAgICAgICAgICAgICAgICBydW46IHJ1biwKICAgICAgICAgICAgICAgICAgICAgICAgdGFnczogdGFnc05vdEZvdW5kLAogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgaWYgKGVudHJ5SW5kZXggPj0gMCkgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBSZW1vdmUgdGhlIHByZXZpb3VzIGVudHJ5LiBJbnNlcnQgdGhlIG5ldyBvbmUuCiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuc3BsaWNlKCdfbWlzc2luZ1RhZ3MnLCBlbnRyeUluZGV4LCAxLCBlbnRyeSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBJbnNlcnQgYSBuZXcgZW50cnkuCiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMucHVzaCgnX21pc3NpbmdUYWdzJywgZW50cnkpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGVudHJ5SW5kZXggPj0gMCkgewogICAgICAgICAgICAgICAgICAgIC8vIFJlbW92ZSB0aGUgcHJldmlvdXMgZW50cnkgaWYgaXQgZXhpc3RzLgogICAgICAgICAgICAgICAgICAgIHRoaXMuc3BsaWNlKCdfbWlzc2luZ1RhZ3MnLCBlbnRyeUluZGV4LCAxKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgX2ZpbmRTdGVwTWlzbWF0Y2godGFnc09iamVjdCwgdmFsdWVTdGVwcywgbG93ZXJTdGVwcywgdXBwZXJTdGVwcykgewogICAgICAgICAgICBpZiAobG9kYXNoLmlzRXF1YWwobG93ZXJTdGVwcywgdmFsdWVTdGVwcykgJiYKICAgICAgICAgICAgICAgIGxvZGFzaC5pc0VxdWFsKHVwcGVyU3RlcHMsIHZhbHVlU3RlcHMpKSB7CiAgICAgICAgICAgICAgICAvLyBUaGVyZSBpcyBubyBtaXNtYXRjaC4KICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBzZXJpZXNPYmplY3Q6IHRhZ3NPYmplY3QsCiAgICAgICAgICAgICAgICB2YWx1ZVN0ZXBzOiB2YWx1ZVN0ZXBzLAogICAgICAgICAgICAgICAgbG93ZXJTdGVwczogbG93ZXJTdGVwcywKICAgICAgICAgICAgICAgIHVwcGVyU3RlcHM6IHVwcGVyU3RlcHMsCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVOZXdEYXRhU2VyaWVzKHJ1biwgdGFnLCBzZXJpZXNOYW1lLCBkYXRhUG9pbnRzKSB7CiAgICAgICAgICAgIC8vIElmIHRoZSBydW4gaGFzIG5vdCBiZWVuIHNlZW4gYmVmb3JlLCBkZWZpbmUgdGhlIG5leHQKICAgICAgICAgICAgLy8gYXZhaWxhYmxlIG1hcmtlciBpbmRleC4KICAgICAgICAgICAgdGhpcy5fcnVuVG9OZXh0QXZhaWxhYmxlU3ltYm9sSW5kZXhbcnVuXSB8PSAwOwogICAgICAgICAgICAvLyBFdmVyeSBkYXRhIHNlcmllcyB3aXRoaW4gYSBydW4gaGFzIGEgdW5pcXVlIHN5bWJvbC4KICAgICAgICAgICAgY29uc3QgbGluZUNoYXJ0U3ltYm9sID0gU1lNQk9MU19MSVNUW3RoaXMuX3J1blRvTmV4dEF2YWlsYWJsZVN5bWJvbEluZGV4W3J1bl1dOwogICAgICAgICAgICAvLyBDcmVhdGUgYSBzZXJpZXMgd2l0aCB0aGlzIG5hbWUuCiAgICAgICAgICAgIGNvbnN0IHNlcmllcyA9IG5ldyBEYXRhU2VyaWVzKHJ1biwgdGFnLCBzZXJpZXNOYW1lLCBkYXRhUG9pbnRzLCBsaW5lQ2hhcnRTeW1ib2wpOwogICAgICAgICAgICAvLyBMb29wIGJhY2sgdG8gdGhlIGJlZ2lubmluZyBpZiB3ZSBhcmUgb3V0IG9mIHN5bWJvbHMuCiAgICAgICAgICAgIGNvbnN0IG51bVN5bWJvbHMgPSBTWU1CT0xTX0xJU1QubGVuZ3RoOwogICAgICAgICAgICB0aGlzLl9ydW5Ub05leHRBdmFpbGFibGVTeW1ib2xJbmRleFtydW5dID0KICAgICAgICAgICAgICAgICh0aGlzLl9ydW5Ub05leHRBdmFpbGFibGVTeW1ib2xJbmRleFtydW5dICsgMSkgJSBudW1TeW1ib2xzOwogICAgICAgICAgICByZXR1cm4gc2VyaWVzOwogICAgICAgIH0KICAgICAgICBfdXBkYXRlQ2hhcnQoKSB7CiAgICAgICAgICAgIHZhciBfbmFtZVRvRGF0YVNlcmllcyA9IHRoaXMuX25hbWVUb0RhdGFTZXJpZXM7CiAgICAgICAgICAgIC8vIEFkZCBuZXcgZGF0YSBzZXJpZXMuCiAgICAgICAgICAgIGxvZGFzaC5mb3JPd24oX25hbWVUb0RhdGFTZXJpZXMsIChkYXRhU2VyaWVzKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLiQubG9hZGVyLnNldFNlcmllc0RhdGEoZGF0YVNlcmllcy5nZXROYW1lKCksIGRhdGFTZXJpZXMuZ2V0RGF0YSgpKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuJC5sb2FkZXIuY29tbWl0Q2hhbmdlcygpOwogICAgICAgIH0KICAgICAgICBnZXQgX3Nlcmllc05hbWVzKCkgewogICAgICAgICAgICBjb25zdCBydW5Mb29rdXAgPSBuZXcgU2V0KHRoaXMucnVucyk7CiAgICAgICAgICAgIHJldHVybiBPYmplY3QuZW50cmllcyh0aGlzLl9uYW1lVG9EYXRhU2VyaWVzKQogICAgICAgICAgICAgICAgLmZpbHRlcigoW18sIHNlcmllc10pID0+IHJ1bkxvb2t1cC5oYXMoc2VyaWVzLnJ1bikpCiAgICAgICAgICAgICAgICAubWFwKChbbmFtZV0pID0+IG5hbWUpOwogICAgICAgIH0KICAgICAgICBfZGV0ZXJtaW5lQ29sb3IoY29sb3JTY2FsZSwgc2VyaWVzTmFtZSkgewogICAgICAgICAgICByZXR1cm4gY29sb3JTY2FsZS5zY2FsZShzZXJpZXNOYW1lKTsKICAgICAgICB9CiAgICAgICAgX3JlZnJlc2hEYXRhU2VyaWVzKCkgewogICAgICAgICAgICB2YXIgX3RhZ0ZpbHRlciA9IHRoaXMuX3RhZ0ZpbHRlcjsKICAgICAgICAgICAgdGhpcy5zZXQoJ19uYW1lVG9EYXRhU2VyaWVzJywge30pOwogICAgICAgIH0KICAgICAgICBfY3JlYXRlU3ltYm9sRnVuY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiAoc2VyaWVzTmFtZSkgPT4gdGhpcy5fbmFtZVRvRGF0YVNlcmllc1tzZXJpZXNOYW1lXS5nZXRTeW1ib2woKS5tZXRob2QoKTsKICAgICAgICB9CiAgICAgICAgX2RldGVybWluZVN5bWJvbChfbmFtZVRvRGF0YVNlcmllcywgc2VyaWVzTmFtZSkgewogICAgICAgICAgICByZXR1cm4gX25hbWVUb0RhdGFTZXJpZXNbc2VyaWVzTmFtZV0uZ2V0U3ltYm9sKCkuY2hhcmFjdGVyOwogICAgICAgIH0KICAgICAgICBnZXQgX3RhZ0ZpbHRlcigpIHsKICAgICAgICAgICAgdmFyIG1hcmdpbkNoYXJ0U2VyaWVzID0gdGhpcy5tYXJnaW5DaGFydFNlcmllczsKICAgICAgICAgICAgY29uc3QgdGFncyA9IGxvZGFzaC5mbGF0dGVuKG1hcmdpbkNoYXJ0U2VyaWVzLm1hcCgoc2VyaWVzKSA9PiBbCiAgICAgICAgICAgICAgICBzZXJpZXMudmFsdWUsCiAgICAgICAgICAgICAgICBzZXJpZXMubG93ZXIsCiAgICAgICAgICAgICAgICBzZXJpZXMudXBwZXIsCiAgICAgICAgICAgIF0pKTsKICAgICAgICAgICAgY29uc3QgZXNjYXBlZFRhZ3MgPSB0YWdzLm1hcCgocikgPT4gJygnICsgdGhpcy5fZXNjYXBlUmVnZXhDaGFyYWN0ZXJzKHIpICsgJyknKTsKICAgICAgICAgICAgLy8gQ29tYmluZSB0aGUgZGlmZmVyZW50IHJlZ2V4ZXMgaW50byBhIHNpbmdsZSByZWdleC4KICAgICAgICAgICAgcmV0dXJuIGVzY2FwZWRUYWdzLmpvaW4oJ3wnKTsKICAgICAgICB9CiAgICAgICAgX2VzY2FwZVJlZ2V4Q2hhcmFjdGVycyhzdHJpbmdWYWx1ZSkgewogICAgICAgICAgICByZXR1cm4gc3RyaW5nVmFsdWUucmVwbGFjZSgvWy4qKz9eJHt9KCl8W1xdXFxdL2csICdcXCQmJyk7CiAgICAgICAgfQogICAgICAgIF9nZXRUb2dnbGVDb2xsYXBzaWJsZUljb24obGlzdE9wZW5lZCkgewogICAgICAgICAgICByZXR1cm4gbGlzdE9wZW5lZCA/ICdleHBhbmQtbGVzcycgOiAnZXhwYW5kLW1vcmUnOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlTWF0Y2hlc09wZW4oKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfbWF0Y2hlc0xpc3RPcGVuZWQnLCAhdGhpcy5fbWF0Y2hlc0xpc3RPcGVuZWQpOwogICAgICAgIH0KICAgICAgICBnZXQgX3RpdGxlRGlzcGxheVN0cmluZygpIHsKICAgICAgICAgICAgdmFyIHRpdGxlID0gdGhpcy50aXRsZTsKICAgICAgICAgICAgLy8gSWYgbm8gdGl0bGUgaXMgcHJvdmlkZWQsIHVzZSB0aGUgdGFnIGZpbHRlciwgd2hpY2ggaXMgYSBjb21iaW5hdGlvbgogICAgICAgICAgICAvLyBvZiB0aGUgdGFncyBmb3IgdGhlIHZhbHVlLCBsb3dlciwgYW5kIHVwcGVyIGZpZWxkcyBvZiBlYWNoIHNlcmllcy4KICAgICAgICAgICAgcmV0dXJuIHRpdGxlIHx8ICd1bnRpdGxlZCc7CiAgICAgICAgfQogICAgICAgIF9zZXBhcmF0ZVdpdGhDb21tYXMobnVtYmVycykgewogICAgICAgICAgICByZXR1cm4gbnVtYmVycy5qb2luKCcsICcpOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlTWlzc2luZ1RhZ3NDb2xsYXBzaWJsZU9wZW4oKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfbWlzc2luZ1RhZ3NDb2xsYXBzaWJsZU9wZW5lZCcsICF0aGlzLl9taXNzaW5nVGFnc0NvbGxhcHNpYmxlT3BlbmVkKTsKICAgICAgICB9CiAgICAgICAgX21hdGNoTGlzdEVudHJ5Q29sb3JVcGRhdGVkKCkgewogICAgICAgICAgICBjb25zdCBkb21SZXBlYXQgPSB0aGlzLiQkKCcjbWF0Y2gtbGlzdC1yZXBlYXQnKTsKICAgICAgICAgICAgaWYgKCFkb21SZXBlYXQpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLnJvb3QKICAgICAgICAgICAgICAgIC5xdWVyeVNlbGVjdG9yQWxsKCcubWF0Y2gtbGlzdC1lbnRyeScpCiAgICAgICAgICAgICAgICAuZm9yRWFjaCgoZW50cnlFbGVtZW50KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBzZXJpZXNOYW1lID0gZG9tUmVwZWF0Lml0ZW1Gb3JFbGVtZW50KGVudHJ5RWxlbWVudCk7CiAgICAgICAgICAgICAgICBlbnRyeUVsZW1lbnQuc3R5bGUuY29sb3IgPSB0aGlzLl9kZXRlcm1pbmVDb2xvcih0aGlzLl9jb2xvclNjYWxlLCBzZXJpZXNOYW1lKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgfTsKICAgIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWNhcmQtaGVhZGluZyBkaXNwbGF5LW5hbWU9IltbX3RpdGxlRGlzcGxheVN0cmluZ11dIj48L3RmLWNhcmQtaGVhZGluZz4KICAgIDxkaXYgaWQ9InRmLWxpbmUtY2hhcnQtZGF0YS1sb2FkZXItY29udGFpbmVyIj4KICAgICAgPHRmLWxpbmUtY2hhcnQtZGF0YS1sb2FkZXIKICAgICAgICBpZD0ibG9hZGVyIgogICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICBjb2xvci1zY2FsZT0iW1tfY29sb3JTY2FsZV1dIgogICAgICAgIGRhdGEtc2VyaWVzPSJbW19zZXJpZXNOYW1lc11dIgogICAgICAgIGZpbGwtYXJlYT0iW1tfZmlsbEFyZWFdXSIKICAgICAgICBpZ25vcmUteS1vdXRsaWVycz0iW1tpZ25vcmVZT3V0bGllcnNdXSIKICAgICAgICBsb2FkLWtleT0iW1tfdGFnRmlsdGVyXV0iCiAgICAgICAgZGF0YS10by1sb2FkPSJbW3J1bnNdXSIKICAgICAgICByZXF1ZXN0LWRhdGE9IltbX3JlcXVlc3REYXRhXV0iCiAgICAgICAgbG9nLXNjYWxlLWFjdGl2ZT0iW1tfbG9nU2NhbGVBY3RpdmVdXSIKICAgICAgICBsb2FkLWRhdGEtY2FsbGJhY2s9IltbX2NyZWF0ZVByb2Nlc3NEYXRhRnVuY3Rpb24obWFyZ2luQ2hhcnRTZXJpZXMpXV0iCiAgICAgICAgcmVxdWVzdC1tYW5hZ2VyPSJbW3JlcXVlc3RNYW5hZ2VyXV0iCiAgICAgICAgc3ltYm9sLWZ1bmN0aW9uPSJbW19jcmVhdGVTeW1ib2xGdW5jdGlvbigpXV0iCiAgICAgICAgdG9vbHRpcC1jb2x1bW5zPSJbW190b29sdGlwQ29sdW1uc11dIgogICAgICAgIHRvb2x0aXAtc29ydGluZy1tZXRob2Q9IltbdG9vbHRpcFNvcnRpbmdNZXRob2RdXSIKICAgICAgICB4LXR5cGU9IltbeFR5cGVdXSIKICAgICAgPgogICAgICA8L3RmLWxpbmUtY2hhcnQtZGF0YS1sb2FkZXI+CiAgICA8L2Rpdj4KICAgIDxkaXYgaWQ9ImJ1dHRvbnMiPgogICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICBzZWxlY3RlZCQ9IltbX2V4cGFuZGVkXV0iCiAgICAgICAgaWNvbj0iZnVsbHNjcmVlbiIKICAgICAgICBvbi10YXA9Il90b2dnbGVFeHBhbmRlZCIKICAgICAgPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICAgIDxwYXBlci1pY29uLWJ1dHRvbgogICAgICAgIHNlbGVjdGVkJD0iW1tfbG9nU2NhbGVBY3RpdmVdXSIKICAgICAgICBpY29uPSJsaW5lLXdlaWdodCIKICAgICAgICBvbi10YXA9Il90b2dnbGVMb2dTY2FsZSIKICAgICAgICB0aXRsZT0iVG9nZ2xlIHktYXhpcyBsb2cgc2NhbGUiCiAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICBpY29uPSJzZXR0aW5ncy1vdmVyc2NhbiIKICAgICAgICBvbi10YXA9Il9yZXNldERvbWFpbiIKICAgICAgICB0aXRsZT0iRml0IGRvbWFpbiB0byBkYXRhIgogICAgICA+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgPHNwYW4gc3R5bGU9ImZsZXgtZ3JvdzogMSI+PC9zcGFuPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9Iltbc2hvd0Rvd25sb2FkTGlua3NdXSI+CiAgICAgICAgPGRpdiBjbGFzcz0iZG93bmxvYWQtbGlua3MiPgogICAgICAgICAgPHBhcGVyLWRyb3Bkb3duLW1lbnUKICAgICAgICAgICAgbm8tbGFiZWwtZmxvYXQ9InRydWUiCiAgICAgICAgICAgIGxhYmVsPSJzZXJpZXMgdG8gZG93bmxvYWQiCiAgICAgICAgICAgIHNlbGVjdGVkLWl0ZW0tbGFiZWw9Int7X2RhdGFTZXJpZXNOYW1lVG9Eb3dubG9hZH19IgogICAgICAgICAgPgogICAgICAgICAgICA8cGFwZXItbGlzdGJveCBjbGFzcz0iZHJvcGRvd24tY29udGVudCIgc2xvdD0iZHJvcGRvd24tY29udGVudCI+CiAgICAgICAgICAgICAgPHRlbXBsYXRlCiAgICAgICAgICAgICAgICBpcz0iZG9tLXJlcGVhdCIKICAgICAgICAgICAgICAgIGl0ZW1zPSJbW19zZXJpZXNOYW1lc11dIgogICAgICAgICAgICAgICAgYXM9ImRhdGFTZXJpZXNOYW1lIgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxwYXBlci1pdGVtIG5vLWxhYmVsLWZsb2F0PSJ0cnVlIgogICAgICAgICAgICAgICAgICA+W1tkYXRhU2VyaWVzTmFtZV1dPC9wYXBlci1pdGVtCiAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPC9wYXBlci1saXN0Ym94PgogICAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgogICAgICAgICAgPGEKICAgICAgICAgICAgZG93bmxvYWQ9IltbX2RhdGFTZXJpZXNOYW1lVG9Eb3dubG9hZF1dLmNzdiIKICAgICAgICAgICAgaHJlZj0iW1tfY3N2VXJsKF9uYW1lVG9EYXRhU2VyaWVzLCBfZGF0YVNlcmllc05hbWVUb0Rvd25sb2FkKV1dIgogICAgICAgICAgICA+Q1NWPC9hCiAgICAgICAgICA+CiAgICAgICAgICA8YQogICAgICAgICAgICBkb3dubG9hZD0iW1tfZGF0YVNlcmllc05hbWVUb0Rvd25sb2FkXV0uanNvbiIKICAgICAgICAgICAgaHJlZj0iW1tfanNvblVybChfbmFtZVRvRGF0YVNlcmllcywgX2RhdGFTZXJpZXNOYW1lVG9Eb3dubG9hZCldXSIKICAgICAgICAgICAgPkpTT048L2EKICAgICAgICAgID4KICAgICAgICA8L2Rpdj4KICAgICAgPC90ZW1wbGF0ZT4KICAgIDwvZGl2PgoKICAgIDwhLS0gaGVyZSAtLT4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfbWlzc2luZ1RhZ3MubGVuZ3RoXV0iPgogICAgICA8ZGl2IGNsYXNzPSJjb2xsYXBzaWJsZS1saXN0LXRpdGxlIj4KICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgIGljb249IltbX2dldFRvZ2dsZUNvbGxhcHNpYmxlSWNvbihfbWlzc2luZ1RhZ3NDb2xsYXBzaWJsZU9wZW5lZCldXSIKICAgICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlTWlzc2luZ1RhZ3NDb2xsYXBzaWJsZU9wZW4iCiAgICAgICAgICBjbGFzcz0idG9nZ2xlLWNvbGxhcHNpYmxlLWJ1dHRvbiIKICAgICAgICA+CiAgICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICA8c3BhbiBjbGFzcz0iY29sbGFwc2libGUtdGl0bGUtdGV4dCI+CiAgICAgICAgICA8aXJvbi1pY29uIGljb249Imljb25zOmVycm9yIj48L2lyb24taWNvbj4gTWlzc2luZyBUYWdzCiAgICAgICAgPC9zcGFuPgogICAgICA8L2Rpdj4KICAgICAgPGlyb24tY29sbGFwc2Ugb3BlbmVkPSJbW19taXNzaW5nVGFnc0NvbGxhcHNpYmxlT3BlbmVkXV0iPgogICAgICAgIDxkaXYgY2xhc3M9ImVycm9yLWNvbnRlbnQiPgogICAgICAgICAgPGlyb24taWNvbiBjbGFzcz0iZXJyb3ItaWNvbiIgaWNvbj0iaWNvbnM6ZXJyb3IiPjwvaXJvbi1pY29uPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfbWlzc2luZ1RhZ3NdXSIgYXM9Im1pc3NpbmdFbnRyeSI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9Im1pc3NpbmctdGFncy1mb3ItcnVuLWNvbnRhaW5lciI+CiAgICAgICAgICAgICAgUnVuICJbW21pc3NpbmdFbnRyeS5ydW5dXSIgbGFja3MgZGF0YSBmb3IgdGFncwogICAgICAgICAgICAgIDx1bD4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgICBpcz0iZG9tLXJlcGVhdCIKICAgICAgICAgICAgICAgICAgaXRlbXM9IltbbWlzc2luZ0VudHJ5LnRhZ3NdXSIKICAgICAgICAgICAgICAgICAgYXM9InRhZyIKICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgPGxpPltbdGFnXV08L2xpPgogICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICA8L3VsPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvaXJvbi1jb2xsYXBzZT4KICAgIDwvdGVtcGxhdGU+CgogICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW190YWdGaWx0ZXJJbnZhbGlkXV0iPgogICAgICA8ZGl2IGNsYXNzPSJlcnJvci1jb250ZW50Ij4KICAgICAgICA8aXJvbi1pY29uIGNsYXNzPSJlcnJvci1pY29uIiBpY29uPSJpY29uczplcnJvciI+PC9pcm9uLWljb24+CiAgICAgICAgVGhpcyByZWd1bGFyIGV4cHJlc2lvbiBpcyBpbnZhbGlkOjxiciAvPgogICAgICAgIDxzcGFuIGNsYXNzPSJpbnZhbGlkLXJlZ2V4Ij5bW190YWdGaWx0ZXJdXTwvc3Bhbj4KICAgICAgPC9kaXY+CiAgICA8L3RlbXBsYXRlPgoKICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfc3RlcHNNaXNtYXRjaF1dIj4KICAgICAgPGRpdiBjbGFzcz0iZXJyb3ItY29udGVudCI+CiAgICAgICAgPGlyb24taWNvbiBjbGFzcz0iZXJyb3ItaWNvbiIgaWNvbj0iaWNvbnM6ZXJyb3IiPjwvaXJvbi1pY29uPgogICAgICAgIFRoZSBzdGVwcyBmb3IgdmFsdWUsIGxvd2VyLCBhbmQgdXBwZXIgdGFncyBkbyBub3QgbWF0Y2g6CiAgICAgICAgPHVsPgogICAgICAgICAgPGxpPgogICAgICAgICAgICA8c3BhbiBjbGFzcz0idGFnLW5hbWUiPltbX3N0ZXBzTWlzbWF0Y2guc2VyaWVzT2JqZWN0LnZhbHVlXV08L3NwYW4+OgogICAgICAgICAgICBbW19zZXBhcmF0ZVdpdGhDb21tYXMoX3N0ZXBzTWlzbWF0Y2gudmFsdWVTdGVwcyldXQogICAgICAgICAgPC9saT4KICAgICAgICAgIDxsaT4KICAgICAgICAgICAgPHNwYW4gY2xhc3M9InRhZy1uYW1lIj5bW19zdGVwc01pc21hdGNoLnNlcmllc09iamVjdC5sb3dlcl1dPC9zcGFuPjoKICAgICAgICAgICAgW1tfc2VwYXJhdGVXaXRoQ29tbWFzKF9zdGVwc01pc21hdGNoLmxvd2VyU3RlcHMpXV0KICAgICAgICAgIDwvbGk+CiAgICAgICAgICA8bGk+CiAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJ0YWctbmFtZSI+W1tfc3RlcHNNaXNtYXRjaC5zZXJpZXNPYmplY3QudXBwZXJdXTwvc3Bhbj46CiAgICAgICAgICAgIFtbX3NlcGFyYXRlV2l0aENvbW1hcyhfc3RlcHNNaXNtYXRjaC51cHBlclN0ZXBzKV1dCiAgICAgICAgICA8L2xpPgogICAgICAgIDwvdWw+CiAgICAgIDwvZGl2PgogICAgPC90ZW1wbGF0ZT4KCiAgICA8ZGl2IGlkPSJtYXRjaGVzLWNvbnRhaW5lciI+CiAgICAgIDxkaXYgY2xhc3M9ImNvbGxhcHNpYmxlLWxpc3QtdGl0bGUiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfc2VyaWVzTmFtZXMubGVuZ3RoXV0iPgogICAgICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgICAgIGljb249IltbX2dldFRvZ2dsZUNvbGxhcHNpYmxlSWNvbihfbWF0Y2hlc0xpc3RPcGVuZWQpXV0iCiAgICAgICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlTWF0Y2hlc09wZW4iCiAgICAgICAgICAgIGNsYXNzPSJ0b2dnbGUtbWF0Y2hlcy1idXR0b24iCiAgICAgICAgICA+CiAgICAgICAgICA8L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgIDwvdGVtcGxhdGU+CgogICAgICAgIDxzcGFuIGNsYXNzPSJjb2xsYXBzaWJsZS10aXRsZS10ZXh0Ij4KICAgICAgICAgIE1hdGNoZXMgKFtbX3Nlcmllc05hbWVzLmxlbmd0aF1dKQogICAgICAgIDwvc3Bhbj4KICAgICAgPC9kaXY+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfc2VyaWVzTmFtZXMubGVuZ3RoXV0iPgogICAgICAgIDxpcm9uLWNvbGxhcHNlIG9wZW5lZD0iW1tfbWF0Y2hlc0xpc3RPcGVuZWRdXSI+CiAgICAgICAgICA8ZGl2IGlkPSJtYXRjaGVzLWxpc3QiPgogICAgICAgICAgICA8dGVtcGxhdGUKICAgICAgICAgICAgICBpcz0iZG9tLXJlcGVhdCIKICAgICAgICAgICAgICBpdGVtcz0iW1tfc2VyaWVzTmFtZXNdXSIKICAgICAgICAgICAgICBhcz0ic2VyaWVzTmFtZSIKICAgICAgICAgICAgICBpZD0ibWF0Y2gtbGlzdC1yZXBlYXQiCiAgICAgICAgICAgICAgb24tZG9tLWNoYW5nZT0iX21hdGNoTGlzdEVudHJ5Q29sb3JVcGRhdGVkIgogICAgICAgICAgICA+CiAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ibWF0Y2gtbGlzdC1lbnRyeSI+CiAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0ibWF0Y2gtZW50cnktc3ltYm9sIj4KICAgICAgICAgICAgICAgICAgW1tfZGV0ZXJtaW5lU3ltYm9sKF9uYW1lVG9EYXRhU2VyaWVzLCBzZXJpZXNOYW1lKV1dCiAgICAgICAgICAgICAgICA8L3NwYW4+CiAgICAgICAgICAgICAgICBbW3Nlcmllc05hbWVdXQogICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC9pcm9uLWNvbGxhcHNlPgogICAgICA8L3RlbXBsYXRlPgogICAgPC9kaXY+CgogICAgPHN0eWxlIGluY2x1ZGU9InRmLWN1c3RvbS1zY2FsYXItY2FyZC1zdHlsZSI+PC9zdHlsZT4KICAgIDxzdHlsZT4KICAgICAgLmVycm9yLWNvbnRlbnQgewogICAgICAgIGJhY2tncm91bmQ6ICNmMDA7CiAgICAgICAgYm9yZGVyLXJhZGl1czogNXB4OwogICAgICAgIGNvbG9yOiAjZmZmOwogICAgICAgIG1hcmdpbjogMTBweCAwIDAgMDsKICAgICAgICBwYWRkaW5nOiAxMHB4OwogICAgICB9CgogICAgICAuZXJyb3ItaWNvbiB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgZmlsbDogI2ZmZjsKICAgICAgICBtYXJnaW46IDAgYXV0byA1cHggYXV0bzsKICAgICAgfQoKICAgICAgLmludmFsaWQtcmVnZXggewogICAgICAgIGZvbnQtd2VpZ2h0OiBib2xkOwogICAgICB9CgogICAgICAuZXJyb3ItY29udGVudCB1bCB7CiAgICAgICAgbWFyZ2luOiAxcHggMCAwIDA7CiAgICAgICAgcGFkZGluZzogMCAwIDAgMTlweDsKICAgICAgfQoKICAgICAgLnRhZy1uYW1lIHsKICAgICAgICBmb250LXdlaWdodDogYm9sZDsKICAgICAgfQoKICAgICAgLmNvbGxhcHNpYmxlLWxpc3QtdGl0bGUgewogICAgICAgIG1hcmdpbjogMTBweCAwIDVweCAwOwogICAgICB9CgogICAgICAuY29sbGFwc2libGUtdGl0bGUtdGV4dCB7CiAgICAgICAgdmVydGljYWwtYWxpZ246IG1pZGRsZTsKICAgICAgfQoKICAgICAgI21hdGNoZXMtbGlzdCB7CiAgICAgICAgbWF4LWhlaWdodDogMjAwcHg7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgfQoKICAgICAgLm1hdGNoLWxpc3QtZW50cnkgewogICAgICAgIG1hcmdpbjogMCAwIDVweCAwOwogICAgICB9CgogICAgICAubWF0Y2gtZW50cnktc3ltYm9sIHsKICAgICAgICBmb250LWZhbWlseTogYXJpYWwsIHNhbnMtc2VyaWY7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIHdpZHRoOiAxMHB4OwogICAgICB9CgogICAgICAubWlzc2luZy10YWdzLWZvci1ydW4tY29udGFpbmVyIHsKICAgICAgICBtYXJnaW46IDhweCAwIDAgMDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgInJ1bnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAieFR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJhY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAidGl0bGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIm1hcmdpbkNoYXJ0U2VyaWVzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAiaWdub3JlWU91dGxpZXJzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVxdWVzdE1hbmFnZXIpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAicmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJzaG93RG93bmxvYWRMaW5rcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ0YWdNZXRhZGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ0b29sdGlwU29ydGluZ01ldGhvZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfY29sb3JTY2FsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl90YWdGaWx0ZXJJbnZhbGlkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9uYW1lVG9EYXRhU2VyaWVzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfZXhwYW5kZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfbG9nU2NhbGVBY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfcmVxdWVzdERhdGEiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAiX3J1blRvTmV4dEF2YWlsYWJsZVN5bWJvbEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAiX21hdGNoZXNMaXN0T3BlbmVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9maWxsQXJlYSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNYXJnaW5DaGFydENhcmQucHJvdG90eXBlLCAiX3Rvb2x0aXBDb2x1bW5zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfbWlzc2luZ1RhZ3MiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfbWlzc2luZ1RhZ3NDb2xsYXBzaWJsZU9wZW5lZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfc3RlcHNNaXNtYXRjaCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdfbmFtZVRvRGF0YVNlcmllcycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl91cGRhdGVDaGFydCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19uYW1lVG9EYXRhU2VyaWVzJywgJ3J1bnMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfc2VyaWVzTmFtZXMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ190YWdGaWx0ZXInKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfcmVmcmVzaERhdGFTZXJpZXMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdtYXJnaW5DaGFydFNlcmllcycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl90YWdGaWx0ZXIiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCd0aXRsZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl90aXRsZURpc3BsYXlTdHJpbmciLCBudWxsKTsKICAgIF9UZkN1c3RvbVNjYWxhck1hcmdpbkNoYXJ0Q2FyZCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWN1c3RvbS1zY2FsYXItbWFyZ2luLWNoYXJ0LWNhcmQnKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTWFyZ2luQ2hhcnRDYXJkKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KCiAgICB2YXIgdGZfYmFja2VuZCA9IC8qI19fUFVSRV9fKi9PYmplY3QuZnJlZXplKHsKICAgICAgICBfX3Byb3RvX186IG51bGwsCiAgICAgICAgVFlQRVM6IFRZUEVTJDEsCiAgICAgICAgZ2V0UnVuc05hbWVkOiBnZXRSdW5zTmFtZWQsCiAgICAgICAgZ2V0VGFnczogZ2V0VGFncywKICAgICAgICBmaWx0ZXJUYWdzOiBmaWx0ZXJUYWdzLAogICAgICAgIExpc3RlbktleTogTGlzdGVuS2V5JDEsCiAgICAgICAgQmFzZVN0b3JlOiBCYXNlU3RvcmUsCiAgICAgICAgQ2FuY2VsbGVyOiBDYW5jZWxsZXIsCiAgICAgICAgRW52aXJvbm1lbnRTdG9yZTogRW52aXJvbm1lbnRTdG9yZSwKICAgICAgICBlbnZpcm9ubWVudFN0b3JlOiBlbnZpcm9ubWVudFN0b3JlLAogICAgICAgIEV4cGVyaW1lbnRzU3RvcmU6IEV4cGVyaW1lbnRzU3RvcmUsCiAgICAgICAgZXhwZXJpbWVudHNTdG9yZTogZXhwZXJpbWVudHNTdG9yZSwKICAgICAgICBSZXF1ZXN0Q2FuY2VsbGF0aW9uRXJyb3I6IFJlcXVlc3RDYW5jZWxsYXRpb25FcnJvciwKICAgICAgICBJbnZhbGlkUmVxdWVzdE9wdGlvbnNFcnJvcjogSW52YWxpZFJlcXVlc3RPcHRpb25zRXJyb3IsCiAgICAgICAgUmVxdWVzdE5ldHdvcmtFcnJvcjogUmVxdWVzdE5ldHdvcmtFcnJvciwKICAgICAgICBnZXQgSHR0cE1ldGhvZFR5cGUgKCkgeyByZXR1cm4gSHR0cE1ldGhvZFR5cGU7IH0sCiAgICAgICAgUmVxdWVzdE9wdGlvbnM6IFJlcXVlc3RPcHRpb25zLAogICAgICAgIFJlcXVlc3RNYW5hZ2VyOiBSZXF1ZXN0TWFuYWdlciwKICAgICAgICBjcmVhdGVSb3V0ZXI6IGNyZWF0ZVJvdXRlciwKICAgICAgICBnZXRSb3V0ZXI6IGdldFJvdXRlciwKICAgICAgICBzZXRSb3V0ZXI6IHNldFJvdXRlciwKICAgICAgICBjcmVhdGVTZWFyY2hQYXJhbTogY3JlYXRlU2VhcmNoUGFyYW0sCiAgICAgICAgUnVuc1N0b3JlOiBSdW5zU3RvcmUsCiAgICAgICAgcnVuc1N0b3JlOiBydW5zU3RvcmUsCiAgICAgICAgYWRkUGFyYW1zOiBhZGRQYXJhbXMKICAgIH0pOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZCA9IGNsYXNzIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZCBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLmFjdGl2ZSA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX2NvbG9yU2NhbGUgPSBuZXcgRGF0YVNlcmllc0NvbG9yU2NhbGUoewogICAgICAgICAgICAgICAgc2NhbGU6IHJ1bnNDb2xvclNjYWxlLAogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fbmFtZVRvRGF0YVNlcmllcyA9IHt9OwogICAgICAgICAgICB0aGlzLl9leHBhbmRlZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9yZXF1ZXN0RGF0YSA9IChpdGVtcywgb25Mb2FkLCBvbkZpbmlzaCkgPT4gewogICAgICAgICAgICAgICAgY29uc3Qgcm91dGVyID0gZ2V0Um91dGVyKCk7CiAgICAgICAgICAgICAgICBjb25zdCBiYXNlVXJsID0gcm91dGVyLnBsdWdpblJvdXRlKCdjdXN0b21fc2NhbGFycycsICcvc2NhbGFycycpOwogICAgICAgICAgICAgICAgUHJvbWlzZS5hbGwoaXRlbXMubWFwKChpdGVtKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcnVuID0gaXRlbTsKICAgICAgICAgICAgICAgICAgICBjb25zdCB0YWcgPSB0aGlzLl90YWdGaWx0ZXI7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgdXJsID0gYWRkUGFyYW1zKGJhc2VVcmwsIHsgdGFnLCBydW4gfSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVxdWVzdE1hbmFnZXIKICAgICAgICAgICAgICAgICAgICAgICAgLnJlcXVlc3QodXJsKQogICAgICAgICAgICAgICAgICAgICAgICAudGhlbigoZGF0YSkgPT4gdm9pZCBvbkxvYWQoeyBpdGVtLCBkYXRhIH0pKTsKICAgICAgICAgICAgICAgIH0pKS5maW5hbGx5KCgpID0+IHZvaWQgb25GaW5pc2goKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX3J1blRvTmV4dEF2YWlsYWJsZVN5bWJvbEluZGV4ID0ge307CiAgICAgICAgICAgIHRoaXMuX21hdGNoZXNMaXN0T3BlbmVkID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgdGhpcy4kLmxvYWRlci5yZWxvYWQoKTsKICAgICAgICB9CiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICB0aGlzLiQubG9hZGVyLnJlZHJhdygpOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlRXhwYW5kZWQoZSkgewogICAgICAgICAgICB0aGlzLnNldCgnX2V4cGFuZGVkJywgIXRoaXMuX2V4cGFuZGVkKTsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUxvZ1NjYWxlKCkgewogICAgICAgICAgICB0aGlzLnNldCgnX2xvZ1NjYWxlQWN0aXZlJywgIXRoaXMuX2xvZ1NjYWxlQWN0aXZlKTsKICAgICAgICB9CiAgICAgICAgX3Jlc2V0RG9tYWluKCkgewogICAgICAgICAgICBjb25zdCBjaGFydCA9IHRoaXMuJC5sb2FkZXI7CiAgICAgICAgICAgIGlmIChjaGFydCkgewogICAgICAgICAgICAgICAgY2hhcnQucmVzZXREb21haW4oKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfY3N2VXJsKG5hbWVUb1NlcmllcywgZGF0YVNlcmllc05hbWUpIHsKICAgICAgICAgICAgaWYgKCFkYXRhU2VyaWVzTmFtZSkKICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgY29uc3QgYmFzZVVybCA9IHRoaXMuX2Rvd25sb2FkRGF0YVVybChuYW1lVG9TZXJpZXMsIGRhdGFTZXJpZXNOYW1lKTsKICAgICAgICAgICAgcmV0dXJuIGFkZFBhcmFtcyhiYXNlVXJsLCB7IGZvcm1hdDogJ2NzdicgfSk7CiAgICAgICAgfQogICAgICAgIF9qc29uVXJsKG5hbWVUb1NlcmllcywgZGF0YVNlcmllc05hbWUpIHsKICAgICAgICAgICAgaWYgKCFkYXRhU2VyaWVzTmFtZSkKICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgY29uc3QgYmFzZVVybCA9IHRoaXMuX2Rvd25sb2FkRGF0YVVybChuYW1lVG9TZXJpZXMsIGRhdGFTZXJpZXNOYW1lKTsKICAgICAgICAgICAgcmV0dXJuIGFkZFBhcmFtcyhiYXNlVXJsLCB7IGZvcm1hdDogJ2pzb24nIH0pOwogICAgICAgIH0KICAgICAgICBfZG93bmxvYWREYXRhVXJsKG5hbWVUb1NlcmllcywgZGF0YVNlcmllc05hbWUpIHsKICAgICAgICAgICAgY29uc3QgZGF0YVNlcmllcyA9IG5hbWVUb1Nlcmllc1tkYXRhU2VyaWVzTmFtZV07CiAgICAgICAgICAgIGNvbnN0IGdldFZhcnMgPSB7CiAgICAgICAgICAgICAgICB0YWc6IGRhdGFTZXJpZXMuZ2V0VGFnKCksCiAgICAgICAgICAgICAgICBydW46IGRhdGFTZXJpZXMuZ2V0UnVuKCksCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHJldHVybiBhZGRQYXJhbXMoZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2N1c3RvbV9zY2FsYXJzJywgJy9kb3dubG9hZF9kYXRhJyksIGdldFZhcnMpOwogICAgICAgIH0KICAgICAgICBfY3JlYXRlUHJvY2Vzc0RhdGFGdW5jdGlvbigpIHsKICAgICAgICAgICAgLy8gVGhpcyBmdW5jdGlvbiBpcyBjYWxsZWQgd2hlbiBkYXRhIGlzIHJlY2VpdmVkIGZyb20gdGhlIGJhY2tlbmQuCiAgICAgICAgICAgIHJldHVybiAoc2NhbGFyQ2hhcnQsIHJ1biwgZGF0YSkgPT4gewogICAgICAgICAgICAgICAgaWYgKGRhdGEucmVnZXhfdmFsaWQpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgdXNlcidzIHJlZ3VsYXIgZXhwcmVzc2lvbiB3YXMgdmFsaWQuCiAgICAgICAgICAgICAgICAgICAgLy8gSW5jb3Jwb3JhdGUgdGhlc2UgbmV3bHkgbG9hZGVkIHZhbHVlcy4KICAgICAgICAgICAgICAgICAgICBjb25zdCBuZXdNYXBwaW5nID0gbG9kYXNoLmNsb25lKHRoaXMuX25hbWVUb0RhdGFTZXJpZXMpOwogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5mb3JPd24oZGF0YS50YWdfdG9fZXZlbnRzLCAoc2NhbGFyRXZlbnRzLCB0YWcpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZGF0YSA9IHNjYWxhckV2ZW50cy5tYXAoKGRhdHVtKSA9PiAoewogICAgICAgICAgICAgICAgICAgICAgICAgICAgd2FsbF90aW1lOiBuZXcgRGF0ZShkYXR1bVswXSAqIDEwMDApLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RlcDogZGF0dW1bMV0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzY2FsYXI6IGRhdHVtWzJdLAogICAgICAgICAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IHNlcmllc05hbWUgPSBnZW5lcmF0ZURhdGFTZXJpZXNOYW1lKHJ1biwgdGFnKTsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZGF0dW0gPSBuZXdNYXBwaW5nW3Nlcmllc05hbWVdOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAoZGF0dW0pIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgc2VyaWVzIGFscmVhZHkgZXhpc3RzLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgZGF0dW0uc2V0RGF0YShkYXRhKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNVbmRlZmluZWQodGhpcy5fcnVuVG9OZXh0QXZhaWxhYmxlU3ltYm9sSW5kZXhbcnVuXSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBUaGUgcnVuIGhhcyBub3QgYmVlbiBzZWVuIGJlZm9yZS4gRGVmaW5lIHRoZSBuZXh0IGF2YWlsYWJsZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIG1hcmtlciBpbmRleC4KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9ydW5Ub05leHRBdmFpbGFibGVTeW1ib2xJbmRleFtydW5dID0gMDsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIEV2ZXJ5IGRhdGEgc2VyaWVzIHdpdGhpbiBhIHJ1biBoYXMgYSB1bmlxdWUgc3ltYm9sLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgbGluZUNoYXJ0U3ltYm9sID0gU1lNQk9MU19MSVNUW3RoaXMuX3J1blRvTmV4dEF2YWlsYWJsZVN5bWJvbEluZGV4W3J1bl1dOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gQ3JlYXRlIGEgc2VyaWVzIHdpdGggdGhpcyBuYW1lLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2VyaWVzID0gbmV3IERhdGFTZXJpZXMocnVuLCB0YWcsIHNlcmllc05hbWUsIGRhdGEsIGxpbmVDaGFydFN5bWJvbCk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBuZXdNYXBwaW5nW3Nlcmllc05hbWVdID0gc2VyaWVzOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gTG9vcCBiYWNrIHRvIHRoZSBiZWdpbm5pbmcgaWYgd2UgYXJlIG91dCBvZiBzeW1ib2xzLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgbnVtU3ltYm9scyA9IFNZTUJPTFNfTElTVC5sZW5ndGg7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9ydW5Ub05leHRBdmFpbGFibGVTeW1ib2xJbmRleFtydW5dID0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAodGhpcy5fcnVuVG9OZXh0QXZhaWxhYmxlU3ltYm9sSW5kZXhbcnVuXSArIDEpICUgbnVtU3ltYm9sczsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfbmFtZVRvRGF0YVNlcmllcycsIG5ld01hcHBpbmcpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBfdXBkYXRlQ2hhcnQoKSB7CiAgICAgICAgICAgIHZhciBfbmFtZVRvRGF0YVNlcmllcyA9IHRoaXMuX25hbWVUb0RhdGFTZXJpZXM7CiAgICAgICAgICAgIC8vIEFkZCBuZXcgZGF0YSBzZXJpZXMuCiAgICAgICAgICAgIE9iamVjdC5lbnRyaWVzKF9uYW1lVG9EYXRhU2VyaWVzKS5mb3JFYWNoKChbbmFtZSwgc2VyaWVzXSkgPT4gewogICAgICAgICAgICAgICAgdGhpcy4kLmxvYWRlci5zZXRTZXJpZXNEYXRhKG5hbWUsIHNlcmllcy5nZXREYXRhKCkpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy4kLmxvYWRlci5jb21taXRDaGFuZ2VzKCk7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlU2VsZWN0ZWRSdW5zU2V0KHJ1bnMpIHsKICAgICAgICAgICAgY29uc3QgbWFwcGluZyA9IHt9OwogICAgICAgICAgICBsb2Rhc2guZm9yRWFjaChydW5zLCAocnVuKSA9PiB7CiAgICAgICAgICAgICAgICBtYXBwaW5nW3J1bl0gPSAxOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIG1hcHBpbmc7CiAgICAgICAgfQogICAgICAgIGdldCBfc2VyaWVzTmFtZXMoKSB7CiAgICAgICAgICAgIGNvbnN0IHJ1bkxvb2t1cCA9IG5ldyBTZXQodGhpcy5ydW5zKTsKICAgICAgICAgICAgcmV0dXJuIE9iamVjdC5lbnRyaWVzKHRoaXMuX25hbWVUb0RhdGFTZXJpZXMpCiAgICAgICAgICAgICAgICAuZmlsdGVyKChbXywgc2VyaWVzXSkgPT4gcnVuTG9va3VwLmhhcyhzZXJpZXMucnVuKSkKICAgICAgICAgICAgICAgIC5tYXAoKFtuYW1lXSkgPT4gbmFtZSk7CiAgICAgICAgfQogICAgICAgIF9kZXRlcm1pbmVDb2xvcihjb2xvclNjYWxlLCBzZXJpZXNOYW1lKSB7CiAgICAgICAgICAgIHJldHVybiBjb2xvclNjYWxlLnNjYWxlKHNlcmllc05hbWUpOwogICAgICAgIH0KICAgICAgICBfcmVmcmVzaERhdGFTZXJpZXMoKSB7CiAgICAgICAgICAgIHZhciBfdGFnRmlsdGVyID0gdGhpcy5fdGFnRmlsdGVyOwogICAgICAgICAgICB0aGlzLnNldCgnX25hbWVUb0RhdGFTZXJpZXMnLCB7fSk7CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVTeW1ib2xGdW5jdGlvbigpIHsKICAgICAgICAgICAgcmV0dXJuIChzZXJpZXNOYW1lKSA9PiB0aGlzLl9uYW1lVG9EYXRhU2VyaWVzW3Nlcmllc05hbWVdLmdldFN5bWJvbCgpLm1ldGhvZCgpOwogICAgICAgIH0KICAgICAgICBfZGV0ZXJtaW5lU3ltYm9sKG5hbWVUb1Nlcmllcywgc2VyaWVzTmFtZSkgewogICAgICAgICAgICByZXR1cm4gbmFtZVRvU2VyaWVzW3Nlcmllc05hbWVdLmdldFN5bWJvbCgpLmNoYXJhY3RlcjsKICAgICAgICB9CiAgICAgICAgZ2V0IF90YWdGaWx0ZXIoKSB7CiAgICAgICAgICAgIHZhciB0YWdSZWdleGVzID0gdGhpcy50YWdSZWdleGVzOwogICAgICAgICAgICBpZiAodGFnUmVnZXhlcy5sZW5ndGggPT09IDEpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0YWdSZWdleGVzWzBdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvbWJpbmUgdGhlIGRpZmZlcmVudCByZWdleGVzIGludG8gYSBzaW5nbGUgcmVnZXguCiAgICAgICAgICAgIHJldHVybiB0YWdSZWdleGVzLm1hcCgocikgPT4gJygnICsgciArICcpJykuam9pbignfCcpOwogICAgICAgIH0KICAgICAgICBfZ2V0VG9nZ2xlTWF0Y2hlc0ljb24obWF0Y2hlc0xpc3RPcGVuZWQpIHsKICAgICAgICAgICAgcmV0dXJuIG1hdGNoZXNMaXN0T3BlbmVkID8gJ2V4cGFuZC1sZXNzJyA6ICdleHBhbmQtbW9yZSc7CiAgICAgICAgfQogICAgICAgIF90b2dnbGVNYXRjaGVzT3BlbigpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19tYXRjaGVzTGlzdE9wZW5lZCcsICF0aGlzLl9tYXRjaGVzTGlzdE9wZW5lZCk7CiAgICAgICAgfQogICAgICAgIGdldCBfdGl0bGVEaXNwbGF5U3RyaW5nKCkgewogICAgICAgICAgICB2YXIgdGl0bGUgPSB0aGlzLnRpdGxlOwogICAgICAgICAgICAvLyBJZiBubyB0aXRsZSBpcyBwcm92aWRlZCwgdXNlIGEgcGxhY2Vob2xkZXIgc3RyaW5nLgogICAgICAgICAgICByZXR1cm4gdGl0bGUgfHwgJ3VudGl0bGVkJzsKICAgICAgICB9CiAgICAgICAgX21hdGNoTGlzdEVudHJ5Q29sb3JVcGRhdGVkKGV2ZW50KSB7CiAgICAgICAgICAgIGNvbnN0IGRvbVJlcGVhdCA9IHRoaXMuJCQoJyNtYXRjaC1saXN0LXJlcGVhdCcpOwogICAgICAgICAgICBpZiAoIWRvbVJlcGVhdCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMucm9vdAogICAgICAgICAgICAgICAgLnF1ZXJ5U2VsZWN0b3JBbGwoJy5tYXRjaC1saXN0LWVudHJ5JykKICAgICAgICAgICAgICAgIC5mb3JFYWNoKChlbnRyeUVsZW1lbnQpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IHNlcmllc05hbWUgPSBkb21SZXBlYXQuaXRlbUZvckVsZW1lbnQoZW50cnlFbGVtZW50KTsKICAgICAgICAgICAgICAgIGVudHJ5RWxlbWVudC5zdHlsZS5jb2xvciA9IHRoaXMuX2RldGVybWluZUNvbG9yKHRoaXMuX2NvbG9yU2NhbGUsIHNlcmllc05hbWUpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICB9OwogICAgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8dGYtY2FyZC1oZWFkaW5nIGRpc3BsYXktbmFtZT0iW1tfdGl0bGVEaXNwbGF5U3RyaW5nXV0iPjwvdGYtY2FyZC1oZWFkaW5nPgogICAgPGRpdiBpZD0idGYtbGluZS1jaGFydC1kYXRhLWxvYWRlci1jb250YWluZXIiPgogICAgICA8dGYtbGluZS1jaGFydC1kYXRhLWxvYWRlcgogICAgICAgIGlkPSJsb2FkZXIiCiAgICAgICAgYWN0aXZlPSJbW2FjdGl2ZV1dIgogICAgICAgIGNvbG9yLXNjYWxlPSJbW19jb2xvclNjYWxlXV0iCiAgICAgICAgZGF0YS1zZXJpZXM9IltbX3Nlcmllc05hbWVzXV0iCiAgICAgICAgaWdub3JlLXktb3V0bGllcnM9IltbaWdub3JlWU91dGxpZXJzXV0iCiAgICAgICAgbG9hZC1rZXk9IltbX3RhZ0ZpbHRlcl1dIgogICAgICAgIGRhdGEtdG8tbG9hZD0iW1tydW5zXV0iCiAgICAgICAgcmVxdWVzdC1kYXRhPSJbW19yZXF1ZXN0RGF0YV1dIgogICAgICAgIGxvZy1zY2FsZS1hY3RpdmU9IltbX2xvZ1NjYWxlQWN0aXZlXV0iCiAgICAgICAgbG9hZC1kYXRhLWNhbGxiYWNrPSJbW19jcmVhdGVQcm9jZXNzRGF0YUZ1bmN0aW9uKCldXSIKICAgICAgICByZXF1ZXN0LW1hbmFnZXI9IltbcmVxdWVzdE1hbmFnZXJdXSIKICAgICAgICBzbW9vdGhpbmctZW5hYmxlZD0iW1tzbW9vdGhpbmdFbmFibGVkXV0iCiAgICAgICAgc21vb3RoaW5nLXdlaWdodD0iW1tzbW9vdGhpbmdXZWlnaHRdXSIKICAgICAgICBzeW1ib2wtZnVuY3Rpb249IltbX2NyZWF0ZVN5bWJvbEZ1bmN0aW9uKCldXSIKICAgICAgICB0b29sdGlwLXNvcnRpbmctbWV0aG9kPSJbW3Rvb2x0aXBTb3J0aW5nTWV0aG9kXV0iCiAgICAgICAgeC10eXBlPSJbW3hUeXBlXV0iCiAgICAgID4KICAgICAgPC90Zi1saW5lLWNoYXJ0LWRhdGEtbG9hZGVyPgogICAgPC9kaXY+CiAgICA8ZGl2IGlkPSJidXR0b25zIj4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgc2VsZWN0ZWQkPSJbW19leHBhbmRlZF1dIgogICAgICAgIGljb249ImZ1bGxzY3JlZW4iCiAgICAgICAgb24tdGFwPSJfdG9nZ2xlRXhwYW5kZWQiCiAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICBzZWxlY3RlZCQ9IltbX2xvZ1NjYWxlQWN0aXZlXV0iCiAgICAgICAgaWNvbj0ibGluZS13ZWlnaHQiCiAgICAgICAgb24tdGFwPSJfdG9nZ2xlTG9nU2NhbGUiCiAgICAgICAgdGl0bGU9IlRvZ2dsZSB5LWF4aXMgbG9nIHNjYWxlIgogICAgICA+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgaWNvbj0ic2V0dGluZ3Mtb3ZlcnNjYW4iCiAgICAgICAgb24tdGFwPSJfcmVzZXREb21haW4iCiAgICAgICAgdGl0bGU9IkZpdCBkb21haW4gdG8gZGF0YSIKICAgICAgPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICAgIDxzcGFuIHN0eWxlPSJmbGV4LWdyb3c6IDEiPjwvc3Bhbj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW3Nob3dEb3dubG9hZExpbmtzXV0iPgogICAgICAgIDxkaXYgY2xhc3M9ImRvd25sb2FkLWxpbmtzIj4KICAgICAgICAgIDxwYXBlci1kcm9wZG93bi1tZW51CiAgICAgICAgICAgIG5vLWxhYmVsLWZsb2F0PSJ0cnVlIgogICAgICAgICAgICBsYWJlbD0ic2VyaWVzIHRvIGRvd25sb2FkIgogICAgICAgICAgICBzZWxlY3RlZC1pdGVtLWxhYmVsPSJ7e19kYXRhU2VyaWVzTmFtZVRvRG93bmxvYWR9fSIKICAgICAgICAgID4KICAgICAgICAgICAgPHBhcGVyLWxpc3Rib3ggY2xhc3M9ImRyb3Bkb3duLWNvbnRlbnQiIHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgICAgICAgICBpdGVtcz0iW1tfc2VyaWVzTmFtZXNdXSIKICAgICAgICAgICAgICAgIGFzPSJkYXRhU2VyaWVzTmFtZSIKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICA8cGFwZXItaXRlbSBuby1sYWJlbC1mbG9hdD0idHJ1ZSIKICAgICAgICAgICAgICAgICAgPltbZGF0YVNlcmllc05hbWVdXTwvcGFwZXItaXRlbQogICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDwvcGFwZXItbGlzdGJveD4KICAgICAgICAgIDwvcGFwZXItZHJvcGRvd24tbWVudT4KICAgICAgICAgIDxhCiAgICAgICAgICAgIGRvd25sb2FkPSJbW19kYXRhU2VyaWVzTmFtZVRvRG93bmxvYWRdXS5jc3YiCiAgICAgICAgICAgIGhyZWY9IltbX2NzdlVybChfbmFtZVRvRGF0YVNlcmllcywgX2RhdGFTZXJpZXNOYW1lVG9Eb3dubG9hZCldXSIKICAgICAgICAgICAgPkNTVjwvYQogICAgICAgICAgPgogICAgICAgICAgPGEKICAgICAgICAgICAgZG93bmxvYWQ9IltbX2RhdGFTZXJpZXNOYW1lVG9Eb3dubG9hZF1dLmpzb24iCiAgICAgICAgICAgIGhyZWY9IltbX2pzb25VcmwoX25hbWVUb0RhdGFTZXJpZXMsIF9kYXRhU2VyaWVzTmFtZVRvRG93bmxvYWQpXV0iCiAgICAgICAgICAgID5KU09OPC9hCiAgICAgICAgICA+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L2Rpdj4KICAgIDxkaXYgaWQ9Im1hdGNoZXMtY29udGFpbmVyIj4KICAgICAgPGRpdiBpZD0ibWF0Y2hlcy1saXN0LXRpdGxlIj4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX3Nlcmllc05hbWVzLmxlbmd0aF1dIj4KICAgICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbgogICAgICAgICAgICBpY29uPSJbW19nZXRUb2dnbGVNYXRjaGVzSWNvbihfbWF0Y2hlc0xpc3RPcGVuZWQpXV0iCiAgICAgICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlTWF0Y2hlc09wZW4iCiAgICAgICAgICAgIGNsYXNzPSJ0b2dnbGUtbWF0Y2hlcy1idXR0b24iCiAgICAgICAgICA+CiAgICAgICAgICA8L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgIDwvdGVtcGxhdGU+CgogICAgICAgIDxzcGFuIGNsYXNzPSJtYXRjaGVzLXRleHQiPiBNYXRjaGVzIChbW19zZXJpZXNOYW1lcy5sZW5ndGhdXSkgPC9zcGFuPgogICAgICA8L2Rpdj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19zZXJpZXNOYW1lcy5sZW5ndGhdXSI+CiAgICAgICAgPGlyb24tY29sbGFwc2Ugb3BlbmVkPSJbW19tYXRjaGVzTGlzdE9wZW5lZF1dIj4KICAgICAgICAgIDxkaXYgaWQ9Im1hdGNoZXMtbGlzdCI+CiAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgIGlzPSJkb20tcmVwZWF0IgogICAgICAgICAgICAgIGl0ZW1zPSJbW19zZXJpZXNOYW1lc11dIgogICAgICAgICAgICAgIGFzPSJzZXJpZXNOYW1lIgogICAgICAgICAgICAgIGlkPSJtYXRjaC1saXN0LXJlcGVhdCIKICAgICAgICAgICAgICBvbi1kb20tY2hhbmdlPSJfbWF0Y2hMaXN0RW50cnlDb2xvclVwZGF0ZWQiCiAgICAgICAgICAgID4KICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJtYXRjaC1saXN0LWVudHJ5Ij4KICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJtYXRjaC1lbnRyeS1zeW1ib2wiPgogICAgICAgICAgICAgICAgICBbW19kZXRlcm1pbmVTeW1ib2woX25hbWVUb0RhdGFTZXJpZXMsIHNlcmllc05hbWUpXV0KICAgICAgICAgICAgICAgIDwvc3Bhbj4KICAgICAgICAgICAgICAgIFtbc2VyaWVzTmFtZV1dCiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L2lyb24tY29sbGFwc2U+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L2Rpdj4KCiAgICA8c3R5bGUgaW5jbHVkZT0idGYtY3VzdG9tLXNjYWxhci1jYXJkLXN0eWxlIj48L3N0eWxlPgogICAgPHN0eWxlPgogICAgICAjbWF0Y2hlcy1saXN0LXRpdGxlIHsKICAgICAgICBtYXJnaW46IDEwcHggMCA1cHggMDsKICAgICAgfQoKICAgICAgI21hdGNoZXMtbGlzdCB7CiAgICAgICAgbWF4LWhlaWdodDogMjAwcHg7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgfQoKICAgICAgLm1hdGNoLWxpc3QtZW50cnkgewogICAgICAgIG1hcmdpbjogMCAwIDVweCAwOwogICAgICB9CgogICAgICAubWF0Y2gtZW50cnktc3ltYm9sIHsKICAgICAgICBmb250LWZhbWlseTogYXJpYWwsIHNhbnMtc2VyaWY7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIHdpZHRoOiAxMHB4OwogICAgICB9CgogICAgICAubWF0Y2hlcy10ZXh0IHsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAicnVucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ4VHlwZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgImFjdGl2ZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ0aXRsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAidGFnUmVnZXhlcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgImlnbm9yZVlPdXRsaWVycyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFJlcXVlc3RNYW5hZ2VyKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgInJlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAic2hvd0Rvd25sb2FkTGlua3MiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJzbW9vdGhpbmdFbmFibGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgInNtb290aGluZ1dlaWdodCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ0YWdNZXRhZGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJ0b29sdGlwU29ydGluZ01ldGhvZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIERhdGFTZXJpZXNDb2xvclNjYWxlKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9jb2xvclNjYWxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9uYW1lVG9EYXRhU2VyaWVzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfZXhwYW5kZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfbG9nU2NhbGVBY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbikKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfcmVxdWVzdERhdGEiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAiX3J1blRvTmV4dEF2YWlsYWJsZVN5bWJvbEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAiX21hdGNoZXNMaXN0T3BlbmVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ19uYW1lVG9EYXRhU2VyaWVzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQucHJvdG90eXBlLCAiX3VwZGF0ZUNoYXJ0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX25hbWVUb0RhdGFTZXJpZXMnLCAncnVucycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9zZXJpZXNOYW1lcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX3RhZ0ZpbHRlcicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgX1RmQ3VzdG9tU2NhbGFyTXVsdGlMaW5lQ2hhcnRDYXJkLnByb3RvdHlwZSwgIl9yZWZyZXNoRGF0YVNlcmllcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ3RhZ1JlZ2V4ZXMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfdGFnRmlsdGVyIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgndGl0bGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkN1c3RvbVNjYWxhck11bHRpTGluZUNoYXJ0Q2FyZC5wcm90b3R5cGUsICJfdGl0bGVEaXNwbGF5U3RyaW5nIiwgbnVsbCk7CiAgICBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1jdXN0b20tc2NhbGFyLW11bHRpLWxpbmUtY2hhcnQtY2FyZCcpCiAgICBdLCBfVGZDdXN0b21TY2FsYXJNdWx0aUxpbmVDaGFydENhcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkID0gY2xhc3MgVGZDdXN0b21TY2FsYXJEYXNoYm9hcmQgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RNYW5hZ2VyID0gbmV3IFJlcXVlc3RNYW5hZ2VyKDUwKTsKICAgICAgICAgICAgdGhpcy5fY2FuY2VsbGVyID0gbmV3IENhbmNlbGxlcigpOwogICAgICAgICAgICB0aGlzLl9zaG93RG93bmxvYWRMaW5rcyA9IGdldEJvb2xlYW5Jbml0aWFsaXplcignX3Nob3dEb3dubG9hZExpbmtzJywgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiBmYWxzZSwKICAgICAgICAgICAgICAgIHVzZUxvY2FsU3RvcmFnZTogdHJ1ZSwKICAgICAgICAgICAgfSkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5fc21vb3RoaW5nV2VpZ2h0ID0gZ2V0TnVtYmVySW5pdGlhbGl6ZXIoJ19zbW9vdGhpbmdXZWlnaHQnLCB7CiAgICAgICAgICAgICAgICBkZWZhdWx0VmFsdWU6IDAuNiwKICAgICAgICAgICAgfSkuY2FsbCh0aGlzKTsKICAgICAgICAgICAgdGhpcy5faWdub3JlWU91dGxpZXJzID0gZ2V0Qm9vbGVhbkluaXRpYWxpemVyKCdfaWdub3JlWU91dGxpZXJzJywgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiB0cnVlLAogICAgICAgICAgICAgICAgdXNlTG9jYWxTdG9yYWdlOiB0cnVlLAogICAgICAgICAgICB9KS5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl94VHlwZSA9ICdzdGVwJzsKICAgICAgICAgICAgdGhpcy5fYWN0aXZlID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5yZWxvYWRPblJlYWR5ID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fc2hvd0Rvd25sb2FkTGlua3NPYnNlcnZlciA9IGdldEJvb2xlYW5PYnNlcnZlcignX3Nob3dEb3dubG9hZExpbmtzJywgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiBmYWxzZSwKICAgICAgICAgICAgICAgIHVzZUxvY2FsU3RvcmFnZTogdHJ1ZSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX3Ntb290aGluZ1dlaWdodE9ic2VydmVyID0gZ2V0TnVtYmVyT2JzZXJ2ZXIoJ19zbW9vdGhpbmdXZWlnaHQnLCB7CiAgICAgICAgICAgICAgICBkZWZhdWx0VmFsdWU6IDAuNiwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuX2lnbm9yZVlPdXRsaWVyc09ic2VydmVyID0gZ2V0Qm9vbGVhbk9ic2VydmVyKCdfaWdub3JlWU91dGxpZXJzJywgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiB0cnVlLAogICAgICAgICAgICAgICAgdXNlTG9jYWxTdG9yYWdlOiB0cnVlLAogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgcmVhZHkoKSB7CiAgICAgICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgICAgIGlmICh0aGlzLnJlbG9hZE9uUmVhZHkpCiAgICAgICAgICAgICAgICB0aGlzLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICByZWxvYWQoKSB7CiAgICAgICAgICAgIGNvbnN0IHVybCA9IGdldFJvdXRlcigpLnBsdWdpbnNMaXN0aW5nKCk7CiAgICAgICAgICAgIGNvbnN0IGhhbmRsZVBsdWdpbnNMaXN0aW5nUmVzcG9uc2UgPSB0aGlzLl9jYW5jZWxsZXIuY2FuY2VsbGFibGUoKHJlc3VsdCkgPT4gewogICAgICAgICAgICAgICAgaWYgKHJlc3VsdC5jYW5jZWxsZWQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX2RhdGFOb3RGb3VuZCcsICFyZXN1bHQudmFsdWVbJ2N1c3RvbV9zY2FsYXJzJ10pOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2RhdGFOb3RGb3VuZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX3JldHJpZXZlTGF5b3V0QW5kRGF0YSgpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwpLnRoZW4oaGFuZGxlUGx1Z2luc0xpc3RpbmdSZXNwb25zZSk7CiAgICAgICAgfQogICAgICAgIF9yZWxvYWRDaGFydHMoKSB7CiAgICAgICAgICAgIGNvbnN0IGNoYXJ0cyA9IHRoaXMucm9vdC5xdWVyeVNlbGVjdG9yQWxsKCd0Zi1jdXN0b20tc2NhbGFyLW1hcmdpbi1jaGFydC1jYXJkLCAnICsKICAgICAgICAgICAgICAgICd0Zi1jdXN0b20tc2NhbGFyLW11bHRpLWxpbmUtY2hhcnQtY2FyZCcpOwogICAgICAgICAgICBjaGFydHMuZm9yRWFjaCgoY2hhcnQpID0+IHsKICAgICAgICAgICAgICAgIGNoYXJ0LnJlbG9hZCgpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX3JldHJpZXZlTGF5b3V0QW5kRGF0YSgpIHsKICAgICAgICAgICAgY29uc3QgdXJsID0gZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2N1c3RvbV9zY2FsYXJzJywgJy9sYXlvdXQnKTsKICAgICAgICAgICAgY29uc3QgdXBkYXRlID0gdGhpcy5fY2FuY2VsbGVyLmNhbmNlbGxhYmxlKChyZXN1bHQpID0+IHsKICAgICAgICAgICAgICAgIGlmIChyZXN1bHQuY2FuY2VsbGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gVGhpcyBwbHVnaW4gaXMgb25seSBhY3RpdmUgaWYgZGF0YSBpcyBhdmFpbGFibGUuCiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX2xheW91dCcsIHJlc3VsdC52YWx1ZSk7CiAgICAgICAgICAgICAgICBpZiAoIXRoaXMuX2RhdGFOb3RGb3VuZCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX3JlbG9hZENoYXJ0cygpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwpLnRoZW4odXBkYXRlKTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9zbW9vdGhpbmdFbmFibGVkKCkgewogICAgICAgICAgICB2YXIgX3Ntb290aGluZ1dlaWdodCA9IHRoaXMuX3Ntb290aGluZ1dlaWdodDsKICAgICAgICAgICAgcmV0dXJuIF9zbW9vdGhpbmdXZWlnaHQgPiAwOwogICAgICAgIH0KICAgICAgICBnZXQgX2NhdGVnb3JpZXMoKSB7CiAgICAgICAgICAgIHZhciBsYXlvdXQgPSB0aGlzLl9sYXlvdXQ7CiAgICAgICAgICAgIGlmICghbGF5b3V0LmNhdGVnb3J5KSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IGZpcnN0VGltZUxvYWQgPSBmYWxzZTsKICAgICAgICAgICAgaWYgKCF0aGlzLl9vcGVuZWRDYXRlZ29yaWVzKSB7CiAgICAgICAgICAgICAgICAvLyBUaGlzIGlzIHRoZSBmaXJzdCB0aW1lIHRoZSB1c2VyIGxvYWRzIHRoZSBjYXRlZ29yaWVzLiBTdGFydCBzdG9yaW5nCiAgICAgICAgICAgICAgICAvLyB3aGljaCBjYXRlZ29yaWVzIGFyZSBvcGVuLgogICAgICAgICAgICAgICAgZmlyc3RUaW1lTG9hZCA9IHRydWU7CiAgICAgICAgICAgICAgICB0aGlzLl9vcGVuZWRDYXRlZ29yaWVzID0ge307CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgY2F0ZWdvcmllcyA9IGxheW91dC5jYXRlZ29yeS5tYXAoKGNhdGVnb3J5KSA9PiB7CiAgICAgICAgICAgICAgICBpZiAoZmlyc3RUaW1lTG9hZCAmJiAhY2F0ZWdvcnkgLyogPz8/ICovLmNsb3NlZCkgewogICAgICAgICAgICAgICAgICAgIC8vIFJlbWVtYmVyIHdoZXRoZXIgdGhpcyBjYXRlZ29yeSBpcyBjdXJyZW50bHkgb3Blbi4KICAgICAgICAgICAgICAgICAgICB0aGlzLl9vcGVuZWRDYXRlZ29yaWVzW2NhdGVnb3J5LnRpdGxlXSA9IHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgIG5hbWU6IGNhdGVnb3J5LnRpdGxlLAogICAgICAgICAgICAgICAgICAgIGl0ZW1zOiBjYXRlZ29yeS5jaGFydCwKICAgICAgICAgICAgICAgICAgICBtZXRhZGF0YTogewogICAgICAgICAgICAgICAgICAgICAgICB0eXBlOiBDYXRlZ29yeVR5cGUuUFJFRklYX0dST1VQLAogICAgICAgICAgICAgICAgICAgICAgICBvcGVuZWQ6ICEhdGhpcy5fb3BlbmVkQ2F0ZWdvcmllc1tjYXRlZ29yeS50aXRsZV0sCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gY2F0ZWdvcmllczsKICAgICAgICB9CiAgICAgICAgX2NhdGVnb3J5T3BlbmVkVG9nZ2xlZChldmVudCkgewogICAgICAgICAgICBjb25zdCBwYW5lID0gZXZlbnQudGFyZ2V0OwogICAgICAgICAgICBpZiAocGFuZS5vcGVuZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX29wZW5lZENhdGVnb3JpZXNbcGFuZS5jYXRlZ29yeS5uYW1lXSA9IHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBkZWxldGUgdGhpcy5fb3BlbmVkQ2F0ZWdvcmllc1twYW5lLmNhdGVnb3J5Lm5hbWVdOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfTsKICAgIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8dGYtZGFzaGJvYXJkLWxheW91dD4KICAgICAgPGRpdiBjbGFzcz0ic2lkZWJhciIgc2xvdD0ic2lkZWJhciI+CiAgICAgICAgPGRpdiBjbGFzcz0ic2V0dGluZ3MiPgogICAgICAgICAgPGRpdiBjbGFzcz0ic2lkZWJhci1zZWN0aW9uIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0ibGluZS1pdGVtIj4KICAgICAgICAgICAgICA8cGFwZXItY2hlY2tib3ggY2hlY2tlZD0ie3tfc2hvd0Rvd25sb2FkTGlua3N9fSIKICAgICAgICAgICAgICAgID5TaG93IGRhdGEgZG93bmxvYWQgbGlua3M8L3BhcGVyLWNoZWNrYm94CiAgICAgICAgICAgICAgPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0ibGluZS1pdGVtIj4KICAgICAgICAgICAgICA8cGFwZXItY2hlY2tib3ggY2hlY2tlZD0ie3tfaWdub3JlWU91dGxpZXJzfX0iCiAgICAgICAgICAgICAgICA+SWdub3JlIG91dGxpZXJzIGluIGNoYXJ0IHNjYWxpbmc8L3BhcGVyLWNoZWNrYm94CiAgICAgICAgICAgICAgPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPGRpdiBpZD0idG9vbHRpcC1zb3J0aW5nIj4KICAgICAgICAgICAgICA8ZGl2IGlkPSJ0b29sdGlwLXNvcnRpbmctbGFiZWwiPlRvb2x0aXAgc29ydGluZyBtZXRob2Q6PC9kaXY+CiAgICAgICAgICAgICAgPHBhcGVyLWRyb3Bkb3duLW1lbnUKICAgICAgICAgICAgICAgIG5vLWxhYmVsLWZsb2F0PSIiCiAgICAgICAgICAgICAgICBzZWxlY3RlZC1pdGVtLWxhYmVsPSJ7e190b29sdGlwU29ydGluZ01ldGhvZH19IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxwYXBlci1saXN0Ym94CiAgICAgICAgICAgICAgICAgIGNsYXNzPSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgICAgICAgICBzZWxlY3RlZD0iMCIKICAgICAgICAgICAgICAgICAgc2xvdD0iZHJvcGRvd24tY29udGVudCIKICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgPHBhcGVyLWl0ZW0+ZGVmYXVsdDwvcGFwZXItaXRlbT4KICAgICAgICAgICAgICAgICAgPHBhcGVyLWl0ZW0+ZGVzY2VuZGluZzwvcGFwZXItaXRlbT4KICAgICAgICAgICAgICAgICAgPHBhcGVyLWl0ZW0+YXNjZW5kaW5nPC9wYXBlci1pdGVtPgogICAgICAgICAgICAgICAgICA8cGFwZXItaXRlbT5uZWFyZXN0PC9wYXBlci1pdGVtPgogICAgICAgICAgICAgICAgPC9wYXBlci1saXN0Ym94PgogICAgICAgICAgICAgIDwvcGFwZXItZHJvcGRvd24tbWVudT4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9InNpZGViYXItc2VjdGlvbiI+CiAgICAgICAgICAgIDx0Zi1zbW9vdGhpbmctaW5wdXQKICAgICAgICAgICAgICB3ZWlnaHQ9Int7X3Ntb290aGluZ1dlaWdodH19IgogICAgICAgICAgICAgIHN0ZXA9IjAuMDAxIgogICAgICAgICAgICAgIG1pbj0iMCIKICAgICAgICAgICAgICBtYXg9IjEiCiAgICAgICAgICAgID48L3RmLXNtb290aGluZy1pbnB1dD4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPGRpdiBjbGFzcz0ic2lkZWJhci1zZWN0aW9uIj4KICAgICAgICAgICAgPHRmLW9wdGlvbi1zZWxlY3RvcgogICAgICAgICAgICAgIGlkPSJ4LXR5cGUtc2VsZWN0b3IiCiAgICAgICAgICAgICAgbmFtZT0iSG9yaXpvbnRhbCBBeGlzIgogICAgICAgICAgICAgIHNlbGVjdGVkLWlkPSJ7e194VHlwZX19IgogICAgICAgICAgICA+CiAgICAgICAgICAgICAgPHBhcGVyLWJ1dHRvbiBpZD0ic3RlcCI+c3RlcDwvcGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgPjwhLS0KICAgICAgICAgICAgLS0+PHBhcGVyLWJ1dHRvbiBpZD0icmVsYXRpdmUiPnJlbGF0aXZlPC9wYXBlci1idXR0b24KICAgICAgICAgICAgICA+PCEtLQogICAgICAgICAgICAtLT48cGFwZXItYnV0dG9uIGlkPSJ3YWxsX3RpbWUiPndhbGw8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgPC90Zi1vcHRpb24tc2VsZWN0b3I+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L2Rpdj4KICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24gcnVucy1zZWxlY3RvciI+CiAgICAgICAgICA8dGYtcnVucy1zZWxlY3RvciBzZWxlY3RlZC1ydW5zPSJ7e19zZWxlY3RlZFJ1bnN9fSI+CiAgICAgICAgICA8L3RmLXJ1bnMtc2VsZWN0b3I+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJjZW50ZXIiIHNsb3Q9ImNlbnRlciIgaWQ9ImNhdGVnb3JpZXMtY29udGFpbmVyIj4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2RhdGFOb3RGb3VuZF1dIj4KICAgICAgICAgIDxkaXYgY2xhc3M9Im5vLWRhdGEtd2FybmluZyI+CiAgICAgICAgICAgIDxoMz5UaGUgY3VzdG9tIHNjYWxhcnMgZGFzaGJvYXJkIGlzIGluYWN0aXZlLjwvaDM+CiAgICAgICAgICAgIDxwPlByb2JhYmxlIGNhdXNlczo8L3A+CiAgICAgICAgICAgIDxvbD4KICAgICAgICAgICAgICA8bGk+WW91IGhhdmVuJ3QgbGFpZCBvdXQgdGhlIGRhc2hib2FyZC48L2xpPgogICAgICAgICAgICAgIDxsaT5Zb3UgaGF2ZW7igJl0IHdyaXR0ZW4gYW55IHNjYWxhciBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgPC9vbD4KCiAgICAgICAgICAgIDxwPgogICAgICAgICAgICAgIFRvIGxheSBvdXQgdGhlIGRhc2hib2FyZCwgcGFzcyBhIDxjb2RlPkxheW91dDwvY29kZT4gcHJvdG9idWZmZXIKICAgICAgICAgICAgICB0byB0aGUgPGNvZGU+c2V0X2xheW91dDwvY29kZT4gbWV0aG9kLiBGb3IgZXhhbXBsZSwKICAgICAgICAgICAgPC9wPgogICAgICAgICAgICA8cHJlPgpmcm9tIHRlbnNvcmJvYXJkIGltcG9ydCBzdW1tYXJ5CmZyb20gdGVuc29yYm9hcmQucGx1Z2lucy5jdXN0b21fc2NhbGFyIGltcG9ydCBsYXlvdXRfcGIyCi4uLgojIFRoaXMgYWN0aW9uIGRvZXMgbm90IGhhdmUgdG8gYmUgcGVyZm9ybWVkIGF0IGV2ZXJ5IHN0ZXAsIHNvIHRoZSBhY3Rpb24gaXMgbm90CiMgdGFrZW4gY2FyZSBvZiBieSBhbiBvcCBpbiB0aGUgZ3JhcGguIFdlIG9ubHkgbmVlZCB0byBzcGVjaWZ5IHRoZSBsYXlvdXQgb25jZQojIChpbnN0ZWFkIG9mIHBlciBzdGVwKS4KbGF5b3V0X3N1bW1hcnkgPSBzdW1tYXJ5X2xpYi5jdXN0b21fc2NhbGFyX3BiKGxheW91dF9wYjIuTGF5b3V0KAogIGNhdGVnb3J5PVsKICAgIGxheW91dF9wYjIuQ2F0ZWdvcnkoCiAgICAgIHRpdGxlPSdsb3NzZXMnLAogICAgICBjaGFydD1bCiAgICAgICAgICBsYXlvdXRfcGIyLkNoYXJ0KAogICAgICAgICAgICAgIHRpdGxlPSdsb3NzZXMnLAogICAgICAgICAgICAgIG11bHRpbGluZT1sYXlvdXRfcGIyLk11bHRpbGluZUNoYXJ0Q29udGVudCgKICAgICAgICAgICAgICAgIHRhZz1bcidsb3NzLionXSwKICAgICAgICAgICAgICApKSwKICAgICAgICAgIGxheW91dF9wYjIuQ2hhcnQoCiAgICAgICAgICAgICAgdGl0bGU9J2JheicsCiAgICAgICAgICAgICAgbWFyZ2luPWxheW91dF9wYjIuTWFyZ2luQ2hhcnRDb250ZW50KAogICAgICAgICAgICAgICAgc2VyaWVzPVsKICAgICAgICAgICAgICAgICAgbGF5b3V0X3BiMi5NYXJnaW5DaGFydENvbnRlbnQuU2VyaWVzKAogICAgICAgICAgICAgICAgICAgIHZhbHVlPSdsb3NzL2Jhei9zY2FsYXJfc3VtbWFyeScsCiAgICAgICAgICAgICAgICAgICAgbG93ZXI9J2Jhel9sb3dlci9iYXovc2NhbGFyX3N1bW1hcnknLAogICAgICAgICAgICAgICAgICAgIHVwcGVyPSdiYXpfdXBwZXIvYmF6L3NjYWxhcl9zdW1tYXJ5JyksCiAgICAgICAgICAgICAgICBdLAogICAgICAgICAgICAgICkpLAogICAgICBdKSwKICAgIGxheW91dF9wYjIuQ2F0ZWdvcnkoCiAgICAgIHRpdGxlPSd0cmlnIGZ1bmN0aW9ucycsCiAgICAgIGNoYXJ0PVsKICAgICAgICAgIGxheW91dF9wYjIuQ2hhcnQoCiAgICAgICAgICAgICAgdGl0bGU9J3dhdmUgdHJpZyBmdW5jdGlvbnMnLAogICAgICAgICAgICAgIG11bHRpbGluZT1sYXlvdXRfcGIyLk11bHRpbGluZUNoYXJ0Q29udGVudCgKICAgICAgICAgICAgICAgIHRhZz1bcid0cmlnRnVuY3Rpb25zL2Nvc2luZScsIHIndHJpZ0Z1bmN0aW9ucy9zaW5lJ10sCiAgICAgICAgICAgICAgKSksCiAgICAgICAgICAjIFRoZSByYW5nZSBvZiB0YW5nZW50IGlzIGRpZmZlcmVudC4gTGV0J3MgZ2l2ZSBpdCBpdHMgb3duIGNoYXJ0LgogICAgICAgICAgbGF5b3V0X3BiMi5DaGFydCgKICAgICAgICAgICAgICB0aXRsZT0ndGFuJywKICAgICAgICAgICAgICBtdWx0aWxpbmU9bGF5b3V0X3BiMi5NdWx0aWxpbmVDaGFydENvbnRlbnQoCiAgICAgICAgICAgICAgICB0YWc9W3IndHJpZ0Z1bmN0aW9ucy90YW5nZW50J10sCiAgICAgICAgICAgICAgKSksCiAgICAgIF0sCiAgICAgICMgVGhpcyBjYXRlZ29yeSB3ZSBjYXJlIGxlc3MgYWJvdXQuIExldCdzIG1ha2UgaXQgaW5pdGlhbGx5IGNsb3NlZC4KICAgICAgY2xvc2VkPVRydWUpLAogIF0pKQp3cml0ZXIuYWRkX3N1bW1hcnkobGF5b3V0X3N1bW1hcnkpCjwvcHJlCiAgICAgICAgICAgID4KICAgICAgICAgICAgPHA+CiAgICAgICAgICAgICAgSWYgeW914oCZcmUgbmV3IHRvIHVzaW5nIFRlbnNvckJvYXJkLCBhbmQgd2FudCB0byBmaW5kIG91dCBob3cgdG8KICAgICAgICAgICAgICBhZGQgZGF0YSBhbmQgc2V0IHVwIHlvdXIgZXZlbnQgZmlsZXMsIGNoZWNrIG91dCB0aGUKICAgICAgICAgICAgICA8YQogICAgICAgICAgICAgICAgaHJlZj0iaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvYmxvYi9tYXN0ZXIvUkVBRE1FLm1kIgogICAgICAgICAgICAgICAgPlJFQURNRTwvYQogICAgICAgICAgICAgID4KICAgICAgICAgICAgICBhbmQgcGVyaGFwcyB0aGUKICAgICAgICAgICAgICA8YQogICAgICAgICAgICAgICAgaHJlZj0iaHR0cHM6Ly93d3cudGVuc29yZmxvdy5vcmcvZ2V0X3N0YXJ0ZWQvc3VtbWFyaWVzX2FuZF90ZW5zb3Jib2FyZCIKICAgICAgICAgICAgICAgID5UZW5zb3JCb2FyZCB0dXRvcmlhbDwvYQogICAgICAgICAgICAgID4uCiAgICAgICAgICAgIDwvcD4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbWyFfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfY2F0ZWdvcmllc11dIiBhcz0iY2F0ZWdvcnkiPgogICAgICAgICAgICA8dGYtY2F0ZWdvcnktcGFnaW5hdGVkLXZpZXcKICAgICAgICAgICAgICBhcz0iY2hhcnQiCiAgICAgICAgICAgICAgY2F0ZWdvcnk9IltbY2F0ZWdvcnldXSIKICAgICAgICAgICAgICBkaXNhYmxlLXBhZ2luYXRpb24KICAgICAgICAgICAgICBpbml0aWFsLW9wZW5lZD0iW1tjYXRlZ29yeS5tZXRhZGF0YS5vcGVuZWRdXSIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tjaGFydC5tdWx0aWxpbmVdXSI+CiAgICAgICAgICAgICAgICAgIDx0Zi1jdXN0b20tc2NhbGFyLW11bHRpLWxpbmUtY2hhcnQtY2FyZAogICAgICAgICAgICAgICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICAgICAgICAgICAgICByZXF1ZXN0LW1hbmFnZXI9IltbX3JlcXVlc3RNYW5hZ2VyXV0iCiAgICAgICAgICAgICAgICAgICAgcnVucz0iW1tfc2VsZWN0ZWRSdW5zXV0iCiAgICAgICAgICAgICAgICAgICAgdGl0bGU9IltbY2hhcnQudGl0bGVdXSIKICAgICAgICAgICAgICAgICAgICB4LXR5cGU9IltbX3hUeXBlXV0iCiAgICAgICAgICAgICAgICAgICAgc21vb3RoaW5nLWVuYWJsZWQ9IltbX3Ntb290aGluZ0VuYWJsZWRdXSIKICAgICAgICAgICAgICAgICAgICBzbW9vdGhpbmctd2VpZ2h0PSJbW19zbW9vdGhpbmdXZWlnaHRdXSIKICAgICAgICAgICAgICAgICAgICB0b29sdGlwLXNvcnRpbmctbWV0aG9kPSJbW3Rvb2x0aXBTb3J0aW5nTWV0aG9kXV0iCiAgICAgICAgICAgICAgICAgICAgaWdub3JlLXktb3V0bGllcnM9IltbX2lnbm9yZVlPdXRsaWVyc11dIgogICAgICAgICAgICAgICAgICAgIHNob3ctZG93bmxvYWQtbGlua3M9IltbX3Nob3dEb3dubG9hZExpbmtzXV0iCiAgICAgICAgICAgICAgICAgICAgdGFnLXJlZ2V4ZXM9IltbY2hhcnQubXVsdGlsaW5lLnRhZ11dIgogICAgICAgICAgICAgICAgICA+PC90Zi1jdXN0b20tc2NhbGFyLW11bHRpLWxpbmUtY2hhcnQtY2FyZD4KICAgICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbY2hhcnQubWFyZ2luXV0iPgogICAgICAgICAgICAgICAgICA8dGYtY3VzdG9tLXNjYWxhci1tYXJnaW4tY2hhcnQtY2FyZAogICAgICAgICAgICAgICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICAgICAgICAgICAgICByZXF1ZXN0LW1hbmFnZXI9IltbX3JlcXVlc3RNYW5hZ2VyXV0iCiAgICAgICAgICAgICAgICAgICAgcnVucz0iW1tfc2VsZWN0ZWRSdW5zXV0iCiAgICAgICAgICAgICAgICAgICAgdGl0bGU9IltbY2hhcnQudGl0bGVdXSIKICAgICAgICAgICAgICAgICAgICB4LXR5cGU9IltbX3hUeXBlXV0iCiAgICAgICAgICAgICAgICAgICAgdG9vbHRpcC1zb3J0aW5nLW1ldGhvZD0iW1t0b29sdGlwU29ydGluZ01ldGhvZF1dIgogICAgICAgICAgICAgICAgICAgIGlnbm9yZS15LW91dGxpZXJzPSJbW19pZ25vcmVZT3V0bGllcnNdXSIKICAgICAgICAgICAgICAgICAgICBzaG93LWRvd25sb2FkLWxpbmtzPSJbW19zaG93RG93bmxvYWRMaW5rc11dIgogICAgICAgICAgICAgICAgICAgIG1hcmdpbi1jaGFydC1zZXJpZXM9IltbY2hhcnQubWFyZ2luLnNlcmllc11dIgogICAgICAgICAgICAgICAgICA+PC90Zi1jdXN0b20tc2NhbGFyLW1hcmdpbi1jaGFydC1jYXJkPgogICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8L3RmLWNhdGVnb3J5LXBhZ2luYXRlZC12aWV3PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICA8L2Rpdj4KICAgIDwvdGYtZGFzaGJvYXJkLWxheW91dD4KCiAgICA8c3R5bGUgaW5jbHVkZT0iZGFzaGJvYXJkLXN0eWxlIj48L3N0eWxlPgogICAgPHN0eWxlPgogICAgICAjdG9vbHRpcC1zb3J0aW5nIHsKICAgICAgICBhbGlnbi1pdGVtczogY2VudGVyOwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZm9udC1zaXplOiAxNHB4OwogICAgICAgIG1hcmdpbi10b3A6IDE1cHg7CiAgICAgIH0KICAgICAgI3Rvb2x0aXAtc29ydGluZyBwYXBlci1kcm9wZG93bi1tZW51IHsKICAgICAgICBtYXJnaW4tbGVmdDogMTBweDsKICAgICAgICAtLXBhcGVyLWlucHV0LWNvbnRhaW5lci1mb2N1cy1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgICAgd2lkdGg6IDEwNXB4OwogICAgICB9CiAgICAgIC5saW5lLWl0ZW0gewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHBhZGRpbmctdG9wOiA1cHg7CiAgICAgIH0KICAgICAgLm5vLWRhdGEtd2FybmluZyB7CiAgICAgICAgbWF4LXdpZHRoOiA1NDBweDsKICAgICAgICBtYXJnaW46IDgwcHggYXV0byAwIGF1dG87CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVxdWVzdE1hbmFnZXIpCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfcmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBDYW5jZWxsZXIpCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfY2FuY2VsbGVyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9zZWxlY3RlZFJ1bnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX3Nob3dEb3dubG9hZExpbmtzT2JzZXJ2ZXInLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9zaG93RG93bmxvYWRMaW5rcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ19zbW9vdGhpbmdXZWlnaHRPYnNlcnZlcicsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfc21vb3RoaW5nV2VpZ2h0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfaWdub3JlWU91dGxpZXJzT2JzZXJ2ZXInLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9pZ25vcmVZT3V0bGllcnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfeFR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfbGF5b3V0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfZGF0YU5vdEZvdW5kIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZDdXN0b21TY2FsYXJEYXNoYm9hcmQucHJvdG90eXBlLCAiX29wZW5lZENhdGVnb3JpZXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9hY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkLnByb3RvdHlwZSwgInJlbG9hZE9uUmVhZHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19zbW9vdGhpbmdXZWlnaHQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkN1c3RvbVNjYWxhckRhc2hib2FyZC5wcm90b3R5cGUsICJfc21vb3RoaW5nRW5hYmxlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19sYXlvdXQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZDdXN0b21TY2FsYXJEYXNoYm9hcmQucHJvdG90eXBlLCAiX2NhdGVnb3JpZXMiLCBudWxsKTsKICAgIFRmQ3VzdG9tU2NhbGFyRGFzaGJvYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtY3VzdG9tLXNjYWxhci1kYXNoYm9hcmQnKQogICAgXSwgVGZDdXN0b21TY2FsYXJEYXNoYm9hcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDE2IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY2xhc3MgRGlzdHJpYnV0aW9uQ2hhcnQgewogICAgICAgIGNvbnN0cnVjdG9yKHhUeXBlLCBjb2xvclNjYWxlKSB7CiAgICAgICAgICAgIHRoaXMucnVuMmRhdGFzZXRzID0ge307CiAgICAgICAgICAgIHRoaXMuY29sb3JTY2FsZSA9IGNvbG9yU2NhbGU7CiAgICAgICAgICAgIHRoaXMuYnVpbGRDaGFydCh4VHlwZSk7CiAgICAgICAgfQogICAgICAgIGdldERhdGFzZXQocnVuKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnJ1bjJkYXRhc2V0c1tydW5dID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMucnVuMmRhdGFzZXRzW3J1bl0gPSBuZXcgc3JjJDIuRGF0YXNldChbXSwgeyBydW46IHJ1biB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdGhpcy5ydW4yZGF0YXNldHNbcnVuXTsKICAgICAgICB9CiAgICAgICAgYnVpbGRDaGFydCh4VHlwZSkgewogICAgICAgICAgICBpZiAodGhpcy5vdXRlcikgewogICAgICAgICAgICAgICAgdGhpcy5vdXRlci5kZXN0cm95KCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IHhDb21wb25lbnRzID0gZ2V0WENvbXBvbmVudHMoeFR5cGUpOwogICAgICAgICAgICB0aGlzLnhBY2Nlc3NvciA9IHhDb21wb25lbnRzLmFjY2Vzc29yOwogICAgICAgICAgICB0aGlzLnhTY2FsZSA9IHhDb21wb25lbnRzLnNjYWxlOwogICAgICAgICAgICB0aGlzLnhBeGlzID0geENvbXBvbmVudHMuYXhpczsKICAgICAgICAgICAgdGhpcy54QXhpcy5tYXJnaW4oMCk7CiAgICAgICAgICAgIHRoaXMueEF4aXMudGlja0xhYmVsUGFkZGluZygzKTsKICAgICAgICAgICAgdGhpcy55U2NhbGUgPSBuZXcgc3JjJDIuU2NhbGVzLkxpbmVhcigpOwogICAgICAgICAgICB0aGlzLnlBeGlzID0gbmV3IHNyYyQyLkF4ZXMuTnVtZXJpYyh0aGlzLnlTY2FsZSwgJ2xlZnQnKTsKICAgICAgICAgICAgbGV0IHlGb3JtYXR0ZXIgPSBtdWx0aXNjYWxlRm9ybWF0dGVyKFlfQVhJU19GT1JNQVRURVJfUFJFQ0lTSU9OKTsKICAgICAgICAgICAgdGhpcy55QXhpcy5tYXJnaW4oMCkudGlja0xhYmVsUGFkZGluZyg1KS5mb3JtYXR0ZXIoeUZvcm1hdHRlcik7CiAgICAgICAgICAgIHRoaXMueUF4aXMudXNlc1RleHRXaWR0aEFwcHJveGltYXRpb24odHJ1ZSk7CiAgICAgICAgICAgIGxldCBjZW50ZXIgPSB0aGlzLmJ1aWxkUGxvdCh0aGlzLnhBY2Nlc3NvciwgdGhpcy54U2NhbGUsIHRoaXMueVNjYWxlKTsKICAgICAgICAgICAgdGhpcy5ncmlkbGluZXMgPSBuZXcgc3JjJDIuQ29tcG9uZW50cy5HcmlkbGluZXModGhpcy54U2NhbGUsIHRoaXMueVNjYWxlKTsKICAgICAgICAgICAgdGhpcy5jZW50ZXIgPSBuZXcgc3JjJDIuQ29tcG9uZW50cy5Hcm91cChbdGhpcy5ncmlkbGluZXMsIGNlbnRlcl0pOwogICAgICAgICAgICB0aGlzLm91dGVyID0gbmV3IHNyYyQyLkNvbXBvbmVudHMuVGFibGUoWwogICAgICAgICAgICAgICAgW3RoaXMueUF4aXMsIHRoaXMuY2VudGVyXSwKICAgICAgICAgICAgICAgIFtudWxsLCB0aGlzLnhBeGlzXSwKICAgICAgICAgICAgXSk7CiAgICAgICAgfQogICAgICAgIGJ1aWxkUGxvdCh4QWNjZXNzb3IsIHhTY2FsZSwgeVNjYWxlKSB7CiAgICAgICAgICAgIGxldCBwZXJjZW50cyA9IFswLCAyMjgsIDE1ODcsIDMwODUsIDUwMDAsIDY5MTUsIDg0MTMsIDk3NzIsIDEwMDAwXTsKICAgICAgICAgICAgbGV0IG9wYWNpdGllcyA9IGxvZGFzaC5yYW5nZShwZXJjZW50cy5sZW5ndGggLSAxKS5tYXAoKGkpID0+IChwZXJjZW50c1tpICsgMV0gLSBwZXJjZW50c1tpXSkgLyAyNTAwKTsKICAgICAgICAgICAgbGV0IGFjY2Vzc29ycyA9IHBlcmNlbnRzLm1hcCgocCwgaSkgPT4gKGRhdHVtKSA9PiBkYXR1bVtpXVsxXSk7CiAgICAgICAgICAgIGxldCBtZWRpYW4gPSA0OwogICAgICAgICAgICBsZXQgbWVkaWFuQWNjZXNzb3IgPSBhY2Nlc3NvcnNbbWVkaWFuXTsKICAgICAgICAgICAgbGV0IHBsb3RzID0gbG9kYXNoLnJhbmdlKGFjY2Vzc29ycy5sZW5ndGggLSAxKS5tYXAoKGkpID0+IHsKICAgICAgICAgICAgICAgIGxldCBwID0gbmV3IHNyYyQyLlBsb3RzLkFyZWEoKTsKICAgICAgICAgICAgICAgIHAueCh4QWNjZXNzb3IsIHhTY2FsZSk7CiAgICAgICAgICAgICAgICBsZXQgeTAgPSBpID4gbWVkaWFuID8gYWNjZXNzb3JzW2ldIDogYWNjZXNzb3JzW2kgKyAxXTsKICAgICAgICAgICAgICAgIGxldCB5ID0gaSA+IG1lZGlhbiA/IGFjY2Vzc29yc1tpICsgMV0gOiBhY2Nlc3NvcnNbaV07CiAgICAgICAgICAgICAgICBwLnkoeSwgeVNjYWxlKTsKICAgICAgICAgICAgICAgIHAueTAoeTApOwogICAgICAgICAgICAgICAgcC5hdHRyKCdmaWxsJywgKGQsIGksIGRhdGFzZXQpID0+IHRoaXMuY29sb3JTY2FsZS5zY2FsZShkYXRhc2V0Lm1ldGFkYXRhKCkucnVuKSk7CiAgICAgICAgICAgICAgICBwLmF0dHIoJ3N0cm9rZScsIChkLCBpLCBkYXRhc2V0KSA9PiB0aGlzLmNvbG9yU2NhbGUuc2NhbGUoZGF0YXNldC5tZXRhZGF0YSgpLnJ1bikpOwogICAgICAgICAgICAgICAgcC5hdHRyKCdzdHJva2Utd2VpZ2h0JywgKGQsIGksIG0pID0+ICcwLjVweCcpOwogICAgICAgICAgICAgICAgcC5hdHRyKCdzdHJva2Utb3BhY2l0eScsICgpID0+IG9wYWNpdGllc1tpXSk7CiAgICAgICAgICAgICAgICBwLmF0dHIoJ2ZpbGwtb3BhY2l0eScsICgpID0+IG9wYWNpdGllc1tpXSk7CiAgICAgICAgICAgICAgICByZXR1cm4gcDsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGxldCBtZWRpYW5QbG90ID0gbmV3IHNyYyQyLlBsb3RzLkxpbmUoKTsKICAgICAgICAgICAgbWVkaWFuUGxvdC54KHhBY2Nlc3NvciwgeFNjYWxlKTsKICAgICAgICAgICAgbWVkaWFuUGxvdC55KG1lZGlhbkFjY2Vzc29yLCB5U2NhbGUpOwogICAgICAgICAgICBtZWRpYW5QbG90LmF0dHIoJ3N0cm9rZScsIChkLCBpLCBtKSA9PiB0aGlzLmNvbG9yU2NhbGUuc2NhbGUobS5ydW4pKTsKICAgICAgICAgICAgdGhpcy5wbG90cyA9IHBsb3RzOwogICAgICAgICAgICByZXR1cm4gbmV3IHNyYyQyLkNvbXBvbmVudHMuR3JvdXAocGxvdHMpOwogICAgICAgIH0KICAgICAgICBzZXRWaXNpYmxlU2VyaWVzKHJ1bnMpIHsKICAgICAgICAgICAgdGhpcy5ydW5zID0gcnVuczsKICAgICAgICAgICAgbGV0IGRhdGFzZXRzID0gcnVucy5tYXAoKHIpID0+IHRoaXMuZ2V0RGF0YXNldChyKSk7CiAgICAgICAgICAgIHRoaXMucGxvdHMuZm9yRWFjaCgocCkgPT4gcC5kYXRhc2V0cyhkYXRhc2V0cykpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBTZXQgdGhlIGRhdGEgb2YgYSBzZXJpZXMgb24gdGhlIGNoYXJ0LgogICAgICAgICAqLwogICAgICAgIHNldFNlcmllc0RhdGEobmFtZSwgZGF0YSkgewogICAgICAgICAgICB0aGlzLmdldERhdGFzZXQobmFtZSkuZGF0YShkYXRhKTsKICAgICAgICB9CiAgICAgICAgcmVuZGVyVG8odGFyZ2V0U1ZHKSB7CiAgICAgICAgICAgIHRoaXMudGFyZ2V0U1ZHID0gdGFyZ2V0U1ZHOwogICAgICAgICAgICB0aGlzLm91dGVyLnJlbmRlclRvKHRhcmdldFNWRyk7CiAgICAgICAgfQogICAgICAgIHJlZHJhdygpIHsKICAgICAgICAgICAgdGhpcy5vdXRlci5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgZGVzdHJveSgpIHsKICAgICAgICAgICAgdGhpcy5vdXRlci5kZXN0cm95KCk7CiAgICAgICAgfQogICAgfQogICAgbGV0IF9WekRpc3RyaWJ1dGlvbkNoYXJ0ID0gY2xhc3MgX1Z6RGlzdHJpYnV0aW9uQ2hhcnQgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5jb2xvclNjYWxlID0gbmV3IHNyYyQyLlNjYWxlcy5Db2xvcigpLnJhbmdlKGNhdGVnb3J5MTAuc2xpY2UoKSk7CiAgICAgICAgICAgIHRoaXMueFR5cGUgPSAnc3RlcCc7CiAgICAgICAgICAgIHRoaXMuX3Zpc2libGVTZXJpZXNDYWNoZSA9IFtdOwogICAgICAgICAgICB0aGlzLl9zZXJpZXNEYXRhQ2FjaGUgPSB7fTsKICAgICAgICAgICAgdGhpcy5fbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgc2V0VmlzaWJsZVNlcmllcyhuYW1lcykgewogICAgICAgICAgICB0aGlzLl92aXNpYmxlU2VyaWVzQ2FjaGUgPSBuYW1lczsKICAgICAgICAgICAgaWYgKHRoaXMuX2NoYXJ0KSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydC5zZXRWaXNpYmxlU2VyaWVzKG5hbWVzKTsKICAgICAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKSB7CiAgICAgICAgICAgIHRoaXMuX3Nlcmllc0RhdGFDYWNoZVtuYW1lXSA9IGRhdGE7CiAgICAgICAgICAgIGlmICh0aGlzLl9jaGFydCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQuc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZWRyYXcoKSB7CiAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnJlZHJhdygpOwogICAgICAgIH0KICAgICAgICBfbWFrZUNoYXJ0KCkgewogICAgICAgICAgICB2YXIgeFR5cGUgPSB0aGlzLnhUeXBlOwogICAgICAgICAgICB2YXIgY29sb3JTY2FsZSA9IHRoaXMuY29sb3JTY2FsZTsKICAgICAgICAgICAgdmFyIF9hdHRhY2hlZCA9IHRoaXMuX2F0dGFjaGVkOwogICAgICAgICAgICBpZiAodGhpcy5fbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLmNhbmNlbEFzeW5jKHRoaXMuX21ha2VDaGFydEFzeW5jQ2FsbGJhY2tJZCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fbWFrZUNoYXJ0QXN5bmNDYWxsYmFja0lkID0gdGhpcy5hc3luYyhmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9tYWtlQ2hhcnRBc3luY0NhbGxiYWNrSWQgPSBudWxsOwogICAgICAgICAgICAgICAgaWYgKCFfYXR0YWNoZWQpCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgaWYgKHRoaXMuX2NoYXJ0KQogICAgICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LmRlc3Ryb3koKTsKICAgICAgICAgICAgICAgIHZhciBjaGFydCA9IG5ldyBEaXN0cmlidXRpb25DaGFydCh4VHlwZSwgY29sb3JTY2FsZSk7CiAgICAgICAgICAgICAgICB2YXIgc3ZnID0gc2VsZWN0KHRoaXMuJC5jaGFydGRpdik7CiAgICAgICAgICAgICAgICBjaGFydC5yZW5kZXJUbyhzdmcpOwogICAgICAgICAgICAgICAgdGhpcy5fY2hhcnQgPSBjaGFydDsKICAgICAgICAgICAgfSwgMzUwKTsKICAgICAgICB9CiAgICAgICAgX3JlbG9hZEZyb21DYWNoZSgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2NoYXJ0KSB7CiAgICAgICAgICAgICAgICB0aGlzLl9jaGFydC5zZXRWaXNpYmxlU2VyaWVzKHRoaXMuX3Zpc2libGVTZXJpZXNDYWNoZSk7CiAgICAgICAgICAgICAgICB0aGlzLl92aXNpYmxlU2VyaWVzQ2FjaGUuZm9yRWFjaChmdW5jdGlvbiAobmFtZSkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX2NoYXJ0LnNldFNlcmllc0RhdGEobmFtZSwgdGhpcy5fc2VyaWVzRGF0YUNhY2hlW25hbWVdIHx8IFtdKTsKICAgICAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuX2F0dGFjaGVkID0gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgZGV0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuX2F0dGFjaGVkID0gZmFsc2U7CiAgICAgICAgfQogICAgfTsKICAgIF9WekRpc3RyaWJ1dGlvbkNoYXJ0LnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGUgaW5jbHVkZT0icGxvdHRhYmxlLXN0eWxlIj48L3N0eWxlPgogICAgPGRpdiBpZD0iY2hhcnRkaXYiPjwvZGl2PgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CiAgICAgICNjaGFydGRpdiB7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAgIGZsZXgtZ3JvdzogMTsKICAgICAgICBmbGV4LXNocmluazogMTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBzcmMkMi5TY2FsZXMuQ29sb3IpCiAgICBdLCBfVnpEaXN0cmlidXRpb25DaGFydC5wcm90b3R5cGUsICJjb2xvclNjYWxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1Z6RGlzdHJpYnV0aW9uQ2hhcnQucHJvdG90eXBlLCAieFR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9WekRpc3RyaWJ1dGlvbkNoYXJ0LnByb3RvdHlwZSwgIl9hdHRhY2hlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIERpc3RyaWJ1dGlvbkNoYXJ0KQogICAgXSwgX1Z6RGlzdHJpYnV0aW9uQ2hhcnQucHJvdG90eXBlLCAiX2NoYXJ0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIF9WekRpc3RyaWJ1dGlvbkNoYXJ0LnByb3RvdHlwZSwgIl92aXNpYmxlU2VyaWVzQ2FjaGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVnpEaXN0cmlidXRpb25DaGFydC5wcm90b3R5cGUsICJfc2VyaWVzRGF0YUNhY2hlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgX1Z6RGlzdHJpYnV0aW9uQ2hhcnQucHJvdG90eXBlLCAiX21ha2VDaGFydEFzeW5jQ2FsbGJhY2tJZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCd4VHlwZScsICdjb2xvclNjYWxlJywgJ19hdHRhY2hlZCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgX1Z6RGlzdHJpYnV0aW9uQ2hhcnQucHJvdG90eXBlLCAiX21ha2VDaGFydCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX2NoYXJ0JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVnpEaXN0cmlidXRpb25DaGFydC5wcm90b3R5cGUsICJfcmVsb2FkRnJvbUNhY2hlIiwgbnVsbCk7CiAgICBfVnpEaXN0cmlidXRpb25DaGFydCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3Z6LWRpc3RyaWJ1dGlvbi1jaGFydCcpCiAgICBdLCBfVnpEaXN0cmlidXRpb25DaGFydCk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAgdGYtZGlzdHJpYnV0aW9uLWxvYWRlciBsb2FkcyBhbiBpbmRpdmlkdWFsIGRpc3RyaWJ1dGlvbiBmcm9tIHRoZQogICAgICBUZW5zb3JCb2FyZCBiYWNrZW5kLCBhbmQgcmVuZGVycyBpdCBpbnRvIGEgdnotZGlzdHJpYnV0aW9uLWNoYXJ0LgogICAgKi8KICAgIGxldCBfVGZEaXN0cmlidXRpb25Mb2FkZXIgPSBjbGFzcyBfVGZEaXN0cmlidXRpb25Mb2FkZXIgZXh0ZW5kcyBEYXRhTG9hZGVyQmVoYXZpb3IoTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLmdldERhdGFMb2FkTmFtZSA9ICh7IHJ1biB9KSA9PiBydW47CiAgICAgICAgICAgIHRoaXMucmVxdWVzdERhdGEgPSAoaXRlbXMsIG9uTG9hZCwgb25GaW5pc2gpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IHJvdXRlciA9IGdldFJvdXRlcigpOwogICAgICAgICAgICAgICAgY29uc3QgYmFzZVVybCA9IHJvdXRlci5wbHVnaW5Sb3V0ZSgnZGlzdHJpYnV0aW9ucycsICcvZGlzdHJpYnV0aW9ucycpOwogICAgICAgICAgICAgICAgUHJvbWlzZS5hbGwoaXRlbXMubWFwKChpdGVtKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgdXJsID0gYWRkUGFyYW1zKGJhc2VVcmwsIHsgdGFnOiBpdGVtLnRhZywgcnVuOiBpdGVtLnJ1biB9KTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5yZXF1ZXN0TWFuYWdlcgogICAgICAgICAgICAgICAgICAgICAgICAucmVxdWVzdCh1cmwpCiAgICAgICAgICAgICAgICAgICAgICAgIC50aGVuKChkYXRhKSA9PiB2b2lkIG9uTG9hZCh7IGl0ZW0sIGRhdGEgfSkpOwogICAgICAgICAgICAgICAgfSkpLmZpbmFsbHkoKCkgPT4gdm9pZCBvbkZpbmlzaCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5sb2FkRGF0YUNhbGxiYWNrID0gKF8sIGRhdHVtLCBiYWNrZW5kRGF0YSkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgZGF0YSA9IGJhY2tlbmREYXRhLm1hcCgoZGF0dW0pID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBgdnotZGlzdHJpYnV0aW9uLWNoYXJ0YCB3YW50cyBlYWNoIGRhdHVtIGFzIGFuIGFycmF5IHdpdGgKICAgICAgICAgICAgICAgICAgICAvLyBleHRyYSBgd2FsbF90aW1lYCBhbmQgYHN0ZXBgIHByb3BlcnRpZXMuCiAgICAgICAgICAgICAgICAgICAgY29uc3QgW3dhbGxfdGltZSwgc3RlcCwgYmluc10gPSBkYXR1bTsKICAgICAgICAgICAgICAgICAgICBiaW5zLndhbGxfdGltZSA9IG5ldyBEYXRlKHdhbGxfdGltZSAqIDEwMDApOwogICAgICAgICAgICAgICAgICAgIGJpbnMuc3RlcCA9IHN0ZXA7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGJpbnM7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGNvbnN0IG5hbWUgPSB0aGlzLmdldERhdGFMb2FkTmFtZShkYXR1bSk7CiAgICAgICAgICAgICAgICB0aGlzLiQuY2hhcnQuc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKTsKICAgICAgICAgICAgICAgIHRoaXMuJC5jaGFydC5zZXRWaXNpYmxlU2VyaWVzKFtuYW1lXSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX2NvbG9yU2NhbGUgPSB7IHNjYWxlOiBydW5zQ29sb3JTY2FsZSB9OwogICAgICAgICAgICB0aGlzLl9leHBhbmRlZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9jYW5jZWxsZXIgPSBuZXcgQ2FuY2VsbGVyKCk7CiAgICAgICAgfQogICAgICAgIF9yZWxvYWRPblJ1blRhZ0NoYW5nZSgpIHsKICAgICAgICAgICAgdGhpcy5yZWxvYWQoKTsKICAgICAgICB9CiAgICAgICAgX3VwZGF0ZURhdGFUb0xvYWQoKSB7CiAgICAgICAgICAgIHZhciBydW4gPSB0aGlzLnJ1bjsKICAgICAgICAgICAgdmFyIHRhZyA9IHRoaXMudGFnOwogICAgICAgICAgICB0aGlzLmRhdGFUb0xvYWQgPSBbeyBydW4sIHRhZyB9XTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9ydW5Db2xvcigpIHsKICAgICAgICAgICAgdmFyIHJ1biA9IHRoaXMucnVuOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fY29sb3JTY2FsZS5zY2FsZShydW4pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBBc2sgdGhlIGRpc3RyaWJ1dGlvbiBjaGFydCB0byByZWRyYXcgaXRzZWxmLiBUaGlzIHNob3VsZCBiZQogICAgICAgICAqIGNhbGxlZCB3aGVuZXZlciB0aGUgZGltZW5zaW9ucyBvZiB0aGUgdmlldyBjaGFuZ2UgKGUuZy4sIHdoZW4KICAgICAgICAgKiB0aGUgY2FyZCBpcyBleHBhbmRlZCksIGFzIHRoZSBkaXN0cmlidXRpb24gY2hhcnQgd2lsbCBuZWVkIHRvCiAgICAgICAgICogcmVjYWxjdWxhdGUgaXRzIGxheW91dC4KICAgICAgICAgKi8KICAgICAgICByZWRyYXcoKSB7CiAgICAgICAgICAgIHRoaXMuJC5jaGFydC5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUV4cGFuZGVkKGUpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19leHBhbmRlZCcsICF0aGlzLl9leHBhbmRlZCk7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgfQogICAgfTsKICAgIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWNhcmQtaGVhZGluZwogICAgICB0YWc9IltbdGFnXV0iCiAgICAgIHJ1bj0iW1tydW5dXSIKICAgICAgZGlzcGxheS1uYW1lPSJbW3RhZ01ldGFkYXRhLmRpc3BsYXlOYW1lXV0iCiAgICAgIGRlc2NyaXB0aW9uPSJbW3RhZ01ldGFkYXRhLmRlc2NyaXB0aW9uXV0iCiAgICAgIGNvbG9yPSJbW19ydW5Db2xvcl1dIgogICAgPjwvdGYtY2FyZC1oZWFkaW5nPgogICAgPCEtLQogICAgICBUaGUgbWFpbiBkaXN0cmlidXRpb24gdGhhdCB3ZSByZW5kZXIuIERhdGEgaXMgc2V0IGRpcmVjdGx5IHdpdGgKICAgICAgXGBzZXRTZXJpZXNEYXRhXGAsIG5vdCB3aXRoIGEgYm91bmQgcHJvcGVydHkuCiAgICAtLT4KICAgIDx2ei1kaXN0cmlidXRpb24tY2hhcnQKICAgICAgaWQ9ImNoYXJ0IgogICAgICB4LXR5cGU9IltbeFR5cGVdXSIKICAgICAgY29sb3Itc2NhbGU9IltbX2NvbG9yU2NhbGVdXSIKICAgID48L3Z6LWRpc3RyaWJ1dGlvbi1jaGFydD4KICAgIDxkaXYgc3R5bGU9ImRpc3BsYXk6IGZsZXg7IGZsZXgtZGlyZWN0aW9uOiByb3c7Ij4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgc2VsZWN0ZWQkPSJbW19leHBhbmRlZF1dIgogICAgICAgIGljb249ImZ1bGxzY3JlZW4iCiAgICAgICAgb24tdGFwPSJfdG9nZ2xlRXhwYW5kZWQiCiAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgd2lkdGg6IDMzMHB4OwogICAgICAgIGhlaWdodDogMjM1cHg7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiAxMHB4OwogICAgICAgIG1hcmdpbi1ib3R0b206IDE1cHg7CiAgICAgIH0KICAgICAgOmhvc3QoW19leHBhbmRlZF0pIHsKICAgICAgICB3aWR0aDogNzAwcHg7CiAgICAgICAgaGVpZ2h0OiA1MDBweDsKICAgICAgfQoKICAgICAgdnotaGlzdG9ncmFtLXRpbWVzZXJpZXMgewogICAgICAgIC1tb3otdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgfQoKICAgICAgcGFwZXItaWNvbi1idXR0b24gewogICAgICAgIGNvbG9yOiAjMjE5NmYzOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDEwMCU7CiAgICAgICAgd2lkdGg6IDMycHg7CiAgICAgICAgaGVpZ2h0OiAzMnB4OwogICAgICAgIHBhZGRpbmc6IDRweDsKICAgICAgfQogICAgICBwYXBlci1pY29uLWJ1dHRvbltzZWxlY3RlZF0gewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXRiLXVpLWxpZ2h0LWFjY2VudCk7CiAgICAgIH0KCiAgICAgIHRmLWNhcmQtaGVhZGluZyB7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMTBweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAicnVuIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1RmRGlzdHJpYnV0aW9uTG9hZGVyLnByb3RvdHlwZSwgInRhZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci5wcm90b3R5cGUsICJ0YWdNZXRhZGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci5wcm90b3R5cGUsICJ4VHlwZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci5wcm90b3R5cGUsICJnZXREYXRhTG9hZE5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAibG9hZERhdGFDYWxsYmFjayIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci5wcm90b3R5cGUsICJfY29sb3JTY2FsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAiX2V4cGFuZGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVxdWVzdE1hbmFnZXIpCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAicmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBDYW5jZWxsZXIpCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAiX2NhbmNlbGxlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdydW4nLCAndGFnJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAiX3JlbG9hZE9uUnVuVGFnQ2hhbmdlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdydW4nLCAndGFnJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVGZEaXN0cmlidXRpb25Mb2FkZXIucHJvdG90eXBlLCAiX3VwZGF0ZURhdGFUb0xvYWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdydW4nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkRpc3RyaWJ1dGlvbkxvYWRlci5wcm90b3R5cGUsICJfcnVuQ29sb3IiLCBudWxsKTsKICAgIF9UZkRpc3RyaWJ1dGlvbkxvYWRlciA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWRpc3RyaWJ1dGlvbi1sb2FkZXInKQogICAgXSwgX1RmRGlzdHJpYnV0aW9uTG9hZGVyKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICBBIGZyb250ZW5kIHRoYXQgZGlzcGxheXMgYSBzZXQgb2YgdGYtZGlzdHJpYnV0aW9uLWxvYWRlcnMsIGVhY2ggb2YKICAgICAgd2hpY2ggZGlzcGxheXMgdGhlIGRpc3RyaWJ1dGlvbiBmb3IgYSBzaW5nbGUgdGFnIG9uIGEgc2luZ2xlIHJ1bi4gVGhpcwogICAgICBkYXNoYm9hcmQgcHJvdmlkZXMgYSBjYXRlZ29yaXplciBhbmQgYWJjaXNzYSBzZWxldG9yIChzdGVwLCByZWxhdGl2ZSwKICAgICAgb3Igd2FsbCB0aW1lKS4KICAgICovCiAgICBsZXQgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQgPSBjbGFzcyBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZCBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLnJlbG9hZE9uUmVhZHkgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl94VHlwZSA9ICdzdGVwJzsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdE1hbmFnZXIgPSBuZXcgUmVxdWVzdE1hbmFnZXIoKTsKICAgICAgICB9CiAgICAgICAgcmVhZHkoKSB7CiAgICAgICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgICAgIGlmICh0aGlzLnJlbG9hZE9uUmVhZHkpCiAgICAgICAgICAgICAgICB0aGlzLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICByZWxvYWQoKSB7CiAgICAgICAgICAgIHRoaXMuX2ZldGNoVGFncygpLnRoZW4oKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5fcmVsb2FkRGlzdHJpYnV0aW9ucygpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2ZldGNoVGFncygpIHsKICAgICAgICAgICAgY29uc3QgdXJsID0gZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2Rpc3RyaWJ1dGlvbnMnLCAnL3RhZ3MnKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3RNYW5hZ2VyLnJlcXVlc3QodXJsKS50aGVuKChydW5Ub1RhZ0luZm8pID0+IHsKICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNFcXVhbChydW5Ub1RhZ0luZm8sIHRoaXMuX3J1blRvVGFnSW5mbykpIHsKICAgICAgICAgICAgICAgICAgICAvLyBObyBuZWVkIHRvIHVwZGF0ZSBhbnl0aGluZyBpZiB0aGVyZSBhcmUgbm8gY2hhbmdlcy4KICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb25zdCBydW5Ub1RhZyA9IGxvZGFzaC5tYXBWYWx1ZXMocnVuVG9UYWdJbmZvLCAoeCkgPT4gT2JqZWN0LmtleXMoeCkpOwogICAgICAgICAgICAgICAgY29uc3QgdGFncyA9IGdldFRhZ3MocnVuVG9UYWcpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19kYXRhTm90Rm91bmQnLCB0YWdzLmxlbmd0aCA9PT0gMCk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3J1blRvVGFnJywgcnVuVG9UYWcpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19ydW5Ub1RhZ0luZm8nLCBydW5Ub1RhZ0luZm8pOwogICAgICAgICAgICAgICAgdGhpcy5hc3luYygoKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgLy8gU2VlIHRoZSBjb21tZW50IGFib3ZlIGBfY2F0ZWdvcmllc0RvbVJlYWR5YC4KICAgICAgICAgICAgICAgICAgICB0aGlzLnNldCgnX2NhdGVnb3JpZXNEb21SZWFkeScsIHRydWUpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfcmVsb2FkRGlzdHJpYnV0aW9ucygpIHsKICAgICAgICAgICAgdGhpcy5yb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ3RmLWRpc3RyaWJ1dGlvbi1sb2FkZXInKS5mb3JFYWNoKChsb2FkZXIpID0+IHsKICAgICAgICAgICAgICAgIGxvYWRlci5yZWxvYWQoKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9zaG91bGRPcGVuKGluZGV4KSB7CiAgICAgICAgICAgIHJldHVybiBpbmRleCA8PSAyOwogICAgICAgIH0KICAgICAgICBnZXQgX2NhdGVnb3JpZXMoKSB7CiAgICAgICAgICAgIHZhciBydW5Ub1RhZyA9IHRoaXMuX3J1blRvVGFnOwogICAgICAgICAgICB2YXIgc2VsZWN0ZWRSdW5zID0gdGhpcy5fc2VsZWN0ZWRSdW5zOwogICAgICAgICAgICB2YXIgdGFnRmlsdGVyID0gdGhpcy5fdGFnRmlsdGVyOwogICAgICAgICAgICB2YXIgY2F0ZWdvcmllc0RvbVJlYWR5ID0gdGhpcy5fY2F0ZWdvcmllc0RvbVJlYWR5OwogICAgICAgICAgICByZXR1cm4gY2F0ZWdvcml6ZVJ1blRhZ0NvbWJpbmF0aW9ucyhydW5Ub1RhZywgc2VsZWN0ZWRSdW5zLCB0YWdGaWx0ZXIpOwogICAgICAgIH0KICAgICAgICBfdGFnTWV0YWRhdGEocnVuVG9UYWdJbmZvLCBydW4sIHRhZykgewogICAgICAgICAgICByZXR1cm4gcnVuVG9UYWdJbmZvW3J1bl1bdGFnXTsKICAgICAgICB9CiAgICB9OwogICAgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQudGVtcGxhdGUgPSBodG1sIGAKICAgIDx0Zi1kYXNoYm9hcmQtbGF5b3V0PgogICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyIiBzbG90PSJzaWRlYmFyIj4KICAgICAgICA8ZGl2IGNsYXNzPSJzZXR0aW5ncyI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24iPgogICAgICAgICAgICA8dGYtb3B0aW9uLXNlbGVjdG9yCiAgICAgICAgICAgICAgaWQ9InhUeXBlU2VsZWN0b3IiCiAgICAgICAgICAgICAgbmFtZT0iSG9yaXpvbnRhbCBheGlzIgogICAgICAgICAgICAgIHNlbGVjdGVkLWlkPSJ7e194VHlwZX19IgogICAgICAgICAgICA+CiAgICAgICAgICAgICAgPHBhcGVyLWJ1dHRvbiBpZD0ic3RlcCI+c3RlcDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24gaWQ9InJlbGF0aXZlIj5yZWxhdGl2ZTwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24gaWQ9IndhbGxfdGltZSI+d2FsbDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICA8L3RmLW9wdGlvbi1zZWxlY3Rvcj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXYgY2xhc3M9InNpZGViYXItc2VjdGlvbiBydW5zLXNlbGVjdG9yIj4KICAgICAgICAgIDx0Zi1ydW5zLXNlbGVjdG9yIHNlbGVjdGVkLXJ1bnM9Int7X3NlbGVjdGVkUnVuc319Ij4KICAgICAgICAgIDwvdGYtcnVucy1zZWxlY3Rvcj4KICAgICAgICA8L2Rpdj4KICAgICAgPC9kaXY+CgogICAgICA8ZGl2IGNsYXNzPSJjZW50ZXIiIHNsb3Q9ImNlbnRlciI+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19kYXRhTm90Rm91bmRdXSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJuby1kYXRhLXdhcm5pbmciPgogICAgICAgICAgICA8aDM+Tm8gZGlzdHJpYnV0aW9uIGRhdGEgd2FzIGZvdW5kLjwvaDM+CiAgICAgICAgICAgIDxwPlByb2JhYmxlIGNhdXNlczo8L3A+CiAgICAgICAgICAgIDx1bD4KICAgICAgICAgICAgICA8bGk+CiAgICAgICAgICAgICAgICBZb3UgaGF2ZW7igJl0IHdyaXR0ZW4gYW55IGhpc3RvZ3JhbSBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuCiAgICAgICAgICAgICAgICAoSGlzdG9ncmFtcyBhbmQgZGlzdHJpYnV0aW9ucyBib3RoIHVzZSB0aGUgaGlzdG9ncmFtIHN1bW1hcnkKICAgICAgICAgICAgICAgIG9wZXJhdGlvbi4pCiAgICAgICAgICAgICAgPC9saT4KCiAgICAgICAgICAgICAgPGxpPlRlbnNvckJvYXJkIGNhbuKAmXQgZmluZCB5b3VyIGV2ZW50IGZpbGVzLjwvbGk+CiAgICAgICAgICAgIDwvdWw+CgogICAgICAgICAgICA8cD4KICAgICAgICAgICAgICBJZiB5b3XigJlyZSBuZXcgdG8gdXNpbmcgVGVuc29yQm9hcmQsIGFuZCB3YW50IHRvIGZpbmQgb3V0IGhvdyB0bwogICAgICAgICAgICAgIGFkZCBkYXRhIGFuZCBzZXQgdXAgeW91ciBldmVudCBmaWxlcywgY2hlY2sgb3V0IHRoZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9ibG9iL21hc3Rlci9SRUFETUUubWQiCiAgICAgICAgICAgICAgICA+UkVBRE1FPC9hCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIGFuZCBwZXJoYXBzIHRoZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL3d3dy50ZW5zb3JmbG93Lm9yZy9nZXRfc3RhcnRlZC9zdW1tYXJpZXNfYW5kX3RlbnNvcmJvYXJkIgogICAgICAgICAgICAgICAgPlRlbnNvckJvYXJkIHR1dG9yaWFsPC9hCiAgICAgICAgICAgICAgPi4KICAgICAgICAgICAgPC9wPgoKICAgICAgICAgICAgPHA+CiAgICAgICAgICAgICAgSWYgeW91IHRoaW5rIFRlbnNvckJvYXJkIGlzIGNvbmZpZ3VyZWQgcHJvcGVybHksIHBsZWFzZSBzZWUKICAgICAgICAgICAgICA8YQogICAgICAgICAgICAgICAgaHJlZj0iaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvYmxvYi9tYXN0ZXIvUkVBRE1FLm1kI215LXRlbnNvcmJvYXJkLWlzbnQtc2hvd2luZy1hbnktZGF0YS13aGF0cy13cm9uZyIKICAgICAgICAgICAgICAgID50aGUgc2VjdGlvbiBvZiB0aGUgUkVBRE1FIGRldm90ZWQgdG8gbWlzc2luZyBkYXRhIHByb2JsZW1zPC9hCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIGFuZCBjb25zaWRlciBmaWxpbmcgYW4gaXNzdWUgb24gR2l0SHViLgogICAgICAgICAgICA8L3A+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shX2RhdGFOb3RGb3VuZF1dIj4KICAgICAgICAgIDx0Zi10YWctZmlsdGVyZXIgdGFnLWZpbHRlcj0ie3tfdGFnRmlsdGVyfX0iPjwvdGYtdGFnLWZpbHRlcmVyPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfY2F0ZWdvcmllc11dIiBhcz0iY2F0ZWdvcnkiPgogICAgICAgICAgICA8dGYtY2F0ZWdvcnktcGFnaW5hdGVkLXZpZXcKICAgICAgICAgICAgICBjYXRlZ29yeT0iW1tjYXRlZ29yeV1dIgogICAgICAgICAgICAgIGluaXRpYWwtb3BlbmVkPSJbW19zaG91bGRPcGVuKGluZGV4KV1dIgogICAgICAgICAgICA+CiAgICAgICAgICAgICAgPHRlbXBsYXRlPgogICAgICAgICAgICAgICAgPHRmLWRpc3RyaWJ1dGlvbi1sb2FkZXIKICAgICAgICAgICAgICAgICAgYWN0aXZlPSJbW2FjdGl2ZV1dIgogICAgICAgICAgICAgICAgICBydW49IltbaXRlbS5ydW5dXSIKICAgICAgICAgICAgICAgICAgdGFnPSJbW2l0ZW0udGFnXV0iCiAgICAgICAgICAgICAgICAgIHRhZy1tZXRhZGF0YT0iW1tfdGFnTWV0YWRhdGEoX3J1blRvVGFnSW5mbywgaXRlbS5ydW4sIGl0ZW0udGFnKV1dIgogICAgICAgICAgICAgICAgICB4LXR5cGU9IltbX3hUeXBlXV0iCiAgICAgICAgICAgICAgICAgIHJlcXVlc3QtbWFuYWdlcj0iW1tfcmVxdWVzdE1hbmFnZXJdXSIKICAgICAgICAgICAgICAgID48L3RmLWRpc3RyaWJ1dGlvbi1sb2FkZXI+CiAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPC90Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldz4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9kaXY+CiAgICA8L3RmLWRhc2hib2FyZC1sYXlvdXQ+CgogICAgPHN0eWxlIGluY2x1ZGU9ImRhc2hib2FyZC1zdHlsZSI+PC9zdHlsZT4KICAgIDxzdHlsZT4KICAgICAgLm5vLWRhdGEtd2FybmluZyB7CiAgICAgICAgbWF4LXdpZHRoOiA1NDBweDsKICAgICAgICBtYXJnaW46IDgwcHggYXV0byAwIGF1dG87CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZC5wcm90b3R5cGUsICJyZWxvYWRPblJlYWR5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQucHJvdG90eXBlLCAiX3hUeXBlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmRGlzdHJpYnV0aW9uRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9zZWxlY3RlZFJ1bnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZC5wcm90b3R5cGUsICJfcnVuVG9UYWciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZC5wcm90b3R5cGUsICJfcnVuVG9UYWdJbmZvIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZC5wcm90b3R5cGUsICJfZGF0YU5vdEZvdW5kIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQucHJvdG90eXBlLCAiX3RhZ0ZpbHRlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQucHJvdG90eXBlLCAiX2NhdGVnb3JpZXNEb21SZWFkeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFJlcXVlc3RNYW5hZ2VyKQogICAgXSwgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQucHJvdG90eXBlLCAiX3JlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfcnVuVG9UYWcnLCAnX3NlbGVjdGVkUnVucycsICdfdGFnRmlsdGVyJywgJ19jYXRlZ29yaWVzRG9tUmVhZHknKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZEaXN0cmlidXRpb25EYXNoYm9hcmQucHJvdG90eXBlLCAiX2NhdGVnb3JpZXMiLCBudWxsKTsKICAgIFRmRGlzdHJpYnV0aW9uRGFzaGJvYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZGlzdHJpYnV0aW9uLWRhc2hib2FyZCcpCiAgICBdLCBUZkRpc3RyaWJ1dGlvbkRhc2hib2FyZCk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCgogICAgdmFyIHRmX3N0b3JhZ2UgPSAvKiNfX1BVUkVfXyovT2JqZWN0LmZyZWV6ZSh7CiAgICAgICAgX19wcm90b19fOiBudWxsLAogICAgICAgIExpc3RlbktleTogTGlzdGVuS2V5LAogICAgICAgIGFkZEhhc2hMaXN0ZW5lcjogYWRkSGFzaExpc3RlbmVyLAogICAgICAgIGFkZFN0b3JhZ2VMaXN0ZW5lcjogYWRkU3RvcmFnZUxpc3RlbmVyLAogICAgICAgIGZpcmVTdG9yYWdlQ2hhbmdlZDogZmlyZVN0b3JhZ2VDaGFuZ2VkLAogICAgICAgIHJlbW92ZUhhc2hMaXN0ZW5lckJ5S2V5OiByZW1vdmVIYXNoTGlzdGVuZXJCeUtleSwKICAgICAgICByZW1vdmVTdG9yYWdlTGlzdGVuZXJCeUtleTogcmVtb3ZlU3RvcmFnZUxpc3RlbmVyQnlLZXksCiAgICAgICAgVEFCOiBUQUIsCiAgICAgICAgRElTQU1CSUdVQVRPUjogRElTQU1CSUdVQVRPUiwKICAgICAgICBnZXRVcmxEaWN0OiBnZXRVcmxEaWN0LAogICAgICAgIGdldFN0cmluZzogZ2V0U3RyaW5nLAogICAgICAgIHNldFN0cmluZzogc2V0U3RyaW5nLAogICAgICAgIGdldFN0cmluZ0luaXRpYWxpemVyOiBnZXRTdHJpbmdJbml0aWFsaXplciwKICAgICAgICBnZXRTdHJpbmdPYnNlcnZlcjogZ2V0U3RyaW5nT2JzZXJ2ZXIsCiAgICAgICAgZGlzcG9zZVN0cmluZ0JpbmRpbmc6IGRpc3Bvc2VTdHJpbmdCaW5kaW5nLAogICAgICAgIGdldEJvb2xlYW46IGdldEJvb2xlYW4sCiAgICAgICAgc2V0Qm9vbGVhbjogc2V0Qm9vbGVhbiwKICAgICAgICBnZXRCb29sZWFuSW5pdGlhbGl6ZXI6IGdldEJvb2xlYW5Jbml0aWFsaXplciwKICAgICAgICBnZXRCb29sZWFuT2JzZXJ2ZXI6IGdldEJvb2xlYW5PYnNlcnZlciwKICAgICAgICBkaXNwb3NlQm9vbGVhbkJpbmRpbmc6IGRpc3Bvc2VCb29sZWFuQmluZGluZywKICAgICAgICBnZXROdW1iZXI6IGdldE51bWJlciwKICAgICAgICBzZXROdW1iZXI6IHNldE51bWJlciwKICAgICAgICBnZXROdW1iZXJJbml0aWFsaXplcjogZ2V0TnVtYmVySW5pdGlhbGl6ZXIsCiAgICAgICAgZ2V0TnVtYmVyT2JzZXJ2ZXI6IGdldE51bWJlck9ic2VydmVyLAogICAgICAgIGRpc3Bvc2VOdW1iZXJCaW5kaW5nOiBkaXNwb3NlTnVtYmVyQmluZGluZywKICAgICAgICBnZXRPYmplY3Q6IGdldE9iamVjdCwKICAgICAgICBzZXRPYmplY3Q6IHNldE9iamVjdCwKICAgICAgICBnZXRPYmplY3RJbml0aWFsaXplcjogZ2V0T2JqZWN0SW5pdGlhbGl6ZXIsCiAgICAgICAgZ2V0T2JqZWN0T2JzZXJ2ZXI6IGdldE9iamVjdE9ic2VydmVyLAogICAgICAgIGRpc3Bvc2VPYmplY3RCaW5kaW5nOiBkaXNwb3NlT2JqZWN0QmluZGluZywKICAgICAgICBtYWtlQmluZGluZ3M6IG1ha2VCaW5kaW5ncywKICAgICAgICBtaWdyYXRlTGVnYWN5VVJMU2NoZW1lOiBtaWdyYXRlTGVnYWN5VVJMU2NoZW1lCiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8vIE5vdGUgdGhhdCB0Zi1ncmFwaC1jb250cm9sIGRlcGVuZHMgb24gdGhlIHZhbHVlIG9mIHRoZSBlbnVtLgogICAgLy8gUG9seW1lciBkb2VzIG5vdCBsZXQgb25lIHVzZSBKUyB2YXJpYWJsZSBhcyBhIHByb3AuCiAgICB2YXIgU2VsZWN0aW9uVHlwZTsKICAgIChmdW5jdGlvbiAoU2VsZWN0aW9uVHlwZSkgewogICAgICAgIFNlbGVjdGlvblR5cGVbIk9QX0dSQVBIIl0gPSAib3BfZ3JhcGgiOwogICAgICAgIFNlbGVjdGlvblR5cGVbIkNPTkNFUFRVQUxfR1JBUEgiXSA9ICJjb25jZXB0dWFsX2dyYXBoIjsKICAgICAgICBTZWxlY3Rpb25UeXBlWyJQUk9GSUxFIl0gPSAicHJvZmlsZSI7CiAgICB9KShTZWxlY3Rpb25UeXBlIHx8IChTZWxlY3Rpb25UeXBlID0ge30pKTsKICAgIC8qKiBFbnVtcyBlbGVtZW50IGNsYXNzIG9mIG9iamVjdHMgaW4gdGhlIHNjZW5lICovCiAgICBsZXQgQ2xhc3MkMSA9IHsKICAgICAgICBOb2RlOiB7CiAgICAgICAgICAgIC8vIDxnPiBlbGVtZW50IHRoYXQgY29udGFpbnMgbm9kZXMuCiAgICAgICAgICAgIENPTlRBSU5FUjogJ25vZGVzJywKICAgICAgICAgICAgLy8gPGc+IGVsZW1lbnQgdGhhdCBjb250YWlucyBkZXRhaWwgYWJvdXQgYSBub2RlLgogICAgICAgICAgICBHUk9VUDogJ25vZGUnLAogICAgICAgICAgICAvLyA8Zz4gZWxlbWVudCB0aGF0IGNvbnRhaW5zIHZpc3VhbCBlbGVtZW50cyAobGlrZSByZWN0LCBlbGxpcHNlKS4KICAgICAgICAgICAgU0hBUEU6ICdub2Rlc2hhcGUnLAogICAgICAgICAgICAvLyA8Kj4gZWxlbWVudChzKSB1bmRlciBTSEFQRSB0aGF0IHNob3VsZCByZWNlaXZlIGNvbG9yIHVwZGF0ZXMuCiAgICAgICAgICAgIENPTE9SX1RBUkdFVDogJ25vZGVjb2xvcnRhcmdldCcsCiAgICAgICAgICAgIC8vIDx0ZXh0PiBlbGVtZW50IHNob3dpbmcgdGhlIG5vZGUncyBsYWJlbC4KICAgICAgICAgICAgTEFCRUw6ICdub2RlbGFiZWwnLAogICAgICAgICAgICAvLyA8Zz4gZWxlbWVudCB0aGF0IGNvbnRhaW5zIGFsbCB2aXN1YWxzIGZvciB0aGUgZXhwYW5kL2NvbGxhcHNlCiAgICAgICAgICAgIC8vIGJ1dHRvbiBmb3IgZXhwYW5kYWJsZSBncm91cCBub2Rlcy4KICAgICAgICAgICAgQlVUVE9OX0NPTlRBSU5FUjogJ2J1dHRvbmNvbnRhaW5lcicsCiAgICAgICAgICAgIC8vIDxjaXJjbGU+IGVsZW1lbnQgdGhhdCBzdXJyb3VuZHMgZXhwYW5kL2NvbGxhcHNlIGJ1dHRvbnMuCiAgICAgICAgICAgIEJVVFRPTl9DSVJDTEU6ICdidXR0b25jaXJjbGUnLAogICAgICAgICAgICAvLyA8cGF0aD4gZWxlbWVudCBvZiB0aGUgZXhwYW5kIGJ1dHRvbi4KICAgICAgICAgICAgRVhQQU5EX0JVVFRPTjogJ2V4cGFuZGJ1dHRvbicsCiAgICAgICAgICAgIC8vIDxwYXRoPiBlbGVtZW50IG9mIHRoZSBjb2xsYXBzZSBidXR0b24uCiAgICAgICAgICAgIENPTExBUFNFX0JVVFRPTjogJ2NvbGxhcHNlYnV0dG9uJywKICAgICAgICB9LAogICAgICAgIEVkZ2U6IHsKICAgICAgICAgICAgQ09OVEFJTkVSOiAnZWRnZXMnLAogICAgICAgICAgICBHUk9VUDogJ2VkZ2UnLAogICAgICAgICAgICBMSU5FOiAnZWRnZWxpbmUnLAogICAgICAgICAgICBSRUZFUkVOQ0VfRURHRTogJ3JlZmVyZW5jZWVkZ2UnLAogICAgICAgICAgICBSRUZfTElORTogJ3JlZmxpbmUnLAogICAgICAgICAgICBTRUxFQ1RBQkxFOiAnc2VsZWN0YWJsZWVkZ2UnLAogICAgICAgICAgICBTRUxFQ1RFRDogJ3NlbGVjdGVkZWRnZScsCiAgICAgICAgICAgIFNUUlVDVFVSQUw6ICdzdHJ1Y3R1cmFsJywKICAgICAgICB9LAogICAgICAgIEFubm90YXRpb246IHsKICAgICAgICAgICAgT1VUQk9YOiAnb3V0LWFubm90YXRpb25zJywKICAgICAgICAgICAgSU5CT1g6ICdpbi1hbm5vdGF0aW9ucycsCiAgICAgICAgICAgIEdST1VQOiAnYW5ub3RhdGlvbicsCiAgICAgICAgICAgIE5PREU6ICdhbm5vdGF0aW9uLW5vZGUnLAogICAgICAgICAgICBFREdFOiAnYW5ub3RhdGlvbi1lZGdlJywKICAgICAgICAgICAgQ09OVFJPTF9FREdFOiAnYW5ub3RhdGlvbi1jb250cm9sLWVkZ2UnLAogICAgICAgICAgICBMQUJFTDogJ2Fubm90YXRpb24tbGFiZWwnLAogICAgICAgICAgICBFTExJUFNJUzogJ2Fubm90YXRpb24tZWxsaXBzaXMnLAogICAgICAgIH0sCiAgICAgICAgU2NlbmU6IHsKICAgICAgICAgICAgR1JPVVA6ICdzY2VuZScsCiAgICAgICAgICAgIENPUkU6ICdjb3JlJywKICAgICAgICAgICAgRlVOQ1RJT05fTElCUkFSWTogJ2Z1bmN0aW9uLWxpYnJhcnknLAogICAgICAgICAgICBJTkVYVFJBQ1Q6ICdpbi1leHRyYWN0JywKICAgICAgICAgICAgT1VURVhUUkFDVDogJ291dC1leHRyYWN0JywKICAgICAgICB9LAogICAgICAgIFN1YnNjZW5lOiB7IEdST1VQOiAnc3Vic2NlbmUnIH0sCiAgICAgICAgT1BOT0RFOiAnb3AnLAogICAgICAgIE1FVEFOT0RFOiAnbWV0YScsCiAgICAgICAgU0VSSUVTTk9ERTogJ3NlcmllcycsCiAgICAgICAgQlJJREdFTk9ERTogJ2JyaWRnZScsCiAgICAgICAgRUxMSVBTSVNOT0RFOiAnZWxsaXBzaXMnLAogICAgfTsKICAgIGNvbnN0IFNWR19OQU1FU1BBQ0UgPSAnaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnOwogICAgLyoqCiAgICAgKiBHaXZlbiBhIGNvbnRhaW5lciBkMyBzZWxlY3Rpb24sIHNlbGVjdCBhIGNoaWxkIGVsZW1lbnQgb2YgYSBnaXZlbiB0YWcgYW5kCiAgICAgKiBjbGFzcy4gSWYgbXVsdGlwbGUgY2hpbGRyZW4gbWF0Y2hlcyB0aGUgdGFnIGFuZCBjbGFzcyBuYW1lLCByZXR1cm5zIG9ubHkKICAgICAqIHRoZSBmaXJzdCBvbmUuCiAgICAgKgogICAgICogQHBhcmFtIGNvbnRhaW5lcgogICAgICogQHBhcmFtIHRhZ05hbWUgdGFnIG5hbWUuCiAgICAgKiBAcGFyYW0gY2xhc3NOYW1lIChvcHRpb25hbCkgQ2xhc3MgbmFtZSBvciBsaXN0IG9mIGNsYXNzIG5hbWVzLgogICAgICogQHJldHVybiBzZWxlY3Rpb24gb2YgdGhlIGVsZW1lbnQsIG9yIGFuIGVtcHR5IHNlbGVjdGlvbgogICAgICovCiAgICBmdW5jdGlvbiBzZWxlY3RDaGlsZChjb250YWluZXIsIHRhZ05hbWUsIGNsYXNzTmFtZSkgewogICAgICAgIGxldCBjaGlsZHJlbiA9IGNvbnRhaW5lci5ub2RlKCkuY2hpbGROb2RlczsKICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGNoaWxkcmVuLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGxldCBjaGlsZCA9IGNoaWxkcmVuW2ldOwogICAgICAgICAgICBpZiAoY2hpbGQudGFnTmFtZSA9PT0gdGFnTmFtZSkgewogICAgICAgICAgICAgICAgaWYgKGNsYXNzTmFtZSBpbnN0YW5jZW9mIEFycmF5KSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IGhhc0FsbENsYXNzZXMgPSB0cnVlOwogICAgICAgICAgICAgICAgICAgIGZvciAobGV0IGogPSAwOyBqIDwgY2xhc3NOYW1lLmxlbmd0aDsgaisrKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGhhc0FsbENsYXNzZXMgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgaGFzQWxsQ2xhc3NlcyAmJiBjaGlsZC5jbGFzc0xpc3QuY29udGFpbnMoY2xhc3NOYW1lW2pdKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgaWYgKGhhc0FsbENsYXNzZXMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHNlbGVjdChjaGlsZCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAoIWNsYXNzTmFtZSB8fCBjaGlsZC5jbGFzc0xpc3QuY29udGFpbnMoY2xhc3NOYW1lKSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBzZWxlY3QoY2hpbGQpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBzZWxlY3QobnVsbCk7CiAgICB9CiAgICAvKioKICAgICAqIEdpdmVuIGEgY29udGFpbmVyIGQzIHNlbGVjdGlvbiwgc2VsZWN0IGEgY2hpbGQgc3ZnIGVsZW1lbnQgb2YgYSBnaXZlbiB0YWcKICAgICAqIGFuZCBjbGFzcyBpZiBleGlzdHMgb3IgYXBwZW5kIC8gaW5zZXJ0IG9uZSBvdGhlcndpc2UuICBJZiBtdWx0aXBsZSBjaGlsZHJlbgogICAgICogbWF0Y2hlcyB0aGUgdGFnIGFuZCBjbGFzcyBuYW1lLCByZXR1cm5zIG9ubHkgdGhlIGZpcnN0IG9uZS4KICAgICAqCiAgICAgKiBAcGFyYW0gY29udGFpbmVyCiAgICAgKiBAcGFyYW0gdGFnTmFtZSB0YWcgbmFtZS4KICAgICAqIEBwYXJhbSBjbGFzc05hbWUgKG9wdGlvbmFsKSBDbGFzcyBuYW1lIG9yIGEgbGlzdCBvZiBjbGFzcyBuYW1lcy4KICAgICAqIEBwYXJhbSBiZWZvcmUgKG9wdGlvbmFsKSByZWZlcmVuY2UgRE9NIG5vZGUgZm9yIGluc2VydGlvbi4KICAgICAqIEByZXR1cm4gc2VsZWN0aW9uIG9mIHRoZSBlbGVtZW50CiAgICAgKi8KICAgIGZ1bmN0aW9uIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoY29udGFpbmVyLCB0YWdOYW1lLCBjbGFzc05hbWUsIGJlZm9yZSkgewogICAgICAgIGxldCBjaGlsZCA9IHNlbGVjdENoaWxkKGNvbnRhaW5lciwgdGFnTmFtZSwgY2xhc3NOYW1lKTsKICAgICAgICBpZiAoIWNoaWxkLmVtcHR5KCkpIHsKICAgICAgICAgICAgcmV0dXJuIGNoaWxkOwogICAgICAgIH0KICAgICAgICBsZXQgbmV3RWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygnaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnLCB0YWdOYW1lKTsKICAgICAgICBpZiAoY2xhc3NOYW1lIGluc3RhbmNlb2YgQXJyYXkpIHsKICAgICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBjbGFzc05hbWUubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIG5ld0VsZW1lbnQuY2xhc3NMaXN0LmFkZChjbGFzc05hbWVbaV0pOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBuZXdFbGVtZW50LmNsYXNzTGlzdC5hZGQoY2xhc3NOYW1lKTsKICAgICAgICB9CiAgICAgICAgaWYgKGJlZm9yZSkgewogICAgICAgICAgICAvLyBpZiBiZWZvcmUgZXhpc3RzLCBpbnNlcnQKICAgICAgICAgICAgY29udGFpbmVyLm5vZGUoKS5pbnNlcnRCZWZvcmUobmV3RWxlbWVudCwgYmVmb3JlKTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIC8vIG90aGVyd2lzZSwgYXBwZW5kCiAgICAgICAgICAgIGNvbnRhaW5lci5ub2RlKCkuYXBwZW5kQ2hpbGQobmV3RWxlbWVudCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiAoc2VsZWN0KG5ld0VsZW1lbnQpCiAgICAgICAgICAgIC8vIG5lZWQgdG8gYmluZCBkYXRhIHRvIGVtdWxhdGUgZDNfc2VsZWN0aW9uLmFwcGVuZAogICAgICAgICAgICAuZGF0dW0oY29udGFpbmVyLmRhdHVtKCkpKTsKICAgIH0KICAgIC8qKgogICAgICogRXhlY3V0aW9uIHN0YXRzIGZvciB0aGUgbm9kZS4KICAgICAqLwogICAgY2xhc3MgTm9kZVN0YXRzIHsKICAgICAgICBjb25zdHJ1Y3RvcihvdXRwdXRTaXplKSB7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBUb3RhbCBudW1iZXIgb2YgYnl0ZXMgdXNlZCBmb3IgdGhlIG5vZGUuIFN1bSBvZiBhbGwgY2hpbGRyZW4KICAgICAgICAgICAgICogaWYgaXQgaXMgYSBHcm91cCBub2RlLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy50b3RhbEJ5dGVzID0gMDsKICAgICAgICAgICAgdGhpcy5vdXRwdXRTaXplID0gb3V0cHV0U2l6ZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkIHRoZSBzdGFydCBhbmQgZW5kIHRpbWUgZm9yIGEgcGFydGljdWxhciBrZXJuZWwgZXhlY3V0aW9uIG9mIHRoaXMgb3AuCiAgICAgICAgICogT3BzIGNhbiBoYXZlIG11bHRpcGxlIGtlcm5lbCBleGVjdXRpb25zIHdpdGhpbiB0aGUgc2FtZSBzZXNzaW9uIHJ1bi4KICAgICAgICAgKi8KICAgICAgICBhZGRFeGVjdXRpb25UaW1lKHN0YXJ0VGltZSwgZW5kVGltZSkgewogICAgICAgICAgICBpZiAodGhpcy5zdGFydFRpbWUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5zdGFydFRpbWUgPSBNYXRoLm1pbih0aGlzLnN0YXJ0VGltZSwgc3RhcnRUaW1lKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuc3RhcnRUaW1lID0gc3RhcnRUaW1lOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLmVuZFRpbWUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgdGhpcy5lbmRUaW1lID0gTWF0aC5tYXgodGhpcy5lbmRUaW1lLCBlbmRUaW1lKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHRoaXMuZW5kVGltZSA9IGVuZFRpbWU7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkIHRoZSBieXRlcyBhbGxvY2F0ZWQgZm9yIGEgcGFydGljdWxhciBrZXJuZWwgZXhlY3V0aW9uIG9mIHRoaXMgb3AuCiAgICAgICAgICogT3BzIGNhbiBoYXZlIG11bHRpcGxlIGtlcm5lbCBleGVjdXRpb25zIHdpdGhpbiB0aGUgc2FtZSBzZXNzaW9uIHJ1bi4KICAgICAgICAgKi8KICAgICAgICBhZGRCeXRlc0FsbG9jYXRpb24odG90YWxCeXRlcykgewogICAgICAgICAgICBpZiAodGhpcy50b3RhbEJ5dGVzICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIHRoaXMudG90YWxCeXRlcyA9IE1hdGgubWF4KHRoaXMudG90YWxCeXRlcywgdG90YWxCeXRlcyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLnRvdGFsQnl0ZXMgPSB0b3RhbEJ5dGVzOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIENvbWJpbmVzIHRoZSBzcGVjaWZpZWQgc3RhdHMgd2l0aCB0aGUgY3VycmVudCBzdGF0cy4KICAgICAgICAgKiBNb2RpZmllcyB0aGUgY3VycmVudCBvYmplY3QuIFRoaXMgbWV0aG9kIGlzIHVzZWQgdG8KICAgICAgICAgKiBjb21wdXRlIGFnZ3JlZ2F0ZSBzdGF0cyBmb3IgZ3JvdXAgbm9kZXMuCiAgICAgICAgICovCiAgICAgICAgY29tYmluZShzdGF0cykgewogICAgICAgICAgICBpZiAoc3RhdHMudG90YWxCeXRlcyAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLnRvdGFsQnl0ZXMgKz0gc3RhdHMudG90YWxCeXRlczsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc3RhdHMuZ2V0VG90YWxNaWNyb3MoKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICB0aGlzLmFkZEV4ZWN1dGlvblRpbWUoc3RhdHMuc3RhcnRUaW1lLCBzdGF0cy5lbmRUaW1lKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBUb3RhbCBudW1iZXIgb2YgY29tcHV0ZSB0aW1lIGluIG1pY3Jvc2Vjb25kcyB1c2VkIGZvciB0aGUgbm9kZS4KICAgICAgICAgKiBTdW0gb2YgYWxsIGNoaWxkcmVuIGlmIGl0IGlzIGEgR3JvdXAgbm9kZS4gTnVsbCBpZiBpdCBpcyB1bmtub3duLgogICAgICAgICAqIFRoaXMgbWV0aG9kIGNhbiBub3QgYmUgc2NhZmZvbGRlZCB1bmRlciBhIGdldHRlciBhdHRyaWJ1dGUgYmVjYXVzZQogICAgICAgICAqIEVDTUFTY3JpcHQgNSBkb2VzIG5vdCBzdXBwb3J0IGdldHRlciBhdHRyaWJ1dGVzLgogICAgICAgICAqLwogICAgICAgIGdldFRvdGFsTWljcm9zKCkgewogICAgICAgICAgICBpZiAodGhpcy5zdGFydFRpbWUgPT0gbnVsbCB8fCB0aGlzLmVuZFRpbWUgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuZW5kVGltZSAtIHRoaXMuc3RhcnRUaW1lOwogICAgICAgIH0KICAgIH0KICAgIC8qKiBUaGUgbWluaW11bSBzdHJva2Ugd2lkdGggb2YgYW4gZWRnZS4gKi8KICAgIGNvbnN0IE1JTl9FREdFX1dJRFRIID0gMC43NTsKICAgIC8qKiBUaGUgbWF4aW11bSBzdHJva2Ugd2lkdGggb2YgYW4gZWRnZS4gKi8KICAgIGNvbnN0IE1BWF9FREdFX1dJRFRIID0gMTI7CiAgICAvKiogVGhlIGV4cG9uZW50IHVzZWQgaW4gdGhlIHBvd2VyIHNjYWxlIGZvciBlZGdlIHRoaWNrbmVzcy4gKi8KICAgIGNvbnN0IEVER0VfV0lEVEhfU0NBTEVfRVhQT05FTlQgPSAwLjM7CiAgICAvKiogVGhlIGRvbWFpbiAobWluIGFuZCBtYXggdmFsdWUpIGZvciB0aGUgZWRnZSB3aWR0aC4gKi8KICAgIGNvbnN0IERPTUFJTl9FREdFX1dJRFRIX1NDQUxFID0gWzEsIDUwMDAwMDBdOwogICAgY29uc3QgRURHRV9XSURUSF9TSVpFX0JBU0VEX1NDQUxFID0gcG93JDEoKQogICAgICAgIC5leHBvbmVudChFREdFX1dJRFRIX1NDQUxFX0VYUE9ORU5UKQogICAgICAgIC5kb21haW4oRE9NQUlOX0VER0VfV0lEVEhfU0NBTEUpCiAgICAgICAgLnJhbmdlKFtNSU5fRURHRV9XSURUSCwgTUFYX0VER0VfV0lEVEhdKQogICAgICAgIC5jbGFtcCh0cnVlKTsKCiAgICAvKioKICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIGxpc3QgY2FjaGUuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGNsZWFyCiAgICAgKiBAbWVtYmVyT2YgTGlzdENhY2hlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxpc3RDYWNoZUNsZWFyKCkgewogICAgICB0aGlzLl9fZGF0YV9fID0gW107CiAgICAgIHRoaXMuc2l6ZSA9IDA7CiAgICB9CgogICAgdmFyIF9saXN0Q2FjaGVDbGVhciA9IGxpc3RDYWNoZUNsZWFyOwoKICAgIC8qKgogICAgICogUGVyZm9ybXMgYQogICAgICogW2BTYW1lVmFsdWVaZXJvYF0oaHR0cDovL2VjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtc2FtZXZhbHVlemVybykKICAgICAqIGNvbXBhcmlzb24gYmV0d2VlbiB0d28gdmFsdWVzIHRvIGRldGVybWluZSBpZiB0aGV5IGFyZSBlcXVpdmFsZW50LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHsqfSBvdGhlciBUaGUgb3RoZXIgdmFsdWUgdG8gY29tcGFyZS4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgdmFsdWVzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSB9OwogICAgICogdmFyIG90aGVyID0geyAnYSc6IDEgfTsKICAgICAqCiAgICAgKiBfLmVxKG9iamVjdCwgb2JqZWN0KTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmVxKG9iamVjdCwgb3RoZXIpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmVxKCdhJywgJ2EnKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmVxKCdhJywgT2JqZWN0KCdhJykpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmVxKE5hTiwgTmFOKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqLwogICAgZnVuY3Rpb24gZXEodmFsdWUsIG90aGVyKSB7CiAgICAgIHJldHVybiB2YWx1ZSA9PT0gb3RoZXIgfHwgKHZhbHVlICE9PSB2YWx1ZSAmJiBvdGhlciAhPT0gb3RoZXIpOwogICAgfQoKICAgIHZhciBlcV8xID0gZXE7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBpbmRleCBhdCB3aGljaCB0aGUgYGtleWAgaXMgZm91bmQgaW4gYGFycmF5YCBvZiBrZXktdmFsdWUgcGFpcnMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICogQHBhcmFtIHsqfSBrZXkgVGhlIGtleSB0byBzZWFyY2ggZm9yLgogICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAqLwogICAgZnVuY3Rpb24gYXNzb2NJbmRleE9mKGFycmF5LCBrZXkpIHsKICAgICAgdmFyIGxlbmd0aCA9IGFycmF5Lmxlbmd0aDsKICAgICAgd2hpbGUgKGxlbmd0aC0tKSB7CiAgICAgICAgaWYgKGVxXzEoYXJyYXlbbGVuZ3RoXVswXSwga2V5KSkgewogICAgICAgICAgcmV0dXJuIGxlbmd0aDsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIC0xOwogICAgfQoKICAgIHZhciBfYXNzb2NJbmRleE9mID0gYXNzb2NJbmRleE9mOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBhcnJheVByb3RvID0gQXJyYXkucHJvdG90eXBlOwoKICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgdmFyIHNwbGljZSA9IGFycmF5UHJvdG8uc3BsaWNlOwoKICAgIC8qKgogICAgICogUmVtb3ZlcyBga2V5YCBhbmQgaXRzIHZhbHVlIGZyb20gdGhlIGxpc3QgY2FjaGUuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGRlbGV0ZQogICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byByZW1vdmUuCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIGVudHJ5IHdhcyByZW1vdmVkLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxpc3RDYWNoZURlbGV0ZShrZXkpIHsKICAgICAgdmFyIGRhdGEgPSB0aGlzLl9fZGF0YV9fLAogICAgICAgICAgaW5kZXggPSBfYXNzb2NJbmRleE9mKGRhdGEsIGtleSk7CgogICAgICBpZiAoaW5kZXggPCAwKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIHZhciBsYXN0SW5kZXggPSBkYXRhLmxlbmd0aCAtIDE7CiAgICAgIGlmIChpbmRleCA9PSBsYXN0SW5kZXgpIHsKICAgICAgICBkYXRhLnBvcCgpOwogICAgICB9IGVsc2UgewogICAgICAgIHNwbGljZS5jYWxsKGRhdGEsIGluZGV4LCAxKTsKICAgICAgfQogICAgICAtLXRoaXMuc2l6ZTsKICAgICAgcmV0dXJuIHRydWU7CiAgICB9CgogICAgdmFyIF9saXN0Q2FjaGVEZWxldGUgPSBsaXN0Q2FjaGVEZWxldGU7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBsaXN0IGNhY2hlIHZhbHVlIGZvciBga2V5YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgZ2V0CiAgICAgKiBAbWVtYmVyT2YgTGlzdENhY2hlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIGdldC4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBlbnRyeSB2YWx1ZS4KICAgICAqLwogICAgZnVuY3Rpb24gbGlzdENhY2hlR2V0KGtleSkgewogICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX18sCiAgICAgICAgICBpbmRleCA9IF9hc3NvY0luZGV4T2YoZGF0YSwga2V5KTsKCiAgICAgIHJldHVybiBpbmRleCA8IDAgPyB1bmRlZmluZWQgOiBkYXRhW2luZGV4XVsxXTsKICAgIH0KCiAgICB2YXIgX2xpc3RDYWNoZUdldCA9IGxpc3RDYWNoZUdldDsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBhIGxpc3QgY2FjaGUgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgaGFzCiAgICAgKiBAbWVtYmVyT2YgTGlzdENhY2hlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIGVudHJ5IHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGFuIGVudHJ5IGZvciBga2V5YCBleGlzdHMsIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gbGlzdENhY2hlSGFzKGtleSkgewogICAgICByZXR1cm4gX2Fzc29jSW5kZXhPZih0aGlzLl9fZGF0YV9fLCBrZXkpID4gLTE7CiAgICB9CgogICAgdmFyIF9saXN0Q2FjaGVIYXMgPSBsaXN0Q2FjaGVIYXM7CgogICAgLyoqCiAgICAgKiBTZXRzIHRoZSBsaXN0IGNhY2hlIGBrZXlgIHRvIGB2YWx1ZWAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIHNldAogICAgICogQG1lbWJlck9mIExpc3RDYWNoZQogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byBzZXQuCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBsaXN0IGNhY2hlIGluc3RhbmNlLgogICAgICovCiAgICBmdW5jdGlvbiBsaXN0Q2FjaGVTZXQoa2V5LCB2YWx1ZSkgewogICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX18sCiAgICAgICAgICBpbmRleCA9IF9hc3NvY0luZGV4T2YoZGF0YSwga2V5KTsKCiAgICAgIGlmIChpbmRleCA8IDApIHsKICAgICAgICArK3RoaXMuc2l6ZTsKICAgICAgICBkYXRhLnB1c2goW2tleSwgdmFsdWVdKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBkYXRhW2luZGV4XVsxXSA9IHZhbHVlOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIHZhciBfbGlzdENhY2hlU2V0ID0gbGlzdENhY2hlU2V0OwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBsaXN0IGNhY2hlIG9iamVjdC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbZW50cmllc10gVGhlIGtleS12YWx1ZSBwYWlycyB0byBjYWNoZS4KICAgICAqLwogICAgZnVuY3Rpb24gTGlzdENhY2hlKGVudHJpZXMpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBlbnRyaWVzID09IG51bGwgPyAwIDogZW50cmllcy5sZW5ndGg7CgogICAgICB0aGlzLmNsZWFyKCk7CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgdmFyIGVudHJ5ID0gZW50cmllc1tpbmRleF07CiAgICAgICAgdGhpcy5zZXQoZW50cnlbMF0sIGVudHJ5WzFdKTsKICAgICAgfQogICAgfQoKICAgIC8vIEFkZCBtZXRob2RzIHRvIGBMaXN0Q2FjaGVgLgogICAgTGlzdENhY2hlLnByb3RvdHlwZS5jbGVhciA9IF9saXN0Q2FjaGVDbGVhcjsKICAgIExpc3RDYWNoZS5wcm90b3R5cGVbJ2RlbGV0ZSddID0gX2xpc3RDYWNoZURlbGV0ZTsKICAgIExpc3RDYWNoZS5wcm90b3R5cGUuZ2V0ID0gX2xpc3RDYWNoZUdldDsKICAgIExpc3RDYWNoZS5wcm90b3R5cGUuaGFzID0gX2xpc3RDYWNoZUhhczsKICAgIExpc3RDYWNoZS5wcm90b3R5cGUuc2V0ID0gX2xpc3RDYWNoZVNldDsKCiAgICB2YXIgX0xpc3RDYWNoZSA9IExpc3RDYWNoZTsKCiAgICAvKioKICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIHN0YWNrLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAbmFtZSBjbGVhcgogICAgICogQG1lbWJlck9mIFN0YWNrCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0YWNrQ2xlYXIoKSB7CiAgICAgIHRoaXMuX19kYXRhX18gPSBuZXcgX0xpc3RDYWNoZTsKICAgICAgdGhpcy5zaXplID0gMDsKICAgIH0KCiAgICB2YXIgX3N0YWNrQ2xlYXIgPSBzdGFja0NsZWFyOwoKICAgIC8qKgogICAgICogUmVtb3ZlcyBga2V5YCBhbmQgaXRzIHZhbHVlIGZyb20gdGhlIHN0YWNrLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAbmFtZSBkZWxldGUKICAgICAqIEBtZW1iZXJPZiBTdGFjawogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byByZW1vdmUuCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIGVudHJ5IHdhcyByZW1vdmVkLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0YWNrRGVsZXRlKGtleSkgewogICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX18sCiAgICAgICAgICByZXN1bHQgPSBkYXRhWydkZWxldGUnXShrZXkpOwoKICAgICAgdGhpcy5zaXplID0gZGF0YS5zaXplOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfc3RhY2tEZWxldGUgPSBzdGFja0RlbGV0ZTsKCiAgICAvKioKICAgICAqIEdldHMgdGhlIHN0YWNrIHZhbHVlIGZvciBga2V5YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgZ2V0CiAgICAgKiBAbWVtYmVyT2YgU3RhY2sKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGVudHJ5IHZhbHVlLgogICAgICovCiAgICBmdW5jdGlvbiBzdGFja0dldChrZXkpIHsKICAgICAgcmV0dXJuIHRoaXMuX19kYXRhX18uZ2V0KGtleSk7CiAgICB9CgogICAgdmFyIF9zdGFja0dldCA9IHN0YWNrR2V0OwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGEgc3RhY2sgdmFsdWUgZm9yIGBrZXlgIGV4aXN0cy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgaGFzCiAgICAgKiBAbWVtYmVyT2YgU3RhY2sKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgZW50cnkgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYW4gZW50cnkgZm9yIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBzdGFja0hhcyhrZXkpIHsKICAgICAgcmV0dXJuIHRoaXMuX19kYXRhX18uaGFzKGtleSk7CiAgICB9CgogICAgdmFyIF9zdGFja0hhcyA9IHN0YWNrSGFzOwoKICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgZ2xvYmFsYCBmcm9tIE5vZGUuanMuICovCiAgICB2YXIgZnJlZUdsb2JhbCA9IHR5cGVvZiBjb21tb25qc0dsb2JhbCA9PSAnb2JqZWN0JyAmJiBjb21tb25qc0dsb2JhbCAmJiBjb21tb25qc0dsb2JhbC5PYmplY3QgPT09IE9iamVjdCAmJiBjb21tb25qc0dsb2JhbDsKCiAgICB2YXIgX2ZyZWVHbG9iYWwgPSBmcmVlR2xvYmFsOwoKICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgc2VsZmAuICovCiAgICB2YXIgZnJlZVNlbGYgPSB0eXBlb2Ygc2VsZiA9PSAnb2JqZWN0JyAmJiBzZWxmICYmIHNlbGYuT2JqZWN0ID09PSBPYmplY3QgJiYgc2VsZjsKCiAgICAvKiogVXNlZCBhcyBhIHJlZmVyZW5jZSB0byB0aGUgZ2xvYmFsIG9iamVjdC4gKi8KICAgIHZhciByb290JDkgPSBfZnJlZUdsb2JhbCB8fCBmcmVlU2VsZiB8fCBGdW5jdGlvbigncmV0dXJuIHRoaXMnKSgpOwoKICAgIHZhciBfcm9vdCA9IHJvb3QkOTsKCiAgICAvKiogQnVpbHQtaW4gdmFsdWUgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBTeW1ib2wkMSA9IF9yb290LlN5bWJvbDsKCiAgICB2YXIgX1N5bWJvbCA9IFN5bWJvbCQxOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byA9IE9iamVjdC5wcm90b3R5cGU7CgogICAgLyoqIFVzZWQgdG8gY2hlY2sgb2JqZWN0cyBmb3Igb3duIHByb3BlcnRpZXMuICovCiAgICB2YXIgaGFzT3duUHJvcGVydHkgPSBvYmplY3RQcm90by5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKioKICAgICAqIFVzZWQgdG8gcmVzb2x2ZSB0aGUKICAgICAqIFtgdG9TdHJpbmdUYWdgXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1vYmplY3QucHJvdG90eXBlLnRvc3RyaW5nKQogICAgICogb2YgdmFsdWVzLgogICAgICovCiAgICB2YXIgbmF0aXZlT2JqZWN0VG9TdHJpbmcgPSBvYmplY3RQcm90by50b1N0cmluZzsKCiAgICAvKiogQnVpbHQtaW4gdmFsdWUgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBzeW1Ub1N0cmluZ1RhZyA9IF9TeW1ib2wgPyBfU3ltYm9sLnRvU3RyaW5nVGFnIDogdW5kZWZpbmVkOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlR2V0VGFnYCB3aGljaCBpZ25vcmVzIGBTeW1ib2wudG9TdHJpbmdUYWdgIHZhbHVlcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSByYXcgYHRvU3RyaW5nVGFnYC4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0UmF3VGFnKHZhbHVlKSB7CiAgICAgIHZhciBpc093biA9IGhhc093blByb3BlcnR5LmNhbGwodmFsdWUsIHN5bVRvU3RyaW5nVGFnKSwKICAgICAgICAgIHRhZyA9IHZhbHVlW3N5bVRvU3RyaW5nVGFnXTsKCiAgICAgIHRyeSB7CiAgICAgICAgdmFsdWVbc3ltVG9TdHJpbmdUYWddID0gdW5kZWZpbmVkOwogICAgICAgIHZhciB1bm1hc2tlZCA9IHRydWU7CiAgICAgIH0gY2F0Y2ggKGUpIHt9CgogICAgICB2YXIgcmVzdWx0ID0gbmF0aXZlT2JqZWN0VG9TdHJpbmcuY2FsbCh2YWx1ZSk7CiAgICAgIGlmICh1bm1hc2tlZCkgewogICAgICAgIGlmIChpc093bikgewogICAgICAgICAgdmFsdWVbc3ltVG9TdHJpbmdUYWddID0gdGFnOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBkZWxldGUgdmFsdWVbc3ltVG9TdHJpbmdUYWddOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfZ2V0UmF3VGFnID0gZ2V0UmF3VGFnOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byQxID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKioKICAgICAqIFVzZWQgdG8gcmVzb2x2ZSB0aGUKICAgICAqIFtgdG9TdHJpbmdUYWdgXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1vYmplY3QucHJvdG90eXBlLnRvc3RyaW5nKQogICAgICogb2YgdmFsdWVzLgogICAgICovCiAgICB2YXIgbmF0aXZlT2JqZWN0VG9TdHJpbmckMSA9IG9iamVjdFByb3RvJDEudG9TdHJpbmc7CgogICAgLyoqCiAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGEgc3RyaW5nIHVzaW5nIGBPYmplY3QucHJvdG90eXBlLnRvU3RyaW5nYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBzdHJpbmcuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG9iamVjdFRvU3RyaW5nKHZhbHVlKSB7CiAgICAgIHJldHVybiBuYXRpdmVPYmplY3RUb1N0cmluZyQxLmNhbGwodmFsdWUpOwogICAgfQoKICAgIHZhciBfb2JqZWN0VG9TdHJpbmcgPSBvYmplY3RUb1N0cmluZzsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgbnVsbFRhZyA9ICdbb2JqZWN0IE51bGxdJywKICAgICAgICB1bmRlZmluZWRUYWcgPSAnW29iamVjdCBVbmRlZmluZWRdJzsKCiAgICAvKiogQnVpbHQtaW4gdmFsdWUgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBzeW1Ub1N0cmluZ1RhZyQxID0gX1N5bWJvbCA/IF9TeW1ib2wudG9TdHJpbmdUYWcgOiB1bmRlZmluZWQ7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgZ2V0VGFnYCB3aXRob3V0IGZhbGxiYWNrcyBmb3IgYnVnZ3kgZW52aXJvbm1lbnRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBxdWVyeS4KICAgICAqIEByZXR1cm5zIHtzdHJpbmd9IFJldHVybnMgdGhlIGB0b1N0cmluZ1RhZ2AuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VHZXRUYWcodmFsdWUpIHsKICAgICAgaWYgKHZhbHVlID09IG51bGwpIHsKICAgICAgICByZXR1cm4gdmFsdWUgPT09IHVuZGVmaW5lZCA/IHVuZGVmaW5lZFRhZyA6IG51bGxUYWc7CiAgICAgIH0KICAgICAgcmV0dXJuIChzeW1Ub1N0cmluZ1RhZyQxICYmIHN5bVRvU3RyaW5nVGFnJDEgaW4gT2JqZWN0KHZhbHVlKSkKICAgICAgICA/IF9nZXRSYXdUYWcodmFsdWUpCiAgICAgICAgOiBfb2JqZWN0VG9TdHJpbmcodmFsdWUpOwogICAgfQoKICAgIHZhciBfYmFzZUdldFRhZyA9IGJhc2VHZXRUYWc7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyB0aGUKICAgICAqIFtsYW5ndWFnZSB0eXBlXShodHRwOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtZWNtYXNjcmlwdC1sYW5ndWFnZS10eXBlcykKICAgICAqIG9mIGBPYmplY3RgLiAoZS5nLiBhcnJheXMsIGZ1bmN0aW9ucywgb2JqZWN0cywgcmVnZXhlcywgYG5ldyBOdW1iZXIoMClgLCBhbmQgYG5ldyBTdHJpbmcoJycpYCkKICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhbiBvYmplY3QsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc09iamVjdCh7fSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc09iamVjdChbMSwgMiwgM10pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNPYmplY3QoXy5ub29wKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzT2JqZWN0KG51bGwpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gaXNPYmplY3QodmFsdWUpIHsKICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgdmFsdWU7CiAgICAgIHJldHVybiB2YWx1ZSAhPSBudWxsICYmICh0eXBlID09ICdvYmplY3QnIHx8IHR5cGUgPT0gJ2Z1bmN0aW9uJyk7CiAgICB9CgogICAgdmFyIGlzT2JqZWN0XzEgPSBpc09iamVjdDsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgYXN5bmNUYWcgPSAnW29iamVjdCBBc3luY0Z1bmN0aW9uXScsCiAgICAgICAgZnVuY1RhZyA9ICdbb2JqZWN0IEZ1bmN0aW9uXScsCiAgICAgICAgZ2VuVGFnID0gJ1tvYmplY3QgR2VuZXJhdG9yRnVuY3Rpb25dJywKICAgICAgICBwcm94eVRhZyA9ICdbb2JqZWN0IFByb3h5XSc7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgYEZ1bmN0aW9uYCBvYmplY3QuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBmdW5jdGlvbiwgZWxzZSBgZmFsc2VgLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLmlzRnVuY3Rpb24oXyk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc0Z1bmN0aW9uKC9hYmMvKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzRnVuY3Rpb24odmFsdWUpIHsKICAgICAgaWYgKCFpc09iamVjdF8xKHZhbHVlKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICAvLyBUaGUgdXNlIG9mIGBPYmplY3QjdG9TdHJpbmdgIGF2b2lkcyBpc3N1ZXMgd2l0aCB0aGUgYHR5cGVvZmAgb3BlcmF0b3IKICAgICAgLy8gaW4gU2FmYXJpIDkgd2hpY2ggcmV0dXJucyAnb2JqZWN0JyBmb3IgdHlwZWQgYXJyYXlzIGFuZCBvdGhlciBjb25zdHJ1Y3RvcnMuCiAgICAgIHZhciB0YWcgPSBfYmFzZUdldFRhZyh2YWx1ZSk7CiAgICAgIHJldHVybiB0YWcgPT0gZnVuY1RhZyB8fCB0YWcgPT0gZ2VuVGFnIHx8IHRhZyA9PSBhc3luY1RhZyB8fCB0YWcgPT0gcHJveHlUYWc7CiAgICB9CgogICAgdmFyIGlzRnVuY3Rpb25fMSA9IGlzRnVuY3Rpb247CgogICAgLyoqIFVzZWQgdG8gZGV0ZWN0IG92ZXJyZWFjaGluZyBjb3JlLWpzIHNoaW1zLiAqLwogICAgdmFyIGNvcmVKc0RhdGEgPSBfcm9vdFsnX19jb3JlLWpzX3NoYXJlZF9fJ107CgogICAgdmFyIF9jb3JlSnNEYXRhID0gY29yZUpzRGF0YTsKCiAgICAvKiogVXNlZCB0byBkZXRlY3QgbWV0aG9kcyBtYXNxdWVyYWRpbmcgYXMgbmF0aXZlLiAqLwogICAgdmFyIG1hc2tTcmNLZXkgPSAoZnVuY3Rpb24oKSB7CiAgICAgIHZhciB1aWQgPSAvW14uXSskLy5leGVjKF9jb3JlSnNEYXRhICYmIF9jb3JlSnNEYXRhLmtleXMgJiYgX2NvcmVKc0RhdGEua2V5cy5JRV9QUk9UTyB8fCAnJyk7CiAgICAgIHJldHVybiB1aWQgPyAoJ1N5bWJvbChzcmMpXzEuJyArIHVpZCkgOiAnJzsKICAgIH0oKSk7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYGZ1bmNgIGhhcyBpdHMgc291cmNlIG1hc2tlZC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYGZ1bmNgIGlzIG1hc2tlZCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBpc01hc2tlZChmdW5jKSB7CiAgICAgIHJldHVybiAhIW1hc2tTcmNLZXkgJiYgKG1hc2tTcmNLZXkgaW4gZnVuYyk7CiAgICB9CgogICAgdmFyIF9pc01hc2tlZCA9IGlzTWFza2VkOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBmdW5jUHJvdG8gPSBGdW5jdGlvbi5wcm90b3R5cGU7CgogICAgLyoqIFVzZWQgdG8gcmVzb2x2ZSB0aGUgZGVjb21waWxlZCBzb3VyY2Ugb2YgZnVuY3Rpb25zLiAqLwogICAgdmFyIGZ1bmNUb1N0cmluZyA9IGZ1bmNQcm90by50b1N0cmluZzsKCiAgICAvKioKICAgICAqIENvbnZlcnRzIGBmdW5jYCB0byBpdHMgc291cmNlIGNvZGUuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNvbnZlcnQuCiAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBzb3VyY2UgY29kZS4KICAgICAqLwogICAgZnVuY3Rpb24gdG9Tb3VyY2UoZnVuYykgewogICAgICBpZiAoZnVuYyAhPSBudWxsKSB7CiAgICAgICAgdHJ5IHsKICAgICAgICAgIHJldHVybiBmdW5jVG9TdHJpbmcuY2FsbChmdW5jKTsKICAgICAgICB9IGNhdGNoIChlKSB7fQogICAgICAgIHRyeSB7CiAgICAgICAgICByZXR1cm4gKGZ1bmMgKyAnJyk7CiAgICAgICAgfSBjYXRjaCAoZSkge30KICAgICAgfQogICAgICByZXR1cm4gJyc7CiAgICB9CgogICAgdmFyIF90b1NvdXJjZSA9IHRvU291cmNlOwoKICAgIC8qKgogICAgICogVXNlZCB0byBtYXRjaCBgUmVnRXhwYAogICAgICogW3N5bnRheCBjaGFyYWN0ZXJzXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1wYXR0ZXJucykuCiAgICAgKi8KICAgIHZhciByZVJlZ0V4cENoYXIgPSAvW1xcXiQuKis/KClbXF17fXxdL2c7CgogICAgLyoqIFVzZWQgdG8gZGV0ZWN0IGhvc3QgY29uc3RydWN0b3JzIChTYWZhcmkpLiAqLwogICAgdmFyIHJlSXNIb3N0Q3RvciA9IC9eXFtvYmplY3QgLis/Q29uc3RydWN0b3JcXSQvOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBmdW5jUHJvdG8kMSA9IEZ1bmN0aW9uLnByb3RvdHlwZSwKICAgICAgICBvYmplY3RQcm90byQyID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogVXNlZCB0byByZXNvbHZlIHRoZSBkZWNvbXBpbGVkIHNvdXJjZSBvZiBmdW5jdGlvbnMuICovCiAgICB2YXIgZnVuY1RvU3RyaW5nJDEgPSBmdW5jUHJvdG8kMS50b1N0cmluZzsKCiAgICAvKiogVXNlZCB0byBjaGVjayBvYmplY3RzIGZvciBvd24gcHJvcGVydGllcy4gKi8KICAgIHZhciBoYXNPd25Qcm9wZXJ0eSQxID0gb2JqZWN0UHJvdG8kMi5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKiogVXNlZCB0byBkZXRlY3QgaWYgYSBtZXRob2QgaXMgbmF0aXZlLiAqLwogICAgdmFyIHJlSXNOYXRpdmUgPSBSZWdFeHAoJ14nICsKICAgICAgZnVuY1RvU3RyaW5nJDEuY2FsbChoYXNPd25Qcm9wZXJ0eSQxKS5yZXBsYWNlKHJlUmVnRXhwQ2hhciwgJ1xcJCYnKQogICAgICAucmVwbGFjZSgvaGFzT3duUHJvcGVydHl8KGZ1bmN0aW9uKS4qPyg/PVxcXCgpfCBmb3IgLis/KD89XFxcXSkvZywgJyQxLio/JykgKyAnJCcKICAgICk7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc05hdGl2ZWAgd2l0aG91dCBiYWQgc2hpbSBjaGVja3MuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBuYXRpdmUgZnVuY3Rpb24sCiAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlSXNOYXRpdmUodmFsdWUpIHsKICAgICAgaWYgKCFpc09iamVjdF8xKHZhbHVlKSB8fCBfaXNNYXNrZWQodmFsdWUpKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIHZhciBwYXR0ZXJuID0gaXNGdW5jdGlvbl8xKHZhbHVlKSA/IHJlSXNOYXRpdmUgOiByZUlzSG9zdEN0b3I7CiAgICAgIHJldHVybiBwYXR0ZXJuLnRlc3QoX3RvU291cmNlKHZhbHVlKSk7CiAgICB9CgogICAgdmFyIF9iYXNlSXNOYXRpdmUgPSBiYXNlSXNOYXRpdmU7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSB2YWx1ZSBhdCBga2V5YCBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3RdIFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBwcm9wZXJ0eSB2YWx1ZS4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0VmFsdWUob2JqZWN0LCBrZXkpIHsKICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8gdW5kZWZpbmVkIDogb2JqZWN0W2tleV07CiAgICB9CgogICAgdmFyIF9nZXRWYWx1ZSA9IGdldFZhbHVlOwoKICAgIC8qKgogICAgICogR2V0cyB0aGUgbmF0aXZlIGZ1bmN0aW9uIGF0IGBrZXlgIG9mIGBvYmplY3RgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIG1ldGhvZCB0byBnZXQuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgZnVuY3Rpb24gaWYgaXQncyBuYXRpdmUsIGVsc2UgYHVuZGVmaW5lZGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldE5hdGl2ZShvYmplY3QsIGtleSkgewogICAgICB2YXIgdmFsdWUgPSBfZ2V0VmFsdWUob2JqZWN0LCBrZXkpOwogICAgICByZXR1cm4gX2Jhc2VJc05hdGl2ZSh2YWx1ZSkgPyB2YWx1ZSA6IHVuZGVmaW5lZDsKICAgIH0KCiAgICB2YXIgX2dldE5hdGl2ZSA9IGdldE5hdGl2ZTsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyB0aGF0IGFyZSB2ZXJpZmllZCB0byBiZSBuYXRpdmUuICovCiAgICB2YXIgTWFwJDUgPSBfZ2V0TmF0aXZlKF9yb290LCAnTWFwJyk7CgogICAgdmFyIF9NYXAgPSBNYXAkNTsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyB0aGF0IGFyZSB2ZXJpZmllZCB0byBiZSBuYXRpdmUuICovCiAgICB2YXIgbmF0aXZlQ3JlYXRlID0gX2dldE5hdGl2ZShPYmplY3QsICdjcmVhdGUnKTsKCiAgICB2YXIgX25hdGl2ZUNyZWF0ZSA9IG5hdGl2ZUNyZWF0ZTsKCiAgICAvKioKICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIGhhc2guCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGNsZWFyCiAgICAgKiBAbWVtYmVyT2YgSGFzaAogICAgICovCiAgICBmdW5jdGlvbiBoYXNoQ2xlYXIoKSB7CiAgICAgIHRoaXMuX19kYXRhX18gPSBfbmF0aXZlQ3JlYXRlID8gX25hdGl2ZUNyZWF0ZShudWxsKSA6IHt9OwogICAgICB0aGlzLnNpemUgPSAwOwogICAgfQoKICAgIHZhciBfaGFzaENsZWFyID0gaGFzaENsZWFyOwoKICAgIC8qKgogICAgICogUmVtb3ZlcyBga2V5YCBhbmQgaXRzIHZhbHVlIGZyb20gdGhlIGhhc2guCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGRlbGV0ZQogICAgICogQG1lbWJlck9mIEhhc2gKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBoYXNoIFRoZSBoYXNoIHRvIG1vZGlmeS4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gcmVtb3ZlLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBlbnRyeSB3YXMgcmVtb3ZlZCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBoYXNoRGVsZXRlKGtleSkgewogICAgICB2YXIgcmVzdWx0ID0gdGhpcy5oYXMoa2V5KSAmJiBkZWxldGUgdGhpcy5fX2RhdGFfX1trZXldOwogICAgICB0aGlzLnNpemUgLT0gcmVzdWx0ID8gMSA6IDA7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9oYXNoRGVsZXRlID0gaGFzaERlbGV0ZTsKCiAgICAvKiogVXNlZCB0byBzdGFuZC1pbiBmb3IgYHVuZGVmaW5lZGAgaGFzaCB2YWx1ZXMuICovCiAgICB2YXIgSEFTSF9VTkRFRklORUQgPSAnX19sb2Rhc2hfaGFzaF91bmRlZmluZWRfXyc7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJDMgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JDIgPSBvYmplY3RQcm90byQzLmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogR2V0cyB0aGUgaGFzaCB2YWx1ZSBmb3IgYGtleWAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGdldAogICAgICogQG1lbWJlck9mIEhhc2gKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGVudHJ5IHZhbHVlLgogICAgICovCiAgICBmdW5jdGlvbiBoYXNoR2V0KGtleSkgewogICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX187CiAgICAgIGlmIChfbmF0aXZlQ3JlYXRlKSB7CiAgICAgICAgdmFyIHJlc3VsdCA9IGRhdGFba2V5XTsKICAgICAgICByZXR1cm4gcmVzdWx0ID09PSBIQVNIX1VOREVGSU5FRCA/IHVuZGVmaW5lZCA6IHJlc3VsdDsKICAgICAgfQogICAgICByZXR1cm4gaGFzT3duUHJvcGVydHkkMi5jYWxsKGRhdGEsIGtleSkgPyBkYXRhW2tleV0gOiB1bmRlZmluZWQ7CiAgICB9CgogICAgdmFyIF9oYXNoR2V0ID0gaGFzaEdldDsKCiAgICAvKiogVXNlZCBmb3IgYnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMuICovCiAgICB2YXIgb2JqZWN0UHJvdG8kNCA9IE9iamVjdC5wcm90b3R5cGU7CgogICAgLyoqIFVzZWQgdG8gY2hlY2sgb2JqZWN0cyBmb3Igb3duIHByb3BlcnRpZXMuICovCiAgICB2YXIgaGFzT3duUHJvcGVydHkkMyA9IG9iamVjdFByb3RvJDQuaGFzT3duUHJvcGVydHk7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYSBoYXNoIHZhbHVlIGZvciBga2V5YCBleGlzdHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGhhcwogICAgICogQG1lbWJlck9mIEhhc2gKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgZW50cnkgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYW4gZW50cnkgZm9yIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBoYXNoSGFzKGtleSkgewogICAgICB2YXIgZGF0YSA9IHRoaXMuX19kYXRhX187CiAgICAgIHJldHVybiBfbmF0aXZlQ3JlYXRlID8gKGRhdGFba2V5XSAhPT0gdW5kZWZpbmVkKSA6IGhhc093blByb3BlcnR5JDMuY2FsbChkYXRhLCBrZXkpOwogICAgfQoKICAgIHZhciBfaGFzaEhhcyA9IGhhc2hIYXM7CgogICAgLyoqIFVzZWQgdG8gc3RhbmQtaW4gZm9yIGB1bmRlZmluZWRgIGhhc2ggdmFsdWVzLiAqLwogICAgdmFyIEhBU0hfVU5ERUZJTkVEJDEgPSAnX19sb2Rhc2hfaGFzaF91bmRlZmluZWRfXyc7CgogICAgLyoqCiAgICAgKiBTZXRzIHRoZSBoYXNoIGBrZXlgIHRvIGB2YWx1ZWAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIHNldAogICAgICogQG1lbWJlck9mIEhhc2gKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gc2V0LgogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0LgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgaGFzaCBpbnN0YW5jZS4KICAgICAqLwogICAgZnVuY3Rpb24gaGFzaFNldChrZXksIHZhbHVlKSB7CiAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXzsKICAgICAgdGhpcy5zaXplICs9IHRoaXMuaGFzKGtleSkgPyAwIDogMTsKICAgICAgZGF0YVtrZXldID0gKF9uYXRpdmVDcmVhdGUgJiYgdmFsdWUgPT09IHVuZGVmaW5lZCkgPyBIQVNIX1VOREVGSU5FRCQxIDogdmFsdWU7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIHZhciBfaGFzaFNldCA9IGhhc2hTZXQ7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgaGFzaCBvYmplY3QuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBjb25zdHJ1Y3RvcgogICAgICogQHBhcmFtIHtBcnJheX0gW2VudHJpZXNdIFRoZSBrZXktdmFsdWUgcGFpcnMgdG8gY2FjaGUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIEhhc2goZW50cmllcykgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IGVudHJpZXMgPT0gbnVsbCA/IDAgOiBlbnRyaWVzLmxlbmd0aDsKCiAgICAgIHRoaXMuY2xlYXIoKTsKICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICB2YXIgZW50cnkgPSBlbnRyaWVzW2luZGV4XTsKICAgICAgICB0aGlzLnNldChlbnRyeVswXSwgZW50cnlbMV0pOwogICAgICB9CiAgICB9CgogICAgLy8gQWRkIG1ldGhvZHMgdG8gYEhhc2hgLgogICAgSGFzaC5wcm90b3R5cGUuY2xlYXIgPSBfaGFzaENsZWFyOwogICAgSGFzaC5wcm90b3R5cGVbJ2RlbGV0ZSddID0gX2hhc2hEZWxldGU7CiAgICBIYXNoLnByb3RvdHlwZS5nZXQgPSBfaGFzaEdldDsKICAgIEhhc2gucHJvdG90eXBlLmhhcyA9IF9oYXNoSGFzOwogICAgSGFzaC5wcm90b3R5cGUuc2V0ID0gX2hhc2hTZXQ7CgogICAgdmFyIF9IYXNoID0gSGFzaDsKCiAgICAvKioKICAgICAqIFJlbW92ZXMgYWxsIGtleS12YWx1ZSBlbnRyaWVzIGZyb20gdGhlIG1hcC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgY2xlYXIKICAgICAqIEBtZW1iZXJPZiBNYXBDYWNoZQogICAgICovCiAgICBmdW5jdGlvbiBtYXBDYWNoZUNsZWFyKCkgewogICAgICB0aGlzLnNpemUgPSAwOwogICAgICB0aGlzLl9fZGF0YV9fID0gewogICAgICAgICdoYXNoJzogbmV3IF9IYXNoLAogICAgICAgICdtYXAnOiBuZXcgKF9NYXAgfHwgX0xpc3RDYWNoZSksCiAgICAgICAgJ3N0cmluZyc6IG5ldyBfSGFzaAogICAgICB9OwogICAgfQoKICAgIHZhciBfbWFwQ2FjaGVDbGVhciA9IG1hcENhY2hlQ2xlYXI7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBzdWl0YWJsZSBmb3IgdXNlIGFzIHVuaXF1ZSBvYmplY3Qga2V5LgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIHN1aXRhYmxlLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzS2V5YWJsZSh2YWx1ZSkgewogICAgICB2YXIgdHlwZSA9IHR5cGVvZiB2YWx1ZTsKICAgICAgcmV0dXJuICh0eXBlID09ICdzdHJpbmcnIHx8IHR5cGUgPT0gJ251bWJlcicgfHwgdHlwZSA9PSAnc3ltYm9sJyB8fCB0eXBlID09ICdib29sZWFuJykKICAgICAgICA/ICh2YWx1ZSAhPT0gJ19fcHJvdG9fXycpCiAgICAgICAgOiAodmFsdWUgPT09IG51bGwpOwogICAgfQoKICAgIHZhciBfaXNLZXlhYmxlID0gaXNLZXlhYmxlOwoKICAgIC8qKgogICAgICogR2V0cyB0aGUgZGF0YSBmb3IgYG1hcGAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBtYXAgVGhlIG1hcCB0byBxdWVyeS4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIHJlZmVyZW5jZSBrZXkuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWFwIGRhdGEuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldE1hcERhdGEobWFwLCBrZXkpIHsKICAgICAgdmFyIGRhdGEgPSBtYXAuX19kYXRhX187CiAgICAgIHJldHVybiBfaXNLZXlhYmxlKGtleSkKICAgICAgICA/IGRhdGFbdHlwZW9mIGtleSA9PSAnc3RyaW5nJyA/ICdzdHJpbmcnIDogJ2hhc2gnXQogICAgICAgIDogZGF0YS5tYXA7CiAgICB9CgogICAgdmFyIF9nZXRNYXBEYXRhID0gZ2V0TWFwRGF0YTsKCiAgICAvKioKICAgICAqIFJlbW92ZXMgYGtleWAgYW5kIGl0cyB2YWx1ZSBmcm9tIHRoZSBtYXAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGRlbGV0ZQogICAgICogQG1lbWJlck9mIE1hcENhY2hlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHZhbHVlIHRvIHJlbW92ZS4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgZW50cnkgd2FzIHJlbW92ZWQsIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gbWFwQ2FjaGVEZWxldGUoa2V5KSB7CiAgICAgIHZhciByZXN1bHQgPSBfZ2V0TWFwRGF0YSh0aGlzLCBrZXkpWydkZWxldGUnXShrZXkpOwogICAgICB0aGlzLnNpemUgLT0gcmVzdWx0ID8gMSA6IDA7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9tYXBDYWNoZURlbGV0ZSA9IG1hcENhY2hlRGVsZXRlOwoKICAgIC8qKgogICAgICogR2V0cyB0aGUgbWFwIHZhbHVlIGZvciBga2V5YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgZ2V0CiAgICAgKiBAbWVtYmVyT2YgTWFwQ2FjaGUKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gZ2V0LgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGVudHJ5IHZhbHVlLgogICAgICovCiAgICBmdW5jdGlvbiBtYXBDYWNoZUdldChrZXkpIHsKICAgICAgcmV0dXJuIF9nZXRNYXBEYXRhKHRoaXMsIGtleSkuZ2V0KGtleSk7CiAgICB9CgogICAgdmFyIF9tYXBDYWNoZUdldCA9IG1hcENhY2hlR2V0OwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGEgbWFwIHZhbHVlIGZvciBga2V5YCBleGlzdHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBuYW1lIGhhcwogICAgICogQG1lbWJlck9mIE1hcENhY2hlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIGVudHJ5IHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGFuIGVudHJ5IGZvciBga2V5YCBleGlzdHMsIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gbWFwQ2FjaGVIYXMoa2V5KSB7CiAgICAgIHJldHVybiBfZ2V0TWFwRGF0YSh0aGlzLCBrZXkpLmhhcyhrZXkpOwogICAgfQoKICAgIHZhciBfbWFwQ2FjaGVIYXMgPSBtYXBDYWNoZUhhczsKCiAgICAvKioKICAgICAqIFNldHMgdGhlIG1hcCBga2V5YCB0byBgdmFsdWVgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAbmFtZSBzZXQKICAgICAqIEBtZW1iZXJPZiBNYXBDYWNoZQogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byBzZXQuCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZXQuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBtYXAgY2FjaGUgaW5zdGFuY2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG1hcENhY2hlU2V0KGtleSwgdmFsdWUpIHsKICAgICAgdmFyIGRhdGEgPSBfZ2V0TWFwRGF0YSh0aGlzLCBrZXkpLAogICAgICAgICAgc2l6ZSA9IGRhdGEuc2l6ZTsKCiAgICAgIGRhdGEuc2V0KGtleSwgdmFsdWUpOwogICAgICB0aGlzLnNpemUgKz0gZGF0YS5zaXplID09IHNpemUgPyAwIDogMTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgdmFyIF9tYXBDYWNoZVNldCA9IG1hcENhY2hlU2V0OwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIG1hcCBjYWNoZSBvYmplY3QgdG8gc3RvcmUga2V5LXZhbHVlIHBhaXJzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAY29uc3RydWN0b3IKICAgICAqIEBwYXJhbSB7QXJyYXl9IFtlbnRyaWVzXSBUaGUga2V5LXZhbHVlIHBhaXJzIHRvIGNhY2hlLgogICAgICovCiAgICBmdW5jdGlvbiBNYXBDYWNoZShlbnRyaWVzKSB7CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gZW50cmllcyA9PSBudWxsID8gMCA6IGVudHJpZXMubGVuZ3RoOwoKICAgICAgdGhpcy5jbGVhcigpOwogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHZhciBlbnRyeSA9IGVudHJpZXNbaW5kZXhdOwogICAgICAgIHRoaXMuc2V0KGVudHJ5WzBdLCBlbnRyeVsxXSk7CiAgICAgIH0KICAgIH0KCiAgICAvLyBBZGQgbWV0aG9kcyB0byBgTWFwQ2FjaGVgLgogICAgTWFwQ2FjaGUucHJvdG90eXBlLmNsZWFyID0gX21hcENhY2hlQ2xlYXI7CiAgICBNYXBDYWNoZS5wcm90b3R5cGVbJ2RlbGV0ZSddID0gX21hcENhY2hlRGVsZXRlOwogICAgTWFwQ2FjaGUucHJvdG90eXBlLmdldCA9IF9tYXBDYWNoZUdldDsKICAgIE1hcENhY2hlLnByb3RvdHlwZS5oYXMgPSBfbWFwQ2FjaGVIYXM7CiAgICBNYXBDYWNoZS5wcm90b3R5cGUuc2V0ID0gX21hcENhY2hlU2V0OwoKICAgIHZhciBfTWFwQ2FjaGUgPSBNYXBDYWNoZTsKCiAgICAvKiogVXNlZCBhcyB0aGUgc2l6ZSB0byBlbmFibGUgbGFyZ2UgYXJyYXkgb3B0aW1pemF0aW9ucy4gKi8KICAgIHZhciBMQVJHRV9BUlJBWV9TSVpFID0gMjAwOwoKICAgIC8qKgogICAgICogU2V0cyB0aGUgc3RhY2sgYGtleWAgdG8gYHZhbHVlYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQG5hbWUgc2V0CiAgICAgKiBAbWVtYmVyT2YgU3RhY2sKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgdmFsdWUgdG8gc2V0LgogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0LgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgc3RhY2sgY2FjaGUgaW5zdGFuY2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN0YWNrU2V0KGtleSwgdmFsdWUpIHsKICAgICAgdmFyIGRhdGEgPSB0aGlzLl9fZGF0YV9fOwogICAgICBpZiAoZGF0YSBpbnN0YW5jZW9mIF9MaXN0Q2FjaGUpIHsKICAgICAgICB2YXIgcGFpcnMgPSBkYXRhLl9fZGF0YV9fOwogICAgICAgIGlmICghX01hcCB8fCAocGFpcnMubGVuZ3RoIDwgTEFSR0VfQVJSQVlfU0laRSAtIDEpKSB7CiAgICAgICAgICBwYWlycy5wdXNoKFtrZXksIHZhbHVlXSk7CiAgICAgICAgICB0aGlzLnNpemUgPSArK2RhdGEuc2l6ZTsKICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgIH0KICAgICAgICBkYXRhID0gdGhpcy5fX2RhdGFfXyA9IG5ldyBfTWFwQ2FjaGUocGFpcnMpOwogICAgICB9CiAgICAgIGRhdGEuc2V0KGtleSwgdmFsdWUpOwogICAgICB0aGlzLnNpemUgPSBkYXRhLnNpemU7CiAgICAgIHJldHVybiB0aGlzOwogICAgfQoKICAgIHZhciBfc3RhY2tTZXQgPSBzdGFja1NldDsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBzdGFjayBjYWNoZSBvYmplY3QgdG8gc3RvcmUga2V5LXZhbHVlIHBhaXJzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAY29uc3RydWN0b3IKICAgICAqIEBwYXJhbSB7QXJyYXl9IFtlbnRyaWVzXSBUaGUga2V5LXZhbHVlIHBhaXJzIHRvIGNhY2hlLgogICAgICovCiAgICBmdW5jdGlvbiBTdGFjayhlbnRyaWVzKSB7CiAgICAgIHZhciBkYXRhID0gdGhpcy5fX2RhdGFfXyA9IG5ldyBfTGlzdENhY2hlKGVudHJpZXMpOwogICAgICB0aGlzLnNpemUgPSBkYXRhLnNpemU7CiAgICB9CgogICAgLy8gQWRkIG1ldGhvZHMgdG8gYFN0YWNrYC4KICAgIFN0YWNrLnByb3RvdHlwZS5jbGVhciA9IF9zdGFja0NsZWFyOwogICAgU3RhY2sucHJvdG90eXBlWydkZWxldGUnXSA9IF9zdGFja0RlbGV0ZTsKICAgIFN0YWNrLnByb3RvdHlwZS5nZXQgPSBfc3RhY2tHZXQ7CiAgICBTdGFjay5wcm90b3R5cGUuaGFzID0gX3N0YWNrSGFzOwogICAgU3RhY2sucHJvdG90eXBlLnNldCA9IF9zdGFja1NldDsKCiAgICB2YXIgX1N0YWNrID0gU3RhY2s7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uZm9yRWFjaGAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yCiAgICAgKiBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIGBhcnJheWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFycmF5RWFjaChhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKCiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgaWYgKGl0ZXJhdGVlKGFycmF5W2luZGV4XSwgaW5kZXgsIGFycmF5KSA9PT0gZmFsc2UpIHsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gYXJyYXk7CiAgICB9CgogICAgdmFyIF9hcnJheUVhY2ggPSBhcnJheUVhY2g7CgogICAgdmFyIGRlZmluZVByb3BlcnR5ID0gKGZ1bmN0aW9uKCkgewogICAgICB0cnkgewogICAgICAgIHZhciBmdW5jID0gX2dldE5hdGl2ZShPYmplY3QsICdkZWZpbmVQcm9wZXJ0eScpOwogICAgICAgIGZ1bmMoe30sICcnLCB7fSk7CiAgICAgICAgcmV0dXJuIGZ1bmM7CiAgICAgIH0gY2F0Y2ggKGUpIHt9CiAgICB9KCkpOwoKICAgIHZhciBfZGVmaW5lUHJvcGVydHkgPSBkZWZpbmVQcm9wZXJ0eTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBhc3NpZ25WYWx1ZWAgYW5kIGBhc3NpZ25NZXJnZVZhbHVlYCB3aXRob3V0CiAgICAgKiB2YWx1ZSBjaGVja3MuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIGFzc2lnbi4KICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGFzc2lnbi4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCB2YWx1ZSkgewogICAgICBpZiAoa2V5ID09ICdfX3Byb3RvX18nICYmIF9kZWZpbmVQcm9wZXJ0eSkgewogICAgICAgIF9kZWZpbmVQcm9wZXJ0eShvYmplY3QsIGtleSwgewogICAgICAgICAgJ2NvbmZpZ3VyYWJsZSc6IHRydWUsCiAgICAgICAgICAnZW51bWVyYWJsZSc6IHRydWUsCiAgICAgICAgICAndmFsdWUnOiB2YWx1ZSwKICAgICAgICAgICd3cml0YWJsZSc6IHRydWUKICAgICAgICB9KTsKICAgICAgfSBlbHNlIHsKICAgICAgICBvYmplY3Rba2V5XSA9IHZhbHVlOwogICAgICB9CiAgICB9CgogICAgdmFyIF9iYXNlQXNzaWduVmFsdWUgPSBiYXNlQXNzaWduVmFsdWU7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJDUgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JDQgPSBvYmplY3RQcm90byQ1Lmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogQXNzaWducyBgdmFsdWVgIHRvIGBrZXlgIG9mIGBvYmplY3RgIGlmIHRoZSBleGlzdGluZyB2YWx1ZSBpcyBub3QgZXF1aXZhbGVudAogICAgICogdXNpbmcgW2BTYW1lVmFsdWVaZXJvYF0oaHR0cDovL2VjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtc2FtZXZhbHVlemVybykKICAgICAqIGZvciBlcXVhbGl0eSBjb21wYXJpc29ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIG1vZGlmeS4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgcHJvcGVydHkgdG8gYXNzaWduLgogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gYXNzaWduLgogICAgICovCiAgICBmdW5jdGlvbiBhc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgdmFsdWUpIHsKICAgICAgdmFyIG9ialZhbHVlID0gb2JqZWN0W2tleV07CiAgICAgIGlmICghKGhhc093blByb3BlcnR5JDQuY2FsbChvYmplY3QsIGtleSkgJiYgZXFfMShvYmpWYWx1ZSwgdmFsdWUpKSB8fAogICAgICAgICAgKHZhbHVlID09PSB1bmRlZmluZWQgJiYgIShrZXkgaW4gb2JqZWN0KSkpIHsKICAgICAgICBfYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCB2YWx1ZSk7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgX2Fzc2lnblZhbHVlID0gYXNzaWduVmFsdWU7CgogICAgLyoqCiAgICAgKiBDb3BpZXMgcHJvcGVydGllcyBvZiBgc291cmNlYCB0byBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IHRvIGNvcHkgcHJvcGVydGllcyBmcm9tLgogICAgICogQHBhcmFtIHtBcnJheX0gcHJvcHMgVGhlIHByb3BlcnR5IGlkZW50aWZpZXJzIHRvIGNvcHkuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gW29iamVjdD17fV0gVGhlIG9iamVjdCB0byBjb3B5IHByb3BlcnRpZXMgdG8uCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb3BpZWQgdmFsdWVzLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAqLwogICAgZnVuY3Rpb24gY29weU9iamVjdChzb3VyY2UsIHByb3BzLCBvYmplY3QsIGN1c3RvbWl6ZXIpIHsKICAgICAgdmFyIGlzTmV3ID0gIW9iamVjdDsKICAgICAgb2JqZWN0IHx8IChvYmplY3QgPSB7fSk7CgogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IHByb3BzLmxlbmd0aDsKCiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgdmFyIGtleSA9IHByb3BzW2luZGV4XTsKCiAgICAgICAgdmFyIG5ld1ZhbHVlID0gY3VzdG9taXplcgogICAgICAgICAgPyBjdXN0b21pemVyKG9iamVjdFtrZXldLCBzb3VyY2Vba2V5XSwga2V5LCBvYmplY3QsIHNvdXJjZSkKICAgICAgICAgIDogdW5kZWZpbmVkOwoKICAgICAgICBpZiAobmV3VmFsdWUgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgbmV3VmFsdWUgPSBzb3VyY2Vba2V5XTsKICAgICAgICB9CiAgICAgICAgaWYgKGlzTmV3KSB7CiAgICAgICAgICBfYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCBuZXdWYWx1ZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIF9hc3NpZ25WYWx1ZShvYmplY3QsIGtleSwgbmV3VmFsdWUpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gb2JqZWN0OwogICAgfQoKICAgIHZhciBfY29weU9iamVjdCA9IGNvcHlPYmplY3Q7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy50aW1lc2Agd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzCiAgICAgKiBvciBtYXggYXJyYXkgbGVuZ3RoIGNoZWNrcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtudW1iZXJ9IG4gVGhlIG51bWJlciBvZiB0aW1lcyB0byBpbnZva2UgYGl0ZXJhdGVlYC4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHJlc3VsdHMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VUaW1lcyhuLCBpdGVyYXRlZSkgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIHJlc3VsdCA9IEFycmF5KG4pOwoKICAgICAgd2hpbGUgKCsraW5kZXggPCBuKSB7CiAgICAgICAgcmVzdWx0W2luZGV4XSA9IGl0ZXJhdGVlKGluZGV4KTsKICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZVRpbWVzID0gYmFzZVRpbWVzOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgb2JqZWN0LWxpa2UuIEEgdmFsdWUgaXMgb2JqZWN0LWxpa2UgaWYgaXQncyBub3QgYG51bGxgCiAgICAgKiBhbmQgaGFzIGEgYHR5cGVvZmAgcmVzdWx0IG9mICJvYmplY3QiLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIG9iamVjdC1saWtlLCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNPYmplY3RMaWtlKHt9KTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzT2JqZWN0TGlrZShbMSwgMiwgM10pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNPYmplY3RMaWtlKF8ubm9vcCk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICoKICAgICAqIF8uaXNPYmplY3RMaWtlKG51bGwpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gaXNPYmplY3RMaWtlKHZhbHVlKSB7CiAgICAgIHJldHVybiB2YWx1ZSAhPSBudWxsICYmIHR5cGVvZiB2YWx1ZSA9PSAnb2JqZWN0JzsKICAgIH0KCiAgICB2YXIgaXNPYmplY3RMaWtlXzEgPSBpc09iamVjdExpa2U7CgogICAgLyoqIGBPYmplY3QjdG9TdHJpbmdgIHJlc3VsdCByZWZlcmVuY2VzLiAqLwogICAgdmFyIGFyZ3NUYWcgPSAnW29iamVjdCBBcmd1bWVudHNdJzsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmlzQXJndW1lbnRzYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhbiBgYXJndW1lbnRzYCBvYmplY3QsCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc0FyZ3VtZW50cyh2YWx1ZSkgewogICAgICByZXR1cm4gaXNPYmplY3RMaWtlXzEodmFsdWUpICYmIF9iYXNlR2V0VGFnKHZhbHVlKSA9PSBhcmdzVGFnOwogICAgfQoKICAgIHZhciBfYmFzZUlzQXJndW1lbnRzID0gYmFzZUlzQXJndW1lbnRzOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byQ2ID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogVXNlZCB0byBjaGVjayBvYmplY3RzIGZvciBvd24gcHJvcGVydGllcy4gKi8KICAgIHZhciBoYXNPd25Qcm9wZXJ0eSQ1ID0gb2JqZWN0UHJvdG8kNi5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKiogQnVpbHQtaW4gdmFsdWUgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBwcm9wZXJ0eUlzRW51bWVyYWJsZSA9IG9iamVjdFByb3RvJDYucHJvcGVydHlJc0VudW1lcmFibGU7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBsaWtlbHkgYW4gYGFyZ3VtZW50c2Agb2JqZWN0LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGFuIGBhcmd1bWVudHNgIG9iamVjdCwKICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNBcmd1bWVudHMoZnVuY3Rpb24oKSB7IHJldHVybiBhcmd1bWVudHM7IH0oKSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc0FyZ3VtZW50cyhbMSwgMiwgM10pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgdmFyIGlzQXJndW1lbnRzID0gX2Jhc2VJc0FyZ3VtZW50cyhmdW5jdGlvbigpIHsgcmV0dXJuIGFyZ3VtZW50czsgfSgpKSA/IF9iYXNlSXNBcmd1bWVudHMgOiBmdW5jdGlvbih2YWx1ZSkgewogICAgICByZXR1cm4gaXNPYmplY3RMaWtlXzEodmFsdWUpICYmIGhhc093blByb3BlcnR5JDUuY2FsbCh2YWx1ZSwgJ2NhbGxlZScpICYmCiAgICAgICAgIXByb3BlcnR5SXNFbnVtZXJhYmxlLmNhbGwodmFsdWUsICdjYWxsZWUnKTsKICAgIH07CgogICAgdmFyIGlzQXJndW1lbnRzXzEgPSBpc0FyZ3VtZW50czsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYW4gYEFycmF5YCBvYmplY3QuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYW4gYXJyYXksIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc0FycmF5KFsxLCAyLCAzXSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc0FycmF5KGRvY3VtZW50LmJvZHkuY2hpbGRyZW4pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmlzQXJyYXkoJ2FiYycpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmlzQXJyYXkoXy5ub29wKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIHZhciBpc0FycmF5ID0gQXJyYXkuaXNBcnJheTsKCiAgICB2YXIgaXNBcnJheV8xID0gaXNBcnJheTsKCiAgICAvKioKICAgICAqIFRoaXMgbWV0aG9kIHJldHVybnMgYGZhbHNlYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMTMuMAogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8udGltZXMoMiwgXy5zdHViRmFsc2UpOwogICAgICogLy8gPT4gW2ZhbHNlLCBmYWxzZV0KICAgICAqLwogICAgZnVuY3Rpb24gc3R1YkZhbHNlKCkgewogICAgICByZXR1cm4gZmFsc2U7CiAgICB9CgogICAgdmFyIHN0dWJGYWxzZV8xID0gc3R1YkZhbHNlOwoKICAgIHZhciBpc0J1ZmZlcl8xID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqIERldGVjdCBmcmVlIHZhcmlhYmxlIGBleHBvcnRzYC4gKi8KICAgIHZhciBmcmVlRXhwb3J0cyA9ICBleHBvcnRzICYmICFleHBvcnRzLm5vZGVUeXBlICYmIGV4cG9ydHM7CgogICAgLyoqIERldGVjdCBmcmVlIHZhcmlhYmxlIGBtb2R1bGVgLiAqLwogICAgdmFyIGZyZWVNb2R1bGUgPSBmcmVlRXhwb3J0cyAmJiAnb2JqZWN0JyA9PSAnb2JqZWN0JyAmJiBtb2R1bGUgJiYgIW1vZHVsZS5ub2RlVHlwZSAmJiBtb2R1bGU7CgogICAgLyoqIERldGVjdCB0aGUgcG9wdWxhciBDb21tb25KUyBleHRlbnNpb24gYG1vZHVsZS5leHBvcnRzYC4gKi8KICAgIHZhciBtb2R1bGVFeHBvcnRzID0gZnJlZU1vZHVsZSAmJiBmcmVlTW9kdWxlLmV4cG9ydHMgPT09IGZyZWVFeHBvcnRzOwoKICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgdmFyIEJ1ZmZlciA9IG1vZHVsZUV4cG9ydHMgPyBfcm9vdC5CdWZmZXIgOiB1bmRlZmluZWQ7CgogICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgZm9yIHRob3NlIHdpdGggdGhlIHNhbWUgbmFtZSBhcyBvdGhlciBgbG9kYXNoYCBtZXRob2RzLiAqLwogICAgdmFyIG5hdGl2ZUlzQnVmZmVyID0gQnVmZmVyID8gQnVmZmVyLmlzQnVmZmVyIDogdW5kZWZpbmVkOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYSBidWZmZXIuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSA0LjMuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBidWZmZXIsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc0J1ZmZlcihuZXcgQnVmZmVyKDIpKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzQnVmZmVyKG5ldyBVaW50OEFycmF5KDIpKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIHZhciBpc0J1ZmZlciA9IG5hdGl2ZUlzQnVmZmVyIHx8IHN0dWJGYWxzZV8xOwoKICAgIG1vZHVsZS5leHBvcnRzID0gaXNCdWZmZXI7CiAgICB9KTsKCiAgICAvKiogVXNlZCBhcyByZWZlcmVuY2VzIGZvciB2YXJpb3VzIGBOdW1iZXJgIGNvbnN0YW50cy4gKi8KICAgIHZhciBNQVhfU0FGRV9JTlRFR0VSID0gOTAwNzE5OTI1NDc0MDk5MTsKCiAgICAvKiogVXNlZCB0byBkZXRlY3QgdW5zaWduZWQgaW50ZWdlciB2YWx1ZXMuICovCiAgICB2YXIgcmVJc1VpbnQgPSAvXig/OjB8WzEtOV1cZCopJC87CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIHZhbGlkIGFycmF5LWxpa2UgaW5kZXguCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHBhcmFtIHtudW1iZXJ9IFtsZW5ndGg9TUFYX1NBRkVfSU5URUdFUl0gVGhlIHVwcGVyIGJvdW5kcyBvZiBhIHZhbGlkIGluZGV4LgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSB2YWxpZCBpbmRleCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBpc0luZGV4KHZhbHVlLCBsZW5ndGgpIHsKICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgdmFsdWU7CiAgICAgIGxlbmd0aCA9IGxlbmd0aCA9PSBudWxsID8gTUFYX1NBRkVfSU5URUdFUiA6IGxlbmd0aDsKCiAgICAgIHJldHVybiAhIWxlbmd0aCAmJgogICAgICAgICh0eXBlID09ICdudW1iZXInIHx8CiAgICAgICAgICAodHlwZSAhPSAnc3ltYm9sJyAmJiByZUlzVWludC50ZXN0KHZhbHVlKSkpICYmCiAgICAgICAgICAgICh2YWx1ZSA+IC0xICYmIHZhbHVlICUgMSA9PSAwICYmIHZhbHVlIDwgbGVuZ3RoKTsKICAgIH0KCiAgICB2YXIgX2lzSW5kZXggPSBpc0luZGV4OwoKICAgIC8qKiBVc2VkIGFzIHJlZmVyZW5jZXMgZm9yIHZhcmlvdXMgYE51bWJlcmAgY29uc3RhbnRzLiAqLwogICAgdmFyIE1BWF9TQUZFX0lOVEVHRVIkMSA9IDkwMDcxOTkyNTQ3NDA5OTE7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhIHZhbGlkIGFycmF5LWxpa2UgbGVuZ3RoLgogICAgICoKICAgICAqICoqTm90ZToqKiBUaGlzIG1ldGhvZCBpcyBsb29zZWx5IGJhc2VkIG9uCiAgICAgKiBbYFRvTGVuZ3RoYF0oaHR0cDovL2VjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtdG9sZW5ndGgpLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgdmFsaWQgbGVuZ3RoLCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNMZW5ndGgoMyk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc0xlbmd0aChOdW1iZXIuTUlOX1ZBTFVFKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKgogICAgICogXy5pc0xlbmd0aChJbmZpbml0eSk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICoKICAgICAqIF8uaXNMZW5ndGgoJzMnKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzTGVuZ3RoKHZhbHVlKSB7CiAgICAgIHJldHVybiB0eXBlb2YgdmFsdWUgPT0gJ251bWJlcicgJiYKICAgICAgICB2YWx1ZSA+IC0xICYmIHZhbHVlICUgMSA9PSAwICYmIHZhbHVlIDw9IE1BWF9TQUZFX0lOVEVHRVIkMTsKICAgIH0KCiAgICB2YXIgaXNMZW5ndGhfMSA9IGlzTGVuZ3RoOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBhcmdzVGFnJDEgPSAnW29iamVjdCBBcmd1bWVudHNdJywKICAgICAgICBhcnJheVRhZyA9ICdbb2JqZWN0IEFycmF5XScsCiAgICAgICAgYm9vbFRhZyA9ICdbb2JqZWN0IEJvb2xlYW5dJywKICAgICAgICBkYXRlVGFnID0gJ1tvYmplY3QgRGF0ZV0nLAogICAgICAgIGVycm9yVGFnID0gJ1tvYmplY3QgRXJyb3JdJywKICAgICAgICBmdW5jVGFnJDEgPSAnW29iamVjdCBGdW5jdGlvbl0nLAogICAgICAgIG1hcFRhZyA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIG51bWJlclRhZyA9ICdbb2JqZWN0IE51bWJlcl0nLAogICAgICAgIG9iamVjdFRhZyA9ICdbb2JqZWN0IE9iamVjdF0nLAogICAgICAgIHJlZ2V4cFRhZyA9ICdbb2JqZWN0IFJlZ0V4cF0nLAogICAgICAgIHNldFRhZyA9ICdbb2JqZWN0IFNldF0nLAogICAgICAgIHN0cmluZ1RhZyA9ICdbb2JqZWN0IFN0cmluZ10nLAogICAgICAgIHdlYWtNYXBUYWcgPSAnW29iamVjdCBXZWFrTWFwXSc7CgogICAgdmFyIGFycmF5QnVmZmVyVGFnID0gJ1tvYmplY3QgQXJyYXlCdWZmZXJdJywKICAgICAgICBkYXRhVmlld1RhZyA9ICdbb2JqZWN0IERhdGFWaWV3XScsCiAgICAgICAgZmxvYXQzMlRhZyA9ICdbb2JqZWN0IEZsb2F0MzJBcnJheV0nLAogICAgICAgIGZsb2F0NjRUYWcgPSAnW29iamVjdCBGbG9hdDY0QXJyYXldJywKICAgICAgICBpbnQ4VGFnID0gJ1tvYmplY3QgSW50OEFycmF5XScsCiAgICAgICAgaW50MTZUYWcgPSAnW29iamVjdCBJbnQxNkFycmF5XScsCiAgICAgICAgaW50MzJUYWcgPSAnW29iamVjdCBJbnQzMkFycmF5XScsCiAgICAgICAgdWludDhUYWcgPSAnW29iamVjdCBVaW50OEFycmF5XScsCiAgICAgICAgdWludDhDbGFtcGVkVGFnID0gJ1tvYmplY3QgVWludDhDbGFtcGVkQXJyYXldJywKICAgICAgICB1aW50MTZUYWcgPSAnW29iamVjdCBVaW50MTZBcnJheV0nLAogICAgICAgIHVpbnQzMlRhZyA9ICdbb2JqZWN0IFVpbnQzMkFycmF5XSc7CgogICAgLyoqIFVzZWQgdG8gaWRlbnRpZnkgYHRvU3RyaW5nVGFnYCB2YWx1ZXMgb2YgdHlwZWQgYXJyYXlzLiAqLwogICAgdmFyIHR5cGVkQXJyYXlUYWdzID0ge307CiAgICB0eXBlZEFycmF5VGFnc1tmbG9hdDMyVGFnXSA9IHR5cGVkQXJyYXlUYWdzW2Zsb2F0NjRUYWddID0KICAgIHR5cGVkQXJyYXlUYWdzW2ludDhUYWddID0gdHlwZWRBcnJheVRhZ3NbaW50MTZUYWddID0KICAgIHR5cGVkQXJyYXlUYWdzW2ludDMyVGFnXSA9IHR5cGVkQXJyYXlUYWdzW3VpbnQ4VGFnXSA9CiAgICB0eXBlZEFycmF5VGFnc1t1aW50OENsYW1wZWRUYWddID0gdHlwZWRBcnJheVRhZ3NbdWludDE2VGFnXSA9CiAgICB0eXBlZEFycmF5VGFnc1t1aW50MzJUYWddID0gdHJ1ZTsKICAgIHR5cGVkQXJyYXlUYWdzW2FyZ3NUYWckMV0gPSB0eXBlZEFycmF5VGFnc1thcnJheVRhZ10gPQogICAgdHlwZWRBcnJheVRhZ3NbYXJyYXlCdWZmZXJUYWddID0gdHlwZWRBcnJheVRhZ3NbYm9vbFRhZ10gPQogICAgdHlwZWRBcnJheVRhZ3NbZGF0YVZpZXdUYWddID0gdHlwZWRBcnJheVRhZ3NbZGF0ZVRhZ10gPQogICAgdHlwZWRBcnJheVRhZ3NbZXJyb3JUYWddID0gdHlwZWRBcnJheVRhZ3NbZnVuY1RhZyQxXSA9CiAgICB0eXBlZEFycmF5VGFnc1ttYXBUYWddID0gdHlwZWRBcnJheVRhZ3NbbnVtYmVyVGFnXSA9CiAgICB0eXBlZEFycmF5VGFnc1tvYmplY3RUYWddID0gdHlwZWRBcnJheVRhZ3NbcmVnZXhwVGFnXSA9CiAgICB0eXBlZEFycmF5VGFnc1tzZXRUYWddID0gdHlwZWRBcnJheVRhZ3Nbc3RyaW5nVGFnXSA9CiAgICB0eXBlZEFycmF5VGFnc1t3ZWFrTWFwVGFnXSA9IGZhbHNlOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNUeXBlZEFycmF5YCB3aXRob3V0IE5vZGUuanMgb3B0aW1pemF0aW9ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHR5cGVkIGFycmF5LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc1R5cGVkQXJyYXkodmFsdWUpIHsKICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZV8xKHZhbHVlKSAmJgogICAgICAgIGlzTGVuZ3RoXzEodmFsdWUubGVuZ3RoKSAmJiAhIXR5cGVkQXJyYXlUYWdzW19iYXNlR2V0VGFnKHZhbHVlKV07CiAgICB9CgogICAgdmFyIF9iYXNlSXNUeXBlZEFycmF5ID0gYmFzZUlzVHlwZWRBcnJheTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnVuYXJ5YCB3aXRob3V0IHN1cHBvcnQgZm9yIHN0b3JpbmcgbWV0YWRhdGEuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGNhcCBhcmd1bWVudHMgZm9yLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgY2FwcGVkIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlVW5hcnkoZnVuYykgewogICAgICByZXR1cm4gZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICByZXR1cm4gZnVuYyh2YWx1ZSk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9iYXNlVW5hcnkgPSBiYXNlVW5hcnk7CgogICAgdmFyIF9ub2RlVXRpbCA9IGNyZWF0ZUNvbW1vbmpzTW9kdWxlKGZ1bmN0aW9uIChtb2R1bGUsIGV4cG9ydHMpIHsKICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgZXhwb3J0c2AuICovCiAgICB2YXIgZnJlZUV4cG9ydHMgPSAgZXhwb3J0cyAmJiAhZXhwb3J0cy5ub2RlVHlwZSAmJiBleHBvcnRzOwoKICAgIC8qKiBEZXRlY3QgZnJlZSB2YXJpYWJsZSBgbW9kdWxlYC4gKi8KICAgIHZhciBmcmVlTW9kdWxlID0gZnJlZUV4cG9ydHMgJiYgJ29iamVjdCcgPT0gJ29iamVjdCcgJiYgbW9kdWxlICYmICFtb2R1bGUubm9kZVR5cGUgJiYgbW9kdWxlOwoKICAgIC8qKiBEZXRlY3QgdGhlIHBvcHVsYXIgQ29tbW9uSlMgZXh0ZW5zaW9uIGBtb2R1bGUuZXhwb3J0c2AuICovCiAgICB2YXIgbW9kdWxlRXhwb3J0cyA9IGZyZWVNb2R1bGUgJiYgZnJlZU1vZHVsZS5leHBvcnRzID09PSBmcmVlRXhwb3J0czsKCiAgICAvKiogRGV0ZWN0IGZyZWUgdmFyaWFibGUgYHByb2Nlc3NgIGZyb20gTm9kZS5qcy4gKi8KICAgIHZhciBmcmVlUHJvY2VzcyA9IG1vZHVsZUV4cG9ydHMgJiYgX2ZyZWVHbG9iYWwucHJvY2VzczsKCiAgICAvKiogVXNlZCB0byBhY2Nlc3MgZmFzdGVyIE5vZGUuanMgaGVscGVycy4gKi8KICAgIHZhciBub2RlVXRpbCA9IChmdW5jdGlvbigpIHsKICAgICAgdHJ5IHsKICAgICAgICAvLyBVc2UgYHV0aWwudHlwZXNgIGZvciBOb2RlLmpzIDEwKy4KICAgICAgICB2YXIgdHlwZXMgPSBmcmVlTW9kdWxlICYmIGZyZWVNb2R1bGUucmVxdWlyZSAmJiBmcmVlTW9kdWxlLnJlcXVpcmUoJ3V0aWwnKS50eXBlczsKCiAgICAgICAgaWYgKHR5cGVzKSB7CiAgICAgICAgICByZXR1cm4gdHlwZXM7CiAgICAgICAgfQoKICAgICAgICAvLyBMZWdhY3kgYHByb2Nlc3MuYmluZGluZygndXRpbCcpYCBmb3IgTm9kZS5qcyA8IDEwLgogICAgICAgIHJldHVybiBmcmVlUHJvY2VzcyAmJiBmcmVlUHJvY2Vzcy5iaW5kaW5nICYmIGZyZWVQcm9jZXNzLmJpbmRpbmcoJ3V0aWwnKTsKICAgICAgfSBjYXRjaCAoZSkge30KICAgIH0oKSk7CgogICAgbW9kdWxlLmV4cG9ydHMgPSBub2RlVXRpbDsKICAgIH0pOwoKICAgIC8qIE5vZGUuanMgaGVscGVyIHJlZmVyZW5jZXMuICovCiAgICB2YXIgbm9kZUlzVHlwZWRBcnJheSA9IF9ub2RlVXRpbCAmJiBfbm9kZVV0aWwuaXNUeXBlZEFycmF5OwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIHR5cGVkIGFycmF5LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMy4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgdHlwZWQgYXJyYXksIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc1R5cGVkQXJyYXkobmV3IFVpbnQ4QXJyYXkpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNUeXBlZEFycmF5KFtdKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIHZhciBpc1R5cGVkQXJyYXkgPSBub2RlSXNUeXBlZEFycmF5ID8gX2Jhc2VVbmFyeShub2RlSXNUeXBlZEFycmF5KSA6IF9iYXNlSXNUeXBlZEFycmF5OwoKICAgIHZhciBpc1R5cGVkQXJyYXlfMSA9IGlzVHlwZWRBcnJheTsKCiAgICAvKiogVXNlZCBmb3IgYnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMuICovCiAgICB2YXIgb2JqZWN0UHJvdG8kNyA9IE9iamVjdC5wcm90b3R5cGU7CgogICAgLyoqIFVzZWQgdG8gY2hlY2sgb2JqZWN0cyBmb3Igb3duIHByb3BlcnRpZXMuICovCiAgICB2YXIgaGFzT3duUHJvcGVydHkkNiA9IG9iamVjdFByb3RvJDcuaGFzT3duUHJvcGVydHk7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHRoZSBlbnVtZXJhYmxlIHByb3BlcnR5IG5hbWVzIG9mIHRoZSBhcnJheS1saWtlIGB2YWx1ZWAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtib29sZWFufSBpbmhlcml0ZWQgU3BlY2lmeSByZXR1cm5pbmcgaW5oZXJpdGVkIHByb3BlcnR5IG5hbWVzLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcy4KICAgICAqLwogICAgZnVuY3Rpb24gYXJyYXlMaWtlS2V5cyh2YWx1ZSwgaW5oZXJpdGVkKSB7CiAgICAgIHZhciBpc0FyciA9IGlzQXJyYXlfMSh2YWx1ZSksCiAgICAgICAgICBpc0FyZyA9ICFpc0FyciAmJiBpc0FyZ3VtZW50c18xKHZhbHVlKSwKICAgICAgICAgIGlzQnVmZiA9ICFpc0FyciAmJiAhaXNBcmcgJiYgaXNCdWZmZXJfMSh2YWx1ZSksCiAgICAgICAgICBpc1R5cGUgPSAhaXNBcnIgJiYgIWlzQXJnICYmICFpc0J1ZmYgJiYgaXNUeXBlZEFycmF5XzEodmFsdWUpLAogICAgICAgICAgc2tpcEluZGV4ZXMgPSBpc0FyciB8fCBpc0FyZyB8fCBpc0J1ZmYgfHwgaXNUeXBlLAogICAgICAgICAgcmVzdWx0ID0gc2tpcEluZGV4ZXMgPyBfYmFzZVRpbWVzKHZhbHVlLmxlbmd0aCwgU3RyaW5nKSA6IFtdLAogICAgICAgICAgbGVuZ3RoID0gcmVzdWx0Lmxlbmd0aDsKCiAgICAgIGZvciAodmFyIGtleSBpbiB2YWx1ZSkgewogICAgICAgIGlmICgoaW5oZXJpdGVkIHx8IGhhc093blByb3BlcnR5JDYuY2FsbCh2YWx1ZSwga2V5KSkgJiYKICAgICAgICAgICAgIShza2lwSW5kZXhlcyAmJiAoCiAgICAgICAgICAgICAgIC8vIFNhZmFyaSA5IGhhcyBlbnVtZXJhYmxlIGBhcmd1bWVudHMubGVuZ3RoYCBpbiBzdHJpY3QgbW9kZS4KICAgICAgICAgICAgICAga2V5ID09ICdsZW5ndGgnIHx8CiAgICAgICAgICAgICAgIC8vIE5vZGUuanMgMC4xMCBoYXMgZW51bWVyYWJsZSBub24taW5kZXggcHJvcGVydGllcyBvbiBidWZmZXJzLgogICAgICAgICAgICAgICAoaXNCdWZmICYmIChrZXkgPT0gJ29mZnNldCcgfHwga2V5ID09ICdwYXJlbnQnKSkgfHwKICAgICAgICAgICAgICAgLy8gUGhhbnRvbUpTIDIgaGFzIGVudW1lcmFibGUgbm9uLWluZGV4IHByb3BlcnRpZXMgb24gdHlwZWQgYXJyYXlzLgogICAgICAgICAgICAgICAoaXNUeXBlICYmIChrZXkgPT0gJ2J1ZmZlcicgfHwga2V5ID09ICdieXRlTGVuZ3RoJyB8fCBrZXkgPT0gJ2J5dGVPZmZzZXQnKSkgfHwKICAgICAgICAgICAgICAgLy8gU2tpcCBpbmRleCBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICBfaXNJbmRleChrZXksIGxlbmd0aCkKICAgICAgICAgICAgKSkpIHsKICAgICAgICAgIHJlc3VsdC5wdXNoKGtleSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9hcnJheUxpa2VLZXlzID0gYXJyYXlMaWtlS2V5czsKCiAgICAvKiogVXNlZCBmb3IgYnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMuICovCiAgICB2YXIgb2JqZWN0UHJvdG8kOCA9IE9iamVjdC5wcm90b3R5cGU7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBsaWtlbHkgYSBwcm90b3R5cGUgb2JqZWN0LgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgcHJvdG90eXBlLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzUHJvdG90eXBlKHZhbHVlKSB7CiAgICAgIHZhciBDdG9yID0gdmFsdWUgJiYgdmFsdWUuY29uc3RydWN0b3IsCiAgICAgICAgICBwcm90byA9ICh0eXBlb2YgQ3RvciA9PSAnZnVuY3Rpb24nICYmIEN0b3IucHJvdG90eXBlKSB8fCBvYmplY3RQcm90byQ4OwoKICAgICAgcmV0dXJuIHZhbHVlID09PSBwcm90bzsKICAgIH0KCiAgICB2YXIgX2lzUHJvdG90eXBlID0gaXNQcm90b3R5cGU7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgdW5hcnkgZnVuY3Rpb24gdGhhdCBpbnZva2VzIGBmdW5jYCB3aXRoIGl0cyBhcmd1bWVudCB0cmFuc2Zvcm1lZC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gd3JhcC4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHRyYW5zZm9ybSBUaGUgYXJndW1lbnQgdHJhbnNmb3JtLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIG92ZXJBcmcoZnVuYywgdHJhbnNmb3JtKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihhcmcpIHsKICAgICAgICByZXR1cm4gZnVuYyh0cmFuc2Zvcm0oYXJnKSk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9vdmVyQXJnID0gb3ZlckFyZzsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyBmb3IgdGhvc2Ugd2l0aCB0aGUgc2FtZSBuYW1lIGFzIG90aGVyIGBsb2Rhc2hgIG1ldGhvZHMuICovCiAgICB2YXIgbmF0aXZlS2V5cyA9IF9vdmVyQXJnKE9iamVjdC5rZXlzLCBPYmplY3QpOwoKICAgIHZhciBfbmF0aXZlS2V5cyA9IG5hdGl2ZUtleXM7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJDkgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JDcgPSBvYmplY3RQcm90byQ5Lmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ua2V5c2Agd2hpY2ggZG9lc24ndCB0cmVhdCBzcGFyc2UgYXJyYXlzIGFzIGRlbnNlLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlS2V5cyhvYmplY3QpIHsKICAgICAgaWYgKCFfaXNQcm90b3R5cGUob2JqZWN0KSkgewogICAgICAgIHJldHVybiBfbmF0aXZlS2V5cyhvYmplY3QpOwogICAgICB9CiAgICAgIHZhciByZXN1bHQgPSBbXTsKICAgICAgZm9yICh2YXIga2V5IGluIE9iamVjdChvYmplY3QpKSB7CiAgICAgICAgaWYgKGhhc093blByb3BlcnR5JDcuY2FsbChvYmplY3QsIGtleSkgJiYga2V5ICE9ICdjb25zdHJ1Y3RvcicpIHsKICAgICAgICAgIHJlc3VsdC5wdXNoKGtleSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9iYXNlS2V5cyA9IGJhc2VLZXlzOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYXJyYXktbGlrZS4gQSB2YWx1ZSBpcyBjb25zaWRlcmVkIGFycmF5LWxpa2UgaWYgaXQncwogICAgICogbm90IGEgZnVuY3Rpb24gYW5kIGhhcyBhIGB2YWx1ZS5sZW5ndGhgIHRoYXQncyBhbiBpbnRlZ2VyIGdyZWF0ZXIgdGhhbiBvcgogICAgICogZXF1YWwgdG8gYDBgIGFuZCBsZXNzIHRoYW4gb3IgZXF1YWwgdG8gYE51bWJlci5NQVhfU0FGRV9JTlRFR0VSYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMC4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhcnJheS1saWtlLCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNBcnJheUxpa2UoWzEsIDIsIDNdKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzQXJyYXlMaWtlKGRvY3VtZW50LmJvZHkuY2hpbGRyZW4pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNBcnJheUxpa2UoJ2FiYycpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNBcnJheUxpa2UoXy5ub29wKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzQXJyYXlMaWtlKHZhbHVlKSB7CiAgICAgIHJldHVybiB2YWx1ZSAhPSBudWxsICYmIGlzTGVuZ3RoXzEodmFsdWUubGVuZ3RoKSAmJiAhaXNGdW5jdGlvbl8xKHZhbHVlKTsKICAgIH0KCiAgICB2YXIgaXNBcnJheUxpa2VfMSA9IGlzQXJyYXlMaWtlOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGVudW1lcmFibGUgcHJvcGVydHkgbmFtZXMgb2YgYG9iamVjdGAuCiAgICAgKgogICAgICogKipOb3RlOioqIE5vbi1vYmplY3QgdmFsdWVzIGFyZSBjb2VyY2VkIHRvIG9iamVjdHMuIFNlZSB0aGUKICAgICAqIFtFUyBzcGVjXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1vYmplY3Qua2V5cykKICAgICAqIGZvciBtb3JlIGRldGFpbHMuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcy4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICogICB0aGlzLmEgPSAxOwogICAgICogICB0aGlzLmIgPSAyOwogICAgICogfQogICAgICoKICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgKgogICAgICogXy5rZXlzKG5ldyBGb28pOwogICAgICogLy8gPT4gWydhJywgJ2InXSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICoKICAgICAqIF8ua2V5cygnaGknKTsKICAgICAqIC8vID0+IFsnMCcsICcxJ10KICAgICAqLwogICAgZnVuY3Rpb24ga2V5cyQyKG9iamVjdCkgewogICAgICByZXR1cm4gaXNBcnJheUxpa2VfMShvYmplY3QpID8gX2FycmF5TGlrZUtleXMob2JqZWN0KSA6IF9iYXNlS2V5cyhvYmplY3QpOwogICAgfQoKICAgIHZhciBrZXlzXzEgPSBrZXlzJDI7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5hc3NpZ25gIHdpdGhvdXQgc3VwcG9ydCBmb3IgbXVsdGlwbGUgc291cmNlcwogICAgICogb3IgYGN1c3RvbWl6ZXJgIGZ1bmN0aW9ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgc291cmNlIG9iamVjdC4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VBc3NpZ24ob2JqZWN0LCBzb3VyY2UpIHsKICAgICAgcmV0dXJuIG9iamVjdCAmJiBfY29weU9iamVjdChzb3VyY2UsIGtleXNfMShzb3VyY2UpLCBvYmplY3QpOwogICAgfQoKICAgIHZhciBfYmFzZUFzc2lnbiA9IGJhc2VBc3NpZ247CgogICAgLyoqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGxpa2UKICAgICAqIFtgT2JqZWN0LmtleXNgXShodHRwOi8vZWNtYS1pbnRlcm5hdGlvbmFsLm9yZy9lY21hLTI2Mi83LjAvI3NlYy1vYmplY3Qua2V5cykKICAgICAqIGV4Y2VwdCB0aGF0IGl0IGluY2x1ZGVzIGluaGVyaXRlZCBlbnVtZXJhYmxlIHByb3BlcnRpZXMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgbmFtZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG5hdGl2ZUtleXNJbihvYmplY3QpIHsKICAgICAgdmFyIHJlc3VsdCA9IFtdOwogICAgICBpZiAob2JqZWN0ICE9IG51bGwpIHsKICAgICAgICBmb3IgKHZhciBrZXkgaW4gT2JqZWN0KG9iamVjdCkpIHsKICAgICAgICAgIHJlc3VsdC5wdXNoKGtleSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9uYXRpdmVLZXlzSW4gPSBuYXRpdmVLZXlzSW47CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJGEgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JDggPSBvYmplY3RQcm90byRhLmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ua2V5c0luYCB3aGljaCBkb2Vzbid0IHRyZWF0IHNwYXJzZSBhcnJheXMgYXMgZGVuc2UuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgbmFtZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VLZXlzSW4ob2JqZWN0KSB7CiAgICAgIGlmICghaXNPYmplY3RfMShvYmplY3QpKSB7CiAgICAgICAgcmV0dXJuIF9uYXRpdmVLZXlzSW4ob2JqZWN0KTsKICAgICAgfQogICAgICB2YXIgaXNQcm90byA9IF9pc1Byb3RvdHlwZShvYmplY3QpLAogICAgICAgICAgcmVzdWx0ID0gW107CgogICAgICBmb3IgKHZhciBrZXkgaW4gb2JqZWN0KSB7CiAgICAgICAgaWYgKCEoa2V5ID09ICdjb25zdHJ1Y3RvcicgJiYgKGlzUHJvdG8gfHwgIWhhc093blByb3BlcnR5JDguY2FsbChvYmplY3QsIGtleSkpKSkgewogICAgICAgICAgcmVzdWx0LnB1c2goa2V5KTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2Jhc2VLZXlzSW4gPSBiYXNlS2V5c0luOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGFuZCBpbmhlcml0ZWQgZW51bWVyYWJsZSBwcm9wZXJ0eSBuYW1lcyBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogTm9uLW9iamVjdCB2YWx1ZXMgYXJlIGNvZXJjZWQgdG8gb2JqZWN0cy4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDMuMC4wCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgKiAgIHRoaXMuYiA9IDI7CiAgICAgKiB9CiAgICAgKgogICAgICogRm9vLnByb3RvdHlwZS5jID0gMzsKICAgICAqCiAgICAgKiBfLmtleXNJbihuZXcgRm9vKTsKICAgICAqIC8vID0+IFsnYScsICdiJywgJ2MnXSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICovCiAgICBmdW5jdGlvbiBrZXlzSW4kMShvYmplY3QpIHsKICAgICAgcmV0dXJuIGlzQXJyYXlMaWtlXzEob2JqZWN0KSA/IF9hcnJheUxpa2VLZXlzKG9iamVjdCwgdHJ1ZSkgOiBfYmFzZUtleXNJbihvYmplY3QpOwogICAgfQoKICAgIHZhciBrZXlzSW5fMSA9IGtleXNJbiQxOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uYXNzaWduSW5gIHdpdGhvdXQgc3VwcG9ydCBmb3IgbXVsdGlwbGUgc291cmNlcwogICAgICogb3IgYGN1c3RvbWl6ZXJgIGZ1bmN0aW9ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgZGVzdGluYXRpb24gb2JqZWN0LgogICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgc291cmNlIG9iamVjdC4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VBc3NpZ25JbihvYmplY3QsIHNvdXJjZSkgewogICAgICByZXR1cm4gb2JqZWN0ICYmIF9jb3B5T2JqZWN0KHNvdXJjZSwga2V5c0luXzEoc291cmNlKSwgb2JqZWN0KTsKICAgIH0KCiAgICB2YXIgX2Jhc2VBc3NpZ25JbiA9IGJhc2VBc3NpZ25JbjsKCiAgICB2YXIgX2Nsb25lQnVmZmVyID0gY3JlYXRlQ29tbW9uanNNb2R1bGUoZnVuY3Rpb24gKG1vZHVsZSwgZXhwb3J0cykgewogICAgLyoqIERldGVjdCBmcmVlIHZhcmlhYmxlIGBleHBvcnRzYC4gKi8KICAgIHZhciBmcmVlRXhwb3J0cyA9ICBleHBvcnRzICYmICFleHBvcnRzLm5vZGVUeXBlICYmIGV4cG9ydHM7CgogICAgLyoqIERldGVjdCBmcmVlIHZhcmlhYmxlIGBtb2R1bGVgLiAqLwogICAgdmFyIGZyZWVNb2R1bGUgPSBmcmVlRXhwb3J0cyAmJiAnb2JqZWN0JyA9PSAnb2JqZWN0JyAmJiBtb2R1bGUgJiYgIW1vZHVsZS5ub2RlVHlwZSAmJiBtb2R1bGU7CgogICAgLyoqIERldGVjdCB0aGUgcG9wdWxhciBDb21tb25KUyBleHRlbnNpb24gYG1vZHVsZS5leHBvcnRzYC4gKi8KICAgIHZhciBtb2R1bGVFeHBvcnRzID0gZnJlZU1vZHVsZSAmJiBmcmVlTW9kdWxlLmV4cG9ydHMgPT09IGZyZWVFeHBvcnRzOwoKICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgdmFyIEJ1ZmZlciA9IG1vZHVsZUV4cG9ydHMgPyBfcm9vdC5CdWZmZXIgOiB1bmRlZmluZWQsCiAgICAgICAgYWxsb2NVbnNhZmUgPSBCdWZmZXIgPyBCdWZmZXIuYWxsb2NVbnNhZmUgOiB1bmRlZmluZWQ7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgIGBidWZmZXJgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0J1ZmZlcn0gYnVmZmVyIFRoZSBidWZmZXIgdG8gY2xvbmUuCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpc0RlZXBdIFNwZWNpZnkgYSBkZWVwIGNsb25lLgogICAgICogQHJldHVybnMge0J1ZmZlcn0gUmV0dXJucyB0aGUgY2xvbmVkIGJ1ZmZlci4KICAgICAqLwogICAgZnVuY3Rpb24gY2xvbmVCdWZmZXIoYnVmZmVyLCBpc0RlZXApIHsKICAgICAgaWYgKGlzRGVlcCkgewogICAgICAgIHJldHVybiBidWZmZXIuc2xpY2UoKTsKICAgICAgfQogICAgICB2YXIgbGVuZ3RoID0gYnVmZmVyLmxlbmd0aCwKICAgICAgICAgIHJlc3VsdCA9IGFsbG9jVW5zYWZlID8gYWxsb2NVbnNhZmUobGVuZ3RoKSA6IG5ldyBidWZmZXIuY29uc3RydWN0b3IobGVuZ3RoKTsKCiAgICAgIGJ1ZmZlci5jb3B5KHJlc3VsdCk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgbW9kdWxlLmV4cG9ydHMgPSBjbG9uZUJ1ZmZlcjsKICAgIH0pOwoKICAgIC8qKgogICAgICogQ29waWVzIHRoZSB2YWx1ZXMgb2YgYHNvdXJjZWAgdG8gYGFycmF5YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheX0gc291cmNlIFRoZSBhcnJheSB0byBjb3B5IHZhbHVlcyBmcm9tLgogICAgICogQHBhcmFtIHtBcnJheX0gW2FycmF5PVtdXSBUaGUgYXJyYXkgdG8gY29weSB2YWx1ZXMgdG8uCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgYGFycmF5YC4KICAgICAqLwogICAgZnVuY3Rpb24gY29weUFycmF5KHNvdXJjZSwgYXJyYXkpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBzb3VyY2UubGVuZ3RoOwoKICAgICAgYXJyYXkgfHwgKGFycmF5ID0gQXJyYXkobGVuZ3RoKSk7CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgYXJyYXlbaW5kZXhdID0gc291cmNlW2luZGV4XTsKICAgICAgfQogICAgICByZXR1cm4gYXJyYXk7CiAgICB9CgogICAgdmFyIF9jb3B5QXJyYXkgPSBjb3B5QXJyYXk7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uZmlsdGVyYCBmb3IgYXJyYXlzIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAqIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgZmlsdGVyZWQgYXJyYXkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFycmF5RmlsdGVyKGFycmF5LCBwcmVkaWNhdGUpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aCwKICAgICAgICAgIHJlc0luZGV4ID0gMCwKICAgICAgICAgIHJlc3VsdCA9IFtdOwoKICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF07CiAgICAgICAgaWYgKHByZWRpY2F0ZSh2YWx1ZSwgaW5kZXgsIGFycmF5KSkgewogICAgICAgICAgcmVzdWx0W3Jlc0luZGV4KytdID0gdmFsdWU7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9hcnJheUZpbHRlciA9IGFycmF5RmlsdGVyOwoKICAgIC8qKgogICAgICogVGhpcyBtZXRob2QgcmV0dXJucyBhIG5ldyBlbXB0eSBhcnJheS4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMTMuMAogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGVtcHR5IGFycmF5LgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgYXJyYXlzID0gXy50aW1lcygyLCBfLnN0dWJBcnJheSk7CiAgICAgKgogICAgICogY29uc29sZS5sb2coYXJyYXlzKTsKICAgICAqIC8vID0+IFtbXSwgW11dCiAgICAgKgogICAgICogY29uc29sZS5sb2coYXJyYXlzWzBdID09PSBhcnJheXNbMV0pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gc3R1YkFycmF5KCkgewogICAgICByZXR1cm4gW107CiAgICB9CgogICAgdmFyIHN0dWJBcnJheV8xID0gc3R1YkFycmF5OwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byRiID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogQnVpbHQtaW4gdmFsdWUgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBwcm9wZXJ0eUlzRW51bWVyYWJsZSQxID0gb2JqZWN0UHJvdG8kYi5wcm9wZXJ0eUlzRW51bWVyYWJsZTsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyBmb3IgdGhvc2Ugd2l0aCB0aGUgc2FtZSBuYW1lIGFzIG90aGVyIGBsb2Rhc2hgIG1ldGhvZHMuICovCiAgICB2YXIgbmF0aXZlR2V0U3ltYm9scyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eVN5bWJvbHM7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHRoZSBvd24gZW51bWVyYWJsZSBzeW1ib2xzIG9mIGBvYmplY3RgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHN5bWJvbHMuCiAgICAgKi8KICAgIHZhciBnZXRTeW1ib2xzID0gIW5hdGl2ZUdldFN5bWJvbHMgPyBzdHViQXJyYXlfMSA6IGZ1bmN0aW9uKG9iamVjdCkgewogICAgICBpZiAob2JqZWN0ID09IG51bGwpIHsKICAgICAgICByZXR1cm4gW107CiAgICAgIH0KICAgICAgb2JqZWN0ID0gT2JqZWN0KG9iamVjdCk7CiAgICAgIHJldHVybiBfYXJyYXlGaWx0ZXIobmF0aXZlR2V0U3ltYm9scyhvYmplY3QpLCBmdW5jdGlvbihzeW1ib2wpIHsKICAgICAgICByZXR1cm4gcHJvcGVydHlJc0VudW1lcmFibGUkMS5jYWxsKG9iamVjdCwgc3ltYm9sKTsKICAgICAgfSk7CiAgICB9OwoKICAgIHZhciBfZ2V0U3ltYm9scyA9IGdldFN5bWJvbHM7CgogICAgLyoqCiAgICAgKiBDb3BpZXMgb3duIHN5bWJvbHMgb2YgYHNvdXJjZWAgdG8gYG9iamVjdGAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzb3VyY2UgVGhlIG9iamVjdCB0byBjb3B5IHN5bWJvbHMgZnJvbS4KICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0PXt9XSBUaGUgb2JqZWN0IHRvIGNvcHkgc3ltYm9scyB0by4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvcHlTeW1ib2xzKHNvdXJjZSwgb2JqZWN0KSB7CiAgICAgIHJldHVybiBfY29weU9iamVjdChzb3VyY2UsIF9nZXRTeW1ib2xzKHNvdXJjZSksIG9iamVjdCk7CiAgICB9CgogICAgdmFyIF9jb3B5U3ltYm9scyA9IGNvcHlTeW1ib2xzOwoKICAgIC8qKgogICAgICogQXBwZW5kcyB0aGUgZWxlbWVudHMgb2YgYHZhbHVlc2AgdG8gYGFycmF5YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIG1vZGlmeS4KICAgICAqIEBwYXJhbSB7QXJyYXl9IHZhbHVlcyBUaGUgdmFsdWVzIHRvIGFwcGVuZC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyBgYXJyYXlgLgogICAgICovCiAgICBmdW5jdGlvbiBhcnJheVB1c2goYXJyYXksIHZhbHVlcykgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IHZhbHVlcy5sZW5ndGgsCiAgICAgICAgICBvZmZzZXQgPSBhcnJheS5sZW5ndGg7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIGFycmF5W29mZnNldCArIGluZGV4XSA9IHZhbHVlc1tpbmRleF07CiAgICAgIH0KICAgICAgcmV0dXJuIGFycmF5OwogICAgfQoKICAgIHZhciBfYXJyYXlQdXNoID0gYXJyYXlQdXNoOwoKICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgdmFyIGdldFByb3RvdHlwZSA9IF9vdmVyQXJnKE9iamVjdC5nZXRQcm90b3R5cGVPZiwgT2JqZWN0KTsKCiAgICB2YXIgX2dldFByb3RvdHlwZSA9IGdldFByb3RvdHlwZTsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyBmb3IgdGhvc2Ugd2l0aCB0aGUgc2FtZSBuYW1lIGFzIG90aGVyIGBsb2Rhc2hgIG1ldGhvZHMuICovCiAgICB2YXIgbmF0aXZlR2V0U3ltYm9scyQxID0gT2JqZWN0LmdldE93blByb3BlcnR5U3ltYm9sczsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgdGhlIG93biBhbmQgaW5oZXJpdGVkIGVudW1lcmFibGUgc3ltYm9scyBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBzeW1ib2xzLgogICAgICovCiAgICB2YXIgZ2V0U3ltYm9sc0luID0gIW5hdGl2ZUdldFN5bWJvbHMkMSA/IHN0dWJBcnJheV8xIDogZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgIHZhciByZXN1bHQgPSBbXTsKICAgICAgd2hpbGUgKG9iamVjdCkgewogICAgICAgIF9hcnJheVB1c2gocmVzdWx0LCBfZ2V0U3ltYm9scyhvYmplY3QpKTsKICAgICAgICBvYmplY3QgPSBfZ2V0UHJvdG90eXBlKG9iamVjdCk7CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH07CgogICAgdmFyIF9nZXRTeW1ib2xzSW4gPSBnZXRTeW1ib2xzSW47CgogICAgLyoqCiAgICAgKiBDb3BpZXMgb3duIGFuZCBpbmhlcml0ZWQgc3ltYm9scyBvZiBgc291cmNlYCB0byBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IHRvIGNvcHkgc3ltYm9scyBmcm9tLgogICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3Q9e31dIFRoZSBvYmplY3QgdG8gY29weSBzeW1ib2xzIHRvLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAqLwogICAgZnVuY3Rpb24gY29weVN5bWJvbHNJbihzb3VyY2UsIG9iamVjdCkgewogICAgICByZXR1cm4gX2NvcHlPYmplY3Qoc291cmNlLCBfZ2V0U3ltYm9sc0luKHNvdXJjZSksIG9iamVjdCk7CiAgICB9CgogICAgdmFyIF9jb3B5U3ltYm9sc0luID0gY29weVN5bWJvbHNJbjsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBnZXRBbGxLZXlzYCBhbmQgYGdldEFsbEtleXNJbmAgd2hpY2ggdXNlcwogICAgICogYGtleXNGdW5jYCBhbmQgYHN5bWJvbHNGdW5jYCB0byBnZXQgdGhlIGVudW1lcmFibGUgcHJvcGVydHkgbmFtZXMgYW5kCiAgICAgKiBzeW1ib2xzIG9mIGBvYmplY3RgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBrZXlzRnVuYyBUaGUgZnVuY3Rpb24gdG8gZ2V0IHRoZSBrZXlzIG9mIGBvYmplY3RgLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gc3ltYm9sc0Z1bmMgVGhlIGZ1bmN0aW9uIHRvIGdldCB0aGUgc3ltYm9scyBvZiBgb2JqZWN0YC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgbmFtZXMgYW5kIHN5bWJvbHMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VHZXRBbGxLZXlzKG9iamVjdCwga2V5c0Z1bmMsIHN5bWJvbHNGdW5jKSB7CiAgICAgIHZhciByZXN1bHQgPSBrZXlzRnVuYyhvYmplY3QpOwogICAgICByZXR1cm4gaXNBcnJheV8xKG9iamVjdCkgPyByZXN1bHQgOiBfYXJyYXlQdXNoKHJlc3VsdCwgc3ltYm9sc0Z1bmMob2JqZWN0KSk7CiAgICB9CgogICAgdmFyIF9iYXNlR2V0QWxsS2V5cyA9IGJhc2VHZXRBbGxLZXlzOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBvd24gZW51bWVyYWJsZSBwcm9wZXJ0eSBuYW1lcyBhbmQgc3ltYm9scyBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBhcnJheSBvZiBwcm9wZXJ0eSBuYW1lcyBhbmQgc3ltYm9scy4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0QWxsS2V5cyhvYmplY3QpIHsKICAgICAgcmV0dXJuIF9iYXNlR2V0QWxsS2V5cyhvYmplY3QsIGtleXNfMSwgX2dldFN5bWJvbHMpOwogICAgfQoKICAgIHZhciBfZ2V0QWxsS2V5cyA9IGdldEFsbEtleXM7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIG93biBhbmQgaW5oZXJpdGVkIGVudW1lcmFibGUgcHJvcGVydHkgbmFtZXMgYW5kCiAgICAgKiBzeW1ib2xzIG9mIGBvYmplY3RgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IG5hbWVzIGFuZCBzeW1ib2xzLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRBbGxLZXlzSW4ob2JqZWN0KSB7CiAgICAgIHJldHVybiBfYmFzZUdldEFsbEtleXMob2JqZWN0LCBrZXlzSW5fMSwgX2dldFN5bWJvbHNJbik7CiAgICB9CgogICAgdmFyIF9nZXRBbGxLZXlzSW4gPSBnZXRBbGxLZXlzSW47CgogICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgdGhhdCBhcmUgdmVyaWZpZWQgdG8gYmUgbmF0aXZlLiAqLwogICAgdmFyIERhdGFWaWV3JDEgPSBfZ2V0TmF0aXZlKF9yb290LCAnRGF0YVZpZXcnKTsKCiAgICB2YXIgX0RhdGFWaWV3ID0gRGF0YVZpZXckMTsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyB0aGF0IGFyZSB2ZXJpZmllZCB0byBiZSBuYXRpdmUuICovCiAgICB2YXIgUHJvbWlzZSQxID0gX2dldE5hdGl2ZShfcm9vdCwgJ1Byb21pc2UnKTsKCiAgICB2YXIgX1Byb21pc2UgPSBQcm9taXNlJDE7CgogICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgdGhhdCBhcmUgdmVyaWZpZWQgdG8gYmUgbmF0aXZlLiAqLwogICAgdmFyIFNldCQ1ID0gX2dldE5hdGl2ZShfcm9vdCwgJ1NldCcpOwoKICAgIHZhciBfU2V0ID0gU2V0JDU7CgogICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgdGhhdCBhcmUgdmVyaWZpZWQgdG8gYmUgbmF0aXZlLiAqLwogICAgdmFyIFdlYWtNYXAkMSA9IF9nZXROYXRpdmUoX3Jvb3QsICdXZWFrTWFwJyk7CgogICAgdmFyIF9XZWFrTWFwID0gV2Vha01hcCQxOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBtYXBUYWckMSA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIG9iamVjdFRhZyQxID0gJ1tvYmplY3QgT2JqZWN0XScsCiAgICAgICAgcHJvbWlzZVRhZyA9ICdbb2JqZWN0IFByb21pc2VdJywKICAgICAgICBzZXRUYWckMSA9ICdbb2JqZWN0IFNldF0nLAogICAgICAgIHdlYWtNYXBUYWckMSA9ICdbb2JqZWN0IFdlYWtNYXBdJzsKCiAgICB2YXIgZGF0YVZpZXdUYWckMSA9ICdbb2JqZWN0IERhdGFWaWV3XSc7CgogICAgLyoqIFVzZWQgdG8gZGV0ZWN0IG1hcHMsIHNldHMsIGFuZCB3ZWFrbWFwcy4gKi8KICAgIHZhciBkYXRhVmlld0N0b3JTdHJpbmcgPSBfdG9Tb3VyY2UoX0RhdGFWaWV3KSwKICAgICAgICBtYXBDdG9yU3RyaW5nID0gX3RvU291cmNlKF9NYXApLAogICAgICAgIHByb21pc2VDdG9yU3RyaW5nID0gX3RvU291cmNlKF9Qcm9taXNlKSwKICAgICAgICBzZXRDdG9yU3RyaW5nID0gX3RvU291cmNlKF9TZXQpLAogICAgICAgIHdlYWtNYXBDdG9yU3RyaW5nID0gX3RvU291cmNlKF9XZWFrTWFwKTsKCiAgICAvKioKICAgICAqIEdldHMgdGhlIGB0b1N0cmluZ1RhZ2Agb2YgYHZhbHVlYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7c3RyaW5nfSBSZXR1cm5zIHRoZSBgdG9TdHJpbmdUYWdgLgogICAgICovCiAgICB2YXIgZ2V0VGFnID0gX2Jhc2VHZXRUYWc7CgogICAgLy8gRmFsbGJhY2sgZm9yIGRhdGEgdmlld3MsIG1hcHMsIHNldHMsIGFuZCB3ZWFrIG1hcHMgaW4gSUUgMTEgYW5kIHByb21pc2VzIGluIE5vZGUuanMgPCA2LgogICAgaWYgKChfRGF0YVZpZXcgJiYgZ2V0VGFnKG5ldyBfRGF0YVZpZXcobmV3IEFycmF5QnVmZmVyKDEpKSkgIT0gZGF0YVZpZXdUYWckMSkgfHwKICAgICAgICAoX01hcCAmJiBnZXRUYWcobmV3IF9NYXApICE9IG1hcFRhZyQxKSB8fAogICAgICAgIChfUHJvbWlzZSAmJiBnZXRUYWcoX1Byb21pc2UucmVzb2x2ZSgpKSAhPSBwcm9taXNlVGFnKSB8fAogICAgICAgIChfU2V0ICYmIGdldFRhZyhuZXcgX1NldCkgIT0gc2V0VGFnJDEpIHx8CiAgICAgICAgKF9XZWFrTWFwICYmIGdldFRhZyhuZXcgX1dlYWtNYXApICE9IHdlYWtNYXBUYWckMSkpIHsKICAgICAgZ2V0VGFnID0gZnVuY3Rpb24odmFsdWUpIHsKICAgICAgICB2YXIgcmVzdWx0ID0gX2Jhc2VHZXRUYWcodmFsdWUpLAogICAgICAgICAgICBDdG9yID0gcmVzdWx0ID09IG9iamVjdFRhZyQxID8gdmFsdWUuY29uc3RydWN0b3IgOiB1bmRlZmluZWQsCiAgICAgICAgICAgIGN0b3JTdHJpbmcgPSBDdG9yID8gX3RvU291cmNlKEN0b3IpIDogJyc7CgogICAgICAgIGlmIChjdG9yU3RyaW5nKSB7CiAgICAgICAgICBzd2l0Y2ggKGN0b3JTdHJpbmcpIHsKICAgICAgICAgICAgY2FzZSBkYXRhVmlld0N0b3JTdHJpbmc6IHJldHVybiBkYXRhVmlld1RhZyQxOwogICAgICAgICAgICBjYXNlIG1hcEN0b3JTdHJpbmc6IHJldHVybiBtYXBUYWckMTsKICAgICAgICAgICAgY2FzZSBwcm9taXNlQ3RvclN0cmluZzogcmV0dXJuIHByb21pc2VUYWc7CiAgICAgICAgICAgIGNhc2Ugc2V0Q3RvclN0cmluZzogcmV0dXJuIHNldFRhZyQxOwogICAgICAgICAgICBjYXNlIHdlYWtNYXBDdG9yU3RyaW5nOiByZXR1cm4gd2Vha01hcFRhZyQxOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9OwogICAgfQoKICAgIHZhciBfZ2V0VGFnID0gZ2V0VGFnOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byRjID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogVXNlZCB0byBjaGVjayBvYmplY3RzIGZvciBvd24gcHJvcGVydGllcy4gKi8KICAgIHZhciBoYXNPd25Qcm9wZXJ0eSQ5ID0gb2JqZWN0UHJvdG8kYy5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKioKICAgICAqIEluaXRpYWxpemVzIGFuIGFycmF5IGNsb25lLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGluaXRpYWxpemVkIGNsb25lLgogICAgICovCiAgICBmdW5jdGlvbiBpbml0Q2xvbmVBcnJheShhcnJheSkgewogICAgICB2YXIgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgcmVzdWx0ID0gbmV3IGFycmF5LmNvbnN0cnVjdG9yKGxlbmd0aCk7CgogICAgICAvLyBBZGQgcHJvcGVydGllcyBhc3NpZ25lZCBieSBgUmVnRXhwI2V4ZWNgLgogICAgICBpZiAobGVuZ3RoICYmIHR5cGVvZiBhcnJheVswXSA9PSAnc3RyaW5nJyAmJiBoYXNPd25Qcm9wZXJ0eSQ5LmNhbGwoYXJyYXksICdpbmRleCcpKSB7CiAgICAgICAgcmVzdWx0LmluZGV4ID0gYXJyYXkuaW5kZXg7CiAgICAgICAgcmVzdWx0LmlucHV0ID0gYXJyYXkuaW5wdXQ7CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2luaXRDbG9uZUFycmF5ID0gaW5pdENsb25lQXJyYXk7CgogICAgLyoqIEJ1aWx0LWluIHZhbHVlIHJlZmVyZW5jZXMuICovCiAgICB2YXIgVWludDhBcnJheSQxID0gX3Jvb3QuVWludDhBcnJheTsKCiAgICB2YXIgX1VpbnQ4QXJyYXkgPSBVaW50OEFycmF5JDE7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgYGFycmF5QnVmZmVyYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheUJ1ZmZlcn0gYXJyYXlCdWZmZXIgVGhlIGFycmF5IGJ1ZmZlciB0byBjbG9uZS4KICAgICAqIEByZXR1cm5zIHtBcnJheUJ1ZmZlcn0gUmV0dXJucyB0aGUgY2xvbmVkIGFycmF5IGJ1ZmZlci4KICAgICAqLwogICAgZnVuY3Rpb24gY2xvbmVBcnJheUJ1ZmZlcihhcnJheUJ1ZmZlcikgewogICAgICB2YXIgcmVzdWx0ID0gbmV3IGFycmF5QnVmZmVyLmNvbnN0cnVjdG9yKGFycmF5QnVmZmVyLmJ5dGVMZW5ndGgpOwogICAgICBuZXcgX1VpbnQ4QXJyYXkocmVzdWx0KS5zZXQobmV3IF9VaW50OEFycmF5KGFycmF5QnVmZmVyKSk7CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9jbG9uZUFycmF5QnVmZmVyID0gY2xvbmVBcnJheUJ1ZmZlcjsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBjbG9uZSBvZiBgZGF0YVZpZXdgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gZGF0YVZpZXcgVGhlIGRhdGEgdmlldyB0byBjbG9uZS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2lzRGVlcF0gU3BlY2lmeSBhIGRlZXAgY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgZGF0YSB2aWV3LgogICAgICovCiAgICBmdW5jdGlvbiBjbG9uZURhdGFWaWV3KGRhdGFWaWV3LCBpc0RlZXApIHsKICAgICAgdmFyIGJ1ZmZlciA9IGlzRGVlcCA/IF9jbG9uZUFycmF5QnVmZmVyKGRhdGFWaWV3LmJ1ZmZlcikgOiBkYXRhVmlldy5idWZmZXI7CiAgICAgIHJldHVybiBuZXcgZGF0YVZpZXcuY29uc3RydWN0b3IoYnVmZmVyLCBkYXRhVmlldy5ieXRlT2Zmc2V0LCBkYXRhVmlldy5ieXRlTGVuZ3RoKTsKICAgIH0KCiAgICB2YXIgX2Nsb25lRGF0YVZpZXcgPSBjbG9uZURhdGFWaWV3OwoKICAgIC8qKiBVc2VkIHRvIG1hdGNoIGBSZWdFeHBgIGZsYWdzIGZyb20gdGhlaXIgY29lcmNlZCBzdHJpbmcgdmFsdWVzLiAqLwogICAgdmFyIHJlRmxhZ3MgPSAvXHcqJC87CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgY2xvbmUgb2YgYHJlZ2V4cGAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSByZWdleHAgVGhlIHJlZ2V4cCB0byBjbG9uZS4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGNsb25lZCByZWdleHAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNsb25lUmVnRXhwKHJlZ2V4cCkgewogICAgICB2YXIgcmVzdWx0ID0gbmV3IHJlZ2V4cC5jb25zdHJ1Y3RvcihyZWdleHAuc291cmNlLCByZUZsYWdzLmV4ZWMocmVnZXhwKSk7CiAgICAgIHJlc3VsdC5sYXN0SW5kZXggPSByZWdleHAubGFzdEluZGV4OwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfY2xvbmVSZWdFeHAgPSBjbG9uZVJlZ0V4cDsKCiAgICAvKiogVXNlZCB0byBjb252ZXJ0IHN5bWJvbHMgdG8gcHJpbWl0aXZlcyBhbmQgc3RyaW5ncy4gKi8KICAgIHZhciBzeW1ib2xQcm90byA9IF9TeW1ib2wgPyBfU3ltYm9sLnByb3RvdHlwZSA6IHVuZGVmaW5lZCwKICAgICAgICBzeW1ib2xWYWx1ZU9mID0gc3ltYm9sUHJvdG8gPyBzeW1ib2xQcm90by52YWx1ZU9mIDogdW5kZWZpbmVkOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGNsb25lIG9mIHRoZSBgc3ltYm9sYCBvYmplY3QuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzeW1ib2wgVGhlIHN5bWJvbCBvYmplY3QgdG8gY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgc3ltYm9sIG9iamVjdC4KICAgICAqLwogICAgZnVuY3Rpb24gY2xvbmVTeW1ib2woc3ltYm9sKSB7CiAgICAgIHJldHVybiBzeW1ib2xWYWx1ZU9mID8gT2JqZWN0KHN5bWJvbFZhbHVlT2YuY2FsbChzeW1ib2wpKSA6IHt9OwogICAgfQoKICAgIHZhciBfY2xvbmVTeW1ib2wgPSBjbG9uZVN5bWJvbDsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBjbG9uZSBvZiBgdHlwZWRBcnJheWAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSB0eXBlZEFycmF5IFRoZSB0eXBlZCBhcnJheSB0byBjbG9uZS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2lzRGVlcF0gU3BlY2lmeSBhIGRlZXAgY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBjbG9uZWQgdHlwZWQgYXJyYXkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNsb25lVHlwZWRBcnJheSh0eXBlZEFycmF5LCBpc0RlZXApIHsKICAgICAgdmFyIGJ1ZmZlciA9IGlzRGVlcCA/IF9jbG9uZUFycmF5QnVmZmVyKHR5cGVkQXJyYXkuYnVmZmVyKSA6IHR5cGVkQXJyYXkuYnVmZmVyOwogICAgICByZXR1cm4gbmV3IHR5cGVkQXJyYXkuY29uc3RydWN0b3IoYnVmZmVyLCB0eXBlZEFycmF5LmJ5dGVPZmZzZXQsIHR5cGVkQXJyYXkubGVuZ3RoKTsKICAgIH0KCiAgICB2YXIgX2Nsb25lVHlwZWRBcnJheSA9IGNsb25lVHlwZWRBcnJheTsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgYm9vbFRhZyQxID0gJ1tvYmplY3QgQm9vbGVhbl0nLAogICAgICAgIGRhdGVUYWckMSA9ICdbb2JqZWN0IERhdGVdJywKICAgICAgICBtYXBUYWckMiA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIG51bWJlclRhZyQxID0gJ1tvYmplY3QgTnVtYmVyXScsCiAgICAgICAgcmVnZXhwVGFnJDEgPSAnW29iamVjdCBSZWdFeHBdJywKICAgICAgICBzZXRUYWckMiA9ICdbb2JqZWN0IFNldF0nLAogICAgICAgIHN0cmluZ1RhZyQxID0gJ1tvYmplY3QgU3RyaW5nXScsCiAgICAgICAgc3ltYm9sVGFnID0gJ1tvYmplY3QgU3ltYm9sXSc7CgogICAgdmFyIGFycmF5QnVmZmVyVGFnJDEgPSAnW29iamVjdCBBcnJheUJ1ZmZlcl0nLAogICAgICAgIGRhdGFWaWV3VGFnJDIgPSAnW29iamVjdCBEYXRhVmlld10nLAogICAgICAgIGZsb2F0MzJUYWckMSA9ICdbb2JqZWN0IEZsb2F0MzJBcnJheV0nLAogICAgICAgIGZsb2F0NjRUYWckMSA9ICdbb2JqZWN0IEZsb2F0NjRBcnJheV0nLAogICAgICAgIGludDhUYWckMSA9ICdbb2JqZWN0IEludDhBcnJheV0nLAogICAgICAgIGludDE2VGFnJDEgPSAnW29iamVjdCBJbnQxNkFycmF5XScsCiAgICAgICAgaW50MzJUYWckMSA9ICdbb2JqZWN0IEludDMyQXJyYXldJywKICAgICAgICB1aW50OFRhZyQxID0gJ1tvYmplY3QgVWludDhBcnJheV0nLAogICAgICAgIHVpbnQ4Q2xhbXBlZFRhZyQxID0gJ1tvYmplY3QgVWludDhDbGFtcGVkQXJyYXldJywKICAgICAgICB1aW50MTZUYWckMSA9ICdbb2JqZWN0IFVpbnQxNkFycmF5XScsCiAgICAgICAgdWludDMyVGFnJDEgPSAnW29iamVjdCBVaW50MzJBcnJheV0nOwoKICAgIC8qKgogICAgICogSW5pdGlhbGl6ZXMgYW4gb2JqZWN0IGNsb25lIGJhc2VkIG9uIGl0cyBgdG9TdHJpbmdUYWdgLgogICAgICoKICAgICAqICoqTm90ZToqKiBUaGlzIGZ1bmN0aW9uIG9ubHkgc3VwcG9ydHMgY2xvbmluZyB2YWx1ZXMgd2l0aCB0YWdzIG9mCiAgICAgKiBgQm9vbGVhbmAsIGBEYXRlYCwgYEVycm9yYCwgYE1hcGAsIGBOdW1iZXJgLCBgUmVnRXhwYCwgYFNldGAsIG9yIGBTdHJpbmdgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gY2xvbmUuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGFnIFRoZSBgdG9TdHJpbmdUYWdgIG9mIHRoZSBvYmplY3QgdG8gY2xvbmUuCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtpc0RlZXBdIFNwZWNpZnkgYSBkZWVwIGNsb25lLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgaW5pdGlhbGl6ZWQgY2xvbmUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGluaXRDbG9uZUJ5VGFnKG9iamVjdCwgdGFnLCBpc0RlZXApIHsKICAgICAgdmFyIEN0b3IgPSBvYmplY3QuY29uc3RydWN0b3I7CiAgICAgIHN3aXRjaCAodGFnKSB7CiAgICAgICAgY2FzZSBhcnJheUJ1ZmZlclRhZyQxOgogICAgICAgICAgcmV0dXJuIF9jbG9uZUFycmF5QnVmZmVyKG9iamVjdCk7CgogICAgICAgIGNhc2UgYm9vbFRhZyQxOgogICAgICAgIGNhc2UgZGF0ZVRhZyQxOgogICAgICAgICAgcmV0dXJuIG5ldyBDdG9yKCtvYmplY3QpOwoKICAgICAgICBjYXNlIGRhdGFWaWV3VGFnJDI6CiAgICAgICAgICByZXR1cm4gX2Nsb25lRGF0YVZpZXcob2JqZWN0LCBpc0RlZXApOwoKICAgICAgICBjYXNlIGZsb2F0MzJUYWckMTogY2FzZSBmbG9hdDY0VGFnJDE6CiAgICAgICAgY2FzZSBpbnQ4VGFnJDE6IGNhc2UgaW50MTZUYWckMTogY2FzZSBpbnQzMlRhZyQxOgogICAgICAgIGNhc2UgdWludDhUYWckMTogY2FzZSB1aW50OENsYW1wZWRUYWckMTogY2FzZSB1aW50MTZUYWckMTogY2FzZSB1aW50MzJUYWckMToKICAgICAgICAgIHJldHVybiBfY2xvbmVUeXBlZEFycmF5KG9iamVjdCwgaXNEZWVwKTsKCiAgICAgICAgY2FzZSBtYXBUYWckMjoKICAgICAgICAgIHJldHVybiBuZXcgQ3RvcjsKCiAgICAgICAgY2FzZSBudW1iZXJUYWckMToKICAgICAgICBjYXNlIHN0cmluZ1RhZyQxOgogICAgICAgICAgcmV0dXJuIG5ldyBDdG9yKG9iamVjdCk7CgogICAgICAgIGNhc2UgcmVnZXhwVGFnJDE6CiAgICAgICAgICByZXR1cm4gX2Nsb25lUmVnRXhwKG9iamVjdCk7CgogICAgICAgIGNhc2Ugc2V0VGFnJDI6CiAgICAgICAgICByZXR1cm4gbmV3IEN0b3I7CgogICAgICAgIGNhc2Ugc3ltYm9sVGFnOgogICAgICAgICAgcmV0dXJuIF9jbG9uZVN5bWJvbChvYmplY3QpOwogICAgICB9CiAgICB9CgogICAgdmFyIF9pbml0Q2xvbmVCeVRhZyA9IGluaXRDbG9uZUJ5VGFnOwoKICAgIC8qKiBCdWlsdC1pbiB2YWx1ZSByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdENyZWF0ZSA9IE9iamVjdC5jcmVhdGU7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5jcmVhdGVgIHdpdGhvdXQgc3VwcG9ydCBmb3IgYXNzaWduaW5nCiAgICAgKiBwcm9wZXJ0aWVzIHRvIHRoZSBjcmVhdGVkIG9iamVjdC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IHByb3RvIFRoZSBvYmplY3QgdG8gaW5oZXJpdCBmcm9tLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgbmV3IG9iamVjdC4KICAgICAqLwogICAgdmFyIGJhc2VDcmVhdGUgPSAoZnVuY3Rpb24oKSB7CiAgICAgIGZ1bmN0aW9uIG9iamVjdCgpIHt9CiAgICAgIHJldHVybiBmdW5jdGlvbihwcm90bykgewogICAgICAgIGlmICghaXNPYmplY3RfMShwcm90bykpIHsKICAgICAgICAgIHJldHVybiB7fTsKICAgICAgICB9CiAgICAgICAgaWYgKG9iamVjdENyZWF0ZSkgewogICAgICAgICAgcmV0dXJuIG9iamVjdENyZWF0ZShwcm90byk7CiAgICAgICAgfQogICAgICAgIG9iamVjdC5wcm90b3R5cGUgPSBwcm90bzsKICAgICAgICB2YXIgcmVzdWx0ID0gbmV3IG9iamVjdDsKICAgICAgICBvYmplY3QucHJvdG90eXBlID0gdW5kZWZpbmVkOwogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH07CiAgICB9KCkpOwoKICAgIHZhciBfYmFzZUNyZWF0ZSA9IGJhc2VDcmVhdGU7CgogICAgLyoqCiAgICAgKiBJbml0aWFsaXplcyBhbiBvYmplY3QgY2xvbmUuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBjbG9uZS4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIGluaXRpYWxpemVkIGNsb25lLgogICAgICovCiAgICBmdW5jdGlvbiBpbml0Q2xvbmVPYmplY3Qob2JqZWN0KSB7CiAgICAgIHJldHVybiAodHlwZW9mIG9iamVjdC5jb25zdHJ1Y3RvciA9PSAnZnVuY3Rpb24nICYmICFfaXNQcm90b3R5cGUob2JqZWN0KSkKICAgICAgICA/IF9iYXNlQ3JlYXRlKF9nZXRQcm90b3R5cGUob2JqZWN0KSkKICAgICAgICA6IHt9OwogICAgfQoKICAgIHZhciBfaW5pdENsb25lT2JqZWN0ID0gaW5pdENsb25lT2JqZWN0OwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBtYXBUYWckMyA9ICdbb2JqZWN0IE1hcF0nOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNNYXBgIHdpdGhvdXQgTm9kZS5qcyBvcHRpbWl6YXRpb25zLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgbWFwLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc01hcCh2YWx1ZSkgewogICAgICByZXR1cm4gaXNPYmplY3RMaWtlXzEodmFsdWUpICYmIF9nZXRUYWcodmFsdWUpID09IG1hcFRhZyQzOwogICAgfQoKICAgIHZhciBfYmFzZUlzTWFwID0gYmFzZUlzTWFwOwoKICAgIC8qIE5vZGUuanMgaGVscGVyIHJlZmVyZW5jZXMuICovCiAgICB2YXIgbm9kZUlzTWFwID0gX25vZGVVdGlsICYmIF9ub2RlVXRpbC5pc01hcDsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBgTWFwYCBvYmplY3QuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSA0LjMuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBtYXAsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc01hcChuZXcgTWFwKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzTWFwKG5ldyBXZWFrTWFwKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKi8KICAgIHZhciBpc01hcCA9IG5vZGVJc01hcCA/IF9iYXNlVW5hcnkobm9kZUlzTWFwKSA6IF9iYXNlSXNNYXA7CgogICAgdmFyIGlzTWFwXzEgPSBpc01hcDsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgc2V0VGFnJDMgPSAnW29iamVjdCBTZXRdJzsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmlzU2V0YCB3aXRob3V0IE5vZGUuanMgb3B0aW1pemF0aW9ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHNldCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlSXNTZXQodmFsdWUpIHsKICAgICAgcmV0dXJuIGlzT2JqZWN0TGlrZV8xKHZhbHVlKSAmJiBfZ2V0VGFnKHZhbHVlKSA9PSBzZXRUYWckMzsKICAgIH0KCiAgICB2YXIgX2Jhc2VJc1NldCA9IGJhc2VJc1NldDsKCiAgICAvKiBOb2RlLmpzIGhlbHBlciByZWZlcmVuY2VzLiAqLwogICAgdmFyIG5vZGVJc1NldCA9IF9ub2RlVXRpbCAmJiBfbm9kZVV0aWwuaXNTZXQ7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBjbGFzc2lmaWVkIGFzIGEgYFNldGAgb2JqZWN0LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4zLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgc2V0LCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNTZXQobmV3IFNldCk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc1NldChuZXcgV2Vha1NldCk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICB2YXIgaXNTZXQgPSBub2RlSXNTZXQgPyBfYmFzZVVuYXJ5KG5vZGVJc1NldCkgOiBfYmFzZUlzU2V0OwoKICAgIHZhciBpc1NldF8xID0gaXNTZXQ7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSBiaXRtYXNrcyBmb3IgY2xvbmluZy4gKi8KICAgIHZhciBDTE9ORV9ERUVQX0ZMQUcgPSAxLAogICAgICAgIENMT05FX0ZMQVRfRkxBRyA9IDIsCiAgICAgICAgQ0xPTkVfU1lNQk9MU19GTEFHID0gNDsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgYXJnc1RhZyQyID0gJ1tvYmplY3QgQXJndW1lbnRzXScsCiAgICAgICAgYXJyYXlUYWckMSA9ICdbb2JqZWN0IEFycmF5XScsCiAgICAgICAgYm9vbFRhZyQyID0gJ1tvYmplY3QgQm9vbGVhbl0nLAogICAgICAgIGRhdGVUYWckMiA9ICdbb2JqZWN0IERhdGVdJywKICAgICAgICBlcnJvclRhZyQxID0gJ1tvYmplY3QgRXJyb3JdJywKICAgICAgICBmdW5jVGFnJDIgPSAnW29iamVjdCBGdW5jdGlvbl0nLAogICAgICAgIGdlblRhZyQxID0gJ1tvYmplY3QgR2VuZXJhdG9yRnVuY3Rpb25dJywKICAgICAgICBtYXBUYWckNCA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIG51bWJlclRhZyQyID0gJ1tvYmplY3QgTnVtYmVyXScsCiAgICAgICAgb2JqZWN0VGFnJDIgPSAnW29iamVjdCBPYmplY3RdJywKICAgICAgICByZWdleHBUYWckMiA9ICdbb2JqZWN0IFJlZ0V4cF0nLAogICAgICAgIHNldFRhZyQ0ID0gJ1tvYmplY3QgU2V0XScsCiAgICAgICAgc3RyaW5nVGFnJDIgPSAnW29iamVjdCBTdHJpbmddJywKICAgICAgICBzeW1ib2xUYWckMSA9ICdbb2JqZWN0IFN5bWJvbF0nLAogICAgICAgIHdlYWtNYXBUYWckMiA9ICdbb2JqZWN0IFdlYWtNYXBdJzsKCiAgICB2YXIgYXJyYXlCdWZmZXJUYWckMiA9ICdbb2JqZWN0IEFycmF5QnVmZmVyXScsCiAgICAgICAgZGF0YVZpZXdUYWckMyA9ICdbb2JqZWN0IERhdGFWaWV3XScsCiAgICAgICAgZmxvYXQzMlRhZyQyID0gJ1tvYmplY3QgRmxvYXQzMkFycmF5XScsCiAgICAgICAgZmxvYXQ2NFRhZyQyID0gJ1tvYmplY3QgRmxvYXQ2NEFycmF5XScsCiAgICAgICAgaW50OFRhZyQyID0gJ1tvYmplY3QgSW50OEFycmF5XScsCiAgICAgICAgaW50MTZUYWckMiA9ICdbb2JqZWN0IEludDE2QXJyYXldJywKICAgICAgICBpbnQzMlRhZyQyID0gJ1tvYmplY3QgSW50MzJBcnJheV0nLAogICAgICAgIHVpbnQ4VGFnJDIgPSAnW29iamVjdCBVaW50OEFycmF5XScsCiAgICAgICAgdWludDhDbGFtcGVkVGFnJDIgPSAnW29iamVjdCBVaW50OENsYW1wZWRBcnJheV0nLAogICAgICAgIHVpbnQxNlRhZyQyID0gJ1tvYmplY3QgVWludDE2QXJyYXldJywKICAgICAgICB1aW50MzJUYWckMiA9ICdbb2JqZWN0IFVpbnQzMkFycmF5XSc7CgogICAgLyoqIFVzZWQgdG8gaWRlbnRpZnkgYHRvU3RyaW5nVGFnYCB2YWx1ZXMgc3VwcG9ydGVkIGJ5IGBfLmNsb25lYC4gKi8KICAgIHZhciBjbG9uZWFibGVUYWdzID0ge307CiAgICBjbG9uZWFibGVUYWdzW2FyZ3NUYWckMl0gPSBjbG9uZWFibGVUYWdzW2FycmF5VGFnJDFdID0KICAgIGNsb25lYWJsZVRhZ3NbYXJyYXlCdWZmZXJUYWckMl0gPSBjbG9uZWFibGVUYWdzW2RhdGFWaWV3VGFnJDNdID0KICAgIGNsb25lYWJsZVRhZ3NbYm9vbFRhZyQyXSA9IGNsb25lYWJsZVRhZ3NbZGF0ZVRhZyQyXSA9CiAgICBjbG9uZWFibGVUYWdzW2Zsb2F0MzJUYWckMl0gPSBjbG9uZWFibGVUYWdzW2Zsb2F0NjRUYWckMl0gPQogICAgY2xvbmVhYmxlVGFnc1tpbnQ4VGFnJDJdID0gY2xvbmVhYmxlVGFnc1tpbnQxNlRhZyQyXSA9CiAgICBjbG9uZWFibGVUYWdzW2ludDMyVGFnJDJdID0gY2xvbmVhYmxlVGFnc1ttYXBUYWckNF0gPQogICAgY2xvbmVhYmxlVGFnc1tudW1iZXJUYWckMl0gPSBjbG9uZWFibGVUYWdzW29iamVjdFRhZyQyXSA9CiAgICBjbG9uZWFibGVUYWdzW3JlZ2V4cFRhZyQyXSA9IGNsb25lYWJsZVRhZ3Nbc2V0VGFnJDRdID0KICAgIGNsb25lYWJsZVRhZ3Nbc3RyaW5nVGFnJDJdID0gY2xvbmVhYmxlVGFnc1tzeW1ib2xUYWckMV0gPQogICAgY2xvbmVhYmxlVGFnc1t1aW50OFRhZyQyXSA9IGNsb25lYWJsZVRhZ3NbdWludDhDbGFtcGVkVGFnJDJdID0KICAgIGNsb25lYWJsZVRhZ3NbdWludDE2VGFnJDJdID0gY2xvbmVhYmxlVGFnc1t1aW50MzJUYWckMl0gPSB0cnVlOwogICAgY2xvbmVhYmxlVGFnc1tlcnJvclRhZyQxXSA9IGNsb25lYWJsZVRhZ3NbZnVuY1RhZyQyXSA9CiAgICBjbG9uZWFibGVUYWdzW3dlYWtNYXBUYWckMl0gPSBmYWxzZTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmNsb25lYCBhbmQgYF8uY2xvbmVEZWVwYCB3aGljaCB0cmFja3MKICAgICAqIHRyYXZlcnNlZCBvYmplY3RzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjbG9uZS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4KICAgICAqICAxIC0gRGVlcCBjbG9uZQogICAgICogIDIgLSBGbGF0dGVuIGluaGVyaXRlZCBwcm9wZXJ0aWVzCiAgICAgKiAgNCAtIENsb25lIHN5bWJvbHMKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNsb25pbmcuCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gW2tleV0gVGhlIGtleSBvZiBgdmFsdWVgLgogICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3RdIFRoZSBwYXJlbnQgb2JqZWN0IG9mIGB2YWx1ZWAuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIG9iamVjdHMgYW5kIHRoZWlyIGNsb25lIGNvdW50ZXJwYXJ0cy4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBjbG9uZWQgdmFsdWUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VDbG9uZSh2YWx1ZSwgYml0bWFzaywgY3VzdG9taXplciwga2V5LCBvYmplY3QsIHN0YWNrKSB7CiAgICAgIHZhciByZXN1bHQsCiAgICAgICAgICBpc0RlZXAgPSBiaXRtYXNrICYgQ0xPTkVfREVFUF9GTEFHLAogICAgICAgICAgaXNGbGF0ID0gYml0bWFzayAmIENMT05FX0ZMQVRfRkxBRywKICAgICAgICAgIGlzRnVsbCA9IGJpdG1hc2sgJiBDTE9ORV9TWU1CT0xTX0ZMQUc7CgogICAgICBpZiAoY3VzdG9taXplcikgewogICAgICAgIHJlc3VsdCA9IG9iamVjdCA/IGN1c3RvbWl6ZXIodmFsdWUsIGtleSwgb2JqZWN0LCBzdGFjaykgOiBjdXN0b21pemVyKHZhbHVlKTsKICAgICAgfQogICAgICBpZiAocmVzdWx0ICE9PSB1bmRlZmluZWQpIHsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CiAgICAgIGlmICghaXNPYmplY3RfMSh2YWx1ZSkpIHsKICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgIH0KICAgICAgdmFyIGlzQXJyID0gaXNBcnJheV8xKHZhbHVlKTsKICAgICAgaWYgKGlzQXJyKSB7CiAgICAgICAgcmVzdWx0ID0gX2luaXRDbG9uZUFycmF5KHZhbHVlKTsKICAgICAgICBpZiAoIWlzRGVlcCkgewogICAgICAgICAgcmV0dXJuIF9jb3B5QXJyYXkodmFsdWUsIHJlc3VsdCk7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIHZhciB0YWcgPSBfZ2V0VGFnKHZhbHVlKSwKICAgICAgICAgICAgaXNGdW5jID0gdGFnID09IGZ1bmNUYWckMiB8fCB0YWcgPT0gZ2VuVGFnJDE7CgogICAgICAgIGlmIChpc0J1ZmZlcl8xKHZhbHVlKSkgewogICAgICAgICAgcmV0dXJuIF9jbG9uZUJ1ZmZlcih2YWx1ZSwgaXNEZWVwKTsKICAgICAgICB9CiAgICAgICAgaWYgKHRhZyA9PSBvYmplY3RUYWckMiB8fCB0YWcgPT0gYXJnc1RhZyQyIHx8IChpc0Z1bmMgJiYgIW9iamVjdCkpIHsKICAgICAgICAgIHJlc3VsdCA9IChpc0ZsYXQgfHwgaXNGdW5jKSA/IHt9IDogX2luaXRDbG9uZU9iamVjdCh2YWx1ZSk7CiAgICAgICAgICBpZiAoIWlzRGVlcCkgewogICAgICAgICAgICByZXR1cm4gaXNGbGF0CiAgICAgICAgICAgICAgPyBfY29weVN5bWJvbHNJbih2YWx1ZSwgX2Jhc2VBc3NpZ25JbihyZXN1bHQsIHZhbHVlKSkKICAgICAgICAgICAgICA6IF9jb3B5U3ltYm9scyh2YWx1ZSwgX2Jhc2VBc3NpZ24ocmVzdWx0LCB2YWx1ZSkpOwogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAoIWNsb25lYWJsZVRhZ3NbdGFnXSkgewogICAgICAgICAgICByZXR1cm4gb2JqZWN0ID8gdmFsdWUgOiB7fTsKICAgICAgICAgIH0KICAgICAgICAgIHJlc3VsdCA9IF9pbml0Q2xvbmVCeVRhZyh2YWx1ZSwgdGFnLCBpc0RlZXApOwogICAgICAgIH0KICAgICAgfQogICAgICAvLyBDaGVjayBmb3IgY2lyY3VsYXIgcmVmZXJlbmNlcyBhbmQgcmV0dXJuIGl0cyBjb3JyZXNwb25kaW5nIGNsb25lLgogICAgICBzdGFjayB8fCAoc3RhY2sgPSBuZXcgX1N0YWNrKTsKICAgICAgdmFyIHN0YWNrZWQgPSBzdGFjay5nZXQodmFsdWUpOwogICAgICBpZiAoc3RhY2tlZCkgewogICAgICAgIHJldHVybiBzdGFja2VkOwogICAgICB9CiAgICAgIHN0YWNrLnNldCh2YWx1ZSwgcmVzdWx0KTsKCiAgICAgIGlmIChpc1NldF8xKHZhbHVlKSkgewogICAgICAgIHZhbHVlLmZvckVhY2goZnVuY3Rpb24oc3ViVmFsdWUpIHsKICAgICAgICAgIHJlc3VsdC5hZGQoYmFzZUNsb25lKHN1YlZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdWJWYWx1ZSwgdmFsdWUsIHN0YWNrKSk7CiAgICAgICAgfSk7CiAgICAgIH0gZWxzZSBpZiAoaXNNYXBfMSh2YWx1ZSkpIHsKICAgICAgICB2YWx1ZS5mb3JFYWNoKGZ1bmN0aW9uKHN1YlZhbHVlLCBrZXkpIHsKICAgICAgICAgIHJlc3VsdC5zZXQoa2V5LCBiYXNlQ2xvbmUoc3ViVmFsdWUsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGtleSwgdmFsdWUsIHN0YWNrKSk7CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIHZhciBrZXlzRnVuYyA9IGlzRnVsbAogICAgICAgID8gKGlzRmxhdCA/IF9nZXRBbGxLZXlzSW4gOiBfZ2V0QWxsS2V5cykKICAgICAgICA6IChpc0ZsYXQgPyBrZXlzSW4gOiBrZXlzXzEpOwoKICAgICAgdmFyIHByb3BzID0gaXNBcnIgPyB1bmRlZmluZWQgOiBrZXlzRnVuYyh2YWx1ZSk7CiAgICAgIF9hcnJheUVhY2gocHJvcHMgfHwgdmFsdWUsIGZ1bmN0aW9uKHN1YlZhbHVlLCBrZXkpIHsKICAgICAgICBpZiAocHJvcHMpIHsKICAgICAgICAgIGtleSA9IHN1YlZhbHVlOwogICAgICAgICAgc3ViVmFsdWUgPSB2YWx1ZVtrZXldOwogICAgICAgIH0KICAgICAgICAvLyBSZWN1cnNpdmVseSBwb3B1bGF0ZSBjbG9uZSAoc3VzY2VwdGlibGUgdG8gY2FsbCBzdGFjayBsaW1pdHMpLgogICAgICAgIF9hc3NpZ25WYWx1ZShyZXN1bHQsIGtleSwgYmFzZUNsb25lKHN1YlZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBrZXksIHZhbHVlLCBzdGFjaykpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2Jhc2VDbG9uZSA9IGJhc2VDbG9uZTsKCiAgICAvKiogVXNlZCB0byBjb21wb3NlIGJpdG1hc2tzIGZvciBjbG9uaW5nLiAqLwogICAgdmFyIENMT05FX1NZTUJPTFNfRkxBRyQxID0gNDsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBzaGFsbG93IGNsb25lIG9mIGB2YWx1ZWAuCiAgICAgKgogICAgICogKipOb3RlOioqIFRoaXMgbWV0aG9kIGlzIGxvb3NlbHkgYmFzZWQgb24gdGhlCiAgICAgKiBbc3RydWN0dXJlZCBjbG9uZSBhbGdvcml0aG1dKGh0dHBzOi8vbWRuLmlvL1N0cnVjdHVyZWRfY2xvbmVfYWxnb3JpdGhtKQogICAgICogYW5kIHN1cHBvcnRzIGNsb25pbmcgYXJyYXlzLCBhcnJheSBidWZmZXJzLCBib29sZWFucywgZGF0ZSBvYmplY3RzLCBtYXBzLAogICAgICogbnVtYmVycywgYE9iamVjdGAgb2JqZWN0cywgcmVnZXhlcywgc2V0cywgc3RyaW5ncywgc3ltYm9scywgYW5kIHR5cGVkCiAgICAgKiBhcnJheXMuIFRoZSBvd24gZW51bWVyYWJsZSBwcm9wZXJ0aWVzIG9mIGBhcmd1bWVudHNgIG9iamVjdHMgYXJlIGNsb25lZAogICAgICogYXMgcGxhaW4gb2JqZWN0cy4gQW4gZW1wdHkgb2JqZWN0IGlzIHJldHVybmVkIGZvciB1bmNsb25lYWJsZSB2YWx1ZXMgc3VjaAogICAgICogYXMgZXJyb3Igb2JqZWN0cywgZnVuY3Rpb25zLCBET00gbm9kZXMsIGFuZCBXZWFrTWFwcy4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgY2xvbmVkIHZhbHVlLgogICAgICogQHNlZSBfLmNsb25lRGVlcAogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgb2JqZWN0cyA9IFt7ICdhJzogMSB9LCB7ICdiJzogMiB9XTsKICAgICAqCiAgICAgKiB2YXIgc2hhbGxvdyA9IF8uY2xvbmUob2JqZWN0cyk7CiAgICAgKiBjb25zb2xlLmxvZyhzaGFsbG93WzBdID09PSBvYmplY3RzWzBdKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqLwogICAgZnVuY3Rpb24gY2xvbmUodmFsdWUpIHsKICAgICAgcmV0dXJuIF9iYXNlQ2xvbmUodmFsdWUsIENMT05FX1NZTUJPTFNfRkxBRyQxKTsKICAgIH0KCiAgICB2YXIgY2xvbmVfMSA9IGNsb25lOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyBgdmFsdWVgLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMi40LjAKICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byByZXR1cm4gZnJvbSB0aGUgbmV3IGZ1bmN0aW9uLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgY29uc3RhbnQgZnVuY3Rpb24uCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciBvYmplY3RzID0gXy50aW1lcygyLCBfLmNvbnN0YW50KHsgJ2EnOiAxIH0pKTsKICAgICAqCiAgICAgKiBjb25zb2xlLmxvZyhvYmplY3RzKTsKICAgICAqIC8vID0+IFt7ICdhJzogMSB9LCB7ICdhJzogMSB9XQogICAgICoKICAgICAqIGNvbnNvbGUubG9nKG9iamVjdHNbMF0gPT09IG9iamVjdHNbMV0pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICovCiAgICBmdW5jdGlvbiBjb25zdGFudCR6KHZhbHVlKSB7CiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICByZXR1cm4gdmFsdWU7CiAgICAgIH07CiAgICB9CgogICAgdmFyIGNvbnN0YW50XzEgPSBjb25zdGFudCR6OwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhIGJhc2UgZnVuY3Rpb24gZm9yIG1ldGhvZHMgbGlrZSBgXy5mb3JJbmAgYW5kIGBfLmZvck93bmAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2Zyb21SaWdodF0gU3BlY2lmeSBpdGVyYXRpbmcgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgYmFzZSBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gY3JlYXRlQmFzZUZvcihmcm9tUmlnaHQpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG9iamVjdCwgaXRlcmF0ZWUsIGtleXNGdW5jKSB7CiAgICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICAgIGl0ZXJhYmxlID0gT2JqZWN0KG9iamVjdCksCiAgICAgICAgICAgIHByb3BzID0ga2V5c0Z1bmMob2JqZWN0KSwKICAgICAgICAgICAgbGVuZ3RoID0gcHJvcHMubGVuZ3RoOwoKICAgICAgICB3aGlsZSAobGVuZ3RoLS0pIHsKICAgICAgICAgIHZhciBrZXkgPSBwcm9wc1tmcm9tUmlnaHQgPyBsZW5ndGggOiArK2luZGV4XTsKICAgICAgICAgIGlmIChpdGVyYXRlZShpdGVyYWJsZVtrZXldLCBrZXksIGl0ZXJhYmxlKSA9PT0gZmFsc2UpIHsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHJldHVybiBvYmplY3Q7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9jcmVhdGVCYXNlRm9yID0gY3JlYXRlQmFzZUZvcjsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBiYXNlRm9yT3duYCB3aGljaCBpdGVyYXRlcyBvdmVyIGBvYmplY3RgCiAgICAgKiBwcm9wZXJ0aWVzIHJldHVybmVkIGJ5IGBrZXlzRnVuY2AgYW5kIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgZWFjaCBwcm9wZXJ0eS4KICAgICAqIEl0ZXJhdGVlIGZ1bmN0aW9ucyBtYXkgZXhpdCBpdGVyYXRpb24gZWFybHkgYnkgZXhwbGljaXRseSByZXR1cm5pbmcgYGZhbHNlYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBrZXlzRnVuYyBUaGUgZnVuY3Rpb24gdG8gZ2V0IHRoZSBrZXlzIG9mIGBvYmplY3RgLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyBgb2JqZWN0YC4KICAgICAqLwogICAgdmFyIGJhc2VGb3IgPSBfY3JlYXRlQmFzZUZvcigpOwoKICAgIHZhciBfYmFzZUZvciA9IGJhc2VGb3I7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5mb3JPd25gIHdpdGhvdXQgc3VwcG9ydCBmb3IgaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlRm9yT3duKG9iamVjdCwgaXRlcmF0ZWUpIHsKICAgICAgcmV0dXJuIG9iamVjdCAmJiBfYmFzZUZvcihvYmplY3QsIGl0ZXJhdGVlLCBrZXlzXzEpOwogICAgfQoKICAgIHZhciBfYmFzZUZvck93biA9IGJhc2VGb3JPd247CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgYGJhc2VFYWNoYCBvciBgYmFzZUVhY2hSaWdodGAgZnVuY3Rpb24uCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVhY2hGdW5jIFRoZSBmdW5jdGlvbiB0byBpdGVyYXRlIG92ZXIgYSBjb2xsZWN0aW9uLgogICAgICogQHBhcmFtIHtib29sZWFufSBbZnJvbVJpZ2h0XSBTcGVjaWZ5IGl0ZXJhdGluZyBmcm9tIHJpZ2h0IHRvIGxlZnQuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBiYXNlIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVCYXNlRWFjaChlYWNoRnVuYywgZnJvbVJpZ2h0KSB7CiAgICAgIHJldHVybiBmdW5jdGlvbihjb2xsZWN0aW9uLCBpdGVyYXRlZSkgewogICAgICAgIGlmIChjb2xsZWN0aW9uID09IG51bGwpIHsKICAgICAgICAgIHJldHVybiBjb2xsZWN0aW9uOwogICAgICAgIH0KICAgICAgICBpZiAoIWlzQXJyYXlMaWtlXzEoY29sbGVjdGlvbikpIHsKICAgICAgICAgIHJldHVybiBlYWNoRnVuYyhjb2xsZWN0aW9uLCBpdGVyYXRlZSk7CiAgICAgICAgfQogICAgICAgIHZhciBsZW5ndGggPSBjb2xsZWN0aW9uLmxlbmd0aCwKICAgICAgICAgICAgaW5kZXggPSBmcm9tUmlnaHQgPyBsZW5ndGggOiAtMSwKICAgICAgICAgICAgaXRlcmFibGUgPSBPYmplY3QoY29sbGVjdGlvbik7CgogICAgICAgIHdoaWxlICgoZnJvbVJpZ2h0ID8gaW5kZXgtLSA6ICsraW5kZXggPCBsZW5ndGgpKSB7CiAgICAgICAgICBpZiAoaXRlcmF0ZWUoaXRlcmFibGVbaW5kZXhdLCBpbmRleCwgaXRlcmFibGUpID09PSBmYWxzZSkgewogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGNvbGxlY3Rpb247CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9jcmVhdGVCYXNlRWFjaCA9IGNyZWF0ZUJhc2VFYWNoOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZm9yRWFjaGAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fE9iamVjdH0gUmV0dXJucyBgY29sbGVjdGlvbmAuCiAgICAgKi8KICAgIHZhciBiYXNlRWFjaCA9IF9jcmVhdGVCYXNlRWFjaChfYmFzZUZvck93bik7CgogICAgdmFyIF9iYXNlRWFjaCA9IGJhc2VFYWNoOwoKICAgIC8qKgogICAgICogVGhpcyBtZXRob2QgcmV0dXJucyB0aGUgZmlyc3QgYXJndW1lbnQgaXQgcmVjZWl2ZXMuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgQW55IHZhbHVlLgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgYHZhbHVlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiAxIH07CiAgICAgKgogICAgICogY29uc29sZS5sb2coXy5pZGVudGl0eShvYmplY3QpID09PSBvYmplY3QpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICovCiAgICBmdW5jdGlvbiBpZGVudGl0eSRuKHZhbHVlKSB7CiAgICAgIHJldHVybiB2YWx1ZTsKICAgIH0KCiAgICB2YXIgaWRlbnRpdHlfMSA9IGlkZW50aXR5JG47CgogICAgLyoqCiAgICAgKiBDYXN0cyBgdmFsdWVgIHRvIGBpZGVudGl0eWAgaWYgaXQncyBub3QgYSBmdW5jdGlvbi4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gaW5zcGVjdC4KICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyBjYXN0IGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjYXN0RnVuY3Rpb24odmFsdWUpIHsKICAgICAgcmV0dXJuIHR5cGVvZiB2YWx1ZSA9PSAnZnVuY3Rpb24nID8gdmFsdWUgOiBpZGVudGl0eV8xOwogICAgfQoKICAgIHZhciBfY2FzdEZ1bmN0aW9uID0gY2FzdEZ1bmN0aW9uOwoKICAgIC8qKgogICAgICogSXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZiBgY29sbGVjdGlvbmAgYW5kIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgZWFjaCBlbGVtZW50LgogICAgICogVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQgd2l0aCB0aHJlZSBhcmd1bWVudHM6ICh2YWx1ZSwgaW5kZXh8a2V5LCBjb2xsZWN0aW9uKS4KICAgICAqIEl0ZXJhdGVlIGZ1bmN0aW9ucyBtYXkgZXhpdCBpdGVyYXRpb24gZWFybHkgYnkgZXhwbGljaXRseSByZXR1cm5pbmcgYGZhbHNlYC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogQXMgd2l0aCBvdGhlciAiQ29sbGVjdGlvbnMiIG1ldGhvZHMsIG9iamVjdHMgd2l0aCBhICJsZW5ndGgiCiAgICAgKiBwcm9wZXJ0eSBhcmUgaXRlcmF0ZWQgbGlrZSBhcnJheXMuIFRvIGF2b2lkIHRoaXMgYmVoYXZpb3IgdXNlIGBfLmZvckluYAogICAgICogb3IgYF8uZm9yT3duYCBmb3Igb2JqZWN0IGl0ZXJhdGlvbi4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAYWxpYXMgZWFjaAogICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fE9iamVjdH0gUmV0dXJucyBgY29sbGVjdGlvbmAuCiAgICAgKiBAc2VlIF8uZm9yRWFjaFJpZ2h0CiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uZm9yRWFjaChbMSwgMl0sIGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgKiAgIGNvbnNvbGUubG9nKHZhbHVlKTsKICAgICAqIH0pOwogICAgICogLy8gPT4gTG9ncyBgMWAgdGhlbiBgMmAuCiAgICAgKgogICAgICogXy5mb3JFYWNoKHsgJ2EnOiAxLCAnYic6IDIgfSwgZnVuY3Rpb24odmFsdWUsIGtleSkgewogICAgICogICBjb25zb2xlLmxvZyhrZXkpOwogICAgICogfSk7CiAgICAgKiAvLyA9PiBMb2dzICdhJyB0aGVuICdiJyAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKS4KICAgICAqLwogICAgZnVuY3Rpb24gZm9yRWFjaChjb2xsZWN0aW9uLCBpdGVyYXRlZSkgewogICAgICB2YXIgZnVuYyA9IGlzQXJyYXlfMShjb2xsZWN0aW9uKSA/IF9hcnJheUVhY2ggOiBfYmFzZUVhY2g7CiAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIF9jYXN0RnVuY3Rpb24oaXRlcmF0ZWUpKTsKICAgIH0KCiAgICB2YXIgZm9yRWFjaF8xID0gZm9yRWFjaDsKCiAgICB2YXIgZWFjaCA9IGZvckVhY2hfMTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmZpbHRlcmAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBwcmVkaWNhdGUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZpbHRlcmVkIGFycmF5LgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlRmlsdGVyKGNvbGxlY3Rpb24sIHByZWRpY2F0ZSkgewogICAgICB2YXIgcmVzdWx0ID0gW107CiAgICAgIF9iYXNlRWFjaChjb2xsZWN0aW9uLCBmdW5jdGlvbih2YWx1ZSwgaW5kZXgsIGNvbGxlY3Rpb24pIHsKICAgICAgICBpZiAocHJlZGljYXRlKHZhbHVlLCBpbmRleCwgY29sbGVjdGlvbikpIHsKICAgICAgICAgIHJlc3VsdC5wdXNoKHZhbHVlKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZUZpbHRlciA9IGJhc2VGaWx0ZXI7CgogICAgLyoqIFVzZWQgdG8gc3RhbmQtaW4gZm9yIGB1bmRlZmluZWRgIGhhc2ggdmFsdWVzLiAqLwogICAgdmFyIEhBU0hfVU5ERUZJTkVEJDIgPSAnX19sb2Rhc2hfaGFzaF91bmRlZmluZWRfXyc7CgogICAgLyoqCiAgICAgKiBBZGRzIGB2YWx1ZWAgdG8gdGhlIGFycmF5IGNhY2hlLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAbmFtZSBhZGQKICAgICAqIEBtZW1iZXJPZiBTZXRDYWNoZQogICAgICogQGFsaWFzIHB1c2gKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNhY2hlLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY2FjaGUgaW5zdGFuY2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHNldENhY2hlQWRkKHZhbHVlKSB7CiAgICAgIHRoaXMuX19kYXRhX18uc2V0KHZhbHVlLCBIQVNIX1VOREVGSU5FRCQyKTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9CgogICAgdmFyIF9zZXRDYWNoZUFkZCA9IHNldENhY2hlQWRkOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgaW4gdGhlIGFycmF5IGNhY2hlLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAbmFtZSBoYXMKICAgICAqIEBtZW1iZXJPZiBTZXRDYWNoZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2VhcmNoIGZvci4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgZm91bmQsIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gc2V0Q2FjaGVIYXModmFsdWUpIHsKICAgICAgcmV0dXJuIHRoaXMuX19kYXRhX18uaGFzKHZhbHVlKTsKICAgIH0KCiAgICB2YXIgX3NldENhY2hlSGFzID0gc2V0Q2FjaGVIYXM7CgogICAgLyoqCiAgICAgKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBjYWNoZSBvYmplY3QgdG8gc3RvcmUgdW5pcXVlIHZhbHVlcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQGNvbnN0cnVjdG9yCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbdmFsdWVzXSBUaGUgdmFsdWVzIHRvIGNhY2hlLgogICAgICovCiAgICBmdW5jdGlvbiBTZXRDYWNoZSh2YWx1ZXMpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSB2YWx1ZXMgPT0gbnVsbCA/IDAgOiB2YWx1ZXMubGVuZ3RoOwoKICAgICAgdGhpcy5fX2RhdGFfXyA9IG5ldyBfTWFwQ2FjaGU7CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgdGhpcy5hZGQodmFsdWVzW2luZGV4XSk7CiAgICAgIH0KICAgIH0KCiAgICAvLyBBZGQgbWV0aG9kcyB0byBgU2V0Q2FjaGVgLgogICAgU2V0Q2FjaGUucHJvdG90eXBlLmFkZCA9IFNldENhY2hlLnByb3RvdHlwZS5wdXNoID0gX3NldENhY2hlQWRkOwogICAgU2V0Q2FjaGUucHJvdG90eXBlLmhhcyA9IF9zZXRDYWNoZUhhczsKCiAgICB2YXIgX1NldENhY2hlID0gU2V0Q2FjaGU7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYF8uc29tZWAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlCiAgICAgKiBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBwcmVkaWNhdGUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbnkgZWxlbWVudCBwYXNzZXMgdGhlIHByZWRpY2F0ZSBjaGVjaywKICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFycmF5U29tZShhcnJheSwgcHJlZGljYXRlKSB7CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIGlmIChwcmVkaWNhdGUoYXJyYXlbaW5kZXhdLCBpbmRleCwgYXJyYXkpKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQoKICAgIHZhciBfYXJyYXlTb21lID0gYXJyYXlTb21lOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGEgYGNhY2hlYCB2YWx1ZSBmb3IgYGtleWAgZXhpc3RzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gY2FjaGUgVGhlIGNhY2hlIHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBlbnRyeSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhbiBlbnRyeSBmb3IgYGtleWAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNhY2hlSGFzKGNhY2hlLCBrZXkpIHsKICAgICAgcmV0dXJuIGNhY2hlLmhhcyhrZXkpOwogICAgfQoKICAgIHZhciBfY2FjaGVIYXMgPSBjYWNoZUhhczsKCiAgICAvKiogVXNlZCB0byBjb21wb3NlIGJpdG1hc2tzIGZvciB2YWx1ZSBjb21wYXJpc29ucy4gKi8KICAgIHZhciBDT01QQVJFX1BBUlRJQUxfRkxBRyA9IDEsCiAgICAgICAgQ09NUEFSRV9VTk9SREVSRURfRkxBRyA9IDI7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYGJhc2VJc0VxdWFsRGVlcGAgZm9yIGFycmF5cyB3aXRoIHN1cHBvcnQgZm9yCiAgICAgKiBwYXJ0aWFsIGRlZXAgY29tcGFyaXNvbnMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtBcnJheX0gb3RoZXIgVGhlIG90aGVyIGFycmF5IHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gYml0bWFzayBUaGUgYml0bWFzayBmbGFncy4gU2VlIGBiYXNlSXNFcXVhbGAgZm9yIG1vcmUgZGV0YWlscy4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGN1c3RvbWl6ZXIgVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb21wYXJpc29ucy4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGVxdWFsRnVuYyBUaGUgZnVuY3Rpb24gdG8gZGV0ZXJtaW5lIGVxdWl2YWxlbnRzIG9mIHZhbHVlcy4KICAgICAqIEBwYXJhbSB7T2JqZWN0fSBzdGFjayBUcmFja3MgdHJhdmVyc2VkIGBhcnJheWAgYW5kIGBvdGhlcmAgb2JqZWN0cy4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgYXJyYXlzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVxdWFsQXJyYXlzKGFycmF5LCBvdGhlciwgYml0bWFzaywgY3VzdG9taXplciwgZXF1YWxGdW5jLCBzdGFjaykgewogICAgICB2YXIgaXNQYXJ0aWFsID0gYml0bWFzayAmIENPTVBBUkVfUEFSVElBTF9GTEFHLAogICAgICAgICAgYXJyTGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgb3RoTGVuZ3RoID0gb3RoZXIubGVuZ3RoOwoKICAgICAgaWYgKGFyckxlbmd0aCAhPSBvdGhMZW5ndGggJiYgIShpc1BhcnRpYWwgJiYgb3RoTGVuZ3RoID4gYXJyTGVuZ3RoKSkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICAvLyBBc3N1bWUgY3ljbGljIHZhbHVlcyBhcmUgZXF1YWwuCiAgICAgIHZhciBzdGFja2VkID0gc3RhY2suZ2V0KGFycmF5KTsKICAgICAgaWYgKHN0YWNrZWQgJiYgc3RhY2suZ2V0KG90aGVyKSkgewogICAgICAgIHJldHVybiBzdGFja2VkID09IG90aGVyOwogICAgICB9CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgcmVzdWx0ID0gdHJ1ZSwKICAgICAgICAgIHNlZW4gPSAoYml0bWFzayAmIENPTVBBUkVfVU5PUkRFUkVEX0ZMQUcpID8gbmV3IF9TZXRDYWNoZSA6IHVuZGVmaW5lZDsKCiAgICAgIHN0YWNrLnNldChhcnJheSwgb3RoZXIpOwogICAgICBzdGFjay5zZXQob3RoZXIsIGFycmF5KTsKCiAgICAgIC8vIElnbm9yZSBub24taW5kZXggcHJvcGVydGllcy4KICAgICAgd2hpbGUgKCsraW5kZXggPCBhcnJMZW5ndGgpIHsKICAgICAgICB2YXIgYXJyVmFsdWUgPSBhcnJheVtpbmRleF0sCiAgICAgICAgICAgIG90aFZhbHVlID0gb3RoZXJbaW5kZXhdOwoKICAgICAgICBpZiAoY3VzdG9taXplcikgewogICAgICAgICAgdmFyIGNvbXBhcmVkID0gaXNQYXJ0aWFsCiAgICAgICAgICAgID8gY3VzdG9taXplcihvdGhWYWx1ZSwgYXJyVmFsdWUsIGluZGV4LCBvdGhlciwgYXJyYXksIHN0YWNrKQogICAgICAgICAgICA6IGN1c3RvbWl6ZXIoYXJyVmFsdWUsIG90aFZhbHVlLCBpbmRleCwgYXJyYXksIG90aGVyLCBzdGFjayk7CiAgICAgICAgfQogICAgICAgIGlmIChjb21wYXJlZCAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICBpZiAoY29tcGFyZWQpIHsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICB9CiAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgICAvLyBSZWN1cnNpdmVseSBjb21wYXJlIGFycmF5cyAoc3VzY2VwdGlibGUgdG8gY2FsbCBzdGFjayBsaW1pdHMpLgogICAgICAgIGlmIChzZWVuKSB7CiAgICAgICAgICBpZiAoIV9hcnJheVNvbWUob3RoZXIsIGZ1bmN0aW9uKG90aFZhbHVlLCBvdGhJbmRleCkgewogICAgICAgICAgICAgICAgaWYgKCFfY2FjaGVIYXMoc2Vlbiwgb3RoSW5kZXgpICYmCiAgICAgICAgICAgICAgICAgICAgKGFyclZhbHVlID09PSBvdGhWYWx1ZSB8fCBlcXVhbEZ1bmMoYXJyVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykpKSB7CiAgICAgICAgICAgICAgICAgIHJldHVybiBzZWVuLnB1c2gob3RoSW5kZXgpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0pKSB7CiAgICAgICAgICAgIHJlc3VsdCA9IGZhbHNlOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgaWYgKCEoCiAgICAgICAgICAgICAgYXJyVmFsdWUgPT09IG90aFZhbHVlIHx8CiAgICAgICAgICAgICAgICBlcXVhbEZ1bmMoYXJyVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykKICAgICAgICAgICAgKSkgewogICAgICAgICAgcmVzdWx0ID0gZmFsc2U7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgIH0KICAgICAgc3RhY2tbJ2RlbGV0ZSddKGFycmF5KTsKICAgICAgc3RhY2tbJ2RlbGV0ZSddKG90aGVyKTsKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2VxdWFsQXJyYXlzID0gZXF1YWxBcnJheXM7CgogICAgLyoqCiAgICAgKiBDb252ZXJ0cyBgbWFwYCB0byBpdHMga2V5LXZhbHVlIHBhaXJzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gbWFwIFRoZSBtYXAgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUga2V5LXZhbHVlIHBhaXJzLgogICAgICovCiAgICBmdW5jdGlvbiBtYXBUb0FycmF5KG1hcCkgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIHJlc3VsdCA9IEFycmF5KG1hcC5zaXplKTsKCiAgICAgIG1hcC5mb3JFYWNoKGZ1bmN0aW9uKHZhbHVlLCBrZXkpIHsKICAgICAgICByZXN1bHRbKytpbmRleF0gPSBba2V5LCB2YWx1ZV07CiAgICAgIH0pOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfbWFwVG9BcnJheSA9IG1hcFRvQXJyYXk7CgogICAgLyoqCiAgICAgKiBDb252ZXJ0cyBgc2V0YCB0byBhbiBhcnJheSBvZiBpdHMgdmFsdWVzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc2V0IFRoZSBzZXQgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBzZXRUb0FycmF5KHNldCkgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIHJlc3VsdCA9IEFycmF5KHNldC5zaXplKTsKCiAgICAgIHNldC5mb3JFYWNoKGZ1bmN0aW9uKHZhbHVlKSB7CiAgICAgICAgcmVzdWx0WysraW5kZXhdID0gdmFsdWU7CiAgICAgIH0pOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfc2V0VG9BcnJheSA9IHNldFRvQXJyYXk7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSBiaXRtYXNrcyBmb3IgdmFsdWUgY29tcGFyaXNvbnMuICovCiAgICB2YXIgQ09NUEFSRV9QQVJUSUFMX0ZMQUckMSA9IDEsCiAgICAgICAgQ09NUEFSRV9VTk9SREVSRURfRkxBRyQxID0gMjsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgYm9vbFRhZyQzID0gJ1tvYmplY3QgQm9vbGVhbl0nLAogICAgICAgIGRhdGVUYWckMyA9ICdbb2JqZWN0IERhdGVdJywKICAgICAgICBlcnJvclRhZyQyID0gJ1tvYmplY3QgRXJyb3JdJywKICAgICAgICBtYXBUYWckNSA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIG51bWJlclRhZyQzID0gJ1tvYmplY3QgTnVtYmVyXScsCiAgICAgICAgcmVnZXhwVGFnJDMgPSAnW29iamVjdCBSZWdFeHBdJywKICAgICAgICBzZXRUYWckNSA9ICdbb2JqZWN0IFNldF0nLAogICAgICAgIHN0cmluZ1RhZyQzID0gJ1tvYmplY3QgU3RyaW5nXScsCiAgICAgICAgc3ltYm9sVGFnJDIgPSAnW29iamVjdCBTeW1ib2xdJzsKCiAgICB2YXIgYXJyYXlCdWZmZXJUYWckMyA9ICdbb2JqZWN0IEFycmF5QnVmZmVyXScsCiAgICAgICAgZGF0YVZpZXdUYWckNCA9ICdbb2JqZWN0IERhdGFWaWV3XSc7CgogICAgLyoqIFVzZWQgdG8gY29udmVydCBzeW1ib2xzIHRvIHByaW1pdGl2ZXMgYW5kIHN0cmluZ3MuICovCiAgICB2YXIgc3ltYm9sUHJvdG8kMSA9IF9TeW1ib2wgPyBfU3ltYm9sLnByb3RvdHlwZSA6IHVuZGVmaW5lZCwKICAgICAgICBzeW1ib2xWYWx1ZU9mJDEgPSBzeW1ib2xQcm90byQxID8gc3ltYm9sUHJvdG8kMS52YWx1ZU9mIDogdW5kZWZpbmVkOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlSXNFcXVhbERlZXBgIGZvciBjb21wYXJpbmcgb2JqZWN0cyBvZgogICAgICogdGhlIHNhbWUgYHRvU3RyaW5nVGFnYC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogVGhpcyBmdW5jdGlvbiBvbmx5IHN1cHBvcnRzIGNvbXBhcmluZyB2YWx1ZXMgd2l0aCB0YWdzIG9mCiAgICAgKiBgQm9vbGVhbmAsIGBEYXRlYCwgYEVycm9yYCwgYE51bWJlcmAsIGBSZWdFeHBgLCBvciBgU3RyaW5nYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb3RoZXIgVGhlIG90aGVyIG9iamVjdCB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtzdHJpbmd9IHRhZyBUaGUgYHRvU3RyaW5nVGFnYCBvZiB0aGUgb2JqZWN0cyB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgYmFzZUlzRXF1YWxgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjdXN0b21pemVyIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgY29tcGFyaXNvbnMuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBlcXVhbEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRldGVybWluZSBlcXVpdmFsZW50cyBvZiB2YWx1ZXMuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc3RhY2sgVHJhY2tzIHRyYXZlcnNlZCBgb2JqZWN0YCBhbmQgYG90aGVyYCBvYmplY3RzLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBvYmplY3RzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVxdWFsQnlUYWcob2JqZWN0LCBvdGhlciwgdGFnLCBiaXRtYXNrLCBjdXN0b21pemVyLCBlcXVhbEZ1bmMsIHN0YWNrKSB7CiAgICAgIHN3aXRjaCAodGFnKSB7CiAgICAgICAgY2FzZSBkYXRhVmlld1RhZyQ0OgogICAgICAgICAgaWYgKChvYmplY3QuYnl0ZUxlbmd0aCAhPSBvdGhlci5ieXRlTGVuZ3RoKSB8fAogICAgICAgICAgICAgIChvYmplY3QuYnl0ZU9mZnNldCAhPSBvdGhlci5ieXRlT2Zmc2V0KSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICBvYmplY3QgPSBvYmplY3QuYnVmZmVyOwogICAgICAgICAgb3RoZXIgPSBvdGhlci5idWZmZXI7CgogICAgICAgIGNhc2UgYXJyYXlCdWZmZXJUYWckMzoKICAgICAgICAgIGlmICgob2JqZWN0LmJ5dGVMZW5ndGggIT0gb3RoZXIuYnl0ZUxlbmd0aCkgfHwKICAgICAgICAgICAgICAhZXF1YWxGdW5jKG5ldyBfVWludDhBcnJheShvYmplY3QpLCBuZXcgX1VpbnQ4QXJyYXkob3RoZXIpKSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKCiAgICAgICAgY2FzZSBib29sVGFnJDM6CiAgICAgICAgY2FzZSBkYXRlVGFnJDM6CiAgICAgICAgY2FzZSBudW1iZXJUYWckMzoKICAgICAgICAgIC8vIENvZXJjZSBib29sZWFucyB0byBgMWAgb3IgYDBgIGFuZCBkYXRlcyB0byBtaWxsaXNlY29uZHMuCiAgICAgICAgICAvLyBJbnZhbGlkIGRhdGVzIGFyZSBjb2VyY2VkIHRvIGBOYU5gLgogICAgICAgICAgcmV0dXJuIGVxXzEoK29iamVjdCwgK290aGVyKTsKCiAgICAgICAgY2FzZSBlcnJvclRhZyQyOgogICAgICAgICAgcmV0dXJuIG9iamVjdC5uYW1lID09IG90aGVyLm5hbWUgJiYgb2JqZWN0Lm1lc3NhZ2UgPT0gb3RoZXIubWVzc2FnZTsKCiAgICAgICAgY2FzZSByZWdleHBUYWckMzoKICAgICAgICBjYXNlIHN0cmluZ1RhZyQzOgogICAgICAgICAgLy8gQ29lcmNlIHJlZ2V4ZXMgdG8gc3RyaW5ncyBhbmQgdHJlYXQgc3RyaW5ncywgcHJpbWl0aXZlcyBhbmQgb2JqZWN0cywKICAgICAgICAgIC8vIGFzIGVxdWFsLiBTZWUgaHR0cDovL3d3dy5lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXJlZ2V4cC5wcm90b3R5cGUudG9zdHJpbmcKICAgICAgICAgIC8vIGZvciBtb3JlIGRldGFpbHMuCiAgICAgICAgICByZXR1cm4gb2JqZWN0ID09IChvdGhlciArICcnKTsKCiAgICAgICAgY2FzZSBtYXBUYWckNToKICAgICAgICAgIHZhciBjb252ZXJ0ID0gX21hcFRvQXJyYXk7CgogICAgICAgIGNhc2Ugc2V0VGFnJDU6CiAgICAgICAgICB2YXIgaXNQYXJ0aWFsID0gYml0bWFzayAmIENPTVBBUkVfUEFSVElBTF9GTEFHJDE7CiAgICAgICAgICBjb252ZXJ0IHx8IChjb252ZXJ0ID0gX3NldFRvQXJyYXkpOwoKICAgICAgICAgIGlmIChvYmplY3Quc2l6ZSAhPSBvdGhlci5zaXplICYmICFpc1BhcnRpYWwpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgICAgLy8gQXNzdW1lIGN5Y2xpYyB2YWx1ZXMgYXJlIGVxdWFsLgogICAgICAgICAgdmFyIHN0YWNrZWQgPSBzdGFjay5nZXQob2JqZWN0KTsKICAgICAgICAgIGlmIChzdGFja2VkKSB7CiAgICAgICAgICAgIHJldHVybiBzdGFja2VkID09IG90aGVyOwogICAgICAgICAgfQogICAgICAgICAgYml0bWFzayB8PSBDT01QQVJFX1VOT1JERVJFRF9GTEFHJDE7CgogICAgICAgICAgLy8gUmVjdXJzaXZlbHkgY29tcGFyZSBvYmplY3RzIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgICBzdGFjay5zZXQob2JqZWN0LCBvdGhlcik7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gX2VxdWFsQXJyYXlzKGNvbnZlcnQob2JqZWN0KSwgY29udmVydChvdGhlciksIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spOwogICAgICAgICAgc3RhY2tbJ2RlbGV0ZSddKG9iamVjdCk7CiAgICAgICAgICByZXR1cm4gcmVzdWx0OwoKICAgICAgICBjYXNlIHN5bWJvbFRhZyQyOgogICAgICAgICAgaWYgKHN5bWJvbFZhbHVlT2YkMSkgewogICAgICAgICAgICByZXR1cm4gc3ltYm9sVmFsdWVPZiQxLmNhbGwob2JqZWN0KSA9PSBzeW1ib2xWYWx1ZU9mJDEuY2FsbChvdGhlcik7CiAgICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQoKICAgIHZhciBfZXF1YWxCeVRhZyA9IGVxdWFsQnlUYWc7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSBiaXRtYXNrcyBmb3IgdmFsdWUgY29tcGFyaXNvbnMuICovCiAgICB2YXIgQ09NUEFSRV9QQVJUSUFMX0ZMQUckMiA9IDE7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJGQgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JGEgPSBvYmplY3RQcm90byRkLmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBiYXNlSXNFcXVhbERlZXBgIGZvciBvYmplY3RzIHdpdGggc3VwcG9ydCBmb3IKICAgICAqIHBhcnRpYWwgZGVlcCBjb21wYXJpc29ucy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb3RoZXIgVGhlIG90aGVyIG9iamVjdCB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtudW1iZXJ9IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuIFNlZSBgYmFzZUlzRXF1YWxgIGZvciBtb3JlIGRldGFpbHMuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjdXN0b21pemVyIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgY29tcGFyaXNvbnMuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBlcXVhbEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGRldGVybWluZSBlcXVpdmFsZW50cyBvZiB2YWx1ZXMuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc3RhY2sgVHJhY2tzIHRyYXZlcnNlZCBgb2JqZWN0YCBhbmQgYG90aGVyYCBvYmplY3RzLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBvYmplY3RzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVxdWFsT2JqZWN0cyhvYmplY3QsIG90aGVyLCBiaXRtYXNrLCBjdXN0b21pemVyLCBlcXVhbEZ1bmMsIHN0YWNrKSB7CiAgICAgIHZhciBpc1BhcnRpYWwgPSBiaXRtYXNrICYgQ09NUEFSRV9QQVJUSUFMX0ZMQUckMiwKICAgICAgICAgIG9ialByb3BzID0gX2dldEFsbEtleXMob2JqZWN0KSwKICAgICAgICAgIG9iakxlbmd0aCA9IG9ialByb3BzLmxlbmd0aCwKICAgICAgICAgIG90aFByb3BzID0gX2dldEFsbEtleXMob3RoZXIpLAogICAgICAgICAgb3RoTGVuZ3RoID0gb3RoUHJvcHMubGVuZ3RoOwoKICAgICAgaWYgKG9iakxlbmd0aCAhPSBvdGhMZW5ndGggJiYgIWlzUGFydGlhbCkgewogICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgfQogICAgICB2YXIgaW5kZXggPSBvYmpMZW5ndGg7CiAgICAgIHdoaWxlIChpbmRleC0tKSB7CiAgICAgICAgdmFyIGtleSA9IG9ialByb3BzW2luZGV4XTsKICAgICAgICBpZiAoIShpc1BhcnRpYWwgPyBrZXkgaW4gb3RoZXIgOiBoYXNPd25Qcm9wZXJ0eSRhLmNhbGwob3RoZXIsIGtleSkpKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8vIEFzc3VtZSBjeWNsaWMgdmFsdWVzIGFyZSBlcXVhbC4KICAgICAgdmFyIHN0YWNrZWQgPSBzdGFjay5nZXQob2JqZWN0KTsKICAgICAgaWYgKHN0YWNrZWQgJiYgc3RhY2suZ2V0KG90aGVyKSkgewogICAgICAgIHJldHVybiBzdGFja2VkID09IG90aGVyOwogICAgICB9CiAgICAgIHZhciByZXN1bHQgPSB0cnVlOwogICAgICBzdGFjay5zZXQob2JqZWN0LCBvdGhlcik7CiAgICAgIHN0YWNrLnNldChvdGhlciwgb2JqZWN0KTsKCiAgICAgIHZhciBza2lwQ3RvciA9IGlzUGFydGlhbDsKICAgICAgd2hpbGUgKCsraW5kZXggPCBvYmpMZW5ndGgpIHsKICAgICAgICBrZXkgPSBvYmpQcm9wc1tpbmRleF07CiAgICAgICAgdmFyIG9ialZhbHVlID0gb2JqZWN0W2tleV0sCiAgICAgICAgICAgIG90aFZhbHVlID0gb3RoZXJba2V5XTsKCiAgICAgICAgaWYgKGN1c3RvbWl6ZXIpIHsKICAgICAgICAgIHZhciBjb21wYXJlZCA9IGlzUGFydGlhbAogICAgICAgICAgICA/IGN1c3RvbWl6ZXIob3RoVmFsdWUsIG9ialZhbHVlLCBrZXksIG90aGVyLCBvYmplY3QsIHN0YWNrKQogICAgICAgICAgICA6IGN1c3RvbWl6ZXIob2JqVmFsdWUsIG90aFZhbHVlLCBrZXksIG9iamVjdCwgb3RoZXIsIHN0YWNrKTsKICAgICAgICB9CiAgICAgICAgLy8gUmVjdXJzaXZlbHkgY29tcGFyZSBvYmplY3RzIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgaWYgKCEoY29tcGFyZWQgPT09IHVuZGVmaW5lZAogICAgICAgICAgICAgID8gKG9ialZhbHVlID09PSBvdGhWYWx1ZSB8fCBlcXVhbEZ1bmMob2JqVmFsdWUsIG90aFZhbHVlLCBiaXRtYXNrLCBjdXN0b21pemVyLCBzdGFjaykpCiAgICAgICAgICAgICAgOiBjb21wYXJlZAogICAgICAgICAgICApKSB7CiAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgICBza2lwQ3RvciB8fCAoc2tpcEN0b3IgPSBrZXkgPT0gJ2NvbnN0cnVjdG9yJyk7CiAgICAgIH0KICAgICAgaWYgKHJlc3VsdCAmJiAhc2tpcEN0b3IpIHsKICAgICAgICB2YXIgb2JqQ3RvciA9IG9iamVjdC5jb25zdHJ1Y3RvciwKICAgICAgICAgICAgb3RoQ3RvciA9IG90aGVyLmNvbnN0cnVjdG9yOwoKICAgICAgICAvLyBOb24gYE9iamVjdGAgb2JqZWN0IGluc3RhbmNlcyB3aXRoIGRpZmZlcmVudCBjb25zdHJ1Y3RvcnMgYXJlIG5vdCBlcXVhbC4KICAgICAgICBpZiAob2JqQ3RvciAhPSBvdGhDdG9yICYmCiAgICAgICAgICAgICgnY29uc3RydWN0b3InIGluIG9iamVjdCAmJiAnY29uc3RydWN0b3InIGluIG90aGVyKSAmJgogICAgICAgICAgICAhKHR5cGVvZiBvYmpDdG9yID09ICdmdW5jdGlvbicgJiYgb2JqQ3RvciBpbnN0YW5jZW9mIG9iakN0b3IgJiYKICAgICAgICAgICAgICB0eXBlb2Ygb3RoQ3RvciA9PSAnZnVuY3Rpb24nICYmIG90aEN0b3IgaW5zdGFuY2VvZiBvdGhDdG9yKSkgewogICAgICAgICAgcmVzdWx0ID0gZmFsc2U7CiAgICAgICAgfQogICAgICB9CiAgICAgIHN0YWNrWydkZWxldGUnXShvYmplY3QpOwogICAgICBzdGFja1snZGVsZXRlJ10ob3RoZXIpOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfZXF1YWxPYmplY3RzID0gZXF1YWxPYmplY3RzOwoKICAgIC8qKiBVc2VkIHRvIGNvbXBvc2UgYml0bWFza3MgZm9yIHZhbHVlIGNvbXBhcmlzb25zLiAqLwogICAgdmFyIENPTVBBUkVfUEFSVElBTF9GTEFHJDMgPSAxOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBhcmdzVGFnJDMgPSAnW29iamVjdCBBcmd1bWVudHNdJywKICAgICAgICBhcnJheVRhZyQyID0gJ1tvYmplY3QgQXJyYXldJywKICAgICAgICBvYmplY3RUYWckMyA9ICdbb2JqZWN0IE9iamVjdF0nOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RQcm90byRlID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogVXNlZCB0byBjaGVjayBvYmplY3RzIGZvciBvd24gcHJvcGVydGllcy4gKi8KICAgIHZhciBoYXNPd25Qcm9wZXJ0eSRiID0gb2JqZWN0UHJvdG8kZS5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKioKICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZUlzRXF1YWxgIGZvciBhcnJheXMgYW5kIG9iamVjdHMgd2hpY2ggcGVyZm9ybXMKICAgICAqIGRlZXAgY29tcGFyaXNvbnMgYW5kIHRyYWNrcyB0cmF2ZXJzZWQgb2JqZWN0cyBlbmFibGluZyBvYmplY3RzIHdpdGggY2lyY3VsYXIKICAgICAqIHJlZmVyZW5jZXMgdG8gYmUgY29tcGFyZWQuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtPYmplY3R9IG90aGVyIFRoZSBvdGhlciBvYmplY3QgdG8gY29tcGFyZS4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBiaXRtYXNrIFRoZSBiaXRtYXNrIGZsYWdzLiBTZWUgYGJhc2VJc0VxdWFsYCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY3VzdG9taXplciBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGNvbXBhcmlzb25zLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZXF1YWxGdW5jIFRoZSBmdW5jdGlvbiB0byBkZXRlcm1pbmUgZXF1aXZhbGVudHMgb2YgdmFsdWVzLgogICAgICogQHBhcmFtIHtPYmplY3R9IFtzdGFja10gVHJhY2tzIHRyYXZlcnNlZCBgb2JqZWN0YCBhbmQgYG90aGVyYCBvYmplY3RzLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIHRoZSBvYmplY3RzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc0VxdWFsRGVlcChvYmplY3QsIG90aGVyLCBiaXRtYXNrLCBjdXN0b21pemVyLCBlcXVhbEZ1bmMsIHN0YWNrKSB7CiAgICAgIHZhciBvYmpJc0FyciA9IGlzQXJyYXlfMShvYmplY3QpLAogICAgICAgICAgb3RoSXNBcnIgPSBpc0FycmF5XzEob3RoZXIpLAogICAgICAgICAgb2JqVGFnID0gb2JqSXNBcnIgPyBhcnJheVRhZyQyIDogX2dldFRhZyhvYmplY3QpLAogICAgICAgICAgb3RoVGFnID0gb3RoSXNBcnIgPyBhcnJheVRhZyQyIDogX2dldFRhZyhvdGhlcik7CgogICAgICBvYmpUYWcgPSBvYmpUYWcgPT0gYXJnc1RhZyQzID8gb2JqZWN0VGFnJDMgOiBvYmpUYWc7CiAgICAgIG90aFRhZyA9IG90aFRhZyA9PSBhcmdzVGFnJDMgPyBvYmplY3RUYWckMyA6IG90aFRhZzsKCiAgICAgIHZhciBvYmpJc09iaiA9IG9ialRhZyA9PSBvYmplY3RUYWckMywKICAgICAgICAgIG90aElzT2JqID0gb3RoVGFnID09IG9iamVjdFRhZyQzLAogICAgICAgICAgaXNTYW1lVGFnID0gb2JqVGFnID09IG90aFRhZzsKCiAgICAgIGlmIChpc1NhbWVUYWcgJiYgaXNCdWZmZXJfMShvYmplY3QpKSB7CiAgICAgICAgaWYgKCFpc0J1ZmZlcl8xKG90aGVyKSkgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICBvYmpJc0FyciA9IHRydWU7CiAgICAgICAgb2JqSXNPYmogPSBmYWxzZTsKICAgICAgfQogICAgICBpZiAoaXNTYW1lVGFnICYmICFvYmpJc09iaikgewogICAgICAgIHN0YWNrIHx8IChzdGFjayA9IG5ldyBfU3RhY2spOwogICAgICAgIHJldHVybiAob2JqSXNBcnIgfHwgaXNUeXBlZEFycmF5XzEob2JqZWN0KSkKICAgICAgICAgID8gX2VxdWFsQXJyYXlzKG9iamVjdCwgb3RoZXIsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spCiAgICAgICAgICA6IF9lcXVhbEJ5VGFnKG9iamVjdCwgb3RoZXIsIG9ialRhZywgYml0bWFzaywgY3VzdG9taXplciwgZXF1YWxGdW5jLCBzdGFjayk7CiAgICAgIH0KICAgICAgaWYgKCEoYml0bWFzayAmIENPTVBBUkVfUEFSVElBTF9GTEFHJDMpKSB7CiAgICAgICAgdmFyIG9iaklzV3JhcHBlZCA9IG9iaklzT2JqICYmIGhhc093blByb3BlcnR5JGIuY2FsbChvYmplY3QsICdfX3dyYXBwZWRfXycpLAogICAgICAgICAgICBvdGhJc1dyYXBwZWQgPSBvdGhJc09iaiAmJiBoYXNPd25Qcm9wZXJ0eSRiLmNhbGwob3RoZXIsICdfX3dyYXBwZWRfXycpOwoKICAgICAgICBpZiAob2JqSXNXcmFwcGVkIHx8IG90aElzV3JhcHBlZCkgewogICAgICAgICAgdmFyIG9ialVud3JhcHBlZCA9IG9iaklzV3JhcHBlZCA/IG9iamVjdC52YWx1ZSgpIDogb2JqZWN0LAogICAgICAgICAgICAgIG90aFVud3JhcHBlZCA9IG90aElzV3JhcHBlZCA/IG90aGVyLnZhbHVlKCkgOiBvdGhlcjsKCiAgICAgICAgICBzdGFjayB8fCAoc3RhY2sgPSBuZXcgX1N0YWNrKTsKICAgICAgICAgIHJldHVybiBlcXVhbEZ1bmMob2JqVW53cmFwcGVkLCBvdGhVbndyYXBwZWQsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIHN0YWNrKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgaWYgKCFpc1NhbWVUYWcpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgc3RhY2sgfHwgKHN0YWNrID0gbmV3IF9TdGFjayk7CiAgICAgIHJldHVybiBfZXF1YWxPYmplY3RzKG9iamVjdCwgb3RoZXIsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGVxdWFsRnVuYywgc3RhY2spOwogICAgfQoKICAgIHZhciBfYmFzZUlzRXF1YWxEZWVwID0gYmFzZUlzRXF1YWxEZWVwOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaXNFcXVhbGAgd2hpY2ggc3VwcG9ydHMgcGFydGlhbCBjb21wYXJpc29ucwogICAgICogYW5kIHRyYWNrcyB0cmF2ZXJzZWQgb2JqZWN0cy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAqIEBwYXJhbSB7Kn0gb3RoZXIgVGhlIG90aGVyIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IGJpdG1hc2sgVGhlIGJpdG1hc2sgZmxhZ3MuCiAgICAgKiAgMSAtIFVub3JkZXJlZCBjb21wYXJpc29uCiAgICAgKiAgMiAtIFBhcnRpYWwgY29tcGFyaXNvbgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgY29tcGFyaXNvbnMuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIGB2YWx1ZWAgYW5kIGBvdGhlcmAgb2JqZWN0cy4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiB0aGUgdmFsdWVzIGFyZSBlcXVpdmFsZW50LCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc0VxdWFsKHZhbHVlLCBvdGhlciwgYml0bWFzaywgY3VzdG9taXplciwgc3RhY2spIHsKICAgICAgaWYgKHZhbHVlID09PSBvdGhlcikgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsIHx8IG90aGVyID09IG51bGwgfHwgKCFpc09iamVjdExpa2VfMSh2YWx1ZSkgJiYgIWlzT2JqZWN0TGlrZV8xKG90aGVyKSkpIHsKICAgICAgICByZXR1cm4gdmFsdWUgIT09IHZhbHVlICYmIG90aGVyICE9PSBvdGhlcjsKICAgICAgfQogICAgICByZXR1cm4gX2Jhc2VJc0VxdWFsRGVlcCh2YWx1ZSwgb3RoZXIsIGJpdG1hc2ssIGN1c3RvbWl6ZXIsIGJhc2VJc0VxdWFsLCBzdGFjayk7CiAgICB9CgogICAgdmFyIF9iYXNlSXNFcXVhbCA9IGJhc2VJc0VxdWFsOwoKICAgIC8qKiBVc2VkIHRvIGNvbXBvc2UgYml0bWFza3MgZm9yIHZhbHVlIGNvbXBhcmlzb25zLiAqLwogICAgdmFyIENPTVBBUkVfUEFSVElBTF9GTEFHJDQgPSAxLAogICAgICAgIENPTVBBUkVfVU5PUkRFUkVEX0ZMQUckMiA9IDI7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc01hdGNoYCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpbnNwZWN0LgogICAgICogQHBhcmFtIHtPYmplY3R9IHNvdXJjZSBUaGUgb2JqZWN0IG9mIHByb3BlcnR5IHZhbHVlcyB0byBtYXRjaC4KICAgICAqIEBwYXJhbSB7QXJyYXl9IG1hdGNoRGF0YSBUaGUgcHJvcGVydHkgbmFtZXMsIHZhbHVlcywgYW5kIGNvbXBhcmUgZmxhZ3MgdG8gbWF0Y2guCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY3VzdG9taXplcl0gVGhlIGZ1bmN0aW9uIHRvIGN1c3RvbWl6ZSBjb21wYXJpc29ucy4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgb2JqZWN0YCBpcyBhIG1hdGNoLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJc01hdGNoKG9iamVjdCwgc291cmNlLCBtYXRjaERhdGEsIGN1c3RvbWl6ZXIpIHsKICAgICAgdmFyIGluZGV4ID0gbWF0Y2hEYXRhLmxlbmd0aCwKICAgICAgICAgIGxlbmd0aCA9IGluZGV4LAogICAgICAgICAgbm9DdXN0b21pemVyID0gIWN1c3RvbWl6ZXI7CgogICAgICBpZiAob2JqZWN0ID09IG51bGwpIHsKICAgICAgICByZXR1cm4gIWxlbmd0aDsKICAgICAgfQogICAgICBvYmplY3QgPSBPYmplY3Qob2JqZWN0KTsKICAgICAgd2hpbGUgKGluZGV4LS0pIHsKICAgICAgICB2YXIgZGF0YSA9IG1hdGNoRGF0YVtpbmRleF07CiAgICAgICAgaWYgKChub0N1c3RvbWl6ZXIgJiYgZGF0YVsyXSkKICAgICAgICAgICAgICA/IGRhdGFbMV0gIT09IG9iamVjdFtkYXRhWzBdXQogICAgICAgICAgICAgIDogIShkYXRhWzBdIGluIG9iamVjdCkKICAgICAgICAgICAgKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICB9CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgZGF0YSA9IG1hdGNoRGF0YVtpbmRleF07CiAgICAgICAgdmFyIGtleSA9IGRhdGFbMF0sCiAgICAgICAgICAgIG9ialZhbHVlID0gb2JqZWN0W2tleV0sCiAgICAgICAgICAgIHNyY1ZhbHVlID0gZGF0YVsxXTsKCiAgICAgICAgaWYgKG5vQ3VzdG9taXplciAmJiBkYXRhWzJdKSB7CiAgICAgICAgICBpZiAob2JqVmFsdWUgPT09IHVuZGVmaW5lZCAmJiAhKGtleSBpbiBvYmplY3QpKSB7CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgdmFyIHN0YWNrID0gbmV3IF9TdGFjazsKICAgICAgICAgIGlmIChjdXN0b21pemVyKSB7CiAgICAgICAgICAgIHZhciByZXN1bHQgPSBjdXN0b21pemVyKG9ialZhbHVlLCBzcmNWYWx1ZSwga2V5LCBvYmplY3QsIHNvdXJjZSwgc3RhY2spOwogICAgICAgICAgfQogICAgICAgICAgaWYgKCEocmVzdWx0ID09PSB1bmRlZmluZWQKICAgICAgICAgICAgICAgID8gX2Jhc2VJc0VxdWFsKHNyY1ZhbHVlLCBvYmpWYWx1ZSwgQ09NUEFSRV9QQVJUSUFMX0ZMQUckNCB8IENPTVBBUkVfVU5PUkRFUkVEX0ZMQUckMiwgY3VzdG9taXplciwgc3RhY2spCiAgICAgICAgICAgICAgICA6IHJlc3VsdAogICAgICAgICAgICAgICkpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KCiAgICB2YXIgX2Jhc2VJc01hdGNoID0gYmFzZUlzTWF0Y2g7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBzdWl0YWJsZSBmb3Igc3RyaWN0IGVxdWFsaXR5IGNvbXBhcmlzb25zLCBpLmUuIGA9PT1gLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlmIHN1aXRhYmxlIGZvciBzdHJpY3QKICAgICAqICBlcXVhbGl0eSBjb21wYXJpc29ucywgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBpc1N0cmljdENvbXBhcmFibGUodmFsdWUpIHsKICAgICAgcmV0dXJuIHZhbHVlID09PSB2YWx1ZSAmJiAhaXNPYmplY3RfMSh2YWx1ZSk7CiAgICB9CgogICAgdmFyIF9pc1N0cmljdENvbXBhcmFibGUgPSBpc1N0cmljdENvbXBhcmFibGU7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBwcm9wZXJ0eSBuYW1lcywgdmFsdWVzLCBhbmQgY29tcGFyZSBmbGFncyBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBtYXRjaCBkYXRhIG9mIGBvYmplY3RgLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRNYXRjaERhdGEob2JqZWN0KSB7CiAgICAgIHZhciByZXN1bHQgPSBrZXlzXzEob2JqZWN0KSwKICAgICAgICAgIGxlbmd0aCA9IHJlc3VsdC5sZW5ndGg7CgogICAgICB3aGlsZSAobGVuZ3RoLS0pIHsKICAgICAgICB2YXIga2V5ID0gcmVzdWx0W2xlbmd0aF0sCiAgICAgICAgICAgIHZhbHVlID0gb2JqZWN0W2tleV07CgogICAgICAgIHJlc3VsdFtsZW5ndGhdID0gW2tleSwgdmFsdWUsIF9pc1N0cmljdENvbXBhcmFibGUodmFsdWUpXTsKICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfZ2V0TWF0Y2hEYXRhID0gZ2V0TWF0Y2hEYXRhOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBtYXRjaGVzUHJvcGVydHlgIGZvciBzb3VyY2UgdmFsdWVzIHN1aXRhYmxlCiAgICAgKiBmb3Igc3RyaWN0IGVxdWFsaXR5IGNvbXBhcmlzb25zLCBpLmUuIGA9PT1gLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30ga2V5IFRoZSBrZXkgb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAqIEBwYXJhbSB7Kn0gc3JjVmFsdWUgVGhlIHZhbHVlIHRvIG1hdGNoLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gbWF0Y2hlc1N0cmljdENvbXBhcmFibGUoa2V5LCBzcmNWYWx1ZSkgewogICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgaWYgKG9iamVjdCA9PSBudWxsKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIHJldHVybiBvYmplY3Rba2V5XSA9PT0gc3JjVmFsdWUgJiYKICAgICAgICAgIChzcmNWYWx1ZSAhPT0gdW5kZWZpbmVkIHx8IChrZXkgaW4gT2JqZWN0KG9iamVjdCkpKTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgX21hdGNoZXNTdHJpY3RDb21wYXJhYmxlID0gbWF0Y2hlc1N0cmljdENvbXBhcmFibGU7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5tYXRjaGVzYCB3aGljaCBkb2Vzbid0IGNsb25lIGBzb3VyY2VgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBvYmplY3Qgb2YgcHJvcGVydHkgdmFsdWVzIHRvIG1hdGNoLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc3BlYyBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZU1hdGNoZXMoc291cmNlKSB7CiAgICAgIHZhciBtYXRjaERhdGEgPSBfZ2V0TWF0Y2hEYXRhKHNvdXJjZSk7CiAgICAgIGlmIChtYXRjaERhdGEubGVuZ3RoID09IDEgJiYgbWF0Y2hEYXRhWzBdWzJdKSB7CiAgICAgICAgcmV0dXJuIF9tYXRjaGVzU3RyaWN0Q29tcGFyYWJsZShtYXRjaERhdGFbMF1bMF0sIG1hdGNoRGF0YVswXVsxXSk7CiAgICAgIH0KICAgICAgcmV0dXJuIGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgIHJldHVybiBvYmplY3QgPT09IHNvdXJjZSB8fCBfYmFzZUlzTWF0Y2gob2JqZWN0LCBzb3VyY2UsIG1hdGNoRGF0YSk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9iYXNlTWF0Y2hlcyA9IGJhc2VNYXRjaGVzOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBzeW1ib2xUYWckMyA9ICdbb2JqZWN0IFN5bWJvbF0nOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgY2xhc3NpZmllZCBhcyBhIGBTeW1ib2xgIHByaW1pdGl2ZSBvciBvYmplY3QuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSA0LjAuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBzeW1ib2wsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc1N5bWJvbChTeW1ib2wuaXRlcmF0b3IpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNTeW1ib2woJ2FiYycpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gaXNTeW1ib2wodmFsdWUpIHsKICAgICAgcmV0dXJuIHR5cGVvZiB2YWx1ZSA9PSAnc3ltYm9sJyB8fAogICAgICAgIChpc09iamVjdExpa2VfMSh2YWx1ZSkgJiYgX2Jhc2VHZXRUYWcodmFsdWUpID09IHN5bWJvbFRhZyQzKTsKICAgIH0KCiAgICB2YXIgaXNTeW1ib2xfMSA9IGlzU3ltYm9sOwoKICAgIC8qKiBVc2VkIHRvIG1hdGNoIHByb3BlcnR5IG5hbWVzIHdpdGhpbiBwcm9wZXJ0eSBwYXRocy4gKi8KICAgIHZhciByZUlzRGVlcFByb3AgPSAvXC58XFsoPzpbXltcXV0qfChbIiddKSg/Oig/IVwxKVteXFxdfFxcLikqP1wxKVxdLywKICAgICAgICByZUlzUGxhaW5Qcm9wID0gL15cdyokLzsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgcHJvcGVydHkgbmFtZSBhbmQgbm90IGEgcHJvcGVydHkgcGF0aC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcGFyYW0ge09iamVjdH0gW29iamVjdF0gVGhlIG9iamVjdCB0byBxdWVyeSBrZXlzIG9uLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYSBwcm9wZXJ0eSBuYW1lLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzS2V5KHZhbHVlLCBvYmplY3QpIHsKICAgICAgaWYgKGlzQXJyYXlfMSh2YWx1ZSkpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgdmFsdWU7CiAgICAgIGlmICh0eXBlID09ICdudW1iZXInIHx8IHR5cGUgPT0gJ3N5bWJvbCcgfHwgdHlwZSA9PSAnYm9vbGVhbicgfHwKICAgICAgICAgIHZhbHVlID09IG51bGwgfHwgaXNTeW1ib2xfMSh2YWx1ZSkpIHsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQogICAgICByZXR1cm4gcmVJc1BsYWluUHJvcC50ZXN0KHZhbHVlKSB8fCAhcmVJc0RlZXBQcm9wLnRlc3QodmFsdWUpIHx8CiAgICAgICAgKG9iamVjdCAhPSBudWxsICYmIHZhbHVlIGluIE9iamVjdChvYmplY3QpKTsKICAgIH0KCiAgICB2YXIgX2lzS2V5ID0gaXNLZXk7CgogICAgLyoqIEVycm9yIG1lc3NhZ2UgY29uc3RhbnRzLiAqLwogICAgdmFyIEZVTkNfRVJST1JfVEVYVCA9ICdFeHBlY3RlZCBhIGZ1bmN0aW9uJzsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0IG1lbW9pemVzIHRoZSByZXN1bHQgb2YgYGZ1bmNgLiBJZiBgcmVzb2x2ZXJgIGlzCiAgICAgKiBwcm92aWRlZCwgaXQgZGV0ZXJtaW5lcyB0aGUgY2FjaGUga2V5IGZvciBzdG9yaW5nIHRoZSByZXN1bHQgYmFzZWQgb24gdGhlCiAgICAgKiBhcmd1bWVudHMgcHJvdmlkZWQgdG8gdGhlIG1lbW9pemVkIGZ1bmN0aW9uLiBCeSBkZWZhdWx0LCB0aGUgZmlyc3QgYXJndW1lbnQKICAgICAqIHByb3ZpZGVkIHRvIHRoZSBtZW1vaXplZCBmdW5jdGlvbiBpcyB1c2VkIGFzIHRoZSBtYXAgY2FjaGUga2V5LiBUaGUgYGZ1bmNgCiAgICAgKiBpcyBpbnZva2VkIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIHRoZSBtZW1vaXplZCBmdW5jdGlvbi4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogVGhlIGNhY2hlIGlzIGV4cG9zZWQgYXMgdGhlIGBjYWNoZWAgcHJvcGVydHkgb24gdGhlIG1lbW9pemVkCiAgICAgKiBmdW5jdGlvbi4gSXRzIGNyZWF0aW9uIG1heSBiZSBjdXN0b21pemVkIGJ5IHJlcGxhY2luZyB0aGUgYF8ubWVtb2l6ZS5DYWNoZWAKICAgICAqIGNvbnN0cnVjdG9yIHdpdGggb25lIHdob3NlIGluc3RhbmNlcyBpbXBsZW1lbnQgdGhlCiAgICAgKiBbYE1hcGBdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXByb3BlcnRpZXMtb2YtdGhlLW1hcC1wcm90b3R5cGUtb2JqZWN0KQogICAgICogbWV0aG9kIGludGVyZmFjZSBvZiBgY2xlYXJgLCBgZGVsZXRlYCwgYGdldGAsIGBoYXNgLCBhbmQgYHNldGAuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IEZ1bmN0aW9uCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBoYXZlIGl0cyBvdXRwdXQgbWVtb2l6ZWQuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcmVzb2x2ZXJdIFRoZSBmdW5jdGlvbiB0byByZXNvbHZlIHRoZSBjYWNoZSBrZXkuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBtZW1vaXplZCBmdW5jdGlvbi4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiAxLCAnYic6IDIgfTsKICAgICAqIHZhciBvdGhlciA9IHsgJ2MnOiAzLCAnZCc6IDQgfTsKICAgICAqCiAgICAgKiB2YXIgdmFsdWVzID0gXy5tZW1vaXplKF8udmFsdWVzKTsKICAgICAqIHZhbHVlcyhvYmplY3QpOwogICAgICogLy8gPT4gWzEsIDJdCiAgICAgKgogICAgICogdmFsdWVzKG90aGVyKTsKICAgICAqIC8vID0+IFszLCA0XQogICAgICoKICAgICAqIG9iamVjdC5hID0gMjsKICAgICAqIHZhbHVlcyhvYmplY3QpOwogICAgICogLy8gPT4gWzEsIDJdCiAgICAgKgogICAgICogLy8gTW9kaWZ5IHRoZSByZXN1bHQgY2FjaGUuCiAgICAgKiB2YWx1ZXMuY2FjaGUuc2V0KG9iamVjdCwgWydhJywgJ2InXSk7CiAgICAgKiB2YWx1ZXMob2JqZWN0KTsKICAgICAqIC8vID0+IFsnYScsICdiJ10KICAgICAqCiAgICAgKiAvLyBSZXBsYWNlIGBfLm1lbW9pemUuQ2FjaGVgLgogICAgICogXy5tZW1vaXplLkNhY2hlID0gV2Vha01hcDsKICAgICAqLwogICAgZnVuY3Rpb24gbWVtb2l6ZSQxKGZ1bmMsIHJlc29sdmVyKSB7CiAgICAgIGlmICh0eXBlb2YgZnVuYyAhPSAnZnVuY3Rpb24nIHx8IChyZXNvbHZlciAhPSBudWxsICYmIHR5cGVvZiByZXNvbHZlciAhPSAnZnVuY3Rpb24nKSkgewogICAgICAgIHRocm93IG5ldyBUeXBlRXJyb3IoRlVOQ19FUlJPUl9URVhUKTsKICAgICAgfQogICAgICB2YXIgbWVtb2l6ZWQgPSBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgYXJncyA9IGFyZ3VtZW50cywKICAgICAgICAgICAga2V5ID0gcmVzb2x2ZXIgPyByZXNvbHZlci5hcHBseSh0aGlzLCBhcmdzKSA6IGFyZ3NbMF0sCiAgICAgICAgICAgIGNhY2hlID0gbWVtb2l6ZWQuY2FjaGU7CgogICAgICAgIGlmIChjYWNoZS5oYXMoa2V5KSkgewogICAgICAgICAgcmV0dXJuIGNhY2hlLmdldChrZXkpOwogICAgICAgIH0KICAgICAgICB2YXIgcmVzdWx0ID0gZnVuYy5hcHBseSh0aGlzLCBhcmdzKTsKICAgICAgICBtZW1vaXplZC5jYWNoZSA9IGNhY2hlLnNldChrZXksIHJlc3VsdCkgfHwgY2FjaGU7CiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgfTsKICAgICAgbWVtb2l6ZWQuY2FjaGUgPSBuZXcgKG1lbW9pemUkMS5DYWNoZSB8fCBfTWFwQ2FjaGUpOwogICAgICByZXR1cm4gbWVtb2l6ZWQ7CiAgICB9CgogICAgLy8gRXhwb3NlIGBNYXBDYWNoZWAuCiAgICBtZW1vaXplJDEuQ2FjaGUgPSBfTWFwQ2FjaGU7CgogICAgdmFyIG1lbW9pemVfMSQxID0gbWVtb2l6ZSQxOwoKICAgIC8qKiBVc2VkIGFzIHRoZSBtYXhpbXVtIG1lbW9pemUgY2FjaGUgc2l6ZS4gKi8KICAgIHZhciBNQVhfTUVNT0laRV9TSVpFID0gNTAwOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLm1lbW9pemVgIHdoaWNoIGNsZWFycyB0aGUgbWVtb2l6ZWQgZnVuY3Rpb24ncwogICAgICogY2FjaGUgd2hlbiBpdCBleGNlZWRzIGBNQVhfTUVNT0laRV9TSVpFYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gaGF2ZSBpdHMgb3V0cHV0IG1lbW9pemVkLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgbWVtb2l6ZWQgZnVuY3Rpb24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIG1lbW9pemVDYXBwZWQoZnVuYykgewogICAgICB2YXIgcmVzdWx0ID0gbWVtb2l6ZV8xJDEoZnVuYywgZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgaWYgKGNhY2hlLnNpemUgPT09IE1BWF9NRU1PSVpFX1NJWkUpIHsKICAgICAgICAgIGNhY2hlLmNsZWFyKCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBrZXk7CiAgICAgIH0pOwoKICAgICAgdmFyIGNhY2hlID0gcmVzdWx0LmNhY2hlOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfbWVtb2l6ZUNhcHBlZCA9IG1lbW9pemVDYXBwZWQ7CgogICAgLyoqIFVzZWQgdG8gbWF0Y2ggcHJvcGVydHkgbmFtZXMgd2l0aGluIHByb3BlcnR5IHBhdGhzLiAqLwogICAgdmFyIHJlUHJvcE5hbWUgPSAvW14uW1xdXSt8XFsoPzooLT9cZCsoPzpcLlxkKyk/KXwoWyInXSkoKD86KD8hXDIpW15cXF18XFwuKSo/KVwyKVxdfCg/PSg/OlwufFxbXF0pKD86XC58XFtcXXwkKSkvZzsKCiAgICAvKiogVXNlZCB0byBtYXRjaCBiYWNrc2xhc2hlcyBpbiBwcm9wZXJ0eSBwYXRocy4gKi8KICAgIHZhciByZUVzY2FwZUNoYXIgPSAvXFwoXFwpPy9nOwoKICAgIC8qKgogICAgICogQ29udmVydHMgYHN0cmluZ2AgdG8gYSBwcm9wZXJ0eSBwYXRoIGFycmF5LgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgcHJvcGVydHkgcGF0aCBhcnJheS4KICAgICAqLwogICAgdmFyIHN0cmluZ1RvUGF0aCA9IF9tZW1vaXplQ2FwcGVkKGZ1bmN0aW9uKHN0cmluZykgewogICAgICB2YXIgcmVzdWx0ID0gW107CiAgICAgIGlmIChzdHJpbmcuY2hhckNvZGVBdCgwKSA9PT0gNDYgLyogLiAqLykgewogICAgICAgIHJlc3VsdC5wdXNoKCcnKTsKICAgICAgfQogICAgICBzdHJpbmcucmVwbGFjZShyZVByb3BOYW1lLCBmdW5jdGlvbihtYXRjaCwgbnVtYmVyLCBxdW90ZSwgc3ViU3RyaW5nKSB7CiAgICAgICAgcmVzdWx0LnB1c2gocXVvdGUgPyBzdWJTdHJpbmcucmVwbGFjZShyZUVzY2FwZUNoYXIsICckMScpIDogKG51bWJlciB8fCBtYXRjaCkpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0pOwoKICAgIHZhciBfc3RyaW5nVG9QYXRoID0gc3RyaW5nVG9QYXRoOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLm1hcGAgZm9yIGFycmF5cyB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlCiAgICAgKiBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgbWFwcGVkIGFycmF5LgogICAgICovCiAgICBmdW5jdGlvbiBhcnJheU1hcChhcnJheSwgaXRlcmF0ZWUpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aCwKICAgICAgICAgIHJlc3VsdCA9IEFycmF5KGxlbmd0aCk7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHJlc3VsdFtpbmRleF0gPSBpdGVyYXRlZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSk7CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2FycmF5TWFwID0gYXJyYXlNYXA7CgogICAgLyoqIFVzZWQgYXMgcmVmZXJlbmNlcyBmb3IgdmFyaW91cyBgTnVtYmVyYCBjb25zdGFudHMuICovCiAgICB2YXIgSU5GSU5JVFkgPSAxIC8gMDsKCiAgICAvKiogVXNlZCB0byBjb252ZXJ0IHN5bWJvbHMgdG8gcHJpbWl0aXZlcyBhbmQgc3RyaW5ncy4gKi8KICAgIHZhciBzeW1ib2xQcm90byQyID0gX1N5bWJvbCA/IF9TeW1ib2wucHJvdG90eXBlIDogdW5kZWZpbmVkLAogICAgICAgIHN5bWJvbFRvU3RyaW5nID0gc3ltYm9sUHJvdG8kMiA/IHN5bWJvbFByb3RvJDIudG9TdHJpbmcgOiB1bmRlZmluZWQ7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy50b1N0cmluZ2Agd2hpY2ggZG9lc24ndCBjb252ZXJ0IG51bGxpc2gKICAgICAqIHZhbHVlcyB0byBlbXB0eSBzdHJpbmdzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBwcm9jZXNzLgogICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgc3RyaW5nLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlVG9TdHJpbmcodmFsdWUpIHsKICAgICAgLy8gRXhpdCBlYXJseSBmb3Igc3RyaW5ncyB0byBhdm9pZCBhIHBlcmZvcm1hbmNlIGhpdCBpbiBzb21lIGVudmlyb25tZW50cy4KICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnc3RyaW5nJykgewogICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgfQogICAgICBpZiAoaXNBcnJheV8xKHZhbHVlKSkgewogICAgICAgIC8vIFJlY3Vyc2l2ZWx5IGNvbnZlcnQgdmFsdWVzIChzdXNjZXB0aWJsZSB0byBjYWxsIHN0YWNrIGxpbWl0cykuCiAgICAgICAgcmV0dXJuIF9hcnJheU1hcCh2YWx1ZSwgYmFzZVRvU3RyaW5nKSArICcnOwogICAgICB9CiAgICAgIGlmIChpc1N5bWJvbF8xKHZhbHVlKSkgewogICAgICAgIHJldHVybiBzeW1ib2xUb1N0cmluZyA/IHN5bWJvbFRvU3RyaW5nLmNhbGwodmFsdWUpIDogJyc7CiAgICAgIH0KICAgICAgdmFyIHJlc3VsdCA9ICh2YWx1ZSArICcnKTsKICAgICAgcmV0dXJuIChyZXN1bHQgPT0gJzAnICYmICgxIC8gdmFsdWUpID09IC1JTkZJTklUWSkgPyAnLTAnIDogcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZVRvU3RyaW5nID0gYmFzZVRvU3RyaW5nOwoKICAgIC8qKgogICAgICogQ29udmVydHMgYHZhbHVlYCB0byBhIHN0cmluZy4gQW4gZW1wdHkgc3RyaW5nIGlzIHJldHVybmVkIGZvciBgbnVsbGAKICAgICAqIGFuZCBgdW5kZWZpbmVkYCB2YWx1ZXMuIFRoZSBzaWduIG9mIGAtMGAgaXMgcHJlc2VydmVkLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb252ZXJ0LgogICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgY29udmVydGVkIHN0cmluZy4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy50b1N0cmluZyhudWxsKTsKICAgICAqIC8vID0+ICcnCiAgICAgKgogICAgICogXy50b1N0cmluZygtMCk7CiAgICAgKiAvLyA9PiAnLTAnCiAgICAgKgogICAgICogXy50b1N0cmluZyhbMSwgMiwgM10pOwogICAgICogLy8gPT4gJzEsMiwzJwogICAgICovCiAgICBmdW5jdGlvbiB0b1N0cmluZyh2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPT0gbnVsbCA/ICcnIDogX2Jhc2VUb1N0cmluZyh2YWx1ZSk7CiAgICB9CgogICAgdmFyIHRvU3RyaW5nXzEgPSB0b1N0cmluZzsKCiAgICAvKioKICAgICAqIENhc3RzIGB2YWx1ZWAgdG8gYSBwYXRoIGFycmF5IGlmIGl0J3Mgbm90IG9uZS4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gaW5zcGVjdC4KICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0XSBUaGUgb2JqZWN0IHRvIHF1ZXJ5IGtleXMgb24uCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGNhc3QgcHJvcGVydHkgcGF0aCBhcnJheS4KICAgICAqLwogICAgZnVuY3Rpb24gY2FzdFBhdGgodmFsdWUsIG9iamVjdCkgewogICAgICBpZiAoaXNBcnJheV8xKHZhbHVlKSkgewogICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgfQogICAgICByZXR1cm4gX2lzS2V5KHZhbHVlLCBvYmplY3QpID8gW3ZhbHVlXSA6IF9zdHJpbmdUb1BhdGgodG9TdHJpbmdfMSh2YWx1ZSkpOwogICAgfQoKICAgIHZhciBfY2FzdFBhdGggPSBjYXN0UGF0aDsKCiAgICAvKiogVXNlZCBhcyByZWZlcmVuY2VzIGZvciB2YXJpb3VzIGBOdW1iZXJgIGNvbnN0YW50cy4gKi8KICAgIHZhciBJTkZJTklUWSQxID0gMSAvIDA7CgogICAgLyoqCiAgICAgKiBDb252ZXJ0cyBgdmFsdWVgIHRvIGEgc3RyaW5nIGtleSBpZiBpdCdzIG5vdCBhIHN0cmluZyBvciBzeW1ib2wuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGluc3BlY3QuCiAgICAgKiBAcmV0dXJucyB7c3RyaW5nfHN5bWJvbH0gUmV0dXJucyB0aGUga2V5LgogICAgICovCiAgICBmdW5jdGlvbiB0b0tleSh2YWx1ZSkgewogICAgICBpZiAodHlwZW9mIHZhbHVlID09ICdzdHJpbmcnIHx8IGlzU3ltYm9sXzEodmFsdWUpKSB7CiAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICB9CiAgICAgIHZhciByZXN1bHQgPSAodmFsdWUgKyAnJyk7CiAgICAgIHJldHVybiAocmVzdWx0ID09ICcwJyAmJiAoMSAvIHZhbHVlKSA9PSAtSU5GSU5JVFkkMSkgPyAnLTAnIDogcmVzdWx0OwogICAgfQoKICAgIHZhciBfdG9LZXkgPSB0b0tleTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmdldGAgd2l0aG91dCBzdXBwb3J0IGZvciBkZWZhdWx0IHZhbHVlcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXNvbHZlZCB2YWx1ZS4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZUdldChvYmplY3QsIHBhdGgpIHsKICAgICAgcGF0aCA9IF9jYXN0UGF0aChwYXRoLCBvYmplY3QpOwoKICAgICAgdmFyIGluZGV4ID0gMCwKICAgICAgICAgIGxlbmd0aCA9IHBhdGgubGVuZ3RoOwoKICAgICAgd2hpbGUgKG9iamVjdCAhPSBudWxsICYmIGluZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgb2JqZWN0ID0gb2JqZWN0W190b0tleShwYXRoW2luZGV4KytdKV07CiAgICAgIH0KICAgICAgcmV0dXJuIChpbmRleCAmJiBpbmRleCA9PSBsZW5ndGgpID8gb2JqZWN0IDogdW5kZWZpbmVkOwogICAgfQoKICAgIHZhciBfYmFzZUdldCA9IGJhc2VHZXQ7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSB2YWx1ZSBhdCBgcGF0aGAgb2YgYG9iamVjdGAuIElmIHRoZSByZXNvbHZlZCB2YWx1ZSBpcwogICAgICogYHVuZGVmaW5lZGAsIHRoZSBgZGVmYXVsdFZhbHVlYCBpcyByZXR1cm5lZCBpbiBpdHMgcGxhY2UuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAzLjcuMAogICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAqIEBwYXJhbSB7Kn0gW2RlZmF1bHRWYWx1ZV0gVGhlIHZhbHVlIHJldHVybmVkIGZvciBgdW5kZWZpbmVkYCByZXNvbHZlZCB2YWx1ZXMuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgcmVzb2x2ZWQgdmFsdWUuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogW3sgJ2InOiB7ICdjJzogMyB9IH1dIH07CiAgICAgKgogICAgICogXy5nZXQob2JqZWN0LCAnYVswXS5iLmMnKTsKICAgICAqIC8vID0+IDMKICAgICAqCiAgICAgKiBfLmdldChvYmplY3QsIFsnYScsICcwJywgJ2InLCAnYyddKTsKICAgICAqIC8vID0+IDMKICAgICAqCiAgICAgKiBfLmdldChvYmplY3QsICdhLmIuYycsICdkZWZhdWx0Jyk7CiAgICAgKiAvLyA9PiAnZGVmYXVsdCcKICAgICAqLwogICAgZnVuY3Rpb24gZ2V0JGMob2JqZWN0LCBwYXRoLCBkZWZhdWx0VmFsdWUpIHsKICAgICAgdmFyIHJlc3VsdCA9IG9iamVjdCA9PSBudWxsID8gdW5kZWZpbmVkIDogX2Jhc2VHZXQob2JqZWN0LCBwYXRoKTsKICAgICAgcmV0dXJuIHJlc3VsdCA9PT0gdW5kZWZpbmVkID8gZGVmYXVsdFZhbHVlIDogcmVzdWx0OwogICAgfQoKICAgIHZhciBnZXRfMSA9IGdldCRjOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaGFzSW5gIHdpdGhvdXQgc3VwcG9ydCBmb3IgZGVlcCBwYXRocy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IFtvYmplY3RdIFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30ga2V5IFRoZSBrZXkgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYGtleWAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VIYXNJbihvYmplY3QsIGtleSkgewogICAgICByZXR1cm4gb2JqZWN0ICE9IG51bGwgJiYga2V5IGluIE9iamVjdChvYmplY3QpOwogICAgfQoKICAgIHZhciBfYmFzZUhhc0luID0gYmFzZUhhc0luOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGBwYXRoYCBleGlzdHMgb24gYG9iamVjdGAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIHRvIGNoZWNrLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaGFzRnVuYyBUaGUgZnVuY3Rpb24gdG8gY2hlY2sgcHJvcGVydGllcy4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgcGF0aGAgZXhpc3RzLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGhhc1BhdGgob2JqZWN0LCBwYXRoLCBoYXNGdW5jKSB7CiAgICAgIHBhdGggPSBfY2FzdFBhdGgocGF0aCwgb2JqZWN0KTsKCiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gcGF0aC5sZW5ndGgsCiAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKCiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgdmFyIGtleSA9IF90b0tleShwYXRoW2luZGV4XSk7CiAgICAgICAgaWYgKCEocmVzdWx0ID0gb2JqZWN0ICE9IG51bGwgJiYgaGFzRnVuYyhvYmplY3QsIGtleSkpKSB7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgb2JqZWN0ID0gb2JqZWN0W2tleV07CiAgICAgIH0KICAgICAgaWYgKHJlc3VsdCB8fCArK2luZGV4ICE9IGxlbmd0aCkgewogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KICAgICAgbGVuZ3RoID0gb2JqZWN0ID09IG51bGwgPyAwIDogb2JqZWN0Lmxlbmd0aDsKICAgICAgcmV0dXJuICEhbGVuZ3RoICYmIGlzTGVuZ3RoXzEobGVuZ3RoKSAmJiBfaXNJbmRleChrZXksIGxlbmd0aCkgJiYKICAgICAgICAoaXNBcnJheV8xKG9iamVjdCkgfHwgaXNBcmd1bWVudHNfMShvYmplY3QpKTsKICAgIH0KCiAgICB2YXIgX2hhc1BhdGggPSBoYXNQYXRoOwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGBwYXRoYCBpcyBhIGRpcmVjdCBvciBpbmhlcml0ZWQgcHJvcGVydHkgb2YgYG9iamVjdGAuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSA0LjAuMAogICAgICogQGNhdGVnb3J5IE9iamVjdAogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHBhdGhgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgb2JqZWN0ID0gXy5jcmVhdGUoeyAnYSc6IF8uY3JlYXRlKHsgJ2InOiAyIH0pIH0pOwogICAgICoKICAgICAqIF8uaGFzSW4ob2JqZWN0LCAnYScpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaGFzSW4ob2JqZWN0LCAnYS5iJyk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5oYXNJbihvYmplY3QsIFsnYScsICdiJ10pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaGFzSW4ob2JqZWN0LCAnYicpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gaGFzSW4ob2JqZWN0LCBwYXRoKSB7CiAgICAgIHJldHVybiBvYmplY3QgIT0gbnVsbCAmJiBfaGFzUGF0aChvYmplY3QsIHBhdGgsIF9iYXNlSGFzSW4pOwogICAgfQoKICAgIHZhciBoYXNJbl8xID0gaGFzSW47CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSBiaXRtYXNrcyBmb3IgdmFsdWUgY29tcGFyaXNvbnMuICovCiAgICB2YXIgQ09NUEFSRV9QQVJUSUFMX0ZMQUckNSA9IDEsCiAgICAgICAgQ09NUEFSRV9VTk9SREVSRURfRkxBRyQzID0gMjsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLm1hdGNoZXNQcm9wZXJ0eWAgd2hpY2ggZG9lc24ndCBjbG9uZSBgc3JjVmFsdWVgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gZ2V0LgogICAgICogQHBhcmFtIHsqfSBzcmNWYWx1ZSBUaGUgdmFsdWUgdG8gbWF0Y2guCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBzcGVjIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlTWF0Y2hlc1Byb3BlcnR5KHBhdGgsIHNyY1ZhbHVlKSB7CiAgICAgIGlmIChfaXNLZXkocGF0aCkgJiYgX2lzU3RyaWN0Q29tcGFyYWJsZShzcmNWYWx1ZSkpIHsKICAgICAgICByZXR1cm4gX21hdGNoZXNTdHJpY3RDb21wYXJhYmxlKF90b0tleShwYXRoKSwgc3JjVmFsdWUpOwogICAgICB9CiAgICAgIHJldHVybiBmdW5jdGlvbihvYmplY3QpIHsKICAgICAgICB2YXIgb2JqVmFsdWUgPSBnZXRfMShvYmplY3QsIHBhdGgpOwogICAgICAgIHJldHVybiAob2JqVmFsdWUgPT09IHVuZGVmaW5lZCAmJiBvYmpWYWx1ZSA9PT0gc3JjVmFsdWUpCiAgICAgICAgICA/IGhhc0luXzEob2JqZWN0LCBwYXRoKQogICAgICAgICAgOiBfYmFzZUlzRXF1YWwoc3JjVmFsdWUsIG9ialZhbHVlLCBDT01QQVJFX1BBUlRJQUxfRkxBRyQ1IHwgQ09NUEFSRV9VTk9SREVSRURfRkxBRyQzKTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgX2Jhc2VNYXRjaGVzUHJvcGVydHkgPSBiYXNlTWF0Y2hlc1Byb3BlcnR5OwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ucHJvcGVydHlgIHdpdGhvdXQgc3VwcG9ydCBmb3IgZGVlcCBwYXRocy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBhY2Nlc3NvciBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZVByb3BlcnR5KGtleSkgewogICAgICByZXR1cm4gZnVuY3Rpb24ob2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8gdW5kZWZpbmVkIDogb2JqZWN0W2tleV07CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9iYXNlUHJvcGVydHkgPSBiYXNlUHJvcGVydHk7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYGJhc2VQcm9wZXJ0eWAgd2hpY2ggc3VwcG9ydHMgZGVlcCBwYXRocy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IHBhdGggVGhlIHBhdGggb2YgdGhlIHByb3BlcnR5IHRvIGdldC4KICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFjY2Vzc29yIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlUHJvcGVydHlEZWVwKHBhdGgpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKG9iamVjdCkgewogICAgICAgIHJldHVybiBfYmFzZUdldChvYmplY3QsIHBhdGgpOwogICAgICB9OwogICAgfQoKICAgIHZhciBfYmFzZVByb3BlcnR5RGVlcCA9IGJhc2VQcm9wZXJ0eURlZXA7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gdGhhdCByZXR1cm5zIHRoZSB2YWx1ZSBhdCBgcGF0aGAgb2YgYSBnaXZlbiBvYmplY3QuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAyLjQuMAogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIG9mIHRoZSBwcm9wZXJ0eSB0byBnZXQuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBhY2Nlc3NvciBmdW5jdGlvbi4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIG9iamVjdHMgPSBbCiAgICAgKiAgIHsgJ2EnOiB7ICdiJzogMiB9IH0sCiAgICAgKiAgIHsgJ2EnOiB7ICdiJzogMSB9IH0KICAgICAqIF07CiAgICAgKgogICAgICogXy5tYXAob2JqZWN0cywgXy5wcm9wZXJ0eSgnYS5iJykpOwogICAgICogLy8gPT4gWzIsIDFdCiAgICAgKgogICAgICogXy5tYXAoXy5zb3J0Qnkob2JqZWN0cywgXy5wcm9wZXJ0eShbJ2EnLCAnYiddKSksICdhLmInKTsKICAgICAqIC8vID0+IFsxLCAyXQogICAgICovCiAgICBmdW5jdGlvbiBwcm9wZXJ0eSQxKHBhdGgpIHsKICAgICAgcmV0dXJuIF9pc0tleShwYXRoKSA/IF9iYXNlUHJvcGVydHkoX3RvS2V5KHBhdGgpKSA6IF9iYXNlUHJvcGVydHlEZWVwKHBhdGgpOwogICAgfQoKICAgIHZhciBwcm9wZXJ0eV8xID0gcHJvcGVydHkkMTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLml0ZXJhdGVlYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSBbdmFsdWU9Xy5pZGVudGl0eV0gVGhlIHZhbHVlIHRvIGNvbnZlcnQgdG8gYW4gaXRlcmF0ZWUuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIGl0ZXJhdGVlLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlSXRlcmF0ZWUodmFsdWUpIHsKICAgICAgLy8gRG9uJ3Qgc3RvcmUgdGhlIGB0eXBlb2ZgIHJlc3VsdCBpbiBhIHZhcmlhYmxlIHRvIGF2b2lkIGEgSklUIGJ1ZyBpbiBTYWZhcmkgOS4KICAgICAgLy8gU2VlIGh0dHBzOi8vYnVncy53ZWJraXQub3JnL3Nob3dfYnVnLmNnaT9pZD0xNTYwMzQgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnZnVuY3Rpb24nKSB7CiAgICAgICAgcmV0dXJuIHZhbHVlOwogICAgICB9CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgcmV0dXJuIGlkZW50aXR5XzE7CiAgICAgIH0KICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnb2JqZWN0JykgewogICAgICAgIHJldHVybiBpc0FycmF5XzEodmFsdWUpCiAgICAgICAgICA/IF9iYXNlTWF0Y2hlc1Byb3BlcnR5KHZhbHVlWzBdLCB2YWx1ZVsxXSkKICAgICAgICAgIDogX2Jhc2VNYXRjaGVzKHZhbHVlKTsKICAgICAgfQogICAgICByZXR1cm4gcHJvcGVydHlfMSh2YWx1ZSk7CiAgICB9CgogICAgdmFyIF9iYXNlSXRlcmF0ZWUgPSBiYXNlSXRlcmF0ZWU7CgogICAgLyoqCiAgICAgKiBJdGVyYXRlcyBvdmVyIGVsZW1lbnRzIG9mIGBjb2xsZWN0aW9uYCwgcmV0dXJuaW5nIGFuIGFycmF5IG9mIGFsbCBlbGVtZW50cwogICAgICogYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yLiBUaGUgcHJlZGljYXRlIGlzIGludm9rZWQgd2l0aCB0aHJlZQogICAgICogYXJndW1lbnRzOiAodmFsdWUsIGluZGV4fGtleSwgY29sbGVjdGlvbikuCiAgICAgKgogICAgICogKipOb3RlOioqIFVubGlrZSBgXy5yZW1vdmVgLCB0aGlzIG1ldGhvZCByZXR1cm5zIGEgbmV3IGFycmF5LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBmaWx0ZXJlZCBhcnJheS4KICAgICAqIEBzZWUgXy5yZWplY3QKICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIHVzZXJzID0gWwogICAgICogICB7ICd1c2VyJzogJ2Jhcm5leScsICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAnYWdlJzogNDAsICdhY3RpdmUnOiBmYWxzZSB9CiAgICAgKiBdOwogICAgICoKICAgICAqIF8uZmlsdGVyKHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiAhby5hY3RpdmU7IH0pOwogICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydmcmVkJ10KICAgICAqCiAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc2AgaXRlcmF0ZWUgc2hvcnRoYW5kLgogICAgICogXy5maWx0ZXIodXNlcnMsIHsgJ2FnZSc6IDM2LCAnYWN0aXZlJzogdHJ1ZSB9KTsKICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFsnYmFybmV5J10KICAgICAqCiAgICAgKiAvLyBUaGUgYF8ubWF0Y2hlc1Byb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgKiBfLmZpbHRlcih1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICogLy8gPT4gb2JqZWN0cyBmb3IgWydmcmVkJ10KICAgICAqCiAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8uZmlsdGVyKHVzZXJzLCAnYWN0aXZlJyk7CiAgICAgKiAvLyA9PiBvYmplY3RzIGZvciBbJ2Jhcm5leSddCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZpbHRlcihjb2xsZWN0aW9uLCBwcmVkaWNhdGUpIHsKICAgICAgdmFyIGZ1bmMgPSBpc0FycmF5XzEoY29sbGVjdGlvbikgPyBfYXJyYXlGaWx0ZXIgOiBfYmFzZUZpbHRlcjsKICAgICAgcmV0dXJuIGZ1bmMoY29sbGVjdGlvbiwgX2Jhc2VJdGVyYXRlZShwcmVkaWNhdGUpKTsKICAgIH0KCiAgICB2YXIgZmlsdGVyXzEgPSBmaWx0ZXI7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJGYgPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JGMgPSBvYmplY3RQcm90byRmLmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaGFzYCB3aXRob3V0IHN1cHBvcnQgZm9yIGRlZXAgcGF0aHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbb2JqZWN0XSBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtBcnJheXxzdHJpbmd9IGtleSBUaGUga2V5IHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBrZXlgIGV4aXN0cywgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlSGFzKG9iamVjdCwga2V5KSB7CiAgICAgIHJldHVybiBvYmplY3QgIT0gbnVsbCAmJiBoYXNPd25Qcm9wZXJ0eSRjLmNhbGwob2JqZWN0LCBrZXkpOwogICAgfQoKICAgIHZhciBfYmFzZUhhcyA9IGJhc2VIYXM7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHBhdGhgIGlzIGEgZGlyZWN0IHByb3BlcnR5IG9mIGBvYmplY3RgLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAqIEBwYXJhbSB7QXJyYXl8c3RyaW5nfSBwYXRoIFRoZSBwYXRoIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGBwYXRoYCBleGlzdHMsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIG9iamVjdCA9IHsgJ2EnOiB7ICdiJzogMiB9IH07CiAgICAgKiB2YXIgb3RoZXIgPSBfLmNyZWF0ZSh7ICdhJzogXy5jcmVhdGUoeyAnYic6IDIgfSkgfSk7CiAgICAgKgogICAgICogXy5oYXMob2JqZWN0LCAnYScpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaGFzKG9iamVjdCwgJ2EuYicpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaGFzKG9iamVjdCwgWydhJywgJ2InXSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5oYXMob3RoZXIsICdhJyk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBoYXMob2JqZWN0LCBwYXRoKSB7CiAgICAgIHJldHVybiBvYmplY3QgIT0gbnVsbCAmJiBfaGFzUGF0aChvYmplY3QsIHBhdGgsIF9iYXNlSGFzKTsKICAgIH0KCiAgICB2YXIgaGFzXzEgPSBoYXM7CgogICAgLyoqIGBPYmplY3QjdG9TdHJpbmdgIHJlc3VsdCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG1hcFRhZyQ2ID0gJ1tvYmplY3QgTWFwXScsCiAgICAgICAgc2V0VGFnJDYgPSAnW29iamVjdCBTZXRdJzsKCiAgICAvKiogVXNlZCBmb3IgYnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMuICovCiAgICB2YXIgb2JqZWN0UHJvdG8kZyA9IE9iamVjdC5wcm90b3R5cGU7CgogICAgLyoqIFVzZWQgdG8gY2hlY2sgb2JqZWN0cyBmb3Igb3duIHByb3BlcnRpZXMuICovCiAgICB2YXIgaGFzT3duUHJvcGVydHkkZCA9IG9iamVjdFByb3RvJGcuaGFzT3duUHJvcGVydHk7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHZhbHVlYCBpcyBhbiBlbXB0eSBvYmplY3QsIGNvbGxlY3Rpb24sIG1hcCwgb3Igc2V0LgogICAgICoKICAgICAqIE9iamVjdHMgYXJlIGNvbnNpZGVyZWQgZW1wdHkgaWYgdGhleSBoYXZlIG5vIG93biBlbnVtZXJhYmxlIHN0cmluZyBrZXllZAogICAgICogcHJvcGVydGllcy4KICAgICAqCiAgICAgKiBBcnJheS1saWtlIHZhbHVlcyBzdWNoIGFzIGBhcmd1bWVudHNgIG9iamVjdHMsIGFycmF5cywgYnVmZmVycywgc3RyaW5ncywgb3IKICAgICAqIGpRdWVyeS1saWtlIGNvbGxlY3Rpb25zIGFyZSBjb25zaWRlcmVkIGVtcHR5IGlmIHRoZXkgaGF2ZSBhIGBsZW5ndGhgIG9mIGAwYC4KICAgICAqIFNpbWlsYXJseSwgbWFwcyBhbmQgc2V0cyBhcmUgY29uc2lkZXJlZCBlbXB0eSBpZiB0aGV5IGhhdmUgYSBgc2l6ZWAgb2YgYDBgLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGVtcHR5LCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNFbXB0eShudWxsKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzRW1wdHkodHJ1ZSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc0VtcHR5KDEpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNFbXB0eShbMSwgMiwgM10pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmlzRW1wdHkoeyAnYSc6IDEgfSk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBpc0VtcHR5KHZhbHVlKSB7CiAgICAgIGlmICh2YWx1ZSA9PSBudWxsKSB7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KICAgICAgaWYgKGlzQXJyYXlMaWtlXzEodmFsdWUpICYmCiAgICAgICAgICAoaXNBcnJheV8xKHZhbHVlKSB8fCB0eXBlb2YgdmFsdWUgPT0gJ3N0cmluZycgfHwgdHlwZW9mIHZhbHVlLnNwbGljZSA9PSAnZnVuY3Rpb24nIHx8CiAgICAgICAgICAgIGlzQnVmZmVyXzEodmFsdWUpIHx8IGlzVHlwZWRBcnJheV8xKHZhbHVlKSB8fCBpc0FyZ3VtZW50c18xKHZhbHVlKSkpIHsKICAgICAgICByZXR1cm4gIXZhbHVlLmxlbmd0aDsKICAgICAgfQogICAgICB2YXIgdGFnID0gX2dldFRhZyh2YWx1ZSk7CiAgICAgIGlmICh0YWcgPT0gbWFwVGFnJDYgfHwgdGFnID09IHNldFRhZyQ2KSB7CiAgICAgICAgcmV0dXJuICF2YWx1ZS5zaXplOwogICAgICB9CiAgICAgIGlmIChfaXNQcm90b3R5cGUodmFsdWUpKSB7CiAgICAgICAgcmV0dXJuICFfYmFzZUtleXModmFsdWUpLmxlbmd0aDsKICAgICAgfQogICAgICBmb3IgKHZhciBrZXkgaW4gdmFsdWUpIHsKICAgICAgICBpZiAoaGFzT3duUHJvcGVydHkkZC5jYWxsKHZhbHVlLCBrZXkpKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0cnVlOwogICAgfQoKICAgIHZhciBpc0VtcHR5XzEgPSBpc0VtcHR5OwoKICAgIC8qKgogICAgICogQ2hlY2tzIGlmIGB2YWx1ZWAgaXMgYHVuZGVmaW5lZGAuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNoZWNrLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgYHVuZGVmaW5lZGAsIGVsc2UgYGZhbHNlYC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5pc1VuZGVmaW5lZCh2b2lkIDApOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNVbmRlZmluZWQobnVsbCk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBpc1VuZGVmaW5lZCh2YWx1ZSkgewogICAgICByZXR1cm4gdmFsdWUgPT09IHVuZGVmaW5lZDsKICAgIH0KCiAgICB2YXIgaXNVbmRlZmluZWRfMSA9IGlzVW5kZWZpbmVkOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ubWFwYCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBtYXBwZWQgYXJyYXkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VNYXAoY29sbGVjdGlvbiwgaXRlcmF0ZWUpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICByZXN1bHQgPSBpc0FycmF5TGlrZV8xKGNvbGxlY3Rpb24pID8gQXJyYXkoY29sbGVjdGlvbi5sZW5ndGgpIDogW107CgogICAgICBfYmFzZUVhY2goY29sbGVjdGlvbiwgZnVuY3Rpb24odmFsdWUsIGtleSwgY29sbGVjdGlvbikgewogICAgICAgIHJlc3VsdFsrK2luZGV4XSA9IGl0ZXJhdGVlKHZhbHVlLCBrZXksIGNvbGxlY3Rpb24pOwogICAgICB9KTsKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2Jhc2VNYXAgPSBiYXNlTWFwOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB2YWx1ZXMgYnkgcnVubmluZyBlYWNoIGVsZW1lbnQgaW4gYGNvbGxlY3Rpb25gIHRocnUKICAgICAqIGBpdGVyYXRlZWAuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggdGhyZWUgYXJndW1lbnRzOgogICAgICogKHZhbHVlLCBpbmRleHxrZXksIGNvbGxlY3Rpb24pLgogICAgICoKICAgICAqIE1hbnkgbG9kYXNoIG1ldGhvZHMgYXJlIGd1YXJkZWQgdG8gd29yayBhcyBpdGVyYXRlZXMgZm9yIG1ldGhvZHMgbGlrZQogICAgICogYF8uZXZlcnlgLCBgXy5maWx0ZXJgLCBgXy5tYXBgLCBgXy5tYXBWYWx1ZXNgLCBgXy5yZWplY3RgLCBhbmQgYF8uc29tZWAuCiAgICAgKgogICAgICogVGhlIGd1YXJkZWQgbWV0aG9kcyBhcmU6CiAgICAgKiBgYXJ5YCwgYGNodW5rYCwgYGN1cnJ5YCwgYGN1cnJ5UmlnaHRgLCBgZHJvcGAsIGBkcm9wUmlnaHRgLCBgZXZlcnlgLAogICAgICogYGZpbGxgLCBgaW52ZXJ0YCwgYHBhcnNlSW50YCwgYHJhbmRvbWAsIGByYW5nZWAsIGByYW5nZVJpZ2h0YCwgYHJlcGVhdGAsCiAgICAgKiBgc2FtcGxlU2l6ZWAsIGBzbGljZWAsIGBzb21lYCwgYHNvcnRCeWAsIGBzcGxpdGAsIGB0YWtlYCwgYHRha2VSaWdodGAsCiAgICAgKiBgdGVtcGxhdGVgLCBgdHJpbWAsIGB0cmltRW5kYCwgYHRyaW1TdGFydGAsIGFuZCBgd29yZHNgCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgbWFwcGVkIGFycmF5LgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBmdW5jdGlvbiBzcXVhcmUobikgewogICAgICogICByZXR1cm4gbiAqIG47CiAgICAgKiB9CiAgICAgKgogICAgICogXy5tYXAoWzQsIDhdLCBzcXVhcmUpOwogICAgICogLy8gPT4gWzE2LCA2NF0KICAgICAqCiAgICAgKiBfLm1hcCh7ICdhJzogNCwgJ2InOiA4IH0sIHNxdWFyZSk7CiAgICAgKiAvLyA9PiBbMTYsIDY0XSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICoKICAgICAqIHZhciB1c2VycyA9IFsKICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknIH0sCiAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcgfQogICAgICogXTsKICAgICAqCiAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8ubWFwKHVzZXJzLCAndXNlcicpOwogICAgICogLy8gPT4gWydiYXJuZXknLCAnZnJlZCddCiAgICAgKi8KICAgIGZ1bmN0aW9uIG1hcCRiKGNvbGxlY3Rpb24sIGl0ZXJhdGVlKSB7CiAgICAgIHZhciBmdW5jID0gaXNBcnJheV8xKGNvbGxlY3Rpb24pID8gX2FycmF5TWFwIDogX2Jhc2VNYXA7CiAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIF9iYXNlSXRlcmF0ZWUoaXRlcmF0ZWUpKTsKICAgIH0KCiAgICB2YXIgbWFwXzEgPSBtYXAkYjsKCiAgICAvKioKICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5yZWR1Y2VgIGZvciBhcnJheXMgd2l0aG91dCBzdXBwb3J0IGZvcgogICAgICogaXRlcmF0ZWUgc2hvcnRoYW5kcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheX0gW2FycmF5XSBUaGUgYXJyYXkgdG8gaXRlcmF0ZSBvdmVyLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gaXRlcmF0ZWUgVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEBwYXJhbSB7Kn0gW2FjY3VtdWxhdG9yXSBUaGUgaW5pdGlhbCB2YWx1ZS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2luaXRBY2N1bV0gU3BlY2lmeSB1c2luZyB0aGUgZmlyc3QgZWxlbWVudCBvZiBgYXJyYXlgIGFzCiAgICAgKiAgdGhlIGluaXRpYWwgdmFsdWUuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgYWNjdW11bGF0ZWQgdmFsdWUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFycmF5UmVkdWNlKGFycmF5LCBpdGVyYXRlZSwgYWNjdW11bGF0b3IsIGluaXRBY2N1bSkgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwoKICAgICAgaWYgKGluaXRBY2N1bSAmJiBsZW5ndGgpIHsKICAgICAgICBhY2N1bXVsYXRvciA9IGFycmF5WysraW5kZXhdOwogICAgICB9CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgYWNjdW11bGF0b3IgPSBpdGVyYXRlZShhY2N1bXVsYXRvciwgYXJyYXlbaW5kZXhdLCBpbmRleCwgYXJyYXkpOwogICAgICB9CiAgICAgIHJldHVybiBhY2N1bXVsYXRvcjsKICAgIH0KCiAgICB2YXIgX2FycmF5UmVkdWNlID0gYXJyYXlSZWR1Y2U7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5yZWR1Y2VgIGFuZCBgXy5yZWR1Y2VSaWdodGAsIHdpdGhvdXQgc3VwcG9ydAogICAgICogZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMsIHdoaWNoIGl0ZXJhdGVzIG92ZXIgYGNvbGxlY3Rpb25gIHVzaW5nIGBlYWNoRnVuY2AuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGl0ZXJhdGVlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcGFyYW0geyp9IGFjY3VtdWxhdG9yIFRoZSBpbml0aWFsIHZhbHVlLgogICAgICogQHBhcmFtIHtib29sZWFufSBpbml0QWNjdW0gU3BlY2lmeSB1c2luZyB0aGUgZmlyc3Qgb3IgbGFzdCBlbGVtZW50IG9mCiAgICAgKiAgYGNvbGxlY3Rpb25gIGFzIHRoZSBpbml0aWFsIHZhbHVlLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZWFjaEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGl0ZXJhdGUgb3ZlciBgY29sbGVjdGlvbmAuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgYWNjdW11bGF0ZWQgdmFsdWUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VSZWR1Y2UoY29sbGVjdGlvbiwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yLCBpbml0QWNjdW0sIGVhY2hGdW5jKSB7CiAgICAgIGVhY2hGdW5jKGNvbGxlY3Rpb24sIGZ1bmN0aW9uKHZhbHVlLCBpbmRleCwgY29sbGVjdGlvbikgewogICAgICAgIGFjY3VtdWxhdG9yID0gaW5pdEFjY3VtCiAgICAgICAgICA/IChpbml0QWNjdW0gPSBmYWxzZSwgdmFsdWUpCiAgICAgICAgICA6IGl0ZXJhdGVlKGFjY3VtdWxhdG9yLCB2YWx1ZSwgaW5kZXgsIGNvbGxlY3Rpb24pOwogICAgICB9KTsKICAgICAgcmV0dXJuIGFjY3VtdWxhdG9yOwogICAgfQoKICAgIHZhciBfYmFzZVJlZHVjZSA9IGJhc2VSZWR1Y2U7CgogICAgLyoqCiAgICAgKiBSZWR1Y2VzIGBjb2xsZWN0aW9uYCB0byBhIHZhbHVlIHdoaWNoIGlzIHRoZSBhY2N1bXVsYXRlZCByZXN1bHQgb2YgcnVubmluZwogICAgICogZWFjaCBlbGVtZW50IGluIGBjb2xsZWN0aW9uYCB0aHJ1IGBpdGVyYXRlZWAsIHdoZXJlIGVhY2ggc3VjY2Vzc2l2ZQogICAgICogaW52b2NhdGlvbiBpcyBzdXBwbGllZCB0aGUgcmV0dXJuIHZhbHVlIG9mIHRoZSBwcmV2aW91cy4gSWYgYGFjY3VtdWxhdG9yYAogICAgICogaXMgbm90IGdpdmVuLCB0aGUgZmlyc3QgZWxlbWVudCBvZiBgY29sbGVjdGlvbmAgaXMgdXNlZCBhcyB0aGUgaW5pdGlhbAogICAgICogdmFsdWUuIFRoZSBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggZm91ciBhcmd1bWVudHM6CiAgICAgKiAoYWNjdW11bGF0b3IsIHZhbHVlLCBpbmRleHxrZXksIGNvbGxlY3Rpb24pLgogICAgICoKICAgICAqIE1hbnkgbG9kYXNoIG1ldGhvZHMgYXJlIGd1YXJkZWQgdG8gd29yayBhcyBpdGVyYXRlZXMgZm9yIG1ldGhvZHMgbGlrZQogICAgICogYF8ucmVkdWNlYCwgYF8ucmVkdWNlUmlnaHRgLCBhbmQgYF8udHJhbnNmb3JtYC4KICAgICAqCiAgICAgKiBUaGUgZ3VhcmRlZCBtZXRob2RzIGFyZToKICAgICAqIGBhc3NpZ25gLCBgZGVmYXVsdHNgLCBgZGVmYXVsdHNEZWVwYCwgYGluY2x1ZGVzYCwgYG1lcmdlYCwgYG9yZGVyQnlgLAogICAgICogYW5kIGBzb3J0QnlgCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHBhcmFtIHsqfSBbYWNjdW11bGF0b3JdIFRoZSBpbml0aWFsIHZhbHVlLgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGFjY3VtdWxhdGVkIHZhbHVlLgogICAgICogQHNlZSBfLnJlZHVjZVJpZ2h0CiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8ucmVkdWNlKFsxLCAyXSwgZnVuY3Rpb24oc3VtLCBuKSB7CiAgICAgKiAgIHJldHVybiBzdW0gKyBuOwogICAgICogfSwgMCk7CiAgICAgKiAvLyA9PiAzCiAgICAgKgogICAgICogXy5yZWR1Y2UoeyAnYSc6IDEsICdiJzogMiwgJ2MnOiAxIH0sIGZ1bmN0aW9uKHJlc3VsdCwgdmFsdWUsIGtleSkgewogICAgICogICAocmVzdWx0W3ZhbHVlXSB8fCAocmVzdWx0W3ZhbHVlXSA9IFtdKSkucHVzaChrZXkpOwogICAgICogICByZXR1cm4gcmVzdWx0OwogICAgICogfSwge30pOwogICAgICogLy8gPT4geyAnMSc6IFsnYScsICdjJ10sICcyJzogWydiJ10gfSAoaXRlcmF0aW9uIG9yZGVyIGlzIG5vdCBndWFyYW50ZWVkKQogICAgICovCiAgICBmdW5jdGlvbiByZWR1Y2UoY29sbGVjdGlvbiwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yKSB7CiAgICAgIHZhciBmdW5jID0gaXNBcnJheV8xKGNvbGxlY3Rpb24pID8gX2FycmF5UmVkdWNlIDogX2Jhc2VSZWR1Y2UsCiAgICAgICAgICBpbml0QWNjdW0gPSBhcmd1bWVudHMubGVuZ3RoIDwgMzsKCiAgICAgIHJldHVybiBmdW5jKGNvbGxlY3Rpb24sIF9iYXNlSXRlcmF0ZWUoaXRlcmF0ZWUpLCBhY2N1bXVsYXRvciwgaW5pdEFjY3VtLCBfYmFzZUVhY2gpOwogICAgfQoKICAgIHZhciByZWR1Y2VfMSA9IHJlZHVjZTsKCiAgICAvKiogYE9iamVjdCN0b1N0cmluZ2AgcmVzdWx0IHJlZmVyZW5jZXMuICovCiAgICB2YXIgc3RyaW5nVGFnJDQgPSAnW29iamVjdCBTdHJpbmddJzsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGNsYXNzaWZpZWQgYXMgYSBgU3RyaW5nYCBwcmltaXRpdmUgb3Igb2JqZWN0LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGEgc3RyaW5nLCBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNTdHJpbmcoJ2FiYycpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNTdHJpbmcoMSk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBpc1N0cmluZyh2YWx1ZSkgewogICAgICByZXR1cm4gdHlwZW9mIHZhbHVlID09ICdzdHJpbmcnIHx8CiAgICAgICAgKCFpc0FycmF5XzEodmFsdWUpICYmIGlzT2JqZWN0TGlrZV8xKHZhbHVlKSAmJiBfYmFzZUdldFRhZyh2YWx1ZSkgPT0gc3RyaW5nVGFnJDQpOwogICAgfQoKICAgIHZhciBpc1N0cmluZ18xID0gaXNTdHJpbmc7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBzaXplIG9mIGFuIEFTQ0lJIGBzdHJpbmdgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgaW5zcGVjdC4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHN0cmluZyBzaXplLgogICAgICovCiAgICB2YXIgYXNjaWlTaXplID0gX2Jhc2VQcm9wZXJ0eSgnbGVuZ3RoJyk7CgogICAgdmFyIF9hc2NpaVNpemUgPSBhc2NpaVNpemU7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIGNoYXJhY3RlciBjbGFzc2VzLiAqLwogICAgdmFyIHJzQXN0cmFsUmFuZ2UgPSAnXFx1ZDgwMC1cXHVkZmZmJywKICAgICAgICByc0NvbWJvTWFya3NSYW5nZSA9ICdcXHUwMzAwLVxcdTAzNmYnLAogICAgICAgIHJlQ29tYm9IYWxmTWFya3NSYW5nZSA9ICdcXHVmZTIwLVxcdWZlMmYnLAogICAgICAgIHJzQ29tYm9TeW1ib2xzUmFuZ2UgPSAnXFx1MjBkMC1cXHUyMGZmJywKICAgICAgICByc0NvbWJvUmFuZ2UgPSByc0NvbWJvTWFya3NSYW5nZSArIHJlQ29tYm9IYWxmTWFya3NSYW5nZSArIHJzQ29tYm9TeW1ib2xzUmFuZ2UsCiAgICAgICAgcnNWYXJSYW5nZSA9ICdcXHVmZTBlXFx1ZmUwZic7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIGNhcHR1cmUgZ3JvdXBzLiAqLwogICAgdmFyIHJzWldKID0gJ1xcdTIwMGQnOwoKICAgIC8qKiBVc2VkIHRvIGRldGVjdCBzdHJpbmdzIHdpdGggW3plcm8td2lkdGggam9pbmVycyBvciBjb2RlIHBvaW50cyBmcm9tIHRoZSBhc3RyYWwgcGxhbmVzXShodHRwOi8vZWV2LmVlL2Jsb2cvMjAxNS8wOS8xMi9kYXJrLWNvcm5lcnMtb2YtdW5pY29kZS8pLiAqLwogICAgdmFyIHJlSGFzVW5pY29kZSA9IFJlZ0V4cCgnWycgKyByc1pXSiArIHJzQXN0cmFsUmFuZ2UgICsgcnNDb21ib1JhbmdlICsgcnNWYXJSYW5nZSArICddJyk7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgYHN0cmluZ2AgY29udGFpbnMgVW5pY29kZSBzeW1ib2xzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgdG8gaW5zcGVjdC4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBhIHN5bWJvbCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBoYXNVbmljb2RlKHN0cmluZykgewogICAgICByZXR1cm4gcmVIYXNVbmljb2RlLnRlc3Qoc3RyaW5nKTsKICAgIH0KCiAgICB2YXIgX2hhc1VuaWNvZGUgPSBoYXNVbmljb2RlOwoKICAgIC8qKiBVc2VkIHRvIGNvbXBvc2UgdW5pY29kZSBjaGFyYWN0ZXIgY2xhc3Nlcy4gKi8KICAgIHZhciByc0FzdHJhbFJhbmdlJDEgPSAnXFx1ZDgwMC1cXHVkZmZmJywKICAgICAgICByc0NvbWJvTWFya3NSYW5nZSQxID0gJ1xcdTAzMDAtXFx1MDM2ZicsCiAgICAgICAgcmVDb21ib0hhbGZNYXJrc1JhbmdlJDEgPSAnXFx1ZmUyMC1cXHVmZTJmJywKICAgICAgICByc0NvbWJvU3ltYm9sc1JhbmdlJDEgPSAnXFx1MjBkMC1cXHUyMGZmJywKICAgICAgICByc0NvbWJvUmFuZ2UkMSA9IHJzQ29tYm9NYXJrc1JhbmdlJDEgKyByZUNvbWJvSGFsZk1hcmtzUmFuZ2UkMSArIHJzQ29tYm9TeW1ib2xzUmFuZ2UkMSwKICAgICAgICByc1ZhclJhbmdlJDEgPSAnXFx1ZmUwZVxcdWZlMGYnOwoKICAgIC8qKiBVc2VkIHRvIGNvbXBvc2UgdW5pY29kZSBjYXB0dXJlIGdyb3Vwcy4gKi8KICAgIHZhciByc0FzdHJhbCA9ICdbJyArIHJzQXN0cmFsUmFuZ2UkMSArICddJywKICAgICAgICByc0NvbWJvID0gJ1snICsgcnNDb21ib1JhbmdlJDEgKyAnXScsCiAgICAgICAgcnNGaXR6ID0gJ1xcdWQ4M2NbXFx1ZGZmYi1cXHVkZmZmXScsCiAgICAgICAgcnNNb2RpZmllciA9ICcoPzonICsgcnNDb21ibyArICd8JyArIHJzRml0eiArICcpJywKICAgICAgICByc05vbkFzdHJhbCA9ICdbXicgKyByc0FzdHJhbFJhbmdlJDEgKyAnXScsCiAgICAgICAgcnNSZWdpb25hbCA9ICcoPzpcXHVkODNjW1xcdWRkZTYtXFx1ZGRmZl0pezJ9JywKICAgICAgICByc1N1cnJQYWlyID0gJ1tcXHVkODAwLVxcdWRiZmZdW1xcdWRjMDAtXFx1ZGZmZl0nLAogICAgICAgIHJzWldKJDEgPSAnXFx1MjAwZCc7CgogICAgLyoqIFVzZWQgdG8gY29tcG9zZSB1bmljb2RlIHJlZ2V4ZXMuICovCiAgICB2YXIgcmVPcHRNb2QgPSByc01vZGlmaWVyICsgJz8nLAogICAgICAgIHJzT3B0VmFyID0gJ1snICsgcnNWYXJSYW5nZSQxICsgJ10/JywKICAgICAgICByc09wdEpvaW4gPSAnKD86JyArIHJzWldKJDEgKyAnKD86JyArIFtyc05vbkFzdHJhbCwgcnNSZWdpb25hbCwgcnNTdXJyUGFpcl0uam9pbignfCcpICsgJyknICsgcnNPcHRWYXIgKyByZU9wdE1vZCArICcpKicsCiAgICAgICAgcnNTZXEgPSByc09wdFZhciArIHJlT3B0TW9kICsgcnNPcHRKb2luLAogICAgICAgIHJzU3ltYm9sID0gJyg/OicgKyBbcnNOb25Bc3RyYWwgKyByc0NvbWJvICsgJz8nLCByc0NvbWJvLCByc1JlZ2lvbmFsLCByc1N1cnJQYWlyLCByc0FzdHJhbF0uam9pbignfCcpICsgJyknOwoKICAgIC8qKiBVc2VkIHRvIG1hdGNoIFtzdHJpbmcgc3ltYm9sc10oaHR0cHM6Ly9tYXRoaWFzYnluZW5zLmJlL25vdGVzL2phdmFzY3JpcHQtdW5pY29kZSkuICovCiAgICB2YXIgcmVVbmljb2RlID0gUmVnRXhwKHJzRml0eiArICcoPz0nICsgcnNGaXR6ICsgJyl8JyArIHJzU3ltYm9sICsgcnNTZXEsICdnJyk7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBzaXplIG9mIGEgVW5pY29kZSBgc3RyaW5nYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtzdHJpbmd9IHN0cmluZyBUaGUgc3RyaW5nIGluc3BlY3QuCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzdHJpbmcgc2l6ZS4KICAgICAqLwogICAgZnVuY3Rpb24gdW5pY29kZVNpemUoc3RyaW5nKSB7CiAgICAgIHZhciByZXN1bHQgPSByZVVuaWNvZGUubGFzdEluZGV4ID0gMDsKICAgICAgd2hpbGUgKHJlVW5pY29kZS50ZXN0KHN0cmluZykpIHsKICAgICAgICArK3Jlc3VsdDsKICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfdW5pY29kZVNpemUgPSB1bmljb2RlU2l6ZTsKCiAgICAvKioKICAgICAqIEdldHMgdGhlIG51bWJlciBvZiBzeW1ib2xzIGluIGBzdHJpbmdgLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge3N0cmluZ30gc3RyaW5nIFRoZSBzdHJpbmcgdG8gaW5zcGVjdC4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIHN0cmluZyBzaXplLgogICAgICovCiAgICBmdW5jdGlvbiBzdHJpbmdTaXplKHN0cmluZykgewogICAgICByZXR1cm4gX2hhc1VuaWNvZGUoc3RyaW5nKQogICAgICAgID8gX3VuaWNvZGVTaXplKHN0cmluZykKICAgICAgICA6IF9hc2NpaVNpemUoc3RyaW5nKTsKICAgIH0KCiAgICB2YXIgX3N0cmluZ1NpemUgPSBzdHJpbmdTaXplOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBtYXBUYWckNyA9ICdbb2JqZWN0IE1hcF0nLAogICAgICAgIHNldFRhZyQ3ID0gJ1tvYmplY3QgU2V0XSc7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSBzaXplIG9mIGBjb2xsZWN0aW9uYCBieSByZXR1cm5pbmcgaXRzIGxlbmd0aCBmb3IgYXJyYXktbGlrZQogICAgICogdmFsdWVzIG9yIHRoZSBudW1iZXIgb2Ygb3duIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnRpZXMgZm9yIG9iamVjdHMuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fHN0cmluZ30gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpbnNwZWN0LgogICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgY29sbGVjdGlvbiBzaXplLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLnNpemUoWzEsIDIsIDNdKTsKICAgICAqIC8vID0+IDMKICAgICAqCiAgICAgKiBfLnNpemUoeyAnYSc6IDEsICdiJzogMiB9KTsKICAgICAqIC8vID0+IDIKICAgICAqCiAgICAgKiBfLnNpemUoJ3BlYmJsZXMnKTsKICAgICAqIC8vID0+IDcKICAgICAqLwogICAgZnVuY3Rpb24gc2l6ZShjb2xsZWN0aW9uKSB7CiAgICAgIGlmIChjb2xsZWN0aW9uID09IG51bGwpIHsKICAgICAgICByZXR1cm4gMDsKICAgICAgfQogICAgICBpZiAoaXNBcnJheUxpa2VfMShjb2xsZWN0aW9uKSkgewogICAgICAgIHJldHVybiBpc1N0cmluZ18xKGNvbGxlY3Rpb24pID8gX3N0cmluZ1NpemUoY29sbGVjdGlvbikgOiBjb2xsZWN0aW9uLmxlbmd0aDsKICAgICAgfQogICAgICB2YXIgdGFnID0gX2dldFRhZyhjb2xsZWN0aW9uKTsKICAgICAgaWYgKHRhZyA9PSBtYXBUYWckNyB8fCB0YWcgPT0gc2V0VGFnJDcpIHsKICAgICAgICByZXR1cm4gY29sbGVjdGlvbi5zaXplOwogICAgICB9CiAgICAgIHJldHVybiBfYmFzZUtleXMoY29sbGVjdGlvbikubGVuZ3RoOwogICAgfQoKICAgIHZhciBzaXplXzEgPSBzaXplOwoKICAgIC8qKgogICAgICogQW4gYWx0ZXJuYXRpdmUgdG8gYF8ucmVkdWNlYDsgdGhpcyBtZXRob2QgdHJhbnNmb3JtcyBgb2JqZWN0YCB0byBhIG5ldwogICAgICogYGFjY3VtdWxhdG9yYCBvYmplY3Qgd2hpY2ggaXMgdGhlIHJlc3VsdCBvZiBydW5uaW5nIGVhY2ggb2YgaXRzIG93bgogICAgICogZW51bWVyYWJsZSBzdHJpbmcga2V5ZWQgcHJvcGVydGllcyB0aHJ1IGBpdGVyYXRlZWAsIHdpdGggZWFjaCBpbnZvY2F0aW9uCiAgICAgKiBwb3RlbnRpYWxseSBtdXRhdGluZyB0aGUgYGFjY3VtdWxhdG9yYCBvYmplY3QuIElmIGBhY2N1bXVsYXRvcmAgaXMgbm90CiAgICAgKiBwcm92aWRlZCwgYSBuZXcgb2JqZWN0IHdpdGggdGhlIHNhbWUgYFtbUHJvdG90eXBlXV1gIHdpbGwgYmUgdXNlZC4gVGhlCiAgICAgKiBpdGVyYXRlZSBpcyBpbnZva2VkIHdpdGggZm91ciBhcmd1bWVudHM6IChhY2N1bXVsYXRvciwgdmFsdWUsIGtleSwgb2JqZWN0KS4KICAgICAqIEl0ZXJhdGVlIGZ1bmN0aW9ucyBtYXkgZXhpdCBpdGVyYXRpb24gZWFybHkgYnkgZXhwbGljaXRseSByZXR1cm5pbmcgYGZhbHNlYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDEuMy4wCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcGFyYW0geyp9IFthY2N1bXVsYXRvcl0gVGhlIGN1c3RvbSBhY2N1bXVsYXRvciB2YWx1ZS4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBhY2N1bXVsYXRlZCB2YWx1ZS4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy50cmFuc2Zvcm0oWzIsIDMsIDRdLCBmdW5jdGlvbihyZXN1bHQsIG4pIHsKICAgICAqICAgcmVzdWx0LnB1c2gobiAqPSBuKTsKICAgICAqICAgcmV0dXJuIG4gJSAyID09IDA7CiAgICAgKiB9LCBbXSk7CiAgICAgKiAvLyA9PiBbNCwgOV0KICAgICAqCiAgICAgKiBfLnRyYW5zZm9ybSh7ICdhJzogMSwgJ2InOiAyLCAnYyc6IDEgfSwgZnVuY3Rpb24ocmVzdWx0LCB2YWx1ZSwga2V5KSB7CiAgICAgKiAgIChyZXN1bHRbdmFsdWVdIHx8IChyZXN1bHRbdmFsdWVdID0gW10pKS5wdXNoKGtleSk7CiAgICAgKiB9LCB7fSk7CiAgICAgKiAvLyA9PiB7ICcxJzogWydhJywgJ2MnXSwgJzInOiBbJ2InXSB9CiAgICAgKi8KICAgIGZ1bmN0aW9uIHRyYW5zZm9ybSQ0KG9iamVjdCwgaXRlcmF0ZWUsIGFjY3VtdWxhdG9yKSB7CiAgICAgIHZhciBpc0FyciA9IGlzQXJyYXlfMShvYmplY3QpLAogICAgICAgICAgaXNBcnJMaWtlID0gaXNBcnIgfHwgaXNCdWZmZXJfMShvYmplY3QpIHx8IGlzVHlwZWRBcnJheV8xKG9iamVjdCk7CgogICAgICBpdGVyYXRlZSA9IF9iYXNlSXRlcmF0ZWUoaXRlcmF0ZWUpOwogICAgICBpZiAoYWNjdW11bGF0b3IgPT0gbnVsbCkgewogICAgICAgIHZhciBDdG9yID0gb2JqZWN0ICYmIG9iamVjdC5jb25zdHJ1Y3RvcjsKICAgICAgICBpZiAoaXNBcnJMaWtlKSB7CiAgICAgICAgICBhY2N1bXVsYXRvciA9IGlzQXJyID8gbmV3IEN0b3IgOiBbXTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoaXNPYmplY3RfMShvYmplY3QpKSB7CiAgICAgICAgICBhY2N1bXVsYXRvciA9IGlzRnVuY3Rpb25fMShDdG9yKSA/IF9iYXNlQ3JlYXRlKF9nZXRQcm90b3R5cGUob2JqZWN0KSkgOiB7fTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICBhY2N1bXVsYXRvciA9IHt9OwogICAgICAgIH0KICAgICAgfQogICAgICAoaXNBcnJMaWtlID8gX2FycmF5RWFjaCA6IF9iYXNlRm9yT3duKShvYmplY3QsIGZ1bmN0aW9uKHZhbHVlLCBpbmRleCwgb2JqZWN0KSB7CiAgICAgICAgcmV0dXJuIGl0ZXJhdGVlKGFjY3VtdWxhdG9yLCB2YWx1ZSwgaW5kZXgsIG9iamVjdCk7CiAgICAgIH0pOwogICAgICByZXR1cm4gYWNjdW11bGF0b3I7CiAgICB9CgogICAgdmFyIHRyYW5zZm9ybV8xID0gdHJhbnNmb3JtJDQ7CgogICAgLyoqIEJ1aWx0LWluIHZhbHVlIHJlZmVyZW5jZXMuICovCiAgICB2YXIgc3ByZWFkYWJsZVN5bWJvbCA9IF9TeW1ib2wgPyBfU3ltYm9sLmlzQ29uY2F0U3ByZWFkYWJsZSA6IHVuZGVmaW5lZDsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgZmxhdHRlbmFibGUgYGFyZ3VtZW50c2Agb2JqZWN0IG9yIGFycmF5LgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjaGVjay4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdmFsdWVgIGlzIGZsYXR0ZW5hYmxlLCBlbHNlIGBmYWxzZWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzRmxhdHRlbmFibGUodmFsdWUpIHsKICAgICAgcmV0dXJuIGlzQXJyYXlfMSh2YWx1ZSkgfHwgaXNBcmd1bWVudHNfMSh2YWx1ZSkgfHwKICAgICAgICAhIShzcHJlYWRhYmxlU3ltYm9sICYmIHZhbHVlICYmIHZhbHVlW3NwcmVhZGFibGVTeW1ib2xdKTsKICAgIH0KCiAgICB2YXIgX2lzRmxhdHRlbmFibGUgPSBpc0ZsYXR0ZW5hYmxlOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uZmxhdHRlbmAgd2l0aCBzdXBwb3J0IGZvciByZXN0cmljdGluZyBmbGF0dGVuaW5nLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gZmxhdHRlbi4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBkZXB0aCBUaGUgbWF4aW11bSByZWN1cnNpb24gZGVwdGguCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtwcmVkaWNhdGU9aXNGbGF0dGVuYWJsZV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2lzU3RyaWN0XSBSZXN0cmljdCB0byB2YWx1ZXMgdGhhdCBwYXNzIGBwcmVkaWNhdGVgIGNoZWNrcy4KICAgICAqIEBwYXJhbSB7QXJyYXl9IFtyZXN1bHQ9W11dIFRoZSBpbml0aWFsIHJlc3VsdCB2YWx1ZS4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZsYXR0ZW5lZCBhcnJheS4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZUZsYXR0ZW4oYXJyYXksIGRlcHRoLCBwcmVkaWNhdGUsIGlzU3RyaWN0LCByZXN1bHQpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICBwcmVkaWNhdGUgfHwgKHByZWRpY2F0ZSA9IF9pc0ZsYXR0ZW5hYmxlKTsKICAgICAgcmVzdWx0IHx8IChyZXN1bHQgPSBbXSk7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHZhciB2YWx1ZSA9IGFycmF5W2luZGV4XTsKICAgICAgICBpZiAoZGVwdGggPiAwICYmIHByZWRpY2F0ZSh2YWx1ZSkpIHsKICAgICAgICAgIGlmIChkZXB0aCA+IDEpIHsKICAgICAgICAgICAgLy8gUmVjdXJzaXZlbHkgZmxhdHRlbiBhcnJheXMgKHN1c2NlcHRpYmxlIHRvIGNhbGwgc3RhY2sgbGltaXRzKS4KICAgICAgICAgICAgYmFzZUZsYXR0ZW4odmFsdWUsIGRlcHRoIC0gMSwgcHJlZGljYXRlLCBpc1N0cmljdCwgcmVzdWx0KTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIF9hcnJheVB1c2gocmVzdWx0LCB2YWx1ZSk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIGlmICghaXNTdHJpY3QpIHsKICAgICAgICAgIHJlc3VsdFtyZXN1bHQubGVuZ3RoXSA9IHZhbHVlOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZUZsYXR0ZW4gPSBiYXNlRmxhdHRlbjsKCiAgICAvKioKICAgICAqIEEgZmFzdGVyIGFsdGVybmF0aXZlIHRvIGBGdW5jdGlvbiNhcHBseWAsIHRoaXMgZnVuY3Rpb24gaW52b2tlcyBgZnVuY2AKICAgICAqIHdpdGggdGhlIGB0aGlzYCBiaW5kaW5nIG9mIGB0aGlzQXJnYCBhbmQgdGhlIGFyZ3VtZW50cyBvZiBgYXJnc2AuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGludm9rZS4KICAgICAqIEBwYXJhbSB7Kn0gdGhpc0FyZyBUaGUgYHRoaXNgIGJpbmRpbmcgb2YgYGZ1bmNgLgogICAgICogQHBhcmFtIHtBcnJheX0gYXJncyBUaGUgYXJndW1lbnRzIHRvIGludm9rZSBgZnVuY2Agd2l0aC4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSByZXN1bHQgb2YgYGZ1bmNgLgogICAgICovCiAgICBmdW5jdGlvbiBhcHBseShmdW5jLCB0aGlzQXJnLCBhcmdzKSB7CiAgICAgIHN3aXRjaCAoYXJncy5sZW5ndGgpIHsKICAgICAgICBjYXNlIDA6IHJldHVybiBmdW5jLmNhbGwodGhpc0FyZyk7CiAgICAgICAgY2FzZSAxOiByZXR1cm4gZnVuYy5jYWxsKHRoaXNBcmcsIGFyZ3NbMF0pOwogICAgICAgIGNhc2UgMjogcmV0dXJuIGZ1bmMuY2FsbCh0aGlzQXJnLCBhcmdzWzBdLCBhcmdzWzFdKTsKICAgICAgICBjYXNlIDM6IHJldHVybiBmdW5jLmNhbGwodGhpc0FyZywgYXJnc1swXSwgYXJnc1sxXSwgYXJnc1syXSk7CiAgICAgIH0KICAgICAgcmV0dXJuIGZ1bmMuYXBwbHkodGhpc0FyZywgYXJncyk7CiAgICB9CgogICAgdmFyIF9hcHBseSA9IGFwcGx5OwoKICAgIC8qIEJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzIGZvciB0aG9zZSB3aXRoIHRoZSBzYW1lIG5hbWUgYXMgb3RoZXIgYGxvZGFzaGAgbWV0aG9kcy4gKi8KICAgIHZhciBuYXRpdmVNYXggPSBNYXRoLm1heDsKCiAgICAvKioKICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZVJlc3RgIHdoaWNoIHRyYW5zZm9ybXMgdGhlIHJlc3QgYXJyYXkuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGFwcGx5IGEgcmVzdCBwYXJhbWV0ZXIgdG8uCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PWZ1bmMubGVuZ3RoLTFdIFRoZSBzdGFydCBwb3NpdGlvbiBvZiB0aGUgcmVzdCBwYXJhbWV0ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSB0cmFuc2Zvcm0gVGhlIHJlc3QgYXJyYXkgdHJhbnNmb3JtLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIG92ZXJSZXN0KGZ1bmMsIHN0YXJ0LCB0cmFuc2Zvcm0pIHsKICAgICAgc3RhcnQgPSBuYXRpdmVNYXgoc3RhcnQgPT09IHVuZGVmaW5lZCA/IChmdW5jLmxlbmd0aCAtIDEpIDogc3RhcnQsIDApOwogICAgICByZXR1cm4gZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGFyZ3MgPSBhcmd1bWVudHMsCiAgICAgICAgICAgIGluZGV4ID0gLTEsCiAgICAgICAgICAgIGxlbmd0aCA9IG5hdGl2ZU1heChhcmdzLmxlbmd0aCAtIHN0YXJ0LCAwKSwKICAgICAgICAgICAgYXJyYXkgPSBBcnJheShsZW5ndGgpOwoKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgYXJyYXlbaW5kZXhdID0gYXJnc1tzdGFydCArIGluZGV4XTsKICAgICAgICB9CiAgICAgICAgaW5kZXggPSAtMTsKICAgICAgICB2YXIgb3RoZXJBcmdzID0gQXJyYXkoc3RhcnQgKyAxKTsKICAgICAgICB3aGlsZSAoKytpbmRleCA8IHN0YXJ0KSB7CiAgICAgICAgICBvdGhlckFyZ3NbaW5kZXhdID0gYXJnc1tpbmRleF07CiAgICAgICAgfQogICAgICAgIG90aGVyQXJnc1tzdGFydF0gPSB0cmFuc2Zvcm0oYXJyYXkpOwogICAgICAgIHJldHVybiBfYXBwbHkoZnVuYywgdGhpcywgb3RoZXJBcmdzKTsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgX292ZXJSZXN0ID0gb3ZlclJlc3Q7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgc2V0VG9TdHJpbmdgIHdpdGhvdXQgc3VwcG9ydCBmb3IgaG90IGxvb3Agc2hvcnRpbmcuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIG1vZGlmeS4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHN0cmluZyBUaGUgYHRvU3RyaW5nYCByZXN1bHQuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgYGZ1bmNgLgogICAgICovCiAgICB2YXIgYmFzZVNldFRvU3RyaW5nID0gIV9kZWZpbmVQcm9wZXJ0eSA/IGlkZW50aXR5XzEgOiBmdW5jdGlvbihmdW5jLCBzdHJpbmcpIHsKICAgICAgcmV0dXJuIF9kZWZpbmVQcm9wZXJ0eShmdW5jLCAndG9TdHJpbmcnLCB7CiAgICAgICAgJ2NvbmZpZ3VyYWJsZSc6IHRydWUsCiAgICAgICAgJ2VudW1lcmFibGUnOiBmYWxzZSwKICAgICAgICAndmFsdWUnOiBjb25zdGFudF8xKHN0cmluZyksCiAgICAgICAgJ3dyaXRhYmxlJzogdHJ1ZQogICAgICB9KTsKICAgIH07CgogICAgdmFyIF9iYXNlU2V0VG9TdHJpbmcgPSBiYXNlU2V0VG9TdHJpbmc7CgogICAgLyoqIFVzZWQgdG8gZGV0ZWN0IGhvdCBmdW5jdGlvbnMgYnkgbnVtYmVyIG9mIGNhbGxzIHdpdGhpbiBhIHNwYW4gb2YgbWlsbGlzZWNvbmRzLiAqLwogICAgdmFyIEhPVF9DT1VOVCA9IDgwMCwKICAgICAgICBIT1RfU1BBTiA9IDE2OwoKICAgIC8qIEJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzIGZvciB0aG9zZSB3aXRoIHRoZSBzYW1lIG5hbWUgYXMgb3RoZXIgYGxvZGFzaGAgbWV0aG9kcy4gKi8KICAgIHZhciBuYXRpdmVOb3cgPSBEYXRlLm5vdzsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBmdW5jdGlvbiB0aGF0J2xsIHNob3J0IG91dCBhbmQgaW52b2tlIGBpZGVudGl0eWAgaW5zdGVhZAogICAgICogb2YgYGZ1bmNgIHdoZW4gaXQncyBjYWxsZWQgYEhPVF9DT1VOVGAgb3IgbW9yZSB0aW1lcyBpbiBgSE9UX1NQQU5gCiAgICAgKiBtaWxsaXNlY29uZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIHJlc3RyaWN0LgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgc2hvcnRhYmxlIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBzaG9ydE91dChmdW5jKSB7CiAgICAgIHZhciBjb3VudCA9IDAsCiAgICAgICAgICBsYXN0Q2FsbGVkID0gMDsKCiAgICAgIHJldHVybiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3RhbXAgPSBuYXRpdmVOb3coKSwKICAgICAgICAgICAgcmVtYWluaW5nID0gSE9UX1NQQU4gLSAoc3RhbXAgLSBsYXN0Q2FsbGVkKTsKCiAgICAgICAgbGFzdENhbGxlZCA9IHN0YW1wOwogICAgICAgIGlmIChyZW1haW5pbmcgPiAwKSB7CiAgICAgICAgICBpZiAoKytjb3VudCA+PSBIT1RfQ09VTlQpIHsKICAgICAgICAgICAgcmV0dXJuIGFyZ3VtZW50c1swXTsKICAgICAgICAgIH0KICAgICAgICB9IGVsc2UgewogICAgICAgICAgY291bnQgPSAwOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZnVuYy5hcHBseSh1bmRlZmluZWQsIGFyZ3VtZW50cyk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9zaG9ydE91dCA9IHNob3J0T3V0OwoKICAgIC8qKgogICAgICogU2V0cyB0aGUgYHRvU3RyaW5nYCBtZXRob2Qgb2YgYGZ1bmNgIHRvIHJldHVybiBgc3RyaW5nYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gZnVuYyBUaGUgZnVuY3Rpb24gdG8gbW9kaWZ5LgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gc3RyaW5nIFRoZSBgdG9TdHJpbmdgIHJlc3VsdC4KICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyBgZnVuY2AuCiAgICAgKi8KICAgIHZhciBzZXRUb1N0cmluZyA9IF9zaG9ydE91dChfYmFzZVNldFRvU3RyaW5nKTsKCiAgICB2YXIgX3NldFRvU3RyaW5nID0gc2V0VG9TdHJpbmc7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5yZXN0YCB3aGljaCBkb2Vzbid0IHZhbGlkYXRlIG9yIGNvZXJjZSBhcmd1bWVudHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGFwcGx5IGEgcmVzdCBwYXJhbWV0ZXIgdG8uCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PWZ1bmMubGVuZ3RoLTFdIFRoZSBzdGFydCBwb3NpdGlvbiBvZiB0aGUgcmVzdCBwYXJhbWV0ZXIuCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZVJlc3QoZnVuYywgc3RhcnQpIHsKICAgICAgcmV0dXJuIF9zZXRUb1N0cmluZyhfb3ZlclJlc3QoZnVuYywgc3RhcnQsIGlkZW50aXR5XzEpLCBmdW5jICsgJycpOwogICAgfQoKICAgIHZhciBfYmFzZVJlc3QgPSBiYXNlUmVzdDsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmZpbmRJbmRleGAgYW5kIGBfLmZpbmRMYXN0SW5kZXhgIHdpdGhvdXQKICAgICAqIHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gcHJlZGljYXRlIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcGFyYW0ge251bWJlcn0gZnJvbUluZGV4IFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2Zyb21SaWdodF0gU3BlY2lmeSBpdGVyYXRpbmcgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICogQHJldHVybnMge251bWJlcn0gUmV0dXJucyB0aGUgaW5kZXggb2YgdGhlIG1hdGNoZWQgdmFsdWUsIGVsc2UgYC0xYC4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZUZpbmRJbmRleChhcnJheSwgcHJlZGljYXRlLCBmcm9tSW5kZXgsIGZyb21SaWdodCkgewogICAgICB2YXIgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgaW5kZXggPSBmcm9tSW5kZXggKyAoZnJvbVJpZ2h0ID8gMSA6IC0xKTsKCiAgICAgIHdoaWxlICgoZnJvbVJpZ2h0ID8gaW5kZXgtLSA6ICsraW5kZXggPCBsZW5ndGgpKSB7CiAgICAgICAgaWYgKHByZWRpY2F0ZShhcnJheVtpbmRleF0sIGluZGV4LCBhcnJheSkpIHsKICAgICAgICAgIHJldHVybiBpbmRleDsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIC0xOwogICAgfQoKICAgIHZhciBfYmFzZUZpbmRJbmRleCA9IGJhc2VGaW5kSW5kZXg7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5pc05hTmAgd2l0aG91dCBzdXBwb3J0IGZvciBudW1iZXIgb2JqZWN0cy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBgTmFOYCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlSXNOYU4odmFsdWUpIHsKICAgICAgcmV0dXJuIHZhbHVlICE9PSB2YWx1ZTsKICAgIH0KCiAgICB2YXIgX2Jhc2VJc05hTiA9IGJhc2VJc05hTjsKCiAgICAvKioKICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgXy5pbmRleE9mYCB3aGljaCBwZXJmb3JtcyBzdHJpY3QgZXF1YWxpdHkKICAgICAqIGNvbXBhcmlzb25zIG9mIHZhbHVlcywgaS5lLiBgPT09YC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBzZWFyY2ggZm9yLgogICAgICogQHBhcmFtIHtudW1iZXJ9IGZyb21JbmRleCBUaGUgaW5kZXggdG8gc2VhcmNoIGZyb20uCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBpbmRleCBvZiB0aGUgbWF0Y2hlZCB2YWx1ZSwgZWxzZSBgLTFgLgogICAgICovCiAgICBmdW5jdGlvbiBzdHJpY3RJbmRleE9mKGFycmF5LCB2YWx1ZSwgZnJvbUluZGV4KSB7CiAgICAgIHZhciBpbmRleCA9IGZyb21JbmRleCAtIDEsCiAgICAgICAgICBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIGlmIChhcnJheVtpbmRleF0gPT09IHZhbHVlKSB7CiAgICAgICAgICByZXR1cm4gaW5kZXg7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiAtMTsKICAgIH0KCiAgICB2YXIgX3N0cmljdEluZGV4T2YgPSBzdHJpY3RJbmRleE9mOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uaW5kZXhPZmAgd2l0aG91dCBgZnJvbUluZGV4YCBib3VuZHMgY2hlY2tzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gZnJvbUluZGV4IFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBtYXRjaGVkIHZhbHVlLCBlbHNlIGAtMWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VJbmRleE9mKGFycmF5LCB2YWx1ZSwgZnJvbUluZGV4KSB7CiAgICAgIHJldHVybiB2YWx1ZSA9PT0gdmFsdWUKICAgICAgICA/IF9zdHJpY3RJbmRleE9mKGFycmF5LCB2YWx1ZSwgZnJvbUluZGV4KQogICAgICAgIDogX2Jhc2VGaW5kSW5kZXgoYXJyYXksIF9iYXNlSXNOYU4sIGZyb21JbmRleCk7CiAgICB9CgogICAgdmFyIF9iYXNlSW5kZXhPZiA9IGJhc2VJbmRleE9mOwoKICAgIC8qKgogICAgICogQSBzcGVjaWFsaXplZCB2ZXJzaW9uIG9mIGBfLmluY2x1ZGVzYCBmb3IgYXJyYXlzIHdpdGhvdXQgc3VwcG9ydCBmb3IKICAgICAqIHNwZWNpZnlpbmcgYW4gaW5kZXggdG8gc2VhcmNoIGZyb20uCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IFthcnJheV0gVGhlIGFycmF5IHRvIGluc3BlY3QuCiAgICAgKiBAcGFyYW0geyp9IHRhcmdldCBUaGUgdmFsdWUgdG8gc2VhcmNoIGZvci4KICAgICAqIEByZXR1cm5zIHtib29sZWFufSBSZXR1cm5zIGB0cnVlYCBpZiBgdGFyZ2V0YCBpcyBmb3VuZCwgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBhcnJheUluY2x1ZGVzKGFycmF5LCB2YWx1ZSkgewogICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgIHJldHVybiAhIWxlbmd0aCAmJiBfYmFzZUluZGV4T2YoYXJyYXksIHZhbHVlLCAwKSA+IC0xOwogICAgfQoKICAgIHZhciBfYXJyYXlJbmNsdWRlcyA9IGFycmF5SW5jbHVkZXM7CgogICAgLyoqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGxpa2UgYGFycmF5SW5jbHVkZXNgIGV4Y2VwdCB0aGF0IGl0IGFjY2VwdHMgYSBjb21wYXJhdG9yLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBbYXJyYXldIFRoZSBhcnJheSB0byBpbnNwZWN0LgogICAgICogQHBhcmFtIHsqfSB0YXJnZXQgVGhlIHZhbHVlIHRvIHNlYXJjaCBmb3IuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBjb21wYXJhdG9yIFRoZSBjb21wYXJhdG9yIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHRhcmdldGAgaXMgZm91bmQsIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gYXJyYXlJbmNsdWRlc1dpdGgoYXJyYXksIHZhbHVlLCBjb21wYXJhdG9yKSB7CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIGlmIChjb21wYXJhdG9yKHZhbHVlLCBhcnJheVtpbmRleF0pKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQoKICAgIHZhciBfYXJyYXlJbmNsdWRlc1dpdGggPSBhcnJheUluY2x1ZGVzV2l0aDsKCiAgICAvKioKICAgICAqIFRoaXMgbWV0aG9kIHJldHVybnMgYHVuZGVmaW5lZGAuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAyLjMuMAogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy50aW1lcygyLCBfLm5vb3ApOwogICAgICogLy8gPT4gW3VuZGVmaW5lZCwgdW5kZWZpbmVkXQogICAgICovCiAgICBmdW5jdGlvbiBub29wJGMoKSB7CiAgICAgIC8vIE5vIG9wZXJhdGlvbiBwZXJmb3JtZWQuCiAgICB9CgogICAgdmFyIG5vb3BfMSA9IG5vb3AkYzsKCiAgICAvKiogVXNlZCBhcyByZWZlcmVuY2VzIGZvciB2YXJpb3VzIGBOdW1iZXJgIGNvbnN0YW50cy4gKi8KICAgIHZhciBJTkZJTklUWSQyID0gMSAvIDA7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgc2V0IG9iamVjdCBvZiBgdmFsdWVzYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheX0gdmFsdWVzIFRoZSB2YWx1ZXMgdG8gYWRkIHRvIHRoZSBzZXQuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgc2V0LgogICAgICovCiAgICB2YXIgY3JlYXRlU2V0ID0gIShfU2V0ICYmICgxIC8gX3NldFRvQXJyYXkobmV3IF9TZXQoWywtMF0pKVsxXSkgPT0gSU5GSU5JVFkkMikgPyBub29wXzEgOiBmdW5jdGlvbih2YWx1ZXMpIHsKICAgICAgcmV0dXJuIG5ldyBfU2V0KHZhbHVlcyk7CiAgICB9OwoKICAgIHZhciBfY3JlYXRlU2V0ID0gY3JlYXRlU2V0OwoKICAgIC8qKiBVc2VkIGFzIHRoZSBzaXplIHRvIGVuYWJsZSBsYXJnZSBhcnJheSBvcHRpbWl6YXRpb25zLiAqLwogICAgdmFyIExBUkdFX0FSUkFZX1NJWkUkMSA9IDIwMDsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnVuaXFCeWAgd2l0aG91dCBzdXBwb3J0IGZvciBpdGVyYXRlZSBzaG9ydGhhbmRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZV0gVGhlIGl0ZXJhdGVlIGludm9rZWQgcGVyIGVsZW1lbnQuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbY29tcGFyYXRvcl0gVGhlIGNvbXBhcmF0b3IgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGR1cGxpY2F0ZSBmcmVlIGFycmF5LgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlVW5pcShhcnJheSwgaXRlcmF0ZWUsIGNvbXBhcmF0b3IpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBpbmNsdWRlcyA9IF9hcnJheUluY2x1ZGVzLAogICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoLAogICAgICAgICAgaXNDb21tb24gPSB0cnVlLAogICAgICAgICAgcmVzdWx0ID0gW10sCiAgICAgICAgICBzZWVuID0gcmVzdWx0OwoKICAgICAgaWYgKGNvbXBhcmF0b3IpIHsKICAgICAgICBpc0NvbW1vbiA9IGZhbHNlOwogICAgICAgIGluY2x1ZGVzID0gX2FycmF5SW5jbHVkZXNXaXRoOwogICAgICB9CiAgICAgIGVsc2UgaWYgKGxlbmd0aCA+PSBMQVJHRV9BUlJBWV9TSVpFJDEpIHsKICAgICAgICB2YXIgc2V0ID0gaXRlcmF0ZWUgPyBudWxsIDogX2NyZWF0ZVNldChhcnJheSk7CiAgICAgICAgaWYgKHNldCkgewogICAgICAgICAgcmV0dXJuIF9zZXRUb0FycmF5KHNldCk7CiAgICAgICAgfQogICAgICAgIGlzQ29tbW9uID0gZmFsc2U7CiAgICAgICAgaW5jbHVkZXMgPSBfY2FjaGVIYXM7CiAgICAgICAgc2VlbiA9IG5ldyBfU2V0Q2FjaGU7CiAgICAgIH0KICAgICAgZWxzZSB7CiAgICAgICAgc2VlbiA9IGl0ZXJhdGVlID8gW10gOiByZXN1bHQ7CiAgICAgIH0KICAgICAgb3V0ZXI6CiAgICAgIHdoaWxlICgrK2luZGV4IDwgbGVuZ3RoKSB7CiAgICAgICAgdmFyIHZhbHVlID0gYXJyYXlbaW5kZXhdLAogICAgICAgICAgICBjb21wdXRlZCA9IGl0ZXJhdGVlID8gaXRlcmF0ZWUodmFsdWUpIDogdmFsdWU7CgogICAgICAgIHZhbHVlID0gKGNvbXBhcmF0b3IgfHwgdmFsdWUgIT09IDApID8gdmFsdWUgOiAwOwogICAgICAgIGlmIChpc0NvbW1vbiAmJiBjb21wdXRlZCA9PT0gY29tcHV0ZWQpIHsKICAgICAgICAgIHZhciBzZWVuSW5kZXggPSBzZWVuLmxlbmd0aDsKICAgICAgICAgIHdoaWxlIChzZWVuSW5kZXgtLSkgewogICAgICAgICAgICBpZiAoc2VlbltzZWVuSW5kZXhdID09PSBjb21wdXRlZCkgewogICAgICAgICAgICAgIGNvbnRpbnVlIG91dGVyOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoaXRlcmF0ZWUpIHsKICAgICAgICAgICAgc2Vlbi5wdXNoKGNvbXB1dGVkKTsKICAgICAgICAgIH0KICAgICAgICAgIHJlc3VsdC5wdXNoKHZhbHVlKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoIWluY2x1ZGVzKHNlZW4sIGNvbXB1dGVkLCBjb21wYXJhdG9yKSkgewogICAgICAgICAgaWYgKHNlZW4gIT09IHJlc3VsdCkgewogICAgICAgICAgICBzZWVuLnB1c2goY29tcHV0ZWQpOwogICAgICAgICAgfQogICAgICAgICAgcmVzdWx0LnB1c2godmFsdWUpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZVVuaXEgPSBiYXNlVW5pcTsKCiAgICAvKioKICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uaXNBcnJheUxpa2VgIGV4Y2VwdCB0aGF0IGl0IGFsc28gY2hlY2tzIGlmIGB2YWx1ZWAKICAgICAqIGlzIGFuIG9iamVjdC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMC4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhbiBhcnJheS1saWtlIG9iamVjdCwKICAgICAqICBlbHNlIGBmYWxzZWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uaXNBcnJheUxpa2VPYmplY3QoWzEsIDIsIDNdKTsKICAgICAqIC8vID0+IHRydWUKICAgICAqCiAgICAgKiBfLmlzQXJyYXlMaWtlT2JqZWN0KGRvY3VtZW50LmJvZHkuY2hpbGRyZW4pOwogICAgICogLy8gPT4gdHJ1ZQogICAgICoKICAgICAqIF8uaXNBcnJheUxpa2VPYmplY3QoJ2FiYycpOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmlzQXJyYXlMaWtlT2JqZWN0KF8ubm9vcCk7CiAgICAgKiAvLyA9PiBmYWxzZQogICAgICovCiAgICBmdW5jdGlvbiBpc0FycmF5TGlrZU9iamVjdCh2YWx1ZSkgewogICAgICByZXR1cm4gaXNPYmplY3RMaWtlXzEodmFsdWUpICYmIGlzQXJyYXlMaWtlXzEodmFsdWUpOwogICAgfQoKICAgIHZhciBpc0FycmF5TGlrZU9iamVjdF8xID0gaXNBcnJheUxpa2VPYmplY3Q7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGFuIGFycmF5IG9mIHVuaXF1ZSB2YWx1ZXMsIGluIG9yZGVyLCBmcm9tIGFsbCBnaXZlbiBhcnJheXMgdXNpbmcKICAgICAqIFtgU2FtZVZhbHVlWmVyb2BdKGh0dHA6Ly9lY21hLWludGVybmF0aW9uYWwub3JnL2VjbWEtMjYyLzcuMC8jc2VjLXNhbWV2YWx1ZXplcm8pCiAgICAgKiBmb3IgZXF1YWxpdHkgY29tcGFyaXNvbnMuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgKiBAcGFyYW0gey4uLkFycmF5fSBbYXJyYXlzXSBUaGUgYXJyYXlzIHRvIGluc3BlY3QuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIG5ldyBhcnJheSBvZiBjb21iaW5lZCB2YWx1ZXMuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8udW5pb24oWzJdLCBbMSwgMl0pOwogICAgICogLy8gPT4gWzIsIDFdCiAgICAgKi8KICAgIHZhciB1bmlvbiA9IF9iYXNlUmVzdChmdW5jdGlvbihhcnJheXMpIHsKICAgICAgcmV0dXJuIF9iYXNlVW5pcShfYmFzZUZsYXR0ZW4oYXJyYXlzLCAxLCBpc0FycmF5TGlrZU9iamVjdF8xLCB0cnVlKSk7CiAgICB9KTsKCiAgICB2YXIgdW5pb25fMSA9IHVuaW9uOwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8udmFsdWVzYCBhbmQgYF8udmFsdWVzSW5gIHdoaWNoIGNyZWF0ZXMgYW4KICAgICAqIGFycmF5IG9mIGBvYmplY3RgIHByb3BlcnR5IHZhbHVlcyBjb3JyZXNwb25kaW5nIHRvIHRoZSBwcm9wZXJ0eSBuYW1lcwogICAgICogb2YgYHByb3BzYC4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtPYmplY3R9IG9iamVjdCBUaGUgb2JqZWN0IHRvIHF1ZXJ5LgogICAgICogQHBhcmFtIHtBcnJheX0gcHJvcHMgVGhlIHByb3BlcnR5IG5hbWVzIHRvIGdldCB2YWx1ZXMgZm9yLgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgYXJyYXkgb2YgcHJvcGVydHkgdmFsdWVzLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlVmFsdWVzKG9iamVjdCwgcHJvcHMpIHsKICAgICAgcmV0dXJuIF9hcnJheU1hcChwcm9wcywgZnVuY3Rpb24oa2V5KSB7CiAgICAgICAgcmV0dXJuIG9iamVjdFtrZXldOwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgX2Jhc2VWYWx1ZXMgPSBiYXNlVmFsdWVzOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiB0aGUgb3duIGVudW1lcmFibGUgc3RyaW5nIGtleWVkIHByb3BlcnR5IHZhbHVlcyBvZiBgb2JqZWN0YC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogTm9uLW9iamVjdCB2YWx1ZXMgYXJlIGNvZXJjZWQgdG8gb2JqZWN0cy4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gcXVlcnkuCiAgICAgKiBAcmV0dXJucyB7QXJyYXl9IFJldHVybnMgdGhlIGFycmF5IG9mIHByb3BlcnR5IHZhbHVlcy4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICogICB0aGlzLmEgPSAxOwogICAgICogICB0aGlzLmIgPSAyOwogICAgICogfQogICAgICoKICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgKgogICAgICogXy52YWx1ZXMobmV3IEZvbyk7CiAgICAgKiAvLyA9PiBbMSwgMl0gKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkKICAgICAqCiAgICAgKiBfLnZhbHVlcygnaGknKTsKICAgICAqIC8vID0+IFsnaCcsICdpJ10KICAgICAqLwogICAgZnVuY3Rpb24gdmFsdWVzJDIob2JqZWN0KSB7CiAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbCA/IFtdIDogX2Jhc2VWYWx1ZXMob2JqZWN0LCBrZXlzXzEob2JqZWN0KSk7CiAgICB9CgogICAgdmFyIHZhbHVlc18xID0gdmFsdWVzJDI7CgogICAgLyogZ2xvYmFsIHdpbmRvdyAqLwoKICAgIHZhciBsb2Rhc2gkMTsKCiAgICBpZiAodHlwZW9mIGNvbW1vbmpzUmVxdWlyZSA9PT0gImZ1bmN0aW9uIikgewogICAgICB0cnkgewogICAgICAgIGxvZGFzaCQxID0gewogICAgICAgICAgY2xvbmU6IGNsb25lXzEsCiAgICAgICAgICBjb25zdGFudDogY29uc3RhbnRfMSwKICAgICAgICAgIGVhY2g6IGVhY2gsCiAgICAgICAgICBmaWx0ZXI6IGZpbHRlcl8xLAogICAgICAgICAgaGFzOiAgaGFzXzEsCiAgICAgICAgICBpc0FycmF5OiBpc0FycmF5XzEsCiAgICAgICAgICBpc0VtcHR5OiBpc0VtcHR5XzEsCiAgICAgICAgICBpc0Z1bmN0aW9uOiBpc0Z1bmN0aW9uXzEsCiAgICAgICAgICBpc1VuZGVmaW5lZDogaXNVbmRlZmluZWRfMSwKICAgICAgICAgIGtleXM6IGtleXNfMSwKICAgICAgICAgIG1hcDogbWFwXzEsCiAgICAgICAgICByZWR1Y2U6IHJlZHVjZV8xLAogICAgICAgICAgc2l6ZTogc2l6ZV8xLAogICAgICAgICAgdHJhbnNmb3JtOiB0cmFuc2Zvcm1fMSwKICAgICAgICAgIHVuaW9uOiB1bmlvbl8xLAogICAgICAgICAgdmFsdWVzOiB2YWx1ZXNfMQogICAgICAgIH07CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAvLyBjb250aW51ZSByZWdhcmRsZXNzIG9mIGVycm9yCiAgICAgIH0KICAgIH0KCiAgICBpZiAoIWxvZGFzaCQxKSB7CiAgICAgIGxvZGFzaCQxID0gd2luZG93Ll87CiAgICB9CgogICAgdmFyIGxvZGFzaF8xID0gbG9kYXNoJDE7CgogICAgdmFyIGdyYXBoID0gR3JhcGg7CgogICAgdmFyIERFRkFVTFRfRURHRV9OQU1FID0gIlx4MDAiOwogICAgdmFyIEdSQVBIX05PREUgPSAiXHgwMCI7CiAgICB2YXIgRURHRV9LRVlfREVMSU0gPSAiXHgwMSI7CgogICAgLy8gSW1wbGVtZW50YXRpb24gbm90ZXM6CiAgICAvLwogICAgLy8gICogTm9kZSBpZCBxdWVyeSBmdW5jdGlvbnMgc2hvdWxkIHJldHVybiBzdHJpbmcgaWRzIGZvciB0aGUgbm9kZXMKICAgIC8vICAqIEVkZ2UgaWQgcXVlcnkgZnVuY3Rpb25zIHNob3VsZCByZXR1cm4gYW4gImVkZ2VPYmoiLCBlZGdlIG9iamVjdCwgdGhhdCBpcwogICAgLy8gICAgY29tcG9zZWQgb2YgZW5vdWdoIGluZm9ybWF0aW9uIHRvIHVuaXF1ZWx5IGlkZW50aWZ5IGFuIGVkZ2U6IHt2LCB3LCBuYW1lfS4KICAgIC8vICAqIEludGVybmFsbHkgd2UgdXNlIGFuICJlZGdlSWQiLCBhIHN0cmluZ2lmaWVkIGZvcm0gb2YgdGhlIGVkZ2VPYmosIHRvCiAgICAvLyAgICByZWZlcmVuY2UgZWRnZXMuIFRoaXMgaXMgYmVjYXVzZSB3ZSBuZWVkIGEgcGVyZm9ybWFudCB3YXkgdG8gbG9vayB0aGVzZQogICAgLy8gICAgZWRnZXMgdXAgYW5kLCBvYmplY3QgcHJvcGVydGllcywgd2hpY2ggaGF2ZSBzdHJpbmcga2V5cywgYXJlIHRoZSBjbG9zZXN0CiAgICAvLyAgICB3ZSdyZSBnb2luZyB0byBnZXQgdG8gYSBwZXJmb3JtYW50IGhhc2h0YWJsZSBpbiBKYXZhU2NyaXB0LgoKICAgIGZ1bmN0aW9uIEdyYXBoKG9wdHMpIHsKICAgICAgdGhpcy5faXNEaXJlY3RlZCA9IGxvZGFzaF8xLmhhcyhvcHRzLCAiZGlyZWN0ZWQiKSA/IG9wdHMuZGlyZWN0ZWQgOiB0cnVlOwogICAgICB0aGlzLl9pc011bHRpZ3JhcGggPSBsb2Rhc2hfMS5oYXMob3B0cywgIm11bHRpZ3JhcGgiKSA/IG9wdHMubXVsdGlncmFwaCA6IGZhbHNlOwogICAgICB0aGlzLl9pc0NvbXBvdW5kID0gbG9kYXNoXzEuaGFzKG9wdHMsICJjb21wb3VuZCIpID8gb3B0cy5jb21wb3VuZCA6IGZhbHNlOwoKICAgICAgLy8gTGFiZWwgZm9yIHRoZSBncmFwaCBpdHNlbGYKICAgICAgdGhpcy5fbGFiZWwgPSB1bmRlZmluZWQ7CgogICAgICAvLyBEZWZhdWx0cyB0byBiZSBzZXQgd2hlbiBjcmVhdGluZyBhIG5ldyBub2RlCiAgICAgIHRoaXMuX2RlZmF1bHROb2RlTGFiZWxGbiA9IGxvZGFzaF8xLmNvbnN0YW50KHVuZGVmaW5lZCk7CgogICAgICAvLyBEZWZhdWx0cyB0byBiZSBzZXQgd2hlbiBjcmVhdGluZyBhIG5ldyBlZGdlCiAgICAgIHRoaXMuX2RlZmF1bHRFZGdlTGFiZWxGbiA9IGxvZGFzaF8xLmNvbnN0YW50KHVuZGVmaW5lZCk7CgogICAgICAvLyB2IC0+IGxhYmVsCiAgICAgIHRoaXMuX25vZGVzID0ge307CgogICAgICBpZiAodGhpcy5faXNDb21wb3VuZCkgewogICAgICAgIC8vIHYgLT4gcGFyZW50CiAgICAgICAgdGhpcy5fcGFyZW50ID0ge307CgogICAgICAgIC8vIHYgLT4gY2hpbGRyZW4KICAgICAgICB0aGlzLl9jaGlsZHJlbiA9IHt9OwogICAgICAgIHRoaXMuX2NoaWxkcmVuW0dSQVBIX05PREVdID0ge307CiAgICAgIH0KCiAgICAgIC8vIHYgLT4gZWRnZU9iagogICAgICB0aGlzLl9pbiA9IHt9OwoKICAgICAgLy8gdSAtPiB2IC0+IE51bWJlcgogICAgICB0aGlzLl9wcmVkcyA9IHt9OwoKICAgICAgLy8gdiAtPiBlZGdlT2JqCiAgICAgIHRoaXMuX291dCA9IHt9OwoKICAgICAgLy8gdiAtPiB3IC0+IE51bWJlcgogICAgICB0aGlzLl9zdWNzID0ge307CgogICAgICAvLyBlIC0+IGVkZ2VPYmoKICAgICAgdGhpcy5fZWRnZU9ianMgPSB7fTsKCiAgICAgIC8vIGUgLT4gbGFiZWwKICAgICAgdGhpcy5fZWRnZUxhYmVscyA9IHt9OwogICAgfQoKICAgIC8qIE51bWJlciBvZiBub2RlcyBpbiB0aGUgZ3JhcGguIFNob3VsZCBvbmx5IGJlIGNoYW5nZWQgYnkgdGhlIGltcGxlbWVudGF0aW9uLiAqLwogICAgR3JhcGgucHJvdG90eXBlLl9ub2RlQ291bnQgPSAwOwoKICAgIC8qIE51bWJlciBvZiBlZGdlcyBpbiB0aGUgZ3JhcGguIFNob3VsZCBvbmx5IGJlIGNoYW5nZWQgYnkgdGhlIGltcGxlbWVudGF0aW9uLiAqLwogICAgR3JhcGgucHJvdG90eXBlLl9lZGdlQ291bnQgPSAwOwoKCiAgICAvKiA9PT0gR3JhcGggZnVuY3Rpb25zID09PT09PT09PSAqLwoKICAgIEdyYXBoLnByb3RvdHlwZS5pc0RpcmVjdGVkID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9pc0RpcmVjdGVkOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuaXNNdWx0aWdyYXBoID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9pc011bHRpZ3JhcGg7CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5pc0NvbXBvdW5kID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9pc0NvbXBvdW5kOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuc2V0R3JhcGggPSBmdW5jdGlvbihsYWJlbCkgewogICAgICB0aGlzLl9sYWJlbCA9IGxhYmVsOwogICAgICByZXR1cm4gdGhpczsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLmdyYXBoID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9sYWJlbDsKICAgIH07CgoKICAgIC8qID09PSBOb2RlIGZ1bmN0aW9ucyA9PT09PT09PT09ICovCgogICAgR3JhcGgucHJvdG90eXBlLnNldERlZmF1bHROb2RlTGFiZWwgPSBmdW5jdGlvbihuZXdEZWZhdWx0KSB7CiAgICAgIGlmICghbG9kYXNoXzEuaXNGdW5jdGlvbihuZXdEZWZhdWx0KSkgewogICAgICAgIG5ld0RlZmF1bHQgPSBsb2Rhc2hfMS5jb25zdGFudChuZXdEZWZhdWx0KTsKICAgICAgfQogICAgICB0aGlzLl9kZWZhdWx0Tm9kZUxhYmVsRm4gPSBuZXdEZWZhdWx0OwogICAgICByZXR1cm4gdGhpczsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLm5vZGVDb3VudCA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5fbm9kZUNvdW50OwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUubm9kZXMgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xLmtleXModGhpcy5fbm9kZXMpOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuc291cmNlcyA9IGZ1bmN0aW9uKCkgewogICAgICB2YXIgc2VsZiA9IHRoaXM7CiAgICAgIHJldHVybiBsb2Rhc2hfMS5maWx0ZXIodGhpcy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaF8xLmlzRW1wdHkoc2VsZi5faW5bdl0pOwogICAgICB9KTsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnNpbmtzID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBzZWxmID0gdGhpczsKICAgICAgcmV0dXJuIGxvZGFzaF8xLmZpbHRlcih0aGlzLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICByZXR1cm4gbG9kYXNoXzEuaXNFbXB0eShzZWxmLl9vdXRbdl0pOwogICAgICB9KTsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnNldE5vZGVzID0gZnVuY3Rpb24odnMsIHZhbHVlKSB7CiAgICAgIHZhciBhcmdzID0gYXJndW1lbnRzOwogICAgICB2YXIgc2VsZiA9IHRoaXM7CiAgICAgIGxvZGFzaF8xLmVhY2godnMsIGZ1bmN0aW9uKHYpIHsKICAgICAgICBpZiAoYXJncy5sZW5ndGggPiAxKSB7CiAgICAgICAgICBzZWxmLnNldE5vZGUodiwgdmFsdWUpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBzZWxmLnNldE5vZGUodik7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5zZXROb2RlID0gZnVuY3Rpb24odiwgdmFsdWUpIHsKICAgICAgaWYgKGxvZGFzaF8xLmhhcyh0aGlzLl9ub2RlcywgdikpIHsKICAgICAgICBpZiAoYXJndW1lbnRzLmxlbmd0aCA+IDEpIHsKICAgICAgICAgIHRoaXMuX25vZGVzW3ZdID0gdmFsdWU7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzOwogICAgICB9CgogICAgICB0aGlzLl9ub2Rlc1t2XSA9IGFyZ3VtZW50cy5sZW5ndGggPiAxID8gdmFsdWUgOiB0aGlzLl9kZWZhdWx0Tm9kZUxhYmVsRm4odik7CiAgICAgIGlmICh0aGlzLl9pc0NvbXBvdW5kKSB7CiAgICAgICAgdGhpcy5fcGFyZW50W3ZdID0gR1JBUEhfTk9ERTsKICAgICAgICB0aGlzLl9jaGlsZHJlblt2XSA9IHt9OwogICAgICAgIHRoaXMuX2NoaWxkcmVuW0dSQVBIX05PREVdW3ZdID0gdHJ1ZTsKICAgICAgfQogICAgICB0aGlzLl9pblt2XSA9IHt9OwogICAgICB0aGlzLl9wcmVkc1t2XSA9IHt9OwogICAgICB0aGlzLl9vdXRbdl0gPSB7fTsKICAgICAgdGhpcy5fc3Vjc1t2XSA9IHt9OwogICAgICArK3RoaXMuX25vZGVDb3VudDsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5ub2RlID0gZnVuY3Rpb24odikgewogICAgICByZXR1cm4gdGhpcy5fbm9kZXNbdl07CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5oYXNOb2RlID0gZnVuY3Rpb24odikgewogICAgICByZXR1cm4gbG9kYXNoXzEuaGFzKHRoaXMuX25vZGVzLCB2KTsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnJlbW92ZU5vZGUgPSAgZnVuY3Rpb24odikgewogICAgICB2YXIgc2VsZiA9IHRoaXM7CiAgICAgIGlmIChsb2Rhc2hfMS5oYXModGhpcy5fbm9kZXMsIHYpKSB7CiAgICAgICAgdmFyIHJlbW92ZUVkZ2UgPSBmdW5jdGlvbihlKSB7IHNlbGYucmVtb3ZlRWRnZShzZWxmLl9lZGdlT2Jqc1tlXSk7IH07CiAgICAgICAgZGVsZXRlIHRoaXMuX25vZGVzW3ZdOwogICAgICAgIGlmICh0aGlzLl9pc0NvbXBvdW5kKSB7CiAgICAgICAgICB0aGlzLl9yZW1vdmVGcm9tUGFyZW50c0NoaWxkTGlzdCh2KTsKICAgICAgICAgIGRlbGV0ZSB0aGlzLl9wYXJlbnRbdl07CiAgICAgICAgICBsb2Rhc2hfMS5lYWNoKHRoaXMuY2hpbGRyZW4odiksIGZ1bmN0aW9uKGNoaWxkKSB7CiAgICAgICAgICAgIHNlbGYuc2V0UGFyZW50KGNoaWxkKTsKICAgICAgICAgIH0pOwogICAgICAgICAgZGVsZXRlIHRoaXMuX2NoaWxkcmVuW3ZdOwogICAgICAgIH0KICAgICAgICBsb2Rhc2hfMS5lYWNoKGxvZGFzaF8xLmtleXModGhpcy5faW5bdl0pLCByZW1vdmVFZGdlKTsKICAgICAgICBkZWxldGUgdGhpcy5faW5bdl07CiAgICAgICAgZGVsZXRlIHRoaXMuX3ByZWRzW3ZdOwogICAgICAgIGxvZGFzaF8xLmVhY2gobG9kYXNoXzEua2V5cyh0aGlzLl9vdXRbdl0pLCByZW1vdmVFZGdlKTsKICAgICAgICBkZWxldGUgdGhpcy5fb3V0W3ZdOwogICAgICAgIGRlbGV0ZSB0aGlzLl9zdWNzW3ZdOwogICAgICAgIC0tdGhpcy5fbm9kZUNvdW50OwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuc2V0UGFyZW50ID0gZnVuY3Rpb24odiwgcGFyZW50KSB7CiAgICAgIGlmICghdGhpcy5faXNDb21wb3VuZCkgewogICAgICAgIHRocm93IG5ldyBFcnJvcigiQ2Fubm90IHNldCBwYXJlbnQgaW4gYSBub24tY29tcG91bmQgZ3JhcGgiKTsKICAgICAgfQoKICAgICAgaWYgKGxvZGFzaF8xLmlzVW5kZWZpbmVkKHBhcmVudCkpIHsKICAgICAgICBwYXJlbnQgPSBHUkFQSF9OT0RFOwogICAgICB9IGVsc2UgewogICAgICAgIC8vIENvZXJjZSBwYXJlbnQgdG8gc3RyaW5nCiAgICAgICAgcGFyZW50ICs9ICIiOwogICAgICAgIGZvciAodmFyIGFuY2VzdG9yID0gcGFyZW50OwogICAgICAgICAgIWxvZGFzaF8xLmlzVW5kZWZpbmVkKGFuY2VzdG9yKTsKICAgICAgICAgIGFuY2VzdG9yID0gdGhpcy5wYXJlbnQoYW5jZXN0b3IpKSB7CiAgICAgICAgICBpZiAoYW5jZXN0b3IgPT09IHYpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJTZXR0aW5nICIgKyBwYXJlbnQrICIgYXMgcGFyZW50IG9mICIgKyB2ICsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICIgd291bGQgY3JlYXRlIGEgY3ljbGUiKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHRoaXMuc2V0Tm9kZShwYXJlbnQpOwogICAgICB9CgogICAgICB0aGlzLnNldE5vZGUodik7CiAgICAgIHRoaXMuX3JlbW92ZUZyb21QYXJlbnRzQ2hpbGRMaXN0KHYpOwogICAgICB0aGlzLl9wYXJlbnRbdl0gPSBwYXJlbnQ7CiAgICAgIHRoaXMuX2NoaWxkcmVuW3BhcmVudF1bdl0gPSB0cnVlOwogICAgICByZXR1cm4gdGhpczsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLl9yZW1vdmVGcm9tUGFyZW50c0NoaWxkTGlzdCA9IGZ1bmN0aW9uKHYpIHsKICAgICAgZGVsZXRlIHRoaXMuX2NoaWxkcmVuW3RoaXMuX3BhcmVudFt2XV1bdl07CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5wYXJlbnQgPSBmdW5jdGlvbih2KSB7CiAgICAgIGlmICh0aGlzLl9pc0NvbXBvdW5kKSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHRoaXMuX3BhcmVudFt2XTsKICAgICAgICBpZiAocGFyZW50ICE9PSBHUkFQSF9OT0RFKSB7CiAgICAgICAgICByZXR1cm4gcGFyZW50OwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuY2hpbGRyZW4gPSBmdW5jdGlvbih2KSB7CiAgICAgIGlmIChsb2Rhc2hfMS5pc1VuZGVmaW5lZCh2KSkgewogICAgICAgIHYgPSBHUkFQSF9OT0RFOwogICAgICB9CgogICAgICBpZiAodGhpcy5faXNDb21wb3VuZCkgewogICAgICAgIHZhciBjaGlsZHJlbiA9IHRoaXMuX2NoaWxkcmVuW3ZdOwogICAgICAgIGlmIChjaGlsZHJlbikgewogICAgICAgICAgcmV0dXJuIGxvZGFzaF8xLmtleXMoY2hpbGRyZW4pOwogICAgICAgIH0KICAgICAgfSBlbHNlIGlmICh2ID09PSBHUkFQSF9OT0RFKSB7CiAgICAgICAgcmV0dXJuIHRoaXMubm9kZXMoKTsKICAgICAgfSBlbHNlIGlmICh0aGlzLmhhc05vZGUodikpIHsKICAgICAgICByZXR1cm4gW107CiAgICAgIH0KICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnByZWRlY2Vzc29ycyA9IGZ1bmN0aW9uKHYpIHsKICAgICAgdmFyIHByZWRzViA9IHRoaXMuX3ByZWRzW3ZdOwogICAgICBpZiAocHJlZHNWKSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaF8xLmtleXMocHJlZHNWKTsKICAgICAgfQogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuc3VjY2Vzc29ycyA9IGZ1bmN0aW9uKHYpIHsKICAgICAgdmFyIHN1Y3NWID0gdGhpcy5fc3Vjc1t2XTsKICAgICAgaWYgKHN1Y3NWKSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaF8xLmtleXMoc3Vjc1YpOwogICAgICB9CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5uZWlnaGJvcnMgPSBmdW5jdGlvbih2KSB7CiAgICAgIHZhciBwcmVkcyA9IHRoaXMucHJlZGVjZXNzb3JzKHYpOwogICAgICBpZiAocHJlZHMpIHsKICAgICAgICByZXR1cm4gbG9kYXNoXzEudW5pb24ocHJlZHMsIHRoaXMuc3VjY2Vzc29ycyh2KSk7CiAgICAgIH0KICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLmlzTGVhZiA9IGZ1bmN0aW9uICh2KSB7CiAgICAgIHZhciBuZWlnaGJvcnM7CiAgICAgIGlmICh0aGlzLmlzRGlyZWN0ZWQoKSkgewogICAgICAgIG5laWdoYm9ycyA9IHRoaXMuc3VjY2Vzc29ycyh2KTsKICAgICAgfSBlbHNlIHsKICAgICAgICBuZWlnaGJvcnMgPSB0aGlzLm5laWdoYm9ycyh2KTsKICAgICAgfQogICAgICByZXR1cm4gbmVpZ2hib3JzLmxlbmd0aCA9PT0gMDsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLmZpbHRlck5vZGVzID0gZnVuY3Rpb24oZmlsdGVyKSB7CiAgICAgIHZhciBjb3B5ID0gbmV3IHRoaXMuY29uc3RydWN0b3IoewogICAgICAgIGRpcmVjdGVkOiB0aGlzLl9pc0RpcmVjdGVkLAogICAgICAgIG11bHRpZ3JhcGg6IHRoaXMuX2lzTXVsdGlncmFwaCwKICAgICAgICBjb21wb3VuZDogdGhpcy5faXNDb21wb3VuZAogICAgICB9KTsKCiAgICAgIGNvcHkuc2V0R3JhcGgodGhpcy5ncmFwaCgpKTsKCiAgICAgIHZhciBzZWxmID0gdGhpczsKICAgICAgbG9kYXNoXzEuZWFjaCh0aGlzLl9ub2RlcywgZnVuY3Rpb24odmFsdWUsIHYpIHsKICAgICAgICBpZiAoZmlsdGVyKHYpKSB7CiAgICAgICAgICBjb3B5LnNldE5vZGUodiwgdmFsdWUpOwogICAgICAgIH0KICAgICAgfSk7CgogICAgICBsb2Rhc2hfMS5lYWNoKHRoaXMuX2VkZ2VPYmpzLCBmdW5jdGlvbihlKSB7CiAgICAgICAgaWYgKGNvcHkuaGFzTm9kZShlLnYpICYmIGNvcHkuaGFzTm9kZShlLncpKSB7CiAgICAgICAgICBjb3B5LnNldEVkZ2UoZSwgc2VsZi5lZGdlKGUpKTsKICAgICAgICB9CiAgICAgIH0pOwoKICAgICAgdmFyIHBhcmVudHMgPSB7fTsKICAgICAgZnVuY3Rpb24gZmluZFBhcmVudCh2KSB7CiAgICAgICAgdmFyIHBhcmVudCA9IHNlbGYucGFyZW50KHYpOwogICAgICAgIGlmIChwYXJlbnQgPT09IHVuZGVmaW5lZCB8fCBjb3B5Lmhhc05vZGUocGFyZW50KSkgewogICAgICAgICAgcGFyZW50c1t2XSA9IHBhcmVudDsKICAgICAgICAgIHJldHVybiBwYXJlbnQ7CiAgICAgICAgfSBlbHNlIGlmIChwYXJlbnQgaW4gcGFyZW50cykgewogICAgICAgICAgcmV0dXJuIHBhcmVudHNbcGFyZW50XTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIGZpbmRQYXJlbnQocGFyZW50KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGlmICh0aGlzLl9pc0NvbXBvdW5kKSB7CiAgICAgICAgbG9kYXNoXzEuZWFjaChjb3B5Lm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICAgIGNvcHkuc2V0UGFyZW50KHYsIGZpbmRQYXJlbnQodikpOwogICAgICAgIH0pOwogICAgICB9CgogICAgICByZXR1cm4gY29weTsKICAgIH07CgogICAgLyogPT09IEVkZ2UgZnVuY3Rpb25zID09PT09PT09PT0gKi8KCiAgICBHcmFwaC5wcm90b3R5cGUuc2V0RGVmYXVsdEVkZ2VMYWJlbCA9IGZ1bmN0aW9uKG5ld0RlZmF1bHQpIHsKICAgICAgaWYgKCFsb2Rhc2hfMS5pc0Z1bmN0aW9uKG5ld0RlZmF1bHQpKSB7CiAgICAgICAgbmV3RGVmYXVsdCA9IGxvZGFzaF8xLmNvbnN0YW50KG5ld0RlZmF1bHQpOwogICAgICB9CiAgICAgIHRoaXMuX2RlZmF1bHRFZGdlTGFiZWxGbiA9IG5ld0RlZmF1bHQ7CiAgICAgIHJldHVybiB0aGlzOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuZWRnZUNvdW50ID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9lZGdlQ291bnQ7CiAgICB9OwoKICAgIEdyYXBoLnByb3RvdHlwZS5lZGdlcyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gbG9kYXNoXzEudmFsdWVzKHRoaXMuX2VkZ2VPYmpzKTsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnNldFBhdGggPSBmdW5jdGlvbih2cywgdmFsdWUpIHsKICAgICAgdmFyIHNlbGYgPSB0aGlzOwogICAgICB2YXIgYXJncyA9IGFyZ3VtZW50czsKICAgICAgbG9kYXNoXzEucmVkdWNlKHZzLCBmdW5jdGlvbih2LCB3KSB7CiAgICAgICAgaWYgKGFyZ3MubGVuZ3RoID4gMSkgewogICAgICAgICAgc2VsZi5zZXRFZGdlKHYsIHcsIHZhbHVlKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgc2VsZi5zZXRFZGdlKHYsIHcpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdzsKICAgICAgfSk7CiAgICAgIHJldHVybiB0aGlzOwogICAgfTsKCiAgICAvKgogICAgICogc2V0RWRnZSh2LCB3LCBbdmFsdWUsIFtuYW1lXV0pCiAgICAgKiBzZXRFZGdlKHsgdiwgdywgW25hbWVdIH0sIFt2YWx1ZV0pCiAgICAgKi8KICAgIEdyYXBoLnByb3RvdHlwZS5zZXRFZGdlID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciB2LCB3LCBuYW1lLCB2YWx1ZTsKICAgICAgdmFyIHZhbHVlU3BlY2lmaWVkID0gZmFsc2U7CiAgICAgIHZhciBhcmcwID0gYXJndW1lbnRzWzBdOwoKICAgICAgaWYgKHR5cGVvZiBhcmcwID09PSAib2JqZWN0IiAmJiBhcmcwICE9PSBudWxsICYmICJ2IiBpbiBhcmcwKSB7CiAgICAgICAgdiA9IGFyZzAudjsKICAgICAgICB3ID0gYXJnMC53OwogICAgICAgIG5hbWUgPSBhcmcwLm5hbWU7CiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDIpIHsKICAgICAgICAgIHZhbHVlID0gYXJndW1lbnRzWzFdOwogICAgICAgICAgdmFsdWVTcGVjaWZpZWQgPSB0cnVlOwogICAgICAgIH0KICAgICAgfSBlbHNlIHsKICAgICAgICB2ID0gYXJnMDsKICAgICAgICB3ID0gYXJndW1lbnRzWzFdOwogICAgICAgIG5hbWUgPSBhcmd1bWVudHNbM107CiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPiAyKSB7CiAgICAgICAgICB2YWx1ZSA9IGFyZ3VtZW50c1syXTsKICAgICAgICAgIHZhbHVlU3BlY2lmaWVkID0gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHYgPSAiIiArIHY7CiAgICAgIHcgPSAiIiArIHc7CiAgICAgIGlmICghbG9kYXNoXzEuaXNVbmRlZmluZWQobmFtZSkpIHsKICAgICAgICBuYW1lID0gIiIgKyBuYW1lOwogICAgICB9CgogICAgICB2YXIgZSA9IGVkZ2VBcmdzVG9JZCh0aGlzLl9pc0RpcmVjdGVkLCB2LCB3LCBuYW1lKTsKICAgICAgaWYgKGxvZGFzaF8xLmhhcyh0aGlzLl9lZGdlTGFiZWxzLCBlKSkgewogICAgICAgIGlmICh2YWx1ZVNwZWNpZmllZCkgewogICAgICAgICAgdGhpcy5fZWRnZUxhYmVsc1tlXSA9IHZhbHVlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpczsKICAgICAgfQoKICAgICAgaWYgKCFsb2Rhc2hfMS5pc1VuZGVmaW5lZChuYW1lKSAmJiAhdGhpcy5faXNNdWx0aWdyYXBoKSB7CiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJDYW5ub3Qgc2V0IGEgbmFtZWQgZWRnZSB3aGVuIGlzTXVsdGlncmFwaCA9IGZhbHNlIik7CiAgICAgIH0KCiAgICAgIC8vIEl0IGRpZG4ndCBleGlzdCwgc28gd2UgbmVlZCB0byBjcmVhdGUgaXQuCiAgICAgIC8vIEZpcnN0IGVuc3VyZSB0aGUgbm9kZXMgZXhpc3QuCiAgICAgIHRoaXMuc2V0Tm9kZSh2KTsKICAgICAgdGhpcy5zZXROb2RlKHcpOwoKICAgICAgdGhpcy5fZWRnZUxhYmVsc1tlXSA9IHZhbHVlU3BlY2lmaWVkID8gdmFsdWUgOiB0aGlzLl9kZWZhdWx0RWRnZUxhYmVsRm4odiwgdywgbmFtZSk7CgogICAgICB2YXIgZWRnZU9iaiA9IGVkZ2VBcmdzVG9PYmoodGhpcy5faXNEaXJlY3RlZCwgdiwgdywgbmFtZSk7CiAgICAgIC8vIEVuc3VyZSB3ZSBhZGQgdW5kaXJlY3RlZCBlZGdlcyBpbiBhIGNvbnNpc3RlbnQgd2F5LgogICAgICB2ID0gZWRnZU9iai52OwogICAgICB3ID0gZWRnZU9iai53OwoKICAgICAgT2JqZWN0LmZyZWV6ZShlZGdlT2JqKTsKICAgICAgdGhpcy5fZWRnZU9ianNbZV0gPSBlZGdlT2JqOwogICAgICBpbmNyZW1lbnRPckluaXRFbnRyeSh0aGlzLl9wcmVkc1t3XSwgdik7CiAgICAgIGluY3JlbWVudE9ySW5pdEVudHJ5KHRoaXMuX3N1Y3Nbdl0sIHcpOwogICAgICB0aGlzLl9pblt3XVtlXSA9IGVkZ2VPYmo7CiAgICAgIHRoaXMuX291dFt2XVtlXSA9IGVkZ2VPYmo7CiAgICAgIHRoaXMuX2VkZ2VDb3VudCsrOwogICAgICByZXR1cm4gdGhpczsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLmVkZ2UgPSBmdW5jdGlvbih2LCB3LCBuYW1lKSB7CiAgICAgIHZhciBlID0gKGFyZ3VtZW50cy5sZW5ndGggPT09IDEKICAgICAgICA/IGVkZ2VPYmpUb0lkKHRoaXMuX2lzRGlyZWN0ZWQsIGFyZ3VtZW50c1swXSkKICAgICAgICA6IGVkZ2VBcmdzVG9JZCh0aGlzLl9pc0RpcmVjdGVkLCB2LCB3LCBuYW1lKSk7CiAgICAgIHJldHVybiB0aGlzLl9lZGdlTGFiZWxzW2VdOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuaGFzRWRnZSA9IGZ1bmN0aW9uKHYsIHcsIG5hbWUpIHsKICAgICAgdmFyIGUgPSAoYXJndW1lbnRzLmxlbmd0aCA9PT0gMQogICAgICAgID8gZWRnZU9ialRvSWQodGhpcy5faXNEaXJlY3RlZCwgYXJndW1lbnRzWzBdKQogICAgICAgIDogZWRnZUFyZ3NUb0lkKHRoaXMuX2lzRGlyZWN0ZWQsIHYsIHcsIG5hbWUpKTsKICAgICAgcmV0dXJuIGxvZGFzaF8xLmhhcyh0aGlzLl9lZGdlTGFiZWxzLCBlKTsKICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLnJlbW92ZUVkZ2UgPSBmdW5jdGlvbih2LCB3LCBuYW1lKSB7CiAgICAgIHZhciBlID0gKGFyZ3VtZW50cy5sZW5ndGggPT09IDEKICAgICAgICA/IGVkZ2VPYmpUb0lkKHRoaXMuX2lzRGlyZWN0ZWQsIGFyZ3VtZW50c1swXSkKICAgICAgICA6IGVkZ2VBcmdzVG9JZCh0aGlzLl9pc0RpcmVjdGVkLCB2LCB3LCBuYW1lKSk7CiAgICAgIHZhciBlZGdlID0gdGhpcy5fZWRnZU9ianNbZV07CiAgICAgIGlmIChlZGdlKSB7CiAgICAgICAgdiA9IGVkZ2UudjsKICAgICAgICB3ID0gZWRnZS53OwogICAgICAgIGRlbGV0ZSB0aGlzLl9lZGdlTGFiZWxzW2VdOwogICAgICAgIGRlbGV0ZSB0aGlzLl9lZGdlT2Jqc1tlXTsKICAgICAgICBkZWNyZW1lbnRPclJlbW92ZUVudHJ5KHRoaXMuX3ByZWRzW3ddLCB2KTsKICAgICAgICBkZWNyZW1lbnRPclJlbW92ZUVudHJ5KHRoaXMuX3N1Y3Nbdl0sIHcpOwogICAgICAgIGRlbGV0ZSB0aGlzLl9pblt3XVtlXTsKICAgICAgICBkZWxldGUgdGhpcy5fb3V0W3ZdW2VdOwogICAgICAgIHRoaXMuX2VkZ2VDb3VudC0tOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzOwogICAgfTsKCiAgICBHcmFwaC5wcm90b3R5cGUuaW5FZGdlcyA9IGZ1bmN0aW9uKHYsIHUpIHsKICAgICAgdmFyIGluViA9IHRoaXMuX2luW3ZdOwogICAgICBpZiAoaW5WKSB7CiAgICAgICAgdmFyIGVkZ2VzID0gbG9kYXNoXzEudmFsdWVzKGluVik7CiAgICAgICAgaWYgKCF1KSB7CiAgICAgICAgICByZXR1cm4gZWRnZXM7CiAgICAgICAgfQogICAgICAgIHJldHVybiBsb2Rhc2hfMS5maWx0ZXIoZWRnZXMsIGZ1bmN0aW9uKGVkZ2UpIHsgcmV0dXJuIGVkZ2UudiA9PT0gdTsgfSk7CiAgICAgIH0KICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLm91dEVkZ2VzID0gZnVuY3Rpb24odiwgdykgewogICAgICB2YXIgb3V0ViA9IHRoaXMuX291dFt2XTsKICAgICAgaWYgKG91dFYpIHsKICAgICAgICB2YXIgZWRnZXMgPSBsb2Rhc2hfMS52YWx1ZXMob3V0Vik7CiAgICAgICAgaWYgKCF3KSB7CiAgICAgICAgICByZXR1cm4gZWRnZXM7CiAgICAgICAgfQogICAgICAgIHJldHVybiBsb2Rhc2hfMS5maWx0ZXIoZWRnZXMsIGZ1bmN0aW9uKGVkZ2UpIHsgcmV0dXJuIGVkZ2UudyA9PT0gdzsgfSk7CiAgICAgIH0KICAgIH07CgogICAgR3JhcGgucHJvdG90eXBlLm5vZGVFZGdlcyA9IGZ1bmN0aW9uKHYsIHcpIHsKICAgICAgdmFyIGluRWRnZXMgPSB0aGlzLmluRWRnZXModiwgdyk7CiAgICAgIGlmIChpbkVkZ2VzKSB7CiAgICAgICAgcmV0dXJuIGluRWRnZXMuY29uY2F0KHRoaXMub3V0RWRnZXModiwgdykpOwogICAgICB9CiAgICB9OwoKICAgIGZ1bmN0aW9uIGluY3JlbWVudE9ySW5pdEVudHJ5KG1hcCwgaykgewogICAgICBpZiAobWFwW2tdKSB7CiAgICAgICAgbWFwW2tdKys7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgbWFwW2tdID0gMTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGRlY3JlbWVudE9yUmVtb3ZlRW50cnkobWFwLCBrKSB7CiAgICAgIGlmICghLS1tYXBba10pIHsgZGVsZXRlIG1hcFtrXTsgfQogICAgfQoKICAgIGZ1bmN0aW9uIGVkZ2VBcmdzVG9JZChpc0RpcmVjdGVkLCB2Xywgd18sIG5hbWUpIHsKICAgICAgdmFyIHYgPSAiIiArIHZfOwogICAgICB2YXIgdyA9ICIiICsgd187CiAgICAgIGlmICghaXNEaXJlY3RlZCAmJiB2ID4gdykgewogICAgICAgIHZhciB0bXAgPSB2OwogICAgICAgIHYgPSB3OwogICAgICAgIHcgPSB0bXA7CiAgICAgIH0KICAgICAgcmV0dXJuIHYgKyBFREdFX0tFWV9ERUxJTSArIHcgKyBFREdFX0tFWV9ERUxJTSArCiAgICAgICAgICAgICAgICAgKGxvZGFzaF8xLmlzVW5kZWZpbmVkKG5hbWUpID8gREVGQVVMVF9FREdFX05BTUUgOiBuYW1lKTsKICAgIH0KCiAgICBmdW5jdGlvbiBlZGdlQXJnc1RvT2JqKGlzRGlyZWN0ZWQsIHZfLCB3XywgbmFtZSkgewogICAgICB2YXIgdiA9ICIiICsgdl87CiAgICAgIHZhciB3ID0gIiIgKyB3XzsKICAgICAgaWYgKCFpc0RpcmVjdGVkICYmIHYgPiB3KSB7CiAgICAgICAgdmFyIHRtcCA9IHY7CiAgICAgICAgdiA9IHc7CiAgICAgICAgdyA9IHRtcDsKICAgICAgfQogICAgICB2YXIgZWRnZU9iaiA9ICB7IHY6IHYsIHc6IHcgfTsKICAgICAgaWYgKG5hbWUpIHsKICAgICAgICBlZGdlT2JqLm5hbWUgPSBuYW1lOwogICAgICB9CiAgICAgIHJldHVybiBlZGdlT2JqOwogICAgfQoKICAgIGZ1bmN0aW9uIGVkZ2VPYmpUb0lkKGlzRGlyZWN0ZWQsIGVkZ2VPYmopIHsKICAgICAgcmV0dXJuIGVkZ2VBcmdzVG9JZChpc0RpcmVjdGVkLCBlZGdlT2JqLnYsIGVkZ2VPYmoudywgZWRnZU9iai5uYW1lKTsKICAgIH0KCiAgICB2YXIgdmVyc2lvbiQ0ID0gJzIuMS44JzsKCiAgICAvLyBJbmNsdWRlcyBvbmx5IHRoZSAiY29yZSIgb2YgZ3JhcGhsaWIKICAgIHZhciBsaWIgPSB7CiAgICAgIEdyYXBoOiBncmFwaCwKICAgICAgdmVyc2lvbjogdmVyc2lvbiQ0CiAgICB9OwoKICAgIHZhciBqc29uJDIgPSB7CiAgICAgIHdyaXRlOiB3cml0ZSwKICAgICAgcmVhZDogcmVhZAogICAgfTsKCiAgICBmdW5jdGlvbiB3cml0ZShnKSB7CiAgICAgIHZhciBqc29uID0gewogICAgICAgIG9wdGlvbnM6IHsKICAgICAgICAgIGRpcmVjdGVkOiBnLmlzRGlyZWN0ZWQoKSwKICAgICAgICAgIG11bHRpZ3JhcGg6IGcuaXNNdWx0aWdyYXBoKCksCiAgICAgICAgICBjb21wb3VuZDogZy5pc0NvbXBvdW5kKCkKICAgICAgICB9LAogICAgICAgIG5vZGVzOiB3cml0ZU5vZGVzKGcpLAogICAgICAgIGVkZ2VzOiB3cml0ZUVkZ2VzKGcpCiAgICAgIH07CiAgICAgIGlmICghbG9kYXNoXzEuaXNVbmRlZmluZWQoZy5ncmFwaCgpKSkgewogICAgICAgIGpzb24udmFsdWUgPSBsb2Rhc2hfMS5jbG9uZShnLmdyYXBoKCkpOwogICAgICB9CiAgICAgIHJldHVybiBqc29uOwogICAgfQoKICAgIGZ1bmN0aW9uIHdyaXRlTm9kZXMoZykgewogICAgICByZXR1cm4gbG9kYXNoXzEubWFwKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBub2RlVmFsdWUgPSBnLm5vZGUodik7CiAgICAgICAgdmFyIHBhcmVudCA9IGcucGFyZW50KHYpOwogICAgICAgIHZhciBub2RlID0geyB2OiB2IH07CiAgICAgICAgaWYgKCFsb2Rhc2hfMS5pc1VuZGVmaW5lZChub2RlVmFsdWUpKSB7CiAgICAgICAgICBub2RlLnZhbHVlID0gbm9kZVZhbHVlOwogICAgICAgIH0KICAgICAgICBpZiAoIWxvZGFzaF8xLmlzVW5kZWZpbmVkKHBhcmVudCkpIHsKICAgICAgICAgIG5vZGUucGFyZW50ID0gcGFyZW50OwogICAgICAgIH0KICAgICAgICByZXR1cm4gbm9kZTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gd3JpdGVFZGdlcyhnKSB7CiAgICAgIHJldHVybiBsb2Rhc2hfMS5tYXAoZy5lZGdlcygpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIGVkZ2VWYWx1ZSA9IGcuZWRnZShlKTsKICAgICAgICB2YXIgZWRnZSA9IHsgdjogZS52LCB3OiBlLncgfTsKICAgICAgICBpZiAoIWxvZGFzaF8xLmlzVW5kZWZpbmVkKGUubmFtZSkpIHsKICAgICAgICAgIGVkZ2UubmFtZSA9IGUubmFtZTsKICAgICAgICB9CiAgICAgICAgaWYgKCFsb2Rhc2hfMS5pc1VuZGVmaW5lZChlZGdlVmFsdWUpKSB7CiAgICAgICAgICBlZGdlLnZhbHVlID0gZWRnZVZhbHVlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZWRnZTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVhZChqc29uKSB7CiAgICAgIHZhciBnID0gbmV3IGdyYXBoKGpzb24ub3B0aW9ucykuc2V0R3JhcGgoanNvbi52YWx1ZSk7CiAgICAgIGxvZGFzaF8xLmVhY2goanNvbi5ub2RlcywgZnVuY3Rpb24oZW50cnkpIHsKICAgICAgICBnLnNldE5vZGUoZW50cnkudiwgZW50cnkudmFsdWUpOwogICAgICAgIGlmIChlbnRyeS5wYXJlbnQpIHsKICAgICAgICAgIGcuc2V0UGFyZW50KGVudHJ5LnYsIGVudHJ5LnBhcmVudCk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgbG9kYXNoXzEuZWFjaChqc29uLmVkZ2VzLCBmdW5jdGlvbihlbnRyeSkgewogICAgICAgIGcuc2V0RWRnZSh7IHY6IGVudHJ5LnYsIHc6IGVudHJ5LncsIG5hbWU6IGVudHJ5Lm5hbWUgfSwgZW50cnkudmFsdWUpOwogICAgICB9KTsKICAgICAgcmV0dXJuIGc7CiAgICB9CgogICAgdmFyIGNvbXBvbmVudHNfMSA9IGNvbXBvbmVudHMkMTsKCiAgICBmdW5jdGlvbiBjb21wb25lbnRzJDEoZykgewogICAgICB2YXIgdmlzaXRlZCA9IHt9OwogICAgICB2YXIgY21wdHMgPSBbXTsKICAgICAgdmFyIGNtcHQ7CgogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIGlmIChsb2Rhc2hfMS5oYXModmlzaXRlZCwgdikpIHJldHVybjsKICAgICAgICB2aXNpdGVkW3ZdID0gdHJ1ZTsKICAgICAgICBjbXB0LnB1c2godik7CiAgICAgICAgbG9kYXNoXzEuZWFjaChnLnN1Y2Nlc3NvcnModiksIGRmcyk7CiAgICAgICAgbG9kYXNoXzEuZWFjaChnLnByZWRlY2Vzc29ycyh2KSwgZGZzKTsKICAgICAgfQoKICAgICAgbG9kYXNoXzEuZWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICBjbXB0ID0gW107CiAgICAgICAgZGZzKHYpOwogICAgICAgIGlmIChjbXB0Lmxlbmd0aCkgewogICAgICAgICAgY21wdHMucHVzaChjbXB0KTsKICAgICAgICB9CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIGNtcHRzOwogICAgfQoKICAgIHZhciBwcmlvcml0eVF1ZXVlID0gUHJpb3JpdHlRdWV1ZTsKCiAgICAvKioKICAgICAqIEEgbWluLXByaW9yaXR5IHF1ZXVlIGRhdGEgc3RydWN0dXJlLiBUaGlzIGFsZ29yaXRobSBpcyBkZXJpdmVkIGZyb20gQ29ybWVuLAogICAgICogZXQgYWwuLCAiSW50cm9kdWN0aW9uIHRvIEFsZ29yaXRobXMiLiBUaGUgYmFzaWMgaWRlYSBvZiBhIG1pbi1wcmlvcml0eQogICAgICogcXVldWUgaXMgdGhhdCB5b3UgY2FuIGVmZmljaWVudGx5IChpbiBPKDEpIHRpbWUpIGdldCB0aGUgc21hbGxlc3Qga2V5IGluCiAgICAgKiB0aGUgcXVldWUuIEFkZGluZyBhbmQgcmVtb3ZpbmcgZWxlbWVudHMgdGFrZXMgTyhsb2cgbikgdGltZS4gQSBrZXkgY2FuCiAgICAgKiBoYXZlIGl0cyBwcmlvcml0eSBkZWNyZWFzZWQgaW4gTyhsb2cgbikgdGltZS4KICAgICAqLwogICAgZnVuY3Rpb24gUHJpb3JpdHlRdWV1ZSgpIHsKICAgICAgdGhpcy5fYXJyID0gW107CiAgICAgIHRoaXMuX2tleUluZGljZXMgPSB7fTsKICAgIH0KCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIG51bWJlciBvZiBlbGVtZW50cyBpbiB0aGUgcXVldWUuIFRha2VzIGBPKDEpYCB0aW1lLgogICAgICovCiAgICBQcmlvcml0eVF1ZXVlLnByb3RvdHlwZS5zaXplID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLl9hcnIubGVuZ3RoOwogICAgfTsKCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGtleXMgdGhhdCBhcmUgaW4gdGhlIHF1ZXVlLiBUYWtlcyBgTyhuKWAgdGltZS4KICAgICAqLwogICAgUHJpb3JpdHlRdWV1ZS5wcm90b3R5cGUua2V5cyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5fYXJyLm1hcChmdW5jdGlvbih4KSB7IHJldHVybiB4LmtleTsgfSk7CiAgICB9OwoKICAgIC8qKgogICAgICogUmV0dXJucyBgdHJ1ZWAgaWYgKiprZXkqKiBpcyBpbiB0aGUgcXVldWUgYW5kIGBmYWxzZWAgaWYgbm90LgogICAgICovCiAgICBQcmlvcml0eVF1ZXVlLnByb3RvdHlwZS5oYXMgPSBmdW5jdGlvbihrZXkpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xLmhhcyh0aGlzLl9rZXlJbmRpY2VzLCBrZXkpOwogICAgfTsKCiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIHByaW9yaXR5IGZvciAqKmtleSoqLiBJZiAqKmtleSoqIGlzIG5vdCBwcmVzZW50IGluIHRoZSBxdWV1ZQogICAgICogdGhlbiB0aGlzIGZ1bmN0aW9uIHJldHVybnMgYHVuZGVmaW5lZGAuIFRha2VzIGBPKDEpYCB0aW1lLgogICAgICoKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBrZXkKICAgICAqLwogICAgUHJpb3JpdHlRdWV1ZS5wcm90b3R5cGUucHJpb3JpdHkgPSBmdW5jdGlvbihrZXkpIHsKICAgICAgdmFyIGluZGV4ID0gdGhpcy5fa2V5SW5kaWNlc1trZXldOwogICAgICBpZiAoaW5kZXggIT09IHVuZGVmaW5lZCkgewogICAgICAgIHJldHVybiB0aGlzLl9hcnJbaW5kZXhdLnByaW9yaXR5OwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgICogUmV0dXJucyB0aGUga2V5IGZvciB0aGUgbWluaW11bSBlbGVtZW50IGluIHRoaXMgcXVldWUuIElmIHRoZSBxdWV1ZSBpcwogICAgICogZW1wdHkgdGhpcyBmdW5jdGlvbiB0aHJvd3MgYW4gRXJyb3IuIFRha2VzIGBPKDEpYCB0aW1lLgogICAgICovCiAgICBQcmlvcml0eVF1ZXVlLnByb3RvdHlwZS5taW4gPSBmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuc2l6ZSgpID09PSAwKSB7CiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJRdWV1ZSB1bmRlcmZsb3ciKTsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5fYXJyWzBdLmtleTsKICAgIH07CgogICAgLyoqCiAgICAgKiBJbnNlcnRzIGEgbmV3IGtleSBpbnRvIHRoZSBwcmlvcml0eSBxdWV1ZS4gSWYgdGhlIGtleSBhbHJlYWR5IGV4aXN0cyBpbgogICAgICogdGhlIHF1ZXVlIHRoaXMgZnVuY3Rpb24gcmV0dXJucyBgZmFsc2VgOyBvdGhlcndpc2UgaXQgd2lsbCByZXR1cm4gYHRydWVgLgogICAgICogVGFrZXMgYE8obilgIHRpbWUuCiAgICAgKgogICAgICogQHBhcmFtIHtPYmplY3R9IGtleSB0aGUga2V5IHRvIGFkZAogICAgICogQHBhcmFtIHtOdW1iZXJ9IHByaW9yaXR5IHRoZSBpbml0aWFsIHByaW9yaXR5IGZvciB0aGUga2V5CiAgICAgKi8KICAgIFByaW9yaXR5UXVldWUucHJvdG90eXBlLmFkZCA9IGZ1bmN0aW9uKGtleSwgcHJpb3JpdHkpIHsKICAgICAgdmFyIGtleUluZGljZXMgPSB0aGlzLl9rZXlJbmRpY2VzOwogICAgICBrZXkgPSBTdHJpbmcoa2V5KTsKICAgICAgaWYgKCFsb2Rhc2hfMS5oYXMoa2V5SW5kaWNlcywga2V5KSkgewogICAgICAgIHZhciBhcnIgPSB0aGlzLl9hcnI7CiAgICAgICAgdmFyIGluZGV4ID0gYXJyLmxlbmd0aDsKICAgICAgICBrZXlJbmRpY2VzW2tleV0gPSBpbmRleDsKICAgICAgICBhcnIucHVzaCh7a2V5OiBrZXksIHByaW9yaXR5OiBwcmlvcml0eX0pOwogICAgICAgIHRoaXMuX2RlY3JlYXNlKGluZGV4KTsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQogICAgICByZXR1cm4gZmFsc2U7CiAgICB9OwoKICAgIC8qKgogICAgICogUmVtb3ZlcyBhbmQgcmV0dXJucyB0aGUgc21hbGxlc3Qga2V5IGluIHRoZSBxdWV1ZS4gVGFrZXMgYE8obG9nIG4pYCB0aW1lLgogICAgICovCiAgICBQcmlvcml0eVF1ZXVlLnByb3RvdHlwZS5yZW1vdmVNaW4gPSBmdW5jdGlvbigpIHsKICAgICAgdGhpcy5fc3dhcCgwLCB0aGlzLl9hcnIubGVuZ3RoIC0gMSk7CiAgICAgIHZhciBtaW4gPSB0aGlzLl9hcnIucG9wKCk7CiAgICAgIGRlbGV0ZSB0aGlzLl9rZXlJbmRpY2VzW21pbi5rZXldOwogICAgICB0aGlzLl9oZWFwaWZ5KDApOwogICAgICByZXR1cm4gbWluLmtleTsKICAgIH07CgogICAgLyoqCiAgICAgKiBEZWNyZWFzZXMgdGhlIHByaW9yaXR5IGZvciAqKmtleSoqIHRvICoqcHJpb3JpdHkqKi4gSWYgdGhlIG5ldyBwcmlvcml0eSBpcwogICAgICogZ3JlYXRlciB0aGFuIHRoZSBwcmV2aW91cyBwcmlvcml0eSwgdGhpcyBmdW5jdGlvbiB3aWxsIHRocm93IGFuIEVycm9yLgogICAgICoKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBrZXkgdGhlIGtleSBmb3Igd2hpY2ggdG8gcmFpc2UgcHJpb3JpdHkKICAgICAqIEBwYXJhbSB7TnVtYmVyfSBwcmlvcml0eSB0aGUgbmV3IHByaW9yaXR5IGZvciB0aGUga2V5CiAgICAgKi8KICAgIFByaW9yaXR5UXVldWUucHJvdG90eXBlLmRlY3JlYXNlID0gZnVuY3Rpb24oa2V5LCBwcmlvcml0eSkgewogICAgICB2YXIgaW5kZXggPSB0aGlzLl9rZXlJbmRpY2VzW2tleV07CiAgICAgIGlmIChwcmlvcml0eSA+IHRoaXMuX2FycltpbmRleF0ucHJpb3JpdHkpIHsKICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIk5ldyBwcmlvcml0eSBpcyBncmVhdGVyIHRoYW4gY3VycmVudCBwcmlvcml0eS4gIiArCiAgICAgICAgICAgICJLZXk6ICIgKyBrZXkgKyAiIE9sZDogIiArIHRoaXMuX2FycltpbmRleF0ucHJpb3JpdHkgKyAiIE5ldzogIiArIHByaW9yaXR5KTsKICAgICAgfQogICAgICB0aGlzLl9hcnJbaW5kZXhdLnByaW9yaXR5ID0gcHJpb3JpdHk7CiAgICAgIHRoaXMuX2RlY3JlYXNlKGluZGV4KTsKICAgIH07CgogICAgUHJpb3JpdHlRdWV1ZS5wcm90b3R5cGUuX2hlYXBpZnkgPSBmdW5jdGlvbihpKSB7CiAgICAgIHZhciBhcnIgPSB0aGlzLl9hcnI7CiAgICAgIHZhciBsID0gMiAqIGk7CiAgICAgIHZhciByID0gbCArIDE7CiAgICAgIHZhciBsYXJnZXN0ID0gaTsKICAgICAgaWYgKGwgPCBhcnIubGVuZ3RoKSB7CiAgICAgICAgbGFyZ2VzdCA9IGFycltsXS5wcmlvcml0eSA8IGFycltsYXJnZXN0XS5wcmlvcml0eSA/IGwgOiBsYXJnZXN0OwogICAgICAgIGlmIChyIDwgYXJyLmxlbmd0aCkgewogICAgICAgICAgbGFyZ2VzdCA9IGFycltyXS5wcmlvcml0eSA8IGFycltsYXJnZXN0XS5wcmlvcml0eSA/IHIgOiBsYXJnZXN0OwogICAgICAgIH0KICAgICAgICBpZiAobGFyZ2VzdCAhPT0gaSkgewogICAgICAgICAgdGhpcy5fc3dhcChpLCBsYXJnZXN0KTsKICAgICAgICAgIHRoaXMuX2hlYXBpZnkobGFyZ2VzdCk7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIFByaW9yaXR5UXVldWUucHJvdG90eXBlLl9kZWNyZWFzZSA9IGZ1bmN0aW9uKGluZGV4KSB7CiAgICAgIHZhciBhcnIgPSB0aGlzLl9hcnI7CiAgICAgIHZhciBwcmlvcml0eSA9IGFycltpbmRleF0ucHJpb3JpdHk7CiAgICAgIHZhciBwYXJlbnQ7CiAgICAgIHdoaWxlIChpbmRleCAhPT0gMCkgewogICAgICAgIHBhcmVudCA9IGluZGV4ID4+IDE7CiAgICAgICAgaWYgKGFycltwYXJlbnRdLnByaW9yaXR5IDwgcHJpb3JpdHkpIHsKICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgICB0aGlzLl9zd2FwKGluZGV4LCBwYXJlbnQpOwogICAgICAgIGluZGV4ID0gcGFyZW50OwogICAgICB9CiAgICB9OwoKICAgIFByaW9yaXR5UXVldWUucHJvdG90eXBlLl9zd2FwID0gZnVuY3Rpb24oaSwgaikgewogICAgICB2YXIgYXJyID0gdGhpcy5fYXJyOwogICAgICB2YXIga2V5SW5kaWNlcyA9IHRoaXMuX2tleUluZGljZXM7CiAgICAgIHZhciBvcmlnQXJySSA9IGFycltpXTsKICAgICAgdmFyIG9yaWdBcnJKID0gYXJyW2pdOwogICAgICBhcnJbaV0gPSBvcmlnQXJySjsKICAgICAgYXJyW2pdID0gb3JpZ0Fyckk7CiAgICAgIGtleUluZGljZXNbb3JpZ0Fyckoua2V5XSA9IGk7CiAgICAgIGtleUluZGljZXNbb3JpZ0Fyckkua2V5XSA9IGo7CiAgICB9OwoKICAgIHZhciBkaWprc3RyYV8xID0gZGlqa3N0cmE7CgogICAgdmFyIERFRkFVTFRfV0VJR0hUX0ZVTkMgPSBsb2Rhc2hfMS5jb25zdGFudCgxKTsKCiAgICBmdW5jdGlvbiBkaWprc3RyYShnLCBzb3VyY2UsIHdlaWdodEZuLCBlZGdlRm4pIHsKICAgICAgcmV0dXJuIHJ1bkRpamtzdHJhKGcsIFN0cmluZyhzb3VyY2UpLAogICAgICAgIHdlaWdodEZuIHx8IERFRkFVTFRfV0VJR0hUX0ZVTkMsCiAgICAgICAgZWRnZUZuIHx8IGZ1bmN0aW9uKHYpIHsgcmV0dXJuIGcub3V0RWRnZXModik7IH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHJ1bkRpamtzdHJhKGcsIHNvdXJjZSwgd2VpZ2h0Rm4sIGVkZ2VGbikgewogICAgICB2YXIgcmVzdWx0cyA9IHt9OwogICAgICB2YXIgcHEgPSBuZXcgcHJpb3JpdHlRdWV1ZSgpOwogICAgICB2YXIgdiwgdkVudHJ5OwoKICAgICAgdmFyIHVwZGF0ZU5laWdoYm9ycyA9IGZ1bmN0aW9uKGVkZ2UpIHsKICAgICAgICB2YXIgdyA9IGVkZ2UudiAhPT0gdiA/IGVkZ2UudiA6IGVkZ2UudzsKICAgICAgICB2YXIgd0VudHJ5ID0gcmVzdWx0c1t3XTsKICAgICAgICB2YXIgd2VpZ2h0ID0gd2VpZ2h0Rm4oZWRnZSk7CiAgICAgICAgdmFyIGRpc3RhbmNlID0gdkVudHJ5LmRpc3RhbmNlICsgd2VpZ2h0OwoKICAgICAgICBpZiAod2VpZ2h0IDwgMCkgewogICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJkaWprc3RyYSBkb2VzIG5vdCBhbGxvdyBuZWdhdGl2ZSBlZGdlIHdlaWdodHMuICIgKwogICAgICAgICAgICAgICAgICAgICAgICAgICJCYWQgZWRnZTogIiArIGVkZ2UgKyAiIFdlaWdodDogIiArIHdlaWdodCk7CiAgICAgICAgfQoKICAgICAgICBpZiAoZGlzdGFuY2UgPCB3RW50cnkuZGlzdGFuY2UpIHsKICAgICAgICAgIHdFbnRyeS5kaXN0YW5jZSA9IGRpc3RhbmNlOwogICAgICAgICAgd0VudHJ5LnByZWRlY2Vzc29yID0gdjsKICAgICAgICAgIHBxLmRlY3JlYXNlKHcsIGRpc3RhbmNlKTsKICAgICAgICB9CiAgICAgIH07CgogICAgICBnLm5vZGVzKCkuZm9yRWFjaChmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIGRpc3RhbmNlID0gdiA9PT0gc291cmNlID8gMCA6IE51bWJlci5QT1NJVElWRV9JTkZJTklUWTsKICAgICAgICByZXN1bHRzW3ZdID0geyBkaXN0YW5jZTogZGlzdGFuY2UgfTsKICAgICAgICBwcS5hZGQodiwgZGlzdGFuY2UpOwogICAgICB9KTsKCiAgICAgIHdoaWxlIChwcS5zaXplKCkgPiAwKSB7CiAgICAgICAgdiA9IHBxLnJlbW92ZU1pbigpOwogICAgICAgIHZFbnRyeSA9IHJlc3VsdHNbdl07CiAgICAgICAgaWYgKHZFbnRyeS5kaXN0YW5jZSA9PT0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZKSB7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CgogICAgICAgIGVkZ2VGbih2KS5mb3JFYWNoKHVwZGF0ZU5laWdoYm9ycyk7CiAgICAgIH0KCiAgICAgIHJldHVybiByZXN1bHRzOwogICAgfQoKICAgIHZhciBkaWprc3RyYUFsbF8xID0gZGlqa3N0cmFBbGw7CgogICAgZnVuY3Rpb24gZGlqa3N0cmFBbGwoZywgd2VpZ2h0RnVuYywgZWRnZUZ1bmMpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xLnRyYW5zZm9ybShnLm5vZGVzKCksIGZ1bmN0aW9uKGFjYywgdikgewogICAgICAgIGFjY1t2XSA9IGRpamtzdHJhXzEoZywgdiwgd2VpZ2h0RnVuYywgZWRnZUZ1bmMpOwogICAgICB9LCB7fSk7CiAgICB9CgogICAgdmFyIHRhcmphbl8xID0gdGFyamFuOwoKICAgIGZ1bmN0aW9uIHRhcmphbihnKSB7CiAgICAgIHZhciBpbmRleCA9IDA7CiAgICAgIHZhciBzdGFjayA9IFtdOwogICAgICB2YXIgdmlzaXRlZCA9IHt9OyAvLyBub2RlIGlkIC0+IHsgb25TdGFjaywgbG93bGluaywgaW5kZXggfQogICAgICB2YXIgcmVzdWx0cyA9IFtdOwoKICAgICAgZnVuY3Rpb24gZGZzKHYpIHsKICAgICAgICB2YXIgZW50cnkgPSB2aXNpdGVkW3ZdID0gewogICAgICAgICAgb25TdGFjazogdHJ1ZSwKICAgICAgICAgIGxvd2xpbms6IGluZGV4LAogICAgICAgICAgaW5kZXg6IGluZGV4KysKICAgICAgICB9OwogICAgICAgIHN0YWNrLnB1c2godik7CgogICAgICAgIGcuc3VjY2Vzc29ycyh2KS5mb3JFYWNoKGZ1bmN0aW9uKHcpIHsKICAgICAgICAgIGlmICghbG9kYXNoXzEuaGFzKHZpc2l0ZWQsIHcpKSB7CiAgICAgICAgICAgIGRmcyh3KTsKICAgICAgICAgICAgZW50cnkubG93bGluayA9IE1hdGgubWluKGVudHJ5Lmxvd2xpbmssIHZpc2l0ZWRbd10ubG93bGluayk7CiAgICAgICAgICB9IGVsc2UgaWYgKHZpc2l0ZWRbd10ub25TdGFjaykgewogICAgICAgICAgICBlbnRyeS5sb3dsaW5rID0gTWF0aC5taW4oZW50cnkubG93bGluaywgdmlzaXRlZFt3XS5pbmRleCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIGlmIChlbnRyeS5sb3dsaW5rID09PSBlbnRyeS5pbmRleCkgewogICAgICAgICAgdmFyIGNtcHQgPSBbXTsKICAgICAgICAgIHZhciB3OwogICAgICAgICAgZG8gewogICAgICAgICAgICB3ID0gc3RhY2sucG9wKCk7CiAgICAgICAgICAgIHZpc2l0ZWRbd10ub25TdGFjayA9IGZhbHNlOwogICAgICAgICAgICBjbXB0LnB1c2godyk7CiAgICAgICAgICB9IHdoaWxlICh2ICE9PSB3KTsKICAgICAgICAgIHJlc3VsdHMucHVzaChjbXB0KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGcubm9kZXMoKS5mb3JFYWNoKGZ1bmN0aW9uKHYpIHsKICAgICAgICBpZiAoIWxvZGFzaF8xLmhhcyh2aXNpdGVkLCB2KSkgewogICAgICAgICAgZGZzKHYpOwogICAgICAgIH0KICAgICAgfSk7CgogICAgICByZXR1cm4gcmVzdWx0czsKICAgIH0KCiAgICB2YXIgZmluZEN5Y2xlc18xID0gZmluZEN5Y2xlczsKCiAgICBmdW5jdGlvbiBmaW5kQ3ljbGVzKGcpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xLmZpbHRlcih0YXJqYW5fMShnKSwgZnVuY3Rpb24oY21wdCkgewogICAgICAgIHJldHVybiBjbXB0Lmxlbmd0aCA+IDEgfHwgKGNtcHQubGVuZ3RoID09PSAxICYmIGcuaGFzRWRnZShjbXB0WzBdLCBjbXB0WzBdKSk7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBmbG95ZFdhcnNoYWxsXzEgPSBmbG95ZFdhcnNoYWxsOwoKICAgIHZhciBERUZBVUxUX1dFSUdIVF9GVU5DJDEgPSBsb2Rhc2hfMS5jb25zdGFudCgxKTsKCiAgICBmdW5jdGlvbiBmbG95ZFdhcnNoYWxsKGcsIHdlaWdodEZuLCBlZGdlRm4pIHsKICAgICAgcmV0dXJuIHJ1bkZsb3lkV2Fyc2hhbGwoZywKICAgICAgICB3ZWlnaHRGbiB8fCBERUZBVUxUX1dFSUdIVF9GVU5DJDEsCiAgICAgICAgZWRnZUZuIHx8IGZ1bmN0aW9uKHYpIHsgcmV0dXJuIGcub3V0RWRnZXModik7IH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHJ1bkZsb3lkV2Fyc2hhbGwoZywgd2VpZ2h0Rm4sIGVkZ2VGbikgewogICAgICB2YXIgcmVzdWx0cyA9IHt9OwogICAgICB2YXIgbm9kZXMgPSBnLm5vZGVzKCk7CgogICAgICBub2Rlcy5mb3JFYWNoKGZ1bmN0aW9uKHYpIHsKICAgICAgICByZXN1bHRzW3ZdID0ge307CiAgICAgICAgcmVzdWx0c1t2XVt2XSA9IHsgZGlzdGFuY2U6IDAgfTsKICAgICAgICBub2Rlcy5mb3JFYWNoKGZ1bmN0aW9uKHcpIHsKICAgICAgICAgIGlmICh2ICE9PSB3KSB7CiAgICAgICAgICAgIHJlc3VsdHNbdl1bd10gPSB7IGRpc3RhbmNlOiBOdW1iZXIuUE9TSVRJVkVfSU5GSU5JVFkgfTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICBlZGdlRm4odikuZm9yRWFjaChmdW5jdGlvbihlZGdlKSB7CiAgICAgICAgICB2YXIgdyA9IGVkZ2UudiA9PT0gdiA/IGVkZ2UudyA6IGVkZ2UudjsKICAgICAgICAgIHZhciBkID0gd2VpZ2h0Rm4oZWRnZSk7CiAgICAgICAgICByZXN1bHRzW3ZdW3ddID0geyBkaXN0YW5jZTogZCwgcHJlZGVjZXNzb3I6IHYgfTsKICAgICAgICB9KTsKICAgICAgfSk7CgogICAgICBub2Rlcy5mb3JFYWNoKGZ1bmN0aW9uKGspIHsKICAgICAgICB2YXIgcm93SyA9IHJlc3VsdHNba107CiAgICAgICAgbm9kZXMuZm9yRWFjaChmdW5jdGlvbihpKSB7CiAgICAgICAgICB2YXIgcm93SSA9IHJlc3VsdHNbaV07CiAgICAgICAgICBub2Rlcy5mb3JFYWNoKGZ1bmN0aW9uKGopIHsKICAgICAgICAgICAgdmFyIGlrID0gcm93SVtrXTsKICAgICAgICAgICAgdmFyIGtqID0gcm93S1tqXTsKICAgICAgICAgICAgdmFyIGlqID0gcm93SVtqXTsKICAgICAgICAgICAgdmFyIGFsdERpc3RhbmNlID0gaWsuZGlzdGFuY2UgKyBrai5kaXN0YW5jZTsKICAgICAgICAgICAgaWYgKGFsdERpc3RhbmNlIDwgaWouZGlzdGFuY2UpIHsKICAgICAgICAgICAgICBpai5kaXN0YW5jZSA9IGFsdERpc3RhbmNlOwogICAgICAgICAgICAgIGlqLnByZWRlY2Vzc29yID0ga2oucHJlZGVjZXNzb3I7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgICB9KTsKCiAgICAgIHJldHVybiByZXN1bHRzOwogICAgfQoKICAgIHZhciB0b3Bzb3J0XzEgPSB0b3Bzb3J0OwogICAgdG9wc29ydC5DeWNsZUV4Y2VwdGlvbiA9IEN5Y2xlRXhjZXB0aW9uOwoKICAgIGZ1bmN0aW9uIHRvcHNvcnQoZykgewogICAgICB2YXIgdmlzaXRlZCA9IHt9OwogICAgICB2YXIgc3RhY2sgPSB7fTsKICAgICAgdmFyIHJlc3VsdHMgPSBbXTsKCiAgICAgIGZ1bmN0aW9uIHZpc2l0KG5vZGUpIHsKICAgICAgICBpZiAobG9kYXNoXzEuaGFzKHN0YWNrLCBub2RlKSkgewogICAgICAgICAgdGhyb3cgbmV3IEN5Y2xlRXhjZXB0aW9uKCk7CiAgICAgICAgfQoKICAgICAgICBpZiAoIWxvZGFzaF8xLmhhcyh2aXNpdGVkLCBub2RlKSkgewogICAgICAgICAgc3RhY2tbbm9kZV0gPSB0cnVlOwogICAgICAgICAgdmlzaXRlZFtub2RlXSA9IHRydWU7CiAgICAgICAgICBsb2Rhc2hfMS5lYWNoKGcucHJlZGVjZXNzb3JzKG5vZGUpLCB2aXNpdCk7CiAgICAgICAgICBkZWxldGUgc3RhY2tbbm9kZV07CiAgICAgICAgICByZXN1bHRzLnB1c2gobm9kZSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBsb2Rhc2hfMS5lYWNoKGcuc2lua3MoKSwgdmlzaXQpOwoKICAgICAgaWYgKGxvZGFzaF8xLnNpemUodmlzaXRlZCkgIT09IGcubm9kZUNvdW50KCkpIHsKICAgICAgICB0aHJvdyBuZXcgQ3ljbGVFeGNlcHRpb24oKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHJlc3VsdHM7CiAgICB9CgogICAgZnVuY3Rpb24gQ3ljbGVFeGNlcHRpb24oKSB7fQogICAgQ3ljbGVFeGNlcHRpb24ucHJvdG90eXBlID0gbmV3IEVycm9yKCk7IC8vIG11c3QgYmUgYW4gaW5zdGFuY2Ugb2YgRXJyb3IgdG8gcGFzcyB0ZXN0aW5nCgogICAgdmFyIGlzQWN5Y2xpY18xID0gaXNBY3ljbGljOwoKICAgIGZ1bmN0aW9uIGlzQWN5Y2xpYyhnKSB7CiAgICAgIHRyeSB7CiAgICAgICAgdG9wc29ydF8xKGcpOwogICAgICB9IGNhdGNoIChlKSB7CiAgICAgICAgaWYgKGUgaW5zdGFuY2VvZiB0b3Bzb3J0XzEuQ3ljbGVFeGNlcHRpb24pIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgICAgdGhyb3cgZTsKICAgICAgfQogICAgICByZXR1cm4gdHJ1ZTsKICAgIH0KCiAgICB2YXIgZGZzXzEgPSBkZnM7CgogICAgLyoKICAgICAqIEEgaGVscGVyIHRoYXQgcHJlZm9ybXMgYSBwcmUtIG9yIHBvc3Qtb3JkZXIgdHJhdmVyc2FsIG9uIHRoZSBpbnB1dCBncmFwaAogICAgICogYW5kIHJldHVybnMgdGhlIG5vZGVzIGluIHRoZSBvcmRlciB0aGV5IHdlcmUgdmlzaXRlZC4gSWYgdGhlIGdyYXBoIGlzCiAgICAgKiB1bmRpcmVjdGVkIHRoZW4gdGhpcyBhbGdvcml0aG0gd2lsbCBuYXZpZ2F0ZSB1c2luZyBuZWlnaGJvcnMuIElmIHRoZSBncmFwaAogICAgICogaXMgZGlyZWN0ZWQgdGhlbiB0aGlzIGFsZ29yaXRobSB3aWxsIG5hdmlnYXRlIHVzaW5nIHN1Y2Nlc3NvcnMuCiAgICAgKgogICAgICogT3JkZXIgbXVzdCBiZSBvbmUgb2YgInByZSIgb3IgInBvc3QiLgogICAgICovCiAgICBmdW5jdGlvbiBkZnMoZywgdnMsIG9yZGVyKSB7CiAgICAgIGlmICghbG9kYXNoXzEuaXNBcnJheSh2cykpIHsKICAgICAgICB2cyA9IFt2c107CiAgICAgIH0KCiAgICAgIHZhciBuYXZpZ2F0aW9uID0gKGcuaXNEaXJlY3RlZCgpID8gZy5zdWNjZXNzb3JzIDogZy5uZWlnaGJvcnMpLmJpbmQoZyk7CgogICAgICB2YXIgYWNjID0gW107CiAgICAgIHZhciB2aXNpdGVkID0ge307CiAgICAgIGxvZGFzaF8xLmVhY2godnMsIGZ1bmN0aW9uKHYpIHsKICAgICAgICBpZiAoIWcuaGFzTm9kZSh2KSkgewogICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJHcmFwaCBkb2VzIG5vdCBoYXZlIG5vZGU6ICIgKyB2KTsKICAgICAgICB9CgogICAgICAgIGRvRGZzKGcsIHYsIG9yZGVyID09PSAicG9zdCIsIHZpc2l0ZWQsIG5hdmlnYXRpb24sIGFjYyk7CiAgICAgIH0pOwogICAgICByZXR1cm4gYWNjOwogICAgfQoKICAgIGZ1bmN0aW9uIGRvRGZzKGcsIHYsIHBvc3RvcmRlciwgdmlzaXRlZCwgbmF2aWdhdGlvbiwgYWNjKSB7CiAgICAgIGlmICghbG9kYXNoXzEuaGFzKHZpc2l0ZWQsIHYpKSB7CiAgICAgICAgdmlzaXRlZFt2XSA9IHRydWU7CgogICAgICAgIGlmICghcG9zdG9yZGVyKSB7IGFjYy5wdXNoKHYpOyB9CiAgICAgICAgbG9kYXNoXzEuZWFjaChuYXZpZ2F0aW9uKHYpLCBmdW5jdGlvbih3KSB7CiAgICAgICAgICBkb0RmcyhnLCB3LCBwb3N0b3JkZXIsIHZpc2l0ZWQsIG5hdmlnYXRpb24sIGFjYyk7CiAgICAgICAgfSk7CiAgICAgICAgaWYgKHBvc3RvcmRlcikgeyBhY2MucHVzaCh2KTsgfQogICAgICB9CiAgICB9CgogICAgdmFyIHBvc3RvcmRlcl8xID0gcG9zdG9yZGVyOwoKICAgIGZ1bmN0aW9uIHBvc3RvcmRlcihnLCB2cykgewogICAgICByZXR1cm4gZGZzXzEoZywgdnMsICJwb3N0Iik7CiAgICB9CgogICAgdmFyIHByZW9yZGVyXzEgPSBwcmVvcmRlcjsKCiAgICBmdW5jdGlvbiBwcmVvcmRlcihnLCB2cykgewogICAgICByZXR1cm4gZGZzXzEoZywgdnMsICJwcmUiKTsKICAgIH0KCiAgICB2YXIgcHJpbV8xID0gcHJpbTsKCiAgICBmdW5jdGlvbiBwcmltKGcsIHdlaWdodEZ1bmMpIHsKICAgICAgdmFyIHJlc3VsdCA9IG5ldyBncmFwaCgpOwogICAgICB2YXIgcGFyZW50cyA9IHt9OwogICAgICB2YXIgcHEgPSBuZXcgcHJpb3JpdHlRdWV1ZSgpOwogICAgICB2YXIgdjsKCiAgICAgIGZ1bmN0aW9uIHVwZGF0ZU5laWdoYm9ycyhlZGdlKSB7CiAgICAgICAgdmFyIHcgPSBlZGdlLnYgPT09IHYgPyBlZGdlLncgOiBlZGdlLnY7CiAgICAgICAgdmFyIHByaSA9IHBxLnByaW9yaXR5KHcpOwogICAgICAgIGlmIChwcmkgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgdmFyIGVkZ2VXZWlnaHQgPSB3ZWlnaHRGdW5jKGVkZ2UpOwogICAgICAgICAgaWYgKGVkZ2VXZWlnaHQgPCBwcmkpIHsKICAgICAgICAgICAgcGFyZW50c1t3XSA9IHY7CiAgICAgICAgICAgIHBxLmRlY3JlYXNlKHcsIGVkZ2VXZWlnaHQpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgaWYgKGcubm9kZUNvdW50KCkgPT09IDApIHsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICB9CgogICAgICBsb2Rhc2hfMS5lYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHBxLmFkZCh2LCBOdW1iZXIuUE9TSVRJVkVfSU5GSU5JVFkpOwogICAgICAgIHJlc3VsdC5zZXROb2RlKHYpOwogICAgICB9KTsKCiAgICAgIC8vIFN0YXJ0IGZyb20gYW4gYXJiaXRyYXJ5IG5vZGUKICAgICAgcHEuZGVjcmVhc2UoZy5ub2RlcygpWzBdLCAwKTsKCiAgICAgIHZhciBpbml0ID0gZmFsc2U7CiAgICAgIHdoaWxlIChwcS5zaXplKCkgPiAwKSB7CiAgICAgICAgdiA9IHBxLnJlbW92ZU1pbigpOwogICAgICAgIGlmIChsb2Rhc2hfMS5oYXMocGFyZW50cywgdikpIHsKICAgICAgICAgIHJlc3VsdC5zZXRFZGdlKHYsIHBhcmVudHNbdl0pOwogICAgICAgIH0gZWxzZSBpZiAoaW5pdCkgewogICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJJbnB1dCBncmFwaCBpcyBub3QgY29ubmVjdGVkOiAiICsgZyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGluaXQgPSB0cnVlOwogICAgICAgIH0KCiAgICAgICAgZy5ub2RlRWRnZXModikuZm9yRWFjaCh1cGRhdGVOZWlnaGJvcnMpOwogICAgICB9CgogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBhbGcgPSB7CiAgICAgIGNvbXBvbmVudHM6IGNvbXBvbmVudHNfMSwKICAgICAgZGlqa3N0cmE6IGRpamtzdHJhXzEsCiAgICAgIGRpamtzdHJhQWxsOiBkaWprc3RyYUFsbF8xLAogICAgICBmaW5kQ3ljbGVzOiBmaW5kQ3ljbGVzXzEsCiAgICAgIGZsb3lkV2Fyc2hhbGw6IGZsb3lkV2Fyc2hhbGxfMSwKICAgICAgaXNBY3ljbGljOiBpc0FjeWNsaWNfMSwKICAgICAgcG9zdG9yZGVyOiBwb3N0b3JkZXJfMSwKICAgICAgcHJlb3JkZXI6IHByZW9yZGVyXzEsCiAgICAgIHByaW06IHByaW1fMSwKICAgICAgdGFyamFuOiB0YXJqYW5fMSwKICAgICAgdG9wc29ydDogdG9wc29ydF8xCiAgICB9OwoKICAgIC8qKgogICAgICogQ29weXJpZ2h0IChjKSAyMDE0LCBDaHJpcyBQZXR0aXR0CiAgICAgKiBBbGwgcmlnaHRzIHJlc2VydmVkLgogICAgICoKICAgICAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNlIGFuZCBiaW5hcnkgZm9ybXMsIHdpdGggb3Igd2l0aG91dAogICAgICogbW9kaWZpY2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRoYXQgdGhlIGZvbGxvd2luZyBjb25kaXRpb25zIGFyZSBtZXQ6CiAgICAgKgogICAgICogMS4gUmVkaXN0cmlidXRpb25zIG9mIHNvdXJjZSBjb2RlIG11c3QgcmV0YWluIHRoZSBhYm92ZSBjb3B5cmlnaHQgbm90aWNlLCB0aGlzCiAgICAgKiBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lci4KICAgICAqCiAgICAgKiAyLiBSZWRpc3RyaWJ1dGlvbnMgaW4gYmluYXJ5IGZvcm0gbXVzdCByZXByb2R1Y2UgdGhlIGFib3ZlIGNvcHlyaWdodCBub3RpY2UsCiAgICAgKiB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyIGluIHRoZSBkb2N1bWVudGF0aW9uCiAgICAgKiBhbmQvb3Igb3RoZXIgbWF0ZXJpYWxzIHByb3ZpZGVkIHdpdGggdGhlIGRpc3RyaWJ1dGlvbi4KICAgICAqCiAgICAgKiAzLiBOZWl0aGVyIHRoZSBuYW1lIG9mIHRoZSBjb3B5cmlnaHQgaG9sZGVyIG5vciB0aGUgbmFtZXMgb2YgaXRzIGNvbnRyaWJ1dG9ycwogICAgICogbWF5IGJlIHVzZWQgdG8gZW5kb3JzZSBvciBwcm9tb3RlIHByb2R1Y3RzIGRlcml2ZWQgZnJvbSB0aGlzIHNvZnR3YXJlIHdpdGhvdXQKICAgICAqIHNwZWNpZmljIHByaW9yIHdyaXR0ZW4gcGVybWlzc2lvbi4KICAgICAqCiAgICAgKiBUSElTIFNPRlRXQVJFIElTIFBST1ZJREVEIEJZIFRIRSBDT1BZUklHSFQgSE9MREVSUyBBTkQgQ09OVFJJQlVUT1JTICJBUyBJUyIgQU5ECiAgICAgKiBBTlkgRVhQUkVTUyBPUiBJTVBMSUVEIFdBUlJBTlRJRVMsIElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBUSEUgSU1QTElFRAogICAgICogV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFkgQU5EIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFIEFSRQogICAgICogRElTQ0xBSU1FRC4gSU4gTk8gRVZFTlQgU0hBTEwgVEhFIENPUFlSSUdIVCBIT0xERVIgT1IgQ09OVFJJQlVUT1JTIEJFIExJQUJMRQogICAgICogRk9SIEFOWSBESVJFQ1QsIElORElSRUNULCBJTkNJREVOVEFMLCBTUEVDSUFMLCBFWEVNUExBUlksIE9SIENPTlNFUVVFTlRJQUwKICAgICAqIERBTUFHRVMgKElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBQUk9DVVJFTUVOVCBPRiBTVUJTVElUVVRFIEdPT0RTIE9SCiAgICAgKiBTRVJWSUNFUzsgTE9TUyBPRiBVU0UsIERBVEEsIE9SIFBST0ZJVFM7IE9SIEJVU0lORVNTIElOVEVSUlVQVElPTikgSE9XRVZFUgogICAgICogQ0FVU0VEIEFORCBPTiBBTlkgVEhFT1JZIE9GIExJQUJJTElUWSwgV0hFVEhFUiBJTiBDT05UUkFDVCwgU1RSSUNUIExJQUJJTElUWSwKICAgICAqIE9SIFRPUlQgKElOQ0xVRElORyBORUdMSUdFTkNFIE9SIE9USEVSV0lTRSkgQVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNFCiAgICAgKiBPRiBUSElTIFNPRlRXQVJFLCBFVkVOIElGIEFEVklTRUQgT0YgVEhFIFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLgogICAgICovCgoKCiAgICB2YXIgZ3JhcGhsaWIgPSB7CiAgICAgIEdyYXBoOiBsaWIuR3JhcGgsCiAgICAgIGpzb246IGpzb24kMiwKICAgICAgYWxnOiBhbGcsCiAgICAgIHZlcnNpb246IGxpYi52ZXJzaW9uCiAgICB9OwoKICAgIC8qIGdsb2JhbCB3aW5kb3cgKi8KCiAgICB2YXIgZ3JhcGhsaWIkMTsKCiAgICBpZiAodHlwZW9mIGNvbW1vbmpzUmVxdWlyZSA9PT0gImZ1bmN0aW9uIikgewogICAgICB0cnkgewogICAgICAgIGdyYXBobGliJDEgPSBncmFwaGxpYjsKICAgICAgfSBjYXRjaCAoZSkgewogICAgICAgIC8vIGNvbnRpbnVlIHJlZ2FyZGxlc3Mgb2YgZXJyb3IKICAgICAgfQogICAgfQoKICAgIGlmICghZ3JhcGhsaWIkMSkgewogICAgICBncmFwaGxpYiQxID0gd2luZG93LmdyYXBobGliOwogICAgfQoKICAgIHZhciBncmFwaGxpYl8xID0gZ3JhcGhsaWIkMTsKCiAgICAvKiogVXNlZCB0byBjb21wb3NlIGJpdG1hc2tzIGZvciBjbG9uaW5nLiAqLwogICAgdmFyIENMT05FX0RFRVBfRkxBRyQxID0gMSwKICAgICAgICBDTE9ORV9TWU1CT0xTX0ZMQUckMiA9IDQ7CgogICAgLyoqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmNsb25lYCBleGNlcHQgdGhhdCBpdCByZWN1cnNpdmVseSBjbG9uZXMgYHZhbHVlYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDEuMC4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gcmVjdXJzaXZlbHkgY2xvbmUuCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgZGVlcCBjbG9uZWQgdmFsdWUuCiAgICAgKiBAc2VlIF8uY2xvbmUKICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIG9iamVjdHMgPSBbeyAnYSc6IDEgfSwgeyAnYic6IDIgfV07CiAgICAgKgogICAgICogdmFyIGRlZXAgPSBfLmNsb25lRGVlcChvYmplY3RzKTsKICAgICAqIGNvbnNvbGUubG9nKGRlZXBbMF0gPT09IG9iamVjdHNbMF0pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqLwogICAgZnVuY3Rpb24gY2xvbmVEZWVwKHZhbHVlKSB7CiAgICAgIHJldHVybiBfYmFzZUNsb25lKHZhbHVlLCBDTE9ORV9ERUVQX0ZMQUckMSB8IENMT05FX1NZTUJPTFNfRkxBRyQyKTsKICAgIH0KCiAgICB2YXIgY2xvbmVEZWVwXzEgPSBjbG9uZURlZXA7CgogICAgLyoqCiAgICAgKiBDaGVja3MgaWYgdGhlIGdpdmVuIGFyZ3VtZW50cyBhcmUgZnJvbSBhbiBpdGVyYXRlZSBjYWxsLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSBwb3RlbnRpYWwgaXRlcmF0ZWUgdmFsdWUgYXJndW1lbnQuCiAgICAgKiBAcGFyYW0geyp9IGluZGV4IFRoZSBwb3RlbnRpYWwgaXRlcmF0ZWUgaW5kZXggb3Iga2V5IGFyZ3VtZW50LgogICAgICogQHBhcmFtIHsqfSBvYmplY3QgVGhlIHBvdGVudGlhbCBpdGVyYXRlZSBvYmplY3QgYXJndW1lbnQuCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgdGhlIGFyZ3VtZW50cyBhcmUgZnJvbSBhbiBpdGVyYXRlZSBjYWxsLAogICAgICogIGVsc2UgYGZhbHNlYC4KICAgICAqLwogICAgZnVuY3Rpb24gaXNJdGVyYXRlZUNhbGwodmFsdWUsIGluZGV4LCBvYmplY3QpIHsKICAgICAgaWYgKCFpc09iamVjdF8xKG9iamVjdCkpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgdmFyIHR5cGUgPSB0eXBlb2YgaW5kZXg7CiAgICAgIGlmICh0eXBlID09ICdudW1iZXInCiAgICAgICAgICAgID8gKGlzQXJyYXlMaWtlXzEob2JqZWN0KSAmJiBfaXNJbmRleChpbmRleCwgb2JqZWN0Lmxlbmd0aCkpCiAgICAgICAgICAgIDogKHR5cGUgPT0gJ3N0cmluZycgJiYgaW5kZXggaW4gb2JqZWN0KQogICAgICAgICAgKSB7CiAgICAgICAgcmV0dXJuIGVxXzEob2JqZWN0W2luZGV4XSwgdmFsdWUpOwogICAgICB9CiAgICAgIHJldHVybiBmYWxzZTsKICAgIH0KCiAgICB2YXIgX2lzSXRlcmF0ZWVDYWxsID0gaXNJdGVyYXRlZUNhbGw7CgogICAgLyoqIFVzZWQgZm9yIGJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzLiAqLwogICAgdmFyIG9iamVjdFByb3RvJGggPSBPYmplY3QucHJvdG90eXBlOwoKICAgIC8qKiBVc2VkIHRvIGNoZWNrIG9iamVjdHMgZm9yIG93biBwcm9wZXJ0aWVzLiAqLwogICAgdmFyIGhhc093blByb3BlcnR5JGUgPSBvYmplY3RQcm90byRoLmhhc093blByb3BlcnR5OwoKICAgIC8qKgogICAgICogQXNzaWducyBvd24gYW5kIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIG9mIHNvdXJjZQogICAgICogb2JqZWN0cyB0byB0aGUgZGVzdGluYXRpb24gb2JqZWN0IGZvciBhbGwgZGVzdGluYXRpb24gcHJvcGVydGllcyB0aGF0CiAgICAgKiByZXNvbHZlIHRvIGB1bmRlZmluZWRgLiBTb3VyY2Ugb2JqZWN0cyBhcmUgYXBwbGllZCBmcm9tIGxlZnQgdG8gcmlnaHQuCiAgICAgKiBPbmNlIGEgcHJvcGVydHkgaXMgc2V0LCBhZGRpdGlvbmFsIHZhbHVlcyBvZiB0aGUgc2FtZSBwcm9wZXJ0eSBhcmUgaWdub3JlZC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgKiBAcGFyYW0gey4uLk9iamVjdH0gW3NvdXJjZXNdIFRoZSBzb3VyY2Ugb2JqZWN0cy4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKiBAc2VlIF8uZGVmYXVsdHNEZWVwCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uZGVmYXVsdHMoeyAnYSc6IDEgfSwgeyAnYic6IDIgfSwgeyAnYSc6IDMgfSk7CiAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAqLwogICAgdmFyIGRlZmF1bHRzID0gX2Jhc2VSZXN0KGZ1bmN0aW9uKG9iamVjdCwgc291cmNlcykgewogICAgICBvYmplY3QgPSBPYmplY3Qob2JqZWN0KTsKCiAgICAgIHZhciBpbmRleCA9IC0xOwogICAgICB2YXIgbGVuZ3RoID0gc291cmNlcy5sZW5ndGg7CiAgICAgIHZhciBndWFyZCA9IGxlbmd0aCA+IDIgPyBzb3VyY2VzWzJdIDogdW5kZWZpbmVkOwoKICAgICAgaWYgKGd1YXJkICYmIF9pc0l0ZXJhdGVlQ2FsbChzb3VyY2VzWzBdLCBzb3VyY2VzWzFdLCBndWFyZCkpIHsKICAgICAgICBsZW5ndGggPSAxOwogICAgICB9CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHZhciBzb3VyY2UgPSBzb3VyY2VzW2luZGV4XTsKICAgICAgICB2YXIgcHJvcHMgPSBrZXlzSW5fMShzb3VyY2UpOwogICAgICAgIHZhciBwcm9wc0luZGV4ID0gLTE7CiAgICAgICAgdmFyIHByb3BzTGVuZ3RoID0gcHJvcHMubGVuZ3RoOwoKICAgICAgICB3aGlsZSAoKytwcm9wc0luZGV4IDwgcHJvcHNMZW5ndGgpIHsKICAgICAgICAgIHZhciBrZXkgPSBwcm9wc1twcm9wc0luZGV4XTsKICAgICAgICAgIHZhciB2YWx1ZSA9IG9iamVjdFtrZXldOwoKICAgICAgICAgIGlmICh2YWx1ZSA9PT0gdW5kZWZpbmVkIHx8CiAgICAgICAgICAgICAgKGVxXzEodmFsdWUsIG9iamVjdFByb3RvJGhba2V5XSkgJiYgIWhhc093blByb3BlcnR5JGUuY2FsbChvYmplY3QsIGtleSkpKSB7CiAgICAgICAgICAgIG9iamVjdFtrZXldID0gc291cmNlW2tleV07CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gb2JqZWN0OwogICAgfSk7CgogICAgdmFyIGRlZmF1bHRzXzEgPSBkZWZhdWx0czsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYSBgXy5maW5kYCBvciBgXy5maW5kTGFzdGAgZnVuY3Rpb24uCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGZpbmRJbmRleEZ1bmMgVGhlIGZ1bmN0aW9uIHRvIGZpbmQgdGhlIGNvbGxlY3Rpb24gaW5kZXguCiAgICAgKiBAcmV0dXJucyB7RnVuY3Rpb259IFJldHVybnMgdGhlIG5ldyBmaW5kIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVGaW5kKGZpbmRJbmRleEZ1bmMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGNvbGxlY3Rpb24sIHByZWRpY2F0ZSwgZnJvbUluZGV4KSB7CiAgICAgICAgdmFyIGl0ZXJhYmxlID0gT2JqZWN0KGNvbGxlY3Rpb24pOwogICAgICAgIGlmICghaXNBcnJheUxpa2VfMShjb2xsZWN0aW9uKSkgewogICAgICAgICAgdmFyIGl0ZXJhdGVlID0gX2Jhc2VJdGVyYXRlZShwcmVkaWNhdGUpOwogICAgICAgICAgY29sbGVjdGlvbiA9IGtleXNfMShjb2xsZWN0aW9uKTsKICAgICAgICAgIHByZWRpY2F0ZSA9IGZ1bmN0aW9uKGtleSkgeyByZXR1cm4gaXRlcmF0ZWUoaXRlcmFibGVba2V5XSwga2V5LCBpdGVyYWJsZSk7IH07CiAgICAgICAgfQogICAgICAgIHZhciBpbmRleCA9IGZpbmRJbmRleEZ1bmMoY29sbGVjdGlvbiwgcHJlZGljYXRlLCBmcm9tSW5kZXgpOwogICAgICAgIHJldHVybiBpbmRleCA+IC0xID8gaXRlcmFibGVbaXRlcmF0ZWUgPyBjb2xsZWN0aW9uW2luZGV4XSA6IGluZGV4XSA6IHVuZGVmaW5lZDsKICAgICAgfTsKICAgIH0KCiAgICB2YXIgX2NyZWF0ZUZpbmQgPSBjcmVhdGVGaW5kOwoKICAgIC8qKiBVc2VkIGFzIHJlZmVyZW5jZXMgZm9yIHZhcmlvdXMgYE51bWJlcmAgY29uc3RhbnRzLiAqLwogICAgdmFyIE5BTiA9IDAgLyAwOwoKICAgIC8qKiBVc2VkIHRvIG1hdGNoIGxlYWRpbmcgYW5kIHRyYWlsaW5nIHdoaXRlc3BhY2UuICovCiAgICB2YXIgcmVUcmltID0gL15ccyt8XHMrJC9nOwoKICAgIC8qKiBVc2VkIHRvIGRldGVjdCBiYWQgc2lnbmVkIGhleGFkZWNpbWFsIHN0cmluZyB2YWx1ZXMuICovCiAgICB2YXIgcmVJc0JhZEhleCA9IC9eWy0rXTB4WzAtOWEtZl0rJC9pOwoKICAgIC8qKiBVc2VkIHRvIGRldGVjdCBiaW5hcnkgc3RyaW5nIHZhbHVlcy4gKi8KICAgIHZhciByZUlzQmluYXJ5ID0gL14wYlswMV0rJC9pOwoKICAgIC8qKiBVc2VkIHRvIGRldGVjdCBvY3RhbCBzdHJpbmcgdmFsdWVzLiAqLwogICAgdmFyIHJlSXNPY3RhbCA9IC9eMG9bMC03XSskL2k7CgogICAgLyoqIEJ1aWx0LWluIG1ldGhvZCByZWZlcmVuY2VzIHdpdGhvdXQgYSBkZXBlbmRlbmN5IG9uIGByb290YC4gKi8KICAgIHZhciBmcmVlUGFyc2VJbnQgPSBwYXJzZUludDsKCiAgICAvKioKICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYSBudW1iZXIuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSA0LjAuMAogICAgICogQGNhdGVnb3J5IExhbmcKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIHByb2Nlc3MuCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBudW1iZXIuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8udG9OdW1iZXIoMy4yKTsKICAgICAqIC8vID0+IDMuMgogICAgICoKICAgICAqIF8udG9OdW1iZXIoTnVtYmVyLk1JTl9WQUxVRSk7CiAgICAgKiAvLyA9PiA1ZS0zMjQKICAgICAqCiAgICAgKiBfLnRvTnVtYmVyKEluZmluaXR5KTsKICAgICAqIC8vID0+IEluZmluaXR5CiAgICAgKgogICAgICogXy50b051bWJlcignMy4yJyk7CiAgICAgKiAvLyA9PiAzLjIKICAgICAqLwogICAgZnVuY3Rpb24gdG9OdW1iZXIodmFsdWUpIHsKICAgICAgaWYgKHR5cGVvZiB2YWx1ZSA9PSAnbnVtYmVyJykgewogICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgfQogICAgICBpZiAoaXNTeW1ib2xfMSh2YWx1ZSkpIHsKICAgICAgICByZXR1cm4gTkFOOwogICAgICB9CiAgICAgIGlmIChpc09iamVjdF8xKHZhbHVlKSkgewogICAgICAgIHZhciBvdGhlciA9IHR5cGVvZiB2YWx1ZS52YWx1ZU9mID09ICdmdW5jdGlvbicgPyB2YWx1ZS52YWx1ZU9mKCkgOiB2YWx1ZTsKICAgICAgICB2YWx1ZSA9IGlzT2JqZWN0XzEob3RoZXIpID8gKG90aGVyICsgJycpIDogb3RoZXI7CiAgICAgIH0KICAgICAgaWYgKHR5cGVvZiB2YWx1ZSAhPSAnc3RyaW5nJykgewogICAgICAgIHJldHVybiB2YWx1ZSA9PT0gMCA/IHZhbHVlIDogK3ZhbHVlOwogICAgICB9CiAgICAgIHZhbHVlID0gdmFsdWUucmVwbGFjZShyZVRyaW0sICcnKTsKICAgICAgdmFyIGlzQmluYXJ5ID0gcmVJc0JpbmFyeS50ZXN0KHZhbHVlKTsKICAgICAgcmV0dXJuIChpc0JpbmFyeSB8fCByZUlzT2N0YWwudGVzdCh2YWx1ZSkpCiAgICAgICAgPyBmcmVlUGFyc2VJbnQodmFsdWUuc2xpY2UoMiksIGlzQmluYXJ5ID8gMiA6IDgpCiAgICAgICAgOiAocmVJc0JhZEhleC50ZXN0KHZhbHVlKSA/IE5BTiA6ICt2YWx1ZSk7CiAgICB9CgogICAgdmFyIHRvTnVtYmVyXzEgPSB0b051bWJlcjsKCiAgICAvKiogVXNlZCBhcyByZWZlcmVuY2VzIGZvciB2YXJpb3VzIGBOdW1iZXJgIGNvbnN0YW50cy4gKi8KICAgIHZhciBJTkZJTklUWSQzID0gMSAvIDAsCiAgICAgICAgTUFYX0lOVEVHRVIgPSAxLjc5NzY5MzEzNDg2MjMxNTdlKzMwODsKCiAgICAvKioKICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYSBmaW5pdGUgbnVtYmVyLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgNC4xMi4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBudW1iZXIuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8udG9GaW5pdGUoMy4yKTsKICAgICAqIC8vID0+IDMuMgogICAgICoKICAgICAqIF8udG9GaW5pdGUoTnVtYmVyLk1JTl9WQUxVRSk7CiAgICAgKiAvLyA9PiA1ZS0zMjQKICAgICAqCiAgICAgKiBfLnRvRmluaXRlKEluZmluaXR5KTsKICAgICAqIC8vID0+IDEuNzk3NjkzMTM0ODYyMzE1N2UrMzA4CiAgICAgKgogICAgICogXy50b0Zpbml0ZSgnMy4yJyk7CiAgICAgKiAvLyA9PiAzLjIKICAgICAqLwogICAgZnVuY3Rpb24gdG9GaW5pdGUodmFsdWUpIHsKICAgICAgaWYgKCF2YWx1ZSkgewogICAgICAgIHJldHVybiB2YWx1ZSA9PT0gMCA/IHZhbHVlIDogMDsKICAgICAgfQogICAgICB2YWx1ZSA9IHRvTnVtYmVyXzEodmFsdWUpOwogICAgICBpZiAodmFsdWUgPT09IElORklOSVRZJDMgfHwgdmFsdWUgPT09IC1JTkZJTklUWSQzKSB7CiAgICAgICAgdmFyIHNpZ24gPSAodmFsdWUgPCAwID8gLTEgOiAxKTsKICAgICAgICByZXR1cm4gc2lnbiAqIE1BWF9JTlRFR0VSOwogICAgICB9CiAgICAgIHJldHVybiB2YWx1ZSA9PT0gdmFsdWUgPyB2YWx1ZSA6IDA7CiAgICB9CgogICAgdmFyIHRvRmluaXRlXzEgPSB0b0Zpbml0ZTsKCiAgICAvKioKICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYW4gaW50ZWdlci4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgaXMgbG9vc2VseSBiYXNlZCBvbgogICAgICogW2BUb0ludGVnZXJgXShodHRwOi8vd3d3LmVjbWEtaW50ZXJuYXRpb25hbC5vcmcvZWNtYS0yNjIvNy4wLyNzZWMtdG9pbnRlZ2VyKS4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMC4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29udmVydC4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGNvbnZlcnRlZCBpbnRlZ2VyLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLnRvSW50ZWdlcigzLjIpOwogICAgICogLy8gPT4gMwogICAgICoKICAgICAqIF8udG9JbnRlZ2VyKE51bWJlci5NSU5fVkFMVUUpOwogICAgICogLy8gPT4gMAogICAgICoKICAgICAqIF8udG9JbnRlZ2VyKEluZmluaXR5KTsKICAgICAqIC8vID0+IDEuNzk3NjkzMTM0ODYyMzE1N2UrMzA4CiAgICAgKgogICAgICogXy50b0ludGVnZXIoJzMuMicpOwogICAgICogLy8gPT4gMwogICAgICovCiAgICBmdW5jdGlvbiB0b0ludGVnZXIodmFsdWUpIHsKICAgICAgdmFyIHJlc3VsdCA9IHRvRmluaXRlXzEodmFsdWUpLAogICAgICAgICAgcmVtYWluZGVyID0gcmVzdWx0ICUgMTsKCiAgICAgIHJldHVybiByZXN1bHQgPT09IHJlc3VsdCA/IChyZW1haW5kZXIgPyByZXN1bHQgLSByZW1haW5kZXIgOiByZXN1bHQpIDogMDsKICAgIH0KCiAgICB2YXIgdG9JbnRlZ2VyXzEgPSB0b0ludGVnZXI7CgogICAgLyogQnVpbHQtaW4gbWV0aG9kIHJlZmVyZW5jZXMgZm9yIHRob3NlIHdpdGggdGhlIHNhbWUgbmFtZSBhcyBvdGhlciBgbG9kYXNoYCBtZXRob2RzLiAqLwogICAgdmFyIG5hdGl2ZU1heCQxID0gTWF0aC5tYXg7CgogICAgLyoqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmZpbmRgIGV4Y2VwdCB0aGF0IGl0IHJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBmaXJzdAogICAgICogZWxlbWVudCBgcHJlZGljYXRlYCByZXR1cm5zIHRydXRoeSBmb3IgaW5zdGVhZCBvZiB0aGUgZWxlbWVudCBpdHNlbGYuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAxLjEuMAogICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gaW5zcGVjdC4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtwcmVkaWNhdGU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBbZnJvbUluZGV4PTBdIFRoZSBpbmRleCB0byBzZWFyY2ggZnJvbS4KICAgICAqIEByZXR1cm5zIHtudW1iZXJ9IFJldHVybnMgdGhlIGluZGV4IG9mIHRoZSBmb3VuZCBlbGVtZW50LCBlbHNlIGAtMWAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciB1c2VycyA9IFsKICAgICAqICAgeyAndXNlcic6ICdiYXJuZXknLCAgJ2FjdGl2ZSc6IGZhbHNlIH0sCiAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgICdhY3RpdmUnOiBmYWxzZSB9LAogICAgICogICB7ICd1c2VyJzogJ3BlYmJsZXMnLCAnYWN0aXZlJzogdHJ1ZSB9CiAgICAgKiBdOwogICAgICoKICAgICAqIF8uZmluZEluZGV4KHVzZXJzLCBmdW5jdGlvbihvKSB7IHJldHVybiBvLnVzZXIgPT0gJ2Jhcm5leSc7IH0pOwogICAgICogLy8gPT4gMAogICAgICoKICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzYCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgKiBfLmZpbmRJbmRleCh1c2VycywgeyAndXNlcic6ICdmcmVkJywgJ2FjdGl2ZSc6IGZhbHNlIH0pOwogICAgICogLy8gPT4gMQogICAgICoKICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzUHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8uZmluZEluZGV4KHVzZXJzLCBbJ2FjdGl2ZScsIGZhbHNlXSk7CiAgICAgKiAvLyA9PiAwCiAgICAgKgogICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgKiBfLmZpbmRJbmRleCh1c2VycywgJ2FjdGl2ZScpOwogICAgICogLy8gPT4gMgogICAgICovCiAgICBmdW5jdGlvbiBmaW5kSW5kZXgoYXJyYXksIHByZWRpY2F0ZSwgZnJvbUluZGV4KSB7CiAgICAgIHZhciBsZW5ndGggPSBhcnJheSA9PSBudWxsID8gMCA6IGFycmF5Lmxlbmd0aDsKICAgICAgaWYgKCFsZW5ndGgpIHsKICAgICAgICByZXR1cm4gLTE7CiAgICAgIH0KICAgICAgdmFyIGluZGV4ID0gZnJvbUluZGV4ID09IG51bGwgPyAwIDogdG9JbnRlZ2VyXzEoZnJvbUluZGV4KTsKICAgICAgaWYgKGluZGV4IDwgMCkgewogICAgICAgIGluZGV4ID0gbmF0aXZlTWF4JDEobGVuZ3RoICsgaW5kZXgsIDApOwogICAgICB9CiAgICAgIHJldHVybiBfYmFzZUZpbmRJbmRleChhcnJheSwgX2Jhc2VJdGVyYXRlZShwcmVkaWNhdGUpLCBpbmRleCk7CiAgICB9CgogICAgdmFyIGZpbmRJbmRleF8xID0gZmluZEluZGV4OwoKICAgIC8qKgogICAgICogSXRlcmF0ZXMgb3ZlciBlbGVtZW50cyBvZiBgY29sbGVjdGlvbmAsIHJldHVybmluZyB0aGUgZmlyc3QgZWxlbWVudAogICAgICogYHByZWRpY2F0ZWAgcmV0dXJucyB0cnV0aHkgZm9yLiBUaGUgcHJlZGljYXRlIGlzIGludm9rZWQgd2l0aCB0aHJlZQogICAgICogYXJndW1lbnRzOiAodmFsdWUsIGluZGV4fGtleSwgY29sbGVjdGlvbikuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IENvbGxlY3Rpb24KICAgICAqIEBwYXJhbSB7QXJyYXl8T2JqZWN0fSBjb2xsZWN0aW9uIFRoZSBjb2xsZWN0aW9uIHRvIGluc3BlY3QuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbcHJlZGljYXRlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW2Zyb21JbmRleD0wXSBUaGUgaW5kZXggdG8gc2VhcmNoIGZyb20uCiAgICAgKiBAcmV0dXJucyB7Kn0gUmV0dXJucyB0aGUgbWF0Y2hlZCBlbGVtZW50LCBlbHNlIGB1bmRlZmluZWRgLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgICdhZ2UnOiAzNiwgJ2FjdGl2ZSc6IHRydWUgfSwKICAgICAqICAgeyAndXNlcic6ICdmcmVkJywgICAgJ2FnZSc6IDQwLCAnYWN0aXZlJzogZmFsc2UgfSwKICAgICAqICAgeyAndXNlcic6ICdwZWJibGVzJywgJ2FnZSc6IDEsICAnYWN0aXZlJzogdHJ1ZSB9CiAgICAgKiBdOwogICAgICoKICAgICAqIF8uZmluZCh1c2VycywgZnVuY3Rpb24obykgeyByZXR1cm4gby5hZ2UgPCA0MDsgfSk7CiAgICAgKiAvLyA9PiBvYmplY3QgZm9yICdiYXJuZXknCiAgICAgKgogICAgICogLy8gVGhlIGBfLm1hdGNoZXNgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8uZmluZCh1c2VycywgeyAnYWdlJzogMSwgJ2FjdGl2ZSc6IHRydWUgfSk7CiAgICAgKiAvLyA9PiBvYmplY3QgZm9yICdwZWJibGVzJwogICAgICoKICAgICAqIC8vIFRoZSBgXy5tYXRjaGVzUHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8uZmluZCh1c2VycywgWydhY3RpdmUnLCBmYWxzZV0pOwogICAgICogLy8gPT4gb2JqZWN0IGZvciAnZnJlZCcKICAgICAqCiAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8uZmluZCh1c2VycywgJ2FjdGl2ZScpOwogICAgICogLy8gPT4gb2JqZWN0IGZvciAnYmFybmV5JwogICAgICovCiAgICB2YXIgZmluZCQyID0gX2NyZWF0ZUZpbmQoZmluZEluZGV4XzEpOwoKICAgIHZhciBmaW5kXzEgPSBmaW5kJDI7CgogICAgLyoqCiAgICAgKiBGbGF0dGVucyBgYXJyYXlgIGEgc2luZ2xlIGxldmVsIGRlZXAuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQGNhdGVnb3J5IEFycmF5CiAgICAgKiBAcGFyYW0ge0FycmF5fSBhcnJheSBUaGUgYXJyYXkgdG8gZmxhdHRlbi4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IGZsYXR0ZW5lZCBhcnJheS4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogXy5mbGF0dGVuKFsxLCBbMiwgWzMsIFs0XV0sIDVdXSk7CiAgICAgKiAvLyA9PiBbMSwgMiwgWzMsIFs0XV0sIDVdCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZsYXR0ZW4oYXJyYXkpIHsKICAgICAgdmFyIGxlbmd0aCA9IGFycmF5ID09IG51bGwgPyAwIDogYXJyYXkubGVuZ3RoOwogICAgICByZXR1cm4gbGVuZ3RoID8gX2Jhc2VGbGF0dGVuKGFycmF5LCAxKSA6IFtdOwogICAgfQoKICAgIHZhciBmbGF0dGVuXzEgPSBmbGF0dGVuOwoKICAgIC8qKgogICAgICogSXRlcmF0ZXMgb3ZlciBvd24gYW5kIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIG9mIGFuCiAgICAgKiBvYmplY3QgYW5kIGludm9rZXMgYGl0ZXJhdGVlYCBmb3IgZWFjaCBwcm9wZXJ0eS4gVGhlIGl0ZXJhdGVlIGlzIGludm9rZWQKICAgICAqIHdpdGggdGhyZWUgYXJndW1lbnRzOiAodmFsdWUsIGtleSwgb2JqZWN0KS4gSXRlcmF0ZWUgZnVuY3Rpb25zIG1heSBleGl0CiAgICAgKiBpdGVyYXRpb24gZWFybHkgYnkgZXhwbGljaXRseSByZXR1cm5pbmcgYGZhbHNlYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuMy4wCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gaXRlcmF0ZSBvdmVyLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2l0ZXJhdGVlPV8uaWRlbnRpdHldIFRoZSBmdW5jdGlvbiBpbnZva2VkIHBlciBpdGVyYXRpb24uCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIGBvYmplY3RgLgogICAgICogQHNlZSBfLmZvckluUmlnaHQKICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICogICB0aGlzLmEgPSAxOwogICAgICogICB0aGlzLmIgPSAyOwogICAgICogfQogICAgICoKICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgKgogICAgICogXy5mb3JJbihuZXcgRm9vLCBmdW5jdGlvbih2YWx1ZSwga2V5KSB7CiAgICAgKiAgIGNvbnNvbGUubG9nKGtleSk7CiAgICAgKiB9KTsKICAgICAqIC8vID0+IExvZ3MgJ2EnLCAnYicsIHRoZW4gJ2MnIChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpLgogICAgICovCiAgICBmdW5jdGlvbiBmb3JJbihvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgIHJldHVybiBvYmplY3QgPT0gbnVsbAogICAgICAgID8gb2JqZWN0CiAgICAgICAgOiBfYmFzZUZvcihvYmplY3QsIF9jYXN0RnVuY3Rpb24oaXRlcmF0ZWUpLCBrZXlzSW5fMSk7CiAgICB9CgogICAgdmFyIGZvckluXzEgPSBmb3JJbjsKCiAgICAvKioKICAgICAqIEdldHMgdGhlIGxhc3QgZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBjYXRlZ29yeSBBcnJheQogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIHF1ZXJ5LgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGxhc3QgZWxlbWVudCBvZiBgYXJyYXlgLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLmxhc3QoWzEsIDIsIDNdKTsKICAgICAqIC8vID0+IDMKICAgICAqLwogICAgZnVuY3Rpb24gbGFzdChhcnJheSkgewogICAgICB2YXIgbGVuZ3RoID0gYXJyYXkgPT0gbnVsbCA/IDAgOiBhcnJheS5sZW5ndGg7CiAgICAgIHJldHVybiBsZW5ndGggPyBhcnJheVtsZW5ndGggLSAxXSA6IHVuZGVmaW5lZDsKICAgIH0KCiAgICB2YXIgbGFzdF8xID0gbGFzdDsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYW4gb2JqZWN0IHdpdGggdGhlIHNhbWUga2V5cyBhcyBgb2JqZWN0YCBhbmQgdmFsdWVzIGdlbmVyYXRlZAogICAgICogYnkgcnVubmluZyBlYWNoIG93biBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0eSBvZiBgb2JqZWN0YCB0aHJ1CiAgICAgKiBgaXRlcmF0ZWVgLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIHRocmVlIGFyZ3VtZW50czoKICAgICAqICh2YWx1ZSwga2V5LCBvYmplY3QpLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMi40LjAKICAgICAqIEBjYXRlZ29yeSBPYmplY3QKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBbaXRlcmF0ZWU9Xy5pZGVudGl0eV0gVGhlIGZ1bmN0aW9uIGludm9rZWQgcGVyIGl0ZXJhdGlvbi4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBtYXBwZWQgb2JqZWN0LgogICAgICogQHNlZSBfLm1hcEtleXMKICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogdmFyIHVzZXJzID0gewogICAgICogICAnZnJlZCc6ICAgIHsgJ3VzZXInOiAnZnJlZCcsICAgICdhZ2UnOiA0MCB9LAogICAgICogICAncGViYmxlcyc6IHsgJ3VzZXInOiAncGViYmxlcycsICdhZ2UnOiAxIH0KICAgICAqIH07CiAgICAgKgogICAgICogXy5tYXBWYWx1ZXModXNlcnMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8uYWdlOyB9KTsKICAgICAqIC8vID0+IHsgJ2ZyZWQnOiA0MCwgJ3BlYmJsZXMnOiAxIH0gKGl0ZXJhdGlvbiBvcmRlciBpcyBub3QgZ3VhcmFudGVlZCkKICAgICAqCiAgICAgKiAvLyBUaGUgYF8ucHJvcGVydHlgIGl0ZXJhdGVlIHNob3J0aGFuZC4KICAgICAqIF8ubWFwVmFsdWVzKHVzZXJzLCAnYWdlJyk7CiAgICAgKiAvLyA9PiB7ICdmcmVkJzogNDAsICdwZWJibGVzJzogMSB9IChpdGVyYXRpb24gb3JkZXIgaXMgbm90IGd1YXJhbnRlZWQpCiAgICAgKi8KICAgIGZ1bmN0aW9uIG1hcFZhbHVlcyhvYmplY3QsIGl0ZXJhdGVlKSB7CiAgICAgIHZhciByZXN1bHQgPSB7fTsKICAgICAgaXRlcmF0ZWUgPSBfYmFzZUl0ZXJhdGVlKGl0ZXJhdGVlKTsKCiAgICAgIF9iYXNlRm9yT3duKG9iamVjdCwgZnVuY3Rpb24odmFsdWUsIGtleSwgb2JqZWN0KSB7CiAgICAgICAgX2Jhc2VBc3NpZ25WYWx1ZShyZXN1bHQsIGtleSwgaXRlcmF0ZWUodmFsdWUsIGtleSwgb2JqZWN0KSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBtYXBWYWx1ZXNfMSA9IG1hcFZhbHVlczsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIG1ldGhvZHMgbGlrZSBgXy5tYXhgIGFuZCBgXy5taW5gIHdoaWNoIGFjY2VwdHMgYQogICAgICogYGNvbXBhcmF0b3JgIHRvIGRldGVybWluZSB0aGUgZXh0cmVtdW0gdmFsdWUuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBpdGVyYXRlZSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgaXRlcmF0aW9uLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY29tcGFyYXRvciBUaGUgY29tcGFyYXRvciB1c2VkIHRvIGNvbXBhcmUgdmFsdWVzLgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIGV4dHJlbXVtIHZhbHVlLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlRXh0cmVtdW0oYXJyYXksIGl0ZXJhdGVlLCBjb21wYXJhdG9yKSB7CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gYXJyYXkubGVuZ3RoOwoKICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICB2YXIgdmFsdWUgPSBhcnJheVtpbmRleF0sCiAgICAgICAgICAgIGN1cnJlbnQgPSBpdGVyYXRlZSh2YWx1ZSk7CgogICAgICAgIGlmIChjdXJyZW50ICE9IG51bGwgJiYgKGNvbXB1dGVkID09PSB1bmRlZmluZWQKICAgICAgICAgICAgICA/IChjdXJyZW50ID09PSBjdXJyZW50ICYmICFpc1N5bWJvbF8xKGN1cnJlbnQpKQogICAgICAgICAgICAgIDogY29tcGFyYXRvcihjdXJyZW50LCBjb21wdXRlZCkKICAgICAgICAgICAgKSkgewogICAgICAgICAgdmFyIGNvbXB1dGVkID0gY3VycmVudCwKICAgICAgICAgICAgICByZXN1bHQgPSB2YWx1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICB2YXIgX2Jhc2VFeHRyZW11bSA9IGJhc2VFeHRyZW11bTsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmd0YCB3aGljaCBkb2Vzbid0IGNvZXJjZSBhcmd1bWVudHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgZ3JlYXRlciB0aGFuIGBvdGhlcmAsCiAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlR3QodmFsdWUsIG90aGVyKSB7CiAgICAgIHJldHVybiB2YWx1ZSA+IG90aGVyOwogICAgfQoKICAgIHZhciBfYmFzZUd0ID0gYmFzZUd0OwoKICAgIC8qKgogICAgICogQ29tcHV0ZXMgdGhlIG1heGltdW0gdmFsdWUgb2YgYGFycmF5YC4gSWYgYGFycmF5YCBpcyBlbXB0eSBvciBmYWxzZXksCiAgICAgKiBgdW5kZWZpbmVkYCBpcyByZXR1cm5lZC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBtYXhpbXVtIHZhbHVlLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLm1heChbNCwgMiwgOCwgNl0pOwogICAgICogLy8gPT4gOAogICAgICoKICAgICAqIF8ubWF4KFtdKTsKICAgICAqIC8vID0+IHVuZGVmaW5lZAogICAgICovCiAgICBmdW5jdGlvbiBtYXgkNihhcnJheSkgewogICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICA/IF9iYXNlRXh0cmVtdW0oYXJyYXksIGlkZW50aXR5XzEsIF9iYXNlR3QpCiAgICAgICAgOiB1bmRlZmluZWQ7CiAgICB9CgogICAgdmFyIG1heF8xID0gbWF4JDY7CgogICAgLyoqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIGlzIGxpa2UgYGFzc2lnblZhbHVlYCBleGNlcHQgdGhhdCBpdCBkb2Vzbid0IGFzc2lnbgogICAgICogYHVuZGVmaW5lZGAgdmFsdWVzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBvYmplY3QgdG8gbW9kaWZ5LgogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSBwcm9wZXJ0eSB0byBhc3NpZ24uCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBhc3NpZ24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFzc2lnbk1lcmdlVmFsdWUob2JqZWN0LCBrZXksIHZhbHVlKSB7CiAgICAgIGlmICgodmFsdWUgIT09IHVuZGVmaW5lZCAmJiAhZXFfMShvYmplY3Rba2V5XSwgdmFsdWUpKSB8fAogICAgICAgICAgKHZhbHVlID09PSB1bmRlZmluZWQgJiYgIShrZXkgaW4gb2JqZWN0KSkpIHsKICAgICAgICBfYmFzZUFzc2lnblZhbHVlKG9iamVjdCwga2V5LCB2YWx1ZSk7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgX2Fzc2lnbk1lcmdlVmFsdWUgPSBhc3NpZ25NZXJnZVZhbHVlOwoKICAgIC8qKiBgT2JqZWN0I3RvU3RyaW5nYCByZXN1bHQgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBvYmplY3RUYWckNCA9ICdbb2JqZWN0IE9iamVjdF0nOwoKICAgIC8qKiBVc2VkIGZvciBidWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcy4gKi8KICAgIHZhciBmdW5jUHJvdG8kMiA9IEZ1bmN0aW9uLnByb3RvdHlwZSwKICAgICAgICBvYmplY3RQcm90byRpID0gT2JqZWN0LnByb3RvdHlwZTsKCiAgICAvKiogVXNlZCB0byByZXNvbHZlIHRoZSBkZWNvbXBpbGVkIHNvdXJjZSBvZiBmdW5jdGlvbnMuICovCiAgICB2YXIgZnVuY1RvU3RyaW5nJDIgPSBmdW5jUHJvdG8kMi50b1N0cmluZzsKCiAgICAvKiogVXNlZCB0byBjaGVjayBvYmplY3RzIGZvciBvd24gcHJvcGVydGllcy4gKi8KICAgIHZhciBoYXNPd25Qcm9wZXJ0eSRmID0gb2JqZWN0UHJvdG8kaS5oYXNPd25Qcm9wZXJ0eTsKCiAgICAvKiogVXNlZCB0byBpbmZlciB0aGUgYE9iamVjdGAgY29uc3RydWN0b3IuICovCiAgICB2YXIgb2JqZWN0Q3RvclN0cmluZyA9IGZ1bmNUb1N0cmluZyQyLmNhbGwoT2JqZWN0KTsKCiAgICAvKioKICAgICAqIENoZWNrcyBpZiBgdmFsdWVgIGlzIGEgcGxhaW4gb2JqZWN0LCB0aGF0IGlzLCBhbiBvYmplY3QgY3JlYXRlZCBieSB0aGUKICAgICAqIGBPYmplY3RgIGNvbnN0cnVjdG9yIG9yIG9uZSB3aXRoIGEgYFtbUHJvdG90eXBlXV1gIG9mIGBudWxsYC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuOC4wCiAgICAgKiBAY2F0ZWdvcnkgTGFuZwogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY2hlY2suCiAgICAgKiBAcmV0dXJucyB7Ym9vbGVhbn0gUmV0dXJucyBgdHJ1ZWAgaWYgYHZhbHVlYCBpcyBhIHBsYWluIG9iamVjdCwgZWxzZSBgZmFsc2VgLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBmdW5jdGlvbiBGb28oKSB7CiAgICAgKiAgIHRoaXMuYSA9IDE7CiAgICAgKiB9CiAgICAgKgogICAgICogXy5pc1BsYWluT2JqZWN0KG5ldyBGb28pOwogICAgICogLy8gPT4gZmFsc2UKICAgICAqCiAgICAgKiBfLmlzUGxhaW5PYmplY3QoWzEsIDIsIDNdKTsKICAgICAqIC8vID0+IGZhbHNlCiAgICAgKgogICAgICogXy5pc1BsYWluT2JqZWN0KHsgJ3gnOiAwLCAneSc6IDAgfSk7CiAgICAgKiAvLyA9PiB0cnVlCiAgICAgKgogICAgICogXy5pc1BsYWluT2JqZWN0KE9iamVjdC5jcmVhdGUobnVsbCkpOwogICAgICogLy8gPT4gdHJ1ZQogICAgICovCiAgICBmdW5jdGlvbiBpc1BsYWluT2JqZWN0JDEodmFsdWUpIHsKICAgICAgaWYgKCFpc09iamVjdExpa2VfMSh2YWx1ZSkgfHwgX2Jhc2VHZXRUYWcodmFsdWUpICE9IG9iamVjdFRhZyQ0KSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIHZhciBwcm90byA9IF9nZXRQcm90b3R5cGUodmFsdWUpOwogICAgICBpZiAocHJvdG8gPT09IG51bGwpIHsKICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQogICAgICB2YXIgQ3RvciA9IGhhc093blByb3BlcnR5JGYuY2FsbChwcm90bywgJ2NvbnN0cnVjdG9yJykgJiYgcHJvdG8uY29uc3RydWN0b3I7CiAgICAgIHJldHVybiB0eXBlb2YgQ3RvciA9PSAnZnVuY3Rpb24nICYmIEN0b3IgaW5zdGFuY2VvZiBDdG9yICYmCiAgICAgICAgZnVuY1RvU3RyaW5nJDIuY2FsbChDdG9yKSA9PSBvYmplY3RDdG9yU3RyaW5nOwogICAgfQoKICAgIHZhciBpc1BsYWluT2JqZWN0XzEgPSBpc1BsYWluT2JqZWN0JDE7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSB2YWx1ZSBhdCBga2V5YCwgdW5sZXNzIGBrZXlgIGlzICJfX3Byb3RvX18iIG9yICJjb25zdHJ1Y3RvciIuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBxdWVyeS4KICAgICAqIEBwYXJhbSB7c3RyaW5nfSBrZXkgVGhlIGtleSBvZiB0aGUgcHJvcGVydHkgdG8gZ2V0LgogICAgICogQHJldHVybnMgeyp9IFJldHVybnMgdGhlIHByb3BlcnR5IHZhbHVlLgogICAgICovCiAgICBmdW5jdGlvbiBzYWZlR2V0KG9iamVjdCwga2V5KSB7CiAgICAgIGlmIChrZXkgPT09ICdjb25zdHJ1Y3RvcicgJiYgdHlwZW9mIG9iamVjdFtrZXldID09PSAnZnVuY3Rpb24nKSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBpZiAoa2V5ID09ICdfX3Byb3RvX18nKSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICByZXR1cm4gb2JqZWN0W2tleV07CiAgICB9CgogICAgdmFyIF9zYWZlR2V0ID0gc2FmZUdldDsKCiAgICAvKioKICAgICAqIENvbnZlcnRzIGB2YWx1ZWAgdG8gYSBwbGFpbiBvYmplY3QgZmxhdHRlbmluZyBpbmhlcml0ZWQgZW51bWVyYWJsZSBzdHJpbmcKICAgICAqIGtleWVkIHByb3BlcnRpZXMgb2YgYHZhbHVlYCB0byBvd24gcHJvcGVydGllcyBvZiB0aGUgcGxhaW4gb2JqZWN0LgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMy4wLjAKICAgICAqIEBjYXRlZ29yeSBMYW5nCiAgICAgKiBAcGFyYW0geyp9IHZhbHVlIFRoZSB2YWx1ZSB0byBjb252ZXJ0LgogICAgICogQHJldHVybnMge09iamVjdH0gUmV0dXJucyB0aGUgY29udmVydGVkIHBsYWluIG9iamVjdC4KICAgICAqIEBleGFtcGxlCiAgICAgKgogICAgICogZnVuY3Rpb24gRm9vKCkgewogICAgICogICB0aGlzLmIgPSAyOwogICAgICogfQogICAgICoKICAgICAqIEZvby5wcm90b3R5cGUuYyA9IDM7CiAgICAgKgogICAgICogXy5hc3NpZ24oeyAnYSc6IDEgfSwgbmV3IEZvbyk7CiAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAqCiAgICAgKiBfLmFzc2lnbih7ICdhJzogMSB9LCBfLnRvUGxhaW5PYmplY3QobmV3IEZvbykpOwogICAgICogLy8gPT4geyAnYSc6IDEsICdiJzogMiwgJ2MnOiAzIH0KICAgICAqLwogICAgZnVuY3Rpb24gdG9QbGFpbk9iamVjdCh2YWx1ZSkgewogICAgICByZXR1cm4gX2NvcHlPYmplY3QodmFsdWUsIGtleXNJbl8xKHZhbHVlKSk7CiAgICB9CgogICAgdmFyIHRvUGxhaW5PYmplY3RfMSA9IHRvUGxhaW5PYmplY3Q7CgogICAgLyoqCiAgICAgKiBBIHNwZWNpYWxpemVkIHZlcnNpb24gb2YgYGJhc2VNZXJnZWAgZm9yIGFycmF5cyBhbmQgb2JqZWN0cyB3aGljaCBwZXJmb3JtcwogICAgICogZGVlcCBtZXJnZXMgYW5kIHRyYWNrcyB0cmF2ZXJzZWQgb2JqZWN0cyBlbmFibGluZyBvYmplY3RzIHdpdGggY2lyY3VsYXIKICAgICAqIHJlZmVyZW5jZXMgdG8gYmUgbWVyZ2VkLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICogQHBhcmFtIHtzdHJpbmd9IGtleSBUaGUga2V5IG9mIHRoZSB2YWx1ZSB0byBtZXJnZS4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzcmNJbmRleCBUaGUgaW5kZXggb2YgYHNvdXJjZWAuCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBtZXJnZUZ1bmMgVGhlIGZ1bmN0aW9uIHRvIG1lcmdlIHZhbHVlcy4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIGFzc2lnbmVkIHZhbHVlcy4KICAgICAqIEBwYXJhbSB7T2JqZWN0fSBbc3RhY2tdIFRyYWNrcyB0cmF2ZXJzZWQgc291cmNlIHZhbHVlcyBhbmQgdGhlaXIgbWVyZ2VkCiAgICAgKiAgY291bnRlcnBhcnRzLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlTWVyZ2VEZWVwKG9iamVjdCwgc291cmNlLCBrZXksIHNyY0luZGV4LCBtZXJnZUZ1bmMsIGN1c3RvbWl6ZXIsIHN0YWNrKSB7CiAgICAgIHZhciBvYmpWYWx1ZSA9IF9zYWZlR2V0KG9iamVjdCwga2V5KSwKICAgICAgICAgIHNyY1ZhbHVlID0gX3NhZmVHZXQoc291cmNlLCBrZXkpLAogICAgICAgICAgc3RhY2tlZCA9IHN0YWNrLmdldChzcmNWYWx1ZSk7CgogICAgICBpZiAoc3RhY2tlZCkgewogICAgICAgIF9hc3NpZ25NZXJnZVZhbHVlKG9iamVjdCwga2V5LCBzdGFja2VkKTsKICAgICAgICByZXR1cm47CiAgICAgIH0KICAgICAgdmFyIG5ld1ZhbHVlID0gY3VzdG9taXplcgogICAgICAgID8gY3VzdG9taXplcihvYmpWYWx1ZSwgc3JjVmFsdWUsIChrZXkgKyAnJyksIG9iamVjdCwgc291cmNlLCBzdGFjaykKICAgICAgICA6IHVuZGVmaW5lZDsKCiAgICAgIHZhciBpc0NvbW1vbiA9IG5ld1ZhbHVlID09PSB1bmRlZmluZWQ7CgogICAgICBpZiAoaXNDb21tb24pIHsKICAgICAgICB2YXIgaXNBcnIgPSBpc0FycmF5XzEoc3JjVmFsdWUpLAogICAgICAgICAgICBpc0J1ZmYgPSAhaXNBcnIgJiYgaXNCdWZmZXJfMShzcmNWYWx1ZSksCiAgICAgICAgICAgIGlzVHlwZWQgPSAhaXNBcnIgJiYgIWlzQnVmZiAmJiBpc1R5cGVkQXJyYXlfMShzcmNWYWx1ZSk7CgogICAgICAgIG5ld1ZhbHVlID0gc3JjVmFsdWU7CiAgICAgICAgaWYgKGlzQXJyIHx8IGlzQnVmZiB8fCBpc1R5cGVkKSB7CiAgICAgICAgICBpZiAoaXNBcnJheV8xKG9ialZhbHVlKSkgewogICAgICAgICAgICBuZXdWYWx1ZSA9IG9ialZhbHVlOwogICAgICAgICAgfQogICAgICAgICAgZWxzZSBpZiAoaXNBcnJheUxpa2VPYmplY3RfMShvYmpWYWx1ZSkpIHsKICAgICAgICAgICAgbmV3VmFsdWUgPSBfY29weUFycmF5KG9ialZhbHVlKTsKICAgICAgICAgIH0KICAgICAgICAgIGVsc2UgaWYgKGlzQnVmZikgewogICAgICAgICAgICBpc0NvbW1vbiA9IGZhbHNlOwogICAgICAgICAgICBuZXdWYWx1ZSA9IF9jbG9uZUJ1ZmZlcihzcmNWYWx1ZSwgdHJ1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICBlbHNlIGlmIChpc1R5cGVkKSB7CiAgICAgICAgICAgIGlzQ29tbW9uID0gZmFsc2U7CiAgICAgICAgICAgIG5ld1ZhbHVlID0gX2Nsb25lVHlwZWRBcnJheShzcmNWYWx1ZSwgdHJ1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgbmV3VmFsdWUgPSBbXTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoaXNQbGFpbk9iamVjdF8xKHNyY1ZhbHVlKSB8fCBpc0FyZ3VtZW50c18xKHNyY1ZhbHVlKSkgewogICAgICAgICAgbmV3VmFsdWUgPSBvYmpWYWx1ZTsKICAgICAgICAgIGlmIChpc0FyZ3VtZW50c18xKG9ialZhbHVlKSkgewogICAgICAgICAgICBuZXdWYWx1ZSA9IHRvUGxhaW5PYmplY3RfMShvYmpWYWx1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICBlbHNlIGlmICghaXNPYmplY3RfMShvYmpWYWx1ZSkgfHwgaXNGdW5jdGlvbl8xKG9ialZhbHVlKSkgewogICAgICAgICAgICBuZXdWYWx1ZSA9IF9pbml0Q2xvbmVPYmplY3Qoc3JjVmFsdWUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgIGlzQ29tbW9uID0gZmFsc2U7CiAgICAgICAgfQogICAgICB9CiAgICAgIGlmIChpc0NvbW1vbikgewogICAgICAgIC8vIFJlY3Vyc2l2ZWx5IG1lcmdlIG9iamVjdHMgYW5kIGFycmF5cyAoc3VzY2VwdGlibGUgdG8gY2FsbCBzdGFjayBsaW1pdHMpLgogICAgICAgIHN0YWNrLnNldChzcmNWYWx1ZSwgbmV3VmFsdWUpOwogICAgICAgIG1lcmdlRnVuYyhuZXdWYWx1ZSwgc3JjVmFsdWUsIHNyY0luZGV4LCBjdXN0b21pemVyLCBzdGFjayk7CiAgICAgICAgc3RhY2tbJ2RlbGV0ZSddKHNyY1ZhbHVlKTsKICAgICAgfQogICAgICBfYXNzaWduTWVyZ2VWYWx1ZShvYmplY3QsIGtleSwgbmV3VmFsdWUpOwogICAgfQoKICAgIHZhciBfYmFzZU1lcmdlRGVlcCA9IGJhc2VNZXJnZURlZXA7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5tZXJnZWAgd2l0aG91dCBzdXBwb3J0IGZvciBtdWx0aXBsZSBzb3VyY2VzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gc291cmNlIFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICogQHBhcmFtIHtudW1iZXJ9IHNyY0luZGV4IFRoZSBpbmRleCBvZiBgc291cmNlYC4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtjdXN0b21pemVyXSBUaGUgZnVuY3Rpb24gdG8gY3VzdG9taXplIG1lcmdlZCB2YWx1ZXMuCiAgICAgKiBAcGFyYW0ge09iamVjdH0gW3N0YWNrXSBUcmFja3MgdHJhdmVyc2VkIHNvdXJjZSB2YWx1ZXMgYW5kIHRoZWlyIG1lcmdlZAogICAgICogIGNvdW50ZXJwYXJ0cy4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZU1lcmdlKG9iamVjdCwgc291cmNlLCBzcmNJbmRleCwgY3VzdG9taXplciwgc3RhY2spIHsKICAgICAgaWYgKG9iamVjdCA9PT0gc291cmNlKSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CiAgICAgIF9iYXNlRm9yKHNvdXJjZSwgZnVuY3Rpb24oc3JjVmFsdWUsIGtleSkgewogICAgICAgIHN0YWNrIHx8IChzdGFjayA9IG5ldyBfU3RhY2spOwogICAgICAgIGlmIChpc09iamVjdF8xKHNyY1ZhbHVlKSkgewogICAgICAgICAgX2Jhc2VNZXJnZURlZXAob2JqZWN0LCBzb3VyY2UsIGtleSwgc3JjSW5kZXgsIGJhc2VNZXJnZSwgY3VzdG9taXplciwgc3RhY2spOwogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgIHZhciBuZXdWYWx1ZSA9IGN1c3RvbWl6ZXIKICAgICAgICAgICAgPyBjdXN0b21pemVyKF9zYWZlR2V0KG9iamVjdCwga2V5KSwgc3JjVmFsdWUsIChrZXkgKyAnJyksIG9iamVjdCwgc291cmNlLCBzdGFjaykKICAgICAgICAgICAgOiB1bmRlZmluZWQ7CgogICAgICAgICAgaWYgKG5ld1ZhbHVlID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgbmV3VmFsdWUgPSBzcmNWYWx1ZTsKICAgICAgICAgIH0KICAgICAgICAgIF9hc3NpZ25NZXJnZVZhbHVlKG9iamVjdCwga2V5LCBuZXdWYWx1ZSk7CiAgICAgICAgfQogICAgICB9LCBrZXlzSW5fMSk7CiAgICB9CgogICAgdmFyIF9iYXNlTWVyZ2UgPSBiYXNlTWVyZ2U7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgZnVuY3Rpb24gbGlrZSBgXy5hc3NpZ25gLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBhc3NpZ25lciBUaGUgZnVuY3Rpb24gdG8gYXNzaWduIHZhbHVlcy4KICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IGFzc2lnbmVyIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVBc3NpZ25lcihhc3NpZ25lcikgewogICAgICByZXR1cm4gX2Jhc2VSZXN0KGZ1bmN0aW9uKG9iamVjdCwgc291cmNlcykgewogICAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgICBsZW5ndGggPSBzb3VyY2VzLmxlbmd0aCwKICAgICAgICAgICAgY3VzdG9taXplciA9IGxlbmd0aCA+IDEgPyBzb3VyY2VzW2xlbmd0aCAtIDFdIDogdW5kZWZpbmVkLAogICAgICAgICAgICBndWFyZCA9IGxlbmd0aCA+IDIgPyBzb3VyY2VzWzJdIDogdW5kZWZpbmVkOwoKICAgICAgICBjdXN0b21pemVyID0gKGFzc2lnbmVyLmxlbmd0aCA+IDMgJiYgdHlwZW9mIGN1c3RvbWl6ZXIgPT0gJ2Z1bmN0aW9uJykKICAgICAgICAgID8gKGxlbmd0aC0tLCBjdXN0b21pemVyKQogICAgICAgICAgOiB1bmRlZmluZWQ7CgogICAgICAgIGlmIChndWFyZCAmJiBfaXNJdGVyYXRlZUNhbGwoc291cmNlc1swXSwgc291cmNlc1sxXSwgZ3VhcmQpKSB7CiAgICAgICAgICBjdXN0b21pemVyID0gbGVuZ3RoIDwgMyA/IHVuZGVmaW5lZCA6IGN1c3RvbWl6ZXI7CiAgICAgICAgICBsZW5ndGggPSAxOwogICAgICAgIH0KICAgICAgICBvYmplY3QgPSBPYmplY3Qob2JqZWN0KTsKICAgICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgICAgdmFyIHNvdXJjZSA9IHNvdXJjZXNbaW5kZXhdOwogICAgICAgICAgaWYgKHNvdXJjZSkgewogICAgICAgICAgICBhc3NpZ25lcihvYmplY3QsIHNvdXJjZSwgaW5kZXgsIGN1c3RvbWl6ZXIpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gb2JqZWN0OwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgX2NyZWF0ZUFzc2lnbmVyID0gY3JlYXRlQXNzaWduZXI7CgogICAgLyoqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLmFzc2lnbmAgZXhjZXB0IHRoYXQgaXQgcmVjdXJzaXZlbHkgbWVyZ2VzIG93biBhbmQKICAgICAqIGluaGVyaXRlZCBlbnVtZXJhYmxlIHN0cmluZyBrZXllZCBwcm9wZXJ0aWVzIG9mIHNvdXJjZSBvYmplY3RzIGludG8gdGhlCiAgICAgKiBkZXN0aW5hdGlvbiBvYmplY3QuIFNvdXJjZSBwcm9wZXJ0aWVzIHRoYXQgcmVzb2x2ZSB0byBgdW5kZWZpbmVkYCBhcmUKICAgICAqIHNraXBwZWQgaWYgYSBkZXN0aW5hdGlvbiB2YWx1ZSBleGlzdHMuIEFycmF5IGFuZCBwbGFpbiBvYmplY3QgcHJvcGVydGllcwogICAgICogYXJlIG1lcmdlZCByZWN1cnNpdmVseS4gT3RoZXIgb2JqZWN0cyBhbmQgdmFsdWUgdHlwZXMgYXJlIG92ZXJyaWRkZW4gYnkKICAgICAqIGFzc2lnbm1lbnQuIFNvdXJjZSBvYmplY3RzIGFyZSBhcHBsaWVkIGZyb20gbGVmdCB0byByaWdodC4gU3Vic2VxdWVudAogICAgICogc291cmNlcyBvdmVyd3JpdGUgcHJvcGVydHkgYXNzaWdubWVudHMgb2YgcHJldmlvdXMgc291cmNlcy4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogVGhpcyBtZXRob2QgbXV0YXRlcyBgb2JqZWN0YC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuNS4wCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBkZXN0aW5hdGlvbiBvYmplY3QuCiAgICAgKiBAcGFyYW0gey4uLk9iamVjdH0gW3NvdXJjZXNdIFRoZSBzb3VyY2Ugb2JqZWN0cy4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciBvYmplY3QgPSB7CiAgICAgKiAgICdhJzogW3sgJ2InOiAyIH0sIHsgJ2QnOiA0IH1dCiAgICAgKiB9OwogICAgICoKICAgICAqIHZhciBvdGhlciA9IHsKICAgICAqICAgJ2EnOiBbeyAnYyc6IDMgfSwgeyAnZSc6IDUgfV0KICAgICAqIH07CiAgICAgKgogICAgICogXy5tZXJnZShvYmplY3QsIG90aGVyKTsKICAgICAqIC8vID0+IHsgJ2EnOiBbeyAnYic6IDIsICdjJzogMyB9LCB7ICdkJzogNCwgJ2UnOiA1IH1dIH0KICAgICAqLwogICAgdmFyIG1lcmdlJDMgPSBfY3JlYXRlQXNzaWduZXIoZnVuY3Rpb24ob2JqZWN0LCBzb3VyY2UsIHNyY0luZGV4KSB7CiAgICAgIF9iYXNlTWVyZ2Uob2JqZWN0LCBzb3VyY2UsIHNyY0luZGV4KTsKICAgIH0pOwoKICAgIHZhciBtZXJnZV8xID0gbWVyZ2UkMzsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLmx0YCB3aGljaCBkb2Vzbid0IGNvZXJjZSBhcmd1bWVudHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7Kn0gdmFsdWUgVGhlIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgKiBAcGFyYW0geyp9IG90aGVyIFRoZSBvdGhlciB2YWx1ZSB0byBjb21wYXJlLgogICAgICogQHJldHVybnMge2Jvb2xlYW59IFJldHVybnMgYHRydWVgIGlmIGB2YWx1ZWAgaXMgbGVzcyB0aGFuIGBvdGhlcmAsCiAgICAgKiAgZWxzZSBgZmFsc2VgLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlTHQodmFsdWUsIG90aGVyKSB7CiAgICAgIHJldHVybiB2YWx1ZSA8IG90aGVyOwogICAgfQoKICAgIHZhciBfYmFzZUx0ID0gYmFzZUx0OwoKICAgIC8qKgogICAgICogQ29tcHV0ZXMgdGhlIG1pbmltdW0gdmFsdWUgb2YgYGFycmF5YC4gSWYgYGFycmF5YCBpcyBlbXB0eSBvciBmYWxzZXksCiAgICAgKiBgdW5kZWZpbmVkYCBpcyByZXR1cm5lZC4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBtaW5pbXVtIHZhbHVlLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLm1pbihbNCwgMiwgOCwgNl0pOwogICAgICogLy8gPT4gMgogICAgICoKICAgICAqIF8ubWluKFtdKTsKICAgICAqIC8vID0+IHVuZGVmaW5lZAogICAgICovCiAgICBmdW5jdGlvbiBtaW4kNChhcnJheSkgewogICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICA/IF9iYXNlRXh0cmVtdW0oYXJyYXksIGlkZW50aXR5XzEsIF9iYXNlTHQpCiAgICAgICAgOiB1bmRlZmluZWQ7CiAgICB9CgogICAgdmFyIG1pbl8xID0gbWluJDQ7CgogICAgLyoqCiAgICAgKiBUaGlzIG1ldGhvZCBpcyBsaWtlIGBfLm1pbmAgZXhjZXB0IHRoYXQgaXQgYWNjZXB0cyBgaXRlcmF0ZWVgIHdoaWNoIGlzCiAgICAgKiBpbnZva2VkIGZvciBlYWNoIGVsZW1lbnQgaW4gYGFycmF5YCB0byBnZW5lcmF0ZSB0aGUgY3JpdGVyaW9uIGJ5IHdoaWNoCiAgICAgKiB0aGUgdmFsdWUgaXMgcmFua2VkLiBUaGUgaXRlcmF0ZWUgaXMgaW52b2tlZCB3aXRoIG9uZSBhcmd1bWVudDogKHZhbHVlKS4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDQuMC4wCiAgICAgKiBAY2F0ZWdvcnkgTWF0aAogICAgICogQHBhcmFtIHtBcnJheX0gYXJyYXkgVGhlIGFycmF5IHRvIGl0ZXJhdGUgb3Zlci4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IFtpdGVyYXRlZT1fLmlkZW50aXR5XSBUaGUgaXRlcmF0ZWUgaW52b2tlZCBwZXIgZWxlbWVudC4KICAgICAqIEByZXR1cm5zIHsqfSBSZXR1cm5zIHRoZSBtaW5pbXVtIHZhbHVlLgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgb2JqZWN0cyA9IFt7ICduJzogMSB9LCB7ICduJzogMiB9XTsKICAgICAqCiAgICAgKiBfLm1pbkJ5KG9iamVjdHMsIGZ1bmN0aW9uKG8pIHsgcmV0dXJuIG8ubjsgfSk7CiAgICAgKiAvLyA9PiB7ICduJzogMSB9CiAgICAgKgogICAgICogLy8gVGhlIGBfLnByb3BlcnR5YCBpdGVyYXRlZSBzaG9ydGhhbmQuCiAgICAgKiBfLm1pbkJ5KG9iamVjdHMsICduJyk7CiAgICAgKiAvLyA9PiB7ICduJzogMSB9CiAgICAgKi8KICAgIGZ1bmN0aW9uIG1pbkJ5KGFycmF5LCBpdGVyYXRlZSkgewogICAgICByZXR1cm4gKGFycmF5ICYmIGFycmF5Lmxlbmd0aCkKICAgICAgICA/IF9iYXNlRXh0cmVtdW0oYXJyYXksIF9iYXNlSXRlcmF0ZWUoaXRlcmF0ZWUpLCBfYmFzZUx0KQogICAgICAgIDogdW5kZWZpbmVkOwogICAgfQoKICAgIHZhciBtaW5CeV8xID0gbWluQnk7CgogICAgLyoqCiAgICAgKiBHZXRzIHRoZSB0aW1lc3RhbXAgb2YgdGhlIG51bWJlciBvZiBtaWxsaXNlY29uZHMgdGhhdCBoYXZlIGVsYXBzZWQgc2luY2UKICAgICAqIHRoZSBVbml4IGVwb2NoICgxIEphbnVhcnkgMTk3MCAwMDowMDowMCBVVEMpLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMi40LjAKICAgICAqIEBjYXRlZ29yeSBEYXRlCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSB0aW1lc3RhbXAuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uZGVmZXIoZnVuY3Rpb24oc3RhbXApIHsKICAgICAqICAgY29uc29sZS5sb2coXy5ub3coKSAtIHN0YW1wKTsKICAgICAqIH0sIF8ubm93KCkpOwogICAgICogLy8gPT4gTG9ncyB0aGUgbnVtYmVyIG9mIG1pbGxpc2Vjb25kcyBpdCB0b29rIGZvciB0aGUgZGVmZXJyZWQgaW52b2NhdGlvbi4KICAgICAqLwogICAgdmFyIG5vdyQ2ID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBfcm9vdC5EYXRlLm5vdygpOwogICAgfTsKCiAgICB2YXIgbm93XzEgPSBub3ckNjsKCiAgICAvKioKICAgICAqIFRoZSBiYXNlIGltcGxlbWVudGF0aW9uIG9mIGBfLnNldGAuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBtb2RpZnkuCiAgICAgKiBAcGFyYW0ge0FycmF5fHN0cmluZ30gcGF0aCBUaGUgcGF0aCBvZiB0aGUgcHJvcGVydHkgdG8gc2V0LgogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gc2V0LgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gW2N1c3RvbWl6ZXJdIFRoZSBmdW5jdGlvbiB0byBjdXN0b21pemUgcGF0aCBjcmVhdGlvbi4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgYG9iamVjdGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VTZXQob2JqZWN0LCBwYXRoLCB2YWx1ZSwgY3VzdG9taXplcikgewogICAgICBpZiAoIWlzT2JqZWN0XzEob2JqZWN0KSkgewogICAgICAgIHJldHVybiBvYmplY3Q7CiAgICAgIH0KICAgICAgcGF0aCA9IF9jYXN0UGF0aChwYXRoLCBvYmplY3QpOwoKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBsZW5ndGggPSBwYXRoLmxlbmd0aCwKICAgICAgICAgIGxhc3RJbmRleCA9IGxlbmd0aCAtIDEsCiAgICAgICAgICBuZXN0ZWQgPSBvYmplY3Q7CgogICAgICB3aGlsZSAobmVzdGVkICE9IG51bGwgJiYgKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHZhciBrZXkgPSBfdG9LZXkocGF0aFtpbmRleF0pLAogICAgICAgICAgICBuZXdWYWx1ZSA9IHZhbHVlOwoKICAgICAgICBpZiAoaW5kZXggIT0gbGFzdEluZGV4KSB7CiAgICAgICAgICB2YXIgb2JqVmFsdWUgPSBuZXN0ZWRba2V5XTsKICAgICAgICAgIG5ld1ZhbHVlID0gY3VzdG9taXplciA/IGN1c3RvbWl6ZXIob2JqVmFsdWUsIGtleSwgbmVzdGVkKSA6IHVuZGVmaW5lZDsKICAgICAgICAgIGlmIChuZXdWYWx1ZSA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgIG5ld1ZhbHVlID0gaXNPYmplY3RfMShvYmpWYWx1ZSkKICAgICAgICAgICAgICA/IG9ialZhbHVlCiAgICAgICAgICAgICAgOiAoX2lzSW5kZXgocGF0aFtpbmRleCArIDFdKSA/IFtdIDoge30pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfYXNzaWduVmFsdWUobmVzdGVkLCBrZXksIG5ld1ZhbHVlKTsKICAgICAgICBuZXN0ZWQgPSBuZXN0ZWRba2V5XTsKICAgICAgfQogICAgICByZXR1cm4gb2JqZWN0OwogICAgfQoKICAgIHZhciBfYmFzZVNldCA9IGJhc2VTZXQ7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiAgYF8ucGlja0J5YCB3aXRob3V0IHN1cHBvcnQgZm9yIGl0ZXJhdGVlIHNob3J0aGFuZHMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIHNvdXJjZSBvYmplY3QuCiAgICAgKiBAcGFyYW0ge3N0cmluZ1tdfSBwYXRocyBUaGUgcHJvcGVydHkgcGF0aHMgdG8gcGljay4KICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IHByZWRpY2F0ZSBUaGUgZnVuY3Rpb24gaW52b2tlZCBwZXIgcHJvcGVydHkuCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgb2JqZWN0LgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlUGlja0J5KG9iamVjdCwgcGF0aHMsIHByZWRpY2F0ZSkgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IHBhdGhzLmxlbmd0aCwKICAgICAgICAgIHJlc3VsdCA9IHt9OwoKICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICB2YXIgcGF0aCA9IHBhdGhzW2luZGV4XSwKICAgICAgICAgICAgdmFsdWUgPSBfYmFzZUdldChvYmplY3QsIHBhdGgpOwoKICAgICAgICBpZiAocHJlZGljYXRlKHZhbHVlLCBwYXRoKSkgewogICAgICAgICAgX2Jhc2VTZXQocmVzdWx0LCBfY2FzdFBhdGgocGF0aCwgb2JqZWN0KSwgdmFsdWUpOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIHZhciBfYmFzZVBpY2tCeSA9IGJhc2VQaWNrQnk7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5waWNrYCB3aXRob3V0IHN1cHBvcnQgZm9yIGluZGl2aWR1YWwKICAgICAqIHByb3BlcnR5IGlkZW50aWZpZXJzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICogQHBhcmFtIHtzdHJpbmdbXX0gcGF0aHMgVGhlIHByb3BlcnR5IHBhdGhzIHRvIHBpY2suCiAgICAgKiBAcmV0dXJucyB7T2JqZWN0fSBSZXR1cm5zIHRoZSBuZXcgb2JqZWN0LgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlUGljayhvYmplY3QsIHBhdGhzKSB7CiAgICAgIHJldHVybiBfYmFzZVBpY2tCeShvYmplY3QsIHBhdGhzLCBmdW5jdGlvbih2YWx1ZSwgcGF0aCkgewogICAgICAgIHJldHVybiBoYXNJbl8xKG9iamVjdCwgcGF0aCk7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBfYmFzZVBpY2sgPSBiYXNlUGljazsKCiAgICAvKioKICAgICAqIEEgc3BlY2lhbGl6ZWQgdmVyc2lvbiBvZiBgYmFzZVJlc3RgIHdoaWNoIGZsYXR0ZW5zIHRoZSByZXN0IGFycmF5LgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdW5jIFRoZSBmdW5jdGlvbiB0byBhcHBseSBhIHJlc3QgcGFyYW1ldGVyIHRvLgogICAgICogQHJldHVybnMge0Z1bmN0aW9ufSBSZXR1cm5zIHRoZSBuZXcgZnVuY3Rpb24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZsYXRSZXN0KGZ1bmMpIHsKICAgICAgcmV0dXJuIF9zZXRUb1N0cmluZyhfb3ZlclJlc3QoZnVuYywgdW5kZWZpbmVkLCBmbGF0dGVuXzEpLCBmdW5jICsgJycpOwogICAgfQoKICAgIHZhciBfZmxhdFJlc3QgPSBmbGF0UmVzdDsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYW4gb2JqZWN0IGNvbXBvc2VkIG9mIHRoZSBwaWNrZWQgYG9iamVjdGAgcHJvcGVydGllcy4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAY2F0ZWdvcnkgT2JqZWN0CiAgICAgKiBAcGFyYW0ge09iamVjdH0gb2JqZWN0IFRoZSBzb3VyY2Ugb2JqZWN0LgogICAgICogQHBhcmFtIHsuLi4oc3RyaW5nfHN0cmluZ1tdKX0gW3BhdGhzXSBUaGUgcHJvcGVydHkgcGF0aHMgdG8gcGljay4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIHZhciBvYmplY3QgPSB7ICdhJzogMSwgJ2InOiAnMicsICdjJzogMyB9OwogICAgICoKICAgICAqIF8ucGljayhvYmplY3QsIFsnYScsICdjJ10pOwogICAgICogLy8gPT4geyAnYSc6IDEsICdjJzogMyB9CiAgICAgKi8KICAgIHZhciBwaWNrID0gX2ZsYXRSZXN0KGZ1bmN0aW9uKG9iamVjdCwgcGF0aHMpIHsKICAgICAgcmV0dXJuIG9iamVjdCA9PSBudWxsID8ge30gOiBfYmFzZVBpY2sob2JqZWN0LCBwYXRocyk7CiAgICB9KTsKCiAgICB2YXIgcGlja18xID0gcGljazsKCiAgICAvKiBCdWlsdC1pbiBtZXRob2QgcmVmZXJlbmNlcyBmb3IgdGhvc2Ugd2l0aCB0aGUgc2FtZSBuYW1lIGFzIG90aGVyIGBsb2Rhc2hgIG1ldGhvZHMuICovCiAgICB2YXIgbmF0aXZlQ2VpbCA9IE1hdGguY2VpbCwKICAgICAgICBuYXRpdmVNYXgkMiA9IE1hdGgubWF4OwoKICAgIC8qKgogICAgICogVGhlIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8ucmFuZ2VgIGFuZCBgXy5yYW5nZVJpZ2h0YCB3aGljaCBkb2Vzbid0CiAgICAgKiBjb2VyY2UgYXJndW1lbnRzLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge251bWJlcn0gc3RhcnQgVGhlIHN0YXJ0IG9mIHRoZSByYW5nZS4KICAgICAqIEBwYXJhbSB7bnVtYmVyfSBlbmQgVGhlIGVuZCBvZiB0aGUgcmFuZ2UuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gc3RlcCBUaGUgdmFsdWUgdG8gaW5jcmVtZW50IG9yIGRlY3JlbWVudCBieS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2Zyb21SaWdodF0gU3BlY2lmeSBpdGVyYXRpbmcgZnJvbSByaWdodCB0byBsZWZ0LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSByYW5nZSBvZiBudW1iZXJzLgogICAgICovCiAgICBmdW5jdGlvbiBiYXNlUmFuZ2Uoc3RhcnQsIGVuZCwgc3RlcCwgZnJvbVJpZ2h0KSB7CiAgICAgIHZhciBpbmRleCA9IC0xLAogICAgICAgICAgbGVuZ3RoID0gbmF0aXZlTWF4JDIobmF0aXZlQ2VpbCgoZW5kIC0gc3RhcnQpIC8gKHN0ZXAgfHwgMSkpLCAwKSwKICAgICAgICAgIHJlc3VsdCA9IEFycmF5KGxlbmd0aCk7CgogICAgICB3aGlsZSAobGVuZ3RoLS0pIHsKICAgICAgICByZXN1bHRbZnJvbVJpZ2h0ID8gbGVuZ3RoIDogKytpbmRleF0gPSBzdGFydDsKICAgICAgICBzdGFydCArPSBzdGVwOwogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9iYXNlUmFuZ2UgPSBiYXNlUmFuZ2U7CgogICAgLyoqCiAgICAgKiBDcmVhdGVzIGEgYF8ucmFuZ2VgIG9yIGBfLnJhbmdlUmlnaHRgIGZ1bmN0aW9uLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IFtmcm9tUmlnaHRdIFNwZWNpZnkgaXRlcmF0aW5nIGZyb20gcmlnaHQgdG8gbGVmdC4KICAgICAqIEByZXR1cm5zIHtGdW5jdGlvbn0gUmV0dXJucyB0aGUgbmV3IHJhbmdlIGZ1bmN0aW9uLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVSYW5nZShmcm9tUmlnaHQpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKHN0YXJ0LCBlbmQsIHN0ZXApIHsKICAgICAgICBpZiAoc3RlcCAmJiB0eXBlb2Ygc3RlcCAhPSAnbnVtYmVyJyAmJiBfaXNJdGVyYXRlZUNhbGwoc3RhcnQsIGVuZCwgc3RlcCkpIHsKICAgICAgICAgIGVuZCA9IHN0ZXAgPSB1bmRlZmluZWQ7CiAgICAgICAgfQogICAgICAgIC8vIEVuc3VyZSB0aGUgc2lnbiBvZiBgLTBgIGlzIHByZXNlcnZlZC4KICAgICAgICBzdGFydCA9IHRvRmluaXRlXzEoc3RhcnQpOwogICAgICAgIGlmIChlbmQgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgZW5kID0gc3RhcnQ7CiAgICAgICAgICBzdGFydCA9IDA7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGVuZCA9IHRvRmluaXRlXzEoZW5kKTsKICAgICAgICB9CiAgICAgICAgc3RlcCA9IHN0ZXAgPT09IHVuZGVmaW5lZCA/IChzdGFydCA8IGVuZCA/IDEgOiAtMSkgOiB0b0Zpbml0ZV8xKHN0ZXApOwogICAgICAgIHJldHVybiBfYmFzZVJhbmdlKHN0YXJ0LCBlbmQsIHN0ZXAsIGZyb21SaWdodCk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIF9jcmVhdGVSYW5nZSA9IGNyZWF0ZVJhbmdlOwoKICAgIC8qKgogICAgICogQ3JlYXRlcyBhbiBhcnJheSBvZiBudW1iZXJzIChwb3NpdGl2ZSBhbmQvb3IgbmVnYXRpdmUpIHByb2dyZXNzaW5nIGZyb20KICAgICAqIGBzdGFydGAgdXAgdG8sIGJ1dCBub3QgaW5jbHVkaW5nLCBgZW5kYC4gQSBzdGVwIG9mIGAtMWAgaXMgdXNlZCBpZiBhIG5lZ2F0aXZlCiAgICAgKiBgc3RhcnRgIGlzIHNwZWNpZmllZCB3aXRob3V0IGFuIGBlbmRgIG9yIGBzdGVwYC4gSWYgYGVuZGAgaXMgbm90IHNwZWNpZmllZCwKICAgICAqIGl0J3Mgc2V0IHRvIGBzdGFydGAgd2l0aCBgc3RhcnRgIHRoZW4gc2V0IHRvIGAwYC4KICAgICAqCiAgICAgKiAqKk5vdGU6KiogSmF2YVNjcmlwdCBmb2xsb3dzIHRoZSBJRUVFLTc1NCBzdGFuZGFyZCBmb3IgcmVzb2x2aW5nCiAgICAgKiBmbG9hdGluZy1wb2ludCB2YWx1ZXMgd2hpY2ggY2FuIHByb2R1Y2UgdW5leHBlY3RlZCByZXN1bHRzLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBzaW5jZSAwLjEuMAogICAgICogQG1lbWJlck9mIF8KICAgICAqIEBjYXRlZ29yeSBVdGlsCiAgICAgKiBAcGFyYW0ge251bWJlcn0gW3N0YXJ0PTBdIFRoZSBzdGFydCBvZiB0aGUgcmFuZ2UuCiAgICAgKiBAcGFyYW0ge251bWJlcn0gZW5kIFRoZSBlbmQgb2YgdGhlIHJhbmdlLgogICAgICogQHBhcmFtIHtudW1iZXJ9IFtzdGVwPTFdIFRoZSB2YWx1ZSB0byBpbmNyZW1lbnQgb3IgZGVjcmVtZW50IGJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSByYW5nZSBvZiBudW1iZXJzLgogICAgICogQHNlZSBfLmluUmFuZ2UsIF8ucmFuZ2VSaWdodAogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLnJhbmdlKDQpOwogICAgICogLy8gPT4gWzAsIDEsIDIsIDNdCiAgICAgKgogICAgICogXy5yYW5nZSgtNCk7CiAgICAgKiAvLyA9PiBbMCwgLTEsIC0yLCAtM10KICAgICAqCiAgICAgKiBfLnJhbmdlKDEsIDUpOwogICAgICogLy8gPT4gWzEsIDIsIDMsIDRdCiAgICAgKgogICAgICogXy5yYW5nZSgwLCAyMCwgNSk7CiAgICAgKiAvLyA9PiBbMCwgNSwgMTAsIDE1XQogICAgICoKICAgICAqIF8ucmFuZ2UoMCwgLTQsIC0xKTsKICAgICAqIC8vID0+IFswLCAtMSwgLTIsIC0zXQogICAgICoKICAgICAqIF8ucmFuZ2UoMSwgNCwgMCk7CiAgICAgKiAvLyA9PiBbMSwgMSwgMV0KICAgICAqCiAgICAgKiBfLnJhbmdlKDApOwogICAgICogLy8gPT4gW10KICAgICAqLwogICAgdmFyIHJhbmdlJDUgPSBfY3JlYXRlUmFuZ2UoKTsKCiAgICB2YXIgcmFuZ2VfMSA9IHJhbmdlJDU7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5zb3J0QnlgIHdoaWNoIHVzZXMgYGNvbXBhcmVyYCB0byBkZWZpbmUgdGhlCiAgICAgKiBzb3J0IG9yZGVyIG9mIGBhcnJheWAgYW5kIHJlcGxhY2VzIGNyaXRlcmlhIG9iamVjdHMgd2l0aCB0aGVpciBjb3JyZXNwb25kaW5nCiAgICAgKiB2YWx1ZXMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IGFycmF5IFRoZSBhcnJheSB0byBzb3J0LgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gY29tcGFyZXIgVGhlIGZ1bmN0aW9uIHRvIGRlZmluZSBzb3J0IG9yZGVyLgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIGBhcnJheWAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VTb3J0QnkoYXJyYXksIGNvbXBhcmVyKSB7CiAgICAgIHZhciBsZW5ndGggPSBhcnJheS5sZW5ndGg7CgogICAgICBhcnJheS5zb3J0KGNvbXBhcmVyKTsKICAgICAgd2hpbGUgKGxlbmd0aC0tKSB7CiAgICAgICAgYXJyYXlbbGVuZ3RoXSA9IGFycmF5W2xlbmd0aF0udmFsdWU7CiAgICAgIH0KICAgICAgcmV0dXJuIGFycmF5OwogICAgfQoKICAgIHZhciBfYmFzZVNvcnRCeSA9IGJhc2VTb3J0Qnk7CgogICAgLyoqCiAgICAgKiBDb21wYXJlcyB2YWx1ZXMgdG8gc29ydCB0aGVtIGluIGFzY2VuZGluZyBvcmRlci4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHsqfSB2YWx1ZSBUaGUgdmFsdWUgdG8gY29tcGFyZS4KICAgICAqIEBwYXJhbSB7Kn0gb3RoZXIgVGhlIG90aGVyIHZhbHVlIHRvIGNvbXBhcmUuCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzb3J0IG9yZGVyIGluZGljYXRvciBmb3IgYHZhbHVlYC4KICAgICAqLwogICAgZnVuY3Rpb24gY29tcGFyZUFzY2VuZGluZyh2YWx1ZSwgb3RoZXIpIHsKICAgICAgaWYgKHZhbHVlICE9PSBvdGhlcikgewogICAgICAgIHZhciB2YWxJc0RlZmluZWQgPSB2YWx1ZSAhPT0gdW5kZWZpbmVkLAogICAgICAgICAgICB2YWxJc051bGwgPSB2YWx1ZSA9PT0gbnVsbCwKICAgICAgICAgICAgdmFsSXNSZWZsZXhpdmUgPSB2YWx1ZSA9PT0gdmFsdWUsCiAgICAgICAgICAgIHZhbElzU3ltYm9sID0gaXNTeW1ib2xfMSh2YWx1ZSk7CgogICAgICAgIHZhciBvdGhJc0RlZmluZWQgPSBvdGhlciAhPT0gdW5kZWZpbmVkLAogICAgICAgICAgICBvdGhJc051bGwgPSBvdGhlciA9PT0gbnVsbCwKICAgICAgICAgICAgb3RoSXNSZWZsZXhpdmUgPSBvdGhlciA9PT0gb3RoZXIsCiAgICAgICAgICAgIG90aElzU3ltYm9sID0gaXNTeW1ib2xfMShvdGhlcik7CgogICAgICAgIGlmICgoIW90aElzTnVsbCAmJiAhb3RoSXNTeW1ib2wgJiYgIXZhbElzU3ltYm9sICYmIHZhbHVlID4gb3RoZXIpIHx8CiAgICAgICAgICAgICh2YWxJc1N5bWJvbCAmJiBvdGhJc0RlZmluZWQgJiYgb3RoSXNSZWZsZXhpdmUgJiYgIW90aElzTnVsbCAmJiAhb3RoSXNTeW1ib2wpIHx8CiAgICAgICAgICAgICh2YWxJc051bGwgJiYgb3RoSXNEZWZpbmVkICYmIG90aElzUmVmbGV4aXZlKSB8fAogICAgICAgICAgICAoIXZhbElzRGVmaW5lZCAmJiBvdGhJc1JlZmxleGl2ZSkgfHwKICAgICAgICAgICAgIXZhbElzUmVmbGV4aXZlKSB7CiAgICAgICAgICByZXR1cm4gMTsKICAgICAgICB9CiAgICAgICAgaWYgKCghdmFsSXNOdWxsICYmICF2YWxJc1N5bWJvbCAmJiAhb3RoSXNTeW1ib2wgJiYgdmFsdWUgPCBvdGhlcikgfHwKICAgICAgICAgICAgKG90aElzU3ltYm9sICYmIHZhbElzRGVmaW5lZCAmJiB2YWxJc1JlZmxleGl2ZSAmJiAhdmFsSXNOdWxsICYmICF2YWxJc1N5bWJvbCkgfHwKICAgICAgICAgICAgKG90aElzTnVsbCAmJiB2YWxJc0RlZmluZWQgJiYgdmFsSXNSZWZsZXhpdmUpIHx8CiAgICAgICAgICAgICghb3RoSXNEZWZpbmVkICYmIHZhbElzUmVmbGV4aXZlKSB8fAogICAgICAgICAgICAhb3RoSXNSZWZsZXhpdmUpIHsKICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIDA7CiAgICB9CgogICAgdmFyIF9jb21wYXJlQXNjZW5kaW5nID0gY29tcGFyZUFzY2VuZGluZzsKCiAgICAvKioKICAgICAqIFVzZWQgYnkgYF8ub3JkZXJCeWAgdG8gY29tcGFyZSBtdWx0aXBsZSBwcm9wZXJ0aWVzIG9mIGEgdmFsdWUgdG8gYW5vdGhlcgogICAgICogYW5kIHN0YWJsZSBzb3J0IHRoZW0uCiAgICAgKgogICAgICogSWYgYG9yZGVyc2AgaXMgdW5zcGVjaWZpZWQsIGFsbCB2YWx1ZXMgYXJlIHNvcnRlZCBpbiBhc2NlbmRpbmcgb3JkZXIuIE90aGVyd2lzZSwKICAgICAqIHNwZWNpZnkgYW4gb3JkZXIgb2YgImRlc2MiIGZvciBkZXNjZW5kaW5nIG9yICJhc2MiIGZvciBhc2NlbmRpbmcgc29ydCBvcmRlcgogICAgICogb2YgY29ycmVzcG9uZGluZyB2YWx1ZXMuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvYmplY3QgVGhlIG9iamVjdCB0byBjb21wYXJlLgogICAgICogQHBhcmFtIHtPYmplY3R9IG90aGVyIFRoZSBvdGhlciBvYmplY3QgdG8gY29tcGFyZS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbltdfHN0cmluZ1tdfSBvcmRlcnMgVGhlIG9yZGVyIHRvIHNvcnQgYnkgZm9yIGVhY2ggcHJvcGVydHkuCiAgICAgKiBAcmV0dXJucyB7bnVtYmVyfSBSZXR1cm5zIHRoZSBzb3J0IG9yZGVyIGluZGljYXRvciBmb3IgYG9iamVjdGAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNvbXBhcmVNdWx0aXBsZShvYmplY3QsIG90aGVyLCBvcmRlcnMpIHsKICAgICAgdmFyIGluZGV4ID0gLTEsCiAgICAgICAgICBvYmpDcml0ZXJpYSA9IG9iamVjdC5jcml0ZXJpYSwKICAgICAgICAgIG90aENyaXRlcmlhID0gb3RoZXIuY3JpdGVyaWEsCiAgICAgICAgICBsZW5ndGggPSBvYmpDcml0ZXJpYS5sZW5ndGgsCiAgICAgICAgICBvcmRlcnNMZW5ndGggPSBvcmRlcnMubGVuZ3RoOwoKICAgICAgd2hpbGUgKCsraW5kZXggPCBsZW5ndGgpIHsKICAgICAgICB2YXIgcmVzdWx0ID0gX2NvbXBhcmVBc2NlbmRpbmcob2JqQ3JpdGVyaWFbaW5kZXhdLCBvdGhDcml0ZXJpYVtpbmRleF0pOwogICAgICAgIGlmIChyZXN1bHQpIHsKICAgICAgICAgIGlmIChpbmRleCA+PSBvcmRlcnNMZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgICAgICAgIH0KICAgICAgICAgIHZhciBvcmRlciA9IG9yZGVyc1tpbmRleF07CiAgICAgICAgICByZXR1cm4gcmVzdWx0ICogKG9yZGVyID09ICdkZXNjJyA/IC0xIDogMSk7CiAgICAgICAgfQogICAgICB9CiAgICAgIC8vIEZpeGVzIGFuIGBBcnJheSNzb3J0YCBidWcgaW4gdGhlIEpTIGVuZ2luZSBlbWJlZGRlZCBpbiBBZG9iZSBhcHBsaWNhdGlvbnMKICAgICAgLy8gdGhhdCBjYXVzZXMgaXQsIHVuZGVyIGNlcnRhaW4gY2lyY3Vtc3RhbmNlcywgdG8gcHJvdmlkZSB0aGUgc2FtZSB2YWx1ZSBmb3IKICAgICAgLy8gYG9iamVjdGAgYW5kIGBvdGhlcmAuIFNlZSBodHRwczovL2dpdGh1Yi5jb20vamFzaGtlbmFzL3VuZGVyc2NvcmUvcHVsbC8xMjQ3CiAgICAgIC8vIGZvciBtb3JlIGRldGFpbHMuCiAgICAgIC8vCiAgICAgIC8vIFRoaXMgYWxzbyBlbnN1cmVzIGEgc3RhYmxlIHNvcnQgaW4gVjggYW5kIG90aGVyIGVuZ2luZXMuCiAgICAgIC8vIFNlZSBodHRwczovL2J1Z3MuY2hyb21pdW0ub3JnL3AvdjgvaXNzdWVzL2RldGFpbD9pZD05MCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICByZXR1cm4gb2JqZWN0LmluZGV4IC0gb3RoZXIuaW5kZXg7CiAgICB9CgogICAgdmFyIF9jb21wYXJlTXVsdGlwbGUgPSBjb21wYXJlTXVsdGlwbGU7CgogICAgLyoqCiAgICAgKiBUaGUgYmFzZSBpbXBsZW1lbnRhdGlvbiBvZiBgXy5vcmRlckJ5YCB3aXRob3V0IHBhcmFtIGd1YXJkcy4KICAgICAqCiAgICAgKiBAcHJpdmF0ZQogICAgICogQHBhcmFtIHtBcnJheXxPYmplY3R9IGNvbGxlY3Rpb24gVGhlIGNvbGxlY3Rpb24gdG8gaXRlcmF0ZSBvdmVyLgogICAgICogQHBhcmFtIHtGdW5jdGlvbltdfE9iamVjdFtdfHN0cmluZ1tdfSBpdGVyYXRlZXMgVGhlIGl0ZXJhdGVlcyB0byBzb3J0IGJ5LgogICAgICogQHBhcmFtIHtzdHJpbmdbXX0gb3JkZXJzIFRoZSBzb3J0IG9yZGVycyBvZiBgaXRlcmF0ZWVzYC4KICAgICAqIEByZXR1cm5zIHtBcnJheX0gUmV0dXJucyB0aGUgbmV3IHNvcnRlZCBhcnJheS4KICAgICAqLwogICAgZnVuY3Rpb24gYmFzZU9yZGVyQnkoY29sbGVjdGlvbiwgaXRlcmF0ZWVzLCBvcmRlcnMpIHsKICAgICAgdmFyIGluZGV4ID0gLTE7CiAgICAgIGl0ZXJhdGVlcyA9IF9hcnJheU1hcChpdGVyYXRlZXMubGVuZ3RoID8gaXRlcmF0ZWVzIDogW2lkZW50aXR5XzFdLCBfYmFzZVVuYXJ5KF9iYXNlSXRlcmF0ZWUpKTsKCiAgICAgIHZhciByZXN1bHQgPSBfYmFzZU1hcChjb2xsZWN0aW9uLCBmdW5jdGlvbih2YWx1ZSwga2V5LCBjb2xsZWN0aW9uKSB7CiAgICAgICAgdmFyIGNyaXRlcmlhID0gX2FycmF5TWFwKGl0ZXJhdGVlcywgZnVuY3Rpb24oaXRlcmF0ZWUpIHsKICAgICAgICAgIHJldHVybiBpdGVyYXRlZSh2YWx1ZSk7CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIHsgJ2NyaXRlcmlhJzogY3JpdGVyaWEsICdpbmRleCc6ICsraW5kZXgsICd2YWx1ZSc6IHZhbHVlIH07CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIF9iYXNlU29ydEJ5KHJlc3VsdCwgZnVuY3Rpb24ob2JqZWN0LCBvdGhlcikgewogICAgICAgIHJldHVybiBfY29tcGFyZU11bHRpcGxlKG9iamVjdCwgb3RoZXIsIG9yZGVycyk7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBfYmFzZU9yZGVyQnkgPSBiYXNlT3JkZXJCeTsKCiAgICAvKioKICAgICAqIENyZWF0ZXMgYW4gYXJyYXkgb2YgZWxlbWVudHMsIHNvcnRlZCBpbiBhc2NlbmRpbmcgb3JkZXIgYnkgdGhlIHJlc3VsdHMgb2YKICAgICAqIHJ1bm5pbmcgZWFjaCBlbGVtZW50IGluIGEgY29sbGVjdGlvbiB0aHJ1IGVhY2ggaXRlcmF0ZWUuIFRoaXMgbWV0aG9kCiAgICAgKiBwZXJmb3JtcyBhIHN0YWJsZSBzb3J0LCB0aGF0IGlzLCBpdCBwcmVzZXJ2ZXMgdGhlIG9yaWdpbmFsIHNvcnQgb3JkZXIgb2YKICAgICAqIGVxdWFsIGVsZW1lbnRzLiBUaGUgaXRlcmF0ZWVzIGFyZSBpbnZva2VkIHdpdGggb25lIGFyZ3VtZW50OiAodmFsdWUpLgogICAgICoKICAgICAqIEBzdGF0aWMKICAgICAqIEBtZW1iZXJPZiBfCiAgICAgKiBAc2luY2UgMC4xLjAKICAgICAqIEBjYXRlZ29yeSBDb2xsZWN0aW9uCiAgICAgKiBAcGFyYW0ge0FycmF5fE9iamVjdH0gY29sbGVjdGlvbiBUaGUgY29sbGVjdGlvbiB0byBpdGVyYXRlIG92ZXIuCiAgICAgKiBAcGFyYW0gey4uLihGdW5jdGlvbnxGdW5jdGlvbltdKX0gW2l0ZXJhdGVlcz1bXy5pZGVudGl0eV1dCiAgICAgKiAgVGhlIGl0ZXJhdGVlcyB0byBzb3J0IGJ5LgogICAgICogQHJldHVybnMge0FycmF5fSBSZXR1cm5zIHRoZSBuZXcgc29ydGVkIGFycmF5LgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiB2YXIgdXNlcnMgPSBbCiAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgJ2FnZSc6IDQ4IH0sCiAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FnZSc6IDM2IH0sCiAgICAgKiAgIHsgJ3VzZXInOiAnZnJlZCcsICAgJ2FnZSc6IDQwIH0sCiAgICAgKiAgIHsgJ3VzZXInOiAnYmFybmV5JywgJ2FnZSc6IDM0IH0KICAgICAqIF07CiAgICAgKgogICAgICogXy5zb3J0QnkodXNlcnMsIFtmdW5jdGlvbihvKSB7IHJldHVybiBvLnVzZXI7IH1dKTsKICAgICAqIC8vID0+IG9iamVjdHMgZm9yIFtbJ2Jhcm5leScsIDM2XSwgWydiYXJuZXknLCAzNF0sIFsnZnJlZCcsIDQ4XSwgWydmcmVkJywgNDBdXQogICAgICoKICAgICAqIF8uc29ydEJ5KHVzZXJzLCBbJ3VzZXInLCAnYWdlJ10pOwogICAgICogLy8gPT4gb2JqZWN0cyBmb3IgW1snYmFybmV5JywgMzRdLCBbJ2Jhcm5leScsIDM2XSwgWydmcmVkJywgNDBdLCBbJ2ZyZWQnLCA0OF1dCiAgICAgKi8KICAgIHZhciBzb3J0QnkgPSBfYmFzZVJlc3QoZnVuY3Rpb24oY29sbGVjdGlvbiwgaXRlcmF0ZWVzKSB7CiAgICAgIGlmIChjb2xsZWN0aW9uID09IG51bGwpIHsKICAgICAgICByZXR1cm4gW107CiAgICAgIH0KICAgICAgdmFyIGxlbmd0aCA9IGl0ZXJhdGVlcy5sZW5ndGg7CiAgICAgIGlmIChsZW5ndGggPiAxICYmIF9pc0l0ZXJhdGVlQ2FsbChjb2xsZWN0aW9uLCBpdGVyYXRlZXNbMF0sIGl0ZXJhdGVlc1sxXSkpIHsKICAgICAgICBpdGVyYXRlZXMgPSBbXTsKICAgICAgfSBlbHNlIGlmIChsZW5ndGggPiAyICYmIF9pc0l0ZXJhdGVlQ2FsbChpdGVyYXRlZXNbMF0sIGl0ZXJhdGVlc1sxXSwgaXRlcmF0ZWVzWzJdKSkgewogICAgICAgIGl0ZXJhdGVlcyA9IFtpdGVyYXRlZXNbMF1dOwogICAgICB9CiAgICAgIHJldHVybiBfYmFzZU9yZGVyQnkoY29sbGVjdGlvbiwgX2Jhc2VGbGF0dGVuKGl0ZXJhdGVlcywgMSksIFtdKTsKICAgIH0pOwoKICAgIHZhciBzb3J0QnlfMSA9IHNvcnRCeTsKCiAgICAvKiogVXNlZCB0byBnZW5lcmF0ZSB1bmlxdWUgSURzLiAqLwogICAgdmFyIGlkQ291bnRlciA9IDA7CgogICAgLyoqCiAgICAgKiBHZW5lcmF0ZXMgYSB1bmlxdWUgSUQuIElmIGBwcmVmaXhgIGlzIGdpdmVuLCB0aGUgSUQgaXMgYXBwZW5kZWQgdG8gaXQuCiAgICAgKgogICAgICogQHN0YXRpYwogICAgICogQHNpbmNlIDAuMS4wCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQGNhdGVnb3J5IFV0aWwKICAgICAqIEBwYXJhbSB7c3RyaW5nfSBbcHJlZml4PScnXSBUaGUgdmFsdWUgdG8gcHJlZml4IHRoZSBJRCB3aXRoLgogICAgICogQHJldHVybnMge3N0cmluZ30gUmV0dXJucyB0aGUgdW5pcXVlIElELgogICAgICogQGV4YW1wbGUKICAgICAqCiAgICAgKiBfLnVuaXF1ZUlkKCdjb250YWN0XycpOwogICAgICogLy8gPT4gJ2NvbnRhY3RfMTA0JwogICAgICoKICAgICAqIF8udW5pcXVlSWQoKTsKICAgICAqIC8vID0+ICcxMDUnCiAgICAgKi8KICAgIGZ1bmN0aW9uIHVuaXF1ZUlkKHByZWZpeCkgewogICAgICB2YXIgaWQgPSArK2lkQ291bnRlcjsKICAgICAgcmV0dXJuIHRvU3RyaW5nXzEocHJlZml4KSArIGlkOwogICAgfQoKICAgIHZhciB1bmlxdWVJZF8xID0gdW5pcXVlSWQ7CgogICAgLyoqCiAgICAgKiBUaGlzIGJhc2UgaW1wbGVtZW50YXRpb24gb2YgYF8uemlwT2JqZWN0YCB3aGljaCBhc3NpZ25zIHZhbHVlcyB1c2luZyBgYXNzaWduRnVuY2AuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqIEBwYXJhbSB7QXJyYXl9IHByb3BzIFRoZSBwcm9wZXJ0eSBpZGVudGlmaWVycy4KICAgICAqIEBwYXJhbSB7QXJyYXl9IHZhbHVlcyBUaGUgcHJvcGVydHkgdmFsdWVzLgogICAgICogQHBhcmFtIHtGdW5jdGlvbn0gYXNzaWduRnVuYyBUaGUgZnVuY3Rpb24gdG8gYXNzaWduIHZhbHVlcy4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJhc2VaaXBPYmplY3QocHJvcHMsIHZhbHVlcywgYXNzaWduRnVuYykgewogICAgICB2YXIgaW5kZXggPSAtMSwKICAgICAgICAgIGxlbmd0aCA9IHByb3BzLmxlbmd0aCwKICAgICAgICAgIHZhbHNMZW5ndGggPSB2YWx1ZXMubGVuZ3RoLAogICAgICAgICAgcmVzdWx0ID0ge307CgogICAgICB3aGlsZSAoKytpbmRleCA8IGxlbmd0aCkgewogICAgICAgIHZhciB2YWx1ZSA9IGluZGV4IDwgdmFsc0xlbmd0aCA/IHZhbHVlc1tpbmRleF0gOiB1bmRlZmluZWQ7CiAgICAgICAgYXNzaWduRnVuYyhyZXN1bHQsIHByb3BzW2luZGV4XSwgdmFsdWUpOwogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIF9iYXNlWmlwT2JqZWN0ID0gYmFzZVppcE9iamVjdDsKCiAgICAvKioKICAgICAqIFRoaXMgbWV0aG9kIGlzIGxpa2UgYF8uZnJvbVBhaXJzYCBleGNlcHQgdGhhdCBpdCBhY2NlcHRzIHR3byBhcnJheXMsCiAgICAgKiBvbmUgb2YgcHJvcGVydHkgaWRlbnRpZmllcnMgYW5kIG9uZSBvZiBjb3JyZXNwb25kaW5nIHZhbHVlcy4KICAgICAqCiAgICAgKiBAc3RhdGljCiAgICAgKiBAbWVtYmVyT2YgXwogICAgICogQHNpbmNlIDAuNC4wCiAgICAgKiBAY2F0ZWdvcnkgQXJyYXkKICAgICAqIEBwYXJhbSB7QXJyYXl9IFtwcm9wcz1bXV0gVGhlIHByb3BlcnR5IGlkZW50aWZpZXJzLgogICAgICogQHBhcmFtIHtBcnJheX0gW3ZhbHVlcz1bXV0gVGhlIHByb3BlcnR5IHZhbHVlcy4KICAgICAqIEByZXR1cm5zIHtPYmplY3R9IFJldHVybnMgdGhlIG5ldyBvYmplY3QuCiAgICAgKiBAZXhhbXBsZQogICAgICoKICAgICAqIF8uemlwT2JqZWN0KFsnYScsICdiJ10sIFsxLCAyXSk7CiAgICAgKiAvLyA9PiB7ICdhJzogMSwgJ2InOiAyIH0KICAgICAqLwogICAgZnVuY3Rpb24gemlwT2JqZWN0KHByb3BzLCB2YWx1ZXMpIHsKICAgICAgcmV0dXJuIF9iYXNlWmlwT2JqZWN0KHByb3BzIHx8IFtdLCB2YWx1ZXMgfHwgW10sIF9hc3NpZ25WYWx1ZSk7CiAgICB9CgogICAgdmFyIHppcE9iamVjdF8xID0gemlwT2JqZWN0OwoKICAgIC8qIGdsb2JhbCB3aW5kb3cgKi8KCiAgICB2YXIgbG9kYXNoJDI7CgogICAgaWYgKHR5cGVvZiBjb21tb25qc1JlcXVpcmUgPT09ICJmdW5jdGlvbiIpIHsKICAgICAgdHJ5IHsKICAgICAgICBsb2Rhc2gkMiA9IHsKICAgICAgICAgIGNsb25lRGVlcDogY2xvbmVEZWVwXzEsCiAgICAgICAgICBjb25zdGFudDogY29uc3RhbnRfMSwKICAgICAgICAgIGRlZmF1bHRzOiBkZWZhdWx0c18xLAogICAgICAgICAgZWFjaDogZWFjaCwKICAgICAgICAgIGZpbHRlcjogZmlsdGVyXzEsCiAgICAgICAgICBmaW5kOiBmaW5kXzEsCiAgICAgICAgICBmbGF0dGVuOiBmbGF0dGVuXzEsCiAgICAgICAgICBmb3JFYWNoOiBmb3JFYWNoXzEsCiAgICAgICAgICBmb3JJbjogZm9ySW5fMSwKICAgICAgICAgIGhhczogIGhhc18xLAogICAgICAgICAgaXNVbmRlZmluZWQ6IGlzVW5kZWZpbmVkXzEsCiAgICAgICAgICBsYXN0OiBsYXN0XzEsCiAgICAgICAgICBtYXA6IG1hcF8xLAogICAgICAgICAgbWFwVmFsdWVzOiBtYXBWYWx1ZXNfMSwKICAgICAgICAgIG1heDogbWF4XzEsCiAgICAgICAgICBtZXJnZTogbWVyZ2VfMSwKICAgICAgICAgIG1pbjogbWluXzEsCiAgICAgICAgICBtaW5CeTogbWluQnlfMSwKICAgICAgICAgIG5vdzogbm93XzEsCiAgICAgICAgICBwaWNrOiBwaWNrXzEsCiAgICAgICAgICByYW5nZTogcmFuZ2VfMSwKICAgICAgICAgIHJlZHVjZTogcmVkdWNlXzEsCiAgICAgICAgICBzb3J0Qnk6IHNvcnRCeV8xLAogICAgICAgICAgdW5pcXVlSWQ6IHVuaXF1ZUlkXzEsCiAgICAgICAgICB2YWx1ZXM6IHZhbHVlc18xLAogICAgICAgICAgemlwT2JqZWN0OiB6aXBPYmplY3RfMSwKICAgICAgICB9OwogICAgICB9IGNhdGNoIChlKSB7CiAgICAgICAgLy8gY29udGludWUgcmVnYXJkbGVzcyBvZiBlcnJvcgogICAgICB9CiAgICB9CgogICAgaWYgKCFsb2Rhc2gkMikgewogICAgICBsb2Rhc2gkMiA9IHdpbmRvdy5fOwogICAgfQoKICAgIHZhciBsb2Rhc2hfMSQxID0gbG9kYXNoJDI7CgogICAgLyoKICAgICAqIFNpbXBsZSBkb3VibHkgbGlua2VkIGxpc3QgaW1wbGVtZW50YXRpb24gZGVyaXZlZCBmcm9tIENvcm1lbiwgZXQgYWwuLAogICAgICogIkludHJvZHVjdGlvbiB0byBBbGdvcml0aG1zIi4KICAgICAqLwoKICAgIHZhciBsaXN0ID0gTGlzdDsKCiAgICBmdW5jdGlvbiBMaXN0KCkgewogICAgICB2YXIgc2VudGluZWwgPSB7fTsKICAgICAgc2VudGluZWwuX25leHQgPSBzZW50aW5lbC5fcHJldiA9IHNlbnRpbmVsOwogICAgICB0aGlzLl9zZW50aW5lbCA9IHNlbnRpbmVsOwogICAgfQoKICAgIExpc3QucHJvdG90eXBlLmRlcXVldWUgPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIHNlbnRpbmVsID0gdGhpcy5fc2VudGluZWw7CiAgICAgIHZhciBlbnRyeSA9IHNlbnRpbmVsLl9wcmV2OwogICAgICBpZiAoZW50cnkgIT09IHNlbnRpbmVsKSB7CiAgICAgICAgdW5saW5rKGVudHJ5KTsKICAgICAgICByZXR1cm4gZW50cnk7CiAgICAgIH0KICAgIH07CgogICAgTGlzdC5wcm90b3R5cGUuZW5xdWV1ZSA9IGZ1bmN0aW9uKGVudHJ5KSB7CiAgICAgIHZhciBzZW50aW5lbCA9IHRoaXMuX3NlbnRpbmVsOwogICAgICBpZiAoZW50cnkuX3ByZXYgJiYgZW50cnkuX25leHQpIHsKICAgICAgICB1bmxpbmsoZW50cnkpOwogICAgICB9CiAgICAgIGVudHJ5Ll9uZXh0ID0gc2VudGluZWwuX25leHQ7CiAgICAgIHNlbnRpbmVsLl9uZXh0Ll9wcmV2ID0gZW50cnk7CiAgICAgIHNlbnRpbmVsLl9uZXh0ID0gZW50cnk7CiAgICAgIGVudHJ5Ll9wcmV2ID0gc2VudGluZWw7CiAgICB9OwoKICAgIExpc3QucHJvdG90eXBlLnRvU3RyaW5nID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBzdHJzID0gW107CiAgICAgIHZhciBzZW50aW5lbCA9IHRoaXMuX3NlbnRpbmVsOwogICAgICB2YXIgY3VyciA9IHNlbnRpbmVsLl9wcmV2OwogICAgICB3aGlsZSAoY3VyciAhPT0gc2VudGluZWwpIHsKICAgICAgICBzdHJzLnB1c2goSlNPTi5zdHJpbmdpZnkoY3VyciwgZmlsdGVyT3V0TGlua3MpKTsKICAgICAgICBjdXJyID0gY3Vyci5fcHJldjsKICAgICAgfQogICAgICByZXR1cm4gIlsiICsgc3Rycy5qb2luKCIsICIpICsgIl0iOwogICAgfTsKCiAgICBmdW5jdGlvbiB1bmxpbmsoZW50cnkpIHsKICAgICAgZW50cnkuX3ByZXYuX25leHQgPSBlbnRyeS5fbmV4dDsKICAgICAgZW50cnkuX25leHQuX3ByZXYgPSBlbnRyeS5fcHJldjsKICAgICAgZGVsZXRlIGVudHJ5Ll9uZXh0OwogICAgICBkZWxldGUgZW50cnkuX3ByZXY7CiAgICB9CgogICAgZnVuY3Rpb24gZmlsdGVyT3V0TGlua3MoaywgdikgewogICAgICBpZiAoayAhPT0gIl9uZXh0IiAmJiBrICE9PSAiX3ByZXYiKSB7CiAgICAgICAgcmV0dXJuIHY7CiAgICAgIH0KICAgIH0KCiAgICB2YXIgR3JhcGgkMSA9IGdyYXBobGliXzEuR3JhcGg7CgoKICAgIC8qCiAgICAgKiBBIGdyZWVkeSBoZXVyaXN0aWMgZm9yIGZpbmRpbmcgYSBmZWVkYmFjayBhcmMgc2V0IGZvciBhIGdyYXBoLiBBIGZlZWRiYWNrCiAgICAgKiBhcmMgc2V0IGlzIGEgc2V0IG9mIGVkZ2VzIHRoYXQgY2FuIGJlIHJlbW92ZWQgdG8gbWFrZSBhIGdyYXBoIGFjeWNsaWMuCiAgICAgKiBUaGUgYWxnb3JpdGhtIGNvbWVzIGZyb206IFAuIEVhZGVzLCBYLiBMaW4sIGFuZCBXLiBGLiBTbXl0aCwgIkEgZmFzdCBhbmQKICAgICAqIGVmZmVjdGl2ZSBoZXVyaXN0aWMgZm9yIHRoZSBmZWVkYmFjayBhcmMgc2V0IHByb2JsZW0uIiBUaGlzIGltcGxlbWVudGF0aW9uCiAgICAgKiBhZGp1c3RzIHRoYXQgZnJvbSB0aGUgcGFwZXIgdG8gYWxsb3cgZm9yIHdlaWdodGVkIGVkZ2VzLgogICAgICovCiAgICB2YXIgZ3JlZWR5RmFzID0gZ3JlZWR5RkFTOwoKICAgIHZhciBERUZBVUxUX1dFSUdIVF9GTiA9IGxvZGFzaF8xJDEuY29uc3RhbnQoMSk7CgogICAgZnVuY3Rpb24gZ3JlZWR5RkFTKGcsIHdlaWdodEZuKSB7CiAgICAgIGlmIChnLm5vZGVDb3VudCgpIDw9IDEpIHsKICAgICAgICByZXR1cm4gW107CiAgICAgIH0KICAgICAgdmFyIHN0YXRlID0gYnVpbGRTdGF0ZShnLCB3ZWlnaHRGbiB8fCBERUZBVUxUX1dFSUdIVF9GTik7CiAgICAgIHZhciByZXN1bHRzID0gZG9HcmVlZHlGQVMoc3RhdGUuZ3JhcGgsIHN0YXRlLmJ1Y2tldHMsIHN0YXRlLnplcm9JZHgpOwoKICAgICAgLy8gRXhwYW5kIG11bHRpLWVkZ2VzCiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLmZsYXR0ZW4obG9kYXNoXzEkMS5tYXAocmVzdWx0cywgZnVuY3Rpb24oZSkgewogICAgICAgIHJldHVybiBnLm91dEVkZ2VzKGUudiwgZS53KTsKICAgICAgfSksIHRydWUpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRvR3JlZWR5RkFTKGcsIGJ1Y2tldHMsIHplcm9JZHgpIHsKICAgICAgdmFyIHJlc3VsdHMgPSBbXTsKICAgICAgdmFyIHNvdXJjZXMgPSBidWNrZXRzW2J1Y2tldHMubGVuZ3RoIC0gMV07CiAgICAgIHZhciBzaW5rcyA9IGJ1Y2tldHNbMF07CgogICAgICB2YXIgZW50cnk7CiAgICAgIHdoaWxlIChnLm5vZGVDb3VudCgpKSB7CiAgICAgICAgd2hpbGUgKChlbnRyeSA9IHNpbmtzLmRlcXVldWUoKSkpICAgeyByZW1vdmVOb2RlKGcsIGJ1Y2tldHMsIHplcm9JZHgsIGVudHJ5KTsgfQogICAgICAgIHdoaWxlICgoZW50cnkgPSBzb3VyY2VzLmRlcXVldWUoKSkpIHsgcmVtb3ZlTm9kZShnLCBidWNrZXRzLCB6ZXJvSWR4LCBlbnRyeSk7IH0KICAgICAgICBpZiAoZy5ub2RlQ291bnQoKSkgewogICAgICAgICAgZm9yICh2YXIgaSA9IGJ1Y2tldHMubGVuZ3RoIC0gMjsgaSA+IDA7IC0taSkgewogICAgICAgICAgICBlbnRyeSA9IGJ1Y2tldHNbaV0uZGVxdWV1ZSgpOwogICAgICAgICAgICBpZiAoZW50cnkpIHsKICAgICAgICAgICAgICByZXN1bHRzID0gcmVzdWx0cy5jb25jYXQocmVtb3ZlTm9kZShnLCBidWNrZXRzLCB6ZXJvSWR4LCBlbnRyeSwgdHJ1ZSkpOwogICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gcmVzdWx0czsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVOb2RlKGcsIGJ1Y2tldHMsIHplcm9JZHgsIGVudHJ5LCBjb2xsZWN0UHJlZGVjZXNzb3JzKSB7CiAgICAgIHZhciByZXN1bHRzID0gY29sbGVjdFByZWRlY2Vzc29ycyA/IFtdIDogdW5kZWZpbmVkOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuaW5FZGdlcyhlbnRyeS52KSwgZnVuY3Rpb24oZWRnZSkgewogICAgICAgIHZhciB3ZWlnaHQgPSBnLmVkZ2UoZWRnZSk7CiAgICAgICAgdmFyIHVFbnRyeSA9IGcubm9kZShlZGdlLnYpOwoKICAgICAgICBpZiAoY29sbGVjdFByZWRlY2Vzc29ycykgewogICAgICAgICAgcmVzdWx0cy5wdXNoKHsgdjogZWRnZS52LCB3OiBlZGdlLncgfSk7CiAgICAgICAgfQoKICAgICAgICB1RW50cnkub3V0IC09IHdlaWdodDsKICAgICAgICBhc3NpZ25CdWNrZXQoYnVja2V0cywgemVyb0lkeCwgdUVudHJ5KTsKICAgICAgfSk7CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5vdXRFZGdlcyhlbnRyeS52KSwgZnVuY3Rpb24oZWRnZSkgewogICAgICAgIHZhciB3ZWlnaHQgPSBnLmVkZ2UoZWRnZSk7CiAgICAgICAgdmFyIHcgPSBlZGdlLnc7CiAgICAgICAgdmFyIHdFbnRyeSA9IGcubm9kZSh3KTsKICAgICAgICB3RW50cnlbImluIl0gLT0gd2VpZ2h0OwogICAgICAgIGFzc2lnbkJ1Y2tldChidWNrZXRzLCB6ZXJvSWR4LCB3RW50cnkpOwogICAgICB9KTsKCiAgICAgIGcucmVtb3ZlTm9kZShlbnRyeS52KTsKCiAgICAgIHJldHVybiByZXN1bHRzOwogICAgfQoKICAgIGZ1bmN0aW9uIGJ1aWxkU3RhdGUoZywgd2VpZ2h0Rm4pIHsKICAgICAgdmFyIGZhc0dyYXBoID0gbmV3IEdyYXBoJDEoKTsKICAgICAgdmFyIG1heEluID0gMDsKICAgICAgdmFyIG1heE91dCA9IDA7CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgZmFzR3JhcGguc2V0Tm9kZSh2LCB7IHY6IHYsICJpbiI6IDAsIG91dDogMCB9KTsKICAgICAgfSk7CgogICAgICAvLyBBZ2dyZWdhdGUgd2VpZ2h0cyBvbiBub2RlcywgYnV0IGFsc28gc3VtIHRoZSB3ZWlnaHRzIGFjcm9zcyBtdWx0aS1lZGdlcwogICAgICAvLyBpbnRvIGEgc2luZ2xlIGVkZ2UgZm9yIHRoZSBmYXNHcmFwaC4KICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBwcmV2V2VpZ2h0ID0gZmFzR3JhcGguZWRnZShlLnYsIGUudykgfHwgMDsKICAgICAgICB2YXIgd2VpZ2h0ID0gd2VpZ2h0Rm4oZSk7CiAgICAgICAgdmFyIGVkZ2VXZWlnaHQgPSBwcmV2V2VpZ2h0ICsgd2VpZ2h0OwogICAgICAgIGZhc0dyYXBoLnNldEVkZ2UoZS52LCBlLncsIGVkZ2VXZWlnaHQpOwogICAgICAgIG1heE91dCA9IE1hdGgubWF4KG1heE91dCwgZmFzR3JhcGgubm9kZShlLnYpLm91dCArPSB3ZWlnaHQpOwogICAgICAgIG1heEluICA9IE1hdGgubWF4KG1heEluLCAgZmFzR3JhcGgubm9kZShlLncpWyJpbiJdICArPSB3ZWlnaHQpOwogICAgICB9KTsKCiAgICAgIHZhciBidWNrZXRzID0gbG9kYXNoXzEkMS5yYW5nZShtYXhPdXQgKyBtYXhJbiArIDMpLm1hcChmdW5jdGlvbigpIHsgcmV0dXJuIG5ldyBsaXN0KCk7IH0pOwogICAgICB2YXIgemVyb0lkeCA9IG1heEluICsgMTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChmYXNHcmFwaC5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgYXNzaWduQnVja2V0KGJ1Y2tldHMsIHplcm9JZHgsIGZhc0dyYXBoLm5vZGUodikpOwogICAgICB9KTsKCiAgICAgIHJldHVybiB7IGdyYXBoOiBmYXNHcmFwaCwgYnVja2V0czogYnVja2V0cywgemVyb0lkeDogemVyb0lkeCB9OwogICAgfQoKICAgIGZ1bmN0aW9uIGFzc2lnbkJ1Y2tldChidWNrZXRzLCB6ZXJvSWR4LCBlbnRyeSkgewogICAgICBpZiAoIWVudHJ5Lm91dCkgewogICAgICAgIGJ1Y2tldHNbMF0uZW5xdWV1ZShlbnRyeSk7CiAgICAgIH0gZWxzZSBpZiAoIWVudHJ5WyJpbiJdKSB7CiAgICAgICAgYnVja2V0c1tidWNrZXRzLmxlbmd0aCAtIDFdLmVucXVldWUoZW50cnkpOwogICAgICB9IGVsc2UgewogICAgICAgIGJ1Y2tldHNbZW50cnkub3V0IC0gZW50cnlbImluIl0gKyB6ZXJvSWR4XS5lbnF1ZXVlKGVudHJ5KTsKICAgICAgfQogICAgfQoKICAgIHZhciBhY3ljbGljID0gewogICAgICBydW46IHJ1biwKICAgICAgdW5kbzogdW5kbwogICAgfTsKCiAgICBmdW5jdGlvbiBydW4oZykgewogICAgICB2YXIgZmFzID0gKGcuZ3JhcGgoKS5hY3ljbGljZXIgPT09ICJncmVlZHkiCiAgICAgICAgPyBncmVlZHlGYXMoZywgd2VpZ2h0Rm4oZykpCiAgICAgICAgOiBkZnNGQVMoZykpOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZmFzLCBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIGxhYmVsID0gZy5lZGdlKGUpOwogICAgICAgIGcucmVtb3ZlRWRnZShlKTsKICAgICAgICBsYWJlbC5mb3J3YXJkTmFtZSA9IGUubmFtZTsKICAgICAgICBsYWJlbC5yZXZlcnNlZCA9IHRydWU7CiAgICAgICAgZy5zZXRFZGdlKGUudywgZS52LCBsYWJlbCwgbG9kYXNoXzEkMS51bmlxdWVJZCgicmV2IikpOwogICAgICB9KTsKCiAgICAgIGZ1bmN0aW9uIHdlaWdodEZuKGcpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24oZSkgewogICAgICAgICAgcmV0dXJuIGcuZWRnZShlKS53ZWlnaHQ7CiAgICAgICAgfTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIGRmc0ZBUyhnKSB7CiAgICAgIHZhciBmYXMgPSBbXTsKICAgICAgdmFyIHN0YWNrID0ge307CiAgICAgIHZhciB2aXNpdGVkID0ge307CgogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyh2aXNpdGVkLCB2KSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICB2aXNpdGVkW3ZdID0gdHJ1ZTsKICAgICAgICBzdGFja1t2XSA9IHRydWU7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcub3V0RWRnZXModiksIGZ1bmN0aW9uKGUpIHsKICAgICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyhzdGFjaywgZS53KSkgewogICAgICAgICAgICBmYXMucHVzaChlKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGRmcyhlLncpOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIGRlbGV0ZSBzdGFja1t2XTsKICAgICAgfQoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZGZzKTsKICAgICAgcmV0dXJuIGZhczsKICAgIH0KCiAgICBmdW5jdGlvbiB1bmRvKGcpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBsYWJlbCA9IGcuZWRnZShlKTsKICAgICAgICBpZiAobGFiZWwucmV2ZXJzZWQpIHsKICAgICAgICAgIGcucmVtb3ZlRWRnZShlKTsKCiAgICAgICAgICB2YXIgZm9yd2FyZE5hbWUgPSBsYWJlbC5mb3J3YXJkTmFtZTsKICAgICAgICAgIGRlbGV0ZSBsYWJlbC5yZXZlcnNlZDsKICAgICAgICAgIGRlbGV0ZSBsYWJlbC5mb3J3YXJkTmFtZTsKICAgICAgICAgIGcuc2V0RWRnZShlLncsIGUudiwgbGFiZWwsIGZvcndhcmROYW1lKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBHcmFwaCQyID0gZ3JhcGhsaWJfMS5HcmFwaDsKCiAgICB2YXIgdXRpbCA9IHsKICAgICAgYWRkRHVtbXlOb2RlOiBhZGREdW1teU5vZGUsCiAgICAgIHNpbXBsaWZ5OiBzaW1wbGlmeSwKICAgICAgYXNOb25Db21wb3VuZEdyYXBoOiBhc05vbkNvbXBvdW5kR3JhcGgsCiAgICAgIHN1Y2Nlc3NvcldlaWdodHM6IHN1Y2Nlc3NvcldlaWdodHMsCiAgICAgIHByZWRlY2Vzc29yV2VpZ2h0czogcHJlZGVjZXNzb3JXZWlnaHRzLAogICAgICBpbnRlcnNlY3RSZWN0OiBpbnRlcnNlY3RSZWN0LAogICAgICBidWlsZExheWVyTWF0cml4OiBidWlsZExheWVyTWF0cml4LAogICAgICBub3JtYWxpemVSYW5rczogbm9ybWFsaXplUmFua3MsCiAgICAgIHJlbW92ZUVtcHR5UmFua3M6IHJlbW92ZUVtcHR5UmFua3MsCiAgICAgIGFkZEJvcmRlck5vZGU6IGFkZEJvcmRlck5vZGUsCiAgICAgIG1heFJhbms6IG1heFJhbmssCiAgICAgIHBhcnRpdGlvbjogcGFydGl0aW9uJDIsCiAgICAgIHRpbWU6IHRpbWUkMiwKICAgICAgbm90aW1lOiBub3RpbWUKICAgIH07CgogICAgLyoKICAgICAqIEFkZHMgYSBkdW1teSBub2RlIHRvIHRoZSBncmFwaCBhbmQgcmV0dXJuIHYuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFkZER1bW15Tm9kZShnLCB0eXBlLCBhdHRycywgbmFtZSkgewogICAgICB2YXIgdjsKICAgICAgZG8gewogICAgICAgIHYgPSBsb2Rhc2hfMSQxLnVuaXF1ZUlkKG5hbWUpOwogICAgICB9IHdoaWxlIChnLmhhc05vZGUodikpOwoKICAgICAgYXR0cnMuZHVtbXkgPSB0eXBlOwogICAgICBnLnNldE5vZGUodiwgYXR0cnMpOwogICAgICByZXR1cm4gdjsKICAgIH0KCiAgICAvKgogICAgICogUmV0dXJucyBhIG5ldyBncmFwaCB3aXRoIG9ubHkgc2ltcGxlIGVkZ2VzLiBIYW5kbGVzIGFnZ3JlZ2F0aW9uIG9mIGRhdGEKICAgICAqIGFzc29jaWF0ZWQgd2l0aCBtdWx0aS1lZGdlcy4KICAgICAqLwogICAgZnVuY3Rpb24gc2ltcGxpZnkoZykgewogICAgICB2YXIgc2ltcGxpZmllZCA9IG5ldyBHcmFwaCQyKCkuc2V0R3JhcGgoZy5ncmFwaCgpKTsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgeyBzaW1wbGlmaWVkLnNldE5vZGUodiwgZy5ub2RlKHYpKTsgfSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgc2ltcGxlTGFiZWwgPSBzaW1wbGlmaWVkLmVkZ2UoZS52LCBlLncpIHx8IHsgd2VpZ2h0OiAwLCBtaW5sZW46IDEgfTsKICAgICAgICB2YXIgbGFiZWwgPSBnLmVkZ2UoZSk7CiAgICAgICAgc2ltcGxpZmllZC5zZXRFZGdlKGUudiwgZS53LCB7CiAgICAgICAgICB3ZWlnaHQ6IHNpbXBsZUxhYmVsLndlaWdodCArIGxhYmVsLndlaWdodCwKICAgICAgICAgIG1pbmxlbjogTWF0aC5tYXgoc2ltcGxlTGFiZWwubWlubGVuLCBsYWJlbC5taW5sZW4pCiAgICAgICAgfSk7CiAgICAgIH0pOwogICAgICByZXR1cm4gc2ltcGxpZmllZDsKICAgIH0KCiAgICBmdW5jdGlvbiBhc05vbkNvbXBvdW5kR3JhcGgoZykgewogICAgICB2YXIgc2ltcGxpZmllZCA9IG5ldyBHcmFwaCQyKHsgbXVsdGlncmFwaDogZy5pc011bHRpZ3JhcGgoKSB9KS5zZXRHcmFwaChnLmdyYXBoKCkpOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgaWYgKCFnLmNoaWxkcmVuKHYpLmxlbmd0aCkgewogICAgICAgICAgc2ltcGxpZmllZC5zZXROb2RlKHYsIGcubm9kZSh2KSk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHNpbXBsaWZpZWQuc2V0RWRnZShlLCBnLmVkZ2UoZSkpOwogICAgICB9KTsKICAgICAgcmV0dXJuIHNpbXBsaWZpZWQ7CiAgICB9CgogICAgZnVuY3Rpb24gc3VjY2Vzc29yV2VpZ2h0cyhnKSB7CiAgICAgIHZhciB3ZWlnaHRNYXAgPSBsb2Rhc2hfMSQxLm1hcChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICB2YXIgc3VjcyA9IHt9OwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm91dEVkZ2VzKHYpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgICBzdWNzW2Uud10gPSAoc3Vjc1tlLnddIHx8IDApICsgZy5lZGdlKGUpLndlaWdodDsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gc3VjczsKICAgICAgfSk7CiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLnppcE9iamVjdChnLm5vZGVzKCksIHdlaWdodE1hcCk7CiAgICB9CgogICAgZnVuY3Rpb24gcHJlZGVjZXNzb3JXZWlnaHRzKGcpIHsKICAgICAgdmFyIHdlaWdodE1hcCA9IGxvZGFzaF8xJDEubWFwKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBwcmVkcyA9IHt9OwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmluRWRnZXModiksIGZ1bmN0aW9uKGUpIHsKICAgICAgICAgIHByZWRzW2Uudl0gPSAocHJlZHNbZS52XSB8fCAwKSArIGcuZWRnZShlKS53ZWlnaHQ7CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIHByZWRzOwogICAgICB9KTsKICAgICAgcmV0dXJuIGxvZGFzaF8xJDEuemlwT2JqZWN0KGcubm9kZXMoKSwgd2VpZ2h0TWFwKTsKICAgIH0KCiAgICAvKgogICAgICogRmluZHMgd2hlcmUgYSBsaW5lIHN0YXJ0aW5nIGF0IHBvaW50ICh7eCwgeX0pIHdvdWxkIGludGVyc2VjdCBhIHJlY3RhbmdsZQogICAgICogKHt4LCB5LCB3aWR0aCwgaGVpZ2h0fSkgaWYgaXQgd2VyZSBwb2ludGluZyBhdCB0aGUgcmVjdGFuZ2xlJ3MgY2VudGVyLgogICAgICovCiAgICBmdW5jdGlvbiBpbnRlcnNlY3RSZWN0KHJlY3QsIHBvaW50KSB7CiAgICAgIHZhciB4ID0gcmVjdC54OwogICAgICB2YXIgeSA9IHJlY3QueTsKCiAgICAgIC8vIFJlY3RhbmdsZSBpbnRlcnNlY3Rpb24gYWxnb3JpdGhtIGZyb206CiAgICAgIC8vIGh0dHA6Ly9tYXRoLnN0YWNrZXhjaGFuZ2UuY29tL3F1ZXN0aW9ucy8xMDgxMTMvZmluZC1lZGdlLWJldHdlZW4tdHdvLWJveGVzCiAgICAgIHZhciBkeCA9IHBvaW50LnggLSB4OwogICAgICB2YXIgZHkgPSBwb2ludC55IC0geTsKICAgICAgdmFyIHcgPSByZWN0LndpZHRoIC8gMjsKICAgICAgdmFyIGggPSByZWN0LmhlaWdodCAvIDI7CgogICAgICBpZiAoIWR4ICYmICFkeSkgewogICAgICAgIHRocm93IG5ldyBFcnJvcigiTm90IHBvc3NpYmxlIHRvIGZpbmQgaW50ZXJzZWN0aW9uIGluc2lkZSBvZiB0aGUgcmVjdGFuZ2xlIik7CiAgICAgIH0KCiAgICAgIHZhciBzeCwgc3k7CiAgICAgIGlmIChNYXRoLmFicyhkeSkgKiB3ID4gTWF0aC5hYnMoZHgpICogaCkgewogICAgICAgIC8vIEludGVyc2VjdGlvbiBpcyB0b3Agb3IgYm90dG9tIG9mIHJlY3QuCiAgICAgICAgaWYgKGR5IDwgMCkgewogICAgICAgICAgaCA9IC1oOwogICAgICAgIH0KICAgICAgICBzeCA9IGggKiBkeCAvIGR5OwogICAgICAgIHN5ID0gaDsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBJbnRlcnNlY3Rpb24gaXMgbGVmdCBvciByaWdodCBvZiByZWN0LgogICAgICAgIGlmIChkeCA8IDApIHsKICAgICAgICAgIHcgPSAtdzsKICAgICAgICB9CiAgICAgICAgc3ggPSB3OwogICAgICAgIHN5ID0gdyAqIGR5IC8gZHg7CiAgICAgIH0KCiAgICAgIHJldHVybiB7IHg6IHggKyBzeCwgeTogeSArIHN5IH07CiAgICB9CgogICAgLyoKICAgICAqIEdpdmVuIGEgREFHIHdpdGggZWFjaCBub2RlIGFzc2lnbmVkICJyYW5rIiBhbmQgIm9yZGVyIiBwcm9wZXJ0aWVzLCB0aGlzCiAgICAgKiBmdW5jdGlvbiB3aWxsIHByb2R1Y2UgYSBtYXRyaXggd2l0aCB0aGUgaWRzIG9mIGVhY2ggbm9kZS4KICAgICAqLwogICAgZnVuY3Rpb24gYnVpbGRMYXllck1hdHJpeChnKSB7CiAgICAgIHZhciBsYXllcmluZyA9IGxvZGFzaF8xJDEubWFwKGxvZGFzaF8xJDEucmFuZ2UobWF4UmFuayhnKSArIDEpLCBmdW5jdGlvbigpIHsgcmV0dXJuIFtdOyB9KTsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIHZhciByYW5rID0gbm9kZS5yYW5rOwogICAgICAgIGlmICghbG9kYXNoXzEkMS5pc1VuZGVmaW5lZChyYW5rKSkgewogICAgICAgICAgbGF5ZXJpbmdbcmFua11bbm9kZS5vcmRlcl0gPSB2OwogICAgICAgIH0KICAgICAgfSk7CiAgICAgIHJldHVybiBsYXllcmluZzsKICAgIH0KCiAgICAvKgogICAgICogQWRqdXN0cyB0aGUgcmFua3MgZm9yIGFsbCBub2RlcyBpbiB0aGUgZ3JhcGggc3VjaCB0aGF0IGFsbCBub2RlcyB2IGhhdmUKICAgICAqIHJhbmsodikgPj0gMCBhbmQgYXQgbGVhc3Qgb25lIG5vZGUgdyBoYXMgcmFuayh3KSA9IDAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG5vcm1hbGl6ZVJhbmtzKGcpIHsKICAgICAgdmFyIG1pbiA9IGxvZGFzaF8xJDEubWluKGxvZGFzaF8xJDEubWFwKGcubm9kZXMoKSwgZnVuY3Rpb24odikgeyByZXR1cm4gZy5ub2RlKHYpLnJhbms7IH0pKTsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyhub2RlLCAicmFuayIpKSB7CiAgICAgICAgICBub2RlLnJhbmsgLT0gbWluOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlRW1wdHlSYW5rcyhnKSB7CiAgICAgIC8vIFJhbmtzIG1heSBub3Qgc3RhcnQgYXQgMCwgc28gd2UgbmVlZCB0byBvZmZzZXQgdGhlbQogICAgICB2YXIgb2Zmc2V0ID0gbG9kYXNoXzEkMS5taW4obG9kYXNoXzEkMS5tYXAoZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7IHJldHVybiBnLm5vZGUodikucmFuazsgfSkpOwoKICAgICAgdmFyIGxheWVycyA9IFtdOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIHJhbmsgPSBnLm5vZGUodikucmFuayAtIG9mZnNldDsKICAgICAgICBpZiAoIWxheWVyc1tyYW5rXSkgewogICAgICAgICAgbGF5ZXJzW3JhbmtdID0gW107CiAgICAgICAgfQogICAgICAgIGxheWVyc1tyYW5rXS5wdXNoKHYpOwogICAgICB9KTsKCiAgICAgIHZhciBkZWx0YSA9IDA7CiAgICAgIHZhciBub2RlUmFua0ZhY3RvciA9IGcuZ3JhcGgoKS5ub2RlUmFua0ZhY3RvcjsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVycywgZnVuY3Rpb24odnMsIGkpIHsKICAgICAgICBpZiAobG9kYXNoXzEkMS5pc1VuZGVmaW5lZCh2cykgJiYgaSAlIG5vZGVSYW5rRmFjdG9yICE9PSAwKSB7CiAgICAgICAgICAtLWRlbHRhOwogICAgICAgIH0gZWxzZSBpZiAoZGVsdGEpIHsKICAgICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaCh2cywgZnVuY3Rpb24odikgeyBnLm5vZGUodikucmFuayArPSBkZWx0YTsgfSk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhZGRCb3JkZXJOb2RlKGcsIHByZWZpeCwgcmFuaywgb3JkZXIpIHsKICAgICAgdmFyIG5vZGUgPSB7CiAgICAgICAgd2lkdGg6IDAsCiAgICAgICAgaGVpZ2h0OiAwCiAgICAgIH07CiAgICAgIGlmIChhcmd1bWVudHMubGVuZ3RoID49IDQpIHsKICAgICAgICBub2RlLnJhbmsgPSByYW5rOwogICAgICAgIG5vZGUub3JkZXIgPSBvcmRlcjsKICAgICAgfQogICAgICByZXR1cm4gYWRkRHVtbXlOb2RlKGcsICJib3JkZXIiLCBub2RlLCBwcmVmaXgpOwogICAgfQoKICAgIGZ1bmN0aW9uIG1heFJhbmsoZykgewogICAgICByZXR1cm4gbG9kYXNoXzEkMS5tYXgobG9kYXNoXzEkMS5tYXAoZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIHJhbmsgPSBnLm5vZGUodikucmFuazsKICAgICAgICBpZiAoIWxvZGFzaF8xJDEuaXNVbmRlZmluZWQocmFuaykpIHsKICAgICAgICAgIHJldHVybiByYW5rOwogICAgICAgIH0KICAgICAgfSkpOwogICAgfQoKICAgIC8qCiAgICAgKiBQYXJ0aXRpb24gYSBjb2xsZWN0aW9uIGludG8gdHdvIGdyb3VwczogYGxoc2AgYW5kIGByaHNgLiBJZiB0aGUgc3VwcGxpZWQKICAgICAqIGZ1bmN0aW9uIHJldHVybnMgdHJ1ZSBmb3IgYW4gZW50cnkgaXQgZ29lcyBpbnRvIGBsaHNgLiBPdGhlcndpc2UgaXQgZ29lcwogICAgICogaW50byBgcmhzLgogICAgICovCiAgICBmdW5jdGlvbiBwYXJ0aXRpb24kMihjb2xsZWN0aW9uLCBmbikgewogICAgICB2YXIgcmVzdWx0ID0geyBsaHM6IFtdLCByaHM6IFtdIH07CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChjb2xsZWN0aW9uLCBmdW5jdGlvbih2YWx1ZSkgewogICAgICAgIGlmIChmbih2YWx1ZSkpIHsKICAgICAgICAgIHJlc3VsdC5saHMucHVzaCh2YWx1ZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJlc3VsdC5yaHMucHVzaCh2YWx1ZSk7CiAgICAgICAgfQogICAgICB9KTsKICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KCiAgICAvKgogICAgICogUmV0dXJucyBhIG5ldyBmdW5jdGlvbiB0aGF0IHdyYXBzIGBmbmAgd2l0aCBhIHRpbWVyLiBUaGUgd3JhcHBlciBsb2dzIHRoZQogICAgICogdGltZSBpdCB0YWtlcyB0byBleGVjdXRlIHRoZSBmdW5jdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gdGltZSQyKG5hbWUsIGZuKSB7CiAgICAgIHZhciBzdGFydCA9IGxvZGFzaF8xJDEubm93KCk7CiAgICAgIHRyeSB7CiAgICAgICAgcmV0dXJuIGZuKCk7CiAgICAgIH0gZmluYWxseSB7CiAgICAgICAgY29uc29sZS5sb2cobmFtZSArICIgdGltZTogIiArIChsb2Rhc2hfMSQxLm5vdygpIC0gc3RhcnQpICsgIm1zIik7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBub3RpbWUobmFtZSwgZm4pIHsKICAgICAgcmV0dXJuIGZuKCk7CiAgICB9CgogICAgdmFyIG5vcm1hbGl6ZSQyID0gewogICAgICBydW46IHJ1biQxLAogICAgICB1bmRvOiB1bmRvJDEKICAgIH07CgogICAgLyoKICAgICAqIEJyZWFrcyBhbnkgbG9uZyBlZGdlcyBpbiB0aGUgZ3JhcGggaW50byBzaG9ydCBzZWdtZW50cyB0aGF0IHNwYW4gMSBsYXllcgogICAgICogZWFjaC4gVGhpcyBvcGVyYXRpb24gaXMgdW5kb2FibGUgd2l0aCB0aGUgZGVub3JtYWxpemUgZnVuY3Rpb24uCiAgICAgKgogICAgICogUHJlLWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gVGhlIGlucHV0IGdyYXBoIGlzIGEgREFHLgogICAgICogICAgMi4gRWFjaCBub2RlIGluIHRoZSBncmFwaCBoYXMgYSAicmFuayIgcHJvcGVydHkuCiAgICAgKgogICAgICogUG9zdC1jb25kaXRpb246CiAgICAgKgogICAgICogICAgMS4gQWxsIGVkZ2VzIGluIHRoZSBncmFwaCBoYXZlIGEgbGVuZ3RoIG9mIDEuCiAgICAgKiAgICAyLiBEdW1teSBub2RlcyBhcmUgYWRkZWQgd2hlcmUgZWRnZXMgaGF2ZSBiZWVuIHNwbGl0IGludG8gc2VnbWVudHMuCiAgICAgKiAgICAzLiBUaGUgZ3JhcGggaXMgYXVnbWVudGVkIHdpdGggYSAiZHVtbXlDaGFpbnMiIGF0dHJpYnV0ZSB3aGljaCBjb250YWlucwogICAgICogICAgICAgdGhlIGZpcnN0IGR1bW15IGluIGVhY2ggY2hhaW4gb2YgZHVtbXkgbm9kZXMgcHJvZHVjZWQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHJ1biQxKGcpIHsKICAgICAgZy5ncmFwaCgpLmR1bW15Q2hhaW5zID0gW107CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGVkZ2UpIHsgbm9ybWFsaXplRWRnZShnLCBlZGdlKTsgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gbm9ybWFsaXplRWRnZShnLCBlKSB7CiAgICAgIHZhciB2ID0gZS52OwogICAgICB2YXIgdlJhbmsgPSBnLm5vZGUodikucmFuazsKICAgICAgdmFyIHcgPSBlLnc7CiAgICAgIHZhciB3UmFuayA9IGcubm9kZSh3KS5yYW5rOwogICAgICB2YXIgbmFtZSA9IGUubmFtZTsKICAgICAgdmFyIGVkZ2VMYWJlbCA9IGcuZWRnZShlKTsKICAgICAgdmFyIGxhYmVsUmFuayA9IGVkZ2VMYWJlbC5sYWJlbFJhbms7CgogICAgICBpZiAod1JhbmsgPT09IHZSYW5rICsgMSkgcmV0dXJuOwoKICAgICAgZy5yZW1vdmVFZGdlKGUpOwoKICAgICAgdmFyIGR1bW15LCBhdHRycywgaTsKICAgICAgZm9yIChpID0gMCwgKyt2UmFuazsgdlJhbmsgPCB3UmFuazsgKytpLCArK3ZSYW5rKSB7CiAgICAgICAgZWRnZUxhYmVsLnBvaW50cyA9IFtdOwogICAgICAgIGF0dHJzID0gewogICAgICAgICAgd2lkdGg6IDAsIGhlaWdodDogMCwKICAgICAgICAgIGVkZ2VMYWJlbDogZWRnZUxhYmVsLCBlZGdlT2JqOiBlLAogICAgICAgICAgcmFuazogdlJhbmsKICAgICAgICB9OwogICAgICAgIGR1bW15ID0gdXRpbC5hZGREdW1teU5vZGUoZywgImVkZ2UiLCBhdHRycywgIl9kIik7CiAgICAgICAgaWYgKHZSYW5rID09PSBsYWJlbFJhbmspIHsKICAgICAgICAgIGF0dHJzLndpZHRoID0gZWRnZUxhYmVsLndpZHRoOwogICAgICAgICAgYXR0cnMuaGVpZ2h0ID0gZWRnZUxhYmVsLmhlaWdodDsKICAgICAgICAgIGF0dHJzLmR1bW15ID0gImVkZ2UtbGFiZWwiOwogICAgICAgICAgYXR0cnMubGFiZWxwb3MgPSBlZGdlTGFiZWwubGFiZWxwb3M7CiAgICAgICAgfQogICAgICAgIGcuc2V0RWRnZSh2LCBkdW1teSwgeyB3ZWlnaHQ6IGVkZ2VMYWJlbC53ZWlnaHQgfSwgbmFtZSk7CiAgICAgICAgaWYgKGkgPT09IDApIHsKICAgICAgICAgIGcuZ3JhcGgoKS5kdW1teUNoYWlucy5wdXNoKGR1bW15KTsKICAgICAgICB9CiAgICAgICAgdiA9IGR1bW15OwogICAgICB9CgogICAgICBnLnNldEVkZ2UodiwgdywgeyB3ZWlnaHQ6IGVkZ2VMYWJlbC53ZWlnaHQgfSwgbmFtZSk7CiAgICB9CgogICAgZnVuY3Rpb24gdW5kbyQxKGcpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZ3JhcGgoKS5kdW1teUNoYWlucywgZnVuY3Rpb24odikgewogICAgICAgIHZhciBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIHZhciBvcmlnTGFiZWwgPSBub2RlLmVkZ2VMYWJlbDsKICAgICAgICB2YXIgdzsKICAgICAgICBnLnNldEVkZ2Uobm9kZS5lZGdlT2JqLCBvcmlnTGFiZWwpOwogICAgICAgIHdoaWxlIChub2RlLmR1bW15KSB7CiAgICAgICAgICB3ID0gZy5zdWNjZXNzb3JzKHYpWzBdOwogICAgICAgICAgZy5yZW1vdmVOb2RlKHYpOwogICAgICAgICAgb3JpZ0xhYmVsLnBvaW50cy5wdXNoKHsgeDogbm9kZS54LCB5OiBub2RlLnkgfSk7CiAgICAgICAgICBpZiAobm9kZS5kdW1teSA9PT0gImVkZ2UtbGFiZWwiKSB7CiAgICAgICAgICAgIG9yaWdMYWJlbC54ID0gbm9kZS54OwogICAgICAgICAgICBvcmlnTGFiZWwueSA9IG5vZGUueTsKICAgICAgICAgICAgb3JpZ0xhYmVsLndpZHRoID0gbm9kZS53aWR0aDsKICAgICAgICAgICAgb3JpZ0xhYmVsLmhlaWdodCA9IG5vZGUuaGVpZ2h0OwogICAgICAgICAgfQogICAgICAgICAgdiA9IHc7CiAgICAgICAgICBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgdmFyIHV0aWwkMSA9IHsKICAgICAgbG9uZ2VzdFBhdGg6IGxvbmdlc3RQYXRoLAogICAgICBzbGFjazogc2xhY2sKICAgIH07CgogICAgLyoKICAgICAqIEluaXRpYWxpemVzIHJhbmtzIGZvciB0aGUgaW5wdXQgZ3JhcGggdXNpbmcgdGhlIGxvbmdlc3QgcGF0aCBhbGdvcml0aG0uIFRoaXMKICAgICAqIGFsZ29yaXRobSBzY2FsZXMgd2VsbCBhbmQgaXMgZmFzdCBpbiBwcmFjdGljZSwgaXQgeWllbGRzIHJhdGhlciBwb29yCiAgICAgKiBzb2x1dGlvbnMuIE5vZGVzIGFyZSBwdXNoZWQgdG8gdGhlIGxvd2VzdCBsYXllciBwb3NzaWJsZSwgbGVhdmluZyB0aGUgYm90dG9tCiAgICAgKiByYW5rcyB3aWRlIGFuZCBsZWF2aW5nIGVkZ2VzIGxvbmdlciB0aGFuIG5lY2Vzc2FyeS4gSG93ZXZlciwgZHVlIHRvIGl0cwogICAgICogc3BlZWQsIHRoaXMgYWxnb3JpdGhtIGlzIGdvb2QgZm9yIGdldHRpbmcgYW4gaW5pdGlhbCByYW5raW5nIHRoYXQgY2FuIGJlIGZlZAogICAgICogaW50byBvdGhlciBhbGdvcml0aG1zLgogICAgICoKICAgICAqIFRoaXMgYWxnb3JpdGhtIGRvZXMgbm90IG5vcm1hbGl6ZSBsYXllcnMgYmVjYXVzZSBpdCB3aWxsIGJlIHVzZWQgYnkgb3RoZXIKICAgICAqIGFsZ29yaXRobXMgaW4gbW9zdCBjYXNlcy4gSWYgdXNpbmcgdGhpcyBhbGdvcml0aG0gZGlyZWN0bHksIGJlIHN1cmUgdG8KICAgICAqIHJ1biBub3JtYWxpemUgYXQgdGhlIGVuZC4KICAgICAqCiAgICAgKiBQcmUtY29uZGl0aW9uczoKICAgICAqCiAgICAgKiAgICAxLiBJbnB1dCBncmFwaCBpcyBhIERBRy4KICAgICAqICAgIDIuIElucHV0IGdyYXBoIG5vZGUgbGFiZWxzIGNhbiBiZSBhc3NpZ25lZCBwcm9wZXJ0aWVzLgogICAgICoKICAgICAqIFBvc3QtY29uZGl0aW9uczoKICAgICAqCiAgICAgKiAgICAxLiBFYWNoIG5vZGUgd2lsbCBiZSBhc3NpZ24gYW4gKHVubm9ybWFsaXplZCkgInJhbmsiIHByb3BlcnR5LgogICAgICovCiAgICBmdW5jdGlvbiBsb25nZXN0UGF0aChnKSB7CiAgICAgIHZhciB2aXNpdGVkID0ge307CgogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIHZhciBsYWJlbCA9IGcubm9kZSh2KTsKICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXModmlzaXRlZCwgdikpIHsKICAgICAgICAgIHJldHVybiBsYWJlbC5yYW5rOwogICAgICAgIH0KICAgICAgICB2aXNpdGVkW3ZdID0gdHJ1ZTsKCiAgICAgICAgdmFyIHJhbmsgPSBsb2Rhc2hfMSQxLm1pbihsb2Rhc2hfMSQxLm1hcChnLm91dEVkZ2VzKHYpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgICByZXR1cm4gZGZzKGUudykgLSBnLmVkZ2UoZSkubWlubGVuOwogICAgICAgIH0pKTsKCiAgICAgICAgaWYgKHJhbmsgPT09IE51bWJlci5QT1NJVElWRV9JTkZJTklUWSB8fCAvLyByZXR1cm4gdmFsdWUgb2YgXy5tYXAoW10pIGZvciBMb2Rhc2ggMwogICAgICAgICAgICByYW5rID09PSB1bmRlZmluZWQgfHwgLy8gcmV0dXJuIHZhbHVlIG9mIF8ubWFwKFtdKSBmb3IgTG9kYXNoIDQKICAgICAgICAgICAgcmFuayA9PT0gbnVsbCkgeyAvLyByZXR1cm4gdmFsdWUgb2YgXy5tYXAoW251bGxdKQogICAgICAgICAgcmFuayA9IDA7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gKGxhYmVsLnJhbmsgPSByYW5rKTsKICAgICAgfQoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuc291cmNlcygpLCBkZnMpOwogICAgfQoKICAgIC8qCiAgICAgKiBSZXR1cm5zIHRoZSBhbW91bnQgb2Ygc2xhY2sgZm9yIHRoZSBnaXZlbiBlZGdlLiBUaGUgc2xhY2sgaXMgZGVmaW5lZCBhcyB0aGUKICAgICAqIGRpZmZlcmVuY2UgYmV0d2VlbiB0aGUgbGVuZ3RoIG9mIHRoZSBlZGdlIGFuZCBpdHMgbWluaW11bSBsZW5ndGguCiAgICAgKi8KICAgIGZ1bmN0aW9uIHNsYWNrKGcsIGUpIHsKICAgICAgcmV0dXJuIGcubm9kZShlLncpLnJhbmsgLSBnLm5vZGUoZS52KS5yYW5rIC0gZy5lZGdlKGUpLm1pbmxlbjsKICAgIH0KCiAgICB2YXIgR3JhcGgkMyA9IGdyYXBobGliXzEuR3JhcGg7CiAgICB2YXIgc2xhY2skMSA9IHV0aWwkMS5zbGFjazsKCiAgICB2YXIgZmVhc2libGVUcmVlXzEgPSBmZWFzaWJsZVRyZWU7CgogICAgLyoKICAgICAqIENvbnN0cnVjdHMgYSBzcGFubmluZyB0cmVlIHdpdGggdGlnaHQgZWRnZXMgYW5kIGFkanVzdGVkIHRoZSBpbnB1dCBub2RlJ3MKICAgICAqIHJhbmtzIHRvIGFjaGlldmUgdGhpcy4gQSB0aWdodCBlZGdlIGlzIG9uZSB0aGF0IGlzIGhhcyBhIGxlbmd0aCB0aGF0IG1hdGNoZXMKICAgICAqIGl0cyAibWlubGVuIiBhdHRyaWJ1dGUuCiAgICAgKgogICAgICogVGhlIGJhc2ljIHN0cnVjdHVyZSBmb3IgdGhpcyBmdW5jdGlvbiBpcyBkZXJpdmVkIGZyb20gR2Fuc25lciwgZXQgYWwuLCAiQQogICAgICogVGVjaG5pcXVlIGZvciBEcmF3aW5nIERpcmVjdGVkIEdyYXBocy4iCiAgICAgKgogICAgICogUHJlLWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gR3JhcGggbXVzdCBiZSBhIERBRy4KICAgICAqICAgIDIuIEdyYXBoIG11c3QgYmUgY29ubmVjdGVkLgogICAgICogICAgMy4gR3JhcGggbXVzdCBoYXZlIGF0IGxlYXN0IG9uZSBub2RlLgogICAgICogICAgNS4gR3JhcGggbm9kZXMgbXVzdCBoYXZlIGJlZW4gcHJldmlvdXNseSBhc3NpZ25lZCBhICJyYW5rIiBwcm9wZXJ0eSB0aGF0CiAgICAgKiAgICAgICByZXNwZWN0cyB0aGUgIm1pbmxlbiIgcHJvcGVydHkgb2YgaW5jaWRlbnQgZWRnZXMuCiAgICAgKiAgICA2LiBHcmFwaCBlZGdlcyBtdXN0IGhhdmUgYSAibWlubGVuIiBwcm9wZXJ0eS4KICAgICAqCiAgICAgKiBQb3N0LWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgLSBHcmFwaCBub2RlcyB3aWxsIGhhdmUgdGhlaXIgcmFuayBhZGp1c3RlZCB0byBlbnN1cmUgdGhhdCBhbGwgZWRnZXMgYXJlCiAgICAgKiAgICAgIHRpZ2h0LgogICAgICoKICAgICAqIFJldHVybnMgYSB0cmVlICh1bmRpcmVjdGVkIGdyYXBoKSB0aGF0IGlzIGNvbnN0cnVjdGVkIHVzaW5nIG9ubHkgInRpZ2h0IgogICAgICogZWRnZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZlYXNpYmxlVHJlZShnKSB7CiAgICAgIHZhciB0ID0gbmV3IEdyYXBoJDMoeyBkaXJlY3RlZDogZmFsc2UgfSk7CgogICAgICAvLyBDaG9vc2UgYXJiaXRyYXJ5IG5vZGUgZnJvbSB3aGljaCB0byBzdGFydCBvdXIgdHJlZQogICAgICB2YXIgc3RhcnQgPSBnLm5vZGVzKClbMF07CiAgICAgIHZhciBzaXplID0gZy5ub2RlQ291bnQoKTsKICAgICAgdC5zZXROb2RlKHN0YXJ0LCB7fSk7CgogICAgICB2YXIgZWRnZSwgZGVsdGE7CiAgICAgIHdoaWxlICh0aWdodFRyZWUodCwgZykgPCBzaXplKSB7CiAgICAgICAgZWRnZSA9IGZpbmRNaW5TbGFja0VkZ2UodCwgZyk7CiAgICAgICAgZGVsdGEgPSB0Lmhhc05vZGUoZWRnZS52KSA/IHNsYWNrJDEoZywgZWRnZSkgOiAtc2xhY2skMShnLCBlZGdlKTsKICAgICAgICBzaGlmdFJhbmtzKHQsIGcsIGRlbHRhKTsKICAgICAgfQoKICAgICAgcmV0dXJuIHQ7CiAgICB9CgogICAgLyoKICAgICAqIEZpbmRzIGEgbWF4aW1hbCB0cmVlIG9mIHRpZ2h0IGVkZ2VzIGFuZCByZXR1cm5zIHRoZSBudW1iZXIgb2Ygbm9kZXMgaW4gdGhlCiAgICAgKiB0cmVlLgogICAgICovCiAgICBmdW5jdGlvbiB0aWdodFRyZWUodCwgZykgewogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVFZGdlcyh2KSwgZnVuY3Rpb24oZSkgewogICAgICAgICAgdmFyIGVkZ2VWID0gZS52LAogICAgICAgICAgICB3ID0gKHYgPT09IGVkZ2VWKSA/IGUudyA6IGVkZ2VWOwogICAgICAgICAgaWYgKCF0Lmhhc05vZGUodykgJiYgIXNsYWNrJDEoZywgZSkpIHsKICAgICAgICAgICAgdC5zZXROb2RlKHcsIHt9KTsKICAgICAgICAgICAgdC5zZXRFZGdlKHYsIHcsIHt9KTsKICAgICAgICAgICAgZGZzKHcpOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2godC5ub2RlcygpLCBkZnMpOwogICAgICByZXR1cm4gdC5ub2RlQ291bnQoKTsKICAgIH0KCiAgICAvKgogICAgICogRmluZHMgdGhlIGVkZ2Ugd2l0aCB0aGUgc21hbGxlc3Qgc2xhY2sgdGhhdCBpcyBpbmNpZGVudCBvbiB0cmVlIGFuZCByZXR1cm5zCiAgICAgKiBpdC4KICAgICAqLwogICAgZnVuY3Rpb24gZmluZE1pblNsYWNrRWRnZSh0LCBnKSB7CiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLm1pbkJ5KGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIGlmICh0Lmhhc05vZGUoZS52KSAhPT0gdC5oYXNOb2RlKGUudykpIHsKICAgICAgICAgIHJldHVybiBzbGFjayQxKGcsIGUpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gc2hpZnRSYW5rcyh0LCBnLCBkZWx0YSkgewogICAgICBsb2Rhc2hfMSQxLmZvckVhY2godC5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgZy5ub2RlKHYpLnJhbmsgKz0gZGVsdGE7CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBzbGFjayQyID0gdXRpbCQxLnNsYWNrOwogICAgdmFyIGluaXRSYW5rID0gdXRpbCQxLmxvbmdlc3RQYXRoOwogICAgdmFyIHByZW9yZGVyJDEgPSBncmFwaGxpYl8xLmFsZy5wcmVvcmRlcjsKICAgIHZhciBwb3N0b3JkZXIkMSA9IGdyYXBobGliXzEuYWxnLnBvc3RvcmRlcjsKICAgIHZhciBzaW1wbGlmeSQxID0gdXRpbC5zaW1wbGlmeTsKCiAgICB2YXIgbmV0d29ya1NpbXBsZXhfMSA9IG5ldHdvcmtTaW1wbGV4OwoKICAgIC8vIEV4cG9zZSBzb21lIGludGVybmFscyBmb3IgdGVzdGluZyBwdXJwb3NlcwogICAgbmV0d29ya1NpbXBsZXguaW5pdExvd0xpbVZhbHVlcyA9IGluaXRMb3dMaW1WYWx1ZXM7CiAgICBuZXR3b3JrU2ltcGxleC5pbml0Q3V0VmFsdWVzID0gaW5pdEN1dFZhbHVlczsKICAgIG5ldHdvcmtTaW1wbGV4LmNhbGNDdXRWYWx1ZSA9IGNhbGNDdXRWYWx1ZTsKICAgIG5ldHdvcmtTaW1wbGV4LmxlYXZlRWRnZSA9IGxlYXZlRWRnZTsKICAgIG5ldHdvcmtTaW1wbGV4LmVudGVyRWRnZSA9IGVudGVyRWRnZTsKICAgIG5ldHdvcmtTaW1wbGV4LmV4Y2hhbmdlRWRnZXMgPSBleGNoYW5nZUVkZ2VzOwoKICAgIC8qCiAgICAgKiBUaGUgbmV0d29yayBzaW1wbGV4IGFsZ29yaXRobSBhc3NpZ25zIHJhbmtzIHRvIGVhY2ggbm9kZSBpbiB0aGUgaW5wdXQgZ3JhcGgKICAgICAqIGFuZCBpdGVyYXRpdmVseSBpbXByb3ZlcyB0aGUgcmFua2luZyB0byByZWR1Y2UgdGhlIGxlbmd0aCBvZiBlZGdlcy4KICAgICAqCiAgICAgKiBQcmVjb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIFRoZSBpbnB1dCBncmFwaCBtdXN0IGJlIGEgREFHLgogICAgICogICAgMi4gQWxsIG5vZGVzIGluIHRoZSBncmFwaCBtdXN0IGhhdmUgYW4gb2JqZWN0IHZhbHVlLgogICAgICogICAgMy4gQWxsIGVkZ2VzIGluIHRoZSBncmFwaCBtdXN0IGhhdmUgIm1pbmxlbiIgYW5kICJ3ZWlnaHQiIGF0dHJpYnV0ZXMuCiAgICAgKgogICAgICogUG9zdGNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gQWxsIG5vZGVzIGluIHRoZSBncmFwaCB3aWxsIGhhdmUgYW4gYXNzaWduZWQgInJhbmsiIGF0dHJpYnV0ZSB0aGF0IGhhcwogICAgICogICAgICAgYmVlbiBvcHRpbWl6ZWQgYnkgdGhlIG5ldHdvcmsgc2ltcGxleCBhbGdvcml0aG0uIFJhbmtzIHN0YXJ0IGF0IDAuCiAgICAgKgogICAgICoKICAgICAqIEEgcm91Z2ggc2tldGNoIG9mIHRoZSBhbGdvcml0aG0gaXMgYXMgZm9sbG93czoKICAgICAqCiAgICAgKiAgICAxLiBBc3NpZ24gaW5pdGlhbCByYW5rcyB0byBlYWNoIG5vZGUuIFdlIHVzZSB0aGUgbG9uZ2VzdCBwYXRoIGFsZ29yaXRobSwKICAgICAqICAgICAgIHdoaWNoIGFzc2lnbnMgcmFua3MgdG8gdGhlIGxvd2VzdCBwb3NpdGlvbiBwb3NzaWJsZS4gSW4gZ2VuZXJhbCB0aGlzCiAgICAgKiAgICAgICBsZWFkcyB0byB2ZXJ5IHdpZGUgYm90dG9tIHJhbmtzIGFuZCB1bm5lY2Vzc2FyaWx5IGxvbmcgZWRnZXMuCiAgICAgKiAgICAyLiBDb25zdHJ1Y3QgYSBmZWFzaWJsZSB0aWdodCB0cmVlLiBBIHRpZ2h0IHRyZWUgaXMgb25lIHN1Y2ggdGhhdCBhbGwKICAgICAqICAgICAgIGVkZ2VzIGluIHRoZSB0cmVlIGhhdmUgbm8gc2xhY2sgKGRpZmZlcmVuY2UgYmV0d2VlbiBsZW5ndGggb2YgZWRnZQogICAgICogICAgICAgYW5kIG1pbmxlbiBmb3IgdGhlIGVkZ2UpLiBUaGlzIGJ5IGl0c2VsZiBncmVhdGx5IGltcHJvdmVzIHRoZSBhc3NpZ25lZAogICAgICogICAgICAgcmFua2luZ3MgYnkgc2hvcnRpbmcgZWRnZXMuCiAgICAgKiAgICAzLiBJdGVyYXRpdmVseSBmaW5kIGVkZ2VzIHRoYXQgaGF2ZSBuZWdhdGl2ZSBjdXQgdmFsdWVzLiBHZW5lcmFsbHkgYQogICAgICogICAgICAgbmVnYXRpdmUgY3V0IHZhbHVlIGluZGljYXRlcyB0aGF0IHRoZSBlZGdlIGNvdWxkIGJlIHJlbW92ZWQgYW5kIGEgbmV3CiAgICAgKiAgICAgICB0cmVlIGVkZ2UgY291bGQgYmUgYWRkZWQgdG8gcHJvZHVjZSBhIG1vcmUgY29tcGFjdCBncmFwaC4KICAgICAqCiAgICAgKiBNdWNoIG9mIHRoZSBhbGdvcml0aG1zIGhlcmUgYXJlIGRlcml2ZWQgZnJvbSBHYW5zbmVyLCBldCBhbC4sICJBIFRlY2huaXF1ZQogICAgICogZm9yIERyYXdpbmcgRGlyZWN0ZWQgR3JhcGhzLiIgVGhlIHN0cnVjdHVyZSBvZiB0aGUgZmlsZSByb3VnaGx5IGZvbGxvd3MgdGhlCiAgICAgKiBzdHJ1Y3R1cmUgb2YgdGhlIG92ZXJhbGwgYWxnb3JpdGhtLgogICAgICovCiAgICBmdW5jdGlvbiBuZXR3b3JrU2ltcGxleChnKSB7CiAgICAgIGcgPSBzaW1wbGlmeSQxKGcpOwogICAgICBpbml0UmFuayhnKTsKICAgICAgdmFyIHQgPSBmZWFzaWJsZVRyZWVfMShnKTsKICAgICAgaW5pdExvd0xpbVZhbHVlcyh0KTsKICAgICAgaW5pdEN1dFZhbHVlcyh0LCBnKTsKCiAgICAgIHZhciBlLCBmOwogICAgICB3aGlsZSAoKGUgPSBsZWF2ZUVkZ2UodCkpKSB7CiAgICAgICAgZiA9IGVudGVyRWRnZSh0LCBnLCBlKTsKICAgICAgICBleGNoYW5nZUVkZ2VzKHQsIGcsIGUsIGYpOwogICAgICB9CiAgICB9CgogICAgLyoKICAgICAqIEluaXRpYWxpemVzIGN1dCB2YWx1ZXMgZm9yIGFsbCBlZGdlcyBpbiB0aGUgdHJlZS4KICAgICAqLwogICAgZnVuY3Rpb24gaW5pdEN1dFZhbHVlcyh0LCBnKSB7CiAgICAgIHZhciB2cyA9IHBvc3RvcmRlciQxKHQsIHQubm9kZXMoKSk7CiAgICAgIHZzID0gdnMuc2xpY2UoMCwgdnMubGVuZ3RoIC0gMSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaCh2cywgZnVuY3Rpb24odikgewogICAgICAgIGFzc2lnbkN1dFZhbHVlKHQsIGcsIHYpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc3NpZ25DdXRWYWx1ZSh0LCBnLCBjaGlsZCkgewogICAgICB2YXIgY2hpbGRMYWIgPSB0Lm5vZGUoY2hpbGQpOwogICAgICB2YXIgcGFyZW50ID0gY2hpbGRMYWIucGFyZW50OwogICAgICB0LmVkZ2UoY2hpbGQsIHBhcmVudCkuY3V0dmFsdWUgPSBjYWxjQ3V0VmFsdWUodCwgZywgY2hpbGQpOwogICAgfQoKICAgIC8qCiAgICAgKiBHaXZlbiB0aGUgdGlnaHQgdHJlZSwgaXRzIGdyYXBoLCBhbmQgYSBjaGlsZCBpbiB0aGUgZ3JhcGggY2FsY3VsYXRlIGFuZAogICAgICogcmV0dXJuIHRoZSBjdXQgdmFsdWUgZm9yIHRoZSBlZGdlIGJldHdlZW4gdGhlIGNoaWxkIGFuZCBpdHMgcGFyZW50LgogICAgICovCiAgICBmdW5jdGlvbiBjYWxjQ3V0VmFsdWUodCwgZywgY2hpbGQpIHsKICAgICAgdmFyIGNoaWxkTGFiID0gdC5ub2RlKGNoaWxkKTsKICAgICAgdmFyIHBhcmVudCA9IGNoaWxkTGFiLnBhcmVudDsKICAgICAgLy8gVHJ1ZSBpZiB0aGUgY2hpbGQgaXMgb24gdGhlIHRhaWwgZW5kIG9mIHRoZSBlZGdlIGluIHRoZSBkaXJlY3RlZCBncmFwaAogICAgICB2YXIgY2hpbGRJc1RhaWwgPSB0cnVlOwogICAgICAvLyBUaGUgZ3JhcGgncyB2aWV3IG9mIHRoZSB0cmVlIGVkZ2Ugd2UncmUgaW5zcGVjdGluZwogICAgICB2YXIgZ3JhcGhFZGdlID0gZy5lZGdlKGNoaWxkLCBwYXJlbnQpOwogICAgICAvLyBUaGUgYWNjdW11bGF0ZWQgY3V0IHZhbHVlIGZvciB0aGUgZWRnZSBiZXR3ZWVuIHRoaXMgbm9kZSBhbmQgaXRzIHBhcmVudAogICAgICB2YXIgY3V0VmFsdWUgPSAwOwoKICAgICAgaWYgKCFncmFwaEVkZ2UpIHsKICAgICAgICBjaGlsZElzVGFpbCA9IGZhbHNlOwogICAgICAgIGdyYXBoRWRnZSA9IGcuZWRnZShwYXJlbnQsIGNoaWxkKTsKICAgICAgfQoKICAgICAgY3V0VmFsdWUgPSBncmFwaEVkZ2Uud2VpZ2h0OwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZUVkZ2VzKGNoaWxkKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBpc091dEVkZ2UgPSBlLnYgPT09IGNoaWxkLAogICAgICAgICAgb3RoZXIgPSBpc091dEVkZ2UgPyBlLncgOiBlLnY7CgogICAgICAgIGlmIChvdGhlciAhPT0gcGFyZW50KSB7CiAgICAgICAgICB2YXIgcG9pbnRzVG9IZWFkID0gaXNPdXRFZGdlID09PSBjaGlsZElzVGFpbCwKICAgICAgICAgICAgb3RoZXJXZWlnaHQgPSBnLmVkZ2UoZSkud2VpZ2h0OwoKICAgICAgICAgIGN1dFZhbHVlICs9IHBvaW50c1RvSGVhZCA/IG90aGVyV2VpZ2h0IDogLW90aGVyV2VpZ2h0OwogICAgICAgICAgaWYgKGlzVHJlZUVkZ2UodCwgY2hpbGQsIG90aGVyKSkgewogICAgICAgICAgICB2YXIgb3RoZXJDdXRWYWx1ZSA9IHQuZWRnZShjaGlsZCwgb3RoZXIpLmN1dHZhbHVlOwogICAgICAgICAgICBjdXRWYWx1ZSArPSBwb2ludHNUb0hlYWQgPyAtb3RoZXJDdXRWYWx1ZSA6IG90aGVyQ3V0VmFsdWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9KTsKCiAgICAgIHJldHVybiBjdXRWYWx1ZTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbml0TG93TGltVmFsdWVzKHRyZWUsIHJvb3QpIHsKICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPCAyKSB7CiAgICAgICAgcm9vdCA9IHRyZWUubm9kZXMoKVswXTsKICAgICAgfQogICAgICBkZnNBc3NpZ25Mb3dMaW0odHJlZSwge30sIDEsIHJvb3QpOwogICAgfQoKICAgIGZ1bmN0aW9uIGRmc0Fzc2lnbkxvd0xpbSh0cmVlLCB2aXNpdGVkLCBuZXh0TGltLCB2LCBwYXJlbnQpIHsKICAgICAgdmFyIGxvdyA9IG5leHRMaW07CiAgICAgIHZhciBsYWJlbCA9IHRyZWUubm9kZSh2KTsKCiAgICAgIHZpc2l0ZWRbdl0gPSB0cnVlOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2godHJlZS5uZWlnaGJvcnModiksIGZ1bmN0aW9uKHcpIHsKICAgICAgICBpZiAoIWxvZGFzaF8xJDEuaGFzKHZpc2l0ZWQsIHcpKSB7CiAgICAgICAgICBuZXh0TGltID0gZGZzQXNzaWduTG93TGltKHRyZWUsIHZpc2l0ZWQsIG5leHRMaW0sIHcsIHYpOwogICAgICAgIH0KICAgICAgfSk7CgogICAgICBsYWJlbC5sb3cgPSBsb3c7CiAgICAgIGxhYmVsLmxpbSA9IG5leHRMaW0rKzsKICAgICAgaWYgKHBhcmVudCkgewogICAgICAgIGxhYmVsLnBhcmVudCA9IHBhcmVudDsKICAgICAgfSBlbHNlIHsKICAgICAgICAvLyBUT0RPIHNob3VsZCBiZSBhYmxlIHRvIHJlbW92ZSB0aGlzIHdoZW4gd2UgaW5jcmVtZW50YWxseSB1cGRhdGUgbG93IGxpbQogICAgICAgIGRlbGV0ZSBsYWJlbC5wYXJlbnQ7CiAgICAgIH0KCiAgICAgIHJldHVybiBuZXh0TGltOwogICAgfQoKICAgIGZ1bmN0aW9uIGxlYXZlRWRnZSh0cmVlKSB7CiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLmZpbmQodHJlZS5lZGdlcygpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgcmV0dXJuIHRyZWUuZWRnZShlKS5jdXR2YWx1ZSA8IDA7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGVudGVyRWRnZSh0LCBnLCBlZGdlKSB7CiAgICAgIHZhciB2ID0gZWRnZS52OwogICAgICB2YXIgdyA9IGVkZ2UudzsKCiAgICAgIC8vIEZvciB0aGUgcmVzdCBvZiB0aGlzIGZ1bmN0aW9uIHdlIGFzc3VtZSB0aGF0IHYgaXMgdGhlIHRhaWwgYW5kIHcgaXMgdGhlCiAgICAgIC8vIGhlYWQsIHNvIGlmIHdlIGRvbid0IGhhdmUgdGhpcyBlZGdlIGluIHRoZSBncmFwaCB3ZSBzaG91bGQgZmxpcCBpdCB0bwogICAgICAvLyBtYXRjaCB0aGUgY29ycmVjdCBvcmllbnRhdGlvbi4KICAgICAgaWYgKCFnLmhhc0VkZ2UodiwgdykpIHsKICAgICAgICB2ID0gZWRnZS53OwogICAgICAgIHcgPSBlZGdlLnY7CiAgICAgIH0KCiAgICAgIHZhciB2TGFiZWwgPSB0Lm5vZGUodik7CiAgICAgIHZhciB3TGFiZWwgPSB0Lm5vZGUodyk7CiAgICAgIHZhciB0YWlsTGFiZWwgPSB2TGFiZWw7CiAgICAgIHZhciBmbGlwID0gZmFsc2U7CgogICAgICAvLyBJZiB0aGUgcm9vdCBpcyBpbiB0aGUgdGFpbCBvZiB0aGUgZWRnZSB0aGVuIHdlIG5lZWQgdG8gZmxpcCB0aGUgbG9naWMgdGhhdAogICAgICAvLyBjaGVja3MgZm9yIHRoZSBoZWFkIGFuZCB0YWlsIG5vZGVzIGluIHRoZSBjYW5kaWRhdGVzIGZ1bmN0aW9uIGJlbG93LgogICAgICBpZiAodkxhYmVsLmxpbSA+IHdMYWJlbC5saW0pIHsKICAgICAgICB0YWlsTGFiZWwgPSB3TGFiZWw7CiAgICAgICAgZmxpcCA9IHRydWU7CiAgICAgIH0KCiAgICAgIHZhciBjYW5kaWRhdGVzID0gbG9kYXNoXzEkMS5maWx0ZXIoZy5lZGdlcygpLCBmdW5jdGlvbihlZGdlKSB7CiAgICAgICAgcmV0dXJuIGZsaXAgPT09IGlzRGVzY2VuZGFudCQxKHQsIHQubm9kZShlZGdlLnYpLCB0YWlsTGFiZWwpICYmCiAgICAgICAgICAgICAgIGZsaXAgIT09IGlzRGVzY2VuZGFudCQxKHQsIHQubm9kZShlZGdlLncpLCB0YWlsTGFiZWwpOwogICAgICB9KTsKCiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLm1pbkJ5KGNhbmRpZGF0ZXMsIGZ1bmN0aW9uKGVkZ2UpIHsgcmV0dXJuIHNsYWNrJDIoZywgZWRnZSk7IH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGV4Y2hhbmdlRWRnZXModCwgZywgZSwgZikgewogICAgICB2YXIgdiA9IGUudjsKICAgICAgdmFyIHcgPSBlLnc7CiAgICAgIHQucmVtb3ZlRWRnZSh2LCB3KTsKICAgICAgdC5zZXRFZGdlKGYudiwgZi53LCB7fSk7CiAgICAgIGluaXRMb3dMaW1WYWx1ZXModCk7CiAgICAgIGluaXRDdXRWYWx1ZXModCwgZyk7CiAgICAgIHVwZGF0ZVJhbmtzKHQsIGcpOwogICAgfQoKICAgIGZ1bmN0aW9uIHVwZGF0ZVJhbmtzKHQsIGcpIHsKICAgICAgdmFyIHJvb3QgPSBsb2Rhc2hfMSQxLmZpbmQodC5ub2RlcygpLCBmdW5jdGlvbih2KSB7IHJldHVybiAhZy5ub2RlKHYpLnBhcmVudDsgfSk7CiAgICAgIHZhciB2cyA9IHByZW9yZGVyJDEodCwgcm9vdCk7CiAgICAgIHZzID0gdnMuc2xpY2UoMSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaCh2cywgZnVuY3Rpb24odikgewogICAgICAgIHZhciBwYXJlbnQgPSB0Lm5vZGUodikucGFyZW50LAogICAgICAgICAgZWRnZSA9IGcuZWRnZSh2LCBwYXJlbnQpLAogICAgICAgICAgZmxpcHBlZCA9IGZhbHNlOwoKICAgICAgICBpZiAoIWVkZ2UpIHsKICAgICAgICAgIGVkZ2UgPSBnLmVkZ2UocGFyZW50LCB2KTsKICAgICAgICAgIGZsaXBwZWQgPSB0cnVlOwogICAgICAgIH0KCiAgICAgICAgZy5ub2RlKHYpLnJhbmsgPSBnLm5vZGUocGFyZW50KS5yYW5rICsgKGZsaXBwZWQgPyBlZGdlLm1pbmxlbiA6IC1lZGdlLm1pbmxlbik7CiAgICAgIH0pOwogICAgfQoKICAgIC8qCiAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhlIGVkZ2UgaXMgaW4gdGhlIHRyZWUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzVHJlZUVkZ2UodHJlZSwgdSwgdikgewogICAgICByZXR1cm4gdHJlZS5oYXNFZGdlKHUsIHYpOwogICAgfQoKICAgIC8qCiAgICAgKiBSZXR1cm5zIHRydWUgaWYgdGhlIHNwZWNpZmllZCBub2RlIGlzIGRlc2NlbmRhbnQgb2YgdGhlIHJvb3Qgbm9kZSBwZXIgdGhlCiAgICAgKiBhc3NpZ25lZCBsb3cgYW5kIGxpbSBhdHRyaWJ1dGVzIGluIHRoZSB0cmVlLgogICAgICovCiAgICBmdW5jdGlvbiBpc0Rlc2NlbmRhbnQkMSh0cmVlLCB2TGFiZWwsIHJvb3RMYWJlbCkgewogICAgICByZXR1cm4gcm9vdExhYmVsLmxvdyA8PSB2TGFiZWwubGltICYmIHZMYWJlbC5saW0gPD0gcm9vdExhYmVsLmxpbTsKICAgIH0KCiAgICB2YXIgbG9uZ2VzdFBhdGgkMSA9IHV0aWwkMS5sb25nZXN0UGF0aDsKCgoKICAgIHZhciByYW5rXzEgPSByYW5rOwoKICAgIC8qCiAgICAgKiBBc3NpZ25zIGEgcmFuayB0byBlYWNoIG5vZGUgaW4gdGhlIGlucHV0IGdyYXBoIHRoYXQgcmVzcGVjdHMgdGhlICJtaW5sZW4iCiAgICAgKiBjb25zdHJhaW50IHNwZWNpZmllZCBvbiBlZGdlcyBiZXR3ZWVuIG5vZGVzLgogICAgICoKICAgICAqIFRoaXMgYmFzaWMgc3RydWN0dXJlIGlzIGRlcml2ZWQgZnJvbSBHYW5zbmVyLCBldCBhbC4sICJBIFRlY2huaXF1ZSBmb3IKICAgICAqIERyYXdpbmcgRGlyZWN0ZWQgR3JhcGhzLiIKICAgICAqCiAgICAgKiBQcmUtY29uZGl0aW9uczoKICAgICAqCiAgICAgKiAgICAxLiBHcmFwaCBtdXN0IGJlIGEgY29ubmVjdGVkIERBRwogICAgICogICAgMi4gR3JhcGggbm9kZXMgbXVzdCBiZSBvYmplY3RzCiAgICAgKiAgICAzLiBHcmFwaCBlZGdlcyBtdXN0IGhhdmUgIndlaWdodCIgYW5kICJtaW5sZW4iIGF0dHJpYnV0ZXMKICAgICAqCiAgICAgKiBQb3N0LWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gR3JhcGggbm9kZXMgd2lsbCBoYXZlIGEgInJhbmsiIGF0dHJpYnV0ZSBiYXNlZCBvbiB0aGUgcmVzdWx0cyBvZiB0aGUKICAgICAqICAgICAgIGFsZ29yaXRobS4gUmFua3MgY2FuIHN0YXJ0IGF0IGFueSBpbmRleCAoaW5jbHVkaW5nIG5lZ2F0aXZlKSwgd2UnbGwKICAgICAqICAgICAgIGZpeCB0aGVtIHVwIGxhdGVyLgogICAgICovCiAgICBmdW5jdGlvbiByYW5rKGcpIHsKICAgICAgc3dpdGNoKGcuZ3JhcGgoKS5yYW5rZXIpIHsKICAgICAgY2FzZSAibmV0d29yay1zaW1wbGV4IjogbmV0d29ya1NpbXBsZXhSYW5rZXIoZyk7IGJyZWFrOwogICAgICBjYXNlICJ0aWdodC10cmVlIjogdGlnaHRUcmVlUmFua2VyKGcpOyBicmVhazsKICAgICAgY2FzZSAibG9uZ2VzdC1wYXRoIjogbG9uZ2VzdFBhdGhSYW5rZXIoZyk7IGJyZWFrOwogICAgICBkZWZhdWx0OiBuZXR3b3JrU2ltcGxleFJhbmtlcihnKTsKICAgICAgfQogICAgfQoKICAgIC8vIEEgZmFzdCBhbmQgc2ltcGxlIHJhbmtlciwgYnV0IHJlc3VsdHMgYXJlIGZhciBmcm9tIG9wdGltYWwuCiAgICB2YXIgbG9uZ2VzdFBhdGhSYW5rZXIgPSBsb25nZXN0UGF0aCQxOwoKICAgIGZ1bmN0aW9uIHRpZ2h0VHJlZVJhbmtlcihnKSB7CiAgICAgIGxvbmdlc3RQYXRoJDEoZyk7CiAgICAgIGZlYXNpYmxlVHJlZV8xKGcpOwogICAgfQoKICAgIGZ1bmN0aW9uIG5ldHdvcmtTaW1wbGV4UmFua2VyKGcpIHsKICAgICAgbmV0d29ya1NpbXBsZXhfMShnKTsKICAgIH0KCiAgICB2YXIgcGFyZW50RHVtbXlDaGFpbnNfMSA9IHBhcmVudER1bW15Q2hhaW5zOwoKICAgIGZ1bmN0aW9uIHBhcmVudER1bW15Q2hhaW5zKGcpIHsKICAgICAgdmFyIHBvc3RvcmRlck51bXMgPSBwb3N0b3JkZXIkMihnKTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmdyYXBoKCkuZHVtbXlDaGFpbnMsIGZ1bmN0aW9uKHYpIHsKICAgICAgICB2YXIgbm9kZSA9IGcubm9kZSh2KTsKICAgICAgICB2YXIgZWRnZU9iaiA9IG5vZGUuZWRnZU9iajsKICAgICAgICB2YXIgcGF0aERhdGEgPSBmaW5kUGF0aChnLCBwb3N0b3JkZXJOdW1zLCBlZGdlT2JqLnYsIGVkZ2VPYmoudyk7CiAgICAgICAgdmFyIHBhdGggPSBwYXRoRGF0YS5wYXRoOwogICAgICAgIHZhciBsY2EgPSBwYXRoRGF0YS5sY2E7CiAgICAgICAgdmFyIHBhdGhJZHggPSAwOwogICAgICAgIHZhciBwYXRoViA9IHBhdGhbcGF0aElkeF07CiAgICAgICAgdmFyIGFzY2VuZGluZyA9IHRydWU7CgogICAgICAgIHdoaWxlICh2ICE9PSBlZGdlT2JqLncpIHsKICAgICAgICAgIG5vZGUgPSBnLm5vZGUodik7CgogICAgICAgICAgaWYgKGFzY2VuZGluZykgewogICAgICAgICAgICB3aGlsZSAoKHBhdGhWID0gcGF0aFtwYXRoSWR4XSkgIT09IGxjYSAmJgogICAgICAgICAgICAgICAgICAgZy5ub2RlKHBhdGhWKS5tYXhSYW5rIDwgbm9kZS5yYW5rKSB7CiAgICAgICAgICAgICAgcGF0aElkeCsrOwogICAgICAgICAgICB9CgogICAgICAgICAgICBpZiAocGF0aFYgPT09IGxjYSkgewogICAgICAgICAgICAgIGFzY2VuZGluZyA9IGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKCFhc2NlbmRpbmcpIHsKICAgICAgICAgICAgd2hpbGUgKHBhdGhJZHggPCBwYXRoLmxlbmd0aCAtIDEgJiYKICAgICAgICAgICAgICAgICAgIGcubm9kZShwYXRoViA9IHBhdGhbcGF0aElkeCArIDFdKS5taW5SYW5rIDw9IG5vZGUucmFuaykgewogICAgICAgICAgICAgIHBhdGhJZHgrKzsKICAgICAgICAgICAgfQogICAgICAgICAgICBwYXRoViA9IHBhdGhbcGF0aElkeF07CiAgICAgICAgICB9CgogICAgICAgICAgZy5zZXRQYXJlbnQodiwgcGF0aFYpOwogICAgICAgICAgdiA9IGcuc3VjY2Vzc29ycyh2KVswXTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIC8vIEZpbmQgYSBwYXRoIGZyb20gdiB0byB3IHRocm91Z2ggdGhlIGxvd2VzdCBjb21tb24gYW5jZXN0b3IgKExDQSkuIFJldHVybiB0aGUKICAgIC8vIGZ1bGwgcGF0aCBhbmQgdGhlIExDQS4KICAgIGZ1bmN0aW9uIGZpbmRQYXRoKGcsIHBvc3RvcmRlck51bXMsIHYsIHcpIHsKICAgICAgdmFyIHZQYXRoID0gW107CiAgICAgIHZhciB3UGF0aCA9IFtdOwogICAgICB2YXIgbG93ID0gTWF0aC5taW4ocG9zdG9yZGVyTnVtc1t2XS5sb3csIHBvc3RvcmRlck51bXNbd10ubG93KTsKICAgICAgdmFyIGxpbSA9IE1hdGgubWF4KHBvc3RvcmRlck51bXNbdl0ubGltLCBwb3N0b3JkZXJOdW1zW3ddLmxpbSk7CiAgICAgIHZhciBwYXJlbnQ7CiAgICAgIHZhciBsY2E7CgogICAgICAvLyBUcmF2ZXJzZSB1cCBmcm9tIHYgdG8gZmluZCB0aGUgTENBCiAgICAgIHBhcmVudCA9IHY7CiAgICAgIGRvIHsKICAgICAgICBwYXJlbnQgPSBnLnBhcmVudChwYXJlbnQpOwogICAgICAgIHZQYXRoLnB1c2gocGFyZW50KTsKICAgICAgfSB3aGlsZSAocGFyZW50ICYmCiAgICAgICAgICAgICAgIChwb3N0b3JkZXJOdW1zW3BhcmVudF0ubG93ID4gbG93IHx8IGxpbSA+IHBvc3RvcmRlck51bXNbcGFyZW50XS5saW0pKTsKICAgICAgbGNhID0gcGFyZW50OwoKICAgICAgLy8gVHJhdmVyc2UgZnJvbSB3IHRvIExDQQogICAgICBwYXJlbnQgPSB3OwogICAgICB3aGlsZSAoKHBhcmVudCA9IGcucGFyZW50KHBhcmVudCkpICE9PSBsY2EpIHsKICAgICAgICB3UGF0aC5wdXNoKHBhcmVudCk7CiAgICAgIH0KCiAgICAgIHJldHVybiB7IHBhdGg6IHZQYXRoLmNvbmNhdCh3UGF0aC5yZXZlcnNlKCkpLCBsY2E6IGxjYSB9OwogICAgfQoKICAgIGZ1bmN0aW9uIHBvc3RvcmRlciQyKGcpIHsKICAgICAgdmFyIHJlc3VsdCA9IHt9OwogICAgICB2YXIgbGltID0gMDsKCiAgICAgIGZ1bmN0aW9uIGRmcyh2KSB7CiAgICAgICAgdmFyIGxvdyA9IGxpbTsKICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5jaGlsZHJlbih2KSwgZGZzKTsKICAgICAgICByZXN1bHRbdl0gPSB7IGxvdzogbG93LCBsaW06IGxpbSsrIH07CiAgICAgIH0KICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuY2hpbGRyZW4oKSwgZGZzKTsKCiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgdmFyIG5lc3RpbmdHcmFwaCA9IHsKICAgICAgcnVuOiBydW4kMiwKICAgICAgY2xlYW51cDogY2xlYW51cAogICAgfTsKCiAgICAvKgogICAgICogQSBuZXN0aW5nIGdyYXBoIGNyZWF0ZXMgZHVtbXkgbm9kZXMgZm9yIHRoZSB0b3BzIGFuZCBib3R0b21zIG9mIHN1YmdyYXBocywKICAgICAqIGFkZHMgYXBwcm9wcmlhdGUgZWRnZXMgdG8gZW5zdXJlIHRoYXQgYWxsIGNsdXN0ZXIgbm9kZXMgYXJlIHBsYWNlZCBiZXR3ZWVuCiAgICAgKiB0aGVzZSBib3VuZHJpZXMsIGFuZCBlbnN1cmVzIHRoYXQgdGhlIGdyYXBoIGlzIGNvbm5lY3RlZC4KICAgICAqCiAgICAgKiBJbiBhZGRpdGlvbiB3ZSBlbnN1cmUsIHRocm91Z2ggdGhlIHVzZSBvZiB0aGUgbWlubGVuIHByb3BlcnR5LCB0aGF0IG5vZGVzCiAgICAgKiBhbmQgc3ViZ3JhcGggYm9yZGVyIG5vZGVzIHRvIG5vdCBlbmQgdXAgb24gdGhlIHNhbWUgcmFuay4KICAgICAqCiAgICAgKiBQcmVjb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIElucHV0IGdyYXBoIGlzIGEgREFHCiAgICAgKiAgICAyLiBOb2RlcyBpbiB0aGUgaW5wdXQgZ3JhcGggaGFzIGEgbWlubGVuIGF0dHJpYnV0ZQogICAgICoKICAgICAqIFBvc3Rjb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIElucHV0IGdyYXBoIGlzIGNvbm5lY3RlZC4KICAgICAqICAgIDIuIER1bW15IG5vZGVzIGFyZSBhZGRlZCBmb3IgdGhlIHRvcHMgYW5kIGJvdHRvbXMgb2Ygc3ViZ3JhcGhzLgogICAgICogICAgMy4gVGhlIG1pbmxlbiBhdHRyaWJ1dGUgZm9yIG5vZGVzIGlzIGFkanVzdGVkIHRvIGVuc3VyZSBub2RlcyBkbyBub3QKICAgICAqICAgICAgIGdldCBwbGFjZWQgb24gdGhlIHNhbWUgcmFuayBhcyBzdWJncmFwaCBib3JkZXIgbm9kZXMuCiAgICAgKgogICAgICogVGhlIG5lc3RpbmcgZ3JhcGggaWRlYSBjb21lcyBmcm9tIFNhbmRlciwgIkxheW91dCBvZiBDb21wb3VuZCBEaXJlY3RlZAogICAgICogR3JhcGhzLiIKICAgICAqLwogICAgZnVuY3Rpb24gcnVuJDIoZykgewogICAgICB2YXIgcm9vdCA9IHV0aWwuYWRkRHVtbXlOb2RlKGcsICJyb290Iiwge30sICJfcm9vdCIpOwogICAgICB2YXIgZGVwdGhzID0gdHJlZURlcHRocyhnKTsKICAgICAgdmFyIGhlaWdodCA9IGxvZGFzaF8xJDEubWF4KGxvZGFzaF8xJDEudmFsdWVzKGRlcHRocykpIC0gMTsgLy8gTm90ZTogZGVwdGhzIGlzIGFuIE9iamVjdCBub3QgYW4gYXJyYXkKICAgICAgdmFyIG5vZGVTZXAgPSAyICogaGVpZ2h0ICsgMTsKCiAgICAgIGcuZ3JhcGgoKS5uZXN0aW5nUm9vdCA9IHJvb3Q7CgogICAgICAvLyBNdWx0aXBseSBtaW5sZW4gYnkgbm9kZVNlcCB0byBhbGlnbiBub2RlcyBvbiBub24tYm9yZGVyIHJhbmtzLgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5lZGdlcygpLCBmdW5jdGlvbihlKSB7IGcuZWRnZShlKS5taW5sZW4gKj0gbm9kZVNlcDsgfSk7CgogICAgICAvLyBDYWxjdWxhdGUgYSB3ZWlnaHQgdGhhdCBpcyBzdWZmaWNpZW50IHRvIGtlZXAgc3ViZ3JhcGhzIHZlcnRpY2FsbHkgY29tcGFjdAogICAgICB2YXIgd2VpZ2h0ID0gc3VtV2VpZ2h0cyhnKSArIDE7CgogICAgICAvLyBDcmVhdGUgYm9yZGVyIG5vZGVzIGFuZCBsaW5rIHRoZW0gdXAKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuY2hpbGRyZW4oKSwgZnVuY3Rpb24oY2hpbGQpIHsKICAgICAgICBkZnMkMShnLCByb290LCBub2RlU2VwLCB3ZWlnaHQsIGhlaWdodCwgZGVwdGhzLCBjaGlsZCk7CiAgICAgIH0pOwoKICAgICAgLy8gU2F2ZSB0aGUgbXVsdGlwbGllciBmb3Igbm9kZSBsYXllcnMgZm9yIGxhdGVyIHJlbW92YWwgb2YgZW1wdHkgYm9yZGVyCiAgICAgIC8vIGxheWVycy4KICAgICAgZy5ncmFwaCgpLm5vZGVSYW5rRmFjdG9yID0gbm9kZVNlcDsKICAgIH0KCiAgICBmdW5jdGlvbiBkZnMkMShnLCByb290LCBub2RlU2VwLCB3ZWlnaHQsIGhlaWdodCwgZGVwdGhzLCB2KSB7CiAgICAgIHZhciBjaGlsZHJlbiA9IGcuY2hpbGRyZW4odik7CiAgICAgIGlmICghY2hpbGRyZW4ubGVuZ3RoKSB7CiAgICAgICAgaWYgKHYgIT09IHJvb3QpIHsKICAgICAgICAgIGcuc2V0RWRnZShyb290LCB2LCB7IHdlaWdodDogMCwgbWlubGVuOiBub2RlU2VwIH0pOwogICAgICAgIH0KICAgICAgICByZXR1cm47CiAgICAgIH0KCiAgICAgIHZhciB0b3AgPSB1dGlsLmFkZEJvcmRlck5vZGUoZywgIl9idCIpOwogICAgICB2YXIgYm90dG9tID0gdXRpbC5hZGRCb3JkZXJOb2RlKGcsICJfYmIiKTsKICAgICAgdmFyIGxhYmVsID0gZy5ub2RlKHYpOwoKICAgICAgZy5zZXRQYXJlbnQodG9wLCB2KTsKICAgICAgbGFiZWwuYm9yZGVyVG9wID0gdG9wOwogICAgICBnLnNldFBhcmVudChib3R0b20sIHYpOwogICAgICBsYWJlbC5ib3JkZXJCb3R0b20gPSBib3R0b207CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goY2hpbGRyZW4sIGZ1bmN0aW9uKGNoaWxkKSB7CiAgICAgICAgZGZzJDEoZywgcm9vdCwgbm9kZVNlcCwgd2VpZ2h0LCBoZWlnaHQsIGRlcHRocywgY2hpbGQpOwoKICAgICAgICB2YXIgY2hpbGROb2RlID0gZy5ub2RlKGNoaWxkKTsKICAgICAgICB2YXIgY2hpbGRUb3AgPSBjaGlsZE5vZGUuYm9yZGVyVG9wID8gY2hpbGROb2RlLmJvcmRlclRvcCA6IGNoaWxkOwogICAgICAgIHZhciBjaGlsZEJvdHRvbSA9IGNoaWxkTm9kZS5ib3JkZXJCb3R0b20gPyBjaGlsZE5vZGUuYm9yZGVyQm90dG9tIDogY2hpbGQ7CiAgICAgICAgdmFyIHRoaXNXZWlnaHQgPSBjaGlsZE5vZGUuYm9yZGVyVG9wID8gd2VpZ2h0IDogMiAqIHdlaWdodDsKICAgICAgICB2YXIgbWlubGVuID0gY2hpbGRUb3AgIT09IGNoaWxkQm90dG9tID8gMSA6IGhlaWdodCAtIGRlcHRoc1t2XSArIDE7CgogICAgICAgIGcuc2V0RWRnZSh0b3AsIGNoaWxkVG9wLCB7CiAgICAgICAgICB3ZWlnaHQ6IHRoaXNXZWlnaHQsCiAgICAgICAgICBtaW5sZW46IG1pbmxlbiwKICAgICAgICAgIG5lc3RpbmdFZGdlOiB0cnVlCiAgICAgICAgfSk7CgogICAgICAgIGcuc2V0RWRnZShjaGlsZEJvdHRvbSwgYm90dG9tLCB7CiAgICAgICAgICB3ZWlnaHQ6IHRoaXNXZWlnaHQsCiAgICAgICAgICBtaW5sZW46IG1pbmxlbiwKICAgICAgICAgIG5lc3RpbmdFZGdlOiB0cnVlCiAgICAgICAgfSk7CiAgICAgIH0pOwoKICAgICAgaWYgKCFnLnBhcmVudCh2KSkgewogICAgICAgIGcuc2V0RWRnZShyb290LCB0b3AsIHsgd2VpZ2h0OiAwLCBtaW5sZW46IGhlaWdodCArIGRlcHRoc1t2XSB9KTsKICAgICAgfQogICAgfQoKICAgIGZ1bmN0aW9uIHRyZWVEZXB0aHMoZykgewogICAgICB2YXIgZGVwdGhzID0ge307CiAgICAgIGZ1bmN0aW9uIGRmcyh2LCBkZXB0aCkgewogICAgICAgIHZhciBjaGlsZHJlbiA9IGcuY2hpbGRyZW4odik7CiAgICAgICAgaWYgKGNoaWxkcmVuICYmIGNoaWxkcmVuLmxlbmd0aCkgewogICAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGNoaWxkcmVuLCBmdW5jdGlvbihjaGlsZCkgewogICAgICAgICAgICBkZnMoY2hpbGQsIGRlcHRoICsgMSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgZGVwdGhzW3ZdID0gZGVwdGg7CiAgICAgIH0KICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuY2hpbGRyZW4oKSwgZnVuY3Rpb24odikgeyBkZnModiwgMSk7IH0pOwogICAgICByZXR1cm4gZGVwdGhzOwogICAgfQoKICAgIGZ1bmN0aW9uIHN1bVdlaWdodHMoZykgewogICAgICByZXR1cm4gbG9kYXNoXzEkMS5yZWR1Y2UoZy5lZGdlcygpLCBmdW5jdGlvbihhY2MsIGUpIHsKICAgICAgICByZXR1cm4gYWNjICsgZy5lZGdlKGUpLndlaWdodDsKICAgICAgfSwgMCk7CiAgICB9CgogICAgZnVuY3Rpb24gY2xlYW51cChnKSB7CiAgICAgIHZhciBncmFwaExhYmVsID0gZy5ncmFwaCgpOwogICAgICBnLnJlbW92ZU5vZGUoZ3JhcGhMYWJlbC5uZXN0aW5nUm9vdCk7CiAgICAgIGRlbGV0ZSBncmFwaExhYmVsLm5lc3RpbmdSb290OwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5lZGdlcygpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIGVkZ2UgPSBnLmVkZ2UoZSk7CiAgICAgICAgaWYgKGVkZ2UubmVzdGluZ0VkZ2UpIHsKICAgICAgICAgIGcucmVtb3ZlRWRnZShlKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIHZhciBhZGRCb3JkZXJTZWdtZW50c18xID0gYWRkQm9yZGVyU2VnbWVudHM7CgogICAgZnVuY3Rpb24gYWRkQm9yZGVyU2VnbWVudHMoZykgewogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIHZhciBjaGlsZHJlbiA9IGcuY2hpbGRyZW4odik7CiAgICAgICAgdmFyIG5vZGUgPSBnLm5vZGUodik7CiAgICAgICAgaWYgKGNoaWxkcmVuLmxlbmd0aCkgewogICAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGNoaWxkcmVuLCBkZnMpOwogICAgICAgIH0KCiAgICAgICAgaWYgKGxvZGFzaF8xJDEuaGFzKG5vZGUsICJtaW5SYW5rIikpIHsKICAgICAgICAgIG5vZGUuYm9yZGVyTGVmdCA9IFtdOwogICAgICAgICAgbm9kZS5ib3JkZXJSaWdodCA9IFtdOwogICAgICAgICAgZm9yICh2YXIgcmFuayA9IG5vZGUubWluUmFuaywgbWF4UmFuayA9IG5vZGUubWF4UmFuayArIDE7CiAgICAgICAgICAgIHJhbmsgPCBtYXhSYW5rOwogICAgICAgICAgICArK3JhbmspIHsKICAgICAgICAgICAgYWRkQm9yZGVyTm9kZSQxKGcsICJib3JkZXJMZWZ0IiwgIl9ibCIsIHYsIG5vZGUsIHJhbmspOwogICAgICAgICAgICBhZGRCb3JkZXJOb2RlJDEoZywgImJvcmRlclJpZ2h0IiwgIl9iciIsIHYsIG5vZGUsIHJhbmspOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuY2hpbGRyZW4oKSwgZGZzKTsKICAgIH0KCiAgICBmdW5jdGlvbiBhZGRCb3JkZXJOb2RlJDEoZywgcHJvcCwgcHJlZml4LCBzZywgc2dOb2RlLCByYW5rKSB7CiAgICAgIHZhciBsYWJlbCA9IHsgd2lkdGg6IDAsIGhlaWdodDogMCwgcmFuazogcmFuaywgYm9yZGVyVHlwZTogcHJvcCB9OwogICAgICB2YXIgcHJldiA9IHNnTm9kZVtwcm9wXVtyYW5rIC0gMV07CiAgICAgIHZhciBjdXJyID0gdXRpbC5hZGREdW1teU5vZGUoZywgImJvcmRlciIsIGxhYmVsLCBwcmVmaXgpOwogICAgICBzZ05vZGVbcHJvcF1bcmFua10gPSBjdXJyOwogICAgICBnLnNldFBhcmVudChjdXJyLCBzZyk7CiAgICAgIGlmIChwcmV2KSB7CiAgICAgICAgZy5zZXRFZGdlKHByZXYsIGN1cnIsIHsgd2VpZ2h0OiAxIH0pOwogICAgICB9CiAgICB9CgogICAgdmFyIGNvb3JkaW5hdGVTeXN0ZW0gPSB7CiAgICAgIGFkanVzdDogYWRqdXN0LAogICAgICB1bmRvOiB1bmRvJDIKICAgIH07CgogICAgZnVuY3Rpb24gYWRqdXN0KGcpIHsKICAgICAgdmFyIHJhbmtEaXIgPSBnLmdyYXBoKCkucmFua2Rpci50b0xvd2VyQ2FzZSgpOwogICAgICBpZiAocmFua0RpciA9PT0gImxyIiB8fCByYW5rRGlyID09PSAicmwiKSB7CiAgICAgICAgc3dhcFdpZHRoSGVpZ2h0KGcpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gdW5kbyQyKGcpIHsKICAgICAgdmFyIHJhbmtEaXIgPSBnLmdyYXBoKCkucmFua2Rpci50b0xvd2VyQ2FzZSgpOwogICAgICBpZiAocmFua0RpciA9PT0gImJ0IiB8fCByYW5rRGlyID09PSAicmwiKSB7CiAgICAgICAgcmV2ZXJzZVkoZyk7CiAgICAgIH0KCiAgICAgIGlmIChyYW5rRGlyID09PSAibHIiIHx8IHJhbmtEaXIgPT09ICJybCIpIHsKICAgICAgICBzd2FwWFkoZyk7CiAgICAgICAgc3dhcFdpZHRoSGVpZ2h0KGcpOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gc3dhcFdpZHRoSGVpZ2h0KGcpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgeyBzd2FwV2lkdGhIZWlnaHRPbmUoZy5ub2RlKHYpKTsgfSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsgc3dhcFdpZHRoSGVpZ2h0T25lKGcuZWRnZShlKSk7IH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHN3YXBXaWR0aEhlaWdodE9uZShhdHRycykgewogICAgICB2YXIgdyA9IGF0dHJzLndpZHRoOwogICAgICBhdHRycy53aWR0aCA9IGF0dHJzLmhlaWdodDsKICAgICAgYXR0cnMuaGVpZ2h0ID0gdzsKICAgIH0KCiAgICBmdW5jdGlvbiByZXZlcnNlWShnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsgcmV2ZXJzZVlPbmUoZy5ub2RlKHYpKTsgfSk7CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5lZGdlcygpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgdmFyIGVkZ2UgPSBnLmVkZ2UoZSk7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGVkZ2UucG9pbnRzLCByZXZlcnNlWU9uZSk7CiAgICAgICAgaWYgKGxvZGFzaF8xJDEuaGFzKGVkZ2UsICJ5IikpIHsKICAgICAgICAgIHJldmVyc2VZT25lKGVkZ2UpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmV2ZXJzZVlPbmUoYXR0cnMpIHsKICAgICAgYXR0cnMueSA9IC1hdHRycy55OwogICAgfQoKICAgIGZ1bmN0aW9uIHN3YXBYWShnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsgc3dhcFhZT25lKGcubm9kZSh2KSk7IH0pOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBlZGdlID0gZy5lZGdlKGUpOwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChlZGdlLnBvaW50cywgc3dhcFhZT25lKTsKICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMoZWRnZSwgIngiKSkgewogICAgICAgICAgc3dhcFhZT25lKGVkZ2UpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gc3dhcFhZT25lKGF0dHJzKSB7CiAgICAgIHZhciB4ID0gYXR0cnMueDsKICAgICAgYXR0cnMueCA9IGF0dHJzLnk7CiAgICAgIGF0dHJzLnkgPSB4OwogICAgfQoKICAgIHZhciBpbml0T3JkZXJfMSA9IGluaXRPcmRlcjsKCiAgICAvKgogICAgICogQXNzaWducyBhbiBpbml0aWFsIG9yZGVyIHZhbHVlIGZvciBlYWNoIG5vZGUgYnkgcGVyZm9ybWluZyBhIERGUyBzZWFyY2gKICAgICAqIHN0YXJ0aW5nIGZyb20gbm9kZXMgaW4gdGhlIGZpcnN0IHJhbmsuIE5vZGVzIGFyZSBhc3NpZ25lZCBhbiBvcmRlciBpbiB0aGVpcgogICAgICogcmFuayBhcyB0aGV5IGFyZSBmaXJzdCB2aXNpdGVkLgogICAgICoKICAgICAqIFRoaXMgYXBwcm9hY2ggY29tZXMgZnJvbSBHYW5zbmVyLCBldCBhbC4sICJBIFRlY2huaXF1ZSBmb3IgRHJhd2luZyBEaXJlY3RlZAogICAgICogR3JhcGhzLiIKICAgICAqCiAgICAgKiBSZXR1cm5zIGEgbGF5ZXJpbmcgbWF0cml4IHdpdGggYW4gYXJyYXkgcGVyIGxheWVyIGFuZCBlYWNoIGxheWVyIHNvcnRlZCBieQogICAgICogdGhlIG9yZGVyIG9mIGl0cyBub2Rlcy4KICAgICAqLwogICAgZnVuY3Rpb24gaW5pdE9yZGVyKGcpIHsKICAgICAgdmFyIHZpc2l0ZWQgPSB7fTsKICAgICAgdmFyIHNpbXBsZU5vZGVzID0gbG9kYXNoXzEkMS5maWx0ZXIoZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgcmV0dXJuICFnLmNoaWxkcmVuKHYpLmxlbmd0aDsKICAgICAgfSk7CiAgICAgIHZhciBtYXhSYW5rID0gbG9kYXNoXzEkMS5tYXgobG9kYXNoXzEkMS5tYXAoc2ltcGxlTm9kZXMsIGZ1bmN0aW9uKHYpIHsgcmV0dXJuIGcubm9kZSh2KS5yYW5rOyB9KSk7CiAgICAgIHZhciBsYXllcnMgPSBsb2Rhc2hfMSQxLm1hcChsb2Rhc2hfMSQxLnJhbmdlKG1heFJhbmsgKyAxKSwgZnVuY3Rpb24oKSB7IHJldHVybiBbXTsgfSk7CgogICAgICBmdW5jdGlvbiBkZnModikgewogICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyh2aXNpdGVkLCB2KSkgcmV0dXJuOwogICAgICAgIHZpc2l0ZWRbdl0gPSB0cnVlOwogICAgICAgIHZhciBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIGxheWVyc1tub2RlLnJhbmtdLnB1c2godik7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuc3VjY2Vzc29ycyh2KSwgZGZzKTsKICAgICAgfQoKICAgICAgdmFyIG9yZGVyZWRWcyA9IGxvZGFzaF8xJDEuc29ydEJ5KHNpbXBsZU5vZGVzLCBmdW5jdGlvbih2KSB7IHJldHVybiBnLm5vZGUodikucmFuazsgfSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChvcmRlcmVkVnMsIGRmcyk7CgogICAgICByZXR1cm4gbGF5ZXJzOwogICAgfQoKICAgIHZhciBjcm9zc0NvdW50XzEgPSBjcm9zc0NvdW50OwoKICAgIC8qCiAgICAgKiBBIGZ1bmN0aW9uIHRoYXQgdGFrZXMgYSBsYXllcmluZyAoYW4gYXJyYXkgb2YgbGF5ZXJzLCBlYWNoIHdpdGggYW4gYXJyYXkgb2YKICAgICAqIG9yZGVyZXJkIG5vZGVzKSBhbmQgYSBncmFwaCBhbmQgcmV0dXJucyBhIHdlaWdodGVkIGNyb3NzaW5nIGNvdW50LgogICAgICoKICAgICAqIFByZS1jb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIElucHV0IGdyYXBoIG11c3QgYmUgc2ltcGxlIChub3QgYSBtdWx0aWdyYXBoKSwgZGlyZWN0ZWQsIGFuZCBpbmNsdWRlCiAgICAgKiAgICAgICBvbmx5IHNpbXBsZSBlZGdlcy4KICAgICAqICAgIDIuIEVkZ2VzIGluIHRoZSBpbnB1dCBncmFwaCBtdXN0IGhhdmUgYXNzaWduZWQgd2VpZ2h0cy4KICAgICAqCiAgICAgKiBQb3N0LWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gVGhlIGdyYXBoIGFuZCBsYXllcmluZyBtYXRyaXggYXJlIGxlZnQgdW5jaGFuZ2VkLgogICAgICoKICAgICAqIFRoaXMgYWxnb3JpdGhtIGlzIGRlcml2ZWQgZnJvbSBCYXJ0aCwgZXQgYWwuLCAiQmlsYXllciBDcm9zcyBDb3VudGluZy4iCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNyb3NzQ291bnQoZywgbGF5ZXJpbmcpIHsKICAgICAgdmFyIGNjID0gMDsKICAgICAgZm9yICh2YXIgaSA9IDE7IGkgPCBsYXllcmluZy5sZW5ndGg7ICsraSkgewogICAgICAgIGNjICs9IHR3b0xheWVyQ3Jvc3NDb3VudChnLCBsYXllcmluZ1tpLTFdLCBsYXllcmluZ1tpXSk7CiAgICAgIH0KICAgICAgcmV0dXJuIGNjOwogICAgfQoKICAgIGZ1bmN0aW9uIHR3b0xheWVyQ3Jvc3NDb3VudChnLCBub3J0aExheWVyLCBzb3V0aExheWVyKSB7CiAgICAgIC8vIFNvcnQgYWxsIG9mIHRoZSBlZGdlcyBiZXR3ZWVuIHRoZSBub3J0aCBhbmQgc291dGggbGF5ZXJzIGJ5IHRoZWlyIHBvc2l0aW9uCiAgICAgIC8vIGluIHRoZSBub3J0aCBsYXllciBhbmQgdGhlbiB0aGUgc291dGguIE1hcCB0aGVzZSBlZGdlcyB0byB0aGUgcG9zaXRpb24gb2YKICAgICAgLy8gdGhlaXIgaGVhZCBpbiB0aGUgc291dGggbGF5ZXIuCiAgICAgIHZhciBzb3V0aFBvcyA9IGxvZGFzaF8xJDEuemlwT2JqZWN0KHNvdXRoTGF5ZXIsCiAgICAgICAgbG9kYXNoXzEkMS5tYXAoc291dGhMYXllciwgZnVuY3Rpb24gKHYsIGkpIHsgcmV0dXJuIGk7IH0pKTsKICAgICAgdmFyIHNvdXRoRW50cmllcyA9IGxvZGFzaF8xJDEuZmxhdHRlbihsb2Rhc2hfMSQxLm1hcChub3J0aExheWVyLCBmdW5jdGlvbih2KSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaF8xJDEuc29ydEJ5KGxvZGFzaF8xJDEubWFwKGcub3V0RWRnZXModiksIGZ1bmN0aW9uKGUpIHsKICAgICAgICAgIHJldHVybiB7IHBvczogc291dGhQb3NbZS53XSwgd2VpZ2h0OiBnLmVkZ2UoZSkud2VpZ2h0IH07CiAgICAgICAgfSksICJwb3MiKTsKICAgICAgfSksIHRydWUpOwoKICAgICAgLy8gQnVpbGQgdGhlIGFjY3VtdWxhdG9yIHRyZWUKICAgICAgdmFyIGZpcnN0SW5kZXggPSAxOwogICAgICB3aGlsZSAoZmlyc3RJbmRleCA8IHNvdXRoTGF5ZXIubGVuZ3RoKSBmaXJzdEluZGV4IDw8PSAxOwogICAgICB2YXIgdHJlZVNpemUgPSAyICogZmlyc3RJbmRleCAtIDE7CiAgICAgIGZpcnN0SW5kZXggLT0gMTsKICAgICAgdmFyIHRyZWUgPSBsb2Rhc2hfMSQxLm1hcChuZXcgQXJyYXkodHJlZVNpemUpLCBmdW5jdGlvbigpIHsgcmV0dXJuIDA7IH0pOwoKICAgICAgLy8gQ2FsY3VsYXRlIHRoZSB3ZWlnaHRlZCBjcm9zc2luZ3MKICAgICAgdmFyIGNjID0gMDsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKHNvdXRoRW50cmllcy5mb3JFYWNoKGZ1bmN0aW9uKGVudHJ5KSB7CiAgICAgICAgdmFyIGluZGV4ID0gZW50cnkucG9zICsgZmlyc3RJbmRleDsKICAgICAgICB0cmVlW2luZGV4XSArPSBlbnRyeS53ZWlnaHQ7CiAgICAgICAgdmFyIHdlaWdodFN1bSA9IDA7CiAgICAgICAgd2hpbGUgKGluZGV4ID4gMCkgewogICAgICAgICAgaWYgKGluZGV4ICUgMikgewogICAgICAgICAgICB3ZWlnaHRTdW0gKz0gdHJlZVtpbmRleCArIDFdOwogICAgICAgICAgfQogICAgICAgICAgaW5kZXggPSAoaW5kZXggLSAxKSA+PiAxOwogICAgICAgICAgdHJlZVtpbmRleF0gKz0gZW50cnkud2VpZ2h0OwogICAgICAgIH0KICAgICAgICBjYyArPSBlbnRyeS53ZWlnaHQgKiB3ZWlnaHRTdW07CiAgICAgIH0pKTsKCiAgICAgIHJldHVybiBjYzsKICAgIH0KCiAgICB2YXIgYmFyeWNlbnRlcl8xID0gYmFyeWNlbnRlcjsKCiAgICBmdW5jdGlvbiBiYXJ5Y2VudGVyKGcsIG1vdmFibGUpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xJDEubWFwKG1vdmFibGUsIGZ1bmN0aW9uKHYpIHsKICAgICAgICB2YXIgaW5WID0gZy5pbkVkZ2VzKHYpOwogICAgICAgIGlmICghaW5WLmxlbmd0aCkgewogICAgICAgICAgcmV0dXJuIHsgdjogdiB9OwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB2YXIgcmVzdWx0ID0gbG9kYXNoXzEkMS5yZWR1Y2UoaW5WLCBmdW5jdGlvbihhY2MsIGUpIHsKICAgICAgICAgICAgdmFyIGVkZ2UgPSBnLmVkZ2UoZSksCiAgICAgICAgICAgICAgbm9kZVUgPSBnLm5vZGUoZS52KTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICBzdW06IGFjYy5zdW0gKyAoZWRnZS53ZWlnaHQgKiBub2RlVS5vcmRlciksCiAgICAgICAgICAgICAgd2VpZ2h0OiBhY2Mud2VpZ2h0ICsgZWRnZS53ZWlnaHQKICAgICAgICAgICAgfTsKICAgICAgICAgIH0sIHsgc3VtOiAwLCB3ZWlnaHQ6IDAgfSk7CgogICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgdjogdiwKICAgICAgICAgICAgYmFyeWNlbnRlcjogcmVzdWx0LnN1bSAvIHJlc3VsdC53ZWlnaHQsCiAgICAgICAgICAgIHdlaWdodDogcmVzdWx0LndlaWdodAogICAgICAgICAgfTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfQoKICAgIHZhciByZXNvbHZlQ29uZmxpY3RzXzEgPSByZXNvbHZlQ29uZmxpY3RzOwoKICAgIC8qCiAgICAgKiBHaXZlbiBhIGxpc3Qgb2YgZW50cmllcyBvZiB0aGUgZm9ybSB7diwgYmFyeWNlbnRlciwgd2VpZ2h0fSBhbmQgYQogICAgICogY29uc3RyYWludCBncmFwaCB0aGlzIGZ1bmN0aW9uIHdpbGwgcmVzb2x2ZSBhbnkgY29uZmxpY3RzIGJldHdlZW4gdGhlCiAgICAgKiBjb25zdHJhaW50IGdyYXBoIGFuZCB0aGUgYmFyeWNlbnRlcnMgZm9yIHRoZSBlbnRyaWVzLiBJZiB0aGUgYmFyeWNlbnRlcnMgZm9yCiAgICAgKiBhbiBlbnRyeSB3b3VsZCB2aW9sYXRlIGEgY29uc3RyYWludCBpbiB0aGUgY29uc3RyYWludCBncmFwaCB0aGVuIHdlIGNvYWxlc2NlCiAgICAgKiB0aGUgbm9kZXMgaW4gdGhlIGNvbmZsaWN0IGludG8gYSBuZXcgbm9kZSB0aGF0IHJlc3BlY3RzIHRoZSBjb250cmFpbnQgYW5kCiAgICAgKiBhZ2dyZWdhdGVzIGJhcnljZW50ZXIgYW5kIHdlaWdodCBpbmZvcm1hdGlvbi4KICAgICAqCiAgICAgKiBUaGlzIGltcGxlbWVudGF0aW9uIGlzIGJhc2VkIG9uIHRoZSBkZXNjcmlwdGlvbiBpbiBGb3JzdGVyLCAiQSBGYXN0IGFuZAogICAgICogU2ltcGxlIEh1ZXJpc3RpYyBmb3IgQ29uc3RyYWluZWQgVHdvLUxldmVsIENyb3NzaW5nIFJlZHVjdGlvbiwiIHRob3VnaHQgaXQKICAgICAqIGRpZmZlcnMgaW4gc29tZSBzcGVjaWZpYyBkZXRhaWxzLgogICAgICoKICAgICAqIFByZS1jb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIEVhY2ggZW50cnkgaGFzIHRoZSBmb3JtIHt2LCBiYXJ5Y2VudGVyLCB3ZWlnaHR9LCBvciBpZiB0aGUgbm9kZSBoYXMKICAgICAqICAgICAgIG5vIGJhcnljZW50ZXIsIHRoZW4ge3Z9LgogICAgICoKICAgICAqIFJldHVybnM6CiAgICAgKgogICAgICogICAgQSBuZXcgbGlzdCBvZiBlbnRyaWVzIG9mIHRoZSBmb3JtIHt2cywgaSwgYmFyeWNlbnRlciwgd2VpZ2h0fS4gVGhlIGxpc3QKICAgICAqICAgIGB2c2AgbWF5IGVpdGhlciBiZSBhIHNpbmdsZXRvbiBvciBpdCBtYXkgYmUgYW4gYWdncmVnYXRpb24gb2Ygbm9kZXMKICAgICAqICAgIG9yZGVyZWQgc3VjaCB0aGF0IHRoZXkgZG8gbm90IHZpb2xhdGUgY29uc3RyYWludHMgZnJvbSB0aGUgY29uc3RyYWludAogICAgICogICAgZ3JhcGguIFRoZSBwcm9wZXJ0eSBgaWAgaXMgdGhlIGxvd2VzdCBvcmlnaW5hbCBpbmRleCBvZiBhbnkgb2YgdGhlCiAgICAgKiAgICBlbGVtZW50cyBpbiBgdnNgLgogICAgICovCiAgICBmdW5jdGlvbiByZXNvbHZlQ29uZmxpY3RzKGVudHJpZXMsIGNnKSB7CiAgICAgIHZhciBtYXBwZWRFbnRyaWVzID0ge307CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChlbnRyaWVzLCBmdW5jdGlvbihlbnRyeSwgaSkgewogICAgICAgIHZhciB0bXAgPSBtYXBwZWRFbnRyaWVzW2VudHJ5LnZdID0gewogICAgICAgICAgaW5kZWdyZWU6IDAsCiAgICAgICAgICAiaW4iOiBbXSwKICAgICAgICAgIG91dDogW10sCiAgICAgICAgICB2czogW2VudHJ5LnZdLAogICAgICAgICAgaTogaQogICAgICAgIH07CiAgICAgICAgaWYgKCFsb2Rhc2hfMSQxLmlzVW5kZWZpbmVkKGVudHJ5LmJhcnljZW50ZXIpKSB7CiAgICAgICAgICB0bXAuYmFyeWNlbnRlciA9IGVudHJ5LmJhcnljZW50ZXI7CiAgICAgICAgICB0bXAud2VpZ2h0ID0gZW50cnkud2VpZ2h0OwogICAgICAgIH0KICAgICAgfSk7CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goY2cuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBlbnRyeVYgPSBtYXBwZWRFbnRyaWVzW2Uudl07CiAgICAgICAgdmFyIGVudHJ5VyA9IG1hcHBlZEVudHJpZXNbZS53XTsKICAgICAgICBpZiAoIWxvZGFzaF8xJDEuaXNVbmRlZmluZWQoZW50cnlWKSAmJiAhbG9kYXNoXzEkMS5pc1VuZGVmaW5lZChlbnRyeVcpKSB7CiAgICAgICAgICBlbnRyeVcuaW5kZWdyZWUrKzsKICAgICAgICAgIGVudHJ5Vi5vdXQucHVzaChtYXBwZWRFbnRyaWVzW2Uud10pOwogICAgICAgIH0KICAgICAgfSk7CgogICAgICB2YXIgc291cmNlU2V0ID0gbG9kYXNoXzEkMS5maWx0ZXIobWFwcGVkRW50cmllcywgZnVuY3Rpb24oZW50cnkpIHsKICAgICAgICByZXR1cm4gIWVudHJ5LmluZGVncmVlOwogICAgICB9KTsKCiAgICAgIHJldHVybiBkb1Jlc29sdmVDb25mbGljdHMoc291cmNlU2V0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBkb1Jlc29sdmVDb25mbGljdHMoc291cmNlU2V0KSB7CiAgICAgIHZhciBlbnRyaWVzID0gW107CgogICAgICBmdW5jdGlvbiBoYW5kbGVJbih2RW50cnkpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24odUVudHJ5KSB7CiAgICAgICAgICBpZiAodUVudHJ5Lm1lcmdlZCkgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBpZiAobG9kYXNoXzEkMS5pc1VuZGVmaW5lZCh1RW50cnkuYmFyeWNlbnRlcikgfHwKICAgICAgICAgICAgICBsb2Rhc2hfMSQxLmlzVW5kZWZpbmVkKHZFbnRyeS5iYXJ5Y2VudGVyKSB8fAogICAgICAgICAgICAgIHVFbnRyeS5iYXJ5Y2VudGVyID49IHZFbnRyeS5iYXJ5Y2VudGVyKSB7CiAgICAgICAgICAgIG1lcmdlRW50cmllcyh2RW50cnksIHVFbnRyeSk7CiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgZnVuY3Rpb24gaGFuZGxlT3V0KHZFbnRyeSkgewogICAgICAgIHJldHVybiBmdW5jdGlvbih3RW50cnkpIHsKICAgICAgICAgIHdFbnRyeVsiaW4iXS5wdXNoKHZFbnRyeSk7CiAgICAgICAgICBpZiAoLS13RW50cnkuaW5kZWdyZWUgPT09IDApIHsKICAgICAgICAgICAgc291cmNlU2V0LnB1c2god0VudHJ5KTsKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICB9CgogICAgICB3aGlsZSAoc291cmNlU2V0Lmxlbmd0aCkgewogICAgICAgIHZhciBlbnRyeSA9IHNvdXJjZVNldC5wb3AoKTsKICAgICAgICBlbnRyaWVzLnB1c2goZW50cnkpOwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChlbnRyeVsiaW4iXS5yZXZlcnNlKCksIGhhbmRsZUluKGVudHJ5KSk7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGVudHJ5Lm91dCwgaGFuZGxlT3V0KGVudHJ5KSk7CiAgICAgIH0KCiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLm1hcChsb2Rhc2hfMSQxLmZpbHRlcihlbnRyaWVzLCBmdW5jdGlvbihlbnRyeSkgeyByZXR1cm4gIWVudHJ5Lm1lcmdlZDsgfSksCiAgICAgICAgZnVuY3Rpb24oZW50cnkpIHsKICAgICAgICAgIHJldHVybiBsb2Rhc2hfMSQxLnBpY2soZW50cnksIFsidnMiLCAiaSIsICJiYXJ5Y2VudGVyIiwgIndlaWdodCJdKTsKICAgICAgICB9KTsKCiAgICB9CgogICAgZnVuY3Rpb24gbWVyZ2VFbnRyaWVzKHRhcmdldCwgc291cmNlKSB7CiAgICAgIHZhciBzdW0gPSAwOwogICAgICB2YXIgd2VpZ2h0ID0gMDsKCiAgICAgIGlmICh0YXJnZXQud2VpZ2h0KSB7CiAgICAgICAgc3VtICs9IHRhcmdldC5iYXJ5Y2VudGVyICogdGFyZ2V0LndlaWdodDsKICAgICAgICB3ZWlnaHQgKz0gdGFyZ2V0LndlaWdodDsKICAgICAgfQoKICAgICAgaWYgKHNvdXJjZS53ZWlnaHQpIHsKICAgICAgICBzdW0gKz0gc291cmNlLmJhcnljZW50ZXIgKiBzb3VyY2Uud2VpZ2h0OwogICAgICAgIHdlaWdodCArPSBzb3VyY2Uud2VpZ2h0OwogICAgICB9CgogICAgICB0YXJnZXQudnMgPSBzb3VyY2UudnMuY29uY2F0KHRhcmdldC52cyk7CiAgICAgIHRhcmdldC5iYXJ5Y2VudGVyID0gc3VtIC8gd2VpZ2h0OwogICAgICB0YXJnZXQud2VpZ2h0ID0gd2VpZ2h0OwogICAgICB0YXJnZXQuaSA9IE1hdGgubWluKHNvdXJjZS5pLCB0YXJnZXQuaSk7CiAgICAgIHNvdXJjZS5tZXJnZWQgPSB0cnVlOwogICAgfQoKICAgIHZhciBzb3J0XzEgPSBzb3J0OwoKICAgIGZ1bmN0aW9uIHNvcnQoZW50cmllcywgYmlhc1JpZ2h0KSB7CiAgICAgIHZhciBwYXJ0cyA9IHV0aWwucGFydGl0aW9uKGVudHJpZXMsIGZ1bmN0aW9uKGVudHJ5KSB7CiAgICAgICAgcmV0dXJuIGxvZGFzaF8xJDEuaGFzKGVudHJ5LCAiYmFyeWNlbnRlciIpOwogICAgICB9KTsKICAgICAgdmFyIHNvcnRhYmxlID0gcGFydHMubGhzLAogICAgICAgIHVuc29ydGFibGUgPSBsb2Rhc2hfMSQxLnNvcnRCeShwYXJ0cy5yaHMsIGZ1bmN0aW9uKGVudHJ5KSB7IHJldHVybiAtZW50cnkuaTsgfSksCiAgICAgICAgdnMgPSBbXSwKICAgICAgICBzdW0gPSAwLAogICAgICAgIHdlaWdodCA9IDAsCiAgICAgICAgdnNJbmRleCA9IDA7CgogICAgICBzb3J0YWJsZS5zb3J0KGNvbXBhcmVXaXRoQmlhcyghIWJpYXNSaWdodCkpOwoKICAgICAgdnNJbmRleCA9IGNvbnN1bWVVbnNvcnRhYmxlKHZzLCB1bnNvcnRhYmxlLCB2c0luZGV4KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChzb3J0YWJsZSwgZnVuY3Rpb24gKGVudHJ5KSB7CiAgICAgICAgdnNJbmRleCArPSBlbnRyeS52cy5sZW5ndGg7CiAgICAgICAgdnMucHVzaChlbnRyeS52cyk7CiAgICAgICAgc3VtICs9IGVudHJ5LmJhcnljZW50ZXIgKiBlbnRyeS53ZWlnaHQ7CiAgICAgICAgd2VpZ2h0ICs9IGVudHJ5LndlaWdodDsKICAgICAgICB2c0luZGV4ID0gY29uc3VtZVVuc29ydGFibGUodnMsIHVuc29ydGFibGUsIHZzSW5kZXgpOwogICAgICB9KTsKCiAgICAgIHZhciByZXN1bHQgPSB7IHZzOiBsb2Rhc2hfMSQxLmZsYXR0ZW4odnMsIHRydWUpIH07CiAgICAgIGlmICh3ZWlnaHQpIHsKICAgICAgICByZXN1bHQuYmFyeWNlbnRlciA9IHN1bSAvIHdlaWdodDsKICAgICAgICByZXN1bHQud2VpZ2h0ID0gd2VpZ2h0OwogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CgogICAgZnVuY3Rpb24gY29uc3VtZVVuc29ydGFibGUodnMsIHVuc29ydGFibGUsIGluZGV4KSB7CiAgICAgIHZhciBsYXN0OwogICAgICB3aGlsZSAodW5zb3J0YWJsZS5sZW5ndGggJiYgKGxhc3QgPSBsb2Rhc2hfMSQxLmxhc3QodW5zb3J0YWJsZSkpLmkgPD0gaW5kZXgpIHsKICAgICAgICB1bnNvcnRhYmxlLnBvcCgpOwogICAgICAgIHZzLnB1c2gobGFzdC52cyk7CiAgICAgICAgaW5kZXgrKzsKICAgICAgfQogICAgICByZXR1cm4gaW5kZXg7CiAgICB9CgogICAgZnVuY3Rpb24gY29tcGFyZVdpdGhCaWFzKGJpYXMpIHsKICAgICAgcmV0dXJuIGZ1bmN0aW9uKGVudHJ5ViwgZW50cnlXKSB7CiAgICAgICAgaWYgKGVudHJ5Vi5iYXJ5Y2VudGVyIDwgZW50cnlXLmJhcnljZW50ZXIpIHsKICAgICAgICAgIHJldHVybiAtMTsKICAgICAgICB9IGVsc2UgaWYgKGVudHJ5Vi5iYXJ5Y2VudGVyID4gZW50cnlXLmJhcnljZW50ZXIpIHsKICAgICAgICAgIHJldHVybiAxOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuICFiaWFzID8gZW50cnlWLmkgLSBlbnRyeVcuaSA6IGVudHJ5Vy5pIC0gZW50cnlWLmk7CiAgICAgIH07CiAgICB9CgogICAgdmFyIHNvcnRTdWJncmFwaF8xID0gc29ydFN1YmdyYXBoOwoKICAgIGZ1bmN0aW9uIHNvcnRTdWJncmFwaChnLCB2LCBjZywgYmlhc1JpZ2h0KSB7CiAgICAgIHZhciBtb3ZhYmxlID0gZy5jaGlsZHJlbih2KTsKICAgICAgdmFyIG5vZGUgPSBnLm5vZGUodik7CiAgICAgIHZhciBibCA9IG5vZGUgPyBub2RlLmJvcmRlckxlZnQgOiB1bmRlZmluZWQ7CiAgICAgIHZhciBiciA9IG5vZGUgPyBub2RlLmJvcmRlclJpZ2h0OiB1bmRlZmluZWQ7CiAgICAgIHZhciBzdWJncmFwaHMgPSB7fTsKCiAgICAgIGlmIChibCkgewogICAgICAgIG1vdmFibGUgPSBsb2Rhc2hfMSQxLmZpbHRlcihtb3ZhYmxlLCBmdW5jdGlvbih3KSB7CiAgICAgICAgICByZXR1cm4gdyAhPT0gYmwgJiYgdyAhPT0gYnI7CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIHZhciBiYXJ5Y2VudGVycyA9IGJhcnljZW50ZXJfMShnLCBtb3ZhYmxlKTsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGJhcnljZW50ZXJzLCBmdW5jdGlvbihlbnRyeSkgewogICAgICAgIGlmIChnLmNoaWxkcmVuKGVudHJ5LnYpLmxlbmd0aCkgewogICAgICAgICAgdmFyIHN1YmdyYXBoUmVzdWx0ID0gc29ydFN1YmdyYXBoKGcsIGVudHJ5LnYsIGNnLCBiaWFzUmlnaHQpOwogICAgICAgICAgc3ViZ3JhcGhzW2VudHJ5LnZdID0gc3ViZ3JhcGhSZXN1bHQ7CiAgICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMoc3ViZ3JhcGhSZXN1bHQsICJiYXJ5Y2VudGVyIikpIHsKICAgICAgICAgICAgbWVyZ2VCYXJ5Y2VudGVycyhlbnRyeSwgc3ViZ3JhcGhSZXN1bHQpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSk7CgogICAgICB2YXIgZW50cmllcyA9IHJlc29sdmVDb25mbGljdHNfMShiYXJ5Y2VudGVycywgY2cpOwogICAgICBleHBhbmRTdWJncmFwaHMoZW50cmllcywgc3ViZ3JhcGhzKTsKCiAgICAgIHZhciByZXN1bHQgPSBzb3J0XzEoZW50cmllcywgYmlhc1JpZ2h0KTsKCiAgICAgIGlmIChibCkgewogICAgICAgIHJlc3VsdC52cyA9IGxvZGFzaF8xJDEuZmxhdHRlbihbYmwsIHJlc3VsdC52cywgYnJdLCB0cnVlKTsKICAgICAgICBpZiAoZy5wcmVkZWNlc3NvcnMoYmwpLmxlbmd0aCkgewogICAgICAgICAgdmFyIGJsUHJlZCA9IGcubm9kZShnLnByZWRlY2Vzc29ycyhibClbMF0pLAogICAgICAgICAgICBiclByZWQgPSBnLm5vZGUoZy5wcmVkZWNlc3NvcnMoYnIpWzBdKTsKICAgICAgICAgIGlmICghbG9kYXNoXzEkMS5oYXMocmVzdWx0LCAiYmFyeWNlbnRlciIpKSB7CiAgICAgICAgICAgIHJlc3VsdC5iYXJ5Y2VudGVyID0gMDsKICAgICAgICAgICAgcmVzdWx0LndlaWdodCA9IDA7CiAgICAgICAgICB9CiAgICAgICAgICByZXN1bHQuYmFyeWNlbnRlciA9IChyZXN1bHQuYmFyeWNlbnRlciAqIHJlc3VsdC53ZWlnaHQgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYmxQcmVkLm9yZGVyICsgYnJQcmVkLm9yZGVyKSAvIChyZXN1bHQud2VpZ2h0ICsgMik7CiAgICAgICAgICByZXN1bHQud2VpZ2h0ICs9IDI7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIGZ1bmN0aW9uIGV4cGFuZFN1YmdyYXBocyhlbnRyaWVzLCBzdWJncmFwaHMpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGVudHJpZXMsIGZ1bmN0aW9uKGVudHJ5KSB7CiAgICAgICAgZW50cnkudnMgPSBsb2Rhc2hfMSQxLmZsYXR0ZW4oZW50cnkudnMubWFwKGZ1bmN0aW9uKHYpIHsKICAgICAgICAgIGlmIChzdWJncmFwaHNbdl0pIHsKICAgICAgICAgICAgcmV0dXJuIHN1YmdyYXBoc1t2XS52czsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybiB2OwogICAgICAgIH0pLCB0cnVlKTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gbWVyZ2VCYXJ5Y2VudGVycyh0YXJnZXQsIG90aGVyKSB7CiAgICAgIGlmICghbG9kYXNoXzEkMS5pc1VuZGVmaW5lZCh0YXJnZXQuYmFyeWNlbnRlcikpIHsKICAgICAgICB0YXJnZXQuYmFyeWNlbnRlciA9ICh0YXJnZXQuYmFyeWNlbnRlciAqIHRhcmdldC53ZWlnaHQgKwogICAgICAgICAgICAgICAgICAgICAgICAgICAgIG90aGVyLmJhcnljZW50ZXIgKiBvdGhlci53ZWlnaHQpIC8KICAgICAgICAgICAgICAgICAgICAgICAgICAgICh0YXJnZXQud2VpZ2h0ICsgb3RoZXIud2VpZ2h0KTsKICAgICAgICB0YXJnZXQud2VpZ2h0ICs9IG90aGVyLndlaWdodDsKICAgICAgfSBlbHNlIHsKICAgICAgICB0YXJnZXQuYmFyeWNlbnRlciA9IG90aGVyLmJhcnljZW50ZXI7CiAgICAgICAgdGFyZ2V0LndlaWdodCA9IG90aGVyLndlaWdodDsKICAgICAgfQogICAgfQoKICAgIHZhciBHcmFwaCQ0ID0gZ3JhcGhsaWJfMS5HcmFwaDsKCiAgICB2YXIgYnVpbGRMYXllckdyYXBoXzEgPSBidWlsZExheWVyR3JhcGg7CgogICAgLyoKICAgICAqIENvbnN0cnVjdHMgYSBncmFwaCB0aGF0IGNhbiBiZSB1c2VkIHRvIHNvcnQgYSBsYXllciBvZiBub2Rlcy4gVGhlIGdyYXBoIHdpbGwKICAgICAqIGNvbnRhaW4gYWxsIGJhc2UgYW5kIHN1YmdyYXBoIG5vZGVzIGZyb20gdGhlIHJlcXVlc3QgbGF5ZXIgaW4gdGhlaXIgb3JpZ2luYWwKICAgICAqIGhpZXJhcmNoeSBhbmQgYW55IGVkZ2VzIHRoYXQgYXJlIGluY2lkZW50IG9uIHRoZXNlIG5vZGVzIGFuZCBhcmUgb2YgdGhlIHR5cGUKICAgICAqIHJlcXVlc3RlZCBieSB0aGUgInJlbGF0aW9uc2hpcCIgcGFyYW1ldGVyLgogICAgICoKICAgICAqIE5vZGVzIGZyb20gdGhlIHJlcXVlc3RlZCByYW5rIHRoYXQgZG8gbm90IGhhdmUgcGFyZW50cyBhcmUgYXNzaWduZWQgYSByb290CiAgICAgKiBub2RlIGluIHRoZSBvdXRwdXQgZ3JhcGgsIHdoaWNoIGlzIHNldCBpbiB0aGUgcm9vdCBncmFwaCBhdHRyaWJ1dGUuIFRoaXMKICAgICAqIG1ha2VzIGl0IGVhc3kgdG8gd2FsayB0aGUgaGllcmFyY2h5IG9mIG1vdmFibGUgbm9kZXMgZHVyaW5nIG9yZGVyaW5nLgogICAgICoKICAgICAqIFByZS1jb25kaXRpb25zOgogICAgICoKICAgICAqICAgIDEuIElucHV0IGdyYXBoIGlzIGEgREFHCiAgICAgKiAgICAyLiBCYXNlIG5vZGVzIGluIHRoZSBpbnB1dCBncmFwaCBoYXZlIGEgcmFuayBhdHRyaWJ1dGUKICAgICAqICAgIDMuIFN1YmdyYXBoIG5vZGVzIGluIHRoZSBpbnB1dCBncmFwaCBoYXMgbWluUmFuayBhbmQgbWF4UmFuayBhdHRyaWJ1dGVzCiAgICAgKiAgICA0LiBFZGdlcyBoYXZlIGFuIGFzc2lnbmVkIHdlaWdodAogICAgICoKICAgICAqIFBvc3QtY29uZGl0aW9uczoKICAgICAqCiAgICAgKiAgICAxLiBPdXRwdXQgZ3JhcGggaGFzIGFsbCBub2RlcyBpbiB0aGUgbW92YWJsZSByYW5rIHdpdGggcHJlc2VydmVkCiAgICAgKiAgICAgICBoaWVyYXJjaHkuCiAgICAgKiAgICAyLiBSb290IG5vZGVzIGluIHRoZSBtb3ZhYmxlIGxheWVyIGFyZSBtYWRlIGNoaWxkcmVuIG9mIHRoZSBub2RlCiAgICAgKiAgICAgICBpbmRpY2F0ZWQgYnkgdGhlIHJvb3QgYXR0cmlidXRlIG9mIHRoZSBncmFwaC4KICAgICAqICAgIDMuIE5vbi1tb3ZhYmxlIG5vZGVzIGluY2lkZW50IG9uIG1vdmFibGUgbm9kZXMsIHNlbGVjdGVkIGJ5IHRoZQogICAgICogICAgICAgcmVsYXRpb25zaGlwIHBhcmFtZXRlciwgYXJlIGluY2x1ZGVkIGluIHRoZSBncmFwaCAod2l0aG91dCBoaWVyYXJjaHkpLgogICAgICogICAgNC4gRWRnZXMgaW5jaWRlbnQgb24gbW92YWJsZSBub2Rlcywgc2VsZWN0ZWQgYnkgdGhlIHJlbGF0aW9uc2hpcAogICAgICogICAgICAgcGFyYW1ldGVyLCBhcmUgYWRkZWQgdG8gdGhlIG91dHB1dCBncmFwaC4KICAgICAqICAgIDUuIFRoZSB3ZWlnaHRzIGZvciBjb3BpZWQgZWRnZXMgYXJlIGFnZ3JlZ2F0ZWQgYXMgbmVlZCwgc2luY2UgdGhlIG91dHB1dAogICAgICogICAgICAgZ3JhcGggaXMgbm90IGEgbXVsdGktZ3JhcGguCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJ1aWxkTGF5ZXJHcmFwaChnLCByYW5rLCByZWxhdGlvbnNoaXApIHsKICAgICAgdmFyIHJvb3QgPSBjcmVhdGVSb290Tm9kZShnKSwKICAgICAgICByZXN1bHQgPSBuZXcgR3JhcGgkNCh7IGNvbXBvdW5kOiB0cnVlIH0pLnNldEdyYXBoKHsgcm9vdDogcm9vdCB9KQogICAgICAgICAgLnNldERlZmF1bHROb2RlTGFiZWwoZnVuY3Rpb24odikgeyByZXR1cm4gZy5ub2RlKHYpOyB9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICB2YXIgbm9kZSA9IGcubm9kZSh2KSwKICAgICAgICAgIHBhcmVudCA9IGcucGFyZW50KHYpOwoKICAgICAgICBpZiAobm9kZS5yYW5rID09PSByYW5rIHx8IG5vZGUubWluUmFuayA8PSByYW5rICYmIHJhbmsgPD0gbm9kZS5tYXhSYW5rKSB7CiAgICAgICAgICByZXN1bHQuc2V0Tm9kZSh2KTsKICAgICAgICAgIHJlc3VsdC5zZXRQYXJlbnQodiwgcGFyZW50IHx8IHJvb3QpOwoKICAgICAgICAgIC8vIFRoaXMgYXNzdW1lcyB3ZSBoYXZlIG9ubHkgc2hvcnQgZWRnZXMhCiAgICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZ1tyZWxhdGlvbnNoaXBdKHYpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgICAgIHZhciB1ID0gZS52ID09PSB2ID8gZS53IDogZS52LAogICAgICAgICAgICAgIGVkZ2UgPSByZXN1bHQuZWRnZSh1LCB2KSwKICAgICAgICAgICAgICB3ZWlnaHQgPSAhbG9kYXNoXzEkMS5pc1VuZGVmaW5lZChlZGdlKSA/IGVkZ2Uud2VpZ2h0IDogMDsKICAgICAgICAgICAgcmVzdWx0LnNldEVkZ2UodSwgdiwgeyB3ZWlnaHQ6IGcuZWRnZShlKS53ZWlnaHQgKyB3ZWlnaHQgfSk7CiAgICAgICAgICB9KTsKCiAgICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMobm9kZSwgIm1pblJhbmsiKSkgewogICAgICAgICAgICByZXN1bHQuc2V0Tm9kZSh2LCB7CiAgICAgICAgICAgICAgYm9yZGVyTGVmdDogbm9kZS5ib3JkZXJMZWZ0W3JhbmtdLAogICAgICAgICAgICAgIGJvcmRlclJpZ2h0OiBub2RlLmJvcmRlclJpZ2h0W3JhbmtdCiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSk7CgogICAgICByZXR1cm4gcmVzdWx0OwogICAgfQoKICAgIGZ1bmN0aW9uIGNyZWF0ZVJvb3ROb2RlKGcpIHsKICAgICAgdmFyIHY7CiAgICAgIHdoaWxlIChnLmhhc05vZGUoKHYgPSBsb2Rhc2hfMSQxLnVuaXF1ZUlkKCJfcm9vdCIpKSkpOwogICAgICByZXR1cm4gdjsKICAgIH0KCiAgICB2YXIgYWRkU3ViZ3JhcGhDb25zdHJhaW50c18xID0gYWRkU3ViZ3JhcGhDb25zdHJhaW50czsKCiAgICBmdW5jdGlvbiBhZGRTdWJncmFwaENvbnN0cmFpbnRzKGcsIGNnLCB2cykgewogICAgICB2YXIgcHJldiA9IHt9LAogICAgICAgIHJvb3RQcmV2OwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKHZzLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIGNoaWxkID0gZy5wYXJlbnQodiksCiAgICAgICAgICBwYXJlbnQsCiAgICAgICAgICBwcmV2Q2hpbGQ7CiAgICAgICAgd2hpbGUgKGNoaWxkKSB7CiAgICAgICAgICBwYXJlbnQgPSBnLnBhcmVudChjaGlsZCk7CiAgICAgICAgICBpZiAocGFyZW50KSB7CiAgICAgICAgICAgIHByZXZDaGlsZCA9IHByZXZbcGFyZW50XTsKICAgICAgICAgICAgcHJldltwYXJlbnRdID0gY2hpbGQ7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBwcmV2Q2hpbGQgPSByb290UHJldjsKICAgICAgICAgICAgcm9vdFByZXYgPSBjaGlsZDsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChwcmV2Q2hpbGQgJiYgcHJldkNoaWxkICE9PSBjaGlsZCkgewogICAgICAgICAgICBjZy5zZXRFZGdlKHByZXZDaGlsZCwgY2hpbGQpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBjaGlsZCA9IHBhcmVudDsKICAgICAgICB9CiAgICAgIH0pOwoKICAgICAgLyoKICAgICAgZnVuY3Rpb24gZGZzKHYpIHsKICAgICAgICB2YXIgY2hpbGRyZW4gPSB2ID8gZy5jaGlsZHJlbih2KSA6IGcuY2hpbGRyZW4oKTsKICAgICAgICBpZiAoY2hpbGRyZW4ubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgbWluID0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZLAogICAgICAgICAgICAgIHN1YmdyYXBocyA9IFtdOwogICAgICAgICAgXy5lYWNoKGNoaWxkcmVuLCBmdW5jdGlvbihjaGlsZCkgewogICAgICAgICAgICB2YXIgY2hpbGRNaW4gPSBkZnMoY2hpbGQpOwogICAgICAgICAgICBpZiAoZy5jaGlsZHJlbihjaGlsZCkubGVuZ3RoKSB7CiAgICAgICAgICAgICAgc3ViZ3JhcGhzLnB1c2goeyB2OiBjaGlsZCwgb3JkZXI6IGNoaWxkTWluIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIG1pbiA9IE1hdGgubWluKG1pbiwgY2hpbGRNaW4pOwogICAgICAgICAgfSk7CiAgICAgICAgICBfLnJlZHVjZShfLnNvcnRCeShzdWJncmFwaHMsICJvcmRlciIpLCBmdW5jdGlvbihwcmV2LCBjdXJyKSB7CiAgICAgICAgICAgIGNnLnNldEVkZ2UocHJldi52LCBjdXJyLnYpOwogICAgICAgICAgICByZXR1cm4gY3VycjsKICAgICAgICAgIH0pOwogICAgICAgICAgcmV0dXJuIG1pbjsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGcubm9kZSh2KS5vcmRlcjsKICAgICAgfQogICAgICBkZnModW5kZWZpbmVkKTsKICAgICAgKi8KICAgIH0KCiAgICB2YXIgR3JhcGgkNSA9IGdyYXBobGliXzEuR3JhcGg7CgoKICAgIHZhciBvcmRlcl8xID0gb3JkZXI7CgogICAgLyoKICAgICAqIEFwcGxpZXMgaGV1cmlzdGljcyB0byBtaW5pbWl6ZSBlZGdlIGNyb3NzaW5ncyBpbiB0aGUgZ3JhcGggYW5kIHNldHMgdGhlIGJlc3QKICAgICAqIG9yZGVyIHNvbHV0aW9uIGFzIGFuIG9yZGVyIGF0dHJpYnV0ZSBvbiBlYWNoIG5vZGUuCiAgICAgKgogICAgICogUHJlLWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gR3JhcGggbXVzdCBiZSBEQUcKICAgICAqICAgIDIuIEdyYXBoIG5vZGVzIG11c3QgYmUgb2JqZWN0cyB3aXRoIGEgInJhbmsiIGF0dHJpYnV0ZQogICAgICogICAgMy4gR3JhcGggZWRnZXMgbXVzdCBoYXZlIHRoZSAid2VpZ2h0IiBhdHRyaWJ1dGUKICAgICAqCiAgICAgKiBQb3N0LWNvbmRpdGlvbnM6CiAgICAgKgogICAgICogICAgMS4gR3JhcGggbm9kZXMgd2lsbCBoYXZlIGFuICJvcmRlciIgYXR0cmlidXRlIGJhc2VkIG9uIHRoZSByZXN1bHRzIG9mIHRoZQogICAgICogICAgICAgYWxnb3JpdGhtLgogICAgICovCiAgICBmdW5jdGlvbiBvcmRlcihnKSB7CiAgICAgIHZhciBtYXhSYW5rID0gdXRpbC5tYXhSYW5rKGcpLAogICAgICAgIGRvd25MYXllckdyYXBocyA9IGJ1aWxkTGF5ZXJHcmFwaHMoZywgbG9kYXNoXzEkMS5yYW5nZSgxLCBtYXhSYW5rICsgMSksICJpbkVkZ2VzIiksCiAgICAgICAgdXBMYXllckdyYXBocyA9IGJ1aWxkTGF5ZXJHcmFwaHMoZywgbG9kYXNoXzEkMS5yYW5nZShtYXhSYW5rIC0gMSwgLTEsIC0xKSwgIm91dEVkZ2VzIik7CgogICAgICB2YXIgbGF5ZXJpbmcgPSBpbml0T3JkZXJfMShnKTsKICAgICAgYXNzaWduT3JkZXIoZywgbGF5ZXJpbmcpOwoKICAgICAgdmFyIGJlc3RDQyA9IE51bWJlci5QT1NJVElWRV9JTkZJTklUWSwKICAgICAgICBiZXN0OwoKICAgICAgZm9yICh2YXIgaSA9IDAsIGxhc3RCZXN0ID0gMDsgbGFzdEJlc3QgPCA0OyArK2ksICsrbGFzdEJlc3QpIHsKICAgICAgICBzd2VlcExheWVyR3JhcGhzKGkgJSAyID8gZG93bkxheWVyR3JhcGhzIDogdXBMYXllckdyYXBocywgaSAlIDQgPj0gMik7CgogICAgICAgIGxheWVyaW5nID0gdXRpbC5idWlsZExheWVyTWF0cml4KGcpOwogICAgICAgIHZhciBjYyA9IGNyb3NzQ291bnRfMShnLCBsYXllcmluZyk7CiAgICAgICAgaWYgKGNjIDwgYmVzdENDKSB7CiAgICAgICAgICBsYXN0QmVzdCA9IDA7CiAgICAgICAgICBiZXN0ID0gbG9kYXNoXzEkMS5jbG9uZURlZXAobGF5ZXJpbmcpOwogICAgICAgICAgYmVzdENDID0gY2M7CiAgICAgICAgfQogICAgICB9CgogICAgICBhc3NpZ25PcmRlcihnLCBiZXN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBidWlsZExheWVyR3JhcGhzKGcsIHJhbmtzLCByZWxhdGlvbnNoaXApIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xJDEubWFwKHJhbmtzLCBmdW5jdGlvbihyYW5rKSB7CiAgICAgICAgcmV0dXJuIGJ1aWxkTGF5ZXJHcmFwaF8xKGcsIHJhbmssIHJlbGF0aW9uc2hpcCk7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHN3ZWVwTGF5ZXJHcmFwaHMobGF5ZXJHcmFwaHMsIGJpYXNSaWdodCkgewogICAgICB2YXIgY2cgPSBuZXcgR3JhcGgkNSgpOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2gobGF5ZXJHcmFwaHMsIGZ1bmN0aW9uKGxnKSB7CiAgICAgICAgdmFyIHJvb3QgPSBsZy5ncmFwaCgpLnJvb3Q7CiAgICAgICAgdmFyIHNvcnRlZCA9IHNvcnRTdWJncmFwaF8xKGxnLCByb290LCBjZywgYmlhc1JpZ2h0KTsKICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goc29ydGVkLnZzLCBmdW5jdGlvbih2LCBpKSB7CiAgICAgICAgICBsZy5ub2RlKHYpLm9yZGVyID0gaTsKICAgICAgICB9KTsKICAgICAgICBhZGRTdWJncmFwaENvbnN0cmFpbnRzXzEobGcsIGNnLCBzb3J0ZWQudnMpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc3NpZ25PcmRlcihnLCBsYXllcmluZykgewogICAgICBsb2Rhc2hfMSQxLmZvckVhY2gobGF5ZXJpbmcsIGZ1bmN0aW9uKGxheWVyKSB7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyLCBmdW5jdGlvbih2LCBpKSB7CiAgICAgICAgICBnLm5vZGUodikub3JkZXIgPSBpOwogICAgICAgIH0pOwogICAgICB9KTsKICAgIH0KCiAgICB2YXIgR3JhcGgkNiA9IGdyYXBobGliXzEuR3JhcGg7CgoKICAgIC8qCiAgICAgKiBUaGlzIG1vZHVsZSBwcm92aWRlcyBjb29yZGluYXRlIGFzc2lnbm1lbnQgYmFzZWQgb24gQnJhbmRlcyBhbmQgS8O2cGYsICJGYXN0CiAgICAgKiBhbmQgU2ltcGxlIEhvcml6b250YWwgQ29vcmRpbmF0ZSBBc3NpZ25tZW50LiIKICAgICAqLwoKICAgIHZhciBiayA9IHsKICAgICAgcG9zaXRpb25YOiBwb3NpdGlvblgsCiAgICAgIGZpbmRUeXBlMUNvbmZsaWN0czogZmluZFR5cGUxQ29uZmxpY3RzLAogICAgICBmaW5kVHlwZTJDb25mbGljdHM6IGZpbmRUeXBlMkNvbmZsaWN0cywKICAgICAgYWRkQ29uZmxpY3Q6IGFkZENvbmZsaWN0LAogICAgICBoYXNDb25mbGljdDogaGFzQ29uZmxpY3QsCiAgICAgIHZlcnRpY2FsQWxpZ25tZW50OiB2ZXJ0aWNhbEFsaWdubWVudCwKICAgICAgaG9yaXpvbnRhbENvbXBhY3Rpb246IGhvcml6b250YWxDb21wYWN0aW9uLAogICAgICBhbGlnbkNvb3JkaW5hdGVzOiBhbGlnbkNvb3JkaW5hdGVzLAogICAgICBmaW5kU21hbGxlc3RXaWR0aEFsaWdubWVudDogZmluZFNtYWxsZXN0V2lkdGhBbGlnbm1lbnQsCiAgICAgIGJhbGFuY2U6IGJhbGFuY2UKICAgIH07CgogICAgLyoKICAgICAqIE1hcmtzIGFsbCBlZGdlcyBpbiB0aGUgZ3JhcGggd2l0aCBhIHR5cGUtMSBjb25mbGljdCB3aXRoIHRoZSAidHlwZTFDb25mbGljdCIKICAgICAqIHByb3BlcnR5LiBBIHR5cGUtMSBjb25mbGljdCBpcyBvbmUgd2hlcmUgYSBub24taW5uZXIgc2VnbWVudCBjcm9zc2VzIGFuCiAgICAgKiBpbm5lciBzZWdtZW50LiBBbiBpbm5lciBzZWdtZW50IGlzIGFuIGVkZ2Ugd2l0aCBib3RoIGluY2lkZW50IG5vZGVzIG1hcmtlZAogICAgICogd2l0aCB0aGUgImR1bW15IiBwcm9wZXJ0eS4KICAgICAqCiAgICAgKiBUaGlzIGFsZ29yaXRobSBzY2FucyBsYXllciBieSBsYXllciwgc3RhcnRpbmcgd2l0aCB0aGUgc2Vjb25kLCBmb3IgdHlwZS0xCiAgICAgKiBjb25mbGljdHMgYmV0d2VlbiB0aGUgY3VycmVudCBsYXllciBhbmQgdGhlIHByZXZpb3VzIGxheWVyLiBGb3IgZWFjaCBsYXllcgogICAgICogaXQgc2NhbnMgdGhlIG5vZGVzIGZyb20gbGVmdCB0byByaWdodCB1bnRpbCBpdCByZWFjaGVzIG9uZSB0aGF0IGlzIGluY2lkZW50CiAgICAgKiBvbiBhbiBpbm5lciBzZWdtZW50LiBJdCB0aGVuIHNjYW5zIHByZWRlY2Vzc29ycyB0byBkZXRlcm1pbmUgaWYgdGhleSBoYXZlCiAgICAgKiBlZGdlcyB0aGF0IGNyb3NzIHRoYXQgaW5uZXIgc2VnbWVudC4gQXQgdGhlIGVuZCBhIGZpbmFsIHNjYW4gaXMgZG9uZSBmb3IgYWxsCiAgICAgKiBub2RlcyBvbiB0aGUgY3VycmVudCByYW5rIHRvIHNlZSBpZiB0aGV5IGNyb3NzIHRoZSBsYXN0IHZpc2l0ZWQgaW5uZXIKICAgICAqIHNlZ21lbnQuCiAgICAgKgogICAgICogVGhpcyBhbGdvcml0aG0gKHNhZmVseSkgYXNzdW1lcyB0aGF0IGEgZHVtbXkgbm9kZSB3aWxsIG9ubHkgYmUgaW5jaWRlbnQgb24gYQogICAgICogc2luZ2xlIG5vZGUgaW4gdGhlIGxheWVycyBiZWluZyBzY2FubmVkLgogICAgICovCiAgICBmdW5jdGlvbiBmaW5kVHlwZTFDb25mbGljdHMoZywgbGF5ZXJpbmcpIHsKICAgICAgdmFyIGNvbmZsaWN0cyA9IHt9OwoKICAgICAgZnVuY3Rpb24gdmlzaXRMYXllcihwcmV2TGF5ZXIsIGxheWVyKSB7CiAgICAgICAgdmFyCiAgICAgICAgICAvLyBsYXN0IHZpc2l0ZWQgbm9kZSBpbiB0aGUgcHJldmlvdXMgbGF5ZXIgdGhhdCBpcyBpbmNpZGVudCBvbiBhbiBpbm5lcgogICAgICAgICAgLy8gc2VnbWVudC4KICAgICAgICAgIGswID0gMCwKICAgICAgICAgIC8vIFRyYWNrcyB0aGUgbGFzdCBub2RlIGluIHRoaXMgbGF5ZXIgc2Nhbm5lZCBmb3IgY3Jvc3NpbmdzIHdpdGggYSB0eXBlLTEKICAgICAgICAgIC8vIHNlZ21lbnQuCiAgICAgICAgICBzY2FuUG9zID0gMCwKICAgICAgICAgIHByZXZMYXllckxlbmd0aCA9IHByZXZMYXllci5sZW5ndGgsCiAgICAgICAgICBsYXN0Tm9kZSA9IGxvZGFzaF8xJDEubGFzdChsYXllcik7CgogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllciwgZnVuY3Rpb24odiwgaSkgewogICAgICAgICAgdmFyIHcgPSBmaW5kT3RoZXJJbm5lclNlZ21lbnROb2RlKGcsIHYpLAogICAgICAgICAgICBrMSA9IHcgPyBnLm5vZGUodykub3JkZXIgOiBwcmV2TGF5ZXJMZW5ndGg7CgogICAgICAgICAgaWYgKHcgfHwgdiA9PT0gbGFzdE5vZGUpIHsKICAgICAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyLnNsaWNlKHNjYW5Qb3MsIGkgKzEpLCBmdW5jdGlvbihzY2FuTm9kZSkgewogICAgICAgICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLnByZWRlY2Vzc29ycyhzY2FuTm9kZSksIGZ1bmN0aW9uKHUpIHsKICAgICAgICAgICAgICAgIHZhciB1TGFiZWwgPSBnLm5vZGUodSksCiAgICAgICAgICAgICAgICAgIHVQb3MgPSB1TGFiZWwub3JkZXI7CiAgICAgICAgICAgICAgICBpZiAoKHVQb3MgPCBrMCB8fCBrMSA8IHVQb3MpICYmCiAgICAgICAgICAgICAgICAgICAgISh1TGFiZWwuZHVtbXkgJiYgZy5ub2RlKHNjYW5Ob2RlKS5kdW1teSkpIHsKICAgICAgICAgICAgICAgICAgYWRkQ29uZmxpY3QoY29uZmxpY3RzLCB1LCBzY2FuTm9kZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBzY2FuUG9zID0gaSArIDE7CiAgICAgICAgICAgIGswID0gazE7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIHJldHVybiBsYXllcjsKICAgICAgfQoKICAgICAgbG9kYXNoXzEkMS5yZWR1Y2UobGF5ZXJpbmcsIHZpc2l0TGF5ZXIpOwogICAgICByZXR1cm4gY29uZmxpY3RzOwogICAgfQoKICAgIGZ1bmN0aW9uIGZpbmRUeXBlMkNvbmZsaWN0cyhnLCBsYXllcmluZykgewogICAgICB2YXIgY29uZmxpY3RzID0ge307CgogICAgICBmdW5jdGlvbiBzY2FuKHNvdXRoLCBzb3V0aFBvcywgc291dGhFbmQsIHByZXZOb3J0aEJvcmRlciwgbmV4dE5vcnRoQm9yZGVyKSB7CiAgICAgICAgdmFyIHY7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxvZGFzaF8xJDEucmFuZ2Uoc291dGhQb3MsIHNvdXRoRW5kKSwgZnVuY3Rpb24oaSkgewogICAgICAgICAgdiA9IHNvdXRoW2ldOwogICAgICAgICAgaWYgKGcubm9kZSh2KS5kdW1teSkgewogICAgICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5wcmVkZWNlc3NvcnModiksIGZ1bmN0aW9uKHUpIHsKICAgICAgICAgICAgICB2YXIgdU5vZGUgPSBnLm5vZGUodSk7CiAgICAgICAgICAgICAgaWYgKHVOb2RlLmR1bW15ICYmCiAgICAgICAgICAgICAgICAgICh1Tm9kZS5vcmRlciA8IHByZXZOb3J0aEJvcmRlciB8fCB1Tm9kZS5vcmRlciA+IG5leHROb3J0aEJvcmRlcikpIHsKICAgICAgICAgICAgICAgIGFkZENvbmZsaWN0KGNvbmZsaWN0cywgdSwgdik7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfQoKCiAgICAgIGZ1bmN0aW9uIHZpc2l0TGF5ZXIobm9ydGgsIHNvdXRoKSB7CiAgICAgICAgdmFyIHByZXZOb3J0aFBvcyA9IC0xLAogICAgICAgICAgbmV4dE5vcnRoUG9zLAogICAgICAgICAgc291dGhQb3MgPSAwOwoKICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goc291dGgsIGZ1bmN0aW9uKHYsIHNvdXRoTG9va2FoZWFkKSB7CiAgICAgICAgICBpZiAoZy5ub2RlKHYpLmR1bW15ID09PSAiYm9yZGVyIikgewogICAgICAgICAgICB2YXIgcHJlZGVjZXNzb3JzID0gZy5wcmVkZWNlc3NvcnModik7CiAgICAgICAgICAgIGlmIChwcmVkZWNlc3NvcnMubGVuZ3RoKSB7CiAgICAgICAgICAgICAgbmV4dE5vcnRoUG9zID0gZy5ub2RlKHByZWRlY2Vzc29yc1swXSkub3JkZXI7CiAgICAgICAgICAgICAgc2Nhbihzb3V0aCwgc291dGhQb3MsIHNvdXRoTG9va2FoZWFkLCBwcmV2Tm9ydGhQb3MsIG5leHROb3J0aFBvcyk7CiAgICAgICAgICAgICAgc291dGhQb3MgPSBzb3V0aExvb2thaGVhZDsKICAgICAgICAgICAgICBwcmV2Tm9ydGhQb3MgPSBuZXh0Tm9ydGhQb3M7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIHNjYW4oc291dGgsIHNvdXRoUG9zLCBzb3V0aC5sZW5ndGgsIG5leHROb3J0aFBvcywgbm9ydGgubGVuZ3RoKTsKICAgICAgICB9KTsKCiAgICAgICAgcmV0dXJuIHNvdXRoOwogICAgICB9CgogICAgICBsb2Rhc2hfMSQxLnJlZHVjZShsYXllcmluZywgdmlzaXRMYXllcik7CiAgICAgIHJldHVybiBjb25mbGljdHM7CiAgICB9CgogICAgZnVuY3Rpb24gZmluZE90aGVySW5uZXJTZWdtZW50Tm9kZShnLCB2KSB7CiAgICAgIGlmIChnLm5vZGUodikuZHVtbXkpIHsKICAgICAgICByZXR1cm4gbG9kYXNoXzEkMS5maW5kKGcucHJlZGVjZXNzb3JzKHYpLCBmdW5jdGlvbih1KSB7CiAgICAgICAgICByZXR1cm4gZy5ub2RlKHUpLmR1bW15OwogICAgICAgIH0pOwogICAgICB9CiAgICB9CgogICAgZnVuY3Rpb24gYWRkQ29uZmxpY3QoY29uZmxpY3RzLCB2LCB3KSB7CiAgICAgIGlmICh2ID4gdykgewogICAgICAgIHZhciB0bXAgPSB2OwogICAgICAgIHYgPSB3OwogICAgICAgIHcgPSB0bXA7CiAgICAgIH0KCiAgICAgIHZhciBjb25mbGljdHNWID0gY29uZmxpY3RzW3ZdOwogICAgICBpZiAoIWNvbmZsaWN0c1YpIHsKICAgICAgICBjb25mbGljdHNbdl0gPSBjb25mbGljdHNWID0ge307CiAgICAgIH0KICAgICAgY29uZmxpY3RzVlt3XSA9IHRydWU7CiAgICB9CgogICAgZnVuY3Rpb24gaGFzQ29uZmxpY3QoY29uZmxpY3RzLCB2LCB3KSB7CiAgICAgIGlmICh2ID4gdykgewogICAgICAgIHZhciB0bXAgPSB2OwogICAgICAgIHYgPSB3OwogICAgICAgIHcgPSB0bXA7CiAgICAgIH0KICAgICAgcmV0dXJuIGxvZGFzaF8xJDEuaGFzKGNvbmZsaWN0c1t2XSwgdyk7CiAgICB9CgogICAgLyoKICAgICAqIFRyeSB0byBhbGlnbiBub2RlcyBpbnRvIHZlcnRpY2FsICJibG9ja3MiIHdoZXJlIHBvc3NpYmxlLiBUaGlzIGFsZ29yaXRobQogICAgICogYXR0ZW1wdHMgdG8gYWxpZ24gYSBub2RlIHdpdGggb25lIG9mIGl0cyBtZWRpYW4gbmVpZ2hib3JzLiBJZiB0aGUgZWRnZQogICAgICogY29ubmVjdGluZyBhIG5laWdoYm9yIGlzIGEgdHlwZS0xIGNvbmZsaWN0IHRoZW4gd2UgaWdub3JlIHRoYXQgcG9zc2liaWxpdHkuCiAgICAgKiBJZiBhIHByZXZpb3VzIG5vZGUgaGFzIGFscmVhZHkgZm9ybWVkIGEgYmxvY2sgd2l0aCBhIG5vZGUgYWZ0ZXIgdGhlIG5vZGUKICAgICAqIHdlJ3JlIHRyeWluZyB0byBmb3JtIGEgYmxvY2sgd2l0aCwgd2UgYWxzbyBpZ25vcmUgdGhhdCBwb3NzaWJpbGl0eSAtIG91cgogICAgICogYmxvY2tzIHdvdWxkIGJlIHNwbGl0IGluIHRoYXQgc2NlbmFyaW8uCiAgICAgKi8KICAgIGZ1bmN0aW9uIHZlcnRpY2FsQWxpZ25tZW50KGcsIGxheWVyaW5nLCBjb25mbGljdHMsIG5laWdoYm9yRm4pIHsKICAgICAgdmFyIHJvb3QgPSB7fSwKICAgICAgICBhbGlnbiA9IHt9LAogICAgICAgIHBvcyA9IHt9OwoKICAgICAgLy8gV2UgY2FjaGUgdGhlIHBvc2l0aW9uIGhlcmUgYmFzZWQgb24gdGhlIGxheWVyaW5nIGJlY2F1c2UgdGhlIGdyYXBoIGFuZAogICAgICAvLyBsYXllcmluZyBtYXkgYmUgb3V0IG9mIHN5bmMuIFRoZSBsYXllcmluZyBtYXRyaXggaXMgbWFuaXB1bGF0ZWQgdG8KICAgICAgLy8gZ2VuZXJhdGUgZGlmZmVyZW50IGV4dHJlbWUgYWxpZ25tZW50cy4KICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyaW5nLCBmdW5jdGlvbihsYXllcikgewogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllciwgZnVuY3Rpb24odiwgb3JkZXIpIHsKICAgICAgICAgIHJvb3Rbdl0gPSB2OwogICAgICAgICAgYWxpZ25bdl0gPSB2OwogICAgICAgICAgcG9zW3ZdID0gb3JkZXI7CiAgICAgICAgfSk7CiAgICAgIH0pOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyaW5nLCBmdW5jdGlvbihsYXllcikgewogICAgICAgIHZhciBwcmV2SWR4ID0gLTE7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyLCBmdW5jdGlvbih2KSB7CiAgICAgICAgICB2YXIgd3MgPSBuZWlnaGJvckZuKHYpOwogICAgICAgICAgaWYgKHdzLmxlbmd0aCkgewogICAgICAgICAgICB3cyA9IGxvZGFzaF8xJDEuc29ydEJ5KHdzLCBmdW5jdGlvbih3KSB7IHJldHVybiBwb3Nbd107IH0pOwogICAgICAgICAgICB2YXIgbXAgPSAod3MubGVuZ3RoIC0gMSkgLyAyOwogICAgICAgICAgICBmb3IgKHZhciBpID0gTWF0aC5mbG9vcihtcCksIGlsID0gTWF0aC5jZWlsKG1wKTsgaSA8PSBpbDsgKytpKSB7CiAgICAgICAgICAgICAgdmFyIHcgPSB3c1tpXTsKICAgICAgICAgICAgICBpZiAoYWxpZ25bdl0gPT09IHYgJiYKICAgICAgICAgICAgICAgICAgcHJldklkeCA8IHBvc1t3XSAmJgogICAgICAgICAgICAgICAgICAhaGFzQ29uZmxpY3QoY29uZmxpY3RzLCB2LCB3KSkgewogICAgICAgICAgICAgICAgYWxpZ25bd10gPSB2OwogICAgICAgICAgICAgICAgYWxpZ25bdl0gPSByb290W3ZdID0gcm9vdFt3XTsKICAgICAgICAgICAgICAgIHByZXZJZHggPSBwb3Nbd107CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIHsgcm9vdDogcm9vdCwgYWxpZ246IGFsaWduIH07CiAgICB9CgogICAgZnVuY3Rpb24gaG9yaXpvbnRhbENvbXBhY3Rpb24oZywgbGF5ZXJpbmcsIHJvb3QsIGFsaWduLCByZXZlcnNlU2VwKSB7CiAgICAgIC8vIFRoaXMgcG9ydGlvbiBvZiB0aGUgYWxnb3JpdGhtIGRpZmZlcnMgZnJvbSBCSyBkdWUgdG8gYSBudW1iZXIgb2YgcHJvYmxlbXMuCiAgICAgIC8vIEluc3RlYWQgb2YgdGhlaXIgYWxnb3JpdGhtIHdlIGNvbnN0cnVjdCBhIG5ldyBibG9jayBncmFwaCBhbmQgZG8gdHdvCiAgICAgIC8vIHN3ZWVwcy4gVGhlIGZpcnN0IHN3ZWVwIHBsYWNlcyBibG9ja3Mgd2l0aCB0aGUgc21hbGxlc3QgcG9zc2libGUKICAgICAgLy8gY29vcmRpbmF0ZXMuIFRoZSBzZWNvbmQgc3dlZXAgcmVtb3ZlcyB1bnVzZWQgc3BhY2UgYnkgbW92aW5nIGJsb2NrcyB0byB0aGUKICAgICAgLy8gZ3JlYXRlc3QgY29vcmRpbmF0ZXMgd2l0aG91dCB2aW9sYXRpbmcgc2VwYXJhdGlvbi4KICAgICAgdmFyIHhzID0ge30sCiAgICAgICAgYmxvY2tHID0gYnVpbGRCbG9ja0dyYXBoKGcsIGxheWVyaW5nLCByb290LCByZXZlcnNlU2VwKSwKICAgICAgICBib3JkZXJUeXBlID0gcmV2ZXJzZVNlcCA/ICJib3JkZXJMZWZ0IiA6ICJib3JkZXJSaWdodCI7CgogICAgICBmdW5jdGlvbiBpdGVyYXRlKHNldFhzRnVuYywgbmV4dE5vZGVzRnVuYykgewogICAgICAgIHZhciBzdGFjayA9IGJsb2NrRy5ub2RlcygpOwogICAgICAgIHZhciBlbGVtID0gc3RhY2sucG9wKCk7CiAgICAgICAgdmFyIHZpc2l0ZWQgPSB7fTsKICAgICAgICB3aGlsZSAoZWxlbSkgewogICAgICAgICAgaWYgKHZpc2l0ZWRbZWxlbV0pIHsKICAgICAgICAgICAgc2V0WHNGdW5jKGVsZW0pOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdmlzaXRlZFtlbGVtXSA9IHRydWU7CiAgICAgICAgICAgIHN0YWNrLnB1c2goZWxlbSk7CiAgICAgICAgICAgIHN0YWNrID0gc3RhY2suY29uY2F0KG5leHROb2Rlc0Z1bmMoZWxlbSkpOwogICAgICAgICAgfQoKICAgICAgICAgIGVsZW0gPSBzdGFjay5wb3AoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8vIEZpcnN0IHBhc3MsIGFzc2lnbiBzbWFsbGVzdCBjb29yZGluYXRlcwogICAgICBmdW5jdGlvbiBwYXNzMShlbGVtKSB7CiAgICAgICAgeHNbZWxlbV0gPSBibG9ja0cuaW5FZGdlcyhlbGVtKS5yZWR1Y2UoZnVuY3Rpb24oYWNjLCBlKSB7CiAgICAgICAgICByZXR1cm4gTWF0aC5tYXgoYWNjLCB4c1tlLnZdICsgYmxvY2tHLmVkZ2UoZSkpOwogICAgICAgIH0sIDApOwogICAgICB9CgogICAgICAvLyBTZWNvbmQgcGFzcywgYXNzaWduIGdyZWF0ZXN0IGNvb3JkaW5hdGVzCiAgICAgIGZ1bmN0aW9uIHBhc3MyKGVsZW0pIHsKICAgICAgICB2YXIgbWluID0gYmxvY2tHLm91dEVkZ2VzKGVsZW0pLnJlZHVjZShmdW5jdGlvbihhY2MsIGUpIHsKICAgICAgICAgIHJldHVybiBNYXRoLm1pbihhY2MsIHhzW2Uud10gLSBibG9ja0cuZWRnZShlKSk7CiAgICAgICAgfSwgTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZKTsKCiAgICAgICAgdmFyIG5vZGUgPSBnLm5vZGUoZWxlbSk7CiAgICAgICAgaWYgKG1pbiAhPT0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZICYmIG5vZGUuYm9yZGVyVHlwZSAhPT0gYm9yZGVyVHlwZSkgewogICAgICAgICAgeHNbZWxlbV0gPSBNYXRoLm1heCh4c1tlbGVtXSwgbWluKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIGl0ZXJhdGUocGFzczEsIGJsb2NrRy5wcmVkZWNlc3NvcnMuYmluZChibG9ja0cpKTsKICAgICAgaXRlcmF0ZShwYXNzMiwgYmxvY2tHLnN1Y2Nlc3NvcnMuYmluZChibG9ja0cpKTsKCiAgICAgIC8vIEFzc2lnbiB4IGNvb3JkaW5hdGVzIHRvIGFsbCBub2RlcwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goYWxpZ24sIGZ1bmN0aW9uKHYpIHsKICAgICAgICB4c1t2XSA9IHhzW3Jvb3Rbdl1dOwogICAgICB9KTsKCiAgICAgIHJldHVybiB4czsKICAgIH0KCgogICAgZnVuY3Rpb24gYnVpbGRCbG9ja0dyYXBoKGcsIGxheWVyaW5nLCByb290LCByZXZlcnNlU2VwKSB7CiAgICAgIHZhciBibG9ja0dyYXBoID0gbmV3IEdyYXBoJDYoKSwKICAgICAgICBncmFwaExhYmVsID0gZy5ncmFwaCgpLAogICAgICAgIHNlcEZuID0gc2VwKGdyYXBoTGFiZWwubm9kZXNlcCwgZ3JhcGhMYWJlbC5lZGdlc2VwLCByZXZlcnNlU2VwKTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllcmluZywgZnVuY3Rpb24obGF5ZXIpIHsKICAgICAgICB2YXIgdTsKICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2gobGF5ZXIsIGZ1bmN0aW9uKHYpIHsKICAgICAgICAgIHZhciB2Um9vdCA9IHJvb3Rbdl07CiAgICAgICAgICBibG9ja0dyYXBoLnNldE5vZGUodlJvb3QpOwogICAgICAgICAgaWYgKHUpIHsKICAgICAgICAgICAgdmFyIHVSb290ID0gcm9vdFt1XSwKICAgICAgICAgICAgICBwcmV2TWF4ID0gYmxvY2tHcmFwaC5lZGdlKHVSb290LCB2Um9vdCk7CiAgICAgICAgICAgIGJsb2NrR3JhcGguc2V0RWRnZSh1Um9vdCwgdlJvb3QsIE1hdGgubWF4KHNlcEZuKGcsIHYsIHUpLCBwcmV2TWF4IHx8IDApKTsKICAgICAgICAgIH0KICAgICAgICAgIHUgPSB2OwogICAgICAgIH0pOwogICAgICB9KTsKCiAgICAgIHJldHVybiBibG9ja0dyYXBoOwogICAgfQoKICAgIC8qCiAgICAgKiBSZXR1cm5zIHRoZSBhbGlnbm1lbnQgdGhhdCBoYXMgdGhlIHNtYWxsZXN0IHdpZHRoIG9mIHRoZSBnaXZlbiBhbGlnbm1lbnRzLgogICAgICovCiAgICBmdW5jdGlvbiBmaW5kU21hbGxlc3RXaWR0aEFsaWdubWVudChnLCB4c3MpIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xJDEubWluQnkobG9kYXNoXzEkMS52YWx1ZXMoeHNzKSwgZnVuY3Rpb24gKHhzKSB7CiAgICAgICAgdmFyIG1heCA9IE51bWJlci5ORUdBVElWRV9JTkZJTklUWTsKICAgICAgICB2YXIgbWluID0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZOwoKICAgICAgICBsb2Rhc2hfMSQxLmZvckluKHhzLCBmdW5jdGlvbiAoeCwgdikgewogICAgICAgICAgdmFyIGhhbGZXaWR0aCA9IHdpZHRoKGcsIHYpIC8gMjsKCiAgICAgICAgICBtYXggPSBNYXRoLm1heCh4ICsgaGFsZldpZHRoLCBtYXgpOwogICAgICAgICAgbWluID0gTWF0aC5taW4oeCAtIGhhbGZXaWR0aCwgbWluKTsKICAgICAgICB9KTsKCiAgICAgICAgcmV0dXJuIG1heCAtIG1pbjsKICAgICAgfSk7CiAgICB9CgogICAgLyoKICAgICAqIEFsaWduIHRoZSBjb29yZGluYXRlcyBvZiBlYWNoIG9mIHRoZSBsYXlvdXQgYWxpZ25tZW50cyBzdWNoIHRoYXQKICAgICAqIGxlZnQtYmlhc2VkIGFsaWdubWVudHMgaGF2ZSB0aGVpciBtaW5pbXVtIGNvb3JkaW5hdGUgYXQgdGhlIHNhbWUgcG9pbnQgYXMKICAgICAqIHRoZSBtaW5pbXVtIGNvb3JkaW5hdGUgb2YgdGhlIHNtYWxsZXN0IHdpZHRoIGFsaWdubWVudCBhbmQgcmlnaHQtYmlhc2VkCiAgICAgKiBhbGlnbm1lbnRzIGhhdmUgdGhlaXIgbWF4aW11bSBjb29yZGluYXRlIGF0IHRoZSBzYW1lIHBvaW50IGFzIHRoZSBtYXhpbXVtCiAgICAgKiBjb29yZGluYXRlIG9mIHRoZSBzbWFsbGVzdCB3aWR0aCBhbGlnbm1lbnQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFsaWduQ29vcmRpbmF0ZXMoeHNzLCBhbGlnblRvKSB7CiAgICAgIHZhciBhbGlnblRvVmFscyA9IGxvZGFzaF8xJDEudmFsdWVzKGFsaWduVG8pLAogICAgICAgIGFsaWduVG9NaW4gPSBsb2Rhc2hfMSQxLm1pbihhbGlnblRvVmFscyksCiAgICAgICAgYWxpZ25Ub01heCA9IGxvZGFzaF8xJDEubWF4KGFsaWduVG9WYWxzKTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChbInUiLCAiZCJdLCBmdW5jdGlvbih2ZXJ0KSB7CiAgICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKFsibCIsICJyIl0sIGZ1bmN0aW9uKGhvcml6KSB7CiAgICAgICAgICB2YXIgYWxpZ25tZW50ID0gdmVydCArIGhvcml6LAogICAgICAgICAgICB4cyA9IHhzc1thbGlnbm1lbnRdLAogICAgICAgICAgICBkZWx0YTsKICAgICAgICAgIGlmICh4cyA9PT0gYWxpZ25UbykgcmV0dXJuOwoKICAgICAgICAgIHZhciB4c1ZhbHMgPSBsb2Rhc2hfMSQxLnZhbHVlcyh4cyk7CiAgICAgICAgICBkZWx0YSA9IGhvcml6ID09PSAibCIgPyBhbGlnblRvTWluIC0gbG9kYXNoXzEkMS5taW4oeHNWYWxzKSA6IGFsaWduVG9NYXggLSBsb2Rhc2hfMSQxLm1heCh4c1ZhbHMpOwoKICAgICAgICAgIGlmIChkZWx0YSkgewogICAgICAgICAgICB4c3NbYWxpZ25tZW50XSA9IGxvZGFzaF8xJDEubWFwVmFsdWVzKHhzLCBmdW5jdGlvbih4KSB7IHJldHVybiB4ICsgZGVsdGE7IH0pOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBiYWxhbmNlKHhzcywgYWxpZ24pIHsKICAgICAgcmV0dXJuIGxvZGFzaF8xJDEubWFwVmFsdWVzKHhzcy51bCwgZnVuY3Rpb24oaWdub3JlLCB2KSB7CiAgICAgICAgaWYgKGFsaWduKSB7CiAgICAgICAgICByZXR1cm4geHNzW2FsaWduLnRvTG93ZXJDYXNlKCldW3ZdOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB2YXIgeHMgPSBsb2Rhc2hfMSQxLnNvcnRCeShsb2Rhc2hfMSQxLm1hcCh4c3MsIHYpKTsKICAgICAgICAgIHJldHVybiAoeHNbMV0gKyB4c1syXSkgLyAyOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcG9zaXRpb25YKGcpIHsKICAgICAgdmFyIGxheWVyaW5nID0gdXRpbC5idWlsZExheWVyTWF0cml4KGcpOwogICAgICB2YXIgY29uZmxpY3RzID0gbG9kYXNoXzEkMS5tZXJnZSgKICAgICAgICBmaW5kVHlwZTFDb25mbGljdHMoZywgbGF5ZXJpbmcpLAogICAgICAgIGZpbmRUeXBlMkNvbmZsaWN0cyhnLCBsYXllcmluZykpOwoKICAgICAgdmFyIHhzcyA9IHt9OwogICAgICB2YXIgYWRqdXN0ZWRMYXllcmluZzsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKFsidSIsICJkIl0sIGZ1bmN0aW9uKHZlcnQpIHsKICAgICAgICBhZGp1c3RlZExheWVyaW5nID0gdmVydCA9PT0gInUiID8gbGF5ZXJpbmcgOiBsb2Rhc2hfMSQxLnZhbHVlcyhsYXllcmluZykucmV2ZXJzZSgpOwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChbImwiLCAiciJdLCBmdW5jdGlvbihob3JpeikgewogICAgICAgICAgaWYgKGhvcml6ID09PSAiciIpIHsKICAgICAgICAgICAgYWRqdXN0ZWRMYXllcmluZyA9IGxvZGFzaF8xJDEubWFwKGFkanVzdGVkTGF5ZXJpbmcsIGZ1bmN0aW9uKGlubmVyKSB7CiAgICAgICAgICAgICAgcmV0dXJuIGxvZGFzaF8xJDEudmFsdWVzKGlubmVyKS5yZXZlcnNlKCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQoKICAgICAgICAgIHZhciBuZWlnaGJvckZuID0gKHZlcnQgPT09ICJ1IiA/IGcucHJlZGVjZXNzb3JzIDogZy5zdWNjZXNzb3JzKS5iaW5kKGcpOwogICAgICAgICAgdmFyIGFsaWduID0gdmVydGljYWxBbGlnbm1lbnQoZywgYWRqdXN0ZWRMYXllcmluZywgY29uZmxpY3RzLCBuZWlnaGJvckZuKTsKICAgICAgICAgIHZhciB4cyA9IGhvcml6b250YWxDb21wYWN0aW9uKGcsIGFkanVzdGVkTGF5ZXJpbmcsCiAgICAgICAgICAgIGFsaWduLnJvb3QsIGFsaWduLmFsaWduLCBob3JpeiA9PT0gInIiKTsKICAgICAgICAgIGlmIChob3JpeiA9PT0gInIiKSB7CiAgICAgICAgICAgIHhzID0gbG9kYXNoXzEkMS5tYXBWYWx1ZXMoeHMsIGZ1bmN0aW9uKHgpIHsgcmV0dXJuIC14OyB9KTsKICAgICAgICAgIH0KICAgICAgICAgIHhzc1t2ZXJ0ICsgaG9yaXpdID0geHM7CiAgICAgICAgfSk7CiAgICAgIH0pOwoKICAgICAgdmFyIHNtYWxsZXN0V2lkdGggPSBmaW5kU21hbGxlc3RXaWR0aEFsaWdubWVudChnLCB4c3MpOwogICAgICBhbGlnbkNvb3JkaW5hdGVzKHhzcywgc21hbGxlc3RXaWR0aCk7CiAgICAgIHJldHVybiBiYWxhbmNlKHhzcywgZy5ncmFwaCgpLmFsaWduKTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZXAobm9kZVNlcCwgZWRnZVNlcCwgcmV2ZXJzZVNlcCkgewogICAgICByZXR1cm4gZnVuY3Rpb24oZywgdiwgdykgewogICAgICAgIHZhciB2TGFiZWwgPSBnLm5vZGUodik7CiAgICAgICAgdmFyIHdMYWJlbCA9IGcubm9kZSh3KTsKICAgICAgICB2YXIgc3VtID0gMDsKICAgICAgICB2YXIgZGVsdGE7CgogICAgICAgIHN1bSArPSB2TGFiZWwud2lkdGggLyAyOwogICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyh2TGFiZWwsICJsYWJlbHBvcyIpKSB7CiAgICAgICAgICBzd2l0Y2ggKHZMYWJlbC5sYWJlbHBvcy50b0xvd2VyQ2FzZSgpKSB7CiAgICAgICAgICBjYXNlICJsIjogZGVsdGEgPSAtdkxhYmVsLndpZHRoIC8gMjsgYnJlYWs7CiAgICAgICAgICBjYXNlICJyIjogZGVsdGEgPSB2TGFiZWwud2lkdGggLyAyOyBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKGRlbHRhKSB7CiAgICAgICAgICBzdW0gKz0gcmV2ZXJzZVNlcCA/IGRlbHRhIDogLWRlbHRhOwogICAgICAgIH0KICAgICAgICBkZWx0YSA9IDA7CgogICAgICAgIHN1bSArPSAodkxhYmVsLmR1bW15ID8gZWRnZVNlcCA6IG5vZGVTZXApIC8gMjsKICAgICAgICBzdW0gKz0gKHdMYWJlbC5kdW1teSA/IGVkZ2VTZXAgOiBub2RlU2VwKSAvIDI7CgogICAgICAgIHN1bSArPSB3TGFiZWwud2lkdGggLyAyOwogICAgICAgIGlmIChsb2Rhc2hfMSQxLmhhcyh3TGFiZWwsICJsYWJlbHBvcyIpKSB7CiAgICAgICAgICBzd2l0Y2ggKHdMYWJlbC5sYWJlbHBvcy50b0xvd2VyQ2FzZSgpKSB7CiAgICAgICAgICBjYXNlICJsIjogZGVsdGEgPSB3TGFiZWwud2lkdGggLyAyOyBicmVhazsKICAgICAgICAgIGNhc2UgInIiOiBkZWx0YSA9IC13TGFiZWwud2lkdGggLyAyOyBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaWYgKGRlbHRhKSB7CiAgICAgICAgICBzdW0gKz0gcmV2ZXJzZVNlcCA/IGRlbHRhIDogLWRlbHRhOwogICAgICAgIH0KICAgICAgICBkZWx0YSA9IDA7CgogICAgICAgIHJldHVybiBzdW07CiAgICAgIH07CiAgICB9CgogICAgZnVuY3Rpb24gd2lkdGgoZywgdikgewogICAgICByZXR1cm4gZy5ub2RlKHYpLndpZHRoOwogICAgfQoKICAgIHZhciBwb3NpdGlvblgkMSA9IGJrLnBvc2l0aW9uWDsKCiAgICB2YXIgcG9zaXRpb25fMSA9IHBvc2l0aW9uOwoKICAgIGZ1bmN0aW9uIHBvc2l0aW9uKGcpIHsKICAgICAgZyA9IHV0aWwuYXNOb25Db21wb3VuZEdyYXBoKGcpOwoKICAgICAgcG9zaXRpb25ZKGcpOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2gocG9zaXRpb25YJDEoZyksIGZ1bmN0aW9uKHgsIHYpIHsKICAgICAgICBnLm5vZGUodikueCA9IHg7CiAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIHBvc2l0aW9uWShnKSB7CiAgICAgIHZhciBsYXllcmluZyA9IHV0aWwuYnVpbGRMYXllck1hdHJpeChnKTsKICAgICAgdmFyIHJhbmtTZXAgPSBnLmdyYXBoKCkucmFua3NlcDsKICAgICAgdmFyIHByZXZZID0gMDsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGxheWVyaW5nLCBmdW5jdGlvbihsYXllcikgewogICAgICAgIHZhciBtYXhIZWlnaHQgPSBsb2Rhc2hfMSQxLm1heChsb2Rhc2hfMSQxLm1hcChsYXllciwgZnVuY3Rpb24odikgeyByZXR1cm4gZy5ub2RlKHYpLmhlaWdodDsgfSkpOwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllciwgZnVuY3Rpb24odikgewogICAgICAgICAgZy5ub2RlKHYpLnkgPSBwcmV2WSArIG1heEhlaWdodCAvIDI7CiAgICAgICAgfSk7CiAgICAgICAgcHJldlkgKz0gbWF4SGVpZ2h0ICsgcmFua1NlcDsKICAgICAgfSk7CiAgICB9CgogICAgdmFyIG5vcm1hbGl6ZVJhbmtzJDEgPSB1dGlsLm5vcm1hbGl6ZVJhbmtzOwoKICAgIHZhciByZW1vdmVFbXB0eVJhbmtzJDEgPSB1dGlsLnJlbW92ZUVtcHR5UmFua3M7CgoKCgoKICAgIHZhciB1dGlsJDIgPSB1dGlsOwogICAgdmFyIEdyYXBoJDcgPSBncmFwaGxpYl8xLkdyYXBoOwoKICAgIHZhciBsYXlvdXRfMSA9IGxheW91dDsKCiAgICBmdW5jdGlvbiBsYXlvdXQoZywgb3B0cykgewogICAgICB2YXIgdGltZSA9IG9wdHMgJiYgb3B0cy5kZWJ1Z1RpbWluZyA/IHV0aWwkMi50aW1lIDogdXRpbCQyLm5vdGltZTsKICAgICAgdGltZSgibGF5b3V0IiwgZnVuY3Rpb24oKSB7CiAgICAgICAgdmFyIGxheW91dEdyYXBoID0gCiAgICAgICAgICB0aW1lKCIgIGJ1aWxkTGF5b3V0R3JhcGgiLCBmdW5jdGlvbigpIHsgcmV0dXJuIGJ1aWxkTGF5b3V0R3JhcGgoZyk7IH0pOwogICAgICAgIHRpbWUoIiAgcnVuTGF5b3V0IiwgICAgICAgIGZ1bmN0aW9uKCkgeyBydW5MYXlvdXQobGF5b3V0R3JhcGgsIHRpbWUpOyB9KTsKICAgICAgICB0aW1lKCIgIHVwZGF0ZUlucHV0R3JhcGgiLCBmdW5jdGlvbigpIHsgdXBkYXRlSW5wdXRHcmFwaChnLCBsYXlvdXRHcmFwaCk7IH0pOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBydW5MYXlvdXQoZywgdGltZSkgewogICAgICB0aW1lKCIgICAgbWFrZVNwYWNlRm9yRWRnZUxhYmVscyIsIGZ1bmN0aW9uKCkgeyBtYWtlU3BhY2VGb3JFZGdlTGFiZWxzKGcpOyB9KTsKICAgICAgdGltZSgiICAgIHJlbW92ZVNlbGZFZGdlcyIsICAgICAgICBmdW5jdGlvbigpIHsgcmVtb3ZlU2VsZkVkZ2VzKGcpOyB9KTsKICAgICAgdGltZSgiICAgIGFjeWNsaWMiLCAgICAgICAgICAgICAgICBmdW5jdGlvbigpIHsgYWN5Y2xpYy5ydW4oZyk7IH0pOwogICAgICB0aW1lKCIgICAgbmVzdGluZ0dyYXBoLnJ1biIsICAgICAgIGZ1bmN0aW9uKCkgeyBuZXN0aW5nR3JhcGgucnVuKGcpOyB9KTsKICAgICAgdGltZSgiICAgIHJhbmsiLCAgICAgICAgICAgICAgICAgICBmdW5jdGlvbigpIHsgcmFua18xKHV0aWwkMi5hc05vbkNvbXBvdW5kR3JhcGgoZykpOyB9KTsKICAgICAgdGltZSgiICAgIGluamVjdEVkZ2VMYWJlbFByb3hpZXMiLCBmdW5jdGlvbigpIHsgaW5qZWN0RWRnZUxhYmVsUHJveGllcyhnKTsgfSk7CiAgICAgIHRpbWUoIiAgICByZW1vdmVFbXB0eVJhbmtzIiwgICAgICAgZnVuY3Rpb24oKSB7IHJlbW92ZUVtcHR5UmFua3MkMShnKTsgfSk7CiAgICAgIHRpbWUoIiAgICBuZXN0aW5nR3JhcGguY2xlYW51cCIsICAgZnVuY3Rpb24oKSB7IG5lc3RpbmdHcmFwaC5jbGVhbnVwKGcpOyB9KTsKICAgICAgdGltZSgiICAgIG5vcm1hbGl6ZVJhbmtzIiwgICAgICAgICBmdW5jdGlvbigpIHsgbm9ybWFsaXplUmFua3MkMShnKTsgfSk7CiAgICAgIHRpbWUoIiAgICBhc3NpZ25SYW5rTWluTWF4IiwgICAgICAgZnVuY3Rpb24oKSB7IGFzc2lnblJhbmtNaW5NYXgoZyk7IH0pOwogICAgICB0aW1lKCIgICAgcmVtb3ZlRWRnZUxhYmVsUHJveGllcyIsIGZ1bmN0aW9uKCkgeyByZW1vdmVFZGdlTGFiZWxQcm94aWVzKGcpOyB9KTsKICAgICAgdGltZSgiICAgIG5vcm1hbGl6ZS5ydW4iLCAgICAgICAgICBmdW5jdGlvbigpIHsgbm9ybWFsaXplJDIucnVuKGcpOyB9KTsKICAgICAgdGltZSgiICAgIHBhcmVudER1bW15Q2hhaW5zIiwgICAgICBmdW5jdGlvbigpIHsgcGFyZW50RHVtbXlDaGFpbnNfMShnKTsgfSk7CiAgICAgIHRpbWUoIiAgICBhZGRCb3JkZXJTZWdtZW50cyIsICAgICAgZnVuY3Rpb24oKSB7IGFkZEJvcmRlclNlZ21lbnRzXzEoZyk7IH0pOwogICAgICB0aW1lKCIgICAgb3JkZXIiLCAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uKCkgeyBvcmRlcl8xKGcpOyB9KTsKICAgICAgdGltZSgiICAgIGluc2VydFNlbGZFZGdlcyIsICAgICAgICBmdW5jdGlvbigpIHsgaW5zZXJ0U2VsZkVkZ2VzKGcpOyB9KTsKICAgICAgdGltZSgiICAgIGFkanVzdENvb3JkaW5hdGVTeXN0ZW0iLCBmdW5jdGlvbigpIHsgY29vcmRpbmF0ZVN5c3RlbS5hZGp1c3QoZyk7IH0pOwogICAgICB0aW1lKCIgICAgcG9zaXRpb24iLCAgICAgICAgICAgICAgIGZ1bmN0aW9uKCkgeyBwb3NpdGlvbl8xKGcpOyB9KTsKICAgICAgdGltZSgiICAgIHBvc2l0aW9uU2VsZkVkZ2VzIiwgICAgICBmdW5jdGlvbigpIHsgcG9zaXRpb25TZWxmRWRnZXMoZyk7IH0pOwogICAgICB0aW1lKCIgICAgcmVtb3ZlQm9yZGVyTm9kZXMiLCAgICAgIGZ1bmN0aW9uKCkgeyByZW1vdmVCb3JkZXJOb2RlcyhnKTsgfSk7CiAgICAgIHRpbWUoIiAgICBub3JtYWxpemUudW5kbyIsICAgICAgICAgZnVuY3Rpb24oKSB7IG5vcm1hbGl6ZSQyLnVuZG8oZyk7IH0pOwogICAgICB0aW1lKCIgICAgZml4dXBFZGdlTGFiZWxDb29yZHMiLCAgIGZ1bmN0aW9uKCkgeyBmaXh1cEVkZ2VMYWJlbENvb3JkcyhnKTsgfSk7CiAgICAgIHRpbWUoIiAgICB1bmRvQ29vcmRpbmF0ZVN5c3RlbSIsICAgZnVuY3Rpb24oKSB7IGNvb3JkaW5hdGVTeXN0ZW0udW5kbyhnKTsgfSk7CiAgICAgIHRpbWUoIiAgICB0cmFuc2xhdGVHcmFwaCIsICAgICAgICAgZnVuY3Rpb24oKSB7IHRyYW5zbGF0ZUdyYXBoKGcpOyB9KTsKICAgICAgdGltZSgiICAgIGFzc2lnbk5vZGVJbnRlcnNlY3RzIiwgICBmdW5jdGlvbigpIHsgYXNzaWduTm9kZUludGVyc2VjdHMoZyk7IH0pOwogICAgICB0aW1lKCIgICAgcmV2ZXJzZVBvaW50cyIsICAgICAgICAgIGZ1bmN0aW9uKCkgeyByZXZlcnNlUG9pbnRzRm9yUmV2ZXJzZWRFZGdlcyhnKTsgfSk7CiAgICAgIHRpbWUoIiAgICBhY3ljbGljLnVuZG8iLCAgICAgICAgICAgZnVuY3Rpb24oKSB7IGFjeWNsaWMudW5kbyhnKTsgfSk7CiAgICB9CgogICAgLyoKICAgICAqIENvcGllcyBmaW5hbCBsYXlvdXQgaW5mb3JtYXRpb24gZnJvbSB0aGUgbGF5b3V0IGdyYXBoIGJhY2sgdG8gdGhlIGlucHV0CiAgICAgKiBncmFwaC4gVGhpcyBwcm9jZXNzIG9ubHkgY29waWVzIHdoaXRlbGlzdGVkIGF0dHJpYnV0ZXMgZnJvbSB0aGUgbGF5b3V0IGdyYXBoCiAgICAgKiB0byB0aGUgaW5wdXQgZ3JhcGgsIHNvIGl0IHNlcnZlcyBhcyBhIGdvb2QgcGxhY2UgdG8gZGV0ZXJtaW5lIHdoYXQKICAgICAqIGF0dHJpYnV0ZXMgY2FuIGluZmx1ZW5jZSBsYXlvdXQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHVwZGF0ZUlucHV0R3JhcGgoaW5wdXRHcmFwaCwgbGF5b3V0R3JhcGgpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGlucHV0R3JhcGgubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBpbnB1dExhYmVsID0gaW5wdXRHcmFwaC5ub2RlKHYpOwogICAgICAgIHZhciBsYXlvdXRMYWJlbCA9IGxheW91dEdyYXBoLm5vZGUodik7CgogICAgICAgIGlmIChpbnB1dExhYmVsKSB7CiAgICAgICAgICBpbnB1dExhYmVsLnggPSBsYXlvdXRMYWJlbC54OwogICAgICAgICAgaW5wdXRMYWJlbC55ID0gbGF5b3V0TGFiZWwueTsKCiAgICAgICAgICBpZiAobGF5b3V0R3JhcGguY2hpbGRyZW4odikubGVuZ3RoKSB7CiAgICAgICAgICAgIGlucHV0TGFiZWwud2lkdGggPSBsYXlvdXRMYWJlbC53aWR0aDsKICAgICAgICAgICAgaW5wdXRMYWJlbC5oZWlnaHQgPSBsYXlvdXRMYWJlbC5oZWlnaHQ7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChpbnB1dEdyYXBoLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgaW5wdXRMYWJlbCA9IGlucHV0R3JhcGguZWRnZShlKTsKICAgICAgICB2YXIgbGF5b3V0TGFiZWwgPSBsYXlvdXRHcmFwaC5lZGdlKGUpOwoKICAgICAgICBpbnB1dExhYmVsLnBvaW50cyA9IGxheW91dExhYmVsLnBvaW50czsKICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMobGF5b3V0TGFiZWwsICJ4IikpIHsKICAgICAgICAgIGlucHV0TGFiZWwueCA9IGxheW91dExhYmVsLng7CiAgICAgICAgICBpbnB1dExhYmVsLnkgPSBsYXlvdXRMYWJlbC55OwogICAgICAgIH0KICAgICAgfSk7CgogICAgICBpbnB1dEdyYXBoLmdyYXBoKCkud2lkdGggPSBsYXlvdXRHcmFwaC5ncmFwaCgpLndpZHRoOwogICAgICBpbnB1dEdyYXBoLmdyYXBoKCkuaGVpZ2h0ID0gbGF5b3V0R3JhcGguZ3JhcGgoKS5oZWlnaHQ7CiAgICB9CgogICAgdmFyIGdyYXBoTnVtQXR0cnMgPSBbIm5vZGVzZXAiLCAiZWRnZXNlcCIsICJyYW5rc2VwIiwgIm1hcmdpbngiLCAibWFyZ2lueSJdOwogICAgdmFyIGdyYXBoRGVmYXVsdHMgPSB7IHJhbmtzZXA6IDUwLCBlZGdlc2VwOiAyMCwgbm9kZXNlcDogNTAsIHJhbmtkaXI6ICJ0YiIgfTsKICAgIHZhciBncmFwaEF0dHJzID0gWyJhY3ljbGljZXIiLCAicmFua2VyIiwgInJhbmtkaXIiLCAiYWxpZ24iXTsKICAgIHZhciBub2RlTnVtQXR0cnMgPSBbIndpZHRoIiwgImhlaWdodCJdOwogICAgdmFyIG5vZGVEZWZhdWx0cyA9IHsgd2lkdGg6IDAsIGhlaWdodDogMCB9OwogICAgdmFyIGVkZ2VOdW1BdHRycyA9IFsibWlubGVuIiwgIndlaWdodCIsICJ3aWR0aCIsICJoZWlnaHQiLCAibGFiZWxvZmZzZXQiXTsKICAgIHZhciBlZGdlRGVmYXVsdHMgPSB7CiAgICAgIG1pbmxlbjogMSwgd2VpZ2h0OiAxLCB3aWR0aDogMCwgaGVpZ2h0OiAwLAogICAgICBsYWJlbG9mZnNldDogMTAsIGxhYmVscG9zOiAiciIKICAgIH07CiAgICB2YXIgZWRnZUF0dHJzID0gWyJsYWJlbHBvcyJdOwoKICAgIC8qCiAgICAgKiBDb25zdHJ1Y3RzIGEgbmV3IGdyYXBoIGZyb20gdGhlIGlucHV0IGdyYXBoLCB3aGljaCBjYW4gYmUgdXNlZCBmb3IgbGF5b3V0LgogICAgICogVGhpcyBwcm9jZXNzIGNvcGllcyBvbmx5IHdoaXRlbGlzdGVkIGF0dHJpYnV0ZXMgZnJvbSB0aGUgaW5wdXQgZ3JhcGggdG8gdGhlCiAgICAgKiBsYXlvdXQgZ3JhcGguIFRodXMgdGhpcyBmdW5jdGlvbiBzZXJ2ZXMgYXMgYSBnb29kIHBsYWNlIHRvIGRldGVybWluZSB3aGF0CiAgICAgKiBhdHRyaWJ1dGVzIGNhbiBpbmZsdWVuY2UgbGF5b3V0LgogICAgICovCiAgICBmdW5jdGlvbiBidWlsZExheW91dEdyYXBoKGlucHV0R3JhcGgpIHsKICAgICAgdmFyIGcgPSBuZXcgR3JhcGgkNyh7IG11bHRpZ3JhcGg6IHRydWUsIGNvbXBvdW5kOiB0cnVlIH0pOwogICAgICB2YXIgZ3JhcGggPSBjYW5vbmljYWxpemUoaW5wdXRHcmFwaC5ncmFwaCgpKTsKCiAgICAgIGcuc2V0R3JhcGgobG9kYXNoXzEkMS5tZXJnZSh7fSwKICAgICAgICBncmFwaERlZmF1bHRzLAogICAgICAgIHNlbGVjdE51bWJlckF0dHJzKGdyYXBoLCBncmFwaE51bUF0dHJzKSwKICAgICAgICBsb2Rhc2hfMSQxLnBpY2soZ3JhcGgsIGdyYXBoQXR0cnMpKSk7CgogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goaW5wdXRHcmFwaC5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIG5vZGUgPSBjYW5vbmljYWxpemUoaW5wdXRHcmFwaC5ub2RlKHYpKTsKICAgICAgICBnLnNldE5vZGUodiwgbG9kYXNoXzEkMS5kZWZhdWx0cyhzZWxlY3ROdW1iZXJBdHRycyhub2RlLCBub2RlTnVtQXR0cnMpLCBub2RlRGVmYXVsdHMpKTsKICAgICAgICBnLnNldFBhcmVudCh2LCBpbnB1dEdyYXBoLnBhcmVudCh2KSk7CiAgICAgIH0pOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGlucHV0R3JhcGguZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBlZGdlID0gY2Fub25pY2FsaXplKGlucHV0R3JhcGguZWRnZShlKSk7CiAgICAgICAgZy5zZXRFZGdlKGUsIGxvZGFzaF8xJDEubWVyZ2Uoe30sCiAgICAgICAgICBlZGdlRGVmYXVsdHMsCiAgICAgICAgICBzZWxlY3ROdW1iZXJBdHRycyhlZGdlLCBlZGdlTnVtQXR0cnMpLAogICAgICAgICAgbG9kYXNoXzEkMS5waWNrKGVkZ2UsIGVkZ2VBdHRycykpKTsKICAgICAgfSk7CgogICAgICByZXR1cm4gZzsKICAgIH0KCiAgICAvKgogICAgICogVGhpcyBpZGVhIGNvbWVzIGZyb20gdGhlIEdhbnNuZXIgcGFwZXI6IHRvIGFjY291bnQgZm9yIGVkZ2UgbGFiZWxzIGluIG91cgogICAgICogbGF5b3V0IHdlIHNwbGl0IGVhY2ggcmFuayBpbiBoYWxmIGJ5IGRvdWJsaW5nIG1pbmxlbiBhbmQgaGFsdmluZyByYW5rc2VwLgogICAgICogVGhlbiB3ZSBjYW4gcGxhY2UgbGFiZWxzIGF0IHRoZXNlIG1pZC1wb2ludHMgYmV0d2VlbiBub2Rlcy4KICAgICAqCiAgICAgKiBXZSBhbHNvIGFkZCBzb21lIG1pbmltYWwgcGFkZGluZyB0byB0aGUgd2lkdGggdG8gcHVzaCB0aGUgbGFiZWwgZm9yIHRoZSBlZGdlCiAgICAgKiBhd2F5IGZyb20gdGhlIGVkZ2UgaXRzZWxmIGEgYml0LgogICAgICovCiAgICBmdW5jdGlvbiBtYWtlU3BhY2VGb3JFZGdlTGFiZWxzKGcpIHsKICAgICAgdmFyIGdyYXBoID0gZy5ncmFwaCgpOwogICAgICBncmFwaC5yYW5rc2VwIC89IDI7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBlZGdlLm1pbmxlbiAqPSAyOwogICAgICAgIGlmIChlZGdlLmxhYmVscG9zLnRvTG93ZXJDYXNlKCkgIT09ICJjIikgewogICAgICAgICAgaWYgKGdyYXBoLnJhbmtkaXIgPT09ICJUQiIgfHwgZ3JhcGgucmFua2RpciA9PT0gIkJUIikgewogICAgICAgICAgICBlZGdlLndpZHRoICs9IGVkZ2UubGFiZWxvZmZzZXQ7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBlZGdlLmhlaWdodCArPSBlZGdlLmxhYmVsb2Zmc2V0OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgLyoKICAgICAqIENyZWF0ZXMgdGVtcG9yYXJ5IGR1bW15IG5vZGVzIHRoYXQgY2FwdHVyZSB0aGUgcmFuayBpbiB3aGljaCBlYWNoIGVkZ2UncwogICAgICogbGFiZWwgaXMgZ29pbmcgdG8sIGlmIGl0IGhhcyBvbmUgb2Ygbm9uLXplcm8gd2lkdGggYW5kIGhlaWdodC4gV2UgZG8gdGhpcwogICAgICogc28gdGhhdCB3ZSBjYW4gc2FmZWx5IHJlbW92ZSBlbXB0eSByYW5rcyB3aGlsZSBwcmVzZXJ2aW5nIGJhbGFuY2UgZm9yIHRoZQogICAgICogbGFiZWwncyBwb3NpdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gaW5qZWN0RWRnZUxhYmVsUHJveGllcyhnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBpZiAoZWRnZS53aWR0aCAmJiBlZGdlLmhlaWdodCkgewogICAgICAgICAgdmFyIHYgPSBnLm5vZGUoZS52KTsKICAgICAgICAgIHZhciB3ID0gZy5ub2RlKGUudyk7CiAgICAgICAgICB2YXIgbGFiZWwgPSB7IHJhbms6ICh3LnJhbmsgLSB2LnJhbmspIC8gMiArIHYucmFuaywgZTogZSB9OwogICAgICAgICAgdXRpbCQyLmFkZER1bW15Tm9kZShnLCAiZWRnZS1wcm94eSIsIGxhYmVsLCAiX2VwIik7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBhc3NpZ25SYW5rTWluTWF4KGcpIHsKICAgICAgdmFyIG1heFJhbmsgPSAwOwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIG5vZGUgPSBnLm5vZGUodik7CiAgICAgICAgaWYgKG5vZGUuYm9yZGVyVG9wKSB7CiAgICAgICAgICBub2RlLm1pblJhbmsgPSBnLm5vZGUobm9kZS5ib3JkZXJUb3ApLnJhbms7CiAgICAgICAgICBub2RlLm1heFJhbmsgPSBnLm5vZGUobm9kZS5ib3JkZXJCb3R0b20pLnJhbms7CiAgICAgICAgICBtYXhSYW5rID0gbG9kYXNoXzEkMS5tYXgobWF4UmFuaywgbm9kZS5tYXhSYW5rKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgICBnLmdyYXBoKCkubWF4UmFuayA9IG1heFJhbms7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlRWRnZUxhYmVsUHJveGllcyhnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICB2YXIgbm9kZSA9IGcubm9kZSh2KTsKICAgICAgICBpZiAobm9kZS5kdW1teSA9PT0gImVkZ2UtcHJveHkiKSB7CiAgICAgICAgICBnLmVkZ2Uobm9kZS5lKS5sYWJlbFJhbmsgPSBub2RlLnJhbms7CiAgICAgICAgICBnLnJlbW92ZU5vZGUodik7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVHcmFwaChnKSB7CiAgICAgIHZhciBtaW5YID0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZOwogICAgICB2YXIgbWF4WCA9IDA7CiAgICAgIHZhciBtaW5ZID0gTnVtYmVyLlBPU0lUSVZFX0lORklOSVRZOwogICAgICB2YXIgbWF4WSA9IDA7CiAgICAgIHZhciBncmFwaExhYmVsID0gZy5ncmFwaCgpOwogICAgICB2YXIgbWFyZ2luWCA9IGdyYXBoTGFiZWwubWFyZ2lueCB8fCAwOwogICAgICB2YXIgbWFyZ2luWSA9IGdyYXBoTGFiZWwubWFyZ2lueSB8fCAwOwoKICAgICAgZnVuY3Rpb24gZ2V0RXh0cmVtZXMoYXR0cnMpIHsKICAgICAgICB2YXIgeCA9IGF0dHJzLng7CiAgICAgICAgdmFyIHkgPSBhdHRycy55OwogICAgICAgIHZhciB3ID0gYXR0cnMud2lkdGg7CiAgICAgICAgdmFyIGggPSBhdHRycy5oZWlnaHQ7CiAgICAgICAgbWluWCA9IE1hdGgubWluKG1pblgsIHggLSB3IC8gMik7CiAgICAgICAgbWF4WCA9IE1hdGgubWF4KG1heFgsIHggKyB3IC8gMik7CiAgICAgICAgbWluWSA9IE1hdGgubWluKG1pblksIHkgLSBoIC8gMik7CiAgICAgICAgbWF4WSA9IE1hdGgubWF4KG1heFksIHkgKyBoIC8gMik7CiAgICAgIH0KCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsgZ2V0RXh0cmVtZXMoZy5ub2RlKHYpKTsgfSk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMoZWRnZSwgIngiKSkgewogICAgICAgICAgZ2V0RXh0cmVtZXMoZWRnZSk7CiAgICAgICAgfQogICAgICB9KTsKCiAgICAgIG1pblggLT0gbWFyZ2luWDsKICAgICAgbWluWSAtPSBtYXJnaW5ZOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIHZhciBub2RlID0gZy5ub2RlKHYpOwogICAgICAgIG5vZGUueCAtPSBtaW5YOwogICAgICAgIG5vZGUueSAtPSBtaW5ZOwogICAgICB9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZWRnZS5wb2ludHMsIGZ1bmN0aW9uKHApIHsKICAgICAgICAgIHAueCAtPSBtaW5YOwogICAgICAgICAgcC55IC09IG1pblk7CiAgICAgICAgfSk7CiAgICAgICAgaWYgKGxvZGFzaF8xJDEuaGFzKGVkZ2UsICJ4IikpIHsgZWRnZS54IC09IG1pblg7IH0KICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMoZWRnZSwgInkiKSkgeyBlZGdlLnkgLT0gbWluWTsgfQogICAgICB9KTsKCiAgICAgIGdyYXBoTGFiZWwud2lkdGggPSBtYXhYIC0gbWluWCArIG1hcmdpblg7CiAgICAgIGdyYXBoTGFiZWwuaGVpZ2h0ID0gbWF4WSAtIG1pblkgKyBtYXJnaW5ZOwogICAgfQoKICAgIGZ1bmN0aW9uIGFzc2lnbk5vZGVJbnRlcnNlY3RzKGcpIHsKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcuZWRnZXMoKSwgZnVuY3Rpb24oZSkgewogICAgICAgIHZhciBlZGdlID0gZy5lZGdlKGUpOwogICAgICAgIHZhciBub2RlViA9IGcubm9kZShlLnYpOwogICAgICAgIHZhciBub2RlVyA9IGcubm9kZShlLncpOwogICAgICAgIHZhciBwMSwgcDI7CiAgICAgICAgaWYgKCFlZGdlLnBvaW50cykgewogICAgICAgICAgZWRnZS5wb2ludHMgPSBbXTsKICAgICAgICAgIHAxID0gbm9kZVc7CiAgICAgICAgICBwMiA9IG5vZGVWOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBwMSA9IGVkZ2UucG9pbnRzWzBdOwogICAgICAgICAgcDIgPSBlZGdlLnBvaW50c1tlZGdlLnBvaW50cy5sZW5ndGggLSAxXTsKICAgICAgICB9CiAgICAgICAgZWRnZS5wb2ludHMudW5zaGlmdCh1dGlsJDIuaW50ZXJzZWN0UmVjdChub2RlViwgcDEpKTsKICAgICAgICBlZGdlLnBvaW50cy5wdXNoKHV0aWwkMi5pbnRlcnNlY3RSZWN0KG5vZGVXLCBwMikpOwogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBmaXh1cEVkZ2VMYWJlbENvb3JkcyhnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBpZiAobG9kYXNoXzEkMS5oYXMoZWRnZSwgIngiKSkgewogICAgICAgICAgaWYgKGVkZ2UubGFiZWxwb3MgPT09ICJsIiB8fCBlZGdlLmxhYmVscG9zID09PSAiciIpIHsKICAgICAgICAgICAgZWRnZS53aWR0aCAtPSBlZGdlLmxhYmVsb2Zmc2V0OwogICAgICAgICAgfQogICAgICAgICAgc3dpdGNoIChlZGdlLmxhYmVscG9zKSB7CiAgICAgICAgICBjYXNlICJsIjogZWRnZS54IC09IGVkZ2Uud2lkdGggLyAyICsgZWRnZS5sYWJlbG9mZnNldDsgYnJlYWs7CiAgICAgICAgICBjYXNlICJyIjogZWRnZS54ICs9IGVkZ2Uud2lkdGggLyAyICsgZWRnZS5sYWJlbG9mZnNldDsgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZXZlcnNlUG9pbnRzRm9yUmV2ZXJzZWRFZGdlcyhnKSB7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICB2YXIgZWRnZSA9IGcuZWRnZShlKTsKICAgICAgICBpZiAoZWRnZS5yZXZlcnNlZCkgewogICAgICAgICAgZWRnZS5wb2ludHMucmV2ZXJzZSgpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcmVtb3ZlQm9yZGVyTm9kZXMoZykgewogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgaWYgKGcuY2hpbGRyZW4odikubGVuZ3RoKSB7CiAgICAgICAgICB2YXIgbm9kZSA9IGcubm9kZSh2KTsKICAgICAgICAgIHZhciB0ID0gZy5ub2RlKG5vZGUuYm9yZGVyVG9wKTsKICAgICAgICAgIHZhciBiID0gZy5ub2RlKG5vZGUuYm9yZGVyQm90dG9tKTsKICAgICAgICAgIHZhciBsID0gZy5ub2RlKGxvZGFzaF8xJDEubGFzdChub2RlLmJvcmRlckxlZnQpKTsKICAgICAgICAgIHZhciByID0gZy5ub2RlKGxvZGFzaF8xJDEubGFzdChub2RlLmJvcmRlclJpZ2h0KSk7CgogICAgICAgICAgbm9kZS53aWR0aCA9IE1hdGguYWJzKHIueCAtIGwueCk7CiAgICAgICAgICBub2RlLmhlaWdodCA9IE1hdGguYWJzKGIueSAtIHQueSk7CiAgICAgICAgICBub2RlLnggPSBsLnggKyBub2RlLndpZHRoIC8gMjsKICAgICAgICAgIG5vZGUueSA9IHQueSArIG5vZGUuaGVpZ2h0IC8gMjsKICAgICAgICB9CiAgICAgIH0pOwoKICAgICAgbG9kYXNoXzEkMS5mb3JFYWNoKGcubm9kZXMoKSwgZnVuY3Rpb24odikgewogICAgICAgIGlmIChnLm5vZGUodikuZHVtbXkgPT09ICJib3JkZXIiKSB7CiAgICAgICAgICBnLnJlbW92ZU5vZGUodik7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiByZW1vdmVTZWxmRWRnZXMoZykgewogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5lZGdlcygpLCBmdW5jdGlvbihlKSB7CiAgICAgICAgaWYgKGUudiA9PT0gZS53KSB7CiAgICAgICAgICB2YXIgbm9kZSA9IGcubm9kZShlLnYpOwogICAgICAgICAgaWYgKCFub2RlLnNlbGZFZGdlcykgewogICAgICAgICAgICBub2RlLnNlbGZFZGdlcyA9IFtdOwogICAgICAgICAgfQogICAgICAgICAgbm9kZS5zZWxmRWRnZXMucHVzaCh7IGU6IGUsIGxhYmVsOiBnLmVkZ2UoZSkgfSk7CiAgICAgICAgICBnLnJlbW92ZUVkZ2UoZSk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBpbnNlcnRTZWxmRWRnZXMoZykgewogICAgICB2YXIgbGF5ZXJzID0gdXRpbCQyLmJ1aWxkTGF5ZXJNYXRyaXgoZyk7CiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllcnMsIGZ1bmN0aW9uKGxheWVyKSB7CiAgICAgICAgdmFyIG9yZGVyU2hpZnQgPSAwOwogICAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllciwgZnVuY3Rpb24odiwgaSkgewogICAgICAgICAgdmFyIG5vZGUgPSBnLm5vZGUodik7CiAgICAgICAgICBub2RlLm9yZGVyID0gaSArIG9yZGVyU2hpZnQ7CiAgICAgICAgICBsb2Rhc2hfMSQxLmZvckVhY2gobm9kZS5zZWxmRWRnZXMsIGZ1bmN0aW9uKHNlbGZFZGdlKSB7CiAgICAgICAgICAgIHV0aWwkMi5hZGREdW1teU5vZGUoZywgInNlbGZlZGdlIiwgewogICAgICAgICAgICAgIHdpZHRoOiBzZWxmRWRnZS5sYWJlbC53aWR0aCwKICAgICAgICAgICAgICBoZWlnaHQ6IHNlbGZFZGdlLmxhYmVsLmhlaWdodCwKICAgICAgICAgICAgICByYW5rOiBub2RlLnJhbmssCiAgICAgICAgICAgICAgb3JkZXI6IGkgKyAoKytvcmRlclNoaWZ0KSwKICAgICAgICAgICAgICBlOiBzZWxmRWRnZS5lLAogICAgICAgICAgICAgIGxhYmVsOiBzZWxmRWRnZS5sYWJlbAogICAgICAgICAgICB9LCAiX3NlIik7CiAgICAgICAgICB9KTsKICAgICAgICAgIGRlbGV0ZSBub2RlLnNlbGZFZGdlczsKICAgICAgICB9KTsKICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcG9zaXRpb25TZWxmRWRnZXMoZykgewogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goZy5ub2RlcygpLCBmdW5jdGlvbih2KSB7CiAgICAgICAgdmFyIG5vZGUgPSBnLm5vZGUodik7CiAgICAgICAgaWYgKG5vZGUuZHVtbXkgPT09ICJzZWxmZWRnZSIpIHsKICAgICAgICAgIHZhciBzZWxmTm9kZSA9IGcubm9kZShub2RlLmUudik7CiAgICAgICAgICB2YXIgeCA9IHNlbGZOb2RlLnggKyBzZWxmTm9kZS53aWR0aCAvIDI7CiAgICAgICAgICB2YXIgeSA9IHNlbGZOb2RlLnk7CiAgICAgICAgICB2YXIgZHggPSBub2RlLnggLSB4OwogICAgICAgICAgdmFyIGR5ID0gc2VsZk5vZGUuaGVpZ2h0IC8gMjsKICAgICAgICAgIGcuc2V0RWRnZShub2RlLmUsIG5vZGUubGFiZWwpOwogICAgICAgICAgZy5yZW1vdmVOb2RlKHYpOwogICAgICAgICAgbm9kZS5sYWJlbC5wb2ludHMgPSBbCiAgICAgICAgICAgIHsgeDogeCArIDIgKiBkeCAvIDMsIHk6IHkgLSBkeSB9LAogICAgICAgICAgICB7IHg6IHggKyA1ICogZHggLyA2LCB5OiB5IC0gZHkgfSwKICAgICAgICAgICAgeyB4OiB4ICsgICAgIGR4ICAgICwgeTogeSB9LAogICAgICAgICAgICB7IHg6IHggKyA1ICogZHggLyA2LCB5OiB5ICsgZHkgfSwKICAgICAgICAgICAgeyB4OiB4ICsgMiAqIGR4IC8gMywgeTogeSArIGR5IH0KICAgICAgICAgIF07CiAgICAgICAgICBub2RlLmxhYmVsLnggPSBub2RlLng7CiAgICAgICAgICBub2RlLmxhYmVsLnkgPSBub2RlLnk7CiAgICAgICAgfQogICAgICB9KTsKICAgIH0KCiAgICBmdW5jdGlvbiBzZWxlY3ROdW1iZXJBdHRycyhvYmosIGF0dHJzKSB7CiAgICAgIHJldHVybiBsb2Rhc2hfMSQxLm1hcFZhbHVlcyhsb2Rhc2hfMSQxLnBpY2sob2JqLCBhdHRycyksIE51bWJlcik7CiAgICB9CgogICAgZnVuY3Rpb24gY2Fub25pY2FsaXplKGF0dHJzKSB7CiAgICAgIHZhciBuZXdBdHRycyA9IHt9OwogICAgICBsb2Rhc2hfMSQxLmZvckVhY2goYXR0cnMsIGZ1bmN0aW9uKHYsIGspIHsKICAgICAgICBuZXdBdHRyc1trLnRvTG93ZXJDYXNlKCldID0gdjsKICAgICAgfSk7CiAgICAgIHJldHVybiBuZXdBdHRyczsKICAgIH0KCiAgICB2YXIgR3JhcGgkOCA9IGdyYXBobGliXzEuR3JhcGg7CgogICAgdmFyIGRlYnVnID0gewogICAgICBkZWJ1Z09yZGVyaW5nOiBkZWJ1Z09yZGVyaW5nCiAgICB9OwoKICAgIC8qIGlzdGFuYnVsIGlnbm9yZSBuZXh0ICovCiAgICBmdW5jdGlvbiBkZWJ1Z09yZGVyaW5nKGcpIHsKICAgICAgdmFyIGxheWVyTWF0cml4ID0gdXRpbC5idWlsZExheWVyTWF0cml4KGcpOwoKICAgICAgdmFyIGggPSBuZXcgR3JhcGgkOCh7IGNvbXBvdW5kOiB0cnVlLCBtdWx0aWdyYXBoOiB0cnVlIH0pLnNldEdyYXBoKHt9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLm5vZGVzKCksIGZ1bmN0aW9uKHYpIHsKICAgICAgICBoLnNldE5vZGUodiwgeyBsYWJlbDogdiB9KTsKICAgICAgICBoLnNldFBhcmVudCh2LCAibGF5ZXIiICsgZy5ub2RlKHYpLnJhbmspOwogICAgICB9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChnLmVkZ2VzKCksIGZ1bmN0aW9uKGUpIHsKICAgICAgICBoLnNldEVkZ2UoZS52LCBlLncsIHt9LCBlLm5hbWUpOwogICAgICB9KTsKCiAgICAgIGxvZGFzaF8xJDEuZm9yRWFjaChsYXllck1hdHJpeCwgZnVuY3Rpb24obGF5ZXIsIGkpIHsKICAgICAgICB2YXIgbGF5ZXJWID0gImxheWVyIiArIGk7CiAgICAgICAgaC5zZXROb2RlKGxheWVyViwgeyByYW5rOiAic2FtZSIgfSk7CiAgICAgICAgbG9kYXNoXzEkMS5yZWR1Y2UobGF5ZXIsIGZ1bmN0aW9uKHUsIHYpIHsKICAgICAgICAgIGguc2V0RWRnZSh1LCB2LCB7IHN0eWxlOiAiaW52aXMiIH0pOwogICAgICAgICAgcmV0dXJuIHY7CiAgICAgICAgfSk7CiAgICAgIH0pOwoKICAgICAgcmV0dXJuIGg7CiAgICB9CgogICAgdmFyIHZlcnNpb24kNSA9ICIwLjguNSI7CgogICAgLyoKICAgIENvcHlyaWdodCAoYykgMjAxMi0yMDE0IENocmlzIFBldHRpdHQKCiAgICBQZXJtaXNzaW9uIGlzIGhlcmVieSBncmFudGVkLCBmcmVlIG9mIGNoYXJnZSwgdG8gYW55IHBlcnNvbiBvYnRhaW5pbmcgYSBjb3B5CiAgICBvZiB0aGlzIHNvZnR3YXJlIGFuZCBhc3NvY2lhdGVkIGRvY3VtZW50YXRpb24gZmlsZXMgKHRoZSAiU29mdHdhcmUiKSwgdG8gZGVhbAogICAgaW4gdGhlIFNvZnR3YXJlIHdpdGhvdXQgcmVzdHJpY3Rpb24sIGluY2x1ZGluZyB3aXRob3V0IGxpbWl0YXRpb24gdGhlIHJpZ2h0cwogICAgdG8gdXNlLCBjb3B5LCBtb2RpZnksIG1lcmdlLCBwdWJsaXNoLCBkaXN0cmlidXRlLCBzdWJsaWNlbnNlLCBhbmQvb3Igc2VsbAogICAgY29waWVzIG9mIHRoZSBTb2Z0d2FyZSwgYW5kIHRvIHBlcm1pdCBwZXJzb25zIHRvIHdob20gdGhlIFNvZnR3YXJlIGlzCiAgICBmdXJuaXNoZWQgdG8gZG8gc28sIHN1YmplY3QgdG8gdGhlIGZvbGxvd2luZyBjb25kaXRpb25zOgoKICAgIFRoZSBhYm92ZSBjb3B5cmlnaHQgbm90aWNlIGFuZCB0aGlzIHBlcm1pc3Npb24gbm90aWNlIHNoYWxsIGJlIGluY2x1ZGVkIGluCiAgICBhbGwgY29waWVzIG9yIHN1YnN0YW50aWFsIHBvcnRpb25zIG9mIHRoZSBTb2Z0d2FyZS4KCiAgICBUSEUgU09GVFdBUkUgSVMgUFJPVklERUQgIkFTIElTIiwgV0lUSE9VVCBXQVJSQU5UWSBPRiBBTlkgS0lORCwgRVhQUkVTUyBPUgogICAgSU1QTElFRCwgSU5DTFVESU5HIEJVVCBOT1QgTElNSVRFRCBUTyBUSEUgV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFksCiAgICBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBTkQgTk9OSU5GUklOR0VNRU5ULiBJTiBOTyBFVkVOVCBTSEFMTCBUSEUKICAgIEFVVEhPUlMgT1IgQ09QWVJJR0hUIEhPTERFUlMgQkUgTElBQkxFIEZPUiBBTlkgQ0xBSU0sIERBTUFHRVMgT1IgT1RIRVIKICAgIExJQUJJTElUWSwgV0hFVEhFUiBJTiBBTiBBQ1RJT04gT0YgQ09OVFJBQ1QsIFRPUlQgT1IgT1RIRVJXSVNFLCBBUklTSU5HIEZST00sCiAgICBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUgVVNFIE9SIE9USEVSIERFQUxJTkdTIElOCiAgICBUSEUgU09GVFdBUkUuCiAgICAqLwoKICAgIHZhciBkYWdyZSA9IHsKICAgICAgZ3JhcGhsaWI6IGdyYXBobGliXzEsCgogICAgICBsYXlvdXQ6IGxheW91dF8xLAogICAgICBkZWJ1ZzogZGVidWcsCiAgICAgIHV0aWw6IHsKICAgICAgICB0aW1lOiB1dGlsLnRpbWUsCiAgICAgICAgbm90aW1lOiB1dGlsLm5vdGltZQogICAgICB9LAogICAgICB2ZXJzaW9uOiB2ZXJzaW9uJDUKICAgIH07CgogICAgLyogQ29weXJpZ2h0IDIwMTUgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgJ0xpY2Vuc2UnKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAnQVMgSVMnIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjb25zdCBBU1lOQ19UQVNLX0RFTEFZID0gMjA7CiAgICAvKioKICAgICAqIE1lYXN1cmUgYW5kIGxvZyBhIHN5bmNocm9ub3VzIHRhc2suCiAgICAgKi8KICAgIGZ1bmN0aW9uIHRpbWUkMyhtc2csIHRhc2spIHsKICAgICAgICBsZXQgc3RhcnQgPSBEYXRlLm5vdygpOwogICAgICAgIGxldCByZXN1bHQgPSB0YXNrKCk7CiAgICAgICAgLyogdHNsaW50OmRpc2FibGUgKi8KICAgICAgICBjb25zb2xlLmxvZyhtc2csICc6JywgRGF0ZS5ub3coKSAtIHN0YXJ0LCAnbXMnKTsKICAgICAgICAvKiB0c2xpbnQ6ZW5hYmxlICovCiAgICAgICAgcmV0dXJuIHJlc3VsdDsKICAgIH0KICAgIC8qKgogICAgICogQ3JlYXRlcyBhIHRyYWNrZXIgdGhhdCBzZXRzIHRoZSBwcm9ncmVzcyBwcm9wZXJ0eSBvZiB0aGUKICAgICAqIHByb3ZpZGVkIHBvbHltZXIgY29tcG9uZW50LiBUaGUgcHJvdmlkZWQgY29tcG9uZW50IG11c3QgaGF2ZQogICAgICogYSBwcm9wZXJ0eSBjYWxsZWQgJ3Byb2dyZXNzJyB0aGF0IGlzIG5vdCByZWFkLW9ubHkuIFRoZSBwcm9ncmVzcwogICAgICogcHJvcGVydHkgaXMgYW4gb2JqZWN0IHdpdGggYSBudW1lcmljYWwgJ3ZhbHVlJyBwcm9wZXJ0eSBhbmQgYQogICAgICogc3RyaW5nICdtc2cnIHByb3BlcnR5LgogICAgICovCiAgICBmdW5jdGlvbiBnZXRUcmFja2VyKHBvbHltZXJDb21wb25lbnQpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgICBzZXRNZXNzYWdlOiBmdW5jdGlvbiAobXNnKSB7CiAgICAgICAgICAgICAgICBwb2x5bWVyQ29tcG9uZW50LnNldCgncHJvZ3Jlc3MnLCB7CiAgICAgICAgICAgICAgICAgICAgdmFsdWU6IHBvbHltZXJDb21wb25lbnQucHJvZ3Jlc3MudmFsdWUsCiAgICAgICAgICAgICAgICAgICAgbXNnOiBtc2csCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSwKICAgICAgICAgICAgdXBkYXRlUHJvZ3Jlc3M6IGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICAgICAgcG9seW1lckNvbXBvbmVudC5zZXQoJ3Byb2dyZXNzJywgewogICAgICAgICAgICAgICAgICAgIHZhbHVlOiBwb2x5bWVyQ29tcG9uZW50LnByb2dyZXNzLnZhbHVlICsgdmFsdWUsCiAgICAgICAgICAgICAgICAgICAgbXNnOiBwb2x5bWVyQ29tcG9uZW50LnByb2dyZXNzLm1zZywKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9LAogICAgICAgICAgICByZXBvcnRFcnJvcjogZnVuY3Rpb24gKG1zZywgZXJyKSB7CiAgICAgICAgICAgICAgICAvLyBMb2cgdGhlIHN0YWNrIHRyYWNlIGluIHRoZSBjb25zb2xlLgogICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcihlcnIuc3RhY2spOwogICAgICAgICAgICAgICAgLy8gQW5kIHNlbmQgYSB1c2VyLWZyaWVuZGx5IG1lc3NhZ2UgdG8gdGhlIFVJLgogICAgICAgICAgICAgICAgcG9seW1lckNvbXBvbmVudC5zZXQoJ3Byb2dyZXNzJywgewogICAgICAgICAgICAgICAgICAgIHZhbHVlOiBwb2x5bWVyQ29tcG9uZW50LnByb2dyZXNzLnZhbHVlLAogICAgICAgICAgICAgICAgICAgIG1zZzogbXNnLAogICAgICAgICAgICAgICAgICAgIGVycm9yOiB0cnVlLAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0sCiAgICAgICAgfTsKICAgIH0KICAgIC8qKgogICAgICogQ3JlYXRlcyBhIHRyYWNrZXIgZm9yIGEgc3VidGFzayBnaXZlbiB0aGUgcGFyZW50IHRyYWNrZXIsIHRoZSB0b3RhbAogICAgICogcHJvZ3Jlc3MKICAgICAqIG9mIHRoZSBzdWJ0YXNrIGFuZCB0aGUgc3VidGFzayBtZXNzYWdlLiBUaGUgcGFyZW50IHRhc2sgc2hvdWxkIHBhc3MgYQogICAgICogc3VidHJhY2tlciB0byBpdHMgc3VidGFza3MuIFRoZSBzdWJ0YXNrIHJlcG9ydHMgaXRzIG93biBwcm9ncmVzcyB3aGljaAogICAgICogYmVjb21lcyByZWxhdGl2ZSB0byB0aGUgbWFpbiB0YXNrLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRTdWJ0YXNrVHJhY2tlcihwYXJlbnRUcmFja2VyLCBpbXBhY3RPblRvdGFsUHJvZ3Jlc3MsIHN1YnRhc2tNc2cpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgICBzZXRNZXNzYWdlOiBmdW5jdGlvbiAocHJvZ3Jlc3NNc2cpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSBwYXJlbnQgc2hvdWxkIHNob3cgYSBjb25jYXRlbmF0aW9uIG9mIGl0cyBtZXNzYWdlIGFsb25nIHdpdGgKICAgICAgICAgICAgICAgIC8vIGl0cyBzdWJ0YXNrIHRyYWNrZXIgbWVzc2FnZS4KICAgICAgICAgICAgICAgIHBhcmVudFRyYWNrZXIuc2V0TWVzc2FnZShzdWJ0YXNrTXNnICsgJzogJyArIHByb2dyZXNzTXNnKTsKICAgICAgICAgICAgfSwKICAgICAgICAgICAgdXBkYXRlUHJvZ3Jlc3M6IGZ1bmN0aW9uIChpbmNyZW1lbnRWYWx1ZSkgewogICAgICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSBwYXJlbnQgcHJvZ3Jlc3MgcmVsYXRpdmUgdG8gdGhlIGNoaWxkIHByb2dyZXNzLgogICAgICAgICAgICAgICAgLy8gRm9yIGV4YW1wbGUsIGlmIHRoZSBzdWItdGFzayBwcm9ncmVzc2VzIGJ5IDMwJSwgYW5kIHRoZSBpbXBhY3Qgb24gdGhlCiAgICAgICAgICAgICAgICAvLyB0b3RhbCBwcm9ncmVzcyBpcyA1MCUsIHRoZW4gdGhlIHRhc2sgcHJvZ3Jlc3NlcyBieSAzMCUgKiA1MCUgPSAxNSUuCiAgICAgICAgICAgICAgICBwYXJlbnRUcmFja2VyLnVwZGF0ZVByb2dyZXNzKChpbmNyZW1lbnRWYWx1ZSAqIGltcGFjdE9uVG90YWxQcm9ncmVzcykgLyAxMDApOwogICAgICAgICAgICB9LAogICAgICAgICAgICByZXBvcnRFcnJvcjogZnVuY3Rpb24gKG1zZywgZXJyKSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgcGFyZW50IHNob3VsZCBzaG93IGEgY29uY2F0ZW5hdGlvbiBvZiBpdHMgbWVzc2FnZSBhbG9uZyB3aXRoCiAgICAgICAgICAgICAgICAvLyBpdHMgc3VidGFzayBlcnJvciBtZXNzYWdlLgogICAgICAgICAgICAgICAgcGFyZW50VHJhY2tlci5yZXBvcnRFcnJvcihzdWJ0YXNrTXNnICsgJzogJyArIG1zZywgZXJyKTsKICAgICAgICAgICAgfSwKICAgICAgICB9OwogICAgfQogICAgLyoqCiAgICAgKiBSdW5zIGEgc3luY2hyb25vdXMgZXhwZW5zaXZlIHRhc2sgYW5kIHJldHVybiB0aGUgcmVzdWx0LgogICAgICogUGxlYXNlIHVzZSBydW5Bc3luY1Byb21pc2VUYXNrIGluIGNhc2UgYSB0YXNrIHJldHVybnMgYSBQcm9taXNlLgogICAgICovCiAgICBmdW5jdGlvbiBydW5UYXNrKG1zZywgaW5jUHJvZ3Jlc3NWYWx1ZSwgdGFzaywgdHJhY2tlcikgewogICAgICAgIC8vIFVwZGF0ZSB0aGUgcHJvZ3Jlc3MgbWVzc2FnZSB0byBzYXkgdGhlIGN1cnJlbnQgcnVubmluZyB0YXNrLgogICAgICAgIHRyYWNrZXIuc2V0TWVzc2FnZShtc2cpOwogICAgICAgIC8vIFJ1biB0aGUgZXhwZW5zaXZlIHRhc2sgd2l0aCBhIGRlbGF5IHRoYXQgZ2l2ZXMgZW5vdWdoIHRpbWUgZm9yIHRoZQogICAgICAgIC8vIFVJIHRvIHVwZGF0ZS4KICAgICAgICB0cnkgewogICAgICAgICAgICBsZXQgcmVzdWx0ID0gdGltZSQzKG1zZywgdGFzayk7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgcHJvZ3Jlc3MgdmFsdWUuCiAgICAgICAgICAgIHRyYWNrZXIudXBkYXRlUHJvZ3Jlc3MoaW5jUHJvZ3Jlc3NWYWx1ZSk7CiAgICAgICAgICAgIC8vIFJldHVybiB0aGUgcmVzdWx0IHRvIGJlIHVzZWQgYnkgb3RoZXIgdGFza3MuCiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQogICAgICAgIGNhdGNoIChlKSB7CiAgICAgICAgICAgIC8vIEVycm9ycyB0aGF0IGhhcHBlbiBpbnNpZGUgYXN5bmNocm9ub3VzIHRhc2tzIGFyZQogICAgICAgICAgICAvLyByZXBvcnRlZCB0byB0aGUgdHJhY2tlciB1c2luZyBhIHVzZXItZnJpZW5kbHkgbWVzc2FnZS4KICAgICAgICAgICAgdHJhY2tlci5yZXBvcnRFcnJvcignRmFpbGVkICcgKyBtc2csIGUpOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogUnVucyBhbiBleHBlbnNpdmUgdGFzayBhc3luY2hyb25vdXNseSBhbmQgcmV0dXJucyBhIHByb21pc2Ugb2YgdGhlIHJlc3VsdC4KICAgICAqLwogICAgZnVuY3Rpb24gcnVuQXN5bmNUYXNrKG1zZywgaW5jUHJvZ3Jlc3NWYWx1ZSwgdGFzaywgdHJhY2tlcikgewogICAgICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgcHJvZ3Jlc3MgbWVzc2FnZSB0byBzYXkgdGhlIGN1cnJlbnQgcnVubmluZyB0YXNrLgogICAgICAgICAgICB0cmFja2VyLnNldE1lc3NhZ2UobXNnKTsKICAgICAgICAgICAgLy8gUnVuIHRoZSBleHBlbnNpdmUgdGFzayB3aXRoIGEgZGVsYXkgdGhhdCBnaXZlcyBlbm91Z2ggdGltZSBmb3IgdGhlCiAgICAgICAgICAgIC8vIFVJIHRvIHVwZGF0ZS4KICAgICAgICAgICAgc2V0VGltZW91dChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgICAgIGxldCByZXN1bHQgPSB0aW1lJDMobXNnLCB0YXNrKTsKICAgICAgICAgICAgICAgICAgICAvLyBVcGRhdGUgdGhlIHByb2dyZXNzIHZhbHVlLgogICAgICAgICAgICAgICAgICAgIHRyYWNrZXIudXBkYXRlUHJvZ3Jlc3MoaW5jUHJvZ3Jlc3NWYWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgLy8gUmV0dXJuIHRoZSByZXN1bHQgdG8gYmUgdXNlZCBieSBvdGhlciB0YXNrcy4KICAgICAgICAgICAgICAgICAgICByZXNvbHZlKHJlc3VsdCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXRjaCAoZSkgewogICAgICAgICAgICAgICAgICAgIC8vIEVycm9ycyB0aGF0IGhhcHBlbiBpbnNpZGUgYXN5bmNocm9ub3VzIHRhc2tzIGFyZQogICAgICAgICAgICAgICAgICAgIC8vIHJlcG9ydGVkIHRvIHRoZSB0cmFja2VyIHVzaW5nIGEgdXNlci1mcmllbmRseSBtZXNzYWdlLgogICAgICAgICAgICAgICAgICAgIHRyYWNrZXIucmVwb3J0RXJyb3IoJ0ZhaWxlZCAnICsgbXNnLCBlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwgQVNZTkNfVEFTS19ERUxBWSk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIEFzeW5jaHJvbm91c2x5IHJ1bnMgYW4gZXhwZW5zaXZlIHRhc2sgdGhhdCByZXR1cm5zIGEgcHJvbWlzZS4gVXBkYXRlcyB0aGUKICAgICAqIHRyYWNrZXIncyBwcm9ncmVzcyBhZnRlciB0aGUgcHJvbWlzZSByZXNvbHZlcy4gUmV0dXJucyBhIG5ldyBwcm9taXNlIHRoYXQKICAgICAqIHJlc29sdmVzIGFmdGVyIHRoZSBwcm9ncmVzcyBpcyB1cGRhdGVkLgogICAgICovCiAgICBmdW5jdGlvbiBydW5Bc3luY1Byb21pc2VUYXNrKG1zZywgaW5jUHJvZ3Jlc3NWYWx1ZSwgdGFzaywgdHJhY2tlcikgewogICAgICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7CiAgICAgICAgICAgIGxldCBoYW5kbGVFcnJvciA9IGZ1bmN0aW9uIChlKSB7CiAgICAgICAgICAgICAgICAvLyBFcnJvcnMgdGhhdCBoYXBwZW4gaW5zaWRlIGFzeW5jaHJvbm91cyB0YXNrcyBhcmUKICAgICAgICAgICAgICAgIC8vIHJlcG9ydGVkIHRvIHRoZSB0cmFja2VyIHVzaW5nIGEgdXNlci1mcmllbmRseSBtZXNzYWdlLgogICAgICAgICAgICAgICAgdHJhY2tlci5yZXBvcnRFcnJvcignRmFpbGVkICcgKyBtc2csIGUpOwogICAgICAgICAgICAgICAgcmVqZWN0KGUpOwogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyBVcGRhdGUgdGhlIHByb2dyZXNzIG1lc3NhZ2UgdG8gc2F5IHRoZSBjdXJyZW50IHJ1bm5pbmcgdGFzay4KICAgICAgICAgICAgdHJhY2tlci5zZXRNZXNzYWdlKG1zZyk7CiAgICAgICAgICAgIC8vIFJ1biB0aGUgZXhwZW5zaXZlIHRhc2sgd2l0aCBhIGRlbGF5IHRoYXQgZ2l2ZXMgZW5vdWdoIHRpbWUgZm9yIHRoZQogICAgICAgICAgICAvLyBVSSB0byB1cGRhdGUuCiAgICAgICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgICAgICBsZXQgc3RhcnQgPSBEYXRlLm5vdygpOwogICAgICAgICAgICAgICAgICAgIHRhc2soKQogICAgICAgICAgICAgICAgICAgICAgICAudGhlbihmdW5jdGlvbiAodmFsdWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLyogdHNsaW50OmRpc2FibGUgKi8KICAgICAgICAgICAgICAgICAgICAgICAgY29uc29sZS5sb2cobXNnLCAnOicsIERhdGUubm93KCkgLSBzdGFydCwgJ21zJyk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgcHJvZ3Jlc3MgdmFsdWUuCiAgICAgICAgICAgICAgICAgICAgICAgIHRyYWNrZXIudXBkYXRlUHJvZ3Jlc3MoaW5jUHJvZ3Jlc3NWYWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFJldHVybiB0aGUgcmVzdWx0IHRvIGJlIHVzZWQgYnkgb3RoZXIgdGFza3MuCiAgICAgICAgICAgICAgICAgICAgICAgIHJlc29sdmUodmFsdWUpOwogICAgICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgICAgIC5jYXRjaChoYW5kbGVFcnJvcik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXRjaCAoZSkgewogICAgICAgICAgICAgICAgICAgIGhhbmRsZUVycm9yKGUpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LCBBU1lOQ19UQVNLX0RFTEFZKTsKICAgICAgICB9KTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhIHF1ZXJ5IHNlbGVjdG9yIHdpdGggZXNjYXBlZCBzcGVjaWFsIGNoYXJhY3RlcnMgdGhhdCBhcmUgbm90CiAgICAgKiBhbGxvd2VkIGluIGEgcXVlcnkgc2VsZWN0b3IuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGVzY2FwZVF1ZXJ5U2VsZWN0b3IocXVlcnlTZWxlY3RvcikgewogICAgICAgIHJldHVybiBxdWVyeVNlbGVjdG9yLnJlcGxhY2UoLyhbOi5cW1xdLC9cXFwoXCldKS9nLCAnXFwkMScpOwogICAgfQogICAgLy8gRm9yIHVuaXQgY29udmVyc2lvbi4KICAgIGNvbnN0IE1FTU9SWV9VTklUUyA9IFsKICAgICAgICAvLyBBdG9taWMgdW5pdC4KICAgICAgICB7IHN5bWJvbDogJ0InIH0sCiAgICAgICAgLy8gbnVtVW5pdHMgc3BlY2lmaWVzIGhvdyBtYW55IHByZXZpb3VzIHVuaXRzIHRoaXMgdW5pdCBjb250YWlucy4KICAgICAgICB7IHN5bWJvbDogJ0tCJywgbnVtVW5pdHM6IDEwMjQgfSwKICAgICAgICB7IHN5bWJvbDogJ01CJywgbnVtVW5pdHM6IDEwMjQgfSwKICAgICAgICB7IHN5bWJvbDogJ0dCJywgbnVtVW5pdHM6IDEwMjQgfSwKICAgICAgICB7IHN5bWJvbDogJ1RCJywgbnVtVW5pdHM6IDEwMjQgfSwKICAgICAgICB7IHN5bWJvbDogJ1BCJywgbnVtVW5pdHM6IDEwMjQgfSwKICAgIF07CiAgICBjb25zdCBUSU1FX1VOSVRTID0gWwogICAgICAgIC8vIEF0b21pYyB1bml0LiBGaW5lc3QgZ3JhbnVsYXJpdHkgaW4gVGVuc29yRmxvdyBzdGF0IGNvbGxlY3Rpb24uCiAgICAgICAgeyBzeW1ib2w6ICfCtXMnIH0sCiAgICAgICAgLy8gbnVtVW5pdHMgc3BlY2lmaWVzIGhvdyBtYW55IHByZXZpb3VzIHVuaXRzIHRoaXMgdW5pdCBjb250YWlucy4KICAgICAgICB7IHN5bWJvbDogJ21zJywgbnVtVW5pdHM6IDEwMDAgfSwKICAgICAgICB7IHN5bWJvbDogJ3MnLCBudW1Vbml0czogMTAwMCB9LAogICAgICAgIHsgc3ltYm9sOiAnbWluJywgbnVtVW5pdHM6IDYwIH0sCiAgICAgICAgeyBzeW1ib2w6ICdocicsIG51bVVuaXRzOiA2MCB9LAogICAgICAgIHsgc3ltYm9sOiAnZGF5cycsIG51bVVuaXRzOiAyNCB9LAogICAgXTsKICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgaHVtYW4gcmVhZGFibGUgdmVyc2lvbiBvZiB0aGUgdW5pdC4KICAgICAqIChlLmcuIDEuMzUgR0IsIDIzIE1CLCAzNCBtcywgNi41MyBtaW4gZXRjKS4KICAgICAqLwogICAgZnVuY3Rpb24gY29udmVydFVuaXRzVG9IdW1hblJlYWRhYmxlKHZhbHVlLCB1bml0cywgdW5pdEluZGV4ID0gMCkgewogICAgICAgIGlmICh1bml0SW5kZXggKyAxIDwgdW5pdHMubGVuZ3RoICYmIHZhbHVlID49IHVuaXRzW3VuaXRJbmRleCArIDFdLm51bVVuaXRzKSB7CiAgICAgICAgICAgIHJldHVybiBjb252ZXJ0VW5pdHNUb0h1bWFuUmVhZGFibGUodmFsdWUgLyB1bml0c1t1bml0SW5kZXggKyAxXS5udW1Vbml0cywgdW5pdHMsIHVuaXRJbmRleCArIDEpOwogICAgICAgIH0KICAgICAgICAvLyB0b1ByZWNpc2lvbigpIGhhcyB0aGUgdGVuZGVuY3kgdG8gcmV0dXJuIGEgbnVtYmVyIGluIHNjaWVudGlmaWMKICAgICAgICAvLyBub3RhdGlvbiBhbmQgY2FzdGluZyBiYWNrIHRvIGEgbnVtYmVyIGJyaW5ncyBpdCBiYWNrIHRvIG5vcm1hbCBub3RhdGlvbi4KICAgICAgICAvLyBlLmcuLAogICAgICAgIC8vICAgPiB2YWx1ZSA9IDIxMzsgdmFsdWUudG9QcmVjaXNpb24oMSkKICAgICAgICAvLyAgIDwgIjJlKzIiCiAgICAgICAgLy8gICA+IE51bWJlcih2YWx1ZS50b1ByZWNpc2lvbigxKSkKICAgICAgICAvLyAgIDwgMjAwCiAgICAgICAgcmV0dXJuIE51bWJlcih2YWx1ZS50b1ByZWNpc2lvbigzKSkgKyAnICcgKyB1bml0c1t1bml0SW5kZXhdLnN5bWJvbDsKICAgIH0KICAgIGZ1bmN0aW9uIGhhc0Rpc3BsYXlhYmxlTm9kZVN0YXRzKHN0YXRzKSB7CiAgICAgICAgaWYgKHN0YXRzICYmCiAgICAgICAgICAgIChzdGF0cy50b3RhbEJ5dGVzID4gMCB8fCBzdGF0cy5nZXRUb3RhbE1pY3JvcygpID4gMCB8fCBzdGF0cy5vdXRwdXRTaXplKSkgewogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQogICAgLyoqCiAgICAgKiBHaXZlbiBhIGxpc3Qgb2Ygc3RyaW5ncywgaXQgcmV0dXJucyBhIG5ldyBsaXN0IG9mIHN0cmluZ3Mgd2l0aCB0aGUgbG9uZ2VzdAogICAgICogY29tbW9uIHByZWZpeCByZW1vdmVkLiBJZiB0aGUgY29tbW9uIHByZWZpeCBpcyBvbmUgb2YgdGhlIHN0cmluZ3MgaW4gdGhlCiAgICAgKiBsaXN0LCBpdCByZXR1cm5zIHRoZSBvcmlnaW5hbCBzdHJpbmdzLgogICAgICovCiAgICBmdW5jdGlvbiByZW1vdmVDb21tb25QcmVmaXgoc3RyaW5ncykgewogICAgICAgIGlmIChzdHJpbmdzLmxlbmd0aCA8IDIpIHsKICAgICAgICAgICAgcmV0dXJuIHN0cmluZ3M7CiAgICAgICAgfQogICAgICAgIGxldCBpbmRleCA9IDA7CiAgICAgICAgbGV0IGxhcmdlc3RJbmRleCA9IDA7CiAgICAgICAgLy8gRmluZCB0aGUgc2hvcnRlc3QgbmFtZSBhY3Jvc3MgYWxsIHN0cmluZ3MuCiAgICAgICAgbGV0IG1pbkxlbmd0aCA9IGxvZGFzaC5taW4obG9kYXNoLm1hcChzdHJpbmdzLCAoc3RyKSA9PiBzdHIubGVuZ3RoKSk7CiAgICAgICAgd2hpbGUgKHRydWUpIHsKICAgICAgICAgICAgaW5kZXgrKzsKICAgICAgICAgICAgbGV0IHByZWZpeGVzID0gbG9kYXNoLm1hcChzdHJpbmdzLCAoc3RyKSA9PiBzdHIuc3Vic3RyaW5nKDAsIGluZGV4KSk7CiAgICAgICAgICAgIGxldCBhbGxUaGVTYW1lID0gcHJlZml4ZXMuZXZlcnkoKHByZWZpeCwgaSkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuIGkgPT09IDAgPyB0cnVlIDogcHJlZml4ID09PSBwcmVmaXhlc1tpIC0gMV07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBpZiAoYWxsVGhlU2FtZSkgewogICAgICAgICAgICAgICAgaWYgKGluZGV4ID49IG1pbkxlbmd0aCkgewogICAgICAgICAgICAgICAgICAgIC8vIFRoZXJlIGlzIGEgc3RyaW5nIHdob3NlIHdob2xlIG5hbWUgaXMgYSBwcmVmaXggdG8gb3RoZXIgc3RyaW5nLgogICAgICAgICAgICAgICAgICAgIC8vIEluIHRoaXMgY2FzZSwgd2UgcmV0dXJuIHRoZSBvcmlnaW5hbCBsaXN0IG9mIHN0cmluZy4KICAgICAgICAgICAgICAgICAgICByZXR1cm4gc3RyaW5nczsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGxhcmdlc3RJbmRleCA9IGluZGV4OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIGxvZGFzaC5tYXAoc3RyaW5ncywgKHN0cikgPT4gc3RyLnN1YnN0cmluZyhsYXJnZXN0SW5kZXgpKTsKICAgIH0KICAgIC8qKgogICAgICogR2l2ZW4gYSB0aW1lc3RhbXAgaW4gbWljcm9zZWNvbmRzLCByZXR1cm4gYSBodW1hbi1mcmllbmRseSBzdHJpbmcgZGVub3RpbmcKICAgICAqIGhvdyBsb25nIGFnbyB0aGUgdGltZXN0YW1wIHdhcy4KICAgICAqLwogICAgZnVuY3Rpb24gY29tcHV0ZUh1bWFuRnJpZW5kbHlUaW1lKHRpbWVJbk1pY3Jvc2Vjb25kcykgewogICAgICAgIHZhciB0aW1lRGlmZmVyZW5jZUluTXMgPSArbmV3IERhdGUoKSAtICtuZXcgRGF0ZSh0aW1lSW5NaWNyb3NlY29uZHMgLyAxMDAwKTsKICAgICAgICBpZiAodGltZURpZmZlcmVuY2VJbk1zIDwgMzAwMDApIHsKICAgICAgICAgICAgcmV0dXJuICdqdXN0IG5vdyc7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHRpbWVEaWZmZXJlbmNlSW5NcyA8IDYwMDAwKSB7CiAgICAgICAgICAgIHJldHVybiBNYXRoLmZsb29yKHRpbWVEaWZmZXJlbmNlSW5NcyAvIDEwMDApICsgJyBzZWNvbmRzIGFnbyc7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHRpbWVEaWZmZXJlbmNlSW5NcyA8IDEyMDAwMCkgewogICAgICAgICAgICByZXR1cm4gJ2EgbWludXRlIGFnbyc7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHRpbWVEaWZmZXJlbmNlSW5NcyA8IDM2MDAwMDApIHsKICAgICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IodGltZURpZmZlcmVuY2VJbk1zIC8gNjAwMDApICsgJyBtaW51dGVzIGFnbyc7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKE1hdGguZmxvb3IodGltZURpZmZlcmVuY2VJbk1zIC8gMzYwMDAwMCkgPT0gMSkgewogICAgICAgICAgICByZXR1cm4gJ2FuIGhvdXIgYWdvJzsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAodGltZURpZmZlcmVuY2VJbk1zIDwgODY0MDAwMDApIHsKICAgICAgICAgICAgcmV0dXJuIE1hdGguZmxvb3IodGltZURpZmZlcmVuY2VJbk1zIC8gMzYwMDAwMCkgKyAnIGhvdXJzIGFnbyc7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHRpbWVEaWZmZXJlbmNlSW5NcyA8IDE3MjgwMDAwMCkgewogICAgICAgICAgICByZXR1cm4gJ3llc3RlcmRheSc7CiAgICAgICAgfQogICAgICAgIHJldHVybiBNYXRoLmZsb29yKHRpbWVEaWZmZXJlbmNlSW5NcyAvIDg2NDAwMDAwKSArICcgZGF5cyBhZ28nOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE1IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICdMaWNlbnNlJyk7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gJ0FTIElTJyBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY29uc3QgTkFNRVNQQUNFX0RFTElNID0gJy8nOwogICAgY29uc3QgUk9PVF9OQU1FID0gJ19fcm9vdF9fJzsKICAgIGNvbnN0IEZVTkNUSU9OX0xJQlJBUllfTk9ERV9QUkVGSVggPSAnX19mdW5jdGlvbl9saWJyYXJ5X18nOwogICAgLyoqIEF0dHJpYnV0ZSBrZXkgdXNlZCBmb3Igc3RvcmluZyBhdHRyaWJ1dGVzIHRoYXQgYXJlIHRvbyBsYXJnZS4gKi8KICAgIGNvbnN0IExBUkdFX0FUVFJTX0tFWSA9ICdfdG9vX2xhcmdlX2F0dHJzJzsKICAgIC8vIFNlcGFyYXRvciBiZXR3ZWVuIHRoZSBzb3VyY2UgYW5kIHRoZSBkZXN0aW5hdGlvbiBuYW1lIG9mIHRoZSBlZGdlLgogICAgY29uc3QgRURHRV9LRVlfREVMSU0kMSA9ICctLSc7CiAgICB2YXIgR3JhcGhUeXBlOwogICAgKGZ1bmN0aW9uIChHcmFwaFR5cGUpIHsKICAgICAgICBHcmFwaFR5cGVbR3JhcGhUeXBlWyJGVUxMIl0gPSAwXSA9ICJGVUxMIjsKICAgICAgICBHcmFwaFR5cGVbR3JhcGhUeXBlWyJFTUJFRERFRCJdID0gMV0gPSAiRU1CRURERUQiOwogICAgICAgIEdyYXBoVHlwZVtHcmFwaFR5cGVbIk1FVEEiXSA9IDJdID0gIk1FVEEiOwogICAgICAgIEdyYXBoVHlwZVtHcmFwaFR5cGVbIlNFUklFUyJdID0gM10gPSAiU0VSSUVTIjsKICAgICAgICBHcmFwaFR5cGVbR3JhcGhUeXBlWyJDT1JFIl0gPSA0XSA9ICJDT1JFIjsKICAgICAgICBHcmFwaFR5cGVbR3JhcGhUeXBlWyJTSEFET1ciXSA9IDVdID0gIlNIQURPVyI7CiAgICAgICAgR3JhcGhUeXBlW0dyYXBoVHlwZVsiQlJJREdFIl0gPSA2XSA9ICJCUklER0UiOwogICAgICAgIEdyYXBoVHlwZVtHcmFwaFR5cGVbIkVER0UiXSA9IDddID0gIkVER0UiOwogICAgfSkoR3JhcGhUeXBlIHx8IChHcmFwaFR5cGUgPSB7fSkpOwogICAgdmFyIE5vZGVUeXBlOwogICAgKGZ1bmN0aW9uIChOb2RlVHlwZSkgewogICAgICAgIE5vZGVUeXBlW05vZGVUeXBlWyJNRVRBIl0gPSAwXSA9ICJNRVRBIjsKICAgICAgICBOb2RlVHlwZVtOb2RlVHlwZVsiT1AiXSA9IDFdID0gIk9QIjsKICAgICAgICBOb2RlVHlwZVtOb2RlVHlwZVsiU0VSSUVTIl0gPSAyXSA9ICJTRVJJRVMiOwogICAgICAgIE5vZGVUeXBlW05vZGVUeXBlWyJCUklER0UiXSA9IDNdID0gIkJSSURHRSI7CiAgICAgICAgTm9kZVR5cGVbTm9kZVR5cGVbIkVMTElQU0lTIl0gPSA0XSA9ICJFTExJUFNJUyI7CiAgICB9KShOb2RlVHlwZSB8fCAoTm9kZVR5cGUgPSB7fSkpOwogICAgLyoqIEluZGljYXRlcyBpZiBhIG5vZGUgaXMgdG8gYmUgaW5jbHVkZWQgaW4gdGhlIG1haW4gZ3JhcGggd2hlbiByZW5kZXJlZC4gKi8KICAgIHZhciBJbmNsdXNpb25UeXBlOwogICAgKGZ1bmN0aW9uIChJbmNsdXNpb25UeXBlKSB7CiAgICAgICAgSW5jbHVzaW9uVHlwZVtJbmNsdXNpb25UeXBlWyJJTkNMVURFIl0gPSAwXSA9ICJJTkNMVURFIjsKICAgICAgICBJbmNsdXNpb25UeXBlW0luY2x1c2lvblR5cGVbIkVYQ0xVREUiXSA9IDFdID0gIkVYQ0xVREUiOwogICAgICAgIEluY2x1c2lvblR5cGVbSW5jbHVzaW9uVHlwZVsiVU5TUEVDSUZJRUQiXSA9IDJdID0gIlVOU1BFQ0lGSUVEIjsKICAgIH0pKEluY2x1c2lvblR5cGUgfHwgKEluY2x1c2lvblR5cGUgPSB7fSkpOwogICAgLyoqIEluZGljYXRlcyBpZiBhIHNlcmllcyBpcyB0byBiZSBncm91cGVkIGluIHRoZSBncmFwaCB3aGVuIHJlbmRlcmVkLiAqLwogICAgdmFyIFNlcmllc0dyb3VwaW5nVHlwZTsKICAgIChmdW5jdGlvbiAoU2VyaWVzR3JvdXBpbmdUeXBlKSB7CiAgICAgICAgU2VyaWVzR3JvdXBpbmdUeXBlW1Nlcmllc0dyb3VwaW5nVHlwZVsiR1JPVVAiXSA9IDBdID0gIkdST1VQIjsKICAgICAgICBTZXJpZXNHcm91cGluZ1R5cGVbU2VyaWVzR3JvdXBpbmdUeXBlWyJVTkdST1VQIl0gPSAxXSA9ICJVTkdST1VQIjsKICAgIH0pKFNlcmllc0dyb3VwaW5nVHlwZSB8fCAoU2VyaWVzR3JvdXBpbmdUeXBlID0ge30pKTsKICAgIC8qKiBBdHRyaWJ1dGUga2V5IHJlc2VydmVkIGZvciB0aGUgc2hhcGVzIG9mIHRoZSBvdXRwdXQgdGVuc29ycy4gKi8KICAgIGNvbnN0IE9VVFBVVF9TSEFQRVNfS0VZID0gJ19vdXRwdXRfc2hhcGVzJzsKICAgIC8qKiBBdHRyaWJ1dGUga2V5IHJlc2VydmVkIGZvciB0aGUgWExBIGNsdXN0ZXIgdGhhdCBhbiBvcCBydW5zIG9uLiAqLwogICAgY29uc3QgX1hMQV9DTFVTVEVSX0tFWSA9ICdfWGxhQ2x1c3Rlcic7CiAgICAvKioKICAgICAqIEEgU2xpbUdyYXBoIGlzIGluc3BpcmVkIGJ5IGdyYXBobGliLkdyYXBoLCBidXQgaGF2aW5nIG9ubHkgdGhlIGZ1bmN0aW9uYWxpdHkKICAgICAqIHRoYXQgd2UgbmVlZC4KICAgICAqLwogICAgY2xhc3MgU2xpbUdyYXBoIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgdGhpcy5ub2RlcyA9IHt9OwogICAgICAgICAgICB0aGlzLmVkZ2VzID0gW107CiAgICAgICAgfQogICAgfQogICAgY2xhc3MgRWxsaXBzaXNOb2RlSW1wbCB7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29uc3RydWN0cyBhIG5ldyBlbGxpcHNpcyBhbm5vdGF0aW9uIG5vZGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gbnVtTm9kZXMgVGhlIG51bWJlciBvZiBhZGRpdGlvbmFsIGFubm90YXRpb25zIHRoaXMgbm9kZSByZXByZXNlbnRzLgogICAgICAgICAqLwogICAgICAgIGNvbnN0cnVjdG9yKG51bU5vZGVzKSB7CiAgICAgICAgICAgIHRoaXMudHlwZSA9IE5vZGVUeXBlLkVMTElQU0lTOwogICAgICAgICAgICB0aGlzLmlzR3JvdXBOb2RlID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuY2FyZGluYWxpdHkgPSAxOwogICAgICAgICAgICB0aGlzLnBhcmVudE5vZGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLnN0YXRzID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5zZXROdW1Nb3JlTm9kZXMobnVtTm9kZXMpOwogICAgICAgICAgICB0aGlzLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVEOwogICAgICAgIH0KICAgICAgICBzZXROdW1Nb3JlTm9kZXMobnVtTm9kZXMpIHsKICAgICAgICAgICAgdGhpcy5udW1Nb3JlTm9kZXMgPSBudW1Ob2RlczsKICAgICAgICAgICAgdGhpcy5uYW1lID0gJy4uLiAnICsgbnVtTm9kZXMgKyAnIG1vcmUnOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQSBsYWJlbCBvYmplY3QgZm9yIG5vZGVzIGluIHRoZSBmdWxsIGdyYXBoIGFuZCBsZWFmIG5vZGVzIGluIHRoZSByZW5kZXIKICAgICAqIGdyYXBoLgogICAgICovCiAgICBjbGFzcyBPcE5vZGVJbXBsIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgbmV3IE9wIG5vZGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gcmF3Tm9kZSBUaGUgcmF3IG5vZGUuCiAgICAgICAgICovCiAgICAgICAgY29uc3RydWN0b3IocmF3Tm9kZSkgewogICAgICAgICAgICB0aGlzLm9wID0gcmF3Tm9kZS5vcDsKICAgICAgICAgICAgdGhpcy5uYW1lID0gcmF3Tm9kZS5uYW1lOwogICAgICAgICAgICB0aGlzLmRldmljZSA9IHJhd05vZGUuZGV2aWNlOwogICAgICAgICAgICB0aGlzLmF0dHIgPSByYXdOb2RlLmF0dHI7CiAgICAgICAgICAgIC8vIEFuIGFycmF5IG9mIG5vcm1hbGl6ZWQgaW5wdXRzIHRoYXQgZGVub3RlIHRoZSBpbmNvbWluZyBlZGdlcyB0bwogICAgICAgICAgICAvLyB0aGUgY3VycmVudCBub2RlLiBFYWNoIGlucHV0IGNvbnRhaW5zIHRoZSBub3JtYWxpemVkIG5hbWUgb2YgdGhlCiAgICAgICAgICAgIC8vIHNvdXJjZSBub2RlLCB3aGV0aGVyIGl0IGhhcyBhIG51bWJlciBwYXJ0IGFuZCB3aGV0aGVyIGl0IGlzIGEKICAgICAgICAgICAgLy8gY29udHJvbCBkZXBlbmRlbmN5LgogICAgICAgICAgICB0aGlzLmlucHV0cyA9IG5vcm1hbGl6ZUlucHV0cyhyYXdOb2RlLmlucHV0KTsKICAgICAgICAgICAgdGhpcy5vdXRwdXRTaGFwZXMgPSBleHRyYWN0T3V0cHV0U2hhcGVzKHJhd05vZGUuYXR0cik7CiAgICAgICAgICAgIHRoaXMueGxhQ2x1c3RlciA9IGV4dHJhY3RYbGFDbHVzdGVyKHJhd05vZGUuYXR0cik7CiAgICAgICAgICAgIHRoaXMuY29tcGF0aWJsZSA9IGZhbHNlOwogICAgICAgICAgICAvLyBhZGRpdGlvbmFsIHByb3BlcnRpZXMKICAgICAgICAgICAgdGhpcy50eXBlID0gTm9kZVR5cGUuT1A7CiAgICAgICAgICAgIHRoaXMuaXNHcm91cE5vZGUgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5jYXJkaW5hbGl0eSA9IDE7CiAgICAgICAgICAgIHRoaXMuaW5FbWJlZGRpbmdzID0gW107CiAgICAgICAgICAgIHRoaXMub3V0RW1iZWRkaW5ncyA9IFtdOwogICAgICAgICAgICB0aGlzLnBhcmVudE5vZGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVEOwogICAgICAgICAgICB0aGlzLm93bmluZ1NlcmllcyA9IG51bGw7CiAgICAgICAgfQogICAgfQogICAgZnVuY3Rpb24gY3JlYXRlTWV0YW5vZGUobmFtZSwgb3B0ID0ge30pIHsKICAgICAgICByZXR1cm4gbmV3IE1ldGFub2RlSW1wbChuYW1lLCBvcHQpOwogICAgfQogICAgLyoqCiAgICAgKiBKb2lucyB0aGUgaW5mb3JtYXRpb24gZnJvbSB0aGUgc3RhdHMgZmlsZSAobWVtb3J5LCBjb21wdXRlIHRpbWUpIHdpdGggdGhlCiAgICAgKiBncmFwaCBpbmZvcm1hdGlvbi4KICAgICAqLwogICAgZnVuY3Rpb24gam9pblN0YXRzSW5mb1dpdGhHcmFwaChncmFwaCwgc3RhdHMsIGRldmljZXNGb3JTdGF0cykgewogICAgICAgIC8vIFJlc2V0IHN0YXRzIGZvciBlYWNoIG5vZGUuCiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGgubm9kZXMsIChub2RlKSA9PiB7CiAgICAgICAgICAgIG5vZGUuc3RhdHMgPSBudWxsOwogICAgICAgIH0pOwogICAgICAgIGxvZGFzaC5lYWNoKHN0YXRzLmRldl9zdGF0cywgKGRldlN0YXRzKSA9PiB7CiAgICAgICAgICAgIC8vIElnbm9yZSBkZXZpY2VzIHRoYXQgYXJlIG5vdCBzZWxlY3RlZC4KICAgICAgICAgICAgaWYgKGRldmljZXNGb3JTdGF0cyAmJiAhZGV2aWNlc0ZvclN0YXRzW2RldlN0YXRzLmRldmljZV0pIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBsb2Rhc2guZWFjaChkZXZTdGF0cy5ub2RlX3N0YXRzLCAobm9kZVN0YXRzKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBMb29rdXAgdGhlIG5vZGUgaW4gdGhlIGdyYXBoIGJ5IGl0cyBvcmlnaW5hbCBuYW1lLCBlLmcuIEEvQi4gSWYgbm90CiAgICAgICAgICAgICAgICAvLyBmb3VuZCwgbG9va3VwIGJ5IHRoZSByZXdyaXR0ZW4gbmFtZSBBL0IvKEIpIGluIGNhc2UgdGhlIG5hbWUgaXMgYm90aAogICAgICAgICAgICAgICAgLy8gYSBuYW1lc3BhY2UgYW5kIGEgbm9kZSBuYW1lLgogICAgICAgICAgICAgICAgbGV0IG5vZGVOYW1lID0gbm9kZVN0YXRzLm5vZGVfbmFtZSBpbiBncmFwaC5ub2RlcwogICAgICAgICAgICAgICAgICAgID8gbm9kZVN0YXRzLm5vZGVfbmFtZQogICAgICAgICAgICAgICAgICAgIDogZ2V0U3RyaWN0TmFtZShub2RlU3RhdHMubm9kZV9uYW1lKTsKICAgICAgICAgICAgICAgIC8vIENvdWxkbid0IGZpbmQgYSBtYXRjaGluZyBub2RlLgogICAgICAgICAgICAgICAgaWYgKCEobm9kZU5hbWUgaW4gZ3JhcGgubm9kZXMpKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gQ29tcHV0ZSB0aGUgdG90YWwgYnl0ZXMgdXNlZC4KICAgICAgICAgICAgICAgIGxldCB0b3RhbEJ5dGVzID0gMDsKICAgICAgICAgICAgICAgIGlmIChub2RlU3RhdHMubWVtb3J5KSB7CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZVN0YXRzLm1lbW9yeSwgKGFsbG9jKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChhbGxvYy50b3RhbF9ieXRlcykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGFsbG9jLnRvdGFsX2J5dGVzID4gMCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRvdGFsQnl0ZXMgKz0gTnVtYmVyKGFsbG9jLnRvdGFsX2J5dGVzKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIHRzbGludDpkaXNhYmxlICovCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc29sZS5sb2coJ2lnbm9yaW5nIG5lZ2F0aXZlIG1lbW9yeSBhbGxvY2F0aW9uIGZvciAnICsgbm9kZU5hbWUpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qIHRzbGludDplbmFibGUgKi8KICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IG91dHB1dFNpemUgPSBudWxsOwogICAgICAgICAgICAgICAgaWYgKG5vZGVTdGF0cy5vdXRwdXQpIHsKICAgICAgICAgICAgICAgICAgICBvdXRwdXRTaXplID0gbG9kYXNoLm1hcChub2RlU3RhdHMub3V0cHV0LCAob3V0cHV0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBsb2Rhc2gubWFwKG91dHB1dC50ZW5zb3JfZGVzY3JpcHRpb24uc2hhcGUuZGltLCAoZGltKSA9PiBOdW1iZXIoZGltLnNpemUpKTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGdyYXBoLm5vZGVzW25vZGVOYW1lXS5kZXZpY2UgPSBkZXZTdGF0cy5kZXZpY2U7CiAgICAgICAgICAgICAgICBpZiAoZ3JhcGgubm9kZXNbbm9kZU5hbWVdLnN0YXRzID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBncmFwaC5ub2Rlc1tub2RlTmFtZV0uc3RhdHMgPSBuZXcgTm9kZVN0YXRzKG91dHB1dFNpemUpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZ3JhcGgubm9kZXNbbm9kZU5hbWVdLnN0YXRzLmFkZEJ5dGVzQWxsb2NhdGlvbih0b3RhbEJ5dGVzKTsKICAgICAgICAgICAgICAgIGlmIChub2RlU3RhdHMuYWxsX2VuZF9yZWxfbWljcm9zKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKG5vZGVTdGF0cy5hbGxfZW5kX3JlbF9taWNyb3MgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGdyYXBoLm5vZGVzW25vZGVOYW1lXS5zdGF0cy5hZGRFeGVjdXRpb25UaW1lKG5vZGVTdGF0cy5hbGxfc3RhcnRfbWljcm9zLCBub2RlU3RhdHMuYWxsX3N0YXJ0X21pY3JvcyArIG5vZGVTdGF0cy5hbGxfZW5kX3JlbF9taWNyb3MpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgLyogdHNsaW50OmRpc2FibGUgKi8KICAgICAgICAgICAgICAgICAgICAgICAgY29uc29sZS5sb2coJ2lnbm9yaW5nIG5lZ2F0aXZlIHJ1bnRpbWUgZm9yICcgKyBub2RlTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8qIHRzbGludDplbmFibGUgKi8KICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgfQogICAgY2xhc3MgTWV0YW5vZGVJbXBsIHsKICAgICAgICAvKiogQSBsYWJlbCBvYmplY3QgZm9yIG1ldGEtbm9kZXMgaW4gdGhlIGdyYXBoIGhpZXJhcmNoeSAqLwogICAgICAgIGNvbnN0cnVjdG9yKG5hbWUsIG9wdCA9IHt9KSB7CiAgICAgICAgICAgIHRoaXMubmFtZSA9IG5hbWU7CiAgICAgICAgICAgIHRoaXMudHlwZSA9IE5vZGVUeXBlLk1FVEE7CiAgICAgICAgICAgIC8qKiBudW1iZXIgb2YgbGV2ZWxzIHVuZGVyIHRoaXMgZ3JvdXAgKi8KICAgICAgICAgICAgdGhpcy5kZXB0aCA9IDE7CiAgICAgICAgICAgIHRoaXMuaXNHcm91cE5vZGUgPSB0cnVlOwogICAgICAgICAgICAvKiogIyBvZiBsZWFmIG5vZGVzIChpbmNsdWRpbmcgZW1iZWRkZWQgb25lcykgKi8KICAgICAgICAgICAgdGhpcy5jYXJkaW5hbGl0eSA9IDA7CiAgICAgICAgICAgIC8qKiBncmFwaCBjb250YWlucyBtZXRhbm9kZXMsIG5vZGVzLCBlZGdlcwogICAgICAgICAgICAgKiBhbmQgbWV0YWVkZ2VzIGZvciBtYWluIGl0ZW1zIHdpdGhpbiB0aGlzIG1ldGFub2RlCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLm1ldGFncmFwaCA9IGNyZWF0ZUdyYXBoKG5hbWUsIEdyYXBoVHlwZS5NRVRBLCBvcHQpOwogICAgICAgICAgICAvKiogYnJpZGdlZ3JhcGggbXVzdCBiZSBjb25zdHJ1Y3RlZCBsYXppbHktc2VlIGhpZXJhcmNoeS5nZXRCcmlkZ2VncmFwaCgpICovCiAgICAgICAgICAgIHRoaXMuYnJpZGdlZ3JhcGggPSBudWxsOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQSBkaWN0aW9uYXJ5IHRoYXQgY291bnQgb3BzIHR5cGUgb2Ygbm9kZXMgaW4gdGhpcyBtZXRhbm9kZQogICAgICAgICAgICAgKiAob3AgdHlwZSA9PiBjb3VudCkuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLm9wSGlzdG9ncmFtID0ge307CiAgICAgICAgICAgIHRoaXMuZGV2aWNlSGlzdG9ncmFtID0ge307CiAgICAgICAgICAgIHRoaXMueGxhQ2x1c3Rlckhpc3RvZ3JhbSA9IHt9OwogICAgICAgICAgICB0aGlzLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0gPSB7IGNvbXBhdGlibGU6IDAsIGluY29tcGF0aWJsZTogMCB9OwogICAgICAgICAgICAvKiogdW5pcXVlIGlkIGZvciBhIG1ldGFub2RlIG9mIHNpbWlsYXIgc3ViZ3JhcGggKi8KICAgICAgICAgICAgdGhpcy50ZW1wbGF0ZUlkID0gbnVsbDsKICAgICAgICAgICAgLyoqIE1ldGFub2RlIHdoaWNoIGNvbnRhaW5zIHRoaXMgbm9kZSwgaWYgYW55ICovCiAgICAgICAgICAgIHRoaXMucGFyZW50Tm9kZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuaGFzTm9uQ29udHJvbEVkZ2VzID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuaW5jbHVkZSA9IEluY2x1c2lvblR5cGUuVU5TUEVDSUZJRUQ7CiAgICAgICAgICAgIHRoaXMuYXNzb2NpYXRlZEZ1bmN0aW9uID0gJyc7CiAgICAgICAgfQogICAgICAgIGdldEZpcnN0Q2hpbGQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLm1ldGFncmFwaC5ub2RlKHRoaXMubWV0YWdyYXBoLm5vZGVzKClbMF0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBvcCBub2RlIGFzc29jaWF0ZWQgd2l0aCB0aGUgbWV0YW5vZGUuCiAgICAgICAgICogRm9yIGV4YW1wbGUsIGlmIHRoZSBtZXRhbm9kZSBpcyAnc2dkJywgdGhlIGFzc29jaWF0ZWQKICAgICAgICAgKiBvcCBub2RlIGlzIHNnZC8oc2dkKS4KICAgICAgICAgKi8KICAgICAgICBnZXRSb290T3AoKSB7CiAgICAgICAgICAgIGxldCBuYW1lU3BsaXQgPSB0aGlzLm5hbWUuc3BsaXQoJy8nKTsKICAgICAgICAgICAgbGV0IHJvb3RPcE5hbWUgPSB0aGlzLm5hbWUgKyAnLygnICsgbmFtZVNwbGl0W25hbWVTcGxpdC5sZW5ndGggLSAxXSArICcpJzsKICAgICAgICAgICAgcmV0dXJuIHRoaXMubWV0YWdyYXBoLm5vZGUocm9vdE9wTmFtZSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybiBhbiBhcnJheSBvZiB0aGUgbmFtZXMgb2YgYWxsIHRoZSBsZWF2ZXMgKG5vbi1Hcm91cE5vZGVzKSBpbnNpZGUKICAgICAgICAgKiB0aGlzIG1ldGFub2RlLiBUaGlzIHBlcmZvcm1zIGEgYnJlYWR0aC1maXJzdCBzZWFyY2ggb2YgdGhlIHRyZWUsIHNvCiAgICAgICAgICogaW1tZWRpYXRlIGNoaWxkIGxlYXZlcyB3aWxsIGFwcGVhciBlYXJsaWVyIGluIHRoZSBvdXRwdXQgYXJyYXkgdGhhbgogICAgICAgICAqIGRlc2NlbmRhbnQgbGVhdmVzLgogICAgICAgICAqLwogICAgICAgIGxlYXZlcygpIHsKICAgICAgICAgICAgbGV0IGxlYXZlcyA9IFtdOwogICAgICAgICAgICBsZXQgcXVldWUgPSBbdGhpc107CiAgICAgICAgICAgIGxldCBtZXRhZ3JhcGg7IC8vIERlZmluZWQgaGVyZSBkdWUgdG8gYSBsaW1pdGF0aW9uIG9mIEVTNi0+NSBjb21waWxhdGlvbi4KICAgICAgICAgICAgd2hpbGUgKHF1ZXVlLmxlbmd0aCkgewogICAgICAgICAgICAgICAgbGV0IG5vZGUgPSBxdWV1ZS5zaGlmdCgpOwogICAgICAgICAgICAgICAgaWYgKG5vZGUuaXNHcm91cE5vZGUpIHsKICAgICAgICAgICAgICAgICAgICBtZXRhZ3JhcGggPSBub2RlLm1ldGFncmFwaDsKICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChtZXRhZ3JhcGgubm9kZXMoKSwgKG5hbWUpID0+IHF1ZXVlLnB1c2gobWV0YWdyYXBoLm5vZGUobmFtZSkpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGxlYXZlcy5wdXNoKG5vZGUubmFtZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGxlYXZlczsKICAgICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBjcmVhdGVNZXRhZWRnZSh2LCB3KSB7CiAgICAgICAgcmV0dXJuIG5ldyBNZXRhZWRnZUltcGwodiwgdyk7CiAgICB9CiAgICAvKioKICAgICAqIEEgbGFiZWwgb2JqZWN0IGZvciBlZGdlcyBiZXR3ZWVuIG1ldGFub2RlcyBvZiBzdWJncmFwaHMgaW4gdGhlIHJlbmRlciBncmFwaC4KICAgICAqLwogICAgY2xhc3MgTWV0YWVkZ2VJbXBsIHsKICAgICAgICBjb25zdHJ1Y3Rvcih2LCB3KSB7CiAgICAgICAgICAgIHRoaXMudiA9IHY7CiAgICAgICAgICAgIHRoaXMudyA9IHc7CiAgICAgICAgICAgIHRoaXMuYmFzZUVkZ2VMaXN0ID0gW107CiAgICAgICAgICAgIHRoaXMuaW5ib3VuZCA9IG51bGw7CiAgICAgICAgICAgIHRoaXMubnVtUmVndWxhckVkZ2VzID0gMDsKICAgICAgICAgICAgdGhpcy5udW1Db250cm9sRWRnZXMgPSAwOwogICAgICAgICAgICB0aGlzLm51bVJlZkVkZ2VzID0gMDsKICAgICAgICAgICAgdGhpcy50b3RhbFNpemUgPSAwOwogICAgICAgIH0KICAgICAgICBhZGRCYXNlRWRnZShlZGdlLCBoKSB7CiAgICAgICAgICAgIHRoaXMuYmFzZUVkZ2VMaXN0LnB1c2goZWRnZSk7CiAgICAgICAgICAgIGlmIChlZGdlLmlzQ29udHJvbERlcGVuZGVuY3kpIHsKICAgICAgICAgICAgICAgIHRoaXMubnVtQ29udHJvbEVkZ2VzICs9IDE7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLm51bVJlZ3VsYXJFZGdlcyArPSAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChlZGdlLmlzUmVmZXJlbmNlRWRnZSkgewogICAgICAgICAgICAgICAgdGhpcy5udW1SZWZFZGdlcyArPSAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvbXB1dGUgdGhlIHNpemUgb2YgdGhlIHRlbnNvciBmbG93aW5nIHRocm91Z2ggdGhpcwogICAgICAgICAgICAvLyBiYXNlIGVkZ2UuCiAgICAgICAgICAgIHRoaXMudG90YWxTaXplICs9IE1ldGFlZGdlSW1wbC5jb21wdXRlU2l6ZU9mRWRnZShlZGdlLCBoKTsKICAgICAgICAgICAgaC5tYXhNZXRhRWRnZVNpemUgPSBNYXRoLm1heChoLm1heE1ldGFFZGdlU2l6ZSwgdGhpcy50b3RhbFNpemUpOwogICAgICAgIH0KICAgICAgICBzdGF0aWMgY29tcHV0ZVNpemVPZkVkZ2UoZWRnZSwgaCkgewogICAgICAgICAgICBsZXQgb3BOb2RlID0gaC5ub2RlKGVkZ2Uudik7CiAgICAgICAgICAgIGlmICghb3BOb2RlLm91dHB1dFNoYXBlcykgewogICAgICAgICAgICAgICAgLy8gTm8gc2hhcGUgaW5mb3JtYXRpb24uIEFzc3N1bWUgYSBzaW5nbGUgbnVtYmVyLiBUaGlzIGdpdmVzCiAgICAgICAgICAgICAgICAvLyBhIGxvd2VyIGJvdW5kIGZvciB0aGUgdG90YWwgc2l6ZS4KICAgICAgICAgICAgICAgIHJldHVybiAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGguaGFzU2hhcGVJbmZvID0gdHJ1ZTsKICAgICAgICAgICAgLy8gU3VtIHRoZSBzaXplcyBvZiBhbGwgb3V0cHV0IHRlbnNvcnMuCiAgICAgICAgICAgIC8vIFRPRE8oc3RlcGhhbndsZWUpOiBVc2UgT2JqZWN0LnZhbHVlcyBhZnRlciBlczIwMTcuCiAgICAgICAgICAgIGNvbnN0IHZhbHVlcyA9IE9iamVjdC5rZXlzKG9wTm9kZS5vdXRwdXRTaGFwZXMpCiAgICAgICAgICAgICAgICAubWFwKChrKSA9PiBvcE5vZGUub3V0cHV0U2hhcGVzW2tdKQogICAgICAgICAgICAgICAgLm1hcCgoc2hhcGUpID0+IHsKICAgICAgICAgICAgICAgIC8vIElmIHRoZSBzaGFwZSBpcyB1bmtub3duLCB0cmVhdCBpdCBhcyAxIHdoZW4gY29tcHV0aW5nCiAgICAgICAgICAgICAgICAvLyB0b3RhbCBzaXplLiBUaGlzIGdpdmVzIGEgbG93ZXIgYm91bmQgZm9yIHRoZSB0b3RhbCBzaXplLgogICAgICAgICAgICAgICAgaWYgKHNoYXBlID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIE11bHRpcGx5IGFsbCBzaGFwZXMgdG8gZ2V0IHRoZSB0b3RhbCBzaXplIG9mIHRoZSB0ZW5zb3IuCiAgICAgICAgICAgICAgICAvLyBFLmcuIFRoZSB0b3RhbCBzaXplIG9mIFs0LCAyLCAxXSBpcyA0ICogMiAqIDEuCiAgICAgICAgICAgICAgICByZXR1cm4gc2hhcGUucmVkdWNlKChhY2N1bXVsYXRlZCwgY3VyclNpemUpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBJZiB0aGlzIHBhcnRpY3VsYXIgZGltZW5zaW9uIGlzIHVua25vd24sIHRyZWF0CiAgICAgICAgICAgICAgICAgICAgLy8gaXQgYXMgMSB3aGVuIGNvbXB1dGluZyB0b3RhbCBzaXplLiBUaGlzIGdpdmVzIGEgbG93ZXIgYm91bmQKICAgICAgICAgICAgICAgICAgICAvLyBmb3IgdGhlIHRvdGFsIHNpemUuCiAgICAgICAgICAgICAgICAgICAgaWYgKGN1cnJTaXplID09PSAtMSkgewogICAgICAgICAgICAgICAgICAgICAgICBjdXJyU2l6ZSA9IDE7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIHJldHVybiBhY2N1bXVsYXRlZCAqIGN1cnJTaXplOwogICAgICAgICAgICAgICAgfSwgMSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gbG9kYXNoLnN1bSh2YWx1ZXMpOwogICAgICAgIH0KICAgIH0KICAgIGZ1bmN0aW9uIGNyZWF0ZVNlcmllc05vZGUocHJlZml4LCBzdWZmaXgsIHBhcmVudCwgY2x1c3RlcklkLCBuYW1lLCBncmFwaE9wdGlvbnMpIHsKICAgICAgICByZXR1cm4gbmV3IFNlcmllc05vZGVJbXBsKHByZWZpeCwgc3VmZml4LCBwYXJlbnQsIGNsdXN0ZXJJZCwgbmFtZSwgZ3JhcGhPcHRpb25zKTsKICAgIH0KICAgIGZ1bmN0aW9uIGdldFNlcmllc05vZGVOYW1lKHByZWZpeCwgc3VmZml4LCBwYXJlbnQsIHN0YXJ0SWQsIGVuZElkKSB7CiAgICAgICAgbGV0IG51bVJlcHJlc2VudGF0aW9uID0gdHlwZW9mIHN0YXJ0SWQgIT09ICd1bmRlZmluZWQnICYmIHR5cGVvZiBlbmRJZCAhPT0gJ3VuZGVmaW5lZCcKICAgICAgICAgICAgPyAnWycgKyBzdGFydElkICsgJy0nICsgZW5kSWQgKyAnXScKICAgICAgICAgICAgOiAnIyc7CiAgICAgICAgbGV0IHBhdHRlcm4gPSBwcmVmaXggKyBudW1SZXByZXNlbnRhdGlvbiArIHN1ZmZpeDsKICAgICAgICByZXR1cm4gKHBhcmVudCA/IHBhcmVudCArICcvJyA6ICcnKSArIHBhdHRlcm47CiAgICB9CiAgICBjbGFzcyBTZXJpZXNOb2RlSW1wbCB7CiAgICAgICAgY29uc3RydWN0b3IocHJlZml4LCBzdWZmaXgsIHBhcmVudCwgY2x1c3RlcklkLCBuYW1lLCBncmFwaE9wdGlvbnMpIHsKICAgICAgICAgICAgdGhpcy5uYW1lID0gbmFtZSB8fCBnZXRTZXJpZXNOb2RlTmFtZShwcmVmaXgsIHN1ZmZpeCwgcGFyZW50KTsKICAgICAgICAgICAgdGhpcy50eXBlID0gTm9kZVR5cGUuU0VSSUVTOwogICAgICAgICAgICB0aGlzLmhhc0xvb3AgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5wcmVmaXggPSBwcmVmaXg7CiAgICAgICAgICAgIHRoaXMuc3VmZml4ID0gc3VmZml4OwogICAgICAgICAgICB0aGlzLmNsdXN0ZXJJZCA9IGNsdXN0ZXJJZDsKICAgICAgICAgICAgdGhpcy5pZHMgPSBbXTsKICAgICAgICAgICAgdGhpcy5wYXJlbnQgPSBwYXJlbnQ7CiAgICAgICAgICAgIHRoaXMuaXNHcm91cE5vZGUgPSB0cnVlOwogICAgICAgICAgICB0aGlzLmNhcmRpbmFsaXR5ID0gMDsKICAgICAgICAgICAgdGhpcy5tZXRhZ3JhcGggPSBjcmVhdGVHcmFwaChuYW1lLCBHcmFwaFR5cGUuU0VSSUVTLCBncmFwaE9wdGlvbnMpOwogICAgICAgICAgICAvLyBicmlkZ2VncmFwaCBtdXN0IGJlIGNvbnN0cnVjdGVkIGxhemlseS1zZWUgaGllcmFyY2h5LmdldEJyaWRnZWdyYXBoKCkKICAgICAgICAgICAgdGhpcy5icmlkZ2VncmFwaCA9IG51bGw7CiAgICAgICAgICAgIHRoaXMucGFyZW50Tm9kZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuZGV2aWNlSGlzdG9ncmFtID0ge307CiAgICAgICAgICAgIHRoaXMueGxhQ2x1c3Rlckhpc3RvZ3JhbSA9IHt9OwogICAgICAgICAgICB0aGlzLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0gPSB7IGNvbXBhdGlibGU6IDAsIGluY29tcGF0aWJsZTogMCB9OwogICAgICAgICAgICB0aGlzLmhhc05vbkNvbnRyb2xFZGdlcyA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVEOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogRXh0cmFjdHMgdGhlIHNoYXBlcyBvZiB0aGUgb3V0cHV0IHRlbnNvcnMgZnJvbSB0aGUgYXR0ciBwcm9wZXJ0eSBpbiB0aGUKICAgICAqIG5vZGUgcHJvdG8uCiAgICAgKi8KICAgIC8vIHRzbGludDpkaXNhYmxlLW5leHQtbGluZTpuby1hbnkKICAgIGZ1bmN0aW9uIGV4dHJhY3RPdXRwdXRTaGFwZXMoYXR0cikgewogICAgICAgIC8vIFdlIGRvbid0IGtub3cgYW55dGhpbmcgYWJvdXQgdGhlIG91dHB1dCB0ZW5zb3JzLgogICAgICAgIGlmICghYXR0cikgewogICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICB9CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBhdHRyLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGxldCB7IGtleSwgdmFsdWUgfSA9IGF0dHJbaV07CiAgICAgICAgICAgIGlmIChrZXkgPT09IE9VVFBVVF9TSEFQRVNfS0VZKSB7CiAgICAgICAgICAgICAgICBpZiAoIXZhbHVlLmxpc3Quc2hhcGUpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgT1VUUFVUX1NIQVBFU19LRVkgbGFja3MgYSB2YWx1ZS4gV2Uga25vdyBub3RoaW5nIGFib3V0IHRoZSBzaGFwZS4KICAgICAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIE1hcCBhbGwgb3V0cHV0IHRlbnNvcnMgaW50byBhcnJheSBvZiBudW1iZXJzIGRlbm90aW5nIHRoZWlyIHNoYXBlLgogICAgICAgICAgICAgICAgbGV0IHJlc3VsdCA9IHZhbHVlLmxpc3Quc2hhcGUubWFwKChzaGFwZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGlmIChzaGFwZS51bmtub3duX3JhbmspIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyBvdXRwdXQgdGVuc29yIGlzIG9mIHVua25vd24gcmFuay4gV2UgZG9uJ3Qga25vdyBpZiBpdCBpcyBhCiAgICAgICAgICAgICAgICAgICAgICAgIC8vIHNjYWxhciwgb3IgYSB0ZW5zb3IsIG9yIG9mIHdoYXQgc2hhcGUgaXQgaXMuCiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpZiAoc2hhcGUuZGltID09IG51bGwgfHwKICAgICAgICAgICAgICAgICAgICAgICAgKHNoYXBlLmRpbS5sZW5ndGggPT09IDEgJiYgc2hhcGUuZGltWzBdLnNpemUgPT0gbnVsbCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyBvdXRwdXQgdGVuc29yIGlzIGEgc2NhbGFyLgogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgb3V0cHV0IHRlbnNvciBoYXMgYSBrbm93biByYW5rLiBNYXAgZWFjaCBkaW1lbnNpb24gc2l6ZQogICAgICAgICAgICAgICAgICAgIC8vIGludG8gYSBudW1iZXIuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHNoYXBlLmRpbS5tYXAoKGRpbSkgPT4gewogICAgICAgICAgICAgICAgICAgICAgICAvLyBTaXplIGNhbiBiZSAtMSBpZiB0aGlzIHBhcnRpY3VsYXIgZGltZW5zaW9uIGlzIHVua25vd24uCiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBkaW0uc2l6ZTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgLy8gU2luY2Ugd2UgYWxyZWFkeSBwcm9jZXNzZWQgaXQsIHJlbW92ZSB0aGUgZW50cnkgZnJvbSB0aGUgYXR0cmlidXRlCiAgICAgICAgICAgICAgICAvLyBsaXN0IChzYXZlcyBtZW1vcnkpLgogICAgICAgICAgICAgICAgYXR0ci5zcGxpY2UoaSwgMSk7CiAgICAgICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIFdlIGRpZG4ndCBmaW5kIE9VVFBVVF9TSEFQRVNfS0VZIGluIGF0dHJpYnV0ZXMsIHNvIHdlIGRvbid0IGtub3cgYW55dGhpbmcKICAgICAgICAvLyBhYm91dCB0aGUgb3V0cHV0IHRlbnNvcnMuCiAgICAgICAgcmV0dXJuIG51bGw7CiAgICB9CiAgICAvKioKICAgICAqIEV4dHJhY3RzIHRoZSBYTEEgQ2x1c3RlciB0aGF0IGFuIG9wIHJ1bnMgb24gZnJvbSB0aGUgYXR0cnMgb2YgdGhlIE9wTm9kZS4KICAgICAqIEBwYXJhbSBhdHRyIFRoZSBhdHRyIHByb3BlcnR5LgogICAgICogQHJldHVybiBBIHN0cmluZyB0aGF0IGlzIHRoZSBuYW1lIG9mIHRoZSBjbHVzdGVyLiBPciBudWxsIGlmIGl0IGNvdWxkIG5vdCBiZQogICAgICogICAgIGRldGVybWluZWQuCiAgICAgKi8KICAgIC8vIHRzbGludDpkaXNhYmxlLW5leHQtbGluZTpuby1hbnkKICAgIGZ1bmN0aW9uIGV4dHJhY3RYbGFDbHVzdGVyKGF0dHIpIHsKICAgICAgICBpZiAoIWF0dHIpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIC8vIEZpbmQgdGhlIGF0dHJpYnV0ZSBmb3IgWExBIGNsdXN0ZXIgaWYgdGhlcmUgaXMgb25lLgogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYXR0ci5sZW5ndGg7IGkrKykgewogICAgICAgICAgICBpZiAoYXR0cltpXS5rZXkgPT09IF9YTEFfQ0xVU1RFUl9LRVkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBhdHRyW2ldLnZhbHVlWydzJ10gfHwgbnVsbDsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gbnVsbDsKICAgIH0KICAgIC8qKgogICAgICogTm9ybWFsaXplcyB0aGUgaW5wdXRzIGFuZCBleHRyYWN0cyBhc3NvY2lhdGVkIG1ldGFkYXRhOgogICAgICogMSkgSW5wdXRzIGNhbiBjb250YWluIGEgY29sb24gZm9sbG93ZWQgYnkgYSBzdWZmaXggb2YgY2hhcmFjdGVycy4KICAgICAqICAgIFRoYXQgc3VmZml4IG1heSBiZSBhIHNpbmdsZSBudW1iZXIgKGUuZy4gaW5wdXROYW1lOjEpIG9yIHNldmVyYWwgd29yZAogICAgICogICAgY2hhcmFjdGVycyBzZXBhcmF0ZWQgZnJvbSBhIG51bWJlciBieSBhIGNvbG9uIChlLmcuIGlucHV0TmFtZTpmb286MSkuIFRoZQogICAgICogICAgbGF0dGVyIGNhc2UgaXMgdXNlZCB0byBkZW5vdGUgaW5wdXRzIGFuZCBvdXRwdXRzIG9mIGZ1bmN0aW9ucy4KICAgICAqIDIpIENvbnRyb2wgZGVwZW5kZW5jeSBpbnB1dHMgY29udGFpbiBjYXJldCBhdCB0aGUgYmVnaW5uaW5nIGFuZCB3ZQogICAgICogICAgcmVtb3ZlIHRoaXMgYW5kIGFubm90YXRlIHRoZSBlZGdlIGFzIGEgY29udHJvbCBkZXBlbmRlbmN5LgogICAgICogQHBhcmFtIGlucHV0cyBBcnJheSBvZiB1bm5vcm1hbGl6ZWQgbmFtZXMgb2YgaW5wdXQgbm9kZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIG5vcm1hbGl6ZUlucHV0cyhpbnB1dHMpIHsKICAgICAgICBsZXQgbm9ybWFsaXplZElucHV0cyA9IFtdOwogICAgICAgIGxvZGFzaC5lYWNoKGlucHV0cywgKGlucHV0TmFtZSkgPT4gewogICAgICAgICAgICBsZXQgaXNDb250cm9sRGVwZW5kZW5jeSA9IGlucHV0TmFtZVswXSA9PT0gJ14nOwogICAgICAgICAgICBpZiAoaXNDb250cm9sRGVwZW5kZW5jeSkgewogICAgICAgICAgICAgICAgLy8gVGhlIGNhcmF0IG1lcmVseSBpbmRpY2F0ZXMgd2hldGhlciB0aGlzIGlucHV0IGlzIGEgY29udHJvbCBkZXBlbmRlbmN5LgogICAgICAgICAgICAgICAgLy8gSXQgc2hvdWxkIG5vdCBiZSBwYXJ0IG9mIHRoZSBuYW1lLgogICAgICAgICAgICAgICAgaW5wdXROYW1lID0gaW5wdXROYW1lLnN1YnN0cmluZygxKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgbmFtZSA9IGlucHV0TmFtZTsKICAgICAgICAgICAgbGV0IG91dHB1dFRlbnNvcktleSA9ICcwJzsKICAgICAgICAgICAgbGV0IG1hdGNoID0gaW5wdXROYW1lLm1hdGNoKC8oLiopOihcdys6XGQrKSQvKTsKICAgICAgICAgICAgaWYgKG1hdGNoKSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgb3V0cHV0IHN0cmluZyBjb25zaXN0cyBvZiBzZXZlcmFsIGNoYXJhY3RlcnMgYW5kIGEgbnVtYmVyIHNlcGFyYXRlZAogICAgICAgICAgICAgICAgLy8gYnkgYSBjb2xvbi4KICAgICAgICAgICAgICAgIG5hbWUgPSBtYXRjaFsxXTsKICAgICAgICAgICAgICAgIG91dHB1dFRlbnNvcktleSA9IG1hdGNoWzJdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgbWF0Y2ggPSBpbnB1dE5hbWUubWF0Y2goLyguKik6KFxkKykkLyk7CiAgICAgICAgICAgICAgICBpZiAobWF0Y2gpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgb3V0cHV0IHN0cmluZyBjb25zaXN0cyBvZiBhIHNpbmdsZSBudW1iZXIuCiAgICAgICAgICAgICAgICAgICAgbmFtZSA9IG1hdGNoWzFdOwogICAgICAgICAgICAgICAgICAgIG91dHB1dFRlbnNvcktleSA9IG1hdGNoWzJdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChub3JtYWxpemVkSW5wdXRzLmxlbmd0aCA9PT0gMCB8fAogICAgICAgICAgICAgICAgbmFtZSAhPT0gbm9ybWFsaXplZElucHV0c1tub3JtYWxpemVkSW5wdXRzLmxlbmd0aCAtIDFdLm5hbWUpIHsKICAgICAgICAgICAgICAgIG5vcm1hbGl6ZWRJbnB1dHMucHVzaCh7CiAgICAgICAgICAgICAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICAgICAgICAgICAgICBvdXRwdXRUZW5zb3JLZXk6IG91dHB1dFRlbnNvcktleSwKICAgICAgICAgICAgICAgICAgICBpc0NvbnRyb2xEZXBlbmRlbmN5OiBpc0NvbnRyb2xEZXBlbmRlbmN5LAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICByZXR1cm4gbm9ybWFsaXplZElucHV0czsKICAgIH0KICAgIGZ1bmN0aW9uIGFkZEVkZ2VUb0dyYXBoKGdyYXBoLCBpbnB1dE5hbWUsIG91dHB1dE5vZGUsIGlucHV0LCBwYXJhbXMsIGluZGV4KSB7CiAgICAgICAgLy8gRG9uJ3QgYWxsb3cgbG9vcHMgaW4gdGhlIGdyYXBoLgogICAgICAgIGlmIChpbnB1dE5hbWUgPT09IG91dHB1dE5vZGUubmFtZSkgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIC8vIENoZWNrIGlmIHRoaXMgb3AgdHlwZSBhbmQgaW5wdXQgbnVtYmVyIGNvcnJlc3BvbmRzIHRvIGEKICAgICAgICAvLyByZWZlcmVuY2UgZWRnZSB1c2luZyB0aGUgcmVmRWRnZXMgZGljdGlvbmFyeSBpbiB0aGUgcGFyYW1zLgogICAgICAgIGxldCBpc1JlZkVkZ2UgPSBwYXJhbXMucmVmRWRnZXNbb3V0cHV0Tm9kZS5vcCArICcgJyArIGluZGV4XSA9PT0gdHJ1ZTsKICAgICAgICBncmFwaC5lZGdlcy5wdXNoKHsKICAgICAgICAgICAgdjogaW5wdXROYW1lLAogICAgICAgICAgICB3OiBvdXRwdXROb2RlLm5hbWUsCiAgICAgICAgICAgIG91dHB1dFRlbnNvcktleTogaW5wdXQub3V0cHV0VGVuc29yS2V5LAogICAgICAgICAgICBpc0NvbnRyb2xEZXBlbmRlbmN5OiBpbnB1dC5pc0NvbnRyb2xEZXBlbmRlbmN5LAogICAgICAgICAgICBpc1JlZmVyZW5jZUVkZ2U6IGlzUmVmRWRnZSwKICAgICAgICB9KTsKICAgIH0KICAgIGNvbnN0IERlZmF1bHRCdWlsZFBhcmFtcyA9IHsKICAgICAgICBlbmFibGVFbWJlZGRpbmc6IHRydWUsCiAgICAgICAgaW5FbWJlZGRpbmdUeXBlczogWydDb25zdCddLAogICAgICAgIG91dEVtYmVkZGluZ1R5cGVzOiBbJ15bYS16QS1aXStTdW1tYXJ5JCddLAogICAgICAgIC8vIFRoaXMgaXMgdGhlIHdoaXRlbGlzdCBvZiBpbnB1dHMgb24gb3AgdHlwZXMgdGhhdCBhcmUgY29uc2lkZXJlZAogICAgICAgIC8vIHJlZmVyZW5jZSBlZGdlcy4gIkFzc2lnbiAwIiBpbmRpY2F0ZXMgdGhhdCB0aGUgZmlyc3QgaW5wdXQgdG8KICAgICAgICAvLyBhbiBPcE5vZGUgd2l0aCBvcGVyYXRpb24gdHlwZSAiQXNzaWduIiBpcyBhIHJlZmVyZW5jZSBlZGdlLgogICAgICAgIHJlZkVkZ2VzOiB7CiAgICAgICAgICAgICdBc3NpZ24gMCc6IHRydWUsCiAgICAgICAgICAgICdBc3NpZ25BZGQgMCc6IHRydWUsCiAgICAgICAgICAgICdBc3NpZ25TdWIgMCc6IHRydWUsCiAgICAgICAgICAgICdhc3NpZ24gMCc6IHRydWUsCiAgICAgICAgICAgICdhc3NpZ25fYWRkIDAnOiB0cnVlLAogICAgICAgICAgICAnYXNzaWduX3N1YiAwJzogdHJ1ZSwKICAgICAgICAgICAgJ2NvdW50X3VwX3RvIDAnOiB0cnVlLAogICAgICAgICAgICAnU2NhdHRlckFkZCAwJzogdHJ1ZSwKICAgICAgICAgICAgJ1NjYXR0ZXJTdWIgMCc6IHRydWUsCiAgICAgICAgICAgICdTY2F0dGVyVXBkYXRlIDAnOiB0cnVlLAogICAgICAgICAgICAnc2NhdHRlcl9hZGQgMCc6IHRydWUsCiAgICAgICAgICAgICdzY2F0dGVyX3N1YiAwJzogdHJ1ZSwKICAgICAgICAgICAgJ3NjYXR0ZXJfdXBkYXRlIDAnOiB0cnVlLAogICAgICAgIH0sCiAgICB9OwogICAgZnVuY3Rpb24gYnVpbGQoZ3JhcGhEZWYsIHBhcmFtcywgdHJhY2tlcikgewogICAgICAgIC8qKgogICAgICAgICAqIEEgZGljdGlvbmFyeSB0aGF0IG1hcHMgZWFjaCBpbi1lbWJlZGRpbmcgbm9kZSBuYW1lIHRvIHRoZSBub2RlCiAgICAgICAgICogb2JqZWN0LgogICAgICAgICAqLwogICAgICAgIGxldCBpbkVtYmVkZGluZyA9IHt9OwogICAgICAgIC8qKgogICAgICAgICAqIEEgZGljdGlvbmFyeSB0aGF0IG1hcHMgZWFjaCBvdXQtZW1iZWRkaW5nIG5vZGUgbmFtZSB0byB0aGUgbm9kZQogICAgICAgICAqIG9iamVjdC4KICAgICAgICAgKi8KICAgICAgICBsZXQgb3V0RW1iZWRkaW5nID0ge307CiAgICAgICAgLyoqCiAgICAgICAgICogQSBkaWN0aW9uYXJ5IHRoYXQgbWFwcyBlYWNoIG5vZGUgbmFtZSB0byBhbiBhcnJheSBvZiB0aGUgbm9kZSdzCiAgICAgICAgICogb3V0LWVtYmVkZGluZyBub2RlIGxhYmVsIG9iamVjdHMuCiAgICAgICAgICovCiAgICAgICAgbGV0IG91dEVtYmVkZGluZ3MgPSB7fTsKICAgICAgICBsZXQgaXNJbkVtYmVkZGVkUHJlZCA9IGdldEVtYmVkUHJlZGljYXRlKHBhcmFtcy5pbkVtYmVkZGluZ1R5cGVzKTsKICAgICAgICBsZXQgaXNPdXRFbWJlZGRlZFByZWQgPSBnZXRFbWJlZFByZWRpY2F0ZShwYXJhbXMub3V0RW1iZWRkaW5nVHlwZXMpOwogICAgICAgIGxldCBlbWJlZGRpbmdOb2RlTmFtZXMgPSBbXTsKICAgICAgICBsZXQgcmF3Tm9kZXMgPSBncmFwaERlZi5ub2RlOwogICAgICAgIC8qKgogICAgICAgICAqIEEgbGlzdCBvZiBhbGwgdGhlIG5vbi1lbWJlZGRpbmcgbm9kZSBuYW1lcyB3aGljaCBhcHBlYXIgaW4gdGhlIHByb2Nlc3NlZAogICAgICAgICAqIGxpc3Qgb2YgcmF3IG5vZGVzLiBIZXJlIHdlIHByZS1hbGxvY2F0ZSBlbm91Z2ggcm9vbSBmb3IgYWxsIHRoZSByYXdOb2RlcywKICAgICAgICAgKiBldmVuIHRob3VnaCB0aGVyZSB3aWxsIHNvbWUgbnVtYmVyIG9mIGVtYmVkZGluZ3MuIFRoZSBleGNlc3MgYXJyYXkgbGVuZ3RoCiAgICAgICAgICogaXMgc3BsaWNlZCBvZmYgbGF0ZXIuCiAgICAgICAgICoKICAgICAgICAgKiBFeHBlcmltZW50YXRpb24gc2hvd3MgdGhhdCBhcm91bmQgMzAlIG9mIHRoZSBhcnJheSB3aWxsIGdvIHVudXNlZCwgYW5kCiAgICAgICAgICogZXZlbiBmb3IgdmVyeSBsYXJnZSBuZXR3b3JrcyB0aGF0IGFtb3VudHMgdG8gbGVzcyB0aGFuIDEwayBzcGFjZXMuCiAgICAgICAgICovCiAgICAgICAgbGV0IG5vZGVOYW1lcyA9IG5ldyBBcnJheShyYXdOb2Rlcy5sZW5ndGgpOwogICAgICAgIHJldHVybiBydW5Bc3luY1Rhc2soJ05vcm1hbGl6aW5nIG5hbWVzJywgMzAsICgpID0+IHsKICAgICAgICAgICAgbGV0IG9wTm9kZXMgPSBuZXcgQXJyYXkocmF3Tm9kZXMubGVuZ3RoKTsKICAgICAgICAgICAgbGV0IGluZGV4ID0gMDsKICAgICAgICAgICAgY29uc3QgcHJvY2Vzc1Jhd05vZGUgPSAocmF3Tm9kZSkgPT4gewogICAgICAgICAgICAgICAgbGV0IG9wTm9kZSA9IG5ldyBPcE5vZGVJbXBsKHJhd05vZGUpOwogICAgICAgICAgICAgICAgaWYgKGlzSW5FbWJlZGRlZFByZWQob3BOb2RlKSkgewogICAgICAgICAgICAgICAgICAgIGVtYmVkZGluZ05vZGVOYW1lcy5wdXNoKG9wTm9kZS5uYW1lKTsKICAgICAgICAgICAgICAgICAgICBpbkVtYmVkZGluZ1tvcE5vZGUubmFtZV0gPSBvcE5vZGU7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9wTm9kZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChpc091dEVtYmVkZGVkUHJlZChvcE5vZGUpKSB7CiAgICAgICAgICAgICAgICAgICAgZW1iZWRkaW5nTm9kZU5hbWVzLnB1c2gob3BOb2RlLm5hbWUpOwogICAgICAgICAgICAgICAgICAgIG91dEVtYmVkZGluZ1tvcE5vZGUubmFtZV0gPSBvcE5vZGU7CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlLmlucHV0cywgKGlucHV0KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIGxldCBpbnB1dE5hbWUgPSBpbnB1dC5uYW1lOwogICAgICAgICAgICAgICAgICAgICAgICBvdXRFbWJlZGRpbmdzW2lucHV0TmFtZV0gPSBvdXRFbWJlZGRpbmdzW2lucHV0TmFtZV0gfHwgW107CiAgICAgICAgICAgICAgICAgICAgICAgIG91dEVtYmVkZGluZ3NbaW5wdXROYW1lXS5wdXNoKG9wTm9kZSk7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG9wTm9kZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFRoZSBub2RlIGlzIG5vdCBhbiBlbWJlZGRpbmcsIHNvIGFkZCBpdCB0byB0aGUgbmFtZXMgYW5kIG5vZGVzCiAgICAgICAgICAgICAgICAvLyBsaXN0cy4KICAgICAgICAgICAgICAgIG9wTm9kZXNbaW5kZXhdID0gb3BOb2RlOwogICAgICAgICAgICAgICAgbm9kZU5hbWVzW2luZGV4XSA9IG9wTm9kZS5uYW1lOwogICAgICAgICAgICAgICAgaW5kZXgrKzsKICAgICAgICAgICAgICAgIHJldHVybiBvcE5vZGU7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKHJhd05vZGVzLCBwcm9jZXNzUmF3Tm9kZSk7CiAgICAgICAgICAgIGNvbnN0IHByb2Nlc3NGdW5jdGlvbiA9IChmdW5jKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBHaXZlIHRoZSBmdW5jdGlvbiBpdHNlbGYgYSBub2RlLgogICAgICAgICAgICAgICAgY29uc3QgZnVuY3Rpb25Ob2RlTmFtZSA9IEZVTkNUSU9OX0xJQlJBUllfTk9ERV9QUkVGSVggKyBmdW5jLnNpZ25hdHVyZS5uYW1lOwogICAgICAgICAgICAgICAgLy8gQ3JlYXRlIGFuIG9wIG5vZGUgZm9yIHRoZSBmdW5jdGlvbi4gTWFyayBpdCBhcyBwYXJ0IG9mIGEKICAgICAgICAgICAgICAgIC8vIGZ1bmN0aW9uIGxpYnJhcnkuCiAgICAgICAgICAgICAgICBwcm9jZXNzUmF3Tm9kZSh7CiAgICAgICAgICAgICAgICAgICAgbmFtZTogZnVuY3Rpb25Ob2RlTmFtZSwKICAgICAgICAgICAgICAgICAgICBpbnB1dDogW10sCiAgICAgICAgICAgICAgICAgICAgZGV2aWNlOiAnJywKICAgICAgICAgICAgICAgICAgICBvcDogJycsCiAgICAgICAgICAgICAgICAgICAgYXR0cjogW10sCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIC8vIElmIHRoZSBmdW5jdGlvbiBoYXMgaW5wdXRzLCBtYWtlIG5vZGVzIG91dCBvZiB0aGVtLgogICAgICAgICAgICAgICAgaWYgKGZ1bmMuc2lnbmF0dXJlLmlucHV0X2FyZykgewogICAgICAgICAgICAgICAgICAgIC8vIE1ha2VzIGFuIE9wTm9kZSBvdXQgb2YgZWl0aGVyIGFuIGlucHV0X2FyZyBvZiBhIGxpYnJhcnkKICAgICAgICAgICAgICAgICAgICAvLyBmdW5jdGlvbi4KICAgICAgICAgICAgICAgICAgICBsZXQgY3VycmVudElucHV0SW5kZXggPSAwOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHByb2Nlc3NJbnB1dCA9IChhcmcpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgb3BOb2RlID0gcHJvY2Vzc1Jhd05vZGUoewogICAgICAgICAgICAgICAgICAgICAgICAgICAgbmFtZTogZnVuY3Rpb25Ob2RlTmFtZSArIE5BTUVTUEFDRV9ERUxJTSArIGFyZy5uYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5wdXQ6IFtdLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgZGV2aWNlOiAnJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wOiAnaW5wdXRfYXJnJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGF0dHI6IFsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGtleTogJ1QnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdHlwZTogYXJnLnR5cGUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIF0sCiAgICAgICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgICAgICAgICBvcE5vZGUuZnVuY3Rpb25JbnB1dEluZGV4ID0gY3VycmVudElucHV0SW5kZXg7CiAgICAgICAgICAgICAgICAgICAgICAgIGN1cnJlbnRJbnB1dEluZGV4Kys7CiAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICAvLyBNYWtlIG5vZGVzIGZvciBpbnB1dCBhcmdzIG9mIHRoZSBmdW5jdGlvbi4gVW5mb3J0dW5hdGVseSwgdGhlCiAgICAgICAgICAgICAgICAgICAgLy8gcGJ0eHQgY29uZmlndXJhdGlvbiBsYW5ndWFnZSBpcyBub3QgcmljaCBlbm91Z2ggdG8KICAgICAgICAgICAgICAgICAgICAvLyBkaWZmZXJlbnRpYXRlIGJldHdlZW4gYW4gYXJyYXkgd2l0aCAxIGl0ZW0gdnMgMSBvYmplY3QKICAgICAgICAgICAgICAgICAgICAvLyBwcm9wZXJ0eS4KICAgICAgICAgICAgICAgICAgICBpZiAoZnVuYy5zaWduYXR1cmUuaW5wdXRfYXJnWyduYW1lJ10pIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhlcmUgaXMgb25seSAxIGlucHV0IGFyZy4KICAgICAgICAgICAgICAgICAgICAgICAgcHJvY2Vzc0lucHV0KGZ1bmMuc2lnbmF0dXJlLmlucHV0X2FyZyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBUaGVyZSBhcmUgc2V2ZXJhbCBpbnB1dCBhcmdzLgogICAgICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChmdW5jLnNpZ25hdHVyZS5pbnB1dF9hcmcsIHByb2Nlc3NJbnB1dCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gTWFrZSBub2RlcyBmb3Igb3V0cHV0IGFyZ3Mgb2YgdGhlIGZ1bmN0aW9uLiBUcmFjayB0aGUgbmFtZXMgb2YKICAgICAgICAgICAgICAgIC8vIG91dHB1dCBhcmdzIHdpdGhpbiB0aGUga2V5cyBvZiB0aGlzIG9iamVjdC4gVW5saWtlIHRoZQogICAgICAgICAgICAgICAgLy8gaW5wdXRfYXJncywgdGhlIG91dHB1dF9hcmdzIGFyZSBhbHJlYWR5IGRlZmluZWQgd2l0aGluIHRoZQogICAgICAgICAgICAgICAgLy8gbm9kZV9kZWZzIG9mIHRoZSBsaWJyYXJ5IGZ1bmN0aW9uLgogICAgICAgICAgICAgICAgbGV0IGN1cnJlbnRPdXRwdXRJbmRleCA9IDA7CiAgICAgICAgICAgICAgICBjb25zdCBvdXRwdXRBcmdOYW1lcyA9IHt9OwogICAgICAgICAgICAgICAgLy8gSWYgdGhlIGZ1bmN0aW9uIGhhcyBvdXRwdXRzLCBtYWtlIG5vZGVzIG91dCBvZiB0aGVtLgogICAgICAgICAgICAgICAgaWYgKGZ1bmMuc2lnbmF0dXJlLm91dHB1dF9hcmcpIHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBwcm9jZXNzT3V0cHV0ID0gKGFyZykgPT4gewogICAgICAgICAgICAgICAgICAgICAgICBvdXRwdXRBcmdOYW1lc1tmdW5jdGlvbk5vZGVOYW1lICsgTkFNRVNQQUNFX0RFTElNICsgYXJnLm5hbWVdID0gY3VycmVudE91dHB1dEluZGV4OwogICAgICAgICAgICAgICAgICAgICAgICBjdXJyZW50T3V0cHV0SW5kZXgrKzsKICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgICAgIGlmIChmdW5jLnNpZ25hdHVyZS5vdXRwdXRfYXJnWyduYW1lJ10pIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhlcmUgaXMgb25seSAxIG91dHB1dCBhcmcuCiAgICAgICAgICAgICAgICAgICAgICAgIHByb2Nlc3NPdXRwdXQoZnVuYy5zaWduYXR1cmUub3V0cHV0X2FyZyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBUaGVyZSBhcmUgc2V2ZXJhbCBvdXRwdXQgYXJncy4KICAgICAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmVhY2goZnVuYy5zaWduYXR1cmUub3V0cHV0X2FyZywgcHJvY2Vzc091dHB1dCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2goZnVuYy5ub2RlX2RlZiwgKHJhd05vZGUpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBQcmVmaXggd2l0aCB0aGUgbmFtZSBvZiB0aGUgZnVuY3Rpb24gc28gdGhhdCB0aGUgZ3JhcGgKICAgICAgICAgICAgICAgICAgICAvLyBjb3JyZWN0bHkgY29tcHV0ZXMgdGhlIGhpZXJhcmNoeSAoYW5kIG1ha2VzIG1ldGFub2RlcykuCiAgICAgICAgICAgICAgICAgICAgcmF3Tm9kZS5uYW1lID0gZnVuY3Rpb25Ob2RlTmFtZSArICcvJyArIHJhd05vZGUubmFtZTsKICAgICAgICAgICAgICAgICAgICBpZiAodHlwZW9mIHJhd05vZGUuaW5wdXQgPT09ICdzdHJpbmcnKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJhd05vZGUuaW5wdXQgPSBbcmF3Tm9kZS5pbnB1dF07CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9wTm9kZSA9IHByb2Nlc3NSYXdOb2RlKHJhd05vZGUpOwogICAgICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNOdW1iZXIob3V0cHV0QXJnTmFtZXNbcmF3Tm9kZS5uYW1lXSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gTWFyayB0aGUgbm9kZSBhcyBvbmUgb2YgdGhlIG91dHB1dHMgb2YgdGhlIGZ1bmN0aW9uLgogICAgICAgICAgICAgICAgICAgICAgICBvcE5vZGUuZnVuY3Rpb25PdXRwdXRJbmRleCA9IG91dHB1dEFyZ05hbWVzW3Jhd05vZGUubmFtZV07CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKG9wTm9kZS5pbnB1dHMsIChub3JtYWxpemVkSW5wdXQpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZElucHV0Lm5hbWUgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb25Ob2RlTmFtZSArIE5BTUVTUEFDRV9ERUxJTSArIG5vcm1hbGl6ZWRJbnB1dC5uYW1lOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGlmIChncmFwaERlZi5saWJyYXJ5ICYmIGdyYXBoRGVmLmxpYnJhcnkuZnVuY3Rpb24pIHsKICAgICAgICAgICAgICAgIC8vIFRoaXMgZ3JhcGggY29udGFpbnMgZnVuY3Rpb25zLgogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGhEZWYubGlicmFyeS5mdW5jdGlvbiwgcHJvY2Vzc0Z1bmN0aW9uKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBvcE5vZGVzLnNwbGljZShpbmRleCk7CiAgICAgICAgICAgIG5vZGVOYW1lcy5zcGxpY2UoaW5kZXgpOwogICAgICAgICAgICByZXR1cm4gb3BOb2RlczsKICAgICAgICB9LCB0cmFja2VyKQogICAgICAgICAgICAudGhlbigob3BOb2RlcykgPT4gewogICAgICAgICAgICAvLyBDcmVhdGUgdGhlIGdyYXBoIGRhdGEgc3RydWN0dXJlIGZyb20gdGhlIGdyYXBobGliIGxpYnJhcnkuCiAgICAgICAgICAgIHJldHVybiBydW5Bc3luY1Rhc2soJ0J1aWxkaW5nIHRoZSBkYXRhIHN0cnVjdHVyZScsIDcwLCAoKSA9PiB7CiAgICAgICAgICAgICAgICBsZXQgbm9ybWFsaXplZE5hbWVEaWN0ID0gbWFwU3RyaWN0SGllcmFyY2h5KG5vZGVOYW1lcywgZW1iZWRkaW5nTm9kZU5hbWVzKTsKICAgICAgICAgICAgICAgIGxldCBncmFwaCA9IG5ldyBTbGltR3JhcGgoKTsKICAgICAgICAgICAgICAgIC8vIEFkZCB0aGUgbm9kZXMgdG8gdGhlIGdyYXBoLgogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlcywgKG9wTm9kZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGxldCBub3JtYWxpemVkTmFtZSA9IG5vcm1hbGl6ZWROYW1lRGljdFtvcE5vZGUubmFtZV0gfHwgb3BOb2RlLm5hbWU7CiAgICAgICAgICAgICAgICAgICAgZ3JhcGgubm9kZXNbbm9ybWFsaXplZE5hbWVdID0gb3BOb2RlOwogICAgICAgICAgICAgICAgICAgIC8vIENoZWNrIGlmIHRoZSBub2RlIGhhcyBvdXQtZW1iZWRkaW5ncy4gSWYgeWVzLCBhZGQgdGhlbSB0byB0aGUKICAgICAgICAgICAgICAgICAgICAvLyBub2RlLgogICAgICAgICAgICAgICAgICAgIGlmIChvcE5vZGUubmFtZSBpbiBvdXRFbWJlZGRpbmdzKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIG9wTm9kZS5vdXRFbWJlZGRpbmdzID0gb3V0RW1iZWRkaW5nc1tvcE5vZGUubmFtZV07CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIE5vcm1hbGl6ZSB0aGUgbmFtZXMgb2YgdGhlIG91dC1lbWJlZGRpbmdzLgogICAgICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChvcE5vZGUub3V0RW1iZWRkaW5ncywgKG5vZGUpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5vZGUubmFtZSA9IG5vcm1hbGl6ZWROYW1lRGljdFtub2RlLm5hbWVdIHx8IG5vZGUubmFtZTsKICAgICAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgbmFtZSBvZiB0aGUgbm9kZS4KICAgICAgICAgICAgICAgICAgICBvcE5vZGUubmFtZSA9IG5vcm1hbGl6ZWROYW1lOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAvLyBWaXNpdCBlYWNoIG5vZGUncyBpbnB1dHMgdG8gYWRkIHRoZSBlZGdlcyB0byB0aGUgZ3JhcGguIElmIHRoZQogICAgICAgICAgICAgICAgLy8gaW5wdXQKICAgICAgICAgICAgICAgIC8vIGlzIGFuIGluLWVtYmVkZGluZywgdGhlbiBhZGQgaXQgdG8gdGhlIG5vZGUncyBpbi1lbWJlZGRpbmdzCiAgICAgICAgICAgICAgICAvLyBpbnN0ZWFkLgogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlcywgKG9wTm9kZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKG9wTm9kZS5pbnB1dHMsIChpbnB1dCwgaSkgPT4gewogICAgICAgICAgICAgICAgICAgICAgICBsZXQgaW5wdXROYW1lID0gaW5wdXQubmFtZTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0TmFtZSBpbiBpbkVtYmVkZGluZykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGluRW1iZWROb2RlID0gaW5FbWJlZGRpbmdbaW5wdXROYW1lXTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9wTm9kZS5pbkVtYmVkZGluZ3MucHVzaChpbkVtYmVkTm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBNb3ZlIHRoZSBpbnB1dHMgb2YgdGhlIGluLWVtYmVkZGluZyBub2RlIGludG8gaW5jb21pbmcKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIGVkZ2VzIG9mCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyB0aGUgbWFpbiBub2RlLiBFLmcuIHRoZSBjb250cm9sIGRlcGVuZGVuY3kgb2YgYSBjb25zdGFudAogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gbm9kZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gc2hvdWxkIGJlIG1vdmVkIHRvIHRoZSBvcCBub2RlIHdoZXJlIHRoZSBjb25zdGFudCBpcwogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gZW1iZWRkZWQuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGxldCBlbWJlZElucHV0IG9mIGluRW1iZWROb2RlLmlucHV0cykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGFkZEVkZ2VUb0dyYXBoKGdyYXBoLCBub3JtYWxpemVkTmFtZURpY3RbZW1iZWRJbnB1dC5uYW1lXSB8fCBlbWJlZElucHV0Lm5hbWUsIG9wTm9kZSwgZW1iZWRJbnB1dCwgcGFyYW1zLCBpKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICBlbHNlIGlmIChpbnB1dE5hbWUgaW4gb3V0RW1iZWRkaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBNb3ZlIHRoZSBpbnB1dHMgb2YgdGhlIG91dC1lbWJlZGRpbmcgbm9kZSBpbnRvIGlucHV0cyBvZgogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gdGhlIG1haW4gbm9kZSB3aGVyZSB0aGUgb3V0LWVtYmVkZGluZyBwb2ludHMgdG8uCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBsZXQgb3V0RW1iZWROb2RlID0gb3V0RW1iZWRkaW5nW2lucHV0TmFtZV07CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBmb3IgKGxldCBlbWJlZElucHV0IG9mIG91dEVtYmVkTm9kZS5pbnB1dHMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBhZGRFZGdlVG9HcmFwaChncmFwaCwgbm9ybWFsaXplZE5hbWVEaWN0W2VtYmVkSW5wdXQubmFtZV0gfHwgZW1iZWRJbnB1dC5uYW1lLCBvcE5vZGUsIGlucHV0LCBwYXJhbXMsIGkpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgYWRkRWRnZVRvR3JhcGgoZ3JhcGgsIG5vcm1hbGl6ZWROYW1lRGljdFtpbnB1dE5hbWVdIHx8IGlucHV0TmFtZSwgb3BOb2RlLCBpbnB1dCwgcGFyYW1zLCBpKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAvLyBOb3JtYWxpemUgdGhlIG5hbWVzIG9mIGluLWVtYmVkZGluZ3MuCiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChpbkVtYmVkZGluZywgKG5vZGUsIG5hbWUpID0+IHsKICAgICAgICAgICAgICAgICAgICBub2RlLm5hbWUgPSBub3JtYWxpemVkTmFtZURpY3Rbbm9kZS5uYW1lXSB8fCBub2RlLm5hbWU7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHJldHVybiBncmFwaDsKICAgICAgICAgICAgfSwgdHJhY2tlcik7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIENyZWF0ZSBhIG5ldyBncmFwaGxpYi5HcmFwaCgpIGluc3RhbmNlIHdpdGggZGVmYXVsdCBwYXJhbWV0ZXJzCiAgICAgKi8KICAgIGZ1bmN0aW9uIGNyZWF0ZUdyYXBoKG5hbWUsIHR5cGUsIG9wdCkgewogICAgICAgIGNvbnN0IGdyYXBoT3B0aW9ucyA9IG9wdCB8fCB7fTsKICAgICAgICBsZXQgZ3JhcGggPSBuZXcgZGFncmUuZ3JhcGhsaWIuR3JhcGgoZ3JhcGhPcHRpb25zKTsKICAgICAgICBncmFwaC5zZXRHcmFwaCh7CiAgICAgICAgICAgIG5hbWU6IG5hbWUsCiAgICAgICAgICAgIHJhbmtkaXI6IGdyYXBoT3B0aW9ucy5yYW5rZGlyIHx8ICdCVCcsCiAgICAgICAgICAgIHR5cGU6IHR5cGUsCiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIGdyYXBoOwogICAgfQogICAgLyoqCiAgICAgKiBDcmVhdGUgYSBwcmVkaWNhdGUgZm9yIGNoZWNraW5nIHdoZXRoZXIgYSBub2RlIHNob3VsZCBiZSBlbWJlZGRlZCBiYXNlZCBvbgogICAgICogdGhlIHNwZWNpZmllZCB0eXBlcy4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0RW1iZWRQcmVkaWNhdGUodHlwZXMpIHsKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKG5vZGUpIHsKICAgICAgICAgICAgLy8gY2hlY2sgdHlwZXMKICAgICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCB0eXBlcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgbGV0IHJlZ0V4cCA9IG5ldyBSZWdFeHAodHlwZXNbaV0pOwogICAgICAgICAgICAgICAgaWYgKHR5cGVvZiBub2RlLm9wID09PSAnc3RyaW5nJyAmJiBub2RlLm9wLm1hdGNoKHJlZ0V4cCkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBhIHN0cmljdCBub2RlIG5hbWUgKG5hbWUgPT4gbmFtZS8obmFtZSkpIHRvIGF2b2lkIGNvbmZsaWN0cwogICAgICogd2hlcmUgdGhlIG5vZGUgbmFtZSBpcyBhbHNvIGEgbmFtZXNwYWNlLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRTdHJpY3ROYW1lKG5hbWUpIHsKICAgICAgICBsZXQgcGFydHMgPSBuYW1lLnNwbGl0KE5BTUVTUEFDRV9ERUxJTSk7CiAgICAgICAgcmV0dXJuIG5hbWUgKyBOQU1FU1BBQ0VfREVMSU0gKyAnKCcgKyBwYXJ0c1twYXJ0cy5sZW5ndGggLSAxXSArICcpJzsKICAgIH0KICAgIC8qKgogICAgICogRm9yIGVhY2ggb3Agbm9kZSAoZW1iZWRkaW5nIG9yIG5vbi1lbWJlZGRpbmcpLCByZW5hbWUgaXQgaWYgdGhlcmUgaXMgYQogICAgICogbm9uLWVtYmVkZGluZyBub2RlIHVuZGVyIGl0cyBuYW1lc3BhY2UuIEZvciBleGFtcGxlLCBhc3N1bWUgbm9kZSBuYW1lICdBJy4KICAgICAqIElmIHRoZXJlIGlzIGEgbm9uLWVtYmVkZGluZyBub2RlIHVuZGVyIGl0cyBuYW1lc3BhY2UgKGUuZy4gJ0EvQicpLCAnQScgd2lsbAogICAgICogYmUgcmVuYW1lZCB0byAnQS8oQSknLiBUaGVuIHRoZSBuYW1lc3BhY2UgJ0EnIHdpbGwgY29udGFpbiAyIG5vZGVzOiAnKEEpJwogICAgICogYW5kICdCJy4gSWYgYWxsIHRoZSBub2RlcyB1bmRlciAnQScgYXJlIGVtYmVkZGluZyBub2RlcyAoZS5nLiBjb25zdGFudCBhbmQKICAgICAqIHN1bW1hcnkpLCBrZWVwICdBJyBhcyBhbiBPcCBub2RlIGFuZCBkb24ndCBjcmVhdGUgYSBuYW1lc3BhY2UuCiAgICAgKgogICAgICogQHBhcmFtIG5vZGVOYW1lcyBBbiBhcnJheSBvZiByZWd1bGFyIChub24tZW1iZWRkaW5nKSBub2RlIG5hbWVzLgogICAgICogQHBhcmFtIGVtYmVkZGluZ05vZGVOYW1lcyBBbiBhcnJheSBvZiBlbWJlZGRpbmcgbm9kZSBuYW1lcy4KICAgICAqIEByZXR1cm4gRGljdGlvbmFyeSBvYmplY3QgbWFwcGluZyBuYW1lcyB0aGF0IG5lZWQgdG8gYmUgcmVuYW1lZCB0bwogICAgICogICAgIG5ldyBuYW1lcy4KICAgICAqLwogICAgZnVuY3Rpb24gbWFwU3RyaWN0SGllcmFyY2h5KG5vZGVOYW1lcywgZW1iZWRkaW5nTm9kZU5hbWVzKSB7CiAgICAgICAgLyoqIERpY3Rpb25hcnkgdGhhdCBtYXBzIHRoZSBvbGQgbmV3IHRvIHRoZSBuZXcgbmFtZSAqLwogICAgICAgIGxldCBuZXdOYW1lRGljdGlvbmFyeSA9IHt9OwogICAgICAgIC8qKiBTZXQgdXNlZCB0byBzdG9yZSBhbGwgbmFtZXNwYWNlcy4gKi8KICAgICAgICBsZXQgbmFtZXNwYWNlU2V0ID0ge307CiAgICAgICAgLy8gc29ydCB0aGUgbm9kZXMgdG8gbWFrZSBwcmVmaXggY2hlY2sgZmFzdGVyCiAgICAgICAgbm9kZU5hbWVzLnNvcnQoKTsKICAgICAgICAvLyBsb29rIGZvciBub2RlcyB3aXRoIGEgcHJlZml4IGEsYS9iIC0+IGEvKGEpLGEvYgogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgbm9kZU5hbWVzLmxlbmd0aCAtIDE7ICsraSkgewogICAgICAgICAgICBsZXQgYSA9IG5vZGVOYW1lc1tpXTsKICAgICAgICAgICAgLy8gR2V0IGFsbCB0aGUgcGFyZW50IG5hbWVzcGFjZXMgb2YgdGhlIGN1cnJlbnQgbm9kZQogICAgICAgICAgICAvLyBhbmQgYWRkIHRoZW0gaW4gdGhlIG5hbWVzcGFjZSBzZXQuCiAgICAgICAgICAgIGxvZGFzaC5lYWNoKGdldEhpZXJhcmNoaWNhbFBhdGgoYSkuc2xpY2UoMCwgLTEpLCAobnMpID0+IHsKICAgICAgICAgICAgICAgIG5hbWVzcGFjZVNldFtuc10gPSB0cnVlOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgZm9yIChsZXQgaiA9IGkgKyAxOyBqIDwgbm9kZU5hbWVzLmxlbmd0aDsgKytqKSB7CiAgICAgICAgICAgICAgICBsZXQgYiA9IG5vZGVOYW1lc1tqXTsKICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guc3RhcnRzV2l0aChiLCBhKSkgewogICAgICAgICAgICAgICAgICAgIGlmIChiLmxlbmd0aCA+IGEubGVuZ3RoICYmIGIuY2hhckF0KGEubGVuZ3RoKSA9PT0gTkFNRVNQQUNFX0RFTElNKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIG5ld05hbWVEaWN0aW9uYXJ5W2FdID0gZ2V0U3RyaWN0TmFtZShhKTsKICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gR28gdGhyb3VnaCBhbGwgdGhlIGVtYmVkZGluZyBub2RlIG5hbWVzIGFuZCByZW5hbWUgdGhlbSBpbiBjYXNlIHRoZXkKICAgICAgICAvLyBjb2xsaWRlIHdpdGggbmFtZXNwYWNlcy4KICAgICAgICBsb2Rhc2guZWFjaChlbWJlZGRpbmdOb2RlTmFtZXMsIChlbWJlZGRpbmdOYW1lKSA9PiB7CiAgICAgICAgICAgIGlmIChlbWJlZGRpbmdOYW1lIGluIG5hbWVzcGFjZVNldCkgewogICAgICAgICAgICAgICAgLy8gUmVuYW1lIHRvIGZvbGxvdyBzdHJpY3QgaGllcmFyY2h5LgogICAgICAgICAgICAgICAgbmV3TmFtZURpY3Rpb25hcnlbZW1iZWRkaW5nTmFtZV0gPSBnZXRTdHJpY3ROYW1lKGVtYmVkZGluZ05hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIG5ld05hbWVEaWN0aW9uYXJ5OwogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm5zIGEgbGlzdCBvZiB0aGUgZGVncmVlcyBvZiBlYWNoIG5vZGUgaW4gdGhlIGdyYXBoLgogICAgICovCiAgICBmdW5jdGlvbiBkZWdyZWVTZXF1ZW5jZShncmFwaCkgewogICAgICAgIGxldCBkZWdyZWVzID0gZ3JhcGgubm9kZXMoKS5tYXAoZnVuY3Rpb24gKG5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIGdyYXBoLm5laWdoYm9ycyhuYW1lKS5sZW5ndGg7CiAgICAgICAgfSk7CiAgICAgICAgZGVncmVlcy5zb3J0KCk7CiAgICAgICAgcmV0dXJuIGRlZ3JlZXM7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgaWYgdGhlIGRlZ3JlZSBzZXF1ZW5jZSBvZiB0aGUgdHdvIGdyYXBocyBpcyB0aGUgc2FtZS4KICAgICAqLwogICAgZnVuY3Rpb24gaGFzU2ltaWxhckRlZ3JlZVNlcXVlbmNlKGdyYXBoMSwgZ3JhcGgyKSB7CiAgICAgICAgbGV0IGRnMSA9IGRlZ3JlZVNlcXVlbmNlKGdyYXBoMSk7CiAgICAgICAgbGV0IGRnMiA9IGRlZ3JlZVNlcXVlbmNlKGdyYXBoMik7CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBkZzEubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgaWYgKGRnMVtpXSAhPT0gZGcyW2ldKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGhpZXJhcmNoaWNhbCBwYXRoIG9mIHRoZSBjdXJyZW50IG5vZGUsIGJhc2VkIG9uIHRoZSBub2RlJ3MgbmFtZS4KICAgICAqIEZvciBleGFtcGxlLCBpZiB0aGUgbmFtZSBpcyAnYS9iL2MnLCB0aGUgcmV0dXJuZWQgcGF0aCBpcwogICAgICogWydhJywgJ2EvYicsICdhL2IvYyddLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRIaWVyYXJjaGljYWxQYXRoKG5hbWUsIHNlcmllc05hbWVzKSB7CiAgICAgICAgbGV0IHBhdGggPSBbXTsKICAgICAgICBsZXQgaSA9IG5hbWUuaW5kZXhPZihOQU1FU1BBQ0VfREVMSU0pOwogICAgICAgIC8vIFB1c2ggYWxsIHBhcmVudCBwb3J0aW9ucyBvZiB0aGUgcGF0aC4KICAgICAgICB3aGlsZSAoaSA+PSAwKSB7CiAgICAgICAgICAgIHBhdGgucHVzaChuYW1lLnN1YnN0cmluZygwLCBpKSk7CiAgICAgICAgICAgIGkgPSBuYW1lLmluZGV4T2YoTkFNRVNQQUNFX0RFTElNLCBpICsgMSk7CiAgICAgICAgfQogICAgICAgIC8vIElmIHRoZSBub2RlJ3MgcGF0aCBpcyB1bmRlciBhIHNlcmllcywgdGhlbiBhZGQgdGhlIHNlcmllcyBub2RlIG5hbWUgdG8gdGhlCiAgICAgICAgLy8gaGllcmFyY2hpY2FsIHBhdGggYXMgdGhlIHBhcmVudCBvZiB0aGUgbGVhZi4KICAgICAgICBpZiAoc2VyaWVzTmFtZXMpIHsKICAgICAgICAgICAgbGV0IHNlcmllc05hbWUgPSBzZXJpZXNOYW1lc1tuYW1lXTsKICAgICAgICAgICAgaWYgKHNlcmllc05hbWUpIHsKICAgICAgICAgICAgICAgIHBhdGgucHVzaChzZXJpZXNOYW1lKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvLyBQdXNoIHRoZSBsZWFmIG9mIHRoZSBwYXRoLgogICAgICAgIHBhdGgucHVzaChuYW1lKTsKICAgICAgICByZXR1cm4gcGF0aDsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgc3RyaW5nIGZvciB0aGUgbm9kZSBpbmNsdXNpb24gdG9nZ2xlIGJ1dHRvbiwgZGVwZW5kYW50CiAgICAgKiBvbiB0aGUgcHJvdmlkZWQgY3VycmVudCBJbmNsdXNpb25UeXBlLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRJbmNsdWRlTm9kZUJ1dHRvblN0cmluZyhpbmNsdWRlKSB7CiAgICAgICAgaWYgKGluY2x1ZGUgPT09IEluY2x1c2lvblR5cGUuRVhDTFVERSkgewogICAgICAgICAgICByZXR1cm4gJ0FkZCB0byBtYWluIGdyYXBoJzsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHJldHVybiAnUmVtb3ZlIGZyb20gbWFpbiBncmFwaCc7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBSZXR1cm5zIHRoZSBzdHJpbmcgZm9yIHRoZSBzZXJpZXMgbm9kZSBncm91cGluZyB0b2dnbGUgYnV0dG9uLCBkZXBlbmRhbnQKICAgICAqIG9uIHRoZSBwcm92aWRlZCBjdXJyZW50IFNlcmllc0dyb3VwaW5nVHlwZS4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0R3JvdXBTZXJpZXNOb2RlQnV0dG9uU3RyaW5nKGdyb3VwKSB7CiAgICAgICAgaWYgKGdyb3VwID09PSBTZXJpZXNHcm91cGluZ1R5cGUuR1JPVVApIHsKICAgICAgICAgICAgcmV0dXJuICdVbmdyb3VwIHRoaXMgc2VyaWVzIG9mIG5vZGVzJzsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHJldHVybiAnR3JvdXAgdGhpcyBzZXJpZXMgb2Ygbm9kZXMnOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogVG9nZ2xlIHRoZSBub2RlIHNlcmllcyBncm91cGluZyBvcHRpb24gaW4gdGhlIHByb3ZpZGVkIG1hcCwgc2V0dGluZyBpdAogICAgICogdG8gdW5ncm91cCBpZiB0aGUgc2VyaWVzIGlzIG5vdCBhbHJlYWR5IGluIHRoZSBtYXAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHRvZ2dsZU5vZGVTZXJpZXNHcm91cChtYXAsIG5hbWUpIHsKICAgICAgICBpZiAoIShuYW1lIGluIG1hcCkgfHwgbWFwW25hbWVdID09PSBTZXJpZXNHcm91cGluZ1R5cGUuR1JPVVApIHsKICAgICAgICAgICAgbWFwW25hbWVdID0gU2VyaWVzR3JvdXBpbmdUeXBlLlVOR1JPVVA7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBtYXBbbmFtZV0gPSBTZXJpZXNHcm91cGluZ1R5cGUuR1JPVVA7CiAgICAgICAgfQogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE1IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICdMaWNlbnNlJyk7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gJ0FTIElTJyBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBDb2xvciBwYXJhbWV0ZXJzIGZvciBvcCBub2Rlcy4KICAgICAqLwogICAgbGV0IE9wTm9kZUNvbG9ycyA9IHsKICAgICAgICBERUZBVUxUX0ZJTEw6ICcjZmZmZmZmJywKICAgICAgICBERUZBVUxUX1NUUk9LRTogJyNiMmIyYjInLAogICAgICAgIENPTVBBVElCTEU6ICcjMGY5ZDU4JywKICAgICAgICBJTkNPTVBBVElCTEU6ICcjZGI0NDM3JywKICAgIH07CiAgICAvKioKICAgICAqIENvbG9yIHBhcmFtZXRlcnMgZm9yIG5vZGUgZW5jb2RpbmcuCiAgICAgKiBAdHlwZSB7T2JqZWN0fQogICAgICovCiAgICBsZXQgTWV0YW5vZGVDb2xvcnMgPSB7CiAgICAgICAgLyoqCiAgICAgICAgICogRGVmYXVsdCBmaWxsIGFuZCBzdHJva2UgdG8gdXNlIHdoZW4gbm8gb3RoZXIgaW5mb3JtYXRpb24gaXMgYXZhaWxhYmxlLgogICAgICAgICAqLwogICAgICAgIERFRkFVTFRfRklMTDogJyNkOWQ5ZDknLAogICAgICAgIERFRkFVTFRfU1RST0tFOiAnI2E2YTZhNicsCiAgICAgICAgU0FUVVJBVElPTjogMC42LAogICAgICAgIExJR0hUTkVTUzogMC44NSwKICAgICAgICAvKioKICAgICAgICAgKiBOZXV0cmFsIGNvbG9yIHRvIHVzZSB3aGVuIHRoZSBub2RlIGlzIGV4cGFuZGVkICh1c2VkIHdoZW4gY29sb3JpbmcgYnkKICAgICAgICAgKiBjb21wdXRlIHRpbWUsIG1lbW9yeSBhbmQgZGV2aWNlKS4KICAgICAgICAgKi8KICAgICAgICBFWFBBTkRFRF9DT0xPUjogJyNmMGYwZjAnLAogICAgICAgIC8qKgogICAgICAgICAqIFN0YW5kYXJkIGh1ZSB2YWx1ZXMgZm9yIG5vZGUgY29sb3IgcGFsZXR0ZS4KICAgICAgICAgKi8KICAgICAgICBIVUVTOiBbMjIwLCAxMDAsIDE4MCwgNDAsIDIwLCAzNDAsIDI2MCwgMzAwLCAxNDAsIDYwXSwKICAgICAgICBTVFJVQ1RVUkVfUEFMRVRURShpZCwgbGlnaHRlbmVkKSB7CiAgICAgICAgICAgIC8vIFRoZSBjb2RlIGJlbG93IGlzIGEgZmxleGlibGUgd2F5IHRvIGNvbXB1dGF0aW9uYWxseSBjcmVhdGUgYSBzZXQKICAgICAgICAgICAgLy8gb2YgY29sb3JzIHRoYXQgZ28gd2VsbCB0b2dldGhlci4KICAgICAgICAgICAgbGV0IGh1ZXMgPSBNZXRhbm9kZUNvbG9ycy5IVUVTOwogICAgICAgICAgICBsZXQgbiA9IGh1ZXMubGVuZ3RoOwogICAgICAgICAgICBsZXQgaHVlID0gaHVlc1tpZCAlIG5dOwogICAgICAgICAgICBsZXQgbSA9IE1hdGguc2luKChodWUgKiBNYXRoLlBJKSAvIDM2MCk7CiAgICAgICAgICAgIGxldCBzYXQgPSBsaWdodGVuZWQgPyAzMCA6IDkwIC0gNjAgKiBtOwogICAgICAgICAgICBsZXQgbGlnaHQgPSBsaWdodGVuZWQgPyA5NSA6IDgwOwogICAgICAgICAgICByZXR1cm4gaHNsKGh1ZSwgMC4wMSAqIHNhdCwgMC4wMSAqIGxpZ2h0KS50b1N0cmluZygpOwogICAgICAgIH0sCiAgICAgICAgREVWSUNFX1BBTEVUVEUoaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIE1ldGFub2RlQ29sb3JzLlNUUlVDVFVSRV9QQUxFVFRFKGluZGV4KTsKICAgICAgICB9LAogICAgICAgIFhMQV9DTFVTVEVSX1BBTEVUVEUoaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIE1ldGFub2RlQ29sb3JzLlNUUlVDVFVSRV9QQUxFVFRFKGluZGV4KTsKICAgICAgICB9LAogICAgICAgIFVOS05PV046ICcjZWVlJywKICAgICAgICBHUkFESUVOVF9PVVRMSU5FOiAnIzg4OCcsCiAgICB9OwogICAgLyoqCiAgICAgKiBDb2xvciBwYXJhbWV0ZXJzIGZvciBvcCBub2Rlcy4KICAgICAqLwogICAgbGV0IFNlcmllc05vZGVDb2xvcnMgPSB7CiAgICAgICAgREVGQVVMVF9GSUxMOiAnd2hpdGUnLAogICAgICAgIERFRkFVTFRfU1RST0tFOiAnI2IyYjJiMicsCiAgICB9OwogICAgLyoqCiAgICAgKiBQYXJhbWV0ZXJzIHRoYXQgYWZmZWN0IGhvdyB0aGUgZ3JhcGggaXMgcmVuZGVyZWQgb24gdGhlIHNjcmVlbi4KICAgICAqLwogICAgY29uc3QgUEFSQU1TID0gewogICAgICAgIC8qKgogICAgICAgICAqIFdoZXRoZXIgdG8gZXh0cmFjdCBoaWdoIGRlZ3JlZSBub2RlcyBmcm9tIHRoZSBjb3JlIHBhcnQgb2YgdGhlIGdyYXBoLgogICAgICAgICAqLwogICAgICAgIGVuYWJsZUV4dHJhY3Rpb246IHRydWUsCiAgICAgICAgLyoqCiAgICAgICAgICogVGhlIG1pbmltdW0gbnVtYmVyIG9mIG5vZGVzIGZvciBhIGdyYXBoIHRvIGhhdmUgaW4gb3JkZXIgZm9yIGhpZ2ggaW4gYW5kCiAgICAgICAgICogb3V0IGRlZ3JlZSBub2RlcyB0byBiZSBleHRyYWN0ZWQgaW4gYXV4aWxpYXJ5LiBUaGUgYWltIGhlcmUgaXMgdG8gcHJldmVudAogICAgICAgICAqIG5vZGVzIGZyb20gYmVpbmcgZXh0cmFjdGVkIGZyb20gc21hbGwgZ3JhcGhzLgogICAgICAgICAqLwogICAgICAgIG1pbk5vZGVDb3VudEZvckV4dHJhY3Rpb246IDE1LAogICAgICAgIC8qKgogICAgICAgICAqIFRoZSBtaW5pbXVtIGluIG9yIG91dCBkZWdyZWUgYSBub2RlIG11c3QgaGF2ZSBpbiBvcmRlciB0byBiZSBwb3NzaWJseQogICAgICAgICAqIGV4dHJhY3RlZC4KICAgICAgICAgKi8KICAgICAgICBtaW5EZWdyZWVGb3JFeHRyYWN0aW9uOiA1LAogICAgICAgIC8qKgogICAgICAgICAqIE1heGltdW0gbnVtYmVyIG9mIGNvbnRyb2wgZWRnZXMgYSBub2RlIGNhbiBoYXZlIGJlZm9yZSB0aGV5IGFyZW4ndAogICAgICAgICAqIGRpc3BsYXllZC4KICAgICAgICAgKi8KICAgICAgICBtYXhDb250cm9sRGVncmVlOiA0LAogICAgICAgIC8qKgogICAgICAgICAqIE1heGltdW0gaW4gKGZvciBvdXRib3VuZCBicmlkZ2UgcGF0aHMpIG9yIG91dCAoZm9yIGluYm91bmQgYnJpZGdlIHBhdGhzKQogICAgICAgICAqIGRlZ3JlZSBvZiBhIG5vZGUgYWxsb3dlZCBmb3IgYSBicmlkZ2UgcGF0aCB0byBiZSByZW5kZXJlZCB0byBpdCBmcm9tIGEKICAgICAgICAgKiBzdWJoaWVyYXJjaHkgb2Ygbm9kZXMuIEhhdmluZyBhIG1heCBwcmV2ZW50cyBoYXZpbmcgdG9vIG1hbnkgbm9kZXMgZW1hbmF0ZQogICAgICAgICAqIGZyb20gYSBzdWJoaWVyYXJjaHkgYW5kIGNyb3dkaW5nIHVwLgogICAgICAgICAqLwogICAgICAgIG1heEJyaWRnZVBhdGhEZWdyZWU6IDQsCiAgICAgICAgLyoqCiAgICAgICAgICogVHlwZXMgcGF0dGVybnMgZm9yIHByZWRlZmluZWQgb3V0LWV4dHJhY3Qgbm9kZXMsIHdoaWNoIGFyZQogICAgICAgICAqIHNpbmstbGlrZSBub2RlcyB0aGF0IHdpbGwgYmUgZXh0cmFjdGVkIGZyb20gdGhlIG1haW4gZ3JhcGguCiAgICAgICAgICovCiAgICAgICAgb3V0RXh0cmFjdFR5cGVzOiBbJ05vT3AnXSwKICAgICAgICAvKioKICAgICAgICAgKiBUeXBlcyBwYXR0ZXJucyBmb3IgcHJlZGVmaW5lZCBpbi1leHRyYWN0IG5vZGVzLCB3aGljaCBhcmUKICAgICAgICAgKiBzb3VyY2UtbGlrZSBub2RlcyB0aGF0IHdpbGwgYmUgZXh0cmFjdGVkIGZyb20gdGhlIG1haW4gZ3JhcGguCiAgICAgICAgICovCiAgICAgICAgaW5FeHRyYWN0VHlwZXM6IFtdLAogICAgICAgIC8qKgogICAgICAgICAqIFdoZW4gcmVtb3ZpbmcgZWRnZXMgZnJvbSBhIGhpZ2ggZGVncmVlIG5vZGUsIHJlbW92ZSBhbGwgb2YgaXRzIGVkZ2VzIGlmCiAgICAgICAgICogZGV0YWNoQWxsRWRnZXNGb3JIaWdoRGVncmVlIGlzIHRydWUuICBPdGhlcndpc2UgcmVtb3ZlIGFsbCBpbi1lZGdlcyBpZgogICAgICAgICAqIHRoZSBub2RlIGhhcyBoaWdoIGluLWRlZ3JlZSwgb3IgYWxsIG91dC1lZGdlcyBpZiB0aGUgbm9kZSBoYXMgaGlnaAogICAgICAgICAqIG91dC1kZWdyZWUuCiAgICAgICAgICovCiAgICAgICAgZGV0YWNoQWxsRWRnZXNGb3JIaWdoRGVncmVlOiB0cnVlLAogICAgICAgIC8qKgogICAgICAgICAqIEFmdGVyIGV4dHJhY3RpbmcgaGlnaCBpbi9vdXQgZGVncmVlIG5vZGVzIGFuZCBwcmVkZWZpbmVkCiAgICAgICAgICogc291cmNlLWxpa2Uvc2luay1saWtlLCBleHRyYWN0IGlzb2xhdGVkIG5vZGVzIHRvIHRoZSBzaWRlCiAgICAgICAgICogaWYgdGhpcyBleHRyYWN0SXNvbGF0ZWROb2Rlc1dpdGhBbm5vdGF0aW9uc09uT25lU2lkZSBpcyB0cnVlLgogICAgICAgICAqLwogICAgICAgIGV4dHJhY3RJc29sYXRlZE5vZGVzV2l0aEFubm90YXRpb25zT25PbmVTaWRlOiB0cnVlLAogICAgICAgIC8qKgogICAgICAgICAqIFdoZXRoZXIgdG8gYWRkIGJyaWRnZSBub2RlcyBhbmQgZWRnZXMgdG8gdGhlIGNvcmUgd2hlbiBidWlsZGluZyB0aGUKICAgICAgICAgKiBzdWJoaWVyYXJjaHkgb2YgYW4gZXhwYW5kZWQgbWV0YW5vZGUuIFNlZSBidWlsZFN1YmhpZXJhcmNoeSgpLgogICAgICAgICAqLwogICAgICAgIGVuYWJsZUJyaWRnZWdyYXBoOiB0cnVlLAogICAgICAgIC8qKgogICAgICAgICAqIDIgY29sb3JzLCBmb3IgdGhlIG1pbmltdW0gYW5kIG1heGltdW0gdmFsdWUgcmVzcGVjdGl2ZWx5LCB3aGVuZXZlciB3ZQogICAgICAgICAqIGhhdmUgYSBncmFkaWVudCBzY2FsZS4KICAgICAgICAgKi8KICAgICAgICBtaW5NYXhDb2xvcnM6IFsnI2ZmZjVmMCcsICcjZmI2YTRhJ10sCiAgICAgICAgLyoqCiAgICAgICAgICogTWF4aW11bSBudW1iZXIgb2YgYW5ub3RhdGlvbnMgdG8gYmUgZGlzcGxheWVkIG9uIGEgbm9kZSBiZWZvcmUgYW4KICAgICAgICAgKiBlbGxpcHNpcyBpcyB1c2VkLgogICAgICAgICAqLwogICAgICAgIG1heEFubm90YXRpb25zOiA1LAogICAgfTsKICAgIC8qKgogICAgICogVGhlIHJlZ3VsYXIgZXhwcmVzc2lvbiB0byB1c2Ugd2hlbiBwYXJzaW5nIGZvciB0aGUgc3RyaW5nIHRoYXQgaXMKICAgICAqIHVzZWQgdG8gbGFiZWwgYSBmdW5jdGlvbiBub2RlIGluIHRoZSBncmFwaC4gV2Ugc3RyaXAgYXdheSBhIHByZWZpeAogICAgICogaW5kaWNhdGluZyB0aGF0IHRoZSBub2RlIHJlcHJlc2VudHMgYSBmdW5jdGlvbiBkZWZpbml0aW9uLiBXZSBhbHNvCiAgICAgKiByZW1vdmUgYW4gYXJiaXRyYXJ5IGhleGFkZWNpbWFsIHN1ZmZpeCBhbmQgdGhlIG51bWJlciBmb2xsb3dpbmcgaXQKICAgICAqIGlmIGl0IGlzIHByZXNlbnQuIFRvIGJlIGNsZWFyLCB3ZSBleHRyYWN0IGZvbyBmcm9tCiAgICAgKiBfX2Z1bmN0aW9uX2xpYnJhcnlfX2Zvb19kZWFkYjAwZl80Mi4KICAgICAqLwogICAgY29uc3Qgbm9kZURpc3BsYXlOYW1lUmVnZXggPSBuZXcgUmVnRXhwKCdeKD86JyArCiAgICAgICAgRlVOQ1RJT05fTElCUkFSWV9OT0RFX1BSRUZJWCArCiAgICAgICAgJyk/KFxcdyspX1thLXowLTldezh9KD86X1xcZCspPyQnKTsKICAgIC8qKgogICAgICogU3RvcmVzIHRoZSByZW5kZXJpbmcgaW5mb3JtYXRpb24sIHN1Y2ggYXMgeCBhbmQgeSBjb29yZGluYXRlcywKICAgICAqIGZvciBlYWNoIG5vZGUgaW4gdGhlIGdyYXBoLgogICAgICovCiAgICBjbGFzcyBSZW5kZXJHcmFwaEluZm8gewogICAgICAgIGNvbnN0cnVjdG9yKGhpZXJhcmNoeSwgZGlzcGxheWluZ1N0YXRzKSB7CiAgICAgICAgICAgIHRoaXMuaGllcmFyY2h5ID0gaGllcmFyY2h5OwogICAgICAgICAgICB0aGlzLmRpc3BsYXlpbmdTdGF0cyA9IGRpc3BsYXlpbmdTdGF0czsKICAgICAgICAgICAgdGhpcy5pbmRleCA9IHt9OwogICAgICAgICAgICB0aGlzLnJlbmRlcmVkT3BOYW1lcyA9IFtdOwogICAgICAgICAgICB0aGlzLmNvbXB1dGVTY2FsZXMoKTsKICAgICAgICAgICAgLy8gTWFwcyBub2RlIG5hbWUgdG8gd2hldGhlciB0aGUgcmVuZGVyaW5nIGhpZXJhcmNoeSB3YXMgYWxyZWFkeQogICAgICAgICAgICAvLyBjb25zdHJ1Y3RlZC4KICAgICAgICAgICAgdGhpcy5oYXNTdWJoaWVyYXJjaHkgPSB7fTsKICAgICAgICAgICAgdGhpcy5yb290ID0gbmV3IFJlbmRlckdyb3VwTm9kZUluZm8oaGllcmFyY2h5LnJvb3QsIGhpZXJhcmNoeS5ncmFwaE9wdGlvbnMpOwogICAgICAgICAgICB0aGlzLmluZGV4W2hpZXJhcmNoeS5yb290Lm5hbWVdID0gdGhpcy5yb290OwogICAgICAgICAgICB0aGlzLnJlbmRlcmVkT3BOYW1lcy5wdXNoKGhpZXJhcmNoeS5yb290Lm5hbWUpOwogICAgICAgICAgICB0aGlzLmJ1aWxkU3ViaGllcmFyY2h5KGhpZXJhcmNoeS5yb290Lm5hbWUpOwogICAgICAgICAgICB0aGlzLnJvb3QuZXhwYW5kZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLnRyYWNlSW5wdXRzID0gZmFsc2U7CiAgICAgICAgfQogICAgICAgIGNvbXB1dGVTY2FsZXMoKSB7CiAgICAgICAgICAgIHRoaXMuZGV2aWNlQ29sb3JNYXAgPSBvcmRpbmFsKCkKICAgICAgICAgICAgICAgIC5kb21haW4odGhpcy5oaWVyYXJjaHkuZGV2aWNlcykKICAgICAgICAgICAgICAgIC5yYW5nZShsb2Rhc2gubWFwKHNlcXVlbmNlKHRoaXMuaGllcmFyY2h5LmRldmljZXMubGVuZ3RoKSwgTWV0YW5vZGVDb2xvcnMuREVWSUNFX1BBTEVUVEUpKTsKICAgICAgICAgICAgdGhpcy54bGFDbHVzdGVyQ29sb3JNYXAgPSBvcmRpbmFsKCkKICAgICAgICAgICAgICAgIC5kb21haW4odGhpcy5oaWVyYXJjaHkueGxhQ2x1c3RlcnMpCiAgICAgICAgICAgICAgICAucmFuZ2UobG9kYXNoLm1hcChzZXF1ZW5jZSh0aGlzLmhpZXJhcmNoeS54bGFDbHVzdGVycy5sZW5ndGgpLCBNZXRhbm9kZUNvbG9ycy5YTEFfQ0xVU1RFUl9QQUxFVFRFKSk7CiAgICAgICAgICAgIGxldCB0b3BMZXZlbEdyYXBoID0gdGhpcy5oaWVyYXJjaHkucm9vdC5tZXRhZ3JhcGg7CiAgICAgICAgICAgIC8vIEZpbmQgdGhlIG1heGltdW0gbWVtb3J5IHVzYWdlLiBVc2UgMCBhcyB0aGUgbWluaW11bS4KICAgICAgICAgICAgbGV0IG1heE1lbW9yeSA9IG1heCh0b3BMZXZlbEdyYXBoLm5vZGVzKCksIChub2RlTmFtZSwgaW5kZXgpID0+IHsKICAgICAgICAgICAgICAgIGxldCBub2RlID0gdG9wTGV2ZWxHcmFwaC5ub2RlKG5vZGVOYW1lKTsKICAgICAgICAgICAgICAgIC8vIFNvbWUgb3BzIGRvbid0IGhhdmUgc3RhdHMgYXQgYWxsLgogICAgICAgICAgICAgICAgaWYgKG5vZGUuc3RhdHMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBub2RlLnN0YXRzLnRvdGFsQnl0ZXM7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLm1lbW9yeVVzYWdlU2NhbGUgPSBsaW5lYXIkMigpCiAgICAgICAgICAgICAgICAuZG9tYWluKFswLCBtYXhNZW1vcnldKQogICAgICAgICAgICAgICAgLnJhbmdlKFBBUkFNUy5taW5NYXhDb2xvcnMpOwogICAgICAgICAgICAvLyBGaW5kIHRoZSBtYXhpbXVtIGNvbXB1dGUgdGltZS4gVXNlIDAgYXMgdGhlIG1pbmltdW0uCiAgICAgICAgICAgIGxldCBtYXhDb21wdXRlVGltZSA9IG1heCh0b3BMZXZlbEdyYXBoLm5vZGVzKCksIChub2RlTmFtZSwgaW5kZXgpID0+IHsKICAgICAgICAgICAgICAgIGxldCBub2RlID0gdG9wTGV2ZWxHcmFwaC5ub2RlKG5vZGVOYW1lKTsKICAgICAgICAgICAgICAgIC8vIFNvbWUgb3BzIGRvbid0IGhhdmUgc3RhdHMgYXQgYWxsLgogICAgICAgICAgICAgICAgaWYgKG5vZGUuc3RhdHMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBub2RlLnN0YXRzLmdldFRvdGFsTWljcm9zKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLmNvbXB1dGVUaW1lU2NhbGUgPSBsaW5lYXIkMigpCiAgICAgICAgICAgICAgICAuZG9tYWluKFswLCBtYXhDb21wdXRlVGltZV0pCiAgICAgICAgICAgICAgICAucmFuZ2UoUEFSQU1TLm1pbk1heENvbG9ycyk7CiAgICAgICAgICAgIHRoaXMuZWRnZVdpZHRoU2l6ZWRCYXNlZFNjYWxlID0gdGhpcy5oaWVyYXJjaHkuaGFzU2hhcGVJbmZvCiAgICAgICAgICAgICAgICA/IEVER0VfV0lEVEhfU0laRV9CQVNFRF9TQ0FMRQogICAgICAgICAgICAgICAgOiBsaW5lYXIkMigpCiAgICAgICAgICAgICAgICAgICAgLmRvbWFpbihbMSwgdGhpcy5oaWVyYXJjaHkubWF4TWV0YUVkZ2VTaXplXSkKICAgICAgICAgICAgICAgICAgICAucmFuZ2UoWwogICAgICAgICAgICAgICAgICAgIE1JTl9FREdFX1dJRFRILAogICAgICAgICAgICAgICAgICAgIE1BWF9FREdFX1dJRFRILAogICAgICAgICAgICAgICAgXSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdldCBhIHByZXZpb3VzbHkgY3JlYXRlZCBSZW5kZXJOb2RlSW5mbyBieSBpdHMgbm9kZSBuYW1lLgogICAgICAgICAqLwogICAgICAgIGdldFJlbmRlck5vZGVCeU5hbWUobm9kZU5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW5kZXhbbm9kZU5hbWVdOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHZXQgdGhlIHVuZGVybHlpbmcgbm9kZSBpbiB0aGUgaGllcmFyY2hpY2FsIGdyYXBoIGJ5IGl0cyBuYW1lLgogICAgICAgICAqLwogICAgICAgIGdldE5vZGVCeU5hbWUobm9kZU5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaGllcmFyY2h5Lm5vZGUobm9kZU5hbWUpOwogICAgICAgIH0KICAgICAgICBjb2xvckhpc3RvZ3JhbShoaXN0b2dyYW0sIGNvbG9ycykgewogICAgICAgICAgICBpZiAoT2JqZWN0LmtleXMoaGlzdG9ncmFtKS5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgICAvLyBDb21wdXRlIHRoZSB0b3RhbCAjIG9mIGl0ZW1zLgogICAgICAgICAgICAgICAgY29uc3QgbnVtSXRlbXMgPSBsb2Rhc2guc3VtKE9iamVjdC5rZXlzKGhpc3RvZ3JhbSkubWFwKChrZXkpID0+IGhpc3RvZ3JhbVtrZXldKSk7CiAgICAgICAgICAgICAgICByZXR1cm4gT2JqZWN0LmtleXMoaGlzdG9ncmFtKS5tYXAoKGtleSkgPT4gKHsKICAgICAgICAgICAgICAgICAgICBjb2xvcjogY29sb3JzKGtleSksCiAgICAgICAgICAgICAgICAgICAgLy8gTm9ybWFsaXplIHRvIGEgcHJvcG9ydGlvbiBvZiB0b3RhbCAjIG9mIGl0ZW1zLgogICAgICAgICAgICAgICAgICAgIHByb3BvcnRpb246IGhpc3RvZ3JhbVtrZXldIC8gbnVtSXRlbXMsCiAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc29sZS5pbmZvKCdubyBwYWlycyBmb3VuZCEnKTsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEdldCBhIHByZXZpb3VzbHkgY3JlYXRlZCBSZW5kZXJOb2RlSW5mbyBmb3IgdGhlIHNwZWNpZmllZCBub2RlIG5hbWUsCiAgICAgICAgICogb3IgY3JlYXRlIG9uZSBpZiBpdCBoYXNuJ3QgYmVlbiBjcmVhdGVkIHlldC4KICAgICAgICAgKi8KICAgICAgICBnZXRPckNyZWF0ZVJlbmRlck5vZGVCeU5hbWUobm9kZU5hbWUpIHsKICAgICAgICAgICAgLy8gUG9seW1lciBtYXkgaW52b2tlIHRoaXMgd2l0aCBudWxsLgogICAgICAgICAgICBpZiAoIW5vZGVOYW1lKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAobm9kZU5hbWUgaW4gdGhpcy5pbmRleCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW5kZXhbbm9kZU5hbWVdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBub2RlID0gdGhpcy5oaWVyYXJjaHkubm9kZShub2RlTmFtZSk7CiAgICAgICAgICAgIC8vIEV4aXQgZWFybHkgaWYgdGhlIG5vZGUgZG9lcyBub3QgZXhpc3QgaW4gdGhlIGhpZXJhcmNoeS4gVGhpcyBjYW4gaGFwcGVuCiAgICAgICAgICAgIC8vIHdoZW4gYSBncmFwaCBpcyByZWxvYWRlZCB3aGlsZSB0aGUgaW5mb2NhcmQgcG9pbnRzIHRvIGEgbm9kZSBub3QgdmlzaWJsZQogICAgICAgICAgICAvLyBhdCB0aGUgdG9wLWxldmVsLgogICAgICAgICAgICBpZiAoIW5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCByZW5kZXJJbmZvID0gbm9kZS5pc0dyb3VwTm9kZQogICAgICAgICAgICAgICAgPyBuZXcgUmVuZGVyR3JvdXBOb2RlSW5mbyhub2RlLCB0aGlzLmhpZXJhcmNoeS5ncmFwaE9wdGlvbnMpCiAgICAgICAgICAgICAgICA6IG5ldyBSZW5kZXJOb2RlSW5mbyhub2RlKTsKICAgICAgICAgICAgdGhpcy5pbmRleFtub2RlTmFtZV0gPSByZW5kZXJJbmZvOwogICAgICAgICAgICB0aGlzLnJlbmRlcmVkT3BOYW1lcy5wdXNoKG5vZGVOYW1lKTsKICAgICAgICAgICAgaWYgKG5vZGUuc3RhdHMpIHsKICAgICAgICAgICAgICAgIHJlbmRlckluZm8ubWVtb3J5Q29sb3IgPSB0aGlzLm1lbW9yeVVzYWdlU2NhbGUobm9kZS5zdGF0cy50b3RhbEJ5dGVzKTsKICAgICAgICAgICAgICAgIHJlbmRlckluZm8uY29tcHV0ZVRpbWVDb2xvciA9IHRoaXMuY29tcHV0ZVRpbWVTY2FsZShub2RlLnN0YXRzLmdldFRvdGFsTWljcm9zKCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFdlIG9ubHkgZmFkZSBub2RlcyB3aGVuIHdlJ3JlIGRpc3BsYXlpbmcgc3RhdHMuCiAgICAgICAgICAgIHJlbmRlckluZm8uaXNGYWRlZE91dCA9CiAgICAgICAgICAgICAgICB0aGlzLmRpc3BsYXlpbmdTdGF0cyAmJgogICAgICAgICAgICAgICAgICAgICFoYXNEaXNwbGF5YWJsZU5vZGVTdGF0cyhub2RlLnN0YXRzKTsKICAgICAgICAgICAgdmFyIGRldmljZUhpc3RvZ3JhbSA9IG51bGw7CiAgICAgICAgICAgIHZhciB4bGFDbHVzdGVySGlzdG9ncmFtID0gbnVsbDsKICAgICAgICAgICAgdmFyIG9wQ29tcGF0aWJpbGl0eSA9IG51bGw7CiAgICAgICAgICAgIGlmIChub2RlLmlzR3JvdXBOb2RlKSB7CiAgICAgICAgICAgICAgICBkZXZpY2VIaXN0b2dyYW0gPSBub2RlLmRldmljZUhpc3RvZ3JhbTsKICAgICAgICAgICAgICAgIHhsYUNsdXN0ZXJIaXN0b2dyYW0gPSBub2RlLnhsYUNsdXN0ZXJIaXN0b2dyYW07CiAgICAgICAgICAgICAgICBsZXQgY29tcGF0ID0gbm9kZS5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGU7CiAgICAgICAgICAgICAgICBsZXQgaW5jb21wYXQgPSBub2RlLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlOwogICAgICAgICAgICAgICAgaWYgKGNvbXBhdCAhPSAwIHx8IGluY29tcGF0ICE9IDApIHsKICAgICAgICAgICAgICAgICAgICBvcENvbXBhdGliaWxpdHkgPSBjb21wYXQgLyAoY29tcGF0ICsgaW5jb21wYXQpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgbGV0IGRldmljZSA9IHJlbmRlckluZm8ubm9kZS5kZXZpY2U7CiAgICAgICAgICAgICAgICBpZiAoZGV2aWNlKSB7CiAgICAgICAgICAgICAgICAgICAgZGV2aWNlSGlzdG9ncmFtID0geyBbZGV2aWNlXTogMSB9OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IHhsYUNsdXN0ZXIgPSByZW5kZXJJbmZvLm5vZGUueGxhQ2x1c3RlcjsKICAgICAgICAgICAgICAgIGlmICh4bGFDbHVzdGVyKSB7CiAgICAgICAgICAgICAgICAgICAgeGxhQ2x1c3Rlckhpc3RvZ3JhbSA9IHsgW3hsYUNsdXN0ZXJdOiAxIH07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAocmVuZGVySW5mby5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLk9QKSB7CiAgICAgICAgICAgICAgICAgICAgb3BDb21wYXRpYmlsaXR5ID0gcmVuZGVySW5mby5ub2RlLmNvbXBhdGlibGUgPyAxIDogMDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoZGV2aWNlSGlzdG9ncmFtKSB7CiAgICAgICAgICAgICAgICByZW5kZXJJbmZvLmRldmljZUNvbG9ycyA9IHRoaXMuY29sb3JIaXN0b2dyYW0oZGV2aWNlSGlzdG9ncmFtLCB0aGlzLmRldmljZUNvbG9yTWFwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoeGxhQ2x1c3Rlckhpc3RvZ3JhbSkgewogICAgICAgICAgICAgICAgcmVuZGVySW5mby54bGFDbHVzdGVyQ29sb3JzID0gdGhpcy5jb2xvckhpc3RvZ3JhbSh4bGFDbHVzdGVySGlzdG9ncmFtLCB0aGlzLnhsYUNsdXN0ZXJDb2xvck1hcCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG9wQ29tcGF0aWJpbGl0eSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICByZW5kZXJJbmZvLmNvbXBhdGliaWxpdHlDb2xvcnMgPSBbCiAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICBjb2xvcjogT3BOb2RlQ29sb3JzLkNPTVBBVElCTEUsCiAgICAgICAgICAgICAgICAgICAgICAgIHByb3BvcnRpb246IG9wQ29tcGF0aWJpbGl0eSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29sb3I6IE9wTm9kZUNvbG9ycy5JTkNPTVBBVElCTEUsCiAgICAgICAgICAgICAgICAgICAgICAgIHByb3BvcnRpb246IDEgLSBvcENvbXBhdGliaWxpdHksCiAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW5kZXhbbm9kZU5hbWVdOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm4gdGhlIG5lYXJlc3QgYW5jZXN0b3Igbm9kZSwgaW5jbHVkaW5nIGl0c2VsZiwgdGhhdCBpcyB2aXNpYmxlCiAgICAgICAgICogaW4gdGhlIHZpc3VhbGl6YXRpb24uIFRoaXMgbWV0aG9kIGlzIHVzZWQgc28gdGhhdCB3ZSBjYW4gc2VsZWN0CiAgICAgICAgICogKGhpZ2hsaWdodCkgYSBub2RlIHRoYXQgaXNuJ3QgZHJhd24geWV0LCBieSBzZWxlY3RpbmcgKGhpZ2hsaWdodGluZykKICAgICAgICAgKiBpdHMgbmVhcmVzdCBhbmNlc3RvciB0aGF0IGhhcyBiZWVuIGRyYXduLgogICAgICAgICAqLwogICAgICAgIGdldE5lYXJlc3RWaXNpYmxlQW5jZXN0b3IobmFtZSkgewogICAgICAgICAgICBsZXQgcGF0aCA9IGdldEhpZXJhcmNoaWNhbFBhdGgobmFtZSk7CiAgICAgICAgICAgIGxldCBpID0gMDsKICAgICAgICAgICAgbGV0IHJlbmRlck5vZGUgPSBudWxsOwogICAgICAgICAgICAvLyBGYWxsdGhyb3VnaC4gSWYgZXZlcnl0aGluZyB3YXMgZXhwYW5kZWQgcmV0dXJuIHRoZSBub2RlLgogICAgICAgICAgICBsZXQgbm9kZU5hbWUgPSBuYW1lOwogICAgICAgICAgICBmb3IgKDsgaSA8IHBhdGgubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIG5vZGVOYW1lID0gcGF0aFtpXTsKICAgICAgICAgICAgICAgIHJlbmRlck5vZGUgPSB0aGlzLmdldFJlbmRlck5vZGVCeU5hbWUobm9kZU5hbWUpOwogICAgICAgICAgICAgICAgLy8gT3Agbm9kZXMgaGF2ZSBleHBhbmRlZCBzZXQgdG8gZmFsc2UgYnkgZGVmYXVsdC4KICAgICAgICAgICAgICAgIGlmICghcmVuZGVyTm9kZS5leHBhbmRlZCkgewogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENoZWNrIGNhc2Ugd2hlcmUgaGlnaGxpZ2h0ZWQgbm9kZSBpcyBhbiBlbWJlZGRlZCBub2RlIHdob3NlIHBhcmVudCBub2RlCiAgICAgICAgICAgIC8vIGlzIGFsc28gaXRzIGhpZXJhcmNoaWNhbCBwYXJlbnQuIEluIHRoaXMgY2FzZSwgd2Ugd2FudCB0byByZXR1cm4gdGhlCiAgICAgICAgICAgIC8vIGVtYmVkZGVkIG5vZGUgbmFtZSwgYXMgaXQgaXMgYWxzbyBkaXNwbGF5ZWQgaWYgaXRzIHBhcmVudCBoYXMgYmVlbgogICAgICAgICAgICAvLyBkaXNwbGF5ZWQuCiAgICAgICAgICAgIGlmIChpID09IHBhdGgubGVuZ3RoIC0gMikgewogICAgICAgICAgICAgICAgbGV0IG5leHROYW1lID0gcGF0aFtpICsgMV07CiAgICAgICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5pbkFubm90YXRpb25zLm5vZGVOYW1lc1tuZXh0TmFtZV0pIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbmV4dE5hbWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5vdXRBbm5vdGF0aW9ucy5ub2RlTmFtZXNbbmV4dE5hbWVdKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG5leHROYW1lOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBub2RlTmFtZTsKICAgICAgICB9CiAgICAgICAgLy8gVE9ETzogRGVsZXRlIHRoaXMgYW4gYW55IGNvZGUgaXQgdG91Y2hlcyAoYWxsIGRlcHJlY2F0ZWQpLgogICAgICAgIHNldERlcHRoKGRlcHRoKSB7CiAgICAgICAgICAgIHNldEdyb3VwTm9kZURlcHRoKHRoaXMucm9vdCwgK2RlcHRoKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSByZW5kZXJOb2RlIGlzIGFuIGlzb2xhdGVkIG5vZGUgd2l0aGluIGl0cyBwYXJlbnQgbm9kZS4KICAgICAgICAgKi8KICAgICAgICBpc05vZGVBdXhpbGlhcnkocmVuZGVyTm9kZSkgewogICAgICAgICAgICBsZXQgcGFyZW50Tm9kZSA9ICh0aGlzLmdldFJlbmRlck5vZGVCeU5hbWUocmVuZGVyTm9kZS5ub2RlLnBhcmVudE5vZGUubmFtZSkpOwogICAgICAgICAgICBsZXQgZm91bmQgPSBsb2Rhc2guZmluZChwYXJlbnROb2RlLmlzb2xhdGVkSW5FeHRyYWN0LCAobm9kZSkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuIG5vZGUubm9kZS5uYW1lID09PSByZW5kZXJOb2RlLm5vZGUubmFtZTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGlmIChmb3VuZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZm91bmQgPSBsb2Rhc2guZmluZChwYXJlbnROb2RlLmlzb2xhdGVkT3V0RXh0cmFjdCwgKG5vZGUpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBub2RlLm5vZGUubmFtZSA9PT0gcmVuZGVyTm9kZS5ub2RlLm5hbWU7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gISFmb3VuZDsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBhIGxpc3Qgb2Ygb3BzIHRoYXQgaGF2ZSBiZWVuIHJlbmRlcmVkIHNvIGZhciBmb3IgdGhpcyBncmFwaC4gTW9yZQogICAgICAgICAqIG9wcyBtYXkgbGF0ZXIgYmUgcmVuZGVyZWQgaWYgdGhlIHVzZXIgZXhwYW5kcyBub2RlcyBmb3IgaW5zdGFuY2UuIFRoZSBsaXN0CiAgICAgICAgICogcmV0dXJuZWQgaGVyZSBjYW4gb25seSBzdGF5IHRoZSBzYW1lIHNpemUgb3IgZ3JvdyBvbiBzdWNjZXNzaXZlIGNhbGxzLgogICAgICAgICAqLwogICAgICAgIGdldE5hbWVzT2ZSZW5kZXJlZE9wcygpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVuZGVyZWRPcE5hbWVzOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBDbG9uZXMgYW4gb3Agbm9kZSBhbmQgYWRkcyBpdCB0byBhIG1ldGFncmFwaC4gRG9lcyBub3RoaW5nIGlmIGFuIG9wIG5vZGUKICAgICAgICAgKiB3aXRoIHRoZSBzYW1lIG5ldyBuYW1lIGhhcyBhbHJlYWR5IGJlZW4gY3JlYXRlZCB3aXRoaW4gdGhlIG1ldGFncmFwaC4gVGhpcwogICAgICAgICAqIG1ldGhvZCBpcyB1c2VkIHdoZW4gZHVwbGljYXRpbmcgYSBsaWJyYXJ5IGZ1bmN0aW9uIHRvIGJlIGluamVjdGVkIHdpdGhpbiBhCiAgICAgICAgICogbWV0YW5vZGUgcmVwcmVzZW50aW5nIGEgZnVuY3Rpb24gY2FsbC4KICAgICAgICAgKiBAcGFyYW0gcGFyZW50TWV0YW5vZGUgVGhlIHBhcmVudCBtZXRhbm9kZSBvbiB3aGljaCB0byBhZGQgdGhlIG5ldyBub2RlLgogICAgICAgICAqIEBwYXJhbSBub2RlIFRoZSBvcCBub2RlIHRvIGNsb25lLgogICAgICAgICAqIEBwYXJhbSBuZXdQcmVmaXggVGhlIHByZWZpeCBzdHJpbmcgdG8gdXNlIGluIGxpZXUgb2YgdGhlIG9uZSB0aGF0IG1lcmVseQogICAgICAgICAqICAgICBpbmRpY2F0ZXMgdGhhdCB0aGUgbWV0YW5vZGUgcmVwcmVzZW50cyBhIGZ1bmN0aW9uIGRlZmluZWQgaW4gdGhlCiAgICAgICAgICogICAgIGxpYnJhcnkuIFRoaXMgcHJlZml4IHNob3VsZCByZWZsZWN0IGdyYXBoIGhpZXJhcmNoeS4KICAgICAgICAgKiBAcmV0dXJuIFRoZSBuZXdseSBjcmVhdGVkIG9wIG5vZGUgKHRoZSBjbG9uZSBvZiB0aGUgb3JpZ2luYWwpLgogICAgICAgICAqLwogICAgICAgIGNsb25lQW5kQWRkRnVuY3Rpb25PcE5vZGUocGFyZW50TWV0YW5vZGUsIGxpYnJhcnlGdW5jdGlvbk5vZGVOYW1lLCBub2RlLCBuZXdQcmVmaXgpIHsKICAgICAgICAgICAgY29uc3QgbmV3TmFtZSA9IG5vZGUubmFtZS5yZXBsYWNlKGxpYnJhcnlGdW5jdGlvbk5vZGVOYW1lLCBuZXdQcmVmaXgpOwogICAgICAgICAgICBsZXQgbmV3T3BOb2RlID0gcGFyZW50TWV0YW5vZGUubWV0YWdyYXBoLm5vZGUobmV3TmFtZSk7CiAgICAgICAgICAgIGlmIChuZXdPcE5vZGUpIHsKICAgICAgICAgICAgICAgIC8vIFRoaXMgbm9kZSBoYWQgYWxyZWFkeSBiZWVuIGNyZWF0ZWQgYW5kIGFkZGVkIHRvIHRoZSBncmFwaC4KICAgICAgICAgICAgICAgIHJldHVybiBuZXdPcE5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQ3JlYXRlIGEgbmV3IG9wIG5vZGUuCiAgICAgICAgICAgIG5ld09wTm9kZSA9IG5ldyBPcE5vZGVJbXBsKHsKICAgICAgICAgICAgICAgIG5hbWU6IG5ld05hbWUsCiAgICAgICAgICAgICAgICBpbnB1dDogW10sCiAgICAgICAgICAgICAgICBkZXZpY2U6IG5vZGUuZGV2aWNlLAogICAgICAgICAgICAgICAgb3A6IG5vZGUub3AsCiAgICAgICAgICAgICAgICBhdHRyOiBsb2Rhc2guY2xvbmVEZWVwKG5vZGUuYXR0ciksCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBVcGRhdGUgdmFyaW91cyBwcm9wZXJ0aWVzLgogICAgICAgICAgICBuZXdPcE5vZGUuY2FyZGluYWxpdHkgPSBub2RlLmNhcmRpbmFsaXR5OwogICAgICAgICAgICBuZXdPcE5vZGUuaW5jbHVkZSA9IG5vZGUuaW5jbHVkZTsKICAgICAgICAgICAgbmV3T3BOb2RlLm91dHB1dFNoYXBlcyA9IGxvZGFzaC5jbG9uZURlZXAobm9kZS5vdXRwdXRTaGFwZXMpOwogICAgICAgICAgICBuZXdPcE5vZGUueGxhQ2x1c3RlciA9IG5vZGUueGxhQ2x1c3RlcjsKICAgICAgICAgICAgbmV3T3BOb2RlLmZ1bmN0aW9uSW5wdXRJbmRleCA9IG5vZGUuZnVuY3Rpb25JbnB1dEluZGV4OwogICAgICAgICAgICBuZXdPcE5vZGUuZnVuY3Rpb25PdXRwdXRJbmRleCA9IG5vZGUuZnVuY3Rpb25PdXRwdXRJbmRleDsKICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSBpbnB1dHMgb2YgdGhlIG5ldyBub2RlIHRvIHJlZmxlY3QgdGhlIG5ldyBwYXRoLgogICAgICAgICAgICBuZXdPcE5vZGUuaW5wdXRzID0gbm9kZS5pbnB1dHMubWFwKChub3JtYWxpemVkSW5wdXQpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IG5ld05vcm1hbGl6ZWRJbnB1dCA9IGxvZGFzaC5jbG9uZShub3JtYWxpemVkSW5wdXQpOwogICAgICAgICAgICAgICAgbmV3Tm9ybWFsaXplZElucHV0Lm5hbWUgPSBub3JtYWxpemVkSW5wdXQubmFtZS5yZXBsYWNlKGxpYnJhcnlGdW5jdGlvbk5vZGVOYW1lLCBuZXdQcmVmaXgpOwogICAgICAgICAgICAgICAgcmV0dXJuIG5ld05vcm1hbGl6ZWRJbnB1dDsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIEFkZCB0aGUgbmV3IG9wIG5vZGUgdG8gdGhlIGhpZXJhcmNoeSBhbmQgbWV0YWdyYXBoLiBBbHNvIGFkZCBpdCB0byBpdHMKICAgICAgICAgICAgLy8gcGFyZW50IG1ldGFub2RlLgogICAgICAgICAgICBuZXdPcE5vZGUucGFyZW50Tm9kZSA9IHBhcmVudE1ldGFub2RlOwogICAgICAgICAgICBwYXJlbnRNZXRhbm9kZS5tZXRhZ3JhcGguc2V0Tm9kZShuZXdPcE5vZGUubmFtZSwgbmV3T3BOb2RlKTsKICAgICAgICAgICAgdGhpcy5oaWVyYXJjaHkuc2V0Tm9kZShuZXdPcE5vZGUubmFtZSwgbmV3T3BOb2RlKTsKICAgICAgICAgICAgLy8gVXBkYXRlIGVtYmVkZGluZ3MuCiAgICAgICAgICAgIGNvbnN0IHVwZGF0ZUVtYmVkZGluZ09wTm9kZSA9IChlbWJlZGRpbmdOb2RlKSA9PiB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5jbG9uZUFuZEFkZEZ1bmN0aW9uT3BOb2RlKHBhcmVudE1ldGFub2RlLCBsaWJyYXJ5RnVuY3Rpb25Ob2RlTmFtZSwgZW1iZWRkaW5nTm9kZSwgbmV3UHJlZml4KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgbmV3T3BOb2RlLmluRW1iZWRkaW5ncyA9IG5vZGUuaW5FbWJlZGRpbmdzLm1hcCh1cGRhdGVFbWJlZGRpbmdPcE5vZGUpOwogICAgICAgICAgICBuZXdPcE5vZGUub3V0RW1iZWRkaW5ncyA9IG5vZGUub3V0RW1iZWRkaW5ncy5tYXAodXBkYXRlRW1iZWRkaW5nT3BOb2RlKTsKICAgICAgICAgICAgcmV0dXJuIG5ld09wTm9kZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQ2xvbmVzIGEgTWV0YW5vZGUgdGhhdCByZXByZXNlbnRzIGEgZnVuY3Rpb24gZGVmaW5lZCBpbiB0aGUgZ3JhcGggbGlicmFyeS4KICAgICAgICAgKiBXZSBkeW5hbWljYWxseSBpbmplY3QgYSBjbG9uZSBvZiBhIGZ1bmN0aW9uIGludG8gYSBtZXRhIGdyYXBoIHdoZW4gdGhlIHVzZXIKICAgICAgICAgKiBleHBhbmRzIGEgZnVuY3Rpb24gY2FsbC4gV2UgY2Fubm90IGRvIHRoaXMgYXQgdGhlIGJlZ2lubmluZyBiZWNhdXNlIHRoZQogICAgICAgICAqIGZ1bmN0aW9ucyBtYXkgcmVjdXJzaXZlbHkgY2FsbCB0aGVtc2VsdmVzIG9yIG90aGVyIGZ1bmN0aW9ucy4KICAgICAgICAgKiBAcGFyYW0gbWV0YWdyYXBoIFRoZSBtZXRhZ3JhcGggd2UgYXJlIGN1cnJlbnRseSByZW5kZXJpbmcgdGhlIHN1Yi1oaWVyYXJjaHkKICAgICAgICAgKiAgICAgZm9yLgogICAgICAgICAqIEBwYXJhbSBvcE5vZGVUb1JlcGxhY2UgVGhlIG9wIG5vZGUgaW4gdGhlIGdyYXBoIHRvIHJlcGxhY2Ugd2l0aCBhIG5ldwogICAgICAgICAqICAgICAoZXhwYW5kYWJsZSkgbWV0YW5vZGUgdGhhdCB2aXN1YWxpemVzIHRoZSBpbm5hcmRzIG9mIGEgZnVuY3Rpb24uCiAgICAgICAgICogQHBhcmFtIGxpYnJhcnlNZXRhbm9kZSBUaGUgbWV0YW5vZGUgZm9yIGEgbGlicmFyeSBmdW5jdGlvbiB0byBjbG9uZS4KICAgICAgICAgKiBAcGFyYW0gb2xkUHJlZml4IFRoZSBvbGQgcHJlZml4IHRvIHJlcGxhY2UgKHRoYXQganVzdCByZWZsZWN0cyBob3cgdGhpcwogICAgICAgICAqICAgICBub2RlIGlzIGZvciBhIGxpYnJhcnkgZnVuY3Rpb24pLgogICAgICAgICAqIEBwYXJhbSBuZXdQcmVmaXggVGhlIHByZWZpeCBzdHJpbmcgdG8gdXNlIGluIGxpZXUgb2YgdGhlIG9uZSB0aGF0IG1lcmVseQogICAgICAgICAqICAgICBpbmRpY2F0ZXMgdGhhdCB0aGUgbWV0YW5vZGUgcmVwcmVzZW50cyBhIGZ1bmN0aW9uIGRlZmluZWQgaW4gdGhlCiAgICAgICAgICogICAgIGxpYnJhcnkuIFRoaXMgcHJlZml4IHNob3VsZCByZWZsZWN0IGdyYXBoIGhpZXJhcmNoeS4KICAgICAgICAgKi8KICAgICAgICBjbG9uZUZ1bmN0aW9uTGlicmFyeU1ldGFub2RlKG1ldGFncmFwaCwgb3BOb2RlVG9SZXBsYWNlLCBsaWJyYXJ5TWV0YW5vZGUsIG9sZFByZWZpeCwgbmV3UHJlZml4KSB7CiAgICAgICAgICAgIC8vIE1ha2UgYSBtYXBwaW5nIGJldHdlZW4gZnVuY3Rpb24gb3V0cHV0IGluZGV4IGFuZCB0aGUgbmV3IG5vZGUgZm9yIHRoZQogICAgICAgICAgICAvLyBvdXRwdXQuCiAgICAgICAgICAgIGNvbnN0IGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGUgPSB7fTsKICAgICAgICAgICAgY29uc3QgbmV3TWV0YW5vZGUgPSB0aGlzLmNsb25lRnVuY3Rpb25MaWJyYXJ5TWV0YW5vZGVIZWxwZXIobWV0YWdyYXBoLCBvcE5vZGVUb1JlcGxhY2UsIGxpYnJhcnlNZXRhbm9kZSwgb2xkUHJlZml4LCBuZXdQcmVmaXgsIGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGUpOwogICAgICAgICAgICBpZiAoIWxvZGFzaC5pc0VtcHR5KGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGUpKSB7CiAgICAgICAgICAgICAgICAvLyBBZnRlciB3ZSBoYXZlIGNsb25lZCB0aGUgZWRnZXMgd2l0aGluIHRoZSBtZXRhbm9kZSwgd2Ugc3RpbGwgbXVzdCBhZGQKICAgICAgICAgICAgICAgIC8vIGVkZ2VzIHRoYXQgZW1hbmF0ZSBvdXQgb2Ygb3V0cHV0IG9wcyB3aXRoaW4gdGhlIGZ1bmN0aW9uLgogICAgICAgICAgICAgICAgdGhpcy5wYXRjaEVkZ2VzRnJvbUZ1bmN0aW9uT3V0cHV0cyhvcE5vZGVUb1JlcGxhY2UsIGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBuZXdNZXRhbm9kZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQSBoZWxwZXIgc3Vicm91dGluZSB0aGF0IHBlcmZvcm1zIHRoZSBidWxrIG9mIHRoZSBsb2dpYyBmb3IKICAgICAgICAgKiBgY2xvbmVGdW5jdGlvbkxpYnJhcnlNZXRhbm9kZWAuCiAgICAgICAgICogQHBhcmFtIG1ldGFncmFwaCBUaGUgbWV0YWdyYXBoIHdlIGFyZSBjdXJyZW50bHkgcmVuZGVyaW5nIHRoZSBzdWItaGllcmFyY2h5CiAgICAgICAgICogICAgIGZvci4KICAgICAgICAgKiBAcGFyYW0gb3BOb2RlVG9SZXBsYWNlIFRoZSBvcCBub2RlIGluIHRoZSBncmFwaCB0byByZXBsYWNlIHdpdGggYSBuZXcKICAgICAgICAgKiAgICAgKGV4cGFuZGFibGUpIG1ldGFub2RlIHRoYXQgdmlzdWFsaXplcyB0aGUgaW5uYXJkcyBvZiBhIGZ1bmN0aW9uLgogICAgICAgICAqIEBwYXJhbSBsaWJyYXJ5TWV0YW5vZGUgVGhlIG1ldGFub2RlIGZvciBhIGxpYnJhcnkgZnVuY3Rpb24gdG8gY2xvbmUuCiAgICAgICAgICogQHBhcmFtIG9sZFByZWZpeCBUaGUgb2xkIHByZWZpeCB0byByZXBsYWNlICh0aGF0IGp1c3QgcmVmbGVjdHMgaG93IHRoaXMKICAgICAgICAgKiAgICAgbm9kZSBpcyBmb3IgYSBsaWJyYXJ5IGZ1bmN0aW9uKS4KICAgICAgICAgKiBAcGFyYW0gbmV3UHJlZml4IFRoZSBwcmVmaXggc3RyaW5nIHRvIHVzZSBpbiBsaWV1IG9mIHRoZSBvbmUgdGhhdCBtZXJlbHkKICAgICAgICAgKiAgICAgaW5kaWNhdGVzIHRoYXQgdGhlIG1ldGFub2RlIHJlcHJlc2VudHMgYSBmdW5jdGlvbiBkZWZpbmVkIGluIHRoZQogICAgICAgICAqICAgICBsaWJyYXJ5LiBUaGlzIHByZWZpeCBzaG91bGQgcmVmbGVjdCBncmFwaCBoaWVyYXJjaHkuCiAgICAgICAgICogQHBhcmFtIGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGUgQSBtYXBwaW5nIGJldHdlZW4gZnVuY3Rpb24gb3V0cHV0IGluZGV4CiAgICAgICAgICogICAgIGFuZCB0aGUgY29ycmVzcG9uZGluZyBvdXRwdXQgbm9kZS4gVXNlZCB0byBjb25uZWN0IG91dHB1dHMgd2l0aAogICAgICAgICAqICAgICBkZXN0aW5hdGlvbnMgb3V0c2lkZSBvZiB0aGUgZnVuY3Rpb24gbWV0YW5vZGUuCiAgICAgICAgICovCiAgICAgICAgY2xvbmVGdW5jdGlvbkxpYnJhcnlNZXRhbm9kZUhlbHBlcihtZXRhZ3JhcGgsIG9wTm9kZVRvUmVwbGFjZSwgbGlicmFyeU1ldGFub2RlLCBvbGRQcmVmaXgsIG5ld1ByZWZpeCwgZnVuY3Rpb25PdXRwdXRJbmRleFRvTm9kZSkgewogICAgICAgICAgICBjb25zdCBuZXdNZXRhbm9kZSA9IGNyZWF0ZU1ldGFub2RlKGxpYnJhcnlNZXRhbm9kZS5uYW1lLnJlcGxhY2Uob2xkUHJlZml4LCBuZXdQcmVmaXgpKTsKICAgICAgICAgICAgLy8gQ29weSBvdmVyIHZhcmlvdXMgcHJvcGVydGllcy4KICAgICAgICAgICAgbmV3TWV0YW5vZGUuZGVwdGggPSBsaWJyYXJ5TWV0YW5vZGUuZGVwdGg7CiAgICAgICAgICAgIG5ld01ldGFub2RlLmNhcmRpbmFsaXR5ID0gbGlicmFyeU1ldGFub2RlLmNhcmRpbmFsaXR5OwogICAgICAgICAgICBuZXdNZXRhbm9kZS50ZW1wbGF0ZUlkID0gbGlicmFyeU1ldGFub2RlLnRlbXBsYXRlSWQ7CiAgICAgICAgICAgIG5ld01ldGFub2RlLm9wSGlzdG9ncmFtID0gbG9kYXNoLmNsb25lKGxpYnJhcnlNZXRhbm9kZS5vcEhpc3RvZ3JhbSk7CiAgICAgICAgICAgIG5ld01ldGFub2RlLmRldmljZUhpc3RvZ3JhbSA9IGxvZGFzaC5jbG9uZShsaWJyYXJ5TWV0YW5vZGUuZGV2aWNlSGlzdG9ncmFtKTsKICAgICAgICAgICAgbmV3TWV0YW5vZGUueGxhQ2x1c3Rlckhpc3RvZ3JhbSA9IGxvZGFzaC5jbG9uZShsaWJyYXJ5TWV0YW5vZGUueGxhQ2x1c3Rlckhpc3RvZ3JhbSk7CiAgICAgICAgICAgIG5ld01ldGFub2RlLmhhc05vbkNvbnRyb2xFZGdlcyA9IGxpYnJhcnlNZXRhbm9kZS5oYXNOb25Db250cm9sRWRnZXM7CiAgICAgICAgICAgIG5ld01ldGFub2RlLmluY2x1ZGUgPSBsaWJyYXJ5TWV0YW5vZGUuaW5jbHVkZTsKICAgICAgICAgICAgbmV3TWV0YW5vZGUubm9kZUF0dHJpYnV0ZXMgPSBsb2Rhc2guY2xvbmUobGlicmFyeU1ldGFub2RlLm5vZGVBdHRyaWJ1dGVzKTsKICAgICAgICAgICAgbmV3TWV0YW5vZGUuYXNzb2NpYXRlZEZ1bmN0aW9uID0gbGlicmFyeU1ldGFub2RlLmFzc29jaWF0ZWRGdW5jdGlvbjsKICAgICAgICAgICAgLy8gUmVjdXJzaXZlbHkgZHVwbGljYXRlIHRoZSBjaGlsZHJlbiBub2Rlcy4KICAgICAgICAgICAgbG9kYXNoLmVhY2gobGlicmFyeU1ldGFub2RlLm1ldGFncmFwaC5ub2RlcygpLCAobm9kZU5hbWUpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IG5vZGUgPSBsaWJyYXJ5TWV0YW5vZGUubWV0YWdyYXBoLm5vZGUobm9kZU5hbWUpOwogICAgICAgICAgICAgICAgc3dpdGNoIChub2RlLnR5cGUpIHsKICAgICAgICAgICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFJlY3Vyc2l2ZWx5IGR1cGxpY2F0ZSB0aGUgbWV0YW5vZGUuCiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IG5ld05vZGUgPSB0aGlzLmNsb25lRnVuY3Rpb25MaWJyYXJ5TWV0YW5vZGVIZWxwZXIobWV0YWdyYXBoLCBvcE5vZGVUb1JlcGxhY2UsIG5vZGUsIG9sZFByZWZpeCwgbmV3UHJlZml4LCBmdW5jdGlvbk91dHB1dEluZGV4VG9Ob2RlKTsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gQWRkIHRoZSBuZXcgbm9kZSB0byB0aGUgZ3JhcGguCiAgICAgICAgICAgICAgICAgICAgICAgIG5ld05vZGUucGFyZW50Tm9kZSA9IG5ld01ldGFub2RlOwogICAgICAgICAgICAgICAgICAgICAgICBuZXdNZXRhbm9kZS5tZXRhZ3JhcGguc2V0Tm9kZShuZXdOb2RlLm5hbWUsIG5ld05vZGUpOwogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmhpZXJhcmNoeS5zZXROb2RlKG5ld05vZGUubmFtZSwgbmV3Tm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuT1A6CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIER1cGxpY2F0ZSB0aGUgb3Agbm9kZS4KICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgbmV3T3BOb2RlID0gdGhpcy5jbG9uZUFuZEFkZEZ1bmN0aW9uT3BOb2RlKG5ld01ldGFub2RlLCBvbGRQcmVmaXgsIG5vZGUsIG5ld1ByZWZpeCk7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNOdW1iZXIobmV3T3BOb2RlLmZ1bmN0aW9uSW5wdXRJbmRleCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgbm9kZSByZXByZXNlbnRzIGFuIGlucHV0X2FyZyBvZiB0aGUgbGlicmFyeSBmdW5jdGlvbi4gR2l2ZQogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gaXQgZWRnZXMgc28gdGhhdCBpdHMgYnJpZGdlIGVkZ2VzIGFyZSBjcmVhdGVkIGNvcnJlY3RseS4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMucGF0Y2hFZGdlc0ludG9GdW5jdGlvbklucHV0cyhvcE5vZGVUb1JlcGxhY2UsIG5ld09wTm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGxvZGFzaC5pc051bWJlcihuZXdPcE5vZGUuZnVuY3Rpb25PdXRwdXRJbmRleCkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uT3V0cHV0SW5kZXhUb05vZGVbbmV3T3BOb2RlLmZ1bmN0aW9uT3V0cHV0SW5kZXhdID0gbmV3T3BOb2RlOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgbG9naWMgc2hvdWxkIG5ldmVyIHJ1biBiZWNhdXNlIHRoZSBtZXRhIGdyYXBoIHNob3VsZCBvbmx5CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIGNvbnRhaW4gbWV0YSBhbmQgb3Agbm9kZXMuCiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnNvbGUud2Fybihub2RlLm5hbWUgKyAnIGlzIG9kZGx5IG5laXRoZXIgYSBtZXRhbm9kZSBub3IgYW4gb3Bub2RlLicpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gQ2xvbmUgdGhlIGVkZ2VzIHdpdGhpbiB0aGUgZnVuY3Rpb24gbGlicmFyeSBtZXRhbm9kZS4KICAgICAgICAgICAgdGhpcy5jbG9uZUxpYnJhcnlNZXRhbm9kZUVkZ2VzKGxpYnJhcnlNZXRhbm9kZSwgbmV3TWV0YW5vZGUsIG9sZFByZWZpeCwgbmV3UHJlZml4KTsKICAgICAgICAgICAgcmV0dXJuIG5ld01ldGFub2RlOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBDbG9uZXMgdGhlIGVkZ2VzIHdpdGhpbiBgbGlicmFyeU1ldGFub2RlYCBhbmQgYWRkcyB0aGVtIHRvIGBuZXdNZXRhbm9kZWAuCiAgICAgICAgICogVGhlIG5hbWVzIG9mIGVkZ2Ugc291cmNlcyBhbmQgZGVzdGluYXRpb25zIGhhdmUgdGhlaXIgcHJlZml4ZXMgcmVwbGFjZWQKICAgICAgICAgKiB3aXRoIG5ldyBwcmVmaXhlcyB0aGF0IHJlZmxlY3QgdGhlaXIgaGllcmFyY2hpY2FsIHBvc2l0aW9ucyBpbiB0aGUgZ3JhcGgKICAgICAgICAgKiBpbnN0ZWFkIG9mIHdpdGhpbiB0aGUgZnVuY3Rpb24gbGlicmFyeSB0ZW1wbGF0ZS4gVGhpcyBpcyBhIHN1YnJvdXRpbmUgZm9yCiAgICAgICAgICogZHluYW1pY2FsbHkgaW5qZWN0aW5nIGEgZnVuY3Rpb24gbWV0YW5vZGUgaW50byB0aGUgZ3JhcGguCiAgICAgICAgICovCiAgICAgICAgY2xvbmVMaWJyYXJ5TWV0YW5vZGVFZGdlcyhsaWJyYXJ5TWV0YW5vZGUsIG5ld01ldGFub2RlLCBvbGRQcmVmaXgsIG5ld1ByZWZpeCkgewogICAgICAgICAgICBsb2Rhc2guZWFjaChsaWJyYXJ5TWV0YW5vZGUubWV0YWdyYXBoLmVkZ2VzKCksIChlZGdlT2JqZWN0KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBlZGdlID0gbGlicmFyeU1ldGFub2RlLm1ldGFncmFwaC5lZGdlKGVkZ2VPYmplY3QpOwogICAgICAgICAgICAgICAgY29uc3QgbmV3ViA9IGVkZ2Uudi5yZXBsYWNlKG9sZFByZWZpeCwgbmV3UHJlZml4KTsKICAgICAgICAgICAgICAgIGNvbnN0IG5ld1cgPSBlZGdlLncucmVwbGFjZShvbGRQcmVmaXgsIG5ld1ByZWZpeCk7CiAgICAgICAgICAgICAgICBjb25zdCBuZXdNZXRhRWRnZSA9IG5ldyBNZXRhZWRnZUltcGwobmV3ViwgbmV3Vyk7CiAgICAgICAgICAgICAgICAvLyBEdXBsaWNhdGUgdmFyaW91cyBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICAgbmV3TWV0YUVkZ2UuaW5ib3VuZCA9IGVkZ2UuaW5ib3VuZDsKICAgICAgICAgICAgICAgIG5ld01ldGFFZGdlLm51bVJlZ3VsYXJFZGdlcyA9IGVkZ2UubnVtUmVndWxhckVkZ2VzOwogICAgICAgICAgICAgICAgbmV3TWV0YUVkZ2UubnVtQ29udHJvbEVkZ2VzID0gZWRnZS5udW1Db250cm9sRWRnZXM7CiAgICAgICAgICAgICAgICBuZXdNZXRhRWRnZS5udW1SZWZFZGdlcyA9IGVkZ2UubnVtUmVmRWRnZXM7CiAgICAgICAgICAgICAgICBuZXdNZXRhRWRnZS50b3RhbFNpemUgPSBlZGdlLnRvdGFsU2l6ZTsKICAgICAgICAgICAgICAgIGlmIChlZGdlLmJhc2VFZGdlTGlzdCkgewogICAgICAgICAgICAgICAgICAgIG5ld01ldGFFZGdlLmJhc2VFZGdlTGlzdCA9IGVkZ2UuYmFzZUVkZ2VMaXN0Lm1hcCgoYmFzZUVkZ2UpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgbmV3QmFzZUVkZ2UgPSBsb2Rhc2guY2xvbmUoYmFzZUVkZ2UpOwogICAgICAgICAgICAgICAgICAgICAgICBuZXdCYXNlRWRnZS52ID0gYmFzZUVkZ2Uudi5yZXBsYWNlKG9sZFByZWZpeCwgbmV3UHJlZml4KTsKICAgICAgICAgICAgICAgICAgICAgICAgbmV3QmFzZUVkZ2UudyA9IGJhc2VFZGdlLncucmVwbGFjZShvbGRQcmVmaXgsIG5ld1ByZWZpeCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBuZXdCYXNlRWRnZTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFNldCB0aGUgZGlyZWN0aW9uIG9mIHRoZSBlZGdlIGJhc2VkIG9uIHdoZXRoZXIgaXQgaXMgaW5ib3VuZC4gVGhlIGVkZ2UKICAgICAgICAgICAgICAgIC8vIGlzIGluYm91bmQgaWYgaXRzIGRlc3RpbmF0aW9uIGlzIHdpdGhpbiB0aGUgbWV0YWdyYXBoLgogICAgICAgICAgICAgICAgaWYgKG5ld01ldGFub2RlLm1ldGFncmFwaC5ub2RlKG5ld1cpKSB7CiAgICAgICAgICAgICAgICAgICAgbmV3TWV0YW5vZGUubWV0YWdyYXBoLnNldEVkZ2UobmV3ViwgbmV3VywgbmV3TWV0YUVkZ2UpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgbmV3TWV0YW5vZGUubWV0YWdyYXBoLnNldEVkZ2UobmV3VywgbmV3ViwgbmV3TWV0YUVkZ2UpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogV2hlbiBhIG1ldGFub2RlIHJlcHJlc2VudGluZyBhIGZ1bmN0aW9uIGlzIGNsb25lZCBhbmQgcGxhY2VkIGludG8gdGhlCiAgICAgICAgICogZ3JhcGgsIHdlIG11c3QgY3JlYXRlIGVkZ2VzIGJldHdlZW4gaW5wdXRzIGludG8gdGhlIGZ1bmN0aW9uIGNhbGwgYW5kIHRoZQogICAgICAgICAqIGlucHV0IG9wcyB3aXRoaW4gdGhlIGZ1bmN0aW9uLiBUaGlzIGZ1bmN0aW9uIHBlcmZvcm1zIHRoYXQgcGF0Y2hpbmcuCiAgICAgICAgICovCiAgICAgICAgcGF0Y2hFZGdlc0ludG9GdW5jdGlvbklucHV0cyhvcE5vZGVUb1JlcGxhY2UsIG5ld09wTm9kZSkgewogICAgICAgICAgICAvLyBJZiB0aGUgbGFzdCBmZXcgcmF3IGlucHV0cyBhcmUgdGhlIHNhbWUgbm9kZSwgcHJldmlvdXMgZ3JhcGggbG9naWMKICAgICAgICAgICAgLy8gY29sbGFwc2VzIHRoZW0gaW50byBhIHNpbmdsZSBub3JtYWxpemVkIGlucHV0LgogICAgICAgICAgICBsZXQgaW5wdXRJbmRleCA9IE1hdGgubWluKG5ld09wTm9kZS5mdW5jdGlvbklucHV0SW5kZXgsIG9wTm9kZVRvUmVwbGFjZS5pbnB1dHMubGVuZ3RoIC0gMSk7CiAgICAgICAgICAgIGxldCBuZXdJbnB1dCA9IGxvZGFzaC5jbG9uZShvcE5vZGVUb1JlcGxhY2UuaW5wdXRzW2lucHV0SW5kZXhdKTsKICAgICAgICAgICAgd2hpbGUgKG5ld0lucHV0LmlzQ29udHJvbERlcGVuZGVuY3kpIHsKICAgICAgICAgICAgICAgIC8vIElnbm9yZSBjb250cm9sIGRlcGVuZGVuY2llcyAtIHRoZXkgYXJlIG5vdCBhc3NpZ25lZCB0bwogICAgICAgICAgICAgICAgLy8gaW5wdXRfYXJncy4KICAgICAgICAgICAgICAgIGlucHV0SW5kZXgrKzsKICAgICAgICAgICAgICAgIG5ld0lucHV0ID0gb3BOb2RlVG9SZXBsYWNlLmlucHV0c1tpbnB1dEluZGV4XTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDbG9uZSB0aGUgbm9ybWFsaXplZCBpbnB1dCBvYmplY3QuCiAgICAgICAgICAgIG5ld09wTm9kZS5pbnB1dHMucHVzaChuZXdJbnB1dCk7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB2YWx1ZXMgaW4gdGhlIGNvcnJlc3BvbmRpbmcgZWRnZSBpbiB0aGUgaGlnaC1sZXZlbAogICAgICAgICAgICAvLyBtZXRhZ3JhcGguCiAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsTWV0YUVkZ2VzID0gdGhpcy5oaWVyYXJjaHkuZ2V0UHJlZGVjZXNzb3JzKG9wTm9kZVRvUmVwbGFjZS5uYW1lKTsKICAgICAgICAgICAgLy8gRmluZCB0aGUgbWV0YWVkZ2UgdGhhdCB0aGUgaW5wdXQgaW5kZXggY29ycmVzcG9uZHMgdG8uCiAgICAgICAgICAgIC8vIEEgbWV0YWVkZ2UgbWF5IGNvcnJlc3BvbmQgdG8gc2V2ZXJhbCBlZGdlcy4gRm9yIGluc3RhbmNlLAogICAgICAgICAgICAvLyBhbiBlZGdlIG1heSBlbnRlciBhIHNlcmllcyBub2RlLgogICAgICAgICAgICBsZXQgb3JpZ2luYWxNZXRhRWRnZTsKICAgICAgICAgICAgbGV0IHJlZ3VsYXJFZGdlQ291bnQgPSAwOwogICAgICAgICAgICBsb2Rhc2guZWFjaChvcmlnaW5hbE1ldGFFZGdlcy5yZWd1bGFyLCAobWV0YUVkZ2UpID0+IHsKICAgICAgICAgICAgICAgIHJlZ3VsYXJFZGdlQ291bnQgKz0gbWV0YUVkZ2UubnVtUmVndWxhckVkZ2VzOwogICAgICAgICAgICAgICAgaWYgKHJlZ3VsYXJFZGdlQ291bnQgPiBpbnB1dEluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgb3JpZ2luYWxNZXRhRWRnZSA9IG1ldGFFZGdlOwogICAgICAgICAgICAgICAgICAgIC8vIFRlcm1pbmF0ZSB0aGUgbG9vcC4KICAgICAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBBbHNvIGNoYW5nZSBhbnkgYmFzZSBlZGdlcyB0aGF0IHBvaW50IGludG8gdGhlIG9yaWdpbmFsIG5vZGUgdG8KICAgICAgICAgICAgLy8gcG9pbnQgdG8gdGhlIGlucHV0IGFyZyB3aXRoaW4gdGhlIGZ1bmN0aW9uLiBUaGVzZSBhcmUgdXNlZCB0bwogICAgICAgICAgICAvLyBtYWtlIGJyaWRnZSBlZGdlcy4KICAgICAgICAgICAgbG9kYXNoLmVhY2gob3JpZ2luYWxNZXRhRWRnZS5iYXNlRWRnZUxpc3QsIChlZGdlKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAoZWRnZS53ID09PSBvcE5vZGVUb1JlcGxhY2UubmFtZSkgewogICAgICAgICAgICAgICAgICAgIGVkZ2UudyA9IG5ld09wTm9kZS5uYW1lOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGVkZ2UudiA9PT0gb3BOb2RlVG9SZXBsYWNlLm5hbWUpIHsKICAgICAgICAgICAgICAgICAgICBlZGdlLnYgPSBuZXdPcE5vZGUubmFtZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFdoZW4gYSBtZXRhbm9kZSByZXByZXNlbnRpbmcgYSBmdW5jdGlvbiBpcyBjbG9uZWQgYW5kIHBsYWNlZCBpbnRvIHRoZQogICAgICAgICAqIGdyYXBoLCB3ZSBtdXN0IGNyZWF0ZSBlZGdlcyBiZXR3ZWVuIG91dHB1dCBvcHMgd2l0aGluIHRoZSBuZXcgZnVuY3Rpb24KICAgICAgICAgKiBtZXRhbm9kZSB0byBpdHMgc3VjY2Vzc29ycy4gVGhpcyBmdW5jdGlvbiBkb2VzIHRoYXQgYWZ0ZXIgc2Nhbm5pbmcgdGhlCiAgICAgICAgICogc3VjY2Vzc29ycyBvZiB0aGUgZnVuY3Rpb24gY2FsbC4KICAgICAgICAgKi8KICAgICAgICBwYXRjaEVkZ2VzRnJvbUZ1bmN0aW9uT3V0cHV0cyhvcE5vZGVUb1JlcGxhY2UsIGZ1bmN0aW9uT3V0cHV0SW5kZXhUb0Rlc3RpbmF0aW9uTm9kZSkgewogICAgICAgICAgICAvLyBDb25uZWN0IHRoZSBvdXRwdXRzIG9mIHRoZSBmdW5jdGlvbiB0byBvdGhlciBvcHMuCiAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsTWV0YUVkZ2VzID0gdGhpcy5oaWVyYXJjaHkuZ2V0U3VjY2Vzc29ycyhvcE5vZGVUb1JlcGxhY2UubmFtZSk7CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKG9yaWdpbmFsTWV0YUVkZ2VzLnJlZ3VsYXIsIChtZXRhZWRnZSkgPT4gewogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gobWV0YWVkZ2UuYmFzZUVkZ2VMaXN0LCAoYmFzZUVkZ2UpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBEZXN0aW5hdGlvbiBub2RlcyB3aXRoaW4gcmVndWxhciBiYXNlIGVkZ2VzIGFyZSBvcCBub2Rlcy4KICAgICAgICAgICAgICAgICAgICBjb25zdCBkZXN0aW5hdGlvbk5vZGUgPSB0aGlzLmhpZXJhcmNoeS5ub2RlKGJhc2VFZGdlLncpOwogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKGRlc3RpbmF0aW9uTm9kZS5pbnB1dHMsIChub3JtYWxpemVkSW5wdXQpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gSWYgYW4gb3V0cHV0IG9mIHRoZSBmdW5jdGlvbiBpcyBhbiBpbnB1dCBpbnRvIHRoZSBvcCwgbWFwIGl0IGJhY2sKICAgICAgICAgICAgICAgICAgICAgICAgLy8gdG8gdGhlIG91dHB1dCB3aXRoaW4gdGhlIGZ1bmN0aW9uIHNvIGJyaWRnZSBlZGdlcyBhcmUgY29tcHV0ZWQuCiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChub3JtYWxpemVkSW5wdXQubmFtZSA9PT0gb3BOb2RlVG9SZXBsYWNlLm5hbWUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIE1hcCB0aGUgb3V0cHV0IHRlbnNvciBpbmRleCAod2hpY2ggaW4gdGhpcyBjYXNlIGlzIGZvciBzdXJlCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBudW1lcmljIGJlY2F1c2UgaXQgaXMgYW4gb3V0cHV0IG9mIGEgbWV0YW5vZGUpIHRvIHRoZSBjb3JyZWN0CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBmdW5jdGlvbiBvdXRwdXQuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBvdXRwdXROb2RlID0gZnVuY3Rpb25PdXRwdXRJbmRleFRvRGVzdGluYXRpb25Ob2RlW25vcm1hbGl6ZWRJbnB1dC5vdXRwdXRUZW5zb3JLZXldOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgbm9ybWFsaXplZElucHV0Lm5hbWUgPSBvdXRwdXROb2RlLm5hbWU7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub3JtYWxpemVkSW5wdXQub3V0cHV0VGVuc29yS2V5ID0gYmFzZUVkZ2Uub3V0cHV0VGVuc29yS2V5OwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIC8vIE1vZGlmeSB0aGUgbGlzdCBvZiBiYXNlIGVkZ2VzIHRvIHBvaW50IGZyb20gdGhlIG91dHB1dCBzbyB0aGF0IGJyaWRnZQogICAgICAgICAgICAgICAgLy8gZWRnZXMgYXJlIGNvcnJlY3QuCiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChtZXRhZWRnZS5iYXNlRWRnZUxpc3QsIChiYXNlRWRnZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGJhc2VFZGdlLnYgPQogICAgICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbk91dHB1dEluZGV4VG9EZXN0aW5hdGlvbk5vZGVbYmFzZUVkZ2Uub3V0cHV0VGVuc29yS2V5XS5uYW1lOwogICAgICAgICAgICAgICAgICAgIGJhc2VFZGdlLm91dHB1dFRlbnNvcktleSA9ICcwJzsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgYnVpbGRTdWJoaWVyYXJjaHkobm9kZU5hbWUpIHsKICAgICAgICAgICAgLy8gVGVybWluYXRlIGlmIHRoZSByZW5kZXJpbmcgaGllcmFyY2h5IHdhcyBhbHJlYWR5IGNvbnN0cnVjdGVkCiAgICAgICAgICAgIC8vIGZvciB0aGlzIG5vZGUuCiAgICAgICAgICAgIGlmIChub2RlTmFtZSBpbiB0aGlzLmhhc1N1YmhpZXJhcmNoeSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFJlY29yZCB0aGF0IHdlIGNvbnN0cnVjdGVkIHRoZSByZW5kZXJpbmcgaGllcmFyY2h5IGZvciB0aGlzIG5vZGUsIHNvIHdlCiAgICAgICAgICAgIC8vIGRvbid0IGNvbnN0cnVjdCBpdCBhbm90aGVyIHRpbWUuCiAgICAgICAgICAgIHRoaXMuaGFzU3ViaGllcmFyY2h5W25vZGVOYW1lXSA9IHRydWU7CiAgICAgICAgICAgIGxldCByZW5kZXJOb2RlSW5mbyA9IHRoaXMuaW5kZXhbbm9kZU5hbWVdOwogICAgICAgICAgICAvLyBJZiBpdCBpcyBub3QgYSBtZXRhIG5vZGUgb3IgYSBzZXJpZXMgbm9kZSwgZG9uJ3QgZG8gYW55dGhpbmcuCiAgICAgICAgICAgIGlmIChyZW5kZXJOb2RlSW5mby5ub2RlLnR5cGUgIT09IE5vZGVUeXBlLk1FVEEgJiYKICAgICAgICAgICAgICAgIHJlbmRlck5vZGVJbmZvLm5vZGUudHlwZSAhPT0gTm9kZVR5cGUuU0VSSUVTKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQXQgdGhpcyBwb2ludCB3ZSBrbm93IHRoZSByZW5kZXJpbmcgaW5mb3JtYXRpb24gaXMgYWJvdXQgYSBncm91cCBub2RlLgogICAgICAgICAgICBsZXQgcmVuZGVyR3JvdXBOb2RlSW5mbyA9IHJlbmRlck5vZGVJbmZvOwogICAgICAgICAgICBsZXQgbWV0YWdyYXBoID0gcmVuZGVyR3JvdXBOb2RlSW5mby5ub2RlLm1ldGFncmFwaDsKICAgICAgICAgICAgbGV0IGNvcmVHcmFwaCA9IHJlbmRlckdyb3VwTm9kZUluZm8uY29yZUdyYXBoOwogICAgICAgICAgICBjb25zdCBub2Rlc1RoYXRHb3RDbG9uZWQgPSBbXTsKICAgICAgICAgICAgY29uc3QgZnVuY3Rpb25DYWxsTWV0YW5vZGVzVG9BZGQgPSBbXTsKICAgICAgICAgICAgaWYgKCFsb2Rhc2guaXNFbXB0eSh0aGlzLmhpZXJhcmNoeS5saWJyYXJ5RnVuY3Rpb25zKSkgewogICAgICAgICAgICAgICAgLy8gVGhpcyBncmFwaCBoYXMgbGlicmFyeSBmdW5jdGlvbnMuIEFkZCB0aGVtIHRvIHRoZSBjdXJyZW50CiAgICAgICAgICAgICAgICAvLyBzdWItaGllcmFyY2h5IGlmIG5lY2Vzc2FyeS4KICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKG1ldGFncmFwaC5ub2RlcygpLCAoY2hpbGROYW1lKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgLy8gV2h5IGlzIHRoaXMgc28gb2Z0ZW4gdW5kZWZpbmVkPwogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsTm9kZSA9IG1ldGFncmFwaC5ub2RlKGNoaWxkTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgbGlicmFyeUZ1bmN0aW9uRGF0YSA9IHRoaXMuaGllcmFyY2h5LmxpYnJhcnlGdW5jdGlvbnNbb3JpZ2luYWxOb2RlLm9wXTsKICAgICAgICAgICAgICAgICAgICBpZiAoIWxpYnJhcnlGdW5jdGlvbkRhdGEpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyBub2RlIGlzIG5vdCBhIGZ1bmN0aW9uIGNhbGwuCiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgaWYgKGNoaWxkTmFtZS5pbmRleE9mKEZVTkNUSU9OX0xJQlJBUllfTk9ERV9QUkVGSVgpID09PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIERvIG5vdCByZXBsYWNlIGxpYnJhcnkgZnVuY3Rpb25zIGluIHRoZSBncmFwaC4gVGhlIGxpYnJhcnkKICAgICAgICAgICAgICAgICAgICAgICAgLy8gZnVuY3Rpb25zIHNlcnZlIGFzIHRlbXBsYXRlcyBmb3Igb3RoZXIgbm9kZXMuCiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgLy8gV2UgbGF0ZXIgcmVwbGFjZSB0aGUgbm9kZSB0aGF0IGlzIGEgZnVuY3Rpb24gY2FsbCB3aXRoIGEgY29weSBvZiB0aGUKICAgICAgICAgICAgICAgICAgICAvLyBmdW5jdGlvbiBtZXRhZ3JhcGguIFdlIGRvIG5vdCBkbyBzbyBub3cgYmVjYXVzZSB3ZSBhcmUgYWxzbyBsb29waW5nCiAgICAgICAgICAgICAgICAgICAgLy8gdGhyb3VnaCBhbGwgdGhlIG5vZGVzLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IGNsb25lZE1ldGFub2RlID0gdGhpcy5jbG9uZUZ1bmN0aW9uTGlicmFyeU1ldGFub2RlKG1ldGFncmFwaCwgb3JpZ2luYWxOb2RlLCBsaWJyYXJ5RnVuY3Rpb25EYXRhLm5vZGUsIGxpYnJhcnlGdW5jdGlvbkRhdGEubm9kZS5uYW1lLCBvcmlnaW5hbE5vZGUubmFtZSk7CiAgICAgICAgICAgICAgICAgICAgbm9kZXNUaGF0R290Q2xvbmVkLnB1c2gob3JpZ2luYWxOb2RlKTsKICAgICAgICAgICAgICAgICAgICBmdW5jdGlvbkNhbGxNZXRhbm9kZXNUb0FkZC5wdXNoKGNsb25lZE1ldGFub2RlKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgLy8gUGVyZm9ybSBub2RlIHJlcGxhY2VtZW50LgogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2goZnVuY3Rpb25DYWxsTWV0YW5vZGVzVG9BZGQsIChjbG9uZWRNZXRhbm9kZSwgaSkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsTm9kZSA9IG5vZGVzVGhhdEdvdENsb25lZFtpXTsKICAgICAgICAgICAgICAgICAgICBjbG9uZWRNZXRhbm9kZS5wYXJlbnROb2RlID0gb3JpZ2luYWxOb2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgICAgICAgICAgbWV0YWdyYXBoLnNldE5vZGUob3JpZ2luYWxOb2RlLm5hbWUsIGNsb25lZE1ldGFub2RlKTsKICAgICAgICAgICAgICAgICAgICB0aGlzLmhpZXJhcmNoeS5zZXROb2RlKG9yaWdpbmFsTm9kZS5uYW1lLCBjbG9uZWRNZXRhbm9kZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDcmVhdGUgcmVuZGVyIG5vZGVzIHRvIHJlcHJlc2VudCBlYWNoIGNoaWxkIGZyb20gdGhlIG1ldGFncmFwaC4gQWx0aG91Z2gKICAgICAgICAgICAgLy8gdGhlc2Ugd2lsbCBpbml0aWFsbHkgYmUgYWRkZWQgdG8gdGhlIGNvcmVHcmFwaCwgdGhleSBtYXkgbGF0ZXIgYmUKICAgICAgICAgICAgLy8gZXh0cmFjdGVkLiBBbHNvLCBkdWUgdG8gZXh0cmFjdGlvbiwgdGhlIGNvcmVHcmFwaCBtYXkgY29udGFpbiBkaXNqb2ludAogICAgICAgICAgICAvLyBncm91cHMgYmV0d2VlbiB3aGljaCB0aGVyZSBpcyBubyB2aXNpYmxlIHBhdGggKG90aGVyIHRoYW4gYW5ub3RhdGlvbnMpLgogICAgICAgICAgICBsb2Rhc2guZWFjaChtZXRhZ3JhcGgubm9kZXMoKSwgKGNoaWxkTmFtZSkgPT4gewogICAgICAgICAgICAgICAgbGV0IGNoaWxkUmVuZGVySW5mbyA9IHRoaXMuZ2V0T3JDcmVhdGVSZW5kZXJOb2RlQnlOYW1lKGNoaWxkTmFtZSk7CiAgICAgICAgICAgICAgICBsZXQgY2hpbGROb2RlID0gY2hpbGRSZW5kZXJJbmZvLm5vZGU7CiAgICAgICAgICAgICAgICBjb3JlR3JhcGguc2V0Tm9kZShjaGlsZE5hbWUsIGNoaWxkUmVuZGVySW5mbyk7CiAgICAgICAgICAgICAgICBpZiAoIWNoaWxkTm9kZS5pc0dyb3VwTm9kZSkgewogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKGNoaWxkTm9kZS5pbkVtYmVkZGluZ3MsIChlbWJlZGRpbmcpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IHJlbmRlck1ldGFlZGdlSW5mbyA9IG5ldyBSZW5kZXJNZXRhZWRnZUluZm8obnVsbCk7CiAgICAgICAgICAgICAgICAgICAgICAgIGxldCByZW5kZXJOb2RlSW5mbyA9IG5ldyBSZW5kZXJOb2RlSW5mbyhlbWJlZGRpbmcpOwogICAgICAgICAgICAgICAgICAgICAgICBhZGRJbkFubm90YXRpb24oY2hpbGRSZW5kZXJJbmZvLCBlbWJlZGRpbmcsIHJlbmRlck5vZGVJbmZvLCByZW5kZXJNZXRhZWRnZUluZm8sIEFubm90YXRpb25UeXBlLkNPTlNUQU5UKTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5pbmRleFtlbWJlZGRpbmcubmFtZV0gPSByZW5kZXJOb2RlSW5mbzsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChjaGlsZE5vZGUub3V0RW1iZWRkaW5ncywgKGVtYmVkZGluZykgPT4gewogICAgICAgICAgICAgICAgICAgICAgICBsZXQgcmVuZGVyTWV0YWVkZ2VJbmZvID0gbmV3IFJlbmRlck1ldGFlZGdlSW5mbyhudWxsKTsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IHJlbmRlck5vZGVJbmZvID0gbmV3IFJlbmRlck5vZGVJbmZvKGVtYmVkZGluZyk7CiAgICAgICAgICAgICAgICAgICAgICAgIGFkZE91dEFubm90YXRpb24oY2hpbGRSZW5kZXJJbmZvLCBlbWJlZGRpbmcsIHJlbmRlck5vZGVJbmZvLCByZW5kZXJNZXRhZWRnZUluZm8sIEFubm90YXRpb25UeXBlLlNVTU1BUlkpOwogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmluZGV4W2VtYmVkZGluZy5uYW1lXSA9IHJlbmRlck5vZGVJbmZvOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gQWRkIHJlbmRlciBtZXRhZWRnZSBpbmZvIGZvciBlZGdlcyBpbiB0aGUgbWV0YWdyYXBoLgogICAgICAgICAgICBsb2Rhc2guZWFjaChtZXRhZ3JhcGguZWRnZXMoKSwgKGVkZ2VPYmopID0+IHsKICAgICAgICAgICAgICAgIGxldCBtZXRhZWRnZSA9IG1ldGFncmFwaC5lZGdlKGVkZ2VPYmopOwogICAgICAgICAgICAgICAgbGV0IHJlbmRlck1ldGFlZGdlSW5mbyA9IG5ldyBSZW5kZXJNZXRhZWRnZUluZm8obWV0YWVkZ2UpOwogICAgICAgICAgICAgICAgcmVuZGVyTWV0YWVkZ2VJbmZvLmlzRmFkZWRPdXQgPQogICAgICAgICAgICAgICAgICAgIHRoaXMuaW5kZXhbZWRnZU9iai52XS5pc0ZhZGVkT3V0IHx8IHRoaXMuaW5kZXhbZWRnZU9iai53XS5pc0ZhZGVkT3V0OwogICAgICAgICAgICAgICAgY29yZUdyYXBoLnNldEVkZ2UoZWRnZU9iai52LCBlZGdlT2JqLncsIHJlbmRlck1ldGFlZGdlSW5mbyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBpZiAoCiAgICAgICAgICAgICAgICByZW5kZXJHcm91cE5vZGVJbmZvLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICAgICAgZXh0cmFjdEhpZ2hEZWdyZWVzKHJlbmRlckdyb3VwTm9kZUluZm8pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIElmIHRoZXJlIGFyZSBmdW5jdGlvbnMsIGl0IGlzIHBvc3NpYmxlIGZvciBtZXRhbm9kZXMgdG8gYmUgZHluYW1pY2FsbHkKICAgICAgICAgICAgLy8gYWRkZWQgbGF0ZXIuIENvbnN0cnVjdCB0aGUgaGllcmFyY2hpZXMgZm9yIG5vZGVzIHRoYXQgYXJlIHByZWRlY2Vzc29ycyB0bwogICAgICAgICAgICAvLyBub2RlcyBpbiB0aGUgY3VycmVudCBoaWVyYXJjaHkgc28gdGhhdCBlZGdlcyBhcmUgZHJhd24gY29ycmVjdGx5LgogICAgICAgICAgICBpZiAoIWxvZGFzaC5pc0VtcHR5KHRoaXMuaGllcmFyY2h5LmxpYnJhcnlGdW5jdGlvbnMpKSB7CiAgICAgICAgICAgICAgICB0aGlzLmJ1aWxkU3ViaGllcmFyY2hpZXNGb3JOZWVkZWRGdW5jdGlvbnMobWV0YWdyYXBoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAobm9kZU5hbWUgPT09IFJPT1RfTkFNRSkgewogICAgICAgICAgICAgICAgLy8gQWRkIGFsbCBtZXRhbm9kZXMgcmVwcmVzZW50aW5nIGxpYnJhcnkgZnVuY3Rpb24gdGVtcGxhdGVzIGludG8gdGhlCiAgICAgICAgICAgICAgICAvLyBsaWJyYXJ5IGZ1bmN0aW9uIHNjZW5lIGdyb3VwIGZvciB0aGUgcm9vdCBub2RlLgogICAgICAgICAgICAgICAgbG9kYXNoLmZvck93bih0aGlzLmhpZXJhcmNoeS5saWJyYXJ5RnVuY3Rpb25zLCAobGlicmFyeUZ1bmN0aW9uRGF0YSwgZnVuY3Rpb25OYW1lKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3Qgbm9kZSA9IGxpYnJhcnlGdW5jdGlvbkRhdGEubm9kZTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBjaGlsZFJlbmRlckluZm8gPSB0aGlzLmdldE9yQ3JlYXRlUmVuZGVyTm9kZUJ5TmFtZShub2RlLm5hbWUpOwogICAgICAgICAgICAgICAgICAgIHJlbmRlckdyb3VwTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0V4dHJhY3QucHVzaChjaGlsZFJlbmRlckluZm8pOwogICAgICAgICAgICAgICAgICAgIC8vIERvIG5vdCByZW5kZXIgZnVuY3Rpb24gZGVmaW5pdGlvbnMgaW4gdGhlIGNvcmUgZ3JhcGguCiAgICAgICAgICAgICAgICAgICAgY2hpbGRSZW5kZXJJbmZvLm5vZGUuaW5jbHVkZSA9IEluY2x1c2lvblR5cGUuRVhDTFVERTsKICAgICAgICAgICAgICAgICAgICBjb3JlR3JhcGgucmVtb3ZlTm9kZShub2RlLm5hbWUpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gTG9vayB1cCB0aGUgcGFyZW50IG5vZGUncyByZW5kZXIgaW5mb3JtYXRpb24gYW5kIHNob3J0IGNpcmN1aXQgaWYgbm9uZS4KICAgICAgICAgICAgbGV0IHBhcmVudE5vZGUgPSByZW5kZXJHcm91cE5vZGVJbmZvLm5vZGUucGFyZW50Tm9kZTsKICAgICAgICAgICAgaWYgKCFwYXJlbnROb2RlKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IHBhcmVudE5vZGVJbmZvID0gdGhpcy5pbmRleFtwYXJlbnROb2RlLm5hbWVdOwogICAgICAgICAgICAvLyBVdGlsaXR5IGZ1bmN0aW9uIGZvciBjb21wdXRpbmcgdGhlIG5hbWUgb2YgYSBicmlkZ2Ugbm9kZS4KICAgICAgICAgICAgbGV0IGdldEJyaWRnZU5vZGVOYW1lID0gKGluYm91bmQsIC4uLnJlc3QpID0+IHJlc3QuY29uY2F0KFtpbmJvdW5kID8gJ0lOJyA6ICdPVVQnXSkuam9pbignfn4nKTsKICAgICAgICAgICAgLy8gQnVpbGQgb3V0IHRoZSBicmlkZ2VncmFwaC4KICAgICAgICAgICAgbGV0IGJyaWRnZWdyYXBoID0gdGhpcy5oaWVyYXJjaHkuZ2V0QnJpZGdlZ3JhcGgobm9kZU5hbWUpOwogICAgICAgICAgICAvLyBMb29rIGZvciBwb3B1bGFyIG5vZGVzIHNvIHdlIGNhbiBtYWtlIGFubm90YXRpb25zIGluc3RlYWQgb2YgcGF0aHMuCiAgICAgICAgICAgIGxldCBvdGhlckNvdW50cyA9IHsKICAgICAgICAgICAgICAgIC8vIENvdW50cyBvZiBlZGdlcyBjb21pbmcgSU5UTyBvdGhlciBub2RlcyBieSBuYW1lIChvdXRnb2luZyBmcm9tIHNlbGYpLgogICAgICAgICAgICAgICAgaW46IHt9LAogICAgICAgICAgICAgICAgLy8gQ291bnRzIG9mIGVkZ2VzIGdvaW5nIE9VVCBmcm9tIG90aGVyIG5vZGVzIGJ5IG5hbWUgKGNvbWluZyBpbnRvIHNlbGYpLgogICAgICAgICAgICAgICAgb3V0OiB7fSwKICAgICAgICAgICAgICAgIC8vIENvdW50cyBvZiBhbGwgY29udHJvbCBlZGdlcyBpbnZvbHZpbmcgb3RoZXIgbm9kZXMgYnkgbmFtZS4KICAgICAgICAgICAgICAgIGNvbnRyb2w6IHt9LAogICAgICAgICAgICB9OwogICAgICAgICAgICBsb2Rhc2guZWFjaChicmlkZ2VncmFwaC5lZGdlcygpLCAoZSkgPT4gewogICAgICAgICAgICAgICAgLy8gQW4gZWRnZSBpcyBpbmJvdW5kIGlmIGl0cyBkZXN0aW5hdGlvbiBub2RlIGlzIGluIHRoZSBtZXRhZ3JhcGguCiAgICAgICAgICAgICAgICBsZXQgaW5ib3VuZCA9ICEhbWV0YWdyYXBoLm5vZGUoZS53KTsKICAgICAgICAgICAgICAgIGxldCBvdGhlck5hbWUgPSBpbmJvdW5kID8gZS52IDogZS53OwogICAgICAgICAgICAgICAgbGV0IG1ldGFlZGdlID0gYnJpZGdlZ3JhcGguZWRnZShlKTsKICAgICAgICAgICAgICAgIGlmICghbWV0YWVkZ2UubnVtUmVndWxhckVkZ2VzKSB7CiAgICAgICAgICAgICAgICAgICAgb3RoZXJDb3VudHMuY29udHJvbFtvdGhlck5hbWVdID0KICAgICAgICAgICAgICAgICAgICAgICAgKG90aGVyQ291bnRzLmNvbnRyb2xbb3RoZXJOYW1lXSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChpbmJvdW5kKSB7CiAgICAgICAgICAgICAgICAgICAgb3RoZXJDb3VudHMub3V0W290aGVyTmFtZV0gPSAob3RoZXJDb3VudHMub3V0W290aGVyTmFtZV0gfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgb3RoZXJDb3VudHMuaW5bb3RoZXJOYW1lXSA9IChvdGhlckNvdW50cy5pbltvdGhlck5hbWVdIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIEFkZCBhbm5vdGF0aW9ucyBhbmQgZWRnZXMgZm9yIGJyaWRnZWdyYXBoIHJlbGF0aW9uc2hpcHMuCiAgICAgICAgICAgIGxldCBoaWVyYXJjaHlOb2RlTWFwID0gdGhpcy5oaWVyYXJjaHkuZ2V0Tm9kZU1hcCgpOwogICAgICAgICAgICBsb2Rhc2guZWFjaChicmlkZ2VncmFwaC5lZGdlcygpLCAoYnJpZGdlRWRnZU9iaikgPT4gewogICAgICAgICAgICAgICAgbGV0IGJyaWRnZU1ldGFlZGdlID0gYnJpZGdlZ3JhcGguZWRnZShicmlkZ2VFZGdlT2JqKTsKICAgICAgICAgICAgICAgIC8vIERldGVybWluZSB3aGV0aGVyIHRoaXMgYnJpZGdlIGVkZ2UgaXMgaW5jb21pbmcgYnkgY2hlY2tpbmcgdGhlCiAgICAgICAgICAgICAgICAvLyBtZXRhZ3JhcGggZm9yIGEgbm9kZSB0aGF0IG1hdGNoZXMgdGhlIGRlc3RpbmF0aW9uIGVuZC4KICAgICAgICAgICAgICAgIGxldCBpbmJvdW5kID0gISFtZXRhZ3JhcGgubm9kZShicmlkZ2VFZGdlT2JqLncpOwogICAgICAgICAgICAgICAgLy8gQmFzZWQgb24gdGhlIGRpcmVjdGlvbiBvZiB0aGUgZWRnZSwgb25lIGVuZHBvaW50IHdpbGwgYmUgYW4gaW1tZWRpYXRlCiAgICAgICAgICAgICAgICAvLyBjaGlsZCBvZiB0aGlzIHJlbmRlck5vZGVJbmZvLCBhbmQgdGhlIG90aGVyIGVuZHBvaW50IHdpbGwgYmUgYSBzaWJsaW5nCiAgICAgICAgICAgICAgICAvLyBvZiB0aGUgcGFyZW50IChvciBhbiBhbmNlc3RvciBmdXJ0aGVyIHVwKS4KICAgICAgICAgICAgICAgIGxldCBbY2hpbGROYW1lLCBvdGhlck5hbWVdID0gaW5ib3VuZAogICAgICAgICAgICAgICAgICAgID8gW2JyaWRnZUVkZ2VPYmoudywgYnJpZGdlRWRnZU9iai52XQogICAgICAgICAgICAgICAgICAgIDogW2JyaWRnZUVkZ2VPYmoudiwgYnJpZGdlRWRnZU9iai53XTsKICAgICAgICAgICAgICAgIGxldCBjaGlsZFJlbmRlckluZm8gPSB0aGlzLmluZGV4W2NoaWxkTmFtZV07CiAgICAgICAgICAgICAgICBsZXQgb3RoZXJSZW5kZXJJbmZvID0gdGhpcy5pbmRleFtvdGhlck5hbWVdOwogICAgICAgICAgICAgICAgbGV0IG90aGVyTm9kZSA9IG90aGVyUmVuZGVySW5mbwogICAgICAgICAgICAgICAgICAgID8gb3RoZXJSZW5kZXJJbmZvLm5vZGUKICAgICAgICAgICAgICAgICAgICA6IGhpZXJhcmNoeU5vZGVNYXBbb3RoZXJOYW1lXTsKICAgICAgICAgICAgICAgIC8vIERldGVybWluZSB3aGV0aGVyIHRoaXMgZWRnZSBpcyBhIGNvbnRyb2wgZWRnZSBiZXR3ZWVuIG5vZGVzIHdoZXJlCiAgICAgICAgICAgICAgICAvLyBlaXRoZXIgbm9kZSBpcyBoaWdoLWRlZ3JlZSB3aXRoIHJlc3BlY3QgdG8gY29udHJvbCBlZGdlcy4gVGhpcyB3aWxsCiAgICAgICAgICAgICAgICAvLyBiZSBhIHNpZ25hbCB0byBzaG93IGl0IGFzIGFuIGFubm90YXRpb24gaW5zdGVhZCBvZiBhIGJyaWRnZSBlZGdlLgogICAgICAgICAgICAgICAgbGV0IGlzSGlnaERlZ3JlZUNvbnRyb2xFZGdlID0gIWJyaWRnZU1ldGFlZGdlLm51bVJlZ3VsYXJFZGdlcyAmJgogICAgICAgICAgICAgICAgICAgIG90aGVyQ291bnRzLmNvbnRyb2xbb3RoZXJOYW1lXSA+IFBBUkFNUy5tYXhDb250cm9sRGVncmVlOwogICAgICAgICAgICAgICAgbGV0IFssIGNoaWxkQW5ub3RhdGlvbnNdID0gaW5ib3VuZAogICAgICAgICAgICAgICAgICAgID8gW3JlbmRlck5vZGVJbmZvLmluQW5ub3RhdGlvbnMsIGNoaWxkUmVuZGVySW5mby5pbkFubm90YXRpb25zXQogICAgICAgICAgICAgICAgICAgIDogW3JlbmRlck5vZGVJbmZvLm91dEFubm90YXRpb25zLCBjaGlsZFJlbmRlckluZm8ub3V0QW5ub3RhdGlvbnNdOwogICAgICAgICAgICAgICAgLy8gRG9uJ3QgcmVuZGVyIGEgYnJpZGdlIHBhdGggaWYgdGhlIG90aGVyIG5vZGUgaGFzIGluIG9yIG91dCBkZWdyZWUgYWJvdmUKICAgICAgICAgICAgICAgIC8vIGEgdGhyZXNob2xkLCBsZXN0IGJyaWRnZSBwYXRocyBlbWFuYXRpbmcgb3V0IG9mIGEgbWV0YWdyYXBoIGNyb3dkIHVwLAogICAgICAgICAgICAgICAgLy8gYXMgd2FzIHRoZSBjYXNlIGZvciB0aGUgRmF0Y2F0IExTVE0gbHN0bV8xID4gbHN0bV8xIG1ldGFncmFwaC4KICAgICAgICAgICAgICAgIGxldCBvdGhlckRlZ3JlZUNvdW50ID0gKGluYm91bmQgPyBvdGhlckNvdW50cy5vdXQgOiBvdGhlckNvdW50cy5pbilbb3RoZXJOYW1lXTsKICAgICAgICAgICAgICAgIGxldCBpc090aGVySGlnaERlZ3JlZSA9IG90aGVyRGVncmVlQ291bnQgPiBQQVJBTVMubWF4QnJpZGdlUGF0aERlZ3JlZTsKICAgICAgICAgICAgICAgIC8vIFRoZSBhZGpvaW5pbmcgcmVuZGVyIG1ldGFlZGdlIGluZm8gZnJvbSB0aGUgcGFyZW50J3MgY29yZUdyYXBoLCBpZiBhbnkuCiAgICAgICAgICAgICAgICAvLyBJdCB3aWxsIGVpdGhlciBiZSBhIE1ldGFlZGdlIGludm9sdmluZyB0aGlzIG5vZGUgZGlyZWN0bHksIGlmIGl0CiAgICAgICAgICAgICAgICAvLyBwcmV2aW91c2x5IGNhbWUgZnJvbSBhIG1ldGFncmFwaCwgb3IgaXQnbGwgYmUgYSBNZXRhZWRnZSBpbnZvbHZpbmcKICAgICAgICAgICAgICAgIC8vIGEgcHJldmlvdXNseSBjcmVhdGVkIGJyaWRnZSBub2RlIHN0YW5kaW5nIGluIGZvciB0aGUgb3RoZXIgbm9kZS4KICAgICAgICAgICAgICAgIGxldCBhZGpvaW5pbmdNZXRhZWRnZSA9IG51bGw7CiAgICAgICAgICAgICAgICAvLyBXZSBjYW4gb25seSBob3BlIHRvIHJlbmRlciBhIGJyaWRnZSBwYXRoIGlmOgogICAgICAgICAgICAgICAgLy8gIC0gYnJpZGdlZ3JhcGggcGF0aHMgYXJlIGVuYWJsZWQsCiAgICAgICAgICAgICAgICAvLyAgLSB0aGUgb3RoZXIgbm9kZSBpcyBub3QgdG9vIGhpZ2gtZGVncmVlLAogICAgICAgICAgICAgICAgLy8gIC0gdGhlIGNoaWxkIGlzIGluIHRoZSBjb3JlIChub3QgZXh0cmFjdGVkIGZvciBiZWluZyBoaWdoLWRlZ3JlZSksIGFuZAogICAgICAgICAgICAgICAgLy8gIC0gdGhlcmUncyBhIHBhdGggKGluIHRoZSB0cmF2ZXJzYWwgc2Vuc2UpIGJldHdlZW4gY2hpbGQgYW5kIG90aGVyLgogICAgICAgICAgICAgICAgbGV0IGNhbkRyYXdCcmlkZ2VQYXRoID0gZmFsc2U7CiAgICAgICAgICAgICAgICBpZiAoCiAgICAgICAgICAgICAgICAgICAgIWlzT3RoZXJIaWdoRGVncmVlICYmCiAgICAgICAgICAgICAgICAgICAgIWlzSGlnaERlZ3JlZUNvbnRyb2xFZGdlICYmCiAgICAgICAgICAgICAgICAgICAgY2hpbGRSZW5kZXJJbmZvLmlzSW5Db3JlKCkpIHsKICAgICAgICAgICAgICAgICAgICAvLyBVdGlsaXR5IGZ1bmN0aW9uIGZvciBmaW5kaW5nIGFuIGFkam9pbmluZyBtZXRhZWRnZS4KICAgICAgICAgICAgICAgICAgICBsZXQgZmluZEFkam9pbmluZ01ldGFlZGdlID0gKHRhcmdldE5hbWUpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGFkam9pbmluZ0VkZ2VPYmogPSBpbmJvdW5kCiAgICAgICAgICAgICAgICAgICAgICAgICAgICA/IHsgdjogdGFyZ2V0TmFtZSwgdzogbm9kZU5hbWUgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgOiB7IHY6IG5vZGVOYW1lLCB3OiB0YXJnZXROYW1lIH07CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiAocGFyZW50Tm9kZUluZm8uY29yZUdyYXBoLmVkZ2UoYWRqb2luaW5nRWRnZU9iaikpOwogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgYWRqb2luaW5nTWV0YWVkZ2UgPSBmaW5kQWRqb2luaW5nTWV0YWVkZ2Uob3RoZXJOYW1lKTsKICAgICAgICAgICAgICAgICAgICBpZiAoIWFkam9pbmluZ01ldGFlZGdlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGFkam9pbmluZ01ldGFlZGdlID0gZmluZEFkam9pbmluZ01ldGFlZGdlKGdldEJyaWRnZU5vZGVOYW1lKGluYm91bmQsIG90aGVyTmFtZSwgcGFyZW50Tm9kZS5uYW1lKSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGNhbkRyYXdCcmlkZ2VQYXRoID0gISFhZGpvaW5pbmdNZXRhZWRnZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEFsdGhvdWdoIGRhdGFmbG93IGVkZ2VzIGFyZSBhY3ljbGljLCBjb250cm9sIGRlcGVuZGVuY3kgZWRnZXMgbWF5CiAgICAgICAgICAgICAgICAvLyBhY3R1YWxseSBwb2ludCAnYmFja3dhcmRzJyBpbiB0aGUgZ3JhcGguIElmIHRoaXMgYnJpZGdlTWV0YWVkZ2UgaXMKICAgICAgICAgICAgICAgIC8vIGEgY29udHJvbCBkZXBlbmRlbmN5LCB3ZSBuZWVkIHRvIGRldGVybWluZSB3aGV0aGVyIGl0J3MgYmFja3dhcmRzCiAgICAgICAgICAgICAgICAvLyBwb2ludGluZyBzbyB0aGF0IHdlIHJlbmRlciBpdCBhcHByb3ByaWF0ZWx5LgogICAgICAgICAgICAgICAgLy8KICAgICAgICAgICAgICAgIC8vIEZvciBpbnN0YW5jZSwgc2F5IHdlJ3JlIHJlbmRlcmluZyBhIGdyYXBoIHdpdGggbm9kZXMgbmFtZWQgQS9CIGFuZCBaL1ksCiAgICAgICAgICAgICAgICAvLyBhbmQgd2UncmUgY3VycmVudGx5IHJlbmRlcmluZyB0aGUgYnJpZGdlZ3JhcGggZm9yIEEuIEZ1cnRoZXIsIGxldCdzIHNheQogICAgICAgICAgICAgICAgLy8gdGhhdCB0aGVyZSB3YXMgYW4gb3JpZ2luYWwgQmFzZUVkZ2UgZnJvbSBBL0ItPlovWSBhbmQgYSBDT05UUk9MIEVER0UKICAgICAgICAgICAgICAgIC8vIGZyb20gWi9ZPT5BL0IuCiAgICAgICAgICAgICAgICAvLwogICAgICAgICAgICAgICAgLy8gICAgICstLS0tLS0tLS0tLS0tLS0tKwogICAgICAgICAgICAgICAgLy8gICAgIHwgQSAgICAgICAgICAgICAgfAogICAgICAgICAgICAgICAgLy8gICAgIHwgICstLS0tLSsgICAgICAgfCAgICAgICAgICstLS0tLS0rCiAgICAgICAgICAgICAgICAvLyAgICAgfCAgfCBCICAgfD4tLS0tLT58Pi0tLS0tLS0+fCBaICAgIHwKICAgICAgICAgICAgICAgIC8vICAgICB8ICB8ICAgICB8ICAgICAgIHwgICAgICAgICB8ICAgICAgfAogICAgICAgICAgICAgICAgLy8gICAgIHwgIHwgICAgIHwgICAqICAgfCAgICAgICAgIHwgICAgICB8CiAgICAgICAgICAgICAgICAvLyAgICAgfCAgfCAgICAgfDw9PT09PTx8PD09PT09PT08fCAgICAgIHwKICAgICAgICAgICAgICAgIC8vICAgICB8ICArLS0tLS0rICAgICAgIHwgICAgICAgICArLS0tLS0tKwogICAgICAgICAgICAgICAgLy8gICAgICstLS0tLS0tLS0tLS0tLS0tKwogICAgICAgICAgICAgICAgLy8KICAgICAgICAgICAgICAgIC8vIFdoZW4gd2UgcmVuZGVyIHRoZSBzdWJoaWVyYXJjaHkgZm9yIE1ldGFub2RlIEEsIHdlJ2xsIGNvbWUgYWNyb3NzIGEKICAgICAgICAgICAgICAgIC8vIGNvbnRyb2wtb25seSBNZXRhZWRnZSBpbiB0aGUgYnJpZGdlZ3JhcGggZnJvbSBaPT5BL0IgKCopLiBUaGUgcXVlc3Rpb24KICAgICAgICAgICAgICAgIC8vIGlzIHdoZXRoZXIgdGhpcyBlZGdlIGlzIGJhY2t3YXJkcy4KICAgICAgICAgICAgICAgIC8vCiAgICAgICAgICAgICAgICAvLyBUbyBhbnN3ZXIgdGhhdCBxdWVzdGlvbiwgd2UgZm9sbG93IHRoZSBjaGFpbiBvZiBhZGpvaW5pbmcgbWV0YWVkZ2VzCiAgICAgICAgICAgICAgICAvLyB1bnRpbCB3ZSByZWFjaCB0aGUgdG9wbW9zdCBvbmUuIEluIHRoaXMgY2FzZSwgdGhhdCdzIHRoZSBjb250cm9sLW9ubHkKICAgICAgICAgICAgICAgIC8vIE1ldGFlZGdlIFo9PkEgaW4gdGhlIFJPT1QncyBtZXRhZ3JhcGguIFdlIGRldGVybWluZSB0aGF0IHRoaXMgZWRnZQogICAgICAgICAgICAgICAgLy8gaXMgYmFja3dhcmRzIGJ5IGxvb2tpbmcgYXQgdGhlIHRvcG9sb2dpY2FsIG9yZGVyaW5nIG9mIFJPT1QncyBtZXRhZ3JhcGgKICAgICAgICAgICAgICAgIC8vICh3aGljaCBpZ25vcmVzIGNvbnRyb2wgZWRnZXMpIGFuZCBzZWVpbmcgdGhhdCBaIGNvbWVzIEFGVEVSIEEuCiAgICAgICAgICAgICAgICAvLwogICAgICAgICAgICAgICAgLy8gVGhlIHByb3BlcnR5IG9mIGJlaW5nIGJhY2t3YXJkcyBpcyBpbmRlcGVuZGVudCBvZiB3aGV0aGVyIHRoZSBlZGdlCiAgICAgICAgICAgICAgICAvLyBpcyBpbmJvdW5kIG9yIG91dGJvdW5kLiBJbiB0aGUgcHJlY2VkaW5nIGV4YW1wbGUsIGlmIHdlIHdlcmUgYnVpbGRpbmcKICAgICAgICAgICAgICAgIC8vIHRoZSBzdWJoaWVyYXJjaHkgZm9yIFosIHdlJ2QgZmluZCBicmlkZ2UgZWRnZSBaL1k9PkEsIHdhbGsgdG8gaXRzCiAgICAgICAgICAgICAgICAvLyB0b3Btb3N0IGFkam9pbmluZyBtZXRhZWRnZSBaPT5BIGFuZCBkaXNjb3ZlciB0aGF0IGl0J3MgYmFja3dhcmRzLgogICAgICAgICAgICAgICAgbGV0IGJhY2t3YXJkcyA9IGZhbHNlOwogICAgICAgICAgICAgICAgaWYgKGFkam9pbmluZ01ldGFlZGdlICYmICFicmlkZ2VNZXRhZWRnZS5udW1SZWd1bGFyRWRnZXMpIHsKICAgICAgICAgICAgICAgICAgICAvLyBGaW5kIHRoZSB0b3AtbW9zdCBhZGpvaW5pbmcgcmVuZGVyIG1ldGFlZGdlIGluZm9ybWF0aW9uLCBhbmQgdGhlCiAgICAgICAgICAgICAgICAgICAgLy8gR3JvdXBOb2RlIHdob3NlIG1ldGFncmFwaCBtdXN0IGNvbnRhaW4gdGhlIGFzc29jaWF0ZWQgbWV0YWVkZ2UuCiAgICAgICAgICAgICAgICAgICAgbGV0IHRvcEFkam9pbmluZ01ldGFlZGdlID0gYWRqb2luaW5nTWV0YWVkZ2U7CiAgICAgICAgICAgICAgICAgICAgbGV0IHRvcEdyb3VwTm9kZSA9IHBhcmVudE5vZGVJbmZvLm5vZGU7CiAgICAgICAgICAgICAgICAgICAgd2hpbGUgKHRvcEFkam9pbmluZ01ldGFlZGdlLmFkam9pbmluZ01ldGFlZGdlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRvcEFkam9pbmluZ01ldGFlZGdlID0gdG9wQWRqb2luaW5nTWV0YWVkZ2UuYWRqb2luaW5nTWV0YWVkZ2U7CiAgICAgICAgICAgICAgICAgICAgICAgIHRvcEdyb3VwTm9kZSA9IHRvcEdyb3VwTm9kZS5wYXJlbnROb2RlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBDaGVjayBhZ2FpbnN0IHRoZSB0b3BvbG9naWNhbCBvcmRlcmluZyBmb3IgdGhlIHRvcCBub2RlLiBUaGUgY3VycmVudAogICAgICAgICAgICAgICAgICAgIC8vIGJyaWRnZSBtZXRhZWRnZSB3ZSdyZSBldmFsdWF0aW5nIGlzIGJhY2t3YXJkcyBpZiBpdHMgc291cmNlIGNvbWVzCiAgICAgICAgICAgICAgICAgICAgLy8gYWZ0ZXIgaXRzIGRlc3RpbmF0aW9uLgogICAgICAgICAgICAgICAgICAgIGxldCBvcmRlcmluZyA9IHRoaXMuaGllcmFyY2h5LmdldFRvcG9sb2dpY2FsT3JkZXJpbmcodG9wR3JvdXBOb2RlLm5hbWUpOwogICAgICAgICAgICAgICAgICAgIGxldCBlID0gdG9wQWRqb2luaW5nTWV0YWVkZ2UubWV0YWVkZ2U7CiAgICAgICAgICAgICAgICAgICAgYmFja3dhcmRzID0gb3JkZXJpbmdbZS52XSA+IG9yZGVyaW5nW2Uud107CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBSZW5kZXIgYmFja3dhcmRzIGNvbnRyb2wgZWRnZXMgYXMgYW5ub3RhdGlvbnMuCiAgICAgICAgICAgICAgICBjYW5EcmF3QnJpZGdlUGF0aCA9IGNhbkRyYXdCcmlkZ2VQYXRoICYmICFiYWNrd2FyZHM7CiAgICAgICAgICAgICAgICAvLyBJZiB3ZSBjYW4ndCBtYWtlIGEgYnJpZGdlIHBhdGggZm9yIGFueSByZWFzb24sIHRoZW4gd2UgYWRkIGFuCiAgICAgICAgICAgICAgICAvLyBhbm5vdGF0aW9uIGluc3RlYWQuCiAgICAgICAgICAgICAgICBpZiAoIWNhbkRyYXdCcmlkZ2VQYXRoKSB7CiAgICAgICAgICAgICAgICAgICAgY2hpbGRBbm5vdGF0aW9ucy5wdXNoKG5ldyBBbm5vdGF0aW9uKG90aGVyTm9kZSwgb3RoZXJSZW5kZXJJbmZvLCBuZXcgUmVuZGVyTWV0YWVkZ2VJbmZvKGJyaWRnZU1ldGFlZGdlKSwgQW5ub3RhdGlvblR5cGUuU0hPUlRDVVQsIGluYm91bmQpKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBBdCB0aGlzIHBvaW50LCBhbGwgY29uZGl0aW9ucyBoYXZlIGJlZW4gbWV0IGZvciBkcmF3aW5nIGEgYnJpZGdlIHBhdGguCiAgICAgICAgICAgICAgICAvLyBGaW5kIG9yIGNyZWF0ZSB0aGUgSU4vT1VUIG5vZGUgcmVwcmVzZW50aW5nIG90aGVyTm9kZS4KICAgICAgICAgICAgICAgIGxldCBicmlkZ2VDb250YWluZXJOYW1lID0gZ2V0QnJpZGdlTm9kZU5hbWUoaW5ib3VuZCwgbm9kZU5hbWUpOwogICAgICAgICAgICAgICAgbGV0IGJyaWRnZU5vZGVOYW1lID0gZ2V0QnJpZGdlTm9kZU5hbWUoaW5ib3VuZCwgb3RoZXJOYW1lLCBub2RlTmFtZSk7CiAgICAgICAgICAgICAgICBsZXQgYnJpZGdlTm9kZVJlbmRlckluZm8gPSBjb3JlR3JhcGgubm9kZShicmlkZ2VOb2RlTmFtZSk7CiAgICAgICAgICAgICAgICBpZiAoIWJyaWRnZU5vZGVSZW5kZXJJbmZvKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gRmluZCBvciBjcmVhdGUgdGhlIGRpcmVjdGlvbmFsIGNvbnRhaW5lciBmb3IgdGhlIGJyaWRnZSBub2RlLgogICAgICAgICAgICAgICAgICAgIGxldCBicmlkZ2VDb250YWluZXJJbmZvID0gY29yZUdyYXBoLm5vZGUoYnJpZGdlQ29udGFpbmVyTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKCFicmlkZ2VDb250YWluZXJJbmZvKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGxldCBicmlkZ2VDb250YWluZXJOb2RlID0gewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gSW1wb3J0YW50IG5vZGUgcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5hbWU6IGJyaWRnZUNvbnRhaW5lck5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0eXBlOiBOb2RlVHlwZS5CUklER0UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBVbnVzZWQgbm9kZSBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaXNHcm91cE5vZGU6IGZhbHNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgY2FyZGluYWxpdHk6IDAsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnROb2RlOiBudWxsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgc3RhdHM6IG51bGwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpbmNsdWRlOiBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVELAogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gQnJpZGdlTm9kZSBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5ib3VuZDogaW5ib3VuZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5vZGVBdHRyaWJ1dGVzOiB7fSwKICAgICAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICAgICAgYnJpZGdlQ29udGFpbmVySW5mbyA9IG5ldyBSZW5kZXJOb2RlSW5mbyhicmlkZ2VDb250YWluZXJOb2RlKTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5pbmRleFticmlkZ2VDb250YWluZXJOYW1lXSA9IGJyaWRnZUNvbnRhaW5lckluZm87CiAgICAgICAgICAgICAgICAgICAgICAgIGNvcmVHcmFwaC5zZXROb2RlKGJyaWRnZUNvbnRhaW5lck5hbWUsIGJyaWRnZUNvbnRhaW5lckluZm8pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBsZXQgYnJpZGdlTm9kZSA9IHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gSW1wb3J0YW50IG5vZGUgcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgbmFtZTogYnJpZGdlTm9kZU5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgIHR5cGU6IE5vZGVUeXBlLkJSSURHRSwKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVW5pbXBvcnRhbnQgbm9kZSBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICAgICAgICAgICBpc0dyb3VwTm9kZTogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgICAgIGNhcmRpbmFsaXR5OiAxLAogICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnROb2RlOiBudWxsLAogICAgICAgICAgICAgICAgICAgICAgICBzdGF0czogbnVsbCwKICAgICAgICAgICAgICAgICAgICAgICAgaW5jbHVkZTogSW5jbHVzaW9uVHlwZS5VTlNQRUNJRklFRCwKICAgICAgICAgICAgICAgICAgICAgICAgLy8gQnJpZGdlTm9kZSBwcm9wZXJ0aWVzLgogICAgICAgICAgICAgICAgICAgICAgICBpbmJvdW5kOiBpbmJvdW5kLAogICAgICAgICAgICAgICAgICAgICAgICBub2RlQXR0cmlidXRlczoge30sCiAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICBicmlkZ2VOb2RlUmVuZGVySW5mbyA9IG5ldyBSZW5kZXJOb2RlSW5mbyhicmlkZ2VOb2RlKTsKICAgICAgICAgICAgICAgICAgICB0aGlzLmluZGV4W2JyaWRnZU5vZGVOYW1lXSA9IGJyaWRnZU5vZGVSZW5kZXJJbmZvOwogICAgICAgICAgICAgICAgICAgIGNvcmVHcmFwaC5zZXROb2RlKGJyaWRnZU5vZGVOYW1lLCBicmlkZ2VOb2RlUmVuZGVySW5mbyk7CiAgICAgICAgICAgICAgICAgICAgLy8gU2V0IGJyaWRnZU5vZGUgdG8gYmUgYSBncmFwaGxpYiBjaGlsZCBvZiB0aGUgY29udGFpbmVyIG5vZGUuCiAgICAgICAgICAgICAgICAgICAgY29yZUdyYXBoLnNldFBhcmVudChicmlkZ2VOb2RlTmFtZSwgYnJpZGdlQ29udGFpbmVyTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgYnJpZGdlQ29udGFpbmVySW5mby5ub2RlLmNhcmRpbmFsaXR5Kys7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBDcmVhdGUgYW5kIGFkZCBhIGJyaWRnZSByZW5kZXIgbWV0YWVkZ2UuCiAgICAgICAgICAgICAgICBsZXQgYnJpZGdlUmVuZGVyTWV0YWVkZ2UgPSBuZXcgUmVuZGVyTWV0YWVkZ2VJbmZvKGJyaWRnZU1ldGFlZGdlKTsKICAgICAgICAgICAgICAgIGJyaWRnZVJlbmRlck1ldGFlZGdlLmFkam9pbmluZ01ldGFlZGdlID0gYWRqb2luaW5nTWV0YWVkZ2U7CiAgICAgICAgICAgICAgICBpbmJvdW5kCiAgICAgICAgICAgICAgICAgICAgPyBjb3JlR3JhcGguc2V0RWRnZShicmlkZ2VOb2RlTmFtZSwgY2hpbGROYW1lLCBicmlkZ2VSZW5kZXJNZXRhZWRnZSkKICAgICAgICAgICAgICAgICAgICA6IGNvcmVHcmFwaC5zZXRFZGdlKGNoaWxkTmFtZSwgYnJpZGdlTm9kZU5hbWUsIGJyaWRnZVJlbmRlck1ldGFlZGdlKTsKICAgICAgICAgICAgfSk7IC8vIEVuZCBfLmVhY2goYnJpZGdlZ3JhcGguZWRnZXMpLgogICAgICAgICAgICAvLyBGb3IgZWFjaCBicmlkZ2UgY29udGFpbmVyIChJTiBhbmQvb3IgT1VUKSwgYWRkIHN0cnVjdHVyYWwgZWRnZXMgYmV0d2VlbgogICAgICAgICAgICAvLyB0ZXJtaW5hbCBub2RlcyBhbmQgdGhhdCBjb250YWluZXIuIEEgdGVybWluYWwgbm9kZSBpcyBvbmUgd2hpY2ggaGFzIG5vCiAgICAgICAgICAgIC8vIG5vbi1icmlkZ2UgZWRnZXMgaW4gdGhlIGRpcmVjdGlvbiBvZiB0aGUgY29udGFpbmVyLgogICAgICAgICAgICAvLwogICAgICAgICAgICAvLyBGb3IgZXhhbXBsZSwgY29uc2lkZXIgYSBNZXRhbm9kZSBBIHdoaWNoIGNvbnRhaW5zIHR3byBjaGlsZCBub2RlcyBBL0IKICAgICAgICAgICAgLy8gYW5kIEEvQy4gTGV0J3Mgc2F5IGl0IGhhcyBvbmUgZWRnZSBpbiB0aGUgbWV0YWdyYXBoIGZyb20gQS9CLT5BL0MsIGFuZAogICAgICAgICAgICAvLyBvbmUgZWRnZSBpbiB0aGUgYnJpZGdlZ3JhcGggZnJvbSBaLT5BL0MuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIEF0IHRoaXMgcG9pbnQsIHdlJ3ZlIGFkZGVkIGEgY29udGFpbmVyIGJyaWRnZSBub2RlIElOIHRvIGhvdXNlIGFsbAogICAgICAgICAgICAvLyBpbmNvbWluZyBicmlkZ2Ugbm9kZXMuIFdlJ3ZlIGFsc28gYWRkZWQgYSBicmlkZ2Ugbm9kZSBaJyAod2l0aCBwYXJlbnQgSU4pCiAgICAgICAgICAgIC8vIHRvIEEsIGFuZCBhIGJyaWRnZSBlZGdlIGZyb20gWictPkMuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vICAgICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsKICAgICAgICAgICAgLy8gICAgIHwgQSAgICAgICAgICArLS0tKyAgICAgfAogICAgICAgICAgICAvLyAgICAgfCAgICArLS0tLS0tPnwgQyB8ICAgICB8CiAgICAgICAgICAgIC8vICAgICB8ICAgIHwgICAgICAgKy0tLSsgICAgIHwKICAgICAgICAgICAgLy8gICAgIHwgICAgfCAgICAgICAgIF4gICAgICAgfAogICAgICAgICAgICAvLyAgICAgfCAgICB8ICAgICAgICAgfCAgICAgICB8CiAgICAgICAgICAgIC8vICAgICB8ICAgIHwgICAgKy0tLS18LS0tLSsgIHwKICAgICAgICAgICAgLy8gICAgIHwgICAgfCAgICB8IElOIHwgICAgfCAgfAogICAgICAgICAgICAvLyAgICAgfCAgKy0tLSsgIHwgICstLS0rICB8ICB8CiAgICAgICAgICAgIC8vICAgICB8ICB8IEIgfCAgfCAgfCBaJ3wgIHwgIHwKICAgICAgICAgICAgLy8gICAgIHwgICstLS0rICB8ICArLS0tKyAgfCAgfAogICAgICAgICAgICAvLyAgICAgfCAgICAgICAgICstLS0tLS0tLS0rICB8CiAgICAgICAgICAgIC8vICAgICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsKICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gV2l0aCBubyBvdGhlciBoZWxwLCBkYWdyZSB3b3VsZCBsYXkgb3V0IEIgYW5kIFonIG9uIHRoZSBzYW1lIGxldmVsLAogICAgICAgICAgICAvLyBiZWNhdXNlIGJvdGggb2YgdGhlbSBoYXZlIG5vIGluY29taW5nIGVkZ2VzLiBJbiBvdGhlciB3b3JkcywgQiBpcyBhCiAgICAgICAgICAgIC8vIHRlcm1pbmFsIG5vZGUgaW4gdGhlIElOQ09NSU5HIGRpcmVjdGlvbi4KICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gQnV0IHdlIHdhbnQgdG8gZm9yY2UgZGFncmUgdG8gbGF5IG91dCBaJyAoYW5kIGV2ZXJ5dGhpbmcgaW4gSU4pIGxvd2VyCiAgICAgICAgICAgIC8vIHRoYW4gYWxsIG5vbi1icmlkZ2Ugbm9kZXMsIHNvIHRoYXQgdGhlcmUncyBlbm91Z2ggcm9vbSBmb3IgdGhlIGJyaWRnZQogICAgICAgICAgICAvLyBlZGdlcyBhZnRlciB0aGV5J3ZlIGJlZW4gYWRqdXN0ZWQgdG8gbWVldCB1cCB3aXRoIHBhdGhzIGNvbWluZyBpbiBmcm9tCiAgICAgICAgICAgIC8vIG91dHNpZGUuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIFRvIGZvcmNlIFonIChhbmQgYWxsIG90aGVyIGJyaWRnZSBub2RlcykgdG8gYmUgbG93ZXN0IGluIHRoZSBncmFwaCwgd2UKICAgICAgICAgICAgLy8gaWRlbnRpZnkgdGVybWluYWwgbm9kZXMgbGlrZSBCIGFuZCBnaXZlIHRoZW0gc3RydWN0dXJhbCBlZGdlcyB0bwogICAgICAgICAgICAvLyBhIG5ldyBzdHJ1Y3R1cmFsIGJyaWRnZSBub2RlIFMgd2hpY2ggd2UgYWRkIHRvIElOLgogICAgICAgICAgICAvLwogICAgICAgICAgICAvLyAgICAgKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rCiAgICAgICAgICAgIC8vICAgICB8IEEgICAgICAgICAgKy0tLSsgICAgIHwKICAgICAgICAgICAgLy8gICAgIHwgICAgICAgKy0tLT58IEMgfCAgICAgfAogICAgICAgICAgICAvLyAgICAgfCAgICAgICB8ICAgICstLS0rICAgICB8CiAgICAgICAgICAgIC8vICAgICB8ICAgICArLS0tKyAgICBeICAgICAgIHwKICAgICAgICAgICAgLy8gICAgIHwgICAgIHwgQiB8ICAgIHwgICAgICAgfAogICAgICAgICAgICAvLyAgICAgfCAgICAgKy0tLSsgICAgfCAgICAgICB8CiAgICAgICAgICAgIC8vICAgICB8ICAgICAgIF4gICAgICB8ICAgICAgIHwKICAgICAgICAgICAgLy8gICAgIHwgICAgICAgfCAgICAgIHwgICAgICAgfAogICAgICAgICAgICAvLyAgICAgfCAgKy0tLS18LS0tLS0tfC0tLS0rICB8CiAgICAgICAgICAgIC8vICAgICB8ICB8SU4gIHwgICAgICB8ICAgIHwgIHwKICAgICAgICAgICAgLy8gICAgIHwgIHwgICstLS0rICArLS0tKyAgfCAgfAogICAgICAgICAgICAvLyAgICAgfCAgfCAgfCBTIHwgIHwgWid8ICB8ICB8CiAgICAgICAgICAgIC8vICAgICB8ICB8ICArLS0tKyAgKy0tLSsgIHwgIHwKICAgICAgICAgICAgLy8gICAgIHwgICstLS0tLS0tLS0tLS0tLS0tKyAgfAogICAgICAgICAgICAvLyAgICAgKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIFRoaXMgZW5zdXJlcyB0aGF0IGRhZ3JlIHdpbGwgbGF5IG91dCB0aGUgYnJpZGdlIGNvbnRhaW5lcnMgc3RyaWN0bHkgYXQKICAgICAgICAgICAgLy8gdGhlIGVuZHMgb2YgdGhlIGdyYXBoLiBUaGUgc3RydWN0dXJhbCBlZGdlcyB3aWxsIG5ldmVyIGJlIHNlZW4gaW4gdGhlCiAgICAgICAgICAgIC8vIHZpc3VhbGl6YXRpb24gZXhjZXB0IGFzIGEgZGVidWdnaW5nIGFpZC4KICAgICAgICAgICAgbG9kYXNoLmVhY2goW3RydWUsIGZhbHNlXSwgKGluYm91bmQpID0+IHsKICAgICAgICAgICAgICAgIGxldCBicmlkZ2VDb250YWluZXJOYW1lID0gZ2V0QnJpZGdlTm9kZU5hbWUoaW5ib3VuZCwgbm9kZU5hbWUpOwogICAgICAgICAgICAgICAgbGV0IGJyaWRnZUNvbnRhaW5lckluZm8gPSBjb3JlR3JhcGgubm9kZShicmlkZ2VDb250YWluZXJOYW1lKTsKICAgICAgICAgICAgICAgIGlmICghYnJpZGdlQ29udGFpbmVySW5mbykgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKGNvcmVHcmFwaC5ub2RlcygpLCAoY2hpbGROYW1lKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgLy8gU2hvcnQtY2lyY3VpdCBpZiB0aGlzIGNoaWxkIGlzIGEgYnJpZGdlIG5vZGUgb3IgaXQncyBub3QgYSB0ZXJtaW5hbAogICAgICAgICAgICAgICAgICAgIC8vIG5vZGUgaW4gdGhlIGRpcmVjdGlvbiB3ZSdyZSBpbnRlcmVzdGVkIGluLgogICAgICAgICAgICAgICAgICAgIGxldCBjaGlsZE5vZGVJbmZvID0gY29yZUdyYXBoLm5vZGUoY2hpbGROYW1lKTsKICAgICAgICAgICAgICAgICAgICBpZiAoY2hpbGROb2RlSW5mby5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLkJSSURHRSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGxldCBpc1Rlcm1pbmFsID0gaW5ib3VuZAogICAgICAgICAgICAgICAgICAgICAgICA/ICFjb3JlR3JhcGgucHJlZGVjZXNzb3JzKGNoaWxkTmFtZSkubGVuZ3RoCiAgICAgICAgICAgICAgICAgICAgICAgIDogIWNvcmVHcmFwaC5zdWNjZXNzb3JzKGNoaWxkTmFtZSkubGVuZ3RoOwogICAgICAgICAgICAgICAgICAgIGlmICghaXNUZXJtaW5hbCkgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIC8vIEZpbmQgb3IgY3JlYXRlIGEgYnJpZGdlIG5vZGUgaW4gdGhlIGNvbnRhaW5lciBmb3IgYWxsIHN0cnVjdHVyYWwKICAgICAgICAgICAgICAgICAgICAvLyBtZXRhZWRnZXMuIEl0IHdvdWxkIGhhdmUgYmVlbiBuaWNlIHRvIHNraXAgdGhpcyBzdGVwIGFuZCBzaW1wbHkKICAgICAgICAgICAgICAgICAgICAvLyBzZXQgYSBtZXRhZWRnZSBiZXR3ZWVuIHRoZSB0ZXJtaW5hbCBub2RlIGFuZCB0aGUgY29udGFpbmVyIG5vZGUsIGJ1dAogICAgICAgICAgICAgICAgICAgIC8vIGluIHRoYXQgY2FzZSwgc29tZXRoaW5nIGFib3V0IHRoZSBncmFwaCB1cHNldHMgZGFncmUubGF5b3V0KCkncwogICAgICAgICAgICAgICAgICAgIC8vIGxvbmdlc3RQYXRoIGFsZ29yaXRobSAod2FzIGdldHRpbmcgZXJyb3JzIGR1ZSB0byBhbiB1bmRlZmluZWQpLgogICAgICAgICAgICAgICAgICAgIGxldCBzdHJ1Y3R1cmFsTm9kZU5hbWUgPSBnZXRCcmlkZ2VOb2RlTmFtZShpbmJvdW5kLCBub2RlTmFtZSwgJ1NUUlVDVFVSQUxfVEFSR0VUJyk7CiAgICAgICAgICAgICAgICAgICAgbGV0IHN0cnVjdHVyYWxSZW5kZXJJbmZvID0gY29yZUdyYXBoLm5vZGUoc3RydWN0dXJhbE5vZGVOYW1lKTsKICAgICAgICAgICAgICAgICAgICBpZiAoIXN0cnVjdHVyYWxSZW5kZXJJbmZvKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGxldCBicmlkZ2VOb2RlID0gewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gSW1wb3J0YW50IE5vZGUgcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5hbWU6IHN0cnVjdHVyYWxOb2RlTmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHR5cGU6IE5vZGVUeXBlLkJSSURHRSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIFVuaW1wb3J0YW50IE5vZGUgcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlzR3JvdXBOb2RlOiBmYWxzZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNhcmRpbmFsaXR5OiAxLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgcGFyZW50Tm9kZTogbnVsbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHN0YXRzOiBudWxsLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5jbHVkZTogSW5jbHVzaW9uVHlwZS5VTlNQRUNJRklFRCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIEJyaWRnZU5vZGUgcHJvcGVydGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGluYm91bmQ6IGluYm91bmQsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2RlQXR0cmlidXRlczoge30sCiAgICAgICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgICAgIHN0cnVjdHVyYWxSZW5kZXJJbmZvID0gbmV3IFJlbmRlck5vZGVJbmZvKGJyaWRnZU5vZGUpOwogICAgICAgICAgICAgICAgICAgICAgICBzdHJ1Y3R1cmFsUmVuZGVySW5mby5zdHJ1Y3R1cmFsID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5pbmRleFtzdHJ1Y3R1cmFsTm9kZU5hbWVdID0gc3RydWN0dXJhbFJlbmRlckluZm87CiAgICAgICAgICAgICAgICAgICAgICAgIGNvcmVHcmFwaC5zZXROb2RlKHN0cnVjdHVyYWxOb2RlTmFtZSwgc3RydWN0dXJhbFJlbmRlckluZm8pOwogICAgICAgICAgICAgICAgICAgICAgICBicmlkZ2VDb250YWluZXJJbmZvLm5vZGUuY2FyZGluYWxpdHkrKzsKICAgICAgICAgICAgICAgICAgICAgICAgY29yZUdyYXBoLnNldFBhcmVudChzdHJ1Y3R1cmFsTm9kZU5hbWUsIGJyaWRnZUNvbnRhaW5lck5hbWUpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAvLyBDcmVhdGUgdGhlIHN0cnVjdHVyYWwgTWV0YWVkZ2UgYW5kIGluc2VydCBpdC4KICAgICAgICAgICAgICAgICAgICBsZXQgc3RydWN0dXJhbE1ldGFlZGdlSW5mbyA9IG5ldyBSZW5kZXJNZXRhZWRnZUluZm8obnVsbCk7CiAgICAgICAgICAgICAgICAgICAgc3RydWN0dXJhbE1ldGFlZGdlSW5mby5zdHJ1Y3R1cmFsID0gdHJ1ZTsKICAgICAgICAgICAgICAgICAgICBzdHJ1Y3R1cmFsTWV0YWVkZ2VJbmZvLndlaWdodC0tOyAvLyBSZWR1Y2Ugd2VpZ2h0IGZvciBkYWdyZSBsYXlvdXQuCiAgICAgICAgICAgICAgICAgICAgaW5ib3VuZAogICAgICAgICAgICAgICAgICAgICAgICA/IGNvcmVHcmFwaC5zZXRFZGdlKHN0cnVjdHVyYWxOb2RlTmFtZSwgY2hpbGROYW1lLCBzdHJ1Y3R1cmFsTWV0YWVkZ2VJbmZvKQogICAgICAgICAgICAgICAgICAgICAgICA6IGNvcmVHcmFwaC5zZXRFZGdlKGNoaWxkTmFtZSwgc3RydWN0dXJhbE5vZGVOYW1lLCBzdHJ1Y3R1cmFsTWV0YWVkZ2VJbmZvKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogVGhpcyBtZXRob2QgYnVpbGRzIHN1YmhpZXJhcmNoaWVzIGZvciBmdW5jdGlvbiBjYWxscyB0aGF0IGFyZSBuZWVkZWQgZm9yCiAgICAgICAgICogcmVuZGVyaW5nIGVkZ2VzIGluIHRoZSBjdXJyZW50IHN1YmhpZXJhcmNoeSBiZWluZyBidWlsdC4KICAgICAgICAgKgogICAgICAgICAqIFdoZW4gYnVpbGRpbmcgc3ViaGllcmFyY2hpZXMgZm9yIGEgbWV0YWdyYXBoIE0sIHRoZSBzdWJoaWVyYXJjaGllcyBvZgogICAgICAgICAqIG1ldGFub2RlcyBjb250YWluaW5nIGVuZHBvaW50IG5vZGVzIGZvciBlZGdlcyB3aXRoaW4gbWV0YWdyYXBoIE0gbXVzdAogICAgICAgICAqIGFscmVhZHkgYmUgYnVpbHQuIE90aGVyd2lzZSwgYnJpZGdlIGVkZ2VzIHdpbGwgYmUgbWlzc2luZyBmcm9tIHRoZSBncmFwaC4KICAgICAgICAgKi8KICAgICAgICBidWlsZFN1YmhpZXJhcmNoaWVzRm9yTmVlZGVkRnVuY3Rpb25zKG1ldGFncmFwaCkgewogICAgICAgICAgICBsb2Rhc2guZWFjaChtZXRhZ3JhcGguZWRnZXMoKSwgKGVkZ2VPYmopID0+IHsKICAgICAgICAgICAgICAgIGxldCBtZXRhZWRnZSA9IG1ldGFncmFwaC5lZGdlKGVkZ2VPYmopOwogICAgICAgICAgICAgICAgbGV0IHJlbmRlck1ldGFlZGdlSW5mbyA9IG5ldyBSZW5kZXJNZXRhZWRnZUluZm8obWV0YWVkZ2UpOwogICAgICAgICAgICAgICAgbG9kYXNoLmZvckVhY2gocmVuZGVyTWV0YWVkZ2VJbmZvLm1ldGFlZGdlLmJhc2VFZGdlTGlzdCwgKGJhc2VFZGdlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc291cmNlUGF0aExpc3QgPSBiYXNlRWRnZS52LnNwbGl0KE5BTUVTUEFDRV9ERUxJTSk7CiAgICAgICAgICAgICAgICAgICAgZm9yIChsZXQgaSA9IHNvdXJjZVBhdGhMaXN0Lmxlbmd0aDsgaSA+PSAwOyBpLS0pIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZnJvbUJlZ2lubmluZ1BhdGhMaXN0ID0gc291cmNlUGF0aExpc3Quc2xpY2UoMCwgaSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IG5vZGUgPSB0aGlzLmhpZXJhcmNoeS5ub2RlKGZyb21CZWdpbm5pbmdQYXRoTGlzdC5qb2luKE5BTUVTUEFDRV9ERUxJTSkpOwogICAgICAgICAgICAgICAgICAgICAgICBpZiAobm9kZSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG5vZGUudHlwZSA9PT0gTm9kZVR5cGUuT1AgJiYKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB0aGlzLmhpZXJhcmNoeS5saWJyYXJ5RnVuY3Rpb25zW25vZGUub3BdKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZm9yIChsZXQgaiA9IDE7IGogPCBmcm9tQmVnaW5uaW5nUGF0aExpc3QubGVuZ3RoOyBqKyspIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gRXhwYW5kIGFsbCBoaWVyYXJjaGllcyBpbmNsdWRpbmcgdGhlIHBhcmVudC4KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgY3VycmVudE5vZGVOYW1lID0gZnJvbUJlZ2lubmluZ1BhdGhMaXN0CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAuc2xpY2UoMCwgaikKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIC5qb2luKE5BTUVTUEFDRV9ERUxJTSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmICghY3VycmVudE5vZGVOYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBCdWlsZCB0aGUgaGllcmFyY2h5IGZvciB0aGlzIGN1cnJlbnQgbGV2ZWwuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuYnVpbGRTdWJoaWVyYXJjaHkoY3VycmVudE5vZGVOYW1lKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBObyBuZWVkIHRvIGFuYWx5emUgdGhlIG90aGVyIGhpZ2hlciBoaWVyYXJjaGllcy4KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQSBjbGFzcyBmb3IgcmVuZGVyaW5nIGFubm90YXRpb24gb2JqZWN0IHdoaWNoIGNvbnRhaW5zIGxhYmVsCiAgICAgKiBhYm91dCB0aGUgbm9kZSBlbWJlZGRlZCBhcyBhbm5vdGF0aW9uLCB0eXBlIG9mIGFubm90YXRpb24gYW5kIHRoZSBsb2NhdGlvbgogICAgICogb2YgYm90aCB0aGUgYW5ub3RhdGlvbidzIG5vZGUgYW5kIGVkZ2UuCiAgICAgKgogICAgICogQW5ub3RhdGlvbiBvYmplY3RzIGluY2x1ZGUgZW1iZWRkZWQgY29uc3RhbnRzLCBlbWJlZGRlZCBzdW1tYXJ5LCBhbmQKICAgICAqIGVkZ2Ugc2hvcnRjdXRzLgogICAgICovCiAgICBjbGFzcyBBbm5vdGF0aW9uIHsKICAgICAgICAvKioKICAgICAgICAgKiBDcmVhdGVzIGEgbmV3IEFubm90YXRpb24uCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gbm9kZSBUaGUgdW5kZXJseWluZyBub2RlIHRoaXMgYW5ub3RhdGlvbiBwb2ludHMgdG8uCiAgICAgICAgICogQHBhcmFtIHJlbmRlck5vZGVJbmZvIFRoZSByZW5kZXIgaW5mb3JtYXRpb24gZm9yIHRoZSB1bmRlcmx5aW5nIG5vZGUKICAgICAgICAgKiAgICAgdGhpcyBhbm5vdGF0aW9uIHBvaW50cyB0by4gVGhpcyBjYW4gYmUgbnVsbCBpZiB0aGUgYW5ub3RhdGlvbgogICAgICAgICAqICAgICBkZW5vdGVzIGFuIGVtYmVkZGluZyAoY29uc3RhbnQsIHN1bW1hcnkpLCBpbiB3aGljaCBjYXNlIHdlCiAgICAgICAgICogICAgIHVzZSB0aGUgbm9kZSBwcm9wZXJ0eS4KICAgICAgICAgKiBAcGFyYW0gcmVuZGVyTWV0YWVkZ2VJbmZvIFRoZSByZW5kZXIgaW5mb3JtYXRpb24gZm9yIHRoZSBlZGdlIGFzc29jaWF0ZWQKICAgICAgICAgKiAgICAgd2l0aCB0aGUgYW5ub3RhdGlvbi4KICAgICAgICAgKiBAcGFyYW0gdHlwZSBUaGUgdHlwZSBvZiB0aGUgYW5ub3RhdGlvbi4KICAgICAgICAgKiBAcGFyYW0gaXNJbiBUcnVlIGlmIGl0IGlzIGFuIGluLWFubm90YXRpb24uIEZhbHNlIGlmIGl0IGlzIGFuCiAgICAgICAgICogICAgIG91dC1hbm5vdGF0aW9uLgogICAgICAgICAqLwogICAgICAgIGNvbnN0cnVjdG9yKG5vZGUsIHJlbmRlck5vZGVJbmZvLCByZW5kZXJNZXRhZWRnZUluZm8sIHR5cGUsIGlzSW4pIHsKICAgICAgICAgICAgdGhpcy5ub2RlID0gbm9kZTsKICAgICAgICAgICAgdGhpcy5yZW5kZXJOb2RlSW5mbyA9IHJlbmRlck5vZGVJbmZvOwogICAgICAgICAgICB0aGlzLnJlbmRlck1ldGFlZGdlSW5mbyA9IHJlbmRlck1ldGFlZGdlSW5mbzsKICAgICAgICAgICAgdGhpcy5hbm5vdGF0aW9uVHlwZSA9IHR5cGU7CiAgICAgICAgICAgIC8vIFByb3BlcnRpZXMgc3BlY2lmaWVkIGJ5IGxheW91dAogICAgICAgICAgICB0aGlzLmR4ID0gMDsKICAgICAgICAgICAgdGhpcy5keSA9IDA7CiAgICAgICAgICAgIHRoaXMud2lkdGggPSAwOwogICAgICAgICAgICB0aGlzLmhlaWdodCA9IDA7CiAgICAgICAgICAgIC8vIFByb3BlcnRpZXMgbmVlZGVkIGZvciBnZW5lcmF0aW5nIGFuIElEIGZvciB0aGUgZWRnZSdzIHBhdGggZWxlbWVudCBpZgogICAgICAgICAgICAvLyB0aGlzIGFubm90YXRpb24gaXMgYXNzb2NpYXRlZCB3aXRoIGEgbWV0YWVkZ2UuCiAgICAgICAgICAgIGlmIChyZW5kZXJNZXRhZWRnZUluZm8gJiYgcmVuZGVyTWV0YWVkZ2VJbmZvLm1ldGFlZGdlKSB7CiAgICAgICAgICAgICAgICB0aGlzLnYgPSByZW5kZXJNZXRhZWRnZUluZm8ubWV0YWVkZ2UudjsKICAgICAgICAgICAgICAgIHRoaXMudyA9IHJlbmRlck1ldGFlZGdlSW5mby5tZXRhZWRnZS53OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuaXNJbiA9IGlzSW47CiAgICAgICAgICAgIHRoaXMucG9pbnRzID0gW107CiAgICAgICAgfQogICAgfQogICAgdmFyIEFubm90YXRpb25UeXBlOwogICAgKGZ1bmN0aW9uIChBbm5vdGF0aW9uVHlwZSkgewogICAgICAgIEFubm90YXRpb25UeXBlW0Fubm90YXRpb25UeXBlWyJTSE9SVENVVCJdID0gMF0gPSAiU0hPUlRDVVQiOwogICAgICAgIEFubm90YXRpb25UeXBlW0Fubm90YXRpb25UeXBlWyJDT05TVEFOVCJdID0gMV0gPSAiQ09OU1RBTlQiOwogICAgICAgIEFubm90YXRpb25UeXBlW0Fubm90YXRpb25UeXBlWyJTVU1NQVJZIl0gPSAyXSA9ICJTVU1NQVJZIjsKICAgICAgICBBbm5vdGF0aW9uVHlwZVtBbm5vdGF0aW9uVHlwZVsiRUxMSVBTSVMiXSA9IDNdID0gIkVMTElQU0lTIjsKICAgIH0pKEFubm90YXRpb25UeXBlIHx8IChBbm5vdGF0aW9uVHlwZSA9IHt9KSk7CiAgICAvKioKICAgICAqIE1hbmFnZXMgYSBsaXN0IG9mIGFubm90YXRpb25zLiBUd28gd2lsbCBiZSB1c2VkIGZvciBlYWNoCiAgICAgKiBSZW5kZXJOb2RlSW5mbywgb25lIGZvciBpbiBhbm5vdGF0aW9ucyBhbmQgb25lIGZvciBvdXQgYW5ub3RhdGlvbnMuCiAgICAgKi8KICAgIGNsYXNzIEFubm90YXRpb25MaXN0IHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgdGhpcy5saXN0ID0gW107CiAgICAgICAgICAgIHRoaXMubm9kZU5hbWVzID0ge307CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEFwcGVuZCBhbiBhbm5vdGF0aW9uIHRvIHRoZSBsaXN0LCBvciBhIHN0YW5kLWluIGVsbGlwc2lzIGFubm90YXRpb24gaW5zdGVhZAogICAgICAgICAqIGlmIHRoaXMgd291bGQgbWFrZSBpdCB0b28gbWFueS4KICAgICAgICAgKi8KICAgICAgICBwdXNoKGFubm90YXRpb24pIHsKICAgICAgICAgICAgaWYgKGFubm90YXRpb24ubm9kZS5uYW1lIGluIHRoaXMubm9kZU5hbWVzKSB7CiAgICAgICAgICAgICAgICByZXR1cm47IC8vIFNraXAgZHVwbGljYXRlIGFubm90YXRpb24uCiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5ub2RlTmFtZXNbYW5ub3RhdGlvbi5ub2RlLm5hbWVdID0gdHJ1ZTsKICAgICAgICAgICAgaWYgKHRoaXMubGlzdC5sZW5ndGggPCBQQVJBTVMubWF4QW5ub3RhdGlvbnMpIHsKICAgICAgICAgICAgICAgIHRoaXMubGlzdC5wdXNoKGFubm90YXRpb24pOwogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBsYXN0QW5ub3RhdGlvbiA9IHRoaXMubGlzdFt0aGlzLmxpc3QubGVuZ3RoIC0gMV07CiAgICAgICAgICAgIGlmIChsYXN0QW5ub3RhdGlvbi5hbm5vdGF0aW9uVHlwZSA9PT0gQW5ub3RhdGlvblR5cGUuRUxMSVBTSVMpIHsKICAgICAgICAgICAgICAgIGxldCBlbGxpcHNpc05vZGUgPSBsYXN0QW5ub3RhdGlvbi5ub2RlOwogICAgICAgICAgICAgICAgZWxsaXBzaXNOb2RlLnNldE51bU1vcmVOb2RlcygrK2VsbGlwc2lzTm9kZS5udW1Nb3JlTm9kZXMpOwogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBlbGxpcHNpc05vZGUgPSBuZXcgRWxsaXBzaXNOb2RlSW1wbCgxKTsKICAgICAgICAgICAgdGhpcy5saXN0LnB1c2gobmV3IEFubm90YXRpb24oZWxsaXBzaXNOb2RlLCBuZXcgUmVuZGVyTm9kZUluZm8oZWxsaXBzaXNOb2RlKSwgbnVsbCwgQW5ub3RhdGlvblR5cGUuRUxMSVBTSVMsIGFubm90YXRpb24uaXNJbikpOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQ29udGFpbnMgcmVuZGVyaW5nIGluZm9ybWF0aW9uIGFib3V0IGEgbm9kZSBpbiB0aGUgaGllcmFyY2hpY2FsIGdyYXBoLgogICAgICovCiAgICBjbGFzcyBSZW5kZXJOb2RlSW5mbyB7CiAgICAgICAgY29uc3RydWN0b3Iobm9kZSkgewogICAgICAgICAgICB0aGlzLm5vZGUgPSBub2RlOwogICAgICAgICAgICB0aGlzLmV4cGFuZGVkID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuaW5Bbm5vdGF0aW9ucyA9IG5ldyBBbm5vdGF0aW9uTGlzdCgpOwogICAgICAgICAgICB0aGlzLm91dEFubm90YXRpb25zID0gbmV3IEFubm90YXRpb25MaXN0KCk7CiAgICAgICAgICAgIC8vIFBhcmFtcyBzcGVjaWZpZWQgYnkgbGF5b3V0CiAgICAgICAgICAgIHRoaXMueCA9IDA7CiAgICAgICAgICAgIHRoaXMueSA9IDA7CiAgICAgICAgICAgIHRoaXMud2lkdGggPSAwOwogICAgICAgICAgICB0aGlzLmhlaWdodCA9IDA7CiAgICAgICAgICAgIHRoaXMuaW5ib3hXaWR0aCA9IDA7CiAgICAgICAgICAgIHRoaXMub3V0Ym94V2lkdGggPSAwOwogICAgICAgICAgICB0aGlzLmV4Y2x1ZGVkID0gZmFsc2U7CiAgICAgICAgICAgIC8vIFBhcmFtcyBmb3IgYnJpZGdlIHBhdGhzLgogICAgICAgICAgICB0aGlzLnN0cnVjdHVyYWwgPSBmYWxzZTsKICAgICAgICAgICAgLy8gUGFyYW1zIGZvciBub2RlIGJveC4KICAgICAgICAgICAgdGhpcy5sYWJlbE9mZnNldCA9IDA7CiAgICAgICAgICAgIHRoaXMucmFkaXVzID0gMDsKICAgICAgICAgICAgLy8gUGFyYW1zIGZvciBleHBhbmRlZCBub2RlCiAgICAgICAgICAgIHRoaXMubGFiZWxIZWlnaHQgPSAwOwogICAgICAgICAgICB0aGlzLnBhZGRpbmdUb3AgPSAwOwogICAgICAgICAgICB0aGlzLnBhZGRpbmdMZWZ0ID0gMDsKICAgICAgICAgICAgdGhpcy5wYWRkaW5nUmlnaHQgPSAwOwogICAgICAgICAgICB0aGlzLnBhZGRpbmdCb3R0b20gPSAwOwogICAgICAgICAgICB0aGlzLmlzSW5FeHRyYWN0ID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuaXNPdXRFeHRyYWN0ID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuY29yZUJveCA9IHsgd2lkdGg6IDAsIGhlaWdodDogMCB9OwogICAgICAgICAgICAvLyBCeSBkZWZhdWx0LCB3ZSBkb24ndCBmYWRlIG5vZGVzIG91dC4gRGVmYXVsdCB0byBmYWxzZSBmb3Igc2FmZXR5LgogICAgICAgICAgICB0aGlzLmlzRmFkZWRPdXQgPSBmYWxzZTsKICAgICAgICAgICAgLy8gT25seSB1c2UgdGhlIHBvcnRpb24gYmV5b25kIHRoZSBsYXN0IGRlbGltaXRlciBhcyB0aGUgZGlzcGxheQogICAgICAgICAgICAvLyBuYW1lLgogICAgICAgICAgICB0aGlzLmRpc3BsYXlOYW1lID0gbm9kZS5uYW1lLnN1YnN0cmluZyhub2RlLm5hbWUubGFzdEluZGV4T2YoTkFNRVNQQUNFX0RFTElNKSArIDEpOwogICAgICAgICAgICBpZiAobm9kZS50eXBlID09PSBOb2RlVHlwZS5NRVRBICYmIG5vZGUuYXNzb2NpYXRlZEZ1bmN0aW9uKSB7CiAgICAgICAgICAgICAgICAvLyBGdW5jdGlvbiBuYW1lcyBhcmUgc3VmZml4ZWQgd2l0aCBhIGxlbmd0aC04IGhleGFkZWNpbWFsIHN0cmluZwogICAgICAgICAgICAgICAgLy8gZm9sbG93ZWQgYnkgYW4gb3B0aW9uYWwgbnVtYmVyLiBXZSByZW1vdmUgdGhhdCBzdWZmaXggYmVjYXVzZQogICAgICAgICAgICAgICAgLy8gdGhlIHVzZXIgZGlkIG5vdCBnZW5lcmF0ZSB0aGF0IHN1ZmZpeC4gVGhhdCBzdWZmaXggbWVyZWx5CiAgICAgICAgICAgICAgICAvLyBzZXJ2ZXMgdG8gZGlmZmVyZW50aWF0ZSBiZXR3ZWVuIGZ1bmN0aW9ucyB3aXRoIGRpZmZlcmVudAogICAgICAgICAgICAgICAgLy8gc2lnbmF0dXJlcyBidXQgdGhlIHNhbWUgbmFtZSBvdGhlcndpc2UuCiAgICAgICAgICAgICAgICAvLyBGdXJ0aGVybW9yZSwgd2UgcmVtb3ZlIHRoZSBwcmVmaXggdGhhdCBtZXJlbHkgYXNjZXJ0YWlucyB0aGlzCiAgICAgICAgICAgICAgICAvLyBub2RlIGFzIGEgZnVuY3Rpb24gZGVmaW5pdGlvbi4gVGhlcmUgaXMgbm8gcmVhc29uIGZvciB0aGUgdXNlcgogICAgICAgICAgICAgICAgLy8gdG8gc2VlIHRoYXQgaW4gdGhlIGdyYXBoLCBhcyB0aGUgbm9kZSB3b3VsZCBhbHJlYWR5IGJlIHdpdGhpbgogICAgICAgICAgICAgICAgLy8gdGhlIGZ1bmN0aW9ucyBzY2VuZSBncm91cC4KICAgICAgICAgICAgICAgIGNvbnN0IG1hdGNoID0gdGhpcy5kaXNwbGF5TmFtZS5tYXRjaChub2RlRGlzcGxheU5hbWVSZWdleCk7CiAgICAgICAgICAgICAgICBpZiAobWF0Y2gpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgZGlzcGxheSBuYW1lIGhhZCBiZWVuIHN1Y2Nlc3NmdWxseSBleHRyYWN0ZWQuIFRoaXMgaXMgdGhlIG1vc3QKICAgICAgICAgICAgICAgICAgICAvLyBjb21tb24gc2NlbmFyaW8uCiAgICAgICAgICAgICAgICAgICAgdGhpcy5kaXNwbGF5TmFtZSA9IG1hdGNoWzFdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAobG9kYXNoLnN0YXJ0c1dpdGgodGhpcy5kaXNwbGF5TmFtZSwgRlVOQ1RJT05fTElCUkFSWV9OT0RFX1BSRUZJWCkpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgc3RyaW5nIGRvZXMgbm90IG1hdGNoIHRoZSB1c3VhbCBwYXR0ZXJuIGZvciBob3cgZnVuY3Rpb25zIGFyZQogICAgICAgICAgICAgICAgICAgIC8vIG5hbWVkLiBKdXN0IHVzZSB0aGUgZW50aXJlIHNlY29uZCBwb3J0aW9uIG9mIHRoZSBzdHJpbmcgYXMgdGhlIG5hbWUKICAgICAgICAgICAgICAgICAgICAvLyBpZiB3ZSBjYW4gc3VjY2Vzc2Z1bGx5IHJlbW92ZSB0aGUgcHJlZml4LgogICAgICAgICAgICAgICAgICAgIHRoaXMuZGlzcGxheU5hbWUgPSB0aGlzLmRpc3BsYXlOYW1lLnN1YnN0cmluZyhGVU5DVElPTl9MSUJSQVJZX05PREVfUFJFRklYLmxlbmd0aCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgaXNJbkNvcmUoKSB7CiAgICAgICAgICAgIHJldHVybiAhdGhpcy5pc0luRXh0cmFjdCAmJiAhdGhpcy5pc091dEV4dHJhY3QgJiYgIXRoaXMuaXNMaWJyYXJ5RnVuY3Rpb247CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBDb250YWlucyByZW5kZXJpbmcgaW5mb3JtYXRpb24gYWJvdXQgYSBNZXRhZWRnZSBmcm9tIHRoZSB1bmRlcmx5aW5nCiAgICAgKiBoaWVyYXJjaGljYWwgZ3JhcGguIEl0IG1heSBiZSBmcm9tIGVpdGhlciBhIG1ldGFncmFwaCBvciBhIGJyaWRnZWdyYXBoLgogICAgICovCiAgICBjbGFzcyBSZW5kZXJNZXRhZWRnZUluZm8gewogICAgICAgIGNvbnN0cnVjdG9yKG1ldGFlZGdlKSB7CiAgICAgICAgICAgIHRoaXMubWV0YWVkZ2UgPSBtZXRhZWRnZTsKICAgICAgICAgICAgdGhpcy5hZGpvaW5pbmdNZXRhZWRnZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuc3RydWN0dXJhbCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLndlaWdodCA9IDE7CiAgICAgICAgICAgIHRoaXMuaXNGYWRlZE91dCA9IGZhbHNlOwogICAgICAgIH0KICAgIH0KICAgIGZ1bmN0aW9uIGFkZEluQW5ub3RhdGlvbihub2RlLCBwcmVkZWNlc3NvciwgcHJlZGVjZXNzb3JSZW5kZXJJbmZvLCBlZGdlLCB0eXBlKSB7CiAgICAgICAgbGV0IGFubm90YXRpb24gPSBuZXcgQW5ub3RhdGlvbihwcmVkZWNlc3NvciwgcHJlZGVjZXNzb3JSZW5kZXJJbmZvLCBlZGdlLCB0eXBlLCB0cnVlKTsKICAgICAgICBub2RlLmluQW5ub3RhdGlvbnMucHVzaChhbm5vdGF0aW9uKTsKICAgIH0KICAgIGZ1bmN0aW9uIGFkZE91dEFubm90YXRpb24obm9kZSwgc3VjY2Vzc29yLCBzdWNjZXNzb3JSZW5kZXJJbmZvLCBlZGdlLCB0eXBlKSB7CiAgICAgICAgbGV0IGFubm90YXRpb24gPSBuZXcgQW5ub3RhdGlvbihzdWNjZXNzb3IsIHN1Y2Nlc3NvclJlbmRlckluZm8sIGVkZ2UsIHR5cGUsIGZhbHNlKTsKICAgICAgICBub2RlLm91dEFubm90YXRpb25zLnB1c2goYW5ub3RhdGlvbik7CiAgICB9CiAgICBmdW5jdGlvbiBzZXRHcmFwaERlcHRoKGdyYXBoLCBkZXB0aCkgewogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLm5vZGVzKCksIChub2RlTmFtZSkgPT4gewogICAgICAgICAgICBsZXQgY2hpbGQgPSBncmFwaC5ub2RlKG5vZGVOYW1lKTsKICAgICAgICAgICAgY2hpbGQuZXhwYW5kZWQgPSBkZXB0aCA+IDE7IC8vIHNldCBhbGwgY2hpbGQgb2YgZGVwdGggMSB0byBjb2xsYXBzZWQKICAgICAgICAgICAgaWYgKGRlcHRoID4gMCkgewogICAgICAgICAgICAgICAgc3dpdGNoIChjaGlsZC5ub2RlLnR5cGUpIHsKICAgICAgICAgICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICAgICAgY2FzZSBOb2RlVHlwZS5TRVJJRVM6CiAgICAgICAgICAgICAgICAgICAgICAgIHNldEdyb3VwTm9kZURlcHRoKGNoaWxkLCBkZXB0aCAtIDEpOwogICAgICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgICAgICAvLyBEbyBub3RoaW5nIGZvciBsZWFmCiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgIH0KICAgIGNsYXNzIFJlbmRlckdyb3VwTm9kZUluZm8gZXh0ZW5kcyBSZW5kZXJOb2RlSW5mbyB7CiAgICAgICAgY29uc3RydWN0b3IoZ3JvdXBOb2RlLCBncmFwaE9wdGlvbnMpIHsKICAgICAgICAgICAgc3VwZXIoZ3JvdXBOb2RlKTsKICAgICAgICAgICAgbGV0IG1ldGFncmFwaCA9IGdyb3VwTm9kZS5tZXRhZ3JhcGg7CiAgICAgICAgICAgIGxldCBnbCA9IG1ldGFncmFwaC5ncmFwaCgpOwogICAgICAgICAgICBncmFwaE9wdGlvbnMuY29tcG91bmQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLmNvcmVHcmFwaCA9IGNyZWF0ZUdyYXBoKGdsLm5hbWUsIEdyYXBoVHlwZS5DT1JFLCBncmFwaE9wdGlvbnMpOwogICAgICAgICAgICB0aGlzLmluRXh0cmFjdEJveCA9IHsgd2lkdGg6IDAsIGhlaWdodDogMCB9OwogICAgICAgICAgICB0aGlzLm91dEV4dHJhY3RCb3ggPSB7IHdpZHRoOiAwLCBoZWlnaHQ6IDAgfTsKICAgICAgICAgICAgdGhpcy5saWJyYXJ5RnVuY3Rpb25zQm94ID0geyB3aWR0aDogMCwgaGVpZ2h0OiAwIH07CiAgICAgICAgICAgIHRoaXMuaXNvbGF0ZWRJbkV4dHJhY3QgPSBbXTsKICAgICAgICAgICAgdGhpcy5pc29sYXRlZE91dEV4dHJhY3QgPSBbXTsKICAgICAgICAgICAgdGhpcy5saWJyYXJ5RnVuY3Rpb25zRXh0cmFjdCA9IFtdOwogICAgICAgIH0KICAgIH0KICAgIGZ1bmN0aW9uIHNldEdyb3VwTm9kZURlcHRoKHJlbmRlckluZm8sIGRlcHRoKSB7CiAgICAgICAgaWYgKHJlbmRlckluZm8uY29yZUdyYXBoKSB7CiAgICAgICAgICAgIHNldEdyYXBoRGVwdGgocmVuZGVySW5mby5jb3JlR3JhcGgsIGRlcHRoKTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIFJlbW92ZSBhbiBlZGdlIGZyb20gdGhlIGdyYXBoIGFuZCBhZGQgYW5ub3RhdGlvbnMgdG8gYm90aCBlbmRzIG9mIHRoZSBlZGdlLgogICAgICoKICAgICAqIEBwYXJhbSBUaGUgY29yZSBncmFwaC4KICAgICAqIEBwYXJhbSB2IFNvdXJjZSBuYW1lLgogICAgICogQHBhcmFtIHcgU2luayBuYW1lLgogICAgICovCiAgICBmdW5jdGlvbiBjcmVhdGVTaG9ydGN1dChncmFwaCwgdiwgdykgewogICAgICAgIGxldCBzcmMgPSBncmFwaC5ub2RlKHYpOwogICAgICAgIGxldCBzaW5rID0gZ3JhcGgubm9kZSh3KTsKICAgICAgICBsZXQgZWRnZSA9IGdyYXBoLmVkZ2Uodiwgdyk7CiAgICAgICAgLy8gSWYgZWl0aGVyIG9mIHRoZSBub2RlcyBpcyBleHBsaWNpdGx5IGluY2x1ZGVkIGluIHRoZSBtYWluIGdyYXBoIGFuZAogICAgICAgIC8vIGJvdGggbm9kZXMgYXJlIGluIHRoZSBtYWluIGdyYXBoIHRoZW4gZG8gbm90IGNyZWF0ZSB0aGUgc2hvcnRjdXQKICAgICAgICAvLyBhbmQgaW5zdGVhZCBrZWVwIHRoZSByZWFsIGVkZ2UuCiAgICAgICAgaWYgKChzcmMubm9kZS5pbmNsdWRlID09PSBJbmNsdXNpb25UeXBlLklOQ0xVREUgfHwKICAgICAgICAgICAgc2luay5ub2RlLmluY2x1ZGUgPT09IEluY2x1c2lvblR5cGUuSU5DTFVERSkgJiYKICAgICAgICAgICAgc3JjLm5vZGUuaW5jbHVkZSAhPT0gSW5jbHVzaW9uVHlwZS5FWENMVURFICYmCiAgICAgICAgICAgIHNpbmsubm9kZS5pbmNsdWRlICE9PSBJbmNsdXNpb25UeXBlLkVYQ0xVREUpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICAvLyBBZGQgZWFjaCBhbm5vdGF0aW9uLgogICAgICAgIGFkZE91dEFubm90YXRpb24oc3JjLCBzaW5rLm5vZGUsIHNpbmssIGVkZ2UsIEFubm90YXRpb25UeXBlLlNIT1JUQ1VUKTsKICAgICAgICBhZGRJbkFubm90YXRpb24oc2luaywgc3JjLm5vZGUsIHNyYywgZWRnZSwgQW5ub3RhdGlvblR5cGUuU0hPUlRDVVQpOwogICAgICAgIC8vIFJlbW92ZSB0aGUgZWRnZSBmcm9tIHRoZSBjb3JlIGdyYXBoLgogICAgICAgIGdyYXBoLnJlbW92ZUVkZ2Uodiwgdyk7CiAgICB9CiAgICAvKioKICAgICAqIFJlbW92ZSBlZGdlcyBmcm9tIGEgbm9kZSwgYW5kIHNldCBpdHMgaXNPdXRFeHRyYWN0IHByb3BlcnR5IHRvIHRydWUsCiAgICAgKiBhbmQgcmVtb3ZlIHRoZSBub2RlIGFuZCBtb3ZlIGl0IHRvIGlzb2xhdGVkT3V0RXh0cmFjdC4KICAgICAqCiAgICAgKiBJZiBkZXRhY2hBbGxFZGdlc0ZvckhpZ2hEZWdyZWUgb3IgZm9yY2VEZXRhY2ggaXMgdHJ1ZSwgZXh0cmFjdCBhbGwgb2YgaXRzCiAgICAgKiBlZGdlcy4gT3RoZXJ3aXNlLCBvbmx5IGV4dHJhY3QgYWxsIGluLWVkZ2VzLgogICAgICovCiAgICBmdW5jdGlvbiBtYWtlT3V0RXh0cmFjdChyZW5kZXJOb2RlLCBuLCBmb3JjZURldGFjaCkgewogICAgICAgIGxldCBncmFwaCA9IHJlbmRlck5vZGUuY29yZUdyYXBoOwogICAgICAgIGxldCBjaGlsZCA9IGdyYXBoLm5vZGUobik7CiAgICAgICAgY2hpbGQuaXNPdXRFeHRyYWN0ID0gdHJ1ZTsKICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5wcmVkZWNlc3NvcnMobiksIChwLCBpbmRleCkgPT4gewogICAgICAgICAgICBjcmVhdGVTaG9ydGN1dChncmFwaCwgcCwgbik7CiAgICAgICAgfSk7CiAgICAgICAgewogICAgICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5zdWNjZXNzb3JzKG4pLCAocywgaW5kZXgpID0+IHsKICAgICAgICAgICAgICAgIGNyZWF0ZVNob3J0Y3V0KGdyYXBoLCBuLCBzKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIC8vIFJlbW92ZSB0aGUgbm9kZSBmcm9tIHRoZSBjb3JlIGdyYXBoIGlmIGl0IG5vIGxvbmdlciBoYXMgbmVpZ2hib3JzLgogICAgICAgIGlmIChncmFwaC5uZWlnaGJvcnMobikubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgIGNoaWxkLm5vZGUuaW5jbHVkZSA9IEluY2x1c2lvblR5cGUuRVhDTFVERTsKICAgICAgICAgICAgcmVuZGVyTm9kZS5pc29sYXRlZE91dEV4dHJhY3QucHVzaChjaGlsZCk7CiAgICAgICAgICAgIGdyYXBoLnJlbW92ZU5vZGUobik7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBSZW1vdmUgZWRnZXMgZnJvbSBhIG5vZGUsIHNldCBpdHMgaXNJbkV4dHJhY3QgcHJvcGVydHkgdG8gdHJ1ZSwKICAgICAqIGFuZCByZW1vdmUgdGhlIG5vZGUgYW5kIG1vdmUgaXQgdG8gaXNvbGF0ZWRJbkV4dHJhY3QuCiAgICAgKgogICAgICogSWYgZGV0YWNoQWxsRWRnZXNGb3JIaWdoRGVncmVlIG9yIGZvcmNlRGV0YWNoIGlzIHRydWUsIGV4dHJhY3QgYWxsIG9mIGl0cwogICAgICogZWRnZXMuIE90aGVyd2lzZSwgb25seSByZW1vdmUgYWxsIG91dC1lZGdlcy4KICAgICAqLwogICAgZnVuY3Rpb24gbWFrZUluRXh0cmFjdChyZW5kZXJOb2RlLCBuLCBmb3JjZURldGFjaCkgewogICAgICAgIGxldCBncmFwaCA9IHJlbmRlck5vZGUuY29yZUdyYXBoOwogICAgICAgIGxldCBjaGlsZCA9IGdyYXBoLm5vZGUobik7CiAgICAgICAgY2hpbGQuaXNJbkV4dHJhY3QgPSB0cnVlOwogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLnN1Y2Nlc3NvcnMobiksIChzLCBpbmRleCkgPT4gewogICAgICAgICAgICBjcmVhdGVTaG9ydGN1dChncmFwaCwgbiwgcyk7CiAgICAgICAgfSk7CiAgICAgICAgewogICAgICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5wcmVkZWNlc3NvcnMobiksIChwLCBpbmRleCkgPT4gewogICAgICAgICAgICAgICAgY3JlYXRlU2hvcnRjdXQoZ3JhcGgsIHAsIG4pOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgLy8gUmVtb3ZlIHRoZSBub2RlIGZyb20gdGhlIGNvcmUgZ3JhcGggaWYgaXQgbm8gbG9uZ2VyIGhhcyBuZWlnaGJvcnMuCiAgICAgICAgaWYgKGdyYXBoLm5laWdoYm9ycyhuKS5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgY2hpbGQubm9kZS5pbmNsdWRlID0gSW5jbHVzaW9uVHlwZS5FWENMVURFOwogICAgICAgICAgICByZW5kZXJOb2RlLmlzb2xhdGVkSW5FeHRyYWN0LnB1c2goY2hpbGQpOwogICAgICAgICAgICBncmFwaC5yZW1vdmVOb2RlKG4pOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQ2hlY2sgd2hldGhlciB0aGUgbm9kZSdzIHR5cGUgaXMgYSBtZW1iZXIgb2YgdGhlIGdpdmVuIGxpc3Qgb2YgdHlwZXMuCiAgICAgKgogICAgICogQHBhcmFtIG5vZGUgTm9kZS4KICAgICAqIEBwYXJhbSB0eXBlcyBMaXN0IG9mIHR5cGUgdG8gbWF0Y2guCiAgICAgKi8KICAgIGZ1bmN0aW9uIGhhc1R5cGVJbihub2RlLCB0eXBlcykgewogICAgICAgIGlmIChub2RlLnR5cGUgPT09IE5vZGVUeXBlLk9QKSB7CiAgICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgdHlwZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIGlmIChub2RlLm9wID09PSB0eXBlc1tpXSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKG5vZGUudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICBsZXQgcm9vdE9wTm9kZSA9IG5vZGUuZ2V0Um9vdE9wKCk7CiAgICAgICAgICAgIGlmIChyb290T3BOb2RlKSB7CiAgICAgICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHR5cGVzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKHJvb3RPcE5vZGUub3AgPT09IHR5cGVzW2ldKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgICAvKiogTW92ZSBub2RlcyB0aGF0IGFyZSBzcGVjaWZpZWQgdG8gYmUgZXhjbHVkZWQgb3V0IG9mIHRoZSBjb3JlIGdyYXBoLiAqLwogICAgZnVuY3Rpb24gZXh0cmFjdFNwZWNpZmllZE5vZGVzKHJlbmRlck5vZGUpIHsKICAgICAgICBsZXQgZ3JhcGggPSByZW5kZXJOb2RlLmNvcmVHcmFwaDsKICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5ub2RlcygpLCAobikgPT4gewogICAgICAgICAgICBsZXQgcmVuZGVySW5mbyA9IGdyYXBoLm5vZGUobik7CiAgICAgICAgICAgIGlmIChyZW5kZXJJbmZvLm5vZGUuaW5jbHVkZSA9PT0gSW5jbHVzaW9uVHlwZS5FWENMVURFICYmCiAgICAgICAgICAgICAgICAhbi5zdGFydHNXaXRoKEZVTkNUSU9OX0xJQlJBUllfTk9ERV9QUkVGSVgpKSB7CiAgICAgICAgICAgICAgICAvLyBNb3ZlIHRoZSBub2RlIGlmIHRoZSBub2RlIGlzIGV4Y2x1ZGVkIGFuZCBub3QgcGFydCBvZiB0aGUgbGlicmFyeQogICAgICAgICAgICAgICAgLy8gZnVuY3Rpb24gc2NlbmUgZ3JvdXAsIHdoaWNoIGNvbnRhaW5zIG5vZGVzIHRoYXQgZG8gbm90IHJlcHJlc2VudCBvcHMgaW4KICAgICAgICAgICAgICAgIC8vIHRoZSBncmFwaCBhbmQgc2hvdWxkIHRodXMgbmV2ZXIgaGF2ZSBpdHMgbm9kZXMgYWRkZWQgdG8gdGhlIGNvcmUgZ3JhcGguCiAgICAgICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5jb3JlR3JhcGgub3V0RWRnZXMobikubGVuZ3RoID4KICAgICAgICAgICAgICAgICAgICByZW5kZXJOb2RlLmNvcmVHcmFwaC5pbkVkZ2VzKG4pLmxlbmd0aCkgewogICAgICAgICAgICAgICAgICAgIG1ha2VPdXRFeHRyYWN0KHJlbmRlck5vZGUsIG4pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgbWFrZUluRXh0cmFjdChyZW5kZXJOb2RlLCBuKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgfQogICAgLyoqIFJlbW92ZSBlZGdlcyBmcm9tIHByZS1kZWZpbmVkIG91dC1leHRyYWN0IHBhdHRlcm5zICovCiAgICBmdW5jdGlvbiBleHRyYWN0UHJlZGVmaW5lZFNpbmsocmVuZGVyTm9kZSkgewogICAgICAgIGxldCBncmFwaCA9IHJlbmRlck5vZGUuY29yZUdyYXBoOwogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLm5vZGVzKCksIChuKSA9PiB7CiAgICAgICAgICAgIGxldCByZW5kZXJJbmZvID0gZ3JhcGgubm9kZShuKTsKICAgICAgICAgICAgaWYgKHJlbmRlckluZm8ubm9kZS5pbmNsdWRlICE9PSBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVEKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGhhc1R5cGVJbihyZW5kZXJJbmZvLm5vZGUsIFBBUkFNUy5vdXRFeHRyYWN0VHlwZXMpKSB7CiAgICAgICAgICAgICAgICBtYWtlT3V0RXh0cmFjdChyZW5kZXJOb2RlLCBuKTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgfQogICAgLyoqIFJlbW92ZSBlZGdlcyBmcm9tIHByZS1kZWZpbmVkIGluLWV4dHJhY3QgcGF0dGVybnMgKi8KICAgIGZ1bmN0aW9uIGV4dHJhY3RQcmVkZWZpbmVkU291cmNlKHJlbmRlck5vZGUpIHsKICAgICAgICBsZXQgZ3JhcGggPSByZW5kZXJOb2RlLmNvcmVHcmFwaDsKICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5ub2RlcygpLCAobikgPT4gewogICAgICAgICAgICBsZXQgcmVuZGVySW5mbyA9IGdyYXBoLm5vZGUobik7CiAgICAgICAgICAgIGlmIChyZW5kZXJJbmZvLm5vZGUuaW5jbHVkZSAhPT0gSW5jbHVzaW9uVHlwZS5VTlNQRUNJRklFRCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChoYXNUeXBlSW4ocmVuZGVySW5mby5ub2RlLCBQQVJBTVMuaW5FeHRyYWN0VHlwZXMpKSB7CiAgICAgICAgICAgICAgICBtYWtlSW5FeHRyYWN0KHJlbmRlck5vZGUsIG4pOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICB9CiAgICAvKiogRXh0cmFjdCBub2RlcyBkZWVtZWQgdG8gaGF2ZSBlaXRoZXIgaGlnaCBpbi1kZWdyZWUgb3IgaGlnaCBvdXQtZGVncmVlLiAqLwogICAgZnVuY3Rpb24gZXh0cmFjdEhpZ2hJbk9yT3V0RGVncmVlKHJlbmRlck5vZGUpIHsKICAgICAgICBsZXQgZ3JhcGggPSByZW5kZXJOb2RlLmNvcmVHcmFwaDsKICAgICAgICAvLyBDcmVhdGUgbWFwcGluZ3MgZnJvbSBub2RlIHRvIGluIGFuZCBvdXQgZGVncmVlcy4gQ291bnQgdGhlIG51bWJlciBvZiB2YWxpZAogICAgICAgIC8vIG5vZGVzIGFsb25nIHRoZSB3YXkuCiAgICAgICAgbGV0IG5vZGVUb0luRGVncmVlID0ge307CiAgICAgICAgbGV0IG5vZGVUb091dERlZ3JlZSA9IHt9OwogICAgICAgIGxldCB2YWxpZE5vZGVDb3VudCA9IDA7CiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGgubm9kZXMoKSwgKGN1cnJlbnROb2RlKSA9PiB7CiAgICAgICAgICAgIGlmIChncmFwaC5ub2RlKGN1cnJlbnROb2RlKS5ub2RlLmluY2x1ZGUgIT09IEluY2x1c2lvblR5cGUuVU5TUEVDSUZJRUQpIHsKICAgICAgICAgICAgICAgIC8vIFRoaXMgbm9kZSBpcyBub3QgaW5jbHVkZWQgaW4gdGhlIGZpcnN0IHBsYWNlLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvdW50IHRoZSBpbiBhbmQgb3V0IGRlZ3JlZXMgYmFzZWQgb24gb25seSByZWd1bGFyIGVkZ2VzLCB1bmxlc3MgdGhlcmUKICAgICAgICAgICAgLy8gYXJlIG5vIHJlZ3VsYXIgZWRnZXMsIGluIHdoaWNoIGNhc2UgdXNlIHRoZSBudW1iZXIgb2YgY29udHJvbCBlZGdlcy4KICAgICAgICAgICAgLy8gVGhpcyBpcyBkb25lIHNvIHRoYXQgY29udHJvbCBlZGdlcyBkb24ndCBhZmZlY3QgaWYgbm9kZXMgYXJlIGV4dHJhY3RlZAogICAgICAgICAgICAvLyBmcm9tIHRoZSBjb3JlIGdyYXBoLCB1bmxlc3MgdGhlIG5vZGUgaXMgb25seSB1c2VkIGZvciBjb250cm9sLgogICAgICAgICAgICBsZXQgaW5EZWdyZWUgPSBsb2Rhc2gucmVkdWNlKGdyYXBoLnByZWRlY2Vzc29ycyhjdXJyZW50Tm9kZSksIChpbkRlZ3JlZSwgcHJlZCkgPT4gewogICAgICAgICAgICAgICAgbGV0IG1ldGFlZGdlID0gZ3JhcGguZWRnZShwcmVkLCBjdXJyZW50Tm9kZSkubWV0YWVkZ2U7CiAgICAgICAgICAgICAgICByZXR1cm4gaW5EZWdyZWUgKyAobWV0YWVkZ2UubnVtUmVndWxhckVkZ2VzID8gMSA6IDApOwogICAgICAgICAgICB9LCAwKTsKICAgICAgICAgICAgaWYgKGluRGVncmVlID09PSAwICYmIGdyYXBoLnByZWRlY2Vzc29ycyhjdXJyZW50Tm9kZSkubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgaW5EZWdyZWUgPSBncmFwaC5wcmVkZWNlc3NvcnMoY3VycmVudE5vZGUpLmxlbmd0aDsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgb3V0RGVncmVlID0gbG9kYXNoLnJlZHVjZShncmFwaC5zdWNjZXNzb3JzKGN1cnJlbnROb2RlKSwgKG91dERlZ3JlZSwgc3VjYykgPT4gewogICAgICAgICAgICAgICAgbGV0IG1ldGFlZGdlID0gZ3JhcGguZWRnZShjdXJyZW50Tm9kZSwgc3VjYykubWV0YWVkZ2U7CiAgICAgICAgICAgICAgICByZXR1cm4gb3V0RGVncmVlICsgKG1ldGFlZGdlLm51bVJlZ3VsYXJFZGdlcyA/IDEgOiAwKTsKICAgICAgICAgICAgfSwgMCk7CiAgICAgICAgICAgIGlmIChvdXREZWdyZWUgPT09IDAgJiYgZ3JhcGguc3VjY2Vzc29ycyhjdXJyZW50Tm9kZSkubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgb3V0RGVncmVlID0gZ3JhcGguc3VjY2Vzc29ycyhjdXJyZW50Tm9kZSkubGVuZ3RoOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFN0b3JlIHRoZSBpbiBhbmQgb3V0IGRlZ3JlZXMgb2YgdGhpcyBub2RlIHRvIGF2b2lkIHJlY29tcHV0aW5nLgogICAgICAgICAgICBub2RlVG9JbkRlZ3JlZVtjdXJyZW50Tm9kZV0gPSBpbkRlZ3JlZTsKICAgICAgICAgICAgbm9kZVRvT3V0RGVncmVlW2N1cnJlbnROb2RlXSA9IG91dERlZ3JlZTsKICAgICAgICAgICAgdmFsaWROb2RlQ291bnQrKzsKICAgICAgICB9KTsKICAgICAgICBpZiAodmFsaWROb2RlQ291bnQgPCBQQVJBTVMubWluTm9kZUNvdW50Rm9yRXh0cmFjdGlvbikgewogICAgICAgICAgICAvLyBUaGlzIGdyYXBoIGhhcyBmZXcgbm9kZXMuIERvIG5vdCBleHRyYWN0IGFueSBub2Rlcy4KICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICAvLyBXZSBvbmx5IGV4dHJhY3QgaWYgdGhlIG5vZGUgaGFzIGEgbWluIGluIG9yIG91dCBkZWdyZWUgZ3JlYXRlciB0aGFuIHRoaXMuCiAgICAgICAgbGV0IG1pblVwcGVyQm91bmQgPSBQQVJBTVMubWluRGVncmVlRm9yRXh0cmFjdGlvbiAtIDE7CiAgICAgICAgLy8gTWFyayBmb3IgZXh0cmFjdGlvbiBub2RlcyB3aXRoIGluLWRlZ3JlZSA+IFEzICsgKFEzIC0gUTEpLgogICAgICAgIGxldCBxM0luZGV4ID0gTWF0aC5yb3VuZCh2YWxpZE5vZGVDb3VudCAqIDAuNzUpOwogICAgICAgIGxldCBxMUluZGV4ID0gTWF0aC5yb3VuZCh2YWxpZE5vZGVDb3VudCAqIDAuMjUpOwogICAgICAgIGxldCBzb3J0ZWRCeUluRGVncmVlID0gT2JqZWN0LmtleXMobm9kZVRvSW5EZWdyZWUpLnNvcnQoKG5vZGUwLCBub2RlMSkgPT4gewogICAgICAgICAgICByZXR1cm4gbm9kZVRvSW5EZWdyZWVbbm9kZTBdIC0gbm9kZVRvSW5EZWdyZWVbbm9kZTFdOwogICAgICAgIH0pOwogICAgICAgIGxldCBpbkRlZ3JlZVEzID0gbm9kZVRvSW5EZWdyZWVbc29ydGVkQnlJbkRlZ3JlZVtxM0luZGV4XV07CiAgICAgICAgbGV0IGluRGVncmVlUTEgPSBub2RlVG9JbkRlZ3JlZVtzb3J0ZWRCeUluRGVncmVlW3ExSW5kZXhdXTsKICAgICAgICBsZXQgaW5EZWdyZWVVcHBlckJvdW5kID0gaW5EZWdyZWVRMyArIGluRGVncmVlUTMgLSBpbkRlZ3JlZVExOwogICAgICAgIC8vIE9ubHkgZXh0cmFjdCBpZiB0aGUgdXBwZXIgYm91bmQgaXMgaGlnaCBlbm91Z2guCiAgICAgICAgaW5EZWdyZWVVcHBlckJvdW5kID0gTWF0aC5tYXgoaW5EZWdyZWVVcHBlckJvdW5kLCBtaW5VcHBlckJvdW5kKTsKICAgICAgICBmb3IgKGxldCBpID0gdmFsaWROb2RlQ291bnQgLSAxOyBub2RlVG9JbkRlZ3JlZVtzb3J0ZWRCeUluRGVncmVlW2ldXSA+IGluRGVncmVlVXBwZXJCb3VuZDsgaS0tKSB7CiAgICAgICAgICAgIC8vIEV4dHJhY3QgYSBoaWdoIGluLWRlZ3JlZSBub2RlLgogICAgICAgICAgICBtYWtlSW5FeHRyYWN0KHJlbmRlck5vZGUsIHNvcnRlZEJ5SW5EZWdyZWVbaV0pOwogICAgICAgIH0KICAgICAgICAvLyBNYXJrIGZvciBleHRyYWN0aW9uIG5vZGVzIHdpdGggb3V0LWRlZ3JlZSA+IFEzICsgKFEzIC0gUTEpICogNC4KICAgICAgICBsZXQgc29ydGVkQnlPdXREZWdyZWUgPSBPYmplY3Qua2V5cyhub2RlVG9PdXREZWdyZWUpLnNvcnQoKG5vZGUwLCBub2RlMSkgPT4gewogICAgICAgICAgICByZXR1cm4gbm9kZVRvT3V0RGVncmVlW25vZGUwXSAtIG5vZGVUb091dERlZ3JlZVtub2RlMV07CiAgICAgICAgfSk7CiAgICAgICAgbGV0IG91dERlZ3JlZVEzID0gbm9kZVRvT3V0RGVncmVlW3NvcnRlZEJ5T3V0RGVncmVlW3EzSW5kZXhdXTsKICAgICAgICBsZXQgb3V0RGVncmVlUTEgPSBub2RlVG9PdXREZWdyZWVbc29ydGVkQnlPdXREZWdyZWVbcTFJbmRleF1dOwogICAgICAgIC8vIFRoZSB1cHBlciBib3VuZCBmb3IgZXh0cmFjdGluZyBvdXQtZGVncmVlIG5vZGVzIGlzIGhpZ2hlciB0aGFuIHRoYXQgZm9yCiAgICAgICAgLy8gZXh0cmFjdGluZyBpbi1kZWdyZWUgb25lcyAoTm90ZSB0aGUgIiogNCIpIGJlY2F1c2UsIGluIHByYWN0aWNlLCBzb21lCiAgICAgICAgLy8gZ3JhcGhzIGxvb2sgd29yc2Ugd2l0aCBhIHNtYWxsZXIgb3V0LWRlZ3JlZSBib3VuZC4gRm9yIGluc3RhbmNlLCBhIHNtYWxsZXIKICAgICAgICAvLyBvdXQtZGVncmVlIGJvdW5kIHJlbW92ZXMgdGhlIGNvbnZvbHV0aW9uIG5vZGVzIGZyb20gY2lmYXIgMTAgdHJhaW4ncyBncmFwaC4KICAgICAgICBsZXQgb3V0RGVncmVlVXBwZXJCb3VuZCA9IG91dERlZ3JlZVEzICsgKG91dERlZ3JlZVEzIC0gb3V0RGVncmVlUTEpICogNDsKICAgICAgICAvLyBPbmx5IGV4dHJhY3QgaWYgdGhlIHVwcGVyIGJvdW5kIGlzIGhpZ2ggZW5vdWdoLgogICAgICAgIG91dERlZ3JlZVVwcGVyQm91bmQgPSBNYXRoLm1heChvdXREZWdyZWVVcHBlckJvdW5kLCBtaW5VcHBlckJvdW5kKTsKICAgICAgICBmb3IgKGxldCBpID0gdmFsaWROb2RlQ291bnQgLSAxOyBub2RlVG9PdXREZWdyZWVbc29ydGVkQnlPdXREZWdyZWVbaV1dID4gb3V0RGVncmVlVXBwZXJCb3VuZDsgaS0tKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gZ3JhcGgubm9kZShzb3J0ZWRCeU91dERlZ3JlZVtpXSk7CiAgICAgICAgICAgIGlmICghbm9kZSB8fCBub2RlLmlzSW5FeHRyYWN0KSB7CiAgICAgICAgICAgICAgICAvLyBUaGlzIG5vZGUgaGFzIGFscmVhZHkgYmVlbiBleHRyYWN0ZWQgZHVlIHRvIGhpZ2ggaW4tZGVncmVlLiBJdCBtaWdodAogICAgICAgICAgICAgICAgLy8gaGF2ZSBiZWVuIHJlbW92ZWQgZnJvbSB0aGUgZ3JhcGggaW4gZ2VuZXJhbCAoZHVyaW5nIGluLWRlZ3JlZQogICAgICAgICAgICAgICAgLy8gZXh0cmFjdGlvbikgZHVlIHRvIGEgbGFjayBvZiBuZWlnaGJvcnMuIERvIG5vdCBleHRyYWN0IHRoaXMgbm9kZSB0d2ljZS4KICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEV4dHJhY3QgYSBoaWdoIG91dC1kZWdyZWUgbm9kZSB0aGF0IGhhcyBub3QgYWxyZWFkeSBiZWVuIGV4dHJhY3RlZC4KICAgICAgICAgICAgbWFrZU91dEV4dHJhY3QocmVuZGVyTm9kZSwgc29ydGVkQnlPdXREZWdyZWVbaV0pOwogICAgICAgIH0KICAgIH0KICAgIC8qKiBSZW1vdmUgY29udHJvbCBlZGdlcyBmcm9tIG5vZGVzIHRoYXQgaGF2ZSB0b28gbWFueSBjb250cm9sIGVkZ2VzICovCiAgICBmdW5jdGlvbiByZW1vdmVDb250cm9sRWRnZXMocmVuZGVyTm9kZSkgewogICAgICAgIGxldCBncmFwaCA9IHJlbmRlck5vZGUuY29yZUdyYXBoOwogICAgICAgIC8vIENvbGxlY3QgY29udHJvbCBlZGdlcyBpbnRvIGEgbWFwIGJ5IG5vZGUgbmFtZS4KICAgICAgICBsZXQgbWFwID0ge307CiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGguZWRnZXMoKSwgKGUpID0+IHsKICAgICAgICAgICAgaWYgKCFncmFwaC5lZGdlKGUpLm1ldGFlZGdlLm51bVJlZ3VsYXJFZGdlcykgewogICAgICAgICAgICAgICAgKG1hcFtlLnZdID0gbWFwW2Uudl0gfHwgW10pLnB1c2goZSk7CiAgICAgICAgICAgICAgICAobWFwW2Uud10gPSBtYXBbZS53XSB8fCBbXSkucHVzaChlKTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIC8vIEZvciBlYWNoIG5vZGUgd2l0aCB0b28gbWFueSBjb250cm9sIGVkZ2VzLCB0dXJuIHRoZW0gaW50byBhbm5vdGF0aW9ucy4KICAgICAgICBsb2Rhc2guZWFjaChtYXAsIChlZGdlcywgbm9kZU5hbWUpID0+IHsKICAgICAgICAgICAgaWYgKGVkZ2VzLmxlbmd0aCA+IFBBUkFNUy5tYXhDb250cm9sRGVncmVlKSB7CiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChlZGdlcywgKGUpID0+IGNyZWF0ZVNob3J0Y3V0KGdyYXBoLCBlLnYsIGUudykpOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIFJlbW92ZSBlZGdlcyBhbmQgYWRkIHRvIGFubm90YXRpb24gaW5zdGVhZC4KICAgICAqCiAgICAgKiBGb3Igcm9vdCBub2RlLCBjb25zaWRlciBwcmVkZWZpbmVkIHR5cGVzIGZvciBzb3VyY2UgYW5kIHNpbmsuCiAgICAgKiBXZSBkbyBub3QgZXh0cmFjdCBwcmVkZWZpbmVkIHR5cGUgZnJvbSBub24tcm9vdCBzbyB0aGF0IFZhcmlhYmxlcyBhbmQgdGhlCiAgICAgKiBzZ2Qgbm9kZSAob3AgdHlwZSA9ICdOb09wJykgZG8gbm90IGdldCBleHRyYWN0IGZyb20gaW5zaWRlIG93biBncm91cC4KICAgICAqCiAgICAgKiBUaGUgb3JkZXIgb2YgZXh0cmFjdGlvbiBpcyBpbXBvcnRhbnQgaGVyZSBhcyBzd2FwcGluZyB0aGUgb3JkZXIgY2FuIHRvdGFsbHkKICAgICAqIHNjcmV3IHVwIHRoZSBncmFwaCBsYXlvdXQuCiAgICAgKgogICAgICogQHBhcmFtIHtSZW5kZXIuTm9kZX0gcmVuZGVyTm9kZSBOb2RlIHRvIG1hbmlwdWxhdGUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGV4dHJhY3RIaWdoRGVncmVlcyhyZW5kZXJOb2RlKSB7CiAgICAgICAgZXh0cmFjdFNwZWNpZmllZE5vZGVzKHJlbmRlck5vZGUpOwogICAgICAgIGlmIChQQVJBTVMub3V0RXh0cmFjdFR5cGVzKSB7CiAgICAgICAgICAgIGV4dHJhY3RQcmVkZWZpbmVkU2luayhyZW5kZXJOb2RlKTsKICAgICAgICB9CiAgICAgICAgLy8gVGhpcyBoYXMgdG8gY29tZSBiZWZvcmUgZXh0cmFjdCBoaWdoIGluLWRlZ3JlZSB0byBwcm90ZWN0IHRoZSBjb3JlIHBhcnQKICAgICAgICAvLyB0aGF0IHRha2VzIG1hbnkgdmFyaWFibGVzLgogICAgICAgIGlmIChQQVJBTVMuaW5FeHRyYWN0VHlwZXMpIHsKICAgICAgICAgICAgZXh0cmFjdFByZWRlZmluZWRTb3VyY2UocmVuZGVyTm9kZSk7CiAgICAgICAgfQogICAgICAgIGV4dHJhY3RIaWdoSW5Pck91dERlZ3JlZShyZW5kZXJOb2RlKTsKICAgICAgICB7CiAgICAgICAgICAgIHJlbW92ZUNvbnRyb2xFZGdlcyhyZW5kZXJOb2RlKTsKICAgICAgICB9CiAgICAgICAgLy8gRXh0cmFjdCBpc29sYXRlZCBub2Rlcywgd2hpY2ggY2FuIGJlCiAgICAgICAgLy8gKDEpIHNvdXJjZS1saWtlIGFuZCBzaW5rLWxpa2Ugbm9kZXMgdGhhdCBhcmUgbm90IG9yaWdpbmFsbHkgaXNvbGF0ZWQgYnV0CiAgICAgICAgLy8gICAgIGJlY29tZSBpc29sYXRlZCBhZnRlciBmdXJ0aGVyIHJlbW92YWwuCiAgICAgICAgLy8gKDIpIGlzb2xhdGVkIG5vZGVzIHdpdGggYW5ub3RhdGlvbnMgb24gb25lLXNpZGUuICBUaGVzZSBtaWdodCBiZSBlaXRoZXIKICAgICAgICAvLyAgICAgLSBub2RlcyB0aGF0IG9yaWdpbmFsbHkgaGF2ZSBoaWdoIG91dC1kZWdyZWUgYnV0IGJlY2F1c2Ugd2UgcmVtb3ZlCiAgICAgICAgLy8gICAgICAgaGlnaCBpbi1kZWdyZWUgbm9kZXMgZmlyc3QsIHRoZXkgbm8gbG9uZ2VyIGhhdmUgaGlnaCBpbi1kZWdyZWUgd2hlbgogICAgICAgIC8vICAgICAgIHdlIGNoZWNrLiAgKERldGVjdGluZyBhbGwgaGlnaC1kZWdyZWUgYmVmb3JlIHJlbW92aW5nIGFsc28gbGVhZHMgdG8KICAgICAgICAvLyAgICAgICBhbm90aGVyIHByb2JsZW0uKQogICAgICAgIC8vICAgICAtIG5vZGVzIHRoYXQgZG8gbm90IGhhdmUgaGlnaCBkZWdyZWUsIGJ1dCB0aGVpciBuZWlnaGJvcnMgYXJlIGFsbAogICAgICAgIC8vICAgICAgIGV4dHJhY3RlZCwgc28gaXQgbWlnaHQgbWFrZSBzZW5zZSB0byBleHRyYWN0IHRoZW0gdG9vLgogICAgICAgIGxldCBncmFwaCA9IHJlbmRlck5vZGUuY29yZUdyYXBoOwogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLm5vZGVzKCksIChuKSA9PiB7CiAgICAgICAgICAgIGxldCBjaGlsZCA9IGdyYXBoLm5vZGUobik7CiAgICAgICAgICAgIGxldCBkZWdyZWUgPSBncmFwaC5uZWlnaGJvcnMobikubGVuZ3RoOwogICAgICAgICAgICBpZiAoY2hpbGQubm9kZS5pbmNsdWRlICE9PSBJbmNsdXNpb25UeXBlLlVOU1BFQ0lGSUVEKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGRlZ3JlZSA9PT0gMCkgewogICAgICAgICAgICAgICAgbGV0IGhhc091dEFubm90YXRpb25zID0gY2hpbGQub3V0QW5ub3RhdGlvbnMubGlzdC5sZW5ndGggPiAwOwogICAgICAgICAgICAgICAgbGV0IGhhc0luQW5ub3RhdGlvbnMgPSBjaGlsZC5pbkFubm90YXRpb25zLmxpc3QubGVuZ3RoID4gMDsKICAgICAgICAgICAgICAgIGlmIChjaGlsZC5pc0luRXh0cmFjdCkgewogICAgICAgICAgICAgICAgICAgIC8vIElzIHNvdXJjZS1saWtlLgogICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgY2FzZSBvbmx5IGhhcHBlbnMgaWYgZGV0YWNoQWxsRWRnZXNGb3JIaWdoRGVncmVlIGlzIGZhbHNlLgogICAgICAgICAgICAgICAgICAgIC8vIChPdGhlcndpc2UgYWxsIHNvdXJjZS1saWtlIG5vZGVzIGFyZSBhbGwgaXNvbGF0ZWQgYWxyZWFkeS4pCiAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5pc29sYXRlZEluRXh0cmFjdC5wdXNoKGNoaWxkKTsKICAgICAgICAgICAgICAgICAgICBjaGlsZC5ub2RlLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLkVYQ0xVREU7CiAgICAgICAgICAgICAgICAgICAgZ3JhcGgucmVtb3ZlTm9kZShuKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGNoaWxkLmlzT3V0RXh0cmFjdCkgewogICAgICAgICAgICAgICAgICAgIC8vIElzIHNpbmstbGlrZS4KICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIGNhc2Ugb25seSBoYXBwZW5zIGlmIGRldGFjaEFsbEVkZ2VzRm9ySGlnaERlZ3JlZSBpcyBmYWxzZS4KICAgICAgICAgICAgICAgICAgICAvLyAvLyAoT3RoZXJ3aXNlIGFsbCBzaW5rLWxpa2Ugbm9kZXMgYXJlIGFsbCBpc29sYXRlZCBhbHJlYWR5LikKICAgICAgICAgICAgICAgICAgICByZW5kZXJOb2RlLmlzb2xhdGVkT3V0RXh0cmFjdC5wdXNoKGNoaWxkKTsKICAgICAgICAgICAgICAgICAgICBjaGlsZC5ub2RlLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLkVYQ0xVREU7CiAgICAgICAgICAgICAgICAgICAgZ3JhcGgucmVtb3ZlTm9kZShuKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGlmIChoYXNPdXRBbm5vdGF0aW9ucyAmJiAhaGFzSW5Bbm5vdGF0aW9ucykgewogICAgICAgICAgICAgICAgICAgICAgICBjaGlsZC5pc0luRXh0cmFjdCA9IHRydWU7IC8vIGZvciBvbmVzIHdpdGggaGlnaCBvdXQtYW5ub3RhdGlvbnMKICAgICAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5pc29sYXRlZEluRXh0cmFjdC5wdXNoKGNoaWxkKTsKICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGQubm9kZS5pbmNsdWRlID0gSW5jbHVzaW9uVHlwZS5FWENMVURFOwogICAgICAgICAgICAgICAgICAgICAgICBncmFwaC5yZW1vdmVOb2RlKG4pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIGlmIChoYXNJbkFubm90YXRpb25zICYmICFoYXNPdXRBbm5vdGF0aW9ucykgewogICAgICAgICAgICAgICAgICAgICAgICBjaGlsZC5pc091dEV4dHJhY3QgPSB0cnVlOyAvLyBmb3Igb25lcyB3aXRoIGhpZ2ggaW4tYW5ub3RhdGlvbnMKICAgICAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5pc29sYXRlZE91dEV4dHJhY3QucHVzaChjaGlsZCk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkLm5vZGUuaW5jbHVkZSA9IEluY2x1c2lvblR5cGUuRVhDTFVERTsKICAgICAgICAgICAgICAgICAgICAgICAgZ3JhcGgucmVtb3ZlTm9kZShuKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgIH0KICAgIC8qKgogICAgICogRXhwYW5kcyBub2RlcyBpbiB0aGUgZ3JhcGggdW50aWwgdGhlIGRlc2lyZWQgbm9kZSBpcyB2aXNpYmxlLgogICAgICoKICAgICAqIEBwYXJhbSBzY2VuZSBUaGUgc2NlbmUgcG9seW1lciBjb21wb25lbnQuCiAgICAgKiBAcGFyYW0gcmVuZGVySGllcmFyY2h5IFRoZSByZW5kZXIgaGllcmFyY2h5LgogICAgICogQHBhcmFtIHRlbnNvck5hbWUgVGhlIG5hbWUgb2YgYSB0ZW5zb3IuCiAgICAgKiBAcmV0dXJuIEEgc3RyaW5nIHRoYXQgaXMgdGhlIG5hbWUgb2YgdGhlIG5vZGUgcmVwcmVzZW50aW5nIHRoZSBnaXZlbiB0ZW5zb3IuCiAgICAgKiAgICAgTm90ZSB0aGF0IHRoZSBvcmlnaW5hbCB0ZW5zb3IgbmFtZSBtaWdodCBkaWZmZXIgZnJvbSB0aGlzIHJldHVybmVkIG5vZGUKICAgICAqICAgICBuYW1lLiBTcGVjaWZpY2FsbHksIGZvciBpbnN0YW5jZSwgdGhlIHRlbnNvciBuYW1lIHVzdWFsbHkgZW5kcyB3aXRoIGFuCiAgICAgKiAgICAgb3V0cHV0IHNsb3QgaW5kZXggKHN1Y2ggYXMgOjApLCB3aGlsZSB0aGUgbm9kZSBuYW1lIGxhY2tzIHRoYXQgc3VmZml4LgogICAgICovCiAgICBmdW5jdGlvbiBleHBhbmRVbnRpbE5vZGVJc1Nob3duKHNjZW5lLCByZW5kZXJIaWVyYXJjaHksIHRlbnNvck5hbWUpIHsKICAgICAgICBjb25zdCBzcGxpdFRlbnNvck5hbWUgPSB0ZW5zb3JOYW1lLnNwbGl0KCcvJyk7CiAgICAgICAgLy8gR3JhcGggbmFtZXMgZG8gbm90IHRha2UgaW50byBhY2NvdW50IHRoZSBvdXRwdXQgc2xvdC4gU3RyaXAgaXQuCiAgICAgICAgY29uc3QgbGFzdE5vZGVOYW1lTWF0Y2ggPSBzcGxpdFRlbnNvck5hbWVbc3BsaXRUZW5zb3JOYW1lLmxlbmd0aCAtIDFdLm1hdGNoKC8oLiopOlx3Ky8pOwogICAgICAgIGlmIChsYXN0Tm9kZU5hbWVNYXRjaC5sZW5ndGggPT09IDIpIHsKICAgICAgICAgICAgc3BsaXRUZW5zb3JOYW1lW3NwbGl0VGVuc29yTmFtZS5sZW5ndGggLSAxXSA9IGxhc3ROb2RlTmFtZU1hdGNoWzFdOwogICAgICAgIH0KICAgICAgICBsZXQgbm9kZU5hbWUgPSBzcGxpdFRlbnNvck5hbWVbMF07CiAgICAgICAgbGV0IHJlbmRlck5vZGUgPSByZW5kZXJIaWVyYXJjaHkuZ2V0UmVuZGVyTm9kZUJ5TmFtZShub2RlTmFtZSk7CiAgICAgICAgZm9yIChsZXQgaSA9IDE7IGkgPCBzcGxpdFRlbnNvck5hbWUubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgLy8gT3Agbm9kZXMgYXJlIG5vdCBleHBhbmRhYmxlLgogICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLk9QKSB7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICByZW5kZXJIaWVyYXJjaHkuYnVpbGRTdWJoaWVyYXJjaHkobm9kZU5hbWUpOwogICAgICAgICAgICByZW5kZXJOb2RlLmV4cGFuZGVkID0gdHJ1ZTsKICAgICAgICAgICAgc2NlbmUuc2V0Tm9kZUV4cGFuZGVkKHJlbmRlck5vZGUpOwogICAgICAgICAgICBub2RlTmFtZSArPSAnLycgKyBzcGxpdFRlbnNvck5hbWVbaV07CiAgICAgICAgICAgIHJlbmRlck5vZGUgPSByZW5kZXJIaWVyYXJjaHkuZ2V0UmVuZGVyTm9kZUJ5TmFtZShub2RlTmFtZSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiByZW5kZXJOb2RlLm5vZGUubmFtZTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNvbnN0IFBBUkFNUyQxID0gewogICAgICAgIGFuaW1hdGlvbjogewogICAgICAgICAgICAvKiogRGVmYXVsdCBkdXJhdGlvbiBmb3IgZ3JhcGggYW5pbWF0aW9ucyBpbiBtcy4gKi8KICAgICAgICAgICAgZHVyYXRpb246IDI1MCwKICAgICAgICB9LAogICAgICAgIGdyYXBoOiB7CiAgICAgICAgICAgIC8qKiBHcmFwaCBwYXJhbWV0ZXIgZm9yIG1ldGFub2RlLiAqLwogICAgICAgICAgICBtZXRhOiB7CiAgICAgICAgICAgICAgICAvKioKICAgICAgICAgICAgICAgICAqIERhZ3JlJ3Mgbm9kZXNlcCBwYXJhbSAtIG51bWJlciBvZiBwaXhlbHMgdGhhdAogICAgICAgICAgICAgICAgICogc2VwYXJhdGUgbm9kZXMgaG9yaXpvbnRhbGx5IGluIHRoZSBsYXlvdXQuCiAgICAgICAgICAgICAgICAgKgogICAgICAgICAgICAgICAgICogU2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9jcGV0dGl0dC9kYWdyZS93aWtpI2NvbmZpZ3VyaW5nLXRoZS1sYXlvdXQKICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgbm9kZVNlcDogNSwKICAgICAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgICAgICogRGFncmUncyByYW5rc2VwIHBhcmFtIC0gbnVtYmVyIG9mIHBpeGVscwogICAgICAgICAgICAgICAgICogYmV0d2VlbiBlYWNoIHJhbmsgaW4gdGhlIGxheW91dC4KICAgICAgICAgICAgICAgICAqCiAgICAgICAgICAgICAgICAgKiBTZWUgaHR0cHM6Ly9naXRodWIuY29tL2NwZXR0aXR0L2RhZ3JlL3dpa2kjY29uZmlndXJpbmctdGhlLWxheW91dAogICAgICAgICAgICAgICAgICovCiAgICAgICAgICAgICAgICByYW5rU2VwOiAyNSwKICAgICAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgICAgICogRGFncmUncyBlZGdlc2VwIHBhcmFtIC0gbnVtYmVyIG9mIHBpeGVscyB0aGF0IHNlcGFyYXRlCiAgICAgICAgICAgICAgICAgKiBlZGdlcyBob3Jpem9udGFsbHkgaW4gdGhlIGxheW91dC4KICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgZWRnZVNlcDogNSwKICAgICAgICAgICAgfSwKICAgICAgICAgICAgLyoqIEdyYXBoIHBhcmFtZXRlciBmb3IgbWV0YW5vZGUuICovCiAgICAgICAgICAgIHNlcmllczogewogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBEYWdyZSdzIG5vZGVzZXAgcGFyYW0gLSBudW1iZXIgb2YgcGl4ZWxzIHRoYXQKICAgICAgICAgICAgICAgICAqIHNlcGFyYXRlIG5vZGVzIGhvcml6b250YWxseSBpbiB0aGUgbGF5b3V0LgogICAgICAgICAgICAgICAgICoKICAgICAgICAgICAgICAgICAqIFNlZSBodHRwczovL2dpdGh1Yi5jb20vY3BldHRpdHQvZGFncmUvd2lraSNjb25maWd1cmluZy10aGUtbGF5b3V0CiAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgIG5vZGVTZXA6IDUsCiAgICAgICAgICAgICAgICAvKioKICAgICAgICAgICAgICAgICAqIERhZ3JlJ3MgcmFua3NlcCBwYXJhbSAtIG51bWJlciBvZiBwaXhlbHMKICAgICAgICAgICAgICAgICAqIGJldHdlZW4gZWFjaCByYW5rIGluIHRoZSBsYXlvdXQuCiAgICAgICAgICAgICAgICAgKgogICAgICAgICAgICAgICAgICogU2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9jcGV0dGl0dC9kYWdyZS93aWtpI2NvbmZpZ3VyaW5nLXRoZS1sYXlvdXQKICAgICAgICAgICAgICAgICAqLwogICAgICAgICAgICAgICAgcmFua1NlcDogMjUsCiAgICAgICAgICAgICAgICAvKioKICAgICAgICAgICAgICAgICAqIERhZ3JlJ3MgZWRnZXNlcCBwYXJhbSAtIG51bWJlciBvZiBwaXhlbHMgdGhhdCBzZXBhcmF0ZQogICAgICAgICAgICAgICAgICogZWRnZXMgaG9yaXpvbnRhbGx5IGluIHRoZSBsYXlvdXQuCiAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgIGVkZ2VTZXA6IDUsCiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBQYWRkaW5nIGlzIHVzZWQgdG8gY29ycmVjdGx5IHBvc2l0aW9uIHRoZSBncmFwaCBTVkcgaW5zaWRlIG9mIGl0cyBwYXJlbnQKICAgICAgICAgICAgICogZWxlbWVudC4gVGhlIHBhZGRpbmcgYW1vdW50cyBhcmUgYXBwbGllZCB1c2luZyBhbiBTVkcgdHJhbnNmb3JtIG9mIFggYW5kCiAgICAgICAgICAgICAqIFkgY29vcmRpbmF0ZXMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBwYWRkaW5nOiB7IHBhZGRpbmdUb3A6IDQwLCBwYWRkaW5nTGVmdDogMjAgfSwKICAgICAgICB9LAogICAgICAgIHN1YnNjZW5lOiB7CiAgICAgICAgICAgIG1ldGE6IHsKICAgICAgICAgICAgICAgIHBhZGRpbmdUb3A6IDEwLAogICAgICAgICAgICAgICAgcGFkZGluZ0JvdHRvbTogMTAsCiAgICAgICAgICAgICAgICBwYWRkaW5nTGVmdDogMTAsCiAgICAgICAgICAgICAgICBwYWRkaW5nUmlnaHQ6IDEwLAogICAgICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAgICAgKiBVc2VkIHRvIGxlYXZlIHJvb20gZm9yIHRoZSBsYWJlbCBvbiB0b3Agb2YgdGhlIGhpZ2hlc3Qgbm9kZSBpbgogICAgICAgICAgICAgICAgICogdGhlIGNvcmUgZ3JhcGguCiAgICAgICAgICAgICAgICAgKi8KICAgICAgICAgICAgICAgIGxhYmVsSGVpZ2h0OiAyMCwKICAgICAgICAgICAgICAgIC8qKiBYLXNwYWNlIGJldHdlZW4gZWFjaCBleHRyYWN0ZWQgbm9kZSBhbmQgdGhlIGNvcmUgZ3JhcGguICovCiAgICAgICAgICAgICAgICBleHRyYWN0WE9mZnNldDogMTUsCiAgICAgICAgICAgICAgICAvKiogWS1zcGFjZSBiZXR3ZWVuIGVhY2ggZXh0cmFjdGVkIG5vZGUuICovCiAgICAgICAgICAgICAgICBleHRyYWN0WU9mZnNldDogMjAsCiAgICAgICAgICAgIH0sCiAgICAgICAgICAgIHNlcmllczogewogICAgICAgICAgICAgICAgcGFkZGluZ1RvcDogMTAsCiAgICAgICAgICAgICAgICBwYWRkaW5nQm90dG9tOiAxMCwKICAgICAgICAgICAgICAgIHBhZGRpbmdMZWZ0OiAxMCwKICAgICAgICAgICAgICAgIHBhZGRpbmdSaWdodDogMTAsCiAgICAgICAgICAgICAgICBsYWJlbEhlaWdodDogMTAsCiAgICAgICAgICAgIH0sCiAgICAgICAgfSwKICAgICAgICBub2RlU2l6ZTogewogICAgICAgICAgICAvKiogU2l6ZSBvZiBtZXRhIG5vZGVzLiAqLwogICAgICAgICAgICBtZXRhOiB7CiAgICAgICAgICAgICAgICByYWRpdXM6IDUsCiAgICAgICAgICAgICAgICB3aWR0aDogNjAsCiAgICAgICAgICAgICAgICBtYXhMYWJlbFdpZHRoOiA1MiwKICAgICAgICAgICAgICAgIC8qKiBBIHNjYWxlIGZvciB0aGUgbm9kZSdzIGhlaWdodCBiYXNlZCBvbiBudW1iZXIgb2Ygbm9kZXMgaW5zaWRlICovCiAgICAgICAgICAgICAgICAvLyBIYWNrIC0gc2V0IHRoaXMgYXMgYW4gYW55IHR5cGUgdG8gYXZvaWQgaXNzdWVzIGluIGV4cG9ydGluZyBhIHR5cGUKICAgICAgICAgICAgICAgIC8vIGZyb20gYW4gZXh0ZXJuYWwgbW9kdWxlLgogICAgICAgICAgICAgICAgaGVpZ2h0OiBsaW5lYXIkMigpCiAgICAgICAgICAgICAgICAgICAgLmRvbWFpbihbMSwgMjAwXSkKICAgICAgICAgICAgICAgICAgICAucmFuZ2UoWzE1LCA2MF0pCiAgICAgICAgICAgICAgICAgICAgLmNsYW1wKHRydWUpLAogICAgICAgICAgICAgICAgLyoqIFRoZSByYWRpdXMgb2YgdGhlIGNpcmNsZSBkZW5vdGluZyB0aGUgZXhwYW5kIGJ1dHRvbi4gKi8KICAgICAgICAgICAgICAgIGV4cGFuZEJ1dHRvblJhZGl1czogMywKICAgICAgICAgICAgfSwKICAgICAgICAgICAgLyoqIFNpemUgb2Ygb3Agbm9kZXMuICovCiAgICAgICAgICAgIG9wOiB7CiAgICAgICAgICAgICAgICB3aWR0aDogMTUsCiAgICAgICAgICAgICAgICBoZWlnaHQ6IDYsCiAgICAgICAgICAgICAgICByYWRpdXM6IDMsCiAgICAgICAgICAgICAgICBsYWJlbE9mZnNldDogLTgsCiAgICAgICAgICAgICAgICBtYXhMYWJlbFdpZHRoOiAzMCwKICAgICAgICAgICAgfSwKICAgICAgICAgICAgLyoqIFNpemUgb2Ygc2VyaWVzIG5vZGVzLiAqLwogICAgICAgICAgICBzZXJpZXM6IHsKICAgICAgICAgICAgICAgIGV4cGFuZGVkOiB7CiAgICAgICAgICAgICAgICAgICAgLy8gRm9yIGV4cGFuZGVkIHNlcmllcyBub2Rlcywgd2lkdGggYW5kIGhlaWdodCB3aWxsIGJlCiAgICAgICAgICAgICAgICAgICAgLy8gY29tcHV0ZWQgdG8gYWNjb3VudCBmb3IgdGhlIHN1YnNjZW5lLgogICAgICAgICAgICAgICAgICAgIHJhZGl1czogMTAsCiAgICAgICAgICAgICAgICAgICAgbGFiZWxPZmZzZXQ6IDAsCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgdmVydGljYWw6IHsKICAgICAgICAgICAgICAgICAgICAvLyBXaGVuIHVuZXhwYW5kZWQsIHNlcmllcyB3aG9zZSB1bmRlcmx5aW5nIG1ldGFncmFwaHMgY29udGFpbgogICAgICAgICAgICAgICAgICAgIC8vIG9uZSBvciBtb3JlIG5vbi1jb250cm9sIGVkZ2VzIHdpbGwgc2hvdyBhcyBhIHZlcnRpY2FsIHN0YWNrCiAgICAgICAgICAgICAgICAgICAgLy8gb2YgZWxsaXBzZXMuCiAgICAgICAgICAgICAgICAgICAgd2lkdGg6IDE2LAogICAgICAgICAgICAgICAgICAgIGhlaWdodDogMTMsCiAgICAgICAgICAgICAgICAgICAgbGFiZWxPZmZzZXQ6IC0xMywKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICBob3Jpem9udGFsOiB7CiAgICAgICAgICAgICAgICAgICAgLy8gV2hlbiB1bmV4cGFuZGVkLCBzZXJpZXMgd2hvc2UgdW5kZXJseWluZyBtZXRhZ3JhcGhzIGNvbnRhaW4KICAgICAgICAgICAgICAgICAgICAvLyBubyBub24tY29udHJvbCBlZGdlcyB3aWxsIHNob3cgYXMgYSBob3Jpem9udGFsIHN0YWNrIG9mCiAgICAgICAgICAgICAgICAgICAgLy8gZWxsaXBzZXMuCiAgICAgICAgICAgICAgICAgICAgd2lkdGg6IDI0LAogICAgICAgICAgICAgICAgICAgIGhlaWdodDogOCwKICAgICAgICAgICAgICAgICAgICByYWRpdXM6IDEwLAogICAgICAgICAgICAgICAgICAgIGxhYmVsT2Zmc2V0OiAtMTAsCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9LAogICAgICAgICAgICAvKiogU2l6ZSBvZiBicmlkZ2Ugbm9kZXMuICovCiAgICAgICAgICAgIGJyaWRnZTogewogICAgICAgICAgICAgICAgLy8gTk9URTogYnJpZGdlIG5vZGVzIHdpbGwgbm9ybWFsbHkgYmUgaW52aXNpYmxlLCBidXQgdGhleSBtdXN0CiAgICAgICAgICAgICAgICAvLyB0YWtlIHVwIHNvbWUgc3BhY2Ugc28gdGhhdCB0aGUgbGF5b3V0IHN0ZXAgbGVhdmVzIHJvb20gZm9yCiAgICAgICAgICAgICAgICAvLyB0aGVpciBlZGdlcy4KICAgICAgICAgICAgICAgIHdpZHRoOiAyMCwKICAgICAgICAgICAgICAgIGhlaWdodDogMjAsCiAgICAgICAgICAgICAgICByYWRpdXM6IDIsCiAgICAgICAgICAgICAgICBsYWJlbE9mZnNldDogMCwKICAgICAgICAgICAgfSwKICAgICAgICB9LAogICAgICAgIHNob3J0Y3V0U2l6ZTogewogICAgICAgICAgICAvKiogU2l6ZSBvZiBzaG9ydGN1dHMgZm9yIG9wIG5vZGVzICovCiAgICAgICAgICAgIG9wOiB7IHdpZHRoOiAxMCwgaGVpZ2h0OiA0IH0sCiAgICAgICAgICAgIC8qKiBTaXplIG9mIHNob3J0Y3V0cyBmb3IgbWV0YSBub2RlcyAqLwogICAgICAgICAgICBtZXRhOiB7IHdpZHRoOiAxMiwgaGVpZ2h0OiA0LCByYWRpdXM6IDEgfSwKICAgICAgICAgICAgLyoqIFNpemUgb2Ygc2hvcnRjdXRzIGZvciBzZXJpZXMgbm9kZXMgKi8KICAgICAgICAgICAgc2VyaWVzOiB7CiAgICAgICAgICAgICAgICB3aWR0aDogMTQsCiAgICAgICAgICAgICAgICBoZWlnaHQ6IDQsCiAgICAgICAgICAgIH0sCiAgICAgICAgfSwKICAgICAgICBhbm5vdGF0aW9uczogewogICAgICAgICAgICAvKiogTWF4aW11bSBwb3NzaWJsZSB3aWR0aCBvZiB0aGUgYm91bmRpbmcgYm94IGZvciBpbiBhbm5vdGF0aW9ucyAqLwogICAgICAgICAgICBpbmJveFdpZHRoOiA1MCwKICAgICAgICAgICAgLyoqIE1heGltdW0gcG9zc2libGUgd2lkdGggb2YgdGhlIGJvdW5kaW5nIGJveCBmb3Igb3V0IGFubm90YXRpb25zICovCiAgICAgICAgICAgIG91dGJveFdpZHRoOiA1MCwKICAgICAgICAgICAgLyoqIFgtc3BhY2UgYmV0d2VlbiB0aGUgc2hhcGUgYW5kIGVhY2ggYW5ub3RhdGlvbi1ub2RlLiAqLwogICAgICAgICAgICB4T2Zmc2V0OiAxMCwKICAgICAgICAgICAgLyoqIFktc3BhY2UgYmV0d2VlbiBlYWNoIGFubm90YXRpb24tbm9kZS4gKi8KICAgICAgICAgICAgeU9mZnNldDogMywKICAgICAgICAgICAgLyoqIFgtc3BhY2UgYmV0d2VlbiBlYWNoIGFubm90YXRpb24tbm9kZSBhbmQgaXRzIGxhYmVsLiAqLwogICAgICAgICAgICBsYWJlbE9mZnNldDogMiwKICAgICAgICAgICAgLyoqIERlZmluZXMgdGhlIG1heCB3aWR0aCBmb3IgYW5ub3RhdGlvbiBsYWJlbCAqLwogICAgICAgICAgICBtYXhMYWJlbFdpZHRoOiAxMjAsCiAgICAgICAgfSwKICAgICAgICBjb25zdGFudDogeyBzaXplOiB7IHdpZHRoOiA0LCBoZWlnaHQ6IDQgfSB9LAogICAgICAgIHNlcmllczogewogICAgICAgICAgICAvKiogTWF4aW11bSBudW1iZXIgb2YgcmVwZWF0ZWQgaXRlbSBmb3IgdW5leHBhbmRlZCBzZXJpZXMgbm9kZS4gKi8KICAgICAgICAgICAgbWF4U3RhY2tDb3VudDogMywKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFBvc2l0aW9uaW5nIG9mZnNldCByYXRpbyBmb3IgY29sbGFwc2VkIHN0YWNrCiAgICAgICAgICAgICAqIG9mIHBhcmFsbGVsIHNlcmllcyAoc2VyaWVzIHdpdGhvdXQgZWRnZXMgYmV0d2VlbiBpdHMgbWVtYmVycykuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBwYXJhbGxlbFN0YWNrT2Zmc2V0UmF0aW86IDAuMiwKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFBvc2l0aW9uaW5nIG9mZnNldCByYXRpbyBmb3IgY29sbGFwc2VkIHN0YWNrCiAgICAgICAgICAgICAqIG9mIHRvd2VyIHNlcmllcyAoc2VyaWVzIHdpdGggZWRnZXMgYmV0d2VlbiBpdHMgbWVtYmVycykuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0b3dlclN0YWNrT2Zmc2V0UmF0aW86IDAuNSwKICAgICAgICB9LAogICAgICAgIG1pbmltYXA6IHsKICAgICAgICAgICAgLyoqIFRoZSBtYXhpbXVtIHdpZHRoL2hlaWdodCB0aGUgbWluaW1hcCBjYW4gaGF2ZS4gKi8KICAgICAgICAgICAgc2l6ZTogMTUwLAogICAgICAgIH0sCiAgICB9OwogICAgLyoqCiAgICAgKiBUaGUgbWluaW11bSB3aWR0aCB3ZSBjb25mZXIgdXBvbiB0aGUgYXV4aWxpYXJ5IG5vZGVzIHNlY3Rpb24gaWYgZnVuY3Rpb25zCiAgICAgKiBhbHNvIGFwcGVhci4gV2l0aG91dCBlbmZvcmNpbmcgdGhpcyBtaW5pbXVtLCBtZXRhbm9kZXMgaW4gdGhlIGZ1bmN0aW9uCiAgICAgKiBsaWJyYXJ5IHNlY3Rpb24gY291bGQganV0IGludG8gdGhlIGF1eGlsaWFyeSBub2RlcyBzZWN0aW9uIGJlY2F1c2UgdGhlCiAgICAgKiB0aXRsZSAiQXV4aWxpYXJ5IE5vZGVzIiBpcyBsb25nZXIgdGhhbiB0aGUgd2lkdGggb2YgdGhlIGF1eGlsaWFyeSBub2RlcwogICAgICogc2VjdGlvbiBpdHNlbGYuCiAgICAgKi8KICAgIGNvbnN0IE1JTl9BVVhfV0lEVEggPSAxNDA7CiAgICAvKiogQ2FsY3VsYXRlIGxheW91dCBmb3IgYSBzY2VuZSBvZiBhIGdyb3VwIG5vZGUuICovCiAgICBmdW5jdGlvbiBsYXlvdXRTY2VuZShyZW5kZXJOb2RlSW5mbykgewogICAgICAgIC8vIFVwZGF0ZSBsYXlvdXQsIHNpemUsIGFuZCBhbm5vdGF0aW9ucyBvZiBpdHMgY2hpbGRyZW4gbm9kZXMgYW5kIGVkZ2VzLgogICAgICAgIGlmIChyZW5kZXJOb2RlSW5mby5ub2RlLmlzR3JvdXBOb2RlKSB7CiAgICAgICAgICAgIGxheW91dENoaWxkcmVuKHJlbmRlck5vZGVJbmZvKTsKICAgICAgICB9CiAgICAgICAgLy8gVXBkYXRlIHBvc2l0aW9uIG9mIGl0cyBjaGlsZHJlbiBub2RlcyBhbmQgZWRnZXMKICAgICAgICBpZiAocmVuZGVyTm9kZUluZm8ubm9kZS50eXBlID09PSBOb2RlVHlwZS5NRVRBKSB7CiAgICAgICAgICAgIGxheW91dE1ldGFub2RlKHJlbmRlck5vZGVJbmZvKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAocmVuZGVyTm9kZUluZm8ubm9kZS50eXBlID09PSBOb2RlVHlwZS5TRVJJRVMpIHsKICAgICAgICAgICAgbGF5b3V0U2VyaWVzTm9kZShyZW5kZXJOb2RlSW5mbyk7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBVcGRhdGVzIHRoZSB0b3RhbCB3aWR0aCBvZiBhbiB1bmV4cGFuZGVkIG5vZGUgd2hpY2ggaW5jbHVkZXMgdGhlIHNpemUgb2YgaXRzCiAgICAgKiBpbiBhbmQgb3V0IGFubm90YXRpb25zLgogICAgICovCiAgICBmdW5jdGlvbiB1cGRhdGVUb3RhbFdpZHRoT2ZOb2RlKHJlbmRlckluZm8pIHsKICAgICAgICByZW5kZXJJbmZvLmluYm94V2lkdGggPQogICAgICAgICAgICByZW5kZXJJbmZvLmluQW5ub3RhdGlvbnMubGlzdC5sZW5ndGggPiAwCiAgICAgICAgICAgICAgICA/IFBBUkFNUyQxLmFubm90YXRpb25zLmluYm94V2lkdGgKICAgICAgICAgICAgICAgIDogMDsKICAgICAgICByZW5kZXJJbmZvLm91dGJveFdpZHRoID0KICAgICAgICAgICAgcmVuZGVySW5mby5vdXRBbm5vdGF0aW9ucy5saXN0Lmxlbmd0aCA+IDAKICAgICAgICAgICAgICAgID8gUEFSQU1TJDEuYW5ub3RhdGlvbnMub3V0Ym94V2lkdGgKICAgICAgICAgICAgICAgIDogMDsKICAgICAgICAvLyBBc3NpZ24gdGhlIHdpZHRoIG9mIHRoZSBjb3JlIGJveCAodGhlIG1haW4gc2hhcGUgb2YgdGhlIG5vZGUpLgogICAgICAgIHJlbmRlckluZm8uY29yZUJveC53aWR0aCA9IHJlbmRlckluZm8ud2lkdGg7CiAgICAgICAgcmVuZGVySW5mby5jb3JlQm94LmhlaWdodCA9IHJlbmRlckluZm8uaGVpZ2h0OwogICAgICAgIC8vIFRPRE86IEFjY291bnQgZm9yIGZvbnQgd2lkdGggcmF0aGVyIHRoYW4gdXNpbmcgYSBtYWdpYyBudW1iZXIuCiAgICAgICAgbGV0IGxhYmVsTGVuZ3RoID0gcmVuZGVySW5mby5kaXNwbGF5TmFtZS5sZW5ndGg7CiAgICAgICAgbGV0IGNoYXJXaWR0aCA9IDM7IC8vIDMgcGl4ZWxzIHBlciBjaGFyYWN0ZXIuCiAgICAgICAgLy8gQ29tcHV0ZSB0aGUgdG90YWwgd2lkdGggb2YgdGhlIG5vZGUuCiAgICAgICAgcmVuZGVySW5mby53aWR0aCA9IE1hdGgubWF4KHJlbmRlckluZm8uY29yZUJveC53aWR0aCArIHJlbmRlckluZm8uaW5ib3hXaWR0aCArIHJlbmRlckluZm8ub3V0Ym94V2lkdGgsIGxhYmVsTGVuZ3RoICogY2hhcldpZHRoKTsKICAgIH0KICAgIC8qKgogICAgICogVXBkYXRlIGxheW91dCwgc2l6ZSwgYW5kIGFubm90YXRpb25zIG9mIGl0cyBjaGlsZHJlbiBub2RlcyBhbmQgZWRnZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxheW91dENoaWxkcmVuKHJlbmRlck5vZGVJbmZvKSB7CiAgICAgICAgbGV0IGNoaWxkcmVuID0gcmVuZGVyTm9kZUluZm8uY29yZUdyYXBoCiAgICAgICAgICAgIC5ub2RlcygpCiAgICAgICAgICAgIC5tYXAoKG4pID0+IHsKICAgICAgICAgICAgcmV0dXJuIHJlbmRlck5vZGVJbmZvLmNvcmVHcmFwaC5ub2RlKG4pOwogICAgICAgIH0pCiAgICAgICAgICAgIC5jb25jYXQocmVuZGVyTm9kZUluZm8uaXNvbGF0ZWRJbkV4dHJhY3QsIHJlbmRlck5vZGVJbmZvLmlzb2xhdGVkT3V0RXh0cmFjdCwgcmVuZGVyTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0V4dHJhY3QpOwogICAgICAgIGxvZGFzaC5lYWNoKGNoaWxkcmVuLCAoY2hpbGROb2RlSW5mbykgPT4gewogICAgICAgICAgICAvLyBTZXQgc2l6ZSBvZiBlYWNoIGNoaWxkCiAgICAgICAgICAgIHN3aXRjaCAoY2hpbGROb2RlSW5mby5ub2RlLnR5cGUpIHsKICAgICAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuT1A6CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmV4dGVuZChjaGlsZE5vZGVJbmZvLCBQQVJBTVMkMS5ub2RlU2l6ZS5vcCk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlIE5vZGVUeXBlLkJSSURHRToKICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZXh0ZW5kKGNoaWxkTm9kZUluZm8sIFBBUkFNUyQxLm5vZGVTaXplLmJyaWRnZSk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICAgICAgaWYgKCFjaGlsZE5vZGVJbmZvLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFNldCBmaXhlZCB3aWR0aCBhbmQgc2NhbGFibGUgaGVpZ2h0IGJhc2VkIG9uIGNhcmRpbmFsaXR5CiAgICAgICAgICAgICAgICAgICAgICAgIGxvZGFzaC5leHRlbmQoY2hpbGROb2RlSW5mbywgUEFSQU1TJDEubm9kZVNpemUubWV0YSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNoaWxkTm9kZUluZm8uaGVpZ2h0ID0gUEFSQU1TJDEubm9kZVNpemUubWV0YS5oZWlnaHQoY2hpbGROb2RlSW5mby5ub2RlLmNhcmRpbmFsaXR5KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGxldCBjaGlsZEdyb3VwTm9kZUluZm8gPSBjaGlsZE5vZGVJbmZvOwogICAgICAgICAgICAgICAgICAgICAgICBsYXlvdXRTY2VuZShjaGlsZEdyb3VwTm9kZUluZm8pOyAvLyBSZWN1cnNpdmVseSBsYXlvdXQgaXRzIHN1YnNjZW5lLgogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuU0VSSUVTOgogICAgICAgICAgICAgICAgICAgIGlmIChjaGlsZE5vZGVJbmZvLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGxvZGFzaC5leHRlbmQoY2hpbGROb2RlSW5mbywgUEFSQU1TJDEubm9kZVNpemUuc2VyaWVzLmV4cGFuZGVkKTsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGNoaWxkR3JvdXBOb2RlSW5mbyA9IGNoaWxkTm9kZUluZm87CiAgICAgICAgICAgICAgICAgICAgICAgIGxheW91dFNjZW5lKGNoaWxkR3JvdXBOb2RlSW5mbyk7IC8vIFJlY3Vyc2l2ZWx5IGxheW91dCBpdHMgc3Vic2NlbmUuCiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBsZXQgY2hpbGRHcm91cE5vZGVJbmZvID0gY2hpbGROb2RlSW5mbzsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IHNlcmllc1BhcmFtcyA9IGNoaWxkR3JvdXBOb2RlSW5mby5ub2RlLmhhc05vbkNvbnRyb2xFZGdlcwogICAgICAgICAgICAgICAgICAgICAgICAgICAgPyBQQVJBTVMkMS5ub2RlU2l6ZS5zZXJpZXMudmVydGljYWwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIDogUEFSQU1TJDEubm9kZVNpemUuc2VyaWVzLmhvcml6b250YWw7CiAgICAgICAgICAgICAgICAgICAgICAgIGxvZGFzaC5leHRlbmQoY2hpbGROb2RlSW5mbywgc2VyaWVzUGFyYW1zKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIHRocm93IEVycm9yKCdVbnJlY29nbml6ZWQgbm9kZSB0eXBlOiAnICsgY2hpbGROb2RlSW5mby5ub2RlLnR5cGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvbXB1dGUgdG90YWwgd2lkdGggb2YgdW4tZXhwYW5kZWQgbm9kZXMuIFdpZHRoIG9mIGV4cGFuZGVkIG5vZGVzCiAgICAgICAgICAgIC8vIGhhcyBhbHJlYWR5IGJlZW4gY29tcHV0ZWQuCiAgICAgICAgICAgIGlmICghY2hpbGROb2RlSW5mby5leHBhbmRlZCkgewogICAgICAgICAgICAgICAgdXBkYXRlVG90YWxXaWR0aE9mTm9kZShjaGlsZE5vZGVJbmZvKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBMYXlvdXQgZWFjaCBjaGlsZCdzIGFubm90YXRpb25zCiAgICAgICAgICAgIGxheW91dEFubm90YXRpb24oY2hpbGROb2RlSW5mbyk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIENhbGN1bGF0ZSBsYXlvdXQgZm9yIGEgZ3JhcGggdXNpbmcgZGFncmUKICAgICAqIEBwYXJhbSBncmFwaCB0aGUgZ3JhcGggdG8gYmUgbGFpZCBvdXQKICAgICAqIEBwYXJhbSBwYXJhbXMgbGF5b3V0IHBhcmFtZXRlcnMKICAgICAqIEByZXR1cm4gd2lkdGggYW5kIGhlaWdodCBvZiB0aGUgY29yZSBncmFwaAogICAgICovCiAgICBmdW5jdGlvbiBkYWdyZUxheW91dChncmFwaCwgcGFyYW1zKSB7CiAgICAgICAgbG9kYXNoLmV4dGVuZChncmFwaC5ncmFwaCgpLCB7CiAgICAgICAgICAgIG5vZGVzZXA6IHBhcmFtcy5ub2RlU2VwLAogICAgICAgICAgICByYW5rc2VwOiBwYXJhbXMucmFua1NlcCwKICAgICAgICAgICAgZWRnZXNlcDogcGFyYW1zLmVkZ2VTZXAsCiAgICAgICAgfSk7CiAgICAgICAgbGV0IG5vbkJyaWRnZU5vZGVOYW1lcyA9IFtdOwogICAgICAgIC8vIFNwbGl0IG91dCBub2RlcyBpbnRvIGJyaWRnZSBhbmQgbm9uLWJyaWRnZSBub2RlcywgYW5kIGNhbGN1bGF0ZSB0aGUgdG90YWwKICAgICAgICAvLyB3aWR0aCB3ZSBzaG91bGQgdXNlIGZvciBicmlkZ2Ugbm9kZXMuCiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGgubm9kZXMoKSwgKG5vZGVOYW1lKSA9PiB7CiAgICAgICAgICAgIGxldCBub2RlSW5mbyA9IGdyYXBoLm5vZGUobm9kZU5hbWUpOwogICAgICAgICAgICBpZiAobm9kZUluZm8ubm9kZS50eXBlID09PSBOb2RlVHlwZS5CUklER0UpIDsKICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBub25CcmlkZ2VOb2RlTmFtZXMucHVzaChub2RlTmFtZSk7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICAvLyBJZiB0aGVyZSBhcmUgbm8gbm9uLWJyaWRnZSBub2RlcywgdGhlbiB0aGUgZ3JhcGggaGFzIHplcm8gc2l6ZS4KICAgICAgICBpZiAoIW5vbkJyaWRnZU5vZGVOYW1lcy5sZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHdpZHRoOiAwLAogICAgICAgICAgICAgICAgaGVpZ2h0OiAwLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBkYWdyZS5sYXlvdXQoZ3JhcGgpOwogICAgICAgIC8vIENhbGN1bGF0ZSB0aGUgdHJ1ZSBib3VuZGluZyBib3ggb2YgdGhlIGdyYXBoIGJ5IGl0ZXJhdGluZyBvdmVyIG5vZGVzIGFuZAogICAgICAgIC8vIGVkZ2VzIHJhdGhlciB0aGFuIGFjY2VwdGluZyBkYWdyZSdzIHdvcmQgZm9yIGl0LiBJbiBwYXJ0aWN1bGFyLCB3ZSBzaG91bGQKICAgICAgICAvLyBpZ25vcmUgdGhlIGV4dHJhLXdpZGUgYnJpZGdlIG5vZGVzIGFuZCBicmlkZ2UgZWRnZXMsIGFuZCBhbGxvdyBmb3IKICAgICAgICAvLyBhbm5vdGF0aW9uIGJveGVzIGFuZCBsYWJlbHMuCiAgICAgICAgbGV0IG1pblggPSBJbmZpbml0eTsKICAgICAgICBsZXQgbWluWSA9IEluZmluaXR5OwogICAgICAgIGxldCBtYXhYID0gLUluZmluaXR5OwogICAgICAgIGxldCBtYXhZID0gLUluZmluaXR5OwogICAgICAgIGxvZGFzaC5lYWNoKG5vbkJyaWRnZU5vZGVOYW1lcywgKG5vZGVOYW1lKSA9PiB7CiAgICAgICAgICAgIGxldCBub2RlSW5mbyA9IGdyYXBoLm5vZGUobm9kZU5hbWUpOwogICAgICAgICAgICBsZXQgdyA9IDAuNSAqIG5vZGVJbmZvLndpZHRoOwogICAgICAgICAgICBsZXQgeDEgPSBub2RlSW5mby54IC0gdzsKICAgICAgICAgICAgbGV0IHgyID0gbm9kZUluZm8ueCArIHc7CiAgICAgICAgICAgIG1pblggPSB4MSA8IG1pblggPyB4MSA6IG1pblg7CiAgICAgICAgICAgIG1heFggPSB4MiA+IG1heFggPyB4MiA6IG1heFg7CiAgICAgICAgICAgIC8vIFRPRE86IEFjY291bnQgZm9yIHRoZSBoZWlnaHQgb2YgbGFiZWxzIGFib3ZlIG9wIG5vZGVzIGhlcmUuCiAgICAgICAgICAgIGxldCBoID0gMC41ICogbm9kZUluZm8uaGVpZ2h0OwogICAgICAgICAgICBsZXQgeTEgPSBub2RlSW5mby55IC0gaDsKICAgICAgICAgICAgbGV0IHkyID0gbm9kZUluZm8ueSArIGg7CiAgICAgICAgICAgIG1pblkgPSB5MSA8IG1pblkgPyB5MSA6IG1pblk7CiAgICAgICAgICAgIG1heFkgPSB5MiA+IG1heFkgPyB5MiA6IG1heFk7CiAgICAgICAgfSk7CiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGguZWRnZXMoKSwgKGVkZ2VPYmopID0+IHsKICAgICAgICAgICAgbGV0IGVkZ2VJbmZvID0gZ3JhcGguZWRnZShlZGdlT2JqKTsKICAgICAgICAgICAgaWYgKGVkZ2VJbmZvLnN0cnVjdHVyYWwpIHsKICAgICAgICAgICAgICAgIHJldHVybjsgLy8gU2tpcCBzdHJ1Y3R1cmFsIGVkZ2VzIGZyb20gbWluL21heCBjYWxjdWxhdGlvbnMuCiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gU2luY2UgdGhlIG5vZGUgc2l6ZSBwYXNzZWQgdG8gZGFncmUgaW5jbHVkZXMgdGhlIGluIGFuZCBvdXQKICAgICAgICAgICAgLy8gYW5ub3RhdGlvbnMsIHRoZSBlbmRwb2ludHMgb2YgdGhlIGVkZ2UgcHJvZHVjZWQgYnkgZGFncmUgbWF5IG5vdAogICAgICAgICAgICAvLyBwb2ludCB0byB0aGUgYWN0dWFsIG5vZGUgc2hhcGUgKHJlY3RhbmdsZSwgZWxsaXBzZSkuIFdlIGNvcnJlY3QgdGhlCiAgICAgICAgICAgIC8vIGVuZC1wb2ludHMgYnkgZmluZGluZyB0aGUgaW50ZXJzZWN0aW9uIG9mIGEgbGluZSBiZXR3ZWVuIHRoZQogICAgICAgICAgICAvLyBuZXh0LXRvLWxhc3QgKG5leHQtdG8tZmlyc3QpIHBvaW50IGFuZCB0aGUgZGVzdGluYXRpb24gKHNvdXJjZSkKICAgICAgICAgICAgLy8gcmVjdGFuZ2xlLgogICAgICAgICAgICBsZXQgc291cmNlTm9kZSA9IGdyYXBoLm5vZGUoZWRnZUluZm8ubWV0YWVkZ2Uudik7CiAgICAgICAgICAgIGxldCBkZXN0Tm9kZSA9IGdyYXBoLm5vZGUoZWRnZUluZm8ubWV0YWVkZ2Uudyk7CiAgICAgICAgICAgIC8vIFN0cmFpZ2h0IDMtcG9pbnRzIGVkZ2VzIGFyZSBzcGVjaWFsIGNhc2UsIHNpbmNlIHRoZXkgYXJlIGN1cnZlZCBhZnRlcgogICAgICAgICAgICAvLyBvdXIgZGVmYXVsdCBjb3JyZWN0aW9uLiBUbyBrZWVwIHRoZW0gc3RyYWlnaHQsIHdlIHJlbW92ZSB0aGUgbWlkIHBvaW50CiAgICAgICAgICAgIC8vIGFuZCBjb3JyZWN0IHRoZSBmaXJzdCBhbmQgdGhlIGxhc3QgcG9pbnQgdG8gYmUgdGhlIGNlbnRlciBvZiB0aGUKICAgICAgICAgICAgLy8gc291cmNlIGFuZCBkZXN0aW5hdGlvbiBub2RlIHJlc3BlY3RpdmVseS4KICAgICAgICAgICAgaWYgKGVkZ2VJbmZvLnBvaW50cy5sZW5ndGggPT09IDMgJiYgaXNTdHJhaWdodExpbmUoZWRnZUluZm8ucG9pbnRzKSkgewogICAgICAgICAgICAgICAgaWYgKHNvdXJjZU5vZGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGxldCBjeFNvdXJjZSA9IHNvdXJjZU5vZGUuZXhwYW5kZWQKICAgICAgICAgICAgICAgICAgICAgICAgPyBzb3VyY2VOb2RlLngKICAgICAgICAgICAgICAgICAgICAgICAgOiBjb21wdXRlQ1hQb3NpdGlvbk9mTm9kZVNoYXBlKHNvdXJjZU5vZGUpOwogICAgICAgICAgICAgICAgICAgIGVkZ2VJbmZvLnBvaW50c1swXS54ID0gY3hTb3VyY2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAoZGVzdE5vZGUgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGxldCBjeERlc3QgPSBkZXN0Tm9kZS5leHBhbmRlZAogICAgICAgICAgICAgICAgICAgICAgICA/IGRlc3ROb2RlLngKICAgICAgICAgICAgICAgICAgICAgICAgOiBjb21wdXRlQ1hQb3NpdGlvbk9mTm9kZVNoYXBlKGRlc3ROb2RlKTsKICAgICAgICAgICAgICAgICAgICBlZGdlSW5mby5wb2ludHNbMl0ueCA9IGN4RGVzdDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFJlbW92ZSB0aGUgbWlkZGxlIHBvaW50IHNvIHRoZSBlZGdlIGRvZXNuJ3QgY3VydmUuCiAgICAgICAgICAgICAgICBlZGdlSW5mby5wb2ludHMgPSBbZWRnZUluZm8ucG9pbnRzWzBdLCBlZGdlSW5mby5wb2ludHNbMV1dOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvcnJlY3QgdGhlIGRlc3RpbmF0aW9uIGVuZHBvaW50IG9mIHRoZSBlZGdlLgogICAgICAgICAgICBsZXQgbmV4dFRvTGFzdFBvaW50ID0gZWRnZUluZm8ucG9pbnRzW2VkZ2VJbmZvLnBvaW50cy5sZW5ndGggLSAyXTsKICAgICAgICAgICAgLy8gVGhlIGRlc3RpbmF0aW9uIG5vZGUgbWlnaHQgYmUgbnVsbCBpZiB0aGlzIGlzIGEgYnJpZGdlIGVkZ2UuCiAgICAgICAgICAgIGlmIChkZXN0Tm9kZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBlZGdlSW5mby5wb2ludHNbZWRnZUluZm8ucG9pbnRzLmxlbmd0aCAtIDFdID0gaW50ZXJzZWN0UG9pbnRBbmROb2RlKG5leHRUb0xhc3RQb2ludCwgZGVzdE5vZGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENvcnJlY3QgdGhlIHNvdXJjZSBlbmRwb2ludCBvZiB0aGUgZWRnZS4KICAgICAgICAgICAgbGV0IHNlY29uZFBvaW50ID0gZWRnZUluZm8ucG9pbnRzWzFdOwogICAgICAgICAgICAvLyBUaGUgc291cmNlIG1pZ2h0IGJlIG51bGwgaWYgdGhpcyBpcyBhIGJyaWRnZSBlZGdlLgogICAgICAgICAgICBpZiAoc291cmNlTm9kZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBlZGdlSW5mby5wb2ludHNbMF0gPSBpbnRlcnNlY3RQb2ludEFuZE5vZGUoc2Vjb25kUG9pbnQsIHNvdXJjZU5vZGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKGVkZ2VJbmZvLnBvaW50cywgKHBvaW50KSA9PiB7CiAgICAgICAgICAgICAgICBtaW5YID0gcG9pbnQueCA8IG1pblggPyBwb2ludC54IDogbWluWDsKICAgICAgICAgICAgICAgIG1heFggPSBwb2ludC54ID4gbWF4WCA/IHBvaW50LnggOiBtYXhYOwogICAgICAgICAgICAgICAgbWluWSA9IHBvaW50LnkgPCBtaW5ZID8gcG9pbnQueSA6IG1pblk7CiAgICAgICAgICAgICAgICBtYXhZID0gcG9pbnQueSA+IG1heFkgPyBwb2ludC55IDogbWF4WTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfSk7CiAgICAgICAgLy8gU2hpZnQgYWxsIG5vZGVzIGFuZCBlZGdlIHBvaW50cyB0byBhY2NvdW50IGZvciB0aGUgbGVmdC1wYWRkaW5nIGFtb3VudCwKICAgICAgICAvLyBhbmQgdGhlIGludmlzaWJsZSBicmlkZ2Ugbm9kZXMuCiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGgubm9kZXMoKSwgKG5vZGVOYW1lKSA9PiB7CiAgICAgICAgICAgIGxldCBub2RlSW5mbyA9IGdyYXBoLm5vZGUobm9kZU5hbWUpOwogICAgICAgICAgICBub2RlSW5mby54IC09IG1pblg7CiAgICAgICAgICAgIG5vZGVJbmZvLnkgLT0gbWluWTsKICAgICAgICB9KTsKICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5lZGdlcygpLCAoZWRnZU9iaikgPT4gewogICAgICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5lZGdlKGVkZ2VPYmopLnBvaW50cywgKHBvaW50KSA9PiB7CiAgICAgICAgICAgICAgICBwb2ludC54IC09IG1pblg7CiAgICAgICAgICAgICAgICBwb2ludC55IC09IG1pblk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgICAgIHJldHVybiB7CiAgICAgICAgICAgIHdpZHRoOiBtYXhYIC0gbWluWCwKICAgICAgICAgICAgaGVpZ2h0OiBtYXhZIC0gbWluWSwKICAgICAgICB9OwogICAgfQogICAgLyoqIExheW91dCBhIG1ldGFub2RlLiBPbmx5IGNhbGxlZCBmb3IgYW4gZXhwYW5kZWQgbm9kZS4gKi8KICAgIGZ1bmN0aW9uIGxheW91dE1ldGFub2RlKHJlbmRlck5vZGVJbmZvKSB7CiAgICAgICAgLy8gRmlyc3QsIGNvcHkgcGFyYW1zIHNwZWNpZmljIHRvIG1ldGEgbm9kZXMgb250byB0aGlzIHJlbmRlciBpbmZvIG9iamVjdC4KICAgICAgICBsZXQgcGFyYW1zID0gUEFSQU1TJDEuc3Vic2NlbmUubWV0YTsKICAgICAgICBsb2Rhc2guZXh0ZW5kKHJlbmRlck5vZGVJbmZvLCBwYXJhbXMpOwogICAgICAgIC8vIEludm9rZSBkYWdyZS5sYXlvdXQoKSBvbiB0aGUgY29yZSBncmFwaCBhbmQgcmVjb3JkIHRoZSBib3VuZGluZyBib3gKICAgICAgICAvLyBkaW1lbnNpb25zLgogICAgICAgIGxvZGFzaC5leHRlbmQocmVuZGVyTm9kZUluZm8uY29yZUJveCwgZGFncmVMYXlvdXQocmVuZGVyTm9kZUluZm8uY29yZUdyYXBoLCBQQVJBTVMkMS5ncmFwaC5tZXRhKSk7CiAgICAgICAgLy8gQ2FsY3VsYXRlIHRoZSBwb3NpdGlvbiBvZiBub2RlcyBpbiBpc29sYXRlZEluRXh0cmFjdCByZWxhdGl2ZSB0byB0aGUKICAgICAgICAvLyB0b3AtbGVmdCBjb3JuZXIgb2YgaW5FeHRyYWN0Qm94ICh0aGUgYm91bmRpbmcgYm94IGZvciBhbGwgaW5FeHRyYWN0IG5vZGVzKQogICAgICAgIC8vIGFuZCBjYWxjdWxhdGUgdGhlIHNpemUgb2YgdGhlIGluRXh0cmFjdEJveC4KICAgICAgICBsZXQgbWF4SW5FeHRyYWN0V2lkdGggPSByZW5kZXJOb2RlSW5mby5pc29sYXRlZEluRXh0cmFjdC5sZW5ndGgKICAgICAgICAgICAgPyBsb2Rhc2gubWF4QnkocmVuZGVyTm9kZUluZm8uaXNvbGF0ZWRJbkV4dHJhY3QsIChyZW5kZXJOb2RlKSA9PiByZW5kZXJOb2RlLndpZHRoKS53aWR0aAogICAgICAgICAgICA6IG51bGw7CiAgICAgICAgcmVuZGVyTm9kZUluZm8uaW5FeHRyYWN0Qm94LndpZHRoID0KICAgICAgICAgICAgbWF4SW5FeHRyYWN0V2lkdGggIT0gbnVsbCA/IG1heEluRXh0cmFjdFdpZHRoIDogMDsKICAgICAgICByZW5kZXJOb2RlSW5mby5pbkV4dHJhY3RCb3guaGVpZ2h0ID0gbG9kYXNoLnJlZHVjZShyZW5kZXJOb2RlSW5mby5pc29sYXRlZEluRXh0cmFjdCwgKGhlaWdodCwgY2hpbGQsIGkpID0+IHsKICAgICAgICAgICAgbGV0IHlPZmZzZXQgPSBpID4gMCA/IHBhcmFtcy5leHRyYWN0WU9mZnNldCA6IDA7CiAgICAgICAgICAgIC8vIHVzZSB3aWR0aC9oZWlnaHQgaGVyZSB0byBhdm9pZCBvdmVybGFwcyBiZXR3ZWVuIGV4dHJhY3RzCiAgICAgICAgICAgIGNoaWxkLnggPSAwOwogICAgICAgICAgICBjaGlsZC55ID0gaGVpZ2h0ICsgeU9mZnNldCArIGNoaWxkLmhlaWdodCAvIDI7CiAgICAgICAgICAgIHJldHVybiBoZWlnaHQgKyB5T2Zmc2V0ICsgY2hpbGQuaGVpZ2h0OwogICAgICAgIH0sIDApOwogICAgICAgIC8vIENhbGN1bGF0ZSB0aGUgcG9zaXRpb24gb2Ygbm9kZXMgaW4gaXNvbGF0ZWRPdXRFeHRyYWN0IHJlbGF0aXZlIHRvIHRoZQogICAgICAgIC8vIHRvcC1sZWZ0IGNvcm5lciBvZiBvdXRFeHRyYWN0Qm94ICh0aGUgYm91bmRpbmcgYm94IGZvciBhbGwgb3V0RXh0cmFjdAogICAgICAgIC8vIG5vZGVzKSBhbmQgY2FsY3VsYXRlIHRoZSBzaXplIG9mIHRoZSBvdXRFeHRyYWN0Qm94LgogICAgICAgIGxldCBtYXhPdXRFeHRyYWN0V2lkdGggPSByZW5kZXJOb2RlSW5mby5pc29sYXRlZE91dEV4dHJhY3QubGVuZ3RoCiAgICAgICAgICAgID8gbG9kYXNoLm1heEJ5KHJlbmRlck5vZGVJbmZvLmlzb2xhdGVkT3V0RXh0cmFjdCwgKHJlbmRlck5vZGUpID0+IHJlbmRlck5vZGUud2lkdGgpLndpZHRoCiAgICAgICAgICAgIDogbnVsbDsKICAgICAgICByZW5kZXJOb2RlSW5mby5vdXRFeHRyYWN0Qm94LndpZHRoID0KICAgICAgICAgICAgbWF4T3V0RXh0cmFjdFdpZHRoICE9IG51bGwgPyBtYXhPdXRFeHRyYWN0V2lkdGggOiAwOwogICAgICAgIHJlbmRlck5vZGVJbmZvLm91dEV4dHJhY3RCb3guaGVpZ2h0ID0gbG9kYXNoLnJlZHVjZShyZW5kZXJOb2RlSW5mby5pc29sYXRlZE91dEV4dHJhY3QsIChoZWlnaHQsIGNoaWxkLCBpKSA9PiB7CiAgICAgICAgICAgIGxldCB5T2Zmc2V0ID0gaSA+IDAgPyBwYXJhbXMuZXh0cmFjdFlPZmZzZXQgOiAwOwogICAgICAgICAgICAvLyB1c2Ugd2lkdGgvaGVpZ2h0IGhlcmUgdG8gYXZvaWQgb3ZlcmxhcHMgYmV0d2VlbiBleHRyYWN0cwogICAgICAgICAgICBjaGlsZC54ID0gMDsKICAgICAgICAgICAgY2hpbGQueSA9IGhlaWdodCArIHlPZmZzZXQgKyBjaGlsZC5oZWlnaHQgLyAyOwogICAgICAgICAgICByZXR1cm4gaGVpZ2h0ICsgeU9mZnNldCArIGNoaWxkLmhlaWdodDsKICAgICAgICB9LCAwKTsKICAgICAgICAvLyBDYWxjdWxhdGUgdGhlIHBvc2l0aW9uIG9mIG5vZGVzIGluIGxpYnJhcnlGdW5jdGlvbnNFeHRyYWN0IHJlbGF0aXZlIHRvIHRoZQogICAgICAgIC8vIHRvcC1sZWZ0IGNvcm5lciBvZiBsaWJyYXJ5RnVuY3Rpb25zQm94ICh0aGUgYm91bmRpbmcgYm94IGZvciBhbGwgbGlicmFyeQogICAgICAgIC8vIGZ1bmN0aW9uIG5vZGVzKSBhbmQgY2FsY3VsYXRlIHRoZSBzaXplIG9mIHRoZSBsaWJyYXJ5RnVuY3Rpb25zQm94LgogICAgICAgIGxldCBtYXhMaWJyYXJ5RnVuY3Rpb25zV2lkdGggPSByZW5kZXJOb2RlSW5mby5saWJyYXJ5RnVuY3Rpb25zRXh0cmFjdC5sZW5ndGgKICAgICAgICAgICAgPyBsb2Rhc2gubWF4QnkocmVuZGVyTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0V4dHJhY3QsIChyZW5kZXJOb2RlKSA9PiByZW5kZXJOb2RlLndpZHRoKS53aWR0aAogICAgICAgICAgICA6IG51bGw7CiAgICAgICAgcmVuZGVyTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0JveC53aWR0aCA9CiAgICAgICAgICAgIG1heExpYnJhcnlGdW5jdGlvbnNXaWR0aCAhPSBudWxsID8gbWF4TGlicmFyeUZ1bmN0aW9uc1dpZHRoIDogMDsKICAgICAgICByZW5kZXJOb2RlSW5mby5saWJyYXJ5RnVuY3Rpb25zQm94LmhlaWdodCA9IGxvZGFzaC5yZWR1Y2UocmVuZGVyTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0V4dHJhY3QsIChoZWlnaHQsIGNoaWxkLCBpKSA9PiB7CiAgICAgICAgICAgIGxldCB5T2Zmc2V0ID0gaSA+IDAgPyBwYXJhbXMuZXh0cmFjdFlPZmZzZXQgOiAwOwogICAgICAgICAgICAvLyB1c2Ugd2lkdGgvaGVpZ2h0IGhlcmUgdG8gYXZvaWQgb3ZlcmxhcHMgYmV0d2VlbiBleHRyYWN0cwogICAgICAgICAgICBjaGlsZC54ID0gMDsKICAgICAgICAgICAgY2hpbGQueSA9IGhlaWdodCArIHlPZmZzZXQgKyBjaGlsZC5oZWlnaHQgLyAyOwogICAgICAgICAgICByZXR1cm4gaGVpZ2h0ICsgeU9mZnNldCArIGNoaWxkLmhlaWdodDsKICAgICAgICB9LCAwKTsKICAgICAgICAvLyBDb21wdXRlIHRoZSB0b3RhbCBwYWRkaW5nIGJldHdlZW4gdGhlIGNvcmUgZ3JhcGgsIGluLWV4dHJhY3QgYW5kCiAgICAgICAgLy8gb3V0LWV4dHJhY3QgYm94ZXMuCiAgICAgICAgbGV0IG51bVBhcnRzID0gMDsKICAgICAgICBpZiAocmVuZGVyTm9kZUluZm8uaXNvbGF0ZWRJbkV4dHJhY3QubGVuZ3RoID4gMCkgewogICAgICAgICAgICBudW1QYXJ0cysrOwogICAgICAgIH0KICAgICAgICBpZiAocmVuZGVyTm9kZUluZm8uaXNvbGF0ZWRPdXRFeHRyYWN0Lmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgbnVtUGFydHMrKzsKICAgICAgICB9CiAgICAgICAgaWYgKHJlbmRlck5vZGVJbmZvLmxpYnJhcnlGdW5jdGlvbnNFeHRyYWN0Lmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgbnVtUGFydHMrKzsKICAgICAgICB9CiAgICAgICAgaWYgKHJlbmRlck5vZGVJbmZvLmNvcmVHcmFwaC5ub2RlQ291bnQoKSA+IDApIHsKICAgICAgICAgICAgbnVtUGFydHMrKzsKICAgICAgICB9CiAgICAgICAgbGV0IG9mZnNldCA9IFBBUkFNUyQxLnN1YnNjZW5lLm1ldGEuZXh0cmFjdFhPZmZzZXQ7CiAgICAgICAgbGV0IHBhZGRpbmcgPSBudW1QYXJ0cyA8PSAxID8gMCA6IG51bVBhcnRzICogb2Zmc2V0OwogICAgICAgIC8vIEFkZCB0aGUgaW4tZXh0cmFjdCBhbmQgb3V0LWV4dHJhY3Qgd2lkdGggdG8gdGhlIGNvcmUgYm94IHdpZHRoLiBEbyBub3QgbGV0CiAgICAgICAgLy8gdGhlIGF1eGlsaWFyeSB3aWR0aCBiZSB0b28gc21hbGwsIGxlc3QgaXQgYmUgc21hbGxlciB0aGFuIHRoZSB0aXRsZS4KICAgICAgICBjb25zdCBhdXhXaWR0aCA9IE1hdGgubWF4KE1JTl9BVVhfV0lEVEgsIHJlbmRlck5vZGVJbmZvLmluRXh0cmFjdEJveC53aWR0aCArIHJlbmRlck5vZGVJbmZvLm91dEV4dHJhY3RCb3gud2lkdGgpOwogICAgICAgIHJlbmRlck5vZGVJbmZvLmNvcmVCb3gud2lkdGggKz0KICAgICAgICAgICAgYXV4V2lkdGggKyBwYWRkaW5nICsgcmVuZGVyTm9kZUluZm8ubGlicmFyeUZ1bmN0aW9uc0JveC53aWR0aCArIHBhZGRpbmc7CiAgICAgICAgcmVuZGVyTm9kZUluZm8uY29yZUJveC5oZWlnaHQgPQogICAgICAgICAgICBwYXJhbXMubGFiZWxIZWlnaHQgKwogICAgICAgICAgICAgICAgTWF0aC5tYXgocmVuZGVyTm9kZUluZm8uaW5FeHRyYWN0Qm94LmhlaWdodCwgcmVuZGVyTm9kZUluZm8uY29yZUJveC5oZWlnaHQsIHJlbmRlck5vZGVJbmZvLmxpYnJhcnlGdW5jdGlvbnNCb3guaGVpZ2h0LCByZW5kZXJOb2RlSW5mby5vdXRFeHRyYWN0Qm94LmhlaWdodCk7CiAgICAgICAgLy8gRGV0ZXJtaW5lIHRoZSB3aG9sZSBtZXRhbm9kZSdzIHdpZHRoIChmcm9tIGxlZnQgdG8gcmlnaHQpLgogICAgICAgIHJlbmRlck5vZGVJbmZvLndpZHRoID0KICAgICAgICAgICAgcmVuZGVyTm9kZUluZm8uY29yZUJveC53aWR0aCArIHBhcmFtcy5wYWRkaW5nTGVmdCArIHBhcmFtcy5wYWRkaW5nUmlnaHQ7CiAgICAgICAgLy8gRGV0ZXJtaW5lIHRoZSB3aG9sZSBtZXRhbm9kZSdzIGhlaWdodCAoZnJvbSB0b3AgdG8gYm90dG9tKS4KICAgICAgICByZW5kZXJOb2RlSW5mby5oZWlnaHQgPQogICAgICAgICAgICByZW5kZXJOb2RlSW5mby5wYWRkaW5nVG9wICsKICAgICAgICAgICAgICAgIHJlbmRlck5vZGVJbmZvLmNvcmVCb3guaGVpZ2h0ICsKICAgICAgICAgICAgICAgIHJlbmRlck5vZGVJbmZvLnBhZGRpbmdCb3R0b207CiAgICB9CiAgICAvKioKICAgICAqIENhbGN1bGF0ZSBsYXlvdXQgZm9yIHNlcmllcyBub2RlJ3MgY29yZSBncmFwaC4gT25seSBjYWxsZWQgZm9yIGFuIGV4cGFuZGVkCiAgICAgKiBzZXJpZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxheW91dFNlcmllc05vZGUobm9kZSkgewogICAgICAgIGxldCBncmFwaCA9IG5vZGUuY29yZUdyYXBoOwogICAgICAgIGxldCBwYXJhbXMgPSBQQVJBTVMkMS5zdWJzY2VuZS5zZXJpZXM7CiAgICAgICAgbG9kYXNoLmV4dGVuZChub2RlLCBwYXJhbXMpOwogICAgICAgIC8vIExheW91dCB0aGUgY29yZS4KICAgICAgICBsb2Rhc2guZXh0ZW5kKG5vZGUuY29yZUJveCwgZGFncmVMYXlvdXQobm9kZS5jb3JlR3JhcGgsIFBBUkFNUyQxLmdyYXBoLnNlcmllcykpOwogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLm5vZGVzKCksIChub2RlTmFtZSkgPT4gewogICAgICAgICAgICBncmFwaC5ub2RlKG5vZGVOYW1lKS5leGNsdWRlZCA9IGZhbHNlOwogICAgICAgIH0pOwogICAgICAgIC8vIFNlcmllcyBkbyBub3QgaGF2ZSBpbi9vdXRFeHRyYWN0Qm94IHNvIG5vIG5lZWQgdG8gaW5jbHVkZSB0aGVtIGhlcmUuCiAgICAgICAgbm9kZS53aWR0aCA9IG5vZGUuY29yZUJveC53aWR0aCArIHBhcmFtcy5wYWRkaW5nTGVmdCArIHBhcmFtcy5wYWRkaW5nUmlnaHQ7CiAgICAgICAgbm9kZS5oZWlnaHQgPSBub2RlLmNvcmVCb3guaGVpZ2h0ICsgcGFyYW1zLnBhZGRpbmdUb3AgKyBwYXJhbXMucGFkZGluZ0JvdHRvbTsKICAgIH0KICAgIC8qKgogICAgICogQ2FsY3VsYXRlIGxheW91dCBmb3IgYW5ub3RhdGlvbnMgb2YgYSBnaXZlbiBub2RlLgogICAgICogVGhpcyB3aWxsIG1vZGlmeSBwb3NpdGlvbnMgb2YgdGhlIGdpdmVuIG5vZGUgYW5kIGl0cyBhbm5vdGF0aW9ucy4KICAgICAqCiAgICAgKiBAc2VlIHRmLmdyYXBoLnJlbmRlci5Ob2RlIGFuZCB0Zi5ncmFwaC5yZW5kZXIuQW5ub3RhdGlvbgogICAgICogZm9yIGRlc2NyaXB0aW9uIG9mIGVhY2ggcHJvcGVydHkgb2YgZWFjaCByZW5kZXIgbm9kZS4KICAgICAqCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxheW91dEFubm90YXRpb24ocmVuZGVyTm9kZUluZm8pIHsKICAgICAgICAvLyBJZiB0aGUgcmVuZGVyIG5vZGUgaXMgYW4gZXhwYW5kZWQgbWV0YW5vZGUsIHRoZW4gaXRzIGFubm90YXRpb25zIHdpbGwgbm90CiAgICAgICAgLy8gYmUgdmlzaWJsZSBhbmQgd2Ugc2hvdWxkIHNraXAgdGhlIGFubm90YXRpb24gY2FsY3VsYXRpb25zLgogICAgICAgIGlmIChyZW5kZXJOb2RlSW5mby5leHBhbmRlZCkgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGxldCBpbkFubm90YXRpb25zID0gcmVuZGVyTm9kZUluZm8uaW5Bbm5vdGF0aW9ucy5saXN0OwogICAgICAgIGxldCBvdXRBbm5vdGF0aW9ucyA9IHJlbmRlck5vZGVJbmZvLm91dEFubm90YXRpb25zLmxpc3Q7CiAgICAgICAgLy8gQ2FsY3VsYXRlIHNpemUgZm9yIGluLWFubm90YXRpb25zCiAgICAgICAgbG9kYXNoLmVhY2goaW5Bbm5vdGF0aW9ucywgKGEpID0+IHNpemVBbm5vdGF0aW9uKGEpKTsKICAgICAgICAvLyBDYWxjdWxhdGUgc2l6ZSBmb3Igb3V0LWFubm90YXRpb25zCiAgICAgICAgbG9kYXNoLmVhY2gob3V0QW5ub3RhdGlvbnMsIChhKSA9PiBzaXplQW5ub3RhdGlvbihhKSk7CiAgICAgICAgbGV0IHBhcmFtcyA9IFBBUkFNUyQxLmFubm90YXRpb25zOwogICAgICAgIC8vIENhbGN1bGF0ZSBhbm5vdGF0aW9uIG5vZGUgcG9zaXRpb24gKGEuZHgsIGEuZHkpCiAgICAgICAgLy8gYW5kIHRvdGFsIGhlaWdodCBmb3IgaW4tYW5ub3RhdGlvbnMKICAgICAgICAvLyBBZnRlciB0aGlzIGNodW5rIG9mIGNvZGU6CiAgICAgICAgLy8gaW5ib3hIZWlnaHQgPSBzdW0gb2YgYW5ub3RhdGlvbiBoZWlnaHRzKyAoYW5ub3RhdGlvbi5sZW5ndGggLSAxICogeU9mZnNldCkKICAgICAgICBsZXQgaW5ib3hIZWlnaHQgPSBsb2Rhc2gucmVkdWNlKGluQW5ub3RhdGlvbnMsIChoZWlnaHQsIGEsIGkpID0+IHsKICAgICAgICAgICAgbGV0IHlPZmZzZXQgPSBpID4gMCA/IHBhcmFtcy55T2Zmc2V0IDogMDsKICAgICAgICAgICAgYS5keCA9IC0ocmVuZGVyTm9kZUluZm8uY29yZUJveC53aWR0aCArIGEud2lkdGgpIC8gMiAtIHBhcmFtcy54T2Zmc2V0OwogICAgICAgICAgICBhLmR5ID0gaGVpZ2h0ICsgeU9mZnNldCArIGEuaGVpZ2h0IC8gMjsKICAgICAgICAgICAgcmV0dXJuIGhlaWdodCArIHlPZmZzZXQgKyBhLmhlaWdodDsKICAgICAgICB9LCAwKTsKICAgICAgICBsb2Rhc2guZWFjaChpbkFubm90YXRpb25zLCAoYSkgPT4gewogICAgICAgICAgICBhLmR5IC09IGluYm94SGVpZ2h0IC8gMjsKICAgICAgICAgICAgYS5sYWJlbE9mZnNldCA9IHBhcmFtcy5sYWJlbE9mZnNldDsKICAgICAgICB9KTsKICAgICAgICAvLyBDYWxjdWxhdGUgYW5ub3RhdGlvbiBub2RlIHBvc2l0aW9uIChhLmR4LCBhLmR5KQogICAgICAgIC8vIGFuZCB0b3RhbCBoZWlnaHQgZm9yIG91dC1hbm5vdGF0aW9ucwogICAgICAgIC8vIEFmdGVyIHRoaXMgY2h1bmsgb2YgY29kZToKICAgICAgICAvLyBvdXRib3hIZWlnaHQgPSBzdW0gb2YgYW5ub3RhdGlvbiBoZWlnaHRzICsKICAgICAgICAvLyAgICAgICAgICAgICAgICAoYW5ub3RhdGlvbi5sZW5ndGggLSAxICogeU9mZnNldCkKICAgICAgICBsZXQgb3V0Ym94SGVpZ2h0ID0gbG9kYXNoLnJlZHVjZShvdXRBbm5vdGF0aW9ucywgKGhlaWdodCwgYSwgaSkgPT4gewogICAgICAgICAgICBsZXQgeU9mZnNldCA9IGkgPiAwID8gcGFyYW1zLnlPZmZzZXQgOiAwOwogICAgICAgICAgICBhLmR4ID0gKHJlbmRlck5vZGVJbmZvLmNvcmVCb3gud2lkdGggKyBhLndpZHRoKSAvIDIgKyBwYXJhbXMueE9mZnNldDsKICAgICAgICAgICAgYS5keSA9IGhlaWdodCArIHlPZmZzZXQgKyBhLmhlaWdodCAvIDI7CiAgICAgICAgICAgIHJldHVybiBoZWlnaHQgKyB5T2Zmc2V0ICsgYS5oZWlnaHQ7CiAgICAgICAgfSwgMCk7CiAgICAgICAgbG9kYXNoLmVhY2gob3V0QW5ub3RhdGlvbnMsIChhKSA9PiB7CiAgICAgICAgICAgIC8vIGFkanVzdCBieSAoaGFsZiBvZiApIHRoZSB0b3RhbCBoZWlnaHQKICAgICAgICAgICAgLy8gc28gZHkgaXMgcmVsYXRpdmUgdG8gdGhlIGhvc3Qgbm9kZSdzIGNlbnRlci4KICAgICAgICAgICAgYS5keSAtPSBvdXRib3hIZWlnaHQgLyAyOwogICAgICAgICAgICBhLmxhYmVsT2Zmc2V0ID0gcGFyYW1zLmxhYmVsT2Zmc2V0OwogICAgICAgIH0pOwogICAgICAgIC8vIENyZWF0aW5nIHNjYWxlcyBmb3IgdG91Y2ggcG9pbnQgYmV0d2VlbiB0aGUgaW4tYW5ub3RhdGlvbiBlZGdlcwogICAgICAgIC8vIGFuZCB0aGVpciBob3N0cy4KICAgICAgICBsZXQgaW5Ub3VjaEhlaWdodCA9IE1hdGgubWluKHJlbmRlck5vZGVJbmZvLmhlaWdodCAvIDIgLSByZW5kZXJOb2RlSW5mby5yYWRpdXMsIGluYm94SGVpZ2h0IC8gMik7CiAgICAgICAgaW5Ub3VjaEhlaWdodCA9IGluVG91Y2hIZWlnaHQgPCAwID8gMCA6IGluVG91Y2hIZWlnaHQ7CiAgICAgICAgbGV0IGluWSA9IGxpbmVhciQyKCkKICAgICAgICAgICAgLmRvbWFpbihbMCwgaW5Bbm5vdGF0aW9ucy5sZW5ndGggLSAxXSkKICAgICAgICAgICAgLnJhbmdlKFstaW5Ub3VjaEhlaWdodCwgaW5Ub3VjaEhlaWdodF0pOwogICAgICAgIC8vIENhbGN1bGF0ZSBhbm5vdGF0aW9uIGVkZ2UgcG9zaXRpb24KICAgICAgICBsb2Rhc2guZWFjaChpbkFubm90YXRpb25zLCAoYSwgaSkgPT4gewogICAgICAgICAgICBhLnBvaW50cyA9IFsKICAgICAgICAgICAgICAgIC8vIFRoZSBhbm5vdGF0aW9uIG5vZGUgZW5kCiAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgZHg6IGEuZHggKyBhLndpZHRoIC8gMiwKICAgICAgICAgICAgICAgICAgICBkeTogYS5keSwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAvLyBUaGUgaG9zdCBub2RlIGVuZAogICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgIGR4OiAtcmVuZGVyTm9kZUluZm8uY29yZUJveC53aWR0aCAvIDIsCiAgICAgICAgICAgICAgICAgICAgLy8gb25seSB1c2Ugc2NhbGUgaWYgdGhlcmUgYXJlIG1vcmUgdGhhbiBvbmUsCiAgICAgICAgICAgICAgICAgICAgLy8gb3RoZXJ3aXNlIGNlbnRlciBpdCB2ZXJ0aWNhbGx5CiAgICAgICAgICAgICAgICAgICAgZHk6IGluQW5ub3RhdGlvbnMubGVuZ3RoID4gMSA/IGluWShpKSA6IDAsCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICBdOwogICAgICAgIH0pOwogICAgICAgIC8vIENyZWF0aW5nIHNjYWxlcyBmb3IgdG91Y2ggcG9pbnQgYmV0d2VlbiB0aGUgb3V0LWFubm90YXRpb24gZWRnZXMKICAgICAgICAvLyBhbmQgdGhlaXIgaG9zdHMuCiAgICAgICAgbGV0IG91dFRvdWNoSGVpZ2h0ID0gTWF0aC5taW4ocmVuZGVyTm9kZUluZm8uaGVpZ2h0IC8gMiAtIHJlbmRlck5vZGVJbmZvLnJhZGl1cywgb3V0Ym94SGVpZ2h0IC8gMik7CiAgICAgICAgb3V0VG91Y2hIZWlnaHQgPSBvdXRUb3VjaEhlaWdodCA8IDAgPyAwIDogb3V0VG91Y2hIZWlnaHQ7CiAgICAgICAgbGV0IG91dFkgPSBsaW5lYXIkMigpCiAgICAgICAgICAgIC5kb21haW4oWzAsIG91dEFubm90YXRpb25zLmxlbmd0aCAtIDFdKQogICAgICAgICAgICAucmFuZ2UoWy1vdXRUb3VjaEhlaWdodCwgb3V0VG91Y2hIZWlnaHRdKTsKICAgICAgICBsb2Rhc2guZWFjaChvdXRBbm5vdGF0aW9ucywgKGEsIGkpID0+IHsKICAgICAgICAgICAgLy8gQWRkIHBvaW50IGZyb20gdGhlIGJvcmRlciBvZiB0aGUgYW5ub3RhdGlvbiBub2RlCiAgICAgICAgICAgIGEucG9pbnRzID0gWwogICAgICAgICAgICAgICAgLy8gVGhlIGhvc3Qgbm9kZSBlbmQKICAgICAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgICAgICBkeDogcmVuZGVyTm9kZUluZm8uY29yZUJveC53aWR0aCAvIDIsCiAgICAgICAgICAgICAgICAgICAgLy8gb25seSB1c2Ugc2NhbGUgaWYgdGhlcmUgYXJlIG1vcmUgdGhhbiBvbmUsCiAgICAgICAgICAgICAgICAgICAgLy8gb3RoZXJ3aXNlIGNlbnRlciBpdCB2ZXJ0aWNhbGx5CiAgICAgICAgICAgICAgICAgICAgZHk6IG91dEFubm90YXRpb25zLmxlbmd0aCA+IDEgPyBvdXRZKGkpIDogMCwKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAvLyBUaGUgYW5ub3RhdGlvbiBub2RlIGVuZAogICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgIGR4OiBhLmR4IC0gYS53aWR0aCAvIDIsCiAgICAgICAgICAgICAgICAgICAgZHk6IGEuZHksCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICBdOwogICAgICAgIH0pOwogICAgICAgIHJlbmRlck5vZGVJbmZvLmhlaWdodCA9IE1hdGgubWF4KHJlbmRlck5vZGVJbmZvLmhlaWdodCwgaW5ib3hIZWlnaHQsIG91dGJveEhlaWdodCk7CiAgICB9CiAgICAvKioKICAgICAqIFNldCBzaXplIG9mIGFuIGFubm90YXRpb24gbm9kZS4KICAgICAqLwogICAgZnVuY3Rpb24gc2l6ZUFubm90YXRpb24oYSkgewogICAgICAgIHN3aXRjaCAoYS5hbm5vdGF0aW9uVHlwZSkgewogICAgICAgICAgICBjYXNlIEFubm90YXRpb25UeXBlLkNPTlNUQU5UOgogICAgICAgICAgICAgICAgbG9kYXNoLmV4dGVuZChhLCBQQVJBTVMkMS5jb25zdGFudC5zaXplKTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIEFubm90YXRpb25UeXBlLlNIT1JUQ1VUOgogICAgICAgICAgICAgICAgaWYgKGEubm9kZS50eXBlID09PSBOb2RlVHlwZS5PUCkgewogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5leHRlbmQoYSwgUEFSQU1TJDEuc2hvcnRjdXRTaXplLm9wKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGEubm9kZS50eXBlID09PSBOb2RlVHlwZS5NRVRBKSB7CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmV4dGVuZChhLCBQQVJBTVMkMS5zaG9ydGN1dFNpemUubWV0YSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChhLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuU0VSSUVTKSB7CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmV4dGVuZChhLCBQQVJBTVMkMS5zaG9ydGN1dFNpemUuc2VyaWVzKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHRocm93IEVycm9yKCdJbnZhbGlkIG5vZGUgdHlwZTogJyArIGEubm9kZS50eXBlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIEFubm90YXRpb25UeXBlLlNVTU1BUlk6CiAgICAgICAgICAgICAgICBsb2Rhc2guZXh0ZW5kKGEsIFBBUkFNUyQxLmNvbnN0YW50LnNpemUpOwogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBEZXRlcm1pbmVzIHRoZSBjZW50ZXIgcG9zaXRpb24gb2YgdGhlIG5vZGUncyBzaGFwZS4gVGhlIHBvc2l0aW9uIGRlcGVuZHMKICAgICAqIG9uIGlmIHRoZSBub2RlIGhhcyBpbiBhbmQgb3V0LWFubm90YXRpb25zLgogICAgICovCiAgICBmdW5jdGlvbiBjb21wdXRlQ1hQb3NpdGlvbk9mTm9kZVNoYXBlKHJlbmRlckluZm8pIHsKICAgICAgICBpZiAocmVuZGVySW5mby5leHBhbmRlZCkgewogICAgICAgICAgICByZXR1cm4gcmVuZGVySW5mby54OwogICAgICAgIH0KICAgICAgICBsZXQgZHggPSByZW5kZXJJbmZvLmluQW5ub3RhdGlvbnMubGlzdC5sZW5ndGggPyByZW5kZXJJbmZvLmluYm94V2lkdGggOiAwOwogICAgICAgIHJldHVybiAocmVuZGVySW5mby54IC0gcmVuZGVySW5mby53aWR0aCAvIDIgKyBkeCArIHJlbmRlckluZm8uY29yZUJveC53aWR0aCAvIDIpOwogICAgfQogICAgLyoqIFJldHVybnMgdGhlIGFuZ2xlIChpbiBkZWdyZWVzKSBiZXR3ZWVuIHR3byBwb2ludHMuICovCiAgICBmdW5jdGlvbiBhbmdsZUJldHdlZW5Ud29Qb2ludHMoYSwgYikgewogICAgICAgIGxldCBkeCA9IGIueCAtIGEueDsKICAgICAgICBsZXQgZHkgPSBiLnkgLSBhLnk7CiAgICAgICAgcmV0dXJuICgxODAgKiBNYXRoLmF0YW4oZHkgLyBkeCkpIC8gTWF0aC5QSTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyBpZiBhIGxpbmUgZ29pbmcgdGhyb3VnaCB0aGUgc3BlY2lmaWVkIHBvaW50cyBpcyBhIHN0cmFpZ2h0IGxpbmUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGlzU3RyYWlnaHRMaW5lKHBvaW50cykgewogICAgICAgIGxldCBhbmdsZSA9IGFuZ2xlQmV0d2VlblR3b1BvaW50cyhwb2ludHNbMF0sIHBvaW50c1sxXSk7CiAgICAgICAgZm9yIChsZXQgaSA9IDE7IGkgPCBwb2ludHMubGVuZ3RoIC0gMTsgaSsrKSB7CiAgICAgICAgICAgIGxldCBuZXdBbmdsZSA9IGFuZ2xlQmV0d2VlblR3b1BvaW50cyhwb2ludHNbaV0sIHBvaW50c1tpICsgMV0pOwogICAgICAgICAgICAvLyBIYXZlIGEgdG9sZXJhbmNlIG9mIDEgZGVncmVlLgogICAgICAgICAgICBpZiAoTWF0aC5hYnMobmV3QW5nbGUgLSBhbmdsZSkgPiAxKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgYW5nbGUgPSBuZXdBbmdsZTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGludGVyc2VjdGlvbiBvZiBhIGxpbmUgYmV0d2VlbiB0aGUgcHJvdmlkZWQgcG9pbnQKICAgICAqIGFuZCB0aGUgcHJvdmlkZWQgcmVjdGFuZ2xlLgogICAgICovCiAgICBmdW5jdGlvbiBpbnRlcnNlY3RQb2ludEFuZE5vZGUocG9pbnQsIG5vZGUpIHsKICAgICAgICAvLyBjeCBhbmQgY3kgYXJlIHRoZSBjZW50ZXIgb2YgdGhlIHJlY3RhbmdsZS4KICAgICAgICBsZXQgY3ggPSBub2RlLmV4cGFuZGVkID8gbm9kZS54IDogY29tcHV0ZUNYUG9zaXRpb25PZk5vZGVTaGFwZShub2RlKTsKICAgICAgICBsZXQgY3kgPSBub2RlLnk7CiAgICAgICAgLy8gQ2FsY3VsYXRlIHRoZSBzbG9wZQogICAgICAgIGxldCBkeCA9IHBvaW50LnggLSBjeDsKICAgICAgICBsZXQgZHkgPSBwb2ludC55IC0gY3k7CiAgICAgICAgbGV0IHcgPSBub2RlLmV4cGFuZGVkID8gbm9kZS53aWR0aCA6IG5vZGUuY29yZUJveC53aWR0aDsKICAgICAgICBsZXQgaCA9IG5vZGUuZXhwYW5kZWQgPyBub2RlLmhlaWdodCA6IG5vZGUuY29yZUJveC5oZWlnaHQ7CiAgICAgICAgbGV0IGRlbHRhWCwgZGVsdGFZOwogICAgICAgIGlmICgoTWF0aC5hYnMoZHkpICogdykgLyAyID4gKE1hdGguYWJzKGR4KSAqIGgpIC8gMikgewogICAgICAgICAgICAvLyBUaGUgaW50ZXJzZWN0aW9uIGlzIGFib3ZlIG9yIGJlbG93IHRoZSByZWN0YW5nbGUuCiAgICAgICAgICAgIGlmIChkeSA8IDApIHsKICAgICAgICAgICAgICAgIGggPSAtaDsKICAgICAgICAgICAgfQogICAgICAgICAgICBkZWx0YVggPSBkeSA9PT0gMCA/IDAgOiAoKGggLyAyKSAqIGR4KSAvIGR5OwogICAgICAgICAgICBkZWx0YVkgPSBoIC8gMjsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIC8vIFRoZSBpbnRlcnNlY3Rpb24gaXMgbGVmdCBvciByaWdodCBvZiB0aGUgcmVjdGFuZ2xlLgogICAgICAgICAgICBpZiAoZHggPCAwKSB7CiAgICAgICAgICAgICAgICB3ID0gLXc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZGVsdGFYID0gdyAvIDI7CiAgICAgICAgICAgIGRlbHRhWSA9IGR4ID09PSAwID8gMCA6ICgodyAvIDIpICogZHkpIC8gZHg7CiAgICAgICAgfQogICAgICAgIHJldHVybiB7IHg6IGN4ICsgZGVsdGFYLCB5OiBjeSArIGRlbHRhWSB9OwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE1IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICdMaWNlbnNlJyk7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gJ0FTIElTJyBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgY29uc3Qgc2VsZWN0Q2hpbGQkMSA9IHNlbGVjdENoaWxkOwogICAgY29uc3QgQ2xhc3MkMiA9IENsYXNzJDE7CiAgICAvKioKICAgICAqIFRoZSBkaW1lbnNpb25zIG9mIHRoZSBtaW5pbWFwIGluY2x1ZGluZyBwYWRkaW5nIGFuZCBtYXJnaW4uCiAgICAgKi8KICAgIGNvbnN0IE1JTklNQVBfQk9YX1dJRFRIID0gMzIwOwogICAgY29uc3QgTUlOSU1BUF9CT1hfSEVJR0hUID0gMTUwOwogICAgbGV0IGhlYWx0aFBpbGxFbnRyaWVzID0gWwogICAgICAgIHsKICAgICAgICAgICAgYmFja2dyb3VuZF9jb2xvcjogJyNDQzJGMkMnLAogICAgICAgICAgICBsYWJlbDogJ05hTicsCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIGJhY2tncm91bmRfY29sb3I6ICcjRkY4RDAwJywKICAgICAgICAgICAgbGFiZWw6ICct4oieJywKICAgICAgICB9LAogICAgICAgIHsKICAgICAgICAgICAgYmFja2dyb3VuZF9jb2xvcjogJyNFQUVBRUEnLAogICAgICAgICAgICBsYWJlbDogJy0nLAogICAgICAgIH0sCiAgICAgICAgewogICAgICAgICAgICBiYWNrZ3JvdW5kX2NvbG9yOiAnI0E1QTVBNScsCiAgICAgICAgICAgIGxhYmVsOiAnMCcsCiAgICAgICAgfSwKICAgICAgICB7CiAgICAgICAgICAgIGJhY2tncm91bmRfY29sb3I6ICcjMjYyNjI2JywKICAgICAgICAgICAgbGFiZWw6ICcrJywKICAgICAgICB9LAogICAgICAgIHsKICAgICAgICAgICAgYmFja2dyb3VuZF9jb2xvcjogJyMwMDNFRDQnLAogICAgICAgICAgICBsYWJlbDogJyviiJ4nLAogICAgICAgIH0sCiAgICBdOwogICAgLyoqCiAgICAgKiBIZWxwZXIgbWV0aG9kIGZvciBmaXR0aW5nIHRoZSBncmFwaCBpbiB0aGUgc3ZnIHZpZXcuCiAgICAgKgogICAgICogQHBhcmFtIHN2ZyBUaGUgbWFpbiBzdmcuCiAgICAgKiBAcGFyYW0gem9vbUcgVGhlIHN2ZyBncm91cCB1c2VkIGZvciBwYW5uaW5nIGFuZCB6b29taW5nLgogICAgICogQHBhcmFtIGQzem9vbSBUaGUgem9vbSBiZWhhdmlvci4KICAgICAqIEBwYXJhbSBjYWxsYmFjayBDYWxsZWQgd2hlbiB0aGUgZml0dGluZyBpcyBkb25lLgogICAgICovCiAgICBmdW5jdGlvbiBmaXQkMihzdmcsIHpvb21HLCBkM3pvb20sIGNhbGxiYWNrKSB7CiAgICAgICAgbGV0IHN2Z1JlY3QgPSBzdmcuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgbGV0IHNjZW5lU2l6ZSA9IG51bGw7CiAgICAgICAgdHJ5IHsKICAgICAgICAgICAgc2NlbmVTaXplID0gem9vbUcuZ2V0QkJveCgpOwogICAgICAgICAgICBpZiAoc2NlbmVTaXplLndpZHRoID09PSAwKSB7CiAgICAgICAgICAgICAgICAvLyBUaGVyZSBpcyBubyBzY2VuZSBhbnltb3JlLiBXZSBoYXZlIGJlZW4gZGV0YWNoZWQgZnJvbSB0aGUgZG9tLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGNhdGNoIChlKSB7CiAgICAgICAgICAgIC8vIEZpcmVmb3ggcHJvZHVjZWQgTlNfRVJST1JfRkFJTFVSRSBpZiB3ZSBoYXZlIGJlZW4KICAgICAgICAgICAgLy8gZGV0YWNoZWQgZnJvbSB0aGUgZG9tLgogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGxldCBzY2FsZSA9IDAuOSAqCiAgICAgICAgICAgIE1hdGgubWluKHN2Z1JlY3Qud2lkdGggLyBzY2VuZVNpemUud2lkdGgsIHN2Z1JlY3QuaGVpZ2h0IC8gc2NlbmVTaXplLmhlaWdodCwgMik7CiAgICAgICAgbGV0IHBhcmFtcyA9IFBBUkFNUyQxLmdyYXBoOwogICAgICAgIGNvbnN0IHRyYW5zZm9ybSA9IGlkZW50aXR5JDkKICAgICAgICAgICAgLnNjYWxlKHNjYWxlKQogICAgICAgICAgICAudHJhbnNsYXRlKHBhcmFtcy5wYWRkaW5nLnBhZGRpbmdMZWZ0LCBwYXJhbXMucGFkZGluZy5wYWRkaW5nVG9wKTsKICAgICAgICBzZWxlY3Qoc3ZnKQogICAgICAgICAgICAudHJhbnNpdGlvbigpCiAgICAgICAgICAgIC5kdXJhdGlvbig1MDApCiAgICAgICAgICAgIC5jYWxsKGQzem9vbS50cmFuc2Zvcm0sIHRyYW5zZm9ybSkKICAgICAgICAgICAgLm9uKCdlbmQuZml0dGVkJywgKCkgPT4gewogICAgICAgICAgICAvLyBSZW1vdmUgdGhlIGxpc3RlbmVyIGZvciB0aGUgem9vbWVuZCBldmVudCwKICAgICAgICAgICAgLy8gc28gd2UgZG9uJ3QgZ2V0IGNhbGxlZCBhdCB0aGUgZW5kIG9mIHJlZ3VsYXIgem9vbSBldmVudHMsCiAgICAgICAgICAgIC8vIGp1c3QgdGhvc2UgdGhhdCBmaXQgdGhlIGdyYXBoIHRvIHNjcmVlbi4KICAgICAgICAgICAgZDN6b29tLm9uKCdlbmQuZml0dGVkJywgbnVsbCk7CiAgICAgICAgICAgIGNhbGxiYWNrKCk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIEhlbHBlciBtZXRob2QgZm9yIHBhbm5pbmcgdGhlIGdyYXBoIHRvIGNlbnRlciBvbiB0aGUgcHJvdmlkZWQgbm9kZSwKICAgICAqIGlmIHRoZSBub2RlIGlzIGN1cnJlbnRseSBvZmYtc2NyZWVuLgogICAgICoKICAgICAqIEBwYXJhbSBub2RlTmFtZSBUaGUgbm9kZSB0byBjZW50ZXIgdGhlIGdyYXBoIG9uCiAgICAgKiBAcGFyYW0gc3ZnIFRoZSByb290IFNWRyBlbGVtZW50IGZvciB0aGUgZ3JhcGgKICAgICAqIEBwYXJhbSB6b29tRyBUaGUgc3ZnIGdyb3VwIHVzZWQgZm9yIHBhbm5pbmcgYW5kIHpvb21pbmcuCiAgICAgKiBAcGFyYW0gZDN6b29tIFRoZSB6b29tIGJlaGF2aW9yLgogICAgICogQHJldHVybiBUcnVlIGlmIHRoZSBncmFwaCBoYWQgdG8gYmUgcGFubmVkIHRvIGRpc3BsYXkgdGhlCiAgICAgKiAgICAgICAgICAgIHByb3ZpZGVkIG5vZGUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBhblRvTm9kZShub2RlTmFtZSwgc3ZnLCB6b29tRywgZDN6b29tKSB7CiAgICAgICAgY29uc3Qgbm9kZSA9IChzZWxlY3Qoc3ZnKS5zZWxlY3QoYFtkYXRhLW5hbWU9IiR7bm9kZU5hbWV9Il1gKS5ub2RlKCkpOwogICAgICAgIGlmICghbm9kZSkgewogICAgICAgICAgICBjb25zb2xlLndhcm4oYHBhblRvTm9kZSgpIGZhaWxlZCBmb3Igbm9kZSBuYW1lICIke25vZGVOYW1lfSJgKTsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICAvLyBDaGVjayBpZiB0aGUgc2VsZWN0ZWQgbm9kZSBpcyBvZmYtc2NyZWVuIGluIGVpdGhlcgogICAgICAgIC8vIFggb3IgWSBkaW1lbnNpb24gaW4gZWl0aGVyIGRpcmVjdGlvbi4KICAgICAgICBsZXQgbm9kZUJveCA9IG5vZGUuZ2V0QkJveCgpOwogICAgICAgIGxldCBub2RlQ3RtID0gbm9kZS5nZXRTY3JlZW5DVE0oKTsKICAgICAgICBsZXQgcG9pbnRUTCA9IHN2Zy5jcmVhdGVTVkdQb2ludCgpOwogICAgICAgIGxldCBwb2ludEJSID0gc3ZnLmNyZWF0ZVNWR1BvaW50KCk7CiAgICAgICAgcG9pbnRUTC54ID0gbm9kZUJveC54OwogICAgICAgIHBvaW50VEwueSA9IG5vZGVCb3gueTsKICAgICAgICBwb2ludEJSLnggPSBub2RlQm94LnggKyBub2RlQm94LndpZHRoOwogICAgICAgIHBvaW50QlIueSA9IG5vZGVCb3gueSArIG5vZGVCb3guaGVpZ2h0OwogICAgICAgIHBvaW50VEwgPSBwb2ludFRMLm1hdHJpeFRyYW5zZm9ybShub2RlQ3RtKTsKICAgICAgICBwb2ludEJSID0gcG9pbnRCUi5tYXRyaXhUcmFuc2Zvcm0obm9kZUN0bSk7CiAgICAgICAgbGV0IGlzT3V0c2lkZU9mQm91bmRzID0gKHN0YXJ0LCBlbmQsIGxvd2VyQm91bmQsIHVwcGVyQm91bmQpID0+IHsKICAgICAgICAgICAgLy8gUmV0dXJuIGlmIGV2ZW4gYSBwYXJ0IG9mIHRoZSBpbnRlcnZhbCBpcyBvdXQgb2YgYm91bmRzLgogICAgICAgICAgICByZXR1cm4gIShzdGFydCA+IGxvd2VyQm91bmQgJiYgZW5kIDwgdXBwZXJCb3VuZCk7CiAgICAgICAgfTsKICAgICAgICBsZXQgc3ZnUmVjdCA9IHN2Zy5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAvLyBTdWJ0cmFjdCB0byBtYWtlIHN1cmUgdGhhdCB0aGUgbm9kZSBpcyBub3QgaGlkZGVuIGJlaGluZCB0aGUgbWluaW1hcC4KICAgICAgICBjb25zdCBob3Jpem9udGFsQm91bmQgPSBzdmdSZWN0LmxlZnQgKyBzdmdSZWN0LndpZHRoIC0gTUlOSU1BUF9CT1hfV0lEVEg7CiAgICAgICAgY29uc3QgdmVydGljYWxCb3VuZCA9IHN2Z1JlY3QudG9wICsgc3ZnUmVjdC5oZWlnaHQgLSBNSU5JTUFQX0JPWF9IRUlHSFQ7CiAgICAgICAgaWYgKGlzT3V0c2lkZU9mQm91bmRzKHBvaW50VEwueCwgcG9pbnRCUi54LCBzdmdSZWN0LmxlZnQsIGhvcml6b250YWxCb3VuZCkgfHwKICAgICAgICAgICAgaXNPdXRzaWRlT2ZCb3VuZHMocG9pbnRUTC55LCBwb2ludEJSLnksIHN2Z1JlY3QudG9wLCB2ZXJ0aWNhbEJvdW5kKSkgewogICAgICAgICAgICAvLyBEZXRlcm1pbmUgdGhlIGFtb3VudCB0byB0cmFuc2xhdGUgdGhlIGdyYXBoIGluIGJvdGggWCBhbmQgWSBkaW1lbnNpb25zIGluCiAgICAgICAgICAgIC8vIG9yZGVyIHRvIGNlbnRlciB0aGUgc2VsZWN0ZWQgbm9kZS4gVGhpcyB0YWtlcyBpbnRvIGFjY291bnQgdGhlIHBvc2l0aW9uCiAgICAgICAgICAgIC8vIG9mIHRoZSBub2RlLCB0aGUgc2l6ZSBvZiB0aGUgc3ZnIHNjZW5lLCB0aGUgYW1vdW50IHRoZSBzY2VuZSBoYXMgYmVlbgogICAgICAgICAgICAvLyBzY2FsZWQgYnkgdGhyb3VnaCB6b29taW5nLCBhbmQgYW55IHByZXZpb3VzIHRyYW5zZm9ybXMgYWxyZWFkeSBwZXJmb3JtZWQKICAgICAgICAgICAgLy8gYnkgdGhpcyBsb2dpYy4KICAgICAgICAgICAgbGV0IGNlbnRlclggPSAocG9pbnRUTC54ICsgcG9pbnRCUi54KSAvIDI7CiAgICAgICAgICAgIGxldCBjZW50ZXJZID0gKHBvaW50VEwueSArIHBvaW50QlIueSkgLyAyOwogICAgICAgICAgICBsZXQgZHggPSBzdmdSZWN0LmxlZnQgKyBzdmdSZWN0LndpZHRoIC8gMiAtIGNlbnRlclg7CiAgICAgICAgICAgIGxldCBkeSA9IHN2Z1JlY3QudG9wICsgc3ZnUmVjdC5oZWlnaHQgLyAyIC0gY2VudGVyWTsKICAgICAgICAgICAgLy8gV2UgdHJhbnNsYXRlIGJ5IHRoaXMgYW1vdW50LiBXZSBkaXZpZGUgdGhlIFggYW5kIFkgdHJhbnNsYXRpb25zIGJ5IHRoZQogICAgICAgICAgICAvLyBzY2FsZSB0byB1bmRvIGhvdyB0cmFuc2xhdGVCeSBzY2FsZXMgdGhlIHRyYW5zbGF0aW9ucyAoaW4gZDMgdjQpLgogICAgICAgICAgICBjb25zdCBzdmdUcmFuc2Zvcm0gPSB0cmFuc2Zvcm0kMShzdmcpOwogICAgICAgICAgICBzZWxlY3Qoc3ZnKQogICAgICAgICAgICAgICAgLnRyYW5zaXRpb24oKQogICAgICAgICAgICAgICAgLmR1cmF0aW9uKDUwMCkKICAgICAgICAgICAgICAgIC5jYWxsKGQzem9vbS50cmFuc2xhdGVCeSwgZHggLyBzdmdUcmFuc2Zvcm0uaywgZHkgLyBzdmdUcmFuc2Zvcm0uayk7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZmFsc2U7CiAgICB9CiAgICAvKioKICAgICAqIEdpdmVuIGEgc2NlbmUncyBzdmcgZ3JvdXAsIHNldCAgZy5pbi1leHRyYWN0LCBnLmNvcmVHcmFwaCwgZy5vdXQtZXh0cmFjdCBzdmcKICAgICAqIGdyb3VwcycgcG9zaXRpb24gcmVsYXRpdmUgdG8gdGhlIHNjZW5lLgogICAgICoKICAgICAqIEBwYXJhbSBzY2VuZUdyb3VwCiAgICAgKiBAcGFyYW0gcmVuZGVyTm9kZSByZW5kZXIgbm9kZSBvZiBhIG1ldGFub2RlIG9yIHNlcmllcyBub2RlLgogICAgICovCiAgICBmdW5jdGlvbiBwb3NpdGlvbiQxKHNjZW5lR3JvdXAsIHJlbmRlck5vZGUpIHsKICAgICAgICAvLyBUcmFuc2xhdGUgc2NlbmVzIGRvd24gYnkgdGhlIGxhYmVsIGhlaWdodCBzbyB0aGF0IHdoZW4gc2hvd2luZyBncmFwaHMgaW4KICAgICAgICAvLyBleHBhbmRlZCBtZXRhbm9kZXMsIHRoZSBncmFwaHMgYXJlIGJlbG93IHRoZSBsYWJlbHMuICBEbyBub3Qgc2hpZnQgdGhlbQogICAgICAgIC8vIGRvd24gZm9yIHNlcmllcyBub2RlcyBhcyBzZXJpZXMgbm9kZXMgZG9uJ3QgaGF2ZSBsYWJlbHMgaW5zaWRlIG9mIHRoZWlyCiAgICAgICAgLy8gYm91bmRpbmcgYm94ZXMuCiAgICAgICAgbGV0IHlUcmFuc2xhdGUgPSByZW5kZXJOb2RlLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuU0VSSUVTCiAgICAgICAgICAgID8gMAogICAgICAgICAgICA6IFBBUkFNUyQxLnN1YnNjZW5lLm1ldGEubGFiZWxIZWlnaHQ7CiAgICAgICAgLy8gY29yZQogICAgICAgIHRyYW5zbGF0ZSQxKHNlbGVjdENoaWxkJDEoc2NlbmVHcm91cCwgJ2cnLCBDbGFzcyQyLlNjZW5lLkNPUkUpLCAwLCB5VHJhbnNsYXRlKTsKICAgICAgICAvLyBpbi1leHRyYWN0CiAgICAgICAgbGV0IGhhc0luRXh0cmFjdCA9IHJlbmRlck5vZGUuaXNvbGF0ZWRJbkV4dHJhY3QubGVuZ3RoID4gMDsKICAgICAgICBsZXQgaGFzT3V0RXh0cmFjdCA9IHJlbmRlck5vZGUuaXNvbGF0ZWRPdXRFeHRyYWN0Lmxlbmd0aCA+IDA7CiAgICAgICAgbGV0IGhhc0xpYnJhcnlGdW5jdGlvbnMgPSByZW5kZXJOb2RlLmxpYnJhcnlGdW5jdGlvbnNFeHRyYWN0Lmxlbmd0aCA+IDA7CiAgICAgICAgbGV0IG9mZnNldCA9IFBBUkFNUyQxLnN1YnNjZW5lLm1ldGEuZXh0cmFjdFhPZmZzZXQ7CiAgICAgICAgbGV0IGF1eFdpZHRoID0gMDsKICAgICAgICBpZiAoaGFzSW5FeHRyYWN0KSB7CiAgICAgICAgICAgIGF1eFdpZHRoICs9IHJlbmRlck5vZGUub3V0RXh0cmFjdEJveC53aWR0aDsKICAgICAgICB9CiAgICAgICAgaWYgKGhhc091dEV4dHJhY3QpIHsKICAgICAgICAgICAgYXV4V2lkdGggKz0gcmVuZGVyTm9kZS5vdXRFeHRyYWN0Qm94LndpZHRoOwogICAgICAgIH0KICAgICAgICBpZiAoaGFzSW5FeHRyYWN0KSB7CiAgICAgICAgICAgIGxldCBpbkV4dHJhY3RYID0gcmVuZGVyTm9kZS5jb3JlQm94LndpZHRoOwogICAgICAgICAgICBpZiAoYXV4V2lkdGggPCBNSU5fQVVYX1dJRFRIKSB7CiAgICAgICAgICAgICAgICBpbkV4dHJhY3RYID0KICAgICAgICAgICAgICAgICAgICBpbkV4dHJhY3RYIC0gTUlOX0FVWF9XSURUSCArIHJlbmRlck5vZGUuaW5FeHRyYWN0Qm94LndpZHRoIC8gMjsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGluRXh0cmFjdFggPQogICAgICAgICAgICAgICAgICAgIGluRXh0cmFjdFggLQogICAgICAgICAgICAgICAgICAgICAgICByZW5kZXJOb2RlLmluRXh0cmFjdEJveC53aWR0aCAvIDIgLQogICAgICAgICAgICAgICAgICAgICAgICByZW5kZXJOb2RlLm91dEV4dHJhY3RCb3gud2lkdGggLQogICAgICAgICAgICAgICAgICAgICAgICAoaGFzT3V0RXh0cmFjdCA/IG9mZnNldCA6IDApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGluRXh0cmFjdFggPQogICAgICAgICAgICAgICAgaW5FeHRyYWN0WCAtCiAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5saWJyYXJ5RnVuY3Rpb25zQm94LndpZHRoIC0KICAgICAgICAgICAgICAgICAgICAoaGFzTGlicmFyeUZ1bmN0aW9ucyA/IG9mZnNldCA6IDApOwogICAgICAgICAgICB0cmFuc2xhdGUkMShzZWxlY3RDaGlsZCQxKHNjZW5lR3JvdXAsICdnJywgQ2xhc3MkMi5TY2VuZS5JTkVYVFJBQ1QpLCBpbkV4dHJhY3RYLCB5VHJhbnNsYXRlKTsKICAgICAgICB9CiAgICAgICAgLy8gb3V0LWV4dHJhY3QKICAgICAgICBpZiAoaGFzT3V0RXh0cmFjdCkgewogICAgICAgICAgICBsZXQgb3V0RXh0cmFjdFggPSByZW5kZXJOb2RlLmNvcmVCb3gud2lkdGg7CiAgICAgICAgICAgIGlmIChhdXhXaWR0aCA8IE1JTl9BVVhfV0lEVEgpIHsKICAgICAgICAgICAgICAgIG91dEV4dHJhY3RYID0KICAgICAgICAgICAgICAgICAgICBvdXRFeHRyYWN0WCAtIE1JTl9BVVhfV0lEVEggKyByZW5kZXJOb2RlLm91dEV4dHJhY3RCb3gud2lkdGggLyAyOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgb3V0RXh0cmFjdFggLT0gcmVuZGVyTm9kZS5vdXRFeHRyYWN0Qm94LndpZHRoIC8gMjsKICAgICAgICAgICAgfQogICAgICAgICAgICBvdXRFeHRyYWN0WCA9CiAgICAgICAgICAgICAgICBvdXRFeHRyYWN0WCAtCiAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5saWJyYXJ5RnVuY3Rpb25zQm94LndpZHRoIC0KICAgICAgICAgICAgICAgICAgICAoaGFzTGlicmFyeUZ1bmN0aW9ucyA/IG9mZnNldCA6IDApOwogICAgICAgICAgICB0cmFuc2xhdGUkMShzZWxlY3RDaGlsZCQxKHNjZW5lR3JvdXAsICdnJywgQ2xhc3MkMi5TY2VuZS5PVVRFWFRSQUNUKSwgb3V0RXh0cmFjdFgsIHlUcmFuc2xhdGUpOwogICAgICAgIH0KICAgICAgICBpZiAoaGFzTGlicmFyeUZ1bmN0aW9ucykgewogICAgICAgICAgICBsZXQgbGlicmFyeUZ1bmN0aW9uc0V4dHJhY3RYID0gcmVuZGVyTm9kZS5jb3JlQm94LndpZHRoIC0gcmVuZGVyTm9kZS5saWJyYXJ5RnVuY3Rpb25zQm94LndpZHRoIC8gMjsKICAgICAgICAgICAgdHJhbnNsYXRlJDEoc2VsZWN0Q2hpbGQkMShzY2VuZUdyb3VwLCAnZycsIENsYXNzJDIuU2NlbmUuRlVOQ1RJT05fTElCUkFSWSksIGxpYnJhcnlGdW5jdGlvbnNFeHRyYWN0WCwgeVRyYW5zbGF0ZSk7CiAgICAgICAgfQogICAgfQogICAgLyoqIEFkZHMgYSBjbGljayBsaXN0ZW5lciB0byBhIGdyb3VwIHRoYXQgZmlyZXMgYSBncmFwaC1zZWxlY3QgZXZlbnQgKi8KICAgIGZ1bmN0aW9uIGFkZEdyYXBoQ2xpY2tMaXN0ZW5lcihncmFwaEdyb3VwLCBzY2VuZUVsZW1lbnQpIHsKICAgICAgICBzZWxlY3QoZ3JhcGhHcm91cCkub24oJ2NsaWNrJywgKCkgPT4gewogICAgICAgICAgICBzY2VuZUVsZW1lbnQuZmlyZSgnZ3JhcGgtc2VsZWN0Jyk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKiogSGVscGVyIGZvciBhZGRpbmcgdHJhbnNmb3JtOiB0cmFuc2xhdGUoeDAsIHkwKSAqLwogICAgZnVuY3Rpb24gdHJhbnNsYXRlJDEoc2VsZWN0aW9uLCB4MCwgeTApIHsKICAgICAgICAvLyBJZiBpdCBpcyBhbHJlYWR5IHBsYWNlZCBvbiB0aGUgc2NyZWVuLCBtYWtlIGl0IGEgdHJhbnNpdGlvbi4KICAgICAgICBpZiAoc2VsZWN0aW9uLmF0dHIoJ3RyYW5zZm9ybScpICE9IG51bGwpIHsKICAgICAgICAgICAgc2VsZWN0aW9uID0gc2VsZWN0aW9uLnRyYW5zaXRpb24oJ3Bvc2l0aW9uJyk7CiAgICAgICAgfQogICAgICAgIHNlbGVjdGlvbi5hdHRyKCd0cmFuc2Zvcm0nLCAndHJhbnNsYXRlKCcgKyB4MCArICcsJyArIHkwICsgJyknKTsKICAgIH0KICAgIC8qKgogICAgICogSGVscGVyIGZvciBzZXR0aW5nIHBvc2l0aW9uIG9mIGEgc3ZnIHJlY3QKICAgICAqIEBwYXJhbSByZWN0IEEgZDMgc2VsZWN0aW9uIG9mIHJlY3QocykgdG8gc2V0IHBvc2l0aW9uIG9mLgogICAgICogQHBhcmFtIGN4IENlbnRlciB4LgogICAgICogQHBhcmFtIGN5IENlbnRlciB4LgogICAgICogQHBhcmFtIHdpZHRoIFdpZHRoIHRvIHNldC4KICAgICAqIEBwYXJhbSBoZWlnaHQgSGVpZ2h0IHRvIHNldC4KICAgICAqLwogICAgZnVuY3Rpb24gcG9zaXRpb25SZWN0KHJlY3QsIGN4LCBjeSwgd2lkdGgsIGhlaWdodCkgewogICAgICAgIHJlY3QKICAgICAgICAgICAgLnRyYW5zaXRpb24oKQogICAgICAgICAgICAuYXR0cigneCcsIGN4IC0gd2lkdGggLyAyKQogICAgICAgICAgICAuYXR0cigneScsIGN5IC0gaGVpZ2h0IC8gMikKICAgICAgICAgICAgLmF0dHIoJ3dpZHRoJywgd2lkdGgpCiAgICAgICAgICAgIC5hdHRyKCdoZWlnaHQnLCBoZWlnaHQpOwogICAgfQogICAgLyoqCiAgICAgKiBQb3NpdGlvbnMgYSB0cmlhbmdsZSBhbmQgc2l6ZXMgaXQuCiAgICAgKiBAcGFyYW0gcG9seWdvbiBwb2x5Z29uIHRvIHNldCBwb3NpdGlvbiBvZi4KICAgICAqIEBwYXJhbSBjeCBDZW50ZXIgeC4KICAgICAqIEBwYXJhbSBjeSBDZW50ZXIgeS4KICAgICAqIEBwYXJhbSB3aWR0aCBXaWR0aCBvZiBib3VuZGluZyBib3ggZm9yIHRyaWFuZ2xlLgogICAgICogQHBhcmFtIGhlaWdodCBIZWlnaHQgb2YgYm91bmRpbmcgYm94IGZvciB0cmlhbmdsZS4KICAgICAqLwogICAgZnVuY3Rpb24gcG9zaXRpb25UcmlhbmdsZShwb2x5Z29uLCBjeCwgY3ksIHdpZHRoLCBoZWlnaHQpIHsKICAgICAgICBjb25zdCBoYWxmSGVpZ2h0ID0gaGVpZ2h0IC8gMjsKICAgICAgICBjb25zdCBoYWxmV2lkdGggPSB3aWR0aCAvIDI7CiAgICAgICAgY29uc3QgcG9pbnRzID0gWwogICAgICAgICAgICBbY3gsIGN5IC0gaGFsZkhlaWdodF0sCiAgICAgICAgICAgIFtjeCArIGhhbGZXaWR0aCwgY3kgKyBoYWxmSGVpZ2h0XSwKICAgICAgICAgICAgW2N4IC0gaGFsZldpZHRoLCBjeSArIGhhbGZIZWlnaHRdLAogICAgICAgIF07CiAgICAgICAgcG9seWdvbgogICAgICAgICAgICAudHJhbnNpdGlvbigpCiAgICAgICAgICAgIC5hdHRyKCdwb2ludHMnLCBwb2ludHMubWFwKChwb2ludCkgPT4gcG9pbnQuam9pbignLCcpKS5qb2luKCcgJykpOwogICAgfQogICAgLyoqCiAgICAgKiBIZWxwZXIgZm9yIHNldHRpbmcgcG9zaXRpb24gb2YgYSBzdmcgZXhwYW5kL2NvbGxhcHNlIGJ1dHRvbgogICAgICogQHBhcmFtIGJ1dHRvbiBjb250YWluZXIgZ3JvdXAKICAgICAqIEBwYXJhbSByZW5kZXJOb2RlIHRoZSByZW5kZXIgbm9kZSBvZiB0aGUgZ3JvdXAgbm9kZSB0byBwb3NpdGlvbgogICAgICogICAgICAgIHRoZSBidXR0b24gb24uCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBvc2l0aW9uQnV0dG9uKGJ1dHRvbiwgcmVuZGVyTm9kZSkgewogICAgICAgIGxldCBjeCA9IGNvbXB1dGVDWFBvc2l0aW9uT2ZOb2RlU2hhcGUocmVuZGVyTm9kZSk7CiAgICAgICAgLy8gUG9zaXRpb24gdGhlIGJ1dHRvbiBpbiB0aGUgdG9wLXJpZ2h0IGNvcm5lciBvZiB0aGUgZ3JvdXAgbm9kZSwKICAgICAgICAvLyB3aXRoIHNwYWNlIGdpdmVuIHRoZSBkcmF3IHRoZSBidXR0b24gaW5zaWRlIG9mIHRoZSBjb3JuZXIuCiAgICAgICAgbGV0IHdpZHRoID0gcmVuZGVyTm9kZS5leHBhbmRlZCA/IHJlbmRlck5vZGUud2lkdGggOiByZW5kZXJOb2RlLmNvcmVCb3gud2lkdGg7CiAgICAgICAgbGV0IGhlaWdodCA9IHJlbmRlck5vZGUuZXhwYW5kZWQKICAgICAgICAgICAgPyByZW5kZXJOb2RlLmhlaWdodAogICAgICAgICAgICA6IHJlbmRlck5vZGUuY29yZUJveC5oZWlnaHQ7CiAgICAgICAgbGV0IHggPSBjeCArIHdpZHRoIC8gMiAtIDY7CiAgICAgICAgbGV0IHkgPSByZW5kZXJOb2RlLnkgLSBoZWlnaHQgLyAyICsgNjsKICAgICAgICAvLyBGb3IgdW5leHBhbmRlZCBzZXJpZXMgbm9kZXMsIHRoZSBidXR0b24gaGFzIHNwZWNpYWwgcGxhY2VtZW50IGR1ZQogICAgICAgIC8vIHRvIHRoZSB1bmlxdWUgdmlzdWFscyBvZiB0aGlzIGdyb3VwIG5vZGUuCiAgICAgICAgaWYgKHJlbmRlck5vZGUubm9kZS50eXBlID09PSBOb2RlVHlwZS5TRVJJRVMgJiYgIXJlbmRlck5vZGUuZXhwYW5kZWQpIHsKICAgICAgICAgICAgeCArPSAxMDsKICAgICAgICAgICAgeSAtPSAyOwogICAgICAgIH0KICAgICAgICBsZXQgdHJhbnNsYXRlU3RyID0gJ3RyYW5zbGF0ZSgnICsgeCArICcsJyArIHkgKyAnKSc7CiAgICAgICAgYnV0dG9uLnNlbGVjdEFsbCgncGF0aCcpLnRyYW5zaXRpb24oKS5hdHRyKCd0cmFuc2Zvcm0nLCB0cmFuc2xhdGVTdHIpOwogICAgICAgIGJ1dHRvbgogICAgICAgICAgICAuc2VsZWN0KCdjaXJjbGUnKQogICAgICAgICAgICAudHJhbnNpdGlvbigpCiAgICAgICAgICAgIC5hdHRyKHsgY3g6IHgsIGN5OiB5LCByOiBQQVJBTVMkMS5ub2RlU2l6ZS5tZXRhLmV4cGFuZEJ1dHRvblJhZGl1cyB9KTsKICAgIH0KICAgIC8qKgogICAgICogSGVscGVyIGZvciBzZXR0aW5nIHBvc2l0aW9uIG9mIGEgc3ZnIGVsbGlwc2UKICAgICAqIEBwYXJhbSBlbGxpcHNlIGVsbGlwc2UgdG8gc2V0IHBvc2l0aW9uIG9mLgogICAgICogQHBhcmFtIGN4IENlbnRlciB4LgogICAgICogQHBhcmFtIGN5IENlbnRlciB4LgogICAgICogQHBhcmFtIHdpZHRoIFdpZHRoIHRvIHNldC4KICAgICAqIEBwYXJhbSBoZWlnaHQgSGVpZ2h0IHRvIHNldC4KICAgICAqLwogICAgZnVuY3Rpb24gcG9zaXRpb25FbGxpcHNlKGVsbGlwc2UsIGN4LCBjeSwgd2lkdGgsIGhlaWdodCkgewogICAgICAgIGVsbGlwc2UKICAgICAgICAgICAgLnRyYW5zaXRpb24oKQogICAgICAgICAgICAuYXR0cignY3gnLCBjeCkKICAgICAgICAgICAgLmF0dHIoJ2N5JywgY3kpCiAgICAgICAgICAgIC5hdHRyKCdyeCcsIHdpZHRoIC8gMikKICAgICAgICAgICAgLmF0dHIoJ3J5JywgaGVpZ2h0IC8gMik7CiAgICB9CiAgICAvKioKICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzdGF0IEEgc3RhdCBmb3IgYSBoZWFsdGggcGlsbCAoc3VjaCBhcyBtZWFuIG9yIHZhcmlhbmNlKS4KICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2hvdWxkUm91bmRPbmVzRGlnaXQgV2hldGhlciB0byByb3VuZCB0aGlzIG51bWJlciB0byB0aGUKICAgICAqICAgICBvbmVzIGRpZ2l0LiBVc2VmdWwgZm9yIHNheSBpbnQsIHVpbnQsIGFuZCBib29sIG91dHB1dCB0eXBlcy4KICAgICAqIEByZXR1cm4ge3N0cmluZ30gQSBodW1hbi1mcmllbmRseSBzdHJpbmcgcmVwcmVzZW50YXRpb24gb2YgdGhhdCBzdGF0LgogICAgICovCiAgICBmdW5jdGlvbiBodW1hbml6ZUhlYWx0aFBpbGxTdGF0KHN0YXQsIHNob3VsZFJvdW5kT25lc0RpZ2l0KSB7CiAgICAgICAgaWYgKHNob3VsZFJvdW5kT25lc0RpZ2l0KSB7CiAgICAgICAgICAgIHJldHVybiBzdGF0LnRvRml4ZWQoMCk7CiAgICAgICAgfQogICAgICAgIGlmIChNYXRoLmFicyhzdGF0KSA+PSAxKSB7CiAgICAgICAgICAgIHJldHVybiBzdGF0LnRvRml4ZWQoMSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBzdGF0LnRvRXhwb25lbnRpYWwoMSk7CiAgICB9CiAgICAvKioKICAgICAqIEdldCB0ZXh0IGNvbnRlbnQgZGVzY3JpYmluZyBhIGhlYWx0aCBwaWxsLgogICAgICovCiAgICBmdW5jdGlvbiBfZ2V0SGVhbHRoUGlsbFRleHRDb250ZW50KGhlYWx0aFBpbGwsIHRvdGFsQ291bnQsIGVsZW1lbnRzQnJlYWtkb3duLCBudW1lcmljU3RhdHMpIHsKICAgICAgICBsZXQgdGV4dCA9ICdEZXZpY2U6ICcgKyBoZWFsdGhQaWxsLmRldmljZV9uYW1lICsgJ1xuJzsKICAgICAgICB0ZXh0ICs9ICdkdHlwZTogJyArIGhlYWx0aFBpbGwuZHR5cGUgKyAnXG4nOwogICAgICAgIGxldCBzaGFwZVN0ciA9ICcoc2NhbGFyKSc7CiAgICAgICAgaWYgKGhlYWx0aFBpbGwuc2hhcGUubGVuZ3RoID4gMCkgewogICAgICAgICAgICBzaGFwZVN0ciA9ICcoJyArIGhlYWx0aFBpbGwuc2hhcGUuam9pbignLCcpICsgJyknOwogICAgICAgIH0KICAgICAgICB0ZXh0ICs9ICdcbnNoYXBlOiAnICsgc2hhcGVTdHIgKyAnXG5cbic7CiAgICAgICAgdGV4dCArPSAnIyhlbGVtZW50cyk6ICcgKyB0b3RhbENvdW50ICsgJ1xuJzsKICAgICAgICBjb25zdCBicmVha2Rvd25JdGVtcyA9IFtdOwogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgZWxlbWVudHNCcmVha2Rvd24ubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgaWYgKGVsZW1lbnRzQnJlYWtkb3duW2ldID4gMCkgewogICAgICAgICAgICAgICAgYnJlYWtkb3duSXRlbXMucHVzaCgnIygnICsgaGVhbHRoUGlsbEVudHJpZXNbaV0ubGFiZWwgKyAnKTogJyArIGVsZW1lbnRzQnJlYWtkb3duW2ldKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB0ZXh0ICs9IGJyZWFrZG93bkl0ZW1zLmpvaW4oJywgJykgKyAnXG5cbic7CiAgICAgICAgLy8gSW4gc29tZSBjYXNlcyAoZS5nLiwgc2l6ZS0wIHRlbnNvcnM7IGFsbCBlbGVtZW50cyBhcmUgbmFuIG9yIGluZikgdGhlCiAgICAgICAgLy8gbWluL21heCBhbmQgbWVhbi9zdGRkZXYgc3RhdHMgYXJlIG1lYW5pbmdsZXNzLgogICAgICAgIGlmIChudW1lcmljU3RhdHMubWF4ID49IG51bWVyaWNTdGF0cy5taW4pIHsKICAgICAgICAgICAgdGV4dCArPSAnbWluOiAnICsgbnVtZXJpY1N0YXRzLm1pbiArICcsIG1heDogJyArIG51bWVyaWNTdGF0cy5tYXggKyAnXG4nOwogICAgICAgICAgICB0ZXh0ICs9ICdtZWFuOiAnICsgbnVtZXJpY1N0YXRzLm1lYW4gKyAnLCBzdGRkZXY6ICcgKyBudW1lcmljU3RhdHMuc3RkZGV2OwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGV4dDsKICAgIH0KICAgIC8qKgogICAgICogUmVuZGVycyBhIGhlYWx0aCBwaWxsIGZvciBhbiBvcCBhdG9wIGEgbm9kZS4KICAgICAqIG5vZGVHcm91cEVsZW1lbnQ6IFRoZSBTVkcgZWxlbWVudCBpbiB3aGljaCB0byByZW5kZXIuCiAgICAgKiBoZWFsdGhQaWxsOiBBIGxpc3Qgb2YgYmFja2VuZC5IZWFsdGhQaWxsIG9iamVjdHMuCiAgICAgKiBub2RlSW5mbzogSW5mbyBvbiB0aGUgYXNzb2NpYXRlZCBub2RlLgogICAgICogaGVhbHRoUGlsbElkOiBBIHVuaXF1ZSBudW1lcmljIElEIGFzc2lnbmVkIHRvIHRoaXMgaGVhbHRoIHBpbGwuCiAgICAgKiBoZWFsdGhQaWxsV2lkdGg6IE9wdGlvbmFsIHdpZHRoIG9mIHRoZSBoZWFsdGggcGlsbC4KICAgICAqIGhlYWx0aFBpbGxIZWlnaHQ6IE9wdGlvbmFsIGhlaWdodCBvZiB0aGUgaGVhbHRoIHBpbGwuCiAgICAgKiBoZWFsdGhQaWxsWU9mZnNldDogT3B0aW9uYWwgeS1vZmZzZXQgb2YgdGhlIGhlYWx0aCBwaWxsICh0aGF0IGlzLCB0aGUKICAgICAqICAgY29sb3ItY29kZWQgcmVnaW9uKS4KICAgICAqIHRleHRPZmZzZXQ6IE9wdGlvbmFsIHZhbHVlIGZvciB0aGUgeC1vZmZzZXQgb2YgdGhlIHRvcCB0ZXh0IGxhYmVsCiAgICAgKiAgIHJlbGF0aXZlIHRvIHRoZSBsZWZ0IGVkZ2Ugb2YgdGhlIGhlYWx0aCBwaWxsLiBJZiBub3QgcHJvdmlkZWQsIHdpbGwKICAgICAqICAgZGVmYXVsdCB0byBgaGVhbHRoUGlsbFdpZHRoIC8gMmAuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFkZEhlYWx0aFBpbGwobm9kZUdyb3VwRWxlbWVudCwgaGVhbHRoUGlsbCwgbm9kZUluZm8sIGhlYWx0aFBpbGxJZCwgaGVhbHRoUGlsbFdpZHRoID0gNjAsIGhlYWx0aFBpbGxIZWlnaHQgPSAxMCwgaGVhbHRoUGlsbFlPZmZzZXQgPSAwLCB0ZXh0WE9mZnNldCkgewogICAgICAgIC8vIENoZWNrIGlmIHRleHQgYWxyZWFkeSBleGlzdHMgYXQgbG9jYXRpb24uCiAgICAgICAgc2VsZWN0KG5vZGVHcm91cEVsZW1lbnQucGFyZW50Tm9kZSkKICAgICAgICAgICAgLnNlbGVjdEFsbCgnLmhlYWx0aC1waWxsJykKICAgICAgICAgICAgLnJlbW92ZSgpOwogICAgICAgIGlmICghaGVhbHRoUGlsbCkgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGNvbnN0IGxhc3RIZWFsdGhQaWxsRGF0YSA9IGhlYWx0aFBpbGwudmFsdWU7CiAgICAgICAgLy8gRm9yIG5vdywgd2Ugb25seSB2aXN1YWxpemUgdGhlIDYgdmFsdWVzIHRoYXQgc3VtbWFyaXplIGNvdW50cyBvZiB0ZW5zb3IKICAgICAgICAvLyBlbGVtZW50cyBvZiB2YXJpb3VzIGNhdGVnb3JpZXM6IC1JbmYsIG5lZ2F0aXZlLCAwLCBwb3NpdGl2ZSwgSW5mLCBhbmQgTmFOLgogICAgICAgIGNvbnN0IGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd24gPSBsYXN0SGVhbHRoUGlsbERhdGEuc2xpY2UoMiwgOCk7CiAgICAgICAgY29uc3QgbmFuQ291bnQgPSBsYXN0SGVhbHRoUGlsbEVsZW1lbnRzQnJlYWtkb3duWzBdOwogICAgICAgIGNvbnN0IG5lZ0luZkNvdW50ID0gbGFzdEhlYWx0aFBpbGxFbGVtZW50c0JyZWFrZG93blsxXTsKICAgICAgICBjb25zdCBwb3NJbmZDb3VudCA9IGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd25bNV07CiAgICAgICAgbGV0IHRvdGFsQ291bnQgPSBsYXN0SGVhbHRoUGlsbERhdGFbMV07CiAgICAgICAgY29uc3QgbnVtZXJpY1N0YXRzID0gewogICAgICAgICAgICBtaW46IGxhc3RIZWFsdGhQaWxsRGF0YVs4XSwKICAgICAgICAgICAgbWF4OiBsYXN0SGVhbHRoUGlsbERhdGFbOV0sCiAgICAgICAgICAgIG1lYW46IGxhc3RIZWFsdGhQaWxsRGF0YVsxMF0sCiAgICAgICAgICAgIHN0ZGRldjogTWF0aC5zcXJ0KGxhc3RIZWFsdGhQaWxsRGF0YVsxMV0pLAogICAgICAgIH07CiAgICAgICAgaWYgKGhlYWx0aFBpbGxXaWR0aCA9PSBudWxsKSB7CiAgICAgICAgICAgIGhlYWx0aFBpbGxXaWR0aCA9IDYwOwogICAgICAgIH0KICAgICAgICBpZiAoaGVhbHRoUGlsbEhlaWdodCA9PSBudWxsKSB7CiAgICAgICAgICAgIGhlYWx0aFBpbGxIZWlnaHQgPSAxMDsKICAgICAgICB9CiAgICAgICAgaWYgKGhlYWx0aFBpbGxZT2Zmc2V0ID09IG51bGwpIHsKICAgICAgICAgICAgaGVhbHRoUGlsbFlPZmZzZXQgPSAwOwogICAgICAgIH0KICAgICAgICBpZiAobm9kZUluZm8gIT0gbnVsbCAmJiBub2RlSW5mby5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLk9QKSB7CiAgICAgICAgICAgIC8vIFVzZSBhIHNtYWxsZXIgaGVhbHRoIHBpbGwgZm9yIG9wIG5vZGVzIChyZW5kZXJlZCBhcyBzbWFsbGVyIGVsbGlwc2VzKS4KICAgICAgICAgICAgaGVhbHRoUGlsbFdpZHRoIC89IDI7CiAgICAgICAgICAgIGhlYWx0aFBpbGxIZWlnaHQgLz0gMjsKICAgICAgICB9CiAgICAgICAgbGV0IGhlYWx0aFBpbGxHcm91cCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAnZycpOwogICAgICAgIGhlYWx0aFBpbGxHcm91cC5jbGFzc0xpc3QuYWRkKCdoZWFsdGgtcGlsbCcpOwogICAgICAgIC8vIERlZmluZSB0aGUgZ3JhZGllbnQgZm9yIHRoZSBoZWFsdGggcGlsbC4KICAgICAgICBsZXQgaGVhbHRoUGlsbERlZnMgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHX05BTUVTUEFDRSwgJ2RlZnMnKTsKICAgICAgICBoZWFsdGhQaWxsR3JvdXAuYXBwZW5kQ2hpbGQoaGVhbHRoUGlsbERlZnMpOwogICAgICAgIGxldCBoZWFsdGhQaWxsR3JhZGllbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHX05BTUVTUEFDRSwgJ2xpbmVhckdyYWRpZW50Jyk7CiAgICAgICAgLy8gRXZlcnkgZWxlbWVudCBpbiBhIHdlYiBwYWdlIG11c3QgaGF2ZSBhIHVuaXF1ZSBJRC4KICAgICAgICBjb25zdCBoZWFsdGhQaWxsR3JhZGllbnRJZCA9ICdoZWFsdGgtcGlsbC1ncmFkaWVudC0nICsgaGVhbHRoUGlsbElkOwogICAgICAgIGhlYWx0aFBpbGxHcmFkaWVudC5zZXRBdHRyaWJ1dGUoJ2lkJywgaGVhbHRoUGlsbEdyYWRpZW50SWQpOwogICAgICAgIGxldCBjdW11bGF0aXZlQ291bnQgPSAwOwogICAgICAgIGxldCBwcmV2aW91c09mZnNldCA9ICcwJSc7CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBsYXN0SGVhbHRoUGlsbEVsZW1lbnRzQnJlYWtkb3duLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGlmICghbGFzdEhlYWx0aFBpbGxFbGVtZW50c0JyZWFrZG93bltpXSkgewogICAgICAgICAgICAgICAgLy8gRXhjbHVkZSBlbXB0eSBjYXRlZ29yaWVzLgogICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY3VtdWxhdGl2ZUNvdW50ICs9IGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd25baV07CiAgICAgICAgICAgIC8vIENyZWF0ZSBhIGNvbG9yIGludGVydmFsIHVzaW5nIDIgc3RvcCBlbGVtZW50cy4KICAgICAgICAgICAgbGV0IHN0b3BFbGVtZW50MCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAnc3RvcCcpOwogICAgICAgICAgICBzdG9wRWxlbWVudDAuc2V0QXR0cmlidXRlKCdvZmZzZXQnLCBwcmV2aW91c09mZnNldCk7CiAgICAgICAgICAgIHN0b3BFbGVtZW50MC5zZXRBdHRyaWJ1dGUoJ3N0b3AtY29sb3InLCBoZWFsdGhQaWxsRW50cmllc1tpXS5iYWNrZ3JvdW5kX2NvbG9yKTsKICAgICAgICAgICAgaGVhbHRoUGlsbEdyYWRpZW50LmFwcGVuZENoaWxkKHN0b3BFbGVtZW50MCk7CiAgICAgICAgICAgIGxldCBzdG9wRWxlbWVudDEgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50TlMoU1ZHX05BTUVTUEFDRSwgJ3N0b3AnKTsKICAgICAgICAgICAgbGV0IHBlcmNlbnQgPSAoY3VtdWxhdGl2ZUNvdW50ICogMTAwKSAvIHRvdGFsQ291bnQgKyAnJSc7CiAgICAgICAgICAgIHN0b3BFbGVtZW50MS5zZXRBdHRyaWJ1dGUoJ29mZnNldCcsIHBlcmNlbnQpOwogICAgICAgICAgICBzdG9wRWxlbWVudDEuc2V0QXR0cmlidXRlKCdzdG9wLWNvbG9yJywgaGVhbHRoUGlsbEVudHJpZXNbaV0uYmFja2dyb3VuZF9jb2xvcik7CiAgICAgICAgICAgIGhlYWx0aFBpbGxHcmFkaWVudC5hcHBlbmRDaGlsZChzdG9wRWxlbWVudDEpOwogICAgICAgICAgICBwcmV2aW91c09mZnNldCA9IHBlcmNlbnQ7CiAgICAgICAgfQogICAgICAgIGhlYWx0aFBpbGxEZWZzLmFwcGVuZENoaWxkKGhlYWx0aFBpbGxHcmFkaWVudCk7CiAgICAgICAgLy8gQ3JlYXRlIHRoZSByZWN0YW5nbGUgZm9yIHRoZSBoZWFsdGggcGlsbC4KICAgICAgICBsZXQgcmVjdCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAncmVjdCcpOwogICAgICAgIHJlY3Quc2V0QXR0cmlidXRlKCdmaWxsJywgJ3VybCgjJyArIGhlYWx0aFBpbGxHcmFkaWVudElkICsgJyknKTsKICAgICAgICByZWN0LnNldEF0dHJpYnV0ZSgnd2lkdGgnLCBTdHJpbmcoaGVhbHRoUGlsbFdpZHRoKSk7CiAgICAgICAgcmVjdC5zZXRBdHRyaWJ1dGUoJ2hlaWdodCcsIFN0cmluZyhoZWFsdGhQaWxsSGVpZ2h0KSk7CiAgICAgICAgcmVjdC5zZXRBdHRyaWJ1dGUoJ3knLCBTdHJpbmcoaGVhbHRoUGlsbFlPZmZzZXQpKTsKICAgICAgICBoZWFsdGhQaWxsR3JvdXAuYXBwZW5kQ2hpbGQocmVjdCk7CiAgICAgICAgLy8gU2hvdyBhIHRpdGxlIHdpdGggc3BlY2lmaWMgY291bnRzIG9uIGhvdmVyLgogICAgICAgIGxldCB0aXRsZVN2ZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAndGl0bGUnKTsKICAgICAgICB0aXRsZVN2Zy50ZXh0Q29udGVudCA9IF9nZXRIZWFsdGhQaWxsVGV4dENvbnRlbnQoaGVhbHRoUGlsbCwgdG90YWxDb3VudCwgbGFzdEhlYWx0aFBpbGxFbGVtZW50c0JyZWFrZG93biwgbnVtZXJpY1N0YXRzKTsKICAgICAgICBoZWFsdGhQaWxsR3JvdXAuYXBwZW5kQ2hpbGQodGl0bGVTdmcpOwogICAgICAgIC8vIENlbnRlciB0aGlzIGhlYWx0aCBwaWxsIGp1c3QgcmlnaHQgYWJvdmUgdGhlIG5vZGUgZm9yIHRoZSBvcC4KICAgICAgICBsZXQgc2hvdWxkUm91bmRPbmVzRGlnaXQgPSBmYWxzZTsKICAgICAgICBpZiAobm9kZUluZm8gIT0gbnVsbCkgewogICAgICAgICAgICBsZXQgaGVhbHRoUGlsbFggPSBub2RlSW5mby54IC0gaGVhbHRoUGlsbFdpZHRoIC8gMjsKICAgICAgICAgICAgbGV0IGhlYWx0aFBpbGxZID0gbm9kZUluZm8ueSAtIGhlYWx0aFBpbGxIZWlnaHQgLSBub2RlSW5mby5oZWlnaHQgLyAyIC0gMjsKICAgICAgICAgICAgaWYgKG5vZGVJbmZvLmxhYmVsT2Zmc2V0IDwgMCkgewogICAgICAgICAgICAgICAgLy8gVGhlIGxhYmVsIGlzIHBvc2l0aW9uZWQgYWJvdmUgdGhlIG5vZGUuIERvIG5vdCBvY2NsdWRlIHRoZSBsYWJlbC4KICAgICAgICAgICAgICAgIGhlYWx0aFBpbGxZICs9IG5vZGVJbmZvLmxhYmVsT2Zmc2V0OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGhlYWx0aFBpbGxHcm91cC5zZXRBdHRyaWJ1dGUoJ3RyYW5zZm9ybScsICd0cmFuc2xhdGUoJyArIGhlYWx0aFBpbGxYICsgJywgJyArIGhlYWx0aFBpbGxZICsgJyknKTsKICAgICAgICAgICAgaWYgKGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd25bMl0gfHwKICAgICAgICAgICAgICAgIGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd25bM10gfHwKICAgICAgICAgICAgICAgIGxhc3RIZWFsdGhQaWxsRWxlbWVudHNCcmVha2Rvd25bNF0pIHsKICAgICAgICAgICAgICAgIC8vIEF0IGxlYXN0IDEgIm5vbi1JbmYgYW5kIG5vbi1OYU4iIHZhbHVlIGV4aXN0cyAoYSAtLCAwLCBvciArIHZhbHVlKS4gU2hvdwogICAgICAgICAgICAgICAgLy8gc3RhdHMgb24gdGVuc29yIHZhbHVlcy4KICAgICAgICAgICAgICAgIC8vIERldGVybWluZSBpZiB3ZSBzaG91bGQgZGlzcGxheSB0aGUgb3V0cHV0IHJhbmdlIGFzIGludGVnZXJzLgogICAgICAgICAgICAgICAgbGV0IG5vZGUgPSBub2RlSW5mby5ub2RlOwogICAgICAgICAgICAgICAgbGV0IGF0dHJpYnV0ZXMgPSBub2RlLmF0dHI7CiAgICAgICAgICAgICAgICBpZiAoYXR0cmlidXRlcyAmJiBhdHRyaWJ1dGVzLmxlbmd0aCkgewogICAgICAgICAgICAgICAgICAgIC8vIEZpbmQgdGhlIGF0dHJpYnV0ZSBmb3Igb3V0cHV0IHR5cGUgaWYgdGhlcmUgaXMgb25lLgogICAgICAgICAgICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgYXR0cmlidXRlcy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgICAgICAgICBpZiAoYXR0cmlidXRlc1tpXS5rZXkgPT09ICdUJykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gTm90ZSB3aGV0aGVyIHRoZSBvdXRwdXQgdHlwZSBpcyBhbiBpbnRlZ2VyLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgbGV0IG91dHB1dFR5cGUgPSBhdHRyaWJ1dGVzW2ldLnZhbHVlWyd0eXBlJ107CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBzaG91bGRSb3VuZE9uZXNEaWdpdCA9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3V0cHV0VHlwZSAmJiAvXkRUXyhCT09MfElOVHxVSU5UKS8udGVzdChvdXRwdXRUeXBlKTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGxldCBzdGF0c1N2ZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAndGV4dCcpOwogICAgICAgIGlmIChOdW1iZXIuaXNGaW5pdGUobnVtZXJpY1N0YXRzLm1pbikgJiYgTnVtYmVyLmlzRmluaXRlKG51bWVyaWNTdGF0cy5tYXgpKSB7CiAgICAgICAgICAgIGNvbnN0IG1pblN0cmluZyA9IGh1bWFuaXplSGVhbHRoUGlsbFN0YXQobnVtZXJpY1N0YXRzLm1pbiwgc2hvdWxkUm91bmRPbmVzRGlnaXQpOwogICAgICAgICAgICBjb25zdCBtYXhTdHJpbmcgPSBodW1hbml6ZUhlYWx0aFBpbGxTdGF0KG51bWVyaWNTdGF0cy5tYXgsIHNob3VsZFJvdW5kT25lc0RpZ2l0KTsKICAgICAgICAgICAgaWYgKHRvdGFsQ291bnQgPiAxKSB7CiAgICAgICAgICAgICAgICBzdGF0c1N2Zy50ZXh0Q29udGVudCA9IG1pblN0cmluZyArICcgfiAnICsgbWF4U3RyaW5nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgc3RhdHNTdmcudGV4dENvbnRlbnQgPSBtaW5TdHJpbmc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG5hbkNvdW50ID4gMCB8fCBuZWdJbmZDb3VudCA+IDAgfHwgcG9zSW5mQ291bnQgPiAwKSB7CiAgICAgICAgICAgICAgICBzdGF0c1N2Zy50ZXh0Q29udGVudCArPSAnICgnOwogICAgICAgICAgICAgICAgY29uc3QgYmFkVmFsdWVTdHJpbmdzID0gW107CiAgICAgICAgICAgICAgICBpZiAobmFuQ291bnQgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgYmFkVmFsdWVTdHJpbmdzLnB1c2goYE5hTsOXJHtuYW5Db3VudH1gKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChuZWdJbmZDb3VudCA+IDApIHsKICAgICAgICAgICAgICAgICAgICBiYWRWYWx1ZVN0cmluZ3MucHVzaChgLeKInsOXJHtuZWdJbmZDb3VudH1gKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChwb3NJbmZDb3VudCA+IDApIHsKICAgICAgICAgICAgICAgICAgICBiYWRWYWx1ZVN0cmluZ3MucHVzaChgK+KInsOXJHtwb3NJbmZDb3VudH1gKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHN0YXRzU3ZnLnRleHRDb250ZW50ICs9IGJhZFZhbHVlU3RyaW5ncy5qb2luKCc7ICcpICsgJyknOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBzdGF0c1N2Zy50ZXh0Q29udGVudCA9ICcoTm8gZmluaXRlIGVsZW1lbnRzKSc7CiAgICAgICAgfQogICAgICAgIHN0YXRzU3ZnLmNsYXNzTGlzdC5hZGQoJ2hlYWx0aC1waWxsLXN0YXRzJyk7CiAgICAgICAgaWYgKHRleHRYT2Zmc2V0ID09IG51bGwpIHsKICAgICAgICAgICAgdGV4dFhPZmZzZXQgPSBoZWFsdGhQaWxsV2lkdGggLyAyOwogICAgICAgIH0KICAgICAgICBzdGF0c1N2Zy5zZXRBdHRyaWJ1dGUoJ3gnLCBTdHJpbmcodGV4dFhPZmZzZXQpKTsKICAgICAgICBzdGF0c1N2Zy5zZXRBdHRyaWJ1dGUoJ3knLCBTdHJpbmcoaGVhbHRoUGlsbFlPZmZzZXQgLSAyKSk7CiAgICAgICAgaGVhbHRoUGlsbEdyb3VwLmFwcGVuZENoaWxkKHN0YXRzU3ZnKTsKICAgICAgICBkb20obm9kZUdyb3VwRWxlbWVudC5wYXJlbnROb2RlKS5hcHBlbmRDaGlsZChoZWFsdGhQaWxsR3JvdXApOwogICAgfQogICAgLyoqCiAgICAgKiBBZGRzIGhlYWx0aCBwaWxscyAod2hpY2ggdmlzdWFsaXplIHRlbnNvciBzdW1tYXJpZXMpIHRvIGEgZ3JhcGggZ3JvdXAuCiAgICAgKiBAcGFyYW0gc3ZnUm9vdCBUaGUgcm9vdCBTVkcgZWxlbWVudCBvZiB0aGUgZ3JhcGggdG8gYWRkIGhlYXRoIHBpbGxzIHRvLgogICAgICogQHBhcmFtIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMgQW4gb2JqZWN0IG1hcHBpbmcgbm9kZSBuYW1lIHRvIGhlYWx0aCBwaWxsLgogICAgICogQHBhcmFtIGNvbG9ycyBBIGxpc3Qgb2YgY29sb3JzIHRvIHVzZS4KICAgICAqLwogICAgZnVuY3Rpb24gYWRkSGVhbHRoUGlsbHMoc3ZnUm9vdCwgbm9kZU5hbWVzVG9IZWFsdGhQaWxscywgaGVhbHRoUGlsbFN0ZXBJbmRleCkgewogICAgICAgIGlmICghbm9kZU5hbWVzVG9IZWFsdGhQaWxscykgewogICAgICAgICAgICAvLyBObyBoZWFsdGggcGlsbCBpbmZvcm1hdGlvbiBhdmFpbGFibGUuCiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgLy8gV2UgZ2VuZXJhdGUgYSB1bmlxdWUgSUQgZm9yIGVhY2ggaGVhbHRoIHBpbGwgYmVjYXVzZSB0aGUgSUQgb2YgZWFjaCBlbGVtZW50CiAgICAgICAgLy8gaW4gYSB3ZWIgcGFnZSBtdXN0IGJlIHVuaXF1ZSwgYW5kIGVhY2ggaGVhbHRoIHBpbGwgZ2VuZXJhdGVzIGEgZ3JhZGllbnQKICAgICAgICAvLyB0aGF0IGl0cyBjb2RlIGxhdGVyIHJlZmVycyB0by4KICAgICAgICBsZXQgaGVhbHRoUGlsbElkID0gMTsKICAgICAgICBsZXQgc3ZnUm9vdFNlbGVjdGlvbiA9IHNlbGVjdChzdmdSb290KTsKICAgICAgICBzdmdSb290U2VsZWN0aW9uCiAgICAgICAgICAgIC5zZWxlY3RBbGwoJ2cubm9kZXNoYXBlJykKICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKG5vZGVJbmZvKSB7CiAgICAgICAgICAgIC8vIE9ubHkgc2hvdyBoZWFsdGggcGlsbCBkYXRhIGZvciB0aGlzIG5vZGUgaWYgaXQgaXMgYXZhaWxhYmxlLgogICAgICAgICAgICBjb25zdCBoZWFsdGhQaWxscyA9IG5vZGVOYW1lc1RvSGVhbHRoUGlsbHNbbm9kZUluZm8ubm9kZS5uYW1lXTsKICAgICAgICAgICAgY29uc3QgaGVhbHRoUGlsbCA9IGhlYWx0aFBpbGxzID8gaGVhbHRoUGlsbHNbaGVhbHRoUGlsbFN0ZXBJbmRleF0gOiBudWxsOwogICAgICAgICAgICBhZGRIZWFsdGhQaWxsKHRoaXMsIGhlYWx0aFBpbGwsIG5vZGVJbmZvLCBoZWFsdGhQaWxsSWQrKyk7CiAgICAgICAgfSk7CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZHcmFwaERlYnVnZ2VyRGF0YUNhcmQgPSBjbGFzcyBUZkdyYXBoRGVidWdnZXJEYXRhQ2FyZCBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvLyBPbmx5IHJlbGV2YW50IGlmIHdlIGFyZSBpbiBhbGwgc3RlcHMgbW9kZSwgaW4gd2hpY2ggY2FzZSB0aGUgdXNlciBtYXkgd2FudCB0byB2aWV3IGhlYWx0aAogICAgICAgICAgICAvLyBwaWxscyBmb3IgYSBzcGVjaWZpYyBzdGVwLgogICAgICAgICAgICB0aGlzLnNwZWNpZmljSGVhbHRoUGlsbFN0ZXAgPSAwOwogICAgICAgICAgICB0aGlzLmhlYWx0aFBpbGxFbnRyaWVzID0gaGVhbHRoUGlsbEVudHJpZXM7CiAgICAgICAgfQogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgICBzdXBlci5yZWFkeSgpOwogICAgICAgICAgICB2YXIgbWFpbkNvbnRhaW5lciA9IGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKCdtYWluQ29udGFpbmVyJyk7CiAgICAgICAgICAgIHZhciBzY3JvbGxiYXJDb250YWluZXIgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCd0Zi1kYXNoYm9hcmQtbGF5b3V0IC5zY3JvbGxiYXInKTsKICAgICAgICAgICAgaWYgKG1haW5Db250YWluZXIgJiYgc2Nyb2xsYmFyQ29udGFpbmVyKSB7CiAgICAgICAgICAgICAgICAvLyBJZiB0aGlzIGNvbXBvbmVudCBpcyBiZWluZyB1c2VkIGluc2lkZSBvZiBUZW5zb3JCb2FyZCdzIGRhc2hib2FyZCBsYXlvdXQsIGl0IG1heSBlYXNpbHkKICAgICAgICAgICAgICAgIC8vIGNhdXNlIHRoZSBkYXNoYm9hcmQgbGF5b3V0IGVsZW1lbnQgdG8gb3ZlcmZsb3csIGdpdmluZyB0aGUgdXNlciAyIHNjcm9sbCBiYXJzLiBQcmV2ZW50CiAgICAgICAgICAgICAgICAvLyB0aGF0IGJ5IGhpZGluZyB3aGF0ZXZlciBjb250ZW50IG92ZXJmbG93cyAtIHRoZSB1c2VyIHdpbGwgaGF2ZSB0byBleHBhbmQgdGhlIHZpZXdwb3J0IHRvCiAgICAgICAgICAgICAgICAvLyB1c2UgdGhpcyBkZWJ1Z2dpbmcgY2FyZC4KICAgICAgICAgICAgICAgIG1haW5Db250YWluZXIuc3R5bGUub3ZlcmZsb3cgPSAnaGlkZGVuJzsKICAgICAgICAgICAgICAgIHNjcm9sbGJhckNvbnRhaW5lci5zdHlsZS5vdmVyZmxvdyA9ICdoaWRkZW4nOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9oZWFsdGhQaWxsc0F2YWlsYWJsZShkZWJ1Z2dlckRhdGFFbmFibGVkLCBub2RlTmFtZXNUb0hlYWx0aFBpbGxzKSB7CiAgICAgICAgICAgIC8vIFNvIGxvbmcgYXMgdGhlcmUgaXMgYSBtYXBwaW5nIChldmVuIGlmIGVtcHR5KSBmcm9tIG5vZGUgbmFtZSB0byBoZWFsdGggcGlsbHMsIHNob3cgdGhlCiAgICAgICAgICAgIC8vIGxlZ2VuZCBhbmQgc2xpZGVyLiBXZSBkbyB0aGF0IGJlY2F1c2UsIGV2ZW4gaWYgbm8gaGVhbHRoIHBpbGxzIGV4aXN0IGF0IHRoZSBjdXJyZW50IHN0ZXAsCiAgICAgICAgICAgIC8vIHRoZSB1c2VyIG1heSBkZXNpcmUgdG8gY2hhbmdlIHN0ZXBzLCBhbmQgdGhlIHNsaWRlciBtdXN0IHNob3cgZm9yIHRoZSB1c2VyIHRvIGRvIHRoYXQuCiAgICAgICAgICAgIHJldHVybiBkZWJ1Z2dlckRhdGFFbmFibGVkICYmIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHM7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlVGVuc29yQ291bnRTdHJpbmcoaGVhbHRoUGlsbFZhbHVlc0ZvclNlbGVjdGVkTm9kZSwgdmFsdWVJbmRleCkgewogICAgICAgICAgICBpZiAoIWhlYWx0aFBpbGxWYWx1ZXNGb3JTZWxlY3RlZE5vZGUpIHsKICAgICAgICAgICAgICAgIC8vIE5vIGhlYWx0aCBwaWxsIGRhdGEgaXMgYXZhaWxhYmxlLgogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBoZWFsdGhQaWxsVmFsdWVzRm9yU2VsZWN0ZWROb2RlW3ZhbHVlSW5kZXhdLnRvRml4ZWQoMCk7CiAgICAgICAgfQogICAgICAgIGdldCBoZWFsdGhQaWxsVmFsdWVzRm9yU2VsZWN0ZWROb2RlKCkgewogICAgICAgICAgICB2YXIgbm9kZU5hbWVzVG9IZWFsdGhQaWxscyA9IHRoaXMubm9kZU5hbWVzVG9IZWFsdGhQaWxsczsKICAgICAgICAgICAgdmFyIGhlYWx0aFBpbGxTdGVwSW5kZXggPSB0aGlzLmhlYWx0aFBpbGxTdGVwSW5kZXg7CiAgICAgICAgICAgIHZhciBzZWxlY3RlZE5vZGUgPSB0aGlzLnNlbGVjdGVkTm9kZTsKICAgICAgICAgICAgdmFyIGFsbFN0ZXBzTW9kZUVuYWJsZWQgPSB0aGlzLmFsbFN0ZXBzTW9kZUVuYWJsZWQ7CiAgICAgICAgICAgIHZhciBhcmVIZWFsdGhQaWxsc0xvYWRpbmcgPSB0aGlzLmFyZUhlYWx0aFBpbGxzTG9hZGluZzsKICAgICAgICAgICAgaWYgKGFyZUhlYWx0aFBpbGxzTG9hZGluZykgewogICAgICAgICAgICAgICAgLy8gSGVhbHRoIHBpbGxzIGFyZSBsb2FkaW5nLiBEbyBub3QgcmVuZGVyIGRhdGEgdGhhdCBpcyBvdXQgb2YgZGF0ZS4KICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghc2VsZWN0ZWROb2RlKSB7CiAgICAgICAgICAgICAgICAvLyBObyBub2RlIGlzIHNlbGVjdGVkLgogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgaGVhbHRoUGlsbHMgPSBub2RlTmFtZXNUb0hlYWx0aFBpbGxzW3NlbGVjdGVkTm9kZV07CiAgICAgICAgICAgIGlmICghaGVhbHRoUGlsbHMpIHsKICAgICAgICAgICAgICAgIC8vIFRoaXMgbm9kZSBsYWNrcyBhIGhlYWx0aCBwaWxsLgogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gSWYgYWxsIHN0ZXBzIG1vZGUgaXMgZW5hYmxlZCwgd2UgdXNlIHRoZSBmaXJzdCBoZWFsdGggcGlsbCBpbiB0aGUgbGlzdCBiZWNhdXNlIHRoZSBKU09OCiAgICAgICAgICAgIC8vIHJlc3BvbnNlIGZyb20gdGhlIHNlcnZlciBpcyBhIG1hcHBpbmcgYmV0d2VlbiBub2RlIG5hbWUgYW5kIGEgbGlzdCBvZiAxIGhlYWx0aCBwaWxsLgogICAgICAgICAgICBjb25zdCBoZWFsdGhQaWxsID0gaGVhbHRoUGlsbHNbYWxsU3RlcHNNb2RlRW5hYmxlZCA/IDAgOiBoZWFsdGhQaWxsU3RlcEluZGV4XTsKICAgICAgICAgICAgaWYgKCFoZWFsdGhQaWxsKSB7CiAgICAgICAgICAgICAgICAvLyBUaGlzIG5vZGUgbGFja3MgYSBoZWFsdGggcGlsbCBhdCB0aGUgY3VycmVudCBzdGVwLgogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVGhlIGhlYWx0aCBwaWxsIGNvdW50IHZhbHVlcyBzdGFydCBhdCAyLiBFYWNoIGhlYWx0aCBwaWxsIGNvbnRhaW5zIDYgdmFsdWVzLgogICAgICAgICAgICByZXR1cm4gaGVhbHRoUGlsbC52YWx1ZS5zbGljZSgyLCA4KTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jdXJyZW50U3RlcERpc3BsYXlWYWx1ZSgpIHsKICAgICAgICAgICAgdmFyIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMgPSB0aGlzLm5vZGVOYW1lc1RvSGVhbHRoUGlsbHM7CiAgICAgICAgICAgIHZhciBoZWFsdGhQaWxsU3RlcEluZGV4ID0gdGhpcy5oZWFsdGhQaWxsU3RlcEluZGV4OwogICAgICAgICAgICB2YXIgYWxsU3RlcHNNb2RlRW5hYmxlZCA9IHRoaXMuYWxsU3RlcHNNb2RlRW5hYmxlZDsKICAgICAgICAgICAgdmFyIHNwZWNpZmljSGVhbHRoUGlsbFN0ZXAgPSB0aGlzLnNwZWNpZmljSGVhbHRoUGlsbFN0ZXA7CiAgICAgICAgICAgIHZhciBhcmVIZWFsdGhQaWxsc0xvYWRpbmcgPSB0aGlzLmFyZUhlYWx0aFBpbGxzTG9hZGluZzsKICAgICAgICAgICAgaWYgKGFsbFN0ZXBzTW9kZUVuYWJsZWQpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSB1c2VyIHNlZWtzIGhlYWx0aCBwaWxscyBmb3Igc3BlY2lmaWMgc3RlcCBmcm9tIHRoZSBzZXJ2ZXIuCiAgICAgICAgICAgICAgICByZXR1cm4gc3BlY2lmaWNIZWFsdGhQaWxsU3RlcC50b0ZpeGVkKDApOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChhcmVIZWFsdGhQaWxsc0xvYWRpbmcpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSBjdXJyZW50IHN0ZXAgaXMgdW5kZWZpbmVkLgogICAgICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZm9yIChsZXQgbm9kZU5hbWUgaW4gbm9kZU5hbWVzVG9IZWFsdGhQaWxscykgewogICAgICAgICAgICAgICAgLy8gQWxsIG5vZGVzIGhhdmUgdGhlIHNhbWUgbnVtYmVyIG9mIHN0ZXBzIHN0b3JlZCwgc28gb25seSBleGFtaW5lIDEgbm9kZS4gV2UgY2Fubm90CiAgICAgICAgICAgICAgICAvLyBkaXJlY3RseSBpbmRleCBpbnRvIHRoZSBub2RlTmFtZXNUb0hlYWx0aFBpbGxzIG9iamVjdCBiZWNhdXNlIHdlIGRvIG5vdCBoYXZlIGEga2V5LgogICAgICAgICAgICAgICAgLy8gSWYgYWxsIHN0ZXBzIG1vZGUgaXMgZW5hYmxlZCwgd2Ugb25seSBoYXZlIDEgc3RlcCB0byBzaG93LgogICAgICAgICAgICAgICAgcmV0dXJuIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHNbbm9kZU5hbWVdW2hlYWx0aFBpbGxTdGVwSW5kZXhdLnN0ZXAudG9GaXhlZCgwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBUaGUgY3VycmVudCBzdGVwIGNvdWxkIG5vdCBiZSBjb21wdXRlZC4KICAgICAgICAgICAgcmV0dXJuIDA7CiAgICAgICAgfQogICAgICAgIC8vIFRoZSBiaWdnZXN0IHN0ZXAgdmFsdWUgZXZlciBzZWVuLiBVc2VkIHRvIGRldGVybWluZSB3aGF0IHN0ZXBzIG9mIGhlYWx0aCBwaWxscyB0byBsZXQgdGhlCiAgICAgICAgLy8gdXNlciBmZXRjaCBpbiBhbGwgc3RlcHMgbW9kZS4KICAgICAgICBnZXQgX2JpZ2dlc3RTdGVwRXZlclNlZW4oKSB7CiAgICAgICAgICAgIHZhciBub2RlTmFtZXNUb0hlYWx0aFBpbGxzID0gdGhpcy5ub2RlTmFtZXNUb0hlYWx0aFBpbGxzOwogICAgICAgICAgICBmb3IgKGxldCBub2RlTmFtZSBpbiBub2RlTmFtZXNUb0hlYWx0aFBpbGxzKSB7CiAgICAgICAgICAgICAgICAvLyBBbGwgbm9kZXMgaGF2ZSB0aGUgc2FtZSBudW1iZXIgb2Ygc3RlcHMgc3RvcmVkLCBzbyBvbmx5IGV4YW1pbmUgMSBub2RlLgogICAgICAgICAgICAgICAgLy8gVGhlIGluZGV4IGlzIDEgbGVzcyB0aGFuIHRoZSBjb3VudC4gVGVuc29yYm9hcmQgYmFja2VuZCBsb2dpYyBndWFyYW50ZWVzIHRoYXQgdGhlIGxlbmd0aAogICAgICAgICAgICAgICAgLy8gb2YgdGhlIGFycmF5IHdpbGwgYmUgZ3JlYXRlciB0aGFuIDEuCiAgICAgICAgICAgICAgICB2YXIgaGVhbHRoUGlsbHMgPSBub2RlTmFtZXNUb0hlYWx0aFBpbGxzW25vZGVOYW1lXTsKICAgICAgICAgICAgICAgIHJldHVybiBNYXRoLm1heCh0aGlzLl9iaWdnZXN0U3RlcEV2ZXJTZWVuLCBoZWFsdGhQaWxsc1toZWFsdGhQaWxscy5sZW5ndGggLSAxXS5zdGVwKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBObyBzdGVwcyBzZWVuIHNvIGZhci4gRGVmYXVsdCB0byAwLgogICAgICAgICAgICByZXR1cm4gdGhpcy5fYmlnZ2VzdFN0ZXBFdmVyU2VlbiB8fCAwOwogICAgICAgIH0KICAgICAgICBnZXQgX21heFN0ZXBJbmRleCgpIHsKICAgICAgICAgICAgdmFyIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMgPSB0aGlzLm5vZGVOYW1lc1RvSGVhbHRoUGlsbHM7CiAgICAgICAgICAgIGZvciAobGV0IG5vZGVOYW1lIGluIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMpIHsKICAgICAgICAgICAgICAgIC8vIEFsbCBub2RlcyBoYXZlIHRoZSBzYW1lIG51bWJlciBvZiBzdGVwcyBzdG9yZWQsIHNvIG9ubHkgZXhhbWluZSAxIG5vZGUuCiAgICAgICAgICAgICAgICAvLyBUaGUgaW5kZXggaXMgMSBsZXNzIHRoYW4gdGhlIGNvdW50LiBUZW5zb3Jib2FyZCBiYWNrZW5kIGxvZ2ljIGd1YXJhbnRlZXMgdGhhdCB0aGUgbGVuZ3RoCiAgICAgICAgICAgICAgICAvLyBvZiB0aGUgYXJyYXkgd2lsbCBiZSBncmVhdGVyIHRoYW4gMS4KICAgICAgICAgICAgICAgIHJldHVybiBub2RlTmFtZXNUb0hlYWx0aFBpbGxzW25vZGVOYW1lXS5sZW5ndGggLSAxOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFJldHVybiBhIGZhbHN5IHZhbHVlLiBUaGUgc2xpZGVyIHNob3VsZCBiZSBoaWRkZW4uCiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgICAgICBfaGFzRGVidWdnZXJOdW1lcmljQWxlcnRzKGRlYnVnZ2VyTnVtZXJpY0FsZXJ0cykgewogICAgICAgICAgICByZXR1cm4gZGVidWdnZXJOdW1lcmljQWxlcnRzICYmIGRlYnVnZ2VyTnVtZXJpY0FsZXJ0cy5sZW5ndGg7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVBbGVydHNMaXN0KCkgewogICAgICAgICAgICB2YXIgZGVidWdnZXJOdW1lcmljQWxlcnRzID0gdGhpcy5kZWJ1Z2dlck51bWVyaWNBbGVydHM7CiAgICAgICAgICAgIHZhciBhbGVydEJvZHkgPSB0aGlzLiQkKCcjbnVtZXJpYy1hbGVydHMtYm9keScpOwogICAgICAgICAgICBpZiAoIWFsZXJ0Qm9keSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGFsZXJ0Qm9keS5pbm5lclRleHQgPSAnJzsKICAgICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCBkZWJ1Z2dlck51bWVyaWNBbGVydHMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIHZhciBhbGVydCA9IGRlYnVnZ2VyTnVtZXJpY0FsZXJ0c1tpXTsKICAgICAgICAgICAgICAgIHZhciB0YWJsZVJvdyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RyJyk7CiAgICAgICAgICAgICAgICB2YXIgdGltZXN0YW1wVGQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZCcpOwogICAgICAgICAgICAgICAgdGltZXN0YW1wVGQuaW5uZXJUZXh0ID0gY29tcHV0ZUh1bWFuRnJpZW5kbHlUaW1lKGFsZXJ0LmZpcnN0X3RpbWVzdGFtcCk7CiAgICAgICAgICAgICAgICB0aW1lc3RhbXBUZC5jbGFzc0xpc3QuYWRkKCdmaXJzdC1vZmZlbnNlLXRkJyk7CiAgICAgICAgICAgICAgICB0YWJsZVJvdy5hcHBlbmRDaGlsZCh0aW1lc3RhbXBUZCk7CiAgICAgICAgICAgICAgICB2YXIgdGVuc29yRGV2aWNlVGQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZCcpOwogICAgICAgICAgICAgICAgdGVuc29yRGV2aWNlVGQuY2xhc3NMaXN0LmFkZCgndGVuc29yLWRldmljZS10ZCcpOwogICAgICAgICAgICAgICAgdmFyIHRlbnNvclNlY3Rpb24gPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgICAgICAgICAgICAgIHRlbnNvclNlY3Rpb24uY2xhc3NMaXN0LmFkZCgndGVuc29yLXNlY3Rpb24td2l0aGluLXRhYmxlJyk7CiAgICAgICAgICAgICAgICB0ZW5zb3JTZWN0aW9uLmlubmVyVGV4dCA9IGFsZXJ0LnRlbnNvcl9uYW1lOwogICAgICAgICAgICAgICAgdGhpcy5fYWRkT3BFeHBhbnNpb25MaXN0ZW5lcih0ZW5zb3JTZWN0aW9uLCBhbGVydC50ZW5zb3JfbmFtZSk7CiAgICAgICAgICAgICAgICB0ZW5zb3JEZXZpY2VUZC5hcHBlbmRDaGlsZCh0ZW5zb3JTZWN0aW9uKTsKICAgICAgICAgICAgICAgIHZhciBkZXZpY2VTZWN0aW9uID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgICAgICAgICBkZXZpY2VTZWN0aW9uLmNsYXNzTGlzdC5hZGQoJ2RldmljZS1zZWN0aW9uLXdpdGhpbi10YWJsZScpOwogICAgICAgICAgICAgICAgZGV2aWNlU2VjdGlvbi5pbm5lclRleHQgPSAnKCcgKyBhbGVydC5kZXZpY2VfbmFtZSArICcpJzsKICAgICAgICAgICAgICAgIHRlbnNvckRldmljZVRkLmFwcGVuZENoaWxkKGRldmljZVNlY3Rpb24pOwogICAgICAgICAgICAgICAgdGFibGVSb3cuYXBwZW5kQ2hpbGQodGVuc29yRGV2aWNlVGQpOwogICAgICAgICAgICAgICAgdmFyIG1pbmlIZWFsdGhQaWxsID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgICAgICAgICBtaW5pSGVhbHRoUGlsbC5jbGFzc0xpc3QuYWRkKCdtaW5pLWhlYWx0aC1waWxsJyk7CiAgICAgICAgICAgICAgICB2YXIgbWluaUhlYWx0aFBpbGxUZCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RkJyk7CiAgICAgICAgICAgICAgICBtaW5pSGVhbHRoUGlsbFRkLmNsYXNzTGlzdC5hZGQoJ21pbmktaGVhbHRoLXBpbGwtdGQnKTsKICAgICAgICAgICAgICAgIG1pbmlIZWFsdGhQaWxsVGQuYXBwZW5kQ2hpbGQobWluaUhlYWx0aFBpbGwpOwogICAgICAgICAgICAgICAgdGFibGVSb3cuYXBwZW5kQ2hpbGQobWluaUhlYWx0aFBpbGxUZCk7CiAgICAgICAgICAgICAgICBpZiAoYWxlcnQubmVnX2luZl9ldmVudF9jb3VudCkgewogICAgICAgICAgICAgICAgICAgIHZhciBuZWdhdGl2ZUluZkNvdW50U2VjdGlvbiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpOwogICAgICAgICAgICAgICAgICAgIG5lZ2F0aXZlSW5mQ291bnRTZWN0aW9uLmNsYXNzTGlzdC5hZGQoJ25lZ2F0aXZlLWluZi1taW5pLWhlYWx0aC1waWxsLXNlY3Rpb24nKTsKICAgICAgICAgICAgICAgICAgICBuZWdhdGl2ZUluZkNvdW50U2VjdGlvbi5pbm5lclRleHQgPSBhbGVydC5uZWdfaW5mX2V2ZW50X2NvdW50OwogICAgICAgICAgICAgICAgICAgIG5lZ2F0aXZlSW5mQ291bnRTZWN0aW9uLnNldEF0dHJpYnV0ZSgndGl0bGUnLCBhbGVydC5uZWdfaW5mX2V2ZW50X2NvdW50ICsgJyBldmVudHMgd2l0aCAtXHUyMjFFJyk7CiAgICAgICAgICAgICAgICAgICAgbWluaUhlYWx0aFBpbGwuYXBwZW5kQ2hpbGQobmVnYXRpdmVJbmZDb3VudFNlY3Rpb24pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGFsZXJ0LnBvc19pbmZfZXZlbnRfY291bnQpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgcG9zaXRpdmVJbmZDb3VudFNlY3Rpb24gPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgICAgICAgICAgICAgICAgICBwb3NpdGl2ZUluZkNvdW50U2VjdGlvbi5jbGFzc0xpc3QuYWRkKCdwb3NpdGl2ZS1pbmYtbWluaS1oZWFsdGgtcGlsbC1zZWN0aW9uJyk7CiAgICAgICAgICAgICAgICAgICAgcG9zaXRpdmVJbmZDb3VudFNlY3Rpb24uaW5uZXJUZXh0ID0gYWxlcnQucG9zX2luZl9ldmVudF9jb3VudDsKICAgICAgICAgICAgICAgICAgICBwb3NpdGl2ZUluZkNvdW50U2VjdGlvbi5zZXRBdHRyaWJ1dGUoJ3RpdGxlJywgYWxlcnQucG9zX2luZl9ldmVudF9jb3VudCArICcgZXZlbnRzIHdpdGggK1x1MjIxRScpOwogICAgICAgICAgICAgICAgICAgIG1pbmlIZWFsdGhQaWxsLmFwcGVuZENoaWxkKHBvc2l0aXZlSW5mQ291bnRTZWN0aW9uKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChhbGVydC5uYW5fZXZlbnRfY291bnQpIHsKICAgICAgICAgICAgICAgICAgICB2YXIgbmFuQ291bnRTZWN0aW9uID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgICAgICAgICAgICAgbmFuQ291bnRTZWN0aW9uLmNsYXNzTGlzdC5hZGQoJ25hbi1taW5pLWhlYWx0aC1waWxsLXNlY3Rpb24nKTsKICAgICAgICAgICAgICAgICAgICBuYW5Db3VudFNlY3Rpb24uaW5uZXJUZXh0ID0gYWxlcnQubmFuX2V2ZW50X2NvdW50OwogICAgICAgICAgICAgICAgICAgIG5hbkNvdW50U2VjdGlvbi5zZXRBdHRyaWJ1dGUoJ3RpdGxlJywgYWxlcnQubmFuX2V2ZW50X2NvdW50ICsgJyBldmVudHMgd2l0aCBOYU4nKTsKICAgICAgICAgICAgICAgICAgICBtaW5pSGVhbHRoUGlsbC5hcHBlbmRDaGlsZChuYW5Db3VudFNlY3Rpb24pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZG9tKGFsZXJ0Qm9keSkuYXBwZW5kQ2hpbGQodGFibGVSb3cpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIEFkZHMgYSBsaXN0ZW5lciB0byBhbiBlbGVtZW50LCBzbyB0aGF0IHdoZW4gdGhhdCBlbGVtZW50IGlzIGNsaWNrZWQsIHRoZSB0ZW5zb3Igd2l0aAogICAgICAgIC8vIHRlbnNvck5hbWUgZXhwYW5kcy4KICAgICAgICBfYWRkT3BFeHBhbnNpb25MaXN0ZW5lcihjbGlja2FibGVFbGVtZW50LCB0ZW5zb3JOYW1lKSB7CiAgICAgICAgICAgIGNsaWNrYWJsZUVsZW1lbnQuYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCAoKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBXaGVuIHRoZSB1c2VyIGNsaWNrcyBvbiBhIHRlbnNvciBuYW1lLCBleHBhbmQgYWxsIG5vZGVzIHVudGlsIHRoZSB1c2VyIGNhbiBzZWUgdGhlCiAgICAgICAgICAgICAgICAvLyBhc3NvY2lhdGVkIG5vZGUuCiAgICAgICAgICAgICAgICB2YXIgbmFtZU9mTm9kZVRvU2VsZWN0ID0gZXhwYW5kVW50aWxOb2RlSXNTaG93bihkb2N1bWVudC5nZXRFbGVtZW50QnlJZCgnc2NlbmUnKSwgdGhpcy5yZW5kZXJIaWVyYXJjaHksIHRlbnNvck5hbWUpOwogICAgICAgICAgICAgICAgLy8gU3RvcmUgdGhlIGN1cnJlbnQgc2Nyb2xsIG9mIHRoZSBncmFwaCBpbmZvIGNhcmQuIE5vZGUgc2VsZWN0aW9uIGFsdGVycyB0aGF0IHNjcm9sbCwgYW5kCiAgICAgICAgICAgICAgICAvLyB3ZSByZXN0b3JlIHRoZSBzY3JvbGwgbGF0ZXIuCiAgICAgICAgICAgICAgICB2YXIgcHJldmlvdXNTY3JvbGxGcm9tQm90dG9tOwogICAgICAgICAgICAgICAgdmFyIGdyYXBoSW5mb0NhcmQgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCd0Zi1ncmFwaC1pbmZvI2dyYXBoLWluZm8nKTsKICAgICAgICAgICAgICAgIGlmIChncmFwaEluZm9DYXJkKSB7CiAgICAgICAgICAgICAgICAgICAgcHJldmlvdXNTY3JvbGxGcm9tQm90dG9tID0KICAgICAgICAgICAgICAgICAgICAgICAgZ3JhcGhJbmZvQ2FyZC5zY3JvbGxIZWlnaHQgLSBncmFwaEluZm9DYXJkLnNjcm9sbFRvcDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgc2VsZWN0ZWQgbm9kZSB3aXRoaW4gZ3JhcGggbG9naWMuCiAgICAgICAgICAgICAgICB2YXIgcHJldmlvdXNTZWxlY3RlZE5vZGUgPSB0aGlzLnNlbGVjdGVkTm9kZTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdzZWxlY3RlZE5vZGUnLCBuYW1lT2ZOb2RlVG9TZWxlY3QpOwogICAgICAgICAgICAgICAgLy8gU2Nyb2xsIHRoZSBncmFwaCBpbmZvIGNhcmQgYmFjayBkb3duIGlmIG5lY2Vzc2FyeSBzbyB0aGF0IHVzZXIgY2FuIHNlZSB0aGUgYWxlcnRzIHNlY3Rpb24KICAgICAgICAgICAgICAgIC8vIGFnYWluLiBTZWxlY3RpbmcgdGhlIG5vZGUgY2F1c2VzIHRoZSBpbmZvIGNhcmQgdG8gc2Nyb2xsIHRvIHRoZSB0b3AsIHdoaWNoIG1heSBtZWFuIHRoZQogICAgICAgICAgICAgICAgLy8gdXNlciBubyBsb25nZXIgc2VlcyB0aGUgbGlzdCBvZiBhbGVydHMuCiAgICAgICAgICAgICAgICB2YXIgc2Nyb2xsVG9PcmlnaW5hbExvY2F0aW9uID0gKCkgPT4gewogICAgICAgICAgICAgICAgICAgIGdyYXBoSW5mb0NhcmQuc2Nyb2xsVG9wID0KICAgICAgICAgICAgICAgICAgICAgICAgZ3JhcGhJbmZvQ2FyZC5zY3JvbGxIZWlnaHQgLSBwcmV2aW91c1Njcm9sbEZyb21Cb3R0b207CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgaWYgKGdyYXBoSW5mb0NhcmQpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIGNvbXBvbmVudCBpcyB1c2VkIHdpdGhpbiBhbiBpbmZvIGNhcmQuIFJlc3RvcmUgdGhlIG9yaWdpbmFsIHNjcm9sbC4KICAgICAgICAgICAgICAgICAgICBpZiAocHJldmlvdXNTZWxlY3RlZE5vZGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhlIGNhcmQgZm9yIHRoZSBzZWxlY3RlZCBub2RlIGhhcyBhbHJlYWR5IG9wZW5lZC4gSW1tZWRpYXRlbHkgcmVzdG9yZSB0aGUgc2Nyb2xsLgogICAgICAgICAgICAgICAgICAgICAgICBzY3JvbGxUb09yaWdpbmFsTG9jYXRpb24oKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIEdpdmUgc29tZSB0aW1lIGZvciB0aGUgRE9NIG9mIHRoZSBpbmZvIGNhcmQgdG8gYmUgY3JlYXRlZCBiZWZvcmUgc2Nyb2xsaW5nIGRvd24uCiAgICAgICAgICAgICAgICAgICAgICAgIHdpbmRvdy5zZXRUaW1lb3V0KHNjcm9sbFRvT3JpZ2luYWxMb2NhdGlvbiwgMjApOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgfTsKICAgIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBmb250LXNpemU6IDEycHg7CiAgICAgICAgbWFyZ2luOiAwOwogICAgICAgIHBhZGRpbmc6IDA7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KCiAgICAgIGgyIHsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICAgIHRleHQtYWxpZ246IGNlbnRlcjsKICAgICAgICBtYXJnaW46IDA7CiAgICAgIH0KCiAgICAgIC5oZWFsdGgtcGlsbC1sZWdlbmQgewogICAgICAgIHBhZGRpbmc6IDE1cHg7CiAgICAgIH0KCiAgICAgIC5oZWFsdGgtcGlsbC1sZWdlbmQgaDIgewogICAgICAgIHRleHQtYWxpZ246IGxlZnQ7CiAgICAgIH0KCiAgICAgIC5oZWFsdGgtcGlsbC1lbnRyeSB7CiAgICAgICAgbWFyZ2luOiAxMHB4IDEwcHggMTBweCAwOwogICAgICB9CgogICAgICAuaGVhbHRoLXBpbGwtZW50cnkgLmNvbG9yLXByZXZpZXcgewogICAgICAgIHdpZHRoOiAyNnB4OwogICAgICAgIGhlaWdodDogMjZweDsKICAgICAgICBib3JkZXItcmFkaXVzOiAzcHg7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIG1hcmdpbjogMCAxMHB4IDAgMDsKICAgICAgfQoKICAgICAgLmhlYWx0aC1waWxsLWVudHJ5IC5jb2xvci1sYWJlbCwKICAgICAgLmhlYWx0aC1waWxsLWVudHJ5IC50ZW5zb3ItY291bnQgewogICAgICAgIGNvbG9yOiAjNzc3OwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBoZWlnaHQ6IDI2cHg7CiAgICAgICAgZm9udC1zaXplOiAyMnB4OwogICAgICAgIGxpbmUtaGVpZ2h0OiAyNnB4OwogICAgICAgIHZlcnRpY2FsLWFsaWduOiB0b3A7CiAgICAgIH0KCiAgICAgIC5oZWFsdGgtcGlsbC1lbnRyeSAudGVuc29yLWNvdW50IHsKICAgICAgICBmbG9hdDogcmlnaHQ7CiAgICAgIH0KCiAgICAgICNoZWFsdGgtcGlsbC1zdGVwLXNsaWRlciB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgbWFyZ2luOiAwIDAgMCAtMTVweDsKICAgICAgICAvKiAzMSBjb21lcyBmcm9tIGFkZGluZyBhIHBhZGRpbmcgb2YgMTVweCBmcm9tIGJvdGggc2lkZXMgb2YgdGhlIHBhcGVyLXNsaWRlciwgc3VidHJhY3RpbmcKICAgKiAxcHggc28gdGhhdCB0aGUgc2xpZGVyIHdpZHRoIGFsaWducyB3aXRoIHRoZSBpbWFnZSAodGhlIGxhc3Qgc2xpZGVyIG1hcmtlciB0YWtlcyB1cCAxcHgpLAogICAqIGFuZCBhZGRpbmcgMnB4IHRvIGFjY291bnQgZm9yIGEgYm9yZGVyIG9mIDFweCBvbiBib3RoIHNpZGVzIG9mIHRoZSBpbWFnZS4gMzAgLSAxICsgMi4KICAgKiBBcHBhcmVudGx5LCB0aGUgcGFwZXItc2xpZGVyIGxhY2tzIGEgbWl4aW4gZm9yIHRob3NlIHBhZGRpbmcgdmFsdWVzLiAqLwogICAgICAgIHdpZHRoOiBjYWxjKDEwMCUgKyAzMXB4KTsKICAgICAgfQoKICAgICAgI2hlYWx0aC1waWxscy1sb2FkaW5nLXNwaW5uZXIgewogICAgICAgIHdpZHRoOiAyMHB4OwogICAgICAgIGhlaWdodDogMjBweDsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogdG9wOwogICAgICB9CgogICAgICAjaGVhbHRoLXBpbGwtc3RlcC1udW1iZXItaW5wdXQgewogICAgICAgIHRleHQtYWxpZ246IGNlbnRlcjsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogdG9wOwogICAgICB9CgogICAgICAjbnVtZXJpYy1hbGVydHMtdGFibGUtY29udGFpbmVyIHsKICAgICAgICBtYXgtaGVpZ2h0OiA0MDBweDsKICAgICAgICBvdmVyZmxvdy14OiBoaWRkZW47CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgfQoKICAgICAgI251bWVyaWMtYWxlcnRzLXRhYmxlIHsKICAgICAgICB0ZXh0LWFsaWduOiBsZWZ0OwogICAgICB9CgogICAgICAjbnVtZXJpYy1hbGVydHMtdGFibGUgdGQgewogICAgICAgIHZlcnRpY2FsLWFsaWduOiB0b3A7CiAgICAgIH0KCiAgICAgICNudW1lcmljLWFsZXJ0cy10YWJsZSAuZmlyc3Qtb2ZmZW5zZS10ZCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICB9CgogICAgICAuZmlyc3Qtb2ZmZW5zZS10ZCB7CiAgICAgICAgd2lkdGg6IDgwcHg7CiAgICAgIH0KCiAgICAgIC50ZW5zb3ItZGV2aWNlLXRkIHsKICAgICAgICBtYXgtd2lkdGg6IDE0MHB4OwogICAgICAgIHdvcmQtd3JhcDogYnJlYWstd29yZDsKICAgICAgfQoKICAgICAgLnRlbnNvci1zZWN0aW9uLXdpdGhpbi10YWJsZSB7CiAgICAgICAgY29sb3I6ICMyNjYyMzY7CiAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICAgIG9wYWNpdHk6IDAuODsKICAgICAgICB0ZXh0LWRlY29yYXRpb246IHVuZGVybGluZTsKICAgICAgfQoKICAgICAgLnRlbnNvci1zZWN0aW9uLXdpdGhpbi10YWJsZTpob3ZlciB7CiAgICAgICAgb3BhY2l0eTogMTsKICAgICAgfQoKICAgICAgLmRldmljZS1zZWN0aW9uLXdpdGhpbi10YWJsZSB7CiAgICAgICAgY29sb3I6ICM2NjY7CiAgICAgIH0KCiAgICAgIC5taW5pLWhlYWx0aC1waWxsIHsKICAgICAgICB3aWR0aDogMTMwcHg7CiAgICAgIH0KCiAgICAgIC5taW5pLWhlYWx0aC1waWxsID4gZGl2IHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgd2lkdGg6IDYwcHg7CiAgICAgICAgYm9yZGVyLXJhZGl1czogM3B4OwogICAgICB9CgogICAgICAjZXZlbnQtY291bnRzLXRoIHsKICAgICAgICBwYWRkaW5nOiAwIDAgMCAxMHB4OwogICAgICB9CgogICAgICAubmVnYXRpdmUtaW5mLW1pbmktaGVhbHRoLXBpbGwtc2VjdGlvbiB7CiAgICAgICAgYmFja2dyb3VuZDogcmdiKDI1NSwgMTQxLCAwKTsKICAgICAgICB3aWR0aDogMjBweDsKICAgICAgfQoKICAgICAgLnBvc2l0aXZlLWluZi1taW5pLWhlYWx0aC1waWxsLXNlY3Rpb24gewogICAgICAgIGJhY2tncm91bmQ6IHJnYigwLCA2MiwgMjEyKTsKICAgICAgICB3aWR0aDogMjBweDsKICAgICAgfQoKICAgICAgLm5hbi1taW5pLWhlYWx0aC1waWxsLXNlY3Rpb24gewogICAgICAgIGJhY2tncm91bmQ6IHJnYigyMDQsIDQ3LCA0NCk7CiAgICAgICAgd2lkdGg6IDIwcHg7CiAgICAgIH0KCiAgICAgIC5uZWdhdGl2ZS1pbmYtbWluaS1oZWFsdGgtcGlsbC1zZWN0aW9uLAogICAgICAucG9zaXRpdmUtaW5mLW1pbmktaGVhbHRoLXBpbGwtc2VjdGlvbiwKICAgICAgLm5hbi1taW5pLWhlYWx0aC1waWxsLXNlY3Rpb24gewogICAgICAgIGNvbG9yOiAjZmZmOwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgbGluZS1oZWlnaHQ6IDIwcHg7CiAgICAgICAgbWFyZ2luOiAwIDAgMCAxMHB4OwogICAgICAgIHRleHQtYWxpZ246IGNlbnRlcjsKICAgICAgfQoKICAgICAgLm5vLW51bWVyaWMtYWxlcnRzLW5vdGlmaWNhdGlvbiB7CiAgICAgICAgbWFyZ2luOiAwOwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPHBhcGVyLW1hdGVyaWFsIGVsZXZhdGlvbj0iMSIgY2xhc3M9ImNhcmQgaGVhbHRoLXBpbGwtbGVnZW5kIj4KICAgICAgPGRpdiBjbGFzcz0idGl0bGUiPgogICAgICAgIEVuYWJsZSBhbGwgKG5vdCBqdXN0IHNhbXBsZWQpIHN0ZXBzLiBSZXF1aXJlcyBzbG93IGRpc2sgcmVhZC4KICAgICAgPC9kaXY+CiAgICAgIDxwYXBlci10b2dnbGUtYnV0dG9uCiAgICAgICAgaWQ9ImVuYWJsZUFsbFN0ZXBzTW9kZVRvZ2dsZSIKICAgICAgICBjaGVja2VkPSJ7e2FsbFN0ZXBzTW9kZUVuYWJsZWR9fSIKICAgICAgPgogICAgICA8L3BhcGVyLXRvZ2dsZS1idXR0b24+CiAgICAgIDxoMj4KICAgICAgICBTdGVwIG9mIEhlYWx0aCBQaWxsczoKICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbYWxsU3RlcHNNb2RlRW5hYmxlZF1dIj4KICAgICAgICAgIDxpbnB1dAogICAgICAgICAgICB0eXBlPSJudW1iZXIiCiAgICAgICAgICAgIGlkPSJoZWFsdGgtcGlsbC1zdGVwLW51bWJlci1pbnB1dCIKICAgICAgICAgICAgbWluPSIwIgogICAgICAgICAgICBtYXg9IltbX2JpZ2dlc3RTdGVwRXZlclNlZW5dXSIKICAgICAgICAgICAgdmFsdWU9Int7c3BlY2lmaWNIZWFsdGhQaWxsU3RlcDo6aW5wdXR9fSIKICAgICAgICAgIC8+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbIWFsbFN0ZXBzTW9kZUVuYWJsZWRdXSI+CiAgICAgICAgICBbW19jdXJyZW50U3RlcERpc3BsYXlWYWx1ZV1dCiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8cGFwZXItc3Bpbm5lci1saXRlCiAgICAgICAgICBhY3RpdmUKICAgICAgICAgIGhpZGRlbiQ9IltbIWFyZUhlYWx0aFBpbGxzTG9hZGluZ11dIgogICAgICAgICAgaWQ9ImhlYWx0aC1waWxscy1sb2FkaW5nLXNwaW5uZXIiCiAgICAgICAgPjwvcGFwZXItc3Bpbm5lci1saXRlPgogICAgICA8L2gyPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbYWxsU3RlcHNNb2RlRW5hYmxlZF1dIj4KICAgICAgICA8cGFwZXItc2xpZGVyCiAgICAgICAgICBpZD0iaGVhbHRoLXBpbGwtc3RlcC1zbGlkZXIiCiAgICAgICAgICBpbW1lZGlhdGUtdmFsdWU9Int7c3BlY2lmaWNIZWFsdGhQaWxsU3RlcH19IgogICAgICAgICAgbWF4PSJbW19iaWdnZXN0U3RlcEV2ZXJTZWVuXV0iCiAgICAgICAgICBzbmFwcwogICAgICAgICAgc3RlcD0iMSIKICAgICAgICAgIHZhbHVlPSJ7e3NwZWNpZmljSGVhbHRoUGlsbFN0ZXB9fSIKICAgICAgICA+PC9wYXBlci1zbGlkZXI+CiAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shYWxsU3RlcHNNb2RlRW5hYmxlZF1dIj4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX21heFN0ZXBJbmRleF1dIj4KICAgICAgICAgIDxwYXBlci1zbGlkZXIKICAgICAgICAgICAgaWQ9ImhlYWx0aC1waWxsLXN0ZXAtc2xpZGVyIgogICAgICAgICAgICBpbW1lZGlhdGUtdmFsdWU9Int7aGVhbHRoUGlsbFN0ZXBJbmRleH19IgogICAgICAgICAgICBtYXg9IltbX21heFN0ZXBJbmRleF1dIgogICAgICAgICAgICBzbmFwcwogICAgICAgICAgICBzdGVwPSIxIgogICAgICAgICAgICB2YWx1ZT0ie3toZWFsdGhQaWxsU3RlcEluZGV4fX0iCiAgICAgICAgICA+PC9wYXBlci1zbGlkZXI+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPGgyPgogICAgICAgIEhlYWx0aCBQaWxsCiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW2hlYWx0aFBpbGxWYWx1ZXNGb3JTZWxlY3RlZE5vZGVdXSI+CiAgICAgICAgICBDb3VudHMgZm9yIFNlbGVjdGVkIE5vZGUKICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shaGVhbHRoUGlsbFZhbHVlc0ZvclNlbGVjdGVkTm9kZV1dIj4KICAgICAgICAgIExlZ2VuZAogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvaDI+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLXJlcGVhdCIgaXRlbXM9IltbaGVhbHRoUGlsbEVudHJpZXNdXSI+CiAgICAgICAgPGRpdiBjbGFzcz0iaGVhbHRoLXBpbGwtZW50cnkiPgogICAgICAgICAgPGRpdgogICAgICAgICAgICBjbGFzcz0iY29sb3ItcHJldmlldyIKICAgICAgICAgICAgc3R5bGU9ImJhY2tncm91bmQ6W1tpdGVtLmJhY2tncm91bmRfY29sb3JdXSIKICAgICAgICAgID48L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbG9yLWxhYmVsIj5bW2l0ZW0ubGFiZWxdXTwvZGl2PgogICAgICAgICAgPGRpdiBjbGFzcz0idGVuc29yLWNvdW50Ij4KICAgICAgICAgICAgW1tfY29tcHV0ZVRlbnNvckNvdW50U3RyaW5nKGhlYWx0aFBpbGxWYWx1ZXNGb3JTZWxlY3RlZE5vZGUsCiAgICAgICAgICAgIGluZGV4KV1dCiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L2Rpdj4KICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPGRpdiBoaWRkZW4kPSJbWyFfaGFzRGVidWdnZXJOdW1lcmljQWxlcnRzKGRlYnVnZ2VyTnVtZXJpY0FsZXJ0cyldXSI+CiAgICAgICAgPGgyIGlkPSJudW1lcmljLWFsZXJ0cy1oZWFkZXIiPk51bWVyaWMgQWxlcnRzPC9oMj4KICAgICAgICA8cD5BbGVydHMgYXJlIHNvcnRlZCBmcm9tIHRvcCB0byBib3R0b20gYnkgaW5jcmVhc2luZyB0aW1lc3RhbXAuPC9wPgogICAgICAgIDxkaXYgaWQ9Im51bWVyaWMtYWxlcnRzLXRhYmxlLWNvbnRhaW5lciI+CiAgICAgICAgICA8dGFibGUgaWQ9Im51bWVyaWMtYWxlcnRzLXRhYmxlIj4KICAgICAgICAgICAgPHRoZWFkPgogICAgICAgICAgICAgIDx0cj4KICAgICAgICAgICAgICAgIDx0aD5GaXJzdCBPZmZlbnNlPC90aD4KICAgICAgICAgICAgICAgIDx0aD5UZW5zb3IgKERldmljZSk8L3RoPgogICAgICAgICAgICAgICAgPHRoIGlkPSJldmVudC1jb3VudHMtdGgiPkV2ZW50IENvdW50czwvdGg+CiAgICAgICAgICAgICAgPC90cj4KICAgICAgICAgICAgPC90aGVhZD4KICAgICAgICAgICAgPHRib2R5IGlkPSJudW1lcmljLWFsZXJ0cy1ib2R5Ij48L3Rib2R5PgogICAgICAgICAgPC90YWJsZT4KICAgICAgICA8L2Rpdj4KICAgICAgPC9kaXY+CiAgICAgIDx0ZW1wbGF0ZQogICAgICAgIGlzPSJkb20taWYiCiAgICAgICAgaWY9IltbIV9oYXNEZWJ1Z2dlck51bWVyaWNBbGVydHMoZGVidWdnZXJOdW1lcmljQWxlcnRzKV1dIgogICAgICA+CiAgICAgICAgPHAgY2xhc3M9Im5vLW51bWVyaWMtYWxlcnRzLW5vdGlmaWNhdGlvbiI+CiAgICAgICAgICBObyBudW1lcmljIGFsZXJ0cyBzbyBmYXIuIFRoYXQgaXMgbGlrZWx5IGdvb2QuIEFsZXJ0cyBpbmRpY2F0ZSB0aGUKICAgICAgICAgIHByZXNlbmNlIG9mIE5hTiBvciAoKy8tKSBJbmZpbml0eSB2YWx1ZXMsIHdoaWNoIG1heSBiZSBjb25jZXJuaW5nLgogICAgICAgIDwvcD4KICAgICAgPC90ZW1wbGF0ZT4KICAgIDwvcGFwZXItbWF0ZXJpYWw+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERlYnVnZ2VyRGF0YUNhcmQucHJvdG90eXBlLCAicmVuZGVySGllcmFyY2h5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgImRlYnVnZ2VyTnVtZXJpY0FsZXJ0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgIm5vZGVOYW1lc1RvSGVhbHRoUGlsbHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgImhlYWx0aFBpbGxTdGVwSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgInNwZWNpZmljSGVhbHRoUGlsbFN0ZXAiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgInNlbGVjdGVkTm9kZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERlYnVnZ2VyRGF0YUNhcmQucHJvdG90eXBlLCAiaGlnaGxpZ2h0ZWROb2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGVidWdnZXJEYXRhQ2FyZC5wcm90b3R5cGUsICJzZWxlY3RlZE5vZGVJbmNsdWRlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgImFyZUhlYWx0aFBpbGxzTG9hZGluZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEFycmF5LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoRGVidWdnZXJEYXRhQ2FyZC5wcm90b3R5cGUsICJoZWFsdGhQaWxsRW50cmllcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgImFsbFN0ZXBzTW9kZUVuYWJsZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ25vZGVOYW1lc1RvSGVhbHRoUGlsbHMnLCAnaGVhbHRoUGlsbFN0ZXBJbmRleCcsICdzZWxlY3RlZE5vZGUnLCAnYWxsU3RlcHNNb2RlRW5hYmxlZCcsICdhcmVIZWFsdGhQaWxsc0xvYWRpbmcnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaERlYnVnZ2VyRGF0YUNhcmQucHJvdG90eXBlLCAiaGVhbHRoUGlsbFZhbHVlc0ZvclNlbGVjdGVkTm9kZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ25vZGVOYW1lc1RvSGVhbHRoUGlsbHMnLCAnaGVhbHRoUGlsbFN0ZXBJbmRleCcsICdhbGxTdGVwc01vZGVFbmFibGVkJywgJ3NwZWNpZmljSGVhbHRoUGlsbFN0ZXAnLCAnYXJlSGVhbHRoUGlsbHNMb2FkaW5nJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoRGVidWdnZXJEYXRhQ2FyZC5wcm90b3R5cGUsICJfY3VycmVudFN0ZXBEaXNwbGF5VmFsdWUiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdub2RlTmFtZXNUb0hlYWx0aFBpbGxzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoRGVidWdnZXJEYXRhQ2FyZC5wcm90b3R5cGUsICJfYmlnZ2VzdFN0ZXBFdmVyU2VlbiIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ25vZGVOYW1lc1RvSGVhbHRoUGlsbHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlciksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkLnByb3RvdHlwZSwgIl9tYXhTdGVwSW5kZXgiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ2RlYnVnZ2VyTnVtZXJpY0FsZXJ0cycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaERlYnVnZ2VyRGF0YUNhcmQucHJvdG90eXBlLCAiX3VwZGF0ZUFsZXJ0c0xpc3QiLCBudWxsKTsKICAgIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZ3JhcGgtZGVidWdnZXItZGF0YS1jYXJkJykKICAgIF0sIFRmR3JhcGhEZWJ1Z2dlckRhdGFDYXJkKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIHZhciBHcmFwaEljb25UeXBlOwogICAgKGZ1bmN0aW9uIChHcmFwaEljb25UeXBlKSB7CiAgICAgICAgR3JhcGhJY29uVHlwZVsiQ09OU1QiXSA9ICJDT05TVCI7CiAgICAgICAgR3JhcGhJY29uVHlwZVsiTUVUQSJdID0gIk1FVEEiOwogICAgICAgIEdyYXBoSWNvblR5cGVbIk9QIl0gPSAiT1AiOwogICAgICAgIEdyYXBoSWNvblR5cGVbIlNFUklFUyJdID0gIlNFUklFUyI7CiAgICAgICAgR3JhcGhJY29uVHlwZVsiU1VNTUFSWSJdID0gIlNVTU1BUlkiOwogICAgfSkoR3JhcGhJY29uVHlwZSB8fCAoR3JhcGhJY29uVHlwZSA9IHt9KSk7CiAgICBsZXQgVGZHcmFwaEljb24gPSBjbGFzcyBUZkdyYXBoSWNvbiBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLnZlcnRpY2FsID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuZmlsbE92ZXJyaWRlID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5zdHJva2VPdmVycmlkZSA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuaGVpZ2h0ID0gMjA7CiAgICAgICAgICAgIHRoaXMuZmFkZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgZ2V0U3ZnRGVmaW5hYmxlRWxlbWVudCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuJC5zdmdEZWZzOwogICAgICAgIH0KICAgICAgICBnZXQgX2ZpbGwoKSB7CiAgICAgICAgICAgIHZhciB0eXBlID0gdGhpcy50eXBlOwogICAgICAgICAgICB2YXIgZmlsbE92ZXJyaWRlID0gdGhpcy5maWxsT3ZlcnJpZGU7CiAgICAgICAgICAgIGlmIChmaWxsT3ZlcnJpZGUgIT0gbnVsbCkKICAgICAgICAgICAgICAgIHJldHVybiBmaWxsT3ZlcnJpZGU7CiAgICAgICAgICAgIHN3aXRjaCAodHlwZSkgewogICAgICAgICAgICAgICAgY2FzZSBHcmFwaEljb25UeXBlLk1FVEE6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIE1ldGFub2RlQ29sb3JzLkRFRkFVTFRfRklMTDsKICAgICAgICAgICAgICAgIGNhc2UgR3JhcGhJY29uVHlwZS5TRVJJRVM6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFNlcmllc05vZGVDb2xvcnMuREVGQVVMVF9GSUxMOwogICAgICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgICAgICByZXR1cm4gT3BOb2RlQ29sb3JzLkRFRkFVTFRfRklMTDsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBnZXQgX3N0cm9rZSgpIHsKICAgICAgICAgICAgdmFyIHR5cGUgPSB0aGlzLnR5cGU7CiAgICAgICAgICAgIHZhciBzdHJva2VPdmVycmlkZSA9IHRoaXMuc3Ryb2tlT3ZlcnJpZGU7CiAgICAgICAgICAgIGlmIChzdHJva2VPdmVycmlkZSAhPSBudWxsKQogICAgICAgICAgICAgICAgcmV0dXJuIHN0cm9rZU92ZXJyaWRlOwogICAgICAgICAgICBzd2l0Y2ggKHR5cGUpIHsKICAgICAgICAgICAgICAgIGNhc2UgR3JhcGhJY29uVHlwZS5NRVRBOgogICAgICAgICAgICAgICAgICAgIHJldHVybiBNZXRhbm9kZUNvbG9ycy5ERUZBVUxUX1NUUk9LRTsKICAgICAgICAgICAgICAgIGNhc2UgR3JhcGhJY29uVHlwZS5TRVJJRVM6CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIFNlcmllc05vZGVDb2xvcnMuREVGQVVMVF9TVFJPS0U7CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIHJldHVybiBPcE5vZGVDb2xvcnMuREVGQVVMVF9TVFJPS0U7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogVGVzdCB3aGV0aGVyIHRoZSBzcGVjaWZpZWQgbm9kZSdzIHR5cGUsIG9yIHRoZSBsaXRlcmFsIHR5cGUgc3RyaW5nLAogICAgICAgICAqIG1hdGNoIGEgcGFydGljdWxhciBvdGhlciB0eXBlLgogICAgICAgICAqLwogICAgICAgIF9pc1R5cGUodHlwZSwgdGFyZ2V0VHlwZSkgewogICAgICAgICAgICByZXR1cm4gdHlwZSA9PT0gdGFyZ2V0VHlwZTsKICAgICAgICB9CiAgICAgICAgX2ZhZGVkQ2xhc3MoZmFkZWQsIHNoYXBlKSB7CiAgICAgICAgICAgIHJldHVybiBmYWRlZCA/ICdmYWRlZC0nICsgc2hhcGUgOiAnJzsKICAgICAgICB9CiAgICB9OwogICAgVGZHcmFwaEljb24udGVtcGxhdGUgPSBodG1sIGAKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGZvbnQtc2l6ZTogMDsKICAgICAgfQoKICAgICAgLmZhZGVkLXJlY3QgewogICAgICAgIGZpbGw6IHVybCgjcmVjdEhhdGNoKTsKICAgICAgfQoKICAgICAgLmZhZGVkLWVsbGlwc2UgewogICAgICAgIGZpbGw6IHVybCgjZWxsaXBzZUhhdGNoKTsKICAgICAgfQoKICAgICAgLmZhZGVkLXJlY3QsCiAgICAgIC5mYWRlZC1lbGxpcHNlLAogICAgICAuZmFkZWQtc2VyaWVzIHsKICAgICAgICBzdHJva2U6IHZhcigtLXRiLWdyYXBoLWZhZGVkKSAhaW1wb3J0YW50OwogICAgICB9CiAgICAgICNyZWN0SGF0Y2ggbGluZSwKICAgICAgI2VsbGlwc2VIYXRjaCBsaW5lIHsKICAgICAgICBjb2xvcjogI2UwZDRiMyAhaW1wb3J0YW50OwogICAgICAgIGZpbGw6IHdoaXRlOwogICAgICAgIHN0cm9rZTogI2UwZDRiMyAhaW1wb3J0YW50OwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPCEtLSBTVkcgZm9yIGRlZmluaXRpb25zIC0tPgogICAgPHN2ZyBoZWlnaHQ9IjAiIHdpZHRoPSIwIiBpZD0ic3ZnRGVmcyI+CiAgICAgIDxkZWZzPgogICAgICAgIDwhLS0gSGF0Y2ggcGF0dGVybnMgZm9yIGZhZGVkIG91dCBub2Rlcy4gLS0+CiAgICAgICAgPHBhdHRlcm4KICAgICAgICAgIGlkPSJyZWN0SGF0Y2giCiAgICAgICAgICBwYXR0ZXJuVHJhbnNmb3JtPSJyb3RhdGUoNDUgMCAwKSIKICAgICAgICAgIHdpZHRoPSI1IgogICAgICAgICAgaGVpZ2h0PSI1IgogICAgICAgICAgcGF0dGVyblVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgICA+CiAgICAgICAgICA8bGluZSB4MT0iMCIgeTE9IjAiIHgyPSIwIiB5Mj0iNSIgc3R5bGU9InN0cm9rZS13aWR0aDogMSI+PC9saW5lPgogICAgICAgIDwvcGF0dGVybj4KICAgICAgICA8cGF0dGVybgogICAgICAgICAgaWQ9ImVsbGlwc2VIYXRjaCIKICAgICAgICAgIHBhdHRlcm5UcmFuc2Zvcm09InJvdGF0ZSg0NSAwIDApIgogICAgICAgICAgd2lkdGg9IjIiCiAgICAgICAgICBoZWlnaHQ9IjIiCiAgICAgICAgICBwYXR0ZXJuVW5pdHM9InVzZXJTcGFjZU9uVXNlIgogICAgICAgID4KICAgICAgICAgIDxsaW5lIHgxPSIwIiB5MT0iMCIgeDI9IjAiIHkyPSIyIiBzdHlsZT0ic3Ryb2tlLXdpZHRoOiAxIj48L2xpbmU+CiAgICAgICAgPC9wYXR0ZXJuPgogICAgICAgIDwhLS0gVGVtcGxhdGUgZm9yIGFuIE9wIG5vZGUgZWxsaXBzZS4gLS0+CiAgICAgICAgPGVsbGlwc2UKICAgICAgICAgIGlkPSJvcC1ub2RlLXN0YW1wIgogICAgICAgICAgcng9IjcuNSIKICAgICAgICAgIHJ5PSIzIgogICAgICAgICAgc3Ryb2tlPSJpbmhlcml0IgogICAgICAgICAgZmlsbD0iaW5oZXJpdCIKICAgICAgICA+PC9lbGxpcHNlPgogICAgICAgIDwhLS0gVGVtcGxhdGUgZm9yIGFuIE9wIG5vZGUgYW5ub3RhdGlvbiBlbGxpcHNlIChzbWFsbGVyKS4gLS0+CiAgICAgICAgPGVsbGlwc2UKICAgICAgICAgIGlkPSJvcC1ub2RlLWFubm90YXRpb24tc3RhbXAiCiAgICAgICAgICByeD0iNSIKICAgICAgICAgIHJ5PSIyIgogICAgICAgICAgc3Ryb2tlPSJpbmhlcml0IgogICAgICAgICAgZmlsbD0iaW5oZXJpdCIKICAgICAgICA+PC9lbGxpcHNlPgogICAgICAgIDwhLS0gVmVydGljYWxseSBzdGFja2VkIHNlcmllcyBvZiBPcCBub2RlcyB3aGVuIHVuZXhwYW5kZWQuIC0tPgogICAgICAgIDxnIGlkPSJvcC1zZXJpZXMtdmVydGljYWwtc3RhbXAiPgogICAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1zdGFtcCIgeD0iOCIgeT0iOSI+PC91c2U+CiAgICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIiB4PSI4IiB5PSI2Ij48L3VzZT4KICAgICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI29wLW5vZGUtc3RhbXAiIHg9IjgiIHk9IjMiPjwvdXNlPgogICAgICAgIDwvZz4KICAgICAgICA8ZyBpZD0ib3Atc2VyaWVzLWhvcml6b250YWwtc3RhbXAiPgogICAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1zdGFtcCIgeD0iMTYiIHk9IjQiPjwvdXNlPgogICAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1zdGFtcCIgeD0iMTIiIHk9IjQiPjwvdXNlPgogICAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1zdGFtcCIgeD0iOCIgeT0iNCI+PC91c2U+CiAgICAgICAgPC9nPgogICAgICAgIDxnCiAgICAgICAgICBpZD0ic3VtbWFyeS1pY29uIgogICAgICAgICAgZmlsbD0iIzg0ODQ4NCIKICAgICAgICAgIGhlaWdodD0iMTIiCiAgICAgICAgICB2aWV3Qm94PSIwIDAgMjQgMjQiCiAgICAgICAgICB3aWR0aD0iMTIiCiAgICAgICAgPgogICAgICAgICAgPHBhdGgKICAgICAgICAgICAgZD0iTTE5IDNINWMtMS4xIDAtMiAuOS0yIDJ2MTRjMCAxLjEuOSAyIDIgMmgxNGMxLjEgMCAyLS45IDItMlY1YzAtMS4xLS45LTItMi0yek05IDE3SDd2LTdoMnY3em00IDBoLTJWN2gydjEwem00IDBoLTJ2LTRoMnY0eiIKICAgICAgICAgID48L3BhdGg+CiAgICAgICAgPC9nPgogICAgICA8L2RlZnM+CiAgICA8L3N2Zz4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaXNUeXBlKHR5cGUsICdDT05TVCcpXV0iPgogICAgICA8c3ZnCiAgICAgICAgaGVpZ2h0JD0iW1toZWlnaHRdXSIKICAgICAgICBwcmVzZXJ2ZUFzcGVjdFJhdGlvPSJ4TWluWU1pZCBtZWV0IgogICAgICAgIHZpZXdCb3g9IjAgMCAxMCAxMCIKICAgICAgPgogICAgICAgIDxjaXJjbGUKICAgICAgICAgIGN4PSI1IgogICAgICAgICAgY3k9IjUiCiAgICAgICAgICByPSIzIgogICAgICAgICAgZmlsbCQ9IltbX2ZpbGxdXSIKICAgICAgICAgIHN0cm9rZSQ9IltbX3N0cm9rZV1dIgogICAgICAgID48L2NpcmNsZT4KICAgICAgPC9zdmc+CiAgICA8L3RlbXBsYXRlPgogICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19pc1R5cGUodHlwZSwgJ1NVTU1BUlknKV1dIj4KICAgICAgPHN2ZwogICAgICAgIHdpZHRoJD0iW1toZWlnaHRdXSIKICAgICAgICBoZWlnaHQkPSJbW2hlaWdodF1dIgogICAgICAgIHZpZXdCb3g9IjAgMCAyNCAyNCIKICAgICAgICBmaWxsPSIjODQ4NDg0IgogICAgICA+CiAgICAgICAgPHBhdGgKICAgICAgICAgIGQ9Ik0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnpNOSAxN0g3di03aDJ2N3ptNCAwaC0yVjdoMnYxMHptNCAwaC0ydi00aDJ2NHoiCiAgICAgICAgPjwvcGF0aD4KICAgICAgPC9zdmc+CiAgICA8L3RlbXBsYXRlPgogICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19pc1R5cGUodHlwZSwgJ09QJyldXSI+CiAgICAgIDxzdmcKICAgICAgICBoZWlnaHQkPSJbW2hlaWdodF1dIgogICAgICAgIHByZXNlcnZlQXNwZWN0UmF0aW89InhNaW5ZTWlkIG1lZXQiCiAgICAgICAgdmlld0JveD0iMCAwIDE2IDgiCiAgICAgID4KICAgICAgICA8dXNlCiAgICAgICAgICB4bWxuczp4bGluaz0iaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIKICAgICAgICAgIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIgogICAgICAgICAgZmlsbCQ9IltbX2ZpbGxdXSIKICAgICAgICAgIHN0cm9rZSQ9IltbX3N0cm9rZV1dIgogICAgICAgICAgY2xhc3MkPSJ7e19mYWRlZENsYXNzKGZhZGVkLCAnZWxsaXBzZScpfX0iCiAgICAgICAgICB4PSI4IgogICAgICAgICAgeT0iNCIKICAgICAgICA+PC91c2U+CiAgICAgIDwvc3ZnPgogICAgPC90ZW1wbGF0ZT4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaXNUeXBlKHR5cGUsICdNRVRBJyldXSI+CiAgICAgIDxzdmcKICAgICAgICBoZWlnaHQkPSJbW2hlaWdodF1dIgogICAgICAgIHByZXNlcnZlQXNwZWN0UmF0aW89InhNaW5ZTWlkIG1lZXQiCiAgICAgICAgdmlld0JveD0iMCAwIDM3IDE2IgogICAgICA+CiAgICAgICAgPHJlY3QKICAgICAgICAgIHg9IjEiCiAgICAgICAgICB5PSIxIgogICAgICAgICAgZmlsbCQ9IltbX2ZpbGxdXSIKICAgICAgICAgIHN0cm9rZSQ9IltbX3N0cm9rZV1dIgogICAgICAgICAgY2xhc3MkPSJ7e19mYWRlZENsYXNzKGZhZGVkLCAncmVjdCcpfX0iCiAgICAgICAgICBzdHJva2Utd2lkdGg9IjJweCIKICAgICAgICAgIGhlaWdodD0iMTQiCiAgICAgICAgICB3aWR0aD0iMzUiCiAgICAgICAgICByeD0iNSIKICAgICAgICAgIHJ5PSI1IgogICAgICAgID48L3JlY3Q+CiAgICAgIDwvc3ZnPgogICAgPC90ZW1wbGF0ZT4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaXNUeXBlKHR5cGUsICdTRVJJRVMnKV1dIj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW3ZlcnRpY2FsXV0iPgogICAgICAgIDxzdmcKICAgICAgICAgIGhlaWdodCQ9IltbaGVpZ2h0XV0iCiAgICAgICAgICBwcmVzZXJ2ZUFzcGVjdFJhdGlvPSJ4TWluWU1pZCBtZWV0IgogICAgICAgICAgdmlld0JveD0iMCAwIDE2IDE1IgogICAgICAgID4KICAgICAgICAgIDx1c2UKICAgICAgICAgICAgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiCiAgICAgICAgICAgIHhsaW5rOmhyZWY9IiNvcC1zZXJpZXMtdmVydGljYWwtc3RhbXAiCiAgICAgICAgICAgIGZpbGwkPSJbW19maWxsXV0iCiAgICAgICAgICAgIHN0cm9rZSQ9IltbX3N0cm9rZV1dIgogICAgICAgICAgICBjbGFzcyQ9Int7X2ZhZGVkQ2xhc3MoZmFkZWQsICdzZXJpZXMnKX19IgogICAgICAgICAgICB4PSIwIgogICAgICAgICAgICB5PSIyIgogICAgICAgICAgPjwvdXNlPgogICAgICAgIDwvc3ZnPgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbIXZlcnRpY2FsXV0iPgogICAgICAgIDxzdmcKICAgICAgICAgIGhlaWdodCQ9IltbaGVpZ2h0XV0iCiAgICAgICAgICBwcmVzZXJ2ZUFzcGVjdFJhdGlvPSJ4TWluWU1pZCBtZWV0IgogICAgICAgICAgdmlld0JveD0iMCAwIDI0IDEwIgogICAgICAgID4KICAgICAgICAgIDx1c2UKICAgICAgICAgICAgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiCiAgICAgICAgICAgIHhsaW5rOmhyZWY9IiNvcC1zZXJpZXMtaG9yaXpvbnRhbC1zdGFtcCIKICAgICAgICAgICAgZmlsbCQ9IltbX2ZpbGxdXSIKICAgICAgICAgICAgc3Ryb2tlJD0iW1tfc3Ryb2tlXV0iCiAgICAgICAgICAgIGNsYXNzJD0ie3tfZmFkZWRDbGFzcyhmYWRlZCwgJ3NlcmllcycpfX0iCiAgICAgICAgICAgIHg9IjAiCiAgICAgICAgICAgIHk9IjEiCiAgICAgICAgICA+PC91c2U+CiAgICAgICAgPC9zdmc+CiAgICAgIDwvdGVtcGxhdGU+CiAgICA8L3RlbXBsYXRlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhJY29uLnByb3RvdHlwZSwgInR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhJY29uLnByb3RvdHlwZSwgInZlcnRpY2FsIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaEljb24ucHJvdG90eXBlLCAiZmlsbE92ZXJyaWRlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaEljb24ucHJvdG90eXBlLCAic3Ryb2tlT3ZlcnJpZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoSWNvbi5wcm90b3R5cGUsICJoZWlnaHQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhJY29uLnByb3RvdHlwZSwgImZhZGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCd0eXBlJywgJ2ZpbGxPdmVycmlkZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaEljb24ucHJvdG90eXBlLCAiX2ZpbGwiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCd0eXBlJywgJ3N0cm9rZU92ZXJyaWRlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoSWNvbi5wcm90b3R5cGUsICJfc3Ryb2tlIiwgbnVsbCk7CiAgICBUZkdyYXBoSWNvbiA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWdyYXBoLWljb24nKQogICAgXSwgVGZHcmFwaEljb24pOwoKICAgIHZhciB0Zl9ncmFwaF9pY29uID0gLyojX19QVVJFX18qL09iamVjdC5mcmVlemUoewogICAgICAgIF9fcHJvdG9fXzogbnVsbCwKICAgICAgICBnZXQgR3JhcGhJY29uVHlwZSAoKSB7IHJldHVybiBHcmFwaEljb25UeXBlOyB9CiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgdG9wIGFuZCBsZWZ0IGRpc3RhbmNlIG9mIHRoZSBzY2VuZSBlbGVtZW50IGZyb20gdGhlIHRvcCBsZWZ0CiAgICAgKiBjb3JuZXIgb2YgdGhlIHNjcmVlbi4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0T2Zmc2V0KHNjZW5lRWxlbWVudCkgewogICAgICAgIGxldCBsZWZ0RGlzdGFuY2UgPSAwOwogICAgICAgIGxldCB0b3BEaXN0YW5jZSA9IDA7CiAgICAgICAgbGV0IGN1cnJlbnRFbGVtZW50ID0gc2NlbmVFbGVtZW50OwogICAgICAgIHdoaWxlIChjdXJyZW50RWxlbWVudCAmJgogICAgICAgICAgICBjdXJyZW50RWxlbWVudC5vZmZzZXRMZWZ0ID49IDAgJiYKICAgICAgICAgICAgY3VycmVudEVsZW1lbnQub2Zmc2V0VG9wID49IDApIHsKICAgICAgICAgICAgbGVmdERpc3RhbmNlICs9IGN1cnJlbnRFbGVtZW50Lm9mZnNldExlZnQgLSBjdXJyZW50RWxlbWVudC5zY3JvbGxMZWZ0OwogICAgICAgICAgICB0b3BEaXN0YW5jZSArPSBjdXJyZW50RWxlbWVudC5vZmZzZXRUb3AgLSBjdXJyZW50RWxlbWVudC5zY3JvbGxUb3A7CiAgICAgICAgICAgIGN1cnJlbnRFbGVtZW50ID0gY3VycmVudEVsZW1lbnQub2Zmc2V0UGFyZW50OwogICAgICAgIH0KICAgICAgICByZXR1cm4gewogICAgICAgICAgICBsZWZ0OiBsZWZ0RGlzdGFuY2UsCiAgICAgICAgICAgIHRvcDogdG9wRGlzdGFuY2UsCiAgICAgICAgfTsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgZXZlbnQgbGlzdGVuZXIsIHdoaWNoIGNhbiBiZSB1c2VkIGFzIGFuIGFyZ3VtZW50IGZvciB0aGUgZDMKICAgICAqIHNlbGVjdGlvbi5vbiBmdW5jdGlvbi4gUmVuZGVycyB0aGUgY29udGV4dCBtZW51IHRoYXQgaXMgdG8gYmUgZGlzcGxheWVkCiAgICAgKiBpbiByZXNwb25zZSB0byB0aGUgZXZlbnQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldE1lbnUoc2NlbmVFbGVtZW50LCBtZW51KSB7CiAgICAgICAgY29uc3QgbWVudU5vZGUgPSBzY2VuZUVsZW1lbnQuZ2V0Q29udGV4dE1lbnUoKTsKICAgICAgICBjb25zdCBtZW51U2VsZWN0aW9uID0gc2VsZWN0KHNjZW5lRWxlbWVudC5nZXRDb250ZXh0TWVudSgpKTsKICAgICAgICAvLyBGdW5jdGlvbiBjYWxsZWQgdG8gcG9wdWxhdGUgdGhlIGNvbnRleHQgbWVudS4KICAgICAgICByZXR1cm4gZnVuY3Rpb24gKGRhdGEsIGluZGV4KSB7CiAgICAgICAgICAgIC8vIFBvc2l0aW9uIGFuZCBkaXNwbGF5IHRoZSBtZW51LgogICAgICAgICAgICBsZXQgZXZlbnQkMSA9IGV2ZW50OwogICAgICAgICAgICBjb25zdCBzY2VuZU9mZnNldCA9IGdldE9mZnNldChzY2VuZUVsZW1lbnQpOwogICAgICAgICAgICBtZW51U2VsZWN0aW9uCiAgICAgICAgICAgICAgICAuc3R5bGUoJ2Rpc3BsYXknLCAnYmxvY2snKQogICAgICAgICAgICAgICAgLnN0eWxlKCdsZWZ0JywgZXZlbnQkMS5jbGllbnRYIC0gc2NlbmVPZmZzZXQubGVmdCArIDEgKyAncHgnKQogICAgICAgICAgICAgICAgLnN0eWxlKCd0b3AnLCBldmVudCQxLmNsaWVudFkgLSBzY2VuZU9mZnNldC50b3AgKyAxICsgJ3B4Jyk7CiAgICAgICAgICAgIC8vIFN0b3AgdGhlIGV2ZW50IGZyb20gcHJvcGFnYXRpbmcgZnVydGhlci4KICAgICAgICAgICAgZXZlbnQkMS5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgICAgICBldmVudCQxLnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgICAgICBmdW5jdGlvbiBtYXliZUNsb3NlTWVudShldmVudCkgewogICAgICAgICAgICAgICAgaWYgKGV2ZW50ICYmIGV2ZW50LmNvbXBvc2VkUGF0aCgpLmluY2x1ZGVzKG1lbnVOb2RlKSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIG1lbnVTZWxlY3Rpb24uc3R5bGUoJ2Rpc3BsYXknLCAnbm9uZScpOwogICAgICAgICAgICAgICAgZG9jdW1lbnQuYm9keS5yZW1vdmVFdmVudExpc3RlbmVyKCdtb3VzZWRvd24nLCBtYXliZUNsb3NlTWVudSwgewogICAgICAgICAgICAgICAgICAgIGNhcHR1cmU6IHRydWUsCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBEaXNtaXNzIGFuZCByZW1vdmUgdGhlIGNsaWNrIGxpc3RlbmVyIGFzIHNvb24gYXMgdGhlcmUgaXMgYSBtb3VzZWRvd24KICAgICAgICAgICAgLy8gb24gdGhlIGRvY3VtZW50LiBXZSB1c2UgY2FwdHVyZSBsaXN0ZW5lciBzbyBubyBjb21wb25lbnQgY2FuIHN0b3AKICAgICAgICAgICAgLy8gY29udGV4dCBtZW51IGZyb20gZGlzbWlzc2luZyBkdWUgdG8gc3RvcHBlZCBwcm9wYWdhdGlvbi4KICAgICAgICAgICAgZG9jdW1lbnQuYm9keS5hZGRFdmVudExpc3RlbmVyKCdtb3VzZWRvd24nLCBtYXliZUNsb3NlTWVudSwgewogICAgICAgICAgICAgICAgY2FwdHVyZTogdHJ1ZSwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIEFkZCBwcm92aWRlZCBpdGVtcyB0byB0aGUgY29udGV4dCBtZW51LgogICAgICAgICAgICBtZW51U2VsZWN0aW9uLmh0bWwoJycpOwogICAgICAgICAgICBsZXQgbGlzdCA9IG1lbnVTZWxlY3Rpb24uYXBwZW5kKCd1bCcpOwogICAgICAgICAgICBsaXN0CiAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCdsaScpCiAgICAgICAgICAgICAgICAuZGF0YShtZW51KQogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2xpJykKICAgICAgICAgICAgICAgIC5vbignY2xpY2snLCAoZCwgaSkgPT4gewogICAgICAgICAgICAgICAgZC5hY3Rpb24odGhpcywgZGF0YSwgaW5kZXgpOwogICAgICAgICAgICAgICAgbWF5YmVDbG9zZU1lbnUoKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5odG1sKGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZC50aXRsZShkYXRhKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKiBEZWxpbWl0ZXIgYmV0d2VlbiBkaW1lbnNpb25zIHdoZW4gc2hvd2luZyBzaXplcyBvZiB0ZW5zb3JzLiAqLwogICAgY29uc3QgVEVOU09SX1NIQVBFX0RFTElNID0gJ1x1MDBENyc7CiAgICBsZXQgYXJyb3doZWFkTWFwID0gcXVhbnRpemUkMSgpCiAgICAgICAgLmRvbWFpbihbTUlOX0VER0VfV0lEVEgsIE1BWF9FREdFX1dJRFRIXSkKICAgICAgICAucmFuZ2UoWydzbWFsbCcsICdtZWRpdW0nLCAnbGFyZ2UnLCAneGxhcmdlJ10pOwogICAgZnVuY3Rpb24gZ2V0RWRnZUtleShlZGdlT2JqKSB7CiAgICAgICAgcmV0dXJuIGVkZ2VPYmoudiArIEVER0VfS0VZX0RFTElNJDEgKyBlZGdlT2JqLnc7CiAgICB9CiAgICAvKioKICAgICAqIFNlbGVjdCBvciBDcmVhdGUgYSAnZy5lZGdlcycgZ3JvdXAgdG8gYSBnaXZlbiBzY2VuZUdyb3VwCiAgICAgKiBhbmQgYnVpbGRzIGEgbnVtYmVyIG9mICdnLmVkZ2UnIGdyb3VwcyBpbnNpZGUgdGhlIGdyb3VwLgogICAgICoKICAgICAqIFN0cnVjdHVyZSBQYXR0ZXJuOgogICAgICoKICAgICAqIDxnIGNsYXNzPSdlZGdlcyc+CiAgICAgKiAgIDxnIGNsYXNzPSdlZGdlJz4KICAgICAqICAgICA8cGF0aCBjbGFzcz0nZWRnZWxpbmUnLz4KICAgICAqICAgPC9nPgogICAgICogICAuLi4KICAgICAqIDwvZz4KICAgICAqCiAgICAgKgogICAgICogQHBhcmFtIHNjZW5lR3JvdXAgY29udGFpbmVyCiAgICAgKiBAcGFyYW0gZ3JhcGgKICAgICAqIEBwYXJhbSBzY2VuZUVsZW1lbnQgPHRmLWdyYXBoLXNjZW5lPiBwb2x5bWVyIGVsZW1lbnQuCiAgICAgKiBAcmV0dXJuIHNlbGVjdGlvbiBvZiB0aGUgY3JlYXRlZCBub2RlR3JvdXBzCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJ1aWxkR3JvdXAoc2NlbmVHcm91cCwgZ3JhcGgsIHNjZW5lRWxlbWVudCkgewogICAgICAgIGNvbnN0IHNjZW5lQ29tcG9uZW50ID0gc2NlbmVFbGVtZW50OwogICAgICAgIGxldCBlZGdlcyA9IFtdOwogICAgICAgIGVkZ2VzID0gbG9kYXNoLnJlZHVjZShncmFwaC5lZGdlcygpLCAoZWRnZXMsIGVkZ2VPYmopID0+IHsKICAgICAgICAgICAgbGV0IGVkZ2VMYWJlbCA9IGdyYXBoLmVkZ2UoZWRnZU9iaik7CiAgICAgICAgICAgIGVkZ2VzLnB1c2goewogICAgICAgICAgICAgICAgdjogZWRnZU9iai52LAogICAgICAgICAgICAgICAgdzogZWRnZU9iai53LAogICAgICAgICAgICAgICAgbGFiZWw6IGVkZ2VMYWJlbCwKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBlZGdlczsKICAgICAgICB9LCBlZGdlcyk7CiAgICAgICAgbGV0IGNvbnRhaW5lciA9IHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2NlbmVHcm91cCwgJ2cnLCBDbGFzcyQxLkVkZ2UuQ09OVEFJTkVSKTsKICAgICAgICAvLyBTZWxlY3QgYWxsIGNoaWxkcmVuIGFuZCBqb2luIHdpdGggZGF0YS4KICAgICAgICAvLyAoTm90ZSB0aGF0IGFsbCBjaGlsZHJlbiBvZiBnLmVkZ2VzIGFyZSBnLmVkZ2UpCiAgICAgICAgbGV0IGVkZ2VHcm91cHMgPSBjb250YWluZXIKICAgICAgICAgICAgLnNlbGVjdEFsbChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmNoaWxkTm9kZXM7CiAgICAgICAgfSkKICAgICAgICAgICAgLmRhdGEoZWRnZXMsIGdldEVkZ2VLZXkpOwogICAgICAgIC8vIE1ha2UgZWRnZXMgYSBncm91cCB0byBzdXBwb3J0IHJlbmRlcmluZyBtdWx0aXBsZSBsaW5lcyBmb3IgbWV0YWVkZ2UKICAgICAgICBlZGdlR3JvdXBzCiAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAuYXR0cignY2xhc3MnLCBDbGFzcyQxLkVkZ2UuR1JPVVApCiAgICAgICAgICAgIC5hdHRyKCdkYXRhLWVkZ2UnLCBnZXRFZGdlS2V5KQogICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoZCkgewogICAgICAgICAgICBsZXQgZWRnZUdyb3VwID0gc2VsZWN0KHRoaXMpOwogICAgICAgICAgICBkLmxhYmVsLmVkZ2VHcm91cCA9IGVkZ2VHcm91cDsKICAgICAgICAgICAgLy8gaW5kZXggbm9kZSBncm91cCBmb3IgcXVpY2sgaGlnaGxpZ2h0aW5nCiAgICAgICAgICAgIHNjZW5lQ29tcG9uZW50Ll9lZGdlR3JvdXBJbmRleFtnZXRFZGdlS2V5KGQpXSA9IGVkZ2VHcm91cDsKICAgICAgICAgICAgaWYgKHNjZW5lQ29tcG9uZW50LmhhbmRsZUVkZ2VTZWxlY3RlZCkgewogICAgICAgICAgICAgICAgLy8gVGhlIHVzZXIgb3Igc29tZSBoaWdoZXItbGV2ZWwgY29tcG9uZW50IGhhcyBvcHRlZCB0byBtYWtlIGVkZ2VzIHNlbGVjdGFibGUuCiAgICAgICAgICAgICAgICBlZGdlR3JvdXAub24oJ2NsaWNrJywgKGQpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBTdG9wIHRoaXMgZXZlbnQncyBwcm9wYWdhdGlvbiBzbyB0aGF0IGl0IGlzbid0IGFsc28gY29uc2lkZXJlZAogICAgICAgICAgICAgICAgICAgIC8vIGEgZ3JhcGgtc2VsZWN0LgogICAgICAgICAgICAgICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgICAgICAgICAgICAgIHNjZW5lQ29tcG9uZW50LmZpcmUoJ2VkZ2Utc2VsZWN0JywgewogICAgICAgICAgICAgICAgICAgICAgICBlZGdlRGF0YTogZCwKICAgICAgICAgICAgICAgICAgICAgICAgZWRnZUdyb3VwOiBlZGdlR3JvdXAsCiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBBZGQgbGluZSBkdXJpbmcgZW50ZXIgYmVjYXVzZSB3ZSdyZSBhc3N1bWluZyB0aGF0IHR5cGUgb2YgbGluZQogICAgICAgICAgICAvLyBub3JtYWxseSBkb2VzIG5vdCBjaGFuZ2UuCiAgICAgICAgICAgIGFwcGVuZEVkZ2UoZWRnZUdyb3VwLCBkLCBzY2VuZUNvbXBvbmVudCk7CiAgICAgICAgfSkKICAgICAgICAgICAgLm1lcmdlKGVkZ2VHcm91cHMpCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgcG9zaXRpb24kMihzY2VuZUVsZW1lbnQsIHRoaXMpOwogICAgICAgIH0pCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgIHN0eWxpemUoc2VsZWN0KHRoaXMpLCBkKTsKICAgICAgICB9KTsKICAgICAgICBlZGdlR3JvdXBzCiAgICAgICAgICAgIC5leGl0KCkKICAgICAgICAgICAgLmVhY2goKGQpID0+IHsKICAgICAgICAgICAgZGVsZXRlIHNjZW5lQ29tcG9uZW50Ll9lZGdlR3JvdXBJbmRleFtnZXRFZGdlS2V5KGQpXTsKICAgICAgICB9KQogICAgICAgICAgICAucmVtb3ZlKCk7CiAgICAgICAgcmV0dXJuIGVkZ2VHcm91cHM7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGxhYmVsIGZvciB0aGUgZ2l2ZW4gYmFzZSBlZGdlLgogICAgICogVGhlIGxhYmVsIGlzIHRoZSBzaGFwZSBvZiB0aGUgdW5kZXJseWluZyB0ZW5zb3IuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldExhYmVsRm9yQmFzZUVkZ2UoYmFzZUVkZ2UsIHJlbmRlckluZm8pIHsKICAgICAgICBsZXQgbm9kZSA9IHJlbmRlckluZm8uZ2V0Tm9kZUJ5TmFtZShiYXNlRWRnZS52KTsKICAgICAgICBpZiAobm9kZS5vdXRwdXRTaGFwZXMgPT0gbnVsbCB8fCBsb2Rhc2guaXNFbXB0eShub2RlLm91dHB1dFNoYXBlcykpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIGxldCBzaGFwZSA9IG5vZGUub3V0cHV0U2hhcGVzW2Jhc2VFZGdlLm91dHB1dFRlbnNvcktleV07CiAgICAgICAgaWYgKHNoYXBlID09IG51bGwpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIGlmIChzaGFwZS5sZW5ndGggPT09IDApIHsKICAgICAgICAgICAgcmV0dXJuICdzY2FsYXInOwogICAgICAgIH0KICAgICAgICByZXR1cm4gc2hhcGUKICAgICAgICAgICAgLm1hcCgoc2l6ZSkgPT4gewogICAgICAgICAgICByZXR1cm4gc2l6ZSA9PT0gLTEgPyAnPycgOiBzaXplOwogICAgICAgIH0pCiAgICAgICAgICAgIC5qb2luKFRFTlNPUl9TSEFQRV9ERUxJTSk7CiAgICB9CiAgICAvKioKICAgICAqIENyZWF0ZXMgdGhlIGxhYmVsIGZvciB0aGUgZ2l2ZW4gbWV0YWVkZ2UuIElmIHRoZSBtZXRhZWRnZSBjb25zaXN0cwogICAgICogb2Ygb25seSAxIHRlbnNvciwgYW5kIGl0J3Mgc2hhcGUgaXMga25vd24sIHRoZSBsYWJlbCB3aWxsIGNvbnRhaW4gdGhhdAogICAgICogc2hhcGUuIE90aGVyd2lzZSwgdGhlIGxhYmVsIHdpbGwgc2F5IHRoZSBudW1iZXIgb2YgdGVuc29ycyBpbiB0aGUgbWV0YWVkZ2UuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldExhYmVsRm9yRWRnZShtZXRhZWRnZSwgcmVuZGVySW5mbykgewogICAgICAgIGlmIChyZW5kZXJJbmZvLmVkZ2VMYWJlbEZ1bmN0aW9uKSB7CiAgICAgICAgICAgIC8vIFRoZSB1c2VyIGhhcyBzcGVjaWZpZWQgYSBtZWFucyBvZiBjb21wdXRpbmcgdGhlIGxhYmVsLgogICAgICAgICAgICByZXR1cm4gcmVuZGVySW5mby5lZGdlTGFiZWxGdW5jdGlvbihtZXRhZWRnZSwgcmVuZGVySW5mbyk7CiAgICAgICAgfQogICAgICAgIC8vIENvbXB1dGUgdGhlIGxhYmVsIGJhc2VkIG9uIGVpdGhlciB0ZW5zb3IgY291bnQgb3Igc2l6ZS4KICAgICAgICBsZXQgaXNNdWx0aUVkZ2UgPSBtZXRhZWRnZS5iYXNlRWRnZUxpc3QubGVuZ3RoID4gMTsKICAgICAgICByZXR1cm4gaXNNdWx0aUVkZ2UKICAgICAgICAgICAgPyBtZXRhZWRnZS5iYXNlRWRnZUxpc3QubGVuZ3RoICsgJyB0ZW5zb3JzJwogICAgICAgICAgICA6IGdldExhYmVsRm9yQmFzZUVkZ2UobWV0YWVkZ2UuYmFzZUVkZ2VMaXN0WzBdLCByZW5kZXJJbmZvKTsKICAgIH0KICAgIC8qKgogICAgICogQ29tcHV0ZXMgdGhlIGluZGV4IGludG8gYSBzZXQgb2YgcG9pbnRzIHRoYXQgY29uc3RpdHV0ZSBhIHBhdGggZm9yIHdoaWNoIHRoZQogICAgICogZGlzdGFuY2UgYWxvbmcgdGhlIHBhdGggZnJvbSB0aGUgaW5pdGlhbCBwb2ludCBpcyBhcyBsYXJnZSBhcyBwb3NzaWJsZQogICAgICogd2l0aG91dCBleGNlZWRpbmcgdGhlIGxlbmd0aC4gVGhpcyBmdW5jdGlvbiB3YXMgaW50cm9kdWNlZCBhZnRlciB0aGUKICAgICAqIG5hdGl2ZSBnZXRQYXRoU2VnQXRMZW5ndGggbWV0aG9kIGdvdCBkZXByZWNhdGVkIGJ5IFNWRyAyLgogICAgICogQHBhcmFtIHBvaW50cyBBcnJheSBvZiBwYXRoIGNvbnRyb2wgcG9pbnRzLiBBIHBvaW50IGhhcyB4IGFuZCB5IHByb3BlcnRpZXMuCiAgICAgKiAgIE11c3QgYmUgb2YgbGVuZ3RoIGF0IGxlYXN0IDIuCiAgICAgKiBAcGFyYW0gbGVuZ3RoIFRoZSBsZW5ndGggKGZsb2F0KS4KICAgICAqIEBwYXJhbSBsaW5lRnVuYyBBIGZ1bmN0aW9uIHRoYXQgdGFrZXMgcG9pbnRzIGFuZCByZXR1cm5zIHRoZSAiZCIgYXR0cmlidXRlCiAgICAgKiAgIG9mIGEgcGF0aCBtYWRlIGZyb20gY29ubmVjdGluZyB0aGUgcG9pbnRzLgogICAgICogQHJldHVybiBUaGUgaW5kZXggaW50byB0aGUgcG9pbnRzIGFycmF5LgogICAgICovCiAgICBmdW5jdGlvbiBnZXRQYXRoU2VnbWVudEluZGV4QXRMZW5ndGgocG9pbnRzLCBsZW5ndGgsIGxpbmVGdW5jKSB7CiAgICAgICAgY29uc3QgcGF0aCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUyhTVkdfTkFNRVNQQUNFLCAncGF0aCcpOwogICAgICAgIGZvciAobGV0IGkgPSAxOyBpIDwgcG9pbnRzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIHBhdGguc2V0QXR0cmlidXRlKCdkJywgbGluZUZ1bmMocG9pbnRzLnNsaWNlKDAsIGkpKSk7CiAgICAgICAgICAgIGlmIChwYXRoLmdldFRvdGFsTGVuZ3RoKCkgPiBsZW5ndGgpIHsKICAgICAgICAgICAgICAgIC8vIFRoaXMgbWFueSBwb2ludHMgaGFzIGFscmVhZHkgZXhjZWVkZWQgdGhlIGxlbmd0aC4KICAgICAgICAgICAgICAgIHJldHVybiBpIC0gMTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvLyBUaGUgZW50aXJlIHBhdGggaXMgc2hvcnRlciB0aGFuIHRoZSBzcGVjaWZpZWQgbGVuZ3RoLgogICAgICAgIHJldHVybiBwb2ludHMubGVuZ3RoIC0gMTsKICAgIH0KICAgIC8qKgogICAgICogU2hvcnRlbnMgdGhlIHBhdGggZW5vdWdodCBzdWNoIHRoYXQgdGhlIHRpcCBvZiB0aGUgc3RhcnQvZW5kIG1hcmtlciB3aWxsCiAgICAgKiBwb2ludCB0byB0aGUgc3RhcnQvZW5kIG9mIHRoZSBwYXRoLiBUaGUgbWFya2VyIGNhbiBiZSBvZiBhcmJpdHJhcnkgc2l6ZS4KICAgICAqCiAgICAgKiBAcGFyYW0gcG9pbnRzIEFycmF5IG9mIHBhdGggY29udHJvbCBwb2ludHMuCiAgICAgKiBAcGFyYW0gbWFya2VyIEQzIHNlbGVjdGlvbiBvZiB0aGUgPG1hcmtlcj4gc3ZnIGVsZW1lbnQuCiAgICAgKiBAcGFyYW0gaXNTdGFydCBJcyB0aGUgbWFya2VyIGEgYHN0YXJ0LW1hcmtlcmAuIElmIGZhbHNlLCB0aGUgbWFya2VyIGlzCiAgICAgKiAgICAgYW4gYGVuZC1tYXJrZXJgLgogICAgICogQHJldHVybiBUaGUgbmV3IGFycmF5IG9mIGNvbnRyb2wgcG9pbnRzLgogICAgICovCiAgICBmdW5jdGlvbiBhZGp1c3RQYXRoUG9pbnRzRm9yTWFya2VyKHBvaW50cywgbWFya2VyLCBpc1N0YXJ0KSB7CiAgICAgICAgbGV0IGxpbmVGdW5jID0gbGluZSgpCiAgICAgICAgICAgIC54KChkKSA9PiBkLngpCiAgICAgICAgICAgIC55KChkKSA9PiBkLnkpOwogICAgICAgIGxldCBwYXRoID0gc2VsZWN0KGRvY3VtZW50LmNyZWF0ZUVsZW1lbnROUygnaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnLCAncGF0aCcpKQogICAgICAgICAgICAuYXR0cignZCcsIGxpbmVGdW5jKHBvaW50cykpOwogICAgICAgIGxldCBtYXJrZXJXaWR0aCA9ICttYXJrZXIuYXR0cignbWFya2VyV2lkdGgnKTsKICAgICAgICBsZXQgdmlld0JveCA9IG1hcmtlci5hdHRyKCd2aWV3Qm94Jykuc3BsaXQoJyAnKS5tYXAoTnVtYmVyKTsKICAgICAgICBsZXQgdmlld0JveFdpZHRoID0gdmlld0JveFsyXSAtIHZpZXdCb3hbMF07CiAgICAgICAgbGV0IHJlZlggPSArbWFya2VyLmF0dHIoJ3JlZlgnKTsKICAgICAgICBsZXQgcGF0aE5vZGUgPSBwYXRoLm5vZGUoKTsKICAgICAgICBpZiAoaXNTdGFydCkgewogICAgICAgICAgICAvLyBUaGUgZWRnZSBmbG93cyBkb3dud2FyZHMuIERvIG5vdCBtYWtlIHRoZSBlZGdlIGdvIHRoZSB3aG9sZSB3YXksIGxlc3Qgd2UKICAgICAgICAgICAgLy8gY2xvYmJlciB0aGUgYXJyb3doZWFkLgogICAgICAgICAgICBjb25zdCBmcmFjdGlvblN0aWNraW5nT3V0ID0gMSAtIHJlZlggLyB2aWV3Qm94V2lkdGg7CiAgICAgICAgICAgIGNvbnN0IGxlbmd0aCA9IG1hcmtlcldpZHRoICogZnJhY3Rpb25TdGlja2luZ091dDsKICAgICAgICAgICAgY29uc3QgcG9pbnQgPSBwYXRoTm9kZS5nZXRQb2ludEF0TGVuZ3RoKGxlbmd0aCk7CiAgICAgICAgICAgIC8vIEZpZ3VyZSBvdXQgaG93IG1hbnkgc2VnbWVudHMgb2YgdGhlIHBhdGggd2UgbmVlZCB0byByZW1vdmUgaW4gb3JkZXIKICAgICAgICAgICAgLy8gdG8gc2hvcnRlbiB0aGUgcGF0aC4KICAgICAgICAgICAgY29uc3Qgc2VnSW5kZXggPSBnZXRQYXRoU2VnbWVudEluZGV4QXRMZW5ndGgocG9pbnRzLCBsZW5ndGgsIGxpbmVGdW5jKTsKICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSB2ZXJ5IGZpcnN0IHNlZ21lbnQuCiAgICAgICAgICAgIHBvaW50c1tzZWdJbmRleCAtIDFdID0geyB4OiBwb2ludC54LCB5OiBwb2ludC55IH07CiAgICAgICAgICAgIC8vIElnbm9yZSBldmVyeSBwb2ludCBiZWZvcmUgc2VnSW5kZXggLSAxLgogICAgICAgICAgICByZXR1cm4gcG9pbnRzLnNsaWNlKHNlZ0luZGV4IC0gMSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICAvLyBUaGUgZWRnZSBmbG93cyB1cHdhcmRzLiBEbyBub3QgbWFrZSB0aGUgZWRnZSBnbyB0aGUgd2hvbGUgd2F5LCBsZXN0IHdlCiAgICAgICAgICAgIC8vIGNsb2JiZXIgdGhlIGFycm93aGVhZC4KICAgICAgICAgICAgY29uc3QgZnJhY3Rpb25TdGlja2luZ091dCA9IDEgLSByZWZYIC8gdmlld0JveFdpZHRoOwogICAgICAgICAgICBjb25zdCBsZW5ndGggPSBwYXRoTm9kZS5nZXRUb3RhbExlbmd0aCgpIC0gbWFya2VyV2lkdGggKiBmcmFjdGlvblN0aWNraW5nT3V0OwogICAgICAgICAgICBjb25zdCBwb2ludCA9IHBhdGhOb2RlLmdldFBvaW50QXRMZW5ndGgobGVuZ3RoKTsKICAgICAgICAgICAgLy8gRmlndXJlIG91dCBob3cgbWFueSBzZWdtZW50cyBvZiB0aGUgcGF0aCB3ZSBuZWVkIHRvIHJlbW92ZSBpbiBvcmRlcgogICAgICAgICAgICAvLyB0byBzaG9ydGVuIHRoZSBwYXRoLgogICAgICAgICAgICBjb25zdCBzZWdJbmRleCA9IGdldFBhdGhTZWdtZW50SW5kZXhBdExlbmd0aChwb2ludHMsIGxlbmd0aCwgbGluZUZ1bmMpOwogICAgICAgICAgICAvLyBVcGRhdGUgdGhlIHZlcnkgbGFzdCBzZWdtZW50LgogICAgICAgICAgICBwb2ludHNbc2VnSW5kZXhdID0geyB4OiBwb2ludC54LCB5OiBwb2ludC55IH07CiAgICAgICAgICAgIC8vIElnbm9yZSBldmVyeSBwb2ludCBhZnRlciBzZWdJbmRleC4KICAgICAgICAgICAgcmV0dXJuIHBvaW50cy5zbGljZSgwLCBzZWdJbmRleCArIDEpOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogRm9yIGEgZ2l2ZW4gZDMgc2VsZWN0aW9uIGFuZCBkYXRhIG9iamVjdCwgY3JlYXRlIGEgcGF0aCB0byByZXByZXNlbnQgdGhlCiAgICAgKiBlZGdlIGRlc2NyaWJlZCBpbiBkLmxhYmVsLgogICAgICoKICAgICAqIElmIGQubGFiZWwgaXMgZGVmaW5lZCwgaXQgd2lsbCBiZSBhIFJlbmRlck1ldGFlZGdlSW5mbyBpbnN0YW5jZS4gSXQKICAgICAqIHdpbGwgc29tZXRpbWVzIGJlIHVuZGVmaW5lZCwgZm9yIGV4YW1wbGUgZm9yIHNvbWUgQW5ub3RhdGlvbiBlZGdlcyBmb3Igd2hpY2gKICAgICAqIHRoZXJlIGlzIG5vIHVuZGVybHlpbmcgTWV0YWVkZ2UgaW4gdGhlIGhpZXJhcmNoaWNhbCBncmFwaC4KICAgICAqLwogICAgZnVuY3Rpb24gYXBwZW5kRWRnZShlZGdlR3JvdXAsIGQsIHNjZW5lRWxlbWVudCwgZWRnZUNsYXNzKSB7CiAgICAgICAgZWRnZUNsYXNzID0gZWRnZUNsYXNzIHx8IENsYXNzJDEuRWRnZS5MSU5FOyAvLyBzZXQgZGVmYXVsdCB0eXBlCiAgICAgICAgaWYgKGQubGFiZWwgJiYgZC5sYWJlbC5zdHJ1Y3R1cmFsKSB7CiAgICAgICAgICAgIGVkZ2VDbGFzcyArPSAnICcgKyBDbGFzcyQxLkVkZ2UuU1RSVUNUVVJBTDsKICAgICAgICB9CiAgICAgICAgaWYgKGQubGFiZWwgJiYgZC5sYWJlbC5tZXRhZWRnZSAmJiBkLmxhYmVsLm1ldGFlZGdlLm51bVJlZkVkZ2VzKSB7CiAgICAgICAgICAgIGVkZ2VDbGFzcyArPSAnICcgKyBDbGFzcyQxLkVkZ2UuUkVGRVJFTkNFX0VER0U7CiAgICAgICAgfQogICAgICAgIGlmIChzY2VuZUVsZW1lbnQuaGFuZGxlRWRnZVNlbGVjdGVkKSB7CiAgICAgICAgICAgIC8vIFRoZSB1c2VyIGhhcyBvcHRlZCB0byBtYWtlIGVkZ2VzIHNlbGVjdGFibGUuCiAgICAgICAgICAgIGVkZ2VDbGFzcyArPSAnICcgKyBDbGFzcyQxLkVkZ2UuU0VMRUNUQUJMRTsKICAgICAgICB9CiAgICAgICAgLy8gR2l2ZSB0aGUgcGF0aCBhIHVuaXF1ZSBpZCwgd2hpY2ggd2lsbCBiZSB1c2VkIHRvIGxpbmsKICAgICAgICAvLyB0aGUgdGV4dFBhdGggKGVkZ2UgbGFiZWwpIHRvIHRoaXMgcGF0aC4KICAgICAgICBsZXQgcGF0aElkID0gJ3BhdGhfJyArIGdldEVkZ2VLZXkoZCk7CiAgICAgICAgbGV0IHN0cm9rZVdpZHRoOwogICAgICAgIGlmIChzY2VuZUVsZW1lbnQucmVuZGVySGllcmFyY2h5LmVkZ2VXaWR0aEZ1bmN0aW9uKSB7CiAgICAgICAgICAgIC8vIENvbXB1dGUgZWRnZSB0aGlja25lc3MgYmFzZWQgb24gdGhlIHVzZXItc3BlY2lmaWVkIG1ldGhvZC4KICAgICAgICAgICAgc3Ryb2tlV2lkdGggPSBzY2VuZUVsZW1lbnQucmVuZGVySGllcmFyY2h5LmVkZ2VXaWR0aEZ1bmN0aW9uKGQsIGVkZ2VDbGFzcyk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICAvLyBFbmNvZGUgdGVuc29yIHNpemUgd2l0aGluIGVkZ2UgdGhpY2tuZXNzLgogICAgICAgICAgICBsZXQgc2l6ZSA9IDE7CiAgICAgICAgICAgIGlmIChkLmxhYmVsICE9IG51bGwgJiYgZC5sYWJlbC5tZXRhZWRnZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBUaGVyZSBpcyBhbiB1bmRlcmx5aW5nIE1ldGFlZGdlLgogICAgICAgICAgICAgICAgc2l6ZSA9IGQubGFiZWwubWV0YWVkZ2UudG90YWxTaXplOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHN0cm9rZVdpZHRoID0gc2NlbmVFbGVtZW50LnJlbmRlckhpZXJhcmNoeS5lZGdlV2lkdGhTaXplZEJhc2VkU2NhbGUoc2l6ZSk7CiAgICAgICAgfQogICAgICAgIGxldCBwYXRoID0gZWRnZUdyb3VwCiAgICAgICAgICAgIC5hcHBlbmQoJ3BhdGgnKQogICAgICAgICAgICAuYXR0cignaWQnLCBwYXRoSWQpCiAgICAgICAgICAgIC5hdHRyKCdjbGFzcycsIGVkZ2VDbGFzcykKICAgICAgICAgICAgLnN0eWxlKCdzdHJva2Utd2lkdGgnLCBzdHJva2VXaWR0aCArICdweCcpOwogICAgICAgIC8vIENoZWNrIGlmIHRoZXJlIGlzIGEgcmVmZXJlbmNlIGVkZ2UgYW5kIGFkZCBhbiBhcnJvd2hlYWQgb2YgdGhlIHJpZ2h0IHNpemUuCiAgICAgICAgaWYgKGQubGFiZWwgJiYgZC5sYWJlbC5tZXRhZWRnZSkgewogICAgICAgICAgICBpZiAoZC5sYWJlbC5tZXRhZWRnZS5udW1SZWZFZGdlcykgewogICAgICAgICAgICAgICAgLy8gV2UgaGF2ZSBhIHJlZmVyZW5jZSBlZGdlLgogICAgICAgICAgICAgICAgY29uc3QgbWFya2VySWQgPSBgcmVmZXJlbmNlLWFycm93aGVhZC0ke2Fycm93aGVhZE1hcChzdHJva2VXaWR0aCl9YDsKICAgICAgICAgICAgICAgIHBhdGguc3R5bGUoJ21hcmtlci1zdGFydCcsIGB1cmwoIyR7bWFya2VySWR9KWApOwogICAgICAgICAgICAgICAgZC5sYWJlbC5zdGFydE1hcmtlcklkID0gbWFya2VySWQ7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAvLyBXZSBoYXZlIGEgZGF0YWZsb3cgZWRnZS4KICAgICAgICAgICAgICAgIGNvbnN0IG1hcmtlcklkID0gYGRhdGFmbG93LWFycm93aGVhZC0ke2Fycm93aGVhZE1hcChzdHJva2VXaWR0aCl9YDsKICAgICAgICAgICAgICAgIHBhdGguc3R5bGUoJ21hcmtlci1lbmQnLCBgdXJsKCMke21hcmtlcklkfSlgKTsKICAgICAgICAgICAgICAgIGQubGFiZWwuZW5kTWFya2VySWQgPSBtYXJrZXJJZDsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoZC5sYWJlbCA9PSBudWxsIHx8IGQubGFiZWwubWV0YWVkZ2UgPT0gbnVsbCkgewogICAgICAgICAgICAvLyBUaGVyZSBpcyBubyBhc3NvY2lhdGVkIG1ldGFlZGdlLCB0aHVzIG5vIHRleHQuCiAgICAgICAgICAgIC8vIFRoaXMgaGFwcGVucyBmb3IgYW5ub3RhdGlvbiBlZGdlcy4KICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBsZXQgbGFiZWxGb3JFZGdlID0gZ2V0TGFiZWxGb3JFZGdlKGQubGFiZWwubWV0YWVkZ2UsIHNjZW5lRWxlbWVudC5yZW5kZXJIaWVyYXJjaHkpOwogICAgICAgIGlmIChsYWJlbEZvckVkZ2UgPT0gbnVsbCkgewogICAgICAgICAgICAvLyBXZSBoYXZlIG5vIGluZm9ybWF0aW9uIHRvIHNob3cgb24gdGhpcyBlZGdlLgogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGVkZ2VHcm91cAogICAgICAgICAgICAuYXBwZW5kKCd0ZXh0JykKICAgICAgICAgICAgLmFwcGVuZCgndGV4dFBhdGgnKQogICAgICAgICAgICAuYXR0cigneGxpbms6aHJlZicsICcjJyArIHBhdGhJZCkKICAgICAgICAgICAgLmF0dHIoJ3N0YXJ0T2Zmc2V0JywgJzUwJScpCiAgICAgICAgICAgIC5hdHRyKCd0ZXh0LWFuY2hvcicsICdtaWRkbGUnKQogICAgICAgICAgICAuYXR0cignZG9taW5hbnQtYmFzZWxpbmUnLCAnY2VudHJhbCcpCiAgICAgICAgICAgIC50ZXh0KGxhYmVsRm9yRWRnZSk7CiAgICB9CiAgICBsZXQgaW50ZXJwb2xhdGUkNyA9IGxpbmUoKQogICAgICAgIC5jdXJ2ZShiYXNpcyQyKQogICAgICAgIC54KChkKSA9PiB7CiAgICAgICAgcmV0dXJuIGQueDsKICAgIH0pCiAgICAgICAgLnkoKGQpID0+IHsKICAgICAgICByZXR1cm4gZC55OwogICAgfSk7CiAgICAvKioKICAgICAqIFJldHVybnMgYSB0d2VlbiBpbnRlcnBvbGF0b3IgZm9yIHRoZSBlbmRwb2ludCBvZiBhbiBlZGdlIHBhdGguCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldEVkZ2VQYXRoSW50ZXJwb2xhdG9yKGNvbXBvbmVudCwgcmVuZGVyUGF0aCwgZCwgaSwgYSkgewogICAgICAgIGxldCByZW5kZXJNZXRhZWRnZUluZm8gPSBkLmxhYmVsOwogICAgICAgIGxldCBhZGpvaW5pbmdNZXRhZWRnZSA9IHJlbmRlck1ldGFlZGdlSW5mby5hZGpvaW5pbmdNZXRhZWRnZTsKICAgICAgICBsZXQgcG9pbnRzID0gcmVuZGVyTWV0YWVkZ2VJbmZvLnBvaW50czsKICAgICAgICAvLyBBZGp1c3QgdGhlIHBhdGggc28gdGhhdCBzdGFydC9lbmQgbWFya2VycyBwb2ludCB0byB0aGUgZW5kCiAgICAgICAgLy8gb2YgdGhlIHBhdGguCiAgICAgICAgY29uc3QgeyBzaGFkb3dSb290IH0gPSBjb21wb25lbnQ7CiAgICAgICAgaWYgKGQubGFiZWwuc3RhcnRNYXJrZXJJZCkgewogICAgICAgICAgICBwb2ludHMgPSBhZGp1c3RQYXRoUG9pbnRzRm9yTWFya2VyKHBvaW50cywgc2VsZWN0KHNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvcignIycgKyBkLmxhYmVsLnN0YXJ0TWFya2VySWQpKSwgdHJ1ZSk7CiAgICAgICAgfQogICAgICAgIGlmIChkLmxhYmVsLmVuZE1hcmtlcklkKSB7CiAgICAgICAgICAgIHBvaW50cyA9IGFkanVzdFBhdGhQb2ludHNGb3JNYXJrZXIocG9pbnRzLCBzZWxlY3Qoc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yKCcjJyArIGQubGFiZWwuZW5kTWFya2VySWQpKSwgZmFsc2UpOwogICAgICAgIH0KICAgICAgICBpZiAoIWFkam9pbmluZ01ldGFlZGdlKSB7CiAgICAgICAgICAgIHJldHVybiBpbnRlcnBvbGF0ZVZhbHVlKGEsIGludGVycG9sYXRlJDcocG9pbnRzKSk7CiAgICAgICAgfQogICAgICAgIC8vIEdldCB0aGUgYWRqb2luaW5nIHBhdGggdGhhdCBtYXRjaGVzIHRoZSBhZGpvaW5pbmcgbWV0YWVkZ2UuCiAgICAgICAgbGV0IGFkam9pbmluZ1BhdGggPSAoYWRqb2luaW5nTWV0YWVkZ2UuZWRnZUdyb3VwLm5vZGUoKS5maXJzdENoaWxkKTsKICAgICAgICAvLyBGaW5kIHRoZSBkZXNpcmVkIFNWR1BvaW50IGFsb25nIHRoZSBhZGpvaW5pbmcgcGF0aCwgdGhlbiBjb252ZXJ0IHRob3NlCiAgICAgICAgLy8gY29vcmRpbmF0ZXMgaW50byB0aGUgc3BhY2Ugb2YgdGhlIHJlbmRlclBhdGggdXNpbmcgaXRzIEN1cnJlbnQKICAgICAgICAvLyBUcmFuc2Zvcm1hdGlvbiBNYXRyaXggKENUTSkuCiAgICAgICAgbGV0IGluYm91bmQgPSByZW5kZXJNZXRhZWRnZUluZm8ubWV0YWVkZ2UuaW5ib3VuZDsKICAgICAgICByZXR1cm4gZnVuY3Rpb24gKHQpIHsKICAgICAgICAgICAgbGV0IGFkam9pbmluZ1BvaW50ID0gYWRqb2luaW5nUGF0aAogICAgICAgICAgICAgICAgLmdldFBvaW50QXRMZW5ndGgoaW5ib3VuZCA/IGFkam9pbmluZ1BhdGguZ2V0VG90YWxMZW5ndGgoKSA6IDApCiAgICAgICAgICAgICAgICAubWF0cml4VHJhbnNmb3JtKGFkam9pbmluZ1BhdGguZ2V0Q1RNKCkpCiAgICAgICAgICAgICAgICAubWF0cml4VHJhbnNmb3JtKHJlbmRlclBhdGguZ2V0Q1RNKCkuaW52ZXJzZSgpKTsKICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSByZWxldmFudCBwb2ludCBpbiB0aGUgcmVuZGVyTWV0YWVkZ2VJbmZvJ3MgcG9pbnRzIGxpc3QsIHRoZW4KICAgICAgICAgICAgLy8gcmUtaW50ZXJwb2xhdGUgdGhlIHBhdGguCiAgICAgICAgICAgIGxldCBpbmRleCA9IGluYm91bmQgPyAwIDogcG9pbnRzLmxlbmd0aCAtIDE7CiAgICAgICAgICAgIHBvaW50c1tpbmRleF0ueCA9IGFkam9pbmluZ1BvaW50Lng7CiAgICAgICAgICAgIHBvaW50c1tpbmRleF0ueSA9IGFkam9pbmluZ1BvaW50Lnk7CiAgICAgICAgICAgIGxldCBkUGF0aCA9IGludGVycG9sYXRlJDcocG9pbnRzKTsKICAgICAgICAgICAgcmV0dXJuIGRQYXRoOwogICAgICAgIH07CiAgICB9CiAgICBmdW5jdGlvbiBwb3NpdGlvbiQyKGNvbXBvbmVudCwgZWRnZUdyb3VwKSB7CiAgICAgICAgc2VsZWN0KGVkZ2VHcm91cCkKICAgICAgICAgICAgLnNlbGVjdCgncGF0aC4nICsgQ2xhc3MkMS5FZGdlLkxJTkUpCiAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgLmF0dHJUd2VlbignZCcsIGZ1bmN0aW9uIChkLCBpLCBhKSB7CiAgICAgICAgICAgIHJldHVybiBnZXRFZGdlUGF0aEludGVycG9sYXRvcihjb21wb25lbnQsIHRoaXMsIGQsIGksIGEpOwogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBGb3IgYSBnaXZlbiBkMyBzZWxlY3Rpb24gYW5kIGRhdGEgb2JqZWN0LCBtYXJrIHRoZSBlZGdlIGFzIGEgY29udHJvbAogICAgICogZGVwZW5kZW5jeSBpZiBpdCBjb250YWlucyBvbmx5IGNvbnRyb2wgZWRnZXMuCiAgICAgKgogICAgICogZCdzIGxhYmVsIHByb3BlcnR5IHdpbGwgYmUgYSBSZW5kZXJNZXRhZWRnZUluZm8gb2JqZWN0LgogICAgICovCiAgICBmdW5jdGlvbiBzdHlsaXplKGVkZ2VHcm91cCwgZCwgc3R5bGl6ZSkgewogICAgICAgIGVkZ2VHcm91cC5jbGFzc2VkKCdmYWRlZCcsIGQubGFiZWwuaXNGYWRlZE91dCk7CiAgICAgICAgbGV0IG1ldGFlZGdlID0gZC5sYWJlbC5tZXRhZWRnZTsKICAgICAgICBlZGdlR3JvdXAKICAgICAgICAgICAgLnNlbGVjdCgncGF0aC4nICsgQ2xhc3MkMS5FZGdlLkxJTkUpCiAgICAgICAgICAgIC5jbGFzc2VkKCdjb250cm9sLWRlcCcsIG1ldGFlZGdlICYmICFtZXRhZWRnZS5udW1SZWd1bGFyRWRnZXMpOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE1IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICdMaWNlbnNlJyk7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gJ0FTIElTJyBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBTZWxlY3Qgb3IgQ3JlYXRlIGEgJ2cubm9kZXMnIGdyb3VwIHRvIGEgZ2l2ZW4gc2NlbmVHcm91cAogICAgICogYW5kIGJ1aWxkcyBhIG51bWJlciBvZiAnZy5ub2RlJyBncm91cHMgaW5zaWRlIHRoZSBncm91cC4KICAgICAqCiAgICAgKiBTdHJ1Y3R1cmUgUGF0dGVybjoKICAgICAqCiAgICAgKiA8ZyBjbGFzcz0nbm9kZXMnPgogICAgICogICA8ZyBjbGFzcz0nbm9kZSc+CiAgICAgKiAgICAgPGcgY2xhc3M9J2luLWFubm90YXRpb25zJz4KICAgICAqICAgICAgIC4uLgogICAgICogICAgIDwvZz4KICAgICAqICAgICA8ZyBjbGFzcz0nb3V0LWFubm90YXRpb25zJz4KICAgICAqICAgICAgIC4uLgogICAgICogICAgIDwvZz4KICAgICAqICAgICA8ZyBjbGFzcz0nbm9kZXNoYXBlJz4KICAgICAqICAgICAgPCEtLQogICAgICogICAgICBDb250ZW50IG9mIHRoZSBub2RlIHNoYXBlIHNob3VsZCBiZSBmb3IgdGhlIG5vZGUgaXRzZWxmLiBGb3IgZXhhbXBsZSBhCiAgICAgKiAgICAgIE1ldGFub2RlIHdvdWxkIGhhdmUgYSA8cmVjdD4gd2l0aCByb3VuZGVkIGVkZ2VzLCBhbiBvcCB3b3VsZCBoYXZlIGFuCiAgICAgKiAgICAgIDxlbGxpcHNlPi4gTW9yZSBjb21wbGV4IG5vZGVzIGxpa2Ugc2VyaWVzIG1heSBjb250YWluIG11bHRpcGxlCiAgICAgKiAgICAgIGVsZW1lbnRzIHdoaWNoIGFyZSBjb25kaXRpb25hbGx5IHZpc2libGUgYmFzZWQgb24gd2hldGhlciB0aGUgbm9kZSBpcwogICAgICogICAgICBleHBhbmRlZC4KICAgICAqICAgICAgLS0+CiAgICAgKiAgICAgPC9nPgogICAgICogICAgIDx0ZXh0IGNsYXNzPSdsYWJlbCc+bm9kZSBuYW1lPC90ZXh0PgogICAgICogICAgIDxnIGNsYXNzPSdzdWJzY2VuZSc+CiAgICAgKiAgICAgICA8IS0tCiAgICAgKiAgICAgICBDb250ZW50IG9mICB0aGUgc3Vic2NlbmUgKG9ubHkgZm9yIG1ldGFub2RlIGFuZCBzZXJpZXMgbm9kZSkuCiAgICAgKgogICAgICogICAgICAgU3Vic2NlbmUgaXMgYSBzdmcgZ3JvdXAgdGhhdCBjb250YWlucyBjb250ZW50IG9mIHRoZQogICAgICogICAgICAgbWV0YW5vZGUncyBtZXRhZ3JhcGggdGhhdCBpcyByZWN1cnNpdmVseSBnZW5lcmF0ZWQgYnkgU2NlbmUuYnVpbGQoKS4KICAgICAqCiAgICAgKiAgICAgICBXaGVuIHRoZSBncmFwaCBpcyBleHBhbmRlZCBtdWx0aXBsZSB0aW1lcywgYSBzdWJzY2VuZSBjYW4gY29udGFpbgogICAgICogICAgICAgbmVzdGVkIHN1YnNjZW5lcyBpbnNpZGUuCiAgICAgKiAgICAgICAtLT4KICAgICAqICAgICA8L2c+CiAgICAgKiAgIDwvZz4KICAgICAqICAgLi4uCiAgICAgKiA8L2c+CiAgICAgKgogICAgICoKICAgICAqIEBwYXJhbSBzY2VuZUdyb3VwIHNlbGVjdGlvbiBvZiB0aGUgY29udGFpbmVyCiAgICAgKiBAcGFyYW0gbm9kZURhdGEgYXJyYXkgb2YgcmVuZGVyIG5vZGUgaW5mb3JtYXRpb24gdG8gbWFwCiAgICAgKiBAcGFyYW0gc2NlbmVFbGVtZW50IDx0Zi1ncmFwaC1zY2VuZT4gcG9seW1lciBlbGVtZW50CiAgICAgKiBAcmV0dXJuIHNlbGVjdGlvbiBvZiB0aGUgY3JlYXRlZCBub2RlR3JvdXBzCiAgICAgKi8KICAgIGZ1bmN0aW9uIGJ1aWxkR3JvdXAkMShzY2VuZUdyb3VwLCBub2RlRGF0YSwgc2NlbmVFbGVtZW50KSB7CiAgICAgICAgbGV0IGNvbnRhaW5lciA9IHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2NlbmVHcm91cCwgJ2cnLCBDbGFzcyQxLk5vZGUuQ09OVEFJTkVSKTsKICAgICAgICAvLyBTZWxlY3QgYWxsIGNoaWxkcmVuIGFuZCBqb2luIHdpdGggZGF0YS4KICAgICAgICAvLyAoTm90ZSB0aGF0IGFsbCBjaGlsZHJlbiBvZiBnLm5vZGVzIGFyZSBnLm5vZGUpCiAgICAgICAgbGV0IG5vZGVHcm91cHMgPSBjb250YWluZXIKICAgICAgICAgICAgLnNlbGVjdEFsbChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmNoaWxkTm9kZXM7CiAgICAgICAgfSkKICAgICAgICAgICAgLmRhdGEobm9kZURhdGEsIChkKSA9PiB7CiAgICAgICAgICAgIC8vIG1ha2Ugc3VyZSB0aGF0IHdlIGRvbid0IGhhdmUgdG8gc3dhcCBzaGFwZSB0eXBlCiAgICAgICAgICAgIHJldHVybiBkLm5vZGUubmFtZSArICc6JyArIGQubm9kZS50eXBlOwogICAgICAgIH0pOwogICAgICAgIC8vIEVOVEVSCiAgICAgICAgbm9kZUdyb3VwcwogICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgLmF0dHIoJ2RhdGEtbmFtZScsIChkKSA9PiB7CiAgICAgICAgICAgIHJldHVybiBkLm5vZGUubmFtZTsKICAgICAgICB9KQogICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoZCkgewogICAgICAgICAgICBsZXQgbm9kZUdyb3VwID0gc2VsZWN0KHRoaXMpOwogICAgICAgICAgICAvLyBpbmRleCBub2RlIGdyb3VwIGZvciBxdWljayBzdHlsaXppbmcKICAgICAgICAgICAgc2NlbmVFbGVtZW50LmFkZE5vZGVHcm91cChkLm5vZGUubmFtZSwgbm9kZUdyb3VwKTsKICAgICAgICB9KQogICAgICAgICAgICAubWVyZ2Uobm9kZUdyb3VwcykKICAgICAgICAgICAgLy8gRU5URVIgKyBVUERBVEUKICAgICAgICAgICAgLmF0dHIoJ2NsYXNzJywgKGQpID0+IHsKICAgICAgICAgICAgcmV0dXJuIENsYXNzJDEuTm9kZS5HUk9VUCArICcgJyArIG5vZGVDbGFzcyhkKTsKICAgICAgICB9KQogICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoZCkgewogICAgICAgICAgICBsZXQgbm9kZUdyb3VwID0gc2VsZWN0KHRoaXMpOwogICAgICAgICAgICAvLyBBZGQgZy5pbi1hbm5vdGF0aW9ucyAoYWx3YXlzIGFkZCAtLSB0byBrZWVwIGxheWVyIG9yZGVyCiAgICAgICAgICAgIC8vIGNvbnNpc3RlbnQuKQogICAgICAgICAgICBsZXQgaW5Bbm5vdGF0aW9uQm94ID0gc2VsZWN0T3JDcmVhdGVDaGlsZChub2RlR3JvdXAsICdnJywgQ2xhc3MkMS5Bbm5vdGF0aW9uLklOQk9YKTsKICAgICAgICAgICAgYnVpbGRHcm91cEZvckFubm90YXRpb24oaW5Bbm5vdGF0aW9uQm94LCBkLmluQW5ub3RhdGlvbnMsIGQsIHNjZW5lRWxlbWVudCk7CiAgICAgICAgICAgIC8vIEFkZCBnLm91dC1hbm5vdGF0aW9ucyAgKGFsd2F5cyBhZGQgLS0gdG8ga2VlcCBsYXllciBvcmRlcgogICAgICAgICAgICAvLyBjb25zaXN0ZW50LikKICAgICAgICAgICAgbGV0IG91dEFubm90YXRpb25Cb3ggPSBzZWxlY3RPckNyZWF0ZUNoaWxkKG5vZGVHcm91cCwgJ2cnLCBDbGFzcyQxLkFubm90YXRpb24uT1VUQk9YKTsKICAgICAgICAgICAgYnVpbGRHcm91cEZvckFubm90YXRpb24ob3V0QW5ub3RhdGlvbkJveCwgZC5vdXRBbm5vdGF0aW9ucywgZCwgc2NlbmVFbGVtZW50KTsKICAgICAgICAgICAgLy8gQnVpbGQgLnNoYXBlIGZpcnN0IChiYWNrZ3JvdW5kIG9mIHRoZSBub2RlKS4KICAgICAgICAgICAgbGV0IHNoYXBlID0gYnVpbGRTaGFwZShub2RlR3JvdXAsIGQsIENsYXNzJDEuTm9kZS5TSEFQRSk7CiAgICAgICAgICAgIGlmIChkLm5vZGUuaXNHcm91cE5vZGUpIHsKICAgICAgICAgICAgICAgIGFkZEJ1dHRvbihzaGFwZSwgZCwgc2NlbmVFbGVtZW50KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBhZGRJbnRlcmFjdGlvbihzaGFwZSwgZCwgc2NlbmVFbGVtZW50KTsKICAgICAgICAgICAgLy8gQnVpbGQgc3Vic2NlbmUgb24gdGhlIHRvcC4KICAgICAgICAgICAgc3Vic2NlbmVCdWlsZChub2RlR3JvdXAsIGQsIHNjZW5lRWxlbWVudCk7CiAgICAgICAgICAgIC8vIEJ1aWxkIGxhYmVsIGxhc3QuIFNob3VsZCBiZSBvbiB0b3Agb2YgZXZlcnl0aGluZyBlbHNlLgogICAgICAgICAgICBsZXQgbGFiZWwgPSBsYWJlbEJ1aWxkKG5vZGVHcm91cCwgZCwgc2NlbmVFbGVtZW50KTsKICAgICAgICAgICAgLy8gRG8gbm90IGFkZCBpbnRlcmFjdGlvbiB0byBtZXRhbm9kZSBsYWJlbHMgYXMgdGhleSBsaXZlIGluc2lkZSB0aGUKICAgICAgICAgICAgLy8gbWV0YW5vZGUgc2hhcGUgd2hpY2ggYWxyZWFkeSBoYXMgdGhlIHNhbWUgaW50ZXJhY3Rpb25zLgogICAgICAgICAgICBhZGRJbnRlcmFjdGlvbihsYWJlbCwgZCwgc2NlbmVFbGVtZW50LCBkLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSk7CiAgICAgICAgICAgIHN0eWxpemUkMShub2RlR3JvdXAsIGQsIHNjZW5lRWxlbWVudCk7CiAgICAgICAgICAgIHBvc2l0aW9uJDMobm9kZUdyb3VwLCBkKTsKICAgICAgICB9KTsKICAgICAgICAvLyBFWElUCiAgICAgICAgbm9kZUdyb3VwcwogICAgICAgICAgICAuZXhpdCgpCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgIC8vIHJlbW92ZSBhbGwgaW5kaWNlcyBvbiByZW1vdmUKICAgICAgICAgICAgc2NlbmVFbGVtZW50LnJlbW92ZU5vZGVHcm91cChkLm5vZGUubmFtZSk7CiAgICAgICAgICAgIGxldCBub2RlR3JvdXAgPSBzZWxlY3QodGhpcyk7CiAgICAgICAgICAgIGlmIChkLmluQW5ub3RhdGlvbnMubGlzdC5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgICBub2RlR3JvdXAKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0KCcuJyArIENsYXNzJDEuQW5ub3RhdGlvbi5JTkJPWCkKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCcuJyArIENsYXNzJDEuQW5ub3RhdGlvbi5HUk9VUCkKICAgICAgICAgICAgICAgICAgICAuZWFjaCgoYSkgPT4gewogICAgICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5yZW1vdmVBbm5vdGF0aW9uR3JvdXAoYSwgZCk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoZC5vdXRBbm5vdGF0aW9ucy5saXN0Lmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgICAgIG5vZGVHcm91cAogICAgICAgICAgICAgICAgICAgIC5zZWxlY3QoJy4nICsgQ2xhc3MkMS5Bbm5vdGF0aW9uLk9VVEJPWCkKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCcuJyArIENsYXNzJDEuQW5ub3RhdGlvbi5HUk9VUCkKICAgICAgICAgICAgICAgICAgICAuZWFjaCgoYSkgPT4gewogICAgICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5yZW1vdmVBbm5vdGF0aW9uR3JvdXAoYSwgZCk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgIH0pCiAgICAgICAgICAgIC5yZW1vdmUoKTsKICAgICAgICByZXR1cm4gbm9kZUdyb3VwczsKICAgIH0KICAgIC8qKgogICAgICogVXBkYXRlIG9yIHJlbW92ZSB0aGUgc3Vic2NlbmUgb2YgYSByZW5kZXIgZ3JvdXAgbm9kZSBkZXBlbmRpbmcgb24gd2hldGhlciBpdAogICAgICogaXMgYSBleHBhbmRlZC4gSWYgdGhlIG5vZGUgaXMgbm90IGEgZ3JvdXAgbm9kZSwgdGhpcyBtZXRob2QgaGFzIG5vIGVmZmVjdC4KICAgICAqCiAgICAgKiBAcGFyYW0gbm9kZUdyb3VwIHNlbGVjdGlvbiBvZiB0aGUgY29udGFpbmVyCiAgICAgKiBAcGFyYW0gcmVuZGVyTm9kZUluZm8gdGhlIHJlbmRlciBpbmZvcm1hdGlvbiBmb3IgdGhlIG5vZGUuCiAgICAgKiBAcGFyYW0gc2NlbmVFbGVtZW50IDx0Zi1ncmFwaC1zY2VuZT4gcG9seW1lciBlbGVtZW50LgogICAgICogQHJldHVybiBTZWxlY3Rpb24gb2YgdGhlIHN1YnNjZW5lIGdyb3VwLCBvciBudWxsIGlmIG5vZGUgZ3JvdXAgZG9lcyBub3QgaGF2ZQogICAgICogICAgICAgIGEgc3Vic2NlbmUuIE9wIG5vZGVzLCBicmlkZ2Ugbm9kZXMgYW5kIHVuZXhwYW5kZWQgZ3JvdXAgbm9kZXMgd2lsbAogICAgICogICAgICAgIG5vdCBoYXZlIGEgc3Vic2NlbmUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN1YnNjZW5lQnVpbGQobm9kZUdyb3VwLCByZW5kZXJOb2RlSW5mbywgc2NlbmVFbGVtZW50KSB7CiAgICAgICAgaWYgKHJlbmRlck5vZGVJbmZvLm5vZGUuaXNHcm91cE5vZGUpIHsKICAgICAgICAgICAgaWYgKHJlbmRlck5vZGVJbmZvLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAvLyBSZWN1cnNpdmVseSBidWlsZCB0aGUgc3Vic2NlbmUuCiAgICAgICAgICAgICAgICByZXR1cm4gYnVpbGRHcm91cEZvclNjZW5lKG5vZGVHcm91cCwgcmVuZGVyTm9kZUluZm8sIHNjZW5lRWxlbWVudCwgQ2xhc3MkMS5TdWJzY2VuZS5HUk9VUCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQ2xlYW4gb3V0IGV4aXN0aW5nIHN1YnNjZW5lIGlmIHRoZSBub2RlIGlzIG5vdCBleHBhbmRlZC4KICAgICAgICAgICAgc2VsZWN0Q2hpbGQkMShub2RlR3JvdXAsICdnJywgQ2xhc3MkMS5TdWJzY2VuZS5HUk9VUCkucmVtb3ZlKCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBudWxsOwogICAgfQogICAgLyoqCiAgICAgKiBUcmFuc2xhdGUgdGhlIHN1YnNjZW5lIG9mIHRoZSBnaXZlbiBub2RlIGdyb3VwCiAgICAgKi8KICAgIGZ1bmN0aW9uIHN1YnNjZW5lUG9zaXRpb24obm9kZUdyb3VwLCBkKSB7CiAgICAgICAgbGV0IHgwID0gZC54IC0gZC53aWR0aCAvIDIgKyBkLnBhZGRpbmdMZWZ0OwogICAgICAgIGxldCB5MCA9IGQueSAtIGQuaGVpZ2h0IC8gMiArIGQucGFkZGluZ1RvcDsKICAgICAgICBsZXQgc3Vic2NlbmUgPSBzZWxlY3RDaGlsZCQxKG5vZGVHcm91cCwgJ2cnLCBDbGFzcyQxLlN1YnNjZW5lLkdST1VQKTsKICAgICAgICB0cmFuc2xhdGUkMShzdWJzY2VuZSwgeDAsIHkwKTsKICAgIH0KICAgIC8qKgogICAgICogQWRkIGFuIGV4cGFuZC9jb2xsYXBzZSBidXR0b24gdG8gYSBncm91cCBub2RlCiAgICAgKgogICAgICogQHBhcmFtIHNlbGVjdGlvbiBUaGUgZ3JvdXAgbm9kZSBzZWxlY3Rpb24uCiAgICAgKiBAcGFyYW0gZCBJbmZvIGFib3V0IHRoZSBub2RlIGJlaW5nIHJlbmRlcmVkLgogICAgICogQHBhcmFtIHNjZW5lRWxlbWVudCA8dGYtZ3JhcGgtc2NlbmU+IHBvbHltZXIgZWxlbWVudC4KICAgICAqLwogICAgZnVuY3Rpb24gYWRkQnV0dG9uKHNlbGVjdGlvbiwgZCwgc2NlbmVFbGVtZW50KSB7CiAgICAgICAgbGV0IGdyb3VwID0gc2VsZWN0T3JDcmVhdGVDaGlsZChzZWxlY3Rpb24sICdnJywgQ2xhc3MkMS5Ob2RlLkJVVFRPTl9DT05UQUlORVIpOwogICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoZ3JvdXAsICdjaXJjbGUnLCBDbGFzcyQxLk5vZGUuQlVUVE9OX0NJUkNMRSk7CiAgICAgICAgc2VsZWN0T3JDcmVhdGVDaGlsZChncm91cCwgJ3BhdGgnLCBDbGFzcyQxLk5vZGUuRVhQQU5EX0JVVFRPTikKICAgICAgICAgICAgLmF0dHIoJ2QnLCAnTTAsLTIuMiBWMi4yIE0tMi4yLDAgSDIuMicpOwogICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoZ3JvdXAsICdwYXRoJywgQ2xhc3MkMS5Ob2RlLkNPTExBUFNFX0JVVFRPTikKICAgICAgICAgICAgLmF0dHIoJ2QnLCAnTS0yLjIsMCBIMi4yJyk7CiAgICAgICAgZ3JvdXAub24oJ2NsaWNrJywgKGQpID0+IHsKICAgICAgICAgICAgLy8gU3RvcCB0aGlzIGV2ZW50J3MgcHJvcGFnYXRpb24gc28gdGhhdCBpdCBpc24ndCBhbHNvIGNvbnNpZGVyZWQgYQogICAgICAgICAgICAvLyBub2RlLXNlbGVjdC4KICAgICAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgICAgICAgIHNjZW5lRWxlbWVudC5maXJlKCdub2RlLXRvZ2dsZS1leHBhbmQnLCB7IG5hbWU6IGQubm9kZS5uYW1lIH0pOwogICAgICAgIH0pOwogICAgICAgIHBvc2l0aW9uQnV0dG9uKGdyb3VwLCBkKTsKICAgIH0KICAgIC8qKgogICAgICogRmlyZSBub2RlLSogZXZlbnRzIHdoZW4gdGhlIHNlbGVjdGlvbiBpcyBpbnRlcmFjdGVkLgogICAgICoKICAgICAqIEBwYXJhbSBkaXNhYmxlSW50ZXJhY3Rpb24gV2hlbiB0cnVlLCBoYXZlIHRoZSBwcm92aWRlZCBzZWxlY3Rpb24KICAgICAqIGlnbm9yZSBhbGwgcG9pbnRlciBldmVudHMuIFVzZWQgZm9yIHRleHQgbGFiZWxzIGluc2lkZSBvZiBtZXRhbm9kZXMsIHdoaWNoCiAgICAgKiBkb24ndCBuZWVkIGludGVyYWN0aW9uIGFzIHRoZWlyIHN1cnJvdW5kaW5nIHNoYXBlIGhhcyBpbnRlcmFjdGlvbiwgYW5kIGlmCiAgICAgKiBnaXZlbiBpbnRlcmFjdGlvbiB3b3VsZCBjYXVzZSBjb25mbGljdHMgd2l0aCB0aGUgZXhwYW5kL2NvbGxhcHNlIGJ1dHRvbi4KICAgICAqLwogICAgZnVuY3Rpb24gYWRkSW50ZXJhY3Rpb24oc2VsZWN0aW9uLCBkLCBzY2VuZUVsZW1lbnQsIGRpc2FibGVJbnRlcmFjdGlvbikgewogICAgICAgIGlmIChkaXNhYmxlSW50ZXJhY3Rpb24pIHsKICAgICAgICAgICAgc2VsZWN0aW9uLmF0dHIoJ3BvaW50ZXItZXZlbnRzJywgJ25vbmUnKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBsZXQgY29udGV4dE1lbnVGdW5jdGlvbiA9IGdldE1lbnUoc2NlbmVFbGVtZW50LCBnZXRDb250ZXh0TWVudShkLm5vZGUsIHNjZW5lRWxlbWVudCkpOwogICAgICAgIHNlbGVjdGlvbgogICAgICAgICAgICAub24oJ2RibGNsaWNrJywgKGQpID0+IHsKICAgICAgICAgICAgc2NlbmVFbGVtZW50LmZpcmUoJ25vZGUtdG9nZ2xlLWV4cGFuZCcsIHsgbmFtZTogZC5ub2RlLm5hbWUgfSk7CiAgICAgICAgfSkKICAgICAgICAgICAgLm9uKCdtb3VzZW92ZXInLCAoZCkgPT4gewogICAgICAgICAgICAvLyBkb24ndCBzZW5kIG1vdXNlb3ZlciBvdmVyIGV4cGFuZGVkIGdyb3VwLAogICAgICAgICAgICAvLyBvdGhlcndpc2UgaXQgaXMgY2F1c2luZyB0b28gbXVjaCBnbGl0Y2hlcwogICAgICAgICAgICBpZiAoc2NlbmVFbGVtZW50LmlzTm9kZUV4cGFuZGVkKGQpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc2NlbmVFbGVtZW50LmZpcmUoJ25vZGUtaGlnaGxpZ2h0JywgeyBuYW1lOiBkLm5vZGUubmFtZSB9KTsKICAgICAgICB9KQogICAgICAgICAgICAub24oJ21vdXNlb3V0JywgKGQpID0+IHsKICAgICAgICAgICAgLy8gZG9uJ3Qgc2VuZCBtb3VzZW92ZXIgb3ZlciBleHBhbmRlZCBncm91cCwKICAgICAgICAgICAgLy8gb3RoZXJ3aXNlIGl0IGlzIGNhdXNpbmcgdG9vIG11Y2ggZ2xpdGNoZXMKICAgICAgICAgICAgaWYgKHNjZW5lRWxlbWVudC5pc05vZGVFeHBhbmRlZChkKSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHNjZW5lRWxlbWVudC5maXJlKCdub2RlLXVuaGlnaGxpZ2h0JywgeyBuYW1lOiBkLm5vZGUubmFtZSB9KTsKICAgICAgICB9KQogICAgICAgICAgICAub24oJ2NsaWNrJywgKGQpID0+IHsKICAgICAgICAgICAgLy8gU3RvcCB0aGlzIGV2ZW50J3MgcHJvcGFnYXRpb24gc28gdGhhdCBpdCBpc24ndCBhbHNvIGNvbnNpZGVyZWQKICAgICAgICAgICAgLy8gYSBncmFwaC1zZWxlY3QuCiAgICAgICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgICAgICBzY2VuZUVsZW1lbnQuZmlyZSgnbm9kZS1zZWxlY3QnLCB7IG5hbWU6IGQubm9kZS5uYW1lIH0pOwogICAgICAgIH0pCiAgICAgICAgICAgIC5vbignY29udGV4dG1lbnUnLCAoZCwgaSkgPT4gewogICAgICAgICAgICBzY2VuZUVsZW1lbnQuZmlyZSgnbm9kZS1zZWxlY3QnLCB7IG5hbWU6IGQubm9kZS5uYW1lIH0pOwogICAgICAgICAgICBjb250ZXh0TWVudUZ1bmN0aW9uLmNhbGwoZCwgaSk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGQzIGNvbnRleHQgbWVudSBzcGVjaWZpY2F0aW9uIGZvciB0aGUgcHJvdmlkZWQgbm9kZS4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0Q29udGV4dE1lbnUobm9kZSwgc2NlbmVFbGVtZW50KSB7CiAgICAgICAgbGV0IG1lbnUgPSBbCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIHRpdGxlOiAoZCkgPT4gewogICAgICAgICAgICAgICAgICAgIHJldHVybiBnZXRJbmNsdWRlTm9kZUJ1dHRvblN0cmluZyhub2RlLmluY2x1ZGUpOwogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGFjdGlvbjogKGVsbSwgZCwgaSkgPT4gewogICAgICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5maXJlKCdub2RlLXRvZ2dsZS1leHRyYWN0JywgeyBuYW1lOiBub2RlLm5hbWUgfSk7CiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9LAogICAgICAgIF07CiAgICAgICAgaWYgKHNjZW5lRWxlbWVudC5ub2RlQ29udGV4dE1lbnVJdGVtcykgewogICAgICAgICAgICAvLyBBZGQgdGhlc2UgYWRkaXRpb25hbCBjb250ZXh0IG1lbnUgaXRlbXMuCiAgICAgICAgICAgIG1lbnUgPSBtZW51LmNvbmNhdChzY2VuZUVsZW1lbnQubm9kZUNvbnRleHRNZW51SXRlbXMpOwogICAgICAgIH0KICAgICAgICBpZiAoY2FuQmVJblNlcmllcyhub2RlKSkgewogICAgICAgICAgICBtZW51LnB1c2goewogICAgICAgICAgICAgICAgdGl0bGU6IChkKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGdldEdyb3VwU2V0dGluZ0xhYmVsKG5vZGUpOwogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGFjdGlvbjogKGVsbSwgZCwgaSkgPT4gewogICAgICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5maXJlKCdub2RlLXRvZ2dsZS1zZXJpZXNncm91cCcsIHsKICAgICAgICAgICAgICAgICAgICAgICAgbmFtZTogZ2V0U2VyaWVzTmFtZShub2RlKSwKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICByZXR1cm4gbWVudTsKICAgIH0KICAgIC8qKiBSZXR1cm5zIGlmIGEgbm9kZSBjYW4gYmUgcGFydCBvZiBhIGdyb3VwZWQgc2VyaWVzICovCiAgICBmdW5jdGlvbiBjYW5CZUluU2VyaWVzKG5vZGUpIHsKICAgICAgICByZXR1cm4gZ2V0U2VyaWVzTmFtZShub2RlKSAhPT0gbnVsbDsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgbmFtZSBvZiB0aGUgcG9zc2libGUgZ3JvdXBlZCBzZXJpZXMgY29udGFpbmluZyB0aGlzIG5vZGUuCiAgICAgKiBSZXR1cm5zIG51bGwgaWYgdGhlIG5vZGUgY2Fubm90IGJlIHBhcnQgb2YgYSBncm91cGVkIHNlcmllcyBvZiBub2Rlcy4KICAgICAqLwogICAgZnVuY3Rpb24gZ2V0U2VyaWVzTmFtZShub2RlKSB7CiAgICAgICAgaWYgKCFub2RlKSB7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICBpZiAobm9kZS50eXBlID09PSBOb2RlVHlwZS5TRVJJRVMpIHsKICAgICAgICAgICAgcmV0dXJuIG5vZGUubmFtZTsKICAgICAgICB9CiAgICAgICAgaWYgKG5vZGUudHlwZSA9PT0gTm9kZVR5cGUuT1ApIHsKICAgICAgICAgICAgbGV0IG9wID0gbm9kZTsKICAgICAgICAgICAgcmV0dXJuIG9wLm93bmluZ1NlcmllczsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIG51bGw7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIFNlcmllc05vZGUgdGhhdCByZXByZXNlbnRzIHRoZSBzZXJpZXMgdGhhdCB0aGUgcHJvdmlkZWQgbm9kZQogICAgICogaXMgY29udGFpbmVkIGluIChvciBpdHNlbGYgaWYgdGhlIHByb3ZpZGVkIG5vZGUgaXMgaXRzZWxmIGEgU2VyaWVzTm9kZSkuCiAgICAgKiBSZXR1cm5zIG51bGwgaWYgdGhlIG5vZGUgaXMgbm90IHJlbmRlcmVkIGFzIHBhcnQgb2YgYSBzZXJpZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldENvbnRhaW5pbmdTZXJpZXMobm9kZSkgewogICAgICAgIGxldCBzID0gbnVsbDsKICAgICAgICBpZiAoIW5vZGUpIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKG5vZGUudHlwZSA9PT0gTm9kZVR5cGUuU0VSSUVTKSB7CiAgICAgICAgICAgIHMgPSBub2RlOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmIChub2RlLnBhcmVudE5vZGUgJiYgbm9kZS5wYXJlbnROb2RlLnR5cGUgPT09IE5vZGVUeXBlLlNFUklFUykgewogICAgICAgICAgICBzID0gbm9kZS5wYXJlbnROb2RlOwogICAgICAgIH0KICAgICAgICByZXR1cm4gczsKICAgIH0KICAgIC8qKgogICAgICogUmV0dXJucyB0aGUgbGFiZWwgZm9yIGEgYnV0dG9uIHRvIHRvZ2dsZSB0aGUgZ3JvdXAgc2V0dGluZyBvZiB0aGUgcHJvdmlkZWQKICAgICAqIG5vZGUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldEdyb3VwU2V0dGluZ0xhYmVsKG5vZGUpIHsKICAgICAgICByZXR1cm4gZ2V0R3JvdXBTZXJpZXNOb2RlQnV0dG9uU3RyaW5nKGdldENvbnRhaW5pbmdTZXJpZXMobm9kZSkgIT09IG51bGwKICAgICAgICAgICAgPyBTZXJpZXNHcm91cGluZ1R5cGUuR1JPVVAKICAgICAgICAgICAgOiBTZXJpZXNHcm91cGluZ1R5cGUuVU5HUk9VUCk7CiAgICB9CiAgICAvKioKICAgICAqIEFwcGVuZCBzdmcgdGV4dCBmb3IgbGFiZWwgYW5kIGFzc2lnbiBkYXRhLgogICAgICogQHBhcmFtIG5vZGVHcm91cAogICAgICogQHBhcmFtIHJlbmRlck5vZGVJbmZvIFRoZSByZW5kZXIgbm9kZSBpbmZvcm1hdGlvbiBmb3IgdGhlIGxhYmVsLgogICAgICogQHBhcmFtIHNjZW5lRWxlbWVudCA8dGYtZ3JhcGgtc2NlbmU+IHBvbHltZXIgZWxlbWVudC4KICAgICAqLwogICAgZnVuY3Rpb24gbGFiZWxCdWlsZChub2RlR3JvdXAsIHJlbmRlck5vZGVJbmZvLCBzY2VuZUVsZW1lbnQpIHsKICAgICAgICBsZXQgdGV4dCA9IHJlbmRlck5vZGVJbmZvLmRpc3BsYXlOYW1lOwogICAgICAgIC8vIFRydW5jYXRlIGxvbmcgbGFiZWxzIGZvciB1bmV4cGFuZGVkIE1ldGFub2Rlcy4KICAgICAgICBsZXQgdXNlRm9udFNjYWxlID0gcmVuZGVyTm9kZUluZm8ubm9kZS50eXBlID09PSBOb2RlVHlwZS5NRVRBICYmICFyZW5kZXJOb2RlSW5mby5leHBhbmRlZDsKICAgICAgICBsZXQgbGFiZWwgPSBzZWxlY3RPckNyZWF0ZUNoaWxkKG5vZGVHcm91cCwgJ3RleHQnLCBDbGFzcyQxLk5vZGUuTEFCRUwpOwogICAgICAgIC8vIE1ha2Ugc3VyZSB0aGUgbGFiZWwgaXMgdmlzdWFsbHkgb24gdG9wIGFtb25nIGl0cyBzaWJsaW5ncy4KICAgICAgICBsZXQgbGFiZWxOb2RlID0gbGFiZWwubm9kZSgpOwogICAgICAgIGxhYmVsTm9kZS5wYXJlbnROb2RlLmFwcGVuZENoaWxkKGxhYmVsTm9kZSk7CiAgICAgICAgbGFiZWwuYXR0cignZHknLCAnLjM1ZW0nKS5hdHRyKCd0ZXh0LWFuY2hvcicsICdtaWRkbGUnKTsKICAgICAgICBpZiAodXNlRm9udFNjYWxlKSB7CiAgICAgICAgICAgIGlmICh0ZXh0Lmxlbmd0aCA+IHNjZW5lRWxlbWVudC5tYXhNZXRhbm9kZUxhYmVsTGVuZ3RoKSB7CiAgICAgICAgICAgICAgICB0ZXh0ID0gdGV4dC5zdWJzdHIoMCwgc2NlbmVFbGVtZW50Lm1heE1ldGFub2RlTGFiZWxMZW5ndGggLSAyKSArICcuLi4nOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBzY2FsZSA9IGdldExhYmVsRm9udFNjYWxlKHNjZW5lRWxlbWVudCk7CiAgICAgICAgICAgIGxhYmVsLmF0dHIoJ2ZvbnQtc2l6ZScsIHNjYWxlKHRleHQubGVuZ3RoKSArICdweCcpOwogICAgICAgIH0KICAgICAgICBsZXQgdHh0RWxlbWVudCA9IGxhYmVsLnRleHQodGV4dCk7CiAgICAgICAgZW5mb3JjZUxhYmVsV2lkdGgodHh0RWxlbWVudCwgcmVuZGVyTm9kZUluZm8ubm9kZS50eXBlLCByZW5kZXJOb2RlSW5mbyk7CiAgICAgICAgcmV0dXJuIGxhYmVsOwogICAgfQogICAgLyoqCiAgICAgKiBUaGlzIGZ1bmN0aW9uIHNob3J0ZW5zIHRleHQgd2hpY2ggd291bGQgZXhjZWVkIHRoZSBtYXhpbXVtIHBpeGVsIHdpZHRoIG9mCiAgICAgKiBhIGxhYmVsLgogICAgICoKICAgICAqIEBwYXJhbSB0eHRFbGVtZW50U2VsZWN0aW9uIFRoZSB0ZXh0IGVsZW1lbnQgY29udGFpbmluZyB0aGUgbGFiZWwncyB0ZXh0IGFzIGQzCiAgICAgKiBzZWxlY3Rpb24uCiAgICAgKiBAcGFyYW0gbm9kZVR5cGUgVGhlIHR5cGUgb2YgdGhlIG5vZGUgdGhlIGxhYmVsIGJlbG9uZ3MgdG8uIElmIHRoZSBub2RlIGlzCiAgICAgKiBhbiBhbm5vdGF0aW9uLCB0aGUgdmFsdWUgaXMgLTEuIExhYmVsIHdpZHRocyBhcmUgZGVmaW5lZCBpbgogICAgICogbGF5b3V0LlBBUkFNUy5ub2RlU2l6ZS57bWV0YXxvcHwuLi59Lm1heExhYmVsV2lkdGggZm9yIG5vZGVzIGFuZAogICAgICogbGF5b3V0LlBBUkFNUy5hbm5vdGF0aW9ucy5sYWJlbFdpZHRoIGZvciBhbm5vdGF0aW9ucy4KICAgICAqIEBwYXJhbSByZW5kZXJOb2RlSW5mbyBUaGUgcmVuZGVyIGluZm9ybWF0aW9uIGFib3V0IHRoZSBub2RlLCByZXF1aXJlZCB0bwogICAgICogZGV0ZXJtaW5lIHdoZXRoZXIgTUVUQSBub2RlcyBhcmUgY29sbGFwc2VkIG9yIGV4cGFuZGVkLgogICAgICovCiAgICBmdW5jdGlvbiBlbmZvcmNlTGFiZWxXaWR0aCh0eHRFbGVtZW50U2VsZWN0aW9uLCBub2RlVHlwZSwgcmVuZGVyTm9kZUluZm8pIHsKICAgICAgICAvLyBHZXQgdGV4dCBlbGVtZW50IGl0c2VsZiBhbmQgaXRzIG9uLXNjcmVlbiB3aWR0aC4KICAgICAgICBsZXQgdHh0Tm9kZSA9IHR4dEVsZW1lbnRTZWxlY3Rpb24ubm9kZSgpOwogICAgICAgIGxldCBjb21wdXRlZFR4dExlbmd0aCA9IHR4dE5vZGUuZ2V0Q29tcHV0ZWRUZXh0TGVuZ3RoKCk7CiAgICAgICAgbGV0IGxhYmVsQ29udGVudCA9IHR4dE5vZGUudGV4dENvbnRlbnQ7CiAgICAgICAgLy8gR2V0IG1heGltdW0gbGVuZ3RoIGZyb20gc2V0dGluZ3MuCiAgICAgICAgbGV0IG1heExlbmd0aCA9IG51bGw7CiAgICAgICAgc3dpdGNoIChub2RlVHlwZSkgewogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICBpZiAocmVuZGVyTm9kZUluZm8gJiYgIXJlbmRlck5vZGVJbmZvLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gT25seSB0cmltIHRleHQgaWYKICAgICAgICAgICAgICAgICAgICAvLyBub2RlIGV4cGFuZGVkLgogICAgICAgICAgICAgICAgICAgIG1heExlbmd0aCA9IFBBUkFNUyQxLm5vZGVTaXplLm1ldGEubWF4TGFiZWxXaWR0aDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk9QOgogICAgICAgICAgICAgICAgbWF4TGVuZ3RoID0gUEFSQU1TJDEubm9kZVNpemUub3AubWF4TGFiZWxXaWR0aDsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIC0xOgogICAgICAgICAgICAgICAgbWF4TGVuZ3RoID0gUEFSQU1TJDEuYW5ub3RhdGlvbnMubWF4TGFiZWxXaWR0aDsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgICAvLyBSZXR1cm4gaWYgbm8gbWF4IGxlbmd0aCBwcm92aWRlZCBmb3Igbm9kZSB0eXBlLCBvciBjdXJyZW50IGxhYmVsIGxlbmd0aCBpcwogICAgICAgIC8vIGxlc3MgdGhhbiBvciBlcXVhbCB0byB0aGUgcHJvdmlkZWQgbGVuZ3RoIGxpbWl0LgogICAgICAgIGlmIChtYXhMZW5ndGggPT09IG51bGwgfHwgY29tcHV0ZWRUeHRMZW5ndGggPD0gbWF4TGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgLy8gRmluZCB0aGUgaW5kZXggb2YgdGhlIGNoYXJhY3RlciB3aGljaCBleGNlZWRzIHRoZSB3aWR0aC4KICAgICAgICAvLyBnZXRTdWJTdHJpbmdMZW5ndGggcGVyZm9ybXMgZmFyIGJldHRlciB0aGFuIGdldENvbXB1dGVkVGV4dExlbmd0aCwgYW5kCiAgICAgICAgLy8gcmVzdWx0cyBpbiBhIDN4IHNwZWVkLXVwIG9uIGF2ZXJhZ2UuCiAgICAgICAgbGV0IGluZGV4ID0gMTsKICAgICAgICB3aGlsZSAodHh0Tm9kZS5nZXRTdWJTdHJpbmdMZW5ndGgoMCwgaW5kZXgpIDwgbWF4TGVuZ3RoKSB7CiAgICAgICAgICAgIGluZGV4Kys7CiAgICAgICAgfQogICAgICAgIC8vIFNob3J0ZW4gdGhlIGxhYmVsIHN0YXJ0aW5nIGF0IHRoZSBzdHJpbmcgbGVuZ3RoIGtub3duIHRvIGJlIG9uZQogICAgICAgIC8vIGNoYXJhY3RlciBhYm92ZSBtYXggcGl4ZWwgbGVuZ3RoLgogICAgICAgIC8vIFdoZW4gc2hvcnRlbmVkIHRoZSBvcmlnaW5hbCBsYWJlbCdzIHN1YnN0cmluZyBpcyBjb25jYXRlbmF0ZWQgd2l0aAogICAgICAgIC8vICcuLi4nLCBiYXNlVGV4dCBjb250YWlucyB0aGUgc3Vic3RyaW5nIG5vdCBpbmNsdWRpbmcgdGhlICcuLi4nLgogICAgICAgIGxldCBiYXNlVGV4dCA9IHR4dE5vZGUudGV4dENvbnRlbnQuc3Vic3RyKDAsIGluZGV4KTsKICAgICAgICBkbyB7CiAgICAgICAgICAgIGJhc2VUZXh0ID0gYmFzZVRleHQuc3Vic3RyKDAsIGJhc2VUZXh0Lmxlbmd0aCAtIDEpOwogICAgICAgICAgICAvLyBSZWNvbXB1dGUgdGV4dCBsZW5ndGguCiAgICAgICAgICAgIHR4dE5vZGUudGV4dENvbnRlbnQgPSBiYXNlVGV4dCArICcuLi4nOwogICAgICAgICAgICBjb21wdXRlZFR4dExlbmd0aCA9IHR4dE5vZGUuZ2V0Q29tcHV0ZWRUZXh0TGVuZ3RoKCk7CiAgICAgICAgfSB3aGlsZSAoY29tcHV0ZWRUeHRMZW5ndGggPiBtYXhMZW5ndGggJiYgYmFzZVRleHQubGVuZ3RoID4gMCk7CiAgICAgICAgLy8gQWRkIHRvb2x0aXAgd2l0aCBmdWxsIG5hbWUgYW5kIHJldHVybi4KICAgICAgICByZXR1cm4gdHh0RWxlbWVudFNlbGVjdGlvbi5hcHBlbmQoJ3RpdGxlJykudGV4dChsYWJlbENvbnRlbnQpOwogICAgfQogICAgLyoqCiAgICAgKiBkMyBzY2FsZSB1c2VkIGZvciBzaXppbmcgZm9udCBvZiBsYWJlbHMsIHVzZWQgYnkgbGFiZWxCdWlsZCwKICAgICAqIGluaXRpYWxpemVkIG9uY2UgYnkgZ2V0TGFiZWxGb250U2NhbGUuCiAgICAgKi8KICAgIGxldCBmb250U2NhbGUgPSBudWxsOwogICAgZnVuY3Rpb24gZ2V0TGFiZWxGb250U2NhbGUoc2NlbmVFbGVtZW50KSB7CiAgICAgICAgaWYgKCFmb250U2NhbGUpIHsKICAgICAgICAgICAgZm9udFNjYWxlID0gbGluZWFyJDIoKQogICAgICAgICAgICAgICAgLmRvbWFpbihbCiAgICAgICAgICAgICAgICBzY2VuZUVsZW1lbnQubWF4TWV0YW5vZGVMYWJlbExlbmd0aExhcmdlRm9udCwKICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5tYXhNZXRhbm9kZUxhYmVsTGVuZ3RoLAogICAgICAgICAgICBdKQogICAgICAgICAgICAgICAgLnJhbmdlKFsKICAgICAgICAgICAgICAgIHNjZW5lRWxlbWVudC5tYXhNZXRhbm9kZUxhYmVsTGVuZ3RoRm9udFNpemUsCiAgICAgICAgICAgICAgICBzY2VuZUVsZW1lbnQubWluTWV0YW5vZGVMYWJlbExlbmd0aEZvbnRTaXplLAogICAgICAgICAgICBdKQogICAgICAgICAgICAgICAgLmNsYW1wKHRydWUpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZm9udFNjYWxlOwogICAgfQogICAgLyoqCiAgICAgKiBTZXQgbGFiZWwgcG9zaXRpb24gb2YgYSBnaXZlbiBub2RlIGdyb3VwCiAgICAgKi8KICAgIGZ1bmN0aW9uIGxhYmVsUG9zaXRpb24obm9kZUdyb3VwLCBjeCwgY3ksIHlPZmZzZXQpIHsKICAgICAgICBzZWxlY3RDaGlsZCQxKG5vZGVHcm91cCwgJ3RleHQnLCBDbGFzcyQxLk5vZGUuTEFCRUwpCiAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgLmF0dHIoJ3gnLCBjeCkKICAgICAgICAgICAgLmF0dHIoJ3knLCBjeSArIHlPZmZzZXQpOwogICAgfQogICAgLyoqCiAgICAgKiBTZWxlY3Qgb3IgYXBwZW5kL2luc2VydCBzaGFwZSBmb3IgYSBub2RlIGFuZCBhc3NpZ24gcmVuZGVyTm9kZQogICAgICogYXMgdGhlIHNoYXBlJ3MgZGF0YS4KICAgICAqCiAgICAgKiBAcGFyYW0gbm9kZUdyb3VwCiAgICAgKiBAcGFyYW0gZCBSZW5kZXIgbm9kZSBpbmZvcm1hdGlvbi4KICAgICAqIEBwYXJhbSBub2RlQ2xhc3MgY2xhc3MgZm9yIHRoZSBlbGVtZW50LgogICAgICogQHJldHVybiBTZWxlY3Rpb24gb2YgdGhlIHNoYXBlLgogICAgICovCiAgICBmdW5jdGlvbiBidWlsZFNoYXBlKG5vZGVHcm91cCwgZCwgbm9kZUNsYXNzKSB7CiAgICAgICAgLy8gQ3JlYXRlIGEgZ3JvdXAgdG8gaG91c2UgdGhlIHVuZGVybHlpbmcgdmlzdWFsIGVsZW1lbnRzLgogICAgICAgIGxldCBzaGFwZUdyb3VwID0gc2VsZWN0T3JDcmVhdGVDaGlsZChub2RlR3JvdXAsICdnJywgbm9kZUNsYXNzKTsKICAgICAgICAvLyBUT0RPOiBET00gc3RydWN0dXJlIHNob3VsZCBiZSB0ZW1wbGF0ZWQgaW4gSFRNTCBzb21ld2hlcmUsIG5vdCBKUy4KICAgICAgICBzd2l0Y2ggKGQubm9kZS50eXBlKSB7CiAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuT1A6CiAgICAgICAgICAgICAgICBjb25zdCBvcE5vZGUgPSBkLm5vZGU7CiAgICAgICAgICAgICAgICBpZiAobG9kYXNoLmlzTnVtYmVyKG9wTm9kZS5mdW5jdGlvbklucHV0SW5kZXgpIHx8CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmlzTnVtYmVyKG9wTm9kZS5mdW5jdGlvbk91dHB1dEluZGV4KSkgewogICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgaXMgaW5wdXQgb3Igb3V0cHV0IGFyZyBmb3IgYSBUZW5zb3JGbG93IGZ1bmN0aW9uLiBVc2UgYSBzcGVjaWFsCiAgICAgICAgICAgICAgICAgICAgLy8gc2hhcGUgKGEgdHJpYW5nbGUpIGZvciB0aGVtLgogICAgICAgICAgICAgICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2hhcGVHcm91cCwgJ3BvbHlnb24nLCBDbGFzcyQxLk5vZGUuQ09MT1JfVEFSR0VUKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2hhcGVHcm91cCwgJ2VsbGlwc2UnLCBDbGFzcyQxLk5vZGUuQ09MT1JfVEFSR0VUKTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLlNFUklFUzoKICAgICAgICAgICAgICAgIC8vIENob29zZSB0aGUgY29ycmVjdCBzdGFtcCB0byB1c2UgdG8gcmVwcmVzZW50IHRoaXMgc2VyaWVzLgogICAgICAgICAgICAgICAgbGV0IHN0YW1wVHlwZSA9ICdhbm5vdGF0aW9uJzsKICAgICAgICAgICAgICAgIGxldCBncm91cE5vZGVJbmZvID0gZDsKICAgICAgICAgICAgICAgIGlmIChncm91cE5vZGVJbmZvLmNvcmVHcmFwaCkgewogICAgICAgICAgICAgICAgICAgIHN0YW1wVHlwZSA9IGdyb3VwTm9kZUluZm8ubm9kZS5oYXNOb25Db250cm9sRWRnZXMKICAgICAgICAgICAgICAgICAgICAgICAgPyAndmVydGljYWwnCiAgICAgICAgICAgICAgICAgICAgICAgIDogJ2hvcml6b250YWwnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IGNsYXNzTGlzdCA9IFtDbGFzcyQxLk5vZGUuQ09MT1JfVEFSR0VUXTsKICAgICAgICAgICAgICAgIGlmIChncm91cE5vZGVJbmZvLmlzRmFkZWRPdXQpIHsKICAgICAgICAgICAgICAgICAgICBjbGFzc0xpc3QucHVzaCgnZmFkZWQtZWxsaXBzZScpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgc2VsZWN0T3JDcmVhdGVDaGlsZChzaGFwZUdyb3VwLCAndXNlJywgY2xhc3NMaXN0KQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCd4bGluazpocmVmJywgJyNvcC1zZXJpZXMtJyArIHN0YW1wVHlwZSArICctc3RhbXAnKTsKICAgICAgICAgICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2hhcGVHcm91cCwgJ3JlY3QnLCBDbGFzcyQxLk5vZGUuQ09MT1JfVEFSR0VUKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdyeCcsIGQucmFkaXVzKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdyeScsIGQucmFkaXVzKTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLkJSSURHRToKICAgICAgICAgICAgICAgIHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2hhcGVHcm91cCwgJ3JlY3QnLCBDbGFzcyQxLk5vZGUuQ09MT1JfVEFSR0VUKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdyeCcsIGQucmFkaXVzKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdyeScsIGQucmFkaXVzKTsKICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICBzZWxlY3RPckNyZWF0ZUNoaWxkKHNoYXBlR3JvdXAsICdyZWN0JywgQ2xhc3MkMS5Ob2RlLkNPTE9SX1RBUkdFVCkKICAgICAgICAgICAgICAgICAgICAuYXR0cigncngnLCBkLnJhZGl1cykKICAgICAgICAgICAgICAgICAgICAuYXR0cigncnknLCBkLnJhZGl1cyk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgZGVmYXVsdDoKICAgICAgICAgICAgICAgIHRocm93IEVycm9yKCdVbnJlY29nbml6ZWQgbm9kZSB0eXBlOiAnICsgZC5ub2RlLnR5cGUpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gc2hhcGVHcm91cDsKICAgIH0KICAgIGZ1bmN0aW9uIG5vZGVDbGFzcyhkKSB7CiAgICAgICAgc3dpdGNoIChkLm5vZGUudHlwZSkgewogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk9QOgogICAgICAgICAgICAgICAgcmV0dXJuIENsYXNzJDEuT1BOT0RFOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6CiAgICAgICAgICAgICAgICByZXR1cm4gQ2xhc3MkMS5NRVRBTk9ERTsKICAgICAgICAgICAgY2FzZSBOb2RlVHlwZS5TRVJJRVM6CiAgICAgICAgICAgICAgICByZXR1cm4gQ2xhc3MkMS5TRVJJRVNOT0RFOwogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLkJSSURHRToKICAgICAgICAgICAgICAgIHJldHVybiBDbGFzcyQxLkJSSURHRU5PREU7CiAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuRUxMSVBTSVM6CiAgICAgICAgICAgICAgICByZXR1cm4gQ2xhc3MkMS5FTExJUFNJU05PREU7CiAgICAgICAgfQogICAgICAgIHRocm93IEVycm9yKCdVbnJlY29nbml6ZWQgbm9kZSB0eXBlOiAnICsgZC5ub2RlLnR5cGUpOwogICAgfQogICAgLyoqIE1vZGlmeSBub2RlIGFuZCBpdHMgc3Vic2NlbmUgYW5kIGl0cyBsYWJlbCdzIHBvc2l0aW9uYWwgYXR0cmlidXRlcyAqLwogICAgZnVuY3Rpb24gcG9zaXRpb24kMyhub2RlR3JvdXAsIGQpIHsKICAgICAgICBsZXQgc2hhcGVHcm91cCA9IHNlbGVjdENoaWxkJDEobm9kZUdyb3VwLCAnZycsIENsYXNzJDEuTm9kZS5TSEFQRSk7CiAgICAgICAgbGV0IGN4ID0gY29tcHV0ZUNYUG9zaXRpb25PZk5vZGVTaGFwZShkKTsKICAgICAgICBzd2l0Y2ggKGQubm9kZS50eXBlKSB7CiAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuT1A6IHsKICAgICAgICAgICAgICAgIC8vIHBvc2l0aW9uIHNoYXBlCiAgICAgICAgICAgICAgICBjb25zdCBvcE5vZGUgPSBkLm5vZGU7CiAgICAgICAgICAgICAgICBpZiAobG9kYXNoLmlzTnVtYmVyKG9wTm9kZS5mdW5jdGlvbklucHV0SW5kZXgpIHx8CiAgICAgICAgICAgICAgICAgICAgbG9kYXNoLmlzTnVtYmVyKG9wTm9kZS5mdW5jdGlvbk91dHB1dEluZGV4KSkgewogICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgc2hhcGUgcmVwcmVzZW50cyB0aGUgaW5wdXQgaW50byBvciBvdXRwdXQgb3V0IG9mIGEgVGVuc29yRmxvdwogICAgICAgICAgICAgICAgICAgIC8vIGZ1bmN0aW9uLgogICAgICAgICAgICAgICAgICAgIGxldCBzaGFwZSA9IHNlbGVjdENoaWxkJDEoc2hhcGVHcm91cCwgJ3BvbHlnb24nKTsKICAgICAgICAgICAgICAgICAgICBwb3NpdGlvblRyaWFuZ2xlKHNoYXBlLCBkLngsIGQueSwgZC5jb3JlQm94LndpZHRoLCBkLmNvcmVCb3guaGVpZ2h0KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGxldCBzaGFwZSA9IHNlbGVjdENoaWxkJDEoc2hhcGVHcm91cCwgJ2VsbGlwc2UnKTsKICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbkVsbGlwc2Uoc2hhcGUsIGN4LCBkLnksIGQuY29yZUJveC53aWR0aCwgZC5jb3JlQm94LmhlaWdodCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBsYWJlbFBvc2l0aW9uKG5vZGVHcm91cCwgY3gsIGQueSwgZC5sYWJlbE9mZnNldCk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBjYXNlIE5vZGVUeXBlLk1FVEE6IHsKICAgICAgICAgICAgICAgIC8vIHBvc2l0aW9uIHNoYXBlCiAgICAgICAgICAgICAgICBsZXQgc2hhcGVzID0gc2hhcGVHcm91cC5zZWxlY3RBbGwoJ3JlY3QnKTsKICAgICAgICAgICAgICAgIGlmIChkLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcG9zaXRpb25SZWN0KHNoYXBlcywgZC54LCBkLnksIGQud2lkdGgsIGQuaGVpZ2h0KTsKICAgICAgICAgICAgICAgICAgICBzdWJzY2VuZVBvc2l0aW9uKG5vZGVHcm91cCwgZCk7CiAgICAgICAgICAgICAgICAgICAgLy8gUHV0IHRoZSBsYWJlbCBvbiB0b3AuCiAgICAgICAgICAgICAgICAgICAgbGFiZWxQb3NpdGlvbihub2RlR3JvdXAsIGN4LCBkLnksIC1kLmhlaWdodCAvIDIgKyBkLmxhYmVsSGVpZ2h0IC8gMik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBwb3NpdGlvblJlY3Qoc2hhcGVzLCBjeCwgZC55LCBkLmNvcmVCb3gud2lkdGgsIGQuY29yZUJveC5oZWlnaHQpOwogICAgICAgICAgICAgICAgICAgIC8vIFBsYWNlIHRoZSBsYWJlbCBpbiB0aGUgbWlkZGxlLgogICAgICAgICAgICAgICAgICAgIGxhYmVsUG9zaXRpb24obm9kZUdyb3VwLCBjeCwgZC55LCAwKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuU0VSSUVTOiB7CiAgICAgICAgICAgICAgICBsZXQgc2hhcGUgPSBzZWxlY3RDaGlsZCQxKHNoYXBlR3JvdXAsICd1c2UnKTsKICAgICAgICAgICAgICAgIGlmIChkLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcG9zaXRpb25SZWN0KHNoYXBlLCBkLngsIGQueSwgZC53aWR0aCwgZC5oZWlnaHQpOwogICAgICAgICAgICAgICAgICAgIHN1YnNjZW5lUG9zaXRpb24obm9kZUdyb3VwLCBkKTsKICAgICAgICAgICAgICAgICAgICAvLyBwdXQgbGFiZWwgb24gdG9wCiAgICAgICAgICAgICAgICAgICAgbGFiZWxQb3NpdGlvbihub2RlR3JvdXAsIGN4LCBkLnksIC1kLmhlaWdodCAvIDIgKyBkLmxhYmVsSGVpZ2h0IC8gMik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBwb3NpdGlvblJlY3Qoc2hhcGUsIGN4LCBkLnksIGQuY29yZUJveC53aWR0aCwgZC5jb3JlQm94LmhlaWdodCk7CiAgICAgICAgICAgICAgICAgICAgbGFiZWxQb3NpdGlvbihub2RlR3JvdXAsIGN4LCBkLnksIGQubGFiZWxPZmZzZXQpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSBOb2RlVHlwZS5CUklER0U6IHsKICAgICAgICAgICAgICAgIC8vIHBvc2l0aW9uIHNoYXBlCiAgICAgICAgICAgICAgICAvLyBOT1RFOiBJbiByZWFsaXR5LCB0aGVzZSB3aWxsIG5vdCBiZSB2aXNpYmxlLCBidXQgaXQgaGVscHMgdG8gcHV0IHRoZW0KICAgICAgICAgICAgICAgIC8vIGluIHRoZSBjb3JyZWN0IHBvc2l0aW9uIGZvciBkZWJ1Z2dpbmcgcHVycG9zZXMuCiAgICAgICAgICAgICAgICBsZXQgc2hhcGUgPSBzZWxlY3RDaGlsZCQxKHNoYXBlR3JvdXAsICdyZWN0Jyk7CiAgICAgICAgICAgICAgICBwb3NpdGlvblJlY3Qoc2hhcGUsIGQueCwgZC55LCBkLndpZHRoLCBkLmhlaWdodCk7CiAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBkZWZhdWx0OiB7CiAgICAgICAgICAgICAgICB0aHJvdyBFcnJvcignVW5yZWNvZ25pemVkIG5vZGUgdHlwZTogJyArIGQubm9kZS50eXBlKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH0KICAgIC8qKiBFbnVtIHNwZWNpZnlpbmcgdGhlIG9wdGlvbnMgdG8gY29sb3Igbm9kZXMgYnkgKi8KICAgIHZhciBDb2xvckJ5OwogICAgKGZ1bmN0aW9uIChDb2xvckJ5KSB7CiAgICAgICAgQ29sb3JCeVtDb2xvckJ5WyJTVFJVQ1RVUkUiXSA9IDBdID0gIlNUUlVDVFVSRSI7CiAgICAgICAgQ29sb3JCeVtDb2xvckJ5WyJERVZJQ0UiXSA9IDFdID0gIkRFVklDRSI7CiAgICAgICAgQ29sb3JCeVtDb2xvckJ5WyJYTEFfQ0xVU1RFUiJdID0gMl0gPSAiWExBX0NMVVNURVIiOwogICAgICAgIENvbG9yQnlbQ29sb3JCeVsiQ09NUFVURV9USU1FIl0gPSAzXSA9ICJDT01QVVRFX1RJTUUiOwogICAgICAgIENvbG9yQnlbQ29sb3JCeVsiTUVNT1JZIl0gPSA0XSA9ICJNRU1PUlkiOwogICAgICAgIENvbG9yQnlbQ29sb3JCeVsiT1BfQ09NUEFUSUJJTElUWSJdID0gNV0gPSAiT1BfQ09NUEFUSUJJTElUWSI7CiAgICB9KShDb2xvckJ5IHx8IChDb2xvckJ5ID0ge30pKTsKICAgIGZ1bmN0aW9uIGdldEdyYWRpZW50KGlkLCBjb2xvcnMsIHN2Z1Jvb3QpIHsKICAgICAgICBsZXQgZXNjYXBlZElkID0gZXNjYXBlUXVlcnlTZWxlY3RvcihpZCk7CiAgICAgICAgaWYgKCFzdmdSb290KQogICAgICAgICAgICByZXR1cm4gYHVybCgjJHtlc2NhcGVkSWR9KWA7CiAgICAgICAgbGV0ICRzdmdSb290ID0gc2VsZWN0KHN2Z1Jvb3QpOwogICAgICAgIGxldCBncmFkaWVudERlZnMgPSAkc3ZnUm9vdC5zZWxlY3QoJ2RlZnMjX2dyYXBoLWdyYWRpZW50cycpOwogICAgICAgIGlmIChncmFkaWVudERlZnMuZW1wdHkoKSkgewogICAgICAgICAgICBncmFkaWVudERlZnMgPSAkc3ZnUm9vdC5hcHBlbmQoJ2RlZnMnKS5hdHRyKCdpZCcsICdfZ3JhcGgtZ3JhZGllbnRzJyk7CiAgICAgICAgfQogICAgICAgIGxldCBsaW5lYXJHcmFkaWVudCA9IGdyYWRpZW50RGVmcy5zZWxlY3QoJ2xpbmVhckdyYWRpZW50IycgKyBlc2NhcGVkSWQpOwogICAgICAgIC8vIElmIHRoZSBsaW5lYXIgZ3JhZGllbnQgaXMgbm90IHRoZXJlIHlldCwgY3JlYXRlIGl0LgogICAgICAgIGlmIChsaW5lYXJHcmFkaWVudC5lbXB0eSgpKSB7CiAgICAgICAgICAgIGxpbmVhckdyYWRpZW50ID0gZ3JhZGllbnREZWZzLmFwcGVuZCgnbGluZWFyR3JhZGllbnQnKS5hdHRyKCdpZCcsIGlkKTsKICAgICAgICAgICAgLy8gUmUtY3JlYXRlIHRoZSBzdG9wcyBvZiB0aGUgbGluZWFyIGdyYWRpZW50LgogICAgICAgICAgICBsaW5lYXJHcmFkaWVudC5zZWxlY3RBbGwoJyonKS5yZW1vdmUoKTsKICAgICAgICAgICAgbGV0IGN1bXVsYXRpdmVQcm9wb3J0aW9uID0gMDsKICAgICAgICAgICAgLy8gRm9yIGVhY2ggY29sb3IsIGNyZWF0ZSBhIHN0b3AgdXNpbmcgdGhlIHByb3BvcnRpb24gb2YgdGhhdCBkZXZpY2UuCiAgICAgICAgICAgIGxvZGFzaC5lYWNoKGNvbG9ycywgKGQpID0+IHsKICAgICAgICAgICAgICAgIGxldCBjb2xvciA9IGQuY29sb3I7CiAgICAgICAgICAgICAgICBsaW5lYXJHcmFkaWVudAogICAgICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3N0b3AnKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdvZmZzZXQnLCBjdW11bGF0aXZlUHJvcG9ydGlvbikKICAgICAgICAgICAgICAgICAgICAuYXR0cignc3RvcC1jb2xvcicsIGNvbG9yKTsKICAgICAgICAgICAgICAgIGxpbmVhckdyYWRpZW50CiAgICAgICAgICAgICAgICAgICAgLmFwcGVuZCgnc3RvcCcpCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoJ29mZnNldCcsIGN1bXVsYXRpdmVQcm9wb3J0aW9uICsgZC5wcm9wb3J0aW9uKQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdzdG9wLWNvbG9yJywgY29sb3IpOwogICAgICAgICAgICAgICAgY3VtdWxhdGl2ZVByb3BvcnRpb24gKz0gZC5wcm9wb3J0aW9uOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGB1cmwoIyR7ZXNjYXBlZElkfSlgOwogICAgfQogICAgZnVuY3Rpb24gcmVtb3ZlR3JhZGllbnREZWZpbml0aW9ucyhzdmdSb290KSB7CiAgICAgICAgc2VsZWN0KHN2Z1Jvb3QpLnNlbGVjdCgnZGVmcyNfZ3JhcGgtZ3JhZGllbnRzJykucmVtb3ZlKCk7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgdGhlIGZpbGwgY29sb3IgZm9yIHRoZSBub2RlIGdpdmVuIGl0cyBzdGF0ZSBhbmQgdGhlICdjb2xvciBieScKICAgICAqIG9wdGlvbi4KICAgICAqIFRha2VzIGluIG9wdGlvbmFsIHN2Z1Jvb3QsIHdoZW4gcGFzc2VkLCB0aGF0IHBvcHVsYXRlcyBTVkcgZGVmaW5pdGlvbnMKICAgICAqIGZvciB0aGUgZmlsbCBpbnNpZGUgdGhlIHN2Z1Jvb3Qgd2hlbiBuZWNlc3NhcnkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldEZpbGxGb3JOb2RlKHRlbXBsYXRlSW5kZXgsIGNvbG9yQnksIHJlbmRlckluZm8sIGlzRXhwYW5kZWQsIHN2Z1Jvb3QpIHsKICAgICAgICBsZXQgY29sb3JQYXJhbXMgPSBNZXRhbm9kZUNvbG9yczsKICAgICAgICBzd2l0Y2ggKGNvbG9yQnkpIHsKICAgICAgICAgICAgY2FzZSBDb2xvckJ5LlNUUlVDVFVSRToKICAgICAgICAgICAgICAgIGlmIChyZW5kZXJJbmZvLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICAgICAgICAgIGxldCB0aWQgPSByZW5kZXJJbmZvLm5vZGUudGVtcGxhdGVJZDsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGlkID09PSBudWxsCiAgICAgICAgICAgICAgICAgICAgICAgID8gY29sb3JQYXJhbXMuVU5LTk9XTgogICAgICAgICAgICAgICAgICAgICAgICA6IGNvbG9yUGFyYW1zLlNUUlVDVFVSRV9QQUxFVFRFKHRlbXBsYXRlSW5kZXgodGlkKSwgaXNFeHBhbmRlZCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChyZW5kZXJJbmZvLm5vZGUudHlwZSA9PT0gTm9kZVR5cGUuU0VSSUVTKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gSWYgZXhwYW5kZWQsIHdlJ3JlIHNob3dpbmcgdGhlIGJhY2tncm91bmQgcmVjdCwgd2hpY2ggd2Ugd2FudCB0bwogICAgICAgICAgICAgICAgICAgIC8vIGFwcGVhciBncmF5LiBPdGhlcndpc2Ugd2UncmUgc2hvd2luZyBhIHN0YWNrIG9mIGVsbGlwc2VzIHdoaWNoIHdlCiAgICAgICAgICAgICAgICAgICAgLy8gd2FudCB0byBzaG93IHdoaXRlLgogICAgICAgICAgICAgICAgICAgIHJldHVybiBpc0V4cGFuZGVkID8gY29sb3JQYXJhbXMuRVhQQU5ERURfQ09MT1IgOiAnd2hpdGUnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAocmVuZGVySW5mby5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLkJSSURHRSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiByZW5kZXJJbmZvLnN0cnVjdHVyYWwKICAgICAgICAgICAgICAgICAgICAgICAgPyAnI2YwZScKICAgICAgICAgICAgICAgICAgICAgICAgOiByZW5kZXJJbmZvLm5vZGUuaW5ib3VuZAogICAgICAgICAgICAgICAgICAgICAgICAgICAgPyAnIzBlZicKICAgICAgICAgICAgICAgICAgICAgICAgICAgIDogJyNmZTAnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSBpZiAobG9kYXNoLmlzTnVtYmVyKHJlbmRlckluZm8ubm9kZS5mdW5jdGlvbklucHV0SW5kZXgpKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyBpcyBhbiBpbnB1dCBvZiBhIFRlbnNvckZsb3cgZnVuY3Rpb24uCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICcjNzk1NTQ4JzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGxvZGFzaC5pc051bWJlcihyZW5kZXJJbmZvLm5vZGUuZnVuY3Rpb25PdXRwdXRJbmRleCkpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIGlzIGFuIG91dHB1dCBvZiBhIFRlbnNvckZsb3cgZnVuY3Rpb24uCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICcjMDA5Njg4JzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIC8vIE9wIG5vZGVzIGFyZSB3aGl0ZS4KICAgICAgICAgICAgICAgICAgICByZXR1cm4gJ3doaXRlJzsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgY2FzZSBDb2xvckJ5LkRFVklDRToKICAgICAgICAgICAgICAgIGlmIChyZW5kZXJJbmZvLmRldmljZUNvbG9ycyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gUmV0dXJuIHRoZSBodWUgZm9yIHVua25vd24gZGV2aWNlLgogICAgICAgICAgICAgICAgICAgIHJldHVybiBjb2xvclBhcmFtcy5VTktOT1dOOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIGlzRXhwYW5kZWQKICAgICAgICAgICAgICAgICAgICA/IGNvbG9yUGFyYW1zLkVYUEFOREVEX0NPTE9SCiAgICAgICAgICAgICAgICAgICAgOiBnZXRHcmFkaWVudCgnZGV2aWNlLScgKyByZW5kZXJJbmZvLm5vZGUubmFtZSwgcmVuZGVySW5mby5kZXZpY2VDb2xvcnMsIHN2Z1Jvb3QpOwogICAgICAgICAgICBjYXNlIENvbG9yQnkuWExBX0NMVVNURVI6CiAgICAgICAgICAgICAgICBpZiAocmVuZGVySW5mby54bGFDbHVzdGVyQ29sb3JzID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAvLyBSZXR1cm4gdGhlIGh1ZSBmb3IgdW5rbm93biB4bGFDbHVzdGVyLgogICAgICAgICAgICAgICAgICAgIHJldHVybiBjb2xvclBhcmFtcy5VTktOT1dOOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIGlzRXhwYW5kZWQKICAgICAgICAgICAgICAgICAgICA/IGNvbG9yUGFyYW1zLkVYUEFOREVEX0NPTE9SCiAgICAgICAgICAgICAgICAgICAgOiBnZXRHcmFkaWVudCgneGxhLScgKyByZW5kZXJJbmZvLm5vZGUubmFtZSwgcmVuZGVySW5mby54bGFDbHVzdGVyQ29sb3JzLCBzdmdSb290KTsKICAgICAgICAgICAgY2FzZSBDb2xvckJ5LkNPTVBVVEVfVElNRToKICAgICAgICAgICAgICAgIHJldHVybiBpc0V4cGFuZGVkCiAgICAgICAgICAgICAgICAgICAgPyBjb2xvclBhcmFtcy5FWFBBTkRFRF9DT0xPUgogICAgICAgICAgICAgICAgICAgIDogcmVuZGVySW5mby5jb21wdXRlVGltZUNvbG9yIHx8IGNvbG9yUGFyYW1zLlVOS05PV047CiAgICAgICAgICAgIGNhc2UgQ29sb3JCeS5NRU1PUlk6CiAgICAgICAgICAgICAgICByZXR1cm4gaXNFeHBhbmRlZAogICAgICAgICAgICAgICAgICAgID8gY29sb3JQYXJhbXMuRVhQQU5ERURfQ09MT1IKICAgICAgICAgICAgICAgICAgICA6IHJlbmRlckluZm8ubWVtb3J5Q29sb3IgfHwgY29sb3JQYXJhbXMuVU5LTk9XTjsKICAgICAgICAgICAgY2FzZSBDb2xvckJ5Lk9QX0NPTVBBVElCSUxJVFk6CiAgICAgICAgICAgICAgICBpZiAocmVuZGVySW5mby5jb21wYXRpYmlsaXR5Q29sb3JzID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAvLyBSZXR1cm4gdGhlIGh1ZSBmb3IgdW5rbm93biBjb21wYXRpYmlsaXR5IGluZm8uCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGNvbG9yUGFyYW1zLlVOS05PV047CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gaXNFeHBhbmRlZAogICAgICAgICAgICAgICAgICAgID8gY29sb3JQYXJhbXMuRVhQQU5ERURfQ09MT1IKICAgICAgICAgICAgICAgICAgICA6IGdldEdyYWRpZW50KCdvcC1jb21wYXQtJyArIHJlbmRlckluZm8ubm9kZS5uYW1lLCByZW5kZXJJbmZvLmNvbXBhdGliaWxpdHlDb2xvcnMsIHN2Z1Jvb3QpOwogICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdVbmtub3duIGNhc2UgdG8gY29sb3Igbm9kZXMgYnknKTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIE1vZGlmeSBub2RlIHN0eWxlIGJ5IHRvZ2dsaW5nIGNsYXNzIGFuZCBhc3NpZ24gYXR0cmlidXRlcyAob25seSBmb3IgdGhpbmdzCiAgICAgKiB0aGF0IGNhbid0IGJlIGRvbmUgaW4gY3NzKS4KICAgICAqLwogICAgZnVuY3Rpb24gc3R5bGl6ZSQxKG5vZGVHcm91cCwgcmVuZGVySW5mbywgc2NlbmVFbGVtZW50LCBub2RlQ2xhc3MpIHsKICAgICAgICBub2RlQ2xhc3MgPSBub2RlQ2xhc3MgfHwgQ2xhc3MkMS5Ob2RlLlNIQVBFOwogICAgICAgIGxldCBpc0hpZ2hsaWdodGVkID0gc2NlbmVFbGVtZW50LmlzTm9kZUhpZ2hsaWdodGVkKHJlbmRlckluZm8ubm9kZS5uYW1lKTsKICAgICAgICBsZXQgaXNTZWxlY3RlZCA9IHNjZW5lRWxlbWVudC5pc05vZGVTZWxlY3RlZChyZW5kZXJJbmZvLm5vZGUubmFtZSk7CiAgICAgICAgbGV0IGlzRXh0cmFjdCA9IHJlbmRlckluZm8uaXNJbkV4dHJhY3QgfHwKICAgICAgICAgICAgcmVuZGVySW5mby5pc091dEV4dHJhY3QgfHwKICAgICAgICAgICAgcmVuZGVySW5mby5pc0xpYnJhcnlGdW5jdGlvbjsKICAgICAgICBsZXQgaXNFeHBhbmRlZCA9IHJlbmRlckluZm8uZXhwYW5kZWQgJiYgbm9kZUNsYXNzICE9PSBDbGFzcyQxLkFubm90YXRpb24uTk9ERTsKICAgICAgICBsZXQgaXNGYWRlZE91dCA9IHJlbmRlckluZm8uaXNGYWRlZE91dDsKICAgICAgICBub2RlR3JvdXAuY2xhc3NlZCgnaGlnaGxpZ2h0ZWQnLCBpc0hpZ2hsaWdodGVkKTsKICAgICAgICBub2RlR3JvdXAuY2xhc3NlZCgnc2VsZWN0ZWQnLCBpc1NlbGVjdGVkKTsKICAgICAgICBub2RlR3JvdXAuY2xhc3NlZCgnZXh0cmFjdCcsIGlzRXh0cmFjdCk7CiAgICAgICAgbm9kZUdyb3VwLmNsYXNzZWQoJ2V4cGFuZGVkJywgaXNFeHBhbmRlZCk7CiAgICAgICAgbm9kZUdyb3VwLmNsYXNzZWQoJ2ZhZGVkJywgaXNGYWRlZE91dCk7CiAgICAgICAgLy8gTWFpbiBub2RlIGFsd2F5cyBleGlzdHMgaGVyZSBhbmQgaXQgd2lsbCBiZSByZWFjaGVkIGJlZm9yZSBzdWJzY2VuZSwKICAgICAgICAvLyBzbyBkMyBzZWxlY3Rpb24gaXMgZmluZSBoZXJlLgogICAgICAgIGxldCBub2RlID0gbm9kZUdyb3VwLnNlbGVjdCgnLicgKyBub2RlQ2xhc3MgKyAnIC4nICsgQ2xhc3MkMS5Ob2RlLkNPTE9SX1RBUkdFVCk7CiAgICAgICAgbGV0IGZpbGxDb2xvciA9IGdldEZpbGxGb3JOb2RlKHNjZW5lRWxlbWVudC50ZW1wbGF0ZUluZGV4LCBDb2xvckJ5W3NjZW5lRWxlbWVudC5jb2xvckJ5LnRvVXBwZXJDYXNlKCldLCByZW5kZXJJbmZvLCBpc0V4cGFuZGVkLCBzY2VuZUVsZW1lbnQuZ2V0R3JhcGhTdmdSb290KCkpOwogICAgICAgIG5vZGUuc3R5bGUoJ2ZpbGwnLCBmaWxsQ29sb3IpOwogICAgICAgIC8vIENob29zZSBvdXRsaW5lIHRvIGJlIGRhcmtlciB2ZXJzaW9uIG9mIG5vZGUgY29sb3IgaWYgdGhlIG5vZGUgaXMgYSBzaW5nbGUKICAgICAgICAvLyBjb2xvciBhbmQgaXMgbm90IHNlbGVjdGVkLgogICAgICAgIG5vZGUuc3R5bGUoJ3N0cm9rZScsIGlzU2VsZWN0ZWQgPyBudWxsIDogZ2V0U3Ryb2tlRm9yRmlsbChmaWxsQ29sb3IpKTsKICAgIH0KICAgIC8qKgogICAgICogR2l2ZW4gYSBub2RlJ3MgZmlsbCBjb2xvci9ncmFkaWVudCwgZGV0ZXJtaW5lIHRoZSBzdHJva2UgZm9yIHRoZSBub2RlLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRTdHJva2VGb3JGaWxsKGZpbGwpIHsKICAgICAgICAvLyBJZiBub2RlIGlzIGNvbG9yZWQgYnkgYSBncmFkaWVudCwgdGhlbiB1c2UgYSBkYXJrIGdyYXkgb3V0bGluZS4KICAgICAgICByZXR1cm4gZmlsbC5zdWJzdHJpbmcoMCwgMykgPT09ICd1cmwnCiAgICAgICAgICAgID8gTWV0YW5vZGVDb2xvcnMuR1JBRElFTlRfT1VUTElORQogICAgICAgICAgICA6IHJnYihmaWxsKS5kYXJrZXIoKS50b1N0cmluZygpOwogICAgfQogICAgLyoqCiAgICAgKiBGaW5kcyBzZWxlY3RlZCBub2RlIGFuZCBoaWdobGlnaHRzIGFsbCBub2RlcyB3aGljaCBhcmUgcHJvdmlkaW5nIGRpcmVjdAogICAgICogb3IgaW5kaXJlY3QgaW5wdXQgdG8gdGhlIG5vZGUgYW5kIGFsbCBlZGdlcyBjb25uZWN0aW5nIHRoZXNlIG5vZGVzCiAgICAgKiB0b2dldGhlciBhbmQgdG8gdGhlIHNlbGVjdGVkIG5vZGUuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHVwZGF0ZUlucHV0VHJhY2Uoc3ZnUm9vdCwgcmVuZGVyR3JhcGhJbmZvLCBzZWxlY3RlZE5vZGVOYW1lLCB0cmFjZUlucHV0cykgewogICAgICAgIC8vIFJlc2V0IGFsbCBzdHlsaW5nLgogICAgICAgIGNvbnN0IHN2ZyA9IHNlbGVjdChzdmdSb290KTsKICAgICAgICBzdmcuc2VsZWN0QWxsKCcuaW5wdXQtaGlnaGxpZ2h0JykuY2xhc3NlZCgnaW5wdXQtaGlnaGxpZ2h0JywgZmFsc2UpOwogICAgICAgIHN2Zy5zZWxlY3RBbGwoJy5ub24taW5wdXQnKS5jbGFzc2VkKCdub24taW5wdXQnLCBmYWxzZSk7CiAgICAgICAgc3ZnLnNlbGVjdEFsbCgnLmlucHV0LXBhcmVudCcpLmNsYXNzZWQoJ2lucHV0LXBhcmVudCcsIGZhbHNlKTsKICAgICAgICBzdmcuc2VsZWN0QWxsKCcuaW5wdXQtY2hpbGQnKS5jbGFzc2VkKCdpbnB1dC1jaGlsZCcsIGZhbHNlKTsKICAgICAgICBzdmcuc2VsZWN0QWxsKCcuaW5wdXQtZWRnZS1oaWdobGlnaHQnKS5jbGFzc2VkKCdpbnB1dC1lZGdlLWhpZ2hsaWdodCcsIGZhbHNlKTsKICAgICAgICBzdmcKICAgICAgICAgICAgLnNlbGVjdEFsbCgnLm5vbi1pbnB1dC1lZGdlLWhpZ2hsaWdodCcpCiAgICAgICAgICAgIC5jbGFzc2VkKCdub24taW5wdXQtZWRnZS1oaWdobGlnaHQnLCBmYWxzZSk7CiAgICAgICAgc3ZnCiAgICAgICAgICAgIC5zZWxlY3RBbGwoJy5pbnB1dC1oaWdobGlnaHQtc2VsZWN0ZWQnKQogICAgICAgICAgICAuY2xhc3NlZCgnaW5wdXQtaGlnaGxpZ2h0LXNlbGVjdGVkJywgZmFsc2UpOwogICAgICAgIC8vIEV4dHJhY3QgY3VycmVudGx5IHNlbGVjdGVkIG5vZGUuIFJldHVybiBpZiBpbnB1dCB0cmFjaW5nIGRpc2FibGVkIG9yIG5vCiAgICAgICAgLy8gbm9kZSBpcyBzZWxlY3RlZC4KICAgICAgICBpZiAoIXJlbmRlckdyYXBoSW5mbyB8fCAhdHJhY2VJbnB1dHMgfHwgIXNlbGVjdGVkTm9kZU5hbWUpIHsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBsZXQgb3BOb2RlcyA9IF9nZXRBbGxDb250YWluZWRPcE5vZGVzKHNlbGVjdGVkTm9kZU5hbWUsIHJlbmRlckdyYXBoSW5mbyk7CiAgICAgICAgbGV0IGFsbFRyYWNlZE5vZGVzID0ge307CiAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlcywgZnVuY3Rpb24gKG5vZGVJbnN0YW5jZSkgewogICAgICAgICAgICBhbGxUcmFjZWROb2RlcyA9IHRyYWNlQWxsSW5wdXRzT2ZPcE5vZGUoc3ZnUm9vdCwgcmVuZGVyR3JhcGhJbmZvLCBub2RlSW5zdGFuY2UsIGFsbFRyYWNlZE5vZGVzKTsKICAgICAgICB9KTsKICAgICAgICAvLyBIaWdobGlnaHQgYWxsIHBhcmVudCBub2RlcyBvZiBlYWNoIE9wTm9kZSBhcyBpbnB1dCBwYXJlbnQgdG8gYWxsb3cKICAgICAgICAvLyBzcGVjaWZpYyBoaWdobGlnaHRpbmcuCiAgICAgICAgbGV0IGhpZ2hsaWdodGVkTm9kZXMgPSBPYmplY3Qua2V5cyhhbGxUcmFjZWROb2Rlcyk7CiAgICAgICAgbGV0IHZpc2libGVOb2RlcyA9IF9maW5kVmlzaWJsZVBhcmVudHNGcm9tT3BOb2RlcyhyZW5kZXJHcmFwaEluZm8sIGhpZ2hsaWdodGVkTm9kZXMpOwogICAgICAgIF9tYXJrUGFyZW50c09mTm9kZXMoc3ZnUm9vdCwgdmlzaWJsZU5vZGVzKTsKICAgICAgICAvLyBBdHRhY2ggY2xhc3MgdG8gYWxsIG5vbi1pbnB1dCBub2RlcyBhbmQgZWRnZXMgZm9yIHN0eWxpbmcuCiAgICAgICAgc3ZnCiAgICAgICAgICAgIC5zZWxlY3RBbGwoJ2cubm9kZTpub3QoLnNlbGVjdGVkKTpub3QoLmlucHV0LWhpZ2hsaWdodCknICsKICAgICAgICAgICAgJzpub3QoLmlucHV0LXBhcmVudCk6bm90KC5pbnB1dC1jaGlsZHJlbiknKQogICAgICAgICAgICAuY2xhc3NlZCgnbm9uLWlucHV0JywgdHJ1ZSkKICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgLy8gTWFyayBhbGwgbm9kZXMgd2l0aCB0aGUgc3BlY2lmaWVkIG5hbWUgYXMgbm9uLWlucHV0cy4gVGhpcwogICAgICAgICAgICAvLyByZXN1bHRzIGluIEFubm90YXRpb24gbm9kZXMgd2hpY2ggYXJlIGF0dGFjaGVkIHRvIGlucHV0cyB0byBiZQogICAgICAgICAgICAvLyB0YWdnZWQgYXMgd2VsbC4KICAgICAgICAgICAgbGV0IG5vZGVOYW1lID0gZC5ub2RlLm5hbWU7CiAgICAgICAgICAgIHN2Zy5zZWxlY3RBbGwoYFtkYXRhLW5hbWU9IiR7bm9kZU5hbWV9Il1gKS5jbGFzc2VkKCdub24taW5wdXQnLCB0cnVlKTsKICAgICAgICB9KTsKICAgICAgICBzdmcKICAgICAgICAgICAgLnNlbGVjdEFsbCgnZy5lZGdlOm5vdCguaW5wdXQtZWRnZS1oaWdobGlnaHQpJykKICAgICAgICAgICAgLmNsYXNzZWQoJ25vbi1pbnB1dC1lZGdlLWhpZ2hsaWdodCcsIHRydWUpOwogICAgfQogICAgLyoqCiAgICAgKiBSZWN1cnNpdmVseSBmaW5kIGFsbCBvcCBub2RlcyBjb250YWluZWQgYnkgdGhlIG5vZGUgaWRlbnRpZmllZCBieSB0aGUKICAgICAqIHByb3ZpZGVkIG5hbWUuCiAgICAgKiBAcGFyYW0gbm9kZU5hbWUgVGhlIG1ldGEgb3Igb3Agbm9kZSBvZiB3aGljaCB0aGUgT3BOb2RlIGluc3RhbmNlcyBhcmUKICAgICAqIHJlcXVpcmVkLgogICAgICogQHBhcmFtIHJlbmRlckdyYXBoSW5mbyBUaGUgcmVuZGVyZWQgZ3JhcGggaW5mb3JtYXRpb24gb2JqZWN0LgogICAgICogQHJldHVybnMge0FycmF5fSBBbiBhcnJheSBvZiBPcE5vZGVJbXBsIGluc3RhbmNlcy4KICAgICAqLwogICAgZnVuY3Rpb24gX2dldEFsbENvbnRhaW5lZE9wTm9kZXMobm9kZU5hbWUsIHJlbmRlckdyYXBoSW5mbykgewogICAgICAgIGxldCBvcE5vZGVzID0gW107CiAgICAgICAgLy8gR2V0IGN1cnJlbnQgbm9kZS4KICAgICAgICBsZXQgbm9kZSA9IHJlbmRlckdyYXBoSW5mby5nZXROb2RlQnlOYW1lKG5vZGVOYW1lKTsKICAgICAgICAvLyBJZiBub2RlIGlzIGFscmVhZHkgT3BOb2RlIHRoZW4gcmV0dXJuIHRoZSBub2RlIHBsdXMgaXRzIGlucHV0IGVtYmVkZGluZ3MuCiAgICAgICAgaWYgKG5vZGUgaW5zdGFuY2VvZiBPcE5vZGVJbXBsKSB7CiAgICAgICAgICAgIHJldHVybiBbbm9kZV0uY29uY2F0KG5vZGUuaW5FbWJlZGRpbmdzKTsKICAgICAgICB9CiAgICAgICAgLy8gT3RoZXJ3aXNlLCBtYWtlIHJlY3Vyc2l2ZSBjYWxsIGZvciBlYWNoIG5vZGUgY29udGFpbmVkIGJ5IHRoZSBHcm91cE5vZGUuCiAgICAgICAgbGV0IGNoaWxkTm9kZU5hbWVzID0gbm9kZS5tZXRhZ3JhcGgubm9kZXMoKTsKICAgICAgICBsb2Rhc2guZWFjaChjaGlsZE5vZGVOYW1lcywgZnVuY3Rpb24gKGNoaWxkTm9kZU5hbWUpIHsKICAgICAgICAgICAgb3BOb2RlcyA9IG9wTm9kZXMuY29uY2F0KF9nZXRBbGxDb250YWluZWRPcE5vZGVzKGNoaWxkTm9kZU5hbWUsIHJlbmRlckdyYXBoSW5mbykpOwogICAgICAgIH0pOwogICAgICAgIHJldHVybiBvcE5vZGVzOwogICAgfQogICAgZnVuY3Rpb24gdHJhY2VBbGxJbnB1dHNPZk9wTm9kZShzdmdSb290LCByZW5kZXJHcmFwaEluZm8sIHN0YXJ0Tm9kZSwgYWxsVHJhY2VkTm9kZXMpIHsKICAgICAgICAvLyBUbyBwcmV2ZW50IGluZmluaXRlIGxvb3BzIGR1ZSB0byBjeWNsaWNhbCByZWxhdGlvbnNoaXBzIGFuZCBpbXByb3ZpbmcKICAgICAgICAvLyBwZXJmb3JtYW5jZSBieSB0cmFjaW5nIE9wTm9kZSB3aGljaCBpcyBpbnB1dCB0byAyKyBub2RlcyBvbmx5IG9uY2UuCiAgICAgICAgaWYgKGFsbFRyYWNlZE5vZGVzW3N0YXJ0Tm9kZS5uYW1lXSkgewogICAgICAgICAgICByZXR1cm4gYWxsVHJhY2VkTm9kZXM7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBhbGxUcmFjZWROb2Rlc1tzdGFydE5vZGUubmFtZV0gPSB0cnVlOwogICAgICAgIH0KICAgICAgICAvLyBFeHRyYWN0IHRoZSBpbnB1dHMuCiAgICAgICAgbGV0IGlucHV0cyA9IHN0YXJ0Tm9kZS5pbnB1dHM7CiAgICAgICAgLy8gR2V0IHZpc2libGUgcGFyZW50LgogICAgICAgIGxldCBjdXJyZW50VmlzaWJsZVBhcmVudCA9IGdldFZpc2libGVQYXJlbnQocmVuZGVyR3JhcGhJbmZvLCBzdGFydE5vZGUpOwogICAgICAgIC8vIE1hcmsgYXMgaW5wdXQgbm9kZS4KICAgICAgICBzZWxlY3Qoc3ZnUm9vdCkKICAgICAgICAgICAgLnNlbGVjdChgLm5vZGVbZGF0YS1uYW1lPSIke2N1cnJlbnRWaXNpYmxlUGFyZW50Lm5hbWV9Il1gKQogICAgICAgICAgICAuY2xhc3NlZCgnaW5wdXQtaGlnaGxpZ2h0JywgdHJ1ZSk7CiAgICAgICAgLy8gRmluZCB0aGUgdmlzaWJsZSBwYXJlbnQgb2YgZWFjaCBpbnB1dC4KICAgICAgICBsZXQgdmlzaWJsZUlucHV0cyA9IHt9OwogICAgICAgIGxvZGFzaC5lYWNoKGlucHV0cywgZnVuY3Rpb24gKG5vZGVJbnN0YW5jZSkgewogICAgICAgICAgICBsZXQgcmVzb2x2ZWROb2RlID0gcmVuZGVyR3JhcGhJbmZvLmdldE5vZGVCeU5hbWUobm9kZUluc3RhbmNlLm5hbWUpOwogICAgICAgICAgICBpZiAocmVzb2x2ZWROb2RlID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIC8vIE5vZGUgY291bGQgbm90IGJlIGZvdW5kIGluIHJlbmRlcmVkIEhpZXJhcmNoeSwgd2hpY2ggaGFwcGVucyB3aGVuCiAgICAgICAgICAgICAgICAvLyB0cmFjaW5nIGlucHV0cyBvZiBhIFN1bW1hcnlOb2RlLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEVuc3VyZSBub2RlIGlzIHJlc29sdmVkIHRvIE9wTm9kZSBpZiBuYW1lIGNvbGxpc2lvbiB3aXRoIE1ldGFub2RlIGV4aXN0cy4KICAgICAgICAgICAgaWYgKHJlc29sdmVkTm9kZSBpbnN0YW5jZW9mIE1ldGFub2RlSW1wbCkgewogICAgICAgICAgICAgICAgbGV0IHJlc29sdmVkTm9kZU5hbWUgPSBnZXRTdHJpY3ROYW1lKHJlc29sdmVkTm9kZS5uYW1lKTsKICAgICAgICAgICAgICAgIHJlc29sdmVkTm9kZSA9IHJlbmRlckdyYXBoSW5mby5nZXROb2RlQnlOYW1lKHJlc29sdmVkTm9kZU5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCB2aXNpYmxlUGFyZW50ID0gZ2V0VmlzaWJsZVBhcmVudChyZW5kZXJHcmFwaEluZm8sIHJlc29sdmVkTm9kZSk7CiAgICAgICAgICAgIC8vIEFwcGVuZCBPcE5vZGUgdG8gdmlzaWJsZSBwYXJlbnQgZW50cnkuCiAgICAgICAgICAgIGxldCB2aXNpYmxlSW5wdXRzRW50cnkgPSB2aXNpYmxlSW5wdXRzW3Zpc2libGVQYXJlbnQubmFtZV07CiAgICAgICAgICAgIGlmICh2aXNpYmxlSW5wdXRzRW50cnkpIHsKICAgICAgICAgICAgICAgIHZpc2libGVJbnB1dHNFbnRyeS5vcE5vZGVzLnB1c2gocmVzb2x2ZWROb2RlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIENyZWF0ZSBuZXcgZW50cnkuCiAgICAgICAgICAgICAgICB2aXNpYmxlSW5wdXRzW3Zpc2libGVQYXJlbnQubmFtZV0gPSB7CiAgICAgICAgICAgICAgICAgICAgdmlzaWJsZVBhcmVudDogdmlzaWJsZVBhcmVudCwKICAgICAgICAgICAgICAgICAgICBvcE5vZGVzOiBbcmVzb2x2ZWROb2RlXSwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICAvLyBGaW5kIGFsbCBwYXJlbnRzIG9mIHRoZSBzdGFydCBub2RlLgogICAgICAgIGxldCBzdGFydE5vZGVQYXJlbnRzID0ge307CiAgICAgICAgbGV0IGluZGV4ZWRTdGFydE5vZGVQYXJlbnRzID0gW2N1cnJlbnRWaXNpYmxlUGFyZW50XTsKICAgICAgICBzdGFydE5vZGVQYXJlbnRzW2N1cnJlbnRWaXNpYmxlUGFyZW50Lm5hbWVdID0gewogICAgICAgICAgICB0cmFjZWQ6IGZhbHNlLAogICAgICAgICAgICBpbmRleDogMCwKICAgICAgICAgICAgY29ubmVjdGlvbkVuZHBvaW50czogW10sCiAgICAgICAgfTsKICAgICAgICBsZXQgY3VycmVudE5vZGUgPSBjdXJyZW50VmlzaWJsZVBhcmVudDsKICAgICAgICBmb3IgKGxldCBpbmRleCA9IDE7IGN1cnJlbnROb2RlLm5hbWUgIT09IFJPT1RfTkFNRTsgaW5kZXgrKykgewogICAgICAgICAgICBjdXJyZW50Tm9kZSA9IGN1cnJlbnROb2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgIHN0YXJ0Tm9kZVBhcmVudHNbY3VycmVudE5vZGUubmFtZV0gPSB7CiAgICAgICAgICAgICAgICB0cmFjZWQ6IGZhbHNlLAogICAgICAgICAgICAgICAgaW5kZXg6IGluZGV4LAogICAgICAgICAgICAgICAgY29ubmVjdGlvbkVuZHBvaW50czogW10sCiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGluZGV4ZWRTdGFydE5vZGVQYXJlbnRzW2luZGV4XSA9IGN1cnJlbnROb2RlOwogICAgICAgIH0KICAgICAgICAvLyBGaW5kIGZpcnN0IG11dHVhbCBwYXJlbnQgb2YgZWFjaCBpbnB1dCBub2RlIGFuZCBoaWdobGlnaHQgY29ubmVjdGlvbi4KICAgICAgICBsb2Rhc2guZm9yT3duKHZpc2libGVJbnB1dHMsIGZ1bmN0aW9uICh2aXNpYmxlUGFyZW50SW5mbywga2V5KSB7CiAgICAgICAgICAgIGxldCBub2RlSW5zdGFuY2UgPSB2aXNpYmxlUGFyZW50SW5mby52aXNpYmxlUGFyZW50OwogICAgICAgICAgICAvLyBNYWtlIHJlY3Vyc2l2ZSBjYWxsIGZvciBlYWNoIGlucHV0LU9wTm9kZSBjb250YWluZWQgYnkgdGhlIHZpc2libGUKICAgICAgICAgICAgLy8gcGFyZW50LgogICAgICAgICAgICBsb2Rhc2guZWFjaCh2aXNpYmxlUGFyZW50SW5mby5vcE5vZGVzLCBmdW5jdGlvbiAob3BOb2RlKSB7CiAgICAgICAgICAgICAgICBhbGxUcmFjZWROb2RlcyA9IHRyYWNlQWxsSW5wdXRzT2ZPcE5vZGUoc3ZnUm9vdCwgcmVuZGVyR3JhcGhJbmZvLCBvcE5vZGUsIGFsbFRyYWNlZE5vZGVzKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGlmIChub2RlSW5zdGFuY2UubmFtZSAhPT0gY3VycmVudFZpc2libGVQYXJlbnQubmFtZSkgewogICAgICAgICAgICAgICAgX2NyZWF0ZVZpc2libGVUcmFjZShzdmdSb290LCBub2RlSW5zdGFuY2UsIHN0YXJ0Tm9kZVBhcmVudHMsIGluZGV4ZWRTdGFydE5vZGVQYXJlbnRzKTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIHJldHVybiBhbGxUcmFjZWROb2RlczsKICAgIH0KICAgIC8qKgogICAgICogQ29sb3JzIHRoZSBlZGdlcyB0byBjb25uZWN0IHRoZSBwYXNzZWQgbm9kZSB0byB0aGUgc3RhcnQgbm9kZS4gVGhpcyBpcwogICAgICogZG9uZSBieToKICAgICAqCiAgICAgKiBhKSBGaW5kaW5nIHRoZSBmaXJzdCAodmlzaWJsZSkgY29tbW9uIHBhcmVudCBpbiB0aGUgcmVuZGVyZWQKICAgICAqIGhpZXJhcmNoeS4KICAgICAqIE5COiBUaGVyZSBhcmUgMiB0eXBlcyBvZiBjb25uZWN0aW9uczoKICAgICAqIDEpIERpcmVjdCBjb25uZWN0aW9ucyBiZXR3ZWVuIG5vZGUgQQogICAgICogYW5kIEIsIG1hcmtlZCBiZWxvdyBhcyBJSSwKICAgICAqIDIpIENvbm5lY3Rpb25zIGZyb20gYW55IG5vZGUgQSB0byBpdHMgcGFyZW50LCBBJy4gTWFya2VkIGJlbG93IGFzIEkgYW5kIElJSS4KICAgICAqIEZvciB0eXBlIDIgY29ubmVjdGlvbiB5b3UgbmVlZCB0byBrbm93IHRoZSBpbm5lci1uZXN0ZWQgbm9kZSwgdGhlCiAgICAgKiBkaXJlY3QgcGFyZW50LCBhbmQgdGhlIHVsdGltYXRlIGRlc3RpbmF0aW9uIG9mIHRoZSBjb25uZWN0aW9uLgogICAgICoKICAgICAqICBBX3BhcmVudCAgICAgIEJfcGFyZW50CiAgICAgKiArLS0tLS0tLS0rICAgICstLS0tLS0tLS0rCiAgICAgKiB8ICAgICAgICB8ICAgIHwgICAgICAgICB8CiAgICAgKiB8ICArLS0rIEl8IElJIHxJSUkrLS0rICB8CiAgICAgKiB8ICB8QSArLS0tLS0tLS0tLT4rQiB8ICB8CiAgICAgKiB8ICArLS0rICB8ICAgIHwgICArLS0rICB8CiAgICAgKiB8ICAgICAgICB8ICAgIHwgICAgICAgICB8CiAgICAgKiArLS0tLS0tLS0rICAgICstLS0tLS0tLS0rCiAgICAgKgogICAgICoKICAgICAqIGIpIEhpZ2hsaWdodGluZyB0aGUgZGlyZWN0IGNvbm5lY3Rpb24gYmV0d2VlbiB0aGUgcGFyZW50cyBvZiBBIGFuZCBCLAogICAgICogY2FsbGVkIEFfcGFyZW50IGFuZCBCX3BhcmVudCwgcy50LiBBX3BhcmVudCBhbmQgQl9wYXJlbnQgYXJlIGNoaWxkcmVuIG9mIHRoZQogICAgICogbXV0dWFsIHBhcmVudCBvZiBBIGFuZCBCIGZvdW5kIGluIGEpLCBtYXJrZWQgYWJvdmUgYXMgSUkuCiAgICAgKgogICAgICogYykgSGlnaGxpZ2h0aW5nIHRoZSBjb25uZWN0aW9uIGZyb20gQSB0byBBX3BhcmVudCBhbmQgQiB0byBCX3BhcmVudAogICAgICogKHRocm91Z2ggYWxsIGxheWVycyBvZiBwYXJlbnRzIGJldHdlZW4gQSBhbmQgQV9wYXJlbnQgYW5kIEIgYW5kIEJfcGFyZW50LAogICAgICogcmVzcGVjdGl2ZWx5KS4gTWFya2VkIGFib3ZlIGFzIEkgYW5kIElJSS4KICAgICAqCiAgICAgKiBAcGFyYW0gbm9kZUluc3RhbmNlIFRoZSBpbnN0YW5jZSBvZiB0aGUgbm9kZSB0byB1c2UgYXMgZGVzdGluYXRpb24gbm9kZSwgQi4KICAgICAqIEBwYXJhbSBzdGFydE5vZGVQYXJlbnRzIE1hcCBvZiBzdGFydE5vZGVQYXJlbnQgbmFtZXMgdG8gaW5mb3JtYXRpb24gb2JqZWN0cwogICAgICogYWJvdXQgdGhlIHBhcmVudC4KICAgICAqIEBwYXJhbSBpbmRleGVkU3RhcnROb2RlUGFyZW50cyBBbiBhcnJheSBvZiBhbGwgcGFyZW50cyBvZiB0aGUgc3RhcnQgbm9kZS4KICAgICAqIFRoaXMgaXMgcmVxdWlyZWQgdG8gZmluZCB0aGUgY2hpbGQgb2YgdGhlIG11dHVhbCBwYXJlbnQgd2hpY2ggaXMgYSBwYXJlbnQKICAgICAqIG9mIHRoZSBzdGFydCBub2RlLgogICAgICogQHByaXZhdGUKICAgICAqLwogICAgZnVuY3Rpb24gX2NyZWF0ZVZpc2libGVUcmFjZShzdmdSb290LCBub2RlSW5zdGFuY2UsIHN0YXJ0Tm9kZVBhcmVudHMsIGluZGV4ZWRTdGFydE5vZGVQYXJlbnRzKSB7CiAgICAgICAgbGV0IGN1cnJlbnROb2RlID0gbm9kZUluc3RhbmNlOwogICAgICAgIGxldCBwcmV2aW91c05vZGUgPSBub2RlSW5zdGFuY2U7CiAgICAgICAgLy8gQXNjZW5kIHRocm91Z2ggcGFyZW50cyB1bnRpbCBhIG11dHVhbCBwYXJlbnQgaXMgZm91bmQgd2l0aCB0aGUgc3RhcnQKICAgICAgICAvLyBub2RlLgogICAgICAgIGxldCBkZXN0aW5hdGlvblBhcmVudFBhaXJzID0gW107CiAgICAgICAgd2hpbGUgKCFzdGFydE5vZGVQYXJlbnRzW2N1cnJlbnROb2RlLm5hbWVdKSB7CiAgICAgICAgICAgIGlmIChwcmV2aW91c05vZGUubmFtZSAhPT0gY3VycmVudE5vZGUubmFtZSkgewogICAgICAgICAgICAgICAgZGVzdGluYXRpb25QYXJlbnRQYWlycy5wdXNoKFtwcmV2aW91c05vZGUsIGN1cnJlbnROb2RlXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcHJldmlvdXNOb2RlID0gY3VycmVudE5vZGU7CiAgICAgICAgICAgIGN1cnJlbnROb2RlID0gY3VycmVudE5vZGUucGFyZW50Tm9kZTsKICAgICAgICB9CiAgICAgICAgLy8gQ29ubmVjdGlvbiBiZXR3ZWVuIG5vZGVzIGlzIGRyYXduIGJldHdlZW4gdGhlIHBhcmVudHMgb2YgZWFjaAogICAgICAgIC8vIHJlc3BlY3RpdmUgbm9kZSwgYm90aCBvZiB3aGljaCBzaGFyZSB0aGUgbXV0dWFsIHBhcmVudC4KICAgICAgICBsZXQgc3RhcnROb2RlSW5kZXggPSBzdGFydE5vZGVQYXJlbnRzW2N1cnJlbnROb2RlLm5hbWVdLmluZGV4OwogICAgICAgIGxldCBzdGFydE5vZGVOYW1lID0gaW5kZXhlZFN0YXJ0Tm9kZVBhcmVudHNbTWF0aC5tYXgoc3RhcnROb2RlSW5kZXggLSAxLCAwKV0ubmFtZTsKICAgICAgICBsZXQgc3RhcnROb2RlVG9wUGFyZW50TmFtZSA9IHN0YXJ0Tm9kZU5hbWU7CiAgICAgICAgbGV0IHRhcmdldE5vZGVUb3BQYXJlbnROYW1lID0gcHJldmlvdXNOb2RlLm5hbWU7CiAgICAgICAgbGV0IGVuZE5vZGVOYW1lID0gcHJldmlvdXNOb2RlLm5hbWU7CiAgICAgICAgY29uc3Qgc3ZnID0gc2VsZWN0KHN2Z1Jvb3QpOwogICAgICAgIHN2ZwogICAgICAgICAgICAuc2VsZWN0QWxsKGBbZGF0YS1lZGdlPSIke2VuZE5vZGVOYW1lfS0tJHtzdGFydE5vZGVOYW1lfSJdYCkKICAgICAgICAgICAgLmNsYXNzZWQoJ2lucHV0LWVkZ2UtaGlnaGxpZ2h0JywgdHJ1ZSk7CiAgICAgICAgLy8gVHJhY2UgdXAgdGhlIHBhcmVudHMgb2YgdGhlIGlucHV0LgogICAgICAgIGxvZGFzaC5lYWNoKGRlc3RpbmF0aW9uUGFyZW50UGFpcnMsIGZ1bmN0aW9uICh2YWx1ZSkgewogICAgICAgICAgICBsZXQgaW5uZXIgPSB2YWx1ZVswXTsKICAgICAgICAgICAgbGV0IG91dGVyID0gdmFsdWVbMV07CiAgICAgICAgICAgIGxldCBlZGdlU2VsZWN0b3IgPSBgW2RhdGEtZWRnZT0iJHtpbm5lci5uYW1lfS0tJHtzdGFydE5vZGVUb3BQYXJlbnROYW1lfWAgKwogICAgICAgICAgICAgICAgYH5+JHtvdXRlci5uYW1lfX5+T1VUIl1gOwogICAgICAgICAgICBzdmcuc2VsZWN0QWxsKGVkZ2VTZWxlY3RvcikuY2xhc3NlZCgnaW5wdXQtZWRnZS1oaWdobGlnaHQnLCB0cnVlKTsKICAgICAgICB9KTsKICAgICAgICAvLyBUcmFjZSB1cCB0aGUgcGFyZW50cyBvZiB0aGUgc3RhcnQgbm9kZS4KICAgICAgICBmb3IgKGxldCBpbmRleCA9IDE7IGluZGV4IDwgc3RhcnROb2RlSW5kZXg7IGluZGV4KyspIHsKICAgICAgICAgICAgbGV0IGlubmVyID0gaW5kZXhlZFN0YXJ0Tm9kZVBhcmVudHNbaW5kZXggLSAxXTsKICAgICAgICAgICAgbGV0IG91dGVyID0gaW5kZXhlZFN0YXJ0Tm9kZVBhcmVudHNbaW5kZXhdOwogICAgICAgICAgICBsZXQgZWRnZVNlbGVjdG9yID0gYFtkYXRhLWVkZ2U9IiR7dGFyZ2V0Tm9kZVRvcFBhcmVudE5hbWV9fn4ke291dGVyLm5hbWV9YCArCiAgICAgICAgICAgICAgICBgfn5JTi0tJHtpbm5lci5uYW1lfSJdYDsKICAgICAgICAgICAgc3ZnLnNlbGVjdEFsbChlZGdlU2VsZWN0b3IpLmNsYXNzZWQoJ2lucHV0LWVkZ2UtaGlnaGxpZ2h0JywgdHJ1ZSk7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBDcmVhdGVzIG1hcCB7IFtuYW1lOiBzdHJpbmddIC0+IE5vZGUgfSBvZiBhbGwgdmlzaWJsZSAvIHJlbmRlcmVkIHBhcmVudHMKICAgICAqIG9mIHRoZSBub2RlcyBpZGVudGlmaWVkIGJ5IHRoZSBub2RlIG5hbWVzIHBhc3NlZCBpbi4KICAgICAqCiAgICAgKiBAcGFyYW0gcmVuZGVyR3JhcGhJbmZvIFRoZSBpbmZvcm1hdGlvbiBvbiB0aGUgcmVuZGVyZWQgZ3JhcGguCiAgICAgKiBAcGFyYW0gbm9kZU5hbWVzIFN0cmluZyBhcnJheSBvZiBub2RlIG5hbWVzLgogICAgICogQHJldHVybnMge1tub2RlTmFtZTogc3RyaW5nXTogTm9kZX0KICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGZ1bmN0aW9uIF9maW5kVmlzaWJsZVBhcmVudHNGcm9tT3BOb2RlcyhyZW5kZXJHcmFwaEluZm8sIG5vZGVOYW1lcykgewogICAgICAgIGxldCB2aXNpYmxlUGFyZW50cyA9IHt9OwogICAgICAgIGxvZGFzaC5lYWNoKG5vZGVOYW1lcywgZnVuY3Rpb24gKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIGxldCBjdXJyZW50Tm9kZSA9IHJlbmRlckdyYXBoSW5mby5nZXROb2RlQnlOYW1lKG5vZGVOYW1lKTsKICAgICAgICAgICAgbGV0IHZpc2libGVQYXJlbnQgPSBnZXRWaXNpYmxlUGFyZW50KHJlbmRlckdyYXBoSW5mbywgY3VycmVudE5vZGUpOwogICAgICAgICAgICB2aXNpYmxlUGFyZW50c1t2aXNpYmxlUGFyZW50Lm5hbWVdID0gdmlzaWJsZVBhcmVudDsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gdmlzaWJsZVBhcmVudHM7CiAgICB9CiAgICAvKioKICAgICAqIFRyYXZlcnNlIHRocm91Z2ggdGhlIHBhcmVudHMgb2YgYWxsIG5vZGVzIGluIHRoZSBsaXN0IGFuZCBtYXJrIGVhY2gKICAgICAqIGVuY291bnRlcmVkIG5vZGUgYXMgaW5wdXQtcGFyZW50LgogICAgICogQHBhcmFtIHZpc2libGVOb2RlcyBNYXAgb2YgaW5wdXQgbm9kZXMsIGhhdmUgdG8gYmUgdmlzaWJsZS9yZW5kZXJlZCB3aGVuCiAgICAgKiBjYWxsZWQuCiAgICAgKiBAcHJpdmF0ZQogICAgICovCiAgICBmdW5jdGlvbiBfbWFya1BhcmVudHNPZk5vZGVzKHN2Z1Jvb3QsIHZpc2libGVOb2RlcykgewogICAgICAgIGxvZGFzaC5mb3JPd24odmlzaWJsZU5vZGVzLCBmdW5jdGlvbiAobm9kZUluc3RhbmNlKSB7CiAgICAgICAgICAgIC8vIE1hcmsgYWxsIHBhcmVudHMgb2YgdGhlIG5vZGUgYXMgaW5wdXQtcGFyZW50cy4KICAgICAgICAgICAgbGV0IGN1cnJlbnROb2RlID0gbm9kZUluc3RhbmNlOwogICAgICAgICAgICB3aGlsZSAoY3VycmVudE5vZGUubmFtZSAhPT0gUk9PVF9OQU1FKSB7CiAgICAgICAgICAgICAgICBjb25zdCByZW5kZXJlZEVsZW1lbnRTZWxlY3Rpb24gPSBzZWxlY3Qoc3ZnUm9vdCkKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0KGAubm9kZVtkYXRhLW5hbWU9IiR7Y3VycmVudE5vZGUubmFtZX0iXWApOwogICAgICAgICAgICAgICAgLy8gT25seSBtYXJrIHRoZSBlbGVtZW50IGFzIGEgcGFyZW50IG5vZGUgdG8gYW4gaW5wdXQgaWYgaXQgaXMgbm90CiAgICAgICAgICAgICAgICAvLyBtYXJrZWQgYXMgaW5wdXQgbm9kZSBpdHNlbGYuCiAgICAgICAgICAgICAgICBpZiAocmVuZGVyZWRFbGVtZW50U2VsZWN0aW9uLm5vZGVzKCkubGVuZ3RoICYmCiAgICAgICAgICAgICAgICAgICAgIXJlbmRlcmVkRWxlbWVudFNlbGVjdGlvbi5jbGFzc2VkKCdpbnB1dC1oaWdobGlnaHQnKSAmJgogICAgICAgICAgICAgICAgICAgICFyZW5kZXJlZEVsZW1lbnRTZWxlY3Rpb24uY2xhc3NlZCgnc2VsZWN0ZWQnKSAmJgogICAgICAgICAgICAgICAgICAgIC8vIE9wTm9kZSBvbmx5IHBhcmVudCBpZiBzdGFydCBub2RlIGlzIGVtYmVkZGVkIG5vZGUsIGluIHdoaWNoIGNhc2UKICAgICAgICAgICAgICAgICAgICAvLyB0aGUgT3BOb2RlIHNob3VsZCBiZSBmYWRlZCBhcyB3ZWxsLgogICAgICAgICAgICAgICAgICAgICFyZW5kZXJlZEVsZW1lbnRTZWxlY3Rpb24uY2xhc3NlZCgnb3AnKSkgewogICAgICAgICAgICAgICAgICAgIHJlbmRlcmVkRWxlbWVudFNlbGVjdGlvbi5jbGFzc2VkKCdpbnB1dC1wYXJlbnQnLCB0cnVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGN1cnJlbnROb2RlID0gY3VycmVudE5vZGUucGFyZW50Tm9kZTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBGaW5kIHRoZSBwYXJlbnQgb2YgdGhlIHBhc3NlZCBpbiBvcCBub2RlIHdoaWNoIGlzIGV4cGFuZGVkLiBUaGlzIGlzIGRvbmUKICAgICAqIGJ5IGdvaW5nIHRocm91Z2ggYWxsIHBhcmVudHMgdW50aWwgdGhlIHBhcmVudCdzIHBhcmVudCBpcyBleHBhbmRlZCwgdGh1cwogICAgICogZmluZGluZyB0aGUgZmlyc3QgdW5leHBhbmRlZCBwYXJlbnQgd2hpY2ggaXMgcmVuZGVyZWQgb24gdGhlIHNjcmVlbi4KICAgICAqIEBwYXJhbSByZW5kZXJHcmFwaEluZm8gVGhlIGdyYXBoIGluZm8gb2JqZWN0IHVzZWQgdG8gZ2FpbiBhY2Nlc3MgdG8gdGhlCiAgICAgKiByZW5kZXIgaW5mbyBvZiB0aGUgcGFyZW50cy4KICAgICAqIEBwYXJhbSBjdXJyZW50Tm9kZSBUaGUgbm9kZSB3aG9zZSBwYXJlbnQgaXMgdG8gYmUgZm91bmQuCiAgICAgKiBAcmV0dXJucyBOb2RlCiAgICAgKi8KICAgIGZ1bmN0aW9uIGdldFZpc2libGVQYXJlbnQocmVuZGVyR3JhcGhJbmZvLCBjdXJyZW50Tm9kZSkgewogICAgICAgIGxldCBmb3VuZCA9IGZhbHNlOwogICAgICAgIGxldCBjdXJyZW50UGFyZW50ID0gY3VycmVudE5vZGU7CiAgICAgICAgd2hpbGUgKCFmb3VuZCkgewogICAgICAgICAgICAvLyBHZXQgcGFyZW50IGVsZW1lbnQsIHRvIGV4dHJhY3QgbmFtZS4KICAgICAgICAgICAgY3VycmVudE5vZGUgPSBjdXJyZW50UGFyZW50OwogICAgICAgICAgICBjdXJyZW50UGFyZW50ID0gY3VycmVudE5vZGUucGFyZW50Tm9kZTsKICAgICAgICAgICAgaWYgKGN1cnJlbnRQYXJlbnQgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgZm91bmQgPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgbGV0IHJlbmRlck5vZGUgPSByZW5kZXJHcmFwaEluZm8uZ2V0UmVuZGVyTm9kZUJ5TmFtZShjdXJyZW50UGFyZW50Lm5hbWUpOwogICAgICAgICAgICAgICAgLy8gRm91bmQgaWYgbm9kZSBpcyByZW5kZXJlZCBvbiB0aGUgc2NyZWVuIChyZW5kZXJOb2RlIHRydXRoeSksIGFuZAogICAgICAgICAgICAgICAgLy8gdGhlIHBhcmVudCBpcyBlaXRoZXIgZXhwYW5kZWQgKGkuZS4gaXQgaXMgYSBtZXRhbm9kZSBvciBzZXJpZXNub2RlKQogICAgICAgICAgICAgICAgLy8gb3IgdGhlIHBhcmVudCBpcyBhbiBPcE5vZGUgaW4gd2hpY2ggY2FzZSBjdXJyZW50Tm9kZSBpcyBhbiBlbWJlZGRlZAogICAgICAgICAgICAgICAgLy8gbm9kZSB3aGljaCBoYXMgYW5vdGhlciBPcE5vZGUgYXMgcGFyZW50LgogICAgICAgICAgICAgICAgaWYgKHJlbmRlck5vZGUgJiYKICAgICAgICAgICAgICAgICAgICAocmVuZGVyTm9kZS5leHBhbmRlZCB8fCBjdXJyZW50UGFyZW50IGluc3RhbmNlb2YgT3BOb2RlSW1wbCkpIHsKICAgICAgICAgICAgICAgICAgICBmb3VuZCA9IHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9IC8vIENsb3NlIHdoaWxlIGxvb3AuCiAgICAgICAgcmV0dXJuIGN1cnJlbnROb2RlOwogICAgfQogICAgLyoqCiAgICAgKiBBbm5vdGF0aW9ucy4KICAgICAqLwogICAgZnVuY3Rpb24gYnVpbGRHcm91cEZvckFubm90YXRpb24oY29udGFpbmVyLCBhbm5vdGF0aW9uRGF0YSwgZCwgc2NlbmVFbGVtZW50KSB7CiAgICAgICAgLy8gU2VsZWN0IGFsbCBjaGlsZHJlbiBhbmQgam9pbiB3aXRoIGRhdGEuCiAgICAgICAgbGV0IGFubm90YXRpb25Hcm91cHMgPSBjb250YWluZXIKICAgICAgICAgICAgLnNlbGVjdEFsbChmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIC8vIHVzaW5nIGQzJ3Mgc2VsZWN0b3IgZnVuY3Rpb24KICAgICAgICAgICAgLy8gU2VlIGh0dHBzOi8vZ2l0aHViLmNvbS9tYm9zdG9jay9kMy9yZWxlYXNlcy90YWcvdjIuMC4wCiAgICAgICAgICAgIC8vIChJdCdzIG5vdCBsaXN0ZWQgaW4gdGhlIGQzIHdpa2kuKQogICAgICAgICAgICByZXR1cm4gdGhpcy5jaGlsZE5vZGVzOwogICAgICAgIH0pCiAgICAgICAgICAgIC5kYXRhKGFubm90YXRpb25EYXRhLmxpc3QsIChkKSA9PiB7CiAgICAgICAgICAgIHJldHVybiBkLm5vZGUubmFtZTsKICAgICAgICB9KTsKICAgICAgICBhbm5vdGF0aW9uR3JvdXBzCiAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAuYXR0cignZGF0YS1uYW1lJywgKGEpID0+IHsKICAgICAgICAgICAgcmV0dXJuIGEubm9kZS5uYW1lOwogICAgICAgIH0pCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChhKSB7CiAgICAgICAgICAgIGxldCBhR3JvdXAgPSBzZWxlY3QodGhpcyk7CiAgICAgICAgICAgIC8vIEFkZCBhbm5vdGF0aW9uIHRvIHRoZSBpbmRleCBpbiB0aGUgc2NlbmUKICAgICAgICAgICAgc2NlbmVFbGVtZW50LmFkZEFubm90YXRpb25Hcm91cChhLCBkLCBhR3JvdXApOwogICAgICAgICAgICAvLyBBcHBlbmQgYW5ub3RhdGlvbiBlZGdlCiAgICAgICAgICAgIGxldCBlZGdlVHlwZSA9IENsYXNzJDEuQW5ub3RhdGlvbi5FREdFOwogICAgICAgICAgICBsZXQgbWV0YWVkZ2UgPSBhLnJlbmRlck1ldGFlZGdlSW5mbyAmJiBhLnJlbmRlck1ldGFlZGdlSW5mby5tZXRhZWRnZTsKICAgICAgICAgICAgaWYgKG1ldGFlZGdlICYmICFtZXRhZWRnZS5udW1SZWd1bGFyRWRnZXMpIHsKICAgICAgICAgICAgICAgIGVkZ2VUeXBlICs9ICcgJyArIENsYXNzJDEuQW5ub3RhdGlvbi5DT05UUk9MX0VER0U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gSWYgYW55IGVkZ2VzIGFyZSByZWZlcmVuY2UgZWRnZXMsIGFkZCB0aGUgcmVmZXJlbmNlIGVkZ2UgY2xhc3MuCiAgICAgICAgICAgIGlmIChtZXRhZWRnZSAmJiBtZXRhZWRnZS5udW1SZWZFZGdlcykgewogICAgICAgICAgICAgICAgZWRnZVR5cGUgKz0gJyAnICsgQ2xhc3MkMS5FZGdlLlJFRl9MSU5FOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGFwcGVuZEVkZ2UoYUdyb3VwLCBhLCBzY2VuZUVsZW1lbnQsIGVkZ2VUeXBlKTsKICAgICAgICAgICAgaWYgKGEuYW5ub3RhdGlvblR5cGUgIT09IEFubm90YXRpb25UeXBlLkVMTElQU0lTKSB7CiAgICAgICAgICAgICAgICBhZGRBbm5vdGF0aW9uTGFiZWxGcm9tTm9kZShhR3JvdXAsIGEpOwogICAgICAgICAgICAgICAgYnVpbGRTaGFwZUZvckFubm90YXRpb24oYUdyb3VwLCBhKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIGFkZEFubm90YXRpb25MYWJlbChhR3JvdXAsIGEubm9kZS5uYW1lLCBhLCBDbGFzcyQxLkFubm90YXRpb24uRUxMSVBTSVMpOwogICAgICAgICAgICB9CiAgICAgICAgfSkKICAgICAgICAgICAgLm1lcmdlKGFubm90YXRpb25Hcm91cHMpCiAgICAgICAgICAgIC5hdHRyKCdjbGFzcycsIChhKSA9PiB7CiAgICAgICAgICAgIHJldHVybiAoQ2xhc3MkMS5Bbm5vdGF0aW9uLkdST1VQICsKICAgICAgICAgICAgICAgICcgJyArCiAgICAgICAgICAgICAgICBhbm5vdGF0aW9uVG9DbGFzc05hbWUoYS5hbm5vdGF0aW9uVHlwZSkgKwogICAgICAgICAgICAgICAgJyAnICsKICAgICAgICAgICAgICAgIG5vZGVDbGFzcyhhKSk7CiAgICAgICAgfSkKICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKGEpIHsKICAgICAgICAgICAgbGV0IGFHcm91cCA9IHNlbGVjdCh0aGlzKTsKICAgICAgICAgICAgdXBkYXRlKGFHcm91cCwgZCwgYSwgc2NlbmVFbGVtZW50KTsKICAgICAgICAgICAgaWYgKGEuYW5ub3RhdGlvblR5cGUgIT09IEFubm90YXRpb25UeXBlLkVMTElQU0lTKSB7CiAgICAgICAgICAgICAgICBhZGRJbnRlcmFjdGlvbkZvckFubm90YXRpb24oYUdyb3VwLCBkLCBhLCBzY2VuZUVsZW1lbnQpOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgYW5ub3RhdGlvbkdyb3VwcwogICAgICAgICAgICAuZXhpdCgpCiAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChhKSB7CiAgICAgICAgICAgIGxldCBhR3JvdXAgPSBzZWxlY3QodGhpcyk7CiAgICAgICAgICAgIC8vIFJlbW92ZSBhbm5vdGF0aW9uIGZyb20gdGhlIGluZGV4IGluIHRoZSBzY2VuZQogICAgICAgICAgICBzY2VuZUVsZW1lbnQucmVtb3ZlQW5ub3RhdGlvbkdyb3VwKGEsIGQsIGFHcm91cCk7CiAgICAgICAgfSkKICAgICAgICAgICAgLnJlbW92ZSgpOwogICAgICAgIHJldHVybiBhbm5vdGF0aW9uR3JvdXBzOwogICAgfQogICAgLyoqCiAgICAgKiBNYXBzIGFuIGFubm90YXRpb24gZW51bSB0byBhIGNsYXNzIG5hbWUgdXNlZCBpbiBjc3MgcnVsZXMuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGFubm90YXRpb25Ub0NsYXNzTmFtZShhbm5vdGF0aW9uVHlwZSkgewogICAgICAgIHJldHVybiAoQW5ub3RhdGlvblR5cGVbYW5ub3RhdGlvblR5cGVdIHx8ICcnKS50b0xvd2VyQ2FzZSgpIHx8IG51bGw7CiAgICB9CiAgICBmdW5jdGlvbiBidWlsZFNoYXBlRm9yQW5ub3RhdGlvbihhR3JvdXAsIGEpIHsKICAgICAgICBpZiAoYS5hbm5vdGF0aW9uVHlwZSA9PT0gQW5ub3RhdGlvblR5cGUuU1VNTUFSWSkgewogICAgICAgICAgICBsZXQgc3VtbWFyeSA9IHNlbGVjdE9yQ3JlYXRlQ2hpbGQoYUdyb3VwLCAndXNlJyk7CiAgICAgICAgICAgIHN1bW1hcnkKICAgICAgICAgICAgICAgIC5hdHRyKCdjbGFzcycsICdzdW1tYXJ5JykKICAgICAgICAgICAgICAgIC5hdHRyKCd4bGluazpocmVmJywgJyNzdW1tYXJ5LWljb24nKQogICAgICAgICAgICAgICAgLmF0dHIoJ2N1cnNvcicsICdwb2ludGVyJyk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBsZXQgc2hhcGUgPSBidWlsZFNoYXBlKGFHcm91cCwgYSwgQ2xhc3MkMS5Bbm5vdGF0aW9uLk5PREUpOwogICAgICAgICAgICAvLyBhZGQgdGl0bGUgdGFnIHRvIGdldCBuYXRpdmUgdG9vbHRpcHMKICAgICAgICAgICAgc2VsZWN0T3JDcmVhdGVDaGlsZChzaGFwZSwgJ3RpdGxlJykudGV4dChhLm5vZGUubmFtZSk7CiAgICAgICAgfQogICAgfQogICAgZnVuY3Rpb24gYWRkQW5ub3RhdGlvbkxhYmVsRnJvbU5vZGUoYUdyb3VwLCBhKSB7CiAgICAgICAgbGV0IG5hbWVQYXRoID0gYS5ub2RlLm5hbWUuc3BsaXQoJy8nKTsKICAgICAgICBsZXQgdGV4dCA9IG5hbWVQYXRoW25hbWVQYXRoLmxlbmd0aCAtIDFdOwogICAgICAgIHJldHVybiBhZGRBbm5vdGF0aW9uTGFiZWwoYUdyb3VwLCB0ZXh0LCBhLCBudWxsKTsKICAgIH0KICAgIGZ1bmN0aW9uIGFkZEFubm90YXRpb25MYWJlbChhR3JvdXAsIGxhYmVsLCBhLCBhZGRpdGlvbmFsQ2xhc3NOYW1lcykgewogICAgICAgIGxldCBjbGFzc05hbWVzID0gQ2xhc3MkMS5Bbm5vdGF0aW9uLkxBQkVMOwogICAgICAgIGlmIChhZGRpdGlvbmFsQ2xhc3NOYW1lcykgewogICAgICAgICAgICBjbGFzc05hbWVzICs9ICcgJyArIGFkZGl0aW9uYWxDbGFzc05hbWVzOwogICAgICAgIH0KICAgICAgICBsZXQgdHh0RWxlbWVudCA9IGFHcm91cAogICAgICAgICAgICAuYXBwZW5kKCd0ZXh0JykKICAgICAgICAgICAgLmF0dHIoJ2NsYXNzJywgY2xhc3NOYW1lcykKICAgICAgICAgICAgLmF0dHIoJ2R5JywgJy4zNWVtJykKICAgICAgICAgICAgLmF0dHIoJ3RleHQtYW5jaG9yJywgYS5pc0luID8gJ2VuZCcgOiAnc3RhcnQnKQogICAgICAgICAgICAudGV4dChsYWJlbCk7CiAgICAgICAgcmV0dXJuIGVuZm9yY2VMYWJlbFdpZHRoKHR4dEVsZW1lbnQsIC0xKTsKICAgIH0KICAgIGZ1bmN0aW9uIGFkZEludGVyYWN0aW9uRm9yQW5ub3RhdGlvbihzZWxlY3Rpb24sIGQsIGFubm90YXRpb24sIHNjZW5lRWxlbWVudCkgewogICAgICAgIHNlbGVjdGlvbgogICAgICAgICAgICAub24oJ21vdXNlb3ZlcicsIChhKSA9PiB7CiAgICAgICAgICAgIHNjZW5lRWxlbWVudC5maXJlKCdhbm5vdGF0aW9uLWhpZ2hsaWdodCcsIHsKICAgICAgICAgICAgICAgIG5hbWU6IGEubm9kZS5uYW1lLAogICAgICAgICAgICAgICAgaG9zdE5hbWU6IGQubm9kZS5uYW1lLAogICAgICAgICAgICB9KTsKICAgICAgICB9KQogICAgICAgICAgICAub24oJ21vdXNlb3V0JywgKGEpID0+IHsKICAgICAgICAgICAgc2NlbmVFbGVtZW50LmZpcmUoJ2Fubm90YXRpb24tdW5oaWdobGlnaHQnLCB7CiAgICAgICAgICAgICAgICBuYW1lOiBhLm5vZGUubmFtZSwKICAgICAgICAgICAgICAgIGhvc3ROYW1lOiBkLm5vZGUubmFtZSwKICAgICAgICAgICAgfSk7CiAgICAgICAgfSkKICAgICAgICAgICAgLm9uKCdjbGljaycsIChhKSA9PiB7CiAgICAgICAgICAgIC8vIFN0b3AgdGhpcyBldmVudCdzIHByb3BhZ2F0aW9uIHNvIHRoYXQgaXQgaXNuJ3QgYWxzbyBjb25zaWRlcmVkIGEKICAgICAgICAgICAgLy8gZ3JhcGgtc2VsZWN0LgogICAgICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgICAgc2NlbmVFbGVtZW50LmZpcmUoJ2Fubm90YXRpb24tc2VsZWN0JywgewogICAgICAgICAgICAgICAgbmFtZTogYS5ub2RlLm5hbWUsCiAgICAgICAgICAgICAgICBob3N0TmFtZTogZC5ub2RlLm5hbWUsCiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgICAgIGlmIChhbm5vdGF0aW9uLmFubm90YXRpb25UeXBlICE9PSBBbm5vdGF0aW9uVHlwZS5TVU1NQVJZICYmCiAgICAgICAgICAgIGFubm90YXRpb24uYW5ub3RhdGlvblR5cGUgIT09IEFubm90YXRpb25UeXBlLkNPTlNUQU5UKSB7CiAgICAgICAgICAgIHNlbGVjdGlvbi5vbignY29udGV4dG1lbnUnLCBnZXRNZW51KHNjZW5lRWxlbWVudCwgZ2V0Q29udGV4dE1lbnUoYW5ub3RhdGlvbi5ub2RlLCBzY2VuZUVsZW1lbnQpKSk7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBBZGp1c3QgYW5ub3RhdGlvbidzIHBvc2l0aW9uLgogICAgICoKICAgICAqIEBwYXJhbSBhR3JvdXAgc2VsZWN0aW9uIG9mIGEgJ2cuYW5ub3RhdGlvbicgZWxlbWVudC4KICAgICAqIEBwYXJhbSBkIEhvc3Qgbm9kZSBkYXRhLgogICAgICogQHBhcmFtIGEgYW5ub3RhdGlvbiBub2RlIGRhdGEuCiAgICAgKiBAcGFyYW0gc2NlbmVFbGVtZW50IDx0Zi1ncmFwaC1zY2VuZT4gcG9seW1lciBlbGVtZW50LgogICAgICovCiAgICBmdW5jdGlvbiB1cGRhdGUoYUdyb3VwLCBkLCBhLCBzY2VuZUVsZW1lbnQpIHsKICAgICAgICBsZXQgY3ggPSBjb21wdXRlQ1hQb3NpdGlvbk9mTm9kZVNoYXBlKGQpOwogICAgICAgIC8vIEFubm90YXRpb25zIHRoYXQgcG9pbnQgdG8gZW1iZWRkZWQgbm9kZXMgKGNvbnN0YW50cyxzdW1tYXJ5KQogICAgICAgIC8vIGRvbid0IGhhdmUgYSByZW5kZXIgaW5mb3JtYXRpb24gYXR0YWNoZWQgc28gd2UgZG9uJ3Qgc3R5bGl6ZSB0aGVzZS4KICAgICAgICAvLyBBbHNvIHdlIGRvbid0IHN0eWxpemUgZWxsaXBzaXMgYW5ub3RhdGlvbnMgKHRoZSBzdHJpbmcgJy4uLiBhbmQgWCBtb3JlJykuCiAgICAgICAgaWYgKGEucmVuZGVyTm9kZUluZm8gJiYgYS5hbm5vdGF0aW9uVHlwZSAhPT0gQW5ub3RhdGlvblR5cGUuRUxMSVBTSVMpIHsKICAgICAgICAgICAgc3R5bGl6ZSQxKGFHcm91cCwgYS5yZW5kZXJOb2RlSW5mbywgc2NlbmVFbGVtZW50LCBDbGFzcyQxLkFubm90YXRpb24uTk9ERSk7CiAgICAgICAgfQogICAgICAgIGlmIChhLmFubm90YXRpb25UeXBlID09PSBBbm5vdGF0aW9uVHlwZS5TVU1NQVJZKSB7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgd2lkdGggb2YgdGhlIGFubm90YXRpb24gdG8gZ2l2ZSBzcGFjZSBmb3IgdGhlIGltYWdlLgogICAgICAgICAgICBhLndpZHRoICs9IDEwOwogICAgICAgIH0KICAgICAgICAvLyBsYWJlbCBwb3NpdGlvbgogICAgICAgIGFHcm91cAogICAgICAgICAgICAuc2VsZWN0KCd0ZXh0LicgKyBDbGFzcyQxLkFubm90YXRpb24uTEFCRUwpCiAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgLmF0dHIoJ3gnLCBjeCArIGEuZHggKyAoYS5pc0luID8gLTEgOiAxKSAqIChhLndpZHRoIC8gMiArIGEubGFiZWxPZmZzZXQpKQogICAgICAgICAgICAuYXR0cigneScsIGQueSArIGEuZHkpOwogICAgICAgIC8vIFNvbWUgYW5ub3RhdGlvbnMgKHN1Y2ggYXMgc3VtbWFyeSkgYXJlIHJlcHJlc2VudGVkIHVzaW5nIGEgMTJ4MTIgaW1hZ2UgdGFnLgogICAgICAgIC8vIFB1cnBvc2VseSBvbWl0dGVkIHVuaXRzIChlLmcuIHBpeGVscykgc2luY2UgdGhlIGltYWdlcyBhcmUgdmVjdG9yIGdyYXBoaWNzLgogICAgICAgIC8vIElmIHRoZXJlIGlzIGFuIGltYWdlLCB3ZSBhZGp1c3QgdGhlIGxvY2F0aW9uIG9mIHRoZSBpbWFnZSB0byBiZSB2ZXJ0aWNhbGx5CiAgICAgICAgLy8gY2VudGVyZWQgd2l0aCB0aGUgbm9kZSBhbmQgaG9yaXpvbnRhbGx5IGNlbnRlcmVkIGJldHdlZW4gdGhlIGFycm93IGFuZCB0aGUKICAgICAgICAvLyB0ZXh0IGxhYmVsLgogICAgICAgIGFHcm91cAogICAgICAgICAgICAuc2VsZWN0KCd1c2Uuc3VtbWFyeScpCiAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgLmF0dHIoJ3gnLCBjeCArIGEuZHggLSAzKQogICAgICAgICAgICAuYXR0cigneScsIGQueSArIGEuZHkgLSA2KTsKICAgICAgICAvLyBOb2RlIHBvc2l0aW9uIChvbmx5IG9uZSBvZiB0aGUgc2hhcGUgc2VsZWN0aW9uIHdpbGwgYmUgbm9uLWVtcHR5LikKICAgICAgICBwb3NpdGlvbkVsbGlwc2UoYUdyb3VwLnNlbGVjdCgnLicgKyBDbGFzcyQxLkFubm90YXRpb24uTk9ERSArICcgZWxsaXBzZScpLCBjeCArIGEuZHgsIGQueSArIGEuZHksIGEud2lkdGgsIGEuaGVpZ2h0KTsKICAgICAgICBwb3NpdGlvblJlY3QoYUdyb3VwLnNlbGVjdCgnLicgKyBDbGFzcyQxLkFubm90YXRpb24uTk9ERSArICcgcmVjdCcpLCBjeCArIGEuZHgsIGQueSArIGEuZHksIGEud2lkdGgsIGEuaGVpZ2h0KTsKICAgICAgICBwb3NpdGlvblJlY3QoYUdyb3VwLnNlbGVjdCgnLicgKyBDbGFzcyQxLkFubm90YXRpb24uTk9ERSArICcgdXNlJyksIGN4ICsgYS5keCwgZC55ICsgYS5keSwgYS53aWR0aCwgYS5oZWlnaHQpOwogICAgICAgIC8vIEVkZ2UgcG9zaXRpb24KICAgICAgICBhR3JvdXAKICAgICAgICAgICAgLnNlbGVjdCgncGF0aC4nICsgQ2xhc3MkMS5Bbm5vdGF0aW9uLkVER0UpCiAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgLmF0dHIoJ2QnLCAoYSkgPT4gewogICAgICAgICAgICAvLyBtYXAgcmVsYXRpdmUgcG9zaXRpb24gdG8gYWJzb2x1dGUgcG9zaXRpb24KICAgICAgICAgICAgbGV0IHBvaW50cyA9IGEucG9pbnRzLm1hcCgocCkgPT4gewogICAgICAgICAgICAgICAgcmV0dXJuIHsgeDogcC5keCArIGN4LCB5OiBwLmR5ICsgZC55IH07CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gaW50ZXJwb2xhdGUkNyhwb2ludHMpOwogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBTY2VuZS4KICAgICAqLwogICAgLyoqCiAgICAgKiBTZWxlY3Qgb3IgY3JlYXRlIGEgc2NlbmVHcm91cCBhbmQgYnVpbGQvdXBkYXRlIGl0cyBub2RlcyBhbmQgZWRnZXMuCiAgICAgKgogICAgICogU3RydWN0dXJlIFBhdHRlcm46CiAgICAgKgogICAgICogPGcgY2xhc3M9J3NjZW5lJz4KICAgICAqICAgPGcgY2xhc3M9J2NvcmUnPgogICAgICogICAgIDxnIGNsYXNzPSdlZGdlcyc+CiAgICAgKiAgICAgICAuLi4gc3R1ZmYgZnJvbSB0Zi5ncmFwaC5zY2VuZS5lZGdlcy5idWlsZCAuLi4KICAgICAqICAgICA8L2c+CiAgICAgKiAgICAgPGcgY2xhc3M9J25vZGVzJz4KICAgICAqICAgICAgIC4uLiBzdHVmZiBmcm9tIHRmLmdyYXBoLnNjZW5lLm5vZGVzLmJ1aWxkIC4uLgogICAgICogICAgIDwvZz4KICAgICAqICAgPC9nPgogICAgICogICA8ZyBjbGFzcz0naW4tZXh0cmFjdCc+CiAgICAgKiAgICAgPGcgY2xhc3M9J25vZGVzJz4KICAgICAqICAgICAgIC4uLiBzdHVmZiBmcm9tIHRmLmdyYXBoLnNjZW5lLm5vZGVzLmJ1aWxkIC4uLgogICAgICogICAgIDwvZz4KICAgICAqICAgPC9nPgogICAgICogICA8ZyBjbGFzcz0nb3V0LWV4dHJhY3QnPgogICAgICogICAgIDxnIGNsYXNzPSdub2Rlcyc+CiAgICAgKiAgICAgICAuLi4gc3R1ZmYgZnJvbSB0Zi5ncmFwaC5zY2VuZS5ub2Rlcy5idWlsZCAuLi4KICAgICAqICAgICA8L2c+CiAgICAgKiAgIDwvZz4KICAgICAqIDwvZz4KICAgICAqCiAgICAgKiBAcGFyYW0gY29udGFpbmVyIEQzIHNlbGVjdGlvbiBvZiB0aGUgcGFyZW50LgogICAgICogQHBhcmFtIHJlbmRlck5vZGUgcmVuZGVyIG5vZGUgb2YgYSBtZXRhbm9kZSBvciBzZXJpZXMgbm9kZS4KICAgICAqIEBwYXJhbSBzY2VuZUVsZW1lbnQgPHRmLWdyYXBoLXNjZW5lPiBwb2x5bWVyIGVsZW1lbnQuCiAgICAgKiBAcGFyYW0gc2NlbmVDbGFzcyBjbGFzcyBhdHRyaWJ1dGUgb2YgdGhlIHNjZW5lIChkZWZhdWx0PSdzY2VuZScpLgogICAgICovCiAgICBmdW5jdGlvbiBidWlsZEdyb3VwRm9yU2NlbmUoY29udGFpbmVyLCByZW5kZXJOb2RlLCBzY2VuZUVsZW1lbnQsIHNjZW5lQ2xhc3MpIHsKICAgICAgICBzY2VuZUNsYXNzID0gc2NlbmVDbGFzcyB8fCBDbGFzcyQxLlNjZW5lLkdST1VQOwogICAgICAgIGxldCBpc05ld1NjZW5lR3JvdXAgPSBzZWxlY3RDaGlsZChjb250YWluZXIsICdnJywgc2NlbmVDbGFzcykuZW1wdHkoKTsKICAgICAgICBsZXQgc2NlbmVHcm91cCA9IHNlbGVjdE9yQ3JlYXRlQ2hpbGQoY29udGFpbmVyLCAnZycsIHNjZW5lQ2xhc3MpOwogICAgICAgIC8vIGNvcmUKICAgICAgICBsZXQgY29yZUdyb3VwID0gc2VsZWN0T3JDcmVhdGVDaGlsZChzY2VuZUdyb3VwLCAnZycsIENsYXNzJDEuU2NlbmUuQ09SRSk7CiAgICAgICAgbGV0IGNvcmVOb2RlcyA9IGxvZGFzaC5yZWR1Y2UocmVuZGVyTm9kZS5jb3JlR3JhcGgubm9kZXMoKSwgKG5vZGVzLCBuYW1lKSA9PiB7CiAgICAgICAgICAgIGxldCBub2RlID0gcmVuZGVyTm9kZS5jb3JlR3JhcGgubm9kZShuYW1lKTsKICAgICAgICAgICAgaWYgKCFub2RlLmV4Y2x1ZGVkKSB7CiAgICAgICAgICAgICAgICBub2Rlcy5wdXNoKG5vZGUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBub2RlczsKICAgICAgICB9LCBbXSk7CiAgICAgICAgaWYgKHJlbmRlck5vZGUubm9kZS50eXBlID09PSBOb2RlVHlwZS5TRVJJRVMpIHsKICAgICAgICAgICAgLy8gRm9yIHNlcmllcywgd2Ugd2FudCB0aGUgZmlyc3QgaXRlbSBvbiB0b3AsIHNvIHJldmVyc2UgdGhlIGFycmF5IHNvCiAgICAgICAgICAgIC8vIHRoZSBmaXJzdCBpdGVtIGluIHRoZSBzZXJpZXMgYmVjb21lcyBsYXN0IGl0ZW0gaW4gdGhlIHRvcCwgYW5kIHRodXMKICAgICAgICAgICAgLy8gaXMgcmVuZGVyZWQgb24gdGhlIHRvcC4KICAgICAgICAgICAgY29yZU5vZGVzLnJldmVyc2UoKTsKICAgICAgICB9CiAgICAgICAgLy8gQ3JlYXRlIHRoZSBsYXllciBvZiBlZGdlcyBmb3IgdGhpcyBzY2VuZSAocGF0aHMpLgogICAgICAgIGJ1aWxkR3JvdXAoY29yZUdyb3VwLCByZW5kZXJOb2RlLmNvcmVHcmFwaCwgc2NlbmVFbGVtZW50KTsKICAgICAgICAvLyBDcmVhdGUgdGhlIGxheWVyIG9mIG5vZGVzIGZvciB0aGlzIHNjZW5lIChlbGxpcHNlcywgcmVjdHMgZXRjKS4KICAgICAgICBidWlsZEdyb3VwJDEoY29yZUdyb3VwLCBjb3JlTm9kZXMsIHNjZW5lRWxlbWVudCk7CiAgICAgICAgLy8gSW4tZXh0cmFjdAogICAgICAgIGlmIChyZW5kZXJOb2RlLmlzb2xhdGVkSW5FeHRyYWN0Lmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgbGV0IGluRXh0cmFjdEdyb3VwID0gc2VsZWN0T3JDcmVhdGVDaGlsZChzY2VuZUdyb3VwLCAnZycsIENsYXNzJDEuU2NlbmUuSU5FWFRSQUNUKTsKICAgICAgICAgICAgYnVpbGRHcm91cCQxKGluRXh0cmFjdEdyb3VwLCByZW5kZXJOb2RlLmlzb2xhdGVkSW5FeHRyYWN0LCBzY2VuZUVsZW1lbnQpOwogICAgICAgIH0KICAgICAgICBlbHNlIHsKICAgICAgICAgICAgc2VsZWN0Q2hpbGQoc2NlbmVHcm91cCwgJ2cnLCBDbGFzcyQxLlNjZW5lLklORVhUUkFDVCkucmVtb3ZlKCk7CiAgICAgICAgfQogICAgICAgIC8vIE91dC1leHRyYWN0CiAgICAgICAgaWYgKHJlbmRlck5vZGUuaXNvbGF0ZWRPdXRFeHRyYWN0Lmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgbGV0IG91dEV4dHJhY3RHcm91cCA9IHNlbGVjdE9yQ3JlYXRlQ2hpbGQoc2NlbmVHcm91cCwgJ2cnLCBDbGFzcyQxLlNjZW5lLk9VVEVYVFJBQ1QpOwogICAgICAgICAgICBidWlsZEdyb3VwJDEob3V0RXh0cmFjdEdyb3VwLCByZW5kZXJOb2RlLmlzb2xhdGVkT3V0RXh0cmFjdCwgc2NlbmVFbGVtZW50KTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHNlbGVjdENoaWxkKHNjZW5lR3JvdXAsICdnJywgQ2xhc3MkMS5TY2VuZS5PVVRFWFRSQUNUKS5yZW1vdmUoKTsKICAgICAgICB9CiAgICAgICAgLy8gTGlicmFyeSBmdW5jdGlvbnMKICAgICAgICBpZiAocmVuZGVyTm9kZS5saWJyYXJ5RnVuY3Rpb25zRXh0cmFjdC5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgIGxldCBvdXRFeHRyYWN0R3JvdXAgPSBzZWxlY3RPckNyZWF0ZUNoaWxkKHNjZW5lR3JvdXAsICdnJywgQ2xhc3MkMS5TY2VuZS5GVU5DVElPTl9MSUJSQVJZKTsKICAgICAgICAgICAgYnVpbGRHcm91cCQxKG91dEV4dHJhY3RHcm91cCwgcmVuZGVyTm9kZS5saWJyYXJ5RnVuY3Rpb25zRXh0cmFjdCwgc2NlbmVFbGVtZW50KTsKICAgICAgICB9CiAgICAgICAgZWxzZSB7CiAgICAgICAgICAgIHNlbGVjdENoaWxkKHNjZW5lR3JvdXAsICdnJywgQ2xhc3MkMS5TY2VuZS5GVU5DVElPTl9MSUJSQVJZKS5yZW1vdmUoKTsKICAgICAgICB9CiAgICAgICAgcG9zaXRpb24kMShzY2VuZUdyb3VwLCByZW5kZXJOb2RlKTsKICAgICAgICAvLyBGYWRlIGluIHRoZSBzY2VuZSBncm91cCBpZiBpdCBkaWRuJ3QgYWxyZWFkeSBleGlzdC4KICAgICAgICBpZiAoaXNOZXdTY2VuZUdyb3VwKSB7CiAgICAgICAgICAgIHNjZW5lR3JvdXAuYXR0cignb3BhY2l0eScsIDApLnRyYW5zaXRpb24oKS5hdHRyKCdvcGFjaXR5JywgMSk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBzY2VuZUdyb3VwOwogICAgfQoKICAgIHZhciB0Zl9ncmFwaF9zY2VuZV9ub2RlID0gLyojX19QVVJFX18qL09iamVjdC5mcmVlemUoewogICAgICAgIF9fcHJvdG9fXzogbnVsbCwKICAgICAgICBidWlsZEdyb3VwOiBidWlsZEdyb3VwJDEsCiAgICAgICAgZ2V0Q29udGV4dE1lbnU6IGdldENvbnRleHRNZW51LAogICAgICAgIGNhbkJlSW5TZXJpZXM6IGNhbkJlSW5TZXJpZXMsCiAgICAgICAgZ2V0U2VyaWVzTmFtZTogZ2V0U2VyaWVzTmFtZSwKICAgICAgICBnZXRHcm91cFNldHRpbmdMYWJlbDogZ2V0R3JvdXBTZXR0aW5nTGFiZWwsCiAgICAgICAgZW5mb3JjZUxhYmVsV2lkdGg6IGVuZm9yY2VMYWJlbFdpZHRoLAogICAgICAgIGJ1aWxkU2hhcGU6IGJ1aWxkU2hhcGUsCiAgICAgICAgbm9kZUNsYXNzOiBub2RlQ2xhc3MsCiAgICAgICAgZ2V0IENvbG9yQnkgKCkgeyByZXR1cm4gQ29sb3JCeTsgfSwKICAgICAgICByZW1vdmVHcmFkaWVudERlZmluaXRpb25zOiByZW1vdmVHcmFkaWVudERlZmluaXRpb25zLAogICAgICAgIGdldEZpbGxGb3JOb2RlOiBnZXRGaWxsRm9yTm9kZSwKICAgICAgICBzdHlsaXplOiBzdHlsaXplJDEsCiAgICAgICAgZ2V0U3Ryb2tlRm9yRmlsbDogZ2V0U3Ryb2tlRm9yRmlsbCwKICAgICAgICB1cGRhdGVJbnB1dFRyYWNlOiB1cGRhdGVJbnB1dFRyYWNlLAogICAgICAgIGdldFZpc2libGVQYXJlbnQ6IGdldFZpc2libGVQYXJlbnQsCiAgICAgICAgYnVpbGRHcm91cEZvckFubm90YXRpb246IGJ1aWxkR3JvdXBGb3JBbm5vdGF0aW9uLAogICAgICAgIGJ1aWxkR3JvdXBGb3JTY2VuZTogYnVpbGRHcm91cEZvclNjZW5lCiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBUZk5vZGVJY29uID0gY2xhc3MgVGZOb2RlSWNvbiBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogTm9kZSB0byByZXByZXNlbnQgd2l0aCBhbiBpY29uLiBPcHRpb25hbCwgYnV0IGlmIHNwZWNpZmllZCwgaXRzCiAgICAgICAgICAgICAqIHByb3BlcnRpZXMgb3ZlcnJpZGUgdGhvc2UgZGVmaW5lZCBpbiB0aGUgdHlwZSwgdmVydGljYWwsIGNvbnN0IGFuZAogICAgICAgICAgICAgKiBzdW1tYXJ5IHByb3BlcnRpZXMuCiAgICAgICAgICAgICAqIFRoaXMgcHJvcGVydHkgaXMgYSB0Zi5ncmFwaC5Ob2RlLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5ub2RlID0gbnVsbDsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIFJlbmRlciBub2RlIGluZm9ybWF0aW9uIGFzc29jaWF0ZWQgd2l0aCB0aGlzIG5vZGUuIE9wdGlvbmFsLiBJZgogICAgICAgICAgICAgKiBzcGVjaWZpZWQsIHRoaXMgaXMgb25seSB1c2VkIHdoZW4gY29tcHV0aW5nIHRoZSBmaWxsIG9mIHRoZSBpY29uCiAgICAgICAgICAgICAqIGVsZW1lbnQuCiAgICAgICAgICAgICAqIFRoaXMgcHJvcGVydHkgaXMgYSB0Zi5ncmFwaC5yZW5kZXIuUmVuZGVyTm9kZUluZm8uCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnJlbmRlckluZm8gPSBudWxsOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogU3RyaW5nIGluZGljYXRpbmcgdGhlIHR5cGUgb2YgY29sb3JpbmcgdG8gdXNlIGZvciB0aGlzIG5vZGUsIHVzZWQKICAgICAgICAgICAgICogb25seSBmb3IgZGV0ZXJtaW5pbmcgdGhlIGZpbGwuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmNvbG9yQnkgPSAnc3RydWN0dXJhbCc7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBGdW5jdGlvbiB1c2VkIGJ5IHN0cnVjdHVyYWwgY29sb3JpbmcgYWxnb3JpdGhtIHRvIGRldGVybWluZSB3aGljaAogICAgICAgICAgICAgKiBjb2xvciB0byB1c2UgYmFzZWQgb24gdGhlIHRlbXBsYXRlIElEIG9mIHRoZSBub2RlLiBPcHRpb25hbC4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMudGVtcGxhdGVJbmRleCA9IG51bGw7CiAgICAgICAgICAgIC8qKiBUeXBlIG9mIG5vZGUgdG8gZHJhdyAoaWdub3JlZCBpZiBub2RlIGlzIHNldCkuICovCiAgICAgICAgICAgIHRoaXMudHlwZSA9IG51bGw7CiAgICAgICAgICAgIC8qKiBEaXJlY3Rpb24gZm9yIHNlcmllcyAoaWdub3JlZCBmb3Igb3RoZXIgdHlwZXMpLiAqLwogICAgICAgICAgICB0aGlzLnZlcnRpY2FsID0gZmFsc2U7CiAgICAgICAgICAgIC8qKiBXaGV0aGVyIHRoZSBvcCBpcyBDb25zdCAoaWdub3JlZCBmb3Igbm9uLW9wcykuICovCiAgICAgICAgICAgIHRoaXMuY29uc3QgPSBmYWxzZTsKICAgICAgICAgICAgLyoqIFdoZXRoZXIgdGhlIG9wIGlzIGEgU3VtbWFyeSAoaWdub3JlZCBmb3Igbm9uLW9wcykuICovCiAgICAgICAgICAgIHRoaXMuc3VtbWFyeSA9IGZhbHNlOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogRmlsbCBmb3IgdGhlIGljb24sIG9wdGlvbmFsLiBJZiBmaWxsIGlzIHNwZWNpZmllZCBhbmQgbm9kZSBpcyBub3QKICAgICAgICAgICAgICogc3BlY2lmaWVkLCB0aGVuIHRoaXMgdmFsdWUgd2lsbCBvdmVycmlkZSB0aGUgZGVmYXVsdCBmb3IgdGhlCiAgICAgICAgICAgICAqIGVsZW1lbnQuIEhvd2V2ZXIsIGlmIG5vZGUgaXMgc3BlY2lmaWVkLCB0aGlzIHZhbHVlIHdpbGwgYmUgaWdub3JlZC4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMuZmlsbCA9IG51bGw7CiAgICAgICAgICAgIC8qKiBIZWlnaHQgb2YgdGhlIFNWRyBlbGVtZW50IGluIHBpeGVscywgdXNlZCBmb3Igc2NhbGluZy4gKi8KICAgICAgICAgICAgdGhpcy5oZWlnaHQgPSAyMDsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyBmaWxsIHZhbHVlIGJhc2VkIG9uIG5vZGUgYW5kIGNvbmZpZ3VyYXRpb24uIElmIGFueSBvZiB0aG9zZQogICAgICAgICAqIGNvbmZpZ3VyYXRpb25zIG9yIG5vZGUgdmFsdWUgbWlzc2luZywgaXQgcmV0dXJucyBgZmlsbGAgcHJvcGVydHkuCiAgICAgICAgICogTm90ZSB0aGF0IGlmIHRoaXMgZXZhbHVhdGVzIHRvIG51bGwsIGl0IHdpbGwgYmUgY2hvc2VuIGJhc2VkIG9uCiAgICAgICAgICogdGhlIHR5cGUgb2YgdGhlIG5vZGUuCiAgICAgICAgICovCiAgICAgICAgX2NvbXB1dGVGaWxsT3ZlcnJpZGUoaW5wdXROb2RlLCBpbnB1dFJlbmRlckluZm8sIGlucHV0Q29sb3JCeSwgaW5wdXRUZW1wbGF0ZUluZGV4LCBpbnB1dEZpbGwpIHsKICAgICAgICAgICAgaWYgKGlucHV0Tm9kZSAmJiBpbnB1dFJlbmRlckluZm8gJiYgaW5wdXRDb2xvckJ5ICYmIGlucHV0VGVtcGxhdGVJbmRleCkgewogICAgICAgICAgICAgICAgdmFyIG5zID0gdGZfZ3JhcGhfc2NlbmVfbm9kZTsKICAgICAgICAgICAgICAgIHZhciBjb2xvckJ5ID0gbnMuQ29sb3JCeVtpbnB1dENvbG9yQnkudG9VcHBlckNhc2UoKV07CiAgICAgICAgICAgICAgICByZXR1cm4gbnMuZ2V0RmlsbEZvck5vZGUoaW5wdXRUZW1wbGF0ZUluZGV4LCBjb2xvckJ5LCBpbnB1dFJlbmRlckluZm8sIGZhbHNlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gaW5wdXRGaWxsOwogICAgICAgIH0KICAgICAgICBfZ2V0U3Ryb2tlT3ZlcnJpZGUoZmlsbE92ZXJyaWRlKSB7CiAgICAgICAgICAgIHJldHVybiBmaWxsT3ZlcnJpZGUKICAgICAgICAgICAgICAgID8gZ2V0U3Ryb2tlRm9yRmlsbChmaWxsT3ZlcnJpZGUpCiAgICAgICAgICAgICAgICA6IG51bGw7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJldHVybnMgZ3JhcGgtaWNvbiB0eXBlIGZyb20gaW5wdXQsIHR5cGUsIGFuZCBzdW1tYXJ5LgogICAgICAgICAqLwogICAgICAgIF9nZXRUeXBlKGlucHV0Tm9kZSwgaXNTdW1tYXJ5LCBpc0NvbnN0LCBpbnB1dFR5cGUpIHsKICAgICAgICAgICAgY29uc3QgeyBHcmFwaEljb25UeXBlIH0gPSB0Zl9ncmFwaF9pY29uOwogICAgICAgICAgICBpZiAoaW5wdXROb2RlKSB7CiAgICAgICAgICAgICAgICBzd2l0Y2ggKGlucHV0Tm9kZS50eXBlKSB7CiAgICAgICAgICAgICAgICAgICAgY2FzZSBOb2RlVHlwZS5PUDogewogICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBvcE5hbWUgPSBpbnB1dE5vZGUub3A7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFRPRE8odGVuc29yYm9hcmFkLXRlYW0pOiBgb3BgIHNob3VsZCBoYXZlIGEgcHJlZGljdGFibGUgdHlwZS4KICAgICAgICAgICAgICAgICAgICAgICAgLy8gUmVtb3ZlIHRoZSB0eXBlIGNoZWNrLgogICAgICAgICAgICAgICAgICAgICAgICBpZiAodHlwZW9mIG9wTmFtZSAhPT0gJ3N0cmluZycpCiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gR3JhcGhJY29uVHlwZS5PUDsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG9wTmFtZSA9PT0gJ0NvbnN0JyB8fCBpc0NvbnN0KQogICAgICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIEdyYXBoSWNvblR5cGUuQ09OU1Q7CiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChvcE5hbWUuZW5kc1dpdGgoJ1N1bW1hcnknKSB8fCBpc1N1bW1hcnkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiBHcmFwaEljb25UeXBlLlNVTU1BUlk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIEdyYXBoSWNvblR5cGUuT1A7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGNhc2UgTm9kZVR5cGUuTUVUQToKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIEdyYXBoSWNvblR5cGUuTUVUQTsKICAgICAgICAgICAgICAgICAgICBjYXNlIE5vZGVUeXBlLlNFUklFUzoKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIEdyYXBoSWNvblR5cGUuU0VSSUVTOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBpbnB1dFR5cGU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFRlc3Qgd2hldGhlciB0aGUgc3BlY2lmaWVkIG5vZGUgc2hvdWxkIGJlIHJlcHJlc2VudGVkIGFzIGEgdmVydGljYWwKICAgICAgICAgKiBzZXJpZXMuIERlZmF1bHRzIHRvIHRoZSB2YWx1ZSBvZiB0aGUgdmVydGljYWwgcHJvcGVydHkgaWYgbm9kZSBpcwogICAgICAgICAqIG5vdCBzcGVjaWZpZWQuCiAgICAgICAgICovCiAgICAgICAgX2lzVmVydGljYWwoaW5wdXROb2RlLCBpbnB1dFZlcnRpY2FsKSB7CiAgICAgICAgICAgIGlmIChpbnB1dE5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBpbnB1dE5vZGUuaGFzTm9uQ29udHJvbEVkZ2VzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiAhIWlucHV0VmVydGljYWw7CiAgICAgICAgfQogICAgICAgIF9nZXRGYWRlZChpdGVtUmVuZGVySW5mbykgewogICAgICAgICAgICByZXR1cm4gaXRlbVJlbmRlckluZm8gJiYgaXRlbVJlbmRlckluZm8uaXNGYWRlZE91dDsKICAgICAgICB9CiAgICAgICAgX29uRmlsbE92ZXJyaWRlQ2hhbmdlZChuZXdGaWxsLCBvbGRGaWxsKSB7CiAgICAgICAgICAgIGNvbnN0IHsgbm9kZSwgcmVuZGVySW5mbywgY29sb3JCeSwgdGVtcGxhdGVJbmRleCB9ID0gdGhpczsKICAgICAgICAgICAgY29uc3QgbnMgPSB0Zl9ncmFwaF9zY2VuZV9ub2RlOwogICAgICAgICAgICBpZiAobmV3RmlsbCAhPT0gb2xkRmlsbCkgewogICAgICAgICAgICAgICAgbnMucmVtb3ZlR3JhZGllbnREZWZpbml0aW9ucyh0aGlzLiQuaWNvbi5nZXRTdmdEZWZpbmFibGVFbGVtZW50KCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChub2RlICYmIHJlbmRlckluZm8gJiYgY29sb3JCeSAmJiB0ZW1wbGF0ZUluZGV4KSB7CiAgICAgICAgICAgICAgICBjb25zdCBuc0NvbG9yQnkgPSBucy5Db2xvckJ5W2NvbG9yQnkudG9VcHBlckNhc2UoKV07CiAgICAgICAgICAgICAgICBucy5nZXRGaWxsRm9yTm9kZSh0ZW1wbGF0ZUluZGV4LCBuc0NvbG9yQnksIHJlbmRlckluZm8sIGZhbHNlLCB0aGlzLiQuaWNvbi5nZXRTdmdEZWZpbmFibGVFbGVtZW50KCkpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfTsKICAgIFRmTm9kZUljb24udGVtcGxhdGUgPSBodG1sIGAKICAgIDxzdHlsZT4KICAgICAgdGYtZ3JhcGgtaWNvbiB7CiAgICAgICAgLS10Yi1ncmFwaC1mYWRlZDogdmFyKC0tdGItZ3JhcGgtZmFkZWQpOwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPHRmLWdyYXBoLWljb24KICAgICAgaWQ9Imljb24iCiAgICAgIHR5cGU9IltbX2dldFR5cGUobm9kZSwgc3VtbWFyeSwgY29uc3QsIHR5cGUpXV0iCiAgICAgIGhlaWdodD0iW1toZWlnaHRdXSIKICAgICAgZmlsbC1vdmVycmlkZT0iW1tfZmlsbE92ZXJyaWRlXV0iCiAgICAgIHN0cm9rZS1vdmVycmlkZT0iW1tfZ2V0U3Ryb2tlT3ZlcnJpZGUoX2ZpbGxPdmVycmlkZSldXSIKICAgICAgZmFkZWQ9IltbX2dldEZhZGVkKHJlbmRlckluZm8pXV0iCiAgICAgIHZlcnRpY2FsPSJbW19pc1ZlcnRpY2FsKG5vZGUsIHZlcnRpY2FsKV1dIgogICAgPjwvdGYtZ3JhcGgtaWNvbj4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJY29uLnByb3RvdHlwZSwgIm5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJY29uLnByb3RvdHlwZSwgInJlbmRlckluZm8iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJY29uLnByb3RvdHlwZSwgImNvbG9yQnkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJY29uLnByb3RvdHlwZSwgInRlbXBsYXRlSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVJY29uLnByb3RvdHlwZSwgInR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAidmVydGljYWwiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAiY29uc3QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAic3VtbWFyeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAiZmlsbCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAiaGVpZ2h0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBjb21wdXRlZDogJ19jb21wdXRlRmlsbE92ZXJyaWRlKG5vZGUsIHJlbmRlckluZm8sIGNvbG9yQnksIHRlbXBsYXRlSW5kZXgsIGZpbGwpJywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfb25GaWxsT3ZlcnJpZGVDaGFuZ2VkJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmTm9kZUljb24ucHJvdG90eXBlLCAiX2ZpbGxPdmVycmlkZSIsIHZvaWQgMCk7CiAgICBUZk5vZGVJY29uID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtbm9kZS1pY29uJykKICAgIF0sIFRmTm9kZUljb24pOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmR3JhcGhPcENvbXBhdExpc3RJdGVtID0gY2xhc3MgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0gZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBfaXRlbVR5cGVDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAodGhpcy5pdGVtVHlwZSAhPT0gJ3N1Ym5vZGUnKSB7CiAgICAgICAgICAgICAgICB0aGlzLiRbJ2xpc3QtaXRlbSddLmNsYXNzTGlzdC5hZGQoJ2NsaWNrYWJsZScpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy4kWydsaXN0LWl0ZW0nXS5jbGFzc0xpc3QucmVtb3ZlKCdjbGlja2FibGUnKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfbm9kZUxpc3RlbmVyKGV2ZW50KSB7CiAgICAgICAgICAgIC8vIGZpcmUgbm9kZS5jbGljay9tb3VzZW92ZXIvbW91c2VvdXQKICAgICAgICAgICAgdGhpcy5maXJlKCdub2RlLWxpc3QtaXRlbS0nICsgZXZlbnQudHlwZSwgewogICAgICAgICAgICAgICAgbm9kZU5hbWU6IHRoaXMubmFtZSwKICAgICAgICAgICAgICAgIHR5cGU6IHRoaXMuaXRlbVR5cGUsCiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfZmFkZWRDbGFzcyhpdGVtUmVuZGVySW5mbykgewogICAgICAgICAgICByZXR1cm4gaXRlbVJlbmRlckluZm8gJiYgaXRlbVJlbmRlckluZm8uaXNGYWRlZE91dCA/ICdmYWRlZCcgOiAnJzsKICAgICAgICB9CiAgICB9OwogICAgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0udGVtcGxhdGUgPSBodG1sIGAKICAgIDxzdHlsZT4KICAgICAgI2xpc3QtaXRlbSB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgY29sb3I6ICM1NjU2NTY7CiAgICAgICAgZm9udC1zaXplOiAxMXB0OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgfQoKICAgICAgI2xpc3QtaXRlbTpob3ZlciB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tZ29vZ2xlLXllbGxvdy0xMDApOwogICAgICB9CgogICAgICAuY2xpY2thYmxlIHsKICAgICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgIH0KCiAgICAgICNsaXN0LWl0ZW0gc3BhbiB7CiAgICAgICAgbWFyZ2luLWxlZnQ6IDQwcHg7CiAgICAgIH0KCiAgICAgICNsaXN0LWl0ZW0uZXhjbHVkZWQgc3BhbiB7CiAgICAgICAgY29sb3I6ICM5OTk7CiAgICAgIH0KCiAgICAgICNsaXN0LWl0ZW0gc3Bhbi5lZGdlLWxhYmVsIHsKICAgICAgICBmbG9hdDogcmlnaHQ7CiAgICAgICAgZm9udC1zaXplOiAxMHB4OwogICAgICAgIG1hcmdpbi1sZWZ0OiAzcHg7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiA1cHg7CiAgICAgIH0KCiAgICAgIC5ub2RlLWljb24gewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDFweDsKICAgICAgICBsZWZ0OiAycHg7CiAgICAgIH0KCiAgICAgIC5mYWRlZCBzcGFuIHsKICAgICAgICBjb2xvcjogdmFyKC0tdGItZ3JhcGgtZmFkZWQpOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxkaXYKICAgICAgaWQ9Imxpc3QtaXRlbSIKICAgICAgb24tbW91c2VvdmVyPSJfbm9kZUxpc3RlbmVyIgogICAgICBvbi1tb3VzZW91dD0iX25vZGVMaXN0ZW5lciIKICAgICAgb24tY2xpY2s9Il9ub2RlTGlzdGVuZXIiCiAgICA+CiAgICAgIDxkaXYgY2xhc3MkPSJ7e19mYWRlZENsYXNzKGl0ZW1SZW5kZXJJbmZvKX19Ij4KICAgICAgICA8dGYtbm9kZS1pY29uCiAgICAgICAgICBjbGFzcz0ibm9kZS1pY29uIgogICAgICAgICAgaGVpZ2h0PSIxMiIKICAgICAgICAgIGNvbG9yLWJ5PSJbW2NvbG9yQnldXSIKICAgICAgICAgIGNvbG9yLWJ5LXBhcmFtcz0iW1tjb2xvckJ5UGFyYW1zXV0iCiAgICAgICAgICBub2RlPSJbW2l0ZW1Ob2RlXV0iCiAgICAgICAgICByZW5kZXItaW5mbz0iW1tpdGVtUmVuZGVySW5mb11dIgogICAgICAgICAgdGVtcGxhdGUtaW5kZXg9IltbdGVtcGxhdGVJbmRleF1dIgogICAgICAgID4KICAgICAgICA8L3RmLW5vZGUtaWNvbj4KICAgICAgICA8c3BhbiB0aXRsZSQ9IltbbmFtZV1dIj5bW25hbWVdXTwvc3Bhbj4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoT3BDb21wYXRMaXN0SXRlbS5wcm90b3R5cGUsICJjYXJkTm9kZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhPcENvbXBhdExpc3RJdGVtLnByb3RvdHlwZSwgIml0ZW1Ob2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0ucHJvdG90eXBlLCAiZWRnZUxhYmVsIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0ucHJvdG90eXBlLCAiaXRlbVJlbmRlckluZm8iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoT3BDb21wYXRMaXN0SXRlbS5wcm90b3R5cGUsICJuYW1lIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBvYnNlcnZlcjogJ19pdGVtVHlwZUNoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0ucHJvdG90eXBlLCAiaXRlbVR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoT3BDb21wYXRMaXN0SXRlbS5wcm90b3R5cGUsICJjb2xvckJ5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0ucHJvdG90eXBlLCAiY29sb3JCeVBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhPcENvbXBhdExpc3RJdGVtLnByb3RvdHlwZSwgInRlbXBsYXRlSW5kZXgiLCB2b2lkIDApOwogICAgVGZHcmFwaE9wQ29tcGF0TGlzdEl0ZW0gPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ncmFwaC1vcC1jb21wYXQtbGlzdC1pdGVtJykKICAgIF0sIFRmR3JhcGhPcENvbXBhdExpc3RJdGVtKTsKCiAgICBmdW5jdGlvbiBkZXRlY3QoaCwgdmVyaWZ5VGVtcGxhdGUpIHsKICAgICAgICAvLyBJbiBhbnkgcGFydGljdWxhciBzdWJncmFwaCwgdGhlcmUgYXJlIGVpdGhlcgogICAgICAgIC8vIC0gbGVhZiBub2RlcyAod2hpY2ggZG8gbm90IGhhdmUgc3ViZ3JhcGgpCiAgICAgICAgLy8gLSBtZXRhbm9kZSBub2RlcyAtIHNvbWUgb2YgdGhlbSBoYXZlIG9ubHkgb25lIG1lbWJlciAoc2luZ3VsYXIgbWV0YW5vZGUpCiAgICAgICAgLy8gICAgICAgICAgICAgICAgICAgIGFuZCBzb21lIGhhdmUgbXVsdGlwbGUgbWVtYmVycyAobm9uLXNpbmd1bGFyIG1ldGFub2RlKQogICAgICAgIC8vIEZpcnN0LCBnZW5lcmF0ZSBhIG5lYXJlc3QgbmVpZ2hib3IgaGFzaCBvZiBtZXRhbm9kZSBub2Rlcy4KICAgICAgICBsZXQgbm5Hcm91cHMgPSBjbHVzdGVyU2ltaWxhclN1YmdyYXBocyhoKTsKICAgICAgICAvLyBGb3IgZWFjaCBtZXRhbm9kZSwgY29tcGFyZSBpdHMgc3ViZ3JhcGggKHN0YXJ0aW5nIGZyb20gc2hhbGxvd2VyIGdyb3VwcykKICAgICAgICAvLyBhbmQgYXNzaWduIHRlbXBsYXRlIGlkLgogICAgICAgIGxldCB0ZW1wbGF0ZXMgPSBncm91cFRlbXBsYXRlQW5kQXNzaWduSWQobm5Hcm91cHMsIHZlcmlmeVRlbXBsYXRlKTsKICAgICAgICAvLyBTb3J0IHRoZSB0ZW1wbGF0ZXMgYnkgbWluaW11bSBsZXZlbCBpbiB0aGUgZ3JhcGggYXQgd2hpY2ggdGhleSBhcHBlYXIsCiAgICAgICAgLy8gYXMgdGhpcyBsZWFkcyB0byBvcHRpbWFsIHNldHRpbmcgb2YgdGhlIGNvbG9ycyBvZiBlYWNoIHRlbXBsYXRlIGZvcgogICAgICAgIC8vIG1heGltdW0gZGlmZmVyZW50aWF0aW9uLgogICAgICAgIHJldHVybiBPYmplY3Qua2V5cyh0ZW1wbGF0ZXMpCiAgICAgICAgICAgIC5zb3J0KChrZXkpID0+IHRlbXBsYXRlc1trZXldLmxldmVsKQogICAgICAgICAgICAucmVkdWNlKChvYmosIGtleSkgPT4gewogICAgICAgICAgICBvYmpba2V5XSA9IHRlbXBsYXRlc1trZXldOwogICAgICAgICAgICByZXR1cm4gb2JqOwogICAgICAgIH0sIHt9KTsKICAgIH0KICAgIC8qKgogICAgICogQHJldHVybiBVbmlxdWUgc3RyaW5nIGZvciBhIG1ldGFub2RlIGJhc2VkIG9uIGRlcHRoLCB8VnwsIHxFfCBhbmQKICAgICAqIG9wIHR5cGUgaGlzdG9ncmFtLgogICAgICovCiAgICBmdW5jdGlvbiBnZXRTaWduYXR1cmUobWV0YW5vZGUpIHsKICAgICAgICAvLyBkZXB0aD08bnVtYmVyPiB8Vnw9PG51bWJlcj4gfEV8PTxudW1iZXI+CiAgICAgICAgbGV0IHByb3BzID0gbG9kYXNoLm1hcCh7CiAgICAgICAgICAgIGRlcHRoOiBtZXRhbm9kZS5kZXB0aCwKICAgICAgICAgICAgJ3xWfCc6IG1ldGFub2RlLm1ldGFncmFwaC5ub2RlcygpLmxlbmd0aCwKICAgICAgICAgICAgJ3xFfCc6IG1ldGFub2RlLm1ldGFncmFwaC5lZGdlcygpLmxlbmd0aCwKICAgICAgICB9LCBmdW5jdGlvbiAodiwgaykgewogICAgICAgICAgICByZXR1cm4gayArICc9JyArIHY7CiAgICAgICAgfSkuam9pbignICcpOwogICAgICAgIC8vIG9wdHlwZTE9Y291bnQxLG9wdHlwZTI9Y291bnQyCiAgICAgICAgbGV0IG9wcyA9IGxvZGFzaC5tYXAobWV0YW5vZGUub3BIaXN0b2dyYW0sIGZ1bmN0aW9uIChjb3VudCwgb3ApIHsKICAgICAgICAgICAgcmV0dXJuIG9wICsgJz0nICsgY291bnQ7CiAgICAgICAgfSkuam9pbignLCcpOwogICAgICAgIHJldHVybiBwcm9wcyArICcgW29wc10gJyArIG9wczsKICAgIH0KICAgIC8qKgogICAgICogR2VuZXJhdGUgYSBuZWFyZXN0IG5laWdoYm9yIGhhc2ggb2YgbWV0YW5vZGVzCiAgICAgKiBiYXNlZCBvbiBkZXB0aCwgfFZ8LCB8RXwsIGFuZCBvcEhpc3RvZ3JhbSBvZiB0aGVpciBzdWJncmFwaAogICAgICogKGV4Y2x1ZGluZyBsZWFmIG5vZGVzIGFuZCBzaW5ndWxhciBtZXRhbm9kZXMpLgogICAgICogQHBhcmFtIGdyYXBoIFRoZSBncmFwaAogICAgICogQHJldHVybiBBcnJheSBvZiBwYWlycyBvZiBbc2lnbmF0dXJlLAogICAgICogICBPYmplY3Qgd2l0aCBtaW4gbGV2ZWwgb2YgdGhlIHRlbXBsYXRlIGFuZCBhbiBBcnJheSBvZiB0Zi5ncmFwaC5Hcm91cF0KICAgICAqICAgc29ydCBieSBhc2NlbmRpbmcgb3JkZXIgb2YgbWluaW11bSBkZXB0aCBhdCB3aGljaCBtZXRhbm9kZSBhcHBlYXJzLgogICAgICovCiAgICBmdW5jdGlvbiBjbHVzdGVyU2ltaWxhclN1YmdyYXBocyhoKSB7CiAgICAgICAgLyoqIGEgZGljdCBmcm9tIG1ldGFub2RlLnNpZ25hdHVyZSgpID0+IEFycmF5IG9mIHRmLmdyYXBoLkdyb3VwcyAqLwogICAgICAgIGNvbnN0IG1hcCA9IGguZ2V0Tm9kZU1hcCgpOwogICAgICAgIGxldCBoYXNoRGljdCA9IE9iamVjdC5rZXlzKG1hcCkucmVkdWNlKChyZWR1Y2VkLCBuYW1lKSA9PiB7CiAgICAgICAgICAgIGNvbnN0IG5vZGUgPSBtYXBbbmFtZV07CiAgICAgICAgICAgIGlmIChub2RlLnR5cGUgIT09IE5vZGVUeXBlLk1FVEEpIHsKICAgICAgICAgICAgICAgIHJldHVybiByZWR1Y2VkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBsZXZlbE9mTWV0YU5vZGUgPSBuYW1lLnNwbGl0KCcvJykubGVuZ3RoIC0gMTsKICAgICAgICAgICAgbGV0IHNpZ25hdHVyZSA9IGdldFNpZ25hdHVyZShub2RlKTsKICAgICAgICAgICAgbGV0IHRlbXBsYXRlSW5mbyA9IHJlZHVjZWRbc2lnbmF0dXJlXSB8fCB7CiAgICAgICAgICAgICAgICBub2RlczogW10sCiAgICAgICAgICAgICAgICBsZXZlbDogbGV2ZWxPZk1ldGFOb2RlLAogICAgICAgICAgICB9OwogICAgICAgICAgICByZWR1Y2VkW3NpZ25hdHVyZV0gPSB0ZW1wbGF0ZUluZm87CiAgICAgICAgICAgIHRlbXBsYXRlSW5mby5ub2Rlcy5wdXNoKG5vZGUpOwogICAgICAgICAgICBpZiAodGVtcGxhdGVJbmZvLmxldmVsID4gbGV2ZWxPZk1ldGFOb2RlKSB7CiAgICAgICAgICAgICAgICB0ZW1wbGF0ZUluZm8ubGV2ZWwgPSBsZXZlbE9mTWV0YU5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHJlZHVjZWQ7CiAgICAgICAgfSwge30pOwogICAgICAgIHJldHVybiBPYmplY3Qua2V5cyhoYXNoRGljdCkKICAgICAgICAgICAgLm1hcCgoa2V5KSA9PiBba2V5LCBoYXNoRGljdFtrZXldXSkKICAgICAgICAgICAgLmZpbHRlcigoW18sIHN1YkdyYXBoXSkgPT4gewogICAgICAgICAgICBjb25zdCB7IG5vZGVzIH0gPSBzdWJHcmFwaDsKICAgICAgICAgICAgaWYgKG5vZGVzLmxlbmd0aCA+IDEpIHsKICAgICAgICAgICAgICAgIC8vIFRoZXJlIGlzIG1vcmUgdGhhbiAxIG5vZGUgd2l0aCB0aGlzIHRlbXBsYXRlLiBJdCBpcyB3b3J0aCBhc3NpZ25pbmcKICAgICAgICAgICAgICAgIC8vIGEgdW5pcXVlIGNvbG9yIHRvIHRoaXMgdGVtcGxhdGUuCiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBJZiB0aGVyZSBpcyBvbmx5IDEgbm9kZSB3aXRoIHRoaXMgdGVtcGxhdGUsIG9ubHkgbWFrZSBhIHRlbXBsYXRlIGZvcgogICAgICAgICAgICAvLyBpdCBpZiBpdCByZXByZXNlbnRzIGEgZnVuY3Rpb24uIEluIHRoYXQgY2FzZSwgdGhlIGdyYXBoIGV4cGxvcmVyIG1heQogICAgICAgICAgICAvLyBhZGQgbW9yZSBub2RlcyB3aXRoIHRoZSB0ZW1wbGF0ZSBsYXRlci4KICAgICAgICAgICAgY29uc3Qgbm9kZSA9IG5vZGVzWzBdOwogICAgICAgICAgICByZXR1cm4gKG5vZGUudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSAmJiBub2RlLmFzc29jaWF0ZWRGdW5jdGlvbik7CiAgICAgICAgfSkKICAgICAgICAgICAgLnNvcnQoKFtfLCBzdWJHcmFwaF0pID0+IHsKICAgICAgICAgICAgLy8gc29ydCBieSBkZXB0aAogICAgICAgICAgICAvLyAoYWxsIG1lbWJlcnMgaW4gdGhlIHNhbWUgbm5Hcm91cCBoYXMgZXF1YWwgZGVwdGgpCiAgICAgICAgICAgIHJldHVybiBzdWJHcmFwaC5ub2Rlc1swXS5kZXB0aDsKICAgICAgICB9KTsKICAgIH0KICAgIGZ1bmN0aW9uIGdyb3VwVGVtcGxhdGVBbmRBc3NpZ25JZChubkdyb3VwcywgdmVyaWZ5VGVtcGxhdGUpIHsKICAgICAgICAvLyBGb3IgZWFjaCBtZXRhbm9kZSwgY29tcGFyZSBpdHMgc3ViZ3JhcGggKHN0YXJ0aW5nIGZyb20gc2hhbGxvd2VyIGdyb3VwcykKICAgICAgICAvLyBhbmQgYXNzaWduIHRlbXBsYXRlIGlkLgogICAgICAgIGxldCByZXN1bHQgPSB7fTsKICAgICAgICByZXR1cm4gbG9kYXNoLnJlZHVjZShubkdyb3VwcywgZnVuY3Rpb24gKHRlbXBsYXRlcywgbm5Hcm91cFBhaXIpIHsKICAgICAgICAgICAgbGV0IHNpZ25hdHVyZSA9IG5uR3JvdXBQYWlyWzBdLCBubkdyb3VwID0gbm5Hcm91cFBhaXJbMV0ubm9kZXMsIGNsdXN0ZXJzID0gW107CiAgICAgICAgICAgIG5uR3JvdXAuZm9yRWFjaChmdW5jdGlvbiAobWV0YW5vZGUpIHsKICAgICAgICAgICAgICAgIC8vIGNoZWNrIHdpdGggZWFjaCBleGlzdGluZyBjbHVzdGVyCiAgICAgICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGNsdXN0ZXJzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IHNpbWlsYXIgPSAhdmVyaWZ5VGVtcGxhdGUgfHwKICAgICAgICAgICAgICAgICAgICAgICAgaXNTaW1pbGFyU3ViZ3JhcGgoY2x1c3RlcnNbaV0ubWV0YW5vZGUubWV0YWdyYXBoLCBtZXRhbm9kZS5tZXRhZ3JhcGgpOwogICAgICAgICAgICAgICAgICAgIC8vIGlmIHNpbWlsYXIsIGp1c3QgYWRkIHRoaXMgbWV0YW5vZGUgdG8gdGhlIGNsdXN0ZXIKICAgICAgICAgICAgICAgICAgICBpZiAoc2ltaWxhcikgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBnZXQgdGVtcGxhdGUgZnJvbSB0aGUgZmlyc3Qgb25lCiAgICAgICAgICAgICAgICAgICAgICAgIG1ldGFub2RlLnRlbXBsYXRlSWQgPSBjbHVzdGVyc1tpXS5tZXRhbm9kZS50ZW1wbGF0ZUlkOwogICAgICAgICAgICAgICAgICAgICAgICBjbHVzdGVyc1tpXS5tZW1iZXJzLnB1c2gobWV0YW5vZGUubmFtZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBvdGhlcndpc2UgY3JlYXRlIGEgbmV3IGNsdXN0ZXIgd2l0aCBpZCAnc2lnbmF0dXJlIFtjb3VudF0gJwogICAgICAgICAgICAgICAgbWV0YW5vZGUudGVtcGxhdGVJZCA9IHNpZ25hdHVyZSArICdbJyArIGNsdXN0ZXJzLmxlbmd0aCArICddJzsKICAgICAgICAgICAgICAgIGNsdXN0ZXJzLnB1c2goewogICAgICAgICAgICAgICAgICAgIG1ldGFub2RlOiBtZXRhbm9kZSwKICAgICAgICAgICAgICAgICAgICBtZW1iZXJzOiBbbWV0YW5vZGUubmFtZV0sCiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGNsdXN0ZXJzLmZvckVhY2goZnVuY3Rpb24gKGMpIHsKICAgICAgICAgICAgICAgIHRlbXBsYXRlc1tjLm1ldGFub2RlLnRlbXBsYXRlSWRdID0gewogICAgICAgICAgICAgICAgICAgIGxldmVsOiBubkdyb3VwUGFpclsxXS5sZXZlbCwKICAgICAgICAgICAgICAgICAgICBub2RlczogYy5tZW1iZXJzLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiB0ZW1wbGF0ZXM7CiAgICAgICAgfSwgcmVzdWx0KTsKICAgIH0KICAgIGZ1bmN0aW9uIHNvcnROb2RlcyhuYW1lcywgZ3JhcGgsIHByZWZpeCkgewogICAgICAgIHJldHVybiBsb2Rhc2guc29ydEJ5KG5hbWVzLCBbCiAgICAgICAgICAgIChuYW1lKSA9PiBncmFwaC5ub2RlKG5hbWUpLm9wLAogICAgICAgICAgICAobmFtZSkgPT4gZ3JhcGgubm9kZShuYW1lKS50ZW1wbGF0ZUlkLAogICAgICAgICAgICAobmFtZSkgPT4gZ3JhcGgubmVpZ2hib3JzKG5hbWUpLmxlbmd0aCwKICAgICAgICAgICAgKG5hbWUpID0+IGdyYXBoLnByZWRlY2Vzc29ycyhuYW1lKS5sZW5ndGgsCiAgICAgICAgICAgIChuYW1lKSA9PiBncmFwaC5zdWNjZXNzb3JzKG5hbWUpLmxlbmd0aCwKICAgICAgICAgICAgKG5hbWUpID0+IG5hbWUuc3Vic3RyKHByZWZpeC5sZW5ndGgpLAogICAgICAgIF0pOwogICAgfQogICAgZnVuY3Rpb24gaXNTaW1pbGFyU3ViZ3JhcGgoZzEsIGcyKSB7CiAgICAgICAgaWYgKCFoYXNTaW1pbGFyRGVncmVlU2VxdWVuY2UoZzEsIGcyKSkgewogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIC8vIGlmIHdlIHdhbnQgdG8gc2tpcCwganVzdCByZXR1cm4gdHJ1ZSBoZXJlLgogICAgICAgIC8vIHJldHVybiB0cnVlOwogICAgICAgIC8vIFZlcmlmeSBzZXF1ZW5jZSBieSBydW5uaW5nIERGUwogICAgICAgIGxldCBnMXByZWZpeCA9IGcxLmdyYXBoKCkubmFtZTsKICAgICAgICBsZXQgZzJwcmVmaXggPSBnMi5ncmFwaCgpLm5hbWU7CiAgICAgICAgbGV0IHZpc2l0ZWQxID0ge307CiAgICAgICAgbGV0IHZpc2l0ZWQyID0ge307CiAgICAgICAgbGV0IHN0YWNrID0gW107CiAgICAgICAgLyoqCiAgICAgICAgICogcHVzaCBzb3VyY2VzIG9yIHN1Y2Nlc3NvcnMgaW50byB0aGUgc3RhY2sKICAgICAgICAgKiBpZiB0aGUgdmlzaXRpbmcgcGF0dGVybiBoYXMgYmVlbiBzaW1pbGFyLgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIHN0YWNrUHVzaElmTm90RGlmZmVyZW50KG4xLCBuMikgewogICAgICAgICAgICBsZXQgc3ViMSA9IG4xLnN1YnN0cihnMXByZWZpeC5sZW5ndGgpLCBzdWIyID0gbjIuc3Vic3RyKGcycHJlZml4Lmxlbmd0aCk7CiAgICAgICAgICAgIC8qIHRzbGludDpkaXNhYmxlICovCiAgICAgICAgICAgIGlmICh2aXNpdGVkMVtzdWIxXSBeIHZpc2l0ZWQyW3N1YjJdKSB7CiAgICAgICAgICAgICAgICBjb25zb2xlLndhcm4oJ2RpZmZlcmVudCB2aXNpdCBwYXR0ZXJuJywgJ1snICsgZzFwcmVmaXggKyAnXScsIHN1YjEsICdbJyArIGcycHJlZml4ICsgJ10nLCBzdWIyKTsKICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8qIHRzbGludDplbmFibGUgKi8KICAgICAgICAgICAgaWYgKCF2aXNpdGVkMVtzdWIxXSkgewogICAgICAgICAgICAgICAgLy8gaW1wbGllZCAmJiAhdmlzaXRlZDJbc3ViMl0KICAgICAgICAgICAgICAgIHZpc2l0ZWQxW3N1YjFdID0gdmlzaXRlZDJbc3ViMl0gPSB0cnVlOwogICAgICAgICAgICAgICAgc3RhY2sucHVzaCh7IG4xOiBuMSwgbjI6IG4yIH0pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgICAgLy8gY2hlY2sgaWYgaGF2ZSBzYW1lICMgb2Ygc291cmNlcyB0aGVuIHNvcnQgYW5kIHB1c2gKICAgICAgICBsZXQgc291cmNlczEgPSBnMS5zb3VyY2VzKCk7CiAgICAgICAgbGV0IHNvdXJjZXMyID0gZzIuc291cmNlcygpOwogICAgICAgIGlmIChzb3VyY2VzMS5sZW5ndGggIT09IHNvdXJjZXMyLmxlbmd0aCkgewogICAgICAgICAgICAvKiB0c2xpbnQ6ZGlzYWJsZSAqLwogICAgICAgICAgICBjb25zb2xlLmxvZygnZGlmZmVyZW50IHNvdXJjZSBsZW5ndGgnKTsKICAgICAgICAgICAgLyogdHNsaW50OmVuYWJsZSAqLwogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQogICAgICAgIHNvdXJjZXMxID0gc29ydE5vZGVzKHNvdXJjZXMxLCBnMSwgZzFwcmVmaXgpOwogICAgICAgIHNvdXJjZXMyID0gc29ydE5vZGVzKHNvdXJjZXMyLCBnMiwgZzJwcmVmaXgpOwogICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgc291cmNlczEubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgbGV0IGRpZmZlcmVudCA9IHN0YWNrUHVzaElmTm90RGlmZmVyZW50KHNvdXJjZXMxW2ldLCBzb3VyY2VzMltpXSk7CiAgICAgICAgICAgIGlmIChkaWZmZXJlbnQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICB3aGlsZSAoc3RhY2subGVuZ3RoID4gMCkgewogICAgICAgICAgICBsZXQgY3VyID0gc3RhY2sucG9wKCk7CiAgICAgICAgICAgIC8vIGNoZWNrIG5vZGUKICAgICAgICAgICAgbGV0IHNpbWlsYXIgPSBpc1NpbWlsYXJOb2RlKGcxLm5vZGUoY3VyLm4xKSwgZzIubm9kZShjdXIubjIpKTsKICAgICAgICAgICAgaWYgKCFzaW1pbGFyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gY2hlY2sgaWYgaGF2ZSBzYW1lICMgb2Ygc3VjY2Vzc29ycyB0aGVuIHNvcnQgYW5kIHB1c2gKICAgICAgICAgICAgbGV0IHN1Y2MxID0gZzEuc3VjY2Vzc29ycyhjdXIubjEpLCBzdWNjMiA9IGcyLnN1Y2Nlc3NvcnMoY3VyLm4yKTsKICAgICAgICAgICAgaWYgKHN1Y2MxLmxlbmd0aCAhPT0gc3VjYzIubGVuZ3RoKSB7CiAgICAgICAgICAgICAgICAvKiB0c2xpbnQ6ZGlzYWJsZSAqLwogICAgICAgICAgICAgICAgY29uc29sZS5sb2coJyMgb2Ygc3VjY2Vzc29ycyBtaXNtYXRjaCcsIHN1Y2MxLCBzdWNjMik7CiAgICAgICAgICAgICAgICAvKiB0c2xpbnQ6ZW5hYmxlICovCiAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc3VjYzEgPSBzb3J0Tm9kZXMoc3VjYzEsIGcxLCBnMXByZWZpeCk7CiAgICAgICAgICAgIHN1Y2MyID0gc29ydE5vZGVzKHN1Y2MyLCBnMiwgZzJwcmVmaXgpOwogICAgICAgICAgICBmb3IgKGxldCBqID0gMDsgaiA8IHN1Y2MxLmxlbmd0aDsgaisrKSB7CiAgICAgICAgICAgICAgICBsZXQgZGlmZmVyZW50ID0gc3RhY2tQdXNoSWZOb3REaWZmZXJlbnQoc3VjYzFbal0sIHN1Y2MyW2pdKTsKICAgICAgICAgICAgICAgIGlmIChkaWZmZXJlbnQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICB9CiAgICAvKioKICAgICAqIFJldHVybnMgaWYgdHdvIG5vZGVzIGhhdmUgaWRlbnRpY2FsIHN0cnVjdHVyZS4KICAgICAqLwogICAgZnVuY3Rpb24gaXNTaW1pbGFyTm9kZShuMSwgbjIpIHsKICAgICAgICBpZiAobjEudHlwZSA9PT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICAvLyBjb21wYXJlIG1ldGFub2RlCiAgICAgICAgICAgIGxldCBtZXRhbm9kZTEgPSBuMTsKICAgICAgICAgICAgbGV0IG1ldGFub2RlMiA9IG4yOwogICAgICAgICAgICByZXR1cm4gKG1ldGFub2RlMS50ZW1wbGF0ZUlkICYmCiAgICAgICAgICAgICAgICBtZXRhbm9kZTIudGVtcGxhdGVJZCAmJgogICAgICAgICAgICAgICAgbWV0YW5vZGUxLnRlbXBsYXRlSWQgPT09IG1ldGFub2RlMi50ZW1wbGF0ZUlkKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAobjEudHlwZSA9PT0gTm9kZVR5cGUuT1AgJiYgbjIudHlwZSA9PT0gTm9kZVR5cGUuT1ApIHsKICAgICAgICAgICAgLy8gY29tcGFyZSBsZWFmIG5vZGUKICAgICAgICAgICAgcmV0dXJuIG4xLm9wID09PSBuMi5vcDsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAobjEudHlwZSA9PT0gTm9kZVR5cGUuU0VSSUVTICYmIG4yLnR5cGUgPT09IE5vZGVUeXBlLlNFUklFUykgewogICAgICAgICAgICAvLyBjb21wYXJlIHNlcmllcyBub2RlIHNpemVzIGFuZCBvcGVyYXRpb25zCiAgICAgICAgICAgIC8vIChvbmx5IG5lZWQgdG8gY2hlY2sgb25lIG9wIGFzIGFsbCBvcCBub2RlcyBhcmUgaWRlbnRpY2FsIGluIHNlcmllcykKICAgICAgICAgICAgbGV0IHNuMSA9IG4xOwogICAgICAgICAgICBsZXQgc24yID0gbjI7CiAgICAgICAgICAgIGxldCBzZXJpZXNub2RlMUNvdW50ID0gc24xLm1ldGFncmFwaC5ub2RlQ291bnQoKTsKICAgICAgICAgICAgcmV0dXJuIChzZXJpZXNub2RlMUNvdW50ID09PSBzbjIubWV0YWdyYXBoLm5vZGVDb3VudCgpICYmCiAgICAgICAgICAgICAgICAoc2VyaWVzbm9kZTFDb3VudCA9PT0gMCB8fAogICAgICAgICAgICAgICAgICAgIHNuMS5tZXRhZ3JhcGgubm9kZShzbjEubWV0YWdyYXBoLm5vZGVzKClbMF0pLm9wID09PQogICAgICAgICAgICAgICAgICAgICAgICBzbjIubWV0YWdyYXBoLm5vZGUoc24yLm1ldGFncmFwaC5ub2RlcygpWzBdKS5vcCkpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZmFsc2U7CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTUgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgJ0xpY2Vuc2UnKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAnQVMgSVMnIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIENsYXNzIGZvciB0aGUgR3JhcGggSGllcmFyY2h5IGZvciBUZW5zb3JGbG93IGdyYXBoLgogICAgICovCiAgICBjbGFzcyBIaWVyYXJjaHlJbXBsIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgaGllcmFyY2h5LgogICAgICAgICAqIEBwYXJhbSBncmFwaE9wdGlvbnMgT3B0aW9ucyBwYXNzZWQgdG8gZGFncmUgZm9yIGNyZWF0aW5nIHRoZSBncmFwaC4gTm90ZQogICAgICAgICAqICAgdGhhdCB0aGUgYGNvbXBvdW5kYCBhcmd1bWVudCB3aWxsIGJlIG92ZXJyaWRkZW4gdG8gdHJ1ZS4KICAgICAgICAgKi8KICAgICAgICBjb25zdHJ1Y3RvcihncmFwaE9wdGlvbnMpIHsKICAgICAgICAgICAgdGhpcy5oYXNTaGFwZUluZm8gPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5tYXhNZXRhRWRnZVNpemUgPSAxOwogICAgICAgICAgICB0aGlzLmdyYXBoT3B0aW9ucyA9IGdyYXBoT3B0aW9ucyB8fCB7fTsKICAgICAgICAgICAgdGhpcy5ncmFwaE9wdGlvbnMuY29tcG91bmQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLnJvb3QgPSBjcmVhdGVNZXRhbm9kZShST09UX05BTUUsIHRoaXMuZ3JhcGhPcHRpb25zKTsKICAgICAgICAgICAgdGhpcy5saWJyYXJ5RnVuY3Rpb25zID0ge307CiAgICAgICAgICAgIHRoaXMudGVtcGxhdGVzID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5kZXZpY2VzID0gbnVsbDsKICAgICAgICAgICAgdGhpcy54bGFDbHVzdGVycyA9IG51bGw7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBAdHlwZSB7T2JqZWN0fSBEaWN0aW9uYXJ5IG9iamVjdCB0aGF0IG1hcHMgbm9kZSBuYW1lIHRvIHRoZSBub2RlCiAgICAgICAgICAgICAqIChjb3VsZCBiZSBvcC1ub2RlLCBtZXRhbm9kZSwgb3Igc2VyaWVzLW5vZGUpCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmluZGV4ID0ge307CiAgICAgICAgICAgIHRoaXMuaW5kZXhbUk9PVF9OQU1FXSA9IHRoaXMucm9vdDsKICAgICAgICAgICAgdGhpcy5vcmRlcmluZ3MgPSB7fTsKICAgICAgICB9CiAgICAgICAgZ2V0Tm9kZU1hcCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuaW5kZXg7CiAgICAgICAgfQogICAgICAgIG5vZGUobmFtZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5pbmRleFtuYW1lXTsKICAgICAgICB9CiAgICAgICAgc2V0Tm9kZShuYW1lLCBub2RlKSB7CiAgICAgICAgICAgIHRoaXMuaW5kZXhbbmFtZV0gPSBub2RlOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBHaXZlbiB0aGUgbmFtZSBvZiBhIG5vZGUgaW4gdGhpcyBoaWVyYXJjaHksIGdldCBpdHMgYnJpZGdlZ3JhcGgsIGNyZWF0aW5nCiAgICAgICAgICogaXQgb24gdGhlIGZseSBpZiBuZWNlc3NhcnkuIElmIHRoZSBub2RlIGlzIG5vdCBhIEdyb3VwTm9kZSwgdGhlbiB0aGlzCiAgICAgICAgICogbWV0aG9kIHJldHVybnMgbnVsbC4gSWYgdGhlIHByb3ZpZGVkIG5hbWUgZG9lcyBub3QgbWFwIHRvIGEgbm9kZSBpbiB0aGUKICAgICAgICAgKiBoaWVyYXJjaHksIGFuIGVycm9yIHdpbGwgYmUgdGhyb3duLgogICAgICAgICAqLwogICAgICAgIGdldEJyaWRnZWdyYXBoKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gdGhpcy5pbmRleFtub2RlTmFtZV07CiAgICAgICAgICAgIGlmICghbm9kZSkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoJ0NvdWxkIG5vdCBmaW5kIG5vZGUgaW4gaGllcmFyY2h5OiAnICsgbm9kZU5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghKCdtZXRhZ3JhcGgnIGluIG5vZGUpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgZ3JvdXBOb2RlID0gbm9kZTsKICAgICAgICAgICAgaWYgKGdyb3VwTm9kZS5icmlkZ2VncmFwaCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGdyb3VwTm9kZS5icmlkZ2VncmFwaDsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgYnJpZGdlZ3JhcGggPSAoZ3JvdXBOb2RlLmJyaWRnZWdyYXBoID0gY3JlYXRlR3JhcGgoJ0JSSURHRUdSQVBIJywgR3JhcGhUeXBlLkJSSURHRSwgdGhpcy5ncmFwaE9wdGlvbnMpKTsKICAgICAgICAgICAgaWYgKCFub2RlLnBhcmVudE5vZGUgfHwgISgnbWV0YWdyYXBoJyBpbiBub2RlLnBhcmVudE5vZGUpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gYnJpZGdlZ3JhcGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbGV0IHBhcmVudE5vZGUgPSBub2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgIGxldCBwYXJlbnRNZXRhZ3JhcGggPSBwYXJlbnROb2RlLm1ldGFncmFwaDsKICAgICAgICAgICAgbGV0IHBhcmVudEJyaWRnZWdyYXBoID0gdGhpcy5nZXRCcmlkZ2VncmFwaChwYXJlbnROb2RlLm5hbWUpOwogICAgICAgICAgICAvLyBGb3IgZWFjaCBvZiB0aGUgcGFyZW50IG5vZGUncyB0d28gTWV0YWVkZ2UgY29udGFpbmluZyBncmFwaHMsIHByb2Nlc3MKICAgICAgICAgICAgLy8gZWFjaCBNZXRhZWRnZSBpbnZvbHZpbmcgdGhpcyBub2RlLgogICAgICAgICAgICBsb2Rhc2guZWFjaChbcGFyZW50TWV0YWdyYXBoLCBwYXJlbnRCcmlkZ2VncmFwaF0sIChwYXJlbnRHcmFwaCkgPT4gewogICAgICAgICAgICAgICAgcGFyZW50R3JhcGgKICAgICAgICAgICAgICAgICAgICAuZWRnZXMoKQogICAgICAgICAgICAgICAgICAgIC5maWx0ZXIoKGUpID0+IGUudiA9PT0gbm9kZU5hbWUgfHwgZS53ID09PSBub2RlTmFtZSkKICAgICAgICAgICAgICAgICAgICAuZm9yRWFjaCgocGFyZW50RWRnZU9iaikgPT4gewogICAgICAgICAgICAgICAgICAgIGxldCBpbmJvdW5kID0gcGFyZW50RWRnZU9iai53ID09PSBub2RlTmFtZTsKICAgICAgICAgICAgICAgICAgICBsZXQgcGFyZW50TWV0YWVkZ2UgPSBwYXJlbnRHcmFwaC5lZGdlKHBhcmVudEVkZ2VPYmopOwogICAgICAgICAgICAgICAgICAgIC8vIFRoZSBwYXJlbnQncyBNZXRhZWRnZSByZXByZXNlbnRzIHNvbWUgbnVtYmVyIG9mIHVuZGVybHlpbmcKICAgICAgICAgICAgICAgICAgICAvLyBCYXNlRWRnZXMgZnJvbSB0aGUgb3JpZ2luYWwgZnVsbCBncmFwaC4gRm9yIGVhY2ggb2YgdGhvc2UsIHdlIG5lZWQKICAgICAgICAgICAgICAgICAgICAvLyB0byBkZXRlcm1pbmUgd2hpY2ggaW1tZWRpYXRlIGNoaWxkIGlzIGludm9sdmVkIGFuZCBtYWtlIHN1cmUKICAgICAgICAgICAgICAgICAgICAvLyB0aGVyZSdzIGEgTWV0YWVkZ2UgaW4gdGhlIGJyaWRnZWdyYXBoIHRoYXQgY292ZXJzIGl0LgogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKHBhcmVudE1ldGFlZGdlLmJhc2VFZGdlTGlzdCwgKGJhc2VFZGdlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIEJhc2VkIG9uIHRoZSBkaXJlY3Rpb24sIGZpZ3VyZSBvdXQgd2hpY2ggaXMgdGhlIGRlc2NlbmRhbnQgbm9kZQogICAgICAgICAgICAgICAgICAgICAgICAvLyBhbmQgd2hpY2ggaXMgdGhlICdvdGhlcicgbm9kZSAoc2libGluZyBvZiBwYXJlbnQgb3IgYW5jZXN0b3IpLgogICAgICAgICAgICAgICAgICAgICAgICBsZXQgW2Rlc2NlbmRhbnROYW1lLCBvdGhlck5hbWVdID0gaW5ib3VuZAogICAgICAgICAgICAgICAgICAgICAgICAgICAgPyBbYmFzZUVkZ2UudywgcGFyZW50RWRnZU9iai52XQogICAgICAgICAgICAgICAgICAgICAgICAgICAgOiBbYmFzZUVkZ2UudiwgcGFyZW50RWRnZU9iai53XTsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gRGV0ZXJtaW5lIHRoZSBpbW1lZGlhdGUgY2hpbGQgY29udGFpbmluZyB0aGlzIGRlc2NlbmRhbnQgbm9kZS4KICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGNoaWxkTmFtZSA9IHRoaXMuZ2V0Q2hpbGROYW1lKG5vZGVOYW1lLCBkZXNjZW5kYW50TmFtZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIExvb2sgZm9yIGFuIGV4aXN0aW5nIE1ldGFlZGdlIGluIHRoZSBicmlkZ2VncmFwaCAob3IgY3JlYXRlIGEKICAgICAgICAgICAgICAgICAgICAgICAgLy8gbmV3IG9uZSkgdGhhdCBjb3ZlcnMgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIGNoaWxkIGFuZCBvdGhlci4KICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGJyaWRnZUVkZ2VPYmogPSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB2OiBpbmJvdW5kID8gb3RoZXJOYW1lIDogY2hpbGROYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgdzogaW5ib3VuZCA/IGNoaWxkTmFtZSA6IG90aGVyTmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICAgICAgbGV0IGJyaWRnZU1ldGFlZGdlID0gYnJpZGdlZ3JhcGguZWRnZShicmlkZ2VFZGdlT2JqKTsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFicmlkZ2VNZXRhZWRnZSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJpZGdlTWV0YWVkZ2UgPSBjcmVhdGVNZXRhZWRnZShicmlkZ2VFZGdlT2JqLnYsIGJyaWRnZUVkZ2VPYmoudyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBicmlkZ2VNZXRhZWRnZS5pbmJvdW5kID0gaW5ib3VuZDsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJyaWRnZWdyYXBoLnNldEVkZ2UoYnJpZGdlRWRnZU9iai52LCBicmlkZ2VFZGdlT2JqLncsIGJyaWRnZU1ldGFlZGdlKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAvLyBDb3B5IHRoZSBCYXNlRWRnZSBmcm9tIHRoZSBwYXJlbnQncyBNZXRhZWRnZSBpbnRvIHRoaXMKICAgICAgICAgICAgICAgICAgICAgICAgLy8gYnJpZGdlZ3JhcGggTWV0YWVkZ2UuCiAgICAgICAgICAgICAgICAgICAgICAgIGJyaWRnZU1ldGFlZGdlLmFkZEJhc2VFZGdlKGJhc2VFZGdlLCB0aGlzKTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIGJyaWRnZWdyYXBoOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBVdGlsaXR5IGZ1bmN0aW9uIGZvciBkZXRlcm1pbmluZyB0aGUgbmFtZSBvZiB0aGUgaW1tZWRpYXRlIGNoaWxkIHVuZGVyIGEKICAgICAgICAgKiBub2RlIGZvciBhIGdpdmVuIGRlc2NlbmRhbnQgcGF0aC4gSWYgdGhlIGRlc2NlbmRhbnQgY29ycmVzcG9uZHMgdG8gbm8KICAgICAgICAgKiBpbW1lZGlhdGUgY2hpbGQsIGFuIGVycm9yIGlzIHRocm93bi4KICAgICAgICAgKi8KICAgICAgICBnZXRDaGlsZE5hbWUobm9kZU5hbWUsIGRlc2NlbmRhbnROYW1lKSB7CiAgICAgICAgICAgIC8vIFdhbGsgdXAgdGhlIGhpZXJhcmNoeSBmcm9tIHRoZSBkZXNjZW5kYW50IHRvIGZpbmQgdGhlIGNoaWxkLgogICAgICAgICAgICBsZXQgY3VycmVudE5vZGUgPSB0aGlzLmluZGV4W2Rlc2NlbmRhbnROYW1lXTsKICAgICAgICAgICAgd2hpbGUgKGN1cnJlbnROb2RlKSB7CiAgICAgICAgICAgICAgICBpZiAoY3VycmVudE5vZGUucGFyZW50Tm9kZSAmJiBjdXJyZW50Tm9kZS5wYXJlbnROb2RlLm5hbWUgPT09IG5vZGVOYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGN1cnJlbnROb2RlLm5hbWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjdXJyZW50Tm9kZSA9IGN1cnJlbnROb2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhyb3cgRXJyb3IoJ0NvdWxkIG5vdCBmaW5kIGltbWVkaWF0ZSBjaGlsZCBmb3IgZGVzY2VuZGFudDogJyArIGRlc2NlbmRhbnROYW1lKTsKICAgICAgICB9CiAgICAgICAgLyoqIEdpdmVuIHRoZSBuYW1lIG9mIGEgbm9kZSwgcmV0dXJuIGl0cyBpbmNvbWluZyBtZXRhZWRnZXMuICovCiAgICAgICAgZ2V0UHJlZGVjZXNzb3JzKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gdGhpcy5pbmRleFtub2RlTmFtZV07CiAgICAgICAgICAgIGlmICghbm9kZSkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoJ0NvdWxkIG5vdCBmaW5kIG5vZGUgd2l0aCBuYW1lOiAnICsgbm9kZU5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBwcmVkZWNlc3NvcnMgPSB0aGlzLmdldE9uZVdheUVkZ2VzKG5vZGUsIHRydWUpOwogICAgICAgICAgICAvLyBBZGQgZW1iZWRkZWQgcHJlZGVjZXNzb3JzLCBzdWNoIGFzIGNvbnN0YW50cy4KICAgICAgICAgICAgaWYgKCFub2RlLmlzR3JvdXBOb2RlKSB7CiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChub2RlLmluRW1iZWRkaW5ncywgKGVtYmVkZGVkTm9kZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKG5vZGUuaW5wdXRzLCAoaW5wdXQpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0Lm5hbWUgPT09IGVtYmVkZGVkTm9kZS5uYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBNYWtlIGEgbmV3IG1ldGFlZGdlIGhvbGRpbmcgdGhlIGVkZ2UgYmV0d2VlbiB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIG5vZGUgYW5kIHRoZSBpbi1lbWJlZGRpbmcuCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBsZXQgbWV0YWVkZ2UgPSBuZXcgTWV0YWVkZ2VJbXBsKGVtYmVkZGVkTm9kZS5uYW1lLCBub2RlTmFtZSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtZXRhZWRnZS5hZGRCYXNlRWRnZSh7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaXNDb250cm9sRGVwZW5kZW5jeTogaW5wdXQuaXNDb250cm9sRGVwZW5kZW5jeSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBvdXRwdXRUZW5zb3JLZXk6IGlucHV0Lm91dHB1dFRlbnNvcktleSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBpc1JlZmVyZW5jZUVkZ2U6IGZhbHNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHY6IGVtYmVkZGVkTm9kZS5uYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHc6IG5vZGVOYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgfSwgdGhpcyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBwcmVkZWNlc3NvcnMucmVndWxhci5wdXNoKG1ldGFlZGdlKTsKICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHByZWRlY2Vzc29yczsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogR2l2ZW4gdGhlIG5hbWUgb2YgYSBub2RlLCByZXR1cm4gaXRzIG91dGdvaW5nIG1ldGFlZGdlcy4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgaXMgdGhlIGludmVyc2Ugb2YgZ2V0UHJlZGVjZXNzb3JzKCkuIFNlZSB0aGF0IG1ldGhvZCdzIGRvY3VtZW50YXRpb24KICAgICAgICAgKiBmb3IgYW4gaW4tZGVwdGggZXhhbXBsZS4KICAgICAgICAgKi8KICAgICAgICBnZXRTdWNjZXNzb3JzKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gdGhpcy5pbmRleFtub2RlTmFtZV07CiAgICAgICAgICAgIGlmICghbm9kZSkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoJ0NvdWxkIG5vdCBmaW5kIG5vZGUgd2l0aCBuYW1lOiAnICsgbm9kZU5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBzdWNjZXNzb3JzID0gdGhpcy5nZXRPbmVXYXlFZGdlcyhub2RlLCBmYWxzZSk7CiAgICAgICAgICAgIC8vIEFkZCBlbWJlZGRlZCBzdWNjZXNzb3JzLCBzdWNoIGFzIHN1bW1hcmllcy4KICAgICAgICAgICAgaWYgKCFub2RlLmlzR3JvdXBOb2RlKSB7CiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChub2RlLm91dEVtYmVkZGluZ3MsIChlbWJlZGRlZE5vZGUpID0+IHsKICAgICAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChlbWJlZGRlZE5vZGUuaW5wdXRzLCAoaW5wdXQpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0Lm5hbWUgPT09IG5vZGVOYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBNYWtlIGEgbmV3IG1ldGFlZGdlIGhvbGRpbmcgdGhlIGVkZ2UgYmV0d2VlbiB0aGUKICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8vIG5vZGUgYW5kIHRoZSBvdXQtZW1iZWRkaW5nLgogICAgICAgICAgICAgICAgICAgICAgICAgICAgbGV0IG1ldGFlZGdlID0gbmV3IE1ldGFlZGdlSW1wbChub2RlTmFtZSwgZW1iZWRkZWROb2RlLm5hbWUpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgbWV0YWVkZ2UuYWRkQmFzZUVkZ2UoewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlzQ29udHJvbERlcGVuZGVuY3k6IGlucHV0LmlzQ29udHJvbERlcGVuZGVuY3ksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3V0cHV0VGVuc29yS2V5OiBpbnB1dC5vdXRwdXRUZW5zb3JLZXksCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaXNSZWZlcmVuY2VFZGdlOiBmYWxzZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2OiBub2RlTmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB3OiBlbWJlZGRlZE5vZGUubmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIHRoaXMpOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgc3VjY2Vzc29ycy5yZWd1bGFyLnB1c2gobWV0YWVkZ2UpOwogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gc3VjY2Vzc29yczsKICAgICAgICB9CiAgICAgICAgLyoqIEhlbHBlciBtZXRob2QgZm9yIGdldFByZWRlY2Vzc29ycyBhbmQgZ2V0U3VjY2Vzc29ycyAqLwogICAgICAgIGdldE9uZVdheUVkZ2VzKG5vZGUsIGluRWRnZXMpIHsKICAgICAgICAgICAgbGV0IGVkZ2VzID0geyBjb250cm9sOiBbXSwgcmVndWxhcjogW10gfTsKICAgICAgICAgICAgLy8gQSBub2RlIHdpdGggbm8gcGFyZW50IGNhbm5vdCBoYXZlIGFueSBlZGdlcy4KICAgICAgICAgICAgaWYgKCFub2RlLnBhcmVudE5vZGUgfHwgIW5vZGUucGFyZW50Tm9kZS5pc0dyb3VwTm9kZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIGVkZ2VzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBwYXJlbnROb2RlID0gbm9kZS5wYXJlbnROb2RlOwogICAgICAgICAgICBsZXQgbWV0YWdyYXBoID0gcGFyZW50Tm9kZS5tZXRhZ3JhcGg7CiAgICAgICAgICAgIGxldCBicmlkZ2VncmFwaCA9IHRoaXMuZ2V0QnJpZGdlZ3JhcGgocGFyZW50Tm9kZS5uYW1lKTsKICAgICAgICAgICAgZmluZEVkZ2VUYXJnZXRzSW5HcmFwaChtZXRhZ3JhcGgsIG5vZGUsIGluRWRnZXMsIGVkZ2VzKTsKICAgICAgICAgICAgZmluZEVkZ2VUYXJnZXRzSW5HcmFwaChicmlkZ2VncmFwaCwgbm9kZSwgaW5FZGdlcywgZWRnZXMpOwogICAgICAgICAgICByZXR1cm4gZWRnZXM7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEZvciBhIGdpdmVuIEdyb3VwTm9kZSwgZ2V0IG9yIGNhbGN1bGF0ZSBhbiBvYmplY3Qgd2hpY2ggZGVzY3JpYmVzIGEKICAgICAgICAgKiB0b3BvbG9naWNhbCBvcmRlcmluZyBvZiBjaGlsZCBub2RlcyB3aXRoaW4gdGhhdCBHcm91cE5vZGUncyBtZXRhZ3JhcGguCiAgICAgICAgICoKICAgICAgICAgKiBUaGlzIG9yZGVyaW5nIGlzIHVzZWQgd2hlbiByZW5kZXJpbmcgYnJpZGdlIGNvbnRyb2wgZWRnZXMgd2hpY2ggYXJlCiAgICAgICAgICogc29tZXRpbWVzIGJhY2t3YXJkcyByZWxhdGl2ZSB0byB0aGUgZGF0YWZsb3cuCiAgICAgICAgICoKICAgICAgICAgKiBGb3IgZXhhbXBsZSwgc2F5IHdlIGhhdmUgYSBncmFwaCB3aXRoIHR3byBlZGdlcyBBLT5CIGFuZCBBLT5DLCBhbmQgd2UncmUKICAgICAgICAgKiBpbnRlcmVzdGVkIGluIHRoZSBvcmRlcmluZyB1bmRlciBST09ULiBJbiB0aGlzIGNhc2UsIGFueSBvZiB0aGUgZm9sbG93aW5nCiAgICAgICAgICogd291bGQgYmUgbGVnaXRpbWF0ZSByZXR1cm4gdmFsdWVzOgogICAgICAgICAqCiAgICAgICAgICogIC0geyAnQSc6IDAsICdCJzogMSwgJ0MnOiAyIH0gLS0gbW9zdCBsaWtlbHkKICAgICAgICAgKiAgLSB7ICdBJzogMCwgJ0InOiAyLCAnQyc6IDEgfSAtLSBsZXNzIGxpa2VseQogICAgICAgICAqICAtIHsgJ0EnOiAxMiwgJ0InOiAxMDAsICdDJzogOTkgfSAtLSB1bmxpa2VseSwgYnV0IHN0aWxsIE9LCiAgICAgICAgICoKICAgICAgICAgKiBUaGUgYWxnb3JpdGhtIGRvZXMgbm90IGd1YXJhbnRlZSB0aGF0IGFsbCBudW1iZXJzIGZyb20gMC1OICh3aGVyZSBOIGlzCiAgICAgICAgICogdGhlIG51bWJlciBvZiBub2RlcykgYXBwZWFyIGV4YWN0bHkgb25jZS4gUmF0aGVyIGl0IGd1YXJhbnRlZXMgdGhhdCBpZgogICAgICAgICAqIHRoZXJlIGlzIGEgcGF0aCBiZXR3ZWVuIHR3byBub2RlcywgdGhlIGVhcmxpZXIgb25lIHdpbGwgaGF2ZSBhIGxvd2VyCiAgICAgICAgICogbnVtYmVyIGluIHRoZSBvcmRlcmluZyBoYXNoLgogICAgICAgICAqCiAgICAgICAgICogV2hlbiBnZW5lcmF0aW5nIHRoZSBvcmRlcmluZywgd2UgaWdub3JlIGNvbnRyb2wgTWV0YWVkZ2VzICh0aG9zZSB3aGljaAogICAgICAgICAqIHJlcHJlc2VudCBvbmx5IEJhc2VFZGdlcyB0aGF0IGhhdmUgaXNDb250cm9sRGVwZW5kZW5jeSBzZXQgdG8gdHJ1ZSkuCiAgICAgICAgICoKICAgICAgICAgKiBJZiB0aGVyZSBpcyBubyBub2RlIHdpdGggdGhlIHNwZWNpZmllZCBuYW1lLCBhbiBlcnJvciBpcyB0aHJvd24uIElmIHRoZQogICAgICAgICAqIG5vZGUgd2l0aCB0aGUgc3BlY2lmaWVkIG5hbWUgaXMgbm90IGEgZ3JvdXAgbm9kZSwgbnVsbCBpcyByZXR1cm5lZC4KICAgICAgICAgKi8KICAgICAgICBnZXRUb3BvbG9naWNhbE9yZGVyaW5nKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIGxldCBub2RlID0gdGhpcy5pbmRleFtub2RlTmFtZV07CiAgICAgICAgICAgIGlmICghbm9kZSkgewogICAgICAgICAgICAgICAgdGhyb3cgRXJyb3IoJ0NvdWxkIG5vdCBmaW5kIG5vZGUgd2l0aCBuYW1lOiAnICsgbm9kZU5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICghbm9kZS5pc0dyb3VwTm9kZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKG5vZGVOYW1lIGluIHRoaXMub3JkZXJpbmdzKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5vcmRlcmluZ3Nbbm9kZU5hbWVdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIE1hcHBpbmcgb2YgYSBjaGlsZCBub2RlIG5hbWVzIHRvIGxpc3RzIG9mIHRoZWlyIHN1Y2Nlc3NvcnMuCiAgICAgICAgICAgIGxldCBzdWNjZXNzb3JzID0ge307CiAgICAgICAgICAgIC8vIFNldCBvZiBub2RlIG5hbWVzIHdoaWNoIGhhdmUgYXBwZWFyZWQgYXMgYSBkZXN0aW5hdGlvbi4KICAgICAgICAgICAgbGV0IGRlc3RpbmF0aW9ucyA9IHt9OwogICAgICAgICAgICBsZXQgbWV0YWdyYXBoID0gbm9kZS5tZXRhZ3JhcGg7CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKG1ldGFncmFwaC5lZGdlcygpLCAoZSkgPT4gewogICAgICAgICAgICAgICAgaWYgKCFtZXRhZ3JhcGguZWRnZShlKS5udW1SZWd1bGFyRWRnZXMpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47IC8vIFNraXAgY29udHJvbCBlZGdlcy4KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEtlZXAgdHJhY2sgb2Ygc3VjY2Vzc29ycyBhbmQgZGVzdGluYXRpb25zLgogICAgICAgICAgICAgICAgaWYgKCEoZS52IGluIHN1Y2Nlc3NvcnMpKSB7CiAgICAgICAgICAgICAgICAgICAgc3VjY2Vzc29yc1tlLnZdID0gW107CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBzdWNjZXNzb3JzW2Uudl0ucHVzaChlLncpOwogICAgICAgICAgICAgICAgZGVzdGluYXRpb25zW2Uud10gPSB0cnVlOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gU2VlZCB0aGUgcXVldWUgd2l0aCB0cnVlIHNvdXJjZXMgKHRob3NlIHRoYXQgYXJlIG5vdCBkZXN0aW5hdGlvbnMpLgogICAgICAgICAgICBsZXQgcXVldWUgPSBsb2Rhc2guZGlmZmVyZW5jZShsb2Rhc2gua2V5cyhzdWNjZXNzb3JzKSwgbG9kYXNoLmtleXMoZGVzdGluYXRpb25zKSk7CiAgICAgICAgICAgIC8vIFByb2R1Y2UgYW4gb3JkZXJpbmcgYnkgdHJhdmVyc2luZyB0aGUgZ3JhcGggYnJlYWR0aCBmaXJzdC4KICAgICAgICAgICAgbGV0IG9yZGVyaW5nID0gKHRoaXMub3JkZXJpbmdzW25vZGVOYW1lXSA9IHt9KTsKICAgICAgICAgICAgbGV0IGluZGV4ID0gMDsKICAgICAgICAgICAgd2hpbGUgKHF1ZXVlLmxlbmd0aCkgewogICAgICAgICAgICAgICAgbGV0IGNoaWxkTmFtZSA9IHF1ZXVlLnNoaWZ0KCk7CiAgICAgICAgICAgICAgICBvcmRlcmluZ1tjaGlsZE5hbWVdID0gaW5kZXgrKzsKICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKHN1Y2Nlc3NvcnNbY2hpbGROYW1lXSwgKHN1Y2NOYW1lKSA9PiBxdWV1ZS5wdXNoKHN1Y2NOYW1lKSk7CiAgICAgICAgICAgICAgICBkZWxldGUgc3VjY2Vzc29yc1tjaGlsZE5hbWVdOyAvLyBQcmV2ZW50IGN5Y2xlcyBmcm9tIGluZmluaXRlIGxvb3BpbmcuCiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG9yZGVyaW5nOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGEgZDMgT3JkaW5hbCBmdW5jdGlvbiB0aGF0IGNhbiBiZSB1c2VkIHRvIGxvb2sgdXAgdGhlIGluZGV4IG9mCiAgICAgICAgICogYSBub2RlIGJhc2VkIG9uIGl0cyB0ZW1wbGF0ZSBpZC4KICAgICAgICAgKi8KICAgICAgICBnZXRUZW1wbGF0ZUluZGV4KCkgewogICAgICAgICAgICBsZXQgdGVtcGxhdGVOYW1lcyA9IGtleXModGhpcy50ZW1wbGF0ZXMpOwogICAgICAgICAgICBsZXQgdGVtcGxhdGVJbmRleCA9IG9yZGluYWwoKQogICAgICAgICAgICAgICAgLmRvbWFpbih0ZW1wbGF0ZU5hbWVzKQogICAgICAgICAgICAgICAgLnJhbmdlKHNlcXVlbmNlKDAsIHRlbXBsYXRlTmFtZXMubGVuZ3RoKSk7CiAgICAgICAgICAgIHJldHVybiAodGVtcGxhdGVJZCkgPT4gdGVtcGxhdGVJbmRleCh0ZW1wbGF0ZUlkKTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIEludGVybmFsIHV0aWxpdHkgZnVuY3Rpb24gLSBnaXZlbiBhIGdyYXBoIChzaG91bGQgYmUgZWl0aGVyIGEgbWV0YWdyYXBoIG9yIGEKICAgICAqIGJyaWRnZWdyYXBoKSBhbmQgYSBub2RlIHdoaWNoIGlzIGtub3duIHRvIGJlIGluIHRoYXQgZ3JhcGgsIGRldGVybWluZQogICAgICogdGhlIG90aGVyIGVuZHMgb2YgZWRnZXMgdGhhdCBpbnZvbHZlIHRoYXQgbm9kZSBpbiB0aGUgZGlyZWN0aW9uIHNwZWNpZmllZAogICAgICogYnkgd2hldGhlciBpdCdzIGluYm91bmQuCiAgICAgKgogICAgICogRm9yIGV4YW1wbGUgaWYgeW91IHdhbnRlZCB0byBmaW5kIHRoZSBwcmVkZWNlc3NvcnMgb2YgYSBub2RlLCB5b3UnZCBjYWxsCiAgICAgKiB0aGlzIG1ldGhvZCBmb3IgdGhlIHBhcmVudCdzIG1ldGFncmFwaCBhbmQgYnJpZGdlZ3JhcGgsIHNwZWNpZnlpbmcgaW5ib3VuZAogICAgICogYXMgdHJ1ZSAobG9vayBhdCB0aGUgc291cmNlIG9mIGluYm91bmQgZWRnZXMgdG8gdGhlIHNwZWNpZmllZCBub2RlKS4KICAgICAqCiAgICAgKiBEaXNjb3ZlcmVkIHRhcmdldCBuYW1lcyBhcmUgYXBwZW5kZWQgdG8gdGhlIHRhcmdldHMgYXJyYXkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZpbmRFZGdlVGFyZ2V0c0luR3JhcGgoZ3JhcGgsIG5vZGUsIGluYm91bmQsIHRhcmdldHMpIHsKICAgICAgICBsZXQgZWRnZXMgPSBpbmJvdW5kID8gZ3JhcGguaW5FZGdlcyhub2RlLm5hbWUpIDogZ3JhcGgub3V0RWRnZXMobm9kZS5uYW1lKTsKICAgICAgICBsb2Rhc2guZWFjaChlZGdlcywgKGUpID0+IHsKICAgICAgICAgICAgbGV0IG1ldGFlZGdlID0gZ3JhcGguZWRnZShlKTsKICAgICAgICAgICAgbGV0IHRhcmdldExpc3QgPSBtZXRhZWRnZS5udW1SZWd1bGFyRWRnZXMKICAgICAgICAgICAgICAgID8gdGFyZ2V0cy5yZWd1bGFyCiAgICAgICAgICAgICAgICA6IHRhcmdldHMuY29udHJvbDsKICAgICAgICAgICAgdGFyZ2V0TGlzdC5wdXNoKG1ldGFlZGdlKTsKICAgICAgICB9KTsKICAgIH0KICAgIGNvbnN0IERlZmF1bHRIaWVyYXJjaHlQYXJhbXMgPSB7CiAgICAgICAgdmVyaWZ5VGVtcGxhdGU6IHRydWUsCiAgICAgICAgc2VyaWVzTm9kZU1pblNpemU6IDUsCiAgICAgICAgc2VyaWVzTWFwOiB7fSwKICAgICAgICByYW5rRGlyZWN0aW9uOiAnQlQnLAogICAgICAgIHVzZUdlbmVyYWxpemVkU2VyaWVzUGF0dGVybnM6IGZhbHNlLAogICAgfTsKICAgIC8qKgogICAgICogQHBhcmFtIGdyYXBoIFRoZSByYXcgZ3JhcGguCiAgICAgKiBAcGFyYW0gcGFyYW1zIFBhcmFtZXRlcnMgdXNlZCB3aGVuIGJ1aWxkaW5nIGEgaGllcmFyY2h5LgogICAgICovCiAgICBmdW5jdGlvbiBidWlsZCQxKGdyYXBoLCBwYXJhbXMsIHRyYWNrZXIpIHsKICAgICAgICBsZXQgaCA9IG5ldyBIaWVyYXJjaHlJbXBsKHsgcmFua2RpcjogcGFyYW1zLnJhbmtEaXJlY3Rpb24gfSk7CiAgICAgICAgbGV0IHNlcmllc05hbWVzID0ge307CiAgICAgICAgcmV0dXJuIHJ1bkFzeW5jVGFzaygnQWRkaW5nIG5vZGVzJywgMjAsICgpID0+IHsKICAgICAgICAgICAgLy8gR2V0IGFsbCB0aGUgcG9zc2libGUgZGV2aWNlIGFuZCBYTEEgY2x1c3RlciBuYW1lcy4KICAgICAgICAgICAgbGV0IGRldmljZU5hbWVzID0ge307CiAgICAgICAgICAgIGxldCB4bGFDbHVzdGVyTmFtZXMgPSB7fTsKICAgICAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGgubm9kZXMsIChub2RlLCBub2RlTmFtZSkgPT4gewogICAgICAgICAgICAgICAgaWYgKG5vZGUuZGV2aWNlKSB7CiAgICAgICAgICAgICAgICAgICAgZGV2aWNlTmFtZXNbbm9kZS5kZXZpY2VdID0gdHJ1ZTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChub2RlLnhsYUNsdXN0ZXIpIHsKICAgICAgICAgICAgICAgICAgICB4bGFDbHVzdGVyTmFtZXNbbm9kZS54bGFDbHVzdGVyXSA9IHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBoLmRldmljZXMgPSBsb2Rhc2gua2V5cyhkZXZpY2VOYW1lcyk7CiAgICAgICAgICAgIGgueGxhQ2x1c3RlcnMgPSBsb2Rhc2gua2V5cyh4bGFDbHVzdGVyTmFtZXMpOwogICAgICAgICAgICBhZGROb2RlcyhoLCBncmFwaCk7CiAgICAgICAgfSwgdHJhY2tlcikKICAgICAgICAgICAgLnRoZW4oKCkgPT4gewogICAgICAgICAgICByZXR1cm4gcnVuQXN5bmNUYXNrKCdEZXRlY3Qgc2VyaWVzJywgMjAsICgpID0+IHsKICAgICAgICAgICAgICAgIGlmIChwYXJhbXMuc2VyaWVzTm9kZU1pblNpemUgPiAwKSB7CiAgICAgICAgICAgICAgICAgICAgZ3JvdXBTZXJpZXMoaC5yb290LCBoLCBzZXJpZXNOYW1lcywgcGFyYW1zLnNlcmllc05vZGVNaW5TaXplLCBwYXJhbXMuc2VyaWVzTWFwLCBwYXJhbXMudXNlR2VuZXJhbGl6ZWRTZXJpZXNQYXR0ZXJucyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sIHRyYWNrZXIpOwogICAgICAgIH0pCiAgICAgICAgICAgIC50aGVuKCgpID0+IHsKICAgICAgICAgICAgcmV0dXJuIHJ1bkFzeW5jVGFzaygnQWRkaW5nIGVkZ2VzJywgMzAsICgpID0+IHsKICAgICAgICAgICAgICAgIGFkZEVkZ2VzKGgsIGdyYXBoKTsKICAgICAgICAgICAgfSwgdHJhY2tlcik7CiAgICAgICAgfSkKICAgICAgICAgICAgLnRoZW4oKCkgPT4gewogICAgICAgICAgICByZXR1cm4gcnVuQXN5bmNUYXNrKCdGaW5kaW5nIHNpbWlsYXIgc3ViZ3JhcGhzJywgMzAsICgpID0+IHsKICAgICAgICAgICAgICAgIGgudGVtcGxhdGVzID0gZGV0ZWN0KGgsIHBhcmFtcy52ZXJpZnlUZW1wbGF0ZSk7CiAgICAgICAgICAgIH0sIHRyYWNrZXIpOwogICAgICAgIH0pCiAgICAgICAgICAgIC50aGVuKCgpID0+IHsKICAgICAgICAgICAgcmV0dXJuIGg7CiAgICAgICAgfSk7CiAgICB9CiAgICBmdW5jdGlvbiBqb2luQW5kQWdncmVnYXRlU3RhdHMoaCwgc3RhdHMpIHsKICAgICAgICAvLyBHZXQgYWxsIHRoZSBwb3NzaWJsZSBkZXZpY2UgYW5kIFhMQSBjbHVzdGVyIG5hbWVzLgogICAgICAgIGxldCBkZXZpY2VOYW1lcyA9IHt9OwogICAgICAgIGxldCB4bGFDbHVzdGVyTmFtZXMgPSB7fTsKICAgICAgICBsb2Rhc2guZWFjaChoLnJvb3QubGVhdmVzKCksIChub2RlTmFtZSkgPT4gewogICAgICAgICAgICBsZXQgbGVhZiA9IGgubm9kZShub2RlTmFtZSk7CiAgICAgICAgICAgIGlmIChsZWFmLmRldmljZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICBkZXZpY2VOYW1lc1tsZWFmLmRldmljZV0gPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChsZWFmLnhsYUNsdXN0ZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgeGxhQ2x1c3Rlck5hbWVzW2xlYWYueGxhQ2x1c3Rlcl0gPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgaC5kZXZpY2VzID0gbG9kYXNoLmtleXMoZGV2aWNlTmFtZXMpOwogICAgICAgIGgueGxhQ2x1c3RlcnMgPSBsb2Rhc2gua2V5cyh4bGFDbHVzdGVyTmFtZXMpOwogICAgICAgIC8vIFJlc2V0IHN0YXRzIGZvciBlYWNoIGdyb3VwIG5vZGUuCiAgICAgICAgbG9kYXNoLmVhY2goaC5nZXROb2RlTWFwKCksIChub2RlLCBub2RlTmFtZSkgPT4gewogICAgICAgICAgICBpZiAobm9kZS5pc0dyb3VwTm9kZSkgewogICAgICAgICAgICAgICAgbm9kZS5zdGF0cyA9IG5ldyBOb2RlU3RhdHMobnVsbCk7CiAgICAgICAgICAgICAgICBub2RlLmRldmljZUhpc3RvZ3JhbSA9IHt9OwogICAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgICAgLy8gQnViYmxlLXVwIHRoZSBzdGF0cyBhbmQgZGV2aWNlIGRpc3RyaWJ1dGlvbiBmcm9tIGxlYXZlcyB0byBwYXJlbnRzLgogICAgICAgIGxvZGFzaC5lYWNoKGgucm9vdC5sZWF2ZXMoKSwgKG5vZGVOYW1lKSA9PiB7CiAgICAgICAgICAgIGxldCBsZWFmID0gaC5ub2RlKG5vZGVOYW1lKTsKICAgICAgICAgICAgbGV0IG5vZGUgPSBsZWFmOwogICAgICAgICAgICB3aGlsZSAobm9kZS5wYXJlbnROb2RlICE9IG51bGwpIHsKICAgICAgICAgICAgICAgIGlmIChsZWFmLmRldmljZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IGRldmljZUhpc3RvZ3JhbSA9IG5vZGUucGFyZW50Tm9kZS5kZXZpY2VIaXN0b2dyYW07CiAgICAgICAgICAgICAgICAgICAgZGV2aWNlSGlzdG9ncmFtW2xlYWYuZGV2aWNlXSA9IChkZXZpY2VIaXN0b2dyYW1bbGVhZi5kZXZpY2VdIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChsZWFmLnhsYUNsdXN0ZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGxldCB4bGFDbHVzdGVySGlzdG9ncmFtID0gbm9kZS5wYXJlbnROb2RlCiAgICAgICAgICAgICAgICAgICAgICAgIC54bGFDbHVzdGVySGlzdG9ncmFtOwogICAgICAgICAgICAgICAgICAgIHhsYUNsdXN0ZXJIaXN0b2dyYW1bbGVhZi54bGFDbHVzdGVyXSA9CiAgICAgICAgICAgICAgICAgICAgICAgICh4bGFDbHVzdGVySGlzdG9ncmFtW2xlYWYueGxhQ2x1c3Rlcl0gfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGxlYWYuc3RhdHMgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIG5vZGUucGFyZW50Tm9kZS5zdGF0cy5jb21iaW5lKGxlYWYuc3RhdHMpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbm9kZSA9IG5vZGUucGFyZW50Tm9kZTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgfQogICAgZnVuY3Rpb24gZ2V0SW5jb21wYXRpYmxlT3BzKGhpZXJhcmNoeSwgaGllcmFyY2h5UGFyYW1zKSB7CiAgICAgICAgbGV0IG5vZGVzID0gW107CiAgICAgICAgbGV0IGFkZGVkU2VyaWVzTm9kZXMgPSB7fTsKICAgICAgICBsb2Rhc2guZWFjaChoaWVyYXJjaHkucm9vdC5sZWF2ZXMoKSwgKGxlYWYpID0+IHsKICAgICAgICAgICAgbGV0IG5vZGUgPSBoaWVyYXJjaHkubm9kZShsZWFmKTsKICAgICAgICAgICAgaWYgKG5vZGUudHlwZSA9PSBOb2RlVHlwZS5PUCkgewogICAgICAgICAgICAgICAgbGV0IG9wTm9kZSA9IG5vZGU7CiAgICAgICAgICAgICAgICBpZiAoIW9wTm9kZS5jb21wYXRpYmxlKSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKG9wTm9kZS5vd25pbmdTZXJpZXMpIHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGhpZXJhcmNoeVBhcmFtcyAmJgogICAgICAgICAgICAgICAgICAgICAgICAgICAgaGllcmFyY2h5UGFyYW1zLnNlcmllc01hcFtvcE5vZGUub3duaW5nU2VyaWVzXSA9PT0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTZXJpZXNHcm91cGluZ1R5cGUuVU5HUk9VUCkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gRm9yIHVuLWdyb3VwZWQgc2VyaWVzIG5vZGUsIGFkZCBlYWNoIG5vZGUgaW5kaXZpZHVhbGx5CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2Rlcy5wdXNoKG9wTm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBpZiAoIWFkZGVkU2VyaWVzTm9kZXNbb3BOb2RlLm93bmluZ1Nlcmllc10pIHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsZXQgc2VyaWVzID0gaGllcmFyY2h5Lm5vZGUob3BOb2RlLm93bmluZ1Nlcmllcyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKHNlcmllcykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBhZGRlZFNlcmllc05vZGVzW29wTm9kZS5vd25pbmdTZXJpZXNdID0gc2VyaWVzOwogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2Rlcy5wdXNoKHNlcmllcyk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBub2Rlcy5wdXNoKG9wTm9kZSk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gQ2hlY2sgdGhlIGVtYmVkZGluZ3MgZm9yIGludmFsaWQgb3BlcmF0aW9ucwogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlLmluRW1iZWRkaW5ncywgKGluTm9kZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGlmICghaW5Ob2RlLmNvbXBhdGlibGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgbm9kZXMucHVzaChpbk5vZGUpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gob3BOb2RlLm91dEVtYmVkZGluZ3MsIChvdXROb2RlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgaWYgKCFvdXROb2RlLmNvbXBhdGlibGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgbm9kZXMucHVzaChvdXROb2RlKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIHJldHVybiBub2RlczsKICAgIH0KICAgIC8qKgogICAgICogQ3JlYXRlcyB0aGUgbWV0YW5vZGVzIGluIHRoZSBoaWVyYXJjaGljYWwgZ3JhcGggYW5kIGFzc2lnbnMgcGFyZW50LWNoaWxkCiAgICAgKiByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGVtLiBBbHNvIGFzc2lnbnMgcmVsYXRpb25zaGlwcyBiZXR3ZWVuIGxpYnJhcnkKICAgICAqIGZ1bmN0aW9ucyBhbmQgdGhlaXIgdXNhZ2VzIHRocm91Z2hvdXQgdGhlIGdyYXBoLgogICAgICovCiAgICBmdW5jdGlvbiBhZGROb2RlcyhoLCBncmFwaCkgewogICAgICAgIC8vIE1hcHMgdGhlIG9wIG9mIGEgbm9kZSB0byBuYW1lcyBvZiBub2RlcyB0aGF0IGhhdmUgdGhlIG9wLiBVc2VkIHRvIHBvcHVsYXRlCiAgICAgICAgLy8gdGhlIGxpYnJhcnlGdW5jdGlvbnMgZmllbGQgb2YgdGhlIGhpZXJhcmNoeS4KICAgICAgICBjb25zdCBvcFRvTm9kZSA9IHt9OwogICAgICAgIGxvZGFzaC5lYWNoKGdyYXBoLm5vZGVzLCAobm9kZSwgbm9kZU5hbWUpID0+IHsKICAgICAgICAgICAgbGV0IHBhdGggPSBnZXRIaWVyYXJjaGljYWxQYXRoKG5vZGUubmFtZSk7CiAgICAgICAgICAgIGxldCBwYXJlbnQgPSBoLnJvb3Q7CiAgICAgICAgICAgIHBhcmVudC5kZXB0aCA9IE1hdGgubWF4KHBhdGgubGVuZ3RoLCBwYXJlbnQuZGVwdGgpOwogICAgICAgICAgICAvLyBUcmFjayB3aGljaCBub2RlcyBhcmUgYXNzb2NpYXRlZCB3aXRoIHdoaWNoIG9wcy4KICAgICAgICAgICAgaWYgKCFvcFRvTm9kZVtub2RlLm9wXSkgewogICAgICAgICAgICAgICAgb3BUb05vZGVbbm9kZS5vcF0gPSBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBvcFRvTm9kZVtub2RlLm9wXS5wdXNoKG5vZGUpOwogICAgICAgICAgICAvLyBDcmVhdGUgcGFyZW50IG1ldGFub2RlcyBmb3IgZWFjaCBkZXB0aC4gRm9yIGV4YW1wbGUgaWYgdGhlIG5vZGUgbmFtZQogICAgICAgICAgICAvLyBpcyAnYS9iL2MnLCB0aGVuIGNyZWF0ZSBtZXRhbm9kZXMgJ2EnIGFuZCAnYS9iJywgd2hlcmUgJ2EvYicgaXMgYSBjaGlsZAogICAgICAgICAgICAvLyBvZiBhLgogICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHBhdGgubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgIHBhcmVudC5kZXB0aCA9IE1hdGgubWF4KHBhcmVudC5kZXB0aCwgcGF0aC5sZW5ndGggLSBpKTsKICAgICAgICAgICAgICAgIHBhcmVudC5jYXJkaW5hbGl0eSArPSBub2RlLmNhcmRpbmFsaXR5OwogICAgICAgICAgICAgICAgcGFyZW50Lm9wSGlzdG9ncmFtW25vZGUub3BdID0gKHBhcmVudC5vcEhpc3RvZ3JhbVtub2RlLm9wXSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICBpZiAobm9kZS5kZXZpY2UgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHBhcmVudC5kZXZpY2VIaXN0b2dyYW1bbm9kZS5kZXZpY2VdID0KICAgICAgICAgICAgICAgICAgICAgICAgKHBhcmVudC5kZXZpY2VIaXN0b2dyYW1bbm9kZS5kZXZpY2VdIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChub2RlLnhsYUNsdXN0ZXIgIT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHBhcmVudC54bGFDbHVzdGVySGlzdG9ncmFtW25vZGUueGxhQ2x1c3Rlcl0gPQogICAgICAgICAgICAgICAgICAgICAgICAocGFyZW50LnhsYUNsdXN0ZXJIaXN0b2dyYW1bbm9kZS54bGFDbHVzdGVyXSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBJbmNyZW1lbnQgcGFyZW50cyBhcHByb3ByaWF0ZSBjb21wYXRpYmlsaXR5IGNvdW50CiAgICAgICAgICAgICAgICBpZiAobm9kZS5jb21wYXRpYmxlKSB7CiAgICAgICAgICAgICAgICAgICAgcGFyZW50LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uY29tcGF0aWJsZSA9CiAgICAgICAgICAgICAgICAgICAgICAgIChwYXJlbnQuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5jb21wYXRpYmxlIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHBhcmVudC5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmluY29tcGF0aWJsZSA9CiAgICAgICAgICAgICAgICAgICAgICAgIChwYXJlbnQuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGUgfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gSW5jcmVtZW50IGNhcGFiaWxpdHkgY291bnRzIGZvciBpbiBhbmQgb3V0IGVtYmVkZGluZ3MKICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKG5vZGUuaW5FbWJlZGRpbmdzLCAoaW5Ob2RlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgaWYgKGluTm9kZS5jb21wYXRpYmxlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHBhcmVudC5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGUgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHBhcmVudC5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGUgfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICAgICAgcGFyZW50LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlID0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIChwYXJlbnQuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGUgfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZS5vdXRFbWJlZGRpbmdzLCAob3V0Tm9kZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGlmIChvdXROb2RlLmNvbXBhdGlibGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcGFyZW50LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uY29tcGF0aWJsZSA9CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAocGFyZW50LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uY29tcGF0aWJsZSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnQuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGUgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHBhcmVudC5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmluY29tcGF0aWJsZSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBpZiAoaSA9PT0gcGF0aC5sZW5ndGggLSAxKSB7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBsZXQgbmFtZSA9IHBhdGhbaV07CiAgICAgICAgICAgICAgICBsZXQgY2hpbGQgPSBoLm5vZGUobmFtZSk7CiAgICAgICAgICAgICAgICBpZiAoIWNoaWxkKSB7CiAgICAgICAgICAgICAgICAgICAgY2hpbGQgPSBjcmVhdGVNZXRhbm9kZShuYW1lLCBoLmdyYXBoT3B0aW9ucyk7CiAgICAgICAgICAgICAgICAgICAgY2hpbGQucGFyZW50Tm9kZSA9IHBhcmVudDsKICAgICAgICAgICAgICAgICAgICBoLnNldE5vZGUobmFtZSwgY2hpbGQpOwogICAgICAgICAgICAgICAgICAgIHBhcmVudC5tZXRhZ3JhcGguc2V0Tm9kZShuYW1lLCBjaGlsZCk7CiAgICAgICAgICAgICAgICAgICAgaWYgKG5hbWUuaW5kZXhPZihGVU5DVElPTl9MSUJSQVJZX05PREVfUFJFRklYKSA9PT0gMCAmJgogICAgICAgICAgICAgICAgICAgICAgICBwYXJlbnQubmFtZSA9PT0gUk9PVF9OQU1FKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgbWV0YW5vZGUgcmVwcmVzZW50cyBhIGZ1bmN0aW9uIGluIHRoZSBMaWJyYXJ5LiBXZSBsYXRlciBjb3B5CiAgICAgICAgICAgICAgICAgICAgICAgIC8vIGl0cyBjb250ZW50cyB0byBkeW5hbWljYWxseSBpbmplY3QgZnVuY3Rpb24gZGF0YSBpbnRvIHRoZSBncmFwaAogICAgICAgICAgICAgICAgICAgICAgICAvLyB3aGVuIHRoZSBzdWJoaWVyYXJjaHkgb2YgYSBtZXRhbm9kZSBpcyBidWlsdCAodXBvbiBpdHMgZXhwYW5zaW9uKS4KICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgZnVuY3Rpb25OYW1lID0gbmFtZS5zdWJzdHJpbmcoRlVOQ1RJT05fTElCUkFSWV9OT0RFX1BSRUZJWC5sZW5ndGgpOwogICAgICAgICAgICAgICAgICAgICAgICAvLyBGb3Igbm93LCByZW1lbWJlciB0aGUgbWV0YW5vZGUgdGhhdCByZXByZXNlbnRzIHRoZSBmdW5jdGlvbiB3aXRoCiAgICAgICAgICAgICAgICAgICAgICAgIC8vIHRoaXMgbmFtZS4KICAgICAgICAgICAgICAgICAgICAgICAgaWYgKCFvcFRvTm9kZVtmdW5jdGlvbk5hbWVdKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBvcFRvTm9kZVtmdW5jdGlvbk5hbWVdID0gW107CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgaC5saWJyYXJ5RnVuY3Rpb25zW2Z1bmN0aW9uTmFtZV0gPSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2RlOiBjaGlsZCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHVzYWdlczogb3BUb05vZGVbZnVuY3Rpb25OYW1lXSwKICAgICAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICAgICAgY2hpbGQuYXNzb2NpYXRlZEZ1bmN0aW9uID0gZnVuY3Rpb25OYW1lOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHBhcmVudCA9IGNoaWxkOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEFzc3VtaW5nIG5vZGUgbmFtZSBpcyAnYS9iL2MnLCBhc3NpZ24gdGhlIE9wTm9kZSBhcyBhIGNoaWxkIG9mIHRoZQogICAgICAgICAgICAvLyBtZXRhbm9kZSAnYS9iJy4KICAgICAgICAgICAgaC5zZXROb2RlKG5vZGUubmFtZSwgbm9kZSk7CiAgICAgICAgICAgIG5vZGUucGFyZW50Tm9kZSA9IHBhcmVudDsKICAgICAgICAgICAgcGFyZW50Lm1ldGFncmFwaC5zZXROb2RlKG5vZGUubmFtZSwgbm9kZSk7CiAgICAgICAgICAgIC8vIEFkZCBlYWNoIG9mIHRoZSBpbi1lbWJlZGRpbmdzIGFuZCBvdXQtZW1iZWRkaW5ncyBpbiB0aGUgaGllcmFyY2h5LgogICAgICAgICAgICBsb2Rhc2guZWFjaChub2RlLmluRW1iZWRkaW5ncywgZnVuY3Rpb24gKGVtYmVkZGluZykgewogICAgICAgICAgICAgICAgaC5zZXROb2RlKGVtYmVkZGluZy5uYW1lLCBlbWJlZGRpbmcpOwogICAgICAgICAgICAgICAgZW1iZWRkaW5nLnBhcmVudE5vZGUgPSBub2RlOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZS5vdXRFbWJlZGRpbmdzLCBmdW5jdGlvbiAoZW1iZWRkaW5nKSB7CiAgICAgICAgICAgICAgICBoLnNldE5vZGUoZW1iZWRkaW5nLm5hbWUsIGVtYmVkZGluZyk7CiAgICAgICAgICAgICAgICBlbWJlZGRpbmcucGFyZW50Tm9kZSA9IG5vZGU7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBGb3IgZWFjaCBtZXRhbm9kZSBpbiB0aGUgaGllcmFyY2hpY2FsIGdyYXBoLCB0aGlzIG1ldGhvZCBhZGRzOgogICAgICogdGhlIGVkZ2VzIGluIHRoZSBtZXRhZ3JhcGguIFRoZXNlIGFyZSBlZGdlcyBiZXR3ZWVuIG5vZGVzCiAgICAgKiB0aGF0IHNoYXJlIHRoZSBzYW1lIHBhcmVudC4KICAgICAqLwogICAgZnVuY3Rpb24gYWRkRWRnZXMoaCwgZ3JhcGgsIHNlcmllc05hbWVzKSB7CiAgICAgICAgbGV0IG5vZGVJbmRleCA9IGguZ2V0Tm9kZU1hcCgpOwogICAgICAgIC8vIEFuY2VzdG9yIHBhdGhzIGZvciB0aGUgc291cmNlIGFuZCBkZXN0aW5hdGlvbiBub2RlcyBvZiBhbiBlZGdlLiBUaGVzZSBhcmUKICAgICAgICAvLyByZXVzZWQgZm9yIGVhY2ggZWRnZSByYXRoZXIgdGhhbiBhbGxvY2F0aW5nIG5ldyBvbmVzLiBJdCdzIGFib3V0IDEwJSBmYXN0ZXIKICAgICAgICAvLyB0aGFuIGFsbG9jYXRpbmcgbmV3IG9uZXMgb24gZWFjaCBwYXNzIHRocm91Z2ggdGhlIGxvb3AuCiAgICAgICAgbGV0IHNvdXJjZVBhdGggPSBbXTsKICAgICAgICBsZXQgZGVzdFBhdGggPSBbXTsKICAgICAgICAvLyBJbnNlcnQgdGhlIGFuY2VzdG9yIHBhdGggZm9yIGEgbm9kZSBpbnRvIHRoZSBwcm92aWRlZCBhcnJheSwgaW5jbHVkaW5nIHRoZQogICAgICAgIC8vIG5vZGUgaXRzZWxmLiBSZXR1cm4gdGhlIGluZGV4IG9mIHRoZSBsYXN0IG5vZGUgaW5zZXJ0ZWQgKGFsd2F5cyBST09UKS4KICAgICAgICBsZXQgZ2V0UGF0aCA9IChub2RlLCBwYXRoKSA9PiB7CiAgICAgICAgICAgIGxldCBpID0gMDsKICAgICAgICAgICAgd2hpbGUgKG5vZGUpIHsKICAgICAgICAgICAgICAgIHBhdGhbaSsrXSA9IG5vZGUubmFtZTsKICAgICAgICAgICAgICAgIG5vZGUgPSBub2RlLnBhcmVudE5vZGU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGkgLSAxOwogICAgICAgIH07CiAgICAgICAgbG9kYXNoLmVhY2goZ3JhcGguZWRnZXMsIChiYXNlRWRnZSkgPT4gewogICAgICAgICAgICAvLyBHZXQgdGhlIGhpZXJhcmNoaWNhbCBwYXRocyBmb3IgdGhlIHNvdXJjZSBhbmQgZGVzdGluYXRpb24gb2YgdGhlIGVkZ2UuCiAgICAgICAgICAgIGxldCBzb3VyY2VBbmNlc3RvckluZGV4ID0gZ2V0UGF0aChncmFwaC5ub2Rlc1tiYXNlRWRnZS52XSwgc291cmNlUGF0aCk7CiAgICAgICAgICAgIGxldCBkZXN0QW5jZXN0b3JJbmRleCA9IGdldFBhdGgoZ3JhcGgubm9kZXNbYmFzZUVkZ2Uud10sIGRlc3RQYXRoKTsKICAgICAgICAgICAgLy8gSWYgdGhlIGhpZXJhcmNoaWNhbCBwYXRoIGNhbm5vdCBiZSBmb3VuZCBmb3IgZWl0aGVyIGVuZHBvaW50LCB0aGVuIHdlCiAgICAgICAgICAgIC8vIGNhbm5vdCBjcmVhdGUgdGhlIGVkZ2UuIFRoaXMgaGFwcGVucyBmb3IgZXhhbXBsZSB3aGVuIGEgbm9kZSBoYXMgYQogICAgICAgICAgICAvLyBjb250cm9sIGRlcGVuZGVuY3kgb24gYSBzdW1tYXJ5IG5vZGUsIHdoaWNoIGFyZSBlbWJlZGRlZC4KICAgICAgICAgICAgaWYgKHNvdXJjZUFuY2VzdG9ySW5kZXggPT09IC0xIHx8IGRlc3RBbmNlc3RvckluZGV4ID09PSAtMSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEZpbmQgdGhlIGxvd2VzdCBzaGFyZWQgYW5jZXN0b3IgYmV0d2VlbiBzb3VyY2UgYW5kIGRlc3QgYnkgbG9va2luZyBmb3IKICAgICAgICAgICAgLy8gdGhlIGhpZ2hlc3Qgbm9kZXMgdGhhdCBkaWZmZXIgYmV0d2VlbiB0aGVpciBhbmNlc3RvciBwYXRocy4KICAgICAgICAgICAgd2hpbGUgKHNvdXJjZVBhdGhbc291cmNlQW5jZXN0b3JJbmRleF0gPT09IGRlc3RQYXRoW2Rlc3RBbmNlc3RvckluZGV4XSkgewogICAgICAgICAgICAgICAgc291cmNlQW5jZXN0b3JJbmRleC0tOwogICAgICAgICAgICAgICAgZGVzdEFuY2VzdG9ySW5kZXgtLTsKICAgICAgICAgICAgICAgIGlmIChzb3VyY2VBbmNlc3RvckluZGV4IDwgMCB8fCBkZXN0QW5jZXN0b3JJbmRleCA8IDApIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIHdvdWxkIG9ubHkgb2NjdXIgaWYgdGhlIHR3byBub2RlcyB3ZXJlIHRoZSBzYW1lIChhIGN5Y2xlIGluIHRoZQogICAgICAgICAgICAgICAgICAgIC8vIGdyYXBoKSwgb3IgaWYgb25lIGVuZHBvaW50IHdhcyBhIHN0cmljdCBhbmNlc3RvciBvZiB0aGUgb3RoZXIuIFRoZQogICAgICAgICAgICAgICAgICAgIC8vIGxhdHRlciBzaG91bGRuJ3QgaGFwcGVuIGJlY2F1c2Ugd2UgcmVuYW1lIG5vZGVzIHdoaWNoIGFyZSBib3RoCiAgICAgICAgICAgICAgICAgICAgLy8gbWV0YW5vZGVzIGFuZCBvcCBub2Rlcy4gRS5nLiAnQS9CJyBiZWNvbWVzICdBL0IvKEIpJy4KICAgICAgICAgICAgICAgICAgICB0aHJvdyBFcnJvcignTm8gZGlmZmVyZW5jZSBmb3VuZCBiZXR3ZWVuIGFuY2VzdG9yIHBhdGhzLicpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBzaGFyZWRBbmNlc3Rvck5vZGUgPSAobm9kZUluZGV4W3NvdXJjZVBhdGhbc291cmNlQW5jZXN0b3JJbmRleCArIDFdXSk7CiAgICAgICAgICAgIGxldCBzb3VyY2VBbmNlc3Rvck5hbWUgPSBzb3VyY2VQYXRoW3NvdXJjZUFuY2VzdG9ySW5kZXhdOwogICAgICAgICAgICBsZXQgZGVzdEFuY2VzdG9yTmFtZSA9IGRlc3RQYXRoW2Rlc3RBbmNlc3RvckluZGV4XTsKICAgICAgICAgICAgLy8gRmluZCBvciBjcmVhdGUgdGhlIE1ldGFlZGdlIHdoaWNoIHNob3VsZCBjb250YWluIHRoaXMgQmFzZUVkZ2UgaW5zaWRlCiAgICAgICAgICAgIC8vIHRoZSBzaGFyZWQgYW5jZXN0b3IuCiAgICAgICAgICAgIGxldCBtZXRhZWRnZSA9IHNoYXJlZEFuY2VzdG9yTm9kZS5tZXRhZ3JhcGguZWRnZShzb3VyY2VBbmNlc3Rvck5hbWUsIGRlc3RBbmNlc3Rvck5hbWUpOwogICAgICAgICAgICBpZiAoIW1ldGFlZGdlKSB7CiAgICAgICAgICAgICAgICBtZXRhZWRnZSA9IGNyZWF0ZU1ldGFlZGdlKHNvdXJjZUFuY2VzdG9yTmFtZSwgZGVzdEFuY2VzdG9yTmFtZSk7CiAgICAgICAgICAgICAgICBzaGFyZWRBbmNlc3Rvck5vZGUubWV0YWdyYXBoLnNldEVkZ2Uoc291cmNlQW5jZXN0b3JOYW1lLCBkZXN0QW5jZXN0b3JOYW1lLCBtZXRhZWRnZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKCFzaGFyZWRBbmNlc3Rvck5vZGUuaGFzTm9uQ29udHJvbEVkZ2VzICYmCiAgICAgICAgICAgICAgICAhYmFzZUVkZ2UuaXNDb250cm9sRGVwZW5kZW5jeSkgewogICAgICAgICAgICAgICAgc2hhcmVkQW5jZXN0b3JOb2RlLmhhc05vbkNvbnRyb2xFZGdlcyA9IHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgbWV0YWVkZ2UuYWRkQmFzZUVkZ2UoYmFzZUVkZ2UsIGgpOwogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBVc2luZyB0aGUgaGllcmFyY2h5IHRlbXBsYXRlIGluZm9ybWF0aW9uLCBkZXRlY3Qgc2VyaWVzIGluIHRoZSBwcm92aWRlZAogICAgICogbWV0YW5vZGUuICBGb3IgZWFjaCBkZXRlY3RlZCBzZXJpZXMsIGNyZWF0ZSBhIG5ldyBTZXJpZXNOb2RlCiAgICAgKiBhbmQgcmVtb3ZlIHNlcmllcyBtZW1iZXJzIGZyb20gdGhlIG1ldGFub2RlJ3MgbWV0YWdyYXBoIGFuZCBtb3ZlIHRoZW0gdG8KICAgICAqIHRoZSBuZXcgc2VyaWVzIG5vZGUncyBtZXRhZ3JhcGguCiAgICAgKgogICAgICogQHBhcmFtIG1ldGFub2RlCiAgICAgKiBAcGFyYW0gaGllcmFyY2h5CiAgICAgKiBAcGFyYW0gc2VyaWVzTmFtZXMgTWFwIG9mIG5vZGUgbmFtZXMgdG8gdGhlaXIgc2VyaWVzIHRoZXkgYXJlIGNvbnRhaW5lZCBpbi4KICAgICAqICAgICBUaGlzIHNob3VsZCBiZSBwcm92aWRlZCBlbXB0eSBhbmQgaXMgcG9wdWxhdGVkIGJ5IHRoaXMgbWV0aG9kLgogICAgICogQHBhcmFtIHRocmVzaG9sZCBJZiB0aGUgc2VyaWVzIGhhcyB0aGlzIG1hbnkgbm9kZXMgb3IgbW9yZSwgdGhlbiBncm91cCB0aGVtCiAgICAgKiAgICAgaW50byBhIHNlcmllcy4KICAgICAqIEBwYXJhbSBtYXAgTWFwIG9mIHNlcmllcyBuYW1lcyB0byB0aGVpciBzZXJpZXMgZ3JvdXBpbmcgdHlwZSwgaWYgb25lIGhhcwogICAgICogICAgIGJlZW4gc2V0LgogICAgICogQHBhcmFtIHVzZUdlbmVyYWxpemVkU2VyaWVzUGF0dGVybnMgV2hldGhlciB0byB1c2UgZmluZCBwYXR0ZXJucyBmb3Igc2VyaWVzCiAgICAgKiAgICAgbm9kZXMgdXNpbmcgYW55IHBhcnRzIG9mIG5hbWVzIG9mIG5vZGVzLiBJZiBmYWxzZSwgb25seSB1c2VzIHBhdHRlcm5zCiAgICAgKiAgICAgZGlzY292ZXJlZCB3aXRoaW4gbnVtZXJpYyBzdWZmaXhlcyBvZiBub2RlcyBuYW1lcy4KICAgICAqIEByZXR1cm4gQSBkaWN0aW9uYXJ5IGZyb20gbm9kZSBuYW1lIHRvIHNlcmllcyBub2RlIG5hbWUgdGhhdCBjb250YWlucyB0aGUKICAgICAqICAgICBub2RlLgogICAgICovCiAgICBmdW5jdGlvbiBncm91cFNlcmllcyhtZXRhbm9kZSwgaGllcmFyY2h5LCBzZXJpZXNOYW1lcywgdGhyZXNob2xkLCBtYXAsIHVzZUdlbmVyYWxpemVkU2VyaWVzUGF0dGVybnMpIHsKICAgICAgICBsZXQgbWV0YWdyYXBoID0gbWV0YW5vZGUubWV0YWdyYXBoOwogICAgICAgIGxvZGFzaC5lYWNoKG1ldGFncmFwaC5ub2RlcygpLCAobikgPT4gewogICAgICAgICAgICBsZXQgY2hpbGQgPSBtZXRhZ3JhcGgubm9kZShuKTsKICAgICAgICAgICAgaWYgKGNoaWxkLnR5cGUgPT09IE5vZGVUeXBlLk1FVEEpIHsKICAgICAgICAgICAgICAgIGdyb3VwU2VyaWVzKGNoaWxkLCBoaWVyYXJjaHksIHNlcmllc05hbWVzLCB0aHJlc2hvbGQsIG1hcCwgdXNlR2VuZXJhbGl6ZWRTZXJpZXNQYXR0ZXJucyk7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICBsZXQgY2x1c3RlcnMgPSBjbHVzdGVyTm9kZXMobWV0YWdyYXBoKTsKICAgICAgICBjb25zdCBkZXRlY3RTZXJpZXNNZXRob2QgPSB1c2VHZW5lcmFsaXplZFNlcmllc1BhdHRlcm5zCiAgICAgICAgICAgID8gZGV0ZWN0U2VyaWVzQW55d2hlcmVJbk5vZGVOYW1lCiAgICAgICAgICAgIDogZGV0ZWN0U2VyaWVzVXNpbmdOdW1lcmljU3VmZml4ZXM7CiAgICAgICAgbGV0IHNlcmllc0RpY3QgPSBkZXRlY3RTZXJpZXNNZXRob2QoY2x1c3RlcnMsIG1ldGFncmFwaCwgaGllcmFyY2h5LmdyYXBoT3B0aW9ucyk7CiAgICAgICAgLy8gQWRkIGVhY2ggc2VyaWVzIG5vZGUgdG8gdGhlIGdyYXBoIGFuZCBhZGQgaXRzIGdyb3VwZWQgY2hpbGRyZW4gdG8gaXRzIG93bgogICAgICAgIC8vIG1ldGFncmFwaC4KICAgICAgICBsb2Rhc2guZWFjaChzZXJpZXNEaWN0LCBmdW5jdGlvbiAoc2VyaWVzTm9kZSwgc2VyaWVzTmFtZSkgewogICAgICAgICAgICBsZXQgbm9kZU1lbWJlck5hbWVzID0gc2VyaWVzTm9kZS5tZXRhZ3JhcGgubm9kZXMoKTsKICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZU1lbWJlck5hbWVzLCAobikgPT4gewogICAgICAgICAgICAgICAgbGV0IGNoaWxkID0gbWV0YWdyYXBoLm5vZGUobik7CiAgICAgICAgICAgICAgICBpZiAoIWNoaWxkLm93bmluZ1NlcmllcykgewogICAgICAgICAgICAgICAgICAgIGNoaWxkLm93bmluZ1NlcmllcyA9IHNlcmllc05hbWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBJZiB0aGUgc2VyaWVzIGNvbnRhaW5zIGxlc3MgdGhhbiB0aGUgdGhyZXNob2xkIG51bWJlciBvZiBub2RlcyBhbmQKICAgICAgICAgICAgLy8gdGhpcyBzZXJpZXMgaGFzIG5vdCBiZWVuIGFkZGluZyB0byB0aGUgc2VyaWVzIG1hcCwgdGhlbiBzZXQgdGhpcwogICAgICAgICAgICAvLyBzZXJpZXMgdG8gYmUgc2hvd24gdW5ncm91cGVkIGluIHRoZSBtYXAuCiAgICAgICAgICAgIGlmIChub2RlTWVtYmVyTmFtZXMubGVuZ3RoIDwgdGhyZXNob2xkICYmICEoc2VyaWVzTm9kZS5uYW1lIGluIG1hcCkpIHsKICAgICAgICAgICAgICAgIG1hcFtzZXJpZXNOb2RlLm5hbWVdID0gU2VyaWVzR3JvdXBpbmdUeXBlLlVOR1JPVVA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gSWYgdGhlIHNlcmllcyBpcyBpbiB0aGUgbWFwIGFzIHVuZ3JvdXBlZCB0aGVuIGRvIG5vdCBncm91cCB0aGUgc2VyaWVzLgogICAgICAgICAgICBpZiAoc2VyaWVzTm9kZS5uYW1lIGluIG1hcCAmJgogICAgICAgICAgICAgICAgbWFwW3Nlcmllc05vZGUubmFtZV0gPT09IFNlcmllc0dyb3VwaW5nVHlwZS5VTkdST1VQKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaGllcmFyY2h5LnNldE5vZGUoc2VyaWVzTmFtZSwgc2VyaWVzTm9kZSk7IC8vIGFkZCB0byB0aGUgaW5kZXgKICAgICAgICAgICAgbWV0YWdyYXBoLnNldE5vZGUoc2VyaWVzTmFtZSwgc2VyaWVzTm9kZSk7CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKG5vZGVNZW1iZXJOYW1lcywgKG4pID0+IHsKICAgICAgICAgICAgICAgIGxldCBjaGlsZCA9IG1ldGFncmFwaC5ub2RlKG4pOwogICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5tZXRhZ3JhcGguc2V0Tm9kZShuLCBjaGlsZCk7CiAgICAgICAgICAgICAgICBzZXJpZXNOb2RlLnBhcmVudE5vZGUgPSBjaGlsZC5wYXJlbnROb2RlOwogICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5jYXJkaW5hbGl0eSsrOwogICAgICAgICAgICAgICAgaWYgKGNoaWxkLmRldmljZSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5kZXZpY2VIaXN0b2dyYW1bY2hpbGQuZGV2aWNlXSA9CiAgICAgICAgICAgICAgICAgICAgICAgIChzZXJpZXNOb2RlLmRldmljZUhpc3RvZ3JhbVtjaGlsZC5kZXZpY2VdIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChjaGlsZC54bGFDbHVzdGVyICE9IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBzZXJpZXNOb2RlLnhsYUNsdXN0ZXJIaXN0b2dyYW1bY2hpbGQueGxhQ2x1c3Rlcl0gPQogICAgICAgICAgICAgICAgICAgICAgICAoc2VyaWVzTm9kZS54bGFDbHVzdGVySGlzdG9ncmFtW2NoaWxkLnhsYUNsdXN0ZXJdIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEluY3JlbWVudCBwYXJlbnRzIGFwcHJvcHJpYXRlIGNvbXBhdGliaWxpdHkgY291bnQKICAgICAgICAgICAgICAgIGlmIChjaGlsZC5jb21wYXRpYmxlKSB7CiAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGUgPQogICAgICAgICAgICAgICAgICAgICAgICAoc2VyaWVzTm9kZS5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGUgfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmluY29tcGF0aWJsZSA9CiAgICAgICAgICAgICAgICAgICAgICAgIChzZXJpZXNOb2RlLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlIHx8IDApICsgMTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEluY3JlbWVudCBjYXBhYmlsaXR5IGNvdW50cyBmb3IgaW4gYW5kIG91dCBlbWJlZGRpbmdzCiAgICAgICAgICAgICAgICBsb2Rhc2guZWFjaChjaGlsZC5pbkVtYmVkZGluZ3MsIChpbk5vZGUpID0+IHsKICAgICAgICAgICAgICAgICAgICBpZiAoaW5Ob2RlLmNvbXBhdGlibGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZS5jb21wYXRpYmlsaXR5SGlzdG9ncmFtLmNvbXBhdGlibGUgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHNlcmllc05vZGUuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5jb21wYXRpYmxlIHx8IDApICsgMTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHNlcmllc05vZGUuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGUgPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgKHNlcmllc05vZGUuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGUgfHwgMCkgKyAxOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgbG9kYXNoLmVhY2goY2hpbGQub3V0RW1iZWRkaW5ncywgKG91dE5vZGUpID0+IHsKICAgICAgICAgICAgICAgICAgICBpZiAob3V0Tm9kZS5jb21wYXRpYmxlKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHNlcmllc05vZGUuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5jb21wYXRpYmxlID0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIChzZXJpZXNOb2RlLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uY29tcGF0aWJsZSB8fCAwKSArIDE7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICBzZXJpZXNOb2RlLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlID0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIChzZXJpZXNOb2RlLmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlIHx8IDApICsgMTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGNoaWxkLnBhcmVudE5vZGUgPSBzZXJpZXNOb2RlOwogICAgICAgICAgICAgICAgc2VyaWVzTmFtZXNbbl0gPSBzZXJpZXNOYW1lOwogICAgICAgICAgICAgICAgLy8gUmVtb3ZlIG5vdy1ncm91cGVkIG5vZGUgZnJvbSBpdHMgb3JpZ2luYWwgcGFyZW50J3MgbWV0YWdyYXBoLgogICAgICAgICAgICAgICAgbWV0YWdyYXBoLnJlbW92ZU5vZGUobik7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgfQogICAgLyoqIGNsdXN0ZXIgb3Atbm9kZXMgd2l0aCBzaW1pbGFyIG9wICovCiAgICBmdW5jdGlvbiBjbHVzdGVyTm9kZXMobWV0YWdyYXBoKSB7CiAgICAgICAgbGV0IHJlc3VsdCA9IHt9OwogICAgICAgIHJldHVybiBsb2Rhc2gucmVkdWNlKG1ldGFncmFwaC5ub2RlcygpLCAoY2x1c3RlcnMsIG4pID0+IHsKICAgICAgICAgICAgbGV0IGNoaWxkID0gbWV0YWdyYXBoLm5vZGUobik7CiAgICAgICAgICAgIGlmIChjaGlsZC50eXBlID09PSBOb2RlVHlwZS5NRVRBKSB7CiAgICAgICAgICAgICAgICAvLyBza2lwIG1ldGFub2RlcwogICAgICAgICAgICAgICAgcmV0dXJuIGNsdXN0ZXJzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCB0ZW1wbGF0ZSA9IGNoaWxkLm9wOwogICAgICAgICAgICBpZiAodGVtcGxhdGUpIHsKICAgICAgICAgICAgICAgIGNsdXN0ZXJzW3RlbXBsYXRlXSA9IGNsdXN0ZXJzW3RlbXBsYXRlXSB8fCBbXTsKICAgICAgICAgICAgICAgIGNsdXN0ZXJzW3RlbXBsYXRlXS5wdXNoKGNoaWxkLm5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBjbHVzdGVyczsKICAgICAgICB9LCByZXN1bHQpOwogICAgfQogICAgLyoqCiAgICAgKiBGb3IgZWFjaCBjbHVzdGVyIG9mIG9wLW5vZGVzIGJhc2VkIG9wIHR5cGUsIHRyeSB0byBkZXRlY3QgZ3JvdXBpbmdzLgogICAgICogSW5mZXIgc2VyaWVzIG5hbWUgdXNpbmcgYnkgdHJ5aW5nIHRvIGZpbmQgcGF0dGVybiAnPG51bWJlcj4nIHRvd2FyZHMgdGhlIGVuZAogICAgICogb2Ygbm9kZSBuYW1lcy4KICAgICAqCiAgICAgKiBAcGFyYW0gY2x1c3RlcnMgRGljdGlvbmFyeSBvdXRwdXQgZnJvbSBjbHVzdGVyTm9kZXMoKS4KICAgICAqIEBwYXJhbSBtZXRhZ3JhcGgKICAgICAqIEByZXR1cm4gQSBkaWN0aW9uYXJ5IGZyb20gc2VyaWVzIG5hbWUgPT4gc2VyaWVzTm9kZQogICAgICovCiAgICBmdW5jdGlvbiBkZXRlY3RTZXJpZXNVc2luZ051bWVyaWNTdWZmaXhlcyhjbHVzdGVycywgbWV0YWdyYXBoLCBncmFwaE9wdGlvbnMpIHsKICAgICAgICBsZXQgc2VyaWVzRGljdCA9IHt9OwogICAgICAgIGxvZGFzaC5lYWNoKGNsdXN0ZXJzLCBmdW5jdGlvbiAobWVtYmVycywgY2x1c3RlcklkKSB7CiAgICAgICAgICAgIGlmIChtZW1iZXJzLmxlbmd0aCA8PSAxKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0gLy8gaXNvbGF0ZWQgY2x1c3RlcnMgY2FuJ3QgbWFrZSBzZXJpZXMKICAgICAgICAgICAgLyoqIEB0eXBlIHtPYmplY3R9ICBBIGRpY3Rpb25hcnkgbWFwcGluZyBzZXJpZXNOYW1lIHRvIHNlcmllc0luZm9BcnJheSwKICAgICAgICAgICAgICogd2hpY2ggaXMgYW4gYXJyYXkgdGhhdCBjb250YWlucyBvYmplY3RzIHdpdGggbmFtZSwgaWQsIHByZWZpeCwgc3VmZml4LAogICAgICAgICAgICAgKiBhbmQgcGFyZW50IHByb3BlcnRpZXMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICBsZXQgY2FuZGlkYXRlc0RpY3QgPSB7fTsKICAgICAgICAgICAgLy8gR3JvdXAgYWxsIG5vZGVzIHRoYXQgaGF2ZSB0aGUgc2FtZSBuYW1lLCB3aXRoIHRoZSBleGNlcHRpb24gb2YgYQogICAgICAgICAgICAvLyBudW1iZXIgYXQgdGhlIGVuZCBvZiB0aGUgbmFtZSBhZnRlciBhbiB1bmRlcnNjb3JlLCB3aGljaCBpcyBhbGxvd2VkIHRvCiAgICAgICAgICAgIC8vIHZhcnkuCiAgICAgICAgICAgIGxvZGFzaC5lYWNoKG1lbWJlcnMsIGZ1bmN0aW9uIChuYW1lKSB7CiAgICAgICAgICAgICAgICBsZXQgaXNHcm91cCA9IG5hbWUuY2hhckF0KG5hbWUubGVuZ3RoIC0gMSkgPT09ICcqJzsKICAgICAgICAgICAgICAgIGxldCBuYW1lcGF0aCA9IG5hbWUuc3BsaXQoJy8nKTsKICAgICAgICAgICAgICAgIGxldCBsZWFmID0gbmFtZXBhdGhbbmFtZXBhdGgubGVuZ3RoIC0gMV07CiAgICAgICAgICAgICAgICBsZXQgcGFyZW50ID0gbmFtZXBhdGguc2xpY2UoMCwgbmFtZXBhdGgubGVuZ3RoIC0gMSkuam9pbignLycpOwogICAgICAgICAgICAgICAgbGV0IG1hdGNoZXMgPSBsZWFmLm1hdGNoKC9eKFxEKilfKFxkKykkLyk7CiAgICAgICAgICAgICAgICBsZXQgcHJlZml4OwogICAgICAgICAgICAgICAgbGV0IGlkOwogICAgICAgICAgICAgICAgbGV0IHN1ZmZpeCA9ICcnOwogICAgICAgICAgICAgICAgaWYgKG1hdGNoZXMpIHsKICAgICAgICAgICAgICAgICAgICAvLyBpZiBmb3VuZCAnPG51bWJlcj4nIGluIHRoZSBuYW1lLCBhc3NpZ24gaWQuCiAgICAgICAgICAgICAgICAgICAgcHJlZml4ID0gbWF0Y2hlc1sxXTsgLy8gdGhlIGZyb250IG5vbi1udW1lcmljIGNoYXJhY3RlcnMKICAgICAgICAgICAgICAgICAgICBpZCA9IG1hdGNoZXNbMl07IC8vIHRoZSBkaWdpdHMKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIC8vIGZvciBub2RlIHdpdGhvdXQgJ188bnVtYmVyPicsIG1ha2UgdGhlbSB6ZXJvLXRoIGl0ZW1zLgogICAgICAgICAgICAgICAgICAgIHByZWZpeCA9IGlzR3JvdXAgPyBsZWFmLnN1YnN0cigwLCBsZWFmLmxlbmd0aCAtIDEpIDogbGVhZjsKICAgICAgICAgICAgICAgICAgICBpZCA9IDA7CiAgICAgICAgICAgICAgICAgICAgc3VmZml4ID0gaXNHcm91cCA/ICcqJyA6ICcnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IHNlcmllc05hbWUgPSBnZXRTZXJpZXNOb2RlTmFtZShwcmVmaXgsIHN1ZmZpeCwgcGFyZW50KTsKICAgICAgICAgICAgICAgIGNhbmRpZGF0ZXNEaWN0W3Nlcmllc05hbWVdID0gY2FuZGlkYXRlc0RpY3Rbc2VyaWVzTmFtZV0gfHwgW107CiAgICAgICAgICAgICAgICBsZXQgc2VyaWVzTm9kZSA9IGNyZWF0ZVNlcmllc05vZGUocHJlZml4LCBzdWZmaXgsIHBhcmVudCwgK2lkLCBuYW1lLCBncmFwaE9wdGlvbnMpOwogICAgICAgICAgICAgICAgY2FuZGlkYXRlc0RpY3Rbc2VyaWVzTmFtZV0ucHVzaChzZXJpZXNOb2RlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIEluIGVhY2ggZ3JvdXAgb2Ygbm9kZXMsIGdyb3VwIG5vZGVzIGluIGJ1bmNoZXMgdGhhdCBoYXZlIG1vbm90b25pY2FsbHkKICAgICAgICAgICAgLy8gaW5jcmVhc2luZyBudW1iZXJzIGluIHRoZWlyIG5hbWVzLiAgRWFjaCBvZiB0aGVzZSBidW5jaGVzIGlzIGEgc2VyaWVzLgogICAgICAgICAgICBsb2Rhc2guZWFjaChjYW5kaWRhdGVzRGljdCwgZnVuY3Rpb24gKHNlcmllc0luZm9BcnJheSwgc2VyaWVzTmFtZSkgewogICAgICAgICAgICAgICAgaWYgKHNlcmllc0luZm9BcnJheS5sZW5ndGggPCAyKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgc2VyaWVzSW5mb0FycmF5LnNvcnQoZnVuY3Rpb24gKGEsIGIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gK2EuY2x1c3RlcklkIC0gK2IuY2x1c3RlcklkOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICAvLyBMb29wIHRocm91Z2ggdGhlIG5vZGVzIHNvcnRlZCBieSBpdHMgZGV0ZWN0ZWQgc2VyaWVzIG51bWJlciwgZ3JvdXBpbmcKICAgICAgICAgICAgICAgIC8vIGFsbCBub2RlcyB3aXRoIG1vbm90b25pY2FsbHktaW5jcmVhc2luZyBzZXJpZXMgbnVtYmVycy4KICAgICAgICAgICAgICAgIGxldCBzZXJpZXNOb2RlcyA9IFtzZXJpZXNJbmZvQXJyYXlbMF1dOwogICAgICAgICAgICAgICAgZm9yIChsZXQgaW5kZXggPSAxOyBpbmRleCA8IHNlcmllc0luZm9BcnJheS5sZW5ndGg7IGluZGV4KyspIHsKICAgICAgICAgICAgICAgICAgICBsZXQgbmV4dE5vZGUgPSBzZXJpZXNJbmZvQXJyYXlbaW5kZXhdOwogICAgICAgICAgICAgICAgICAgIGlmIChuZXh0Tm9kZS5jbHVzdGVySWQgPT09CiAgICAgICAgICAgICAgICAgICAgICAgIHNlcmllc05vZGVzW3Nlcmllc05vZGVzLmxlbmd0aCAtIDFdLmNsdXN0ZXJJZCArIDEpIHsKICAgICAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZXMucHVzaChuZXh0Tm9kZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBhZGRTZXJpZXNUb0RpY3Qoc2VyaWVzTm9kZXMsIHNlcmllc0RpY3QsICtjbHVzdGVySWQsIG1ldGFncmFwaCwgZ3JhcGhPcHRpb25zKTsKICAgICAgICAgICAgICAgICAgICBzZXJpZXNOb2RlcyA9IFtuZXh0Tm9kZV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBhZGRTZXJpZXNUb0RpY3Qoc2VyaWVzTm9kZXMsIHNlcmllc0RpY3QsICtjbHVzdGVySWQsIG1ldGFncmFwaCwgZ3JhcGhPcHRpb25zKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfSk7CiAgICAgICAgcmV0dXJuIHNlcmllc0RpY3Q7CiAgICB9CiAgICAvKioKICAgICAqIEZvciBlYWNoIGNsdXN0ZXIgb2Ygb3Atbm9kZXMgYmFzZWQgb3AgdHlwZSwgdHJ5IHRvIGRldGVjdCBncm91cGluZ3MuCiAgICAgKiBJbmZlciBzZXJpZXMgbmFtZSB1c2luZyBieSB0cnlpbmcgdG8gZmluZCBhIHBhdHRlcm4gb2YgbnVtYmVycwogICAgICogYW55d2hlcmUgd2l0aGluIG5vZGUgbmFtZXMuCiAgICAgKgogICAgICogQHBhcmFtIGNsdXN0ZXJzIERpY3Rpb25hcnkgb3V0cHV0IGZyb20gY2x1c3Rlck5vZGVzKCkuCiAgICAgKiBAcGFyYW0gbWV0YWdyYXBoCiAgICAgKiBAcmV0dXJuIEEgZGljdGlvbmFyeSBmcm9tIHNlcmllcyBuYW1lID0+IHNlcmllc05vZGUKICAgICAqLwogICAgZnVuY3Rpb24gZGV0ZWN0U2VyaWVzQW55d2hlcmVJbk5vZGVOYW1lKGNsdXN0ZXJzLCBtZXRhZ3JhcGgsIGdyYXBoT3B0aW9ucykgewogICAgICAgIGxldCBzZXJpZXNEaWN0ID0ge307CiAgICAgICAgbG9kYXNoLmVhY2goY2x1c3RlcnMsIGZ1bmN0aW9uIChtZW1iZXJzLCBjbHVzdGVySWQpIHsKICAgICAgICAgICAgaWYgKG1lbWJlcnMubGVuZ3RoIDw9IDEpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfSAvLyBpc29sYXRlZCBjbHVzdGVycyBjYW4ndCBtYWtlIHNlcmllcwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUge09iamVjdH0gIEEgZGljdGlvbmFyeSBtYXBwaW5nIGEgc2VyaWVzIG5hbWUgdG8gYSBTZXJpZXNOb2RlLgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgbGV0IGZvcndhcmREaWN0ID0ge307CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBAdHlwZSB7T2JqZWN0fSAgQSBkaWN0aW9uYXJ5IG1hcHBpbmcgbWVtYmVyIG5hbWUgdG8gYW4gYXJyYXkgb2Ygc2VyaWVzCiAgICAgICAgICAgICAqIG5hbWVzIHRoaXMgbWVtYmVyIGNvdWxkIHBvdGVudGlhbGx5IGJlIGdyb3VwZWQgdW5kZXIgYW5kIHRoZQogICAgICAgICAgICAgKiBjb3JyZXNwb25kaW5nIGlkcy4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIGxldCByZXZlcnNlRGljdCA9IHt9OwogICAgICAgICAgICAvLyBHcm91cCBhbGwgbm9kZXMgdGhhdCBoYXZlIHRoZSBzYW1lIG5hbWUsIHdpdGggdGhlIGV4Y2VwdGlvbiBvZiBhCiAgICAgICAgICAgIC8vIG51bWJlciBhdCB0aGUgZW5kIG9mIHRoZSBuYW1lIGFmdGVyIGFuIHVuZGVyc2NvcmUsIHdoaWNoIGlzIGFsbG93ZWQgdG8KICAgICAgICAgICAgLy8gdmFyeS4KICAgICAgICAgICAgbG9kYXNoLmVhY2gobWVtYmVycywgZnVuY3Rpb24gKG5hbWUpIHsKICAgICAgICAgICAgICAgIGxldCBpc0dyb3VwID0gbmFtZS5jaGFyQXQobmFtZS5sZW5ndGggLSAxKSA9PT0gJyonOwogICAgICAgICAgICAgICAgbGV0IG5hbWVwYXRoID0gbmFtZS5zcGxpdCgnLycpOwogICAgICAgICAgICAgICAgbGV0IGxlYWYgPSBuYW1lcGF0aFtuYW1lcGF0aC5sZW5ndGggLSAxXTsKICAgICAgICAgICAgICAgIGxldCBwYXJlbnQgPSBuYW1lcGF0aC5zbGljZSgwLCBuYW1lcGF0aC5sZW5ndGggLSAxKS5qb2luKCcvJyk7CiAgICAgICAgICAgICAgICBjb25zdCBudW1SZWdleCA9IC8oXGQrKS9nOwogICAgICAgICAgICAgICAgbGV0IG1hdGNoUmVzdWx0OwogICAgICAgICAgICAgICAgbGV0IHByZWZpeDsKICAgICAgICAgICAgICAgIGxldCBpZDsKICAgICAgICAgICAgICAgIGxldCBzdWZmaXg7CiAgICAgICAgICAgICAgICBsZXQgc2VyaWVzTmFtZTsKICAgICAgICAgICAgICAgIGxldCBtYXRjaGVkID0gMDsKICAgICAgICAgICAgICAgIC8vIFNjYW4gb3ZlciB0aGUgZW50aXJlIGxlYWYgbmFtZSBhbmQgbWF0Y2ggYW55IHBvc3NpYmxlIG51bWJlcnMsCiAgICAgICAgICAgICAgICAvLyBhbmQgcHV0IHRoZSByZXN1bHRzIGludG8gY29ycmVzcG9uZGluZyBkaWN0aW9uYXJpZXMuCiAgICAgICAgICAgICAgICB3aGlsZSAoKG1hdGNoUmVzdWx0ID0gbnVtUmVnZXguZXhlYyhsZWFmKSkpIHsKICAgICAgICAgICAgICAgICAgICArK21hdGNoZWQ7CiAgICAgICAgICAgICAgICAgICAgcHJlZml4ID0gbGVhZi5zbGljZSgwLCBtYXRjaFJlc3VsdC5pbmRleCk7CiAgICAgICAgICAgICAgICAgICAgaWQgPSBtYXRjaFJlc3VsdFswXTsKICAgICAgICAgICAgICAgICAgICBzdWZmaXggPSBsZWFmLnNsaWNlKG1hdGNoUmVzdWx0LmluZGV4ICsgbWF0Y2hSZXN1bHRbMF0ubGVuZ3RoKTsKICAgICAgICAgICAgICAgICAgICBzZXJpZXNOYW1lID0gZ2V0U2VyaWVzTm9kZU5hbWUocHJlZml4LCBzdWZmaXgsIHBhcmVudCk7CiAgICAgICAgICAgICAgICAgICAgZm9yd2FyZERpY3Rbc2VyaWVzTmFtZV0gPSBmb3J3YXJkRGljdFtzZXJpZXNOYW1lXTsKICAgICAgICAgICAgICAgICAgICBpZiAoIWZvcndhcmREaWN0W3Nlcmllc05hbWVdKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGZvcndhcmREaWN0W3Nlcmllc05hbWVdID0gY3JlYXRlU2VyaWVzTm9kZShwcmVmaXgsIHN1ZmZpeCwgcGFyZW50LCAraWQsIG5hbWUsIGdyYXBoT3B0aW9ucyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGZvcndhcmREaWN0W3Nlcmllc05hbWVdLmlkcy5wdXNoKGlkKTsKICAgICAgICAgICAgICAgICAgICByZXZlcnNlRGljdFtuYW1lXSA9IHJldmVyc2VEaWN0W25hbWVdIHx8IFtdOwogICAgICAgICAgICAgICAgICAgIHJldmVyc2VEaWN0W25hbWVdLnB1c2goW3Nlcmllc05hbWUsIGlkXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAobWF0Y2hlZCA8IDEpIHsKICAgICAgICAgICAgICAgICAgICBwcmVmaXggPSBpc0dyb3VwID8gbGVhZi5zdWJzdHIoMCwgbGVhZi5sZW5ndGggLSAxKSA6IGxlYWY7CiAgICAgICAgICAgICAgICAgICAgaWQgPSAwOwogICAgICAgICAgICAgICAgICAgIHN1ZmZpeCA9IGlzR3JvdXAgPyAnKicgOiAnJzsKICAgICAgICAgICAgICAgICAgICBzZXJpZXNOYW1lID0gZ2V0U2VyaWVzTm9kZU5hbWUocHJlZml4LCBzdWZmaXgsIHBhcmVudCk7CiAgICAgICAgICAgICAgICAgICAgZm9yd2FyZERpY3Rbc2VyaWVzTmFtZV0gPSBmb3J3YXJkRGljdFtzZXJpZXNOYW1lXTsKICAgICAgICAgICAgICAgICAgICBpZiAoIWZvcndhcmREaWN0W3Nlcmllc05hbWVdKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGZvcndhcmREaWN0W3Nlcmllc05hbWVdID0gY3JlYXRlU2VyaWVzTm9kZShwcmVmaXgsIHN1ZmZpeCwgcGFyZW50LCAraWQsIG5hbWUsIGdyYXBoT3B0aW9ucyk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGZvcndhcmREaWN0W3Nlcmllc05hbWVdLmlkcy5wdXNoKGlkKTsKICAgICAgICAgICAgICAgICAgICByZXZlcnNlRGljdFtuYW1lXSA9IHJldmVyc2VEaWN0W25hbWVdIHx8IFtdOwogICAgICAgICAgICAgICAgICAgIHJldmVyc2VEaWN0W25hbWVdLnB1c2goW3Nlcmllc05hbWUsIGlkXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvKiogQHR5cGUge09iamVjdH0gIEEgZGljdGlvbmFyeSBtYXBwaW5nIHNlcmllc05hbWUgdG8gc2VyaWVzSW5mb0FycmF5LAogICAgICAgICAgICAgKiB3aGljaCBpcyBhbiBhcnJheSB0aGF0IGNvbnRhaW5zIG9iamVjdHMgd2l0aCBuYW1lLCBpZCwgcHJlZml4LCBzdWZmaXgsCiAgICAgICAgICAgICAqIGFuZCBwYXJlbnQgcHJvcGVydGllcy4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHZhciBjYW5kaWRhdGVzRGljdCA9IHt9OwogICAgICAgICAgICAvLyBGb3IgZWFjaCBvZiB0aGUgbWVtYmVyLCBwdXQgaXQgaW50byB0aGUgbWF4aW11bSBwb3NzaWJsZSBzZXJpZXMsCiAgICAgICAgICAgIC8vIGFuZCBjcmVhdGUgY2FuZGlkYXRlc0RpY3QgYWNjb3JkaW5nbHkuCiAgICAgICAgICAgIGxvZGFzaC5lYWNoKHJldmVyc2VEaWN0LCBmdW5jdGlvbiAoc2VyaWVzTmFtZUlkQXJyYXksIG5hbWUpIHsKICAgICAgICAgICAgICAgIHNlcmllc05hbWVJZEFycmF5LnNvcnQoZnVuY3Rpb24gKGEsIGIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZm9yd2FyZERpY3RbYlswXV0uaWRzLmxlbmd0aCAtIGZvcndhcmREaWN0W2FbMF1dLmlkcy5sZW5ndGg7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHZhciBzZXJpZXNOYW1lID0gc2VyaWVzTmFtZUlkQXJyYXlbMF1bMF07CiAgICAgICAgICAgICAgICB2YXIgaWQgPSBzZXJpZXNOYW1lSWRBcnJheVswXVsxXTsKICAgICAgICAgICAgICAgIGNhbmRpZGF0ZXNEaWN0W3Nlcmllc05hbWVdID0gY2FuZGlkYXRlc0RpY3Rbc2VyaWVzTmFtZV0gfHwgW107CiAgICAgICAgICAgICAgICBjb25zdCBuYW1lcGF0aCA9IG5hbWUuc3BsaXQoJy8nKTsKICAgICAgICAgICAgICAgIGNvbnN0IGxlYWYgPSBuYW1lcGF0aFtuYW1lcGF0aC5sZW5ndGggLSAxXTsKICAgICAgICAgICAgICAgIGNvbnN0IHBhcmVudCA9IG5hbWVwYXRoLnNsaWNlKDAsIG5hbWVwYXRoLmxlbmd0aCAtIDEpLmpvaW4oJy8nKTsKICAgICAgICAgICAgICAgIHZhciBzZXJpZXNOb2RlID0gY3JlYXRlU2VyaWVzTm9kZShmb3J3YXJkRGljdFtzZXJpZXNOYW1lXS5wcmVmaXgsIGZvcndhcmREaWN0W3Nlcmllc05hbWVdLnN1ZmZpeCwgcGFyZW50LCAraWQsIG5hbWUsIGdyYXBoT3B0aW9ucyk7CiAgICAgICAgICAgICAgICBjYW5kaWRhdGVzRGljdFtzZXJpZXNOYW1lXS5wdXNoKHNlcmllc05vZGUpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gSW4gZWFjaCBncm91cCBvZiBub2RlcywgZ3JvdXAgbm9kZXMgaW4gYnVuY2hlcyB0aGF0IGhhdmUgbW9ub3RvbmljYWxseQogICAgICAgICAgICAvLyBpbmNyZWFzaW5nIG51bWJlcnMgaW4gdGhlaXIgbmFtZXMuICBFYWNoIG9mIHRoZXNlIGJ1bmNoZXMgaXMgYSBzZXJpZXMuCiAgICAgICAgICAgIGxvZGFzaC5lYWNoKGNhbmRpZGF0ZXNEaWN0LCBmdW5jdGlvbiAoc2VyaWVzSW5mb0FycmF5LCBzZXJpZXNOYW1lKSB7CiAgICAgICAgICAgICAgICBpZiAoc2VyaWVzSW5mb0FycmF5Lmxlbmd0aCA8IDIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBzZXJpZXNJbmZvQXJyYXkuc29ydChmdW5jdGlvbiAoYSwgYikgewogICAgICAgICAgICAgICAgICAgIHJldHVybiArYS5jbHVzdGVySWQgLSArYi5jbHVzdGVySWQ7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIC8vIExvb3AgdGhyb3VnaCB0aGUgbm9kZXMgc29ydGVkIGJ5IGl0cyBkZXRlY3RlZCBzZXJpZXMgbnVtYmVyLCBncm91cGluZwogICAgICAgICAgICAgICAgLy8gYWxsIG5vZGVzIHdpdGggbW9ub3RvbmljYWxseS1pbmNyZWFzaW5nIHNlcmllcyBudW1iZXJzLgogICAgICAgICAgICAgICAgbGV0IHNlcmllc05vZGVzID0gW3Nlcmllc0luZm9BcnJheVswXV07CiAgICAgICAgICAgICAgICBmb3IgKGxldCBpbmRleCA9IDE7IGluZGV4IDwgc2VyaWVzSW5mb0FycmF5Lmxlbmd0aDsgaW5kZXgrKykgewogICAgICAgICAgICAgICAgICAgIGxldCBuZXh0Tm9kZSA9IHNlcmllc0luZm9BcnJheVtpbmRleF07CiAgICAgICAgICAgICAgICAgICAgaWYgKG5leHROb2RlLmNsdXN0ZXJJZCA9PT0KICAgICAgICAgICAgICAgICAgICAgICAgc2VyaWVzTm9kZXNbc2VyaWVzTm9kZXMubGVuZ3RoIC0gMV0uY2x1c3RlcklkICsgMSkgewogICAgICAgICAgICAgICAgICAgICAgICBzZXJpZXNOb2Rlcy5wdXNoKG5leHROb2RlKTsKICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGFkZFNlcmllc1RvRGljdChzZXJpZXNOb2Rlcywgc2VyaWVzRGljdCwgK2NsdXN0ZXJJZCwgbWV0YWdyYXBoLCBncmFwaE9wdGlvbnMpOwogICAgICAgICAgICAgICAgICAgIHNlcmllc05vZGVzID0gW25leHROb2RlXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGFkZFNlcmllc1RvRGljdChzZXJpZXNOb2Rlcywgc2VyaWVzRGljdCwgK2NsdXN0ZXJJZCwgbWV0YWdyYXBoLCBncmFwaE9wdGlvbnMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9KTsKICAgICAgICByZXR1cm4gc2VyaWVzRGljdDsKICAgIH0KICAgIC8qKgogICAgICogQWRkIGEgc2VyaWVzIHRvIHRoZSBwcm92aWRlZCBkaWN0aW9uYXJ5IG1hcHBpbmcgc2VyaWVzIG5hbWVzIHRvIHNlcmllcy4KICAgICAqCiAgICAgKiBAcGFyYW0gc2VyaWVzTm9kZXMgdGhlIG5vZGVzIGluIHRoZSBzZXJpZXMuIENvbnRhaW5zCiAgICAgKiAgICAgbmFtZSwgaWQsIHByZWZpeCwgc3VmZml4IGFuZCBwYXJlbnQgcHJvcGVydGllcyBvZiB0aGUgbm9kZS4KICAgICAqIEBwYXJhbSBzZXJpZXNEaWN0IHRoZSBkaWN0aW9uYXJ5IG9mIHNlcmllcwogICAgICogQHBhcmFtIGNsdXN0ZXJJZCBJRCBvZiB0aGUgdGVtcGxhdGUgb2YgdGhlIG5vZGVzIG9mIHRoZSBzZXJpZXMKICAgICAqIEBwYXJhbSBtZXRhZ3JhcGgKICAgICAqIEBwYXJhbSBncmFwaE9wdGlvbnMKICAgICAqLwogICAgZnVuY3Rpb24gYWRkU2VyaWVzVG9EaWN0KHNlcmllc05vZGVzLCBzZXJpZXNEaWN0LCBjbHVzdGVySWQsIG1ldGFncmFwaCwgZ3JhcGhPcHRpb25zKSB7CiAgICAgICAgaWYgKHNlcmllc05vZGVzLmxlbmd0aCA+IDEpIHsKICAgICAgICAgICAgbGV0IGN1clNlcmllc05hbWUgPSBnZXRTZXJpZXNOb2RlTmFtZShzZXJpZXNOb2Rlc1swXS5wcmVmaXgsIHNlcmllc05vZGVzWzBdLnN1ZmZpeCwgc2VyaWVzTm9kZXNbMF0ucGFyZW50LCBzZXJpZXNOb2Rlc1swXS5jbHVzdGVySWQsIHNlcmllc05vZGVzW3Nlcmllc05vZGVzLmxlbmd0aCAtIDFdLmNsdXN0ZXJJZCk7CiAgICAgICAgICAgIGxldCBjdXJTZXJpZXNOb2RlID0gY3JlYXRlU2VyaWVzTm9kZShzZXJpZXNOb2Rlc1swXS5wcmVmaXgsIHNlcmllc05vZGVzWzBdLnN1ZmZpeCwgc2VyaWVzTm9kZXNbMF0ucGFyZW50LCBjbHVzdGVySWQsIGN1clNlcmllc05hbWUsIGdyYXBoT3B0aW9ucyk7CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKHNlcmllc05vZGVzLCBmdW5jdGlvbiAobm9kZSkgewogICAgICAgICAgICAgICAgY3VyU2VyaWVzTm9kZS5pZHMucHVzaChub2RlLmNsdXN0ZXJJZCk7CiAgICAgICAgICAgICAgICBjdXJTZXJpZXNOb2RlLm1ldGFncmFwaC5zZXROb2RlKG5vZGUubmFtZSwgbWV0YWdyYXBoLm5vZGUobm9kZS5uYW1lKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBzZXJpZXNEaWN0W2N1clNlcmllc05hbWVdID0gY3VyU2VyaWVzTm9kZTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZHcmFwaE9wQ29tcGF0Q2FyZCA9IGNsYXNzIFRmR3JhcGhPcENvbXBhdENhcmQgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fZXhwYW5kZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9vcENvbXBhdENvbG9yID0gT3BOb2RlQ29sb3JzLkNPTVBBVElCTEU7CiAgICAgICAgICAgIHRoaXMuX29wSW5jb21wYXRDb2xvciA9IE9wTm9kZUNvbG9ycy5JTkNPTVBBVElCTEU7CiAgICAgICAgfQogICAgICAgIGdldCBfdGVtcGxhdGVJbmRleCgpIHsKICAgICAgICAgICAgdmFyIGdyYXBoSGllcmFyY2h5ID0gdGhpcy5ncmFwaEhpZXJhcmNoeTsKICAgICAgICAgICAgcmV0dXJuIGdyYXBoSGllcmFyY2h5LmdldFRlbXBsYXRlSW5kZXgoKTsKICAgICAgICB9CiAgICAgICAgX2dldE5vZGUobm9kZU5hbWUsIGdyYXBoSGllcmFyY2h5KSB7CiAgICAgICAgICAgIHJldHVybiBncmFwaEhpZXJhcmNoeS5ub2RlKG5vZGVOYW1lKTsKICAgICAgICB9CiAgICAgICAgX2dldFJlbmRlckluZm8obm9kZU5hbWUsIHJlbmRlckhpZXJhcmNoeSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5yZW5kZXJIaWVyYXJjaHkuZ2V0T3JDcmVhdGVSZW5kZXJOb2RlQnlOYW1lKG5vZGVOYW1lKTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUV4cGFuZGVkKCkgewogICAgICAgICAgICB0aGlzLl9leHBhbmRlZCA9ICF0aGlzLl9leHBhbmRlZDsKICAgICAgICB9CiAgICAgICAgX2dldFRvZ2dsZUljb24oZXhwYW5kZWQpIHsKICAgICAgICAgICAgcmV0dXJuIGV4cGFuZGVkID8gJ2V4cGFuZC1sZXNzJyA6ICdleHBhbmQtbW9yZSc7CiAgICAgICAgfQogICAgICAgIF9yZXNpemVMaXN0KHNlbGVjdG9yKSB7CiAgICAgICAgICAgIHZhciBsaXN0ID0gZG9jdW1lbnQucXVlcnlTZWxlY3RvcihzZWxlY3Rvcik7CiAgICAgICAgICAgIGlmIChsaXN0KSB7CiAgICAgICAgICAgICAgICBsaXN0LmZpcmUoJ2lyb24tcmVzaXplJyk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgZ2V0IF9pbmNvbXBhdGlibGVPcE5vZGVzKCkgewogICAgICAgICAgICB2YXIgZ3JhcGhIaWVyYXJjaHkgPSB0aGlzLmdyYXBoSGllcmFyY2h5OwogICAgICAgICAgICB2YXIgaGllcmFyY2h5UGFyYW1zID0gdGhpcy5oaWVyYXJjaHlQYXJhbXM7CiAgICAgICAgICAgIGlmIChncmFwaEhpZXJhcmNoeSAmJiBncmFwaEhpZXJhcmNoeS5yb290KSB7CiAgICAgICAgICAgICAgICB0aGlzLmFzeW5jKHRoaXMuX3Jlc2l6ZUxpc3QuYmluZCh0aGlzLCAnI2luY29tcGF0aWJsZU9wc0xpc3QnKSk7CiAgICAgICAgICAgICAgICByZXR1cm4gZ2V0SW5jb21wYXRpYmxlT3BzKGdyYXBoSGllcmFyY2h5LCBoaWVyYXJjaHlQYXJhbXMpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGdldCBfb3BDb21wYXRTY29yZSgpIHsKICAgICAgICAgICAgdmFyIGdyYXBoSGllcmFyY2h5ID0gdGhpcy5ncmFwaEhpZXJhcmNoeTsKICAgICAgICAgICAgaWYgKGdyYXBoSGllcmFyY2h5ICYmIGdyYXBoSGllcmFyY2h5LnJvb3QpIHsKICAgICAgICAgICAgICAgIHZhciByb290ID0gZ3JhcGhIaWVyYXJjaHkucm9vdDsKICAgICAgICAgICAgICAgIHZhciBudW1Db21wYXQgPSByb290LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uY29tcGF0aWJsZTsKICAgICAgICAgICAgICAgIHZhciBudW1JbmNvbXBhdCA9IHJvb3QuY29tcGF0aWJpbGl0eUhpc3RvZ3JhbS5pbmNvbXBhdGlibGU7CiAgICAgICAgICAgICAgICBpZiAobnVtQ29tcGF0ID09IDAgJiYgbnVtSW5jb21wYXQgPT0gMCkKICAgICAgICAgICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICAgICAgICAgIHZhciBudW1Ub3RhbCA9IG51bUNvbXBhdCArIG51bUluY29tcGF0OwogICAgICAgICAgICAgICAgLy8gUm91bmQgdGhlIHJhdGlvIHRvd2FyZHMgbmVnYXRpdmUgaW5maW5pdHkuCiAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5mbG9vcigoMTAwICogbnVtQ29tcGF0KSAvIG51bVRvdGFsKSAvIDEwMDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9vcENvbXBhdFNjb3JlTGFiZWwoKSB7CiAgICAgICAgICAgIHZhciBvcENvbXBhdFNjb3JlID0gdGhpcy5fb3BDb21wYXRTY29yZTsKICAgICAgICAgICAgcmV0dXJuIGZvcm1hdCgnLjAlJykob3BDb21wYXRTY29yZSk7CiAgICAgICAgfQogICAgICAgIGdldCBfdG90YWxJbmNvbXBhdE9wcygpIHsKICAgICAgICAgICAgdmFyIGdyYXBoSGllcmFyY2h5ID0gdGhpcy5ncmFwaEhpZXJhcmNoeTsKICAgICAgICAgICAgaWYgKGdyYXBoSGllcmFyY2h5ICYmIGdyYXBoSGllcmFyY2h5LnJvb3QpIHsKICAgICAgICAgICAgICAgIHJldHVybiBncmFwaEhpZXJhcmNoeS5yb290LmNvbXBhdGliaWxpdHlIaXN0b2dyYW0uaW5jb21wYXRpYmxlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgIH07CiAgICBUZkdyYXBoT3BDb21wYXRDYXJkLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBtYXgtaGVpZ2h0OiA1MDBweDsKICAgICAgfQoKICAgICAgLmluY29tcGF0aWJsZS1vcHMtbGlzdCB7CiAgICAgICAgaGVpZ2h0OiAzNTBweDsKICAgICAgICBtYXgtaGVpZ2h0OiA0MDBweDsKICAgICAgICBvdmVyZmxvdy15OiBzY3JvbGw7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogICAgICB9CgogICAgICBpcm9uLWxpc3QgewogICAgICAgIGZsZXg6IDEgMSBhdXRvOwogICAgICB9CgogICAgICBwYXBlci1pdGVtIHsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICAgIGJhY2tncm91bmQ6ICNlOWU5ZTk7CiAgICAgIH0KCiAgICAgIHBhcGVyLWl0ZW0tYm9keVt0d28tbGluZV0gewogICAgICAgIG1pbi1oZWlnaHQ6IDA7CiAgICAgICAgcGFkZGluZzogOHB4IDEycHggNHB4OwogICAgICB9CgogICAgICAuZXhwYW5kZWRJbmZvIHsKICAgICAgICBwYWRkaW5nOiA4cHggMTJweDsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIGZvbnQtc2l6ZTogMTJwdDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgLm5vZGUtbmFtZSB7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vcm1hbDsKICAgICAgICB3b3JkLXdyYXA6IGJyZWFrLXdvcmQ7CiAgICAgICAgZm9udC1zaXplOiAxNHB0OwogICAgICAgIGZvbnQtd2VpZ2h0OiA1MDA7CiAgICAgIH0KCiAgICAgIC5zdWJ0aXRsZSB7CiAgICAgICAgZm9udC1zaXplOiAxMnB0OwogICAgICAgIGNvbG9yOiAjNWU1ZTVlOwogICAgICB9CgogICAgICAudG9nZ2xlLWJ1dHRvbiB7CiAgICAgICAgZmxvYXQ6IHJpZ2h0OwogICAgICAgIG1heC1oZWlnaHQ6IDIwcHg7CiAgICAgICAgbWF4LXdpZHRoOiAyMHB4OwogICAgICAgIHBhZGRpbmc6IDA7CiAgICAgIH0KCiAgICAgIC5ub24tY29udHJvbC1saXN0LWl0ZW0gewogICAgICAgIHBhZGRpbmctbGVmdDogMTBweDsKICAgICAgfQoKICAgICAgZGl2Lm9wLWNvbXBhdC1kaXNwbGF5IHsKICAgICAgICBtYXJnaW4tdG9wOiAxMHB4OwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgfQoKICAgICAgc3ZnLm9wLWNvbXBhdCB7CiAgICAgICAgd2lkdGg6IDI1MHB4OwogICAgICAgIGhlaWdodDogMjVweDsKICAgICAgICBmbG9hdDogbGVmdDsKICAgICAgfQoKICAgICAgZGl2Lm9wLWNvbXBhdC12YWx1ZSB7CiAgICAgICAgZmxvYXQ6IHJpZ2h0OwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgY29sb3I6IGJsYWNrOwogICAgICAgIG1hcmdpbi1sZWZ0OiAxMHB4OwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxwYXBlci1pdGVtPgogICAgICA8cGFwZXItaXRlbS1ib2R5IHR3by1saW5lPgogICAgICAgIDxkaXY+CiAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgICAgaWNvbj0ie3tfZ2V0VG9nZ2xlSWNvbihfZXhwYW5kZWQpfX0iCiAgICAgICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlRXhwYW5kZWQiCiAgICAgICAgICAgIGNsYXNzPSJ0b2dnbGUtYnV0dG9uIgogICAgICAgICAgPgogICAgICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgIDxkaXYgY2xhc3M9Im5vZGUtbmFtZSIgaWQ9Im5vZGV0aXRsZSI+W1tub2RlVGl0bGVdXTwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXYgc2Vjb25kYXJ5PgogICAgICAgICAgPGRpdiBjbGFzcz0ic3VidGl0bGUiPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJvcC1jb21wYXQtZGlzcGxheSI+CiAgICAgICAgICAgICAgPHN2ZwogICAgICAgICAgICAgICAgY2xhc3M9Im9wLWNvbXBhdCIKICAgICAgICAgICAgICAgIHByZXNlcnZlQXNwZWN0UmF0aW89InhNaW5ZTWlkIG1lZXQiCiAgICAgICAgICAgICAgICB2aWV3Qm94PSIwIDAgMjUwIDI1IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxkZWZzPgogICAgICAgICAgICAgICAgICA8bGluZWFyR3JhZGllbnQgaWQ9Im9wLWNvbXBhdC1maWxsIj4KICAgICAgICAgICAgICAgICAgICA8c3RvcCBvZmZzZXQ9IjAiIHN0b3AtY29sb3IkPSJbW19vcENvbXBhdENvbG9yXV0iPjwvc3RvcD4KICAgICAgICAgICAgICAgICAgICA8c3RvcAogICAgICAgICAgICAgICAgICAgICAgb2Zmc2V0JD0iW1tfb3BDb21wYXRTY29yZV1dIgogICAgICAgICAgICAgICAgICAgICAgc3RvcC1jb2xvciQ9IltbX29wQ29tcGF0Q29sb3JdXSIKICAgICAgICAgICAgICAgICAgICA+PC9zdG9wPgogICAgICAgICAgICAgICAgICAgIDxzdG9wCiAgICAgICAgICAgICAgICAgICAgICBvZmZzZXQkPSJbW19vcENvbXBhdFNjb3JlXV0iCiAgICAgICAgICAgICAgICAgICAgICBzdG9wLWNvbG9yJD0iW1tfb3BJbmNvbXBhdENvbG9yXV0iCiAgICAgICAgICAgICAgICAgICAgPjwvc3RvcD4KICAgICAgICAgICAgICAgICAgICA8c3RvcCBvZmZzZXQ9IjEiIHN0b3AtY29sb3IkPSJbW19vcEluY29tcGF0Q29sb3IgXV0iPjwvc3RvcD4KICAgICAgICAgICAgICAgICAgPC9saW5lYXJHcmFkaWVudD4KICAgICAgICAgICAgICAgIDwvZGVmcz4KICAgICAgICAgICAgICAgIDxyZWN0CiAgICAgICAgICAgICAgICAgIGhlaWdodD0iMjUiCiAgICAgICAgICAgICAgICAgIHdpZHRoPSIyNTAiCiAgICAgICAgICAgICAgICAgIHJ4PSI1IgogICAgICAgICAgICAgICAgICByeT0iNSIKICAgICAgICAgICAgICAgICAgc3R5bGU9ImZpbGw6IHVybCgnI29wLWNvbXBhdC1maWxsJyk7IgogICAgICAgICAgICAgICAgPjwvcmVjdD4KICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJvcC1jb21wYXQtdmFsdWUiPltbX29wQ29tcGF0U2NvcmVMYWJlbF1dPC9kaXY+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvcGFwZXItaXRlbS1ib2R5PgogICAgPC9wYXBlci1pdGVtPgoKICAgIDxpcm9uLWNvbGxhcHNlIG9wZW5lZD0ie3tfZXhwYW5kZWR9fSI+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfZXhwYW5kZWR9fSIgcmVzdGFtcD0idHJ1ZSI+CiAgICAgICAgPGRpdiBjbGFzcz0iZXhwYW5kZWRJbmZvIj4KICAgICAgICAgIEluY29tcGF0aWJsZSBPcGVyYXRpb25zOiAoPHNwYW4+W1tfdG90YWxJbmNvbXBhdE9wc11dPC9zcGFuPikKICAgICAgICAgIDxpcm9uLWxpc3QKICAgICAgICAgICAgY2xhc3M9ImluY29tcGF0aWJsZS1vcHMtbGlzdCIKICAgICAgICAgICAgaWQ9ImluY29tcGF0aWJsZU9wc0xpc3QiCiAgICAgICAgICAgIGl0ZW1zPSJbW19pbmNvbXBhdGlibGVPcE5vZGVzXV0iCiAgICAgICAgICA+CiAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICA8dGYtZ3JhcGgtb3AtY29tcGF0LWxpc3QtaXRlbQogICAgICAgICAgICAgICAgY2xhc3M9Im5vbi1jb250cm9sLWxpc3QtaXRlbSIKICAgICAgICAgICAgICAgIGl0ZW0tbm9kZT0iW1tpdGVtXV0iCiAgICAgICAgICAgICAgICBpdGVtLXJlbmRlci1pbmZvPSJbW19nZXRSZW5kZXJJbmZvKGl0ZW0ubmFtZSwgcmVuZGVySGllcmFyY2h5KV1dIgogICAgICAgICAgICAgICAgbmFtZT0iW1tpdGVtLm5hbWVdXSIKICAgICAgICAgICAgICAgIHRlbXBsYXRlLWluZGV4PSJbW190ZW1wbGF0ZUluZGV4XV0iCiAgICAgICAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICAgICAgICBpdGVtLXR5cGU9ImluY29tcGF0aWJsZS1vcHMiCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgIDwvdGYtZ3JhcGgtb3AtY29tcGF0LWxpc3QtaXRlbT4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDwvaXJvbi1saXN0PgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgPC9pcm9uLWNvbGxhcHNlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAiZ3JhcGhIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoT3BDb21wYXRDYXJkLnByb3RvdHlwZSwgImhpZXJhcmNoeVBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAicmVuZGVySGllcmFyY2h5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0Q2FyZC5wcm90b3R5cGUsICJub2RlVGl0bGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAiX2V4cGFuZGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0Q2FyZC5wcm90b3R5cGUsICJfb3BDb21wYXRDb2xvciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAiX29wSW5jb21wYXRDb2xvciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnZ3JhcGhIaWVyYXJjaHknKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAiX3RlbXBsYXRlSW5kZXgiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdncmFwaEhpZXJhcmNoeScsICdoaWVyYXJjaHlQYXJhbXMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQucHJvdG90eXBlLCAiX2luY29tcGF0aWJsZU9wTm9kZXMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdncmFwaEhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0Q2FyZC5wcm90b3R5cGUsICJfb3BDb21wYXRTY29yZSIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19vcENvbXBhdFNjb3JlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoT3BDb21wYXRDYXJkLnByb3RvdHlwZSwgIl9vcENvbXBhdFNjb3JlTGFiZWwiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdncmFwaEhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaE9wQ29tcGF0Q2FyZC5wcm90b3R5cGUsICJfdG90YWxJbmNvbXBhdE9wcyIsIG51bGwpOwogICAgVGZHcmFwaE9wQ29tcGF0Q2FyZCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWdyYXBoLW9wLWNvbXBhdC1jYXJkJykKICAgIF0sIFRmR3JhcGhPcENvbXBhdENhcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmTm9kZUxpc3RJdGVtID0gY2xhc3MgVGZOb2RlTGlzdEl0ZW0gZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBfaXRlbVR5cGVDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAodGhpcy5pdGVtVHlwZSAhPT0gJ3N1Ym5vZGUnKSB7CiAgICAgICAgICAgICAgICB0aGlzLiRbJ2xpc3QtaXRlbSddLmNsYXNzTGlzdC5hZGQoJ2NsaWNrYWJsZScpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy4kWydsaXN0LWl0ZW0nXS5jbGFzc0xpc3QucmVtb3ZlKCdjbGlja2FibGUnKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfbm9kZUxpc3RlbmVyKGV2ZW50KSB7CiAgICAgICAgICAgIC8vIGZpcmUgbm9kZS5jbGljay9tb3VzZW92ZXIvbW91c2VvdXQKICAgICAgICAgICAgdGhpcy5maXJlKCdub2RlLWxpc3QtaXRlbS0nICsgZXZlbnQudHlwZSwgewogICAgICAgICAgICAgICAgY2FyZE5vZGU6IHRoaXMuY2FyZE5vZGUubmFtZSwKICAgICAgICAgICAgICAgIG5vZGVOYW1lOiB0aGlzLm5hbWUsCiAgICAgICAgICAgICAgICB0eXBlOiB0aGlzLml0ZW1UeXBlLAogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2ZhZGVkQ2xhc3MoaXRlbVJlbmRlckluZm8pIHsKICAgICAgICAgICAgcmV0dXJuIGl0ZW1SZW5kZXJJbmZvICYmIGl0ZW1SZW5kZXJJbmZvLmlzRmFkZWRPdXQgPyAnZmFkZWQnIDogJyc7CiAgICAgICAgfQogICAgfTsKICAgIFRmTm9kZUxpc3RJdGVtLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGU+CiAgICAgICNsaXN0LWl0ZW0gewogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGNvbG9yOiAjNTY1NjU2OwogICAgICAgIGZvbnQtc2l6ZTogMTFwdDsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgIH0KCiAgICAgICNsaXN0LWl0ZW06aG92ZXIgewogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWdvb2dsZS15ZWxsb3ctMTAwKTsKICAgICAgfQoKICAgICAgLmNsaWNrYWJsZSB7CiAgICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICB9CgogICAgICAjbGlzdC1pdGVtIHNwYW4gewogICAgICAgIG1hcmdpbi1sZWZ0OiA0MHB4OwogICAgICB9CgogICAgICAjbGlzdC1pdGVtLmV4Y2x1ZGVkIHNwYW4gewogICAgICAgIGNvbG9yOiAjOTk5OwogICAgICB9CgogICAgICAjbGlzdC1pdGVtIHNwYW4uZWRnZS1sYWJlbCB7CiAgICAgICAgZmxvYXQ6IHJpZ2h0OwogICAgICAgIGZvbnQtc2l6ZTogMTBweDsKICAgICAgICBtYXJnaW4tbGVmdDogM3B4OwogICAgICAgIG1hcmdpbi1yaWdodDogNXB4OwogICAgICB9CgogICAgICAubm9kZS1pY29uIHsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAxcHg7CiAgICAgICAgbGVmdDogMnB4OwogICAgICB9CgogICAgICAuZmFkZWQgc3BhbiB7CiAgICAgICAgY29sb3I6IHZhcigtLXRiLWdyYXBoLWZhZGVkKTsKICAgICAgfQogICAgPC9zdHlsZT4KICAgIDxkaXYKICAgICAgaWQ9Imxpc3QtaXRlbSIKICAgICAgb24tbW91c2VvdmVyPSJfbm9kZUxpc3RlbmVyIgogICAgICBvbi1tb3VzZW91dD0iX25vZGVMaXN0ZW5lciIKICAgICAgb24tY2xpY2s9Il9ub2RlTGlzdGVuZXIiCiAgICA+CiAgICAgIDxkaXYgY2xhc3MkPSJ7e19mYWRlZENsYXNzKGl0ZW1SZW5kZXJJbmZvKX19Ij4KICAgICAgICA8dGYtbm9kZS1pY29uCiAgICAgICAgICBjbGFzcz0ibm9kZS1pY29uIgogICAgICAgICAgaGVpZ2h0PSIxMiIKICAgICAgICAgIGNvbG9yLWJ5PSJbW2NvbG9yQnldXSIKICAgICAgICAgIGNvbG9yLWJ5LXBhcmFtcz0iW1tjb2xvckJ5UGFyYW1zXV0iCiAgICAgICAgICBub2RlPSJbW2l0ZW1Ob2RlXV0iCiAgICAgICAgICByZW5kZXItaW5mbz0iW1tpdGVtUmVuZGVySW5mb11dIgogICAgICAgICAgdGVtcGxhdGUtaW5kZXg9IltbdGVtcGxhdGVJbmRleF1dIgogICAgICAgID48L3RmLW5vZGUtaWNvbj4KICAgICAgICA8c3BhbiB0aXRsZSQ9IltbbmFtZV1dIj5bW25hbWVdXTwvc3Bhbj4KICAgICAgICA8c3BhbiBjbGFzcz0iZWRnZS1sYWJlbCI+W1tlZGdlTGFiZWxdXTwvc3Bhbj4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVMaXN0SXRlbS5wcm90b3R5cGUsICJjYXJkTm9kZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmTm9kZUxpc3RJdGVtLnByb3RvdHlwZSwgIml0ZW1Ob2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZOb2RlTGlzdEl0ZW0ucHJvdG90eXBlLCAiZWRnZUxhYmVsIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZOb2RlTGlzdEl0ZW0ucHJvdG90eXBlLCAiaXRlbVJlbmRlckluZm8iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVMaXN0SXRlbS5wcm90b3R5cGUsICJuYW1lIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBvYnNlcnZlcjogJ19pdGVtVHlwZUNoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZOb2RlTGlzdEl0ZW0ucHJvdG90eXBlLCAiaXRlbVR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVMaXN0SXRlbS5wcm90b3R5cGUsICJjb2xvckJ5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZOb2RlTGlzdEl0ZW0ucHJvdG90eXBlLCAiY29sb3JCeVBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmTm9kZUxpc3RJdGVtLnByb3RvdHlwZSwgInRlbXBsYXRlSW5kZXgiLCB2b2lkIDApOwogICAgVGZOb2RlTGlzdEl0ZW0gPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ub2RlLWxpc3QtaXRlbScpCiAgICBdLCBUZk5vZGVMaXN0SXRlbSk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZOb2RlSW5mbyA9IGNsYXNzIFRmTm9kZUluZm8gZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fZXhwYW5kZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sUHJlZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sU3VjYyA9IGZhbHNlOwogICAgICAgIH0KICAgICAgICBleHBhbmROb2RlKCkgewogICAgICAgICAgICB0aGlzLmZpcmUoJ19ub2RlLmV4cGFuZCcsIHRoaXMubm9kZSk7CiAgICAgICAgfQogICAgICAgIGdldCBfdGVtcGxhdGVJbmRleCgpIHsKICAgICAgICAgICAgdmFyIGdyYXBoSGllcmFyY2h5ID0gdGhpcy5ncmFwaEhpZXJhcmNoeTsKICAgICAgICAgICAgcmV0dXJuIGdyYXBoSGllcmFyY2h5LmdldFRlbXBsYXRlSW5kZXgoKTsKICAgICAgICB9CiAgICAgICAgX2dldE5vZGUoZ3JhcGhOb2RlTmFtZSwgZ3JhcGhIaWVyYXJjaHkpIHsKICAgICAgICAgICAgcmV0dXJuIGdyYXBoSGllcmFyY2h5Lm5vZGUoZ3JhcGhOb2RlTmFtZSk7CiAgICAgICAgfQogICAgICAgIF9nZXROb2RlU3RhdHMoZ3JhcGhOb2RlTmFtZSwgZ3JhcGhIaWVyYXJjaHkpIHsKICAgICAgICAgICAgdmFyIG5vZGUgPSB0aGlzLl9nZXROb2RlKGdyYXBoTm9kZU5hbWUsIGdyYXBoSGllcmFyY2h5KTsKICAgICAgICAgICAgaWYgKG5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBub2RlLnN0YXRzOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICBfZ2V0VG90YWxNaWNyb3Moc3RhdHMpIHsKICAgICAgICAgICAgcmV0dXJuIHN0YXRzID8gc3RhdHMuZ2V0VG90YWxNaWNyb3MoKSA6IDA7CiAgICAgICAgfQogICAgICAgIGdldCBfaGFzRGlzcGxheWFibGVOb2RlU3RhdHMoKSB7CiAgICAgICAgICAgIHZhciBzdGF0cyA9IHRoaXMuX25vZGVTdGF0czsKICAgICAgICAgICAgcmV0dXJuIGhhc0Rpc3BsYXlhYmxlTm9kZVN0YXRzKHN0YXRzKTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9ub2RlU3RhdHNGb3JtYXR0ZWRCeXRlcygpIHsKICAgICAgICAgICAgdmFyIHN0YXRzID0gdGhpcy5fbm9kZVN0YXRzOwogICAgICAgICAgICBpZiAoIXN0YXRzIHx8ICFzdGF0cy50b3RhbEJ5dGVzKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGNvbnZlcnRVbml0c1RvSHVtYW5SZWFkYWJsZShzdGF0cy50b3RhbEJ5dGVzLCBNRU1PUllfVU5JVFMpOwogICAgICAgIH0KICAgICAgICBnZXQgX25vZGVTdGF0c0Zvcm1hdHRlZENvbXB1dGVUaW1lKCkgewogICAgICAgICAgICB2YXIgc3RhdHMgPSB0aGlzLl9ub2RlU3RhdHM7CiAgICAgICAgICAgIGlmICghc3RhdHMgfHwgIXN0YXRzLmdldFRvdGFsTWljcm9zKCkpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gY29udmVydFVuaXRzVG9IdW1hblJlYWRhYmxlKHN0YXRzLmdldFRvdGFsTWljcm9zKCksIFRJTUVfVU5JVFMpOwogICAgICAgIH0KICAgICAgICBnZXQgX25vZGVTdGF0c0Zvcm1hdHRlZE91dHB1dFNpemVzKCkgewogICAgICAgICAgICB2YXIgc3RhdHMgPSB0aGlzLl9ub2RlU3RhdHM7CiAgICAgICAgICAgIGlmICghc3RhdHMgfHwgIXN0YXRzLm91dHB1dFNpemUgfHwgIXN0YXRzLm91dHB1dFNpemUubGVuZ3RoKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGxvZGFzaC5tYXAoc3RhdHMub3V0cHV0U2l6ZSwgZnVuY3Rpb24gKHNoYXBlKSB7CiAgICAgICAgICAgICAgICBpZiAoc2hhcGUubGVuZ3RoID09PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICdzY2FsYXInOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuICdbJyArIHNoYXBlLmpvaW4oJywgJykgKyAnXSc7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfZ2V0UmVuZGVySW5mbyhncmFwaE5vZGVOYW1lLCByZW5kZXJIaWVyYXJjaHkpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVuZGVySGllcmFyY2h5LmdldE9yQ3JlYXRlUmVuZGVyTm9kZUJ5TmFtZShncmFwaE5vZGVOYW1lKTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9hdHRyaWJ1dGVzKCkgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXMuX25vZGU7CiAgICAgICAgICAgIHRoaXMuYXN5bmModGhpcy5fcmVzaXplTGlzdC5iaW5kKHRoaXMsICcjYXR0cmlidXRlc0xpc3QnKSk7CiAgICAgICAgICAgIGlmICghbm9kZSB8fCAhbm9kZS5hdHRyKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGF0dHJzID0gW107CiAgICAgICAgICAgIGxvZGFzaC5lYWNoKG5vZGUuYXR0ciwgZnVuY3Rpb24gKGVudHJ5KSB7CiAgICAgICAgICAgICAgICAvLyBVbnBhY2sgdGhlICJ0b28gbGFyZ2UiIGF0dHJpYnV0ZXMgaW50byBzZXBhcmF0ZSBhdHRyaWJ1dGVzCiAgICAgICAgICAgICAgICAvLyBpbiB0aGUgaW5mbyBjYXJkLCB3aXRoIHZhbHVlcyAidG9vIGxhcmdlIHRvIHNob3ciLgogICAgICAgICAgICAgICAgaWYgKGVudHJ5LmtleSA9PT0gTEFSR0VfQVRUUlNfS0VZKSB7CiAgICAgICAgICAgICAgICAgICAgYXR0cnMgPSBhdHRycy5jb25jYXQoZW50cnkudmFsdWUubGlzdC5zLm1hcChmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB7IGtleToga2V5LCB2YWx1ZTogJ1RvbyBsYXJnZSB0byBzaG93Li4uJyB9OwogICAgICAgICAgICAgICAgICAgIH0pKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIGF0dHJzLnB1c2goewogICAgICAgICAgICAgICAgICAgICAgICBrZXk6IGVudHJ5LmtleSwKICAgICAgICAgICAgICAgICAgICAgICAgdmFsdWU6IEpTT04uc3RyaW5naWZ5KGVudHJ5LnZhbHVlKSwKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBhdHRyczsKICAgICAgICB9CiAgICAgICAgZ2V0IF9kZXZpY2UoKSB7CiAgICAgICAgICAgIHZhciBub2RlID0gdGhpcy5fbm9kZTsKICAgICAgICAgICAgcmV0dXJuIG5vZGUgPyBub2RlLmRldmljZSA6IG51bGw7CiAgICAgICAgfQogICAgICAgIGdldCBfc3VjY2Vzc29ycygpIHsKICAgICAgICAgICAgdmFyIG5vZGUgPSB0aGlzLl9ub2RlOwogICAgICAgICAgICB2YXIgaGllcmFyY2h5ID0gdGhpcy5ncmFwaEhpZXJhcmNoeTsKICAgICAgICAgICAgdGhpcy5fcmVmcmVzaE5vZGVJdGVtTGlzdCgnaW5wdXRzTGlzdCcpOwogICAgICAgICAgICBpZiAoIW5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiB7IHJlZ3VsYXI6IFtdLCBjb250cm9sOiBbXSB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb252ZXJ0RWRnZUxpc3RUb0VkZ2VJbmZvTGlzdChoaWVyYXJjaHkuZ2V0U3VjY2Vzc29ycyhub2RlLm5hbWUpLCBmYWxzZSwgbm9kZS5pc0dyb3VwTm9kZSk7CiAgICAgICAgfQogICAgICAgIGdldCBfcHJlZGVjZXNzb3JzKCkgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXMuX25vZGU7CiAgICAgICAgICAgIHZhciBoaWVyYXJjaHkgPSB0aGlzLmdyYXBoSGllcmFyY2h5OwogICAgICAgICAgICB0aGlzLl9yZWZyZXNoTm9kZUl0ZW1MaXN0KCdvdXRwdXRzTGlzdCcpOwogICAgICAgICAgICBpZiAoIW5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiB7IHJlZ3VsYXI6IFtdLCBjb250cm9sOiBbXSB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9jb252ZXJ0RWRnZUxpc3RUb0VkZ2VJbmZvTGlzdChoaWVyYXJjaHkuZ2V0UHJlZGVjZXNzb3JzKG5vZGUubmFtZSksIHRydWUsIG5vZGUuaXNHcm91cE5vZGUpOwogICAgICAgIH0KICAgICAgICAvLyBPbmx5IHJlbGV2YW50IGlmIHRoaXMgaXMgYSBsaWJyYXJ5IGZ1bmN0aW9uLiBBIGxpc3Qgb2Ygbm9kZXMgdGhhdAogICAgICAgIC8vIHJlcHJlc2VudCB3aGVyZSB0aGUgZnVuY3Rpb24gaXMgdXNlZC4KICAgICAgICBnZXQgX2Z1bmN0aW9uVXNhZ2VzKCkgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXMuX25vZGU7CiAgICAgICAgICAgIHZhciBoaWVyYXJjaHkgPSB0aGlzLmdyYXBoSGllcmFyY2h5OwogICAgICAgICAgICB0aGlzLl9yZWZyZXNoTm9kZUl0ZW1MaXN0KCdmdW5jdGlvblVzYWdlc0xpc3QnKTsKICAgICAgICAgICAgaWYgKCFub2RlIHx8IG5vZGUudHlwZSAhPT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICAgICAgLy8gRnVuY3Rpb25zIG11c3QgYmUgcmVwcmVzZW50ZWQgYnkgbWV0YW5vZGVzLgogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGxpYnJhcnlGdW5jdGlvbkRhdGEgPSBoaWVyYXJjaHkubGlicmFyeUZ1bmN0aW9uc1tub2RlLmFzc29jaWF0ZWRGdW5jdGlvbl07CiAgICAgICAgICAgIGlmICghbGlicmFyeUZ1bmN0aW9uRGF0YSkgewogICAgICAgICAgICAgICAgLy8gVGhpcyBpcyBubyBmdW5jdGlvbi4KICAgICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZXR1cm4gd2hlcmUgdGhlIGZ1bmN0aW9uIGlzIHVzZWQuCiAgICAgICAgICAgIHJldHVybiBsaWJyYXJ5RnVuY3Rpb25EYXRhLnVzYWdlczsKICAgICAgICB9CiAgICAgICAgLy8gVGhlIGlyb24gbGlzdHMgdGhhdCBlbnVtZXJhdGUgb3BzIG11c3QgYmUgYXN5bmNocm9ub3VzbHkgdXBkYXRlZCB3aGVuCiAgICAgICAgLy8gdGhlIGRhdGEgdGhleSByZW5kZXIgY2hhbmdlcy4gVGhpcyBmdW5jdGlvbiB0cmlnZ2VycyB0aGF0IHVwZGF0ZS4KICAgICAgICBfcmVmcmVzaE5vZGVJdGVtTGlzdChub2RlTGlzdElkKSB7CiAgICAgICAgICAgIHRoaXMuYXN5bmModGhpcy5fcmVzaXplTGlzdC5iaW5kKHRoaXMsIGAjJHtub2RlTGlzdElkfWApKTsKICAgICAgICB9CiAgICAgICAgX2NvbnZlcnRFZGdlTGlzdFRvRWRnZUluZm9MaXN0KGxpc3QsIGlzUHJlZGVjZXNzb3IsIGlzR3JvdXBOb2RlKSB7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBVbnBhY2tzIHRoZSBtZXRhZWRnZSBpbnRvIGEgbGlzdCBvZiBiYXNlIGVkZ2UgaW5mb3JtYXRpb24KICAgICAgICAgICAgICogdGhhdCBjYW4gYmUgcmVuZGVyZWQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB2YXIgdW5wYWNrTWV0YWVkZ2UgPSAobWV0YWVkZ2UpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBsb2Rhc2gubWFwKG1ldGFlZGdlLmJhc2VFZGdlTGlzdCwgKGJhc2VFZGdlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgdmFyIG5hbWUgPSBpc1ByZWRlY2Vzc29yID8gYmFzZUVkZ2UudiA6IGJhc2VFZGdlLnc7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICAgICAgICAgICAgICAgICAgbm9kZTogdGhpcy5fZ2V0Tm9kZShuYW1lLCB0aGlzLmdyYXBoSGllcmFyY2h5KSwKICAgICAgICAgICAgICAgICAgICAgICAgZWRnZUxhYmVsOiBnZXRMYWJlbEZvckJhc2VFZGdlKGJhc2VFZGdlLCB0aGlzLnJlbmRlckhpZXJhcmNoeSksCiAgICAgICAgICAgICAgICAgICAgICAgIHJlbmRlckluZm86IHRoaXMuX2dldFJlbmRlckluZm8obmFtZSwgdGhpcy5yZW5kZXJIaWVyYXJjaHkpLAogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIENvbnZlcnRzIGEgbGlzdCBvZiBtZXRhZWRnZXMgdG8gYSBsaXN0IG9mIGVkZ2UgaW5mb3JtYXRpb24KICAgICAgICAgICAgICogdGhhdCBjYW4gYmUgcmVuZGVyZWQuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB2YXIgdG9FZGdlSW5mb0xpc3QgPSBmdW5jdGlvbiAoZWRnZXMpIHsKICAgICAgICAgICAgICAgIHZhciBlZGdlSW5mb0xpc3QgPSBbXTsKICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKGVkZ2VzLCAobWV0YWVkZ2UpID0+IHsKICAgICAgICAgICAgICAgICAgICB2YXIgbmFtZSA9IGlzUHJlZGVjZXNzb3IgPyBtZXRhZWRnZS52IDogbWV0YWVkZ2UudzsKICAgICAgICAgICAgICAgICAgICAvLyBFbnVtZXJhdGUgYWxsIHRoZSBiYXNlIGVkZ2VzIGlmIHRoZSBub2RlIGlzIGFuIE9wTm9kZSwgb3IgdGhlCiAgICAgICAgICAgICAgICAgICAgLy8gbWV0YWVkZ2UgaGFzIG9ubHkgMSBlZGdlIGluIGl0LgogICAgICAgICAgICAgICAgICAgIGlmICghaXNHcm91cE5vZGUgfHwgbWV0YWVkZ2UuYmFzZUVkZ2VMaXN0Lmxlbmd0aCA9PSAxKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGVkZ2VJbmZvTGlzdCA9IGVkZ2VJbmZvTGlzdC5jb25jYXQodW5wYWNrTWV0YWVkZ2UobWV0YWVkZ2UpKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGVkZ2VJbmZvTGlzdC5wdXNoKHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIG5hbWU6IG5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBub2RlOiB0aGlzLl9nZXROb2RlKG5hbWUsIHRoaXMuZ3JhcGhIaWVyYXJjaHkpLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgZWRnZUxhYmVsOiBnZXRMYWJlbEZvckVkZ2UobWV0YWVkZ2UsIHRoaXMucmVuZGVySGllcmFyY2h5KSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlbmRlckluZm86IHRoaXMuX2dldFJlbmRlckluZm8obmFtZSwgdGhpcy5yZW5kZXJIaWVyYXJjaHkpLAogICAgICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIHJldHVybiBlZGdlSW5mb0xpc3Q7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHJlZ3VsYXI6IHRvRWRnZUluZm9MaXN0KGxpc3QucmVndWxhciksCiAgICAgICAgICAgICAgICBjb250cm9sOiB0b0VkZ2VJbmZvTGlzdChsaXN0LmNvbnRyb2wpLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBnZXQgX3N1Ym5vZGVzKCkgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXMuX25vZGU7CiAgICAgICAgICAgIHJldHVybiBub2RlICYmIG5vZGUubWV0YWdyYXBoID8gbm9kZS5tZXRhZ3JhcGgubm9kZXMoKSA6IG51bGw7CiAgICAgICAgfQogICAgICAgIGdldCBfdG90YWxQcmVkZWNlc3NvcnMoKSB7CiAgICAgICAgICAgIHZhciBwcmVkZWNlc3NvcnMgPSB0aGlzLl9wcmVkZWNlc3NvcnM7CiAgICAgICAgICAgIHJldHVybiBwcmVkZWNlc3NvcnMucmVndWxhci5sZW5ndGggKyBwcmVkZWNlc3NvcnMuY29udHJvbC5sZW5ndGg7CiAgICAgICAgfQogICAgICAgIGdldCBfdG90YWxTdWNjZXNzb3JzKCkgewogICAgICAgICAgICB2YXIgc3VjY2Vzc29ycyA9IHRoaXMuX3N1Y2Nlc3NvcnM7CiAgICAgICAgICAgIHJldHVybiBzdWNjZXNzb3JzLnJlZ3VsYXIubGVuZ3RoICsgc3VjY2Vzc29ycy5jb250cm9sLmxlbmd0aDsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUNvbnRyb2xQcmVkKCkgewogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sUHJlZCA9ICF0aGlzLl9vcGVuZWRDb250cm9sUHJlZDsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUNvbnRyb2xTdWNjKCkgewogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sU3VjYyA9ICF0aGlzLl9vcGVuZWRDb250cm9sU3VjYzsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUV4cGFuZGVkKCkgewogICAgICAgICAgICB0aGlzLl9leHBhbmRlZCA9ICF0aGlzLl9leHBhbmRlZDsKICAgICAgICB9CiAgICAgICAgX2dldFRvZ2dsZUljb24oZXhwYW5kZWQpIHsKICAgICAgICAgICAgcmV0dXJuIGV4cGFuZGVkID8gJ2V4cGFuZC1sZXNzJyA6ICdleHBhbmQtbW9yZSc7CiAgICAgICAgfQogICAgICAgIF9yZXNldFN0YXRlKCkgewogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sUHJlZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9vcGVuZWRDb250cm9sU3VjYyA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLnNldCgnX2dyb3VwQnV0dG9uVGV4dCcsIGdldEdyb3VwU2V0dGluZ0xhYmVsKHRoaXMuX25vZGUpKTsKICAgICAgICB9CiAgICAgICAgX3Jlc2l6ZUxpc3Qoc2VsZWN0b3IpIHsKICAgICAgICAgICAgdmFyIGxpc3QgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKHNlbGVjdG9yKTsKICAgICAgICAgICAgaWYgKGxpc3QpIHsKICAgICAgICAgICAgICAgIGxpc3QuZmlyZSgnaXJvbi1yZXNpemUnKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfdG9nZ2xlSW5jbHVkZSgpIHsKICAgICAgICAgICAgdGhpcy5maXJlKCdub2RlLXRvZ2dsZS1pbmNsdXNpb24nLCB7IG5hbWU6IHRoaXMuZ3JhcGhOb2RlTmFtZSB9KTsKICAgICAgICB9CiAgICAgICAgX25vZGVJbmNsdWRlU3RhdGVDaGFuZ2VkKGluY2x1ZGUsIG9sZEluY2x1ZGUpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19hdXhCdXR0b25UZXh0JywgZ2V0SW5jbHVkZU5vZGVCdXR0b25TdHJpbmcoaW5jbHVkZSkpOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlR3JvdXAoKSB7CiAgICAgICAgICAgIHZhciBzZXJpZXNOYW1lID0gZ2V0U2VyaWVzTmFtZSh0aGlzLl9ub2RlKTsKICAgICAgICAgICAgdGhpcy5maXJlKCdub2RlLXRvZ2dsZS1zZXJpZXNncm91cCcsIHsgbmFtZTogc2VyaWVzTmFtZSB9KTsKICAgICAgICB9CiAgICAgICAgX2lzTGlicmFyeUZ1bmN0aW9uKG5vZGUpIHsKICAgICAgICAgICAgLy8gSWYgdGhlIG5vZGUgbmFtZSBzdGFydHMgd2l0aCB0aGlzIHN0cmluZywgdGhlIG5vZGUgaXMgZWl0aGVyIGEKICAgICAgICAgICAgLy8gbGlicmFyeSBmdW5jdGlvbiBvciBhIG5vZGUgd2l0aGluIGl0LiBUaG9zZSBub2RlcyBzaG91bGQgbmV2ZXIgYmUKICAgICAgICAgICAgLy8gZXh0cmFjdGVkIGludG8gdGhlIGF1eGlsaWFyeSBzY2VuZSBncm91cCBiZWNhdXNlIHRoZXkgcmVwcmVzZW50CiAgICAgICAgICAgIC8vIHRlbXBsYXRlcyBmb3IgZnVuY3Rpb24gY2FsbCBub2Rlcywgbm90IG9wcyBpbiB0aGUgZ3JhcGggdGhlbXNlbHZlcy4KICAgICAgICAgICAgcmV0dXJuIG5vZGUgJiYgbm9kZS5uYW1lLnN0YXJ0c1dpdGgoRlVOQ1RJT05fTElCUkFSWV9OT0RFX1BSRUZJWCk7CiAgICAgICAgfQogICAgICAgIF9pc0luU2VyaWVzKG5vZGUpIHsKICAgICAgICAgICAgcmV0dXJuIGNhbkJlSW5TZXJpZXMobm9kZSk7CiAgICAgICAgfQogICAgfTsKICAgIFRmTm9kZUluZm8udGVtcGxhdGUgPSBodG1sIGAKICAgIDxzdHlsZT4KICAgICAgLnN1Yi1saXN0LWdyb3VwIHsKICAgICAgICBmb250LXdlaWdodDogNTAwOwogICAgICAgIGZvbnQtc2l6ZTogMTJwdDsKICAgICAgICBwYWRkaW5nLWJvdHRvbTogOHB4OwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAuc3ViLWxpc3QgewogICAgICAgIG1heC1oZWlnaHQ6IDMwMHB4OwogICAgICAgIG92ZXJmbG93LXk6IHNjcm9sbDsKICAgICAgfQoKICAgICAgLmF0dHItbGVmdCB7CiAgICAgICAgZmxvYXQ6IGxlZnQ7CiAgICAgICAgd2lkdGg6IDMwJTsKICAgICAgICB3b3JkLXdyYXA6IGJyZWFrLXdvcmQ7CiAgICAgICAgY29sb3I6ICM1NjU2NTY7CiAgICAgICAgZm9udC1zaXplOiAxMXB0OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgIH0KCiAgICAgIC5hdHRyLXJpZ2h0IHsKICAgICAgICBtYXJnaW4tbGVmdDogMzAlOwogICAgICAgIHdvcmQtd3JhcDogYnJlYWstd29yZDsKICAgICAgICBjb2xvcjogIzU2NTY1NjsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICB9CgogICAgICAuc3ViLWxpc3QtdGFibGUgewogICAgICAgIGRpc3BsYXk6IHRhYmxlOwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAuc3ViLWxpc3QtdGFibGUtcm93IHsKICAgICAgICBkaXNwbGF5OiB0YWJsZS1yb3c7CiAgICAgIH0KCiAgICAgIC5zdWItbGlzdC10YWJsZS1yb3cgLnN1Yi1saXN0LXRhYmxlLWNlbGw6bGFzdC1jaGlsZCB7CiAgICAgICAgdGV4dC1hbGlnbjogcmlnaHQ7CiAgICAgIH0KCiAgICAgIC5zdWItbGlzdC10YWJsZS1jZWxsIHsKICAgICAgICBjb2xvcjogIzU2NTY1NjsKICAgICAgICBkaXNwbGF5OiB0YWJsZS1jZWxsOwogICAgICAgIGZvbnQtc2l6ZTogMTFwdDsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICAgIG1heC13aWR0aDogMjAwcHg7CiAgICAgICAgcGFkZGluZzogMCA0cHg7CiAgICAgIH0KCiAgICAgIHBhcGVyLWl0ZW0gewogICAgICAgIHBhZGRpbmc6IDA7CiAgICAgICAgYmFja2dyb3VuZDogI2U5ZTllOTsKICAgICAgfQoKICAgICAgcGFwZXItaXRlbS1ib2R5W3R3by1saW5lXSB7CiAgICAgICAgbWluLWhlaWdodDogMDsKICAgICAgICBwYWRkaW5nOiA4cHggMTJweCA0cHg7CiAgICAgIH0KCiAgICAgIC5leHBhbmRlZEluZm8gewogICAgICAgIHBhZGRpbmc6IDhweCAxMnB4OwogICAgICB9CgogICAgICAuY29udHJvbERlcHMgewogICAgICAgIHBhZGRpbmc6IDAgMCAwIDhweDsKICAgICAgfQoKICAgICAgLm5vZGUtbmFtZSB7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vcm1hbDsKICAgICAgICB3b3JkLXdyYXA6IGJyZWFrLXdvcmQ7CiAgICAgICAgZm9udC1zaXplOiAxNHB0OwogICAgICAgIGZvbnQtd2VpZ2h0OiA1MDA7CiAgICAgIH0KCiAgICAgIC5ub2RlLWljb24gewogICAgICAgIGZsb2F0OiByaWdodDsKICAgICAgfQoKICAgICAgLnN1YnRpdGxlIHsKICAgICAgICBmb250LXNpemU6IDEycHQ7CiAgICAgICAgY29sb3I6ICM1ZTVlNWU7CiAgICAgIH0KCiAgICAgIC5jb250cm9sTGluZSB7CiAgICAgICAgZm9udC1zaXplOiAxMXB0OwogICAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7CiAgICAgIH0KCiAgICAgIC50b2dnbGUtYnV0dG9uIHsKICAgICAgICBmbG9hdDogcmlnaHQ7CiAgICAgICAgbWF4LWhlaWdodDogMjBweDsKICAgICAgICBtYXgtd2lkdGg6IDIwcHg7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgfQoKICAgICAgLmNvbnRyb2wtdG9nZ2xlLWJ1dHRvbiB7CiAgICAgICAgZmxvYXQ6IGxlZnQ7CiAgICAgICAgbWF4LWhlaWdodDogMjBweDsKICAgICAgICBtYXgtd2lkdGg6IDIwcHg7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgfQoKICAgICAgLnRvZ2dsZS1pbmNsdWRlLWdyb3VwIHsKICAgICAgICBwYWRkaW5nLXRvcDogNHB4OwogICAgICB9CgogICAgICAudG9nZ2xlLWluY2x1ZGUgewogICAgICAgIG1hcmdpbjogNXB4IDZweDsKICAgICAgICB0ZXh0LXRyYW5zZm9ybTogbm9uZTsKICAgICAgICBwYWRkaW5nOiA0cHggNnB4OwogICAgICAgIGZvbnQtc2l6ZTogMTBwdDsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZmFmYWZhOwogICAgICAgIGNvbG9yOiAjNjY2OwogICAgICB9CgogICAgICAudG9nZ2xlLWluY2x1ZGU6aG92ZXIgewogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWdvb2dsZS15ZWxsb3ctMTAwKTsKICAgICAgfQoKICAgICAgLm5vbi1jb250cm9sLWxpc3QtaXRlbSB7CiAgICAgICAgcGFkZGluZy1sZWZ0OiAxMHB4OwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPHBhcGVyLWl0ZW0+CiAgICAgIDxwYXBlci1pdGVtLWJvZHkgdHdvLWxpbmU+CiAgICAgICAgPGRpdj4KICAgICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbgogICAgICAgICAgICBpY29uPSJ7e19nZXRUb2dnbGVJY29uKF9leHBhbmRlZCl9fSIKICAgICAgICAgICAgb24tY2xpY2s9Il90b2dnbGVFeHBhbmRlZCIKICAgICAgICAgICAgY2xhc3M9InRvZ2dsZS1idXR0b24iCiAgICAgICAgICA+CiAgICAgICAgICA8L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgICAgPGRpdiBjbGFzcz0ibm9kZS1uYW1lIj4KICAgICAgICAgICAgPHRmLXdici1zdHJpbmcgdmFsdWU9IltbX25vZGUubmFtZV1dIiBkZWxpbWl0ZXItcGF0dGVybj0iLyI+CiAgICAgICAgICAgIDwvdGYtd2JyLXN0cmluZz4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXYgc2Vjb25kYXJ5PgogICAgICAgICAgPHRmLW5vZGUtaWNvbgogICAgICAgICAgICBjbGFzcz0ibm9kZS1pY29uIgogICAgICAgICAgICBub2RlPSJbW19ub2RlXV0iCiAgICAgICAgICAgIHJlbmRlci1pbmZvPSJbW19nZXRSZW5kZXJJbmZvKGdyYXBoTm9kZU5hbWUsIHJlbmRlckhpZXJhcmNoeSldXSIKICAgICAgICAgICAgY29sb3ItYnk9IltbY29sb3JCeV1dIgogICAgICAgICAgICB0ZW1wbGF0ZS1pbmRleD0iW1tfdGVtcGxhdGVJbmRleF1dIgogICAgICAgICAgPjwvdGYtbm9kZS1pY29uPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJ7e19ub2RlLm9wfX0iPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJzdWJ0aXRsZSI+CiAgICAgICAgICAgICAgT3BlcmF0aW9uOgogICAgICAgICAgICAgIDxzcGFuPltbX25vZGUub3BdXTwvc3Bhbj4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJ7e19ub2RlLm1ldGFncmFwaH19Ij4KICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3VidGl0bGUiPgogICAgICAgICAgICAgIFN1YmdyYXBoOgogICAgICAgICAgICAgIDxzcGFuPltbX25vZGUuY2FyZGluYWxpdHldXTwvc3Bhbj4gbm9kZXMKICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvZGl2PgogICAgICA8L3BhcGVyLWl0ZW0tYm9keT4KICAgIDwvcGFwZXItaXRlbT4KICAgIDxpcm9uLWNvbGxhcHNlIG9wZW5lZD0ie3tfZXhwYW5kZWR9fSI+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfZXhwYW5kZWR9fSIgcmVzdGFtcD0idHJ1ZSI+CiAgICAgICAgPGRpdiBjbGFzcz0iZXhwYW5kZWRJbmZvIj4KICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LWdyb3VwIGF0dHJpYnV0ZXMiPgogICAgICAgICAgICBBdHRyaWJ1dGVzICg8c3Bhbj5bW19hdHRyaWJ1dGVzLmxlbmd0aF1dPC9zcGFuPikKICAgICAgICAgICAgPGlyb24tbGlzdAogICAgICAgICAgICAgIGNsYXNzPSJzdWItbGlzdCIKICAgICAgICAgICAgICBpZD0iYXR0cmlidXRlc0xpc3QiCiAgICAgICAgICAgICAgaXRlbXM9IltbX2F0dHJpYnV0ZXNdXSIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDxkaXY+CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImF0dHItbGVmdCI+W1tpdGVtLmtleV1dPC9kaXY+CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImF0dHItcmlnaHQiPltbaXRlbS52YWx1ZV1dPC9kaXY+CiAgICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8L2lyb24tbGlzdD4KICAgICAgICAgIDwvZGl2PgoKICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfZGV2aWNlfX0iPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJzdWItbGlzdC1ncm91cCBkZXZpY2UiPgogICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImF0dHItbGVmdCI+RGV2aWNlPC9kaXY+CiAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iYXR0ci1yaWdodCI+W1tfZGV2aWNlXV08L2Rpdj4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgoKICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LWdyb3VwIHByZWRlY2Vzc29ycyI+CiAgICAgICAgICAgIElucHV0cyAoPHNwYW4+W1tfdG90YWxQcmVkZWNlc3NvcnNdXTwvc3Bhbj4pCiAgICAgICAgICAgIDxpcm9uLWxpc3QKICAgICAgICAgICAgICBjbGFzcz0ic3ViLWxpc3QiCiAgICAgICAgICAgICAgaWQ9ImlucHV0c0xpc3QiCiAgICAgICAgICAgICAgaXRlbXM9IltbX3ByZWRlY2Vzc29ycy5yZWd1bGFyXV0iCiAgICAgICAgICAgID4KICAgICAgICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICAgICAgICA8dGYtbm9kZS1saXN0LWl0ZW0KICAgICAgICAgICAgICAgICAgY2xhc3M9Im5vbi1jb250cm9sLWxpc3QtaXRlbSIKICAgICAgICAgICAgICAgICAgY2FyZC1ub2RlPSJbW19ub2RlXV0iCiAgICAgICAgICAgICAgICAgIGl0ZW0tbm9kZT0iW1tpdGVtLm5vZGVdXSIKICAgICAgICAgICAgICAgICAgZWRnZS1sYWJlbD0iW1tpdGVtLmVkZ2VMYWJlbF1dIgogICAgICAgICAgICAgICAgICBpdGVtLXJlbmRlci1pbmZvPSJbW2l0ZW0ucmVuZGVySW5mb11dIgogICAgICAgICAgICAgICAgICBuYW1lPSJbW2l0ZW0ubmFtZV1dIgogICAgICAgICAgICAgICAgICBpdGVtLXR5cGU9InByZWRlY2Vzc29ycyIKICAgICAgICAgICAgICAgICAgY29sb3ItYnk9IltbY29sb3JCeV1dIgogICAgICAgICAgICAgICAgICB0ZW1wbGF0ZS1pbmRleD0iW1tfdGVtcGxhdGVJbmRleF1dIgogICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgPC90Zi1ub2RlLWxpc3QtaXRlbT4KICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8L2lyb24tbGlzdD4KICAgICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19wcmVkZWNlc3NvcnMuY29udHJvbC5sZW5ndGhdXSI+CiAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29udHJvbERlcHMiPgogICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29udHJvbExpbmUiPgogICAgICAgICAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgICAgICAgICAgICBpY29uPSJ7e19nZXRUb2dnbGVJY29uKF9vcGVuZWRDb250cm9sUHJlZCl9fSIKICAgICAgICAgICAgICAgICAgICBvbi1jbGljaz0iX3RvZ2dsZUNvbnRyb2xQcmVkIgogICAgICAgICAgICAgICAgICAgIGNsYXNzPSJjb250cm9sLXRvZ2dsZS1idXR0b24iCiAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgICAgICAgICAgQ29udHJvbCBkZXBlbmRlbmNpZXMKICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPGlyb24tY29sbGFwc2Ugb3BlbmVkPSJ7e19vcGVuZWRDb250cm9sUHJlZH19IiBuby1hbmltYXRpb24+CiAgICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgICAgIGlzPSJkb20taWYiCiAgICAgICAgICAgICAgICAgICAgaWY9Int7X29wZW5lZENvbnRyb2xQcmVkfX0iCiAgICAgICAgICAgICAgICAgICAgcmVzdGFtcD0idHJ1ZSIKICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgIDxpcm9uLWxpc3QKICAgICAgICAgICAgICAgICAgICAgIGNsYXNzPSJzdWItbGlzdCIKICAgICAgICAgICAgICAgICAgICAgIGl0ZW1zPSJbW19wcmVkZWNlc3NvcnMuY29udHJvbF1dIgogICAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICAgICAgICAgICAgPHRmLW5vZGUtbGlzdC1pdGVtCiAgICAgICAgICAgICAgICAgICAgICAgICAgY2FyZC1ub2RlPSJbW19ub2RlXV0iCiAgICAgICAgICAgICAgICAgICAgICAgICAgaXRlbS1ub2RlPSJbW2l0ZW0ubm9kZV1dIgogICAgICAgICAgICAgICAgICAgICAgICAgIGl0ZW0tcmVuZGVyLWluZm89IltbaXRlbS5yZW5kZXJJbmZvXV0iCiAgICAgICAgICAgICAgICAgICAgICAgICAgbmFtZT0iW1tpdGVtLm5hbWVdXSIKICAgICAgICAgICAgICAgICAgICAgICAgICBpdGVtLXR5cGU9InByZWRlY2Vzc29ycyIKICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGUtaW5kZXg9IltbX3RlbXBsYXRlSW5kZXhdXSIKICAgICAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgICA8L3RmLW5vZGUtbGlzdC1pdGVtPgogICAgICAgICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgICAgICA8L2lyb24tbGlzdD4KICAgICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDwvaXJvbi1jb2xsYXBzZT4KICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDwvZGl2PgoKICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LWdyb3VwIHN1Y2Nlc3NvcnMiPgogICAgICAgICAgICBPdXRwdXRzICg8c3Bhbj5bW190b3RhbFN1Y2Nlc3NvcnNdXTwvc3Bhbj4pCiAgICAgICAgICAgIDxpcm9uLWxpc3QKICAgICAgICAgICAgICBjbGFzcz0ic3ViLWxpc3QiCiAgICAgICAgICAgICAgaWQ9Im91dHB1dHNMaXN0IgogICAgICAgICAgICAgIGl0ZW1zPSJbW19zdWNjZXNzb3JzLnJlZ3VsYXJdXSIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDx0Zi1ub2RlLWxpc3QtaXRlbQogICAgICAgICAgICAgICAgICBjbGFzcz0ibm9uLWNvbnRyb2wtbGlzdC1pdGVtIgogICAgICAgICAgICAgICAgICBjYXJkLW5vZGU9IltbX25vZGVdXSIKICAgICAgICAgICAgICAgICAgaXRlbS1ub2RlPSJbW2l0ZW0ubm9kZV1dIgogICAgICAgICAgICAgICAgICBlZGdlLWxhYmVsPSJbW2l0ZW0uZWRnZUxhYmVsXV0iCiAgICAgICAgICAgICAgICAgIGl0ZW0tcmVuZGVyLWluZm89IltbaXRlbS5yZW5kZXJJbmZvXV0iCiAgICAgICAgICAgICAgICAgIG5hbWU9IltbaXRlbS5uYW1lXV0iCiAgICAgICAgICAgICAgICAgIGl0ZW0tdHlwZT0ic3VjY2Vzc29yIgogICAgICAgICAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICAgICAgICAgIHRlbXBsYXRlLWluZGV4PSJbW190ZW1wbGF0ZUluZGV4XV0iCiAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICA8L3RmLW5vZGUtbGlzdC1pdGVtPgogICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDwvaXJvbi1saXN0PgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX3N1Y2Nlc3NvcnMuY29udHJvbC5sZW5ndGhdXSI+CiAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29udHJvbERlcHMiPgogICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29udHJvbExpbmUiPgogICAgICAgICAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgICAgICAgICAgICBpY29uPSJ7e19nZXRUb2dnbGVJY29uKF9vcGVuZWRDb250cm9sU3VjYyl9fSIKICAgICAgICAgICAgICAgICAgICBvbi1jbGljaz0iX3RvZ2dsZUNvbnRyb2xTdWNjIgogICAgICAgICAgICAgICAgICAgIGNsYXNzPSJjb250cm9sLXRvZ2dsZS1idXR0b24iCiAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgICAgICAgICAgQ29udHJvbCBkZXBlbmRlbmNpZXMKICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPGlyb24tY29sbGFwc2Ugb3BlbmVkPSJ7e19vcGVuZWRDb250cm9sU3VjY319IiBuby1hbmltYXRpb24+CiAgICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgICAgIGlzPSJkb20taWYiCiAgICAgICAgICAgICAgICAgICAgaWY9Int7X29wZW5lZENvbnRyb2xTdWNjfX0iCiAgICAgICAgICAgICAgICAgICAgcmVzdGFtcD0idHJ1ZSIKICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgIDxpcm9uLWxpc3QgY2xhc3M9InN1Yi1saXN0IiBpdGVtcz0iW1tfc3VjY2Vzc29ycy5jb250cm9sXV0iPgogICAgICAgICAgICAgICAgICAgICAgPHRlbXBsYXRlPgogICAgICAgICAgICAgICAgICAgICAgICA8dGYtbm9kZS1saXN0LWl0ZW0KICAgICAgICAgICAgICAgICAgICAgICAgICBjYXJkLW5vZGU9IltbX25vZGVdXSIKICAgICAgICAgICAgICAgICAgICAgICAgICBpdGVtLW5vZGU9IltbaXRlbS5ub2RlXV0iCiAgICAgICAgICAgICAgICAgICAgICAgICAgaXRlbS1yZW5kZXItaW5mbz0iW1tpdGVtLnJlbmRlckluZm9dXSIKICAgICAgICAgICAgICAgICAgICAgICAgICBuYW1lPSJbW2l0ZW0ubmFtZV1dIgogICAgICAgICAgICAgICAgICAgICAgICAgIGl0ZW0tdHlwZT0ic3VjY2Vzc29ycyIKICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGUtaW5kZXg9IltbX3RlbXBsYXRlSW5kZXhdXSIKICAgICAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgICA8L3RmLW5vZGUtbGlzdC1pdGVtPgogICAgICAgICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgICAgICA8L2lyb24tbGlzdD4KICAgICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDwvaXJvbi1jb2xsYXBzZT4KICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJ7e19oYXNEaXNwbGF5YWJsZU5vZGVTdGF0c319Ij4KICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtZ3JvdXAgbm9kZS1zdGF0cyI+CiAgICAgICAgICAgICAgTm9kZSBTdGF0cwogICAgICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LXRhYmxlIj4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfbm9kZVN0YXRzLnRvdGFsQnl0ZXN9fSI+CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LXRhYmxlLXJvdyI+CiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtdGFibGUtY2VsbCI+TWVtb3J5PC9kaXY+CiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtdGFibGUtY2VsbCI+CiAgICAgICAgICAgICAgICAgICAgICBbW19ub2RlU3RhdHNGb3JtYXR0ZWRCeXRlc11dCiAgICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfZ2V0VG90YWxNaWNyb3MoX25vZGVTdGF0cyl9fSI+CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LXRhYmxlLXJvdyI+CiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtdGFibGUtY2VsbCI+Q29tcHV0ZSBUaW1lPC9kaXY+CiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtdGFibGUtY2VsbCI+CiAgICAgICAgICAgICAgICAgICAgICBbW19ub2RlU3RhdHNGb3JtYXR0ZWRDb21wdXRlVGltZV1dCiAgICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfbm9kZVN0YXRzLm91dHB1dFNpemV9fSI+CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LXRhYmxlLXJvdyI+CiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtdGFibGUtY2VsbCI+VGVuc29yIE91dHB1dCBTaXplczwvZGl2PgogICAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9InN1Yi1saXN0LXRhYmxlLWNlbGwiPgogICAgICAgICAgICAgICAgICAgICAgPHRlbXBsYXRlCiAgICAgICAgICAgICAgICAgICAgICAgIGlzPSJkb20tcmVwZWF0IgogICAgICAgICAgICAgICAgICAgICAgICBpdGVtcz0ie3tfbm9kZVN0YXRzRm9ybWF0dGVkT3V0cHV0U2l6ZXN9fSIKICAgICAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgICAgICAgW1tpdGVtXV0gPGJyIC8+CiAgICAgICAgICAgICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KCiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2Z1bmN0aW9uVXNhZ2VzLmxlbmd0aF1dIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0ic3ViLWxpc3QtZ3JvdXAgcHJlZGVjZXNzb3JzIj4KICAgICAgICAgICAgICBVc2FnZXMgb2YgdGhlIEZ1bmN0aW9uICg8c3Bhbj5bW19mdW5jdGlvblVzYWdlcy5sZW5ndGhdXTwvc3Bhbj4pCiAgICAgICAgICAgICAgPGlyb24tbGlzdAogICAgICAgICAgICAgICAgY2xhc3M9InN1Yi1saXN0IgogICAgICAgICAgICAgICAgaWQ9ImZ1bmN0aW9uVXNhZ2VzTGlzdCIKICAgICAgICAgICAgICAgIGl0ZW1zPSJbW19mdW5jdGlvblVzYWdlc11dIgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgICAgICAgPHRmLW5vZGUtbGlzdC1pdGVtCiAgICAgICAgICAgICAgICAgICAgY2xhc3M9Im5vbi1jb250cm9sLWxpc3QtaXRlbSIKICAgICAgICAgICAgICAgICAgICBjYXJkLW5vZGU9IltbX25vZGVdXSIKICAgICAgICAgICAgICAgICAgICBpdGVtLW5vZGU9IltbaXRlbV1dIgogICAgICAgICAgICAgICAgICAgIG5hbWU9IltbaXRlbS5uYW1lXV0iCiAgICAgICAgICAgICAgICAgICAgaXRlbS10eXBlPSJmdW5jdGlvblVzYWdlcyIKICAgICAgICAgICAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICAgICAgICAgICAgdGVtcGxhdGUtaW5kZXg9IltbX3RlbXBsYXRlSW5kZXhdXSIKICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICA8L3RmLW5vZGUtbGlzdC1pdGVtPgogICAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgICA8L2lyb24tbGlzdD4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgoKICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shX2lzTGlicmFyeUZ1bmN0aW9uKF9ub2RlKV1dIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0idG9nZ2xlLWluY2x1ZGUtZ3JvdXAiPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24KICAgICAgICAgICAgICAgIHJhaXNlZAogICAgICAgICAgICAgICAgY2xhc3M9InRvZ2dsZS1pbmNsdWRlIgogICAgICAgICAgICAgICAgb24tY2xpY2s9Il90b2dnbGVJbmNsdWRlIgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxzcGFuPltbX2F1eEJ1dHRvblRleHRdXTwvc3Bhbj4KICAgICAgICAgICAgICA8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgoKICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0ie3tfaXNJblNlcmllcyhfbm9kZSl9fSI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9InRvZ2dsZS1pbmNsdWRlLWdyb3VwIj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgICByYWlzZWQKICAgICAgICAgICAgICAgIGNsYXNzPSJ0b2dnbGUtaW5jbHVkZSIKICAgICAgICAgICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlR3JvdXAiCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgPHNwYW4+W1tfZ3JvdXBCdXR0b25UZXh0XV08L3NwYW4+CiAgICAgICAgICAgICAgPC9wYXBlci1idXR0b24+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8L2Rpdj4KICAgICAgPC90ZW1wbGF0ZT4KICAgIDwvaXJvbi1jb2xsYXBzZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgImdyYXBoTm9kZU5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgImdyYXBoSGllcmFyY2h5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJyZW5kZXJIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgImNvbG9yQnkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2dldE5vZGUoZ3JhcGhOb2RlTmFtZSwgZ3JhcGhIaWVyYXJjaHkpJywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfcmVzZXRTdGF0ZScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9ub2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBjb21wdXRlZDogJ19nZXROb2RlU3RhdHMoZ3JhcGhOb2RlTmFtZSwgZ3JhcGhIaWVyYXJjaHkpJywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfcmVzZXRTdGF0ZScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9ub2RlU3RhdHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX25vZGVJbmNsdWRlU3RhdGVDaGFuZ2VkJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmTm9kZUluZm8ucHJvdG90eXBlLCAibm9kZUluY2x1ZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmTm9kZUluZm8ucHJvdG90eXBlLCAiX2V4cGFuZGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9vcGVuZWRDb250cm9sUHJlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfb3BlbmVkQ29udHJvbFN1Y2MiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9hdXhCdXR0b25UZXh0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfZ3JvdXBCdXR0b25UZXh0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdncmFwaEhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfdGVtcGxhdGVJbmRleCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ub2RlU3RhdHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9oYXNEaXNwbGF5YWJsZU5vZGVTdGF0cyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ub2RlU3RhdHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmTm9kZUluZm8ucHJvdG90eXBlLCAiX25vZGVTdGF0c0Zvcm1hdHRlZEJ5dGVzIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX25vZGVTdGF0cycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfbm9kZVN0YXRzRm9ybWF0dGVkQ29tcHV0ZVRpbWUiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfbm9kZVN0YXRzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmTm9kZUluZm8ucHJvdG90eXBlLCAiX25vZGVTdGF0c0Zvcm1hdHRlZE91dHB1dFNpemVzIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX25vZGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfYXR0cmlidXRlcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ub2RlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9kZXZpY2UiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfbm9kZScsICdncmFwaEhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfc3VjY2Vzc29ycyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ub2RlJywgJ2dyYXBoSGllcmFyY2h5JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9wcmVkZWNlc3NvcnMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfbm9kZScsICdncmFwaEhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZk5vZGVJbmZvLnByb3RvdHlwZSwgIl9mdW5jdGlvblVzYWdlcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ub2RlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmTm9kZUluZm8ucHJvdG90eXBlLCAiX3N1Ym5vZGVzIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX3ByZWRlY2Vzc29ycycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfdG90YWxQcmVkZWNlc3NvcnMiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfc3VjY2Vzc29ycycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZOb2RlSW5mby5wcm90b3R5cGUsICJfdG90YWxTdWNjZXNzb3JzIiwgbnVsbCk7CiAgICBUZk5vZGVJbmZvID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtbm9kZS1pbmZvJykKICAgIF0sIFRmTm9kZUluZm8pOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmR3JhcGhJbmZvID0gY2xhc3MgVGZHcmFwaEluZm8gZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdub2RlLWxpc3QtaXRlbS1jbGljaycsIHRoaXMuX25vZGVMaXN0SXRlbUNsaWNrZWQuYmluZCh0aGlzKSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbm9kZS1saXN0LWl0ZW0tbW91c2VvdmVyJywgdGhpcy5fbm9kZUxpc3RJdGVtTW91c2VvdmVyLmJpbmQodGhpcykpOwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ25vZGUtbGlzdC1pdGVtLW1vdXNlb3V0JywgdGhpcy5fbm9kZUxpc3RJdGVtTW91c2VvdXQuYmluZCh0aGlzKSk7CiAgICAgICAgfQogICAgICAgIF9ub2RlTGlzdEl0ZW1DbGlja2VkKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuc2VsZWN0ZWROb2RlID0gZXZlbnQuZGV0YWlsLm5vZGVOYW1lOwogICAgICAgIH0KICAgICAgICBfbm9kZUxpc3RJdGVtTW91c2VvdmVyKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuaGlnaGxpZ2h0ZWROb2RlID0gZXZlbnQuZGV0YWlsLm5vZGVOYW1lOwogICAgICAgIH0KICAgICAgICBfbm9kZUxpc3RJdGVtTW91c2VvdXQoKSB7CiAgICAgICAgICAgIHRoaXMuaGlnaGxpZ2h0ZWROb2RlID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgX2hlYWx0aFBpbGxzQXZhaWxhYmxlKGRlYnVnZ2VyRGF0YUVuYWJsZWQsIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMpIHsKICAgICAgICAgICAgLy8gU28gbG9uZyBhcyB0aGVyZSBpcyBhIG1hcHBpbmcgKGV2ZW4gaWYgZW1wdHkpIGZyb20gbm9kZSBuYW1lIHRvIGhlYWx0aCBwaWxscywgc2hvdyB0aGUKICAgICAgICAgICAgLy8gbGVnZW5kIGFuZCBzbGlkZXIuIFdlIGRvIHRoYXQgYmVjYXVzZSwgZXZlbiBpZiBubyBoZWFsdGggcGlsbHMgZXhpc3QgYXQgdGhlIGN1cnJlbnQgc3RlcCwKICAgICAgICAgICAgLy8gdGhlIHVzZXIgbWF5IGRlc2lyZSB0byBjaGFuZ2Ugc3RlcHMsIGFuZCB0aGUgc2xpZGVyIG11c3Qgc2hvdyBmb3IgdGhlIHVzZXIgdG8gZG8gdGhhdC4KICAgICAgICAgICAgcmV0dXJuIChkZWJ1Z2dlckRhdGFFbmFibGVkICYmCiAgICAgICAgICAgICAgICBub2RlTmFtZXNUb0hlYWx0aFBpbGxzICYmCiAgICAgICAgICAgICAgICBPYmplY3Qua2V5cyhub2RlTmFtZXNUb0hlYWx0aFBpbGxzKS5sZW5ndGggPiAwKTsKICAgICAgICB9CiAgICAgICAgX2VxdWFscyhhLCBiKSB7CiAgICAgICAgICAgIHJldHVybiBhID09PSBiOwogICAgICAgIH0KICAgIH07CiAgICBUZkdyYXBoSW5mby50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZm9udC1zaXplOiAxMnB4OwogICAgICAgIG1hcmdpbjogMDsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIG1heC1oZWlnaHQ6IDY1MHB4OwogICAgICAgIG92ZXJmbG93LXg6IGhpZGRlbjsKICAgICAgICBvdmVyZmxvdy15OiBhdXRvOwogICAgICB9CgogICAgICBoMiB7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgICB0ZXh0LWFsaWduOiBjZW50ZXI7CiAgICAgICAgbWFyZ2luOiAwOwogICAgICB9CiAgICA8L3N0eWxlPgogICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJ7e3NlbGVjdGVkTm9kZX19Ij4KICAgICAgPHBhcGVyLW1hdGVyaWFsIGVsZXZhdGlvbj0iMSIgY2xhc3M9ImNhcmQiPgogICAgICAgIDx0Zi1ub2RlLWluZm8KICAgICAgICAgIGdyYXBoLWhpZXJhcmNoeT0iW1tncmFwaEhpZXJhcmNoeV1dIgogICAgICAgICAgcmVuZGVyLWhpZXJhcmNoeT0iW1tyZW5kZXJIaWVyYXJjaHldXSIKICAgICAgICAgIGZsYXQtZ3JhcGg9IltbZ3JhcGhdXSIKICAgICAgICAgIGdyYXBoLW5vZGUtbmFtZT0iW1tzZWxlY3RlZE5vZGVdXSIKICAgICAgICAgIG5vZGUtaW5jbHVkZT0iW1tzZWxlY3RlZE5vZGVJbmNsdWRlXV0iCiAgICAgICAgICBoaWdobGlnaHRlZC1ub2RlPSJ7e2hpZ2hsaWdodGVkTm9kZX19IgogICAgICAgICAgY29sb3ItYnk9IltbY29sb3JCeV1dIgogICAgICAgID4KICAgICAgICA8L3RmLW5vZGUtaW5mbz4KICAgICAgPC9wYXBlci1tYXRlcmlhbD4KICAgIDwvdGVtcGxhdGU+CiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2VxdWFscyhjb2xvckJ5LCAnb3BfY29tcGF0aWJpbGl0eScpXV0iPgogICAgICA8dGYtZ3JhcGgtb3AtY29tcGF0LWNhcmQKICAgICAgICBncmFwaC1oaWVyYXJjaHk9IltbZ3JhcGhIaWVyYXJjaHldXSIKICAgICAgICBoaWVyYXJjaHktcGFyYW1zPSJbW2hpZXJhcmNoeVBhcmFtc11dIgogICAgICAgIHJlbmRlci1oaWVyYXJjaHk9IltbcmVuZGVySGllcmFyY2h5XV0iCiAgICAgICAgY29sb3ItYnk9IltbY29sb3JCeV1dIgogICAgICAgIG5vZGUtdGl0bGU9IltbY29tcGF0Tm9kZVRpdGxlXV0iCiAgICAgID4KICAgICAgPC90Zi1ncmFwaC1vcC1jb21wYXQtY2FyZD4KICAgIDwvdGVtcGxhdGU+CiAgICA8dGVtcGxhdGUKICAgICAgaXM9ImRvbS1pZiIKICAgICAgaWY9IltbX2hlYWx0aFBpbGxzQXZhaWxhYmxlKGRlYnVnZ2VyRGF0YUVuYWJsZWQsIG5vZGVOYW1lc1RvSGVhbHRoUGlsbHMpXV0iCiAgICA+CiAgICAgIDx0Zi1ncmFwaC1kZWJ1Z2dlci1kYXRhLWNhcmQKICAgICAgICByZW5kZXItaGllcmFyY2h5PSJbW3JlbmRlckhpZXJhcmNoeV1dIgogICAgICAgIGRlYnVnZ2VyLW51bWVyaWMtYWxlcnRzPSJbW2RlYnVnZ2VyTnVtZXJpY0FsZXJ0c11dIgogICAgICAgIG5vZGUtbmFtZXMtdG8taGVhbHRoLXBpbGxzPSJbW25vZGVOYW1lc1RvSGVhbHRoUGlsbHNdXSIKICAgICAgICBzZWxlY3RlZC1ub2RlPSJ7e3NlbGVjdGVkTm9kZX19IgogICAgICAgIGhpZ2hsaWdodGVkLW5vZGU9Int7aGlnaGxpZ2h0ZWROb2RlfX0iCiAgICAgICAgYXJlLWhlYWx0aC1waWxscy1sb2FkaW5nPSJbW2FyZUhlYWx0aFBpbGxzTG9hZGluZ11dIgogICAgICAgIGFsbC1zdGVwcy1tb2RlLWVuYWJsZWQ9Int7YWxsU3RlcHNNb2RlRW5hYmxlZH19IgogICAgICAgIHNwZWNpZmljLWhlYWx0aC1waWxsLXN0ZXA9Int7c3BlY2lmaWNIZWFsdGhQaWxsU3RlcH19IgogICAgICAgIGhlYWx0aC1waWxsLXN0ZXAtaW5kZXg9Int7aGVhbHRoUGlsbFN0ZXBJbmRleH19IgogICAgICA+CiAgICAgIDwvdGYtZ3JhcGgtZGVidWdnZXItZGF0YS1jYXJkPgogICAgPC90ZW1wbGF0ZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoSW5mby5wcm90b3R5cGUsICJ0aXRsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhJbmZvLnByb3RvdHlwZSwgImdyYXBoSGllcmFyY2h5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEluZm8ucHJvdG90eXBlLCAiZ3JhcGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoSW5mby5wcm90b3R5cGUsICJyZW5kZXJIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoSW5mby5wcm90b3R5cGUsICJub2RlTmFtZXNUb0hlYWx0aFBpbGxzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoSW5mby5wcm90b3R5cGUsICJoZWFsdGhQaWxsU3RlcEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaEluZm8ucHJvdG90eXBlLCAiY29sb3JCeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhJbmZvLnByb3RvdHlwZSwgImNvbXBhdE5vZGVUaXRsZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaEluZm8ucHJvdG90eXBlLCAic2VsZWN0ZWROb2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoSW5mby5wcm90b3R5cGUsICJoaWdobGlnaHRlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhJbmZvLnByb3RvdHlwZSwgInNlbGVjdGVkTm9kZUluY2x1ZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhJbmZvLnByb3RvdHlwZSwgImRlYnVnZ2VyRGF0YUVuYWJsZWQiLCB2b2lkIDApOwogICAgVGZHcmFwaEluZm8gPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ncmFwaC1pbmZvJykKICAgIF0sIFRmR3JhcGhJbmZvKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNvbnN0IEZSQUNfVklFV1BPSU5UX0FSRUEgPSAwLjg7CiAgICBjbGFzcyBNaW5pbWFwIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgbmV3IG1pbmltYXAuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gc3ZnIFRoZSBtYWluIHN2ZyBlbGVtZW50LgogICAgICAgICAqIEBwYXJhbSB6b29tRyBUaGUgc3ZnIGdyb3VwIHVzZWQgZm9yIHBhbm5pbmcgYW5kIHpvb21pbmcgdGhlIG1haW4gc3ZnLgogICAgICAgICAqIEBwYXJhbSBtYWluWm9vbSBUaGUgbWFpbiB6b29tIGJlaGF2aW9yLgogICAgICAgICAqIEBwYXJhbSBtaW5pbWFwIFRoZSBtaW5pbWFwIGNvbnRhaW5lci4KICAgICAgICAgKiBAcGFyYW0gbWF4V2FuZEggVGhlIG1heGltdW0gd2lkdGgvaGVpZ2h0IGZvciB0aGUgbWluaW1hcC4KICAgICAgICAgKiBAcGFyYW0gbGFiZWxQYWRkaW5nIFBhZGRpbmcgaW4gcGl4ZWxzIGR1ZSB0byB0aGUgbWFpbiBncmFwaCBsYWJlbHMuCiAgICAgICAgICovCiAgICAgICAgY29uc3RydWN0b3Ioc3ZnLCB6b29tRywgbWFpblpvb20sIG1pbmltYXAsIG1heFdhbmRILCBsYWJlbFBhZGRpbmcpIHsKICAgICAgICAgICAgdGhpcy5zdmcgPSBzdmc7CiAgICAgICAgICAgIHRoaXMubGFiZWxQYWRkaW5nID0gbGFiZWxQYWRkaW5nOwogICAgICAgICAgICB0aGlzLnpvb21HID0gem9vbUc7CiAgICAgICAgICAgIHRoaXMubWFpblpvb20gPSBtYWluWm9vbTsKICAgICAgICAgICAgdGhpcy5tYXhXYW5kSCA9IG1heFdhbmRIOwogICAgICAgICAgICBsZXQgJHNoYWRvd1Jvb3QgPSBzZWxlY3QobWluaW1hcC5zaGFkb3dSb290KTsKICAgICAgICAgICAgLy8gVGhlIG1pbmltYXAgd2lsbCBoYXZlIDIgbWFpbiBjb21wb25lbnRzOiB0aGUgY2FudmFzIHNob3dpbmcgdGhlIGNvbnRlbnQKICAgICAgICAgICAgLy8gYW5kIGFuIHN2ZyBzaG93aW5nIGEgcmVjdGFuZ2xlIG9mIHRoZSBjdXJyZW50bHkgem9vbWVkL3Bhbm5lZCB2aWV3cG9pbnQuCiAgICAgICAgICAgIGxldCAkbWluaW1hcFN2ZyA9ICRzaGFkb3dSb290LnNlbGVjdCgnc3ZnJyk7CiAgICAgICAgICAgIC8vIE1ha2UgdGhlIHZpZXdwb2ludCByZWN0YW5nbGUgZHJhZ2dhYmxlLgogICAgICAgICAgICBsZXQgJHZpZXdwb2ludCA9ICRtaW5pbWFwU3ZnLnNlbGVjdCgncmVjdCcpOwogICAgICAgICAgICBsZXQgZHJhZ21vdmUgPSAoZCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy52aWV3cG9pbnRDb29yZC54ID0gZXZlbnQueDsKICAgICAgICAgICAgICAgIHRoaXMudmlld3BvaW50Q29vcmQueSA9IGV2ZW50Lnk7CiAgICAgICAgICAgICAgICB0aGlzLnVwZGF0ZVZpZXdwb2ludCgpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLnZpZXdwb2ludENvb3JkID0geyB4OiAwLCB5OiAwIH07CiAgICAgICAgICAgIGxldCBkcmFnJDEgPSBkcmFnKCkuc3ViamVjdChPYmplY3QpLm9uKCdkcmFnJywgZHJhZ21vdmUpOwogICAgICAgICAgICAkdmlld3BvaW50LmRhdHVtKHRoaXMudmlld3BvaW50Q29vcmQpLmNhbGwoZHJhZyQxKTsKICAgICAgICAgICAgLy8gTWFrZSB0aGUgbWluaW1hcCBjbGlja2FibGUuCiAgICAgICAgICAgICRtaW5pbWFwU3ZnLm9uKCdjbGljaycsICgpID0+IHsKICAgICAgICAgICAgICAgIGlmIChldmVudC5kZWZhdWx0UHJldmVudGVkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyBjbGljayB3YXMgcGFydCBvZiBhIGRyYWcgZXZlbnQsIHNvIHN1cHByZXNzIGl0LgogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgY29vcmRpbmF0ZXMgb2YgdGhlIHZpZXdwb2ludC4KICAgICAgICAgICAgICAgIGxldCB3aWR0aCA9IE51bWJlcigkdmlld3BvaW50LmF0dHIoJ3dpZHRoJykpOwogICAgICAgICAgICAgICAgbGV0IGhlaWdodCA9IE51bWJlcigkdmlld3BvaW50LmF0dHIoJ2hlaWdodCcpKTsKICAgICAgICAgICAgICAgIGxldCBjbGlja0Nvb3JkcyA9IG1vdXNlKCRtaW5pbWFwU3ZnLm5vZGUoKSk7CiAgICAgICAgICAgICAgICB0aGlzLnZpZXdwb2ludENvb3JkLnggPSBjbGlja0Nvb3Jkc1swXSAtIHdpZHRoIC8gMjsKICAgICAgICAgICAgICAgIHRoaXMudmlld3BvaW50Q29vcmQueSA9IGNsaWNrQ29vcmRzWzFdIC0gaGVpZ2h0IC8gMjsKICAgICAgICAgICAgICAgIHRoaXMudXBkYXRlVmlld3BvaW50KCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLnZpZXdwb2ludCA9ICR2aWV3cG9pbnQubm9kZSgpOwogICAgICAgICAgICB0aGlzLm1pbmltYXBTdmcgPSAkbWluaW1hcFN2Zy5ub2RlKCk7CiAgICAgICAgICAgIHRoaXMubWluaW1hcCA9IG1pbmltYXA7CiAgICAgICAgICAgIHRoaXMuY2FudmFzID0gJHNoYWRvd1Jvb3Quc2VsZWN0KCdjYW52YXMuZmlyc3QnKS5ub2RlKCk7CiAgICAgICAgICAgIHRoaXMuY2FudmFzQnVmZmVyID0gKCRzaGFkb3dSb290LnNlbGVjdCgnY2FudmFzLnNlY29uZCcpLm5vZGUoKSk7CiAgICAgICAgICAgIHRoaXMuZG93bmxvYWRDYW52YXMgPSAoJHNoYWRvd1Jvb3Quc2VsZWN0KCdjYW52YXMuZG93bmxvYWQnKS5ub2RlKCkpOwogICAgICAgICAgICBzZWxlY3QodGhpcy5kb3dubG9hZENhbnZhcykuc3R5bGUoJ2Rpc3BsYXknLCAnbm9uZScpOwogICAgICAgICAgICB0aGlzLnVwZGF0ZSgpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBVcGRhdGVzIHRoZSBwb3NpdGlvbiBhbmQgdGhlIHNpemUgb2YgdGhlIHZpZXdwb2ludCByZWN0YW5nbGUuCiAgICAgICAgICogSXQgYWxzbyBub3RpZmllcyB0aGUgbWFpbiBzdmcgYWJvdXQgdGhlIG5ldyBwYW5uZWQgcG9zaXRpb24uCiAgICAgICAgICovCiAgICAgICAgdXBkYXRlVmlld3BvaW50KCkgewogICAgICAgICAgICAvLyBVcGRhdGUgdGhlIGNvb3JkaW5hdGVzIG9mIHRoZSB2aWV3cG9pbnQgcmVjdGFuZ2xlLgogICAgICAgICAgICBzZWxlY3QodGhpcy52aWV3cG9pbnQpCiAgICAgICAgICAgICAgICAuYXR0cigneCcsIHRoaXMudmlld3BvaW50Q29vcmQueCkKICAgICAgICAgICAgICAgIC5hdHRyKCd5JywgdGhpcy52aWV3cG9pbnRDb29yZC55KTsKICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSB0cmFuc2xhdGlvbiB2ZWN0b3Igb2YgdGhlIG1haW4gc3ZnIHRvIHJlZmxlY3QgdGhlCiAgICAgICAgICAgIC8vIG5ldyB2aWV3cG9pbnQuCiAgICAgICAgICAgIGxldCBtYWluWCA9ICgtdGhpcy52aWV3cG9pbnRDb29yZC54ICogdGhpcy5zY2FsZU1haW4pIC8gdGhpcy5zY2FsZU1pbmltYXA7CiAgICAgICAgICAgIGxldCBtYWluWSA9ICgtdGhpcy52aWV3cG9pbnRDb29yZC55ICogdGhpcy5zY2FsZU1haW4pIC8gdGhpcy5zY2FsZU1pbmltYXA7CiAgICAgICAgICAgIHNlbGVjdCh0aGlzLnN2ZykuY2FsbCh0aGlzLm1haW5ab29tLnRyYW5zZm9ybSwgaWRlbnRpdHkkOS50cmFuc2xhdGUobWFpblgsIG1haW5ZKS5zY2FsZSh0aGlzLnNjYWxlTWFpbikpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZWRyYXdzIHRoZSBtaW5pbWFwLiBTaG91bGQgYmUgY2FsbGVkIHdoZW5ldmVyIHRoZSBtYWluIHN2ZwogICAgICAgICAqIHdhcyB1cGRhdGVkIChlLmcuIHdoZW4gYSBub2RlIHdhcyBleHBhbmRlZCkuCiAgICAgICAgICovCiAgICAgICAgdXBkYXRlKCkgewogICAgICAgICAgICBsZXQgc2NlbmVTaXplID0gbnVsbDsKICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgIC8vIEdldCB0aGUgc2l6ZSBvZiB0aGUgZW50aXJlIHNjZW5lLgogICAgICAgICAgICAgICAgc2NlbmVTaXplID0gdGhpcy56b29tRy5nZXRCQm94KCk7CiAgICAgICAgICAgICAgICBpZiAoc2NlbmVTaXplLndpZHRoID09PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGhlcmUgaXMgbm8gc2NlbmUgYW55bW9yZS4gV2UgaGF2ZSBiZWVuIGRldGFjaGVkIGZyb20gdGhlIGRvbS4KICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgIC8vIEZpcmVmb3ggcHJvZHVjZWQgTlNfRVJST1JfRkFJTFVSRSBpZiB3ZSBoYXZlIGJlZW4KICAgICAgICAgICAgICAgIC8vIGRldGFjaGVkIGZyb20gdGhlIGRvbS4KICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBsZXQgJGRvd25sb2FkID0gc2VsZWN0KCcjZ3JhcGhkb3dubG9hZCcpOwogICAgICAgICAgICB0aGlzLmRvd25sb2FkID0gJGRvd25sb2FkLm5vZGUoKTsKICAgICAgICAgICAgJGRvd25sb2FkLm9uKCdjbGljaycsIChkKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBSZXZva2UgdGhlIG9sZCBVUkwsIGlmIGFueS4gVGhlbiwgZ2VuZXJhdGUgYSBuZXcgVVJMLgogICAgICAgICAgICAgICAgVVJMLnJldm9rZU9iamVjdFVSTCh0aGlzLmRvd25sb2FkLmhyZWYpOwogICAgICAgICAgICAgICAgLy8gV2UgY2FuJ3QgdXNlIHRoZSBgSFRNTENhbnZhc0VsZW1lbnQudG9CbG9iYCBBUEkgYmVjYXVzZSBpdCBkb2VzCiAgICAgICAgICAgICAgICAvLyBub3QgaGF2ZSBhIHN5bmNocm9ub3VzIHZhcmlhbnQsIGFuZCB3ZSBuZWVkIHRvIHVwZGF0ZSB0aGlzIGhyZWYKICAgICAgICAgICAgICAgIC8vIHN5bmNocm9ub3VzbHkuIEluc3RlYWQsIHdlIGNyZWF0ZSBhIGJsb2IgbWFudWFsbHkgZnJvbSB0aGUgZGF0YQogICAgICAgICAgICAgICAgLy8gVVJMLgogICAgICAgICAgICAgICAgY29uc3QgZGF0YVVybCA9IHRoaXMuZG93bmxvYWRDYW52YXMudG9EYXRhVVJMKCdpbWFnZS9wbmcnKTsKICAgICAgICAgICAgICAgIGNvbnN0IHByZWZpeCA9IGRhdGFVcmwuc2xpY2UoMCwgZGF0YVVybC5pbmRleE9mKCcsJykpOwogICAgICAgICAgICAgICAgaWYgKCFwcmVmaXguZW5kc1dpdGgoJztiYXNlNjQnKSkgewogICAgICAgICAgICAgICAgICAgIGNvbnNvbGUud2Fybihgbm9uLWJhc2U2NCBkYXRhIFVSTCAoJHtwcmVmaXh9KTsgY2Fubm90IHVzZSBibG9iIGRvd25sb2FkYCk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5kb3dubG9hZC5ocmVmID0gZGF0YVVybDsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb25zdCBkYXRhID0gYXRvYihkYXRhVXJsLnNsaWNlKGRhdGFVcmwuaW5kZXhPZignLCcpICsgMSkpOwogICAgICAgICAgICAgICAgY29uc3QgYnl0ZXMgPSBuZXcgVWludDhBcnJheShkYXRhLmxlbmd0aCkubWFwKChfLCBpKSA9PiBkYXRhLmNoYXJDb2RlQXQoaSkpOwogICAgICAgICAgICAgICAgY29uc3QgYmxvYiA9IG5ldyBCbG9iKFtieXRlc10sIHsgdHlwZTogJ2ltYWdlL3BuZycgfSk7CiAgICAgICAgICAgICAgICB0aGlzLmRvd25sb2FkLmhyZWYgPSBVUkwuY3JlYXRlT2JqZWN0VVJMKGJsb2IpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgbGV0ICRzdmcgPSBzZWxlY3QodGhpcy5zdmcpOwogICAgICAgICAgICAvLyBSZWFkIGFsbCB0aGUgc3R5bGUgcnVsZXMgaW4gdGhlIGRvY3VtZW50IGFuZCBlbWJlZCB0aGVtIGludG8gdGhlIHN2Zy4KICAgICAgICAgICAgLy8gVGhlIHN2ZyBuZWVkcyB0byBiZSBzZWxmIGNvbnRhaW5lZCwgaS5lLiBhbGwgdGhlIHN0eWxlIHJ1bGVzIG5lZWQgdG8gYmUKICAgICAgICAgICAgLy8gZW1iZWRkZWQgc28gdGhlIGNhbnZhcyBvdXRwdXQgbWF0Y2hlcyB0aGUgb3JpZ2luLgogICAgICAgICAgICBsZXQgc3R5bGVzVGV4dCA9ICcnOwogICAgICAgICAgICBjb25zdCBhbnlTdmcgPSB0aGlzLnN2ZzsKICAgICAgICAgICAgLy8gTVNFZGdlIGRvZXMgbm90IGhhdmUgYGdldFJvb3ROb2RlYC4gSW4gdGhhdCBjYXNlLCBtYW51YWxseSBnZXQgdGhlIHJvb3QKICAgICAgICAgICAgLy8gbm9kZS4gVGhpcyBpcyBtb3JlIGJyaXR0bGUgdGhhbiB0aGUgZ2V0Um9vdE5vZGUgYXMgY2hhbmdpbmcgRE9NIHN0cnVjdHVyZQogICAgICAgICAgICAvLyB3aWxsIGJyZWFrIHRoaXMuCiAgICAgICAgICAgIGNvbnN0IHJvb3ROb2RlID0gYW55U3ZnLmdldFJvb3ROb2RlCiAgICAgICAgICAgICAgICA/IGFueVN2Zy5nZXRSb290Tm9kZSgpCiAgICAgICAgICAgICAgICA6IHRoaXMuc3ZnLnBhcmVudE5vZGU7CiAgICAgICAgICAgIGNvbnN0IHN0eWxlU2hlZXRzID0gcm9vdE5vZGUuc3R5bGVTaGVldHM7CiAgICAgICAgICAgIGZvciAobGV0IGsgPSAwOyBrIDwgc3R5bGVTaGVldHMubGVuZ3RoOyBrKyspIHsKICAgICAgICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IGNzc1J1bGVzID0gc3R5bGVTaGVldHNba10uY3NzUnVsZXMgfHwgc3R5bGVTaGVldHNba10ucnVsZXM7CiAgICAgICAgICAgICAgICAgICAgaWYgKGNzc1J1bGVzID09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgY3NzUnVsZXMubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gUmVtb3ZlIHRmLSogc2VsZWN0b3JzIGZyb20gdGhlIHN0eWxlcy4KICAgICAgICAgICAgICAgICAgICAgICAgc3R5bGVzVGV4dCArPQogICAgICAgICAgICAgICAgICAgICAgICAgICAgY3NzUnVsZXNbaV0uY3NzVGV4dC5yZXBsYWNlKC8gP3RmLVtcdy1dKyA/L2csICcnKSArICdcbic7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgICAgICBpZiAoZS5uYW1lICE9PSAnU2VjdXJpdHlFcnJvcicpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhyb3cgZTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVGVtcG9yYXJpbHkgYWRkIHRoZSBjc3MgcnVsZXMgdG8gdGhlIG1haW4gc3ZnLgogICAgICAgICAgICBsZXQgc3ZnU3R5bGUgPSAkc3ZnLmFwcGVuZCgnc3R5bGUnKTsKICAgICAgICAgICAgc3ZnU3R5bGUudGV4dChzdHlsZXNUZXh0KTsKICAgICAgICAgICAgLy8gVGVtcG9yYXJpbHkgcmVtb3ZlIHRoZSB6b29tL3BhbiB0cmFuc2Zvcm0gZnJvbSB0aGUgbWFpbiBzdmcgc2luY2Ugd2UKICAgICAgICAgICAgLy8gd2FudCB0aGUgbWluaW1hcCB0byBzaG93IGEgem9vbWVkLW91dCBhbmQgY2VudGVyZWQgdmlldy4KICAgICAgICAgICAgbGV0ICR6b29tRyA9IHNlbGVjdCh0aGlzLnpvb21HKTsKICAgICAgICAgICAgbGV0IHpvb21UcmFuc2Zvcm0gPSAkem9vbUcuYXR0cigndHJhbnNmb3JtJyk7CiAgICAgICAgICAgICR6b29tRy5hdHRyKCd0cmFuc2Zvcm0nLCBudWxsKTsKICAgICAgICAgICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvaXNzdWVzLzE1OTgKICAgICAgICAgICAgLy8gQWNjb3VudCBmb3IgU1ZHIGNvbnRlbnQgc2hpZnQuIFNWR0dyYXBoaWNzRWxlbWVudC5nZXRCQm94KCkud2lkdGggcmV0dXJucwogICAgICAgICAgICAvLyB3aWR0aCBpbiBwaXhlbCB2YWx1ZSBvZiB2ZXJ5IHRpZ2h0IGJvdW5kaW5nIGJveCBvZiBub24tZW1wdHkgY29udGVudC4KICAgICAgICAgICAgLy8gU2luY2Ugd2Ugd2FudCB0byBtZWFzdXJlIHRoZSBzY2VuZVNpemUgZnJvbSB0aGUgb3JpZ2luIHRvIHRoZSByaWdodCBtb3N0CiAgICAgICAgICAgIC8vIGVkZ2Ugb2YgdGhlIHJpZ2h0IG1vc3Qgbm9kZSwgd2UgbmVlZCB0byBhY2NvdW50IGZvciBkaXN0YW5jZSBmcm9tIHRoZQogICAgICAgICAgICAvLyBvcmlnaW4gdG8gdGhlIGxlZnQgZWRnZSBvZiB0aGUgYm91bmRpbmcgYm94LgogICAgICAgICAgICBzY2VuZVNpemUuaGVpZ2h0ICs9IHNjZW5lU2l6ZS55OwogICAgICAgICAgICBzY2VuZVNpemUud2lkdGggKz0gc2NlbmVTaXplLng7CiAgICAgICAgICAgIC8vIFNpbmNlIHdlIGFkZCBwYWRkaW5nLCBhY2NvdW50IGZvciB0aGF0IGhlcmUuCiAgICAgICAgICAgIHNjZW5lU2l6ZS5oZWlnaHQgKz0gdGhpcy5sYWJlbFBhZGRpbmcgKiAyOwogICAgICAgICAgICBzY2VuZVNpemUud2lkdGggKz0gdGhpcy5sYWJlbFBhZGRpbmcgKiAyOwogICAgICAgICAgICAvLyBUZW1wb3JhcmlseSBhc3NpZ24gYW4gZXhwbGljaXQgd2lkdGgvaGVpZ2h0IHRvIHRoZSBtYWluIHN2Zywgc2luY2UKICAgICAgICAgICAgLy8gaXQgZG9lc24ndCBoYXZlIG9uZSAodXNlcyBmbGV4LWJveCksIGJ1dCB3ZSBuZWVkIGl0IGZvciB0aGUgY2FudmFzCiAgICAgICAgICAgIC8vIHRvIHdvcmsuCiAgICAgICAgICAgICRzdmcuYXR0cignd2lkdGgnLCBzY2VuZVNpemUud2lkdGgpLmF0dHIoJ2hlaWdodCcsIHNjZW5lU2l6ZS5oZWlnaHQpOwogICAgICAgICAgICAvLyBTaW5jZSB0aGUgY29udGVudCBpbnNpZGUgdGhlIHN2ZyBjaGFuZ2VkIChlLmcuIGEgbm9kZSB3YXMgZXhwYW5kZWQpLAogICAgICAgICAgICAvLyB0aGUgYXNwZWN0IHJhdGlvIGhhdmUgYWxzbyBjaGFuZ2VkLiBUaHVzLCB3ZSBuZWVkIHRvIHVwZGF0ZSB0aGUgc2NhbGUKICAgICAgICAgICAgLy8gZmFjdG9yIG9mIHRoZSBtaW5pbWFwLiBUaGUgc2NhbGUgZmFjdG9yIGlzIGRldGVybWluZWQgc3VjaCB0aGF0IGJvdGgKICAgICAgICAgICAgLy8gdGhlIHdpZHRoIGFuZCBoZWlnaHQgb2YgdGhlIG1pbmltYXAgYXJlIDw9IG1heGltdW0gc3BlY2lmaWVkIHcvaC4KICAgICAgICAgICAgdGhpcy5zY2FsZU1pbmltYXAgPQogICAgICAgICAgICAgICAgdGhpcy5tYXhXYW5kSCAvIE1hdGgubWF4KHNjZW5lU2l6ZS53aWR0aCwgc2NlbmVTaXplLmhlaWdodCk7CiAgICAgICAgICAgIHRoaXMubWluaW1hcFNpemUgPSB7CiAgICAgICAgICAgICAgICB3aWR0aDogc2NlbmVTaXplLndpZHRoICogdGhpcy5zY2FsZU1pbmltYXAsCiAgICAgICAgICAgICAgICBoZWlnaHQ6IHNjZW5lU2l6ZS5oZWlnaHQgKiB0aGlzLnNjYWxlTWluaW1hcCwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSBzaXplIG9mIHRoZSBtaW5pbWFwJ3Mgc3ZnLCB0aGUgYnVmZmVyIGNhbnZhcyBhbmQgdGhlCiAgICAgICAgICAgIC8vIHZpZXdwb2ludCByZWN0LgogICAgICAgICAgICBzZWxlY3QodGhpcy5taW5pbWFwU3ZnKS5hdHRyKHRoaXMubWluaW1hcFNpemUpOwogICAgICAgICAgICBzZWxlY3QodGhpcy5jYW52YXNCdWZmZXIpLmF0dHIodGhpcy5taW5pbWFwU2l6ZSk7CiAgICAgICAgICAgIC8vIERvd25sb2FkIGNhbnZhcyB3aWR0aCBhbmQgaGVpZ2h0IGFyZSBtdWx0aXBsZXMgb2YgdGhlIHN0eWxlIHdpZHRoIGFuZAogICAgICAgICAgICAvLyBoZWlnaHQgaW4gb3JkZXIgdG8gaW5jcmVhc2UgcGl4ZWwgZGVuc2l0eSBvZiB0aGUgUE5HIGZvciBjbGFyaXR5LgogICAgICAgICAgICBjb25zdCBkb3dubG9hZENhbnZhc1NlbGVjdGlvbiA9IHNlbGVjdCh0aGlzLmRvd25sb2FkQ2FudmFzKTsKICAgICAgICAgICAgZG93bmxvYWRDYW52YXNTZWxlY3Rpb24uc3R5bGUoJ3dpZHRoJywgc2NlbmVTaXplLndpZHRoKTsKICAgICAgICAgICAgZG93bmxvYWRDYW52YXNTZWxlY3Rpb24uc3R5bGUoJ2hlaWdodCcsIHNjZW5lU2l6ZS5oZWlnaHQpOwogICAgICAgICAgICBkb3dubG9hZENhbnZhc1NlbGVjdGlvbi5hdHRyKCd3aWR0aCcsIDMgKiBzY2VuZVNpemUud2lkdGgpOwogICAgICAgICAgICBkb3dubG9hZENhbnZhc1NlbGVjdGlvbi5hdHRyKCdoZWlnaHQnLCAzICogc2NlbmVTaXplLmhlaWdodCk7CiAgICAgICAgICAgIGlmICh0aGlzLnRyYW5zbGF0ZSAhPSBudWxsICYmIHRoaXMuem9vbSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBVcGRhdGUgdGhlIHZpZXdwb2ludCByZWN0YW5nbGUgc2hhcGUgc2luY2UgdGhlIGFzcGVjdCByYXRpbyBvZiB0aGUKICAgICAgICAgICAgICAgIC8vIG1hcCBoYXMgY2hhbmdlZC4KICAgICAgICAgICAgICAgIHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB0aGlzLnpvb20oKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVE9ETyhzdGVwaGFud2xlZSk6IENvbnNpZGVyIG5vdCBtdXRhdGluZyB0aGUgb3JpZ2luYWwgRE9NIHRoZW4gcmVhZCBpdCAtLQogICAgICAgICAgICAvLyB0aGlzIG1heSBjYXVzZSByZWZsb3cuCiAgICAgICAgICAgIC8vIFNlcmlhbGl6ZSB0aGUgbWFpbiBzdmcgdG8gYSBzdHJpbmcgd2hpY2ggd2lsbCBiZSB1c2VkIGFzIHRoZSByZW5kZXJpbmcKICAgICAgICAgICAgLy8gY29udGVudCBmb3IgdGhlIGNhbnZhcy4KICAgICAgICAgICAgbGV0IHN2Z1htbCA9IG5ldyBYTUxTZXJpYWxpemVyKCkuc2VyaWFsaXplVG9TdHJpbmcodGhpcy5zdmcpOwogICAgICAgICAgICAvLyBOb3cgdGhhdCB0aGUgc3ZnIGlzIHNlcmlhbGl6ZWQgZm9yIHJlbmRlcmluZywgcmVtb3ZlIHRoZSB0ZW1wb3JhcmlseQogICAgICAgICAgICAvLyBhc3NpZ25lZCBzdHlsZXMsIGV4cGxpY2l0IHdpZHRoIGFuZCBoZWlnaHQgYW5kIGJyaW5nIGJhY2sgdGhlIHBhbi96b29tCiAgICAgICAgICAgIC8vIHRyYW5zZm9ybS4KICAgICAgICAgICAgc3ZnU3R5bGUucmVtb3ZlKCk7CiAgICAgICAgICAgICRzdmcuYXR0cignd2lkdGgnLCBudWxsKS5hdHRyKCdoZWlnaHQnLCBudWxsKTsKICAgICAgICAgICAgJHpvb21HLmF0dHIoJ3RyYW5zZm9ybScsIHpvb21UcmFuc2Zvcm0pOwogICAgICAgICAgICBsZXQgaW1hZ2UgPSBuZXcgSW1hZ2UoKTsKICAgICAgICAgICAgaW1hZ2Uub25sb2FkID0gKCkgPT4gewogICAgICAgICAgICAgICAgLy8gRHJhdyB0aGUgc3ZnIGNvbnRlbnQgb250byB0aGUgYnVmZmVyIGNhbnZhcy4KICAgICAgICAgICAgICAgIGxldCBjb250ZXh0ID0gdGhpcy5jYW52YXNCdWZmZXIuZ2V0Q29udGV4dCgnMmQnKTsKICAgICAgICAgICAgICAgIGNvbnRleHQuY2xlYXJSZWN0KDAsIDAsIHRoaXMuY2FudmFzQnVmZmVyLndpZHRoLCB0aGlzLmNhbnZhc0J1ZmZlci5oZWlnaHQpOwogICAgICAgICAgICAgICAgY29udGV4dC5kcmF3SW1hZ2UoaW1hZ2UsIDAsIDAsIHRoaXMubWluaW1hcFNpemUud2lkdGgsIHRoaXMubWluaW1hcFNpemUuaGVpZ2h0KTsKICAgICAgICAgICAgICAgIHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgLy8gSGlkZSB0aGUgb2xkIGNhbnZhcyBhbmQgc2hvdyB0aGUgbmV3IGJ1ZmZlciBjYW52YXMuCiAgICAgICAgICAgICAgICAgICAgc2VsZWN0KHRoaXMuY2FudmFzQnVmZmVyKS5zdHlsZSgnZGlzcGxheScsIG51bGwpOwogICAgICAgICAgICAgICAgICAgIHNlbGVjdCh0aGlzLmNhbnZhcykuc3R5bGUoJ2Rpc3BsYXknLCAnbm9uZScpOwogICAgICAgICAgICAgICAgICAgIC8vIFN3YXAgdGhlIHR3byBjYW52YXNlcy4KICAgICAgICAgICAgICAgICAgICBbdGhpcy5jYW52YXMsIHRoaXMuY2FudmFzQnVmZmVyXSA9IFt0aGlzLmNhbnZhc0J1ZmZlciwgdGhpcy5jYW52YXNdOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBsZXQgZG93bmxvYWRDb250ZXh0ID0gdGhpcy5kb3dubG9hZENhbnZhcy5nZXRDb250ZXh0KCcyZCcpOwogICAgICAgICAgICAgICAgZG93bmxvYWRDb250ZXh0LmNsZWFyUmVjdCgwLCAwLCB0aGlzLmRvd25sb2FkQ2FudmFzLndpZHRoLCB0aGlzLmRvd25sb2FkQ2FudmFzLmhlaWdodCk7CiAgICAgICAgICAgICAgICBkb3dubG9hZENvbnRleHQuZHJhd0ltYWdlKGltYWdlLCAwLCAwLCB0aGlzLmRvd25sb2FkQ2FudmFzLndpZHRoLCB0aGlzLmRvd25sb2FkQ2FudmFzLmhlaWdodCk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGltYWdlLm9uZXJyb3IgPSAoKSA9PiB7CiAgICAgICAgICAgICAgICBsZXQgYmxvYiA9IG5ldyBCbG9iKFtzdmdYbWxdLCB7IHR5cGU6ICdpbWFnZS9zdmcreG1sO2NoYXJzZXQ9dXRmLTgnIH0pOwogICAgICAgICAgICAgICAgaW1hZ2Uuc3JjID0gVVJMLmNyZWF0ZU9iamVjdFVSTChibG9iKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgaW1hZ2Uuc3JjID0KICAgICAgICAgICAgICAgICdkYXRhOmltYWdlL3N2Zyt4bWw7Y2hhcnNldD11dGYtOCwnICsgZW5jb2RlVVJJQ29tcG9uZW50KHN2Z1htbCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEhhbmRsZXMgY2hhbmdlcyBpbiB6b29taW5nL3Bhbm5pbmcuIFNob3VsZCBiZSBjYWxsZWQgZnJvbSB0aGUgbWFpbiBzdmcKICAgICAgICAgKiB0byBub3RpZnkgdGhhdCBhIHpvb20vcGFuIHdhcyBwZXJmb3JtZWQgYW5kIHRoaXMgbWluaW1hcCB3aWxsIHVwZGF0ZSBpdCdzCiAgICAgICAgICogdmlld3BvaW50IHJlY3RhbmdsZS4KICAgICAgICAgKgogICAgICAgICAqIEBwYXJhbSB0cmFuc2xhdGUgVGhlIHRyYW5zbGF0ZSB2ZWN0b3IsIG9yIG5vbmUgdG8gdXNlIHRoZSBsYXN0IHVzZWQgb25lLgogICAgICAgICAqIEBwYXJhbSBzY2FsZSBUaGUgc2NhbGluZyBmYWN0b3IsIG9yIG5vbmUgdG8gdXNlIHRoZSBsYXN0IHVzZWQgb25lLgogICAgICAgICAqLwogICAgICAgIHpvb20odHJhbnNmb3JtKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnNjYWxlTWluaW1hcCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBTY2VuZSBpcyBub3QgcmVhZHkgeWV0LgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgbmV3IHRyYW5zbGF0ZSBhbmQgc2NhbGUgcGFyYW1zLCBvbmx5IGlmIHNwZWNpZmllZC4KICAgICAgICAgICAgaWYgKHRyYW5zZm9ybSkgewogICAgICAgICAgICAgICAgdGhpcy50cmFuc2xhdGUgPSBbdHJhbnNmb3JtLngsIHRyYW5zZm9ybS55XTsKICAgICAgICAgICAgICAgIHRoaXMuc2NhbGVNYWluID0gdHJhbnNmb3JtLms7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSBsb2NhdGlvbiBvZiB0aGUgdmlld3BvaW50IHJlY3RhbmdsZS4KICAgICAgICAgICAgbGV0IHN2Z1JlY3QgPSB0aGlzLnN2Zy5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAgICAgbGV0ICR2aWV3cG9pbnQgPSBzZWxlY3QodGhpcy52aWV3cG9pbnQpOwogICAgICAgICAgICB0aGlzLnZpZXdwb2ludENvb3JkLnggPQogICAgICAgICAgICAgICAgKC10aGlzLnRyYW5zbGF0ZVswXSAqIHRoaXMuc2NhbGVNaW5pbWFwKSAvIHRoaXMuc2NhbGVNYWluOwogICAgICAgICAgICB0aGlzLnZpZXdwb2ludENvb3JkLnkgPQogICAgICAgICAgICAgICAgKC10aGlzLnRyYW5zbGF0ZVsxXSAqIHRoaXMuc2NhbGVNaW5pbWFwKSAvIHRoaXMuc2NhbGVNYWluOwogICAgICAgICAgICBsZXQgdmlld3BvaW50V2lkdGggPSAoc3ZnUmVjdC53aWR0aCAqIHRoaXMuc2NhbGVNaW5pbWFwKSAvIHRoaXMuc2NhbGVNYWluOwogICAgICAgICAgICBsZXQgdmlld3BvaW50SGVpZ2h0ID0gKHN2Z1JlY3QuaGVpZ2h0ICogdGhpcy5zY2FsZU1pbmltYXApIC8gdGhpcy5zY2FsZU1haW47CiAgICAgICAgICAgICR2aWV3cG9pbnQKICAgICAgICAgICAgICAgIC5hdHRyKCd4JywgdGhpcy52aWV3cG9pbnRDb29yZC54KQogICAgICAgICAgICAgICAgLmF0dHIoJ3knLCB0aGlzLnZpZXdwb2ludENvb3JkLnkpCiAgICAgICAgICAgICAgICAuYXR0cignd2lkdGgnLCB2aWV3cG9pbnRXaWR0aCkKICAgICAgICAgICAgICAgIC5hdHRyKCdoZWlnaHQnLCB2aWV3cG9pbnRIZWlnaHQpOwogICAgICAgICAgICAvLyBTaG93L2hpZGUgdGhlIG1pbmltYXAgZGVwZW5kaW5nIG9uIHRoZSB2aWV3cG9pbnQgYXJlYSBhcyBmcmFjdGlvbiBvZiB0aGUKICAgICAgICAgICAgLy8gd2hvbGUgbWluaW1hcC4KICAgICAgICAgICAgbGV0IG1hcFdpZHRoID0gdGhpcy5taW5pbWFwU2l6ZS53aWR0aDsKICAgICAgICAgICAgbGV0IG1hcEhlaWdodCA9IHRoaXMubWluaW1hcFNpemUuaGVpZ2h0OwogICAgICAgICAgICBsZXQgeCA9IHRoaXMudmlld3BvaW50Q29vcmQueDsKICAgICAgICAgICAgbGV0IHkgPSB0aGlzLnZpZXdwb2ludENvb3JkLnk7CiAgICAgICAgICAgIGxldCB3ID0gTWF0aC5taW4oTWF0aC5tYXgoMCwgeCArIHZpZXdwb2ludFdpZHRoKSwgbWFwV2lkdGgpIC0KICAgICAgICAgICAgICAgIE1hdGgubWluKE1hdGgubWF4KDAsIHgpLCBtYXBXaWR0aCk7CiAgICAgICAgICAgIGxldCBoID0gTWF0aC5taW4oTWF0aC5tYXgoMCwgeSArIHZpZXdwb2ludEhlaWdodCksIG1hcEhlaWdodCkgLQogICAgICAgICAgICAgICAgTWF0aC5taW4oTWF0aC5tYXgoMCwgeSksIG1hcEhlaWdodCk7CiAgICAgICAgICAgIGxldCBmcmFjSW50ZXJzZWN0ID0gKHcgKiBoKSAvIChtYXBXaWR0aCAqIG1hcEhlaWdodCk7CiAgICAgICAgICAgIGlmIChmcmFjSW50ZXJzZWN0IDwgRlJBQ19WSUVXUE9JTlRfQVJFQSkgewogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLmNsYXNzTGlzdC5yZW1vdmUoJ2hpZGRlbicpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLmNsYXNzTGlzdC5hZGQoJ2hpZGRlbicpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmR3JhcGhNaW5pbWFwID0gY2xhc3MgVGZHcmFwaE1pbmltYXAgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgLyoqCiAgICAgICAgICogSW5pdGlhbGl6ZXMgdGhlIG1pbmltYXAgYW5kIHJldHVybnMgYSBtaW5pbWFwIG9iamVjdCB0byBub3RpZnkgd2hlbgogICAgICAgICAqIHRoaW5ncyB1cGRhdGUuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gc3ZnIFRoZSBtYWluIHN2ZyBlbGVtZW50LgogICAgICAgICAqIEBwYXJhbSB6b29tRyBUaGUgc3ZnIGdyb3VwIHVzZWQgZm9yIHBhbm5pbmcgYW5kIHpvb21pbmcgdGhlIG1haW4gc3ZnLgogICAgICAgICAqIEBwYXJhbSBtYWluWm9vbSBUaGUgbWFpbiB6b29tIGJlaGF2aW9yLgogICAgICAgICAqIEBwYXJhbSBtYXhXQW5kSCBUaGUgbWF4aW11bSB3aWR0aC9oZWlnaHQgZm9yIHRoZSBtaW5pbWFwLgogICAgICAgICAqIEBwYXJhbSBsYWJlbFBhZGRpbmcgUGFkZGluZyBpbiBwaXhlbHMgZHVlIHRvIHRoZSBtYWluIGdyYXBoIGxhYmVscy4KICAgICAgICAgKi8KICAgICAgICBpbml0KHN2Zywgem9vbUcsIG1haW5ab29tLCBtYXhXQW5kSCwgbGFiZWxQYWRkaW5nKSB7CiAgICAgICAgICAgIHJldHVybiBuZXcgTWluaW1hcChzdmcsIHpvb21HLCBtYWluWm9vbSwgdGhpcywgbWF4V0FuZEgsIGxhYmVsUGFkZGluZyk7CiAgICAgICAgfQogICAgfTsKICAgIFRmR3JhcGhNaW5pbWFwLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB3aGl0ZTsKICAgICAgICB0cmFuc2l0aW9uOiBvcGFjaXR5IDAuM3MgbGluZWFyOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBhdXRvOwogICAgICB9CgogICAgICA6aG9zdCguaGlkZGVuKSB7CiAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICBwb2ludGVyLWV2ZW50czogbm9uZTsKICAgICAgfQoKICAgICAgY2FudmFzIHsKICAgICAgICBib3JkZXI6IDFweCBzb2xpZCAjOTk5OwogICAgICB9CgogICAgICByZWN0IHsKICAgICAgICBmaWxsOiB3aGl0ZTsKICAgICAgICBzdHJva2U6ICMxMTExMTE7CiAgICAgICAgc3Ryb2tlLXdpZHRoOiAxcHg7CiAgICAgICAgZmlsbC1vcGFjaXR5OiAwOwogICAgICAgIGZpbHRlcjogdXJsKCNtaW5pbWFwRHJvcFNoYWRvdyk7CiAgICAgICAgY3Vyc29yOiBtb3ZlOwogICAgICB9CgogICAgICBzdmcgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgfQogICAgPC9zdHlsZT4KICAgIDxzdmc+CiAgICAgIDxkZWZzPgogICAgICAgIDxmaWx0ZXIKICAgICAgICAgIGlkPSJtaW5pbWFwRHJvcFNoYWRvdyIKICAgICAgICAgIHg9Ii0yMCUiCiAgICAgICAgICB5PSItMjAlIgogICAgICAgICAgd2lkdGg9IjE1MCUiCiAgICAgICAgICBoZWlnaHQ9IjE1MCUiCiAgICAgICAgPgogICAgICAgICAgPGZlT2Zmc2V0IHJlc3VsdD0ib2ZmT3V0IiBpbj0iU291cmNlR3JhcGhpYyIgZHg9IjEiIGR5PSIxIj48L2ZlT2Zmc2V0PgogICAgICAgICAgPGZlQ29sb3JNYXRyaXgKICAgICAgICAgICAgcmVzdWx0PSJtYXRyaXhPdXQiCiAgICAgICAgICAgIGluPSJvZmZPdXQiCiAgICAgICAgICAgIHR5cGU9Im1hdHJpeCIKICAgICAgICAgICAgdmFsdWVzPSIwLjEgMCAwIDAgMCAwIDAuMSAwIDAgMCAwIDAgMC4xIDAgMCAwIDAgMCAwLjUgMCIKICAgICAgICAgID48L2ZlQ29sb3JNYXRyaXg+CiAgICAgICAgICA8ZmVHYXVzc2lhbkJsdXIKICAgICAgICAgICAgcmVzdWx0PSJibHVyT3V0IgogICAgICAgICAgICBpbj0ibWF0cml4T3V0IgogICAgICAgICAgICBzdGREZXZpYXRpb249IjIiCiAgICAgICAgICA+PC9mZUdhdXNzaWFuQmx1cj4KICAgICAgICAgIDxmZUJsZW5kIGluPSJTb3VyY2VHcmFwaGljIiBpbjI9ImJsdXJPdXQiIG1vZGU9Im5vcm1hbCI+PC9mZUJsZW5kPgogICAgICAgIDwvZmlsdGVyPgogICAgICA8L2RlZnM+CiAgICAgIDxyZWN0PjwvcmVjdD4KICAgIDwvc3ZnPgogICAgPGNhbnZhcyBjbGFzcz0iZmlyc3QiPjwvY2FudmFzPgogICAgPCEtLSBBZGRpdGlvbmFsIGNhbnZhcyB0byB1c2UgYXMgYnVmZmVyIHRvIGF2b2lkIGZsaWNrZXJpbmcgYmV0d2VlbiB1cGRhdGVzIC0tPgogICAgPGNhbnZhcyBjbGFzcz0ic2Vjb25kIj48L2NhbnZhcz4KICAgIDxjYW52YXMgY2xhc3M9ImRvd25sb2FkIj48L2NhbnZhcz4KICBgOwogICAgVGZHcmFwaE1pbmltYXAgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ncmFwaC1taW5pbWFwJykKICAgIF0sIFRmR3JhcGhNaW5pbWFwKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNvbnN0IHRlbXBsYXRlJGogPSBodG1sIGAKICA8c3R5bGU+CiAgICA6aG9zdCB7CiAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgIGZvbnQtc2l6ZTogMjBweDsKICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB3aWR0aDogMTAwJTsKICAgIH0KCiAgICAjc3ZnIHsKICAgICAgZmxleDogMTsKICAgICAgZm9udC1mYW1pbHk6IFJvYm90bywgc2Fucy1zZXJpZjsKICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICB3aWR0aDogMTAwJTsKICAgIH0KCiAgICAjaGlkZGVuIHsKICAgICAgcG9zaXRpb246IGZpeGVkOwogICAgICB0b3A6IDBweDsKICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgfQoKICAgIC8qIC0tLSBOb2RlIGFuZCBhbm5vdGF0aW9uLW5vZGUgZm9yIE1ldGFub2RlIC0tLSAqLwoKICAgIC5tZXRhID4gLm5vZGVzaGFwZSA+IHJlY3QsCiAgICAubWV0YSA+IC5hbm5vdGF0aW9uLW5vZGUgPiByZWN0IHsKICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICBmaWxsOiBoc2woMCwgMCUsIDcwJSk7CiAgICB9CiAgICAubm9kZS5tZXRhLmhpZ2hsaWdodGVkID4gLm5vZGVzaGFwZSA+IHJlY3QsCiAgICAubm9kZS5tZXRhLmhpZ2hsaWdodGVkID4gLmFubm90YXRpb24tbm9kZSA+IHJlY3QgewogICAgICBzdHJva2Utd2lkdGg6IDI7CiAgICB9CiAgICAuYW5ub3RhdGlvbi5tZXRhLmhpZ2hsaWdodGVkID4gLm5vZGVzaGFwZSA+IHJlY3QsCiAgICAuYW5ub3RhdGlvbi5tZXRhLmhpZ2hsaWdodGVkID4gLmFubm90YXRpb24tbm9kZSA+IHJlY3QgewogICAgICBzdHJva2Utd2lkdGg6IDE7CiAgICB9CiAgICAubWV0YS5zZWxlY3RlZCA+IC5ub2Rlc2hhcGUgPiByZWN0LAogICAgLm1ldGEuc2VsZWN0ZWQgPiAuYW5ub3RhdGlvbi1ub2RlID4gcmVjdCB7CiAgICAgIHN0cm9rZTogcmVkOwogICAgICBzdHJva2Utd2lkdGg6IDI7CiAgICB9CiAgICAubm9kZS5tZXRhLnNlbGVjdGVkLmV4cGFuZGVkID4gLm5vZGVzaGFwZSA+IHJlY3QsCiAgICAubm9kZS5tZXRhLnNlbGVjdGVkLmV4cGFuZGVkID4gLmFubm90YXRpb24tbm9kZSA+IHJlY3QgewogICAgICBzdHJva2U6IHJlZDsKICAgICAgc3Ryb2tlLXdpZHRoOiAzOwogICAgfQogICAgLmFubm90YXRpb24ubWV0YS5zZWxlY3RlZCA+IC5ub2Rlc2hhcGUgPiByZWN0LAogICAgLmFubm90YXRpb24ubWV0YS5zZWxlY3RlZCA+IC5hbm5vdGF0aW9uLW5vZGUgPiByZWN0IHsKICAgICAgc3Ryb2tlOiByZWQ7CiAgICAgIHN0cm9rZS13aWR0aDogMjsKICAgIH0KICAgIC5ub2RlLm1ldGEuc2VsZWN0ZWQuZXhwYW5kZWQuaGlnaGxpZ2h0ZWQgPiAubm9kZXNoYXBlID4gcmVjdCwKICAgIC5ub2RlLm1ldGEuc2VsZWN0ZWQuZXhwYW5kZWQuaGlnaGxpZ2h0ZWQgPiAuYW5ub3RhdGlvbi1ub2RlID4gcmVjdCB7CiAgICAgIHN0cm9rZTogcmVkOwogICAgICBzdHJva2Utd2lkdGg6IDQ7CiAgICB9CgogICAgLmZhZGVkLAogICAgLmZhZGVkIHJlY3QsCiAgICAuZmFkZWQgZWxsaXBzZSwKICAgIC5mYWRlZCBwYXRoLAogICAgLmZhZGVkIHVzZSwKICAgICNyZWN0SGF0Y2ggbGluZSwKICAgICNlbGxpcHNlSGF0Y2ggbGluZSB7CiAgICAgIGNvbG9yOiAjZTBkNGIzICFpbXBvcnRhbnQ7CiAgICAgIGZpbGw6IHdoaXRlOwogICAgICBzdHJva2U6ICNlMGQ0YjMgIWltcG9ydGFudDsKICAgIH0KCiAgICAuZmFkZWQgcGF0aCB7CiAgICAgIHN0cm9rZS13aWR0aDogMXB4ICFpbXBvcnRhbnQ7CiAgICB9CgogICAgLmZhZGVkIHJlY3QgewogICAgICBmaWxsOiB1cmwoI3JlY3RIYXRjaCkgIWltcG9ydGFudDsKICAgIH0KCiAgICAuZmFkZWQgZWxsaXBzZSwKICAgIC5mYWRlZCB1c2UgewogICAgICBmaWxsOiB1cmwoI2VsbGlwc2VIYXRjaCkgIWltcG9ydGFudDsKICAgIH0KCiAgICAuZmFkZWQgdGV4dCB7CiAgICAgIG9wYWNpdHk6IDA7CiAgICB9CgogICAgLyogUnVsZXMgdXNlZCBmb3IgaW5wdXQtdHJhY2luZy4gKi8KICAgIC5pbnB1dC1oaWdobGlnaHQgPiAqID4gcmVjdCwKICAgIC5pbnB1dC1oaWdobGlnaHQgPiAqID4gZWxsaXBzZSwKICAgIC5pbnB1dC1oaWdobGlnaHQgPiAqID4gdXNlIHsKICAgICAgZmlsbDogd2hpdGU7CiAgICAgIHN0cm9rZTogI2ZmOTgwMCAhaW1wb3J0YW50OwogICAgfQoKICAgIC8qICAtIEZhZGVkIG5vbi1pbnB1dCBzdHlsaW5nICovCiAgICAubm9uLWlucHV0ID4gKiA+IHJlY3QsCi5ub24taW5wdXQgPiAqID4gZWxsaXBzZSwKLm5vbi1pbnB1dCA+ICogPiB1c2UsCi8qIEZvciBDb25zdCBub2Rlcy4gKi8KLm5vbi1pbnB1dCA+ICogPiAuY29uc3RhbnQ6bm90KFtjbGFzcyo9ImlucHV0LWhpZ2hsaWdodCJdKSA+CiAgLmFubm90YXRpb24tbm9kZSA+IGVsbGlwc2UsCi8qIEZvciBzdHlsaW5nIG9mIGFubm90YXRpb24gbm9kZXMgb2Ygbm9uLWlucHV0IG5vZGVzLiAqLwoubm9uLWlucHV0ID4gZyA+IC5hbm5vdGF0aW9uID4gLmFubm90YXRpb24tbm9kZSA+IHJlY3QgewogICAgICBzdHJva2U6ICNlMGQ0YjMgIWltcG9ydGFudDsKICAgICAgc3Ryb2tlLXdpZHRoOiBpbmhlcml0OwogICAgICBzdHJva2UtZGFzaGFycmF5OiBpbmhlcml0OwogICAgfQoKICAgIC5ub24taW5wdXQgcGF0aCB7CiAgICAgIHZpc2liaWxpdHk6IGhpZGRlbjsKICAgIH0KCiAgICAubm9uLWlucHV0ID4gLm5vZGVzaGFwZSA+IHJlY3QsCi5ub24taW5wdXQgPiAuYW5ub3RhdGlvbi1ub2RlID4gcmVjdCwKLyogRm9yIHN0eWxpbmcgb2YgYW5ub3RhdGlvbiBub2RlcyBvZiBub24taW5wdXQgbm9kZXMuICovCi5ub24taW5wdXQgPiBnID4gLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1ub2RlID4gcmVjdCB7CiAgICAgIGZpbGw6IHVybCgjcmVjdEhhdGNoKSAhaW1wb3J0YW50OwogICAgfQoKICAgIC5ub24taW5wdXQgZWxsaXBzZSwKICAgIC5ub24taW5wdXQgdXNlIHsKICAgICAgZmlsbDogdXJsKCNlbGxpcHNlSGF0Y2gpICFpbXBvcnRhbnQ7CiAgICB9CgogICAgLm5vbi1pbnB1dCA+IHRleHQgewogICAgICBvcGFjaXR5OiAwOwogICAgfQoKICAgIC5ub24taW5wdXQgLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1lZGdlIHsKICAgICAgbWFya2VyLWVuZDogdXJsKCNhbm5vdGF0aW9uLWFycm93aGVhZC1mYWRlZCk7CiAgICB9CgogICAgLm5vbi1pbnB1dCAuYW5ub3RhdGlvbiA+IC5hbm5vdGF0aW9uLWVkZ2UucmVmbGluZSB7CiAgICAgIG1hcmtlci1zdGFydDogdXJsKCNyZWYtYW5ub3RhdGlvbi1hcnJvd2hlYWQtZmFkZWQpOwogICAgfQoKICAgIC8qIElucHV0IGVkZ2VzLiAqLwogICAgLmlucHV0LWVkZ2UtaGlnaGxpZ2h0ID4gdGV4dCB7CiAgICAgIGZpbGw6IGJsYWNrICFpbXBvcnRhbnQ7CiAgICB9CiAgICAuaW5wdXQtaGlnaGxpZ2h0ID4gLmluLWFubm90YXRpb25zID4gLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1lZGdlLAogICAgLmlucHV0LWhpZ2hsaWdodC1zZWxlY3RlZAogICAgICA+IC5pbi1hbm5vdGF0aW9ucwogICAgICA+IC5hbm5vdGF0aW9uCiAgICAgID4gLmFubm90YXRpb24tZWRnZSB7CiAgICAgIHN0cm9rZTogIzk5OSAhaW1wb3J0YW50OwogICAgfQoKICAgIC8qIE5vbi1pbnB1dCBlZGdlcy4gKi8KICAgIC5ub24taW5wdXQtZWRnZS1oaWdobGlnaHQsCi5ub24taW5wdXQgPiBnID4gLmFubm90YXRpb24gPiBwYXRoLAovKiBBbm5vdGF0aW9uIHN0eWxlcyAobGFiZWwgYW5kIGVkZ2VzIHJlc3BlY3RpdmVseSkuICovCi5ub24taW5wdXQgPiBnID4KLmFubm90YXRpb246bm90KC5pbnB1dC1oaWdobGlnaHQpOm5vdCguaW5wdXQtaGlnaGxpZ2h0LXNlbGVjdGVkKSA+Ci5hbm5vdGF0aW9uLWxhYmVsCi8qLmFubm90YXRpb24tZWRnZSovIHsKICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgfQoKICAgIC8qIC0tLSBPcCBOb2RlIC0tLSAqLwoKICAgIC5vcCA+IC5ub2Rlc2hhcGUgPiAubm9kZWNvbG9ydGFyZ2V0LAogICAgLm9wID4gLmFubm90YXRpb24tbm9kZSA+IC5ub2RlY29sb3J0YXJnZXQgewogICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgIGZpbGw6ICNmZmY7CiAgICAgIHN0cm9rZTogI2NjYzsKICAgIH0KCiAgICAub3Auc2VsZWN0ZWQgPiAubm9kZXNoYXBlID4gLm5vZGVjb2xvcnRhcmdldCwKICAgIC5vcC5zZWxlY3RlZCA+IC5hbm5vdGF0aW9uLW5vZGUgPiAubm9kZWNvbG9ydGFyZ2V0IHsKICAgICAgc3Ryb2tlOiByZWQ7CiAgICAgIHN0cm9rZS13aWR0aDogMjsKICAgIH0KCiAgICAub3AuaGlnaGxpZ2h0ZWQgPiAubm9kZXNoYXBlID4gLm5vZGVjb2xvcnRhcmdldCwKICAgIC5vcC5oaWdobGlnaHRlZCA+IC5hbm5vdGF0aW9uLW5vZGUgPiAubm9kZWNvbG9ydGFyZ2V0IHsKICAgICAgc3Ryb2tlLXdpZHRoOiAyOwogICAgfQoKICAgIC8qIC0tLSBTZXJpZXMgTm9kZSAtLS0gKi8KCiAgICAvKiBCeSBkZWZhdWx0LCBkb24ndCBzaG93IHRoZSBzZXJpZXMgYmFja2dyb3VuZCA8cmVjdD4uICovCiAgICAuc2VyaWVzID4gLm5vZGVzaGFwZSA+IHJlY3QgewogICAgICBmaWxsOiBoc2woMCwgMCUsIDcwJSk7CiAgICAgIGZpbGwtb3BhY2l0eTogMDsKICAgICAgc3Ryb2tlLWRhc2hhcnJheTogNSwgNTsKICAgICAgc3Ryb2tlLW9wYWNpdHk6IDA7CiAgICAgIGN1cnNvcjogcG9pbnRlcjsKICAgIH0KCiAgICAvKiBPbmNlIGV4cGFuZGVkLCBzaG93IHRoZSBzZXJpZXMgYmFja2dyb3VuZCA8cmVjdD4gYW5kIGhpZGUgdGhlIDx1c2U+LiAqLwogICAgLnNlcmllcy5leHBhbmRlZCA+IC5ub2Rlc2hhcGUgPiByZWN0IHsKICAgICAgZmlsbC1vcGFjaXR5OiAwLjE1OwogICAgICBzdHJva2U6IGhzbCgwLCAwJSwgNzAlKTsKICAgICAgc3Ryb2tlLW9wYWNpdHk6IDE7CiAgICB9CiAgICAuc2VyaWVzLmV4cGFuZGVkID4gLm5vZGVzaGFwZSA+IHVzZSB7CiAgICAgIHZpc2liaWxpdHk6IGhpZGRlbjsKICAgIH0KCiAgICAvKioKICogVE9ETzogU2ltcGxpZnkgdGhpcyBieSBhcHBseWluZyBhIHN0YWJsZSBjbGFzcyBuYW1lIHRvIGFsbCA8Zz4KICogZWxlbWVudHMgdGhhdCBjdXJyZW50bHkgaGF2ZSBlaXRoZXIgdGhlIG5vZGVzaGFwZSBvciBhbm5vdGF0aW9uLW5vZGUgY2xhc3Nlcy4KICovCiAgICAuc2VyaWVzID4gLm5vZGVzaGFwZSA+IHVzZSwKICAgIC5zZXJpZXMgPiAuYW5ub3RhdGlvbi1ub2RlID4gdXNlIHsKICAgICAgc3Ryb2tlOiAjY2NjOwogICAgfQogICAgLnNlcmllcy5oaWdobGlnaHRlZCA+IC5ub2Rlc2hhcGUgPiB1c2UsCiAgICAuc2VyaWVzLmhpZ2hsaWdodGVkID4gLmFubm90YXRpb24tbm9kZSA+IHVzZSB7CiAgICAgIHN0cm9rZS13aWR0aDogMjsKICAgIH0KICAgIC5zZXJpZXMuc2VsZWN0ZWQgPiAubm9kZXNoYXBlID4gdXNlLAogICAgLnNlcmllcy5zZWxlY3RlZCA+IC5hbm5vdGF0aW9uLW5vZGUgPiB1c2UgewogICAgICBzdHJva2U6IHJlZDsKICAgICAgc3Ryb2tlLXdpZHRoOiAyOwogICAgfQoKICAgIC5zZXJpZXMuc2VsZWN0ZWQgPiAubm9kZXNoYXBlID4gcmVjdCB7CiAgICAgIHN0cm9rZTogcmVkOwogICAgICBzdHJva2Utd2lkdGg6IDI7CiAgICB9CgogICAgLmFubm90YXRpb24uc2VyaWVzLnNlbGVjdGVkID4gLmFubm90YXRpb24tbm9kZSA+IHVzZSB7CiAgICAgIHN0cm9rZTogcmVkOwogICAgICBzdHJva2Utd2lkdGg6IDI7CiAgICB9CgogICAgLyogLS0tIEJyaWRnZSBOb2RlIC0tLSAqLwogICAgLmJyaWRnZSA+IC5ub2Rlc2hhcGUgPiByZWN0IHsKICAgICAgc3Ryb2tlOiAjZjBmOwogICAgICBvcGFjaXR5OiAwLjI7CiAgICAgIGRpc3BsYXk6IG5vbmU7CiAgICB9CgogICAgLyogLS0tIFN0cnVjdHVyYWwgRWxlbWVudHMgLS0tICovCiAgICAuZWRnZSA+IHBhdGguZWRnZWxpbmUuc3RydWN0dXJhbCB7CiAgICAgIHN0cm9rZTogI2YwZjsKICAgICAgb3BhY2l0eTogMC4yOwogICAgICBkaXNwbGF5OiBub25lOwogICAgfQoKICAgIC8qIFJlZmVyZW5jZSBFZGdlICovCiAgICAuZWRnZSA+IHBhdGguZWRnZWxpbmUucmVmZXJlbmNlZWRnZSB7CiAgICAgIHN0cm9rZTogI2ZmYjc0ZDsKICAgICAgb3BhY2l0eTogMTsKICAgIH0KCiAgICAvKiAtLS0gU2VyaWVzIE5vZGVzIC0tLSAqLwoKICAgIC8qIEhpZGUgdGhlIHJlY3QgZm9yIGEgc2VyaWVzJyBhbm5vdGF0aW9uLiAqLwogICAgLnNlcmllcyA+IC5hbm5vdGF0aW9uLW5vZGUgPiByZWN0IHsKICAgICAgZGlzcGxheTogbm9uZTsKICAgIH0KCiAgICAvKiAtLS0gTm9kZSBsYWJlbCAtLS0gKi8KCiAgICAubm9kZSA+IHRleHQubm9kZWxhYmVsIHsKICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICBmaWxsOiAjNDQ0OwogICAgfQoKICAgIC5tZXRhLmV4cGFuZGVkID4gdGV4dC5ub2RlbGFiZWwgewogICAgICBmb250LXNpemU6IDlweDsKICAgIH0KCiAgICAuc2VyaWVzID4gdGV4dC5ub2RlbGFiZWwgewogICAgICBmb250LXNpemU6IDhweDsKICAgIH0KCiAgICAub3AgPiB0ZXh0Lm5vZGVsYWJlbCB7CiAgICAgIGZvbnQtc2l6ZTogNnB4OwogICAgfQoKICAgIC5icmlkZ2UgPiB0ZXh0Lm5vZGVsYWJlbCB7CiAgICAgIGRpc3BsYXk6IG5vbmU7CiAgICB9CgogICAgLm5vZGUubWV0YS5leHBhbmRlZCA+IHRleHQubm9kZWxhYmVsIHsKICAgICAgY3Vyc29yOiBub3JtYWw7CiAgICB9CgogICAgLmFubm90YXRpb24ubWV0YS5oaWdobGlnaHRlZCA+IHRleHQuYW5ub3RhdGlvbi1sYWJlbCB7CiAgICAgIGZpbGw6ICM1MGEzZjc7CiAgICB9CgogICAgLmFubm90YXRpb24ubWV0YS5zZWxlY3RlZCA+IHRleHQuYW5ub3RhdGlvbi1sYWJlbCB7CiAgICAgIGZpbGw6ICM0Mjg1ZjQ7CiAgICB9CgogICAgLyogLS0tIEFubm90YXRpb24gLS0tICovCgogICAgLyogb25seSBhcHBsaWVkIGZvciBhbm5vdGF0aW9ucyB0aGF0IGFyZSBub3Qgc3VtbWFyeSBvciBjb25zdGFudC4KKC5zdW1tYXJ5LCAuY29uc3RhbnQgZ2V0cyBvdmVycmlkZGVuIGJlbG93KSAqLwogICAgLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1ub2RlID4gKiB7CiAgICAgIHN0cm9rZS13aWR0aDogMC41OwogICAgICBzdHJva2UtZGFzaGFycmF5OiAxLCAxOwogICAgfQoKICAgIC5hbm5vdGF0aW9uLnN1bW1hcnkgPiAuYW5ub3RhdGlvbi1ub2RlID4gKiwKICAgIC5hbm5vdGF0aW9uLmNvbnN0YW50ID4gLmFubm90YXRpb24tbm9kZSA+ICogewogICAgICBzdHJva2Utd2lkdGg6IDE7CiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IG5vbmU7CiAgICB9CgogICAgLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1lZGdlIHsKICAgICAgZmlsbDogbm9uZTsKICAgICAgc3Ryb2tlOiAjYWFhOwogICAgICBzdHJva2Utd2lkdGg6IDAuNTsKICAgICAgbWFya2VyLWVuZDogdXJsKCNhbm5vdGF0aW9uLWFycm93aGVhZCk7CiAgICB9CgogICAgLmZhZGVkIC5hbm5vdGF0aW9uID4gLmFubm90YXRpb24tZWRnZSB7CiAgICAgIG1hcmtlci1lbmQ6IHVybCgjYW5ub3RhdGlvbi1hcnJvd2hlYWQtZmFkZWQpOwogICAgfQoKICAgIC5hbm5vdGF0aW9uID4gLmFubm90YXRpb24tZWRnZS5yZWZsaW5lIHsKICAgICAgbWFya2VyLXN0YXJ0OiB1cmwoI3JlZi1hbm5vdGF0aW9uLWFycm93aGVhZCk7CiAgICB9CgogICAgLmZhZGVkIC5hbm5vdGF0aW9uID4gLmFubm90YXRpb24tZWRnZS5yZWZsaW5lIHsKICAgICAgbWFya2VyLXN0YXJ0OiB1cmwoI3JlZi1hbm5vdGF0aW9uLWFycm93aGVhZC1mYWRlZCk7CiAgICB9CgogICAgLmFubm90YXRpb24gPiAuYW5ub3RhdGlvbi1jb250cm9sLWVkZ2UgewogICAgICBzdHJva2UtZGFzaGFycmF5OiAxLCAxOwogICAgfQoKICAgICNhbm5vdGF0aW9uLWFycm93aGVhZCB7CiAgICAgIGZpbGw6ICNhYWE7CiAgICB9CgogICAgI2Fubm90YXRpb24tYXJyb3doZWFkLWZhZGVkIHsKICAgICAgZmlsbDogI2UwZDRiMzsKICAgIH0KCiAgICAjcmVmLWFubm90YXRpb24tYXJyb3doZWFkIHsKICAgICAgZmlsbDogI2FhYTsKICAgIH0KCiAgICAjcmVmLWFubm90YXRpb24tYXJyb3doZWFkLWZhZGVkIHsKICAgICAgZmlsbDogI2UwZDRiMzsKICAgIH0KCiAgICAuYW5ub3RhdGlvbiA+IC5hbm5vdGF0aW9uLWxhYmVsIHsKICAgICAgZm9udC1zaXplOiA1cHg7CiAgICAgIGN1cnNvcjogcG9pbnRlcjsKICAgIH0KICAgIC5hbm5vdGF0aW9uID4gLmFubm90YXRpb24tbGFiZWwuYW5ub3RhdGlvbi1lbGxpcHNpcyB7CiAgICAgIGN1cnNvcjogZGVmYXVsdDsKICAgIH0KCiAgICAvKiBIaWRlIGFubm90YXRpb25zIG9uIGV4cGFuZGVkIG1ldGEgbm9kZXMgc2luY2UgdGhleSdyZSByZWR1bmRhbnQuICovCiAgICAuZXhwYW5kZWQgPiAuaW4tYW5ub3RhdGlvbnMsCiAgICAuZXhwYW5kZWQgPiAub3V0LWFubm90YXRpb25zIHsKICAgICAgZGlzcGxheTogbm9uZTsKICAgIH0KCiAgICAvKiAtLS0gQW5ub3RhdGlvbjogQ29uc3RhbnQgLS0tICovCgogICAgLmNvbnN0YW50ID4gLmFubm90YXRpb24tbm9kZSA+IGVsbGlwc2UgewogICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgIGZpbGw6IHdoaXRlOwogICAgICBzdHJva2U6ICM4NDg0ODQ7CiAgICB9CgogICAgLmNvbnN0YW50LnNlbGVjdGVkID4gLmFubm90YXRpb24tbm9kZSA+IGVsbGlwc2UgewogICAgICBmaWxsOiB3aGl0ZTsKICAgICAgc3Ryb2tlOiByZWQ7CiAgICB9CgogICAgLmNvbnN0YW50LmhpZ2hsaWdodGVkID4gLmFubm90YXRpb24tbm9kZSA+IGVsbGlwc2UgewogICAgICBzdHJva2Utd2lkdGg6IDEuNTsKICAgIH0KCiAgICAvKiAtLS0gQW5ub3RhdGlvbjogU3VtbWFyeSAtLS0gKi8KCiAgICAuc3VtbWFyeSA+IC5hbm5vdGF0aW9uLW5vZGUgPiBlbGxpcHNlIHsKICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgICBmaWxsOiAjZGI0NDM3OwogICAgICBzdHJva2U6ICNkYjQ0Mzc7CiAgICB9CgogICAgLnN1bW1hcnkuc2VsZWN0ZWQgPiAuYW5ub3RhdGlvbi1ub2RlID4gZWxsaXBzZSB7CiAgICAgIGZpbGw6ICNhNTI3MTQ7CiAgICAgIHN0cm9rZTogI2E1MjcxNDsKICAgIH0KCiAgICAuc3VtbWFyeS5oaWdobGlnaHRlZCA+IC5hbm5vdGF0aW9uLW5vZGUgPiBlbGxpcHNlIHsKICAgICAgc3Ryb2tlLXdpZHRoOiAxLjU7CiAgICB9CgogICAgLyogLS0tIEVkZ2UgLS0tICovCgogICAgLmVkZ2UgPiBwYXRoLmVkZ2VsaW5lIHsKICAgICAgZmlsbDogbm9uZTsKICAgICAgc3Ryb2tlOiAjYmJiOwogICAgICBzdHJva2UtbGluZWNhcDogcm91bmQ7CiAgICAgIHN0cm9rZS13aWR0aDogMC43NTsKICAgIH0KCiAgICAuZWRnZSAuc2VsZWN0YWJsZWVkZ2UgewogICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICB9CgogICAgLnNlbGVjdGVkZWRnZSA+IHBhdGguZWRnZWxpbmUgewogICAgICBjdXJzb3I6IGRlZmF1bHQ7CiAgICAgIHN0cm9rZTogI2YwMDsKICAgIH0KCiAgICAuZWRnZS5zZWxlY3RlZGVkZ2UgdGV4dCB7CiAgICAgIGZpbGw6ICMwMDA7CiAgICB9CgogICAgLyogTGFiZWxzIHNob3dpbmcgdGVuc29yIHNoYXBlcyBvbiBlZGdlcyAqLwogICAgLmVkZ2UgPiB0ZXh0IHsKICAgICAgZm9udC1zaXplOiAzLjVweDsKICAgICAgZmlsbDogIzY2NjsKICAgIH0KCiAgICAuZGF0YWZsb3ctYXJyb3doZWFkIHsKICAgICAgZmlsbDogI2JiYjsKICAgIH0KCiAgICAucmVmZXJlbmNlLWFycm93aGVhZCB7CiAgICAgIGZpbGw6ICNmZmI3NGQ7CiAgICB9CgogICAgLnNlbGVjdGVkLWFycm93aGVhZCB7CiAgICAgIGZpbGw6ICNmMDA7CiAgICB9CgogICAgLmVkZ2UgLmNvbnRyb2wtZGVwIHsKICAgICAgc3Ryb2tlLWRhc2hhcnJheTogMiwgMjsKICAgIH0KCiAgICAvKiAtLS0gR3JvdXAgbm9kZSBleHBhbmQvY29sbGFwc2UgYnV0dG9uIC0tLSAqLwoKICAgIC8qIEhpZGVzIGV4cGFuZC9jb2xsYXBzZSBidXR0b25zIHdoZW4gYSBub2RlIGlzbid0IGV4cGFuZGVkIG9yIGhpZ2hsaWdodGVkLiBVc2luZwogICBpbmNyZWRpYmx5IHNtYWxsIG9wYWNpdHkgc28gdGhhdCB0aGUgYm91bmRpbmcgYm94IG9mIHRoZSA8Zz4gcGFyZW50IHN0aWxsIHRha2VzCiAgIHRoaXMgY29udGFpbmVyIGludG8gYWNjb3VudCBldmVuIHdoZW4gaXQgaXNuJ3QgdmlzaWJsZSAqLwogICAgLm5vZGU6bm90KC5oaWdobGlnaHRlZCk6bm90KC5leHBhbmRlZCkgPiAubm9kZXNoYXBlID4gLmJ1dHRvbmNvbnRhaW5lciB7CiAgICAgIG9wYWNpdHk6IDAuMDE7CiAgICB9CiAgICAubm9kZS5oaWdobGlnaHRlZCA+IC5ub2Rlc2hhcGUgPiAuYnV0dG9uY29udGFpbmVyIHsKICAgICAgY3Vyc29yOiBwb2ludGVyOwogICAgfQogICAgLmJ1dHRvbmNpcmNsZSB7CiAgICAgIGZpbGw6ICNlNzgxMWQ7CiAgICB9CiAgICAuYnV0dG9uY2lyY2xlOmhvdmVyIHsKICAgICAgZmlsbDogI2I5NjcxNzsKICAgIH0KICAgIC5leHBhbmRidXR0b24sCiAgICAuY29sbGFwc2VidXR0b24gewogICAgICBzdHJva2U6IHdoaXRlOwogICAgfQogICAgLyogRG8gbm90IGxldCB0aGUgcGF0aCBlbGVtZW50cyBpbiB0aGUgYnV0dG9uIHRha2UgcG9pbnRlciBmb2N1cyAqLwogICAgLm5vZGUgPiAubm9kZXNoYXBlID4gLmJ1dHRvbmNvbnRhaW5lciA+IC5leHBhbmRidXR0b24sCiAgICAubm9kZSA+IC5ub2Rlc2hhcGUgPiAuYnV0dG9uY29udGFpbmVyID4gLmNvbGxhcHNlYnV0dG9uIHsKICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICB9CiAgICAvKiBPbmx5IHNob3cgdGhlIGV4cGFuZCBidXR0b24gd2hlbiBhIG5vZGUgaXMgY29sbGFwc2VkIGFuZCBvbmx5IHNob3cgdGhlCiAgIGNvbGxhcHNlIGJ1dHRvbiB3aGVuIGEgbm9kZSBpcyBleHBhbmRlZC4gKi8KICAgIC5ub2RlLmV4cGFuZGVkID4gLm5vZGVzaGFwZSA+IC5idXR0b25jb250YWluZXIgPiAuZXhwYW5kYnV0dG9uIHsKICAgICAgZGlzcGxheTogbm9uZTsKICAgIH0KICAgIC5ub2RlOm5vdCguZXhwYW5kZWQpID4gLm5vZGVzaGFwZSA+IC5idXR0b25jb250YWluZXIgPiAuY29sbGFwc2VidXR0b24gewogICAgICBkaXNwbGF5OiBub25lOwogICAgfQoKICAgIC5oZWFsdGgtcGlsbC1zdGF0cyB7CiAgICAgIGZvbnQtc2l6ZTogNHB4OwogICAgICB0ZXh0LWFuY2hvcjogbWlkZGxlOwogICAgfQoKICAgIC5oZWFsdGgtcGlsbCByZWN0IHsKICAgICAgZmlsdGVyOiB1cmwoI2hlYWx0aC1waWxsLXNoYWRvdyk7CiAgICAgIHJ4OiAzOwogICAgICByeTogMzsKICAgIH0KCiAgICAudGl0bGVDb250YWluZXIgewogICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIHRvcDogMjBweDsKICAgIH0KCiAgICAudGl0bGUsCiAgICAuYXV4VGl0bGUsCiAgICAuZnVuY3Rpb25MaWJyYXJ5VGl0bGUgewogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICB9CgogICAgI21pbmltYXAgewogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgIHJpZ2h0OiAyMHB4OwogICAgICBib3R0b206IDIwcHg7CiAgICB9CgogICAgLmNvbnRleHQtbWVudSB7CiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgZGlzcGxheTogbm9uZTsKICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2UyZTJlMjsKICAgICAgYm9yZGVyLXJhZGl1czogMnB4OwogICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgIG1pbi13aWR0aDogMTUwcHg7CiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICNkNGQ0ZDQ7CiAgICB9CgogICAgLmNvbnRleHQtbWVudSB1bCB7CiAgICAgIGxpc3Qtc3R5bGUtdHlwZTogbm9uZTsKICAgICAgbWFyZ2luOiAwOwogICAgICBwYWRkaW5nOiAwOwogICAgICBjdXJzb3I6IGRlZmF1bHQ7CiAgICB9CgogICAgLmNvbnRleHQtbWVudSB1bCBsaSB7CiAgICAgIHBhZGRpbmc6IDRweCAxNnB4OwogICAgfQoKICAgIC5jb250ZXh0LW1lbnUgdWwgbGk6aG92ZXIgewogICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZjM5MTNlOwogICAgICBjb2xvcjogd2hpdGU7CiAgICB9CiAgPC9zdHlsZT4KICA8ZGl2IGNsYXNzPSJ0aXRsZUNvbnRhaW5lciI+CiAgICA8ZGl2IGlkPSJ0aXRsZSIgY2xhc3M9InRpdGxlIj5NYWluIEdyYXBoPC9kaXY+CiAgICA8ZGl2IGlkPSJhdXhUaXRsZSIgY2xhc3M9ImF1eFRpdGxlIj5BdXhpbGlhcnkgTm9kZXM8L2Rpdj4KICAgIDxkaXYgaWQ9ImZ1bmN0aW9uTGlicmFyeVRpdGxlIiBjbGFzcz0iZnVuY3Rpb25MaWJyYXJ5VGl0bGUiPkZ1bmN0aW9uczwvZGl2PgogIDwvZGl2PgogIDxzdmcgaWQ9InN2ZyI+CiAgICA8ZGVmcz4KICAgICAgPCEtLSBBcnJvdyBoZWFkcyBmb3IgcmVmZXJlbmNlIGVkZ2UgcGF0aHMgb2YgZGlmZmVyZW50IHByZWRlZmluZWQgc2l6ZXMgcGVyIGNvbG9yLiAtLT4KICAgICAgPHBhdGgKICAgICAgICBpZD0icmVmZXJlbmNlLWFycm93aGVhZC1wYXRoIgogICAgICAgIGQ9Ik0gMCwwIEwgMTAsNSBMIDAsMTAgQyAzLDcgMywzIDAsMCIKICAgICAgPjwvcGF0aD4KICAgICAgPG1hcmtlcgogICAgICAgIGNsYXNzPSJyZWZlcmVuY2UtYXJyb3doZWFkIgogICAgICAgIGlkPSJyZWZlcmVuY2UtYXJyb3doZWFkLXNtYWxsIgogICAgICAgIHZpZXdCb3g9IjAgMCAxMCAxMCIKICAgICAgICBtYXJrZXJXaWR0aD0iNSIKICAgICAgICBtYXJrZXJIZWlnaHQ9IjUiCiAgICAgICAgcmVmWD0iMiIKICAgICAgICByZWZZPSI1IgogICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgIG1hcmtlclVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI3JlZmVyZW5jZS1hcnJvd2hlYWQtcGF0aCI+PC91c2U+CiAgICAgIDwvbWFya2VyPgogICAgICA8bWFya2VyCiAgICAgICAgY2xhc3M9InJlZmVyZW5jZS1hcnJvd2hlYWQiCiAgICAgICAgaWQ9InJlZmVyZW5jZS1hcnJvd2hlYWQtbWVkaXVtIgogICAgICAgIHZpZXdCb3g9IjAgMCAxMCAxMCIKICAgICAgICBtYXJrZXJXaWR0aD0iMTMiCiAgICAgICAgbWFya2VySGVpZ2h0PSIxMyIKICAgICAgICByZWZYPSIyIgogICAgICAgIHJlZlk9IjUiCiAgICAgICAgb3JpZW50PSJhdXRvLXN0YXJ0LXJldmVyc2UiCiAgICAgICAgbWFya2VyVW5pdHM9InVzZXJTcGFjZU9uVXNlIgogICAgICA+CiAgICAgICAgPHVzZSB4bGluazpocmVmPSIjcmVmZXJlbmNlLWFycm93aGVhZC1wYXRoIj48L3VzZT4KICAgICAgPC9tYXJrZXI+CiAgICAgIDxtYXJrZXIKICAgICAgICBjbGFzcz0icmVmZXJlbmNlLWFycm93aGVhZCIKICAgICAgICBpZD0icmVmZXJlbmNlLWFycm93aGVhZC1sYXJnZSIKICAgICAgICB2aWV3Qm94PSIwIDAgMTAgMTAiCiAgICAgICAgbWFya2VyV2lkdGg9IjE2IgogICAgICAgIG1hcmtlckhlaWdodD0iMTYiCiAgICAgICAgcmVmWD0iMiIKICAgICAgICByZWZZPSI1IgogICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgIG1hcmtlclVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI3JlZmVyZW5jZS1hcnJvd2hlYWQtcGF0aCI+PC91c2U+CiAgICAgIDwvbWFya2VyPgogICAgICA8bWFya2VyCiAgICAgICAgY2xhc3M9InJlZmVyZW5jZS1hcnJvd2hlYWQiCiAgICAgICAgaWQ9InJlZmVyZW5jZS1hcnJvd2hlYWQteGxhcmdlIgogICAgICAgIHZpZXdCb3g9IjAgMCAxMCAxMCIKICAgICAgICBtYXJrZXJXaWR0aD0iMjAiCiAgICAgICAgbWFya2VySGVpZ2h0PSIyMCIKICAgICAgICByZWZYPSIyIgogICAgICAgIHJlZlk9IjUiCiAgICAgICAgb3JpZW50PSJhdXRvLXN0YXJ0LXJldmVyc2UiCiAgICAgICAgbWFya2VyVW5pdHM9InVzZXJTcGFjZU9uVXNlIgogICAgICA+CiAgICAgICAgPHVzZSB4bGluazpocmVmPSIjcmVmZXJlbmNlLWFycm93aGVhZC1wYXRoIj48L3VzZT4KICAgICAgPC9tYXJrZXI+CgogICAgICA8IS0tIEFycm93IGhlYWRzIGZvciBkYXRhZmxvdyBlZGdlIHBhdGhzIG9mIGRpZmZlcmVudCBwcmVkZWZpbmVkIHNpemVzIHBlciBjb2xvci4gLS0+CiAgICAgIDxwYXRoCiAgICAgICAgaWQ9ImRhdGFmbG93LWFycm93aGVhZC1wYXRoIgogICAgICAgIGQ9Ik0gMCwwIEwgMTAsNSBMIDAsMTAgQyAzLDcgMywzIDAsMCIKICAgICAgPjwvcGF0aD4KICAgICAgPG1hcmtlcgogICAgICAgIGNsYXNzPSJkYXRhZmxvdy1hcnJvd2hlYWQiCiAgICAgICAgaWQ9ImRhdGFmbG93LWFycm93aGVhZC1zbWFsbCIKICAgICAgICB2aWV3Qm94PSIwIDAgMTAgMTAiCiAgICAgICAgbWFya2VyV2lkdGg9IjUiCiAgICAgICAgbWFya2VySGVpZ2h0PSI1IgogICAgICAgIHJlZlg9IjIiCiAgICAgICAgcmVmWT0iNSIKICAgICAgICBvcmllbnQ9ImF1dG8tc3RhcnQtcmV2ZXJzZSIKICAgICAgICBtYXJrZXJVbml0cz0idXNlclNwYWNlT25Vc2UiCiAgICAgID4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNkYXRhZmxvdy1hcnJvd2hlYWQtcGF0aCI+PC91c2U+CiAgICAgIDwvbWFya2VyPgogICAgICA8bWFya2VyCiAgICAgICAgY2xhc3M9ImRhdGFmbG93LWFycm93aGVhZCIKICAgICAgICBpZD0iZGF0YWZsb3ctYXJyb3doZWFkLW1lZGl1bSIKICAgICAgICB2aWV3Qm94PSIwIDAgMTAgMTAiCiAgICAgICAgbWFya2VyV2lkdGg9IjEzIgogICAgICAgIG1hcmtlckhlaWdodD0iMTMiCiAgICAgICAgcmVmWD0iMiIKICAgICAgICByZWZZPSI1IgogICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgIG1hcmtlclVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI2RhdGFmbG93LWFycm93aGVhZC1wYXRoIj48L3VzZT4KICAgICAgPC9tYXJrZXI+CiAgICAgIDxtYXJrZXIKICAgICAgICBjbGFzcz0iZGF0YWZsb3ctYXJyb3doZWFkIgogICAgICAgIGlkPSJkYXRhZmxvdy1hcnJvd2hlYWQtbGFyZ2UiCiAgICAgICAgdmlld0JveD0iMCAwIDEwIDEwIgogICAgICAgIG1hcmtlcldpZHRoPSIxNiIKICAgICAgICBtYXJrZXJIZWlnaHQ9IjE2IgogICAgICAgIHJlZlg9IjIiCiAgICAgICAgcmVmWT0iNSIKICAgICAgICBvcmllbnQ9ImF1dG8tc3RhcnQtcmV2ZXJzZSIKICAgICAgICBtYXJrZXJVbml0cz0idXNlclNwYWNlT25Vc2UiCiAgICAgID4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNkYXRhZmxvdy1hcnJvd2hlYWQtcGF0aCI+PC91c2U+CiAgICAgIDwvbWFya2VyPgogICAgICA8bWFya2VyCiAgICAgICAgY2xhc3M9ImRhdGFmbG93LWFycm93aGVhZCIKICAgICAgICBpZD0iZGF0YWZsb3ctYXJyb3doZWFkLXhsYXJnZSIKICAgICAgICB2aWV3Qm94PSIwIDAgMTAgMTAiCiAgICAgICAgbWFya2VyV2lkdGg9IjIwIgogICAgICAgIG1hcmtlckhlaWdodD0iMjAiCiAgICAgICAgcmVmWD0iMiIKICAgICAgICByZWZZPSI1IgogICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgIG1hcmtlclVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI2RhdGFmbG93LWFycm93aGVhZC1wYXRoIj48L3VzZT4KICAgICAgPC9tYXJrZXI+CgogICAgICA8IS0tIEFycm93IGhlYWQgZm9yIGFubm90YXRpb24gZWRnZSBwYXRocy4gLS0+CiAgICAgIDxtYXJrZXIKICAgICAgICBpZD0iYW5ub3RhdGlvbi1hcnJvd2hlYWQiCiAgICAgICAgbWFya2VyV2lkdGg9IjUiCiAgICAgICAgbWFya2VySGVpZ2h0PSI1IgogICAgICAgIHJlZlg9IjUiCiAgICAgICAgcmVmWT0iMi41IgogICAgICAgIG9yaWVudD0iYXV0byIKICAgICAgPgogICAgICAgIDxwYXRoIGQ9Ik0gMCwwIEwgNSwyLjUgTCAwLDUgTCAwLDAiPjwvcGF0aD4KICAgICAgPC9tYXJrZXI+CiAgICAgIDxtYXJrZXIKICAgICAgICBpZD0iYW5ub3RhdGlvbi1hcnJvd2hlYWQtZmFkZWQiCiAgICAgICAgbWFya2VyV2lkdGg9IjUiCiAgICAgICAgbWFya2VySGVpZ2h0PSI1IgogICAgICAgIHJlZlg9IjUiCiAgICAgICAgcmVmWT0iMi41IgogICAgICAgIG9yaWVudD0iYXV0byIKICAgICAgPgogICAgICAgIDxwYXRoIGQ9Ik0gMCwwIEwgNSwyLjUgTCAwLDUgTCAwLDAiPjwvcGF0aD4KICAgICAgPC9tYXJrZXI+CiAgICAgIDxtYXJrZXIKICAgICAgICBpZD0icmVmLWFubm90YXRpb24tYXJyb3doZWFkIgogICAgICAgIG1hcmtlcldpZHRoPSI1IgogICAgICAgIG1hcmtlckhlaWdodD0iNSIKICAgICAgICByZWZYPSIwIgogICAgICAgIHJlZlk9IjIuNSIKICAgICAgICBvcmllbnQ9ImF1dG8iCiAgICAgID4KICAgICAgICA8cGF0aCBkPSJNIDUsMCBMIDAsMi41IEwgNSw1IEwgNSwwIj48L3BhdGg+CiAgICAgIDwvbWFya2VyPgogICAgICA8bWFya2VyCiAgICAgICAgaWQ9InJlZi1hbm5vdGF0aW9uLWFycm93aGVhZC1mYWRlZCIKICAgICAgICBtYXJrZXJXaWR0aD0iNSIKICAgICAgICBtYXJrZXJIZWlnaHQ9IjUiCiAgICAgICAgcmVmWD0iMCIKICAgICAgICByZWZZPSIyLjUiCiAgICAgICAgb3JpZW50PSJhdXRvIgogICAgICA+CiAgICAgICAgPHBhdGggZD0iTSA1LDAgTCAwLDIuNSBMIDUsNSBMIDUsMCI+PC9wYXRoPgogICAgICA8L21hcmtlcj4KICAgICAgPCEtLSBUZW1wbGF0ZSBmb3IgYW4gT3Agbm9kZSBlbGxpcHNlLiAtLT4KICAgICAgPGVsbGlwc2UKICAgICAgICBpZD0ib3Atbm9kZS1zdGFtcCIKICAgICAgICByeD0iNy41IgogICAgICAgIHJ5PSIzIgogICAgICAgIHN0cm9rZT0iaW5oZXJpdCIKICAgICAgICBmaWxsPSJpbmhlcml0IgogICAgICA+PC9lbGxpcHNlPgogICAgICA8IS0tIFRlbXBsYXRlIGZvciBhbiBPcCBub2RlIGFubm90YXRpb24gZWxsaXBzZSAoc21hbGxlcikuIC0tPgogICAgICA8ZWxsaXBzZQogICAgICAgIGlkPSJvcC1ub2RlLWFubm90YXRpb24tc3RhbXAiCiAgICAgICAgcng9IjUiCiAgICAgICAgcnk9IjIiCiAgICAgICAgc3Ryb2tlPSJpbmhlcml0IgogICAgICAgIGZpbGw9ImluaGVyaXQiCiAgICAgID48L2VsbGlwc2U+CiAgICAgIDwhLS0gVmVydGljYWxseSBzdGFja2VkIHNlcmllcyBvZiBPcCBub2RlcyB3aGVuIHVuZXhwYW5kZWQuIC0tPgogICAgICA8ZyBpZD0ib3Atc2VyaWVzLXZlcnRpY2FsLXN0YW1wIj4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIiB4PSI4IiB5PSI5Ij48L3VzZT4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIiB4PSI4IiB5PSI2Ij48L3VzZT4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIiB4PSI4IiB5PSIzIj48L3VzZT4KICAgICAgPC9nPgogICAgICA8IS0tIEhvcml6b250YWxseSBzdGFja2VkIHNlcmllcyBvZiBPcCBub2RlcyB3aGVuIHVuZXhwYW5kZWQuIC0tPgogICAgICA8ZyBpZD0ib3Atc2VyaWVzLWhvcml6b250YWwtc3RhbXAiPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI29wLW5vZGUtc3RhbXAiIHg9IjE2IiB5PSI0Ij48L3VzZT4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLXN0YW1wIiB4PSIxMiIgeT0iNCI+PC91c2U+CiAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1zdGFtcCIgeD0iOCIgeT0iNCI+PC91c2U+CiAgICAgIDwvZz4KICAgICAgPCEtLSBIb3Jpem9udGFsbHkgc3RhY2tlZCBzZXJpZXMgb2YgT3Agbm9kZXMgZm9yIGFubm90YXRpb24uIC0tPgogICAgICA8ZyBpZD0ib3Atc2VyaWVzLWFubm90YXRpb24tc3RhbXAiPgogICAgICAgIDx1c2UgeGxpbms6aHJlZj0iI29wLW5vZGUtYW5ub3RhdGlvbi1zdGFtcCIgeD0iOSIgeT0iMiI+PC91c2U+CiAgICAgICAgPHVzZSB4bGluazpocmVmPSIjb3Atbm9kZS1hbm5vdGF0aW9uLXN0YW1wIiB4PSI3IiB5PSIyIj48L3VzZT4KICAgICAgICA8dXNlIHhsaW5rOmhyZWY9IiNvcC1ub2RlLWFubm90YXRpb24tc3RhbXAiIHg9IjUiIHk9IjIiPjwvdXNlPgogICAgICA8L2c+CiAgICAgIDxzdmcKICAgICAgICBpZD0ic3VtbWFyeS1pY29uIgogICAgICAgIGZpbGw9IiM4NDg0ODQiCiAgICAgICAgaGVpZ2h0PSIxMiIKICAgICAgICB2aWV3Qm94PSIwIDAgMjQgMjQiCiAgICAgICAgd2lkdGg9IjEyIgogICAgICA+CiAgICAgICAgPHBhdGgKICAgICAgICAgIGQ9Ik0xOSAzSDVjLTEuMSAwLTIgLjktMiAydjE0YzAgMS4xLjkgMiAyIDJoMTRjMS4xIDAgMi0uOSAyLTJWNWMwLTEuMS0uOS0yLTItMnpNOSAxN0g3di03aDJ2N3ptNCAwaC0yVjdoMnYxMHptNCAwaC0ydi00aDJ2NHoiCiAgICAgICAgPjwvcGF0aD4KICAgICAgPC9zdmc+CgogICAgICA8IS0tIEhhdGNoIHBhdHRlcm5zIGZvciBmYWRlZCBvdXQgbm9kZXMuIC0tPgogICAgICA8cGF0dGVybgogICAgICAgIGlkPSJyZWN0SGF0Y2giCiAgICAgICAgcGF0dGVyblRyYW5zZm9ybT0icm90YXRlKDQ1IDAgMCkiCiAgICAgICAgd2lkdGg9IjUiCiAgICAgICAgaGVpZ2h0PSI1IgogICAgICAgIHBhdHRlcm5Vbml0cz0idXNlclNwYWNlT25Vc2UiCiAgICAgID4KICAgICAgICA8bGluZSB4MT0iMCIgeTE9IjAiIHgyPSIwIiB5Mj0iNSIgc3R5bGU9InN0cm9rZS13aWR0aDogMSI+PC9saW5lPgogICAgICA8L3BhdHRlcm4+CiAgICAgIDxwYXR0ZXJuCiAgICAgICAgaWQ9ImVsbGlwc2VIYXRjaCIKICAgICAgICBwYXR0ZXJuVHJhbnNmb3JtPSJyb3RhdGUoNDUgMCAwKSIKICAgICAgICB3aWR0aD0iMiIKICAgICAgICBoZWlnaHQ9IjIiCiAgICAgICAgcGF0dGVyblVuaXRzPSJ1c2VyU3BhY2VPblVzZSIKICAgICAgPgogICAgICAgIDxsaW5lIHgxPSIwIiB5MT0iMCIgeDI9IjAiIHkyPSIyIiBzdHlsZT0ic3Ryb2tlLXdpZHRoOiAxIj48L2xpbmU+CiAgICAgIDwvcGF0dGVybj4KCiAgICAgIDwhLS0gQSBzaGFkb3cgZm9yIGhlYWx0aCBwaWxscy4gLS0+CiAgICAgIDxmaWx0ZXIKICAgICAgICBpZD0iaGVhbHRoLXBpbGwtc2hhZG93IgogICAgICAgIHg9Ii00MCUiCiAgICAgICAgeT0iLTQwJSIKICAgICAgICB3aWR0aD0iMTgwJSIKICAgICAgICBoZWlnaHQ9IjE4MCUiCiAgICAgID4KICAgICAgICA8ZmVHYXVzc2lhbkJsdXIgaW49IlNvdXJjZUFscGhhIiBzdGREZXZpYXRpb249IjAuOCI+PC9mZUdhdXNzaWFuQmx1cj4KICAgICAgICA8ZmVPZmZzZXQgZHg9IjAiIGR5PSIwIiByZXN1bHQ9Im9mZnNldGJsdXIiPjwvZmVPZmZzZXQ+CiAgICAgICAgPGZlRmxvb2QgZmxvb2QtY29sb3I9IiMwMDAwMDAiPjwvZmVGbG9vZD4KICAgICAgICA8ZmVDb21wb3NpdGUgaW4yPSJvZmZzZXRibHVyIiBvcGVyYXRvcj0iaW4iPjwvZmVDb21wb3NpdGU+CiAgICAgICAgPGZlTWVyZ2U+CiAgICAgICAgICA8ZmVNZXJnZU5vZGU+PC9mZU1lcmdlTm9kZT4KICAgICAgICAgIDxmZU1lcmdlTm9kZSBpbj0iU291cmNlR3JhcGhpYyI+PC9mZU1lcmdlTm9kZT4KICAgICAgICA8L2ZlTWVyZ2U+CiAgICAgIDwvZmlsdGVyPgogICAgPC9kZWZzPgogICAgPCEtLSBNYWtlIGEgbGFyZ2UgcmVjdGFuZ2xlIHRoYXQgZmlsbHMgdGhlIHN2ZyBzcGFjZSBzbyB0aGF0CiAgem9vbSBldmVudHMgZ2V0IGNhcHR1cmVkIG9uIHNhZmFyaSAtLT4KICAgIDxyZWN0IGZpbGw9IndoaXRlIiB3aWR0aD0iMTAwMDAiIGhlaWdodD0iMTAwMDAiPjwvcmVjdD4KICAgIDxnIGlkPSJyb290Ij48L2c+CiAgPC9zdmc+CiAgPHRmLWdyYXBoLW1pbmltYXAgaWQ9Im1pbmltYXAiPjwvdGYtZ3JhcGgtbWluaW1hcD4KICA8ZGl2IGlkPSJjb250ZXh0TWVudSIgY2xhc3M9ImNvbnRleHQtbWVudSI+PC9kaXY+CmA7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZHcmFwaFNjZW5lMiA9IGNsYXNzIFRmR3JhcGhTY2VuZTIgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgLyoqIEtlZXBzIHRyYWNrIG9mIGlmIHRoZSBncmFwaCBoYXMgYmVlbiB6b29tZWQvcGFubmVkIHNpbmNlIGxvYWRpbmcgKi8KICAgICAgICAgICAgdGhpcy5fem9vbWVkID0gZmFsc2U7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBLZWVwcyB0cmFjayBvZiB0aGUgc3RhcnRpbmcgY29vcmRpbmF0ZXMgb2YgYSBncmFwaCB6b29tL3Bhbi4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICogQHByaXZhdGUge3t4OiBudW1iZXIsIHk6IG51bWJlcn0/fQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5fem9vbVN0YXJ0Q29vcmRzID0gbnVsbDsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEtlZXBzIHRyYWNrIG9mIHRoZSBjdXJyZW50IGNvb3JkaW5hdGVzIG9mIGEgZ3JhcGggem9vbS9wYW4KICAgICAgICAgICAgICoKICAgICAgICAgICAgICogQHByaXZhdGUge3t4OiBudW1iZXIsIHk6IG51bWJlcn0/fQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5fem9vbVRyYW5zZm9ybSA9IG51bGw7CiAgICAgICAgICAgIC8qKiBNYXhpbXVtIGRpc3RhbmNlIG9mIGEgem9vbSBldmVudCBmb3IgaXQgdG8gYmUgaW50ZXJwcmV0ZWQgYXMgYSBjbGljayAqLwogICAgICAgICAgICB0aGlzLl9tYXhab29tRGlzdGFuY2VGb3JDbGljayA9IDIwOwogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBEaWN0aW9uYXJ5IGZvciBlYXNpbHkgc3R5bGl6aW5nIG5vZGVzIHdoZW4gc3RhdGUgY2hhbmdlcy4KICAgICAgICAgICAgICogX25vZGVHcm91cEluZGV4W25vZGVOYW1lXSA9IGQzX3NlbGVjdGlvbiBvZiB0aGUgbm9kZUdyb3VwCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9ub2RlR3JvdXBJbmRleCA9IHt9OwogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBEaWN0aW9uYXJ5IGZvciBlYXNpbHkgc3R5bGl6aW5nIGFubm90YXRpb24gbm9kZXMgd2hlbiBzdGF0ZSBjaGFuZ2VzLgogICAgICAgICAgICAgKiBfYW5ub3RhdGlvbkdyb3VwSW5kZXhbbm9kZU5hbWVdW2hvc3ROb2RlTmFtZV0gPQogICAgICAgICAgICAgKiAgIGQzX3NlbGVjdGlvbiBvZiB0aGUgYW5ub3RhdGlvbkdyb3VwCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uR3JvdXBJbmRleCA9IHt9OwogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBEaWN0aW9uYXJ5IGZvciBlYXNpbHkgc3R5bGl6aW5nIGVkZ2VzIHdoZW4gc3RhdGUgY2hhbmdlcy4KICAgICAgICAgICAgICogX2VkZ2VHcm91cEluZGV4W2VkZ2VOYW1lXSA9IGQzX3NlbGVjdGlvbiBvZiB0aGUgZWRnZUdyb3VwCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9lZGdlR3JvdXBJbmRleCA9IHt9OwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogTWF4IGZvbnQgc2l6ZSBmb3IgbWV0YW5vZGUgbGFiZWwgc3RyaW5ncy4KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMubWF4TWV0YW5vZGVMYWJlbExlbmd0aEZvbnRTaXplID0gOTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIE1pbiBmb250IHNpemUgZm9yIG1ldGFub2RlIGxhYmVsIHN0cmluZ3MuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLm1pbk1ldGFub2RlTGFiZWxMZW5ndGhGb250U2l6ZSA9IDY7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBNZXRhbm9kZSBsYWJlbCBzdHJpbmdzIGxvbmdlciB0aGFuIHRoaXMgYXJlIGdpdmVuIHNtYWxsZXIgZm9udHMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLm1heE1ldGFub2RlTGFiZWxMZW5ndGhMYXJnZUZvbnQgPSAxMTsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIE1ldGFub2RlIGxhYmVsIHN0cmluZ3MgbG9uZ2VyIHRoYW4gdGhpcyBhcmUgdHJ1bmNhdGVkIHdpdGggZWxsaXBzZXMuCiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLm1heE1ldGFub2RlTGFiZWxMZW5ndGggPSAxODsKICAgICAgICB9CiAgICAgICAgZ2V0Tm9kZShub2RlTmFtZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5yZW5kZXJIaWVyYXJjaHkuZ2V0UmVuZGVyTm9kZUJ5TmFtZShub2RlTmFtZSk7CiAgICAgICAgfQogICAgICAgIGlzTm9kZUV4cGFuZGVkKG5vZGUpIHsKICAgICAgICAgICAgcmV0dXJuIG5vZGUuZXhwYW5kZWQ7CiAgICAgICAgfQogICAgICAgIHNldE5vZGVFeHBhbmRlZChyZW5kZXJOb2RlKSB7CiAgICAgICAgICAgIHRoaXMuX2J1aWxkKHRoaXMucmVuZGVySGllcmFyY2h5KTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlTGFiZWxzKCF0aGlzLl96b29tZWQpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBQYW5zIHRvIGEgbm9kZS4gQXNzdW1lcyB0aGF0IHRoZSBub2RlIGV4aXN0cy4KICAgICAgICAgKiBAcGFyYW0gbm9kZU5hbWUge3N0cmluZ30gVGhlIG5hbWUgb2YgdGhlIG5vZGUgdG8gcGFuIHRvLgogICAgICAgICAqLwogICAgICAgIHBhblRvTm9kZShub2RlTmFtZSkgewogICAgICAgICAgICBjb25zdCB6b29tZWQgPSBwYW5Ub05vZGUobm9kZU5hbWUsIHRoaXMuJC5zdmcsIHRoaXMuJC5yb290LCB0aGlzLl96b29tKTsKICAgICAgICAgICAgaWYgKHpvb21lZCkgewogICAgICAgICAgICAgICAgdGhpcy5fem9vbWVkID0gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIHRoZSBvdXRlci1tb3N0IFNWRyB0aGF0IHJlbmRlcnMgdGhlIGdyYXBoLgogICAgICAgICAqLwogICAgICAgIGdldEdyYXBoU3ZnUm9vdCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuJC5zdmc7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEByZXR1cm5zIHshSFRNTEVsZW1lbnR9CiAgICAgICAgICovCiAgICAgICAgZ2V0Q29udGV4dE1lbnUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLiQuY29udGV4dE1lbnU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJlc2V0cyB0aGUgc3RhdGUgb2YgdGhlIGNvbXBvbmVudC4gQ2FsbGVkIHdoZW5ldmVyIHRoZSB3aG9sZSBncmFwaAogICAgICAgICAqIChkYXRhc2V0KSBjaGFuZ2VzLgogICAgICAgICAqLwogICAgICAgIF9yZXNldFN0YXRlKCkgewogICAgICAgICAgICAvLyBSZXNldCB0aGUgc3RhdGUgb2YgdGhlIGNvbXBvbmVudC4KICAgICAgICAgICAgdGhpcy5fbm9kZUdyb3VwSW5kZXggPSB7fTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvbkdyb3VwSW5kZXggPSB7fTsKICAgICAgICAgICAgdGhpcy5fZWRnZUdyb3VwSW5kZXggPSB7fTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlTGFiZWxzKGZhbHNlKTsKICAgICAgICAgICAgLy8gUmVtb3ZlIGFsbCBzdmcgZWxlbWVudHMgdW5kZXIgdGhlICdyb290JyBzdmcgZ3JvdXAuCiAgICAgICAgICAgIHNlbGVjdCh0aGlzLiQuc3ZnKS5zZWxlY3QoJyNyb290Jykuc2VsZWN0QWxsKCcqJykucmVtb3ZlKCk7CiAgICAgICAgICAgIC8vIEFuZCB0aGUgZGVmcy4KICAgICAgICAgICAgcmVtb3ZlR3JhZGllbnREZWZpbml0aW9ucyh0aGlzLiQuc3ZnKTsKICAgICAgICB9CiAgICAgICAgLyoqIE1haW4gbWV0aG9kIGZvciBidWlsZGluZyB0aGUgc2NlbmUgKi8KICAgICAgICBfYnVpbGQocmVuZGVySGllcmFyY2h5KSB7CiAgICAgICAgICAgIHRoaXMudGVtcGxhdGVJbmRleCA9IHJlbmRlckhpZXJhcmNoeS5oaWVyYXJjaHkuZ2V0VGVtcGxhdGVJbmRleCgpOwogICAgICAgICAgICB0aW1lJDMoJ3RmLWdyYXBoLXNjZW5lIChsYXlvdXQpOicsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIC8vIGxheW91dCB0aGUgc2NlbmUgZm9yIHRoaXMgbWV0YSAvIHNlcmllcyBub2RlCiAgICAgICAgICAgICAgICBsYXlvdXRTY2VuZShyZW5kZXJIaWVyYXJjaHkucm9vdCk7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgICAgIHRpbWUkMygndGYtZ3JhcGgtc2NlbmUgKGJ1aWxkIHNjZW5lKTonLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBidWlsZEdyb3VwRm9yU2NlbmUoc2VsZWN0KHRoaXMuJC5yb290KSwgcmVuZGVySGllcmFyY2h5LnJvb3QsIHRoaXMpOwogICAgICAgICAgICAgICAgYWRkR3JhcGhDbGlja0xpc3RlbmVyKHRoaXMuJC5zdmcsIHRoaXMpOwogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlSW5wdXRUcmFjZSgpOwogICAgICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICAgICAgICAvLyBVcGRhdGUgdGhlIG1pbmltYXAgYWdhaW4gd2hlbiB0aGUgZ3JhcGggaXMgZG9uZSBhbmltYXRpbmcuCiAgICAgICAgICAgIHNldFRpbWVvdXQoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlSGVhbHRoUGlsbHModGhpcy5ub2RlTmFtZXNUb0hlYWx0aFBpbGxzLCB0aGlzLmhlYWx0aFBpbGxTdGVwSW5kZXgpOwogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLnVwZGF0ZSgpOwogICAgICAgICAgICB9LmJpbmQodGhpcyksIFBBUkFNUyQxLmFuaW1hdGlvbi5kdXJhdGlvbik7CiAgICAgICAgfQogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgICBzdXBlci5yZWFkeSgpOwogICAgICAgICAgICB0aGlzLl96b29tID0gem9vbSgpCiAgICAgICAgICAgICAgICAub24oJ2VuZCcsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl96b29tU3RhcnRDb29yZHMpIHsKICAgICAgICAgICAgICAgICAgICAvLyBDYWxjdWxhdGUgdGhlIHRvdGFsIGRpc3RhbmNlIGRyYWdnZWQgZHVyaW5nIHRoZSB6b29tIGV2ZW50LgogICAgICAgICAgICAgICAgICAgIC8vIElmIGl0IGlzIHN1ZmZpY2llbnRseSBzbWFsbCwgdGhlbiBmaXJlIGFuIGV2ZW50IGluZGljYXRpbmcKICAgICAgICAgICAgICAgICAgICAvLyB0aGF0IHpvb21pbmcgaGFzIGVuZGVkLiBPdGhlcndpc2Ugd2FpdCB0byBmaXJlIHRoZSB6b29tIGVuZAogICAgICAgICAgICAgICAgICAgIC8vIGV2ZW50LCBzbyB0aGF0IGEgbW91c2UgY2xpY2sgcmVnaXN0ZXJlZCBhcyBwYXJ0IG9mIHRoaXMgem9vbWluZwogICAgICAgICAgICAgICAgICAgIC8vIGlzIGlnbm9yZWQgKGFzIHRoaXMgbW91c2UgY2xpY2sgd2FzIHBhcnQgb2YgYSB6b29taW5nLCBhbmQgc2hvdWxkCiAgICAgICAgICAgICAgICAgICAgLy8gbm90IGJlIHVzZWQgdG8gaW5kaWNhdGUgYW4gYWN0dWFsIGNsaWNrIG9uIHRoZSBncmFwaCkuCiAgICAgICAgICAgICAgICAgICAgdmFyIGRyYWdEaXN0YW5jZSA9IE1hdGguc3FydChNYXRoLnBvdyh0aGlzLl96b29tU3RhcnRDb29yZHMueCAtIHRoaXMuX3pvb21UcmFuc2Zvcm0ueCwgMikgKwogICAgICAgICAgICAgICAgICAgICAgICBNYXRoLnBvdyh0aGlzLl96b29tU3RhcnRDb29yZHMueSAtIHRoaXMuX3pvb21UcmFuc2Zvcm0ueSwgMikpOwogICAgICAgICAgICAgICAgICAgIGlmIChkcmFnRGlzdGFuY2UgPCB0aGlzLl9tYXhab29tRGlzdGFuY2VGb3JDbGljaykgewogICAgICAgICAgICAgICAgICAgICAgICB0aGlzLl9maXJlRW5hYmxlQ2xpY2soKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHNldFRpbWVvdXQodGhpcy5fZmlyZUVuYWJsZUNsaWNrLmJpbmQodGhpcyksIDUwKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl96b29tU3RhcnRDb29yZHMgPSBudWxsOwogICAgICAgICAgICB9LmJpbmQodGhpcykpCiAgICAgICAgICAgICAgICAub24oJ3pvb20nLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICAvLyBTdG9yZSB0aGUgY29vcmRpbmF0ZXMgb2YgdGhlIHpvb20gZXZlbnQuCiAgICAgICAgICAgICAgICB0aGlzLl96b29tVHJhbnNmb3JtID0gZXZlbnQudHJhbnNmb3JtOwogICAgICAgICAgICAgICAgLy8gSWYgdGhpcyBpcyB0aGUgZmlyc3Qgem9vbSBldmVudCBhZnRlciBhIHpvb20tZW5kLCB0aGVuCiAgICAgICAgICAgICAgICAvLyBzdG9yZSB0aGUgY29vcmRpbmF0ZXMgYXMgdGhlIHN0YXJ0IGNvb3JkaW5hdGVzIGFzIHdlbGwsCiAgICAgICAgICAgICAgICAvLyBhbmQgZmlyZSBhbiBldmVudCB0byBpbmRpY2F0ZSB0aGF0IHpvb21pbmcgaGFzIHN0YXJ0ZWQuCiAgICAgICAgICAgICAgICAvLyBUaGlzIGRvZXNuJ3QgdXNlIHRoZSB6b29tc3RhcnQgZXZlbnQsIGFzIGQzIHNlbmRzIHRoaXMKICAgICAgICAgICAgICAgIC8vIGV2ZW50IG9uIG1vdXNlLWRvd24sIGV2ZW4gaWYgdGhlcmUgaGFzIGJlZW4gbm8gZHJhZ2dpbmcKICAgICAgICAgICAgICAgIC8vIGRvbmUgdG8gdHJhbnNsYXRlIHRoZSBncmFwaCBhcm91bmQuCiAgICAgICAgICAgICAgICBpZiAoIXRoaXMuX3pvb21TdGFydENvb3JkcykgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX3pvb21TdGFydENvb3JkcyA9IHRoaXMuX3pvb21UcmFuc2Zvcm07CiAgICAgICAgICAgICAgICAgICAgdGhpcy5maXJlKCdkaXNhYmxlLWNsaWNrJyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl96b29tZWQgPSB0cnVlOwogICAgICAgICAgICAgICAgc2VsZWN0KHRoaXMuJC5yb290KS5hdHRyKCd0cmFuc2Zvcm0nLCBldmVudC50cmFuc2Zvcm0pOwogICAgICAgICAgICAgICAgLy8gTm90aWZ5IHRoZSBtaW5pbWFwLgogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLnpvb20oZXZlbnQudHJhbnNmb3JtKTsKICAgICAgICAgICAgfS5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgc2VsZWN0KHRoaXMuJC5zdmcpCiAgICAgICAgICAgICAgICAuY2FsbCh0aGlzLl96b29tKQogICAgICAgICAgICAgICAgLm9uKCdkYmxjbGljay56b29tJywgbnVsbCk7CiAgICAgICAgICAgIHNlbGVjdCh3aW5kb3cpLm9uKCdyZXNpemUnLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICAvLyBOb3RpZnkgdGhlIG1pbmltYXAgdGhhdCB0aGUgdXNlcidzIHdpbmRvdyB3YXMgcmVzaXplZC4KICAgICAgICAgICAgICAgIC8vIFRoZSBtaW5pbWFwIHdpbGwgZmlndXJlIG91dCB0aGUgbmV3IGRpbWVuc2lvbnMgb2YgdGhlIG1haW4gc3ZnCiAgICAgICAgICAgICAgICAvLyBhbmQgd2lsbCB1c2UgdGhlIGV4aXN0aW5nIHRyYW5zbGF0ZSBhbmQgc2NhbGUgcGFyYW1zLgogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLnpvb20oKTsKICAgICAgICAgICAgfS5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgLy8gSW5pdGlhbGl6ZSB0aGUgbWluaW1hcC4KICAgICAgICAgICAgdGhpcy5taW5pbWFwID0gdGhpcy4kLm1pbmltYXAuaW5pdCh0aGlzLiQuc3ZnLCB0aGlzLiQucm9vdCwgdGhpcy5fem9vbSwgUEFSQU1TJDEubWluaW1hcC5zaXplLCBQQVJBTVMkMS5zdWJzY2VuZS5tZXRhLmxhYmVsSGVpZ2h0KTsKICAgICAgICB9CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfaXNBdHRhY2hlZCcsIHRydWUpOwogICAgICAgIH0KICAgICAgICBkZXRhY2hlZCgpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19pc0F0dGFjaGVkJywgZmFsc2UpOwogICAgICAgIH0KICAgICAgICBfcmVuZGVySGllcmFyY2h5Q2hhbmdlZCgpIHsKICAgICAgICAgICAgdmFyIHJlbmRlckhpZXJhcmNoeSA9IHRoaXMucmVuZGVySGllcmFyY2h5OwogICAgICAgICAgICB0aGlzLl9oYXNSZW5kZXJIaWVyYXJjaHlCZWVuRml0T25jZSA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl9yZXNldFN0YXRlKCk7CiAgICAgICAgICAgIHRoaXMuX2J1aWxkKHJlbmRlckhpZXJhcmNoeSk7CiAgICAgICAgfQogICAgICAgIC8vIEFuaW1hdGlvbiBhbmQgZml0dGluZyBtdXN0IGNvbWUgYWZ0ZXIgdGhlIG9ic2VydmVyIGZvciB0aGUgaGllcmFyY2h5IGNoYW5naW5nIGJlY2F1c2Ugd2UgbXVzdAogICAgICAgIC8vIGZpcnN0IGJ1aWxkIHRoZSByZW5kZXIgaGllcmFyY2h5LgogICAgICAgIF9hbmltYXRlQW5kRml0KCkgewogICAgICAgICAgICB2YXIgaXNBdHRhY2hlZCA9IHRoaXMuX2lzQXR0YWNoZWQ7CiAgICAgICAgICAgIHZhciByZW5kZXJIaWVyYXJjaHkgPSB0aGlzLnJlbmRlckhpZXJhcmNoeTsKICAgICAgICAgICAgaWYgKHRoaXMuX2hhc1JlbmRlckhpZXJhcmNoeUJlZW5GaXRPbmNlIHx8ICFpc0F0dGFjaGVkKSB7CiAgICAgICAgICAgICAgICAvLyBEbyBub3QgYW5pbWF0ZSBhbmQgZml0IGlmIHRoZSBzY2VuZSBoYXMgYWxyZWFkeSBmaXR0ZWQgdGhpcyByZW5kZXIgaGllcmFyY2h5IG9uY2UuIE9yIGlmCiAgICAgICAgICAgICAgICAvLyB0aGUgZ3JhcGggZGFzaGJvYXJkIGlzIG5vdCBhdHRhY2hlZCAoaW4gd2hpY2ggY2FzZSB0aGUgc2NlbmUgbGFja3MgRE9NIGluZm8gZm9yIGZpdHRpbmcpLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEZpdCB0byBzY3JlZW4gYWZ0ZXIgdGhlIGdyYXBoIGlzIGRvbmUgYW5pbWF0aW5nLgogICAgICAgICAgICBzZXRUaW1lb3V0KHRoaXMuZml0LmJpbmQodGhpcyksIFBBUkFNUyQxLmFuaW1hdGlvbi5kdXJhdGlvbik7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVMYWJlbHMoc2hvd0xhYmVscykgewogICAgICAgICAgICB2YXIgbWFpbkdyYXBoVGl0bGVFbGVtZW50ID0gdGhpcy4kJCgnLnRpdGxlJyk7CiAgICAgICAgICAgIHZhciB0aXRsZVN0eWxlID0gbWFpbkdyYXBoVGl0bGVFbGVtZW50LnN0eWxlOwogICAgICAgICAgICB2YXIgYXV4VGl0bGVFbGVtZW50ID0gdGhpcy4kJCgnLmF1eFRpdGxlJyk7CiAgICAgICAgICAgIHZhciBhdXhUaXRsZVN0eWxlID0gYXV4VGl0bGVFbGVtZW50LnN0eWxlOwogICAgICAgICAgICB2YXIgZnVuY3Rpb25MaWJyYXJ5VGl0bGVTdHlsZSA9IHRoaXMuJCQoJy5mdW5jdGlvbkxpYnJhcnlUaXRsZScpLnN0eWxlOwogICAgICAgICAgICBjb25zdCByb290ID0gc2VsZWN0KHRoaXMuJC5zdmcpOwogICAgICAgICAgICB2YXIgY29yZSA9IHJvb3QKICAgICAgICAgICAgICAgIC5zZWxlY3QoJy4nICsKICAgICAgICAgICAgICAgIENsYXNzJDIuU2NlbmUuR1JPVVAgKwogICAgICAgICAgICAgICAgJz4uJyArCiAgICAgICAgICAgICAgICBDbGFzcyQyLlNjZW5lLkNPUkUpCiAgICAgICAgICAgICAgICAubm9kZSgpOwogICAgICAgICAgICAvLyBPbmx5IHNob3cgbGFiZWxzIGlmIHRoZSBncmFwaCBpcyBmdWxseSBsb2FkZWQuCiAgICAgICAgICAgIGlmIChzaG93TGFiZWxzICYmIGNvcmUgJiYgdGhpcy5wcm9ncmVzcyAmJiB0aGlzLnByb2dyZXNzLnZhbHVlID09PSAxMDApIHsKICAgICAgICAgICAgICAgIHZhciBhdXggPSByb290CiAgICAgICAgICAgICAgICAgICAgLnNlbGVjdCgnLicgKwogICAgICAgICAgICAgICAgICAgIENsYXNzJDIuU2NlbmUuR1JPVVAgKwogICAgICAgICAgICAgICAgICAgICc+LicgKwogICAgICAgICAgICAgICAgICAgIENsYXNzJDIuU2NlbmUuSU5FWFRSQUNUKQogICAgICAgICAgICAgICAgICAgIC5ub2RlKCkgfHwKICAgICAgICAgICAgICAgICAgICByb290CiAgICAgICAgICAgICAgICAgICAgICAgIC5zZWxlY3QoJy4nICsKICAgICAgICAgICAgICAgICAgICAgICAgQ2xhc3MkMi5TY2VuZS5HUk9VUCArCiAgICAgICAgICAgICAgICAgICAgICAgICc+LicgKwogICAgICAgICAgICAgICAgICAgICAgICBDbGFzcyQyLlNjZW5lLk9VVEVYVFJBQ1QpCiAgICAgICAgICAgICAgICAgICAgICAgIC5ub2RlKCk7CiAgICAgICAgICAgICAgICB2YXIgY29yZVggPSBjb3JlLmdldENUTSgpLmU7CiAgICAgICAgICAgICAgICB2YXIgYXV4WCA9IGF1eCA/IGF1eC5nZXRDVE0oKS5lIDogbnVsbDsKICAgICAgICAgICAgICAgIHRpdGxlU3R5bGUuZGlzcGxheSA9ICdpbmxpbmUnOwogICAgICAgICAgICAgICAgdGl0bGVTdHlsZS5sZWZ0ID0gY29yZVggKyAncHgnOwogICAgICAgICAgICAgICAgaWYgKGF1eFggIT09IG51bGwgJiYgYXV4WCAhPT0gY29yZVgpIHsKICAgICAgICAgICAgICAgICAgICBhdXhUaXRsZVN0eWxlLmRpc3BsYXkgPSAnaW5saW5lJzsKICAgICAgICAgICAgICAgICAgICAvLyBNYWtlIHN1cmUgdGhhdCB0aGUgYXV4IHRpdGxlIGlzIHBvc2l0aW9uZWQgcmlnaHR3YXJkcyBlbm91Z2ggc28gYXMgdG8KICAgICAgICAgICAgICAgICAgICAvLyBwcmV2ZW50IG92ZXJsYXAgd2l0aCB0aGUgbWFpbiBncmFwaCB0aXRsZS4KICAgICAgICAgICAgICAgICAgICBhdXhYID0gTWF0aC5tYXgoY29yZVggKyBtYWluR3JhcGhUaXRsZUVsZW1lbnQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkud2lkdGgsIGF1eFgpOwogICAgICAgICAgICAgICAgICAgIGF1eFRpdGxlU3R5bGUubGVmdCA9IGF1eFggKyAncHgnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgYXV4VGl0bGVTdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgbGV0IGZ1bmN0aW9uTGlicmFyeSA9IHJvb3QKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0KCcuJyArCiAgICAgICAgICAgICAgICAgICAgQ2xhc3MkMi5TY2VuZS5HUk9VUCArCiAgICAgICAgICAgICAgICAgICAgJz4uJyArCiAgICAgICAgICAgICAgICAgICAgQ2xhc3MkMi5TY2VuZS5GVU5DVElPTl9MSUJSQVJZKQogICAgICAgICAgICAgICAgICAgIC5ub2RlKCk7CiAgICAgICAgICAgICAgICBsZXQgZnVuY3Rpb25MaWJyYXJ5WCA9IGZ1bmN0aW9uTGlicmFyeQogICAgICAgICAgICAgICAgICAgID8gZnVuY3Rpb25MaWJyYXJ5LmdldENUTSgpLmUKICAgICAgICAgICAgICAgICAgICA6IG51bGw7CiAgICAgICAgICAgICAgICBpZiAoZnVuY3Rpb25MaWJyYXJ5WCAhPT0gbnVsbCAmJiBmdW5jdGlvbkxpYnJhcnlYICE9PSBhdXhYKSB7CiAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb25MaWJyYXJ5VGl0bGVTdHlsZS5kaXNwbGF5ID0gJ2lubGluZSc7CiAgICAgICAgICAgICAgICAgICAgLy8gTWFrZSBzdXJlIHRoYXQgdGhlIGZ1bmN0aW9uIGxpYnJhcnkgdGl0bGUgaXMgcG9zaXRpb25lZCByaWdodHdhcmRzCiAgICAgICAgICAgICAgICAgICAgLy8gZW5vdWdoIHNvIGFzIHRvIHByZXZlbnQgb3ZlcmxhcCB3aXRoIG90aGVyIGNvbnRlbnQuCiAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb25MaWJyYXJ5WCA9IE1hdGgubWF4KGF1eFggKyBhdXhUaXRsZUVsZW1lbnQuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkud2lkdGgsIGZ1bmN0aW9uTGlicmFyeVgpOwogICAgICAgICAgICAgICAgICAgIGZ1bmN0aW9uTGlicmFyeVRpdGxlU3R5bGUubGVmdCA9IGZ1bmN0aW9uTGlicmFyeVggKyAncHgnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb25MaWJyYXJ5VGl0bGVTdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGl0bGVTdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgICAgICAgYXV4VGl0bGVTdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgICAgICAgZnVuY3Rpb25MaWJyYXJ5VGl0bGVTdHlsZS5kaXNwbGF5ID0gJ25vbmUnOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIENhbGxlZCB3aGVuZXZlciB0aGUgdXNlciBjaGFuZ2VkIHRoZSAnY29sb3IgYnknIG9wdGlvbiBpbiB0aGUKICAgICAgICAgKiBVSSBjb250cm9scy4KICAgICAgICAgKi8KICAgICAgICBfY29sb3JCeUNoYW5nZWQoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnJlbmRlckhpZXJhcmNoeSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBXZSBpdGVyYXRlIHRocm91Z2ggZWFjaCBzdmcgbm9kZSBhbmQgdXBkYXRlIGl0cyBzdGF0ZS4KICAgICAgICAgICAgICAgIGxvZGFzaC5lYWNoKHRoaXMuX25vZGVHcm91cEluZGV4LCAobm9kZUdyb3VwLCBub2RlTmFtZSkgPT4gewogICAgICAgICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZU5vZGVTdGF0ZShub2RlTmFtZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIC8vIE5vdGlmeSBhbHNvIHRoZSBtaW5pbWFwLgogICAgICAgICAgICAgICAgdGhpcy5taW5pbWFwLnVwZGF0ZSgpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGZpdCgpIHsKICAgICAgICAgICAgdGhpcy5faGFzUmVuZGVySGllcmFyY2h5QmVlbkZpdE9uY2UgPSB0cnVlOwogICAgICAgICAgICBmaXQkMih0aGlzLiQuc3ZnLCB0aGlzLiQucm9vdCwgdGhpcy5fem9vbSwgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdGhpcy5fem9vbWVkID0gZmFsc2U7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgfQogICAgICAgIGlzTm9kZVNlbGVjdGVkKG4pIHsKICAgICAgICAgICAgcmV0dXJuIG4gPT09IHRoaXMuc2VsZWN0ZWROb2RlOwogICAgICAgIH0KICAgICAgICBpc05vZGVIaWdobGlnaHRlZChuKSB7CiAgICAgICAgICAgIHJldHVybiBuID09PSB0aGlzLmhpZ2hsaWdodGVkTm9kZTsKICAgICAgICB9CiAgICAgICAgYWRkQW5ub3RhdGlvbkdyb3VwKGEsIGQsIHNlbGVjdGlvbikgewogICAgICAgICAgICB2YXIgYW4gPSBhLm5vZGUubmFtZTsKICAgICAgICAgICAgdGhpcy5fYW5ub3RhdGlvbkdyb3VwSW5kZXhbYW5dID0gdGhpcy5fYW5ub3RhdGlvbkdyb3VwSW5kZXhbYW5dIHx8IHt9OwogICAgICAgICAgICB0aGlzLl9hbm5vdGF0aW9uR3JvdXBJbmRleFthbl1bZC5ub2RlLm5hbWVdID0gc2VsZWN0aW9uOwogICAgICAgIH0KICAgICAgICBnZXRBbm5vdGF0aW9uR3JvdXBzSW5kZXgoYSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fYW5ub3RhdGlvbkdyb3VwSW5kZXhbYV07CiAgICAgICAgfQogICAgICAgIHJlbW92ZUFubm90YXRpb25Hcm91cChhLCBkKSB7CiAgICAgICAgICAgIGRlbGV0ZSB0aGlzLl9hbm5vdGF0aW9uR3JvdXBJbmRleFthLm5vZGUubmFtZV1bZC5ub2RlLm5hbWVdOwogICAgICAgIH0KICAgICAgICBhZGROb2RlR3JvdXAobiwgc2VsZWN0aW9uKSB7CiAgICAgICAgICAgIHRoaXMuX25vZGVHcm91cEluZGV4W25dID0gc2VsZWN0aW9uOwogICAgICAgIH0KICAgICAgICBnZXROb2RlR3JvdXAobikgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fbm9kZUdyb3VwSW5kZXhbbl07CiAgICAgICAgfQogICAgICAgIHJlbW92ZU5vZGVHcm91cChuKSB7CiAgICAgICAgICAgIGRlbGV0ZSB0aGlzLl9ub2RlR3JvdXBJbmRleFtuXTsKICAgICAgICB9CiAgICAgICAgYWRkRWRnZUdyb3VwKG4sIHNlbGVjdGlvbikgewogICAgICAgICAgICB0aGlzLl9lZGdlR3JvdXBJbmRleFtuXSA9IHNlbGVjdGlvbjsKICAgICAgICB9CiAgICAgICAgZ2V0RWRnZUdyb3VwKGUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2VkZ2VHcm91cEluZGV4W2VdOwogICAgICAgIH0KICAgICAgICBfdXBkYXRlSGVhbHRoUGlsbHMoKSB7CiAgICAgICAgICAgIHZhciBub2RlTmFtZXNUb0hlYWx0aFBpbGxzID0gdGhpcy5ub2RlTmFtZXNUb0hlYWx0aFBpbGxzOwogICAgICAgICAgICB2YXIgaGVhbHRoUGlsbFN0ZXBJbmRleCA9IHRoaXMuaGVhbHRoUGlsbFN0ZXBJbmRleDsKICAgICAgICAgICAgYWRkSGVhbHRoUGlsbHModGhpcy4kLnN2Zywgbm9kZU5hbWVzVG9IZWFsdGhQaWxscywgaGVhbHRoUGlsbFN0ZXBJbmRleCk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFVwZGF0ZSBub2RlIGFuZCBhbm5vdGF0aW9uIG5vZGUgb2YgdGhlIGdpdmVuIG5hbWUuCiAgICAgICAgICogQHBhcmFtICB7U3RyaW5nfSBuIG5vZGUgbmFtZQogICAgICAgICAqLwogICAgICAgIF91cGRhdGVOb2RlU3RhdGUobikgewogICAgICAgICAgICB2YXIgbm9kZSA9IHRoaXMuZ2V0Tm9kZShuKTsKICAgICAgICAgICAgdmFyIG5vZGVHcm91cCA9IHRoaXMuZ2V0Tm9kZUdyb3VwKG4pOwogICAgICAgICAgICBpZiAobm9kZUdyb3VwKSB7CiAgICAgICAgICAgICAgICBzdHlsaXplJDEobm9kZUdyb3VwLCBub2RlLCB0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAobm9kZS5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLk1FVEEgJiYKICAgICAgICAgICAgICAgIG5vZGUubm9kZS5hc3NvY2lhdGVkRnVuY3Rpb24gJiYKICAgICAgICAgICAgICAgICFub2RlLmlzTGlicmFyeUZ1bmN0aW9uKSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgbm9kZSBpcyB0aGF0IG9mIGEgZnVuY3Rpb24gY2FsbC4gQWxzbyBsaW5rIHRoZSBub2RlIHdpdGhpbiB0aGUKICAgICAgICAgICAgICAgIC8vIGZ1bmN0aW9uIGxpYnJhcnkuIFRoaXMgY2xhcmlmaWVzIHRvIHRoZSB1c2VyIHRoYXQgdGhlIGxpYnJhcnkgZnVuY3Rpb24KICAgICAgICAgICAgICAgIC8vIGlzIGJlaW5nIHVzZWQuCiAgICAgICAgICAgICAgICB2YXIgbGlicmFyeUZ1bmN0aW9uTm9kZU5hbWUgPSBGVU5DVElPTl9MSUJSQVJZX05PREVfUFJFRklYICsKICAgICAgICAgICAgICAgICAgICBub2RlLm5vZGUuYXNzb2NpYXRlZEZ1bmN0aW9uOwogICAgICAgICAgICAgICAgdmFyIGZ1bmN0aW9uR3JvdXAgPSBzZWxlY3QoJy4nICsKICAgICAgICAgICAgICAgICAgICBDbGFzcyQyLlNjZW5lLkdST1VQICsKICAgICAgICAgICAgICAgICAgICAnPi4nICsKICAgICAgICAgICAgICAgICAgICBDbGFzcyQyLlNjZW5lLkZVTkNUSU9OX0xJQlJBUlkgKwogICAgICAgICAgICAgICAgICAgICcgZ1tkYXRhLW5hbWU9IicgKwogICAgICAgICAgICAgICAgICAgIGxpYnJhcnlGdW5jdGlvbk5vZGVOYW1lICsKICAgICAgICAgICAgICAgICAgICAnIl0nKTsKICAgICAgICAgICAgICAgIHN0eWxpemUkMShmdW5jdGlvbkdyb3VwLCBub2RlLCB0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB2YXIgYW5ub3RhdGlvbkdyb3VwSW5kZXggPSB0aGlzLmdldEFubm90YXRpb25Hcm91cHNJbmRleChuKTsKICAgICAgICAgICAgbG9kYXNoLmVhY2goYW5ub3RhdGlvbkdyb3VwSW5kZXgsIChhR3JvdXAsIGhvc3ROYW1lKSA9PiB7CiAgICAgICAgICAgICAgICBzdHlsaXplJDEoYUdyb3VwLCBub2RlLCB0aGlzLCBDbGFzcyQyLkFubm90YXRpb24uTk9ERSk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBIYW5kbGVzIG5ldyBub2RlIHNlbGVjdGlvbi4gMSkgVXBkYXRlcyB0aGUgc2VsZWN0ZWQtc3RhdGUgb2YgZWFjaCBub2RlLAogICAgICAgICAqIDIpIHRyaWdnZXJzIGlucHV0IHRyYWNpbmcuCiAgICAgICAgICogQHBhcmFtIHNlbGVjdGVkTm9kZSB7c3RyaW5nfSBUaGUgbmFtZSBvZiB0aGUgbmV3bHkgc2VsZWN0ZWQgbm9kZS4KICAgICAgICAgKiBAcGFyYW0gb2xkU2VsZWN0ZWROb2RlIHtzdHJpbmd9IFRoZSBuYW1lIG9mIHRoZSBwcmV2aW91c2x5IHNlbGVjdGVkIG5vZGUuCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKi8KICAgICAgICBfc2VsZWN0ZWROb2RlQ2hhbmdlZChzZWxlY3RlZE5vZGUsIG9sZFNlbGVjdGVkTm9kZSkgewogICAgICAgICAgICBpZiAoc2VsZWN0ZWROb2RlID09PSBvbGRTZWxlY3RlZE5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob2xkU2VsZWN0ZWROb2RlKSB7CiAgICAgICAgICAgICAgICB0aGlzLl91cGRhdGVOb2RlU3RhdGUob2xkU2VsZWN0ZWROb2RlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoIXNlbGVjdGVkTm9kZSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgbWluaW1hcCB0byByZWZsZWN0IHRoZSBoaWdobGlnaHRlZCAoc2VsZWN0ZWQpIG5vZGUuCiAgICAgICAgICAgIHRoaXMubWluaW1hcC51cGRhdGUoKTsKICAgICAgICAgICAgdmFyIG5vZGUgPSB0aGlzLnJlbmRlckhpZXJhcmNoeS5oaWVyYXJjaHkubm9kZShzZWxlY3RlZE5vZGUpOwogICAgICAgICAgICB2YXIgbm9kZVBhcmVudHMgPSBbXTsKICAgICAgICAgICAgLy8gQ3JlYXRlIGxpc3Qgb2YgYWxsIG1ldGFub2RlIHBhcmVudHMgb2YgdGhlIHNlbGVjdGVkIG5vZGUuCiAgICAgICAgICAgIHdoaWxlIChub2RlLnBhcmVudE5vZGUgIT0gbnVsbCAmJgogICAgICAgICAgICAgICAgbm9kZS5wYXJlbnROb2RlLm5hbWUgIT0gUk9PVF9OQU1FKSB7CiAgICAgICAgICAgICAgICBub2RlID0gbm9kZS5wYXJlbnROb2RlOwogICAgICAgICAgICAgICAgbm9kZVBhcmVudHMucHVzaChub2RlLm5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEVuc3VyZSBlYWNoIHBhcmVudCBtZXRhbm9kZSBpcyBidWlsdCBhbmQgZXhwYW5kZWQuCiAgICAgICAgICAgIHZhciB0b3BQYXJlbnROb2RlVG9CZUV4cGFuZGVkOwogICAgICAgICAgICBsb2Rhc2guZm9yRWFjaFJpZ2h0KG5vZGVQYXJlbnRzLCAocGFyZW50TmFtZSkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5yZW5kZXJIaWVyYXJjaHkuYnVpbGRTdWJoaWVyYXJjaHkocGFyZW50TmFtZSk7CiAgICAgICAgICAgICAgICB2YXIgcmVuZGVyTm9kZSA9IHRoaXMucmVuZGVySGllcmFyY2h5LmdldFJlbmRlck5vZGVCeU5hbWUocGFyZW50TmFtZSk7CiAgICAgICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5ub2RlLmlzR3JvdXBOb2RlICYmICFyZW5kZXJOb2RlLmV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5leHBhbmRlZCA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgaWYgKCF0b3BQYXJlbnROb2RlVG9CZUV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHRvcFBhcmVudE5vZGVUb0JlRXhwYW5kZWQgPSByZW5kZXJOb2RlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIElmIGFueSBleHBhbnNpb24gd2FzIG5lZWRlZCB0byBkaXNwbGF5IHRoaXMgc2VsZWN0ZWQgbm9kZSwgdGhlbgogICAgICAgICAgICAvLyBpbmZvcm0gdGhlIHNjZW5lIG9mIHRoZSB0b3AtbW9zdCBleHBhbnNpb24uCiAgICAgICAgICAgIGlmICh0b3BQYXJlbnROb2RlVG9CZUV4cGFuZGVkKSB7CiAgICAgICAgICAgICAgICB0aGlzLnNldE5vZGVFeHBhbmRlZCh0b3BQYXJlbnROb2RlVG9CZUV4cGFuZGVkKTsKICAgICAgICAgICAgICAgIHRoaXMuX3pvb21lZCA9IHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHNlbGVjdGVkTm9kZSkgewogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlTm9kZVN0YXRlKHNlbGVjdGVkTm9kZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gR2l2ZSB0aW1lIGZvciBhbnkgZXhwYW5kaW5nIHRvIGZpbmlzaCBiZWZvcmUgcGFubmluZyB0byBhIG5vZGUuCiAgICAgICAgICAgIC8vIE90aGVyd2lzZSwgdGhlIHBhbiB3aWxsIGJlIGNvbXB1dGVkIGZyb20gaW5jb3JyZWN0IG1lYXN1cmVtZW50cy4KICAgICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLnBhblRvTm9kZShzZWxlY3RlZE5vZGUpOwogICAgICAgICAgICB9LCBQQVJBTVMkMS5hbmltYXRpb24uZHVyYXRpb24pOwogICAgICAgIH0KICAgICAgICBfaGlnaGxpZ2h0ZWROb2RlQ2hhbmdlZChoaWdobGlnaHRlZE5vZGUsIG9sZEhpZ2hsaWdodGVkTm9kZSkgewogICAgICAgICAgICBpZiAoaGlnaGxpZ2h0ZWROb2RlID09PSBvbGRIaWdobGlnaHRlZE5vZGUpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoaGlnaGxpZ2h0ZWROb2RlKSB7CiAgICAgICAgICAgICAgICB0aGlzLl91cGRhdGVOb2RlU3RhdGUoaGlnaGxpZ2h0ZWROb2RlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob2xkSGlnaGxpZ2h0ZWROb2RlKSB7CiAgICAgICAgICAgICAgICB0aGlzLl91cGRhdGVOb2RlU3RhdGUob2xkSGlnaGxpZ2h0ZWROb2RlKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBfb25ab29tQ2hhbmdlZCgpIHsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlTGFiZWxzKCF0aGlzLl96b29tZWQpOwogICAgICAgIH0KICAgICAgICBfZmlyZUVuYWJsZUNsaWNrKCkgewogICAgICAgICAgICB0aGlzLmZpcmUoJ2VuYWJsZS1jbGljaycpOwogICAgICAgIH0KICAgICAgICAvLyBXaGVuIHJlbmRlckhpZXJhcmNoeSBjaGFuZ2VzLCB3ZSBuZWVkIHRvIGZpcnN0IGJ1aWxkIHRoZSBuZXcgU1ZHIGJhc2VkCiAgICAgICAgLy8gb24gdGhlIG5ldyBoaWVyYXJjaHkgKGFuZCBpdCBpcyBhc3luY2hyb25vdXMpLiBXZSB3aWxsIGxldCB0aGF0IG9ic2VydmVyCiAgICAgICAgLy8gdXBkYXRlIHRoZSBpbnB1dCB0cmFjZS4KICAgICAgICBfdXBkYXRlSW5wdXRUcmFjZSgpIHsKICAgICAgICAgICAgdXBkYXRlSW5wdXRUcmFjZSh0aGlzLmdldEdyYXBoU3ZnUm9vdCgpLCB0aGlzLnJlbmRlckhpZXJhcmNoeSwgdGhpcy5zZWxlY3RlZE5vZGUsIHRoaXMudHJhY2VJbnB1dHMpOwogICAgICAgIH0KICAgIH07CiAgICBUZkdyYXBoU2NlbmUyLnRlbXBsYXRlID0gdGVtcGxhdGUkajsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVuZGVyR3JhcGhJbmZvKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJyZW5kZXJIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIm5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgImNvbG9yQnkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAidHJhY2VJbnB1dHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAiX2hhc1JlbmRlckhpZXJhcmNoeUJlZW5GaXRPbmNlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl9pc0F0dGFjaGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfem9vbSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfaGlnaGxpZ2h0ZWROb2RlQ2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgImhpZ2hsaWdodGVkTm9kZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfc2VsZWN0ZWROb2RlQ2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgInNlbGVjdGVkTm9kZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAiaGFuZGxlRWRnZVNlbGVjdGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfb25ab29tQ2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfem9vbWVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfem9vbVN0YXJ0Q29vcmRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfem9vbVRyYW5zZm9ybSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAiX21heFpvb21EaXN0YW5jZUZvckNsaWNrIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgInRlbXBsYXRlSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIm1pbmltYXAiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl9ub2RlR3JvdXBJbmRleCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAiX2Fubm90YXRpb25Hcm91cEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfZWRnZUdyb3VwSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIm1heE1ldGFub2RlTGFiZWxMZW5ndGhGb250U2l6ZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhTY2VuZTIucHJvdG90eXBlLCAibWluTWV0YW5vZGVMYWJlbExlbmd0aEZvbnRTaXplIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJtYXhNZXRhbm9kZUxhYmVsTGVuZ3RoTGFyZ2VGb250Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJtYXhNZXRhbm9kZUxhYmVsTGVuZ3RoIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJwcm9ncmVzcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIm5vZGVDb250ZXh0TWVudUl0ZW1zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJub2RlTmFtZXNUb0hlYWx0aFBpbGxzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJoZWFsdGhQaWxsU3RlcEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3JlbmRlckhpZXJhcmNoeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaFNjZW5lMi5wcm90b3R5cGUsICJfcmVuZGVySGllcmFyY2h5Q2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX2lzQXR0YWNoZWQnLCAncmVuZGVySGllcmFyY2h5JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl9hbmltYXRlQW5kRml0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdjb2xvckJ5JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl9jb2xvckJ5Q2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnbm9kZU5hbWVzVG9IZWFsdGhQaWxscycsICdoZWFsdGhQaWxsU3RlcEluZGV4JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl91cGRhdGVIZWFsdGhQaWxscyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgndHJhY2VJbnB1dHMnLCAnc2VsZWN0ZWROb2RlJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoU2NlbmUyLnByb3RvdHlwZSwgIl91cGRhdGVJbnB1dFRyYWNlIiwgbnVsbCk7CiAgICBUZkdyYXBoU2NlbmUyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZ3JhcGgtc2NlbmUnKQogICAgXSwgVGZHcmFwaFNjZW5lMik7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZHcmFwaCA9IGNsYXNzIFRmR3JhcGggZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fcmVuZGVyRGVwdGggPSAxOwogICAgICAgICAgICB0aGlzLl9hbGxvd0dyYXBoU2VsZWN0ID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5lZGdlV2lkdGhGdW5jdGlvbiA9ICcnOwogICAgICAgICAgICB0aGlzLmhhbmRsZU5vZGVTZWxlY3RlZCA9ICcnOwogICAgICAgICAgICB0aGlzLmVkZ2VMYWJlbEZ1bmN0aW9uID0gJyc7CiAgICAgICAgICAgIHRoaXMuaGFuZGxlRWRnZVNlbGVjdGVkID0gJyc7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFBhbnMgdG8gYSBub2RlLiBBc3N1bWVzIHRoYXQgdGhlIG5vZGUgZXhpc3RzLgogICAgICAgICAqIEBwYXJhbSBub2RlTmFtZSB7c3RyaW5nfSBUaGUgbmFtZSBvZiB0aGUgbm9kZSB0byBwYW4gdG8uCiAgICAgICAgICovCiAgICAgICAgcGFuVG9Ob2RlKG5vZGVOYW1lKSB7CiAgICAgICAgICAgIHRoaXMuJCQoJ3RmLWdyYXBoLXNjZW5lJykucGFuVG9Ob2RlKG5vZGVOYW1lKTsKICAgICAgICB9CiAgICAgICAgX2J1aWxkTmV3UmVuZGVySGllcmFyY2h5KCkgewogICAgICAgICAgICB2YXIgZ3JhcGhIaWVyYXJjaHkgPSB0aGlzLmdyYXBoSGllcmFyY2h5OwogICAgICAgICAgICBpZiAoIWdyYXBoSGllcmFyY2h5KQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB0aGlzLl9idWlsZFJlbmRlckhpZXJhcmNoeShncmFwaEhpZXJhcmNoeSk7CiAgICAgICAgfQogICAgICAgIF9zdGF0c0NoYW5nZWQoKSB7CiAgICAgICAgICAgIHZhciBzdGF0cyA9IHRoaXMuc3RhdHM7CiAgICAgICAgICAgIHZhciBkZXZpY2VzRm9yU3RhdHMgPSB0aGlzLmRldmljZXNGb3JTdGF0czsKICAgICAgICAgICAgaWYgKHRoaXMuZ3JhcGhIaWVyYXJjaHkpIHsKICAgICAgICAgICAgICAgIGlmIChzdGF0cyAmJiBkZXZpY2VzRm9yU3RhdHMpIHsKICAgICAgICAgICAgICAgICAgICBqb2luU3RhdHNJbmZvV2l0aEdyYXBoKHRoaXMuYmFzaWNHcmFwaCwgc3RhdHMsIGRldmljZXNGb3JTdGF0cyk7CiAgICAgICAgICAgICAgICAgICAgam9pbkFuZEFnZ3JlZ2F0ZVN0YXRzKHRoaXMuZ3JhcGhIaWVyYXJjaHkpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gUmVjb21wdXRlIHRoZSByZW5kZXJpbmcgaW5mb3JtYXRpb24uCiAgICAgICAgICAgICAgICB0aGlzLl9idWlsZFJlbmRlckhpZXJhcmNoeSh0aGlzLmdyYXBoSGllcmFyY2h5KTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdncmFwaC1zZWxlY3QnLCB0aGlzLl9ncmFwaFNlbGVjdGVkLmJpbmQodGhpcykpOwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2Rpc2FibGUtY2xpY2snLCB0aGlzLl9kaXNhYmxlQ2xpY2suYmluZCh0aGlzKSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignZW5hYmxlLWNsaWNrJywgdGhpcy5fZW5hYmxlQ2xpY2suYmluZCh0aGlzKSk7CiAgICAgICAgICAgIC8vIE5vZGVzCiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbm9kZS10b2dnbGUtZXhwYW5kJywgdGhpcy5fbm9kZVRvZ2dsZUV4cGFuZC5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdub2RlLXNlbGVjdCcsIHRoaXMuX25vZGVTZWxlY3RlZC5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdub2RlLWhpZ2hsaWdodCcsIHRoaXMuX25vZGVIaWdobGlnaHRlZC5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdub2RlLXVuaGlnaGxpZ2h0JywgdGhpcy5fbm9kZVVuaGlnaGxpZ2h0ZWQuYmluZCh0aGlzKSk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbm9kZS10b2dnbGUtZXh0cmFjdCcsIHRoaXMuX25vZGVUb2dnbGVFeHRyYWN0LmJpbmQodGhpcykpOwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ25vZGUtdG9nZ2xlLXNlcmllc2dyb3VwJywgdGhpcy5fbm9kZVRvZ2dsZVNlcmllc0dyb3VwLmJpbmQodGhpcykpOwogICAgICAgICAgICAvLyBFZGdlcwogICAgICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2VkZ2Utc2VsZWN0JywgdGhpcy5fZWRnZVNlbGVjdGVkLmJpbmQodGhpcykpOwogICAgICAgICAgICAvLyBBbm5vdGF0aW9ucwogICAgICAgICAgICAvKiBOb3RlOiBjdXJyZW50bHkgaGlnaGxpZ2h0aW5nL3NlbGVjdGluZyBhbm5vdGF0aW9uIG5vZGUgaGFzIHRoZSBzYW1lCiAgICAgICAgICAgICAqIGJlaGF2aW9yIGFzIGhpZ2hsaWdodGluZy9zZWxlY3RpbmcgYWN0dWFsIG5vZGUgc28gd2UgcG9pbnQgdG8gdGhlIHNhbWUKICAgICAgICAgICAgICogc2V0IG9mIGV2ZW50IGxpc3RlbmVycy4gIEhvd2V2ZXIsIHdlIG1pZ2h0IHJlZGVzaWduIHRoaXMgdG8gYmUgYSBiaXQKICAgICAgICAgICAgICogZGlmZmVyZW50LgogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdhbm5vdGF0aW9uLXNlbGVjdCcsIHRoaXMuX25vZGVTZWxlY3RlZC5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdhbm5vdGF0aW9uLWhpZ2hsaWdodCcsIHRoaXMuX25vZGVIaWdobGlnaHRlZC5iaW5kKHRoaXMpKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdhbm5vdGF0aW9uLXVuaGlnaGxpZ2h0JywgdGhpcy5fbm9kZVVuaGlnaGxpZ2h0ZWQuYmluZCh0aGlzKSk7CiAgICAgICAgfQogICAgICAgIF9idWlsZFJlbmRlckhpZXJhcmNoeShncmFwaEhpZXJhcmNoeSkgewogICAgICAgICAgICB0aW1lJDMoJ25ldyB0Zl9ncmFwaF9yZW5kZXIuSGllcmFyY2h5JywgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgaWYgKGdyYXBoSGllcmFyY2h5LnJvb3QudHlwZSAhPT0gTm9kZVR5cGUuTUVUQSkgewogICAgICAgICAgICAgICAgICAgIC8vIHJvb3QgbXVzdCBiZSBtZXRhbm9kZSBidXQgc29tZXRpbWVzIFBvbHltZXIncyBkb20taWYgaGFzIG5vdAogICAgICAgICAgICAgICAgICAgIC8vIHJlbW92ZSB0Zi1ncmFwaCBlbGVtZW50IHlldCBpbiA8dGYtbm9kZS1pbmZvPgogICAgICAgICAgICAgICAgICAgIC8vIGFuZCB0aHVzIG1pc3Rha2VubHkgcGFzcyBub24tbWV0YW5vZGUgdG8gdGhpcyBtb2R1bGUuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgdmFyIHJlbmRlckdyYXBoID0gbmV3IFJlbmRlckdyYXBoSW5mbyhncmFwaEhpZXJhcmNoeSwgISF0aGlzLnN0YXRzIC8qKiBkaXNwbGF5aW5nU3RhdHMgKi8pOwogICAgICAgICAgICAgICAgcmVuZGVyR3JhcGguZWRnZUxhYmVsRnVuY3Rpb24gPSB0aGlzLmVkZ2VMYWJlbEZ1bmN0aW9uOwogICAgICAgICAgICAgICAgcmVuZGVyR3JhcGguZWRnZVdpZHRoRnVuY3Rpb24gPSB0aGlzLmVkZ2VXaWR0aEZ1bmN0aW9uOwogICAgICAgICAgICAgICAgLy8gUHJvZHVjaW5nIHRoZSAnY29sb3IgYnknIHBhcmFtZXRlcnMgdG8gYmUgY29uc3VtZWQKICAgICAgICAgICAgICAgIC8vIGJ5IHRoZSB0Zi1ncmFwaC1jb250cm9scyBwYW5lbC4gSXQgY29udGFpbnMgaW5mb3JtYXRpb24gYWJvdXQgdGhlCiAgICAgICAgICAgICAgICAvLyBtaW4gYW5kIG1heCB2YWx1ZXMgYW5kIHRoZWlyIHJlc3BlY3RpdmUgY29sb3JzLCBhcyB3ZWxsIGFzIGxpc3QKICAgICAgICAgICAgICAgIC8vIG9mIGRldmljZXMgd2l0aCB0aGVpciByZXNwZWN0aXZlIGNvbG9ycy4KICAgICAgICAgICAgICAgIGZ1bmN0aW9uIGdldENvbG9yUGFyYW1zRnJvbVNjYWxlKHNjYWxlKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICAgICAgbWluVmFsdWU6IHNjYWxlLmRvbWFpbigpWzBdLAogICAgICAgICAgICAgICAgICAgICAgICBtYXhWYWx1ZTogc2NhbGUuZG9tYWluKClbMV0sCiAgICAgICAgICAgICAgICAgICAgICAgIHN0YXJ0Q29sb3I6IHNjYWxlLnJhbmdlKClbMF0sCiAgICAgICAgICAgICAgICAgICAgICAgIGVuZENvbG9yOiBzY2FsZS5yYW5nZSgpWzFdLAogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB0aGlzLl9zZXRDb2xvckJ5UGFyYW1zKHsKICAgICAgICAgICAgICAgICAgICBjb21wdXRlX3RpbWU6IGdldENvbG9yUGFyYW1zRnJvbVNjYWxlKHJlbmRlckdyYXBoLmNvbXB1dGVUaW1lU2NhbGUpLAogICAgICAgICAgICAgICAgICAgIG1lbW9yeTogZ2V0Q29sb3JQYXJhbXNGcm9tU2NhbGUocmVuZGVyR3JhcGgubWVtb3J5VXNhZ2VTY2FsZSksCiAgICAgICAgICAgICAgICAgICAgZGV2aWNlOiBsb2Rhc2gubWFwKHJlbmRlckdyYXBoLmRldmljZUNvbG9yTWFwLmRvbWFpbigpLCBmdW5jdGlvbiAoZGV2aWNlTmFtZSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgICAgICAgICAgICAgZGV2aWNlOiBkZXZpY2VOYW1lLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29sb3I6IHJlbmRlckdyYXBoLmRldmljZUNvbG9yTWFwKGRldmljZU5hbWUpLAogICAgICAgICAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgICAgIH0pLAogICAgICAgICAgICAgICAgICAgIHhsYV9jbHVzdGVyOiBsb2Rhc2gubWFwKHJlbmRlckdyYXBoLnhsYUNsdXN0ZXJDb2xvck1hcC5kb21haW4oKSwgZnVuY3Rpb24gKHhsYUNsdXN0ZXJOYW1lKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB4bGFfY2x1c3RlcjogeGxhQ2x1c3Rlck5hbWUsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xvcjogcmVuZGVyR3JhcGgueGxhQ2x1c3RlckNvbG9yTWFwKHhsYUNsdXN0ZXJOYW1lKSwKICAgICAgICAgICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgICAgICB9KSwKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fc2V0UmVuZGVySGllcmFyY2h5KHJlbmRlckdyYXBoKTsKICAgICAgICAgICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuZmlyZSgncmVuZGVyZWQnKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICAgIH0KICAgICAgICBfZ2V0VmlzaWJsZShuYW1lKSB7CiAgICAgICAgICAgIGlmICghbmFtZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIG5hbWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVuZGVySGllcmFyY2h5LmdldE5lYXJlc3RWaXNpYmxlQW5jZXN0b3IobmFtZSk7CiAgICAgICAgfQogICAgICAgIGZpdCgpIHsKICAgICAgICAgICAgdGhpcy4kLnNjZW5lLmZpdCgpOwogICAgICAgIH0KICAgICAgICBfZ3JhcGhDaGFuZ2VkKCkgewogICAgICAgICAgICAvLyBXaGVuIGEgbmV3IGdyYXBoIGlzIGxvYWRlZCwgZmlyZSB0aGlzIGV2ZW50IHNvIHRoYXQgdGhlcmUgaXMgbm8KICAgICAgICAgICAgLy8gaW5mby1jYXJkIGJlaW5nIGRpc3BsYXllZCBmb3IgdGhlIHByZXZpb3VzbHktbG9hZGVkIGdyYXBoLgogICAgICAgICAgICB0aGlzLmZpcmUoJ2dyYXBoLXNlbGVjdCcpOwogICAgICAgIH0KICAgICAgICBfZ3JhcGhTZWxlY3RlZChldmVudCkgewogICAgICAgICAgICAvLyBHcmFwaCBzZWxlY3Rpb24gaXMgbm90IGFsbG93ZWQgZHVyaW5nIGFuIGFjdGl2ZSB6b29tIGV2ZW50LCBhcyB0aGUKICAgICAgICAgICAgLy8gY2xpY2sgc2VlbiBkdXJpbmcgYSB6b29tL3BhbiBpcyBwYXJ0IG9mIHRoZSB6b29taW5nIGFuZCBkb2VzIG5vdAogICAgICAgICAgICAvLyBpbmRpY2F0ZSBhIHVzZXIgZGVzaXJlIHRvIGNsaWNrIG9uIGEgc3BlY2lmaWMgc2VjdGlvbiBvZiB0aGUgZ3JhcGguCiAgICAgICAgICAgIGlmICh0aGlzLl9hbGxvd0dyYXBoU2VsZWN0KSB7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnc2VsZWN0ZWROb2RlJywgbnVsbCk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnc2VsZWN0ZWRFZGdlJywgbnVsbCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVzZXQgdGhpcyB2YXJpYWJsZSBhcyBhIGJ1ZyBpbiBkMyB6b29tIGJlaGF2aW9yIGNhbiBjYXVzZSB6b29tZW5kCiAgICAgICAgICAgIC8vIGNhbGxiYWNrIG5vdCB0byBiZSBjYWxsZWQgaWYgYSByaWdodC1jbGljayBoYXBwZW5zIGR1cmluZyBhIHpvb20gZXZlbnQuCiAgICAgICAgICAgIHRoaXMuX2FsbG93R3JhcGhTZWxlY3QgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBfZGlzYWJsZUNsaWNrKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuX2FsbG93R3JhcGhTZWxlY3QgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgX2VuYWJsZUNsaWNrKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuX2FsbG93R3JhcGhTZWxlY3QgPSB0cnVlOwogICAgICAgIH0KICAgICAgICAvLyBDYWxsZWQgd2hlbiB0aGUgc2VsZWN0ZWQgbm9kZSBjaGFuZ2VzLCBpZSB0aGVyZSBpcyBhIG5ldyBzZWxlY3RlZCBub2RlIG9yCiAgICAgICAgLy8gdGhlIGN1cnJlbnQgb25lIGlzIHVuc2VsZWN0ZWQuCiAgICAgICAgX3NlbGVjdGVkTm9kZUNoYW5nZWQoKSB7CiAgICAgICAgICAgIHZhciBzZWxlY3RlZE5vZGUgPSB0aGlzLnNlbGVjdGVkTm9kZTsKICAgICAgICAgICAgaWYgKHRoaXMuaGFuZGxlTm9kZVNlbGVjdGVkKSB7CiAgICAgICAgICAgICAgICAvLyBBIGhpZ2hlci1sZXZlbCBjb21wb25lbnQgcHJvdmlkZWQgYSBjYWxsYmFjay4gUnVuIGl0LgogICAgICAgICAgICAgICAgdGhpcy5oYW5kbGVOb2RlU2VsZWN0ZWQoc2VsZWN0ZWROb2RlKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvLyBDYWxsZWQgd2hlbiB0aGUgc2VsZWN0ZWQgZWRnZSBjaGFuZ2VzLCBpZSB0aGVyZSBpcyBhIG5ldyBzZWxlY3RlZCBlZGdlIG9yCiAgICAgICAgLy8gdGhlIGN1cnJlbnQgb25lIGlzIHVuc2VsZWN0ZWQuCiAgICAgICAgX3NlbGVjdGVkRWRnZUNoYW5nZWQoKSB7CiAgICAgICAgICAgIHZhciBzZWxlY3RlZEVkZ2UgPSB0aGlzLnNlbGVjdGVkRWRnZTsKICAgICAgICAgICAgdGhpcy5fZGVzZWxlY3RQcmV2aW91c0VkZ2UoKTsKICAgICAgICAgICAgLy8gVmlzdWFsbHkgbWFyayB0aGlzIG5ldyBlZGdlIGFzIHNlbGVjdGVkLgogICAgICAgICAgICBpZiAoc2VsZWN0ZWRFZGdlKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9sYXN0U2VsZWN0ZWRFZGdlR3JvdXAuY2xhc3NlZChDbGFzcyQyLkVkZ2UuU0VMRUNURUQsIHRydWUpOwogICAgICAgICAgICAgICAgLy8gVXBkYXRlIHRoZSBjb2xvciBvZiB0aGUgbWFya2VyIHRvbyBpZiB0aGUgZWRnZSBoYXMgb25lLgogICAgICAgICAgICAgICAgdGhpcy5fdXBkYXRlTWFya2VyT2ZTZWxlY3RlZEVkZ2Uoc2VsZWN0ZWRFZGdlKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5oYW5kbGVFZGdlU2VsZWN0ZWQpIHsKICAgICAgICAgICAgICAgIC8vIEEgaGlnaGVyLWxldmVsIGNvbXBvbmVudCBwcm92aWRlZCBhIGNhbGxiYWNrLiBSdW4gaXQuCiAgICAgICAgICAgICAgICB0aGlzLmhhbmRsZUVkZ2VTZWxlY3RlZChzZWxlY3RlZEVkZ2UpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIENhbGxlZCBvbmx5IHdoZW4gYSBuZXcgKG5vbi1udWxsKSBub2RlIGlzIHNlbGVjdGVkLgogICAgICAgIF9ub2RlU2VsZWN0ZWQoZXZlbnQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2FsbG93R3JhcGhTZWxlY3QpIHsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdzZWxlY3RlZE5vZGUnLCBldmVudC5kZXRhaWwubmFtZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVzZXQgdGhpcyB2YXJpYWJsZSBhcyBhIGJ1ZyBpbiBkMyB6b29tIGJlaGF2aW9yIGNhbiBjYXVzZSB6b29tZW5kCiAgICAgICAgICAgIC8vIGNhbGxiYWNrIG5vdCB0byBiZSBjYWxsZWQgaWYgYSByaWdodC1jbGljayBoYXBwZW5zIGR1cmluZyBhIHpvb20gZXZlbnQuCiAgICAgICAgICAgIHRoaXMuX2FsbG93R3JhcGhTZWxlY3QgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBfZWRnZVNlbGVjdGVkKGV2ZW50KSB7CiAgICAgICAgICAgIGlmICh0aGlzLl9hbGxvd0dyYXBoU2VsZWN0KSB7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX2xhc3RTZWxlY3RlZEVkZ2VHcm91cCcsIGV2ZW50LmRldGFpbC5lZGdlR3JvdXApOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ3NlbGVjdGVkRWRnZScsIGV2ZW50LmRldGFpbC5lZGdlRGF0YSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVzZXQgdGhpcyB2YXJpYWJsZSBhcyBhIGJ1ZyBpbiBkMyB6b29tIGJlaGF2aW9yIGNhbiBjYXVzZSB6b29tZW5kCiAgICAgICAgICAgIC8vIGNhbGxiYWNrIG5vdCB0byBiZSBjYWxsZWQgaWYgYSByaWdodC1jbGljayBoYXBwZW5zIGR1cmluZyBhIHpvb20gZXZlbnQuCiAgICAgICAgICAgIHRoaXMuX2FsbG93R3JhcGhTZWxlY3QgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBfbm9kZUhpZ2hsaWdodGVkKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdoaWdobGlnaHRlZE5vZGUnLCBldmVudC5kZXRhaWwubmFtZSk7CiAgICAgICAgfQogICAgICAgIF9ub2RlVW5oaWdobGlnaHRlZChldmVudCkgewogICAgICAgICAgICB0aGlzLnNldCgnaGlnaGxpZ2h0ZWROb2RlJywgbnVsbCk7CiAgICAgICAgfQogICAgICAgIF9ub2RlVG9nZ2xlRXhwYW5kKGV2ZW50KSB7CiAgICAgICAgICAgIC8vIEltbWVkaWF0ZWx5IHNlbGVjdCB0aGUgbm9kZSB0aGF0IGlzIGFib3V0IHRvIGJlIGV4cGFuZGVkLgogICAgICAgICAgICB0aGlzLl9ub2RlU2VsZWN0ZWQoZXZlbnQpOwogICAgICAgICAgICAvLyBDb21wdXRlIHRoZSBzdWItaGllcmFyY2h5IHNjZW5lLgogICAgICAgICAgICB2YXIgbm9kZU5hbWUgPSBldmVudC5kZXRhaWwubmFtZTsKICAgICAgICAgICAgdmFyIHJlbmRlck5vZGUgPSB0aGlzLnJlbmRlckhpZXJhcmNoeS5nZXRSZW5kZXJOb2RlQnlOYW1lKG5vZGVOYW1lKTsKICAgICAgICAgICAgLy8gT3Agbm9kZXMgYXJlIG5vdCBleHBhbmRhYmxlLgogICAgICAgICAgICBpZiAocmVuZGVyTm9kZS5ub2RlLnR5cGUgPT09IE5vZGVUeXBlLk9QKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5yZW5kZXJIaWVyYXJjaHkuYnVpbGRTdWJoaWVyYXJjaHkobm9kZU5hbWUpOwogICAgICAgICAgICByZW5kZXJOb2RlLmV4cGFuZGVkID0gIXJlbmRlck5vZGUuZXhwYW5kZWQ7CiAgICAgICAgICAgIC8vIEV4cGFuZCB0aGUgbm9kZSB3aXRoIHNvbWUgZGVsYXkgc28gdGhhdCB0aGUgdXNlciBjYW4gaW1tZWRpYXRlbHkgc2VlCiAgICAgICAgICAgIC8vIHRoZSB2aXN1YWwgZWZmZWN0IG9mIHNlbGVjdGluZyB0aGF0IG5vZGUsIGJlZm9yZSB0aGUgZXhwYW5zaW9uIGlzCiAgICAgICAgICAgIC8vIGRvbmUuCiAgICAgICAgICAgIHRoaXMuYXN5bmMoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgdGhpcy4kLnNjZW5lLnNldE5vZGVFeHBhbmRlZChyZW5kZXJOb2RlKTsKICAgICAgICAgICAgfSwgNzUpOwogICAgICAgIH0KICAgICAgICBfbm9kZVRvZ2dsZUV4dHJhY3QoZXZlbnQpIHsKICAgICAgICAgICAgLy8gVG9nZ2xlIHRoZSBpbmNsdWRlIHNldHRpbmcgb2YgdGhlIHNwZWNpZmllZCBub2RlIGFwcHJvcHJpYXRlbHkuCiAgICAgICAgICAgIHZhciBub2RlTmFtZSA9IGV2ZW50LmRldGFpbC5uYW1lOwogICAgICAgICAgICB0aGlzLm5vZGVUb2dnbGVFeHRyYWN0KG5vZGVOYW1lKTsKICAgICAgICB9CiAgICAgICAgbm9kZVRvZ2dsZUV4dHJhY3Qobm9kZU5hbWUpIHsKICAgICAgICAgICAgdmFyIHJlbmRlck5vZGUgPSB0aGlzLnJlbmRlckhpZXJhcmNoeS5nZXRSZW5kZXJOb2RlQnlOYW1lKG5vZGVOYW1lKTsKICAgICAgICAgICAgaWYgKHJlbmRlck5vZGUubm9kZS5pbmNsdWRlID09IEluY2x1c2lvblR5cGUuSU5DTFVERSkgewogICAgICAgICAgICAgICAgcmVuZGVyTm9kZS5ub2RlLmluY2x1ZGUgPSBJbmNsdXNpb25UeXBlLkVYQ0xVREU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAocmVuZGVyTm9kZS5ub2RlLmluY2x1ZGUgPT0gSW5jbHVzaW9uVHlwZS5FWENMVURFKSB7CiAgICAgICAgICAgICAgICByZW5kZXJOb2RlLm5vZGUuaW5jbHVkZSA9IEluY2x1c2lvblR5cGUuSU5DTFVERTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJlbmRlck5vZGUubm9kZS5pbmNsdWRlID0gdGhpcy5yZW5kZXJIaWVyYXJjaHkuaXNOb2RlQXV4aWxpYXJ5KHJlbmRlck5vZGUpCiAgICAgICAgICAgICAgICAgICAgPyBJbmNsdXNpb25UeXBlLklOQ0xVREUKICAgICAgICAgICAgICAgICAgICA6IEluY2x1c2lvblR5cGUuRVhDTFVERTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZWJ1aWxkIHRoZSByZW5kZXIgaGllcmFyY2h5LgogICAgICAgICAgICB0aGlzLl9idWlsZFJlbmRlckhpZXJhcmNoeSh0aGlzLmdyYXBoSGllcmFyY2h5KTsKICAgICAgICB9CiAgICAgICAgX25vZGVUb2dnbGVTZXJpZXNHcm91cChldmVudCkgewogICAgICAgICAgICAvLyBUb2dnbGUgdGhlIGdyb3VwIHNldHRpbmcgb2YgdGhlIHNwZWNpZmllZCBub2RlIGFwcHJvcHJpYXRlbHkuCiAgICAgICAgICAgIHZhciBub2RlTmFtZSA9IGV2ZW50LmRldGFpbC5uYW1lOwogICAgICAgICAgICB0aGlzLm5vZGVUb2dnbGVTZXJpZXNHcm91cChub2RlTmFtZSk7CiAgICAgICAgfQogICAgICAgIG5vZGVUb2dnbGVTZXJpZXNHcm91cChub2RlTmFtZSkgewogICAgICAgICAgICAvLyBUb2dnbGUgdGhlIGdyb3VwIHNldHRpbmcgb2YgdGhlIHNwZWNpZmllZCBub2RlIGFwcHJvcHJpYXRlbHkuCiAgICAgICAgICAgIHRvZ2dsZU5vZGVTZXJpZXNHcm91cCh0aGlzLmhpZXJhcmNoeVBhcmFtcy5zZXJpZXNNYXAsIG5vZGVOYW1lKTsKICAgICAgICAgICAgLy8gUmVidWlsZCB0aGUgcmVuZGVyIGhpZXJhcmNoeSB3aXRoIHRoZSB1cGRhdGVkIHNlcmllcyBncm91cGluZyBtYXAuCiAgICAgICAgICAgIHRoaXMuc2V0KCdwcm9ncmVzcycsIHsKICAgICAgICAgICAgICAgIHZhbHVlOiAwLAogICAgICAgICAgICAgICAgbXNnOiAnJywKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciB0cmFja2VyID0gZ2V0VHJhY2tlcih0aGlzKTsKICAgICAgICAgICAgdmFyIGhpZXJhcmNoeVRyYWNrZXIgPSBnZXRTdWJ0YXNrVHJhY2tlcih0cmFja2VyLCAxMDAsICdOYW1lc3BhY2UgaGllcmFyY2h5Jyk7CiAgICAgICAgICAgIGJ1aWxkJDEodGhpcy5iYXNpY0dyYXBoLCB0aGlzLmhpZXJhcmNoeVBhcmFtcywgaGllcmFyY2h5VHJhY2tlcikKICAgICAgICAgICAgICAgIC50aGVuKGZ1bmN0aW9uIChncmFwaEhpZXJhcmNoeSkgewogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ2dyYXBoSGllcmFyY2h5JywgZ3JhcGhIaWVyYXJjaHkpOwogICAgICAgICAgICAgICAgdGhpcy5fYnVpbGRSZW5kZXJIaWVyYXJjaHkodGhpcy5ncmFwaEhpZXJhcmNoeSk7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgfQogICAgICAgIF9kZXNlbGVjdFByZXZpb3VzRWRnZSgpIHsKICAgICAgICAgICAgY29uc3Qgc2VsZWN0ZWRTZWxlY3RvciA9ICcuJyArIENsYXNzJDIuRWRnZS5TRUxFQ1RFRDsKICAgICAgICAgICAgLy8gVmlzdWFsbHkgbWFyayB0aGUgcHJldmlvdXNseSBzZWxlY3RlZCBlZGdlIChpZiBhbnkpIGFzIGRlc2VsZWN0ZWQuCiAgICAgICAgICAgIHNlbGVjdChzZWxlY3RlZFNlbGVjdG9yKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoQ2xhc3MkMi5FZGdlLlNFTEVDVEVELCBmYWxzZSkKICAgICAgICAgICAgICAgIC5lYWNoKChkLCBpKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBSZXNldCBpdHMgbWFya2VyLgogICAgICAgICAgICAgICAgaWYgKGQubGFiZWwpIHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBwYXRocyA9IHNlbGVjdCh0aGlzKS5zZWxlY3RBbGwoJ3BhdGguZWRnZWxpbmUnKTsKICAgICAgICAgICAgICAgICAgICBpZiAoZC5sYWJlbC5zdGFydE1hcmtlcklkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHBhdGhzLnN0eWxlKCdtYXJrZXItc3RhcnQnLCBgdXJsKCMke2QubGFiZWwuc3RhcnRNYXJrZXJJZH0pYCk7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmIChkLmxhYmVsLmVuZE1hcmtlcklkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHBhdGhzLnN0eWxlKCdtYXJrZXItZW5kJywgYHVybCgjJHtkLmxhYmVsLmVuZE1hcmtlcklkfSlgKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfdXBkYXRlTWFya2VyT2ZTZWxlY3RlZEVkZ2Uoc2VsZWN0ZWRFZGdlKSB7CiAgICAgICAgICAgIGlmIChzZWxlY3RlZEVkZ2UubGFiZWwpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSBtYXJrZXIgd2lsbCB2YXJ5IGJhc2VkIG9uIHRoZSBkaXJlY3Rpb24gb2YgdGhlIGVkZ2UuCiAgICAgICAgICAgICAgICBjb25zdCBtYXJrZXJJZCA9IHNlbGVjdGVkRWRnZS5sYWJlbC5zdGFydE1hcmtlcklkIHx8IHNlbGVjdGVkRWRnZS5sYWJlbC5lbmRNYXJrZXJJZDsKICAgICAgICAgICAgICAgIGlmIChtYXJrZXJJZCkgewogICAgICAgICAgICAgICAgICAgIC8vIEZpbmQgdGhlIGNvcnJlc3BvbmRpbmcgbWFya2VyIGZvciBhIHNlbGVjdGVkIGVkZ2UuCiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2VsZWN0ZWRNYXJrZXJJZCA9IG1hcmtlcklkLnJlcGxhY2UoJ2RhdGFmbG93LScsICdzZWxlY3RlZC0nKTsKICAgICAgICAgICAgICAgICAgICBsZXQgc2VsZWN0ZWRNYXJrZXIgPSB0aGlzLiQkKCcjJyArIHNlbGVjdGVkTWFya2VySWQpOwogICAgICAgICAgICAgICAgICAgIGlmICghc2VsZWN0ZWRNYXJrZXIpIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gVGhlIG1hcmtlciBmb3IgYSBzZWxlY3RlZCBlZGdlIG9mIHRoaXMgc2l6ZSBkb2VzIG5vdCBleGlzdCB5ZXQuIENyZWF0ZSBpdC4KICAgICAgICAgICAgICAgICAgICAgICAgY29uc3Qgb3JpZ2luYWxNYXJrZXIgPSB0aGlzLiQuc2NlbmUucXVlcnlTZWxlY3RvcignIycgKyBtYXJrZXJJZCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHNlbGVjdGVkTWFya2VyID0gb3JpZ2luYWxNYXJrZXIuY2xvbmVOb2RlKHRydWUpOwogICAgICAgICAgICAgICAgICAgICAgICBzZWxlY3RlZE1hcmtlci5zZXRBdHRyaWJ1dGUoJ2lkJywgc2VsZWN0ZWRNYXJrZXJJZCk7CiAgICAgICAgICAgICAgICAgICAgICAgIHNlbGVjdGVkTWFya2VyLmNsYXNzTGlzdC5hZGQoJ3NlbGVjdGVkLWFycm93aGVhZCcpOwogICAgICAgICAgICAgICAgICAgICAgICBvcmlnaW5hbE1hcmtlci5wYXJlbnROb2RlLmFwcGVuZENoaWxkKHNlbGVjdGVkTWFya2VyKTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgLy8gTWFrZSB0aGUgcGF0aCB1c2UgdGhpcyBuZXcgbWFya2VyIHdoaWxlIGl0IGlzIHNlbGVjdGVkLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IG1hcmtlckF0dHJpYnV0ZSA9IHNlbGVjdGVkRWRnZS5sYWJlbC5zdGFydE1hcmtlcklkCiAgICAgICAgICAgICAgICAgICAgICAgID8gJ21hcmtlci1zdGFydCcKICAgICAgICAgICAgICAgICAgICAgICAgOiAnbWFya2VyLWVuZCc7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fbGFzdFNlbGVjdGVkRWRnZUdyb3VwCiAgICAgICAgICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJ3BhdGguZWRnZWxpbmUnKQogICAgICAgICAgICAgICAgICAgICAgICAuc3R5bGUobWFya2VyQXR0cmlidXRlLCBgdXJsKCMke3NlbGVjdGVkTWFya2VySWR9KWApOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIG5vdCh4KSB7CiAgICAgICAgICAgIHJldHVybiAheDsKICAgICAgICB9CiAgICB9OwogICAgVGZHcmFwaC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHN0eWxlPgogICAgICAuY29udGFpbmVyIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgYmFja2dyb3VuZDogd2hpdGU7CiAgICAgICAgYm94LXNoYWRvdzogMCAxcHggNXB4IHJnYmEoMCwgMCwgMCwgMC4yKTsKICAgICAgfQoKICAgICAgLnZlcnRpY2FsIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LXZlcnRpY2FsOwogICAgICB9CgogICAgICAuYXV0byB7CiAgICAgICAgQGFwcGx5IC0tbGF5b3V0LWZsZXgtYXV0bzsKICAgICAgICBAYXBwbHkgLS1sYXlvdXQtdmVydGljYWw7CiAgICAgIH0KCiAgICAgIGgyIHsKICAgICAgICB0ZXh0LWFsaWduOiBjZW50ZXI7CiAgICAgIH0KCiAgICAgIHBhcGVyLWJ1dHRvbiB7CiAgICAgICAgdGV4dC10cmFuc2Zvcm06IG5vbmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgICA8ZGl2IGNsYXNzPSJjb250YWluZXIiPgogICAgICA8ZGl2IGNsYXNzPSJ2ZXJ0aWNhbCI+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW3RpdGxlXV0iPgogICAgICAgICAgPGgyPltbdGl0bGVdXTwvaDI+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8dGYtZ3JhcGgtc2NlbmUKICAgICAgICAgIGlkPSJzY2VuZSIKICAgICAgICAgIGNsYXNzPSJhdXRvIgogICAgICAgICAgcmVuZGVyLWhpZXJhcmNoeT0iW1tyZW5kZXJIaWVyYXJjaHldXSIKICAgICAgICAgIGhpZ2hsaWdodGVkLW5vZGU9IltbX2dldFZpc2libGUoaGlnaGxpZ2h0ZWROb2RlKV1dIgogICAgICAgICAgc2VsZWN0ZWQtbm9kZT0ie3tzZWxlY3RlZE5vZGV9fSIKICAgICAgICAgIHNlbGVjdGVkLWVkZ2U9Int7c2VsZWN0ZWRFZGdlfX0iCiAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICBwcm9ncmVzcz0iW1twcm9ncmVzc11dIgogICAgICAgICAgbm9kZS1jb250ZXh0LW1lbnUtaXRlbXM9Iltbbm9kZUNvbnRleHRNZW51SXRlbXNdXSIKICAgICAgICAgIG5vZGUtbmFtZXMtdG8taGVhbHRoLXBpbGxzPSJbW25vZGVOYW1lc1RvSGVhbHRoUGlsbHNdXSIKICAgICAgICAgIGhlYWx0aC1waWxsLXN0ZXAtaW5kZXg9Int7aGVhbHRoUGlsbFN0ZXBJbmRleH19IgogICAgICAgICAgaGFuZGxlLWVkZ2Utc2VsZWN0ZWQ9IltbaGFuZGxlRWRnZVNlbGVjdGVkXV0iCiAgICAgICAgICB0cmFjZS1pbnB1dHM9IltbdHJhY2VJbnB1dHNdXSIKICAgICAgICA+PC90Zi1ncmFwaC1zY2VuZT4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZ3JhcGhDaGFuZ2VkJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAiZ3JhcGhIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImJhc2ljR3JhcGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgInN0YXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJkZXZpY2VzRm9yU3RhdHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImhpZXJhcmNoeVBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJwcm9ncmVzcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAidGl0bGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAic2VsZWN0ZWROb2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgInNlbGVjdGVkRWRnZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAiX2xhc3RTZWxlY3RlZEVkZ2VHcm91cCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJoaWdobGlnaHRlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImNvbG9yQnkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImNvbG9yQnlQYXJhbXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgInJlbmRlckhpZXJhcmNoeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJ0cmFjZUlucHV0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgIm5vZGVDb250ZXh0TWVudUl0ZW1zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJfcmVuZGVyRGVwdGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAiX2FsbG93R3JhcGhTZWxlY3QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgIm5vZGVOYW1lc1RvSGVhbHRoUGlsbHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImhlYWx0aFBpbGxTdGVwSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImVkZ2VXaWR0aEZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJoYW5kbGVOb2RlU2VsZWN0ZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoLnByb3RvdHlwZSwgImVkZ2VMYWJlbEZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJoYW5kbGVFZGdlU2VsZWN0ZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnZ3JhcGhIaWVyYXJjaHknLCAnZWRnZVdpZHRoRnVuY3Rpb24nLCAnaGFuZGxlTm9kZVNlbGVjdGVkJywgJ2VkZ2VMYWJlbEZ1bmN0aW9uJywgJ2hhbmRsZUVkZ2VTZWxlY3RlZCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJfYnVpbGROZXdSZW5kZXJIaWVyYXJjaHkiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3N0YXRzJywgJ2RldmljZXNGb3JTdGF0cycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJfc3RhdHNDaGFuZ2VkIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdzZWxlY3RlZE5vZGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmR3JhcGgucHJvdG90eXBlLCAiX3NlbGVjdGVkTm9kZUNoYW5nZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3NlbGVjdGVkRWRnZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaC5wcm90b3R5cGUsICJfc2VsZWN0ZWRFZGdlQ2hhbmdlZCIsIG51bGwpOwogICAgVGZHcmFwaCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWdyYXBoJykKICAgIF0sIFRmR3JhcGgpOwoKICAgIC8qKgogICAgICogRWxlbWVudCBmb3IgcHV0dGluZyB0Zi1ncmFwaCBhbmQgdGYtZ3JhcGgtaW5mbyBzaWRlIGJ5IHNpZGUuCiAgICAgKgogICAgICogRXhhbXBsZQogICAgICogPHRmLWdyYXBoLWJvYXJkIGdyYXBoPVtbZ3JhcGhdXT48L3RmLWdyYXBoLWJvYXJkPgogICAgICovCiAgICBsZXQgVGZHcmFwaEJvYXJkID0gY2xhc3MgVGZHcmFwaEJvYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8vIFdoZXRoZXIgdGhlIHVzZXIgY2FuIHJlcXVlc3QgaGVhbHRoIHBpbGxzIGZvciBpbmRpdmlkdWFsIHN0ZXBzIGZyb20gdGhlIHNlcnZlci4gVGhpcyBjYW4gYmUKICAgICAgICAgICAgLy8gc2xvdyBjb21wYXJlZCB0aGUgZGVmYXVsdCBvZiBzaG93aW5nIHNhbXBsZWQgaGVhbHRoIHBpbGxzLgogICAgICAgICAgICB0aGlzLmFsbFN0ZXBzTW9kZUVuYWJsZWQgPSBmYWxzZTsKICAgICAgICAgICAgLy8gUmVsZXZhbnQgaWYgYWxsU3RlcHNNb2RlRW5hYmxlZC4gVGhlIHNwZWNpZmljIHN0ZXAgZm9yIHdoaWNoIHRvIGZldGNoIGhlYWx0aCBwaWxscyBmcm9tIHRoZQogICAgICAgICAgICAvLyBzZXJ2ZXIgZm9yLgogICAgICAgICAgICB0aGlzLnNwZWNpZmljSGVhbHRoUGlsbFN0ZXAgPSAwOwogICAgICAgICAgICB0aGlzLmNvbXBhdE5vZGVUaXRsZSA9ICdUUFUgQ29tcGF0aWJpbGl0eSc7CiAgICAgICAgfQogICAgICAgIGZpdCgpIHsKICAgICAgICAgICAgdGhpcy4kLmdyYXBoLmZpdCgpOwogICAgICAgIH0KICAgICAgICAvKiogVHJ1ZSBpZiB0aGUgcHJvZ3Jlc3MgaXMgbm90IGNvbXBsZXRlIHlldCAoPCAxMDAgJSkuICovCiAgICAgICAgX2lzTm90Q29tcGxldGUocHJvZ3Jlc3MpIHsKICAgICAgICAgICAgcmV0dXJuIHByb2dyZXNzLnZhbHVlIDwgMTAwOwogICAgICAgIH0KICAgICAgICBfZ2V0Q29udGFpbmVyQ2xhc3MocHJvZ3Jlc3MpIHsKICAgICAgICAgICAgdmFyIHJlc3VsdCA9ICdjb250YWluZXInOwogICAgICAgICAgICBpZiAocHJvZ3Jlc3MuZXJyb3IpIHsKICAgICAgICAgICAgICAgIHJlc3VsdCArPSAnIGVycm9yJzsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5faXNOb3RDb21wbGV0ZShwcm9ncmVzcykpIHsKICAgICAgICAgICAgICAgIHJlc3VsdCArPSAnIGxvYWRpbmcnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgICAgfQogICAgICAgIF9vbk5vZGVJbmNsdXNpb25Ub2dnbGVkKGV2ZW50KSB7CiAgICAgICAgICAgIHRoaXMuJC5ncmFwaC5ub2RlVG9nZ2xlRXh0cmFjdChldmVudC5kZXRhaWwubmFtZSk7CiAgICAgICAgfQogICAgICAgIF9vbk5vZGVTZXJpZXNHcm91cFRvZ2dsZWQoZXZlbnQpIHsKICAgICAgICAgICAgdGhpcy4kLmdyYXBoLm5vZGVUb2dnbGVTZXJpZXNHcm91cChldmVudC5kZXRhaWwubmFtZSk7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVOb2RlSW5jbHVkZSgpIHsKICAgICAgICAgICAgY29uc3Qgbm9kZSA9ICF0aGlzLnJlbmRlckhpZXJhcmNoeQogICAgICAgICAgICAgICAgPyBudWxsCiAgICAgICAgICAgICAgICA6IHRoaXMucmVuZGVySGllcmFyY2h5LmdldE5vZGVCeU5hbWUodGhpcy5zZWxlY3RlZE5vZGUpOwogICAgICAgICAgICB0aGlzLl9zZWxlY3RlZE5vZGVJbmNsdWRlID0gbm9kZQogICAgICAgICAgICAgICAgPyBub2RlLmluY2x1ZGUKICAgICAgICAgICAgICAgIDogSW5jbHVzaW9uVHlwZS5VTlNQRUNJRklFRDsKICAgICAgICB9CiAgICB9OwogICAgVGZHcmFwaEJvYXJkLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8c3R5bGU+CiAgICAgIDo6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KCiAgICAgIC9kZWVwLyAuY2xvc2UgewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgICAgbGVmdDogMTVweDsKICAgICAgICBib3R0b206IDE1cHg7CiAgICAgIH0KCiAgICAgIC5jb250YWluZXIgewogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICB9CgogICAgICAuY29udGFpbmVyLmxvYWRpbmcgewogICAgICAgIGN1cnNvcjogcHJvZ3Jlc3M7CiAgICAgICAgb3BhY2l0eTogMC4xOwogICAgICB9CgogICAgICAuY29udGFpbmVyLmxvYWRpbmcuZXJyb3IgewogICAgICAgIGN1cnNvcjogYXV0bzsKICAgICAgfQoKICAgICAgI2luZm8gewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICByaWdodDogNXB4OwogICAgICAgIHRvcDogNXB4OwogICAgICAgIHBhZGRpbmc6IDBweDsKICAgICAgICBtYXgtd2lkdGg6IDM4MHB4OwogICAgICAgIG1pbi13aWR0aDogMzIwcHg7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogcmdiYSgyNTUsIDI1NSwgMjU1LCAwLjkpOwogICAgICAgIEBhcHBseSAtLXNoYWRvdy1lbGV2YXRpb24tMmRwOwogICAgICB9CgogICAgICAjbWFpbiB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CgogICAgICAjcHJvZ3Jlc3MtYmFyIHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiA0MHB4OwogICAgICAgIGxlZnQ6IDA7CiAgICAgICAgZm9udC1zaXplOiAxM3B4OwogICAgICB9CgogICAgICAjcHJvZ3Jlc3MtbXNnIHsKICAgICAgICBtYXJnaW4tYm90dG9tOiA1cHg7CiAgICAgICAgd2hpdGUtc3BhY2U6IHByZS13cmFwOwogICAgICAgIHdpZHRoOiA0MDBweDsKICAgICAgfQoKICAgICAgcGFwZXItcHJvZ3Jlc3MgewogICAgICAgIHdpZHRoOiA0MDBweDsKICAgICAgICAtLXBhcGVyLXByb2dyZXNzLWhlaWdodDogNnB4OwogICAgICAgIC0tcGFwZXItcHJvZ3Jlc3MtYWN0aXZlLWNvbG9yOiAjZjM5MTNlOwogICAgICB9CgogICAgICAuY29udGV4dC1tZW51IHsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgZGlzcGxheTogbm9uZTsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZTJlMmUyOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDJweDsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgbWluLXdpZHRoOiAxNTBweDsKICAgICAgICBib3JkZXI6IDFweCBzb2xpZCAjZDRkNGQ0OwogICAgICB9CgogICAgICAvZGVlcC8gLmNvbnRleHQtbWVudSB1bCB7CiAgICAgICAgbGlzdC1zdHlsZS10eXBlOiBub25lOwogICAgICAgIG1hcmdpbjogMDsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICAgIGN1cnNvcjogZGVmYXVsdDsKICAgICAgfQoKICAgICAgL2RlZXAvIC5jb250ZXh0LW1lbnUgdWwgbGkgewogICAgICAgIHBhZGRpbmc6IDRweCAxNnB4OwogICAgICB9CgogICAgICAvZGVlcC8gLmNvbnRleHQtbWVudSB1bCBsaTpob3ZlciB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2YzOTEzZTsKICAgICAgICBjb2xvcjogd2hpdGU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2lzTm90Q29tcGxldGUocHJvZ3Jlc3MpXV0iPgogICAgICA8ZGl2IGlkPSJwcm9ncmVzcy1iYXIiPgogICAgICAgIDxkaXYgaWQ9InByb2dyZXNzLW1zZyI+W1twcm9ncmVzcy5tc2ddXTwvZGl2PgogICAgICAgIDxwYXBlci1wcm9ncmVzcyB2YWx1ZT0iW1twcm9ncmVzcy52YWx1ZV1dIj48L3BhcGVyLXByb2dyZXNzPgogICAgICA8L2Rpdj4KICAgIDwvdGVtcGxhdGU+CiAgICA8ZGl2IGNsYXNzJD0iW1tfZ2V0Q29udGFpbmVyQ2xhc3MocHJvZ3Jlc3MpXV0iPgogICAgICA8ZGl2IGlkPSJtYWluIj4KICAgICAgICA8dGYtZ3JhcGgKICAgICAgICAgIGlkPSJncmFwaCIKICAgICAgICAgIGdyYXBoLWhpZXJhcmNoeT0ie3tncmFwaEhpZXJhcmNoeX19IgogICAgICAgICAgYmFzaWMtZ3JhcGg9IltbZ3JhcGhdXSIKICAgICAgICAgIGhpZXJhcmNoeS1wYXJhbXM9IltbaGllcmFyY2h5UGFyYW1zXV0iCiAgICAgICAgICByZW5kZXItaGllcmFyY2h5PSJ7e3JlbmRlckhpZXJhcmNoeX19IgogICAgICAgICAgZGV2aWNlcy1mb3Itc3RhdHM9IltbZGV2aWNlc0ZvclN0YXRzXV0iCiAgICAgICAgICBzdGF0cz0iW1tzdGF0c11dIgogICAgICAgICAgc2VsZWN0ZWQtbm9kZT0ie3tzZWxlY3RlZE5vZGV9fSIKICAgICAgICAgIGhpZ2hsaWdodGVkLW5vZGU9Int7X2hpZ2hsaWdodGVkTm9kZX19IgogICAgICAgICAgY29sb3ItYnk9IltbY29sb3JCeV1dIgogICAgICAgICAgY29sb3ItYnktcGFyYW1zPSJ7e2NvbG9yQnlQYXJhbXN9fSIKICAgICAgICAgIHByb2dyZXNzPSJ7e3Byb2dyZXNzfX0iCiAgICAgICAgICBlZGdlLWxhYmVsLWZ1bmN0aW9uPSJbW2VkZ2VMYWJlbEZ1bmN0aW9uXV0iCiAgICAgICAgICBlZGdlLXdpZHRoLWZ1bmN0aW9uPSJbW2VkZ2VXaWR0aEZ1bmN0aW9uXV0iCiAgICAgICAgICBub2RlLW5hbWVzLXRvLWhlYWx0aC1waWxscz0iW1tub2RlTmFtZXNUb0hlYWx0aFBpbGxzXV0iCiAgICAgICAgICBoZWFsdGgtcGlsbC1zdGVwLWluZGV4PSJbW2hlYWx0aFBpbGxTdGVwSW5kZXhdXSIKICAgICAgICAgIGhhbmRsZS1ub2RlLXNlbGVjdGVkPSJbW2hhbmRsZU5vZGVTZWxlY3RlZF1dIgogICAgICAgICAgaGFuZGxlLWVkZ2Utc2VsZWN0ZWQ9IltbaGFuZGxlRWRnZVNlbGVjdGVkXV0iCiAgICAgICAgICB0cmFjZS1pbnB1dHM9IltbdHJhY2VJbnB1dHNdXSIKICAgICAgICA+PC90Zi1ncmFwaD4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgaWQ9ImluZm8iPgogICAgICAgIDx0Zi1ncmFwaC1pbmZvCiAgICAgICAgICBpZD0iZ3JhcGgtaW5mbyIKICAgICAgICAgIHRpdGxlPSJzZWxlY3RlZCIKICAgICAgICAgIGdyYXBoLWhpZXJhcmNoeT0iW1tncmFwaEhpZXJhcmNoeV1dIgogICAgICAgICAgaGllcmFyY2h5LXBhcmFtcz0iW1toaWVyYXJjaHlQYXJhbXNdXSIKICAgICAgICAgIHJlbmRlci1oaWVyYXJjaHk9IltbcmVuZGVySGllcmFyY2h5XV0iCiAgICAgICAgICBncmFwaD0iW1tncmFwaF1dIgogICAgICAgICAgc2VsZWN0ZWQtbm9kZT0ie3tzZWxlY3RlZE5vZGV9fSIKICAgICAgICAgIHNlbGVjdGVkLW5vZGUtaW5jbHVkZT0ie3tfc2VsZWN0ZWROb2RlSW5jbHVkZX19IgogICAgICAgICAgaGlnaGxpZ2h0ZWQtbm9kZT0ie3tfaGlnaGxpZ2h0ZWROb2RlfX0iCiAgICAgICAgICBjb2xvci1ieT0iW1tjb2xvckJ5XV0iCiAgICAgICAgICBjb2xvci1ieS1wYXJhbXM9IltbY29sb3JCeVBhcmFtc11dIgogICAgICAgICAgZGVidWdnZXItZGF0YS1lbmFibGVkPSJbW2RlYnVnZ2VyRGF0YUVuYWJsZWRdXSIKICAgICAgICAgIGFyZS1oZWFsdGgtcGlsbHMtbG9hZGluZz0iW1thcmVIZWFsdGhQaWxsc0xvYWRpbmddXSIKICAgICAgICAgIGRlYnVnZ2VyLW51bWVyaWMtYWxlcnRzPSJbW2RlYnVnZ2VyTnVtZXJpY0FsZXJ0c11dIgogICAgICAgICAgbm9kZS1uYW1lcy10by1oZWFsdGgtcGlsbHM9Iltbbm9kZU5hbWVzVG9IZWFsdGhQaWxsc11dIgogICAgICAgICAgYWxsLXN0ZXBzLW1vZGUtZW5hYmxlZD0ie3thbGxTdGVwc01vZGVFbmFibGVkfX0iCiAgICAgICAgICBzcGVjaWZpYy1oZWFsdGgtcGlsbC1zdGVwPSJ7e3NwZWNpZmljSGVhbHRoUGlsbFN0ZXB9fSIKICAgICAgICAgIGhlYWx0aC1waWxsLXN0ZXAtaW5kZXg9Int7aGVhbHRoUGlsbFN0ZXBJbmRleH19IgogICAgICAgICAgY29tcGF0LW5vZGUtdGl0bGU9IltbY29tcGF0Tm9kZVRpdGxlXV0iCiAgICAgICAgICBvbi1ub2RlLXRvZ2dsZS1pbmNsdXNpb249Il9vbk5vZGVJbmNsdXNpb25Ub2dnbGVkIgogICAgICAgICAgb24tbm9kZS10b2dnbGUtc2VyaWVzZ3JvdXA9Il9vbk5vZGVTZXJpZXNHcm91cFRvZ2dsZWQiCiAgICAgICAgPjwvdGYtZ3JhcGgtaW5mbz4KICAgICAgPC9kaXY+CiAgICA8L2Rpdj4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiZ3JhcGhIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiZ3JhcGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAic3RhdHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAicHJvZ3Jlc3MiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhCb2FyZC5wcm90b3R5cGUsICJ0cmFjZUlucHV0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhCb2FyZC5wcm90b3R5cGUsICJjb2xvckJ5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiY29sb3JCeVBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgInJlbmRlckhpZXJhcmNoeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImRlYnVnZ2VyRGF0YUVuYWJsZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhCb2FyZC5wcm90b3R5cGUsICJhcmVIZWFsdGhQaWxsc0xvYWRpbmciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiZGVidWdnZXJOdW1lcmljQWxlcnRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgIm5vZGVOYW1lc1RvSGVhbHRoUGlsbHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImFsbFN0ZXBzTW9kZUVuYWJsZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhCb2FyZC5wcm90b3R5cGUsICJzcGVjaWZpY0hlYWx0aFBpbGxTdGVwIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImhlYWx0aFBpbGxTdGVwSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhCb2FyZC5wcm90b3R5cGUsICJzZWxlY3RlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiY29tcGF0Tm9kZVRpdGxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImVkZ2VXaWR0aEZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgIl9zZWxlY3RlZE5vZGVJbmNsdWRlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgIl9oaWdobGlnaHRlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiaGFuZGxlTm9kZVNlbGVjdGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImVkZ2VMYWJlbEZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaEJvYXJkLnByb3RvdHlwZSwgImhhbmRsZUVkZ2VTZWxlY3RlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdzZWxlY3RlZE5vZGUnLCAncmVuZGVySGllcmFyY2h5JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoQm9hcmQucHJvdG90eXBlLCAiX3VwZGF0ZU5vZGVJbmNsdWRlIiwgbnVsbCk7CiAgICBUZkdyYXBoQm9hcmQgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ncmFwaC1ib2FyZCcpCiAgICBdLCBUZkdyYXBoQm9hcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmR3JhcGhOb2RlU2VhcmNoID0gY2xhc3MgVGZHcmFwaE5vZGVTZWFyY2ggZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5fcmF3UmVnZXhJbnB1dCA9ICcnOwogICAgICAgICAgICAvLyBUaGUgdmFsdWUgb2YgdGhlIHJlZ2V4IGlucHV0IGZvciB0aGUgbGFzdCBzZWFyY2guCiAgICAgICAgICAgIHRoaXMuX3ByZXZpb3VzUmVnZXhJbnB1dCA9ICcnOwogICAgICAgICAgICB0aGlzLl9zZWFyY2hUaW1lb3V0RGVsYXkgPSAxNTA7CiAgICAgICAgICAgIHRoaXMuX21heFJlZ2V4UmVzdWx0cyA9IDQyOwogICAgICAgIH0KICAgICAgICAvLyBUaGlzIGlzIHRoZSBjbGVhbmVkIGlucHV0LgogICAgICAgIGdldCBfcmVnZXhJbnB1dCgpIHsKICAgICAgICAgICAgdmFyIHJlbmRlckhpZXJhcmNoeSA9IHRoaXMucmVuZGVySGllcmFyY2h5OwogICAgICAgICAgICB2YXIgcmF3UmVnZXhJbnB1dCA9IHRoaXMuX3Jhd1JlZ2V4SW5wdXQ7CiAgICAgICAgICAgIHJldHVybiByYXdSZWdleElucHV0LnRyaW0oKTsKICAgICAgICB9CiAgICAgICAgX3JlZ2V4SW5wdXRDaGFuZ2VkKCkgewogICAgICAgICAgICB2YXIgcmVnZXhJbnB1dCA9IHRoaXMuX3JlZ2V4SW5wdXQ7CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RTZWFyY2goKTsKICAgICAgICB9CiAgICAgICAgX2NsZWFyU2VhcmNoUmVzdWx0cygpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19yZWdleE1hdGNoZXMnLCBbXSk7CiAgICAgICAgfQogICAgICAgIF9yZXF1ZXN0U2VhcmNoKCkgewogICAgICAgICAgICBpZiAodGhpcy5fc2VhcmNoUGVuZGluZykgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmICh0aGlzLl9yZWdleElucHV0ID09PSB0aGlzLl9wcmV2aW91c1JlZ2V4SW5wdXQpIHsKICAgICAgICAgICAgICAgIC8vIE5vIG5ldyBzZWFyY2ggaXMgbmVlZGVkLgogICAgICAgICAgICAgICAgdGhpcy5fc2VhcmNoUGVuZGluZyA9IGZhbHNlOwogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NlYXJjaFBlbmRpbmcgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9leGVjdXRlU2VhcmNoKCk7CiAgICAgICAgICAgIC8vIEFmdGVyIHNvbWUgdGltZSwgcGVyaGFwcyBleGVjdXRlIGFub3RoZXIgc2VhcmNoLgogICAgICAgICAgICB0aGlzLmFzeW5jKCgpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuX3NlYXJjaFBlbmRpbmcgPSBmYWxzZTsKICAgICAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RTZWFyY2goKTsKICAgICAgICAgICAgfSwgdGhpcy5fc2VhcmNoVGltZW91dERlbGF5KTsKICAgICAgICB9CiAgICAgICAgX2V4ZWN1dGVTZWFyY2goKSB7CiAgICAgICAgICAgIHRoaXMuX3ByZXZpb3VzUmVnZXhJbnB1dCA9IHRoaXMuX3JlZ2V4SW5wdXQ7CiAgICAgICAgICAgIGlmICghdGhpcy5fcmVnZXhJbnB1dCkgewogICAgICAgICAgICAgICAgdGhpcy5fY2xlYXJTZWFyY2hSZXN1bHRzKCk7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgICAgIHZhciByZWdleCA9IG5ldyBSZWdFeHAodGhpcy5fcmVnZXhJbnB1dCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgIC8vIFRoZSByZWd1bGFyIGV4cHJlc3Npb24gaXMgaW52YWxpZC4KICAgICAgICAgICAgICAgIHRoaXMuX2NsZWFyU2VhcmNoUmVzdWx0cygpOwogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IG1hdGNoZWROb2RlcyA9IFtdOwogICAgICAgICAgICBjb25zdCBub2RlTWFwID0gdGhpcy5yZW5kZXJIaWVyYXJjaHkuaGllcmFyY2h5LmdldE5vZGVNYXAoKTsKICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZU1hcCwgKF8sIG5vZGVOYW1lKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAobWF0Y2hlZE5vZGVzLmxlbmd0aCA+PSB0aGlzLl9tYXhSZWdleFJlc3VsdHMpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUZXJtaW5hdGUuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKCFyZWdleC50ZXN0KG5vZGVOYW1lKSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIG1hdGNoZWROb2Rlcy5wdXNoKG5vZGVOYW1lKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfcmVnZXhNYXRjaGVzJywgbWF0Y2hlZE5vZGVzKTsKICAgICAgICB9CiAgICAgICAgX21hdGNoQ2xpY2tlZChlKSB7CiAgICAgICAgICAgIGNvbnN0IG5vZGUgPSBlLm1vZGVsLml0ZW07CiAgICAgICAgICAgIHRoaXMuc2V0KCdzZWxlY3RlZE5vZGUnLCBub2RlKTsKICAgICAgICB9CiAgICB9OwogICAgVGZHcmFwaE5vZGVTZWFyY2gudGVtcGxhdGUgPSBodG1sIGAKICAgIDxkaXYgaWQ9InNlYXJjaC1jb250YWluZXIiPgogICAgICA8cGFwZXItaW5wdXQKICAgICAgICBpZD0icnVucy1yZWdleCIKICAgICAgICBsYWJlbD0iU2VhcmNoIG5vZGVzLiBSZWdleGVzIHN1cHBvcnRlZC4iCiAgICAgICAgdmFsdWU9Int7X3Jhd1JlZ2V4SW5wdXR9fSIKICAgICAgPgogICAgICA8L3BhcGVyLWlucHV0PgogICAgICA8ZGl2IGlkPSJzZWFyY2gtcmVzdWx0cy1hbmNob3IiPgogICAgICAgIDxkaXYgaWQ9InNlYXJjaC1yZXN1bHRzIj4KICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLXJlcGVhdCIgaXRlbXM9IltbX3JlZ2V4TWF0Y2hlc11dIj4KICAgICAgICAgICAgPGRpdiBpZD0ic2VhcmNoLW1hdGNoIiBvbi1jbGljaz0iX21hdGNoQ2xpY2tlZCI+W1tpdGVtXV08L2Rpdj4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvZGl2PgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgICNzZWFyY2gtY29udGFpbmVyIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBvdmVyZmxvdzogdmlzaWJsZTsKICAgICAgfQoKICAgICAgI3J1bnMtcmVnZXggewogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAjc2VhcmNoLXJlc3VsdHMtYW5jaG9yIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIH0KCiAgICAgICNzZWFyY2gtcmVzdWx0cyB7CiAgICAgICAgY29sb3I6ICNmZmY7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIG1heC1oZWlnaHQ6IDIwMHB4OwogICAgICAgIG92ZXJmbG93LXg6IGhpZGRlbjsKICAgICAgICBvdmVyZmxvdy15OiBhdXRvOwogICAgICAgIHRleHQtYWxpZ246IHJpZ2h0OwogICAgICAgIG1heC13aWR0aDogMTAwJTsKICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICB9CgogICAgICAjc2VhcmNoLW1hdGNoIHsKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICBwYWRkaW5nOiAzcHg7CiAgICAgICAgZmxvYXQ6IHJpZ2h0OwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgZGlyZWN0aW9uOiBydGw7CiAgICAgIH0KCiAgICAgICNzZWFyY2gtbWF0Y2g6aG92ZXIgewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXRiLW9yYW5nZS13ZWFrKTsKICAgICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaE5vZGVTZWFyY2gucHJvdG90eXBlLCAicmVuZGVySGllcmFyY2h5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaC5wcm90b3R5cGUsICJzZWxlY3RlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaC5wcm90b3R5cGUsICJfcmF3UmVnZXhJbnB1dCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmR3JhcGhOb2RlU2VhcmNoLnByb3RvdHlwZSwgIl9wcmV2aW91c1JlZ2V4SW5wdXQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaC5wcm90b3R5cGUsICJfc2VhcmNoVGltZW91dERlbGF5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaC5wcm90b3R5cGUsICJfc2VhcmNoUGVuZGluZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhOb2RlU2VhcmNoLnByb3RvdHlwZSwgIl9tYXhSZWdleFJlc3VsdHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZHcmFwaE5vZGVTZWFyY2gucHJvdG90eXBlLCAiX3JlZ2V4TWF0Y2hlcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgncmVuZGVySGllcmFyY2h5JywgJ19yYXdSZWdleElucHV0JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaC5wcm90b3R5cGUsICJfcmVnZXhJbnB1dCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX3JlZ2V4SW5wdXQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmR3JhcGhOb2RlU2VhcmNoLnByb3RvdHlwZSwgIl9yZWdleElucHV0Q2hhbmdlZCIsIG51bGwpOwogICAgVGZHcmFwaE5vZGVTZWFyY2ggPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ncmFwaC1ub2RlLXNlYXJjaCcpCiAgICBdLCBUZkdyYXBoTm9kZVNlYXJjaCk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBjb25zdCBERVZJQ0VfTkFNRV9SRUdFWCA9IC9kZXZpY2U6KFteOl0rOlswLTldKykkLzsKICAgIC8qKgogICAgICogRGlzcGxheSBvbmx5IGRldmljZXMgbWF0Y2hpbmcgb25lIG9mIHRoZSBmb2xsb3dpbmcgcmVnZXguCiAgICAgKi8KICAgIGNvbnN0IERFVklDRV9OQU1FU19JTkNMVURFID0gWwogICAgICAgIHsKICAgICAgICAgICAgLy8gRG9uJ3QgaW5jbHVkZSBHUFUgc3RyZWFtLCBtZW1jcHksIGV0Yy4gZGV2aWNlcwogICAgICAgICAgICByZWdleDogREVWSUNFX05BTUVfUkVHRVgsCiAgICAgICAgfSwKICAgIF07CiAgICAvKioKICAgICAqIFN0YXRzIGZyb20gZGV2aWNlIG5hbWVzIHRoYXQgbWF0Y2ggdGhlc2UgcmVnZXhlcyB3aWxsIGJlIGRpc2FibGVkIGJ5IGRlZmF1bHQuCiAgICAgKiBUaGUgdXNlciBjYW4gc3RpbGwgdHVybiBvbiBhIGRldmljZSBieSBzZWxlY3RpbmcgdGhlIGNoZWNrYm94IGluIHRoZSBkZXZpY2UgbGlzdC4KICAgICAqLwogICAgY29uc3QgREVWSUNFX1NUQVRTX0RFRkFVTFRfT0ZGID0gW107CiAgICB2YXIgQ29sb3JCeSQxOwogICAgKGZ1bmN0aW9uIChDb2xvckJ5KSB7CiAgICAgICAgQ29sb3JCeVsiQ09NUFVURV9USU1FIl0gPSAiY29tcHV0ZV90aW1lIjsKICAgICAgICBDb2xvckJ5WyJNRU1PUlkiXSA9ICJtZW1vcnkiOwogICAgICAgIENvbG9yQnlbIlNUUlVDVFVSRSJdID0gInN0cnVjdHVyZSI7CiAgICAgICAgQ29sb3JCeVsiWExBX0NMVVNURVIiXSA9ICJ4bGFfY2x1c3RlciI7CiAgICAgICAgQ29sb3JCeVsiT1BfQ09NUEFUSUJJTElUWSJdID0gIm9wX2NvbXBhdGliaWxpdHkiOwogICAgfSkoQ29sb3JCeSQxIHx8IChDb2xvckJ5JDEgPSB7fSkpOwogICAgY29uc3QgR1JBRElFTlRfQ09NUEFUSUJMRV9DT0xPUl9CWSA9IG5ldyBTZXQoWwogICAgICAgIENvbG9yQnkkMS5DT01QVVRFX1RJTUUsCiAgICAgICAgQ29sb3JCeSQxLk1FTU9SWSwKICAgIF0pOwogICAgbGV0IFRmR3JhcGhDb250cm9scyA9IGNsYXNzIFRmR3JhcGhDb250cm9scyBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvLyBQdWJsaWMgQVBJLgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUgez90Zl9ncmFwaF9wcm90by5TdGVwU3RhdHN9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnN0YXRzID0gbnVsbDsKICAgICAgICAgICAgLyoqCiAgICAgICAgICAgICAqIEB0eXBlIHs/T2JqZWN0PHN0cmluZywgYm9vbGVhbj59CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmRldmljZXNGb3JTdGF0cyA9IG51bGw7CiAgICAgICAgICAgIC8qKgogICAgICAgICAgICAgKiBAdHlwZSB7IUNvbG9yQnl9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmNvbG9yQnkgPSBDb2xvckJ5JDEuU1RSVUNUVVJFOwogICAgICAgICAgICB0aGlzLmRhdGFzZXRzID0gW107CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkUnVuSW5kZXggPSAwOwogICAgICAgICAgICB0aGlzLnRyYWNlSW5wdXRzID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkVGFnSW5kZXggPSAwOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUge3RmX2dyYXBoX2NvbW1vbi5TZWxlY3Rpb25UeXBlfQogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWRHcmFwaFR5cGUgPSBTZWxlY3Rpb25UeXBlLk9QX0dSQVBIOwogICAgICAgICAgICB0aGlzLnNob3dTZXNzaW9uUnVuc0Ryb3Bkb3duID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5zaG93VXBsb2FkQnV0dG9uID0gdHJ1ZTsKICAgICAgICAgICAgdGhpcy5fbGVnZW5kT3BlbmVkID0gdHJ1ZTsKICAgICAgICB9CiAgICAgICAgX3hsYUNsdXN0ZXJzUHJvdmlkZWQocmVuZGVySGllcmFyY2h5KSB7CiAgICAgICAgICAgIHJldHVybiAocmVuZGVySGllcmFyY2h5ICYmCiAgICAgICAgICAgICAgICByZW5kZXJIaWVyYXJjaHkuaGllcmFyY2h5ICYmCiAgICAgICAgICAgICAgICByZW5kZXJIaWVyYXJjaHkuaGllcmFyY2h5LnhsYUNsdXN0ZXJzLmxlbmd0aCA+IDApOwogICAgICAgIH0KICAgICAgICBfc3RhdHNDaGFuZ2VkKHN0YXRzKSB7CiAgICAgICAgICAgIGlmIChzdGF0cyA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIGRldmljZXNGb3JTdGF0cyA9IHt9OwogICAgICAgICAgICB2YXIgZGV2aWNlcyA9IGxvZGFzaC5lYWNoKHN0YXRzLmRldl9zdGF0cywgZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIC8vIE9ubHkgY29uc2lkZXJlZCBpbmNsdWRlZCBkZXZpY2VzLgogICAgICAgICAgICAgICAgdmFyIGluY2x1ZGUgPSBsb2Rhc2guc29tZShERVZJQ0VfTkFNRVNfSU5DTFVERSwgZnVuY3Rpb24gKHJ1bGUpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gcnVsZS5yZWdleC50ZXN0KGQuZGV2aWNlKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgLy8gRXhjbHVkZSBkZXZpY2UgbmFtZXMgdGhhdCBhcmUgaWdub3JlZCBieSBkZWZhdWx0LgogICAgICAgICAgICAgICAgdmFyIGV4Y2x1ZGUgPSBsb2Rhc2guc29tZShERVZJQ0VfU1RBVFNfREVGQVVMVF9PRkYsIGZ1bmN0aW9uIChydWxlKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHJ1bGUucmVnZXgudGVzdChkLmRldmljZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGlmIChpbmNsdWRlICYmICFleGNsdWRlKSB7CiAgICAgICAgICAgICAgICAgICAgZGV2aWNlc0ZvclN0YXRzW2QuZGV2aWNlXSA9IHRydWU7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLnNldCgnZGV2aWNlc0ZvclN0YXRzJywgZGV2aWNlc0ZvclN0YXRzKTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jdXJyZW50RGV2aWNlcygpIHsKICAgICAgICAgICAgdmFyIGRldmljZXNGb3JTdGF0cyA9IHRoaXMuZGV2aWNlc0ZvclN0YXRzOwogICAgICAgICAgICBjb25zdCBzdGF0cyA9IHRoaXMuc3RhdHM7CiAgICAgICAgICAgIGNvbnN0IGRldlN0YXRzID0gc3RhdHMgPyBzdGF0cy5kZXZfc3RhdHMgOiBbXTsKICAgICAgICAgICAgY29uc3QgYWxsRGV2aWNlcyA9IGRldlN0YXRzLm1hcCgoZCkgPT4gZC5kZXZpY2UpOwogICAgICAgICAgICBjb25zdCBkZXZpY2VzID0gYWxsRGV2aWNlcy5maWx0ZXIoKGRldmljZU5hbWUpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBERVZJQ0VfTkFNRVNfSU5DTFVERS5zb21lKChydWxlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHJ1bGUucmVnZXgudGVzdChkZXZpY2VOYW1lKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gRGV2aWNlcyBuYW1lcyBjYW4gYmUgbG9uZyBzbyB3ZSByZW1vdmUgdGhlIGxvbmdlc3QgY29tbW9uIHByZWZpeAogICAgICAgICAgICAvLyBiZWZvcmUgc2hvd2luZyB0aGUgZGV2aWNlcyBpbiBhIGxpc3QuCiAgICAgICAgICAgIGNvbnN0IHN1ZmZpeGVzID0gcmVtb3ZlQ29tbW9uUHJlZml4KGRldmljZXMpOwogICAgICAgICAgICBpZiAoc3VmZml4ZXMubGVuZ3RoID09IDEpIHsKICAgICAgICAgICAgICAgIGNvbnN0IGZvdW5kID0gc3VmZml4ZXNbMF0ubWF0Y2goREVWSUNFX05BTUVfUkVHRVgpOwogICAgICAgICAgICAgICAgaWYgKGZvdW5kKSB7CiAgICAgICAgICAgICAgICAgICAgc3VmZml4ZXNbMF0gPSBmb3VuZFsxXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZGV2aWNlcy5tYXAoKGRldmljZSwgaSkgPT4gewogICAgICAgICAgICAgICAgbGV0IGlnbm9yZWRNc2cgPSBudWxsOwogICAgICAgICAgICAgICAgLy8gVE9ETyhzdGVwaGFud2xlZSk6IHRoaXMgc2hvdWxkIHByb2JhYmx5IGJhaWwgb24gdGhlIGZpcnN0IG1hdGNoIG9yCiAgICAgICAgICAgICAgICAvLyBkbyBzb21ldGhpbmcgdXNlZnVsIHdpdGggbXVsdGlwbGUgcnVsZS5tc2dzLgogICAgICAgICAgICAgICAgREVWSUNFX1NUQVRTX0RFRkFVTFRfT0ZGLmZvckVhY2goKHJ1bGUpID0+IHsKICAgICAgICAgICAgICAgICAgICBpZiAocnVsZS5yZWdleC50ZXN0KGRldmljZSkpIHsKICAgICAgICAgICAgICAgICAgICAgICAgaWdub3JlZE1zZyA9IHJ1bGUubXNnOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBkZXZpY2U6IGRldmljZSwKICAgICAgICAgICAgICAgICAgICBzdWZmaXg6IHN1ZmZpeGVzW2ldLAogICAgICAgICAgICAgICAgICAgIHVzZWQ6IGRldmljZXNGb3JTdGF0c1tkZXZpY2VdLAogICAgICAgICAgICAgICAgICAgIGlnbm9yZWRNc2c6IGlnbm9yZWRNc2csCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2RldmljZUNoZWNrYm94Q2xpY2tlZChldmVudCkgewogICAgICAgICAgICAvLyBVcGRhdGUgdGhlIGRldmljZSBtYXAuCiAgICAgICAgICAgIGNvbnN0IGlucHV0ID0gZXZlbnQudGFyZ2V0OwogICAgICAgICAgICBjb25zdCBkZXZpY2VzRm9yU3RhdHMgPSBPYmplY3QuYXNzaWduKHt9LCB0aGlzLmRldmljZXNGb3JTdGF0cyk7CiAgICAgICAgICAgIGNvbnN0IGRldmljZSA9IGlucHV0LnZhbHVlOwogICAgICAgICAgICBpZiAoaW5wdXQuY2hlY2tlZCkgewogICAgICAgICAgICAgICAgZGV2aWNlc0ZvclN0YXRzW2RldmljZV0gPSB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgZGVsZXRlIGRldmljZXNGb3JTdGF0c1tkZXZpY2VdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuc2V0KCdkZXZpY2VzRm9yU3RhdHMnLCBkZXZpY2VzRm9yU3RhdHMpOwogICAgICAgIH0KICAgICAgICBfbnVtVGFncyhkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2dldFRhZ3MoZGF0YXNldHMsIF9zZWxlY3RlZFJ1bkluZGV4KS5sZW5ndGg7CiAgICAgICAgfQogICAgICAgIF9nZXRUYWdzKGRhdGFzZXRzLCBfc2VsZWN0ZWRSdW5JbmRleCkgewogICAgICAgICAgICBpZiAoIWRhdGFzZXRzIHx8ICFkYXRhc2V0c1tfc2VsZWN0ZWRSdW5JbmRleF0pIHsKICAgICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gZGF0YXNldHNbX3NlbGVjdGVkUnVuSW5kZXhdLnRhZ3M7CiAgICAgICAgfQogICAgICAgIF9maXQoKSB7CiAgICAgICAgICAgIHRoaXMuZmlyZSgnZml0LXRhcCcpOwogICAgICAgIH0KICAgICAgICBfaXNHcmFkaWVudENvbG9yaW5nKHN0YXRzLCBjb2xvckJ5KSB7CiAgICAgICAgICAgIHJldHVybiBHUkFESUVOVF9DT01QQVRJQkxFX0NPTE9SX0JZLmhhcyhjb2xvckJ5KSAmJiBzdGF0cyAhPSBudWxsOwogICAgICAgIH0KICAgICAgICBfZXF1YWxzKGEsIGIpIHsKICAgICAgICAgICAgcmV0dXJuIGEgPT09IGI7CiAgICAgICAgfQogICAgICAgIGdldCBfY3VycmVudERldmljZVBhcmFtcygpIHsKICAgICAgICAgICAgdmFyIGNvbG9yQnlQYXJhbXMgPSB0aGlzLmNvbG9yQnlQYXJhbXM7CiAgICAgICAgICAgIGNvbnN0IGRldmljZVBhcmFtcyA9IGNvbG9yQnlQYXJhbXMuZGV2aWNlLmZpbHRlcigocGFyYW0pID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBERVZJQ0VfTkFNRVNfSU5DTFVERS5zb21lKChydWxlKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHJ1bGUucmVnZXgudGVzdChwYXJhbS5kZXZpY2UpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBSZW1vdmUgY29tbW9uIHByZWZpeCBhbmQgbWVyZ2UgYmFjayBjb3JyZXNwb25kaW5nIGNvbG9yLiBJZgogICAgICAgICAgICAvLyB0aGVyZSBpcyBvbmx5IG9uZSBkZXZpY2UgdGhlbiByZW1vdmUgZXZlcnl0aGluZyB1cCB0byAiL2RldmljZToiLgogICAgICAgICAgICBjb25zdCBzdWZmaXhlcyA9IHJlbW92ZUNvbW1vblByZWZpeChkZXZpY2VQYXJhbXMubWFwKChkKSA9PiBkLmRldmljZSkpOwogICAgICAgICAgICBpZiAoc3VmZml4ZXMubGVuZ3RoID09IDEpIHsKICAgICAgICAgICAgICAgIHZhciBmb3VuZCA9IHN1ZmZpeGVzWzBdLm1hdGNoKERFVklDRV9OQU1FX1JFR0VYKTsKICAgICAgICAgICAgICAgIGlmIChmb3VuZCkgewogICAgICAgICAgICAgICAgICAgIHN1ZmZpeGVzWzBdID0gZm91bmRbMV07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGRldmljZVBhcmFtcy5tYXAoKGQsIGkpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiB7IGRldmljZTogc3VmZml4ZXNbaV0sIGNvbG9yOiBkLmNvbG9yIH07CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBnZXQgX2N1cnJlbnRYbGFDbHVzdGVyUGFyYW1zKCkgewogICAgICAgICAgICB2YXIgY29sb3JCeVBhcmFtcyA9IHRoaXMuY29sb3JCeVBhcmFtczsKICAgICAgICAgICAgcmV0dXJuIGNvbG9yQnlQYXJhbXMueGxhX2NsdXN0ZXI7CiAgICAgICAgfQogICAgICAgIGdldCBfY3VycmVudEdyYWRpZW50UGFyYW1zKCkgewogICAgICAgICAgICB2YXIgY29sb3JCeVBhcmFtcyA9IHRoaXMuY29sb3JCeVBhcmFtczsKICAgICAgICAgICAgdmFyIGNvbG9yQnkgPSB0aGlzLmNvbG9yQnk7CiAgICAgICAgICAgIGlmICghdGhpcy5faXNHcmFkaWVudENvbG9yaW5nKHRoaXMuc3RhdHMsIGNvbG9yQnkpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgcGFyYW1zID0gY29sb3JCeVBhcmFtc1tjb2xvckJ5XTsKICAgICAgICAgICAgbGV0IG1pblZhbHVlID0gcGFyYW1zLm1pblZhbHVlOwogICAgICAgICAgICBsZXQgbWF4VmFsdWUgPSBwYXJhbXMubWF4VmFsdWU7CiAgICAgICAgICAgIGlmIChjb2xvckJ5ID09PSBDb2xvckJ5JDEuTUVNT1JZKSB7CiAgICAgICAgICAgICAgICBtaW5WYWx1ZSA9IGNvbnZlcnRVbml0c1RvSHVtYW5SZWFkYWJsZShtaW5WYWx1ZSwgTUVNT1JZX1VOSVRTKTsKICAgICAgICAgICAgICAgIG1heFZhbHVlID0gY29udmVydFVuaXRzVG9IdW1hblJlYWRhYmxlKG1heFZhbHVlLCBNRU1PUllfVU5JVFMpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKGNvbG9yQnkgPT09IENvbG9yQnkkMS5DT01QVVRFX1RJTUUpIHsKICAgICAgICAgICAgICAgIG1pblZhbHVlID0gY29udmVydFVuaXRzVG9IdW1hblJlYWRhYmxlKG1pblZhbHVlLCBUSU1FX1VOSVRTKTsKICAgICAgICAgICAgICAgIG1heFZhbHVlID0gY29udmVydFVuaXRzVG9IdW1hblJlYWRhYmxlKG1heFZhbHVlLCBUSU1FX1VOSVRTKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbWluVmFsdWUsCiAgICAgICAgICAgICAgICBtYXhWYWx1ZSwKICAgICAgICAgICAgICAgIHN0YXJ0Q29sb3I6IHBhcmFtcy5zdGFydENvbG9yLAogICAgICAgICAgICAgICAgZW5kQ29sb3I6IHBhcmFtcy5lbmRDb2xvciwKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgZG93bmxvYWQoKSB7CiAgICAgICAgICAgIHRoaXMuJC5ncmFwaGRvd25sb2FkLmNsaWNrKCk7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVGaWxlSW5wdXQoZSkgewogICAgICAgICAgICBjb25zdCBmaWxlID0gZS50YXJnZXQuZmlsZXNbMF07CiAgICAgICAgICAgIGlmICghZmlsZSkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgLy8gU3RyaXAgb2ZmIGV2ZXJ5dGhpbmcgYmVmb3JlIHRoZSBsYXN0ICIvIiBhbmQgc3RyaXAgb2ZmIHRoZSBmaWxlCiAgICAgICAgICAgIC8vIGV4dGVuc2lvbiBpbiBvcmRlciB0byBnZXQgdGhlIG5hbWUgb2YgdGhlIFBORyBmb3IgdGhlIGdyYXBoLgogICAgICAgICAgICBsZXQgZmlsZVBhdGggPSBmaWxlLm5hbWU7CiAgICAgICAgICAgIGNvbnN0IGRvdEluZGV4ID0gZmlsZVBhdGgubGFzdEluZGV4T2YoJy4nKTsKICAgICAgICAgICAgaWYgKGRvdEluZGV4ID49IDApIHsKICAgICAgICAgICAgICAgIGZpbGVQYXRoID0gZmlsZVBhdGguc3Vic3RyaW5nKDAsIGRvdEluZGV4KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBsYXN0U2xhc2hJbmRleCA9IGZpbGVQYXRoLmxhc3RJbmRleE9mKCcvJyk7CiAgICAgICAgICAgIGlmIChsYXN0U2xhc2hJbmRleCA+PSAwKSB7CiAgICAgICAgICAgICAgICBmaWxlUGF0aCA9IGZpbGVQYXRoLnN1YnN0cmluZyhsYXN0U2xhc2hJbmRleCArIDEpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX3NldERvd25sb2FkRmlsZW5hbWUoZmlsZVBhdGgpOwogICAgICAgICAgICB0aGlzLnNldCgnc2VsZWN0ZWRGaWxlJywgZSk7CiAgICAgICAgfQogICAgICAgIF9kYXRhc2V0c0NoYW5nZWQobmV3RGF0YXNldHMsIG9sZERhdGFzZXRzKSB7CiAgICAgICAgICAgIGlmIChvbGREYXRhc2V0cyAhPSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBTZWxlY3QgdGhlIGZpcnN0IGRhdGFzZXQgYnkgZGVmYXVsdC4KICAgICAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkUnVuSW5kZXggPSAwOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlU2VsZWN0aW9uKGRhdGFzZXRzLCBfc2VsZWN0ZWRSdW5JbmRleCwgX3NlbGVjdGVkVGFnSW5kZXgsIF9zZWxlY3RlZEdyYXBoVHlwZSkgewogICAgICAgICAgICBpZiAoIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XSkgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIHJ1bjogZGF0YXNldHNbX3NlbGVjdGVkUnVuSW5kZXhdLm5hbWUsCiAgICAgICAgICAgICAgICB0YWc6IGRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XS50YWcsCiAgICAgICAgICAgICAgICB0eXBlOiBfc2VsZWN0ZWRHcmFwaFR5cGUsCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIF9zZWxlY3RlZFJ1bkluZGV4Q2hhbmdlZChydW5JbmRleCkgewogICAgICAgICAgICBpZiAoIXRoaXMuZGF0YXNldHMpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIC8vIFJlc2V0IHRoZSBzdGF0ZXMgd2hlbiB1c2VyIHBpY2sgYSBkaWZmZXJlbnQgcnVuLgogICAgICAgICAgICB0aGlzLmNvbG9yQnkgPSBDb2xvckJ5JDEuU1RSVUNUVVJFOwogICAgICAgICAgICB0aGlzLl9zZWxlY3RlZFRhZ0luZGV4ID0gMDsKICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWRHcmFwaFR5cGUgPSB0aGlzLl9nZXREZWZhdWx0U2VsZWN0aW9uVHlwZSgpOwogICAgICAgICAgICB0aGlzLnRyYWNlSW5wdXRzID0gZmFsc2U7IC8vIFNldCB0cmFjZSBpbnB1dCB0byBvZmYtc3RhdGUuCiAgICAgICAgICAgIHRoaXMuX3NldERvd25sb2FkRmlsZW5hbWUodGhpcy5kYXRhc2V0c1tydW5JbmRleF0gPyB0aGlzLmRhdGFzZXRzW3J1bkluZGV4XS5uYW1lIDogJycpOwogICAgICAgIH0KICAgICAgICBfc2VsZWN0ZWRUYWdJbmRleENoYW5nZWQoKSB7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkR3JhcGhUeXBlID0gdGhpcy5fZ2V0RGVmYXVsdFNlbGVjdGlvblR5cGUoKTsKICAgICAgICB9CiAgICAgICAgX2dldERlZmF1bHRTZWxlY3Rpb25UeXBlKCkgewogICAgICAgICAgICBjb25zdCB7IGRhdGFzZXRzLCBfc2VsZWN0ZWRSdW5JbmRleDogcnVuLCBfc2VsZWN0ZWRUYWdJbmRleDogdGFnIH0gPSB0aGlzOwogICAgICAgICAgICBpZiAoIWRhdGFzZXRzIHx8CiAgICAgICAgICAgICAgICAhZGF0YXNldHNbcnVuXSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW3J1bl0udGFnc1t0YWddIHx8CiAgICAgICAgICAgICAgICBkYXRhc2V0c1tydW5dLnRhZ3NbdGFnXS5vcEdyYXBoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gU2VsZWN0aW9uVHlwZS5PUF9HUkFQSDsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBkYXRhc2V0Rm9yUnVuID0gZGF0YXNldHNbcnVuXTsKICAgICAgICAgICAgaWYgKGRhdGFzZXRGb3JSdW4udGFnc1t0YWddLnByb2ZpbGUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBTZWxlY3Rpb25UeXBlLlBST0ZJTEU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKGRhdGFzZXRGb3JSdW4udGFnc1t0YWddLmNvbmNlcHR1YWxHcmFwaCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFNlbGVjdGlvblR5cGUuQ09OQ0VQVFVBTF9HUkFQSDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gU2VsZWN0aW9uVHlwZS5PUF9HUkFQSDsKICAgICAgICB9CiAgICAgICAgX2dldEZpbGUoKSB7CiAgICAgICAgICAgIHRoaXMuJCQoJyNmaWxlJykuY2xpY2soKTsKICAgICAgICB9CiAgICAgICAgX3NldERvd25sb2FkRmlsZW5hbWUobmFtZSkgewogICAgICAgICAgICB0aGlzLiQuZ3JhcGhkb3dubG9hZC5zZXRBdHRyaWJ1dGUoJ2Rvd25sb2FkJywgbmFtZSArICcucG5nJyk7CiAgICAgICAgfQogICAgICAgIF9zdGF0c05vdE51bGwoc3RhdHMpIHsKICAgICAgICAgICAgcmV0dXJuIHN0YXRzICE9PSBudWxsOwogICAgICAgIH0KICAgICAgICBfdG9nZ2xlTGVnZW5kT3BlbigpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19sZWdlbmRPcGVuZWQnLCAhdGhpcy5fbGVnZW5kT3BlbmVkKTsKICAgICAgICB9CiAgICAgICAgX2dldFRvZ2dsZVRleHQobGVnZW5kT3BlbmVkKSB7CiAgICAgICAgICAgIHJldHVybiBsZWdlbmRPcGVuZWQgPyAnQ2xvc2UgbGVnZW5kLicgOiAnRXhwYW5kIGxlZ2VuZC4nOwogICAgICAgIH0KICAgICAgICBfZ2V0VG9nZ2xlTGVnZW5kSWNvbihsZWdlbmRPcGVuZWQpIHsKICAgICAgICAgICAgLy8gVGhpcyBzZWVtcyBjb3VudGVyLWludHVpdGl2ZSwgYnV0IGFjdHVhbGx5IG1ha2VzIHNlbnNlIGJlY2F1c2UgdGhlCiAgICAgICAgICAgIC8vIGV4cGFuZC1tb3JlIGJ1dHRvbiBwb2ludHMgZG93bndhcmRzLCBhbmQgdGhlIGV4cGFuZC1sZXNzIGJ1dHRvbiBwb2ludHMKICAgICAgICAgICAgLy8gdXB3YXJkcy4gRm9yIG1vc3QgY29sbGFwc2libGVzLCB0aGlzIHdvcmtzIGJlY2F1c2UgdGhlIGNvbGxhcHNpYmxlcwogICAgICAgICAgICAvLyBleHBhbmQgaW4gdGhlIGRvd253YXJkcyBkaXJlY3Rpb24uIFRoaXMgY29sbGFwc2libGUgZXhwYW5kcyB1cHdhcmRzCiAgICAgICAgICAgIC8vIHRob3VnaCwgc28gd2UgcmV2ZXJzZSB0aGUgaWNvbnMuCiAgICAgICAgICAgIHJldHVybiBsZWdlbmRPcGVuZWQgPyAnZXhwYW5kLW1vcmUnIDogJ2V4cGFuZC1sZXNzJzsKICAgICAgICB9CiAgICAgICAgX2dldFNlbGVjdGlvbk9wR3JhcGhEaXNhYmxlZChkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgsIF9zZWxlY3RlZFRhZ0luZGV4KSB7CiAgICAgICAgICAgIHJldHVybiAoIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XS5vcEdyYXBoKTsKICAgICAgICB9CiAgICAgICAgX2dldFNlbGVjdGlvblByb2ZpbGVEaXNhYmxlZChkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgsIF9zZWxlY3RlZFRhZ0luZGV4KSB7CiAgICAgICAgICAgIHJldHVybiAoIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XSB8fAogICAgICAgICAgICAgICAgIWRhdGFzZXRzW19zZWxlY3RlZFJ1bkluZGV4XS50YWdzW19zZWxlY3RlZFRhZ0luZGV4XS5wcm9maWxlKTsKICAgICAgICB9CiAgICAgICAgX2dldFNlbGVjdGlvbkNvbmNlcHR1YWxHcmFwaERpc2FibGVkKGRhdGFzZXRzLCBfc2VsZWN0ZWRSdW5JbmRleCwgX3NlbGVjdGVkVGFnSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuICghZGF0YXNldHNbX3NlbGVjdGVkUnVuSW5kZXhdIHx8CiAgICAgICAgICAgICAgICAhZGF0YXNldHNbX3NlbGVjdGVkUnVuSW5kZXhdLnRhZ3NbX3NlbGVjdGVkVGFnSW5kZXhdIHx8CiAgICAgICAgICAgICAgICAhZGF0YXNldHNbX3NlbGVjdGVkUnVuSW5kZXhdLnRhZ3NbX3NlbGVjdGVkVGFnSW5kZXhdLmNvbmNlcHR1YWxHcmFwaCk7CiAgICAgICAgfQogICAgfTsKICAgIFRmR3JhcGhDb250cm9scy50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgY29sb3I6IGdyYXk7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogICAgICAgIGZvbnQtc2l6ZTogMTJweDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgcGFwZXItZHJvcGRvd24tbWVudSB7CiAgICAgICAgLS1wYXBlci1kcm9wZG93bi1tZW51LWlucHV0OiB7CiAgICAgICAgICBwYWRkaW5nOiAwOwogICAgICAgICAgY29sb3I6IGdyYXk7CiAgICAgICAgfQogICAgICAgIC0taXJvbi1pY29uLXdpZHRoOiAxNXB4OwogICAgICAgIC0taXJvbi1pY29uLWhlaWdodDogMTVweDsKICAgICAgICAtLXByaW1hcnktdGV4dC1jb2xvcjogZ3JheTsKICAgICAgICAtLXBhcGVyLWl0ZW0tbWluLWhlaWdodDogMzBweDsKICAgICAgfQoKICAgICAgcGFwZXItYnV0dG9uW3JhaXNlZF0ua2V5Ym9hcmQtZm9jdXMgewogICAgICAgIGZvbnQtd2VpZ2h0OiBub3JtYWw7CiAgICAgIH0KCiAgICAgIC5ydW4tZHJvcGRvd24gewogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyOiB7CiAgICAgICAgICBwYWRkaW5nOiA4cHggMCA4cHggMTBweDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC5jb2xvci1kcm9wZG93biB7CiAgICAgICAgLS1wYXBlci1pbnB1dC1jb250YWluZXI6IHsKICAgICAgICAgIHBhZGRpbmc6IDlweCAwIDAgMTNweDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHRhYmxlIHsKICAgICAgICBib3JkZXItY29sbGFwc2U6IGNvbGxhcHNlOwogICAgICAgIGJvcmRlci1zcGFjaW5nOiAwOwogICAgICB9CgogICAgICB0YWJsZSB0ZCB7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgICBtYXJnaW46IDA7CiAgICAgIH0KCiAgICAgIC5hbGxjb250cm9scyB7CiAgICAgICAgcGFkZGluZzogMCAyMHB4IDIwcHg7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICAgIG92ZXJmbG93LXk6IGF1dG87CiAgICAgIH0KCiAgICAgIC5sZWdlbmQtaG9sZGVyIHsKICAgICAgICBiYWNrZ3JvdW5kOiAjZTllOWU5OwogICAgICAgIGJvcmRlci10b3A6IDFweCBzb2xpZCAjY2NjOwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgY29sb3I6ICM1NTU7CiAgICAgICAgcGFkZGluZzogMTVweCAyMHB4OwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAudG9nZ2xlLWxlZ2VuZC1idXR0b24gewogICAgICAgIG1heC1oZWlnaHQ6IDIwcHg7CiAgICAgICAgbWF4LXdpZHRoOiAyMHB4OwogICAgICAgIHBhZGRpbmc6IDA7CiAgICAgIH0KCiAgICAgIC50b2dnbGUtbGVnZW5kLXRleHQgewogICAgICAgIHZlcnRpY2FsLWFsaWduOiBtaWRkbGU7CiAgICAgIH0KCiAgICAgIHBhcGVyLXJhZGlvLWJ1dHRvbiB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgcGFkZGluZzogNXB4OwogICAgICB9CiAgICAgIHN2Zy5pY29uLAogICAgICB0Zi1ncmFwaC1pY29uIHsKICAgICAgICB3aWR0aDogNjBweDsKICAgICAgICBoZWlnaHQ6IDE4cHg7CiAgICAgIH0KICAgICAgLmRvbWFpblZhbHVlcyB7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMTBweDsKICAgICAgICB3aWR0aDogMTY1cHg7CiAgICAgIH0KICAgICAgLmRvbWFpblN0YXJ0IHsKICAgICAgICBmbG9hdDogbGVmdDsKICAgICAgfQogICAgICAuZG9tYWluRW5kIHsKICAgICAgICBmbG9hdDogcmlnaHQ7CiAgICAgIH0KICAgICAgLmNvbG9yQm94IHsKICAgICAgICB3aWR0aDogMjBweDsKICAgICAgfQoKICAgICAgLmltYWdlLWljb24gewogICAgICAgIHdpZHRoOiAyNHB4OwogICAgICAgIGhlaWdodDogMjRweDsKICAgICAgfQoKICAgICAgLmhlbHAtaWNvbiB7CiAgICAgICAgaGVpZ2h0OiAxNXB4OwogICAgICAgIG1hcmdpbjogMDsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICB9CgogICAgICAuZ3JheSB7CiAgICAgICAgY29sb3I6ICM2NjY7CiAgICAgIH0KCiAgICAgIC50aXRsZSB7CiAgICAgICAgZm9udC1zaXplOiAxNnB4OwogICAgICAgIG1hcmdpbjogOHB4IDVweCA4cHggMDsKICAgICAgICBjb2xvcjogYmxhY2s7CiAgICAgIH0KICAgICAgLnRpdGxlIHNtYWxsIHsKICAgICAgICBmb250LXdlaWdodDogbm9ybWFsOwogICAgICB9CiAgICAgIC5kZXZpY2VMaXN0LAogICAgICAueGxhQ2x1c3Rlckxpc3QgewogICAgICAgIG1heC1oZWlnaHQ6IDIwMHB4OwogICAgICAgIG92ZXJmbG93LXk6IGF1dG87CiAgICAgIH0KCiAgICAgICNmaWxlIHsKICAgICAgICBwYWRkaW5nOiA4cHggMDsKICAgICAgfQoKICAgICAgLmNvbG9yLWxlZ2VuZC1yb3cgewogICAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7CiAgICAgICAgY2xlYXI6IGJvdGg7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBoZWlnaHQ6IDIwcHg7CiAgICAgICAgbWFyZ2luLXRvcDogNXB4OwogICAgICB9CgogICAgICAuY29sb3ItbGVnZW5kLXJvdyAubGFiZWwsCiAgICAgIC5jb2xvci1sZWdlbmQtcm93IHN2ZywKICAgICAgLmNvbG9yLWxlZ2VuZC1yb3cgdGYtZ3JhcGgtaWNvbiB7CiAgICAgICAgZmxleDogMCAwIDQwcHg7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiAyMHB4OwogICAgICB9CgogICAgICAuZGV2aWNlcy1jaGVja2JveCBpbnB1dCB7CiAgICAgICAgdGV4dC1hbGlnbjogbGVmdDsKICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlOwogICAgICB9CgogICAgICAuY29udHJvbC1ob2xkZXIgLmljb24tYnV0dG9uIHsKICAgICAgICBmb250LXNpemU6IDE0cHg7CiAgICAgICAgbWFyZ2luOiAwIC01cHg7CiAgICAgICAgcGFkZGluZzogNXB4OwogICAgICB9CgogICAgICAuYnV0dG9uLXRleHQgewogICAgICAgIHBhZGRpbmctbGVmdDogMjBweDsKICAgICAgICB0ZXh0LXRyYW5zZm9ybTogbm9uZTsKICAgICAgfQoKICAgICAgLnVwbG9hZC1idXR0b24gewogICAgICAgIHdpZHRoOiAxNjVweDsKICAgICAgICBoZWlnaHQ6IDI1cHg7CiAgICAgICAgdGV4dC10cmFuc2Zvcm06IG5vbmU7CiAgICAgICAgbWFyZ2luLXRvcDogNHB4OwogICAgICB9CgogICAgICAuYnV0dG9uLWljb24gewogICAgICAgIHdpZHRoOiAyNnB4OwogICAgICAgIGhlaWdodDogMjZweDsKICAgICAgICBjb2xvcjogdmFyKC0tcGFwZXItb3JhbmdlLTUwMCk7CiAgICAgIH0KCiAgICAgIC5oaWRkZW4taW5wdXQgewogICAgICAgIGhlaWdodDogMHB4OwogICAgICAgIHdpZHRoOiAwcHg7CiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgICAgfQoKICAgICAgLmFsbGNvbnRyb2xzIC5jb250cm9sLWhvbGRlciB7CiAgICAgICAgY2xlYXI6IGJvdGg7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47CiAgICAgIH0KCiAgICAgIC5hbGxjb250cm9scyAuY29udHJvbC1ob2xkZXIgcGFwZXItcmFkaW8tZ3JvdXAgewogICAgICAgIG1hcmdpbi10b3A6IDVweDsKICAgICAgfQoKICAgICAgc3Bhbi5jb3VudGVyIHsKICAgICAgICBmb250LXNpemU6IDEzcHg7CiAgICAgICAgY29sb3I6IGdyYXk7CiAgICAgIH0KCiAgICAgIC5ydW5zIHBhcGVyLWl0ZW0gewogICAgICAgIC0tcGFwZXItaXRlbTogewogICAgICAgICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIHRhYmxlLmNvbnRyb2wtaG9sZGVyIHsKICAgICAgICBib3JkZXI6IDA7CiAgICAgICAgYm9yZGVyLWNvbGxhcHNlOiBjb2xsYXBzZTsKICAgICAgfQoKICAgICAgdGFibGUudGYtZ3JhcGgtY29udHJvbHMgdGQuaW5wdXQtZWxlbWVudC10YWJsZS1kYXRhIHsKICAgICAgICBwYWRkaW5nOiAwIDAgMCAyMHB4OwogICAgICB9CgogICAgICAuc3BhY2VyIHsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgIH0KCiAgICAgIC5jb2xvci10ZXh0IHsKICAgICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgICB9CgogICAgICAvKiogT3ZlcnJpZGUgaW5saW5lIHN0eWxlcyB0aGF0IHN1cHByZXNzIHBvaW50ZXIgZXZlbnRzIGZvciBkaXNhYmxlZCBidXR0b25zLiBPdGhlcndpc2UsIHRoZSAqLwogICAgICAvKiAgdG9vbHRpcHMgZG8gbm90IGFwcGVhci4gKi8KICAgICAgcGFwZXItcmFkaW8tZ3JvdXAgcGFwZXItcmFkaW8tYnV0dG9uIHsKICAgICAgICBwb2ludGVyLWV2ZW50czogYXV0byAhaW1wb3J0YW50OwogICAgICB9CgogICAgICAubGVnZW5kLWNsYXJpZmllciB7CiAgICAgICAgY29sb3I6ICMyNjYyMzY7CiAgICAgICAgY3Vyc29yOiBoZWxwOwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICB0ZXh0LWRlY29yYXRpb246IHVuZGVybGluZTsKICAgICAgfQoKICAgICAgLmxlZ2VuZC1jbGFyaWZpZXIgcGFwZXItdG9vbHRpcCB7CiAgICAgICAgd2lkdGg6IDE1MHB4OwogICAgICB9CgogICAgICAvKiogT3RoZXJ3aXNlLCBwb2x5bWVyIFVJIGNvbnRyb2xzIGFwcGVhciBhdG9wIG5vZGUgc2VhcmNoLiAqLwogICAgICB0Zi1ncmFwaC1ub2RlLXNlYXJjaCB7CiAgICAgICAgei1pbmRleDogMTsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgcGFwZXItZHJvcGRvd24tbWVudSB7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICB9CiAgICA8L3N0eWxlPgoKICAgIDxkaXYgY2xhc3M9ImFsbGNvbnRyb2xzIj4KICAgICAgPGRpdiBjbGFzcz0iY29udHJvbC1ob2xkZXIiPgogICAgICAgIDx0Zi1ncmFwaC1ub2RlLXNlYXJjaAogICAgICAgICAgc2VsZWN0ZWQtbm9kZT0ie3tzZWxlY3RlZE5vZGV9fSIKICAgICAgICAgIHJlbmRlci1oaWVyYXJjaHk9IltbcmVuZGVySGllcmFyY2h5XV0iCiAgICAgICAgPjwvdGYtZ3JhcGgtbm9kZS1zZWFyY2g+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IGNsYXNzPSJjb250cm9sLWhvbGRlciI+CiAgICAgICAgPHBhcGVyLWJ1dHRvbiBjbGFzcz0iaWNvbi1idXR0b24iIG9uLXRhcD0iX2ZpdCIgYWx0PSJGaXQgdG8gc2NyZWVuIj4KICAgICAgICAgIDxpcm9uLWljb24gaWNvbj0iYXNwZWN0LXJhdGlvIiBjbGFzcz0iYnV0dG9uLWljb24iPjwvaXJvbi1pY29uPgogICAgICAgICAgPHNwYW4gY2xhc3M9ImJ1dHRvbi10ZXh0Ij5GaXQgdG8gU2NyZWVuPC9zcGFuPgogICAgICAgIDwvcGFwZXItYnV0dG9uPgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBjbGFzcz0iY29udHJvbC1ob2xkZXIiPgogICAgICAgIDxwYXBlci1idXR0b24KICAgICAgICAgIGNsYXNzPSJpY29uLWJ1dHRvbiIKICAgICAgICAgIG9uLWNsaWNrPSJkb3dubG9hZCIKICAgICAgICAgIGFsdD0iRG93bmxvYWQgUE5HIgogICAgICAgID4KICAgICAgICAgIDxpcm9uLWljb24gaWNvbj0iZmlsZS1kb3dubG9hZCIgY2xhc3M9ImJ1dHRvbi1pY29uIj48L2lyb24taWNvbj4KICAgICAgICAgIDxzcGFuIGNsYXNzPSJidXR0b24tdGV4dCI+RG93bmxvYWQgUE5HPC9zcGFuPgogICAgICAgIDwvcGFwZXItYnV0dG9uPgogICAgICAgIDxhIGhyZWY9IiMiIGlkPSJncmFwaGRvd25sb2FkIiBjbGFzcz0idGl0bGUiIGRvd25sb2FkPSJncmFwaC5wbmciPjwvYT4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgY2xhc3M9ImNvbnRyb2wtaG9sZGVyIHJ1bnMiPgogICAgICAgIDxkaXYgY2xhc3M9InRpdGxlIj4KICAgICAgICAgIFJ1biA8c3BhbiBjbGFzcz0iY291bnRlciI+KFtbZGF0YXNldHMubGVuZ3RoXV0pPC9zcGFuPgogICAgICAgIDwvZGl2PgogICAgICAgIDxwYXBlci1kcm9wZG93bi1tZW51CiAgICAgICAgICBuby1sYWJlbC1mbG9hdAogICAgICAgICAgbm8tYW5pbWF0aW9ucwogICAgICAgICAgbm9pbmsKICAgICAgICAgIGhvcml6b250YWwtYWxpZ249ImxlZnQiCiAgICAgICAgICBjbGFzcz0icnVuLWRyb3Bkb3duIgogICAgICAgID4KICAgICAgICAgIDxwYXBlci1saXN0Ym94CiAgICAgICAgICAgIGNsYXNzPSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgICBzZWxlY3RlZD0ie3tfc2VsZWN0ZWRSdW5JbmRleH19IgogICAgICAgICAgICBzbG90PSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgPgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW2RhdGFzZXRzXV0iPgogICAgICAgICAgICAgIDxwYXBlci1pdGVtPltbaXRlbS5uYW1lXV08L3BhcGVyLWl0ZW0+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgogICAgICA8L2Rpdj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW3Nob3dTZXNzaW9uUnVuc0Ryb3Bkb3duXV0iPgogICAgICAgIDxkaXYgY2xhc3M9ImNvbnRyb2wtaG9sZGVyIj4KICAgICAgICAgIDxkaXYgY2xhc3M9InRpdGxlIj4KICAgICAgICAgICAgVGFnCiAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjb3VudGVyIgogICAgICAgICAgICAgID4oW1tfbnVtVGFncyhkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgpXV0pPC9zcGFuCiAgICAgICAgICAgID4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPHBhcGVyLWRyb3Bkb3duLW1lbnUKICAgICAgICAgICAgbm8tbGFiZWwtZmxvYXQKICAgICAgICAgICAgbm8tYW5pbWF0aW9ucwogICAgICAgICAgICBob3Jpem9udGFsLWFsaWduPSJsZWZ0IgogICAgICAgICAgICBub2luawogICAgICAgICAgICBjbGFzcz0icnVuLWRyb3Bkb3duIgogICAgICAgICAgPgogICAgICAgICAgICA8cGFwZXItbGlzdGJveAogICAgICAgICAgICAgIGNsYXNzPSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgICAgIHNlbGVjdGVkPSJ7e19zZWxlY3RlZFRhZ0luZGV4fX0iCiAgICAgICAgICAgICAgc2xvdD0iZHJvcGRvd24tY29udGVudCIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgICAgICAgICBpdGVtcz0iW1tfZ2V0VGFncyhkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgpXV0iCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgPHBhcGVyLWl0ZW0+W1tpdGVtLmRpc3BsYXlOYW1lXV08L3BhcGVyLWl0ZW0+CiAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPC9wYXBlci1saXN0Ym94PgogICAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9Iltbc2hvd1VwbG9hZEJ1dHRvbl1dIj4KICAgICAgICA8ZGl2IGNsYXNzPSJjb250cm9sLWhvbGRlciI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJ0aXRsZSI+VXBsb2FkPC9kaXY+CiAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgIHJhaXNlZAogICAgICAgICAgICBjbGFzcz0idXBsb2FkLWJ1dHRvbiIKICAgICAgICAgICAgb24tY2xpY2s9Il9nZXRGaWxlIgogICAgICAgICAgICB0aXRsZT0iVXBsb2FkIGEgZ3JhcGggcGJ0eHQgZmlsZSB0byB2aWV3IHRoZSBncmFwaCIKICAgICAgICAgID4KICAgICAgICAgICAgQ2hvb3NlIEZpbGUKICAgICAgICAgIDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgPGRpdiBjbGFzcz0iaGlkZGVuLWlucHV0Ij4KICAgICAgICAgICAgPGlucHV0CiAgICAgICAgICAgICAgdHlwZT0iZmlsZSIKICAgICAgICAgICAgICBpZD0iZmlsZSIKICAgICAgICAgICAgICBuYW1lPSJmaWxlIgogICAgICAgICAgICAgIG9uLWNoYW5nZT0iX3VwZGF0ZUZpbGVJbnB1dCIKICAgICAgICAgICAgICBhY2NlcHQ9Ii5wYnR4dCIKICAgICAgICAgICAgLz4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgICA8ZGl2IGNsYXNzPSJjb250cm9sLWhvbGRlciI+CiAgICAgICAgPHBhcGVyLXJhZGlvLWdyb3VwIHNlbGVjdGVkPSJ7e19zZWxlY3RlZEdyYXBoVHlwZX19Ij4KICAgICAgICAgIDwhLS0gTm90ZSB0aGF0IHRoZSBuYW1lIGhhcyB0byBtYXRjaCB0aGF0IG9mIHRmX2dyYXBoX2NvbW1vbi5TZWxlY3Rpb25UeXBlLiAtLT4KICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24KICAgICAgICAgICAgbmFtZT0ib3BfZ3JhcGgiCiAgICAgICAgICAgIGRpc2FibGVkPSJbW19nZXRTZWxlY3Rpb25PcEdyYXBoRGlzYWJsZWQoZGF0YXNldHMsIF9zZWxlY3RlZFJ1bkluZGV4LCBfc2VsZWN0ZWRUYWdJbmRleCldXSIKICAgICAgICAgICAgPkdyYXBoPC9wYXBlci1yYWRpby1idXR0b24KICAgICAgICAgID4KICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24KICAgICAgICAgICAgbmFtZT0iY29uY2VwdHVhbF9ncmFwaCIKICAgICAgICAgICAgZGlzYWJsZWQ9IltbX2dldFNlbGVjdGlvbkNvbmNlcHR1YWxHcmFwaERpc2FibGVkKGRhdGFzZXRzLCBfc2VsZWN0ZWRSdW5JbmRleCwgX3NlbGVjdGVkVGFnSW5kZXgpXV0iCiAgICAgICAgICAgID5Db25jZXB0dWFsIEdyYXBoPC9wYXBlci1yYWRpby1idXR0b24KICAgICAgICAgID4KICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24KICAgICAgICAgICAgbmFtZT0icHJvZmlsZSIKICAgICAgICAgICAgZGlzYWJsZWQ9IltbX2dldFNlbGVjdGlvblByb2ZpbGVEaXNhYmxlZChkYXRhc2V0cywgX3NlbGVjdGVkUnVuSW5kZXgsIF9zZWxlY3RlZFRhZ0luZGV4KV1dIgogICAgICAgICAgICA+UHJvZmlsZTwvcGFwZXItcmFkaW8tYnV0dG9uCiAgICAgICAgICA+CiAgICAgICAgPC9wYXBlci1yYWRpby1ncm91cD4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgY2xhc3M9ImNvbnRyb2wtaG9sZGVyIj4KICAgICAgICA8ZGl2PgogICAgICAgICAgPHBhcGVyLXRvZ2dsZS1idXR0b24gY2hlY2tlZD0ie3t0cmFjZUlucHV0c319IiBjbGFzcz0idGl0bGUiPgogICAgICAgICAgICBUcmFjZSBpbnB1dHMKICAgICAgICAgIDwvcGFwZXItdG9nZ2xlLWJ1dHRvbj4KICAgICAgICA8L2Rpdj4KICAgICAgPC9kaXY+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1toZWFsdGhQaWxsc0ZlYXR1cmVFbmFibGVkXV0iPgogICAgICAgIDxkaXYgY2xhc3M9ImNvbnRyb2wtaG9sZGVyIj4KICAgICAgICAgIDxwYXBlci10b2dnbGUtYnV0dG9uIGNoZWNrZWQ9Int7aGVhbHRoUGlsbHNUb2dnbGVkT259fSIgY2xhc3M9InRpdGxlIgogICAgICAgICAgICA+U2hvdyBoZWFsdGggcGlsbHM8L3BhcGVyLXRvZ2dsZS1idXR0b24KICAgICAgICAgID4KICAgICAgICA8L2Rpdj4KICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPGRpdiBjbGFzcz0iY29udHJvbC1ob2xkZXIiPgogICAgICAgIDxkaXYgY2xhc3M9InRpdGxlIj5Db2xvcjwvZGl2PgogICAgICAgIDxwYXBlci1yYWRpby1ncm91cCBzZWxlY3RlZD0ie3tjb2xvckJ5fX0iPgogICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbiBuYW1lPSJzdHJ1Y3R1cmUiPlN0cnVjdHVyZTwvcGFwZXItcmFkaW8tYnV0dG9uPgoKICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24gbmFtZT0iZGV2aWNlIj5EZXZpY2U8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KCiAgICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uCiAgICAgICAgICAgIGlkPSJ4bGEtY2x1c3Rlci1yYWRpby1idXR0b24iCiAgICAgICAgICAgIG5hbWU9InhsYV9jbHVzdGVyIgogICAgICAgICAgICBkaXNhYmxlZD0iW1shX3hsYUNsdXN0ZXJzUHJvdmlkZWQocmVuZGVySGllcmFyY2h5KV1dIgogICAgICAgICAgPgogICAgICAgICAgICBYTEEgQ2x1c3RlcgogICAgICAgICAgPC9wYXBlci1yYWRpby1idXR0b24+CiAgICAgICAgICA8cGFwZXItdG9vbHRpcAogICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgIGZvcj0ieGxhLWNsdXN0ZXItcmFkaW8tYnV0dG9uIgogICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgID4KICAgICAgICAgICAgQ29sb3JpbmcgYnkgWExBIGNsdXN0ZXIgaXMgb25seSBlbmFibGVkIGlmIGF0IGxlYXN0IDEgb3Agc3BlY2lmaWVzCiAgICAgICAgICAgIGFuIFhMQSBjbHVzdGVyLgogICAgICAgICAgPC9wYXBlci10b29sdGlwPgoKICAgICAgICAgIDxwYXBlci1yYWRpby1idXR0b24KICAgICAgICAgICAgaWQ9ImNvbXB1dGUtdGltZS1yYWRpby1idXR0b24iCiAgICAgICAgICAgIG5hbWU9ImNvbXB1dGVfdGltZSIKICAgICAgICAgICAgZGlzYWJsZWQ9IltbIXN0YXRzXV0iCiAgICAgICAgICA+CiAgICAgICAgICAgIENvbXB1dGUgdGltZQogICAgICAgICAgPC9wYXBlci1yYWRpby1idXR0b24+CiAgICAgICAgICA8cGFwZXItdG9vbHRpcAogICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgIGZvcj0iY29tcHV0ZS10aW1lLXJhZGlvLWJ1dHRvbiIKICAgICAgICAgICAgcG9zaXRpb249InJpZ2h0IgogICAgICAgICAgICBvZmZzZXQ9IjAiCiAgICAgICAgICA+CiAgICAgICAgICAgIENvbG9yaW5nIGJ5IGNvbXB1dGUgdGltZSBpcyBvbmx5IGVuYWJsZWQgaWYgdGhlIFJ1bk1ldGFkYXRhIHByb3RvIGlzCiAgICAgICAgICAgIHBhc3NlZCB0byB0aGUgRmlsZVdyaXRlciB3aGVuIGEgc3BlY2lmaWMgc2Vzc2lvbiBpcyBydW4uCiAgICAgICAgICA8L3BhcGVyLXRvb2x0aXA+CgogICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbgogICAgICAgICAgICBpZD0ibWVtb3J5LXJhZGlvLWJ1dHRvbiIKICAgICAgICAgICAgbmFtZT0ibWVtb3J5IgogICAgICAgICAgICBkaXNhYmxlZD0iW1shc3RhdHNdXSIKICAgICAgICAgID4KICAgICAgICAgICAgTWVtb3J5CiAgICAgICAgICA8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgZm9yPSJtZW1vcnktcmFkaW8tYnV0dG9uIgogICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgID4KICAgICAgICAgICAgQ29sb3JpbmcgYnkgbWVtb3J5IGlzIG9ubHkgZW5hYmxlZCBpZiB0aGUgUnVuTWV0YWRhdGEgcHJvdG8gaXMKICAgICAgICAgICAgcGFzc2VkIHRvIHRoZSBGaWxlV3JpdGVyIHdoZW4gYSBzcGVjaWZpYyBzZXNzaW9uIGlzIHJ1bi4KICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KCiAgICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uCiAgICAgICAgICAgIGlkPSJ0cHUtY29tcGF0aWJpbGl0eS1yYWRpby1idXR0b24iCiAgICAgICAgICAgIG5hbWU9Im9wX2NvbXBhdGliaWxpdHkiCiAgICAgICAgICA+CiAgICAgICAgICAgIFRQVSBDb21wYXRpYmlsaXR5CiAgICAgICAgICA8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgZm9yPSJ0cHUtY29tcGF0aWJpbGl0eS1yYWRpby1idXR0b24iCiAgICAgICAgICAgIHBvc2l0aW9uPSJyaWdodCIKICAgICAgICAgICAgb2Zmc2V0PSIwIgogICAgICAgICAgPgogICAgICAgICAgICBDb2xvcmluZyBieSB3aGV0aGVyIGFuIG9wZXJhdGlvbiBpcyBjb21wYXRpYmxlIGZvciB0aGUgVFBVIGRldmljZS4KICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICA8L3BhcGVyLXJhZGlvLWdyb3VwPgogICAgICAgIDxzcGFuIGNsYXNzPSJzcGFjZXIiPjwvc3Bhbj4KICAgICAgPC9kaXY+CiAgICAgIDxkaXY+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19pc0dyYWRpZW50Q29sb3Jpbmcoc3RhdHMsIGNvbG9yQnkpXV0iPgogICAgICAgICAgPHN2ZyB3aWR0aD0iMTQwIiBoZWlnaHQ9IjIwIiBzdHlsZT0ibWFyZ2luOiAwIDVweCIgY2xhc3M9ImNvbG9yLXRleHQiPgogICAgICAgICAgICA8ZGVmcz4KICAgICAgICAgICAgICA8bGluZWFyR3JhZGllbnQKICAgICAgICAgICAgICAgIGlkPSJsaW5lYXJHcmFkaWVudCIKICAgICAgICAgICAgICAgIHgxPSIwJSIKICAgICAgICAgICAgICAgIHkxPSIwJSIKICAgICAgICAgICAgICAgIHgyPSIxMDAlIgogICAgICAgICAgICAgICAgeTI9IjAlIgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxzdG9wCiAgICAgICAgICAgICAgICAgIGNsYXNzPSJzdGFydCIKICAgICAgICAgICAgICAgICAgb2Zmc2V0PSIwJSIKICAgICAgICAgICAgICAgICAgc3RvcC1jb2xvciQ9IltbX2N1cnJlbnRHcmFkaWVudFBhcmFtcy5zdGFydENvbG9yXV0iCiAgICAgICAgICAgICAgICA+PC9zdG9wPgogICAgICAgICAgICAgICAgPHN0b3AKICAgICAgICAgICAgICAgICAgY2xhc3M9ImVuZCIKICAgICAgICAgICAgICAgICAgb2Zmc2V0PSIxMDAlIgogICAgICAgICAgICAgICAgICBzdG9wLWNvbG9yJD0iW1tfY3VycmVudEdyYWRpZW50UGFyYW1zLmVuZENvbG9yXV0iCiAgICAgICAgICAgICAgICA+PC9zdG9wPgogICAgICAgICAgICAgIDwvbGluZWFyR3JhZGllbnQ+CiAgICAgICAgICAgIDwvZGVmcz4KICAgICAgICAgICAgPHJlY3QKICAgICAgICAgICAgICB4PSIwIgogICAgICAgICAgICAgIHk9IjAiCiAgICAgICAgICAgICAgd2lkdGg9IjEzNSIKICAgICAgICAgICAgICBoZWlnaHQ9IjIwIgogICAgICAgICAgICAgIGZpbGw9InVybCgjbGluZWFyR3JhZGllbnQpIgogICAgICAgICAgICAgIHN0cm9rZT0iYmxhY2siCiAgICAgICAgICAgID48L3JlY3Q+CiAgICAgICAgICA8L3N2Zz4KICAgICAgICAgIDxkaXYgY2xhc3M9ImRvbWFpblZhbHVlcyBjb2xvci10ZXh0Ij4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iZG9tYWluU3RhcnQiPltbX2N1cnJlbnRHcmFkaWVudFBhcmFtcy5taW5WYWx1ZV1dPC9kaXY+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9ImRvbWFpbkVuZCI+W1tfY3VycmVudEdyYWRpZW50UGFyYW1zLm1heFZhbHVlXV08L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPGJyIHN0eWxlPSJjbGVhcjogYm90aCIgLz4KICAgICAgICAgIDxkaXY+RGV2aWNlcyBpbmNsdWRlZCBpbiBzdGF0czo8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImRldmljZUxpc3QiPgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19jdXJyZW50RGV2aWNlc11dIj4KICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJjb2xvci1sZWdlbmQtcm93IGRldmljZXMtY2hlY2tib3giPgogICAgICAgICAgICAgICAgPHNwYW4KICAgICAgICAgICAgICAgICAgPjxpbnB1dAogICAgICAgICAgICAgICAgICAgIHR5cGU9ImNoZWNrYm94IgogICAgICAgICAgICAgICAgICAgIHZhbHVlJD0iW1tpdGVtLmRldmljZV1dIgogICAgICAgICAgICAgICAgICAgIGNoZWNrZWQkPSJbW2l0ZW0udXNlZF1dIgogICAgICAgICAgICAgICAgICAgIG9uLWNsaWNrPSJfZGV2aWNlQ2hlY2tib3hDbGlja2VkIgogICAgICAgICAgICAgICAgLz48L3NwYW4+CiAgICAgICAgICAgICAgICA8c3Bhbj5bW2l0ZW0uc3VmZml4XV08L3NwYW4+CiAgICAgICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbaXRlbS5pZ25vcmVkTXNnXV0iPgogICAgICAgICAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgICAgICAgICAgICBpY29uPSJoZWxwIgogICAgICAgICAgICAgICAgICAgIGNsYXNzPSJoZWxwLWljb24iCiAgICAgICAgICAgICAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgICAgICAgICAgICA8cGFwZXItdG9vbHRpcCBwb3NpdGlvbj0icmlnaHQiIG9mZnNldD0iMCIgYW5pbWF0aW9uLWRlbGF5PSIwIgogICAgICAgICAgICAgICAgICAgID5bW2l0ZW0uaWdub3JlZE1zZ11dPC9wYXBlci10b29sdGlwCiAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZXF1YWxzKGNvbG9yQnksICdzdHJ1Y3R1cmUnKV1dIj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbG9yLXRleHQiPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJjb2xvci1sZWdlbmQtcm93Ij4KICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0ibGFiZWwiPiBjb2xvcnMgPC9zcGFuPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjb2xvci1sZWdlbmQtdmFsdWUiPnNhbWUgc3Vic3RydWN0dXJlPC9zcGFuPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29sb3ItbGVnZW5kLXJvdyI+CiAgICAgICAgICAgICAgPHRmLWdyYXBoLWljb24KICAgICAgICAgICAgICAgIHR5cGU9Ik1FVEEiCiAgICAgICAgICAgICAgICBoZWlnaHQ9IjE2IgogICAgICAgICAgICAgICAgZmlsbC1vdmVycmlkZT0iI2VlZSIKICAgICAgICAgICAgICAgIHN0cm9rZS1vdmVycmlkZT0iI2E2YTZhNiIKICAgICAgICAgICAgICA+PC90Zi1ncmFwaC1pY29uPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjb2xvci1sZWdlbmQtdmFsdWUiPnVuaXF1ZSBzdWJzdHJ1Y3R1cmU8L3NwYW4+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC9kaXY+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2VxdWFscyhjb2xvckJ5LCAnZGV2aWNlJyldXSI+CiAgICAgICAgICA8ZGl2PgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19jdXJyZW50RGV2aWNlUGFyYW1zXV0iPgogICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbG9yLWxlZ2VuZC1yb3ciPgogICAgICAgICAgICAgICAgPHRmLWdyYXBoLWljb24KICAgICAgICAgICAgICAgICAgdHlwZT0iTUVUQSIKICAgICAgICAgICAgICAgICAgaGVpZ2h0PSIxNiIKICAgICAgICAgICAgICAgICAgZmlsbC1vdmVycmlkZT0iW1tpdGVtLmNvbG9yXV0iCiAgICAgICAgICAgICAgICAgIHN0cm9rZS1vdmVycmlkZT0iI2E2YTZhNiIKICAgICAgICAgICAgICAgID48L3RmLWdyYXBoLWljb24+CiAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0iY29sb3ItbGVnZW5kLXZhbHVlIj5bW2l0ZW0uZGV2aWNlXV08L3NwYW4+CiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbG9yLWxlZ2VuZC1yb3ciPgogICAgICAgICAgICAgIDx0Zi1ncmFwaC1pY29uCiAgICAgICAgICAgICAgICB0eXBlPSJNRVRBIgogICAgICAgICAgICAgICAgaGVpZ2h0PSIxNiIKICAgICAgICAgICAgICAgIGZpbGwtb3ZlcnJpZGU9IiNlZWUiCiAgICAgICAgICAgICAgICBzdHJva2Utb3ZlcnJpZGU9IiNhNmE2YTYiCiAgICAgICAgICAgICAgPjwvdGYtZ3JhcGgtaWNvbj4KICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0iY29sb3ItbGVnZW5kLXZhbHVlIj51bmtub3duIGRldmljZTwvc3Bhbj4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZXF1YWxzKGNvbG9yQnksICd4bGFfY2x1c3RlcicpXV0iPgogICAgICAgICAgPGRpdj4KICAgICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfY3VycmVudFhsYUNsdXN0ZXJQYXJhbXNdXSI+CiAgICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29sb3ItbGVnZW5kLXJvdyI+CiAgICAgICAgICAgICAgICA8c3ZnPgogICAgICAgICAgICAgICAgICA8dXNlCiAgICAgICAgICAgICAgICAgICAgeG1sbnM6eGxpbms9Imh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmsiCiAgICAgICAgICAgICAgICAgICAgeGxpbms6aHJlZj0iI3VuZmlsbGVkLXJlY3QiCiAgICAgICAgICAgICAgICAgICAgeD0iMCIKICAgICAgICAgICAgICAgICAgICB5PSIwIgogICAgICAgICAgICAgICAgICAgIHN0eWxlPSJmaWxsOltbaXRlbS5jb2xvcl1dIgogICAgICAgICAgICAgICAgICA+PC91c2U+CiAgICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjb2xvci1sZWdlbmQtdmFsdWUiPltbaXRlbS54bGFfY2x1c3Rlcl1dPC9zcGFuPgogICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJjb2xvci1sZWdlbmQtcm93Ij4KICAgICAgICAgICAgICA8c3ZnPgogICAgICAgICAgICAgICAgPHVzZQogICAgICAgICAgICAgICAgICB4bWxuczp4bGluaz0iaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIKICAgICAgICAgICAgICAgICAgeGxpbms6aHJlZj0iI2dyZXktcmVjdCIKICAgICAgICAgICAgICAgICAgeD0iMCIKICAgICAgICAgICAgICAgICAgeT0iMCIKICAgICAgICAgICAgICAgID48L3VzZT4KICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0iY29sb3ItbGVnZW5kLXZhbHVlIj51bmtub3duIFhMQSBjbHVzdGVyPC9zcGFuPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19lcXVhbHMoY29sb3JCeSwgJ29wX2NvbXBhdGliaWxpdHknKV1dIj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbG9yLXRleHQiPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJjb2xvci1sZWdlbmQtcm93Ij4KICAgICAgICAgICAgICA8dGYtZ3JhcGgtaWNvbgogICAgICAgICAgICAgICAgdHlwZT0iT1AiCiAgICAgICAgICAgICAgICBoZWlnaHQ9IjE2IgogICAgICAgICAgICAgICAgZmlsbC1vdmVycmlkZT0iIzBmOWQ1OCIKICAgICAgICAgICAgICAgIHN0cm9rZS1vdmVycmlkZT0iI2NjYyIKICAgICAgICAgICAgICA+PC90Zi1ncmFwaC1pY29uPgogICAgICAgICAgICAgIDxzcGFuIGNsYXNzPSJjb2xvci1sZWdlbmQtdmFsdWUiPlZhbGlkIE9wPC9zcGFuPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iY29sb3ItbGVnZW5kLXJvdyI+CiAgICAgICAgICAgICAgPHRmLWdyYXBoLWljb24KICAgICAgICAgICAgICAgIHR5cGU9Ik9QIgogICAgICAgICAgICAgICAgaGVpZ2h0PSIxNiIKICAgICAgICAgICAgICAgIGZpbGwtb3ZlcnJpZGU9IiNkYjQ0MzciCiAgICAgICAgICAgICAgICBzdHJva2Utb3ZlcnJpZGU9IiNjY2MiCiAgICAgICAgICAgICAgPjwvdGYtZ3JhcGgtaWNvbj4KICAgICAgICAgICAgICA8c3BhbiBjbGFzcz0iY29sb3ItbGVnZW5kLXZhbHVlIj5JbnZhbGlkIE9wPC9zcGFuPgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19zdGF0c05vdE51bGwoc3RhdHMpXV0iPgogICAgICAgICAgPGRpdiBjbGFzcz0iY29sb3ItbGVnZW5kLXJvdyI+CiAgICAgICAgICAgIDx0Zi1ncmFwaC1pY29uIHR5cGU9Ik1FVEEiIGhlaWdodD0iMTYiIGZhZGVkPjwvdGYtZ3JhcGgtaWNvbj4KICAgICAgICAgICAgPHNwYW4gY2xhc3M9ImNvbG9yLWxlZ2VuZC12YWx1ZSI+dW51c2VkIHN1YnN0cnVjdHVyZTwvc3Bhbj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgPC9kaXY+CiAgICA8ZGl2IGNsYXNzPSJsZWdlbmQtaG9sZGVyIj4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgaWNvbj0iW1tfZ2V0VG9nZ2xlTGVnZW5kSWNvbihfbGVnZW5kT3BlbmVkKV1dIgogICAgICAgIG9uLWNsaWNrPSJfdG9nZ2xlTGVnZW5kT3BlbiIKICAgICAgICBjbGFzcz0idG9nZ2xlLWxlZ2VuZC1idXR0b24iCiAgICAgID4KICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgPHNwYW4gY2xhc3M9InRvZ2dsZS1sZWdlbmQtdGV4dCI+CiAgICAgICAgW1tfZ2V0VG9nZ2xlVGV4dChfbGVnZW5kT3BlbmVkKV1dCiAgICAgIDwvc3Bhbj4KICAgICAgPGlyb24tY29sbGFwc2Ugb3BlbmVkPSJbW19sZWdlbmRPcGVuZWRdXSI+CiAgICAgICAgPGRpdj4KICAgICAgICAgIDx0YWJsZT4KICAgICAgICAgICAgPHRib2R5PgogICAgICAgICAgICAgIDx0cj4KICAgICAgICAgICAgICAgIDx0ZD48ZGl2IGNsYXNzPSJ0aXRsZSI+R3JhcGg8L2Rpdj48L3RkPgogICAgICAgICAgICAgICAgPHRkPigqID0gZXhwYW5kYWJsZSk8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8dGYtZ3JhcGgtaWNvbgogICAgICAgICAgICAgICAgICAgIHR5cGU9Ik1FVEEiCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0PSIxNiIKICAgICAgICAgICAgICAgICAgICBmaWxsLW92ZXJyaWRlPSIjZDlkOWQ5IgogICAgICAgICAgICAgICAgICAgIHN0cm9rZS1vdmVycmlkZT0iI2NjYyIKICAgICAgICAgICAgICAgICAgPjwvdGYtZ3JhcGgtaWNvbj4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIE5hbWVzcGFjZTxzcGFuIGNsYXNzPSJncmF5Ij4qPC9zcGFuPgogICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJsZWdlbmQtY2xhcmlmaWVyIj4KICAgICAgICAgICAgICAgICAgICA8c3Bhbj4/PC9zcGFuPgogICAgICAgICAgICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgICAgICAgICAgICBvZmZzZXQ9IjAiCiAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgRW5jYXBzdWxhdGVzIGEgc2V0IG9mIG5vZGVzLiBOYW1lc3BhY2UgaXMgaGllcmFyY2hpY2FsIGFuZAogICAgICAgICAgICAgICAgICAgICAgYmFzZWQgb24gc2NvcGUuCiAgICAgICAgICAgICAgICAgICAgPC9wYXBlci10b29sdGlwPgogICAgICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgPC90cj4KICAgICAgICAgICAgICA8dHI+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIDx0Zi1ncmFwaC1pY29uIHR5cGU9Ik9QIiBoZWlnaHQ9IjE2Ij48L3RmLWdyYXBoLWljb24+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICBPcE5vZGUKICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz0ibGVnZW5kLWNsYXJpZmllciI+CiAgICAgICAgICAgICAgICAgICAgPHNwYW4+Pzwvc3Bhbj4KICAgICAgICAgICAgICAgICAgICA8cGFwZXItdG9vbHRpcAogICAgICAgICAgICAgICAgICAgICAgYW5pbWF0aW9uLWRlbGF5PSIwIgogICAgICAgICAgICAgICAgICAgICAgcG9zaXRpb249InJpZ2h0IgogICAgICAgICAgICAgICAgICAgICAgb2Zmc2V0PSIwIgogICAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgICAgIE5vZGUgdGhhdCBwZXJmb3JtcyBhbiBvcGVyYXRpb24uIFRoZXNlIG5vZGVzIGNhbm5vdAogICAgICAgICAgICAgICAgICAgICAgZXhwYW5kLgogICAgICAgICAgICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8dGYtZ3JhcGgtaWNvbiB0eXBlPSJTRVJJRVMiIGhlaWdodD0iMTYiPjwvdGYtZ3JhcGgtaWNvbj4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIFVuY29ubmVjdGVkIHNlcmllczxzcGFuIGNsYXNzPSJncmF5Ij4qPC9zcGFuPgogICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJsZWdlbmQtY2xhcmlmaWVyIj4KICAgICAgICAgICAgICAgICAgICA8c3Bhbj4/PC9zcGFuPgogICAgICAgICAgICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgICAgICAgICAgICBvZmZzZXQ9IjAiCiAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgU2VxdWVuY2Ugb2YgbnVtYmVyZWQgbm9kZXMgdGhhdCBhcmUgbm90IGNvbm5lY3RlZCB0byBlYWNoCiAgICAgICAgICAgICAgICAgICAgICBvdGhlci4KICAgICAgICAgICAgICAgICAgICA8L3BhcGVyLXRvb2x0aXA+CiAgICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPC90ZD4KICAgICAgICAgICAgICA8L3RyPgogICAgICAgICAgICAgIDx0cj4KICAgICAgICAgICAgICAgIDx0ZD4KICAgICAgICAgICAgICAgICAgPHRmLWdyYXBoLWljb24KICAgICAgICAgICAgICAgICAgICB0eXBlPSJTRVJJRVMiCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0PSIxNiIKICAgICAgICAgICAgICAgICAgICB2ZXJ0aWNhbAogICAgICAgICAgICAgICAgICA+PC90Zi1ncmFwaC1pY29uPgogICAgICAgICAgICAgICAgPC90ZD4KICAgICAgICAgICAgICAgIDx0ZD4KICAgICAgICAgICAgICAgICAgQ29ubmVjdGVkIHNlcmllczxzcGFuIGNsYXNzPSJncmF5Ij4qPC9zcGFuPgogICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJsZWdlbmQtY2xhcmlmaWVyIj4KICAgICAgICAgICAgICAgICAgICA8c3Bhbj4/PC9zcGFuPgogICAgICAgICAgICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgICAgICAgICAgICBvZmZzZXQ9IjAiCiAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgU2VxdWVuY2Ugb2YgbnVtYmVyZWQgbm9kZXMgdGhhdCBhcmUgY29ubmVjdGVkIHRvIGVhY2gKICAgICAgICAgICAgICAgICAgICAgIG90aGVyLgogICAgICAgICAgICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8c3ZnIGNsYXNzPSJpY29uIj4KICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlCiAgICAgICAgICAgICAgICAgICAgICBmaWxsPSJ3aGl0ZSIKICAgICAgICAgICAgICAgICAgICAgIHN0cm9rZT0iIzg0ODQ4NCIKICAgICAgICAgICAgICAgICAgICAgIGN4PSIxMCIKICAgICAgICAgICAgICAgICAgICAgIGN5PSIxMCIKICAgICAgICAgICAgICAgICAgICAgIHI9IjUiCiAgICAgICAgICAgICAgICAgICAgPjwvY2lyY2xlPgogICAgICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIENvbnN0YW50CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImxlZ2VuZC1jbGFyaWZpZXIiPgogICAgICAgICAgICAgICAgICAgIDxzcGFuPj88L3NwYW4+CiAgICAgICAgICAgICAgICAgICAgPHBhcGVyLXRvb2x0aXAKICAgICAgICAgICAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgICAgICAgICAgIHBvc2l0aW9uPSJyaWdodCIKICAgICAgICAgICAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgICBOb2RlIHRoYXQgb3V0cHV0cyBhIGNvbnN0YW50IHZhbHVlLgogICAgICAgICAgICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8dGYtZ3JhcGgtaWNvbiB0eXBlPSJTVU1NQVJZIiBoZWlnaHQ9IjIwIj48L3RmLWdyYXBoLWljb24+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICBTdW1tYXJ5CiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImxlZ2VuZC1jbGFyaWZpZXIiPgogICAgICAgICAgICAgICAgICAgIDxzcGFuPj88L3NwYW4+CiAgICAgICAgICAgICAgICAgICAgPHBhcGVyLXRvb2x0aXAKICAgICAgICAgICAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgICAgICAgICAgIHBvc2l0aW9uPSJyaWdodCIKICAgICAgICAgICAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgICBOb2RlIHRoYXQgY29sbGVjdHMgZGF0YSBmb3IgdmlzdWFsaXphdGlvbiB3aXRoaW4KICAgICAgICAgICAgICAgICAgICAgIFRlbnNvckJvYXJkLgogICAgICAgICAgICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8c3ZnCiAgICAgICAgICAgICAgICAgICAgY2xhc3M9Imljb24iCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0PSIxNXB4IgogICAgICAgICAgICAgICAgICAgIHByZXNlcnZlQXNwZWN0UmF0aW89InhNaW5ZTWlkIG1lZXQiCiAgICAgICAgICAgICAgICAgICAgdmlld0JveD0iMCAwIDE1IDE1IgogICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgPGRlZnM+CiAgICAgICAgICAgICAgICAgICAgICA8bWFya2VyCiAgICAgICAgICAgICAgICAgICAgICAgIGlkPSJkYXRhZmxvdy1hcnJvd2hlYWQtbGVnZW5kIgogICAgICAgICAgICAgICAgICAgICAgICBmaWxsPSIjYmJiIgogICAgICAgICAgICAgICAgICAgICAgICBtYXJrZXJXaWR0aD0iMTAiCiAgICAgICAgICAgICAgICAgICAgICAgIG1hcmtlckhlaWdodD0iMTAiCiAgICAgICAgICAgICAgICAgICAgICAgIHJlZlg9IjkiCiAgICAgICAgICAgICAgICAgICAgICAgIHJlZlk9IjUiCiAgICAgICAgICAgICAgICAgICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgICA8cGF0aCBkPSJNIDAsMCBMIDEwLDUgTCAwLDEwIEMgMyw3IDMsMyAwLDAiPjwvcGF0aD4KICAgICAgICAgICAgICAgICAgICAgIDwvbWFya2VyPgogICAgICAgICAgICAgICAgICAgIDwvZGVmcz4KICAgICAgICAgICAgICAgICAgICA8cGF0aAogICAgICAgICAgICAgICAgICAgICAgbWFya2VyLWVuZD0idXJsKCNkYXRhZmxvdy1hcnJvd2hlYWQtbGVnZW5kKSIKICAgICAgICAgICAgICAgICAgICAgIHN0cm9rZT0iI2JiYiIKICAgICAgICAgICAgICAgICAgICAgIGQ9Ik0yIDkgbCAyOSAwIgogICAgICAgICAgICAgICAgICAgICAgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIgogICAgICAgICAgICAgICAgICAgID48L3BhdGg+CiAgICAgICAgICAgICAgICAgIDwvc3ZnPgogICAgICAgICAgICAgICAgPC90ZD4KICAgICAgICAgICAgICAgIDx0ZD4KICAgICAgICAgICAgICAgICAgRGF0YWZsb3cgZWRnZQogICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPSJsZWdlbmQtY2xhcmlmaWVyIj4KICAgICAgICAgICAgICAgICAgICA8c3Bhbj4/PC9zcGFuPgogICAgICAgICAgICAgICAgICAgIDxwYXBlci10b29sdGlwCiAgICAgICAgICAgICAgICAgICAgICBhbmltYXRpb24tZGVsYXk9IjAiCiAgICAgICAgICAgICAgICAgICAgICBwb3NpdGlvbj0icmlnaHQiCiAgICAgICAgICAgICAgICAgICAgICBvZmZzZXQ9IjAiCiAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgRWRnZSBzaG93aW5nIHRoZSBkYXRhIGZsb3cgYmV0d2VlbiBvcGVyYXRpb25zLiBFZGdlcyBmbG93CiAgICAgICAgICAgICAgICAgICAgICB1cHdhcmRzIHVubGVzcyBhcnJvd2hlYWRzIHNwZWNpZnkgb3RoZXJ3aXNlLgogICAgICAgICAgICAgICAgICAgIDwvcGFwZXItdG9vbHRpcD4KICAgICAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgICAgICA8L3RkPgogICAgICAgICAgICAgIDwvdHI+CiAgICAgICAgICAgICAgPHRyPgogICAgICAgICAgICAgICAgPHRkPgogICAgICAgICAgICAgICAgICA8c3ZnCiAgICAgICAgICAgICAgICAgICAgY2xhc3M9Imljb24iCiAgICAgICAgICAgICAgICAgICAgaGVpZ2h0PSIxNXB4IgogICAgICAgICAgICAgICAgICAgIHByZXNlcnZlQXNwZWN0UmF0aW89InhNaW5ZTWlkIG1lZXQiCiAgICAgICAgICAgICAgICAgICAgdmlld0JveD0iMCAwIDE1IDE1IgogICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgPHBhdGgKICAgICAgICAgICAgICAgICAgICAgIHN0cm9rZT0iI2JiYiIKICAgICAgICAgICAgICAgICAgICAgIGQ9Ik0yIDkgbCAyOSAwIgogICAgICAgICAgICAgICAgICAgICAgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIgogICAgICAgICAgICAgICAgICAgICAgc3Ryb2tlLWRhc2hhcnJheT0iMiwgMiIKICAgICAgICAgICAgICAgICAgICA+PC9wYXRoPgogICAgICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIENvbnRyb2wgZGVwZW5kZW5jeSBlZGdlCiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImxlZ2VuZC1jbGFyaWZpZXIiPgogICAgICAgICAgICAgICAgICAgIDxzcGFuPj88L3NwYW4+CiAgICAgICAgICAgICAgICAgICAgPHBhcGVyLXRvb2x0aXAKICAgICAgICAgICAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgICAgICAgICAgIHBvc2l0aW9uPSJyaWdodCIKICAgICAgICAgICAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgICBFZGdlIHNob3dpbmcgdGhlIGNvbnRyb2wgZGVwZW5kZW5jeSBiZXR3ZWVuIG9wZXJhdGlvbnMuCiAgICAgICAgICAgICAgICAgICAgPC9wYXBlci10b29sdGlwPgogICAgICAgICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgPC90cj4KICAgICAgICAgICAgICA8dHI+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIDxzdmcKICAgICAgICAgICAgICAgICAgICBjbGFzcz0iaWNvbiIKICAgICAgICAgICAgICAgICAgICBoZWlnaHQ9IjE1cHgiCiAgICAgICAgICAgICAgICAgICAgcHJlc2VydmVBc3BlY3RSYXRpbz0ieE1pbllNaWQgbWVldCIKICAgICAgICAgICAgICAgICAgICB2aWV3Qm94PSIwIDAgMTUgMTUiCiAgICAgICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgICAgICA8ZGVmcz4KICAgICAgICAgICAgICAgICAgICAgIDxtYXJrZXIKICAgICAgICAgICAgICAgICAgICAgICAgaWQ9InJlZmVyZW5jZS1hcnJvd2hlYWQtbGVnZW5kIgogICAgICAgICAgICAgICAgICAgICAgICBmaWxsPSIjRkZCNzREIgogICAgICAgICAgICAgICAgICAgICAgICBtYXJrZXJXaWR0aD0iMTAiCiAgICAgICAgICAgICAgICAgICAgICAgIG1hcmtlckhlaWdodD0iMTAiCiAgICAgICAgICAgICAgICAgICAgICAgIHJlZlg9IjkiCiAgICAgICAgICAgICAgICAgICAgICAgIHJlZlk9IjUiCiAgICAgICAgICAgICAgICAgICAgICAgIG9yaWVudD0iYXV0by1zdGFydC1yZXZlcnNlIgogICAgICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgICAgICA8cGF0aCBkPSJNIDAsMCBMIDEwLDUgTCAwLDEwIEMgMyw3IDMsMyAwLDAiPjwvcGF0aD4KICAgICAgICAgICAgICAgICAgICAgIDwvbWFya2VyPgogICAgICAgICAgICAgICAgICAgIDwvZGVmcz4KICAgICAgICAgICAgICAgICAgICA8cGF0aAogICAgICAgICAgICAgICAgICAgICAgbWFya2VyLWVuZD0idXJsKCNyZWZlcmVuY2UtYXJyb3doZWFkLWxlZ2VuZCkiCiAgICAgICAgICAgICAgICAgICAgICBzdHJva2U9IiNGRkI3NEQiCiAgICAgICAgICAgICAgICAgICAgICBkPSJNMiA5IGwgMjkgMCIKICAgICAgICAgICAgICAgICAgICAgIHN0cm9rZS1saW5lY2FwPSJyb3VuZCIKICAgICAgICAgICAgICAgICAgICA+PC9wYXRoPgogICAgICAgICAgICAgICAgICA8L3N2Zz4KICAgICAgICAgICAgICAgIDwvdGQ+CiAgICAgICAgICAgICAgICA8dGQ+CiAgICAgICAgICAgICAgICAgIFJlZmVyZW5jZSBlZGdlCiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImxlZ2VuZC1jbGFyaWZpZXIiPgogICAgICAgICAgICAgICAgICAgIDxzcGFuPj88L3NwYW4+CiAgICAgICAgICAgICAgICAgICAgPHBhcGVyLXRvb2x0aXAKICAgICAgICAgICAgICAgICAgICAgIGFuaW1hdGlvbi1kZWxheT0iMCIKICAgICAgICAgICAgICAgICAgICAgIHBvc2l0aW9uPSJyaWdodCIKICAgICAgICAgICAgICAgICAgICAgIG9mZnNldD0iMCIKICAgICAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgICAgICBFZGdlIHNob3dpbmcgdGhhdCB0aGUgb3V0Z29pbmcgb3BlcmF0aW9uIG5vZGUgY2FuIG11dGF0ZQogICAgICAgICAgICAgICAgICAgICAgdGhlIGluY29taW5nIHRlbnNvci4KICAgICAgICAgICAgICAgICAgICA8L3BhcGVyLXRvb2x0aXA+CiAgICAgICAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgICAgICAgPC90ZD4KICAgICAgICAgICAgICA8L3RyPgogICAgICAgICAgICA8L3Rib2R5PgogICAgICAgICAgPC90YWJsZT4KICAgICAgICA8L2Rpdj4KICAgICAgPC9pcm9uLWNvbGxhcHNlPgogICAgPC9kaXY+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBvYnNlcnZlcjogJ19zdGF0c0NoYW5nZWQnLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaENvbnRyb2xzLnByb3RvdHlwZSwgInN0YXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiZGV2aWNlc0ZvclN0YXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiY29sb3JCeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaENvbnRyb2xzLnByb3RvdHlwZSwgImNvbG9yQnlQYXJhbXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZGF0YXNldHNDaGFuZ2VkJywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhDb250cm9scy5wcm90b3R5cGUsICJkYXRhc2V0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhDb250cm9scy5wcm90b3R5cGUsICJyZW5kZXJIaWVyYXJjaHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgICAgIGNvbXB1dGVkOiAnX2NvbXB1dGVTZWxlY3Rpb24oZGF0YXNldHMsIF9zZWxlY3RlZFJ1bkluZGV4LCBfc2VsZWN0ZWRUYWdJbmRleCwgX3NlbGVjdGVkR3JhcGhUeXBlKScsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAic2VsZWN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAic2VsZWN0ZWRGaWxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBvYnNlcnZlcjogJ19zZWxlY3RlZFJ1bkluZGV4Q2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiX3NlbGVjdGVkUnVuSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaENvbnRyb2xzLnByb3RvdHlwZSwgInRyYWNlSW5wdXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBvYnNlcnZlcjogJ19zZWxlY3RlZFRhZ0luZGV4Q2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiX3NlbGVjdGVkVGFnSW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiX3NlbGVjdGVkR3JhcGhUeXBlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAic2VsZWN0ZWROb2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAic2hvd1Nlc3Npb25SdW5zRHJvcGRvd24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhDb250cm9scy5wcm90b3R5cGUsICJzaG93VXBsb2FkQnV0dG9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiaGVhbHRoUGlsbHNGZWF0dXJlRW5hYmxlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiaGVhbHRoUGlsbHNUb2dnbGVkT24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhDb250cm9scy5wcm90b3R5cGUsICJfbGVnZW5kT3BlbmVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdkZXZpY2VzRm9yU3RhdHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaENvbnRyb2xzLnByb3RvdHlwZSwgIl9jdXJyZW50RGV2aWNlcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ2NvbG9yQnlQYXJhbXMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZHcmFwaENvbnRyb2xzLnByb3RvdHlwZSwgIl9jdXJyZW50RGV2aWNlUGFyYW1zIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnY29sb3JCeVBhcmFtcycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiX2N1cnJlbnRYbGFDbHVzdGVyUGFyYW1zIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnY29sb3JCeVBhcmFtcycsICdjb2xvckJ5JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkdyYXBoQ29udHJvbHMucHJvdG90eXBlLCAiX2N1cnJlbnRHcmFkaWVudFBhcmFtcyIsIG51bGwpOwogICAgVGZHcmFwaENvbnRyb2xzID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZ3JhcGgtY29udHJvbHMnKQogICAgXSwgVGZHcmFwaENvbnRyb2xzKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNyBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAnTGljZW5zZScpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICdBUyBJUycgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGNsYXNzIFRwdUNvbXBhdGliaWxpdHlQcm92aWRlciB7CiAgICAgICAgLyoqCiAgICAgICAgICogUmV0dXJucyB0cnVlIGlmIHRoZSBub2RlJ3MgaW5mZXJyZWQgZGV2aWNlIGlzIG5vdCB0aGUgVFBVLgogICAgICAgICAqIE5vdGUgdGhhdCB0aGlzIGlzIG9ubHkgYSBiZXN0LWVmZm9ydCBjaGVjay4KICAgICAgICAgKi8KICAgICAgICBpc05vdFRwdU9wKG9wRGV2aWNlKSB7CiAgICAgICAgICAgIGlmIChvcERldmljZS50b0xvd2VyQ2FzZSgpLnNlYXJjaCgnY3B1OicpICE9IC0xKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob3BEZXZpY2UudG9Mb3dlckNhc2UoKS5zZWFyY2goJ2dwdTonKSAhPSAtMSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG9wRGV2aWNlLnRvTG93ZXJDYXNlKCkuc2VhcmNoKCd0cHUnKSA9PSAtMTsKICAgICAgICB9CiAgICAgICAgb3BWYWxpZChvcE5vZGUpIHsKICAgICAgICAgICAgLy8gRnVuY3Rpb24gbGlicmFyeSBub2RlcyBhcmUgZ2VuZXJhbGx5IGZvciBpbnRlcm5hbCB1c2UuCiAgICAgICAgICAgIGlmIChvcE5vZGUubmFtZS5zZWFyY2goRlVOQ1RJT05fTElCUkFSWV9OT0RFX1BSRUZJWCkgPT0gMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gTm9kZXMgdGhhdCBsYWNrIG9wIHR5cGVzIHNob3VsZCBiZSBpZ25vcmVkLgogICAgICAgICAgICBpZiAoIW9wTm9kZS5vcCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gSWYgYXNzaWduZWQgYSBkZXZpY2UgdGhhdCBpcyBub3QgVFBVLXJlbGF0ZWQgYXNzdW1lIG9wIGlzIHZhbGlkLgogICAgICAgICAgICBpZiAob3BOb2RlLmRldmljZSAmJiB0aGlzLmlzTm90VHB1T3Aob3BOb2RlLmRldmljZSkpIHsKICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIElmIGFzc2lnbmVkIHRvIHRoZSBUUFVfU1lTVEVNIGRldmljZSwgYXNzdW1lIG9wIGlzIHZhbGlkLgogICAgICAgICAgICBpZiAob3BOb2RlLmRldmljZSAmJiBvcE5vZGUuZGV2aWNlLnNlYXJjaCgnVFBVX1NZU1RFTScpICE9IC0xKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gbG9kYXNoLmluY2x1ZGVzKFRwdUNvbXBhdGliaWxpdHlQcm92aWRlci5XSElURUxJU1QsIG9wTm9kZS5vcCk7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBBbGxvd2VkIGxpc3Qgb2YgY3VycmVudCBUZW5zb3JmbG93IG9wcyB2YWxpZCBvbiB0aGUgVFBVLgogICAgICogTm90ZSB0aGF0IHNvbWUgZGF0YSB0eXBlcyBtYXkgYmUgdW5zdXBwb3J0ZWQuCiAgICAgKi8KICAgIFRwdUNvbXBhdGliaWxpdHlQcm92aWRlci5XSElURUxJU1QgPSBbCiAgICAgICAgJ0FicycsCiAgICAgICAgJ0Fjb3MnLAogICAgICAgICdBY29zaCcsCiAgICAgICAgJ0FkZCcsCiAgICAgICAgJ0FkZE4nLAogICAgICAgICdBZGRWMicsCiAgICAgICAgJ0FkanVzdENvbnRyYXN0djInLAogICAgICAgICdBZGp1c3RIdWUnLAogICAgICAgICdBZGp1c3RTYXR1cmF0aW9uJywKICAgICAgICAnQWxsJywKICAgICAgICAnQWxsVG9BbGwnLAogICAgICAgICdBbmdsZScsCiAgICAgICAgJ0FueScsCiAgICAgICAgJ0FwcHJveGltYXRlRXF1YWwnLAogICAgICAgICdBcmdNYXgnLAogICAgICAgICdBcmdNaW4nLAogICAgICAgICdBc2luJywKICAgICAgICAnQXNpbmgnLAogICAgICAgICdBc3NlcnQnLAogICAgICAgICdBc3NpZ25BZGRWYXJpYWJsZU9wJywKICAgICAgICAnQXNzaWduU3ViVmFyaWFibGVPcCcsCiAgICAgICAgJ0Fzc2lnblZhcmlhYmxlT3AnLAogICAgICAgICdBdGFuJywKICAgICAgICAnQXRhbjInLAogICAgICAgICdBdGFuaCcsCiAgICAgICAgJ0F2Z1Bvb2wnLAogICAgICAgICdBdmdQb29sM0QnLAogICAgICAgICdBdmdQb29sM0RHcmFkJywKICAgICAgICAnQXZnUG9vbEdyYWQnLAogICAgICAgICdCYXRjaE1hdE11bCcsCiAgICAgICAgJ0JhdGNoTWF0TXVsVjInLAogICAgICAgICdCYXRjaFRvU3BhY2UnLAogICAgICAgICdCYXRjaFRvU3BhY2VORCcsCiAgICAgICAgJ0Jlc3NlbEkwZScsCiAgICAgICAgJ0Jlc3NlbEkxZScsCiAgICAgICAgJ0JldGFpbmMnLAogICAgICAgICdCaWFzQWRkJywKICAgICAgICAnQmlhc0FkZEdyYWQnLAogICAgICAgICdCaWFzQWRkVjEnLAogICAgICAgICdCaXRjYXN0JywKICAgICAgICAnQml0d2lzZUFuZCcsCiAgICAgICAgJ0JpdHdpc2VPcicsCiAgICAgICAgJ0JpdHdpc2VYb3InLAogICAgICAgICdCcm9hZGNhc3RBcmdzJywKICAgICAgICAnQnJvYWRjYXN0R3JhZGllbnRBcmdzJywKICAgICAgICAnQnJvYWRjYXN0VG8nLAogICAgICAgICdCdWNrZXRpemUnLAogICAgICAgICdDYXNlJywKICAgICAgICAnQ2FzdCcsCiAgICAgICAgJ0NlaWwnLAogICAgICAgICdDaGVja051bWVyaWNzJywKICAgICAgICAnQ2hvbGVza3knLAogICAgICAgICdDbGlwQnlWYWx1ZScsCiAgICAgICAgJ0NvbGxlY3RpdmVQZXJtdXRlJywKICAgICAgICAnQ29tcGxleCcsCiAgICAgICAgJ0NvbXBsZXhBYnMnLAogICAgICAgICdDb25jYXQnLAogICAgICAgICdDb25jYXRPZmZzZXQnLAogICAgICAgICdDb25jYXRWMicsCiAgICAgICAgJ0NvbmonLAogICAgICAgICdDb25qdWdhdGVUcmFuc3Bvc2UnLAogICAgICAgICdDb25zdCcsCiAgICAgICAgJ0NvbnRyb2xUcmlnZ2VyJywKICAgICAgICAnQ29udjJEJywKICAgICAgICAnQ29udjJEQmFja3Byb3BGaWx0ZXInLAogICAgICAgICdDb252MkRCYWNrcHJvcElucHV0JywKICAgICAgICAnQ29udjNEJywKICAgICAgICAnQ29udjNEQmFja3Byb3BGaWx0ZXJWMicsCiAgICAgICAgJ0NvbnYzREJhY2twcm9wSW5wdXRWMicsCiAgICAgICAgJ0NvcycsCiAgICAgICAgJ0Nvc2gnLAogICAgICAgICdDcm9zcycsCiAgICAgICAgJ0Nyb3NzUmVwbGljYVN1bScsCiAgICAgICAgJ0N1bXByb2QnLAogICAgICAgICdDdW1zdW0nLAogICAgICAgICdEYXRhRm9ybWF0RGltTWFwJywKICAgICAgICAnRGF0YUZvcm1hdFZlY1Blcm11dGUnLAogICAgICAgICdEYXRhRm9ybWF0VmVjUGVybXV0ZScsCiAgICAgICAgJ0RlcHRoVG9TcGFjZScsCiAgICAgICAgJ0RlcHRod2lzZUNvbnYyZE5hdGl2ZScsCiAgICAgICAgJ0RlcHRod2lzZUNvbnYyZE5hdGl2ZUJhY2twcm9wRmlsdGVyJywKICAgICAgICAnRGVwdGh3aXNlQ29udjJkTmF0aXZlQmFja3Byb3BJbnB1dCcsCiAgICAgICAgJ0RlcXVhbnRpemUnLAogICAgICAgICdEZXZpY2VJbmRleCcsCiAgICAgICAgJ0RpYWcnLAogICAgICAgICdEaWFnUGFydCcsCiAgICAgICAgJ0RpZ2FtbWEnLAogICAgICAgICdEaXYnLAogICAgICAgICdEaXZOb05hbicsCiAgICAgICAgJ0R5bmFtaWNTdGl0Y2gnLAogICAgICAgICdFaW5zdW0nLAogICAgICAgICdFbHUnLAogICAgICAgICdFbHVHcmFkJywKICAgICAgICAnRW1wdHknLAogICAgICAgICdFbXB0eVRlbnNvckxpc3QnLAogICAgICAgICdFbnN1cmVTaGFwZScsCiAgICAgICAgJ0VxdWFsJywKICAgICAgICAnRXJmJywKICAgICAgICAnRXJmYycsCiAgICAgICAgJ0VyZmludicsCiAgICAgICAgJ0V4cCcsCiAgICAgICAgJ0V4cGFuZERpbXMnLAogICAgICAgICdFeHBtMScsCiAgICAgICAgJ0V4dHJhY3RJbWFnZVBhdGNoZXMnLAogICAgICAgICdGRlQnLAogICAgICAgICdGRlQyRCcsCiAgICAgICAgJ0ZGVDNEJywKICAgICAgICAnRmFrZVBhcmFtJywKICAgICAgICAnRmFrZVF1YW50V2l0aE1pbk1heEFyZ3MnLAogICAgICAgICdGYWtlUXVhbnRXaXRoTWluTWF4QXJnc0dyYWRpZW50JywKICAgICAgICAnRmFrZVF1YW50V2l0aE1pbk1heFZhcnMnLAogICAgICAgICdGYWtlUXVhbnRXaXRoTWluTWF4VmFyc0dyYWRpZW50JywKICAgICAgICAnRmlsbCcsCiAgICAgICAgJ0Zsb29yJywKICAgICAgICAnRmxvb3JEaXYnLAogICAgICAgICdGbG9vck1vZCcsCiAgICAgICAgJ0Z1c2VkQmF0Y2hOb3JtJywKICAgICAgICAnRnVzZWRCYXRjaE5vcm1HcmFkJywKICAgICAgICAnRnVzZWRCYXRjaE5vcm1HcmFkVjInLAogICAgICAgICdGdXNlZEJhdGNoTm9ybUdyYWRWMycsCiAgICAgICAgJ0Z1c2VkQmF0Y2hOb3JtVjInLAogICAgICAgICdGdXNlZEJhdGNoTm9ybVYzJywKICAgICAgICAnR2F0aGVyJywKICAgICAgICAnR2F0aGVyTmQnLAogICAgICAgICdHYXRoZXJWMicsCiAgICAgICAgJ0dldEl0ZW0nLAogICAgICAgICdHcmVhdGVyJywKICAgICAgICAnR3JlYXRlckVxdWFsJywKICAgICAgICAnSFNWVG9SR0InLAogICAgICAgICdJRkZUJywKICAgICAgICAnSUZGVDJEJywKICAgICAgICAnSUZGVDNEJywKICAgICAgICAnSVJGRlQnLAogICAgICAgICdJUkZGVDJEJywKICAgICAgICAnSVJGRlQzRCcsCiAgICAgICAgJ0lkZW50aXR5JywKICAgICAgICAnSWRlbnRpdHlOJywKICAgICAgICAnSWYnLAogICAgICAgICdJZ2FtbWEnLAogICAgICAgICdJZ2FtbWFHcmFkQScsCiAgICAgICAgJ0lnYW1tYWMnLAogICAgICAgICdJbWFnJywKICAgICAgICAnSW5Ub3BLVjInLAogICAgICAgICdJbmZlZWREZXF1ZXVlJywKICAgICAgICAnSW5mZWVkRGVxdWV1ZVR1cGxlJywKICAgICAgICAnSW5wbGFjZUFkZCcsCiAgICAgICAgJ0lucGxhY2VVcGRhdGUnLAogICAgICAgICdJbnYnLAogICAgICAgICdJbnZlcnQnLAogICAgICAgICdJbnZlcnRQZXJtdXRhdGlvbicsCiAgICAgICAgJ0lzRmluaXRlJywKICAgICAgICAnSXNJbmYnLAogICAgICAgICdJc05hbicsCiAgICAgICAgJ0t0aE9yZGVyU3RhdGlzdGljJywKICAgICAgICAnTDJMb3NzJywKICAgICAgICAnTFJOJywKICAgICAgICAnTFJOR3JhZCcsCiAgICAgICAgJ0xlYWt5UmVsdScsCiAgICAgICAgJ0xlYWt5UmVsdUdyYWQnLAogICAgICAgICdMZWZ0U2hpZnQnLAogICAgICAgICdMZXNzJywKICAgICAgICAnTGVzc0VxdWFsJywKICAgICAgICAnTGdhbW1hJywKICAgICAgICAnTGluU3BhY2UnLAogICAgICAgICdMaXN0RGlmZicsCiAgICAgICAgJ0xvZycsCiAgICAgICAgJ0xvZzFwJywKICAgICAgICAnTG9nU29mdG1heCcsCiAgICAgICAgJ0xvZ2ljYWxBbmQnLAogICAgICAgICdMb2dpY2FsTm90JywKICAgICAgICAnTG9naWNhbE9yJywKICAgICAgICAnTG93ZXJCb3VuZCcsCiAgICAgICAgJ01ha2VVbmlxdWUnLAogICAgICAgICdNYXRNdWwnLAogICAgICAgICdNYXRyaXhCYW5kUGFydCcsCiAgICAgICAgJ01hdHJpeERpYWcnLAogICAgICAgICdNYXRyaXhEaWFnUGFydCcsCiAgICAgICAgJ01hdHJpeERpYWdQYXJ0VjInLAogICAgICAgICdNYXRyaXhEaWFnUGFydFYzJywKICAgICAgICAnTWF0cml4RGlhZ1YyJywKICAgICAgICAnTWF0cml4RGlhZ1YzJywKICAgICAgICAnTWF0cml4SW52ZXJzZScsCiAgICAgICAgJ01hdHJpeFNldERpYWcnLAogICAgICAgICdNYXRyaXhTZXREaWFnVjInLAogICAgICAgICdNYXRyaXhTZXREaWFnVjMnLAogICAgICAgICdNYXRyaXhTb2x2ZScsCiAgICAgICAgJ01hdHJpeFRyaWFuZ3VsYXJTb2x2ZScsCiAgICAgICAgJ01heCcsCiAgICAgICAgJ01heFBvb2wnLAogICAgICAgICdNYXhQb29sM0QnLAogICAgICAgICdNYXhQb29sM0RHcmFkJywKICAgICAgICAnTWF4UG9vbDNER3JhZEdyYWQnLAogICAgICAgICdNYXhQb29sR3JhZCcsCiAgICAgICAgJ01heFBvb2xHcmFkR3JhZCcsCiAgICAgICAgJ01heFBvb2xHcmFkR3JhZFYyJywKICAgICAgICAnTWF4UG9vbEdyYWRWMicsCiAgICAgICAgJ01heFBvb2xWMicsCiAgICAgICAgJ01heGltdW0nLAogICAgICAgICdNZWFuJywKICAgICAgICAnTWluJywKICAgICAgICAnTWluaW11bScsCiAgICAgICAgJ01pcnJvclBhZCcsCiAgICAgICAgJ01vZCcsCiAgICAgICAgJ011bCcsCiAgICAgICAgJ011bE5vTmFuJywKICAgICAgICAnTXVsdGlub21pYWwnLAogICAgICAgICdOZHRyaScsCiAgICAgICAgJ05lZycsCiAgICAgICAgJ05leHRBZnRlcicsCiAgICAgICAgJ05vT3AnLAogICAgICAgICdOb25NYXhTdXBwcmVzc2lvblY0JywKICAgICAgICAnTm90RXF1YWwnLAogICAgICAgICdPbmVIb3QnLAogICAgICAgICdPbmVzTGlrZScsCiAgICAgICAgJ091dGZlZWRFbnF1ZXVlJywKICAgICAgICAnT3V0ZmVlZEVucXVldWVUdXBsZScsCiAgICAgICAgJ1BhY2snLAogICAgICAgICdQYWQnLAogICAgICAgICdQYWRWMicsCiAgICAgICAgJ1BhcmFsbGVsRHluYW1pY1N0aXRjaCcsCiAgICAgICAgJ1BhcmFtZXRlcml6ZWRUcnVuY2F0ZWROb3JtYWwnLAogICAgICAgICdQYXJ0aXRpb25lZENhbGwnLAogICAgICAgICdQbGFjZWhvbGRlcldpdGhEZWZhdWx0JywKICAgICAgICAnUG9wdWxhdGlvbkNvdW50JywKICAgICAgICAnUG93JywKICAgICAgICAnUHJldmVudEdyYWRpZW50JywKICAgICAgICAnUHJvZCcsCiAgICAgICAgJ1FyJywKICAgICAgICAnUXVhbnRpemVBbmREZXF1YW50aXplVjInLAogICAgICAgICdRdWFudGl6ZUFuZERlcXVhbnRpemVWMycsCiAgICAgICAgJ1JGRlQnLAogICAgICAgICdSRkZUMkQnLAogICAgICAgICdSRkZUM0QnLAogICAgICAgICdSR0JUb0hTVicsCiAgICAgICAgJ1JhbmRvbUdhbW1hR3JhZCcsCiAgICAgICAgJ1JhbmRvbVNodWZmbGUnLAogICAgICAgICdSYW5kb21TdGFuZGFyZE5vcm1hbCcsCiAgICAgICAgJ1JhbmRvbVVuaWZvcm0nLAogICAgICAgICdSYW5kb21Vbmlmb3JtSW50JywKICAgICAgICAnUmFuZ2UnLAogICAgICAgICdSYW5rJywKICAgICAgICAnUmVhZFZhcmlhYmxlT3AnLAogICAgICAgICdSZWFsJywKICAgICAgICAnUmVhbERpdicsCiAgICAgICAgJ1JlY2lwcm9jYWwnLAogICAgICAgICdSZWNpcHJvY2FsR3JhZCcsCiAgICAgICAgJ1JlbHUnLAogICAgICAgICdSZWx1NicsCiAgICAgICAgJ1JlbHU2R3JhZCcsCiAgICAgICAgJ1JlbHVHcmFkJywKICAgICAgICAnUmVzaGFwZScsCiAgICAgICAgJ1Jlc2l6ZUJpbGluZWFyJywKICAgICAgICAnUmVzaXplQmlsaW5lYXJHcmFkJywKICAgICAgICAnUmVzaXplTmVhcmVzdE5laWdoYm9yJywKICAgICAgICAnUmVzaXplTmVhcmVzdE5laWdoYm9yR3JhZCcsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlBZGFNYXgnLAogICAgICAgICdSZXNvdXJjZUFwcGx5QWRhZGVsdGEnLAogICAgICAgICdSZXNvdXJjZUFwcGx5QWRhZ3JhZCcsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlBZGFncmFkREEnLAogICAgICAgICdSZXNvdXJjZUFwcGx5QWRhZ3JhZFYyJywKICAgICAgICAnUmVzb3VyY2VBcHBseUFkYW0nLAogICAgICAgICdSZXNvdXJjZUFwcGx5QWRkU2lnbicsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlDZW50ZXJlZFJNU1Byb3AnLAogICAgICAgICdSZXNvdXJjZUFwcGx5RnRybCcsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlGdHJsVjInLAogICAgICAgICdSZXNvdXJjZUFwcGx5R3JhZGllbnREZXNjZW50JywKICAgICAgICAnUmVzb3VyY2VBcHBseUtlcmFzTW9tZW50dW0nLAogICAgICAgICdSZXNvdXJjZUFwcGx5TW9tZW50dW0nLAogICAgICAgICdSZXNvdXJjZUFwcGx5UG93ZXJTaWduJywKICAgICAgICAnUmVzb3VyY2VBcHBseVByb3hpbWFsQWRhZ3JhZCcsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlQcm94aW1hbEdyYWRpZW50RGVzY2VudCcsCiAgICAgICAgJ1Jlc291cmNlQXBwbHlSTVNQcm9wJywKICAgICAgICAnUmVzb3VyY2VHYXRoZXInLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJBZGQnLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJEaXYnLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJNYXgnLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJNaW4nLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJNdWwnLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJOZEFkZCcsCiAgICAgICAgJ1Jlc291cmNlU2NhdHRlck5kU3ViJywKICAgICAgICAnUmVzb3VyY2VTY2F0dGVyTmRVcGRhdGUnLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJTdWInLAogICAgICAgICdSZXNvdXJjZVNjYXR0ZXJVcGRhdGUnLAogICAgICAgICdSZXNvdXJjZVN0cmlkZWRTbGljZUFzc2lnbicsCiAgICAgICAgJ1JldmVyc2UnLAogICAgICAgICdSZXZlcnNlU2VxdWVuY2UnLAogICAgICAgICdSZXZlcnNlVjInLAogICAgICAgICdSaWdodFNoaWZ0JywKICAgICAgICAnUmludCcsCiAgICAgICAgJ1JvbGwnLAogICAgICAgICdSb3VuZCcsCiAgICAgICAgJ1JzcXJ0JywKICAgICAgICAnUnNxcnRHcmFkJywKICAgICAgICAnU2NhdHRlck5kJywKICAgICAgICAnU2VsZWN0JywKICAgICAgICAnU2VsZWN0VjInLAogICAgICAgICdTZWxmQWRqb2ludEVpZ1YyJywKICAgICAgICAnU2VsdScsCiAgICAgICAgJ1NlbHVHcmFkJywKICAgICAgICAnU2hhcGUnLAogICAgICAgICdTaGFwZU4nLAogICAgICAgICdTaWdtb2lkJywKICAgICAgICAnU2lnbW9pZEdyYWQnLAogICAgICAgICdTaWduJywKICAgICAgICAnU2luJywKICAgICAgICAnU2luaCcsCiAgICAgICAgJ1NpemUnLAogICAgICAgICdTbGljZScsCiAgICAgICAgJ1NuYXBzaG90JywKICAgICAgICAnU29mdG1heCcsCiAgICAgICAgJ1NvZnRtYXhDcm9zc0VudHJvcHlXaXRoTG9naXRzJywKICAgICAgICAnU29mdHBsdXMnLAogICAgICAgICdTb2Z0cGx1c0dyYWQnLAogICAgICAgICdTb2Z0c2lnbicsCiAgICAgICAgJ1NvZnRzaWduR3JhZCcsCiAgICAgICAgJ1NwYWNlVG9CYXRjaCcsCiAgICAgICAgJ1NwYWNlVG9CYXRjaE5EJywKICAgICAgICAnU3BhY2VUb0RlcHRoJywKICAgICAgICAnU3BhcnNlTWF0TXVsJywKICAgICAgICAnU3BhcnNlU29mdG1heENyb3NzRW50cm9weVdpdGhMb2dpdHMnLAogICAgICAgICdTcGFyc2VUb0RlbnNlJywKICAgICAgICAnU3BsaXQnLAogICAgICAgICdTcGxpdFYnLAogICAgICAgICdTcXJ0JywKICAgICAgICAnU3FydEdyYWQnLAogICAgICAgICdTcXVhcmUnLAogICAgICAgICdTcXVhcmVkRGlmZmVyZW5jZScsCiAgICAgICAgJ1NxdWVlemUnLAogICAgICAgICdTdGFja0Nsb3NlVjInLAogICAgICAgICdTdGFja1BvcFYyJywKICAgICAgICAnU3RhY2tQdXNoVjInLAogICAgICAgICdTdGFja1YyJywKICAgICAgICAnU3RhdGVmdWxQYXJ0aXRpb25lZENhbGwnLAogICAgICAgICdTdGF0ZWZ1bFN0YW5kYXJkTm9ybWFsVjInLAogICAgICAgICdTdGF0ZWZ1bFRydW5jYXRlZE5vcm1hbCcsCiAgICAgICAgJ1N0YXRlZnVsVW5pZm9ybScsCiAgICAgICAgJ1N0YXRlZnVsVW5pZm9ybUZ1bGxJbnQnLAogICAgICAgICdTdGF0ZWZ1bFVuaWZvcm1JbnQnLAogICAgICAgICdTdGF0ZWxlc3NDYXNlJywKICAgICAgICAnU3RhdGVsZXNzSWYnLAogICAgICAgICdTdGF0ZWxlc3NNdWx0aW5vbWlhbCcsCiAgICAgICAgJ1N0YXRlbGVzc1JhbmRvbU5vcm1hbCcsCiAgICAgICAgJ1N0YXRlbGVzc1JhbmRvbVVuaWZvcm0nLAogICAgICAgICdTdGF0ZWxlc3NSYW5kb21Vbmlmb3JtRnVsbEludCcsCiAgICAgICAgJ1N0YXRlbGVzc1JhbmRvbVVuaWZvcm1JbnQnLAogICAgICAgICdTdGF0ZWxlc3NUcnVuY2F0ZWROb3JtYWwnLAogICAgICAgICdTdGF0ZWxlc3NXaGlsZScsCiAgICAgICAgJ1N0b3BHcmFkaWVudCcsCiAgICAgICAgJ1N0cmlkZWRTbGljZScsCiAgICAgICAgJ1N0cmlkZWRTbGljZUdyYWQnLAogICAgICAgICdTdWInLAogICAgICAgICdTdW0nLAogICAgICAgICdTdmQnLAogICAgICAgICdTeW1ib2xpY0dyYWRpZW50JywKICAgICAgICAnVFBVRW1iZWRkaW5nQWN0aXZhdGlvbnMnLAogICAgICAgICdUYW4nLAogICAgICAgICdUYW5oJywKICAgICAgICAnVGFuaEdyYWQnLAogICAgICAgICdUZW5zb3JBcnJheUNsb3NlVjMnLAogICAgICAgICdUZW5zb3JBcnJheUNvbmNhdFYzJywKICAgICAgICAnVGVuc29yQXJyYXlHYXRoZXJWMycsCiAgICAgICAgJ1RlbnNvckFycmF5R3JhZFYzJywKICAgICAgICAnVGVuc29yQXJyYXlSZWFkVjMnLAogICAgICAgICdUZW5zb3JBcnJheVNjYXR0ZXJWMycsCiAgICAgICAgJ1RlbnNvckFycmF5U2l6ZVYzJywKICAgICAgICAnVGVuc29yQXJyYXlTcGxpdFYzJywKICAgICAgICAnVGVuc29yQXJyYXlWMycsCiAgICAgICAgJ1RlbnNvckFycmF5V3JpdGVWMycsCiAgICAgICAgJ1RlbnNvckxpc3RDb25jYXRWMicsCiAgICAgICAgJ1RlbnNvckxpc3RFbGVtZW50U2hhcGUnLAogICAgICAgICdUZW5zb3JMaXN0RnJvbVRlbnNvcicsCiAgICAgICAgJ1RlbnNvckxpc3RHYXRoZXInLAogICAgICAgICdUZW5zb3JMaXN0R2V0SXRlbScsCiAgICAgICAgJ1RlbnNvckxpc3RMZW5ndGgnLAogICAgICAgICdUZW5zb3JMaXN0UG9wQmFjaycsCiAgICAgICAgJ1RlbnNvckxpc3RQdXNoQmFjaycsCiAgICAgICAgJ1RlbnNvckxpc3RSZXNlcnZlJywKICAgICAgICAnVGVuc29yTGlzdFNldEl0ZW0nLAogICAgICAgICdUZW5zb3JMaXN0U3BsaXQnLAogICAgICAgICdUZW5zb3JMaXN0U3RhY2snLAogICAgICAgICdUZW5zb3JTY2F0dGVyQWRkJywKICAgICAgICAnVGVuc29yU2NhdHRlclN1YicsCiAgICAgICAgJ1RlbnNvclNjYXR0ZXJVcGRhdGUnLAogICAgICAgICdUaWxlJywKICAgICAgICAnVG9wS1VuaXF1ZScsCiAgICAgICAgJ1RvcEtWMicsCiAgICAgICAgJ1RvcEtXaXRoVW5pcXVlJywKICAgICAgICAnVHJhbnNwb3NlJywKICAgICAgICAnVHJpZGlhZ29uYWxTb2x2ZScsCiAgICAgICAgJ1RydW5jYXRlRGl2JywKICAgICAgICAnVHJ1bmNhdGVNb2QnLAogICAgICAgICdUcnVuY2F0ZWROb3JtYWwnLAogICAgICAgICdVbnBhY2snLAogICAgICAgICdVbnNvcnRlZFNlZ21lbnRNYXgnLAogICAgICAgICdVbnNvcnRlZFNlZ21lbnRNaW4nLAogICAgICAgICdVbnNvcnRlZFNlZ21lbnRQcm9kJywKICAgICAgICAnVW5zb3J0ZWRTZWdtZW50U3VtJywKICAgICAgICAnVXBwZXJCb3VuZCcsCiAgICAgICAgJ1ZhcklzSW5pdGlhbGl6ZWRPcCcsCiAgICAgICAgJ1ZhcmlhYmxlU2hhcGUnLAogICAgICAgICdXaGVyZScsCiAgICAgICAgJ1doaWxlJywKICAgICAgICAnWGRpdnknLAogICAgICAgICdYbGFCcm9hZGNhc3RIZWxwZXInLAogICAgICAgICdYbGFDb252JywKICAgICAgICAnWGxhRGVxdWFudGl6ZScsCiAgICAgICAgJ1hsYURvdCcsCiAgICAgICAgJ1hsYUR5bmFtaWNTbGljZScsCiAgICAgICAgJ1hsYUR5bmFtaWNVcGRhdGVTbGljZScsCiAgICAgICAgJ1hsYUVpbnN1bScsCiAgICAgICAgJ1hsYUdhdGhlcicsCiAgICAgICAgJ1hsYUhvc3RDb21wdXRlJywKICAgICAgICAnWGxhSWYnLAogICAgICAgICdYbGFLZXlWYWx1ZVNvcnQnLAogICAgICAgICdYbGFQYWQnLAogICAgICAgICdYbGFSZWN2JywKICAgICAgICAnWGxhUmVjdkZyb21Ib3N0JywKICAgICAgICAnWGxhUmVkdWNlJywKICAgICAgICAnWGxhUmVkdWNlV2luZG93JywKICAgICAgICAnWGxhUmVwbGljYUlkJywKICAgICAgICAnWGxhU2NhdHRlcicsCiAgICAgICAgJ1hsYVNlbGVjdEFuZFNjYXR0ZXInLAogICAgICAgICdYbGFTZWxmQWRqb2ludEVpZycsCiAgICAgICAgJ1hsYVNlbmQnLAogICAgICAgICdYbGFTZW5kVG9Ib3N0JywKICAgICAgICAnWGxhU2hhcmRpbmcnLAogICAgICAgICdYbGFTb3J0JywKICAgICAgICAnWGxhU3BtZEZ1bGxUb1NoYXJkU2hhcGUnLAogICAgICAgICdYbGFTcG1kU2hhcmRUb0Z1bGxTaGFwZScsCiAgICAgICAgJ1hsYVN2ZCcsCiAgICAgICAgJ1hsYVdoaWxlJywKICAgICAgICAnWGxvZzFweScsCiAgICAgICAgJ1hsb2d5JywKICAgICAgICAnWmVyb3NMaWtlJywKICAgICAgICAvLyBPcHMgYmVsb3cgYXJlIG1hbnVhbGx5IHdoaXRlbGlzdGVkIGFuZCBzaG91bGQgbm90IGJlIGV2YWx1YXRlZCBmb3IKICAgICAgICAvLyBjb21wYXRpYmlsaXR5IGZvciB2YXJpb3VzIHJlYXNvbnMuCiAgICAgICAgLy8gQ29udHJvbCBmbG93IG9wcy4KICAgICAgICAnRW50ZXInLAogICAgICAgICdFeGl0JywKICAgICAgICAnTG9vcENvbmQnLAogICAgICAgICdNZXJnZScsCiAgICAgICAgJ05leHRJdGVyYXRpb24nLAogICAgICAgICdTd2l0Y2gnLAogICAgICAgIC8vIE9wcyBiZWxvdyBhcmUgaW5zZXJ0ZWQgYnkgdGhlIGNvbXBpbGVyLgogICAgICAgICdfQXJnJywKICAgICAgICAnX0FycmF5VG9MaXN0JywKICAgICAgICAnX0Z1c2VkQmF0Y2hOb3JtRXgnLAogICAgICAgICdfTGlzdFRvQXJyYXknLAogICAgICAgICdfUGFyYWxsZWxDb25jYXRVcGRhdGUnLAogICAgICAgICdfUmVjdlRQVUVtYmVkZGluZ0FjdGl2YXRpb25zJywKICAgICAgICAnX1JlY3ZUUFVFbWJlZGRpbmdEZWR1cGxpY2F0aW9uRGF0YScsCiAgICAgICAgJ19SZXR2YWwnLAogICAgICAgICdfU2VuZFRQVUVtYmVkZGluZ0dyYWRpZW50cycsCiAgICAgICAgJ19UUFVDb21waWxlJywKICAgICAgICAnX1RQVUV4ZWN1dGUnLAogICAgICAgICdfVW5hcnlPcHNDb21wb3NpdGlvbicsCiAgICAgICAgLy8gRGlzdHJpYnV0ZWQgVFBVIG9wcy4KICAgICAgICAnVFBVQ29tcGlsYXRpb25SZXN1bHQnLAogICAgICAgICdUUFVSZXBsaWNhdGVkSW5wdXQnLAogICAgICAgICdUUFVSZXBsaWNhdGVkT3V0cHV0JywKICAgICAgICAnVFBVUmVwbGljYXRlTWV0YWRhdGEnLAogICAgICAgIC8vIENoZWNrcG9pbnRpbmcgb3BzLgogICAgICAgICdNZXJnZVYyQ2hlY2twb2ludHMnLAogICAgICAgICdSZXN0b3JlVjInLAogICAgICAgICdTYXZlVjInLAogICAgICAgIC8vIE1pc2NlbGxhbmVvdXMgQ1BVIG9wcy4KICAgICAgICAnQWJvcnQnLAogICAgICAgICdBc3NlcnQnLAogICAgICAgICdBc3NpZ24nLAogICAgICAgICdQbGFjZWhvbGRlcicsCiAgICAgICAgJ1BsYWNlaG9sZGVyVjInLAogICAgICAgICdTaGFyZGVkRmlsZW5hbWUnLAogICAgICAgICdTdHJpbmdKb2luJywKICAgICAgICAnVmFyaWFibGUnLAogICAgICAgICdWYXJpYWJsZVYyJywKICAgICAgICAnVmFySGFuZGxlT3AnLAogICAgICAgIC8vIFN1bW1hcnkgb3BzLgogICAgICAgICdBdWRpb1N1bW1hcnknLAogICAgICAgICdBdWRpb1N1bW1hcnlWMicsCiAgICAgICAgJ0RlYnVnTnVtZXJpY1N1bW1hcnknLAogICAgICAgICdIaXN0b2dyYW1TdW1tYXJ5JywKICAgICAgICAnSW1hZ2VTdW1tYXJ5JywKICAgICAgICAnTWVyZ2VTdW1tYXJ5JywKICAgICAgICAnU2NhbGFyU3VtbWFyeScsCiAgICAgICAgJ1N0YXRzQWdncmVnYXRvclN1bW1hcnknLAogICAgXTsKICAgIGZ1bmN0aW9uIGNoZWNrT3BzRm9yQ29tcGF0aWJpbGl0eShncmFwaCwgcHJvdmlkZXIpIHsKICAgICAgICBpZiAocHJvdmlkZXIgPT09IG51bGwpIHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdDb21wYXRpYmlsaXR5IHByb3ZpZGVyIHJlcXVpcmVkLCBidXQgZ290OiAnICsgcHJvdmlkZXIpOwogICAgICAgIH0KICAgICAgICBsb2Rhc2guZWFjaChncmFwaC5ub2RlcywgKG5vZGUpID0+IHsKICAgICAgICAgICAgbm9kZS5jb21wYXRpYmxlID0gcHJvdmlkZXIub3BWYWxpZChub2RlKTsKICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZS5pbkVtYmVkZGluZ3MsIChub2RlKSA9PiB7CiAgICAgICAgICAgICAgICBub2RlLmNvbXBhdGlibGUgPSBwcm92aWRlci5vcFZhbGlkKG5vZGUpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgbG9kYXNoLmVhY2gobm9kZS5vdXRFbWJlZGRpbmdzLCAobm9kZSkgPT4gewogICAgICAgICAgICAgICAgbm9kZS5jb21wYXRpYmxlID0gcHJvdmlkZXIub3BWYWxpZChub2RlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfSk7CiAgICB9CgogICAgZnVuY3Rpb24gcGFyc2VWYWx1ZSh2YWx1ZSkgewogICAgICAgIGlmICh2YWx1ZSA9PT0gJ3RydWUnKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgIH0KICAgICAgICBpZiAodmFsdWUgPT09ICdmYWxzZScpIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KICAgICAgICBsZXQgZmlyc3RDaGFyID0gdmFsdWVbMF07CiAgICAgICAgaWYgKGZpcnN0Q2hhciA9PT0gJyInKSB7CiAgICAgICAgICAgIHJldHVybiB2YWx1ZS5zdWJzdHJpbmcoMSwgdmFsdWUubGVuZ3RoIC0gMSk7CiAgICAgICAgfQogICAgICAgIGxldCBudW0gPSBwYXJzZUZsb2F0KHZhbHVlKTsKICAgICAgICByZXR1cm4gaXNOYU4obnVtKSA/IHZhbHVlIDogbnVtOwogICAgfQogICAgLyoqCiAgICAgKiBGZXRjaGVzIGEgdGV4dCBmaWxlIGFuZCByZXR1cm5zIGEgcHJvbWlzZSBvZiB0aGUgcmVzdWx0LgogICAgICovCiAgICBmdW5jdGlvbiBmZXRjaFBiVHh0KGZpbGVwYXRoKSB7CiAgICAgICAgcmV0dXJuIG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHsKICAgICAgICAgICAgZmV0Y2goZmlsZXBhdGgpLnRoZW4oKHJlcykgPT4gewogICAgICAgICAgICAgICAgLy8gRmV0Y2ggZG9lcyBub3QgcmVqZWN0IGZvciA0MDArLgogICAgICAgICAgICAgICAgaWYgKHJlcy5vaykgewogICAgICAgICAgICAgICAgICAgIHJlcy5hcnJheUJ1ZmZlcigpLnRoZW4ocmVzb2x2ZSwgcmVqZWN0KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgIHJlcy50ZXh0KCkudGhlbihyZWplY3QsIHJlamVjdCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgIH0pOwogICAgfQogICAgLyoqCiAgICAgKiBGZXRjaGVzIHRoZSBtZXRhZGF0YSBmaWxlLCBwYXJzZXMgaXQgYW5kIHJldHVybnMgYSBwcm9taXNlIG9mIHRoZSByZXN1bHQuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZldGNoQW5kUGFyc2VNZXRhZGF0YShwYXRoLCB0cmFja2VyKSB7CiAgICAgICAgcmV0dXJuIHJ1blRhc2soJ1JlYWRpbmcgbWV0YWRhdGEgcGJ0eHQnLCA0MCwgKCkgPT4gewogICAgICAgICAgICBpZiAocGF0aCA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gUHJvbWlzZS5yZXNvbHZlKG51bGwpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBmZXRjaFBiVHh0KHBhdGgpOwogICAgICAgIH0sIHRyYWNrZXIpCiAgICAgICAgICAgIC50aGVuKChhcnJheUJ1ZmZlcikgPT4gewogICAgICAgICAgICByZXR1cm4gcnVuQXN5bmNQcm9taXNlVGFzaygnUGFyc2luZyBtZXRhZGF0YS5wYnR4dCcsIDYwLCAoKSA9PiB7CiAgICAgICAgICAgICAgICByZXR1cm4gYXJyYXlCdWZmZXIgIT0gbnVsbAogICAgICAgICAgICAgICAgICAgID8gcGFyc2VTdGF0c1BiVHh0KGFycmF5QnVmZmVyKQogICAgICAgICAgICAgICAgICAgIDogUHJvbWlzZS5yZXNvbHZlKG51bGwpOwogICAgICAgICAgICB9LCB0cmFja2VyKTsKICAgICAgICB9KTsKICAgIH0KICAgIC8qKgogICAgICogRmV0Y2hlcyB0aGUgZ3JhcGggZmlsZSwgcGFyc2VzIGl0IGFuZCByZXR1cm5zIGEgcHJvbWlzZSBvZiB0aGUgcmVzdWx0LiBUaGUKICAgICAqIHJlc3VsdCB3aWxsIGJlIHVuZGVmaW5lZCBpZiB0aGUgZ3JhcGggaXMgZW1wdHkuCiAgICAgKi8KICAgIGZ1bmN0aW9uIGZldGNoQW5kUGFyc2VHcmFwaERhdGEocGF0aCwgcGJUeHRGaWxlLCB0cmFja2VyKSB7CiAgICAgICAgcmV0dXJuIHJ1bkFzeW5jUHJvbWlzZVRhc2soJ1JlYWRpbmcgZ3JhcGggcGJ0eHQnLCA0MCwgKCkgPT4gewogICAgICAgICAgICBpZiAocGJUeHRGaWxlKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24gKHJlc29sdmUsIHJlamVjdCkgewogICAgICAgICAgICAgICAgICAgIGxldCBmaWxlUmVhZGVyID0gbmV3IEZpbGVSZWFkZXIoKTsKICAgICAgICAgICAgICAgICAgICBmaWxlUmVhZGVyLm9ubG9hZCA9ICgpID0+IHJlc29sdmUoZmlsZVJlYWRlci5yZXN1bHQpOwogICAgICAgICAgICAgICAgICAgIGZpbGVSZWFkZXIub25lcnJvciA9ICgpID0+IHJlamVjdChmaWxlUmVhZGVyLmVycm9yKTsKICAgICAgICAgICAgICAgICAgICBmaWxlUmVhZGVyLnJlYWRBc0FycmF5QnVmZmVyKHBiVHh0RmlsZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIHJldHVybiBmZXRjaFBiVHh0KHBhdGgpOwogICAgICAgICAgICB9CiAgICAgICAgfSwgdHJhY2tlcikKICAgICAgICAgICAgLnRoZW4oKGFycmF5QnVmZmVyKSA9PiB7CiAgICAgICAgICAgIHJldHVybiBydW5Bc3luY1Byb21pc2VUYXNrKCdQYXJzaW5nIGdyYXBoLnBidHh0JywgNjAsICgpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBwYXJzZUdyYXBoUGJUeHQoYXJyYXlCdWZmZXIpOwogICAgICAgICAgICB9LCB0cmFja2VyKTsKICAgICAgICB9KTsKICAgIH0KICAgIC8qKgogICAgICogUGFyc2UgYSBmaWxlIG9iamVjdCBpbiBhIHN0cmVhbWluZyBmYXNoaW9uIGxpbmUgYnkgbGluZSAob3IgY3VzdG9tIGRlbGltKS4KICAgICAqIENhbiBoYW5kbGUgdmVyeSBsYXJnZSBmaWxlcy4KICAgICAqIEBwYXJhbSBpbnB1dCBUaGUgZmlsZSBvYmplY3QgYXMgYW4gYXJyYXkgYnVmZmVyLgogICAgICogQHBhcmFtIGNhbGxiYWNrIFRoZSBjYWxsYmFjayBjYWxsZWQgb24gZWFjaCBsaW5lCiAgICAgKiBAcGFyYW0gY2h1bmtTaXplIFRoZSBzaXplIG9mIGVhY2ggcmVhZCBjaHVuay4gKG9wdGlvbmFsKQogICAgICogQHBhcmFtIGRlbGltIFRoZSBkZWxpbWl0ZXIgdXNlZCB0byBzcGxpdCBhIGxpbmUuIChvcHRpb25hbCkKICAgICAqIEByZXR1cm5zIFByb21pc2UgdGhhdCByZXNvbHZlcyB3aXRoIHRydWUgd2hlbiBpdCBpcyBmaW5pc2hlZC4KICAgICAqLwogICAgZnVuY3Rpb24gc3RyZWFtUGFyc2UoYXJyYXlCdWZmZXIsIGNhbGxiYWNrLCBjaHVua1NpemUgPSAxMDAwMDAwLCBkZWxpbSA9ICdcbicpIHsKICAgICAgICByZXR1cm4gbmV3IFByb21pc2UoZnVuY3Rpb24gKHJlc29sdmUsIHJlamVjdCkgewogICAgICAgICAgICBmdW5jdGlvbiByZWFkQ2h1bmsob2xkRGF0YSwgbmV3RGF0YSwgb2Zmc2V0KSB7CiAgICAgICAgICAgICAgICBjb25zdCBkb25lUmVhZGluZyA9IG9mZnNldCA+PSBhcnJheUJ1ZmZlci5ieXRlTGVuZ3RoOwogICAgICAgICAgICAgICAgY29uc3QgcGFydHMgPSBuZXdEYXRhLnNwbGl0KGRlbGltKTsKICAgICAgICAgICAgICAgIHBhcnRzWzBdID0gb2xkRGF0YSArIHBhcnRzWzBdOwogICAgICAgICAgICAgICAgLy8gVGhlIGxhc3QgcGFydCBtYXkgYmUgcGFydCBvZiBhIGxvbmdlciBzdHJpbmcgdGhhdCBnb3QgY3V0IG9mZgogICAgICAgICAgICAgICAgLy8gZHVlIHRvIHRoZSBjaHVua2luZy4KICAgICAgICAgICAgICAgIGNvbnN0IHJlbWFpbmRlciA9IGRvbmVSZWFkaW5nID8gJycgOiBwYXJ0cy5wb3AoKTsKICAgICAgICAgICAgICAgIGZvciAobGV0IHBhcnQgb2YgcGFydHMpIHsKICAgICAgICAgICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgICAgICAgICAgICBjYWxsYmFjayhwYXJ0KTsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgY2F0Y2ggKGUpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmVqZWN0KGUpOwogICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGRvbmVSZWFkaW5nKSB7CiAgICAgICAgICAgICAgICAgICAgcmVzb2x2ZSh0cnVlKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb25zdCBuZXh0Q2h1bmsgPSBuZXcgQmxvYihbCiAgICAgICAgICAgICAgICAgICAgYXJyYXlCdWZmZXIuc2xpY2Uob2Zmc2V0LCBvZmZzZXQgKyBjaHVua1NpemUpLAogICAgICAgICAgICAgICAgXSk7CiAgICAgICAgICAgICAgICBjb25zdCBmaWxlID0gbmV3IEZpbGVSZWFkZXIoKTsKICAgICAgICAgICAgICAgIGZpbGUub25sb2FkID0gZnVuY3Rpb24gKGUpIHsKICAgICAgICAgICAgICAgICAgICByZWFkQ2h1bmsocmVtYWluZGVyLCBlLnRhcmdldC5yZXN1bHQsIG9mZnNldCArIGNodW5rU2l6ZSk7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICAgICAgZmlsZS5yZWFkQXNUZXh0KG5leHRDaHVuayk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmVhZENodW5rKCcnLCAnJywgMCk7CiAgICAgICAgfSk7CiAgICB9CiAgICAvKioKICAgICAqIFNpbmNlIHByb3RvLXR4dCBkb2Vzbid0IGV4cGxpY2l0bHkgc2F5IHdoZXRoZXIgYW4gYXR0cmlidXRlIGlzIHJlcGVhdGVkCiAgICAgKiAoYW4gYXJyYXkpIG9yIG5vdCwgd2Uga2VlcCBhIGhhcmQtY29kZWQgbGlzdCBvZiBhdHRyaWJ1dGVzIHRoYXQgYXJlIGtub3duCiAgICAgKiB0byBiZSByZXBlYXRlZC4gVGhpcyBsaXN0IGlzIHVzZWQgaW4gcGFyc2luZyB0aW1lIHRvIGNvbnZlcnQgcmVwZWF0ZWQKICAgICAqIGF0dHJpYnV0ZXMgaW50byBhcnJheXMgZXZlbiB3aGVuIHRoZSBhdHRyaWJ1dGUgb25seSBzaG93cyB1cCBvbmNlIGluIHRoZQogICAgICogb2JqZWN0LgogICAgICogUmVwZWF0ZWQgZmllbGRzIGhhdmUgdG8gYmUgaW4gc3luYyB3aXRoIGdyYXBoLnByb3RvIGFuZCBhbGwgb2YgaXRzCiAgICAgKiBkZXBlbmRlbmNpZXMuCiAgICAgKiBTZWUgaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yZmxvdy9ibG9iL21hc3Rlci90ZW5zb3JmbG93L2NvcmUvZnJhbWV3b3JrL2dyYXBoLnByb3RvCiAgICAgKi8KICAgIGNvbnN0IEdSQVBIX1JFUEVBVEVEX0ZJRUxEUyA9IHsKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbic6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYnOiB0cnVlLAogICAgICAgICdsaWJyYXJ5LmZ1bmN0aW9uLm5vZGVfZGVmLmlucHV0JzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5ub2RlX2RlZi5hdHRyJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5ub2RlX2RlZi5hdHRyLnZhbHVlLmxpc3QuYic6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYuYXR0ci52YWx1ZS5saXN0LmYnOiB0cnVlLAogICAgICAgICdsaWJyYXJ5LmZ1bmN0aW9uLm5vZGVfZGVmLmF0dHIudmFsdWUubGlzdC5mdW5jJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5ub2RlX2RlZi5hdHRyLnZhbHVlLmxpc3QuaSc6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYuYXR0ci52YWx1ZS5saXN0LnMnOiB0cnVlLAogICAgICAgICdsaWJyYXJ5LmZ1bmN0aW9uLm5vZGVfZGVmLmF0dHIudmFsdWUubGlzdC5zaGFwZSc6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYuYXR0ci52YWx1ZS5saXN0LnNoYXBlLmRpbSc6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYuYXR0ci52YWx1ZS5saXN0LnRlbnNvcic6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkuZnVuY3Rpb24ubm9kZV9kZWYuYXR0ci52YWx1ZS5saXN0LnR5cGUnOiB0cnVlLAogICAgICAgICdsaWJyYXJ5LmZ1bmN0aW9uLm5vZGVfZGVmLmF0dHIudmFsdWUuc2hhcGUuZGltJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5ub2RlX2RlZi5hdHRyLnZhbHVlLnRlbnNvci5zdHJpbmdfdmFsJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5ub2RlX2RlZi5hdHRyLnZhbHVlLnRlbnNvci50ZW5zb3Jfc2hhcGUuZGltJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5zaWduYXR1cmUuaW5wdXRfYXJnJzogdHJ1ZSwKICAgICAgICAnbGlicmFyeS5mdW5jdGlvbi5zaWduYXR1cmUub3V0cHV0X2FyZyc6IHRydWUsCiAgICAgICAgJ2xpYnJhcnkudmVyc2lvbnMnOiB0cnVlLAogICAgICAgIG5vZGU6IHRydWUsCiAgICAgICAgJ25vZGUuaW5wdXQnOiB0cnVlLAogICAgICAgICdub2RlLmF0dHInOiB0cnVlLAogICAgICAgICdub2RlLmF0dHIudmFsdWUubGlzdC5iJzogdHJ1ZSwKICAgICAgICAnbm9kZS5hdHRyLnZhbHVlLmxpc3QuZic6IHRydWUsCiAgICAgICAgJ25vZGUuYXR0ci52YWx1ZS5saXN0LmZ1bmMnOiB0cnVlLAogICAgICAgICdub2RlLmF0dHIudmFsdWUubGlzdC5pJzogdHJ1ZSwKICAgICAgICAnbm9kZS5hdHRyLnZhbHVlLmxpc3Qucyc6IHRydWUsCiAgICAgICAgJ25vZGUuYXR0ci52YWx1ZS5saXN0LnNoYXBlJzogdHJ1ZSwKICAgICAgICAnbm9kZS5hdHRyLnZhbHVlLmxpc3Quc2hhcGUuZGltJzogdHJ1ZSwKICAgICAgICAnbm9kZS5hdHRyLnZhbHVlLmxpc3QudGVuc29yJzogdHJ1ZSwKICAgICAgICAnbm9kZS5hdHRyLnZhbHVlLmxpc3QudHlwZSc6IHRydWUsCiAgICAgICAgJ25vZGUuYXR0ci52YWx1ZS5zaGFwZS5kaW0nOiB0cnVlLAogICAgICAgICdub2RlLmF0dHIudmFsdWUudGVuc29yLnN0cmluZ192YWwnOiB0cnVlLAogICAgICAgICdub2RlLmF0dHIudmFsdWUudGVuc29yLnRlbnNvcl9zaGFwZS5kaW0nOiB0cnVlLAogICAgfTsKICAgIGNvbnN0IE1FVEFEQVRBX1JFUEVBVEVEX0ZJRUxEUyA9IHsKICAgICAgICAnc3RlcF9zdGF0cy5kZXZfc3RhdHMnOiB0cnVlLAogICAgICAgICdzdGVwX3N0YXRzLmRldl9zdGF0cy5ub2RlX3N0YXRzJzogdHJ1ZSwKICAgICAgICAnc3RlcF9zdGF0cy5kZXZfc3RhdHMubm9kZV9zdGF0cy5vdXRwdXQnOiB0cnVlLAogICAgICAgICdzdGVwX3N0YXRzLmRldl9zdGF0cy5ub2RlX3N0YXRzLm1lbW9yeSc6IHRydWUsCiAgICAgICAgJ3N0ZXBfc3RhdHMuZGV2X3N0YXRzLm5vZGVfc3RhdHMub3V0cHV0LnRlbnNvcl9kZXNjcmlwdGlvbi5zaGFwZS5kaW0nOiB0cnVlLAogICAgfTsKICAgIC8qKgogICAgICogUGFyc2VzIGFuIEFycmF5QnVmZmVyIG9mIGEgcHJvdG8gdHh0IGZpbGUgaW50byBhIHJhdyBHcmFwaCBvYmplY3QuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBhcnNlR3JhcGhQYlR4dChpbnB1dCkgewogICAgICAgIHJldHVybiBwYXJzZVBidHh0RmlsZShpbnB1dCwgR1JBUEhfUkVQRUFURURfRklFTERTKTsKICAgIH0KICAgIC8qKgogICAgICogUGFyc2VzIGFuIEFycmF5QnVmZmVyIG9mIGEgcHJvdG8gdHh0IGZpbGUgaW50byBhIFN0ZXBTdGF0cyBvYmplY3QuCiAgICAgKi8KICAgIGZ1bmN0aW9uIHBhcnNlU3RhdHNQYlR4dChpbnB1dCkgewogICAgICAgIHJldHVybiBwYXJzZVBidHh0RmlsZShpbnB1dCwgTUVUQURBVEFfUkVQRUFURURfRklFTERTKS50aGVuKChvYmopID0+IG9ialsnc3RlcF9zdGF0cyddKTsKICAgIH0KICAgIC8qKgogICAgICogUGFyc2VzIGEgQXJyYXlCdWZmZXIgb2YgYSBwcm90byB0eHQgZmlsZSBpbnRvIGphdmFzY3JpcHQgb2JqZWN0LgogICAgICoKICAgICAqIEBwYXJhbSBpbnB1dCBUaGUgQXJyYXlCdWZmZXIgb3IgZmlsZSBvYmplY3QgaW1wbGVtZW50aW5nIHNsaWNlLgogICAgICogQHBhcmFtIHJlcGVhdGVkRmllbGRzIE1hcCAoU2V0KSBvZiBhbGwgdGhlIHJlcGVhdGVkIGZpZWxkcywgc2luY2UgeW91IGNhbid0CiAgICAgKiAgIHRlbGwgZGlyZWN0bHkgZnJvbSB0aGUgcGJ0eHQgaWYgYSBmaWVsZCBpcyByZXBlYXRlZCBvciBub3QuCiAgICAgKiBAcmV0dXJucyBUaGUgcGFyc2VkIG9iamVjdC4KICAgICAqLwogICAgZnVuY3Rpb24gcGFyc2VQYnR4dEZpbGUoaW5wdXQsIHJlcGVhdGVkRmllbGRzKSB7CiAgICAgICAgbGV0IG91dHB1dCA9IHt9OwogICAgICAgIGxldCBzdGFjayA9IFtdOwogICAgICAgIGxldCBwYXRoID0gW107CiAgICAgICAgbGV0IGN1cnJlbnQgPSBvdXRwdXQ7CiAgICAgICAgZnVuY3Rpb24gc3BsaXROYW1lQW5kVmFsdWVJbkF0dHJpYnV0ZShsaW5lKSB7CiAgICAgICAgICAgIGxldCBjb2xvbkluZGV4ID0gbGluZS5pbmRleE9mKCc6Jyk7CiAgICAgICAgICAgIGxldCBuYW1lID0gbGluZS5zdWJzdHJpbmcoMCwgY29sb25JbmRleCkudHJpbSgpOwogICAgICAgICAgICBsZXQgdmFsdWUgPSBwYXJzZVZhbHVlKGxpbmUuc3Vic3RyaW5nKGNvbG9uSW5kZXggKyAyKS50cmltKCkpOwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgbmFtZTogbmFtZSwKICAgICAgICAgICAgICAgIHZhbHVlOiB2YWx1ZSwKICAgICAgICAgICAgfTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQWRkcyBhIHZhbHVlLCBnaXZlbiB0aGUgYXR0cmlidXRlIG5hbWUgYW5kIHRoZSBob3N0IG9iamVjdC4gSWYgdGhlCiAgICAgICAgICogYXR0cmlidXRlIGFscmVhZHkgZXhpc3RzLCBidXQgaXMgbm90IGFuIGFycmF5LCBpdCB3aWxsIGNvbnZlcnQgaXQgdG8gYW4KICAgICAgICAgKiBhcnJheSBvZiB2YWx1ZXMuCiAgICAgICAgICoKICAgICAgICAgKiBAcGFyYW0gb2JqIFRoZSBob3N0IG9iamVjdCB0aGF0IGhvbGRzIHRoZSBhdHRyaWJ1dGUuCiAgICAgICAgICogQHBhcmFtIG5hbWUgVGhlIGF0dHJpYnV0ZSBuYW1lIChrZXkpLgogICAgICAgICAqIEBwYXJhbSB2YWx1ZSBUaGUgYXR0cmlidXRlIHZhbHVlLgogICAgICAgICAqIEBwYXJhbSBwYXRoIEEgcGF0aCB0aGF0IGlkZW50aWZpZXMgdGhlIGF0dHJpYnV0ZS4gVXNlZCB0byBjaGVjayBpZgogICAgICAgICAqICAgICBhbiBhdHRyaWJ1dGUgaXMgYW4gYXJyYXkgb3Igbm90LgogICAgICAgICAqLwogICAgICAgIGZ1bmN0aW9uIGFkZEF0dHJpYnV0ZShvYmosIG5hbWUsIHZhbHVlLCBwYXRoKSB7CiAgICAgICAgICAgIC8vIFdlIHRyZWF0ICdub2RlJyBzcGVjaWFsbHkgc2luY2UgaXQgaXMgZG9uZSBzbyBvZnRlbi4KICAgICAgICAgICAgbGV0IGV4aXN0aW5nVmFsdWUgPSBvYmpbbmFtZV07CiAgICAgICAgICAgIGlmIChleGlzdGluZ1ZhbHVlID09IG51bGwpIHsKICAgICAgICAgICAgICAgIG9ialtuYW1lXSA9IHBhdGguam9pbignLicpIGluIHJlcGVhdGVkRmllbGRzID8gW3ZhbHVlXSA6IHZhbHVlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKEFycmF5LmlzQXJyYXkoZXhpc3RpbmdWYWx1ZSkpIHsKICAgICAgICAgICAgICAgIGV4aXN0aW5nVmFsdWUucHVzaCh2YWx1ZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBvYmpbbmFtZV0gPSBbZXhpc3RpbmdWYWx1ZSwgdmFsdWVdOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIC8vIFJ1biB0aHJvdWdoIHRoZSBmaWxlIGEgbGluZSBhdCBhIHRpbWUuCiAgICAgICAgcmV0dXJuIHN0cmVhbVBhcnNlKGlucHV0LCBmdW5jdGlvbiAobGluZSkgewogICAgICAgICAgICBpZiAoIWxpbmUpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBsaW5lID0gbGluZS50cmltKCk7CiAgICAgICAgICAgIHN3aXRjaCAobGluZVtsaW5lLmxlbmd0aCAtIDFdKSB7CiAgICAgICAgICAgICAgICBjYXNlICd7JzogLy8gY3JlYXRlIG5ldyBvYmplY3QKICAgICAgICAgICAgICAgICAgICBsZXQgbmFtZSA9IGxpbmUuc3Vic3RyaW5nKDAsIGxpbmUubGVuZ3RoIC0gMikudHJpbSgpOwogICAgICAgICAgICAgICAgICAgIGxldCBuZXdWYWx1ZSA9IHt9OwogICAgICAgICAgICAgICAgICAgIHN0YWNrLnB1c2goY3VycmVudCk7CiAgICAgICAgICAgICAgICAgICAgcGF0aC5wdXNoKG5hbWUpOwogICAgICAgICAgICAgICAgICAgIGFkZEF0dHJpYnV0ZShjdXJyZW50LCBuYW1lLCBuZXdWYWx1ZSwgcGF0aCk7CiAgICAgICAgICAgICAgICAgICAgY3VycmVudCA9IG5ld1ZhbHVlOwogICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgY2FzZSAnfSc6CiAgICAgICAgICAgICAgICAgICAgY3VycmVudCA9IHN0YWNrLnBvcCgpOwogICAgICAgICAgICAgICAgICAgIHBhdGgucG9wKCk7CiAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIGxldCB4ID0gc3BsaXROYW1lQW5kVmFsdWVJbkF0dHJpYnV0ZShsaW5lKTsKICAgICAgICAgICAgICAgICAgICBhZGRBdHRyaWJ1dGUoY3VycmVudCwgeC5uYW1lLCB4LnZhbHVlLCBwYXRoLmNvbmNhdCh4Lm5hbWUpKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgIH0pLnRoZW4oZnVuY3Rpb24gKCkgewogICAgICAgICAgICByZXR1cm4gb3V0cHV0OwogICAgICAgIH0pOwogICAgfQoKICAgIGZ1bmN0aW9uIGZldGNoQW5kQ29uc3RydWN0SGllcmFyY2hpY2FsR3JhcGgodHJhY2tlciwgcmVtb3RlUGF0aCwgcGJUeHRGaWxlLCBjb21wYXRpYmlsaXR5UHJvdmlkZXIgPSBuZXcgVHB1Q29tcGF0aWJpbGl0eVByb3ZpZGVyKCksIGhpZXJhcmNoeVBhcmFtcyA9IERlZmF1bHRIaWVyYXJjaHlQYXJhbXMpIHsKICAgICAgICBjb25zdCBkYXRhVHJhY2tlciA9IGdldFN1YnRhc2tUcmFja2VyKHRyYWNrZXIsIDMwLCAnRGF0YScpOwogICAgICAgIGNvbnN0IGdyYXBoVHJhY2tlciA9IGdldFN1YnRhc2tUcmFja2VyKHRyYWNrZXIsIDIwLCAnR3JhcGgnKTsKICAgICAgICBjb25zdCBoaWVyYXJjaHlUcmFja2VyID0gZ2V0U3VidGFza1RyYWNrZXIodHJhY2tlciwgNTAsICdOYW1lc3BhY2UgaGllcmFyY2h5Jyk7CiAgICAgICAgcmV0dXJuIGZldGNoQW5kUGFyc2VHcmFwaERhdGEocmVtb3RlUGF0aCwgcGJUeHRGaWxlLCBkYXRhVHJhY2tlcikKICAgICAgICAgICAgLnRoZW4oZnVuY3Rpb24gKGdyYXBoKSB7CiAgICAgICAgICAgIGlmICghZ3JhcGgubm9kZSkgewogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdUaGUgZ3JhcGggaXMgZW1wdHkuIFRoaXMgY2FuIGhhcHBlbiB3aGVuICcgKwogICAgICAgICAgICAgICAgICAgICdUZW5zb3JGbG93IGNvdWxkIG5vdCB0cmFjZSBhbnkgZ3JhcGguIFBsZWFzZSByZWZlciB0byAnICsKICAgICAgICAgICAgICAgICAgICAnaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvaXNzdWVzLzE5NjEgZm9yIG1vcmUgJyArCiAgICAgICAgICAgICAgICAgICAgJ2luZm9ybWF0aW9uLicpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBidWlsZChncmFwaCwgRGVmYXVsdEJ1aWxkUGFyYW1zLCBncmFwaFRyYWNrZXIpOwogICAgICAgIH0sICgpID0+IHsKICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdNYWxmb3JtZWQgR3JhcGhEZWYuIFRoaXMgY2FuIHNvbWV0aW1lcyBiZSBjYXVzZWQgYnkgJyArCiAgICAgICAgICAgICAgICAnYSBiYWQgbmV0d29yayBjb25uZWN0aW9uIG9yIGRpZmZpY3VsdHkgcmVjb25jaWxpbmcgbXVsdGlwbGUgJyArCiAgICAgICAgICAgICAgICAnR3JhcGhEZWZzOyBmb3IgdGhlIGxhdHRlciBjYXNlLCBwbGVhc2UgcmVmZXIgdG8gJyArCiAgICAgICAgICAgICAgICAnaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvaXNzdWVzLzE5MjkuJyk7CiAgICAgICAgfSkKICAgICAgICAgICAgLnRoZW4oKGdyYXBoKSA9PiBfX2F3YWl0ZXIodGhpcywgdm9pZCAwLCB2b2lkIDAsIGZ1bmN0aW9uKiAoKSB7CiAgICAgICAgICAgIC8vIFBvcHVsYXRlIGNvbXBhdGliaWxlIGZpZWxkIG9mIE9wTm9kZSBiYXNlZCBvbiB3aGl0ZWxpc3QKICAgICAgICAgICAgY2hlY2tPcHNGb3JDb21wYXRpYmlsaXR5KGdyYXBoLCBjb21wYXRpYmlsaXR5UHJvdmlkZXIpOwogICAgICAgICAgICBjb25zdCBncmFwaEhpZXJhcmNoeSA9IHlpZWxkIGJ1aWxkJDEoZ3JhcGgsIGhpZXJhcmNoeVBhcmFtcywgaGllcmFyY2h5VHJhY2tlcik7CiAgICAgICAgICAgIHJldHVybiB7IGdyYXBoLCBncmFwaEhpZXJhcmNoeSB9OwogICAgICAgIH0pKQogICAgICAgICAgICAuY2F0Y2goKGUpID0+IHsKICAgICAgICAgICAgLy8gR2VuZXJpYyBlcnJvciBjYXRjaCwgZm9yIGVycm9ycyB0aGF0IGhhcHBlbmVkIG91dHNpZGUKICAgICAgICAgICAgLy8gYXN5bmNocm9ub3VzIHRhc2tzLgogICAgICAgICAgICBjb25zdCBtc2cgPSBgR3JhcGggdmlzdWFsaXphdGlvbiBmYWlsZWQuXG5cbiR7ZX1gOwogICAgICAgICAgICB0cmFja2VyLnJlcG9ydEVycm9yKG1zZywgZSk7CiAgICAgICAgICAgIC8vIERvbid0IHN3YWxsb3cgdGhlIGVycm9yLgogICAgICAgICAgICB0aHJvdyBlOwogICAgICAgIH0pOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBEYXRhIGxvYWRlciBmb3IgdGYtZ3JhcGgtZGFzaGJvYXJkLgogICAgICoKICAgICAqIFRoZSBsb2FkZXIgbG9hZHMgb3AgZ3JhcGgsIGNvbmNlcHR1YWwgZ3JhcGhzLCBhbmQgUnVuTWV0YWRhdGEgYXNzb2NpYXRlZCB3aXRoCiAgICAgKiBhbiBvcCBncmFwaCB3aGljaCBpcyB0aGUgbWFqb3IgZGlmZmVyZW5jZSBmcm9tIHRoZSB0Zi1ncmFwaC1sb2FkZXIgd2hpY2ggaXMKICAgICAqIG9ubHkgY2FwYWJsZSBvZiBsb2FkaW5nIGFuIG9wIGdyYXBoLiBBbm90aGVyIGRpZmZlcmVuY2UgaXMgdGhhdCB0aGUgbG9hZGVyCiAgICAgKiB0YWtlcyBgc2VsZWN0aW9uYCBmcm9tIHRoZSB0Zi1ncmFwaC1jb250cm9scyBhcyBhbiBpbnB1dCBhcyBvcHBvc2VkIHRvIFVSTAogICAgICogcGF0aCBvZiBhbiBkYXRhIGVuZHBvaW50LgogICAgICovCiAgICBsZXQgVGZHcmFwaERhc2hib2FyZExvYWRlciA9IGNsYXNzIFRmR3JhcGhEYXNoYm9hcmRMb2FkZXIgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5jb21wYXRpYmlsaXR5UHJvdmlkZXIgPSBuZXcgVHB1Q29tcGF0aWJpbGl0eVByb3ZpZGVyKCk7CiAgICAgICAgICAgIHRoaXMuaGllcmFyY2h5UGFyYW1zID0gRGVmYXVsdEhpZXJhcmNoeVBhcmFtczsKICAgICAgICAgICAgdGhpcy5fdGVtcGxhdGUgPSBudWxsOwogICAgICAgIH0KICAgICAgICBfc2VsZWN0aW9uQ2hhbmdlZCgpIHsKICAgICAgICAgICAgLy8gc2VsZWN0aW9uIGNhbiBjaGFuZ2UgYSBsb3Qgd2l0aGluIGEgbWljcm90YXNrLgogICAgICAgICAgICAvLyBEb24ndCBmZXRjaCB0b28gbXVjaCB0b28gZmFzdCBhbmQgaW50cm9kdWNlIHJhY2UgY29uZGl0aW9uLgogICAgICAgICAgICB0aGlzLmRlYm91bmNlKCdzZWxlY3Rpb25jaGFuZ2UnLCAoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9sb2FkKHRoaXMuc2VsZWN0aW9uKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9sb2FkKHNlbGVjdGlvbikgewogICAgICAgICAgICBjb25zdCB7IHJ1biwgdGFnLCB0eXBlOiBzZWxlY3Rpb25UeXBlIH0gPSBzZWxlY3Rpb247CiAgICAgICAgICAgIHN3aXRjaCAoc2VsZWN0aW9uVHlwZSkgewogICAgICAgICAgICAgICAgY2FzZSBTZWxlY3Rpb25UeXBlLk9QX0dSQVBIOgogICAgICAgICAgICAgICAgY2FzZSBTZWxlY3Rpb25UeXBlLkNPTkNFUFRVQUxfR1JBUEg6IHsKICAgICAgICAgICAgICAgICAgICAvLyBDbGVhciBzdGF0cyBhYm91dCB0aGUgcHJldmlvdXMgZ3JhcGguCiAgICAgICAgICAgICAgICAgICAgKGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fc2V0T3V0U3RhdHMobnVsbCk7CiAgICAgICAgICAgICAgICAgICAgfS5iaW5kKHRoaXMpKCkpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHBhcmFtcyA9IG5ldyBVUkxTZWFyY2hQYXJhbXMoKTsKICAgICAgICAgICAgICAgICAgICBwYXJhbXMuc2V0KCdydW4nLCBydW4pOwogICAgICAgICAgICAgICAgICAgIHBhcmFtcy5zZXQoJ2NvbmNlcHR1YWwnLCBTdHJpbmcoc2VsZWN0aW9uVHlwZSA9PT0gU2VsZWN0aW9uVHlwZS5DT05DRVBUVUFMX0dSQVBIKSk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHRhZykKICAgICAgICAgICAgICAgICAgICAgICAgcGFyYW1zLnNldCgndGFnJywgdGFnKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBncmFwaFBhdGggPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnZ3JhcGhzJywgJy9ncmFwaCcsIHBhcmFtcyk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2ZldGNoQW5kQ29uc3RydWN0SGllcmFyY2hpY2FsR3JhcGgoZ3JhcGhQYXRoKS50aGVuKCgpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgdGhpcy5fZ3JhcGhSdW5UYWcgPSB7IHJ1biwgdGFnIH07CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXNlIFNlbGVjdGlvblR5cGUuUFJPRklMRTogewogICAgICAgICAgICAgICAgICAgIGNvbnN0IHsgdGFncyB9ID0gdGhpcy5kYXRhc2V0cy5maW5kKCh7IG5hbWUgfSkgPT4gbmFtZSA9PT0gcnVuKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCB0YWdNZXRhID0gdGFncy5maW5kKCh0KSA9PiB0LnRhZyA9PT0gdGFnKTsKICAgICAgICAgICAgICAgICAgICAvLyBJbiBjYXNlIGN1cnJlbnQgdGFnIG1pc3NlcyBvcEdyYXBoIGJ1dCBoYXMgcHJvZmlsZSBpbmZvcm1hdGlvbiwKICAgICAgICAgICAgICAgICAgICAvLyB3ZSBmYWxsYmFjayB0byB0aGUgdjEgYmVoYXZpb3Igb2YgZmV0Y2hpbmcgdGhlIHJ1biBncmFwaC4KICAgICAgICAgICAgICAgICAgICBjb25zdCByZXF1aXJlZE9wR3JhcGhUYWcgPSB0YWdNZXRhLm9wR3JhcGggPyB0YWcgOiBudWxsOwogICAgICAgICAgICAgICAgICAgIGNvbnNvbGUuYXNzZXJ0KHRhZ3MuZmluZCgodCkgPT4gdC50YWcgPT09IHJlcXVpcmVkT3BHcmFwaFRhZyksIGBSZXF1aXJlZCB0YWcgKCR7cmVxdWlyZWRPcEdyYXBoVGFnfSkgaXMgbWlzc2luZy5gKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBzaG91bGRGZXRjaEdyYXBoID0gIXRoaXMuX2dyYXBoUnVuVGFnIHx8CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2dyYXBoUnVuVGFnLnJ1biAhPT0gcnVuIHx8CiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuX2dyYXBoUnVuVGFnLnRhZyAhPT0gcmVxdWlyZWRPcEdyYXBoVGFnOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IG1heWJlRmV0Y2hHcmFwaFByb21pc2UgPSBzaG91bGRGZXRjaEdyYXBoCiAgICAgICAgICAgICAgICAgICAgICAgID8gdGhpcy5fbG9hZCh7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBydW4sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB0YWc6IHJlcXVpcmVkT3BHcmFwaFRhZywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHR5cGU6IFNlbGVjdGlvblR5cGUuT1BfR1JBUEgsCiAgICAgICAgICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgICAgIDogUHJvbWlzZS5yZXNvbHZlKCk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcygpOwogICAgICAgICAgICAgICAgICAgIHBhcmFtcy5zZXQoJ3RhZycsIHRhZyk7CiAgICAgICAgICAgICAgICAgICAgcGFyYW1zLnNldCgncnVuJywgcnVuKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBtZXRhZGF0YVBhdGggPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnZ3JhcGhzJywgJy9ydW5fbWV0YWRhdGEnLCBwYXJhbXMpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBtYXliZUZldGNoR3JhcGhQcm9taXNlLnRoZW4oKCkgPT4gdGhpcy5fcmVhZEFuZFBhcnNlTWV0YWRhdGEobWV0YWRhdGFQYXRoKSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBkZWZhdWx0OgogICAgICAgICAgICAgICAgICAgIHJldHVybiBQcm9taXNlLnJlamVjdChuZXcgRXJyb3IoYFVua25vd24gc2VsZWN0aW9uIHR5cGU6ICR7c2VsZWN0aW9uVHlwZX1gKSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgX3JlYWRBbmRQYXJzZU1ldGFkYXRhKHBhdGgpIHsKICAgICAgICAgICAgLy8gUmVzZXQgdGhlIHByb2dyZXNzIGJhciB0byAwLgogICAgICAgICAgICB0aGlzLnNldCgncHJvZ3Jlc3MnLCB7CiAgICAgICAgICAgICAgICB2YWx1ZTogMCwKICAgICAgICAgICAgICAgIG1zZzogJycsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgdHJhY2tlciA9IGdldFRyYWNrZXIodGhpcyk7CiAgICAgICAgICAgIGZldGNoQW5kUGFyc2VNZXRhZGF0YShwYXRoLCB0cmFja2VyKS50aGVuKGZ1bmN0aW9uIChzdGF0cykgewogICAgICAgICAgICAgICAgdGhpcy5fc2V0T3V0U3RhdHMoc3RhdHMpOwogICAgICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICAgIH0KICAgICAgICBfZmV0Y2hBbmRDb25zdHJ1Y3RIaWVyYXJjaGljYWxHcmFwaChwYXRoLCBwYlR4dEZpbGUpIHsKICAgICAgICAgICAgLy8gUmVzZXQgdGhlIHByb2dyZXNzIGJhciB0byAwLgogICAgICAgICAgICB0aGlzLnNldCgncHJvZ3Jlc3MnLCB7CiAgICAgICAgICAgICAgICB2YWx1ZTogMCwKICAgICAgICAgICAgICAgIG1zZzogJycsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBjb25zdCB0cmFja2VyID0gZ2V0VHJhY2tlcih0aGlzKTsKICAgICAgICAgICAgcmV0dXJuIGZldGNoQW5kQ29uc3RydWN0SGllcmFyY2hpY2FsR3JhcGgodHJhY2tlciwgcGF0aCwgcGJUeHRGaWxlLCB0aGlzLmNvbXBhdGliaWxpdHlQcm92aWRlciwgdGhpcy5oaWVyYXJjaHlQYXJhbXMpCiAgICAgICAgICAgICAgICAudGhlbihmdW5jdGlvbiAoeyBncmFwaCwgZ3JhcGhIaWVyYXJjaHkgfSkgewogICAgICAgICAgICAgICAgdGhpcy5fc2V0T3V0R3JhcGgoZ3JhcGgpOwogICAgICAgICAgICAgICAgdGhpcy5fc2V0T3V0R3JhcGhIaWVyYXJjaHkoZ3JhcGhIaWVyYXJjaHkpOwogICAgICAgICAgICB9LmJpbmQodGhpcykpOwogICAgICAgIH0KICAgICAgICBfc2VsZWN0ZWRGaWxlQ2hhbmdlZCgpIHsKICAgICAgICAgICAgdmFyIGUgPSB0aGlzLnNlbGVjdGVkRmlsZTsKICAgICAgICAgICAgaWYgKCFlKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgdGFyZ2V0ID0gZS50YXJnZXQ7CiAgICAgICAgICAgIGNvbnN0IGZpbGUgPSB0YXJnZXQuZmlsZXNbMF07CiAgICAgICAgICAgIGlmICghZmlsZSkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIENsZWFyIG91dCB0aGUgdmFsdWUgb2YgdGhlIGZpbGUgY2hvb3Nlci4gVGhpcyBlbnN1cmVzIHRoYXQgaWYgdGhlIHVzZXIKICAgICAgICAgICAgLy8gc2VsZWN0cyB0aGUgc2FtZSBmaWxlLCB3ZSdsbCByZS1yZWFkIGl0LgogICAgICAgICAgICB0YXJnZXQudmFsdWUgPSAnJzsKICAgICAgICAgICAgdGhpcy5fZmV0Y2hBbmRDb25zdHJ1Y3RIaWVyYXJjaGljYWxHcmFwaChudWxsLCBmaWxlKTsKICAgICAgICB9CiAgICB9OwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJkYXRhc2V0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJwcm9ncmVzcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmRMb2FkZXIucHJvdG90eXBlLCAic2VsZWN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJzZWxlY3RlZEZpbGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkTG9hZGVyLnByb3RvdHlwZSwgImNvbXBhdGliaWxpdHlQcm92aWRlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmRMb2FkZXIucHJvdG90eXBlLCAiaGllcmFyY2h5UGFyYW1zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICByZWFkT25seTogdHJ1ZSwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJvdXRHcmFwaEhpZXJhcmNoeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmRMb2FkZXIucHJvdG90eXBlLCAib3V0R3JhcGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIHJlYWRPbmx5OiB0cnVlLAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkTG9hZGVyLnByb3RvdHlwZSwgIm91dFN0YXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJfZ3JhcGhSdW5UYWciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnc2VsZWN0aW9uJywgJ2NvbXBhdGliaWxpdHlQcm92aWRlcicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJfc2VsZWN0aW9uQ2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnc2VsZWN0ZWRGaWxlJywgJ2NvbXBhdGliaWxpdHlQcm92aWRlcicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlci5wcm90b3R5cGUsICJfc2VsZWN0ZWRGaWxlQ2hhbmdlZCIsIG51bGwpOwogICAgVGZHcmFwaERhc2hib2FyZExvYWRlciA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWdyYXBoLWRhc2hib2FyZC1sb2FkZXInKQogICAgXSwgVGZHcmFwaERhc2hib2FyZExvYWRlcik7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIFRoZSAoc3RyaW5nKSBuYW1lIGZvciB0aGUgcnVuIG9mIHRoZSBzZWxlY3RlZCBkYXRhc2V0IGluIHRoZSBncmFwaCBkYXNoYm9hcmQuCiAgICAgKi8KICAgIGNvbnN0IFJVTl9TVE9SQUdFX0tFWSA9ICdydW4nOwogICAgLyoqCiAgICAgKiB0Zi1ncmFwaC1kYXNoYm9hcmQgZGlzcGxheXMgYSBncmFwaCBmcm9tIGEgVGVuc29yRmxvdyBydW4uCiAgICAgKgogICAgICogSXQgaGFzIHNpbXBsZSBiZWhhdmlvcjogQ3JlYXRlcyBhIHVybC1nZW5lcmF0b3IgYW5kIHJ1bi1nZW5lcmF0b3IKICAgICAqIHRvIHRhbGsgdG8gdGhlIGJhY2tlbmQsIGFuZCB0aGVuIHBhc3NlcyB0aGUgcnVuc1dpdGhHcmFwaCAobGlzdCBvZiBydW5zIHdpdGgKICAgICAqIGFzc29jaWF0ZWQgZ3JhcGhzKSBhbG9uZyB3aXRoIHRoZSB1cmwgZ2VuZXJhdG9yIGludG8gdGYtZ3JhcGgtYm9hcmQgZm9yIGRpc3BsYXkuCiAgICAgKgogICAgICogSWYgdGhlcmUgYXJlIG11bHRpcGxlIHJ1bnMgd2l0aCBncmFwaHMsIHRoZSBmaXJzdCBydW4ncyBncmFwaCBpcyBzaG93bgogICAgICogYnkgZGVmYXVsdC4gVGhlIHVzZXIgY2FuIHNlbGVjdCBhIGRpZmZlcmVudCBydW4gZnJvbSBhIGRyb3Bkb3duIG1lbnUuCiAgICAgKi8KICAgIGxldCBUZkdyYXBoRGFzaGJvYXJkID0gY2xhc3MgVGZHcmFwaERhc2hib2FyZCBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUgeyFBcnJheTwhUnVuSXRlbT59CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLl9kYXRhc2V0cyA9IFtdOwogICAgICAgICAgICB0aGlzLl9kYXRhc2V0c0ZldGNoZWQgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWREYXRhc2V0ID0gMDsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdE1hbmFnZXIgPSBuZXcgUmVxdWVzdE1hbmFnZXIoKTsKICAgICAgICAgICAgdGhpcy5fY2FuY2VsbGVyID0gbmV3IENhbmNlbGxlcigpOwogICAgICAgICAgICB0aGlzLnNwZWNpZmljSGVhbHRoUGlsbFN0ZXAgPSAwOwogICAgICAgICAgICB0aGlzLmhlYWx0aFBpbGxzVG9nZ2xlZE9uID0gZmFsc2U7CiAgICAgICAgICAgIC8vIEFuIGFycmF5IG9mIGFsZXJ0cyAoaW4gY2hyb25vbG9naWNhbCBvcmRlcikgcHJvdmlkZWQgYnkgZGVidWdnaW5nIGxpYnJhcmllcyBvbiB3aGVuIGJhZAogICAgICAgICAgICAvLyB2YWx1ZXMgKE5hTiwgKy8tIEluZikgYXBwZWFyLgogICAgICAgICAgICB0aGlzLl9kZWJ1Z2dlck51bWVyaWNBbGVydHMgPSBbXTsKICAgICAgICAgICAgLy8gTWFwcyB0aGUgbmFtZXMgb2Ygbm9kZXMgdG8gYW4gYXJyYXkgb2YgaGVhbHRoIHBpbGxzIChIZWFsdGhQaWxsRGF0dW1zKS4KICAgICAgICAgICAgdGhpcy5fbm9kZU5hbWVzVG9IZWFsdGhQaWxscyA9IHt9OwogICAgICAgICAgICAvLyBBIHN0cmljdGx5IGluY3JlYXNpbmcgSUQuIEVhY2ggcmVxdWVzdCBmb3IgaGVhbHRoIHBpbGxzIGhhcyBhIHVuaXF1ZSBJRC4gVGhpcyBoZWxwcyB1cwogICAgICAgICAgICAvLyBpZGVudGlmeSBzdGFsZSByZXF1ZXN0cy4KICAgICAgICAgICAgdGhpcy5faGVhbHRoUGlsbFJlcXVlc3RJZCA9IDE7CiAgICAgICAgICAgIC8vIFRoZSByZXF1ZXN0IGZvciBoZWFsdGggcGlsbHMgYXQgYSBzcGVjaWZpYyBzdGVwIChhcyBvcHBvc2VkIHRvIGFsbCBzYW1wbGVkIGhlYWx0aCBwaWxscykgbWF5CiAgICAgICAgICAgIC8vIGludm9sdmUgc2xvdyBkaXNrIHJlYWRzLiBIZW5jZSwgd2UgdGhyb3R0bGUgdG8gMSBvZiB0aG9zZSByZXF1ZXN0cyBldmVyeSB0aGlzIG1hbnkgbXMuCiAgICAgICAgICAgIHRoaXMuX2hlYWx0aFBpbGxTdGVwUmVxdWVzdFRpbWVyRGVsYXkgPSA1MDA7CiAgICAgICAgICAgIHRoaXMucnVuID0gZ2V0U3RyaW5nSW5pdGlhbGl6ZXIoUlVOX1NUT1JBR0VfS0VZLCB7CiAgICAgICAgICAgICAgICBkZWZhdWx0VmFsdWU6ICcnLAogICAgICAgICAgICAgICAgdXNlTG9jYWxTdG9yYWdlOiBmYWxzZSwKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5jYWxsKHRoaXMpOwogICAgICAgICAgICB0aGlzLl9ydW5PYnNlcnZlciA9IGdldFN0cmluZ09ic2VydmVyKFJVTl9TVE9SQUdFX0tFWSwgewogICAgICAgICAgICAgICAgZGVmYXVsdFZhbHVlOiAnJywKICAgICAgICAgICAgICAgIHBvbHltZXJQcm9wZXJ0eTogJ3J1bicsCiAgICAgICAgICAgICAgICB1c2VMb2NhbFN0b3JhZ2U6IGZhbHNlLAogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgYXR0YWNoZWQoKSB7CiAgICAgICAgICAgIHRoaXMuc2V0KCdfaXNBdHRhY2hlZCcsIHRydWUpOwogICAgICAgIH0KICAgICAgICBkZXRhY2hlZCgpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19pc0F0dGFjaGVkJywgZmFsc2UpOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdub2RlLXRvZ2dsZS1leHBhbmQnLCB0aGlzLl9oYW5kbGVOb2RlVG9nZ2xlRXhwYW5kLmJpbmQodGhpcykpOwogICAgICAgIH0KICAgICAgICByZWxvYWQoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fZGVidWdnZXJEYXRhRW5hYmxlZCkgewogICAgICAgICAgICAgICAgLy8gQ2hlY2sgaWYgdGhlIGRlYnVnZ2VyIHBsdWdpbiBpcyBlbmFibGVkIG5vdy4KICAgICAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RNYW5hZ2VyLnJlcXVlc3QoZ2V0Um91dGVyKCkucGx1Z2luc0xpc3RpbmcoKSkudGhlbih0aGlzLl9jYW5jZWxsZXIuY2FuY2VsbGFibGUoKHJlc3VsdCkgPT4gewogICAgICAgICAgICAgICAgICAgIGlmIChyZXN1bHQuY2FuY2VsbGVkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgaWYgKHJlc3VsdC52YWx1ZVsnZGVidWdnZXInXSkgewogICAgICAgICAgICAgICAgICAgICAgICAvLyBUaGUgZGVidWdnZXIgcGx1Z2luIGlzIGVuYWJsZWQuIFJlcXVlc3QgZGVidWdnZXItcmVsYXRlZAogICAgICAgICAgICAgICAgICAgICAgICAvLyBkYXRhLiBQZXJoYXBzIHRoZSBkZWJ1Z2dlciBwbHVnaW4gaGFkIGJlZW4gZGlzYWJsZWQKICAgICAgICAgICAgICAgICAgICAgICAgLy8gYmVmb3JlaGFuZCBiZWNhdXNlIG5vIGJhZCB2YWx1ZXMgKE5hTiwgLS8rIEluZikgaGFkIGJlZW4KICAgICAgICAgICAgICAgICAgICAgICAgLy8gZm91bmQgYW5kIG11dGVkX2lmX2hlYWx0aHkgaGFkIGJlZW4gb24uCiAgICAgICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfZGVidWdnZXJEYXRhRW5hYmxlZCcsIHRydWUpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pKTsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLl9tYXliZUZldGNoSGVhbHRoUGlsbHMoKTsKICAgICAgICB9CiAgICAgICAgX2ZpdCgpIHsKICAgICAgICAgICAgdGhpcy4kJCgnI2dyYXBoYm9hcmQnKS5maXQoKTsKICAgICAgICB9CiAgICAgICAgX2ZldGNoRGF0YXNldCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3RNYW5hZ2VyLnJlcXVlc3QoZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2dyYXBocycsICcvaW5mbycpKTsKICAgICAgICB9CiAgICAgICAgLyoKICAgICAgICAgKiBTZWUgYWxzbyBfbWF5YmVGZXRjaEhlYWx0aFBpbGxzLCBfaW5pdGlhdGVOZXR3b3JrUmVxdWVzdEZvckhlYWx0aFBpbGxzLgogICAgICAgICAqIFRoaXMgZnVuY3Rpb24gcmV0dXJucyBhIHByb21pc2Ugd2l0aCB0aGUgcmF3IGhlYWx0aCBwaWxsIGRhdGEuCiAgICAgICAgICovCiAgICAgICAgX2ZldGNoSGVhbHRoUGlsbHMobm9kZU5hbWVzLCBzdGVwKSB7CiAgICAgICAgICAgIGNvbnN0IHBvc3REYXRhID0gewogICAgICAgICAgICAgICAgbm9kZV9uYW1lczogSlNPTi5zdHJpbmdpZnkobm9kZU5hbWVzKSwKICAgICAgICAgICAgICAgIC8vIEV2ZW50cyBmaWxlcyB3aXRoIGRlYnVnZ2VyIGRhdGEgZmFsbCB1bmRlciB0aGlzIHNwZWNpYWwgcnVuLgogICAgICAgICAgICAgICAgcnVuOiAnX19kZWJ1Z2dlcl9kYXRhX18nLAogICAgICAgICAgICB9OwogICAgICAgICAgICBpZiAoc3RlcCAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgdXNlciByZXF1ZXN0ZWQgaGVhbHRoIHBpbGxzIGZvciBhIHNwZWNpZmljIHN0ZXAuIFRoaXMgcmVxdWVzdAogICAgICAgICAgICAgICAgLy8gbWlnaHQgYmUgc2xvdyBzaW5jZSB0aGUgYmFja2VuZCByZWFkcyBldmVudHMgc2VxdWVudGlhbGx5IGZyb20gZGlzay4KICAgICAgICAgICAgICAgIHBvc3REYXRhWydzdGVwJ10gPSBzdGVwOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHVybCA9IGdldFJvdXRlcigpLnBsdWdpblJvdXRlKCdkZWJ1Z2dlcicsICcvaGVhbHRoX3BpbGxzJyk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9yZXF1ZXN0TWFuYWdlci5yZXF1ZXN0KHVybCwgcG9zdERhdGEpOwogICAgICAgIH0KICAgICAgICBfZmV0Y2hEZWJ1Z2dlck51bWVyaWNzQWxlcnRzKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdChnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnZGVidWdnZXInLCAnL251bWVyaWNzX2FsZXJ0X3JlcG9ydCcpKTsKICAgICAgICB9CiAgICAgICAgX2dyYXBoVXJsKHJ1biwgbGltaXRBdHRyU2l6ZSwgbGFyZ2VBdHRyc0tleSkgewogICAgICAgICAgICByZXR1cm4gZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ2dyYXBocycsICcvZ3JhcGgnLCBuZXcgVVJMU2VhcmNoUGFyYW1zKHsKICAgICAgICAgICAgICAgIHJ1bjogcnVuLAogICAgICAgICAgICAgICAgbGltaXRfYXR0cl9zaXplOiBsaW1pdEF0dHJTaXplLAogICAgICAgICAgICAgICAgbGFyZ2VfYXR0cnNfa2V5OiBsYXJnZUF0dHJzS2V5LAogICAgICAgICAgICB9KSk7CiAgICAgICAgfQogICAgICAgIF9zaG91bGRSZXF1ZXN0SGVhbHRoUGlsbHMoKSB7CiAgICAgICAgICAgIC8vIERvIG5vdCBsb2FkIGRlYnVnZ2VyIGRhdGEgaWYgdGhlIGZlYXR1cmUgaXMgZGlzYWJsZWQsIGlmIHRoZSB1c2VyIHRvZ2dsZWQgb2ZmIHRoZSBmZWF0dXJlLAogICAgICAgICAgICAvLyBvciBpZiB0aGUgZ3JhcGggaXRzZWxmIGhhcyBub3QgbG9hZGVkIHlldC4gV2UgbmVlZCB0aGUgZ3JhcGggdG8gbG9hZCBzbyB0aGF0IHdlIGtub3cgd2hpY2gKICAgICAgICAgICAgLy8gbm9kZXMgdG8gcmVxdWVzdCBoZWFsdGggcGlsbHMgZm9yLgogICAgICAgICAgICByZXR1cm4gKHRoaXMuX2RlYnVnZ2VyRGF0YUVuYWJsZWQgJiYKICAgICAgICAgICAgICAgIHRoaXMuaGVhbHRoUGlsbHNUb2dnbGVkT24gJiYKICAgICAgICAgICAgICAgIHRoaXMuX3JlbmRlckhpZXJhcmNoeSAmJgogICAgICAgICAgICAgICAgdGhpcy5fZGF0YXNldHNTdGF0ZSh0aGlzLl9kYXRhc2V0c0ZldGNoZWQsIHRoaXMuX2RhdGFzZXRzLCAnUFJFU0VOVCcpKTsKICAgICAgICB9CiAgICAgICAgX21heWJlSW5pdGlhbGl6ZURhc2hib2FyZCgpIHsKICAgICAgICAgICAgdmFyIGlzQXR0YWNoZWQgPSB0aGlzLl9pc0F0dGFjaGVkOwogICAgICAgICAgICBpZiAodGhpcy5faW5pdGlhbGl6ZWQgfHwgIWlzQXR0YWNoZWQpIHsKICAgICAgICAgICAgICAgIC8vIEVpdGhlciB0aGlzIGRhc2hib2FyZCBpcyBhbHJlYWR5IGluaXRpYWxpemVkIC4uLiBvciB3ZSBhcmUgbm90IHlldCByZWFkeSB0byBpbml0aWFsaXplLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuc2V0KCdfY29tcGF0aWJpbGl0eVByb3ZpZGVyJywgbmV3IFRwdUNvbXBhdGliaWxpdHlQcm92aWRlcigpKTsKICAgICAgICAgICAgLy8gU2V0IHRoaXMgdG8gdHJ1ZSBzbyB3ZSBvbmx5IGluaXRpYWxpemUgb25jZS4KICAgICAgICAgICAgdGhpcy5faW5pdGlhbGl6ZWQgPSB0cnVlOwogICAgICAgICAgICB0aGlzLl9mZXRjaERhdGFzZXQoKS50aGVuKChkYXRhc2V0KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBydW5OYW1lcyA9IE9iamVjdC5rZXlzKGRhdGFzZXQpOwogICAgICAgICAgICAgICAgLy8gVHJhbnNmb3JtIHJhdyBkYXRhIGludG8gVUkgZnJpZW5kbHkgZGF0YS4KICAgICAgICAgICAgICAgIHRoaXMuX2RhdGFzZXRzID0gcnVuTmFtZXMKICAgICAgICAgICAgICAgICAgICAuc29ydChjb21wYXJlVGFnTmFtZXMpCiAgICAgICAgICAgICAgICAgICAgLm1hcCgocnVuTmFtZSkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IHJ1bkRhdGEgPSBkYXRhc2V0W3J1bk5hbWVdOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IHRhZ05hbWVzID0gT2JqZWN0LmtleXMocnVuRGF0YS50YWdzKS5zb3J0KGNvbXBhcmVUYWdOYW1lcyk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgdGFncyA9IHRhZ05hbWVzCiAgICAgICAgICAgICAgICAgICAgICAgIC5tYXAoKG5hbWUpID0+IHJ1bkRhdGEudGFnc1tuYW1lXSkKICAgICAgICAgICAgICAgICAgICAgICAgLm1hcCgoeyB0YWcsIGNvbmNlcHR1YWxfZ3JhcGgsIG9wX2dyYXBoLCBwcm9maWxlIH0pID0+ICh7CiAgICAgICAgICAgICAgICAgICAgICAgIHRhZywKICAgICAgICAgICAgICAgICAgICAgICAgZGlzcGxheU5hbWU6IHRhZywKICAgICAgICAgICAgICAgICAgICAgICAgY29uY2VwdHVhbEdyYXBoOiBjb25jZXB0dWFsX2dyYXBoLAogICAgICAgICAgICAgICAgICAgICAgICBvcEdyYXBoOiBvcF9ncmFwaCwKICAgICAgICAgICAgICAgICAgICAgICAgcHJvZmlsZSwKICAgICAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgICAgICAgICAgLy8gVHJhbnNsYXRlIGEgcnVuLXdpZGUgR3JhcGhEZWYgaW50byBzcGVjaWFsbHkgbmFtZWQgKHdpdGhvdXQgYSB0YWcpIG9wIGdyYXBoCiAgICAgICAgICAgICAgICAgICAgLy8gdG8gYWJzdHJhY3QgdGhlIGRpZmZlcmVuY2UgYmV0d2VlbiBydW5fZ3JhcGggdnMuIG9wX2dyYXBoIGZyb20gb3RoZXIKICAgICAgICAgICAgICAgICAgICAvLyBjb21wb25lbnRzLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IHRhZ3NXaXRoVjFHcmFwaCA9IHJ1bkRhdGEucnVuX2dyYXBoCiAgICAgICAgICAgICAgICAgICAgICAgID8gWwogICAgICAgICAgICAgICAgICAgICAgICAgICAgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHRhZzogbnVsbCwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBkaXNwbGF5TmFtZTogJ0RlZmF1bHQnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbmNlcHR1YWxHcmFwaDogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgb3BHcmFwaDogdHJ1ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBwcm9maWxlOiBmYWxzZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAuLi50YWdzLAogICAgICAgICAgICAgICAgICAgICAgICBdCiAgICAgICAgICAgICAgICAgICAgICAgIDogdGFnczsKICAgICAgICAgICAgICAgICAgICByZXR1cm4geyBuYW1lOiBydW5OYW1lLCB0YWdzOiB0YWdzV2l0aFYxR3JhcGggfTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgdGhpcy5fZGF0YXNldHNGZXRjaGVkID0gdHJ1ZTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9kZXRlcm1pbmVTZWxlY3RlZERhdGFzZXQoKSB7CiAgICAgICAgICAgIHZhciBkYXRhc2V0c0ZldGNoZWQgPSB0aGlzLl9kYXRhc2V0c0ZldGNoZWQ7CiAgICAgICAgICAgIHZhciBkYXRhc2V0cyA9IHRoaXMuX2RhdGFzZXRzOwogICAgICAgICAgICB2YXIgcnVuID0gdGhpcy5ydW47CiAgICAgICAgICAgIC8vIEJ5IGRlZmF1bHQsIGxvYWQgdGhlIGZpcnN0IGRhdGFzZXQuCiAgICAgICAgICAgIGlmICghcnVuKSB7CiAgICAgICAgICAgICAgICAvLyBCeSBkZWZhdWx0LCBsb2FkIHRoZSBmaXJzdCBkYXRhc2V0LgogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19zZWxlY3RlZERhdGFzZXQnLCAwKTsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBJZiB0aGUgVVJMIHNwZWNpZmllcyBhIGRhdGFzZXQsIGxvYWQgaXQuCiAgICAgICAgICAgIGNvbnN0IGRhdGFzZXQgPSBkYXRhc2V0cy5maW5kSW5kZXgoKGQpID0+IGQubmFtZSA9PT0gcnVuKTsKICAgICAgICAgICAgaWYgKGRhdGFzZXQgPT09IC0xKSB7CiAgICAgICAgICAgICAgICBpZiAoZGF0YXNldHNGZXRjaGVkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGVsbCB0aGUgdXNlciBpZiB0aGUgZGF0YXNldCBjYW5ub3QgYmUgZm91bmQgdG8gYXZvaWQgbWlzbGVhZGluZwogICAgICAgICAgICAgICAgICAgIC8vIHRoZSB1c2VyLgogICAgICAgICAgICAgICAgICAgIGNvbnN0IGRpYWxvZyA9IHRoaXMuJCQoJyNlcnJvci1kaWFsb2cnKTsKICAgICAgICAgICAgICAgICAgICBkaWFsb2cudGV4dENvbnRlbnQgPSBgTm8gZGF0YXNldCBuYW1lZCAiJHtydW59IiBjb3VsZCBiZSBmb3VuZC5gOwogICAgICAgICAgICAgICAgICAgIGRpYWxvZy5vcGVuKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5zZXQoJ19zZWxlY3RlZERhdGFzZXQnLCBkYXRhc2V0KTsKICAgICAgICB9CiAgICAgICAgX3VwZGF0ZVNlbGVjdGVkRGF0YXNldE5hbWUoKSB7CiAgICAgICAgICAgIHZhciBkYXRhc2V0c0ZldGNoZWQgPSB0aGlzLl9kYXRhc2V0c0ZldGNoZWQ7CiAgICAgICAgICAgIHZhciBkYXRhc2V0cyA9IHRoaXMuX2RhdGFzZXRzOwogICAgICAgICAgICB2YXIgc2VsZWN0ZWREYXRhc2V0ID0gdGhpcy5fc2VsZWN0ZWREYXRhc2V0OwogICAgICAgICAgICBpZiAoIWRhdGFzZXRzRmV0Y2hlZCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgLy8gQ2Fubm90IHVwZGF0ZSBgcnVuYCB0byB1cGRhdGUgdGhlIGhhc2ggaW4gY2FzZSBkYXRhc2V0cyBmb3IgZ3JhcGggaXMgZW1wdHkuCiAgICAgICAgICAgIGlmIChkYXRhc2V0cy5sZW5ndGggPD0gc2VsZWN0ZWREYXRhc2V0KQogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB0aGlzLnNldCgncnVuJywgZGF0YXNldHNbc2VsZWN0ZWREYXRhc2V0XS5uYW1lKTsKICAgICAgICB9CiAgICAgICAgX3JlcXVlc3RIZWFsdGhQaWxscygpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19hcmVIZWFsdGhQaWxsc0xvYWRpbmcnLCB0cnVlKTsKICAgICAgICAgICAgdmFyIHJlcXVlc3RJZCA9ICsrdGhpcy5faGVhbHRoUGlsbFJlcXVlc3RJZDsKICAgICAgICAgICAgaWYgKHRoaXMuX2hlYWx0aFBpbGxTdGVwUmVxdWVzdFRpbWVySWQgIT09IG51bGwpIHsKICAgICAgICAgICAgICAgIC8vIEEgcmVxdWVzdCBmb3IgaGVhbHRoIHBpbGxzIGlzIGFscmVhZHkgc2NoZWR1bGVkIHRvIGJlIGluaXRpYXRlZC4gQ2xlYXIgaXQsIGFuZCBzY2hlZHVsZSBhCiAgICAgICAgICAgICAgICAvLyBuZXcgcmVxdWVzdC4KICAgICAgICAgICAgICAgIHdpbmRvdy5jbGVhclRpbWVvdXQodGhpcy5faGVhbHRoUGlsbFN0ZXBSZXF1ZXN0VGltZXJJZCk7CiAgICAgICAgICAgICAgICB0aGlzLl9oZWFsdGhQaWxsU3RlcFJlcXVlc3RUaW1lcklkID0gbnVsbDsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhpcy5hbGxTdGVwc01vZGVFbmFibGVkKSB7CiAgICAgICAgICAgICAgICAvLyBUaGlzIHBhdGggbWF5IGJlIHNsb3cuIFNjaGVkdWxlIG5ldHdvcmsgcmVxdWVzdHMgdG8gc3RhcnQgc29tZSB0aW1lIGxhdGVyLiBJZiBhbm90aGVyCiAgICAgICAgICAgICAgICAvLyByZXF1ZXN0IGlzIHNjaGVkdWxlZCBpbiB0aGUgbWVhbiB0aW1lLCBkcm9wIHRoaXMgY3VycmVudCByZXF1ZXN0LgogICAgICAgICAgICAgICAgdGhpcy5faGVhbHRoUGlsbFN0ZXBSZXF1ZXN0VGltZXJJZCA9IHNldFRpbWVvdXQoZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuX2hlYWx0aFBpbGxTdGVwUmVxdWVzdFRpbWVySWQgPSBudWxsOwogICAgICAgICAgICAgICAgICAgIHRoaXMuX2luaXRpYXRlTmV0d29ya1JlcXVlc3RGb3JIZWFsdGhQaWxscyhyZXF1ZXN0SWQpOwogICAgICAgICAgICAgICAgfS5iaW5kKHRoaXMpLCB0aGlzLl9oZWFsdGhQaWxsU3RlcFJlcXVlc3RUaW1lckRlbGF5KTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgIC8vIFRoZSB1c2VyIGlzIGZldGNoaW5nIHNhbXBsZWQgc3RlcHMuIFRoaXMgcGF0aCBpcyBmYXN0LCBzbyBubyBuZWVkIHRvIHRocm90dGxlLiBEaXJlY3RseQogICAgICAgICAgICAgICAgLy8gZmV0Y2ggdGhlIGhlYWx0aCBwaWxscyBhY3Jvc3MgdGhlIG5ldHdvcmsuCiAgICAgICAgICAgICAgICB0aGlzLl9pbml0aWF0ZU5ldHdvcmtSZXF1ZXN0Rm9ySGVhbHRoUGlsbHMocmVxdWVzdElkKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvLyBJbml0aWF0ZXMgdGhlIG5ldHdvcmsgcmVxdWVzdCBmb3IgaGVhbHRoIHBpbGxzLiBEbyBub3QgZGlyZWN0bHkgY2FsbCB0aGlzIG1ldGhvZCAtIG5ldHdvcmsKICAgICAgICAvLyByZXF1ZXN0cyBtYXkgYmUgdGhyb3R0bGVkLiBJbnN0ZWFkLCBjYWxsIF9yZXF1ZXN0SGVhbHRoUGlsbHMsIHdoaWNoIHVzZXMgdGhpcyBtZXRob2QuCiAgICAgICAgX2luaXRpYXRlTmV0d29ya1JlcXVlc3RGb3JIZWFsdGhQaWxscyhyZXF1ZXN0SWQpIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2hlYWx0aFBpbGxSZXF1ZXN0SWQgIT09IHJlcXVlc3RJZCkgewogICAgICAgICAgICAgICAgLy8gVGhpcyBwb3NzaWJseSBzY2hlZHVsZWQgcmVxdWVzdCB3YXMgb3V0ZGF0ZWQgYmVmb3JlIGl0IHdhcyBldmVuIHNlbnQgYWNyb3NzIHRoZSBuZXR3b3JrLiBEbwogICAgICAgICAgICAgICAgLy8gbm90IGJvdGhlciBpbml0aWF0aW5nIGl0LgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHNwZWNpZmljU3RlcCA9IHRoaXMuYWxsU3RlcHNNb2RlRW5hYmxlZAogICAgICAgICAgICAgICAgPyB0aGlzLnNwZWNpZmljSGVhbHRoUGlsbFN0ZXAKICAgICAgICAgICAgICAgIDogdW5kZWZpbmVkOwogICAgICAgICAgICBjb25zdCBoZWFsdGhQaWxsc1Byb21pc2UgPSB0aGlzLl9mZXRjaEhlYWx0aFBpbGxzKHRoaXMuX3JlbmRlckhpZXJhcmNoeS5nZXROYW1lc09mUmVuZGVyZWRPcHMoKSwgc3BlY2lmaWNTdGVwKTsKICAgICAgICAgICAgY29uc3QgYWxlcnRzUHJvbWlzZSA9IHRoaXMuX2ZldGNoRGVidWdnZXJOdW1lcmljc0FsZXJ0cygpOwogICAgICAgICAgICBQcm9taXNlLmFsbChbaGVhbHRoUGlsbHNQcm9taXNlLCBhbGVydHNQcm9taXNlXSkudGhlbihmdW5jdGlvbiAocmVzdWx0KSB7CiAgICAgICAgICAgICAgICB2YXIgaGVhbHRoUGlsbHNSZXN1bHQgPSByZXN1bHRbMF07CiAgICAgICAgICAgICAgICB2YXIgYWxlcnRzUmVzdWx0ID0gcmVzdWx0WzFdOwogICAgICAgICAgICAgICAgaWYgKCF0aGlzLmhlYWx0aFBpbGxzVG9nZ2xlZE9uKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGhlIHVzZXIgaGFzIG9wdGVkIHRvIGhpZGUgaGVhbHRoIHBpbGxzIHZpYSB0aGUgdG9nZ2xlIGJ1dHRvbi4KICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBpZiAocmVxdWVzdElkICE9PSB0aGlzLl9oZWFsdGhQaWxsUmVxdWVzdElkKSB7CiAgICAgICAgICAgICAgICAgICAgLy8gVGhpcyByZXNwb25zZSBpcyBubyBsb25nZXIgcmVsZXZhbnQuCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgLy8gU2V0IHRoZSBpbmRleCBmb3Igd2hpY2ggc3RlcCB0byBzaG93IGZvciB0aGUgaGVhbHRoIHBpbGxzLiBCeSBkZWZhdWx0LCBzaG93IHRoZSBsYXN0IHN0ZXAuCiAgICAgICAgICAgICAgICAvLyBBIHByZWNvbmRpdGlvbiB3ZSBhc3N1bWUgKHRoYXQgVGVuc29yYm9hcmQncyByZXNlcnZvaXIgc2FtcGxpbmcgZ3VhcmFudGVlcykgaXMgdGhhdCBhbGwKICAgICAgICAgICAgICAgIC8vIG5vZGUgbmFtZXMgc2hvdWxkIGJlIG1hcHBlZCB0byB0aGUgc2FtZSBudW1iZXIgb2Ygc3RlcHMuCiAgICAgICAgICAgICAgICBmb3IgKHZhciBub2RlTmFtZSBpbiBoZWFsdGhQaWxsc1Jlc3VsdCkgewogICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfaGVhbHRoUGlsbFN0ZXBJbmRleCcsIGhlYWx0aFBpbGxzUmVzdWx0W25vZGVOYW1lXS5sZW5ndGggLSAxKTsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfZGVidWdnZXJOdW1lcmljQWxlcnRzJywgYWxlcnRzUmVzdWx0KTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfbm9kZU5hbWVzVG9IZWFsdGhQaWxscycsIGhlYWx0aFBpbGxzUmVzdWx0KTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfYXJlSGVhbHRoUGlsbHNMb2FkaW5nJywgZmFsc2UpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19oZWFsdGhQaWxsU3RlcFJlcXVlc3RUaW1lcklkJywgbnVsbCk7CiAgICAgICAgICAgIH0uYmluZCh0aGlzKSk7CiAgICAgICAgfQogICAgICAgIF9kYXRhc2V0c1N0YXRlKGRhdGFzZXRzRmV0Y2hlZCwgZGF0YXNldHMsIHN0YXRlKSB7CiAgICAgICAgICAgIGlmICghZGF0YXNldHNGZXRjaGVkKQogICAgICAgICAgICAgICAgcmV0dXJuIHN0YXRlID09PSAnTk9UX0xPQURFRCc7CiAgICAgICAgICAgIGlmICghZGF0YXNldHMgfHwgIWRhdGFzZXRzLmxlbmd0aCkKICAgICAgICAgICAgICAgIHJldHVybiBzdGF0ZSA9PT0gJ0VNUFRZJzsKICAgICAgICAgICAgcmV0dXJuIHN0YXRlID09PSAnUFJFU0VOVCc7CiAgICAgICAgfQogICAgICAgIF9yZW5kZXJIaWVyYXJjaHlDaGFuZ2VkKHJlbmRlckhpZXJhcmNoeSkgewogICAgICAgICAgICAvLyBSZWxvYWQgYW55IGRhdGEgb24gdGhlIGdyYXBoIHdoZW4gdGhlIHJlbmRlciBoaWVyYXJjaHkgKHdoaWNoIGRldGVybWluZXMgd2hpY2ggbm9kZXMgYXJlCiAgICAgICAgICAgIC8vIHJlbmRlcmVkKSBjaGFuZ2VzLgogICAgICAgICAgICB0aGlzLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICBfaGFuZGxlTm9kZVRvZ2dsZUV4cGFuZCgpIHsKICAgICAgICAgICAgLy8gTm9kZXMgd2VyZSB0b2dnbGVkLiBXZSBtYXkgbmVlZCB0byByZXF1ZXN0IGhlYWx0aCBwaWxscyBmb3IgbW9yZSBub2Rlcy4KICAgICAgICAgICAgdGhpcy5fbWF5YmVGZXRjaEhlYWx0aFBpbGxzKCk7CiAgICAgICAgfQogICAgICAgIF9oZWFsdGhQaWxsc1RvZ2dsZWRPbkNoYW5nZWQoaGVhbHRoUGlsbHNUb2dnbGVkT24pIHsKICAgICAgICAgICAgaWYgKGhlYWx0aFBpbGxzVG9nZ2xlZE9uKSB7CiAgICAgICAgICAgICAgICAvLyBMb2FkIGhlYWx0aCBwaWxscy4KICAgICAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAvLyBSZW1vdmUgYWxsIGhlYWx0aCBwaWxscyBieSBzZXR0aW5nIGFuIGVtcHR5IG1hcHBpbmcuCiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX25vZGVOYW1lc1RvSGVhbHRoUGlsbHMnLCB7fSk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgLy8gRmV0Y2ggaGVhbHRoIHBpbGxzIGZvciBhIHNwZWNpZmljIHN0ZXAgaWYgYXBwbGljYWJsZS4KICAgICAgICBfbWF5YmVGZXRjaEhlYWx0aFBpbGxzKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuX3Nob3VsZFJlcXVlc3RIZWFsdGhQaWxscygpKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fcmVxdWVzdEhlYWx0aFBpbGxzKCk7CiAgICAgICAgfQogICAgfTsKICAgIFRmR3JhcGhEYXNoYm9hcmQudGVtcGxhdGUgPSBodG1sIGAKICAgIDxwYXBlci1kaWFsb2cgaWQ9ImVycm9yLWRpYWxvZyIgd2l0aC1iYWNrZHJvcD48L3BhcGVyLWRpYWxvZz4KICAgIDx0ZW1wbGF0ZQogICAgICBpcz0iZG9tLWlmIgogICAgICBpZj0iW1tfZGF0YXNldHNTdGF0ZShfZGF0YXNldHNGZXRjaGVkLCBfZGF0YXNldHMsICdFTVBUWScpXV0iCiAgICA+CiAgICAgIDxkaXYgc3R5bGU9Im1heC13aWR0aDogNTQwcHg7IG1hcmdpbjogODBweCBhdXRvIDAgYXV0bzsiPgogICAgICAgIDxoMz5ObyBncmFwaCBkZWZpbml0aW9uIGZpbGVzIHdlcmUgZm91bmQuPC9oMz4KICAgICAgICA8cD4KICAgICAgICAgIFRvIHN0b3JlIGEgZ3JhcGgsIGNyZWF0ZSBhCiAgICAgICAgICA8Y29kZT50Zi5zdW1tYXJ5LkZpbGVXcml0ZXI8L2NvZGU+CiAgICAgICAgICBhbmQgcGFzcyB0aGUgZ3JhcGggZWl0aGVyIHZpYSB0aGUgY29uc3RydWN0b3IsIG9yIGJ5IGNhbGxpbmcgaXRzCiAgICAgICAgICA8Y29kZT5hZGRfZ3JhcGgoKTwvY29kZT4gbWV0aG9kLiBZb3UgbWF5IHdhbnQgdG8gY2hlY2sgb3V0IHRoZQogICAgICAgICAgPGEgaHJlZj0iaHR0cHM6Ly93d3cudGVuc29yZmxvdy5vcmcvZ2V0X3N0YXJ0ZWQvZ3JhcGhfdml6IgogICAgICAgICAgICA+Z3JhcGggdmlzdWFsaXplciB0dXRvcmlhbDwvYQogICAgICAgICAgPi4KICAgICAgICA8L3A+CgogICAgICAgIDxwPgogICAgICAgICAgSWYgeW914oCZcmUgbmV3IHRvIHVzaW5nIFRlbnNvckJvYXJkLCBhbmQgd2FudCB0byBmaW5kIG91dCBob3cgdG8gYWRkCiAgICAgICAgICBkYXRhIGFuZCBzZXQgdXAgeW91ciBldmVudCBmaWxlcywgY2hlY2sgb3V0IHRoZQogICAgICAgICAgPGEKICAgICAgICAgICAgaHJlZj0iaHR0cHM6Ly9naXRodWIuY29tL3RlbnNvcmZsb3cvdGVuc29yYm9hcmQvYmxvYi9tYXN0ZXIvUkVBRE1FLm1kIgogICAgICAgICAgICA+UkVBRE1FPC9hCiAgICAgICAgICA+CiAgICAgICAgICBhbmQgcGVyaGFwcyB0aGUKICAgICAgICAgIDxhCiAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vd3d3LnRlbnNvcmZsb3cub3JnL2dldF9zdGFydGVkL3N1bW1hcmllc19hbmRfdGVuc29yYm9hcmQiCiAgICAgICAgICAgID5UZW5zb3JCb2FyZCB0dXRvcmlhbDwvYQogICAgICAgICAgPi4KICAgICAgICA8L3A+CgogICAgICAgIDxwPgogICAgICAgICAgSWYgeW91IHRoaW5rIFRlbnNvckJvYXJkIGlzIGNvbmZpZ3VyZWQgcHJvcGVybHksIHBsZWFzZSBzZWUKICAgICAgICAgIDxhCiAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS90ZW5zb3JmbG93L3RlbnNvcmJvYXJkL2Jsb2IvbWFzdGVyL1JFQURNRS5tZCNteS10ZW5zb3Jib2FyZC1pc250LXNob3dpbmctYW55LWRhdGEtd2hhdHMtd3JvbmciCiAgICAgICAgICAgID50aGUgc2VjdGlvbiBvZiB0aGUgUkVBRE1FIGRldm90ZWQgdG8gbWlzc2luZyBkYXRhIHByb2JsZW1zPC9hCiAgICAgICAgICA+CiAgICAgICAgICBhbmQgY29uc2lkZXIgZmlsaW5nIGFuIGlzc3VlIG9uIEdpdEh1Yi4KICAgICAgICA8L3A+CiAgICAgIDwvZGl2PgogICAgPC90ZW1wbGF0ZT4KICAgIDx0ZW1wbGF0ZQogICAgICBpcz0iZG9tLWlmIgogICAgICBpZj0iW1tfZGF0YXNldHNTdGF0ZShfZGF0YXNldHNGZXRjaGVkLCBfZGF0YXNldHMsICdQUkVTRU5UJyldXSIKICAgID4KICAgICAgPHRmLWRhc2hib2FyZC1sYXlvdXQ+CiAgICAgICAgPHRmLWdyYXBoLWNvbnRyb2xzCiAgICAgICAgICBpZD0iY29udHJvbHMiCiAgICAgICAgICBjbGFzcz0ic2lkZWJhciIKICAgICAgICAgIHNsb3Q9InNpZGViYXIiCiAgICAgICAgICBkZXZpY2VzLWZvci1zdGF0cz0ie3tfZGV2aWNlc0ZvclN0YXRzfX0iCiAgICAgICAgICBjb2xvci1ieS1wYXJhbXM9IltbX2NvbG9yQnlQYXJhbXNdXSIKICAgICAgICAgIHN0YXRzPSJbW19zdGF0c11dIgogICAgICAgICAgY29sb3ItYnk9Int7X2NvbG9yQnl9fSIKICAgICAgICAgIGRhdGFzZXRzPSJbW19kYXRhc2V0c11dIgogICAgICAgICAgcmVuZGVyLWhpZXJhcmNoeT0iW1tfcmVuZGVySGllcmFyY2h5XV0iCiAgICAgICAgICBzZWxlY3Rpb249Int7X3NlbGVjdGlvbn19IgogICAgICAgICAgc2VsZWN0ZWQtZmlsZT0ie3tfc2VsZWN0ZWRGaWxlfX0iCiAgICAgICAgICBzZWxlY3RlZC1ub2RlPSJ7e19zZWxlY3RlZE5vZGV9fSIKICAgICAgICAgIGhlYWx0aC1waWxscy1mZWF0dXJlLWVuYWJsZWQ9IltbX2RlYnVnZ2VyRGF0YUVuYWJsZWRdXSIKICAgICAgICAgIGhlYWx0aC1waWxscy10b2dnbGVkLW9uPSJ7e2hlYWx0aFBpbGxzVG9nZ2xlZE9ufX0iCiAgICAgICAgICBvbi1maXQtdGFwPSJfZml0IgogICAgICAgICAgdHJhY2UtaW5wdXRzPSJ7e190cmFjZUlucHV0c319IgogICAgICAgID48L3RmLWdyYXBoLWNvbnRyb2xzPgogICAgICAgIDxkaXYgY2xhc3M9ImNlbnRlciIgc2xvdD0iY2VudGVyIj4KICAgICAgICAgIDx0Zi1ncmFwaC1kYXNoYm9hcmQtbG9hZGVyCiAgICAgICAgICAgIGlkPSJsb2FkZXIiCiAgICAgICAgICAgIGRhdGFzZXRzPSJbW19kYXRhc2V0c11dIgogICAgICAgICAgICBzZWxlY3Rpb249IltbX3NlbGVjdGlvbl1dIgogICAgICAgICAgICBzZWxlY3RlZC1maWxlPSJbW19zZWxlY3RlZEZpbGVdXSIKICAgICAgICAgICAgb3V0LWdyYXBoLWhpZXJhcmNoeT0ie3tfZ3JhcGhIaWVyYXJjaHl9fSIKICAgICAgICAgICAgb3V0LWdyYXBoPSJ7e19ncmFwaH19IgogICAgICAgICAgICBvdXQtc3RhdHM9Int7X3N0YXRzfX0iCiAgICAgICAgICAgIHByb2dyZXNzPSJ7e19wcm9ncmVzc319IgogICAgICAgICAgICBoaWVyYXJjaHktcGFyYW1zPSJbW19oaWVyYXJjaHlQYXJhbXNdXSIKICAgICAgICAgICAgY29tcGF0aWJpbGl0eS1wcm92aWRlcj0iW1tfY29tcGF0aWJpbGl0eVByb3ZpZGVyXV0iCiAgICAgICAgICA+PC90Zi1ncmFwaC1kYXNoYm9hcmQtbG9hZGVyPgogICAgICAgICAgPHRmLWdyYXBoLWJvYXJkCiAgICAgICAgICAgIGlkPSJncmFwaGJvYXJkIgogICAgICAgICAgICBkZXZpY2VzLWZvci1zdGF0cz0iW1tfZGV2aWNlc0ZvclN0YXRzXV0iCiAgICAgICAgICAgIGNvbG9yLWJ5PSJbW19jb2xvckJ5XV0iCiAgICAgICAgICAgIGNvbG9yLWJ5LXBhcmFtcz0ie3tfY29sb3JCeVBhcmFtc319IgogICAgICAgICAgICBncmFwaC1oaWVyYXJjaHk9IltbX2dyYXBoSGllcmFyY2h5XV0iCiAgICAgICAgICAgIGdyYXBoPSJbW19ncmFwaF1dIgogICAgICAgICAgICBoaWVyYXJjaHktcGFyYW1zPSJbW19oaWVyYXJjaHlQYXJhbXNdXSIKICAgICAgICAgICAgcHJvZ3Jlc3M9IltbX3Byb2dyZXNzXV0iCiAgICAgICAgICAgIGRlYnVnZ2VyLWRhdGEtZW5hYmxlZD0iW1tfZGVidWdnZXJEYXRhRW5hYmxlZF1dIgogICAgICAgICAgICBhcmUtaGVhbHRoLXBpbGxzLWxvYWRpbmc9IltbX2FyZUhlYWx0aFBpbGxzTG9hZGluZ11dIgogICAgICAgICAgICBkZWJ1Z2dlci1udW1lcmljLWFsZXJ0cz0iW1tfZGVidWdnZXJOdW1lcmljQWxlcnRzXV0iCiAgICAgICAgICAgIG5vZGUtbmFtZXMtdG8taGVhbHRoLXBpbGxzPSJbW19ub2RlTmFtZXNUb0hlYWx0aFBpbGxzXV0iCiAgICAgICAgICAgIGFsbC1zdGVwcy1tb2RlLWVuYWJsZWQ9Int7YWxsU3RlcHNNb2RlRW5hYmxlZH19IgogICAgICAgICAgICBzcGVjaWZpYy1oZWFsdGgtcGlsbC1zdGVwPSJ7e3NwZWNpZmljSGVhbHRoUGlsbFN0ZXB9fSIKICAgICAgICAgICAgaGVhbHRoLXBpbGwtc3RlcC1pbmRleD0iW1tfaGVhbHRoUGlsbFN0ZXBJbmRleF1dIgogICAgICAgICAgICByZW5kZXItaGllcmFyY2h5PSJ7e19yZW5kZXJIaWVyYXJjaHl9fSIKICAgICAgICAgICAgc2VsZWN0ZWQtbm9kZT0ie3tfc2VsZWN0ZWROb2RlfX0iCiAgICAgICAgICAgIHN0YXRzPSJbW19zdGF0c11dIgogICAgICAgICAgICB0cmFjZS1pbnB1dHM9IltbX3RyYWNlSW5wdXRzXV0iCiAgICAgICAgICA+PC90Zi1ncmFwaC1ib2FyZD4KICAgICAgICA8L2Rpdj4KICAgICAgPC90Zi1kYXNoYm9hcmQtbGF5b3V0PgogICAgPC90ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgOmhvc3QgL2RlZXAvIHsKICAgICAgICBmb250LWZhbWlseTogJ1JvYm90bycsIHNhbnMtc2VyaWY7CiAgICAgIH0KCiAgICAgIC5zaWRlYmFyIHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQoKICAgICAgLmNlbnRlciB7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQoKICAgICAgcGFwZXItZGlhbG9nIHsKICAgICAgICBwYWRkaW5nOiAyMHB4OwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEFycmF5LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kYXRhc2V0cyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfZGF0YXNldHNGZXRjaGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfc2VsZWN0ZWREYXRhc2V0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0LCBvYnNlcnZlcjogJ19yZW5kZXJIaWVyYXJjaHlDaGFuZ2VkJyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX3JlbmRlckhpZXJhcmNoeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFJlcXVlc3RNYW5hZ2VyKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfcmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBDYW5jZWxsZXIpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9jYW5jZWxsZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX2RlYnVnZ2VyRGF0YUVuYWJsZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiYWxsU3RlcHNNb2RlRW5hYmxlZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAic3BlY2lmaWNIZWFsdGhQaWxsU3RlcCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG9ic2VydmVyOiAnX2hlYWx0aFBpbGxzVG9nZ2xlZE9uQ2hhbmdlZCcsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJoZWFsdGhQaWxsc1RvZ2dsZWRPbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJzZWxlY3RlZE5vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX2lzQXR0YWNoZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX2luaXRpYWxpemVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9hcmVIZWFsdGhQaWxsc0xvYWRpbmciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kZWJ1Z2dlck51bWVyaWNBbGVydHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9ub2RlTmFtZXNUb0hlYWx0aFBpbGxzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfaGVhbHRoUGlsbFN0ZXBJbmRleCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX2hlYWx0aFBpbGxSZXF1ZXN0SWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9oZWFsdGhQaWxsU3RlcFJlcXVlc3RUaW1lcklkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfaGVhbHRoUGlsbFN0ZXBSZXF1ZXN0VGltZXJEZWxheSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgInJ1bnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfcnVuT2JzZXJ2ZXInLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJydW4iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9zZWxlY3Rpb24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9jb21wYXRpYmlsaXR5UHJvdmlkZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQucHJvdG90eXBlLCAiX3RyYWNlSW5wdXRzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ19pc0F0dGFjaGVkJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9tYXliZUluaXRpYWxpemVEYXNoYm9hcmQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ19kYXRhc2V0c0ZldGNoZWQnLCAnX2RhdGFzZXRzJywgJ3J1bicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZHcmFwaERhc2hib2FyZC5wcm90b3R5cGUsICJfZGV0ZXJtaW5lU2VsZWN0ZWREYXRhc2V0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdfZGF0YXNldHNGZXRjaGVkJywgJ19kYXRhc2V0cycsICdfc2VsZWN0ZWREYXRhc2V0JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkdyYXBoRGFzaGJvYXJkLnByb3RvdHlwZSwgIl91cGRhdGVTZWxlY3RlZERhdGFzZXROYW1lIiwgbnVsbCk7CiAgICBUZkdyYXBoRGFzaGJvYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZ3JhcGgtZGFzaGJvYXJkJykKICAgIF0sIFRmR3JhcGhEYXNoYm9hcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDE2IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gVHlwZVNjcmlwdCBjYW4ndCBkZWFsIHdpdGggZDMncyBzdHlsZSBvZiBvdmVybG9hZGluZyBhbmQKICAgIC8vIHBvbHltb3JwaGlzbSwgYW5kIGNvbnN0YW50bHkgZmFpbHMgdG8gc2VsZWN0IHRoZSBjb3JyZWN0IG92ZXJsb2FkLgogICAgLy8gVGhpcyBtb2R1bGUgd2FzIGNvbnZlcnRlZCBmcm9tIHdvcmtpbmcgbm9uLVR5cGVTY3JpcHQgY29kZSwgc28gd2UKICAgIC8vIGdyYW5kZmF0aGVyIGl0IGluIHVudHlwZWQuCiAgICBjb25zdCBkMyQxID0gZDNUeXBlZDsKICAgIGxldCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzID0gY2xhc3MgX1Z6SGlzdG9ncmFtVGltZXNlcmllcyBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLm1vZGUgPSAnb2Zmc2V0JzsKICAgICAgICAgICAgdGhpcy50aW1lUHJvcGVydHkgPSAnc3RlcCc7CiAgICAgICAgICAgIHRoaXMuYmlucyA9ICdiaW5zJzsKICAgICAgICAgICAgdGhpcy54ID0gJ3gnOwogICAgICAgICAgICB0aGlzLmR4ID0gJ2R4JzsKICAgICAgICAgICAgdGhpcy55ID0gJ3knOwogICAgICAgICAgICB0aGlzLmNvbG9yU2NhbGUgPSBkMyQxLnNjYWxlT3JkaW5hbChkMyQxLnNjaGVtZUNhdGVnb3J5MTApOwogICAgICAgICAgICB0aGlzLm1vZGVUcmFuc2l0aW9uRHVyYXRpb24gPSA1MDA7CiAgICAgICAgICAgIHRoaXMuX25hbWUgPSBudWxsOwogICAgICAgICAgICB0aGlzLl9kYXRhID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgcmVhZHkoKSB7CiAgICAgICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgICAgIC8vIFBvbHltZXIncyB3YXkgb2Ygc2NvcGluZyBzdHlsZXMgb24gbm9kZXMgdGhhdCBkMyBjcmVhdGVkCiAgICAgICAgICAgIHRoaXMuc2NvcGVTdWJ0cmVlKHRoaXMuJC5zdmcsIHRydWUpOwogICAgICAgIH0KICAgICAgICBhdHRhY2hlZCgpIHsKICAgICAgICAgICAgdGhpcy5fYXR0YWNoZWQgPSB0cnVlOwogICAgICAgIH0KICAgICAgICBkZXRhY2hlZCgpIHsKICAgICAgICAgICAgdGhpcy5fYXR0YWNoZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgc2V0U2VyaWVzRGF0YShuYW1lLCBkYXRhKSB7CiAgICAgICAgICAgIHRoaXMuX25hbWUgPSBuYW1lOwogICAgICAgICAgICB0aGlzLl9kYXRhID0gZGF0YTsKICAgICAgICAgICAgdGhpcy5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgX3JlZHJhd09uQ2hhbmdlKCkgewogICAgICAgICAgICB0aGlzLnJlZHJhdygpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZWRyYXdzIHRoZSBjaGFydC4gVGhpcyBpcyBvbmx5IGNhbGxlZCBpZiB0aGUgY2hhcnQgaXMgYXR0YWNoZWQgdG8gdGhlCiAgICAgICAgICogc2NyZWVuIGFuZCBpZiB0aGUgY2hhcnQgaGFzIGRhdGEuCiAgICAgICAgICovCiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICB0aGlzLl9kcmF3KDApOwogICAgICAgIH0KICAgICAgICBfbW9kZVJlZHJhdygpIHsKICAgICAgICAgICAgdGhpcy5fZHJhdyh0aGlzLm1vZGVUcmFuc2l0aW9uRHVyYXRpb24pOwogICAgICAgIH0KICAgICAgICBfZHJhdyhkdXJhdGlvbikgewogICAgICAgICAgICBpZiAoIXRoaXMuX2F0dGFjaGVkIHx8ICF0aGlzLl9kYXRhKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gRGF0YSB2ZXJpZmljYXRpb24KICAgICAgICAgICAgLy8KICAgICAgICAgICAgaWYgKGR1cmF0aW9uID09PSB1bmRlZmluZWQpCiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoJ3Z6LWhpc3RvZ3JhbS10aW1lc2VyaWVzIF9kcmF3IG5lZWRzIGR1cmF0aW9uJyk7CiAgICAgICAgICAgIGlmICh0aGlzLl9kYXRhLmxlbmd0aCA8PSAwKQogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdOb3QgZW5vdWdoIHN0ZXBzIGluIHRoZSBkYXRhJyk7CiAgICAgICAgICAgIGlmICghdGhpcy5fZGF0YVswXS5oYXNPd25Qcm9wZXJ0eSh0aGlzLmJpbnMpKQogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCJObyBiaW5zIHByb3BlcnR5IG9mICciICsgdGhpcy5iaW5zICsgIicgaW4gZGF0YSIpOwogICAgICAgICAgICBpZiAodGhpcy5fZGF0YVswXVt0aGlzLmJpbnNdLmxlbmd0aCA8PSAwKQogICAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdNdXN0IGhhdmUgYXQgbGVhc3Qgb25lIGJpbiBpbiBiaW5zIGluIGRhdGEnKTsKICAgICAgICAgICAgaWYgKCF0aGlzLl9kYXRhWzBdW3RoaXMuYmluc11bMF0uaGFzT3duUHJvcGVydHkodGhpcy54KSkKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiTm8geCBwcm9wZXJ0eSAnIiArIHRoaXMueCArICInIG9uIGJpbnMgZGF0YSIpOwogICAgICAgICAgICBpZiAoIXRoaXMuX2RhdGFbMF1bdGhpcy5iaW5zXVswXS5oYXNPd25Qcm9wZXJ0eSh0aGlzLmR4KSkKICAgICAgICAgICAgICAgIHRocm93IG5ldyBFcnJvcigiTm8gZHggcHJvcGVydHkgJyIgKyB0aGlzLmR4ICsgIicgb24gYmlucyBkYXRhIik7CiAgICAgICAgICAgIGlmICghdGhpcy5fZGF0YVswXVt0aGlzLmJpbnNdWzBdLmhhc093blByb3BlcnR5KHRoaXMueSkpCiAgICAgICAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoIk5vIHkgcHJvcGVydHkgJyIgKyB0aGlzLnkgKyAiJyBvbiBiaW5zIGRhdGEiKTsKICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gSW5pdGlhbGl6YXRpb24KICAgICAgICAgICAgLy8KICAgICAgICAgICAgdmFyIHRpbWVQcm9wID0gdGhpcy50aW1lUHJvcGVydHk7CiAgICAgICAgICAgIHZhciB4UHJvcCA9IHRoaXMueDsKICAgICAgICAgICAgdmFyIGJpbnNQcm9wID0gdGhpcy5iaW5zOwogICAgICAgICAgICB2YXIgZHhQcm9wID0gdGhpcy5keDsKICAgICAgICAgICAgdmFyIHlQcm9wID0gdGhpcy55OwogICAgICAgICAgICB2YXIgZGF0YSA9IHRoaXMuX2RhdGE7CiAgICAgICAgICAgIHZhciBuYW1lID0gdGhpcy5fbmFtZTsKICAgICAgICAgICAgdmFyIG1vZGUgPSB0aGlzLm1vZGU7CiAgICAgICAgICAgIHZhciBjb2xvciA9IGQzJDEuaGNsKHRoaXMuY29sb3JTY2FsZShuYW1lKSk7CiAgICAgICAgICAgIHZhciB0b29sdGlwID0gZDMkMS5zZWxlY3QodGhpcy4kLnRvb2x0aXApOwogICAgICAgICAgICB2YXIgeEFjY2Vzc29yID0gZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkW3hQcm9wXTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdmFyIHlBY2Nlc3NvciA9IGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZFt5UHJvcF07CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB4UmlnaHRBY2Nlc3NvciA9IGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gZFt4UHJvcF0gKyBkW2R4UHJvcF07CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciB0aW1lQWNjZXNzb3IgPSBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIGRbdGltZVByb3BdOwogICAgICAgICAgICB9OwogICAgICAgICAgICBpZiAodGltZVByb3AgPT09ICdyZWxhdGl2ZScpIHsKICAgICAgICAgICAgICAgIHRpbWVBY2Nlc3NvciA9IGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGQud2FsbF90aW1lIC0gZGF0YVswXS53YWxsX3RpbWU7CiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIHZhciBicmVjdCA9IHRoaXMuJC5zdmcuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgICAgIHZhciBvdXRlcldpZHRoID0gYnJlY3Qud2lkdGgsIG91dGVySGVpZ2h0ID0gYnJlY3QuaGVpZ2h0OwogICAgICAgICAgICB2YXIgc2xpY2VIZWlnaHQsIG1hcmdpbiA9IHsgdG9wOiA1LCByaWdodDogNjAsIGJvdHRvbTogMjAsIGxlZnQ6IDI0IH07CiAgICAgICAgICAgIGlmIChtb2RlID09PSAnb2Zmc2V0JykgewogICAgICAgICAgICAgICAgc2xpY2VIZWlnaHQgPSBvdXRlckhlaWdodCAvIDIuNTsKICAgICAgICAgICAgICAgIG1hcmdpbi50b3AgPSBzbGljZUhlaWdodCArIDU7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICBzbGljZUhlaWdodCA9IG91dGVySGVpZ2h0IC0gbWFyZ2luLnRvcCAtIG1hcmdpbi5ib3R0b207CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdmFyIHdpZHRoID0gb3V0ZXJXaWR0aCAtIG1hcmdpbi5sZWZ0IC0gbWFyZ2luLnJpZ2h0LCBoZWlnaHQgPSBvdXRlckhlaWdodCAtIG1hcmdpbi50b3AgLSBtYXJnaW4uYm90dG9tOwogICAgICAgICAgICB2YXIgbGVmdE1pbiA9IGQzJDEubWluKGRhdGEsIHhBY2Nlc3NvciksIHJpZ2h0TWF4ID0gZDMkMS5tYXgoZGF0YSwgeFJpZ2h0QWNjZXNzb3IpOwogICAgICAgICAgICAvLwogICAgICAgICAgICAvLyBUZXh0IGZvcm1hdHRlcnMKICAgICAgICAgICAgLy8KICAgICAgICAgICAgdmFyIGZvcm1hdCA9IGQzJDEuZm9ybWF0KCcuM24nKTsKICAgICAgICAgICAgdmFyIHlBeGlzRm9ybWF0ID0gZDMkMS5mb3JtYXQoJy4wZicpOwogICAgICAgICAgICBpZiAodGltZVByb3AgPT09ICd3YWxsX3RpbWUnKSB7CiAgICAgICAgICAgICAgICB5QXhpc0Zvcm1hdCA9IGQzJDEudGltZUZvcm1hdCgnJW0vJWQgJVgnKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBlbHNlIGlmICh0aW1lUHJvcCA9PT0gJ3JlbGF0aXZlJykgewogICAgICAgICAgICAgICAgeUF4aXNGb3JtYXQgPSBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBkMyQxLmZvcm1hdCgnLjFyJykoZCAvIDMuNmU2KSArICdoJzsgLy8gQ29udmVydCB0byBob3Vycy4KICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gQ2FsY3VsYXRlIHRoZSBleHRlbnRzCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIHZhciB4RXh0ZW50cyA9IGRhdGEubWFwKGZ1bmN0aW9uIChkLCBpKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gWwogICAgICAgICAgICAgICAgICAgIGQzJDEubWluKGRbYmluc1Byb3BdLCB4QWNjZXNzb3IpLAogICAgICAgICAgICAgICAgICAgIGQzJDEubWF4KGRbYmluc1Byb3BdLCB4UmlnaHRBY2Nlc3NvciksCiAgICAgICAgICAgICAgICBdOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIHlFeHRlbnRzID0gZGF0YS5tYXAoZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkMyQxLmV4dGVudChkW2JpbnNQcm9wXSwgeUFjY2Vzc29yKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIFNjYWxlcyBhbmQgYXhpcwogICAgICAgICAgICAvLwogICAgICAgICAgICB2YXIgb3V0bGluZUNhbnZhc1NpemUgPSA1MDA7CiAgICAgICAgICAgIHZhciBleHRlbnQgPSBkMyQxLmV4dGVudChkYXRhLCB0aW1lQWNjZXNzb3IpOwogICAgICAgICAgICB2YXIgeVNjYWxlID0gKHRpbWVQcm9wID09PSAnd2FsbF90aW1lJyA/IGQzJDEuc2NhbGVUaW1lKCkgOiBkMyQxLnNjYWxlTGluZWFyKCkpCiAgICAgICAgICAgICAgICAuZG9tYWluKGV4dGVudCkKICAgICAgICAgICAgICAgIC5yYW5nZShbMCwgbW9kZSA9PT0gJ29mZnNldCcgPyBoZWlnaHQgOiAwXSk7CiAgICAgICAgICAgIHZhciB5U2xpY2VTY2FsZSA9IGQzJDEKICAgICAgICAgICAgICAgIC5zY2FsZUxpbmVhcigpCiAgICAgICAgICAgICAgICAuZG9tYWluKFsKICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgICAgICBkMyQxLm1heChkYXRhLCBmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiB5RXh0ZW50c1tpXVsxXTsKICAgICAgICAgICAgICAgIH0pLAogICAgICAgICAgICBdKQogICAgICAgICAgICAgICAgLnJhbmdlKFtzbGljZUhlaWdodCwgMF0pOwogICAgICAgICAgICB2YXIgeUxpbmVTY2FsZSA9IGQzJDEKICAgICAgICAgICAgICAgIC5zY2FsZUxpbmVhcigpCiAgICAgICAgICAgICAgICAuZG9tYWluKHlTbGljZVNjYWxlLmRvbWFpbigpKQogICAgICAgICAgICAgICAgLnJhbmdlKFtvdXRsaW5lQ2FudmFzU2l6ZSwgMF0pOwogICAgICAgICAgICB2YXIgeFNjYWxlID0gZDMkMQogICAgICAgICAgICAgICAgLnNjYWxlTGluZWFyKCkKICAgICAgICAgICAgICAgIC5kb21haW4oWwogICAgICAgICAgICAgICAgZDMkMS5taW4oZGF0YSwgZnVuY3Rpb24gKGQsIGkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4geEV4dGVudHNbaV1bMF07CiAgICAgICAgICAgICAgICB9KSwKICAgICAgICAgICAgICAgIGQzJDEubWF4KGRhdGEsIGZ1bmN0aW9uIChkLCBpKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHhFeHRlbnRzW2ldWzFdOwogICAgICAgICAgICAgICAgfSksCiAgICAgICAgICAgIF0pCiAgICAgICAgICAgICAgICAubmljZSgpCiAgICAgICAgICAgICAgICAucmFuZ2UoWzAsIHdpZHRoXSk7CiAgICAgICAgICAgIHZhciB4TGluZVNjYWxlID0gZDMkMQogICAgICAgICAgICAgICAgLnNjYWxlTGluZWFyKCkKICAgICAgICAgICAgICAgIC5kb21haW4oeFNjYWxlLmRvbWFpbigpKQogICAgICAgICAgICAgICAgLnJhbmdlKFswLCBvdXRsaW5lQ2FudmFzU2l6ZV0pOwogICAgICAgICAgICB2YXIgb3V0bGluZUNvbG9yID0gZDMkMQogICAgICAgICAgICAgICAgLnNjYWxlTGluZWFyKCkKICAgICAgICAgICAgICAgIC5kb21haW4oZDMkMS5leHRlbnQoZGF0YSwgdGltZUFjY2Vzc29yKSkKICAgICAgICAgICAgICAgIC5yYW5nZShbY29sb3IuZGFya2VyKCksIGNvbG9yLmJyaWdodGVyKCldKQogICAgICAgICAgICAgICAgLmludGVycG9sYXRlKGQzJDEuaW50ZXJwb2xhdGVIY2wpOwogICAgICAgICAgICB2YXIgeEF4aXMgPSBkMyQxLmF4aXNCb3R0b20oeFNjYWxlKS50aWNrcyhNYXRoLm1heCgyLCB3aWR0aCAvIDIwKSk7CiAgICAgICAgICAgIHZhciB5QXhpcyA9IGQzJDEKICAgICAgICAgICAgICAgIC5heGlzUmlnaHQoeVNjYWxlKQogICAgICAgICAgICAgICAgLnRpY2tzKE1hdGgubWF4KDIsIGhlaWdodCAvIDE1KSkKICAgICAgICAgICAgICAgIC50aWNrRm9ybWF0KHlBeGlzRm9ybWF0KTsKICAgICAgICAgICAgdmFyIHlTbGljZUF4aXMgPSBkMyQxCiAgICAgICAgICAgICAgICAuYXhpc1JpZ2h0KHlTbGljZVNjYWxlKQogICAgICAgICAgICAgICAgLnRpY2tzKE1hdGgubWF4KDIsIGhlaWdodCAvIDE1KSkKICAgICAgICAgICAgICAgIC50aWNrU2l6ZSh3aWR0aCArIDUpCiAgICAgICAgICAgICAgICAudGlja0Zvcm1hdChmb3JtYXQpOwogICAgICAgICAgICB2YXIgeEJpbkNlbnRyb2lkID0gZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBkW3hQcm9wXSArIGRbZHhQcm9wXSAvIDI7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHZhciBsaW5lUGF0aCA9IGQzJDEKICAgICAgICAgICAgICAgIC5saW5lKCkKICAgICAgICAgICAgICAgIC54KGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4geExpbmVTY2FsZSh4QmluQ2VudHJvaWQoZCkpOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLnkoZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHJldHVybiB5TGluZVNjYWxlKGRbeVByb3BdKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHZhciBwYXRoID0gZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIC8vIERyYXcgYSBsaW5lIGZyb20gMCB0byB0aGUgZmlyc3QgcG9pbnQgYW5kIGZyb20gdGhlIGxhc3QgcG9pbnQgdG8gMC4KICAgICAgICAgICAgICAgIHJldHVybiAoJ00nICsKICAgICAgICAgICAgICAgICAgICB4TGluZVNjYWxlKHhCaW5DZW50cm9pZChkWzBdKSkgKwogICAgICAgICAgICAgICAgICAgICcsJyArCiAgICAgICAgICAgICAgICAgICAgeUxpbmVTY2FsZSgwKSArCiAgICAgICAgICAgICAgICAgICAgJ0wnICsKICAgICAgICAgICAgICAgICAgICBsaW5lUGF0aChkKS5zbGljZSgxKSArCiAgICAgICAgICAgICAgICAgICAgJ0wnICsKICAgICAgICAgICAgICAgICAgICB4TGluZVNjYWxlKHhCaW5DZW50cm9pZChkW2QubGVuZ3RoIC0gMV0pKSArCiAgICAgICAgICAgICAgICAgICAgJywnICsKICAgICAgICAgICAgICAgICAgICB5TGluZVNjYWxlKDApKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gUmVuZGVyCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIHZhciBzdmdOb2RlID0gdGhpcy4kLnN2ZzsKICAgICAgICAgICAgdmFyIHN2ZyA9IGQzJDEuc2VsZWN0KHN2Z05vZGUpOwogICAgICAgICAgICB2YXIgc3ZnVHJhbnNpdGlvbiA9IHN2Zy50cmFuc2l0aW9uKCkuZHVyYXRpb24oZHVyYXRpb24pOwogICAgICAgICAgICB2YXIgZyA9IHN2ZwogICAgICAgICAgICAgICAgLnNlbGVjdCgnZycpCiAgICAgICAgICAgICAgICAuY2xhc3NlZCgnc21hbGwnLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gd2lkdGggPiAwICYmIHdpZHRoIDw9IDE1MDsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCdtZWRpdW0nLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gd2lkdGggPiAxNTAgJiYgd2lkdGggPD0gMzAwOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2xhcmdlJywgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHdpZHRoID4gMzAwOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdmFyIGdUcmFuc2l0aW9uID0gc3ZnVHJhbnNpdGlvbgogICAgICAgICAgICAgICAgLnNlbGVjdCgnZycpCiAgICAgICAgICAgICAgICAuYXR0cigndHJhbnNmb3JtJywgJ3RyYW5zbGF0ZSgnICsgbWFyZ2luLmxlZnQgKyAnLCcgKyBtYXJnaW4udG9wICsgJyknKTsKICAgICAgICAgICAgdmFyIGJpc2VjdCA9IGQzJDEuYmlzZWN0b3IoeFJpZ2h0QWNjZXNzb3IpLmxlZnQ7CiAgICAgICAgICAgIHZhciBzdGFnZSA9IGcKICAgICAgICAgICAgICAgIC5zZWxlY3QoJy5zdGFnZScpCiAgICAgICAgICAgICAgICAub24oJ21vdXNlb3ZlcicsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIGhvdmVyVXBkYXRlLnN0eWxlKCdvcGFjaXR5JywgMSk7CiAgICAgICAgICAgICAgICB4QXhpc0hvdmVyVXBkYXRlLnN0eWxlKCdvcGFjaXR5JywgMSk7CiAgICAgICAgICAgICAgICB5QXhpc0hvdmVyVXBkYXRlLnN0eWxlKCdvcGFjaXR5JywgMSk7CiAgICAgICAgICAgICAgICB5U2xpY2VBeGlzSG92ZXJVcGRhdGUuc3R5bGUoJ29wYWNpdHknLCAxKTsKICAgICAgICAgICAgICAgIHRvb2x0aXAuc3R5bGUoJ29wYWNpdHknLCAxKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5vbignbW91c2VvdXQnLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgICAgICBob3ZlclVwZGF0ZS5zdHlsZSgnb3BhY2l0eScsIDApOwogICAgICAgICAgICAgICAgeEF4aXNIb3ZlclVwZGF0ZS5zdHlsZSgnb3BhY2l0eScsIDApOwogICAgICAgICAgICAgICAgeUF4aXNIb3ZlclVwZGF0ZS5zdHlsZSgnb3BhY2l0eScsIDApOwogICAgICAgICAgICAgICAgeVNsaWNlQXhpc0hvdmVyVXBkYXRlLnN0eWxlKCdvcGFjaXR5JywgMCk7CiAgICAgICAgICAgICAgICBob3ZlclVwZGF0ZS5jbGFzc2VkKCdob3Zlci1jbG9zZXN0JywgZmFsc2UpOwogICAgICAgICAgICAgICAgb3V0bGluZVVwZGF0ZS5jbGFzc2VkKCdvdXRsaW5lLWhvdmVyJywgZmFsc2UpOwogICAgICAgICAgICAgICAgdG9vbHRpcC5zdHlsZSgnb3BhY2l0eScsIDApOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLm9uKCdtb3VzZW1vdmUnLCBvbk1vdXNlTW92ZSk7CiAgICAgICAgICAgIHZhciBiYWNrZ3JvdW5kID0gc3RhZ2UKICAgICAgICAgICAgICAgIC5zZWxlY3QoJy5iYWNrZ3JvdW5kJykKICAgICAgICAgICAgICAgIC5hdHRyKCd0cmFuc2Zvcm0nLCAndHJhbnNsYXRlKCcgKyAtbWFyZ2luLmxlZnQgKyAnLCcgKyAtbWFyZ2luLnRvcCArICcpJykKICAgICAgICAgICAgICAgIC5hdHRyKCd3aWR0aCcsIG91dGVyV2lkdGgpCiAgICAgICAgICAgICAgICAuYXR0cignaGVpZ2h0Jywgb3V0ZXJIZWlnaHQpOwogICAgICAgICAgICB2YXIgaGlzdG9ncmFtID0gc3RhZ2Uuc2VsZWN0QWxsKCcuaGlzdG9ncmFtJykuZGF0YShkYXRhKSwgaGlzdG9ncmFtRXhpdCA9IGhpc3RvZ3JhbS5leGl0KCkucmVtb3ZlKCksIGhpc3RvZ3JhbUVudGVyID0gaGlzdG9ncmFtLmVudGVyKCkuYXBwZW5kKCdnJykuYXR0cignY2xhc3MnLCAnaGlzdG9ncmFtJyksIGhpc3RvZ3JhbVVwZGF0ZSA9IGhpc3RvZ3JhbUVudGVyLm1lcmdlKGhpc3RvZ3JhbSkuc29ydChmdW5jdGlvbiAoYSwgYikgewogICAgICAgICAgICAgICAgcmV0dXJuIHRpbWVBY2Nlc3NvcihhKSAtIHRpbWVBY2Nlc3NvcihiKTsKICAgICAgICAgICAgfSksIGhpc3RvZ3JhbVRyYW5zaXRpb24gPSBnVHJhbnNpdGlvbgogICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgnLmhpc3RvZ3JhbScpCiAgICAgICAgICAgICAgICAuYXR0cigndHJhbnNmb3JtJywgZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgIHJldHVybiAoJ3RyYW5zbGF0ZSgwLCAnICsKICAgICAgICAgICAgICAgICAgICAobW9kZSA9PT0gJ29mZnNldCcgPyB5U2NhbGUodGltZUFjY2Vzc29yKGQpKSAtIHNsaWNlSGVpZ2h0IDogMCkgKwogICAgICAgICAgICAgICAgICAgICcpJyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgYmFzZWxpbmVFbnRlciA9IGhpc3RvZ3JhbUVudGVyLmFwcGVuZCgnbGluZScpLmF0dHIoJ2NsYXNzJywgJ2Jhc2VsaW5lJyksIGJhc2VsaW5lVXBkYXRlID0gaGlzdG9ncmFtVHJhbnNpdGlvbgogICAgICAgICAgICAgICAgLnNlbGVjdCgnLmJhc2VsaW5lJykKICAgICAgICAgICAgICAgIC5zdHlsZSgnc3Ryb2tlLW9wYWNpdHknLCBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG1vZGUgPT09ICdvZmZzZXQnID8gMC4xIDogMDsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5hdHRyKCd5MScsIHNsaWNlSGVpZ2h0KQogICAgICAgICAgICAgICAgLmF0dHIoJ3kyJywgc2xpY2VIZWlnaHQpCiAgICAgICAgICAgICAgICAuYXR0cigneDInLCB3aWR0aCk7CiAgICAgICAgICAgIHZhciBvdXRsaW5lRW50ZXIgPSBoaXN0b2dyYW1FbnRlci5hcHBlbmQoJ3BhdGgnKS5hdHRyKCdjbGFzcycsICdvdXRsaW5lJyksIG91dGxpbmVVcGRhdGUgPSBoaXN0b2dyYW1VcGRhdGUKICAgICAgICAgICAgICAgIC5zZWxlY3QoJy5vdXRsaW5lJykKICAgICAgICAgICAgICAgIC5hdHRyKCd2ZWN0b3ItZWZmZWN0JywgJ25vbi1zY2FsaW5nLXN0cm9rZScpCiAgICAgICAgICAgICAgICAuYXR0cignZCcsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gcGF0aChkW2JpbnNQcm9wXSk7CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAuc3R5bGUoJ3N0cm9rZS13aWR0aCcsIDEpLCBvdXRsaW5lVHJhbnNpdGlvbiA9IGhpc3RvZ3JhbVRyYW5zaXRpb24KICAgICAgICAgICAgICAgIC5zZWxlY3QoJy5vdXRsaW5lJykKICAgICAgICAgICAgICAgIC5hdHRyKCd0cmFuc2Zvcm0nLCAnc2NhbGUoJyArCiAgICAgICAgICAgICAgICB3aWR0aCAvIG91dGxpbmVDYW52YXNTaXplICsKICAgICAgICAgICAgICAgICcsICcgKwogICAgICAgICAgICAgICAgc2xpY2VIZWlnaHQgLyBvdXRsaW5lQ2FudmFzU2l6ZSArCiAgICAgICAgICAgICAgICAnKScpCiAgICAgICAgICAgICAgICAuc3R5bGUoJ3N0cm9rZScsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbW9kZSA9PT0gJ29mZnNldCcgPyAnd2hpdGUnIDogb3V0bGluZUNvbG9yKHRpbWVBY2Nlc3NvcihkKSk7CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAuc3R5bGUoJ2ZpbGwtb3BhY2l0eScsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbW9kZSA9PT0gJ29mZnNldCcgPyAxIDogMDsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5zdHlsZSgnZmlsbCcsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gb3V0bGluZUNvbG9yKHRpbWVBY2Nlc3NvcihkKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB2YXIgaG92ZXJFbnRlciA9IGhpc3RvZ3JhbUVudGVyLmFwcGVuZCgnZycpLmF0dHIoJ2NsYXNzJywgJ2hvdmVyJyk7CiAgICAgICAgICAgIHZhciBob3ZlclVwZGF0ZSA9IGhpc3RvZ3JhbVVwZGF0ZQogICAgICAgICAgICAgICAgLnNlbGVjdCgnLmhvdmVyJykKICAgICAgICAgICAgICAgIC5zdHlsZSgnZmlsbCcsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gb3V0bGluZUNvbG9yKHRpbWVBY2Nlc3NvcihkKSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBob3ZlckVudGVyLmFwcGVuZCgnY2lyY2xlJykuYXR0cigncicsIDIpOwogICAgICAgICAgICBob3ZlckVudGVyLmFwcGVuZCgndGV4dCcpLnN0eWxlKCdkaXNwbGF5JywgJ25vbmUnKS5hdHRyKCdkeCcsIDQpOwogICAgICAgICAgICB2YXIgeEF4aXNIb3ZlciA9IGcuc2VsZWN0KCcueC1heGlzLWhvdmVyJykuc2VsZWN0QWxsKCcubGFiZWwnKS5kYXRhKFsneCddKSwgeEF4aXNIb3ZlckVudGVyID0geEF4aXNIb3Zlci5lbnRlcigpLmFwcGVuZCgnZycpLmF0dHIoJ2NsYXNzJywgJ2xhYmVsJyksIHhBeGlzSG92ZXJVcGRhdGUgPSB4QXhpc0hvdmVyLm1lcmdlKHhBeGlzSG92ZXJFbnRlcik7CiAgICAgICAgICAgIHhBeGlzSG92ZXJFbnRlcgogICAgICAgICAgICAgICAgLmFwcGVuZCgncmVjdCcpCiAgICAgICAgICAgICAgICAuYXR0cigneCcsIC0yMCkKICAgICAgICAgICAgICAgIC5hdHRyKCd5JywgNikKICAgICAgICAgICAgICAgIC5hdHRyKCd3aWR0aCcsIDQwKQogICAgICAgICAgICAgICAgLmF0dHIoJ2hlaWdodCcsIDE0KTsKICAgICAgICAgICAgeEF4aXNIb3ZlckVudGVyCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdsaW5lJykKICAgICAgICAgICAgICAgIC5hdHRyKCd4MScsIDApCiAgICAgICAgICAgICAgICAuYXR0cigneDInLCAwKQogICAgICAgICAgICAgICAgLmF0dHIoJ3kxJywgMCkKICAgICAgICAgICAgICAgIC5hdHRyKCd5MicsIDYpOwogICAgICAgICAgICB4QXhpc0hvdmVyRW50ZXIuYXBwZW5kKCd0ZXh0JykuYXR0cignZHknLCAxOCk7CiAgICAgICAgICAgIHZhciB5QXhpc0hvdmVyID0gZy5zZWxlY3QoJy55LWF4aXMtaG92ZXInKS5zZWxlY3RBbGwoJy5sYWJlbCcpLmRhdGEoWyd5J10pLCB5QXhpc0hvdmVyRW50ZXIgPSB5QXhpc0hvdmVyLmVudGVyKCkuYXBwZW5kKCdnJykuYXR0cignY2xhc3MnLCAnbGFiZWwnKSwgeUF4aXNIb3ZlclVwZGF0ZSA9IHlBeGlzSG92ZXIubWVyZ2UoeUF4aXNIb3ZlckVudGVyKTsKICAgICAgICAgICAgeUF4aXNIb3ZlckVudGVyCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdyZWN0JykKICAgICAgICAgICAgICAgIC5hdHRyKCd4JywgOCkKICAgICAgICAgICAgICAgIC5hdHRyKCd5JywgLTYpCiAgICAgICAgICAgICAgICAuYXR0cignd2lkdGgnLCA0MCkKICAgICAgICAgICAgICAgIC5hdHRyKCdoZWlnaHQnLCAxNCk7CiAgICAgICAgICAgIHlBeGlzSG92ZXJFbnRlcgogICAgICAgICAgICAgICAgLmFwcGVuZCgnbGluZScpCiAgICAgICAgICAgICAgICAuYXR0cigneDEnLCAwKQogICAgICAgICAgICAgICAgLmF0dHIoJ3gyJywgNikKICAgICAgICAgICAgICAgIC5hdHRyKCd5MScsIDApCiAgICAgICAgICAgICAgICAuYXR0cigneTInLCAwKTsKICAgICAgICAgICAgeUF4aXNIb3ZlckVudGVyLmFwcGVuZCgndGV4dCcpLmF0dHIoJ2R4JywgOCkuYXR0cignZHknLCA0KTsKICAgICAgICAgICAgdmFyIHlTbGljZUF4aXNIb3ZlciA9IGcKICAgICAgICAgICAgICAgIC5zZWxlY3QoJy55LXNsaWNlLWF4aXMtaG92ZXInKQogICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgnLmxhYmVsJykKICAgICAgICAgICAgICAgIC5kYXRhKFsneSddKSwgeVNsaWNlQXhpc0hvdmVyRW50ZXIgPSB5U2xpY2VBeGlzSG92ZXIKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5hdHRyKCdjbGFzcycsICdsYWJlbCcpLCB5U2xpY2VBeGlzSG92ZXJVcGRhdGUgPSB5U2xpY2VBeGlzSG92ZXIubWVyZ2UoeVNsaWNlQXhpc0hvdmVyRW50ZXIpOwogICAgICAgICAgICB5U2xpY2VBeGlzSG92ZXJFbnRlcgogICAgICAgICAgICAgICAgLmFwcGVuZCgncmVjdCcpCiAgICAgICAgICAgICAgICAuYXR0cigneCcsIDgpCiAgICAgICAgICAgICAgICAuYXR0cigneScsIC02KQogICAgICAgICAgICAgICAgLmF0dHIoJ3dpZHRoJywgNDApCiAgICAgICAgICAgICAgICAuYXR0cignaGVpZ2h0JywgMTQpOwogICAgICAgICAgICB5U2xpY2VBeGlzSG92ZXJFbnRlcgogICAgICAgICAgICAgICAgLmFwcGVuZCgnbGluZScpCiAgICAgICAgICAgICAgICAuYXR0cigneDEnLCAwKQogICAgICAgICAgICAgICAgLmF0dHIoJ3gyJywgNikKICAgICAgICAgICAgICAgIC5hdHRyKCd5MScsIDApCiAgICAgICAgICAgICAgICAuYXR0cigneTInLCAwKTsKICAgICAgICAgICAgeVNsaWNlQXhpc0hvdmVyRW50ZXIuYXBwZW5kKCd0ZXh0JykuYXR0cignZHgnLCA4KS5hdHRyKCdkeScsIDQpOwogICAgICAgICAgICBnVHJhbnNpdGlvbgogICAgICAgICAgICAgICAgLnNlbGVjdCgnLnkuYXhpcy5zbGljZScpCiAgICAgICAgICAgICAgICAuc3R5bGUoJ29wYWNpdHknLCBtb2RlID09PSAnb2Zmc2V0JyA/IDAgOiAxKQogICAgICAgICAgICAgICAgLmF0dHIoJ3RyYW5zZm9ybScsICd0cmFuc2xhdGUoMCwgJyArIChtb2RlID09PSAnb2Zmc2V0JyA/IC1zbGljZUhlaWdodCA6IDApICsgJyknKQogICAgICAgICAgICAgICAgLmNhbGwoeVNsaWNlQXhpcyk7CiAgICAgICAgICAgIGdUcmFuc2l0aW9uCiAgICAgICAgICAgICAgICAuc2VsZWN0KCcueC5heGlzJykKICAgICAgICAgICAgICAgIC5hdHRyKCd0cmFuc2Zvcm0nLCAndHJhbnNsYXRlKDAsICcgKyBoZWlnaHQgKyAnKScpCiAgICAgICAgICAgICAgICAuY2FsbCh4QXhpcyk7CiAgICAgICAgICAgIGdUcmFuc2l0aW9uCiAgICAgICAgICAgICAgICAuc2VsZWN0KCcueS5heGlzJykKICAgICAgICAgICAgICAgIC5zdHlsZSgnb3BhY2l0eScsIG1vZGUgPT09ICdvZmZzZXQnID8gMSA6IDApCiAgICAgICAgICAgICAgICAuYXR0cigndHJhbnNmb3JtJywgJ3RyYW5zbGF0ZSgnICsgd2lkdGggKyAnLCAnICsgKG1vZGUgPT09ICdvZmZzZXQnID8gMCA6IGhlaWdodCkgKyAnKScpCiAgICAgICAgICAgICAgICAuY2FsbCh5QXhpcyk7CiAgICAgICAgICAgIGdUcmFuc2l0aW9uLnNlbGVjdEFsbCgnLnRpY2sgdGV4dCcpLmF0dHIoJ2ZpbGwnLCAnI2FhYScpOwogICAgICAgICAgICBnVHJhbnNpdGlvbi5zZWxlY3RBbGwoJy5heGlzIHBhdGguZG9tYWluJykuYXR0cignc3Ryb2tlJywgJ25vbmUnKTsKICAgICAgICAgICAgZnVuY3Rpb24gb25Nb3VzZU1vdmUoKSB7CiAgICAgICAgICAgICAgICB2YXIgbSA9IGQzJDEubW91c2UodGhpcyksIHYgPSB4U2NhbGUuaW52ZXJ0KG1bMF0pLCB0ID0geVNjYWxlLmludmVydChtWzFdKTsKICAgICAgICAgICAgICAgIGZ1bmN0aW9uIGhvdmVyWEluZGV4KGQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gTWF0aC5taW4oZFtiaW5zUHJvcF0ubGVuZ3RoIC0gMSwgYmlzZWN0KGRbYmluc1Byb3BdLCB2KSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICB2YXIgY2xvc2VzdFNsaWNlRGF0YTsKICAgICAgICAgICAgICAgIHZhciBjbG9zZXN0U2xpY2VEaXN0YW5jZSA9IEluZmluaXR5OwogICAgICAgICAgICAgICAgdmFyIGxhc3RTbGljZURhdGE7CiAgICAgICAgICAgICAgICBob3ZlclVwZGF0ZS5hdHRyKCd0cmFuc2Zvcm0nLCBmdW5jdGlvbiAoZCwgaSkgewogICAgICAgICAgICAgICAgICAgIHZhciBpbmRleCA9IGhvdmVyWEluZGV4KGQpOwogICAgICAgICAgICAgICAgICAgIGxhc3RTbGljZURhdGEgPSBkOwogICAgICAgICAgICAgICAgICAgIHZhciB4ID0geFNjYWxlKGRbYmluc1Byb3BdW2luZGV4XVt4UHJvcF0gKyBkW2JpbnNQcm9wXVtpbmRleF1bZHhQcm9wXSAvIDIpOwogICAgICAgICAgICAgICAgICAgIHZhciB5ID0geVNsaWNlU2NhbGUoZFtiaW5zUHJvcF1baW5kZXhdW3lQcm9wXSk7CiAgICAgICAgICAgICAgICAgICAgdmFyIGdsb2JhbFkgPSBtb2RlID09PSAnb2Zmc2V0JyA/IHlTY2FsZSh0aW1lQWNjZXNzb3IoZCkpIC0gKHNsaWNlSGVpZ2h0IC0geSkgOiB5OwogICAgICAgICAgICAgICAgICAgIHZhciBkaXN0ID0gTWF0aC5hYnMobVsxXSAtIGdsb2JhbFkpOwogICAgICAgICAgICAgICAgICAgIGlmIChkaXN0IDwgY2xvc2VzdFNsaWNlRGlzdGFuY2UpIHsKICAgICAgICAgICAgICAgICAgICAgICAgY2xvc2VzdFNsaWNlRGlzdGFuY2UgPSBkaXN0OwogICAgICAgICAgICAgICAgICAgICAgICBjbG9zZXN0U2xpY2VEYXRhID0gZDsKICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICd0cmFuc2xhdGUoJyArIHggKyAnLCcgKyB5ICsgJyknOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBob3ZlclVwZGF0ZS5zZWxlY3QoJ3RleHQnKS50ZXh0KGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICAgICAgdmFyIGluZGV4ID0gaG92ZXJYSW5kZXgoZCk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGRbYmluc1Byb3BdW2luZGV4XVt5UHJvcF07CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGhvdmVyVXBkYXRlLmNsYXNzZWQoJ2hvdmVyLWNsb3Nlc3QnLCBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBkID09PSBjbG9zZXN0U2xpY2VEYXRhOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBvdXRsaW5lVXBkYXRlLmNsYXNzZWQoJ291dGxpbmUtaG92ZXInLCBmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBkID09PSBjbG9zZXN0U2xpY2VEYXRhOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB2YXIgaW5kZXggPSBob3ZlclhJbmRleChsYXN0U2xpY2VEYXRhKTsKICAgICAgICAgICAgICAgIHhBeGlzSG92ZXJVcGRhdGUKICAgICAgICAgICAgICAgICAgICAuYXR0cigndHJhbnNmb3JtJywgZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gKCd0cmFuc2xhdGUoJyArCiAgICAgICAgICAgICAgICAgICAgICAgIHhTY2FsZShsYXN0U2xpY2VEYXRhW2JpbnNQcm9wXVtpbmRleF1beFByb3BdICsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGxhc3RTbGljZURhdGFbYmluc1Byb3BdW2luZGV4XVtkeFByb3BdIC8gMikgKwogICAgICAgICAgICAgICAgICAgICAgICAnLCAnICsKICAgICAgICAgICAgICAgICAgICAgICAgaGVpZ2h0ICsKICAgICAgICAgICAgICAgICAgICAgICAgJyknKTsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLnNlbGVjdCgndGV4dCcpCiAgICAgICAgICAgICAgICAgICAgLnRleHQoZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZm9ybWF0KGxhc3RTbGljZURhdGFbYmluc1Byb3BdW2luZGV4XVt4UHJvcF0gKwogICAgICAgICAgICAgICAgICAgICAgICBsYXN0U2xpY2VEYXRhW2JpbnNQcm9wXVtpbmRleF1bZHhQcm9wXSAvIDIpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB2YXIgZnkgPSB5QXhpcy50aWNrRm9ybWF0KCk7CiAgICAgICAgICAgICAgICB5QXhpc0hvdmVyVXBkYXRlCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoJ3RyYW5zZm9ybScsIGZ1bmN0aW9uIChkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuICgndHJhbnNsYXRlKCcgKwogICAgICAgICAgICAgICAgICAgICAgICB3aWR0aCArCiAgICAgICAgICAgICAgICAgICAgICAgICcsICcgKwogICAgICAgICAgICAgICAgICAgICAgICAobW9kZSA9PT0gJ29mZnNldCcgPyB5U2NhbGUodGltZUFjY2Vzc29yKGNsb3Nlc3RTbGljZURhdGEpKSA6IDApICsKICAgICAgICAgICAgICAgICAgICAgICAgJyknKTsKICAgICAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAgICAgLnN0eWxlKCdkaXNwbGF5JywgbW9kZSA9PT0gJ29mZnNldCcgPyAnJyA6ICdub25lJykKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0KCd0ZXh0JykKICAgICAgICAgICAgICAgICAgICAudGV4dChmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBmeSh0aW1lQWNjZXNzb3IoY2xvc2VzdFNsaWNlRGF0YSkpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB2YXIgZnN5ID0geVNsaWNlQXhpcy50aWNrRm9ybWF0KCk7CiAgICAgICAgICAgICAgICB5U2xpY2VBeGlzSG92ZXJVcGRhdGUKICAgICAgICAgICAgICAgICAgICAuYXR0cigndHJhbnNmb3JtJywgZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gKCd0cmFuc2xhdGUoJyArCiAgICAgICAgICAgICAgICAgICAgICAgIHdpZHRoICsKICAgICAgICAgICAgICAgICAgICAgICAgJywgJyArCiAgICAgICAgICAgICAgICAgICAgICAgIChtb2RlID09PSAnb2Zmc2V0JwogICAgICAgICAgICAgICAgICAgICAgICAgICAgPyAwCiAgICAgICAgICAgICAgICAgICAgICAgICAgICA6IHlTbGljZVNjYWxlKGNsb3Nlc3RTbGljZURhdGFbYmluc1Byb3BdW2luZGV4XVt5UHJvcF0pKSArCiAgICAgICAgICAgICAgICAgICAgICAgICcpJyk7CiAgICAgICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgICAgIC5zdHlsZSgnZGlzcGxheScsIG1vZGUgPT09ICdvZmZzZXQnID8gJ25vbmUnIDogJycpCiAgICAgICAgICAgICAgICAgICAgLnNlbGVjdCgndGV4dCcpCiAgICAgICAgICAgICAgICAgICAgLnRleHQoZnVuY3Rpb24gKGQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gZnN5KGNsb3Nlc3RTbGljZURhdGFbYmluc1Byb3BdW2luZGV4XVt5UHJvcF0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB2YXIgc3ZnTW91c2UgPSBkMyQxLm1vdXNlKHN2Z05vZGUpOwogICAgICAgICAgICAgICAgdG9vbHRpcAogICAgICAgICAgICAgICAgICAgIC5zdHlsZSgndHJhbnNmb3JtJywgJ3RyYW5zbGF0ZSgnICsgKHN2Z01vdXNlWzBdICsgMTUpICsgJ3B4LCcgKyAoc3ZnTW91c2VbMV0gLSAxNSkgKyAncHgpJykKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0KCdzcGFuJykKICAgICAgICAgICAgICAgICAgICAudGV4dChtb2RlID09PSAnb2Zmc2V0JwogICAgICAgICAgICAgICAgICAgID8gZnN5KGNsb3Nlc3RTbGljZURhdGFbYmluc1Byb3BdW2luZGV4XVt5UHJvcF0pCiAgICAgICAgICAgICAgICAgICAgOiAodGltZVByb3AgPT09ICdzdGVwJyA/ICdzdGVwICcgOiAnJykgKwogICAgICAgICAgICAgICAgICAgICAgICBmeSh0aW1lQWNjZXNzb3IoY2xvc2VzdFNsaWNlRGF0YSkpKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIH07CiAgICBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJ0b29sdGlwIj48c3Bhbj48L3NwYW4+PC9kaXY+CiAgICA8c3ZnIGlkPSJzdmciPgogICAgICA8Zz4KICAgICAgICA8ZyBjbGFzcz0iYXhpcyB4Ij48L2c+CiAgICAgICAgPGcgY2xhc3M9ImF4aXMgeSI+PC9nPgogICAgICAgIDxnIGNsYXNzPSJheGlzIHkgc2xpY2UiPjwvZz4KICAgICAgICA8ZyBjbGFzcz0ic3RhZ2UiPgogICAgICAgICAgPHJlY3QgY2xhc3M9ImJhY2tncm91bmQiPjwvcmVjdD4KICAgICAgICA8L2c+CiAgICAgICAgPGcgY2xhc3M9IngtYXhpcy1ob3ZlciI+PC9nPgogICAgICAgIDxnIGNsYXNzPSJ5LWF4aXMtaG92ZXIiPjwvZz4KICAgICAgICA8ZyBjbGFzcz0ieS1zbGljZS1heGlzLWhvdmVyIj48L2c+CiAgICAgIDwvZz4KICAgIDwvc3ZnPgoKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICB9CgogICAgICBzdmcgewogICAgICAgIGZvbnQtZmFtaWx5OiByb2JvdG8sIHNhbnMtc2VyaWY7CiAgICAgICAgb3ZlcmZsb3c6IHZpc2libGU7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICAgIGZsZXgtc2hyaW5rOiAxOwogICAgICB9CgogICAgICAjdG9vbHRpcCB7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgZm9udC13ZWlnaHQ6IGJvbGQ7CiAgICAgICAgZm9udC1zaXplOiAxMXB4OwogICAgICB9CgogICAgICAuYmFja2dyb3VuZCB7CiAgICAgICAgZmlsbC1vcGFjaXR5OiAwOwogICAgICAgIGZpbGw6IHJlZDsKICAgICAgfQoKICAgICAgLmhpc3RvZ3JhbSB7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgIH0KCiAgICAgIC5ob3ZlciB7CiAgICAgICAgZm9udC1zaXplOiA5cHg7CiAgICAgICAgZG9taW5hbnQtYmFzZWxpbmU6IG1pZGRsZTsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICB9CgogICAgICAuaG92ZXIgY2lyY2xlIHsKICAgICAgICBzdHJva2U6IHdoaXRlOwogICAgICAgIHN0cm9rZS1vcGFjaXR5OiAwLjU7CiAgICAgICAgc3Ryb2tlLXdpZHRoOiAxcHg7CiAgICAgIH0KCiAgICAgIC5ob3ZlciB0ZXh0IHsKICAgICAgICBmaWxsOiBibGFjazsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICB9CgogICAgICAuaG92ZXIuaG92ZXItY2xvc2VzdCBjaXJjbGUgewogICAgICAgIGZpbGw6IGJsYWNrICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC5ob3Zlci5ob3Zlci1jbG9zZXN0IHRleHQgewogICAgICAgIG9wYWNpdHk6IDE7CiAgICAgIH0KCiAgICAgIC5iYXNlbGluZSB7CiAgICAgICAgc3Ryb2tlOiBibGFjazsKICAgICAgICBzdHJva2Utb3BhY2l0eTogMC4xOwogICAgICB9CgogICAgICAub3V0bGluZSB7CiAgICAgICAgZmlsbDogbm9uZTsKICAgICAgICBzdHJva2U6IHdoaXRlOwogICAgICAgIHN0cm9rZS1vcGFjaXR5OiAwLjU7CiAgICAgIH0KCiAgICAgIC5vdXRsaW5lLm91dGxpbmUtaG92ZXIgewogICAgICAgIHN0cm9rZTogYmxhY2sgIWltcG9ydGFudDsKICAgICAgICBzdHJva2Utb3BhY2l0eTogMTsKICAgICAgfQoKICAgICAgLngtYXhpcy1ob3ZlciwKICAgICAgLnktYXhpcy1ob3ZlciwKICAgICAgLnktc2xpY2UtYXhpcy1ob3ZlciB7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgIH0KCiAgICAgIC54LWF4aXMtaG92ZXIgLmxhYmVsLAogICAgICAueS1heGlzLWhvdmVyIC5sYWJlbCwKICAgICAgLnktc2xpY2UtYXhpcy1ob3ZlciAubGFiZWwgewogICAgICAgIG9wYWNpdHk6IDA7CiAgICAgICAgZm9udC13ZWlnaHQ6IGJvbGQ7CiAgICAgICAgZm9udC1zaXplOiAxMXB4OwogICAgICAgIHRleHQtYW5jaG9yOiBlbmQ7CiAgICAgIH0KCiAgICAgIC54LWF4aXMtaG92ZXIgdGV4dCB7CiAgICAgICAgdGV4dC1hbmNob3I6IG1pZGRsZTsKICAgICAgfQoKICAgICAgLnktYXhpcy1ob3ZlciB0ZXh0LAogICAgICAueS1zbGljZS1heGlzLWhvdmVyIHRleHQgewogICAgICAgIHRleHQtYW5jaG9yOiBzdGFydDsKICAgICAgfQoKICAgICAgLngtYXhpcy1ob3ZlciBsaW5lLAogICAgICAueS1heGlzLWhvdmVyIGxpbmUsCiAgICAgIC55LXNsaWNlLWF4aXMtaG92ZXIgbGluZSB7CiAgICAgICAgc3Ryb2tlOiBibGFjazsKICAgICAgfQoKICAgICAgLngtYXhpcy1ob3ZlciByZWN0LAogICAgICAueS1heGlzLWhvdmVyIHJlY3QsCiAgICAgIC55LXNsaWNlLWF4aXMtaG92ZXIgcmVjdCB7CiAgICAgICAgZmlsbDogd2hpdGU7CiAgICAgIH0KCiAgICAgIC5heGlzIHsKICAgICAgICBmb250LXNpemU6IDExcHg7CiAgICAgIH0KCiAgICAgIC5heGlzIHBhdGguZG9tYWluIHsKICAgICAgICBmaWxsOiBub25lOwogICAgICB9CgogICAgICAuYXhpcyAudGljayBsaW5lIHsKICAgICAgICBzdHJva2U6ICNkZGQ7CiAgICAgIH0KCiAgICAgIC5heGlzLnNsaWNlIHsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICB9CgogICAgICAuYXhpcy5zbGljZSAudGljayBsaW5lIHsKICAgICAgICBzdHJva2UtZGFzaGFycmF5OiAyOwogICAgICB9CgogICAgICAuc21hbGwgLmF4aXMgdGV4dCB7CiAgICAgICAgZGlzcGxheTogbm9uZTsKICAgICAgfQogICAgICAuc21hbGwgLmF4aXMgLnRpY2s6Zmlyc3Qtb2YtdHlwZSB0ZXh0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQogICAgICAuc21hbGwgLmF4aXMgLnRpY2s6bGFzdC1vZi10eXBlIHRleHQgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CiAgICAgIC5tZWRpdW0gLmF4aXMgdGV4dCB7CiAgICAgICAgZGlzcGxheTogbm9uZTsKICAgICAgfQogICAgICAubWVkaXVtIC5heGlzIC50aWNrOm50aC1jaGlsZCgybiArIDEpIHRleHQgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CiAgICAgIC5sYXJnZSAuYXhpcyB0ZXh0IHsKICAgICAgICBkaXNwbGF5OiBub25lOwogICAgICB9CiAgICAgIC5sYXJnZSAuYXhpcyAudGljazpudGgtY2hpbGQoMm4gKyAxKSB0ZXh0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgIm1vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgInRpbWVQcm9wZXJ0eSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMucHJvdG90eXBlLCAiYmlucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMucHJvdG90eXBlLCAieCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMucHJvdG90eXBlLCAiZHgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgInkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgImNvbG9yU2NhbGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgIm1vZGVUcmFuc2l0aW9uRHVyYXRpb24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMucHJvdG90eXBlLCAiX2F0dGFjaGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1Z6SGlzdG9ncmFtVGltZXNlcmllcy5wcm90b3R5cGUsICJfbmFtZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzLnByb3RvdHlwZSwgIl9kYXRhIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3RpbWVQcm9wZXJ0eScsICdjb2xvclNjYWxlJywgJ19hdHRhY2hlZCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgX1Z6SGlzdG9ncmFtVGltZXNlcmllcy5wcm90b3R5cGUsICJfcmVkcmF3T25DaGFuZ2UiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ21vZGUnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMucHJvdG90eXBlLCAiX21vZGVSZWRyYXciLCBudWxsKTsKICAgIF9Wekhpc3RvZ3JhbVRpbWVzZXJpZXMgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd2ei1oaXN0b2dyYW0tdGltZXNlcmllcycpCiAgICBdLCBfVnpIaXN0b2dyYW1UaW1lc2VyaWVzKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNSBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGZ1bmN0aW9uIGJhY2tlbmRUb0ludGVybWVkaWF0ZShoaXN0b2dyYW0pIHsKICAgICAgICBjb25zdCBbd2FsbF90aW1lLCBzdGVwLCBidWNrZXRzXSA9IGhpc3RvZ3JhbTsKICAgICAgICByZXR1cm4gewogICAgICAgICAgICB3YWxsX3RpbWUsCiAgICAgICAgICAgIHN0ZXAsCiAgICAgICAgICAgIG1pbjogbWluKGJ1Y2tldHMubWFwKChbbGVmdCwgLF0pID0+IGxlZnQpKSwKICAgICAgICAgICAgbWF4OiBtYXgoYnVja2V0cy5tYXAoKFssIHJpZ2h0XSkgPT4gcmlnaHQpKSwKICAgICAgICAgICAgYnVja2V0czogYnVja2V0cy5tYXAoKFtsZWZ0LCByaWdodCwgY291bnRdKSA9PiAoeyBsZWZ0LCByaWdodCwgY291bnQgfSkpLAogICAgICAgIH07CiAgICB9CiAgICAvKioKICAgICAqIENvbnZlcnQgaGlzdG9ncmFtIGRhdGEgdG8gdGhlIHN0YW5kYXJkIEQzIGZvcm1hdCB0byBtYWtlIGl0IG1vcmUKICAgICAqIGNvbXBhdGlibGUgYW5kIGVhc2llciB0byB2aXN1YWxpemUuIFdoZW4gcmVuZGVyaW5nIGhpc3RvZ3JhbXMsIGhhdmluZwogICAgICogYWNjZXNzIHRvIHRoZSBsZWZ0IGVkZ2UgYW5kIHdpZHRoIG9mIGVhY2ggYmluIG1ha2VzIHRoaW5ncyBxdWl0ZSBhCiAgICAgKiBiaXQgZWFzaWVyLCBzbyB3ZSBpbmNsdWRlIHRoZXNlIGluIHRoZSByZXN1bHQuIFdlIGFsc28gY29udmVydCB0aGUKICAgICAqIGJpbnMgdG8gaGF2ZSBhIHVuaWZvcm0gd2lkdGgsIHdoaWNoIG1ha2VzIHRoZSB2aXN1YWxpemF0aW9uIGVhc2llciB0bwogICAgICogdW5kZXJzdGFuZC4KICAgICAqCiAgICAgKiBAcGFyYW0gaGlzdG9ncmFtCiAgICAgKiBAcGFyYW0gbWluIFRoZSBsZWZ0bW9zdCBlZGdlLiBUaGUgYmlubmluZyB3aWxsIHN0YXJ0IG9uIGl0LgogICAgICogQHBhcmFtIG1heCBUaGUgcmlnaHRtb3N0IGVkZ2UuIFRoZSBiaW5uaW5nIHdpbGwgZW5kIG9uIGl0LgogICAgICogQHBhcmFtIG51bUJpbnMgVGhlIG51bWJlciBvZiBiaW5zIG9mIHRoZSBjb252ZXJ0ZWQgZGF0YS4gVGhlIGRlZmF1bHQKICAgICAqIG9mIDMwIGlzIHNlbnNpYmxlOiBpZiB5b3UgdXNlIG1vcmUsIHlvdSBzdGFydCB0byBnZXQgYXJ0aWZhY3RzCiAgICAgKiBiZWNhdXNlIHRoZSBldmVudCBkYXRhIGlzIHN0b3JlZCBpbiBidWNrZXRzLCBhbmQgeW91IHN0YXJ0IGJlaW5nIGFibGUKICAgICAqIHRvIHNlZSB0aGUgYWxpYXNlZCBib3JkZXJzIGJldHdlZW4gZWFjaCBidWNrZXQuCiAgICAgKgogICAgICogQHJldHVybiBBIGxpc3Qgb2YgaGlzdG9ncmFtIGJpbnMuIEVhY2ggYmluIGhhcyBhbiBgeGAgKGxlZnQKICAgICAqICAgICBlZGdlKSwgYSBgZHhgICh3aWR0aCksIGFuZCBhIGB5YCAoY291bnQpLiBJZiB0aGUgZ2l2ZW4KICAgICAqICAgICByaWdodCBlZGdlcyBhcmUgaW5jbHVzaXZlLCB0aGVuIHRoZXNlIGxlZnQgZWRnZXMgKGB4YCkgYXJlCiAgICAgKiAgICAgZXhjbHVzaXZlLgogICAgICovCiAgICBmdW5jdGlvbiBpbnRlcm1lZGlhdGVUb0QzKGhpc3RvZ3JhbSwgbWluLCBtYXgsIG51bUJpbnMgPSAzMCkgewogICAgICAgIGlmIChtYXggPT09IG1pbikgewogICAgICAgICAgICAvLyBDcmVhdGUgYmlucyBldmVuIGlmIGFsbCB0aGUgZGF0YSBoYXMgYSBzaW5nbGUgdmFsdWUuCiAgICAgICAgICAgIG1heCA9IG1pbiAqIDEuMSArIDE7CiAgICAgICAgICAgIG1pbiA9IG1pbiAvIDEuMSAtIDE7CiAgICAgICAgfQogICAgICAgIC8vIFRlcm1pbm9sb2d5IG5vdGU6IF9idWNrZXRzXyBhcmUgdGhlIGlucHV0IHRvIHRoaXMgZnVuY3Rpb24sCiAgICAgICAgLy8gd2hpbGUgX2JpbnNfIGFyZSBvdXIgb3V0cHV0LgogICAgICAgIGNvbnN0IGJpbldpZHRoID0gKG1heCAtIG1pbikgLyBudW1CaW5zOwogICAgICAgIGxldCBidWNrZXRJbmRleCA9IDA7CiAgICAgICAgcmV0dXJuIHNlcXVlbmNlKG1pbiwgbWF4LCBiaW5XaWR0aCkubWFwKChiaW5MZWZ0KSA9PiB7CiAgICAgICAgICAgIGNvbnN0IGJpblJpZ2h0ID0gYmluTGVmdCArIGJpbldpZHRoOwogICAgICAgICAgICAvLyBUYWtlIHRoZSBjb3VudCBvZiBlYWNoIGV4aXN0aW5nIGJ1Y2tldCwgbXVsdGlwbHkgaXQgYnkgdGhlCiAgICAgICAgICAgIC8vIHByb3BvcnRpb24gb2Ygb3ZlcmxhcCB3aXRoIHRoZSBuZXcgYmluLCB0aGVuIHN1bSBhbmQgc3RvcmUgYXMgdGhlCiAgICAgICAgICAgIC8vIGNvdW50IGZvciB0aGUgbmV3IGJpbi4gSWYgbm8gb3ZlcmxhcCwgd2lsbCBhZGQgdG8gemVybzsgaWYgMTAwJQogICAgICAgICAgICAvLyBvdmVybGFwLCB3aWxsIGluY2x1ZGUgdGhlIGZ1bGwgY291bnQgaW50byBuZXcgYmluLgogICAgICAgICAgICBsZXQgYmluWSA9IDA7CiAgICAgICAgICAgIHdoaWxlIChidWNrZXRJbmRleCA8IGhpc3RvZ3JhbS5idWNrZXRzLmxlbmd0aCkgewogICAgICAgICAgICAgICAgLy8gQ2xpcCB0aGUgcmlnaHQgZWRnZSBiZWNhdXNlIHJpZ2h0LW1vc3QgZWRnZSBjYW4gYmUKICAgICAgICAgICAgICAgIC8vIGluZmluaXRlLXNpemVkLgogICAgICAgICAgICAgICAgY29uc3QgYnVja2V0UmlnaHQgPSBNYXRoLm1pbihtYXgsIGhpc3RvZ3JhbS5idWNrZXRzW2J1Y2tldEluZGV4XS5yaWdodCk7CiAgICAgICAgICAgICAgICBjb25zdCBidWNrZXRMZWZ0ID0gTWF0aC5tYXgobWluLCBoaXN0b2dyYW0uYnVja2V0c1tidWNrZXRJbmRleF0ubGVmdCk7CiAgICAgICAgICAgICAgICBjb25zdCBpbnRlcnNlY3QgPSBNYXRoLm1pbihidWNrZXRSaWdodCwgYmluUmlnaHQpIC0gTWF0aC5tYXgoYnVja2V0TGVmdCwgYmluTGVmdCk7CiAgICAgICAgICAgICAgICBjb25zdCBjb3VudCA9IChpbnRlcnNlY3QgLyAoYnVja2V0UmlnaHQgLSBidWNrZXRMZWZ0KSkgKgogICAgICAgICAgICAgICAgICAgIGhpc3RvZ3JhbS5idWNrZXRzW2J1Y2tldEluZGV4XS5jb3VudDsKICAgICAgICAgICAgICAgIGJpblkgKz0gaW50ZXJzZWN0ID4gMCA/IGNvdW50IDogMDsKICAgICAgICAgICAgICAgIC8vIElmIGBidWNrZXRSaWdodGAgaXMgYmlnZ2VyIHRoYW4gYGJpblJpZ2h0YCwgdGhlbiB0aGlzIGJpbiBpcwogICAgICAgICAgICAgICAgLy8gZmluaXNoZWQgYW5kIHRoZXJlIGlzIGRhdGEgZm9yIHRoZSBuZXh0IGJpbiwgc28gZG9uJ3QgaW5jcmVtZW50CiAgICAgICAgICAgICAgICAvLyBgYnVja2V0SW5kZXhgLgogICAgICAgICAgICAgICAgaWYgKGJ1Y2tldFJpZ2h0ID4gYmluUmlnaHQpIHsKICAgICAgICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGJ1Y2tldEluZGV4Kys7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsgeDogYmluTGVmdCwgZHg6IGJpbldpZHRoLCB5OiBiaW5ZIH07CiAgICAgICAgfSk7CiAgICB9CiAgICBmdW5jdGlvbiBiYWNrZW5kVG9WeihoaXN0b2dyYW1zKSB7CiAgICAgICAgY29uc3QgaW50ZXJtZWRpYXRlSGlzdG9ncmFtcyA9IGhpc3RvZ3JhbXMubWFwKGJhY2tlbmRUb0ludGVybWVkaWF0ZSk7CiAgICAgICAgY29uc3QgbWlubWluID0gbWluKGludGVybWVkaWF0ZUhpc3RvZ3JhbXMsIChoKSA9PiBoLm1pbik7CiAgICAgICAgY29uc3QgbWF4bWF4ID0gbWF4KGludGVybWVkaWF0ZUhpc3RvZ3JhbXMsIChoKSA9PiBoLm1heCk7CiAgICAgICAgcmV0dXJuIGludGVybWVkaWF0ZUhpc3RvZ3JhbXMubWFwKChoKSA9PiAoewogICAgICAgICAgICB3YWxsX3RpbWU6IGgud2FsbF90aW1lLAogICAgICAgICAgICBzdGVwOiBoLnN0ZXAsCiAgICAgICAgICAgIGJpbnM6IGludGVybWVkaWF0ZVRvRDMoaCwgbWlubWluLCBtYXhtYXgpLAogICAgICAgIH0pKTsKICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBfVGZIaXN0b2dyYW1Mb2FkZXIgPSBjbGFzcyBfVGZIaXN0b2dyYW1Mb2FkZXIgZXh0ZW5kcyBEYXRhTG9hZGVyQmVoYXZpb3IoTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICB0aGlzLmdldERhdGFMb2FkTmFtZSA9ICh7IHJ1biB9KSA9PiBydW47CiAgICAgICAgICAgIHRoaXMucmVxdWVzdERhdGEgPSAoaXRlbXMsIG9uTG9hZCwgb25GaW5pc2gpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IHJvdXRlciA9IGdldFJvdXRlcigpOwogICAgICAgICAgICAgICAgY29uc3QgYmFzZVVybCA9IHJvdXRlci5wbHVnaW5Sb3V0ZSgnaGlzdG9ncmFtcycsICcvaGlzdG9ncmFtcycpOwogICAgICAgICAgICAgICAgUHJvbWlzZS5hbGwoaXRlbXMubWFwKChpdGVtKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgdXJsID0gYWRkUGFyYW1zKGJhc2VVcmwsIHsgdGFnOiBpdGVtLnRhZywgcnVuOiBpdGVtLnJ1biB9KTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5yZXF1ZXN0TWFuYWdlcgogICAgICAgICAgICAgICAgICAgICAgICAucmVxdWVzdCh1cmwpCiAgICAgICAgICAgICAgICAgICAgICAgIC50aGVuKChkYXRhKSA9PiB2b2lkIG9uTG9hZCh7IGl0ZW0sIGRhdGEgfSkpOwogICAgICAgICAgICAgICAgfSkpLmZpbmFsbHkoKCkgPT4gdm9pZCBvbkZpbmlzaCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5sb2FkRGF0YUNhbGxiYWNrID0gKF8sIGRhdHVtLCBkYXRhKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBkM0RhdGEgPSBiYWNrZW5kVG9WeihkYXRhKTsKICAgICAgICAgICAgICAgIGNvbnN0IG5hbWUgPSB0aGlzLmdldERhdGFMb2FkTmFtZShkYXR1bSk7CiAgICAgICAgICAgICAgICB0aGlzLiQuY2hhcnQuc2V0U2VyaWVzRGF0YShuYW1lLCBkM0RhdGEpOwogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLl9jb2xvclNjYWxlRnVuY3Rpb24gPSBydW5zQ29sb3JTY2FsZTsKICAgICAgICAgICAgdGhpcy5fZXhwYW5kZWQgPSBmYWxzZTsKICAgICAgICB9CiAgICAgICAgX3JlbG9hZE9uUnVuVGFnUmVxdWVzdE1hbmFnZXJDaGFuZ2UoKSB7CiAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgfQogICAgICAgIF91cGRhdGVEYXRhVG9Mb2FkKCkgewogICAgICAgICAgICB2YXIgcnVuID0gdGhpcy5ydW47CiAgICAgICAgICAgIHZhciB0YWcgPSB0aGlzLnRhZzsKICAgICAgICAgICAgdGhpcy5kYXRhVG9Mb2FkID0gW3sgcnVuLCB0YWcgfV07CiAgICAgICAgfQogICAgICAgIGdldCBfcnVuQ29sb3IoKSB7CiAgICAgICAgICAgIHZhciBydW4gPSB0aGlzLnJ1bjsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbG9yU2NhbGVGdW5jdGlvbihydW4pOwogICAgICAgIH0KICAgICAgICByZWRyYXcoKSB7CiAgICAgICAgICAgIHRoaXMuJC5jaGFydC5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUV4cGFuZGVkKGUpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19leHBhbmRlZCcsICF0aGlzLl9leHBhbmRlZCk7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgfQogICAgfTsKICAgIF9UZkhpc3RvZ3JhbUxvYWRlci50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWNhcmQtaGVhZGluZwogICAgICB0YWc9IltbdGFnXV0iCiAgICAgIHJ1bj0iW1tydW5dXSIKICAgICAgZGlzcGxheS1uYW1lPSJbW3RhZ01ldGFkYXRhLmRpc3BsYXlOYW1lXV0iCiAgICAgIGRlc2NyaXB0aW9uPSJbW3RhZ01ldGFkYXRhLmRlc2NyaXB0aW9uXV0iCiAgICAgIGNvbG9yPSJbW19ydW5Db2xvcl1dIgogICAgPjwvdGYtY2FyZC1oZWFkaW5nPgogICAgPCEtLQogICAgICBUaGUgbWFpbiBoaXN0b2dyYW0gdGhhdCB3ZSByZW5kZXIuIERhdGEgaXMgc2V0IGRpcmVjdGx5IHdpdGgKICAgICAgXGBzZXRTZXJpZXNEYXRhXGAsIG5vdCB3aXRoIGEgYm91bmQgcHJvcGVydHkuCiAgICAtLT4KICAgIDx2ei1oaXN0b2dyYW0tdGltZXNlcmllcwogICAgICBpZD0iY2hhcnQiCiAgICAgIHRpbWUtcHJvcGVydHk9IltbdGltZVByb3BlcnR5XV0iCiAgICAgIG1vZGU9IltbaGlzdG9ncmFtTW9kZV1dIgogICAgICBjb2xvci1zY2FsZT0iW1tfY29sb3JTY2FsZUZ1bmN0aW9uXV0iCiAgICA+PC92ei1oaXN0b2dyYW0tdGltZXNlcmllcz4KICAgIDxkaXYgc3R5bGU9ImRpc3BsYXk6IGZsZXg7IGZsZXgtZGlyZWN0aW9uOiByb3c7Ij4KICAgICAgPHBhcGVyLWljb24tYnV0dG9uCiAgICAgICAgc2VsZWN0ZWQkPSJbW19leHBhbmRlZF1dIgogICAgICAgIGljb249ImZ1bGxzY3JlZW4iCiAgICAgICAgb24tdGFwPSJfdG9nZ2xlRXhwYW5kZWQiCiAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47CiAgICAgICAgd2lkdGg6IDMzMHB4OwogICAgICAgIGhlaWdodDogMjM1cHg7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiAxMHB4OwogICAgICAgIG1hcmdpbi1ib3R0b206IDE1cHg7CiAgICAgIH0KICAgICAgOmhvc3QoW19leHBhbmRlZF0pIHsKICAgICAgICB3aWR0aDogNzAwcHg7CiAgICAgICAgaGVpZ2h0OiA1MDBweDsKICAgICAgfQoKICAgICAgdnotaGlzdG9ncmFtLXRpbWVzZXJpZXMgewogICAgICAgIC1tb3otdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLXdlYmtpdC11c2VyLXNlbGVjdDogbm9uZTsKICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtOwogICAgICB9CgogICAgICBwYXBlci1pY29uLWJ1dHRvbiB7CiAgICAgICAgY29sb3I6ICMyMTk2ZjM7CiAgICAgICAgYm9yZGVyLXJhZGl1czogMTAwJTsKICAgICAgICB3aWR0aDogMzJweDsKICAgICAgICBoZWlnaHQ6IDMycHg7CiAgICAgICAgcGFkZGluZzogNHB4OwogICAgICB9CgogICAgICBwYXBlci1pY29uLWJ1dHRvbltzZWxlY3RlZF0gewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXRiLXVpLWxpZ2h0LWFjY2VudCk7CiAgICAgIH0KCiAgICAgIHRmLWNhcmQtaGVhZGluZyB7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMTBweDsKICAgICAgICB3aWR0aDogOTAlOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIF9UZkhpc3RvZ3JhbUxvYWRlci5wcm90b3R5cGUsICJydW4iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZIaXN0b2dyYW1Mb2FkZXIucHJvdG90eXBlLCAidGFnIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyLnByb3RvdHlwZSwgImdldERhdGFMb2FkTmFtZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFJlcXVlc3RNYW5hZ2VyKQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyLnByb3RvdHlwZSwgInJlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyLnByb3RvdHlwZSwgImxvYWREYXRhQ2FsbGJhY2siLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBfVGZIaXN0b2dyYW1Mb2FkZXIucHJvdG90eXBlLCAidGFnTWV0YWRhdGEiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBfVGZIaXN0b2dyYW1Mb2FkZXIucHJvdG90eXBlLCAidGltZVByb3BlcnR5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyLnByb3RvdHlwZSwgImhpc3RvZ3JhbU1vZGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbikKICAgIF0sIF9UZkhpc3RvZ3JhbUxvYWRlci5wcm90b3R5cGUsICJfY29sb3JTY2FsZUZ1bmN0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiwgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIF9UZkhpc3RvZ3JhbUxvYWRlci5wcm90b3R5cGUsICJfZXhwYW5kZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgncnVuJywgJ3RhZycsICdyZXF1ZXN0TWFuYWdlcicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyLnByb3RvdHlwZSwgIl9yZWxvYWRPblJ1blRhZ1JlcXVlc3RNYW5hZ2VyQ2hhbmdlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdydW4nLCAndGFnJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBfVGZIaXN0b2dyYW1Mb2FkZXIucHJvdG90eXBlLCAiX3VwZGF0ZURhdGFUb0xvYWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdydW4nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIF9UZkhpc3RvZ3JhbUxvYWRlci5wcm90b3R5cGUsICJfcnVuQ29sb3IiLCBudWxsKTsKICAgIF9UZkhpc3RvZ3JhbUxvYWRlciA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhpc3RvZ3JhbS1sb2FkZXInKQogICAgXSwgX1RmSGlzdG9ncmFtTG9hZGVyKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBUZkhpc3RvZ3JhbURhc2hib2FyZCA9IGNsYXNzIFRmSGlzdG9ncmFtRGFzaGJvYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMucmVsb2FkT25SZWFkeSA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX2hpc3RvZ3JhbU1vZGUgPSAnb2Zmc2V0JzsKICAgICAgICAgICAgdGhpcy5fdGltZVByb3BlcnR5ID0gJ3N0ZXAnOwogICAgICAgICAgICB0aGlzLl9yZXN0YW1wID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RNYW5hZ2VyID0gbmV3IFJlcXVlc3RNYW5hZ2VyKCk7CiAgICAgICAgfQogICAgICAgIF9yZWRyYXdDYXRlZ29yeVBhbmUoZXZlbnQsIHZhbCkgewogICAgICAgICAgICBpZiAoIXZhbCkKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgZXZlbnQudGFyZ2V0CiAgICAgICAgICAgICAgICAucXVlcnlTZWxlY3RvckFsbCgndGYtaGlzdG9ncmFtLWxvYWRlcicpCiAgICAgICAgICAgICAgICAuZm9yRWFjaCgoaGlzdG9ncmFtKSA9PiBoaXN0b2dyYW0ucmVkcmF3KCkpOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgaWYgKHRoaXMucmVsb2FkT25SZWFkeSkKICAgICAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgfQogICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgdGhpcy5fZmV0Y2hUYWdzKCkudGhlbigoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9yZWxvYWRIaXN0b2dyYW1zKCk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfZmV0Y2hUYWdzKCkgewogICAgICAgICAgICBjb25zdCB1cmwgPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnaGlzdG9ncmFtcycsICcvdGFncycpOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwpLnRoZW4oKHJ1blRvVGFnSW5mbykgPT4gewogICAgICAgICAgICAgICAgaWYgKGxvZGFzaC5pc0VxdWFsKHJ1blRvVGFnSW5mbywgdGhpcy5fcnVuVG9UYWdJbmZvKSkgewogICAgICAgICAgICAgICAgICAgIC8vIE5vIG5lZWQgdG8gdXBkYXRlIGFueXRoaW5nIGlmIHRoZXJlIGFyZSBubyBjaGFuZ2VzLgogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNvbnN0IHJ1blRvVGFnID0gbG9kYXNoLm1hcFZhbHVlcyhydW5Ub1RhZ0luZm8sICh4KSA9PiBPYmplY3Qua2V5cyh4KSk7CiAgICAgICAgICAgICAgICBjb25zdCB0YWdzID0gZ2V0VGFncyhydW5Ub1RhZyk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX2RhdGFOb3RGb3VuZCcsIHRhZ3MubGVuZ3RoID09PSAwKTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfcnVuVG9UYWcnLCBydW5Ub1RhZyk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3J1blRvVGFnSW5mbycsIHJ1blRvVGFnSW5mbyk7CiAgICAgICAgICAgICAgICB0aGlzLmFzeW5jKCgpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBTZWUgdGhlIGNvbW1lbnQgYWJvdmUgYF9jYXRlZ29yaWVzRG9tUmVhZHlgLgogICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfY2F0ZWdvcmllc0RvbVJlYWR5JywgdHJ1ZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9yZWxvYWRIaXN0b2dyYW1zKCkgewogICAgICAgICAgICB0aGlzLnJvb3QucXVlcnlTZWxlY3RvckFsbCgndGYtaGlzdG9ncmFtLWxvYWRlcicpLmZvckVhY2goKGhpc3RvZ3JhbSkgPT4gewogICAgICAgICAgICAgICAgaGlzdG9ncmFtLnJlbG9hZCgpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX3Nob3VsZE9wZW4oaW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIGluZGV4IDw9IDI7CiAgICAgICAgfQogICAgICAgIGdldCBfY2F0ZWdvcmllcygpIHsKICAgICAgICAgICAgdmFyIHJ1blRvVGFnID0gdGhpcy5fcnVuVG9UYWc7CiAgICAgICAgICAgIHZhciBzZWxlY3RlZFJ1bnMgPSB0aGlzLl9zZWxlY3RlZFJ1bnM7CiAgICAgICAgICAgIHZhciB0YWdGaWx0ZXIgPSB0aGlzLl90YWdGaWx0ZXI7CiAgICAgICAgICAgIHZhciBjYXRlZ29yaWVzRG9tUmVhZHkgPSB0aGlzLl9jYXRlZ29yaWVzRG9tUmVhZHk7CiAgICAgICAgICAgIHJldHVybiBjYXRlZ29yaXplUnVuVGFnQ29tYmluYXRpb25zKHJ1blRvVGFnLCBzZWxlY3RlZFJ1bnMsIHRhZ0ZpbHRlcik7CiAgICAgICAgfQogICAgICAgIF90YWdNZXRhZGF0YShydW5Ub1RhZ0luZm8sIHJ1biwgdGFnKSB7CiAgICAgICAgICAgIHJldHVybiBydW5Ub1RhZ0luZm9bcnVuXVt0YWddOwogICAgICAgIH0KICAgIH07CiAgICBUZkhpc3RvZ3JhbURhc2hib2FyZC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWRhc2hib2FyZC1sYXlvdXQ+CiAgICAgIDxkaXYgc2xvdD0ic2lkZWJhciI+CiAgICAgICAgPGRpdiBjbGFzcz0ic2V0dGluZ3MiPgogICAgICAgICAgPGRpdiBjbGFzcz0ic2lkZWJhci1zZWN0aW9uIj4KICAgICAgICAgICAgPHRmLW9wdGlvbi1zZWxlY3RvcgogICAgICAgICAgICAgIGlkPSJoaXN0b2dyYW1Nb2RlU2VsZWN0b3IiCiAgICAgICAgICAgICAgbmFtZT0iSGlzdG9ncmFtIG1vZGUiCiAgICAgICAgICAgICAgc2VsZWN0ZWQtaWQ9Int7X2hpc3RvZ3JhbU1vZGV9fSIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24gaWQ9Im92ZXJsYXkiPm92ZXJsYXk8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uIGlkPSJvZmZzZXQiPm9mZnNldDwvcGFwZXItYnV0dG9uPgogICAgICAgICAgICA8L3RmLW9wdGlvbi1zZWxlY3Rvcj4KICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPGRpdiBjbGFzcz0ic2lkZWJhci1zZWN0aW9uIj4KICAgICAgICAgICAgPHRmLW9wdGlvbi1zZWxlY3RvcgogICAgICAgICAgICAgIGlkPSJ0aW1lUHJvcGVydHlTZWxlY3RvciIKICAgICAgICAgICAgICBuYW1lPSJPZmZzZXQgdGltZSBheGlzIgogICAgICAgICAgICAgIHNlbGVjdGVkLWlkPSJ7e190aW1lUHJvcGVydHl9fSIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIDxwYXBlci1idXR0b24gaWQ9InN0ZXAiPnN0ZXA8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uIGlkPSJyZWxhdGl2ZSI+cmVsYXRpdmU8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uIGlkPSJ3YWxsX3RpbWUiPndhbGw8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgPC90Zi1vcHRpb24tc2VsZWN0b3I+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L2Rpdj4KICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24gcnVucy1zZWxlY3RvciI+CiAgICAgICAgICA8dGYtcnVucy1zZWxlY3RvciBzZWxlY3RlZC1ydW5zPSJ7e19zZWxlY3RlZFJ1bnN9fSI+CiAgICAgICAgICA8L3RmLXJ1bnMtc2VsZWN0b3I+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IHNsb3Q9ImNlbnRlciI+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW19kYXRhTm90Rm91bmRdXSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJuby1kYXRhLXdhcm5pbmciPgogICAgICAgICAgICA8aDM+Tm8gaGlzdG9ncmFtIGRhdGEgd2FzIGZvdW5kLjwvaDM+CiAgICAgICAgICAgIDxwPlByb2JhYmxlIGNhdXNlczo8L3A+CiAgICAgICAgICAgIDx1bD4KICAgICAgICAgICAgICA8bGk+CiAgICAgICAgICAgICAgICBZb3UgaGF2ZW7igJl0IHdyaXR0ZW4gYW55IGhpc3RvZ3JhbSBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuCiAgICAgICAgICAgICAgPC9saT4KICAgICAgICAgICAgICA8bGk+VGVuc29yQm9hcmQgY2Fu4oCZdCBmaW5kIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgPC91bD4KCiAgICAgICAgICAgIDxwPgogICAgICAgICAgICAgIElmIHlvdeKAmXJlIG5ldyB0byB1c2luZyBUZW5zb3JCb2FyZCwgYW5kIHdhbnQgdG8gZmluZCBvdXQgaG93IHRvCiAgICAgICAgICAgICAgYWRkIGRhdGEgYW5kIHNldCB1cCB5b3VyIGV2ZW50IGZpbGVzLCBjaGVjayBvdXQgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS90ZW5zb3JmbG93L3RlbnNvcmJvYXJkL2Jsb2IvbWFzdGVyL1JFQURNRS5tZCIKICAgICAgICAgICAgICAgID5SRUFETUU8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIHBlcmhhcHMgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vd3d3LnRlbnNvcmZsb3cub3JnL2dldF9zdGFydGVkL3N1bW1hcmllc19hbmRfdGVuc29yYm9hcmQiCiAgICAgICAgICAgICAgICA+VGVuc29yQm9hcmQgdHV0b3JpYWw8L2EKICAgICAgICAgICAgICA+LgogICAgICAgICAgICA8L3A+CgogICAgICAgICAgICA8cD4KICAgICAgICAgICAgICBJZiB5b3UgdGhpbmsgVGVuc29yQm9hcmQgaXMgY29uZmlndXJlZCBwcm9wZXJseSwgcGxlYXNlIHNlZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9ibG9iL21hc3Rlci9SRUFETUUubWQjbXktdGVuc29yYm9hcmQtaXNudC1zaG93aW5nLWFueS1kYXRhLXdoYXRzLXdyb25nIgogICAgICAgICAgICAgICAgPnRoZSBzZWN0aW9uIG9mIHRoZSBSRUFETUUgZGV2b3RlZCB0byBtaXNzaW5nIGRhdGEgcHJvYmxlbXM8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIGNvbnNpZGVyIGZpbGluZyBhbiBpc3N1ZSBvbiBHaXRIdWIuCiAgICAgICAgICAgIDwvcD4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbWyFfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPHRmLXRhZy1maWx0ZXJlciB0YWctZmlsdGVyPSJ7e190YWdGaWx0ZXJ9fSI+PC90Zi10YWctZmlsdGVyZXI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19jYXRlZ29yaWVzXV0iIGFzPSJjYXRlZ29yeSI+CiAgICAgICAgICAgIDx0Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldwogICAgICAgICAgICAgIGNhdGVnb3J5PSJbW2NhdGVnb3J5XV0iCiAgICAgICAgICAgICAgaW5pdGlhbC1vcGVuZWQ9IltbX3Nob3VsZE9wZW4oaW5kZXgpXV0iCiAgICAgICAgICAgID4KICAgICAgICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICAgICAgICA8dGYtaGlzdG9ncmFtLWxvYWRlcgogICAgICAgICAgICAgICAgICBydW49IltbaXRlbS5ydW5dXSIKICAgICAgICAgICAgICAgICAgdGFnPSJbW2l0ZW0udGFnXV0iCiAgICAgICAgICAgICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICAgICAgICAgICAgdGFnLW1ldGFkYXRhPSJbW190YWdNZXRhZGF0YShfcnVuVG9UYWdJbmZvLCBpdGVtLnJ1biwgaXRlbS50YWcpXV0iCiAgICAgICAgICAgICAgICAgIHRpbWUtcHJvcGVydHk9IltbX3RpbWVQcm9wZXJ0eV1dIgogICAgICAgICAgICAgICAgICBoaXN0b2dyYW0tbW9kZT0iW1tfaGlzdG9ncmFtTW9kZV1dIgogICAgICAgICAgICAgICAgICByZXF1ZXN0LW1hbmFnZXI9IltbX3JlcXVlc3RNYW5hZ2VyXV0iCiAgICAgICAgICAgICAgICA+PC90Zi1oaXN0b2dyYW0tbG9hZGVyPgogICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDwvdGYtY2F0ZWdvcnktcGFnaW5hdGVkLXZpZXc+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgPC90Zi1kYXNoYm9hcmQtbGF5b3V0PgoKICAgIDxzdHlsZSBpbmNsdWRlPSJkYXNoYm9hcmQtc3R5bGUiPjwvc3R5bGU+CiAgICA8c3R5bGU+CiAgICAgIC5uby1kYXRhLXdhcm5pbmcgewogICAgICAgIG1heC13aWR0aDogNTQwcHg7CiAgICAgICAgbWFyZ2luOiA4MHB4IGF1dG8gMCBhdXRvOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZIaXN0b2dyYW1EYXNoYm9hcmQucHJvdG90eXBlLCAicmVsb2FkT25SZWFkeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSGlzdG9ncmFtRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9oaXN0b2dyYW1Nb2RlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZIaXN0b2dyYW1EYXNoYm9hcmQucHJvdG90eXBlLCAiX3RpbWVQcm9wZXJ0eSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkhpc3RvZ3JhbURhc2hib2FyZC5wcm90b3R5cGUsICJfc2VsZWN0ZWRSdW5zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIaXN0b2dyYW1EYXNoYm9hcmQucHJvdG90eXBlLCAiX3J1blRvVGFnIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIaXN0b2dyYW1EYXNoYm9hcmQucHJvdG90eXBlLCAiX3J1blRvVGFnSW5mbyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZIaXN0b2dyYW1EYXNoYm9hcmQucHJvdG90eXBlLCAiX2RhdGFOb3RGb3VuZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSGlzdG9ncmFtRGFzaGJvYXJkLnByb3RvdHlwZSwgIl90YWdGaWx0ZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSGlzdG9ncmFtRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9yZXN0YW1wIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkhpc3RvZ3JhbURhc2hib2FyZC5wcm90b3R5cGUsICJfY2F0ZWdvcmllc0RvbVJlYWR5Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgUmVxdWVzdE1hbmFnZXIpCiAgICBdLCBUZkhpc3RvZ3JhbURhc2hib2FyZC5wcm90b3R5cGUsICJfcmVxdWVzdE1hbmFnZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19ydW5Ub1RhZycsICdfc2VsZWN0ZWRSdW5zJywgJ190YWdGaWx0ZXInLCAnX2NhdGVnb3JpZXNEb21SZWFkeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkhpc3RvZ3JhbURhc2hib2FyZC5wcm90b3R5cGUsICJfY2F0ZWdvcmllcyIsIG51bGwpOwogICAgVGZIaXN0b2dyYW1EYXNoYm9hcmQgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1oaXN0b2dyYW0tZGFzaGJvYXJkJykKICAgIF0sIFRmSGlzdG9ncmFtRGFzaGJvYXJkKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCiAgICAvLyBGdW5jdGlvbnMgZm9yIGRlYWxpbmcgd2l0aCBIUGFyYW1zLCBNZXRyaWNzLCBDb2x1bW5zLAogICAgLy8gU2Vzc2lvbkdyb3VwcyBhbmQgU2NoZW1hIG9iamVjdHMuCiAgICAvLyBJbiB0aGUgZm9sbG93aW5nIHJvdXRpbmVzIHdlIHVzZSB0aGUgZm9sbG93aW5nIG5hbWluZyBjb252ZW50aW9ucyBmb3IKICAgIC8vIHBhcmFtZXRlcnM6CiAgICAvLwogICAgLy8gaHBhcmFtSW5mbywgbWV0cmljSW5mbzogQSBKYXZhU2NyaXB0IG9iamVjdCByZXByZXNlbnRhdGlvbiBvZiB0aGUKICAgIC8vICAgICBIUGFyYW1JbmZvIHByb3RvIGRlZmluZWQgaW4gYXBpLnByb3RvLgogICAgLy8gc2NoZW1hOiBUaGUgb2JqZWN0IHN0b3JpbmcgbWV0YWRhdGEgb24gdGhlIG1ldHJpY3MgYW5kIGhwYXJhbXMgdXNlZAogICAgLy8gICAgIGluIHRoZSBleHBlcmltZW50LiBTZWUgdGhlIGRvY3VtZW50YXRpb24gaW4KICAgIC8vICAgICAndGYtaHBhcmFtcy1xdWVyeS1wYW5lLmh0bWwnLgogICAgLy8gdmlzaWJsZVNjaGVtYTogVGhlIG9iamVjdCBzdG9yaW5nIG1ldGFkYXRhIG9uIGp1c3QgdGhlIHZpc2libGUgbWV0cmljcwogICAgLy8gICAgIGFuZCBocGFyYW1zIGluICdzY2hlbWEnLiBUaGlzIGlzIHRoZSBvYmplY3Qgc3RvcmVkIGluIHRoZSBwcm9wZXJ0eQogICAgLy8gICAgICd2aXNpYmxlU2NoZW1hJyBvZiAnY29uZmlndXJhdGlvbicgKHNlZSB0aGUgZG9jdW1lbnRhdGlvbiBpbgogICAgLy8gICAgIHRmLWhwYXJhbXMtcXVlcnktcGFuZS5odG1sJyBmb3IgbW9yZSBkZXRhaWxzKS4gVGhpcyBvYmplY3QgYW5kIHRoZQogICAgLy8gICAgIHV0aWxpdHkgZnVuY3Rpb25zIGJlbG93IHRoYXQgYWNjZXB0IGl0IGFyZSBkZXByZWNhdGVkIGFuZCB0aGUKICAgIC8vICAgICBpbnRlbnRpb24gaXMgdG8gZXZlbnR1YWxseSByZW1vdmUgdGhlbS4KICAgIC8vICAgICBOZXcgY29kZSBzaG91bGQgaW5zdGVhZCBmaWx0ZXIgdGhlIGVudHJpZXMgaW4gdGhlIHNjaGVtYSBvYmplY3QKICAgIC8vICAgICBkaXJlY3RseSB0byBmaW5kIGFsbCB0aGUgdmlzaWJsZSBjb2x1bW5zIGFuZCBvbmx5IHVzZSB0aGUgZnVuY3Rpb25zCiAgICAvLyAgICAgYmVsb3cgdGhhdCB0YWtlIGEgJ3NjaGVtYScgb2JqZWN0LgogICAgLy8gc2Vzc2lvbkdyb3VwOiBBIEphdmFTY3JpcHQgb2JqZWN0IHJlcHJlc2VudGF0aW9uIG9mIHRoZSBTZXNzaW9uR3JvdXAKICAgIC8vICAgICBwcm90byBkZWZpbmVkIGluIGFwaS5wcm90by4KICAgIC8vIHNlc3Npb25Hcm91cHM6IEFuIGFycmF5IG9mICdzZXNzaW9uR3JvdXAnIG9iamVjdHMuCiAgICAvLyBjb2x1bW5JbmRleDogQW4gaW5kZXggb2YgYSAnY29sdW1uJyBvZiBhIHNlc3Npb25Hcm91cCB3aXRoIHJlc3BlY3QKICAgIC8vICAgICB0byBhIHNjaGVtYSBvciB2aXNpYmxlU2NoZW1hIG9iamVjdC4gV2UgcmVnYXJkIGEKICAgIC8vICAgICBzZXNzaW9uR3JvdXAgYXMgYSByb3cgaW4gYSB0YWJsZSB3aGVyZSB0aGUgY29sdW1ucyByZXByZXNlbnQKICAgIC8vICAgICBocGFyYW1zIGFuZCBtZXRyaWMgdmFsdWVzIGZvciB0aGUgc2Vzc2lvbiBncm91cC4gVGhlIGNvbHVtbnMgYXJlCiAgICAvLyAgICAgb3JkZXJlZCBieSBsaXN0aW5nIHRoZSBocGFyYW0gY29sdW1ucyBmaXJzdCBpbiB0aGUgc2FtZSBvcmRlciBhcwogICAgLy8gICAgIHRoZSBjb3JyZXNwb25kaW5nIGVsZW1lbnRzIG9mIHNjaGVtYS5ocGFyYW1Db2x1bW5zIG9yCiAgICAvLyAgICAgdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcywgZm9sbG93ZWQgYnkgdGhlCiAgICAvLyAgICAgbWV0cmljIGNvbHVtbnMgaW4gdGhlIHNhbWUgb3JkZXIgYXMgdGhlIGNvcnJlc3BvbmRpbmcgZWxlbWVudHMgb2YKICAgIC8vICAgICBzY2hlbWEubWV0cmljQ29sdW1ucyBvciB2aXNpYmxlU2NoZW1hLm1ldHJpY0luZm9zLiBXaGV0aGVyIHRoZQogICAgLy8gICAgIGluZGV4IGlzIGdpdmVuIHdpdGggcmVzcGVjdCB0byBhIHNjaGVtYSBvciBhIHZpc2libGVTY2hlbWUgZGVwZW5kcwogICAgLy8gICAgIG9uIHRoZSB0eXBlIG9mIHNjaGVtYSBwYXJhbWV0ZXIgdGhlIHV0aWxpdHkgZnVuY3Rpb24gYmVsb3cgYWNjZXB0cwogICAgLy8gICAgIGluIGFkZGl0aW9uIHRvIHRoZSBjb2x1bW5JbmRleCBwYXJhbWV0ZXIuCiAgICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgLy8gQ29tcHV0ZXMgdGhlIG5hbWUgdG8gZGlzcGxheSBmb3IgdGhlIGdpdmVuICdocGFyYW1JbmZvJyBvYmplY3QuCiAgICBmdW5jdGlvbiBocGFyYW1OYW1lKGhwYXJhbUluZm8pIHsKICAgICAgICBpZiAoaHBhcmFtSW5mby5kaXNwbGF5TmFtZSAhPT0gJycgJiYgaHBhcmFtSW5mby5kaXNwbGF5TmFtZSAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgIHJldHVybiBocGFyYW1JbmZvLmRpc3BsYXlOYW1lOwogICAgICAgIH0KICAgICAgICByZXR1cm4gaHBhcmFtSW5mby5uYW1lOwogICAgfQogICAgLy8gQ29tcHV0ZXMgdGhlIG5hbWUgdG8gZGlzcGxheSBmb3IgdGhlIGdpdmVuIG1ldHJpY0luZm8gb2JqZWN0LgogICAgZnVuY3Rpb24gbWV0cmljTmFtZShtZXRyaWNJbmZvKSB7CiAgICAgICAgaWYgKG1ldHJpY0luZm8uZGlzcGxheU5hbWUgIT09ICcnICYmIG1ldHJpY0luZm8uZGlzcGxheU5hbWUgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICByZXR1cm4gbWV0cmljSW5mby5kaXNwbGF5TmFtZTsKICAgICAgICB9CiAgICAgICAgbGV0IGdyb3VwID0gbWV0cmljSW5mby5uYW1lLmdyb3VwOwogICAgICAgIGxldCB0YWcgPSBtZXRyaWNJbmZvLm5hbWUudGFnOwogICAgICAgIGlmIChncm91cCA9PT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgIGdyb3VwID0gJyc7CiAgICAgICAgfQogICAgICAgIGlmICh0YWcgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICB0YWcgPSAnJzsKICAgICAgICB9CiAgICAgICAgaWYgKGdyb3VwID09PSAnJykgewogICAgICAgICAgICByZXR1cm4gdGFnOwogICAgICAgIH0KICAgICAgICByZXR1cm4gZ3JvdXAgKyAnLicgKyB0YWc7CiAgICB9CiAgICBmdW5jdGlvbiBzY2hlbWFDb2x1bW5OYW1lKHNjaGVtYSwgY29sdW1uSW5kZXgpIHsKICAgICAgICBpZiAoY29sdW1uSW5kZXggPCBzY2hlbWEuaHBhcmFtQ29sdW1ucy5sZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIGhwYXJhbU5hbWUoc2NoZW1hLmhwYXJhbUNvbHVtbnNbY29sdW1uSW5kZXhdLmhwYXJhbUluZm8pOwogICAgICAgIH0KICAgICAgICBjb25zdCBtZXRyaWNJbmRleCA9IGNvbHVtbkluZGV4IC0gc2NoZW1hLmhwYXJhbUNvbHVtbnMubGVuZ3RoOwogICAgICAgIHJldHVybiBtZXRyaWNOYW1lKHNjaGVtYS5tZXRyaWNDb2x1bW5zW21ldHJpY0luZGV4XS5tZXRyaWNJbmZvKTsKICAgIH0KICAgIC8vIFJldHVybnMgdGhlIG51bWJlciBvZiBocGFyYW1zIGluIHNjaGVtYSAodmlzaWJsZSBhbmQgaW52aXNpYmxlKS4KICAgIGZ1bmN0aW9uIG51bUhQYXJhbXMoc2NoZW1hKSB7CiAgICAgICAgcmV0dXJuIHNjaGVtYS5ocGFyYW1Db2x1bW5zLmxlbmd0aDsKICAgIH0KICAgIC8vIFJldHVybnMgdGhlIG51bWJlciBvZiBtZXRyaWNzIGluIHNjaGVtYSAodmlzaWJsZSBhbmQgaW52aXNpYmxlKS4KICAgIGZ1bmN0aW9uIG51bU1ldHJpY3Moc2NoZW1hKSB7CiAgICAgICAgcmV0dXJuIHNjaGVtYS5tZXRyaWNDb2x1bW5zLmxlbmd0aDsKICAgIH0KICAgIC8vIFJldHVybnMgdGhlIG51bWJlciBvZiBjb2x1bW5zIGluIHNjaGVtYSAodmlzaWJsZSBhbmQgaW52aXNpYmxlKS4KICAgIGZ1bmN0aW9uIG51bUNvbHVtbnMoc2NoZW1hKSB7CiAgICAgICAgcmV0dXJuIG51bUhQYXJhbXMoc2NoZW1hKSArIG51bU1ldHJpY3Moc2NoZW1hKTsKICAgIH0KICAgIC8vIFJldHVybnMgaHBhcmFtVmFsdWVzW2hwYXJhbU5hbWVdLiBUbyBiZSB1c2VkIGluIGEgUG9seW1lciBkYXRhYmluZGluZwogICAgLy8gYW5ub3RhdGlvbiAoYXMgUG9seW1lciBkb2Vzbid0IGhhdmUgYW4gYW5ub3RhdGlvbiBmb3IgbG9va2luZyB1cCBhCiAgICAvLyBwcm9wZXJ0eSBpbiBhbiBKUyBvYmplY3QpLgogICAgZnVuY3Rpb24gaHBhcmFtVmFsdWVCeU5hbWUoaHBhcmFtVmFsdWVzLCBocGFyYW1OYW1lKSB7CiAgICAgICAgcmV0dXJuIGhwYXJhbVZhbHVlc1tocGFyYW1OYW1lXTsKICAgIH0KICAgIC8vIEdpdmVuIGFuIGFycmF5ICdtZXRyaWNWYWx1ZXMnIG9mIChqYXZhc2NyaXB0IG9iamVjdCByZXByZXNlbnRhdGlvbikgb2YKICAgIC8vIHRlbnNvcmJvYXJkLmhwYXJhbXMuTWV0cmljVmFsdWUncyBwcm90b2NvbCBidWZmZXJzLCByZXR1cm5zIHRoZSBmaXJzdAogICAgLy8gZWxlbWVudCB3aG9zZSBtZXRyaWMgbmFtZSBpcyAnbWV0cmljTmFtZScgb3IgdW5kZWZpbmVkIGlmIG5vIHN1Y2gKICAgIC8vIGVsZW1lbnQgZXhpc3RzLgogICAgZnVuY3Rpb24gbWV0cmljVmFsdWVCeU5hbWUobWV0cmljVmFsdWVzLCBtZXRyaWNOYW1lKSB7CiAgICAgICAgcmV0dXJuIG1ldHJpY1ZhbHVlcy5maW5kKChtdikgPT4gbG9kYXNoLmlzRXF1YWwobXYubmFtZSwgbWV0cmljTmFtZSkpOwogICAgfQogICAgLy8gUmV0dXJucyBzZXNzaW9uR3JvdXAncyBtZXRyaWMgdmFsdWUgb2YgdGhlIG1ldHJpYyB3aXRoIGluZGV4CiAgICAvLyAnbWV0cmljSW5kZXgnIGluIHNjaGVtYS5tZXRyaWNDb2x1bW5zLgogICAgZnVuY3Rpb24gaHBhcmFtVmFsdWVCeUluZGV4KHNjaGVtYSwgc2Vzc2lvbkdyb3VwLCBocGFyYW1JbmRleCkgewogICAgICAgIHJldHVybiBzZXNzaW9uR3JvdXAuaHBhcmFtc1tzY2hlbWEuaHBhcmFtQ29sdW1uc1tocGFyYW1JbmRleF0uaHBhcmFtSW5mby5uYW1lXTsKICAgIH0KICAgIC8vIFJldHVybnMgc2Vzc2lvbkdyb3VwJ3MgbWV0cmljIHZhbHVlIG9mIHRoZSBtZXRyaWMgd2l0aCBpbmRleAogICAgLy8gJ21ldHJpY0luZGV4JyBpbiBzY2hlbWEubWV0cmljQ29sdW1ucy4KICAgIGZ1bmN0aW9uIG1ldHJpY1ZhbHVlQnlJbmRleChzY2hlbWEsIHNlc3Npb25Hcm91cCwgbWV0cmljSW5kZXgpIHsKICAgICAgICBjb25zdCBtZXRyaWNOYW1lID0gc2NoZW1hLm1ldHJpY0NvbHVtbnNbbWV0cmljSW5kZXhdLm1ldHJpY0luZm8ubmFtZTsKICAgICAgICBjb25zdCBtZXRyaWNWYWx1ZSA9IG1ldHJpY1ZhbHVlQnlOYW1lKHNlc3Npb25Hcm91cC5tZXRyaWNWYWx1ZXMsIG1ldHJpY05hbWUpOwogICAgICAgIHJldHVybiBtZXRyaWNWYWx1ZSA9PT0gdW5kZWZpbmVkID8gdW5kZWZpbmVkIDogbWV0cmljVmFsdWUudmFsdWU7CiAgICB9CiAgICAvLyBSZXR1cm5zIHNlc3Npb25Hcm91cCdzIGNvbHVtbiB2YWx1ZSBvZiB0aGUgY29sdW1uIHdpdGggaW5kZXgKICAgIC8vICdjb2x1bW5JbmRleCcgaW4gc2NoZW1hLgogICAgZnVuY3Rpb24gY29sdW1uVmFsdWVCeUluZGV4KHNjaGVtYSwgc2Vzc2lvbkdyb3VwLCBjb2x1bW5JbmRleCkgewogICAgICAgIGlmIChjb2x1bW5JbmRleCA8IHNjaGVtYS5ocGFyYW1Db2x1bW5zLmxlbmd0aCkgewogICAgICAgICAgICByZXR1cm4gaHBhcmFtVmFsdWVCeUluZGV4KHNjaGVtYSwgc2Vzc2lvbkdyb3VwLCBjb2x1bW5JbmRleCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiBtZXRyaWNWYWx1ZUJ5SW5kZXgoc2NoZW1hLCBzZXNzaW9uR3JvdXAsIGNvbHVtbkluZGV4IC0gc2NoZW1hLmhwYXJhbUNvbHVtbnMubGVuZ3RoKTsKICAgIH0KICAgIC8vIFJldHVybnMgYW4gYXJyYXkgW21pbiwgbWF4XSByZXByZXNlbnRpbmcgdGhlIG1pbmltdW0gYW5kIG1heGltdW0KICAgIC8vIHZhbHVlIG9mIHRoZSBnaXZlbiBjb2x1bW4gaW4gdGhlIHNlc3Npb25Hcm91cHMgYXJyYXkuCiAgICAvLyBJZ25vcmVzIHNlc3Npb24gZ3JvdXBzIHdpdGggbWlzc2luZyB2YWx1ZXMgZm9yIHRoZSBjb2x1bW4uCiAgICBmdW5jdGlvbiBudW1lcmljQ29sdW1uRXh0ZW50KHNjaGVtYSwgc2Vzc2lvbkdyb3VwcywgY29sdW1uSW5kZXgpIHsKICAgICAgICByZXR1cm4gZXh0ZW50KHNlc3Npb25Hcm91cHMsIChzZykgPT4gY29sdW1uVmFsdWVCeUluZGV4KHNjaGVtYSwgc2csIGNvbHVtbkluZGV4KSk7CiAgICB9CiAgICAvLyBDb252ZXJ0cyBhIHZpc2libGVTY2hlbWEgY29sdW1uSW5kZXggdG8gYSBzY2hlbWEgY29sdW1uSW5kZXguCiAgICAvLyBSZXR1cm5zIHRoZSBzY2hlbWEtcmVsYXRpdmUgY29sdW1uSW5kZXggZm9yIHRoZSB2aXNpYmxlIGNvbHVtbiB3aXRoCiAgICAvLyB2aXNpYmxlU2NoZW1hLXJlbGVhdGl2ZSBjb2x1bW5JbmRleCBnaXZlbiBieSAndmlzaWJsZUNvbHVtbkluZGV4Jy4KICAgIGZ1bmN0aW9uIGdldEFic29sdXRlQ29sdW1uSW5kZXgoc2NoZW1hLCB2aXNpYmxlU2NoZW1hLCB2aXNpYmxlQ29sdW1uSW5kZXgpIHsKICAgICAgICBsZXQgcmVzdWx0OwogICAgICAgIGlmICh2aXNpYmxlQ29sdW1uSW5kZXggPCB2aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zLmxlbmd0aCkgewogICAgICAgICAgICByZXN1bHQgPSBzY2hlbWEuaHBhcmFtQ29sdW1ucy5maW5kSW5kZXgoKGMpID0+IGMuaHBhcmFtSW5mby5uYW1lID09PSB2aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zW3Zpc2libGVDb2x1bW5JbmRleF0ubmFtZSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICBjb25zdCBtZXRyaWNJbmRleCA9IHZpc2libGVDb2x1bW5JbmRleCAtIHZpc2libGVTY2hlbWEuaHBhcmFtSW5mb3MubGVuZ3RoOwogICAgICAgICAgICBjb25zdCBtZXRyaWNOYW1lID0gdmlzaWJsZVNjaGVtYS5tZXRyaWNJbmZvc1ttZXRyaWNJbmRleF0ubmFtZTsKICAgICAgICAgICAgcmVzdWx0ID0KICAgICAgICAgICAgICAgIHNjaGVtYS5ocGFyYW1Db2x1bW5zLmxlbmd0aCArCiAgICAgICAgICAgICAgICAgICAgc2NoZW1hLm1ldHJpY0NvbHVtbnMuZmluZEluZGV4KChjKSA9PiBjLm1ldHJpY0luZm8ubmFtZSA9PT0gbWV0cmljTmFtZSk7CiAgICAgICAgfQogICAgICAgIGNvbnNvbGUuYXNzZXJ0KHJlc3VsdCAhPT0gLTEpOwogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICB9CiAgICAvLyBERVBSRUNBVEVELiBVc2Ugc2NoZW1hQ29sdW1uTmFtZSBpbnN0ZWFkICh3aXRoIGFuICJhYnNvbHV0ZSIKICAgIC8vIGNvbHVtbkluZGV4KS4KICAgIC8vIENvbXB1dGVzIHRoZSBuYW1lIHRvIGRpc3BsYXkgZm9yIHRoZSBnaXZlbiB2aXNpYmxlIGNvbHVtbiBpbmRleC4KICAgIGZ1bmN0aW9uIHNjaGVtYVZpc2libGVDb2x1bW5OYW1lKHZpc2libGVTY2hlbWEsIGNvbHVtbkluZGV4KSB7CiAgICAgICAgaWYgKGNvbHVtbkluZGV4IDwgdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGgpIHsKICAgICAgICAgICAgcmV0dXJuIGhwYXJhbU5hbWUodmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvc1tjb2x1bW5JbmRleF0pOwogICAgICAgIH0KICAgICAgICBjb25zdCBtZXRyaWNJbmRleCA9IGNvbHVtbkluZGV4IC0gdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGg7CiAgICAgICAgcmV0dXJuIG1ldHJpY05hbWUodmlzaWJsZVNjaGVtYS5tZXRyaWNJbmZvc1ttZXRyaWNJbmRleF0pOwogICAgfQogICAgLy8gREVQUkVDQVRFRC4gVXNlIG51bURpc3BsYXllZEhQYXJhbXMgaW5zdGVhZC4KICAgIC8vIFJldHVybnMgdGhlIG51bWJlciBvZiBocGFyYW1zIGluIHZpc2libGVTY2hlbWEuIFRoaXMgaXMgdGhlIHNhbWUKICAgIC8vIHZhbHVlIGFzIG51bURpc3BsYXllZEhQYXJhbXMoc2NoZW1hKSB3aXRoIHNjaGVtYSBiZWluZyB0aGUgImNvbnRhaW5pbmciCiAgICAvLyBzY2hlbWEgb2YgdmlzaWJsZVNjaGVtYS4KICAgIGZ1bmN0aW9uIG51bVZpc2libGVIUGFyYW1zKHZpc2libGVTY2hlbWEpIHsKICAgICAgICByZXR1cm4gdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGg7CiAgICB9CiAgICAvLyBERVBSRUNBVEVELiBVc2UgbnVtRGlzcGxheWVkTWV0cmljcyBpbnN0ZWFkLgogICAgLy8gUmV0dXJucyB0aGUgbnVtYmVyIG9mIGhwYXJhbXMgaW4gdmlzaWJsZVNjaGVtYS4gVGhpcyBpcyB0aGUgc2FtZQogICAgLy8gdmFsdWUgYXMgbnVtRGlzcGxheWVkTWV0cmljcyhzY2hlbWEpIHdpdGggc2NoZW1hIGJlaW5nIHRoZSAiY29udGFpbmluZyIKICAgIC8vIHNjaGVtYSBvZiB2aXNpYmxlU2NoZW1hLgogICAgZnVuY3Rpb24gbnVtVmlzaWJsZU1ldHJpY3ModmlzaWJsZVNjaGVtYSkgewogICAgICAgIHJldHVybiB2aXNpYmxlU2NoZW1hLm1ldHJpY0luZm9zLmxlbmd0aDsKICAgIH0KICAgIC8vIERFUFJFQ0FURUQuCiAgICAvLyBSZXR1cm5zIHRoZSBudW1iZXIgb2YgdmlzaWJsZSBjb2x1bW5zIChoYXZpbmcgJ2Rpc3BsYXllZCcgdHJ1ZSkuCiAgICAvLyBUaGlzIGlzIHRoZSBzYW1lIHZhbHVlIGFzIG51bURpc3BsYXllZENvbHVtbnMoc2NoZW1hKSB3aXRoIHNjaGVtYQogICAgLy8gYmVpbmcgdGhlICJjb250YWluaW5nIiBzY2hlbWEgb2YgdmlzaWJsZVNjaGVtYS4KICAgIGZ1bmN0aW9uIG51bVZpc2libGVDb2x1bW5zKHZpc2libGVTY2hlbWEpIHsKICAgICAgICByZXR1cm4gbnVtVmlzaWJsZUhQYXJhbXModmlzaWJsZVNjaGVtYSkgKyBudW1WaXNpYmxlTWV0cmljcyh2aXNpYmxlU2NoZW1hKTsKICAgIH0KICAgIC8vIERFUFJFQ0FURUQuIFVzZSBudW1lcmljQ29sdW1uRXh0ZW50IHdpdGggYSBzY2hlbWEgY29sdW1uSW5kZXggaW5zdGVhZC4KICAgIC8vIFJldHVybnMgYW4gYXJyYXkgW21pbiwgbWF4XSByZXByZXNlbnRpbmcgdGhlIG1pbmltdW0gYW5kIG1heGltdW0KICAgIC8vIHZhbHVlIG9mIHRoZSBnaXZlbiB2aXNpYmxlIGNvbHVtbiBpbiB0aGUgc2Vzc2lvbkdyb3VwcyBhcnJheS4KICAgIC8vIElnbm9yZXMgc2Vzc2lvbiBncm91cHMgd2l0aCBtaXNzaW5nIHZhbHVlcyBmb3IgdGhlIGNvbHVtbi4KICAgIGZ1bmN0aW9uIHZpc2libGVOdW1lcmljQ29sdW1uRXh0ZW50KHZpc2libGVTY2hlbWEsIHNlc3Npb25Hcm91cHMsIGNvbHVtbkluZGV4KSB7CiAgICAgICAgcmV0dXJuIGV4dGVudChzZXNzaW9uR3JvdXBzLCAoc2cpID0+IGNvbHVtblZhbHVlQnlWaXNpYmxlSW5kZXgodmlzaWJsZVNjaGVtYSwgc2csIGNvbHVtbkluZGV4KSk7CiAgICB9CiAgICAvLyBSZXR1cm5zIGEgc3RyaW5nIHJlcHJlc2VudGF0aW9uIG9mIGhwYXJhbVZhbHVlc1tocGFyYW1OYW1lXSBzdWl0YWJsZQogICAgLy8gZm9yIGRpc3BsYXkuCiAgICBmdW5jdGlvbiBwcmV0dHlQcmludEhQYXJhbVZhbHVlQnlOYW1lKGhwYXJhbVZhbHVlcywgaHBhcmFtTmFtZSkgewogICAgICAgIHJldHVybiBwcmV0dHlQcmludChocGFyYW1WYWx1ZUJ5TmFtZShocGFyYW1WYWx1ZXMsIGhwYXJhbU5hbWUpKTsKICAgIH0KICAgIC8vIFJldHVybnMgYSBzdHJpbmcgcmVwcmVzZW50YXRpb24gb2YgbWV0cmljVmFsdWVCeU5hbWUgc3VpdGFibGUgZm9yCiAgICAvLyBkaXNwbGF5LgogICAgZnVuY3Rpb24gcHJldHR5UHJpbnRNZXRyaWNWYWx1ZUJ5TmFtZShtZXRyaWNWYWx1ZXMsIG1ldHJpY05hbWUpIHsKICAgICAgICByZXR1cm4gcHJldHR5UHJpbnQobWV0cmljVmFsdWVCeU5hbWUobWV0cmljVmFsdWVzLCBtZXRyaWNOYW1lKSk7CiAgICB9CiAgICAvLyBSZXR1cm5zIHRoZSBzZXNzaW9uIGdyb3VwIHdpdGggbmFtZSAnbmFtZScgaW4gc2Vzc2lvbkdyb3VwcyBvcgogICAgLy8gdW5kZWZpbmVkIG9mIG5vIHN1Y2ggZWxlbWVudCBleGlzdC4KICAgIGZ1bmN0aW9uIHNlc3Npb25Hcm91cFdpdGhOYW1lKHNlc3Npb25Hcm91cHMsIG5hbWUpIHsKICAgICAgICByZXR1cm4gc2Vzc2lvbkdyb3Vwcy5maW5kKChzZykgPT4gc2cubmFtZSA9PT0gbmFtZSk7CiAgICB9CiAgICAvLyBERVBSRUNBVEVELiBVc2UgaHBhcmFtVmFsdWVCeUluZGV4IHdpdGggYSBzY2hlbWEgaHBhcmFtSW5kZXggaW5zdGVhZC4KICAgIC8vIFJldHVybnMgc2Vzc2lvbkdyb3VwJ3MgaHBhcmFtIHZhbHVlIG9mIHRoZSB2aXNpYmxlIGhwYXJhbSB3aXRoIGluZGV4CiAgICAvLyAnaHBhcmFtSW5kZXgnIGluIHZpc2libGVTY2hlbWEuaHBhcmFtSW5mb3MuCiAgICBmdW5jdGlvbiBocGFyYW1WYWx1ZUJ5VmlzaWJsZUluZGV4KHZpc2libGVTY2hlbWEsIHNlc3Npb25Hcm91cCwgaHBhcmFtSW5kZXgpIHsKICAgICAgICByZXR1cm4gc2Vzc2lvbkdyb3VwLmhwYXJhbXNbdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvc1tocGFyYW1JbmRleF0ubmFtZV07CiAgICB9CiAgICAvLyBERVBSRUNBVEVELiBVc2UgbWV0cmljVmFsdWVCeUluZGV4IHdpdGggYSBzY2hlbWEgbWV0cmljSW5kZXggaW5zdGVhZC4KICAgIC8vIFJldHVybnMgc2Vzc2lvbkdyb3VwJ3MgbWV0cmljIHZhbHVlIG9mIHRoZSB2aXNpYmxlIG1ldHJpYyB3aXRoIGluZGV4CiAgICAvLyAnbWV0cmljSW5kZXgnIGluIHZpc2libGVTY2hlbWEubWV0cmljSW5mb3MuCiAgICBmdW5jdGlvbiBtZXRyaWNWYWx1ZUJ5VmlzaWJsZUluZGV4KHZpc2libGVTY2hlbWEsIHNlc3Npb25Hcm91cCwgdmlzaWJsZU1ldHJpY0luZGV4KSB7CiAgICAgICAgY29uc3QgbWV0cmljTmFtZSA9IHZpc2libGVTY2hlbWEubWV0cmljSW5mb3NbdmlzaWJsZU1ldHJpY0luZGV4XS5uYW1lOwogICAgICAgIGNvbnN0IG1ldHJpY1ZhbHVlID0gbWV0cmljVmFsdWVCeU5hbWUoc2Vzc2lvbkdyb3VwLm1ldHJpY1ZhbHVlcywgbWV0cmljTmFtZSk7CiAgICAgICAgcmV0dXJuIG1ldHJpY1ZhbHVlID09PSB1bmRlZmluZWQgPyB1bmRlZmluZWQgOiBtZXRyaWNWYWx1ZS52YWx1ZTsKICAgIH0KICAgIC8vIERFUFJFQ0FURUQuIFVzZSBjb2x1bW5WYWx1ZUJ5SW5kZXggd2l0aCBhIHNjaGVtYSBjb2x1bW5JbmRleCBpbnN0ZWFkLgogICAgLy8gUmV0dXJucyBzZXNzaW9uR3JvdXAncyBjb2x1bW4gdmFsdWUgb2YgdGhlIHZpc2libGUgY29sdW1uIHdpdGggaW5kZXgKICAgIC8vICdjb2x1bW5JbmRleCcgaW4gdmlzaWJsZVNjaGVtYS4KICAgIGZ1bmN0aW9uIGNvbHVtblZhbHVlQnlWaXNpYmxlSW5kZXgodmlzaWJsZVNjaGVtYSwgc2Vzc2lvbkdyb3VwLCBjb2x1bW5JbmRleCkgewogICAgICAgIGlmIChjb2x1bW5JbmRleCA8IHZpc2libGVTY2hlbWEuaHBhcmFtSW5mb3MubGVuZ3RoKSB7CiAgICAgICAgICAgIHJldHVybiBocGFyYW1WYWx1ZUJ5VmlzaWJsZUluZGV4KHZpc2libGVTY2hlbWEsIHNlc3Npb25Hcm91cCwgY29sdW1uSW5kZXgpOwogICAgICAgIH0KICAgICAgICByZXR1cm4gbWV0cmljVmFsdWVCeVZpc2libGVJbmRleCh2aXNpYmxlU2NoZW1hLCBzZXNzaW9uR3JvdXAsIGNvbHVtbkluZGV4IC0gdmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGgpOwogICAgfQogICAgLy8gLS0tLSBNaXNjIGZ1bmN0aW9ucyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgIC8vIFJldHVybnMgYSBzdHJpbmcgcmVwcmVzZW50YXRpb24gb2YgJ3ZhbHVlJyBzdWl0YWJsZSBmb3IgZGlzcGxheS4KICAgIGZ1bmN0aW9uIHByZXR0eVByaW50KHZhbHVlKSB7CiAgICAgICAgaWYgKGxvZGFzaC5pc051bWJlcih2YWx1ZSkpIHsKICAgICAgICAgICAgLy8gVE9ETyhlcmV6KTpNYWtlIHRoZSBwcmVjaXNpb24gdXNlci1jb25maWd1cmFibGUuCiAgICAgICAgICAgIHJldHVybiB2YWx1ZS50b1ByZWNpc2lvbig1KTsKICAgICAgICB9CiAgICAgICAgaWYgKHZhbHVlID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdmFsdWUudG9TdHJpbmcoKTsKICAgIH0KICAgIC8vIFJldHVybnMgdGhlIHNxdWFyZSBvZiB0aGUgTDItbm9ybSBvZiAoeCwgeSkuCiAgICBmdW5jdGlvbiBsMk5vcm1TcXVhcmVkKHgsIHkpIHsKICAgICAgICByZXR1cm4geCAqIHggKyB5ICogeTsKICAgIH0KICAgIC8vIFJldHVybnMgdGhlIGV1Y2xpZGVhbiBkaXN0YW5jZSBiZXR3ZWVuICh4MCwgeTApIGFuZCAoeDEsIHkxKS4KICAgIGZ1bmN0aW9uIGV1Y2xpZGVhbkRpc3QoeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgICByZXR1cm4gTWF0aC5zcXJ0KGwyTm9ybVNxdWFyZWQoeDAgLSB4MSwgeTAgLSB5MSkpOwogICAgfQogICAgLy8gUmV0dXJucyB0aGUgKGV1Y2xpZGVhbikgZGlzdGFuY2UgYmV0d2VlbiB0aGUgcG9pbnQgKHgsIHkpIGFuZCB0aGUKICAgIC8vIHJlY3RhbmdsZSBbeDAsIHgxKSB4IFt5MCwgeTEpLgogICAgZnVuY3Rpb24gcG9pbnRUb1JlY3RhbmdsZURpc3QoeCwgeSwgeDAsIHkwLCB4MSwgeTEpIHsKICAgICAgICBpZiAoeCA8IHgwICYmIHkgPCB5MCkgewogICAgICAgICAgICByZXR1cm4gZXVjbGlkZWFuRGlzdCh4LCB5LCB4MCwgeTApOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmICh4MCA8PSB4ICYmIHggPCB4MSAmJiB5IDwgeTApIHsKICAgICAgICAgICAgcmV0dXJuIHkwIC0geTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoeDEgPD0geCAmJiB5IDwgeTApIHsKICAgICAgICAgICAgcmV0dXJuIGV1Y2xpZGVhbkRpc3QoeCwgeSwgeDEsIHkwKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoeCA8IHgwICYmIHkwIDw9IHkgJiYgeSA8IHkxKSB7CiAgICAgICAgICAgIHJldHVybiB4MCAtIHg7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHgwIDw9IHggJiYgeCA8IHgxICYmIHkwIDw9IHkgJiYgeSA8IHkxKSB7CiAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgICAgICBlbHNlIGlmICh4MSA8PSB4ICYmIHkwIDw9IHkgJiYgeSA8IHkxKSB7CiAgICAgICAgICAgIHJldHVybiB4IC0geDE7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHggPCB4MCAmJiB5MSA8PSB5KSB7CiAgICAgICAgICAgIHJldHVybiBldWNsaWRlYW5EaXN0KHgsIHksIHgwLCB5MSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHgwIDw9IHggJiYgeCA8IHgxICYmIHkxIDw9IHkpIHsKICAgICAgICAgICAgcmV0dXJuIHkgLSB5MTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoeDEgPD0geCAmJiB5MSA8PSB5KSB7CiAgICAgICAgICAgIHJldHVybiBldWNsaWRlYW5EaXN0KHgsIHksIHgxLCB5MSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgewogICAgICAgICAgICB0aHJvdyAnUG9pbnQgKHgseSkgbXVzdCBiZSBpbiBvbmUgb2YgdGhlIHJlZ2lvbnMgZGVmaW5lZCBhYm92ZS4nOwogICAgICAgIH0KICAgIH0KICAgIC8vIFNWRyBlbGVtZW50cyBzdWNoIGFzIDxnPiBjYW4gb3B0aW9uYWxseSBoYXZlIGEgInRyYW5zZm9ybSIgYXR0cmlidXRlCiAgICAvLyB0aGUgYWx0ZXJzIHRoZSB3YXkgdGhlIGVsZW1lbnQgYW5kIGl0cyBjaGlsZHJlbiBhcmUgZHJhd24uCiAgICAvLyBUaGUgZm9sbG93aW5nIGZ1bmN0aW9uIGhlbHBzIGdlbmVyYXRlIGEgInRyYW5zbGF0ZSBmdW5jdGlvbiIgdmFsdWUKICAgIC8vIGZvciB0aGlzIGF0dHJpYnV0ZS4KICAgIC8vIFNlZQogICAgLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvU1ZHL0F0dHJpYnV0ZS90cmFuc2Zvcm0KICAgIC8vIGZvciBtb3JlIGRldGFpbHMuCiAgICBmdW5jdGlvbiB0cmFuc2xhdGVTdHIoeCwgb3B0X3kpIHsKICAgICAgICBpZiAob3B0X3kgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICByZXR1cm4gJ3RyYW5zbGF0ZSgnICsgeCArICcpJzsKICAgICAgICB9CiAgICAgICAgcmV0dXJuICd0cmFuc2xhdGUoJyArIHggKyAnLCcgKyBvcHRfeSArICcpJzsKICAgIH0KICAgIC8vIFNWRyBlbGVtZW50cyBzdWNoIGFzIDxnPiBjYW4gb3B0aW9uYWxseSBoYXZlIGEgInRyYW5zZm9ybSIgYXR0cmlidXRlCiAgICAvLyB0aGUgYWx0ZXJzIHRoZSB3YXkgdGhlIGVsZW1lbnQgYW5kIGl0cyBjaGlsZHJlbiBhcmUgZHJhd24uCiAgICAvLyBUaGUgZm9sbG93aW5nIGZ1bmN0aW9uIGhlbHBzIGdlbmVyYXRlIGEgInJvdGF0ZSBmdW5jdGlvbiIgdmFsdWUKICAgIC8vIGZvciB0aGlzIGF0dHJpYnV0ZS4KICAgIC8vIFNlZQogICAgLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvU1ZHL0F0dHJpYnV0ZS90cmFuc2Zvcm0KICAgIC8vIGZvciBtb3JlIGRldGFpbHMuCiAgICBmdW5jdGlvbiByb3RhdGVTdHIoYW5nbGUsIHgsIHkpIHsKICAgICAgICBsZXQgcmVzdWx0ID0gJ3JvdGF0ZSgnICsgYW5nbGU7CiAgICAgICAgaWYgKHggIT09IHVuZGVmaW5lZCAmJiB5ICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgcmVzdWx0ID0gcmVzdWx0ICsgJywnICsgeCArICcsJyArIHk7CiAgICAgICAgfQogICAgICAgIHJlc3VsdCA9IHJlc3VsdCArICcpJzsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgfQogICAgZnVuY3Rpb24gaXNOdWxsT3JVbmRlZmluZWQoeCkgewogICAgICAgIHJldHVybiB4ID09PSBudWxsIHx8IHggPT09IHVuZGVmaW5lZDsKICAgIH0KICAgIC8vIEdpdmVuIGEgZDMucXVhZFRyZWUgb2JqZWN0LCB2aXNpdHMgYWxsIHRoZSBwb2ludHMgaW4gaXQKICAgIC8vIHRoYXQgbGllIGluc2lkZSB0aGUgcmVjdGFuZ2xlIFt4MCwgeDEpIHggW3kwLCB5MSkuCiAgICAvLyBGb3IgZWFjaCBzdWNoIHBvaW50IGNhbGxzIHRoZSBnaXZlbiBjYWxsYmFjaywgcGFzc2luZyB0aGUKICAgIC8vIHBvaW50J3MgcXVhZHRyZWUgZGF0YS4KICAgIGZ1bmN0aW9uIHF1YWRUcmVlVmlzaXRQb2ludHNJblJlY3QocXVhZFRyZWUsIHgwLCB5MCwgeDEsIHkxLCBjYWxsYmFjaykgewogICAgICAgIHF1YWRUcmVlLnZpc2l0KChub2RlLCBueDAsIG55MCwgbngxLCBueTEpID0+IHsKICAgICAgICAgICAgLy8gUmVwcmVzZW50cyB0aGUgc2V0IG9mIHBvaW50cyBbbngwLCBueDEpIHggW255MCwgbnkxKS4KICAgICAgICAgICAgaWYgKG5vZGUubGVuZ3RoID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIGRvIHsKICAgICAgICAgICAgICAgICAgICBjb25zdCB4ID0gcXVhZFRyZWUueCgpKG5vZGUuZGF0YSk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgeSA9IHF1YWRUcmVlLnkoKShub2RlLmRhdGEpOwogICAgICAgICAgICAgICAgICAgIGlmICh4MCA8PSB4ICYmIHggPCB4MSAmJiB5MCA8PSB5ICYmIHkgPCB5MSkgewogICAgICAgICAgICAgICAgICAgICAgICBjYWxsYmFjayhub2RlLmRhdGEpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0gd2hpbGUgKChub2RlID0gbm9kZS5uZXh0KSk7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBTa2lwIHRoaXMgbm9kZSBpZiBJbnRlcnNlY3Rpb24oW254MCwgbngxKSB4IFtueTAsIG55MSksCiAgICAgICAgICAgIC8vICBbeDAsIHgxKSB4IFt5MCwgeTEpKSBpcyBlbXB0eSwgb3IgZXF1aXZhbGVudGx5LCBpZgogICAgICAgICAgICAvLyBlaXRoZXIgSW50ZXJzZWN0aW9uKFtueDAsIG54MSksIFt4MCwgeDEpKSBvcgogICAgICAgICAgICAvLyBJbnRlcnNlY3Rpb24oW255MCwgbnkxKSwgW3kwLCB5MSkpIGlzIGVtcHR5LgogICAgICAgICAgICByZXR1cm4gbngwID49IHgxIHx8IG54MSA8PSB4MCB8fCBueTAgPj0geTEgfHwgbnkxIDw9IHkwOwogICAgICAgIH0pOwogICAgfQogICAgLy8gR2l2ZW4gYSBkMy5xdWFkVHJlZSBvYmplY3QsIHZpc2l0cyBhbGwgdGhlIHBvaW50cyBpbiBpdAogICAgLy8gdGhhdCBsaWUgaW5zaWRlIHRoZSBjbG9zZWQgZGlzayBjZW50ZXJlZCBhdCAoY2VudGVyWCwgY2VudGVyWSkKICAgIC8vIHdpdGggdGhlIGdpdmVuIHJhZGl1cy4KICAgIC8vIEZvciBlYWNoIHN1Y2ggcG9pbnQgY2FsbHMgdGhlIGdpdmVuIGNhbGxiYWNrLCBwYXNzaW5nIHRoZQogICAgLy8gcG9pbnQncyBxdWFkdHJlZSBkYXRhIGFuZCB0aGUgZGlzdGFuY2UgZnJvbSB0aGUgcG9pbnQgdG8gdGhlIGNlbnRlcgogICAgLy8gb2YgdGhlIGRpc2suCiAgICBmdW5jdGlvbiBxdWFkVHJlZVZpc2l0UG9pbnRzSW5EaXNrKHF1YWRUcmVlLCBjZW50ZXJYLCBjZW50ZXJZLCByYWRpdXMsIGNhbGxiYWNrKSB7CiAgICAgICAgcXVhZFRyZWUudmlzaXQoKG5vZGUsIHgwLCB5MCwgeDEsIHkxKSA9PiB7CiAgICAgICAgICAgIC8vIFJlcHJlc2VudHMgdGhlIHNldCBvZiBwb2ludHMgW3gwLCB4MSkgeCBbeTAsIHkxKS4KICAgICAgICAgICAgaWYgKG5vZGUubGVuZ3RoID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIGRvIHsKICAgICAgICAgICAgICAgICAgICBjb25zdCB4ID0gcXVhZFRyZWUueCgpKG5vZGUuZGF0YSk7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgeSA9IHF1YWRUcmVlLnkoKShub2RlLmRhdGEpOwogICAgICAgICAgICAgICAgICAgIGNvbnN0IGNlbnRlckRpc3QgPSBldWNsaWRlYW5EaXN0KGNlbnRlclgsIGNlbnRlclksIHgsIHkpOwogICAgICAgICAgICAgICAgICAgIGlmIChjZW50ZXJEaXN0IDw9IHJhZGl1cykgewogICAgICAgICAgICAgICAgICAgICAgICBjYWxsYmFjayhub2RlLmRhdGEsIGNlbnRlckRpc3QpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0gd2hpbGUgKChub2RlID0gbm9kZS5uZXh0KSk7CiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBTa2lwIG5vZGVzIHRoYXQgcmVwcmVzZW50IGEgcmVjdGFuZ2xlIHRoYXQgZG9lcyBub3QgaW50ZXJzZWN0IHRoZQogICAgICAgICAgICAvLyBkaXNrLiBFcXVpdmFsZW50bHksIHNraXAgbm9kZXMgdGhhdCByZXByZXNlbnQgYSByZWN0YW5nbGUgd2hvc2UKICAgICAgICAgICAgLy8gZGlzdGFuY2UgdG8gKGNlbnRlclgsIGNlbnRlclkpIGlzIGxhcmdlciB0aGFuIHJhZGl1cy4KICAgICAgICAgICAgcmV0dXJuIHBvaW50VG9SZWN0YW5nbGVEaXN0KGNlbnRlclgsIGNlbnRlclksIHgwLCB5MCwgeDEsIHkxKSA+IHJhZGl1czsKICAgICAgICB9KTsKICAgIH0KICAgIC8vIFJldHVybnMgYSBTZXQgY29uc2lzdGluZyBvZiBhbGwgZWxlbWVudHMgaW4gJ3NldCcgZm9yIHdoaWNoCiAgICAvLyBwcmVkaWNhdGVGbiBldmFsdWF0ZXMgdG8gYSB0cnV0aHkgdmFsdWUuCiAgICBmdW5jdGlvbiBmaWx0ZXJTZXQoc2V0LCBwcmVkaWNhdGVGbikgewogICAgICAgIGNvbnN0IHJlc3VsdCA9IG5ldyBTZXQoKTsKICAgICAgICBzZXQuZm9yRWFjaCgodmFsKSA9PiB7CiAgICAgICAgICAgIGlmIChwcmVkaWNhdGVGbih2YWwpKSB7CiAgICAgICAgICAgICAgICByZXN1bHQuYWRkKHZhbCk7CiAgICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgfQogICAgLy8gU2V0cyB0aGUgYXJyYXkgcHJvcGVydHkgb2YgcG9seW1lckVsZW1lbnQgdG8gJ25ld0FycmF5JyBpbgogICAgLy8gYSBQb2x5bWVyLSJvYnNlcnZhYmxlIiBtYW5uZXIsIHNvIHRoYXQgb3RoZXIgZWxlbWVudHMgdGhhdCBoYXZlCiAgICAvLyB0aGUgYXJyYXkgYXMgYSBwcm9wZXJ0eSAobGlrZSBhIGRvbS1yZXBlYXQpIHdvdWxkIHVwZGF0ZSBjb3JyZWN0bHkuCiAgICAvLyBBcmdzOgogICAgLy8gICBwb2x5bWVyRWxlbWVudDogdGhlIHBvbHltZXIgZWxlbWVudCB3aG9zZSBhcnJheSBwcm9wZXJ0eSB3ZSB3YW50CiAgICAvLyAgICAgICAgICAgICAgICAgICB0byBjaGFuZ2UuCiAgICAvLyAgIHBhdGhUb0FycmF5OiBhIHBvbHltZXIgZG90LXNlcGFyYXRlZCBwYXRoIHN0cmluZyB0byB0aGUgYXJyYXkKICAgIC8vICAgbmV3QXJyYXk6IHRoZSBuZXcgYXJyYXkgdG8gc2V0LgogICAgZnVuY3Rpb24gc2V0QXJyYXlPYnNlcnZhYmx5KHBvbHltZXJFbGVtZW50LCBwYXRoVG9BcnJheSwgbmV3QXJyYXkpIHsKICAgICAgICBjb25zdCBjdXJyZW50QXJyYXkgPSBwb2x5bWVyRWxlbWVudC5nZXQocGF0aFRvQXJyYXksIHBvbHltZXJFbGVtZW50KTsKICAgICAgICAvLyBJZiB0aGUgY3VycmVudCB2YWx1ZSBpcyBub3QgYW4gYXJyYXksIHRoZW4gd2UgdXNlCiAgICAgICAgLy8gJ3BvbHltZXJFbGVtZW50LnNldCcgdG8gcmVwbGFjZSBpdCB3aXRoIG5ld0FycmF5LgogICAgICAgIGlmICghQXJyYXkuaXNBcnJheShjdXJyZW50QXJyYXkpKSB7CiAgICAgICAgICAgIHBvbHltZXJFbGVtZW50LnNldChwYXRoVG9BcnJheSwgbmV3QXJyYXkpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIC8vIENhbGwgUG9seW1lci5CYXNlLnNwbGljZSgpIHJlbW92aW5nIHRoZSBvbGQgZWxlbWVudHMgYW5kIGluc2VydGluZwogICAgICAgIC8vIHRoZSBuZXcgb25lcy4KICAgICAgICAvLyBXZSBuZWVkIHRvIGNhbGwgcG9seW1lckVsZW1lbnQuc3BsaWNlIHdpdGggJ2FwcGx5JyBzaW5jZSBzcGxpY2UKICAgICAgICAvLyByZWNlaXZlcyBhIHZhcmlhYmxlIGFyZ3VtZW50LWxpc3QgYW5kIHdlIHdhbnQgdG8gcGFzcyBpdCBhbiBhcnJheQogICAgICAgIC8vIChuZXdBcnJheSkuCiAgICAgICAgcG9seW1lckVsZW1lbnQuc3BsaWNlLmFwcGx5KHBvbHltZXJFbGVtZW50LCBbcGF0aFRvQXJyYXksIDAsIGN1cnJlbnRBcnJheS5sZW5ndGhdLmNvbmNhdChuZXdBcnJheSkpOwogICAgfQogICAgLy8gQ29tcHV0ZXMgYSBzaW1wbGUgbm90LXNlY3VyZSAzMi1iaXQgaW50ZWdlciBoYXNoIHZhbHVlIGZvciBhIHN0cmluZy4KICAgIGZ1bmN0aW9uIGhhc2hPZlN0cmluZyhzdHIpIHsKICAgICAgICBsZXQgcmVzdWx0ID0gMDsKICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHN0ci5sZW5ndGg7ICsraSkgewogICAgICAgICAgICByZXN1bHQgPSAocmVzdWx0ICogMzEgKyBzdHIuY2hhckNvZGVBdChpKSkgJiA0Mjk0OTY3Mjk1OwogICAgICAgIH0KICAgICAgICAvLyBCaXR3aXNlIG9wZXJhdGlvbnMgaW4gSmF2YVNjcmlwdCBjb252ZXJ0IG9wZXJhbmRzIHRvIDMyLWJpdCAyJ3MKICAgICAgICAvLyBjb21wbGVtZW50IHJlcHJlc2VudGF0aW9uIGluIHRoZSByYW5nZSBbLTIqKjMxLCgyKiozMSktMV0uIFNoaWZ0IGl0CiAgICAgICAgLy8gdG8gdGhlIHJhbmdlIFswLCAoMioqMzIpLTFdLgogICAgICAgIHJldHVybiByZXN1bHQgKyBNYXRoLnBvdygyLCAzMSk7CiAgICB9CgogICAgdmFyIHRmX2hwYXJhbXNfdXRpbHMgPSAvKiNfX1BVUkVfXyovT2JqZWN0LmZyZWV6ZSh7CiAgICAgICAgX19wcm90b19fOiBudWxsLAogICAgICAgIGhwYXJhbU5hbWU6IGhwYXJhbU5hbWUsCiAgICAgICAgbWV0cmljTmFtZTogbWV0cmljTmFtZSwKICAgICAgICBzY2hlbWFDb2x1bW5OYW1lOiBzY2hlbWFDb2x1bW5OYW1lLAogICAgICAgIG51bUhQYXJhbXM6IG51bUhQYXJhbXMsCiAgICAgICAgbnVtTWV0cmljczogbnVtTWV0cmljcywKICAgICAgICBudW1Db2x1bW5zOiBudW1Db2x1bW5zLAogICAgICAgIGhwYXJhbVZhbHVlQnlOYW1lOiBocGFyYW1WYWx1ZUJ5TmFtZSwKICAgICAgICBtZXRyaWNWYWx1ZUJ5TmFtZTogbWV0cmljVmFsdWVCeU5hbWUsCiAgICAgICAgaHBhcmFtVmFsdWVCeUluZGV4OiBocGFyYW1WYWx1ZUJ5SW5kZXgsCiAgICAgICAgbWV0cmljVmFsdWVCeUluZGV4OiBtZXRyaWNWYWx1ZUJ5SW5kZXgsCiAgICAgICAgY29sdW1uVmFsdWVCeUluZGV4OiBjb2x1bW5WYWx1ZUJ5SW5kZXgsCiAgICAgICAgbnVtZXJpY0NvbHVtbkV4dGVudDogbnVtZXJpY0NvbHVtbkV4dGVudCwKICAgICAgICBnZXRBYnNvbHV0ZUNvbHVtbkluZGV4OiBnZXRBYnNvbHV0ZUNvbHVtbkluZGV4LAogICAgICAgIHNjaGVtYVZpc2libGVDb2x1bW5OYW1lOiBzY2hlbWFWaXNpYmxlQ29sdW1uTmFtZSwKICAgICAgICBudW1WaXNpYmxlSFBhcmFtczogbnVtVmlzaWJsZUhQYXJhbXMsCiAgICAgICAgbnVtVmlzaWJsZU1ldHJpY3M6IG51bVZpc2libGVNZXRyaWNzLAogICAgICAgIG51bVZpc2libGVDb2x1bW5zOiBudW1WaXNpYmxlQ29sdW1ucywKICAgICAgICB2aXNpYmxlTnVtZXJpY0NvbHVtbkV4dGVudDogdmlzaWJsZU51bWVyaWNDb2x1bW5FeHRlbnQsCiAgICAgICAgcHJldHR5UHJpbnRIUGFyYW1WYWx1ZUJ5TmFtZTogcHJldHR5UHJpbnRIUGFyYW1WYWx1ZUJ5TmFtZSwKICAgICAgICBwcmV0dHlQcmludE1ldHJpY1ZhbHVlQnlOYW1lOiBwcmV0dHlQcmludE1ldHJpY1ZhbHVlQnlOYW1lLAogICAgICAgIHNlc3Npb25Hcm91cFdpdGhOYW1lOiBzZXNzaW9uR3JvdXBXaXRoTmFtZSwKICAgICAgICBocGFyYW1WYWx1ZUJ5VmlzaWJsZUluZGV4OiBocGFyYW1WYWx1ZUJ5VmlzaWJsZUluZGV4LAogICAgICAgIG1ldHJpY1ZhbHVlQnlWaXNpYmxlSW5kZXg6IG1ldHJpY1ZhbHVlQnlWaXNpYmxlSW5kZXgsCiAgICAgICAgY29sdW1uVmFsdWVCeVZpc2libGVJbmRleDogY29sdW1uVmFsdWVCeVZpc2libGVJbmRleCwKICAgICAgICBwcmV0dHlQcmludDogcHJldHR5UHJpbnQsCiAgICAgICAgbDJOb3JtU3F1YXJlZDogbDJOb3JtU3F1YXJlZCwKICAgICAgICBldWNsaWRlYW5EaXN0OiBldWNsaWRlYW5EaXN0LAogICAgICAgIHBvaW50VG9SZWN0YW5nbGVEaXN0OiBwb2ludFRvUmVjdGFuZ2xlRGlzdCwKICAgICAgICB0cmFuc2xhdGVTdHI6IHRyYW5zbGF0ZVN0ciwKICAgICAgICByb3RhdGVTdHI6IHJvdGF0ZVN0ciwKICAgICAgICBpc051bGxPclVuZGVmaW5lZDogaXNOdWxsT3JVbmRlZmluZWQsCiAgICAgICAgcXVhZFRyZWVWaXNpdFBvaW50c0luUmVjdDogcXVhZFRyZWVWaXNpdFBvaW50c0luUmVjdCwKICAgICAgICBxdWFkVHJlZVZpc2l0UG9pbnRzSW5EaXNrOiBxdWFkVHJlZVZpc2l0UG9pbnRzSW5EaXNrLAogICAgICAgIGZpbHRlclNldDogZmlsdGVyU2V0LAogICAgICAgIHNldEFycmF5T2JzZXJ2YWJseTogc2V0QXJyYXlPYnNlcnZhYmx5LAogICAgICAgIGhhc2hPZlN0cmluZzogaGFzaE9mU3RyaW5nCiAgICB9KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBIcGFyYW1zU3BsaXRMYXlvdXQgPSBjbGFzcyBIcGFyYW1zU3BsaXRMYXlvdXQgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMub3JpZW50YXRpb24gPSAnaG9yaXpvbnRhbCc7CiAgICAgICAgfQogICAgfTsKICAgIEhwYXJhbXNTcGxpdExheW91dC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHNsb3QgbmFtZT0iY29udGVudCI+PC9zbG90PgoKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CgogICAgICA6aG9zdCBzbG90IHsKICAgICAgICBkaXNwbGF5OiBmbGV4OwogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgOmhvc3QgOjpzbG90dGVkKCopIHsKICAgICAgICBmbGV4OiAwIDAgYXV0bzsKICAgICAgfQoKICAgICAgOmhvc3QoW29yaWVudGF0aW9uPSdob3Jpem9udGFsJ10pIHNsb3QgewogICAgICAgIGZsZXgtZGlyZWN0aW9uOiByb3c7CiAgICAgICAgb3ZlcmZsb3cteDogYXV0bzsKICAgICAgfQoKICAgICAgOmhvc3QoW29yaWVudGF0aW9uPSd2ZXJ0aWNhbCddKSBzbG90IHsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uOwogICAgICAgIG92ZXJmbG93LXk6IGF1dG87CiAgICAgIH0KCiAgICAgIDpob3N0IDo6c2xvdHRlZCgqOm5vdCg6bGFzdC1jaGlsZCkpIHsKICAgICAgICBib3JkZXI6IDAgc29saWQgdmFyKC0tZGl2aWRlci1jb2xvciwgI2NjYyk7CiAgICAgIH0KCiAgICAgIDpob3N0KFtvcmllbnRhdGlvbj0ndmVydGljYWwnXSkgOjpzbG90dGVkKCo6bm90KDpsYXN0LWNoaWxkKSkgewogICAgICAgIGJvcmRlci1ib3R0b20td2lkdGg6IDVweDsKICAgICAgfQoKICAgICAgOmhvc3QoW29yaWVudGF0aW9uPSdob3Jpem9udGFsJ10pIDo6c2xvdHRlZCgqOm5vdCg6bGFzdC1jaGlsZCkpIHsKICAgICAgICBib3JkZXItcmlnaHQtd2lkdGg6IDVweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcsIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIEhwYXJhbXNTcGxpdExheW91dC5wcm90b3R5cGUsICJvcmllbnRhdGlvbiIsIHZvaWQgMCk7CiAgICBIcGFyYW1zU3BsaXRMYXlvdXQgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCdocGFyYW1zLXNwbGl0LWxheW91dCcpCiAgICBdLCBIcGFyYW1zU3BsaXRMYXlvdXQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBUaGUgdGYtaHBhcmFtcy1xdWVyeS1wYW5lIGVsZW1lbnQgaW1wbGVtZW50cyBjb250cm9scyBmb3IgcXVlcnlpbmcgdGhlCiAgICAgKiBzZXJ2ZXIgZm9yIGEgbGlzdCBvZiBzZXNzaW9uIGdyb3Vwcy4gSXQgcHJvdmlkZXMgZmlsdGVyaW5nLCBhbmQKICAgICAqIHNvcnRpbmcgY29udHJvbHMuCiAgICAgKgogICAgICogVE9ETyhlcmV6KTogQWRkIGFnZ3JlZ2F0aW9uIGNvbnRyb2xzIGZvciByZXBlYXRlZCBzZXNzaW9ucy4KICAgICAqLwogICAgbGV0IFRmSHBhcmFtc1F1ZXJ5UGFuZSA9IGNsYXNzIFRmSHBhcmFtc1F1ZXJ5UGFuZSBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvLyBDb250YWlucyB0aGUgc2NoZW1hIGFuZCBjb2x1bW5zIHZpc2liaWxpdHkgc3RhdHVzLgogICAgICAgICAgICAvLyBXZSB1c2UgYSBzaW5nbGUgb2JqZWN0IHdlIGNhbGwgJ2NvbmZpZ3VyYXRpb24nIHRvIGhvbGQgYm90aCBvZgogICAgICAgICAgICAvLyB0aGVzZSBwcm9wZXJ0aWVzLCBzaW5jZSBQb2x5bWVyICh2MSkgZG9lc24ndCBhbGxvdyBhdG9taWMKICAgICAgICAgICAgLy8gY2hhbmdlcyB0byBtdWx0aXBsZSBwcm9wZXJ0aWVzICh0aGF0IGlzLCBzZW5kaW5nIHRoZSBub3RpZmljYXRpb24KICAgICAgICAgICAgLy8gdG8gZG93bnN0cmVhbSBjb25zdW1lcnMgb25seSBhZnRlciBhbGwgcHJvcGVydGllcyBoYXZlIGJlZW4gdXBkYXRlZCkuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIFByb3BlcnRpZXM6CiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tCiAgICAgICAgICAgIC8vIHNjaGVtYS5ocGFyYW1Db2x1bW5zW2ldLmhwYXJhbUluZm8gY29udGFpbnMgdGhlIEhQYXJhbUluZm8gcHJvdG9jb2wKICAgICAgICAgICAgLy8gYnVmZmVyIHJlcHJlc2VudGluZyB0aGUgaXRoIGhwYXJhbS4KICAgICAgICAgICAgLy8gc2NoZW1hLm1ldHJpY0NvbHVtbnNbaV0ubWV0cmljSW5mbyBjb250YWlucyB0aGUgTWV0cmljSW5mbyBwcm90b2NvbAogICAgICAgICAgICAvLyBidWZmZXIgcmVwcmVzZW50aW5nIHRoZSBpdGggbWV0cmljLgogICAgICAgICAgICAvLwogICAgICAgICAgICAvLyBjb2x1bW5zVmlzaWJpbGl0eVtdLgogICAgICAgICAgICAvLyBBIGJvb2xlYW4gYXJyYXkgd2hvc2UgaXRoIGVudHJ5IGlzIHRydWUgaWYKICAgICAgICAgICAgLy8gdGhlIGl0aCBjb2x1bW4gaXMgdmlzaWJsZSAoc2VsZWN0ZWQgdG8gYmUgZGlzcGxheWVkIGJ5IHRoZSB1c2VyKS4KICAgICAgICAgICAgLy8gQ29sdW1ucyBhcmUgaW5kZXhlZCBieSBsaXN0aW5nIHRoZSBoeXBlcnBhcmFtZXRlcnMgZmlyc3QgaW4KICAgICAgICAgICAgLy8gdGhlIG9yZGVyIHRoZXkgYXJlIHJlcHJlc2VudGVkIGJ5IHNjaGVtYS5ocGFyYW1Db2x1bW5zLCBmb2xsb3dlZAogICAgICAgICAgICAvLyBieSB0aGUgbWV0cmljcyBpbiB0aGUgb3JkZXIgdGhleSBhcmUgcmVwcmVzZW50ZWQgYnkKICAgICAgICAgICAgLy8gc2NoZW1hLm1ldHJpY0NvbHVtbnMuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIHZpc2libGVTY2hlbWEuCiAgICAgICAgICAgIC8vIERFUFJFQ0FURUQuIE5ldyBjb2RlIHNob3VsZCB1c2UgdGhlIHNjaGVtYSBhbmQgY29sdW1uVmlzaWJpbGUKICAgICAgICAgICAgLy8gcHJvcGVydGllcyBpbnN0ZWFkLgogICAgICAgICAgICAvLyBUT0RPKCk6IFJlbW92ZSB3aGVuIGFsbCBjb25zdW1lcnMgYXJlIG1pZ3JhdGVkIHRvIHVzZSB0aGUKICAgICAgICAgICAgLy8gc2NoZW1hIGFuZCBjb2x1bW5WaXNpYmlsZSBmaWVsZHMuCiAgICAgICAgICAgIC8vIENvbnRhaW5zIGFycmF5cyBvZiBIUGFyYW1JbmZvIGFuZCBNZXRyaWNJbmZvIHByb3RvY29sIGJ1ZmZlcnMKICAgICAgICAgICAgLy8gY29uc2lzdGluZyBvZiBvbmx5IHRoZSB2aXNpYmxlIGh5cGVycGFyYW1ldGVycyBhbmQgbWV0cmljcywKICAgICAgICAgICAgLy8gcmVzcGVjdGl2ZWx5LgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUge3sKICAgICAgICAgICAgICogICAgc2NoZW1hOiB7CiAgICAgICAgICAgICAqICAgICAgaHBhcmFtQ29sdW1uczogQXJyYXk8e2hwYXJhbUluZm86IE9iamVjdH0+LAogICAgICAgICAgICAgKiAgICAgIG1ldHJpY0NvbHVtbnM6IEFycmF5PHttZXRyaWNJbmZvOiBPYmplY3R9PiwKICAgICAgICAgICAgICogICAgfSwKICAgICAgICAgICAgICogICAgY29sdW1uc1Zpc2liaWxpdHk6IEFycmF5PEJvb2xlYW4+LAogICAgICAgICAgICAgKiAgICB2aXNpYmxlU2NoZW1hOiB7CiAgICAgICAgICAgICAqICAgICAgaHBhcmFtSW5mb3M6IEFycmF5PE9iamVjdD4sCiAgICAgICAgICAgICAqICAgICAgbWV0cmljSW5mb3M6IEFycmF5PE9iamVjdD4sCiAgICAgICAgICAgICAqICAgIH0KICAgICAgICAgICAgICogfX0KICAgICAgICAgICAgICovCiAgICAgICAgICAgIHRoaXMuY29uZmlndXJhdGlvbiA9IHsKICAgICAgICAgICAgICAgIHNjaGVtYTogewogICAgICAgICAgICAgICAgICAgIGhwYXJhbUNvbHVtbnM6IFtdLAogICAgICAgICAgICAgICAgICAgIG1ldHJpY0NvbHVtbnM6IFtdLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgIGNvbHVtbnNWaXNpYmlsaXR5OiBbXSwKICAgICAgICAgICAgICAgIHZpc2libGVTY2hlbWE6IHsKICAgICAgICAgICAgICAgICAgICBocGFyYW1JbmZvczogW10sCiAgICAgICAgICAgICAgICAgICAgbWV0cmljSW5mb3M6IFtdLAogICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgfTsKICAgICAgICAgICAgLy8gVGhlIGxhdGVzdCBsaXN0IG9mIHNlc3Npb24gZ3JvdXBzIHJlY2VpdmVkIGZyb20gdGhlIHNlcnZlci4KICAgICAgICAgICAgLy8gU2VlIHRoZSBjb21tZW50cyBpbiB0aGUgX2J1aWxkTGlzdFNlc3Npb25Hcm91cHNSZXF1ZXN0KCkgbWV0aG9kcyBmb3IKICAgICAgICAgICAgLy8gbW9yZSBkZXRhaWxzLgogICAgICAgICAgICB0aGlzLnNlc3Npb25Hcm91cHMgPSBbXTsKICAgICAgICAgICAgLy8gV2UgdHJhY2sgYm90aCAiZGF0YSBmb3VuZCIgYW5kICJkYXRhIG5vdCBmb3VuZCIsIGJlY2F1c2UgdGhpcwogICAgICAgICAgICAvLyBtYWtlcyBpdCBleHBlZGllbnQgdG8gZGlzcGxheSBub3RoaW5nIHVudGlsIHRoZSBpbml0aWFsIGZldGNoIGlzCiAgICAgICAgICAgIC8vIGNvbXBsZXRlLiAgSW4gdGhlIGFic2VuY2Ugb2YgdGhpcyAidW5kZWZpbmVkIiBjYXNlLCB3ZSB3b3VsZCBlbmQgdXAKICAgICAgICAgICAgLy8gYnJpZWZseSBkaXNwbGF5aW5nIHRoZSAibm8gZGF0YSIgbWVzc2FnZSBiZWZvcmUgdGhlIGRhdGEgYXJyaXZlcy4KICAgICAgICAgICAgLy8gTm90ZSB0aGF0LCBpbiB0aGUgY29udGV4dCBvZiBhIGRvbS1pZiBjb25kaXRpb24sIHdlIGNhbm5vdCBlYXNpbHkKICAgICAgICAgICAgLy8gZGlzdGluZ3Vpc2ggYmV0d2VlbiBmYWxzZSBhbmQgdW5kZWZpbmVkLgogICAgICAgICAgICB0aGlzLmRhdGFMb2FkZWRXaXRoTm9uRW1wdHlIcGFyYW1zID0gZmFsc2U7CiAgICAgICAgICAgIC8vIE5vdGUgdGhhdCBgZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXMgPSBmYWxzZWAgbWVhbnMgdGhhdCB3ZSBkb24ndAogICAgICAgICAgICAvLyBrbm93IHlldCB3aGV0aGVyIGRhdGEgd2lsbCBiZSBmb3VuZCBvciBub3QgKGkuZS4sIHRoZSBmZXRjaCBoYXMgbm90CiAgICAgICAgICAgIC8vIHlldCByZXR1cm5lZCkuICBgZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXMgPSB0cnVlYCBtZWFucyB0aGUgZmV0Y2gKICAgICAgICAgICAgLy8gY29tcGxldGVkLCBhbmQgdGhlcmUgcmVhbGx5IGlzIG5vIGRhdGEuCiAgICAgICAgICAgIHRoaXMuZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXMgPSBmYWxzZTsKICAgICAgICAgICAgLy8gQW4gYXJyYXkgb2Ygb2JqZWN0cyBlYWNoIHJlcHJlc2VudGluZyBpbmZvcm1hdGlvbiBhYm91dCBhIHNlc3Npb24KICAgICAgICAgICAgLy8gc3RhdHVzIGFuZCB3aGV0aGVyIGl0IGlzIGN1cnJlbnRseSBhbGxvd2VkIGJ5IHRoZSB1c2VyLgogICAgICAgICAgICB0aGlzLl9zdGF0dXNlcyA9IFsKICAgICAgICAgICAgICAgIHsgdmFsdWU6ICdTVEFUVVNfVU5LTk9XTicsIGRpc3BsYXlOYW1lOiAnVW5rbm93bicsIGFsbG93ZWQ6IHRydWUgfSwKICAgICAgICAgICAgICAgIHsgdmFsdWU6ICdTVEFUVVNfU1VDQ0VTUycsIGRpc3BsYXlOYW1lOiAnU3VjY2VzcycsIGFsbG93ZWQ6IHRydWUgfSwKICAgICAgICAgICAgICAgIHsgdmFsdWU6ICdTVEFUVVNfRkFJTFVSRScsIGRpc3BsYXlOYW1lOiAnRmFpbHVyZScsIGFsbG93ZWQ6IHRydWUgfSwKICAgICAgICAgICAgICAgIHsgdmFsdWU6ICdTVEFUVVNfUlVOTklORycsIGRpc3BsYXlOYW1lOiAnUnVubmluZycsIGFsbG93ZWQ6IHRydWUgfSwKICAgICAgICAgICAgXTsKICAgICAgICAgICAgLy8gQSBwcm9taXNlIHRoYXQgcmVzb2x2ZXMgYWZ0ZXIgdGhlIGluaXRpYWwgZ2V0RXhwZXJpbWVudCBuZXR3b3JrIFJQQwogICAgICAgICAgICAvLyByZXNvbHZlcy4gVXNlZCBmb3IgdW5pdC10ZXN0IHRvIGFsbG93IHRlc3RpbmcgdG8gcnVuIGFmdGVyIHRoZQogICAgICAgICAgICAvLyBlbGVtZW50IGhhcyBpbml0aWFsaXplZC4KICAgICAgICAgICAgdGhpcy5fZ2V0RXhwZXJpbWVudFJlc29sdmVkID0gbmV3IFByb21pc2UoKHJlc29sdmUpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuX3Jlc29sdmVHZXRFeHBlcmltZW50ID0gcmVzb2x2ZTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIEEgdGZfYmFja2VuZC5jYW5jZWxsZXIgdXNlZCB0byBrZWVwIHRyYWNrIG9mIHBlbmRpbmcKICAgICAgICAgICAgLy8gTGlzdFNlc3Npb25Hcm91cHMgcmVxdWVzdHMgYW5kIGNhbmNlbCB0aGVpciByZXN1bHRpbmcgVUkgdXBkYXRlcwogICAgICAgICAgICAvLyB3aGVuIGEgbmV3IExpc3RTZXNzaW9uR3JvdXBzIHJlcXVlc3QgaXMgbWFkZS4KICAgICAgICAgICAgdGhpcy5fbGlzdFNlc3Npb25Hcm91cHNDYW5jZWxsZXIgPSBuZXcgQ2FuY2VsbGVyKCk7CiAgICAgICAgICAgIC8vIFRoZSB2YWx1ZSBhbmQgaW52YWxpZCBwcm9wZXJ0aWVzIG9mIHRoZSAncGFnZS1zaXplJyBpbnB1dCBib3guCiAgICAgICAgICAgIHRoaXMuX3BhZ2VTaXplSW5wdXQgPSB7IHZhbHVlOiAnMTAwJywgaW52YWxpZDogZmFsc2UgfTsKICAgICAgICAgICAgLy8gVGhlIHZhbHVlIGFuZCBpbnZhbGlkIHByb3BlcnRpZXMgb2YgdGhlICdwYWdlLW51bWJlcicgaW5wdXQgYm94LgogICAgICAgICAgICB0aGlzLl9wYWdlTnVtYmVySW5wdXQgPSB7IHZhbHVlOiAnMScsIGludmFsaWQ6IGZhbHNlIH07CiAgICAgICAgICAgIC8vIFRoZSBzdHJpbmcgZGlzcGxheWluZyB0aGUgdG90YWwgbnVtYmVyIG9mIHBhZ2VzIG9yICc/JyBpZiB1bmtub3duLgogICAgICAgICAgICB0aGlzLl9wYWdlQ291bnRTdHIgPSAnPyc7CiAgICAgICAgICAgIHRoaXMuX2hwYXJhbU5hbWUgPSBocGFyYW1OYW1lOwogICAgICAgICAgICB0aGlzLl9tZXRyaWNOYW1lID0gbWV0cmljTmFtZTsKICAgICAgICAgICAgdGhpcy5fcHJldHR5UHJpbnQgPSBwcmV0dHlQcmludDsKICAgICAgICB9CiAgICAgICAgcmVsb2FkKCkgewogICAgICAgICAgICB0aGlzLl9xdWVyeVNlcnZlcigpOwogICAgICAgIH0KICAgICAgICBfY3N2VXJsKHJlcXVlc3QsIGNvbmZpZ3VyYXRpb24pIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Rvd25sb2FkRGF0YVVybChyZXF1ZXN0LCBjb25maWd1cmF0aW9uLCAnY3N2Jyk7CiAgICAgICAgfQogICAgICAgIF9qc29uVXJsKHJlcXVlc3QsIGNvbmZpZ3VyYXRpb24pIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2Rvd25sb2FkRGF0YVVybChyZXF1ZXN0LCBjb25maWd1cmF0aW9uLCAnanNvbicpOwogICAgICAgIH0KICAgICAgICBfbGF0ZXhVcmwocmVxdWVzdCwgY29uZmlndXJhdGlvbikgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fZG93bmxvYWREYXRhVXJsKHJlcXVlc3QsIGNvbmZpZ3VyYXRpb24sICdsYXRleCcpOwogICAgICAgIH0KICAgICAgICBfZG93bmxvYWREYXRhVXJsKHJlcXVlc3QsIGNvbmZpZ3VyYXRpb24sIGZvcm1hdCkgewogICAgICAgICAgICBjb25zdCB2aXNpYmlsaXR5ID0gY29uZmlndXJhdGlvbi5jb2x1bW5zVmlzaWJpbGl0eTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuYmFja2VuZC5nZXREb3dubG9hZFVybChmb3JtYXQsIHJlcXVlc3QsIHZpc2liaWxpdHkpOwogICAgICAgIH0KICAgICAgICAvLyBTZW5kcyBhIHJlcXVlc3QgZm9yIGV4cGVyaW1lbnQgdG8gdGhlIHNlcnZlciwgYW5kIHVwZGF0ZXMKICAgICAgICAvLyB0aGUgc3RhdGUgb2YgdGhpcyBlbGVtZW50IGFjY29yZGluZ2x5LiBDdXJyZW50bHksIG9ubHkgY2FsbGVkCiAgICAgICAgLy8gb25jZSBvbiBlbGVtZW50IGluaXRpYWxpemF0aW9uLgogICAgICAgIF9jb21wdXRlRXhwZXJpbWVudEFuZFJlbGF0ZWRQcm9wcygpIHsKICAgICAgICAgICAgY29uc3QgdXRpbHMgPSB0Zl9ocGFyYW1zX3V0aWxzOwogICAgICAgICAgICBpZiAodXRpbHMuaXNOdWxsT3JVbmRlZmluZWQodGhpcy5iYWNrZW5kKSB8fAogICAgICAgICAgICAgICAgdXRpbHMuaXNOdWxsT3JVbmRlZmluZWQodGhpcy5leHBlcmltZW50TmFtZSkpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBleHBlcmltZW50UmVxdWVzdCA9IHsKICAgICAgICAgICAgICAgIGV4cGVyaW1lbnROYW1lOiB0aGlzLmV4cGVyaW1lbnROYW1lLAogICAgICAgICAgICB9OwogICAgICAgICAgICB0aGlzLmJhY2tlbmQKICAgICAgICAgICAgICAgIC5nZXRFeHBlcmltZW50KGV4cGVyaW1lbnRSZXF1ZXN0KQogICAgICAgICAgICAgICAgLnRoZW4oKGV4cGVyaW1lbnQpID0+IHsKICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNFcXVhbChleHBlcmltZW50LCB0aGlzLl9leHBlcmltZW50KSkgewogICAgICAgICAgICAgICAgICAgIC8vIE5vIG5lZWQgdG8gdXBkYXRlIGFueXRoaW5nIGlmIHRoZXJlIGFyZSBubyBjaGFuZ2VzLgogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfZXhwZXJpbWVudCcsIGV4cGVyaW1lbnQpOwogICAgICAgICAgICAgICAgdGhpcy5fY29tcHV0ZUhQYXJhbXMoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbXB1dGVNZXRyaWNzKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9xdWVyeVNlcnZlcigpOwogICAgICAgICAgICAgICAgdGhpcy5fcmVzb2x2ZUdldEV4cGVyaW1lbnQoKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5maW5hbGx5KCgpID0+IHsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbXB1dGVEYXRhRm91bmQoKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlRGF0YUZvdW5kKCkgewogICAgICAgICAgICBjb25zdCByZXN1bHQgPSBCb29sZWFuKHRoaXMuX2V4cGVyaW1lbnQgJiYKICAgICAgICAgICAgICAgIHRoaXMuX2V4cGVyaW1lbnQuaHBhcmFtSW5mb3MgJiYKICAgICAgICAgICAgICAgIHRoaXMuX2V4cGVyaW1lbnQuaHBhcmFtSW5mb3MubGVuZ3RoID4gMCAmJgogICAgICAgICAgICAgICAgdGhpcy5fZXhwZXJpbWVudC5tZXRyaWNJbmZvcyAmJgogICAgICAgICAgICAgICAgdGhpcy5fZXhwZXJpbWVudC5tZXRyaWNJbmZvcy5sZW5ndGggPiAwKTsKICAgICAgICAgICAgdGhpcy5zZXQoJ2RhdGFMb2FkZWRXaXRoTm9uRW1wdHlIcGFyYW1zJywgcmVzdWx0KTsKICAgICAgICAgICAgdGhpcy5zZXQoJ2RhdGFMb2FkZWRXaXRoRW1wdHlIcGFyYW1zJywgIXJlc3VsdCk7CiAgICAgICAgfQogICAgICAgIC8vIFVwZGF0ZXMgdGhlIF9ocGFyYW1zIHByb3BlcnR5IGZyb20gdGhlIF9leHBlcmltZW50IHByb3BlcnR5LgogICAgICAgIF9jb21wdXRlSFBhcmFtcygpIHsKICAgICAgICAgICAgY29uc3QgcmVzdWx0ID0gW107CiAgICAgICAgICAgIGNvbnN0IGtOdW1IUGFyYW1zVG9EaXNwbGF5QnlEZWZhdWx0ID0gNTsKICAgICAgICAgICAgdGhpcy5fZXhwZXJpbWVudC5ocGFyYW1JbmZvcy5mb3JFYWNoKChhbkluZm8sIGluZGV4KSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBocGFyYW0gPSB7CiAgICAgICAgICAgICAgICAgICAgaW5mbzogYW5JbmZvLAogICAgICAgICAgICAgICAgICAgIGRpc3BsYXllZDogaW5kZXggPCBrTnVtSFBhcmFtc1RvRGlzcGxheUJ5RGVmYXVsdCwKICAgICAgICAgICAgICAgICAgICBmaWx0ZXI6IHt9LAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGlmIChocGFyYW0uaW5mby5oYXNPd25Qcm9wZXJ0eSgnZG9tYWluRGlzY3JldGUnKSkgewogICAgICAgICAgICAgICAgICAgIGhwYXJhbS5maWx0ZXIuZG9tYWluRGlzY3JldGUgPSBbXTsKICAgICAgICAgICAgICAgICAgICBocGFyYW0uaW5mby5kb21haW5EaXNjcmV0ZS5mb3JFYWNoKCh2YWwpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgaHBhcmFtLmZpbHRlci5kb21haW5EaXNjcmV0ZS5wdXNoKHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZhbHVlOiB2YWwsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGVja2VkOiB0cnVlLAogICAgICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGhwYXJhbS5pbmZvLnR5cGUgPT09ICdEQVRBX1RZUEVfQk9PTCcpIHsKICAgICAgICAgICAgICAgICAgICBocGFyYW0uZmlsdGVyLmRvbWFpbkRpc2NyZXRlID0gWwogICAgICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjaGVja2VkOiB0cnVlLAogICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogdHJ1ZSwKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNoZWNrZWQ6IHRydWUsCiAgICAgICAgICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgICAgICAgICAgXTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGhwYXJhbS5pbmZvLnR5cGUgPT09ICdEQVRBX1RZUEVfRkxPQVQ2NCcpIHsKICAgICAgICAgICAgICAgICAgICBocGFyYW0uZmlsdGVyLmludGVydmFsID0gewogICAgICAgICAgICAgICAgICAgICAgICBtaW46IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZhbHVlOiAnJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludmFsaWQ6IGZhbHNlLAogICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICBtYXg6IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIHZhbHVlOiAnJywKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludmFsaWQ6IGZhbHNlLAogICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIGlmIChocGFyYW0uaW5mby50eXBlID09PSAnREFUQV9UWVBFX1NUUklORycpIHsKICAgICAgICAgICAgICAgICAgICBocGFyYW0uZmlsdGVyLnJlZ2V4cCA9ICcnOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgY29uc29sZS53YXJuKCd1bmtub3duIGhwYXJhbS5pbmZvLnR5cGU6ICVzJywgaHBhcmFtLmluZm8udHlwZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXN1bHQucHVzaChocGFyYW0pOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5zZXQoJ19ocGFyYW1zJywgcmVzdWx0KTsKICAgICAgICB9CiAgICAgICAgLy8gVXBkYXRlcyB0aGUgX21ldHJpY3MgcHJvcGVydHkgZnJvbSB0aGUgX2V4cGVyaW1lbnQgcHJvcGVydHkuCiAgICAgICAgX2NvbXB1dGVNZXRyaWNzKCkgewogICAgICAgICAgICBjb25zdCByZXN1bHQgPSBbXTsKICAgICAgICAgICAgLy8gQnkgZGVmYXVsdCB3ZSBkaXNwbGF5IHRoZSBmaXJzdCBrTnVtTWV0cmljc1RvRGlzcGxheUJ5RGVmYXVsdCBtZXRyaWNzCiAgICAgICAgICAgIC8vIGFuZCBub3QgdGhlIHJlc3QuCiAgICAgICAgICAgIGNvbnN0IGtOdW1NZXRyaWNzVG9EaXNwbGF5QnlEZWZhdWx0ID0gNTsKICAgICAgICAgICAgdGhpcy5fZXhwZXJpbWVudC5tZXRyaWNJbmZvcy5mb3JFYWNoKChpbmZvLCBpbmRleCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgbWV0cmljID0gewogICAgICAgICAgICAgICAgICAgIGluZm86IGluZm8sCiAgICAgICAgICAgICAgICAgICAgZmlsdGVyOiB7CiAgICAgICAgICAgICAgICAgICAgICAgIGludGVydmFsOiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBtaW46IHsKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogJycsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaW52YWxpZDogZmFsc2UsCiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgICAgICAgICAgbWF4OiB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgdmFsdWU6ICcnLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGludmFsaWQ6IGZhbHNlLAogICAgICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICAgICAgfSwKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgICAgIGRpc3BsYXllZDogaW5kZXggPCBrTnVtTWV0cmljc1RvRGlzcGxheUJ5RGVmYXVsdCwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICByZXN1bHQucHVzaChtZXRyaWMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5zZXQoJ19tZXRyaWNzJywgcmVzdWx0KTsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVTY2hlbWEoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5faHBhcmFtcyB8fCAhdGhpcy5fbWV0cmljcykgewogICAgICAgICAgICAgICAgcmV0dXJuIHsgaHBhcmFtQ29sdW1uczogW10sIG1ldHJpY0NvbHVtbnM6IFtdIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGhwYXJhbUNvbHVtbnM6IHRoaXMuX2hwYXJhbXMubWFwKChocGFyYW0pID0+ICh7CiAgICAgICAgICAgICAgICAgICAgaHBhcmFtSW5mbzogaHBhcmFtLmluZm8sCiAgICAgICAgICAgICAgICB9KSksCiAgICAgICAgICAgICAgICBtZXRyaWNDb2x1bW5zOiB0aGlzLl9tZXRyaWNzLm1hcCgobWV0cmljKSA9PiAoewogICAgICAgICAgICAgICAgICAgIG1ldHJpY0luZm86IG1ldHJpYy5pbmZvLAogICAgICAgICAgICAgICAgfSkpLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBfdXBkYXRlQ29uZmlndXJhdGlvbigpIHsKICAgICAgICAgICAgdGhpcy5kZWJvdW5jZSgnX3VwZGF0ZUNvbmZpZ3VyYXRpb24nLCAoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLmNvbmZpZ3VyYXRpb24gPSB7CiAgICAgICAgICAgICAgICAgICAgc2NoZW1hOiB0aGlzLl9jb21wdXRlU2NoZW1hKCksCiAgICAgICAgICAgICAgICAgICAgY29sdW1uc1Zpc2liaWxpdHk6IHRoaXMuX2NvbXB1dGVDb2x1bW5zVmlzaWJpbGl0eSgpLAogICAgICAgICAgICAgICAgICAgIHZpc2libGVTY2hlbWE6IHRoaXMuX2NvbXB1dGVWaXNpYmxlU2NoZW1hKCksCiAgICAgICAgICAgICAgICB9OwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2NvbXB1dGVDb2x1bW5zVmlzaWJpbGl0eSgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9ocGFyYW1zIHx8ICF0aGlzLl9tZXRyaWNzKQogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICByZXR1cm4gdGhpcy5faHBhcmFtcwogICAgICAgICAgICAgICAgLm1hcCgoaHBhcmFtKSA9PiBocGFyYW0uZGlzcGxheWVkKQogICAgICAgICAgICAgICAgLmNvbmNhdCh0aGlzLl9tZXRyaWNzLm1hcCgobWV0cmljKSA9PiBtZXRyaWMuZGlzcGxheWVkKSk7CiAgICAgICAgfQogICAgICAgIF9jb21wdXRlVmlzaWJsZVNjaGVtYSgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9ocGFyYW1zIHx8ICF0aGlzLl9tZXRyaWNzKSB7CiAgICAgICAgICAgICAgICByZXR1cm4geyBocGFyYW1JbmZvczogW10sIG1ldHJpY0luZm9zOiBbXSB9OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IG5ld0hQYXJhbUluZm9zID0gdGhpcy5faHBhcmFtcwogICAgICAgICAgICAgICAgLmZpbHRlcigoaHBhcmFtKSA9PiBocGFyYW0uZGlzcGxheWVkKQogICAgICAgICAgICAgICAgLm1hcCgoaHBhcmFtKSA9PiBocGFyYW0uaW5mbyk7CiAgICAgICAgICAgIGNvbnN0IG5ld01ldHJpY0luZm9zID0gdGhpcy5fbWV0cmljcwogICAgICAgICAgICAgICAgLmZpbHRlcigobWV0cmljKSA9PiBtZXRyaWMuZGlzcGxheWVkKQogICAgICAgICAgICAgICAgLm1hcCgobWV0cmljKSA9PiBtZXRyaWMuaW5mbyk7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBocGFyYW1JbmZvczogbmV3SFBhcmFtSW5mb3MsCiAgICAgICAgICAgICAgICBtZXRyaWNJbmZvczogbmV3TWV0cmljSW5mb3MsCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIC8vIFNlbmRzIGEgcXVlcnkgdG8gdGhlIHNlcnZlciBmb3IgdGhlIGxpc3Qgb2Ygc2Vzc2lvbiBncm91cHMuCiAgICAgICAgLy8gQXN5bmNocm9ub3VzbHkgdXBkYXRlcyB0aGUgc2Vzc2lvbkdyb3VwcyBwcm9wZXJ0eSB3aXRoIHRoZSByZXNwb25zZS4KICAgICAgICBfcXVlcnlTZXJ2ZXIoKSB7CiAgICAgICAgICAgIHRoaXMuZGVib3VuY2UoJ3F1ZXJ5U2VydmVyJywgKCkgPT4gdGhpcy5fcXVlcnlTZXJ2ZXJOb0RlYm91bmNlKCksIDEwMCk7CiAgICAgICAgfQogICAgICAgIC8vIERpcmVjdGx5IHF1ZXJpZXMgdGhlIHNlcnZlciB3aXRob3V0IGEgZGVib3VuY2UsIGNhbGxlZCBpbiBxdWVyeVNlcnZlcigpCiAgICAgICAgLy8gYWJvdmUuIFJldHVybnMgYSBwcm9taXNlLCBmb3IgdXNlIGluIHVuaXQtdGVzdHMsIHRoYXQgcmVzb2x2ZXMgKHdpdGgKICAgICAgICAvLyAndW5kZWZpbmVkJykgd2hlbiB0aGUgTGlzdFNlc3Npb25Hcm91cHMgUlBDIHJldHVybnMuCiAgICAgICAgX3F1ZXJ5U2VydmVyTm9EZWJvdW5jZSgpIHsKICAgICAgICAgICAgaWYgKCF0aGlzLl9ocGFyYW1zIHx8ICF0aGlzLl9tZXRyaWNzKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NlbmRMaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QoKS50aGVuKHRoaXMuX2xpc3RTZXNzaW9uR3JvdXBzQ2FuY2VsbGVyLmNhbmNlbGxhYmxlKCh7IHZhbHVlLCBjYW5jZWxsZWQgfSkgPT4gewogICAgICAgICAgICAgICAgaWYgKGNhbmNlbGxlZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFRoZSBzZXJ2ZXIgbWF5IG5vdCBzdXBwb3J0IGEgInRvdGFsU2l6ZSIgZmllbGQgaW4KICAgICAgICAgICAgICAgIC8vIHdoaWNoIGNhc2UgdGhpcyBmaWVsZCB3b3VsZCBiZSBuZWdhdGl2ZSwgYW5kIHdlCiAgICAgICAgICAgICAgICAvLyBwb3B1bGF0ZSB0aGUgcGFnZSBjb3VudCB3aXRoIGEgIj8iLgogICAgICAgICAgICAgICAgaWYgKHZhbHVlLnRvdGFsU2l6ZSA+PSAwKSB7CiAgICAgICAgICAgICAgICAgICAgY29uc3QgcGFnZVNpemUgPSArdGhpcy5fcGFnZVNpemVJbnB1dC52YWx1ZTsKICAgICAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3BhZ2VDb3VudFN0cicsIFN0cmluZyhNYXRoLmNlaWwodmFsdWUudG90YWxTaXplIC8gcGFnZVNpemUpKSk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXQoJ190b3RhbFNlc3Npb25Hcm91cHNDb3VudFN0cicsIHZhbHVlLnRvdGFsU2l6ZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3BhZ2VDb3VudFN0cicsICc/Jyk7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5zZXQoJ190b3RhbFNlc3Npb25Hcm91cHNDb3VudFN0cicsICdVbmtub3duJyk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBzZXRBcnJheU9ic2VydmFibHkodGhpcywgJ3Nlc3Npb25Hcm91cHMnLCB2YWx1ZS5zZXNzaW9uR3JvdXBzKTsKICAgICAgICAgICAgfSkpOwogICAgICAgIH0KICAgICAgICBfc2VuZExpc3RTZXNzaW9uR3JvdXBzUmVxdWVzdCgpIHsKICAgICAgICAgICAgY29uc3QgcmVxdWVzdCA9IHRoaXMuX2J1aWxkTGlzdFNlc3Npb25Hcm91cHNSZXF1ZXN0KCk7CiAgICAgICAgICAgIGlmIChyZXF1ZXN0ID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBJZiBxdWVyeSBjb25maWd1cmF0aW9uIGlzIG5vdCB2YWxpZCBkb24ndCBzZW5kIGEgcmVxdWVzdC4KICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICB0aGlzLnNldCgnX3Nlc3Npb25Hcm91cHNSZXF1ZXN0JywgcmVxdWVzdCk7CiAgICAgICAgICAgIC8vIE5vdGUgdGhhdCB0aGUgcmVzcG9uc2VzIHRvIHRoZSBSUENzIHNlbnQKICAgICAgICAgICAgLy8gdG8gdGhlIGJhY2tlbmQgbWF5IHJldHVybiBpbiBhIGRpZmZlcmVudCBvcmRlciB0aGFuIHRoZSBvcmRlciBpbgogICAgICAgICAgICAvLyB3aGljaCB0aGV5IHdlcmUgc2VudC4gSWYgd2UganVzdCB1cGRhdGUgc2Vzc2lvbkdyb3VwcyBpbiB0aGUKICAgICAgICAgICAgLy8gb3JkZXIgb2YgcmVzcG9uc2VzIHJlY2VpdmVkLCB3ZSBjYW4gZW5kIHVwCiAgICAgICAgICAgIC8vIHdpdGggYSBzZXNzaW9uR3JvdXBzIG9iamVjdCB0aGF0IGRvZXNuJ3QgbWF0Y2ggdGhlIGZpbHRlcmluZyBhbmQKICAgICAgICAgICAgLy8gc29ydGluZyBjb25maWd1cmF0aW9uLiBGb3IgZXhhbXBsZSwgaWYgdGhlIGxhc3QgcmVzcG9uc2UgcmVjZWl2ZWQKICAgICAgICAgICAgLy8gd2FzIGZvciBhIHF1ZXJ5IGJlbG9uZ2luZyB0byB0aGUgcGVudWx0aW1hdGUgZmlsdGVyaW5nIGFuZAogICAgICAgICAgICAvLyBzb3J0aW5nIGNvbmZpZ3VyYXRpb24uIFRvIHNvbHZlIHRoaXMsIHdlIHVzZSB0Zl9iYWNrZW5kLmNhbmNlbGxlcgogICAgICAgICAgICAvLyB0byBjYW5jZWwgYWxsIHRoZSBwZW5kaW5nIHByb21pc2VzIGZyb20gcHJldmlvdXMgcXVlcmllcyBmb3Igd2hpY2gKICAgICAgICAgICAgLy8gd2UgaGF2ZW4ndCByZWNlaXZlZCBhIHJlc3BvbnNlIHlldC4KICAgICAgICAgICAgdGhpcy5fbGlzdFNlc3Npb25Hcm91cHNDYW5jZWxsZXIuY2FuY2VsQWxsKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmJhY2tlbmQubGlzdFNlc3Npb25Hcm91cHMocmVxdWVzdCk7CiAgICAgICAgfQogICAgICAgIC8vIFJlYWRzIHRoZSB2YWx1ZXMgb2YgdGhlIHByb3BlcnRpZXMgYm91bmQgdG8gdGhlIHF1ZXJ5IGVsZW1lbnRzCiAgICAgICAgLy8gYW5kIGJ1aWxkcyB0aGUgY29ycmVzcG9uZGluZyBMaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QuCiAgICAgICAgLy8gSWYgdGhlIHVzZXIgc2V0dGluZ3MgYXJlIGludmFsaWQgKGUuZy4gYW4gaW5wdXQtYm94IGRvZXNuJ3QgY29udGFpbnQKICAgICAgICAvLyBhIHBhcnNhYmxlIG51bWJlciksIG1hcmtzIHRoZSBjb3JyZXNwb25kaW5nIGVsZW1lbnRzIChpZiB0aGV5IGV4aXN0LAogICAgICAgIC8vIHNlZSBuZXh0IHBhcmFncmFwaCkgYXMgaW52YWxpZCBzbyB0aGF0IHRoZXkgd2lsbCBkaXNwbGF5IGFuCiAgICAgICAgLy8gZXJyb3IgbWVzc2FnZSBhbmQgcmV0dXJucyBudWxsLgogICAgICAgIC8vCiAgICAgICAgLy8gTm90ZSwgdGhhdCB0aGlzIG1ldGhvZCBjYW4gYmUgY2FsbGVkIGJlZm9yZSB0aGUgZWxlbWVudHMgaGF2ZQogICAgICAgIC8vIGJlZW4gcmVuZGVyZWQgKHdoZW4gdGhlIHRmLWhwYXJhbXMtcXVlcnkgaXMgZmlyc3QgY3JlYXRlZCksIGluIHdoaWNoCiAgICAgICAgLy8gY2FzZSBpdCB3aWxsIG5vdCB0cnkgdG8gbWFyayB0aGUgZWxlbWVudHMgYXMgaW52YWxpZC4KICAgICAgICBfYnVpbGRMaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QoKSB7CiAgICAgICAgICAgIGNvbnN0IF90aGlzID0gdGhpczsKICAgICAgICAgICAgLy8gV2lsbCBiZSBzZXQgdG8gZmFsc2UgaWYgd2UgZW5jb3VudGVyIGFueSBpbnZhbGlkIGlucHV0cy4KICAgICAgICAgICAgbGV0IHF1ZXJ5VmFsaWQgPSB0cnVlOwogICAgICAgICAgICAvLyBQYXJzZXMgYW4gaW5wdXRJbnRlcnZhbCBvYmplY3Qgb2YgdGhlIGZvcm06CiAgICAgICAgICAgIC8vIHttaW46IHt2YWx1ZTogc3RyaW5nLCBpbnZhbGlkOiBib29sZWFufSwKICAgICAgICAgICAgLy8gIG1heDoge3ZhbHVlOiBzdHJpbmcgIGludmFsaWQ6IGJvb2xlYW59fS4gUmV0dXJucyBhbiBvYmplY3QKICAgICAgICAgICAgLy8gb2YgdGhlIGZvcm06IHttaW5WYWx1ZTogbnVtYmVyLCBtYXhWYWx1ZTogbnVtYmVyfSBzdWl0YWJsZSB0bwogICAgICAgICAgICAvLyBiZSBpbmNsdWRlZCBhcyBhbiBpbnRlcnZhbCBpbiBMaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QuIElmIHRoZQogICAgICAgICAgICAvLyBtaW4gb3IgbWF4IHZhbHVlcyBjYW5ub3QgYmUgcGFyc2VkLCByZXR1cm5zIG51bGwuIEluIGJvdGggY2FzZXMKICAgICAgICAgICAgLy8gc2V0cyB0aGUgJ2ludmFsaWQnIGZpZWxkcyB0byBkZW5vdGUgd2hldGhlciB0aGUgaW5wdXRzIGlzIGludmFsaWQuCiAgICAgICAgICAgIC8vCiAgICAgICAgICAgIC8vIFRoZSBpbnB1dEludGVydmFsUGF0aCBzaG91bGQgYmUgYSBQb2x5bWVyIHBhdGggZm9yIHRoZSBpbnB1dEludGVydmFsCiAgICAgICAgICAgIC8vIG9iamVjdC4gV2Ugd29yayB3aXRoIHBhdGhzLCByYXRoZXIgdGhhbiB0aGUgb2JqZWN0LCBzbyB0aGF0IHdlCiAgICAgICAgICAgIC8vIGNhbiBtYWtlIG9ic2VydmFibGUgY2hhbmdlcy4KICAgICAgICAgICAgZnVuY3Rpb24gcGFyc2VJbnB1dEludGVydmFsKGlucHV0SW50ZXJ2YWxQYXRoKSB7CiAgICAgICAgICAgICAgICBjb25zdCBtaW5WYWx1ZVN0ciA9IF90aGlzLmdldChpbnB1dEludGVydmFsUGF0aCArICcubWluLnZhbHVlJyk7CiAgICAgICAgICAgICAgICBjb25zb2xlLmFzc2VydChtaW5WYWx1ZVN0ciAhPT0gdW5kZWZpbmVkKTsKICAgICAgICAgICAgICAgIC8vIFRoZSBwcm90b2J1ZmZlciBKU09OIG1hcHBpbmcgbWFwcyB0aGUgc3RyaW5ncyAiLUluZmluaXR5IiBhbmQKICAgICAgICAgICAgICAgIC8vICJJbmZpbml0eSIgdG8gdGhlIGZsb2F0aW5nLXBvaW50IGluZmluaXR5IGFuZCAtaW5maW5pdHkgdmFsdWVzLgogICAgICAgICAgICAgICAgY29uc3QgbWluVmFsdWUgPSBtaW5WYWx1ZVN0ciA9PT0gJycgPyAnLUluZmluaXR5JyA6ICttaW5WYWx1ZVN0cjsKICAgICAgICAgICAgICAgIF90aGlzLnNldChpbnB1dEludGVydmFsUGF0aCArICcubWluLmludmFsaWQnLCBpc05hTihtaW5WYWx1ZSkpOwogICAgICAgICAgICAgICAgcXVlcnlWYWxpZCA9IHF1ZXJ5VmFsaWQgJiYgIWlzTmFOKG1pblZhbHVlKTsKICAgICAgICAgICAgICAgIGNvbnN0IG1heFZhbHVlU3RyID0gX3RoaXMuZ2V0KGlucHV0SW50ZXJ2YWxQYXRoICsgJy5tYXgudmFsdWUnKTsKICAgICAgICAgICAgICAgIGNvbnNvbGUuYXNzZXJ0KG1heFZhbHVlU3RyICE9PSB1bmRlZmluZWQpOwogICAgICAgICAgICAgICAgY29uc3QgbWF4VmFsdWUgPSBtYXhWYWx1ZVN0ciA9PT0gJycgPyAnSW5maW5pdHknIDogK21heFZhbHVlU3RyOwogICAgICAgICAgICAgICAgX3RoaXMuc2V0KGlucHV0SW50ZXJ2YWxQYXRoICsgJy5tYXguaW52YWxpZCcsIGlzTmFOKG1heFZhbHVlKSk7CiAgICAgICAgICAgICAgICBxdWVyeVZhbGlkID0gcXVlcnlWYWxpZCAmJiAhaXNOYU4obWF4VmFsdWUpOwogICAgICAgICAgICAgICAgaWYgKGlzTmFOKG1pblZhbHVlKSB8fCBpc05hTihtYXhWYWx1ZSkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbnVsbDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiB7IG1pblZhbHVlOiBtaW5WYWx1ZSwgbWF4VmFsdWU6IG1heFZhbHVlIH07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUGFyc2VzIHRoZSB2YWx1ZSBvZiBhbiBpbnB1dCBvYmplY3Qgb2YgdGhlIGZvcm06CiAgICAgICAgICAgIC8vIHt2YWx1ZTogc3RyaW5nLCBpbnZhbGlkOiBib29sZWFufSBhcyBhIHBvc2l0aXZlIGludGVnZXIgYW5kIHJldHVybnMKICAgICAgICAgICAgLy8gdGhlIGludGVnZXIgb3IgbnVsbCBpZiB0aGUgcGFyc2luZyBmYWlscy4KICAgICAgICAgICAgLy8gSWYgcGFyc2luZyBmYWlscywgYWxzbyBzZXRzIHRoZSAnaW52YWxpZCcgcHJvcGVydHkgb2YgdGhlIGlucHV0CiAgICAgICAgICAgIC8vIG9iamVjdCB0byBmYWxzZS4KICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gVGhlIGlucHV0UGF0aCBzaG91bGQgYmUgYSBQb2x5bWVyIHBhdGggdG8gaW5wdXQgb2JqZWN0LiBXZSB3b3JrCiAgICAgICAgICAgIC8vIHdpdGggcGF0aHMsIHJhdGhlciB0aGFuIHRoZSBvYmplY3QsIHNvIHRoYXQgd2UgY2FuIG1ha2Ugb2JzZXJ2YWJsZQogICAgICAgICAgICAvLyBjaGFuZ2VzLgogICAgICAgICAgICBmdW5jdGlvbiBwYXJzZUlucHV0QXNQb3NpdGl2ZUludChpbnB1dFBhdGgpIHsKICAgICAgICAgICAgICAgIGNvbnN0IGlucHV0VmFsdWVTdHIgPSBfdGhpcy5nZXQoaW5wdXRQYXRoICsgJy52YWx1ZScpOwogICAgICAgICAgICAgICAgY29uc29sZS5hc3NlcnQoaW5wdXRWYWx1ZVN0ciAhPT0gdW5kZWZpbmVkKTsKICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9ICtpbnB1dFZhbHVlU3RyOwogICAgICAgICAgICAgICAgY29uc3QgdmFsaWRSZXN1bHQgPSBOdW1iZXIuaXNJbnRlZ2VyKHJlc3VsdCkgJiYgcmVzdWx0ID4gMDsKICAgICAgICAgICAgICAgIF90aGlzLnNldChpbnB1dFBhdGggKyAnLmludmFsaWQnLCAhdmFsaWRSZXN1bHQpOwogICAgICAgICAgICAgICAgcXVlcnlWYWxpZCA9IHF1ZXJ5VmFsaWQgJiYgdmFsaWRSZXN1bHQ7CiAgICAgICAgICAgICAgICBpZiAodmFsaWRSZXN1bHQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQnVpbGQgdGhlIGFsbG93ZWQgc3RhdHVzIGZpbHRlcnMuCiAgICAgICAgICAgIGNvbnN0IGFsbG93ZWRTdGF0dXNlcyA9IHRoaXMuX3N0YXR1c2VzCiAgICAgICAgICAgICAgICAuZmlsdGVyKChzKSA9PiBzLmFsbG93ZWQpCiAgICAgICAgICAgICAgICAubWFwKChzKSA9PiBzLnZhbHVlKTsKICAgICAgICAgICAgbGV0IGNvbFBhcmFtcyA9IFtdOwogICAgICAgICAgICAvLyBCdWlsZCB0aGUgaHBhcmFtcyBmaWx0ZXJzIGluIHRoZSByZXF1ZXN0LgogICAgICAgICAgICB0aGlzLl9ocGFyYW1zLmZvckVhY2goKGhwYXJhbSwgaW5kZXgpID0+IHsKICAgICAgICAgICAgICAgIGxldCBjb2xQYXJhbSA9IHsgaHBhcmFtOiBocGFyYW0uaW5mby5uYW1lIH07CiAgICAgICAgICAgICAgICBpZiAoaHBhcmFtLmZpbHRlci5kb21haW5EaXNjcmV0ZSkgewogICAgICAgICAgICAgICAgICAgIGNvbFBhcmFtLmZpbHRlckRpc2NyZXRlID0gW107CiAgICAgICAgICAgICAgICAgICAgaHBhcmFtLmZpbHRlci5kb21haW5EaXNjcmV0ZS5mb3JFYWNoKChmaWx0ZXJWYWwpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGZpbHRlclZhbC5jaGVja2VkKSB7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb2xQYXJhbS5maWx0ZXJEaXNjcmV0ZS5wdXNoKGZpbHRlclZhbC52YWx1ZSk7CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGhwYXJhbS5maWx0ZXIuaW50ZXJ2YWwpIHsKICAgICAgICAgICAgICAgICAgICBjb2xQYXJhbS5maWx0ZXJJbnRlcnZhbCA9IHBhcnNlSW5wdXRJbnRlcnZhbCgnX2hwYXJhbXMuJyArIGluZGV4ICsgJy5maWx0ZXIuaW50ZXJ2YWwnKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGVsc2UgaWYgKGhwYXJhbS5maWx0ZXIucmVnZXhwKSB7CiAgICAgICAgICAgICAgICAgICAgY29sUGFyYW0uZmlsdGVyUmVnZXhwID0gaHBhcmFtLmZpbHRlci5yZWdleHA7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdocGFyYW0uZmlsdGVyIHdpdGggbm8gZG9tYWluRGlzY3JldGUsIGludGVydmFsIG9yIHJlZ2V4cCcgKwogICAgICAgICAgICAgICAgICAgICAgICAnIHByb3BlcnRpZXMgc2V0OiAlcycsIGhwYXJhbSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb2xQYXJhbXMucHVzaChjb2xQYXJhbSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBCdWlsZCB0aGUgbWV0cmljIGZpbHRlcnMgaW4gdGhlIHJlcXVlc3QuCiAgICAgICAgICAgIHRoaXMuX21ldHJpY3MuZm9yRWFjaCgobWV0cmljLCBpbmRleCkgPT4gewogICAgICAgICAgICAgICAgbGV0IGNvbFBhcmFtID0gewogICAgICAgICAgICAgICAgICAgIG1ldHJpYzogbWV0cmljLmluZm8ubmFtZSwKICAgICAgICAgICAgICAgICAgICBmaWx0ZXJJbnRlcnZhbDogcGFyc2VJbnB1dEludGVydmFsKCdfbWV0cmljcy4nICsgaW5kZXggKyAnLmZpbHRlci5pbnRlcnZhbCcpLAogICAgICAgICAgICAgICAgfTsKICAgICAgICAgICAgICAgIGNvbFBhcmFtcy5wdXNoKGNvbFBhcmFtKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIFNvcnRpbmcuCiAgICAgICAgICAgIC8vIFRPRE8oZXJleik6IFN1cHBvcnQgc29ydGluZyBieSBtdWx0aXBsZSBjb2x1bW5zLgogICAgICAgICAgICBpZiAodGhpcy5fc29ydEJ5SW5kZXggIT09IHVuZGVmaW5lZCAmJiB0aGlzLl9zb3J0RGlyZWN0aW9uICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIGlmICghKHRoaXMuX3NvcnRCeUluZGV4IGluIGNvbFBhcmFtcykpIHsKICAgICAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCdObyBjb2x1bW4gaW4gY29sUGFyYW1zIHdpdGggaW5kZXggc29ydEJ5SW5kZXg6ICVzJywgdGhpcy5fc29ydEJ5SW5kZXgpOwogICAgICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29sUGFyYW1zW3RoaXMuX3NvcnRCeUluZGV4XS5vcmRlciA9CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fc29ydERpcmVjdGlvbiA9PT0gMCA/ICdPUkRFUl9BU0MnIDogJ09SREVSX0RFU0MnOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFBhZ2luZy4KICAgICAgICAgICAgY29uc3QgcGFnZU51bSA9IHBhcnNlSW5wdXRBc1Bvc2l0aXZlSW50KCdfcGFnZU51bWJlcklucHV0Jyk7CiAgICAgICAgICAgIGNvbnN0IHBhZ2VTaXplID0gcGFyc2VJbnB1dEFzUG9zaXRpdmVJbnQoJ19wYWdlU2l6ZUlucHV0Jyk7CiAgICAgICAgICAgIGlmICghcXVlcnlWYWxpZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3Qgc3RhcnRJbmRleCA9IHBhZ2VTaXplICogKHBhZ2VOdW0gLSAxKTsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGV4cGVyaW1lbnROYW1lOiB0aGlzLmV4cGVyaW1lbnROYW1lLAogICAgICAgICAgICAgICAgYWxsb3dlZFN0YXR1c2VzOiBhbGxvd2VkU3RhdHVzZXMsCiAgICAgICAgICAgICAgICBjb2xQYXJhbXM6IGNvbFBhcmFtcywKICAgICAgICAgICAgICAgIHN0YXJ0SW5kZXg6IHN0YXJ0SW5kZXgsCiAgICAgICAgICAgICAgICBzbGljZVNpemU6IHBhZ2VTaXplLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICAvLyBXZSBhbGxvdyBzb3J0aW5nIGJ5IGFueSBjb2x1bW4gb2YgYSBzZXNzaW9uIGdyb3VwLiBBIGNvbHVtbiBpcyBlaXRoZXIgYQogICAgICAgIC8vIG1ldHJpYyBvciBhIGh5cGVycGFyYW1ldGVyLgogICAgICAgIC8vIEZvciB0aGUgcHVycG9zZSBvZiBzb3J0aW5nLCB3ZSBpZGVudGlmeSBlYWNoIHN1Y2ggY29sdW1uIGJ5IGl0cyBpbmRleAogICAgICAgIC8vIGluIHRoZSBsaXN0IGZvcm1lZCBieSBjb25jYXRlbmF0aW5nIHRoZSBtZXRyaWMgaW4gX21ldHJpY3MgYWZ0ZXIgdGhlCiAgICAgICAgLy8gaHBhcmFtcyBpbiBfaHBhcmFtcy4gVGhpcyBtZXRob2QgY29tcHV0ZXMgdGhpcyBzb3J0aW5nIGluZGV4IG9mIHRoZQogICAgICAgIC8vIG1ldHJpYyBjb2x1bW4gcmVwcmVzZW50ZWQgYnkgX21ldHJpY3NbbWV0cmljSW5kZXhdLgogICAgICAgIF9tZXRyaWNTb3J0QnlJbmRleChtZXRyaWNJbmRleCkgewogICAgICAgICAgICByZXR1cm4gbWV0cmljSW5kZXggKyB0aGlzLl9ocGFyYW1zLmxlbmd0aDsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zUXVlcnlQYW5lLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8aHBhcmFtcy1zcGxpdC1sYXlvdXQgb3JpZW50YXRpb249InZlcnRpY2FsIj4KICAgICAgPGRpdiBzbG90PSJjb250ZW50IiBjbGFzcz0ic2VjdGlvbiBoeXBlcnBhcmFtZXRlcnMiPgogICAgICAgIDxkaXYgY2xhc3M9InNlY3Rpb24tdGl0bGUiPkh5cGVycGFyYW1ldGVyczwvZGl2PgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLXJlcGVhdCIgaXRlbXM9Int7X2hwYXJhbXN9fSIgYXM9ImhwYXJhbSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJocGFyYW0iPgogICAgICAgICAgICA8cGFwZXItY2hlY2tib3gKICAgICAgICAgICAgICBjaGVja2VkPSJ7e2hwYXJhbS5kaXNwbGF5ZWR9fSIKICAgICAgICAgICAgICBjbGFzcz0iaHBhcmFtLWNoZWNrYm94IgogICAgICAgICAgICA+CiAgICAgICAgICAgICAgW1tfaHBhcmFtTmFtZShocGFyYW0uaW5mbyldXQogICAgICAgICAgICA8L3BhcGVyLWNoZWNrYm94PgogICAgICAgICAgICA8IS0tIFByZWNpc2VseSBvbmUgb2YgdGhlIHRlbXBsYXRlcyBiZWxvdyB3aWxsIGJlIHN0YW1wZWQuLS0+CiAgICAgICAgICAgIDwhLS0gMS4gQSBsaXN0IG9mIGNoZWNrYm94ZXMgLS0+CiAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tocGFyYW0uZmlsdGVyLmRvbWFpbkRpc2NyZXRlXV0iPgogICAgICAgICAgICAgIDx0ZW1wbGF0ZQogICAgICAgICAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgICAgICAgICBpdGVtcz0iW1tocGFyYW0uZmlsdGVyLmRvbWFpbkRpc2NyZXRlXV0iCiAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgPHBhcGVyLWNoZWNrYm94CiAgICAgICAgICAgICAgICAgIGNoZWNrZWQ9Int7aXRlbS5jaGVja2VkfX0iCiAgICAgICAgICAgICAgICAgIGNsYXNzPSJkaXNjcmV0ZS12YWx1ZS1jaGVja2JveCIKICAgICAgICAgICAgICAgICAgb24tY2hhbmdlPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgICAgIFtbX3ByZXR0eVByaW50KGl0ZW0udmFsdWUpXV0KICAgICAgICAgICAgICAgIDwvcGFwZXItY2hlY2tib3g+CiAgICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPCEtLSAyLiBBIG51bWVyaWMgaW50ZXJ2YWwgLS0+CiAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tocGFyYW0uZmlsdGVyLmludGVydmFsXV0iPgogICAgICAgICAgICAgIDxwYXBlci1pbnB1dAogICAgICAgICAgICAgICAgbGFiZWw9Ik1pbiIKICAgICAgICAgICAgICAgIHZhbHVlPSJ7e2hwYXJhbS5maWx0ZXIuaW50ZXJ2YWwubWluLnZhbHVlfX0iCiAgICAgICAgICAgICAgICBhbGxvd2VkX3BhdHRlcm49IlswLTkuZVxcLV0iCiAgICAgICAgICAgICAgICBvbi12YWx1ZS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICAgICAgaW52YWxpZD0iW1tocGFyYW0uZmlsdGVyLmludGVydmFsLm1pbi5pbnZhbGlkXV0iCiAgICAgICAgICAgICAgICBwbGFjZWhvbGRlcj0iLWluZmluaXR5IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICA8L3BhcGVyLWlucHV0PgogICAgICAgICAgICAgIDxwYXBlci1pbnB1dAogICAgICAgICAgICAgICAgbGFiZWw9Ik1heCIKICAgICAgICAgICAgICAgIHZhbHVlPSJ7e2hwYXJhbS5maWx0ZXIuaW50ZXJ2YWwubWF4LnZhbHVlfX0iCiAgICAgICAgICAgICAgICBhbGxvd2VkX3BhdHRlcm49IlswLTkuZVxcLV0iCiAgICAgICAgICAgICAgICBvbi12YWx1ZS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICAgICAgaW52YWxpZD0iW1tocGFyYW0uZmlsdGVyLmludGVydmFsLm1heC5pbnZhbGlkXV0iCiAgICAgICAgICAgICAgICBwbGFjZWhvbGRlcj0iK2luZmluaXR5IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICA8L3BhcGVyLWlucHV0PgogICAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgICA8IS0tIDMuIEEgcmVnZXhwIC0tPgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbaHBhcmFtLmZpbHRlci5yZWdleHBdXSI+CiAgICAgICAgICAgICAgPHBhcGVyLWlucHV0CiAgICAgICAgICAgICAgICBsYWJlbD0iUmVndWxhciBleHByZXNzaW9uIgogICAgICAgICAgICAgICAgdmFsdWU9Int7aHBhcmFtLmZpbHRlci5yZWdleHB9fSIKICAgICAgICAgICAgICAgIG9uLXZhbHVlLWNoYW5nZWQ9Il9xdWVyeVNlcnZlciIKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgPC9wYXBlci1pbnB1dD4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IHNsb3Q9ImNvbnRlbnQiIGNsYXNzPSJzZWN0aW9uIG1ldHJpY3MiPgogICAgICAgIDxkaXYgY2xhc3M9InNlY3Rpb24tdGl0bGUiPk1ldHJpY3M8L2Rpdj4KICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJ7e19tZXRyaWNzfX0iIGFzPSJtZXRyaWMiPgogICAgICAgICAgPGRpdiBjbGFzcz0ibWV0cmljIj4KICAgICAgICAgICAgPCEtLSBUT0RPKGVyZXopOiBNYWtlIGl0IGVhc2llciB0byBoYW5kbGUgYSBsYXJnZSBudW1iZXIgb2YKICAgICAgICAgICAgICAgICAgbWV0cmljczoKICAgICAgICAgICAgICAgICAgMS4gQWRkIGFuICdpc29sYXRvcicgcmFkaW8tYnV0dG9uIHRvIHNlbGVjdCBqdXN0IG9uZQogICAgICAgICAgICAgICAgICBtZXRyaWMgYW5kCiAgICAgICAgICAgICAgICAgIGhpZGUgYWxsIHRoZSByZXN0CiAgICAgICAgICAgICAgICAgIDIuIEFkZCBhICd0b2dnbGUtYWxsJyBidXR0b24gdGhhdCB3aWxsIGhpZGUvdW5oaWRlCiAgICAgICAgICAgICAgICAgICAgYWxsIHRoZQogICAgICAgICAgICAgICAgICBtZXRyaWNzLgogICAgICAgICAgICAgICAgICBVc2Ugc2ltaWxhciBsb2dpYy9hcHBlYXJhbmNlIHRvIHRoZSBydW4tc2VsZWN0b3Igb2YKICAgICAgICAgICAgICAgICAgc2NhbGFycy4tLT4KICAgICAgICAgICAgPHBhcGVyLWNoZWNrYm94CiAgICAgICAgICAgICAgY2hlY2tlZD0ie3ttZXRyaWMuZGlzcGxheWVkfX0iCiAgICAgICAgICAgICAgY2xhc3M9Im1ldHJpYy1jaGVja2JveCIKICAgICAgICAgICAgPgogICAgICAgICAgICAgIFtbX21ldHJpY05hbWUobWV0cmljLmluZm8pXV0KICAgICAgICAgICAgPC9wYXBlci1jaGVja2JveD4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iaW5saW5lLWVsZW1lbnQiPgogICAgICAgICAgICAgIDxwYXBlci1pbnB1dAogICAgICAgICAgICAgICAgbGFiZWw9Ik1pbiIKICAgICAgICAgICAgICAgIHZhbHVlPSJ7e21ldHJpYy5maWx0ZXIuaW50ZXJ2YWwubWluLnZhbHVlfX0iCiAgICAgICAgICAgICAgICBhbGxvd2VkLXBhdHRlcm49IlswLTkuZVxcLV0iCiAgICAgICAgICAgICAgICBvbi12YWx1ZS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICAgICAgaW52YWxpZD0ie3ttZXRyaWMuZmlsdGVyLmludGVydmFsLm1pbi5pbnZhbGlkfX0iCiAgICAgICAgICAgICAgICBwbGFjZWhvbGRlcj0iLWluZmluaXR5IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICA8L3BhcGVyLWlucHV0PgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0iaW5saW5lLWVsZW1lbnQiPgogICAgICAgICAgICAgIDxwYXBlci1pbnB1dAogICAgICAgICAgICAgICAgbGFiZWw9Ik1heCIKICAgICAgICAgICAgICAgIGFsbG93ZWQtcGF0dGVybj0iWzAtOS5lXFwtXSIKICAgICAgICAgICAgICAgIHZhbHVlPSJ7e21ldHJpYy5maWx0ZXIuaW50ZXJ2YWwubWF4LnZhbHVlfX0iCiAgICAgICAgICAgICAgICBvbi12YWx1ZS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICAgICAgaW52YWxpZD0ie3ttZXRyaWMuZmlsdGVyLmludGVydmFsLm1heC5pbnZhbGlkfX0iCiAgICAgICAgICAgICAgICBwbGFjZWhvbGRlcj0iK2luZmluaXR5IgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICA8L3BhcGVyLWlucHV0PgogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IHNsb3Q9ImNvbnRlbnQiIGNsYXNzPSJzZWN0aW9uIHN0YXR1cyI+CiAgICAgICAgPGRpdiBjbGFzcz0ic2VjdGlvbi10aXRsZSI+U3RhdHVzPC9kaXY+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfc3RhdHVzZXNdXSIgYXM9InN0YXR1cyI+CiAgICAgICAgICA8cGFwZXItY2hlY2tib3ggY2hlY2tlZD0ie3tzdGF0dXMuYWxsb3dlZH19IiBvbi1jaGFuZ2U9Il9xdWVyeVNlcnZlciI+CiAgICAgICAgICAgIFtbc3RhdHVzLmRpc3BsYXlOYW1lXV0KICAgICAgICAgIDwvcGFwZXItY2hlY2tib3g+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgc2xvdD0iY29udGVudCIgY2xhc3M9InNlY3Rpb24gc29ydGluZyI+CiAgICAgICAgPGRpdiBjbGFzcz0ic2VjdGlvbi10aXRsZSI+U29ydGluZzwvZGl2PgogICAgICAgIDxwYXBlci1kcm9wZG93bi1tZW51CiAgICAgICAgICBsYWJlbD0iU29ydCBieSIKICAgICAgICAgIG9uLXNlbGVjdGVkLWl0ZW0tY2hhbmdlZD0iX3F1ZXJ5U2VydmVyIgogICAgICAgICAgaG9yaXpvbnRhbC1hbGlnbj0ibGVmdCIKICAgICAgICA+CiAgICAgICAgICA8cGFwZXItbGlzdGJveAogICAgICAgICAgICBjbGFzcz0iZHJvcGRvd24tY29udGVudCIKICAgICAgICAgICAgc2xvdD0iZHJvcGRvd24tY29udGVudCIKICAgICAgICAgICAgc2VsZWN0ZWQ9Int7X3NvcnRCeUluZGV4fX0iCiAgICAgICAgICAgIG9uLXNlbGVjdGVkLWl0ZW0tY2hhbmdlZD0iX3F1ZXJ5U2VydmVyIgogICAgICAgICAgPgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19ocGFyYW1zXV0iIGFzPSJocGFyYW0iPgogICAgICAgICAgICAgIDxwYXBlci1pdGVtPiBbW19ocGFyYW1OYW1lKGhwYXJhbS5pbmZvKV1dIDwvcGFwZXItaXRlbT4KICAgICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0iW1tfbWV0cmljc11dIiBhcz0ibWV0cmljIj4KICAgICAgICAgICAgICA8cGFwZXItaXRlbT4gW1tfbWV0cmljTmFtZShtZXRyaWMuaW5mbyldXSA8L3BhcGVyLWl0ZW0+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgogICAgICAgIDxwYXBlci1kcm9wZG93bi1tZW51CiAgICAgICAgICBsYWJlbD0iRGlyZWN0aW9uIgogICAgICAgICAgb24tc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICBob3Jpem9udGFsLWFsaWduPSJsZWZ0IgogICAgICAgID4KICAgICAgICAgIDxwYXBlci1saXN0Ym94CiAgICAgICAgICAgIGNsYXNzPSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgICBzbG90PSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgICBzZWxlY3RlZD0ie3tfc29ydERpcmVjdGlvbn19IgogICAgICAgICAgPgogICAgICAgICAgICA8cGFwZXItaXRlbT5Bc2NlbmRpbmc8L3BhcGVyLWl0ZW0+CiAgICAgICAgICAgIDxwYXBlci1pdGVtPkRlc2NlbmRpbmc8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBzbG90PSJjb250ZW50IiBjbGFzcz0ic2VjdGlvbiBwYWdpbmciPgogICAgICAgIDxkaXYgY2xhc3M9InNlY3Rpb24tdGl0bGUiPlBhZ2luZzwvZGl2PgogICAgICAgIDxkaXY+CiAgICAgICAgICBOdW1iZXIgb2YgbWF0Y2hpbmcgc2Vzc2lvbiBncm91cHM6IFtbX3RvdGFsU2Vzc2lvbkdyb3Vwc0NvdW50U3RyXV0KICAgICAgICA8L2Rpdj4KICAgICAgICA8ZGl2IGNsYXNzPSJpbmxpbmUtZWxlbWVudCBwYWdlLW51bWJlci1pbnB1dCI+CiAgICAgICAgICA8cGFwZXItaW5wdXQKICAgICAgICAgICAgbGFiZWw9IlBhZ2UgIyIKICAgICAgICAgICAgdmFsdWU9Int7X3BhZ2VOdW1iZXJJbnB1dC52YWx1ZX19IgogICAgICAgICAgICBhbGxvd2VkLXBhdHRlcm49IlswLTldIgogICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICBpbnZhbGlkPSJbW19wYWdlTnVtYmVySW5wdXQuaW52YWxpZF1dIgogICAgICAgICAgICBvbi12YWx1ZS1jaGFuZ2VkPSJfcXVlcnlTZXJ2ZXIiCiAgICAgICAgICA+CiAgICAgICAgICAgIDxkaXYgc2xvdD0ic3VmZml4IiBjbGFzcz0icGFnZS1zdWZmaXgiPi8gW1tfcGFnZUNvdW50U3RyXV08L2Rpdj4KICAgICAgICAgIDwvcGFwZXItaW5wdXQ+CiAgICAgICAgPC9kaXY+CiAgICAgICAgPGRpdiBjbGFzcz0iaW5saW5lLWVsZW1lbnQgcGFnZS1zaXplLWlucHV0Ij4KICAgICAgICAgIDxwYXBlci1pbnB1dAogICAgICAgICAgICBsYWJlbD0iTWF4ICMgb2Ygc2Vzc2lvbiBncm91cHMgcGVyIHBhZ2U6IgogICAgICAgICAgICB2YWx1ZT0ie3tfcGFnZVNpemVJbnB1dC52YWx1ZX19IgogICAgICAgICAgICBhbGxvd2VkLXBhdHRlcm49IlswLTldIgogICAgICAgICAgICBlcnJvci1tZXNzYWdlPSJJbnZhbGlkIGlucHV0IgogICAgICAgICAgICBpbnZhbGlkPSJbW19wYWdlU2l6ZUlucHV0LmludmFsaWRdXSIKICAgICAgICAgICAgb24tdmFsdWUtY2hhbmdlZD0iX3F1ZXJ5U2VydmVyIgogICAgICAgICAgPgogICAgICAgICAgPC9wYXBlci1pbnB1dD4KICAgICAgICA8L2Rpdj4KICAgICAgPC9kaXY+CiAgICAgIDxkaXYgc2xvdD0iY29udGVudCIgY2xhc3M9InNlY3Rpb24gZG93bmxvYWQiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfc2Vzc2lvbkdyb3Vwc1JlcXVlc3RdXSI+CiAgICAgICAgICBEb3dubG9hZCBkYXRhIGFzCiAgICAgICAgICA8c3Bhbj4KICAgICAgICAgICAgPGEKICAgICAgICAgICAgICBpZD0iY3N2TGluayIKICAgICAgICAgICAgICBkb3dubG9hZD0iaHBhcmFtc190YWJsZS5jc3YiCiAgICAgICAgICAgICAgaHJlZj0iW1tfY3N2VXJsKF9zZXNzaW9uR3JvdXBzUmVxdWVzdCwgY29uZmlndXJhdGlvbildXSIKICAgICAgICAgICAgICA+Q1NWPC9hCiAgICAgICAgICAgID4KICAgICAgICAgICAgPGEKICAgICAgICAgICAgICBpZD0ianNvbkxpbmsiCiAgICAgICAgICAgICAgZG93bmxvYWQ9ImhwYXJhbXNfdGFibGUuanNvbiIKICAgICAgICAgICAgICBocmVmPSJbW19qc29uVXJsKF9zZXNzaW9uR3JvdXBzUmVxdWVzdCwgY29uZmlndXJhdGlvbildXSIKICAgICAgICAgICAgICA+SlNPTjwvYQogICAgICAgICAgICA+CiAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgaWQ9ImxhdGV4TGluayIKICAgICAgICAgICAgICBkb3dubG9hZD0iaHBhcmFtc190YWJsZS50ZXgiCiAgICAgICAgICAgICAgaHJlZj0iW1tfbGF0ZXhVcmwoX3Nlc3Npb25Hcm91cHNSZXF1ZXN0LCBjb25maWd1cmF0aW9uKV1dIgogICAgICAgICAgICAgID5MYVRlWDwvYQogICAgICAgICAgICA+CiAgICAgICAgICA8L3NwYW4+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC9kaXY+CiAgICA8L2hwYXJhbXMtc3BsaXQtbGF5b3V0PgogICAgPHN0eWxlPgogICAgICAuc2VjdGlvbiB7CiAgICAgICAgcGFkZGluZzogMTBweDsKICAgICAgfQogICAgICAuc2VjdGlvbi10aXRsZSB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgZm9udC13ZWlnaHQ6IGJvbGQ7CiAgICAgICAgdGV4dC1kZWNvcmF0aW9uOiB1bmRlcmxpbmU7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogN3B4OwogICAgICB9CiAgICAgIC5kaXNjcmV0ZS12YWx1ZS1jaGVja2JveCwKICAgICAgLm1ldHJpYy1jaGVja2JveCwKICAgICAgLmhwYXJhbS1jaGVja2JveCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KICAgICAgLmRpc2NyZXRlLXZhbHVlLWNoZWNrYm94IHsKICAgICAgICBtYXJnaW4tbGVmdDogMjBweDsKICAgICAgfQogICAgICAuaHBhcmFtLAogICAgICAubWV0cmljIHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQogICAgICAuaW5saW5lLWVsZW1lbnQgewogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICB3aWR0aDogNDAlOwogICAgICAgIG1hcmdpbi1sZWZ0OiAxMHB4OwogICAgICB9CiAgICAgIC5wYWdlLW51bWJlci1pbnB1dCB7CiAgICAgICAgd2lkdGg6IDIwJTsKICAgICAgfQogICAgICAucGFnZS1zaXplLWlucHV0IHsKICAgICAgICB3aWR0aDogNjAlOwogICAgICB9CiAgICAgIHZhYWRpbi1zcGxpdC1sYXlvdXQgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQogICAgICBwYXBlci1saXN0Ym94IHsKICAgICAgICBtYXgtaGVpZ2h0OiAxNWVtOwogICAgICB9CiAgICAgIC5wYWdlLXN1ZmZpeCB7CiAgICAgICAgd2hpdGUtc3BhY2U6IG5vd3JhcDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiZXhwZXJpbWVudE5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJjb25maWd1cmF0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJzZXNzaW9uR3JvdXBzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJkYXRhTG9hZGVkV2l0aE5vbkVtcHR5SHBhcmFtcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX2V4cGVyaW1lbnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZIcGFyYW1zUXVlcnlQYW5lLnByb3RvdHlwZSwgIl9ocGFyYW1zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJfbWV0cmljcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IEFycmF5LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zUXVlcnlQYW5lLnByb3RvdHlwZSwgIl9zdGF0dXNlcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJfZ2V0RXhwZXJpbWVudFJlc29sdmVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX3Jlc29sdmVHZXRFeHBlcmltZW50Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zUXVlcnlQYW5lLnByb3RvdHlwZSwgIl9saXN0U2Vzc2lvbkdyb3Vwc0NhbmNlbGxlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJfc29ydEJ5SW5kZXgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX3NvcnREaXJlY3Rpb24iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX3BhZ2VTaXplSW5wdXQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX3BhZ2VOdW1iZXJJbnB1dCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJfcGFnZUNvdW50U3RyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZIcGFyYW1zUXVlcnlQYW5lLnByb3RvdHlwZSwgIl90b3RhbFNlc3Npb25Hcm91cHNDb3VudFN0ciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1F1ZXJ5UGFuZS5wcm90b3R5cGUsICJfc2Vzc2lvbkdyb3Vwc1JlcXVlc3QiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnYmFja2VuZCcsICdleHBlcmltZW50TmFtZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZIcGFyYW1zUXVlcnlQYW5lLnByb3RvdHlwZSwgIl9jb21wdXRlRXhwZXJpbWVudEFuZFJlbGF0ZWRQcm9wcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnX2hwYXJhbXMuKicsICdfbWV0cmljcy4qJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUucHJvdG90eXBlLCAiX3VwZGF0ZUNvbmZpZ3VyYXRpb24iLCBudWxsKTsKICAgIFRmSHBhcmFtc1F1ZXJ5UGFuZSA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhwYXJhbXMtcXVlcnktcGFuZScpCiAgICBdLCBUZkhwYXJhbXNRdWVyeVBhbmUpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmSHBhcmFtc1NjYWxlQW5kQ29sb3JDb250cm9scyA9IGNsYXNzIFRmSHBhcmFtc1NjYWxlQW5kQ29sb3JDb250cm9scyBleHRlbmRzIFBvbHltZXJFbGVtZW50IHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5vcHRpb25zID0gbnVsbDsKICAgICAgICB9CiAgICAgICAgLyogUHJpdmF0ZSBtZXRob2RzICovCiAgICAgICAgX2NvbmZpZ3VyYXRpb25DaGFuZ2VkKCkgewogICAgICAgICAgICAvLyBQb3B1bGF0ZSBvcHRpb25zLmNvbHVtbnMgd2l0aCBhIGxpbmVhciBzY2FsZSBmb3IgZWFjaCBjb2x1bW4gKAogICAgICAgICAgICAvLyBocGFyYW0gb3IgbWV0cmljKS4KICAgICAgICAgICAgY29uc3QgdmlzaWJsZVNjaGVtYSA9IHRoaXMuY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hOwogICAgICAgICAgICBjb25zdCBzY2hlbWEgPSB0aGlzLmNvbmZpZ3VyYXRpb24uc2NoZW1hOwogICAgICAgICAgICBjb25zdCBuZXdIUGFyYW1Db2x1bW4gPSAoaW5mbywgaW5kZXgpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICAgICAgbmFtZTogaHBhcmFtTmFtZShpbmZvKSwKICAgICAgICAgICAgICAgICAgICBpbmRleDogaW5kZXgsCiAgICAgICAgICAgICAgICAgICAgYWJzb2x1dGVJbmRleDogZ2V0QWJzb2x1dGVDb2x1bW5JbmRleChzY2hlbWEsIHZpc2libGVTY2hlbWEsIGluZGV4KSwKICAgICAgICAgICAgICAgICAgICBzY2FsZTogdGhpcy5faXNOdW1lcmljQ29sdW1uKGluZGV4KSA/ICdMSU5FQVInIDogJ05PTl9OVU1FUklDJywKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGNvbnN0IG5ld01ldHJpY0NvbHVtbiA9IChpbmZvLCBpbmRleCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgY29sSW5kZXggPSBpbmRleCArIHZpc2libGVTY2hlbWEuaHBhcmFtSW5mb3MubGVuZ3RoOwogICAgICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgICAgICBzY2FsZTogJ0xJTkVBUicsCiAgICAgICAgICAgICAgICAgICAgbmFtZTogbWV0cmljTmFtZShpbmZvKSwKICAgICAgICAgICAgICAgICAgICBpbmRleDogY29sSW5kZXgsCiAgICAgICAgICAgICAgICAgICAgYWJzb2x1dGVJbmRleDogZ2V0QWJzb2x1dGVDb2x1bW5JbmRleChzY2hlbWEsIHZpc2libGVTY2hlbWEsIGNvbEluZGV4KSwKICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGNvbnN0IG9wdGlvbnMgPSB7CiAgICAgICAgICAgICAgICBjb2x1bW5zOiB2aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zCiAgICAgICAgICAgICAgICAgICAgLm1hcChuZXdIUGFyYW1Db2x1bW4pCiAgICAgICAgICAgICAgICAgICAgLmNvbmNhdCh2aXNpYmxlU2NoZW1hLm1ldHJpY0luZm9zLm1hcChuZXdNZXRyaWNDb2x1bW4pKSwKICAgICAgICAgICAgICAgIG1pbkNvbG9yOiAnIzAwMDBGRicsCiAgICAgICAgICAgICAgICBtYXhDb2xvcjogJyNGRjAwMDAnLAogICAgICAgICAgICAgICAgY29uZmlndXJhdGlvbjogdGhpcy5jb25maWd1cmF0aW9uLAogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyBTZXQgdGhlIGNvbG9yQnlDb2x1bW5JbmRleCBwcm9wZXJ0eS4KICAgICAgICAgICAgLy8gSWYgd2Ugc2V0IG9wdGlvbnMuY29sb3JCeUNvbHVtbkluZGV4IGF0IHRoZSBzYW1lIHRpbWUgYXMgd2UKICAgICAgICAgICAgLy8gc2V0IHRoZSBvdGhlciBvcHRpb25zLCBQb2x5bWVyIGZpcnN0IHVwZGF0ZXMgdGhlIGRyb3AtZG93biBtZW51CiAgICAgICAgICAgIC8vIHNlbGVjdGVkIGxhYmVsIGFuZCBvbmx5IHRoZW4gdXBkYXRlcyB0aGUgbGlzdCBib3ggd2l0aCB0aGUgbmV3IGl0ZW1zLgogICAgICAgICAgICAvLyBBcyBhIHJlc3VsdCB0aGUgc2VsZWN0ZWQgbGFiZWwgZ2V0cyBhbiBlcnJvbmVvdXMgdmFsdWUgKGJhc2VkIG9uCiAgICAgICAgICAgIC8vIHRoZSBvbGQgZWxlbWVudHMgaW4gdGhlIGxpc3QpLgogICAgICAgICAgICAvLyBUbyBvdmVyY29tZSB0aGlzLCB3ZSBmaXJzdCBzZXQgdGhlIHNlbGVjdGVkIGl0ZW0gdG8gInVuZGVmaW5lZCIsCiAgICAgICAgICAgIC8vIGNhbGwgZmx1c2ggdG8gc3luY2hyb25vdXNseSB1cGRhdGUgdGhlIGRyb3AtZG93biBtZW51IGxpc3Qgd2l0aAogICAgICAgICAgICAvLyB0aGUgbmV3IGl0ZW1zLCBhbmQgdGhlbiByZXNldCB0aGUgc2VsZWN0ZWQgaXRlbSBpbmRleCBzbyB0aGF0CiAgICAgICAgICAgIC8vIFBvbHltZXIgd2lsbCB1cGRhdGUgdGhlIGxhYmVsIGJhc2VkIG9uIHRoZSBuZXcgbGlzdC4KICAgICAgICAgICAgLy8gU2VlIGFsc286IGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyRWxlbWVudHMvcGFwZXItZHJvcGRvd24tbWVudS9pc3N1ZXMvMTk3I2lzc3VlY29tbWVudC0yNDk5MjczNzEsIGFuZCBodHRwOi8vanNiaW4uY29tL2Z1cW95ZS9lZGl0P2h0bWwsb3V0cHV0LgogICAgICAgICAgICB0aGlzLnNldCgnb3B0aW9ucycsIG9wdGlvbnMpOyAvLyBzZXQgdGhlIGJvdW5kIHNlbGVjdGVkIGl0ZW0gdG8KICAgICAgICAgICAgLy8gdW5kZWZpbmVkLgogICAgICAgICAgICBmbHVzaCgpOwogICAgICAgICAgICB0aGlzLnNldCgnb3B0aW9ucy5jb2xvckJ5Q29sdW1uSW5kZXgnLCB0aGlzLl9kZWZhdWx0Q29sb3JCeUNvbHVtbkluZGV4KCkpOwogICAgICAgIH0KICAgICAgICBfdW5zZWxlY3REaXNhYmxlZExvZ1NjYWxlcygpIHsKICAgICAgICAgICAgaWYgKHRoaXMub3B0aW9ucyA9PT0gbnVsbCkgewogICAgICAgICAgICAgICAgLy8gV2UgbWF5IGJlIGNhbGxlZCBiZWZvcmUgdGhlIG9wdGlvbnMgYXJlIGNvbnN0cnVjdGVkIGJ5CiAgICAgICAgICAgICAgICAvLyBfY29uZmlndXJhdGlvbkNoYW5nZWQoKS4gSW4gdGhpcyBjYXNlIHdlIG5lZWQgbm90IHdvcnJ5CiAgICAgICAgICAgICAgICAvLyBhYm91dCBzZWxlY3RlZCBkaXNhYmxlZCBsb2cgc2NhbGVzLgogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMub3B0aW9ucy5jb2x1bW5zLmZvckVhY2goKGNvbCkgPT4gewogICAgICAgICAgICAgICAgY29uc3QgY29sUGF0aCA9ICdvcHRpb25zLmNvbHVtbnMuJyArIGNvbC5pbmRleDsKICAgICAgICAgICAgICAgIGlmICghdGhpcy5fYWxsb3dMb2dTY2FsZShjb2wpICYmIGNvbC5zY2FsZSA9PT0gJ0xPRycpIHsKICAgICAgICAgICAgICAgICAgICAvLyBXZSBuZWVkIHRvIHVzZSBQb2x5bWVyIHBhdGhzIHRvIG1ha2UgdGhlIGNoYW5nZSBvYnNlcnZhYmxlLgogICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KGNvbFBhdGggKyAnLnNjYWxlJywgJ0xJTkVBUicpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2FsbG93TG9nU2NhbGUoY29sdW1uKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5faXNOdW1lcmljQ29sdW1uKGNvbHVtbi5pbmRleCkgfHwgIXRoaXMuc2Vzc2lvbkdyb3VwcykgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IFttaW4sIG1heF0gPSB2aXNpYmxlTnVtZXJpY0NvbHVtbkV4dGVudCh0aGlzLmNvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYSwgdGhpcy5zZXNzaW9uR3JvdXBzLCBjb2x1bW4uaW5kZXgpOwogICAgICAgICAgICAvLyBMb2cgc2NhbGUgaXMgb25seSBkZWZpbmVkIHdoZW4gdGhlIGRvbWFpbiBkb2VzIG5vdCBpbmNsdWRlIDAuCiAgICAgICAgICAgIHJldHVybiBtaW4gPiAwIHx8IG1heCA8IDA7CiAgICAgICAgfQogICAgICAgIC8vIFJldHVybnMgdHJ1ZSBpZiB0aGUgc2NhbGUgaXMgbnVtZXJpYy4KICAgICAgICAvLyBVc2VkIHRvIHByZXZlbnQgbm9uLW51bWVyaWMgY29sdW1ucyBmcm9tIGhhdmluZyBhIHNjYWxlLXNlbGVjdGlvbgogICAgICAgIC8vIHJhZGlvIGdyb3VwLgogICAgICAgIF9pc051bWVyaWNDb2x1bW4oY29sSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIChjb2xJbmRleCA+PSB0aGlzLmNvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGggfHwKICAgICAgICAgICAgICAgIHRoaXMuY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zW2NvbEluZGV4XS50eXBlID09PQogICAgICAgICAgICAgICAgICAgICdEQVRBX1RZUEVfRkxPQVQ2NCcpOwogICAgICAgIH0KICAgICAgICAvLyBVc2UgdGhlIGZpcnN0IG1ldHJpYyBpZiB0aGVyZSBhcmUgbWV0cmljcywgb3Igb3RoZXJ3aXNlIHRoZSBmaXJzdAogICAgICAgIC8vIG51bWVyaWMgaHBhcmFtIGlmIHRoZXJlIGFyZSBocGFyYW1zLiBJZiB0aGVyZSBhcmUgbm8gbnVtZXJpYyBjb2x1bW5zCiAgICAgICAgLy8gcmV0dXJuIHVuZGVmaW5lZC4KICAgICAgICBfZGVmYXVsdENvbG9yQnlDb2x1bW5JbmRleCgpIHsKICAgICAgICAgICAgaWYgKHRoaXMuY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hLm1ldHJpY0luZm9zLmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiB0aGlzLmNvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYS5ocGFyYW1JbmZvcy5sZW5ndGg7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgaSA9IHRoaXMuY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zLmZpbmRJbmRleCgoaW5mbykgPT4gaW5mby50eXBlID09PSAnREFUQV9UWVBFX0ZMT0FUNjQnKTsKICAgICAgICAgICAgaWYgKGkgIT09IC0xKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gaTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gdW5kZWZpbmVkOwogICAgICAgIH0KICAgIH07CiAgICBUZkhwYXJhbXNTY2FsZUFuZENvbG9yQ29udHJvbHMudGVtcGxhdGUgPSBodG1sIGAKICAgIDxkaXYgY2xhc3M9ImNvbnRyb2wtcGFuZWwiPgogICAgICA8IS0tICdDb2xvciBieScgZHJvcCBkb3duIG1lbnUgLS0+CiAgICAgIDxwYXBlci1kcm9wZG93bi1tZW51CiAgICAgICAgbGFiZWw9IkNvbG9yIGJ5IgogICAgICAgIGlkPSJjb2xvckJ5RHJvcERvd25NZW51IgogICAgICAgIGhvcml6b250YWwtYWxpZ249ImxlZnQiCiAgICAgID4KICAgICAgICA8cGFwZXItbGlzdGJveAogICAgICAgICAgY2xhc3M9ImRyb3Bkb3duLWNvbnRlbnQiCiAgICAgICAgICBzbG90PSJkcm9wZG93bi1jb250ZW50IgogICAgICAgICAgc2VsZWN0ZWQ9Int7b3B0aW9ucy5jb2xvckJ5Q29sdW1uSW5kZXh9fSIKICAgICAgICAgIGlkPSJjb2xvckJ5TGlzdEJveCIKICAgICAgICA+CiAgICAgICAgICA8dGVtcGxhdGUKICAgICAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgICAgIGl0ZW1zPSJbW29wdGlvbnMuY29sdW1uc11dIgogICAgICAgICAgICBhcz0iY29sdW1uIgogICAgICAgICAgICBpZD0iY29sb3JCeUNvbHVtblRlbXBsYXRlIgogICAgICAgICAgPgogICAgICAgICAgICA8cGFwZXItaXRlbSBkaXNhYmxlZD0iW1shX2lzTnVtZXJpY0NvbHVtbihjb2x1bW4uaW5kZXgpXV0iPgogICAgICAgICAgICAgIFtbY29sdW1uLm5hbWVdXQogICAgICAgICAgICA8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvcGFwZXItbGlzdGJveD4KICAgICAgPC9wYXBlci1kcm9wZG93bi1tZW51PgoKICAgICAgPCEtLSBDb2x1bW5zIHNjYWxlcyAtLT4KICAgICAgPGRpdiBjbGFzcz0iY29sdW1ucy1jb250YWluZXIiPgogICAgICAgIDwhLS0gU2NhbGUgb3B0aW9ucyBmb3IgZWFjaCBudW1lcmljIGZlYXR1cmUgLS0+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20tcmVwZWF0IiBpdGVtcz0ie3tvcHRpb25zLmNvbHVtbnN9fSIgYXM9ImNvbHVtbiI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2lzTnVtZXJpY0NvbHVtbihjb2x1bW4uaW5kZXgpXV0iPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJjb2x1bW4iPgogICAgICAgICAgICAgIDxkaXYgY2xhc3M9ImNvbHVtbi10aXRsZSI+W1tjb2x1bW4ubmFtZV1dPC9kaXY+CiAgICAgICAgICAgICAgPGRpdj4KICAgICAgICAgICAgICAgIDxwYXBlci1yYWRpby1ncm91cAogICAgICAgICAgICAgICAgICBjbGFzcz0ic2NhbGUtcmFkaW8tZ3JvdXAiCiAgICAgICAgICAgICAgICAgIHNlbGVjdGVkPSJ7e2NvbHVtbi5zY2FsZX19IgogICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uIG5hbWU9IkxJTkVBUiI+CiAgICAgICAgICAgICAgICAgICAgTGluZWFyCiAgICAgICAgICAgICAgICAgIDwvcGFwZXItcmFkaW8tYnV0dG9uPgogICAgICAgICAgICAgICAgICA8IS0tIFRoZSBpZCBoZXJlIGlzIHVzZWQgdG8gYWNjZXNzIHRoaXMgYnV0dG9uIGluIHVuaXQKICAgICAgICAgICAgICAgICAgICAgICB0ZXN0cy4tLT4KICAgICAgICAgICAgICAgICAgPHBhcGVyLXJhZGlvLWJ1dHRvbgogICAgICAgICAgICAgICAgICAgIGlkPSJsb2dTY2FsZUJ1dHRvbl9bW2NvbHVtbi5uYW1lXV0iCiAgICAgICAgICAgICAgICAgICAgbmFtZT0iTE9HIgogICAgICAgICAgICAgICAgICAgIGRpc2FibGVkPSJbWyFfYWxsb3dMb2dTY2FsZShjb2x1bW4sIHNlc3Npb25Hcm91cHMuKildXSIKICAgICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICAgIExvZ2FyaXRobWljCiAgICAgICAgICAgICAgICAgIDwvcGFwZXItcmFkaW8tYnV0dG9uPgogICAgICAgICAgICAgICAgICA8cGFwZXItcmFkaW8tYnV0dG9uIG5hbWU9IlFVQU5USUxFIj4KICAgICAgICAgICAgICAgICAgICBRdWFudGlsZQogICAgICAgICAgICAgICAgICA8L3BhcGVyLXJhZGlvLWJ1dHRvbj4KICAgICAgICAgICAgICAgIDwvcGFwZXItcmFkaW8tZ3JvdXA+CiAgICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICA8L2Rpdj4KICAgIDwvZGl2PgoKICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CiAgICAgIC5jb250cm9sLXBhbmVsIHsKICAgICAgICBvdmVyZmxvdzogYXV0bzsKICAgICAgfQogICAgICAuY29sdW1uIHsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgbWFyZ2luLXJpZ2h0OiA1cHg7CiAgICAgICAgYm9yZGVyOiBzb2xpZCAxcHggZGFya2dyYXk7CiAgICAgICAgcGFkZGluZzogM3B4OwogICAgICB9CiAgICAgIC5jb2x1bW4tdGl0bGUgewogICAgICAgIC8qIEZpdCBldmVyeSB0aXRsZSBpbiBvbmUgbGluZSBzbyB0aGUgcmFkaW8gYm94ZXMgYWxpZ24gdmVydGljYWxseS4gKi8KICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICAgIHRleHQtZGVjb3JhdGlvbjogdW5kZXJsaW5lOwogICAgICB9CiAgICAgIC5jb2x1bW5zLWNvbnRhaW5lciB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogICAgICB9CiAgICAgIC5zY2FsZS1yYWRpby1ncm91cCBwYXBlci1yYWRpby1idXR0b24gewogICAgICAgIHBhZGRpbmc6IDJweDsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQogICAgICBwYXBlci1saXN0Ym94IHsKICAgICAgICBtYXgtaGVpZ2h0OiAxNWVtOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1NjYWxlQW5kQ29sb3JDb250cm9scy5wcm90b3R5cGUsICJjb25maWd1cmF0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc1NjYWxlQW5kQ29sb3JDb250cm9scy5wcm90b3R5cGUsICJzZXNzaW9uR3JvdXBzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTY2FsZUFuZENvbG9yQ29udHJvbHMucHJvdG90eXBlLCAib3B0aW9ucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdjb25maWd1cmF0aW9uLionKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmSHBhcmFtc1NjYWxlQW5kQ29sb3JDb250cm9scy5wcm90b3R5cGUsICJfY29uZmlndXJhdGlvbkNoYW5nZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3Nlc3Npb25Hcm91cHMuKicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZIcGFyYW1zU2NhbGVBbmRDb2xvckNvbnRyb2xzLnByb3RvdHlwZSwgIl91bnNlbGVjdERpc2FibGVkTG9nU2NhbGVzIiwgbnVsbCk7CiAgICBUZkhwYXJhbXNTY2FsZUFuZENvbG9yQ29udHJvbHMgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ocGFyYW1zLXNjYWxlLWFuZC1jb2xvci1jb250cm9scycpCiAgICBdLCBUZkhwYXJhbXNTY2FsZUFuZENvbG9yQ29udHJvbHMpOwoKICAgIGNsYXNzIEx1bW8gZXh0ZW5kcyBIVE1MRWxlbWVudCB7CiAgICAgIHN0YXRpYyBnZXQgdmVyc2lvbigpIHsKICAgICAgICByZXR1cm4gJzEuNi4wJzsKICAgICAgfQogICAgfQoKICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgndmFhZGluLWx1bW8tc3R5bGVzJywgTHVtbyk7CgogICAgY29uc3QgJF9kb2N1bWVudENvbnRhaW5lciQ1ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTsKCiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDUuaW5uZXJIVE1MID0gYDxjdXN0b20tc3R5bGU+CiAgPHN0eWxlPgogICAgaHRtbCB7CiAgICAgIC8qIEJhc2UgKGJhY2tncm91bmQpICovCiAgICAgIC0tbHVtby1iYXNlLWNvbG9yOiAjRkZGOwoKICAgICAgLyogVGludCAqLwogICAgICAtLWx1bW8tdGludC01cGN0OiBoc2xhKDAsIDAlLCAxMDAlLCAwLjMpOwogICAgICAtLWx1bW8tdGludC0xMHBjdDogaHNsYSgwLCAwJSwgMTAwJSwgMC4zNyk7CiAgICAgIC0tbHVtby10aW50LTIwcGN0OiBoc2xhKDAsIDAlLCAxMDAlLCAwLjQ0KTsKICAgICAgLS1sdW1vLXRpbnQtMzBwY3Q6IGhzbGEoMCwgMCUsIDEwMCUsIDAuNSk7CiAgICAgIC0tbHVtby10aW50LTQwcGN0OiBoc2xhKDAsIDAlLCAxMDAlLCAwLjU3KTsKICAgICAgLS1sdW1vLXRpbnQtNTBwY3Q6IGhzbGEoMCwgMCUsIDEwMCUsIDAuNjQpOwogICAgICAtLWx1bW8tdGludC02MHBjdDogaHNsYSgwLCAwJSwgMTAwJSwgMC43KTsKICAgICAgLS1sdW1vLXRpbnQtNzBwY3Q6IGhzbGEoMCwgMCUsIDEwMCUsIDAuNzcpOwogICAgICAtLWx1bW8tdGludC04MHBjdDogaHNsYSgwLCAwJSwgMTAwJSwgMC44NCk7CiAgICAgIC0tbHVtby10aW50LTkwcGN0OiBoc2xhKDAsIDAlLCAxMDAlLCAwLjkpOwogICAgICAtLWx1bW8tdGludDogI0ZGRjsKCiAgICAgIC8qIFNoYWRlICovCiAgICAgIC0tbHVtby1zaGFkZS01cGN0OiBoc2xhKDIxNCwgNjElLCAyNSUsIDAuMDUpOwogICAgICAtLWx1bW8tc2hhZGUtMTBwY3Q6IGhzbGEoMjE0LCA1NyUsIDI0JSwgMC4xKTsKICAgICAgLS1sdW1vLXNoYWRlLTIwcGN0OiBoc2xhKDIxNCwgNTMlLCAyMyUsIDAuMTYpOwogICAgICAtLWx1bW8tc2hhZGUtMzBwY3Q6IGhzbGEoMjE0LCA1MCUsIDIyJSwgMC4yNik7CiAgICAgIC0tbHVtby1zaGFkZS00MHBjdDogaHNsYSgyMTQsIDQ3JSwgMjElLCAwLjM4KTsKICAgICAgLS1sdW1vLXNoYWRlLTUwcGN0OiBoc2xhKDIxNCwgNDUlLCAyMCUsIDAuNSk7CiAgICAgIC0tbHVtby1zaGFkZS02MHBjdDogaHNsYSgyMTQsIDQzJSwgMTklLCAwLjYxKTsKICAgICAgLS1sdW1vLXNoYWRlLTcwcGN0OiBoc2xhKDIxNCwgNDIlLCAxOCUsIDAuNzIpOwogICAgICAtLWx1bW8tc2hhZGUtODBwY3Q6IGhzbGEoMjE0LCA0MSUsIDE3JSwgMC44Myk7CiAgICAgIC0tbHVtby1zaGFkZS05MHBjdDogaHNsYSgyMTQsIDQwJSwgMTYlLCAwLjk0KTsKICAgICAgLS1sdW1vLXNoYWRlOiBoc2woMjE0LCAzNSUsIDE1JSk7CgogICAgICAvKiBDb250cmFzdCAqLwogICAgICAtLWx1bW8tY29udHJhc3QtNXBjdDogdmFyKC0tbHVtby1zaGFkZS01cGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTEwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTEwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTIwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTIwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTMwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTMwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTQwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTQwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTUwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTUwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTYwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTYwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTcwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTcwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTgwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTgwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0LTkwcGN0OiB2YXIoLS1sdW1vLXNoYWRlLTkwcGN0KTsKICAgICAgLS1sdW1vLWNvbnRyYXN0OiB2YXIoLS1sdW1vLXNoYWRlKTsKCiAgICAgIC8qIFRleHQgKi8KICAgICAgLS1sdW1vLWhlYWRlci10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0KTsKICAgICAgLS1sdW1vLWJvZHktdGV4dC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC05MHBjdCk7CiAgICAgIC0tbHVtby1zZWNvbmRhcnktdGV4dC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC03MHBjdCk7CiAgICAgIC0tbHVtby10ZXJ0aWFyeS10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTUwcGN0KTsKICAgICAgLS1sdW1vLWRpc2FibGVkLXRleHQtY29sb3I6IHZhcigtLWx1bW8tY29udHJhc3QtMzBwY3QpOwoKICAgICAgLyogUHJpbWFyeSAqLwogICAgICAtLWx1bW8tcHJpbWFyeS1jb2xvcjogaHNsKDIxNCwgOTAlLCA1MiUpOwogICAgICAtLWx1bW8tcHJpbWFyeS1jb2xvci01MHBjdDogaHNsYSgyMTQsIDkwJSwgNTIlLCAwLjUpOwogICAgICAtLWx1bW8tcHJpbWFyeS1jb2xvci0xMHBjdDogaHNsYSgyMTQsIDkwJSwgNTIlLCAwLjEpOwogICAgICAtLWx1bW8tcHJpbWFyeS10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLXByaW1hcnktY29sb3IpOwogICAgICAtLWx1bW8tcHJpbWFyeS1jb250cmFzdC1jb2xvcjogI0ZGRjsKCiAgICAgIC8qIEVycm9yICovCiAgICAgIC0tbHVtby1lcnJvci1jb2xvcjogaHNsKDMsIDEwMCUsIDYxJSk7CiAgICAgIC0tbHVtby1lcnJvci1jb2xvci01MHBjdDogaHNsYSgzLCAxMDAlLCA2MCUsIDAuNSk7CiAgICAgIC0tbHVtby1lcnJvci1jb2xvci0xMHBjdDogaHNsYSgzLCAxMDAlLCA2MCUsIDAuMSk7CiAgICAgIC0tbHVtby1lcnJvci10ZXh0LWNvbG9yOiBoc2woMywgOTIlLCA1MyUpOwogICAgICAtLWx1bW8tZXJyb3ItY29udHJhc3QtY29sb3I6ICNGRkY7CgogICAgICAvKiBTdWNjZXNzICovCiAgICAgIC0tbHVtby1zdWNjZXNzLWNvbG9yOiBoc2woMTQ1LCA4MCUsIDQyJSk7IC8qIGhzbCgxNDQsODIlLDM3JSk7ICovCiAgICAgIC0tbHVtby1zdWNjZXNzLWNvbG9yLTUwcGN0OiBoc2xhKDE0NSwgNzYlLCA0NCUsIDAuNTUpOwogICAgICAtLWx1bW8tc3VjY2Vzcy1jb2xvci0xMHBjdDogaHNsYSgxNDUsIDc2JSwgNDQlLCAwLjEyKTsKICAgICAgLS1sdW1vLXN1Y2Nlc3MtdGV4dC1jb2xvcjogaHNsKDE0NSwgMTAwJSwgMzIlKTsKICAgICAgLS1sdW1vLXN1Y2Nlc3MtY29udHJhc3QtY29sb3I6ICNGRkY7CiAgICB9CiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+PGRvbS1tb2R1bGUgaWQ9Imx1bW8tY29sb3IiPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgW3RoZW1lfj0iZGFyayJdIHsKICAgICAgICAvKiBCYXNlIChiYWNrZ3JvdW5kKSAqLwogICAgICAgIC0tbHVtby1iYXNlLWNvbG9yOiBoc2woMjE0LCAzNSUsIDIxJSk7CgogICAgICAgIC8qIFRpbnQgKi8KICAgICAgICAtLWx1bW8tdGludC01cGN0OiBoc2xhKDIxNCwgNjUlLCA4NSUsIDAuMDYpOwogICAgICAgIC0tbHVtby10aW50LTEwcGN0OiBoc2xhKDIxNCwgNjAlLCA4MCUsIDAuMTQpOwogICAgICAgIC0tbHVtby10aW50LTIwcGN0OiBoc2xhKDIxNCwgNjQlLCA4MiUsIDAuMjMpOwogICAgICAgIC0tbHVtby10aW50LTMwcGN0OiBoc2xhKDIxNCwgNjklLCA4NCUsIDAuMzIpOwogICAgICAgIC0tbHVtby10aW50LTQwcGN0OiBoc2xhKDIxNCwgNzMlLCA4NiUsIDAuNDEpOwogICAgICAgIC0tbHVtby10aW50LTUwcGN0OiBoc2xhKDIxNCwgNzglLCA4OCUsIDAuNSk7CiAgICAgICAgLS1sdW1vLXRpbnQtNjBwY3Q6IGhzbGEoMjE0LCA4MiUsIDkwJSwgMC42KTsKICAgICAgICAtLWx1bW8tdGludC03MHBjdDogaHNsYSgyMTQsIDg3JSwgOTIlLCAwLjcpOwogICAgICAgIC0tbHVtby10aW50LTgwcGN0OiBoc2xhKDIxNCwgOTElLCA5NCUsIDAuOCk7CiAgICAgICAgLS1sdW1vLXRpbnQtOTBwY3Q6IGhzbGEoMjE0LCA5NiUsIDk2JSwgMC45KTsKICAgICAgICAtLWx1bW8tdGludDogaHNsKDIxNCwgMTAwJSwgOTglKTsKCiAgICAgICAgLyogU2hhZGUgKi8KICAgICAgICAtLWx1bW8tc2hhZGUtNXBjdDogaHNsYSgyMTQsIDAlLCAwJSwgMC4wNyk7CiAgICAgICAgLS1sdW1vLXNoYWRlLTEwcGN0OiBoc2xhKDIxNCwgNCUsIDIlLCAwLjE1KTsKICAgICAgICAtLWx1bW8tc2hhZGUtMjBwY3Q6IGhzbGEoMjE0LCA4JSwgNCUsIDAuMjMpOwogICAgICAgIC0tbHVtby1zaGFkZS0zMHBjdDogaHNsYSgyMTQsIDEyJSwgNiUsIDAuMzIpOwogICAgICAgIC0tbHVtby1zaGFkZS00MHBjdDogaHNsYSgyMTQsIDE2JSwgOCUsIDAuNDEpOwogICAgICAgIC0tbHVtby1zaGFkZS01MHBjdDogaHNsYSgyMTQsIDIwJSwgMTAlLCAwLjUpOwogICAgICAgIC0tbHVtby1zaGFkZS02MHBjdDogaHNsYSgyMTQsIDI0JSwgMTIlLCAwLjYpOwogICAgICAgIC0tbHVtby1zaGFkZS03MHBjdDogaHNsYSgyMTQsIDI4JSwgMTMlLCAwLjcpOwogICAgICAgIC0tbHVtby1zaGFkZS04MHBjdDogaHNsYSgyMTQsIDMyJSwgMTMlLCAwLjgpOwogICAgICAgIC0tbHVtby1zaGFkZS05MHBjdDogaHNsYSgyMTQsIDMzJSwgMTMlLCAwLjkpOwogICAgICAgIC0tbHVtby1zaGFkZTogaHNsKDIxNCwgMzMlLCAxMyUpOwoKICAgICAgICAvKiBDb250cmFzdCAqLwogICAgICAgIC0tbHVtby1jb250cmFzdC01cGN0OiB2YXIoLS1sdW1vLXRpbnQtNXBjdCk7CiAgICAgICAgLS1sdW1vLWNvbnRyYXN0LTEwcGN0OiB2YXIoLS1sdW1vLXRpbnQtMTBwY3QpOwogICAgICAgIC0tbHVtby1jb250cmFzdC0yMHBjdDogdmFyKC0tbHVtby10aW50LTIwcGN0KTsKICAgICAgICAtLWx1bW8tY29udHJhc3QtMzBwY3Q6IHZhcigtLWx1bW8tdGludC0zMHBjdCk7CiAgICAgICAgLS1sdW1vLWNvbnRyYXN0LTQwcGN0OiB2YXIoLS1sdW1vLXRpbnQtNDBwY3QpOwogICAgICAgIC0tbHVtby1jb250cmFzdC01MHBjdDogdmFyKC0tbHVtby10aW50LTUwcGN0KTsKICAgICAgICAtLWx1bW8tY29udHJhc3QtNjBwY3Q6IHZhcigtLWx1bW8tdGludC02MHBjdCk7CiAgICAgICAgLS1sdW1vLWNvbnRyYXN0LTcwcGN0OiB2YXIoLS1sdW1vLXRpbnQtNzBwY3QpOwogICAgICAgIC0tbHVtby1jb250cmFzdC04MHBjdDogdmFyKC0tbHVtby10aW50LTgwcGN0KTsKICAgICAgICAtLWx1bW8tY29udHJhc3QtOTBwY3Q6IHZhcigtLWx1bW8tdGludC05MHBjdCk7CiAgICAgICAgLS1sdW1vLWNvbnRyYXN0OiB2YXIoLS1sdW1vLXRpbnQpOwoKICAgICAgICAvKiBUZXh0ICovCiAgICAgICAgLS1sdW1vLWhlYWRlci10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0KTsKICAgICAgICAtLWx1bW8tYm9keS10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTkwcGN0KTsKICAgICAgICAtLWx1bW8tc2Vjb25kYXJ5LXRleHQtY29sb3I6IHZhcigtLWx1bW8tY29udHJhc3QtNzBwY3QpOwogICAgICAgIC0tbHVtby10ZXJ0aWFyeS10ZXh0LWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTUwcGN0KTsKICAgICAgICAtLWx1bW8tZGlzYWJsZWQtdGV4dC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0zMHBjdCk7CgogICAgICAgIC8qIFByaW1hcnkgKi8KICAgICAgICAtLWx1bW8tcHJpbWFyeS1jb2xvcjogaHNsKDIxNCwgODYlLCA1NSUpOwogICAgICAgIC0tbHVtby1wcmltYXJ5LWNvbG9yLTUwcGN0OiBoc2xhKDIxNCwgODYlLCA1NSUsIDAuNSk7CiAgICAgICAgLS1sdW1vLXByaW1hcnktY29sb3ItMTBwY3Q6IGhzbGEoMjE0LCA5MCUsIDYzJSwgMC4xKTsKICAgICAgICAtLWx1bW8tcHJpbWFyeS10ZXh0LWNvbG9yOiBoc2woMjE0LCAxMDAlLCA3MCUpOwogICAgICAgIC0tbHVtby1wcmltYXJ5LWNvbnRyYXN0LWNvbG9yOiAjRkZGOwoKICAgICAgICAvKiBFcnJvciAqLwogICAgICAgIC0tbHVtby1lcnJvci1jb2xvcjogaHNsKDMsIDkwJSwgNjMlKTsKICAgICAgICAtLWx1bW8tZXJyb3ItY29sb3ItNTBwY3Q6IGhzbGEoMywgOTAlLCA2MyUsIDAuNSk7CiAgICAgICAgLS1sdW1vLWVycm9yLWNvbG9yLTEwcGN0OiBoc2xhKDMsIDkwJSwgNjMlLCAwLjEpOwogICAgICAgIC0tbHVtby1lcnJvci10ZXh0LWNvbG9yOiBoc2woMywgMTAwJSwgNjclKTsKCiAgICAgICAgLyogU3VjY2VzcyAqLwogICAgICAgIC0tbHVtby1zdWNjZXNzLWNvbG9yOiBoc2woMTQ1LCA2NSUsIDQyJSk7CiAgICAgICAgLS1sdW1vLXN1Y2Nlc3MtY29sb3ItNTBwY3Q6IGhzbGEoMTQ1LCA2NSUsIDQyJSwgMC41KTsKICAgICAgICAtLWx1bW8tc3VjY2Vzcy1jb2xvci0xMHBjdDogaHNsYSgxNDUsIDY1JSwgNDIlLCAwLjEpOwogICAgICAgIC0tbHVtby1zdWNjZXNzLXRleHQtY29sb3I6IGhzbCgxNDUsIDg1JSwgNDclKTsKICAgICAgfQoKICAgICAgaHRtbCB7CiAgICAgICAgY29sb3I6IHZhcigtLWx1bW8tYm9keS10ZXh0LWNvbG9yKTsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1sdW1vLWJhc2UtY29sb3IpOwogICAgICB9CgogICAgICBbdGhlbWV+PSJkYXJrIl0gewogICAgICAgIGNvbG9yOiB2YXIoLS1sdW1vLWJvZHktdGV4dC1jb2xvcik7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1iYXNlLWNvbG9yKTsKICAgICAgfQoKICAgICAgaDEsCiAgICAgIGgyLAogICAgICBoMywKICAgICAgaDQsCiAgICAgIGg1LAogICAgICBoNiB7CiAgICAgICAgY29sb3I6IHZhcigtLWx1bW8taGVhZGVyLXRleHQtY29sb3IpOwogICAgICB9CgogICAgICBhIHsKICAgICAgICBjb2xvcjogdmFyKC0tbHVtby1wcmltYXJ5LXRleHQtY29sb3IpOwogICAgICB9CgogICAgICBibG9ja3F1b3RlIHsKICAgICAgICBjb2xvcjogdmFyKC0tbHVtby1zZWNvbmRhcnktdGV4dC1jb2xvcik7CiAgICAgIH0KCiAgICAgIGNvZGUsCiAgICAgIHByZSB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0xMHBjdCk7CiAgICAgICAgYm9yZGVyLXJhZGl1czogdmFyKC0tbHVtby1ib3JkZXItcmFkaXVzLW0pOwogICAgICB9CiAgICA8L3N0eWxlPgogIDwvdGVtcGxhdGU+CjwvZG9tLW1vZHVsZT48ZG9tLW1vZHVsZSBpZD0ibHVtby1jb2xvci1sZWdhY3kiPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZSBpbmNsdWRlPSJsdW1vLWNvbG9yIj4KICAgICAgOmhvc3QgewogICAgICAgIGNvbG9yOiB2YXIoLS1sdW1vLWJvZHktdGV4dC1jb2xvcikgIWltcG9ydGFudDsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1sdW1vLWJhc2UtY29sb3IpICFpbXBvcnRhbnQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJDUuY29udGVudCk7CgogICAgY29uc3QgJF9kb2N1bWVudENvbnRhaW5lciQ2ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTsKCiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDYuaW5uZXJIVE1MID0gYDxjdXN0b20tc3R5bGU+CiAgPHN0eWxlPgogICAgQGZvbnQtZmFjZSB7CiAgICAgIGZvbnQtZmFtaWx5OiAnbHVtby1pY29ucyc7CiAgICAgIHNyYzogdXJsKGRhdGE6YXBwbGljYXRpb24vZm9udC13b2ZmO2NoYXJzZXQ9dXRmLTg7YmFzZTY0LGQwOUdSZ0FCQUFBQUFCRWdBQXNBQUFBQUlpd0FBUUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFCSFUxVkNBQUFCQ0FBQUFEc0FBQUJVSUlzbGVrOVRMeklBQUFGRUFBQUFRd0FBQUZaQUlVdUtZMjFoY0FBQUFZZ0FBQUQ0QUFBRHJzQ1U4ZDVuYkhsbUFBQUNnQUFBQzJNQUFCZDRoOVRvMldobFlXUUFBQTNrQUFBQU1RQUFBRFlTbkNrdWFHaGxZUUFBRGhnQUFBQWRBQUFBSkFicEEzNW9iWFI0QUFBT09BQUFBQkFBQUFDc3BCQUFBR3h2WTJFQUFBNUlBQUFBV0FBQUFGaDU1SUFzYldGNGNBQUFEcUFBQUFBZkFBQUFJQUZLQVhCdVlXMWxBQUFPd0FBQUFURUFBQUl1VVVKWkNIQnZjM1FBQUEvMEFBQUJLd0FBQWVsbThTelZlSnhqWUdSZ1lPQmlNR0N3WTJCeWNmTUpZZURMU1N6Slk1QmlZR0dBQUpBOE1wc3hKek05a1lFRHhnUEtzWUJwRGlCbWc0Z0NBQ1k3QlVnQWVKeGpZR1MreURpQmdaV0JnYW1LYVE4REEwTVBoR1o4d0dESXlBUVVaV0JsWnNBS0F0SmNVeGdjWGpHKzBtSU8rcC9GRU1VY3hEQU5LTXdJa2dNQUJuOE1MUUI0bk8zU1dXNkRNQUJGMFV0d0NFbklQTS96aExLOExxaGZYUnliU1AxNFhVWXRIVjloR1lRd1FCTklvM2NVSVBraFFlTTdyaWIxZWtxblhnOTgxWHVDMXF2eTg0bHpvamxlaDNwdXhMMGhQakdqUlU0NzN0ZWxvRWVmQVVOR2pKa3daY2FjQlV0V3JObXdaY2VlQTBkT25MbHc1Y2FkQjA5ZWxQR2hHZitqME5USS82NUtmWGVyVDZKaHFLbnBSS3RnT3B1cWFUcnRLalBVbHFIbWh0bzIxSTdwTDZpNmhscVkzcTdxR1dyZlVBZUdPalRVa2FHT0RYVmlxRk5EblJucTNGQVhocm8wMUpXaHJnMTFZNmhiUTkwWjZ0NVFENFo2Tk5TVG9aNE45V0tvVjBPOUdlcmRVQitHK2pUVWw2R1dSdmtMMjRCa0VYaWN0Vmg5YkZ2VkZiL254dmJ6KzdSZi9ONnpIY2QyYkNmUCtXZ2MxWjlOMGpwTm5FTDZrYlJWUzZIQTJoUVlHaDlUR1IxQ2JDcWEyclhyV09rUUUvc0hOSmdtdFp2b1ZOWnFFMUIxRE5IeHpUUXhDZWhVVFlpSlRReUVOdWkwcVNMZXpyM1BkdXlRZmdtUldPZmRlOCs5NTUxejdybm4vTzRqTG9KL2JSUDBVYUtRTUxGSmpwQkF2cGhMWkMzRGswb2s3V0J6UjIvdXBKczdSeXcvbmZGYmxuL3V1Ti9hcEN2d3JLTHJTdlVxUnVmYm01cG4wZnMwdzRnWXhuR1ZQNnFIbk80YldpRFFHUWd3dFM2bG0zbEIzUW9YMU0ydndFbXV6aXJGMzl5K0VzMitESjhkMXBreXFCSXFvemUzRDErWno0RHJGb2F6eEk4ZFd3TXJEbFoyRE1xUUFSOUFST3NKVSsyY21sVFBhelRjbzUyRjF4VGEyYTIrSzh2dnE5MmRWSG10TG9QZVFYL0FaUFJZR3RoRFlPZVpqQmpLb0ZzVkd1bFIzbFdVOTVXZUNLNDRxSFU3TWhXVUdVS1pEVDNvS1VjRzJHV3VoK0VERGZVWUEvamhBaGwwVE9zSk5ZU0V1N21RbWkzVXpmWHdaS0E0QnNWc0hMWFFZR2dSVzk1dUV0cEoxVmZuOVhpTHJpUkJsRkVxeHNEakEwOXlDTlVvUXh4d2Q3S1dTVHQyeTNHVEtpZmxxSFJTb1daYzNtMTFXYS9mSmRGZ1hENHNTWWZsZUpCS2Q4R016N0o4ZFpuL2NHUkNjS0dEbkEyR2UzZkt6Y3ZsblRETnRoR1dMWHpYL1dhWHRVQW1SZ2VMbEhTcjMwcjBHOVVUWE1iMEF0bXd6T295NzNma1NsSFprZHV3L1RZdVU5Y0FENFl1dFBveFRUc0EzNzk3d1ZyNFovMU5DNXpBUkhyNHZ0eEpqeElmaVpNaE1rYldrKzE0Qm5KWkt3cUdad0Rmc3dMeXhXRFNnMTFyRkxKRjdOb3B4amQxaDEvUU9UK29lemdmdTNZcStIaytkdWY1eCs0MG8xR1RrYUlnaWtLL0lFbkM2YVl4Q1VCYVpKU040WFRZRmpVL1lNTklLcUp3aERHT0NDSThGRFhuWG1YanRHaEdKeVNocWpBT25CT2tXMkpHOVM3R2dZZU1XQVU1SnpobldtQk9hT00rQ0tFUG9xU2ZGREMyVW5xK0RMbFVnVVZVRkZMWkdKZzZqdGxvanNkc2E4a1BPYlB1SmRpNWRuQmRCc0xKTUdUV0RhNHQySnZ0d3VQbzlzK1k4NnN1di9XMzNRRzFyQWFPQVVWK3Z4NEs2ZjJEMDRQVktsQzdXTFNyWnpBaTQ1WlY2bElDN1dvWHFtUnl2VXFvVndyelVvVnNJamVUWFdRditSSDVHVGxCWGlCL0luOGxuMEliQkNBRk9hakFKcmdaWXlPSFdxT2ZVZS9hSGpJMTJSNk9RbzFqQ2d0MjE1bCs0ZjZYUGIrME1Ob3UwVis0M24yRjc3dFNmUmIyNGQ3eml0Z25LbXZZSHM2OXp1Z2FQdkJ3djZpb1hrYjJMZEw2NUF0dzUxdUxrWGx1MWJoTU1SY1hTUGNZb3FLSVJsaDM0bFFQOC81SmJ1VUZ5ZTR2eEQ2LzZNeEZGMTFDMHVWTHI5VWxndzQ0dFMzcE1WaU5MVUV4YnljRmdMSWN0K1FETWliUmlteDF5ZFV6OEZYWml1T0lEQk9NVlgyblVaYytodU5FNVhVSjgxdWlKb2lhYndxYVZGMHVhY0tiYXUvcGw0UjJWVzBYWGxKcmE2Ym9WcllHNjQ2VEY1Tll6d3k0dmpFTlZyRGxjTnBaUGw4REg2WFg4WFdDeDBtdldWWlk2S0ZMcnZzWTY2L3pQaWN0NUZueGFOVVIvanV2WkNNM1R2RDYwRTJXMXRaaXpiWFRQRHVhYmNtMG5iYnpwV0twbUExYXlCUThnaWVkTFVNK0Ewa05qQmpRam11WXo3WXJnSVhZdm1GNjNaTEJ3U1hycG45VGI5d3dkZC9VMUgwUE1RSzNYY084dWwzV1Q3UHlQUGRweTBUZW1LeE5SY0pOYXVpWEpublVEcFVwcFFXczRTblVJeTBFRVNHWXFKWVFMR0h4emFHV3dWSWFTNlk3bVFGTThaallEUTNheGpmNjFTV2pVMzNKd09aQTFwd2FHMUw5bXpmNzFhSFJkWDFKSHc2RnAwYVhoTndicXllR05nNE5iZHpHQ0J4b3o0WlhqeTROdTY5WnI2c0RZNnZNckxVNW5BMVA4SmtiZFdYSjZFUmZNcnl2TmgxSmZROStUNGRJaEd2Szl3M2R4akJCemF0c1EvTWxPSFZJRG5ZcER6Nm9kQVhsUTAxdDJQYTVJYWZkOE1NcHhBZURLUDBDNkNqZ1ZMVDVvc0I2aWNVeDAxbFdqWHh6VC9HeVJGMndlbEVNNVovN2pHM1ZqUTFTck5uNUlieXpPRzVkb2JCMy9RSHh5WnZzWGNvejhJb0V3UzdwbENnK3p4SFFrNDI0cTlCZkVwa0VTSmJGSFF1c0RCU1dGa3VCa29QTzBrTEt3UlZZanhHWGxIVGNURFFNSi9INlRYOWFma083bW5yYVRPMWZlVG5aQVhMdTRjcDdIQVhNbU5HMXllRms5VGdTL05IaFpSLzRRb0JUci9aQis2aENneWwxNU5xMVViTjZuRTEvWm5QMVUyY2l6Q0JwdnM4Y0pRWko0TGtZeDVOL3laUEFVWk5RUTBWNGYzQlFsbFdySzNZUnpsMzBkT1Q2UlZuMnVwTnVyNndvU2E4Q3FwZFQvYUtuQk00bzNqTnVyOWQ5eHF0VVQ2dmVCRXQ5Q2E5YXQrRVJ6RUVoVWtSOHNhNW1RNGFWdkpvVmVFQTh6STRlaTVtVUxYRkd5VTd6LzZUQWVZTFZjcHpTV1pZOFBZWUY1eXJUVjYwc1QwK1hWMTQxdlgrK1dmMTZWMmJGZUdWUFpYeEZwa3Z5ZUtUV0xsemZXMG1uS3hzWTZZMzI5NC8wOTk4U0NmWDFibG01cGJjdkZHbHEvcjA3TVJBTWhZSURpVzVKRktXVzN2ZHJFcENzWlNKRytvbTdadS9QU1NjWkpoTmtMYm1XNVdzcjEycFdxVzV6S3Rsd1JTNGJGT3hVdzE3bUN6eTZsc2tDRGwxV1lPR1dEWXJBRHJNQTdCRER3ZVdXTmQ1a29pSm5SMWR6K3l0TFAycTBTcVBCMWxuSzJjY0I3UlllNEZTb1BrczNpQjN0NHR4VFNIY3RiMnN5MWl2azBwdkh1Q05tNncxZjZ3eHYzK09DZ043OExxZFFuVVZoN1Iwb1RBcDB6T2YycmJXNzcwVnU1QzJkSXlHZFRuSG84elNqaTdkcHBqMFVTb1ZDeitsaFJNVGg1M1RlcTlWYkdmYmp1U2JBb29TZFhheVk0UFlIZzM3NEM2ZjdnbDFCL0RYdUo0L1FYeE9CZEpGSnNwRnNJM2VncG9XVVVDamxUSUZuTllObCtaeVpLbUJlWUtHSGtEMVF5RGxoYUtiS3dLY0lKcUo0VExKMk9tZFkvSldYYWU0RGRHQnc4SFo3ZVhjZ0ZGMnpyMlNvYWxEcnk1aUtxb2EwUHVoZTNoUFEyczNlbFRZTStNSStuM3JLMEtnTDcvTGEzR2VNTHQ2bTd1OTEydkdudnRPUmlJYTBxQm1ocVZpK1hXOVhOQm1xYjhlVmdLeklIZkdJNWJOb0c3WDBVQ3plSVNtcUljTy9uWThGSDdVOGF2WDlmeC9TVCtoeDBzZXpQdzlReThNdW0zR1dmMk40VXkveUlZR1ZCWGJKSFdJWnA3ZGZUY3B0ZE1UcjlRbXE3RGFpSy91a3FDTDRrdDRSVWZTNVhQbk10bVQyMi9tUUZxRjdlbVNxdHJsdThTVkVseERSSnJaT0RrcHV3ZTBWZlRmamRFcDFmN0E3ditmb3pOQlhVSi82V1R1SzJUdEZscEZWWkFaM0xjRnZVaTFaMnAyWVQrRU1Ba0dKVlN0T3pMVEFQZzRJcVdJQWx6UlNqT0JrbDJ6eGozVEt5Y3B6VC9NbnZYM3VhU01XTStnVTBya1hqb2hoZWZWUk1hcHMzL2tMTVNLdjIzbFQyM3V4UXJrUWp5T0psZU1Ec2RoQW5ENlpHRWxXWjVNakNYekNFL2hrV1grV0Y0a256R2hWT3lLMmVRWmVrVjNleW8wekw4a3VZV0NuREN2ampoQWtjVFBPQkRYVmRvYXYzSFZjRm5Rakx2dFY5UzJwMHpBNkplZ1B3TVF4dCt5RmIzbGw5ekdscS81ZFJLYjNjRXlRWW9hTllwaGFySjd4Q0I3QVd4c0xZM2pqWlhZMFhzWmowV2p3YzlJNlBQL2RLQUJuQ1phcUhwYVpFQUN4azRaZUxaU0tOZ1pBQmwrbFlRWDFzSlFPU1gzbjZyNDEwZXZjb3VkNUplQUdVWFZQOUgxdFpPS2VqVHE0T25vMHowZXJybzFGcm5PcG9odmExZC9oVGR0VnNRZEtONVc5UmxUM05qRDBuem55S05UZ0tBTWZXTldjeW9kVjBJR0xQSUhPRjBvNEp5cXVmYUs0ejZXSUl6dUdoM2Q4Yzhjd1FnOEVSK09WeHlyamRtOHZOdWh0czRMb09paEd4SU11VWRnendpWU43eGhoMStvWm5KTnVURzdnUVp2dTRYV1o5R0FaWmpHRXVid2VQcVlodEtEVEgrOVZRa2wxNy9pR3lic25KKzgrc0t0eVByY2xsOXR5NjVac2RzdC85aXFwRUtoN001VmRCeGgzY3NPZE5jNnRXM0kxdXlNMVB6T1hlZ1NPckxGc0ZOSTJPMjdNK1RGMkFwbk45TVV2NXVkNkxqeEl2RVFuSFJ6eEl1NElzQTlNTEZrSm4ydGNab1o3T043ZFhlN3VqcmM4SHJ1c1BLYW1scVh3ZDc3bFFVdUxwaWxhdTRQVU1hcHVlQmI3aXJVNFJvVVhFWVh1VnVJR2xSR21PcCsybE5rYVJQVnppT3FtbGFadmFxRzRkRmdTajBqeEVKV3J2MTJJVVdudG13K3JmUWFyUkUwQXBoNG9jSTZubFVsR3FzK3UzLytUL2V0aFc2MlBwSHAyZUhiWnN0bmgvd09POTV5REFIaWNZMkJrWUdBQVlpMk5PSjk0ZnB1dkROek1MNEFpRE5jL2Z6cUVvUCsvWnA3S2RBdkk1V0JnQW9rQ0FHa2NEZmdBQUFCNG5HTmdaR0JnRHZxZkJTUmZNQUFCODFRR1JnWlVvQTBBVnZZRGJ3QUFBSGljWTJCZ1lHQitNVFF3QU04RUpvOEFBQUFBQUU0QW1nRG9BUW9CTEFGT0FYQUJtZ0hFQWU0Q0dnS2NBdWdFbWdTOEJOWUU4Z1VPQlNvRmVnWFFCZjRHUkFabUJyWUhHQWVRQ0JnSVVnaHFDUDRKUmdtK0Nkb0tCQW84Q29JS3VBcndDMUFMbGd1OGVKeGpZR1JnWU5CbVRHRVFaUUFCSmlEbUFrSUdodjlnUGdNQUdKUUJ2QUI0bkcyUlBVN0RNQmlHMy9RUDBVb0lCR0poOFFJTGF2b3pkbVJvOXc3ZDA5UnBVemx4NUxnVnZRTW40QkFjZ29FemNBZ093VnZ6U1pWUWJjbmY0OGZ2RnlzSmdHdDhJY0p4Uk9pRzlUZ2F1T0R1ajV1a0crRVcrVUc0alI0ZWhUdjBRK0V1bmpFUjd1RVdtaytJV3BjMGQzZ1ZidUFLYjhKTituZmhGdmxEdUkxN2ZBcDM2TCtGdTFqZ1I3aUhwK2pGN0FyYnoxTmIxbk85M3BuRW5jU0pGdHJWdVMzVktCNmU1RXlYMmlWZXI5VHlvT3I5ZXV4OXBqSm5DelcxcGRmR1dGVTV1OVdwanpmZVY1UEJJQk1mcDdhQXdRNEZMUHJJa2JLV3FESG4rNjdwRFJLNHM0bHpic0V1eDVxSHZjSUlNYi9udWVTTXlUS2tFM2pXRmROTEhMalcyUFBtTWExSHhuM0dqR1cvd2pUMEh0T0cwOUpVNFd4TGs5TEgySVN1aXY5dHdKbjl5OGZoOXVJWEkrQmtuQUFBQUhpY2JZN1pib013RUVXNUNWQkNTTHJ2Kzc2a2ZKUmpUd0hGc2RHQUcrWHZ5NUpVZmVoSUhwMHJueG1OTi9ENmlyMy9hNFlCaHZBUklNUU9Jb3dRWTR3RUUweXhpejNzNHdDSE9NSXhUbkNLTTV6akFwZTR3alZ1Y0lzNzNPTUJqM2pDTTE3d2lqZTg0d016ZkhxSjBFVm1Va21tSm83N29PbXJIdmZJUlpiWHNUQ1pwbFRabGRsZ2IzVFlHVkhQcm93RnMxMXQxQTU3dGNPTjJyRXJSM1BCcWN3RjEvNmN0STZrMEdTVTRKSE1TUzZXZ2hkSlE5OXNUYmZ1TjdRTEo5dlEzN2ROcmd5a3RuSXhsRFlMSk51cWl0cFJiWVdLRk51eURUNnBvZzZvT1lLSHRLYWtlYWtxS2pIWHBQd2xHUmNzQytPcXhMSWlKcFhxb3FxRE1yZUcybDVidjlSaTNUUlgrYzIzRFpuYTlXRkZnbVh1TzZQczFKbS93NkVyVzhOM0ZiSG4vUUM0NDRqMEFBPT0pIGZvcm1hdCgnd29mZicpOwogICAgICBmb250LXdlaWdodDogbm9ybWFsOwogICAgICBmb250LXN0eWxlOiBub3JtYWw7CiAgICB9CgogICAgaHRtbCB7CiAgICAgIC0tbHVtby1pY29ucy1hbGlnbi1jZW50ZXI6ICJcXGVhMDEiOwogICAgICAtLWx1bW8taWNvbnMtYWxpZ24tbGVmdDogIlxcZWEwMiI7CiAgICAgIC0tbHVtby1pY29ucy1hbGlnbi1yaWdodDogIlxcZWEwMyI7CiAgICAgIC0tbHVtby1pY29ucy1hbmdsZS1kb3duOiAiXFxlYTA0IjsKICAgICAgLS1sdW1vLWljb25zLWFuZ2xlLWxlZnQ6ICJcXGVhMDUiOwogICAgICAtLWx1bW8taWNvbnMtYW5nbGUtcmlnaHQ6ICJcXGVhMDYiOwogICAgICAtLWx1bW8taWNvbnMtYW5nbGUtdXA6ICJcXGVhMDciOwogICAgICAtLWx1bW8taWNvbnMtYXJyb3ctZG93bjogIlxcZWEwOCI7CiAgICAgIC0tbHVtby1pY29ucy1hcnJvdy1sZWZ0OiAiXFxlYTA5IjsKICAgICAgLS1sdW1vLWljb25zLWFycm93LXJpZ2h0OiAiXFxlYTBhIjsKICAgICAgLS1sdW1vLWljb25zLWFycm93LXVwOiAiXFxlYTBiIjsKICAgICAgLS1sdW1vLWljb25zLWJhci1jaGFydDogIlxcZWEwYyI7CiAgICAgIC0tbHVtby1pY29ucy1iZWxsOiAiXFxlYTBkIjsKICAgICAgLS1sdW1vLWljb25zLWNhbGVuZGFyOiAiXFxlYTBlIjsKICAgICAgLS1sdW1vLWljb25zLWNoZWNrbWFyazogIlxcZWEwZiI7CiAgICAgIC0tbHVtby1pY29ucy1jaGV2cm9uLWRvd246ICJcXGVhMTAiOwogICAgICAtLWx1bW8taWNvbnMtY2hldnJvbi1sZWZ0OiAiXFxlYTExIjsKICAgICAgLS1sdW1vLWljb25zLWNoZXZyb24tcmlnaHQ6ICJcXGVhMTIiOwogICAgICAtLWx1bW8taWNvbnMtY2hldnJvbi11cDogIlxcZWExMyI7CiAgICAgIC0tbHVtby1pY29ucy1jbG9jazogIlxcZWExNCI7CiAgICAgIC0tbHVtby1pY29ucy1jb2c6ICJcXGVhMTUiOwogICAgICAtLWx1bW8taWNvbnMtY3Jvc3M6ICJcXGVhMTYiOwogICAgICAtLWx1bW8taWNvbnMtZG93bmxvYWQ6ICJcXGVhMTciOwogICAgICAtLWx1bW8taWNvbnMtZHJvcGRvd246ICJcXGVhMTgiOwogICAgICAtLWx1bW8taWNvbnMtZWRpdDogIlxcZWExOSI7CiAgICAgIC0tbHVtby1pY29ucy1lcnJvcjogIlxcZWExYSI7CiAgICAgIC0tbHVtby1pY29ucy1leWU6ICJcXGVhMWIiOwogICAgICAtLWx1bW8taWNvbnMtZXllLWRpc2FibGVkOiAiXFxlYTFjIjsKICAgICAgLS1sdW1vLWljb25zLW1lbnU6ICJcXGVhMWQiOwogICAgICAtLWx1bW8taWNvbnMtbWludXM6ICJcXGVhMWUiOwogICAgICAtLWx1bW8taWNvbnMtb3JkZXJlZC1saXN0OiAiXFxlYTFmIjsKICAgICAgLS1sdW1vLWljb25zLXBob25lOiAiXFxlYTIwIjsKICAgICAgLS1sdW1vLWljb25zLXBob3RvOiAiXFxlYTIxIjsKICAgICAgLS1sdW1vLWljb25zLXBsYXk6ICJcXGVhMjIiOwogICAgICAtLWx1bW8taWNvbnMtcGx1czogIlxcZWEyMyI7CiAgICAgIC0tbHVtby1pY29ucy1yZWRvOiAiXFxlYTI0IjsKICAgICAgLS1sdW1vLWljb25zLXJlbG9hZDogIlxcZWEyNSI7CiAgICAgIC0tbHVtby1pY29ucy1zZWFyY2g6ICJcXGVhMjYiOwogICAgICAtLWx1bW8taWNvbnMtdW5kbzogIlxcZWEyNyI7CiAgICAgIC0tbHVtby1pY29ucy11bm9yZGVyZWQtbGlzdDogIlxcZWEyOCI7CiAgICAgIC0tbHVtby1pY29ucy11cGxvYWQ6ICJcXGVhMjkiOwogICAgICAtLWx1bW8taWNvbnMtdXNlcjogIlxcZWEyYSI7CiAgICB9CiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+YDsKCiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKCRfZG9jdW1lbnRDb250YWluZXIkNi5jb250ZW50KTsKCiAgICBjb25zdCAkX2RvY3VtZW50Q29udGFpbmVyJDcgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwoKICAgICRfZG9jdW1lbnRDb250YWluZXIkNy5pbm5lckhUTUwgPSBgPGN1c3RvbS1zdHlsZT4KICA8c3R5bGU+CiAgICBodG1sIHsKICAgICAgLS1sdW1vLXNpemUteHM6IDEuNjI1cmVtOwogICAgICAtLWx1bW8tc2l6ZS1zOiAxLjg3NXJlbTsKICAgICAgLS1sdW1vLXNpemUtbTogMi4yNXJlbTsKICAgICAgLS1sdW1vLXNpemUtbDogMi43NXJlbTsKICAgICAgLS1sdW1vLXNpemUteGw6IDMuNXJlbTsKCiAgICAgIC8qIEljb25zICovCiAgICAgIC0tbHVtby1pY29uLXNpemUtczogMS4yNWVtOwogICAgICAtLWx1bW8taWNvbi1zaXplLW06IDEuNWVtOwogICAgICAtLWx1bW8taWNvbi1zaXplLWw6IDIuMjVlbTsKICAgICAgLyogRm9yIGJhY2t3YXJkcyBjb21wYXRpYmlsaXR5ICovCiAgICAgIC0tbHVtby1pY29uLXNpemU6IHZhcigtLWx1bW8taWNvbi1zaXplLW0pOwogICAgfQogIDwvc3R5bGU+CjwvY3VzdG9tLXN0eWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJDcuY29udGVudCk7CgogICAgY29uc3QgJF9kb2N1bWVudENvbnRhaW5lciQ4ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTsKCiAgICAkX2RvY3VtZW50Q29udGFpbmVyJDguaW5uZXJIVE1MID0gYDxjdXN0b20tc3R5bGU+CiAgPHN0eWxlPgogICAgaHRtbCB7CiAgICAgIC8qIFNxdWFyZSAqLwogICAgICAtLWx1bW8tc3BhY2UteHM6IDAuMjVyZW07CiAgICAgIC0tbHVtby1zcGFjZS1zOiAwLjVyZW07CiAgICAgIC0tbHVtby1zcGFjZS1tOiAxcmVtOwogICAgICAtLWx1bW8tc3BhY2UtbDogMS41cmVtOwogICAgICAtLWx1bW8tc3BhY2UteGw6IDIuNXJlbTsKCiAgICAgIC8qIFdpZGUgKi8KICAgICAgLS1sdW1vLXNwYWNlLXdpZGUteHM6IGNhbGModmFyKC0tbHVtby1zcGFjZS14cykgLyAyKSB2YXIoLS1sdW1vLXNwYWNlLXhzKTsKICAgICAgLS1sdW1vLXNwYWNlLXdpZGUtczogY2FsYyh2YXIoLS1sdW1vLXNwYWNlLXMpIC8gMikgdmFyKC0tbHVtby1zcGFjZS1zKTsKICAgICAgLS1sdW1vLXNwYWNlLXdpZGUtbTogY2FsYyh2YXIoLS1sdW1vLXNwYWNlLW0pIC8gMikgdmFyKC0tbHVtby1zcGFjZS1tKTsKICAgICAgLS1sdW1vLXNwYWNlLXdpZGUtbDogY2FsYyh2YXIoLS1sdW1vLXNwYWNlLWwpIC8gMikgdmFyKC0tbHVtby1zcGFjZS1sKTsKICAgICAgLS1sdW1vLXNwYWNlLXdpZGUteGw6IGNhbGModmFyKC0tbHVtby1zcGFjZS14bCkgLyAyKSB2YXIoLS1sdW1vLXNwYWNlLXhsKTsKCiAgICAgIC8qIFRhbGwgKi8KICAgICAgLS1sdW1vLXNwYWNlLXRhbGwteHM6IHZhcigtLWx1bW8tc3BhY2UteHMpIGNhbGModmFyKC0tbHVtby1zcGFjZS14cykgLyAyKTsKICAgICAgLS1sdW1vLXNwYWNlLXRhbGwtczogdmFyKC0tbHVtby1zcGFjZS1zKSBjYWxjKHZhcigtLWx1bW8tc3BhY2UtcykgLyAyKTsKICAgICAgLS1sdW1vLXNwYWNlLXRhbGwtbTogdmFyKC0tbHVtby1zcGFjZS1tKSBjYWxjKHZhcigtLWx1bW8tc3BhY2UtbSkgLyAyKTsKICAgICAgLS1sdW1vLXNwYWNlLXRhbGwtbDogdmFyKC0tbHVtby1zcGFjZS1sKSBjYWxjKHZhcigtLWx1bW8tc3BhY2UtbCkgLyAyKTsKICAgICAgLS1sdW1vLXNwYWNlLXRhbGwteGw6IHZhcigtLWx1bW8tc3BhY2UteGwpIGNhbGModmFyKC0tbHVtby1zcGFjZS14bCkgLyAyKTsKICAgIH0KICA8L3N0eWxlPgo8L2N1c3RvbS1zdHlsZT5gOwoKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoJF9kb2N1bWVudENvbnRhaW5lciQ4LmNvbnRlbnQpOwoKICAgIGNvbnN0ICRfZG9jdW1lbnRDb250YWluZXIkOSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RlbXBsYXRlJyk7CgogICAgJF9kb2N1bWVudENvbnRhaW5lciQ5LmlubmVySFRNTCA9IGA8Y3VzdG9tLXN0eWxlPgogIDxzdHlsZT4KICAgIGh0bWwgewogICAgICAvKiBCb3JkZXIgcmFkaXVzICovCiAgICAgIC0tbHVtby1ib3JkZXItcmFkaXVzLXM6IDAuMjVlbTsgLyogQ2hlY2tib3gsIGJhZGdlLCBkYXRlLXBpY2tlciB5ZWFyIGluZGljYXRvciwgZXRjICovCiAgICAgIC0tbHVtby1ib3JkZXItcmFkaXVzLW06IHZhcigtLWx1bW8tYm9yZGVyLXJhZGl1cywgMC4yNWVtKTsgLyogQnV0dG9uLCB0ZXh0IGZpZWxkLCBtZW51IG92ZXJsYXksIGV0YyAqLwogICAgICAtLWx1bW8tYm9yZGVyLXJhZGl1cy1sOiAwLjVlbTsgLyogRGlhbG9nLCBub3RpZmljYXRpb24sIGV0YyAqLwogICAgICAtLWx1bW8tYm9yZGVyLXJhZGl1czogMC4yNWVtOyAvKiBEZXByZWNhdGVkICovCgogICAgICAvKiBTaGFkb3cgKi8KICAgICAgLS1sdW1vLWJveC1zaGFkb3cteHM6IDAgMXB4IDRweCAtMXB4IHZhcigtLWx1bW8tc2hhZGUtNTBwY3QpOwogICAgICAtLWx1bW8tYm94LXNoYWRvdy1zOiAwIDJweCA0cHggLTFweCB2YXIoLS1sdW1vLXNoYWRlLTIwcGN0KSwgMCAzcHggMTJweCAtMXB4IHZhcigtLWx1bW8tc2hhZGUtMzBwY3QpOwogICAgICAtLWx1bW8tYm94LXNoYWRvdy1tOiAwIDJweCA2cHggLTFweCB2YXIoLS1sdW1vLXNoYWRlLTIwcGN0KSwgMCA4cHggMjRweCAtNHB4IHZhcigtLWx1bW8tc2hhZGUtNDBwY3QpOwogICAgICAtLWx1bW8tYm94LXNoYWRvdy1sOiAwIDNweCAxOHB4IC0ycHggdmFyKC0tbHVtby1zaGFkZS0yMHBjdCksIDAgMTJweCA0OHB4IC02cHggdmFyKC0tbHVtby1zaGFkZS00MHBjdCk7CiAgICAgIC0tbHVtby1ib3gtc2hhZG93LXhsOiAwIDRweCAyNHB4IC0zcHggdmFyKC0tbHVtby1zaGFkZS0yMHBjdCksIDAgMThweCA2NHB4IC04cHggdmFyKC0tbHVtby1zaGFkZS00MHBjdCk7CgogICAgICAvKiBDbGlja2FibGUgZWxlbWVudCBjdXJzb3IgKi8KICAgICAgLS1sdW1vLWNsaWNrYWJsZS1jdXJzb3I6IGRlZmF1bHQ7CiAgICB9CiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+YDsKCiAgICBkb2N1bWVudC5oZWFkLmFwcGVuZENoaWxkKCRfZG9jdW1lbnRDb250YWluZXIkOS5jb250ZW50KTsKCiAgICBjb25zdCAkX2RvY3VtZW50Q29udGFpbmVyJGEgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpOwoKICAgICRfZG9jdW1lbnRDb250YWluZXIkYS5pbm5lckhUTUwgPSBgPGN1c3RvbS1zdHlsZT4KICA8c3R5bGU+CiAgICBodG1sIHsKICAgICAgLyogRm9udCBmYW1pbGllcyAqLwogICAgICAtLWx1bW8tZm9udC1mYW1pbHk6IC1hcHBsZS1zeXN0ZW0sIEJsaW5rTWFjU3lzdGVtRm9udCwgIlJvYm90byIsICJTZWdvZSBVSSIsIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWYsICJBcHBsZSBDb2xvciBFbW9qaSIsICJTZWdvZSBVSSBFbW9qaSIsICJTZWdvZSBVSSBTeW1ib2wiOwoKICAgICAgLyogRm9udCBzaXplcyAqLwogICAgICAtLWx1bW8tZm9udC1zaXplLXh4czogLjc1cmVtOwogICAgICAtLWx1bW8tZm9udC1zaXplLXhzOiAuODEyNXJlbTsKICAgICAgLS1sdW1vLWZvbnQtc2l6ZS1zOiAuODc1cmVtOwogICAgICAtLWx1bW8tZm9udC1zaXplLW06IDFyZW07CiAgICAgIC0tbHVtby1mb250LXNpemUtbDogMS4xMjVyZW07CiAgICAgIC0tbHVtby1mb250LXNpemUteGw6IDEuMzc1cmVtOwogICAgICAtLWx1bW8tZm9udC1zaXplLXh4bDogMS43NXJlbTsKICAgICAgLS1sdW1vLWZvbnQtc2l6ZS14eHhsOiAyLjVyZW07CgogICAgICAvKiBMaW5lIGhlaWdodHMgKi8KICAgICAgLS1sdW1vLWxpbmUtaGVpZ2h0LXhzOiAxLjI1OwogICAgICAtLWx1bW8tbGluZS1oZWlnaHQtczogMS4zNzU7CiAgICAgIC0tbHVtby1saW5lLWhlaWdodC1tOiAxLjYyNTsKICAgIH0KCiAgPC9zdHlsZT4KPC9jdXN0b20tc3R5bGU+PGRvbS1tb2R1bGUgaWQ9Imx1bW8tdHlwb2dyYXBoeSI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICBodG1sIHsKICAgICAgICBmb250LWZhbWlseTogdmFyKC0tbHVtby1mb250LWZhbWlseSk7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZSwgdmFyKC0tbHVtby1mb250LXNpemUtbSkpOwogICAgICAgIGxpbmUtaGVpZ2h0OiB2YXIoLS1sdW1vLWxpbmUtaGVpZ2h0LW0pOwogICAgICAgIC13ZWJraXQtdGV4dC1zaXplLWFkanVzdDogMTAwJTsKICAgICAgICAtd2Via2l0LWZvbnQtc21vb3RoaW5nOiBhbnRpYWxpYXNlZDsKICAgICAgICAtbW96LW9zeC1mb250LXNtb290aGluZzogZ3JheXNjYWxlOwogICAgICB9CgogICAgICAvKiBDYW7igJl0IGNvbWJpbmUgd2l0aCB0aGUgYWJvdmUgc2VsZWN0b3IgYmVjYXVzZSB0aGF0IGRvZXNu4oCZdCB3b3JrIGluIGJyb3dzZXJzIHdpdGhvdXQgbmF0aXZlIHNoYWRvdyBkb20gKi8KICAgICAgOmhvc3QgewogICAgICAgIGZvbnQtZmFtaWx5OiB2YXIoLS1sdW1vLWZvbnQtZmFtaWx5KTsKICAgICAgICBmb250LXNpemU6IHZhcigtLWx1bW8tZm9udC1zaXplLCB2YXIoLS1sdW1vLWZvbnQtc2l6ZS1tKSk7CiAgICAgICAgbGluZS1oZWlnaHQ6IHZhcigtLWx1bW8tbGluZS1oZWlnaHQtbSk7CiAgICAgICAgLXdlYmtpdC10ZXh0LXNpemUtYWRqdXN0OiAxMDAlOwogICAgICAgIC13ZWJraXQtZm9udC1zbW9vdGhpbmc6IGFudGlhbGlhc2VkOwogICAgICAgIC1tb3otb3N4LWZvbnQtc21vb3RoaW5nOiBncmF5c2NhbGU7CiAgICAgIH0KCiAgICAgIHNtYWxsLAogICAgICBbdGhlbWV+PSJmb250LXNpemUtcyJdIHsKICAgICAgICBmb250LXNpemU6IHZhcigtLWx1bW8tZm9udC1zaXplLXMpOwogICAgICAgIGxpbmUtaGVpZ2h0OiB2YXIoLS1sdW1vLWxpbmUtaGVpZ2h0LXMpOwogICAgICB9CgogICAgICBbdGhlbWV+PSJmb250LXNpemUteHMiXSB7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZS14cyk7CiAgICAgICAgbGluZS1oZWlnaHQ6IHZhcigtLWx1bW8tbGluZS1oZWlnaHQteHMpOwogICAgICB9CgogICAgICBoMSwKICAgICAgaDIsCiAgICAgIGgzLAogICAgICBoNCwKICAgICAgaDUsCiAgICAgIGg2IHsKICAgICAgICBmb250LXdlaWdodDogNjAwOwogICAgICAgIGxpbmUtaGVpZ2h0OiB2YXIoLS1sdW1vLWxpbmUtaGVpZ2h0LXhzKTsKICAgICAgICBtYXJnaW4tdG9wOiAxLjI1ZW07CiAgICAgIH0KCiAgICAgIGgxIHsKICAgICAgICBmb250LXNpemU6IHZhcigtLWx1bW8tZm9udC1zaXplLXh4eGwpOwogICAgICAgIG1hcmdpbi1ib3R0b206IDAuNzVlbTsKICAgICAgfQoKICAgICAgaDIgewogICAgICAgIGZvbnQtc2l6ZTogdmFyKC0tbHVtby1mb250LXNpemUteHhsKTsKICAgICAgICBtYXJnaW4tYm90dG9tOiAwLjVlbTsKICAgICAgfQoKICAgICAgaDMgewogICAgICAgIGZvbnQtc2l6ZTogdmFyKC0tbHVtby1mb250LXNpemUteGwpOwogICAgICAgIG1hcmdpbi1ib3R0b206IDAuNWVtOwogICAgICB9CgogICAgICBoNCB7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZS1sKTsKICAgICAgICBtYXJnaW4tYm90dG9tOiAwLjVlbTsKICAgICAgfQoKICAgICAgaDUgewogICAgICAgIGZvbnQtc2l6ZTogdmFyKC0tbHVtby1mb250LXNpemUtbSk7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMC4yNWVtOwogICAgICB9CgogICAgICBoNiB7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZS14cyk7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogMDsKICAgICAgICB0ZXh0LXRyYW5zZm9ybTogdXBwZXJjYXNlOwogICAgICAgIGxldHRlci1zcGFjaW5nOiAwLjAzZW07CiAgICAgIH0KCiAgICAgIHAsCiAgICAgIGJsb2NrcXVvdGUgewogICAgICAgIG1hcmdpbi10b3A6IDAuNWVtOwogICAgICAgIG1hcmdpbi1ib3R0b206IDAuNzVlbTsKICAgICAgfQoKICAgICAgYSB7CiAgICAgICAgdGV4dC1kZWNvcmF0aW9uOiBub25lOwogICAgICB9CgogICAgICBhOmhvdmVyIHsKICAgICAgICB0ZXh0LWRlY29yYXRpb246IHVuZGVybGluZTsKICAgICAgfQoKICAgICAgaHIgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIGFsaWduLXNlbGY6IHN0cmV0Y2g7CiAgICAgICAgaGVpZ2h0OiAxcHg7CiAgICAgICAgYm9yZGVyOiAwOwogICAgICAgIHBhZGRpbmc6IDA7CiAgICAgICAgbWFyZ2luOiB2YXIoLS1sdW1vLXNwYWNlLXMpIGNhbGModmFyKC0tbHVtby1ib3JkZXItcmFkaXVzLW0pIC8gMik7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0xMHBjdCk7CiAgICAgIH0KCiAgICAgIGJsb2NrcXVvdGUgewogICAgICAgIGJvcmRlci1sZWZ0OiAycHggc29saWQgdmFyKC0tbHVtby1jb250cmFzdC0zMHBjdCk7CiAgICAgIH0KCiAgICAgIGIsCiAgICAgIHN0cm9uZyB7CiAgICAgICAgZm9udC13ZWlnaHQ6IDYwMDsKICAgICAgfQoKICAgICAgLyogUlRMIHNwZWNpZmljIHN0eWxlcyAqLwoKICAgICAgYmxvY2txdW90ZVtkaXI9InJ0bCJdIHsKICAgICAgICBib3JkZXItbGVmdDogbm9uZTsKICAgICAgICBib3JkZXItcmlnaHQ6IDJweCBzb2xpZCB2YXIoLS1sdW1vLWNvbnRyYXN0LTMwcGN0KTsKICAgICAgfQoKICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJGEuY29udGVudCk7CgogICAgY29uc3QgJF9kb2N1bWVudENvbnRhaW5lciRiID0gaHRtbGA8ZG9tLW1vZHVsZSBpZD0ibHVtby1jaGVja2JveCIgdGhlbWUtZm9yPSJ2YWFkaW4tY2hlY2tib3giPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZSBpbmNsdWRlPSJsdW1vLWNoZWNrYm94LXN0eWxlIGx1bW8tY2hlY2tib3gtZWZmZWN0cyI+CiAgICAgIC8qIElFMTEgb25seSAqLwogICAgICA6Oi1tcy1iYWNrZHJvcCwKICAgICAgW3BhcnQ9ImNoZWNrYm94Il0gewogICAgICAgIGxpbmUtaGVpZ2h0OiAxOwogICAgICB9CiAgICA8L3N0eWxlPgogIDwvdGVtcGxhdGU+CjwvZG9tLW1vZHVsZT48ZG9tLW1vZHVsZSBpZD0ibHVtby1jaGVja2JveC1zdHlsZSI+CiAgPHRlbXBsYXRlPgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKICAgICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogICAgICAgIC1tb3otdXNlci1zZWxlY3Q6IG5vbmU7CiAgICAgICAgLW1zLXVzZXItc2VsZWN0OiBub25lOwogICAgICAgIHVzZXItc2VsZWN0OiBub25lOwogICAgICAgIGN1cnNvcjogZGVmYXVsdDsKICAgICAgICBvdXRsaW5lOiBub25lOwogICAgICB9CgogICAgICBbcGFydD0ibGFiZWwiXTpub3QoW2VtcHR5XSkgewogICAgICAgIG1hcmdpbjogMC4xODc1ZW0gMC44NzVlbSAwLjE4NzVlbSAwLjM3NWVtOwogICAgICB9CgogICAgICBbcGFydD0iY2hlY2tib3giXSB7CiAgICAgICAgd2lkdGg6IGNhbGMoMWVtICsgMnB4KTsKICAgICAgICBoZWlnaHQ6IGNhbGMoMWVtICsgMnB4KTsKICAgICAgICBtYXJnaW46IDAuMTg3NWVtOwogICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgICBib3JkZXItcmFkaXVzOiB2YXIoLS1sdW1vLWJvcmRlci1yYWRpdXMtcyk7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0yMHBjdCk7CiAgICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtIDAuMnMgY3ViaWMtYmV6aWVyKC4xMiwgLjMyLCAuNTQsIDIpLCBiYWNrZ3JvdW5kLWNvbG9yIDAuMTVzOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGxpbmUtaGVpZ2h0OiAxLjI7CiAgICAgIH0KCiAgICAgIDpob3N0KFtpbmRldGVybWluYXRlXSkgW3BhcnQ9ImNoZWNrYm94Il0sCiAgICAgIDpob3N0KFtjaGVja2VkXSkgW3BhcnQ9ImNoZWNrYm94Il0gewogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWx1bW8tcHJpbWFyeS1jb2xvcik7CiAgICAgIH0KCiAgICAgIC8qIE5lZWRlZCB0byBhbGlnbiB0aGUgY2hlY2tib3ggbmljZWx5IG9uIHRoZSBiYXNlbGluZSAqLwogICAgICBbcGFydD0iY2hlY2tib3giXTo6YmVmb3JlIHsKICAgICAgICBjb250ZW50OiAiXFwyMDAzIjsKICAgICAgfQoKICAgICAgLyogQ2hlY2ttYXJrICovCiAgICAgIFtwYXJ0PSJjaGVja2JveCJdOjphZnRlciB7CiAgICAgICAgY29udGVudDogIiI7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIHdpZHRoOiAwOwogICAgICAgIGhlaWdodDogMDsKICAgICAgICBib3JkZXI6IDAgc29saWQgdmFyKC0tbHVtby1wcmltYXJ5LWNvbnRyYXN0LWNvbG9yKTsKICAgICAgICBib3JkZXItd2lkdGg6IDAuMTg3NWVtIDAgMCAwLjE4NzVlbTsKICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgIHRyYW5zZm9ybS1vcmlnaW46IDAgMDsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAwLjgxMjVlbTsKICAgICAgICBsZWZ0OiAwLjVlbTsKICAgICAgICB0cmFuc2Zvcm06IHNjYWxlKDAuNTUpIHJvdGF0ZSgtMTM1ZGVnKTsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICB9CgogICAgICA6aG9zdChbY2hlY2tlZF0pIFtwYXJ0PSJjaGVja2JveCJdOjphZnRlciB7CiAgICAgICAgb3BhY2l0eTogMTsKICAgICAgICB3aWR0aDogMC42MjVlbTsKICAgICAgICBoZWlnaHQ6IDEuMDYyNWVtOwogICAgICB9CgogICAgICAvKiBJbmRldGVybWluYXRlIGNoZWNrbWFyayAqLwoKICAgICAgOmhvc3QoW2luZGV0ZXJtaW5hdGVdKSBbcGFydD0iY2hlY2tib3giXTo6YWZ0ZXIgewogICAgICAgIHRyYW5zZm9ybTogbm9uZTsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICAgIHRvcDogNDUlOwogICAgICAgIGhlaWdodDogMTAlOwogICAgICAgIGxlZnQ6IDIyJTsKICAgICAgICByaWdodDogMjIlOwogICAgICAgIHdpZHRoOiBhdXRvOwogICAgICAgIGJvcmRlcjogMDsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1sdW1vLXByaW1hcnktY29udHJhc3QtY29sb3IpOwogICAgICAgIHRyYW5zaXRpb246IG9wYWNpdHkgMC4yNXM7CiAgICAgIH0KCiAgICAgIC8qIEZvY3VzIHJpbmcgKi8KCiAgICAgIDpob3N0KFtmb2N1cy1yaW5nXSkgW3BhcnQ9ImNoZWNrYm94Il0gewogICAgICAgIGJveC1zaGFkb3c6IDAgMCAwIDNweCB2YXIoLS1sdW1vLXByaW1hcnktY29sb3ItNTBwY3QpOwogICAgICB9CgogICAgICAvKiBEaXNhYmxlZCAqLwoKICAgICAgOmhvc3QoW2Rpc2FibGVkXSkgewogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGNvbG9yOiB2YXIoLS1sdW1vLWRpc2FibGVkLXRleHQtY29sb3IpOwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSBbcGFydD0ibGFiZWwiXSA6OnNsb3R0ZWQoKikgewogICAgICAgIGNvbG9yOiBpbmhlcml0OwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSBbcGFydD0iY2hlY2tib3giXSB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0xMHBjdCk7CiAgICAgIH0KCiAgICAgIDpob3N0KFtkaXNhYmxlZF0pIFtwYXJ0PSJjaGVja2JveCJdOjphZnRlciB7CiAgICAgICAgYm9yZGVyLWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTMwcGN0KTsKICAgICAgfQoKICAgICAgOmhvc3QoW2luZGV0ZXJtaW5hdGVdW2Rpc2FibGVkXSkgW3BhcnQ9ImNoZWNrYm94Il06OmFmdGVyIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTMwcGN0KTsKICAgICAgfQoKICAgICAgLyogUlRMIHNwZWNpZmljIHN0eWxlcyAqLwoKICAgICAgOmhvc3QoW2Rpcj0icnRsIl0pIFtwYXJ0PSJsYWJlbCJdOm5vdChbZW1wdHldKSB7CiAgICAgICAgbWFyZ2luOiAwLjE4NzVlbSAwLjM3NWVtIDAuMTg3NWVtIDAuODc1ZW07CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPjxkb20tbW9kdWxlIGlkPSJsdW1vLWNoZWNrYm94LWVmZmVjdHMiPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgLyogVHJhbnNpdGlvbiB0aGUgY2hlY2ttYXJrIGlmIGFjdGl2YXRlZCB3aXRoIHRoZSBtb3VzZSAoZGlzYWJsZWQgZm9yIGdyaWQgc2VsZWN0LWFsbCB0aGlzIHdheSkgKi8KICAgICAgOmhvc3QoOmhvdmVyKSBbcGFydD0iY2hlY2tib3giXTo6YWZ0ZXIgewogICAgICAgIHRyYW5zaXRpb246IHdpZHRoIDAuMXMsIGhlaWdodCAwLjI1czsKICAgICAgfQoKICAgICAgLyogVXNlZCBmb3IgYWN0aXZhdGlvbiAiaGFsbyIgKi8KICAgICAgW3BhcnQ9ImNoZWNrYm94Il06OmJlZm9yZSB7CiAgICAgICAgY29sb3I6IHRyYW5zcGFyZW50OwogICAgICAgIGRpc3BsYXk6IGlubGluZS1ibG9jazsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgYm9yZGVyLXJhZGl1czogaW5oZXJpdDsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiBpbmhlcml0OwogICAgICAgIHRyYW5zZm9ybTogc2NhbGUoMS40KTsKICAgICAgICBvcGFjaXR5OiAwOwogICAgICAgIHRyYW5zaXRpb246IHRyYW5zZm9ybSAwLjFzLCBvcGFjaXR5IDAuOHM7CiAgICAgIH0KCiAgICAgIC8qIEhvdmVyICovCgogICAgICA6aG9zdCg6bm90KFtjaGVja2VkXSk6bm90KFtpbmRldGVybWluYXRlXSk6bm90KFtkaXNhYmxlZF0pOmhvdmVyKSBbcGFydD0iY2hlY2tib3giXSB7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0zMHBjdCk7CiAgICAgIH0KCiAgICAgIC8qIERpc2FibGUgaG92ZXIgZm9yIHRvdWNoIGRldmljZXMgKi8KICAgICAgQG1lZGlhIChwb2ludGVyOiBjb2Fyc2UpIHsKICAgICAgICA6aG9zdCg6bm90KFtjaGVja2VkXSk6bm90KFtpbmRldGVybWluYXRlXSk6bm90KFtkaXNhYmxlZF0pOmhvdmVyKSBbcGFydD0iY2hlY2tib3giXSB7CiAgICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTIwcGN0KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qIEFjdGl2ZSAqLwoKICAgICAgOmhvc3QoW2FjdGl2ZV0pIFtwYXJ0PSJjaGVja2JveCJdIHsKICAgICAgICB0cmFuc2Zvcm06IHNjYWxlKDAuOSk7CiAgICAgICAgdHJhbnNpdGlvbi1kdXJhdGlvbjogMC4wNXM7CiAgICAgIH0KCiAgICAgIDpob3N0KFthY3RpdmVdW2NoZWNrZWRdKSBbcGFydD0iY2hlY2tib3giXSB7CiAgICAgICAgdHJhbnNmb3JtOiBzY2FsZSgxLjEpOwogICAgICB9CgogICAgICA6aG9zdChbYWN0aXZlXTpub3QoW2NoZWNrZWRdKSkgW3BhcnQ9ImNoZWNrYm94Il06OmJlZm9yZSB7CiAgICAgICAgdHJhbnNpdGlvbi1kdXJhdGlvbjogMC4wMXMsIDAuMDFzOwogICAgICAgIHRyYW5zZm9ybTogc2NhbGUoMCk7CiAgICAgICAgb3BhY2l0eTogMC40OwogICAgICB9CiAgICA8L3N0eWxlPgogIDwvdGVtcGxhdGU+CjwvZG9tLW1vZHVsZT5gOwoKICAgIGRvY3VtZW50LmhlYWQuYXBwZW5kQ2hpbGQoJF9kb2N1bWVudENvbnRhaW5lciRiLmNvbnRlbnQpOwoKICAgIC8qKgogICAgICogQHBvbHltZXJNaXhpbgogICAgICovCiAgICBjb25zdCBUaGVtZVByb3BlcnR5TWl4aW4gPSBzdXBlckNsYXNzID0+IGNsYXNzIFZhYWRpblRoZW1lUHJvcGVydHlNaXhpbiBleHRlbmRzIHN1cGVyQ2xhc3MgewogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogSGVscGVyIHByb3BlcnR5IHdpdGggdGhlbWUgYXR0cmlidXRlIHZhbHVlIGZhY2lsaXRhdGluZyBwcm9wYWdhdGlvbgogICAgICAgICAgICogaW4gc2hhZG93IERPTS4KICAgICAgICAgICAqCiAgICAgICAgICAgKiBFbmFibGVzIHRoZSBjb21wb25lbnQgaW1wbGVtZW50YXRpb24gdG8gcHJvcGFnYXRlIHRoZSBgdGhlbWVgCiAgICAgICAgICAgKiBhdHRyaWJ1dGUgdmFsdWUgdG8gdGhlIHN1YmNvbXBvbmVudHMgaW4gU2hhZG93IERPTSBieSBiaW5kaW5nCiAgICAgICAgICAgKiB0aGUgc3ViY29tcG9uZW504oCZcyAidGhlbWUiIGF0dHJpYnV0ZSB0byB0aGUgYHRoZW1lYCBwcm9wZXJ0eSBvZgogICAgICAgICAgICogdGhlIGhvc3QuCiAgICAgICAgICAgKgogICAgICAgICAgICogKipOT1RFOioqIEV4dGVuZGluZyB0aGUgbWl4aW4gb25seSBwcm92aWRlcyB0aGUgcHJvcGVydHkgZm9yIGJpbmRpbmcsCiAgICAgICAgICAgKiBhbmQgZG9lcyBub3QgbWFrZSB0aGUgcHJvcGFnYXRpb24gYWxvbmUuCiAgICAgICAgICAgKgogICAgICAgICAgICogU2VlIFtUaGVtZSBBdHRyaWJ1dGUgYW5kIFN1YmNvbXBvbmVudHNdKGh0dHBzOi8vZ2l0aHViLmNvbS92YWFkaW4vdmFhZGluLXRoZW1hYmxlLW1peGluL3dpa2kvNS4tVGhlbWUtQXR0cmlidXRlLWFuZC1TdWJjb21wb25lbnRzKS4KICAgICAgICAgICAqIHBhZ2UgZm9yIG1vcmUgaW5mb3JtYXRpb24uCiAgICAgICAgICAgKgogICAgICAgICAgICogQHByb3RlY3RlZAogICAgICAgICAgICovCiAgICAgICAgICB0aGVtZTogewogICAgICAgICAgICB0eXBlOiBTdHJpbmcsCiAgICAgICAgICAgIHJlYWRPbmx5OiB0cnVlCiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLyoqIEBwcm90ZWN0ZWQgKi8KICAgICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSkgewogICAgICAgIHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpOwoKICAgICAgICBpZiAobmFtZSA9PT0gJ3RoZW1lJykgewogICAgICAgICAgdGhpcy5fc2V0VGhlbWUobmV3VmFsdWUpOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqIEBtaXhlcyBUaGVtZVByb3BlcnR5TWl4aW4KICAgICAqLwogICAgY29uc3QgVGhlbWFibGVNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgVmFhZGluVGhlbWFibGVNaXhpbiBleHRlbmRzIFRoZW1lUHJvcGVydHlNaXhpbihzdXBlckNsYXNzKSB7CgogICAgICAvKiogQHByb3RlY3RlZCAqLwogICAgICBzdGF0aWMgZmluYWxpemUoKSB7CiAgICAgICAgc3VwZXIuZmluYWxpemUoKTsKCiAgICAgICAgY29uc3QgdGVtcGxhdGUgPSB0aGlzLnByb3RvdHlwZS5fdGVtcGxhdGU7CgogICAgICAgIGNvbnN0IGhhc093blRlbXBsYXRlID0gdGhpcy50ZW1wbGF0ZSAmJiB0aGlzLnRlbXBsYXRlLnBhcmVudEVsZW1lbnQgJiYgdGhpcy50ZW1wbGF0ZS5wYXJlbnRFbGVtZW50LmlkID09PSB0aGlzLmlzOwogICAgICAgIGNvbnN0IGluaGVyaXRlZFRlbXBsYXRlID0gT2JqZWN0LmdldFByb3RvdHlwZU9mKHRoaXMucHJvdG90eXBlKS5fdGVtcGxhdGU7CiAgICAgICAgaWYgKGluaGVyaXRlZFRlbXBsYXRlICYmICFoYXNPd25UZW1wbGF0ZSkgewogICAgICAgICAgLy8gVGhlIGVsZW1lbnQgZG9lc24ndCBkZWZpbmUgaXRzIG93biB0ZW1wbGF0ZSAtPiBpbmNsdWRlIHRoZSB0aGVtZSBtb2R1bGVzIGZyb20gdGhlIGluaGVyaXRlZCB0ZW1wbGF0ZQogICAgICAgICAgQXJyYXkuZnJvbShpbmhlcml0ZWRUZW1wbGF0ZS5jb250ZW50LnF1ZXJ5U2VsZWN0b3JBbGwoJ3N0eWxlW2luY2x1ZGVdJykpLmZvckVhY2gocyA9PiB7CiAgICAgICAgICAgIHRoaXMuX2luY2x1ZGVTdHlsZShzLmdldEF0dHJpYnV0ZSgnaW5jbHVkZScpLCB0ZW1wbGF0ZSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2luY2x1ZGVNYXRjaGluZ1RoZW1lcyh0ZW1wbGF0ZSk7CiAgICAgIH0KCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBzdGF0aWMgX2luY2x1ZGVNYXRjaGluZ1RoZW1lcyh0ZW1wbGF0ZSkgewogICAgICAgIGNvbnN0IGRvbU1vZHVsZSA9IERvbU1vZHVsZTsKICAgICAgICBjb25zdCBtb2R1bGVzID0gZG9tTW9kdWxlLnByb3RvdHlwZS5tb2R1bGVzOwoKICAgICAgICBsZXQgaGFzVGhlbWVzID0gZmFsc2U7CiAgICAgICAgY29uc3QgZGVmYXVsdE1vZHVsZU5hbWUgPSB0aGlzLmlzICsgJy1kZWZhdWx0LXRoZW1lJzsKCiAgICAgICAgT2JqZWN0LmtleXMobW9kdWxlcykKICAgICAgICAgIC5zb3J0KChtb2R1bGVOYW1lQSwgbW9kdWxlTmFtZUIpID0+IHsKICAgICAgICAgICAgY29uc3QgdmFhZGluQSA9IG1vZHVsZU5hbWVBLmluZGV4T2YoJ3ZhYWRpbi0nKSA9PT0gMDsKICAgICAgICAgICAgY29uc3QgdmFhZGluQiA9IG1vZHVsZU5hbWVCLmluZGV4T2YoJ3ZhYWRpbi0nKSA9PT0gMDsKCiAgICAgICAgICAgIGNvbnN0IHZhYWRpblRoZW1lUHJlZml4ZXMgPSBbJ2x1bW8tJywgJ21hdGVyaWFsLSddOwogICAgICAgICAgICBjb25zdCB2YWFkaW5UaGVtZUEgPSB2YWFkaW5UaGVtZVByZWZpeGVzLmZpbHRlcihwcmVmaXggPT4gbW9kdWxlTmFtZUEuaW5kZXhPZihwcmVmaXgpID09PSAwKS5sZW5ndGggPiAwOwogICAgICAgICAgICBjb25zdCB2YWFkaW5UaGVtZUIgPSB2YWFkaW5UaGVtZVByZWZpeGVzLmZpbHRlcihwcmVmaXggPT4gbW9kdWxlTmFtZUIuaW5kZXhPZihwcmVmaXgpID09PSAwKS5sZW5ndGggPiAwOwoKICAgICAgICAgICAgaWYgKHZhYWRpbkEgIT09IHZhYWRpbkIpIHsKICAgICAgICAgICAgICAvLyBJbmNsdWRlIHZhYWRpbiBjb3JlIHN0eWxlcyBmaXJzdAogICAgICAgICAgICAgIHJldHVybiB2YWFkaW5BID8gLTEgOiAxOwogICAgICAgICAgICB9IGVsc2UgaWYgKHZhYWRpblRoZW1lQSAhPT0gdmFhZGluVGhlbWVCKSB7CiAgICAgICAgICAgICAgLy8gSW5jbHVkZSB2YWFkaW4gdGhlbWUgc3R5bGVzIGFmdGVyIHRoYXQKICAgICAgICAgICAgICByZXR1cm4gdmFhZGluVGhlbWVBID8gLTEgOiAxOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIC8vIExhc3RseSBpbmNsdWRlIGN1c3RvbSBzdHlsZXMgc28gdGhleSBvdmVycmlkZSBhbGwgdmFhZGluIHN0eWxlcwogICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICB9CiAgICAgICAgICB9KQogICAgICAgICAgLmZvckVhY2gobW9kdWxlTmFtZSA9PiB7CiAgICAgICAgICAgIGlmIChtb2R1bGVOYW1lICE9PSBkZWZhdWx0TW9kdWxlTmFtZSkgewogICAgICAgICAgICAgIGNvbnN0IHRoZW1lRm9yID0gbW9kdWxlc1ttb2R1bGVOYW1lXS5nZXRBdHRyaWJ1dGUoJ3RoZW1lLWZvcicpOwogICAgICAgICAgICAgIGlmICh0aGVtZUZvcikgewogICAgICAgICAgICAgICAgdGhlbWVGb3Iuc3BsaXQoJyAnKS5mb3JFYWNoKHRoZW1lRm9yVG9rZW4gPT4gewogICAgICAgICAgICAgICAgICBpZiAobmV3IFJlZ0V4cCgnXicgKyB0aGVtZUZvclRva2VuLnNwbGl0KCcqJykuam9pbignLionKSArICckJykudGVzdCh0aGlzLmlzKSkgewogICAgICAgICAgICAgICAgICAgIGhhc1RoZW1lcyA9IHRydWU7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5faW5jbHVkZVN0eWxlKG1vZHVsZU5hbWUsIHRlbXBsYXRlKTsKICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKCiAgICAgICAgaWYgKCFoYXNUaGVtZXMgJiYgbW9kdWxlc1tkZWZhdWx0TW9kdWxlTmFtZV0pIHsKICAgICAgICAgIC8vIE5vIHRoZW1lIG1vZHVsZXMgZm91bmQsIGluY2x1ZGUgdGhlIGRlZmF1bHQgbW9kdWxlIGlmIGl0IGV4aXN0cwogICAgICAgICAgdGhpcy5faW5jbHVkZVN0eWxlKGRlZmF1bHRNb2R1bGVOYW1lLCB0ZW1wbGF0ZSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKiogQHByaXZhdGUgKi8KICAgICAgc3RhdGljIF9pbmNsdWRlU3R5bGUobW9kdWxlTmFtZSwgdGVtcGxhdGUpIHsKICAgICAgICBpZiAodGVtcGxhdGUgJiYgIXRlbXBsYXRlLmNvbnRlbnQucXVlcnlTZWxlY3Rvcihgc3R5bGVbaW5jbHVkZT0iJHttb2R1bGVOYW1lfSJdYCkpIHsKICAgICAgICAgIGNvbnN0IHN0eWxlRWwgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdzdHlsZScpOwogICAgICAgICAgc3R5bGVFbC5zZXRBdHRyaWJ1dGUoJ2luY2x1ZGUnLCBtb2R1bGVOYW1lKTsKICAgICAgICAgIHRlbXBsYXRlLmNvbnRlbnQuYXBwZW5kQ2hpbGQoc3R5bGVFbCk7CiAgICAgICAgfQogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIEEgcHJpdmF0ZSBtaXhpbiB0byBhdm9pZCBwcm9ibGVtcyB3aXRoIGR5bmFtaWMgcHJvcGVydGllcyBhbmQgUG9seW1lciBBbmFseXplci4KICAgICAqIE5vIG5lZWQgdG8gZXhwb3NlIHRoZXNlIHByb3BlcnRpZXMgaW4gdGhlIEFQSSBkb2NzLgogICAgICogQHBvbHltZXJNaXhpbgogICAgICogQHByaXZhdGUKICAgICAqLwogICAgY29uc3QgVGFiSW5kZXhNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgVmFhZGluVGFiSW5kZXhNaXhpbiBleHRlbmRzIHN1cGVyQ2xhc3MgewogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgdmFyIHByb3BlcnRpZXMgPSB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEludGVybmFsIHByb3BlcnR5IG5lZWRlZCB0byBsaXN0ZW4gdG8gYHRhYmluZGV4YCBhdHRyaWJ1dGUgY2hhbmdlcy4KICAgICAgICAgICAqCiAgICAgICAgICAgKiBGb3IgY2hhbmdpbmcgdGhlIHRhYmluZGV4IG9mIHRoaXMgY29tcG9uZW50IHVzZSB0aGUgbmF0aXZlIGB0YWJJbmRleGAgcHJvcGVydHkuCiAgICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAgICovCiAgICAgICAgICB0YWJpbmRleDogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIHZhbHVlOiAwLAogICAgICAgICAgICByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWUsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX3RhYmluZGV4Q2hhbmdlZCcKICAgICAgICAgIH0KICAgICAgICB9OwoKICAgICAgICBpZiAod2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgICAvLyBTaGFkeURPTSBicm93c2VycyBuZWVkIHRoZSBgdGFiSW5kZXhgIGluIG9yZGVyIHRvIG5vdGlmeSB3aGVuIHRoZSB1c2VyIGNoYW5nZXMgaXQgcHJvZ3JhbW1hdGljYWxseS4KICAgICAgICAgIHByb3BlcnRpZXNbJ3RhYkluZGV4J10gPSBwcm9wZXJ0aWVzLnRhYmluZGV4OwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHByb3BlcnRpZXM7CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICAgKiBQb2x5bWVyLklyb25Db250cm9sU3RhdGUgaXMgbm90IGEgcHJvcGVyIDIuMCBjbGFzcywgYWxzbywgaXRzIHRhYmluZGV4CiAgICAgKiBpbXBsZW1lbnRhdGlvbiBmYWlscyBpbiB0aGUgc2hhZG93IGRvbSwgc28gd2UgaGF2ZSB0aGlzIGZvciB2YWFkaW4gZWxlbWVudHMuCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IENvbnRyb2xTdGF0ZU1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBWYWFkaW5Db250cm9sU3RhdGVNaXhpbiBleHRlbmRzIFRhYkluZGV4TWl4aW4oc3VwZXJDbGFzcykgewogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogU3BlY2lmeSB0aGF0IHRoaXMgY29udHJvbCBzaG91bGQgaGF2ZSBpbnB1dCBmb2N1cyB3aGVuIHRoZSBwYWdlIGxvYWRzLgogICAgICAgICAgICovCiAgICAgICAgICBhdXRvZm9jdXM6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbgogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFN0b3JlcyB0aGUgcHJldmlvdXMgdmFsdWUgb2YgdGFiaW5kZXggYXR0cmlidXRlIG9mIHRoZSBkaXNhYmxlZCBlbGVtZW50CiAgICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAgICovCiAgICAgICAgICBfcHJldmlvdXNUYWJJbmRleDogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBJZiB0cnVlLCB0aGUgdXNlciBjYW5ub3QgaW50ZXJhY3Qgd2l0aCB0aGlzIGVsZW1lbnQuCiAgICAgICAgICAgKi8KICAgICAgICAgIGRpc2FibGVkOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG9ic2VydmVyOiAnX2Rpc2FibGVkQ2hhbmdlZCcsCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZQogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEBwcml2YXRlCiAgICAgICAgICAgKi8KICAgICAgICAgIF9pc1NoaWZ0VGFiYmluZzogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuCiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIHJlYWR5KCkgewogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignZm9jdXNpbicsIGUgPT4gewogICAgICAgICAgaWYgKGUuY29tcG9zZWRQYXRoKClbMF0gPT09IHRoaXMpIHsKICAgICAgICAgICAgLy8gT25seSBmb2N1cyBpZiB0aGUgZm9jdXMgaXMgcmVjZWl2ZWQgZnJvbSBzb21ld2hlcmUgb3V0c2lkZQogICAgICAgICAgICBpZiAoIXRoaXMuY29udGFpbnMoZS5yZWxhdGVkVGFyZ2V0KSkgewogICAgICAgICAgICAgIHRoaXMuX2ZvY3VzKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAoZS5jb21wb3NlZFBhdGgoKS5pbmRleE9mKHRoaXMuZm9jdXNFbGVtZW50KSAhPT0gLTEgJiYgIXRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgICAgdGhpcy5fc2V0Rm9jdXNlZCh0cnVlKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3Vzb3V0JywgZSA9PiB0aGlzLl9zZXRGb2N1c2VkKGZhbHNlKSk7CgogICAgICAgIC8vIEluIHN1cGVyLnJlYWR5KCkgb3RoZXIgJ2ZvY3VzaW4nIGFuZCAnZm9jdXNvdXQnIGxpc3RlbmVycyBtaWdodCBiZQogICAgICAgIC8vIGFkZGVkLCBzbyB3ZSBjYWxsIGl0IGFmdGVyIG91ciBvd24gb25lcyB0byBlbnN1cmUgdGhleSBleGVjdXRlIGZpcnN0LgogICAgICAgIC8vIElzc3VlIHRvIHdhdGNoIG91dDogd2hlbiBpbmNvcnJlY3QsIDx2YWFkaW4tY29tYm8tYm94PiByZWZvY3VzZXMgdGhlCiAgICAgICAgLy8gaW5wdXQgZmllbGQgb24gaU9TIGFmdGVyIOKAnERvbmXigJ0gaXMgcHJlc3NlZC4KICAgICAgICBzdXBlci5yZWFkeSgpOwoKICAgICAgICAvLyBUaGlzIGZpeGVzIHRoZSBidWcgaW4gRmlyZWZveCA2MSAoaHR0cHM6Ly9idWd6aWxsYS5tb3ppbGxhLm9yZy9zaG93X2J1Zy5jZ2k/aWQ9MTQ3Mjg4NykKICAgICAgICAvLyB3aGVyZSBmb2N1c291dCBldmVudCBkb2VzIG5vdCBnbyBvdXQgb2Ygc2hhZHkgRE9NIGJlY2F1c2UgY29tcG9zZWQgcHJvcGVydHkgaW4gdGhlIGV2ZW50IGlzIG5vdCB0cnVlCiAgICAgICAgY29uc3QgZW5zdXJlRXZlbnRDb21wb3NlZCA9IGUgPT4gewogICAgICAgICAgaWYgKCFlLmNvbXBvc2VkKSB7CiAgICAgICAgICAgIGUudGFyZ2V0LmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KGUudHlwZSwgewogICAgICAgICAgICAgIGJ1YmJsZXM6IHRydWUsCiAgICAgICAgICAgICAgY29tcG9zZWQ6IHRydWUsCiAgICAgICAgICAgICAgY2FuY2VsYWJsZTogZmFsc2UKICAgICAgICAgICAgfSkpOwogICAgICAgICAgfQogICAgICAgIH07CiAgICAgICAgdGhpcy5zaGFkb3dSb290LmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3VzaW4nLCBlbnN1cmVFdmVudENvbXBvc2VkKTsKICAgICAgICB0aGlzLnNoYWRvd1Jvb3QuYWRkRXZlbnRMaXN0ZW5lcignZm9jdXNvdXQnLCBlbnN1cmVFdmVudENvbXBvc2VkKTsKCiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdrZXlkb3duJywgZSA9PiB7CiAgICAgICAgICBpZiAoIWUuZGVmYXVsdFByZXZlbnRlZCAmJiBlLmtleUNvZGUgPT09IDkpIHsKICAgICAgICAgICAgaWYgKGUuc2hpZnRLZXkpIHsKICAgICAgICAgICAgICAvLyBGbGFnIGlzIGNoZWNrZWQgaW4gX2ZvY3VzIGV2ZW50IGhhbmRsZXIuCiAgICAgICAgICAgICAgdGhpcy5faXNTaGlmdFRhYmJpbmcgPSB0cnVlOwogICAgICAgICAgICAgIEhUTUxFbGVtZW50LnByb3RvdHlwZS5mb2N1cy5hcHBseSh0aGlzKTsKICAgICAgICAgICAgICB0aGlzLl9zZXRGb2N1c2VkKGZhbHNlKTsKICAgICAgICAgICAgICAvLyBFdmVudCBoYW5kbGluZyBpbiBJRSBpcyBhc3luY2hyb25vdXMgYW5kIHRoZSBmbGFnIGlzIHJlbW92ZWQgYXN5bmNocm9ub3VzbHkgYXMgd2VsbAogICAgICAgICAgICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy5faXNTaGlmdFRhYmJpbmcgPSBmYWxzZSwgMCk7CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgLy8gV29ya2Fyb3VuZCBmb3IgRkY2My02NSBidWcgdGhhdCBjYXVzZXMgdGhlIGZvY3VzIHRvIGdldCBsb3N0IHdoZW4KICAgICAgICAgICAgICAvLyBibHVycmluZyBhIHNsb3R0ZWQgY29tcG9uZW50IHdpdGggZm9jdXNhYmxlIHNoYWRvdyByb290IGNvbnRlbnQKICAgICAgICAgICAgICAvLyBodHRwczovL2J1Z3ppbGxhLm1vemlsbGEub3JnL3Nob3dfYnVnLmNnaT9pZD0xNTI4Njg2CiAgICAgICAgICAgICAgLy8gVE9ETzogUmVtb3ZlIHdoZW4gc2FmZQogICAgICAgICAgICAgIGNvbnN0IGZpcmVmb3ggPSB3aW5kb3cubmF2aWdhdG9yLnVzZXJBZ2VudC5tYXRjaCgvRmlyZWZveFwvKFxkXGRcLlxkKS8pOwogICAgICAgICAgICAgIGlmIChmaXJlZm94CiAgICAgICAgICAgICAgICAmJiBwYXJzZUZsb2F0KGZpcmVmb3hbMV0pID49IDYzCiAgICAgICAgICAgICAgICAmJiBwYXJzZUZsb2F0KGZpcmVmb3hbMV0pIDwgNjYKICAgICAgICAgICAgICAgICYmIHRoaXMucGFyZW50Tm9kZQogICAgICAgICAgICAgICAgJiYgdGhpcy5uZXh0U2libGluZykgewogICAgICAgICAgICAgICAgY29uc3QgZmFrZVRhcmdldCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2lucHV0Jyk7CiAgICAgICAgICAgICAgICBmYWtlVGFyZ2V0LnN0eWxlLnBvc2l0aW9uID0gJ2Fic29sdXRlJzsKICAgICAgICAgICAgICAgIGZha2VUYXJnZXQuc3R5bGUub3BhY2l0eSA9ICcwJzsKICAgICAgICAgICAgICAgIGZha2VUYXJnZXQudGFiSW5kZXggPSB0aGlzLnRhYkluZGV4OwoKICAgICAgICAgICAgICAgIHRoaXMucGFyZW50Tm9kZS5pbnNlcnRCZWZvcmUoZmFrZVRhcmdldCwgdGhpcy5uZXh0U2libGluZyk7CiAgICAgICAgICAgICAgICBmYWtlVGFyZ2V0LmZvY3VzKCk7CiAgICAgICAgICAgICAgICBmYWtlVGFyZ2V0LmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3Vzb3V0JywgKCkgPT4gdGhpcy5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKGZha2VUYXJnZXQpKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIGlmICh0aGlzLmF1dG9mb2N1cyAmJiAhdGhpcy5kaXNhYmxlZCkgewogICAgICAgICAgd2luZG93LnJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICAgIHRoaXMuX2ZvY3VzKCk7CiAgICAgICAgICAgIHRoaXMuX3NldEZvY3VzZWQodHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdmb2N1cy1yaW5nJywgJycpOwogICAgICAgICAgfSk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9ib3VuZEtleWRvd25MaXN0ZW5lciA9IHRoaXMuX2JvZHlLZXlkb3duTGlzdGVuZXIuYmluZCh0aGlzKTsKICAgICAgICB0aGlzLl9ib3VuZEtleXVwTGlzdGVuZXIgPSB0aGlzLl9ib2R5S2V5dXBMaXN0ZW5lci5iaW5kKHRoaXMpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsKCiAgICAgICAgZG9jdW1lbnQuYm9keS5hZGRFdmVudExpc3RlbmVyKCdrZXlkb3duJywgdGhpcy5fYm91bmRLZXlkb3duTGlzdGVuZXIsIHRydWUpOwogICAgICAgIGRvY3VtZW50LmJvZHkuYWRkRXZlbnRMaXN0ZW5lcigna2V5dXAnLCB0aGlzLl9ib3VuZEtleXVwTGlzdGVuZXIsIHRydWUpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKCiAgICAgICAgZG9jdW1lbnQuYm9keS5yZW1vdmVFdmVudExpc3RlbmVyKCdrZXlkb3duJywgdGhpcy5fYm91bmRLZXlkb3duTGlzdGVuZXIsIHRydWUpOwogICAgICAgIGRvY3VtZW50LmJvZHkucmVtb3ZlRXZlbnRMaXN0ZW5lcigna2V5dXAnLCB0aGlzLl9ib3VuZEtleXVwTGlzdGVuZXIsIHRydWUpOwoKICAgICAgICAvLyBpbiBub24tQ2hyb21lIGJyb3dzZXJzLCBibHVyIGRvZXMgbm90IGZpcmUgb24gdGhlIGVsZW1lbnQgd2hlbiBpdCBpcyBkaXNjb25uZWN0ZWQuCiAgICAgICAgLy8gcmVwcm9kdWNpYmxlIGluIGA8dmFhZGluLWRhdGUtcGlja2VyPmAgd2hlbiBjbG9zaW5nIG9uIGBDYW5jZWxgIG9yIGBUb2RheWAgY2xpY2suCiAgICAgICAgaWYgKHRoaXMuaGFzQXR0cmlidXRlKCdmb2N1c2VkJykpIHsKICAgICAgICAgIHRoaXMuX3NldEZvY3VzZWQoZmFsc2UpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gZm9jdXNlZAogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfc2V0Rm9jdXNlZChmb2N1c2VkKSB7CiAgICAgICAgaWYgKGZvY3VzZWQpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdmb2N1c2VkJywgJycpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnZm9jdXNlZCcpOwogICAgICAgIH0KCiAgICAgICAgLy8gZm9jdXMtcmluZyBpcyB0cnVlIHdoZW4gdGhlIGVsZW1lbnQgd2FzIGZvY3VzZWQgZnJvbSB0aGUga2V5Ym9hcmQuCiAgICAgICAgLy8gRm9jdXMgUmluZyBbQTExeWNhc3RzXTogaHR0cHM6Ly95b3V0dS5iZS9pbGoyUDUtNUNqSQogICAgICAgIGlmIChmb2N1c2VkICYmIHRoaXMuX3RhYlByZXNzZWQpIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdmb2N1cy1yaW5nJywgJycpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnZm9jdXMtcmluZycpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7S2V5Ym9hcmRFdmVudH0gZQogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX2JvZHlLZXlkb3duTGlzdGVuZXIoZSkgewogICAgICAgIHRoaXMuX3RhYlByZXNzZWQgPSBlLmtleUNvZGUgPT09IDk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX2JvZHlLZXl1cExpc3RlbmVyKCkgewogICAgICAgIHRoaXMuX3RhYlByZXNzZWQgPSBmYWxzZTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEFueSBlbGVtZW50IGV4dGVuZGluZyB0aGlzIG1peGluIGlzIHJlcXVpcmVkIHRvIGltcGxlbWVudCB0aGlzIGdldHRlci4KICAgICAgICogSXQgcmV0dXJucyB0aGUgYWN0dWFsIGZvY3VzYWJsZSBlbGVtZW50IGluIHRoZSBjb21wb25lbnQuCiAgICAgICAqIEByZXR1cm4ge0VsZW1lbnQgfCBudWxsIHwgdW5kZWZpbmVkfQogICAgICAgKi8KICAgICAgZ2V0IGZvY3VzRWxlbWVudCgpIHsKICAgICAgICB3aW5kb3cuY29uc29sZS53YXJuKGBQbGVhc2UgaW1wbGVtZW50IHRoZSAnZm9jdXNFbGVtZW50JyBwcm9wZXJ0eSBpbiA8JHt0aGlzLmxvY2FsTmFtZX0+YCk7CiAgICAgICAgcmV0dXJuIHRoaXM7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfZm9jdXMoKSB7CiAgICAgICAgaWYgKCF0aGlzLmZvY3VzRWxlbWVudCB8fCB0aGlzLl9pc1NoaWZ0VGFiYmluZykgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5mb2N1c0VsZW1lbnQuZm9jdXMoKTsKICAgICAgICB0aGlzLl9zZXRGb2N1c2VkKHRydWUpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogTW92aW5nIHRoZSBmb2N1cyBmcm9tIHRoZSBob3N0IGVsZW1lbnQgY2F1c2VzIGZpcmluZyBvZiB0aGUgYmx1ciBldmVudCB3aGF0IGxlYWRzIHRvIHByb2JsZW1zIGluIElFLgogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgZm9jdXMoKSB7CiAgICAgICAgaWYgKCF0aGlzLmZvY3VzRWxlbWVudCB8fCB0aGlzLmRpc2FibGVkKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICB0aGlzLmZvY3VzRWxlbWVudC5mb2N1cygpOwogICAgICAgIHRoaXMuX3NldEZvY3VzZWQodHJ1ZSk7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBOYXRpdmUgYmx1cmluZyBpbiB0aGUgaG9zdCBlbGVtZW50IGRvZXMgbm90aGluZyBiZWNhdXNlIGl0IGRvZXMgbm90IGhhdmUgdGhlIGZvY3VzLgogICAgICAgKiBJbiBjaHJvbWUgaXQgd29ya3MsIGJ1dCBub3QgaW4gRkYuCiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBibHVyKCkgewogICAgICAgIGlmICghdGhpcy5mb2N1c0VsZW1lbnQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgdGhpcy5mb2N1c0VsZW1lbnQuYmx1cigpOwogICAgICAgIHRoaXMuX3NldEZvY3VzZWQoZmFsc2UpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHBhcmFtIHtib29sZWFufSBkaXNhYmxlZAogICAgICAgKiBAcHJpdmF0ZQogICAgICAgKi8KICAgICAgX2Rpc2FibGVkQ2hhbmdlZChkaXNhYmxlZCkgewogICAgICAgIHRoaXMuZm9jdXNFbGVtZW50LmRpc2FibGVkID0gZGlzYWJsZWQ7CiAgICAgICAgaWYgKGRpc2FibGVkKSB7CiAgICAgICAgICB0aGlzLmJsdXIoKTsKICAgICAgICAgIHRoaXMuX3ByZXZpb3VzVGFiSW5kZXggPSB0aGlzLnRhYmluZGV4OwogICAgICAgICAgdGhpcy50YWJpbmRleCA9IC0xOwogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtZGlzYWJsZWQnLCAndHJ1ZScpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpZiAodHlwZW9mIHRoaXMuX3ByZXZpb3VzVGFiSW5kZXggIT09ICd1bmRlZmluZWQnKSB7CiAgICAgICAgICAgIHRoaXMudGFiaW5kZXggPSB0aGlzLl9wcmV2aW91c1RhYkluZGV4OwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoJ2FyaWEtZGlzYWJsZWQnKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBAcGFyYW0ge251bWJlciB8IG51bGwgfCB1bmRlZmluZWR9IHRhYmluZGV4CiAgICAgICAqIEBwcml2YXRlCiAgICAgICAqLwogICAgICBfdGFiaW5kZXhDaGFuZ2VkKHRhYmluZGV4KSB7CiAgICAgICAgaWYgKHRhYmluZGV4ICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgIHRoaXMuZm9jdXNFbGVtZW50LnRhYkluZGV4ID0gdGFiaW5kZXg7CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy5kaXNhYmxlZCAmJiB0aGlzLnRhYmluZGV4KSB7CiAgICAgICAgICAvLyBJZiB0YWJpbmRleCBhdHRyaWJ1dGUgd2FzIGNoYW5nZWQgd2hpbGUgY2hlY2tib3ggd2FzIGRpc2FibGVkCiAgICAgICAgICBpZiAodGhpcy50YWJpbmRleCAhPT0gLTEpIHsKICAgICAgICAgICAgdGhpcy5fcHJldmlvdXNUYWJJbmRleCA9IHRoaXMudGFiaW5kZXg7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLnRhYmluZGV4ID0gdGFiaW5kZXggPSB1bmRlZmluZWQ7CiAgICAgICAgfQoKICAgICAgICBpZiAod2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgICB0aGlzLnNldFByb3BlcnRpZXMoe3RhYkluZGV4OiB0YWJpbmRleCwgdGFiaW5kZXg6IHRhYmluZGV4fSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogQHByb3RlY3RlZAogICAgICAgKi8KICAgICAgY2xpY2soKSB7CiAgICAgICAgaWYgKCF0aGlzLmRpc2FibGVkKSB7CiAgICAgICAgICBzdXBlci5jbGljaygpOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMjAgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIEhlbHBlciB0aGF0IHByb3ZpZGVzIGEgc2V0IG9mIGZ1bmN0aW9ucyBmb3IgUlRMLgogICAgICovCiAgICBjbGFzcyBEaXJIZWxwZXIgewogICAgICAvKioKICAgICAgICogR2V0IHRoZSBzY3JvbGwgdHlwZSBpbiB0aGUgY3VycmVudCBicm93c2VyIHZpZXcuCiAgICAgICAqCiAgICAgICAqIEByZXR1cm4ge3N0cmluZ30gdGhlIHNjcm9sbCB0eXBlLiBQb3NzaWJsZSB2YWx1ZXMgYXJlIGBkZWZhdWx0fHJldmVyc2V8bmVnYXRpdmVgCiAgICAgICAqLwogICAgICBzdGF0aWMgZGV0ZWN0U2Nyb2xsVHlwZSgpIHsKICAgICAgICBjb25zdCBkdW1teSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpOwogICAgICAgIGR1bW15LnRleHRDb250ZW50ID0gJ0FCQ0QnOwogICAgICAgIGR1bW15LmRpciA9ICdydGwnOwogICAgICAgIGR1bW15LnN0eWxlLmZvbnRTaXplID0gJzE0cHgnOwogICAgICAgIGR1bW15LnN0eWxlLndpZHRoID0gJzRweCc7CiAgICAgICAgZHVtbXkuc3R5bGUuaGVpZ2h0ID0gJzFweCc7CiAgICAgICAgZHVtbXkuc3R5bGUucG9zaXRpb24gPSAnYWJzb2x1dGUnOwogICAgICAgIGR1bW15LnN0eWxlLnRvcCA9ICctMTAwMHB4JzsKICAgICAgICBkdW1teS5zdHlsZS5vdmVyZmxvdyA9ICdzY3JvbGwnOwogICAgICAgIGRvY3VtZW50LmJvZHkuYXBwZW5kQ2hpbGQoZHVtbXkpOwoKICAgICAgICBsZXQgY2FjaGVkVHlwZSA9ICdyZXZlcnNlJzsKICAgICAgICBpZiAoZHVtbXkuc2Nyb2xsTGVmdCA+IDApIHsKICAgICAgICAgIGNhY2hlZFR5cGUgPSAnZGVmYXVsdCc7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGR1bW15LnNjcm9sbExlZnQgPSAxOwogICAgICAgICAgaWYgKGR1bW15LnNjcm9sbExlZnQgPT09IDApIHsKICAgICAgICAgICAgY2FjaGVkVHlwZSA9ICduZWdhdGl2ZSc7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIGRvY3VtZW50LmJvZHkucmVtb3ZlQ2hpbGQoZHVtbXkpOwogICAgICAgIHJldHVybiBjYWNoZWRUeXBlOwogICAgICB9CgogICAgICAvKioKICAgICAgICogR2V0IHRoZSBzY3JvbGxMZWZ0IHZhbHVlIG9mIHRoZSBlbGVtZW50IHJlbGF0aXZlIHRvIHRoZSBkaXJlY3Rpb24KICAgICAgICoKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHNjcm9sbFR5cGUgdHlwZSBvZiB0aGUgc2Nyb2xsIGRldGVjdGVkIHdpdGggYGRldGVjdFNjcm9sbFR5cGVgCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBkaXJlY3Rpb24gY3VycmVudCBkaXJlY3Rpb24gb2YgdGhlIGVsZW1lbnQKICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgICAqIEByZXR1cm4ge251bWJlcn0gdGhlIHNjcm9sbExlZnQgdmFsdWUuCiAgICAgICovCiAgICAgIHN0YXRpYyBnZXROb3JtYWxpemVkU2Nyb2xsTGVmdChzY3JvbGxUeXBlLCBkaXJlY3Rpb24sIGVsZW1lbnQpIHsKICAgICAgICBjb25zdCB7c2Nyb2xsTGVmdH0gPSBlbGVtZW50OwogICAgICAgIGlmIChkaXJlY3Rpb24gIT09ICdydGwnIHx8ICFzY3JvbGxUeXBlKSB7CiAgICAgICAgICByZXR1cm4gc2Nyb2xsTGVmdDsKICAgICAgICB9CgogICAgICAgIHN3aXRjaCAoc2Nyb2xsVHlwZSkgewogICAgICAgICAgY2FzZSAnbmVnYXRpdmUnOgogICAgICAgICAgICByZXR1cm4gZWxlbWVudC5zY3JvbGxXaWR0aCAtIGVsZW1lbnQuY2xpZW50V2lkdGggKyBzY3JvbGxMZWZ0OwogICAgICAgICAgY2FzZSAncmV2ZXJzZSc6CiAgICAgICAgICAgIHJldHVybiBlbGVtZW50LnNjcm9sbFdpZHRoIC0gZWxlbWVudC5jbGllbnRXaWR0aCAtIHNjcm9sbExlZnQ7CiAgICAgICAgfQogICAgICAgIHJldHVybiBzY3JvbGxMZWZ0OwogICAgICB9CgogICAgICAvKioKICAgICAgICogU2V0IHRoZSBzY3JvbGxMZWZ0IHZhbHVlIG9mIHRoZSBlbGVtZW50IHJlbGF0aXZlIHRvIHRoZSBkaXJlY3Rpb24KICAgICAgICoKICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHNjcm9sbFR5cGUgdHlwZSBvZiB0aGUgc2Nyb2xsIGRldGVjdGVkIHdpdGggYGRldGVjdFNjcm9sbFR5cGVgCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBkaXJlY3Rpb24gY3VycmVudCBkaXJlY3Rpb24gb2YgdGhlIGVsZW1lbnQKICAgICAgICogQHBhcmFtIHtFbGVtZW50fSBlbGVtZW50CiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzY3JvbGxMZWZ0IHRoZSBzY3JvbGxMZWZ0IHZhbHVlIHRvIGJlIHNldAogICAgICAgKi8KICAgICAgc3RhdGljIHNldE5vcm1hbGl6ZWRTY3JvbGxMZWZ0KHNjcm9sbFR5cGUsIGRpcmVjdGlvbiwgZWxlbWVudCwgc2Nyb2xsTGVmdCkgewogICAgICAgIGlmIChkaXJlY3Rpb24gIT09ICdydGwnIHx8ICFzY3JvbGxUeXBlKSB7CiAgICAgICAgICBlbGVtZW50LnNjcm9sbExlZnQgPSBzY3JvbGxMZWZ0OwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgc3dpdGNoIChzY3JvbGxUeXBlKSB7CiAgICAgICAgICBjYXNlICduZWdhdGl2ZSc6CiAgICAgICAgICAgIGVsZW1lbnQuc2Nyb2xsTGVmdCA9IGVsZW1lbnQuY2xpZW50V2lkdGggLSBlbGVtZW50LnNjcm9sbFdpZHRoICsgc2Nyb2xsTGVmdDsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdyZXZlcnNlJzoKICAgICAgICAgICAgZWxlbWVudC5zY3JvbGxMZWZ0ID0gZWxlbWVudC5zY3JvbGxXaWR0aCAtIGVsZW1lbnQuY2xpZW50V2lkdGggLSBzY3JvbGxMZWZ0OwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGRlZmF1bHQ6CiAgICAgICAgICAgIGVsZW1lbnQuc2Nyb2xsTGVmdCA9IHNjcm9sbExlZnQ7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KICAgICAgfQogICAgfQoKICAgIC8qKgogICAgICogQXJyYXkgb2YgVmFhZGluIGN1c3RvbSBlbGVtZW50IGNsYXNzZXMgdGhhdCBoYXZlIGJlZW4gc3Vic2NyaWJlZCB0byB0aGUgZGlyIGNoYW5nZXMuCiAgICAgKi8KICAgIGNvbnN0IGRpcmVjdGlvblN1YnNjcmliZXJzID0gW107CiAgICBjb25zdCBkaXJlY3Rpb25VcGRhdGVyID0gZnVuY3Rpb24oKSB7CiAgICAgIGNvbnN0IGRvY3VtZW50RGlyID0gZ2V0RG9jdW1lbnREaXIoKTsKICAgICAgZGlyZWN0aW9uU3Vic2NyaWJlcnMuZm9yRWFjaChlbGVtZW50ID0+IHsKICAgICAgICBhbGlnbkRpcnMoZWxlbWVudCwgZG9jdW1lbnREaXIpOwogICAgICB9KTsKICAgIH07CgogICAgbGV0IHNjcm9sbFR5cGU7CgogICAgY29uc3QgZGlyZWN0aW9uT2JzZXJ2ZXIgPSBuZXcgTXV0YXRpb25PYnNlcnZlcihkaXJlY3Rpb25VcGRhdGVyKTsKICAgIGRpcmVjdGlvbk9ic2VydmVyLm9ic2VydmUoZG9jdW1lbnQuZG9jdW1lbnRFbGVtZW50LCB7YXR0cmlidXRlczogdHJ1ZSwgYXR0cmlidXRlRmlsdGVyOiBbJ2RpciddfSk7CgogICAgY29uc3QgYWxpZ25EaXJzID0gZnVuY3Rpb24oZWxlbWVudCwgZG9jdW1lbnREaXIpIHsKICAgICAgaWYgKGRvY3VtZW50RGlyKSB7CiAgICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoJ2RpcicsIGRvY3VtZW50RGlyKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBlbGVtZW50LnJlbW92ZUF0dHJpYnV0ZSgnZGlyJyk7CiAgICAgIH0KICAgIH07CgogICAgY29uc3QgZ2V0RG9jdW1lbnREaXIgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIGRvY3VtZW50LmRvY3VtZW50RWxlbWVudC5nZXRBdHRyaWJ1dGUoJ2RpcicpOwogICAgfTsKCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgRGlyTWl4aW4kMSA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgVmFhZGluRGlyTWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICAgICAqLwogICAgICAgICAgZGlyOiB7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgcmVhZE9ubHk6IHRydWUKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICB9CgogICAgICAvKiogQHByb3RlY3RlZCAqLwogICAgICBzdGF0aWMgZmluYWxpemUoKSB7CiAgICAgICAgc3VwZXIuZmluYWxpemUoKTsKCiAgICAgICAgaWYgKCFzY3JvbGxUeXBlKSB7CiAgICAgICAgICBzY3JvbGxUeXBlID0gRGlySGVscGVyLmRldGVjdFNjcm9sbFR5cGUoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKiBAcHJvdGVjdGVkICovCiAgICAgIGNvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CgogICAgICAgIGlmICghdGhpcy5oYXNBdHRyaWJ1dGUoJ2RpcicpKSB7CiAgICAgICAgICB0aGlzLl9fc3Vic2NyaWJlKCk7CiAgICAgICAgICBhbGlnbkRpcnModGhpcywgZ2V0RG9jdW1lbnREaXIoKSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKiogQHByb3RlY3RlZCAqLwogICAgICBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sobmFtZSwgb2xkVmFsdWUsIG5ld1ZhbHVlKSB7CiAgICAgICAgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSk7CiAgICAgICAgaWYgKG5hbWUgIT09ICdkaXInKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICAvLyBOZXcgdmFsdWUgZXF1YWxzIHRvIHRoZSBkb2N1bWVudCBkaXJlY3Rpb24gYW5kIHRoZSBlbGVtZW50IGlzIG5vdCBzdWJzY3JpYmVkIHRvIHRoZSBjaGFuZ2VzCiAgICAgICAgY29uc3QgbmV3VmFsdWVFcWxEb2NEaXIgPSBuZXdWYWx1ZSA9PT0gZ2V0RG9jdW1lbnREaXIoKSAmJiBkaXJlY3Rpb25TdWJzY3JpYmVycy5pbmRleE9mKHRoaXMpID09PSAtMTsKICAgICAgICAvLyBWYWx1ZSB3YXMgZW1wdGllZCBhbmQgdGhlIGVsZW1lbnQgaXMgbm90IHN1YnNjcmliZWQgdG8gdGhlIGNoYW5nZXMKICAgICAgICBjb25zdCBuZXdWYWx1ZUVtcHRpZWQgPSAhbmV3VmFsdWUgJiYgb2xkVmFsdWUgJiYgZGlyZWN0aW9uU3Vic2NyaWJlcnMuaW5kZXhPZih0aGlzKSA9PT0gLTE7CiAgICAgICAgLy8gTmV3IHZhbHVlIGlzIGRpZmZlcmVudCBhbmQgdGhlIG9sZCBlcXVhbHMgdG8gZG9jdW1lbnQgZGlyZWN0aW9uIGFuZCB0aGUgZWxlbWVudCBpcyBub3Qgc3Vic2NyaWJlZCB0byB0aGUgY2hhbmdlcwogICAgICAgIGNvbnN0IG5ld0RpZmZWYWx1ZSA9IG5ld1ZhbHVlICE9PSBnZXREb2N1bWVudERpcigpICYmIG9sZFZhbHVlID09PSBnZXREb2N1bWVudERpcigpOwoKICAgICAgICBpZiAobmV3VmFsdWVFcWxEb2NEaXIgfHwgbmV3VmFsdWVFbXB0aWVkKSB7CiAgICAgICAgICB0aGlzLl9fc3Vic2NyaWJlKCk7CiAgICAgICAgICBhbGlnbkRpcnModGhpcywgZ2V0RG9jdW1lbnREaXIoKSk7CiAgICAgICAgfSBlbHNlIGlmIChuZXdEaWZmVmFsdWUpIHsKICAgICAgICAgIHRoaXMuX19zdWJzY3JpYmUoZmFsc2UpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqIEBwcm90ZWN0ZWQgKi8KICAgICAgZGlzY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuZGlzY29ubmVjdGVkQ2FsbGJhY2soKTsKICAgICAgICB0aGlzLl9fc3Vic2NyaWJlKGZhbHNlKTsKICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnZGlyJyk7CiAgICAgIH0KCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfX3N1YnNjcmliZShwdXNoID0gdHJ1ZSkgewogICAgICAgIGlmIChwdXNoKSB7CiAgICAgICAgICBkaXJlY3Rpb25TdWJzY3JpYmVycy5pbmRleE9mKHRoaXMpID09PSAtMSAmJgogICAgICAgICAgICBkaXJlY3Rpb25TdWJzY3JpYmVycy5wdXNoKHRoaXMpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBkaXJlY3Rpb25TdWJzY3JpYmVycy5pbmRleE9mKHRoaXMpID4gLTEgJiYKICAgICAgICAgICAgZGlyZWN0aW9uU3Vic2NyaWJlcnMuc3BsaWNlKGRpcmVjdGlvblN1YnNjcmliZXJzLmluZGV4T2YodGhpcyksIDEpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7RWxlbWVudH0gZWxlbWVudAogICAgICAgKiBAcmV0dXJuIHtudW1iZXJ9CiAgICAgICAqIEBwcm90ZWN0ZWQKICAgICAgICovCiAgICAgIF9fZ2V0Tm9ybWFsaXplZFNjcm9sbExlZnQoZWxlbWVudCkgewogICAgICAgIHJldHVybiBEaXJIZWxwZXIuZ2V0Tm9ybWFsaXplZFNjcm9sbExlZnQoc2Nyb2xsVHlwZSwgdGhpcy5nZXRBdHRyaWJ1dGUoJ2RpcicpIHx8ICdsdHInLCBlbGVtZW50KTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7RWxlbWVudH0gZWxlbWVudAogICAgICAgKiBAcGFyYW0ge251bWJlcn0gc2Nyb2xsTGVmdAogICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICAqLwogICAgICBfX3NldE5vcm1hbGl6ZWRTY3JvbGxMZWZ0KGVsZW1lbnQsIHNjcm9sbExlZnQpIHsKICAgICAgICByZXR1cm4gRGlySGVscGVyLnNldE5vcm1hbGl6ZWRTY3JvbGxMZWZ0KHNjcm9sbFR5cGUsIHRoaXMuZ2V0QXR0cmlidXRlKCdkaXInKSB8fCAnbHRyJywgZWxlbWVudCwgc2Nyb2xsTGVmdCk7CiAgICAgIH0KICAgIH07CgogICAgY29uc3QgREVWX01PREVfQ09ERV9SRUdFWFAgPQogICAgICAvXC9cKlwqXHMrdmFhZGluLWRldi1tb2RlOnN0YXJ0KFtcc1xTXSopdmFhZGluLWRldi1tb2RlOmVuZFxzK1wqXCpcLy9pOwoKICAgIGNvbnN0IEZsb3dDbGllbnRzID0gd2luZG93LlZhYWRpbiAmJiB3aW5kb3cuVmFhZGluLkZsb3cgJiYgd2luZG93LlZhYWRpbi5GbG93LmNsaWVudHM7CgogICAgZnVuY3Rpb24gaXNNaW5pZmllZCgpIHsKICAgICAgZnVuY3Rpb24gdGVzdCgpIHsKICAgICAgICAvKiogdmFhZGluLWRldi1tb2RlOnN0YXJ0CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIHZhYWRpbi1kZXYtbW9kZTplbmQgKiovCiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KICAgICAgcmV0dXJuIHVuY29tbWVudEFuZFJ1bih0ZXN0KTsKICAgIH0KCiAgICBmdW5jdGlvbiBpc0RldmVsb3BtZW50TW9kZSgpIHsKICAgICAgdHJ5IHsKICAgICAgICBpZiAoaXNGb3JjZWREZXZlbG9wbWVudE1vZGUoKSkgewogICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgfQoKICAgICAgICBpZiAoIWlzTG9jYWxob3N0KCkpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CgogICAgICAgIGlmIChGbG93Q2xpZW50cykgewogICAgICAgICAgcmV0dXJuICFpc0Zsb3dQcm9kdWN0aW9uTW9kZSgpOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuICFpc01pbmlmaWVkKCk7CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAvLyBTb21lIGVycm9yIGluIHRoaXMgY29kZSwgYXNzdW1lIHByb2R1Y3Rpb24gc28gbm8gZnVydGhlciBhY3Rpb25zIHdpbGwgYmUgdGFrZW4KICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgIH0KCiAgICBmdW5jdGlvbiBpc0ZvcmNlZERldmVsb3BtZW50TW9kZSgpIHsKICAgICAgcmV0dXJuIGxvY2FsU3RvcmFnZS5nZXRJdGVtKCJ2YWFkaW4uZGV2ZWxvcG1lbnRtb2RlLmZvcmNlIik7CiAgICB9CgogICAgZnVuY3Rpb24gaXNMb2NhbGhvc3QoKSB7CiAgICAgIHJldHVybiAoWyJsb2NhbGhvc3QiLCIxMjcuMC4wLjEiXS5pbmRleE9mKHdpbmRvdy5sb2NhdGlvbi5ob3N0bmFtZSkgPj0gMCk7CiAgICB9CgogICAgZnVuY3Rpb24gaXNGbG93UHJvZHVjdGlvbk1vZGUoKSB7CiAgICAgIGlmIChGbG93Q2xpZW50cykgewogICAgICAgIGNvbnN0IHByb2R1Y3Rpb25Nb2RlQXBwcyA9IE9iamVjdC5rZXlzKEZsb3dDbGllbnRzKQogICAgICAgICAgLm1hcChrZXkgPT4gRmxvd0NsaWVudHNba2V5XSkKICAgICAgICAgIC5maWx0ZXIoY2xpZW50ID0+IGNsaWVudC5wcm9kdWN0aW9uTW9kZSk7CiAgICAgICAgaWYgKHByb2R1Y3Rpb25Nb2RlQXBwcy5sZW5ndGggPiAwKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfQoKICAgIGZ1bmN0aW9uIHVuY29tbWVudEFuZFJ1bihjYWxsYmFjaywgYXJncykgewogICAgICBpZiAodHlwZW9mIGNhbGxiYWNrICE9PSAnZnVuY3Rpb24nKSB7CiAgICAgICAgcmV0dXJuOwogICAgICB9CgogICAgICBjb25zdCBtYXRjaCA9IERFVl9NT0RFX0NPREVfUkVHRVhQLmV4ZWMoY2FsbGJhY2sudG9TdHJpbmcoKSk7CiAgICAgIGlmIChtYXRjaCkgewogICAgICAgIHRyeSB7CiAgICAgICAgICAvLyByZXF1aXJlcyBDU1A6IHNjcmlwdC1zcmMgJ3Vuc2FmZS1ldmFsJwogICAgICAgICAgY2FsbGJhY2sgPSBuZXcgRnVuY3Rpb24obWF0Y2hbMV0pOwogICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgIC8vIGVhdCB0aGUgZXhjZXB0aW9uCiAgICAgICAgICBjb25zb2xlLmxvZygndmFhZGluLWRldmVsb3BtZW50LW1vZGUtZGV0ZWN0b3I6IHVuY29tbWVudEFuZFJ1bigpIGZhaWxlZCcsIGUpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmV0dXJuIGNhbGxiYWNrKGFyZ3MpOwogICAgfQoKICAgIC8vIEEgZ3VhcmQgYWdhaW5zdCBwb2x5bWVyLW1vZHVsaXplciByZW1vdmluZyB0aGUgd2luZG93LlZhYWRpbgogICAgLy8gaW5pdGlhbGl6YXRpb24gYWJvdmUuCiAgICB3aW5kb3dbJ1ZhYWRpbiddID0gd2luZG93WydWYWFkaW4nXSB8fCB7fTsKCiAgICAvKioKICAgICAqIEluc3BlY3RzIHRoZSBzb3VyY2UgY29kZSBvZiB0aGUgZ2l2ZW4gYGNhbGxiYWNrYCBmdW5jdGlvbiBmb3IKICAgICAqIHNwZWNpYWxseS1tYXJrZWQgX2NvbW1lbnRlZF8gY29kZS4gSWYgc3VjaCBjb21tZW50ZWQgY29kZSBpcyBmb3VuZCBpbiB0aGUKICAgICAqIGNhbGxiYWNrIHNvdXJjZSwgdW5jb21tZW50cyBhbmQgcnVucyB0aGF0IGNvZGUgaW5zdGVhZCBvZiB0aGUgY2FsbGJhY2sKICAgICAqIGl0c2VsZi4gT3RoZXJ3aXNlIHJ1bnMgdGhlIGNhbGxiYWNrIGFzIGlzLgogICAgICoKICAgICAqIFRoZSBvcHRpb25hbCBhcmd1bWVudHMgYXJlIHBhc3NlZCBpbnRvIHRoZSBjYWxsYmFjayAvIHVuY29tbWVudGVkIGNvZGUsCiAgICAgKiB0aGUgcmVzdWx0IGlzIHJldHVybmVkLgogICAgICoKICAgICAqIFNlZSB0aGUgYGlzTWluaWZpZWQoKWAgZnVuY3Rpb24gc291cmNlIGNvZGUgaW4gdGhpcyBmaWxlIGZvciBhbiBleGFtcGxlLgogICAgICoKICAgICAqLwogICAgY29uc3QgcnVuSWZEZXZlbG9wbWVudE1vZGUgPSBmdW5jdGlvbihjYWxsYmFjaywgYXJncykgewogICAgICBpZiAod2luZG93LlZhYWRpbi5kZXZlbG9wbWVudE1vZGUpIHsKICAgICAgICByZXR1cm4gdW5jb21tZW50QW5kUnVuKGNhbGxiYWNrLCBhcmdzKTsKICAgICAgfQogICAgfTsKCiAgICBpZiAod2luZG93LlZhYWRpbi5kZXZlbG9wbWVudE1vZGUgPT09IHVuZGVmaW5lZCkgewogICAgICB3aW5kb3cuVmFhZGluLmRldmVsb3BtZW50TW9kZSA9IGlzRGV2ZWxvcG1lbnRNb2RlKCk7CiAgICB9CgogICAgLyogVGhpcyBmaWxlIGlzIGF1dG9nZW5lcmF0ZWQgZnJvbSBzcmMvdmFhZGluLXVzYWdlLXN0YXRpc3RpY3MudHBsLmh0bWwgKi8KCiAgICBmdW5jdGlvbiBtYXliZUdhdGhlckFuZFNlbmRTdGF0cygpIHsKICAgICAgLyoqIHZhYWRpbi1kZXYtbW9kZTpzdGFydAogICAgICAoZnVuY3Rpb24gKCkgewogICAgJ3VzZSBzdHJpY3QnOwoKICAgIHZhciBfdHlwZW9mID0gdHlwZW9mIFN5bWJvbCA9PT0gImZ1bmN0aW9uIiAmJiB0eXBlb2YgU3ltYm9sLml0ZXJhdG9yID09PSAic3ltYm9sIiA/IGZ1bmN0aW9uIChvYmopIHsKICAgICAgcmV0dXJuIHR5cGVvZiBvYmo7CiAgICB9IDogZnVuY3Rpb24gKG9iaikgewogICAgICByZXR1cm4gb2JqICYmIHR5cGVvZiBTeW1ib2wgPT09ICJmdW5jdGlvbiIgJiYgb2JqLmNvbnN0cnVjdG9yID09PSBTeW1ib2wgJiYgb2JqICE9PSBTeW1ib2wucHJvdG90eXBlID8gInN5bWJvbCIgOiB0eXBlb2Ygb2JqOwogICAgfTsKCiAgICB2YXIgY2xhc3NDYWxsQ2hlY2sgPSBmdW5jdGlvbiAoaW5zdGFuY2UsIENvbnN0cnVjdG9yKSB7CiAgICAgIGlmICghKGluc3RhbmNlIGluc3RhbmNlb2YgQ29uc3RydWN0b3IpKSB7CiAgICAgICAgdGhyb3cgbmV3IFR5cGVFcnJvcigiQ2Fubm90IGNhbGwgYSBjbGFzcyBhcyBhIGZ1bmN0aW9uIik7CiAgICAgIH0KICAgIH07CgogICAgdmFyIGNyZWF0ZUNsYXNzID0gZnVuY3Rpb24gKCkgewogICAgICBmdW5jdGlvbiBkZWZpbmVQcm9wZXJ0aWVzKHRhcmdldCwgcHJvcHMpIHsKICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IHByb3BzLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICB2YXIgZGVzY3JpcHRvciA9IHByb3BzW2ldOwogICAgICAgICAgZGVzY3JpcHRvci5lbnVtZXJhYmxlID0gZGVzY3JpcHRvci5lbnVtZXJhYmxlIHx8IGZhbHNlOwogICAgICAgICAgZGVzY3JpcHRvci5jb25maWd1cmFibGUgPSB0cnVlOwogICAgICAgICAgaWYgKCJ2YWx1ZSIgaW4gZGVzY3JpcHRvcikgZGVzY3JpcHRvci53cml0YWJsZSA9IHRydWU7CiAgICAgICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBkZXNjcmlwdG9yLmtleSwgZGVzY3JpcHRvcik7CiAgICAgICAgfQogICAgICB9CgogICAgICByZXR1cm4gZnVuY3Rpb24gKENvbnN0cnVjdG9yLCBwcm90b1Byb3BzLCBzdGF0aWNQcm9wcykgewogICAgICAgIGlmIChwcm90b1Byb3BzKSBkZWZpbmVQcm9wZXJ0aWVzKENvbnN0cnVjdG9yLnByb3RvdHlwZSwgcHJvdG9Qcm9wcyk7CiAgICAgICAgaWYgKHN0YXRpY1Byb3BzKSBkZWZpbmVQcm9wZXJ0aWVzKENvbnN0cnVjdG9yLCBzdGF0aWNQcm9wcyk7CiAgICAgICAgcmV0dXJuIENvbnN0cnVjdG9yOwogICAgICB9OwogICAgfSgpOwoKICAgIHZhciBnZXRQb2x5bWVyVmVyc2lvbiA9IGZ1bmN0aW9uIGdldFBvbHltZXJWZXJzaW9uKCkgewogICAgICByZXR1cm4gd2luZG93LlBvbHltZXIgJiYgd2luZG93LlBvbHltZXIudmVyc2lvbjsKICAgIH07CgogICAgdmFyIFN0YXRpc3RpY3NHYXRoZXJlciA9IGZ1bmN0aW9uICgpIHsKICAgICAgZnVuY3Rpb24gU3RhdGlzdGljc0dhdGhlcmVyKGxvZ2dlcikgewogICAgICAgIGNsYXNzQ2FsbENoZWNrKHRoaXMsIFN0YXRpc3RpY3NHYXRoZXJlcik7CgogICAgICAgIHRoaXMubm93ID0gbmV3IERhdGUoKS5nZXRUaW1lKCk7CiAgICAgICAgdGhpcy5sb2dnZXIgPSBsb2dnZXI7CiAgICAgIH0KCiAgICAgIGNyZWF0ZUNsYXNzKFN0YXRpc3RpY3NHYXRoZXJlciwgW3sKICAgICAgICBrZXk6ICdmcmFtZXdvcmtWZXJzaW9uRGV0ZWN0b3JzJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gZnJhbWV3b3JrVmVyc2lvbkRldGVjdG9ycygpIHsKICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICdGbG93JzogZnVuY3Rpb24gRmxvdygpIHsKICAgICAgICAgICAgICBpZiAod2luZG93LlZhYWRpbiAmJiB3aW5kb3cuVmFhZGluLkZsb3cgJiYgd2luZG93LlZhYWRpbi5GbG93LmNsaWVudHMpIHsKICAgICAgICAgICAgICAgIHZhciBmbG93VmVyc2lvbnMgPSBPYmplY3Qua2V5cyh3aW5kb3cuVmFhZGluLkZsb3cuY2xpZW50cykubWFwKGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIHdpbmRvdy5WYWFkaW4uRmxvdy5jbGllbnRzW2tleV07CiAgICAgICAgICAgICAgICB9KS5maWx0ZXIoZnVuY3Rpb24gKGNsaWVudCkgewogICAgICAgICAgICAgICAgICByZXR1cm4gY2xpZW50LmdldFZlcnNpb25JbmZvOwogICAgICAgICAgICAgICAgfSkubWFwKGZ1bmN0aW9uIChjbGllbnQpIHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIGNsaWVudC5nZXRWZXJzaW9uSW5mbygpLmZsb3c7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGlmIChmbG93VmVyc2lvbnMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgICByZXR1cm4gZmxvd1ZlcnNpb25zWzBdOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgJ1ZhYWRpbiBGcmFtZXdvcmsnOiBmdW5jdGlvbiBWYWFkaW5GcmFtZXdvcmsoKSB7CiAgICAgICAgICAgICAgaWYgKHdpbmRvdy52YWFkaW4gJiYgd2luZG93LnZhYWRpbi5jbGllbnRzKSB7CiAgICAgICAgICAgICAgICB2YXIgZnJhbWV3b3JrVmVyc2lvbnMgPSBPYmplY3QudmFsdWVzKHdpbmRvdy52YWFkaW4uY2xpZW50cykuZmlsdGVyKGZ1bmN0aW9uIChjbGllbnQpIHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIGNsaWVudC5nZXRWZXJzaW9uSW5mbzsKICAgICAgICAgICAgICAgIH0pLm1hcChmdW5jdGlvbiAoY2xpZW50KSB7CiAgICAgICAgICAgICAgICAgIHJldHVybiBjbGllbnQuZ2V0VmVyc2lvbkluZm8oKS52YWFkaW5WZXJzaW9uOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBpZiAoZnJhbWV3b3JrVmVyc2lvbnMubGVuZ3RoID4gMCkgewogICAgICAgICAgICAgICAgICByZXR1cm4gZnJhbWV3b3JrVmVyc2lvbnNbMF07CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICAnQW5ndWxhckpzJzogZnVuY3Rpb24gQW5ndWxhckpzKCkgewogICAgICAgICAgICAgIGlmICh3aW5kb3cuYW5ndWxhciAmJiB3aW5kb3cuYW5ndWxhci52ZXJzaW9uICYmIHdpbmRvdy5hbmd1bGFyLnZlcnNpb24pIHsKICAgICAgICAgICAgICAgIHJldHVybiB3aW5kb3cuYW5ndWxhci52ZXJzaW9uLmZ1bGw7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICAnQW5ndWxhcic6IGZ1bmN0aW9uIEFuZ3VsYXIoKSB7CiAgICAgICAgICAgICAgaWYgKHdpbmRvdy5uZykgewogICAgICAgICAgICAgICAgdmFyIHRhZ3MgPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yQWxsKCJbbmctdmVyc2lvbl0iKTsKICAgICAgICAgICAgICAgIGlmICh0YWdzLmxlbmd0aCA+IDApIHsKICAgICAgICAgICAgICAgICAgcmV0dXJuIHRhZ3NbMF0uZ2V0QXR0cmlidXRlKCJuZy12ZXJzaW9uIik7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gIlVua25vd24iOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgJ0JhY2tib25lLmpzJzogZnVuY3Rpb24gQmFja2JvbmVKcygpIHsKICAgICAgICAgICAgICBpZiAod2luZG93LkJhY2tib25lKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gd2luZG93LkJhY2tib25lLlZFUlNJT047CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICAnUmVhY3QnOiBmdW5jdGlvbiBSZWFjdCgpIHsKICAgICAgICAgICAgICB2YXIgcmVhY3RTZWxlY3RvciA9ICdbZGF0YS1yZWFjdHJvb3RdLCBbZGF0YS1yZWFjdGlkXSc7CiAgICAgICAgICAgICAgaWYgKCEhZG9jdW1lbnQucXVlcnlTZWxlY3RvcihyZWFjdFNlbGVjdG9yKSkgewogICAgICAgICAgICAgICAgLy8gUmVhY3QgZG9lcyBub3QgcHVibGlzaCB0aGUgdmVyc2lvbiBieSBkZWZhdWx0CiAgICAgICAgICAgICAgICByZXR1cm4gInVua25vd24iOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgJ0VtYmVyJzogZnVuY3Rpb24gRW1iZXIoKSB7CiAgICAgICAgICAgICAgaWYgKHdpbmRvdy5FbSAmJiB3aW5kb3cuRW0uVkVSU0lPTikgewogICAgICAgICAgICAgICAgcmV0dXJuIHdpbmRvdy5FbS5WRVJTSU9OOwogICAgICAgICAgICAgIH0gZWxzZSBpZiAod2luZG93LkVtYmVyICYmIHdpbmRvdy5FbWJlci5WRVJTSU9OKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gd2luZG93LkVtYmVyLlZFUlNJT047CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICAnalF1ZXJ5JzogZnVuY3Rpb24gKF9qUXVlcnkpIHsKICAgICAgICAgICAgICBmdW5jdGlvbiBqUXVlcnkoKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gX2pRdWVyeS5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgalF1ZXJ5LnRvU3RyaW5nID0gZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgcmV0dXJuIF9qUXVlcnkudG9TdHJpbmcoKTsKICAgICAgICAgICAgICB9OwoKICAgICAgICAgICAgICByZXR1cm4galF1ZXJ5OwogICAgICAgICAgICB9KGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICBpZiAodHlwZW9mIGpRdWVyeSA9PT0gJ2Z1bmN0aW9uJyAmJiBqUXVlcnkucHJvdG90eXBlLmpxdWVyeSAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm4galF1ZXJ5LnByb3RvdHlwZS5qcXVlcnk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KSwKICAgICAgICAgICAgJ1BvbHltZXInOiBmdW5jdGlvbiBQb2x5bWVyKCkgewogICAgICAgICAgICAgIHZhciB2ZXJzaW9uID0gZ2V0UG9seW1lclZlcnNpb24oKTsKICAgICAgICAgICAgICBpZiAodmVyc2lvbikgewogICAgICAgICAgICAgICAgcmV0dXJuIHZlcnNpb247CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9LAogICAgICAgICAgICAnTGl0RWxlbWVudCc6IGZ1bmN0aW9uIExpdEVsZW1lbnQoKSB7CiAgICAgICAgICAgICAgdmFyIHZlcnNpb24gPSB3aW5kb3cubGl0RWxlbWVudFZlcnNpb25zICYmIHdpbmRvdy5saXRFbGVtZW50VmVyc2lvbnNbMF07CiAgICAgICAgICAgICAgaWYgKHZlcnNpb24pIHsKICAgICAgICAgICAgICAgIHJldHVybiB2ZXJzaW9uOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSwKICAgICAgICAgICAgJ0xpdEh0bWwnOiBmdW5jdGlvbiBMaXRIdG1sKCkgewogICAgICAgICAgICAgIHZhciB2ZXJzaW9uID0gd2luZG93LmxpdEh0bWxWZXJzaW9ucyAmJiB3aW5kb3cubGl0SHRtbFZlcnNpb25zWzBdOwogICAgICAgICAgICAgIGlmICh2ZXJzaW9uKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdmVyc2lvbjsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sCiAgICAgICAgICAgICdWdWUuanMnOiBmdW5jdGlvbiBWdWVKcygpIHsKICAgICAgICAgICAgICBpZiAod2luZG93LlZ1ZSkgewogICAgICAgICAgICAgICAgcmV0dXJuIHdpbmRvdy5WdWUudmVyc2lvbjsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH07CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnZ2V0VXNlZFZhYWRpbkVsZW1lbnRzJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gZ2V0VXNlZFZhYWRpbkVsZW1lbnRzKGVsZW1lbnRzKSB7CiAgICAgICAgICB2YXIgdmVyc2lvbiA9IGdldFBvbHltZXJWZXJzaW9uKCk7CiAgICAgICAgICB2YXIgZWxlbWVudENsYXNzZXMgPSB2b2lkIDA7CiAgICAgICAgICAvLyBOT1RFOiBJbiBjYXNlIHlvdSBlZGl0IHRoZSBjb2RlIGhlcmUsIFlPVSBNVVNUIFVQREFURSBhbnkgc3RhdGlzdGljcyByZXBvcnRpbmcgY29kZSBpbiBGbG93LgogICAgICAgICAgLy8gQ2hlY2sgYWxsIGxvY2F0aW9ucyBjYWxsaW5nIHRoZSBtZXRob2QgZ2V0RW50cmllcygpIGluCiAgICAgICAgICAvLyBodHRwczovL2dpdGh1Yi5jb20vdmFhZGluL2Zsb3cvYmxvYi9tYXN0ZXIvZmxvdy1zZXJ2ZXIvc3JjL21haW4vamF2YS9jb20vdmFhZGluL2Zsb3cvaW50ZXJuYWwvVXNhZ2VTdGF0aXN0aWNzLmphdmEjTDEwNgogICAgICAgICAgLy8gQ3VycmVudGx5IGl0IGlzIG9ubHkgdXNlZCBieSBCb290c3RyYXBIYW5kbGVyLgogICAgICAgICAgaWYgKHZlcnNpb24gJiYgdmVyc2lvbi5pbmRleE9mKCcyJykgPT09IDApIHsKICAgICAgICAgICAgLy8gUG9seW1lciAyOiBjb21wb25lbnRzIGNsYXNzZXMgYXJlIHN0b3JlZCBpbiB3aW5kb3cuVmFhZGluCiAgICAgICAgICAgIGVsZW1lbnRDbGFzc2VzID0gT2JqZWN0LmtleXMod2luZG93LlZhYWRpbikubWFwKGZ1bmN0aW9uIChjKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHdpbmRvdy5WYWFkaW5bY107CiAgICAgICAgICAgIH0pLmZpbHRlcihmdW5jdGlvbiAoYykgewogICAgICAgICAgICAgIHJldHVybiBjLmlzOwogICAgICAgICAgICB9KTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIFBvbHltZXIgMzogY29tcG9uZW50cyBjbGFzc2VzIGFyZSBzdG9yZWQgaW4gd2luZG93LlZhYWRpbi5yZWdpc3RyYXRpb25zCiAgICAgICAgICAgIGVsZW1lbnRDbGFzc2VzID0gd2luZG93LlZhYWRpbi5yZWdpc3RyYXRpb25zIHx8IFtdOwogICAgICAgICAgfQogICAgICAgICAgZWxlbWVudENsYXNzZXMuZm9yRWFjaChmdW5jdGlvbiAoa2xhc3MpIHsKICAgICAgICAgICAgdmFyIHZlcnNpb24gPSBrbGFzcy52ZXJzaW9uID8ga2xhc3MudmVyc2lvbiA6ICIwLjAuMCI7CiAgICAgICAgICAgIGVsZW1lbnRzW2tsYXNzLmlzXSA9IHsgdmVyc2lvbjogdmVyc2lvbiB9OwogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnZ2V0VXNlZFZhYWRpblRoZW1lcycsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIGdldFVzZWRWYWFkaW5UaGVtZXModGhlbWVzKSB7CiAgICAgICAgICBbJ0x1bW8nLCAnTWF0ZXJpYWwnXS5mb3JFYWNoKGZ1bmN0aW9uICh0aGVtZU5hbWUpIHsKICAgICAgICAgICAgdmFyIHRoZW1lOwogICAgICAgICAgICB2YXIgdmVyc2lvbiA9IGdldFBvbHltZXJWZXJzaW9uKCk7CiAgICAgICAgICAgIGlmICh2ZXJzaW9uICYmIHZlcnNpb24uaW5kZXhPZignMicpID09PSAwKSB7CiAgICAgICAgICAgICAgLy8gUG9seW1lciAyOiB0aGVtZXMgYXJlIHN0b3JlZCBpbiB3aW5kb3cuVmFhZGluCiAgICAgICAgICAgICAgdGhlbWUgPSB3aW5kb3cuVmFhZGluW3RoZW1lTmFtZV07CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgLy8gUG9seW1lciAzOiB0aGVtZXMgYXJlIHN0b3JlZCBpbiBjdXN0b20gZWxlbWVudCByZWdpc3RyeQogICAgICAgICAgICAgIHRoZW1lID0gY3VzdG9tRWxlbWVudHMuZ2V0KCd2YWFkaW4tJyArIHRoZW1lTmFtZS50b0xvd2VyQ2FzZSgpICsgJy1zdHlsZXMnKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAodGhlbWUgJiYgdGhlbWUudmVyc2lvbikgewogICAgICAgICAgICAgIHRoZW1lc1t0aGVtZU5hbWVdID0geyB2ZXJzaW9uOiB0aGVtZS52ZXJzaW9uIH07CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfSwgewogICAgICAgIGtleTogJ2dldEZyYW1ld29ya3MnLAogICAgICAgIHZhbHVlOiBmdW5jdGlvbiBnZXRGcmFtZXdvcmtzKGZyYW1ld29ya3MpIHsKICAgICAgICAgIHZhciBkZXRlY3RvcnMgPSB0aGlzLmZyYW1ld29ya1ZlcnNpb25EZXRlY3RvcnMoKTsKICAgICAgICAgIE9iamVjdC5rZXlzKGRldGVjdG9ycykuZm9yRWFjaChmdW5jdGlvbiAoZnJhbWV3b3JrKSB7CiAgICAgICAgICAgIHZhciBkZXRlY3RvciA9IGRldGVjdG9yc1tmcmFtZXdvcmtdOwogICAgICAgICAgICB0cnkgewogICAgICAgICAgICAgIHZhciB2ZXJzaW9uID0gZGV0ZWN0b3IoKTsKICAgICAgICAgICAgICBpZiAodmVyc2lvbikgewogICAgICAgICAgICAgICAgZnJhbWV3b3Jrc1tmcmFtZXdvcmtdID0geyB2ZXJzaW9uOiB2ZXJzaW9uIH07CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9IGNhdGNoIChlKSB7fQogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnZ2F0aGVyJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gZ2F0aGVyKHN0b3JhZ2UpIHsKICAgICAgICAgIHZhciBzdG9yZWRTdGF0cyA9IHN0b3JhZ2UucmVhZCgpOwogICAgICAgICAgdmFyIGdhdGhlcmVkU3RhdHMgPSB7fTsKICAgICAgICAgIHZhciB0eXBlcyA9IFsiZWxlbWVudHMiLCAiZnJhbWV3b3JrcyIsICJ0aGVtZXMiXTsKCiAgICAgICAgICB0eXBlcy5mb3JFYWNoKGZ1bmN0aW9uICh0eXBlKSB7CiAgICAgICAgICAgIGdhdGhlcmVkU3RhdHNbdHlwZV0gPSB7fTsKICAgICAgICAgICAgaWYgKCFzdG9yZWRTdGF0c1t0eXBlXSkgewogICAgICAgICAgICAgIHN0b3JlZFN0YXRzW3R5cGVdID0ge307CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwoKICAgICAgICAgIHZhciBwcmV2aW91c1N0YXRzID0gSlNPTi5zdHJpbmdpZnkoc3RvcmVkU3RhdHMpOwoKICAgICAgICAgIHRoaXMuZ2V0VXNlZFZhYWRpbkVsZW1lbnRzKGdhdGhlcmVkU3RhdHMuZWxlbWVudHMpOwogICAgICAgICAgdGhpcy5nZXRGcmFtZXdvcmtzKGdhdGhlcmVkU3RhdHMuZnJhbWV3b3Jrcyk7CiAgICAgICAgICB0aGlzLmdldFVzZWRWYWFkaW5UaGVtZXMoZ2F0aGVyZWRTdGF0cy50aGVtZXMpOwoKICAgICAgICAgIHZhciBub3cgPSB0aGlzLm5vdzsKICAgICAgICAgIHR5cGVzLmZvckVhY2goZnVuY3Rpb24gKHR5cGUpIHsKICAgICAgICAgICAgdmFyIGtleXMgPSBPYmplY3Qua2V5cyhnYXRoZXJlZFN0YXRzW3R5cGVdKTsKICAgICAgICAgICAga2V5cy5mb3JFYWNoKGZ1bmN0aW9uIChrZXkpIHsKICAgICAgICAgICAgICBpZiAoIXN0b3JlZFN0YXRzW3R5cGVdW2tleV0gfHwgX3R5cGVvZihzdG9yZWRTdGF0c1t0eXBlXVtrZXldKSAhPSBfdHlwZW9mKHt9KSkgewogICAgICAgICAgICAgICAgc3RvcmVkU3RhdHNbdHlwZV1ba2V5XSA9IHsgZmlyc3RVc2VkOiBub3cgfTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgLy8gRGlzY2FyZHMgYW55IHByZXZpb3VzbHkgbG9nZ2VkIHZlcnNpb24gbnVtYmVyCiAgICAgICAgICAgICAgc3RvcmVkU3RhdHNbdHlwZV1ba2V5XS52ZXJzaW9uID0gZ2F0aGVyZWRTdGF0c1t0eXBlXVtrZXldLnZlcnNpb247CiAgICAgICAgICAgICAgc3RvcmVkU3RhdHNbdHlwZV1ba2V5XS5sYXN0VXNlZCA9IG5vdzsKICAgICAgICAgICAgfSk7CiAgICAgICAgICB9KTsKCiAgICAgICAgICB2YXIgbmV3U3RhdHMgPSBKU09OLnN0cmluZ2lmeShzdG9yZWRTdGF0cyk7CiAgICAgICAgICBzdG9yYWdlLndyaXRlKG5ld1N0YXRzKTsKICAgICAgICAgIGlmIChuZXdTdGF0cyAhPSBwcmV2aW91c1N0YXRzICYmIE9iamVjdC5rZXlzKHN0b3JlZFN0YXRzKS5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgIHRoaXMubG9nZ2VyLmRlYnVnKCJOZXcgc3RhdHM6ICIgKyBuZXdTdGF0cyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9XSk7CiAgICAgIHJldHVybiBTdGF0aXN0aWNzR2F0aGVyZXI7CiAgICB9KCk7CgogICAgdmFyIFN0YXRpc3RpY3NTdG9yYWdlID0gZnVuY3Rpb24gKCkgewogICAgICBmdW5jdGlvbiBTdGF0aXN0aWNzU3RvcmFnZShrZXkpIHsKICAgICAgICBjbGFzc0NhbGxDaGVjayh0aGlzLCBTdGF0aXN0aWNzU3RvcmFnZSk7CgogICAgICAgIHRoaXMua2V5ID0ga2V5OwogICAgICB9CgogICAgICBjcmVhdGVDbGFzcyhTdGF0aXN0aWNzU3RvcmFnZSwgW3sKICAgICAgICBrZXk6ICdyZWFkJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gcmVhZCgpIHsKICAgICAgICAgIHZhciBsb2NhbFN0b3JhZ2VTdGF0c1N0cmluZyA9IGxvY2FsU3RvcmFnZS5nZXRJdGVtKHRoaXMua2V5KTsKICAgICAgICAgIHRyeSB7CiAgICAgICAgICAgIHJldHVybiBKU09OLnBhcnNlKGxvY2FsU3RvcmFnZVN0YXRzU3RyaW5nID8gbG9jYWxTdG9yYWdlU3RhdHNTdHJpbmcgOiAne30nKTsKICAgICAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICAgICAgcmV0dXJuIHt9OwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfSwgewogICAgICAgIGtleTogJ3dyaXRlJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gd3JpdGUoZGF0YSkgewogICAgICAgICAgbG9jYWxTdG9yYWdlLnNldEl0ZW0odGhpcy5rZXksIGRhdGEpOwogICAgICAgIH0KICAgICAgfSwgewogICAgICAgIGtleTogJ2NsZWFyJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gY2xlYXIoKSB7CiAgICAgICAgICBsb2NhbFN0b3JhZ2UucmVtb3ZlSXRlbSh0aGlzLmtleSk7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnaXNFbXB0eScsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIGlzRW1wdHkoKSB7CiAgICAgICAgICB2YXIgc3RvcmVkU3RhdHMgPSB0aGlzLnJlYWQoKTsKICAgICAgICAgIHZhciBlbXB0eSA9IHRydWU7CiAgICAgICAgICBPYmplY3Qua2V5cyhzdG9yZWRTdGF0cykuZm9yRWFjaChmdW5jdGlvbiAoa2V5KSB7CiAgICAgICAgICAgIGlmIChPYmplY3Qua2V5cyhzdG9yZWRTdGF0c1trZXldKS5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgICAgZW1wdHkgPSBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CgogICAgICAgICAgcmV0dXJuIGVtcHR5OwogICAgICAgIH0KICAgICAgfV0pOwogICAgICByZXR1cm4gU3RhdGlzdGljc1N0b3JhZ2U7CiAgICB9KCk7CgogICAgdmFyIFN0YXRpc3RpY3NTZW5kZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgIGZ1bmN0aW9uIFN0YXRpc3RpY3NTZW5kZXIodXJsLCBsb2dnZXIpIHsKICAgICAgICBjbGFzc0NhbGxDaGVjayh0aGlzLCBTdGF0aXN0aWNzU2VuZGVyKTsKCiAgICAgICAgdGhpcy51cmwgPSB1cmw7CiAgICAgICAgdGhpcy5sb2dnZXIgPSBsb2dnZXI7CiAgICAgIH0KCiAgICAgIGNyZWF0ZUNsYXNzKFN0YXRpc3RpY3NTZW5kZXIsIFt7CiAgICAgICAga2V5OiAnc2VuZCcsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIHNlbmQoZGF0YSwgZXJyb3JIYW5kbGVyKSB7CiAgICAgICAgICB2YXIgbG9nZ2VyID0gdGhpcy5sb2dnZXI7CgogICAgICAgICAgaWYgKG5hdmlnYXRvci5vbkxpbmUgPT09IGZhbHNlKSB7CiAgICAgICAgICAgIGxvZ2dlci5kZWJ1ZygiT2ZmbGluZSwgY2FuJ3Qgc2VuZCIpOwogICAgICAgICAgICBlcnJvckhhbmRsZXIoKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQogICAgICAgICAgbG9nZ2VyLmRlYnVnKCJTZW5kaW5nIGRhdGEgdG8gIiArIHRoaXMudXJsKTsKCiAgICAgICAgICB2YXIgcmVxID0gbmV3IFhNTEh0dHBSZXF1ZXN0KCk7CiAgICAgICAgICByZXEud2l0aENyZWRlbnRpYWxzID0gdHJ1ZTsKICAgICAgICAgIHJlcS5hZGRFdmVudExpc3RlbmVyKCJsb2FkIiwgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAvLyBTdGF0cyBzZW50LCBub3RoaW5nIG1vcmUgdG8gZG8KICAgICAgICAgICAgbG9nZ2VyLmRlYnVnKCJSZXNwb25zZTogIiArIHJlcS5yZXNwb25zZVRleHQpOwogICAgICAgICAgfSk7CiAgICAgICAgICByZXEuYWRkRXZlbnRMaXN0ZW5lcigiZXJyb3IiLCBmdW5jdGlvbiAoKSB7CiAgICAgICAgICAgIGxvZ2dlci5kZWJ1ZygiU2VuZCBmYWlsZWQiKTsKICAgICAgICAgICAgZXJyb3JIYW5kbGVyKCk7CiAgICAgICAgICB9KTsKICAgICAgICAgIHJlcS5hZGRFdmVudExpc3RlbmVyKCJhYm9ydCIsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgbG9nZ2VyLmRlYnVnKCJTZW5kIGFib3J0ZWQiKTsKICAgICAgICAgICAgZXJyb3JIYW5kbGVyKCk7CiAgICAgICAgICB9KTsKICAgICAgICAgIHJlcS5vcGVuKCJQT1NUIiwgdGhpcy51cmwpOwogICAgICAgICAgcmVxLnNldFJlcXVlc3RIZWFkZXIoIkNvbnRlbnQtVHlwZSIsICJhcHBsaWNhdGlvbi9qc29uIik7CiAgICAgICAgICByZXEuc2VuZChkYXRhKTsKICAgICAgICB9CiAgICAgIH1dKTsKICAgICAgcmV0dXJuIFN0YXRpc3RpY3NTZW5kZXI7CiAgICB9KCk7CgogICAgdmFyIFN0YXRpc3RpY3NMb2dnZXIgPSBmdW5jdGlvbiAoKSB7CiAgICAgIGZ1bmN0aW9uIFN0YXRpc3RpY3NMb2dnZXIoaWQpIHsKICAgICAgICBjbGFzc0NhbGxDaGVjayh0aGlzLCBTdGF0aXN0aWNzTG9nZ2VyKTsKCiAgICAgICAgdGhpcy5pZCA9IGlkOwogICAgICB9CgogICAgICBjcmVhdGVDbGFzcyhTdGF0aXN0aWNzTG9nZ2VyLCBbewogICAgICAgIGtleTogJ19pc0RlYnVnJywKICAgICAgICB2YWx1ZTogZnVuY3Rpb24gX2lzRGVidWcoKSB7CiAgICAgICAgICByZXR1cm4gbG9jYWxTdG9yYWdlLmdldEl0ZW0oInZhYWRpbi4iICsgdGhpcy5pZCArICIuZGVidWciKTsKICAgICAgICB9CiAgICAgIH0sIHsKICAgICAgICBrZXk6ICdkZWJ1ZycsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIGRlYnVnKG1zZykgewogICAgICAgICAgaWYgKHRoaXMuX2lzRGVidWcoKSkgewogICAgICAgICAgICBjb25zb2xlLmluZm8odGhpcy5pZCArICI6ICIgKyBtc2cpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfV0pOwogICAgICByZXR1cm4gU3RhdGlzdGljc0xvZ2dlcjsKICAgIH0oKTsKCiAgICB2YXIgVXNhZ2VTdGF0aXN0aWNzID0gZnVuY3Rpb24gKCkgewogICAgICBmdW5jdGlvbiBVc2FnZVN0YXRpc3RpY3MoKSB7CiAgICAgICAgY2xhc3NDYWxsQ2hlY2sodGhpcywgVXNhZ2VTdGF0aXN0aWNzKTsKCiAgICAgICAgdGhpcy5ub3cgPSBuZXcgRGF0ZSgpOwogICAgICAgIHRoaXMudGltZU5vdyA9IHRoaXMubm93LmdldFRpbWUoKTsKICAgICAgICB0aGlzLmdhdGhlckRlbGF5ID0gMTA7IC8vIERlbGF5IGJldHdlZW4gbG9hZGluZyB0aGlzIGZpbGUgYW5kIGdhdGhlcmluZyBzdGF0cwogICAgICAgIHRoaXMuaW5pdGlhbERlbGF5ID0gMjQgKiA2MCAqIDYwOwoKICAgICAgICB0aGlzLmxvZ2dlciA9IG5ldyBTdGF0aXN0aWNzTG9nZ2VyKCJzdGF0aXN0aWNzIik7CiAgICAgICAgdGhpcy5zdG9yYWdlID0gbmV3IFN0YXRpc3RpY3NTdG9yYWdlKCJ2YWFkaW4uc3RhdGlzdGljcy5iYXNrZXQiKTsKICAgICAgICB0aGlzLmdhdGhlcmVyID0gbmV3IFN0YXRpc3RpY3NHYXRoZXJlcih0aGlzLmxvZ2dlcik7CiAgICAgICAgdGhpcy5zZW5kZXIgPSBuZXcgU3RhdGlzdGljc1NlbmRlcigiaHR0cHM6Ly90b29scy52YWFkaW4uY29tL3VzYWdlLXN0YXRzL3N1Ym1pdCIsIHRoaXMubG9nZ2VyKTsKICAgICAgfQoKICAgICAgY3JlYXRlQ2xhc3MoVXNhZ2VTdGF0aXN0aWNzLCBbewogICAgICAgIGtleTogJ21heWJlR2F0aGVyQW5kU2VuZCcsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIG1heWJlR2F0aGVyQW5kU2VuZCgpIHsKICAgICAgICAgIHZhciBfdGhpcyA9IHRoaXM7CgogICAgICAgICAgaWYgKGxvY2FsU3RvcmFnZS5nZXRJdGVtKFVzYWdlU3RhdGlzdGljcy5vcHRPdXRLZXkpKSB7CiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuZ2F0aGVyZXIuZ2F0aGVyKHRoaXMuc3RvcmFnZSk7CiAgICAgICAgICBzZXRUaW1lb3V0KGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgX3RoaXMubWF5YmVTZW5kKCk7CiAgICAgICAgICB9LCB0aGlzLmdhdGhlckRlbGF5ICogMTAwMCk7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnbG90dGVyeScsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIGxvdHRlcnkoKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICAgIH0sIHsKICAgICAgICBrZXk6ICdjdXJyZW50TW9udGgnLAogICAgICAgIHZhbHVlOiBmdW5jdGlvbiBjdXJyZW50TW9udGgoKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5ub3cuZ2V0WWVhcigpICogMTIgKyB0aGlzLm5vdy5nZXRNb250aCgpOwogICAgICAgIH0KICAgICAgfSwgewogICAgICAgIGtleTogJ21heWJlU2VuZCcsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIG1heWJlU2VuZCgpIHsKICAgICAgICAgIHZhciBmaXJzdFVzZSA9IE51bWJlcihsb2NhbFN0b3JhZ2UuZ2V0SXRlbShVc2FnZVN0YXRpc3RpY3MuZmlyc3RVc2VLZXkpKTsKICAgICAgICAgIHZhciBtb250aFByb2Nlc3NlZCA9IE51bWJlcihsb2NhbFN0b3JhZ2UuZ2V0SXRlbShVc2FnZVN0YXRpc3RpY3MubW9udGhQcm9jZXNzZWRLZXkpKTsKCiAgICAgICAgICBpZiAoIWZpcnN0VXNlKSB7CiAgICAgICAgICAgIC8vIFVzZSBhIGdyYWNlIHBlcmlvZCB0byBhdm9pZCBpbnRlcmZlcmluZyB3aXRoIHRlc3RzLCBpbmNvZ25pdG8gbW9kZSBldGMKICAgICAgICAgICAgZmlyc3RVc2UgPSB0aGlzLnRpbWVOb3c7CiAgICAgICAgICAgIGxvY2FsU3RvcmFnZS5zZXRJdGVtKFVzYWdlU3RhdGlzdGljcy5maXJzdFVzZUtleSwgZmlyc3RVc2UpOwogICAgICAgICAgfQoKICAgICAgICAgIGlmICh0aGlzLnRpbWVOb3cgPCBmaXJzdFVzZSArIHRoaXMuaW5pdGlhbERlbGF5ICogMTAwMCkgewogICAgICAgICAgICB0aGlzLmxvZ2dlci5kZWJ1ZygiTm8gc3RhdGlzdGljcyB3aWxsIGJlIHNlbnQgdW50aWwgdGhlIGluaXRpYWwgZGVsYXkgb2YgIiArIHRoaXMuaW5pdGlhbERlbGF5ICsgInMgaGFzIHBhc3NlZCIpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBpZiAodGhpcy5jdXJyZW50TW9udGgoKSA8PSBtb250aFByb2Nlc3NlZCkgewogICAgICAgICAgICB0aGlzLmxvZ2dlci5kZWJ1ZygiVGhpcyBtb250aCBoYXMgYWxyZWFkeSBiZWVuIHByb2Nlc3NlZCIpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBsb2NhbFN0b3JhZ2Uuc2V0SXRlbShVc2FnZVN0YXRpc3RpY3MubW9udGhQcm9jZXNzZWRLZXksIHRoaXMuY3VycmVudE1vbnRoKCkpOwogICAgICAgICAgLy8gVXNlIHJhbmRvbSBzYW1wbGluZwogICAgICAgICAgaWYgKHRoaXMubG90dGVyeSgpKSB7CiAgICAgICAgICAgIHRoaXMubG9nZ2VyLmRlYnVnKCJDb25ncmF0dWxhdGlvbnMsIHdlIGhhdmUgYSB3aW5uZXIhIik7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLmxvZ2dlci5kZWJ1ZygiU29ycnksIG5vIHN0YXRzIGZyb20geW91IHRoaXMgdGltZSIpOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CgogICAgICAgICAgdGhpcy5zZW5kKCk7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnc2VuZCcsCiAgICAgICAgdmFsdWU6IGZ1bmN0aW9uIHNlbmQoKSB7CiAgICAgICAgICAvLyBFbnN1cmUgd2UgaGF2ZSB0aGUgbGF0ZXN0IGRhdGEKICAgICAgICAgIHRoaXMuZ2F0aGVyZXIuZ2F0aGVyKHRoaXMuc3RvcmFnZSk7CgogICAgICAgICAgLy8gUmVhZCwgc2VuZCBhbmQgY2xlYW4gdXAKICAgICAgICAgIHZhciBkYXRhID0gdGhpcy5zdG9yYWdlLnJlYWQoKTsKICAgICAgICAgIGRhdGFbImZpcnN0VXNlIl0gPSBOdW1iZXIobG9jYWxTdG9yYWdlLmdldEl0ZW0oVXNhZ2VTdGF0aXN0aWNzLmZpcnN0VXNlS2V5KSk7CiAgICAgICAgICBkYXRhWyJ1c2FnZVN0YXRpc3RpY3NWZXJzaW9uIl0gPSBVc2FnZVN0YXRpc3RpY3MudmVyc2lvbjsKICAgICAgICAgIHZhciBpbmZvID0gJ1RoaXMgcmVxdWVzdCBjb250YWlucyB1c2FnZSBzdGF0aXN0aWNzIGdhdGhlcmVkIGZyb20gdGhlIGFwcGxpY2F0aW9uIHJ1bm5pbmcgaW4gZGV2ZWxvcG1lbnQgbW9kZS4gXG5cblN0YXRpc3RpY3MgZ2F0aGVyaW5nIGlzIGF1dG9tYXRpY2FsbHkgZGlzYWJsZWQgYW5kIGV4Y2x1ZGVkIGZyb20gcHJvZHVjdGlvbiBidWlsZHMuXG5cbkZvciBkZXRhaWxzIGFuZCB0byBvcHQtb3V0LCBzZWUgaHR0cHM6Ly9naXRodWIuY29tL3ZhYWRpbi92YWFkaW4tdXNhZ2Utc3RhdGlzdGljcy5cblxuXG5cbic7CiAgICAgICAgICB2YXIgc2VsZiA9IHRoaXM7CiAgICAgICAgICB0aGlzLnNlbmRlci5zZW5kKGluZm8gKyBKU09OLnN0cmluZ2lmeShkYXRhKSwgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAvLyBSZXZlcnQgdGhlICdtb250aCBwcm9jZXNzZWQnIGZsYWcKICAgICAgICAgICAgbG9jYWxTdG9yYWdlLnNldEl0ZW0oVXNhZ2VTdGF0aXN0aWNzLm1vbnRoUHJvY2Vzc2VkS2V5LCBzZWxmLmN1cnJlbnRNb250aCgpIC0gMSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH1dLCBbewogICAgICAgIGtleTogJ3ZlcnNpb24nLAogICAgICAgIGdldDogZnVuY3Rpb24gZ2V0JDEoKSB7CiAgICAgICAgICByZXR1cm4gJzIuMS4wJzsKICAgICAgICB9CiAgICAgIH0sIHsKICAgICAgICBrZXk6ICdmaXJzdFVzZUtleScsCiAgICAgICAgZ2V0OiBmdW5jdGlvbiBnZXQkMSgpIHsKICAgICAgICAgIHJldHVybiAndmFhZGluLnN0YXRpc3RpY3MuZmlyc3R1c2UnOwogICAgICAgIH0KICAgICAgfSwgewogICAgICAgIGtleTogJ21vbnRoUHJvY2Vzc2VkS2V5JywKICAgICAgICBnZXQ6IGZ1bmN0aW9uIGdldCQxKCkgewogICAgICAgICAgcmV0dXJuICd2YWFkaW4uc3RhdGlzdGljcy5tb250aFByb2Nlc3NlZCc7CiAgICAgICAgfQogICAgICB9LCB7CiAgICAgICAga2V5OiAnb3B0T3V0S2V5JywKICAgICAgICBnZXQ6IGZ1bmN0aW9uIGdldCQxKCkgewogICAgICAgICAgcmV0dXJuICd2YWFkaW4uc3RhdGlzdGljcy5vcHRvdXQnOwogICAgICAgIH0KICAgICAgfV0pOwogICAgICByZXR1cm4gVXNhZ2VTdGF0aXN0aWNzOwogICAgfSgpOwoKICAgIHRyeSB7CiAgICAgIHdpbmRvdy5WYWFkaW4gPSB3aW5kb3cuVmFhZGluIHx8IHt9OwogICAgICB3aW5kb3cuVmFhZGluLnVzYWdlU3RhdHNDaGVja2VyID0gd2luZG93LlZhYWRpbi51c2FnZVN0YXRzQ2hlY2tlciB8fCBuZXcgVXNhZ2VTdGF0aXN0aWNzKCk7CiAgICAgIHdpbmRvdy5WYWFkaW4udXNhZ2VTdGF0c0NoZWNrZXIubWF5YmVHYXRoZXJBbmRTZW5kKCk7CiAgICB9IGNhdGNoIChlKSB7CiAgICAgIC8vIEludGVudGlvbmFsbHkgaWdub3JlZCBhcyB0aGlzIGlzIG5vdCBhIHByb2JsZW0gaW4gdGhlIGFwcCBiZWluZyBkZXZlbG9wZWQKICAgIH0KCiAgICB9KCkpOwoKICAgICAgdmFhZGluLWRldi1tb2RlOmVuZCAqKi8KICAgIH0KCiAgICBjb25zdCB1c2FnZVN0YXRpc3RpY3MgPSBmdW5jdGlvbigpIHsKICAgICAgaWYgKHR5cGVvZiBydW5JZkRldmVsb3BtZW50TW9kZSA9PT0gJ2Z1bmN0aW9uJykgewogICAgICAgIHJldHVybiBydW5JZkRldmVsb3BtZW50TW9kZShtYXliZUdhdGhlckFuZFNlbmRTdGF0cyk7CiAgICAgIH0KICAgIH07CgogICAgaWYgKCF3aW5kb3cuVmFhZGluKSB7CiAgICAgIHdpbmRvd1snVmFhZGluJ10gPSB7fTsKICAgIH0KCiAgICAvKioKICAgICAqIEFycmF5IG9mIFZhYWRpbiBjdXN0b20gZWxlbWVudCBjbGFzc2VzIHRoYXQgaGF2ZSBiZWVuIGZpbmFsaXplZC4KICAgICAqLwogICAgd2luZG93WydWYWFkaW4nXS5yZWdpc3RyYXRpb25zID0gd2luZG93LlZhYWRpbi5yZWdpc3RyYXRpb25zIHx8IFtdOwoKICAgIC8vIFVzZSB0aGUgaGFjayB0byBwcmV2ZW50IHBvbHltZXItbW9kdWxpemVyIGZyb20gY29udmVydGluZyB0byBleHBvcnRzCiAgICB3aW5kb3dbJ1ZhYWRpbiddLmRldmVsb3BtZW50TW9kZUNhbGxiYWNrID0gd2luZG93LlZhYWRpbi5kZXZlbG9wbWVudE1vZGVDYWxsYmFjayB8fCB7fTsKICAgIHdpbmRvd1snVmFhZGluJ10uZGV2ZWxvcG1lbnRNb2RlQ2FsbGJhY2tbJ3ZhYWRpbi11c2FnZS1zdGF0aXN0aWNzJ10gPSBmdW5jdGlvbigpIHsKICAgICAgaWYgKHVzYWdlU3RhdGlzdGljcykgewogICAgICAgIHVzYWdlU3RhdGlzdGljcygpOwogICAgICB9CiAgICB9OwoKICAgIGxldCBzdGF0c0pvYjsKCiAgICBjb25zdCByZWdpc3RlcmVkID0gbmV3IFNldCgpOwoKICAgIC8qKgogICAgICogQHBvbHltZXJNaXhpbgogICAgICogQG1peGVzIERpck1peGluCiAgICAgKi8KICAgIGNvbnN0IEVsZW1lbnRNaXhpbiQxID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBWYWFkaW5FbGVtZW50TWl4aW4gZXh0ZW5kcyBEaXJNaXhpbiQxKHN1cGVyQ2xhc3MpIHsKICAgICAgLyoqIEBwcm90ZWN0ZWQgKi8KICAgICAgc3RhdGljIGZpbmFsaXplKCkgewogICAgICAgIHN1cGVyLmZpbmFsaXplKCk7CgogICAgICAgIGNvbnN0IHtpc30gPSB0aGlzOwoKICAgICAgICAvLyBSZWdpc3RlcnMgYSBjbGFzcyBwcm90b3R5cGUgZm9yIHRlbGVtZXRyeSBwdXJwb3Nlcy4KICAgICAgICBpZiAoaXMgJiYgIXJlZ2lzdGVyZWQuaGFzKGlzKSkgewogICAgICAgICAgd2luZG93LlZhYWRpbi5yZWdpc3RyYXRpb25zLnB1c2godGhpcyk7CiAgICAgICAgICByZWdpc3RlcmVkLmFkZChpcyk7CgogICAgICAgICAgaWYgKHdpbmRvdy5WYWFkaW4uZGV2ZWxvcG1lbnRNb2RlQ2FsbGJhY2spIHsKICAgICAgICAgICAgc3RhdHNKb2IgPSBEZWJvdW5jZXIuZGVib3VuY2Uoc3RhdHNKb2IsCiAgICAgICAgICAgICAgaWRsZVBlcmlvZCwgKCkgPT4gewogICAgICAgICAgICAgICAgd2luZG93LlZhYWRpbi5kZXZlbG9wbWVudE1vZGVDYWxsYmFja1sndmFhZGluLXVzYWdlLXN0YXRpc3RpY3MnXSgpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgKTsKICAgICAgICAgICAgZW5xdWV1ZURlYm91bmNlcihzdGF0c0pvYik7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICBzdXBlcigpOwogICAgICAgIGlmIChkb2N1bWVudC5kb2N0eXBlID09PSBudWxsKSB7CiAgICAgICAgICBjb25zb2xlLndhcm4oCiAgICAgICAgICAgICdWYWFkaW4gY29tcG9uZW50cyByZXF1aXJlIHRoZSAic3RhbmRhcmRzIG1vZGUiIGRlY2xhcmF0aW9uLiBQbGVhc2UgYWRkIDwhRE9DVFlQRSBodG1sPiB0byB0aGUgSFRNTCBkb2N1bWVudC4nCiAgICAgICAgICApOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIGA8dmFhZGluLWNoZWNrYm94PmAgaXMgYSBXZWIgQ29tcG9uZW50IGZvciBjdXN0b21pemVkIGNoZWNrYm94ZXMuCiAgICAgKgogICAgICogYGBgaHRtbAogICAgICogPHZhYWRpbi1jaGVja2JveD4KICAgICAqICAgTWFrZSBteSBwcm9maWxlIHZpc2libGUKICAgICAqIDwvdmFhZGluLWNoZWNrYm94PgogICAgICogYGBgCiAgICAgKgogICAgICogIyMjIFN0eWxpbmcKICAgICAqCiAgICAgKiBUaGUgZm9sbG93aW5nIHNoYWRvdyBET00gcGFydHMgYXJlIGF2YWlsYWJsZSBmb3Igc3R5bGluZzoKICAgICAqCiAgICAgKiBQYXJ0IG5hbWUgICAgICAgICB8IERlc2NyaXB0aW9uCiAgICAgKiAtLS0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLS0tLQogICAgICogYGNoZWNrYm94YCAgICAgICAgfCBUaGUgd3JhcHBlciBlbGVtZW50IGZvciB0aGUgbmF0aXZlIDxpbnB1dCB0eXBlPSJjaGVja2JveCI+CiAgICAgKiBgbGFiZWxgICAgICAgICAgICB8IFRoZSB3cmFwcGVyIGVsZW1lbnQgaW4gd2hpY2ggdGhlIGNvbXBvbmVudCdzIGNoaWxkcmVuLCBuYW1lbHkgdGhlIGxhYmVsLCBpcyBzbG90dGVkCiAgICAgKgogICAgICogVGhlIGZvbGxvd2luZyBzdGF0ZSBhdHRyaWJ1dGVzIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CiAgICAgKgogICAgICogQXR0cmlidXRlICAgIHwgRGVzY3JpcHRpb24gfCBQYXJ0IG5hbWUKICAgICAqIC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0tLQogICAgICogYGFjdGl2ZWAgICAgIHwgU2V0IHdoZW4gdGhlIGNoZWNrYm94IGlzIHByZXNzZWQgZG93biwgZWl0aGVyIHdpdGggbW91c2UsIHRvdWNoIG9yIHRoZSBrZXlib2FyZC4gfCBgOmhvc3RgCiAgICAgKiBgZGlzYWJsZWRgICAgfCBTZXQgd2hlbiB0aGUgY2hlY2tib3ggaXMgZGlzYWJsZWQuIHwgYDpob3N0YAogICAgICogYGZvY3VzLXJpbmdgIHwgU2V0IHdoZW4gdGhlIGNoZWNrYm94IGlzIGZvY3VzZWQgdXNpbmcgdGhlIGtleWJvYXJkLiB8IGA6aG9zdGAKICAgICAqIGBmb2N1c2VkYCAgICB8IFNldCB3aGVuIHRoZSBjaGVja2JveCBpcyBmb2N1c2VkLiB8IGA6aG9zdGAKICAgICAqIGBpbmRldGVybWluYXRlYCB8IFNldCB3aGVuIHRoZSBjaGVja2JveCBpcyBpbiBpbmRldGVybWluYXRlIG1vZGUuIHwgYDpob3N0YAogICAgICogYGNoZWNrZWRgIHwgU2V0IHdoZW4gdGhlIGNoZWNrYm94IGlzIGNoZWNrZWQuIHwgYDpob3N0YAogICAgICogYGVtcHR5YCB8IFNldCB3aGVuIHRoZXJlIGlzIG5vIGxhYmVsIHByb3ZpZGVkLiB8IGBsYWJlbGAKICAgICAqCiAgICAgKiBTZWUgW1RoZW1hYmxlTWl4aW4g4oCTIGhvdyB0byBhcHBseSBzdHlsZXMgZm9yIHNoYWRvdyBwYXJ0c10oaHR0cHM6Ly9naXRodWIuY29tL3ZhYWRpbi92YWFkaW4tdGhlbWFibGUtbWl4aW4vd2lraSkKICAgICAqCiAgICAgKiBAZXh0ZW5kcyBQb2x5bWVyRWxlbWVudAogICAgICogQG1peGVzIEVsZW1lbnRNaXhpbgogICAgICogQG1peGVzIENvbnRyb2xTdGF0ZU1peGluCiAgICAgKiBAbWl4ZXMgVGhlbWFibGVNaXhpbgogICAgICogQG1peGVzIEdlc3R1cmVFdmVudExpc3RlbmVycwogICAgICogQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAgKi8KICAgIGNsYXNzIENoZWNrYm94RWxlbWVudCBleHRlbmRzCiAgICAgIEVsZW1lbnRNaXhpbiQxKAogICAgICAgIENvbnRyb2xTdGF0ZU1peGluKAogICAgICAgICAgVGhlbWFibGVNaXhpbigKICAgICAgICAgICAgR2VzdHVyZUV2ZW50TGlzdGVuZXJzKFBvbHltZXJFbGVtZW50KSkpKSB7CiAgICAgIHN0YXRpYyBnZXQgdGVtcGxhdGUoKSB7CiAgICAgICAgcmV0dXJuIGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7CiAgICAgIH0KCiAgICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgICB9CgogICAgICBsYWJlbCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWZsZXg7CiAgICAgICAgYWxpZ24taXRlbXM6IGJhc2VsaW5lOwogICAgICAgIG91dGxpbmU6IG5vbmU7CiAgICAgIH0KCiAgICAgIFtwYXJ0PSJjaGVja2JveCJdIHsKICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrOwogICAgICAgIGZsZXg6IG5vbmU7CiAgICAgIH0KCiAgICAgIGlucHV0W3R5cGU9ImNoZWNrYm94Il0gewogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB0b3A6IDA7CiAgICAgICAgbGVmdDogMDsKICAgICAgICByaWdodDogMDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICBjdXJzb3I6IGluaGVyaXQ7CiAgICAgICAgbWFyZ2luOiAwOwogICAgICB9CgogICAgICA6aG9zdChbZGlzYWJsZWRdKSB7CiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKICAgICAgfQogICAgPC9zdHlsZT4KCiAgICA8bGFiZWw+CiAgICAgIDxzcGFuIHBhcnQ9ImNoZWNrYm94Ij4KICAgICAgICA8aW5wdXQgdHlwZT0iY2hlY2tib3giIGNoZWNrZWQ9Int7Y2hlY2tlZDo6Y2hhbmdlfX0iIGRpc2FibGVkXCQ9IltbZGlzYWJsZWRdXSIgaW5kZXRlcm1pbmF0ZT0ie3tpbmRldGVybWluYXRlOjpjaGFuZ2V9fSIgcm9sZT0icHJlc2VudGF0aW9uIiB0YWJpbmRleD0iLTEiPgogICAgICA8L3NwYW4+CgogICAgICA8c3BhbiBwYXJ0PSJsYWJlbCI+CiAgICAgICAgPHNsb3Q+PC9zbG90PgogICAgICA8L3NwYW4+CiAgICA8L2xhYmVsPgpgOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IGlzKCkgewogICAgICAgIHJldHVybiAndmFhZGluLWNoZWNrYm94JzsKICAgICAgfQoKICAgICAgc3RhdGljIGdldCB2ZXJzaW9uKCkgewogICAgICAgIHJldHVybiAnMi4zLjAnOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogVHJ1ZSBpZiB0aGUgY2hlY2tib3ggaXMgY2hlY2tlZC4KICAgICAgICAgICAqLwogICAgICAgICAgY2hlY2tlZDogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfY2hlY2tlZENoYW5nZWQnLAogICAgICAgICAgICByZWZsZWN0VG9BdHRyaWJ1dGU6IHRydWUKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBJbmRldGVybWluYXRlIHN0YXRlIG9mIHRoZSBjaGVja2JveCB3aGVuIGl0J3MgbmVpdGhlciBjaGVja2VkIG5vciB1bmNoZWNrZWQsIGJ1dCB1bmRldGVybWluZWQuCiAgICAgICAgICAgKiBodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9IVE1ML0VsZW1lbnQvaW5wdXQvY2hlY2tib3gjSW5kZXRlcm1pbmF0ZV9zdGF0ZV9jaGVja2JveGVzCiAgICAgICAgICAgKi8KICAgICAgICAgIGluZGV0ZXJtaW5hdGU6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ19pbmRldGVybWluYXRlQ2hhbmdlZCcsCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgICAgdmFsdWU6IGZhbHNlCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogVGhlIHZhbHVlIGdpdmVuIHRvIHRoZSBkYXRhIHN1Ym1pdHRlZCB3aXRoIHRoZSBjaGVja2JveCdzIG5hbWUgdG8gdGhlIHNlcnZlciB3aGVuIHRoZSBjb250cm9sIGlzIGluc2lkZSBhIGZvcm0uCiAgICAgICAgICAgKi8KICAgICAgICAgIHZhbHVlOiB7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgdmFsdWU6ICdvbicKICAgICAgICAgIH0sCgogICAgICAgICAgX25hdGl2ZUNoZWNrYm94OiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdAogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CiAgICAgICAgLyoqCiAgICAgICAgICogQHR5cGUge3N0cmluZ30KICAgICAgICAgKiBOYW1lIG9mIHRoZSBlbGVtZW50LgogICAgICAgICAqLwogICAgICAgIHRoaXMubmFtZTsKICAgICAgfQoKICAgICAgZ2V0IG5hbWUoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuY2hlY2tlZCA/IHRoaXMuX3N0b3JlZE5hbWUgOiAnJzsKICAgICAgfQoKICAgICAgc2V0IG5hbWUobmFtZSkgewogICAgICAgIHRoaXMuX3N0b3JlZE5hbWUgPSBuYW1lOwogICAgICB9CgogICAgICByZWFkeSgpIHsKICAgICAgICBzdXBlci5yZWFkeSgpOwoKICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgncm9sZScsICdjaGVja2JveCcpOwoKICAgICAgICB0aGlzLl9uYXRpdmVDaGVja2JveCA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yKCdpbnB1dFt0eXBlPSJjaGVja2JveCJdJyk7CgogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCB0aGlzLl9oYW5kbGVDbGljay5iaW5kKHRoaXMpKTsKCiAgICAgICAgdGhpcy5fYWRkQWN0aXZlTGlzdGVuZXJzKCk7CgogICAgICAgIGNvbnN0IGF0dHJOYW1lID0gdGhpcy5nZXRBdHRyaWJ1dGUoJ25hbWUnKTsKICAgICAgICBpZiAoYXR0ck5hbWUpIHsKICAgICAgICAgIHRoaXMubmFtZSA9IGF0dHJOYW1lOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3IoJ1twYXJ0fj0ibGFiZWwiXScpLnF1ZXJ5U2VsZWN0b3IoJ3Nsb3QnKQogICAgICAgICAgLmFkZEV2ZW50TGlzdGVuZXIoJ3Nsb3RjaGFuZ2UnLCB0aGlzLl91cGRhdGVMYWJlbEF0dHJpYnV0ZS5iaW5kKHRoaXMpKTsKCiAgICAgICAgdGhpcy5fdXBkYXRlTGFiZWxBdHRyaWJ1dGUoKTsKICAgICAgfQoKICAgICAgX3VwZGF0ZUxhYmVsQXR0cmlidXRlKCkgewogICAgICAgIGNvbnN0IGxhYmVsID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3IoJ1twYXJ0fj0ibGFiZWwiXScpOwogICAgICAgIGNvbnN0IGFzc2lnbmVkTm9kZXMgPSBsYWJlbC5maXJzdEVsZW1lbnRDaGlsZC5hc3NpZ25lZE5vZGVzKCk7CiAgICAgICAgaWYgKHRoaXMuX2lzQXNzaWduZWROb2Rlc0VtcHR5KGFzc2lnbmVkTm9kZXMpKSB7CiAgICAgICAgICBsYWJlbC5zZXRBdHRyaWJ1dGUoJ2VtcHR5JywgJycpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBsYWJlbC5yZW1vdmVBdHRyaWJ1dGUoJ2VtcHR5Jyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfaXNBc3NpZ25lZE5vZGVzRW1wdHkobm9kZXMpIHsKICAgICAgICAvLyBUaGUgYXNzaWduZWQgbm9kZXMgY29uc2lkZXJlZCB0byBiZSBlbXB0eSBpZiB0aGVyZSBpcyBubyBzbG90dGVkIGNvbnRlbnQgb3Igb25seSBvbmUgZW1wdHkgdGV4dCBub2RlCiAgICAgICAgcmV0dXJuIG5vZGVzLmxlbmd0aCA9PT0gMCB8fAogICAgICAgICAgICAgIChub2Rlcy5sZW5ndGggPT0gMQogICAgICAgICAgICAgICYmIG5vZGVzWzBdLm5vZGVUeXBlID09IE5vZGUuVEVYVF9OT0RFCiAgICAgICAgICAgICAgJiYgbm9kZXNbMF0udGV4dENvbnRlbnQudHJpbSgpID09PSAnJyk7CiAgICAgIH0KCiAgICAgIF9jaGVja2VkQ2hhbmdlZChjaGVja2VkKSB7CiAgICAgICAgaWYgKHRoaXMuaW5kZXRlcm1pbmF0ZSkgewogICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtY2hlY2tlZCcsICdtaXhlZCcpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1jaGVja2VkJywgQm9vbGVhbihjaGVja2VkKSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfaW5kZXRlcm1pbmF0ZUNoYW5nZWQoaW5kZXRlcm1pbmF0ZSkgewogICAgICAgIGlmIChpbmRldGVybWluYXRlKSB7CiAgICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1jaGVja2VkJywgJ21peGVkJyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdhcmlhLWNoZWNrZWQnLCB0aGlzLmNoZWNrZWQpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2FkZEFjdGl2ZUxpc3RlbmVycygpIHsKICAgICAgICAvLyBET1dOCiAgICAgICAgdGhpcy5fYWRkRXZlbnRMaXN0ZW5lclRvTm9kZSh0aGlzLCAnZG93bicsIChlKSA9PiB7CiAgICAgICAgICBpZiAodGhpcy5fX2ludGVyYWN0aW9uc0FsbG93ZWQoZSkpIHsKICAgICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FjdGl2ZScsICcnKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgLy8gVVAKICAgICAgICB0aGlzLl9hZGRFdmVudExpc3RlbmVyVG9Ob2RlKHRoaXMsICd1cCcsICgpID0+IHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhY3RpdmUnKSk7CgogICAgICAgIC8vIEtFWURPV04KICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2tleWRvd24nLCBlID0+IHsKICAgICAgICAgIGlmICh0aGlzLl9faW50ZXJhY3Rpb25zQWxsb3dlZChlKSAmJiBlLmtleUNvZGUgPT09IDMyKSB7CiAgICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FjdGl2ZScsICcnKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgLy8gS0VZVVAKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2tleXVwJywgZSA9PiB7CiAgICAgICAgICBpZiAodGhpcy5fX2ludGVyYWN0aW9uc0FsbG93ZWQoZSkgJiYgZS5rZXlDb2RlID09PSAzMikgewogICAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICAgIHRoaXMuX3RvZ2dsZUNoZWNrZWQoKTsKICAgICAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoJ2FjdGl2ZScpOwoKICAgICAgICAgICAgaWYgKHRoaXMuaW5kZXRlcm1pbmF0ZSkgewogICAgICAgICAgICAgIHRoaXMuaW5kZXRlcm1pbmF0ZSA9IGZhbHNlOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIC8qKiBAcHJvdGVjdGVkICovCiAgICAgIGdldCBmb2N1c0VsZW1lbnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yKCdpbnB1dCcpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVHJ1ZSBpZiB1c2VycycgaW50ZXJhY3Rpb25zIChtb3VzZSBvciBrZXlib2FyZCkKICAgICAgICogc2hvdWxkIHRvZ2dsZSB0aGUgY2hlY2tib3gKICAgICAgICovCiAgICAgIF9faW50ZXJhY3Rpb25zQWxsb3dlZChlKSB7CiAgICAgICAgaWYgKHRoaXMuZGlzYWJsZWQpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CgogICAgICAgIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS92YWFkaW4vdmFhZGluLWNoZWNrYm94L2lzc3Vlcy82MwogICAgICAgIGlmIChlLnRhcmdldC5sb2NhbE5hbWUgPT09ICdhJykgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KCiAgICAgIF9oYW5kbGVDbGljayhlKSB7CiAgICAgICAgaWYgKHRoaXMuX19pbnRlcmFjdGlvbnNBbGxvd2VkKGUpKSB7CiAgICAgICAgICBpZiAoIXRoaXMuaW5kZXRlcm1pbmF0ZSkgewogICAgICAgICAgICBpZiAoZS5jb21wb3NlZFBhdGgoKVswXSAhPT0gdGhpcy5fbmF0aXZlQ2hlY2tib3gpIHsKICAgICAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQ2hlY2tlZCgpOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAvKgogICAgICAgICAgICAgKiBSZXF1aXJlZCBmb3IgSUUgMTEgYW5kIEVkZ2UuCiAgICAgICAgICAgICAqIFNlZSBpc3N1ZSBoZXJlOiBodHRwczovL2RldmVsb3Blci5taWNyb3NvZnQuY29tL2VuLXVzL21pY3Jvc29mdC1lZGdlL3BsYXRmb3JtL2lzc3Vlcy83MzQ0NDE4LwogICAgICAgICAgICAgKi8KICAgICAgICAgICAgdGhpcy5pbmRldGVybWluYXRlID0gZmFsc2U7CiAgICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQ2hlY2tlZCgpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgX3RvZ2dsZUNoZWNrZWQoKSB7CiAgICAgICAgdGhpcy5jaGVja2VkID0gIXRoaXMuY2hlY2tlZDsKICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjaGFuZ2UnLCB7Y29tcG9zZWQ6IGZhbHNlLCBidWJibGVzOiB0cnVlfSkpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogRmlyZWQgd2hlbiB0aGUgdXNlciBjb21taXRzIGEgdmFsdWUgY2hhbmdlLgogICAgICAgKgogICAgICAgKiBAZXZlbnQgY2hhbmdlCiAgICAgICAqLwogICAgfQoKICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZShDaGVja2JveEVsZW1lbnQuaXMsIENoZWNrYm94RWxlbWVudCk7CgogICAgY29uc3QgJF9kb2N1bWVudENvbnRhaW5lciRjID0gaHRtbGA8ZG9tLW1vZHVsZSBpZD0ibHVtby1ncmlkIiB0aGVtZS1mb3I9InZhYWRpbi1ncmlkIj4KICA8dGVtcGxhdGU+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBmb250LWZhbWlseTogdmFyKC0tbHVtby1mb250LWZhbWlseSk7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZS1tKTsKICAgICAgICBsaW5lLWhlaWdodDogdmFyKC0tbHVtby1saW5lLWhlaWdodC1zKTsKICAgICAgICBjb2xvcjogdmFyKC0tbHVtby1ib2R5LXRleHQtY29sb3IpOwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWx1bW8tYmFzZS1jb2xvcik7CiAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgICAtd2Via2l0LXRleHQtc2l6ZS1hZGp1c3Q6IDEwMCU7CiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiB0cmFuc3BhcmVudDsKICAgICAgICAtd2Via2l0LWZvbnQtc21vb3RoaW5nOiBhbnRpYWxpYXNlZDsKICAgICAgICAtbW96LW9zeC1mb250LXNtb290aGluZzogZ3JheXNjYWxlOwoKICAgICAgICAvKiBGb3IgaW50ZXJuYWwgdXNlIG9ubHkgKi8KICAgICAgICAtLV9sdW1vLWdyaWQtYm9yZGVyLWNvbG9yOiB2YXIoLS1sdW1vLWNvbnRyYXN0LTIwcGN0KTsKICAgICAgICAtLV9sdW1vLWdyaWQtc2Vjb25kYXJ5LWJvcmRlci1jb2xvcjogdmFyKC0tbHVtby1jb250cmFzdC0xMHBjdCk7CiAgICAgICAgLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aDogMXB4OwogICAgICAgIC0tX2x1bW8tZ3JpZC1zZWxlY3RlZC1yb3ctY29sb3I6IHZhcigtLWx1bW8tcHJpbWFyeS1jb2xvci0xMHBjdCk7CiAgICAgIH0KCiAgICAgIC8qIE5vIChvdXRlcikgYm9yZGVyICovCgogICAgICA6aG9zdCg6bm90KFt0aGVtZX49Im5vLWJvcmRlciJdKSkgewogICAgICAgIGJvcmRlcjogdmFyKC0tX2x1bW8tZ3JpZC1ib3JkZXItd2lkdGgpIHNvbGlkIHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLWNvbG9yKTsKICAgICAgfQoKICAgICAgLyogQ2VsbCBzdHlsZXMgKi8KCiAgICAgIFtwYXJ0fj0iY2VsbCJdIHsKICAgICAgICBtaW4taGVpZ2h0OiB2YXIoLS1sdW1vLXNpemUtbSk7CiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogdmFyKC0tbHVtby1iYXNlLWNvbG9yKTsKICAgICAgfQoKICAgICAgW3BhcnR+PSJjZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCkgewogICAgICAgIGN1cnNvcjogZGVmYXVsdDsKICAgICAgICBwYWRkaW5nOiB2YXIoLS1sdW1vLXNwYWNlLXhzKSB2YXIoLS1sdW1vLXNwYWNlLW0pOwogICAgICB9CgogICAgICAvKiBBcHBseSByb3cgYm9yZGVycyBieSBkZWZhdWx0IGFuZCBpbnRyb2R1Y2UgdGhlICJuby1yb3ctYm9yZGVycyIgdmFyaWFudCAqLwogICAgICA6aG9zdCg6bm90KFt0aGVtZX49Im5vLXJvdy1ib3JkZXJzIl0pKSBbcGFydH49ImNlbGwiXTpub3QoW3BhcnR+PSJkZXRhaWxzLWNlbGwiXSkgewogICAgICAgIGJvcmRlci10b3A6IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLXdpZHRoKSBzb2xpZCB2YXIoLS1fbHVtby1ncmlkLXNlY29uZGFyeS1ib3JkZXItY29sb3IpOwogICAgICB9CgogICAgICAvKiBIaWRlIGZpcnN0IGJvZHkgcm93IHRvcCBib3JkZXIgKi8KICAgICAgOmhvc3QoOm5vdChbdGhlbWV+PSJuby1yb3ctYm9yZGVycyJdKSkgW3BhcnQ9InJvdyJdW2ZpcnN0XSBbcGFydH49ImNlbGwiXTpub3QoW3BhcnR+PSJkZXRhaWxzLWNlbGwiXSkgewogICAgICAgIGJvcmRlci10b3A6IDA7CiAgICAgICAgbWluLWhlaWdodDogY2FsYyh2YXIoLS1sdW1vLXNpemUtbSkgLSB2YXIoLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aCkpOwogICAgICB9CgogICAgICAvKiBGb2N1cy1yaW5nICovCgogICAgICBbcGFydH49ImNlbGwiXTpmb2N1cyB7CiAgICAgICAgb3V0bGluZTogbm9uZTsKICAgICAgfQoKICAgICAgOmhvc3QoW25hdmlnYXRpbmddKSBbcGFydH49ImNlbGwiXTpmb2N1czo6YmVmb3JlIHsKICAgICAgICBjb250ZW50OiAiIjsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGJveC1zaGFkb3c6IGluc2V0IDAgMCAwIDJweCB2YXIoLS1sdW1vLXByaW1hcnktY29sb3ItNTBwY3QpOwogICAgICB9CgogICAgICAvKiBEcmFnIGFuZCBEcm9wIHN0eWxlcyAqLwogICAgICA6aG9zdChbZHJhZ292ZXJdKTo6YWZ0ZXIgewogICAgICAgIGNvbnRlbnQ6ICIiOwogICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgICAgICB6LWluZGV4OiAxMDA7CiAgICAgICAgdG9wOiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGJveC1zaGFkb3c6IGluc2V0IDAgMCAwIDJweCB2YXIoLS1sdW1vLXByaW1hcnktY29sb3ItNTBwY3QpOwogICAgICB9CgogICAgICBbcGFydH49InJvdyJdW2RyYWdvdmVyXSB7CiAgICAgICAgei1pbmRleDogMTAwICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIFtwYXJ0fj0icm93Il1bZHJhZ292ZXJdIFtwYXJ0fj0iY2VsbCJdIHsKICAgICAgICBvdmVyZmxvdzogdmlzaWJsZTsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkcmFnb3Zlcl0gW3BhcnR+PSJjZWxsIl06OmFmdGVyIHsKICAgICAgICBjb250ZW50OiAiIjsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgdG9wOiAwOwogICAgICAgIHJpZ2h0OiAwOwogICAgICAgIGJvdHRvbTogMDsKICAgICAgICBsZWZ0OiAwOwogICAgICAgIGhlaWdodDogY2FsYyh2YXIoLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aCkgKyAycHgpOwogICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLWx1bW8tcHJpbWFyeS1jb2xvci01MHBjdCk7CiAgICAgIH0KCiAgICAgIDpob3N0KFt0aGVtZX49Im5vLXJvdy1ib3JkZXJzIl0pIFtkcmFnb3Zlcl0gW3BhcnR+PSJjZWxsIl06OmFmdGVyIHsKICAgICAgICBoZWlnaHQ6IDJweDsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkcmFnb3Zlcj0iYmVsb3ciXSBbcGFydH49ImNlbGwiXTo6YWZ0ZXIgewogICAgICAgIHRvcDogMTAwJTsKICAgICAgICBib3R0b206IGF1dG87CiAgICAgICAgbWFyZ2luLXRvcDogLTFweDsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkcmFnb3Zlcj0iYWJvdmUiXSBbcGFydH49ImNlbGwiXTo6YWZ0ZXIgewogICAgICAgIHRvcDogYXV0bzsKICAgICAgICBib3R0b206IDEwMCU7CiAgICAgICAgbWFyZ2luLWJvdHRvbTogLTFweDsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkZXRhaWxzLW9wZW5lZF1bZHJhZ292ZXI9ImJlbG93Il0gW3BhcnR+PSJjZWxsIl06bm90KFtwYXJ0fj0iZGV0YWlscy1jZWxsIl0pOjphZnRlciwKICAgICAgW3BhcnR+PSJyb3ciXVtkZXRhaWxzLW9wZW5lZF1bZHJhZ292ZXI9ImFib3ZlIl0gW3BhcnR+PSJkZXRhaWxzLWNlbGwiXTo6YWZ0ZXIgewogICAgICAgIGRpc3BsYXk6IG5vbmU7CiAgICAgIH0KCiAgICAgIFtwYXJ0fj0icm93Il1bZHJhZ292ZXJdW2RyYWdvdmVyPSJvbi10b3AiXSBbcGFydH49ImNlbGwiXTo6YWZ0ZXIgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkcmFnc3RhcnRdIHsKICAgICAgICAvKiBBZGQgYm90dG9tLXNwYWNlIHRvIHRoZSByb3cgc28gdGhlIGRyYWcgbnVtYmVyIGRvZXNuJ3QgZ2V0IGNsaXBwZWQuIE5lZWRlZCBmb3IgSUUvRWRnZSAqLwogICAgICAgIGJvcmRlci1ib3R0b206IDEwMHB4IHNvbGlkIHRyYW5zcGFyZW50OwogICAgICAgIHotaW5kZXg6IDEwMCAhaW1wb3J0YW50OwogICAgICAgIG9wYWNpdHk6IDAuOTsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyb3ciXVtkcmFnc3RhcnRdIFtwYXJ0fj0iY2VsbCJdIHsKICAgICAgICBib3JkZXI6IG5vbmUgIWltcG9ydGFudDsKICAgICAgICBib3gtc2hhZG93OiBub25lICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIFtwYXJ0fj0icm93Il1bZHJhZ3N0YXJ0XSBbcGFydH49ImNlbGwiXVtsYXN0LWNvbHVtbl0gewogICAgICAgIGJvcmRlci1yYWRpdXM6IDAgdmFyKC0tbHVtby1ib3JkZXItcmFkaXVzLXMpIHZhcigtLWx1bW8tYm9yZGVyLXJhZGl1cy1zKSAwOwogICAgICB9CgogICAgICBbcGFydH49InJvdyJdW2RyYWdzdGFydF0gW3BhcnR+PSJjZWxsIl1bZmlyc3QtY29sdW1uXSB7CiAgICAgICAgYm9yZGVyLXJhZGl1czogdmFyKC0tbHVtby1ib3JkZXItcmFkaXVzLXMpIDAgMCB2YXIoLS1sdW1vLWJvcmRlci1yYWRpdXMtcyk7CiAgICAgIH0KCiAgICAgIFtpb3NdIFtwYXJ0fj0icm93Il1bZHJhZ3N0YXJ0XSBbcGFydH49ImNlbGwiXSB7CiAgICAgICAgYmFja2dyb3VuZDogdmFyKC0tbHVtby1wcmltYXJ5LWNvbG9yLTUwcGN0KTsKICAgICAgfQoKICAgICAgI3Njcm9sbGVyOm5vdChbaW9zXSkgW3BhcnR+PSJyb3ciXVtkcmFnc3RhcnRdOm5vdChbZHJhZ3N0YXJ0PSIiXSk6OmFmdGVyIHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgICAgbGVmdDogdmFyKC0tX2dyaWQtZHJhZy1zdGFydC14KTsKICAgICAgICB0b3A6IHZhcigtLV9ncmlkLWRyYWctc3RhcnQteSk7CiAgICAgICAgei1pbmRleDogMTAwOwogICAgICAgIGNvbnRlbnQ6IGF0dHIoZHJhZ3N0YXJ0KTsKICAgICAgICBhbGlnbi1pdGVtczogY2VudGVyOwogICAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyOwogICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgICAgcGFkZGluZzogY2FsYyh2YXIoLS1sdW1vLXNwYWNlLXhzKSAqIDAuOCk7CiAgICAgICAgY29sb3I6IHZhcigtLWx1bW8tZXJyb3ItY29udHJhc3QtY29sb3IpOwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWx1bW8tZXJyb3ItY29sb3IpOwogICAgICAgIGJvcmRlci1yYWRpdXM6IHZhcigtLWx1bW8tYm9yZGVyLXJhZGl1cy1tKTsKICAgICAgICBmb250LWZhbWlseTogdmFyKC0tbHVtby1mb250LWZhbWlseSk7CiAgICAgICAgZm9udC1zaXplOiB2YXIoLS1sdW1vLWZvbnQtc2l6ZS14eHMpOwogICAgICAgIGxpbmUtaGVpZ2h0OiAxOwogICAgICAgIGZvbnQtd2VpZ2h0OiA1MDA7CiAgICAgICAgdGV4dC10cmFuc2Zvcm06IGluaXRpYWw7CiAgICAgICAgbGV0dGVyLXNwYWNpbmc6IGluaXRpYWw7CiAgICAgICAgbWluLXdpZHRoOiBjYWxjKHZhcigtLWx1bW8tc2l6ZS1zKSAqIDAuNyk7CiAgICAgICAgdGV4dC1hbGlnbjogY2VudGVyOwogICAgICB9CgogICAgICAvKiBIZWFkZXJzIGFuZCBmb290ZXJzICovCgogICAgICBbcGFydH49ImhlYWRlci1jZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCksCiAgICAgIFtwYXJ0fj0iZm9vdGVyLWNlbGwiXSA6OnNsb3R0ZWQodmFhZGluLWdyaWQtY2VsbC1jb250ZW50KSwKICAgICAgW3BhcnR+PSJyZW9yZGVyLWdob3N0Il0gewogICAgICAgIGZvbnQtc2l6ZTogdmFyKC0tbHVtby1mb250LXNpemUtcyk7CiAgICAgICAgZm9udC13ZWlnaHQ6IDUwMDsKICAgICAgfQoKICAgICAgW3BhcnR+PSJmb290ZXItY2VsbCJdIDo6c2xvdHRlZCh2YWFkaW4tZ3JpZC1jZWxsLWNvbnRlbnQpIHsKICAgICAgICBmb250LXdlaWdodDogNDAwOwogICAgICB9CgogICAgICBbcGFydD0icm93Il06b25seS1jaGlsZCBbcGFydH49ImhlYWRlci1jZWxsIl0gewogICAgICAgIG1pbi1oZWlnaHQ6IHZhcigtLWx1bW8tc2l6ZS14bCk7CiAgICAgIH0KCiAgICAgIC8qIEhlYWRlciBib3JkZXJzICovCgogICAgICAvKiBIaWRlIGZpcnN0IGhlYWRlciByb3cgdG9wIGJvcmRlciAqLwogICAgICA6aG9zdCg6bm90KFt0aGVtZX49Im5vLXJvdy1ib3JkZXJzIl0pKSBbcGFydD0icm93Il06Zmlyc3QtY2hpbGQgW3BhcnR+PSJoZWFkZXItY2VsbCJdIHsKICAgICAgICBib3JkZXItdG9wOiAwOwogICAgICB9CgogICAgICBbcGFydD0icm93Il06bGFzdC1jaGlsZCBbcGFydH49ImhlYWRlci1jZWxsIl0gewogICAgICAgIGJvcmRlci1ib3R0b206IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLXdpZHRoKSBzb2xpZCB0cmFuc3BhcmVudDsKICAgICAgfQoKICAgICAgOmhvc3QoOm5vdChbdGhlbWV+PSJuby1yb3ctYm9yZGVycyJdKSkgW3BhcnQ9InJvdyJdOmxhc3QtY2hpbGQgW3BhcnR+PSJoZWFkZXItY2VsbCJdIHsKICAgICAgICBib3JkZXItYm90dG9tLWNvbG9yOiB2YXIoLS1fbHVtby1ncmlkLXNlY29uZGFyeS1ib3JkZXItY29sb3IpOwogICAgICB9CgogICAgICAvKiBPdmVyZmxvdyB1c2VzIGEgc3Ryb25nZXIgYm9yZGVyIGNvbG9yICovCiAgICAgIDpob3N0KFtvdmVyZmxvd349InRvcCJdKSBbcGFydD0icm93Il06bGFzdC1jaGlsZCBbcGFydH49ImhlYWRlci1jZWxsIl0gewogICAgICAgIGJvcmRlci1ib3R0b20tY29sb3I6IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLWNvbG9yKTsKICAgICAgfQoKICAgICAgLyogRm9vdGVyIGJvcmRlcnMgKi8KCiAgICAgIFtwYXJ0PSJyb3ciXTpmaXJzdC1jaGlsZCBbcGFydH49ImZvb3Rlci1jZWxsIl0gewogICAgICAgIGJvcmRlci10b3A6IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLXdpZHRoKSBzb2xpZCB0cmFuc3BhcmVudDsKICAgICAgfQoKICAgICAgOmhvc3QoOm5vdChbdGhlbWV+PSJuby1yb3ctYm9yZGVycyJdKSkgW3BhcnQ9InJvdyJdOmZpcnN0LWNoaWxkIFtwYXJ0fj0iZm9vdGVyLWNlbGwiXSB7CiAgICAgICAgYm9yZGVyLXRvcC1jb2xvcjogdmFyKC0tX2x1bW8tZ3JpZC1zZWNvbmRhcnktYm9yZGVyLWNvbG9yKTsKICAgICAgfQoKICAgICAgLyogT3ZlcmZsb3cgdXNlcyBhIHN0cm9uZ2VyIGJvcmRlciBjb2xvciAqLwogICAgICA6aG9zdChbb3ZlcmZsb3d+PSJib3R0b20iXSkgW3BhcnQ9InJvdyJdOmZpcnN0LWNoaWxkIFtwYXJ0fj0iZm9vdGVyLWNlbGwiXSB7CiAgICAgICAgYm9yZGVyLXRvcC1jb2xvcjogdmFyKC0tX2x1bW8tZ3JpZC1ib3JkZXItY29sb3IpOwogICAgICB9CgogICAgICAvKiBDb2x1bW4gcmVvcmRlcmluZyAqLwoKICAgICAgOmhvc3QoW3Jlb3JkZXJpbmddKSBbcGFydH49ImNlbGwiXSB7CiAgICAgICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KHZhcigtLWx1bW8tc2hhZGUtMjBwY3QpLCB2YXIoLS1sdW1vLXNoYWRlLTIwcGN0KSkgdmFyKC0tbHVtby1iYXNlLWNvbG9yKTsKICAgICAgfQoKICAgICAgOmhvc3QoW3Jlb3JkZXJpbmddKSBbcGFydH49ImNlbGwiXVtyZW9yZGVyLXN0YXR1cz0iYWxsb3dlZCJdIHsKICAgICAgICBiYWNrZ3JvdW5kOiB2YXIoLS1sdW1vLWJhc2UtY29sb3IpOwogICAgICB9CgogICAgICA6aG9zdChbcmVvcmRlcmluZ10pIFtwYXJ0fj0iY2VsbCJdW3Jlb3JkZXItc3RhdHVzPSJkcmFnZ2luZyJdIHsKICAgICAgICBiYWNrZ3JvdW5kOiBsaW5lYXItZ3JhZGllbnQodmFyKC0tbHVtby1jb250cmFzdC01cGN0KSwgdmFyKC0tbHVtby1jb250cmFzdC01cGN0KSkgdmFyKC0tbHVtby1iYXNlLWNvbG9yKTsKICAgICAgfQoKICAgICAgW3BhcnR+PSJyZW9yZGVyLWdob3N0Il0gewogICAgICAgIG9wYWNpdHk6IDAuODU7CiAgICAgICAgYm94LXNoYWRvdzogdmFyKC0tbHVtby1ib3gtc2hhZG93LXMpOwogICAgICAgIC8qIFRPRE8gVXNlIHRoZSBzYW1lIHN0eWxlcyBhcyBmb3IgdGhlIGNlbGwgZWxlbWVudCAocmVvcmRlci1naG9zdCBjb3BpZXMgc3R5bGVzIGZyb20gdGhlIGNlbGwgZWxlbWVudCkgKi8KICAgICAgICBwYWRkaW5nOiB2YXIoLS1sdW1vLXNwYWNlLXMpIHZhcigtLWx1bW8tc3BhY2UtbSkgIWltcG9ydGFudDsKICAgICAgfQoKICAgICAgLyogQ29sdW1uIHJlc2l6aW5nICovCgogICAgICBbcGFydD0icmVzaXplLWhhbmRsZSJdIHsKICAgICAgICB3aWR0aDogM3B4OwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigtLWx1bW8tcHJpbWFyeS1jb2xvci01MHBjdCk7CiAgICAgICAgb3BhY2l0eTogMDsKICAgICAgICB0cmFuc2l0aW9uOiBvcGFjaXR5IDAuMnM7CiAgICAgIH0KCiAgICAgIDpob3N0KDpub3QoW3Jlb3JkZXJpbmddKSkgKjpub3QoW2NvbHVtbi1yZXNpemluZ10pIFtwYXJ0fj0iY2VsbCJdOmhvdmVyIFtwYXJ0PSJyZXNpemUtaGFuZGxlIl0sCiAgICAgIFtwYXJ0PSJyZXNpemUtaGFuZGxlIl06YWN0aXZlIHsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICAgIHRyYW5zaXRpb24tZGVsYXk6IDAuMTVzOwogICAgICB9CgogICAgICAvKiBDb2x1bW4gYm9yZGVycyAqLwoKICAgICAgOmhvc3QoW3RoZW1lfj0iY29sdW1uLWJvcmRlcnMiXSkgW3BhcnR+PSJjZWxsIl06bm90KFtsYXN0LWNvbHVtbl0pOm5vdChbcGFydH49ImRldGFpbHMtY2VsbCJdKSB7CiAgICAgICAgYm9yZGVyLXJpZ2h0OiB2YXIoLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aCkgc29saWQgdmFyKC0tX2x1bW8tZ3JpZC1zZWNvbmRhcnktYm9yZGVyLWNvbG9yKTsKICAgICAgfQoKICAgICAgLyogRnJvemVuIGNvbHVtbnMgKi8KCiAgICAgIFtsYXN0LWZyb3plbl0gewogICAgICAgIGJvcmRlci1yaWdodDogdmFyKC0tX2x1bW8tZ3JpZC1ib3JkZXItd2lkdGgpIHNvbGlkIHRyYW5zcGFyZW50OwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KCiAgICAgIDpob3N0KFtvdmVyZmxvd349ImxlZnQiXSkgW3BhcnR+PSJjZWxsIl1bbGFzdC1mcm96ZW5dOm5vdChbcGFydH49ImRldGFpbHMtY2VsbCJdKSB7CiAgICAgICAgYm9yZGVyLXJpZ2h0LWNvbG9yOiB2YXIoLS1fbHVtby1ncmlkLWJvcmRlci1jb2xvcik7CiAgICAgIH0KCiAgICAgIC8qIFJvdyBzdHJpcGVzICovCgogICAgICA6aG9zdChbdGhlbWV+PSJyb3ctc3RyaXBlcyJdKSBbcGFydH49InJvdyJdOm5vdChbb2RkXSkgW3BhcnR+PSJib2R5LWNlbGwiXSwKICAgICAgOmhvc3QoW3RoZW1lfj0icm93LXN0cmlwZXMiXSkgW3BhcnR+PSJyb3ciXTpub3QoW29kZF0pIFtwYXJ0fj0iZGV0YWlscy1jZWxsIl0gewogICAgICAgIGJhY2tncm91bmQtaW1hZ2U6IGxpbmVhci1ncmFkaWVudCh2YXIoLS1sdW1vLWNvbnRyYXN0LTVwY3QpLCB2YXIoLS1sdW1vLWNvbnRyYXN0LTVwY3QpKTsKICAgICAgICBiYWNrZ3JvdW5kLXJlcGVhdDogcmVwZWF0LXg7CiAgICAgIH0KCiAgICAgIC8qIFNlbGVjdGVkIHJvdyAqLwoKICAgICAgLyogUmFpc2UgdGhlIHNlbGVjdGVkIHJvd3MgYWJvdmUgdW5zZWxlY3RlZCByb3dzIChzbyB0aGF0IGJveC1zaGFkb3cgY2FuIGNvdmVyIHVuc2VsZWN0ZWQgcm93cykgKi8KICAgICAgOmhvc3QoOm5vdChbcmVvcmRlcmluZ10pKSBbcGFydH49InJvdyJdW3NlbGVjdGVkXSB7CiAgICAgICAgei1pbmRleDogMTsKICAgICAgfQoKICAgICAgOmhvc3QoOm5vdChbcmVvcmRlcmluZ10pKSBbcGFydH49InJvdyJdW3NlbGVjdGVkXSBbcGFydH49ImJvZHktY2VsbCJdOm5vdChbcGFydH49ImRldGFpbHMtY2VsbCJdKSB7CiAgICAgICAgYmFja2dyb3VuZC1pbWFnZTogbGluZWFyLWdyYWRpZW50KHZhcigtLV9sdW1vLWdyaWQtc2VsZWN0ZWQtcm93LWNvbG9yKSwgdmFyKC0tX2x1bW8tZ3JpZC1zZWxlY3RlZC1yb3ctY29sb3IpKTsKICAgICAgICBiYWNrZ3JvdW5kLXJlcGVhdDogcmVwZWF0OwogICAgICB9CgogICAgICAvKiBDb3ZlciB0aGUgYm9yZGVyIG9mIGFuIHVuc2VsZWN0ZWQgcm93ICovCiAgICAgIDpob3N0KDpub3QoW3RoZW1lfj0ibm8tcm93LWJvcmRlcnMiXSkpIFtwYXJ0fj0icm93Il1bc2VsZWN0ZWRdIFtwYXJ0fj0iY2VsbCJdOm5vdChbcGFydH49ImRldGFpbHMtY2VsbCJdKSB7CiAgICAgICAgYm94LXNoYWRvdzogMCB2YXIoLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aCkgMCAwIHZhcigtLV9sdW1vLWdyaWQtc2VsZWN0ZWQtcm93LWNvbG9yKTsKICAgICAgfQoKICAgICAgLyogQ29tcGFjdCAqLwoKICAgICAgOmhvc3QoW3RoZW1lfj0iY29tcGFjdCJdKSBbcGFydD0icm93Il06b25seS1jaGlsZCBbcGFydH49ImhlYWRlci1jZWxsIl0gewogICAgICAgIG1pbi1oZWlnaHQ6IHZhcigtLWx1bW8tc2l6ZS1tKTsKICAgICAgfQoKICAgICAgOmhvc3QoW3RoZW1lfj0iY29tcGFjdCJdKSBbcGFydH49ImNlbGwiXSB7CiAgICAgICAgbWluLWhlaWdodDogdmFyKC0tbHVtby1zaXplLXMpOwogICAgICB9CgogICAgICA6aG9zdChbdGhlbWV+PSJjb21wYWN0Il0pIFtwYXJ0PSJyb3ciXVtmaXJzdF0gW3BhcnR+PSJjZWxsIl06bm90KFtwYXJ0fj0iZGV0YWlscy1jZWxsIl0pIHsKICAgICAgICBtaW4taGVpZ2h0OiBjYWxjKHZhcigtLWx1bW8tc2l6ZS1zKSAtIHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLXdpZHRoKSk7CiAgICAgIH0KCiAgICAgIDpob3N0KFt0aGVtZX49ImNvbXBhY3QiXSkgW3BhcnR+PSJjZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCkgewogICAgICAgIHBhZGRpbmc6IHZhcigtLWx1bW8tc3BhY2UteHMpIHZhcigtLWx1bW8tc3BhY2Utcyk7CiAgICAgIH0KCiAgICAgIC8qIFdyYXAgY2VsbCBjb250ZW50cyAqLwoKICAgICAgOmhvc3QoW3RoZW1lfj0id3JhcC1jZWxsLWNvbnRlbnQiXSkgW3BhcnR+PSJjZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCkgewogICAgICAgIHdoaXRlLXNwYWNlOiBub3JtYWw7CiAgICAgIH0KCiAgICAgIC8qIFJUTCBzcGVjaWZpYyBzdHlsZXMgKi8KCiAgICAgIDpob3N0KFtkaXI9InJ0bCJdKSBbcGFydH49InJvdyJdW2RyYWdzdGFydF0gW3BhcnR+PSJjZWxsIl1bbGFzdC1jb2x1bW5dIHsKICAgICAgICBib3JkZXItcmFkaXVzOiB2YXIoLS1sdW1vLWJvcmRlci1yYWRpdXMtcykgMCAwIHZhcigtLWx1bW8tYm9yZGVyLXJhZGl1cy1zKTsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpcj0icnRsIl0pIFtwYXJ0fj0icm93Il1bZHJhZ3N0YXJ0XSBbcGFydH49ImNlbGwiXVtmaXJzdC1jb2x1bW5dIHsKICAgICAgICBib3JkZXItcmFkaXVzOiAwIHZhcigtLWx1bW8tYm9yZGVyLXJhZGl1cy1zKSB2YXIoLS1sdW1vLWJvcmRlci1yYWRpdXMtcykgMDsKICAgICAgfQoKICAgICAgOmhvc3QoW2Rpcj0icnRsIl1bdGhlbWV+PSJjb2x1bW4tYm9yZGVycyJdKSBbcGFydH49ImNlbGwiXTpub3QoW2xhc3QtY29sdW1uXSk6bm90KFtwYXJ0fj0iZGV0YWlscy1jZWxsIl0pIHsKICAgICAgICBib3JkZXItcmlnaHQ6IG5vbmU7CiAgICAgICAgYm9yZGVyLWxlZnQ6IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLXdpZHRoKSBzb2xpZCB2YXIoLS1fbHVtby1ncmlkLXNlY29uZGFyeS1ib3JkZXItY29sb3IpOwogICAgICB9CgogICAgICA6aG9zdChbZGlyPSJydGwiXSkgW2xhc3QtZnJvemVuXSB7CiAgICAgICAgYm9yZGVyLXJpZ2h0OiBub25lOwogICAgICAgIGJvcmRlci1sZWZ0OiB2YXIoLS1fbHVtby1ncmlkLWJvcmRlci13aWR0aCkgc29saWQgdHJhbnNwYXJlbnQ7CiAgICAgIH0KCiAgICAgIDpob3N0KFtkaXI9InJ0bCJdW292ZXJmbG93fj0icmlnaHQiXSkgW3BhcnR+PSJjZWxsIl1bbGFzdC1mcm96ZW5dOm5vdChbcGFydH49ImRldGFpbHMtY2VsbCJdKSB7CiAgICAgICAgYm9yZGVyLWxlZnQtY29sb3I6IHZhcigtLV9sdW1vLWdyaWQtYm9yZGVyLWNvbG9yKTsKICAgICAgfQogICAgPC9zdHlsZT4KICA8L3RlbXBsYXRlPgo8L2RvbS1tb2R1bGU+PGRvbS1tb2R1bGUgdGhlbWUtZm9yPSJ2YWFkaW4tY2hlY2tib3giIGlkPSJ2YWFkaW4tZ3JpZC1zZWxlY3QtYWxsLWNoZWNrYm94LWx1bW8iPgogIDx0ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgOmhvc3QoLnZhYWRpbi1ncmlkLXNlbGVjdC1hbGwtY2hlY2tib3gpIHsKICAgICAgICBmb250LXNpemU6IHZhcigtLWx1bW8tZm9udC1zaXplLW0pOwogICAgICB9CiAgIDwvc3R5bGU+CiAgPC90ZW1wbGF0ZT4KPC9kb20tbW9kdWxlPmA7CgogICAgZG9jdW1lbnQuaGVhZC5hcHBlbmRDaGlsZCgkX2RvY3VtZW50Q29udGFpbmVyJGMuY29udGVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE2IFRoZSBQb2x5bWVyIFByb2plY3QgQXV0aG9ycy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KICAgIFRoaXMgY29kZSBtYXkgb25seSBiZSB1c2VkIHVuZGVyIHRoZSBCU0Qgc3R5bGUgbGljZW5zZSBmb3VuZCBhdCBodHRwOi8vcG9seW1lci5naXRodWIuaW8vTElDRU5TRS50eHQKICAgIFRoZSBjb21wbGV0ZSBzZXQgb2YgYXV0aG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0FVVEhPUlMudHh0CiAgICBUaGUgY29tcGxldGUgc2V0IG9mIGNvbnRyaWJ1dG9ycyBtYXkgYmUgZm91bmQgYXQgaHR0cDovL3BvbHltZXIuZ2l0aHViLmlvL0NPTlRSSUJVVE9SUy50eHQKICAgIENvZGUgZGlzdHJpYnV0ZWQgYnkgR29vZ2xlIGFzIHBhcnQgb2YgdGhlIHBvbHltZXIgcHJvamVjdCBpcyBhbHNvCiAgICBzdWJqZWN0IHRvIGFuIGFkZGl0aW9uYWwgSVAgcmlnaHRzIGdyYW50IGZvdW5kIGF0IGh0dHA6Ly9wb2x5bWVyLmdpdGh1Yi5pby9QQVRFTlRTLnR4dAogICAgKi8KICAgIHZhciBJT1MkMSA9IG5hdmlnYXRvci51c2VyQWdlbnQubWF0Y2goL2lQKD86aG9uZXxhZDsoPzogVTspPyBDUFUpIE9TIChcZCspLyk7CiAgICB2YXIgSU9TX1RPVUNIX1NDUk9MTElORyQxID0gSU9TJDEgJiYgSU9TJDFbMV0gPj0gODsKICAgIHZhciBERUZBVUxUX1BIWVNJQ0FMX0NPVU5UJDEgPSAzOwogICAgdmFyIEFOSU1BVElPTl9GUkFNRSA9IGFuaW1hdGlvbkZyYW1lOwogICAgdmFyIElETEVfVElNRSA9IGlkbGVQZXJpb2Q7CiAgICB2YXIgTUlDUk9fVEFTSyA9IG1pY3JvVGFzazsKCiAgICBjb25zdCBQb2x5bWVySXJvbkxpc3QgPSBDbGFzcyh7CgogICAgICBiZWhhdmlvcnM6IFsKICAgICAgICBJcm9uUmVzaXphYmxlQmVoYXZpb3IsCiAgICAgICAgSXJvblNjcm9sbFRhcmdldEJlaGF2aW9yCiAgICAgIF0sCgogICAgICAvKioKICAgICAgICogVGhlIHJhdGlvIG9mIGhpZGRlbiB0aWxlcyB0aGF0IHNob3VsZCByZW1haW4gaW4gdGhlIHNjcm9sbCBkaXJlY3Rpb24uCiAgICAgICAqIFJlY29tbWVuZGVkIHZhbHVlIH4wLjUsIHNvIGl0IHdpbGwgZGlzdHJpYnV0ZSB0aWxlcyBldmVubHkgaW4gYm90aCBkaXJlY3Rpb25zLgogICAgICAgKi8KICAgICAgX3JhdGlvOiAwLjUsCgogICAgICAvKioKICAgICAgICogVGhlIHBhZGRpbmctdG9wIHZhbHVlIGZvciB0aGUgbGlzdC4KICAgICAgICovCiAgICAgIF9zY3JvbGxlclBhZGRpbmdUb3A6IDAsCgogICAgICAvKioKICAgICAgICogVGhpcyB2YWx1ZSBpcyB0aGUgc2FtZSBhcyBgc2Nyb2xsVG9wYC4KICAgICAgICovCiAgICAgIF9zY3JvbGxQb3NpdGlvbjogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgc3VtIG9mIHRoZSBoZWlnaHRzIG9mIGFsbCB0aGUgdGlsZXMgaW4gdGhlIERPTS4KICAgICAgICovCiAgICAgIF9waHlzaWNhbFNpemU6IDAsCgogICAgICAvKioKICAgICAgICogVGhlIGF2ZXJhZ2UgYG9mZnNldEhlaWdodGAgb2YgdGhlIHRpbGVzIG9ic2VydmVkIHRpbGwgbm93LgogICAgICAgKi8KICAgICAgX3BoeXNpY2FsQXZlcmFnZTogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbnVtYmVyIG9mIHRpbGVzIHdoaWNoIGBvZmZzZXRIZWlnaHRgID4gMCBvYnNlcnZlZCB1bnRpbCBub3cuCiAgICAgICAqLwogICAgICBfcGh5c2ljYWxBdmVyYWdlQ291bnQ6IDAsCgogICAgICAvKioKICAgICAgICogVGhlIFkgcG9zaXRpb24gb2YgdGhlIGl0ZW0gcmVuZGVyZWQgaW4gdGhlIGBfcGh5c2ljYWxTdGFydGAKICAgICAgICogdGlsZSByZWxhdGl2ZSB0byB0aGUgc2Nyb2xsaW5nIGxpc3QuCiAgICAgICAqLwogICAgICBfcGh5c2ljYWxUb3A6IDAsCgogICAgICAvKioKICAgICAgICogVGhlIG51bWJlciBvZiBpdGVtcyBpbiB0aGUgbGlzdC4KICAgICAgICovCiAgICAgIF92aXJ0dWFsQ291bnQ6IDAsCgogICAgICAvKioKICAgICAgICogVGhlIGVzdGltYXRlZCBzY3JvbGwgaGVpZ2h0IGJhc2VkIG9uIGBfcGh5c2ljYWxBdmVyYWdlYAogICAgICAgKi8KICAgICAgX2VzdFNjcm9sbEhlaWdodDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgc2Nyb2xsIGhlaWdodCBvZiB0aGUgZG9tIG5vZGUKICAgICAgICovCiAgICAgIF9zY3JvbGxIZWlnaHQ6IDAsCgogICAgICAvKioKICAgICAgICogVGhlIGhlaWdodCBvZiB0aGUgbGlzdC4gVGhpcyBpcyByZWZlcnJlZCBhcyB0aGUgdmlld3BvcnQgaW4gdGhlIGNvbnRleHQgb2YgbGlzdC4KICAgICAgICovCiAgICAgIF92aWV3cG9ydEhlaWdodDogMCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgd2lkdGggb2YgdGhlIGxpc3QuIFRoaXMgaXMgcmVmZXJyZWQgYXMgdGhlIHZpZXdwb3J0IGluIHRoZSBjb250ZXh0IG9mIGxpc3QuCiAgICAgICAqLwogICAgICBfdmlld3BvcnRXaWR0aDogMCwKCiAgICAgIC8qKgogICAgICAgKiBBbiBhcnJheSBvZiBET00gbm9kZXMgdGhhdCBhcmUgY3VycmVudGx5IGluIHRoZSB0cmVlCiAgICAgICAqIEB0eXBlIHs/QXJyYXk8IVRlbXBsYXRpemVyTm9kZT59CiAgICAgICAqLwogICAgICBfcGh5c2ljYWxJdGVtczogbnVsbCwKCiAgICAgIC8qKgogICAgICAgKiBBbiBhcnJheSBvZiBoZWlnaHRzIGZvciBlYWNoIGl0ZW0gaW4gYF9waHlzaWNhbEl0ZW1zYAogICAgICAgKiBAdHlwZSB7P0FycmF5PG51bWJlcj59CiAgICAgICAqLwogICAgICBfcGh5c2ljYWxTaXplczogbnVsbCwKCiAgICAgIC8qKgogICAgICAgKiBBIGNhY2hlZCB2YWx1ZSBmb3IgdGhlIGZpcnN0IHZpc2libGUgaW5kZXguCiAgICAgICAqIFNlZSBgZmlyc3RWaXNpYmxlSW5kZXhgCiAgICAgICAqIEB0eXBlIHs/bnVtYmVyfQogICAgICAgKi8KICAgICAgX2ZpcnN0VmlzaWJsZUluZGV4VmFsOiBudWxsLAoKICAgICAgLyoqCiAgICAgICAqIEEgUG9seW1lciBjb2xsZWN0aW9uIGZvciB0aGUgaXRlbXMuCiAgICAgICAqIEB0eXBlIHs/UG9seW1lci5Db2xsZWN0aW9ufQogICAgICAgKi8KICAgICAgX2NvbGxlY3Rpb246IG51bGwsCgogICAgICAvKioKICAgICAgICogQSBjYWNoZWQgdmFsdWUgZm9yIHRoZSBsYXN0IHZpc2libGUgaW5kZXguCiAgICAgICAqIFNlZSBgbGFzdFZpc2libGVJbmRleGAKICAgICAgICogQHR5cGUgez9udW1iZXJ9CiAgICAgICAqLwogICAgICBfbGFzdFZpc2libGVJbmRleFZhbDogbnVsbCwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbWF4IG51bWJlciBvZiBwYWdlcyB0byByZW5kZXIuIE9uZSBwYWdlIGlzIGVxdWl2YWxlbnQgdG8gdGhlIGhlaWdodCBvZiB0aGUgbGlzdC4KICAgICAgICovCiAgICAgIF9tYXhQYWdlczogMiwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgdmlydHVhbCBpbmRleCBvZiB0aGUgZm9jdXNlZCBpdGVtLgogICAgICAgKi8KICAgICAgX2ZvY3VzZWRWaXJ0dWFsSW5kZXg6IC0xLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBtYXhpbXVtIGl0ZW1zIHBlciByb3cKICAgICAgICovCiAgICAgIF9pdGVtc1BlclJvdzogMSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgaGVpZ2h0IG9mIHRoZSByb3cgaW4gZ3JpZCBsYXlvdXQuCiAgICAgICAqLwogICAgICBfcm93SGVpZ2h0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBjb3N0IG9mIHN0YW1waW5nIGEgdGVtcGxhdGUgaW4gbXMuCiAgICAgICAqLwogICAgICBfdGVtcGxhdGVDb3N0OiAwLAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBib3R0b20gb2YgdGhlIHBoeXNpY2FsIGNvbnRlbnQuCiAgICAgICAqLwogICAgICBnZXQgX3BoeXNpY2FsQm90dG9tKCkgewogICAgICAgIHJldHVybiB0aGlzLl9waHlzaWNhbFRvcCArIHRoaXMuX3BoeXNpY2FsU2l6ZTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgYm90dG9tIG9mIHRoZSBzY3JvbGwuCiAgICAgICAqLwogICAgICBnZXQgX3Njcm9sbEJvdHRvbSgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fc2Nyb2xsUG9zaXRpb24gKyB0aGlzLl92aWV3cG9ydEhlaWdodDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgbi10aCBpdGVtIHJlbmRlcmVkIGluIHRoZSBsYXN0IHBoeXNpY2FsIGl0ZW0uCiAgICAgICAqLwogICAgICBnZXQgX3ZpcnR1YWxFbmQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX3ZpcnR1YWxTdGFydCArIHRoaXMuX3BoeXNpY2FsQ291bnQgLSAxOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBoZWlnaHQgb2YgdGhlIHBoeXNpY2FsIGNvbnRlbnQgdGhhdCBpc24ndCBvbiB0aGUgc2NyZWVuLgogICAgICAgKi8KICAgICAgZ2V0IF9oaWRkZW5Db250ZW50U2l6ZSgpIHsKICAgICAgICB2YXIgc2l6ZSA9IHRoaXMuZ3JpZCA/IHRoaXMuX3BoeXNpY2FsUm93cyAqIHRoaXMuX3Jvd0hlaWdodCA6IHRoaXMuX3BoeXNpY2FsU2l6ZTsKICAgICAgICByZXR1cm4gc2l6ZSAtIHRoaXMuX3ZpZXdwb3J0SGVpZ2h0OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFRoZSBtYXhpbXVtIHNjcm9sbCB0b3AgdmFsdWUuCiAgICAgICAqLwogICAgICBnZXQgX21heFNjcm9sbFRvcCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fZXN0U2Nyb2xsSGVpZ2h0IC0gdGhpcy5fdmlld3BvcnRIZWlnaHQgKyB0aGlzLl9zY3JvbGxPZmZzZXQ7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIGxhcmdlc3Qgbi10aCB2YWx1ZSBmb3IgYW4gaXRlbSBzdWNoIHRoYXQgaXQgY2FuIGJlIHJlbmRlcmVkIGluIGBfcGh5c2ljYWxTdGFydGAuCiAgICAgICAqLwogICAgICBnZXQgX21heFZpcnR1YWxTdGFydCgpIHsKICAgICAgICB2YXIgdmlydHVhbENvdW50ID0gdGhpcy5fY29udmVydEluZGV4VG9Db21wbGV0ZVJvdyh0aGlzLl92aXJ0dWFsQ291bnQpOwogICAgICAgIHJldHVybiBNYXRoLm1heCgwLCB2aXJ0dWFsQ291bnQgLSB0aGlzLl9waHlzaWNhbENvdW50KTsKICAgICAgfSwKCiAgICAgIHNldCBfdmlydHVhbFN0YXJ0KHZhbCkgewogICAgICAgIHZhbCA9IHRoaXMuX2NsYW1wKHZhbCwgMCwgdGhpcy5fbWF4VmlydHVhbFN0YXJ0KTsKICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICB2YWwgPSB2YWwgLSAodmFsICUgdGhpcy5faXRlbXNQZXJSb3cpOwogICAgICAgIH0KICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnRWYWwgPSB2YWw7CiAgICAgIH0sCgogICAgICBnZXQgX3ZpcnR1YWxTdGFydCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fdmlydHVhbFN0YXJ0VmFsIHx8IDA7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVGhlIGstdGggdGlsZSB0aGF0IGlzIGF0IHRoZSB0b3Agb2YgdGhlIHNjcm9sbGluZyBsaXN0LgogICAgICAgKi8KICAgICAgc2V0IF9waHlzaWNhbFN0YXJ0KHZhbCkgewogICAgICAgIHZhbCA9IHZhbCAlIHRoaXMuX3BoeXNpY2FsQ291bnQ7CiAgICAgICAgaWYgKHZhbCA8IDApIHsKICAgICAgICAgIHZhbCA9IHRoaXMuX3BoeXNpY2FsQ291bnQgKyB2YWw7CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLmdyaWQpIHsKICAgICAgICAgIHZhbCA9IHZhbCAtICh2YWwgJSB0aGlzLl9pdGVtc1BlclJvdyk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnRWYWwgPSB2YWw7CiAgICAgIH0sCgogICAgICBnZXQgX3BoeXNpY2FsU3RhcnQoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX3BoeXNpY2FsU3RhcnRWYWwgfHwgMDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBUaGUgay10aCB0aWxlIHRoYXQgaXMgYXQgdGhlIGJvdHRvbSBvZiB0aGUgc2Nyb2xsaW5nIGxpc3QuCiAgICAgICAqLwogICAgICBnZXQgX3BoeXNpY2FsRW5kKCkgewogICAgICAgIHJldHVybiAodGhpcy5fcGh5c2ljYWxTdGFydCArIHRoaXMuX3BoeXNpY2FsQ291bnQgLSAxKSAlIHRoaXMuX3BoeXNpY2FsQ291bnQ7CiAgICAgIH0sCgogICAgICBzZXQgX3BoeXNpY2FsQ291bnQodmFsKSB7CiAgICAgICAgdGhpcy5fcGh5c2ljYWxDb3VudFZhbCA9IHZhbDsKICAgICAgfSwKCiAgICAgIGdldCBfcGh5c2ljYWxDb3VudCgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fcGh5c2ljYWxDb3VudFZhbCB8fCAwOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEFuIG9wdGltYWwgcGh5c2ljYWwgc2l6ZSBzdWNoIHRoYXQgd2Ugd2lsbCBoYXZlIGVub3VnaCBwaHlzaWNhbCBpdGVtcwogICAgICAgKiB0byBmaWxsIHVwIHRoZSB2aWV3cG9ydCBhbmQgcmVjeWNsZSB3aGVuIHRoZSB1c2VyIHNjcm9sbHMuCiAgICAgICAqCiAgICAgICAqIFRoaXMgZGVmYXVsdCB2YWx1ZSBhc3N1bWVzIHRoYXQgd2Ugd2lsbCBhdCBsZWFzdCBoYXZlIHRoZSBlcXVpdmFsZW50CiAgICAgICAqIHRvIGEgdmlld3BvcnQgb2YgcGh5c2ljYWwgaXRlbXMgYWJvdmUgYW5kIGJlbG93IHRoZSB1c2VyJ3Mgdmlld3BvcnQuCiAgICAgICAqLwogICAgICBnZXQgX29wdFBoeXNpY2FsU2l6ZSgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fdmlld3BvcnRIZWlnaHQgPT09IDAgPyBJbmZpbml0eSA6IHRoaXMuX3ZpZXdwb3J0SGVpZ2h0ICogdGhpcy5fbWF4UGFnZXM7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVHJ1ZSBpZiB0aGUgY3VycmVudCBsaXN0IGlzIHZpc2libGUuCiAgICAgICAqLwogICAgICBnZXQgX2lzVmlzaWJsZSgpIHsKICAgICAgICByZXR1cm4gQm9vbGVhbih0aGlzLm9mZnNldFdpZHRoIHx8IHRoaXMub2Zmc2V0SGVpZ2h0KTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBHZXRzIHRoZSBpbmRleCBvZiB0aGUgZmlyc3QgdmlzaWJsZSBpdGVtIGluIHRoZSB2aWV3cG9ydC4KICAgICAgICoKICAgICAgICogQHR5cGUge251bWJlcn0KICAgICAgICovCiAgICAgIGdldCBmaXJzdFZpc2libGVJbmRleCgpIHsKICAgICAgICB2YXIgaWR4ID0gdGhpcy5fZmlyc3RWaXNpYmxlSW5kZXhWYWw7CiAgICAgICAgaWYgKGlkeCA9PSBudWxsKSB7CiAgICAgICAgICB2YXIgcGh5c2ljYWxPZmZzZXQgPSB0aGlzLl9waHlzaWNhbFRvcCArIHRoaXMuX3Njcm9sbE9mZnNldDsKCiAgICAgICAgICBpZHggPSB0aGlzLl9pdGVyYXRlSXRlbXMoZnVuY3Rpb24ocGlkeCwgdmlkeCkgewogICAgICAgICAgICBwaHlzaWNhbE9mZnNldCArPSB0aGlzLl9nZXRQaHlzaWNhbFNpemVJbmNyZW1lbnQocGlkeCk7CgogICAgICAgICAgICBpZiAocGh5c2ljYWxPZmZzZXQgPiB0aGlzLl9zY3JvbGxQb3NpdGlvbikgewogICAgICAgICAgICAgIHJldHVybiB0aGlzLmdyaWQgPyB2aWR4IC0gKHZpZHggJSB0aGlzLl9pdGVtc1BlclJvdykgOiB2aWR4OwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEhhbmRsZSBhIHBhcnRpYWxseSByZW5kZXJlZCBmaW5hbCByb3cgaW4gZ3JpZCBtb2RlCiAgICAgICAgICAgIGlmICh0aGlzLmdyaWQgJiYgdGhpcy5fdmlydHVhbENvdW50IC0gMSA9PT0gdmlkeCkgewogICAgICAgICAgICAgIHJldHVybiB2aWR4IC0gKHZpZHggJSB0aGlzLl9pdGVtc1BlclJvdyk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pIHx8IDA7CiAgICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IGlkeDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGlkeDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBHZXRzIHRoZSBpbmRleCBvZiB0aGUgbGFzdCB2aXNpYmxlIGl0ZW0gaW4gdGhlIHZpZXdwb3J0LgogICAgICAgKgogICAgICAgKiBAdHlwZSB7bnVtYmVyfQogICAgICAgKi8KICAgICAgZ2V0IGxhc3RWaXNpYmxlSW5kZXgoKSB7CiAgICAgICAgdmFyIGlkeCA9IHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWw7CiAgICAgICAgaWYgKGlkeCA9PSBudWxsKSB7CiAgICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICAgIGlkeCA9IE1hdGgubWluKHRoaXMuX3ZpcnR1YWxDb3VudCwgdGhpcy5maXJzdFZpc2libGVJbmRleCArIHRoaXMuX2VzdFJvd3NJblZpZXcgKiB0aGlzLl9pdGVtc1BlclJvdyAtIDEpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdmFyIHBoeXNpY2FsT2Zmc2V0ID0gdGhpcy5fcGh5c2ljYWxUb3AgKyB0aGlzLl9zY3JvbGxPZmZzZXQ7CiAgICAgICAgICAgIHRoaXMuX2l0ZXJhdGVJdGVtcyhmdW5jdGlvbihwaWR4LCB2aWR4KSB7CiAgICAgICAgICAgICAgaWYgKHBoeXNpY2FsT2Zmc2V0IDwgdGhpcy5fc2Nyb2xsQm90dG9tKSB7CiAgICAgICAgICAgICAgICBpZHggPSB2aWR4OwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBwaHlzaWNhbE9mZnNldCArPSB0aGlzLl9nZXRQaHlzaWNhbFNpemVJbmNyZW1lbnQocGlkeCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fbGFzdFZpc2libGVJbmRleFZhbCA9IGlkeDsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGlkeDsKICAgICAgfSwKCiAgICAgIGdldCBfc2Nyb2xsT2Zmc2V0KCkgewogICAgICAgIHJldHVybiB0aGlzLl9zY3JvbGxlclBhZGRpbmdUb3A7CiAgICAgIH0sCgogICAgICBhdHRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fZGVib3VuY2UoJ19yZW5kZXInLCB0aGlzLl9yZW5kZXIsIEFOSU1BVElPTl9GUkFNRSk7CiAgICAgICAgLy8gYGlyb24tcmVzaXplYCBpcyBmaXJlZCB3aGVuIHRoZSBsaXN0IGlzIGF0dGFjaGVkIGlmIHRoZSBldmVudCBpcyBhZGRlZAogICAgICAgIC8vIGJlZm9yZSBhdHRhY2hlZCBjYXVzaW5nIHVubmVjZXNzYXJ5IHdvcmsuCiAgICAgICAgdGhpcy5saXN0ZW4odGhpcywgJ2lyb24tcmVzaXplJywgJ19yZXNpemVIYW5kbGVyJyk7CiAgICAgIH0sCgogICAgICBkZXRhY2hlZDogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy51bmxpc3Rlbih0aGlzLCAnaXJvbi1yZXNpemUnLCAnX3Jlc2l6ZUhhbmRsZXInKTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBJbnZva2UgdGhpcyBtZXRob2QgaWYgeW91IGR5bmFtaWNhbGx5IHVwZGF0ZSB0aGUgdmlld3BvcnQncwogICAgICAgKiBzaXplIG9yIENTUyBwYWRkaW5nLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHVwZGF0ZVZpZXdwb3J0Qm91bmRhcmllcwogICAgICAgKi8KICAgICAgdXBkYXRlVmlld3BvcnRCb3VuZGFyaWVzOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc3R5bGVzID0gd2luZG93LmdldENvbXB1dGVkU3R5bGUodGhpcyk7CiAgICAgICAgdGhpcy5fc2Nyb2xsZXJQYWRkaW5nVG9wID0gdGhpcy5zY3JvbGxUYXJnZXQgPT09IHRoaXMgPyAwIDogcGFyc2VJbnQoc3R5bGVzWydwYWRkaW5nLXRvcCddLCAxMCk7CiAgICAgICAgdGhpcy5faXNSVEwgPSBCb29sZWFuKHN0eWxlcy5kaXJlY3Rpb24gPT09ICdydGwnKTsKICAgICAgICB0aGlzLl92aWV3cG9ydFdpZHRoID0gdGhpcy4kLml0ZW1zLm9mZnNldFdpZHRoOwogICAgICAgIHRoaXMuX3ZpZXdwb3J0SGVpZ2h0ID0gdGhpcy5fc2Nyb2xsVGFyZ2V0SGVpZ2h0OwogICAgICAgIHRoaXMuZ3JpZCAmJiB0aGlzLl91cGRhdGVHcmlkTWV0cmljcygpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJlY3ljbGVzIHRoZSBwaHlzaWNhbCBpdGVtcyB3aGVuIG5lZWRlZC4KICAgICAgICovCiAgICAgIF9zY3JvbGxIYW5kbGVyOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgc2Nyb2xsVG9wID0gTWF0aC5tYXgoMCwgTWF0aC5taW4odGhpcy5fbWF4U2Nyb2xsVG9wLCB0aGlzLl9zY3JvbGxUb3ApKTsKICAgICAgICB2YXIgZGVsdGEgPSBzY3JvbGxUb3AgLSB0aGlzLl9zY3JvbGxQb3NpdGlvbjsKICAgICAgICB2YXIgaXNTY3JvbGxpbmdEb3duID0gZGVsdGEgPj0gMDsKICAgICAgICAvLyBUcmFjayB0aGUgY3VycmVudCBzY3JvbGwgcG9zaXRpb24uCiAgICAgICAgdGhpcy5fc2Nyb2xsUG9zaXRpb24gPSBzY3JvbGxUb3A7CiAgICAgICAgLy8gQ2xlYXIgaW5kZXhlcyBmb3IgZmlyc3QgYW5kIGxhc3QgdmlzaWJsZSBpbmRleGVzLgogICAgICAgIHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICB0aGlzLl9sYXN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICAvLyBSYW5kb20gYWNjZXNzLgogICAgICAgIGlmIChNYXRoLmFicyhkZWx0YSkgPiB0aGlzLl9waHlzaWNhbFNpemUgJiYgdGhpcy5fcGh5c2ljYWxTaXplID4gMCkgewogICAgICAgICAgZGVsdGEgPSBkZWx0YSAtIHRoaXMuX3Njcm9sbE9mZnNldDsKICAgICAgICAgIHZhciBpZHhBZGp1c3RtZW50ID0gTWF0aC5yb3VuZChkZWx0YSAvIHRoaXMuX3BoeXNpY2FsQXZlcmFnZSkgKiB0aGlzLl9pdGVtc1BlclJvdzsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydCA9IHRoaXMuX3ZpcnR1YWxTdGFydCArIGlkeEFkanVzdG1lbnQ7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFN0YXJ0ID0gdGhpcy5fcGh5c2ljYWxTdGFydCArIGlkeEFkanVzdG1lbnQ7CiAgICAgICAgICAvLyBFc3RpbWF0ZSBuZXcgcGh5c2ljYWwgb2Zmc2V0LgogICAgICAgICAgdGhpcy5fcGh5c2ljYWxUb3AgPSBNYXRoLmZsb29yKHRoaXMuX3ZpcnR1YWxTdGFydCAvIHRoaXMuX2l0ZW1zUGVyUm93KSAqIHRoaXMuX3BoeXNpY2FsQXZlcmFnZTsKICAgICAgICAgIHRoaXMuX3VwZGF0ZSgpOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5fcGh5c2ljYWxDb3VudCA+IDApIHsKICAgICAgICAgIHZhciByZXVzYWJsZXMgPSB0aGlzLl9nZXRSZXVzYWJsZXMoaXNTY3JvbGxpbmdEb3duKTsKICAgICAgICAgIGlmIChpc1Njcm9sbGluZ0Rvd24pIHsKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxUb3AgPSByZXVzYWJsZXMucGh5c2ljYWxUb3A7CiAgICAgICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydCA9IHRoaXMuX3ZpcnR1YWxTdGFydCArIHJldXNhYmxlcy5pbmRleGVzLmxlbmd0aDsKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxTdGFydCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQgKyByZXVzYWJsZXMuaW5kZXhlcy5sZW5ndGg7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgLSByZXVzYWJsZXMuaW5kZXhlcy5sZW5ndGg7CiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnQgPSB0aGlzLl9waHlzaWNhbFN0YXJ0IC0gcmV1c2FibGVzLmluZGV4ZXMubGVuZ3RoOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fdXBkYXRlKHJldXNhYmxlcy5pbmRleGVzLCBpc1Njcm9sbGluZ0Rvd24gPyBudWxsIDogcmV1c2FibGVzLmluZGV4ZXMpOwogICAgICAgICAgdGhpcy5fZGVib3VuY2UoJ19pbmNyZWFzZVBvb2xJZk5lZWRlZCcsIHRoaXMuX2luY3JlYXNlUG9vbElmTmVlZGVkLmJpbmQodGhpcywgMCksIE1JQ1JPX1RBU0spOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGFuIG9iamVjdCB0aGF0IGNvbnRhaW5zIHRoZSBpbmRleGVzIG9mIHRoZSBwaHlzaWNhbCBpdGVtcwogICAgICAgKiB0aGF0IG1pZ2h0IGJlIHJldXNlZCBhbmQgdGhlIHBoeXNpY2FsVG9wLgogICAgICAgKgogICAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IGZyb21Ub3AgSWYgdGhlIHBvdGVudGlhbCByZXVzYWJsZSBpdGVtcyBhcmUgYWJvdmUgdGhlIHNjcm9sbGluZyByZWdpb24uCiAgICAgICAqLwogICAgICBfZ2V0UmV1c2FibGVzOiBmdW5jdGlvbihmcm9tVG9wKSB7CiAgICAgICAgdmFyIGl0aCwgb2Zmc2V0Q29udGVudCwgcGh5c2ljYWxJdGVtSGVpZ2h0OwogICAgICAgIHZhciBpZHhzID0gW107CiAgICAgICAgdmFyIHByb3RlY3RlZE9mZnNldENvbnRlbnQgPSB0aGlzLl9oaWRkZW5Db250ZW50U2l6ZSAqIHRoaXMuX3JhdGlvOwogICAgICAgIHZhciB2aXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQ7CiAgICAgICAgdmFyIHZpcnR1YWxFbmQgPSB0aGlzLl92aXJ0dWFsRW5kOwogICAgICAgIHZhciBwaHlzaWNhbENvdW50ID0gdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgICB2YXIgdG9wID0gdGhpcy5fcGh5c2ljYWxUb3AgKyB0aGlzLl9zY3JvbGxPZmZzZXQ7CiAgICAgICAgdmFyIGJvdHRvbSA9IHRoaXMuX3BoeXNpY2FsQm90dG9tICsgdGhpcy5fc2Nyb2xsT2Zmc2V0OwogICAgICAgIHZhciBzY3JvbGxUb3AgPSB0aGlzLl9zY3JvbGxUb3A7CiAgICAgICAgdmFyIHNjcm9sbEJvdHRvbSA9IHRoaXMuX3Njcm9sbEJvdHRvbTsKCiAgICAgICAgaWYgKGZyb21Ub3ApIHsKICAgICAgICAgIGl0aCA9IHRoaXMuX3BoeXNpY2FsU3RhcnQ7CiAgICAgICAgICBvZmZzZXRDb250ZW50ID0gc2Nyb2xsVG9wIC0gdG9wOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBpdGggPSB0aGlzLl9waHlzaWNhbEVuZDsKICAgICAgICAgIG9mZnNldENvbnRlbnQgPSBib3R0b20gLSBzY3JvbGxCb3R0b207CiAgICAgICAgfQogICAgICAgIC8vIGVzbGludC1kaXNhYmxlLW5leHQtbGluZSBuby1jb25zdGFudC1jb25kaXRpb24KICAgICAgICB3aGlsZSAodHJ1ZSkgewogICAgICAgICAgcGh5c2ljYWxJdGVtSGVpZ2h0ID0gdGhpcy5fZ2V0UGh5c2ljYWxTaXplSW5jcmVtZW50KGl0aCk7CiAgICAgICAgICBvZmZzZXRDb250ZW50ID0gb2Zmc2V0Q29udGVudCAtIHBoeXNpY2FsSXRlbUhlaWdodDsKICAgICAgICAgIGlmIChpZHhzLmxlbmd0aCA+PSBwaHlzaWNhbENvdW50IHx8IG9mZnNldENvbnRlbnQgPD0gcHJvdGVjdGVkT2Zmc2V0Q29udGVudCkgewogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChmcm9tVG9wKSB7CiAgICAgICAgICAgIC8vIENoZWNrIHRoYXQgaW5kZXggaXMgd2l0aGluIHRoZSB2YWxpZCByYW5nZS4KICAgICAgICAgICAgaWYgKHZpcnR1YWxFbmQgKyBpZHhzLmxlbmd0aCArIDEgPj0gdGhpcy5fdmlydHVhbENvdW50KSB7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQ2hlY2sgdGhhdCB0aGUgaW5kZXggaXMgbm90IHZpc2libGUuCiAgICAgICAgICAgIGlmICh0b3AgKyBwaHlzaWNhbEl0ZW1IZWlnaHQgPj0gc2Nyb2xsVG9wIC0gdGhpcy5fc2Nyb2xsT2Zmc2V0KSB7CiAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWR4cy5wdXNoKGl0aCk7CiAgICAgICAgICAgIHRvcCA9IHRvcCArIHBoeXNpY2FsSXRlbUhlaWdodDsKICAgICAgICAgICAgaXRoID0gKGl0aCArIDEpICUgcGh5c2ljYWxDb3VudDsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIENoZWNrIHRoYXQgaW5kZXggaXMgd2l0aGluIHRoZSB2YWxpZCByYW5nZS4KICAgICAgICAgICAgaWYgKHZpcnR1YWxTdGFydCAtIGlkeHMubGVuZ3RoIDw9IDApIHsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBDaGVjayB0aGF0IHRoZSBpbmRleCBpcyBub3QgdmlzaWJsZS4KICAgICAgICAgICAgaWYgKHRvcCArIHRoaXMuX3BoeXNpY2FsU2l6ZSAtIHBoeXNpY2FsSXRlbUhlaWdodCA8PSBzY3JvbGxCb3R0b20pIHsKICAgICAgICAgICAgICBicmVhazsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZHhzLnB1c2goaXRoKTsKICAgICAgICAgICAgdG9wID0gdG9wIC0gcGh5c2ljYWxJdGVtSGVpZ2h0OwogICAgICAgICAgICBpdGggPSAoaXRoID09PSAwKSA/IHBoeXNpY2FsQ291bnQgLSAxIDogaXRoIC0gMTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIHtpbmRleGVzOiBpZHhzLCBwaHlzaWNhbFRvcDogdG9wIC0gdGhpcy5fc2Nyb2xsT2Zmc2V0fTsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBVcGRhdGUgdGhlIGxpc3Qgb2YgaXRlbXMsIHN0YXJ0aW5nIGZyb20gdGhlIGBfdmlydHVhbFN0YXJ0YCBpdGVtLgogICAgICAgKiBAcGFyYW0geyFBcnJheTxudW1iZXI+PX0gaXRlbVNldAogICAgICAgKiBAcGFyYW0geyFBcnJheTxudW1iZXI+PX0gbW92aW5nVXAKICAgICAgICovCiAgICAgIF91cGRhdGU6IGZ1bmN0aW9uKGl0ZW1TZXQsIG1vdmluZ1VwKSB7CiAgICAgICAgaWYgKChpdGVtU2V0ICYmIGl0ZW1TZXQubGVuZ3RoID09PSAwKSB8fCB0aGlzLl9waHlzaWNhbENvdW50ID09PSAwKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIHRoaXMuX21hbmFnZUZvY3VzKCk7CiAgICAgICAgdGhpcy5fYXNzaWduTW9kZWxzKGl0ZW1TZXQpOwogICAgICAgIHRoaXMuX3VwZGF0ZU1ldHJpY3MoaXRlbVNldCk7CiAgICAgICAgLy8gQWRqdXN0IG9mZnNldCBhZnRlciBtZWFzdXJpbmcuCiAgICAgICAgaWYgKG1vdmluZ1VwKSB7CiAgICAgICAgICB3aGlsZSAobW92aW5nVXAubGVuZ3RoKSB7CiAgICAgICAgICAgIHZhciBpZHggPSBtb3ZpbmdVcC5wb3AoKTsKICAgICAgICAgICAgdGhpcy5fcGh5c2ljYWxUb3AgLT0gdGhpcy5fZ2V0UGh5c2ljYWxTaXplSW5jcmVtZW50KGlkeCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHRoaXMuX3Bvc2l0aW9uSXRlbXMoKTsKICAgICAgICB0aGlzLl91cGRhdGVTY3JvbGxlclNpemUoKTsKICAgICAgfSwKCiAgICAgIF9pc0NsaWVudEZ1bGw6IGZ1bmN0aW9uKCkgewogICAgICAgIHJldHVybiB0aGlzLl9zY3JvbGxCb3R0b20gIT0gMCAmJiB0aGlzLl9waHlzaWNhbEJvdHRvbSAtIDEgPj0gdGhpcy5fc2Nyb2xsQm90dG9tICYmCiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsVG9wIDw9IHRoaXMuX3Njcm9sbFBvc2l0aW9uOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEluY3JlYXNlcyB0aGUgcG9vbCBzaXplLgogICAgICAgKi8KICAgICAgX2luY3JlYXNlUG9vbElmTmVlZGVkOiBmdW5jdGlvbihjb3VudCkgewogICAgICAgIHZhciBuZXh0UGh5c2ljYWxDb3VudCA9IHRoaXMuX2NsYW1wKHRoaXMuX3BoeXNpY2FsQ291bnQgKyBjb3VudCwKICAgICAgICAgIERFRkFVTFRfUEhZU0lDQUxfQ09VTlQkMSwgdGhpcy5fdmlydHVhbENvdW50IC0gdGhpcy5fdmlydHVhbFN0YXJ0KTsKICAgICAgICBuZXh0UGh5c2ljYWxDb3VudCA9IHRoaXMuX2NvbnZlcnRJbmRleFRvQ29tcGxldGVSb3cobmV4dFBoeXNpY2FsQ291bnQpOwogICAgICAgIHZhciBkZWx0YSA9IG5leHRQaHlzaWNhbENvdW50IC0gdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgICB2YXIgbmV4dEluY3JlYXNlID0gTWF0aC5yb3VuZCh0aGlzLl9waHlzaWNhbENvdW50ICogMC41KTsKCiAgICAgICAgaWYgKGRlbHRhIDwgMCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAoZGVsdGEgPiAwKSB7CiAgICAgICAgICB2YXIgdHMgPSB3aW5kb3cucGVyZm9ybWFuY2Uubm93KCk7CiAgICAgICAgICAvLyBDb25jYXQgYXJyYXlzIGluIHBsYWNlLgogICAgICAgICAgW10ucHVzaC5hcHBseSh0aGlzLl9waHlzaWNhbEl0ZW1zLCB0aGlzLl9jcmVhdGVQb29sKGRlbHRhKSk7CiAgICAgICAgICAvLyBQdXNoIDBzIGludG8gcGh5c2ljYWxTaXplcy4gQ2FuJ3QgdXNlIEFycmF5LmZpbGwgYmVjYXVzZSBJRTExIGRvZXNuJ3Qgc3VwcG9ydCBpdC4KICAgICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwgZGVsdGE7IGkrKykgewogICAgICAgICAgICB0aGlzLl9waHlzaWNhbFNpemVzLnB1c2goMCk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9waHlzaWNhbENvdW50ID0gdGhpcy5fcGh5c2ljYWxDb3VudCArIGRlbHRhOwogICAgICAgICAgLy8gVXBkYXRlIHRoZSBwaHlzaWNhbCBzdGFydCBpZiBpdCBuZWVkcyB0byBwcmVzZXJ2ZSB0aGUgbW9kZWwgb2YgdGhlIGZvY3VzZWQgaXRlbS4KICAgICAgICAgIC8vIEluIHRoaXMgc2l0dWF0aW9uLCB0aGUgZm9jdXNlZCBpdGVtIGlzIGN1cnJlbnRseSByZW5kZXJlZCBhbmQgaXRzIG1vZGVsIHdvdWxkCiAgICAgICAgICAvLyBoYXZlIGNoYW5nZWQgYWZ0ZXIgaW5jcmVhc2luZyB0aGUgcG9vbCBpZiB0aGUgcGh5c2ljYWwgc3RhcnQgcmVtYWluZWQgdW5jaGFuZ2VkLgogICAgICAgICAgaWYgKHRoaXMuX3BoeXNpY2FsU3RhcnQgPiB0aGlzLl9waHlzaWNhbEVuZCAmJgogICAgICAgICAgICAgIHRoaXMuX2lzSW5kZXhSZW5kZXJlZCh0aGlzLl9mb2N1c2VkVmlydHVhbEluZGV4KSAmJgogICAgICAgICAgICAgIHRoaXMuX2dldFBoeXNpY2FsSW5kZXgodGhpcy5fZm9jdXNlZFZpcnR1YWxJbmRleCkgPCB0aGlzLl9waHlzaWNhbEVuZCkgewogICAgICAgICAgICB0aGlzLl9waHlzaWNhbFN0YXJ0ID0gdGhpcy5fcGh5c2ljYWxTdGFydCArIGRlbHRhOwogICAgICAgICAgfQogICAgICAgICAgdGhpcy5fdXBkYXRlKCk7CiAgICAgICAgICB0aGlzLl90ZW1wbGF0ZUNvc3QgPSAod2luZG93LnBlcmZvcm1hbmNlLm5vdygpIC0gdHMpIC8gZGVsdGE7CiAgICAgICAgICBuZXh0SW5jcmVhc2UgPSBNYXRoLnJvdW5kKHRoaXMuX3BoeXNpY2FsQ291bnQgKiAwLjUpOwogICAgICAgIH0KICAgICAgICAvLyBUaGUgdXBwZXIgYm91bmRzIGlzIG5vdCBmaXhlZCB3aGVuIGRlYWxpbmcgd2l0aCBhIGdyaWQgdGhhdCBkb2Vzbid0CiAgICAgICAgLy8gZmlsbCBpdCdzIGxhc3Qgcm93IHdpdGggdGhlIGV4YWN0IG51bWJlciBvZiBpdGVtcyBwZXIgcm93LgogICAgICAgIGlmICh0aGlzLl92aXJ0dWFsRW5kID49IHRoaXMuX3ZpcnR1YWxDb3VudCAtIDEgfHwgbmV4dEluY3JlYXNlID09PSAwKSA7IGVsc2UgaWYgKCF0aGlzLl9pc0NsaWVudEZ1bGwoKSkgewogICAgICAgICAgdGhpcy5fZGVib3VuY2UoCiAgICAgICAgICAgICdfaW5jcmVhc2VQb29sSWZOZWVkZWQnLAogICAgICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZC5iaW5kKAogICAgICAgICAgICAgIHRoaXMsCiAgICAgICAgICAgICAgbmV4dEluY3JlYXNlCiAgICAgICAgICAgICksIE1JQ1JPX1RBU0spOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5fcGh5c2ljYWxTaXplIDwgdGhpcy5fb3B0UGh5c2ljYWxTaXplKSB7CiAgICAgICAgICAvLyBZaWVsZCBhbmQgaW5jcmVhc2UgdGhlIHBvb2wgZHVyaW5nIGlkbGUgdGltZSB1bnRpbCB0aGUgcGh5c2ljYWwgc2l6ZSBpcyBvcHRpbWFsLgogICAgICAgICAgdGhpcy5fZGVib3VuY2UoCiAgICAgICAgICAgICdfaW5jcmVhc2VQb29sSWZOZWVkZWQnLAogICAgICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZC5iaW5kKAogICAgICAgICAgICAgIHRoaXMsCiAgICAgICAgICAgICAgdGhpcy5fY2xhbXAoTWF0aC5yb3VuZCg1MCAvIHRoaXMuX3RlbXBsYXRlQ29zdCksIDEsIG5leHRJbmNyZWFzZSkKICAgICAgICAgICAgKSwgSURMRV9USU1FKTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVuZGVycyB0aGUgYSBuZXcgbGlzdC4KICAgICAgICovCiAgICAgIF9yZW5kZXI6IGZ1bmN0aW9uKCkgewogICAgICAgIGlmICghdGhpcy5pc0F0dGFjaGVkIHx8ICF0aGlzLl9pc1Zpc2libGUpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CiAgICAgICAgaWYgKHRoaXMuX3BoeXNpY2FsQ291bnQgIT09IDApIHsKICAgICAgICAgIHZhciByZXVzYWJsZXMgPSB0aGlzLl9nZXRSZXVzYWJsZXModHJ1ZSk7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IHJldXNhYmxlcy5waHlzaWNhbFRvcDsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydCA9IHRoaXMuX3ZpcnR1YWxTdGFydCArIHJldXNhYmxlcy5pbmRleGVzLmxlbmd0aDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU3RhcnQgPSB0aGlzLl9waHlzaWNhbFN0YXJ0ICsgcmV1c2FibGVzLmluZGV4ZXMubGVuZ3RoOwogICAgICAgICAgdGhpcy5fdXBkYXRlKHJldXNhYmxlcy5pbmRleGVzKTsKICAgICAgICAgIHRoaXMuX3VwZGF0ZSgpOwogICAgICAgICAgdGhpcy5faW5jcmVhc2VQb29sSWZOZWVkZWQoMCk7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl92aXJ0dWFsQ291bnQgPiAwKSB7CiAgICAgICAgICAvLyBJbml0aWFsIHJlbmRlcgogICAgICAgICAgdGhpcy51cGRhdGVWaWV3cG9ydEJvdW5kYXJpZXMoKTsKICAgICAgICAgIHRoaXMuX2luY3JlYXNlUG9vbElmTmVlZGVkKERFRkFVTFRfUEhZU0lDQUxfQ09VTlQkMSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENhbGxlZCB3aGVuIHRoZSBpdGVtcyBoYXZlIGNoYW5nZWQuIFRoYXQgaXMsIHJlYXNzaWdubWVudHMKICAgICAgICogdG8gYGl0ZW1zYCwgc3BsaWNlcyBvciB1cGRhdGVzIHRvIGEgc2luZ2xlIGl0ZW0uCiAgICAgICAqLwogICAgICBfaXRlbXNDaGFuZ2VkOiBmdW5jdGlvbihjaGFuZ2UpIHsKICAgICAgICBpZiAoY2hhbmdlLnBhdGggPT09ICdpdGVtcycpIHsKICAgICAgICAgIHRoaXMuX3ZpcnR1YWxTdGFydCA9IDA7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IDA7CiAgICAgICAgICB0aGlzLl92aXJ0dWFsQ291bnQgPSB0aGlzLml0ZW1zID8gdGhpcy5pdGVtcy5sZW5ndGggOiAwOwogICAgICAgICAgdGhpcy5fY29sbGVjdGlvbiA9IHRoaXMuaXRlbXMgJiYgdW5kZWZpbmVkID8KICAgICAgICAgICAgdW5kZWZpbmVkLmdldCh0aGlzLml0ZW1zKSA6IG51bGw7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbEluZGV4Rm9yS2V5ID0ge307CiAgICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgICAgICB0aGlzLl9sYXN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQ291bnQgPSB0aGlzLl9waHlzaWNhbENvdW50IHx8IDA7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbEl0ZW1zID0gdGhpcy5fcGh5c2ljYWxJdGVtcyB8fCBbXTsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU2l6ZXMgPSB0aGlzLl9waHlzaWNhbFNpemVzIHx8IFtdOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTdGFydCA9IDA7CiAgICAgICAgICBpZiAodGhpcy5fc2Nyb2xsVG9wID4gdGhpcy5fc2Nyb2xsT2Zmc2V0KSB7CiAgICAgICAgICAgIHRoaXMuX3Jlc2V0U2Nyb2xsUG9zaXRpb24oMCk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9yZW1vdmVGb2N1c2VkSXRlbSgpOwogICAgICAgICAgdGhpcy5fZGVib3VuY2UoJ19yZW5kZXInLCB0aGlzLl9yZW5kZXIsIEFOSU1BVElPTl9GUkFNRSk7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEV4ZWN1dGVzIGEgcHJvdmlkZWQgZnVuY3Rpb24gcGVyIGV2ZXJ5IHBoeXNpY2FsIGluZGV4IGluIGBpdGVtU2V0YAogICAgICAgKiBgaXRlbVNldGAgZGVmYXVsdCB2YWx1ZSBpcyBlcXVpdmFsZW50IHRvIHRoZSBlbnRpcmUgc2V0IG9mIHBoeXNpY2FsIGluZGV4ZXMuCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7IWZ1bmN0aW9uKG51bWJlciwgbnVtYmVyKX0gZm4KICAgICAgICogQHBhcmFtIHshQXJyYXk8bnVtYmVyPj19IGl0ZW1TZXQKICAgICAgICovCiAgICAgIF9pdGVyYXRlSXRlbXM6IGZ1bmN0aW9uKGZuLCBpdGVtU2V0KSB7CiAgICAgICAgdmFyIHBpZHgsIHZpZHgsIHJ0biwgaTsKCiAgICAgICAgaWYgKGFyZ3VtZW50cy5sZW5ndGggPT09IDIgJiYgaXRlbVNldCkgewogICAgICAgICAgZm9yIChpID0gMDsgaSA8IGl0ZW1TZXQubGVuZ3RoOyBpKyspIHsKICAgICAgICAgICAgcGlkeCA9IGl0ZW1TZXRbaV07CiAgICAgICAgICAgIHZpZHggPSB0aGlzLl9jb21wdXRlVmlkeChwaWR4KTsKICAgICAgICAgICAgaWYgKChydG4gPSBmbi5jYWxsKHRoaXMsIHBpZHgsIHZpZHgpKSAhPSBudWxsKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHJ0bjsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBwaWR4ID0gdGhpcy5fcGh5c2ljYWxTdGFydDsKICAgICAgICAgIHZpZHggPSB0aGlzLl92aXJ0dWFsU3RhcnQ7CiAgICAgICAgICBmb3IgKDsgcGlkeCA8IHRoaXMuX3BoeXNpY2FsQ291bnQ7IHBpZHgrKywgdmlkeCsrKSB7CiAgICAgICAgICAgIGlmICgocnRuID0gZm4uY2FsbCh0aGlzLCBwaWR4LCB2aWR4KSkgIT0gbnVsbCkgewogICAgICAgICAgICAgIHJldHVybiBydG47CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICAgIGZvciAocGlkeCA9IDA7IHBpZHggPCB0aGlzLl9waHlzaWNhbFN0YXJ0OyBwaWR4KyssIHZpZHgrKykgewogICAgICAgICAgICBpZiAoKHJ0biA9IGZuLmNhbGwodGhpcywgcGlkeCwgdmlkeCkpICE9IG51bGwpIHsKICAgICAgICAgICAgICByZXR1cm4gcnRuOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgdGhlIHZpcnR1YWwgaW5kZXggZm9yIGEgZ2l2ZW4gcGh5c2ljYWwgaW5kZXgKICAgICAgICoKICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHBpZHggUGh5c2ljYWwgaW5kZXgKICAgICAgICogQHJldHVybiB7bnVtYmVyfQogICAgICAgKi8KICAgICAgX2NvbXB1dGVWaWR4OiBmdW5jdGlvbihwaWR4KSB7CiAgICAgICAgaWYgKHBpZHggPj0gdGhpcy5fcGh5c2ljYWxTdGFydCkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX3ZpcnR1YWxTdGFydCArIChwaWR4IC0gdGhpcy5fcGh5c2ljYWxTdGFydCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLl92aXJ0dWFsU3RhcnQgKyAodGhpcy5fcGh5c2ljYWxDb3VudCAtIHRoaXMuX3BoeXNpY2FsU3RhcnQpICsgcGlkeDsKICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBVcGRhdGVzIHRoZSBoZWlnaHQgZm9yIGEgZ2l2ZW4gc2V0IG9mIGl0ZW1zLgogICAgICAgKgogICAgICAgKiBAcGFyYW0geyFBcnJheTxudW1iZXI+PX0gaXRlbVNldAogICAgICAgKi8KICAgICAgX3VwZGF0ZU1ldHJpY3M6IGZ1bmN0aW9uKGl0ZW1TZXQpIHsKICAgICAgICAvLyBNYWtlIHN1cmUgd2UgZGlzdHJpYnV0ZWQgYWxsIHRoZSBwaHlzaWNhbCBpdGVtcwogICAgICAgIC8vIHNvIHdlIGNhbiBtZWFzdXJlIHRoZW0uCiAgICAgICAgZmx1c2ggPyBmbHVzaCgpIDogZmx1c2goKTsKCiAgICAgICAgdmFyIG5ld1BoeXNpY2FsU2l6ZSA9IDA7CiAgICAgICAgdmFyIG9sZFBoeXNpY2FsU2l6ZSA9IDA7CiAgICAgICAgdmFyIHByZXZBdmdDb3VudCA9IHRoaXMuX3BoeXNpY2FsQXZlcmFnZUNvdW50OwogICAgICAgIHZhciBwcmV2UGh5c2ljYWxBdmcgPSB0aGlzLl9waHlzaWNhbEF2ZXJhZ2U7CgogICAgICAgIHRoaXMuX2l0ZXJhdGVJdGVtcyhmdW5jdGlvbihwaWR4LCB2aWR4KSB7CiAgICAgICAgICBvbGRQaHlzaWNhbFNpemUgKz0gdGhpcy5fcGh5c2ljYWxTaXplc1twaWR4XTsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU2l6ZXNbcGlkeF0gPSB0aGlzLl9waHlzaWNhbEl0ZW1zW3BpZHhdLm9mZnNldEhlaWdodDsKICAgICAgICAgIG5ld1BoeXNpY2FsU2l6ZSArPSB0aGlzLl9waHlzaWNhbFNpemVzW3BpZHhdOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlQ291bnQgKz0gdGhpcy5fcGh5c2ljYWxTaXplc1twaWR4XSA/IDEgOiAwOwogICAgICAgIH0sIGl0ZW1TZXQpOwoKICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICB0aGlzLl91cGRhdGVHcmlkTWV0cmljcygpOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxTaXplID0gTWF0aC5jZWlsKHRoaXMuX3BoeXNpY2FsQ291bnQgLyB0aGlzLl9pdGVtc1BlclJvdykgKiB0aGlzLl9yb3dIZWlnaHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIG9sZFBoeXNpY2FsU2l6ZSA9ICh0aGlzLl9pdGVtc1BlclJvdyA9PT0gMSkgPwogICAgICAgICAgICBvbGRQaHlzaWNhbFNpemUgOgogICAgICAgICAgICBNYXRoLmNlaWwodGhpcy5fcGh5c2ljYWxDb3VudCAvIHRoaXMuX2l0ZW1zUGVyUm93KSAqIHRoaXMuX3Jvd0hlaWdodDsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsU2l6ZSA9IHRoaXMuX3BoeXNpY2FsU2l6ZSArIG5ld1BoeXNpY2FsU2l6ZSAtIG9sZFBoeXNpY2FsU2l6ZTsKICAgICAgICAgIHRoaXMuX2l0ZW1zUGVyUm93ID0gMTsKICAgICAgICB9CiAgICAgICAgLy8gVXBkYXRlIHRoZSBhdmVyYWdlIGlmIGl0IG1lYXN1cmVkIHNvbWV0aGluZy4KICAgICAgICBpZiAodGhpcy5fcGh5c2ljYWxBdmVyYWdlQ291bnQgIT09IHByZXZBdmdDb3VudCkgewogICAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlID0gTWF0aC5yb3VuZCgKICAgICAgICAgICAgKChwcmV2UGh5c2ljYWxBdmcgKiBwcmV2QXZnQ291bnQpICsgbmV3UGh5c2ljYWxTaXplKSAvCiAgICAgICAgICAgIHRoaXMuX3BoeXNpY2FsQXZlcmFnZUNvdW50KTsKICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogVXBkYXRlcyB0aGUgcG9zaXRpb24gb2YgdGhlIHBoeXNpY2FsIGl0ZW1zLgogICAgICAgKi8KICAgICAgX3Bvc2l0aW9uSXRlbXM6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2FkanVzdFNjcm9sbFBvc2l0aW9uKCk7CgogICAgICAgIHZhciB5ID0gdGhpcy5fcGh5c2ljYWxUb3A7CgogICAgICAgIHRoaXMuX2l0ZXJhdGVJdGVtcyhmdW5jdGlvbihwaWR4LCB2aWR4KSB7CiAgICAgICAgICB0aGlzLnRyYW5zbGF0ZTNkKDAsIHkgKyAncHgnLCAwLCB0aGlzLl9waHlzaWNhbEl0ZW1zW3BpZHhdKTsKICAgICAgICAgIHkgKz0gdGhpcy5fcGh5c2ljYWxTaXplc1twaWR4XTsKICAgICAgICB9KTsKICAgICAgfSwKCiAgICAgIF9nZXRQaHlzaWNhbFNpemVJbmNyZW1lbnQ6IGZ1bmN0aW9uKHBpZHgpIHsKICAgICAgICBpZiAoIXRoaXMuZ3JpZCkgewogICAgICAgICAgcmV0dXJuIHRoaXMuX3BoeXNpY2FsU2l6ZXNbcGlkeF07CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLl9jb21wdXRlVmlkeChwaWR4KSAlIHRoaXMuX2l0ZW1zUGVyUm93ICE9PSB0aGlzLl9pdGVtc1BlclJvdyAtIDEpIHsKICAgICAgICAgIHJldHVybiAwOwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy5fcm93SGVpZ2h0OwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIEFkanVzdHMgdGhlIHNjcm9sbCBwb3NpdGlvbiB3aGVuIGl0IHdhcyBvdmVyZXN0aW1hdGVkLgogICAgICAgKi8KICAgICAgX2FkanVzdFNjcm9sbFBvc2l0aW9uOiBmdW5jdGlvbigpIHsKICAgICAgICB2YXIgZGVsdGFIZWlnaHQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgPT09IDAgPyB0aGlzLl9waHlzaWNhbFRvcCA6IE1hdGgubWluKHRoaXMuX3Njcm9sbFBvc2l0aW9uICsgdGhpcy5fcGh5c2ljYWxUb3AsIDApOwogICAgICAgIC8vIE5vdGU6IHRoZSBkZWx0YSBjYW4gYmUgcG9zaXRpdmUgb3IgbmVnYXRpdmUuCiAgICAgICAgaWYgKGRlbHRhSGVpZ2h0ICE9PSAwKSB7CiAgICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IHRoaXMuX3BoeXNpY2FsVG9wIC0gZGVsdGFIZWlnaHQ7CiAgICAgICAgICB2YXIgc2Nyb2xsVG9wID0gdGhpcy5fc2Nyb2xsVG9wOwogICAgICAgICAgLy8ganVraW5nIHNjcm9sbCBwb3NpdGlvbiBkdXJpbmcgaW50ZXJpYWwgc2Nyb2xsaW5nIG9uIGlPUyBpcyBubyBidWVubwogICAgICAgICAgaWYgKCFJT1NfVE9VQ0hfU0NST0xMSU5HJDEgJiYgc2Nyb2xsVG9wID4gMCkgewogICAgICAgICAgICB0aGlzLl9yZXNldFNjcm9sbFBvc2l0aW9uKHNjcm9sbFRvcCAtIGRlbHRhSGVpZ2h0KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogU2V0cyB0aGUgcG9zaXRpb24gb2YgdGhlIHNjcm9sbC4KICAgICAgICovCiAgICAgIF9yZXNldFNjcm9sbFBvc2l0aW9uOiBmdW5jdGlvbihwb3MpIHsKICAgICAgICBpZiAodGhpcy5zY3JvbGxUYXJnZXQgJiYgcG9zID49IDApIHsKICAgICAgICAgIHRoaXMuX3Njcm9sbFRvcCA9IHBvczsKICAgICAgICAgIHRoaXMuX3Njcm9sbFBvc2l0aW9uID0gdGhpcy5fc2Nyb2xsVG9wOwogICAgICAgIH0KICAgICAgfSwKCiAgICAgIC8qKgogICAgICAgKiBTZXRzIHRoZSBzY3JvbGwgaGVpZ2h0LCB0aGF0J3MgdGhlIGhlaWdodCBvZiB0aGUgY29udGVudCwKICAgICAgICoKICAgICAgICogQHBhcmFtIHtib29sZWFuPX0gZm9yY2VVcGRhdGUgSWYgdHJ1ZSwgdXBkYXRlcyB0aGUgaGVpZ2h0IG5vIG1hdHRlciB3aGF0LgogICAgICAgKi8KICAgICAgX3VwZGF0ZVNjcm9sbGVyU2l6ZTogZnVuY3Rpb24oZm9yY2VVcGRhdGUpIHsKICAgICAgICBpZiAodGhpcy5ncmlkKSB7CiAgICAgICAgICB0aGlzLl9lc3RTY3JvbGxIZWlnaHQgPSB0aGlzLl92aXJ0dWFsUm93Q291bnQgKiB0aGlzLl9yb3dIZWlnaHQ7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX2VzdFNjcm9sbEhlaWdodCA9ICh0aGlzLl9waHlzaWNhbEJvdHRvbSArCiAgICAgICAgICAgICAgTWF0aC5tYXgodGhpcy5fdmlydHVhbENvdW50IC0gdGhpcy5fcGh5c2ljYWxDb3VudCAtIHRoaXMuX3ZpcnR1YWxTdGFydCwgMCkgKiB0aGlzLl9waHlzaWNhbEF2ZXJhZ2UpOwogICAgICAgIH0KICAgICAgICBmb3JjZVVwZGF0ZSA9IGZvcmNlVXBkYXRlIHx8IHRoaXMuX3Njcm9sbEhlaWdodCA9PT0gMDsKICAgICAgICBmb3JjZVVwZGF0ZSA9IGZvcmNlVXBkYXRlIHx8IHRoaXMuX3Njcm9sbFBvc2l0aW9uID49IHRoaXMuX2VzdFNjcm9sbEhlaWdodCAtIHRoaXMuX3BoeXNpY2FsU2l6ZTsKICAgICAgICBmb3JjZVVwZGF0ZSA9IGZvcmNlVXBkYXRlIHx8IHRoaXMuZ3JpZCAmJiB0aGlzLiQuaXRlbXMuc3R5bGUuaGVpZ2h0IDwgdGhpcy5fZXN0U2Nyb2xsSGVpZ2h0OwogICAgICAgIC8vIEFtb3J0aXplIGhlaWdodCBhZGp1c3RtZW50LCBzbyBpdCB3b24ndCB0cmlnZ2VyIGxhcmdlIHJlcGFpbnRzIHRvbyBvZnRlbi4KICAgICAgICBpZiAoZm9yY2VVcGRhdGUgfHwgTWF0aC5hYnModGhpcy5fZXN0U2Nyb2xsSGVpZ2h0IC0gdGhpcy5fc2Nyb2xsSGVpZ2h0KSA+PSB0aGlzLl92aWV3cG9ydEhlaWdodCkgewogICAgICAgICAgdGhpcy4kLml0ZW1zLnN0eWxlLmhlaWdodCA9IHRoaXMuX2VzdFNjcm9sbEhlaWdodCArICdweCc7CiAgICAgICAgICB0aGlzLl9zY3JvbGxIZWlnaHQgPSB0aGlzLl9lc3RTY3JvbGxIZWlnaHQ7CiAgICAgICAgfQogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIFNjcm9sbCB0byBhIHNwZWNpZmljIGluZGV4IGluIHRoZSB2aXJ0dWFsIGxpc3QgcmVnYXJkbGVzcwogICAgICAgKiBvZiB0aGUgcGh5c2ljYWwgaXRlbXMgaW4gdGhlIERPTSB0cmVlLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHNjcm9sbFRvSW5kZXgKICAgICAgICogQHBhcmFtIHtudW1iZXJ9IGlkeCBUaGUgaW5kZXggb2YgdGhlIGl0ZW0KICAgICAgICovCiAgICAgIHNjcm9sbFRvSW5kZXg6IGZ1bmN0aW9uKGlkeCkgewogICAgICAgIGlmICh0eXBlb2YgaWR4ICE9PSAnbnVtYmVyJyB8fCBpZHggPCAwIHx8IGlkeCA+IHRoaXMuaXRlbXMubGVuZ3RoIC0gMSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBmbHVzaCA/IGZsdXNoKCkgOiBmbHVzaCgpOwogICAgICAgIC8vIEl0ZW1zIHNob3VsZCBoYXZlIGJlZW4gcmVuZGVyZWQgcHJpb3Igc2Nyb2xsaW5nIHRvIGFuIGluZGV4LgogICAgICAgIGlmICh0aGlzLl9waHlzaWNhbENvdW50ID09PSAwKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIGlkeCA9IHRoaXMuX2NsYW1wKGlkeCwgMCwgdGhpcy5fdmlydHVhbENvdW50IC0gMSk7CiAgICAgICAgLy8gVXBkYXRlIHRoZSB2aXJ0dWFsIHN0YXJ0IG9ubHkgd2hlbiBuZWVkZWQuCiAgICAgICAgaWYgKCF0aGlzLl9pc0luZGV4UmVuZGVyZWQoaWR4KSB8fCBpZHggPj0gdGhpcy5fbWF4VmlydHVhbFN0YXJ0KSB7CiAgICAgICAgICB0aGlzLl92aXJ0dWFsU3RhcnQgPSB0aGlzLmdyaWQgPyAoaWR4IC0gdGhpcy5faXRlbXNQZXJSb3cgKiAyKSA6IChpZHggLSAxKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fbWFuYWdlRm9jdXMoKTsKICAgICAgICB0aGlzLl9hc3NpZ25Nb2RlbHMoKTsKICAgICAgICB0aGlzLl91cGRhdGVNZXRyaWNzKCk7CiAgICAgICAgLy8gRXN0aW1hdGUgbmV3IHBoeXNpY2FsIG9mZnNldC4KICAgICAgICB0aGlzLl9waHlzaWNhbFRvcCA9IE1hdGguZmxvb3IodGhpcy5fdmlydHVhbFN0YXJ0IC8gdGhpcy5faXRlbXNQZXJSb3cpICogdGhpcy5fcGh5c2ljYWxBdmVyYWdlOwoKICAgICAgICB2YXIgY3VycmVudFRvcEl0ZW0gPSB0aGlzLl9waHlzaWNhbFN0YXJ0OwogICAgICAgIHZhciBjdXJyZW50VmlydHVhbEl0ZW0gPSB0aGlzLl92aXJ0dWFsU3RhcnQ7CiAgICAgICAgdmFyIHRhcmdldE9mZnNldFRvcCA9IDA7CiAgICAgICAgdmFyIGhpZGRlbkNvbnRlbnRTaXplID0gdGhpcy5faGlkZGVuQ29udGVudFNpemU7CiAgICAgICAgLy8gc2Nyb2xsIHRvIHRoZSBpdGVtIGFzIG11Y2ggYXMgd2UgY2FuLgogICAgICAgIHdoaWxlIChjdXJyZW50VmlydHVhbEl0ZW0gPCBpZHggJiYgdGFyZ2V0T2Zmc2V0VG9wIDw9IGhpZGRlbkNvbnRlbnRTaXplKSB7CiAgICAgICAgICB0YXJnZXRPZmZzZXRUb3AgPSB0YXJnZXRPZmZzZXRUb3AgKyB0aGlzLl9nZXRQaHlzaWNhbFNpemVJbmNyZW1lbnQoY3VycmVudFRvcEl0ZW0pOwogICAgICAgICAgY3VycmVudFRvcEl0ZW0gPSAoY3VycmVudFRvcEl0ZW0gKyAxKSAlIHRoaXMuX3BoeXNpY2FsQ291bnQ7CiAgICAgICAgICBjdXJyZW50VmlydHVhbEl0ZW0rKzsKICAgICAgICB9CiAgICAgICAgdGhpcy5fdXBkYXRlU2Nyb2xsZXJTaXplKHRydWUpOwogICAgICAgIHRoaXMuX3Bvc2l0aW9uSXRlbXMoKTsKICAgICAgICB0aGlzLl9yZXNldFNjcm9sbFBvc2l0aW9uKHRoaXMuX3BoeXNpY2FsVG9wICsgdGhpcy5fc2Nyb2xsT2Zmc2V0ICsgdGFyZ2V0T2Zmc2V0VG9wKTsKICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZCgwKTsKICAgICAgICAvLyBjbGVhciBjYWNoZWQgdmlzaWJsZSBpbmRleC4KICAgICAgICB0aGlzLl9maXJzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgICAgdGhpcy5fbGFzdFZpc2libGVJbmRleFZhbCA9IG51bGw7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogUmVzZXQgdGhlIHBoeXNpY2FsIGF2ZXJhZ2UgYW5kIHRoZSBhdmVyYWdlIGNvdW50LgogICAgICAgKi8KICAgICAgX3Jlc2V0QXZlcmFnZTogZnVuY3Rpb24oKSB7CiAgICAgICAgdGhpcy5fcGh5c2ljYWxBdmVyYWdlID0gMDsKICAgICAgICB0aGlzLl9waHlzaWNhbEF2ZXJhZ2VDb3VudCA9IDA7CiAgICAgIH0sCgogICAgICAvKioKICAgICAgICogQSBoYW5kbGVyIGZvciB0aGUgYGlyb24tcmVzaXplYCBldmVudCB0cmlnZ2VyZWQgYnkgYElyb25SZXNpemFibGVCZWhhdmlvcmAKICAgICAgICogd2hlbiB0aGUgZWxlbWVudCBpcyByZXNpemVkLgogICAgICAgKi8KICAgICAgX3Jlc2l6ZUhhbmRsZXI6IGZ1bmN0aW9uKCkgewogICAgICAgIHRoaXMuX2RlYm91bmNlKCdfcmVuZGVyJywgZnVuY3Rpb24oKSB7CiAgICAgICAgICAvLyBjbGVhciBjYWNoZWQgdmlzaWJsZSBpbmRleC4KICAgICAgICAgIHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4VmFsID0gbnVsbDsKICAgICAgICAgIHRoaXMuX2xhc3RWaXNpYmxlSW5kZXhWYWwgPSBudWxsOwogICAgICAgICAgLy8gU2tpcCB0aGUgcmVzaXplIGV2ZW50IG9uIHRvdWNoIGRldmljZXMgd2hlbiB0aGUgYWRkcmVzcyBiYXIgc2xpZGVzIHVwLgogICAgICAgICAgdGhpcy51cGRhdGVWaWV3cG9ydEJvdW5kYXJpZXMoKTsKICAgICAgICAgIGlmICh0aGlzLl9pc1Zpc2libGUpIHsKICAgICAgICAgICAgLy8gUmVpbnN0YWxsIHRoZSBzY3JvbGwgZXZlbnQgbGlzdGVuZXIuCiAgICAgICAgICAgIHRoaXMudG9nZ2xlU2Nyb2xsTGlzdGVuZXIodHJ1ZSk7CiAgICAgICAgICAgIHRoaXMuX3Jlc2V0QXZlcmFnZSgpOwogICAgICAgICAgICB0aGlzLl9yZW5kZXIoKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIFVuaW5zdGFsbCB0aGUgc2Nyb2xsIGV2ZW50IGxpc3RlbmVyLgogICAgICAgICAgICB0aGlzLnRvZ2dsZVNjcm9sbExpc3RlbmVyKGZhbHNlKTsKICAgICAgICAgIH0KICAgICAgICB9LCBBTklNQVRJT05fRlJBTUUpOwogICAgICB9LAoKICAgICAgLyoqCiAgICAgICAqIENvbnZlcnRzIGEgcmFuZG9tIGluZGV4IHRvIHRoZSBpbmRleCBvZiB0aGUgaXRlbSB0aGF0IGNvbXBsZXRlcyBpdCdzIHJvdy4KICAgICAgICogQWxsb3dzIGZvciBiZXR0ZXIgb3JkZXIgYW5kIGZpbGwgY29tcHV0YXRpb24gd2hlbiBncmlkID09IHRydWUuCiAgICAgICAqLwogICAgICBfY29udmVydEluZGV4VG9Db21wbGV0ZVJvdzogZnVuY3Rpb24oaWR4KSB7CiAgICAgICAgLy8gd2hlbiBncmlkID09IGZhbHNlIF9pdGVtUGVyUm93IGNhbiBiZSB1bnNldC4KICAgICAgICB0aGlzLl9pdGVtc1BlclJvdyA9IHRoaXMuX2l0ZW1zUGVyUm93IHx8IDE7CiAgICAgICAgcmV0dXJuIHRoaXMuZ3JpZCA/IE1hdGguY2VpbChpZHggLyB0aGlzLl9pdGVtc1BlclJvdykgKiB0aGlzLl9pdGVtc1BlclJvdyA6IGlkeDsKICAgICAgfSwKCiAgICAgIF9pc0luZGV4UmVuZGVyZWQ6IGZ1bmN0aW9uKGlkeCkgewogICAgICAgIHJldHVybiBpZHggPj0gdGhpcy5fdmlydHVhbFN0YXJ0ICYmIGlkeCA8PSB0aGlzLl92aXJ0dWFsRW5kOwogICAgICB9LAoKICAgICAgX2dldFBoeXNpY2FsSW5kZXg6IGZ1bmN0aW9uKHZpZHgpIHsKICAgICAgICByZXR1cm4gKHRoaXMuX3BoeXNpY2FsU3RhcnQgKyAodmlkeCAtIHRoaXMuX3ZpcnR1YWxTdGFydCkpICUgdGhpcy5fcGh5c2ljYWxDb3VudDsKICAgICAgfSwKCiAgICAgIF9jbGFtcDogZnVuY3Rpb24odiwgbWluLCBtYXgpIHsKICAgICAgICByZXR1cm4gTWF0aC5taW4obWF4LCBNYXRoLm1heChtaW4sIHYpKTsKICAgICAgfSwKCiAgICAgIF9kZWJvdW5jZTogZnVuY3Rpb24obmFtZSwgY2IsIGFzeW5jTW9kdWxlKSB7CiAgICAgICAgdGhpcy5fZGVib3VuY2VycyA9IHRoaXMuX2RlYm91bmNlcnMgfHwge307CiAgICAgICAgdGhpcy5fZGVib3VuY2Vyc1tuYW1lXSA9IERlYm91bmNlci5kZWJvdW5jZSgKICAgICAgICAgIHRoaXMuX2RlYm91bmNlcnNbbmFtZV0sCiAgICAgICAgICBhc3luY01vZHVsZSwKICAgICAgICAgIGNiLmJpbmQodGhpcykpOwogICAgICAgIGVucXVldWVEZWJvdW5jZXIodGhpcy5fZGVib3VuY2Vyc1tuYW1lXSk7CiAgICAgIH0KCiAgICB9KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIFRoaXMgRWxlbWVudCBpcyB1c2VkIGludGVybmFsbHkgYnkgdmFhZGluLWdyaWQuCiAgICAgKgogICAgICogQHByaXZhdGUKICAgICAqLwogICAgY2xhc3MgR3JpZFNjcm9sbGVyRWxlbWVudCBleHRlbmRzIFBvbHltZXJJcm9uTGlzdCB7CgogICAgICBzdGF0aWMgZ2V0IGlzKCkgewogICAgICAgIHJldHVybiAndmFhZGluLWdyaWQtc2Nyb2xsZXInOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIHNpemU6IHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICBub3RpZnk6IHRydWUKICAgICAgICAgIH0sCiAgICAgICAgICBfdmlkeE9mZnNldDogewogICAgICAgICAgICB2YWx1ZTogMAogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX2VmZmVjdGl2ZVNpemVDaGFuZ2VkKF9lZmZlY3RpdmVTaXplKScKICAgICAgICBdOwogICAgICB9CgogICAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgIHRoaXMuX3Njcm9sbEhhbmRsZXIoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICogQHByb3RlY3RlZAogICAgICAqLwogICAgICBfdXBkYXRlU2Nyb2xsZXJJdGVtKGl0ZW0sIGluZGV4KSB7fQogICAgICAvKioKICAgICAgKiBAcHJvdGVjdGVkCiAgICAgICovCiAgICAgIF9hZnRlclNjcm9sbCgpIHt9CiAgICAgIC8qKgogICAgICAqIEBwcm90ZWN0ZWQKICAgICAgKi8KICAgICAgX2dldFJvd1RhcmdldCgpIHt9CiAgICAgIC8qKgogICAgICAqIEBwcm90ZWN0ZWQKICAgICAgKi8KICAgICAgX2NyZWF0ZVNjcm9sbGVyUm93cygpIHt9CiAgICAgIC8qKgogICAgICAqIEBwcm90ZWN0ZWQKICAgICAgKi8KICAgICAgX2NhblBvcHVsYXRlKCkge30KCiAgICAgIC8qKgogICAgICAqIEBwcml2YXRlCiAgICAgICovCiAgICAgIHNjcm9sbFRvSW5kZXgoaW5kZXgpIHsKICAgICAgICB0aGlzLl93YXJuUHJpdmF0ZUFQSUFjY2Vzcygnc2Nyb2xsVG9JbmRleCcpOwoKICAgICAgICBpZiAoaW5kZXggPiAwKSB7CiAgICAgICAgICB0aGlzLl9wZW5kaW5nU2Nyb2xsVG9JbmRleCA9IG51bGw7CiAgICAgICAgfQogICAgICAgIGlmICghcGFyc2VJbnQodGhpcy4kLml0ZW1zLnN0eWxlLmJvcmRlclRvcFdpZHRoKSAmJiBpbmRleCA+IDApIHsKICAgICAgICAgIC8vIFNjaGVkdWxlIGFub3RoZXIgc2Nyb2xsIHRvIGJlIGludm9rZWQgb25jZSBpbml0IGlzIGNvbXBsZXRlCiAgICAgICAgICB0aGlzLl9wZW5kaW5nU2Nyb2xsVG9JbmRleCA9IGluZGV4OwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fc2Nyb2xsaW5nVG9JbmRleCA9IHRydWU7CiAgICAgICAgaW5kZXggPSBNYXRoLm1pbihNYXRoLm1heChpbmRleCwgMCksIHRoaXMuX2VmZmVjdGl2ZVNpemUgLSAxKTsKICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsVG9wID0gaW5kZXggLyB0aGlzLl9lZmZlY3RpdmVTaXplICogKHRoaXMuJC50YWJsZS5zY3JvbGxIZWlnaHQgLSB0aGlzLiQudGFibGUub2Zmc2V0SGVpZ2h0KTsKICAgICAgICB0aGlzLl9zY3JvbGxIYW5kbGVyKCk7CgogICAgICAgIGlmICh0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSSgoKSA9PiB0aGlzLl9tYXhTY3JvbGxUb3ApICYmIHRoaXMuX3ZpcnR1YWxDb3VudCA8IHRoaXMuX2VmZmVjdGl2ZVNpemUpIHsKICAgICAgICAgIHRoaXMuX2FkanVzdFZpcnR1YWxJbmRleE9mZnNldCgxMDAwMDAwKTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2FjY2Vzc0lyb25MaXN0QVBJKCgpID0+IHN1cGVyLnNjcm9sbFRvSW5kZXgoaW5kZXggLSB0aGlzLl92aWR4T2Zmc2V0KSk7CiAgICAgICAgdGhpcy5fc2Nyb2xsSGFuZGxlcigpOwoKICAgICAgICAvLyBFbnN1cmUgc2Nyb2xsIHBvc2l0aW9uCiAgICAgICAgY29uc3Qgcm93ID0gQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pLmZpbHRlcihjaGlsZCA9PiBjaGlsZC5pbmRleCA9PT0gaW5kZXgpWzBdOwogICAgICAgIGlmIChyb3cpIHsKICAgICAgICAgIGNvbnN0IGhlYWRlck9mZnNldCA9IHJvdy5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS50b3AgLSB0aGlzLiQuaGVhZGVyLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLmJvdHRvbTsKICAgICAgICAgIGlmIChNYXRoLmFicyhoZWFkZXJPZmZzZXQpID4gMSkgewogICAgICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsVG9wICs9IGhlYWRlck9mZnNldDsKICAgICAgICAgICAgdGhpcy5fc2Nyb2xsSGFuZGxlcigpOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5fc2Nyb2xsaW5nVG9JbmRleCA9IGZhbHNlOwogICAgICB9CgogICAgICBfZWZmZWN0aXZlU2l6ZUNoYW5nZWQoc2l6ZSkgewogICAgICAgIGxldCBmdmk7IC8vIGZpcnN0IHZpc2libGUgKGFkanVzdGVkKSBpbmRleAogICAgICAgIGxldCBmdmlPZmZzZXQgPSAwOwogICAgICAgIHRoaXMuX2l0ZXJhdGVJdGVtcygocGlkeCwgdmlkeCkgPT4gewogICAgICAgICAgaWYgKHZpZHggPT09IHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4KSB7CiAgICAgICAgICAgIGNvbnN0IHJvdyA9IHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF07CiAgICAgICAgICAgIGZ2aSA9IHJvdy5pbmRleDsKICAgICAgICAgICAgZnZpT2Zmc2V0ID0gcm93LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLnRvcDsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgaWYgKHRoaXMuaXRlbXMgJiYgc2l6ZSA8IHRoaXMuaXRlbXMubGVuZ3RoKSB7CiAgICAgICAgICAvLyBTaXplIHdhcyByZWR1Y2VkLCBzY3JvbGwgdG8gMCBmaXJzdAogICAgICAgICAgdGhpcy5fc2Nyb2xsVG9wID0gMDsKICAgICAgICB9CiAgICAgICAgaWYgKCFBcnJheS5pc0FycmF5KHRoaXMuaXRlbXMpKSB7CiAgICAgICAgICAvLyBFZGdlL0lFIHNlZW1zIHRvIGhhdmUgdGhlIGxvd2VzdCBtYXhpbXVtCiAgICAgICAgICBjb25zdCBtYXhWaXJ0dWFsSXRlbXMgPSB0aGlzLl9lZGdlIHx8IHRoaXMuX2llID8gMzAwMDAgOiAxMDAwMDA7CiAgICAgICAgICB0aGlzLml0ZW1zID0ge2xlbmd0aDogTWF0aC5taW4oc2l6ZSwgbWF4VmlydHVhbEl0ZW1zKX07CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSSgoKSA9PiBzdXBlci5faXRlbXNDaGFuZ2VkKHtwYXRoOiAnaXRlbXMnfSkpOwoKICAgICAgICB0aGlzLl92aXJ0dWFsQ291bnQgPSBNYXRoLm1pbih0aGlzLml0ZW1zLmxlbmd0aCwgc2l6ZSkgfHwgMDsKCiAgICAgICAgaWYgKHRoaXMuX3Njcm9sbFRvcCA9PT0gMCkgewogICAgICAgICAgdGhpcy5fYWNjZXNzSXJvbkxpc3RBUEkoKCkgPT4gdGhpcy5fc2Nyb2xsVG9JbmRleChNYXRoLm1pbihzaXplIC0gMSwgZnZpKSkpOwogICAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKChwaWR4LCB2aWR4KSA9PiB7CiAgICAgICAgICAgIGNvbnN0IHJvdyA9IHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF07CiAgICAgICAgICAgIGlmIChyb3cuaW5kZXggPT09IGZ2aSkgewogICAgICAgICAgICAgIHRoaXMuJC50YWJsZS5zY3JvbGxUb3AgKz0gTWF0aC5yb3VuZChyb3cuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkudG9wIC0gZnZpT2Zmc2V0KTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZXN0b3JlIGtleWJvYXJkIGZvY3VzIHRvIHRoZSByaWdodCBjZWxsCiAgICAgICAgICAgIGlmIChyb3cuaW5kZXggPT09IHRoaXMuX2ZvY3VzZWRJdGVtSW5kZXggJiYgdGhpcy5faXRlbXNGb2N1c2FibGUgJiYgdGhpcy4kLml0ZW1zLmNvbnRhaW5zKHRoaXMuc2hhZG93Um9vdC5hY3RpdmVFbGVtZW50KSkgewogICAgICAgICAgICAgIGNvbnN0IGNlbGxJbmRleCA9IEFycmF5LmZyb20odGhpcy5faXRlbXNGb2N1c2FibGUucGFyZW50RWxlbWVudC5jaGlsZHJlbikuaW5kZXhPZih0aGlzLl9pdGVtc0ZvY3VzYWJsZSk7CiAgICAgICAgICAgICAgcm93LmNoaWxkcmVuW2NlbGxJbmRleF0uZm9jdXMoKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX2Fzc2lnbk1vZGVscygpOwogICAgICAgIHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB0aGlzLl91cGRhdGUoKSk7CiAgICAgIH0KCiAgICAgIF9wb3NpdGlvbkl0ZW1zKCkgewogICAgICAgIHRoaXMuX2FkanVzdFNjcm9sbFBvc2l0aW9uKCk7CgogICAgICAgIGxldCByZVBvc2l0aW9uOwogICAgICAgIGlmIChpc05hTih0aGlzLl9waHlzaWNhbFRvcCkpIHsKICAgICAgICAgIHJlUG9zaXRpb24gPSB0cnVlOwogICAgICAgICAgdGhpcy5fcGh5c2ljYWxUb3AgPSAwOwogICAgICAgIH0KCiAgICAgICAgbGV0IHkgPSB0aGlzLl9waHlzaWNhbFRvcDsKICAgICAgICB0aGlzLl9pdGVyYXRlSXRlbXMoKHBpZHgsIHZpZHgpID0+IHsKICAgICAgICAgIHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF0uc3R5bGUudHJhbnNmb3JtID0gYHRyYW5zbGF0ZVkoJHt5fXB4KWA7CiAgICAgICAgICB5ICs9IHRoaXMuX3BoeXNpY2FsU2l6ZXNbcGlkeF07CiAgICAgICAgfSk7CgogICAgICAgIGlmIChyZVBvc2l0aW9uKSB7CiAgICAgICAgICB0aGlzLl9zY3JvbGxUb0luZGV4KDApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2luY3JlYXNlUG9vbElmTmVlZGVkKGNvdW50KSB7CiAgICAgICAgaWYgKChjb3VudCA9PT0gMCAmJiB0aGlzLl9zY3JvbGxpbmdUb0luZGV4KSB8fCAhdGhpcy5fY2FuUG9wdWxhdGUoKSB8fCAhdGhpcy5fZWZmZWN0aXZlU2l6ZSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKCF0aGlzLl9pbml0aWFsUG9vbENyZWF0ZWQpIHsKICAgICAgICAgIHRoaXMuX2luaXRpYWxQb29sQ3JlYXRlZCA9IHRydWU7CiAgICAgICAgICBzdXBlci5faW5jcmVhc2VQb29sSWZOZWVkZWQoMjUpOwogICAgICAgIH0gZWxzZSBpZiAodGhpcy5fb3B0UGh5c2ljYWxTaXplICE9PSBJbmZpbml0eSkgewogICAgICAgICAgdGhpcy5fZGVib3VuY2VJbmNyZWFzZVBvb2wgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgIHRoaXMuX2RlYm91bmNlSW5jcmVhc2VQb29sLAogICAgICAgICAgICBhbmltYXRpb25GcmFtZSwKICAgICAgICAgICAgKCkgPT4gewogICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZU1ldHJpY3MoKTsKICAgICAgICAgICAgICBjb25zdCByZW1haW5pbmdQaHlzaWNhbFNpemUgPSB0aGlzLl9vcHRQaHlzaWNhbFNpemUgLSB0aGlzLl9waHlzaWNhbFNpemU7CiAgICAgICAgICAgICAgbGV0IGVzdGltYXRlZE1pc3NpbmdSb3dDb3VudCA9IE1hdGguY2VpbChyZW1haW5pbmdQaHlzaWNhbFNpemUgLyB0aGlzLl9waHlzaWNhbEF2ZXJhZ2UpOwoKICAgICAgICAgICAgICBpZiAodGhpcy5fcGh5c2ljYWxDb3VudCArIGVzdGltYXRlZE1pc3NpbmdSb3dDb3VudCA+IHRoaXMuX2VmZmVjdGl2ZVNpemUpIHsKICAgICAgICAgICAgICAgIC8vIERvIG5vdCBpbmNyZWFzZSB0aGUgcGh5c2ljYWwgaXRlbSBjb3VudCBhYm92ZSB0aGUgdGhpcy5fZWZmZWN0aXZlU2l6ZQogICAgICAgICAgICAgICAgZXN0aW1hdGVkTWlzc2luZ1Jvd0NvdW50ID0gTWF0aC5tYXgoMCwgdGhpcy5fZWZmZWN0aXZlU2l6ZSAtIHRoaXMuX3BoeXNpY2FsQ291bnQpOwogICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgaWYgKHRoaXMuX3BoeXNpY2FsU2l6ZSAmJiBlc3RpbWF0ZWRNaXNzaW5nUm93Q291bnQgPiAwICYmIHRoaXMuX29wdFBoeXNpY2FsU2l6ZSAhPT0gSW5maW5pdHkpIHsKICAgICAgICAgICAgICAgIHN1cGVyLl9pbmNyZWFzZVBvb2xJZk5lZWRlZChlc3RpbWF0ZWRNaXNzaW5nUm93Q291bnQpOwogICAgICAgICAgICAgICAgLy8gRW5zdXJlIHRoZSByb3dzIGFyZSBpbiBvcmRlciBhZnRlciBpbmNyZWFzaW5nIHBvb2wKICAgICAgICAgICAgICAgIHRoaXMuX19yZW9yZGVyQ2hpbGROb2RlcygpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfX3Jlb3JkZXJDaGlsZE5vZGVzKCkgewogICAgICAgIGNvbnN0IGNoaWxkTm9kZXMgPSBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5jaGlsZE5vZGVzKTsKICAgICAgICBjb25zdCByb3dzSW5PcmRlciA9ICEhY2hpbGROb2Rlcy5yZWR1Y2UoKGluT3JkZXIsIGN1cnJlbnQsIGN1cnJlbnRJbmRleCwgYXJyYXkpID0+IHsKICAgICAgICAgIGlmIChjdXJyZW50SW5kZXggPT09IDAgfHwgYXJyYXlbY3VycmVudEluZGV4IC0gMV0uaW5kZXggPT09IGN1cnJlbnQuaW5kZXggLSAxKSB7CiAgICAgICAgICAgIHJldHVybiBpbk9yZGVyOwogICAgICAgICAgfQogICAgICAgIH0sIHRydWUpOwoKICAgICAgICBpZiAoIXJvd3NJbk9yZGVyKSB7CiAgICAgICAgICBjaGlsZE5vZGVzLnNvcnQoKHJvdzEsIHJvdzIpID0+IHsKICAgICAgICAgICAgcmV0dXJuIHJvdzEuaW5kZXggLSByb3cyLmluZGV4OwogICAgICAgICAgfSkuZm9yRWFjaChyb3cgPT4gdGhpcy4kLml0ZW1zLmFwcGVuZENoaWxkKHJvdykpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2NyZWF0ZVBvb2woc2l6ZSkgewogICAgICAgIGNvbnN0IGZyYWdtZW50ID0gZG9jdW1lbnQuY3JlYXRlRG9jdW1lbnRGcmFnbWVudCgpOwogICAgICAgIGNvbnN0IHBoeXNpY2FsSXRlbXMgPSB0aGlzLl9jcmVhdGVTY3JvbGxlclJvd3Moc2l6ZSk7CgogICAgICAgIHBoeXNpY2FsSXRlbXMuZm9yRWFjaChpbnN0ID0+IGZyYWdtZW50LmFwcGVuZENoaWxkKGluc3QpKTsKICAgICAgICB0aGlzLl9nZXRSb3dUYXJnZXQoKS5hcHBlbmRDaGlsZChmcmFnbWVudCk7CgogICAgICAgIC8vIFdlaXJkIGhhY2sgbmVlZGVkIHRvIGdldCBTYWZhcmkgdG8gYWN0dWFsbHkgZGlzdHJpYnV0ZSBzbG90cwogICAgICAgIGNvbnN0IGNvbnRlbnQgPSB0aGlzLnF1ZXJ5U2VsZWN0b3IoJ1tzbG90XScpOwogICAgICAgIGlmIChjb250ZW50KSB7CiAgICAgICAgICBjb25zdCBzbG90ID0gY29udGVudC5nZXRBdHRyaWJ1dGUoJ3Nsb3QnKTsKICAgICAgICAgIGNvbnRlbnQuc2V0QXR0cmlidXRlKCdzbG90JywgJ2Zvby1iYXInKTsKICAgICAgICAgIGNvbnRlbnQuc2V0QXR0cmlidXRlKCdzbG90Jywgc2xvdCk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl91cGRhdGVIZWFkZXJGb290ZXJNZXRyaWNzKCk7CgogICAgICAgIGFmdGVyTmV4dFJlbmRlcih0aGlzLCAoKSA9PiB0aGlzLm5vdGlmeVJlc2l6ZSgpKTsKICAgICAgICByZXR1cm4gcGh5c2ljYWxJdGVtczsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEFzc2lnbnMgdGhlIGRhdGEgbW9kZWxzIHRvIGEgZ2l2ZW4gc2V0IG9mIGl0ZW1zLgogICAgICAgKiBAcGFyYW0geyFBcnJheTxudW1iZXI+PX0gaXRlbVNldAogICAgICAgKi8KICAgICAgX2Fzc2lnbk1vZGVscyhpdGVtU2V0KSB7CiAgICAgICAgdGhpcy5faXRlcmF0ZUl0ZW1zKChwaWR4LCB2aWR4KSA9PiB7CiAgICAgICAgICBjb25zdCBlbCA9IHRoaXMuX3BoeXNpY2FsSXRlbXNbcGlkeF07CiAgICAgICAgICB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ2hpZGRlbicsIHZpZHggPj0gdGhpcy5fZWZmZWN0aXZlU2l6ZSwgZWwpOwogICAgICAgICAgdGhpcy5fdXBkYXRlU2Nyb2xsZXJJdGVtKGVsLCB2aWR4ICsgKHRoaXMuX3ZpZHhPZmZzZXQgfHwgMCkpOwogICAgICAgIH0sIGl0ZW1TZXQpOwogICAgICB9CgogICAgICBfc2Nyb2xsSGFuZGxlcigpIHsKICAgICAgICBjb25zdCBkZWx0YSA9IHRoaXMuJC50YWJsZS5zY3JvbGxUb3AgLSB0aGlzLl9zY3JvbGxQb3NpdGlvbjsKICAgICAgICB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSShzdXBlci5fc2Nyb2xsSGFuZGxlcik7CiAgICAgICAgY29uc3Qgb2xkT2Zmc2V0ID0gdGhpcy5fdmlkeE9mZnNldDsKICAgICAgICBpZiAodGhpcy5fYWNjZXNzSXJvbkxpc3RBUEkoKCkgPT4gdGhpcy5fbWF4U2Nyb2xsVG9wKSAmJiB0aGlzLl92aXJ0dWFsQ291bnQgPCB0aGlzLl9lZmZlY3RpdmVTaXplKSB7CiAgICAgICAgICB0aGlzLl9hZGp1c3RWaXJ0dWFsSW5kZXhPZmZzZXQoZGVsdGEpOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fdmlkeE9mZnNldCAhPT0gb2xkT2Zmc2V0KSB7CiAgICAgICAgICB0aGlzLl91cGRhdGUoKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fYWZ0ZXJTY3JvbGwoKTsKICAgICAgfQoKICAgICAgX2FkanVzdFZpcnR1YWxJbmRleE9mZnNldChkZWx0YSkgewogICAgICAgIGlmIChNYXRoLmFicyhkZWx0YSkgPiAxMDAwMCkgewogICAgICAgICAgaWYgKHRoaXMuX25vU2NhbGUpIHsKICAgICAgICAgICAgdGhpcy5fbm9TY2FsZSA9IGZhbHNlOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CiAgICAgICAgICBjb25zdCBzY2FsZSA9IHRoaXMuJC50YWJsZS5zY3JvbGxUb3AgLyAodGhpcy4kLnRhYmxlLnNjcm9sbEhlaWdodCAtIHRoaXMuJC50YWJsZS5vZmZzZXRIZWlnaHQpOwogICAgICAgICAgY29uc3Qgb2Zmc2V0ID0gc2NhbGUgKiB0aGlzLl9lZmZlY3RpdmVTaXplOwogICAgICAgICAgdGhpcy5fdmlkeE9mZnNldCA9IE1hdGgucm91bmQob2Zmc2V0IC0gc2NhbGUgKiB0aGlzLl92aXJ0dWFsQ291bnQpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAvLyBNYWtlIHN1cmUgdXNlciBjYW4gYWx3YXlzIHN3aXBlL3doZWVsIHNjcm9sbCB0byB0aGUgc3RhcnQgYW5kIGVuZAogICAgICAgICAgY29uc3Qgb2xkT2Zmc2V0ID0gdGhpcy5fdmlkeE9mZnNldCB8fCAwOwogICAgICAgICAgY29uc3QgdGhyZXNob2xkID0gMTAwMDsKICAgICAgICAgIGNvbnN0IG1heFNoaWZ0ID0gMTAwOwogICAgICAgICAgLy8gQXQgc3RhcnQKICAgICAgICAgIGlmICh0aGlzLl9zY3JvbGxUb3AgPT09IDApIHsKICAgICAgICAgICAgdGhpcy5fdmlkeE9mZnNldCA9IDA7CiAgICAgICAgICAgIGlmIChvbGRPZmZzZXQgIT09IHRoaXMuX3ZpZHhPZmZzZXQpIHsKICAgICAgICAgICAgICBzdXBlci5zY3JvbGxUb0luZGV4KDApOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuZmlyc3RWaXNpYmxlSW5kZXggPCB0aHJlc2hvbGQgJiYgdGhpcy5fdmlkeE9mZnNldCA+IDApIHsKICAgICAgICAgICAgdGhpcy5fdmlkeE9mZnNldCAtPSBNYXRoLm1pbih0aGlzLl92aWR4T2Zmc2V0LCBtYXhTaGlmdCk7CiAgICAgICAgICAgIGlmIChvbGRPZmZzZXQgIT09IHRoaXMuX3ZpZHhPZmZzZXQpIHsKICAgICAgICAgICAgICBzdXBlci5zY3JvbGxUb0luZGV4KHRoaXMuZmlyc3RWaXNpYmxlSW5kZXggKyAob2xkT2Zmc2V0IC0gdGhpcy5fdmlkeE9mZnNldCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX25vU2NhbGUgPSB0cnVlOwogICAgICAgICAgfQogICAgICAgICAgLy8gQXQgZW5kCiAgICAgICAgICBjb25zdCBtYXhPZmZzZXQgPSB0aGlzLl9lZmZlY3RpdmVTaXplIC0gdGhpcy5fdmlydHVhbENvdW50OwogICAgICAgICAgaWYgKHRoaXMuX3Njcm9sbFRvcCA+PSB0aGlzLl9tYXhTY3JvbGxUb3AgJiYgdGhpcy5fbWF4U2Nyb2xsVG9wID4gMCkgewogICAgICAgICAgICB0aGlzLl92aWR4T2Zmc2V0ID0gbWF4T2Zmc2V0OwogICAgICAgICAgICBpZiAob2xkT2Zmc2V0ICE9PSB0aGlzLl92aWR4T2Zmc2V0KSB7CiAgICAgICAgICAgICAgc3VwZXIuc2Nyb2xsVG9JbmRleCh0aGlzLl92aXJ0dWFsQ291bnQpOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuZmlyc3RWaXNpYmxlSW5kZXggPiB0aGlzLl92aXJ0dWFsQ291bnQgLSB0aHJlc2hvbGQgJiYgdGhpcy5fdmlkeE9mZnNldCA8IG1heE9mZnNldCkgewogICAgICAgICAgICB0aGlzLl92aWR4T2Zmc2V0ICs9IE1hdGgubWluKG1heE9mZnNldCAtIHRoaXMuX3ZpZHhPZmZzZXQsIG1heFNoaWZ0KTsKICAgICAgICAgICAgaWYgKG9sZE9mZnNldCAhPT0gdGhpcy5fdmlkeE9mZnNldCkgewogICAgICAgICAgICAgIHN1cGVyLnNjcm9sbFRvSW5kZXgodGhpcy5maXJzdFZpc2libGVJbmRleCAtICh0aGlzLl92aWR4T2Zmc2V0IC0gb2xkT2Zmc2V0KSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fbm9TY2FsZSA9IHRydWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfYWNjZXNzSXJvbkxpc3RBUEkoY2IpIHsKICAgICAgICB0aGlzLl93YXJuUHJpdmF0ZUFQSUFjY2Vzc0FzeW5jRW5hYmxlZCA9IGZhbHNlOwogICAgICAgIGNvbnN0IHJldHVyblZhbHVlID0gY2IuYXBwbHkodGhpcyk7CiAgICAgICAgdGhpcy5fZGVib3VuY2VyV2FyblByaXZhdGVBUElBY2Nlc3MgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJXYXJuUHJpdmF0ZUFQSUFjY2VzcywKICAgICAgICAgIGFuaW1hdGlvbkZyYW1lLAogICAgICAgICAgKCkgPT4gdGhpcy5fd2FyblByaXZhdGVBUElBY2Nlc3NBc3luY0VuYWJsZWQgPSB0cnVlCiAgICAgICAgKTsKICAgICAgICByZXR1cm4gcmV0dXJuVmFsdWU7CiAgICAgIH0KCiAgICAgIC8qIEFsbG93IGlyb24tbGlzdCB0byBhY2Nlc3MgaXRzIEFQSXMgZnJvbSBkZWJvdW5jZWQgY2FsbGJhY2tzIHdpdGhvdXQgd2FybnMgKi8KICAgICAgX2RlYm91bmNlUmVuZGVyKGNiLCBhc3luY01vZHVsZSkgewogICAgICAgIHN1cGVyLl9kZWJvdW5jZVJlbmRlcigoKSA9PiB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSShjYiksIGFzeW5jTW9kdWxlKTsKICAgICAgfQoKICAgICAgLyogV2FybiB3aGVuIGlyb24tbGlzdCBBUElzIGFyZSBiZWluZyBhY2Nlc3NlZCBkaXJlY3RseSAqLwogICAgICBfd2FyblByaXZhdGVBUElBY2Nlc3MoYXBpTmFtZSkgewogICAgICAgIGlmICh0aGlzLl93YXJuUHJpdmF0ZUFQSUFjY2Vzc0FzeW5jRW5hYmxlZCkgewogICAgICAgICAgY29uc29sZS53YXJuKGBBY2Nlc3NpbmcgcHJpdmF0ZSBBUEkgKCR7YXBpTmFtZX0pIWApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3JlbmRlcigpIHsKICAgICAgICB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSShzdXBlci5fcmVuZGVyKTsKICAgICAgfQoKICAgICAgX2NyZWF0ZUZvY3VzQmFja2ZpbGxJdGVtKCkgeyAvKiBJZ25vcmUgKi8gfQogICAgICBfbXVsdGlTZWxlY3Rpb25DaGFuZ2VkKCkgeyAvKiBJZ25vcmUgKi8gfQogICAgICBjbGVhclNlbGVjdGlvbigpIHsgLyogSWdub3JlICovIH0KICAgICAgX2l0ZW1zQ2hhbmdlZCgpIHsgLyogSWdub3JlICovIH0KICAgICAgX21hbmFnZUZvY3VzKCkgeyAvKiBJZ25vcmUgKi8gfQogICAgICBfcmVtb3ZlRm9jdXNlZEl0ZW0oKSB7IC8qIElnbm9yZSAqLyB9CgogICAgICBnZXQgX2ZpcnN0VmlzaWJsZUluZGV4KCkgewogICAgICAgIHJldHVybiB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSSgoKSA9PiBzdXBlci5maXJzdFZpc2libGVJbmRleCk7CiAgICAgIH0KICAgICAgZ2V0IF9sYXN0VmlzaWJsZUluZGV4KCkgewogICAgICAgIHJldHVybiB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSSgoKSA9PiBzdXBlci5sYXN0VmlzaWJsZUluZGV4KTsKICAgICAgfQogICAgICBfc2Nyb2xsVG9JbmRleChpbmRleCkgewogICAgICAgIHRoaXMuX2FjY2Vzc0lyb25MaXN0QVBJKCgpID0+IHRoaXMuc2Nyb2xsVG9JbmRleChpbmRleCkpOwogICAgICB9CiAgICAgIGdldCBmaXJzdFZpc2libGVJbmRleCgpIHsKICAgICAgICB0aGlzLl93YXJuUHJpdmF0ZUFQSUFjY2VzcygnZmlyc3RWaXNpYmxlSW5kZXgnKTsgcmV0dXJuIHN1cGVyLmZpcnN0VmlzaWJsZUluZGV4OwogICAgICB9CiAgICAgIHNldCBmaXJzdFZpc2libGVJbmRleCh2YWx1ZSkgewogICAgICAgIHRoaXMuX3dhcm5Qcml2YXRlQVBJQWNjZXNzKCdmaXJzdFZpc2libGVJbmRleCcpOyBzdXBlci5maXJzdFZpc2libGVJbmRleCA9IHZhbHVlOwogICAgICB9CiAgICAgIGdldCBsYXN0VmlzaWJsZUluZGV4KCkgewogICAgICAgIHRoaXMuX3dhcm5Qcml2YXRlQVBJQWNjZXNzKCdsYXN0VmlzaWJsZUluZGV4Jyk7IHJldHVybiBzdXBlci5sYXN0VmlzaWJsZUluZGV4OwogICAgICB9CiAgICAgIHNldCBsYXN0VmlzaWJsZUluZGV4KHZhbHVlKSB7CiAgICAgICAgdGhpcy5fd2FyblByaXZhdGVBUElBY2Nlc3MoJ2xhc3RWaXNpYmxlSW5kZXgnKTsgc3VwZXIubGFzdFZpc2libGVJbmRleCA9IHZhbHVlOwogICAgICB9CiAgICAgIHVwZGF0ZVZpZXdwb3J0Qm91bmRhcmllcygpIHsKICAgICAgICB0aGlzLl93YXJuUHJpdmF0ZUFQSUFjY2VzcygndXBkYXRlVmlld3BvcnRCb3VuZGFyaWVzJyk7IHN1cGVyLnVwZGF0ZVZpZXdwb3J0Qm91bmRhcmllcy5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICB9CiAgICAgIF9yZXNpemVIYW5kbGVyKCkgewogICAgICAgIHN1cGVyLl9yZXNpemVIYW5kbGVyKCk7CiAgICAgICAgZmx1c2goKTsKICAgICAgfQogICAgfQoKICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZShHcmlkU2Nyb2xsZXJFbGVtZW50LmlzLCBHcmlkU2Nyb2xsZXJFbGVtZW50KTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgQTExeU1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBBMTF5TWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgc3RhdGljIGdldCBvYnNlcnZlcnMoKSB7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICdfYTExeVVwZGF0ZUdyaWRTaXplKHNpemUsIF9jb2x1bW5UcmVlLCBfY29sdW1uVHJlZS4qKScKICAgICAgICBdOwogICAgICB9CgogICAgICBfYTExeUdldEhlYWRlclJvd0NvdW50KF9jb2x1bW5UcmVlKSB7CiAgICAgICAgcmV0dXJuIF9jb2x1bW5UcmVlLmZpbHRlcihsZXZlbCA9PiBsZXZlbC5zb21lKGNvbCA9PiBjb2wuX2hlYWRlclRlbXBsYXRlIHx8IGNvbC5oZWFkZXJSZW5kZXJlciB8fCBjb2wucGF0aCB8fCBjb2wuaGVhZGVyKSkubGVuZ3RoOwogICAgICB9CgogICAgICBfYTExeUdldEZvb3RlclJvd0NvdW50KF9jb2x1bW5UcmVlKSB7CiAgICAgICAgcmV0dXJuIF9jb2x1bW5UcmVlLmZpbHRlcihsZXZlbCA9PiBsZXZlbC5zb21lKGNvbCA9PiBjb2wuX2hlYWRlclRlbXBsYXRlIHx8IGNvbC5oZWFkZXJSZW5kZXJlcikpLmxlbmd0aDsKICAgICAgfQoKICAgICAgX2ExMXlVcGRhdGVHcmlkU2l6ZShzaXplLCBfY29sdW1uVHJlZSkgewogICAgICAgIGlmIChzaXplID09PSB1bmRlZmluZWQgfHwgX2NvbHVtblRyZWUgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgY29uc3QgYm9keUNvbHVtbnMgPSBfY29sdW1uVHJlZVtfY29sdW1uVHJlZS5sZW5ndGggLSAxXTsKICAgICAgICB0aGlzLiQudGFibGUuc2V0QXR0cmlidXRlKAogICAgICAgICAgJ2FyaWEtcm93Y291bnQnLAogICAgICAgICAgc2l6ZSArIHRoaXMuX2ExMXlHZXRIZWFkZXJSb3dDb3VudChfY29sdW1uVHJlZSkgKyB0aGlzLl9hMTF5R2V0Rm9vdGVyUm93Q291bnQoX2NvbHVtblRyZWUpCiAgICAgICAgKTsKICAgICAgICB0aGlzLiQudGFibGUuc2V0QXR0cmlidXRlKCdhcmlhLWNvbGNvdW50JywgYm9keUNvbHVtbnMgJiYgYm9keUNvbHVtbnMubGVuZ3RoIHx8IDApOwoKICAgICAgICB0aGlzLl9hMTF5VXBkYXRlSGVhZGVyUm93cygpOwogICAgICAgIHRoaXMuX2ExMXlVcGRhdGVGb290ZXJSb3dzKCk7CiAgICAgIH0KCiAgICAgIF9hMTF5VXBkYXRlSGVhZGVyUm93cygpIHsKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5oZWFkZXIuY2hpbGRyZW4pLmZvckVhY2goKGhlYWRlclJvdywgaW5kZXgpID0+CiAgICAgICAgICBoZWFkZXJSb3cuc2V0QXR0cmlidXRlKCdhcmlhLXJvd2luZGV4JywgaW5kZXggKyAxKQogICAgICAgICk7CiAgICAgIH0KCiAgICAgIF9hMTF5VXBkYXRlRm9vdGVyUm93cygpIHsKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5mb290ZXIuY2hpbGRyZW4pLmZvckVhY2goKGZvb3RlclJvdywgaW5kZXgpID0+CiAgICAgICAgICBmb290ZXJSb3cuc2V0QXR0cmlidXRlKAogICAgICAgICAgICAnYXJpYS1yb3dpbmRleCcsCiAgICAgICAgICAgIHRoaXMuX2ExMXlHZXRIZWFkZXJSb3dDb3VudCh0aGlzLl9jb2x1bW5UcmVlKSArIHRoaXMuc2l6ZSArIGluZGV4ICsgMQogICAgICAgICAgKQogICAgICAgICk7CiAgICAgIH0KCiAgICAgIF9hMTF5VXBkYXRlUm93Um93aW5kZXgocm93LCBpbmRleCkgewogICAgICAgIHJvdy5zZXRBdHRyaWJ1dGUoJ2FyaWEtcm93aW5kZXgnLCBpbmRleCArIHRoaXMuX2ExMXlHZXRIZWFkZXJSb3dDb3VudCh0aGlzLl9jb2x1bW5UcmVlKSArIDEpOwogICAgICB9CgogICAgICBfYTExeVVwZGF0ZVJvd1NlbGVjdGVkKHJvdywgc2VsZWN0ZWQpIHsKICAgICAgICAvLyBKYXdzIHJlYWRzIHNlbGVjdGlvbiBvbmx5IGZvciByb3dzLCBOVkRBIG9ubHkgZm9yIGNlbGxzCiAgICAgICAgcm93LnNldEF0dHJpYnV0ZSgnYXJpYS1zZWxlY3RlZCcsIEJvb2xlYW4oc2VsZWN0ZWQpKTsKICAgICAgICBBcnJheS5mcm9tKHJvdy5jaGlsZHJlbikuZm9yRWFjaChjZWxsID0+CiAgICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgnYXJpYS1zZWxlY3RlZCcsIEJvb2xlYW4oc2VsZWN0ZWQpKQogICAgICAgICk7CiAgICAgIH0KCiAgICAgIF9hMTF5VXBkYXRlUm93TGV2ZWwocm93LCBsZXZlbCkgewogICAgICAgIHJvdy5zZXRBdHRyaWJ1dGUoJ2FyaWEtbGV2ZWwnLCBsZXZlbCArIDEpOwogICAgICB9CgogICAgICBfYTExeVVwZGF0ZVJvd0RldGFpbHNPcGVuZWQocm93LCBkZXRhaWxzT3BlbmVkKSB7CiAgICAgICAgQXJyYXkuZnJvbShyb3cuY2hpbGRyZW4pLmZvckVhY2goY2VsbCA9PiB7CiAgICAgICAgICBpZiAodHlwZW9mIGRldGFpbHNPcGVuZWQgPT09ICdib29sZWFuJykgewogICAgICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgnYXJpYS1leHBhbmRlZCcsIGRldGFpbHNPcGVuZWQpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgaWYgKGNlbGwuaGFzQXR0cmlidXRlKCdhcmlhLWV4cGFuZGVkJykpIHsKICAgICAgICAgICAgICBjZWxsLnJlbW92ZUF0dHJpYnV0ZSgnYXJpYS1leHBhbmRlZCcpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIF9hMTF5U2V0Um93RGV0YWlsc0NlbGwocm93LCBkZXRhaWxzQ2VsbCkgewogICAgICAgIEFycmF5LmZyb20ocm93LmNoaWxkcmVuKS5mb3JFYWNoKGNlbGwgPT4gewogICAgICAgICAgaWYgKGNlbGwgIT09IGRldGFpbHNDZWxsKSB7CiAgICAgICAgICAgIGNlbGwuc2V0QXR0cmlidXRlKCdhcmlhLWNvbnRyb2xzJywgZGV0YWlsc0NlbGwuaWQpOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CgogICAgICBfYTExeVVwZGF0ZUNlbGxDb2xzcGFuKGNlbGwsIGNvbHNwYW4pIHsKICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgnYXJpYS1jb2xzcGFuJywgTnVtYmVyKGNvbHNwYW4pKTsKICAgICAgfQoKICAgICAgX2ExMXlVcGRhdGVTb3J0ZXJzKCkgewogICAgICAgIEFycmF5LmZyb20odGhpcy5xdWVyeVNlbGVjdG9yQWxsKCd2YWFkaW4tZ3JpZC1zb3J0ZXInKSkuZm9yRWFjaChzb3J0ZXIgPT4gewogICAgICAgICAgbGV0IGNlbGxDb250ZW50ID0gc29ydGVyLnBhcmVudE5vZGU7CiAgICAgICAgICB3aGlsZSAoY2VsbENvbnRlbnQgJiYgY2VsbENvbnRlbnQubG9jYWxOYW1lICE9PSAndmFhZGluLWdyaWQtY2VsbC1jb250ZW50JykgewogICAgICAgICAgICBjZWxsQ29udGVudCA9IGNlbGxDb250ZW50LnBhcmVudE5vZGU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoY2VsbENvbnRlbnQgJiYgY2VsbENvbnRlbnQuYXNzaWduZWRTbG90KSB7CiAgICAgICAgICAgIGNvbnN0IGNlbGwgPSBjZWxsQ29udGVudC5hc3NpZ25lZFNsb3QucGFyZW50Tm9kZTsKICAgICAgICAgICAgY2VsbC5zZXRBdHRyaWJ1dGUoJ2FyaWEtc29ydCcsIHsKICAgICAgICAgICAgICAnYXNjJzogJ2FzY2VuZGluZycsCiAgICAgICAgICAgICAgJ2Rlc2MnOiAnZGVzY2VuZGluZycKICAgICAgICAgICAgfVtTdHJpbmcoc29ydGVyLmRpcmVjdGlvbildIHx8ICdub25lJyk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IEFjdGl2ZUl0ZW1NaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgQWN0aXZlSXRlbU1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogVGhlIGl0ZW0gdXNlciBoYXMgbGFzdCBpbnRlcmFjdGVkIHdpdGguIFR1cm5zIHRvIGBudWxsYCBhZnRlciB1c2VyIGRlYWN0aXZhdGVzCiAgICAgICAgICAgKiB0aGUgaXRlbSBieSByZS1pbnRlcmFjdGluZyB3aXRoIHRoZSBjdXJyZW50bHkgYWN0aXZlIGl0ZW0uCiAgICAgICAgICAgKi8KICAgICAgICAgIGFjdGl2ZUl0ZW06IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICAgIHZhbHVlOiBudWxsCiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgcmVhZHkoKSB7CiAgICAgICAgc3VwZXIucmVhZHkoKTsKCiAgICAgICAgdGhpcy4kLnNjcm9sbGVyLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgdGhpcy5fb25DbGljay5iaW5kKHRoaXMpKTsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2NlbGwtYWN0aXZhdGUnLCB0aGlzLl9hY3RpdmF0ZUl0ZW0uYmluZCh0aGlzKSk7CiAgICAgIH0KCiAgICAgIF9hY3RpdmF0ZUl0ZW0oZSkgewogICAgICAgIGNvbnN0IG1vZGVsID0gZS5kZXRhaWwubW9kZWw7CiAgICAgICAgY29uc3QgY2xpY2tlZEl0ZW0gPSBtb2RlbCA/IG1vZGVsLml0ZW0gOiBudWxsOwoKICAgICAgICBpZiAoY2xpY2tlZEl0ZW0pIHsKICAgICAgICAgIHRoaXMuYWN0aXZlSXRlbSA9ICF0aGlzLl9pdGVtc0VxdWFsKHRoaXMuYWN0aXZlSXRlbSwgY2xpY2tlZEl0ZW0pID8gY2xpY2tlZEl0ZW0gOiBudWxsOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLy8gd2UgbmVlZCB0byBsaXN0ZW4gdG8gY2xpY2sgaW5zdGVhZCBvZiB0YXAgYmVjYXVzZSBvbiBtb2JpbGUgc2FmYXJpLCB0aGUKICAgICAgLy8gZG9jdW1lbnQuYWN0aXZlRWxlbWVudCBoYXMgbm90IGJlZW4gdXBkYXRlZCAoZm9jdXMgaGFzIG5vdCBiZWVuIHNoaWZ0ZWQpCiAgICAgIC8vIHlldCBhdCB0aGUgcG9pbnQgd2hlbiB0YXAgZXZlbnQgaXMgYmVpbmcgZXhlY3V0ZWQuCiAgICAgIF9vbkNsaWNrKGUpIHsKICAgICAgICBpZiAoZS5kZWZhdWx0UHJldmVudGVkKSB7CiAgICAgICAgICAvLyBTb21ldGhpbmcgaGFzIGhhbmRsZWQgdGhpcyBjbGljayBhbHJlYWR5LCBlLiBnLiwgPHZhYWRpbi1ncmlkLXNvcnRlcj4KICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIGNvbnN0IHBhdGggPSBlLmNvbXBvc2VkUGF0aCgpOwogICAgICAgIGNvbnN0IGNlbGwgPSBwYXRoW3BhdGguaW5kZXhPZih0aGlzLiQudGFibGUpIC0gM107CiAgICAgICAgaWYgKCFjZWxsIHx8IGNlbGwuZ2V0QXR0cmlidXRlKCdwYXJ0JykuaW5kZXhPZignZGV0YWlscy1jZWxsJykgPiAtMSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBjb25zdCBjZWxsQ29udGVudCA9IGNlbGwuX2NvbnRlbnQ7CgogICAgICAgIGNvbnN0IGFjdGl2ZUVsZW1lbnQgPSB0aGlzLmdldFJvb3ROb2RlKCkuYWN0aXZlRWxlbWVudDsKICAgICAgICBjb25zdCBjZWxsQ29udGVudEhhc0ZvY3VzID0gY2VsbENvbnRlbnQuY29udGFpbnMoYWN0aXZlRWxlbWVudCkgJiYKICAgICAgICAgIC8vIE1TSUUgYnVnOiBmbGV4IGNoaWxkcmVuIHJlY2VpdmUgZm9jdXMuIE1ha2UgdHlwZSAmIGF0dHJpYnV0ZXMgY2hlY2suCiAgICAgICAgICAoIXRoaXMuX2llIHx8IHRoaXMuX2lzRm9jdXNhYmxlKGFjdGl2ZUVsZW1lbnQpKTsKICAgICAgICBpZiAoIWNlbGxDb250ZW50SGFzRm9jdXMgJiYgIXRoaXMuX2lzRm9jdXNhYmxlKGUudGFyZ2V0KSkgewogICAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY2VsbC1hY3RpdmF0ZScsIHtkZXRhaWw6IHsKICAgICAgICAgICAgbW9kZWw6IHRoaXMuX19nZXRSb3dNb2RlbChjZWxsLnBhcmVudEVsZW1lbnQpCiAgICAgICAgICB9fSkpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2lzRm9jdXNhYmxlKHRhcmdldCkgewogICAgICAgIGlmICghdGFyZ2V0LnBhcmVudE5vZGUpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9CiAgICAgICAgY29uc3QgZm9jdXNhYmxlcyA9IEFycmF5LmZyb20odGFyZ2V0LnBhcmVudE5vZGUKICAgICAgICAgIC5xdWVyeVNlbGVjdG9yQWxsKCdbdGFiaW5kZXhdLCBidXR0b24sIGlucHV0LCBzZWxlY3QsIHRleHRhcmVhLCBvYmplY3QsIGlmcmFtZSwgbGFiZWwsIGFbaHJlZl0sIGFyZWFbaHJlZl0nKSkKICAgICAgICAgIC5maWx0ZXIoZWxlbWVudCA9PiBlbGVtZW50LmdldEF0dHJpYnV0ZSgncGFydCcpICE9PSAnY2VsbCBib2R5LWNlbGwnKTsKCiAgICAgICAgY29uc3QgaXNGb2N1c2FibGVFbGVtZW50ID0gZm9jdXNhYmxlcy5pbmRleE9mKHRhcmdldCkgIT09IC0xOwogICAgICAgIHJldHVybiAhdGFyZ2V0LmRpc2FibGVkICYmIGlzRm9jdXNhYmxlRWxlbWVudDsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IEFycmF5RGF0YVByb3ZpZGVyTWl4aW4gPSBzdXBlckNsYXNzID0+IGNsYXNzIEFycmF5RGF0YVByb3ZpZGVyTWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKCiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogQW4gYXJyYXkgY29udGFpbmluZyB0aGUgaXRlbXMgd2hpY2ggd2lsbCBiZSBzdGFtcGVkIHRvIHRoZSBjb2x1bW4gdGVtcGxhdGUKICAgICAgICAgICAqIGluc3RhbmNlcy4KICAgICAgICAgICAqLwogICAgICAgICAgaXRlbXM6IEFycmF5CgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX2l0ZW1zQ2hhbmdlZChpdGVtcywgaXRlbXMuKiwgaXNBdHRhY2hlZCknCiAgICAgICAgXTsKICAgICAgfQoKICAgICAgX2l0ZW1zQ2hhbmdlZChpdGVtcywgc3BsaWNlcywgaXNBdHRhY2hlZCkgewogICAgICAgIGlmICghaXNBdHRhY2hlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAoIUFycmF5LmlzQXJyYXkoaXRlbXMpKSB7CiAgICAgICAgICBpZiAoaXRlbXMgPT09IHVuZGVmaW5lZCB8fCBpdGVtcyA9PT0gbnVsbCkgewogICAgICAgICAgICB0aGlzLnNpemUgPSAwOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHRoaXMuZGF0YVByb3ZpZGVyID09PSB0aGlzLl9hcnJheURhdGFQcm92aWRlcikgewogICAgICAgICAgICB0aGlzLmRhdGFQcm92aWRlciA9IHVuZGVmaW5lZDsKICAgICAgICAgIH0KICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIHRoaXMuc2l6ZSA9IGl0ZW1zLmxlbmd0aDsKICAgICAgICB0aGlzLmRhdGFQcm92aWRlciA9IHRoaXMuZGF0YVByb3ZpZGVyIHx8IHRoaXMuX2FycmF5RGF0YVByb3ZpZGVyOwogICAgICAgIHRoaXMuY2xlYXJDYWNoZSgpOwogICAgICAgIHRoaXMuX2Vuc3VyZUZpcnN0UGFnZUxvYWRlZCgpOwogICAgICB9CgogICAgICBfYXJyYXlEYXRhUHJvdmlkZXIob3B0cywgY2IpIHsKICAgICAgICBsZXQgaXRlbXMgPSAoQXJyYXkuaXNBcnJheSh0aGlzLml0ZW1zKSA/IHRoaXMuaXRlbXMgOiBbXSkuc2xpY2UoMCk7CgogICAgICAgIGlmICh0aGlzLl9maWx0ZXJzICYmIHRoaXMuX2NoZWNrUGF0aHModGhpcy5fZmlsdGVycywgJ2ZpbHRlcmluZycsIGl0ZW1zKSkgewogICAgICAgICAgaXRlbXMgPSB0aGlzLl9maWx0ZXIoaXRlbXMpOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5zaXplID0gaXRlbXMubGVuZ3RoOwoKICAgICAgICBpZiAob3B0cy5zb3J0T3JkZXJzLmxlbmd0aCAmJiB0aGlzLl9jaGVja1BhdGhzKHRoaXMuX3NvcnRlcnMsICdzb3J0aW5nJywgaXRlbXMpKSB7CiAgICAgICAgICBpdGVtcyA9IGl0ZW1zLnNvcnQodGhpcy5fbXVsdGlTb3J0LmJpbmQodGhpcykpOwogICAgICAgIH0KCiAgICAgICAgY29uc3Qgc3RhcnQgPSBvcHRzLnBhZ2UgKiBvcHRzLnBhZ2VTaXplOwogICAgICAgIGNvbnN0IGVuZCA9IHN0YXJ0ICsgb3B0cy5wYWdlU2l6ZTsKICAgICAgICBjb25zdCBzbGljZSA9IGl0ZW1zLnNsaWNlKHN0YXJ0LCBlbmQpOwogICAgICAgIGNiKHNsaWNlLCBpdGVtcy5sZW5ndGgpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ2hlY2sgYXJyYXkgb2YgZmlsdGVycy9zb3J0ZXJzIGZvciBwYXRocyB2YWxpZGl0eSwgY29uc29sZS53YXJuIGludmFsaWQgaXRlbXMKICAgICAgICogQHBhcmFtIHtBcnJheX0gIGFycmF5VG9DaGVjayBUaGUgYXJyYXkgb2YgZmlsdGVycy9zb3J0ZXJzIHRvIGNoZWNrCiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBhY3Rpb24gICAgICAgVGhlIG5hbWUgb2YgYWN0aW9uIHRvIGluY2x1ZGUgaW4gd2FybmluZyAoZmlsdGVyaW5nLCBzb3J0aW5nKQogICAgICAgKiBAcGFyYW0ge0FycmF5fSAgaXRlbXMKICAgICAgICovCiAgICAgIF9jaGVja1BhdGhzKGFycmF5VG9DaGVjaywgYWN0aW9uLCBpdGVtcykgewogICAgICAgIGlmICghaXRlbXMubGVuZ3RoKSB7CiAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgfQoKICAgICAgICBsZXQgcmVzdWx0ID0gdHJ1ZTsKCiAgICAgICAgZm9yICh2YXIgaSBpbiBhcnJheVRvQ2hlY2spIHsKICAgICAgICAgIGNvbnN0IHBhdGggPSBhcnJheVRvQ2hlY2tbaV0ucGF0aDsKCiAgICAgICAgICAvLyBza2lwIHNpbXBsZSBwYXRocwogICAgICAgICAgaWYgKCFwYXRoIHx8IHBhdGguaW5kZXhPZignLicpID09PSAtMSkgewogICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgIH0KCiAgICAgICAgICBjb25zdCBwYXJlbnRQcm9wZXJ0eSA9IHBhdGgucmVwbGFjZSgvXC5bXlwuXSokLywgJycpOyAvLyBhLmIuYyAtPiBhLmIKICAgICAgICAgIGlmIChCYXNlLmdldChwYXJlbnRQcm9wZXJ0eSwgaXRlbXNbMF0pID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgY29uc29sZS53YXJuKGBQYXRoICIke3BhdGh9IiB1c2VkIGZvciAke2FjdGlvbn0gZG9lcyBub3QgZXhpc3QgaW4gYWxsIG9mIHRoZSBpdGVtcywgJHthY3Rpb259IGlzIGRpc2FibGVkLmApOwogICAgICAgICAgICByZXN1bHQgPSBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICAgIF9tdWx0aVNvcnQoYSwgYikgewogICAgICAgIHJldHVybiB0aGlzLl9zb3J0ZXJzLm1hcChzb3J0ID0+IHsKICAgICAgICAgIGlmIChzb3J0LmRpcmVjdGlvbiA9PT0gJ2FzYycpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbXBhcmUoQmFzZS5nZXQoc29ydC5wYXRoLCBhKSwgQmFzZS5nZXQoc29ydC5wYXRoLCBiKSk7CiAgICAgICAgICB9IGVsc2UgaWYgKHNvcnQuZGlyZWN0aW9uID09PSAnZGVzYycpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbXBhcmUoQmFzZS5nZXQoc29ydC5wYXRoLCBiKSwgQmFzZS5nZXQoc29ydC5wYXRoLCBhKSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gMDsKICAgICAgICB9KS5yZWR1Y2UoKHAsIG4pID0+IHsKICAgICAgICAgIHJldHVybiBwID8gcCA6IG47CiAgICAgICAgfSwgMCk7CiAgICAgIH0KCiAgICAgIF9ub3JtYWxpemVFbXB0eVZhbHVlKHZhbHVlKSB7CiAgICAgICAgaWYgKFt1bmRlZmluZWQsIG51bGxdLmluZGV4T2YodmFsdWUpID49IDApIHsKICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICB9IGVsc2UgaWYgKGlzTmFOKHZhbHVlKSkgewogICAgICAgICAgcmV0dXJuIHZhbHVlLnRvU3RyaW5nKCk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJldHVybiB2YWx1ZTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9jb21wYXJlKGEsIGIpIHsKICAgICAgICBhID0gdGhpcy5fbm9ybWFsaXplRW1wdHlWYWx1ZShhKTsKICAgICAgICBiID0gdGhpcy5fbm9ybWFsaXplRW1wdHlWYWx1ZShiKTsKCiAgICAgICAgaWYgKGEgPCBiKSB7CiAgICAgICAgICByZXR1cm4gLTE7CiAgICAgICAgfQogICAgICAgIGlmIChhID4gYikgewogICAgICAgICAgcmV0dXJuIDE7CiAgICAgICAgfQogICAgICAgIHJldHVybiAwOwogICAgICB9CgogICAgICBfZmlsdGVyKGl0ZW1zKSB7CiAgICAgICAgcmV0dXJuIGl0ZW1zLmZpbHRlcigoaXRlbSwgaW5kZXgpID0+IHsKICAgICAgICAgIHJldHVybiB0aGlzLl9maWx0ZXJzLmZpbHRlcihmaWx0ZXIgPT4gewogICAgICAgICAgICBjb25zdCB2YWx1ZSA9IHRoaXMuX25vcm1hbGl6ZUVtcHR5VmFsdWUoQmFzZS5nZXQoZmlsdGVyLnBhdGgsIGl0ZW0pKTsKICAgICAgICAgICAgY29uc3QgZmlsdGVyVmFsdWVMb3dlcmNhc2UgPSB0aGlzLl9ub3JtYWxpemVFbXB0eVZhbHVlKGZpbHRlci52YWx1ZSkudG9TdHJpbmcoKS50b0xvd2VyQ2FzZSgpOwogICAgICAgICAgICByZXR1cm4gdmFsdWUudG9TdHJpbmcoKS50b0xvd2VyQ2FzZSgpLmluZGV4T2YoZmlsdGVyVmFsdWVMb3dlcmNhc2UpID09PSAtMTsKICAgICAgICAgIH0pLmxlbmd0aCA9PT0gMDsKICAgICAgICB9KTsKICAgICAgfQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwoKICAgIC8qKgogICAgICogQHBvbHltZXJNaXhpbgogICAgICovCiAgICBjb25zdCBDb2x1bW5SZXNpemluZ01peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBDb2x1bW5SZXNpemluZ01peGluIGV4dGVuZHMgR2VzdHVyZUV2ZW50TGlzdGVuZXJzKHN1cGVyQ2xhc3MpIHsKCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgY29uc3Qgc2Nyb2xsZXIgPSB0aGlzLiQuc2Nyb2xsZXI7CiAgICAgICAgYWRkTGlzdGVuZXIoc2Nyb2xsZXIsICd0cmFjaycsIHRoaXMuX29uSGVhZGVyVHJhY2suYmluZCh0aGlzKSk7CgogICAgICAgIC8vIERpc2FsbG93IHNjcm9sbGluZyB3aGlsZSByZXNpemluZwogICAgICAgIHNjcm9sbGVyLmFkZEV2ZW50TGlzdGVuZXIoJ3RvdWNobW92ZScsIGUgPT4gc2Nyb2xsZXIuaGFzQXR0cmlidXRlKCdjb2x1bW4tcmVzaXppbmcnKSAmJiBlLnByZXZlbnREZWZhdWx0KCkpOwoKICAgICAgICAvLyBEaXNhYmxlIGNvbnRleHRtZW51IG9uIGFueSByZXNpemUgc2VwYXJhdG9yLgogICAgICAgIHNjcm9sbGVyLmFkZEV2ZW50TGlzdGVuZXIoJ2NvbnRleHRtZW51JywgZSA9PiBlLnRhcmdldC5nZXRBdHRyaWJ1dGUoJ3BhcnQnKSA9PSAncmVzaXplLWhhbmRsZScgJiYgZS5wcmV2ZW50RGVmYXVsdCgpKTsKCiAgICAgICAgLy8gRGlzYWJsZSBuYXRpdmUgY2VsbCBmb2N1cyB3aGVuIHJlc2l6aW5nCiAgICAgICAgc2Nyb2xsZXIuYWRkRXZlbnRMaXN0ZW5lcignbW91c2Vkb3duJywgZSA9PiBlLnRhcmdldC5nZXRBdHRyaWJ1dGUoJ3BhcnQnKSA9PT0gJ3Jlc2l6ZS1oYW5kbGUnICYmIGUucHJldmVudERlZmF1bHQoKSk7CiAgICAgIH0KCiAgICAgIF9vbkhlYWRlclRyYWNrKGUpIHsKICAgICAgICBjb25zdCBoYW5kbGUgPSBlLnRhcmdldDsKICAgICAgICBpZiAoaGFuZGxlLmdldEF0dHJpYnV0ZSgncGFydCcpID09PSAncmVzaXplLWhhbmRsZScpIHsKICAgICAgICAgIGNvbnN0IGNlbGwgPSBoYW5kbGUucGFyZW50RWxlbWVudDsKICAgICAgICAgIGxldCBjb2x1bW4gPSBjZWxsLl9jb2x1bW47CgogICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdjb2x1bW4tcmVzaXppbmcnLCB0cnVlLCB0aGlzLiQuc2Nyb2xsZXIpOwoKICAgICAgICAgIC8vIEdldCB0aGUgdGFyZ2V0IGNvbHVtbiB0byByZXNpemUKICAgICAgICAgIHdoaWxlIChjb2x1bW4ubG9jYWxOYW1lID09PSAndmFhZGluLWdyaWQtY29sdW1uLWdyb3VwJykgewogICAgICAgICAgICBjb2x1bW4gPSBBcnJheS5wcm90b3R5cGUuc2xpY2UuY2FsbChjb2x1bW4uX2NoaWxkQ29sdW1ucywgMCkKICAgICAgICAgICAgICAuc29ydChmdW5jdGlvbihhLCBiKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gYS5fb3JkZXIgLSBiLl9vcmRlcjsKICAgICAgICAgICAgICB9KQogICAgICAgICAgICAgIC5maWx0ZXIoZnVuY3Rpb24oY29sdW1uKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gIWNvbHVtbi5oaWRkZW47CiAgICAgICAgICAgICAgfSkucG9wKCk7CiAgICAgICAgICB9CgogICAgICAgICAgY29uc3QgY29sdW1uUm93Q2VsbHMgPSBBcnJheS5mcm9tKHRoaXMuJC5oZWFkZXIucXVlcnlTZWxlY3RvckFsbCgnW3BhcnR+PSJyb3ciXTpsYXN0LWNoaWxkIFtwYXJ0fj0iY2VsbCJdJykpOwogICAgICAgICAgdmFyIHRhcmdldENlbGwgPSBjb2x1bW5Sb3dDZWxscy5maWx0ZXIoY2VsbCA9PiBjZWxsLl9jb2x1bW4gPT09IGNvbHVtbilbMF07CiAgICAgICAgICAvLyBSZXNpemUgdGhlIHRhcmdldCBjb2x1bW4KICAgICAgICAgIGlmICh0YXJnZXRDZWxsLm9mZnNldFdpZHRoKSB7CiAgICAgICAgICAgIHZhciBzdHlsZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKHRhcmdldENlbGwpOwogICAgICAgICAgICB2YXIgbWluV2lkdGggPSAxMCArIHBhcnNlSW50KHN0eWxlLnBhZGRpbmdMZWZ0KSArIHBhcnNlSW50KHN0eWxlLnBhZGRpbmdSaWdodCkgKyBwYXJzZUludChzdHlsZS5ib3JkZXJMZWZ0V2lkdGgpCiAgICAgICAgICAgICAgKyBwYXJzZUludChzdHlsZS5ib3JkZXJSaWdodFdpZHRoKSArIHBhcnNlSW50KHN0eWxlLm1hcmdpbkxlZnQpICsgcGFyc2VJbnQoc3R5bGUubWFyZ2luUmlnaHQpOwogICAgICAgICAgICBjb25zdCBtYXhXaWR0aCA9IHRhcmdldENlbGwub2Zmc2V0V2lkdGggKyAodGhpcy5fX2lzUlRMID8gdGFyZ2V0Q2VsbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5sZWZ0IC0gZS5kZXRhaWwueCA6CiAgICAgICAgICAgICAgZS5kZXRhaWwueCAtIHRhcmdldENlbGwuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkucmlnaHQpOwogICAgICAgICAgICBjb2x1bW4ud2lkdGggPSBNYXRoLm1heChtaW5XaWR0aCwgbWF4V2lkdGgpICsgJ3B4JzsKICAgICAgICAgICAgY29sdW1uLmZsZXhHcm93ID0gMDsKICAgICAgICAgIH0KICAgICAgICAgIC8vIEZpeCB3aWR0aCBhbmQgZmxleC1ncm93IGZvciBhbGwgcHJlY2VkaW5nIGNvbHVtbnMKICAgICAgICAgIGNvbHVtblJvd0NlbGxzCiAgICAgICAgICAgIC5zb3J0KAogICAgICAgICAgICAgIGZ1bmN0aW9uKGEsIGIpIHsKICAgICAgICAgICAgICAgIHJldHVybiBhLl9jb2x1bW4uX29yZGVyIC0gYi5fY29sdW1uLl9vcmRlcjsKICAgICAgICAgICAgICB9KQogICAgICAgICAgICAuZm9yRWFjaChmdW5jdGlvbihjZWxsLCBpbmRleCwgYXJyYXkpIHsKICAgICAgICAgICAgICBpZiAoaW5kZXggPCBhcnJheS5pbmRleE9mKHRhcmdldENlbGwpKSB7CiAgICAgICAgICAgICAgICBjZWxsLl9jb2x1bW4ud2lkdGggPSBjZWxsLm9mZnNldFdpZHRoICsgJ3B4JzsKICAgICAgICAgICAgICAgIGNlbGwuX2NvbHVtbi5mbGV4R3JvdyA9IDA7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKCiAgICAgICAgICBpZiAoZS5kZXRhaWwuc3RhdGUgPT09ICdlbmQnKSB7CiAgICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnY29sdW1uLXJlc2l6aW5nJywgZmFsc2UsIHRoaXMuJC5zY3JvbGxlcik7CiAgICAgICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2NvbHVtbi1yZXNpemUnLCB7CiAgICAgICAgICAgICAgZGV0YWlsOiB7cmVzaXplZENvbHVtbjogY29sdW1ufQogICAgICAgICAgICB9KSk7CiAgICAgICAgICB9CgogICAgICAgICAgLy8gTm90aWZ5IHJlc2l6ZQogICAgICAgICAgdGhpcy5fcmVzaXplSGFuZGxlcigpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICogRmlyZWQgd2hlbiBhIGNvbHVtbiBpbiB0aGUgZ3JpZCBpcyByZXNpemVkIGJ5IHRoZSB1c2VyLgogICAgICAqCiAgICAgICogQGV2ZW50IGNvbHVtbi1yZXNpemUKICAgICAgKiBAcGFyYW0ge09iamVjdH0gZGV0YWlsCiAgICAgICogQHBhcmFtIHtPYmplY3R9IGRldGFpbC5yZXNpemVkQ29sdW1uIHRoZSBjb2x1bW4gdGhhdCB3YXMgcmVzaXplZAogICAgICAqLwogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCgogICAgY29uc3QgSXRlbUNhY2hlID0gY2xhc3MgSXRlbUNhY2hlIHsKCiAgICAgIGNvbnN0cnVjdG9yKGdyaWQsIHBhcmVudENhY2hlLCBwYXJlbnRJdGVtKSB7CiAgICAgICAgdGhpcy5ncmlkID0gZ3JpZDsKICAgICAgICB0aGlzLnBhcmVudENhY2hlID0gcGFyZW50Q2FjaGU7CiAgICAgICAgdGhpcy5wYXJlbnRJdGVtID0gcGFyZW50SXRlbTsKICAgICAgICB0aGlzLml0ZW1DYWNoZXMgPSB7fTsKICAgICAgICB0aGlzLml0ZW1zID0ge307CiAgICAgICAgdGhpcy5lZmZlY3RpdmVTaXplID0gMDsKICAgICAgICB0aGlzLnNpemUgPSAwOwogICAgICAgIHRoaXMucGVuZGluZ1JlcXVlc3RzID0ge307CiAgICAgIH0KCiAgICAgIGlzTG9hZGluZygpIHsKICAgICAgICByZXR1cm4gT2JqZWN0LmtleXModGhpcy5wZW5kaW5nUmVxdWVzdHMpLmxlbmd0aCB8fCBPYmplY3Qua2V5cyh0aGlzLml0ZW1DYWNoZXMpLmZpbHRlcihpbmRleCA9PiB7CiAgICAgICAgICByZXR1cm4gdGhpcy5pdGVtQ2FjaGVzW2luZGV4XS5pc0xvYWRpbmcoKTsKICAgICAgICB9KVswXTsKICAgICAgfQoKICAgICAgZ2V0SXRlbUZvckluZGV4KGluZGV4KSB7CiAgICAgICAgY29uc3Qge2NhY2hlLCBzY2FsZWRJbmRleH0gPSB0aGlzLmdldENhY2hlQW5kSW5kZXgoaW5kZXgpOwogICAgICAgIHJldHVybiBjYWNoZS5pdGVtc1tzY2FsZWRJbmRleF07CiAgICAgIH0KCiAgICAgIHVwZGF0ZVNpemUoKSB7CiAgICAgICAgdGhpcy5lZmZlY3RpdmVTaXplID0gKCF0aGlzLnBhcmVudEl0ZW0gfHwgdGhpcy5ncmlkLl9pc0V4cGFuZGVkKHRoaXMucGFyZW50SXRlbSkpID8KICAgICAgICAgIHRoaXMuc2l6ZSArIE9iamVjdC5rZXlzKHRoaXMuaXRlbUNhY2hlcykucmVkdWNlKChwcmV2LCBjdXJyKSA9PiB7CiAgICAgICAgICAgIGNvbnN0IHN1YkNhY2hlID0gdGhpcy5pdGVtQ2FjaGVzW2N1cnJdOwogICAgICAgICAgICBzdWJDYWNoZS51cGRhdGVTaXplKCk7CiAgICAgICAgICAgIHJldHVybiBwcmV2ICsgc3ViQ2FjaGUuZWZmZWN0aXZlU2l6ZTsKICAgICAgICAgIH0sIDApIDoKICAgICAgICAgIDA7CiAgICAgIH0KCiAgICAgIGVuc3VyZVN1YkNhY2hlRm9yU2NhbGVkSW5kZXgoc2NhbGVkSW5kZXgpIHsKICAgICAgICBpZiAoIXRoaXMuaXRlbUNhY2hlc1tzY2FsZWRJbmRleF0pIHsKICAgICAgICAgIGNvbnN0IHN1YkNhY2hlID0gbmV3IEl0ZW1DYWNoZSh0aGlzLmdyaWQsIHRoaXMsIHRoaXMuaXRlbXNbc2NhbGVkSW5kZXhdKTsKICAgICAgICAgIHRoaXMuaXRlbUNhY2hlc1tzY2FsZWRJbmRleF0gPSBzdWJDYWNoZTsKICAgICAgICAgIHRoaXMuZ3JpZC5fbG9hZFBhZ2UoMCwgc3ViQ2FjaGUpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgZ2V0Q2FjaGVBbmRJbmRleChpbmRleCkgewogICAgICAgIGxldCB0aGlzTGV2ZWxJbmRleCA9IGluZGV4OwogICAgICAgIGNvbnN0IGtleXMgPSBPYmplY3Qua2V5cyh0aGlzLml0ZW1DYWNoZXMpOwogICAgICAgIGZvciAodmFyIGkgPSAwOyBpIDwga2V5cy5sZW5ndGg7IGkrKykgewogICAgICAgICAgY29uc3QgZXhwYW5kZWRJbmRleCA9IE51bWJlcihrZXlzW2ldKTsKICAgICAgICAgIGNvbnN0IHN1YkNhY2hlID0gdGhpcy5pdGVtQ2FjaGVzW2V4cGFuZGVkSW5kZXhdOwogICAgICAgICAgaWYgKHRoaXNMZXZlbEluZGV4IDw9IGV4cGFuZGVkSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIHtjYWNoZTogdGhpcywgc2NhbGVkSW5kZXg6IHRoaXNMZXZlbEluZGV4fTsKICAgICAgICAgIH0gZWxzZSBpZiAodGhpc0xldmVsSW5kZXggPD0gZXhwYW5kZWRJbmRleCArIHN1YkNhY2hlLmVmZmVjdGl2ZVNpemUpIHsKICAgICAgICAgICAgcmV0dXJuIHN1YkNhY2hlLmdldENhY2hlQW5kSW5kZXgodGhpc0xldmVsSW5kZXggLSBleHBhbmRlZEluZGV4IC0gMSk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzTGV2ZWxJbmRleCAtPSBzdWJDYWNoZS5lZmZlY3RpdmVTaXplOwogICAgICAgIH0KICAgICAgICByZXR1cm4ge2NhY2hlOiB0aGlzLCBzY2FsZWRJbmRleDogdGhpc0xldmVsSW5kZXh9OwogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgRGF0YVByb3ZpZGVyTWl4aW4gPSBzdXBlckNsYXNzID0+IGNsYXNzIERhdGFQcm92aWRlck1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIE51bWJlciBvZiBpdGVtcyBmZXRjaGVkIGF0IGEgdGltZSBmcm9tIHRoZSBkYXRhcHJvdmlkZXIuCiAgICAgICAgICAgKi8KICAgICAgICAgIHBhZ2VTaXplOiB7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgdmFsdWU6IDUwLAogICAgICAgICAgICBvYnNlcnZlcjogJ19wYWdlU2l6ZUNoYW5nZWQnCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogRnVuY3Rpb24gdGhhdCBwcm92aWRlcyBpdGVtcyBsYXppbHkuIFJlY2VpdmVzIGFyZ3VtZW50cyBgcGFyYW1zYCwgYGNhbGxiYWNrYAogICAgICAgICAgICoKICAgICAgICAgICAqIGBwYXJhbXMucGFnZWAgUmVxdWVzdGVkIHBhZ2UgaW5kZXgKICAgICAgICAgICAqCiAgICAgICAgICAgKiBgcGFyYW1zLnBhZ2VTaXplYCBDdXJyZW50IHBhZ2Ugc2l6ZQogICAgICAgICAgICoKICAgICAgICAgICAqIGBwYXJhbXMuZmlsdGVyc2AgQ3VycmVudGx5IGFwcGxpZWQgZmlsdGVycwogICAgICAgICAgICoKICAgICAgICAgICAqIGBwYXJhbXMuc29ydE9yZGVyc2AgQ3VycmVudGx5IGFwcGxpZWQgc29ydGluZyBvcmRlcnMKICAgICAgICAgICAqCiAgICAgICAgICAgKiBgcGFyYW1zLnBhcmVudEl0ZW1gIFdoZW4gdHJlZSBpcyB1c2VkLCBhbmQgc3VibGV2ZWwgaXRlbXMKICAgICAgICAgICAqIGFyZSByZXF1ZXN0ZWQsIHJlZmVyZW5jZSB0byBwYXJlbnQgaXRlbSBvZiB0aGUgcmVxdWVzdGVkIHN1YmxldmVsLgogICAgICAgICAgICogT3RoZXJ3aXNlIGB1bmRlZmluZWRgLgogICAgICAgICAgICoKICAgICAgICAgICAqIGBjYWxsYmFjayhpdGVtcywgc2l6ZSlgIENhbGxiYWNrIGZ1bmN0aW9uIHdpdGggYXJndW1lbnRzOgogICAgICAgICAgICogICAtIGBpdGVtc2AgQ3VycmVudCBwYWdlIG9mIGl0ZW1zCiAgICAgICAgICAgKiAgIC0gYHNpemVgIFRvdGFsIG51bWJlciBvZiBpdGVtcy4gV2hlbiB0cmVlIHN1YmxldmVsIGl0ZW1zCiAgICAgICAgICAgKiAgICAgYXJlIHJlcXVlc3RlZCwgdG90YWwgbnVtYmVyIG9mIGl0ZW1zIGluIHRoZSByZXF1ZXN0ZWQgc3VibGV2ZWwuCiAgICAgICAgICAgKiAgICAgT3B0aW9uYWwgd2hlbiB0cmVlIGlzIG5vdCB1c2VkLCByZXF1aXJlZCBmb3IgdHJlZS4KICAgICAgICAgICAqLwogICAgICAgICAgZGF0YVByb3ZpZGVyOiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgICAgICBvYnNlcnZlcjogJ19kYXRhUHJvdmlkZXJDaGFuZ2VkJwogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIGB0cnVlYCB3aGlsZSBkYXRhIGlzIGJlaW5nIHJlcXVlc3RlZCBmcm9tIHRoZSBkYXRhIHByb3ZpZGVyLgogICAgICAgICAgICovCiAgICAgICAgICBsb2FkaW5nOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgcmVhZE9ubHk6IHRydWUsCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZQogICAgICAgICAgfSwKCiAgICAgICAgICBfY2FjaGU6IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgY29uc3QgY2FjaGUgPSBuZXcgSXRlbUNhY2hlKHRoaXMpOwogICAgICAgICAgICAgIHJldHVybiBjYWNoZTsKICAgICAgICAgICAgfQogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFBhdGggdG8gYW4gaXRlbSBzdWItcHJvcGVydHkgdGhhdCBpZGVudGlmaWVzIHRoZSBpdGVtLgogICAgICAgICAgICovCiAgICAgICAgICBpdGVtSWRQYXRoOiB7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICAgICAgdmFsdWU6IG51bGwKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBBbiBhcnJheSB0aGF0IGNvbnRhaW5zIHRoZSBleHBhbmRlZCBpdGVtcy4KICAgICAgICAgICAqLwogICAgICAgICAgZXhwYW5kZWRJdGVtczogewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICAgICAgdmFsdWU6ICgpID0+IFtdCiAgICAgICAgICB9CgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX3NpemVDaGFuZ2VkKHNpemUpJywKICAgICAgICAgICdfaXRlbUlkUGF0aENoYW5nZWQoaXRlbUlkUGF0aCknLAogICAgICAgICAgJ19leHBhbmRlZEl0ZW1zQ2hhbmdlZChleHBhbmRlZEl0ZW1zLiopJwogICAgICAgIF07CiAgICAgIH0KCiAgICAgIF9zaXplQ2hhbmdlZChzaXplKSB7CiAgICAgICAgY29uc3QgZGVsdGEgPSBzaXplIC0gdGhpcy5fY2FjaGUuc2l6ZTsKICAgICAgICB0aGlzLl9jYWNoZS5zaXplICs9IGRlbHRhOwogICAgICAgIHRoaXMuX2NhY2hlLmVmZmVjdGl2ZVNpemUgKz0gZGVsdGE7CiAgICAgICAgdGhpcy5fZWZmZWN0aXZlU2l6ZSA9IHRoaXMuX2NhY2hlLmVmZmVjdGl2ZVNpemU7CiAgICAgIH0KCiAgICAgIF9nZXRJdGVtKGluZGV4LCBlbCkgewogICAgICAgIGlmIChpbmRleCA+PSB0aGlzLl9lZmZlY3RpdmVTaXplKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBlbC5pbmRleCA9IGluZGV4OwogICAgICAgIGNvbnN0IHtjYWNoZSwgc2NhbGVkSW5kZXh9ID0gdGhpcy5fY2FjaGUuZ2V0Q2FjaGVBbmRJbmRleChpbmRleCk7CiAgICAgICAgY29uc3QgaXRlbSA9IGNhY2hlLml0ZW1zW3NjYWxlZEluZGV4XTsKICAgICAgICBpZiAoaXRlbSkgewogICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdsb2FkaW5nJywgZmFsc2UsIGVsKTsKICAgICAgICAgIHRoaXMuX3VwZGF0ZUl0ZW0oZWwsIGl0ZW0pOwogICAgICAgICAgaWYgKHRoaXMuX2lzRXhwYW5kZWQoaXRlbSkpIHsKICAgICAgICAgICAgY2FjaGUuZW5zdXJlU3ViQ2FjaGVGb3JTY2FsZWRJbmRleChzY2FsZWRJbmRleCk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbG9hZGluZycsIHRydWUsIGVsKTsKICAgICAgICAgIHRoaXMuX2xvYWRQYWdlKHRoaXMuX2dldFBhZ2VGb3JJbmRleChzY2FsZWRJbmRleCksIGNhY2hlKTsKICAgICAgICB9CgogICAgICB9CgogICAgICBfZXhwYW5kZWRJbnN0YW5jZUNoYW5nZWRDYWxsYmFjayhpbnN0LCB2YWx1ZSkgewogICAgICAgIGlmIChpbnN0Lml0ZW0gPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAodmFsdWUpIHsKICAgICAgICAgIHRoaXMuZXhwYW5kSXRlbShpbnN0Lml0ZW0pOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICB0aGlzLmNvbGxhcHNlSXRlbShpbnN0Lml0ZW0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJldHVybnMgYSB2YWx1ZSB0aGF0IGlkZW50aWZpZXMgdGhlIGl0ZW0uIFVzZXMgYGl0ZW1JZFBhdGhgIGlmIGF2YWlsYWJsZS4KICAgICAgICogQ2FuIGJlIGN1c3RvbWl6ZWQgYnkgb3ZlcnJpZGluZy4KICAgICAgICovCiAgICAgIGdldEl0ZW1JZChpdGVtKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuaXRlbUlkUGF0aCA/IHRoaXMuZ2V0KHRoaXMuaXRlbUlkUGF0aCwgaXRlbSkgOiBpdGVtOwogICAgICB9CgogICAgICBfaXNFeHBhbmRlZChpdGVtKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX19leHBhbmRlZEtleXMuaGFzKHRoaXMuZ2V0SXRlbUlkKGl0ZW0pKTsKICAgICAgfQoKICAgICAgX2V4cGFuZGVkSXRlbXNDaGFuZ2VkKGUpIHsKICAgICAgICB0aGlzLl9fY2FjaGVFeHBhbmRlZEtleXMoKTsKICAgICAgICB0aGlzLl9jYWNoZS51cGRhdGVTaXplKCk7CiAgICAgICAgdGhpcy5fZWZmZWN0aXZlU2l6ZSA9IHRoaXMuX2NhY2hlLmVmZmVjdGl2ZVNpemU7CiAgICAgICAgdGhpcy5fYXNzaWduTW9kZWxzKCk7CiAgICAgIH0KCiAgICAgIF9pdGVtSWRQYXRoQ2hhbmdlZChlKSB7CiAgICAgICAgdGhpcy5fX2NhY2hlRXhwYW5kZWRLZXlzKCk7CiAgICAgIH0KCiAgICAgIF9fY2FjaGVFeHBhbmRlZEtleXMoKSB7CiAgICAgICAgaWYgKHRoaXMuZXhwYW5kZWRJdGVtcykgewogICAgICAgICAgdGhpcy5fX2V4cGFuZGVkS2V5cyA9IG5ldyBTZXQoKTsKICAgICAgICAgIHRoaXMuZXhwYW5kZWRJdGVtcy5mb3JFYWNoKGl0ZW0gPT4gewogICAgICAgICAgICB0aGlzLl9fZXhwYW5kZWRLZXlzLmFkZCh0aGlzLmdldEl0ZW1JZChpdGVtKSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBFeHBhbmRzIHRoZSBnaXZlbiBpdGVtIHRyZWUuCiAgICAgICAqLwogICAgICBleHBhbmRJdGVtKGl0ZW0pIHsKICAgICAgICBpZiAoIXRoaXMuX2lzRXhwYW5kZWQoaXRlbSkpIHsKICAgICAgICAgIHRoaXMucHVzaCgnZXhwYW5kZWRJdGVtcycsIGl0ZW0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIENvbGxhcHNlcyB0aGUgZ2l2ZW4gaXRlbSB0cmVlLgogICAgICAgKi8KICAgICAgY29sbGFwc2VJdGVtKGl0ZW0pIHsKICAgICAgICBpZiAodGhpcy5faXNFeHBhbmRlZChpdGVtKSkgewogICAgICAgICAgdGhpcy5zcGxpY2UoJ2V4cGFuZGVkSXRlbXMnLCB0aGlzLl9nZXRJdGVtSW5kZXhJbkFycmF5KGl0ZW0sIHRoaXMuZXhwYW5kZWRJdGVtcyksIDEpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2dldEluZGV4TGV2ZWwoaW5kZXgpIHsKICAgICAgICBsZXQge2NhY2hlfSA9IHRoaXMuX2NhY2hlLmdldENhY2hlQW5kSW5kZXgoaW5kZXgpOwogICAgICAgIGxldCBsZXZlbCA9IDA7CiAgICAgICAgd2hpbGUgKGNhY2hlLnBhcmVudENhY2hlKSB7CiAgICAgICAgICBjYWNoZSA9IGNhY2hlLnBhcmVudENhY2hlOwogICAgICAgICAgbGV2ZWwrKzsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIGxldmVsOwogICAgICB9CgogICAgICBfY2FuUG9wdWxhdGUoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2hhc0RhdGEgJiYgdGhpcy5fY29sdW1uVHJlZTsKICAgICAgfQoKICAgICAgX2xvYWRQYWdlKHBhZ2UsIGNhY2hlKSB7CiAgICAgICAgLy8gbWFrZSBzdXJlIHNhbWUgcGFnZSBpc24ndCByZXF1ZXN0ZWQgbXVsdGlwbGUgdGltZXMuCiAgICAgICAgaWYgKCFjYWNoZS5wZW5kaW5nUmVxdWVzdHNbcGFnZV0gJiYgdGhpcy5kYXRhUHJvdmlkZXIpIHsKICAgICAgICAgIHRoaXMuX3NldExvYWRpbmcodHJ1ZSk7CiAgICAgICAgICBjYWNoZS5wZW5kaW5nUmVxdWVzdHNbcGFnZV0gPSB0cnVlOwogICAgICAgICAgY29uc3QgcGFyYW1zID0gewogICAgICAgICAgICBwYWdlLAogICAgICAgICAgICBwYWdlU2l6ZTogdGhpcy5wYWdlU2l6ZSwKICAgICAgICAgICAgc29ydE9yZGVyczogdGhpcy5fbWFwU29ydGVycygpLAogICAgICAgICAgICBmaWx0ZXJzOiB0aGlzLl9tYXBGaWx0ZXJzKCksCiAgICAgICAgICAgIHBhcmVudEl0ZW06IGNhY2hlLnBhcmVudEl0ZW0KICAgICAgICAgIH07CgogICAgICAgICAgdGhpcy5kYXRhUHJvdmlkZXIocGFyYW1zLCAoaXRlbXMsIHNpemUpID0+IHsKICAgICAgICAgICAgaWYgKHNpemUgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgIGNhY2hlLnNpemUgPSBzaXplOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGlmIChwYXJhbXMucGFyZW50SXRlbSkgewogICAgICAgICAgICAgICAgY2FjaGUuc2l6ZSA9IGl0ZW1zLmxlbmd0aDsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIGNvbnN0IGN1cnJlbnRJdGVtcyA9IEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5tYXAocm93ID0+IHJvdy5faXRlbSk7CgogICAgICAgICAgICAvLyBQb3B1bGF0ZSB0aGUgY2FjaGUgd2l0aCBuZXcgaXRlbXMKICAgICAgICAgICAgaXRlbXMuZm9yRWFjaCgoaXRlbSwgaXRlbXNJbmRleCkgPT4gewogICAgICAgICAgICAgIGNvbnN0IGl0ZW1JbmRleCA9IHBhZ2UgKiB0aGlzLnBhZ2VTaXplICsgaXRlbXNJbmRleDsKICAgICAgICAgICAgICBjYWNoZS5pdGVtc1tpdGVtSW5kZXhdID0gaXRlbTsKICAgICAgICAgICAgICBpZiAodGhpcy5faXNFeHBhbmRlZChpdGVtKSAmJiBjdXJyZW50SXRlbXMuaW5kZXhPZihpdGVtKSA+IC0xKSB7CiAgICAgICAgICAgICAgICAvLyBGb3JjZSBzeW5jaHJvbm91cyBkYXRhIHJlcXVlc3QgZm9yIGV4cGFuZGVkIGl0ZW0gc3ViLWNhY2hlCiAgICAgICAgICAgICAgICBjYWNoZS5lbnN1cmVTdWJDYWNoZUZvclNjYWxlZEluZGV4KGl0ZW1JbmRleCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKCiAgICAgICAgICAgIHRoaXMuX2hhc0RhdGEgPSB0cnVlOwoKICAgICAgICAgICAgZGVsZXRlIGNhY2hlLnBlbmRpbmdSZXF1ZXN0c1twYWdlXTsKCiAgICAgICAgICAgIHRoaXMuX3NldExvYWRpbmcoZmFsc2UpOwogICAgICAgICAgICB0aGlzLl9jYWNoZS51cGRhdGVTaXplKCk7CiAgICAgICAgICAgIHRoaXMuX2VmZmVjdGl2ZVNpemUgPSB0aGlzLl9jYWNoZS5lZmZlY3RpdmVTaXplOwoKICAgICAgICAgICAgQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pCiAgICAgICAgICAgICAgLmZpbHRlcihyb3cgPT4gIXJvdy5oaWRkZW4pCiAgICAgICAgICAgICAgLmZvckVhY2gocm93ID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IGNhY2hlZEl0ZW0gPSB0aGlzLl9jYWNoZS5nZXRJdGVtRm9ySW5kZXgocm93LmluZGV4KTsKICAgICAgICAgICAgICAgIGlmIChjYWNoZWRJdGVtKSB7CiAgICAgICAgICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbG9hZGluZycsIGZhbHNlLCByb3cpOwogICAgICAgICAgICAgICAgICB0aGlzLl91cGRhdGVJdGVtKHJvdywgY2FjaGVkSXRlbSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfSk7CgogICAgICAgICAgICB0aGlzLl9pbmNyZWFzZVBvb2xJZk5lZWRlZCgwKTsKCiAgICAgICAgICAgIHRoaXMuX19pdGVtc1JlY2VpdmVkKCk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9nZXRQYWdlRm9ySW5kZXgoaW5kZXgpIHsKICAgICAgICByZXR1cm4gTWF0aC5mbG9vcihpbmRleCAvIHRoaXMucGFnZVNpemUpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQ2xlYXJzIHRoZSBjYWNoZWQgcGFnZXMgYW5kIHJlbG9hZHMgZGF0YSBmcm9tIGRhdGFwcm92aWRlciB3aGVuIG5lZWRlZC4KICAgICAgICovCiAgICAgIGNsZWFyQ2FjaGUoKSB7CiAgICAgICAgdGhpcy5fY2FjaGUgPSBuZXcgSXRlbUNhY2hlKHRoaXMpOwogICAgICAgIEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5mb3JFYWNoKHJvdyA9PiB7CiAgICAgICAgICBBcnJheS5mcm9tKHJvdy5jaGlsZHJlbikuZm9yRWFjaChjZWxsID0+IHsKICAgICAgICAgICAgLy8gRm9yY2UgZGF0YSBzeXN0ZW0gdG8gcGljayB1cCBzdWJwcm9wZXJ0eSBjaGFuZ2VzCiAgICAgICAgICAgIGNlbGwuX2luc3RhbmNlICYmIGNlbGwuX2luc3RhbmNlLl9zZXRQZW5kaW5nUHJvcGVydHkoJ2l0ZW0nLCB7fSwgZmFsc2UpOwogICAgICAgICAgfSk7CiAgICAgICAgfSk7CiAgICAgICAgdGhpcy5fY2FjaGUuc2l6ZSA9IHRoaXMuc2l6ZSB8fCAwOwogICAgICAgIHRoaXMuX2NhY2hlLnVwZGF0ZVNpemUoKTsKICAgICAgICB0aGlzLl9oYXNEYXRhID0gZmFsc2U7CiAgICAgICAgdGhpcy5fYXNzaWduTW9kZWxzKCk7CgogICAgICAgIGlmICghdGhpcy5fZWZmZWN0aXZlU2l6ZSkgewogICAgICAgICAgdGhpcy5fbG9hZFBhZ2UoMCwgdGhpcy5fY2FjaGUpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3BhZ2VTaXplQ2hhbmdlZChwYWdlU2l6ZSwgb2xkUGFnZVNpemUpIHsKICAgICAgICBpZiAob2xkUGFnZVNpemUgIT09IHVuZGVmaW5lZCAmJiBwYWdlU2l6ZSAhPT0gb2xkUGFnZVNpemUpIHsKICAgICAgICAgIHRoaXMuY2xlYXJDYWNoZSgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2NoZWNrU2l6ZSgpIHsKICAgICAgICBpZiAodGhpcy5zaXplID09PSB1bmRlZmluZWQgJiYgdGhpcy5fZWZmZWN0aXZlU2l6ZSA9PT0gMCkgewogICAgICAgICAgY29uc29sZS53YXJuKAogICAgICAgICAgICAnVGhlIDx2YWFkaW4tZ3JpZD4gbmVlZHMgdGhlIHRvdGFsIG51bWJlciBvZiBpdGVtcycgKwogICAgICAgICAgICAnIGluIG9yZGVyIHRvIGRpc3BsYXkgcm93cy4gU2V0IHRoZSB0b3RhbCBudW1iZXIgb2YgaXRlbXMnICsKICAgICAgICAgICAgJyB0byB0aGUgYHNpemVgIHByb3BlcnR5LCBvciBwcm92aWRlIHRoZSB0b3RhbCBudW1iZXIgb2YgaXRlbXMnICsKICAgICAgICAgICAgJyBpbiB0aGUgc2Vjb25kIGFyZ3VtZW50IG9mIHRoZSBgZGF0YVByb3ZpZGVyYOKAmXMgYGNhbGxiYWNrYCBjYWxsLicKICAgICAgICAgICk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfZGF0YVByb3ZpZGVyQ2hhbmdlZChkYXRhUHJvdmlkZXIsIG9sZERhdGFQcm92aWRlcikgewogICAgICAgIGlmIChvbGREYXRhUHJvdmlkZXIgIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgdGhpcy5jbGVhckNhY2hlKCk7CiAgICAgICAgfQoKICAgICAgICBpZiAoZGF0YVByb3ZpZGVyICYmIHRoaXMuaXRlbXMgJiYgdGhpcy5pdGVtcy5sZW5ndGgpIHsKICAgICAgICAgIC8vIEZpeGVzIHBvc3NpYmx5IGludmFsaWQgY2FjaGVkIGxhc3RWaXNpYmxlSW5kZXggdmFsdWUgaW4gPGlyb24tbGlzdD4KICAgICAgICAgIHRoaXMuX3Njcm9sbFRvSW5kZXgodGhpcy5fZmlyc3RWaXNpYmxlSW5kZXgpOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fZW5zdXJlRmlyc3RQYWdlTG9hZGVkKCk7CgogICAgICAgIHRoaXMuX2RlYm91bmNlckNoZWNrU2l6ZSA9IERlYm91bmNlci5kZWJvdW5jZSgKICAgICAgICAgIHRoaXMuX2RlYm91bmNlckNoZWNrU2l6ZSwKICAgICAgICAgIHRpbWVPdXQuYWZ0ZXIoMjAwMCksCiAgICAgICAgICB0aGlzLl9jaGVja1NpemUuYmluZCh0aGlzKSk7CgogICAgICAgIHRoaXMuX3Njcm9sbEhhbmRsZXIoKTsKICAgICAgfQoKICAgICAgX2Vuc3VyZUZpcnN0UGFnZUxvYWRlZCgpIHsKICAgICAgICBpZiAoIXRoaXMuX2hhc0RhdGEpIHsKICAgICAgICAgIC8vIGxvYWQgZGF0YSBiZWZvcmUgYWRkaW5nIHJvd3MgdG8gbWFrZSBzdXJlIHRoZXkgaGF2ZSBjb250ZW50IHdoZW4KICAgICAgICAgIC8vIHJlbmRlcmVkIGZvciB0aGUgZmlyc3QgdGltZS4KICAgICAgICAgIHRoaXMuX2xvYWRQYWdlKDAsIHRoaXMuX2NhY2hlLCAoKSA9PiB7CiAgICAgICAgICAgIGNvbnN0IGhhZERhdGEgPSB0aGlzLl9oYXNEYXRhOwogICAgICAgICAgICB0aGlzLl9oYXNEYXRhID0gdHJ1ZTsKICAgICAgICAgICAgaWYgKCFoYWREYXRhKSB7CiAgICAgICAgICAgICAgdGhpcy5ub3RpZnlSZXNpemUoKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfaXRlbXNFcXVhbChpdGVtMSwgaXRlbTIpIHsKICAgICAgICByZXR1cm4gdGhpcy5nZXRJdGVtSWQoaXRlbTEpID09PSB0aGlzLmdldEl0ZW1JZChpdGVtMik7CiAgICAgIH0KCiAgICAgIF9nZXRJdGVtSW5kZXhJbkFycmF5KGl0ZW0sIGFycmF5KSB7CiAgICAgICAgbGV0IHJlc3VsdCA9IC0xOwogICAgICAgIGFycmF5LmZvckVhY2goKGksIGlkeCkgPT4gewogICAgICAgICAgaWYgKHRoaXMuX2l0ZW1zRXF1YWwoaSwgaXRlbSkpIHsKICAgICAgICAgICAgcmVzdWx0ID0gaWR4OwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIHJldHVybiByZXN1bHQ7CiAgICAgIH0KCiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgRHluYW1pY0NvbHVtbnNNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgRHluYW1pY0NvbHVtbnNNaXhpbiBleHRlbmRzIHN1cGVyQ2xhc3MgewoKICAgICAgcmVhZHkoKSB7CiAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICB0aGlzLl9hZGROb2RlT2JzZXJ2ZXIoKTsKICAgICAgfQoKICAgICAgX2hhc0NvbHVtbkdyb3Vwcyhjb2x1bW5zKSB7CiAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBjb2x1bW5zLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICBpZiAoY29sdW1uc1tpXS5sb2NhbE5hbWUgPT09ICd2YWFkaW4tZ3JpZC1jb2x1bW4tZ3JvdXAnKSB7CiAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CgogICAgICBfZ2V0Q2hpbGRDb2x1bW5zKGVsKSB7CiAgICAgICAgcmV0dXJuIEZsYXR0ZW5lZE5vZGVzT2JzZXJ2ZXIuZ2V0RmxhdHRlbmVkTm9kZXMoZWwpLmZpbHRlcih0aGlzLl9pc0NvbHVtbkVsZW1lbnQpOwogICAgICB9CgogICAgICBfZmxhdHRlbkNvbHVtbkdyb3Vwcyhjb2x1bW5zKSB7CiAgICAgICAgcmV0dXJuIGNvbHVtbnMubWFwKGNvbCA9PiB7CiAgICAgICAgICBpZiAoY29sLmxvY2FsTmFtZSA9PT0gJ3ZhYWRpbi1ncmlkLWNvbHVtbi1ncm91cCcpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2dldENoaWxkQ29sdW1ucyhjb2wpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgcmV0dXJuIFtjb2xdOwogICAgICAgICAgfQogICAgICAgIH0pLnJlZHVjZSgocHJldiwgY3VycikgPT4gewogICAgICAgICAgcmV0dXJuIHByZXYuY29uY2F0KGN1cnIpOwogICAgICAgIH0sIFtdKTsKICAgICAgfQoKICAgICAgX2dldENvbHVtblRyZWUoKSB7CiAgICAgICAgdmFyIHJvb3RDb2x1bW5zID0gRmxhdHRlbmVkTm9kZXNPYnNlcnZlci5nZXRGbGF0dGVuZWROb2Rlcyh0aGlzKS5maWx0ZXIodGhpcy5faXNDb2x1bW5FbGVtZW50KTsKICAgICAgICB2YXIgX2NvbHVtblRyZWUgPSBbXTsKCiAgICAgICAgZm9yICh2YXIgYyA9IHJvb3RDb2x1bW5zOyA7KSB7CiAgICAgICAgICBfY29sdW1uVHJlZS5wdXNoKGMpOwogICAgICAgICAgaWYgKCF0aGlzLl9oYXNDb2x1bW5Hcm91cHMoYykpIHsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICB9CiAgICAgICAgICBjID0gdGhpcy5fZmxhdHRlbkNvbHVtbkdyb3VwcyhjKTsKICAgICAgICB9CgogICAgICAgIHJldHVybiBfY29sdW1uVHJlZTsKICAgICAgfQoKICAgICAgX3VwZGF0ZUNvbHVtblRyZWUoKSB7CiAgICAgICAgdmFyIGNvbHVtblRyZWUgPSB0aGlzLl9nZXRDb2x1bW5UcmVlKCk7CiAgICAgICAgaWYgKCF0aGlzLl9hcnJheUVxdWFscyhjb2x1bW5UcmVlLCB0aGlzLl9jb2x1bW5UcmVlKSkgewogICAgICAgICAgdGhpcy5fY29sdW1uVHJlZSA9IGNvbHVtblRyZWU7CiAgICAgICAgfQogICAgICB9CgogICAgICBfYWRkTm9kZU9ic2VydmVyKCkgewogICAgICAgIHRoaXMuX29ic2VydmVyID0gbmV3IEZsYXR0ZW5lZE5vZGVzT2JzZXJ2ZXIodGhpcywgaW5mbyA9PiB7CgogICAgICAgICAgY29uc3Qgcm93RGV0YWlsc1RlbXBsYXRlID0gaW5mby5hZGRlZE5vZGVzLmZpbHRlcihuID0+IG4ubG9jYWxOYW1lID09PSAndGVtcGxhdGUnICYmIG4uY2xhc3NMaXN0LmNvbnRhaW5zKCdyb3ctZGV0YWlscycpKVswXTsKICAgICAgICAgIGlmIChyb3dEZXRhaWxzVGVtcGxhdGUgJiYgdGhpcy5fcm93RGV0YWlsc1RlbXBsYXRlICE9PSByb3dEZXRhaWxzVGVtcGxhdGUpIHsKICAgICAgICAgICAgdGhpcy5fcm93RGV0YWlsc1RlbXBsYXRlID0gcm93RGV0YWlsc1RlbXBsYXRlOwogICAgICAgICAgfQoKICAgICAgICAgIGlmIChpbmZvLmFkZGVkTm9kZXMuZmlsdGVyKHRoaXMuX2lzQ29sdW1uRWxlbWVudCkubGVuZ3RoID4gMCB8fAogICAgICAgICAgICBpbmZvLnJlbW92ZWROb2Rlcy5maWx0ZXIodGhpcy5faXNDb2x1bW5FbGVtZW50KS5sZW5ndGggPiAwKSB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZUNvbHVtblRyZWUoKTsKICAgICAgICAgIH0KCiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJDaGVja0ltcG9ydHMgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgIHRoaXMuX2RlYm91bmNlckNoZWNrSW1wb3J0cywKICAgICAgICAgICAgdGltZU91dC5hZnRlcigyMDAwKSwKICAgICAgICAgICAgdGhpcy5fY2hlY2tJbXBvcnRzLmJpbmQodGhpcykpOwoKICAgICAgICAgIHRoaXMuX2Vuc3VyZUZpcnN0UGFnZUxvYWRlZCgpOwogICAgICAgIH0pOwogICAgICB9CgogICAgICBfYXJyYXlFcXVhbHMoYXJyMSwgYXJyMikgewogICAgICAgIGlmICghYXJyMSB8fCAhYXJyMiB8fCBhcnIxLmxlbmd0aCAhPSBhcnIyLmxlbmd0aCkgewogICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgIH0KCiAgICAgICAgZm9yICh2YXIgaSA9IDAsIGwgPSBhcnIxLmxlbmd0aDsgaSA8IGw7IGkrKykgewogICAgICAgICAgLy8gQ2hlY2sgaWYgd2UgaGF2ZSBuZXN0ZWQgYXJyYXlzCiAgICAgICAgICBpZiAoYXJyMVtpXSBpbnN0YW5jZW9mIEFycmF5ICYmIGFycjJbaV0gaW5zdGFuY2VvZiBBcnJheSkgewogICAgICAgICAgICAvLyByZWN1cnNlIGludG8gdGhlIG5lc3RlZCBhcnJheXMKICAgICAgICAgICAgaWYgKCF0aGlzLl9hcnJheUVxdWFscyhhcnIxW2ldLCBhcnIyW2ldKSkgewogICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIGlmIChhcnIxW2ldICE9IGFycjJbaV0pIHsKICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgfQoKICAgICAgX2NoZWNrSW1wb3J0cygpIHsKICAgICAgICBbCiAgICAgICAgICAndmFhZGluLWdyaWQtY29sdW1uLWdyb3VwJywKICAgICAgICAgICd2YWFkaW4tZ3JpZC1maWx0ZXInLAogICAgICAgICAgJ3ZhYWRpbi1ncmlkLWZpbHRlci1jb2x1bW4nLAogICAgICAgICAgJ3ZhYWRpbi1ncmlkLXRyZWUtdG9nZ2xlJywKICAgICAgICAgICd2YWFkaW4tZ3JpZC1zZWxlY3Rpb24tY29sdW1uJywKICAgICAgICAgICd2YWFkaW4tZ3JpZC1zb3J0LWNvbHVtbicsCiAgICAgICAgICAndmFhZGluLWdyaWQtc29ydGVyJwogICAgICAgIF0uZm9yRWFjaChlbGVtZW50TmFtZSA9PiB7CiAgICAgICAgICB2YXIgZWxlbWVudCA9IHRoaXMucXVlcnlTZWxlY3RvcihlbGVtZW50TmFtZSk7CiAgICAgICAgICBpZiAoZWxlbWVudCAmJiAhKGVsZW1lbnQgaW5zdGFuY2VvZiBQb2x5bWVyRWxlbWVudCkpIHsKICAgICAgICAgICAgY29uc29sZS53YXJuKGBNYWtlIHN1cmUgeW91IGhhdmUgaW1wb3J0ZWQgdGhlIHJlcXVpcmVkIG1vZHVsZSBmb3IgPCR7ZWxlbWVudE5hbWV9PiBlbGVtZW50LmApOwogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CgogICAgICBfdXBkYXRlRmlyc3RBbmRMYXN0Q29sdW1uKCkgewogICAgICAgIEFycmF5LmZyb20odGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ3RyJykpLmZvckVhY2gocm93ID0+IHRoaXMuX3VwZGF0ZUZpcnN0QW5kTGFzdENvbHVtbkZvclJvdyhyb3cpKTsKICAgICAgfQoKICAgICAgX3VwZGF0ZUZpcnN0QW5kTGFzdENvbHVtbkZvclJvdyhyb3cpIHsKICAgICAgICBBcnJheS5mcm9tKHJvdy5xdWVyeVNlbGVjdG9yQWxsKCdbcGFydH49ImNlbGwiXTpub3QoW3BhcnR+PSJkZXRhaWxzLWNlbGwiXSknKSkKICAgICAgICAgIC5zb3J0KChhLCBiKSA9PiB7CiAgICAgICAgICAgIHJldHVybiBhLl9jb2x1bW4uX29yZGVyIC0gYi5fY29sdW1uLl9vcmRlcjsKICAgICAgICAgIH0pLmZvckVhY2goKGNlbGwsIGNlbGxJbmRleCwgY2hpbGRyZW4pID0+IHsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdmaXJzdC1jb2x1bW4nLCBjZWxsSW5kZXggPT09IDAsIGNlbGwpOwogICAgICAgICAgICB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ2xhc3QtY29sdW1uJywgY2VsbEluZGV4ID09PSBjaGlsZHJlbi5sZW5ndGggLSAxLCBjZWxsKTsKICAgICAgICAgIH0pOwogICAgICB9CgogICAgICBfaXNDb2x1bW5FbGVtZW50KG5vZGUpIHsKICAgICAgICByZXR1cm4gbm9kZS5ub2RlVHlwZSA9PT0gTm9kZS5FTEVNRU5UX05PREUgJiYgL1xiY29sdW1uXGIvLnRlc3Qobm9kZS5sb2NhbE5hbWUpOwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxOCBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KICAgIC8qKgogICAgICogQHBvbHltZXJNaXhpbgogICAgICovCiAgICBjb25zdCBFdmVudENvbnRleHRNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgRXZlbnRDb250ZXh0TWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKCiAgICAgIC8qKgogICAgICAgKiBSZXR1cm5zIGFuIG9iamVjdCB3aXRoIGNvbnRleHQgaW5mb3JtYXRpb24gYWJvdXQgdGhlIGV2ZW50IHRhcmdldDoKICAgICAgICogLSBgaXRlbWA6IHRoZSBkYXRhIG9iamVjdCBjb3JyZXNwb25kaW5nIHRvIHRoZSB0YXJnZXRlZCByb3cgKG5vdCBzcGVjaWZpZWQgd2hlbiB0YXJnZXRpbmcgaGVhZGVyIG9yIGZvb3RlcikKICAgICAgICogLSBgY29sdW1uYDogdGhlIGNvbHVtbiBlbGVtZW50IGNvcnJlc3BvbmRpbmcgdG8gdGhlIHRhcmdldGVkIGNlbGwgKG5vdCBzcGVjaWZpZWQgd2hlbiB0YXJnZXRpbmcgcm93IGRldGFpbHMpCiAgICAgICAqIC0gYHNlY3Rpb25gOiB3aGV0aGVyIHRoZSBldmVudCB0YXJnZXRlZCB0aGUgYm9keSwgaGVhZGVyLCBmb290ZXIgb3IgZGV0YWlscyBvZiB0aGUgZ3JpZAogICAgICAgKgogICAgICAgKiBUaGVzZSBhZGRpdGlvbmFsIHByb3BlcnRpZXMgYXJlIGluY2x1ZGVkIHdoZW4gYGl0ZW1gIGlzIHNwZWNpZmllZDoKICAgICAgICogLSBgaW5kZXhgOiB0aGUgaW5kZXggb2YgdGhlIGl0ZW0KICAgICAgICogLSBgc2VsZWN0ZWRgOiB0aGUgc2VsZWN0ZWQgc3RhdGUgb2YgdGhlIGl0ZW0KICAgICAgICogLSBgZGV0YWlsc09wZW5lZGA6IHdoZXRoZXIgdGhlIHJvdyBkZXRhaWxzIGFyZSBvcGVuIGZvciB0aGUgaXRlbQogICAgICAgKiAtIGBleHBhbmRlZGA6IHRoZSBleHBhbmRlZCBzdGF0ZSBvZiB0aGUgdHJlZSB0b2dnbGUKICAgICAgICogLSBgbGV2ZWxgOiB0aGUgdHJlZSBoaWVyYXJjaHkgbGV2ZWwKICAgICAgICoKICAgICAgICogVGhlIHJldHVybmVkIG9iamVjdCBpcyBwb3B1bGF0ZWQgb25seSB3aGVuIGEgZ3JpZCBjZWxsLCBoZWFkZXIsIGZvb3RlciBvciByb3cgZGV0YWlscyBpcyBmb3VuZCBpbiBgZXZlbnQuY29tcG9zZWRQYXRoKClgLgogICAgICAgKiBUaGlzIG1lYW5zIG1vc3RseSBtb3VzZSBhbmQga2V5Ym9hcmQgZXZlbnRzLiBJZiBzdWNoIGEgZ3JpZCBwYXJ0IGlzIG5vdCBmb3VuZCBpbiB0aGUgcGF0aCwgYW4gZW1wdHkgb2JqZWN0IGlzIHJldHVybmVkLgogICAgICAgKiBUaGlzIG1heSBiZSB0aGUgY2FzZSBlZy4gaWYgdGhlIGV2ZW50IGlzIGZpcmVkIG9uIHRoZSBgPHZhYWRpbi1ncmlkPmAgZWxlbWVudCBhbmQgbm90IGFueSBkZWVwZXIgaW4gdGhlIERPTSwgb3IgaWYKICAgICAgICogdGhlIGV2ZW50IHRhcmdldHMgdGhlIGVtcHR5IHBhcnQgb2YgdGhlIGdyaWQgYm9keS4KICAgICAgICovCiAgICAgIGdldEV2ZW50Q29udGV4dChldmVudCkgewoKICAgICAgICBjb25zdCBjb250ZXh0ID0ge307CgogICAgICAgIGNvbnN0IHBhdGggPSBldmVudC5jb21wb3NlZFBhdGgoKTsKICAgICAgICBjb25zdCBjZWxsID0gcGF0aFtwYXRoLmluZGV4T2YodGhpcy4kLnRhYmxlKSAtIDNdOwoKICAgICAgICBpZiAoIWNlbGwpIHsKICAgICAgICAgIHJldHVybiBjb250ZXh0OwogICAgICAgIH0KCiAgICAgICAgY29udGV4dC5zZWN0aW9uID0gWydib2R5JywgJ2hlYWRlcicsICdmb290ZXInLCAnZGV0YWlscyddCiAgICAgICAgICAuZmlsdGVyKHNlY3Rpb24gPT4gY2VsbC5nZXRBdHRyaWJ1dGUoJ3BhcnQnKS5pbmRleE9mKHNlY3Rpb24pID4gLTEpWzBdOwoKICAgICAgICBpZiAoY2VsbC5fY29sdW1uKSB7CiAgICAgICAgICBjb250ZXh0LmNvbHVtbiA9IGNlbGwuX2NvbHVtbjsKICAgICAgICB9CgogICAgICAgIGlmIChjb250ZXh0LnNlY3Rpb24gPT09ICdib2R5JyB8fCBjb250ZXh0LnNlY3Rpb24gPT09ICdkZXRhaWxzJykgewogICAgICAgICAgT2JqZWN0LmFzc2lnbihjb250ZXh0LCB0aGlzLl9fZ2V0Um93TW9kZWwoY2VsbC5wYXJlbnRFbGVtZW50KSk7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gY29udGV4dDsKICAgICAgfQoKICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IEZpbHRlck1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBGaWx0ZXJNaXhpbiBleHRlbmRzIHN1cGVyQ2xhc3MgewoKICAgICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICBfZmlsdGVyczogewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdmaWx0ZXItY2hhbmdlZCcsIHRoaXMuX2ZpbHRlckNoYW5nZWQuYmluZCh0aGlzKSk7CiAgICAgIH0KCiAgICAgIF9maWx0ZXJDaGFuZ2VkKGUpIHsKICAgICAgICBpZiAodGhpcy5fZmlsdGVycy5pbmRleE9mKGUudGFyZ2V0KSA9PT0gLTEpIHsKICAgICAgICAgIHRoaXMuX2ZpbHRlcnMucHVzaChlLnRhcmdldCk7CiAgICAgICAgfQoKICAgICAgICBlLnN0b3BQcm9wYWdhdGlvbigpOwoKICAgICAgICBpZiAodGhpcy5kYXRhUHJvdmlkZXIpIHsKICAgICAgICAgIHRoaXMuY2xlYXJDYWNoZSgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX21hcEZpbHRlcnMoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2ZpbHRlcnMubWFwKGZpbHRlciA9PiB7CiAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICBwYXRoOiBmaWx0ZXIucGF0aCwKICAgICAgICAgICAgdmFsdWU6IGZpbHRlci52YWx1ZQogICAgICAgICAgfTsKICAgICAgICB9KTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIGB2YWFkaW4tZ3JpZC10ZW1wbGF0aXplcmAgaXMgYSBoZWxwZXIgZWxlbWVudCBmb3IgdGhlIGB2YWFkaW4tZ3JpZGAgdGhhdCBpcyBwcmVwYXJpbmcgYW5kCiAgICAgKiBzdGFtcGluZyBpbnN0YW5jZXMgb2YgY2VsbHMgYW5kIGNvbHVtbnMgdGVtcGxhdGVzCiAgICAgKgogICAgICogQGV4dGVuZHMgUG9seW1lckVsZW1lbnQKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGNsYXNzIEdyaWRUZW1wbGF0aXplciBleHRlbmRzIChjbGFzcyBleHRlbmRzIFBvbHltZXJFbGVtZW50IHt9KSB7CiAgICAgIHN0YXRpYyBnZXQgaXMoKSB7CiAgICAgICAgcmV0dXJuICd2YWFkaW4tZ3JpZC10ZW1wbGF0aXplcic7CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgZGF0YUhvc3Q6IE9iamVjdCwKCiAgICAgICAgICB0ZW1wbGF0ZTogT2JqZWN0LAoKICAgICAgICAgIF90ZW1wbGF0ZUluc3RhbmNlczogewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgfSwKCiAgICAgICAgICBfcGFyZW50UGF0aFZhbHVlczogewogICAgICAgICAgICB2YWx1ZTogZnVuY3Rpb24oKSB7CiAgICAgICAgICAgICAgcmV0dXJuIHt9OwogICAgICAgICAgICB9CiAgICAgICAgICB9LAoKICAgICAgICAgIF9ncmlkOiBPYmplY3QKICAgICAgICB9OwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IG9ic2VydmVycygpIHsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgJ190ZW1wbGF0ZUluc3RhbmNlc0NoYW5nZWQoX3RlbXBsYXRlSW5zdGFuY2VzLiosIF9wYXJlbnRQYXRoVmFsdWVzLiopJwogICAgICAgIF07CiAgICAgIH0KCiAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgIHN1cGVyKCk7CgogICAgICAgIHRoaXMuX2luc3RhbmNlUHJvcHMgPSB7CiAgICAgICAgICBkZXRhaWxzT3BlbmVkOiB0cnVlLAogICAgICAgICAgaW5kZXg6IHRydWUsCiAgICAgICAgICBpdGVtOiB0cnVlLAogICAgICAgICAgc2VsZWN0ZWQ6IHRydWUsCiAgICAgICAgICBleHBhbmRlZDogdHJ1ZSwKICAgICAgICAgIGxldmVsOiB0cnVlCiAgICAgICAgfTsKICAgICAgfQoKICAgICAgY3JlYXRlSW5zdGFuY2UoKSB7CiAgICAgICAgdGhpcy5fZW5zdXJlVGVtcGxhdGl6ZWQoKTsKICAgICAgICBjb25zdCBpbnN0YW5jZSA9IG5ldyB0aGlzLl9UZW1wbGF0ZUNsYXNzKHt9KTsKICAgICAgICB0aGlzLmFkZEluc3RhbmNlKGluc3RhbmNlKTsKCiAgICAgICAgcmV0dXJuIGluc3RhbmNlOwogICAgICB9CgogICAgICBhZGRJbnN0YW5jZShpbnN0YW5jZSkgewogICAgICAgIGlmICh0aGlzLl90ZW1wbGF0ZUluc3RhbmNlcy5pbmRleE9mKGluc3RhbmNlKSA9PT0gLTEpIHsKICAgICAgICAgIHRoaXMuX3RlbXBsYXRlSW5zdGFuY2VzLnB1c2goaW5zdGFuY2UpOwogICAgICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKCgpID0+IHRoaXMubm90aWZ5UGF0aCgnX3RlbXBsYXRlSW5zdGFuY2VzLionLCB0aGlzLl90ZW1wbGF0ZUluc3RhbmNlcykpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgcmVtb3ZlSW5zdGFuY2UoaW5zdGFuY2UpIHsKICAgICAgICBjb25zdCBpbmRleCA9IHRoaXMuX3RlbXBsYXRlSW5zdGFuY2VzLmluZGV4T2YoaW5zdGFuY2UpOwogICAgICAgIHRoaXMuc3BsaWNlKCdfdGVtcGxhdGVJbnN0YW5jZXMnLCBpbmRleCwgMSk7CiAgICAgIH0KCiAgICAgIF9lbnN1cmVUZW1wbGF0aXplZCgpIHsKICAgICAgICBpZiAoIXRoaXMuX1RlbXBsYXRlQ2xhc3MpIHsKICAgICAgICAgIHRoaXMuX1RlbXBsYXRlQ2xhc3MgPSB0ZW1wbGF0aXplKHRoaXMudGVtcGxhdGUsIHRoaXMsIHsKICAgICAgICAgICAgaW5zdGFuY2VQcm9wczogdGhpcy5faW5zdGFuY2VQcm9wcywKICAgICAgICAgICAgcGFyZW50TW9kZWw6IHRydWUsCgogICAgICAgICAgICBmb3J3YXJkSG9zdFByb3A6IGZ1bmN0aW9uKHByb3AsIHZhbHVlKSB7CiAgICAgICAgICAgICAgdGhpcy5fZm9yd2FyZFBhcmVudFByb3AocHJvcCwgdmFsdWUpOwoKICAgICAgICAgICAgICBpZiAodGhpcy5fdGVtcGxhdGVJbnN0YW5jZXMpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3RlbXBsYXRlSW5zdGFuY2VzLmZvckVhY2goaW5zdCA9PiBpbnN0Lm5vdGlmeVBhdGgocHJvcCwgdmFsdWUpKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0sCgogICAgICAgICAgICBub3RpZnlJbnN0YW5jZVByb3A6IGZ1bmN0aW9uKGluc3QsIHByb3AsIHZhbHVlKSB7CiAgICAgICAgICAgICAgaWYgKHByb3AgPT09ICdpbmRleCcgfHwgcHJvcCA9PT0gJ2l0ZW0nKSB7CiAgICAgICAgICAgICAgICAvLyBXZSBkb27igJl0IG5lZWQgYSBjaGFuZ2Ugbm90aWZpY2F0aW9uIGZvciB0aGVzZS4KICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgIGNvbnN0IG9yaWdpbmFsUHJvcCA9IGBfXyR7cHJvcH1fX2A7CgogICAgICAgICAgICAgIC8vIE5vdGlmeSBmb3Igb25seSB1c2VyLWFjdGlvbiBjaGFuZ2VzLCBub3QgZm9yIHNjcm9sbGluZyB1cGRhdGVzLiBFLiBnLiwKICAgICAgICAgICAgICAvLyBpZiBgZGV0YWlsc09wZW5lZGAgaXMgZGlmZmVyZW50IGZyb20gYF9fZGV0YWlsc09wZW5lZF9fYCwgd2hpY2ggd2FzIHNldCBkdXJpbmcgcmVuZGVyLgogICAgICAgICAgICAgIGlmIChpbnN0W29yaWdpbmFsUHJvcF0gPT09IHZhbHVlKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGluc3Rbb3JpZ2luYWxQcm9wXSA9IHZhbHVlOwoKICAgICAgICAgICAgICBjb25zdCByb3cgPSBBcnJheS5mcm9tKHRoaXMuX2dyaWQuJC5pdGVtcy5jaGlsZHJlbikuZmlsdGVyKHJvdyA9PiB0aGlzLl9ncmlkLl9pdGVtc0VxdWFsKHJvdy5faXRlbSwgaW5zdC5pdGVtKSlbMF07CiAgICAgICAgICAgICAgaWYgKHJvdykgewogICAgICAgICAgICAgICAgQXJyYXkuZnJvbShyb3cuY2hpbGRyZW4pLmZvckVhY2goY2VsbCA9PiB7CiAgICAgICAgICAgICAgICAgIGlmIChjZWxsLl9pbnN0YW5jZSkgewogICAgICAgICAgICAgICAgICAgIGNlbGwuX2luc3RhbmNlW29yaWdpbmFsUHJvcF0gPSB2YWx1ZTsKICAgICAgICAgICAgICAgICAgICBjZWxsLl9pbnN0YW5jZS5ub3RpZnlQYXRoKHByb3AsIHZhbHVlKTsKICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICBjb25zdCBpdGVtUHJlZml4ID0gJ2l0ZW0uJzsKICAgICAgICAgICAgICBpZiAoQXJyYXkuaXNBcnJheSh0aGlzLl9ncmlkLml0ZW1zKSAmJiBwcm9wLmluZGV4T2YoaXRlbVByZWZpeCkgPT09IDApIHsKICAgICAgICAgICAgICAgIGNvbnN0IGl0ZW1zSW5kZXggPSB0aGlzLl9ncmlkLml0ZW1zLmluZGV4T2YoaW5zdC5pdGVtKTsKICAgICAgICAgICAgICAgIGNvbnN0IHBhdGggPSBwcm9wLnNsaWNlKGl0ZW1QcmVmaXgubGVuZ3RoKTsKICAgICAgICAgICAgICAgIHRoaXMuX2dyaWQubm90aWZ5UGF0aChgaXRlbXMuJHtpdGVtc0luZGV4fS4ke3BhdGh9YCwgdmFsdWUpOwogICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgY29uc3QgZ3JpZENhbGxiYWNrID0gYF8ke3Byb3B9SW5zdGFuY2VDaGFuZ2VkQ2FsbGJhY2tgOwogICAgICAgICAgICAgIGlmICh0aGlzLl9ncmlkICYmIHRoaXMuX2dyaWRbZ3JpZENhbGxiYWNrXSkgewogICAgICAgICAgICAgICAgdGhpcy5fZ3JpZFtncmlkQ2FsbGJhY2tdKGluc3QsIHZhbHVlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KCiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9mb3J3YXJkUGFyZW50UHJvcChwcm9wLCB2YWx1ZSkgewogICAgICAgIHRoaXMuX3BhcmVudFBhdGhWYWx1ZXNbcHJvcF0gPSB2YWx1ZTsKICAgICAgICB0aGlzLl90ZW1wbGF0ZUluc3RhbmNlcy5mb3JFYWNoKGluc3QgPT4gaW5zdC5ub3RpZnlQYXRoKHByb3AsIHZhbHVlKSk7CiAgICAgIH0KCiAgICAgIF90ZW1wbGF0ZUluc3RhbmNlc0NoYW5nZWQodCwgcCkgewogICAgICAgIGxldCBpbmRleCwgY291bnQ7CiAgICAgICAgaWYgKHQucGF0aCA9PT0gJ190ZW1wbGF0ZUluc3RhbmNlcycpIHsKICAgICAgICAgIC8vIEl0ZXJhdGUgYWxsIGluc3RhbmNlcwogICAgICAgICAgaW5kZXggPSAwOwogICAgICAgICAgY291bnQgPSB0aGlzLl90ZW1wbGF0ZUluc3RhbmNlcy5sZW5ndGg7CiAgICAgICAgfSBlbHNlIGlmICh0LnBhdGggPT09ICdfdGVtcGxhdGVJbnN0YW5jZXMuc3BsaWNlcycpIHsKICAgICAgICAgIC8vIEl0ZXJhdGUgb25seSBuZXcgaW5zdGFuY2VzCiAgICAgICAgICBpbmRleCA9IHQudmFsdWUuaW5kZXg7CiAgICAgICAgICBjb3VudCA9IHQudmFsdWUuYWRkZWRDb3VudDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBPYmplY3Qua2V5cyh0aGlzLl9wYXJlbnRQYXRoVmFsdWVzIHx8IHt9KS5mb3JFYWNoKGtleU5hbWUgPT4gewogICAgICAgICAgZm9yICh2YXIgaSA9IGluZGV4OyBpIDwgaW5kZXggKyBjb3VudDsgaSsrKSB7CiAgICAgICAgICAgIHRoaXMuX3RlbXBsYXRlSW5zdGFuY2VzW2ldLnNldChrZXlOYW1lLCB0aGlzLl9wYXJlbnRQYXRoVmFsdWVzW2tleU5hbWVdKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfQoKICAgIH0KCiAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoR3JpZFRlbXBsYXRpemVyLmlzLCBHcmlkVGVtcGxhdGl6ZXIpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgUm93RGV0YWlsc01peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBSb3dEZXRhaWxzTWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIEFuIGFycmF5IGNvbnRhaW5pbmcgcmVmZXJlbmNlcyB0byBpdGVtcyB3aXRoIG9wZW4gcm93IGRldGFpbHMuCiAgICAgICAgICAgKi8KICAgICAgICAgIGRldGFpbHNPcGVuZWRJdGVtczogewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgfSwKCiAgICAgICAgICBfcm93RGV0YWlsc1RlbXBsYXRlOiBPYmplY3QsCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBDdXN0b20gZnVuY3Rpb24gZm9yIHJlbmRlcmluZyB0aGUgY29udGVudCBvZiB0aGUgcm93IGRldGFpbHMuCiAgICAgICAgICAgKiBSZWNlaXZlcyB0aHJlZSBhcmd1bWVudHM6CiAgICAgICAgICAgKgogICAgICAgICAgICogLSBgcm9vdGAgVGhlIHJvdyBkZXRhaWxzIGNvbnRlbnQgRE9NIGVsZW1lbnQuIEFwcGVuZCB5b3VyIGNvbnRlbnQgdG8gaXQuCiAgICAgICAgICAgKiAtIGBncmlkYCBUaGUgYDx2YWFkaW4tZ3JpZD5gIGVsZW1lbnQuCiAgICAgICAgICAgKiAtIGByb3dEYXRhYCBUaGUgb2JqZWN0IHdpdGggdGhlIHByb3BlcnRpZXMgcmVsYXRlZCB3aXRoCiAgICAgICAgICAgKiAgIHRoZSByZW5kZXJlZCBpdGVtLCBjb250YWluczoKICAgICAgICAgICAqICAgLSBgcm93RGF0YS5pbmRleGAgVGhlIGluZGV4IG9mIHRoZSBpdGVtLgogICAgICAgICAgICogICAtIGByb3dEYXRhLml0ZW1gIFRoZSBpdGVtLgogICAgICAgICAgICovCiAgICAgICAgICByb3dEZXRhaWxzUmVuZGVyZXI6IEZ1bmN0aW9uLAoKICAgICAgICAgIF9kZXRhaWxzQ2VsbHM6IHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICB9CiAgICAgICAgfTsKICAgICAgfQoKICAgICAgc3RhdGljIGdldCBvYnNlcnZlcnMoKSB7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICdfZGV0YWlsc09wZW5lZEl0ZW1zQ2hhbmdlZChkZXRhaWxzT3BlbmVkSXRlbXMuKiwgX3Jvd0RldGFpbHNUZW1wbGF0ZSwgcm93RGV0YWlsc1JlbmRlcmVyKScsCiAgICAgICAgICAnX3Jvd0RldGFpbHNUZW1wbGF0ZU9yUmVuZGVyZXJDaGFuZ2VkKF9yb3dEZXRhaWxzVGVtcGxhdGUsIHJvd0RldGFpbHNSZW5kZXJlciknCiAgICAgICAgXTsKICAgICAgfQoKICAgICAgX3Jvd0RldGFpbHNUZW1wbGF0ZU9yUmVuZGVyZXJDaGFuZ2VkKHJvd0RldGFpbHNUZW1wbGF0ZSwgcm93RGV0YWlsc1JlbmRlcmVyKSB7CiAgICAgICAgaWYgKHJvd0RldGFpbHNUZW1wbGF0ZSAmJiByb3dEZXRhaWxzUmVuZGVyZXIpIHsKICAgICAgICAgIHRocm93IG5ldyBFcnJvcignWW91IHNob3VsZCBvbmx5IHVzZSBlaXRoZXIgYSByZW5kZXJlciBvciBhIHRlbXBsYXRlIGZvciByb3cgZGV0YWlscycpOwogICAgICAgIH0KICAgICAgICBpZiAocm93RGV0YWlsc1RlbXBsYXRlIHx8IHJvd0RldGFpbHNSZW5kZXJlcikgewogICAgICAgICAgaWYgKHJvd0RldGFpbHNUZW1wbGF0ZSAmJiAhcm93RGV0YWlsc1RlbXBsYXRlLnRlbXBsYXRpemVyKSB7CiAgICAgICAgICAgIHZhciB0ZW1wbGF0aXplciA9IG5ldyBHcmlkVGVtcGxhdGl6ZXIoKTsKICAgICAgICAgICAgdGVtcGxhdGl6ZXIuX2dyaWQgPSB0aGlzOwogICAgICAgICAgICB0ZW1wbGF0aXplci5kYXRhSG9zdCA9IHRoaXMuZGF0YUhvc3Q7CiAgICAgICAgICAgIHRlbXBsYXRpemVyLnRlbXBsYXRlID0gcm93RGV0YWlsc1RlbXBsYXRlOwogICAgICAgICAgICByb3dEZXRhaWxzVGVtcGxhdGUudGVtcGxhdGl6ZXIgPSB0ZW1wbGF0aXplcjsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAodGhpcy5fY29sdW1uVHJlZSkgewogICAgICAgICAgICAvLyBPbmx5IHVwZGF0ZSB0aGUgcm93cyBpZiB0aGUgY29sdW1uIHRyZWUgaGFzIGFscmVhZHkgYmVlbiBpbml0aWFsaXplZAogICAgICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5jaGlsZHJlbikuZm9yRWFjaChyb3cgPT4gewogICAgICAgICAgICAgIGlmICghcm93LnF1ZXJ5U2VsZWN0b3IoJ1twYXJ0fj1kZXRhaWxzLWNlbGxdJykpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVJvdyhyb3csIHRoaXMuX2NvbHVtblRyZWVbdGhpcy5fY29sdW1uVHJlZS5sZW5ndGggLSAxXSk7CiAgICAgICAgICAgICAgICB0aGlzLl9hMTF5VXBkYXRlUm93RGV0YWlsc09wZW5lZChyb3csIGZhbHNlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgLy8gQ2xlYXIgYW55IG9sZCB0ZW1wbGF0ZSBpbnN0YW5jZXMKICAgICAgICAgICAgICBkZWxldGUgcm93LnF1ZXJ5U2VsZWN0b3IoJ1twYXJ0fj1kZXRhaWxzLWNlbGxdJykuX2luc3RhbmNlOwogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAodGhpcy5kZXRhaWxzT3BlbmVkSXRlbXMubGVuZ3RoKSB7CiAgICAgICAgICAgIEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5mb3JFYWNoKHRoaXMuX3RvZ2dsZURldGFpbHNDZWxsLCB0aGlzKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlKCk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfZGV0YWlsc09wZW5lZEl0ZW1zQ2hhbmdlZChjaGFuZ2VSZWNvcmQsIHJvd0RldGFpbHNUZW1wbGF0ZSwgcm93RGV0YWlsc1JlbmRlcmVyKSB7CiAgICAgICAgaWYgKGNoYW5nZVJlY29yZC5wYXRoID09PSAnZGV0YWlsc09wZW5lZEl0ZW1zLmxlbmd0aCcgfHwgIWNoYW5nZVJlY29yZC52YWx1ZSkgewogICAgICAgICAgLy8gTGV04oCZcyBhdm9pZCBkdXBsaWNhdGUgd29yayBvZiBib3RoIOKAnC5zcGxpY2Vz4oCdIGFuZCDigJwubGVuZ3Ro4oCdIHVwZGF0ZXMuCiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICAgIEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5mb3JFYWNoKHJvdyA9PiB7CiAgICAgICAgICB0aGlzLl90b2dnbGVEZXRhaWxzQ2VsbChyb3csIHJvdy5faXRlbSk7CiAgICAgICAgICB0aGlzLl9hMTF5VXBkYXRlUm93RGV0YWlsc09wZW5lZChyb3csIHRoaXMuX2lzRGV0YWlsc09wZW5lZChyb3cuX2l0ZW0pKTsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnZGV0YWlscy1vcGVuZWQnLCB0aGlzLl9pc0RldGFpbHNPcGVuZWQocm93Ll9pdGVtKSwgcm93KTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgX2NvbmZpZ3VyZURldGFpbHNDZWxsKGNlbGwpIHsKICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgncGFydCcsICdjZWxsIGRldGFpbHMtY2VsbCcpOwogICAgICAgIC8vIEZyZWV6ZSB0aGUgZGV0YWlscyBjZWxsLCBzbyB0aGF0IGl0IGRvZXMgbm90IHNjcm9sbCBob3Jpem9udGFsbHkKICAgICAgICAvLyB3aXRoIHRoZSBub3JtYWwgY2VsbHMuIFRoaXMgd2F5IGl0IGxvb2tzIGxlc3Mgd2VpcmQuCiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdmcm96ZW4nLCB0cnVlLCBjZWxsKTsKICAgICAgfQoKICAgICAgX3RvZ2dsZURldGFpbHNDZWxsKHJvdywgaXRlbSkgewogICAgICAgIGNvbnN0IGNlbGwgPSByb3cucXVlcnlTZWxlY3RvcignW3BhcnR+PSJkZXRhaWxzLWNlbGwiXScpOwogICAgICAgIGlmICghY2VsbCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBjb25zdCBkZXRhaWxzSGlkZGVuID0gIXRoaXMuX2lzRGV0YWlsc09wZW5lZChpdGVtKTsKICAgICAgICBjb25zdCBoaWRkZW5DaGFuZ2VkID0gISFjZWxsLmhpZGRlbiAhPT0gZGV0YWlsc0hpZGRlbjsKCiAgICAgICAgaWYgKCFjZWxsLl9pbnN0YW5jZSAmJiAhY2VsbC5fcmVuZGVyZXIgfHwgY2VsbC5oaWRkZW4gIT09IGRldGFpbHNIaWRkZW4pIHsKICAgICAgICAgIGNlbGwuaGlkZGVuID0gZGV0YWlsc0hpZGRlbjsKICAgICAgICAgIGlmIChkZXRhaWxzSGlkZGVuKSB7CiAgICAgICAgICAgIHJvdy5zdHlsZS5yZW1vdmVQcm9wZXJ0eSgncGFkZGluZy1ib3R0b20nKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGlmICh0aGlzLnJvd0RldGFpbHNSZW5kZXJlcikgewogICAgICAgICAgICAgIGNlbGwuX3JlbmRlcmVyID0gdGhpcy5yb3dEZXRhaWxzUmVuZGVyZXI7CiAgICAgICAgICAgICAgY2VsbC5fcmVuZGVyZXIuY2FsbCh0aGlzLCBjZWxsLl9jb250ZW50LCB0aGlzLCB7aW5kZXg6IHJvdy5pbmRleCwgaXRlbTogaXRlbX0pOwogICAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX3Jvd0RldGFpbHNUZW1wbGF0ZSAmJiAhY2VsbC5faW5zdGFuY2UpIHsKICAgICAgICAgICAgICAvLyBTdGFtcCB0aGUgdGVtcGxhdGUKICAgICAgICAgICAgICBjZWxsLl9pbnN0YW5jZSA9IHRoaXMuX3Jvd0RldGFpbHNUZW1wbGF0ZS50ZW1wbGF0aXplci5jcmVhdGVJbnN0YW5jZSgpOwogICAgICAgICAgICAgIGNlbGwuX2NvbnRlbnQuaW5uZXJIVE1MID0gJyc7CiAgICAgICAgICAgICAgY2VsbC5fY29udGVudC5hcHBlbmRDaGlsZChjZWxsLl9pbnN0YW5jZS5yb290KTsKICAgICAgICAgICAgICB0aGlzLl91cGRhdGVJdGVtKHJvdywgaXRlbSk7CiAgICAgICAgICAgIH0KCiAgICAgICAgICAgIGZsdXNoKCk7CiAgICAgICAgICAgIHJvdy5zdHlsZS5zZXRQcm9wZXJ0eSgncGFkZGluZy1ib3R0b20nLCBgJHtjZWxsLm9mZnNldEhlaWdodH1weGApOwoKICAgICAgICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKCgpID0+IHRoaXMubm90aWZ5UmVzaXplKCkpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAoaGlkZGVuQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5fdXBkYXRlTWV0cmljcygpOwogICAgICAgICAgdGhpcy5fcG9zaXRpb25JdGVtcygpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3VwZGF0ZURldGFpbHNDZWxsSGVpZ2h0cygpIHsKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5xdWVyeVNlbGVjdG9yQWxsKCdbcGFydH49ImRldGFpbHMtY2VsbCJdOm5vdChbaGlkZGVuXSknKSkuZm9yRWFjaChjZWxsID0+IHsKICAgICAgICAgIGNlbGwucGFyZW50RWxlbWVudC5zdHlsZS5zZXRQcm9wZXJ0eSgncGFkZGluZy1ib3R0b20nLCBgJHtjZWxsLm9mZnNldEhlaWdodH1weGApOwogICAgICAgIH0pOwogICAgICB9CgogICAgICBfaXNEZXRhaWxzT3BlbmVkKGl0ZW0pIHsKICAgICAgICByZXR1cm4gdGhpcy5kZXRhaWxzT3BlbmVkSXRlbXMgJiYgdGhpcy5fZ2V0SXRlbUluZGV4SW5BcnJheShpdGVtLCB0aGlzLmRldGFpbHNPcGVuZWRJdGVtcykgIT09IC0xOwogICAgICB9CgogICAgICAvKioKICAgICAgICogT3BlbiB0aGUgZGV0YWlscyByb3cgb2YgYSBnaXZlbiBpdGVtLgogICAgICAgKi8KICAgICAgb3Blbkl0ZW1EZXRhaWxzKGl0ZW0pIHsKICAgICAgICBpZiAoIXRoaXMuX2lzRGV0YWlsc09wZW5lZChpdGVtKSkgewogICAgICAgICAgdGhpcy5wdXNoKCdkZXRhaWxzT3BlbmVkSXRlbXMnLCBpdGVtKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBDbG9zZSB0aGUgZGV0YWlscyByb3cgb2YgYSBnaXZlbiBpdGVtLgogICAgICAgKi8KICAgICAgY2xvc2VJdGVtRGV0YWlscyhpdGVtKSB7CiAgICAgICAgaWYgKHRoaXMuX2lzRGV0YWlsc09wZW5lZChpdGVtKSkgewogICAgICAgICAgdGhpcy5zcGxpY2UoJ2RldGFpbHNPcGVuZWRJdGVtcycsIHRoaXMuX2dldEl0ZW1JbmRleEluQXJyYXkoaXRlbSwgdGhpcy5kZXRhaWxzT3BlbmVkSXRlbXMpLCAxKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9kZXRhaWxzT3BlbmVkSW5zdGFuY2VDaGFuZ2VkQ2FsbGJhY2soaW5zdGFuY2UsIHZhbHVlKSB7CiAgICAgICAgaWYgKHN1cGVyLl9kZXRhaWxzT3BlbmVkSW5zdGFuY2VDaGFuZ2VkQ2FsbGJhY2spIHsKICAgICAgICAgIHN1cGVyLl9kZXRhaWxzT3BlbmVkSW5zdGFuY2VDaGFuZ2VkQ2FsbGJhY2soaW5zdGFuY2UsIHZhbHVlKTsKICAgICAgICB9CiAgICAgICAgaWYgKHZhbHVlKSB7CiAgICAgICAgICB0aGlzLm9wZW5JdGVtRGV0YWlscyhpbnN0YW5jZS5pdGVtKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5jbG9zZUl0ZW1EZXRhaWxzKGluc3RhbmNlLml0ZW0pOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IFNjcm9sbE1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBTY3JvbGxNaXhpbiBleHRlbmRzIHN1cGVyQ2xhc3MgewoKICAgICAgZ2V0IF90aW1lb3V0cygpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgU0NST0xMX1BFUklPRDogMTAwMCwKICAgICAgICAgIFdIRUVMX1NDUk9MTElORzogMjAwLAogICAgICAgICAgU0NST0xMSU5HOiAxMDAsCiAgICAgICAgICBJR05PUkVfV0hFRUw6IDUwMAogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewoKICAgICAgICAgIC8vIENhY2hlZCBhcnJheSBvZiBmcm96ZW4gY2VsbHMKICAgICAgICAgIF9mcm96ZW5DZWxsczogewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfSwKICAgICAgICAgIH0sCgogICAgICAgICAgX3Njcm9sbGJhcldpZHRoOiB7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIC8vIENyZWF0ZSB0aGUgbWVhc3VyZW1lbnQgbm9kZQogICAgICAgICAgICAgIHZhciBzY3JvbGxEaXYgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgICAgICAgICAgICBzY3JvbGxEaXYuc3R5bGUud2lkdGggPSAnMTAwcHgnOwogICAgICAgICAgICAgIHNjcm9sbERpdi5zdHlsZS5oZWlnaHQgPSAnMTAwcHgnOwogICAgICAgICAgICAgIHNjcm9sbERpdi5zdHlsZS5vdmVyZmxvdyA9ICdzY3JvbGwnOwogICAgICAgICAgICAgIHNjcm9sbERpdi5zdHlsZS5wb3NpdGlvbiA9ICdhYnNvbHV0ZSc7CiAgICAgICAgICAgICAgc2Nyb2xsRGl2LnN0eWxlLnRvcCA9ICctOTk5OXB4JzsKICAgICAgICAgICAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKHNjcm9sbERpdik7CiAgICAgICAgICAgICAgLy8gR2V0IHRoZSBzY3JvbGxiYXIgd2lkdGgKICAgICAgICAgICAgICB2YXIgc2Nyb2xsYmFyV2lkdGggPSBzY3JvbGxEaXYub2Zmc2V0V2lkdGggLSBzY3JvbGxEaXYuY2xpZW50V2lkdGg7CiAgICAgICAgICAgICAgLy8gRGVsZXRlIHRoZSBESVYKICAgICAgICAgICAgICBkb2N1bWVudC5ib2R5LnJlbW92ZUNoaWxkKHNjcm9sbERpdik7CiAgICAgICAgICAgICAgcmV0dXJuIHNjcm9sbGJhcldpZHRoOwogICAgICAgICAgICB9CiAgICAgICAgICB9LAoKICAgICAgICAgIF9yb3dXaXRoRm9jdXNlZEVsZW1lbnQ6IEVsZW1lbnQsCgogICAgICAgICAgX2RlbHRhWUFjYzogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIHZhbHVlOiAwCiAgICAgICAgICB9CgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX3Njcm9sbEhlaWdodFVwZGF0ZWQoX2VzdFNjcm9sbEhlaWdodCknLAogICAgICAgICAgJ19zY3JvbGxWaWV3cG9ydEhlaWdodFVwZGF0ZWQoX3ZpZXdwb3J0SGVpZ2h0KScKICAgICAgICBdOwogICAgICB9CgogICAgICAvLyBPdmVycmlkZSAoZnJvbSBpcm9uLXNjcm9sbC10YXJnZXQtYmVoYXZpb3IpIHRvIGF2b2lkIGRvY3VtZW50IHNjcm9sbAogICAgICBzZXQgX3Njcm9sbFRvcCh0b3ApIHsKICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsVG9wID0gdG9wOwogICAgICB9CgogICAgICBnZXQgX3Njcm9sbFRvcCgpIHsKICAgICAgICByZXR1cm4gdGhpcy4kLnRhYmxlLnNjcm9sbFRvcDsKICAgICAgfQoKICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgc3VwZXIoKTsKICAgICAgICB0aGlzLl9zY3JvbGxMaW5lSGVpZ2h0ID0gdGhpcy5fZ2V0U2Nyb2xsTGluZUhlaWdodCgpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogQHJldHVybnMge051bWJlcnx1bmRlZmluZWR9IC0gVGhlIGJyb3dzZXIncyBkZWZhdWx0IGZvbnQtc2l6ZSBpbiBwaXhlbHMKICAgICAgICovCiAgICAgIF9nZXRTY3JvbGxMaW5lSGVpZ2h0KCkgewogICAgICAgIGNvbnN0IGVsID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgZWwuc3R5bGUuZm9udFNpemUgPSAnaW5pdGlhbCc7CiAgICAgICAgZWwuc3R5bGUuZGlzcGxheSA9ICdub25lJzsKICAgICAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKGVsKTsKICAgICAgICBjb25zdCBmb250U2l6ZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKGVsKS5mb250U2l6ZTsKICAgICAgICBkb2N1bWVudC5ib2R5LnJlbW92ZUNoaWxkKGVsKTsKICAgICAgICByZXR1cm4gZm9udFNpemUgPyB3aW5kb3cucGFyc2VJbnQoZm9udFNpemUpIDogdW5kZWZpbmVkOwogICAgICB9CgogICAgICBfc2Nyb2xsVmlld3BvcnRIZWlnaHRVcGRhdGVkKF92aWV3cG9ydEhlaWdodCkgewogICAgICAgIHRoaXMuX3Njcm9sbFBhZ2VIZWlnaHQgPSBfdmlld3BvcnRIZWlnaHQgLSB0aGlzLiQuaGVhZGVyLmNsaWVudEhlaWdodCAtIHRoaXMuJC5mb290ZXIuY2xpZW50SGVpZ2h0IC0gdGhpcy5fc2Nyb2xsTGluZUhlaWdodDsKICAgICAgfQoKICAgICAgcmVhZHkoKSB7CiAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICB0aGlzLnNjcm9sbFRhcmdldCA9IHRoaXMuJC50YWJsZTsKCiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCd3aGVlbCcsIGUgPT4gewogICAgICAgICAgdGhpcy5fd2hlZWxTY3JvbGxpbmcgPSB0cnVlOwogICAgICAgICAgdGhpcy5fZGVib3VuY2VyV2hlZWxTY3JvbGxpbmcgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgIHRoaXMuX2RlYm91bmNlcldoZWVsU2Nyb2xsaW5nLAogICAgICAgICAgICB0aW1lT3V0LmFmdGVyKHRoaXMuX3RpbWVvdXRzLldIRUVMX1NDUk9MTElORyksCiAgICAgICAgICAgICgpID0+IHRoaXMuX3doZWVsU2Nyb2xsaW5nID0gZmFsc2UKICAgICAgICAgICk7CiAgICAgICAgICB0aGlzLl9vbldoZWVsKGUpOwogICAgICAgIH0pOwoKICAgICAgICB0aGlzLiQudGFibGUuYWRkRXZlbnRMaXN0ZW5lcignc2Nyb2xsJywgZSA9PiB7CiAgICAgICAgICBpZiAodGhpcy4kLm91dGVyc2Nyb2xsZXIub3V0ZXJTY3JvbGxpbmcpIHsKICAgICAgICAgICAgZS5zdG9wSW1tZWRpYXRlUHJvcGFnYXRpb24oKTsKICAgICAgICAgIH0KICAgICAgICB9LCB0cnVlKTsKCiAgICAgICAgdGhpcy4kLml0ZW1zLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3VzaW4nLCAoZSkgPT4gewogICAgICAgICAgY29uc3QgaXRlbXNJbmRleCA9IGUuY29tcG9zZWRQYXRoKCkuaW5kZXhPZih0aGlzLiQuaXRlbXMpOwogICAgICAgICAgdGhpcy5fcm93V2l0aEZvY3VzZWRFbGVtZW50ID0gZS5jb21wb3NlZFBhdGgoKVtpdGVtc0luZGV4IC0gMV07CiAgICAgICAgfSk7CiAgICAgICAgdGhpcy4kLml0ZW1zLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3Vzb3V0JywgKCkgPT4gdGhpcy5fcm93V2l0aEZvY3VzZWRFbGVtZW50ID0gdW5kZWZpbmVkKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFNjcm9sbCB0byBhIHNwZWNpZmljIHJvdyBpbmRleCBpbiB0aGUgdmlydHVhbCBsaXN0LiBOb3RlIHRoYXQgdGhlIHJvdyBpbmRleCBpcwogICAgICAgKiBub3QgYWx3YXlzIHRoZSBzYW1lIGZvciBhbnkgcGFydGljdWxhciBpdGVtLiBGb3IgZXhhbXBsZSwgc29ydGluZy9maWx0ZXJpbmcvZXhwYW5kaW5nCiAgICAgICAqIG9yIGNvbGxhcHNpbmcgaGllcmFyY2hpY2FsIGl0ZW1zIGNhbiBhZmZlY3QgdGhlIHJvdyBpbmRleCByZWxhdGVkIHRvIGFuIGl0ZW0uCiAgICAgICAqCiAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBpbmRleCBSb3cgaW5kZXggdG8gc2Nyb2xsIHRvCiAgICAgICAqLwogICAgICBzY3JvbGxUb0luZGV4KGluZGV4KSB7CiAgICAgICAgdGhpcy5fYWNjZXNzSXJvbkxpc3RBUEkoKCkgPT4gc3VwZXIuc2Nyb2xsVG9JbmRleChpbmRleCkpOwogICAgICB9CgogICAgICBfb25XaGVlbChlKSB7CiAgICAgICAgaWYgKGUuY3RybEtleSB8fCB0aGlzLl9oYXNTY3JvbGxlZEFuY2VzdG9yKGUudGFyZ2V0LCBlLmRlbHRhWCwgZS5kZWx0YVkpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBjb25zdCB0YWJsZSA9IHRoaXMuJC50YWJsZTsKCiAgICAgICAgbGV0IGRlbHRhWSA9IGUuZGVsdGFZOwogICAgICAgIGlmIChlLmRlbHRhTW9kZSA9PT0gV2hlZWxFdmVudC5ET01fREVMVEFfTElORSkgewogICAgICAgICAgLy8gU2Nyb2xsaW5nIGJ5ICJsaW5lcyBvZiB0ZXh0IiBpbnN0ZWFkIG9mIHBpeGVscwogICAgICAgICAgZGVsdGFZICo9IHRoaXMuX3Njcm9sbExpbmVIZWlnaHQ7CiAgICAgICAgfSBlbHNlIGlmIChlLmRlbHRhTW9kZSA9PT0gV2hlZWxFdmVudC5ET01fREVMVEFfUEFHRSkgewogICAgICAgICAgLy8gU2Nyb2xsaW5nIGJ5ICJwYWdlcyIgaW5zdGVhZCBvZiBwaXhlbHMKICAgICAgICAgIGRlbHRhWSAqPSB0aGlzLl9zY3JvbGxQYWdlSGVpZ2h0OwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuX3doZWVsQW5pbWF0aW9uRnJhbWUpIHsKICAgICAgICAgIC8vIFNraXAgbmV3IHdoZWVsIGV2ZW50cyB3aGlsZSBvbmUgaXMgYmVpbmcgcHJvY2Vzc2VkCiAgICAgICAgICB0aGlzLl9kZWx0YVlBY2MgKz0gZGVsdGFZOwogICAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgZGVsdGFZICs9IHRoaXMuX2RlbHRhWUFjYzsKICAgICAgICB0aGlzLl9kZWx0YVlBY2MgPSAwOwoKICAgICAgICB0aGlzLl93aGVlbEFuaW1hdGlvbkZyYW1lID0gdHJ1ZTsKICAgICAgICB0aGlzLl9kZWJvdW5jZXJXaGVlbEFuaW1hdGlvbkZyYW1lID0gRGVib3VuY2VyLmRlYm91bmNlKAogICAgICAgICAgdGhpcy5fZGVib3VuY2VyV2hlZWxBbmltYXRpb25GcmFtZSwKICAgICAgICAgIGFuaW1hdGlvbkZyYW1lLAogICAgICAgICAgKCkgPT4gdGhpcy5fd2hlZWxBbmltYXRpb25GcmFtZSA9IGZhbHNlCiAgICAgICAgKTsKCiAgICAgICAgdmFyIG1vbWVudHVtID0gTWF0aC5hYnMoZS5kZWx0YVgpICsgTWF0aC5hYnMoZGVsdGFZKTsKCiAgICAgICAgaWYgKHRoaXMuX2NhblNjcm9sbCh0YWJsZSwgZS5kZWx0YVgsIGRlbHRhWSkpIHsKICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgIHRhYmxlLnNjcm9sbFRvcCArPSBkZWx0YVk7CiAgICAgICAgICB0YWJsZS5zY3JvbGxMZWZ0ICs9IGUuZGVsdGFYOwogICAgICAgICAgdGhpcy5fc2Nyb2xsSGFuZGxlcigpOwogICAgICAgICAgdGhpcy5faGFzUmVzaWR1YWxNb21lbnR1bSA9IHRydWU7CgogICAgICAgICAgdGhpcy5faWdub3JlTmV3V2hlZWwgPSB0cnVlOwogICAgICAgICAgdGhpcy5fZGVib3VuY2VySWdub3JlTmV3V2hlZWwgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICAgIHRoaXMuX2RlYm91bmNlcklnbm9yZU5ld1doZWVsLAogICAgICAgICAgICB0aW1lT3V0LmFmdGVyKHRoaXMuX3RpbWVvdXRzLklHTk9SRV9XSEVFTCksCiAgICAgICAgICAgICgpID0+IHRoaXMuX2lnbm9yZU5ld1doZWVsID0gZmFsc2UKICAgICAgICAgICk7CiAgICAgICAgfSBlbHNlIGlmICh0aGlzLl9oYXNSZXNpZHVhbE1vbWVudHVtICYmIG1vbWVudHVtIDw9IHRoaXMuX3ByZXZpb3VzTW9tZW50dW0gfHwgdGhpcy5faWdub3JlTmV3V2hlZWwpIHsKICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICB9IGVsc2UgaWYgKG1vbWVudHVtID4gdGhpcy5fcHJldmlvdXNNb21lbnR1bSkgewogICAgICAgICAgdGhpcy5faGFzUmVzaWR1YWxNb21lbnR1bSA9IGZhbHNlOwogICAgICAgIH0KICAgICAgICB0aGlzLl9wcmV2aW91c01vbWVudHVtID0gbW9tZW50dW07CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBEZXRlcm1pbmVzIGlmIHRoZSBlbGVtZW50IGhhcyBhbiBhbmNlc3RvciBwcmlvciB0byB0aGlzCiAgICAgICAqIGNlbGwgY29udGVudCB0aGF0IGhhbmRsZXMgdGhlIHNjcm9sbCBkZWx0YQogICAgICAgKi8KICAgICAgX2hhc1Njcm9sbGVkQW5jZXN0b3IoZWwsIGRlbHRhWCwgZGVsdGFZKSB7CiAgICAgICAgaWYgKGVsLmxvY2FsTmFtZSA9PT0gJ3ZhYWRpbi1ncmlkLWNlbGwtY29udGVudCcpIHsKICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX2NhblNjcm9sbChlbCwgZGVsdGFYLCBkZWx0YVkpCiAgICAgICAgICAmJiBbJ2F1dG8nLCAnc2Nyb2xsJ10uaW5kZXhPZihnZXRDb21wdXRlZFN0eWxlKGVsKS5vdmVyZmxvdykgIT09IC0xKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9IGVsc2UgaWYgKGVsICE9PSB0aGlzICYmIGVsLnBhcmVudEVsZW1lbnQpIHsKICAgICAgICAgIHJldHVybiB0aGlzLl9oYXNTY3JvbGxlZEFuY2VzdG9yKGVsLnBhcmVudEVsZW1lbnQsIGRlbHRhWCwgZGVsdGFZKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBEZXRlcm1pbmVzIGlmIHRoZSB0aGUgZ2l2ZW4gc2Nyb2xsIGRlbHRhcyBjYW4gYmUgYXBwbGllZCB0byB0aGUgZWxlbWVudAogICAgICAgKiAoZnVsbHkgb3IgcGFydGlhbGx5KQogICAgICAgKi8KICAgICAgX2NhblNjcm9sbChlbCwgZGVsdGFYLCBkZWx0YVkpIHsKICAgICAgICByZXR1cm4gKGRlbHRhWSA+IDAgJiYgZWwuc2Nyb2xsVG9wIDwgZWwuc2Nyb2xsSGVpZ2h0IC0gZWwub2Zmc2V0SGVpZ2h0KSB8fAogICAgICAgIChkZWx0YVkgPCAwICYmIGVsLnNjcm9sbFRvcCA+IDApIHx8CiAgICAgICAgKGRlbHRhWCA+IDAgJiYgZWwuc2Nyb2xsTGVmdCA8IGVsLnNjcm9sbFdpZHRoIC0gZWwub2Zmc2V0V2lkdGgpIHx8CiAgICAgICAgKGRlbHRhWCA8IDAgJiYgZWwuc2Nyb2xsTGVmdCA+IDApOwogICAgICB9CgogICAgICBfc2NoZWR1bGVTY3JvbGxpbmcoKSB7CiAgICAgICAgaWYgKCF0aGlzLl9zY3JvbGxpbmdGcmFtZSkgewogICAgICAgICAgLy8gRGVmZXIgc2V0dGluZyBzdGF0ZSBhdHRyaWJ1dGVzIHRvIGF2b2lkIEVkZ2UgaGljY3VwcwogICAgICAgICAgdGhpcy5fc2Nyb2xsaW5nRnJhbWUgPSByZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdzY3JvbGxpbmcnLCB0cnVlLCB0aGlzLiQuc2Nyb2xsZXIpKTsKICAgICAgICB9CiAgICAgICAgdGhpcy5fZGVib3VuY2VTY3JvbGxpbmcgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICB0aGlzLl9kZWJvdW5jZVNjcm9sbGluZywKICAgICAgICAgIHRpbWVPdXQuYWZ0ZXIodGhpcy5fdGltZW91dHMuU0NST0xMSU5HKSwKICAgICAgICAgICgpID0+IHsKICAgICAgICAgICAgY2FuY2VsQW5pbWF0aW9uRnJhbWUodGhpcy5fc2Nyb2xsaW5nRnJhbWUpOwogICAgICAgICAgICBkZWxldGUgdGhpcy5fc2Nyb2xsaW5nRnJhbWU7CiAgICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnc2Nyb2xsaW5nJywgZmFsc2UsIHRoaXMuJC5zY3JvbGxlcik7CiAgICAgICAgICAgIGlmICghdGhpcy4kLm91dGVyc2Nyb2xsZXIub3V0ZXJTY3JvbGxpbmcpIHsKICAgICAgICAgICAgICB0aGlzLl9yZW9yZGVyUm93cygpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgKTsKCiAgICAgICAgaWYgKCF0aGlzLl9zY3JvbGxQZXJpb2RGcmFtZSkgewogICAgICAgICAgdGhpcy5fc2Nyb2xsUGVyaW9kRnJhbWUgPSByZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdzY3JvbGwtcGVyaW9kJywgdHJ1ZSwgdGhpcy4kLnNjcm9sbGVyKSk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX2RlYm91bmNlU2Nyb2xsUGVyaW9kID0gRGVib3VuY2VyLmRlYm91bmNlKAogICAgICAgICAgdGhpcy5fZGVib3VuY2VTY3JvbGxQZXJpb2QsCiAgICAgICAgICB0aW1lT3V0LmFmdGVyKHRoaXMuX3RpbWVvdXRzLlNDUk9MTF9QRVJJT0QpLAogICAgICAgICAgKCkgPT4gewogICAgICAgICAgICBjYW5jZWxBbmltYXRpb25GcmFtZSh0aGlzLl9zY3JvbGxQZXJpb2RGcmFtZSk7CiAgICAgICAgICAgIGRlbGV0ZSB0aGlzLl9zY3JvbGxQZXJpb2RGcmFtZTsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdzY3JvbGwtcGVyaW9kJywgZmFsc2UsIHRoaXMuJC5zY3JvbGxlcik7CiAgICAgICAgICB9CiAgICAgICAgKTsKICAgICAgfQoKICAgICAgX2FmdGVyU2Nyb2xsKCkgewogICAgICAgIHRoaXMuX3RyYW5zbGF0ZVN0YXRpb25hcnlFbGVtZW50cygpOwoKICAgICAgICBpZiAoIXRoaXMuaGFzQXR0cmlidXRlKCdyZW9yZGVyaW5nJykpIHsKICAgICAgICAgIHRoaXMuX3NjaGVkdWxlU2Nyb2xsaW5nKCk7CiAgICAgICAgfQoKICAgICAgICBjb25zdCBvcyA9IHRoaXMuJC5vdXRlcnNjcm9sbGVyOwogICAgICAgIGlmICghdGhpcy5faW9zICYmICh0aGlzLl93aGVlbFNjcm9sbGluZyB8fCBvcy5wYXNzdGhyb3VnaCkpIHsKICAgICAgICAgIG9zLnN5bmNPdXRlclNjcm9sbGVyKCk7CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy5faW9zKSB7CiAgICAgICAgICAvLyBFbmFibGUgdmVydGljYWwgcnViYmVyYmFuZCBmZWVkYmFjawogICAgICAgICAgY29uc3Qgb3ZlclNjcm9sbCA9IE1hdGgubWF4KC1vcy5zY3JvbGxUb3AsIDApIHx8CiAgICAgICAgICAgIE1hdGgubWluKDAsIG9zLnNjcm9sbEhlaWdodCAtIG9zLnNjcm9sbFRvcCAtIG9zLm9mZnNldEhlaWdodCk7CiAgICAgICAgICB0aGlzLiQuaXRlbXMuc3R5bGUudHJhbnNmb3JtID0gYHRyYW5zbGF0ZVkoJHtvdmVyU2Nyb2xsfXB4KWA7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl91cGRhdGVPdmVyZmxvdygpOwogICAgICB9CgogICAgICBfdXBkYXRlT3ZlcmZsb3coKSB7CiAgICAgICAgLy8gU2V0IG92ZXJmbG93IHN0eWxpbmcgYXR0cmlidXRlcwogICAgICAgIGxldCBvdmVyZmxvdyA9ICcnOwogICAgICAgIGNvbnN0IHRhYmxlID0gdGhpcy4kLnRhYmxlOwogICAgICAgIGlmICh0YWJsZS5zY3JvbGxUb3AgPCB0YWJsZS5zY3JvbGxIZWlnaHQgLSB0YWJsZS5jbGllbnRIZWlnaHQpIHsKICAgICAgICAgIG92ZXJmbG93ICs9ICcgYm90dG9tJzsKICAgICAgICB9CgogICAgICAgIGlmICh0YWJsZS5zY3JvbGxUb3AgPiAwKSB7CiAgICAgICAgICBvdmVyZmxvdyArPSAnIHRvcCc7CiAgICAgICAgfQoKICAgICAgICBpZiAodGFibGUuc2Nyb2xsTGVmdCA8IHRhYmxlLnNjcm9sbFdpZHRoIC0gdGFibGUuY2xpZW50V2lkdGgpIHsKICAgICAgICAgIG92ZXJmbG93ICs9ICcgcmlnaHQnOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRhYmxlLnNjcm9sbExlZnQgPiAwKSB7CiAgICAgICAgICBvdmVyZmxvdyArPSAnIGxlZnQnOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fZGVib3VuY2VPdmVyZmxvdyA9IERlYm91bmNlci5kZWJvdW5jZSgKICAgICAgICAgIHRoaXMuX2RlYm91bmNlT3ZlcmZsb3csCiAgICAgICAgICBhbmltYXRpb25GcmFtZSwKICAgICAgICAgICgpID0+IHsKICAgICAgICAgICAgY29uc3QgdmFsdWUgPSBvdmVyZmxvdy50cmltKCk7CiAgICAgICAgICAgIGlmICh2YWx1ZS5sZW5ndGggPiAwICYmIHRoaXMuZ2V0QXR0cmlidXRlKCdvdmVyZmxvdycpICE9PSB2YWx1ZSkgewogICAgICAgICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCdvdmVyZmxvdycsIHZhbHVlKTsKICAgICAgICAgICAgfSBlbHNlIGlmICh2YWx1ZS5sZW5ndGggPT0gMCAmJiB0aGlzLmhhc0F0dHJpYnV0ZSgnb3ZlcmZsb3cnKSkgewogICAgICAgICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdvdmVyZmxvdycpOwogICAgICAgICAgICB9CiAgICAgICAgICB9CiAgICAgICAgKTsKICAgICAgfQoKICAgICAgLy8gY29ycmVjdCBvcmRlciBuZWVkZWQgZm9yIHByZXNlcnZpbmcgY29ycmVjdCB0YWIgb3JkZXIgYmV0d2VlbiBjZWxsIGNvbnRlbnRzLgogICAgICBfcmVvcmRlclJvd3MoKSB7CiAgICAgICAgY29uc3QgYm9keSA9IHRoaXMuJC5pdGVtczsKICAgICAgICBjb25zdCBpdGVtcyA9IGJvZHkucXVlcnlTZWxlY3RvckFsbCgndHInKTsKICAgICAgICBpZiAoIWl0ZW1zLmxlbmd0aCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgY29uc3QgYWRqdXN0ZWRWaXJ0dWFsU3RhcnQgPSB0aGlzLl92aXJ0dWFsU3RhcnQgKyB0aGlzLl92aWR4T2Zmc2V0OwoKICAgICAgICAvLyBXaGljaCByb3cgdG8gdXNlIGFzIGEgdGFyZ2V0PwogICAgICAgIGNvbnN0IHRhcmdldFJvdyA9IHRoaXMuX3Jvd1dpdGhGb2N1c2VkRWxlbWVudCB8fCBBcnJheS5mcm9tKGl0ZW1zKS5maWx0ZXIocm93ID0+ICFyb3cuaGlkZGVuKVswXTsKICAgICAgICBpZiAoIXRhcmdldFJvdykgewogICAgICAgICAgLy8gQWxsIHJvd3MgYXJlIGhpZGRlbiwgZG9uJ3QgcmVvcmRlcgogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gV2hlcmUgdGhlIHRhcmdldCByb3cgc2hvdWxkIGJlPwogICAgICAgIGNvbnN0IHRhcmdldFBoeXNpY2FsSW5kZXggPSB0YXJnZXRSb3cuaW5kZXggLSBhZGp1c3RlZFZpcnR1YWxTdGFydDsKCiAgICAgICAgLy8gUmVvZHJlciB0aGUgRE9NIGVsZW1lbnRzIHRvIGtlZXAgdGhlIHRhcmdldCByb3cgYXQgdGhlIHRhcmdldCBwaHlzaWNhbCBpbmRleAogICAgICAgIGNvbnN0IGRlbHRhID0gQXJyYXkuZnJvbShpdGVtcykuaW5kZXhPZih0YXJnZXRSb3cpIC0gdGFyZ2V0UGh5c2ljYWxJbmRleDsKICAgICAgICBpZiAoZGVsdGEgPiAwKSB7CiAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IGRlbHRhOyBpKyspIHsKICAgICAgICAgICAgYm9keS5hcHBlbmRDaGlsZChpdGVtc1tpXSk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIGlmIChkZWx0YSA8IDApIHsKICAgICAgICAgIGZvciAobGV0IGkgPSBpdGVtcy5sZW5ndGggKyBkZWx0YTsgaSA8IGl0ZW1zLmxlbmd0aDsgaSsrKSB7CiAgICAgICAgICAgIGJvZHkuaW5zZXJ0QmVmb3JlKGl0ZW1zW2ldLCBpdGVtc1swXSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfZnJvemVuQ2VsbHNDaGFuZ2VkKCkgewogICAgICAgIHRoaXMuX2RlYm91bmNlckNhY2hlRWxlbWVudHMgPSBEZWJvdW5jZXIuZGVib3VuY2UoCiAgICAgICAgICB0aGlzLl9kZWJvdW5jZXJDYWNoZUVsZW1lbnRzLAogICAgICAgICAgbWljcm9UYXNrLAogICAgICAgICAgKCkgPT4gewogICAgICAgICAgICBBcnJheS5mcm9tKHRoaXMucm9vdC5xdWVyeVNlbGVjdG9yQWxsKCdbcGFydH49ImNlbGwiXScpKS5mb3JFYWNoKGZ1bmN0aW9uKGNlbGwpIHsKICAgICAgICAgICAgICBjZWxsLnN0eWxlLnRyYW5zZm9ybSA9ICcnOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fZnJvemVuQ2VsbHMgPSBBcnJheS5wcm90b3R5cGUuc2xpY2UuY2FsbCh0aGlzLiQudGFibGUucXVlcnlTZWxlY3RvckFsbCgnW2Zyb3plbl0nKSk7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVNjcm9sbGVyTWVhc3VyZW1lbnRzKCk7CiAgICAgICAgICAgIHRoaXMuX3RyYW5zbGF0ZVN0YXRpb25hcnlFbGVtZW50cygpOwogICAgICAgICAgfQogICAgICAgICk7CiAgICAgICAgdGhpcy5fdXBkYXRlTGFzdEZyb3plbigpOwogICAgICB9CgogICAgICBfdXBkYXRlU2Nyb2xsZXJNZWFzdXJlbWVudHMoKSB7CiAgICAgICAgaWYgKHRoaXMuX2Zyb3plbkNlbGxzLmxlbmd0aCA+IDAgJiYgdGhpcy5fX2lzUlRMKSB7CiAgICAgICAgICB0aGlzLl9fc2Nyb2xsZXJNZXRyaWNzID0gewogICAgICAgICAgICBzY3JvbGxXaWR0aDogdGhpcy4kLm91dGVyc2Nyb2xsZXIuc2Nyb2xsV2lkdGgsCiAgICAgICAgICAgIGNsaWVudFdpZHRoOiB0aGlzLiQub3V0ZXJzY3JvbGxlci5jbGllbnRXaWR0aAogICAgICAgICAgfTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF91cGRhdGVMYXN0RnJvemVuKCkgewogICAgICAgIGlmICghdGhpcy5fY29sdW1uVHJlZSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgY29uc3QgY29sdW1uc1JvdyA9IHRoaXMuX2NvbHVtblRyZWVbdGhpcy5fY29sdW1uVHJlZS5sZW5ndGggLSAxXS5zbGljZSgwKTsKICAgICAgICBjb2x1bW5zUm93LnNvcnQoKGEsIGIpID0+IHsKICAgICAgICAgIHJldHVybiBhLl9vcmRlciAtIGIuX29yZGVyOwogICAgICAgIH0pOwogICAgICAgIGNvbnN0IGxhc3RGcm96ZW4gPSBjb2x1bW5zUm93LnJlZHVjZSgocHJldiwgY29sLCBpbmRleCkgPT4gewogICAgICAgICAgY29sLl9sYXN0RnJvemVuID0gZmFsc2U7CiAgICAgICAgICByZXR1cm4gY29sLmZyb3plbiAmJiAhY29sLmhpZGRlbiA/IGluZGV4IDogcHJldjsKICAgICAgICB9LCB1bmRlZmluZWQpOwogICAgICAgIGlmIChsYXN0RnJvemVuICE9PSB1bmRlZmluZWQpIHsKICAgICAgICAgIGNvbHVtbnNSb3dbbGFzdEZyb3plbl0uX2xhc3RGcm96ZW4gPSB0cnVlOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3RyYW5zbGF0ZVN0YXRpb25hcnlFbGVtZW50cygpIHsKICAgICAgICBpZiAodGhpcy5fZWRnZSAmJiAhdGhpcy5fc2Nyb2xsYmFyV2lkdGgpIHsKICAgICAgICAgIC8vIEZpeGVkIG1vZGUgKFRhYmxldCBFZGdlKQogICAgICAgICAgdGhpcy4kLml0ZW1zLnN0eWxlLnRyYW5zZm9ybSA9CiAgICAgICAgICB0aGlzLl9nZXRUcmFuc2xhdGUoLXRoaXMuX3Njcm9sbExlZnQgfHwgMCwgLXRoaXMuX3Njcm9sbFRvcCB8fCAwKTsKCiAgICAgICAgICB0aGlzLiQuZm9vdGVyLnN0eWxlLnRyYW5zZm9ybSA9IHRoaXMuJC5oZWFkZXIuc3R5bGUudHJhbnNmb3JtID0KICAgICAgICAgIHRoaXMuX2dldFRyYW5zbGF0ZSgtdGhpcy5fc2Nyb2xsTGVmdCB8fCAwLCAwKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy4kLmZvb3Rlci5zdHlsZS50cmFuc2Zvcm0gPSB0aGlzLiQuaGVhZGVyLnN0eWxlLnRyYW5zZm9ybSA9IHRoaXMuX2dldFRyYW5zbGF0ZSgwLCB0aGlzLl9zY3JvbGxUb3ApOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuX2Zyb3plbkNlbGxzLmxlbmd0aCA+IDApIHsKICAgICAgICAgIGNvbnN0IHggPSB0aGlzLl9faXNSVEwgPwogICAgICAgICAgICB0aGlzLl9fZ2V0Tm9ybWFsaXplZFNjcm9sbExlZnQodGhpcy4kLnRhYmxlKSArIHRoaXMuX19zY3JvbGxlck1ldHJpY3MuY2xpZW50V2lkdGggLQogICAgICAgICAgICB0aGlzLl9fc2Nyb2xsZXJNZXRyaWNzLnNjcm9sbFdpZHRoCiAgICAgICAgICAgIDogdGhpcy5fc2Nyb2xsTGVmdDsKICAgICAgICAgIHZhciBmcm96ZW5DZWxsVHJhbnNmb3JtID0gdGhpcy5fZ2V0VHJhbnNsYXRlKHgsIDApOwogICAgICAgICAgZm9yICh2YXIgaSA9IDA7IGkgPCB0aGlzLl9mcm96ZW5DZWxscy5sZW5ndGg7IGkrKykgewogICAgICAgICAgICB0aGlzLl9mcm96ZW5DZWxsc1tpXS5zdHlsZS50cmFuc2Zvcm0gPSBmcm96ZW5DZWxsVHJhbnNmb3JtOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgX2dldFRyYW5zbGF0ZSh4LCB5KSB7CiAgICAgICAgcmV0dXJuICd0cmFuc2xhdGUoJyArIHggKyAncHgsJyArIHkgKyAncHgpJzsKICAgICAgfQoKICAgICAgX3Njcm9sbEhlaWdodFVwZGF0ZWQoX2VzdFNjcm9sbEhlaWdodCkgewogICAgICAgIHRoaXMuJC5vdXRlcnNpemVyLnN0eWxlLnRvcCA9IHRoaXMuJC5maXhlZHNpemVyLnN0eWxlLnRvcCA9IF9lc3RTY3JvbGxIZWlnaHQgKyAncHgnOwogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgU2VsZWN0aW9uTWl4aW4gPSBzdXBlckNsYXNzID0+IGNsYXNzIFNlbGVjdGlvbk1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogQW4gYXJyYXkgdGhhdCBjb250YWlucyB0aGUgc2VsZWN0ZWQgaXRlbXMuCiAgICAgICAgICAgKi8KICAgICAgICAgIHNlbGVjdGVkSXRlbXM6IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgICAgIHZhbHVlOiAoKSA9PiBbXQogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX3NlbGVjdGVkSXRlbXNDaGFuZ2VkKHNlbGVjdGVkSXRlbXMuKiknCiAgICAgICAgXTsKICAgICAgfQoKICAgICAgX2lzU2VsZWN0ZWQoaXRlbSkgewogICAgICAgIHJldHVybiB0aGlzLnNlbGVjdGVkSXRlbXMgJiYgdGhpcy5fZ2V0SXRlbUluZGV4SW5BcnJheShpdGVtLCB0aGlzLnNlbGVjdGVkSXRlbXMpID4gLTE7CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBTZWxlY3RzIHRoZSBnaXZlbiBpdGVtLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIHNlbGVjdEl0ZW0KICAgICAgICogQHBhcmFtIHtPYmplY3R9IGl0ZW0gVGhlIGl0ZW0gb2JqZWN0CiAgICAgICAqLwogICAgICBzZWxlY3RJdGVtKGl0ZW0pIHsKICAgICAgICBpZiAoIXRoaXMuX2lzU2VsZWN0ZWQoaXRlbSkpIHsKICAgICAgICAgIHRoaXMucHVzaCgnc2VsZWN0ZWRJdGVtcycsIGl0ZW0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIERlc2VsZWN0cyB0aGUgZ2l2ZW4gaXRlbSBpZiBpdCBpcyBhbHJlYWR5IHNlbGVjdGVkLgogICAgICAgKgogICAgICAgKiBAbWV0aG9kIGRlc2VsZWN0CiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBpdGVtIFRoZSBpdGVtIG9iamVjdAogICAgICAgKi8KICAgICAgZGVzZWxlY3RJdGVtKGl0ZW0pIHsKICAgICAgICBjb25zdCBpbmRleCA9IHRoaXMuX2dldEl0ZW1JbmRleEluQXJyYXkoaXRlbSwgdGhpcy5zZWxlY3RlZEl0ZW1zKTsKICAgICAgICBpZiAoaW5kZXggPiAtMSkgewogICAgICAgICAgdGhpcy5zcGxpY2UoJ3NlbGVjdGVkSXRlbXMnLCBpbmRleCwgMSk7CiAgICAgICAgfQogICAgICB9CgogICAgICAvKioKICAgICAgICogVG9nZ2xlcyB0aGUgc2VsZWN0ZWQgc3RhdGUgb2YgdGhlIGdpdmVuIGl0ZW0uCiAgICAgICAqCiAgICAgICAqIEBtZXRob2QgdG9nZ2xlCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBpdGVtIFRoZSBpdGVtIG9iamVjdAogICAgICAgKi8KICAgICAgX3RvZ2dsZUl0ZW0oaXRlbSkgewogICAgICAgIGNvbnN0IGluZGV4ID0gdGhpcy5fZ2V0SXRlbUluZGV4SW5BcnJheShpdGVtLCB0aGlzLnNlbGVjdGVkSXRlbXMpOwogICAgICAgIGlmIChpbmRleCA9PT0gLTEpIHsKICAgICAgICAgIHRoaXMuc2VsZWN0SXRlbShpdGVtKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5kZXNlbGVjdEl0ZW0oaXRlbSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfc2VsZWN0ZWRJdGVtc0NoYW5nZWQoZSkgewogICAgICAgIGlmICh0aGlzLiQuaXRlbXMuY2hpbGRyZW4ubGVuZ3RoICYmIChlLnBhdGggPT09ICdzZWxlY3RlZEl0ZW1zJyB8fCBlLnBhdGggPT09ICdzZWxlY3RlZEl0ZW1zLnNwbGljZXMnKSkgewogICAgICAgICAgQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pLmZvckVhY2gocm93ID0+IHsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlSXRlbShyb3csIHJvdy5faXRlbSk7CiAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9zZWxlY3RlZEluc3RhbmNlQ2hhbmdlZENhbGxiYWNrKGluc3RhbmNlLCB2YWx1ZSkgewogICAgICAgIGlmIChzdXBlci5fc2VsZWN0ZWRJbnN0YW5jZUNoYW5nZWRDYWxsYmFjaykgewogICAgICAgICAgc3VwZXIuX3NlbGVjdGVkSW5zdGFuY2VDaGFuZ2VkQ2FsbGJhY2soaW5zdGFuY2UsIHZhbHVlKTsKICAgICAgICB9CiAgICAgICAgaWYgKHZhbHVlKSB7CiAgICAgICAgICB0aGlzLnNlbGVjdEl0ZW0oaW5zdGFuY2UuaXRlbSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHRoaXMuZGVzZWxlY3RJdGVtKGluc3RhbmNlLml0ZW0pOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IFNvcnRNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgU29ydE1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIGB0cnVlYCwgYWxsIGA8dmFhZGluLWdyaWQtc29ydGVyPmAgYXJlIGFwcGxpZWQgZm9yIHNvcnRpbmcuCiAgICAgICAgICAgKi8KICAgICAgICAgIG11bHRpU29ydDogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogZmFsc2UKICAgICAgICAgIH0sCgogICAgICAgICAgX3NvcnRlcnM6IHsKICAgICAgICAgICAgdHlwZTogQXJyYXksCiAgICAgICAgICAgIHZhbHVlOiBmdW5jdGlvbigpIHsKICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgIH0sCgogICAgICAgICAgX3ByZXZpb3VzU29ydGVyczogewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiBbXTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdzb3J0ZXItY2hhbmdlZCcsIHRoaXMuX29uU29ydGVyQ2hhbmdlZCk7CgogICAgICAgIC8vIFdpdGggUG9seW1lciAyICYgc2hhZHkgdGhlICdzb3J0ZXItY2hhbmdlZCcgbGlzdGVuZXIgaXNuJ3QgZ3VhcmFudGVlZCB0byBiZSByZWdpc3RlcmVkCiAgICAgICAgLy8gYmVmb3JlIGNoaWxkIDx2YWFkaW4tZ3JpZC1zb3J0ZXI+J3MgdXBncmFkZSBhbmQgZmlyZSB0aGUgZXZlbnRzLiBUaGUgZm9sbG93aW5nCiAgICAgICAgLy8gbWFrZXMgc3VyZSB0aGF0ICdzb3J0ZXItY2hhbmdlZCcgaXMgZmlyZWQgZm9yIGFsbCA8dmFhZGluLWdyaWQtc29ydGVyPiBlbGVtZW50cwogICAgICAgIC8vIGFmdGVyIHRoaXMgKDx2YWFkaW4tZ3JpZD4pIGlzIHJlYWR5IChhbmQgdGhlIGxpc3RlbmVycyBhcmUgYWN0aXZlKS4KICAgICAgICBpZiAod2luZG93LlNoYWR5RE9NKSB7CiAgICAgICAgICBtaWNyb1Rhc2sucnVuKCgpID0+IHsKICAgICAgICAgICAgY29uc3Qgc29ydGVycyA9IHRoaXMucXVlcnlTZWxlY3RvckFsbCgndmFhZGluLWdyaWQtc29ydGVyJyk7CiAgICAgICAgICAgIEFycmF5LmZyb20oc29ydGVycykuZm9yRWFjaCgoc29ydGVyKSA9PiB7CiAgICAgICAgICAgICAgLy8gRG9uJ3QgdHJ5IHRvIGZpcmUgaWYgdGhlIHNvcnRlciBoYXNuJ3QgYmVlbiB1cGdyYWRlZCB5ZXQKICAgICAgICAgICAgICBpZiAoc29ydGVyIGluc3RhbmNlb2YgUG9seW1lckVsZW1lbnQpIHsKICAgICAgICAgICAgICAgIHNvcnRlci5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnc29ydGVyLWNoYW5nZWQnLCB7YnViYmxlczogdHJ1ZSwgY29tcG9zZWQ6IHRydWV9KSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX29uU29ydGVyQ2hhbmdlZChlKSB7CiAgICAgICAgY29uc3Qgc29ydGVyID0gZS50YXJnZXQ7CgogICAgICAgIHRoaXMuX3JlbW92ZUFycmF5SXRlbSh0aGlzLl9zb3J0ZXJzLCBzb3J0ZXIpOwogICAgICAgIHNvcnRlci5fb3JkZXIgPSBudWxsOwoKICAgICAgICBpZiAodGhpcy5tdWx0aVNvcnQpIHsKICAgICAgICAgIGlmIChzb3J0ZXIuZGlyZWN0aW9uKSB7CiAgICAgICAgICAgIHRoaXMuX3NvcnRlcnMudW5zaGlmdChzb3J0ZXIpOwogICAgICAgICAgfQoKICAgICAgICAgIHRoaXMuX3NvcnRlcnMuZm9yRWFjaCgoc29ydGVyLCBpbmRleCkgPT4gc29ydGVyLl9vcmRlciA9IHRoaXMuX3NvcnRlcnMubGVuZ3RoID4gMSA/IGluZGV4IDogbnVsbCwgdGhpcyk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmIChzb3J0ZXIuZGlyZWN0aW9uKSB7CiAgICAgICAgICAgIHRoaXMuX3NvcnRlcnMuZm9yRWFjaChzb3J0ZXIgPT4gewogICAgICAgICAgICAgIHNvcnRlci5fb3JkZXIgPSBudWxsOwogICAgICAgICAgICAgIHNvcnRlci5kaXJlY3Rpb24gPSBudWxsOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgdGhpcy5fc29ydGVycyA9IFtzb3J0ZXJdOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTsKCiAgICAgICAgaWYgKHRoaXMuZGF0YVByb3ZpZGVyICYmCiAgICAgICAgICAvLyBObyBuZWVkIHRvIGNsZWFyIGNhY2hlIGlmIHNvcnRlcnMgZGlkbid0IGNoYW5nZQogICAgICAgICAgSlNPTi5zdHJpbmdpZnkodGhpcy5fcHJldmlvdXNTb3J0ZXJzKSAhPT0gSlNPTi5zdHJpbmdpZnkodGhpcy5fbWFwU29ydGVycygpKSkgewogICAgICAgICAgdGhpcy5jbGVhckNhY2hlKCk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9hMTF5VXBkYXRlU29ydGVycygpOwoKICAgICAgICB0aGlzLl9wcmV2aW91c1NvcnRlcnMgPSB0aGlzLl9tYXBTb3J0ZXJzKCk7CiAgICAgIH0KCiAgICAgIF9tYXBTb3J0ZXJzKCkgewogICAgICAgIHJldHVybiB0aGlzLl9zb3J0ZXJzLm1hcChzb3J0ZXIgPT4gewogICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgcGF0aDogc29ydGVyLnBhdGgsCiAgICAgICAgICAgIGRpcmVjdGlvbjogc29ydGVyLmRpcmVjdGlvbgogICAgICAgICAgfTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgX3JlbW92ZUFycmF5SXRlbShhcnJheSwgaXRlbSkgewogICAgICAgIGNvbnN0IGluZGV4ID0gYXJyYXkuaW5kZXhPZihpdGVtKTsKICAgICAgICBpZiAoaW5kZXggPiAtMSkgewogICAgICAgICAgYXJyYXkuc3BsaWNlKGluZGV4LCAxKTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE4IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IFN0eWxpbmdNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgU3R5bGluZ01peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogQSBmdW5jdGlvbiB0aGF0IGFsbG93cyBnZW5lcmF0aW5nIENTUyBjbGFzcyBuYW1lcyBmb3IgZ3JpZCBjZWxscwogICAgICAgICAgICogYmFzZWQgb24gdGhlaXIgcm93IGFuZCBjb2x1bW4uIFRoZSByZXR1cm4gdmFsdWUgc2hvdWxkIGJlIHRoZSBnZW5lcmF0ZWQKICAgICAgICAgICAqIGNsYXNzIG5hbWUgYXMgYSBzdHJpbmcsIG9yIG11bHRpcGxlIGNsYXNzIG5hbWVzIHNlcGFyYXRlZCBieSB3aGl0ZXNwYWNlCiAgICAgICAgICAgKiBjaGFyYWN0ZXJzLgogICAgICAgICAgICoKICAgICAgICAgICAqIFJlY2VpdmVzIHR3byBhcmd1bWVudHM6CiAgICAgICAgICAgKiAtIGBjb2x1bW5gIFRoZSBgPHZhYWRpbi1ncmlkLWNvbHVtbj5gIGVsZW1lbnQgKGB1bmRlZmluZWRgIGZvciBkZXRhaWxzLWNlbGwpLgogICAgICAgICAgICogLSBgcm93RGF0YWAgVGhlIG9iamVjdCB3aXRoIHRoZSBwcm9wZXJ0aWVzIHJlbGF0ZWQgd2l0aAogICAgICAgICAgICogICB0aGUgcmVuZGVyZWQgaXRlbSwgY29udGFpbnM6CiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuaW5kZXhgIFRoZSBpbmRleCBvZiB0aGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5pdGVtYCBUaGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5leHBhbmRlZGAgU3VibGV2ZWwgdG9nZ2xlIHN0YXRlLgogICAgICAgICAgICogICAtIGByb3dEYXRhLmxldmVsYCBMZXZlbCBvZiB0aGUgdHJlZSByZXByZXNlbnRlZCB3aXRoIGEgaG9yaXpvbnRhbCBvZmZzZXQgb2YgdGhlIHRvZ2dsZSBidXR0b24uCiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuc2VsZWN0ZWRgIFNlbGVjdGVkIHN0YXRlLgogICAgICAgICAgICovCiAgICAgICAgICBjZWxsQ2xhc3NOYW1lR2VuZXJhdG9yOiBGdW5jdGlvbgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX19jZWxsQ2xhc3NOYW1lR2VuZXJhdG9yQ2hhbmdlZChjZWxsQ2xhc3NOYW1lR2VuZXJhdG9yKScKICAgICAgICBdOwogICAgICB9CgogICAgICBfX2NlbGxDbGFzc05hbWVHZW5lcmF0b3JDaGFuZ2VkKGNlbGxDbGFzc0dlbmVyYXRvcikgewogICAgICAgIHRoaXMuZ2VuZXJhdGVDZWxsQ2xhc3NOYW1lcygpOwogICAgICB9CgogICAgICAvKioKICAgICAgICogUnVucyB0aGUgYGNlbGxDbGFzc05hbWVHZW5lcmF0b3JgIGZvciB0aGUgdmlzaWJsZSBjZWxscy4KICAgICAgICogSWYgdGhlIGdlbmVyYXRvciBkZXBlbmRzIG9uIHZhcnlpbmcgY29uZGl0aW9ucywgeW91IG5lZWQgdG8KICAgICAgICogY2FsbCB0aGlzIGZ1bmN0aW9uIG1hbnVhbGx5IGluIG9yZGVyIHRvIHVwZGF0ZSB0aGUgc3R5bGVzIHdoZW4KICAgICAgICogdGhlIGNvbmRpdGlvbnMgY2hhbmdlLgogICAgICAgKi8KICAgICAgZ2VuZXJhdGVDZWxsQ2xhc3NOYW1lcygpIHsKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5jaGlsZHJlbikuZmlsdGVyKHJvdyA9PiAhcm93LmhpZGRlbikuZm9yRWFjaCgKICAgICAgICAgIHJvdyA9PiB0aGlzLl9nZW5lcmF0ZUNlbGxDbGFzc05hbWVzKHJvdywgdGhpcy5fX2dldFJvd01vZGVsKHJvdykpKTsKICAgICAgfQoKICAgICAgX2dlbmVyYXRlQ2VsbENsYXNzTmFtZXMocm93LCByb3dEYXRhKSB7CiAgICAgICAgQXJyYXkuZnJvbShyb3cuY2hpbGRyZW4pLmZvckVhY2goY2VsbCA9PiB7CiAgICAgICAgICBpZiAoY2VsbC5fX2dlbmVyYXRlZENsYXNzZXMpIHsKICAgICAgICAgICAgY2VsbC5fX2dlbmVyYXRlZENsYXNzZXMuZm9yRWFjaChjbGFzc05hbWUgPT4gY2VsbC5jbGFzc0xpc3QucmVtb3ZlKGNsYXNzTmFtZSkpOwogICAgICAgICAgfQogICAgICAgICAgaWYgKHRoaXMuY2VsbENsYXNzTmFtZUdlbmVyYXRvcikgewogICAgICAgICAgICBjb25zdCByZXN1bHQgPSB0aGlzLmNlbGxDbGFzc05hbWVHZW5lcmF0b3IoY2VsbC5fY29sdW1uLCByb3dEYXRhKTsKICAgICAgICAgICAgY2VsbC5fX2dlbmVyYXRlZENsYXNzZXMgPSByZXN1bHQgJiYgcmVzdWx0LnNwbGl0KCcgJykuZmlsdGVyKGNsYXNzTmFtZSA9PiBjbGFzc05hbWUubGVuZ3RoID4gMCk7CiAgICAgICAgICAgIGlmIChjZWxsLl9fZ2VuZXJhdGVkQ2xhc3NlcykgewogICAgICAgICAgICAgIGNlbGwuX19nZW5lcmF0ZWRDbGFzc2VzLmZvckVhY2goY2xhc3NOYW1lID0+IGNlbGwuY2xhc3NMaXN0LmFkZChjbGFzc05hbWUpKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxOSBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KICAgIGNvbnN0IERyb3BNb2RlID0gewogICAgICBCRVRXRUVOOiAnYmV0d2VlbicsCiAgICAgIE9OX1RPUDogJ29uLXRvcCcsCiAgICAgIE9OX1RPUF9PUl9CRVRXRUVOOiAnb24tdG9wLW9yLWJldHdlZW4nLAogICAgICBPTl9HUklEOiAnb24tZ3JpZCcKICAgIH07CgogICAgY29uc3QgRHJvcExvY2F0aW9uID0gewogICAgICBPTl9UT1A6ICdvbi10b3AnLAogICAgICBBQk9WRTogJ2Fib3ZlJywKICAgICAgQkVMT1c6ICdiZWxvdycsCiAgICAgIEVNUFRZOiAnZW1wdHknCiAgICB9OwoKICAgIC8qKgogICAgICogQHBvbHltZXJNaXhpbgogICAgICovCiAgICBjb25zdCBEcmFnQW5kRHJvcE1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBEcmFnQW5kRHJvcE1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogRGVmaW5lcyB0aGUgbG9jYXRpb25zIHdpdGhpbiB0aGUgR3JpZCByb3cgd2hlcmUgYW4gZWxlbWVudCBjYW4gYmUgZHJvcHBlZC4KICAgICAgICAgICAqCiAgICAgICAgICAgKiBQb3NzaWJsZSB2YWx1ZXMgYXJlOgogICAgICAgICAgICogLSBgYmV0d2VlbmA6IFRoZSBkcm9wIGV2ZW50IGNhbiBoYXBwZW4gYmV0d2VlbiBHcmlkIHJvd3MuCiAgICAgICAgICAgKiAtIGBvbi10b3BgOiBUaGUgZHJvcCBldmVudCBjYW4gaGFwcGVuIG9uIHRvcCBvZiBHcmlkIHJvd3MuCiAgICAgICAgICAgKiAtIGBvbi10b3Atb3ItYmV0d2VlbmA6IFRoZSBkcm9wIGV2ZW50IGNhbiBoYXBwZW4gZWl0aGVyIG9uIHRvcCBvZiBvciBiZXR3ZWVuIEdyaWQgcm93cy4KICAgICAgICAgICAqIC0gYG9uLWdyaWRgOiBUaGUgZHJvcCBldmVudCB3aWxsIG5vdCBoYXBwZW4gb24gYW55IHNwZWNpZmljIHJvdywgaXQgd2lsbCBzaG93IHRoZSBkcm9wIHRhcmdldCBvdXRsaW5lIGFyb3VuZCB0aGUgd2hvbGUgZ3JpZC4KICAgICAgICAgICAqLwogICAgICAgICAgZHJvcE1vZGU6IFN0cmluZywKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIE1hcmtzIHRoZSBncmlkJ3Mgcm93cyB0byBiZSBhdmFpbGFibGUgZm9yIGRyYWdnaW5nLgogICAgICAgICAgICovCiAgICAgICAgICByb3dzRHJhZ2dhYmxlOiBCb29sZWFuLAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQSBmdW5jdGlvbiB0aGF0IGZpbHRlcnMgZHJhZ2dpbmcgb2Ygc3BlY2lmaWMgZ3JpZCByb3dzLiBUaGUgcmV0dXJuIHZhbHVlIHNob3VsZCBiZSBmYWxzZQogICAgICAgICAgICogaWYgZHJhZ2dpbmcgb2YgdGhlIHJvdyBzaG91bGQgYmUgZGlzYWJsZWQuCiAgICAgICAgICAgKgogICAgICAgICAgICogUmVjZWl2ZXMgb25lIGFyZ3VtZW50OgogICAgICAgICAgICogLSBgcm93RGF0YWAgVGhlIG9iamVjdCB3aXRoIHRoZSBwcm9wZXJ0aWVzIHJlbGF0ZWQgd2l0aAogICAgICAgICAgICogICB0aGUgcmVuZGVyZWQgaXRlbSwgY29udGFpbnM6CiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuaW5kZXhgIFRoZSBpbmRleCBvZiB0aGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5pdGVtYCBUaGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5leHBhbmRlZGAgU3VibGV2ZWwgdG9nZ2xlIHN0YXRlLgogICAgICAgICAgICogICAtIGByb3dEYXRhLmxldmVsYCBMZXZlbCBvZiB0aGUgdHJlZSByZXByZXNlbnRlZCB3aXRoIGEgaG9yaXpvbnRhbCBvZmZzZXQgb2YgdGhlIHRvZ2dsZSBidXR0b24uCiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuc2VsZWN0ZWRgIFNlbGVjdGVkIHN0YXRlLgogICAgICAgICAgICovCiAgICAgICAgICBkcmFnRmlsdGVyOiBGdW5jdGlvbiwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEEgZnVuY3Rpb24gdGhhdCBmaWx0ZXJzIGRyb3BwaW5nIG9uIHNwZWNpZmljIGdyaWQgcm93cy4gVGhlIHJldHVybiB2YWx1ZSBzaG91bGQgYmUgZmFsc2UKICAgICAgICAgICAqIGlmIGRyb3BwaW5nIG9uIHRoZSByb3cgc2hvdWxkIGJlIGRpc2FibGVkLgogICAgICAgICAgICoKICAgICAgICAgICAqIFJlY2VpdmVzIG9uZSBhcmd1bWVudDoKICAgICAgICAgICAqIC0gYHJvd0RhdGFgIFRoZSBvYmplY3Qgd2l0aCB0aGUgcHJvcGVydGllcyByZWxhdGVkIHdpdGgKICAgICAgICAgICAqICAgdGhlIHJlbmRlcmVkIGl0ZW0sIGNvbnRhaW5zOgogICAgICAgICAgICogICAtIGByb3dEYXRhLmluZGV4YCBUaGUgaW5kZXggb2YgdGhlIGl0ZW0uCiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuaXRlbWAgVGhlIGl0ZW0uCiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuZXhwYW5kZWRgIFN1YmxldmVsIHRvZ2dsZSBzdGF0ZS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5sZXZlbGAgTGV2ZWwgb2YgdGhlIHRyZWUgcmVwcmVzZW50ZWQgd2l0aCBhIGhvcml6b250YWwgb2Zmc2V0IG9mIHRoZSB0b2dnbGUgYnV0dG9uLgogICAgICAgICAgICogICAtIGByb3dEYXRhLnNlbGVjdGVkYCBTZWxlY3RlZCBzdGF0ZS4KICAgICAgICAgICAqLwogICAgICAgICAgZHJvcEZpbHRlcjogRnVuY3Rpb24sCgogICAgICAgICAgX19kbmRBdXRvU2Nyb2xsVGhyZXNob2xkOiB7CiAgICAgICAgICAgIHZhbHVlOiA1MAogICAgICAgICAgfQoKICAgICAgICB9OwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IG9ic2VydmVycygpIHsKICAgICAgICByZXR1cm4gWwogICAgICAgICAgJ19kcmFnRHJvcEFjY2Vzc0NoYW5nZWQocm93c0RyYWdnYWJsZSwgZHJvcE1vZGUsIGRyYWdGaWx0ZXIsIGRyb3BGaWx0ZXIpJwogICAgICAgIF07CiAgICAgIH0KCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgdGhpcy4kLnRhYmxlLmFkZEV2ZW50TGlzdGVuZXIoJ2RyYWdzdGFydCcsIHRoaXMuX29uRHJhZ1N0YXJ0LmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuJC50YWJsZS5hZGRFdmVudExpc3RlbmVyKCdkcmFnZW5kJywgdGhpcy5fb25EcmFnRW5kLmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuJC50YWJsZS5hZGRFdmVudExpc3RlbmVyKCdkcmFnb3ZlcicsIHRoaXMuX29uRHJhZ092ZXIuYmluZCh0aGlzKSk7CiAgICAgICAgdGhpcy4kLnRhYmxlLmFkZEV2ZW50TGlzdGVuZXIoJ2RyYWdsZWF2ZScsIHRoaXMuX29uRHJhZ0xlYXZlLmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuJC50YWJsZS5hZGRFdmVudExpc3RlbmVyKCdkcm9wJywgdGhpcy5fb25Ecm9wLmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuJC50YWJsZS5hZGRFdmVudExpc3RlbmVyKCdkcmFnZW50ZXInLCBlID0+IHsKICAgICAgICAgIGlmICh0aGlzLmRyb3BNb2RlKSB7CiAgICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgIH0KCiAgICAgIF9vbkRyYWdTdGFydChlKSB7CiAgICAgICAgaWYgKHRoaXMucm93c0RyYWdnYWJsZSkgewogICAgICAgICAgbGV0IHJvdyA9IGUudGFyZ2V0OwogICAgICAgICAgaWYgKHJvdy5sb2NhbE5hbWUgPT09ICd2YWFkaW4tZ3JpZC1jZWxsLWNvbnRlbnQnKSB7CiAgICAgICAgICAgIC8vIFRoZSBkcmFnZ2FibGUgbm9kZSBpcyB0aGUgY2VsbCBjb250ZW50IGVsZW1lbnQgb24gYnJvd3NlcnMgdGhhdCBzdXBwb3J0IG5hdGl2ZSBzaGFkb3cKICAgICAgICAgICAgcm93ID0gcm93LmFzc2lnbmVkU2xvdC5wYXJlbnROb2RlLnBhcmVudE5vZGU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAocm93LnBhcmVudE5vZGUgIT09IHRoaXMuJC5pdGVtcykgewogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CgogICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnZHJhZ2dpbmctcm93cycsIHRydWUsIHRoaXMpOwoKICAgICAgICAgIGlmICh0aGlzLl9zYWZhcmkpIHsKICAgICAgICAgICAgLy8gU2FmYXJpIGRvZXNuJ3QgZ2V0IHByb3BlciBkcmFnIGltYWdlcyBmcm9tIHRyYW5zZm9ybWVkCiAgICAgICAgICAgIC8vIGVsZW1lbnRzIHNvIHdlIG5lZWQgdG8gc3dpdGNoIHRvIHRvcCB0ZW1wb3JhcmlseQogICAgICAgICAgICBjb25zdCB0cmFuc2Zvcm0gPSByb3cuc3R5bGUudHJhbnNmb3JtOwogICAgICAgICAgICByb3cuc3R5bGUudG9wID0gL3RyYW5zbGF0ZVlcKCguKilcKS8uZXhlYyh0cmFuc2Zvcm0pWzFdOwogICAgICAgICAgICByb3cuc3R5bGUudHJhbnNmb3JtID0gJ25vbmUnOwogICAgICAgICAgICByZXF1ZXN0QW5pbWF0aW9uRnJhbWUoKCkgPT4gewogICAgICAgICAgICAgIHJvdy5zdHlsZS50b3AgPSAnJzsKICAgICAgICAgICAgICByb3cuc3R5bGUudHJhbnNmb3JtID0gdHJhbnNmb3JtOwogICAgICAgICAgICB9KTsKICAgICAgICAgIH0KCiAgICAgICAgICBjb25zdCByb3dSZWN0ID0gcm93LmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgICAgaWYgKCF3aW5kb3cuU2hhZHlET00pIHsKICAgICAgICAgICAgaWYgKHRoaXMuX2lvcykgewogICAgICAgICAgICAgIGUuZGF0YVRyYW5zZmVyLnNldERyYWdJbWFnZShyb3cpOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIGUuZGF0YVRyYW5zZmVyLnNldERyYWdJbWFnZShyb3csIGUuY2xpZW50WCAtIHJvd1JlY3QubGVmdCwgZS5jbGllbnRZIC0gcm93UmVjdC50b3ApOwogICAgICAgICAgICB9CgogICAgICAgICAgfQoKICAgICAgICAgIGxldCByb3dzID0gW3Jvd107CiAgICAgICAgICBpZiAodGhpcy5faXNTZWxlY3RlZChyb3cuX2l0ZW0pKSB7CiAgICAgICAgICAgIHJvd3MgPSB0aGlzLl9fZ2V0Vmlld3BvcnRSb3dzKCkKICAgICAgICAgICAgICAuZmlsdGVyKHJvdyA9PiB0aGlzLl9pc1NlbGVjdGVkKHJvdy5faXRlbSkpCiAgICAgICAgICAgICAgLmZpbHRlcihyb3cgPT4gIXRoaXMuZHJhZ0ZpbHRlciB8fCB0aGlzLmRyYWdGaWx0ZXIodGhpcy5fX2dldFJvd01vZGVsKHJvdykpKTsKICAgICAgICAgIH0KCiAgICAgICAgICAvLyBTZXQgdGhlIGRlZmF1bHQgdHJhbnNmZXIgZGF0YQogICAgICAgICAgZS5kYXRhVHJhbnNmZXIuc2V0RGF0YSgndGV4dCcsIHRoaXMuX19mb3JtYXREZWZhdWx0VHJhbnNmZXJEYXRhKHJvd3MpKTsKCiAgICAgICAgICByb3cuc2V0QXR0cmlidXRlKCdkcmFnc3RhcnQnLCByb3dzLmxlbmd0aCA+IDEgPyByb3dzLmxlbmd0aCA6ICcnKTsKICAgICAgICAgIHRoaXMudXBkYXRlU3R5bGVzKHsKICAgICAgICAgICAgJy0tX2dyaWQtZHJhZy1zdGFydC14JzogYCR7ZS5jbGllbnRYIC0gcm93UmVjdC5sZWZ0ICsgMjB9cHhgLAogICAgICAgICAgICAnLS1fZ3JpZC1kcmFnLXN0YXJ0LXknOiBgJHtlLmNsaWVudFkgLSByb3dSZWN0LnRvcCArIDEwfXB4YAogICAgICAgICAgfSk7CgogICAgICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKCgpID0+IHsKICAgICAgICAgICAgcm93LnJlbW92ZUF0dHJpYnV0ZSgnZHJhZ3N0YXJ0Jyk7CiAgICAgICAgICAgIHRoaXMudXBkYXRlU3R5bGVzKHsnLS1fZ3JpZC1kcmFnLXN0YXJ0LXgnOiAnJywgJy0tX2dyaWQtZHJhZy1zdGFydC15JzogJyd9KTsKICAgICAgICAgIH0pOwoKICAgICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdncmlkLWRyYWdzdGFydCcsIHsKICAgICAgICAgICAgZGV0YWlsOiB7CiAgICAgICAgICAgICAgZHJhZ2dlZEl0ZW1zOiByb3dzLm1hcChyb3cgPT4gcm93Ll9pdGVtKSwKICAgICAgICAgICAgICBzZXREcmFnRGF0YTogKHR5cGUsIGRhdGEpID0+IGUuZGF0YVRyYW5zZmVyLnNldERhdGEodHlwZSwgZGF0YSksCiAgICAgICAgICAgICAgc2V0RHJhZ2dlZEl0ZW1zQ291bnQ6IGNvdW50ID0+IHJvdy5zZXRBdHRyaWJ1dGUoJ2RyYWdzdGFydCcsIGNvdW50KQogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICAgIGV2ZW50Lm9yaWdpbmFsRXZlbnQgPSBlOwogICAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9vbkRyYWdFbmQoZSkgewogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnZHJhZ2dpbmctcm93cycsIGZhbHNlLCB0aGlzKTsKICAgICAgICBlLnN0b3BQcm9wYWdhdGlvbigpOwogICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdncmlkLWRyYWdlbmQnKTsKICAgICAgICBldmVudC5vcmlnaW5hbEV2ZW50ID0gZTsKICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpOwogICAgICB9CgogICAgICBfb25EcmFnTGVhdmUoZSkgewogICAgICAgIGUuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgICAgdGhpcy5fY2xlYXJEcmFnU3R5bGVzKCk7CiAgICAgIH0KCiAgICAgIF9vbkRyYWdPdmVyKGUpIHsKCiAgICAgICAgaWYgKHRoaXMuZHJvcE1vZGUpIHsKICAgICAgICAgIHRoaXMuX2Ryb3BMb2NhdGlvbiA9IHVuZGVmaW5lZDsKICAgICAgICAgIHRoaXMuX2RyYWdPdmVySXRlbSA9IHVuZGVmaW5lZDsKCiAgICAgICAgICBpZiAodGhpcy5fX2RuZEF1dG9TY3JvbGwoZS5jbGllbnRZKSkgewogICAgICAgICAgICB0aGlzLl9jbGVhckRyYWdTdHlsZXMoKTsKICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgfQoKICAgICAgICAgIGxldCByb3cgPSBlLmNvbXBvc2VkUGF0aCgpLmZpbHRlcihub2RlID0+IG5vZGUubG9jYWxOYW1lID09PSAndHInKVswXTsKCiAgICAgICAgICBpZiAoIXRoaXMuX2VmZmVjdGl2ZVNpemUgfHwgdGhpcy5kcm9wTW9kZSA9PT0gRHJvcE1vZGUuT05fR1JJRCkgewogICAgICAgICAgICAvLyBUaGUgZ3JpZCBpcyBlbXB0eSBvciAib24tZ3JpZCIgZHJvcCBtb2RlIHdhcyB1c2VkLCBhbHdheXMgZGVmYXVsdCB0byAiZW1wdHkiCiAgICAgICAgICAgIHRoaXMuX2Ryb3BMb2NhdGlvbiA9IERyb3BMb2NhdGlvbi5FTVBUWTsKICAgICAgICAgIH0gZWxzZSBpZiAoIXJvdyB8fCByb3cucGFyZW50Tm9kZSAhPT0gdGhpcy4kLml0ZW1zKSB7CiAgICAgICAgICAgIC8vIFRoZSBkcmFnb3ZlciBkaWRuJ3Qgb2NjdXIgb24gYSBib2R5IHJvdyBidXQgdGhlIGdyaWQgaGFzIGl0ZW1zCiAgICAgICAgICAgIGlmIChyb3cpIHsKICAgICAgICAgICAgICAvLyBUaGUgZHJhZ292ZXIgb2NjdXJyZWQgb3ZlciBhIGhlYWRlci9mb290ZXIgcm93CiAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuZHJvcE1vZGUgPT09IERyb3BNb2RlLkJFVFdFRU4gfHwgdGhpcy5kcm9wTW9kZSA9PT0gRHJvcE1vZGUuT05fVE9QX09SX0JFVFdFRU4pIHsKICAgICAgICAgICAgICAvLyBUaGUgZHJvcCBtb2RlIGFsbG93cyBzZXR0aW5nIHRoZSBsYXN0IHJvdyBhcyB0aGUgZHJhZyBvdmVyIGl0ZW0KICAgICAgICAgICAgICByb3cgPSBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5jaGlsZHJlbikuZmlsdGVyKHJvdyA9PiAhcm93LmhpZGRlbikucG9wKCk7CiAgICAgICAgICAgICAgdGhpcy5fZHJvcExvY2F0aW9uID0gRHJvcExvY2F0aW9uLkJFTE9XOwogICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgIC8vIERyb3AgbW9kZSBvbi10b3AgdXNlZCBidXQgdGhlIGRyYWdvdmVyIGRpZG4ndCBvY2N1ciBvdmVyIG9uZSBvZiB0aGUgZXhpc3Rpbmcgcm93cwogICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gVGhlIGRyYWdvdmVyIG9jY3VycmVkIG9uIGEgYm9keSByb3csIGRldGVybWluZSB0aGUgZHJvcCBsb2NhdGlvbiBmcm9tIGNvb3JkaW5hdGVzCiAgICAgICAgICAgIGNvbnN0IHJvd1JlY3QgPSByb3cuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CgogICAgICAgICAgICB0aGlzLl9kcm9wTG9jYXRpb24gPSBEcm9wTG9jYXRpb24uT05fVE9QOwoKICAgICAgICAgICAgaWYgKHRoaXMuZHJvcE1vZGUgPT09IERyb3BNb2RlLkJFVFdFRU4pIHsKICAgICAgICAgICAgICBjb25zdCBkcm9wQWJvdmUgPSBlLmNsaWVudFkgLSByb3dSZWN0LnRvcCA8IHJvd1JlY3QuYm90dG9tIC0gZS5jbGllbnRZOwogICAgICAgICAgICAgIHRoaXMuX2Ryb3BMb2NhdGlvbiA9IGRyb3BBYm92ZSA/IERyb3BMb2NhdGlvbi5BQk9WRSA6IERyb3BMb2NhdGlvbi5CRUxPVzsKCiAgICAgICAgICAgIH0gZWxzZSBpZiAodGhpcy5kcm9wTW9kZSA9PT0gRHJvcE1vZGUuT05fVE9QX09SX0JFVFdFRU4pIHsKICAgICAgICAgICAgICBpZiAoZS5jbGllbnRZIC0gcm93UmVjdC50b3AgPCByb3dSZWN0LmhlaWdodCAvIDMpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2Ryb3BMb2NhdGlvbiA9IERyb3BMb2NhdGlvbi5BQk9WRTsKICAgICAgICAgICAgICB9IGVsc2UgaWYgKGUuY2xpZW50WSAtIHJvd1JlY3QudG9wID4gKHJvd1JlY3QuaGVpZ2h0IC8gMykgKiAyKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9kcm9wTG9jYXRpb24gPSBEcm9wTG9jYXRpb24uQkVMT1c7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKHJvdyAmJiByb3cuaGFzQXR0cmlidXRlKCdkcm9wLWRpc2FibGVkJykpIHsKICAgICAgICAgICAgdGhpcy5fZHJvcExvY2F0aW9uID0gdW5kZWZpbmVkOwogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CgogICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKCiAgICAgICAgICBpZiAodGhpcy5fZHJvcExvY2F0aW9uID09PSBEcm9wTG9jYXRpb24uRU1QVFkpIHsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdkcmFnb3ZlcicsIHRydWUsIHRoaXMpOwogICAgICAgICAgfSBlbHNlIGlmIChyb3cpIHsKICAgICAgICAgICAgdGhpcy5fZHJhZ092ZXJJdGVtID0gcm93Ll9pdGVtOwogICAgICAgICAgICBpZiAocm93LmdldEF0dHJpYnV0ZSgnZHJhZ292ZXInKSAhPT0gdGhpcy5fZHJvcExvY2F0aW9uKSB7CiAgICAgICAgICAgICAgcm93LnNldEF0dHJpYnV0ZSgnZHJhZ292ZXInLCB0aGlzLl9kcm9wTG9jYXRpb24pOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLl9jbGVhckRyYWdTdHlsZXMoKTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9fZG5kQXV0b1Njcm9sbChjbGllbnRZKSB7CiAgICAgICAgaWYgKHRoaXMuX19kbmRBdXRvU2Nyb2xsaW5nKSB7CiAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CgogICAgICAgIGNvbnN0IGhlYWRlckJvdHRvbSA9IHRoaXMuJC5oZWFkZXIuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkuYm90dG9tOwogICAgICAgIGNvbnN0IGZvb3RlclRvcCA9IHRoaXMuJC5mb290ZXIuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkudG9wOwogICAgICAgIGNvbnN0IHRvcERpZmYgPSBoZWFkZXJCb3R0b20gLSBjbGllbnRZICsgdGhpcy5fX2RuZEF1dG9TY3JvbGxUaHJlc2hvbGQ7CiAgICAgICAgY29uc3QgYm90dG9tRGlmZiA9IGNsaWVudFkgLSBmb290ZXJUb3AgKyB0aGlzLl9fZG5kQXV0b1Njcm9sbFRocmVzaG9sZDsKICAgICAgICBsZXQgc2Nyb2xsVG9wRGVsdGEgPSAwOwoKICAgICAgICBpZiAoYm90dG9tRGlmZiA+IDApIHsKICAgICAgICAgIHNjcm9sbFRvcERlbHRhID0gYm90dG9tRGlmZiAqIDI7CiAgICAgICAgfSBlbHNlIGlmICh0b3BEaWZmID4gMCkgewogICAgICAgICAgc2Nyb2xsVG9wRGVsdGEgPSAtdG9wRGlmZiAqIDI7CiAgICAgICAgfQoKICAgICAgICBpZiAoc2Nyb2xsVG9wRGVsdGEpIHsKICAgICAgICAgIGNvbnN0IHNjcm9sbFRvcCA9IHRoaXMuJC50YWJsZS5zY3JvbGxUb3A7CiAgICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsVG9wICs9IHNjcm9sbFRvcERlbHRhOwogICAgICAgICAgY29uc3Qgc2Nyb2xsVG9wQ2hhbmdlZCA9IHNjcm9sbFRvcCAhPT0gdGhpcy4kLnRhYmxlLnNjcm9sbFRvcDsKICAgICAgICAgIGlmIChzY3JvbGxUb3BDaGFuZ2VkKSB7CiAgICAgICAgICAgIHRoaXMuX19kbmRBdXRvU2Nyb2xsaW5nID0gdHJ1ZTsKICAgICAgICAgICAgLy8gRGlzYWxsb3cgbW9yZSBhdXRvLXNjcm9sbHMgd2l0aGluIDIwbXMKICAgICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB0aGlzLl9fZG5kQXV0b1Njcm9sbGluZyA9IGZhbHNlLCAyMCk7CiAgICAgICAgICAgIHRoaXMuX3Njcm9sbEhhbmRsZXIoKTsKICAgICAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfX2dldFZpZXdwb3J0Um93cygpIHsKICAgICAgICBjb25zdCBoZWFkZXJCb3R0b20gPSB0aGlzLiQuaGVhZGVyLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLmJvdHRvbTsKICAgICAgICBjb25zdCBmb290ZXJUb3AgPSB0aGlzLiQuZm9vdGVyLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLnRvcDsKICAgICAgICByZXR1cm4gQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pCiAgICAgICAgICAuZmlsdGVyKHJvdyA9PiB7CiAgICAgICAgICAgIGNvbnN0IHJvd1JlY3QgPSByb3cuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgICAgIHJldHVybiByb3dSZWN0LmJvdHRvbSA+IGhlYWRlckJvdHRvbSAmJiByb3dSZWN0LnRvcCA8IGZvb3RlclRvcDsKICAgICAgICAgIH0pOwogICAgICB9CgogICAgICBfY2xlYXJEcmFnU3R5bGVzKCkgewogICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdkcmFnb3ZlcicpOwogICAgICAgIEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5mb3JFYWNoKHJvdyA9PiByb3cucmVtb3ZlQXR0cmlidXRlKCdkcmFnb3ZlcicpKTsKICAgICAgfQoKICAgICAgX29uRHJvcChlKSB7CiAgICAgICAgaWYgKHRoaXMuZHJvcE1vZGUpIHsKICAgICAgICAgIGUuc3RvcFByb3BhZ2F0aW9uKCk7CiAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CgogICAgICAgICAgY29uc3QgZHJhZ0RhdGEgPSBlLmRhdGFUcmFuc2Zlci50eXBlcyAmJiBBcnJheS5mcm9tKGUuZGF0YVRyYW5zZmVyLnR5cGVzKS5tYXAodHlwZSA9PiB7CiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgdHlwZSwKICAgICAgICAgICAgICBkYXRhOiBlLmRhdGFUcmFuc2Zlci5nZXREYXRhKHR5cGUpCiAgICAgICAgICAgIH07CiAgICAgICAgICB9KTsKCiAgICAgICAgICB0aGlzLl9jbGVhckRyYWdTdHlsZXMoKTsKCiAgICAgICAgICBjb25zdCBldmVudCA9IG5ldyBDdXN0b21FdmVudCgnZ3JpZC1kcm9wJywgewogICAgICAgICAgICBidWJibGVzOiBlLmJ1YmJsZXMsCiAgICAgICAgICAgIGNhbmNlbGFibGU6IGUuY2FuY2VsYWJsZSwKICAgICAgICAgICAgZGV0YWlsOiB7CiAgICAgICAgICAgICAgZHJvcFRhcmdldEl0ZW06IHRoaXMuX2RyYWdPdmVySXRlbSwKICAgICAgICAgICAgICBkcm9wTG9jYXRpb246IHRoaXMuX2Ryb3BMb2NhdGlvbiwKICAgICAgICAgICAgICBkcmFnRGF0YQogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICAgIGV2ZW50Lm9yaWdpbmFsRXZlbnQgPSBlOwogICAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9fZm9ybWF0RGVmYXVsdFRyYW5zZmVyRGF0YShyb3dzKSB7CiAgICAgICAgcmV0dXJuIHJvd3MKICAgICAgICAgIC5tYXAocm93ID0+IHsKICAgICAgICAgICAgcmV0dXJuIEFycmF5LmZyb20ocm93LmNoaWxkcmVuKQogICAgICAgICAgICAgIC5maWx0ZXIoY2VsbCA9PiAhY2VsbC5oaWRkZW4gJiYgY2VsbC5nZXRBdHRyaWJ1dGUoJ3BhcnQnKS5pbmRleE9mKCdkZXRhaWxzLWNlbGwnKSA9PT0gLTEpCiAgICAgICAgICAgICAgLnNvcnQoKGEsIGIpID0+IHsKICAgICAgICAgICAgICAgIHJldHVybiBhLl9jb2x1bW4uX29yZGVyID4gYi5fY29sdW1uLl9vcmRlciA/IDEgOiAtMTsKICAgICAgICAgICAgICB9KQogICAgICAgICAgICAgIC5tYXAoY2VsbCA9PiBjZWxsLl9jb250ZW50LnRleHRDb250ZW50LnRyaW0oKSkKICAgICAgICAgICAgICAuZmlsdGVyKGNvbnRlbnQgPT4gY29udGVudCkKICAgICAgICAgICAgICAuam9pbignXHQnKTsKICAgICAgICAgIH0pCiAgICAgICAgICAuam9pbignXG4nKTsKICAgICAgfQoKICAgICAgX2RyYWdEcm9wQWNjZXNzQ2hhbmdlZChyb3dzRHJhZ2dhYmxlLCBkcm9wTW9kZSwgZHJhZ0ZpbHRlciwgZHJvcEZpbHRlcikgewogICAgICAgIHRoaXMuZmlsdGVyRHJhZ0FuZERyb3AoKTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIFJ1bnMgdGhlIGBkcmFnRmlsdGVyYCBhbmQgYGRyb3BGaWx0ZXJgIGhvb2tzIGZvciB0aGUgdmlzaWJsZSBjZWxscy4KICAgICAgICogSWYgdGhlIGZpbHRlciBkZXBlbmRzIG9uIHZhcnlpbmcgY29uZGl0aW9ucywgeW91IG1heSBuZWVkIHRvCiAgICAgICAqIGNhbGwgdGhpcyBmdW5jdGlvbiBtYW51YWxseSBpbiBvcmRlciB0byB1cGRhdGUgdGhlIGRyYWdnYWJpbGl0eSB3aGVuCiAgICAgICAqIHRoZSBjb25kaXRpb25zIGNoYW5nZS4KICAgICAgICovCiAgICAgIGZpbHRlckRyYWdBbmREcm9wKCkgewogICAgICAgIEFycmF5LmZyb20odGhpcy4kLml0ZW1zLmNoaWxkcmVuKS5maWx0ZXIocm93ID0+ICFyb3cuaGlkZGVuKS5mb3JFYWNoKAogICAgICAgICAgcm93ID0+IHsKICAgICAgICAgICAgdGhpcy5fZmlsdGVyRHJhZ0FuZERyb3Aocm93LCB0aGlzLl9fZ2V0Um93TW9kZWwocm93KSk7CiAgICAgICAgICB9CiAgICAgICAgKTsKICAgICAgfQoKICAgICAgX2ZpbHRlckRyYWdBbmREcm9wKHJvdywgcm93RGF0YSkgewogICAgICAgIGNvbnN0IGRyYWdEaXNhYmxlZCA9ICF0aGlzLnJvd3NEcmFnZ2FibGUgfHwgKHRoaXMuZHJhZ0ZpbHRlciAmJiAhdGhpcy5kcmFnRmlsdGVyKHJvd0RhdGEpKTsKICAgICAgICBjb25zdCBkcm9wRGlzYWJsZWQgPSAhdGhpcy5kcm9wTW9kZSB8fCAodGhpcy5kcm9wRmlsdGVyICYmICF0aGlzLmRyb3BGaWx0ZXIocm93RGF0YSkpOwoKICAgICAgICBjb25zdCBkcmFnZ2FibGVFbGVtZW50cyA9IHdpbmRvdy5TaGFkeURPTQogICAgICAgICAgPyBbcm93XQogICAgICAgICAgOiBBcnJheS5mcm9tKHJvdy5jaGlsZHJlbikubWFwKGNlbGwgPT4gY2VsbC5fY29udGVudCk7CgogICAgICAgIGRyYWdnYWJsZUVsZW1lbnRzLmZvckVhY2goZSA9PiB7CiAgICAgICAgICBpZiAoZHJhZ0Rpc2FibGVkKSB7CiAgICAgICAgICAgIGUucmVtb3ZlQXR0cmlidXRlKCdkcmFnZ2FibGUnKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIGUuc2V0QXR0cmlidXRlKCdkcmFnZ2FibGUnLCB0cnVlKTsKICAgICAgICAgIH0KICAgICAgICB9KTsKCiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdkcmFnLWRpc2FibGVkJywgZHJhZ0Rpc2FibGVkLCByb3cpOwogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnZHJvcC1kaXNhYmxlZCcsIGRyb3BEaXNhYmxlZCwgcm93KTsKICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gc3RhcnRpbmcgdG8gZHJhZyBncmlkIHJvd3MuCiAgICAgICAqCiAgICAgICAqIEBldmVudCBncmlkLWRyYWdzdGFydAogICAgICAgKiBAcGFyYW0ge09iamVjdH0gb3JpZ2luYWxFdmVudCBUaGUgbmF0aXZlIGRyYWdzdGFydCBldmVudAogICAgICAgKiBAcGFyYW0ge09iamVjdH0gZGV0YWlsCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBkZXRhaWwuZHJhZ2dlZEl0ZW1zIHRoZSBpdGVtcyBpbiB0aGUgdmlzaWJsZSB2aWV3cG9ydCB0aGF0IGFyZSBkcmFnZ2VkCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGRldGFpbC5zZXREcmFnZ2VkSXRlbXNDb3VudCBPdmVycmlkZXMgdGhlIGRlZmF1bHQgbnVtYmVyIHNob3duIGluIHRoZSBkcmFnIGltYWdlIG9uIG11bHRpIHJvdyBkcmFnLgogICAgICAgKiBQYXJhbWV0ZXIgaXMgb2YgdHlwZSBudW1iZXIuCiAgICAgICAqIEBwYXJhbSB7RnVuY3Rpb259IGRldGFpbC5zZXREcmFnRGF0YSBTZXRzIGRhdGFUcmFuc2ZlciBkYXRhIGZvciB0aGUgZHJhZyBvcGVyYXRpb24uCiAgICAgICAqIE5vdGUgdGhhdCAidGV4dCIgaXMgdGhlIG9ubHkgZGF0YSB0eXBlIHN1cHBvcnRlZCBieSBhbGwgdGhlIGJyb3dzZXJzIHRoZSBncmlkIGN1cnJlbnRseSBzdXBwb3J0cyAoaW5jbHVkaW5nIElFMTEpLgogICAgICAgKiBUaGUgZnVuY3Rpb24gdGFrZXMgdHdvIHBhcmFtZXRlcnM6CiAgICAgICAqIC0gdHlwZTpzdHJpbmcgVGhlIHR5cGUgb2YgdGhlIGRhdGEKICAgICAgICogLSBkYXRhOnN0cmluZyBUaGUgZGF0YQogICAgICAgKi8KCiAgICAgIC8qKgogICAgICAgKiBGaXJlZCB3aGVuIHRoZSBkcmFnZ2luZyBvZiB0aGUgcm93cyBlbmRzLgogICAgICAgKgogICAgICAgKiBAZXZlbnQgZ3JpZC1kcmFnZW5kCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvcmlnaW5hbEV2ZW50IFRoZSBuYXRpdmUgZHJhZ2VuZCBldmVudAogICAgICAgKi8KCiAgICAgIC8qKgogICAgICAgKiBGaXJlZCB3aGVuIGEgZHJvcCBvY2N1cnMgb24gdG9wIG9mIHRoZSBncmlkLgogICAgICAgKgogICAgICAgKiBAZXZlbnQgZ3JpZC1kcm9wCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBvcmlnaW5hbEV2ZW50IFRoZSBuYXRpdmUgZHJvcCBldmVudAogICAgICAgKiBAcGFyYW0ge09iamVjdH0gZGV0YWlsCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBkZXRhaWwuZHJvcFRhcmdldEl0ZW0gVGhlIGl0ZW0gb2YgdGhlIGdyaWQgcm93IG9uIHdoaWNoIHRoZSBkcm9wIG9jY3VycmVkLgogICAgICAgKiBAcGFyYW0ge3N0cmluZ30gZGV0YWlsLmRyb3BMb2NhdGlvbiBUaGUgcG9zaXRpb24gYXQgd2hpY2ggdGhlIGRyb3AgZXZlbnQgdG9vayBwbGFjZSByZWxhdGl2ZSB0byBhIHJvdy4KICAgICAgICogRGVwZW5kaW5nIG9uIHRoZSBkcm9wTW9kZSB2YWx1ZSwgdGhlIGRyb3AgbG9jYXRpb24gY2FuIGJlIG9uZSBvZiB0aGUgZm9sbG93aW5nCiAgICAgICAqIC0gYG9uLXRvcGA6IHdoZW4gdGhlIGRyb3Agb2NjdXJyZWQgb24gdG9wIG9mIHRoZSByb3cKICAgICAgICogLSBgYWJvdmVgOiB3aGVuIHRoZSBkcm9wIG9jY3VycmVkIGFib3ZlIHRoZSByb3cKICAgICAgICogLSBgYmVsb3dgOiB3aGVuIHRoZSBkcm9wIG9jY3VycmVkIGJlbG93IHRoZSByb3cKICAgICAgICogLSBgZW1wdHlgOiB3aGVuIHRoZSBkcm9wIG9jY3VycmVkIG92ZXIgdGhlIGdyaWQsIG5vdCByZWxhdGl2ZSB0byBhbnkgc3BlY2lmaWMgcm93CiAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBkZXRhaWwuZHJhZ0RhdGEgQW4gYXJyYXkgb2YgaXRlbXMgd2l0aCB0aGUgcGF5bG9hZCBhcyBhIHN0cmluZyByZXByZXNlbnRhdGlvbiBhcyB0aGUKICAgICAgICogYGRhdGFgIHByb3BlcnR5IGFuZCB0aGUgdHlwZSBvZiB0aGUgZGF0YSBhcyBgdHlwZWAgcHJvcGVydHkuCiAgICAgICAqLwogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgS2V5Ym9hcmROYXZpZ2F0aW9uTWl4aW4gPSBzdXBlckNsYXNzID0+IGNsYXNzIEtleWJvYXJkTmF2aWdhdGlvbk1peGluIGV4dGVuZHMgc3VwZXJDbGFzcyB7CiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgX2hlYWRlckZvY3VzYWJsZTogewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG9ic2VydmVyOiAnX2ZvY3VzYWJsZUNoYW5nZWQnCiAgICAgICAgICB9LAogICAgICAgICAgX2l0ZW1zRm9jdXNhYmxlOiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZm9jdXNhYmxlQ2hhbmdlZCcKICAgICAgICAgIH0sCiAgICAgICAgICBfZm9vdGVyRm9jdXNhYmxlOiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfZm9jdXNhYmxlQ2hhbmdlZCcKICAgICAgICAgIH0sCiAgICAgICAgICBfbmF2aWdhdGluZ0lzSGlkZGVuOiBCb29sZWFuLAogICAgICAgICAgX2ZvY3VzZWRJdGVtSW5kZXg6IHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgICAgICB2YWx1ZTogMAogICAgICAgICAgfSwKICAgICAgICAgIF9mb2N1c2VkQ29sdW1uT3JkZXI6IE51bWJlcgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CgogICAgICAgIGlmICh0aGlzLl9pb3MgfHwgdGhpcy5fYW5kcm9pZCkgewogICAgICAgICAgLy8gRGlzYWJsZSBrZXlib2FyZCBuYXZpZ2F0aW9uIG9uIG1vYmlsZSBkZXZpY2VzCiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2tleWRvd24nLCB0aGlzLl9vbktleURvd24pOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcigna2V5dXAnLCB0aGlzLl9vbktleVVwKTsKCiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdmb2N1c2luJywgdGhpcy5fb25Gb2N1c0luKTsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3Vzb3V0JywgdGhpcy5fb25Gb2N1c091dCk7CgogICAgICAgIC8vIFdoZW4gZm9jdXMgZ29lcyBmcm9tIGNlbGwgdG8gYW5vdGhlciBjZWxsLCBmb2N1c2luL2ZvY3Vzb3V0IGV2ZW50cyBkbwogICAgICAgIC8vIG5vdCBlc2NhcGUgdGhlIGdyaWTigJlzIHNoYWRvd1Jvb3QsIHRodXMgbGlzdGVuaW5nIGluc2lkZSB0aGUgc2hhZG93Um9vdC4KICAgICAgICB0aGlzLiQudGFibGUuYWRkRXZlbnRMaXN0ZW5lcignZm9jdXNpbicsIHRoaXMuX29uQ2VsbEZvY3VzSW4uYmluZCh0aGlzKSk7CiAgICAgICAgdGhpcy4kLnRhYmxlLmFkZEV2ZW50TGlzdGVuZXIoJ2ZvY3Vzb3V0JywgdGhpcy5fb25DZWxsRm9jdXNPdXQuYmluZCh0aGlzKSk7CgogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbW91c2Vkb3duJywgKCkgPT4gewogICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduYXZpZ2F0aW5nJywgZmFsc2UsIHRoaXMpOwogICAgICAgICAgdGhpcy5faXNNb3VzZWRvd24gPSB0cnVlOwogICAgICAgIH0pOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbW91c2V1cCcsICgpID0+IHRoaXMuX2lzTW91c2Vkb3duID0gZmFsc2UpOwogICAgICB9CgogICAgICBfZm9jdXNhYmxlQ2hhbmdlZChmb2N1c2FibGUsIG9sZEZvY3VzYWJsZSkgewogICAgICAgIGlmIChvbGRGb2N1c2FibGUpIHsKICAgICAgICAgIG9sZEZvY3VzYWJsZS5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgJy0xJyk7CiAgICAgICAgfQogICAgICAgIGlmIChmb2N1c2FibGUpIHsKICAgICAgICAgIGZvY3VzYWJsZS5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgJzAnKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9vbktleURvd24oZSkgewogICAgICAgIC8vIEVuc3VyZSBzdGFuZGFyZCBrZXkgdmFsdWUsIHVuaWZpZWQgYWNyb3NzIGJyb3dzZXJzCiAgICAgICAgbGV0IGtleSA9IGUua2V5OwogICAgICAgIGlmIChrZXkgPT09ICdVcCcgfHwga2V5ID09PSAnRG93bicgfHwga2V5ID09PSAnTGVmdCcgfHwga2V5ID09PSAnUmlnaHQnKSB7CiAgICAgICAgICAvLyBNU0lFICYgRWRnZQogICAgICAgICAga2V5ID0gJ0Fycm93JyArIGtleTsKICAgICAgICB9CiAgICAgICAgaWYgKGtleSA9PT0gJ0VzYycpIHsKICAgICAgICAgIC8vIE1TSUUgJiBFZGdlCiAgICAgICAgICBrZXkgPSAnRXNjYXBlJzsKICAgICAgICB9CiAgICAgICAgaWYgKGtleSA9PT0gJ1NwYWNlYmFyJykgewogICAgICAgICAgLy8gTVNJRQogICAgICAgICAga2V5ID0gJyAnOwogICAgICAgIH0KCiAgICAgICAgbGV0IGtleUdyb3VwOwogICAgICAgIHN3aXRjaCAoa2V5KSB7CiAgICAgICAgICBjYXNlICdBcnJvd1VwJzoKICAgICAgICAgIGNhc2UgJ0Fycm93RG93bic6CiAgICAgICAgICBjYXNlICdBcnJvd0xlZnQnOgogICAgICAgICAgY2FzZSAnQXJyb3dSaWdodCc6CiAgICAgICAgICBjYXNlICdQYWdlVXAnOgogICAgICAgICAgY2FzZSAnUGFnZURvd24nOgogICAgICAgICAgY2FzZSAnSG9tZSc6CiAgICAgICAgICBjYXNlICdFbmQnOgogICAgICAgICAgICBrZXlHcm91cCA9ICdOYXZpZ2F0aW9uJzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdFbnRlcic6CiAgICAgICAgICBjYXNlICdFc2NhcGUnOgogICAgICAgICAgY2FzZSAnRjInOgogICAgICAgICAgICBrZXlHcm91cCA9ICdJbnRlcmFjdGlvbic7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnVGFiJzoKICAgICAgICAgICAga2V5R3JvdXAgPSAnVGFiJzsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICcgJzoKICAgICAgICAgICAga2V5R3JvdXAgPSAnU3BhY2UnOwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2RldGVjdEludGVyYWN0aW5nKGUpOwogICAgICAgIGlmICh0aGlzLmhhc0F0dHJpYnV0ZSgnaW50ZXJhY3RpbmcnKSAmJiBrZXlHcm91cCAhPT0gJ0ludGVyYWN0aW9uJykgewogICAgICAgICAgLy8gV2hlbiBpbiB0aGUgaW50ZXJhY3RpbmcgbW9kZSwgb25seSB0aGUg4oCcSW50ZXJhY3Rpb27igJ0ga2V5cyBhcmUgaGFuZGxlZC4KICAgICAgICAgIGtleUdyb3VwID0gdW5kZWZpbmVkOwogICAgICAgIH0KCiAgICAgICAgaWYgKGtleUdyb3VwKSB7CiAgICAgICAgICB0aGlzW2Bfb24ke2tleUdyb3VwfUtleURvd25gXShlLCBrZXkpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2Vuc3VyZVNjcm9sbGVkVG9JbmRleChpbmRleCkgewogICAgICAgIGNvbnN0IHRhcmdldFJvd0luRG9tID0gQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pLmZpbHRlcihjaGlsZCA9PiBjaGlsZC5pbmRleCA9PT0gaW5kZXgpWzBdOwogICAgICAgIGlmICghdGFyZ2V0Um93SW5Eb20pIHsKICAgICAgICAgIHRoaXMuX3Njcm9sbFRvSW5kZXgoaW5kZXgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX29uTmF2aWdhdGlvbktleURvd24oZSwga2V5KSB7CiAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwoKICAgICAgICBmdW5jdGlvbiBpbmRleE9mQ2hpbGRFbGVtZW50KGVsKSB7CiAgICAgICAgICByZXR1cm4gQXJyYXkucHJvdG90eXBlLmluZGV4T2YuY2FsbChlbC5wYXJlbnROb2RlLmNoaWxkcmVuLCBlbCk7CiAgICAgICAgfQoKICAgICAgICBjb25zdCB2aXNpYmxlSXRlbXNDb3VudCA9IHRoaXMuX2xhc3RWaXNpYmxlSW5kZXggLSB0aGlzLl9maXJzdFZpc2libGVJbmRleCAtIDE7CgogICAgICAgIGxldCBkeCA9IDAsIGR5ID0gMDsKICAgICAgICBzd2l0Y2ggKGtleSkgewogICAgICAgICAgY2FzZSAnQXJyb3dSaWdodCc6CiAgICAgICAgICAgIGR4ID0gdGhpcy5fX2lzUlRMID8gLTEgOiAxOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgJ0Fycm93TGVmdCc6CiAgICAgICAgICAgIGR4ID0gdGhpcy5fX2lzUlRMID8gMSA6IC0xOwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgJ0hvbWUnOgogICAgICAgICAgICBkeCA9IC1JbmZpbml0eTsKICAgICAgICAgICAgZS5jdHJsS2V5ICYmIChkeSA9IC1JbmZpbml0eSk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnRW5kJzoKICAgICAgICAgICAgZHggPSBJbmZpbml0eTsKICAgICAgICAgICAgZS5jdHJsS2V5ICYmIChkeSA9IEluZmluaXR5KTsKICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICBjYXNlICdBcnJvd0Rvd24nOgogICAgICAgICAgICBkeSA9IDE7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnQXJyb3dVcCc6CiAgICAgICAgICAgIGR5ID0gLTE7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnUGFnZURvd24nOgogICAgICAgICAgICBkeSA9IHZpc2libGVJdGVtc0NvdW50OwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIGNhc2UgJ1BhZ2VVcCc6CiAgICAgICAgICAgIGR5ID0gLXZpc2libGVJdGVtc0NvdW50OwogICAgICAgICAgICBicmVhazsKICAgICAgICB9CgogICAgICAgIGNvbnN0IGFjdGl2ZUNlbGwgPSBlLmNvbXBvc2VkUGF0aCgpWzBdOwogICAgICAgIGNvbnN0IGNvbHVtbkluZGV4ID0gaW5kZXhPZkNoaWxkRWxlbWVudChhY3RpdmVDZWxsKTsKICAgICAgICBjb25zdCBpc1Jvd0RldGFpbHMgPSB0aGlzLl9lbGVtZW50TWF0Y2hlcyhhY3RpdmVDZWxsLCAnW3BhcnR+PSJkZXRhaWxzLWNlbGwiXScpOwoKICAgICAgICBjb25zdCBhY3RpdmVSb3cgPSBhY3RpdmVDZWxsLnBhcmVudE5vZGU7CgogICAgICAgIGNvbnN0IGFjdGl2ZVJvd0dyb3VwID0gYWN0aXZlUm93LnBhcmVudE5vZGU7CiAgICAgICAgY29uc3QgbWF4Um93SW5kZXggPSAoYWN0aXZlUm93R3JvdXAgPT09IHRoaXMuJC5pdGVtcyA/IHRoaXMuX2VmZmVjdGl2ZVNpemUgOiBhY3RpdmVSb3dHcm91cC5jaGlsZHJlbi5sZW5ndGgpIC0gMTsKCiAgICAgICAgLy8gQm9keSByb3dzIGhhdmUgaW5kZXggcHJvcGVydHksIG90aGVyd2lzZSBET00gY2hpbGQgaW5kZXggb2YgdGhlIHJvdyBpcyB1c2VkLgogICAgICAgIGNvbnN0IHJvd0luZGV4ID0gKGFjdGl2ZVJvd0dyb3VwID09PSB0aGlzLiQuaXRlbXMpID8KICAgICAgICAgICh0aGlzLl9mb2N1c2VkSXRlbUluZGV4ICE9PSB1bmRlZmluZWQgPyB0aGlzLl9mb2N1c2VkSXRlbUluZGV4IDogYWN0aXZlUm93LmluZGV4KSA6CiAgICAgICAgICBpbmRleE9mQ2hpbGRFbGVtZW50KGFjdGl2ZVJvdyk7CgogICAgICAgIC8vIEluZGV4IG9mIHRoZSBkZXN0aW5hdGlvbiByb3cKICAgICAgICBsZXQgZHN0Um93SW5kZXggPSBNYXRoLm1heCgwLCBNYXRoLm1pbihyb3dJbmRleCArIGR5LCBtYXhSb3dJbmRleCkpOwoKICAgICAgICAvLyBSb3cgZGV0YWlscyBuYXZpZ2F0aW9uIGxvZ2ljCiAgICAgICAgbGV0IGRzdElzUm93RGV0YWlscyA9IGZhbHNlOwogICAgICAgIGlmIChhY3RpdmVSb3dHcm91cCA9PT0gdGhpcy4kLml0ZW1zKSB7CiAgICAgICAgICBjb25zdCBpdGVtID0gYWN0aXZlUm93Ll9pdGVtOwogICAgICAgICAgY29uc3QgZHN0SXRlbSA9IHRoaXMuX2NhY2hlLmdldEl0ZW1Gb3JJbmRleChkc3RSb3dJbmRleCk7CiAgICAgICAgICAvLyBTaG91bGQgd2UgbmF2aWdhdGUgdG8gcm93IGRldGFpbHM/CiAgICAgICAgICBpZiAoaXNSb3dEZXRhaWxzKSB7CiAgICAgICAgICAgIGRzdElzUm93RGV0YWlscyA9IGR5ID09PSAwOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgZHN0SXNSb3dEZXRhaWxzID0gZHkgPT09IDEgJiYgdGhpcy5faXNEZXRhaWxzT3BlbmVkKGl0ZW0pIHx8CiAgICAgICAgICAgICAgZHkgPT09IC0xICYmIGRzdFJvd0luZGV4ICE9PSByb3dJbmRleCAmJiB0aGlzLl9pc0RldGFpbHNPcGVuZWQoZHN0SXRlbSk7CiAgICAgICAgICB9CiAgICAgICAgICAvLyBTaG91bGQgd2UgbmF2aWdhdGUgYmV0d2VlbiBkZXRhaWxzIGFuZCByZWd1bGFyIGNlbGxzIG9mIHRoZSBzYW1lIHJvdz8KICAgICAgICAgIGlmIChkc3RJc1Jvd0RldGFpbHMgIT09IGlzUm93RGV0YWlscyAmJgogICAgICAgICAgICAgIChkeSA9PT0gMSAmJiBkc3RJc1Jvd0RldGFpbHMgfHwgZHkgPT09IC0xICYmICFkc3RJc1Jvd0RldGFpbHMpKSB7CiAgICAgICAgICAgIGRzdFJvd0luZGV4ID0gcm93SW5kZXg7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICAvLyBIZWFkZXIgYW5kIGZvb3RlciBjb3VsZCBoYXZlIGhpZGRlbiByb3dzLCBlLiBnLiwgaWYgbm9uZSBvZiB0aGUgY29sdW1ucwogICAgICAgIC8vIG9yIGdyb3VwcyBvbiB0aGUgZ2l2ZW4gY29sdW1uIHRyZWUgbGV2ZWwgZGVmaW5lIHRlbXBsYXRlLiBTa2lwIHRoZW0KICAgICAgICAvLyBpbiB2ZXJ0aWNhbCBrZXlib2FyZCBuYXZpZ2F0aW9uLgogICAgICAgIGlmIChhY3RpdmVSb3dHcm91cCAhPT0gdGhpcy4kLml0ZW1zKSB7CiAgICAgICAgICBpZiAoZHN0Um93SW5kZXggPiByb3dJbmRleCkgewogICAgICAgICAgICB3aGlsZSAoCiAgICAgICAgICAgICAgZHN0Um93SW5kZXggPCBtYXhSb3dJbmRleCAmJgogICAgICAgICAgICAgIGFjdGl2ZVJvd0dyb3VwLmNoaWxkcmVuW2RzdFJvd0luZGV4XS5oaWRkZW4KICAgICAgICAgICAgKSB7CiAgICAgICAgICAgICAgZHN0Um93SW5kZXgrKzsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIGlmIChkc3RSb3dJbmRleCA8IHJvd0luZGV4KSB7CiAgICAgICAgICAgIHdoaWxlICgKICAgICAgICAgICAgICBkc3RSb3dJbmRleCA+IDAgJiYKICAgICAgICAgICAgICBhY3RpdmVSb3dHcm91cC5jaGlsZHJlbltkc3RSb3dJbmRleF0uaGlkZGVuCiAgICAgICAgICAgICkgewogICAgICAgICAgICAgIGRzdFJvd0luZGV4LS07CiAgICAgICAgICAgIH0KICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIF9mb2N1c2VkQ29sdW1uT3JkZXIgaXMgbWVtb2l6ZWQg4oCUIHRoaXMgaXMgdG8gZW5zdXJlIHByZWRpY3RhYmxlCiAgICAgICAgLy8gbmF2aWdhdGlvbiB3aGVuIGVudGVyaW5nIGFuZCBsZWF2aW5nIGRldGFpbCBhbmQgY29sdW1uIGdyb3VwIGNlbGxzLgogICAgICAgIGlmICh0aGlzLl9mb2N1c2VkQ29sdW1uT3JkZXIgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgaWYgKGlzUm93RGV0YWlscykgewogICAgICAgICAgICB0aGlzLl9mb2N1c2VkQ29sdW1uT3JkZXIgPSAwOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgdGhpcy5fZm9jdXNlZENvbHVtbk9yZGVyID0gdGhpcy5fZ2V0Q29sdW1ucyhhY3RpdmVSb3dHcm91cCwgcm93SW5kZXgpLmZpbHRlcihjID0+ICFjLmhpZGRlbilbY29sdW1uSW5kZXhdLl9vcmRlcjsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIC8vIEZpbmQgb3JkZXJlZENvbHVtbkluZGV4IOKAlCB0aGUgaW5kZXggb2Ygb3JkZXIgY2xvc2VzdCBtYXRjaGluZyB0aGUKICAgICAgICAvLyBvcmlnaW5hbCBfZm9jdXNlZENvbHVtbk9yZGVyIGluIHRoZSBzb3J0ZWQgYXJyYXkgb2Ygb3JkZXJzCiAgICAgICAgLy8gb2YgdGhlIHZpc2libGUgY29sdW1ucyBvbiB0aGUgZGVzdGluYXRpb24gcm93LgogICAgICAgIGNvbnN0IGRzdENvbHVtbnMgPSB0aGlzLl9nZXRDb2x1bW5zKGFjdGl2ZVJvd0dyb3VwLCBkc3RSb3dJbmRleCkuZmlsdGVyKGMgPT4gIWMuaGlkZGVuKTsKICAgICAgICBjb25zdCBkc3RTb3J0ZWRDb2x1bW5PcmRlcnMgPSBkc3RDb2x1bW5zLm1hcChjID0+IGMuX29yZGVyKQogICAgICAgICAgLnNvcnQoKGIsIGEpID0+IChiIC0gYSkpOwogICAgICAgIGNvbnN0IG1heE9yZGVyZWRDb2x1bW5JbmRleCA9IGRzdFNvcnRlZENvbHVtbk9yZGVycy5sZW5ndGggLSAxOwogICAgICAgIGNvbnN0IG9yZGVyZWRDb2x1bW5JbmRleCA9IGRzdFNvcnRlZENvbHVtbk9yZGVycy5pbmRleE9mKAogICAgICAgICAgZHN0U29ydGVkQ29sdW1uT3JkZXJzLnNsaWNlKDApLnNvcnQoKGIsIGEpID0+CiAgICAgICAgICAgIE1hdGguYWJzKGIgLSB0aGlzLl9mb2N1c2VkQ29sdW1uT3JkZXIpIC0gTWF0aC5hYnMoYSAtIHRoaXMuX2ZvY3VzZWRDb2x1bW5PcmRlcikKICAgICAgICAgIClbMF0KICAgICAgICApOwoKICAgICAgICAvLyBJbmRleCBvZiB0aGUgZGVzdGluYXRpb24gY29sdW1uIG9yZGVyCiAgICAgICAgY29uc3QgZHN0T3JkZXJlZENvbHVtbkluZGV4ID0gKGR5ID09PSAwICYmIGlzUm93RGV0YWlscykgPyBvcmRlcmVkQ29sdW1uSW5kZXggOgogICAgICAgICAgTWF0aC5tYXgoMCwgTWF0aC5taW4ob3JkZXJlZENvbHVtbkluZGV4ICsgZHgsIG1heE9yZGVyZWRDb2x1bW5JbmRleCkpOwoKICAgICAgICBpZiAoZHN0T3JkZXJlZENvbHVtbkluZGV4ICE9PSBvcmRlcmVkQ29sdW1uSW5kZXgpIHsKICAgICAgICAgIC8vIEhvcml6b250YWwgbW92ZW1lbnQgaW52YWxpZGF0ZXMgc3RvcmVkIF9mb2N1c2VkQ29sdW1uT3JkZXIKICAgICAgICAgIHRoaXMuX2ZvY3VzZWRDb2x1bW5PcmRlciA9IHVuZGVmaW5lZDsKICAgICAgICB9CgogICAgICAgIC8vIEVuc3VyZSBjb3JyZWN0IHZlcnRpY2FsIHNjcm9sbCBwb3NpdGlvbiwgZGVzdGluYXRpb24gcm93IGlzIHZpc2libGUKICAgICAgICBpZiAoYWN0aXZlUm93R3JvdXAgPT09IHRoaXMuJC5pdGVtcykgewogICAgICAgICAgdGhpcy5fZW5zdXJlU2Nyb2xsZWRUb0luZGV4KGRzdFJvd0luZGV4KTsKICAgICAgICB9CgogICAgICAgIC8vIFRoaXMgaGFzIHRvIGJlIHNldCBhZnRlciBzY3JvbGxpbmcsIG90aGVyd2lzZSBpdCBjYW4gYmUgcmVtb3ZlZCBieQogICAgICAgIC8vIGBfcHJldmVudFNjcm9sbGVyUm90YXRpbmdDZWxsRm9jdXMoaXRlbSwgaW5kZXgpYCBkdXJpbmcgc2Nyb2xsaW5nLgogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbmF2aWdhdGluZycsIHRydWUsIHRoaXMpOwoKICAgICAgICBjb25zdCBjb2x1bW5JbmRleEJ5T3JkZXIgPSBkc3RDb2x1bW5zLnJlZHVjZSgoYWNjLCBjb2wsIGkpID0+IChhY2NbY29sLl9vcmRlcl0gPSBpLCBhY2MpLCB7fSk7CiAgICAgICAgY29uc3QgZHN0Q29sdW1uSW5kZXggPSBjb2x1bW5JbmRleEJ5T3JkZXJbZHN0U29ydGVkQ29sdW1uT3JkZXJzW2RzdE9yZGVyZWRDb2x1bW5JbmRleF1dOwoKICAgICAgICAvLyBGb3IgYm9keSByb3dzLCB1c2UgaW5kZXggcHJvcGVydHkgdG8gZmluZCBkZXN0aW5hdGlvbiByb3csIG90aGVyd2lzZSB1c2UgRE9NIGNoaWxkIGluZGV4CiAgICAgICAgY29uc3QgZHN0Um93ID0gYWN0aXZlUm93R3JvdXAgPT09IHRoaXMuJC5pdGVtcyA/CiAgICAgICAgICBBcnJheS5mcm9tKGFjdGl2ZVJvd0dyb3VwLmNoaWxkcmVuKS5maWx0ZXIoZWwgPT4gZWwuaW5kZXggPT09IGRzdFJvd0luZGV4KVswXSA6CiAgICAgICAgICBhY3RpdmVSb3dHcm91cC5jaGlsZHJlbltkc3RSb3dJbmRleF07CiAgICAgICAgaWYgKCFkc3RSb3cpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIEhlcmUgd2UgZ28hCiAgICAgICAgY29uc3QgZHN0Q2VsbCA9IGRzdElzUm93RGV0YWlscyA/CiAgICAgICAgICBBcnJheS5mcm9tKGRzdFJvdy5jaGlsZHJlbikKICAgICAgICAgICAgLmZpbHRlcihlbCA9PiB0aGlzLl9lbGVtZW50TWF0Y2hlcyhlbCwgJ1twYXJ0fj0iZGV0YWlscy1jZWxsIl0nKSlbMF0gOgogICAgICAgICAgZHN0Um93LmNoaWxkcmVuW2RzdENvbHVtbkluZGV4XTsKICAgICAgICB0aGlzLl9zY3JvbGxIb3Jpem9udGFsbHlUb0NlbGwoZHN0Q2VsbCk7CiAgICAgICAgaWYgKGFjdGl2ZVJvd0dyb3VwID09PSB0aGlzLiQuaXRlbXMpIHsKICAgICAgICAgIC8vIFdoZW4gc2Nyb2xsaW5nIHdpdGggcmVwZWF0ZWQga2V5ZG93biwgc29tZXRpbWVzIEZvY3VzRXZlbnQgbGlzdGVuZXJzCiAgICAgICAgICAvLyBhcmUgdG9vIGxhdGUgdG8gdXBkYXRlIF9mb2N1c2VkSXRlbUluZGV4LiBFbnN1cmUgbmV4dCBrZXlkb3duCiAgICAgICAgICAvLyBsaXN0ZW5lciBpbnZvY2F0aW9uIGdldHMgdXBkYXRlZCBfZm9jdXNlZEl0ZW1JbmRleCB2YWx1ZS4KICAgICAgICAgIHRoaXMuX2ZvY3VzZWRJdGVtSW5kZXggPSBkc3RSb3dJbmRleDsKICAgICAgICB9CgogICAgICAgIGlmIChhY3RpdmVSb3dHcm91cCA9PT0gdGhpcy4kLml0ZW1zKSB7CiAgICAgICAgICBjb25zdCBkc3RSZWN0ID0gZHN0Q2VsbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICAgIGNvbnN0IGZvb3RlclRvcCA9IHRoaXMuJC5mb290ZXIuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkudG9wOwogICAgICAgICAgY29uc3QgaGVhZGVyQm90dG9tID0gdGhpcy4kLmhlYWRlci5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5ib3R0b207CiAgICAgICAgICBpZiAoZHN0UmVjdC5ib3R0b20gPiBmb290ZXJUb3ApIHsKICAgICAgICAgICAgdGhpcy4kLnRhYmxlLnNjcm9sbFRvcCArPSBkc3RSZWN0LmJvdHRvbSAtIGZvb3RlclRvcDsKICAgICAgICAgICAgdGhpcy5fc2Nyb2xsSGFuZGxlcigpOwogICAgICAgICAgfSBlbHNlIGlmIChkc3RSZWN0LnRvcCA8IGhlYWRlckJvdHRvbSkgewogICAgICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsVG9wIC09IGhlYWRlckJvdHRvbSAtIGRzdFJlY3QudG9wOwogICAgICAgICAgICB0aGlzLl9zY3JvbGxIYW5kbGVyKCk7CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBkc3RDZWxsLmZvY3VzKCk7CiAgICAgIH0KCiAgICAgIF9wYXJzZUV2ZW50UGF0aChwYXRoKSB7CiAgICAgICAgY29uc3QgdGFibGVJbmRleCA9IHBhdGguaW5kZXhPZih0aGlzLiQudGFibGUpOwogICAgICAgIHJldHVybiB7CiAgICAgICAgICByb3dHcm91cDogcGF0aFt0YWJsZUluZGV4IC0gMV0sCiAgICAgICAgICByb3c6IHBhdGhbdGFibGVJbmRleCAtIDJdLAogICAgICAgICAgY2VsbDogcGF0aFt0YWJsZUluZGV4IC0gM10KICAgICAgICB9OwogICAgICB9CgogICAgICBfb25JbnRlcmFjdGlvbktleURvd24oZSwga2V5KSB7CiAgICAgICAgY29uc3QgbG9jYWxUYXJnZXQgPSBlLmNvbXBvc2VkUGF0aCgpWzBdOwogICAgICAgIGNvbnN0IGxvY2FsVGFyZ2V0SXNUZXh0SW5wdXQgPSBsb2NhbFRhcmdldC5sb2NhbE5hbWUgPT09ICdpbnB1dCcgJiYKICAgICAgICAgICEvXihidXR0b258Y2hlY2tib3h8Y29sb3J8ZmlsZXxpbWFnZXxyYWRpb3xyYW5nZXxyZXNldHxzdWJtaXQpJC9pLnRlc3QobG9jYWxUYXJnZXQudHlwZSk7CgogICAgICAgIGxldCB3YW50SW50ZXJhY3Rpbmc7CiAgICAgICAgc3dpdGNoIChrZXkpIHsKICAgICAgICAgIGNhc2UgJ0VudGVyJzoKICAgICAgICAgICAgd2FudEludGVyYWN0aW5nID0gdGhpcy5oYXNBdHRyaWJ1dGUoJ2ludGVyYWN0aW5nJykgPyAhbG9jYWxUYXJnZXRJc1RleHRJbnB1dCA6IHRydWU7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnRXNjYXBlJzoKICAgICAgICAgICAgd2FudEludGVyYWN0aW5nID0gZmFsc2U7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgY2FzZSAnRjInOgogICAgICAgICAgICB3YW50SW50ZXJhY3RpbmcgPSAhdGhpcy5oYXNBdHRyaWJ1dGUoJ2ludGVyYWN0aW5nJyk7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgIH0KCiAgICAgICAgY29uc3Qge2NlbGx9ID0gdGhpcy5fcGFyc2VFdmVudFBhdGgoZS5jb21wb3NlZFBhdGgoKSk7CgogICAgICAgIGlmICh0aGlzLmhhc0F0dHJpYnV0ZSgnaW50ZXJhY3RpbmcnKSAhPT0gd2FudEludGVyYWN0aW5nKSB7CiAgICAgICAgICBpZiAod2FudEludGVyYWN0aW5nKSB7CiAgICAgICAgICAgIGNvbnN0IGZvY3VzVGFyZ2V0ID0gY2VsbC5fY29udGVudC5xdWVyeVNlbGVjdG9yKCdbZm9jdXMtdGFyZ2V0XScpIHx8CiAgICAgICAgICAgICAgY2VsbC5fY29udGVudC5maXJzdEVsZW1lbnRDaGlsZDsKICAgICAgICAgICAgaWYgKGZvY3VzVGFyZ2V0KSB7CiAgICAgICAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgICAgICAgIGZvY3VzVGFyZ2V0LmZvY3VzKCk7CiAgICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdpbnRlcmFjdGluZycsIHRydWUsIHRoaXMpOwogICAgICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbmF2aWdhdGluZycsIGZhbHNlLCB0aGlzKTsKICAgICAgICAgICAgfQogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgICAgICB0aGlzLl9mb2N1c2VkQ29sdW1uT3JkZXIgPSB1bmRlZmluZWQ7CiAgICAgICAgICAgIGNlbGwuZm9jdXMoKTsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdpbnRlcmFjdGluZycsIGZhbHNlLCB0aGlzKTsKICAgICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduYXZpZ2F0aW5nJywgdHJ1ZSwgdGhpcyk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfcHJlZGljdEZvY3VzU3RlcFRhcmdldChzcmNFbGVtZW50LCBzdGVwKSB7CiAgICAgICAgY29uc3QgdGFiT3JkZXIgPSBbCiAgICAgICAgICB0aGlzLiQudGFibGUsCiAgICAgICAgICB0aGlzLl9oZWFkZXJGb2N1c2FibGUsCiAgICAgICAgICB0aGlzLl9pdGVtc0ZvY3VzYWJsZSwKICAgICAgICAgIHRoaXMuX2Zvb3RlckZvY3VzYWJsZSwKICAgICAgICAgIHRoaXMuJC5mb2N1c2V4aXQKICAgICAgICBdOwoKICAgICAgICBsZXQgaW5kZXggPSB0YWJPcmRlci5pbmRleE9mKHNyY0VsZW1lbnQpOwoKICAgICAgICBpbmRleCArPSBzdGVwOwogICAgICAgIHdoaWxlIChpbmRleCA+PSAwICYmIGluZGV4IDw9IHRhYk9yZGVyLmxlbmd0aCAtIDEgJiYKICAgICAgICAgICAgKCF0YWJPcmRlcltpbmRleF0gfHwgdGFiT3JkZXJbaW5kZXhdLnBhcmVudE5vZGUuaGlkZGVuKSkgewogICAgICAgICAgaW5kZXggKz0gc3RlcDsKICAgICAgICB9CgogICAgICAgIHJldHVybiB0YWJPcmRlcltpbmRleF07CiAgICAgIH0KCiAgICAgIF9vblRhYktleURvd24oZSkgewogICAgICAgIGNvbnN0IGZvY3VzVGFyZ2V0ID0gdGhpcy5fcHJlZGljdEZvY3VzU3RlcFRhcmdldChlLmNvbXBvc2VkUGF0aCgpWzBdLCBlLnNoaWZ0S2V5ID8gLTEgOiAxKTsKCiAgICAgICAgaWYgKGZvY3VzVGFyZ2V0ID09PSB0aGlzLiQudGFibGUpIHsKICAgICAgICAgIC8vIFRoZSBmb2N1cyBpcyBhYm91dCB0byBleGl0IHRoZSBncmlkIHRvIHRoZSB0b3AuCiAgICAgICAgICB0aGlzLiQudGFibGUuZm9jdXMoKTsKICAgICAgICB9IGVsc2UgaWYgKGZvY3VzVGFyZ2V0ID09PSB0aGlzLiQuZm9jdXNleGl0KSB7CiAgICAgICAgICAvLyBUaGUgZm9jdXMgaXMgYWJvdXQgdG8gZXhpdCB0aGUgZ3JpZCB0byB0aGUgYm90dG9tLgogICAgICAgICAgdGhpcy4kLmZvY3VzZXhpdC5mb2N1cygpOwogICAgICAgIH0gZWxzZSBpZiAoZm9jdXNUYXJnZXQgPT09IHRoaXMuX2l0ZW1zRm9jdXNhYmxlKSB7CiAgICAgICAgICBsZXQgaXRlbXNGb2N1c1RhcmdldCA9IGZvY3VzVGFyZ2V0OwogICAgICAgICAgY29uc3QgdGFyZ2V0Um93ID0gdGhpcy5faXRlbXNGb2N1c2FibGUucGFyZW50Tm9kZTsKICAgICAgICAgIHRoaXMuX2Vuc3VyZVNjcm9sbGVkVG9JbmRleCh0aGlzLl9mb2N1c2VkSXRlbUluZGV4KTsKICAgICAgICAgIGlmICh0YXJnZXRSb3cuaW5kZXggIT09IHRoaXMuX2ZvY3VzZWRJdGVtSW5kZXgpIHsKICAgICAgICAgICAgLy8gVGhlIHRhcmdldCByb3csIHdoaWNoIGlzIGFib3V0IHRvIGJlIGZvY3VzZWQgbmV4dCwgaGFzIGJlZW4KICAgICAgICAgICAgLy8gYXNzaWduZWQgd2l0aCBhIG5ldyBpbmRleCBzaW5jZSBsYXN0IGZvY3VzLCBwcm9iYWJseSBiZWNhdXNlIG9mCiAgICAgICAgICAgIC8vIHNjcm9sbGluZy4gRm9jdXMgdGhlIHJvdyBmb3IgdGhlIHN0b3JlZCBmb2N1c2VkIGl0ZW0gaW5kZXggaW5zdGVhZC4KICAgICAgICAgICAgY29uc3QgY29sdW1uSW5kZXggPSBBcnJheS5mcm9tKHRhcmdldFJvdy5jaGlsZHJlbikuaW5kZXhPZih0aGlzLl9pdGVtc0ZvY3VzYWJsZSk7CiAgICAgICAgICAgIGNvbnN0IGZvY3VzZWRJdGVtUm93ID0gQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pCiAgICAgICAgICAgICAgLmZpbHRlcihyb3cgPT4gcm93LmluZGV4ID09PSB0aGlzLl9mb2N1c2VkSXRlbUluZGV4KVswXTsKICAgICAgICAgICAgaWYgKGZvY3VzZWRJdGVtUm93KSB7CiAgICAgICAgICAgICAgaXRlbXNGb2N1c1RhcmdldCA9IGZvY3VzZWRJdGVtUm93LmNoaWxkcmVuW2NvbHVtbkluZGV4XTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwogICAgICAgICAgaXRlbXNGb2N1c1RhcmdldC5mb2N1cygpOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgICBmb2N1c1RhcmdldC5mb2N1cygpOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduYXZpZ2F0aW5nJywgdHJ1ZSwgdGhpcyk7CiAgICAgIH0KCiAgICAgIF9vblNwYWNlS2V5RG93bihlKSB7CiAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpOwoKICAgICAgICBjb25zdCBjZWxsID0gZS5jb21wb3NlZFBhdGgoKVswXTsKICAgICAgICBpZiAoIWNlbGwuX2NvbnRlbnQgfHwgIWNlbGwuX2NvbnRlbnQuZmlyc3RFbGVtZW50Q2hpbGQpIHsKICAgICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2NlbGwtYWN0aXZhdGUnLCB7ZGV0YWlsOiB7CiAgICAgICAgICAgIG1vZGVsOiB0aGlzLl9fZ2V0Um93TW9kZWwoY2VsbC5wYXJlbnRFbGVtZW50KQogICAgICAgICAgfX0pKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKiBAcHJpdmF0ZSAqLwogICAgICBfb25LZXlVcChlKSB7CiAgICAgICAgaWYgKCEvXiggfFNwYWNlQmFyKSQvLnRlc3QoZS5rZXkpKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CgogICAgICAgIGNvbnN0IGNlbGwgPSBlLmNvbXBvc2VkUGF0aCgpWzBdOwogICAgICAgIGlmIChjZWxsLl9jb250ZW50ICYmIGNlbGwuX2NvbnRlbnQuZmlyc3RFbGVtZW50Q2hpbGQpIHsKICAgICAgICAgIGNvbnN0IHdhc05hdmlnYXRpbmcgPSB0aGlzLmhhc0F0dHJpYnV0ZSgnbmF2aWdhdGluZycpOwogICAgICAgICAgY2VsbC5fY29udGVudC5maXJzdEVsZW1lbnRDaGlsZC5jbGljaygpOwogICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduYXZpZ2F0aW5nJywgd2FzTmF2aWdhdGluZywgdGhpcyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfb25Gb2N1c0luKGUpIHsKICAgICAgICBpZiAoIXRoaXMuX2lzTW91c2Vkb3duKSB7CiAgICAgICAgICB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ25hdmlnYXRpbmcnLCB0cnVlLCB0aGlzKTsKICAgICAgICB9CgogICAgICAgIGNvbnN0IHJvb3RUYXJnZXQgPSBlLmNvbXBvc2VkUGF0aCgpWzBdOwoKICAgICAgICBpZiAocm9vdFRhcmdldCA9PT0gdGhpcy4kLnRhYmxlIHx8CiAgICAgICAgICAgIHJvb3RUYXJnZXQgPT09IHRoaXMuJC5mb2N1c2V4aXQpIHsKICAgICAgICAgIC8vIFRoZSBmb2N1cyBlbnRlcnMgdGhlIHRvcCAoYm90dG9tKSBvZiB0aGUgZ3JpZCwgbWVhbmluZyB0aGF0IHVzZXIgaGFzCiAgICAgICAgICAvLyB0YWJiZWQgKHNoaWZ0LXRhYmJlZCkgaW50byB0aGUgZ3JpZC4gTW92ZSB0aGUgZm9jdXMgdG8KICAgICAgICAgIC8vIHRoZSBmaXJzdCAodGhlIGxhc3QpIGZvY3VzYWJsZS4KICAgICAgICAgIHRoaXMuX3ByZWRpY3RGb2N1c1N0ZXBUYXJnZXQoCiAgICAgICAgICAgIHJvb3RUYXJnZXQsCiAgICAgICAgICAgIHJvb3RUYXJnZXQgPT09IHRoaXMuJC50YWJsZSA/IDEgOiAtMQogICAgICAgICAgKS5mb2N1cygpOwogICAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdpbnRlcmFjdGluZycsIGZhbHNlLCB0aGlzKTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgdGhpcy5fZGV0ZWN0SW50ZXJhY3RpbmcoZSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfb25Gb2N1c091dChlKSB7CiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduYXZpZ2F0aW5nJywgZmFsc2UsIHRoaXMpOwogICAgICAgIHRoaXMuX2RldGVjdEludGVyYWN0aW5nKGUpOwogICAgICB9CgogICAgICBfb25DZWxsRm9jdXNJbihlKSB7CiAgICAgICAgdGhpcy5fZGV0ZWN0SW50ZXJhY3RpbmcoZSk7CgogICAgICAgIGlmIChlLmNvbXBvc2VkUGF0aCgpLmluZGV4T2YodGhpcy4kLnRhYmxlKSA9PT0gMykgewogICAgICAgICAgY29uc3QgY2VsbCA9IGUuY29tcG9zZWRQYXRoKClbMF07CiAgICAgICAgICB0aGlzLl9hY3RpdmVSb3dHcm91cCA9IGNlbGwucGFyZW50Tm9kZS5wYXJlbnROb2RlOwogICAgICAgICAgaWYgKHRoaXMuX2FjdGl2ZVJvd0dyb3VwID09PSB0aGlzLiQuaGVhZGVyKSB7CiAgICAgICAgICAgIHRoaXMuX2hlYWRlckZvY3VzYWJsZSA9IGNlbGw7CiAgICAgICAgICB9IGVsc2UgaWYgKHRoaXMuX2FjdGl2ZVJvd0dyb3VwID09PSB0aGlzLiQuaXRlbXMpIHsKICAgICAgICAgICAgdGhpcy5faXRlbXNGb2N1c2FibGUgPSBjZWxsOwogICAgICAgICAgfSBlbHNlIGlmICh0aGlzLl9hY3RpdmVSb3dHcm91cCA9PT0gdGhpcy4kLmZvb3RlcikgewogICAgICAgICAgICB0aGlzLl9mb290ZXJGb2N1c2FibGUgPSBjZWxsOwogICAgICAgICAgfQogICAgICAgICAgLy8gSW5mb3JtIGNlbGwgY29udGVudCBvZiB0aGUgZm9jdXMgKHVzZWQgaW4gPHZhYWRpbi1ncmlkLXNvcnRlcj4pCiAgICAgICAgICBjZWxsLl9jb250ZW50LmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjZWxsLWZvY3VzaW4nLCB7YnViYmxlczogZmFsc2V9KSk7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl9kZXRlY3RGb2N1c2VkSXRlbUluZGV4KGUpOwogICAgICB9CgogICAgICBfb25DZWxsRm9jdXNPdXQoZSkgewogICAgICAgIGlmIChlLmNvbXBvc2VkUGF0aCgpLmluZGV4T2YodGhpcy4kLnRhYmxlKSA9PT0gMykgewogICAgICAgICAgY29uc3QgY2VsbCA9IGUuY29tcG9zZWRQYXRoKClbMF07CiAgICAgICAgICAvLyBJbmZvcm0gY2VsbCBjb250ZW50IG9mIHRoZSBmb2N1cyAodXNlZCBpbiA8dmFhZGluLWdyaWQtc29ydGVyPikKICAgICAgICAgIGNlbGwuX2NvbnRlbnQuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2NlbGwtZm9jdXNvdXQnLCB7YnViYmxlczogZmFsc2V9KSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfZGV0ZWN0SW50ZXJhY3RpbmcoZSkgewogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnaW50ZXJhY3RpbmcnLAogICAgICAgICAgZS5jb21wb3NlZFBhdGgoKS5zb21lKGVsID0+IGVsLmxvY2FsTmFtZSA9PT0gJ3ZhYWRpbi1ncmlkLWNlbGwtY29udGVudCcpLAogICAgICAgICAgdGhpcyk7CiAgICAgIH0KCiAgICAgIF9kZXRlY3RGb2N1c2VkSXRlbUluZGV4KGUpIHsKICAgICAgICBjb25zdCB7cm93R3JvdXAsIHJvd30gPSB0aGlzLl9wYXJzZUV2ZW50UGF0aChlLmNvbXBvc2VkUGF0aCgpKTsKICAgICAgICBpZiAocm93R3JvdXAgPT09IHRoaXMuJC5pdGVtcykgewogICAgICAgICAgdGhpcy5fZm9jdXNlZEl0ZW1JbmRleCA9IHJvdy5pbmRleDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9wcmV2ZW50U2Nyb2xsZXJSb3RhdGluZ0NlbGxGb2N1cyhpdGVtLCBpbmRleCkgewogICAgICAgIGlmIChpdGVtLmluZGV4ID09PSB0aGlzLl9mb2N1c2VkSXRlbUluZGV4ICYmIHRoaXMuaGFzQXR0cmlidXRlKCduYXZpZ2F0aW5nJykgJiYgdGhpcy5fYWN0aXZlUm93R3JvdXAgPT09IHRoaXMuJC5pdGVtcykgewogICAgICAgICAgLy8gRm9jdXNlZCBpdGVtIGhhcyB3ZW50LCBoaWRlIG5hdmlnYXRpb24gbW9kZQogICAgICAgICAgdGhpcy5fbmF2aWdhdGluZ0lzSGlkZGVuID0gdHJ1ZTsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbmF2aWdhdGluZycsIGZhbHNlLCB0aGlzKTsKICAgICAgICB9CiAgICAgICAgaWYgKGluZGV4ID09PSB0aGlzLl9mb2N1c2VkSXRlbUluZGV4ICYmIHRoaXMuX25hdmlnYXRpbmdJc0hpZGRlbikgewogICAgICAgICAgLy8gRm9jdXNlZCBpdGVtIGlzIGJhY2ssIHJlc3RvcmUgbmF2aWdhdGlvbiBtb2RlCiAgICAgICAgICB0aGlzLl9uYXZpZ2F0aW5nSXNIaWRkZW4gPSBmYWxzZTsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbmF2aWdhdGluZycsIHRydWUsIHRoaXMpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2dldENvbHVtbnMocm93R3JvdXAsIHJvd0luZGV4KSB7CiAgICAgICAgbGV0IGNvbHVtblRyZWVMZXZlbCA9IHRoaXMuX2NvbHVtblRyZWUubGVuZ3RoIC0gMTsKICAgICAgICBpZiAocm93R3JvdXAgPT09IHRoaXMuJC5oZWFkZXIpIHsKICAgICAgICAgIGNvbHVtblRyZWVMZXZlbCA9IHJvd0luZGV4OwogICAgICAgIH0gZWxzZSBpZiAocm93R3JvdXAgPT09IHRoaXMuJC5mb290ZXIpIHsKICAgICAgICAgIGNvbHVtblRyZWVMZXZlbCA9IHRoaXMuX2NvbHVtblRyZWUubGVuZ3RoIC0gMSAtIHJvd0luZGV4OwogICAgICAgIH0KICAgICAgICByZXR1cm4gdGhpcy5fY29sdW1uVHJlZVtjb2x1bW5UcmVlTGV2ZWxdOwogICAgICB9CgogICAgICBfcmVzZXRLZXlib2FyZE5hdmlnYXRpb24oKSB7CiAgICAgICAgaWYgKHRoaXMuJC5oZWFkZXIuZmlyc3RFbGVtZW50Q2hpbGQpIHsKICAgICAgICAgIHRoaXMuX2hlYWRlckZvY3VzYWJsZSA9IEFycmF5LmZyb20odGhpcy4kLmhlYWRlci5maXJzdEVsZW1lbnRDaGlsZC5jaGlsZHJlbikuZmlsdGVyKGVsID0+ICFlbC5oaWRkZW4pWzBdOwogICAgICAgIH0KCiAgICAgICAgaWYgKHRoaXMuJC5pdGVtcy5maXJzdEVsZW1lbnRDaGlsZCkgewogICAgICAgICAgY29uc3QgZmlyc3RWaXNpYmxlSW5kZXhSb3cgPSB0aGlzLl9pdGVyYXRlSXRlbXMoKHBpZHgsIHZpZHgpID0+IHsKICAgICAgICAgICAgaWYgKHRoaXMuX2ZpcnN0VmlzaWJsZUluZGV4ID09PSB2aWR4KSB7CiAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuJC5pdGVtcy5jaGlsZHJlbltwaWR4XTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgICBpZiAoZmlyc3RWaXNpYmxlSW5kZXhSb3cpIHsKICAgICAgICAgICAgdGhpcy5faXRlbXNGb2N1c2FibGUgPSBBcnJheS5mcm9tKGZpcnN0VmlzaWJsZUluZGV4Um93LmNoaWxkcmVuKS5maWx0ZXIoZWwgPT4gIWVsLmhpZGRlbilbMF07CiAgICAgICAgICB9CiAgICAgICAgfQoKICAgICAgICBpZiAodGhpcy4kLmZvb3Rlci5maXJzdEVsZW1lbnRDaGlsZCkgewogICAgICAgICAgdGhpcy5fZm9vdGVyRm9jdXNhYmxlID0gQXJyYXkuZnJvbSh0aGlzLiQuZm9vdGVyLmZpcnN0RWxlbWVudENoaWxkLmNoaWxkcmVuKS5maWx0ZXIoZWwgPT4gIWVsLmhpZGRlbilbMF07CiAgICAgICAgfQogICAgICB9CgogICAgICBfc2Nyb2xsSG9yaXpvbnRhbGx5VG9DZWxsKGRzdENlbGwpIHsKICAgICAgICBpZiAoZHN0Q2VsbC5oYXNBdHRyaWJ1dGUoJ2Zyb3plbicpIHx8IHRoaXMuX2VsZW1lbnRNYXRjaGVzKGRzdENlbGwsICdbcGFydH49ImRldGFpbHMtY2VsbCJdJykpIHsKICAgICAgICAgIC8vIFRoZXNlIGNlbGxzIGFyZSwgYnkgZGVzaWduLCBhbHdheXMgdmlzaWJsZSwgbm8gbmVlZCB0byBzY3JvbGwuCiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBjb25zdCBkc3RDZWxsUmVjdCA9IGRzdENlbGwuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgY29uc3QgZHN0Um93ID0gZHN0Q2VsbC5wYXJlbnROb2RlOwogICAgICAgIGNvbnN0IGRzdENlbGxJbmRleCA9IEFycmF5LmZyb20oZHN0Um93LmNoaWxkcmVuKS5pbmRleE9mKGRzdENlbGwpOwogICAgICAgIGNvbnN0IHRhYmxlUmVjdCA9IHRoaXMuJC50YWJsZS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTsKICAgICAgICBsZXQgbGVmdEJvdW5kYXJ5ID0gdGFibGVSZWN0LmxlZnQsIHJpZ2h0Qm91bmRhcnkgPSB0YWJsZVJlY3QucmlnaHQ7CiAgICAgICAgZm9yIChsZXQgaSA9IGRzdENlbGxJbmRleCAtIDE7IGkgPj0gMDsgaS0tKSB7CiAgICAgICAgICBjb25zdCBjZWxsID0gZHN0Um93LmNoaWxkcmVuW2ldOwogICAgICAgICAgaWYgKGNlbGwuaGFzQXR0cmlidXRlKCdoaWRkZW4nKSB8fAogICAgICAgICAgICAgIHRoaXMuX2VsZW1lbnRNYXRjaGVzKGNlbGwsICdbcGFydH49ImRldGFpbHMtY2VsbCJdJykpIHsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICB9CiAgICAgICAgICBpZiAoY2VsbC5oYXNBdHRyaWJ1dGUoJ2Zyb3plbicpKSB7CiAgICAgICAgICAgIGxlZnRCb3VuZGFyeSA9IGNlbGwuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkucmlnaHQ7CiAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBmb3IgKGxldCBpID0gZHN0Q2VsbEluZGV4ICsgMTsgaSA8IGRzdFJvdy5jaGlsZHJlbi5sZW5ndGg7IGkrKykgewogICAgICAgICAgY29uc3QgY2VsbCA9IGRzdFJvdy5jaGlsZHJlbltpXTsKICAgICAgICAgIGlmIChjZWxsLmhhc0F0dHJpYnV0ZSgnaGlkZGVuJykgfHwKICAgICAgICAgICAgICB0aGlzLl9lbGVtZW50TWF0Y2hlcyhjZWxsLCAnW3BhcnR+PSJkZXRhaWxzLWNlbGwiXScpKSB7CiAgICAgICAgICAgIGNvbnRpbnVlOwogICAgICAgICAgfQogICAgICAgICAgaWYgKGNlbGwuaGFzQXR0cmlidXRlKCdmcm96ZW4nKSkgewogICAgICAgICAgICByaWdodEJvdW5kYXJ5ID0gY2VsbC5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5sZWZ0OwogICAgICAgICAgICBicmVhazsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmIChkc3RDZWxsUmVjdC5sZWZ0IDwgbGVmdEJvdW5kYXJ5KSB7CiAgICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsTGVmdCArPSBNYXRoLnJvdW5kKGRzdENlbGxSZWN0LmxlZnQgLSBsZWZ0Qm91bmRhcnkpOwogICAgICAgIH0KICAgICAgICBpZiAoZHN0Q2VsbFJlY3QucmlnaHQgPiByaWdodEJvdW5kYXJ5KSB7CiAgICAgICAgICB0aGlzLiQudGFibGUuc2Nyb2xsTGVmdCArPSBNYXRoLnJvdW5kKGRzdENlbGxSZWN0LnJpZ2h0IC0gcmlnaHRCb3VuZGFyeSk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfZWxlbWVudE1hdGNoZXMoZWwsIHF1ZXJ5KSB7CiAgICAgICAgcmV0dXJuIGVsLm1hdGNoZXMgPyBlbC5tYXRjaGVzKHF1ZXJ5KSA6CiAgICAgICAgICBBcnJheS5mcm9tKGVsLnBhcmVudE5vZGUucXVlcnlTZWxlY3RvckFsbChxdWVyeSkpLmluZGV4T2YoZWwpICE9PSAtMTsKICAgICAgfQogICAgfTsKCiAgICAvKioKICAgIEBsaWNlbnNlCiAgICBDb3B5cmlnaHQgKGMpIDIwMTcgVmFhZGluIEx0ZC4KICAgIFRoaXMgcHJvZ3JhbSBpcyBhdmFpbGFibGUgdW5kZXIgQXBhY2hlIExpY2Vuc2UgVmVyc2lvbiAyLjAsIGF2YWlsYWJsZSBhdCBodHRwczovL3ZhYWRpbi5jb20vbGljZW5zZS8KICAgICovCgogICAgLyoqCiAgICAgKiBAcG9seW1lck1peGluCiAgICAgKi8KICAgIGNvbnN0IENvbHVtblJlb3JkZXJpbmdNaXhpbiA9IHN1cGVyQ2xhc3MgPT4gY2xhc3MgQ29sdW1uUmVvcmRlcmluZ01peGluIGV4dGVuZHMgR2VzdHVyZUV2ZW50TGlzdGVuZXJzKHN1cGVyQ2xhc3MpIHsKCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBTZXQgdG8gdHJ1ZSB0byBhbGxvdyBjb2x1bW4gcmVvcmRlcmluZy4KICAgICAgICAgICAqLwogICAgICAgICAgY29sdW1uUmVvcmRlcmluZ0FsbG93ZWQ6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IGZhbHNlCiAgICAgICAgICB9LAoKICAgICAgICAgIF9vcmRlckJhc2VTY29wZTogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIHZhbHVlOiAxMDAwMDAwMAogICAgICAgICAgfQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX3VwZGF0ZU9yZGVycyhfY29sdW1uVHJlZSwgX2NvbHVtblRyZWUuKiknCiAgICAgICAgXTsKICAgICAgfQoKICAgICAgcmVhZHkoKSB7CiAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICBhZGRMaXN0ZW5lcih0aGlzLCAndHJhY2snLCB0aGlzLl9vblRyYWNrRXZlbnQpOwogICAgICAgIHRoaXMuX3Jlb3JkZXJHaG9zdCA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yKCdbcGFydD0icmVvcmRlci1naG9zdCJdJyk7CgogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcigndG91Y2hzdGFydCcsIHRoaXMuX29uVG91Y2hTdGFydC5iaW5kKHRoaXMpKTsKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ3RvdWNobW92ZScsIHRoaXMuX29uVG91Y2hNb3ZlLmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcigndG91Y2hlbmQnLCB0aGlzLl9vblRvdWNoRW5kLmJpbmQodGhpcykpOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignY29udGV4dG1lbnUnLCB0aGlzLl9vbkNvbnRleHRNZW51LmJpbmQodGhpcykpOwogICAgICB9CgogICAgICBfb25Db250ZXh0TWVudShlKSB7CiAgICAgICAgaWYgKHRoaXMuaGFzQXR0cmlidXRlKCdyZW9yZGVyaW5nJykpIHsKICAgICAgICAgIGUucHJldmVudERlZmF1bHQoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9vblRvdWNoU3RhcnQoZSkgewogICAgICAgIC8vIFRvdWNoIGV2ZW50LCBkZWxheSBhY3RpdmF0aW9uIGJ5IDEwMG1zCiAgICAgICAgdGhpcy5fc3RhcnRUb3VjaFJlb3JkZXJUaW1lb3V0ID0gc2V0VGltZW91dCgoKSA9PiB7CiAgICAgICAgICB0aGlzLl9vblRyYWNrU3RhcnQoewogICAgICAgICAgICBkZXRhaWw6IHsKICAgICAgICAgICAgICB4OiBlLnRvdWNoZXNbMF0uY2xpZW50WCwKICAgICAgICAgICAgICB5OiBlLnRvdWNoZXNbMF0uY2xpZW50WQogICAgICAgICAgICB9CiAgICAgICAgICB9KTsKICAgICAgICB9LCAxMDApOwogICAgICB9CgogICAgICBfb25Ub3VjaE1vdmUoZSkgewogICAgICAgIGlmICh0aGlzLl9kcmFnZ2VkQ29sdW1uKSB7CiAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7CiAgICAgICAgfQogICAgICAgIGNsZWFyVGltZW91dCh0aGlzLl9zdGFydFRvdWNoUmVvcmRlclRpbWVvdXQpOwogICAgICB9CgogICAgICBfb25Ub3VjaEVuZCgpIHsKICAgICAgICBjbGVhclRpbWVvdXQodGhpcy5fc3RhcnRUb3VjaFJlb3JkZXJUaW1lb3V0KTsKICAgICAgICB0aGlzLl9vblRyYWNrRW5kKCk7CiAgICAgIH0KCiAgICAgIF9vblRyYWNrRXZlbnQoZSkgewogICAgICAgIGlmIChlLmRldGFpbC5zdGF0ZSA9PT0gJ3N0YXJ0JykgewogICAgICAgICAgY29uc3QgcGF0aCA9IGUuY29tcG9zZWRQYXRoKCk7CiAgICAgICAgICBjb25zdCBoZWFkZXJDZWxsID0gcGF0aFtwYXRoLmluZGV4T2YodGhpcy4kLmhlYWRlcikgLSAyXTsKICAgICAgICAgIGlmICghaGVhZGVyQ2VsbCB8fCAhaGVhZGVyQ2VsbC5fY29udGVudCkgewogICAgICAgICAgICAvLyBOb3QgYSBoZWFkZXIgY29sdW1uCiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICBjb25zdCBhY3RpdmVFbGVtZW50ID0gdGhpcy5nZXRSb290Tm9kZSgpLmFjdGl2ZUVsZW1lbnQ7CiAgICAgICAgICBpZiAoaGVhZGVyQ2VsbC5fY29udGVudC5jb250YWlucyh0aGlzLmdldFJvb3ROb2RlKCkuYWN0aXZlRWxlbWVudCkKICAgICAgICAgICAgICAmJiAoIXRoaXMuX2llIHx8ICF0aGlzLl9pc0ZvY3VzYWJsZShhY3RpdmVFbGVtZW50KSkpIHsKICAgICAgICAgICAgLy8gU29tZXRoaW5nIHdhcyBmb2N1c2VkIGluc2lkZSB0aGUgY2VsbAogICAgICAgICAgICByZXR1cm47CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKHRoaXMuJC5zY3JvbGxlci5oYXNBdHRyaWJ1dGUoJ2NvbHVtbi1yZXNpemluZycpKSB7CiAgICAgICAgICAgIC8vIFJlc2l6aW5nIGlzIGluIHByb2dyZXNzCiAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgIH0KCiAgICAgICAgICBpZiAoIXRoaXMuX3RvdWNoRGV2aWNlKSB7CiAgICAgICAgICAgIC8vIE5vdCBhIHRvdWNoIGRldmljZQogICAgICAgICAgICB0aGlzLl9vblRyYWNrU3RhcnQoZSk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIGlmIChlLmRldGFpbC5zdGF0ZSA9PT0gJ3RyYWNrJykgewogICAgICAgICAgdGhpcy5fb25UcmFjayhlKTsKICAgICAgICB9IGVsc2UgaWYgKGUuZGV0YWlsLnN0YXRlID09PSAnZW5kJykgewogICAgICAgICAgdGhpcy5fb25UcmFja0VuZChlKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9vblRyYWNrU3RhcnQoZSkgewogICAgICAgIGlmICghdGhpcy5jb2x1bW5SZW9yZGVyaW5nQWxsb3dlZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgLy8gQ2FuY2VsIHJlb3JkZXJpbmcgaWYgdGhlcmUgYXJlIGRyYWdnYWJsZSBub2RlcyBvbiB0aGUgZXZlbnQgcGF0aAogICAgICAgIGNvbnN0IHBhdGggPSBlLnBhdGggfHwgZG9tKGUpLnBhdGg7CiAgICAgICAgaWYgKHBhdGggJiYgcGF0aC5maWx0ZXIobm9kZSA9PiBub2RlLmhhc0F0dHJpYnV0ZSAmJiBub2RlLmhhc0F0dHJpYnV0ZSgnZHJhZ2dhYmxlJykpWzBdKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBjb25zdCBoZWFkZXJDZWxsID0gdGhpcy5fY2VsbEZyb21Qb2ludChlLmRldGFpbC54LCBlLmRldGFpbC55KTsKICAgICAgICBpZiAoIWhlYWRlckNlbGwgfHwgaGVhZGVyQ2VsbC5nZXRBdHRyaWJ1dGUoJ3BhcnQnKS5pbmRleE9mKCdoZWFkZXItY2VsbCcpID09PSAtMSkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdyZW9yZGVyaW5nJywgdHJ1ZSwgdGhpcyk7CiAgICAgICAgdGhpcy5fZHJhZ2dlZENvbHVtbiA9IGhlYWRlckNlbGwuX2NvbHVtbjsKICAgICAgICB3aGlsZSAodGhpcy5fZHJhZ2dlZENvbHVtbi5wYXJlbnRFbGVtZW50LmNoaWxkRWxlbWVudENvdW50ID09PSAxKSB7CiAgICAgICAgICAvLyBUaGlzIGlzIHRoZSBvbmx5IGNvbHVtbiBpbiB0aGUgZ3JvdXAsIGRyYWcgdGhlIHdob2xlIGdyb3VwIGluc3RlYWQKICAgICAgICAgIHRoaXMuX2RyYWdnZWRDb2x1bW4gPSB0aGlzLl9kcmFnZ2VkQ29sdW1uLnBhcmVudEVsZW1lbnQ7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3NldFNpYmxpbmdzUmVvcmRlclN0YXR1cyh0aGlzLl9kcmFnZ2VkQ29sdW1uLCAnYWxsb3dlZCcpOwogICAgICAgIHRoaXMuX2RyYWdnZWRDb2x1bW4uX3Jlb3JkZXJTdGF0dXMgPSAnZHJhZ2dpbmcnOwoKICAgICAgICB0aGlzLl91cGRhdGVHaG9zdChoZWFkZXJDZWxsKTsKICAgICAgICB0aGlzLl9yZW9yZGVyR2hvc3Quc3R5bGUudmlzaWJpbGl0eSA9ICd2aXNpYmxlJzsKICAgICAgICB0aGlzLl91cGRhdGVHaG9zdFBvc2l0aW9uKGUuZGV0YWlsLngsIHRoaXMuX3RvdWNoRGV2aWNlID8gZS5kZXRhaWwueSAtIDUwIDogZS5kZXRhaWwueSk7CiAgICAgICAgdGhpcy5fYXV0b1Njcm9sbGVyKCk7CiAgICAgIH0KCiAgICAgIF9vblRyYWNrKGUpIHsKICAgICAgICBpZiAoIXRoaXMuX2RyYWdnZWRDb2x1bW4pIHsKICAgICAgICAgIC8vIFJlb3JkZXJpbmcgZGlkbuKAmXQgc3RhcnQuIFNraXAgdGhpcyBldmVudC4KICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIGNvbnN0IHRhcmdldENlbGwgPSB0aGlzLl9jZWxsRnJvbVBvaW50KGUuZGV0YWlsLngsIGUuZGV0YWlsLnkpOwogICAgICAgIGlmICghdGFyZ2V0Q2VsbCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgY29uc3QgdGFyZ2V0Q29sdW1uID0gdGhpcy5fZ2V0VGFyZ2V0Q29sdW1uKHRhcmdldENlbGwsIHRoaXMuX2RyYWdnZWRDb2x1bW4pOwogICAgICAgIGlmICh0aGlzLl9pc1N3YXBBbGxvd2VkKHRoaXMuX2RyYWdnZWRDb2x1bW4sIHRhcmdldENvbHVtbikgJiYKICAgICAgICAgIHRoaXMuX2lzU3dhcHBhYmxlQnlQb3NpdGlvbih0YXJnZXRDb2x1bW4sIGUuZGV0YWlsLngpKSB7CiAgICAgICAgICB0aGlzLl9zd2FwQ29sdW1uT3JkZXJzKHRoaXMuX2RyYWdnZWRDb2x1bW4sIHRhcmdldENvbHVtbik7CiAgICAgICAgfQoKICAgICAgICB0aGlzLl91cGRhdGVHaG9zdFBvc2l0aW9uKGUuZGV0YWlsLngsIHRoaXMuX3RvdWNoRGV2aWNlID8gZS5kZXRhaWwueSAtIDUwIDogZS5kZXRhaWwueSk7CiAgICAgICAgdGhpcy5fbGFzdERyYWdDbGllbnRYID0gZS5kZXRhaWwueDsKICAgICAgfQoKICAgICAgX29uVHJhY2tFbmQoKSB7CiAgICAgICAgaWYgKCF0aGlzLl9kcmFnZ2VkQ29sdW1uKSB7CiAgICAgICAgICAvLyBSZW9yZGVyaW5nIGRpZG7igJl0IHN0YXJ0LiBTa2lwIHRoaXMgZXZlbnQuCiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ3Jlb3JkZXJpbmcnLCBmYWxzZSwgdGhpcyk7CiAgICAgICAgdGhpcy5fZHJhZ2dlZENvbHVtbi5fcmVvcmRlclN0YXR1cyA9ICcnOwogICAgICAgIHRoaXMuX3NldFNpYmxpbmdzUmVvcmRlclN0YXR1cyh0aGlzLl9kcmFnZ2VkQ29sdW1uLCAnJyk7CiAgICAgICAgdGhpcy5fZHJhZ2dlZENvbHVtbiA9IG51bGw7CiAgICAgICAgdGhpcy5fbGFzdERyYWdDbGllbnRYID0gbnVsbDsKICAgICAgICB0aGlzLl9yZW9yZGVyR2hvc3Quc3R5bGUudmlzaWJpbGl0eSA9ICdoaWRkZW4nOwoKICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjb2x1bW4tcmVvcmRlcicsIHtkZXRhaWw6IHsKICAgICAgICAgIGNvbHVtbnM6IHRoaXMuX2dldENvbHVtbnNJbk9yZGVyKCkKICAgICAgICB9fSkpOwogICAgICB9CgogICAgICBfZ2V0Q29sdW1uc0luT3JkZXIoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX2NvbHVtblRyZWUuc2xpY2UoMCkucG9wKCkKICAgICAgICAgIC5maWx0ZXIoYyA9PiAhYy5oaWRkZW4pCiAgICAgICAgICAuc29ydCgoYiwgYSkgPT4gKGIuX29yZGVyIC0gYS5fb3JkZXIpKTsKICAgICAgfQoKICAgICAgX2NlbGxGcm9tUG9pbnQoeCwgeSkgewogICAgICAgIHggPSB4IHx8IDA7CiAgICAgICAgeSA9IHkgfHwgMDsKICAgICAgICBpZiAoIXRoaXMuX2RyYWdnZWRDb2x1bW4pIHsKICAgICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnbm8tY29udGVudC1wb2ludGVyLWV2ZW50cycsIHRydWUsIHRoaXMuJC5zY3JvbGxlcik7CiAgICAgICAgfQogICAgICAgIGxldCBjZWxsOwogICAgICAgIGlmICh1c2VTaGFkb3cpIHsKICAgICAgICAgIGNlbGwgPSB0aGlzLnNoYWRvd1Jvb3QuZWxlbWVudEZyb21Qb2ludCh4LCB5KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY2VsbCA9IGRvY3VtZW50LmVsZW1lbnRGcm9tUG9pbnQoeCwgeSk7CgogICAgICAgICAgLy8gV29ya2Fyb3VuZCBhIEZGNTggYnVnCiAgICAgICAgICBpZiAoY2VsbC5sb2NhbE5hbWUgPT09ICd2YWFkaW4tZ3JpZC1jZWxsLWNvbnRlbnQnKSB7CiAgICAgICAgICAgIGNlbGwgPSBjZWxsLmFzc2lnbmVkU2xvdC5wYXJlbnROb2RlOwogICAgICAgICAgfQoKICAgICAgICB9CiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCduby1jb250ZW50LXBvaW50ZXItZXZlbnRzJywgZmFsc2UsIHRoaXMuJC5zY3JvbGxlcik7CgogICAgICAgIC8vIE1ha2Ugc3VyZSB0aGUgZWxlbWVudCBpcyBhY3R1YWxseSBhIGNlbGwKICAgICAgICBpZiAoY2VsbCAmJiBjZWxsLl9jb2x1bW4pIHsKICAgICAgICAgIHJldHVybiBjZWxsOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3VwZGF0ZUdob3N0UG9zaXRpb24oZXZlbnRDbGllbnRYLCBldmVudENsaWVudFkpIHsKICAgICAgICBjb25zdCBnaG9zdFJlY3QgPSB0aGlzLl9yZW9yZGVyR2hvc3QuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCk7CiAgICAgICAgLy8gLy8gVGhpcyBpcyB3aGVyZSB3ZSB3YW50IHRvIHBvc2l0aW9uIHRoZSBnaG9zdAogICAgICAgIGNvbnN0IHRhcmdldExlZnQgPSBldmVudENsaWVudFggLSBnaG9zdFJlY3Qud2lkdGggLyAyOwogICAgICAgIGNvbnN0IHRhcmdldFRvcCA9IGV2ZW50Q2xpZW50WSAtIGdob3N0UmVjdC5oZWlnaHQgLyAyOwogICAgICAgIC8vIEN1cnJlbnQgcG9zaXRpb24KICAgICAgICBjb25zdCBfbGVmdCA9IHBhcnNlSW50KHRoaXMuX3Jlb3JkZXJHaG9zdC5fbGVmdCB8fCAwKTsKICAgICAgICBjb25zdCBfdG9wID0gcGFyc2VJbnQodGhpcy5fcmVvcmRlckdob3N0Ll90b3AgfHwgMCk7CiAgICAgICAgLy8gUmVwb3NpdGlvbiB0aGUgZ2hvc3QKICAgICAgICB0aGlzLl9yZW9yZGVyR2hvc3QuX2xlZnQgPSBfbGVmdCAtIChnaG9zdFJlY3QubGVmdCAtIHRhcmdldExlZnQpOwogICAgICAgIHRoaXMuX3Jlb3JkZXJHaG9zdC5fdG9wID0gX3RvcCAtIChnaG9zdFJlY3QudG9wIC0gdGFyZ2V0VG9wKTsKICAgICAgICB0aGlzLl9yZW9yZGVyR2hvc3Quc3R5bGUudHJhbnNmb3JtID0gYHRyYW5zbGF0ZSgke3RoaXMuX3Jlb3JkZXJHaG9zdC5fbGVmdH1weCwgJHt0aGlzLl9yZW9yZGVyR2hvc3QuX3RvcH1weClgOwogICAgICB9CgogICAgICBfZ2V0SW5uZXJUZXh0KGUpIHsKICAgICAgICBpZiAoZS5sb2NhbE5hbWUpIHsKICAgICAgICAgIC8vIEN1c3RvbSBpbXBsZW1lbnRhdGlvbiBuZWVkZWQgc2luY2UgSUUxMSBkb2Vzbid0IHJlc3BlY3QgdGhlIHNwZWMgaW4gY2FzZSBvZiBoaWRkZW4gZWxlbWVudHMKICAgICAgICAgIGlmIChnZXRDb21wdXRlZFN0eWxlKGUpLmRpc3BsYXkgPT09ICdub25lJykgewogICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXR1cm4gQXJyYXkuZnJvbShlLmNoaWxkTm9kZXMpLm1hcChuID0+IHRoaXMuX2dldElubmVyVGV4dChuKSkuam9pbignJyk7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJldHVybiBlLnRleHRDb250ZW50OwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3VwZGF0ZUdob3N0KGNlbGwpIHsKICAgICAgICBjb25zdCBnaG9zdCA9IHRoaXMuX3Jlb3JkZXJHaG9zdDsKICAgICAgICBnaG9zdC50ZXh0Q29udGVudCA9IHRoaXMuX2dldElubmVyVGV4dChjZWxsLl9jb250ZW50KTsKICAgICAgICBjb25zdCBzdHlsZSA9IHdpbmRvdy5nZXRDb21wdXRlZFN0eWxlKGNlbGwpOwogICAgICAgIFsnYm94U2l6aW5nJywgJ2Rpc3BsYXknLCAnd2lkdGgnLCAnaGVpZ2h0JywgJ2JhY2tncm91bmQnLCAnYWxpZ25JdGVtcycsICdwYWRkaW5nJywgJ2JvcmRlcicsICdmbGV4LWRpcmVjdGlvbicsICdvdmVyZmxvdyddCiAgICAgICAgICAuZm9yRWFjaChwcm9wZXJ0eU5hbWUgPT4gZ2hvc3Quc3R5bGVbcHJvcGVydHlOYW1lXSA9IHN0eWxlW3Byb3BlcnR5TmFtZV0pOwogICAgICAgIHJldHVybiBnaG9zdDsKICAgICAgfQoKICAgICAgX3VwZGF0ZU9yZGVycyhjb2x1bW5UcmVlLCBzcGxpY2VzKSB7CiAgICAgICAgaWYgKGNvbHVtblRyZWUgPT09IHVuZGVmaW5lZCB8fCBzcGxpY2VzID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIC8vIFJlc2V0IGFsbCBjb2x1bW4gb3JkZXJzCiAgICAgICAgY29sdW1uVHJlZVswXS5mb3JFYWNoKChjb2x1bW4sIGluZGV4KSA9PiBjb2x1bW4uX29yZGVyID0gMCk7CiAgICAgICAgLy8gU2V0IG9yZGVyIG51bWJlcnMgdG8gdG9wLWxldmVsIGNvbHVtbnMKICAgICAgICBjb2x1bW5UcmVlWzBdLmZvckVhY2goKGNvbHVtbiwgaW5kZXgpID0+IGNvbHVtbi5fb3JkZXIgPSAoaW5kZXggKyAxKSAqIHRoaXMuX29yZGVyQmFzZVNjb3BlKTsKICAgICAgfQoKICAgICAgX3NldFNpYmxpbmdzUmVvcmRlclN0YXR1cyhjb2x1bW4sIHN0YXR1cykgewogICAgICAgIEFycmF5LmZyb20oY29sdW1uLnBhcmVudE5vZGUuY2hpbGRyZW4pCiAgICAgICAgICAuZmlsdGVyKGNoaWxkID0+IC9jb2x1bW4vLnRlc3QoY2hpbGQubG9jYWxOYW1lKSAmJiB0aGlzLl9pc1N3YXBBbGxvd2VkKGNoaWxkLCBjb2x1bW4pKQogICAgICAgICAgLmZvckVhY2goc2libGluZyA9PiBzaWJsaW5nLl9yZW9yZGVyU3RhdHVzID0gc3RhdHVzKTsKICAgICAgfQoKICAgICAgX2F1dG9TY3JvbGxlcigpIHsKICAgICAgICBpZiAodGhpcy5fbGFzdERyYWdDbGllbnRYKSB7CiAgICAgICAgICBjb25zdCByaWdodERpZmYgPSB0aGlzLl9sYXN0RHJhZ0NsaWVudFggLSB0aGlzLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLnJpZ2h0ICsgNTA7CiAgICAgICAgICBjb25zdCBsZWZ0RGlmZiA9IHRoaXMuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkubGVmdCAtIHRoaXMuX2xhc3REcmFnQ2xpZW50WCArIDUwOwoKICAgICAgICAgIGlmIChyaWdodERpZmYgPiAwKSB7CiAgICAgICAgICAgIHRoaXMuJC50YWJsZS5zY3JvbGxMZWZ0ICs9IHJpZ2h0RGlmZiAvIDEwOwogICAgICAgICAgfSBlbHNlIGlmIChsZWZ0RGlmZiA+IDApIHsKICAgICAgICAgICAgdGhpcy4kLnRhYmxlLnNjcm9sbExlZnQgLT0gbGVmdERpZmYgLyAxMDsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMuX3Njcm9sbEhhbmRsZXIoKTsKICAgICAgICB9CgogICAgICAgIGlmICh0aGlzLl9kcmFnZ2VkQ29sdW1uKSB7CiAgICAgICAgICB0aGlzLmFzeW5jKHRoaXMuX2F1dG9TY3JvbGxlciwgMTApOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2lzU3dhcEFsbG93ZWQoY29sdW1uMSwgY29sdW1uMikgewogICAgICAgIGlmIChjb2x1bW4xICYmIGNvbHVtbjIpIHsKICAgICAgICAgIGNvbnN0IGRpZmZlcmVudENvbHVtbnMgPSBjb2x1bW4xICE9PSBjb2x1bW4yOwogICAgICAgICAgY29uc3Qgc2FtZVBhcmVudCA9IGNvbHVtbjEucGFyZW50RWxlbWVudCA9PT0gY29sdW1uMi5wYXJlbnRFbGVtZW50OwogICAgICAgICAgY29uc3Qgc2FtZUZyb3plbiA9IGNvbHVtbjEuZnJvemVuID09PSBjb2x1bW4yLmZyb3plbjsKICAgICAgICAgIHJldHVybiBkaWZmZXJlbnRDb2x1bW5zICYmIHNhbWVQYXJlbnQgJiYgc2FtZUZyb3plbjsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9pc1N3YXBwYWJsZUJ5UG9zaXRpb24odGFyZ2V0Q29sdW1uLCBjbGllbnRYKSB7CiAgICAgICAgY29uc3QgdGFyZ2V0Q2VsbCA9CiAgICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5oZWFkZXIucXVlcnlTZWxlY3RvckFsbCgndHI6bm90KFtoaWRkZW5dKSBbcGFydH49ImNlbGwiXScpKS5maWx0ZXIoY2VsbCA9PiB0YXJnZXRDb2x1bW4uY29udGFpbnMoY2VsbC5fY29sdW1uKSlbMF07CiAgICAgICAgY29uc3Qgc291cmNlQ2VsbFJlY3QgPSB0aGlzLiQuaGVhZGVyLnF1ZXJ5U2VsZWN0b3IoJ3RyOm5vdChbaGlkZGVuXSkgW3Jlb3JkZXItc3RhdHVzPWRyYWdnaW5nXScpLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIGNvbnN0IHRhcmdldFJlY3QgPSB0YXJnZXRDZWxsLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpOwogICAgICAgIGlmICh0YXJnZXRSZWN0LmxlZnQgPiBzb3VyY2VDZWxsUmVjdC5sZWZ0KSB7CiAgICAgICAgICByZXR1cm4gY2xpZW50WCA+IHRhcmdldFJlY3QucmlnaHQgLSBzb3VyY2VDZWxsUmVjdC53aWR0aDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIGNsaWVudFggPCB0YXJnZXRSZWN0LmxlZnQgKyBzb3VyY2VDZWxsUmVjdC53aWR0aDsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9zd2FwQ29sdW1uT3JkZXJzKGNvbHVtbjEsIGNvbHVtbjIpIHsKICAgICAgICBjb25zdCBfb3JkZXIgPSBjb2x1bW4xLl9vcmRlcjsKICAgICAgICBjb2x1bW4xLl9vcmRlciA9IGNvbHVtbjIuX29yZGVyOwogICAgICAgIGNvbHVtbjIuX29yZGVyID0gX29yZGVyOwogICAgICAgIHRoaXMuX3VwZGF0ZUxhc3RGcm96ZW4oKTsKICAgICAgICB0aGlzLl91cGRhdGVGaXJzdEFuZExhc3RDb2x1bW4oKTsKICAgICAgfQoKICAgICAgX2dldFRhcmdldENvbHVtbih0YXJnZXRDZWxsLCBkcmFnZ2VkQ29sdW1uKSB7CiAgICAgICAgaWYgKHRhcmdldENlbGwgJiYgZHJhZ2dlZENvbHVtbikgewogICAgICAgICAgbGV0IGNhbmRpZGF0ZSA9IHRhcmdldENlbGwuX2NvbHVtbjsKICAgICAgICAgIHdoaWxlIChjYW5kaWRhdGUucGFyZW50RWxlbWVudCAhPT0gZHJhZ2dlZENvbHVtbi5wYXJlbnRFbGVtZW50ICYmIGNhbmRpZGF0ZSAhPT0gdGhpcykgewogICAgICAgICAgICBjYW5kaWRhdGUgPSBjYW5kaWRhdGUucGFyZW50RWxlbWVudDsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChjYW5kaWRhdGUucGFyZW50RWxlbWVudCA9PT0gZHJhZ2dlZENvbHVtbi5wYXJlbnRFbGVtZW50KSB7CiAgICAgICAgICAgIHJldHVybiBjYW5kaWRhdGU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICByZXR1cm4gdGFyZ2V0Q2VsbC5fY29sdW1uOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEZpcmVkIHdoZW4gdGhlIGNvbHVtbnMgaW4gdGhlIGdyaWQgYXJlIHJlb3JkZXJlZC4KICAgICAgICoKICAgICAgICogQGV2ZW50IGNvbHVtbi1yZW9yZGVyCiAgICAgICAqIEBwYXJhbSB7T2JqZWN0fSBkZXRhaWwKICAgICAgICogQHBhcmFtIHtPYmplY3R9IGRldGFpbC5jb2x1bW5zIHRoZSBjb2x1bW5zIGluIHRoZSBuZXcgb3JkZXIKICAgICAgICovCiAgICB9OwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxOCBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KCiAgICAvKioKICAgICAqIEBwb2x5bWVyTWl4aW4KICAgICAqLwogICAgY29uc3QgQ29sdW1uQmFzZU1peGluID0gc3VwZXJDbGFzcyA9PiBjbGFzcyBDb2x1bW5CYXNlTWl4aW4gZXh0ZW5kcyBzdXBlckNsYXNzIHsKICAgICAgc3RhdGljIGdldCBwcm9wZXJ0aWVzKCkgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICAvKioKICAgICAgICAgICAqIFdoZW4gc2V0IHRvIHRydWUsIHRoZSBjb2x1bW4gaXMgdXNlci1yZXNpemFibGUuCiAgICAgICAgICAgKiBAZGVmYXVsdCBmYWxzZQogICAgICAgICAgICovCiAgICAgICAgICByZXNpemFibGU6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIGlmICh0aGlzLmxvY2FsTmFtZSA9PT0gJ3ZhYWRpbi1ncmlkLWNvbHVtbi1ncm91cCcpIHsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICB9CgogICAgICAgICAgICAgIGNvbnN0IHBhcmVudCA9IHRoaXMucGFyZW50Tm9kZTsKICAgICAgICAgICAgICBpZiAocGFyZW50ICYmIHBhcmVudC5sb2NhbE5hbWUgPT09ICd2YWFkaW4tZ3JpZC1jb2x1bW4tZ3JvdXAnKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gcGFyZW50LnJlc2l6YWJsZSB8fCBmYWxzZTsKICAgICAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfQogICAgICAgICAgfSwKCiAgICAgICAgICBfaGVhZGVyVGVtcGxhdGU6IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0CiAgICAgICAgICB9LAoKICAgICAgICAgIF9mb290ZXJUZW1wbGF0ZTogewogICAgICAgICAgICB0eXBlOiBPYmplY3QKICAgICAgICAgIH0sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBXaGVuIHRydWUsIHRoZSBjb2x1bW4gaXMgZnJvemVuLiBXaGVuIGEgY29sdW1uIGluc2lkZSBvZiBhIGNvbHVtbiBncm91cCBpcyBmcm96ZW4sCiAgICAgICAgICAgKiBhbGwgb2YgdGhlIHNpYmxpbmcgY29sdW1ucyBpbnNpZGUgdGhlIGdyb3VwIHdpbGwgZ2V0IGZyb3plbiBhbHNvLgogICAgICAgICAgICovCiAgICAgICAgICBmcm96ZW46IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IGZhbHNlCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogV2hlbiBzZXQgdG8gdHJ1ZSwgdGhlIGNlbGxzIGZvciB0aGlzIGNvbHVtbiBhcmUgaGlkZGVuLgogICAgICAgICAgICovCiAgICAgICAgICBoaWRkZW46IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbgogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIFRleHQgY29udGVudCB0byBkaXNwbGF5IGluIHRoZSBoZWFkZXIgY2VsbCBvZiB0aGUgY29sdW1uLgogICAgICAgICAgICovCiAgICAgICAgICBoZWFkZXI6IHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQWxpZ25zIHRoZSBjb2x1bW5zIGNlbGwgY29udGVudCBob3Jpem9udGFsbHkuCiAgICAgICAgICAgKiBTdXBwb3J0ZWQgdmFsdWVzOiAic3RhcnQiLCAiY2VudGVyIiBhbmQgImVuZCIuCiAgICAgICAgICAgKi8KICAgICAgICAgIHRleHRBbGlnbjogewogICAgICAgICAgICB0eXBlOiBTdHJpbmcKICAgICAgICAgIH0sCgogICAgICAgICAgX2xhc3RGcm96ZW46IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IGZhbHNlCiAgICAgICAgICB9LAoKICAgICAgICAgIF9vcmRlcjogTnVtYmVyLAoKICAgICAgICAgIF9yZW9yZGVyU3RhdHVzOiBCb29sZWFuLAoKICAgICAgICAgIF9lbXB0eUNlbGxzOiBBcnJheSwKCiAgICAgICAgICBfaGVhZGVyQ2VsbDogT2JqZWN0LAoKICAgICAgICAgIF9mb290ZXJDZWxsOiBPYmplY3QsCgogICAgICAgICAgX2dyaWQ6IE9iamVjdCwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEN1c3RvbSBmdW5jdGlvbiBmb3IgcmVuZGVyaW5nIHRoZSBoZWFkZXIgY29udGVudC4KICAgICAgICAgICAqIFJlY2VpdmVzIHR3byBhcmd1bWVudHM6CiAgICAgICAgICAgKgogICAgICAgICAgICogLSBgcm9vdGAgVGhlIGhlYWRlciBjZWxsIGNvbnRlbnQgRE9NIGVsZW1lbnQuIEFwcGVuZCB5b3VyIGNvbnRlbnQgdG8gaXQuCiAgICAgICAgICAgKiAtIGBjb2x1bW5gIFRoZSBgPHZhYWRpbi1ncmlkLWNvbHVtbj5gIGVsZW1lbnQuCiAgICAgICAgICAgKi8KICAgICAgICAgIGhlYWRlclJlbmRlcmVyOiBGdW5jdGlvbiwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEN1c3RvbSBmdW5jdGlvbiBmb3IgcmVuZGVyaW5nIHRoZSBmb290ZXIgY29udGVudC4KICAgICAgICAgICAqIFJlY2VpdmVzIHR3byBhcmd1bWVudHM6CiAgICAgICAgICAgKgogICAgICAgICAgICogLSBgcm9vdGAgVGhlIGZvb3RlciBjZWxsIGNvbnRlbnQgRE9NIGVsZW1lbnQuIEFwcGVuZCB5b3VyIGNvbnRlbnQgdG8gaXQuCiAgICAgICAgICAgKiAtIGBjb2x1bW5gIFRoZSBgPHZhYWRpbi1ncmlkLWNvbHVtbj5gIGVsZW1lbnQuCiAgICAgICAgICAgKi8KICAgICAgICAgIGZvb3RlclJlbmRlcmVyOiBGdW5jdGlvbgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZXJzKCkgewogICAgICAgIHJldHVybiBbCiAgICAgICAgICAnX3dpZHRoQ2hhbmdlZCh3aWR0aCwgX2hlYWRlckNlbGwsIF9mb290ZXJDZWxsLCBfY2VsbHMuKiknLAogICAgICAgICAgJ19mcm96ZW5DaGFuZ2VkKGZyb3plbiwgX2hlYWRlckNlbGwsIF9mb290ZXJDZWxsLCBfY2VsbHMuKiknLAogICAgICAgICAgJ19mbGV4R3Jvd0NoYW5nZWQoZmxleEdyb3csIF9oZWFkZXJDZWxsLCBfZm9vdGVyQ2VsbCwgX2NlbGxzLiopJywKICAgICAgICAgICdfcGF0aE9ySGVhZGVyQ2hhbmdlZChwYXRoLCBoZWFkZXIsIF9oZWFkZXJDZWxsLCBfZm9vdGVyQ2VsbCwgX2NlbGxzLiosIHJlbmRlcmVyLCBoZWFkZXJSZW5kZXJlciwgX2JvZHlUZW1wbGF0ZSwgX2hlYWRlclRlbXBsYXRlKScsCiAgICAgICAgICAnX3RleHRBbGlnbkNoYW5nZWQodGV4dEFsaWduLCBfY2VsbHMuKiwgX2hlYWRlckNlbGwsIF9mb290ZXJDZWxsKScsCiAgICAgICAgICAnX29yZGVyQ2hhbmdlZChfb3JkZXIsIF9oZWFkZXJDZWxsLCBfZm9vdGVyQ2VsbCwgX2NlbGxzLiopJywKICAgICAgICAgICdfbGFzdEZyb3plbkNoYW5nZWQoX2xhc3RGcm96ZW4pJywKICAgICAgICAgICdfc2V0Qm9keVRlbXBsYXRlT3JSZW5kZXJlcihfYm9keVRlbXBsYXRlLCByZW5kZXJlciwgX2NlbGxzLCBfY2VsbHMuKiknLAogICAgICAgICAgJ19zZXRIZWFkZXJUZW1wbGF0ZU9yUmVuZGVyZXIoX2hlYWRlclRlbXBsYXRlLCBoZWFkZXJSZW5kZXJlciwgX2hlYWRlckNlbGwpJywKICAgICAgICAgICdfc2V0Rm9vdGVyVGVtcGxhdGVPclJlbmRlcmVyKF9mb290ZXJUZW1wbGF0ZSwgZm9vdGVyUmVuZGVyZXIsIF9mb290ZXJDZWxsKScsCiAgICAgICAgICAnX3Jlc2l6YWJsZUNoYW5nZWQocmVzaXphYmxlLCBfaGVhZGVyQ2VsbCknLAogICAgICAgICAgJ19yZW9yZGVyU3RhdHVzQ2hhbmdlZChfcmVvcmRlclN0YXR1cywgX2hlYWRlckNlbGwsIF9mb290ZXJDZWxsLCBfY2VsbHMuKiknLAogICAgICAgICAgJ19oaWRkZW5DaGFuZ2VkKGhpZGRlbiwgX2hlYWRlckNlbGwsIF9mb290ZXJDZWxsLCBfY2VsbHMuKiknCiAgICAgICAgXTsKICAgICAgfQoKICAgICAgLyoqIEBwcm90ZWN0ZWQgKi8KICAgICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsKCiAgICAgICAgdGhpcy5fYm9keVRlbXBsYXRlICYmICh0aGlzLl9ib2R5VGVtcGxhdGUudGVtcGxhdGl6ZXIuX2dyaWQgPSB0aGlzLl9ncmlkKTsKICAgICAgICB0aGlzLl9oZWFkZXJUZW1wbGF0ZSAmJiAodGhpcy5faGVhZGVyVGVtcGxhdGUudGVtcGxhdGl6ZXIuX2dyaWQgPSB0aGlzLl9ncmlkKTsKICAgICAgICB0aGlzLl9mb290ZXJUZW1wbGF0ZSAmJiAodGhpcy5fZm9vdGVyVGVtcGxhdGUudGVtcGxhdGl6ZXIuX2dyaWQgPSB0aGlzLl9ncmlkKTsKCiAgICAgICAgdGhpcy5fdGVtcGxhdGVPYnNlcnZlci5mbHVzaCgpOwogICAgICAgIGlmICghdGhpcy5fYm9keVRlbXBsYXRlKSB7CiAgICAgICAgICAvLyBUaGUgb2JzZXJ2ZXIgbWlnaHQgbm90IGhhdmUgdHJpZ2dlcmVkIGlmIHRoZSB0YWcgaXMgZW1wdHkuIFJ1biBtYW51YWxseS4KICAgICAgICAgIHRoaXMuX3RlbXBsYXRlT2JzZXJ2ZXIuY2FsbGJhY2soKTsKICAgICAgICB9CgogICAgICAgIHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICB0aGlzLl9hbGxDZWxscy5mb3JFYWNoKGNlbGwgPT4gewogICAgICAgICAgICBpZiAoIWNlbGwuX2NvbnRlbnQucGFyZW50Tm9kZSkgewogICAgICAgICAgICAgIHRoaXMuX2dyaWQgJiYgdGhpcy5fZ3JpZC5hcHBlbmRDaGlsZChjZWxsLl9jb250ZW50KTsKICAgICAgICAgICAgfQogICAgICAgICAgfSk7CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIC8qKiBAcHJvdGVjdGVkICovCiAgICAgIGRpc2Nvbm5lY3RlZENhbGxiYWNrKCkgewogICAgICAgIHN1cGVyLmRpc2Nvbm5lY3RlZENhbGxiYWNrKCk7CgogICAgICAgIHJlcXVlc3RBbmltYXRpb25GcmFtZSgoKSA9PiB7CiAgICAgICAgICBpZiAoIXRoaXMuX2ZpbmRIb3N0R3JpZCgpKSB7CiAgICAgICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiB7CiAgICAgICAgICAgICAgaWYgKGNlbGwuX2NvbnRlbnQucGFyZW50Tm9kZSkgewogICAgICAgICAgICAgICAgY2VsbC5fY29udGVudC5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKGNlbGwuX2NvbnRlbnQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIHRoaXMuX2dyaWRWYWx1ZSA9IHVuZGVmaW5lZDsKICAgICAgfQoKICAgICAgX2ZpbmRIb3N0R3JpZCgpIHsKICAgICAgICBsZXQgZWwgPSB0aGlzOwogICAgICAgIC8vIEN1c3RvbSBlbGVtZW50cyBleHRlbmRpbmcgZ3JpZCBtdXN0IGhhdmUgYSBzcGVjaWZpYyBsb2NhbE5hbWUKICAgICAgICB3aGlsZSAoZWwgJiYgIS9edmFhZGluLipncmlkKC1wcm8pPyQvLnRlc3QoZWwubG9jYWxOYW1lKSkgewogICAgICAgICAgZWwgPSBlbC5hc3NpZ25lZFNsb3QgPyBlbC5hc3NpZ25lZFNsb3QucGFyZW50Tm9kZSA6IGVsLnBhcmVudE5vZGU7CiAgICAgICAgfQogICAgICAgIHJldHVybiBlbCB8fCB1bmRlZmluZWQ7CiAgICAgIH0KCiAgICAgIGdldCBfZ3JpZCgpIHsKICAgICAgICBpZiAoIXRoaXMuX2dyaWRWYWx1ZSkgewogICAgICAgICAgdGhpcy5fZ3JpZFZhbHVlID0gdGhpcy5fZmluZEhvc3RHcmlkKCk7CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLl9ncmlkVmFsdWU7CiAgICAgIH0KCiAgICAgIGdldCBfYWxsQ2VsbHMoKSB7CiAgICAgICAgcmV0dXJuIFtdCiAgICAgICAgICAuY29uY2F0KHRoaXMuX2NlbGxzIHx8IFtdKQogICAgICAgICAgLmNvbmNhdCh0aGlzLl9lbXB0eUNlbGxzIHx8IFtdKQogICAgICAgICAgLmNvbmNhdCh0aGlzLl9oZWFkZXJDZWxsKQogICAgICAgICAgLmNvbmNhdCh0aGlzLl9mb290ZXJDZWxsKQogICAgICAgICAgLmZpbHRlcihjZWxsID0+IGNlbGwpOwogICAgICB9CgogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICBzdXBlcigpOwoKICAgICAgICB0aGlzLl90ZW1wbGF0ZU9ic2VydmVyID0gbmV3IEZsYXR0ZW5lZE5vZGVzT2JzZXJ2ZXIodGhpcywgaW5mbyA9PiB7CiAgICAgICAgICB0aGlzLl9oZWFkZXJUZW1wbGF0ZSA9IHRoaXMuX3ByZXBhcmVIZWFkZXJUZW1wbGF0ZSgpOwogICAgICAgICAgdGhpcy5fZm9vdGVyVGVtcGxhdGUgPSB0aGlzLl9wcmVwYXJlRm9vdGVyVGVtcGxhdGUoKTsKICAgICAgICAgIHRoaXMuX2JvZHlUZW1wbGF0ZSA9IHRoaXMuX3ByZXBhcmVCb2R5VGVtcGxhdGUoKTsKICAgICAgICB9KTsKICAgICAgfQoKICAgICAgX3ByZXBhcmVIZWFkZXJUZW1wbGF0ZSgpIHsKICAgICAgICByZXR1cm4gdGhpcy5fcHJlcGFyZVRlbXBsYXRpemVyKHRoaXMuX2ZpbmRUZW1wbGF0ZSh0cnVlKSB8fCBudWxsLCB7fSk7CiAgICAgIH0KCiAgICAgIF9wcmVwYXJlRm9vdGVyVGVtcGxhdGUoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX3ByZXBhcmVUZW1wbGF0aXplcih0aGlzLl9maW5kVGVtcGxhdGUoZmFsc2UsIHRydWUpIHx8IG51bGwsIHt9KTsKICAgICAgfQoKICAgICAgX3ByZXBhcmVCb2R5VGVtcGxhdGUoKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuX3ByZXBhcmVUZW1wbGF0aXplcih0aGlzLl9maW5kVGVtcGxhdGUoKSB8fCBudWxsKTsKICAgICAgfQoKICAgICAgX3ByZXBhcmVUZW1wbGF0aXplcih0ZW1wbGF0ZSwgaW5zdGFuY2VQcm9wcykgewogICAgICAgIGlmICh0ZW1wbGF0ZSAmJiAhdGVtcGxhdGUudGVtcGxhdGl6ZXIpIHsKICAgICAgICAgIGNvbnN0IHRlbXBsYXRpemVyID0gbmV3IEdyaWRUZW1wbGF0aXplcigpOwogICAgICAgICAgdGVtcGxhdGl6ZXIuX2dyaWQgPSB0aGlzLl9ncmlkOwogICAgICAgICAgdGVtcGxhdGl6ZXIuZGF0YUhvc3QgPSB0aGlzLmRhdGFIb3N0OwogICAgICAgICAgdGVtcGxhdGl6ZXIuX2luc3RhbmNlUHJvcHMgPSBpbnN0YW5jZVByb3BzIHx8IHRlbXBsYXRpemVyLl9pbnN0YW5jZVByb3BzOwogICAgICAgICAgdGVtcGxhdGl6ZXIudGVtcGxhdGUgPSB0ZW1wbGF0ZTsKICAgICAgICAgIHRlbXBsYXRlLnRlbXBsYXRpemVyID0gdGVtcGxhdGl6ZXI7CiAgICAgICAgfQoKICAgICAgICByZXR1cm4gdGVtcGxhdGU7CiAgICAgIH0KCiAgICAgIF9yZW5kZXJIZWFkZXJBbmRGb290ZXIoKSB7CiAgICAgICAgaWYgKHRoaXMuaGVhZGVyUmVuZGVyZXIgJiYgdGhpcy5faGVhZGVyQ2VsbCkgewogICAgICAgICAgdGhpcy5fX3J1blJlbmRlcmVyKHRoaXMuaGVhZGVyUmVuZGVyZXIsIHRoaXMuX2hlYWRlckNlbGwpOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5mb290ZXJSZW5kZXJlciAmJiB0aGlzLl9mb290ZXJDZWxsKSB7CiAgICAgICAgICB0aGlzLl9fcnVuUmVuZGVyZXIodGhpcy5mb290ZXJSZW5kZXJlciwgdGhpcy5fZm9vdGVyQ2VsbCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfX3J1blJlbmRlcmVyKHJlbmRlcmVyLCBjZWxsLCByb3dEYXRhKSB7CiAgICAgICAgY29uc3QgYXJncyA9IFtjZWxsLl9jb250ZW50LCB0aGlzXTsKICAgICAgICBpZiAocm93RGF0YSAmJiByb3dEYXRhLml0ZW0pIHsKICAgICAgICAgIGFyZ3MucHVzaChyb3dEYXRhKTsKICAgICAgICB9CiAgICAgICAgcmVuZGVyZXIuYXBwbHkodGhpcywgYXJncyk7CiAgICAgIH0KCiAgICAgIF9fc2V0Q29sdW1uVGVtcGxhdGVPclJlbmRlcmVyKHRlbXBsYXRlLCByZW5kZXJlciwgY2VsbHMpIHsKICAgICAgICBpZiAodGVtcGxhdGUgJiYgcmVuZGVyZXIpIHsKICAgICAgICAgIHRocm93IG5ldyBFcnJvcignWW91IHNob3VsZCBvbmx5IHVzZSBlaXRoZXIgYSByZW5kZXJlciBvciBhIHRlbXBsYXRlJyk7CiAgICAgICAgfQoKICAgICAgICBjZWxscy5mb3JFYWNoKGNlbGwgPT4gewogICAgICAgICAgY29uc3QgbW9kZWwgPSB0aGlzLl9ncmlkLl9fZ2V0Um93TW9kZWwoY2VsbC5wYXJlbnRFbGVtZW50KTsKCiAgICAgICAgICBpZiAocmVuZGVyZXIpIHsKICAgICAgICAgICAgY2VsbC5fcmVuZGVyZXIgPSByZW5kZXJlcjsKCiAgICAgICAgICAgIGlmIChtb2RlbC5pdGVtIHx8IHJlbmRlcmVyID09PSB0aGlzLmhlYWRlclJlbmRlcmVyIHx8IHJlbmRlcmVyID09PSB0aGlzLmZvb3RlclJlbmRlcmVyKSB7CiAgICAgICAgICAgICAgdGhpcy5fX3J1blJlbmRlcmVyKHJlbmRlcmVyLCBjZWxsLCBtb2RlbCk7CiAgICAgICAgICAgIH0KICAgICAgICAgIH0gZWxzZSBpZiAoY2VsbC5fdGVtcGxhdGUgIT09IHRlbXBsYXRlKSB7CiAgICAgICAgICAgIGNlbGwuX3RlbXBsYXRlID0gdGVtcGxhdGU7CgogICAgICAgICAgICBjZWxsLl9jb250ZW50LmlubmVySFRNTCA9ICcnOwogICAgICAgICAgICB0ZW1wbGF0ZS50ZW1wbGF0aXplci5fZ3JpZCA9IHRlbXBsYXRlLnRlbXBsYXRpemVyLl9ncmlkIHx8IHRoaXMuX2dyaWQ7CiAgICAgICAgICAgIGNvbnN0IGluc3QgPSB0ZW1wbGF0ZS50ZW1wbGF0aXplci5jcmVhdGVJbnN0YW5jZSgpOwogICAgICAgICAgICBjZWxsLl9jb250ZW50LmFwcGVuZENoaWxkKGluc3Qucm9vdCk7CiAgICAgICAgICAgIGNlbGwuX2luc3RhbmNlID0gaW5zdDsKICAgICAgICAgICAgaWYgKG1vZGVsLml0ZW0pIHsKICAgICAgICAgICAgICBjZWxsLl9pbnN0YW5jZS5zZXRQcm9wZXJ0aWVzKG1vZGVsKTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0pOwogICAgICB9CgogICAgICBfc2V0Qm9keVRlbXBsYXRlT3JSZW5kZXJlcih0ZW1wbGF0ZSwgcmVuZGVyZXIsIGNlbGxzLCBzcGxpY2VzKSB7CiAgICAgICAgaWYgKCh0ZW1wbGF0ZSB8fCByZW5kZXJlcikgJiYgY2VsbHMpIHsKICAgICAgICAgIHRoaXMuX19zZXRDb2x1bW5UZW1wbGF0ZU9yUmVuZGVyZXIodGVtcGxhdGUsIHJlbmRlcmVyLCBjZWxscyk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfc2V0SGVhZGVyVGVtcGxhdGVPclJlbmRlcmVyKGhlYWRlclRlbXBsYXRlLCBoZWFkZXJSZW5kZXJlciwgaGVhZGVyQ2VsbCkgewogICAgICAgIGlmICgoaGVhZGVyVGVtcGxhdGUgfHwgaGVhZGVyUmVuZGVyZXIpICYmIGhlYWRlckNlbGwpIHsKICAgICAgICAgIHRoaXMuX19zZXRDb2x1bW5UZW1wbGF0ZU9yUmVuZGVyZXIoaGVhZGVyVGVtcGxhdGUsIGhlYWRlclJlbmRlcmVyLCBbaGVhZGVyQ2VsbF0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3NldEZvb3RlclRlbXBsYXRlT3JSZW5kZXJlcihmb290ZXJUZW1wbGF0ZSwgZm9vdGVyUmVuZGVyZXIsIGZvb3RlckNlbGwpIHsKICAgICAgICBpZiAoKGZvb3RlclRlbXBsYXRlIHx8IGZvb3RlclJlbmRlcmVyKSAmJiBmb290ZXJDZWxsKSB7CiAgICAgICAgICB0aGlzLl9fc2V0Q29sdW1uVGVtcGxhdGVPclJlbmRlcmVyKGZvb3RlclRlbXBsYXRlLCBmb290ZXJSZW5kZXJlciwgW2Zvb3RlckNlbGxdKTsKICAgICAgICAgIHRoaXMuX2dyaWQuX191cGRhdGVIZWFkZXJGb290ZXJSb3dWaXNpYmlsaXR5KGZvb3RlckNlbGwucGFyZW50RWxlbWVudCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfc2VsZWN0Rmlyc3RUZW1wbGF0ZShoZWFkZXIgPSBmYWxzZSwgZm9vdGVyID0gZmFsc2UpIHsKICAgICAgICByZXR1cm4gRmxhdHRlbmVkTm9kZXNPYnNlcnZlci5nZXRGbGF0dGVuZWROb2Rlcyh0aGlzKQogICAgICAgICAgLmZpbHRlcihub2RlID0+CiAgICAgICAgICAgIG5vZGUubG9jYWxOYW1lID09PSAndGVtcGxhdGUnCiAgICAgICAgICAgICYmIG5vZGUuY2xhc3NMaXN0LmNvbnRhaW5zKCdoZWFkZXInKSA9PT0gaGVhZGVyCiAgICAgICAgICAgICYmIG5vZGUuY2xhc3NMaXN0LmNvbnRhaW5zKCdmb290ZXInKSA9PT0gZm9vdGVyCiAgICAgICAgICApWzBdOwogICAgICB9CgogICAgICBfZmluZFRlbXBsYXRlKGhlYWRlciwgZm9vdGVyKSB7CiAgICAgICAgY29uc3QgdGVtcGxhdGUgPSB0aGlzLl9zZWxlY3RGaXJzdFRlbXBsYXRlKGhlYWRlciwgZm9vdGVyKTsKICAgICAgICBpZiAodGVtcGxhdGUpIHsKICAgICAgICAgIGlmICh0aGlzLmRhdGFIb3N0KSB7CiAgICAgICAgICAgIC8vIHNldCBkYXRhSG9zdCB0byB0aGUgY29udGV4dCB3aGVyZSB0ZW1wbGF0ZSBoYXMgYmVlbiBkZWZpbmVkCiAgICAgICAgICAgIHRlbXBsYXRlLl9yb290RGF0YUhvc3QgPSB0aGlzLmRhdGFIb3N0Ll9yb290RGF0YUhvc3QgfHwgdGhpcy5kYXRhSG9zdDsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRlbXBsYXRlOwogICAgICB9CgogICAgICBfZmxleEdyb3dDaGFuZ2VkKGZsZXhHcm93LCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscykgewogICAgICAgIGlmICh0aGlzLnBhcmVudEVsZW1lbnQgJiYgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCgnZmxleEdyb3cnKTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiBjZWxsLnN0eWxlLmZsZXhHcm93ID0gZmxleEdyb3cpOwogICAgICB9CgogICAgICBfb3JkZXJDaGFuZ2VkKG9yZGVyLCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscykgewogICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiBjZWxsLnN0eWxlLm9yZGVyID0gb3JkZXIpOwogICAgICB9CgogICAgICBfd2lkdGhDaGFuZ2VkKHdpZHRoLCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscykgewogICAgICAgIGlmICh0aGlzLnBhcmVudEVsZW1lbnQgJiYgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCgnd2lkdGgnKTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiBjZWxsLnN0eWxlLndpZHRoID0gd2lkdGgpOwoKICAgICAgICAvLyBGb3JjZSBhIHJlZmxvdyB0byB3b3JrYXJvdW5kIGJyb3dzZXIgaXNzdWVzIGNhdXNpbmcgZG91YmxlIHNjcm9sbGJhcnMgdG8gZ3JpZAogICAgICAgIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS92YWFkaW4vdmFhZGluLWdyaWQvaXNzdWVzLzE1ODYKICAgICAgICBpZiAodGhpcy5fZ3JpZCAmJiB0aGlzLl9ncmlkLl9fZm9yY2VSZWZsb3cpIHsKICAgICAgICAgIHRoaXMuX2dyaWQuX19mb3JjZVJlZmxvdygpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX2Zyb3plbkNoYW5nZWQoZnJvemVuLCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscykgewogICAgICAgIGlmICh0aGlzLnBhcmVudEVsZW1lbnQgJiYgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCgnZnJvemVuJywgZnJvemVuKTsKICAgICAgICB9CgogICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ2Zyb3plbicsIGZyb3plbiwgY2VsbCkpOwoKICAgICAgICB0aGlzLl9ncmlkICYmIHRoaXMuX2dyaWQuX2Zyb3plbkNlbGxzQ2hhbmdlZCAmJiB0aGlzLl9ncmlkLl9mcm96ZW5DZWxsc0NoYW5nZWQoKTsKICAgICAgfQoKICAgICAgX2xhc3RGcm96ZW5DaGFuZ2VkKGxhc3RGcm96ZW4pIHsKICAgICAgICB0aGlzLl9hbGxDZWxscy5mb3JFYWNoKGNlbGwgPT4gdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdsYXN0LWZyb3plbicsIGxhc3RGcm96ZW4sIGNlbGwpKTsKCiAgICAgICAgaWYgKHRoaXMucGFyZW50RWxlbWVudCAmJiB0aGlzLnBhcmVudEVsZW1lbnQuX2NvbHVtblByb3BDaGFuZ2VkKSB7CiAgICAgICAgICB0aGlzLnBhcmVudEVsZW1lbnQuX2xhc3RGcm96ZW4gPSBsYXN0RnJvemVuOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3BhdGhPckhlYWRlckNoYW5nZWQocGF0aCwgaGVhZGVyLCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscywgcmVuZGVyZXIsIGhlYWRlclJlbmRlcmVyLCBib2R5VGVtcGxhdGUsIGhlYWRlclRlbXBsYXRlKSB7CiAgICAgICAgY29uc3QgaGFzSGVhZGVyVGV4dCA9IGhlYWRlciAhPT0gdW5kZWZpbmVkOwogICAgICAgIGlmICghaGVhZGVyUmVuZGVyZXIgJiYgIWhlYWRlclRlbXBsYXRlICYmIGhhc0hlYWRlclRleHQgJiYgaGVhZGVyQ2VsbCkgewogICAgICAgICAgdGhpcy5fX3NldFRleHRDb250ZW50KGhlYWRlckNlbGwuX2NvbnRlbnQsIGhlYWRlcik7CiAgICAgICAgfQoKICAgICAgICBpZiAocGF0aCAmJiBjZWxscy52YWx1ZSkgewogICAgICAgICAgaWYgKCFyZW5kZXJlciAmJiAhYm9keVRlbXBsYXRlKSB7CiAgICAgICAgICAgIGNvbnN0IHBhdGhSZW5kZXJlciA9IChyb290LCBvd25lciwge2l0ZW19KSA9PiB0aGlzLl9fc2V0VGV4dENvbnRlbnQocm9vdCwgdGhpcy5nZXQocGF0aCwgaXRlbSkpOwogICAgICAgICAgICB0aGlzLl9fc2V0Q29sdW1uVGVtcGxhdGVPclJlbmRlcmVyKHVuZGVmaW5lZCwgcGF0aFJlbmRlcmVyLCBjZWxscy52YWx1ZSk7CiAgICAgICAgICB9CgogICAgICAgICAgaWYgKCFoZWFkZXJSZW5kZXJlciAmJiAhaGVhZGVyVGVtcGxhdGUgJiYgIWhhc0hlYWRlclRleHQgJiYgaGVhZGVyQ2VsbCAmJiBoZWFkZXIgIT09IG51bGwpIHsKICAgICAgICAgICAgdGhpcy5fX3NldFRleHRDb250ZW50KGhlYWRlckNlbGwuX2NvbnRlbnQsIHRoaXMuX2dlbmVyYXRlSGVhZGVyKHBhdGgpKTsKICAgICAgICAgIH0KICAgICAgICB9CgogICAgICAgIGlmIChoZWFkZXJDZWxsKSB7CiAgICAgICAgICB0aGlzLl9ncmlkLl9fdXBkYXRlSGVhZGVyRm9vdGVyUm93VmlzaWJpbGl0eShoZWFkZXJDZWxsLnBhcmVudEVsZW1lbnQpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX19zZXRUZXh0Q29udGVudChub2RlLCB0ZXh0Q29udGVudCkgewogICAgICAgIG5vZGUudGV4dENvbnRlbnQgIT09IHRleHRDb250ZW50ICYmIChub2RlLnRleHRDb250ZW50ID0gdGV4dENvbnRlbnQpOwogICAgICB9CgogICAgICBfZ2VuZXJhdGVIZWFkZXIocGF0aCkgewogICAgICAgIHJldHVybiBwYXRoCiAgICAgICAgICAuc3Vic3RyKHBhdGgubGFzdEluZGV4T2YoJy4nKSArIDEpCiAgICAgICAgICAucmVwbGFjZSgvKFtBLVpdKS9nLCAnLSQxJykudG9Mb3dlckNhc2UoKQogICAgICAgICAgLnJlcGxhY2UoLy0vZywgJyAnKQogICAgICAgICAgLnJlcGxhY2UoL14uLywgbWF0Y2ggPT4gbWF0Y2gudG9VcHBlckNhc2UoKSk7CiAgICAgIH0KCiAgICAgIF90b2dnbGVBdHRyaWJ1dGUobmFtZSwgYm9vbCwgbm9kZSkgewogICAgICAgIGlmIChub2RlLmhhc0F0dHJpYnV0ZShuYW1lKSA9PT0gIWJvb2wpIHsKICAgICAgICAgIGlmIChib29sKSB7CiAgICAgICAgICAgIG5vZGUuc2V0QXR0cmlidXRlKG5hbWUsICcnKTsKICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIG5vZGUucmVtb3ZlQXR0cmlidXRlKG5hbWUpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgX3Jlb3JkZXJTdGF0dXNDaGFuZ2VkKHJlb3JkZXJTdGF0dXMsIGhlYWRlckNlbGwsIGZvb3RlckNlbGwsIGNlbGxzKSB7CiAgICAgICAgdGhpcy5fYWxsQ2VsbHMuZm9yRWFjaChjZWxsID0+IGNlbGwuc2V0QXR0cmlidXRlKCdyZW9yZGVyLXN0YXR1cycsIHJlb3JkZXJTdGF0dXMpKTsKICAgICAgfQoKICAgICAgX3Jlc2l6YWJsZUNoYW5nZWQocmVzaXphYmxlLCBoZWFkZXJDZWxsKSB7CiAgICAgICAgaWYgKHJlc2l6YWJsZSA9PT0gdW5kZWZpbmVkIHx8IGhlYWRlckNlbGwgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KCiAgICAgICAgaWYgKGhlYWRlckNlbGwpIHsKICAgICAgICAgIFtoZWFkZXJDZWxsXS5jb25jYXQodGhpcy5fZW1wdHlDZWxscykuZm9yRWFjaChjZWxsID0+IHsKICAgICAgICAgICAgaWYgKGNlbGwpIHsKICAgICAgICAgICAgICBjb25zdCBleGlzdGluZ0hhbmRsZSA9IGNlbGwucXVlcnlTZWxlY3RvcignW3BhcnR+PSJyZXNpemUtaGFuZGxlIl0nKTsKICAgICAgICAgICAgICBpZiAoZXhpc3RpbmdIYW5kbGUpIHsKICAgICAgICAgICAgICAgIGNlbGwucmVtb3ZlQ2hpbGQoZXhpc3RpbmdIYW5kbGUpOwogICAgICAgICAgICAgIH0KCiAgICAgICAgICAgICAgaWYgKHJlc2l6YWJsZSkgewogICAgICAgICAgICAgICAgY29uc3QgaGFuZGxlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7CiAgICAgICAgICAgICAgICBoYW5kbGUuc2V0QXR0cmlidXRlKCdwYXJ0JywgJ3Jlc2l6ZS1oYW5kbGUnKTsKICAgICAgICAgICAgICAgIGNlbGwuYXBwZW5kQ2hpbGQoaGFuZGxlKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3RleHRBbGlnbkNoYW5nZWQodGV4dEFsaWduLCBfY2VsbHMsIF9oZWFkZXJDZWxsLCBfZm9vdGVyQ2VsbCkgewogICAgICAgIGlmICh0ZXh0QWxpZ24gPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgcmV0dXJuOwogICAgICAgIH0KICAgICAgICBpZiAoWydzdGFydCcsICdlbmQnLCAnY2VudGVyJ10uaW5kZXhPZih0ZXh0QWxpZ24pID09PSAtMSkgewogICAgICAgICAgY29uc29sZS53YXJuKCd0ZXh0QWxpZ24gY2FuIG9ubHkgYmUgc2V0IGFzICJzdGFydCIsICJlbmQiIG9yICJjZW50ZXIiJyk7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICBsZXQgdGV4dEFsaWduRmFsbGJhY2s7CiAgICAgICAgaWYgKGdldENvbXB1dGVkU3R5bGUodGhpcy5fZ3JpZCkuZGlyZWN0aW9uID09PSAnbHRyJykgewogICAgICAgICAgaWYgKHRleHRBbGlnbiA9PT0gJ3N0YXJ0JykgewogICAgICAgICAgICB0ZXh0QWxpZ25GYWxsYmFjayA9ICdsZWZ0JzsKICAgICAgICAgIH0gZWxzZSBpZiAodGV4dEFsaWduID09PSAnZW5kJykgewogICAgICAgICAgICB0ZXh0QWxpZ25GYWxsYmFjayA9ICdyaWdodCc7CiAgICAgICAgICB9CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGlmICh0ZXh0QWxpZ24gPT09ICdzdGFydCcpIHsKICAgICAgICAgICAgdGV4dEFsaWduRmFsbGJhY2sgPSAncmlnaHQnOwogICAgICAgICAgfSBlbHNlIGlmICh0ZXh0QWxpZ24gPT09ICdlbmQnKSB7CiAgICAgICAgICAgIHRleHRBbGlnbkZhbGxiYWNrID0gJ2xlZnQnOwogICAgICAgICAgfQogICAgICAgIH0KCiAgICAgICAgdGhpcy5fYWxsQ2VsbHMuZm9yRWFjaChjZWxsID0+IHsKICAgICAgICAgIGNlbGwuX2NvbnRlbnQuc3R5bGUudGV4dEFsaWduID0gdGV4dEFsaWduOwogICAgICAgICAgaWYgKGdldENvbXB1dGVkU3R5bGUoY2VsbC5fY29udGVudCkudGV4dEFsaWduICE9PSB0ZXh0QWxpZ24pIHsKICAgICAgICAgICAgY2VsbC5fY29udGVudC5zdHlsZS50ZXh0QWxpZ24gPSB0ZXh0QWxpZ25GYWxsYmFjazsKICAgICAgICAgIH0KICAgICAgICB9KTsKICAgICAgfQoKICAgICAgX2hpZGRlbkNoYW5nZWQoaGlkZGVuLCBoZWFkZXJDZWxsLCBmb290ZXJDZWxsLCBjZWxscykgewogICAgICAgIGlmICh0aGlzLnBhcmVudEVsZW1lbnQgJiYgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCkgewogICAgICAgICAgdGhpcy5wYXJlbnRFbGVtZW50Ll9jb2x1bW5Qcm9wQ2hhbmdlZCgnaGlkZGVuJywgaGlkZGVuKTsKICAgICAgICB9CgogICAgICAgIGlmICghIWhpZGRlbiAhPT0gISF0aGlzLl9wcmV2aW91c0hpZGRlbiAmJiB0aGlzLl9ncmlkKSB7CiAgICAgICAgICBpZiAoaGlkZGVuID09PSB0cnVlKSB7CiAgICAgICAgICAgIHRoaXMuX2FsbENlbGxzLmZvckVhY2goY2VsbCA9PiB7CiAgICAgICAgICAgICAgaWYgKGNlbGwuX2NvbnRlbnQucGFyZW50Tm9kZSkgewogICAgICAgICAgICAgICAgY2VsbC5fY29udGVudC5wYXJlbnROb2RlLnJlbW92ZUNoaWxkKGNlbGwuX2NvbnRlbnQpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgICB0aGlzLl9ncmlkLl9kZWJvdW5jZXJIaWRkZW5DaGFuZ2VkID0gRGVib3VuY2VyLmRlYm91bmNlKAogICAgICAgICAgICB0aGlzLl9ncmlkLl9kZWJvdW5jZXJIaWRkZW5DaGFuZ2VkLAogICAgICAgICAgICBhbmltYXRpb25GcmFtZSwKICAgICAgICAgICAgKCkgPT4gewogICAgICAgICAgICAgIGlmICh0aGlzLl9ncmlkICYmIHRoaXMuX2dyaWQuX3JlbmRlckNvbHVtblRyZWUpIHsKICAgICAgICAgICAgICAgIHRoaXMuX2dyaWQuX3JlbmRlckNvbHVtblRyZWUodGhpcy5fZ3JpZC5fY29sdW1uVHJlZSk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICB9CiAgICAgICAgICApOwoKICAgICAgICAgIHRoaXMuX2dyaWQuX3VwZGF0ZUxhc3RGcm96ZW4gJiYgdGhpcy5fZ3JpZC5fdXBkYXRlTGFzdEZyb3plbigpOwogICAgICAgICAgdGhpcy5fZ3JpZC5ub3RpZnlSZXNpemUgJiYgdGhpcy5fZ3JpZC5ub3RpZnlSZXNpemUoKTsKICAgICAgICAgIHRoaXMuX2dyaWQuX3Jlc2V0S2V5Ym9hcmROYXZpZ2F0aW9uICYmIHRoaXMuX2dyaWQuX3Jlc2V0S2V5Ym9hcmROYXZpZ2F0aW9uKCk7CiAgICAgICAgfQogICAgICAgIHRoaXMuX3ByZXZpb3VzSGlkZGVuID0gaGlkZGVuOwogICAgICB9CgogICAgfTsKCiAgICAvKioKICAgICAqIEEgYDx2YWFkaW4tZ3JpZC1jb2x1bW4+YCBpcyB1c2VkIHRvIGNvbmZpZ3VyZSBob3cgYSBjb2x1bW4gaW4gYDx2YWFkaW4tZ3JpZD5gCiAgICAgKiBzaG91bGQgbG9vayBsaWtlLgogICAgICoKICAgICAqIFNlZSBgPHZhYWRpbi1ncmlkPmAgZG9jdW1lbnRhdGlvbiBhbmQgZGVtb3MgZm9yIGluc3RydWN0aW9ucyBhbmQgZXhhbXBsZXMgb24gaG93CiAgICAgKiB0byBjb25maWd1cmUgdGhlIGA8dmFhZGluLWdyaWQtY29sdW1uPmAuCiAgICAgKiBgYGAKICAgICAqCiAgICAgKiBAZXh0ZW5kcyBQb2x5bWVyRWxlbWVudAogICAgICogQG1peGVzIEdyaWQuQ29sdW1uQmFzZU1peGluCiAgICAgKi8KICAgIGNsYXNzIEdyaWRDb2x1bW5FbGVtZW50IGV4dGVuZHMgQ29sdW1uQmFzZU1peGluKERpck1peGluJDEoUG9seW1lckVsZW1lbnQpKSB7CiAgICAgIHN0YXRpYyBnZXQgaXMoKSB7CiAgICAgICAgcmV0dXJuICd2YWFkaW4tZ3JpZC1jb2x1bW4nOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgIC8qKgogICAgICAgICAgICogV2lkdGggb2YgdGhlIGNlbGxzIGZvciB0aGlzIGNvbHVtbi4KICAgICAgICAgICAqLwogICAgICAgICAgd2lkdGg6IHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nLAogICAgICAgICAgICB2YWx1ZTogJzEwMHB4JwogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIEZsZXggZ3JvdyByYXRpbyBmb3IgdGhlIGNlbGwgd2lkdGhzLiBXaGVuIHNldCB0byAwLCBjZWxsIHdpZHRoIGlzIGZpeGVkLgogICAgICAgICAgICovCiAgICAgICAgICBmbGV4R3JvdzogewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgICAgIHZhbHVlOiAxCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQ3VzdG9tIGZ1bmN0aW9uIGZvciByZW5kZXJpbmcgdGhlIGNlbGwgY29udGVudC4KICAgICAgICAgICAqIFJlY2VpdmVzIHRocmVlIGFyZ3VtZW50czoKICAgICAgICAgICAqCiAgICAgICAgICAgKiAtIGByb290YCBUaGUgY2VsbCBjb250ZW50IERPTSBlbGVtZW50LiBBcHBlbmQgeW91ciBjb250ZW50IHRvIGl0LgogICAgICAgICAgICogLSBgY29sdW1uYCBUaGUgYDx2YWFkaW4tZ3JpZC1jb2x1bW4+YCBlbGVtZW50LgogICAgICAgICAgICogLSBgcm93RGF0YWAgVGhlIG9iamVjdCB3aXRoIHRoZSBwcm9wZXJ0aWVzIHJlbGF0ZWQgd2l0aAogICAgICAgICAgICogICB0aGUgcmVuZGVyZWQgaXRlbSwgY29udGFpbnM6CiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuaW5kZXhgIFRoZSBpbmRleCBvZiB0aGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5pdGVtYCBUaGUgaXRlbS4KICAgICAgICAgICAqICAgLSBgcm93RGF0YS5leHBhbmRlZGAgU3VibGV2ZWwgdG9nZ2xlIHN0YXRlLgogICAgICAgICAgICogICAtIGByb3dEYXRhLmxldmVsYCBMZXZlbCBvZiB0aGUgdHJlZSByZXByZXNlbnRlZCB3aXRoIGEgaG9yaXpvbnRhbCBvZmZzZXQgb2YgdGhlIHRvZ2dsZSBidXR0b24uCiAgICAgICAgICAgKiAgIC0gYHJvd0RhdGEuc2VsZWN0ZWRgIFNlbGVjdGVkIHN0YXRlLgogICAgICAgICAgICovCiAgICAgICAgICByZW5kZXJlcjogRnVuY3Rpb24sCgogICAgICAgICAgLyoqCiAgICAgICAgICAgKiBQYXRoIHRvIGFuIGl0ZW0gc3ViLXByb3BlcnR5IHdob3NlIHZhbHVlIGdldHMgZGlzcGxheWVkIGluIHRoZSBjb2x1bW4gYm9keSBjZWxscy4KICAgICAgICAgICAqIFRoZSBwcm9wZXJ0eSBuYW1lIGlzIGFsc28gc2hvd24gaW4gdGhlIGNvbHVtbiBoZWFkZXIgaWYgYW4gZXhwbGljaXQgaGVhZGVyIG9yIHJlbmRlcmVyIGlzbid0IGRlZmluZWQuCiAgICAgICAgICAgKi8KICAgICAgICAgIHBhdGg6IHsKICAgICAgICAgICAgdHlwZTogU3RyaW5nCiAgICAgICAgICB9LAoKICAgICAgICAgIC8qKgogICAgICAgICAgICogQXV0b21hdGljYWxseSBzZXRzIHRoZSB3aWR0aCBvZiB0aGUgY29sdW1uIGJhc2VkIG9uIHRoZSBjb2x1bW4gY29udGVudHMgd2hlbiB0aGlzIGlzIHNldCB0byBgdHJ1ZWAuCiAgICAgICAgICAgKgogICAgICAgICAgICogRm9yIHBlcmZvcm1hbmNlIHJlYXNvbnMgdGhlIGNvbHVtbiB3aWR0aCBpcyBjYWxjdWxhdGVkIGF1dG9tYXRpY2FsbHkgb25seSBvbmNlIHdoZW4gdGhlIGdyaWQgaXRlbXMKICAgICAgICAgICAqIGFyZSByZW5kZXJlZCBmb3IgdGhlIGZpcnN0IHRpbWUgYW5kIHRoZSBjYWxjdWxhdGlvbiBvbmx5IGNvbnNpZGVycyB0aGUgcm93cyB3aGljaCBhcmUgY3VycmVudGx5CiAgICAgICAgICAgKiByZW5kZXJlZCBpbiBET00gKGEgYml0IG1vcmUgdGhhbiB3aGF0IGlzIGN1cnJlbnRseSB2aXNpYmxlKS4gSWYgdGhlIGdyaWQgaXMgc2Nyb2xsZWQsIG9yIHRoZSBjZWxsCiAgICAgICAgICAgKiBjb250ZW50IGNoYW5nZXMsIHRoZSBjb2x1bW4gd2lkdGggbWlnaHQgbm90IG1hdGNoIHRoZSBjb250ZW50cyBhbnltb3JlLgogICAgICAgICAgICoKICAgICAgICAgICAqIEhpZGRlbiBjb2x1bW5zIGFyZSBpZ25vcmVkIGluIHRoZSBjYWxjdWxhdGlvbiBhbmQgdGhlaXIgd2lkdGhzIGFyZSBub3QgYXV0b21hdGljYWxseSB1cGRhdGVkIHdoZW4KICAgICAgICAgICAqIHlvdSBzaG93IGEgY29sdW1uIHRoYXQgd2FzIGluaXRpYWxseSBoaWRkZW4uCiAgICAgICAgICAgKgogICAgICAgICAgICogWW91IGNhbiBtYW51YWxseSB0cmlnZ2VyIHRoZSBhdXRvIHNpemluZyBiZWhhdmlvciBhZ2FpbiBieSBjYWxsaW5nIGBncmlkLnJlY2FsY3VsYXRlQ29sdW1uV2lkdGhzKClgLgogICAgICAgICAgICoKICAgICAgICAgICAqIFRoZSBjb2x1bW4gd2lkdGggbWF5IHN0aWxsIGdyb3cgbGFyZ2VyIHdoZW4gYGZsZXhHcm93YCBpcyBub3QgMC4KICAgICAgICAgICAqLwogICAgICAgICAgYXV0b1dpZHRoOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIHZhbHVlOiBmYWxzZQogICAgICAgICAgfSwKCiAgICAgICAgICBfYm9keVRlbXBsYXRlOiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdAogICAgICAgICAgfSwKCiAgICAgICAgICBfY2VsbHM6IEFycmF5CgogICAgICAgIH07CiAgICAgIH0KCiAgICB9CgogICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKEdyaWRDb2x1bW5FbGVtZW50LmlzLCBHcmlkQ29sdW1uRWxlbWVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwogICAgLyoqCiAgICAgKiBUaGlzIEVsZW1lbnQgaXMgdXNlZCBpbnRlcm5hbGx5IGJ5IHZhYWRpbi1ncmlkLgogICAgICoKICAgICAqIEBwcml2YXRlCiAgICAgKi8KICAgIGNsYXNzIEdyaWRPdXRlclNjcm9sbGVyRWxlbWVudCBleHRlbmRzIChjbGFzcyBleHRlbmRzIFBvbHltZXJFbGVtZW50IHt9KSB7CiAgICAgIHN0YXRpYyBnZXQgdGVtcGxhdGUoKSB7CiAgICAgICAgcmV0dXJuIGh0bWxgCiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICAgIHRvcDogMDsKICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICAgIG92ZXJmbG93OiBhdXRvOwogICAgICB9CgogICAgICA6aG9zdChbcGFzc3Rocm91Z2hdKSB7CiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CgogICAgPHNsb3Q+PC9zbG90PgpgOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IGlzKCkgewogICAgICAgIHJldHVybiAndmFhZGluLWdyaWQtb3V0ZXItc2Nyb2xsZXInOwogICAgICB9CgogICAgICBzdGF0aWMgZ2V0IHByb3BlcnRpZXMoKSB7CiAgICAgICAgcmV0dXJuIHsKCiAgICAgICAgICBzY3JvbGxUYXJnZXQ6IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0CiAgICAgICAgICB9LAoKICAgICAgICAgIHNjcm9sbEhhbmRsZXI6IHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0CiAgICAgICAgICB9LAoKICAgICAgICAgIHBhc3N0aHJvdWdoOiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgICAgdmFsdWU6IHRydWUKICAgICAgICAgIH0sCgogICAgICAgICAgb3V0ZXJTY3JvbGxpbmc6IEJvb2xlYW4sCgogICAgICAgICAgbm9TY3JvbGxiYXJzOiBCb29sZWFuLAoKICAgICAgICAgIF90b3VjaERldmljZTogQm9vbGVhbgogICAgICAgIH07CiAgICAgIH0KCiAgICAgIHJlYWR5KCkgewogICAgICAgIHN1cGVyLnJlYWR5KCk7CiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdzY3JvbGwnLCAoKSA9PiB0aGlzLl9zeW5jU2Nyb2xsVGFyZ2V0KCkpOwogICAgICAgIHRoaXMucGFyZW50RWxlbWVudC5hZGRFdmVudExpc3RlbmVyKCdtb3VzZW1vdmUnLCB0aGlzLl9vbk1vdXNlTW92ZS5iaW5kKHRoaXMpKTsKCiAgICAgICAgLy8gZm9yIHNvbWUgcmVhc29uIHNjcm9sbCBiYXJzIGFyZSBoaWRkZW4gaW4gaU9TIGlmIHRoaXMgc3R5bGUgaXMKICAgICAgICAvLyBhZGRlZCBpbiBzdHlsZXNoZWV0cyBvciBiZWZvcmUgYXR0YWNoaW5nLgogICAgICAgIHRoaXMuc3R5bGUud2Via2l0T3ZlcmZsb3dTY3JvbGxpbmcgPSAndG91Y2gnOwoKICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlZG93bicsIF8gPT4gdGhpcy5vdXRlclNjcm9sbGluZyA9IHRydWUpOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignbW91c2V1cCcsIF8gPT4gewogICAgICAgICAgdGhpcy5vdXRlclNjcm9sbGluZyA9IGZhbHNlOwogICAgICAgICAgdGhpcy5zY3JvbGxIYW5kbGVyLl9zY3JvbGxIYW5kbGVyKCk7CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIF9vbk1vdXNlTW92ZShlKSB7CiAgICAgICAgLy8gSWdub3JlIG1vdXNlbW92ZSBldmVudHMgb24gdG91Y2ggZGV2aWNlcwogICAgICAgIGlmICghdGhpcy5fdG91Y2hEZXZpY2UpIHsKICAgICAgICAgIGlmICh0aGlzLm5vU2Nyb2xsYmFycyAmJiB0aGlzLnBhcmVudEVsZW1lbnQuaGFzQXR0cmlidXRlKCdzY3JvbGwtcGVyaW9kJykpIHsKICAgICAgICAgICAgdGhpcy5wYXNzdGhyb3VnaCA9IGUub2Zmc2V0WSA8PSB0aGlzLmNsaWVudEhlaWdodCAtIDIwICYmIGUub2Zmc2V0WCA8PSB0aGlzLmNsaWVudFdpZHRoIC0gMjA7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLnBhc3N0aHJvdWdoID0gZS5vZmZzZXRZIDw9IHRoaXMuY2xpZW50SGVpZ2h0ICYmIGUub2Zmc2V0WCA8PSB0aGlzLmNsaWVudFdpZHRoOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQoKICAgICAgc3luY091dGVyU2Nyb2xsZXIoKSB7CiAgICAgICAgdGhpcy5zY3JvbGxUb3AgPSB0aGlzLnNjcm9sbFRhcmdldC5zY3JvbGxUb3A7CiAgICAgICAgdGhpcy5zY3JvbGxMZWZ0ID0gdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsTGVmdDsKICAgICAgfQoKICAgICAgX3N5bmNTY3JvbGxUYXJnZXQoKSB7CiAgICAgICAgcmVxdWVzdEFuaW1hdGlvbkZyYW1lKCgpID0+IHsKICAgICAgICAgIHRoaXMuc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCA9IHRoaXMuc2Nyb2xsVG9wOwogICAgICAgICAgdGhpcy5zY3JvbGxUYXJnZXQuc2Nyb2xsTGVmdCA9IHRoaXMuc2Nyb2xsTGVmdDsKICAgICAgICAgIHRoaXMuc2Nyb2xsSGFuZGxlci5fc2Nyb2xsSGFuZGxlcigpOwogICAgICAgIH0pOwoKICAgICAgfQogICAgfQoKICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZShHcmlkT3V0ZXJTY3JvbGxlckVsZW1lbnQuaXMsIEdyaWRPdXRlclNjcm9sbGVyRWxlbWVudCk7CgogICAgLyoqCiAgICBAbGljZW5zZQogICAgQ29weXJpZ2h0IChjKSAyMDE3IFZhYWRpbiBMdGQuCiAgICBUaGlzIHByb2dyYW0gaXMgYXZhaWxhYmxlIHVuZGVyIEFwYWNoZSBMaWNlbnNlIFZlcnNpb24gMi4wLCBhdmFpbGFibGUgYXQgaHR0cHM6Ly92YWFkaW4uY29tL2xpY2Vuc2UvCiAgICAqLwogICAgY29uc3QgVmFhZGluR3JpZFN0eWxlcyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RvbS1tb2R1bGUnKTsKCiAgICAvLyBOT1RFKHdlYi1wYWRhd2FuKTogaHR0cHM6Ly9naXRodWIuY29tL3ZhYWRpbi92YWFkaW4tZ3JpZC9pc3N1ZXMvMTUxNAogICAgVmFhZGluR3JpZFN0eWxlcy5hcHBlbmRDaGlsZCgKICAgICAgaHRtbGAKICA8c3R5bGU+CiAgICBAa2V5ZnJhbWVzIHZhYWRpbi1ncmlkLWFwcGVhciB7CiAgICAgIHRvIHsKICAgICAgICBvcGFjaXR5OiAxOwogICAgICB9CiAgICB9CgogICAgOmhvc3QgewogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgYW5pbWF0aW9uOiAxbXMgdmFhZGluLWdyaWQtYXBwZWFyOwogICAgICBoZWlnaHQ6IDQwMHB4OwogICAgICBmbGV4OiAxIDEgYXV0bzsKICAgICAgYWxpZ24tc2VsZjogc3RyZXRjaDsKICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgfQoKICAgIDpob3N0KFtoaWRkZW5dKSB7CiAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgIH0KCiAgICAjc2Nyb2xsZXIgewogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKDApOwogICAgICB3aWR0aDogYXV0bzsKICAgICAgaGVpZ2h0OiBhdXRvOwogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgIHRvcDogMDsKICAgICAgcmlnaHQ6IDA7CiAgICAgIGJvdHRvbTogMDsKICAgICAgbGVmdDogMDsKICAgIH0KCiAgICA6aG9zdChbaGVpZ2h0LWJ5LXJvd3NdKSB7CiAgICAgIGhlaWdodDogYXV0bzsKICAgICAgYWxpZ24tc2VsZjogZmxleC1zdGFydDsKICAgICAgZmxleC1ncm93OiAwOwogICAgICB3aWR0aDogMTAwJTsKICAgIH0KCiAgICA6aG9zdChbaGVpZ2h0LWJ5LXJvd3NdKSAjc2Nyb2xsZXIgewogICAgICB3aWR0aDogMTAwJTsKICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICB9CgogICAgI3RhYmxlIHsKICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgIG92ZXJmbG93OiBhdXRvOwogICAgICB6LWluZGV4OiAtMjsKICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICBvdXRsaW5lOiBub25lOwogICAgfQoKICAgICNoZWFkZXIgewogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICB0b3A6IDA7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgfQoKICAgIHRoIHsKICAgICAgdGV4dC1hbGlnbjogaW5oZXJpdDsKICAgIH0KCiAgICAvKiBTYWZhcmkgZG9lc24ndCB3b3JrIHdpdGggImluaGVyaXQiICovCiAgICBbc2FmYXJpXSB0aCB7CiAgICAgIHRleHQtYWxpZ246IGluaXRpYWw7CiAgICB9CgogICAgI2Zvb3RlciB7CiAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgIGJvdHRvbTogMDsKICAgICAgd2lkdGg6IDEwMCU7CiAgICB9CgogICAgI2l0ZW1zIHsKICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIHdpZHRoOiAxMDAlOwogICAgICBwb3NpdGlvbjogcmVsYXRpdmU7CiAgICAgIHotaW5kZXg6IC0xOwogICAgfQoKICAgICNpdGVtcywKICAgICNvdXRlcnNpemVyLAogICAgI2ZpeGVkc2l6ZXIgewogICAgICBib3JkZXItdG9wOiAwIHNvbGlkIHRyYW5zcGFyZW50OwogICAgICBib3JkZXItYm90dG9tOiAwIHNvbGlkIHRyYW5zcGFyZW50OwogICAgfQoKICAgIFtwYXJ0fj0icm93Il0gewogICAgICBkaXNwbGF5OiBmbGV4OwogICAgICB3aWR0aDogMTAwJTsKICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDsKICAgICAgbWFyZ2luOiAwOwogICAgfQoKICAgIFtwYXJ0fj0icm93Il1bbG9hZGluZ10gW3BhcnR+PSJib2R5LWNlbGwiXSA6OnNsb3R0ZWQodmFhZGluLWdyaWQtY2VsbC1jb250ZW50KSB7CiAgICAgIG9wYWNpdHk6IDA7CiAgICB9CgogICAgI2l0ZW1zIFtwYXJ0fj0icm93Il0gewogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICB9CgogICAgI2l0ZW1zIFtwYXJ0fj0icm93Il06ZW1wdHkgewogICAgICBoZWlnaHQ6IDFlbTsKICAgIH0KCiAgICBbcGFydH49ImNlbGwiXTpub3QoW3BhcnR+PSJkZXRhaWxzLWNlbGwiXSkgewogICAgICBmbGV4LXNocmluazogMDsKICAgICAgZmxleC1ncm93OiAxOwogICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94OwogICAgICBkaXNwbGF5OiBmbGV4OwogICAgICB3aWR0aDogMTAwJTsKICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICBhbGlnbi1pdGVtczogY2VudGVyOwogICAgICBwYWRkaW5nOiAwOwogICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgfQoKICAgIFtwYXJ0fj0iZGV0YWlscy1jZWxsIl0gewogICAgICBwb3NpdGlvbjogYWJzb2x1dGU7CiAgICAgIGJvdHRvbTogMDsKICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgIHBhZGRpbmc6IDA7CiAgICB9CgogICAgW3BhcnR+PSJjZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCkgewogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7CiAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzOwogICAgfQoKICAgIFtoaWRkZW5dIHsKICAgICAgZGlzcGxheTogbm9uZSAhaW1wb3J0YW50OwogICAgfQoKICAgIFtmcm96ZW5dIHsKICAgICAgei1pbmRleDogMjsKICAgICAgd2lsbC1jaGFuZ2U6IHRyYW5zZm9ybTsKICAgIH0KCiAgICAjb3V0ZXJzY3JvbGxlciB7CiAgICAgIC8qIE5lZWRlZCAoYXQgbGVhc3QpIGZvciBBbmRyb2lkIENocm9tZSAqLwogICAgICB6LWluZGV4OiAwOwogICAgfQoKICAgICNzY3JvbGxlcjpub3QoW3NhZmFyaV0pICNvdXRlcnNjcm9sbGVyIHsKICAgICAgLyogTmVlZGVkIGZvciBBbmRyb2lkIENocm9tZSAoIzEwMjApLiBDYW4ndCBiZSBhcHBsaWVkIHRvIFNhZmFyaQogICAgICBzaW5jZSBpdCB3b3VsZCByZS1pbnRyb2R1Y2UgdGhlIHN1Yi1waXhlbCBvdmVyZmxvdyBidWcgKCM4NTMpICovCiAgICAgIHdpbGwtY2hhbmdlOiB0cmFuc2Zvcm07CiAgICB9CgogICAgW25vLXNjcm9sbGJhcnNdOm5vdChbc2FmYXJpXSk6bm90KFtmaXJlZm94XSkgI291dGVyc2Nyb2xsZXIsCiAgICBbbm8tc2Nyb2xsYmFyc11bc2FmYXJpXSAjdGFibGUsCiAgICBbbm8tc2Nyb2xsYmFyc11bZmlyZWZveF0gI3RhYmxlIHsKICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsKICAgIH0KCiAgICBbbm8tc2Nyb2xsYmFyc106bm90KFtzYWZhcmldKTpub3QoW2ZpcmVmb3hdKSAjb3V0ZXJzY3JvbGxlciB7CiAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgfQoKICAgIC8qIFJlb3JkZXJpbmcgc3R5bGVzICovCiAgICA6aG9zdChbcmVvcmRlcmluZ10pIFtwYXJ0fj0iY2VsbCJdIDo6c2xvdHRlZCh2YWFkaW4tZ3JpZC1jZWxsLWNvbnRlbnQpLAogICAgOmhvc3QoW3Jlb3JkZXJpbmddKSBbcGFydH49InJlc2l6ZS1oYW5kbGUiXSwKICAgICNzY3JvbGxlcltuby1jb250ZW50LXBvaW50ZXItZXZlbnRzXSBbcGFydH49ImNlbGwiXSA6OnNsb3R0ZWQodmFhZGluLWdyaWQtY2VsbC1jb250ZW50KSB7CiAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgfQoKICAgIFtwYXJ0fj0icmVvcmRlci1naG9zdCJdIHsKICAgICAgdmlzaWJpbGl0eTogaGlkZGVuOwogICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOwogICAgICBvcGFjaXR5OiAwLjU7CgogICAgICAvKiBQcmV2ZW50IG92ZXJmbG93aW5nIHRoZSBncmlkIGluIEZpcmVmb3ggKi8KICAgICAgdG9wOiAwOwogICAgICBsZWZ0OiAwOwogICAgfQoKICAgIDpob3N0KFtyZW9yZGVyaW5nXSkgewogICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogICAgICB1c2VyLXNlbGVjdDogbm9uZTsKICAgIH0KCiAgICAjc2Nyb2xsZXJbaWVdW2NvbHVtbi1yZW9yZGVyaW5nLWFsbG93ZWRdIFtwYXJ0fj0iaGVhZGVyLWNlbGwiXSB7CiAgICAgIC1tcy11c2VyLXNlbGVjdDogbm9uZTsKICAgIH0KCiAgICA6aG9zdChbcmVvcmRlcmluZ10pICNvdXRlcnNjcm9sbGVyIHsKICAgICAgLXdlYmtpdC1vdmVyZmxvdy1zY3JvbGxpbmc6IGF1dG8gIWltcG9ydGFudDsKICAgIH0KCiAgICAvKiBSZXNpemluZyBzdHlsZXMgKi8KICAgIFtwYXJ0fj0icmVzaXplLWhhbmRsZSJdIHsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICB0b3A6IDA7CiAgICAgIHJpZ2h0OiAwOwogICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgIGN1cnNvcjogY29sLXJlc2l6ZTsKICAgICAgei1pbmRleDogMTsKICAgIH0KCiAgICBbcGFydH49InJlc2l6ZS1oYW5kbGUiXTo6YmVmb3JlIHsKICAgICAgcG9zaXRpb246IGFic29sdXRlOwogICAgICBjb250ZW50OiAiIjsKICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB3aWR0aDogMzVweDsKICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVYKC01MCUpOwogICAgfQoKICAgIFtsYXN0LWNvbHVtbl0gW3BhcnR+PSJyZXNpemUtaGFuZGxlIl06OmJlZm9yZSwKICAgIFtsYXN0LWZyb3plbl0gW3BhcnR+PSJyZXNpemUtaGFuZGxlIl06OmJlZm9yZSB7CiAgICAgIHdpZHRoOiAxOHB4OwogICAgICB0cmFuc2Zvcm06IG5vbmU7CiAgICAgIHJpZ2h0OiAwOwogICAgfQoKICAgICNzY3JvbGxlcltjb2x1bW4tcmVzaXppbmddIHsKICAgICAgLW1zLXVzZXItc2VsZWN0OiBub25lOwogICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lOwogICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lOwogICAgICB1c2VyLXNlbGVjdDogbm9uZTsKICAgIH0KCiAgICAvKiBTaXplciBzdHlsZXMgKi8KICAgIC5zaXplciB7CiAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsKICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIHZpc2liaWxpdHk6IGhpZGRlbjsKICAgIH0KCiAgICAuc2l6ZXIgW3BhcnR+PSJkZXRhaWxzLWNlbGwiXSB7CiAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgIH0KCiAgICAuc2l6ZXIgW3BhcnR+PSJjZWxsIl1baGlkZGVuXSB7CiAgICAgIGRpc3BsYXk6IG5vbmUgIWltcG9ydGFudDsKICAgIH0KCiAgICAuc2l6ZXIgW3BhcnR+PSJjZWxsIl0gewogICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgZmxleC1zaHJpbms6IDA7CiAgICAgIGxpbmUtaGVpZ2h0OiAwOwogICAgICBtYXJnaW4tdG9wOiAtMWVtOwogICAgICBoZWlnaHQ6IDAgIWltcG9ydGFudDsKICAgICAgbWluLWhlaWdodDogMCAhaW1wb3J0YW50OwogICAgICBtYXgtaGVpZ2h0OiAwICFpbXBvcnRhbnQ7CiAgICAgIHBhZGRpbmc6IDAgIWltcG9ydGFudDsKICAgIH0KCiAgICAuc2l6ZXIgW3BhcnR+PSJjZWxsIl06OmJlZm9yZSB7CiAgICAgIGNvbnRlbnQ6ICItIjsKICAgIH0KCiAgICAuc2l6ZXIgW3BhcnR+PSJjZWxsIl0gOjpzbG90dGVkKHZhYWRpbi1ncmlkLWNlbGwtY29udGVudCkgewogICAgICBkaXNwbGF5OiBub25lICFpbXBvcnRhbnQ7CiAgICB9CgogICAgLyogRml4ZWQgbW9kZSAoVGFibGV0IEVkZ2UpICovCiAgICAjZml4ZWRzaXplciB7CiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTsKICAgIH0KCiAgICA6bm90KFtlZGdlXVtuby1zY3JvbGxiYXJzXSkgI2ZpeGVkc2l6ZXIgewogICAgICBkaXNwbGF5OiBub25lOwogICAgfQoKICAgIFtlZGdlXVtuby1zY3JvbGxiYXJzXSB7CiAgICAgIC8qIEFueSB2YWx1ZSBvdGhlciB0aGFuIOKAmG5vbmXigJkgZm9yIHRoZSB0cmFuc2Zvcm0gcmVzdWx0cyBpbiB0aGUgY3JlYXRpb24gb2YgYm90aCBhIHN0YWNraW5nIGNvbnRleHQgYW5kCiAgICAgIGEgY29udGFpbmluZyBibG9jay4gVGhlIG9iamVjdCBhY3RzIGFzIGEgY29udGFpbmluZyBibG9jayBmb3IgZml4ZWQgcG9zaXRpb25lZCBkZXNjZW5kYW50cy4gKi8KICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVaKDApOwogICAgICBvdmVyZmxvdzogaGlkZGVuOwogICAgfQoKICAgIFtlZGdlXVtuby1zY3JvbGxiYXJzXSAjaGVhZGVyLAogICAgW2VkZ2VdW25vLXNjcm9sbGJhcnNdICNmb290ZXIgewogICAgICBwb3NpdGlvbjogZml4ZWQ7CiAgICB9CgogICAgW2VkZ2VdW25vLXNjcm9sbGJhcnNdICNpdGVtcyB7CiAgICAgIHBvc2l0aW9uOiBmaXhlZDsKICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIHdpbGwtY2hhbmdlOiB0cmFuc2Zvcm07CiAgICB9CgogICAgLyogUlRMIHNwZWNpZmljIHN0eWxlcyAqLwoKICAgIDpob3N0KFtkaXI9InJ0bCJdKSBbcGFydH49InJlb3JkZXItZ2hvc3QiXSB7CiAgICAgIGxlZnQ6IGF1dG87CiAgICAgIHJpZ2h0OiAwOwogICAgfQoKICAgIDpob3N0KFtkaXI9InJ0bCJdKSBbcGFydH49InJlc2l6ZS1oYW5kbGUiXSB7CiAgICAgIGxlZnQ6IDA7CiAgICAgIHJpZ2h0OiBhdXRvOwogICAgfQoKICAgIDpob3N0KFtkaXI9InJ0bCJdKSBbcGFydH49InJlc2l6ZS1oYW5kbGUiXTo6YmVmb3JlIHsKICAgICAgdHJhbnNmb3JtOiB0cmFuc2xhdGVYKDUwJSk7CiAgICB9CgogICAgOmhvc3QoW2Rpcj0icnRsIl0pIFtsYXN0LWNvbHVtbl0gW3BhcnR+PSJyZXNpemUtaGFuZGxlIl06OmJlZm9yZSwKICAgIDpob3N0KFtkaXI9InJ0bCJdKSBbbGFzdC1mcm96ZW5dIFtwYXJ0fj0icmVzaXplLWhhbmRsZSJdOjpiZWZvcmUgewogICAgICBsZWZ0OiAwOwogICAgICByaWdodDogYXV0bzsKICAgIH0KICA8L3N0eWxlPgpgKTsKCiAgICBjb25zdCBzYWZhcmkgPSAvXigoPyFjaHJvbWV8YW5kcm9pZCkuKSpzYWZhcmkvaS50ZXN0KG5hdmlnYXRvci51c2VyQWdlbnQpOwogICAgY29uc3QgZmlyZWZveCA9IG5hdmlnYXRvci51c2VyQWdlbnQudG9Mb3dlckNhc2UoKS5pbmRleE9mKCdmaXJlZm94JykgPiAtMTsKCiAgICBpZiAoc2FmYXJpIHx8IGZpcmVmb3gpIHsKICAgICAgY29uc3Qgc2Nyb2xsaW5nU3R5bGVzID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc3R5bGUnKTsKICAgICAgc2Nyb2xsaW5nU3R5bGVzLnRleHRDb250ZW50ID0gYAogICAgW3Njcm9sbGluZ11bc2FmYXJpXSAjb3V0ZXJzY3JvbGxlciwKICAgIFtzY3JvbGxpbmddW2ZpcmVmb3hdICNvdXRlcnNjcm9sbGVyIHsKICAgICAgcG9pbnRlci1ldmVudHM6IGF1dG87CiAgICB9CgogICAgW2lvc10gI291dGVyc2Nyb2xsZXIgewogICAgICBwb2ludGVyLWV2ZW50czogYXV0bzsKICAgICAgei1pbmRleDogLTM7CiAgICB9CgogICAgW2lvc11bc2Nyb2xsaW5nXSAjb3V0ZXJzY3JvbGxlciB7CiAgICAgIHotaW5kZXg6IDA7CiAgICB9CgogICAgW2lvc10gW2Zyb3plbl0gewogICAgICB3aWxsLWNoYW5nZTogYXV0bzsKICAgIH0KICBgOwogICAgICBWYWFkaW5HcmlkU3R5bGVzLnF1ZXJ5U2VsZWN0b3IoJ3RlbXBsYXRlJykuY29udGVudC5hcHBlbmRDaGlsZChzY3JvbGxpbmdTdHlsZXMpOwogICAgfQoKICAgIFZhYWRpbkdyaWRTdHlsZXMucmVnaXN0ZXIoJ3ZhYWRpbi1ncmlkLXN0eWxlcycpOwoKICAgIC8qKgogICAgQGxpY2Vuc2UKICAgIENvcHlyaWdodCAoYykgMjAxNyBWYWFkaW4gTHRkLgogICAgVGhpcyBwcm9ncmFtIGlzIGF2YWlsYWJsZSB1bmRlciBBcGFjaGUgTGljZW5zZSBWZXJzaW9uIDIuMCwgYXZhaWxhYmxlIGF0IGh0dHBzOi8vdmFhZGluLmNvbS9saWNlbnNlLwogICAgKi8KCiAgICBjb25zdCBUT1VDSF9ERVZJQ0UgPSAoKCkgPT4gewogICAgICB0cnkgewogICAgICAgIGRvY3VtZW50LmNyZWF0ZUV2ZW50KCdUb3VjaEV2ZW50Jyk7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0gY2F0Y2ggKGUpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgIH0pKCk7CgogICAgLyoqCiAgICAgKgogICAgICogYDx2YWFkaW4tZ3JpZD5gIGlzIGEgZnJlZSwgaGlnaCBxdWFsaXR5IGRhdGEgZ3JpZCAvIGRhdGEgdGFibGUgV2ViIENvbXBvbmVudC4gVGhlIGNvbnRlbnQgb2YgdGhlCiAgICAgKiB0aGUgZ3JpZCBjYW4gYmUgcG9wdWxhdGVkIGluIHR3byB3YXlzOiBpbXBlcmF0aXZlbHkgYnkgdXNpbmcgcmVuZGVyZXIgY2FsbGJhY2sgZnVuY3Rpb24gYW5kCiAgICAgKiBkZWNsYXJhdGl2ZWx5IGJ5IHVzaW5nIFBvbHltZXIncyBUZW1wbGF0ZXMuCiAgICAgKgogICAgICogIyMjIFF1aWNrIFN0YXJ0CiAgICAgKgogICAgICogU3RhcnQgd2l0aCBhbiBhc3NpZ25pbmcgYW4gYXJyYXkgdG8gdGhlIFtgaXRlbXNgXSgjL2VsZW1lbnRzL3ZhYWRpbi1ncmlkI3Byb3BlcnR5LWl0ZW1zKSBwcm9wZXJ0eSB0byB2aXN1YWxpemUgeW91ciBkYXRhLgogICAgICoKICAgICAqIFVzZSB0aGUgW2A8dmFhZGluLWdyaWQtY29sdW1uPmBdKCMvZWxlbWVudHMvdmFhZGluLWdyaWQtY29sdW1uKSBlbGVtZW50IHRvIGNvbmZpZ3VyZSB0aGUgZ3JpZCBjb2x1bW5zLiBTZXQgYHBhdGhgIGFuZCBgaGVhZGVyYAogICAgICogc2hvcnRoYW5kIHByb3BlcnRpZXMgZm9yIHRoZSBjb2x1bW5zIHRvIGRlZmluZSB3aGF0IGdldHMgcmVuZGVyZWQgaW4gdGhlIGNlbGxzIG9mIHRoZSBjb2x1bW4uCiAgICAgKgogICAgICogIyMjIyBFeGFtcGxlOgogICAgICogYGBgaHRtbAogICAgICogPHZhYWRpbi1ncmlkPgogICAgICogICA8dmFhZGluLWdyaWQtY29sdW1uIHBhdGg9Im5hbWUuZmlyc3QiIGhlYWRlcj0iRmlyc3QgbmFtZSI+PC92YWFkaW4tZ3JpZC1jb2x1bW4+CiAgICAgKiAgIDx2YWFkaW4tZ3JpZC1jb2x1bW4gcGF0aD0ibmFtZS5sYXN0IiBoZWFkZXI9Ikxhc3QgbmFtZSI+PC92YWFkaW4tZ3JpZC1jb2x1bW4+CiAgICAgKiAgIDx2YWFkaW4tZ3JpZC1jb2x1bW4gcGF0aD0iZW1haWwiPjwvdmFhZGluLWdyaWQtY29sdW1uPgogICAgICogPC92YWFkaW4tZ3JpZD4KICAgICAqIGBgYAogICAgICoKICAgICAqIEZvciBjdXN0b20gY29udGVudCBgdmFhZGluLWdyaWQtY29sdW1uYCBlbGVtZW50IHByb3ZpZGVzIHlvdSB3aXRoIHRocmVlIHR5cGVzIG9mIGByZW5kZXJlcmAgY2FsbGJhY2sgZnVuY3Rpb25zOiBgaGVhZGVyUmVuZGVyZXJgLAogICAgICogYHJlbmRlcmVyYCBhbmQgYGZvb3RlclJlbmRlcmVyYC4KICAgICAqCiAgICAgKiBFYWNoIG9mIHRob3NlIHJlbmRlcmVyIGZ1bmN0aW9ucyBwcm92aWRlcyBgcm9vdGAsIGBjb2x1bW5gLCBgcm93RGF0YWAgYXJndW1lbnRzIHdoZW4gYXBwbGljYWJsZS4KICAgICAqIEdlbmVyYXRlIERPTSBjb250ZW50LCBhcHBlbmQgaXQgdG8gdGhlIGByb290YCBlbGVtZW50IGFuZCBjb250cm9sIHRoZSBzdGF0ZQogICAgICogb2YgdGhlIGhvc3QgZWxlbWVudCBieSBhY2Nlc3NpbmcgYGNvbHVtbmAuIEJlZm9yZSBnZW5lcmF0aW5nIG5ldyBjb250ZW50LAogICAgICogdXNlcnMgYXJlIGFibGUgdG8gY2hlY2sgaWYgdGhlcmUgaXMgYWxyZWFkeSBjb250ZW50IGluIGByb290YCBmb3IgcmV1c2luZyBpdC4KICAgICAqCiAgICAgKiBSZW5kZXJlcnMgYXJlIGNhbGxlZCBvbiBpbml0aWFsaXphdGlvbiBvZiBuZXcgY29sdW1uIGNlbGxzIGFuZCBlYWNoIHRpbWUgdGhlCiAgICAgKiByZWxhdGVkIHJvdyBkYXRhIGlzIHVwZGF0ZWQuIERPTSBnZW5lcmF0ZWQgZHVyaW5nIHRoZSByZW5kZXJlciBjYWxsIGNhbiBiZSByZXVzZWQKICAgICAqIGluIHRoZSBuZXh0IHJlbmRlcmVyIGNhbGwgYW5kIHdpbGwgYmUgcHJvdmlkZWQgd2l0aCB0aGUgYHJvb3RgIGFyZ3VtZW50LgogICAgICogT24gZmlyc3QgY2FsbCBpdCB3aWxsIGJlIGVtcHR5LgogICAgICoKICAgICAqICMjIyMgRXhhbXBsZToKICAgICAqIGBgYGh0bWwKICAgICAqIDx2YWFkaW4tZ3JpZD4KICAgICAqICAgPHZhYWRpbi1ncmlkLWNvbHVtbj48L3ZhYWRpbi1ncmlkLWNvbHVtbj4KICAgICAqICAgPHZhYWRpbi1ncmlkLWNvbHVtbj48L3ZhYWRpbi1ncmlkLWNvbHVtbj4KICAgICAqICAgPHZhYWRpbi1ncmlkLWNvbHVtbj48L3ZhYWRpbi1ncmlkLWNvbHVtbj4KICAgICAqIDwvdmFhZGluLWdyaWQ+CiAgICAgKiBgYGAKICAgICAqIGBgYGpzCiAgICAgKiBjb25zdCBncmlkID0gZG9jdW1lbnQucXVlcnlTZWxlY3RvcigndmFhZGluLWdyaWQnKTsKICAgICAqIGdyaWQuaXRlbXMgPSBbeyduYW1lJzogJ0pvaG4nLCAnc3VybmFtZSc6ICdMZW5ub24nLCAncm9sZSc6ICdzaW5nZXInfSwKICAgICAqICAgICAgICAgICAgICAgeyduYW1lJzogJ1JpbmdvJywgJ3N1cm5hbWUnOiAnU3RhcnInLCAncm9sZSc6ICdkcnVtcyd9XTsKICAgICAqCiAgICAgKiBjb25zdCBjb2x1bW5zID0gZ3JpZC5xdWVyeVNlbGVjdG9yQWxsKCd2YWFkaW4tZ3JpZC1jb2x1bW4nKTsKICAgICAqCiAgICAgKiBjb2x1bW5zWzBdLmhlYWRlclJlbmRlcmVyID0gZnVuY3Rpb24ocm9vdCkgewogICAgICogICByb290LnRleHRDb250ZW50ID0gJ05hbWUnOwogICAgICogfTsKICAgICAqIGNvbHVtbnNbMF0ucmVuZGVyZXIgPSBmdW5jdGlvbihyb290LCBjb2x1bW4sIHJvd0RhdGEpIHsKICAgICAqICAgcm9vdC50ZXh0Q29udGVudCA9IHJvd0RhdGEuaXRlbS5uYW1lOwogICAgICogfTsKICAgICAqCiAgICAgKiBjb2x1bW5zWzFdLmhlYWRlclJlbmRlcmVyID0gZnVuY3Rpb24ocm9vdCkgewogICAgICogICByb290LnRleHRDb250ZW50ID0gJ1N1cm5hbWUnOwogICAgICogfTsKICAgICAqIGNvbHVtbnNbMV0ucmVuZGVyZXIgPSBmdW5jdGlvbihyb290LCBjb2x1bW4sIHJvd0RhdGEpIHsKICAgICAqICAgcm9vdC50ZXh0Q29udGVudCA9IHJvd0RhdGEuaXRlbS5zdXJuYW1lOwogICAgICogfTsKICAgICAqCiAgICAgKiBjb2x1bW5zWzJdLmhlYWRlclJlbmRlcmVyID0gZnVuY3Rpb24ocm9vdCkgewogICAgICogICByb290LnRleHRDb250ZW50ID0gJ1JvbGUnOwogICAgICogfTsKICAgICAqIGNvbHVtbnNbMl0ucmVuZGVyZXIgPSBmdW5jdGlvbihyb290LCBjb2x1bW4sIHJvd0RhdGEpIHsKICAgICAqICAgcm9vdC50ZXh0Q29udGVudCA9IHJvd0RhdGEuaXRlbS5yb2xlOwogICAgICogfTsKICAgICAqIGBgYAogICAgICoKICAgICAqIEFsdGVybmF0aXZlbHksIHRoZSBjb250ZW50IGNhbiBiZSBwcm92aWRlZCB3aXRoIFBvbHltZXIncyBUZW1wbGF0ZXM6CiAgICAgKgogICAgICogIyMjIyBFeGFtcGxlOgogICAgICogYGBgaHRtbAogICAgICogPHZhYWRpbi1ncmlkIGl0ZW1zPSdbeyJuYW1lIjogIkpvaG4iLCAic3VybmFtZSI6ICJMZW5ub24iLCAicm9sZSI6ICJzaW5nZXIifSwKICAgICAqIHsibmFtZSI6ICJSaW5nbyIsICJzdXJuYW1lIjogIlN0YXJyIiwgInJvbGUiOiAiZHJ1bXMifV0nPgogICAgICogICA8dmFhZGluLWdyaWQtY29sdW1uPgogICAgICogICAgIDx0ZW1wbGF0ZSBjbGFzcz0iaGVhZGVyIj5OYW1lPC90ZW1wbGF0ZT4KICAgICAqICAgICA8dGVtcGxhdGU+W1tpdGVtLm5hbWVdXTwvdGVtcGxhdGU+CiAgICAgKiAgIDwvdmFhZGluLWdyaWQtY29sdW1uPgogICAgICogICA8dmFhZGluLWdyaWQtY29sdW1uPgogICAgICogICAgIDx0ZW1wbGF0ZSBjbGFzcz0iaGVhZGVyIj5TdXJuYW1lPC90ZW1wbGF0ZT4KICAgICAqICAgICA8dGVtcGxhdGU+W1tpdGVtLnN1cm5hbWVdXTwvdGVtcGxhdGU+CiAgICAgKiAgIDwvdmFhZGluLWdyaWQtY29sdW1uPgogICAgICogICA8dmFhZGluLWdyaWQtY29sdW1uPgogICAgICogICAgIDx0ZW1wbGF0ZSBjbGFzcz0iaGVhZGVyIj5Sb2xlPC90ZW1wbGF0ZT4KICAgICAqICAgICA8dGVtcGxhdGU+W1tpdGVtLnJvbGVdXTwvdGVtcGxhdGU+CiAgICAgKiAgIDwvdmFhZGluLWdyaWQtY29sdW1uPgogICAgICogPC92YWFkaW4tZ3JpZD4KICAgICAqIGBgYAogICAgICoKICAgICAqIFRoZSBmb2xsb3dpbmcgaGVscGVyIGVsZW1lbnRzIGNhbiBiZSB1c2VkIGZvciBmdXJ0aGVyIGN1c3RvbWl6YXRpb246CiAgICAgKiAtIFtgPHZhYWRpbi1ncmlkLWNvbHVtbi1ncm91cD5gXSgjL2VsZW1lbnRzL3ZhYWRpbi1ncmlkLWNvbHVtbi1ncm91cCkKICAgICAqIC0gW2A8dmFhZGluLWdyaWQtZmlsdGVyPmBdKCMvZWxlbWVudHMvdmFhZGluLWdyaWQtZmlsdGVyKQogICAgICogLSBbYDx2YWFkaW4tZ3JpZC1zb3J0ZXI+YF0oIy9lbGVtZW50cy92YWFkaW4tZ3JpZC1zb3J0ZXIpCiAgICAgKiAtIFtgPHZhYWRpbi1ncmlkLXNlbGVjdGlvbi1jb2x1bW4+YF0oIy9lbGVtZW50cy92YWFkaW4tZ3JpZC1zZWxlY3Rpb24tY29sdW1uKQogICAgICogLSBbYDx2YWFkaW4tZ3JpZC10cmVlLXRvZ2dsZT5gXSgjL2VsZW1lbnRzL3ZhYWRpbi1ncmlkLXRyZWUtdG9nZ2xlKQogICAgICoKICAgICAqIF9fTm90ZSB0aGF0IHRoZSBoZWxwZXIgZWxlbWVudHMgbXVzdCBiZSBleHBsaWNpdGx5IGltcG9ydGVkLl9fCiAgICAgKiBJZiB5b3Ugd2FudCB0byBpbXBvcnQgZXZlcnl0aGluZyBhdCBvbmNlIHlvdSBjYW4gdXNlIHRoZSBgYWxsLWltcG9ydHMuaHRtbGAgYnVuZGxlLgogICAgICoKICAgICAqIEEgY29sdW1uIHRlbXBsYXRlIGNhbiBiZSBkZWNvcmF0ZWQgd2l0aCBvbmUgdGhlIGZvbGxvd2luZyBjbGFzcyBuYW1lcyB0byBzcGVjaWZ5IGl0cyBwdXJwb3NlCiAgICAgKiAtIGBoZWFkZXJgOiBNYXJrcyBhIGhlYWRlciB0ZW1wbGF0ZQogICAgICogLSBgZm9vdGVyYDogTWFya3MgYSBmb290ZXIgdGVtcGxhdGUKICAgICAqIC0gYHJvdy1kZXRhaWxzYDogTWFya3MgYSByb3cgZGV0YWlscyB0ZW1wbGF0ZQogICAgICoKICAgICAqIFRoZSBmb2xsb3dpbmcgYnVpbHQtaW4gdGVtcGxhdGUgdmFyaWFibGVzIGNhbiBiZSBib3VuZCB0byBpbnNpZGUgdGhlIGNvbHVtbiB0ZW1wbGF0ZXM6CiAgICAgKiAtIGBbW2luZGV4XV1gOiBOdW1iZXIgcmVwcmVzZW50aW5nIHRoZSByb3cgaW5kZXgKICAgICAqIC0gYFtbaXRlbV1dYCBhbmQgaXQncyBzdWItcHJvcGVydGllczogRGF0YSBvYmplY3QgKHByb3ZpZGVkIGJ5IGEgZGF0YSBwcm92aWRlciAvIGl0ZW1zIGFycmF5KQogICAgICogLSBge3tzZWxlY3RlZH19YDogVHJ1ZSBpZiB0aGUgaXRlbSBpcyBzZWxlY3RlZCAoY2FuIGJlIHR3by13YXkgYm91bmQpCiAgICAgKiAtIGB7e2RldGFpbHNPcGVuZWR9fWA6IFRydWUgaWYgdGhlIGl0ZW0gaGFzIHJvdyBkZXRhaWxzIG9wZW5lZCAoY2FuIGJlIHR3by13YXkgYm91bmQpCiAgICAgKiAtIGB7e2V4cGFuZGVkfX1gOiBUcnVlIGlmIHRoZSBpdGVtIGhhcyB0cmVlIHN1YmxldmVsIGV4cGFuZGVkIChjYW4gYmUgdHdvLXdheSBib3VuZCkKICAgICAqIC0gYFtbbGV2ZWxdXWA6IE51bWJlciBvZiB0aGUgdHJlZSBzdWJsZXZlbCBvZiB0aGUgaXRlbSwgZmlyc3QgbGV2ZWwtaXRlbXMgaGF2ZSAwCiAgICAgKgogICAgICogIyMjIExhenkgTG9hZGluZyB3aXRoIEZ1bmN0aW9uIERhdGEgUHJvdmlkZXIKICAgICAqCiAgICAgKiBJbiBhZGRpdGlvbiB0byBhc3NpZ25pbmcgYW4gYXJyYXkgdG8gdGhlIGl0ZW1zIHByb3BlcnR5LCB5b3UgY2FuIGFsdGVybmF0aXZlbHkKICAgICAqIHByb3ZpZGUgdGhlIGA8dmFhZGluLWdyaWQ+YCBkYXRhIHRocm91Z2ggdGhlCiAgICAgKiBbYGRhdGFQcm92aWRlcmBdKCMvZWxlbWVudHMvdmFhZGluLWdyaWQjcHJvcGVydHktZGF0YVByb3ZpZGVyKSBmdW5jdGlvbiBwcm9wZXJ0eS4KICAgICAqIFRoZSBgPHZhYWRpbi1ncmlkPmAgY2FsbHMgdGhpcyBmdW5jdGlvbiBsYXppbHksIG9ubHkgd2hlbiBpdCBuZWVkcyBtb3JlIGRhdGEKICAgICAqIHRvIGJlIGRpc3BsYXllZC4KICAgICAqCiAgICAgKiBTZWUgdGhlIFtgZGF0YVByb3ZpZGVyYF0oIy9lbGVtZW50cy92YWFkaW4tZ3JpZCNwcm9wZXJ0eS1kYXRhUHJvdmlkZXIpIGluCiAgICAgKiB0aGUgQVBJIHJlZmVyZW5jZSBiZWxvdyBmb3IgdGhlIGRldGFpbGVkIGRhdGEgcHJvdmlkZXIgYXJndW1lbnRzIGRlc2NyaXB0aW9uLAogICAgICogYW5kIHRoZSDigJxBc3NpZ25pbmcgRGF0YeKAnSBwYWdlIGluIHRoZSBkZW1vcy4KICAgICAqCiAgICAgKiBfX05vdGUgdGhhdCBleHBhbmRpbmcgdGhlIHRyZWUgZ3JpZCdzIGl0ZW0gd2lsbCB0cmlnZ2VyIGEgY2FsbCB0byB0aGUgYGRhdGFQcm92aWRlcmAuX18KICAgICAqCiAgICAgKiBfX0Fsc28sIG5vdGUgdGhhdCB3aGVuIHVzaW5nIGZ1bmN0aW9uIGRhdGEgcHJvdmlkZXJzLCB0aGUgdG90YWwgbnVtYmVyIG9mIGl0ZW1zCiAgICAgKiBuZWVkcyB0byBiZSBzZXQgbWFudWFsbHkuIFRoZSB0b3RhbCBudW1iZXIgb2YgaXRlbXMgY2FuIGJlIHJldHVybmVkCiAgICAgKiBpbiB0aGUgc2Vjb25kIGFyZ3VtZW50IG9mIHRoZSBkYXRhIHByb3ZpZGVyIGNhbGxiYWNrOl9fCiAgICAgKgogICAgICogYGBgamF2YXNjcmlwdAogICAgICogZ3JpZC5kYXRhUHJvdmlkZXIgPSBmdW5jdGlvbihwYXJhbXMsIGNhbGxiYWNrKSB7CiAgICAgKiAgIHZhciB1cmwgPSAnaHR0cHM6Ly9hcGkuZXhhbXBsZS9kYXRhJyArCiAgICAgKiAgICAgICAnP3BhZ2U9JyArIHBhcmFtcy5wYWdlICsgICAgICAgIC8vIHRoZSByZXF1ZXN0ZWQgcGFnZSBpbmRleAogICAgICogICAgICAgJyZwZXJfcGFnZT0nICsgcGFyYW1zLnBhZ2VTaXplOyAvLyBudW1iZXIgb2YgaXRlbXMgb24gdGhlIHBhZ2UKICAgICAqICAgdmFyIHhociA9IG5ldyBYTUxIdHRwUmVxdWVzdCgpOwogICAgICogICB4aHIub25sb2FkID0gZnVuY3Rpb24oKSB7CiAgICAgKiAgICAgdmFyIHJlc3BvbnNlID0gSlNPTi5wYXJzZSh4aHIucmVzcG9uc2VUZXh0KTsKICAgICAqICAgICBjYWxsYmFjaygKICAgICAqICAgICAgIHJlc3BvbnNlLmVtcGxveWVlcywgLy8gcmVxdWVzdGVkIHBhZ2Ugb2YgaXRlbXMKICAgICAqICAgICAgIHJlc3BvbnNlLnRvdGFsU2l6ZSAgLy8gdG90YWwgbnVtYmVyIG9mIGl0ZW1zCiAgICAgKiAgICAgKTsKICAgICAqICAgfTsKICAgICAqICAgeGhyLm9wZW4oJ0dFVCcsIHVybCwgdHJ1ZSk7CiAgICAgKiAgIHhoci5zZW5kKCk7CiAgICAgKiB9OwogICAgICogYGBgCiAgICAgKgogICAgICogX19BbHRlcm5hdGl2ZWx5LCB5b3UgY2FuIHVzZSB0aGUgYHNpemVgIHByb3BlcnR5IHRvIHNldCB0aGUgdG90YWwgbnVtYmVyIG9mIGl0ZW1zOl9fCiAgICAgKgogICAgICogYGBgamF2YXNjcmlwdAogICAgICogZ3JpZC5zaXplID0gMjAwOyAvLyBUaGUgdG90YWwgbnVtYmVyIG9mIGl0ZW1zCiAgICAgKiBncmlkLmRhdGFQcm92aWRlciA9IGZ1bmN0aW9uKHBhcmFtcywgY2FsbGJhY2spIHsKICAgICAqICAgdmFyIHVybCA9ICdodHRwczovL2FwaS5leGFtcGxlL2RhdGEnICsKICAgICAqICAgICAgICc/cGFnZT0nICsgcGFyYW1zLnBhZ2UgKyAgICAgICAgLy8gdGhlIHJlcXVlc3RlZCBwYWdlIGluZGV4CiAgICAgKiAgICAgICAnJnBlcl9wYWdlPScgKyBwYXJhbXMucGFnZVNpemU7IC8vIG51bWJlciBvZiBpdGVtcyBvbiB0aGUgcGFnZQogICAgICogICB2YXIgeGhyID0gbmV3IFhNTEh0dHBSZXF1ZXN0KCk7CiAgICAgKiAgIHhoci5vbmxvYWQgPSBmdW5jdGlvbigpIHsKICAgICAqICAgICB2YXIgcmVzcG9uc2UgPSBKU09OLnBhcnNlKHhoci5yZXNwb25zZVRleHQpOwogICAgICogICAgIGNhbGxiYWNrKHJlc3BvbnNlLmVtcGxveWVlcyk7CiAgICAgKiAgIH07CiAgICAgKiAgIHhoci5vcGVuKCdHRVQnLCB1cmwsIHRydWUpOwogICAgICogICB4aHIuc2VuZCgpOwogICAgICogfTsKICAgICAqIGBgYAogICAgICoKICAgICAqICMjIyBTdHlsaW5nCiAgICAgKgogICAgICogVGhlIGZvbGxvd2luZyBzaGFkb3cgRE9NIHBhcnRzIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CiAgICAgKgogICAgICogUGFydCBuYW1lIHwgRGVzY3JpcHRpb24KICAgICAqIC0tLS0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLS0tLQogICAgICogYHJvd2AgfCBSb3cgaW4gdGhlIGludGVybmFsIHRhYmxlCiAgICAgKiBgY2VsbGAgfCBDZWxsIGluIHRoZSBpbnRlcm5hbCB0YWJsZQogICAgICogYGhlYWRlci1jZWxsYCB8IEhlYWRlciBjZWxsIGluIHRoZSBpbnRlcm5hbCB0YWJsZQogICAgICogYGJvZHktY2VsbGAgfCBCb2R5IGNlbGwgaW4gdGhlIGludGVybmFsIHRhYmxlCiAgICAgKiBgZm9vdGVyLWNlbGxgIHwgRm9vdGVyIGNlbGwgaW4gdGhlIGludGVybmFsIHRhYmxlCiAgICAgKiBgZGV0YWlscy1jZWxsYCB8IFJvdyBkZXRhaWxzIGNlbGwgaW4gdGhlIGludGVybmFsIHRhYmxlCiAgICAgKiBgcmVzaXplLWhhbmRsZWAgfCBIYW5kbGUgZm9yIHJlc2l6aW5nIHRoZSBjb2x1bW5zCiAgICAgKiBgcmVvcmRlci1naG9zdGAgfCBHaG9zdCBlbGVtZW50IG9mIHRoZSBoZWFkZXIgY2VsbCBiZWluZyBkcmFnZ2VkCiAgICAgKgogICAgICogVGhlIGZvbGxvd2luZyBzdGF0ZSBhdHRyaWJ1dGVzIGFyZSBhdmFpbGFibGUgZm9yIHN0eWxpbmc6CiAgICAgKgogICAgICogQXR0cmlidXRlICAgIHwgRGVzY3JpcHRpb24gfCBQYXJ0IG5hbWUKICAgICAqIC0tLS0tLS0tLS0tLS18LS0tLS0tLS0tLS0tLXwtLS0tLS0tLS0tLS0KICAgICAqIGBsb2FkaW5nYCB8IFNldCB3aGVuIHRoZSBncmlkIGlzIGxvYWRpbmcgZGF0YSBmcm9tIGRhdGEgcHJvdmlkZXIgfCA6aG9zdAogICAgICogYGludGVyYWN0aW5nYCB8IEtleWJvYXJkIG5hdmlnYXRpb24gaW4gaW50ZXJhY3Rpb24gbW9kZSB8IDpob3N0CiAgICAgKiBgbmF2aWdhdGluZ2AgfCBLZXlib2FyZCBuYXZpZ2F0aW9uIGluIG5hdmlnYXRpb24gbW9kZSB8IDpob3N0CiAgICAgKiBgb3ZlcmZsb3dgIHwgU2V0IHdoZW4gcm93cyBhcmUgb3ZlcmZsb3dpbmcgdGhlIGdyaWQgdmlld3BvcnQuIFBvc3NpYmxlIHZhbHVlczogYHRvcGAsIGBib3R0b21gLCBgbGVmdGAsIGByaWdodGAgfCA6aG9zdAogICAgICogYHJlb3JkZXJpbmdgIHwgU2V0IHdoZW4gdGhlIGdyaWQncyBjb2x1bW5zIGFyZSBiZWluZyByZW9yZGVyZWQgfCA6aG9zdAogICAgICogYGRyYWdvdmVyYCB8IFNldCB3aGVuIHRoZSBncmlkIChub3QgYSBzcGVjaWZpYyByb3cpIGlzIGRyYWdnZWQgb3ZlciB8IDpob3N0CiAgICAgKiBgZHJhZ2dpbmctcm93c2AgOiBTZXQgd2hlbiBncmlkIHJvd3MgYXJlIGRyYWdnZWQgIHwgOmhvc3QKICAgICAqIGByZW9yZGVyLXN0YXR1c2AgfCBSZWZsZWN0cyB0aGUgc3RhdHVzIG9mIGEgY2VsbCB3aGlsZSBjb2x1bW5zIGFyZSBiZWluZyByZW9yZGVyZWQgfCBjZWxsCiAgICAgKiBgZnJvemVuYCB8IEZyb3plbiBjZWxsIHwgY2VsbAogICAgICogYGxhc3QtZnJvemVuYCB8IExhc3QgZnJvemVuIGNlbGwgfCBjZWxsCiAgICAqICogYGZpcnN0LWNvbHVtbmAgfCBGaXJzdCB2aXNpYmxlIGNlbGwgb24gYSByb3cgfCBjZWxsCiAgICAgKiBgbGFzdC1jb2x1bW5gIHwgTGFzdCB2aXNpYmxlIGNlbGwgb24gYSByb3cgfCBjZWxsCiAgICAgKiBgc2VsZWN0ZWRgIHwgU2VsZWN0ZWQgcm93IHwgcm93CiAgICAgKiBgZXhwYW5kZWRgIHwgRXhwYW5kZWQgcm93IHwgcm93CiAgICAgKiBgZGV0YWlscy1vcGVuZWRgIHwgUm93IHdpdGggZGV0YWlscyBvcGVuIHwgcm93CiAgICAgKiBgbG9hZGluZ2AgfCBSb3cgdGhhdCBpcyB3YWl0aW5nIGZvciBkYXRhIGZyb20gZGF0YSBwcm92aWRlciB8IHJvdwogICAgICogYG9kZGAgfCBPZGQgcm93IHwgcm93CiAgICAgKiBgZmlyc3RgIHwgVGhlIGZpcnN0IGJvZHkgcm93IHwgcm93CiAgICAgKiBgZHJhZ3N0YXJ0YCB8IFNldCBmb3Igb25lIGZyYW1lIHdoZW4gZHJhZyBvZiBhIHJvdyBpcyBzdGFydGluZy4gVGhlIHZhbHVlIGlzIGEgbnVtYmVyIHdoZW4gbXVsdGlwbGUgcm93cyBhcmUgZHJhZ2dlZCB8IHJvdwogICAgICogYGRyYWdvdmVyYCB8IFNldCB3aGVuIHRoZSByb3cgaXMgZHJhZ2dlZCBvdmVyIHwgcm93CiAgICAgKiBgZHJhZy1kaXNhYmxlZGAgfCBTZXQgdG8gYSByb3cgdGhhdCBpc24ndCBhdmFpbGFibGUgZm9yIGRyYWdnaW5nIHwgcm93CiAgICAgKiBgZHJvcC1kaXNhYmxlZGAgfCBTZXQgdG8gYSByb3cgdGhhdCBjYW4ndCBiZSBkcm9wcGVkIG9uIHRvcCBvZiB8IHJvdwogICAgICoKICAgICAqIFNlZSBbVGhlbWFibGVNaXhpbiDigJMgaG93IHRvIGFwcGx5IHN0eWxlcyBmb3Igc2hhZG93IHBhcnRzXShodHRwczovL2dpdGh1Yi5jb20vdmFhZGluL3ZhYWRpbi10aGVtYWJsZS1taXhpbi93aWtpKQogICAgICoKICAgICAqIEBleHRlbmRzIFBvbHltZXJFbGVtZW50CiAgICAgKiBAbWl4ZXMgVGhlbWFibGVNaXhpbgogICAgICogQG1peGVzIEdyaWQuQTExeU1peGluCiAgICAgKiBAbWl4ZXMgR3JpZC5BY3RpdmVJdGVtTWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLkFycmF5RGF0YVByb3ZpZGVyTWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLkNvbHVtblJlc2l6aW5nTWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLkRhdGFQcm92aWRlck1peGluCiAgICAgKiBAbWl4ZXMgR3JpZC5EeW5hbWljQ29sdW1uc01peGluCiAgICAgKiBAbWl4ZXMgR3JpZC5GaWx0ZXJNaXhpbgogICAgICogQG1peGVzIEdyaWQuUm93RGV0YWlsc01peGluCiAgICAgKiBAbWl4ZXMgR3JpZC5TY3JvbGxNaXhpbgogICAgICogQG1peGVzIEdyaWQuU2VsZWN0aW9uTWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLlNvcnRNaXhpbgogICAgICogQG1peGVzIEdyaWQuS2V5Ym9hcmROYXZpZ2F0aW9uTWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLkNvbHVtblJlb3JkZXJpbmdNaXhpbgogICAgICogQG1peGVzIEdyaWQuRXZlbnRDb250ZXh0TWl4aW4KICAgICAqIEBtaXhlcyBHcmlkLlN0eWxpbmdNaXhpbgogICAgICogQG1peGVzIEdyaWQuRHJhZ0FuZERyb3BNaXhpbgogICAgICogQGRlbW8gZGVtby9pbmRleC5odG1sCiAgICAgKi8KICAgIGNsYXNzIEdyaWRFbGVtZW50IGV4dGVuZHMKICAgICAgRWxlbWVudE1peGluJDEoCiAgICAgICAgVGhlbWFibGVNaXhpbigKICAgICAgICAgIERhdGFQcm92aWRlck1peGluKAogICAgICAgICAgICBBcnJheURhdGFQcm92aWRlck1peGluKAogICAgICAgICAgICAgIER5bmFtaWNDb2x1bW5zTWl4aW4oCiAgICAgICAgICAgICAgICBBY3RpdmVJdGVtTWl4aW4oCiAgICAgICAgICAgICAgICAgIFNjcm9sbE1peGluKAogICAgICAgICAgICAgICAgICAgIFNlbGVjdGlvbk1peGluKAogICAgICAgICAgICAgICAgICAgICAgU29ydE1peGluKAogICAgICAgICAgICAgICAgICAgICAgICBSb3dEZXRhaWxzTWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgS2V5Ym9hcmROYXZpZ2F0aW9uTWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgICBBMTF5TWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEZpbHRlck1peGluKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENvbHVtblJlb3JkZXJpbmdNaXhpbigKICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIENvbHVtblJlc2l6aW5nTWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEV2ZW50Q29udGV4dE1peGluKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIERyYWdBbmREcm9wTWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBTdHlsaW5nTWl4aW4oCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIEdyaWRTY3JvbGxlckVsZW1lbnQpKSkpKSkpKSkpKSkpKSkpKSkgewogICAgICBzdGF0aWMgZ2V0IHRlbXBsYXRlKCkgewogICAgICAgIHJldHVybiBodG1sYAogICAgPHN0eWxlIGluY2x1ZGU9InZhYWRpbi1ncmlkLXN0eWxlcyI+PC9zdHlsZT4KCiAgICA8ZGl2IGlkPSJzY3JvbGxlciIgbm8tc2Nyb2xsYmFyc1wkPSJbWyFfc2Nyb2xsYmFyV2lkdGhdXSIgd2hlZWwtc2Nyb2xsaW5nXCQ9IltbX3doZWVsU2Nyb2xsaW5nXV0iIHNhZmFyaVwkPSJbW19zYWZhcmldXSIgaW9zXCQ9IltbX2lvc11dIiBsb2FkaW5nXCQ9IltbbG9hZGluZ11dIiBlZGdlXCQ9IltbX2VkZ2VdXSIgZmlyZWZveFwkPSJbW19maXJlZm94XV0iIGllXCQ9IltbX2llXV0iIGNvbHVtbi1yZW9yZGVyaW5nLWFsbG93ZWRcJD0iW1tjb2x1bW5SZW9yZGVyaW5nQWxsb3dlZF1dIj4KCiAgICAgIDx0YWJsZSBpZD0idGFibGUiIHJvbGU9ImdyaWQiIGFyaWEtbXVsdGlzZWxlY3RhYmxlPSJ0cnVlIiB0YWJpbmRleD0iMCI+CiAgICAgICAgPGNhcHRpb24gaWQ9ImZpeGVkc2l6ZXIiIGNsYXNzPSJzaXplciIgcGFydD0icm93Ij48L2NhcHRpb24+CiAgICAgICAgPHRoZWFkIGlkPSJoZWFkZXIiIHJvbGU9InJvd2dyb3VwIj48L3RoZWFkPgogICAgICAgIDx0Ym9keSBpZD0iaXRlbXMiIHJvbGU9InJvd2dyb3VwIj48L3Rib2R5PgogICAgICAgIDx0Zm9vdCBpZD0iZm9vdGVyIiByb2xlPSJyb3dncm91cCI+PC90Zm9vdD4KICAgICAgPC90YWJsZT4KCiAgICAgIDxkaXYgcGFydD0icmVvcmRlci1naG9zdCI+PC9kaXY+CiAgICAgIDx2YWFkaW4tZ3JpZC1vdXRlci1zY3JvbGxlciBpZD0ib3V0ZXJzY3JvbGxlciIgX3RvdWNoLWRldmljZT0iW1tfdG91Y2hEZXZpY2VdXSIgc2Nyb2xsLXRhcmdldD0iW1tzY3JvbGxUYXJnZXRdXSIgc2Nyb2xsLWhhbmRsZXI9IltbX3RoaXNdXSIgbm8tc2Nyb2xsYmFycz0iW1shX3Njcm9sbGJhcldpZHRoXV0iPgogICAgICAgIDxkaXYgaWQ9Im91dGVyc2l6ZXIiIGNsYXNzPSJzaXplciIgcGFydD0icm93Ij48L2Rpdj4KICAgICAgPC92YWFkaW4tZ3JpZC1vdXRlci1zY3JvbGxlcj4KICAgIDwvZGl2PgoKICAgIDwhLS0gVGhlIHRlbXBsYXRlIG5lZWRzIGF0IGxlYXN0IG9uZSBzbG90IG9yIGVsc2Ugc2hhZHkgZG9lc24ndCBkaXN0cmlidXRlIC0tPgogICAgPHNsb3QgbmFtZT0ibm9kaXN0cmlidXRlIj48L3Nsb3Q+CgogICAgPGRpdiBpZD0iZm9jdXNleGl0IiB0YWJpbmRleD0iMCI+PC9kaXY+CmA7CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgaXMoKSB7CiAgICAgICAgcmV0dXJuICd2YWFkaW4tZ3JpZCc7CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgdmVyc2lvbigpIHsKICAgICAgICByZXR1cm4gJzUuNi42JzsKICAgICAgfQoKICAgICAgc3RhdGljIGdldCBvYnNlcnZlcnMoKSB7CiAgICAgICAgcmV0dXJuIFsKICAgICAgICAgICdfY29sdW1uVHJlZUNoYW5nZWQoX2NvbHVtblRyZWUsIF9jb2x1bW5UcmVlLiopJwogICAgICAgIF07CiAgICAgIH0KCiAgICAgIHN0YXRpYyBnZXQgcHJvcGVydGllcygpIHsKICAgICAgICByZXR1cm4gewoKICAgICAgICAgIF90aGlzOiB7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgdmFsdWU6IGZ1bmN0aW9uKCkgewogICAgICAgICAgICAgIHJldHVybiB0aGlzOwogICAgICAgICAgICB9CiAgICAgICAgICB9LAoKICAgICAgICAgIF9zYWZhcmk6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IC9eKCg/IWNocm9tZXxhbmRyb2lkKS4pKnNhZmFyaS9pLnRlc3QobmF2aWdhdG9yLnVzZXJBZ2VudCkKICAgICAgICAgIH0sCgogICAgICAgICAgX2lvczogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogKC9pUGFkfGlQaG9uZXxpUG9kLy50ZXN0KG5hdmlnYXRvci51c2VyQWdlbnQpICYmICF3aW5kb3cuTVNTdHJlYW0pCiAgICAgICAgICAgICAgfHwgKG5hdmlnYXRvci5wbGF0Zm9ybSA9PT0gJ01hY0ludGVsJyAmJiBuYXZpZ2F0b3IubWF4VG91Y2hQb2ludHMgPiAxKQogICAgICAgICAgfSwKCiAgICAgICAgICBfZWRnZTogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogdHlwZW9mIENTUyAhPT0gJ3VuZGVmaW5lZCcgJiYgQ1NTLnN1cHBvcnRzKCcoLW1zLWltZS1hbGlnbjphdXRvKScpCiAgICAgICAgICB9LAoKICAgICAgICAgIF9pZTogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogISEobmF2aWdhdG9yLnVzZXJBZ2VudC5tYXRjaCgvVHJpZGVudC8pICYmICFuYXZpZ2F0b3IudXNlckFnZW50Lm1hdGNoKC9NU0lFLykpCiAgICAgICAgICB9LAoKICAgICAgICAgIF9maXJlZm94OiB7CiAgICAgICAgICAgIHR5cGU6IEJvb2xlYW4sCiAgICAgICAgICAgIHZhbHVlOiBuYXZpZ2F0b3IudXNlckFnZW50LnRvTG93ZXJDYXNlKCkuaW5kZXhPZignZmlyZWZveCcpID4gLTEKICAgICAgICAgIH0sCgogICAgICAgICAgX2FuZHJvaWQ6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IC9hbmRyb2lkL2kudGVzdChuYXZpZ2F0b3IudXNlckFnZW50KQogICAgICAgICAgfSwKCiAgICAgICAgICBfdG91Y2hEZXZpY2U6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IFRPVUNIX0RFVklDRQogICAgICAgICAgfSwKCiAgICAgICAgICAvKioKICAgICAgICAgICAqIElmIHRydWUsIHRoZSBncmlkJ3MgaGVpZ2h0IGlzIGRlZmluZWQgYnkgaXRzIHJvd3MuCiAgICAgICAgICAgKgogICAgICAgICAgICogRWZmZWN0aXZlbHksIHRoaXMgZGlzYWJsZXMgdGhlIGdyaWQncyB2aXJ0dWFsIHNjcm9sbGluZyBzbyB0aGF0IGFsbCB0aGUgcm93cyBhcmUgcmVuZGVyZWQgaW4gdGhlIERPTSBhdCBvbmNlLgogICAgICAgICAgICogSWYgdGhlIGdyaWQgaGFzIGEgbGFyZ2UgbnVtYmVyIG9mIGl0ZW1zLCB1c2luZyB0aGUgZmVhdHVyZSBpcyBkaXNjb3VyYWdlZCB0byBhdm9pZCBwZXJmb3JtYW5jZSBpc3N1ZXMuCiAgICAgICAgICAgKi8KICAgICAgICAgIGhlaWdodEJ5Um93czogewogICAgICAgICAgICB0eXBlOiBCb29sZWFuLAogICAgICAgICAgICB2YWx1ZTogZmFsc2UsCiAgICAgICAgICAgIHJlZmxlY3RUb0F0dHJpYnV0ZTogdHJ1ZSwKICAgICAgICAgICAgb2JzZXJ2ZXI6ICdfaGVpZ2h0QnlSb3dzQ2hhbmdlZCcKICAgICAgICAgIH0sCiAgICAgICAgICBfcmVjYWxjdWxhdGVDb2x1bW5XaWR0aE9uY2VMb2FkaW5nRmluaXNoZWQ6IHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgdmFsdWU6IHRydWUKICAgICAgICAgIH0KICAgICAgICB9OwogICAgICB9CgogICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICBzdXBlcigpOwogICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignYW5pbWF0aW9uZW5kJywgdGhpcy5fb25BbmltYXRpb25FbmQpOwogICAgICB9CgogICAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHsKICAgICAgICBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOwogICAgICAgIHRoaXMucmVjYWxjdWxhdGVDb2x1bW5XaWR0aHMoKTsKICAgICAgfQoKICAgICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSkgewogICAgICAgIHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpOwogICAgICAgIGlmIChuYW1lID09PSAnZGlyJykgewogICAgICAgICAgdGhpcy5fX2lzUlRMID0gbmV3VmFsdWUgPT09ICdydGwnOwogICAgICAgICAgdGhpcy5fdXBkYXRlU2Nyb2xsZXJNZWFzdXJlbWVudHMoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIF9faGFzUm93c1dpdGhDbGllbnRIZWlnaHQoKSB7CiAgICAgICAgcmV0dXJuICEhQXJyYXkuZnJvbSh0aGlzLiQuaXRlbXMuY2hpbGRyZW4pLmZpbHRlcihyb3cgPT4gcm93LmNsaWVudEhlaWdodCkubGVuZ3RoOwogICAgICB9CgogICAgICBfX2l0ZW1zUmVjZWl2ZWQoKSB7CiAgICAgICAgaWYgKHRoaXMuX3JlY2FsY3VsYXRlQ29sdW1uV2lkdGhPbmNlTG9hZGluZ0ZpbmlzaGVkCiAgICAgICAgICAmJiAhdGhpcy5fY2FjaGUuaXNMb2FkaW5nKCkKICAgICAgICAgICYmIHRoaXMuX19oYXNSb3dzV2l0aENsaWVudEhlaWdodCgpKSB7CiAgICAgICAgICB0aGlzLl9yZWNhbGN1bGF0ZUNvbHVtbldpZHRoT25jZUxvYWRpbmdGaW5pc2hlZCA9IGZhbHNlOwogICAgICAgICAgdGhpcy5yZWNhbGN1bGF0ZUNvbHVtbldpZHRocygpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgLyoqCiAgICAgICAqIEBwYXJhbSB7QXJyYXk8VmFhZGluLkdyaWRDb2x1bW5FbGVtZW50Pn0gY29scyB0aGUgY29sdW1ucyB0byBhdXRvIHNpemUgYmFzZWQgb24gdGhlaXIgY29udGVudCB3aWR0aAogICAgICAgKi8KICAgICAgX3JlY2FsY3VsYXRlQ29sdW1uV2lkdGhzKGNvbHMpIHsKICAgICAgICAvLyBOb3RlOiBUaGUgYGNvbHMuZm9yRWFjaCgpYCBsb29wcyBiZWxvdyBjb3VsZCBiZSBpbXBsZW1lbnRlZCBhcyBhIHNpbmdsZSBsb29wIGJ1dCB0aGlzIGhhcyBiZWVuCiAgICAgICAgLy8gc3BsaXQgZm9yIHBlcmZvcm1hbmNlIHJlYXNvbnMgdG8gYmF0Y2ggdGhlc2Ugc2ltaWxhciBhY3Rpb25zIFt3cml0ZS9yZWFkXSB0b2dldGhlciB0byBhdm9pZAogICAgICAgIC8vIHVubmVjZXNzYXJ5IGxheW91dCB0cmFzaGluZy4KCiAgICAgICAgLy8gW3dyaXRlXSBTZXQgYXV0b21hdGljIHdpZHRoIGZvciBhbGwgY2VsbHMgKGJyZWFrcyBjb2x1bW4gYWxpZ25tZW50KQogICAgICAgIGNvbHMuZm9yRWFjaChjb2wgPT4gewogICAgICAgICAgY29sLndpZHRoID0gJ2F1dG8nOwogICAgICAgICAgY29sLl9vcmlnRmxleEdyb3cgPSBjb2wuZmxleEdyb3c7CiAgICAgICAgICBjb2wuZmxleEdyb3cgPSAwOwogICAgICAgIH0pOwogICAgICAgIC8vIFtyZWFkXSBNZWFzdXJlIG1heCBjZWxsIHdpZHRoIGluIGVhY2ggY29sdW1uCiAgICAgICAgY29scy5mb3JFYWNoKGNvbCA9PiB7CiAgICAgICAgICBjb2wuX2N1cnJlbnRXaWR0aCA9IDA7CiAgICAgICAgICAvLyBOb3RlOiBfYWxsQ2VsbHMgb25seSBjb250YWlucyBjZWxscyB3aGljaCBhcmUgY3VycmVudGx5IHJlbmRlcmVkIGluIERPTQogICAgICAgICAgY29sLl9hbGxDZWxscy5mb3JFYWNoKGMgPT4gewogICAgICAgICAgICAvLyBBZGQgMXB4IGJ1ZmZlciB0byB0aGUgb2Zmc2V0IHdpZHRoIHRvIGF2b2lkIHRvbyBuYXJyb3cgY29sdW1ucyAoc3ViLXBpeGVsIHJlbmRlcmluZykKICAgICAgICAgICAgY29uc3QgY2VsbFdpZHRoID0gYy5vZmZzZXRXaWR0aCArIDE7CiAgICAgICAgICAgIGNvbC5fY3VycmVudFdpZHRoID0gTWF0aC5tYXgoY29sLl9jdXJyZW50V2lkdGgsIGNlbGxXaWR0aCk7CiAgICAgICAgICB9KTsKICAgICAgICB9KTsKICAgICAgICAvLyBbd3JpdGVdIFNldCBjb2x1bW4gd2lkdGhzIHRvIGZpdCB3aWRlc3QgbWVhc3VyZWQgY29udGVudAogICAgICAgIGNvbHMuZm9yRWFjaChjb2wgPT4gewogICAgICAgICAgY29sLndpZHRoID0gYCR7Y29sLl9jdXJyZW50V2lkdGh9cHhgOwogICAgICAgICAgY29sLmZsZXhHcm93ID0gY29sLl9vcmlnRmxleEdyb3c7CiAgICAgICAgICBjb2wuX2N1cnJlbnRXaWR0aCA9IHVuZGVmaW5lZDsKICAgICAgICAgIGNvbC5fb3JpZ0ZsZXhHcm93ID0gdW5kZWZpbmVkOwogICAgICAgIH0pOwogICAgICB9CgogICAgICAvKioKICAgICAgICogVXBkYXRlcyB0aGUgYHdpZHRoYCBvZiBhbGwgY29sdW1ucyB3aGljaCBoYXZlIGBhdXRvV2lkdGhgIHNldCB0byBgdHJ1ZWAuCiAgICAgICAqLwogICAgICByZWNhbGN1bGF0ZUNvbHVtbldpZHRocygpIHsKICAgICAgICBpZiAoIXRoaXMuX2NvbHVtblRyZWUpIHsKICAgICAgICAgIHJldHVybjsgLy8gTm8gY29sdW1ucwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5fY2FjaGUuaXNMb2FkaW5nKCkpIHsKICAgICAgICAgIHRoaXMuX3JlY2FsY3VsYXRlQ29sdW1uV2lkdGhPbmNlTG9hZGluZ0ZpbmlzaGVkID0gdHJ1ZTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgY29uc3QgY29scyA9IHRoaXMuX2dldENvbHVtbnMoKS5maWx0ZXIoY29sID0+ICFjb2wuaGlkZGVuICYmIGNvbC5hdXRvV2lkdGgpOwogICAgICAgICAgdGhpcy5fcmVjYWxjdWxhdGVDb2x1bW5XaWR0aHMoY29scyk7CgogICAgICAgIH0KICAgICAgfQoKICAgICAgX2NyZWF0ZVNjcm9sbGVyUm93cyhjb3VudCkgewogICAgICAgIGNvbnN0IHJvd3MgPSBbXTsKICAgICAgICBmb3IgKHZhciBpID0gMDsgaSA8IGNvdW50OyBpKyspIHsKICAgICAgICAgIGNvbnN0IHJvdyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RyJyk7CiAgICAgICAgICByb3cuc2V0QXR0cmlidXRlKCdwYXJ0JywgJ3JvdycpOwogICAgICAgICAgcm93LnNldEF0dHJpYnV0ZSgncm9sZScsICdyb3cnKTsKICAgICAgICAgIGlmICh0aGlzLl9jb2x1bW5UcmVlKSB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZVJvdyhyb3csIHRoaXMuX2NvbHVtblRyZWVbdGhpcy5fY29sdW1uVHJlZS5sZW5ndGggLSAxXSwgJ2JvZHknLCBmYWxzZSwgdHJ1ZSk7CiAgICAgICAgICB9CiAgICAgICAgICByb3dzLnB1c2gocm93KTsKICAgICAgICB9CgogICAgICAgIGlmICh0aGlzLl9jb2x1bW5UcmVlKSB7CiAgICAgICAgICB0aGlzLl9jb2x1bW5UcmVlW3RoaXMuX2NvbHVtblRyZWUubGVuZ3RoIC0gMV0uZm9yRWFjaChjID0+IGMubm90aWZ5UGF0aCAmJiBjLm5vdGlmeVBhdGgoJ19jZWxscy4qJywgYy5fY2VsbHMpKTsKICAgICAgICB9CgogICAgICAgIGJlZm9yZU5leHRSZW5kZXIodGhpcywgKCkgPT4gewogICAgICAgICAgdGhpcy5fdXBkYXRlRmlyc3RBbmRMYXN0Q29sdW1uKCk7CiAgICAgICAgICB0aGlzLl9yZXNldEtleWJvYXJkTmF2aWdhdGlvbigpOwogICAgICAgIH0pOwogICAgICAgIHJldHVybiByb3dzOwogICAgICB9CgogICAgICBfZ2V0Um93VGFyZ2V0KCkgewogICAgICAgIHJldHVybiB0aGlzLiQuaXRlbXM7CiAgICAgIH0KCiAgICAgIF9jcmVhdGVDZWxsKHRhZ05hbWUpIHsKICAgICAgICBjb25zdCBjb250ZW50SWQgPSB0aGlzLl9jb250ZW50SW5kZXggPSB0aGlzLl9jb250ZW50SW5kZXggKyAxIHx8IDA7CiAgICAgICAgY29uc3Qgc2xvdE5hbWUgPSAndmFhZGluLWdyaWQtY2VsbC1jb250ZW50LScgKyBjb250ZW50SWQ7CgogICAgICAgIGNvbnN0IGNlbGxDb250ZW50ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndmFhZGluLWdyaWQtY2VsbC1jb250ZW50Jyk7CiAgICAgICAgY2VsbENvbnRlbnQuc2V0QXR0cmlidXRlKCdzbG90Jywgc2xvdE5hbWUpOwoKICAgICAgICBjb25zdCBjZWxsID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCh0YWdOYW1lKTsKICAgICAgICBjZWxsLmlkID0gc2xvdE5hbWUucmVwbGFjZSgnLWNvbnRlbnQtJywgJy0nKTsKICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgndGFiaW5kZXgnLCAnLTEnKTsKICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgncm9sZScsIHRhZ05hbWUgPT09ICd0ZCcgPyAnZ3JpZGNlbGwnIDogJ2NvbHVtbmhlYWRlcicpOwoKICAgICAgICBjb25zdCBzbG90ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnc2xvdCcpOwogICAgICAgIHNsb3Quc2V0QXR0cmlidXRlKCduYW1lJywgc2xvdE5hbWUpOwoKICAgICAgICBjZWxsLmFwcGVuZENoaWxkKHNsb3QpOwoKICAgICAgICBjZWxsLl9jb250ZW50ID0gY2VsbENvbnRlbnQ7CgogICAgICAgIC8vIFdpdGggbmF0aXZlIFNoYWRvdyBET00sIG1vdXNlZG93biBvbiBzbG90dGVkIGVsZW1lbnQgZG9lcyBub3QgZm9jdXMKICAgICAgICAvLyBmb2N1c2FibGUgc2xvdCB3cmFwcGVyLCB0aGF0IGlzIHdoeSBjZWxscyBhcmUgbm90IGZvY3VzZWQgd2l0aAogICAgICAgIC8vIG1vdXNlZG93bi4gV29ya2Fyb3VuZDogbGlzdGVuIGZvciBtb3VzZWRvd24gYW5kIGZvY3VzIG1hbnVhbGx5LgogICAgICAgIGNlbGxDb250ZW50LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlZG93bicsICgpID0+IHsKICAgICAgICAgIGlmICh3aW5kb3cuY2hyb21lKSB7CiAgICAgICAgICAgIC8vIENocm9tZSBidWc6IGZvY3VzaW5nIGJlZm9yZSBtb3VzZXVwIHByZXZlbnRzIHRleHQgc2VsZWN0aW9uLCBzZWUgaHR0cDovL2NyYnVnLmNvbS83NzE5MDMKICAgICAgICAgICAgY29uc3QgbW91c2VVcExpc3RlbmVyID0gKCkgPT4gewogICAgICAgICAgICAgIGlmICghY2VsbENvbnRlbnQuY29udGFpbnModGhpcy5nZXRSb290Tm9kZSgpLmFjdGl2ZUVsZW1lbnQpKSB7CiAgICAgICAgICAgICAgICBjZWxsLmZvY3VzKCk7CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIC8vIElmIGZvY3VzIGlzIGluIHRoZSBjZWxsIGNvbnRlbnQg4oCUIHJlc3BlY3QgaXQsIGRvIG5vdCBjaGFuZ2UuCiAgICAgICAgICAgICAgZG9jdW1lbnQucmVtb3ZlRXZlbnRMaXN0ZW5lcignbW91c2V1cCcsIG1vdXNlVXBMaXN0ZW5lciwgdHJ1ZSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNldXAnLCBtb3VzZVVwTGlzdGVuZXIsIHRydWUpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgLy8gRm9jdXMgb24gbW91c2V1cCwgb24gdGhlIG90aGVyIGhhbmQsIHJlbW92ZXMgc2VsZWN0aW9uIG9uIFNhZmFyaS4KICAgICAgICAgICAgLy8gV2F0Y2ggb3V0IHN5bmMgZm9jdXMgcmVtb3ZhbCBpc3N1ZSwgb25seSBhc3luYyBmb2N1cyB3b3JrcyBoZXJlLgogICAgICAgICAgICBzZXRUaW1lb3V0KCgpID0+IHsKICAgICAgICAgICAgICBpZiAoIWNlbGxDb250ZW50LmNvbnRhaW5zKHRoaXMuZ2V0Um9vdE5vZGUoKS5hY3RpdmVFbGVtZW50KSkgewogICAgICAgICAgICAgICAgY2VsbC5mb2N1cygpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CgogICAgICAgIHJldHVybiBjZWxsOwogICAgICB9CgogICAgICBfdXBkYXRlUm93KHJvdywgY29sdW1ucywgc2VjdGlvbiwgaXNDb2x1bW5Sb3csIG5vTm90aWZ5KSB7CiAgICAgICAgc2VjdGlvbiA9IHNlY3Rpb24gfHwgJ2JvZHknOwoKICAgICAgICBjb25zdCBjb250ZW50c0ZyYWdtZW50ID0gZG9jdW1lbnQuY3JlYXRlRG9jdW1lbnRGcmFnbWVudCgpOwoKICAgICAgICBBcnJheS5mcm9tKHJvdy5jaGlsZHJlbikuZm9yRWFjaChjZWxsID0+IGNlbGwuX3ZhY2FudCA9IHRydWUpOwogICAgICAgIHJvdy5pbm5lckhUTUwgPSAnJzsKICAgICAgICBpZiAocm93LmlkICE9PSAnb3V0ZXJzaXplcicgJiYgcm93LmlkICE9PSAnZml4ZWRzaXplcicpIHsKICAgICAgICAgIHJvdy5oaWRkZW4gPSB0cnVlOwogICAgICAgIH0KICAgICAgICBjb2x1bW5zCiAgICAgICAgICAuZmlsdGVyKGNvbHVtbiA9PiAhY29sdW1uLmhpZGRlbikKICAgICAgICAgIC5mb3JFYWNoKChjb2x1bW4sIGluZGV4LCBjb2xzKSA9PiB7CiAgICAgICAgICAgIGxldCBjZWxsOwoKICAgICAgICAgICAgaWYgKHNlY3Rpb24gPT09ICdib2R5JykgewogICAgICAgICAgICAvLyBCb2R5CiAgICAgICAgICAgICAgY29sdW1uLl9jZWxscyA9IGNvbHVtbi5fY2VsbHMgfHwgW107CiAgICAgICAgICAgICAgY2VsbCA9IGNvbHVtbi5fY2VsbHMuZmlsdGVyKGNlbGwgPT4gY2VsbC5fdmFjYW50KVswXTsKICAgICAgICAgICAgICBpZiAoIWNlbGwpIHsKICAgICAgICAgICAgICAgIGNlbGwgPSB0aGlzLl9jcmVhdGVDZWxsKCd0ZCcpOwogICAgICAgICAgICAgICAgY29sdW1uLl9jZWxscy5wdXNoKGNlbGwpOwogICAgICAgICAgICAgIH0KICAgICAgICAgICAgICBjZWxsLnNldEF0dHJpYnV0ZSgncGFydCcsICdjZWxsIGJvZHktY2VsbCcpOwogICAgICAgICAgICAgIHJvdy5hcHBlbmRDaGlsZChjZWxsKTsKCiAgICAgICAgICAgICAgaWYgKGluZGV4ID09PSBjb2xzLmxlbmd0aCAtIDEgJiYgKHRoaXMuX3Jvd0RldGFpbHNUZW1wbGF0ZSB8fCB0aGlzLnJvd0RldGFpbHNSZW5kZXJlcikpIHsKICAgICAgICAgICAgICAvLyBBZGQgZGV0YWlscyBjZWxsIGFzIGxhc3QgY2VsbCB0byBib2R5IHJvd3MKICAgICAgICAgICAgICAgIHRoaXMuX2RldGFpbHNDZWxscyA9IHRoaXMuX2RldGFpbHNDZWxscyB8fCBbXTsKICAgICAgICAgICAgICAgIGNvbnN0IGRldGFpbHNDZWxsID0gdGhpcy5fZGV0YWlsc0NlbGxzLmZpbHRlcihjZWxsID0+IGNlbGwuX3ZhY2FudClbMF0gfHwgdGhpcy5fY3JlYXRlQ2VsbCgndGQnKTsKICAgICAgICAgICAgICAgIGlmICh0aGlzLl9kZXRhaWxzQ2VsbHMuaW5kZXhPZihkZXRhaWxzQ2VsbCkgPT09IC0xKSB7CiAgICAgICAgICAgICAgICAgIHRoaXMuX2RldGFpbHNDZWxscy5wdXNoKGRldGFpbHNDZWxsKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmICghZGV0YWlsc0NlbGwuX2NvbnRlbnQucGFyZW50RWxlbWVudCkgewogICAgICAgICAgICAgICAgICBjb250ZW50c0ZyYWdtZW50LmFwcGVuZENoaWxkKGRldGFpbHNDZWxsLl9jb250ZW50KTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2NvbmZpZ3VyZURldGFpbHNDZWxsKGRldGFpbHNDZWxsKTsKICAgICAgICAgICAgICAgIHJvdy5hcHBlbmRDaGlsZChkZXRhaWxzQ2VsbCk7CiAgICAgICAgICAgICAgICB0aGlzLl9hMTF5U2V0Um93RGV0YWlsc0NlbGwocm93LCBkZXRhaWxzQ2VsbCk7CiAgICAgICAgICAgICAgICBkZXRhaWxzQ2VsbC5fdmFjYW50ID0gZmFsc2U7CiAgICAgICAgICAgICAgfQoKICAgICAgICAgICAgICBpZiAoY29sdW1uLm5vdGlmeVBhdGggJiYgIW5vTm90aWZ5KSB7CiAgICAgICAgICAgICAgICBjb2x1bW4ubm90aWZ5UGF0aCgnX2NlbGxzLionLCBjb2x1bW4uX2NlbGxzKTsKICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgIC8vIEhlYWRlciAmIGZvb3RlcgogICAgICAgICAgICAgIGNvbnN0IHRhZ05hbWUgPSBzZWN0aW9uID09PSAnaGVhZGVyJyA/ICd0aCcgOiAndGQnOwogICAgICAgICAgICAgIGlmIChpc0NvbHVtblJvdyB8fCBjb2x1bW4ubG9jYWxOYW1lID09PSAndmFhZGluLWdyaWQtY29sdW1uLWdyb3VwJykgewogICAgICAgICAgICAgICAgY2VsbCA9IGNvbHVtbltgXyR7c2VjdGlvbn1DZWxsYF0gfHwgdGhpcy5fY3JlYXRlQ2VsbCh0YWdOYW1lKTsKICAgICAgICAgICAgICAgIGNlbGwuX2NvbHVtbiA9IGNvbHVtbjsKICAgICAgICAgICAgICAgIHJvdy5hcHBlbmRDaGlsZChjZWxsKTsKICAgICAgICAgICAgICAgIGNvbHVtbltgXyR7c2VjdGlvbn1DZWxsYF0gPSBjZWxsOwogICAgICAgICAgICAgIH0gZWxzZSB7CiAgICAgICAgICAgICAgICBjb2x1bW4uX2VtcHR5Q2VsbHMgPSBjb2x1bW4uX2VtcHR5Q2VsbHMgfHwgW107CiAgICAgICAgICAgICAgICBjZWxsID0gY29sdW1uLl9lbXB0eUNlbGxzLmZpbHRlcihjZWxsID0+IGNlbGwuX3ZhY2FudClbMF0gfHwgdGhpcy5fY3JlYXRlQ2VsbCh0YWdOYW1lKTsKICAgICAgICAgICAgICAgIGNlbGwuX2NvbHVtbiA9IGNvbHVtbjsKICAgICAgICAgICAgICAgIHJvdy5hcHBlbmRDaGlsZChjZWxsKTsKICAgICAgICAgICAgICAgIGlmIChjb2x1bW4uX2VtcHR5Q2VsbHMuaW5kZXhPZihjZWxsKSA9PT0gLTEpIHsKICAgICAgICAgICAgICAgICAgY29sdW1uLl9lbXB0eUNlbGxzLnB1c2goY2VsbCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgfQogICAgICAgICAgICAgIGNlbGwuc2V0QXR0cmlidXRlKCdwYXJ0JywgYGNlbGwgJHtzZWN0aW9ufS1jZWxsYCk7CiAgICAgICAgICAgICAgdGhpcy5fX3VwZGF0ZUhlYWRlckZvb3RlclJvd1Zpc2liaWxpdHkocm93KTsKICAgICAgICAgICAgfQoKICAgICAgICAgICAgaWYgKCFjZWxsLl9jb250ZW50LnBhcmVudEVsZW1lbnQpIHsKICAgICAgICAgICAgICBjb250ZW50c0ZyYWdtZW50LmFwcGVuZENoaWxkKGNlbGwuX2NvbnRlbnQpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNlbGwuX3ZhY2FudCA9IGZhbHNlOwogICAgICAgICAgICBjZWxsLl9jb2x1bW4gPSBjb2x1bW47CiAgICAgICAgICB9KTsKCiAgICAgICAgLy8gTWlnaHQgYmUgZW1wdHkgaWYgb25seSBjYWNoZSB3YXMgdXNlZAogICAgICAgIHRoaXMuYXBwZW5kQ2hpbGQoY29udGVudHNGcmFnbWVudCk7CgogICAgICAgIHRoaXMuX2Zyb3plbkNlbGxzQ2hhbmdlZCgpOwogICAgICAgIHRoaXMuX3VwZGF0ZUZpcnN0QW5kTGFzdENvbHVtbkZvclJvdyhyb3cpOwogICAgICB9CgogICAgICBfX3VwZGF0ZUhlYWRlckZvb3RlclJvd1Zpc2liaWxpdHkocm93KSB7CiAgICAgICAgaWYgKCFyb3cpIHsKICAgICAgICAgIHJldHVybjsKICAgICAgICB9CgogICAgICAgIGNvbnN0IHZpc2libGVSb3dDZWxscyA9IEFycmF5LmZyb20ocm93LmNoaWxkcmVuKS5maWx0ZXIoY2VsbCA9PiB7CiAgICAgICAgICBjb25zdCBjb2x1bW4gPSBjZWxsLl9jb2x1bW47CiAgICAgICAgICBpZiAoY29sdW1uLl9lbXB0eUNlbGxzICYmIGNvbHVtbi5fZW1wdHlDZWxscy5pbmRleE9mKGNlbGwpID4gLTEpIHsKICAgICAgICAgICAgLy8gVGhlIGNlbGwgaXMgYW4gImVtcHR5IGNlbGwiICAtPiBkb2Vzbid0IGJsb2NrIGhpZGluZyB0aGUgcm93CiAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChyb3cucGFyZW50RWxlbWVudCA9PT0gdGhpcy4kLmhlYWRlcikgewogICAgICAgICAgICBpZiAoY29sdW1uLmhlYWRlclJlbmRlcmVyIHx8IGNvbHVtbi5faGVhZGVyVGVtcGxhdGUpIHsKICAgICAgICAgICAgICAvLyBUaGUgY2VsbCBpcyB0aGUgaGVhZGVyIGNlbGwgb2YgYSBjb2x1bW4gdGhhdCBoYXMgYSBoZWFkZXIgcmVuZGVyZXIKICAgICAgICAgICAgICAvLyBvciBhIGhlYWRlciB0ZW1wbGF0ZSAtPiByb3cgc2hvdWxkIGJlIHZpc2libGUKICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoY29sdW1uLmhlYWRlciA9PT0gbnVsbCkgewogICAgICAgICAgICAgIC8vIFRoZSBjb2x1bW4gaGVhZGVyIGlzIGV4cGxpY2lsdHkgc2V0IHRvIG51bGwgLT4gZG9lc24ndCBibG9jayBoaWRpbmcgdGhlIHJvdwogICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoY29sdW1uLnBhdGggfHwgY29sdW1uLmhlYWRlciAhPT0gdW5kZWZpbmVkKSB7CiAgICAgICAgICAgICAgLy8gVGhlIGNvbHVtbiBoYXMgYW4gZXhwbGljaXQgbm9uLW51bGwgaGVhZGVyIG9yIGEgcGF0aCB0aGF0IGdlbmVyYXRlcyBhIGhlYWRlcgogICAgICAgICAgICAgIC8vIC0+IHJvdyBzaG91bGQgYmUgdmlzaWJsZQogICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBpZiAoY29sdW1uLmZvb3RlclJlbmRlcmVyIHx8IGNvbHVtbi5fZm9vdGVyVGVtcGxhdGUpIHsKICAgICAgICAgICAgICAvLyBUaGUgY2VsbCBpcyB0aGUgZm9vdGVyIGNlbGwgb2YgYSBjb2x1bW4gdGhhdCBoYXMgYSBmb290ZXIgcmVuZGVyZXIKICAgICAgICAgICAgICAvLyBvciBhIGZvb3RlciB0ZW1wbGF0ZSAtPiByb3cgc2hvdWxkIGJlIHZpc2libGUKICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICAgICAgfQogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICBpZiAocm93LmhpZGRlbiAhPT0gIXZpc2libGVSb3dDZWxscy5sZW5ndGgpIHsKICAgICAgICAgIHJvdy5oaWRkZW4gPSAhdmlzaWJsZVJvd0NlbGxzLmxlbmd0aDsKICAgICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfdXBkYXRlU2Nyb2xsZXJJdGVtKHJvdywgaW5kZXgpIHsKICAgICAgICB0aGlzLl9wcmV2ZW50U2Nyb2xsZXJSb3RhdGluZ0NlbGxGb2N1cyhyb3csIGluZGV4KTsKCiAgICAgICAgaWYgKCF0aGlzLl9jb2x1bW5UcmVlKSB7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQoKICAgICAgICB0aGlzLl90b2dnbGVBdHRyaWJ1dGUoJ2ZpcnN0JywgaW5kZXggPT09IDAsIHJvdyk7CiAgICAgICAgdGhpcy5fdG9nZ2xlQXR0cmlidXRlKCdvZGQnLCBpbmRleCAlIDIsIHJvdyk7CiAgICAgICAgdGhpcy5fYTExeVVwZGF0ZVJvd1Jvd2luZGV4KHJvdywgaW5kZXgpOwogICAgICAgIHRoaXMuX2dldEl0ZW0oaW5kZXgsIHJvdyk7CiAgICAgIH0KCiAgICAgIF9jb2x1bW5UcmVlQ2hhbmdlZChjb2x1bW5UcmVlLCBzcGxpY2VzKSB7CiAgICAgICAgdGhpcy5fcmVuZGVyQ29sdW1uVHJlZShjb2x1bW5UcmVlKTsKICAgICAgICB0aGlzLnJlY2FsY3VsYXRlQ29sdW1uV2lkdGhzKCk7CiAgICAgIH0KCiAgICAgIF9yZW5kZXJDb2x1bW5UcmVlKGNvbHVtblRyZWUpIHsKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5pdGVtcy5jaGlsZHJlbikuZm9yRWFjaCgocm93KSA9PiB0aGlzLl91cGRhdGVSb3cocm93LCBjb2x1bW5UcmVlW2NvbHVtblRyZWUubGVuZ3RoIC0gMV0sIG51bGwsIGZhbHNlLCB0cnVlKSk7CgogICAgICAgIHdoaWxlICh0aGlzLiQuaGVhZGVyLmNoaWxkcmVuLmxlbmd0aCA8IGNvbHVtblRyZWUubGVuZ3RoKSB7CiAgICAgICAgICBjb25zdCBoZWFkZXJSb3cgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0cicpOwogICAgICAgICAgaGVhZGVyUm93LnNldEF0dHJpYnV0ZSgncGFydCcsICdyb3cnKTsKICAgICAgICAgIGhlYWRlclJvdy5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCAncm93Jyk7CiAgICAgICAgICB0aGlzLiQuaGVhZGVyLmFwcGVuZENoaWxkKGhlYWRlclJvdyk7CgogICAgICAgICAgY29uc3QgZm9vdGVyUm93ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndHInKTsKICAgICAgICAgIGZvb3RlclJvdy5zZXRBdHRyaWJ1dGUoJ3BhcnQnLCAncm93Jyk7CiAgICAgICAgICBmb290ZXJSb3cuc2V0QXR0cmlidXRlKCdyb2xlJywgJ3JvdycpOwogICAgICAgICAgdGhpcy4kLmZvb3Rlci5hcHBlbmRDaGlsZChmb290ZXJSb3cpOwogICAgICAgIH0KICAgICAgICB3aGlsZSAodGhpcy4kLmhlYWRlci5jaGlsZHJlbi5sZW5ndGggPiBjb2x1bW5UcmVlLmxlbmd0aCkgewogICAgICAgICAgdGhpcy4kLmhlYWRlci5yZW1vdmVDaGlsZCh0aGlzLiQuaGVhZGVyLmZpcnN0RWxlbWVudENoaWxkKTsKICAgICAgICAgIHRoaXMuJC5mb290ZXIucmVtb3ZlQ2hpbGQodGhpcy4kLmZvb3Rlci5maXJzdEVsZW1lbnRDaGlsZCk7CiAgICAgICAgfQoKICAgICAgICBBcnJheS5mcm9tKHRoaXMuJC5oZWFkZXIuY2hpbGRyZW4pCiAgICAgICAgICAuZm9yRWFjaCgoaGVhZGVyUm93LCBpbmRleCkgPT4gdGhpcy5fdXBkYXRlUm93KGhlYWRlclJvdywgY29sdW1uVHJlZVtpbmRleF0sICdoZWFkZXInLCBpbmRleCA9PT0gY29sdW1uVHJlZS5sZW5ndGggLSAxKSk7CgogICAgICAgIEFycmF5LmZyb20odGhpcy4kLmZvb3Rlci5jaGlsZHJlbikKICAgICAgICAgIC5mb3JFYWNoKChmb290ZXJSb3csIGluZGV4KSA9PiB0aGlzLl91cGRhdGVSb3coZm9vdGVyUm93LCBjb2x1bW5UcmVlW2NvbHVtblRyZWUubGVuZ3RoIC0gMSAtIGluZGV4XSwgJ2Zvb3RlcicsIGluZGV4ID09PSAwKSk7CgogICAgICAgIC8vIFNpemVyIHJvd3MKICAgICAgICB0aGlzLl91cGRhdGVSb3codGhpcy4kLm91dGVyc2l6ZXIsIGNvbHVtblRyZWVbY29sdW1uVHJlZS5sZW5ndGggLSAxXSwgbnVsbCwgZmFsc2UsIHRydWUpOwogICAgICAgIHRoaXMuX3VwZGF0ZVJvdyh0aGlzLiQuZml4ZWRzaXplciwgY29sdW1uVHJlZVtjb2x1bW5UcmVlLmxlbmd0aCAtIDFdKTsKCiAgICAgICAgdGhpcy5fcmVzaXplSGFuZGxlcigpOwogICAgICAgIHRoaXMuX2Zyb3plbkNlbGxzQ2hhbmdlZCgpOwogICAgICAgIHRoaXMuX3VwZGF0ZUZpcnN0QW5kTGFzdENvbHVtbigpOwogICAgICAgIHRoaXMuX3Jlc2V0S2V5Ym9hcmROYXZpZ2F0aW9uKCk7CiAgICAgICAgdGhpcy5fYTExeVVwZGF0ZUhlYWRlclJvd3MoKTsKICAgICAgICB0aGlzLl9hMTF5VXBkYXRlRm9vdGVyUm93cygpOwogICAgICB9CgogICAgICBfdXBkYXRlSXRlbShyb3csIGl0ZW0pIHsKICAgICAgICByb3cuX2l0ZW0gPSBpdGVtOwogICAgICAgIGNvbnN0IG1vZGVsID0gdGhpcy5fX2dldFJvd01vZGVsKHJvdyk7CgogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnc2VsZWN0ZWQnLCBtb2RlbC5zZWxlY3RlZCwgcm93KTsKICAgICAgICB0aGlzLl9hMTF5VXBkYXRlUm93U2VsZWN0ZWQocm93LCBtb2RlbC5zZWxlY3RlZCk7CiAgICAgICAgdGhpcy5fYTExeVVwZGF0ZVJvd0xldmVsKHJvdywgbW9kZWwubGV2ZWwpOwogICAgICAgIHRoaXMuX3RvZ2dsZUF0dHJpYnV0ZSgnZXhwYW5kZWQnLCBtb2RlbC5leHBhbmRlZCwgcm93KTsKICAgICAgICBpZiAodGhpcy5fcm93RGV0YWlsc1RlbXBsYXRlIHx8IHRoaXMucm93RGV0YWlsc1JlbmRlcmVyKSB7CiAgICAgICAgICB0aGlzLl90b2dnbGVEZXRhaWxzQ2VsbChyb3csIGl0ZW0pOwogICAgICAgIH0KICAgICAgICB0aGlzLl9nZW5lcmF0ZUNlbGxDbGFzc05hbWVzKHJvdywgbW9kZWwpOwogICAgICAgIHRoaXMuX2ZpbHRlckRyYWdBbmREcm9wKHJvdywgbW9kZWwpOwoKICAgICAgICBBcnJheS5mcm9tKHJvdy5jaGlsZHJlbikuZm9yRWFjaChjZWxsID0+IHsKICAgICAgICAgIGlmIChjZWxsLl9yZW5kZXJlcikgewogICAgICAgICAgICBjb25zdCBvd25lciA9IGNlbGwuX2NvbHVtbiB8fCB0aGlzOwogICAgICAgICAgICBjZWxsLl9yZW5kZXJlci5jYWxsKG93bmVyLCBjZWxsLl9jb250ZW50LCBvd25lciwgbW9kZWwpOwogICAgICAgICAgfSBlbHNlIGlmIChjZWxsLl9pbnN0YW5jZSkgewogICAgICAgICAgICBjZWxsLl9pbnN0YW5jZS5fX2RldGFpbHNPcGVuZWRfXyA9IG1vZGVsLmRldGFpbHNPcGVuZWQ7CiAgICAgICAgICAgIGNlbGwuX2luc3RhbmNlLl9fc2VsZWN0ZWRfXyA9IG1vZGVsLnNlbGVjdGVkOwogICAgICAgICAgICBjZWxsLl9pbnN0YW5jZS5fX2xldmVsX18gPSBtb2RlbC5sZXZlbDsKICAgICAgICAgICAgY2VsbC5faW5zdGFuY2UuX19leHBhbmRlZF9fID0gbW9kZWwuZXhwYW5kZWQ7CiAgICAgICAgICAgIGNlbGwuX2luc3RhbmNlLnNldFByb3BlcnRpZXMobW9kZWwpOwogICAgICAgICAgfQogICAgICAgIH0pOwoKICAgICAgICB0aGlzLl9kZWJvdW5jZXJVcGRhdGVIZWlnaHRzID0gRGVib3VuY2VyLmRlYm91bmNlKHRoaXMuX2RlYm91bmNlclVwZGF0ZUhlaWdodHMsCiAgICAgICAgICB0aW1lT3V0LmFmdGVyKDEpLCAoKSA9PiB7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZU1ldHJpY3MoKTsKICAgICAgICAgICAgdGhpcy5fcG9zaXRpb25JdGVtcygpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVTY3JvbGxlclNpemUoKTsKICAgICAgICAgIH0KICAgICAgICApOwogICAgICB9CgogICAgICBfcmVzaXplSGFuZGxlcigpIHsKICAgICAgICB0aGlzLl91cGRhdGVEZXRhaWxzQ2VsbEhlaWdodHMoKTsKICAgICAgICB0aGlzLl9hY2Nlc3NJcm9uTGlzdEFQSShzdXBlci5fcmVzaXplSGFuZGxlciwgdHJ1ZSk7CiAgICAgICAgdGhpcy5fdXBkYXRlU2Nyb2xsZXJNZWFzdXJlbWVudHMoKTsKICAgICAgICB0aGlzLl91cGRhdGVIZWFkZXJGb290ZXJNZXRyaWNzKCk7CiAgICAgIH0KCiAgICAgIF91cGRhdGVIZWFkZXJGb290ZXJNZXRyaWNzKCkgewogICAgICAgIGNvbnN0IGhlYWRlckhlaWdodCA9IHRoaXMuJC5oZWFkZXIuY2xpZW50SGVpZ2h0ICsgJ3B4JzsKICAgICAgICBjb25zdCBmb290ZXJIZWlnaHQgPSB0aGlzLiQuZm9vdGVyLmNsaWVudEhlaWdodCArICdweCc7CiAgICAgICAgW3RoaXMuJC5vdXRlcnNpemVyLCB0aGlzLiQuZml4ZWRzaXplciwgdGhpcy4kLml0ZW1zXS5mb3JFYWNoKGVsZW1lbnQgPT4gewogICAgICAgICAgZWxlbWVudC5zdHlsZS5ib3JkZXJUb3BXaWR0aCA9IGhlYWRlckhlaWdodDsKICAgICAgICAgIGVsZW1lbnQuc3R5bGUuYm9yZGVyQm90dG9tV2lkdGggPSBmb290ZXJIZWlnaHQ7CiAgICAgICAgfSk7CgogICAgICAgIGFmdGVyTmV4dFJlbmRlcih0aGlzLiQuaGVhZGVyLCAoKSA9PiB7CiAgICAgICAgICBpZiAodGhpcy5fcGVuZGluZ1Njcm9sbFRvSW5kZXgpIHsKICAgICAgICAgICAgdGhpcy5fc2Nyb2xsVG9JbmRleCh0aGlzLl9wZW5kaW5nU2Nyb2xsVG9JbmRleCk7CiAgICAgICAgICB9CiAgICAgICAgfSk7CiAgICAgIH0KCiAgICAgIF9vbkFuaW1hdGlvbkVuZChlKSB7CiAgICAgICAgLy8gU2hhZHlDU1MgYXBwbGllcyBzY29waW5nIHN1ZmZpeGVzIHRvIGFuaW1hdGlvbiBuYW1lcwogICAgICAgIGlmIChlLmFuaW1hdGlvbk5hbWUuaW5kZXhPZigndmFhZGluLWdyaWQtYXBwZWFyJykgPT09IDApIHsKICAgICAgICAgIHRoaXMuX3JlbmRlcigpOwogICAgICAgICAgdGhpcy5fdXBkYXRlSGVhZGVyRm9vdGVyTWV0cmljcygpOwogICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTsKICAgICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgICB0aGlzLl9faXRlbXNSZWNlaXZlZCgpOwogICAgICAgIH0KICAgICAgfQoKICAgICAgX3RvZ2dsZUF0dHJpYnV0ZShuYW1lLCBib29sLCBub2RlKSB7CiAgICAgICAgaWYgKG5vZGUuaGFzQXR0cmlidXRlKG5hbWUpID09PSAhYm9vbCkgewogICAgICAgICAgaWYgKGJvb2wpIHsKICAgICAgICAgICAgbm9kZS5zZXRBdHRyaWJ1dGUobmFtZSwgJycpOwogICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgbm9kZS5yZW1vdmVBdHRyaWJ1dGUobmFtZSk7CiAgICAgICAgICB9CiAgICAgICAgfQogICAgICB9CgogICAgICBfX2dldFJvd01vZGVsKHJvdykgewogICAgICAgIHJldHVybiB7CiAgICAgICAgICBpbmRleDogcm93LmluZGV4LAogICAgICAgICAgaXRlbTogcm93Ll9pdGVtLAogICAgICAgICAgbGV2ZWw6IHRoaXMuX2dldEluZGV4TGV2ZWwocm93LmluZGV4KSwKICAgICAgICAgIGV4cGFuZGVkOiB0aGlzLl9pc0V4cGFuZGVkKHJvdy5faXRlbSksCiAgICAgICAgICBzZWxlY3RlZDogdGhpcy5faXNTZWxlY3RlZChyb3cuX2l0ZW0pLAogICAgICAgICAgZGV0YWlsc09wZW5lZDoKICAgICAgICAgICAgISEodGhpcy5fcm93RGV0YWlsc1RlbXBsYXRlIHx8IHRoaXMucm93RGV0YWlsc1JlbmRlcmVyKSAmJiB0aGlzLl9pc0RldGFpbHNPcGVuZWQocm93Ll9pdGVtKQogICAgICAgIH07CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBNYW51YWxseSBpbnZva2UgZXhpc3RpbmcgcmVuZGVyZXJzIGZvciBhbGwgdGhlIGNvbHVtbnMKICAgICAgICogKGhlYWRlciwgZm9vdGVyIGFuZCBib2R5IGNlbGxzKSBhbmQgb3BlbmVkIHJvdyBkZXRhaWxzLgogICAgICAgKi8KICAgICAgcmVuZGVyKCkgewogICAgICAgIGlmICh0aGlzLl9jb2x1bW5UcmVlKSB7CiAgICAgICAgICAvLyBoZWFkZXIgYW5kIGZvb3RlciByZW5kZXJlcnMKICAgICAgICAgIHRoaXMuX2NvbHVtblRyZWUuZm9yRWFjaChsZXZlbCA9PiB7CiAgICAgICAgICAgIGxldmVsLmZvckVhY2goY29sdW1uID0+IGNvbHVtbi5fcmVuZGVySGVhZGVyQW5kRm9vdGVyKCkpOwogICAgICAgICAgfSk7CgogICAgICAgICAgLy8gYm9keSBhbmQgcm93IGRldGFpbHMgcmVuZGVyZXJzCiAgICAgICAgICB0aGlzLl91cGRhdGUoKTsKICAgICAgICB9CiAgICAgIH0KCiAgICAgIC8qKgogICAgICAgKiBVcGRhdGVzIHRoZSBjb21wdXRlZCBtZXRyaWNzIGFuZCBwb3NpdGlvbmluZyBvZiBpbnRlcm5hbCBncmlkIHBhcnRzCiAgICAgICAqIChyb3cvZGV0YWlscyBjZWxsIHBvc2l0aW9uaW5nIGV0YykuIE5lZWRzIHRvIGJlIGludm9rZWQgd2hlbmV2ZXIgdGhlIHNpemluZyBvZiBncmlkCiAgICAgICAqIGNvbnRlbnQgY2hhbmdlcyBhc3luY2hyb25vdXNseSB0byBlbnN1cmUgY29uc2lzdGVudCBhcHBlYXJhbmNlIChlLmcuIHdoZW4gYQogICAgICAgKiBjb250YWluZWQgaW1hZ2Ugd2hvc2UgYm91bmRzIGFyZW4ndCBrbm93biBiZWZvcmVoYW5kIGZpbmlzaGVzIGxvYWRpbmcpLgogICAgICAgKi8KICAgICAgbm90aWZ5UmVzaXplKCkgewogICAgICAgIHN1cGVyLm5vdGlmeVJlc2l6ZSgpOwogICAgICB9CgogICAgICBfaGVpZ2h0QnlSb3dzQ2hhbmdlZCh2YWx1ZSwgb2xkVmFsdWUpIHsKICAgICAgICBpZiAodmFsdWUgfHwgb2xkVmFsdWUpIHsKICAgICAgICAgIHRoaXMubm90aWZ5UmVzaXplKCk7CiAgICAgICAgfQogICAgICB9CgogICAgICBfX2ZvcmNlUmVmbG93KCkgewogICAgICAgIHRoaXMuX2RlYm91bmNlckZvcmNlUmVmbG93ID0gRGVib3VuY2VyLmRlYm91bmNlKHRoaXMuX2RlYm91bmNlckZvcmNlUmVmbG93LAogICAgICAgICAgYW5pbWF0aW9uRnJhbWUsICgpID0+IHsKICAgICAgICAgICAgdGhpcy4kLnNjcm9sbGVyLnN0eWxlLm92ZXJmbG93ID0gJ2hpZGRlbic7CiAgICAgICAgICAgIHNldFRpbWVvdXQoKCkgPT4gdGhpcy4kLnNjcm9sbGVyLnN0eWxlLm92ZXJmbG93ID0gJycpOwogICAgICAgICAgfQogICAgICAgICk7CiAgICAgIH0KICAgIH0KCiAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoR3JpZEVsZW1lbnQuaXMsIEdyaWRFbGVtZW50KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAxNiBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBUZkRvd25sb2FkZXIgPSBjbGFzcyBUZkRvd25sb2FkZXIgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX3J1biA9ICcnOwogICAgICAgIH0KICAgICAgICBfY3N2VXJsKHRhZywgcnVuLCB1cmxGbikgewogICAgICAgICAgICBpZiAoIXJ1bikKICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgcmV0dXJuIGFkZFBhcmFtcyh1cmxGbih0YWcsIHJ1biksIHsgZm9ybWF0OiAnY3N2JyB9KTsKICAgICAgICB9CiAgICAgICAgX2pzb25VcmwodGFnLCBydW4sIHVybEZuKSB7CiAgICAgICAgICAgIGlmICghcnVuKQogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICByZXR1cm4gdXJsRm4odGFnLCBydW4pOwogICAgICAgIH0KICAgICAgICBfY3N2TmFtZSh0YWcsIHJ1bikgewogICAgICAgICAgICBpZiAoIXJ1bikKICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgcmV0dXJuIGBydW4tJHtydW59LXRhZy0ke3RhZ30uY3N2YDsKICAgICAgICB9CiAgICAgICAgX2pzb25OYW1lKHRhZywgcnVuKSB7CiAgICAgICAgICAgIGlmICghcnVuKQogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICByZXR1cm4gYHJ1bi0ke3J1bn0tdGFnLSR7dGFnfS5qc29uYDsKICAgICAgICB9CiAgICB9OwogICAgVGZEb3dubG9hZGVyLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8cGFwZXItZHJvcGRvd24tbWVudQogICAgICBuby1sYWJlbC1mbG9hdD0idHJ1ZSIKICAgICAgbGFiZWw9InJ1biB0byBkb3dubG9hZCIKICAgICAgc2VsZWN0ZWQtaXRlbS1sYWJlbD0ie3tfcnVufX0iCiAgICA+CiAgICAgIDxwYXBlci1saXN0Ym94IHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLXJlcGVhdCIgaXRlbXM9IltbcnVuc11dIj4KICAgICAgICAgIDxwYXBlci1pdGVtIG5vLWxhYmVsLWZsb2F0PSJ0cnVlIj5bW2l0ZW1dXTwvcGFwZXItaXRlbT4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICA8L3BhcGVyLWRyb3Bkb3duLW1lbnU+CiAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX3J1bl1dIj4KICAgICAgPGEgZG93bmxvYWQ9IltbX2Nzdk5hbWUodGFnLCBfcnVuKV1dIiBocmVmPSJbW19jc3ZVcmwodGFnLCBfcnVuLCB1cmxGbildXSIKICAgICAgICA+Q1NWPC9hCiAgICAgID48IS0tCiAgICAgIC0tPjxhCiAgICAgICAgZG93bmxvYWQ9IltbX2pzb25OYW1lKHRhZywgX3J1bildXSIKICAgICAgICBocmVmPSJbW19qc29uVXJsKHRhZywgX3J1biwgdXJsRm4pXV0iCiAgICAgICAgPkpTT048L2EKICAgICAgPgogICAgPC90ZW1wbGF0ZT4KICAgIDxzdHlsZT4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICBoZWlnaHQ6IDMycHg7CiAgICAgIH0KICAgICAgcGFwZXItZHJvcGRvd24tbWVudSB7CiAgICAgICAgd2lkdGg6IDEwMHB4OwogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsOiB7CiAgICAgICAgICBmb250LXNpemU6IDEwcHg7CiAgICAgICAgfQogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0OiB7CiAgICAgICAgICBmb250LXNpemU6IDEwcHg7CiAgICAgICAgfQogICAgICB9CiAgICAgIGEgewogICAgICAgIGZvbnQtc2l6ZTogMTBweDsKICAgICAgICBtYXJnaW46IDAgMC4yZW07CiAgICAgIH0KICAgICAgcGFwZXItaW5wdXQgewogICAgICAgIGZvbnQtc2l6ZTogMjJweDsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkRvd25sb2FkZXIucHJvdG90eXBlLCAiX3J1biIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkRvd25sb2FkZXIucHJvdG90eXBlLCAicnVucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmRG93bmxvYWRlci5wcm90b3R5cGUsICJ0YWciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkRvd25sb2FkZXIucHJvdG90eXBlLCAidXJsRm4iLCB2b2lkIDApOwogICAgVGZEb3dubG9hZGVyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtZG93bmxvYWRlcicpCiAgICBdLCBUZkRvd25sb2FkZXIpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBTYXZlIHRoZSBpbml0aWFsIFVSTCBxdWVyeSBwYXJhbXMsIGJlZm9yZSB0aGUgQXBwUm91dGluZ0VmZmVjdHMgaW5pdGlhbGl6ZS4KICAgICAqLwogICAgY29uc3QgaW5pdGlhbFVSTFNlYXJjaFBhcmFtcyQxID0gbmV3IFVSTFNlYXJjaFBhcmFtcyh3aW5kb3cubG9jYXRpb24uc2VhcmNoKTsKICAgIC8qKgogICAgICogQSBjYXJkIHRoYXQgaGFuZGxlcyBsb2FkaW5nIGRhdGEgKGF0IHRoZSByaWdodCB0aW1lcyksIHJlbmRlcmluZyBhIHNjYWxhcgogICAgICogY2hhcnQsIGFuZCBwcm92aWRpbmcgVUkgYWZmb3JkYW5jZXMgKHN1Y2ggYXMgYnV0dG9ucykgZm9yIHNjYWxhciBkYXRhLgogICAgICovCiAgICBsZXQgVGZTY2FsYXJDYXJkID0gCiAgICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bm8tdW51c2VkLXZhcmlhYmxlCiAgICBjbGFzcyBUZlNjYWxhckNhcmQgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8vIElmIHNwZWNpZmllZCB1c2VzIHRoZSBnaXZlbiBjb2xvclNjYWxlOyBvdGhlcndpc2UsIHVzZXMgYSBidWlsdC1pbgogICAgICAgICAgICAvLyBkZWZhdWx0LiBTZWUgX2dldENvbG9yU2NhbGUgYmVsb3cgZm9yIG1vcmUgZGV0YWlscy4KICAgICAgICAgICAgdGhpcy5jb2xvclNjYWxlID0gbnVsbDsKICAgICAgICAgICAgLy8gVGhpcyBmdW5jdGlvbiBpcyBjYWxsZWQgd2hlbiBkYXRhIGlzIHJlY2VpdmVkIGZyb20gdGhlIGJhY2tlbmQuCiAgICAgICAgICAgIHRoaXMuX2xvYWREYXRhQ2FsbGJhY2sgPSAoc2NhbGFyQ2hhcnQsIGl0ZW0sIG1heWJlRGF0YSkgPT4gewogICAgICAgICAgICAgICAgaWYgKG1heWJlRGF0YSA9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgY29uc29sZS5lcnJvcignRmFpbGVkIHRvIGxvYWQgZGF0YSBmb3I6JywgaXRlbSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29uc3QgZm9ybWF0dGVkRGF0YSA9IG1heWJlRGF0YS5tYXAoKGRhdHVtKSA9PiAoewogICAgICAgICAgICAgICAgICAgIHdhbGxfdGltZTogbmV3IERhdGUoZGF0dW1bMF0gKiAxMDAwKSwKICAgICAgICAgICAgICAgICAgICBzdGVwOiBkYXR1bVsxXSwKICAgICAgICAgICAgICAgICAgICBzY2FsYXI6IGRhdHVtWzJdLAogICAgICAgICAgICAgICAgfSkpOwogICAgICAgICAgICAgICAgY29uc3QgbmFtZSA9IHRoaXMuX2dldFNlcmllc05hbWVGcm9tRGF0dW0oaXRlbSk7CiAgICAgICAgICAgICAgICBzY2FsYXJDaGFydC5zZXRTZXJpZXNNZXRhZGF0YShuYW1lLCBpdGVtKTsKICAgICAgICAgICAgICAgIHNjYWxhckNoYXJ0LnNldFNlcmllc0RhdGEobmFtZSwgZm9ybWF0dGVkRGF0YSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuZ2V0RGF0YUxvYWRVcmwgPSAoeyB0YWcsIHJ1biB9KSA9PiB7CiAgICAgICAgICAgICAgICByZXR1cm4gZ2V0Um91dGVyKCkucGx1Z2luUm91dGUoJ3NjYWxhcnMnLCAnL3NjYWxhcnMnLCBuZXcgVVJMU2VhcmNoUGFyYW1zKHsgdGFnLCBydW4gfSkpOwogICAgICAgICAgICB9OwogICAgICAgICAgICAvLyBUbyBiZSBwcm92aWRlZCBhcyB0aGUgYHVybC1mbmAgcHJvcGVydHkgdG8gYHRmLWRvd25sb2FkZXJgLgogICAgICAgICAgICB0aGlzLl9kb3dubG9hZFVybEZuID0gKHRhZywgcnVuKSA9PiB0aGlzLmdldERhdGFMb2FkVXJsKHsgdGFnLCBydW4gfSk7CiAgICAgICAgICAgIC8vIEEgZnVuY3Rpb24gY2FsbGVkIHRvIGZldGNoIHRoZSBzY2FsYXJzIGRhdGEgZnJvbSB0aGUgYmFja2VuZC4KICAgICAgICAgICAgLy8gU2hvdWxkIHJlY2VpdmUgYSB7dGFnLCBydW4sIGV4cGVyaW1lbnR9IG9iamVjdCBhbmQgcmV0dXJuCiAgICAgICAgICAgIC8vIGEgcHJvbWlzZSByZXNvbHZpbmcgd2l0aCB0aGUgZmV0Y2hlZCBzY2FsYXJzLiBUaGUgZGVmYXVsdAogICAgICAgICAgICAvLyBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIGZ1bmN0aW9uIGV4ZWN1dGVzOgogICAgICAgICAgICAvLyB0aGlzLnJlcXVlc3RNYW5hZ2VyLnJlcXVlc3QoCiAgICAgICAgICAgIC8vICAgICAgdGhpcy5nZXREYXRhTG9hZFVybCh7dGFnLCBydW4sIGV4cGVyaW1lbnR9KQogICAgICAgICAgICB0aGlzLnJlcXVlc3REYXRhID0gKGl0ZW1zLCBvbkxvYWQsIG9uRmluaXNoKSA9PiB7CiAgICAgICAgICAgICAgICAvLyBHb29nbGUtaW50ZXJuYWwgQ29sYWIgZG9lc24ndCBzdXBwb3J0IEhUVFAgUE9TVCByZXF1ZXN0cywgc28gd2UgZmFsbAogICAgICAgICAgICAgICAgLy8gYmFjayB0byBIVFRQIEdFVCAoZXZlbiB0aG91Z2ggcHVibGljIENvbGFiIHN1cHBvcnRzIFBPU1QpLgogICAgICAgICAgICAgICAgLy8gU2VlIGIvMTI2Mzg3MTA2LgogICAgICAgICAgICAgICAgY29uc3QgaW5Db2xhYiA9IGluaXRpYWxVUkxTZWFyY2hQYXJhbXMkMS5nZXQoJ3RlbnNvcmJvYXJkQ29sYWInKSA9PT0gJ3RydWUnOwogICAgICAgICAgICAgICAgaWYgKGluQ29sYWIpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVxdWVzdERhdGFHZXQoaXRlbXMsIG9uTG9hZCwgb25GaW5pc2gpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3REYXRhUG9zdChpdGVtcywgb25Mb2FkLCBvbkZpbmlzaCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3REYXRhR2V0ID0gKGl0ZW1zLCBvbkxvYWQsIG9uRmluaXNoKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCByb3V0ZXIgPSBnZXRSb3V0ZXIoKTsKICAgICAgICAgICAgICAgIGNvbnN0IGJhc2VVcmwgPSByb3V0ZXIucGx1Z2luUm91dGUoJ3NjYWxhcnMnLCAnL3NjYWxhcnMnKTsKICAgICAgICAgICAgICAgIFByb21pc2UuYWxsKGl0ZW1zLm1hcCgoaXRlbSkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IHVybCA9IGFkZFBhcmFtcyhiYXNlVXJsLCB7IHRhZzogaXRlbS50YWcsIHJ1bjogaXRlbS5ydW4gfSk7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVxdWVzdE1hbmFnZXIKICAgICAgICAgICAgICAgICAgICAgICAgLnJlcXVlc3QodXJsKQogICAgICAgICAgICAgICAgICAgICAgICAudGhlbigoZGF0YSkgPT4gdm9pZCBvbkxvYWQoeyBpdGVtLCBkYXRhIH0pKTsKICAgICAgICAgICAgICAgIH0pKS5maW5hbGx5KCgpID0+IHZvaWQgb25GaW5pc2goKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3REYXRhUG9zdCA9IChpdGVtcywgb25Mb2FkLCBvbkZpbmlzaCkgPT4gewogICAgICAgICAgICAgICAgY29uc3Qgcm91dGVyID0gZ2V0Um91dGVyKCk7CiAgICAgICAgICAgICAgICBjb25zdCB1cmwgPSByb3V0ZXIucGx1Z2luUm91dGUoJ3NjYWxhcnMnLCAnL3NjYWxhcnNfbXVsdGlydW4nKTsKICAgICAgICAgICAgICAgIGNvbnN0IHJ1bnNCeVRhZyA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgICAgIGZvciAoY29uc3QgeyB0YWcsIHJ1biB9IG9mIGl0ZW1zKSB7CiAgICAgICAgICAgICAgICAgICAgbGV0IHJ1bnMgPSBydW5zQnlUYWcuZ2V0KHRhZyk7CiAgICAgICAgICAgICAgICAgICAgaWYgKHJ1bnMgPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgICAgICBydW5zQnlUYWcuc2V0KHRhZywgKHJ1bnMgPSBbXSkpOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBydW5zLnB1c2gocnVuKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIFJlcXVlc3QgYXQgbW9zdCB0aGlzIG1hbnkgcnVucyBhdCBvbmNlLgogICAgICAgICAgICAgICAgLy8KICAgICAgICAgICAgICAgIC8vIEJhY2stb2YtdGhlLWVudmVsb3BlIG1hdGg6IGVhY2ggc2NhbGFyIGRhdHVtIEpTT04gdmFsdWUgY29udGFpbnMKICAgICAgICAgICAgICAgIC8vIHR3byBmbG9hdHMgYW5kIGEgc21hbGwtaXNoIGludGVnZXIuIEZsb2F0cyBhcmUgYWJvdXQgMTggYnl0ZXMsCiAgICAgICAgICAgICAgICAvLyBzaW5jZSBmNjRzIGhhdmUgLWxvZ18xMCgyXi01Mykgfj0gMTYgZGlnaXRzIG9mIHByZWNpc2lvbiBwbHVzCiAgICAgICAgICAgICAgICAvLyBkZWNpbWFsIHBvaW50IGFuZCBsZWFkaW5nIHplcm8uIFNtYWxsLWlzaCBpbnRlZ2VycyAoc3RlcHMpIGFyZQogICAgICAgICAgICAgICAgLy8gYWJvdXQgNSBieXRlcy4gQWRkIEpTT04gb3ZlcmhlYWQgYFssLF0sYCBhbmQgeW91J3JlIGxvb2tpbmcgYXQKICAgICAgICAgICAgICAgIC8vIGFib3V0IDQ4IGJ5dGVzIHBlciBkYXR1bS4gV2l0aCBzdGFuZGFyZCBkb3duc2FtcGxpbmcgb2YKICAgICAgICAgICAgICAgIC8vIDEwMDAgcG9pbnRzIHBlciB0aW1lIHNlcmllcywgZXhwZWN0IH41MCBLQiBvZiByZXNwb25zZSBwYXlsb2FkCiAgICAgICAgICAgICAgICAvLyBwZXIgcmVxdWVzdGVkIHRpbWUgc2VyaWVzLgogICAgICAgICAgICAgICAgLy8KICAgICAgICAgICAgICAgIC8vIFJlcXVlc3RpbmcgNjQgdGltZSBzZXJpZXMgd2FycmFudHMgYSB+MyBNQiByZXNwb25zZSwgd2hpY2ggc2VlbXMKICAgICAgICAgICAgICAgIC8vIHJlYXNvbmFibGUuCiAgICAgICAgICAgICAgICBjb25zdCBCQVRDSF9TSVpFID0gNjQ7CiAgICAgICAgICAgICAgICBjb25zdCByZXF1ZXN0R3JvdXBzID0gW107CiAgICAgICAgICAgICAgICBmb3IgKGNvbnN0IFt0YWcsIHJ1bnNdIG9mIHJ1bnNCeVRhZykgewogICAgICAgICAgICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgcnVucy5sZW5ndGg7IGkgKz0gQkFUQ0hfU0laRSkgewogICAgICAgICAgICAgICAgICAgICAgICByZXF1ZXN0R3JvdXBzLnB1c2goeyB0YWcsIHJ1bnM6IHJ1bnMuc2xpY2UoaSwgaSArIEJBVENIX1NJWkUpIH0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIFByb21pc2UuYWxsKHJlcXVlc3RHcm91cHMubWFwKCh7IHRhZywgcnVucyB9KSA9PiB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMucmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwsIHsgdGFnLCBydW5zIH0pLnRoZW4oKGFsbERhdGEpID0+IHsKICAgICAgICAgICAgICAgICAgICAgICAgZm9yIChjb25zdCBydW4gb2YgcnVucykgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgaXRlbSA9IHsgdGFnLCBydW4gfTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlmIChPYmplY3QucHJvdG90eXBlLmhhc093blByb3BlcnR5LmNhbGwoYWxsRGF0YSwgcnVuKSkgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uTG9hZCh7IGl0ZW0sIGRhdGE6IGFsbERhdGFbcnVuXSB9KTsKICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIG9uTG9hZCh7IGl0ZW0sIGRhdGE6IG51bGwgfSk7CiAgICAgICAgICAgICAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIH0pKS5maW5hbGx5KCgpID0+IHZvaWQgb25GaW5pc2goKSk7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIHRoaXMuX2dldERhdGFMb2FkTmFtZSA9IChkYXR1bSkgPT4gdGhpcy5fZ2V0U2VyaWVzTmFtZUZyb21EYXR1bShkYXR1bSk7CiAgICAgICAgICAgIHRoaXMuX2V4cGFuZGVkID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuX3Rvb2x0aXBDb2x1bW5zID0gKCgpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IGNvbHVtbnMgPSBERUZBVUxUX1RPT0xUSVBfQ09MVU1OUy5zbGljZSgpOwogICAgICAgICAgICAgICAgY29uc3QgaW5kID0gY29sdW1ucy5maW5kSW5kZXgoKGMpID0+IGMudGl0bGUgPT0gJ05hbWUnKTsKICAgICAgICAgICAgICAgIGNvbHVtbnMuc3BsaWNlKGluZCwgMSwgewogICAgICAgICAgICAgICAgICAgIHRpdGxlOiAnTmFtZScsCiAgICAgICAgICAgICAgICAgICAgZXZhbHVhdGU6IChkKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdHVtID0gZC5kYXRhc2V0Lm1ldGFkYXRhKCkubWV0YTsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2dldFNlcmllc0Rpc3BsYXlOYW1lRnJvbURhdHVtKGRhdHVtKTsKICAgICAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICByZXR1cm4gY29sdW1uczsKICAgICAgICAgICAgfSkoKTsKICAgICAgICB9CiAgICAgICAgX2dldENoYXJ0RGF0YUxvYWRlcigpIHsKICAgICAgICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLXVubmVjZXNzYXJ5LXR5cGUtYXNzZXJ0aW9uCiAgICAgICAgICAgIHJldHVybiB0aGlzLnNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvcigndGYtbGluZS1jaGFydC1kYXRhLWxvYWRlcicpOyAvLyBUZkxpbmVDaGFydERhdGFMb2FkZXIKICAgICAgICB9CiAgICAgICAgcmVsb2FkKCkgewogICAgICAgICAgICB0aGlzLl9nZXRDaGFydERhdGFMb2FkZXIoKS5yZWxvYWQoKTsKICAgICAgICB9CiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICB0aGlzLl9nZXRDaGFydERhdGFMb2FkZXIoKS5yZWRyYXcoKTsKICAgICAgICB9CiAgICAgICAgX3RvZ2dsZUV4cGFuZGVkKGUpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19leHBhbmRlZCcsICF0aGlzLl9leHBhbmRlZCk7CiAgICAgICAgICAgIHRoaXMucmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIF90b2dnbGVMb2dTY2FsZSgpIHsKICAgICAgICAgICAgdGhpcy5zZXQoJ19sb2dTY2FsZUFjdGl2ZScsICF0aGlzLl9sb2dTY2FsZUFjdGl2ZSk7CiAgICAgICAgfQogICAgICAgIF9yZXNldERvbWFpbigpIHsKICAgICAgICAgICAgY29uc3QgY2hhcnQgPSB0aGlzLl9nZXRDaGFydERhdGFMb2FkZXIoKTsKICAgICAgICAgICAgaWYgKGNoYXJ0KSB7CiAgICAgICAgICAgICAgICBjaGFydC5yZXNldERvbWFpbigpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIF91cGRhdGVEb3dubG9hZExpbmsoKSB7CiAgICAgICAgICAgIGNvbnN0IHN2Z1N0ciA9IHRoaXMuX2dldENoYXJ0RGF0YUxvYWRlcigpLmV4cG9ydEFzU3ZnU3RyaW5nKCk7CiAgICAgICAgICAgIC8vIFRoZSBTVkcgY29kZSBzdHJpbmcgbWF5IGluY2x1ZGUgaGFzaCBjaGFyYWN0ZXJzLCBzdWNoIGFzIGFuCiAgICAgICAgICAgIC8vIGF0dHJpYnV0ZSBgY2xpcFBhdGg9InVybCgjZm9vKSJgLiBUaHVzLCB3ZSBiYXNlNjQtZW5jb2RlIHRoZQogICAgICAgICAgICAvLyBkYXRhIHNvIHRoYXQgc3VjaCBhIGhhc2ggaXMgbm90IGludGVycHJldGVkIGFzIGEgZnJhZ21lbnQKICAgICAgICAgICAgLy8gc3BlY2lmaWVyLCB0cnVuY2F0aW5nIHRoZSBTVkcuIChTZWUgaXNzdWUgIzE4NzQuKQogICAgICAgICAgICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bm8tdW5uZWNlc3NhcnktdHlwZS1hc3NlcnRpb24KICAgICAgICAgICAgY29uc3Qgc3ZnTGluayA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yKCcjc3ZnTGluaycpOwogICAgICAgICAgICBzdmdMaW5rLmhyZWYgPSBgZGF0YTppbWFnZS9zdmcreG1sO2Jhc2U2NCwke2J0b2Eoc3ZnU3RyKX1gOwogICAgICAgIH0KICAgICAgICBfcnVuc0Zyb21EYXRhKGRhdGEpIHsKICAgICAgICAgICAgcmV0dXJuIGRhdGEubWFwKChkYXR1bSkgPT4gZGF0dW0ucnVuKTsKICAgICAgICB9CiAgICAgICAgX2dldERhdGFTZXJpZXMoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLmRhdGFUb0xvYWQubWFwKChkKSA9PiB0aGlzLl9nZXRTZXJpZXNOYW1lRnJvbURhdHVtKGQpKTsKICAgICAgICB9CiAgICAgICAgLy8gbmFtZSBpcyBhIHN0YWJsZSBpZGVudGlmaWVyIGZvciBhIHNlcmllcy4KICAgICAgICBfZ2V0U2VyaWVzTmFtZUZyb21EYXR1bSh7IHJ1biwgZXhwZXJpbWVudCA9IHsgbmFtZTogJ19kZWZhdWx0JyB9IH0pIHsKICAgICAgICAgICAgcmV0dXJuIEpTT04uc3RyaW5naWZ5KFtleHBlcmltZW50Lm5hbWUsIHJ1bl0pOwogICAgICAgIH0KICAgICAgICAvLyB0aXRsZSBpcyBhIHZpc2libGUgc3RyaW5nIG9mIGEgc2VyaWVzIGZvciB0aGUgVUkuCiAgICAgICAgX2dldFNlcmllc0Rpc3BsYXlOYW1lRnJvbURhdHVtKGRhdHVtKSB7CiAgICAgICAgICAgIHJldHVybiBkYXR1bS5ydW47CiAgICAgICAgfQogICAgICAgIF9nZXRDb2xvclNjYWxlKCkgewogICAgICAgICAgICBpZiAodGhpcy5jb2xvclNjYWxlICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5jb2xvclNjYWxlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIElmICdjb2xvclNjYWxlJyBpc24ndCBleHBsaWNpdGx5IHNwZWNpZmllZCwgdXNlIHRoZSBvbmVzCiAgICAgICAgICAgIC8vIGRlZmluZWQgaW4gdGZfY29sb3Jfc2NhbGUuCiAgICAgICAgICAgIHJldHVybiB7CiAgICAgICAgICAgICAgICBzY2FsZTogKG5hbWUpID0+IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBbLCBydW5dID0gSlNPTi5wYXJzZShuYW1lKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gcnVuc0NvbG9yU2NhbGUocnVuKTsKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgfTsKICAgIFRmU2NhbGFyQ2FyZC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWNhcmQtaGVhZGluZwogICAgICB0YWc9IltbdGFnXV0iCiAgICAgIGRpc3BsYXktbmFtZT0iW1t0YWdNZXRhZGF0YS5kaXNwbGF5TmFtZV1dIgogICAgICBkZXNjcmlwdGlvbj0iW1t0YWdNZXRhZGF0YS5kZXNjcmlwdGlvbl1dIgogICAgPjwvdGYtY2FyZC1oZWFkaW5nPgogICAgPGRpdiBpZD0idGYtbGluZS1jaGFydC1kYXRhLWxvYWRlci1jb250YWluZXIiPgogICAgICA8dGYtbGluZS1jaGFydC1kYXRhLWxvYWRlcgogICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICBjb2xvci1zY2FsZT0iW1tfZ2V0Q29sb3JTY2FsZShjb2xvclNjYWxlKV1dIgogICAgICAgIGRhdGEtc2VyaWVzPSJbW19nZXREYXRhU2VyaWVzKGRhdGFUb0xvYWQuKildXSIKICAgICAgICBkYXRhLXRvLWxvYWQ9IltbZGF0YVRvTG9hZF1dIgogICAgICAgIGdldC1kYXRhLWxvYWQtbmFtZT0iW1tfZ2V0RGF0YUxvYWROYW1lXV0iCiAgICAgICAgZ2V0LWRhdGEtbG9hZC11cmw9IltbZ2V0RGF0YUxvYWRVcmxdXSIKICAgICAgICByZXF1ZXN0LWRhdGE9IltbcmVxdWVzdERhdGFdXSIKICAgICAgICBpZ25vcmUteS1vdXRsaWVycz0iW1tpZ25vcmVZT3V0bGllcnNdXSIKICAgICAgICBsb2FkLWRhdGEtY2FsbGJhY2s9IltbX2xvYWREYXRhQ2FsbGJhY2tdXSIKICAgICAgICBsb2FkLWtleT0iW1t0YWddXSIKICAgICAgICBsb2ctc2NhbGUtYWN0aXZlPSJbW19sb2dTY2FsZUFjdGl2ZV1dIgogICAgICAgIHJlcXVlc3QtbWFuYWdlcj0iW1tyZXF1ZXN0TWFuYWdlcl1dIgogICAgICAgIHNtb290aGluZy1lbmFibGVkPSJbW3Ntb290aGluZ0VuYWJsZWRdXSIKICAgICAgICBzbW9vdGhpbmctd2VpZ2h0PSJbW3Ntb290aGluZ1dlaWdodF1dIgogICAgICAgIHRhZy1tZXRhZGF0YT0iW1t0YWdNZXRhZGF0YV1dIgogICAgICAgIHRvb2x0aXAtY29sdW1ucz0iW1tfdG9vbHRpcENvbHVtbnNdXSIKICAgICAgICB0b29sdGlwLXBvc2l0aW9uPSJhdXRvIgogICAgICAgIHRvb2x0aXAtc29ydGluZy1tZXRob2Q9IltbdG9vbHRpcFNvcnRpbmdNZXRob2RdXSIKICAgICAgICB4LXR5cGU9IltbeFR5cGVdXSIKICAgICAgPgogICAgICA8L3RmLWxpbmUtY2hhcnQtZGF0YS1sb2FkZXI+CiAgICA8L2Rpdj4KICAgIDxkaXYgaWQ9ImJ1dHRvbnMiPgogICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICBzZWxlY3RlZCQ9IltbX2V4cGFuZGVkXV0iCiAgICAgICAgaWNvbj0iZnVsbHNjcmVlbiIKICAgICAgICBvbi10YXA9Il90b2dnbGVFeHBhbmRlZCIKICAgICAgPjwvcGFwZXItaWNvbi1idXR0b24+CiAgICAgIDxwYXBlci1pY29uLWJ1dHRvbgogICAgICAgIHNlbGVjdGVkJD0iW1tfbG9nU2NhbGVBY3RpdmVdXSIKICAgICAgICBpY29uPSJsaW5lLXdlaWdodCIKICAgICAgICBvbi10YXA9Il90b2dnbGVMb2dTY2FsZSIKICAgICAgICB0aXRsZT0iVG9nZ2xlIHktYXhpcyBsb2cgc2NhbGUiCiAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICBpY29uPSJzZXR0aW5ncy1vdmVyc2NhbiIKICAgICAgICBvbi10YXA9Il9yZXNldERvbWFpbiIKICAgICAgICB0aXRsZT0iRml0IGRvbWFpbiB0byBkYXRhIgogICAgICA+PC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbW3Nob3dEb3dubG9hZExpbmtzXV0iPgogICAgICAgIDxwYXBlci1tZW51LWJ1dHRvbiBvbi1wYXBlci1kcm9wZG93bi1vcGVuPSJfdXBkYXRlRG93bmxvYWRMaW5rIj4KICAgICAgICAgIDxwYXBlci1pY29uLWJ1dHRvbgogICAgICAgICAgICBjbGFzcz0iZHJvcGRvd24tdHJpZ2dlciIKICAgICAgICAgICAgc2xvdD0iZHJvcGRvd24tdHJpZ2dlciIKICAgICAgICAgICAgaWNvbj0iZmlsZS1kb3dubG9hZCIKICAgICAgICAgID48L3BhcGVyLWljb24tYnV0dG9uPgogICAgICAgICAgPHBhcGVyLWxpc3Rib3ggY2xhc3M9ImRyb3Bkb3duLWNvbnRlbnQiIHNsb3Q9ImRyb3Bkb3duLWNvbnRlbnQiPgogICAgICAgICAgICA8cGFwZXItaXRlbT4KICAgICAgICAgICAgICA8YSBpZD0ic3ZnTGluayIgZG93bmxvYWQ9IltbdGFnXV0uc3ZnIj4KICAgICAgICAgICAgICAgIERvd25sb2FkIEN1cnJlbnQgQ2hhcnQgYXMgU1ZHCiAgICAgICAgICAgICAgPC9hPgogICAgICAgICAgICA8L3BhcGVyLWl0ZW0+CiAgICAgICAgICA8L3BhcGVyLWxpc3Rib3g+CiAgICAgICAgPC9wYXBlci1tZW51LWJ1dHRvbj4KICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPHNwYW4gc3R5bGU9ImZsZXgtZ3JvdzogMSI+PC9zcGFuPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9Iltbc2hvd0Rvd25sb2FkTGlua3NdXSI+CiAgICAgICAgPGRpdiBjbGFzcz0iZG93bmxvYWQtbGlua3MiPgogICAgICAgICAgPHRmLWRvd25sb2FkZXIKICAgICAgICAgICAgcnVucz0iW1tfcnVuc0Zyb21EYXRhKGRhdGFUb0xvYWQpXV0iCiAgICAgICAgICAgIHRhZz0iW1t0YWddXSIKICAgICAgICAgICAgdXJsLWZuPSJbW19kb3dubG9hZFVybEZuXV0iCiAgICAgICAgICA+PC90Zi1kb3dubG9hZGVyPgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBtYXJnaW46IDVweDsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICB3aWR0aDogMzMwcHg7CiAgICAgIH0KCiAgICAgIDpob3N0KFtfZXhwYW5kZWRdKSB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIH0KCiAgICAgIDpob3N0KFtfZXhwYW5kZWRdKSAjdGYtbGluZS1jaGFydC1kYXRhLWxvYWRlci1jb250YWluZXIgewogICAgICAgIGhlaWdodDogNDAwcHg7CiAgICAgIH0KCiAgICAgICN0Zi1saW5lLWNoYXJ0LWRhdGEtbG9hZGVyLWNvbnRhaW5lciB7CiAgICAgICAgaGVpZ2h0OiAyMDBweDsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgdGYtY2FyZC1oZWFkaW5nIHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBtYXJnaW4tYm90dG9tOiAxMHB4OwogICAgICB9CgogICAgICAjYnV0dG9ucyB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBmbGV4LWRpcmVjdGlvbjogcm93OwogICAgICB9CgogICAgICBwYXBlci1pY29uLWJ1dHRvbiB7CiAgICAgICAgY29sb3I6ICMyMTk2ZjM7CiAgICAgICAgYm9yZGVyLXJhZGl1czogMTAwJTsKICAgICAgICB3aWR0aDogMzJweDsKICAgICAgICBoZWlnaHQ6IDMycHg7CiAgICAgICAgcGFkZGluZzogNHB4OwogICAgICB9CgogICAgICBwYXBlci1pY29uLWJ1dHRvbltzZWxlY3RlZF0gewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXRiLXVpLWxpZ2h0LWFjY2VudCk7CiAgICAgIH0KCiAgICAgIC5kb3dubG9hZC1saW5rcyB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgICBoZWlnaHQ6IDMycHg7CiAgICAgIH0KCiAgICAgIC5kb3dubG9hZC1saW5rcyBhIHsKICAgICAgICBhbGlnbi1zZWxmOiBjZW50ZXI7CiAgICAgICAgZm9udC1zaXplOiAxMHB4OwogICAgICAgIG1hcmdpbjogMnB4OwogICAgICB9CgogICAgICAuZG93bmxvYWQtbGlua3MgcGFwZXItZHJvcGRvd24tbWVudSB7CiAgICAgICAgd2lkdGg6IDEwMHB4OwogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWxhYmVsOiB7CiAgICAgICAgICBmb250LXNpemU6IDEwcHg7CiAgICAgICAgfQogICAgICAgIC0tcGFwZXItaW5wdXQtY29udGFpbmVyLWlucHV0OiB7CiAgICAgICAgICBmb250LXNpemU6IDEwcHg7CiAgICAgICAgfQogICAgICB9CgogICAgICBwYXBlci1tZW51LWJ1dHRvbiB7CiAgICAgICAgcGFkZGluZzogMDsKICAgICAgfQogICAgICBwYXBlci1pdGVtIGEgewogICAgICAgIGNvbG9yOiBpbmhlcml0OwogICAgICAgIHRleHQtZGVjb3JhdGlvbjogbm9uZTsKICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJ0YWciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgImRhdGFUb0xvYWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZlNjYWxhckNhcmQucHJvdG90eXBlLCAieFR5cGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJhY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJpZ25vcmVZT3V0bGllcnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBSZXF1ZXN0TWFuYWdlcikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJyZXF1ZXN0TWFuYWdlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgInNob3dEb3duTGlua3MiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJzbW9vdGhpbmdFbmFibGVkIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgInNtb290aGluZ1dlaWdodCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJ0YWdNZXRhZGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJjb2xvclNjYWxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgInRvb2x0aXBTb3J0aW5nTWV0aG9kIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgIl9sb2FkRGF0YUNhbGxiYWNrIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pCiAgICBdLCBUZlNjYWxhckNhcmQucHJvdG90eXBlLCAiZ2V0RGF0YUxvYWRVcmwiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZlNjYWxhckNhcmQucHJvdG90eXBlLCAiX2Rvd25sb2FkVXJsRm4iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJyZXF1ZXN0RGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJfZ2V0RGF0YUxvYWROYW1lIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJfZXhwYW5kZWQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmU2NhbGFyQ2FyZC5wcm90b3R5cGUsICJfbG9nU2NhbGVBY3RpdmUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZTY2FsYXJDYXJkLnByb3RvdHlwZSwgIl90b29sdGlwQ29sdW1ucyIsIHZvaWQgMCk7CiAgICBUZlNjYWxhckNhcmQgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1zY2FsYXItY2FyZCcpCiAgICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm5vLXVudXNlZC12YXJpYWJsZQogICAgXSwgVGZTY2FsYXJDYXJkKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogU2hvd3MgYSBzZXNzaW9uIGdyb3VwIGluIG1vcmUgZGV0YWlsLiBTcGVjaWZpY2FsbHksIHNob3dzIGdyYXBocyBvZiB0aGUKICAgICAqIG1ldHJpY3MgZm9yIHRoZSBzZXNzaW9uIGluIHRoZSBncm91cCBhcyBhIGZ1bmN0aW9uIG9mIHRoZSB0cmFpbmluZyBzdGVwLgogICAgICogVGhpcyBlbGVtZW50IGlzIHNob3duIG9uZSB0aGUgdXNlciAiZHJpbGxzLWluIiB0byBhIHNlc3Npb24gZ3JvdXAsIGZvcgogICAgICogZXhhbXBsZSB3aGVuIHNoZSBjbGlja3Mgb24gYSByb3cgaW4gdGFibGUtdmlldyBvciBhIGN1cnZlIGluIHBhcmFsbGVsLWNvb3JkcwogICAgICogdmlldy4KICAgICAqLwogICAgbGV0IFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMgPSBjbGFzcyBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzIGV4dGVuZHMgbWl4aW5CZWhhdmlvcnMoW0lyb25SZXNpemFibGVCZWhhdmlvciQxXSwgUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgLy8gVGhlIHNlc3Npb24gZ3JvdXAgb2JqZWN0IHRvIGRpc3BsYXkuIE1hdGNoZXMgdGhlIFNlc3Npb25Hcm91cAogICAgICAgICAgICAvLyBwcm90b2NvbCBidWZmZXIgZGVmaW5lZCBpbiBhcGkucHJvdG8uCiAgICAgICAgICAgIHRoaXMuc2Vzc2lvbkdyb3VwID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5feFR5cGUgPSBYVHlwZS5TVEVQOwogICAgICAgICAgICB0aGlzLl9ub011bHRpRXhwZXJpbWVudHMgPSBmYWxzZTsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdERhdGEgPSAoaXRlbXMsIG9uTG9hZCwgb25GaW5pc2gpID0+IHsKICAgICAgICAgICAgICAgIFByb21pc2UuYWxsKGl0ZW1zLm1hcCgoaXRlbSkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IHJlcXVlc3QgPSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGV4cGVyaW1lbnROYW1lOiB0aGlzLmV4cGVyaW1lbnROYW1lLAogICAgICAgICAgICAgICAgICAgICAgICBzZXNzaW9uTmFtZTogaXRlbS5ydW4sCiAgICAgICAgICAgICAgICAgICAgICAgIG1ldHJpY05hbWU6IGl0ZW0udGFnLAogICAgICAgICAgICAgICAgICAgIH07CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHRoaXMuYmFja2VuZAogICAgICAgICAgICAgICAgICAgICAgICAubGlzdE1ldHJpY0V2YWxzKHJlcXVlc3QpCiAgICAgICAgICAgICAgICAgICAgICAgIC50aGVuKChkYXRhKSA9PiB2b2lkIG9uTG9hZCh7IGl0ZW0sIGRhdGEgfSkpOwogICAgICAgICAgICAgICAgfSkpLmZpbmFsbHkoKCkgPT4gdm9pZCBvbkZpbmlzaCgpKTsKICAgICAgICAgICAgfTsKICAgICAgICAgICAgdGhpcy5fY29sb3JTY2FsZSA9IHsKICAgICAgICAgICAgICAgIHNjYWxlOiAoc2VyaWVzTmFtZSkgPT4gewogICAgICAgICAgICAgICAgICAgIC8vIFRoZSB0Zi1zY2FsYXItY2FyZCBBUEkgc2VuZHMgYSBzZXJpZXNOYW1lIGFzIGEgSlNPTgogICAgICAgICAgICAgICAgICAgIC8vIHJlcHJlc2VudGF0aW9uIG9mIHRoZSAyLWVsZW1lbnQgYXJyYXkgW2V4cGVyaW1lbnQsIHJ1bl0sCiAgICAgICAgICAgICAgICAgICAgLy8gd2hlcmUgJ3J1bicgaXMgdGhlIHJ1biB3ZSByZXR1cm4gaW4gdGhlICdyZXF1ZXN0RGF0YScKICAgICAgICAgICAgICAgICAgICAvLyBmdW5jdGlvbi0taW4gb3VyIGNhc2UgdGhhdCBpcyB0aGUgc2Vzc2lvbiBuYW1lLCBhbmQKICAgICAgICAgICAgICAgICAgICAvLyAnZXhwZXJpbWVudCcgaXMgbm90IHVzZWQgaGVyZSB0Zi1zY2FsYXItY2FyZCdzCiAgICAgICAgICAgICAgICAgICAgLy8gbXVsdGktZXhwZXJpbWVudCBhdHRyaWJ1dGUgaXMgdHVybmVkIG9mZiBoZXJlKS4KICAgICAgICAgICAgICAgICAgICAvLyBUaGUgY29sb3Igb2YgYSBzZXNzaW9uIGlzIGRldGVybWluZWQgYnkgY2hvb3NpbmcgYQogICAgICAgICAgICAgICAgICAgIC8vIHN0YXJ0aW5nIHBvaW50IGluICdwYWxldHRlJyBiYXNlZCBvbiB0aGUgc2Vzc2lvbkdyb3VwIG5hbWUKICAgICAgICAgICAgICAgICAgICAvLyBhbmQgd2Fsa2luZyBjeWNsaWNseSAnc2Vzc2lvbkluZGV4JyBzdGVwcyBpbiB0aGUgYXJyYXksIHdoZXJlCiAgICAgICAgICAgICAgICAgICAgLy8gc2VzaW9uSW5kZXggaXMgdGhlIGluZGV4IG9mIHRoZSBzZXNzaW9uIGluIHRoZQogICAgICAgICAgICAgICAgICAgIC8vIGdyb3VwLiBXZSBkbyB0aGlzIGluc3RlYWQgb2YganVzdCBoYXNoaW5nIHRoZSBzZXNzaW9uIG5hbWUsCiAgICAgICAgICAgICAgICAgICAgLy8gdG8gZ3VhcmFudGVlIHRoYXQgd2UgZG9uJ3QgcmVwZWF0IGEgY29sb3IgaWYgdGhlIG51bWJlcgogICAgICAgICAgICAgICAgICAgIC8vIG9mIHNlc3Npb25zIGlzIGF0IG1vc3QgdGhlIHNpemUgb2YgdGhlIHBhbGV0dGUuCiAgICAgICAgICAgICAgICAgICAgLy8gTm90ZSB0aGF0IHRoaXMgbWV0aG9kIGlzIGNhbGxlZCBldmVyeSB0aW1lIHRoZSB1c2VyIG1vdmVzCiAgICAgICAgICAgICAgICAgICAgLy8gb3ZlciB0aGUgbWV0cmljIHBsb3QsIHNvIGl0IG5lZWRzIHRvIGJlIHJlYXNvbmFibHkgZmFzdC4KICAgICAgICAgICAgICAgICAgICBjb25zdCBzZXNzaW9uTmFtZSA9IEpTT04ucGFyc2Uoc2VyaWVzTmFtZSlbMV07CiAgICAgICAgICAgICAgICAgICAgY29uc3Qgc2Vzc2lvbkluZGV4ID0gdGhpcy5faW5kZXhPZlNlc3Npb24uZ2V0KHNlc3Npb25OYW1lKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBwYWxldHRlID0gc3RhbmRhcmQ7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHBhbGV0dGVbKHRoaXMuX3Nlc3Npb25Hcm91cE5hbWVIYXNoICsgc2Vzc2lvbkluZGV4KSAlIHBhbGV0dGUubGVuZ3RoXTsKICAgICAgICAgICAgICAgIH0sCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIC8vIFdoZW5ldmVyIHRoZSBiYWNrZW5kIHNlbmRzIGEgbmV3ICdzZXNzaW9uR3JvdXBzJyBhcnJheSByZXBseSB0byB0aGUKICAgICAgICAvLyBMaXN0U2Vzc2lvbkdyb3VwcyBSUEMsIHdlIHJlY3JlYXRlIHRoZSB0Zi1zZXNzaW9uLWdyb3VwLWRldGFpbAogICAgICAgIC8vIGVsZW1lbnRzIHRoYXQgY29ycmVzcG9uZCB0byBzZXNzaW9uIGdyb3VwcyB3aG9zZSBuYW1lIGlzIGluIHRoZSBuZXcKICAgICAgICAvLyBzZXNzaW9uR3JvdXBzIGFycmF5LiBBcyBzdWNoIHRoaXMgZWxlbWVudCBjYW4gYmUgY29uc3RydWN0ZWQgd2hlbiBvbmUKICAgICAgICAvLyBvZiBpdHMgcGFyZW50cyBjb250YWluZXIgaXMgaW52aXNpYmxlOiBmb3IgZXhhbXBsZSwgaWYgc2Vzc2lvbkdyb3VwcwogICAgICAgIC8vIHdhcyByZXBsYWNlZCB3aGVuIHRoZSB1c2VyIHdhcyBvbiB0aGUgcGFyYWxsZWwtY29vcmRpbmF0ZXMgdmlldyB0YWIKICAgICAgICAvLyBhbmQgdGhlIG5ldyBzZXNzaW9uR3JvdXBzIGNvbnRhaW5zIGEgc2Vzc2lvbiBncm91cCBvYmplY3QKICAgICAgICAvLyB3aG9zZSBtZXRyaWNzIHdlcmUgb3BlbiBpbiB0aGUgdGFibGUgdmlldyB0YWIgKGkuZS4gdGhlIG9sZAogICAgICAgIC8vIHNlc3Npb25Hcm91cHMgYXJyYXkgY29udGFpbmVkIGEgZGlzdGluY3QgSmF2YVNjcmlwdCBzZXNzaW9uR3JvdXAKICAgICAgICAvLyBvYmplY3Qgd2l0aCBzYW1lIG5hbWUpLgogICAgICAgIC8vIElmIHRoaXMgaGFwcGVucywgdGhlIHRmLXNjYWxhci1jYXJkIGNoaWxkIGVsZW1lbnRzIG9mIHRoaXMgZWxlbWVudAogICAgICAgIC8vIHdvdWxkIG1lYXN1cmUgYSAwIHNpemUgb2YgdGhlaXIgYm91bmRpbmcgYm94ZXMgYW5kIHdvdWxkIHJlbmRlcgogICAgICAgIC8vIGluY29ycmVjdGx5LiBUbyBhdm9pZCB0aGF0LCB3ZSBsaXN0ZW4gZm9yIHRoZSAnaXJvbi1yZXNpemUnIGV2ZW50CiAgICAgICAgLy8gdGhhdCBpcyBmaXJlZCBieSAnaXJvbi1wYWdlcycgd2hlbmV2ZXIgdGhlIGFjdGl2ZSBwYWdlIGNoYW5nZXMgYW5kCiAgICAgICAgLy8gcmVkcmF3IGVhY2ggdGYtc2NhbGFyLWNhcmQgY2hpbGQuCiAgICAgICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7CiAgICAgICAgICAgIHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7CiAgICAgICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcignaXJvbi1yZXNpemUnLCB0aGlzLnJlZHJhdy5iaW5kKHRoaXMpKTsKICAgICAgICB9CiAgICAgICAgcmVkcmF3KCkgewogICAgICAgICAgICB0aGlzLnNoYWRvd1Jvb3QKICAgICAgICAgICAgICAgIC5xdWVyeVNlbGVjdG9yQWxsKCd0Zi1zY2FsYXItY2FyZCcpCiAgICAgICAgICAgICAgICAuZm9yRWFjaCgoYykgPT4gYy5yZWRyYXcoKSk7CiAgICAgICAgfQogICAgICAgIF9zZXNzaW9uR3JvdXBDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAoIXRoaXMuc2Vzc2lvbkdyb3VwIHx8IE9iamVjdC5rZXlzKHRoaXMuc2Vzc2lvbkdyb3VwKS5sZW5ndGggPT0gMCkgewogICAgICAgICAgICAgICAgdGhpcy5faW5kZXhPZlNlc3Npb24gPSBuZXcgTWFwKCk7CiAgICAgICAgICAgICAgICB0aGlzLl9zZXNzaW9uR3JvdXBOYW1lSGFzaCA9IDA7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aGlzLl9pbmRleE9mU2Vzc2lvbiA9IG5ldyBNYXAodGhpcy5zZXNzaW9uR3JvdXAuc2Vzc2lvbnMubWFwKChzZXNzaW9uLCBpbmRleCkgPT4gWwogICAgICAgICAgICAgICAgICAgIHNlc3Npb24ubmFtZSwKICAgICAgICAgICAgICAgICAgICBpbmRleCwKICAgICAgICAgICAgICAgIF0pKTsKICAgICAgICAgICAgICAgIHRoaXMuX3Nlc3Npb25Hcm91cE5hbWVIYXNoID0gaGFzaE9mU3RyaW5nKHRoaXMuc2Vzc2lvbkdyb3VwLm5hbWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIFJlc2V0IGVhY2ggc2NhbGFyLWNhcmQgYnkgcHJvZGRpbmcgJ3RhZycuCiAgICAgICAgICAgIC8vIFdlIGRvIHRoaXMgc28gdGhlIGNhcmQgd2lsbCByZXNldCBpdHMgZG9tYWluIG9uIHRoZSBuZXh0IGxvYWQuCiAgICAgICAgICAgIHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCd0Zi1zY2FsYXItY2FyZCcpLmZvckVhY2goKGMpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IGFueUNhcmQgPSBjOwogICAgICAgICAgICAgICAgY29uc3QgdGFnID0gYW55Q2FyZC5nZXQoJ3RhZycpOwogICAgICAgICAgICAgICAgYW55Q2FyZC5zZXQoJ3RhZycsICcnKTsKICAgICAgICAgICAgICAgIGFueUNhcmQuc2V0KCd0YWcnLCB0YWcpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgX2hhdmVNZXRyaWNzKCkgewogICAgICAgICAgICByZXR1cm4gKHRoaXMudmlzaWJsZVNjaGVtYSAmJgogICAgICAgICAgICAgICAgQXJyYXkuaXNBcnJheSh0aGlzLnZpc2libGVTY2hlbWEubWV0cmljSW5mb3MpICYmCiAgICAgICAgICAgICAgICB0aGlzLnZpc2libGVTY2hlbWEubWV0cmljSW5mb3MubGVuZ3RoID4gMCk7CiAgICAgICAgfQogICAgICAgIF9oYXZlTWV0cmljc0FuZFNlc3Npb25Hcm91cCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuc2Vzc2lvbkdyb3VwICYmIHRoaXMuX2hhdmVNZXRyaWNzKCk7CiAgICAgICAgfQogICAgICAgIC8vIFJldHVybnMgYW4gYXJyYXkgb2YgdGhlIHRlbnNvcmJvYXJkICdydW5zJyBhbmQgJ3RhZ3MnIGNvcnJlc3BvbmRpbmcgdG8KICAgICAgICAvLyB0aGUgZ2l2ZW4gbWV0cmljIGluIGVhY2ggb2YgdGhlIHNlc3Npb25zIGluIHRoZSBnaXZlbiBzZXNzaW9uIGdyb3VwLgogICAgICAgIF9jb21wdXRlU2VyaWVzRm9yU2Vzc2lvbkdyb3VwTWV0cmljKHNlc3Npb25Hcm91cCwgbWV0cmljSW5mbykgewogICAgICAgICAgICBpZiAoc2Vzc2lvbkdyb3VwID09PSBudWxsIHx8CiAgICAgICAgICAgICAgICBPYmplY3Qua2V5cyhzZXNzaW9uR3JvdXApLmxlbmd0aCA9PSAwIHx8CiAgICAgICAgICAgICAgICBtZXRyaWNJbmZvID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW107CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHNlc3Npb25Hcm91cC5zZXNzaW9ucwogICAgICAgICAgICAgICAgLmZpbHRlcigKICAgICAgICAgICAgLy8gSWYgdGhpcyBzZXNzaW9uIGRvZXMgbm90IGN1cnJlbnRseSBoYXZlIGEgdmFsdWUgZm9yIHRoZSBnaXZlbgogICAgICAgICAgICAvLyBtZXRyaWMgdGhlbiB3ZSBkb24ndCB3YW50IHRvIGluY2x1ZGUgaXRzIHJ1bi4KICAgICAgICAgICAgKHNlc3Npb24pID0+IG1ldHJpY1ZhbHVlQnlOYW1lKHNlc3Npb24ubWV0cmljVmFsdWVzLCBtZXRyaWNJbmZvLm5hbWUpICE9PSB1bmRlZmluZWQpCiAgICAgICAgICAgICAgICAubWFwKAogICAgICAgICAgICAvLyBTaW5jZSB0aGUgJ3RhZycgYW5kICdydW4nIGZpZWxkcyBhcmUgZXNzZW50aWFsbHkgb3BhcXVlCiAgICAgICAgICAgIC8vIGZvciB0aGUgdGYtc2NhbGFyLWNhcmQgZWxlbWVudCwgYW5kIHBhc3NlZCBhcyBpcyB0byB0aGUKICAgICAgICAgICAgLy8gcmVxdWVzdERhdGEgZnVuY3Rpb24sIHdlIHVzZSB0aGVtIHRvIGVuY29kZSB0aGUgZmllbGRzIHdlCiAgICAgICAgICAgIC8vIG5lZWQgdG8gc3VwcGx5IHRvIHRoZSBldmFsX21ldHJpY3MgQVBJIChjYWxsZWQgaW4gb3VyCiAgICAgICAgICAgIC8vIGltcGxlbWVudGF0aW9uIG9mIHJlcXVlc3REYXRhIGFib3ZlKS4KICAgICAgICAgICAgKHNlc3Npb24pID0+ICh7IHRhZzogbWV0cmljSW5mby5uYW1lLCBydW46IHNlc3Npb24ubmFtZSB9KSk7CiAgICAgICAgfQogICAgICAgIC8vIENvbXB1dGVzIHRoZSB0YWctbWV0YWRhdGEgYXR0cmlidXRlIHRvIHNlbmQgdG8gdGhlCiAgICAgICAgLy8gdGYtc2NhbGFyLWNhcmQgZWxlbWVudC4KICAgICAgICBfY29tcHV0ZVRhZ01ldGFkYXRhKG1ldHJpY0luZm8pIHsKICAgICAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICAgICAgIGRpc3BsYXlOYW1lOiBtZXRyaWNOYW1lKG1ldHJpY0luZm8pLAogICAgICAgICAgICAgICAgZGVzY3JpcHRpb246IG1ldHJpY0luZm8uZGVzY3JpcHRpb24gfHwgJycsCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgfTsKICAgIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMudGVtcGxhdGUgPSBodG1sIGAKICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shc2Vzc2lvbkdyb3VwXV0iPgogICAgICA8ZGl2PgogICAgICAgIDxoMz5ObyBzZXNzaW9uIGdyb3VwIHNlbGVjdGVkPC9oMz4KICAgICAgICA8cD5QbGVhc2Ugc2VsZWN0IGEgc2Vzc2lvbiBncm91cCB0byBzZWUgaXRzIG1ldHJpYy1ncmFwaHMgaGVyZS48L3A+CiAgICAgIDwvZGl2PgogICAgPC90ZW1wbGF0ZT4KICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1shX2hhdmVNZXRyaWNzKHZpc2libGVTY2hlbWEuKildXSI+CiAgICAgIDxkaXY+CiAgICAgICAgPGgzPk5vIG1ldHJpY3MgYXJlIGVuYWJsZWQ8L2gzPgogICAgICAgIDxwPlBsZWFzZSBlbmFibGUgc29tZSBtZXRyaWNzIHRvIHNlZSBjb250ZW50IGhlcmUuPC9wPgogICAgICA8L2Rpdj4KICAgIDwvdGVtcGxhdGU+CiAgICA8ZGl2IGNsYXNzPSJsYXlvdXQgaG9yaXpvbnRhbCB3cmFwIHNlc3Npb24tZ3JvdXAtZGV0YWlscyI+CiAgICAgIDx0ZW1wbGF0ZQogICAgICAgIGlzPSJkb20taWYiCiAgICAgICAgaWY9IltbX2hhdmVNZXRyaWNzQW5kU2Vzc2lvbkdyb3VwKHZpc2libGVTY2hlbWEuKiwgc2Vzc2lvbkdyb3VwKV1dIgogICAgICA+CiAgICAgICAgPHRlbXBsYXRlCiAgICAgICAgICBpcz0iZG9tLXJlcGVhdCIKICAgICAgICAgIGl0ZW1zPSJbW3Zpc2libGVTY2hlbWEubWV0cmljSW5mb3NdXSIKICAgICAgICAgIGFzPSJtZXRyaWNJbmZvIgogICAgICAgID4KICAgICAgICAgIDwhLS0gTm90ZSB0aGF0IHdlIGRvIG5vdCBwcm92aWRlIGEgcmVxdWVzdC1tYW5hZ2VyIGF0dHJpYnV0ZSBzaW5jZQogICAgICAgICAgICAgICB3ZSBwcm92aWRlIGEgZnVuY3Rpb24gaW4gcmVxdWVzdC1kYXRhIGZvciBjYWxsaW5nIHRoZSBiYWNrZW5kCiAgICAgICAgICAgICAgIHRvIGdldCB0aGUgbWV0cmljcyBkYXRhLgogICAgICAgICAgICAtLT4KICAgICAgICAgIDx0Zi1zY2FsYXItY2FyZAogICAgICAgICAgICBjbGFzcz0ic2NhbGFyLWNhcmQiCiAgICAgICAgICAgIGNvbG9yLXNjYWxlPSJbW19jb2xvclNjYWxlXV0iCiAgICAgICAgICAgIGRhdGEtdG8tbG9hZD0iW1tfY29tcHV0ZVNlcmllc0ZvclNlc3Npb25Hcm91cE1ldHJpYyhzZXNzaW9uR3JvdXAsIG1ldHJpY0luZm8pXV0iCiAgICAgICAgICAgIHRhZz0iW1ttZXRyaWNJbmZvLm5hbWUudGFnXV0iCiAgICAgICAgICAgIHRhZy1tZXRhZGF0YT0iW1tfY29tcHV0ZVRhZ01ldGFkYXRhKG1ldHJpY0luZm8pXV0iCiAgICAgICAgICAgIHgtdHlwZT0iW1tfeFR5cGVdXSIKICAgICAgICAgICAgbXVsdGktZXhwZXJpbWVudHM9IltbX25vTXVsdGlFeHBlcmltZW50c11dIgogICAgICAgICAgICByZXF1ZXN0LWRhdGE9IltbX3JlcXVlc3REYXRhXV0iCiAgICAgICAgICAgIGFjdGl2ZQogICAgICAgICAgPgogICAgICAgICAgPC90Zi1zY2FsYXItY2FyZD4KICAgICAgICA8L3RlbXBsYXRlPgogICAgICA8L3RlbXBsYXRlPgogICAgPC9kaXY+CiAgICA8IS0tICJpcm9uLWZsZXgiIGlzIG5lZWRlZCB0byB1c2UgdGhlIGxheW91dCBjbGFzc2VzIGluIHRoZSBkaXYgYWJvdmUgLS0+CiAgICA8c3R5bGUgaW5jbHVkZT0iaXJvbi1mbGV4Ij4KICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiYmFja2VuZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiZXhwZXJpbWVudE5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzLnByb3RvdHlwZSwgInZpc2libGVTY2hlbWEiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzLnByb3RvdHlwZSwgInNlc3Npb25Hcm91cCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IFN0cmluZywKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiX3hUeXBlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzLnByb3RvdHlwZSwgIl9ub011bHRpRXhwZXJpbWVudHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzLnByb3RvdHlwZSwgIl9pbmRleE9mU2Vzc2lvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiX3Nlc3Npb25Hcm91cE5hbWVIYXNoIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzLnByb3RvdHlwZSwgIl9yZXF1ZXN0RGF0YSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiX2NvbG9yU2NhbGUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnc2Vzc2lvbkdyb3VwLionKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMucHJvdG90eXBlLCAiX3Nlc3Npb25Hcm91cENoYW5nZWQiLCBudWxsKTsKICAgIFRmSHBhcmFtc1Nlc3Npb25Hcm91cERldGFpbHMgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtZGV0YWlscycpCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uR3JvdXBEZXRhaWxzKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIGxldCBUZkhwYXJhbXNUYWJsZVZpZXcgPSBjbGFzcyBUZkhwYXJhbXNUYWJsZVZpZXcgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5faHBhcmFtTmFtZSA9IGhwYXJhbU5hbWU7CiAgICAgICAgICAgIHRoaXMuX21ldHJpY05hbWUgPSBtZXRyaWNOYW1lOwogICAgICAgIH0KICAgICAgICBfdmlzaWJsZVNjaGVtYU9yU2Vzc2lvbkdyb3Vwc0NoYW5nZWQoKSB7CiAgICAgICAgICAgIC8vIEZyb20gdmFhZGluLWdyaWQgMy4wLjA6CiAgICAgICAgICAgIC8vIFZhYWRpbi1ncmlkIHJlbW92ZXMgJ3Jvdy1kZXRhaWxzJyBpZiB0aGUgdmlzaWJsZVNjaGVtYSBjaGFuZ2VzCiAgICAgICAgICAgIC8vIGFuZCBkb2Vzbid0IHVwZGF0ZSAnZXhwYW5kZWRJdGVtcycuIFNvIHdlIGZpcnN0IGNsb3NlIHRoZQogICAgICAgICAgICAvLyBleHBhbmRlZCBpdGVtcywgY2FsbCBQb2x5bWVyLmRvbS5mbHVzaCgpIHRvIHVwZGF0ZSB0aGUgZ3JpZCwKICAgICAgICAgICAgLy8gYW5kIHRoZW4gcmUtb3BlbiB0aGUgZ3JvdXBzIHRoYXQgd2VyZSBvcGVuIGJlZm9yZS4KICAgICAgICAgICAgLy8KICAgICAgICAgICAgLy8gU2luY2UgdGhlbiwgd2UgaGF2ZSB1cGdyYWRlZCB0byB2YWFkaW4tZ3JpZCA1LjYuNiwgd2hlcmUgdGhlIGNvbW1lbnQKICAgICAgICAgICAgLy8gbWF5IGJlIHN0YWxlLiBOb3RhYmx5LCBWYWFkaW4gcmVuYW1lZCAnZXhwYW5kZWRJdGVtcycgdG8KICAgICAgICAgICAgLy8gJ2RldGFpbHNPcGVuZWRJdGVtcycuCiAgICAgICAgICAgIGNvbnN0IGV4cGFuZGVkSXRlbXMgPSB0aGlzLiQuc2Vzc2lvbkdyb3Vwc1RhYmxlLmdldCgnZGV0YWlsc09wZW5lZEl0ZW1zJyk7CiAgICAgICAgICAgIHRoaXMuJC5zZXNzaW9uR3JvdXBzVGFibGUuc2V0KCdkZXRhaWxzT3BlbmVkSXRlbXMnLCBbXSk7CiAgICAgICAgICAgIGZsdXNoKCk7CiAgICAgICAgICAgIC8vIEluZGV4IHNlc3Npb25Hcm91cHMgYnkgbmFtZS4KICAgICAgICAgICAgY29uc3Qgc2Vzc2lvbkdyb3Vwc0J5TmFtZSA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgdGhpcy5zZXNzaW9uR3JvdXBzLmZvckVhY2goKHNnKSA9PiB7CiAgICAgICAgICAgICAgICBzZXNzaW9uR3JvdXBzQnlOYW1lLnNldChzZy5uYW1lLCBzZyk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLiQuc2Vzc2lvbkdyb3Vwc1RhYmxlLnNldCgnZGV0YWlsc09wZW5lZEl0ZW1zJywgZXhwYW5kZWRJdGVtcwogICAgICAgICAgICAgICAgLm1hcCgoc2cpID0+IHNlc3Npb25Hcm91cHNCeU5hbWUuZ2V0KHNnLm5hbWUpKQogICAgICAgICAgICAgICAgLmZpbHRlcihCb29sZWFuKSk7CiAgICAgICAgfQogICAgICAgIF9zZXNzaW9uR3JvdXBIUGFyYW0oc2Vzc2lvbkdyb3VwLCBocGFyYW0pIHsKICAgICAgICAgICAgaWYgKHNlc3Npb25Hcm91cCA9PSBudWxsIHx8CiAgICAgICAgICAgICAgICBPYmplY3Qua2V5cyhzZXNzaW9uR3JvdXApLmxlbmd0aCA9PSAwIHx8CiAgICAgICAgICAgICAgICAhT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKHNlc3Npb25Hcm91cC5ocGFyYW1zLCBocGFyYW0pKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gJyc7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIHByZXR0eVByaW50KHNlc3Npb25Hcm91cC5ocGFyYW1zW2hwYXJhbV0pOwogICAgICAgIH0KICAgICAgICAvLyBSZXR1cm5zIHRoZSBtZXRyaWMgdmFsdWUgb2YgdGhlIGdpdmVuIHNlc3Npb25Hcm91cC4gVGhlIHZhbHVlIGlzCiAgICAgICAgLy8gcmV0dXJuZWQgYXMgYSBzdHJpbmcgc3VpdGFibGUgZm9yIGRpc3BsYXkuCiAgICAgICAgX3Nlc3Npb25Hcm91cE1ldHJpYyhzZXNzaW9uR3JvdXAsIG1ldHJpY05hbWUpIHsKICAgICAgICAgICAgaWYgKHNlc3Npb25Hcm91cCA9PSBudWxsIHx8IE9iamVjdC5rZXlzKHNlc3Npb25Hcm91cCkubGVuZ3RoID09IDApIHsKICAgICAgICAgICAgICAgIHJldHVybiAnJzsKICAgICAgICAgICAgfQogICAgICAgICAgICBmb3IgKGxldCBpID0gMDsgaSA8IHNlc3Npb25Hcm91cC5tZXRyaWNWYWx1ZXMubGVuZ3RoOyArK2kpIHsKICAgICAgICAgICAgICAgIGxldCBtZXRyaWNWYWwgPSBzZXNzaW9uR3JvdXAubWV0cmljVmFsdWVzW2ldOwogICAgICAgICAgICAgICAgaWYgKG1ldHJpY1ZhbC5uYW1lLmdyb3VwID09PSBtZXRyaWNOYW1lLmdyb3VwICYmCiAgICAgICAgICAgICAgICAgICAgbWV0cmljVmFsLm5hbWUudGFnID09IG1ldHJpY05hbWUudGFnKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIHByZXR0eVByaW50KG1ldHJpY1ZhbC52YWx1ZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgIH0KICAgICAgICBfcm93TnVtYmVyKHJvd0luZGV4KSB7CiAgICAgICAgICAgIHJldHVybiByb3dJbmRleCArIDE7CiAgICAgICAgfQogICAgfTsKICAgIFRmSHBhcmFtc1RhYmxlVmlldy50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHZhYWRpbi1ncmlkCiAgICAgIGNsYXNzPSJzZXNzaW9uLWdyb3VwLXRhYmxlIgogICAgICBpZD0ic2Vzc2lvbkdyb3Vwc1RhYmxlIgogICAgICBjb2x1bW4tcmVvcmRlcmluZy1hbGxvd2VkPSIiCiAgICAgIGl0ZW1zPSJbW3Nlc3Npb25Hcm91cHNdXSIKICAgID4KICAgICAgPHZhYWRpbi1ncmlkLWNvbHVtbiBmbGV4LWdyb3c9IjAiIHdpZHRoPSIxMGVtIiByZXNpemFibGU9IiI+CiAgICAgICAgPHRlbXBsYXRlIGNsYXNzPSJoZWFkZXIiPgogICAgICAgICAgPGRpdiBjbGFzcz0idGFibGUtaGVhZGVyIHRhYmxlLWNlbGwiPlRyaWFsIElEPC9kaXY+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJ0YWJsZS1jZWxsIj5bW2l0ZW0ubmFtZV1dPC9kaXY+CiAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPC92YWFkaW4tZ3JpZC1jb2x1bW4+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tlbmFibGVTaG93TWV0cmljc11dIj4KICAgICAgICA8dmFhZGluLWdyaWQtY29sdW1uIGZsZXgtZ3Jvdz0iMCIgYXV0b1dpZHRoPSIiIHJlc2l6YWJsZT0iIj4KICAgICAgICAgIDx0ZW1wbGF0ZSBjbGFzcz0iaGVhZGVyIj4KICAgICAgICAgICAgPGRpdiBjbGFzcz0idGFibGUtaGVhZGVyIHRhYmxlLWNlbGwiPlNob3cgTWV0cmljczwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgPHBhcGVyLWNoZWNrYm94IGNsYXNzPSJ0YWJsZS1jZWxsIiBjaGVja2VkPSJ7e2RldGFpbHNPcGVuZWR9fSI+CiAgICAgICAgICAgIDwvcGFwZXItY2hlY2tib3g+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvdmFhZGluLWdyaWQtY29sdW1uPgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUKICAgICAgICBpcz0iZG9tLXJlcGVhdCIKICAgICAgICBpdGVtcz0iW1t2aXNpYmxlU2NoZW1hLmhwYXJhbUluZm9zXV0iCiAgICAgICAgYXM9ImhwYXJhbUluZm8iCiAgICAgICAgaW5kZXgtYXM9ImhwYXJhbUluZGV4IgogICAgICA+CiAgICAgICAgPHZhYWRpbi1ncmlkLWNvbHVtbiBmbGV4LWdyb3c9IjIiIHdpZHRoPSIxMGVtIiByZXNpemFibGU9IiI+CiAgICAgICAgICA8dGVtcGxhdGUgY2xhc3M9ImhlYWRlciI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9InRhYmxlLWhlYWRlciB0YWJsZS1jZWxsIj4KICAgICAgICAgICAgICBbW19ocGFyYW1OYW1lKGhwYXJhbUluZm8pXV0KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgICAgPHRlbXBsYXRlPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJ0YWJsZS1jZWxsIj4KICAgICAgICAgICAgICBbW19zZXNzaW9uR3JvdXBIUGFyYW0oaXRlbSwgaHBhcmFtSW5mby5uYW1lKV1dCiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICA8L3ZhYWRpbi1ncmlkLWNvbHVtbj4KICAgICAgPC90ZW1wbGF0ZT4KICAgICAgPHRlbXBsYXRlCiAgICAgICAgaXM9ImRvbS1yZXBlYXQiCiAgICAgICAgaXRlbXM9Int7dmlzaWJsZVNjaGVtYS5tZXRyaWNJbmZvc319IgogICAgICAgIGFzPSJtZXRyaWNJbmZvIgogICAgICAgIGluZGV4LWFzPSJtZXRyaWNJbmRleCIKICAgICAgPgogICAgICAgIDx2YWFkaW4tZ3JpZC1jb2x1bW4gZmxleC1ncm93PSIyIiB3aWR0aD0iMTBlbSIgcmVzaXphYmxlPSIiPgogICAgICAgICAgPHRlbXBsYXRlIGNsYXNzPSJoZWFkZXIiPgogICAgICAgICAgICA8ZGl2IGNsYXNzPSJ0YWJsZS1oZWFkZXIgdGFibGUtY2VsbCI+CiAgICAgICAgICAgICAgW1tfbWV0cmljTmFtZShtZXRyaWNJbmZvKV1dCiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC90ZW1wbGF0ZT4KICAgICAgICAgIDx0ZW1wbGF0ZT4KICAgICAgICAgICAgPGRpdiBjbGFzcz0idGFibGUtY2VsbCI+CiAgICAgICAgICAgICAgW1tfc2Vzc2lvbkdyb3VwTWV0cmljKGl0ZW0sIG1ldHJpY0luZm8ubmFtZSldXQogICAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPC92YWFkaW4tZ3JpZC1jb2x1bW4+CiAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDx0ZW1wbGF0ZSBjbGFzcz0icm93LWRldGFpbHMiPgogICAgICAgIDx0Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtZGV0YWlscwogICAgICAgICAgYmFja2VuZD0iW1tiYWNrZW5kXV0iCiAgICAgICAgICBleHBlcmltZW50LW5hbWU9IltbZXhwZXJpbWVudE5hbWVdXSIKICAgICAgICAgIHNlc3Npb24tZ3JvdXA9IltbaXRlbV1dIgogICAgICAgICAgdmlzaWJsZS1zY2hlbWE9IltbdmlzaWJsZVNjaGVtYV1dIgogICAgICAgICAgY2xhc3M9InNlc3Npb24tZ3JvdXAtZGV0YWlscyIKICAgICAgICA+CiAgICAgICAgPC90Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtZGV0YWlscz4KICAgICAgPC90ZW1wbGF0ZT4KICAgIDwvdmFhZGluLWdyaWQ+CgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogaW5saW5lOwogICAgICB9CiAgICAgIC50YWJsZS1jZWxsIHsKICAgICAgICB3aGl0ZS1zcGFjZTogbm93cmFwOwogICAgICAgIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzOwogICAgICAgIG92ZXJmbG93OiBoaWRkZW47CiAgICAgIH0KICAgICAgLnRhYmxlLWhlYWRlciB7CiAgICAgICAgLyogbGluZS1icmVhayBvdmVyZmxvd2luZyBjb2x1bW4gaGVhZGVycyAqLwogICAgICAgIHdoaXRlLXNwYWNlOiBub3JtYWw7CiAgICAgICAgb3ZlcmZsb3ctd3JhcDogYnJlYWstd29yZDsKICAgICAgfQogICAgICAuc2Vzc2lvbi1ncm91cC10YWJsZSB7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CiAgICAgIC5zZXNzaW9uLWdyb3VwLWRldGFpbHMgewogICAgICAgIGhlaWdodDogMzYwcHg7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNUYWJsZVZpZXcucHJvdG90eXBlLCAidmlzaWJsZVNjaGVtYSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkhwYXJhbXNUYWJsZVZpZXcucHJvdG90eXBlLCAic2Vzc2lvbkdyb3VwcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEJvb2xlYW4gfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKQogICAgXSwgVGZIcGFyYW1zVGFibGVWaWV3LnByb3RvdHlwZSwgImVuYWJsZVNob3dNZXRyaWNzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zVGFibGVWaWV3LnByb3RvdHlwZSwgImJhY2tlbmQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkhwYXJhbXNUYWJsZVZpZXcucHJvdG90eXBlLCAiZXhwZXJpbWVudE5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgndmlzaWJsZVNjaGVtYS4qJywgJ3Nlc3Npb25Hcm91cHMuKicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZIcGFyYW1zVGFibGVWaWV3LnByb3RvdHlwZSwgIl92aXNpYmxlU2NoZW1hT3JTZXNzaW9uR3JvdXBzQ2hhbmdlZCIsIG51bGwpOwogICAgVGZIcGFyYW1zVGFibGVWaWV3ID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtaHBhcmFtcy10YWJsZS12aWV3JykKICAgIF0sIFRmSHBhcmFtc1RhYmxlVmlldyk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZIcGFyYW1zU2Vzc2lvbkdyb3VwVmFsdWVzID0gY2xhc3MgVGZIcGFyYW1zU2Vzc2lvbkdyb3VwVmFsdWVzIGV4dGVuZHMgUG9seW1lckVsZW1lbnQgewogICAgICAgIGNvbnN0cnVjdG9yKCkgewogICAgICAgICAgICBzdXBlciguLi5hcmd1bWVudHMpOwogICAgICAgICAgICAvLyBUaGUgc2Vzc2lvbiBncm91cCB3aG9zZSB2YWx1ZXMgd2lsbCBiZSBkaXNwbGF5ZWQuCiAgICAgICAgICAgIC8vIEEgSmF2YVNjcmlwdCByZXByZXNlbnRhdGlvbiBvZiB0aGUgdGVuc29yYm9hcmQuaHBhcmFtcy5TZXNzaW9uR3JvdXAKICAgICAgICAgICAgLy8gcHJvdG9jb2wgYnVmZmVyLgogICAgICAgICAgICB0aGlzLnNlc3Npb25Hcm91cCA9IG51bGw7CiAgICAgICAgICAgIC8vIFRoZSB2aXNpYmxlU2NoZW1hIGRlZmluaW5nIHRoZSBjb2x1bW5zIHRvIHVzZS4KICAgICAgICAgICAgLy8gT25seSB0aGUgdmFsdWVzIG9mIGNvbHVtbnMgaW4gdGhlIHZpc2libGVTY2hlbWEgd2lsbCBiZSBkaXNwbGF5ZWQuCiAgICAgICAgICAgIC8vIFNlZSB0Zi1ocGFyYW1zLXF1ZXJ5LXBhbmUgZm9yIHRoZSBkZWZpbml0aW9uIG9mIHRoaXMgb2JqZWN0LgogICAgICAgICAgICB0aGlzLnZpc2libGVTY2hlbWEgPSBudWxsOwogICAgICAgIH0KICAgICAgICBfcHJvcGVydGllc0FyZVBvcHVsYXRlZCh2aXNpYmxlU2NoZW1hLCBzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgcmV0dXJuICh2aXNpYmxlU2NoZW1hICE9PSB1bmRlZmluZWQgJiYKICAgICAgICAgICAgICAgIHZpc2libGVTY2hlbWEgIT09IG51bGwgJiYKICAgICAgICAgICAgICAgIHNlc3Npb25Hcm91cCAhPT0gdW5kZWZpbmVkICYmCiAgICAgICAgICAgICAgICBzZXNzaW9uR3JvdXAgIT09IG51bGwpOwogICAgICAgIH0KICAgICAgICBfc2luZ2xldG9uU2Vzc2lvbkdyb3VwcyhzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgaWYgKHNlc3Npb25Hcm91cCA9PT0gbnVsbCB8fCBzZXNzaW9uR3JvdXAgPT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFtdOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBbc2Vzc2lvbkdyb3VwXTsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zU2Vzc2lvbkdyb3VwVmFsdWVzLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8IS0tIElmIHNlc3Npb25Hcm91cCBvciB2aXNpYmxlU2NoZW1hIGFyZSBub3QgcG9wdWxhdGVkLCBkbyBub3QgZGlzcGxheQogICAgICAgICBhbnl0aGluZy4KICAgICAgLS0+CiAgICA8dGVtcGxhdGUKICAgICAgaXM9ImRvbS1pZiIKICAgICAgaWY9IltbX3Byb3BlcnRpZXNBcmVQb3B1bGF0ZWQodmlzaWJsZVNjaGVtYSwgc2Vzc2lvbkdyb3VwKV1dIgogICAgPgogICAgICA8IS0tIERpc3BsYXkgb25lIHJvdyB3aXRob3V0IGEgInNob3ctbWV0cmljcyIgY29sdW1uIC0tPgogICAgICA8dGYtaHBhcmFtcy10YWJsZS12aWV3CiAgICAgICAgdmlzaWJsZS1zY2hlbWE9IltbdmlzaWJsZVNjaGVtYV1dIgogICAgICAgIHNlc3Npb24tZ3JvdXBzPSJbW19zaW5nbGV0b25TZXNzaW9uR3JvdXBzKHNlc3Npb25Hcm91cCldXSIKICAgICAgPgogICAgICA8L3RmLWhwYXJhbXMtdGFibGUtdmlldz4KICAgIDwvdGVtcGxhdGU+CiAgICA8dGVtcGxhdGUKICAgICAgaXM9ImRvbS1pZiIKICAgICAgaWY9IltbIV9wcm9wZXJ0aWVzQXJlUG9wdWxhdGVkKHZpc2libGVTY2hlbWEsIHNlc3Npb25Hcm91cCldXSIKICAgID4KICAgICAgPGRpdj5DbGljayBvciBob3ZlciBvdmVyIGEgc2Vzc2lvbiBncm91cCB0byBkaXNwbGF5IGl0cyB2YWx1ZXMgaGVyZS48L2Rpdj4KICAgIDwvdGVtcGxhdGU+CgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2Vzc2lvbkdyb3VwVmFsdWVzLnByb3RvdHlwZSwgInNlc3Npb25Hcm91cCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25Hcm91cFZhbHVlcy5wcm90b3R5cGUsICJ2aXNpYmxlU2NoZW1hIiwgdm9pZCAwKTsKICAgIFRmSHBhcmFtc1Nlc3Npb25Hcm91cFZhbHVlcyA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhwYXJhbXMtc2Vzc2lvbi1ncm91cC12YWx1ZXMnKQogICAgXSwgVGZIcGFyYW1zU2Vzc2lvbkdyb3VwVmFsdWVzKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8vIEZpbmRzIHRoZSAiY2xvc2VzdCIgcGF0aCB0byBhIGdpdmVuICd0YXJnZXQnIHBvaW50IGZyb20gYSBnaXZlbiBhcnJheQogICAgLy8gb2YgJ3BhdGhzJy4KICAgIC8vIEVhY2ggZWxlbWVudCBpbiAncGF0aHMnIHJlcHJlc2VudHMgYSBwYXRoIGFuZCBzaG91bGQgYmUgYW4gb2JqZWN0IHdpdGgKICAgIC8vIGEgJ2NvbnRyb2xQb2ludHMnIHByb3BlcnR5IGNvbnRhaW5pbmcgYSBkLWVsZW1lbnQgYXJyYXkgb2YgdGhlIGZvcm0KICAgIC8vIFtbeDEseTFdLC4uLixbeF9kLHlfZF1dIGNvbnRhaW5pbmcgdGhlIHBhdGgncyBjb250cm9sIHBvaW50cwogICAgLy8gaW4gYXNjZW5kaW5nICd4JyBjb29yZGluYXRlIG9yZGVyLCB3aGVyZSBkIGlzIHRoZSBudW1iZXIgb2YgYXhlcy4KICAgIC8vICdheGVzUG9zJyBzaG91bGQgYmUgYSBkLWVsZW1lbnQgYXJyYXkgY29udGFpbm5nIHRoZSB4IGNvb3JkaW5hdGUgb2YKICAgIC8vIGVhY2ggYXhpcy4KICAgIC8vICd0YXJnZXQnIHNob3VsZCBiZSBhIDItZCBhcnJheSBvZiB0aGUgZm9ybSBbeCwgeV0gZGVmaW5pbmcgdGhlIHRhcmdldAogICAgLy8gcG9pbnQuCiAgICAvLyAndGhyZXNob2xkJyBkZW5vdGVzIGEgdGhyZXNob2xkIHdoZXJlIGlmIHRoZSBjbG9zZXN0IHBhdGggaGFzIGRpc3RhbmNlCiAgICAvLyAoc2VlIGJlbG93KSBvZiBtb3JlIHRoYW4gJ3RocmVzaG9sZCcsIHRoZSByZXR1cm4gdmFsdWUgaXMgbnVsbC4KICAgIC8vCiAgICAvLyBXZSBkZWZpbmUgIkNsb3Nlc3QgcGF0aCIgd2l0aCByZXNwZWN0IHRvIHRoZSBmb2xsb3dpbmcgZGVmaW5pdGlvbiBvZgogICAgLy8gZGlzdGFuY2UuIFRoZSBkaXN0YW5jZSBmcm9tIGEgcG9pbnQgJ3RhcmdldCcgdG8gYSBwYXRoICdwJyBpcwogICAgLy8gdGhlIG1pbmltdW0gRXVjbGlkZWFuIGRpc3RhbmNlIGZyb20gJ3RhcmdldCcgdG8gYSBwb2ludCBpbiB0aGUKICAgIC8vIHN0cmFpZ2h0LWxpbmUgc2VnbWVudCBjb25uZWN0aW5nIHRoZSB0d28gY29udHJvbCBwb2ludHMgb2YgJ3AnCiAgICAvLyAiYXNzb2NpYXRlZCIgd2l0aCAndGFyZ2V0Jy4gVGhlIGNvbnRyb2wgcG9pbnRzIGFzc29jaWF0ZWQgd2l0aCB0YXJnZXQKICAgIC8vIGFyZSB0aG9zZSBjb3JyZXNwb25kaW5nIHRvIHRoZSAyIGF4ZXMgY2xvc2VzdCAodW5kZXIgdGhlIHVzdWFsCiAgICAvLyBFdWNsaWRlYW4gbWVhbmluZykgdG8gJ3RhcmdldCcgKHRpZXMgYXJlIGJyb2tlbiBieSBwcmVmZXJyaW5nIGF4ZXMKICAgIC8vIHdpdGggc21hbGxlciBjb29yZGluYXRlcykuCiAgICAvLwogICAgLy8gVGhlIHJldHVybiB2YWx1ZSBvZiB0aGlzIG1ldGhvZCBpcyBhIGNsb3Nlc3QgbWVtYmVyIG9mICdwYXRocycgdG8KICAgIC8vICd0YXJnZXQnIGlmIHRoZSBjbG9zZXN0IGRpc3RhbmNlIGlzIGF0IG1vc3QgJ3RocmVzaG9sZCcgb3IgbnVsbAogICAgLy8gb3RoZXJ3aXNlLgogICAgZnVuY3Rpb24gZmluZENsb3Nlc3RQYXRoKHBhdGhzLCBheGVzUG9zLCB0YXJnZXQsIHRocmVzaG9sZCkgewogICAgICAgIGlmIChheGVzUG9zLmxlbmd0aCA8IDIpIHsKICAgICAgICAgICAgY29uc29sZS5lcnJvcignTGVzcyB0aGFuIHR3byBheGVzIGluIHBhcmFsbGVsIGNvb3JkaW5hdGVzIHBsb3QuJyk7CiAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgIH0KICAgICAgICBjb25zdCBjeCA9IHRhcmdldFswXTsKICAgICAgICBjb25zdCBjeSA9IHRhcmdldFsxXTsKICAgICAgICBpZiAoY3ggPD0gYXhlc1Bvc1swXSB8fCBjeCA+PSBheGVzUG9zW2F4ZXNQb3MubGVuZ3RoIC0gMV0pIHsKICAgICAgICAgICAgcmV0dXJuIG51bGw7CiAgICAgICAgfQogICAgICAgIC8vIEZpbmQgdGhlIGluZGljZXMgYSwgYiBvZiB0aGUgdHdvIGF4ZXMgY2xvc2VzdCB0byAndGFyZ2V0Jy4KICAgICAgICBjb25zdCBiID0gbG9kYXNoLnNvcnRlZEluZGV4KGF4ZXNQb3MsIGN4KTsKICAgICAgICBjb25zb2xlLmFzc2VydChiID4gMCk7CiAgICAgICAgY29uc29sZS5hc3NlcnQoYiA8IGF4ZXNQb3MubGVuZ3RoKTsKICAgICAgICBjb25zdCBhID0gYiAtIDE7CiAgICAgICAgLy8gQ29tcHV0ZXMgdGhlIHNxdWFyZSBvZiB0aGUgbWluaW11bSBFdWNsaWRlYW4gZGlzdGFuY2UgZnJvbQogICAgICAgIC8vIChjeCwgY3kpIHRvIGEgcG9pbnQgb24gdGhlIGxpbmUgc2VnbWVudCBjb25uZWN0aW5nCiAgICAgICAgLy8gKGF4LGF5KSBhbmQgKGJ4LGJ5KS4KICAgICAgICAvLwogICAgICAgIC8vIE1ldGhvZDogTGV0IEE9KGF4LGF5KSwgQj0oYngsYnkpIGFuZCBDPShjeCwgY3kpOgogICAgICAgIC8vIEEgcGFyYW1ldHJpYyBmcm9tIG9mIHRoZSBsaW5lIHBhc3NpbmcgdGhyb3VnaCBBIGFuZCBCIGlzOgogICAgICAgIC8vIEIrdChBLUIpOyB0IHJlYWwuCiAgICAgICAgLy8gVGhlIGxpbmUgc2VnbWVudCBpcyB0aGUgcGFydCB3aXRoIDA8PXQ8PTEuCiAgICAgICAgLy8gTGV0ICd0cCcgYmUgdGhlICd0JyBjb3JyZXNwb25kaW5nIHRvIHRoZSBwcm9qZWN0aW9uIG9mIEMgb250byB0aGUKICAgICAgICAvLyBsaW5lLiBDbGVhcmx5LCAndHAnIHNhdGlzZmllczoKICAgICAgICAvLyA8Qy0oQit0cChBLUIpKSxBLUI+ID0gMCwgd2hlcmUgPD4gZGVub3RlcyB0aGUgZG90IHByb2R1Y3QuIFNvbHZpbmcKICAgICAgICAvLyBmb3IgdHAsIG9uZSBnZXRzOiB0cCA9IDxBLUIsQy1CPiAvIDxBLUIsQS1CPi4KICAgICAgICAvLyBTaW5jZSB0aGUgcG9pbnQgb24gdGhlIGxpbmUgc2VnbWVudCBjbG9zZXN0IHRvIEMgaXMgdGhlIHBvaW50IG9uCiAgICAgICAgLy8gdGhlIHNlZ21lbnQgY2xvc2VzdCB0byB0aGUgcHJvamVjdGlvbiBvZiBDIG9udG8gdGhlIGxpbmUsIHdlIGdldDoKICAgICAgICAvLyBpZiB0cDw9MCwgdGhlIGNsb3Nlc3QgcG9pbnQgb24gdGhlIGxpbmUgc2VnbWVudCBpcyBCLgogICAgICAgIC8vIGlmIHRwPj0xLCB0aGUgY2xvc2VzdCBwb2ludCBvbiB0aGUgc2VnbWVudCBpcyBBLgogICAgICAgIC8vIE90aGVyd2lzZSwgdGhlIGNsb3Nlc3QgcG9pbnQgaXMgQit0cChBLUIpLgogICAgICAgIGZ1bmN0aW9uIGRpc3RGbihheCwgYXksIGJ4LCBieSkgewogICAgICAgICAgICBjb25zdCBhYnggPSBheCAtIGJ4OwogICAgICAgICAgICBjb25zdCBhYnkgPSBheSAtIGJ5OwogICAgICAgICAgICBjb25zdCBjYnggPSBjeCAtIGJ4OwogICAgICAgICAgICBjb25zdCBjYnkgPSBjeSAtIGJ5OwogICAgICAgICAgICBjb25zdCB0cCA9IChhYnggKiBjYnggKyBhYnkgKiBjYnkpIC8gKGFieCAqIGFieCArIGFieSAqIGFieSk7CiAgICAgICAgICAgIGlmICh0cCA8PSAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbDJOb3JtU3F1YXJlZChjYngsIGNieSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgaWYgKHRwID49IDEpIHsKICAgICAgICAgICAgICAgIGNvbnN0IGNheCA9IGF4IC0gY3g7CiAgICAgICAgICAgICAgICBjb25zdCBjYXkgPSBheSAtIGN5OwogICAgICAgICAgICAgICAgcmV0dXJuIGwyTm9ybVNxdWFyZWQoY2F4LCBjYXkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBsMk5vcm1TcXVhcmVkKGNieCAtIHRwICogYWJ4LCBjYnkgLSB0cCAqIGFieSk7CiAgICAgICAgfQogICAgICAgIGxldCBtaW5EaXN0ID0gbnVsbDsKICAgICAgICBsZXQgY2xvc2VzdFBhdGggPSBudWxsOwogICAgICAgIHBhdGhzLmZvckVhY2goKHApID0+IHsKICAgICAgICAgICAgY29uc3QgZGlzdCA9IGRpc3RGbihwLmNvbnRyb2xQb2ludHNbYV1bMF0sIHAuY29udHJvbFBvaW50c1thXVsxXSwgcC5jb250cm9sUG9pbnRzW2JdWzBdLCBwLmNvbnRyb2xQb2ludHNbYl1bMV0pOwogICAgICAgICAgICBpZiAoZGlzdCA+IHRocmVzaG9sZCkgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGlmIChtaW5EaXN0ID09PSBudWxsIHx8IGRpc3QgPCBtaW5EaXN0KSB7CiAgICAgICAgICAgICAgICBtaW5EaXN0ID0gZGlzdDsKICAgICAgICAgICAgICAgIGNsb3Nlc3RQYXRoID0gcDsKICAgICAgICAgICAgfQogICAgICAgIH0pOwogICAgICAgIHJldHVybiBjbG9zZXN0UGF0aDsKICAgIH0KICAgIC8vIENvbXB1dGVzIHRoZSBpbnZlcnNlIGltYWdlIChpbiB0aGUgbWF0aGVtYXRpY2FsIHNlbnNlKSBvZiB0aGUKICAgIC8vIHJlYWwtbGluZSBpbnRlcnZhbCBbYSxiXSB1bmRlciB0aGUgZ2l2ZW4gcG9pbnQgc2NhbGUgbWFwcGluZy4KICAgIC8vIFJldHVybnMgdGhlIGFycmF5IGNvbnNpc3Rpbmcgb2YgYWxsIGVsZW1lbnRzIHggc3VjaCB0aGF0IHNjYWxlKHgpCiAgICAvLyBpcyBpbiB0aGUgcmVhbC1saW5lIGludGVydmFsIFthLGJdLgogICAgZnVuY3Rpb24gcG9pbnRTY2FsZUludmVyc2VJbWFnZShzY2FsZSwgYSwgYikgewogICAgICAgIHJldHVybiBzY2FsZS5kb21haW4oKS5maWx0ZXIoKHgpID0+IHsKICAgICAgICAgICAgY29uc3QgeSA9IHNjYWxlKHgpOwogICAgICAgICAgICByZXR1cm4gYSA8PSB5ICYmIHkgPD0gYjsKICAgICAgICB9KTsKICAgIH0KICAgIC8vIENvbXB1dGVzIHRoZSBpbnZlcnNlIGltYWdlIChpbiB0aGUgbWF0aGVtYXRpY2FsIHNlbnNlKSBvZiB0aGUKICAgIC8vIHJlYWwtbGluZSBpbnRlcnZhbCBbYSxiXSB1bmRlciB0aGUgZ2l2ZW4gcXVhbnRpbGUgc2NhbGUgbWFwcGluZzsKICAgIC8vIHByZWNpc2VseToge3ggOiBzY2FsZSh4KSBpbiBbYSxiXX0KICAgIC8vIE5vdGUgdGhhdCBmb3IgYSBEMyBxdWFudGlsZSBzY2FsZSB0aGlzIHNldCBpcyBhIHJlYWwtbGluZSBoYWxmLW9wZW4KICAgIC8vIGludGVydmFsIG9mIHRoZSBmb3JtIFtjLGQpLgogICAgLy8gVGhpcyBmdW5jdGlvbiByZXR1cm5zIHRoYXQgaW50ZXJ2YWwgYXMgYSAyLWVsZW1lbnQgYXJyYXkgW2MsIGRdLgogICAgZnVuY3Rpb24gcXVhbnRpbGVTY2FsZUludmVyc2VJbWFnZShzY2FsZSwgYSwgYikgewogICAgICAgIGNvbnN0IHJhbmdlID0gc2NhbGUucmFuZ2UoKTsKICAgICAgICBjb25zdCBkb21haW5zID0gcmFuZ2UKICAgICAgICAgICAgLmZpbHRlcigoeSkgPT4gYSA8PSB5ICYmIHkgPD0gYikKICAgICAgICAgICAgLm1hcCgoeSkgPT4gewogICAgICAgICAgICBjb25zdCBkb21haW4gPSBzY2FsZS5pbnZlcnRFeHRlbnQoeSk7CiAgICAgICAgICAgIC8vIEZpbmQgdGhlIGhhbGYgb3BlbiBpbnRlcnZhbCBvZiByZWFsIG51bWJlcnMgbWFwcGluZyB0byB5LgogICAgICAgICAgICAvLyBUaGlzIGlzIHR5cGljYWxseSByZXR1cm5lZCBieSBzY2FsZS5pbnZlcnRFeHRlbnQoeSkuCiAgICAgICAgICAgIC8vIEhvd2V2ZXIsIGlmICd5JyBpcyB0aGUgbGFzdCB2YWx1ZSBpbiB0aGUgcmFuZ2UsIHRoYXQKICAgICAgICAgICAgLy8gaW50ZXJ2YWwgaGFzIHRoZSBmb3JtIFtkLCtpbmZpbml0eSksIHdoZXJlYXMgdGhlIHVwcGVyCiAgICAgICAgICAgIC8vIGJvdW5kIHJldHVybmVkIGJ5IHNjYWxlLmludmVydEV4dGVudCBpcyB0aGUgbGFyZ2VzdCBlbGVtZW50CiAgICAgICAgICAgIC8vIGluIHNjYWxlLmRvbWFpbigpLiBTaW5jZSB3ZSByZXR1cm4gYSBoYWxmLW9wZW4gaW50ZXJ2YWwsIGlmCiAgICAgICAgICAgIC8vIHdlIHVzZSB0aGF0IHZhbHVlLCB3ZSB3aWxsIGRyb3Agc2Vzc2lvbiBncm91cHMgd2hvc2UKICAgICAgICAgICAgLy8gY29sdW1uIHZhbHVlIGV4YWN0bHkgZXF1YWxzIGl0LiBTbyB3ZSB0ZXN0IGZvciB0aGlzIHNwZWNpYWwKICAgICAgICAgICAgLy8gY2FzZSBoZXJlIGFuZCBhZGp1c3QgZG9tYWluWzFdIHRvIGNvbXBlbnNhdGUuCiAgICAgICAgICAgIHJldHVybiB5ID09PSByYW5nZVtyYW5nZS5sZW5ndGggLSAxXQogICAgICAgICAgICAgICAgPyBbZG9tYWluWzBdLCBkb21haW5bMV0gKyAxXQogICAgICAgICAgICAgICAgOiBkb21haW47CiAgICAgICAgfSk7CiAgICAgICAgaWYgKGRvbWFpbnMubGVuZ3RoID09IDApIHsKICAgICAgICAgICAgcmV0dXJuIFswLCAwXTsgLy8gUmV0dXJuIGFuIGVtcHR5IGludGVydmFsIFswLDApLgogICAgICAgIH0KICAgICAgICAvLyBTaW5jZSBvdXIgc291cmNlIHNldCBpcyBhIGNvbnRpZ3VvdXMgaW50ZXJ2YWwgW2EsYl0sIHRoZSB1bmlvbiBvZgogICAgICAgIC8vIGRvbWFpbnMgaXMgYSBzaW5nbGUgaGFsZi1vcGVuIGludGVydmFsLgogICAgICAgIHJldHVybiBleHRlbnQobWVyZ2UoZG9tYWlucykpOwogICAgfQogICAgLy8gQ29tcHV0ZXMgdGhlIGludmVyc2UgaW1hZ2UgKGluIHRoZSBtYXRoZW1hdGljYWwgc2Vuc2UpIG9mIHRoZQogICAgLy8gcmVhbC1saW5lIGludGVydmFsIFthLGJdIHVuZGVyIHRoZSBnaXZlbiBjb250aW51b3VzIHNjYWxlIG1hcHBpbmc7CiAgICAvLyBwcmVjaXNlbHk6IHt4IDogc2NhbGUoeCkgaW4gW2EsYl19CiAgICAvLyBOb3RlIHRoYXQgZm9yIGEgRDMgY29udGludW91cyBzY2FsZSB0aGlzIHNldCBpcyBhIHJlYWwtbGluZSBjbG9zZWQKICAgIC8vIGludGVydmFsLiBUaGlzIGZ1bmN0aW9uIHJldHVybnMgdGhhdCBpbnRlcnZhbCBhcyBhIDItZWxlbWVudCBhcnJheS4KICAgIGZ1bmN0aW9uIGNvbnRpbnVvdXNTY2FsZUludmVyc2VJbWFnZShzY2FsZSwgYSwgYikgewogICAgICAgIC8vIEQzIGNvbnRpbnVvdXMgc2NhbGVzIGFyZSBtb25vdG9uaWMgY29udGludW91cyBmdW5jdGlvbnM7IGhlbmNlIHRvCiAgICAgICAgLy8gZ2V0IHRoZSBpbnZlcnNlIGltYWdlIGludGVydmFsIHdlIGp1c3QgbmVlZCB0byBpbnZlcnQgdGhlCiAgICAgICAgLy8gZW5kLXBvaW50cyBvZiB0aGUgc291cmNlIGludGVydmFsLiBXZSBzb3J0IHRoZSByZXN1bHRpbmcgZW5kLXBvaW50cywKICAgICAgICAvLyB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgdGhlIHNjYWxlIGlzIGRlY3JlYXNpbmcuCiAgICAgICAgcmV0dXJuIFtzY2FsZS5pbnZlcnQoYSksIHNjYWxlLmludmVydChiKV0uc29ydCgoeCwgeSkgPT4geCAtIHkpOwogICAgfQogICAgLy8gQ3JlYXRlcyB0aGUgZDMtc2NhbGUgdG8gdXNlIGZvciB0aGUgYXhpcyB3aXRoIGdpdmVuIGRvbWFpbiB2YWx1ZXMKICAgIC8vIGFuZCBoZWlnaHQgYW5kIHNjYWxlLXR5cGUuIFRoaXMgZnVuY3Rpb24gbWF5IHBlcm11dGUgdGhlIGdpdmVuCiAgICAvLyAnZG9tYWluVmFsdWVzJyBhcnJheS4KICAgIGZ1bmN0aW9uIGNyZWF0ZUF4aXNTY2FsZShkb21haW5WYWx1ZXMsIGF4aXNIZWlnaHQsIHNjYWxlVHlwZSkgewogICAgICAgIGZ1bmN0aW9uIGNvbXB1dGVOdW1lcmljRXh0ZW50KCkgewogICAgICAgICAgICBpZiAoZG9tYWluVmFsdWVzLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgLy8gSWYgdGhlcmUgYXJlIG5vIHZhbHVlcywgdGhlcmUgd29uJ3QgYmUgYW55IHNlc3Npb24gZ3JvdXBzLgogICAgICAgICAgICAgICAgLy8gV2UgY2hvb3NlIGFuIGFyYml0cmFyeSBudW1lcmljIGRvbWFpbiB0aGF0IGRvZXNuJ3QgY29udGFpbiAwCiAgICAgICAgICAgICAgICAvLyAodG8gYWxsb3cgYSBsb2cgc2NhbGUpLgogICAgICAgICAgICAgICAgcmV0dXJuIFsxLCAyXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBbbWluLCBtYXhdID0gZXh0ZW50KGRvbWFpblZhbHVlcyk7CiAgICAgICAgICAgIGlmIChtaW4gIT09IG1heCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFttaW4sIG1heF07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gV2Ugc2hpZnQgdGhlIG1pbiBhbmQgbWF4IG9mIHRoZSBleHRlbnQgaGVyZSBzaW5jZQogICAgICAgICAgICAvLyBkMy5zY2FsZUxpbmVhcigpIGFuZCBkMy5zY2FsZUxvZygpIGJvdGggZXhwZWN0IHRoZSBkb21haW4KICAgICAgICAgICAgLy8gdG8gYmUgYW4gaW50ZXJ2YWwgd2l0aCBtb3JlIHRoYW4gb25lIHBvaW50LiBTaW5jZSBpbiB0aGlzIGNhc2UKICAgICAgICAgICAgLy8gYWxsIHNlc3Npb24gZ3JvdXBzIHdvdWxkIHBhc3MgdGhyb3VnaCBhIHNpbmdsZSBwb2ludCBpbiB0aGUgYXhpcywKICAgICAgICAgICAgLy8gdGhlIGF4aXMgcmVzb2x1dGlvbiBkb2Vzbid0IG1hdHRlciBtdWNoIHNvIHRoZSBhbW91bnQgd2Ugc2hpZnQgYnkKICAgICAgICAgICAgLy8gZG9lc24ndCBtYXR0ZXIgbXVjaCBhcyB3ZWxsLiBTaW5jZSBmb3IgbG9nIHNjYWxlcyB3ZSBkb24ndCBhbGxvdwogICAgICAgICAgICAvLyB0aGUgZG9tYWluIHRvIGNvbnRhaW4gMCwgd2UgbmVlZCB0byBiZSBjYXJlZnVsIG5vdCB0byBtYWtlIHRoZQogICAgICAgICAgICAvLyBkb21haW4gY29udGFpbiAwIGlmIGl0IGhhZG4ndCBiZWZvcmUuCiAgICAgICAgICAgIGlmIChtaW4gPiAwKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gW21pbiAqIDAuNSwgbWluICogMS41XTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAobWluIDwgMCkgewogICAgICAgICAgICAgICAgcmV0dXJuIFttaW4gKiAxLjUsIG1pbiAqIDAuNV07CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIFstMSwgMV07CiAgICAgICAgfQogICAgICAgIGlmIChzY2FsZVR5cGUgPT09ICdMSU5FQVInKSB7CiAgICAgICAgICAgIHJldHVybiBsaW5lYXIkMigpCiAgICAgICAgICAgICAgICAuZG9tYWluKGNvbXB1dGVOdW1lcmljRXh0ZW50KCkpCiAgICAgICAgICAgICAgICAucmFuZ2UoW2F4aXNIZWlnaHQsIDBdKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoc2NhbGVUeXBlID09PSAnTE9HJykgewogICAgICAgICAgICBjb25zdCBleHRlbnQgPSBjb21wdXRlTnVtZXJpY0V4dGVudCgpOwogICAgICAgICAgICBpZiAoZXh0ZW50WzBdIDw9IDAgJiYgZXh0ZW50WzFdID49IDApIHsKICAgICAgICAgICAgICAgIC8vIFdlIGNhbid0IGhhdmUgYSBsb2cgc2NhbGUgZm9yIGRhdGEgd2hvc2UgZXh0ZW50IGNvbnRhaW5zIDAuCiAgICAgICAgICAgICAgICAvLyBVc2UgYSBsaW5lYXIgc2NhbGUgaW5zdGVhZC4KICAgICAgICAgICAgICAgIC8vIFRPRE8oZXJleik6IENyZWF0ZSBhIHN5bWxvZyBzY2FsZSBzaW1pbGFyIHRvIE1hdHBsb3RsaWIncwogICAgICAgICAgICAgICAgLy8gc3ltbG9nLiBTZWUgYWxzbyBkMyBpc3N1ZSBoZXJlOgogICAgICAgICAgICAgICAgLy8gaHR0cHM6Ly9naXRodWIuY29tL2QzL2QzLXNjYWxlL2lzc3Vlcy8xMDUKICAgICAgICAgICAgICAgIC8vIGFuZCBiLzExMTc1NTU0MAogICAgICAgICAgICAgICAgcmV0dXJuIGNyZWF0ZUF4aXNTY2FsZShkb21haW5WYWx1ZXMsIGF4aXNIZWlnaHQsICdMSU5FQVInKTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gbG9nJDEoKQogICAgICAgICAgICAgICAgLmRvbWFpbihleHRlbnQpCiAgICAgICAgICAgICAgICAucmFuZ2UoW2F4aXNIZWlnaHQsIDBdKTsKICAgICAgICB9CiAgICAgICAgZWxzZSBpZiAoc2NhbGVUeXBlID09PSAnUVVBTlRJTEUnKSB7CiAgICAgICAgICAgIC8vIENvbXB1dGUga051bVF1YW50aWxlcyBxdWFudGlsZXMuCiAgICAgICAgICAgIGNvbnN0IGtOdW1RdWFudGlsZXMgPSAyMDsKICAgICAgICAgICAgLy8gQ29tcHV0ZSB0aGUgc2NhbGUncyByYW5nZSB0byBiZSB0aGUgYXJyYXk6CiAgICAgICAgICAgIC8vIFtheGlzSGVpZ2h0LAogICAgICAgICAgICAvLyAgYXhpc0hlaWdodC0xKmF4aXNIZWlnaHQvKGtOdW1RdWFudGlsZXMtMSksCiAgICAgICAgICAgIC8vICBheGlzSGVpZ2h0LTIqYXhpc0hlaWdodC8oa051bVF1YW50aWxlcy0xKSwgLi4uLAogICAgICAgICAgICAvLyAgMF0uCiAgICAgICAgICAgIC8vIFVuZm9ydHVuYXRsZXksCiAgICAgICAgICAgIC8vIGQzLnJhbmdlKGF4aXNIZWlnaHQsIC1heGlzSGVpZ2h0LyhrTnVtUXVhbnRpbGVzLTEpLAogICAgICAgICAgICAvLyAgICAgICAgICAtYXhpc0hlaWdodC8oa051bVF1YW50aWxlcy0xKSkKICAgICAgICAgICAgLy8gaGFzIG51bWVyaWNhbCBpc3N1ZXMgYW5kIG1heSBwcm9kdWNlIGFuIGV4dHJhIG1lbWJlciwgc28gd2UgdXNlIGEKICAgICAgICAgICAgLy8gZGlmZmVyZW50IHByb2NlZHVyZToKICAgICAgICAgICAgY29uc3Qgc2NhbGVSYW5nZSA9IHNlcXVlbmNlKGtOdW1RdWFudGlsZXMpCiAgICAgICAgICAgICAgICAubWFwKChpKSA9PiBheGlzSGVpZ2h0IC0gKGkgKiBheGlzSGVpZ2h0KSAvIChrTnVtUXVhbnRpbGVzIC0gMSkpOwogICAgICAgICAgICBpZiAoZG9tYWluVmFsdWVzLmxlbmd0aCA9PT0gMCkgewogICAgICAgICAgICAgICAgLy8gTm8gc2Vzc2lvbiBncm91cHMgaW4gdGhpcyBjYXNlLiBXZSB1c2UgYSBkdW1teSB2YWx1ZSBzaW5jZQogICAgICAgICAgICAgICAgLy8gZDMuc2NhbGVRdWFudGlsZSgpIHJlcXVpcmVzIGEgbm9uLWVtcHR5IGRvbWFpbi4KICAgICAgICAgICAgICAgIGRvbWFpblZhbHVlcyA9IFsxXTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gcXVhbnRpbGUoKS5kb21haW4obG9kYXNoLnVuaXEoZG9tYWluVmFsdWVzKSkucmFuZ2Uoc2NhbGVSYW5nZSk7CiAgICAgICAgfQogICAgICAgIGVsc2UgaWYgKHNjYWxlVHlwZSA9PT0gJ05PTl9OVU1FUklDJykgewogICAgICAgICAgICByZXR1cm4gcG9pbnQkMSgpCiAgICAgICAgICAgICAgICAuZG9tYWluKAogICAgICAgICAgICAvLyBXZSBzb3J0IHRoZSBkb21haW4gdmFsdWVzIHRvIG1ha2UgdGhlIG9yZGVyCiAgICAgICAgICAgIC8vIHN0YWJsZSBhY3Jvc3MgJ0xpc3RTZXNzaW9uR3JvdXBzJyBSUENzCiAgICAgICAgICAgIGxvZGFzaC51bmlxKGRvbWFpblZhbHVlcy5zb3J0KCkpKQogICAgICAgICAgICAgICAgLnJhbmdlKFtheGlzSGVpZ2h0LCAwXSkKICAgICAgICAgICAgICAgIC5wYWRkaW5nKDAuMSk7CiAgICAgICAgfQogICAgICAgIGVsc2UKICAgICAgICAgICAgdGhyb3cgUmFuZ2VFcnJvcignVW5rbm93biBzY2FsZTogJyArIHNjYWxlVHlwZSk7CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTkgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgJ0xpY2Vuc2UnKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAnQVMgSVMnIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICB2YXIgU2NhbGVUeXBlOwogICAgKGZ1bmN0aW9uIChTY2FsZVR5cGUpIHsKICAgICAgICBTY2FsZVR5cGVbIkxJTkVBUiJdID0gIkxJTkVBUiI7CiAgICAgICAgU2NhbGVUeXBlWyJMT0ciXSA9ICJMT0ciOwogICAgICAgIFNjYWxlVHlwZVsiUVVBTlRJTEUiXSA9ICJRVUFOVElMRSI7CiAgICAgICAgU2NhbGVUeXBlWyJOT05fTlVNRVJJQyJdID0gIk5PTl9OVU1FUklDIjsKICAgIH0pKFNjYWxlVHlwZSB8fCAoU2NhbGVUeXBlID0ge30pKTsKICAgIC8qKgogICAgICogQW4gQWx3YXlzUGFzc2luZ0JydXNoRmlsdGVyIHJldHVybnMgJ3RydWUnIGZvciBhbnkgdmFsdWUuIEl0IGlzIHVzZWQKICAgICAqIHRvIHJlcHJlc2VudCB0aGUgY2FzZSB3aGVuIGFuIEF4aXMgZG9lcyBub3QgaGF2ZSBhbiBhY3RpdmUgYnJ1c2ggc2VsZWN0aW9uLgogICAgICovCiAgICBjbGFzcyBBbHdheXNQYXNzaW5nQnJ1c2hGaWx0ZXIgewogICAgICAgIGlzUGFzc2luZyh2YWx1ZSkgewogICAgICAgICAgICByZXR1cm4gdHJ1ZTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIEFuIEludGVydmFsQnJ1c2hGaWx0ZXIgcmV0dXJucyAndHJ1ZScgaWYgdGhlIGdpdmVuIChudW1lcmljKSB2YWx1ZSBsaWVzCiAgICAgKiBpbiBhIGdpdmVuIGludGVydmFsIHNwZWNpZmllZCBvbiBjb25zdHJ1Y3Rpb24gLiBJdCdzIHVzZWQgdG8gcmVwcmVzZW50CiAgICAgKiBicnVzaCBmaWx0ZXJzIGZvciBBeGlzIHdpdGggbGluZWFyLCBsb2dhcml0aG1pYyBvciBxdWFudGlsZSBzY2FsZXMuCiAgICAgKi8KICAgIGNsYXNzIEludGVydmFsQnJ1c2hGaWx0ZXIgewogICAgICAgIC8qKiBDb25zdHJ1Y3RzIHRoZSBmaWx0ZXIuIFRoZSBpbnRlcnZhbCB1c2VkIGlzIGRlZmluZWQgYnkgbG93ZXIsIGFuZCB1cHBlci4KICAgICAgICAgKiBJZiBsb3dlck9wZW4gKHJlc3AuIHVwcGVyT3BlbikgaXMgdHJ1ZSwgdGhlIGludGVydmFsIHdpbGwgYmUgb3BlbiBpbgogICAgICAgICAqIGl0cyBsb3dlciAocmVzcC4gdXBwZXIpIGVuZCwgb3RoZXJ3aXNlIGl0IHdpbGwgYmUgY2xvc2VkLgogICAgICAgICAqLwogICAgICAgIGNvbnN0cnVjdG9yKGxvd2VyLCB1cHBlciwgbG93ZXJPcGVuLCB1cHBlck9wZW4pIHsKICAgICAgICAgICAgdGhpcy5fbG93ZXIgPSBsb3dlcjsKICAgICAgICAgICAgdGhpcy5fdXBwZXIgPSB1cHBlcjsKICAgICAgICAgICAgdGhpcy5fbG93ZXJPcGVuID0gbG93ZXJPcGVuOwogICAgICAgICAgICB0aGlzLl91cHBlck9wZW4gPSB1cHBlck9wZW47CiAgICAgICAgfQogICAgICAgIGlzUGFzc2luZyh2YWx1ZSkgewogICAgICAgICAgICBjb25zdCBudW1WYWx1ZSA9IHZhbHVlOwogICAgICAgICAgICByZXR1cm4gKHRoaXMuX2JlZm9yZSh0aGlzLl9sb3dlciwgbnVtVmFsdWUsICF0aGlzLl9sb3dlck9wZW4pICYmCiAgICAgICAgICAgICAgICB0aGlzLl9iZWZvcmUobnVtVmFsdWUsIHRoaXMuX3VwcGVyLCAhdGhpcy5fdXBwZXJPcGVuKSk7CiAgICAgICAgfQogICAgICAgIF9iZWZvcmUoYSwgYiwgaW5jbHVzaXZlKSB7CiAgICAgICAgICAgIGlmIChpbmNsdXNpdmUpIHsKICAgICAgICAgICAgICAgIHJldHVybiBhIDw9IGI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIGEgPCBiOwogICAgICAgIH0KICAgIH0KICAgIC8qKgogICAgICogQSBTZXRCcnVzaEZpbHRlciByZXR1cm5zICd0cnVlJyBpZiB0aGUgdmFsdWUgaXMgaW4gYSBnaXZlbiBzZXQgc3BlY2lmaWVkCiAgICAgKiBpbiBjb25zdHJ1Y3Rpb24uCiAgICAgKi8KICAgIGNsYXNzIFNldEJydXNoRmlsdGVyIHsKICAgICAgICBjb25zdHJ1Y3Rvcihkb21haW5TZXQpIHsKICAgICAgICAgICAgdGhpcy5fZG9tYWluU2V0ID0gZG9tYWluU2V0OwogICAgICAgIH0KICAgICAgICBpc1Bhc3NpbmcodmFsdWUpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2RvbWFpblNldC5maW5kSW5kZXgoKGVsZW1lbnQpID0+IGVsZW1lbnQgPT09IHZhbHVlKSAhPT0gLTE7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBSZXByZXNlbnRzIGEgc2luZ2xlIEF4aXMuIEFuIGF4aXMgZG9lcyBub3Qga25vdyBpdHMgaG9yaXpvbnRhbCBsb2NhdGlvbiBpbgogICAgICogdGhlIFNWRzsgaW5zdGVhZCB0aGUgYXhlcyBsb2NhdGlvbnMgYXJlIG1hbmFnZWQgYnkgdGhlIEF4ZXNDb2xsZWN0aW9uIGNsYXNzLgogICAgICogQW4gYXhpcyByZXByZXNlbnRzIGEgc2luZ2xlIGNvbHVtbiAobWV0cmljIG9yIGhhcGFyYW0pLiBJdCBzdG9yZXMgYSBzY2FsZQogICAgICogdHlwZSBhbmQgYSBEMyBzY2FsZSB0aGF0IG1hcHMgdmFsdWVzIGluIHRoZSBheGlzIGRvbWFpbiAoY29sdW1uIHZhbHVlcykKICAgICAqIHRvIHktY29vcmRpbmF0ZXMgaW4gdGhlIFNWRy4gQWRkaXRpb25hbGx5LCBhbiBheGlzIHN0b3JlcyBhCiAgICAgKiBEMy1icnVzaC1zZWxlY3Rpb24gd2hpY2ggaXMgYSAyLWVsZW1lbnQgbnVtZXJpYyBhcnJheSBvZiB0aGUgZm9ybQogICAgICogW2xvd2VyLCB1cHBlcl0gY29udGFpbmluZyB0aGUgdXBwZXIgYW5kIGxvd2VyIHktY29vcmRpbmF0ZXMgb2YgdGhlIGN1cnJlbnQKICAgICAqIGJydXNoIHNlbGVjdGlvbi4gSWYgbm8gYnJ1c2ggc2VsZWN0aW9uIGV4aXN0cywgdGhlIGJydXNoIHNlbGVjdGlvbiBzdG9yZWQgaXMKICAgICAqIG51bGwuCiAgICAgKiBGaW5hbGx5LCBhbiBheGlzIGNhbiBiZSB2aXNpYmxlIChkaXNwbGF5ZWQpIG9yIGludmlzaWJsZSAod2hpY2ggd2lsbCBiZQogICAgICogc2V0IGJhc2VkIG9uIHRoZSB1c2VyJ3Mgc2V0dGluZ3MgZm9yIHRoZSBjb3JyZXNwb25kaW5nIGNvbHVtbikuIEFuIGludmlzaWJsZQogICAgICogYXhpcyBuZWVkIG5vdCBoYXZlIGl0cyBzY2FsZSBvciBzY2FsZS10eXBlIHBvcHVsYXRlZC4KICAgICAqLwogICAgY2xhc3MgQXhpcyB7CiAgICAgICAgLyoqCiAgICAgICAgICogQ29uc3RydWN0cyBhbiBheGlzIHJlcHJlc2VudGluZyB0aGUgY29sdW1uIGluZGV4ZWQgYnkgJ2NvbEluZGV4JyB3aXRoCiAgICAgICAgICogcmVzcGVjdCB0byAnc2NoZW1hJy4gTmVlZHMgYW4gSW50ZXJhY3Rpb25NYW5hZ2VyIGluc3RhbmNlIHNvIHRoYXQgaXQgY2FuCiAgICAgICAgICogY2FsbCBpdHMgZXZlbnQgaGFuZGxlcnMgdXBvbiByZWNlaXZpbmcgZXZlbnRzIGZyb20gdGhlIERPTS4KICAgICAgICAgKi8KICAgICAgICBjb25zdHJ1Y3RvcihzdmdQcm9wcywgc2NoZW1hLCBpbnRlcmFjdGlvbk1hbmFnZXIsIGNvbEluZGV4KSB7CiAgICAgICAgICAgIHRoaXMuX3N2Z1Byb3BzID0gc3ZnUHJvcHM7CiAgICAgICAgICAgIHRoaXMuX3NjaGVtYSA9IHNjaGVtYTsKICAgICAgICAgICAgdGhpcy5faW50ZXJhY3Rpb25NYW5hZ2VyID0gaW50ZXJhY3Rpb25NYW5hZ2VyOwogICAgICAgICAgICB0aGlzLl9jb2xJbmRleCA9IGNvbEluZGV4OwogICAgICAgICAgICB0aGlzLl9pc0Rpc3BsYXllZCA9IGZhbHNlOwogICAgICAgICAgICB0aGlzLl95U2NhbGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLl9zY2FsZVR5cGUgPSBudWxsOwogICAgICAgICAgICB0aGlzLnNldEJydXNoU2VsZWN0aW9uKG51bGwpOwogICAgICAgIH0KICAgICAgICBjb2xJbmRleCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2NvbEluZGV4OwogICAgICAgIH0KICAgICAgICB5U2NhbGUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl95U2NhbGU7CiAgICAgICAgfQogICAgICAgIHNjYWxlVHlwZSgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NjYWxlVHlwZTsKICAgICAgICB9CiAgICAgICAgYnJ1c2hTZWxlY3Rpb24oKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9icnVzaFNlbGVjdGlvbjsKICAgICAgICB9CiAgICAgICAgaXNEaXNwbGF5ZWQoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9pc0Rpc3BsYXllZDsKICAgICAgICB9CiAgICAgICAgc2V0QnJ1c2hTZWxlY3Rpb24oYnJ1c2hTZWxlY3Rpb24pIHsKICAgICAgICAgICAgdGhpcy5fYnJ1c2hTZWxlY3Rpb24gPSBicnVzaFNlbGVjdGlvbjsKICAgICAgICAgICAgdGhpcy5fYnJ1c2hGaWx0ZXIgPSB0aGlzLl9idWlsZEJydXNoRmlsdGVyKHRoaXMuYnJ1c2hTZWxlY3Rpb24oKSwgdGhpcy5zY2FsZVR5cGUoKSwgdGhpcy55U2NhbGUoKSk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFNldHMgdGhlIGRvbWFpbiBhbmQgc2NhbGUgdHlwZSBmb3IgdGhlIGF4aXMuIFRoZSBjdXJyZW50IGJydXNoIHNlbGVjdGlvbgogICAgICAgICAqIGlzIHByZXNlcnZlZC4KICAgICAgICAgKi8KICAgICAgICBzZXREb21haW5BbmRTY2FsZShkb21haW5WYWx1ZXMsIHNjYWxlVHlwZSkgewogICAgICAgICAgICB0aGlzLl9zY2FsZVR5cGUgPSBzY2FsZVR5cGU7CiAgICAgICAgICAgIHRoaXMuX3lTY2FsZSA9IGNyZWF0ZUF4aXNTY2FsZSgKICAgICAgICAgICAgLy8gUGFzcyBhIGNvcHkgc2luY2UgY3JlYXRlQXhpc1NjYWxlIG1heSBwZXJtdXRlIHRoZSBkb21haW5WYWx1ZXMgYXJyYXkuCiAgICAgICAgICAgIGRvbWFpblZhbHVlcy5zbGljZSgpLCB0aGlzLl9zdmdQcm9wcy5oZWlnaHQsIHRoaXMuc2NhbGVUeXBlKCkpOwogICAgICAgICAgICAvLyBUT0RPKGVyZXopOiBUcnkgdG8gbW9kaWZ5IHRoZSBicnVzaCBzZWxlY3Rpb24gc28gdGhhdCBpdCBzZWxlY3RzCiAgICAgICAgICAgIC8vIHRoZSBzYW1lIHN1YnNldCBvZiB0aGUgYXhpcyBkb21haW4gd2hpY2ggd2FzIHNlbGVjdGVkIGJlZm9yZQogICAgICAgICAgICAvLyB0aGlzIG1ldGhvZCB3YXMgY2FsbGVkLgogICAgICAgICAgICAvLyBUaGlzIGNhbid0IGFsd2F5cyBiZSBkb25lIChlLmcuIGlmIHdlIHN3aXRjaGVkIGZyb20gYSBsaW5lYXIgdG8gYQogICAgICAgICAgICAvLyBxdWFudGlsZSBzY2FsZSwgb3IgaWYgdGhlIGRvbWFpbiB2YWx1ZXMgY2hhbmdlZCBzaWduaWZpY2FudGx5KSBidXQgaW4KICAgICAgICAgICAgLy8gdGhlIGNhc2VzIHdoZW4gaXQgaXMgcG9zc2libGUsIGl0IHdpbGwgYmUgbW9yZSBjb252ZW5pZW50IHRvIHRoZSB1c2VyLgogICAgICAgICAgICAvLyBDdXJyZW50bHksIHdlIGtlZXAgdGhlIHNhbWUgYnJ1c2ggc2VsZWN0aW9uIGFuZCByZWNhbGN1bGF0ZSB0aGUgZmlsdGVyLgogICAgICAgICAgICAvLyBOb3RlIHRoYXQgdGhpcyBmdW5jdGlvbiB3aWxsIGJlIGNhbGxlZCBldmVyeSB0aW1lIGRhdGEgaXMgcmVsb2FkZWQKICAgICAgICAgICAgLy8gKGUuZy4gZXZlcnkgMzAgc2Vjb25kcyBieSBkZWZhdWx0IGluIFRlbnNvcmJvYXJkKSwgc28gd2UgaGF2ZSB0byBtYWtlCiAgICAgICAgICAgIC8vIHN1cmUgbm90IHRvIGNoYW5nZSB0aGUgc2VsZWN0aW9uIGlmIHRoZSBkYXRhIGhhc24ndCBjaGFuZ2VkLCBhcyB0aGF0CiAgICAgICAgICAgIC8vIHdvdWxkIGJlIHZlcnkgYW5ub3lpbmcgdG8gdGhlIGVuZCB1c2VyLgogICAgICAgICAgICB0aGlzLl9icnVzaEZpbHRlciA9IHRoaXMuX2J1aWxkQnJ1c2hGaWx0ZXIodGhpcy5icnVzaFNlbGVjdGlvbigpLCB0aGlzLnNjYWxlVHlwZSgpLCB0aGlzLnlTY2FsZSgpKTsKICAgICAgICB9CiAgICAgICAgYnJ1c2hGaWx0ZXIoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9icnVzaEZpbHRlcjsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUmVuZGVycyB0aGUgYXhpcyBhcyBjaGlsZCBlbGVtZW50cyBvZiAnYXhpc1BhcmVudCcuIFJlbW92ZXMgYW55IHByZWV4aXN0aW5nCiAgICAgICAgICogY2hpbGRyZW4gb2YgYXhpc1BhcmVudC4gJ2F4aXNQYXJlbnQnIGlzIGV4cGVjdGVkIHRvIGJlIGEgPGc+IGVsZW1lbnQuCiAgICAgICAgICovCiAgICAgICAgdXBkYXRlRE9NKGF4aXNQYXJlbnQgLyogSFRNTEVsZW1lbnQgKi8pIHsKICAgICAgICAgICAgbGV0IGQzQXhpcyA9IGF4aXNMZWZ0KHRoaXMueVNjYWxlKCkpOwogICAgICAgICAgICBpZiAodGhpcy5zY2FsZVR5cGUoKSA9PT0gU2NhbGVUeXBlLlFVQU5USUxFKSB7CiAgICAgICAgICAgICAgICAvLyBUaGUgZGVmYXVsdCB0aWNrVmFsdWVzIG9mIGEgcXVhbnRpbGUgc2NhbGUgaXMganVzdCB0aGUKICAgICAgICAgICAgICAgIC8vIHNjYWxlIGRvbWFpbiwgd2hpY2ggcHJvZHVjZXMgb3ZlcmxhcHBpbmcgbGFiZWxzIGlmIHRoZQogICAgICAgICAgICAgICAgLy8gbnVtYmVyIG9mIGVsZW1lbnRzIGluIHRoZSBkb21haW4gaXMgZ3JlYXRlciB0aGFuIHRoZQogICAgICAgICAgICAgICAgLy8gbnVtYmVyIG9mIHF1YW50aWxlcyAoc2luY2UgdGhlbiB0aGUgc2NhbGUgbWFwcyBtb3JlIHRoYW4KICAgICAgICAgICAgICAgIC8vIG9uZSBkb21haW4gdmFsdWUgdG8gdGhlIHNhbWUgcXVhbnRpbGUpLgogICAgICAgICAgICAgICAgZDNBeGlzID0gZDNBeGlzCiAgICAgICAgICAgICAgICAgICAgLnRpY2tWYWx1ZXModGhpcy55U2NhbGUoKS5xdWFudGlsZXMoKSkKICAgICAgICAgICAgICAgICAgICAudGlja0Zvcm1hdChmb3JtYXQoJy0uNmcnKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3QgYXhpc1BhcmVudFNlbCA9IHNlbGVjdChheGlzUGFyZW50KTsKICAgICAgICAgICAgYXhpc1BhcmVudFNlbC5zZWxlY3RBbGwoJ2cnKS5yZW1vdmUoKTsKICAgICAgICAgICAgYXhpc1BhcmVudFNlbAogICAgICAgICAgICAgICAgLmFwcGVuZCgnZycpCiAgICAgICAgICAgICAgICAuY2xhc3NlZCgnYXhpcycsIHRydWUpCiAgICAgICAgICAgICAgICAuY2FsbChkM0F4aXMpCiAgICAgICAgICAgICAgICAvLyBBZGQgYXhpcyB0aXRsZS4KICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3RleHQnKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2F4aXMtdGl0bGUnLCB0cnVlKQogICAgICAgICAgICAgICAgLnN0eWxlKCdjdXJzb3InLCAnbW92ZScpCiAgICAgICAgICAgICAgICAuc3R5bGUoJ3RleHQtYW5jaG9yJywgJ21pZGRsZScpCiAgICAgICAgICAgICAgICAuYXR0cigneScsIC05KQogICAgICAgICAgICAgICAgLnRleHQoKGNvbEluZGV4KSA9PiBzY2hlbWFDb2x1bW5OYW1lKHRoaXMuX3NjaGVtYSwgY29sSW5kZXgpKTsKICAgICAgICAgICAgLy8gQWRkIGRyYWdnaW5nIGV2ZW50IGhhbmRsZXJzLgogICAgICAgICAgICBheGlzUGFyZW50U2VsLmNhbGwoZHJhZygpCiAgICAgICAgICAgICAgICAub24oJ3N0YXJ0JywgKCkgPT4gewogICAgICAgICAgICAgICAgLy8gV2Ugc2V0IGFuIGF0dHJpYnV0ZSBvbiB0aGUgYXhpcyB0aGF0IHNpZ25hbHMKICAgICAgICAgICAgICAgIC8vIHRoYXQgaXQgaXMgYmVpbmcgZHJhZ2dlZC4gVGhpcyBhbGxvd3MKICAgICAgICAgICAgICAgIC8vIGludGVncmF0aW9uIHRlc3RzIHRvIGtub3cgd2hlbiBkcmFnZ2luZyBpcyBkb25lLgogICAgICAgICAgICAgICAgYXhpc1BhcmVudC5zZXRBdHRyaWJ1dGUoJ2lzLWRyYWdnaW5nJywgJycpOwogICAgICAgICAgICAgICAgdGhpcy5faW50ZXJhY3Rpb25NYW5hZ2VyLm9uRHJhZ1N0YXJ0KHRoaXMuY29sSW5kZXgoKSk7CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAub24oJ2RyYWcnLCAoKSA9PiB0aGlzLl9pbnRlcmFjdGlvbk1hbmFnZXIub25EcmFnKGV2ZW50LngpKQogICAgICAgICAgICAgICAgLm9uKCdlbmQnLCAoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9pbnRlcmFjdGlvbk1hbmFnZXIub25EcmFnRW5kKCk7CiAgICAgICAgICAgICAgICBheGlzUGFyZW50LnJlbW92ZUF0dHJpYnV0ZSgnaXMtZHJhZ2dpbmcnKTsKICAgICAgICAgICAgfSkpOwogICAgICAgICAgICAvLyBBZGQgdGhlIGJydXNoLgogICAgICAgICAgICBjb25zdCBkM0JydXNoID0gYnJ1c2hZKCkKICAgICAgICAgICAgICAgIC5leHRlbnQoWwogICAgICAgICAgICAgICAgWy04LCAwXSwKICAgICAgICAgICAgICAgIFs4LCB0aGlzLl9zdmdQcm9wcy5oZWlnaHQgKyAxXSwKICAgICAgICAgICAgXSkKICAgICAgICAgICAgICAgIC8qIERlZmluZSB0aGUgYnJ1c2ggZXZlbnQgaGFuZGxlcnMuIEQzIHdpbGwgY2FsbCB0aGVzZSBib3RoIHdoZW4KICAgICAgICAgICAgICAgICAgICAgICB0aGUgdXNlciBtb3ZlcyB0aGUgYnJ1c2ggc2VsZWN0aW9uIGFuZCB3aGVuIHdlIGNoYW5nZSB0aGUgYnJ1c2gKICAgICAgICAgICAgICAgICAgICAgICBzZWxlY3Rpb24gcHJvZ3JhbW1hdGljYWxseSB1c2luZyBkM0JydXNoLm1vdmUoKS4gV2UnZCBsaWtlIHRvCiAgICAgICAgICAgICAgICAgICAgICAgYXZvaWQgY2FsbGluZyB0aGUgaW50ZXJhY3Rpb25NYW5hZ2VyIGluIHRoZSBsYXR0ZXIgY2FzZTsgdGh1cywKICAgICAgICAgICAgICAgICAgICAgICB3ZSBjYWxsIF9pc0ludGVyYWN0aXZlRDNFdmVudCgpIHRvIGZpbmQgb3V0IGlmIHRoZSBldmVudCB3YXMgZmlyZWQKICAgICAgICAgICAgICAgICAgICAgICBkdWUgdG8gYSBwcm9ncmFtbWV0aWMgY2hhbmdlIG9mIHRoZSBicnVzaCBzZWxlY3Rpb24gLCBhbmQgaWYgc28sCiAgICAgICAgICAgICAgICAgICAgICAgaWdub3JlIHRoZSBldmVudC4gKi8KICAgICAgICAgICAgICAgIC5vbignc3RhcnQnLCAoKSA9PiB7CiAgICAgICAgICAgICAgICBpZiAoIV9pc0ludGVyYWN0aXZlRDNFdmVudChldmVudCkpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICAvLyBXZSBzZXQgdGhlICdpcy1icnVzaGluZycgYXR0cmlidXRlIG9uIHRoZSBjb250YWluaW5nCiAgICAgICAgICAgICAgICAvLyAnYXhpcy1wYXJlbnQnLWNsYXNzZWQgPGc+IGVsZW1lbnQgdG8gbm90aWZ5IGludGVncmF0aW9uIHRlc3RzCiAgICAgICAgICAgICAgICAvLyB0aGF0IHRoZSBheGlzIGlzIGJ1c3kgYnJ1c2hpbmcuCiAgICAgICAgICAgICAgICBheGlzUGFyZW50LnNldEF0dHJpYnV0ZSgnaXMtYnJ1c2hpbmcnLCAnJyk7CiAgICAgICAgICAgICAgICB0aGlzLl9pbnRlcmFjdGlvbk1hbmFnZXIub25CcnVzaENoYW5nZWQodGhpcy5jb2xJbmRleCgpLCBldmVudC5zZWxlY3Rpb24pOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLm9uKCdicnVzaCcsICgpID0+IHsKICAgICAgICAgICAgICAgIGlmICghX2lzSW50ZXJhY3RpdmVEM0V2ZW50KGV2ZW50KSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2ludGVyYWN0aW9uTWFuYWdlci5vbkJydXNoQ2hhbmdlZCh0aGlzLmNvbEluZGV4KCksIGV2ZW50LnNlbGVjdGlvbik7CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAub24oJ2VuZCcsICgpID0+IHsKICAgICAgICAgICAgICAgIGlmICghX2lzSW50ZXJhY3RpdmVEM0V2ZW50KGV2ZW50KSkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHRoaXMuX2ludGVyYWN0aW9uTWFuYWdlci5vbkJydXNoQ2hhbmdlZCh0aGlzLmNvbEluZGV4KCksIGV2ZW50LnNlbGVjdGlvbik7CiAgICAgICAgICAgICAgICBheGlzUGFyZW50LnJlbW92ZUF0dHJpYnV0ZSgnaXMtYnJ1c2hpbmcnKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIGNvbnN0IGJydXNoRyA9IHNlbGVjdChheGlzUGFyZW50KQogICAgICAgICAgICAgICAgLmFwcGVuZCgnZycpCiAgICAgICAgICAgICAgICAuY2xhc3NlZCgnYnJ1c2gnLCB0cnVlKTsKICAgICAgICAgICAgYnJ1c2hHLmNhbGwoZDNCcnVzaCk7CiAgICAgICAgICAgIC8vIFNldCB0aGUgYnJ1c2ggc2VsZWN0aW9uIHByb2dyYW1tYXRpY2FsbHkuCiAgICAgICAgICAgIC8vIFdlIG5lZWQgdG8gY2FzdCBicnVzaEcgdG8gJ2FueScgaGVyZSBzaW5jZSBUeXBlU2NyaXB0IGRvZXNuJ3QgcmVhbGl6ZQogICAgICAgICAgICAvLyB0aGUgYnJ1c2hHIGlzIGEgPGc+IHNlbGVjdGlvbiBhbmQgY29tcGxhaW5zLgogICAgICAgICAgICBkM0JydXNoLm1vdmUoYnJ1c2hHLCB0aGlzLmJydXNoU2VsZWN0aW9uKCkpOwogICAgICAgIH0KICAgICAgICBzZXREaXNwbGF5ZWQodmFsdWUpIHsKICAgICAgICAgICAgdGhpcy5faXNEaXNwbGF5ZWQgPSB2YWx1ZTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB0aGUgYnJ1c2ggZmlsdGVyIGZvciB0aGUgZ2l2ZW4gc2VsZWN0aW9uIHVzaW5nIHRoZSBjdXJyZW50CiAgICAgICAgICogc2NhbGUuCiAgICAgICAgICovCiAgICAgICAgX2J1aWxkQnJ1c2hGaWx0ZXIoYnJ1c2hTZWxlY3Rpb24sIHNjYWxlVHlwZSwgeVNjYWxlIC8qIEQzIHNjYWxlICovKSB7CiAgICAgICAgICAgIGlmIChicnVzaFNlbGVjdGlvbiA9PT0gbnVsbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBBbHdheXNQYXNzaW5nQnJ1c2hGaWx0ZXIoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoc2NhbGVUeXBlID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICBjb25zb2xlLmVycm9yKCJTY2FsZSB0eXBlIGlzIG51bGwsIGJ1dCBicnVzaFNlbGVjdGlvbiBpc24ndDogIiwgYnJ1c2hTZWxlY3Rpb24pOwogICAgICAgICAgICAgICAgcmV0dXJuIG5ldyBBbHdheXNQYXNzaW5nQnJ1c2hGaWx0ZXIoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBzd2l0Y2ggKHNjYWxlVHlwZSkgewogICAgICAgICAgICAgICAgY2FzZSBTY2FsZVR5cGUuTElORUFSOgogICAgICAgICAgICAgICAgY2FzZSBTY2FsZVR5cGUuTE9HOiB7CiAgICAgICAgICAgICAgICAgICAgLyogRmFsbCBUaHJvdWdoICovCiAgICAgICAgICAgICAgICAgICAgY29uc3QgW2xvd2VyLCB1cHBlcixdID0gY29udGludW91c1NjYWxlSW52ZXJzZUltYWdlKHlTY2FsZSwgYnJ1c2hTZWxlY3Rpb25bMF0sIGJydXNoU2VsZWN0aW9uWzFdKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbmV3IEludGVydmFsQnJ1c2hGaWx0ZXIobG93ZXIsIHVwcGVyLCAKICAgICAgICAgICAgICAgICAgICAvKmxvd2VyT3Blbj0qLyBmYWxzZSwgCiAgICAgICAgICAgICAgICAgICAgLyp1cHBlck9wZW49Ki8gZmFsc2UpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY2FzZSBTY2FsZVR5cGUuUVVBTlRJTEU6IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBbbG93ZXIsIHVwcGVyLF0gPSBxdWFudGlsZVNjYWxlSW52ZXJzZUltYWdlKHlTY2FsZSwgYnJ1c2hTZWxlY3Rpb25bMF0sIGJydXNoU2VsZWN0aW9uWzFdKTsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbmV3IEludGVydmFsQnJ1c2hGaWx0ZXIobG93ZXIsIHVwcGVyLCAKICAgICAgICAgICAgICAgICAgICAvKmxvd2VyT3Blbj0qLyBmYWxzZSwgCiAgICAgICAgICAgICAgICAgICAgLyp1cHBlck9wZW49Ki8gdHJ1ZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjYXNlIFNjYWxlVHlwZS5OT05fTlVNRVJJQzoKICAgICAgICAgICAgICAgICAgICByZXR1cm4gbmV3IFNldEJydXNoRmlsdGVyKHBvaW50U2NhbGVJbnZlcnNlSW1hZ2UoeVNjYWxlLCBicnVzaFNlbGVjdGlvblswXSwgYnJ1c2hTZWxlY3Rpb25bMV0pKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zb2xlLmVycm9yKCdVbmtub3duIHNjYWxlIHR5cGU6ICcsIHNjYWxlVHlwZSk7CiAgICAgICAgICAgIHJldHVybiBuZXcgQWx3YXlzUGFzc2luZ0JydXNoRmlsdGVyKCk7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBNYW5hZ2VzIHRoZSBjb2xsZWN0aW9uIG9mIGF4ZXMgc2hvd24gaW4gdGhlIHBsb3QuIEhhcyBtZXRob2RzIHRoYXQgaGFuZGxlCiAgICAgKiBkcmFnZ2luZyBhbiBheGlzIGFuZCBjb250YWlucyB0aGUgbG9naWMgZm9yIHJlLW9yZGVyaW5nIHRoZSBheGVzCiAgICAgKiBkdXJpbmcgZHJhZ2dpbmcuCiAgICAgKi8KICAgIGNsYXNzIEF4ZXNDb2xsZWN0aW9uIHsKICAgICAgICBjb25zdHJ1Y3RvcihzdmdQcm9wcywgc2NoZW1hLCBpbnRlcmFjdGlvbk1hbmFnZXIpIHsKICAgICAgICAgICAgdGhpcy5fc3ZnUHJvcHMgPSBzdmdQcm9wczsKICAgICAgICAgICAgdGhpcy5fc2NoZW1hID0gc2NoZW1hOwogICAgICAgICAgICB0aGlzLl9heGVzID0gdGhpcy5fY3JlYXRlQXhlcyhpbnRlcmFjdGlvbk1hbmFnZXIpOwogICAgICAgICAgICB0aGlzLl9zdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucyA9IHBvaW50JDEoKQogICAgICAgICAgICAgICAgLnJhbmdlKFsxLCB0aGlzLl9zdmdQcm9wcy53aWR0aCAtIDFdKQogICAgICAgICAgICAgICAgLnBhZGRpbmcoMC41KTsKICAgICAgICAgICAgdGhpcy5fZHJhZ2dlZEF4aXMgPSBudWxsOwogICAgICAgICAgICB0aGlzLl9zdmdQcm9wcy5zdmdHLnNlbGVjdEFsbCgnZy5heGlzLXBhcmVudCcpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9wYXJlbnRzU2VsID0gdGhpcy5fc3ZnUHJvcHMuc3ZnRy5zZWxlY3RBbGwoJy5heGlzLXBhcmVudCcpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBVcGRhdGVzIGFsbCBheGVzIGJhc2VkIG9uIHRoZSBnaXZlbiAnb3B0aW9ucycgKHNlZSB0aGUgY29tbWVudHMgaW4KICAgICAgICAgKiB0Zi1ocGFyYW1zLXNjYWxlLWFuZC1jb2xvci1jb250cm9scy5odG1sKSBhbmQgc2Vzc2lvbkdyb3Vwcy4gU2Vzc2lvbkdyb3VwcwogICAgICAgICAqIGFyZSB1c2VkIHRvIHVwZGF0ZSB0aGUgZG9tYWluIChhbmQgdGh1cyBzY2FsZSkgb2YgdGhlIGF4ZXMuIFRoZSAnb3B0aW9ucycKICAgICAgICAgKiBvYmplY3QgY29udHJvbCB3aGljaCBheGVzIGFyZSB2aXNpYmxlLgogICAgICAgICAqLwogICAgICAgIHVwZGF0ZUF4ZXMob3B0aW9ucywgc2Vzc2lvbkdyb3VwcykgewogICAgICAgICAgICBjb25zb2xlLmFzc2VydCghdGhpcy5pc0F4aXNEcmFnZ2luZygpKTsKICAgICAgICAgICAgLy8gVHJhdmVyc2Ugb3B0aW9ucy5jb2x1bW5zLCBhbmQgdXBkYXRlIGVhY2ggY29ycmVzcG9uZGluZyBheGlzLgogICAgICAgICAgICBjb25zdCB2aXNpYmxlQ29sSW5kaWNlcyA9IG5ldyBTZXQoKTsKICAgICAgICAgICAgb3B0aW9ucy5jb2x1bW5zLmZvckVhY2goKGNvbHVtbikgPT4gewogICAgICAgICAgICAgICAgY29uc3QgY29sSW5kZXggPSBjb2x1bW4uYWJzb2x1dGVJbmRleDsKICAgICAgICAgICAgICAgIGxldCBheGlzID0gdGhpcy5fYXhlc1tjb2xJbmRleF07CiAgICAgICAgICAgICAgICBheGlzLnNldERpc3BsYXllZCh0cnVlKTsKICAgICAgICAgICAgICAgIGNvbnN0IGRvbWFpblZhbHVlcyA9IHNlc3Npb25Hcm91cHMubWFwKChzZykgPT4gY29sdW1uVmFsdWVCeUluZGV4KHRoaXMuX3NjaGVtYSwgc2csIGNvbEluZGV4KSk7CiAgICAgICAgICAgICAgICBheGlzLnNldERvbWFpbkFuZFNjYWxlKGRvbWFpblZhbHVlcywgY29sdW1uLnNjYWxlKTsKICAgICAgICAgICAgICAgIHZpc2libGVDb2xJbmRpY2VzLmFkZChjb2xJbmRleCk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICAvLyBTZXQgdGhlIHZpc2liaWxpdHkgb2YgdGhlIHJlbWFpbmluZyBheGVzIHRvIGZhbHNlLgogICAgICAgICAgICB0aGlzLl9heGVzLmZvckVhY2goKGF4aXMpID0+IHsKICAgICAgICAgICAgICAgIGlmICghdmlzaWJsZUNvbEluZGljZXMuaGFzKGF4aXMuY29sSW5kZXgoKSkpIHsKICAgICAgICAgICAgICAgICAgICBheGlzLnNldERpc3BsYXllZChmYWxzZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLl91cGRhdGVTdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucyh2aXNpYmxlQ29sSW5kaWNlcyk7CiAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgRE9NLgogICAgICAgICAgICB0aGlzLl9wYXJlbnRzU2VsID0gdGhpcy5fcGFyZW50c1NlbC5kYXRhKEFycmF5LmZyb20odmlzaWJsZUNvbEluZGljZXMpLCAKICAgICAgICAgICAgLyprZXk9Ki8gKGNvbEluZGV4KSA9PiBjb2xJbmRleCk7CiAgICAgICAgICAgIHRoaXMuX3BhcmVudHNTZWwuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9wYXJlbnRzU2VsID0gdGhpcy5fcGFyZW50c1NlbAogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2F4aXMtcGFyZW50JywgdHJ1ZSkKICAgICAgICAgICAgICAgIC5tZXJnZSh0aGlzLl9wYXJlbnRzU2VsKTsKICAgICAgICAgICAgY29uc3QgX3RoaXMgPSB0aGlzOwogICAgICAgICAgICB0aGlzLl9wYXJlbnRzU2VsCiAgICAgICAgICAgICAgICAuY2FsbCgoc2VsKSA9PiB0aGlzLl91cGRhdGVBeGVzUG9zaXRpb25zSW5ET00oc2VsKSkKICAgICAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChjb2xJbmRleCkgewogICAgICAgICAgICAgICAgLyogSGVyZSAndGhpcycgaXMgdGhlICdheGlzLXBhcmVudCctY2xhc3NlZCA8Zz4gZWxlbWVudCwKICAgICAgICAgICAgICAgICAgICAgYW5kICdfdGhpcycgaXMgdGhlIEF4ZXNDb2xsZWN0aW9uIGVsZW1lbnQuICovCiAgICAgICAgICAgICAgICBfdGhpcy5fYXhlc1tjb2xJbmRleF0udXBkYXRlRE9NKHRoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogRXhlY3V0ZXMgbWFwRnVuY3Rpb24gb24gZWFjaCB2aXNpYmxlIGF4aXMuIFJldHVybnMgYW4gYXJyYXkgY29udGFpbmluZyB0aGUKICAgICAgICAgKiByZXN1bHQgZnJvbSBlYWNoIGludm9jYXRpb24uIFRoZSBmdW5jdGlvbiBpcyBpbnZva2VkIG9uIHRoZSBheGVzIG9yZGVyZWQKICAgICAgICAgKiBieSB0aGVpciBpbmNyZWFzaW5nIHhQb3NpdGlvbi4KICAgICAgICAgKi8KICAgICAgICBtYXBWaXNpYmxlQXhlcyhtYXBGdW5jdGlvbikgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc3RhdGlvbmFyeUF4ZXNQb3NpdGlvbnMKICAgICAgICAgICAgICAgIC5kb21haW4oKQogICAgICAgICAgICAgICAgLm1hcCgoY29sSW5kZXgpID0+IG1hcEZ1bmN0aW9uKHRoaXMuZ2V0QXhpc1Bvc2l0aW9uKGNvbEluZGV4KSwgdGhpcy5fYXhlc1tjb2xJbmRleF0pKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogQHJldHVybiB0cnVlIGlmIHRoZSBnaXZlbiBwcmVkaWNhdGUgcmV0dXJucyB0cnVlIG9uIGV2ZXJ5IHZpc2libGUgYXhpcywKICAgICAgICAgKiAgICAgZmFsc2Ugb3RoZXJ3aXNlLiBOb3RlIHRoYXQgdGhlIHByZWRpY2F0ZSB3aWxsIG9ubHkgYmUgZXZhbHVhdGVkIHVudGlsCiAgICAgICAgICogICAgIHRoZSBmaXJzdCB0aW1lIGl0IHJldHVybnMgZmFsc2UuCiAgICAgICAgICovCiAgICAgICAgYWxsVmlzaWJsZUF4ZXNTYXRpc2Z5KHByZWRpY2F0ZSkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc3RhdGlvbmFyeUF4ZXNQb3NpdGlvbnMKICAgICAgICAgICAgICAgIC5kb21haW4oKQogICAgICAgICAgICAgICAgLmV2ZXJ5KChjb2xJbmRleCkgPT4gcHJlZGljYXRlKHRoaXMuZ2V0QXhpc1Bvc2l0aW9uKGNvbEluZGV4KSwgdGhpcy5fYXhlc1tjb2xJbmRleF0pKTsKICAgICAgICB9CiAgICAgICAgZ2V0QXhpc0ZvckNvbEluZGV4KGNvbEluZGV4KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9heGVzW2NvbEluZGV4XTsKICAgICAgICB9CiAgICAgICAgLyogQXhpcyBkcmFnZ2luZy4KICAgICAgICAgKiBUbyBkcmFnIGFuIGF4aXMsIGNhbGw6IGRyYWdTdGFydCgpLCBmb2xsb3dlZCBieSBvbmUgb3IgbW9yZSBkcmFnKCkgY2FsbHMKICAgICAgICAgKiBmb2xsb3dlZCBieSBhIHNpbmdsZSBjYWxsIHRvIGRyYWdFbmQoKS4KICAgICAgICAgKiBBdCBtb3N0IG9uZSBheGlzIGNhbiBiZSBkcmFnZ2VkIGF0IGFueSBnaXZlbiB0aW1lLgogICAgICAgICAqIEVhY2ggYXhpcyAod2hldGhlciBkcmFnZ2VkIG9yIG5vdCkgaGFzIGFuIGFzc29jaWF0ZWQgInN0YXRpb25hcnkiCiAgICAgICAgICogcG9zaXRpb24gd2hpY2ggaXMgaXRzICh4LWNvb3JkaW5hdGUpIHBvc2l0aW9uIHdoZW4gaXQgaXMgbm90IGJlaW5nIGRyYWdnZWQuCiAgICAgICAgICogVGhlIGFjdHVhbCBwb3NpdGlvbiBvZiBhbiBheGlzIGlzIGVpdGhlciBpdHMgYXNzb2NpYXRlZCBzdGF0aW9uYXJ5CiAgICAgICAgICogcG9zaXRpb24gaWYgaXRzIG5vdCBkcmFnZ2VkIG9yIGl0cyBjdXJyZW50bHkgZHJhZ2dlZCBwb3NpdGlvbi4gVGhpcyBjbGFzcwogICAgICAgICAqIG1haW50YWlucyB0aGUgaW52YXJpYW50IHRoYXQgdGhlIGF4ZXMnIHN0YXRpb25hcnkgcG9zaXRpb25zIG1hdGNoIHRoZSBvcmRlcgogICAgICAgICAqIG9mIHRoZWlyIGFjdHVhbCBwb3NpdGlvbiBieSByZS1hc3NpZ25pbmcgc3RhdGlvbmFyeSBwb3NpdGlvbnMgdG8gYXhlcyB3aGVuCiAgICAgICAgICogZHJhZ2dpbmcgYW4gYXhpcyBjYXVzZXMgaXQgdG8gInBhc3MiIGFub3RoZXIgYXhlcy4KICAgICAgICAgKi8KICAgICAgICBkcmFnU3RhcnQoY29sSW5kZXgpIHsKICAgICAgICAgICAgY29uc29sZS5hc3NlcnQoIXRoaXMuaXNBeGlzRHJhZ2dpbmcoKSk7CiAgICAgICAgICAgIGNvbnNvbGUuYXNzZXJ0KHRoaXMuX2F4ZXNbY29sSW5kZXhdLmlzRGlzcGxheWVkKCkpOwogICAgICAgICAgICB0aGlzLl9kcmFnZ2VkQXhpcyA9IHRoaXMuX2F4ZXNbY29sSW5kZXhdOwogICAgICAgICAgICB0aGlzLl9kcmFnZ2VkQXhpc1Bvc2l0aW9uID0gdGhpcy5fc3RhdGlvbmFyeUF4ZXNQb3NpdGlvbnMoY29sSW5kZXgpOwogICAgICAgIH0KICAgICAgICBkcmFnKG5ld1gpIHsKICAgICAgICAgICAgbmV3WCA9IE1hdGgubWluKE1hdGgubWF4KG5ld1gsIDApLCB0aGlzLl9zdmdQcm9wcy53aWR0aCk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdnZWRBeGlzUG9zaXRpb24gPSBuZXdYOwogICAgICAgICAgICBsZXQgdmlzaWJsZUNvbEluZGljZXMgPSB0aGlzLl9zdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucy5kb21haW4oKTsKICAgICAgICAgICAgdmlzaWJsZUNvbEluZGljZXMuc29ydCgoY2kxLCBjaTIpID0+IHRoaXMuZ2V0QXhpc1Bvc2l0aW9uKGNpMSkgLSB0aGlzLmdldEF4aXNQb3NpdGlvbihjaTIpKTsKICAgICAgICAgICAgdGhpcy5fc3RhdGlvbmFyeUF4ZXNQb3NpdGlvbnMuZG9tYWluKHZpc2libGVDb2xJbmRpY2VzKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlQXhlc1Bvc2l0aW9uc0luRE9NKHRoaXMuX3BhcmVudHNTZWwpOwogICAgICAgIH0KICAgICAgICBkcmFnRW5kKGR1cmF0aW9uKSB7CiAgICAgICAgICAgIGNvbnNvbGUuYXNzZXJ0KHRoaXMuaXNBeGlzRHJhZ2dpbmcoKSk7CiAgICAgICAgICAgIHRoaXMuX2RyYWdnZWRBeGlzUG9zaXRpb24gPSBudWxsOwogICAgICAgICAgICB0aGlzLl9kcmFnZ2VkQXhpcyA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX3VwZGF0ZUF4ZXNQb3NpdGlvbnNJbkRPTSh0aGlzLl9wYXJlbnRzU2VsLnRyYW5zaXRpb24oKS5kdXJhdGlvbihkdXJhdGlvbikpOwogICAgICAgIH0KICAgICAgICBpc0F4aXNEcmFnZ2luZygpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2RyYWdnZWRBeGlzICE9PSBudWxsOwogICAgICAgIH0KICAgICAgICBnZXRBeGlzUG9zaXRpb24oY29sSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2RyYWdnZWRBeGlzICE9PSBudWxsICYmCiAgICAgICAgICAgICAgICB0aGlzLl9kcmFnZ2VkQXhpcy5jb2xJbmRleCgpID09PSBjb2xJbmRleAogICAgICAgICAgICAgICAgPyB0aGlzLl9kcmFnZ2VkQXhpc1Bvc2l0aW9uCiAgICAgICAgICAgICAgICA6IHRoaXMuX3N0YXRpb25hcnlBeGVzUG9zaXRpb25zKGNvbEluZGV4KTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyB0aGUgZG9tYWluIG9mICdzdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucycgdG8gYmUgcHJlY2lzZWx5IHRoZSBnaXZlbgogICAgICAgICAqIHZpc2libGVDb2xJbmRpY2VzLCBidXQgcHJlc2VydmVzIHRoZSBvcmRlciBvZiB0aGUgY29sdW1uIGluZGljZXMgdGhhdAogICAgICAgICAqIGFyZSBhbHJlYWR5IGluIHRoZSBkb21haW4uIEVzc2VudGlhbGx5LCB0aGlzIG1ldGhvZCByZW1vdmVzIGluZGljZXMgaW4KICAgICAgICAgKiB0aGUgZG9tYWluIHRoYXQgYXJlIG5vdCBpbiB2aXNpYmxlQ29sSW5kaWNlcyBhbmQgdGhlbiBhcHBlbmRzIGluZGljZXMgaW4KICAgICAgICAgKiB2aXNpYmxlQ29sSW5kaWNlcyB0aGF0IGFyZSBub3QgY3VycmVudGx5IGluIHRoZSBkb21haW4uIFRodXMsIGluZGljZXMgaW4KICAgICAgICAgKiB2aXNpYmxlQ29sSW5kaWNlcyB0aGF0IGFyZSBhbHJlYWR5IGluIHN0YXRpb25hcnlBeGVzUG9zaXRpb25zCiAgICAgICAgICogd2lsbCBtYWludGFpbiB0aGVpciBvcmRlciBpbiBzdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucyBhbmQgd2lsbCBwcmVjZWRlCiAgICAgICAgICogdGhlIG5ldyBlbGVtZW50cy4KICAgICAgICAgKgogICAgICAgICAqIFRoaXMgcmVhc3NpZ25zIHN0YXRpb25hcnkgcG9zaXRpb25zIHRvIGF4ZXMgc28gdGhhdCB0aGUgb25seSB2aXNpYmxlCiAgICAgICAgICogYXhlcyBhcmUgdGhlIG9uZXMgd2l0aCBjb2x1bW4gaW5kaWNlcyBpbiAndmlzaWJsZUNvbEluZGljZXMnLCBidXQgcHJlc2VydmVzCiAgICAgICAgICogdGhlIG9yZGVyIG9mIGF4ZXMgaW5kZXhlZCBieSB2aXNpYmxlQ29sSW5kaWNlcyB0aGF0IGFyZSBhbHJlYWR5IHZpc2libGUuCiAgICAgICAgICovCiAgICAgICAgX3VwZGF0ZVN0YXRpb25hcnlBeGVzUG9zaXRpb25zKHZpc2libGVDb2xJbmRpY2VzKSB7CiAgICAgICAgICAgIGNvbnN0IHZpc2libGVEb21haW4gPSB0aGlzLl9zdGF0aW9uYXJ5QXhlc1Bvc2l0aW9ucwogICAgICAgICAgICAgICAgLmRvbWFpbigpCiAgICAgICAgICAgICAgICAuZmlsdGVyKChjb2xJbmRleCkgPT4gdmlzaWJsZUNvbEluZGljZXMuaGFzKGNvbEluZGV4KSk7CiAgICAgICAgICAgIGNvbnN0IG5ld0RvbWFpbiA9IEFycmF5LmZyb20obmV3IFNldChbLi4udmlzaWJsZURvbWFpbiwgLi4uQXJyYXkuZnJvbSh2aXNpYmxlQ29sSW5kaWNlcyldKSk7CiAgICAgICAgICAgIHRoaXMuX3N0YXRpb25hcnlBeGVzUG9zaXRpb25zLmRvbWFpbihuZXdEb21haW4pOwogICAgICAgIH0KICAgICAgICBfdXBkYXRlQXhlc1Bvc2l0aW9uc0luRE9NKHNlbGVjdGlvbk9yVHJhbnNpdGlvbikgewogICAgICAgICAgICBzZWxlY3Rpb25PclRyYW5zaXRpb24uYXR0cigndHJhbnNmb3JtJywgKGNvbEluZGV4KSA9PiB0cmFuc2xhdGVTdHIodGhpcy5nZXRBeGlzUG9zaXRpb24oY29sSW5kZXgpKSk7CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVBeGVzKGludGVyYWN0aW9uTWFuYWdlcikgewogICAgICAgICAgICByZXR1cm4gc2VxdWVuY2UobnVtQ29sdW1ucyh0aGlzLl9zY2hlbWEpKQogICAgICAgICAgICAgICAgLm1hcCgoY29sSW5kZXgpID0+IG5ldyBBeGlzKHRoaXMuX3N2Z1Byb3BzLCB0aGlzLl9zY2hlbWEsIGludGVyYWN0aW9uTWFuYWdlciwgY29sSW5kZXgpKTsKICAgICAgICB9CiAgICB9CiAgICBmdW5jdGlvbiBfaXNJbnRlcmFjdGl2ZUQzRXZlbnQoZDNFdmVudCkgewogICAgICAgIHJldHVybiBkM0V2ZW50LnNvdXJjZUV2ZW50ICE9PSBudWxsOwogICAgfQoKICAgIC8qIENvcHlyaWdodCAyMDE5IFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICdMaWNlbnNlJyk7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gJ0FTIElTJyBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgdmFyIExpbmVUeXBlOwogICAgKGZ1bmN0aW9uIChMaW5lVHlwZSkgewogICAgICAgIExpbmVUeXBlW0xpbmVUeXBlWyJGT1JFR1JPVU5EIl0gPSAwXSA9ICJGT1JFR1JPVU5EIjsKICAgICAgICBMaW5lVHlwZVtMaW5lVHlwZVsiQkFDS0dST1VORCJdID0gMV0gPSAiQkFDS0dST1VORCI7CiAgICB9KShMaW5lVHlwZSB8fCAoTGluZVR5cGUgPSB7fSkpOwogICAgLyoqCiAgICAgKiBBIGhhbmRsZSB0byBhIHJlcHJlc2VudGF0aW9uIG9mIGEgc2Vzc2lvbiBncm91cCBpbiB0aGUgJ0xpbmVzQ29sbGVjdGlvbicKICAgICAqIGNsYXNzIGJlbG93LiBUaGUgaGFuZGxlIGNhbiBhbHNvIGJlICJudWxsIiAtLSBtZWFuaW5nIGl0IHJlZmVyZW5jZXMgbm8KICAgICAqIHNlc3Npb24gZ3JvdXAgKHNpbWlsYXIgdG8gYSAibnVsbCBwb2ludGVyIiksIGluIHdoaWNoIGNhc2UgdGhlCiAgICAgKiAnc2Vzc2lvbkdyb3VwKCknIG1ldGhvZCByZXR1cm5zIG51bGwuCiAgICAgKgogICAgICogTm90ZTogd2UgdXNlIHRoaXMgY2xhc3MgcmF0aGVyIHRoYW4gYSBzaW1wbGUgU2Vzc2lvbkdyb3VwIG9iamVjdCBzbyB0aGF0IHdlCiAgICAgKiB3b24ndCBuZWVkIHRvIHNlYXJjaCB0aGUgRE9NIGZvciB0aGUgPHBhdGg+IHJlcHJlc2VudGluZyB0aGUgc2Vzc2lvbiBncm91cDsKICAgICAqIGluc3RlYWQgdGhlIChmb3JlZ3JvdW5kKSA8cGF0aD4gZWxlbWVudCBpcyBzdG9yZWQgaW4gdGhlIGhhbmRsZS4KICAgICAqLwogICAgY2xhc3MgU2Vzc2lvbkdyb3VwSGFuZGxlIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb25zdHJ1Y3RzIGEgc2Vzc2lvbiBncm91cCBoYW5kbGUgZnJvbSBhIEQzIHNlbGVjdGlvbiBvZiB0aGUgcGF0aAogICAgICAgICAqIGVsZW1lbnQgcmVwcmVzZW50aW5nIHRoZSBzZXNzaW9uR3JvdXAuIFRoaXMgc2hvdWxkIG9ubHkgYmUgY2FsbGVkIGJ5IHRoZQogICAgICAgICAqICdMaW5lc0NvbGxlY3Rpb24nIGNsYXNzIGJlbG93LiBJZiBzZXNzaW9uR3JvdXBTZWwgaXMgZW1wdHkgb3IgdW5kZWZpbmVkLCBhCiAgICAgICAgICogIm51bGwiIGhhbmRsZSB3aWxsIGJlIGNvbnN0cnVjdGVkLgogICAgICAgICAqLwogICAgICAgIGNvbnN0cnVjdG9yKHNlc3Npb25Hcm91cFNlbCkgewogICAgICAgICAgICBpZiAoc2Vzc2lvbkdyb3VwU2VsID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHNlc3Npb25Hcm91cFNlbCA9IHNlbGVjdEFsbChudWxsKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zb2xlLmFzc2VydChzZXNzaW9uR3JvdXBTZWwuc2l6ZSgpIDw9IDEpOwogICAgICAgICAgICB0aGlzLl9zZXNzaW9uR3JvdXBTZWwgPSBzZXNzaW9uR3JvdXBTZWw7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIEByZXR1cm4gdGhlIHNlc3Npb25Hcm91cCBvYmplY3QgdGhpcyBoYW5kbGUgcmVmZXJlbmNlcyBvciBudWxsIGlmCiAgICAgICAgICogdGhpcyBpcyBhICJudWxsIiByZWZlcmVuY2UuCiAgICAgICAgICovCiAgICAgICAgc2Vzc2lvbkdyb3VwKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc2Vzc2lvbkdyb3VwU2VsLnNpemUoKSA9PT0gMQogICAgICAgICAgICAgICAgPyB0aGlzLl9zZXNzaW9uR3JvdXBTZWwuZGF0dW0oKQogICAgICAgICAgICAgICAgOiBudWxsOwogICAgICAgIH0KICAgICAgICBpc051bGwoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLnNlc3Npb25Hcm91cCgpID09PSBudWxsOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBTaG91bGQgb25seSBiZSBjYWxsZWQgYnkgdGhlICdMaW5lc0NvbGxlY3Rpb24nIGNsYXNzIGJlbG93LgogICAgICAgICAqIEByZXR1cm4gdGhlIGQzLXNlbGVjdGlvbiBnaXZlbiBvbiBjb25zdHJ1Y3Rpb24uCiAgICAgICAgICovCiAgICAgICAgc2VsZWN0aW9uKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc2Vzc2lvbkdyb3VwU2VsOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBDb21wYXJlcyB0aGlzIGhhbmRsZSB0byAnb3RoZXJIYW5kbGUnIGFuZCByZXR1cm5zIHRydWUgaWYgYm90aCBhcmUgbnVsbAogICAgICAgICAqIG9yIGJvdGggYXJlIG5vdCBudWxsIGFuZCB0aGV5IHJlZmVyZW5jZSBlcXVhbCBzZXNzaW9uIGdyb3Vwcy4KICAgICAgICAgKiBTZXNzaW9uIGdyb3VwIGVxdWFsaXR5IGlzIGRldGVybWluZWQgYnkgdGhlaXIgbmFtZXMuCiAgICAgICAgICovCiAgICAgICAgZXF1YWxzVG8ob3RoZXJIYW5kbGUpIHsKICAgICAgICAgICAgaWYgKHRoaXMuaXNOdWxsKCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBvdGhlckhhbmRsZS5pc051bGwoKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAob3RoZXJIYW5kbGUuaXNOdWxsKCkpIHsKICAgICAgICAgICAgICAgIHJldHVybiBmYWxzZTsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gb3RoZXJIYW5kbGUuc2Vzc2lvbkdyb3VwKCkubmFtZSA9PSB0aGlzLnNlc3Npb25Hcm91cCgpLm5hbWU7CiAgICAgICAgfQogICAgfQogICAgLyoqCiAgICAgKiBNYW5hZ2VzIHRoZSBsaW5lcyByZXByZXNlbnRpbmcgdGhlIHNlc3Npb24gZ3JvdXBzLiBFYWNoIHNlc3Npb24gZ3JvdXAgaXMKICAgICAqIHJlcHJlc2VudGVkIGJ5IHR3byA8cGF0aD4gZWxlbWVudHMgd2l0aCB0aGUgc2FtZSBjb250cm9sIHBvaW50czogYSBmb3JlZ3JvdW5kCiAgICAgKiBhbmQgYSBiYWNrZ3JvdW5kIGxpbmUsIHdpdGggdGhlIGZvcmVncm91bmQgbGluZSBhbHdheXMgcmVuZGVyZWQgYWZ0ZXIgdGhlCiAgICAgKiBiYWNrZ3JvdW5kIGxpbmUgKGl0IHN1Y2NlZWRzIGl0IGluIGRvY3VtZW50IG9yZGVyKS4gVGhlIGZvcmVncm91bmQgbGluZSBpcwogICAgICogY29sb3JlZCBiYXNlZCBvbiB0aGUgdmFsdWUgIG9mIHRoZSAnY29sb3ItYnknIGNvbHVtbiAoc3BlY2lmaWVkIGluIG9wdGlvbnMpLAogICAgICogd2hlcmVhcyB0aGUgYmFja2dyb3VuZCBsaW5lIGlzIGdyYXkuIFRoZSBmb3JlZ3JvdW5kIGxpbmUgaXMgZGlzcGxheWVkIG9ubHkKICAgICAqIGlmIHRoZSBzZXNzaW9uIGdyb3VwIHBhc3NlcyB0aGUgY3VycmVudCBheGVzIGJydXNoIGZpbHRlcnMuIFRoaXMgd2F5LCBvbmx5CiAgICAgKiBzZXNzaW9uIGdyb3VwcyB0aGF0IHBhc3MgdGhlIGN1cnJlbnQgYnJ1c2ggZmlsdGVycyB3aWxsIGJlIHJlcHJlc2VudGVkIGJ5CiAgICAgKiBjb2xvcmVkIGxpbmVzLCBhbmQgdGhlIG90aGVyIHNlc3Npb24gZ3JvdXBzIHdpbGwgYmUgcmVwcmVzZW50ZWQgYnkgZ3JheQogICAgICogbGluZXMuCiAgICAgKgogICAgICogTm90ZSB0aGF0IHdlIGNvdWxkIGhhdmUgcmVwcmVzZW50ZWQgZWFjaCBzZXNzaW9uIGdyb3VwIHdpdGggYSBzaW5nbGUgbGluZQogICAgICogd2l0aCBhIGNvbG9yIHRoYXQgZGVwZW5kcyBvbiB3aGV0aGVyIHRoZSBzZXNzaW9uIGdyb3VwIHBhc3NlZCB0aGUgYnJ1c2gKICAgICAqIGZpbHRlcnMuIEhvd2V2ZXIsIHRoaXMgd291bGQgaGF2ZSByZXF1aXJlZCB1cyB0byByZS1vcmRlciB0aGUgRE9NIHRvIGF2b2lkCiAgICAgKiByZW5kZXJpbmcgZ3JheSBsaW5lcyBvbiB0b3Agb2YgY29sb3JlZCBsaW5lcyAod2hpY2ggd291bGQgbG9vayBiYWQsCiAgICAgKiBlc3BlY2lhbGx5IGlmIHRoZSBkZW5zaXR5IG9mIGxpbmVzIGlzIGxhcmdlKS4KICAgICAqCiAgICAgKiBUaGlzIGNsYXNzIGFsc28gc3RvcmVzIHR3byBTZXNzaW9uR3JvdXBIYW5kbGVzOiBwZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUgYW5kCiAgICAgKiBzZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZSwgYW5kIHByb3ZpZGVzIG1ldGhvZHMgZm9yIHVwZGF0aW5nIHRoZW0uIFRoZXNlCiAgICAgKiBhcmUgdXNlZCB0byBzdG9yZSB0aGUgcGVha2VkIHNlc3Npb24gZ3JvdXA6IHRoZSBzZXNzaW9uIGdyb3VwIHdob3NlIGxpbmUKICAgICAqIGlzIGNsb3Nlc3QgdG8gdGhlIG1vdXNlIHBvaW50LiBUaGUgcGVha2VkIHNlc3Npb24gZ3JvdXAgY2FuIGJlIHNlbGVjdGVkCiAgICAgKiBieSBjbGlja2luZyB0aGUgbW91c2UgcG9pbnRlci4gVGhlIGN1cnJlbnRseSBzZWxlY3RlZCBzZXNzaW9uIGdyb3VwIGlzCiAgICAgKiByZWZlcmVuY2VkIGJ5IHRoZSBzZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZS4KICAgICAqLwogICAgY2xhc3MgTGluZXNDb2xsZWN0aW9uIHsKICAgICAgICBjb25zdHJ1Y3RvcihzdmdQcm9wcywgc2NoZW1hLCBheGVzQ29sbGVjdGlvbikgewogICAgICAgICAgICB0aGlzLl9zdmdQcm9wcyA9IHN2Z1Byb3BzOwogICAgICAgICAgICB0aGlzLl9zY2hlbWEgPSBzY2hlbWE7CiAgICAgICAgICAgIHRoaXMuX2F4ZXNDb2xsZWN0aW9uID0gYXhlc0NvbGxlY3Rpb247CiAgICAgICAgICAgIHRoaXMuX3Nlc3Npb25Hcm91cHMgPSBbXTsKICAgICAgICAgICAgdGhpcy5fc3ZnUHJvcHMuc3ZnRy5zZWxlY3RBbGwoJ2cuYmFja2dyb3VuZCcpLnJlbW92ZSgpOwogICAgICAgICAgICB0aGlzLl9zdmdQcm9wcy5zdmdHLnNlbGVjdEFsbCgnZy5mb3JlZ3JvdW5kJykucmVtb3ZlKCk7CiAgICAgICAgICAgIHRoaXMuX2JnUGF0aHNTZWwgPSB0aGlzLl9zdmdQcm9wcy5zdmdHCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCdiYWNrZ3JvdW5kJywgdHJ1ZSkKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJ3BhdGgnKTsKICAgICAgICAgICAgdGhpcy5fZmdQYXRoc1NlbCA9IHRoaXMuX3N2Z1Byb3BzLnN2Z0cKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2ZvcmVncm91bmQnLCB0cnVlKQogICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgncGF0aCcpOwogICAgICAgICAgICB0aGlzLl91cGRhdGVWaXNpYmxlRmdQYXRoc1NlbCgpOwogICAgICAgICAgICB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUgPSBuZXcgU2Vzc2lvbkdyb3VwSGFuZGxlKCk7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlID0gbmV3IFNlc3Npb25Hcm91cEhhbmRsZSgpOwogICAgICAgICAgICB0aGlzLl9kM2xpbmUgPSBsaW5lKCkuY3VydmUoY3VydmVMaW5lYXIpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBAcmV0dXJuIGEgU2Vzc2lvbkdyb3VwSGFuZGxlIHJlZmVyZW5jaW5nIHRoZSBnaXZlbiBzZXNzaW9uR3JvdXAuIElmIHRoZQogICAgICAgICAqIGdpdmVuIHNlc3Npb25Hcm91cCBpcyBudWxsIG9yIHVuZGVmaW5lZCByZXR1cm5zIGEgIm51bGwiIGhhbmRsZS4KICAgICAgICAgKi8KICAgICAgICBnZXRTZXNzaW9uR3JvdXBIYW5kbGUoc2Vzc2lvbkdyb3VwKSB7CiAgICAgICAgICAgIGlmIChzZXNzaW9uR3JvdXAgPT09IG51bGwgfHwgc2Vzc2lvbkdyb3VwID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHJldHVybiBuZXcgU2Vzc2lvbkdyb3VwSGFuZGxlKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgcmV0dXJuIG5ldyBTZXNzaW9uR3JvdXBIYW5kbGUodGhpcy5fZmdQYXRoc1NlbC5maWx0ZXIoKHNnKSA9PiBzZy5uYW1lID09PSBzZXNzaW9uR3JvdXAubmFtZSkpOwogICAgICAgIH0KICAgICAgICBoaWRlQmFja2dyb3VuZExpbmVzKCkgewogICAgICAgICAgICB0aGlzLl9iZ1BhdGhzU2VsLmF0dHIoJ3Zpc2liaWxpdHknLCAnaGlkZGVuJyk7CiAgICAgICAgfQogICAgICAgIHNob3dCYWNrZ3JvdW5kTGluZXMoKSB7CiAgICAgICAgICAgIHRoaXMuX2JnUGF0aHNTZWwuYXR0cigndmlzaWJpbGl0eScsIG51bGwpOwogICAgICAgIH0KICAgICAgICBwZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUoKSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGU7CiAgICAgICAgfQogICAgICAgIHNlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlKCkgewogICAgICAgICAgICByZXR1cm4gdGhpcy5fc2VsZWN0ZWRTZXNzaW9uR3JvdXBIYW5kbGU7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJlY29tcHV0ZXMgdGhlIGNvbnRyb2wgcG9pbnRzIG9mIHRoZSBsaW5lcyB3aXRoIHRoZSBnaXZlbiAndHlwZScKICAgICAgICAgKiAoZm9yZWdyb3VuZCBvciBiYWNrZ3JvdW5kKSB0byBjb3JyZXNwb25kIHRvIHRoZSBjdXJyZW50IHN0YXRlIG9mIHRoZQogICAgICAgICAqIGF4ZXNDb2xsZWN0aW9uLgogICAgICAgICAqCiAgICAgICAgICogQHBhcmFtIGxpbmVUeXBlIC0gVGhlIHR5cGUgb2YgbGluZXMgdG8gdXBkYXRlLgogICAgICAgICAqIEBwYXJhbSB0cmFuc2l0aW9uRHVyYXRpb24gLSBUaGUgbGluZXMgd2lsbCBiZSB0cmFuc2l0aW9uZWQgKGFuaW1hdGVkKSB0bwogICAgICAgICAqICAgICB0aGVpciBuZXcgc3RhdGUuIFRoaXMgc3BlY2lmaWVzIHRoZSBkdXJhdGlvbiBvZiB0aGF0IHRyYW5zaXRpb24uIDAKICAgICAgICAgKiAgICAgbWVhbnMgbm8gYW5pbWF0aW9uLgogICAgICAgICAqLwogICAgICAgIHJlY29tcHV0ZUNvbnRyb2xQb2ludHMobGluZVR5cGUsIHRyYW5zaXRpb25EdXJhdGlvbiA9IDApIHsKICAgICAgICAgICAgY29uc3QgcGF0aFNlbCA9IGxpbmVUeXBlID09PSBMaW5lVHlwZS5GT1JFR1JPVU5EID8gdGhpcy5fZmdQYXRoc1NlbCA6IHRoaXMuX2JnUGF0aHNTZWw7CiAgICAgICAgICAgIHBhdGhTZWwKICAgICAgICAgICAgICAgIC50cmFuc2l0aW9uKCkKICAgICAgICAgICAgICAgIC5kdXJhdGlvbih0cmFuc2l0aW9uRHVyYXRpb24pCiAgICAgICAgICAgICAgICAuYXR0cignZCcsIChzZXNzaW9uR3JvdXApID0+IHRoaXMuX3BhdGhEQXR0cmlidXRlKHNlc3Npb25Hcm91cCkpOwogICAgICAgICAgICBpZiAobGluZVR5cGUgPT09IExpbmVUeXBlLkZPUkVHUk9VTkQpIHsKICAgICAgICAgICAgICAgIC8vIFVwZGF0ZSB0aGUgY29udHJvbCBwb2ludHMgcHJvcGVydHksIGlmIHdlJ3JlIHVwZGF0aW5nIHRoZSBmb3JlZ3JvdW5kCiAgICAgICAgICAgICAgICAvLyBsaW5lcy4KICAgICAgICAgICAgICAgIHdpbmRvdy5zZXRUaW1lb3V0KCgpID0+IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgICAgICAgICAgdGhpcy5fZmdQYXRoc1NlbC5lYWNoKGZ1bmN0aW9uIChzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgICAgICAgICAgICAgLy8gJ190aGlzJyByZWZlcnMgdG8gdGhlICdMaW5lc0NvbGxlY3Rpb24nIGluc3RhbmNlLgogICAgICAgICAgICAgICAgICAgICAgICBfdGhpcy5fc2V0Q29udHJvbFBvaW50c1Byb3BlcnR5KHRoaXMsIHNlc3Npb25Hcm91cCk7CiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXJlbmRlcnMgdGhlIGZvcmVncm91bmQgbGluZXMgc28gdGhhdCB0aGVpciB2aXNpYmlsaXR5IG1hdGNoZXMgdGhlCiAgICAgICAgICogY3VycmVudCBicnVzaCBmaWx0ZXJzLgogICAgICAgICAqLwogICAgICAgIHJlY29tcHV0ZUZvcmVncm91bmRMaW5lc1Zpc2liaWxpdHkoKSB7CiAgICAgICAgICAgIHRoaXMuX2ZnUGF0aHNTZWwuY2xhc3NlZCgnaW52aXNpYmxlLXBhdGgnLCAoc2Vzc2lvbkdyb3VwKSA9PiAhdGhpcy5fYXhlc0NvbGxlY3Rpb24uYWxsVmlzaWJsZUF4ZXNTYXRpc2Z5KCh4UG9zaXRpb24sIGF4aXMpID0+IGF4aXMKICAgICAgICAgICAgICAgIC5icnVzaEZpbHRlcigpCiAgICAgICAgICAgICAgICAuaXNQYXNzaW5nKGNvbHVtblZhbHVlQnlJbmRleCh0aGlzLl9zY2hlbWEsIHNlc3Npb25Hcm91cCwgYXhpcy5jb2xJbmRleCgpKSkpKTsKICAgICAgICAgICAgdGhpcy5fdXBkYXRlVmlzaWJsZUZnUGF0aHNTZWwoKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogU2V0cyB0aGUgY29sb3Jpbmcgc2NoZW1lIG9mIHRoZSAodmlzaWJsZSkgZm9yZWdyb3VuZCBsaW5lcy4KICAgICAgICAgKiBBIGZvcmVncm91bmQgbGluZSB3aWxsIGJlIGNvbG9yZWQgYnkgYSBjb2xvciBjb3JyZXNwb25kaW5nIHRvIHRoZSB2YWx1ZQogICAgICAgICAqIG9mIHRoZSBjb2x1bW4gaW5kZXhlZCBieSBjb2xvckJ5Q29sdW1uSW5kZXggaW4gdGhlIHNlc3Npb24gZ3JvdXAKICAgICAgICAgKiByZXByZXNlbnRlZCBieSB0aGUgbGluZS4gVGhlIGNvbG9yIGNvcnJlc3BvbmRpbmcgdG8gYSB2YWx1ZSBpcwogICAgICAgICAqIGludGVycG9sYXRlZCBiZXR3ZWVuIG1pbkNvbG9yIGFuZCBtYXhDb2xvci4KICAgICAgICAgKi8KICAgICAgICBzZXRGb3JlZ3JvdW5kTGluZXNDb2xvcihjb2xvckJ5Q29sdW1uSW5kZXgsIG1pbkNvbG9yLCBtYXhDb2xvcikgewogICAgICAgICAgICBjb25zdCBsaW5lQ29sb3JGdW5jdGlvbiA9IHRoaXMuX2NyZWF0ZUxpbmVDb2xvckZ1bmN0aW9uKGNvbG9yQnlDb2x1bW5JbmRleCwgbWluQ29sb3IsIG1heENvbG9yKTsKICAgICAgICAgICAgdGhpcy5fZmdQYXRoc1NlbC5hdHRyKCdzdHJva2UnLCBsaW5lQ29sb3JGdW5jdGlvbik7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFVwZGF0ZXMgdGhlIHNlc3Npb25Hcm91cHMsIGNvbG9yQnlDb2x1bW5JbmRleCwgbWluQ29sb3IgYW5kIG1heENvbG9yIGFuZAogICAgICAgICAqIHJlZHJhd3MgdGhlIGxpbmVzLgogICAgICAgICAqLwogICAgICAgIHJlZHJhdyhzZXNzaW9uR3JvdXBzLCBjb2xvckJ5Q29sdW1uSW5kZXgsIG1pbkNvbG9yLCBtYXhDb2xvcikgewogICAgICAgICAgICBjb25zdCBwZWFrZWRTRyA9IHRoaXMuX3BlYWtlZFNlc3Npb25Hcm91cEhhbmRsZS5zZXNzaW9uR3JvdXAoKTsKICAgICAgICAgICAgY29uc3Qgc2VsZWN0ZWRTRyA9IHRoaXMuX3NlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlLnNlc3Npb25Hcm91cCgpOwogICAgICAgICAgICB0aGlzLl9zZXNzaW9uR3JvdXBzID0gc2Vzc2lvbkdyb3VwczsKICAgICAgICAgICAgdGhpcy5fZmdQYXRoc1NlbCA9IHRoaXMuX3JlY29tcHV0ZVBhdGhTZWxlY3Rpb24odGhpcy5fZmdQYXRoc1NlbCk7CiAgICAgICAgICAgIHRoaXMuX2JnUGF0aHNTZWwgPSB0aGlzLl9yZWNvbXB1dGVQYXRoU2VsZWN0aW9uKHRoaXMuX2JnUGF0aHNTZWwpOwogICAgICAgICAgICB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUgPSB0aGlzLmdldFNlc3Npb25Hcm91cEhhbmRsZShwZWFrZWRTRyk7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlID0gdGhpcy5nZXRTZXNzaW9uR3JvdXBIYW5kbGUoc2VsZWN0ZWRTRyk7CiAgICAgICAgICAgIHRoaXMucmVjb21wdXRlQ29udHJvbFBvaW50cyhMaW5lVHlwZS5GT1JFR1JPVU5EKTsKICAgICAgICAgICAgdGhpcy5yZWNvbXB1dGVDb250cm9sUG9pbnRzKExpbmVUeXBlLkJBQ0tHUk9VTkQpOwogICAgICAgICAgICB0aGlzLnJlY29tcHV0ZUZvcmVncm91bmRMaW5lc1Zpc2liaWxpdHkoKTsKICAgICAgICAgICAgdGhpcy5zZXRGb3JlZ3JvdW5kTGluZXNDb2xvcihjb2xvckJ5Q29sdW1uSW5kZXgsIG1pbkNvbG9yLCBtYXhDb2xvcik7CiAgICAgICAgfQogICAgICAgIHVwZGF0ZVBlYWtlZFNlc3Npb25Hcm91cChuZXdIYW5kbGUpIHsKICAgICAgICAgICAgdGhpcy5fcGVha2VkU2Vzc2lvbkdyb3VwSGFuZGxlLnNlbGVjdGlvbigpLmNsYXNzZWQoJ3BlYWtlZC1wYXRoJywgZmFsc2UpOwogICAgICAgICAgICB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUgPSBuZXdIYW5kbGU7CiAgICAgICAgICAgIHRoaXMuX3BlYWtlZFNlc3Npb25Hcm91cEhhbmRsZS5zZWxlY3Rpb24oKS5jbGFzc2VkKCdwZWFrZWQtcGF0aCcsIHRydWUpOwogICAgICAgIH0KICAgICAgICBjbGVhclBlYWtlZFNlc3Npb25Hcm91cCgpIHsKICAgICAgICAgICAgdGhpcy51cGRhdGVQZWFrZWRTZXNzaW9uR3JvdXAobmV3IFNlc3Npb25Hcm91cEhhbmRsZSgpKTsKICAgICAgICB9CiAgICAgICAgdXBkYXRlU2VsZWN0ZWRTZXNzaW9uR3JvdXAobmV3SGFuZGxlKSB7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlCiAgICAgICAgICAgICAgICAuc2VsZWN0aW9uKCkKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCdzZWxlY3RlZC1wYXRoJywgZmFsc2UpOwogICAgICAgICAgICB0aGlzLl9zZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZSA9IG5ld0hhbmRsZTsKICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWRTZXNzaW9uR3JvdXBIYW5kbGUuc2VsZWN0aW9uKCkuY2xhc3NlZCgnc2VsZWN0ZWQtcGF0aCcsIHRydWUpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXR1cm5zIGEgaGFuZGxlIHJlZmVyZW5jaW5nIHRoZSBjbG9zZXN0IHNlc3Npb24gZ3JvdXAgdG8gYSBnaXZlbiBwb2ludAogICAgICAgICAqIGluIHRoZSBTVkcgb3IgYSBudWxsIGhhbmRsZSBpZiB0aGUgY2xvc2VzdCBzZXNzaW9uIGdyb3VwIGlzCiAgICAgICAgICogdG9vIGZhciBhd2F5LgogICAgICAgICAqLwogICAgICAgIGZpbmRDbG9zZXN0U2Vzc2lvbkdyb3VwKHgsIHkpIHsKICAgICAgICAgICAgY29uc3QgYXhlc1Bvc2l0aW9ucyA9IHRoaXMuX2F4ZXNDb2xsZWN0aW9uLm1hcFZpc2libGVBeGVzKCh4UG9zaXRpb24sIGF4aXMpID0+IHhQb3NpdGlvbik7CiAgICAgICAgICAgIGNvbnN0IGNsb3Nlc3RGZ1BhdGggPSBmaW5kQ2xvc2VzdFBhdGgodGhpcy5fdmlzaWJsZUZnUGF0aHNTZWwubm9kZXMoKSwgYXhlc1Bvc2l0aW9ucywgW3gsIHldLCAKICAgICAgICAgICAgLyogdGhyZXNob2xkICovIDEwMCk7CiAgICAgICAgICAgIGlmIChjbG9zZXN0RmdQYXRoID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gbmV3IFNlc3Npb25Hcm91cEhhbmRsZSgpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHJldHVybiBuZXcgU2Vzc2lvbkdyb3VwSGFuZGxlKHNlbGVjdChjbG9zZXN0RmdQYXRoKSk7CiAgICAgICAgfQogICAgICAgIF9jcmVhdGVMaW5lQ29sb3JGdW5jdGlvbihjb2xvckJ5Q29sdW1uSW5kZXgsIG1pbkNvbG9yLCBtYXhDb2xvcikgewogICAgICAgICAgICBpZiAoY29sb3JCeUNvbHVtbkluZGV4ID09PSBudWxsKSB7CiAgICAgICAgICAgICAgICAvKiBVc2UgYSBkZWZhdWx0IGNvbG9yIGlmIG5vIGNvbG9yLWJ5IGNvbHVtbiBpcyBzZWxlY3RlZC4gKi8KICAgICAgICAgICAgICAgIHJldHVybiAoKSA9PiAncmVkJzsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBjb2xvclNjYWxlID0gbGluZWFyJDIoKQogICAgICAgICAgICAgICAgLmRvbWFpbihudW1lcmljQ29sdW1uRXh0ZW50KHRoaXMuX3NjaGVtYSwgdGhpcy5fc2Vzc2lvbkdyb3VwcywgY29sb3JCeUNvbHVtbkluZGV4KSkKICAgICAgICAgICAgICAgIC5yYW5nZShbbWluQ29sb3IsIG1heENvbG9yXSkKICAgICAgICAgICAgICAgIC5pbnRlcnBvbGF0ZShsYWIkMSk7CiAgICAgICAgICAgIHJldHVybiAoc2Vzc2lvbkdyb3VwKSA9PiBjb2xvclNjYWxlKGNvbHVtblZhbHVlQnlJbmRleCh0aGlzLl9zY2hlbWEsIHNlc3Npb25Hcm91cCwgY29sb3JCeUNvbHVtbkluZGV4KSk7CiAgICAgICAgfQogICAgICAgIF9yZWNvbXB1dGVQYXRoU2VsZWN0aW9uKGN1cnJlbnRQYXRoU2VsIC8qIGQzIHNlbGVjdGlvbiAqLykgewogICAgICAgICAgICBjdXJyZW50UGF0aFNlbCA9IGN1cnJlbnRQYXRoU2VsLmRhdGEodGhpcy5fc2Vzc2lvbkdyb3VwcywgCiAgICAgICAgICAgIC8qa2V5PSovIChzZXNzaW9uR3JvdXApID0+IHNlc3Npb25Hcm91cC5uYW1lKTsKICAgICAgICAgICAgY3VycmVudFBhdGhTZWwuZXhpdCgpLnJlbW92ZSgpOwogICAgICAgICAgICByZXR1cm4gY3VycmVudFBhdGhTZWwuZW50ZXIoKS5hcHBlbmQoJ3BhdGgnKS5tZXJnZShjdXJyZW50UGF0aFNlbCk7CiAgICAgICAgfQogICAgICAgIC8qKiBTZXRzIHRoZSBjb250cm9sUG9pbnRzIHByb3BlcnR5IG9mICdwYXRoRWxlbWVudCcgdG8gdGhlIGNvbnRyb2wtcG9pbnRzCiAgICAgICAgICogYXJyYXkgb2YgdGhlIGdpdmVuIHNlc3Npb25Hcm91cCB3aXRoIHJlc3BlY3QgdG8gdGhlIGN1cnJlbnQgc3RhdGUgb2YKICAgICAgICAgKiB0aGUgYXhlc0NvbGxlY3Rpb24uCiAgICAgICAgICovCiAgICAgICAgX3NldENvbnRyb2xQb2ludHNQcm9wZXJ0eShwYXRoRWxlbWVudCwgc2Vzc2lvbkdyb3VwKSB7CiAgICAgICAgICAgIHBhdGhFbGVtZW50LmNvbnRyb2xQb2ludHMgPSB0aGlzLl9jb21wdXRlQ29udHJvbFBvaW50cyhzZXNzaW9uR3JvdXApOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBAcmV0dXJuIGFuIGFycmF5IG9mIDItdHVwbGVzLS1lYWNoIHJlcHJlc2VudGluZyBhIGNvbnRyb2wgcG9pbnQgZm9yCiAgICAgICAgICogYSBsaW5lIHJlcHJlc2VudGluZyB0aGUgZ2l2ZW4gJ3Nlc3Npb25Hcm91cCcuIFRoZSBjb250cm9sIHBvaW50cyBhcmUKICAgICAgICAgKiBjb21wdXRlZCB3aXRoIHJlc3BlY3QgdG8gdGhlIGN1cnJlbnQgc3RhdGUgb2YgdGhlIGF4ZXNDb2xsZWN0aW9uLgogICAgICAgICAqLwogICAgICAgIF9jb21wdXRlQ29udHJvbFBvaW50cyhzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2F4ZXNDb2xsZWN0aW9uLm1hcFZpc2libGVBeGVzKCh4UG9zaXRpb24sIGF4aXMpID0+IFsKICAgICAgICAgICAgICAgIHhQb3NpdGlvbiwKICAgICAgICAgICAgICAgIGF4aXMueVNjYWxlKCkoY29sdW1uVmFsdWVCeUluZGV4KHRoaXMuX3NjaGVtYSwgc2Vzc2lvbkdyb3VwLCBheGlzLmNvbEluZGV4KCkpKSwKICAgICAgICAgICAgXSk7CiAgICAgICAgfQogICAgICAgIF9wYXRoREF0dHJpYnV0ZShzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX2QzbGluZSh0aGlzLl9jb21wdXRlQ29udHJvbFBvaW50cyhzZXNzaW9uR3JvdXApKTsKICAgICAgICB9CiAgICAgICAgX3VwZGF0ZVZpc2libGVGZ1BhdGhzU2VsKCkgewogICAgICAgICAgICB0aGlzLl92aXNpYmxlRmdQYXRoc1NlbCA9IHRoaXMuX2ZnUGF0aHNTZWwuZmlsdGVyKCc6bm90KC5pbnZpc2libGUtcGF0aCknKTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMTkgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgJ0xpY2Vuc2UnKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAnQVMgSVMnIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIFN0b3JlcyBzb21lIGdsb2JhbCBwcm9wZXJ0aWVzIHN1Y2ggYXMgd2lkdGggYW5kIGhlaWdodCBvZiB0aGUgU1ZHIGVsZW1lbnQKICAgICAqIHVzZWQgZm9yIHJlbmRlcmluZyB0aGUgcGFyYWxsZWwgY29vcmRpbmF0ZXMgcGxvdC4gQWxzbyBjb250YWlucyB0aGUgdG9wLWxldmVsCiAgICAgKiBET00gPGc+IGVsZW1lbnQgdW5kZXJ3aGljaCB0aGUgcGxvdCB3aWxsIGJlIHJlbmRlcmVkLgogICAgICovCiAgICBjbGFzcyBTVkdQcm9wZXJ0aWVzIHsKICAgICAgICAvKioKICAgICAgICAgKiBDb21wdXRlcyB0aGUgd2lkdGggYW5kIGhlaWdodCBvZiB0aGUgU1ZHIGVsZW1lbnQgYmFzZWQgb24gdGhlIG51bWJlciBvZgogICAgICAgICAqIGNvbHVtbnMgaW4gdGhlIHNjaGVtYS4gQWRkcyBzb21lIG1hcmdpbnMgYW5kIGFkZHMgYSB0b3AtbGV2ZWwgPGc+IGVsZW1lbnQKICAgICAgICAgKiB1bmRlcndoaWNoIHRoZSBwbG90IHNob3VsZCBiZSByZW5kZXJlZC4KICAgICAgICAgKi8KICAgICAgICBjb25zdHJ1Y3RvcihzdmcsIG51bUNvbHVtbnMpIHsKICAgICAgICAgICAgLy8gV2UgdXNlIHRoZSBmb2xsb3dpbmcgYWxnb3JpdGhtIGZvciBsYXlpbmcgb3V0IG91ciBTVkc6CiAgICAgICAgICAgIC8vIFdlIGNvbXB1dGUgYSBtaW5pbXVtIHNpemUgZm9yIHRoZSBTVkcgYmFzZWQgb24gdGhlIG51bWJlciBjb2x1bW5zCiAgICAgICAgICAgIC8vIGFuZCBzb21lIG1hcmdpbnMuIFdlIHNldCB0aGUgc3ZnICJ3aWR0aCIgYW5kICJoZWlnaHQiIHN0eWxlcwogICAgICAgICAgICAvLyB0byAiMTAwJSIgc28gdGhhdCBpdCB0YWtlcyB1cCB0aGUgZnVsbCBhcmVhIG9mIGl0cyBwYXJlbnQsIGJ1dCB1c2UKICAgICAgICAgICAgLy8gIm1pbi13aWR0aCIgYW5kICJtaW4taGVpZ2h0Iiwgc28gdGhhdCBpZiB0aGUgcGFyZW50IGlzIHRvbyBzbWFsbAogICAgICAgICAgICAvLyB0aGUgc3ZnIHdvbid0IHNocmluayBkb3duIChpdCB3aWxsIG92ZXJmbG93IHdpdGggc2Nyb2xsIGJhcnMpLgogICAgICAgICAgICAvLyBJZiB0aGUgcGFyZW50IGlzIGxhcmdlciB0aGFuIHRoZSBtaW5pbXVtIHNpemUsIHdlIHVzZSBpdHMKICAgICAgICAgICAgLy8gcHJlc2VydmVBc3BlY3RSYXRpbyBhdHRyIHRvIHNjYWxlIHRoZSBjb250ZW50cyB0byBmaXQgdGhlIGxhcmdlciBzaXplLgogICAgICAgICAgICB0aGlzLnN2ZyA9IHNlbGVjdChzdmcpOwogICAgICAgICAgICBjb25zdCBtYXJnaW4gPSB7IHRvcDogMzAsIHJpZ2h0OiAxMCwgYm90dG9tOiAxMCwgbGVmdDogMTAgfTsKICAgICAgICAgICAgY29uc3QgQ09MX1dJRFRIID0gMTAwOwogICAgICAgICAgICBjb25zdCBDT0xfSEVJR0hUID0gMjAwOwogICAgICAgICAgICBjb25zdCB0b3RhbFdpZHRoID0gbnVtQ29sdW1ucyAqIENPTF9XSURUSCArIG1hcmdpbi5sZWZ0ICsgbWFyZ2luLnJpZ2h0OwogICAgICAgICAgICBjb25zdCB0b3RhbEhlaWdodCA9IENPTF9IRUlHSFQgKyBtYXJnaW4udG9wICsgbWFyZ2luLmJvdHRvbTsKICAgICAgICAgICAgdGhpcy5zdmcuYXR0cigndmlld0JveCcsIGAwIDAgJHt0b3RhbFdpZHRofSAke3RvdGFsSGVpZ2h0fWApOwogICAgICAgICAgICB0aGlzLnN2Zy5hdHRyKCdwcmVzZXJ2ZUFzcGVjdFJhdGlvJywgJ3hNaWRZTWlkJyk7CiAgICAgICAgICAgIC8vIFNldCBhIG1pbmltdW0gd2lkdGggc28gc2NhbGUgZmFjdG9yIHdhbnQgYmUgbGVzcyB0aGFuIDEKICAgICAgICAgICAgLy8gKGJ1dCBpZiBzaXplIG9mICcjY29udGFpbmVyJyBpcyBsYXJnZXIgdGhlbiB3ZSdsbCBzY2FsZSB1cAogICAgICAgICAgICAvLyBvdXIgc3ZnKS4KICAgICAgICAgICAgdGhpcy5zdmcuc3R5bGUoJ21pbi13aWR0aCcsIHRvdGFsV2lkdGggKyAncHgnKTsKICAgICAgICAgICAgdGhpcy5zdmcuc3R5bGUoJ21pbi1oZWlnaHQnLCB0b3RhbEhlaWdodCArICdweCcpOwogICAgICAgICAgICAvLyAnd2lkdGgnIGFuZCAnaGVpZ2h0JyBzdG9yZSB0aGUgd2lkdGggb2YgdGhlIHN2ZyB3aXRob3V0IG91ciBtYXJnaW5zLgogICAgICAgICAgICB0aGlzLndpZHRoID0gdG90YWxXaWR0aCAtIG1hcmdpbi5sZWZ0IC0gbWFyZ2luLnJpZ2h0OwogICAgICAgICAgICB0aGlzLmhlaWdodCA9IHRvdGFsSGVpZ2h0IC0gbWFyZ2luLnRvcCAtIG1hcmdpbi5ib3R0b207CiAgICAgICAgICAgIHRoaXMuc3ZnRyA9IHRoaXMuc3ZnCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5hdHRyKCd0cmFuc2Zvcm0nLCB0cmFuc2xhdGVTdHIobWFyZ2luLmxlZnQsIG1hcmdpbi50b3ApKTsKICAgICAgICB9CiAgICB9CiAgICAvKioKICAgICAqIE9yY2hhc3RyYXRlcyB0aGUgYmVoYXZpb3Igb2YgdGhlIHBhcmFsbGVsIGNvb3JkaW5hdGVzIHBsb3QuIFRoaXMgaXMgdGhlCiAgICAgKiBjbGFzcyB0aGF0IGNvbnN1bWVycyBvZiB0aGlzIG1vZHVsZSBzaG91bGQgdXNlLgogICAgICogVXNhZ2UgZXhhbXBsZToKICAgICAqICAgIG1hbmFnZXIgPSBuZXcgSW50ZXJhY3Rpb25NYW5hZ2VyKHN2Z1Byb3BzLCBzY2hlbWEsIHBlYWtlZFNlc3Npb25DaGFuZ2VkQ0IsCiAgICAgKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZWxlY3RlZFNlc3Npb25DaGFuZ2VkQ0IpOwogICAgICogICAgLi4uCiAgICAgKiAgICAvLyBOb3RpZnkgbWFuYWdlciBvZiBuZXcgb3B0aW9ucyBvciBzZXNzaW9uIGdyb3VwczoKICAgICAqICAgIG1hbmFnZXIub25PcHRpb25zT3JTZXNzaW9uR3JvdXBzQ2hhbmdlZChuZXdPcHRpb25zLCBuZXdTZXNzaW9uR3JvdXBzKQogICAgICogICAgLi4uCiAgICAgKiAgICAvLyBUaGlzIHdpbGwgYmUgY2FsbGVkIHdoZW4gcGVha2VkIHNlc3Npb24gY2hhbmdlZDoKICAgICAqICAgIGZ1bmN0aW9uIHBlYWtlZFNlc3Npb25DaGFuZ2VkQ0IobmV3U2Vzc2lvbkdyb3VwKSB7CiAgICAgKiAgICAgIC8vIERvIHNvbWV0aGluZyB3aXRoIHRoZSBuZXdTZXNzaW9uR3JvdXAuCiAgICAgKiAgICB9CiAgICAgKi8KICAgIGNsYXNzIEludGVyYWN0aW9uTWFuYWdlciB7CiAgICAgICAgY29uc3RydWN0b3Ioc3ZnUHJvcHMsIHNjaGVtYSwgcGVha2VkU2Vzc2lvbkdyb3VwQ2hhbmdlZENhbGxiYWNrLCBzZWxlY3RlZFNlc3Npb25DaGFuZ2VkQ2FsbGJhY2spIHsKICAgICAgICAgICAgdGhpcy5fc3ZnUHJvcHMgPSBzdmdQcm9wczsKICAgICAgICAgICAgdGhpcy5fc2NoZW1hID0gc2NoZW1hOwogICAgICAgICAgICB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBDaGFuZ2VkQ0IgPSBwZWFrZWRTZXNzaW9uR3JvdXBDaGFuZ2VkQ2FsbGJhY2s7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkU2Vzc2lvbkdyb3VwQ2hhbmdlZENCID0gc2VsZWN0ZWRTZXNzaW9uQ2hhbmdlZENhbGxiYWNrOwogICAgICAgICAgICB0aGlzLl9heGVzQ29sbGVjdGlvbiA9IG5ldyBBeGVzQ29sbGVjdGlvbihzdmdQcm9wcywgc2NoZW1hLCAKICAgICAgICAgICAgLyppbnRlcmFjdGlvbk1hbmFnZXI9Ki8gdGhpcyk7CiAgICAgICAgICAgIHRoaXMuX2xpbmVzQ29sbGVjdGlvbiA9IG5ldyBMaW5lc0NvbGxlY3Rpb24oc3ZnUHJvcHMsIHNjaGVtYSwgdGhpcy5fYXhlc0NvbGxlY3Rpb24pOwogICAgICAgICAgICB0aGlzLl9zdmdQcm9wcy5zdmcKICAgICAgICAgICAgICAgIC5vbignY2xpY2snLCAoKSA9PiB0aGlzLm9uQ2xpY2soKSkKICAgICAgICAgICAgICAgIC5vbignbW91c2Vtb3ZlIG1vdXNlZW50ZXInLCAoKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBbeCwgeV0gPSBtb3VzZSh0aGlzLl9zdmdQcm9wcy5zdmdHLm5vZGUoKSk7CiAgICAgICAgICAgICAgICB0aGlzLm9uTW91c2VNb3ZlZCh4LCB5KTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5vbignbW91c2VsZWF2ZScsICgpID0+IHRoaXMub25Nb3VzZUxlYXZlKCkpOwogICAgICAgIH0KICAgICAgICBvbkRyYWdTdGFydChjb2xJbmRleCkgewogICAgICAgICAgICB0aGlzLl9heGVzQ29sbGVjdGlvbi5kcmFnU3RhcnQoY29sSW5kZXgpOwogICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24uaGlkZUJhY2tncm91bmRMaW5lcygpOwogICAgICAgIH0KICAgICAgICBvbkRyYWcobmV3WCkgewogICAgICAgICAgICB0aGlzLl9heGVzQ29sbGVjdGlvbi5kcmFnKG5ld1gpOwogICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24ucmVjb21wdXRlQ29udHJvbFBvaW50cyhMaW5lVHlwZS5GT1JFR1JPVU5EKTsKICAgICAgICB9CiAgICAgICAgb25EcmFnRW5kKCkgewogICAgICAgICAgICB0aGlzLl9heGVzQ29sbGVjdGlvbi5kcmFnRW5kKC8qdHJhbnNpdGlvbkR1cmF0aW9uPSovIDUwMCk7CiAgICAgICAgICAgIHRoaXMuX2xpbmVzQ29sbGVjdGlvbi5yZWNvbXB1dGVDb250cm9sUG9pbnRzKExpbmVUeXBlLkZPUkVHUk9VTkQsIAogICAgICAgICAgICAvKiB0cmFuc2l0aW9uRHVyYXRpb249Ki8gNTAwKTsKICAgICAgICAgICAgd2luZG93LnNldFRpbWVvdXQoKCkgPT4gewogICAgICAgICAgICAgICAgdGhpcy5fbGluZXNDb2xsZWN0aW9uLnJlY29tcHV0ZUNvbnRyb2xQb2ludHMoTGluZVR5cGUuQkFDS0dST1VORCk7CiAgICAgICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24uc2hvd0JhY2tncm91bmRMaW5lcygpOwogICAgICAgICAgICB9LCA1MDApOwogICAgICAgIH0KICAgICAgICBvbkJydXNoQ2hhbmdlZChjb2xJbmRleCwgbmV3QnJ1c2hTZWxlY3Rpb24pIHsKICAgICAgICAgICAgdGhpcy5fYXhlc0NvbGxlY3Rpb24KICAgICAgICAgICAgICAgIC5nZXRBeGlzRm9yQ29sSW5kZXgoY29sSW5kZXgpCiAgICAgICAgICAgICAgICAuc2V0QnJ1c2hTZWxlY3Rpb24obmV3QnJ1c2hTZWxlY3Rpb24pOwogICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24ucmVjb21wdXRlRm9yZWdyb3VuZExpbmVzVmlzaWJpbGl0eSgpOwogICAgICAgIH0KICAgICAgICBvbk1vdXNlTW92ZWQobmV3WCwgbmV3WSkgewogICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24udXBkYXRlUGVha2VkU2Vzc2lvbkdyb3VwKHRoaXMuX2xpbmVzQ29sbGVjdGlvbi5maW5kQ2xvc2VzdFNlc3Npb25Hcm91cChuZXdYLCBuZXdZKSk7CiAgICAgICAgICAgIHRoaXMuX3BlYWtlZFNlc3Npb25Hcm91cENoYW5nZWRDQih0aGlzLl9saW5lc0NvbGxlY3Rpb24ucGVha2VkU2Vzc2lvbkdyb3VwSGFuZGxlKCkuc2Vzc2lvbkdyb3VwKCkpOwogICAgICAgIH0KICAgICAgICBvbk1vdXNlTGVhdmUoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5fbGluZXNDb2xsZWN0aW9uLnBlYWtlZFNlc3Npb25Hcm91cEhhbmRsZSgpLmlzTnVsbCgpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24uY2xlYXJQZWFrZWRTZXNzaW9uR3JvdXAoKTsKICAgICAgICAgICAgICAgIHRoaXMuX3BlYWtlZFNlc3Npb25Hcm91cENoYW5nZWRDQihudWxsKTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBvbkNsaWNrKCkgewogICAgICAgICAgICBpZiAodGhpcy5fbGluZXNDb2xsZWN0aW9uLnBlYWtlZFNlc3Npb25Hcm91cEhhbmRsZSgpLnNlc3Npb25Hcm91cCgpID09PQogICAgICAgICAgICAgICAgdGhpcy5fbGluZXNDb2xsZWN0aW9uLnNlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlKCkuc2Vzc2lvbkdyb3VwKCkpIHsKICAgICAgICAgICAgICAgIC8qIElmIHRoZSBzZWxlY3RlZCBzZXNzaW9uIGdyb3VwIGlzIHRoZSBzYW1lIGFzIHRoZSAicGVha2VkIiBvbmUsCiAgICAgICAgICAgICAgICAgICAgICAgY2xlYXIgdGhlIHNlbGVjdGlvbi4gKi8KICAgICAgICAgICAgICAgIHRoaXMuX2xpbmVzQ29sbGVjdGlvbi51cGRhdGVTZWxlY3RlZFNlc3Npb25Hcm91cChuZXcgU2Vzc2lvbkdyb3VwSGFuZGxlKCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgewogICAgICAgICAgICAgICAgdGhpcy5fbGluZXNDb2xsZWN0aW9uLnVwZGF0ZVNlbGVjdGVkU2Vzc2lvbkdyb3VwKHRoaXMuX2xpbmVzQ29sbGVjdGlvbi5wZWFrZWRTZXNzaW9uR3JvdXBIYW5kbGUoKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWRTZXNzaW9uR3JvdXBDaGFuZ2VkQ0IodGhpcy5fbGluZXNDb2xsZWN0aW9uLnNlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlKCkuc2Vzc2lvbkdyb3VwKCkpOwogICAgICAgIH0KICAgICAgICBvbk9wdGlvbnNPclNlc3Npb25Hcm91cHNDaGFuZ2VkKG5ld09wdGlvbnMsIG5ld1Nlc3Npb25Hcm91cHMpIHsKICAgICAgICAgICAgdGhpcy5fYXhlc0NvbGxlY3Rpb24udXBkYXRlQXhlcyhuZXdPcHRpb25zLCBuZXdTZXNzaW9uR3JvdXBzKTsKICAgICAgICAgICAgY29uc3Qgb2xkUGVha2VkU2Vzc2lvbkdyb3VwSGFuZGxlID0gdGhpcy5fbGluZXNDb2xsZWN0aW9uLnBlYWtlZFNlc3Npb25Hcm91cEhhbmRsZSgpOwogICAgICAgICAgICBjb25zdCBvbGRTZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZSA9IHRoaXMuX2xpbmVzQ29sbGVjdGlvbi5zZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZSgpOwogICAgICAgICAgICB0aGlzLl9saW5lc0NvbGxlY3Rpb24ucmVkcmF3KG5ld1Nlc3Npb25Hcm91cHMsIG5ld09wdGlvbnMuY29sb3JCeUNvbHVtbkluZGV4ICE9PSB1bmRlZmluZWQKICAgICAgICAgICAgICAgID8gbmV3T3B0aW9ucy5jb2x1bW5zW25ld09wdGlvbnMuY29sb3JCeUNvbHVtbkluZGV4XS5hYnNvbHV0ZUluZGV4CiAgICAgICAgICAgICAgICA6IG51bGwsIG5ld09wdGlvbnMubWluQ29sb3IsIG5ld09wdGlvbnMubWF4Q29sb3IpOwogICAgICAgICAgICAvLyBBIHJlZHJhdyBtYXkgY2hhbmdlIHRoZSBzZWxlY3RlZCAvIHBlYWtlZCBzZXNzaW9uIGdyb3VwLiBTbyBjYWxsIHRoZQogICAgICAgICAgICAvLyBhcHByb3ByaWF0ZSBjYWxsYmFja3MgaWYgbmVlZGVkLgogICAgICAgICAgICBpZiAoIW9sZFBlYWtlZFNlc3Npb25Hcm91cEhhbmRsZS5lcXVhbHNUbyh0aGlzLl9saW5lc0NvbGxlY3Rpb24ucGVha2VkU2Vzc2lvbkdyb3VwSGFuZGxlKCkpKSB7CiAgICAgICAgICAgICAgICB0aGlzLl9wZWFrZWRTZXNzaW9uR3JvdXBDaGFuZ2VkQ0IodGhpcy5fbGluZXNDb2xsZWN0aW9uLnBlYWtlZFNlc3Npb25Hcm91cEhhbmRsZSgpLnNlc3Npb25Hcm91cCgpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICBpZiAoIW9sZFNlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlLmVxdWFsc1RvKHRoaXMuX2xpbmVzQ29sbGVjdGlvbi5zZWxlY3RlZFNlc3Npb25Hcm91cEhhbmRsZSgpKSkgewogICAgICAgICAgICAgICAgdGhpcy5fc2VsZWN0ZWRTZXNzaW9uR3JvdXBDaGFuZ2VkQ0IodGhpcy5fbGluZXNDb2xsZWN0aW9uLnNlbGVjdGVkU2Vzc2lvbkdyb3VwSGFuZGxlKCkuc2Vzc2lvbkdyb3VwKCkpOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgICAgIHNjaGVtYSgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NjaGVtYTsKICAgICAgICB9CiAgICB9CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90ID0gY2xhc3MgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90IGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8vIFRoZSBsYXN0IHNlc3Npb24gZ3JvdXAgdGhhdCB3YXMgY2xpY2tlZCBvbiBvciBudWxsIGlmIG5vCiAgICAgICAgICAgIC8vIHNlc3Npb24gZ3JvdXAgd2FzIGNsaWNrZWQgb24geWV0LgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUgez9PYmplY3R9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwID0gbnVsbDsKICAgICAgICAgICAgLy8gVGhlIHNlc3Npb24gZ3JvdXAgcmVwcmVzZW50ZWQgYnkgdGhlIGN1cnZlICJjbG9zZXN0IiB0byB0aGUgbW91c2UKICAgICAgICAgICAgLy8gcG9pbnRlciAodGhlIGNvcnJlc3BvbmRpbmcgcGF0aCBlbGVtZW50IHdpbGwgaGF2ZSB0aGUgJ3BlYWtlZC1wYXRoJwogICAgICAgICAgICAvLyBjbGFzcykuIElmIHRoZSBjbG9zZXN0IHNlc3Npb24gZ3JvdXAgZGlzdGFuY2UgaXMgbGFyZ2VyIHRoYW4gYQogICAgICAgICAgICAvLyB0aHJlc2hvbGQsIHRoaXMgcHJvcGVydHkgd2lsbCBiZSBudWxsLgogICAgICAgICAgICAvKioKICAgICAgICAgICAgICogQHR5cGUgez9PYmplY3R9CiAgICAgICAgICAgICAqLwogICAgICAgICAgICB0aGlzLmNsb3Nlc3RTZXNzaW9uR3JvdXAgPSBudWxsOwogICAgICAgICAgICAvLyBDb3VudHMgdGhlIG51bWJlciBvZiB0aW1lcyB0aGUgZWxlbWVudCBoYXMgYmVlbiByZWRyYXduIHNpbmNlIGl0CiAgICAgICAgICAgIC8vIHdhcyBjcmVhdGVkLiBUaGlzIGlzIGluY3JlbWVudGVkIGF0IHRoZSBlbmQgb2YgYSByZWRyYXcgYW5kIGFsbG93cwogICAgICAgICAgICAvLyBpbnRlZ3JhdGlvbiB0ZXN0cyB0byB3YWl0IGZvciB0aGUgZWxlbWVudCB0byBmaW5pc2ggcmVkcmF3aW5nLgogICAgICAgICAgICB0aGlzLnJlZHJhd0NvdW50ID0gMDsKICAgICAgICB9CiAgICAgICAgX29wdGlvbnNPclNlc3Npb25Hcm91cHNDaGFuZ2VkKCkgewogICAgICAgICAgICBpZiAoIXRoaXMub3B0aW9ucykgewogICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGNvbmZpZ3VyYXRpb24gPSB0aGlzLm9wdGlvbnMuY29uZmlndXJhdGlvbjsKICAgICAgICAgICAgLy8gU2VlIGlmIHdlIG5lZWQgdG8gcmVkcmF3IGZyb20gc2NyYXRjaC4gV2UgcmVkcmF3IGZyb20gc2NyYXRjaCBpZgogICAgICAgICAgICAvLyB0aGlzIGlzIGluaXRpYWxpemF0aW9uIG9yIGlmIGNvbmZpZ3VyYXRpb24uc2NoZW1hIGhhcyBjaGFuZ2VkLgogICAgICAgICAgICBpZiAodGhpcy5faW50ZXJhY3Rpb25NYW5hZ2VyID09PSB1bmRlZmluZWQgfHwKICAgICAgICAgICAgICAgICFsb2Rhc2guaXNFcXVhbCh0aGlzLl9pbnRlcmFjdGlvbk1hbmFnZXIuc2NoZW1hKCksIGNvbmZpZ3VyYXRpb24uc2NoZW1hKSkgewogICAgICAgICAgICAgICAgLy8gUmVtb3ZlIGFueSBwcmUtZXhpc3RpbmcgRE9NIGNoaWxkcmVuIG9mIG91ciBTVkcuCiAgICAgICAgICAgICAgICBzZWxlY3QodGhpcy4kLnN2ZykKICAgICAgICAgICAgICAgICAgICAuc2VsZWN0QWxsKCcqJykKICAgICAgICAgICAgICAgICAgICAucmVtb3ZlKCk7CiAgICAgICAgICAgICAgICBjb25zdCBzdmdQcm9wcyA9IG5ldyBTVkdQcm9wZXJ0aWVzKHRoaXMuJC5zdmcsIG51bUNvbHVtbnMoY29uZmlndXJhdGlvbi5zY2hlbWEpKTsKICAgICAgICAgICAgICAgIC8vIExpc3RlbiB0byBET00gY2hhbmdlcyB1bmRlcm5lYXRoIHRoaXMuJC5zdmcsIGFuZCBhcHBseSBsb2NhbCBDU1MKICAgICAgICAgICAgICAgIC8vIHNjb3BpbmcgcnVsZXMgc28gdGhhdCBvdXIgcnVsZXMgaW4gdGhlIDxzdHlsZT4gc2VjdGlvbiBhYm92ZQogICAgICAgICAgICAgICAgLy8gd291bGQgYXBwbHkuCiAgICAgICAgICAgICAgICB0aGlzLnNjb3BlU3VidHJlZSh0aGlzLiQuc3ZnLCB0cnVlKTsKICAgICAgICAgICAgICAgIHRoaXMuX2ludGVyYWN0aW9uTWFuYWdlciA9IG5ldyBJbnRlcmFjdGlvbk1hbmFnZXIoc3ZnUHJvcHMsIGNvbmZpZ3VyYXRpb24uc2NoZW1hLCAoc2Vzc2lvbkdyb3VwKSA9PiB0aGlzLmNsb3Nlc3RTZXNzaW9uR3JvdXBDaGFuZ2VkKHNlc3Npb25Hcm91cCksIChzZXNzaW9uR3JvdXApID0+IHRoaXMuc2VsZWN0ZWRTZXNzaW9uR3JvdXBDaGFuZ2VkKHNlc3Npb25Hcm91cCkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIHRoaXMuX2NvbXB1dGVWYWxpZFNlc3Npb25Hcm91cHMoKTsKICAgICAgICAgICAgdGhpcy5faW50ZXJhY3Rpb25NYW5hZ2VyLm9uT3B0aW9uc09yU2Vzc2lvbkdyb3Vwc0NoYW5nZWQodGhpcy5vcHRpb25zLCB0aGlzLl92YWxpZFNlc3Npb25Hcm91cHMpOwogICAgICAgICAgICB0aGlzLnJlZHJhd0NvdW50Kys7CiAgICAgICAgfQogICAgICAgIGNsb3Nlc3RTZXNzaW9uR3JvdXBDaGFuZ2VkKHNlc3Npb25Hcm91cCkgewogICAgICAgICAgICB0aGlzLmNsb3Nlc3RTZXNzaW9uR3JvdXAgPSBzZXNzaW9uR3JvdXA7CiAgICAgICAgfQogICAgICAgIHNlbGVjdGVkU2Vzc2lvbkdyb3VwQ2hhbmdlZChzZXNzaW9uR3JvdXApIHsKICAgICAgICAgICAgdGhpcy5zZWxlY3RlZFNlc3Npb25Hcm91cCA9IHNlc3Npb25Hcm91cDsKICAgICAgICB9CiAgICAgICAgLy8gY29tcHV0ZXMgdmFsaWRTZXNzaW9uR3JvdXBzOiBGaWx0ZXJzIG91dCB0aGUgc2Vzc2lvbiBncm91cHMgaW4gdGhlCiAgICAgICAgLy8gc2Vzc2lvbkdyb3VwcyB0aGF0IGhhdmUgb25lIG9yIG1vcmUgb2YgdGhlaXIgY29sdW1uIHZhbHVlcyB1bmRlZmluZWQuCiAgICAgICAgLy8gSWYgc2Vzc2lvbkdyb3VwcyBpcyB1bmRlZmluZWQgc2V0cyB2YWxpZFNlc3Npb25Hcm91cHMgdG8gYmUKICAgICAgICAvLyB1bmRlZmluZWQgYXMgd2VsbC4gKFRoaXMgY2FuIGhhcHBlbiBkdXJpbmcgdGVzdGluZyB3aGVuIHdlIGRvbid0IHNldAogICAgICAgIC8vIHRoZSBzZXNzaW9uR3JvdXBzIHByb3BlcnR5KS4KICAgICAgICBfY29tcHV0ZVZhbGlkU2Vzc2lvbkdyb3VwcygpIHsKICAgICAgICAgICAgY29uc3QgdXRpbHMgPSB0Zl9ocGFyYW1zX3V0aWxzOwogICAgICAgICAgICBpZiAodGhpcy5zZXNzaW9uR3JvdXBzID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgIHRoaXMuX3ZhbGlkU2Vzc2lvbkdyb3VwcyA9IHVuZGVmaW5lZDsKICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBzY2hlbWEgPSB0aGlzLm9wdGlvbnMuY29uZmlndXJhdGlvbi5zY2hlbWE7CiAgICAgICAgICAgIHRoaXMuX3ZhbGlkU2Vzc2lvbkdyb3VwcyA9IHRoaXMuc2Vzc2lvbkdyb3Vwcy5maWx0ZXIoKHNnKSA9PiB7CiAgICAgICAgICAgICAgICBmb3IgKGxldCBjb2xJbmRleCA9IDA7IGNvbEluZGV4IDwgdXRpbHMubnVtQ29sdW1ucyhzY2hlbWEpOyArK2NvbEluZGV4KSB7CiAgICAgICAgICAgICAgICAgICAgaWYgKCF0aGlzLm9wdGlvbnMuY29uZmlndXJhdGlvbi5jb2x1bW5zVmlzaWJpbGl0eVtjb2xJbmRleF0pIHsKICAgICAgICAgICAgICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgICAgIGlmICh1dGlscy5jb2x1bW5WYWx1ZUJ5SW5kZXgoc2NoZW1hLCBzZywgY29sSW5kZXgpID09PSB1bmRlZmluZWQpIHsKICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHJldHVybiB0cnVlOwogICAgICAgICAgICB9KTsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90LnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJjb250YWluZXIiPgogICAgICA8c3ZnIGlkPSJzdmciPjwvc3ZnPgogICAgPC9kaXY+CiAgICA8c3R5bGU+CiAgICAgIDpob3N0IHsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgfQogICAgICBzdmcgewogICAgICAgIGZvbnQ6IDEwcHggc2Fucy1zZXJpZjsKICAgICAgfQoKICAgICAgLmJhY2tncm91bmQgcGF0aCB7CiAgICAgICAgZmlsbDogbm9uZTsKICAgICAgICBzdHJva2U6ICNkZGQ7CiAgICAgICAgc2hhcGUtcmVuZGVyaW5nOiBjcmlzcEVkZ2VzOwogICAgICB9CgogICAgICAuZm9yZWdyb3VuZCBwYXRoIHsKICAgICAgICBmaWxsOiBub25lOwogICAgICAgIHN0cm9rZS1vcGFjaXR5OiAwLjc7CiAgICAgICAgc3Ryb2tlLXdpZHRoOiAxOwogICAgICB9CgogICAgICAvKiBXaWxsIGJlIHNldCBvbiBmb3JlZ3JvdW5kIHBhdGhzIHRoYXQgYXJlIG5vdCAiY29udGFpbmVkIiBpbiB0aGUgY3VycmVudAogICAgICAgICBheGVzIGJydXNoZXMuIElmIG5vIGJydXNoZXMgYXJlIHNldCwgbm8gcGF0aCB3aWxsIGhhdmUgdGhpcyBjbGFzcy4gKi8KICAgICAgLmZvcmVncm91bmQgLmludmlzaWJsZS1wYXRoIHsKICAgICAgICBkaXNwbGF5OiBub25lOwogICAgICB9CgogICAgICAvKiBTdHlsZSBmb3IgdGhlIHBhdGggY2xvc2VzdCB0byB0aGUgbW91c2UgcG9pbnRlciAodHlwaWNhbGx5IHdpbGwgYmVjb21lCiAgICAgIHRoZSBzZWxlY3RlZCBwYXRoIHdoZW4gdGhlIHVzZXIgY2xpY2tzKS4gKi8KICAgICAgLmZvcmVncm91bmQgLnBlYWtlZC1wYXRoIHsKICAgICAgICBzdHJva2Utd2lkdGg6IDM7CiAgICAgIH0KCiAgICAgIC8qIFRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgcGF0aCBjbGFzcy4gV2UgdXNlICFpbXBvcnRhbnQgdG8gb3ZlcnJpZGUgdGhlCiAgICAgICAgIGlubGluZSBzdHlsZSB0aGF0IHNldHMgdGhlIHJlZ3VsYXIgY29sb3Igb2YgYSBwYXRoLiAqLwogICAgICAuZm9yZWdyb3VuZCAuc2VsZWN0ZWQtcGF0aCB7CiAgICAgICAgc3Ryb2tlLXdpZHRoOiAzICFpbXBvcnRhbnQ7CiAgICAgICAgc3Ryb2tlOiAjMGYwICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgICNjb250YWluZXIgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgfQoKICAgICAgc3ZnIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgIH0KCiAgICAgIC5heGlzIHRleHQgewogICAgICAgIHRleHQtc2hhZG93OiAwIDFweCAwICNmZmYsIDFweCAwIDAgI2ZmZiwgMCAtMXB4IDAgI2ZmZiwgLTFweCAwIDAgI2ZmZjsKICAgICAgICBmaWxsOiAjMDAwOwogICAgICAgIGN1cnNvcjogbW92ZTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90LnByb3RvdHlwZSwgInNlc3Npb25Hcm91cHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1Bsb3QucHJvdG90eXBlLCAib3B0aW9ucyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90LnByb3RvdHlwZSwgInNlbGVjdGVkU2Vzc2lvbkdyb3VwIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgICAgICBub3RpZnk6IHRydWUsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1Bsb3QucHJvdG90eXBlLCAiY2xvc2VzdFNlc3Npb25Hcm91cCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzUGxvdC5wcm90b3R5cGUsICJyZWRyYXdDb3VudCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1Bsb3QucHJvdG90eXBlLCAiX3ZhbGlkU2Vzc2lvbkdyb3VwcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzUGxvdC5wcm90b3R5cGUsICJfaW50ZXJhY3Rpb25NYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ29wdGlvbnMuKicsICdzZXNzaW9uR3JvdXBzLionKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzUGxvdC5wcm90b3R5cGUsICJfb3B0aW9uc09yU2Vzc2lvbkdyb3Vwc0NoYW5nZWQiLCBudWxsKTsKICAgIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzUGxvdCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhwYXJhbXMtcGFyYWxsZWwtY29vcmRzLXBsb3QnKQogICAgXSwgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNQbG90KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogVGhlcmUgYXJlIDMgZWxlbWVudHMgaW52b2x2ZWQgaW4gdGhlIHBhcmFsbGVsIGNvb3JkaW5hdGVzIHZpc3VhbGl6YXRpb246CiAgICAgKgogICAgICogMS4gPHRmLWhwYXJhbXMtcGFyYWxsZWwtY29vcmRzLXBsb3Q+CiAgICAgKiAgIFJlbmRlcnMgdGhlIGFjdHVhbCBwYXJhbGxlbCBjb29yZGluYXRlIHBsb3QuIFNlZSB0aGUgY29tbWVudHMgaW4gdGhlCiAgICAgKiAgIGNvZGUgZm9yIHRoYXQgZWxlbWVudCBmb3IgbW9yZSBkZXRhaWxzLgogICAgICogMi4gPHRmLWhwYXJhbXMtc2NhbGUtYW5kLWNvbG9yLWNvbnRyb2xzPgogICAgICogICBBIGNvbnRyb2wgcGFuZWwgZm9yIGNvbmZpZ3VyaW5nIHRoZSBiZWhhdmlvciBvZiB0aGUgcGxvdCAoZS5nLiBzY2FsZQogICAgICogICBvZiBlYWNoIGF4aXMsIGNvbG9ybWFwLCBldGMuKQogICAgICogMy4gPHRmLWhwYXJhbXMtcGFyYWxsZWwtY29vcmRzLXZpZXc+CiAgICAgKiAgIFRoZSBjb250YWluZXIgZWxlbWVudCBmb3IgdGhlIGFib3ZlIDIgZWxlbWVudHMuCiAgICAgKi8KICAgIGxldCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcgPSBjbGFzcyBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgX2Nsb3Nlc3RPclNlbGVjdGVkKGNsb3Nlc3RTZXNzaW9uR3JvdXAsIHNlbGVjdGVkU2Vzc2lvbkdyb3VwKSB7CiAgICAgICAgICAgIGlmIChjbG9zZXN0U2Vzc2lvbkdyb3VwICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY2xvc2VzdFNlc3Npb25Hcm91cDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gc2VsZWN0ZWRTZXNzaW9uR3JvdXA7CiAgICAgICAgfQogICAgfTsKICAgIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzVmlldy50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPCEtLSBDb250cm9scyBiZWhhdmlvciBvZiBwYXJhbGxlbCBjb29yZGluYXRlcyBwbG90CiAgICAgICAgIG91dHB1dHMgc2V0IG9wdGlvbnMgdG8gdGhlIF9vcHRpb25zIHByb3BlcnR5LgogICAgICAtLT4KICAgIDxocGFyYW1zLXNwbGl0LWxheW91dCBvcmllbnRhdGlvbj0idmVydGljYWwiPgogICAgICA8IS0tIFRoZSBzY2FsZSBhbmQgY29sb3IgY29udHJvbHMuIC0tPgogICAgICA8dGYtaHBhcmFtcy1zY2FsZS1hbmQtY29sb3ItY29udHJvbHMKICAgICAgICBpZD0iY29udHJvbHMiCiAgICAgICAgc2xvdD0iY29udGVudCIKICAgICAgICBjbGFzcz0ic2VjdGlvbiIKICAgICAgICBjb25maWd1cmF0aW9uPSJbW2NvbmZpZ3VyYXRpb25dXSIKICAgICAgICBzZXNzaW9uLWdyb3Vwcz0iW1tzZXNzaW9uR3JvdXBzXV0iCiAgICAgICAgb3B0aW9ucz0ie3tfb3B0aW9uc319IgogICAgICA+CiAgICAgIDwvdGYtaHBhcmFtcy1zY2FsZS1hbmQtY29sb3ItY29udHJvbHM+CiAgICAgIDwhLS0gVGhlIGFjdHVhbCBwYXJhbGxlbCBjb29yZGluYXRlcyBwbG90IC0tPgogICAgICA8dGYtaHBhcmFtcy1wYXJhbGxlbC1jb29yZHMtcGxvdAogICAgICAgIGlkPSJwbG90IgogICAgICAgIHNsb3Q9ImNvbnRlbnQiCiAgICAgICAgY2xhc3M9InNlY3Rpb24iCiAgICAgICAgc2Vzc2lvbi1ncm91cHM9Iltbc2Vzc2lvbkdyb3Vwc11dIgogICAgICAgIHNlbGVjdGVkLXNlc3Npb24tZ3JvdXA9Int7X3NlbGVjdGVkR3JvdXB9fSIKICAgICAgICBjbG9zZXN0LXNlc3Npb24tZ3JvdXA9Int7X2Nsb3Nlc3RHcm91cH19IgogICAgICAgIG9wdGlvbnM9IltbX29wdGlvbnNdXSIKICAgICAgPgogICAgICA8L3RmLWhwYXJhbXMtcGFyYWxsZWwtY29vcmRzLXBsb3Q+CiAgICAgIDx0Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtdmFsdWVzCiAgICAgICAgaWQ9InZhbHVlcyIKICAgICAgICBzbG90PSJjb250ZW50IgogICAgICAgIGNsYXNzPSJzZWN0aW9uIgogICAgICAgIHZpc2libGUtc2NoZW1hPSJbW2NvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYV1dIgogICAgICAgIHNlc3Npb24tZ3JvdXA9IltbX2Nsb3Nlc3RPclNlbGVjdGVkKAogICAgICAgICAgICAgICAgICAgICAgICAgICAgIF9jbG9zZXN0R3JvdXAsIF9zZWxlY3RlZEdyb3VwKV1dIgogICAgICA+CiAgICAgIDwvdGYtaHBhcmFtcy1zZXNzaW9uLWdyb3VwLXZhbHVlcz4KICAgICAgPHRmLWhwYXJhbXMtc2Vzc2lvbi1ncm91cC1kZXRhaWxzCiAgICAgICAgaWQ9ImRldGFpbHMiCiAgICAgICAgc2xvdD0iY29udGVudCIKICAgICAgICBjbGFzcz0ic2VjdGlvbiIKICAgICAgICBiYWNrZW5kPSJbW2JhY2tlbmRdXSIKICAgICAgICBleHBlcmltZW50LW5hbWU9IltbZXhwZXJpbWVudE5hbWVdXSIKICAgICAgICBzZXNzaW9uLWdyb3VwPSJbW19zZWxlY3RlZEdyb3VwXV0iCiAgICAgICAgdmlzaWJsZS1zY2hlbWE9IltbY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hXV0iCiAgICAgID4KICAgICAgPC90Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtZGV0YWlscz4KICAgIDwvaHBhcmFtcy1zcGxpdC1sYXlvdXQ+CgogICAgPHN0eWxlPgogICAgICAuc2VjdGlvbiB7CiAgICAgICAgcGFkZGluZzogMTBweDsKICAgICAgfQogICAgICAjdmFsdWVzIHsKICAgICAgICBoZWlnaHQ6IDExNXB4OwogICAgICB9CiAgICAgICNkZXRhaWxzIHsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgbWF4LWhlaWdodDogZml0LWNvbnRlbnQ7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zUGFyYWxsZWxDb29yZHNWaWV3LnByb3RvdHlwZSwgImJhY2tlbmQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcucHJvdG90eXBlLCAiZXhwZXJpbWVudE5hbWUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcucHJvdG90eXBlLCAiY29uZmlndXJhdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IEFycmF5IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcucHJvdG90eXBlLCAic2Vzc2lvbkdyb3VwcyIsIHZvaWQgMCk7CiAgICBUZkhwYXJhbXNQYXJhbGxlbENvb3Jkc1ZpZXcgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ocGFyYW1zLXBhcmFsbGVsLWNvb3Jkcy12aWV3JykKICAgIF0sIFRmSHBhcmFtc1BhcmFsbGVsQ29vcmRzVmlldyk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIEEgZDMtYmFzZWQgc2NhdHRlciBwbG90IG1hdHJpeCB2aXN1YWxpemF0aW9uIGNvbXBvbmVudC4KICAgICAqIFRoaXMgY29tcG9uZW50IHJlbmRlcnMgdGhlIGFjdHVhbCBwbG90czsgdGhlICJjb250cm9scyIgcGFydCBvZiB0aGUKICAgICAqIHZpc3VhbGl6YXRpb24gYXJlIHJlbmRlcmVkIGJ5IHRmLWhwYXJhbXMtc2NhbGUtYW5kLWNvbG9yLWNvbnRyb2xzLgogICAgICoKICAgICAqIFRPRE8oZXJleik6IFRoZSBsb2dpYyBmb3IgY29tcHV0aW5nIHRoZSBudW1iZXIgb2YgdGlja3Mgc28gdGhhdCB0aWNrIGxhYmVscwogICAgICogZG8gbm90IG92ZXJsYXAgaXMgaWdub3JlZCwgZm9yIHNvbWUgcmVhc29uLCB3aGVuIHdlIHNldCBjb21waWxlPVRydWUgaW4KICAgICAqIHRoZSB2dWxjYW5pemF0aW9uIGJ1aWxkIHN0ZXAuIEZpZ3VyZSBvdXQgd2h5LgogICAgICovCiAgICBsZXQgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90ID0gY2xhc3MgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90IGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIC8vIFRoZSBsYXN0IHNlc3Npb24gZ3JvdXAgdGhhdCB3YXMgY2xpY2tlZCBvbiBvciBudWxsIGlmIG5vCiAgICAgICAgICAgIC8vIHNlc3Npb24gZ3JvdXAgd2FzIGNsaWNrZWQgb24geWV0LgogICAgICAgICAgICB0aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwID0gbnVsbDsKICAgICAgICAgICAgLy8gVGhlIHNlc3Npb24gZ3JvdXAgcmVwcmVzZW50ZWQgYnkgdGhlIG1hcmtlciAiY2xvc2VzdCIgdG8gdGhlIG1vdXNlCiAgICAgICAgICAgIC8vIHBvaW50ZXIuIElmIHRoZSBjbG9zZXN0IHNlc3Npb24gZ3JvdXAgZGlzdGFuY2UgaXMgbGFyZ2VyIHRoYW4gYQogICAgICAgICAgICAvLyB0aHJlc2hvbGQsIHRoaXMgcHJvcGVydHkgd2lsbCBiZSBudWxsLgogICAgICAgICAgICB0aGlzLmNsb3Nlc3RTZXNzaW9uR3JvdXAgPSBudWxsOwogICAgICAgICAgICAvLyBUaGUgPGRpdj4gZWxlbWVudCB3aXRoIGlkICJjb250YWluZXIiLgogICAgICAgICAgICB0aGlzLl9jb250YWluZXIgPSBudWxsOwogICAgICAgICAgICAvLyBBIEQzIHNlbGVjdGlvbiBjb250YWluaW5nIGp1c3QgdGhlIHJvb3QgPHN2Zz4gZWxlbWVudC4KICAgICAgICAgICAgdGhpcy5fc3ZnID0gbnVsbDsKICAgICAgICAgICAgdGhpcy53aWR0aCA9IDA7CiAgICAgICAgICAgIHRoaXMuaGVpZ2h0ID0gMDsKICAgICAgICAgICAgLy8gVGhlIGluZGV4IG9mIHRoZSBjZWxsIGNvbnRhaW5pbmcgYSBicnVzaCBzZWxlY3Rpb24gYXMgYW4gYXJyYXkKICAgICAgICAgICAgLy8gb2YgdGhlIGZvcm0gW2NvbCwgbWV0cmljXSBvciBudWxsIGlmIG5vIGNlbGwgaGFzIGFuIGFjdGl2ZSBicnVzaAogICAgICAgICAgICAvLyBzZWxlY3Rpb24uCiAgICAgICAgICAgIHRoaXMuX2JydXNoZWRDZWxsSW5kZXggPSBudWxsOwogICAgICAgICAgICAvLyBUaGUgdGhlIGFjdGl2ZSBicnVzaCBzZWxlY3Rpb24gaW4gdGhlIGZvcm0KICAgICAgICAgICAgLy8gW1t4MCx5MF0sW3gxLHkxXV0gd2hlcmUgdGhlIGNvb3JkaW5hdGVzIGFyZSByZWxhdGl2ZSB0byB0aGUgY2VsbAogICAgICAgICAgICAvLyBpbmRleGVkIGJ5IF9icnVzaGVkQ2VsbEluZGV4LiBTZXQgdG8gbnVsbCwgaWYgdGhlcmUgaXMgbm8gYWN0aXZlCiAgICAgICAgICAgIC8vIGJydXNoLgogICAgICAgICAgICB0aGlzLl9icnVzaFNlbGVjdGlvbiA9IG51bGw7CiAgICAgICAgfQogICAgICAgIHJlYWR5KCkgewogICAgICAgICAgICBzdXBlci5yZWFkeSgpOwogICAgICAgICAgICB0aGlzLl9jb250YWluZXIgPSB0aGlzLiRbJ2NvbnRhaW5lciddOwogICAgICAgICAgICB0aGlzLl9zdmcgPSBzZWxlY3QodGhpcy4kWydzdmcnXSk7CiAgICAgICAgICAgIHRoaXMuX3JlZHJhdygpOwogICAgICAgIH0KICAgICAgICBfc2Vzc2lvbkdyb3Vwc0NoYW5nZWQoKSB7CiAgICAgICAgICAgIGlmICh0aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAvLyBUcnkgdG8ga2VlcCB0aGUgc2VsZWN0ZWQgc2Vzc2lvbiBncm91cDogaWYgdGhlIG5ldyBzZXNzaW9uR3JvdXBzCiAgICAgICAgICAgICAgICAvLyBhcnJheSBoYXMgYSBzZXNzaW9uR3JvdXAgd2l0aCB0aGUgc2FtZSBuYW1lIGFzIHRoZSBvbmUgdGhhdCB3YXMKICAgICAgICAgICAgICAgIC8vIHNlbGVjdGVkIGJlZm9yZSwgc2VsZWN0IGl0LgogICAgICAgICAgICAgICAgdGhpcy5zZWxlY3RlZFNlc3Npb25Hcm91cCA9CiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbkdyb3VwV2l0aE5hbWUodGhpcy5zZXNzaW9uR3JvdXBzLCB0aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwLm5hbWUpIHx8IG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fcmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIF92aXNpYmxlU2NoZW1hQ2hhbmdlZCgpIHsKICAgICAgICAgICAgdGhpcy5fYnJ1c2hlZENlbGxJbmRleCA9IG51bGw7CiAgICAgICAgICAgIHRoaXMuX2JydXNoU2VsZWN0aW9uID0gbnVsbDsKICAgICAgICAgICAgdGhpcy5fcmVkcmF3KCk7CiAgICAgICAgfQogICAgICAgIC8vIFJlZHJhd3MgdGhlIHBsb3QuCiAgICAgICAgX3JlZHJhdygpIHsKICAgICAgICAgICAgdGhpcy5kZWJvdW5jZSgnX3JlZHJhdycsICgpID0+IHsKICAgICAgICAgICAgICAgIGNvbnN0IHV0aWxzID0gdGZfaHBhcmFtc191dGlsczsKICAgICAgICAgICAgICAgIGNvbnN0IFBMT1RfTUlOX1dJRFRIID0gMTIwMDsKICAgICAgICAgICAgICAgIGNvbnN0IFBMT1RfTUlOX0hFSUdIVCA9IDAuNCAqIFBMT1RfTUlOX1dJRFRIOwogICAgICAgICAgICAgICAgY29uc3QgQ0VMTF9NSU5fV0lEVEggPSAxNTA7CiAgICAgICAgICAgICAgICBjb25zdCBDRUxMX01JTl9IRUlHSFQgPSAwLjc1ICogQ0VMTF9NSU5fV0lEVEg7CiAgICAgICAgICAgICAgICB0aGlzLndpZHRoID0gTWF0aC5tYXgoQ0VMTF9NSU5fV0lEVEggKiB1dGlscy5udW1WaXNpYmxlQ29sdW1ucyh0aGlzLnZpc2libGVTY2hlbWEpLCBQTE9UX01JTl9XSURUSCk7CiAgICAgICAgICAgICAgICB0aGlzLmhlaWdodCA9IE1hdGgubWF4KENFTExfTUlOX0hFSUdIVCAqIHV0aWxzLm51bVZpc2libGVNZXRyaWNzKHRoaXMudmlzaWJsZVNjaGVtYSksIFBMT1RfTUlOX0hFSUdIVCk7CiAgICAgICAgICAgICAgICB0aGlzLl9jb250YWluZXIuc3R5bGUud2lkdGggPSB0aGlzLndpZHRoICsgJ3B4JzsKICAgICAgICAgICAgICAgIHRoaXMuX2NvbnRhaW5lci5zdHlsZS5oZWlnaHQgPSB0aGlzLmhlaWdodCArICdweCc7CiAgICAgICAgICAgICAgICB0aGlzLl9zdmcuYXR0cignd2lkdGgnLCB0aGlzLndpZHRoKS5hdHRyKCdoZWlnaHQnLCB0aGlzLmhlaWdodCk7CiAgICAgICAgICAgICAgICAvLyBEZWxldGUgYWxsIGVsZW1lbnRzIGluIHRoZSBzdmcgc3VidHJlZQogICAgICAgICAgICAgICAgdGhpcy5fc3ZnLnNlbGVjdEFsbCgnZycpLnJlbW92ZSgpOwogICAgICAgICAgICAgICAgLy8gRHJhdy4KICAgICAgICAgICAgICAgIHRoaXMuX2RyYXcoKTsKICAgICAgICAgICAgfSwgMTAwKTsKICAgICAgICB9CiAgICAgICAgLy8gQ3JlYXRlcyB0aGUgRE9NIGVsZW1lbnRzIGNvbXByaXNpbmcgdGhlIHNjYXR0ZXItcGxvdC1tYXRyaXggcGxvdCBhbmQKICAgICAgICAvLyByZWdpc3RlcnMgZXZlbnQgaGFuZGxlcnMgdG8gaGFuZGxlIHVzZXIgYWN0aW9ucy4KICAgICAgICBfZHJhdygpIHsKICAgICAgICAgICAgY29uc3QgdXRpbHMgPSB0Zl9ocGFyYW1zX3V0aWxzOwogICAgICAgICAgICBjb25zdCBfdGhpcyA9IHRoaXM7CiAgICAgICAgICAgIGlmICghdGhpcy5zZXNzaW9uR3JvdXBzIHx8CiAgICAgICAgICAgICAgICB0aGlzLnNlc3Npb25Hcm91cHMubGVuZ3RoID09IDAgfHwKICAgICAgICAgICAgICAgICF0aGlzLnZpc2libGVTY2hlbWEgfHwKICAgICAgICAgICAgICAgIHRoaXMudmlzaWJsZVNjaGVtYS5tZXRyaWNJbmZvcy5sZW5ndGggPT0gMCkgewogICAgICAgICAgICAgICAgLy8gSWYgdGhlcmUncyBubyBtZXRyaWNzIG9yIHNlc3Npb24gZ3JvdXBzLiBUaGVyZSdzIG5vdGhpbmcgdG8gZHJhdy4KICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBBbiBhcnJheSBjb250YWluaW5nIHRoZSB2aXNpYmxlU2NoZW1hLWNvbHVtbnMgKGhwYXJhbXMgZm9sbG93ZWQgYnkKICAgICAgICAgICAgLy8gbWV0cmljcykgaW5kaWNlcy4gVGhlc2UgaW5kZXggdGhlIGNvbHVtbnMgb2YgdGhlIHNjYXR0ZXIgcGxvdCBtYXRyaXguCiAgICAgICAgICAgIGNvbnN0IGNvbHMgPSBzZXF1ZW5jZSh1dGlscy5udW1WaXNpYmxlQ29sdW1ucyhfdGhpcy52aXNpYmxlU2NoZW1hKSk7CiAgICAgICAgICAgIC8vIEFuIGFycmF5IGNvbnRhaW5pbmcgdGhlIG1ldHJpYyBpbmRpY2VzLiBUaGVzZSBpbmRleCB0aGUgcm93cyBvZiB0aGUKICAgICAgICAgICAgLy8gc2NhdHRlciBwbG90IG1hdHJpeC4KICAgICAgICAgICAgY29uc3QgbWV0cmljcyA9IHNlcXVlbmNlKHV0aWxzLm51bVZpc2libGVNZXRyaWNzKF90aGlzLnZpc2libGVTY2hlbWEpKTsKICAgICAgICAgICAgLy8gVGhlIG1hcmdpbiBpbiBwaXhlbHMgZnJvbSB0aGUgbGVmdCB0byBsZWF2ZSBmb3IgdGhlIHktYXhpcyB0ZXh0CiAgICAgICAgICAgIC8vICh0aWNrIHZhbHVlcyBhbmQgeC1heGlzIGxhYmVsKS4KICAgICAgICAgICAgY29uc3QgeUF4aXNUZXh0TWFyZ2luID0gODA7CiAgICAgICAgICAgIC8vIFRoZSBtYXJnaW4gaW4gcGl4ZWxzIGZyb20gdGhlIGJvdHRvbSB0byBsZWF2ZSBmb3IgdGhlIHgtYXhpcyB0ZXh0CiAgICAgICAgICAgIC8vICh0aWNrIHZhbHVlcyBhbmQgeC1heGlzIGxhYmVsKS4KICAgICAgICAgICAgY29uc3QgeEF4aXNUZXh0TWFyZ2luID0gNTA7CiAgICAgICAgICAgIC8vIEVhY2ggY2VsbCBpbiB0aGUgc2NhdHRlciBwbG90IG1hdHJpeCBoYXMgYSByZWN0YW5ndWxhciBmcmFtZS4KICAgICAgICAgICAgLy8gVGhlIG1hcmdpbiBpbiBwaXhlbHMgdG8gdXNlIGJldHdlZW4gdGhlIGNlbGwgYm91bmRhcnkgYW5kIGl0cyBmcmFtZS4KICAgICAgICAgICAgY29uc3QgZnJhbWVNYXJnaW4gPSA1OwogICAgICAgICAgICAvLyBjZWxsWChjb2wpLCBjZWxsWShtZXRyaWMpIGFyZSB0aGUgc3ZnIGNvb3JkaW5hdGVzIG9mIHRoZSB1cHBlcgogICAgICAgICAgICAvLyBsZWZ0IGNvcm5lciBvZiB0aGUgYm91bmRhcnkgb2YgdGhlIGNlbGwgaW5kZXhlZCBieSAoY29sLCBtZXRyaWMpLgogICAgICAgICAgICBjb25zdCBjZWxsWCA9IGJhbmQoKQogICAgICAgICAgICAgICAgLmRvbWFpbihjb2xzKQogICAgICAgICAgICAgICAgLnJhbmdlKFt5QXhpc1RleHRNYXJnaW4gKyBmcmFtZU1hcmdpbiwgdGhpcy53aWR0aCAtIDEgLSBmcmFtZU1hcmdpbl0pCiAgICAgICAgICAgICAgICAucGFkZGluZ0lubmVyKDAuMSk7CiAgICAgICAgICAgIGNvbnN0IGNlbGxZID0gYmFuZCgpCiAgICAgICAgICAgICAgICAuZG9tYWluKG1ldHJpY3MpCiAgICAgICAgICAgICAgICAucmFuZ2UoW3RoaXMuaGVpZ2h0IC0gMSAtIGZyYW1lTWFyZ2luIC0geEF4aXNUZXh0TWFyZ2luLCBmcmFtZU1hcmdpbl0pCiAgICAgICAgICAgICAgICAucGFkZGluZ0lubmVyKDAuMSk7CiAgICAgICAgICAgIGNvbnN0IGNlbGxXaWR0aCA9IGNlbGxYLmJhbmR3aWR0aCgpOwogICAgICAgICAgICBjb25zdCBjZWxsSGVpZ2h0ID0gY2VsbFkuYmFuZHdpZHRoKCk7CiAgICAgICAgICAgIC8vIHhDb29yZHNbY29sXShjb2xWYWx1ZSksIHlDb29yZHNbbWV0cmljXShtZXRyaWNWYWx1ZSkgYXJlIHRoZQogICAgICAgICAgICAvLyBjb29yZGluYXRlcyBvZiB0aGUgbWFya2VyIHJlcHJlc2VudGluZyB0aGUgZGF0YQogICAgICAgICAgICAvLyAoY29sVmFsdWUsIG1ldHJpY1ZhbHVlKSBpbiB0aGUgY2VsbCBpbmRleGVkIGJ5IChjb2wsIG1ldHJpYykuCiAgICAgICAgICAgIC8vIFRoZSBjb29yZGluYXRlcyBhcmUgcmVsYXRpdmUgdG8gdGhlIGNlbGwgYm91bmRhcnkncyB1cHBlcgogICAgICAgICAgICAvLyBsZWZ0IGNvcm5lci4KICAgICAgICAgICAgY29uc3QgeENvb3JkcyA9IGNvbHMubWFwKChjKSA9PiBfdGhpcy5fY2VsbFNjYWxlKGMsIFswLCBjZWxsV2lkdGggLSAxXSkpOwogICAgICAgICAgICBjb25zdCB5Q29vcmRzID0gbWV0cmljcy5tYXAoKG0pID0+IF90aGlzLl9jZWxsU2NhbGUobSArIHV0aWxzLm51bVZpc2libGVIUGFyYW1zKF90aGlzLnZpc2libGVTY2hlbWEpLCBbCiAgICAgICAgICAgICAgICBjZWxsSGVpZ2h0IC0gMSwKICAgICAgICAgICAgICAgIDAsCiAgICAgICAgICAgIF0pKTsKICAgICAgICAgICAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCiAgICAgICAgICAgIC8vIERyYXcgYXhlcy4KICAgICAgICAgICAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCiAgICAgICAgICAgIC8vIFgtQXhlcyBhbmQgbGFiZWxzLgogICAgICAgICAgICBjb25zdCB4QXhlc0cgPSB0aGlzLl9zdmcKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJy54LWF4aXMnKQogICAgICAgICAgICAgICAgLmRhdGEoY29scykKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCd4LWF4aXMnLCB0cnVlKQogICAgICAgICAgICAgICAgLmF0dHIoJ3RyYW5zZm9ybScsIChjb2wpID0+IHV0aWxzLnRyYW5zbGF0ZVN0cihjZWxsWChjb2wpLCAwKSk7CiAgICAgICAgICAgIGZ1bmN0aW9uIHhBeGlzQ2xpcFBhdGhJZChjb2wpIHsKICAgICAgICAgICAgICAgIHJldHVybiAneC1heGlzLWNsaXAtcGF0aC0nICsgY29sOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGZ1bmN0aW9uIHhMYWJlbENsaXBQYXRoSWQoY29sKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gJ3gtbGFiZWwtY2xpcC1wYXRoLScgKyBjb2w7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgeEF4ZXNHCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdjbGlwUGF0aCcpCiAgICAgICAgICAgICAgICAuYXR0cignaWQnLCB4QXhpc0NsaXBQYXRoSWQpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdyZWN0JykKICAgICAgICAgICAgICAgIC5hdHRyKCd4JywgLWZyYW1lTWFyZ2luKQogICAgICAgICAgICAgICAgLmF0dHIoJ3knLCAwKQogICAgICAgICAgICAgICAgLmF0dHIoJ3dpZHRoJywgY2VsbFdpZHRoICsgMiAqIGZyYW1lTWFyZ2luKQogICAgICAgICAgICAgICAgLmF0dHIoJ2hlaWdodCcsIF90aGlzLmhlaWdodCAtIHhBeGlzVGV4dE1hcmdpbiAvIDIpOwogICAgICAgICAgICB4QXhlc0cKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2NsaXBQYXRoJykKICAgICAgICAgICAgICAgIC5hdHRyKCdpZCcsIHhMYWJlbENsaXBQYXRoSWQpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdyZWN0JykKICAgICAgICAgICAgICAgIC5hdHRyKCd4JywgMCkKICAgICAgICAgICAgICAgIC5hdHRyKCd5JywgX3RoaXMuaGVpZ2h0IC0geEF4aXNUZXh0TWFyZ2luIC8gMikKICAgICAgICAgICAgICAgIC5hdHRyKCd3aWR0aCcsIGNlbGxXaWR0aCkKICAgICAgICAgICAgICAgIC5hdHRyKCdoZWlnaHQnLCB4QXhpc1RleHRNYXJnaW4gLyAyKTsKICAgICAgICAgICAgeEF4ZXNHCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5hdHRyKCdjbGlwLXBhdGgnLCAoY29sKSA9PiAndXJsKCMnICsgeEF4aXNDbGlwUGF0aElkKGNvbCkgKyAnKScpCiAgICAgICAgICAgICAgICAuZWFjaChmdW5jdGlvbiAoY29sKSB7CiAgICAgICAgICAgICAgICBzZWxlY3QodGhpcykuY2FsbChkcmF3QXhpcywgYXhpc0JvdHRvbSh4Q29vcmRzW2NvbF0pCiAgICAgICAgICAgICAgICAgICAgLnRpY2tTaXplKF90aGlzLmhlaWdodCAtIHhBeGlzVGV4dE1hcmdpbiksIGNlbGxXaWR0aCwgCiAgICAgICAgICAgICAgICAvKiBtaW5MYWJlbFNpemUgKi8gNDAsIF90aGlzLm9wdGlvbnMuY29sdW1uc1tjb2xdLnNjYWxlKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIC8vIERyYXcgYSBsYWJlbCBmb3IgZWFjaCBheGlzLgogICAgICAgICAgICB4QXhlc0cKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ3gtYXhpcy1sYWJlbCcsIHRydWUpCiAgICAgICAgICAgICAgICAuYXR0cignY2xpcC1wYXRoJywgKGNvbCkgPT4gJ3VybCgjJyArIHhMYWJlbENsaXBQYXRoSWQoY29sKSArICcpJykKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3RleHQnKQogICAgICAgICAgICAgICAgLmF0dHIoJ3RleHQtYW5jaG9yJywgJ21pZGRsZScpCiAgICAgICAgICAgICAgICAuYXR0cigneCcsIGNlbGxXaWR0aCAvIDIpCiAgICAgICAgICAgICAgICAuYXR0cigneScsIF90aGlzLmhlaWdodCAtIDEgLSB4QXhpc1RleHRNYXJnaW4gLyA0KQogICAgICAgICAgICAgICAgLnRleHQoKGNvbCkgPT4gdXRpbHMuc2NoZW1hVmlzaWJsZUNvbHVtbk5hbWUoX3RoaXMudmlzaWJsZVNjaGVtYSwgY29sKSkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3RpdGxlJykgLy8gU2hvdyBmdWxsIG5hbWUgYXMgYSB0b29sdGlwLgogICAgICAgICAgICAgICAgLnRleHQoKGNvbCkgPT4gdXRpbHMuc2NoZW1hVmlzaWJsZUNvbHVtbk5hbWUoX3RoaXMudmlzaWJsZVNjaGVtYSwgY29sKSk7CiAgICAgICAgICAgIC8vIFktQXhlcyBhbmQgbGFiZWxzLgogICAgICAgICAgICBjb25zdCB5QXhlc0cgPSB0aGlzLl9zdmcKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJy55LWF4aXMnKQogICAgICAgICAgICAgICAgLmRhdGEobWV0cmljcykKICAgICAgICAgICAgICAgIC5lbnRlcigpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCd5LWF4aXMnLCB0cnVlKQogICAgICAgICAgICAgICAgLmF0dHIoJ3RyYW5zZm9ybScsIChtZXRyaWMpID0+IHV0aWxzLnRyYW5zbGF0ZVN0cihfdGhpcy53aWR0aCAtIDEsIGNlbGxZKG1ldHJpYykpKTsKICAgICAgICAgICAgZnVuY3Rpb24geUF4aXNDbGlwUGF0aElkKG1ldHJpYykgewogICAgICAgICAgICAgICAgcmV0dXJuICd5LWF4aXMtY2xpcC1wYXRoLScgKyBtZXRyaWM7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZnVuY3Rpb24geUxhYmVsQ2xpcFBhdGhJZChtZXRyaWMpIHsKICAgICAgICAgICAgICAgIHJldHVybiAneS1sYWJlbC1jbGlwLXBhdGgtJyArIG1ldHJpYzsKICAgICAgICAgICAgfQogICAgICAgICAgICB5QXhlc0cKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2NsaXBQYXRoJykKICAgICAgICAgICAgICAgIC5hdHRyKCdpZCcsIHlBeGlzQ2xpcFBhdGhJZCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3JlY3QnKQogICAgICAgICAgICAgICAgLmF0dHIoJ3gnLCAtKF90aGlzLndpZHRoIC0geUF4aXNUZXh0TWFyZ2luIC8gMiAtIDEpKQogICAgICAgICAgICAgICAgLmF0dHIoJ3knLCAtZnJhbWVNYXJnaW4pCiAgICAgICAgICAgICAgICAuYXR0cignd2lkdGgnLCBfdGhpcy53aWR0aCAtIHlBeGlzVGV4dE1hcmdpbiAvIDIpCiAgICAgICAgICAgICAgICAuYXR0cignaGVpZ2h0JywgY2VsbEhlaWdodCArIDIgKiBmcmFtZU1hcmdpbik7CiAgICAgICAgICAgIHlBeGVzRwogICAgICAgICAgICAgICAgLmFwcGVuZCgnY2xpcFBhdGgnKQogICAgICAgICAgICAgICAgLmF0dHIoJ2lkJywgeUxhYmVsQ2xpcFBhdGhJZCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3JlY3QnKQogICAgICAgICAgICAgICAgLmF0dHIoJ3gnLCAtKF90aGlzLndpZHRoIC0gMSkpCiAgICAgICAgICAgICAgICAuYXR0cigneScsIDApCiAgICAgICAgICAgICAgICAuYXR0cignd2lkdGgnLCB5QXhpc1RleHRNYXJnaW4gLyAyKQogICAgICAgICAgICAgICAgLmF0dHIoJ2hlaWdodCcsIGNlbGxIZWlnaHQpOwogICAgICAgICAgICB5QXhlc0cKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAgICAgLmF0dHIoJ2NsaXAtcGF0aCcsIChtZXRyaWMpID0+ICd1cmwoIycgKyB5QXhpc0NsaXBQYXRoSWQobWV0cmljKSArICcpJykKICAgICAgICAgICAgICAgIC5lYWNoKGZ1bmN0aW9uIChtZXRyaWMpIHsKICAgICAgICAgICAgICAgIHNlbGVjdCh0aGlzKS5jYWxsKGRyYXdBeGlzLCBheGlzTGVmdCh5Q29vcmRzW21ldHJpY10pCiAgICAgICAgICAgICAgICAgICAgLnRpY2tTaXplKF90aGlzLndpZHRoIC0geUF4aXNUZXh0TWFyZ2luKSwgY2VsbEhlaWdodCwgCiAgICAgICAgICAgICAgICAvKiBtaW5MYWJlbFNpemUgKi8gMjAsIF90aGlzLm9wdGlvbnMuY29sdW1uc1ttZXRyaWMgKyB1dGlscy5udW1WaXNpYmxlSFBhcmFtcyhfdGhpcy52aXNpYmxlU2NoZW1hKV0uc2NhbGUpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gQXBwZW5kIGEgbGFiZWwgZm9yIGVhY2ggYXhpcy4KICAgICAgICAgICAgeUF4ZXNHCiAgICAgICAgICAgICAgICAuYXBwZW5kKCdnJykKICAgICAgICAgICAgICAgIC5jbGFzc2VkKCd5LWF4aXMtbGFiZWwnLCB0cnVlKQogICAgICAgICAgICAgICAgLmF0dHIoJ2NsaXAtcGF0aCcsIChtZXRyaWMpID0+ICd1cmwoIycgKyB5TGFiZWxDbGlwUGF0aElkKG1ldHJpYykgKyAnKScpCiAgICAgICAgICAgICAgICAuYXBwZW5kKCd0ZXh0JykKICAgICAgICAgICAgICAgIC5hdHRyKCd0ZXh0LWFuY2hvcicsICdtaWRkbGUnKQogICAgICAgICAgICAgICAgLmF0dHIoJ3gnLCAtKF90aGlzLndpZHRoIC0geUF4aXNUZXh0TWFyZ2luIC8gNCAtIDEpKQogICAgICAgICAgICAgICAgLmF0dHIoJ3knLCBjZWxsSGVpZ2h0IC8gMikKICAgICAgICAgICAgICAgIC5hdHRyKCd0cmFuc2Zvcm0nLCB1dGlscy5yb3RhdGVTdHIoOTAsIC0oX3RoaXMud2lkdGggLSB5QXhpc1RleHRNYXJnaW4gLyA0IC0gMSksIGNlbGxIZWlnaHQgLyAyKSkKICAgICAgICAgICAgICAgIC50ZXh0KChtZXRyaWMpID0+IHV0aWxzLm1ldHJpY05hbWUoX3RoaXMudmlzaWJsZVNjaGVtYS5tZXRyaWNJbmZvc1ttZXRyaWNdKSkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ3RpdGxlJykgLy8gU2hvdyBmdWxsIG5hbWUgYXMgYSB0b29sdGlwLgogICAgICAgICAgICAgICAgLnRleHQoKG1ldHJpYykgPT4gdXRpbHMubWV0cmljTmFtZShfdGhpcy52aXNpYmxlU2NoZW1hLm1ldHJpY0luZm9zW21ldHJpY10pKTsKICAgICAgICAgICAgZnVuY3Rpb24gZHJhd0F4aXMoZywgYXhpc0dlbiwgYXhpc0xlbmd0aCwgbWluTGFiZWxTaXplLCBzY2FsZVR5cGUpIHsKICAgICAgICAgICAgICAgIC8vIFdlIGNvbXB1dGUgdGhlIG51bWJlciBvZiB0aWNrcyB0byBkaXNwbGF5IGJhc2VkIG9uIHRoZSBlc3RpbWF0ZQogICAgICAgICAgICAgICAgLy8gb2YgdGhlIG1pbmltdW0gc2l6ZSB0byBhbGxvdyBmb3IgYSBsYWJlbC4KICAgICAgICAgICAgICAgIGNvbnN0IG51bVRpY2tzID0gTWF0aC5mbG9vcihheGlzTGVuZ3RoIC8gbWluTGFiZWxTaXplKTsKICAgICAgICAgICAgICAgIGNvbnN0IHNjYWxlID0gYXhpc0dlbi5zY2FsZSgpOwogICAgICAgICAgICAgICAgaWYgKHNjYWxlVHlwZSA9PT0gJ1FVQU5USUxFJykgewogICAgICAgICAgICAgICAgICAgIC8vIFRoZSBkZWZhdWx0IHRpY2tWYWx1ZXMgb2YgYSBxdWFudGlsZSBzY2FsZSBpcyBqdXN0IHRoZSBzY2FsZQogICAgICAgICAgICAgICAgICAgIC8vIGRvbWFpbiwgd2hpY2ggcHJvZHVjZXMgb3ZlcmxhcHBpbmcgbGFiZWxzIGlmIHRoZSBudW1iZXIgb2YKICAgICAgICAgICAgICAgICAgICAvLyBlbGVtZW50cyBpbiB0aGUgZG9tYWluIGlzIGdyZWF0ZXIgdGhhbiB0aGUgbnVtYmVyIG9mCiAgICAgICAgICAgICAgICAgICAgLy8gcXVhbnRpbGVzLgogICAgICAgICAgICAgICAgICAgIGxldCBxdWFudGlsZXMgPSBzY2FsZS5xdWFudGlsZXMoKTsKICAgICAgICAgICAgICAgICAgICBjb25zdCBzdGVwID0gTWF0aC5jZWlsKHF1YW50aWxlcy5sZW5ndGggLyBudW1UaWNrcyk7CiAgICAgICAgICAgICAgICAgICAgcXVhbnRpbGVzID0gc2VxdWVuY2UoMCwgcXVhbnRpbGVzLmxlbmd0aCwgc3RlcCkKICAgICAgICAgICAgICAgICAgICAgICAgLm1hcCgoaSkgPT4gcXVhbnRpbGVzW2ldKTsKICAgICAgICAgICAgICAgICAgICBheGlzR2VuLnRpY2tWYWx1ZXMocXVhbnRpbGVzKS50aWNrRm9ybWF0KGZvcm1hdCgnLS4yZycpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChzY2FsZVR5cGUgPT09ICdMSU5FQVInIHx8IHNjYWxlVHlwZSA9PT0gJ0xPRycpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgZm9sbG93aW5nIGlzIGVxdWl2YWxlbnQgdG86IGF4aXNHZW4udGlja3MobnVtVGlja3MpLiBXZQogICAgICAgICAgICAgICAgICAgIC8vIHVzZSB0aGUgZm9ybSBiZWxvdywgc2luY2Ugb3RoZXJ3aXNlIHRoZSBjbG9zdXJlIGNvbXBpbGVyCiAgICAgICAgICAgICAgICAgICAgLy8gZXJyb25lb3VzbHkgZHJvcHMgdGhlIHBhcmFtZXRlciAnbnVtVGlja3MnIGZyb20gdGhlIGNhbGwuIEl0IGRvZXMKICAgICAgICAgICAgICAgICAgICAvLyB0aGlzLCBzaW5jZSBkMyBkZWZpbmVzIHRoZSB2YXJpYWRpYyAndGlja3MnIG1ldGhvZCBhcwogICAgICAgICAgICAgICAgICAgIC8vIGZ1bmN0aW9uKCksIHdoaWNoIGNsb3N1cmUgcmVnYXJkcyBhcyBhIGZ1bmN0aW9uIHRoYXQgdGFrZXMgbm8KICAgICAgICAgICAgICAgICAgICAvLyBwYXJhbWV0ZXJzLgogICAgICAgICAgICAgICAgICAgIGF4aXNHZW5bJ3RpY2tzJ10obnVtVGlja3MpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZy5jYWxsKGF4aXNHZW4pOwogICAgICAgICAgICAgICAgLy8gUmVtb3ZlIHRoZSBhY3R1YWwgYXhpcyBsaW5lLCBhbmQgZ3JleSBvdXQgdGhlIHRpY2sgbGluZXMuCiAgICAgICAgICAgICAgICBnLnNlbGVjdEFsbCgnLmRvbWFpbicpLnJlbW92ZSgpOwogICAgICAgICAgICAgICAgZy5zZWxlY3RBbGwoJy50aWNrIGxpbmUnKS5hdHRyKCdzdHJva2UnLCAnI2RkZCcpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgICAvLyBEcmF3IGNlbGwgZnJhbWVzLgogICAgICAgICAgICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICAgICAgY29uc3QgY2VsbHMgPSB0aGlzLl9zdmcKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJy5jZWxsJykKICAgICAgICAgICAgICAgIC5kYXRhKGNyb3NzKGNvbHMsIG1ldHJpY3MpKQogICAgICAgICAgICAgICAgLmVudGVyKCkKICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2cnKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2NlbGwnLCB0cnVlKQogICAgICAgICAgICAgICAgLmF0dHIoJ3RyYW5zZm9ybScsIChbY29sLCBtZXRyaWNdKSA9PiB1dGlscy50cmFuc2xhdGVTdHIoY2VsbFgoY29sKSwgY2VsbFkobWV0cmljKSkpOwogICAgICAgICAgICBjb25zdCBmcmFtZXMgPSBjZWxscwogICAgICAgICAgICAgICAgLmFwcGVuZCgnZycpCiAgICAgICAgICAgICAgICAuY2xhc3NlZCgnZnJhbWUnLCB0cnVlKQogICAgICAgICAgICAgICAgLmFwcGVuZCgncmVjdCcpCiAgICAgICAgICAgICAgICAuYXR0cigneCcsIC1mcmFtZU1hcmdpbikKICAgICAgICAgICAgICAgIC5hdHRyKCd5JywgLWZyYW1lTWFyZ2luKQogICAgICAgICAgICAgICAgLmF0dHIoJ3dpZHRoJywgY2VsbFdpZHRoICsgMiAqIGZyYW1lTWFyZ2luKQogICAgICAgICAgICAgICAgLmF0dHIoJ2hlaWdodCcsIGNlbGxIZWlnaHQgKyAyICogZnJhbWVNYXJnaW4pCiAgICAgICAgICAgICAgICAuYXR0cignc3Ryb2tlJywgJyMwMDAnKQogICAgICAgICAgICAgICAgLmF0dHIoJ2ZpbGwnLCAnbm9uZScpCiAgICAgICAgICAgICAgICAuYXR0cignc2hhcGUtcmVuZGVyaW5nJywgJ2NyaXNwRWRnZXMnKTsKICAgICAgICAgICAgLy8gLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tCiAgICAgICAgICAgIC8vIERyYXcgZGF0YSBwb2ludCBtYXJrZXJzLgogICAgICAgICAgICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICAgICAgbGV0IGNvbG9yU2NhbGUgPSBudWxsOwogICAgICAgICAgICBpZiAoX3RoaXMub3B0aW9ucy5jb2xvckJ5Q29sdW1uSW5kZXggIT09IHVuZGVmaW5lZCkgewogICAgICAgICAgICAgICAgY29sb3JTY2FsZSA9IGxpbmVhciQyKCkKICAgICAgICAgICAgICAgICAgICAuZG9tYWluKHRoaXMuX2NvbEV4dGVudCh0aGlzLm9wdGlvbnMuY29sb3JCeUNvbHVtbkluZGV4KSkKICAgICAgICAgICAgICAgICAgICAucmFuZ2UoW3RoaXMub3B0aW9ucy5taW5Db2xvciwgdGhpcy5vcHRpb25zLm1heENvbG9yXSkKICAgICAgICAgICAgICAgICAgICAuaW50ZXJwb2xhdGUobGFiJDEpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIEEgZnVuY3Rpb24gbWFwcGluZyBhIHNlc3Npb25Hcm91cCB0byBpdHMgbWFya2VyJ3MgY29sb3IuCiAgICAgICAgICAgIGNvbnN0IG1hcmtlckNvbG9yRm4gPSBfdGhpcy5vcHRpb25zLmNvbG9yQnlDb2x1bW5JbmRleCA9PT0gdW5kZWZpbmVkCiAgICAgICAgICAgICAgICA/IC8qIFVzZSBkZWZhdWx0IGNvbG9yIGlmIG5vIGNvbG9yLWJ5IGNvbHVtbiBpcyBzZWxlY3RlZC4gKi8KICAgICAgICAgICAgICAgICAgICAoKSA9PiAncmVkJwogICAgICAgICAgICAgICAgOiAoeyBzZXNzaW9uR3JvdXAgfSkgPT4gY29sb3JTY2FsZSh0aGlzLl9jb2xWYWx1ZShzZXNzaW9uR3JvdXAsIF90aGlzLm9wdGlvbnMuY29sb3JCeUNvbHVtbkluZGV4KSk7CiAgICAgICAgICAgIC8vIFJldHVybnMgdGhlIHggY29vcmRpbmF0ZSBmb3IgdGhlIG1hcmtlciByZXByZXNlbnRpbmcgc2Vzc2lvbkdyb3VwCiAgICAgICAgICAgIC8vIGluIGEgY2VsbCBpbiB0aGUgc2NhdHRlciBwbG90IG1hdHJpeCBjb2x1bW4gaW5kZXhlZCBieSAnY29sJy4KICAgICAgICAgICAgZnVuY3Rpb24gbWFya2VyWChzZXNzaW9uR3JvdXAsIGNvbCkgewogICAgICAgICAgICAgICAgcmV0dXJuIHhDb29yZHNbY29sXShfdGhpcy5fY29sVmFsdWUoc2Vzc2lvbkdyb3VwLCBjb2wpKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZXR1cm5zIHRoZSB5IGNvb3JkaW5hdGUgZm9yIHRoZSBtYXJrZXIgcmVwcmVzZW50aW5nIHNlc3Npb25Hcm91cAogICAgICAgICAgICAvLyBpbiBhIGNlbGwgaW4gdGhlIHNjYXR0ZXIgcGxvdCBtYXRyaXggcm93IGluZGV4ZWQgYnkgJ21ldHJpYycuCiAgICAgICAgICAgIGZ1bmN0aW9uIG1hcmtlclkoc2Vzc2lvbkdyb3VwLCBtZXRyaWMpIHsKICAgICAgICAgICAgICAgIHJldHVybiB5Q29vcmRzW21ldHJpY10oX3RoaXMuX21ldHJpY1ZhbHVlKHNlc3Npb25Hcm91cCwgbWV0cmljKSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gQSBmdW5jdGlvbiB0aGF0IGdldHMgYSBzZWxlY3Rpb24gb2YgPGc+IGVsZW1lbnRzLS1lYWNoIHNob3VsZCBiZQogICAgICAgICAgICAvLyBhIGNoaWxkIG5vZGUgb2YgYSBjZWxsIDxnPiBlbGVtZW50IChhIG1lbWViZXIgb2YgdGhlICdjZWxscycKICAgICAgICAgICAgLy8gc2VsZWN0aW9uKSBhbmQgZHJhd3MgbWFya2VycyByZXByZXNlbnRpbmcgdGhlIGRhdGEgcG9pbnRzIGluIGVhY2gKICAgICAgICAgICAgLy8gY2VsbC4gVGhlIHBhcmFtZXRlciAnZmlsbCcgaXMgZWl0aGVyIGEgY29uc3RhbnQgc3BlY2lmeWluZyB0aGUKICAgICAgICAgICAgLy8gJ2ZpbGwnIGF0dHJpYnV0ZSBvZiBlYWNoIG1hcmtlciBvciBhIGZ1bmN0aW9uIHRha2luZyBhIHNlc3Npb24KICAgICAgICAgICAgLy8gZ3JvdXAgdGhhdCByZXR1cm5zIHRoZSBmaWxsIGF0dHJpYnV0ZSB0aGF0IHNob3VsZCBiZSBzZXQgZm9yIHRoZQogICAgICAgICAgICAvLyBtYXJrZXIgcmVwcmVzZW50aW5nIHRoZSBnaXZlbiBzZXNzaW9uIGdyb3VwLiBUaGUgZnVuY3Rpb24gcmV0dXJucwogICAgICAgICAgICAvLyBhIDMtdHVwbGUgb2YgW21hcmtlcnMsIGNlbGxNYXJrZXJzLCBzZXNzaW9uR3JvdXBNYXJrZXJzTWFwXSwKICAgICAgICAgICAgLy8gd2hlcmU6IG1hcmtlcnMgaXMgdGhlIGQzLXNlbGVjdGlvbiBvZiB0aGUgbWFya2VycywKICAgICAgICAgICAgLy8gY2VsbE1hcmtlcnMgaXMgYSAyLUQgYXJyYXkgd2hvc2UgW2NvbF1bbWV0cmljXSBlbnRyeSBoYXMgYQogICAgICAgICAgICAvLyBkMy1zZWxlY3Rpb24gY29udGFpbmluZyB0aGUgbWFya2VycyBpbiB0aGUgW2NvbCwgbWV0cmljXSBjZWxsLAogICAgICAgICAgICAvLyBhbmQgc2Vzc2lvbkdyb3VwTWFya2Vyc01hcCBpcyBhIE1hcCBtYXBwaW5nIGEgc2Vzc2lvbkdyb3VwIHRvIHRoZQogICAgICAgICAgICAvLyBhcnJheSBvZiBtYXJrZXIgSFRNTCBlbGVtZW50cyByZXByZXNlbnRpbmcgdGhhdCBzZXNzaW9uR3JvdXAuCiAgICAgICAgICAgIGZ1bmN0aW9uIGFkZE1hcmtlcnMoY2VsbHNHU2VsZWN0aW9uLCBmaWxsKSB7CiAgICAgICAgICAgICAgICBjb25zdCBtYXJrZXJzID0gY2VsbHNHU2VsZWN0aW9uCiAgICAgICAgICAgICAgICAgICAgLnNlbGVjdEFsbCgnLmRhdGEtbWFya2VyJykKICAgICAgICAgICAgICAgICAgICAuZGF0YSgoW2NvbCwgbWV0cmljXSkgPT4gCiAgICAgICAgICAgICAgICAvLyBGaWx0ZXIgb3V0IHNlc3Npb24gZ3JvdXBzIHRoYXQgZG9uJ3QgaGF2ZSBhIG1ldHJpYy12YWx1ZQogICAgICAgICAgICAgICAgLy8gb3IgYSBjb2x1bW4tdmFsdWUgZm9yIHRoZSBjdXJyZW50IGNlbGwuCiAgICAgICAgICAgICAgICBfdGhpcy5zZXNzaW9uR3JvdXBzCiAgICAgICAgICAgICAgICAgICAgLmZpbHRlcigoc2Vzc2lvbkdyb3VwKSA9PiBfdGhpcy5fY29sVmFsdWUoc2Vzc2lvbkdyb3VwLCBjb2wpICE9PSB1bmRlZmluZWQgJiYKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fbWV0cmljVmFsdWUoc2Vzc2lvbkdyb3VwLCBtZXRyaWMpICE9PSB1bmRlZmluZWQpCiAgICAgICAgICAgICAgICAgICAgLm1hcCgoc2Vzc2lvbkdyb3VwKSA9PiAoewogICAgICAgICAgICAgICAgICAgIGNvbDogY29sLAogICAgICAgICAgICAgICAgICAgIG1ldHJpYzogbWV0cmljLAogICAgICAgICAgICAgICAgICAgIHNlc3Npb25Hcm91cDogc2Vzc2lvbkdyb3VwLAogICAgICAgICAgICAgICAgICAgIHg6IG1hcmtlclgoc2Vzc2lvbkdyb3VwLCBjb2wpLAogICAgICAgICAgICAgICAgICAgIHk6IG1hcmtlclkoc2Vzc2lvbkdyb3VwLCBtZXRyaWMpLAogICAgICAgICAgICAgICAgICAgIC8vIFRoaXMgd2lsbCBiZSBwb3B1bGF0ZWQgYnkgdGhlIGNvZGUgYmVsb3cgd2l0aAogICAgICAgICAgICAgICAgICAgIC8vIGEgU2V0IG9mIGFsbCB0aGUgbWFya2VycyByZXByZXNlbnRpbmcgdGhpcyBzZXNzaW9uCiAgICAgICAgICAgICAgICAgICAgLy8gZ3JvdXAuCiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbkdyb3VwTWFya2VyczogbnVsbCwKICAgICAgICAgICAgICAgIH0pKSkKICAgICAgICAgICAgICAgICAgICAuZW50ZXIoKQogICAgICAgICAgICAgICAgICAgIC5hcHBlbmQoJ2NpcmNsZScpCiAgICAgICAgICAgICAgICAgICAgLmNsYXNzZWQoJ2RhdGEtbWFya2VyJywgdHJ1ZSkKICAgICAgICAgICAgICAgICAgICAuYXR0cignY3gnLCAoeyB4IH0pID0+IHgpCiAgICAgICAgICAgICAgICAgICAgLmF0dHIoJ2N5JywgKHsgeSB9KSA9PiB5KQogICAgICAgICAgICAgICAgICAgIC5hdHRyKCdyJywgMikKICAgICAgICAgICAgICAgICAgICAuYXR0cignZmlsbCcsIGZpbGwpOwogICAgICAgICAgICAgICAgY29uc3Qgc2Vzc2lvbkdyb3VwTWFya2Vyc01hcCA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgICAgIF90aGlzLnNlc3Npb25Hcm91cHMuZm9yRWFjaCgoc2Vzc2lvbkdyb3VwKSA9PiB7CiAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbkdyb3VwTWFya2Vyc01hcC5zZXQoc2Vzc2lvbkdyb3VwLCBbXSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIG1hcmtlcnMuZWFjaChmdW5jdGlvbiAoZCkgewogICAgICAgICAgICAgICAgICAgIHNlc3Npb25Hcm91cE1hcmtlcnNNYXAuZ2V0KGQuc2Vzc2lvbkdyb3VwKS5wdXNoKHRoaXMpOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICBtYXJrZXJzLmVhY2goKGQpID0+IHsKICAgICAgICAgICAgICAgICAgICBjb25zdCBzZXNzaW9uR3JvdXBNYXJrZXJzID0gc2Vzc2lvbkdyb3VwTWFya2Vyc01hcC5nZXQoZC5zZXNzaW9uR3JvdXApOwogICAgICAgICAgICAgICAgICAgIGQuc2Vzc2lvbkdyb3VwTWFya2VycyA9IG5ldyBTZXQoc2Vzc2lvbkdyb3VwTWFya2Vycyk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgICAgIGNvbnN0IGNlbGxNYXJrZXJzID0gY29scy5tYXAoKGNvbCkgPT4gbWV0cmljcy5tYXAoKG1ldHJpYykgPT4gbWFya2Vycy5maWx0ZXIoKGQpID0+IGQuY29sID09IGNvbCAmJiBkLm1ldHJpYyA9PSBtZXRyaWMpKSk7CiAgICAgICAgICAgICAgICByZXR1cm4gW21hcmtlcnMsIGNlbGxNYXJrZXJzLCBzZXNzaW9uR3JvdXBNYXJrZXJzTWFwXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBjb25zdCBbbWFya2VycywgY2VsbE1hcmtlcnMsIHNlc3Npb25Hcm91cE1hcmtlcnNNYXBdID0gYWRkTWFya2VycyhjZWxscy5hcHBlbmQoJ2cnKSwgCiAgICAgICAgICAgIC8qIGZpbGwgKi8gbWFya2VyQ29sb3JGbik7CiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgICAvLyBDcmVhdGUgYSBicnVzaCBmb3IgZWFjaCBjZWxsLiBCcnVzaGluZyBhIGNlbGwgbWFrZXMgInZpc2libGUiIG9ubHkKICAgICAgICAgICAgLy8gdGhlIG1hcmtlcnMgYXNzb2NpYXRlZCB3aXRoIHNlc3Npb24gZ3JvdXBzIHdob3NlIG1hcmtlcnMKICAgICAgICAgICAgLy8gaW4gdGhlIGJydXNoZWQgY2VsbCBsaWUgd2l0aGluIHRoZSBicnVzaCBzZWxlY3Rpb24uIEJ5ICJ2aXNpYmlsZSIKICAgICAgICAgICAgLy8gaGVyZSwgd2UgbWFuIGNvbG9yZWQgYWNjb3JkaW5nIHRvIGNvbG9yLWJ5IGNvbHVtbi4gTWFya2VycyB0aGF0CiAgICAgICAgICAgIC8vIGFyZSBub3QgInZpc2liaWxlIiB3aWxsIGJlIHNob3duIGFzIGdyYXllZCBvdXQuCiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgICAvLyBGb3IgZWFjaCBjZWxsLCB3ZSBpbmRleCB0aGUgbWFya2VycyBpbiBhIHF1YWQtdHJlZSB0byBxdWlja2x5CiAgICAgICAgICAgIC8vIGZpbmQgdGhlIGludGVyc2VjdGlvbiBvZiB0aGUgbWFya2VycyB3aXRoIHRoZSAoYnJ1c2gpIHNlbGVjdGlvbi4KICAgICAgICAgICAgLy8gVGhlIGZvbGxvd2luZyBmdW5jdGlvbiBjcmVhdGVzIHRoaXMgcXVhZC10cmVlIGZvciB0aGUgY2VsbCBpbmRleGVkIGJ5CiAgICAgICAgICAgIC8vIChjb2wsIG1ldHJpYykuIEVhY2ggcXVhZCB0cmVlIGRhdHVtIGlzIHRoZSBjb3JyZXNwb25kaW5nIG1hcmtlcidzCiAgICAgICAgICAgIC8vIGVsZW1lbnQuCiAgICAgICAgICAgIGZ1bmN0aW9uIGNyZWF0ZUNlbGxRdWFkVHJlZShjb2wsIG1ldHJpYykgewogICAgICAgICAgICAgICAgY29uc3QgZGF0YSA9IFtdOwogICAgICAgICAgICAgICAgY2VsbE1hcmtlcnNbY29sXVttZXRyaWNdLmVhY2goZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgICAgIGRhdGEucHVzaCh0aGlzKTsKICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgcmV0dXJuIHF1YWR0cmVlKCkKICAgICAgICAgICAgICAgICAgICAueCgoZWxlbSkgPT4gc2VsZWN0KGVsZW0pLmRhdHVtKCkueCkKICAgICAgICAgICAgICAgICAgICAueSgoZWxlbSkgPT4gc2VsZWN0KGVsZW0pLmRhdHVtKCkueSkKICAgICAgICAgICAgICAgICAgICAuYWRkQWxsKGRhdGEpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IHF1YWRUcmVlcyA9IGNvbHMubWFwKChjb2wpID0+IG1ldHJpY3MubWFwKChtZXRyaWMpID0+IGNyZWF0ZUNlbGxRdWFkVHJlZShjb2wsIG1ldHJpYykpKTsKICAgICAgICAgICAgLy8gQSBkMy1zZWxlY3Rpb24gb2YgdGhlIGNlbGwgaW4gJ2NlbGxzJyB0aGF0IGhhcyB0aGUgYWN0aXZlCiAgICAgICAgICAgIC8vIGJydXNoIHNlbGVjdGlvbiwgb3IgbnVsbCBpZiB0aGUgYnJ1c2ggaXMgbm90IGFjdGl2ZS4KICAgICAgICAgICAgbGV0IGJydXNoZWRDZWxsRyA9IG51bGw7CiAgICAgICAgICAgIGlmIChpc0JydXNoQWN0aXZlKCkpIHsKICAgICAgICAgICAgICAgIGJydXNoZWRDZWxsRyA9IGNlbGxzLmZpbHRlcigoY2VsbEluZGV4KSA9PiBsb2Rhc2guaXNFcXVhbChjZWxsSW5kZXgsIF90aGlzLl9icnVzaGVkQ2VsbEluZGV4KSk7CiAgICAgICAgICAgICAgICBjb25zb2xlLmFzc2VydChicnVzaGVkQ2VsbEcuc2l6ZSgpID09IDEsIGJydXNoZWRDZWxsRyk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gVGhlIHNldCBvZiBtYXJrZXJzIChpbiBhbGwgY2VsbHMpIHRoYXQgYXJlIHZpc2libGUuIFdlIGtlZXAgdGhpcwogICAgICAgICAgICAvLyBzZXQgYXJvdW5kIHNvIHRoYXQgd2hlbiB0aGUgYnJ1c2ggc2VsZWN0aW9uIGNoYW5nZXMgd2UgY2FuIGNoYW5nZQogICAgICAgICAgICAvLyB0aGUgImZpbGwiIGF0dHJpYnV0ZSBvZiBvbmx5IHRoZSBtYXJrZXJzIHdlIG5lZWQgdG8uIFRoaXMgcmVkdWNlcwogICAgICAgICAgICAvLyB0aGUgYnJvd3NlcidzIHJlbmRlcmluZyB0aW1lIGFuZCBtYWtlcyBicnVzaGluZyBzbW9vdGhlci4KICAgICAgICAgICAgbGV0IHZpc2libGVNYXJrZXJzID0gbmV3IFNldChtYXJrZXJzLm5vZGVzKCkpOwogICAgICAgICAgICB1cGRhdGVWaXNpYmxlTWFya2VycygpOwogICAgICAgICAgICBmdW5jdGlvbiB1cGRhdGVWaXNpYmxlTWFya2VycygpIHsKICAgICAgICAgICAgICAgIC8vIFdlIHJlZ2FyZCBhbiBlbXB0eSAob3IgaW5hY3RpdmUpIGJydXNoIHNlbGVjdGlvbiBhcyBzZWxlY3RpbmcKICAgICAgICAgICAgICAgIC8vIGFsbCBtYXJrZXJzLgogICAgICAgICAgICAgICAgbGV0IG5ld1Zpc2libGVNYXJrZXJzID0gbmV3IFNldChtYXJrZXJzLm5vZGVzKCkpOwogICAgICAgICAgICAgICAgaWYgKCFpc0JydXNoU2VsZWN0aW9uRW1wdHkoKSkgewogICAgICAgICAgICAgICAgICAgIG5ld1Zpc2libGVNYXJrZXJzID0gZmluZE1hcmtlcnNJblNlbGVjdGlvbihfdGhpcy5fYnJ1c2hlZENlbGxJbmRleCwgX3RoaXMuX2JydXNoU2VsZWN0aW9uKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIC8vIEhpZ2hsaWdodCB0aGUgbmV3IHZpc2libGUgbWFya2Vycy4KICAgICAgICAgICAgICAgIHNlbGVjdEFsbChBcnJheS5mcm9tKHV0aWxzLmZpbHRlclNldChuZXdWaXNpYmxlTWFya2VycywgKGVsZW0pID0+ICF2aXNpYmxlTWFya2Vycy5oYXMoZWxlbSkpKSkuYXR0cignZmlsbCcsIG1hcmtlckNvbG9yRm4pOwogICAgICAgICAgICAgICAgLy8gR3JheS1vdXQgdGhlIG5vLWxvbmdlciB2aXNpYmxlIG1hcmtlcnMuCiAgICAgICAgICAgICAgICBzZWxlY3RBbGwoQXJyYXkuZnJvbSh1dGlscy5maWx0ZXJTZXQodmlzaWJsZU1hcmtlcnMsIChlbGVtKSA9PiAhbmV3VmlzaWJsZU1hcmtlcnMuaGFzKGVsZW0pKSkpLmF0dHIoJ2ZpbGwnLCAnI2RkZCcpOwogICAgICAgICAgICAgICAgdmlzaWJsZU1hcmtlcnMgPSBuZXdWaXNpYmxlTWFya2VyczsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyBSZXR1cm5zIGEgU2V0IG9mIGFsbCBtYXJrZXIgZWxlbWVudHMgdGhhdCBhcmUgaW4gdGhlCiAgICAgICAgICAgIC8vIHJlY3RhbmdsZSAnc2VsZWN0aW9uJyBnaXZlbiBpbiBjb29yZGluYXRlcyByZWxhdGl2ZSB0byB0aGUKICAgICAgICAgICAgLy8gY2VsbCBpbmRleGVkIGJ5IGNlbGxJbmRleCAuCiAgICAgICAgICAgIGZ1bmN0aW9uIGZpbmRNYXJrZXJzSW5TZWxlY3Rpb24oY2VsbEluZGV4LCBzZWxlY3Rpb24pIHsKICAgICAgICAgICAgICAgIGNvbnNvbGUuYXNzZXJ0KGNlbGxJbmRleCAhPT0gbnVsbCk7CiAgICAgICAgICAgICAgICBjb25zb2xlLmFzc2VydChzZWxlY3Rpb24gIT09IG51bGwpOwogICAgICAgICAgICAgICAgY29uc3QgW2NvbCwgbWV0cmljXSA9IGNlbGxJbmRleDsKICAgICAgICAgICAgICAgIGNvbnN0IHJlc3VsdCA9IG5ldyBTZXQoKTsKICAgICAgICAgICAgICAgIHV0aWxzLnF1YWRUcmVlVmlzaXRQb2ludHNJblJlY3QocXVhZFRyZWVzW2NvbF1bbWV0cmljXSwgc2VsZWN0aW9uWzBdWzBdLCBzZWxlY3Rpb25bMF1bMV0sIHNlbGVjdGlvblsxXVswXSwgc2VsZWN0aW9uWzFdWzFdLCAoZWxlbSkgPT4gewogICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBzZWxlY3QoZWxlbSkuZGF0dW0oKTsKICAgICAgICAgICAgICAgICAgICBkYXRhLnNlc3Npb25Hcm91cE1hcmtlcnMuZm9yRWFjaCgoc2dfZWxlbSkgPT4gewogICAgICAgICAgICAgICAgICAgICAgICByZXN1bHQuYWRkKHNnX2VsZW0pOwogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICByZXR1cm4gcmVzdWx0OwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNvbnN0IGJydXNoJDEgPSBicnVzaCgpCiAgICAgICAgICAgICAgICAuZXh0ZW50KFsKICAgICAgICAgICAgICAgIFstZnJhbWVNYXJnaW4gKyAxLCAtZnJhbWVNYXJnaW4gKyAxXSwKICAgICAgICAgICAgICAgIFtjZWxsV2lkdGggLSAxICsgZnJhbWVNYXJnaW4gLSAxLCBjZWxsSGVpZ2h0IC0gMSArIGZyYW1lTWFyZ2luIC0gMV0sCiAgICAgICAgICAgIF0pCiAgICAgICAgICAgICAgICAub24oJ3N0YXJ0JywgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgaWYgKGlzQnJ1c2hBY3RpdmUoKSAmJiBicnVzaGVkQ2VsbEcubm9kZSgpICE9IHRoaXMpIHsKICAgICAgICAgICAgICAgICAgICAvLyBUaGUgYnJ1c2ggaXMgYWN0aXZlIGluIGEgZGlmZmVyZW50IGNlbGwuCiAgICAgICAgICAgICAgICAgICAgLy8gQ2xlYXIgdGhlIHNlbGVjdGlvbiBmaXJzdC4KICAgICAgICAgICAgICAgICAgICAvLyBUaGlzIHdpbGwgcmVjdXJzaXZlbHkgY2FsbCB0aGUgJ3N0YXJ0JywgJ2JydXNoJywgYW5kCiAgICAgICAgICAgICAgICAgICAgLy8gJ2VuZCcgZXZlbnQgbGlzdGVuZXJzIGZvciB0aGUgY2VsbCB3aXRoIHRoZSBzZWxlY3Rpb24KICAgICAgICAgICAgICAgICAgICAvLyBhbmQgd2lsbCB1cGRhdGUgdGhlIG1hcmtlcnMuIFRoZSAnaWYnIGFib3ZlCiAgICAgICAgICAgICAgICAgICAgLy8gcHJldmVudHMgaW5maW5pdGUgcmVjdXJzaW9uLgogICAgICAgICAgICAgICAgICAgIGJydXNoJDEubW92ZShicnVzaGVkQ2VsbEcsIG51bGwpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgYnJ1c2hDaGFuZ2VkKHRoaXMpOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLm9uKCdicnVzaCcsIGZ1bmN0aW9uICgpIHsKICAgICAgICAgICAgICAgIGJydXNoQ2hhbmdlZCh0aGlzKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5vbignZW5kJywgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgYnJ1c2hDaGFuZ2VkKHRoaXMpOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gVXBkYXRlcyB0aGUgaW50ZXJuYWwgc3RhdGUgaW4gcmVzcG9uc2UgdG8gYSBicnVzaCBldmVudCBpbgogICAgICAgICAgICAvLyB0aGUgY2VsbCB3aG9zZSA8Zz4gZWxlbWVudCAoaW4gJ2NlbGxzJykgaXMgZ2l2ZW4gYnkgY2VsbEdOb2RlCiAgICAgICAgICAgIGZ1bmN0aW9uIGJydXNoQ2hhbmdlZChjZWxsR05vZGUpIHsKICAgICAgICAgICAgICAgIC8vIEZvciBzb21lIHJlYXNvbiB0aGUgY2xvc3VyZSBjb21waWxlciBkcm9wcyB0aGUgYXJndW1lbnQgd2hlbiB3ZQogICAgICAgICAgICAgICAgLy8gd3JpdGUgdGhlIGNhbGwgYmVsb3cgYXMgJ2QzLmJydXNoU2VsZWN0aW9uKGNlbGxHTm9kZSknLgogICAgICAgICAgICAgICAgY29uc3QgYnJ1c2hTZWxlY3Rpb24kMSA9IGJydXNoU2VsZWN0aW9uKGNlbGxHTm9kZSk7CiAgICAgICAgICAgICAgICBpZiAoKCFpc0JydXNoQWN0aXZlKCkgJiYgYnJ1c2hTZWxlY3Rpb24kMSA9PT0gbnVsbCkgfHwKICAgICAgICAgICAgICAgICAgICAoaXNCcnVzaEFjdGl2ZSgpICYmCiAgICAgICAgICAgICAgICAgICAgICAgIGNlbGxHTm9kZSA9PT0gYnJ1c2hlZENlbGxHLm5vZGUoKSAmJgogICAgICAgICAgICAgICAgICAgICAgICBsb2Rhc2guaXNFcXVhbChicnVzaFNlbGVjdGlvbiQxLCBfdGhpcy5fYnJ1c2hTZWxlY3Rpb24pKSkgewogICAgICAgICAgICAgICAgICAgIC8vIE5vdGhpbmcgdG8gZG8gaWYgc2VsZWN0aW9uIGhhc24ndCBjaGFuZ2VkLgogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIF90aGlzLl9icnVzaFNlbGVjdGlvbiA9IGJydXNoU2VsZWN0aW9uJDE7CiAgICAgICAgICAgICAgICBpZiAoYnJ1c2hTZWxlY3Rpb24kMSAhPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIGJydXNoZWRDZWxsRyA9IHNlbGVjdChjZWxsR05vZGUpOwogICAgICAgICAgICAgICAgICAgIF90aGlzLl9icnVzaGVkQ2VsbEluZGV4ID0gYnJ1c2hlZENlbGxHLmRhdHVtKCk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBlbHNlIHsKICAgICAgICAgICAgICAgICAgICBicnVzaGVkQ2VsbEcgPSBudWxsOwogICAgICAgICAgICAgICAgICAgIF90aGlzLl9icnVzaGVkQ2VsbEluZGV4ID0gbnVsbDsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIHVwZGF0ZVZpc2libGVNYXJrZXJzKCk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZnVuY3Rpb24gaXNCcnVzaEFjdGl2ZSgpIHsKICAgICAgICAgICAgICAgIHJldHVybiBfdGhpcy5fYnJ1c2hlZENlbGxJbmRleCAhPT0gbnVsbCAmJiBfdGhpcy5fYnJ1c2hTZWxlY3Rpb24gIT09IG51bGw7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZnVuY3Rpb24gaXNCcnVzaFNlbGVjdGlvbkVtcHR5KCkgewogICAgICAgICAgICAgICAgcmV0dXJuICghaXNCcnVzaEFjdGl2ZSgpIHx8CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuX2JydXNoU2VsZWN0aW9uWzBdWzBdID09PSBfdGhpcy5fYnJ1c2hTZWxlY3Rpb25bMV1bMF0gfHwKICAgICAgICAgICAgICAgICAgICBfdGhpcy5fYnJ1c2hTZWxlY3Rpb25bMF1bMV0gPT09IF90aGlzLl9icnVzaFNlbGVjdGlvblsxXVsxXSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgLy8gUmVuZGVyIHRoZSBicnVzaCBlbGVtZW50cyBvbiBlYWNoIGNlbGwuCiAgICAgICAgICAgIGNlbGxzLmNhbGwoYnJ1c2gkMSk7CiAgICAgICAgICAgIGlmIChpc0JydXNoQWN0aXZlKCkpIHsKICAgICAgICAgICAgICAgIC8vIFNldCB0aGUgaW50ZXJuYWwgYnJ1c2ggc2VsZWN0aW9uIHRvIHdoYXQgaXQgd2FzIGJlZm9yZQogICAgICAgICAgICAgICAgLy8gdGhlICdyZWRyYXcoKScuCiAgICAgICAgICAgICAgICBicnVzaCQxLm1vdmUoYnJ1c2hlZENlbGxHLCBfdGhpcy5fYnJ1c2hTZWxlY3Rpb24pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgICAvLyBBZGQgZXZlbnQgbGlzdGVuZXJzIGZvciBoaWdobGlnaHRpbmcgdGhlIHNlc3Npb24gZ3JvdXAgd2hvc2UgbWFya2VycwogICAgICAgICAgICAvLyBhcmUgY2xvc2VzdCB0byB0aGUgbW91c2UgcG9pbnRlciAob25seSAidmlzaWJsZSIgc2Vzc2lvbiBncm91cHMKICAgICAgICAgICAgLy8gYXJlIGNvbnNpZGVyZWQgLS0gc2VlIGJydXNoaW5nIGFib3ZlKS4gQWxzbywgYWRkIGV2ZW50IGxpc3RlbmVycwogICAgICAgICAgICAvLyBmb3IgbWFraW5nIHRoZSBoaWdobGlnaHRlZCBzZXNzaW9uIGdyb3VwIHRoZSBjdXJyZW50bHktc2VsZWN0ZWQKICAgICAgICAgICAgLy8gZ3JvdXAgYnkgY2xpY2tpbmcuCiAgICAgICAgICAgIC8vIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLQogICAgICAgICAgICAvLyBBIGQzLXNlbGVjdGlvbiBjb250YWluaW5nIHRoZSBub2RlcyBpbiBtYXJrZXJzIHJlcHJlc2VudGluZyB0aGUKICAgICAgICAgICAgLy8gU2Vzc2lvbkdyb3VwIHdpdGggYSBtYXJrZXIgY2xvc2VzdCB0byB0aGUgbW91c2UgcG9pbnRlciBvciBudWxsCiAgICAgICAgICAgIC8vIGlmIHRoZSBkaXN0YW5jZSB0byB0aGUgY2xvc2VzdCBzZXNzaW9uIGdyb3VwIGlzIGdyZWF0ZXIgdGhhbiBhCiAgICAgICAgICAgIC8vIHRocmVzaG9sZC4gVGhpcyB3b24ndCBnZXQgc2V0IHVudGlsIHRoZSBmaXJzdCBtb3VzZSBtb3ZlbWVudCBvdmVyCiAgICAgICAgICAgIC8vIGEgY2VsbC4KICAgICAgICAgICAgbGV0IGNsb3Nlc3RNYXJrZXJzID0gbnVsbDsKICAgICAgICAgICAgLy8gQSBkMy1zZWxlY3Rpb24gY29udGFpbmluZyB0aGUgbm9kZXMgaW4gbWFya2VycyByZXByZXNlbnRpbmcgdGhlCiAgICAgICAgICAgIC8vIG1hcmtlcnMgb2YgdGhlIGN1cnJlbnRseSBzZWxlY3RlZCBzZXNzaW9uIGdyb3VwIG9yIG51bGwgaWYgbm8KICAgICAgICAgICAgLy8gc2Vzc2lvbiBncm91cCBpcyBzZWxlY3RlZC4KICAgICAgICAgICAgbGV0IHNlbGVjdGVkTWFya2VycyA9IG51bGw7CiAgICAgICAgICAgIGlmICh0aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICBzZWxlY3RlZE1hcmtlcnMgPSBzZWxlY3RBbGwoc2Vzc2lvbkdyb3VwTWFya2Vyc01hcC5nZXQodGhpcy5zZWxlY3RlZFNlc3Npb25Hcm91cCkpCiAgICAgICAgICAgICAgICAgICAgLmNsYXNzZWQoJ3NlbGVjdGVkLW1hcmtlcicsIHRydWUpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGNlbGxzCiAgICAgICAgICAgICAgICAub24oJ2NsaWNrJywgZnVuY3Rpb24gKCkgewogICAgICAgICAgICAgICAgY29uc3QgbmV3U2VsZWN0ZWRNYXJrZXJzID0gY2xvc2VzdE1hcmtlcnMgPT09IHNlbGVjdGVkTWFya2VycyA/IG51bGwgOiBjbG9zZXN0TWFya2VyczsKICAgICAgICAgICAgICAgIGlmIChuZXdTZWxlY3RlZE1hcmtlcnMgPT09IHNlbGVjdGVkTWFya2VycykgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGlmIChzZWxlY3RlZE1hcmtlcnMgIT09IG51bGwpIHsKICAgICAgICAgICAgICAgICAgICBzZWxlY3RlZE1hcmtlcnMuY2xhc3NlZCgnc2VsZWN0ZWQtbWFya2VyJywgZmFsc2UpOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgc2VsZWN0ZWRNYXJrZXJzID0gbmV3U2VsZWN0ZWRNYXJrZXJzOwogICAgICAgICAgICAgICAgaWYgKHNlbGVjdGVkTWFya2VycyAhPT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHNlbGVjdGVkTWFya2Vycy5jbGFzc2VkKCdzZWxlY3RlZC1tYXJrZXInLCB0cnVlKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNvbnN0IG5ld1Nlc3Npb25Hcm91cCA9IHNlbGVjdGVkTWFya2VycyA9PT0gbnVsbAogICAgICAgICAgICAgICAgICAgID8gbnVsbAogICAgICAgICAgICAgICAgICAgIDogLy8gQWxsIGVsZW1lbnRzIGluIHNlbGVjdGVkTWFya2VycyBzaG91bGQgaGF2ZSB0aGUgc2FtZQogICAgICAgICAgICAgICAgICAgICAgICAvLyBzZXNzaW9uR3JvdXAuCiAgICAgICAgICAgICAgICAgICAgICAgIHNlbGVjdGVkTWFya2Vycy5kYXR1bSgpLnNlc3Npb25Hcm91cDsKICAgICAgICAgICAgICAgIF90aGlzLnNlbGVjdGVkU2Vzc2lvbkdyb3VwID0gbmV3U2Vzc2lvbkdyb3VwOwogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLm9uKCdtb3VzZW1vdmUgbW91c2VlbnRlcicsIGZ1bmN0aW9uIChbY29sLCBtZXRyaWNdKSB7CiAgICAgICAgICAgICAgICBjb25zdCBbeCwgeV0gPSBtb3VzZSh0aGlzKTsKICAgICAgICAgICAgICAgIGNvbnN0IG5ld0Nsb3Nlc3RNYXJrZXJzID0gZmluZENsb3Nlc3RNYXJrZXJzKGNvbCwgbWV0cmljLCB4LCB5LCAKICAgICAgICAgICAgICAgIC8qIHRocmVzaG9sZCAqLyAyMCk7CiAgICAgICAgICAgICAgICBpZiAoY2xvc2VzdE1hcmtlcnMgPT09IG5ld0Nsb3Nlc3RNYXJrZXJzKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgaWYgKGNsb3Nlc3RNYXJrZXJzICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdE1hcmtlcnMuY2xhc3NlZCgnY2xvc2VzdC1tYXJrZXInLCBmYWxzZSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjbG9zZXN0TWFya2VycyA9IG5ld0Nsb3Nlc3RNYXJrZXJzOwogICAgICAgICAgICAgICAgaWYgKGNsb3Nlc3RNYXJrZXJzICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdE1hcmtlcnMuY2xhc3NlZCgnY2xvc2VzdC1tYXJrZXInLCB0cnVlKTsKICAgICAgICAgICAgICAgICAgICAvLyBBbGwgZWxlbWVudHMgaW4gY2xvc2VzdE1hcmtlcnMgc2hvdWxkIGhhdmUgdGhlIHNhbWUKICAgICAgICAgICAgICAgICAgICAvLyBzZXNzaW9uR3JvdXAuCiAgICAgICAgICAgICAgICAgICAgX3RoaXMuY2xvc2VzdFNlc3Npb25Hcm91cCA9IGNsb3Nlc3RNYXJrZXJzLmRhdHVtKCkuc2Vzc2lvbkdyb3VwOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICAgICAgX3RoaXMuY2xvc2VzdFNlc3Npb25Hcm91cCA9IG51bGw7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgIH0pCiAgICAgICAgICAgICAgICAub24oJ21vdXNlbGVhdmUnLCBmdW5jdGlvbiAoW2NvbCwgbWV0cmljXSkgewogICAgICAgICAgICAgICAgaWYgKGNsb3Nlc3RNYXJrZXJzICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdE1hcmtlcnMuY2xhc3NlZCgnY2xvc2VzdC1tYXJrZXInLCBmYWxzZSk7CiAgICAgICAgICAgICAgICAgICAgY2xvc2VzdE1hcmtlcnMgPSBudWxsOwogICAgICAgICAgICAgICAgICAgIF90aGlzLmNsb3Nlc3RTZXNzaW9uR3JvdXAgPSBudWxsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICB9KTsKICAgICAgICAgICAgLy8gRmluZHMgYSBjbG9zZXN0IHZpc2libGUgbWFya2VyIGluIHRoZSBbY29sLG1ldHJpY10gY2VsbCB0byB0aGUgcG9pbnQKICAgICAgICAgICAgLy8gd2l0aCBjZWxsLXJlbGF0aXZlIGNvb3JkaW5hdGVzICh4LHkpLiBJZiB0aGF0IHBvaW50J3MgZGlzdGFuY2UKICAgICAgICAgICAgLy8gdG8gdGhlIHBvaW50IGF0ICh4LHkpIGlzIGxhcmdlciB0aGFuIHRocmVzaG9sZCwgcmV0dXJucyBudWxsOwogICAgICAgICAgICAvLyBvdGhlcndpc2UgcmV0dXJucyB0aGUgZDMtc2VsZWN0aW9uIGNvbnNpc3Rpbmcgb2YgdGhlIG1hcmtlcnMKICAgICAgICAgICAgLy8gcmVwcmVzZW50aW5nIHRoZSBzZXNzaW9uIGdyb3VwIG9mIHRoYXQgY2xvc2VzdCBtYXJrZXIuCiAgICAgICAgICAgIGZ1bmN0aW9uIGZpbmRDbG9zZXN0TWFya2VycyhtZXRyaWMsIGNvbCwgeCwgeSwgdGhyZXNob2xkKSB7CiAgICAgICAgICAgICAgICBsZXQgbWluRGlzdCA9IEluZmluaXR5OwogICAgICAgICAgICAgICAgbGV0IG1pblNlc3Npb25Hcm91cCA9IG51bGw7CiAgICAgICAgICAgICAgICB1dGlscy5xdWFkVHJlZVZpc2l0UG9pbnRzSW5EaXNrKHF1YWRUcmVlc1ttZXRyaWNdW2NvbF0sIHgsIHksIHRocmVzaG9sZCwgKGVsZW0sIGRpc3RhbmNlVG9DZW50ZXIpID0+IHsKICAgICAgICAgICAgICAgICAgICBpZiAodmlzaWJsZU1hcmtlcnMuaGFzKGVsZW0pICYmIGRpc3RhbmNlVG9DZW50ZXIgPCBtaW5EaXN0KSB7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IGRhdGEgPSBzZWxlY3QoZWxlbSkuZGF0dW0oKTsKICAgICAgICAgICAgICAgICAgICAgICAgbWluRGlzdCA9IGRpc3RhbmNlVG9DZW50ZXI7CiAgICAgICAgICAgICAgICAgICAgICAgIG1pblNlc3Npb25Hcm91cCA9IGRhdGEuc2Vzc2lvbkdyb3VwOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgaWYgKG1pblNlc3Npb25Hcm91cCA9PT0gbnVsbCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBudWxsOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIHNlbGVjdEFsbChzZXNzaW9uR3JvdXBNYXJrZXJzTWFwLmdldChtaW5TZXNzaW9uR3JvdXApKTsKICAgICAgICAgICAgfQogICAgICAgICAgICAvLyAtLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICAgICAgLy8gUG9seW1lciBhZGRzIGFuIGV4dHJhICIudGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXBsb3QiIGNsYXNzIHRvCiAgICAgICAgICAgIC8vIGVhY2ggcnVsZSBzZWxlY3RvciBpbiB0aGUgPHN0eWxlPiBzZWN0aW9uIHdyaXR0ZW4gYWJvdmUuIFdoZW4KICAgICAgICAgICAgLy8gcG9seW1lciBzdGFtcHMgYSB0ZW1wbGF0ZSBpdCBhZGRzIHRoaXMgY2xhc3MgdG8gZXZlcnkgZWxlbWVudAogICAgICAgICAgICAvLyBzdGFtcGVkOyBzaW5jZSB3ZSdyZSBpbmplY3Rpbmcgb3VyIG93biBlbGVtZW50cyBoZXJlLCB3ZSBhZGQgdGhpcwogICAgICAgICAgICAvLyBjbGFzcyB0byBlYWNoIGVsZW1lbnQgc28gdGhhdCB0aGUgc3R5bGUgcnVsZXMgZGVmaW5lZCBhYm92ZSB3aWxsCiAgICAgICAgICAgIC8vIGFwcGx5LgogICAgICAgICAgICB0aGlzLl9zdmcKICAgICAgICAgICAgICAgIC5zZWxlY3RBbGwoJyonKQogICAgICAgICAgICAgICAgLmNsYXNzZWQoJ3RmLWhwYXJhbXMtc2NhdHRlci1wbG90LW1hdHJpeC1wbG90JywgdHJ1ZSk7CiAgICAgICAgfQogICAgICAgIC8vIFJldHVybnMgYSBkMyBzY2FsZSBtYXBwaW5nIGVpdGhlciBhIG1ldHJpYyBvciBhbiBocGFyYW0gdmFsdWUKICAgICAgICAvLyB0byB0aGUgY2VsbCdzIGNvb3JkaW5hdGUgc3lzdGVtLiAncmFuZ2UnIHNob3VsZCBiZSBhbiBpbnRlcnZhbCBpbiB0aGUKICAgICAgICAvLyBjZWxsJ3MgY29vcmRpbmF0ZSBzeXN0ZW0gcmVwcmVzZW50aW5nIHRoZSByYW5nZSBvZiB0aGUgc2NhbGUuIFRoZQogICAgICAgIC8vIG1ldHJpYyBvciBocGFyYW0gdG8gYmUgbWFwcGVkIHNob3VsZCBiZSBzcGVjaWZpZWQgYXMgdGhlCiAgICAgICAgLy8gdmlzaWJsZVNjaGVtYS1jb2x1bW4gaW5kZXhlZCBieSBjb2xJbmRleC4KICAgICAgICBfY2VsbFNjYWxlKGNvbEluZGV4LCByYW5nZSkgewogICAgICAgICAgICBjb25zdCBleHRlbnQgPSB0aGlzLl9jb2xFeHRlbnQoY29sSW5kZXgpOwogICAgICAgICAgICBjb25zdCBsaW5lYXJTY2FsZSA9IGxpbmVhciQyKCkuZG9tYWluKGV4dGVudCkucmFuZ2UocmFuZ2UpOwogICAgICAgICAgICBpZiAodGhpcy5vcHRpb25zLmNvbHVtbnNbY29sSW5kZXhdLnNjYWxlID09PSAnTElORUFSJykgewogICAgICAgICAgICAgICAgcmV0dXJuIGxpbmVhclNjYWxlOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHRoaXMub3B0aW9ucy5jb2x1bW5zW2NvbEluZGV4XS5zY2FsZSA9PT0gJ0xPRycpIHsKICAgICAgICAgICAgICAgIGlmIChleHRlbnRbMF0gPD0gMCAmJiBleHRlbnRbMV0gPj0gMCkgewogICAgICAgICAgICAgICAgICAgIC8vIFdlIGNhbid0IGhhdmUgYSBsb2cgc2NhbGUgZm9yIGRhdGEgd2hvc2UgZXh0ZW50IGNvbnRhaW5zIDAuCiAgICAgICAgICAgICAgICAgICAgLy8gVXNlIGEgbGluZWFyIHNjYWxlIGluc3RlYWQuCiAgICAgICAgICAgICAgICAgICAgLy8gVE9ETyhlcmV6KTogQ3JlYXRlIGEgc3ltbG9nIHNjYWxlIHNpbWlsYXIgdG8gTWF0cGxvdGxpYidzCiAgICAgICAgICAgICAgICAgICAgLy8gc3ltbG9nLiBTZWUgYWxzbyBkMyBpc3N1ZSBoZXJlOgogICAgICAgICAgICAgICAgICAgIC8vIGh0dHBzOi8vZ2l0aHViLmNvbS9kMy9kMy1zY2FsZS9pc3N1ZXMvMTA1CiAgICAgICAgICAgICAgICAgICAgLy8gYW5kIGIvMTExNzU1NTQwCiAgICAgICAgICAgICAgICAgICAgcmV0dXJuIGxpbmVhclNjYWxlOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIGxvZyQxKCkuZG9tYWluKGV4dGVudCkucmFuZ2UocmFuZ2UpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGVsc2UgaWYgKHRoaXMub3B0aW9ucy5jb2x1bW5zW2NvbEluZGV4XS5zY2FsZSA9PT0gJ1FVQU5USUxFJykgewogICAgICAgICAgICAgICAgLy8gQ29tcHV0ZSAyMC1xdWFudGlsZXM6CiAgICAgICAgICAgICAgICBjb25zdCBzdGVwID0gKHJhbmdlWzFdIC0gcmFuZ2VbMF0pIC8gMTk7CiAgICAgICAgICAgICAgICAvLyBDb21wdXRlIHRoZSBzY2FsZSdzIHJhbmdlIHRvIGJlOgogICAgICAgICAgICAgICAgLy8ge3JhbmdlWzBdLCByYW5nZVswXStzdGVwLCAuLi4sIHJhbmdlWzFdfS4KICAgICAgICAgICAgICAgIC8vIGQzLnJhbmdlKHJhbmdlWzBdLCByYW5nZVsxXStzdGVwLCBzdGVwKSBoYXMgbnVtZXJpY2FsCiAgICAgICAgICAgICAgICAvLyBpc3N1ZXMgYW5kIG1heSBwcm9kdWNlIGFuIGV4dHJhIG1lbWJlciwgc28gd2UgdXNlIGEKICAgICAgICAgICAgICAgIC8vIGRpZmZlcmVudCBwcm9jZWR1cmU6CiAgICAgICAgICAgICAgICBjb25zdCBzY2FsZVJhbmdlID0gc2VxdWVuY2UoMjApLm1hcCgoaSkgPT4gcmFuZ2VbMF0gKyBzdGVwICogaSk7CiAgICAgICAgICAgICAgICByZXR1cm4gcXVhbnRpbGUoKQogICAgICAgICAgICAgICAgICAgIC5kb21haW4obG9kYXNoLnVuaXEodGhpcy5zZXNzaW9uR3JvdXBzLm1hcCgoc2cpID0+IHRoaXMuX2NvbFZhbHVlKHNnLCBjb2xJbmRleCkpKSkKICAgICAgICAgICAgICAgICAgICAucmFuZ2Uoc2NhbGVSYW5nZSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSBpZiAodGhpcy5vcHRpb25zLmNvbHVtbnNbY29sSW5kZXhdLnNjYWxlID09PSAnTk9OX05VTUVSSUMnKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gcG9pbnQkMSgpCiAgICAgICAgICAgICAgICAgICAgLmRvbWFpbigKICAgICAgICAgICAgICAgIC8vIFdlIHNvcnQgdGhlIHNlc3Npb24gZ3JvdXBzIHRvIG1ha2UgdGhlIG9yZGVyCiAgICAgICAgICAgICAgICAvLyBzdGFibGUgYWNyb3NzICdMaXN0U2Vzc2lvbkdyb3VwcycgUlBDcwogICAgICAgICAgICAgICAgbG9kYXNoLnVuaXEodGhpcy5zZXNzaW9uR3JvdXBzLm1hcCgoc2cpID0+IHRoaXMuX2NvbFZhbHVlKHNnLCBjb2xJbmRleCkpLnNvcnQoKSkpCiAgICAgICAgICAgICAgICAgICAgLnJhbmdlKHJhbmdlKQogICAgICAgICAgICAgICAgICAgIC5wYWRkaW5nKDAuMSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgZWxzZSB7CiAgICAgICAgICAgICAgICB0aHJvdyAoJ1Vua25vd24gc2NhbGUgZm9yIGNvbHVtbjogJyArIGNvbEluZGV4ICsgJy4gb3B0aW9uczogJyArIHRoaXMub3B0aW9ucyk7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgX2NvbFZhbHVlKHNlc3Npb25Hcm91cCwgY29sSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIGNvbHVtblZhbHVlQnlWaXNpYmxlSW5kZXgodGhpcy52aXNpYmxlU2NoZW1hLCBzZXNzaW9uR3JvdXAsIGNvbEluZGV4KTsKICAgICAgICB9CiAgICAgICAgX21ldHJpY1ZhbHVlKHNlc3Npb25Hcm91cCwgbWV0cmljSW5kZXgpIHsKICAgICAgICAgICAgcmV0dXJuIG1ldHJpY1ZhbHVlQnlWaXNpYmxlSW5kZXgodGhpcy52aXNpYmxlU2NoZW1hLCBzZXNzaW9uR3JvdXAsIG1ldHJpY0luZGV4KTsKICAgICAgICB9CiAgICAgICAgX2NvbEV4dGVudChjb2xJbmRleCkgewogICAgICAgICAgICByZXR1cm4gdmlzaWJsZU51bWVyaWNDb2x1bW5FeHRlbnQodGhpcy52aXNpYmxlU2NoZW1hLCB0aGlzLnNlc3Npb25Hcm91cHMsIGNvbEluZGV4KTsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnRlbXBsYXRlID0gaHRtbCBgCiAgICA8ZGl2IGlkPSJjb250YWluZXIiPgogICAgICA8c3ZnIGlkPSJzdmciPjwvc3ZnPgogICAgPC9kaXY+CgogICAgPHN0eWxlPgogICAgICA6aG9zdCB7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgIH0KICAgICAgc3ZnIHsKICAgICAgICBmb250OiAxMHB4IHNhbnMtc2VyaWY7CiAgICAgIH0KCiAgICAgIC8qIFRoZSBjbG9zZXN0IGRhdGEgcG9pbnQgbWFya2VyIHRvIHRoZSBtb3VzZSBwb2ludGVyLiBXZSB1c2UgIWltcG9ydGFudAogICAgICAgICB0byBvdmVycmlkZSB0aGUgaW5saW5lIHN0eWxlIHRoYXQgc2V0cyB0aGUgcmVndWxhciBzdHlsZSBvZiBhIG1hcmtlci4KICAgICAgKi8KICAgICAgLmNsb3Nlc3QtbWFya2VyIHsKICAgICAgICByOiA2ICFpbXBvcnRhbnQ7CiAgICAgIH0KCiAgICAgIC8qIFRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgZGF0YSBwb2ludCBtYXJrZXIuIFdlIHVzZSAhaW1wb3J0YW50IHRvCiAgICAgICAgIG92ZXJyaWRlIHRoZSBpbmxpbmUgc3R5bGUgdGhhdCBzZXRzIHRoZSByZWd1bGFyIHN0eWxlIG9mIGEgbWFya2VyLiAqLwogICAgICAuc2VsZWN0ZWQtbWFya2VyIHsKICAgICAgICByOiA2ICFpbXBvcnRhbnQ7CiAgICAgICAgZmlsbDogIzBmMCAhaW1wb3J0YW50OwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4UGxvdC5wcm90b3R5cGUsICJ2aXNpYmxlU2NoZW1hIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4UGxvdC5wcm90b3R5cGUsICJzZXNzaW9uR3JvdXBzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgIm9wdGlvbnMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgICAgIG5vdGlmeTogdHJ1ZSwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4UGxvdC5wcm90b3R5cGUsICJzZWxlY3RlZFNlc3Npb25Hcm91cCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgImNsb3Nlc3RTZXNzaW9uR3JvdXAiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBPYmplY3QsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBIVE1MRWxlbWVudCkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4UGxvdC5wcm90b3R5cGUsICJfY29udGFpbmVyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgIl9zdmciLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFBsb3QucHJvdG90eXBlLCAid2lkdGgiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFBsb3QucHJvdG90eXBlLCAiaGVpZ2h0Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgIl9icnVzaGVkQ2VsbEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgIl9icnVzaFNlbGVjdGlvbiIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBvYnNlcnZlKCdzZXNzaW9uR3JvdXBzLionKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4UGxvdC5wcm90b3R5cGUsICJfc2Vzc2lvbkdyb3Vwc0NoYW5nZWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ3Zpc2libGVTY2hlbWEuKicpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90LnByb3RvdHlwZSwgIl92aXNpYmxlU2NoZW1hQ2hhbmdlZCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgnb3B0aW9ucy4qJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBGdW5jdGlvbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnJldHVybnR5cGUiLCB2b2lkIDApCiAgICBdLCBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFBsb3QucHJvdG90eXBlLCAiX3JlZHJhdyIsIG51bGwpOwogICAgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90ID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXBsb3QnKQogICAgXSwgVGZIcGFyYW1zU2NhdHRlclBsb3RNYXRyaXhQbG90KTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogQSBEMy1iYXNlZCBpbXBsZW1lbnRhdGlvbiBvZiBhIHNjYXR0ZXIgcGxvdCBtYXRyaXggb2YgdGhlIHNlc3Npb25zCiAgICAgKiBncm91cHMuCiAgICAgKgogICAgICogRm9yIG1vcmUgZGV0YWlscyBvbiBhIHNjYXR0ZXIgcGxvdCBtYXRyaXggdmlzdWFsaXphdGlvbiBzZWUgZm9yIGV4YW1wbGU6CiAgICAgKiBodHRwczovL3d3dy5pdGwubmlzdC5nb3YvZGl2ODk4L2hhbmRib29rL2VkYS9zZWN0aW9uMy9lZGEzM3FiLmh0bQogICAgICoKICAgICAqIFRoZXJlIGFyZSAzIGVsZW1lbnRzIGludm9sdmVkIGluIHRoZSBzY2F0dGVyIHBsb3QgdmlzdWFsaXphdGlvbjoKICAgICAqCiAgICAgKiAxLiA8dGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXBsb3Q+CiAgICAgKiAgIFJlbmRlcnMgdGhlIGFjdHVhbCBzY2F0dGVyIHBsb3QgbWF0cml4CiAgICAgKiAyLiA8dGYtaHBhcmFtcy1zY2FsZS1hbmQtY29sb3ItY29udHJvbHM+CiAgICAgKiAgIEEgY29udHJvbCBwYW5lbCBmb3IgY29uZmlndXJpbmcgdGhlIGJlaGF2aW9yIG9mIHRoZSBwbG90IChlLmcuIHNjYWxlCiAgICAgKiAgIG9mIGVhY2ggYXhpcywgY29sb3JtYXAsIGV0Yy4pCiAgICAgKiAzLiA8dGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXZpZXc+CiAgICAgKiAgIFRoZSBjb250YWluZXIgZWxlbWVudCBmb3IgdGhlIGFib3ZlIDIgZWxlbWVudHMuCiAgICAgKi8KICAgIGxldCBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFZpZXcgPSBjbGFzcyBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFZpZXcgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgX2Nsb3Nlc3RPclNlbGVjdGVkKGNsb3Nlc3RTZXNzaW9uR3JvdXAsIHNlbGVjdGVkU2Vzc2lvbkdyb3VwKSB7CiAgICAgICAgICAgIGlmIChjbG9zZXN0U2Vzc2lvbkdyb3VwICE9PSBudWxsKSB7CiAgICAgICAgICAgICAgICByZXR1cm4gY2xvc2VzdFNlc3Npb25Hcm91cDsKICAgICAgICAgICAgfQogICAgICAgICAgICByZXR1cm4gc2VsZWN0ZWRTZXNzaW9uR3JvdXA7CiAgICAgICAgfQogICAgfTsKICAgIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4Vmlldy50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPGhwYXJhbXMtc3BsaXQtbGF5b3V0IG9yaWVudGF0aW9uPSJ2ZXJ0aWNhbCI+CiAgICAgIDwhLS0gQ29udHJvbHMgYmVoYXZpb3Igb2YgdGhlIHNjYXR0ZXIgcGxvdCBtYXRyaXgKICAgICAgICAgICAgIG91dHB1dHMgdGhlIGNvbmZpZ3VyZWQgb3B0aW9ucyB0byB0aGUgX29wdGlvbnMgcHJvcGVydHkuIC0tPgogICAgICA8dGYtaHBhcmFtcy1zY2FsZS1hbmQtY29sb3ItY29udHJvbHMKICAgICAgICBzbG90PSJjb250ZW50IgogICAgICAgIGNsYXNzPSJzZWN0aW9uIgogICAgICAgIGlkPSJjb250cm9scyIKICAgICAgICBjb25maWd1cmF0aW9uPSJbW2NvbmZpZ3VyYXRpb25dXSIKICAgICAgICBzZXNzaW9uLWdyb3Vwcz0iW1tzZXNzaW9uR3JvdXBzXV0iCiAgICAgICAgb3B0aW9ucz0ie3tfb3B0aW9uc319IgogICAgICA+CiAgICAgIDwvdGYtaHBhcmFtcy1zY2FsZS1hbmQtY29sb3ItY29udHJvbHM+CiAgICAgIDwhLS0gVGhlIGFjdHVhbCBzY2F0dGVyIHBsb3QgbWF0cml4IC0tPgogICAgICA8dGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXBsb3QKICAgICAgICBzbG90PSJjb250ZW50IgogICAgICAgIGNsYXNzPSJzZWN0aW9uIgogICAgICAgIGlkPSJwbG90IgogICAgICAgIHZpc2libGUtc2NoZW1hPSJbW2NvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYV1dIgogICAgICAgIHNlc3Npb24tZ3JvdXBzPSJbW3Nlc3Npb25Hcm91cHNdXSIKICAgICAgICBzZWxlY3RlZC1zZXNzaW9uLWdyb3VwPSJ7e19zZWxlY3RlZEdyb3VwfX0iCiAgICAgICAgY2xvc2VzdC1zZXNzaW9uLWdyb3VwPSJ7e19jbG9zZXN0R3JvdXB9fSIKICAgICAgICBvcHRpb25zPSJbW19vcHRpb25zXV0iCiAgICAgID4KICAgICAgPC90Zi1ocGFyYW1zLXNjYXR0ZXItcGxvdC1tYXRyaXgtcGxvdD4KICAgICAgPHRmLWhwYXJhbXMtc2Vzc2lvbi1ncm91cC12YWx1ZXMKICAgICAgICBzbG90PSJjb250ZW50IgogICAgICAgIGNsYXNzPSJzZWN0aW9uIgogICAgICAgIGlkPSJ2YWx1ZXMiCiAgICAgICAgdmlzaWJsZS1zY2hlbWE9IltbY29uZmlndXJhdGlvbi52aXNpYmxlU2NoZW1hXV0iCiAgICAgICAgc2Vzc2lvbi1ncm91cD0iW1tfY2xvc2VzdE9yU2VsZWN0ZWQoCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIF9jbG9zZXN0R3JvdXAsIF9zZWxlY3RlZEdyb3VwKV1dIgogICAgICA+CiAgICAgIDwvdGYtaHBhcmFtcy1zZXNzaW9uLWdyb3VwLXZhbHVlcz4KICAgICAgPCEtLSBTaG93cyBzZXNzaW9uIGdyb3VwIGRldGFpbHMgZm9yIHRoZSBjbGlja2VkIG1hcmtlci4gLS0+CiAgICAgIDx0Zi1ocGFyYW1zLXNlc3Npb24tZ3JvdXAtZGV0YWlscwogICAgICAgIHNsb3Q9ImNvbnRlbnQiCiAgICAgICAgY2xhc3M9InNlY3Rpb24iCiAgICAgICAgaWQ9ImRldGFpbHMiCiAgICAgICAgYmFja2VuZD0iW1tiYWNrZW5kXV0iCiAgICAgICAgZXhwZXJpbWVudC1uYW1lPSJbW2V4cGVyaW1lbnROYW1lXV0iCiAgICAgICAgc2Vzc2lvbi1ncm91cD0iW1tfc2VsZWN0ZWRHcm91cF1dIgogICAgICAgIHZpc2libGUtc2NoZW1hPSJbW2NvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYV1dIgogICAgICA+CiAgICAgIDwvdGYtaHBhcmFtcy1zZXNzaW9uLWdyb3VwLWRldGFpbHM+CiAgICA8L2hwYXJhbXMtc3BsaXQtbGF5b3V0PgogICAgPHN0eWxlPgogICAgICAuc2VjdGlvbiB7CiAgICAgICAgcGFkZGluZzogMTBweDsKICAgICAgfQogICAgICAjY29udHJvbHMgewogICAgICAgIGZsZXgtZ3JvdzogMDsKICAgICAgICBmbGV4LXNocmluazogMDsKICAgICAgICBmbGV4LWJhc2lzOiBhdXRvOwogICAgICAgIGhlaWdodDogYXV0bzsKICAgICAgICBvdmVyZmxvdy15OiBhdXRvOwogICAgICAgIG1heC1oZWlnaHQ6IGZpdC1jb250ZW50OwogICAgICB9CiAgICAgICNwbG90IHsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgZmxleC1iYXNpczogYXV0bzsKICAgICAgICBoZWlnaHQ6IGF1dG87CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICBtYXgtaGVpZ2h0OiBmaXQtY29udGVudDsKICAgICAgfQogICAgICAjdmFsdWVzIHsKICAgICAgICBmbGV4LWdyb3c6IDA7CiAgICAgICAgZmxleC1zaHJpbms6IDA7CiAgICAgICAgZmxleC1iYXNpczogYXV0bzsKICAgICAgICBoZWlnaHQ6IDExNXB4OwogICAgICAgIG92ZXJmbG93LXk6IGF1dG87CiAgICAgICAgbWF4LWhlaWdodDogZml0LWNvbnRlbnQ7CiAgICAgIH0KICAgICAgI2RldGFpbHMgewogICAgICAgIGZsZXgtZ3JvdzogMDsKICAgICAgICBmbGV4LXNocmluazogMTsKICAgICAgICBmbGV4LWJhc2lzOiBhdXRvOwogICAgICAgIGhlaWdodDogYXV0bzsKICAgICAgICBvdmVyZmxvdy15OiBhdXRvOwogICAgICAgIG1heC1oZWlnaHQ6IGZpdC1jb250ZW50OwogICAgICB9CiAgICAgIHZhYWRpbi1zcGxpdC1sYXlvdXQgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTY2F0dGVyUGxvdE1hdHJpeFZpZXcucHJvdG90eXBlLCAiYmFja2VuZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4Vmlldy5wcm90b3R5cGUsICJleHBlcmltZW50TmFtZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4Vmlldy5wcm90b3R5cGUsICJjb25maWd1cmF0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4Vmlldy5wcm90b3R5cGUsICJzZXNzaW9uR3JvdXBzIiwgdm9pZCAwKTsKICAgIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4VmlldyA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhwYXJhbXMtc2NhdHRlci1wbG90LW1hdHJpeC12aWV3JykKICAgIF0sIFRmSHBhcmFtc1NjYXR0ZXJQbG90TWF0cml4Vmlldyk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICAvKioKICAgICAqIFRoZSB0Zi1ocGFyYW1zLXNlc3Npb24tcGFuZSBlbGVtZW50IGltcGxlbWVudHMgYSB0YWJiZWQgdmlldyBvZiB0aGUKICAgICAqIHNlc3Npb24gZ3JvdXBzLiBFYWNoIHRhYiBpcyBpbXBsZW1lbnRlZCBieSBpdHMgb3duIGVsZW1lbnQgYW5kIHNob3dzCiAgICAgKiBhIHNwZWNpZmljIHZpZXcgb2YgdGhlIHNlc3Npb24gZ3JvdXBzIGxpc3QuIEV4YW1wbGUgb2Ygdmlld3MgYXJlIGEgdGFibGUtdmlldwogICAgICogYW5kIHBhcmFsbGVsLWNvb3JkaW5hdGVzIChodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9QYXJhbGxlbF9jb29yZGluYXRlcykKICAgICAqIHZpZXcuCiAgICAgKi8KICAgIGxldCBUZkhwYXJhbXNTZXNzaW9uc1BhbmUgPSBjbGFzcyBUZkhwYXJhbXNTZXNzaW9uc1BhbmUgZXh0ZW5kcyBQb2x5bWVyRWxlbWVudCB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX3NlbGVjdGVkVGFiID0gMDsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zU2Vzc2lvbnNQYW5lLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8cGFwZXItaGVhZGVyLXBhbmVsPgogICAgICA8cGFwZXItdG9vbGJhciBzbG90PSJoZWFkZXIiIGNsYXNzPSJ0YWItYmFyIj4KICAgICAgICA8cGFwZXItdGFicyBzZWxlY3RlZD0ie3tfc2VsZWN0ZWRUYWJ9fSIgc2xvdD0idG9wIj4KICAgICAgICAgIDwhLS0gdmlldy1pZCBjYW4gYmUgdXNlZCBieSBpbnRlZ3JhdGlvbiB0ZXN0cyB0byBsb2NhdGUgYSB0YWIuCiAgICAgICAgICAgICAgIEl0IHNob3VsZCBiZSB0aGUgbmFtZSBvZiB0aGUgcm9vdCBlbGVtZW50IGltcGxlbWVudGluZyB0aGUgdmlldwogICAgICAgICAgICAgICB3aXRob3V0IHRoZSAndGYtaHBhcmFtcy0nIHByZWZpeC4gLS0+CiAgICAgICAgICA8cGFwZXItdGFiIHZpZXctaWQ9InRhYmxlLXZpZXciPiBUQUJMRSBWSUVXIDwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYiB2aWV3LWlkPSJwYXJhbGxlbC1jb29yZHMtdmlldyI+CiAgICAgICAgICAgIFBBUkFMTEVMIENPT1JESU5BVEVTIFZJRVcKICAgICAgICAgIDwvcGFwZXItdGFiPgogICAgICAgICAgPHBhcGVyLXRhYiB2aWV3LWlkPSJzY2F0dGVyLXBsb3QtbWF0cml4LXZpZXciPgogICAgICAgICAgICBTQ0FUVEVSIFBMT1QgTUFUUklYIFZJRVcKICAgICAgICAgIDwvcGFwZXItdGFiPgogICAgICAgICAgPGRpdiBjbGFzcz0iaGVscC1hbmQtZmVlZGJhY2siPgogICAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbYnVnUmVwb3J0VXJsXV0iPgogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmJD0iW1tidWdSZXBvcnRVcmxdXSIKICAgICAgICAgICAgICAgIHRhcmdldD0iX2JsYW5rIgogICAgICAgICAgICAgICAgcmVsPSJub29wZW5lciBub3JlZmVycmVyIgogICAgICAgICAgICAgID4KICAgICAgICAgICAgICAgIDxwYXBlci1idXR0b24KICAgICAgICAgICAgICAgICAgaWQ9ImJ1Zy1yZXBvcnQiCiAgICAgICAgICAgICAgICAgIHJhaXNlZAogICAgICAgICAgICAgICAgICB0aXRsZT0iU2VuZCBhIGJ1ZyByZXBvcnQgb3IgZmVhdHVyZSByZXF1ZXN0IgogICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgICBCdWcgUmVwb3J0IC8gRmVhdHVyZSBSZXF1ZXN0CiAgICAgICAgICAgICAgICA8L3BhcGVyLWJ1dHRvbj4KICAgICAgICAgICAgICA8L2E+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1toZWxwVXJsXV0iPgogICAgICAgICAgICAgIDxhIGhyZWYkPSJbW2hlbHBVcmxdXSIgdGFyZ2V0PSJfYmxhbmsiIHJlbD0ibm9vcGVuZXIgbm9yZWZlcnJlciI+CiAgICAgICAgICAgICAgICA8cGFwZXItaWNvbi1idXR0b24KICAgICAgICAgICAgICAgICAgaWNvbj0iaGVscC1vdXRsaW5lIgogICAgICAgICAgICAgICAgICB0aXRsZT0iVmlldyBkb2N1bWVudGF0aW9uIgogICAgICAgICAgICAgICAgPgogICAgICAgICAgICAgICAgPC9wYXBlci1pY29uLWJ1dHRvbj4KICAgICAgICAgICAgICA8L2E+CiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L3BhcGVyLXRhYnM+CiAgICAgIDwvcGFwZXItdG9vbGJhcj4KICAgICAgPGlyb24tcGFnZXMgc2VsZWN0ZWQ9IltbX3NlbGVjdGVkVGFiXV0iIGNsYXNzPSJmaXQgdGFiLXZpZXciPgogICAgICAgIDxkaXYgaWQ9IjAiIGNsYXNzPSJ0YWIiPgogICAgICAgICAgPHRmLWhwYXJhbXMtdGFibGUtdmlldwogICAgICAgICAgICBiYWNrZW5kPSJbW2JhY2tlbmRdXSIKICAgICAgICAgICAgZXhwZXJpbWVudC1uYW1lPSJbW2V4cGVyaW1lbnROYW1lXV0iCiAgICAgICAgICAgIHZpc2libGUtc2NoZW1hPSJbW2NvbmZpZ3VyYXRpb24udmlzaWJsZVNjaGVtYV1dIgogICAgICAgICAgICBzZXNzaW9uLWdyb3Vwcz0iW1tzZXNzaW9uR3JvdXBzXV0iCiAgICAgICAgICAgIGVuYWJsZS1zaG93LW1ldHJpY3MKICAgICAgICAgID4KICAgICAgICAgIDwvdGYtaHBhcmFtcy10YWJsZS12aWV3PgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXYgaWQ9IjEiIGNsYXNzPSJ0YWIiPgogICAgICAgICAgPHRmLWhwYXJhbXMtcGFyYWxsZWwtY29vcmRzLXZpZXcKICAgICAgICAgICAgYmFja2VuZD0iW1tiYWNrZW5kXV0iCiAgICAgICAgICAgIGV4cGVyaW1lbnQtbmFtZT0iW1tleHBlcmltZW50TmFtZV1dIgogICAgICAgICAgICBjb25maWd1cmF0aW9uPSJbW2NvbmZpZ3VyYXRpb25dXSIKICAgICAgICAgICAgc2Vzc2lvbi1ncm91cHM9Iltbc2Vzc2lvbkdyb3Vwc11dIgogICAgICAgICAgPgogICAgICAgICAgPC90Zi1ocGFyYW1zLXBhcmFsbGVsLWNvb3Jkcy12aWV3PgogICAgICAgIDwvZGl2PgogICAgICAgIDxkaXYgaWQ9IjIiIGNsYXNzPSJ0YWIiPgogICAgICAgICAgPHRmLWhwYXJhbXMtc2NhdHRlci1wbG90LW1hdHJpeC12aWV3CiAgICAgICAgICAgIGJhY2tlbmQ9IltbYmFja2VuZF1dIgogICAgICAgICAgICBleHBlcmltZW50LW5hbWU9IltbZXhwZXJpbWVudE5hbWVdXSIKICAgICAgICAgICAgY29uZmlndXJhdGlvbj0iW1tjb25maWd1cmF0aW9uXV0iCiAgICAgICAgICAgIHNlc3Npb24tZ3JvdXBzPSJbW3Nlc3Npb25Hcm91cHNdXSIKICAgICAgICAgID4KICAgICAgICAgIDwvdGYtaHBhcmFtcy1zY2F0dGVyLXBsb3QtbWF0cml4LXZpZXc+CiAgICAgICAgPC9kaXY+CiAgICAgIDwvaXJvbi1wYWdlcz4KICAgIDwvcGFwZXItaGVhZGVyLXBhbmVsPgoKICAgIDxzdHlsZT4KICAgICAgLnRhYi12aWV3IHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgIH0KICAgICAgLnRhYi1iYXIgewogICAgICAgIG92ZXJmbG93LXk6IGF1dG87CiAgICAgICAgY29sb3I6IHdoaXRlOwogICAgICAgIGJhY2tncm91bmQtY29sb3I6IHZhcigKICAgICAgICAgIC0tdGItdG9vbGJhci1iYWNrZ3JvdW5kLWNvbG9yLAogICAgICAgICAgdmFyKC0tdGItb3JhbmdlLXN0cm9uZykKICAgICAgICApOwogICAgICB9CiAgICAgIC50YWIgewogICAgICAgIGhlaWdodDogMTAwJTsKICAgICAgfQogICAgICBwYXBlci10YWJzIHsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICAgIC0tcGFwZXItdGFicy1zZWxlY3Rpb24tYmFyLWNvbG9yOiB3aGl0ZTsKICAgICAgICAtLXBhcGVyLXRhYnMtY29udGVudDogewogICAgICAgICAgLXdlYmtpdC1mb250LXNtb290aGluZzogYW50aWFsaWFzZWQ7CiAgICAgICAgfQogICAgICB9CiAgICAgIHRmLWhwYXJhbXMtdGFibGUtdmlldyB7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgICAgaGVpZ2h0OiAxMDAlOwogICAgICB9CiAgICAgIC5oZWxwLWFuZC1mZWVkYmFjayB7CiAgICAgICAgZGlzcGxheTogaW5saW5lLWZsZXg7IC8qIEVuc3VyZSB0aGF0IGljb25zIHN0YXkgYWxpZ25lZCAqLwogICAgICAgIGp1c3RpZnktY29udGVudDogZmxleC1lbmQ7CiAgICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjsKICAgICAgICB0ZXh0LWFsaWduOiByaWdodDsKICAgICAgICBjb2xvcjogd2hpdGU7CiAgICAgIH0KICAgICAgI2J1Zy1yZXBvcnQgewogICAgICAgIGJvcmRlcjogc29saWQgYmxhY2s7CiAgICAgICAgYmFja2dyb3VuZDogcmVkOwogICAgICAgIHdoaXRlLXNwYWNlOiBub3JtYWw7CiAgICAgICAgd29yZC1icmVhazogYnJlYWstd29yZHM7CiAgICAgICAgZm9udC1zaXplOiAxMnB4OwogICAgICAgIG1heC13aWR0aDogMTUwcHg7CiAgICAgICAgdGV4dC1hbGlnbjogbGVmdDsKICAgICAgfQogICAgICAuaGVscC1hbmQtZmVlZGJhY2sgYSB7CiAgICAgICAgY29sb3I6IHdoaXRlOwogICAgICAgIHRleHQtZGVjb3JhdGlvbjogbm9uZTsKICAgICAgfQogICAgPC9zdHlsZT4KICBgOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNTZXNzaW9uc1BhbmUucHJvdG90eXBlLCAiYmFja2VuZCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25zUGFuZS5wcm90b3R5cGUsICJoZWxwVXJsIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZIcGFyYW1zU2Vzc2lvbnNQYW5lLnByb3RvdHlwZSwgImJ1Z1JlcG9ydFVybCIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IFN0cmluZyB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFN0cmluZykKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25zUGFuZS5wcm90b3R5cGUsICJleHBlcmltZW50TmFtZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25zUGFuZS5wcm90b3R5cGUsICJjb25maWd1cmF0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc1Nlc3Npb25zUGFuZS5wcm90b3R5cGUsICJzZXNzaW9uR3JvdXBzIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogTnVtYmVyLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZIcGFyYW1zU2Vzc2lvbnNQYW5lLnByb3RvdHlwZSwgIl9zZWxlY3RlZFRhYiIsIHZvaWQgMCk7CiAgICBUZkhwYXJhbXNTZXNzaW9uc1BhbmUgPSBfX2RlY29yYXRlKFsKICAgICAgICBjdXN0b21FbGVtZW50KCd0Zi1ocGFyYW1zLXNlc3Npb25zLXBhbmUnKQogICAgXSwgVGZIcGFyYW1zU2Vzc2lvbnNQYW5lKTsKCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qIEEgJ3RmLWhwYXJhbXMtYmFja2VuZCcgZW5jYXBzdWxhdGVzIHNlbmRpbmcgSFBhcmFtcyBBUEkgcmVxdWVzdHMgdG8gdGhlCiAgICAgICBiYWNrZW5kLgogICAgICAgQW55IGltcGxlbWVudGF0aW9uIHdpdGggdGhlIHNhbWUgcHVibGljIGludGVyZmFjZSBjYW4gYmUgcGFzc2VkIHRvCiAgICAgICB0Zi1ocGFyYW1zLW1haW4gYXMgdGhlICdiYWNrZW5kJyBwcm9wZXJ0eS4KICAgICovCiAgICBjbGFzcyBCYWNrZW5kIHsKICAgICAgICAvLyBDb25zdHJ1Y3RzIGEgYmFja2VuZCB0aGF0IHVzZXMgdGhlIGdpdmVuIHRmX2JhY2tlbmQucmVxdWVzdE1hbmFnZXIgdG8KICAgICAgICAvLyBzZW5kIHJlcXVlc3RzLiBUaGUgYXBpVXJsIHBhcmFtZXRlciBzaG91bGQgZGVub3RlIHRoZSBiYXNlCiAgICAgICAgLy8gdXJsIHRvIHVzZS4gSWYgdXNlSHR0cEdldCBpcyB0cnVlIHVzZXMgSFRUUCBHRVQgdG8gc2VuZCBhIHJlcXVlc3QKICAgICAgICAvLyBvdGhlcndpc2UgdXNlcyBIVFRQIFBPU1QuIFNlZSB0ZW5zb3Jib2FyZC9wbHVnaW5zL2hwYXJhbXMvaHR0cF9hcGkubWQKICAgICAgICAvLyBmb3IgZGV0YWlscyBvbiBob3cgdGhlIHJlcXVlc3RzIGFuZCByZXNwb25zZXMgYXJlIGVuY29kZWQgaW4gZWFjaAogICAgICAgIC8vIHNjaGVtZSAoR0VUIG9yIFBPU1QpLgogICAgICAgIGNvbnN0cnVjdG9yKGFwaVVybCwgcmVxdWVzdE1hbmFnZXIsIHVzZUh0dHBHZXQgPSB0cnVlKSB7CiAgICAgICAgICAgIHRoaXMuX2FwaVVybCA9IGFwaVVybDsKICAgICAgICAgICAgdGhpcy5fcmVxdWVzdE1hbmFnZXIgPSByZXF1ZXN0TWFuYWdlcjsKICAgICAgICAgICAgdGhpcy5fdXNlSHR0cEdldCA9IHVzZUh0dHBHZXQ7CiAgICAgICAgfQogICAgICAgIC8vIEluIHRoZSBBUEkgbWV0aG9kcyBiZWxvdywgJ3JlcXVlc3QnIHNob3VsZCBiZSBhIEpTT04gdHJhbnNsYXRlZCByZXF1ZXN0CiAgICAgICAgLy8gcHJvdG9jb2wgYnVmZmVyIGFuZCB0aGUgcmVzcG9uc2UgaXMgYSBKU09OIHRyYW5zbGF0ZWQgcmVzcG9uc2UgcHJvdG9jb2wKICAgICAgICAvLyBidWZmZXIuIFNlZSBhcGkucHJvdG8gZm9yIHRoZSBkZXRhaWxzLgogICAgICAgIGdldEV4cGVyaW1lbnQoZXhwZXJpbWVudFJlcXVlc3QpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NlbmRSZXF1ZXN0KCdleHBlcmltZW50JywgZXhwZXJpbWVudFJlcXVlc3QpOwogICAgICAgIH0KICAgICAgICBnZXREb3dubG9hZFVybChmb3JtYXQsIGxpc3RTZXNzaW9uR3JvdXBzUmVxdWVzdCwgY29sdW1uc1Zpc2liaWxpdHkpIHsKICAgICAgICAgICAgcmV0dXJuICh0aGlzLl9hcGlVcmwgKwogICAgICAgICAgICAgICAgJy9kb3dubG9hZF9kYXRhPycgKwogICAgICAgICAgICAgICAgbmV3IFVSTFNlYXJjaFBhcmFtcyh7CiAgICAgICAgICAgICAgICAgICAgZm9ybWF0OiBmb3JtYXQsCiAgICAgICAgICAgICAgICAgICAgY29sdW1uc1Zpc2liaWxpdHk6IEpTT04uc3RyaW5naWZ5KGNvbHVtbnNWaXNpYmlsaXR5KSwKICAgICAgICAgICAgICAgICAgICByZXF1ZXN0OiBKU09OLnN0cmluZ2lmeShsaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QpLAogICAgICAgICAgICAgICAgfSkpOwogICAgICAgIH0KICAgICAgICBsaXN0U2Vzc2lvbkdyb3VwcyhsaXN0U2Vzc2lvbkdyb3Vwc1JlcXVlc3QpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3NlbmRSZXF1ZXN0KCdzZXNzaW9uX2dyb3VwcycsIGxpc3RTZXNzaW9uR3JvdXBzUmVxdWVzdCk7CiAgICAgICAgfQogICAgICAgIGxpc3RNZXRyaWNFdmFscyhsaXN0TWV0cmljRXZhbHNSZXF1ZXN0KSB7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9zZW5kUmVxdWVzdCgnbWV0cmljX2V2YWxzJywgbGlzdE1ldHJpY0V2YWxzUmVxdWVzdCk7CiAgICAgICAgfQogICAgICAgIC8vIC0tLS0gUHJpdmF0ZSBtZXRob2RzIGJlbG93IC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0KICAgICAgICBfc2VuZFJlcXVlc3QobWV0aG9kTmFtZSwgcmVxdWVzdF9wcm90bykgewogICAgICAgICAgICBpZiAodGhpcy5fdXNlSHR0cEdldCkgewogICAgICAgICAgICAgICAgY29uc3QgZW5jb2RlZFJlcXVlc3QgPSBlbmNvZGVVUklDb21wb25lbnQoSlNPTi5zdHJpbmdpZnkocmVxdWVzdF9wcm90bykpOwogICAgICAgICAgICAgICAgY29uc3QgdXJsID0gdGhpcy5fYXBpVXJsICsgJy8nICsgbWV0aG9kTmFtZSArICc/cmVxdWVzdD0nICsgZW5jb2RlZFJlcXVlc3Q7CiAgICAgICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdCh1cmwpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIC8qIFVzZSBQT1NUICovCiAgICAgICAgICAgIGNvbnN0IHJlcXVlc3RPcHRpb25zID0gbmV3IFJlcXVlc3RPcHRpb25zKCk7CiAgICAgICAgICAgIHJlcXVlc3RPcHRpb25zLndpdGhDcmVkZW50aWFscyA9IHRydWU7CiAgICAgICAgICAgIHJlcXVlc3RPcHRpb25zLm1ldGhvZFR5cGUgPSBIdHRwTWV0aG9kVHlwZS5QT1NUOwogICAgICAgICAgICByZXF1ZXN0T3B0aW9ucy5jb250ZW50VHlwZSA9ICd0ZXh0L3BsYWluJzsKICAgICAgICAgICAgcmVxdWVzdE9wdGlvbnMuYm9keSA9IEpTT04uc3RyaW5naWZ5KHJlcXVlc3RfcHJvdG8pOwogICAgICAgICAgICBjb25zdCB1cmwgPSB0aGlzLl9hcGlVcmwgKyAnLycgKyBtZXRob2ROYW1lOwogICAgICAgICAgICByZXR1cm4gdGhpcy5fcmVxdWVzdE1hbmFnZXIucmVxdWVzdFdpdGhPcHRpb25zKHVybCwgcmVxdWVzdE9wdGlvbnMpOwogICAgICAgIH0KICAgIH0KCiAgICAvKiBDb3B5cmlnaHQgMjAyMCBUaGUgVGVuc29yRmxvdyBBdXRob3JzLiBBbGwgUmlnaHRzIFJlc2VydmVkLgoKICAgIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSAiTGljZW5zZSIpOwogICAgeW91IG1heSBub3QgdXNlIHRoaXMgZmlsZSBleGNlcHQgaW4gY29tcGxpYW5jZSB3aXRoIHRoZSBMaWNlbnNlLgogICAgWW91IG1heSBvYnRhaW4gYSBjb3B5IG9mIHRoZSBMaWNlbnNlIGF0CgogICAgICAgIGh0dHA6Ly93d3cuYXBhY2hlLm9yZy9saWNlbnNlcy9MSUNFTlNFLTIuMAoKICAgIFVubGVzcyByZXF1aXJlZCBieSBhcHBsaWNhYmxlIGxhdyBvciBhZ3JlZWQgdG8gaW4gd3JpdGluZywgc29mdHdhcmUKICAgIGRpc3RyaWJ1dGVkIHVuZGVyIHRoZSBMaWNlbnNlIGlzIGRpc3RyaWJ1dGVkIG9uIGFuICJBUyBJUyIgQkFTSVMsCiAgICBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC4KICAgIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmQKICAgIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLgogICAgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ki8KICAgIC8qKgogICAgICogVGhlIGVudHJ5IHBvaW50IGludG8gdGhlIGhwYXJhbXMgcGx1Z2luIGZyb250ZW5kLgogICAgICogQSBjb250YWluZXIgZm9yIHR3byBzdWItZWxlbWVudHM6CiAgICAgKiAxLiBUaGUgcXVlcnktcGFuZSBlbmNhcHN1bGF0ZWQgYnkgdGhlIHRmLWhwYXJhbXMtcXVlcnktcGFuZSBlbGVtZW50LiBUaGlzCiAgICAgKiBlbGVtZW50IGlzc3VlcyBxdWVyaWVzIHRvIHRoZSBiYWNrZW5kIHRvIGdldCBhIGxpc3Qgb2Ygc2Vzc2lvbiBncm91cHMuIEl0IGhhcwogICAgICogY29udHJvbHMgdG8gYWxsb3cgdGhlIHVzZXIgdG8gc3BlY2lmeSBmaWx0ZXJzIGFuZCBzb3J0aW5nIG9wdGlvbnMgaW4gdGhlCiAgICAgKiBpc3N1ZWQtcXVlcnkuIFRoZSBhY3R1YWwgZmlsdGVyaW5nIGFuZCBzb3J0aW5nIGlzIGRvbmUgYnkgdGhlIGJhY2tlbmQuCiAgICAgKiAyLiBUaGUgc2Vzc2lvbi1wYW5lIGVuY2Fwc3VsYXRlZCBieSB0aGUgdGYtaHBhcmFtcy1zZXNzaW9uLXBhbmUgZWxlbWVudC4gVGhpcwogICAgICogZWxlbWVudCBkaXNwbGF5cyBtdWx0aXBsZSB0YWJzLS1lYWNoIHByb3ZpZGluZyBhICJ2aWV3IiBvZiB0aGUgbGlzdCBvZgogICAgICogc2Vzc2lvbiBncm91cHMuIEV4YW1wbGUgb2Ygdmlld3MgYXJlIGEgdGFibGUtdmlldyBhbmQgYSBwYXJhbGxlbC1jb29yZGluYXRlCiAgICAgKiB2aWV3LgogICAgICoKICAgICAqIFRPRE8oZXJleik6IEFkZCBhZ2dyZWdhdGlvbiBvZiByZXBlYXRlZCB0cmlhbHMuCiAgICAgKi8KICAgIGxldCBUZkhwYXJhbXNNYWluID0gY2xhc3MgVGZIcGFyYW1zTWFpbiBleHRlbmRzIExlZ2FjeUVsZW1lbnRNaXhpbihQb2x5bWVyRWxlbWVudCkgewogICAgICAgIC8vIFRoaXMgY2FuIGJlIGNhbGxlZCB0byByZWZyZXNoIHRoZSBwbHVnaW4uCiAgICAgICAgcmVsb2FkKCkgewogICAgICAgICAgICB0aGlzLiRbJ3F1ZXJ5LXBhbmUnXS5yZWxvYWQoKTsKICAgICAgICB9CiAgICB9OwogICAgVGZIcGFyYW1zTWFpbi50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPGhwYXJhbXMtc3BsaXQtbGF5b3V0PgogICAgICA8ZGl2IHNsb3Q9ImNvbnRlbnQiIGNsYXNzPSJzaWRlYmFyIj4KICAgICAgICA8dGYtaHBhcmFtcy1xdWVyeS1wYW5lCiAgICAgICAgICBpZD0icXVlcnktcGFuZSIKICAgICAgICAgIGJhY2tlbmQ9IltbYmFja2VuZF1dIgogICAgICAgICAgZXhwZXJpbWVudC1uYW1lPSJbW2V4cGVyaW1lbnROYW1lXV0iCiAgICAgICAgICBjb25maWd1cmF0aW9uPSJ7e19jb25maWd1cmF0aW9ufX0iCiAgICAgICAgICBzZXNzaW9uLWdyb3Vwcz0ie3tfc2Vzc2lvbkdyb3Vwc319IgogICAgICAgICAgZGF0YS1sb2FkZWQtd2l0aC1ub24tZW1wdHktaHBhcmFtcz0ie3tfZGF0YUxvYWRlZFdpdGhOb25FbXB0eUhwYXJhbXN9fSIKICAgICAgICAgIGRhdGEtbG9hZGVkLXdpdGgtZW1wdHktaHBhcmFtcz0ie3tfZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXN9fSIKICAgICAgICA+CiAgICAgICAgPC90Zi1ocGFyYW1zLXF1ZXJ5LXBhbmU+CiAgICAgIDwvZGl2PgogICAgICA8ZGl2IHNsb3Q9ImNvbnRlbnQiIGNsYXNzPSJjZW50ZXIiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZGF0YUxvYWRlZFdpdGhFbXB0eUhwYXJhbXNdXSI+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJuby1kYXRhLXdhcm5pbmciPgogICAgICAgICAgICA8aDM+Tm8gaHBhcmFtcyBkYXRhIHdhcyBmb3VuZC48L2gzPgogICAgICAgICAgICA8cD5Qcm9iYWJsZSBjYXVzZXM6PC9wPgogICAgICAgICAgICA8dWw+CiAgICAgICAgICAgICAgPGxpPllvdSBoYXZlbuKAmXQgd3JpdHRlbiBhbnkgaHBhcmFtcyBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgICA8bGk+CiAgICAgICAgICAgICAgICBFdmVudCBmaWxlcyBhcmUgc3RpbGwgYmVpbmcgbG9hZGVkICh0cnkgcmVsb2FkaW5nIHRoaXMgcGFnZSkuCiAgICAgICAgICAgICAgPC9saT4KICAgICAgICAgICAgICA8bGk+VGVuc29yQm9hcmQgY2Fu4oCZdCBmaW5kIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgPC91bD4KCiAgICAgICAgICAgIDxwPgogICAgICAgICAgICAgIElmIHlvdeKAmXJlIG5ldyB0byB1c2luZyBUZW5zb3JCb2FyZCwgYW5kIHdhbnQgdG8gZmluZCBvdXQgaG93IHRvCiAgICAgICAgICAgICAgYWRkIGRhdGEgYW5kIHNldCB1cCB5b3VyIGV2ZW50IGZpbGVzLCBjaGVjayBvdXQgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS90ZW5zb3JmbG93L3RlbnNvcmJvYXJkL2Jsb2IvbWFzdGVyL1JFQURNRS5tZCIKICAgICAgICAgICAgICAgID5SRUFETUU8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIHBlcmhhcHMgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vd3d3LnRlbnNvcmZsb3cub3JnL2dldF9zdGFydGVkL3N1bW1hcmllc19hbmRfdGVuc29yYm9hcmQiCiAgICAgICAgICAgICAgICA+VGVuc29yQm9hcmQgdHV0b3JpYWw8L2EKICAgICAgICAgICAgICA+LgogICAgICAgICAgICA8L3A+CgogICAgICAgICAgICA8cD4KICAgICAgICAgICAgICBJZiB5b3UgdGhpbmsgVGVuc29yQm9hcmQgaXMgY29uZmlndXJlZCBwcm9wZXJseSwgcGxlYXNlIHNlZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9ibG9iL21hc3Rlci9SRUFETUUubWQjbXktdGVuc29yYm9hcmQtaXNudC1zaG93aW5nLWFueS1kYXRhLXdoYXRzLXdyb25nIgogICAgICAgICAgICAgICAgPnRoZSBzZWN0aW9uIG9mIHRoZSBSRUFETUUgZGV2b3RlZCB0byBtaXNzaW5nIGRhdGEgcHJvYmxlbXM8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIGNvbnNpZGVyIGZpbGluZyBhbiBpc3N1ZSBvbiBHaXRIdWIuCiAgICAgICAgICAgIDwvcD4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZGF0YUxvYWRlZFdpdGhOb25FbXB0eUhwYXJhbXNdXSI+CiAgICAgICAgICA8dGYtaHBhcmFtcy1zZXNzaW9ucy1wYW5lCiAgICAgICAgICAgIGlkPSJzZXNzaW9ucy1wYW5lIgogICAgICAgICAgICBiYWNrZW5kPSJbW2JhY2tlbmRdXSIKICAgICAgICAgICAgaGVscC11cmw9IltbaGVscFVybF1dIgogICAgICAgICAgICBidWctcmVwb3J0LXVybD0iW1tidWdSZXBvcnRVcmxdXSIKICAgICAgICAgICAgZXhwZXJpbWVudC1uYW1lPSJbW2V4cGVyaW1lbnROYW1lXV0iCiAgICAgICAgICAgIGNvbmZpZ3VyYXRpb249IltbX2NvbmZpZ3VyYXRpb25dXSIKICAgICAgICAgICAgc2Vzc2lvbi1ncm91cHM9IltbX3Nlc3Npb25Hcm91cHNdXSIKICAgICAgICAgID4KICAgICAgICAgIDwvdGYtaHBhcmFtcy1zZXNzaW9ucy1wYW5lPgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgPC9ocGFyYW1zLXNwbGl0LWxheW91dD4KICAgIDxzdHlsZT4KICAgICAgaHBhcmFtcy1zcGxpdC1sYXlvdXQgewogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICB9CgogICAgICAuc2lkZWJhciB7CiAgICAgICAgd2lkdGg6IDIwJTsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgb3ZlcmZsb3c6IGF1dG87CiAgICAgICAgZmxleC1ncm93OiAwOwogICAgICAgIGZsZXgtc2hyaW5rOiAwOwogICAgICAgIG1pbi13aWR0aDogMTAlOwogICAgICB9CgogICAgICAuY2VudGVyIHsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgb3ZlcmZsb3cteTogYXV0bzsKICAgICAgICBmbGV4LWdyb3c6IDE7CiAgICAgICAgZmxleC1zaHJpbms6IDE7CiAgICAgICAgd2lkdGg6IDgwJTsKICAgICAgfQoKICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGZsZXg7CiAgICAgICAgZmxleC1kaXJlY3Rpb246IHJvdzsKICAgICAgICBoZWlnaHQ6IDEwMCU7CiAgICAgICAgd2lkdGg6IDEwMCU7CiAgICAgIH0KCiAgICAgIC5uby1kYXRhLXdhcm5pbmcgewogICAgICAgIG1heC13aWR0aDogNTQwcHg7CiAgICAgICAgbWFyZ2luOiA4MHB4IGF1dG8gMCBhdXRvOwogICAgICB9CiAgICA8L3N0eWxlPgogIGA7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJhY2tlbmQpCiAgICBdLCBUZkhwYXJhbXNNYWluLnByb3RvdHlwZSwgImJhY2tlbmQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkhwYXJhbXNNYWluLnByb3RvdHlwZSwgImV4cGVyaW1lbnROYW1lIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZIcGFyYW1zTWFpbi5wcm90b3R5cGUsICJoZWxwVXJsIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZIcGFyYW1zTWFpbi5wcm90b3R5cGUsICJidWdSZXBvcnRVcmwiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkhwYXJhbXNNYWluLnByb3RvdHlwZSwgIl9jb25maWd1cmF0aW9uIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQXJyYXkgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBBcnJheSkKICAgIF0sIFRmSHBhcmFtc01haW4ucHJvdG90eXBlLCAiX3Nlc3Npb25Hcm91cHMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSHBhcmFtc01haW4ucHJvdG90eXBlLCAiX2RhdGFMb2FkZWRXaXRoTm9uRW1wdHlIcGFyYW1zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkhwYXJhbXNNYWluLnByb3RvdHlwZSwgIl9kYXRhTG9hZGVkV2l0aEVtcHR5SHBhcmFtcyIsIHZvaWQgMCk7CiAgICBUZkhwYXJhbXNNYWluID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtaHBhcmFtcy1tYWluJykKICAgIF0sIFRmSHBhcmFtc01haW4pOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLy8gUmVhZCBVUkwgYXQgbW9kdWxlIGltcG9ydCB0aW1lLCBiZWZvcmUgQXBwUm91dGluZ0VmZmVjdHMgc3RvbXBzIGl0LgogICAgY29uc3QgaW5Db2xhYiA9IG5ldyBVUkxTZWFyY2hQYXJhbXMod2luZG93LmxvY2F0aW9uLnNlYXJjaCkuZ2V0KCd0ZW5zb3Jib2FyZENvbGFiJykgPT09CiAgICAgICAgJ3RydWUnOwogICAgY29uc3QgUExVR0lOX05BTUUgPSAnaHBhcmFtcyc7CiAgICBsZXQgVGZIcGFyYW1zRGFzaGJvYXJkID0gY2xhc3MgVGZIcGFyYW1zRGFzaGJvYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMuX2JhY2tlbmQgPSBuZXcgQmFja2VuZCgKICAgICAgICAgICAgLyogYXBpVXJsPSAqLyBnZXRSb3V0ZXIoKQogICAgICAgICAgICAgICAgLnBsdWdpblJvdXRlKC8qIHBsdWdpbk5hbWU9ICovIFBMVUdJTl9OQU1FLCAvKiByb3V0ZT0gKi8gJycpLCBuZXcgUmVxdWVzdE1hbmFnZXIoKSwgCiAgICAgICAgICAgIC8qIFVzZSBHRVRzIGlmIHdlJ3JlIHJ1bm5pbmcgaW4gY29sYWIgKGR1ZSB0byBiLzEyNjM4NzEwNikuCiAgICAgICAgICAgICAgICAgIE90aGVyd2lzZSB1c2UgUE9TVHMuICovCiAgICAgICAgICAgIC8qIHVzZUh0dHBHZXQ9ICovIGluQ29sYWIpOwogICAgICAgIH0KICAgICAgICAvLyBUaGlzIGlzIGNhbGxlZCBieSB0aGUgdGVuc29yYm9hcmQgd2ViIGZyYW1ld29yayB0byByZWZyZXNoIHRoZSBwbHVnaW4uCiAgICAgICAgcmVsb2FkKCkgewogICAgICAgICAgICB0aGlzLiRbJ2hwYXJhbXMtbWFpbiddLnJlbG9hZCgpOwogICAgICAgIH0KICAgIH07CiAgICBUZkhwYXJhbXNEYXNoYm9hcmQudGVtcGxhdGUgPSBodG1sIGAKICAgIDwhLS0gVGVuc29yQm9hcmQgZG9lcyBub3Qgc3BlY2lmeSBhbiBleHBlcmltZW50TmFtZS4gQ3VycmVudGx5IGl0IG9ubHkKICAgICAgICAgc3VwcG9ydHMgb25lIGV4cGVyaW1lbnQgcGVyIGludm9jYXRpb24uIC0tPgogICAgPHRmLWhwYXJhbXMtbWFpbgogICAgICBpZD0iaHBhcmFtcy1tYWluIgogICAgICBiYWNrZW5kPSJbW19iYWNrZW5kXV0iCiAgICAgIGV4cGVyaW1lbnQtbmFtZT0iIgogICAgPgogICAgPC90Zi1ocGFyYW1zLW1haW4+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZIcGFyYW1zRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9iYWNrZW5kIiwgdm9pZCAwKTsKICAgIFRmSHBhcmFtc0Rhc2hib2FyZCA9IF9fZGVjb3JhdGUoWwogICAgICAgIGN1c3RvbUVsZW1lbnQoJ3RmLWhwYXJhbXMtZGFzaGJvYXJkJykKICAgIF0sIFRmSHBhcmFtc0Rhc2hib2FyZCk7CgogICAgLyogQ29weXJpZ2h0IDIwMjAgVGhlIFRlbnNvckZsb3cgQXV0aG9ycy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC4KCiAgICBMaWNlbnNlZCB1bmRlciB0aGUgQXBhY2hlIExpY2Vuc2UsIFZlcnNpb24gMi4wICh0aGUgIkxpY2Vuc2UiKTsKICAgIHlvdSBtYXkgbm90IHVzZSB0aGlzIGZpbGUgZXhjZXB0IGluIGNvbXBsaWFuY2Ugd2l0aCB0aGUgTGljZW5zZS4KICAgIFlvdSBtYXkgb2J0YWluIGEgY29weSBvZiB0aGUgTGljZW5zZSBhdAoKICAgICAgICBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjAKCiAgICBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlCiAgICBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiAiQVMgSVMiIEJBU0lTLAogICAgV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuCiAgICBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kCiAgICBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS4KICAgID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSovCiAgICBsZXQgVGZJbWFnZUxvYWRlciA9IGNsYXNzIFRmSW1hZ2VMb2FkZXIgZXh0ZW5kcyBMZWdhY3lFbGVtZW50TWl4aW4oUG9seW1lckVsZW1lbnQpIHsKICAgICAgICBjb25zdHJ1Y3RvcigpIHsKICAgICAgICAgICAgc3VwZXIoLi4uYXJndW1lbnRzKTsKICAgICAgICAgICAgdGhpcy5hY3R1YWxTaXplID0gZmFsc2U7CiAgICAgICAgICAgIHRoaXMuYnJpZ2h0bmVzc0FkanVzdG1lbnQgPSAwLjU7CiAgICAgICAgICAgIHRoaXMuY29udHJhc3RQZXJjZW50YWdlID0gMDsKICAgICAgICAgICAgdGhpcy5fbWV0YWRhdGFDYW5jZWxsZXIgPSBuZXcgQ2FuY2VsbGVyKCk7CiAgICAgICAgICAgIHRoaXMuX2ltYWdlQ2FuY2VsbGVyID0gbmV3IENhbmNlbGxlcigpOwogICAgICAgICAgICB0aGlzLl9zdGVwcyA9IFtdOwogICAgICAgICAgICB0aGlzLl9pc0ltYWdlTG9hZGluZyA9IGZhbHNlOwogICAgICAgIH0KICAgICAgICBnZXQgX3J1bkNvbG9yKCkgewogICAgICAgICAgICB2YXIgcnVuID0gdGhpcy5ydW47CiAgICAgICAgICAgIHJldHVybiBydW5zQ29sb3JTY2FsZShydW4pOwogICAgICAgIH0KICAgICAgICBnZXQgX2hhc0F0TGVhc3RPbmVTdGVwKCkgewogICAgICAgICAgICB2YXIgc3RlcHMgPSB0aGlzLl9zdGVwczsKICAgICAgICAgICAgcmV0dXJuICEhc3RlcHMgJiYgc3RlcHMubGVuZ3RoID4gMDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9oYXNNdWx0aXBsZVN0ZXBzKCkgewogICAgICAgICAgICB2YXIgc3RlcHMgPSB0aGlzLl9zdGVwczsKICAgICAgICAgICAgcmV0dXJuICEhc3RlcHMgJiYgc3RlcHMubGVuZ3RoID4gMTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jdXJyZW50U3RlcCgpIHsKICAgICAgICAgICAgdmFyIHN0ZXBzID0gdGhpcy5fc3RlcHM7CiAgICAgICAgICAgIHZhciBzdGVwSW5kZXggPSB0aGlzLl9zdGVwSW5kZXg7CiAgICAgICAgICAgIHJldHVybiBzdGVwc1tzdGVwSW5kZXhdIHx8IG51bGw7CiAgICAgICAgfQogICAgICAgIGdldCBfc3RlcFZhbHVlKCkgewogICAgICAgICAgICB2YXIgY3VycmVudFN0ZXAgPSB0aGlzLl9jdXJyZW50U3RlcDsKICAgICAgICAgICAgaWYgKCFjdXJyZW50U3RlcCkKICAgICAgICAgICAgICAgIHJldHVybiAwOwogICAgICAgICAgICByZXR1cm4gY3VycmVudFN0ZXAuc3RlcDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jdXJyZW50V2FsbFRpbWUoKSB7CiAgICAgICAgICAgIHZhciBjdXJyZW50U3RlcCA9IHRoaXMuX2N1cnJlbnRTdGVwOwogICAgICAgICAgICBpZiAoIWN1cnJlbnRTdGVwKQogICAgICAgICAgICAgICAgcmV0dXJuICcnOwogICAgICAgICAgICByZXR1cm4gZm9ybWF0RGF0ZSQxKGN1cnJlbnRTdGVwLndhbGxfdGltZSk7CiAgICAgICAgfQogICAgICAgIGdldCBfbWF4U3RlcEluZGV4KCkgewogICAgICAgICAgICB2YXIgc3RlcHMgPSB0aGlzLl9zdGVwczsKICAgICAgICAgICAgcmV0dXJuIHN0ZXBzLmxlbmd0aCAtIDE7CiAgICAgICAgfQogICAgICAgIGdldCBfc2FtcGxlVGV4dCgpIHsKICAgICAgICAgICAgdmFyIHNhbXBsZSA9IHRoaXMuc2FtcGxlOwogICAgICAgICAgICByZXR1cm4gYCR7c2FtcGxlICsgMX1gOwogICAgICAgIH0KICAgICAgICBnZXQgX2hhc011bHRpcGxlU2FtcGxlcygpIHsKICAgICAgICAgICAgdmFyIG9mU2FtcGxlcyA9IHRoaXMub2ZTYW1wbGVzOwogICAgICAgICAgICByZXR1cm4gb2ZTYW1wbGVzID4gMTsKICAgICAgICB9CiAgICAgICAgX2dldEFyaWFFeHBhbmRlZCgpIHsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuYWN0dWFsU2l6ZSA/ICd0cnVlJyA6ICdmYWxzZSc7CiAgICAgICAgfQogICAgICAgIGF0dGFjaGVkKCkgewogICAgICAgICAgICB0aGlzLnJlbG9hZCgpOwogICAgICAgIH0KICAgICAgICByZWxvYWQoKSB7CiAgICAgICAgICAgIGlmICghdGhpcy5pc0F0dGFjaGVkKSB7CiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIH0KICAgICAgICAgICAgdGhpcy5fbWV0YWRhdGFDYW5jZWxsZXIuY2FuY2VsQWxsKCk7CiAgICAgICAgICAgIGNvbnN0IHJvdXRlciA9IGdldFJvdXRlcigpOwogICAgICAgICAgICBjb25zdCB1cmwgPSBhZGRQYXJhbXMocm91dGVyLnBsdWdpblJvdXRlKCdpbWFnZXMnLCAnL2ltYWdlcycpLCB7CiAgICAgICAgICAgICAgICB0YWc6IHRoaXMudGFnLAogICAgICAgICAgICAgICAgcnVuOiB0aGlzLnJ1biwKICAgICAgICAgICAgICAgIHNhbXBsZTogdGhpcy5zYW1wbGUsCiAgICAgICAgICAgIH0pOwogICAgICAgICAgICBjb25zdCB1cGRhdGVTdGVwcyA9IHRoaXMuX21ldGFkYXRhQ2FuY2VsbGVyLmNhbmNlbGxhYmxlKChyZXN1bHQpID0+IHsKICAgICAgICAgICAgICAgIGlmIChyZXN1bHQuY2FuY2VsbGVkKSB7CiAgICAgICAgICAgICAgICAgICAgcmV0dXJuOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgY29uc3QgZGF0YSA9IHJlc3VsdC52YWx1ZTsKICAgICAgICAgICAgICAgIGNvbnN0IHN0ZXBzID0gZGF0YS5tYXAodGhpcy5fY3JlYXRlU3RlcERhdHVtLmJpbmQodGhpcykpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19zdGVwcycsIHN0ZXBzKTsKICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfc3RlcEluZGV4Jywgc3RlcHMubGVuZ3RoIC0gMSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICB0aGlzLnJlcXVlc3RNYW5hZ2VyLnJlcXVlc3QodXJsKS50aGVuKHVwZGF0ZVN0ZXBzKTsKICAgICAgICB9CiAgICAgICAgX2NyZWF0ZVN0ZXBEYXR1bShpbWFnZU1ldGFkYXRhKSB7CiAgICAgICAgICAgIGxldCB1cmwgPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnaW1hZ2VzJywgJy9pbmRpdmlkdWFsSW1hZ2UnKTsKICAgICAgICAgICAgLy8gSW5jbHVkZSB3YWxsX3RpbWUganVzdCB0byBkaXNhbWJpZ3VhdGUgdGhlIFVSTCBhbmQgZm9yY2UKICAgICAgICAgICAgLy8gdGhlIGJyb3dzZXIgdG8gcmVsb2FkIHRoZSBpbWFnZSB3aGVuIHRoZSBVUkwgY2hhbmdlcy4gVGhlCiAgICAgICAgICAgIC8vIGJhY2tlbmQgZG9lc24ndCBjYXJlIGFib3V0IHRoZSB2YWx1ZS4KICAgICAgICAgICAgdXJsID0gYWRkUGFyYW1zKHVybCwgeyB0czogaW1hZ2VNZXRhZGF0YS53YWxsX3RpbWUgfSk7CiAgICAgICAgICAgIHVybCArPSAnJicgKyBpbWFnZU1ldGFkYXRhLnF1ZXJ5OwogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgLy8gVGhlIHdhbGwgdGltZSB3aXRoaW4gdGhlIG1ldGFkYXRhIGlzIGluIHNlY29uZHMuIFRoZSBEYXRlCiAgICAgICAgICAgICAgICAvLyBjb25zdHJ1Y3RvciBhY2NlcHRzIGEgdGltZSBpbiBtaWxsaXNlY29uZHMsIHNvIHdlIG11bHRpcGx5IGJ5IDEwMDAuCiAgICAgICAgICAgICAgICB3YWxsX3RpbWU6IG5ldyBEYXRlKGltYWdlTWV0YWRhdGEud2FsbF90aW1lICogMTAwMCksCiAgICAgICAgICAgICAgICBzdGVwOiBpbWFnZU1ldGFkYXRhLnN0ZXAsCiAgICAgICAgICAgICAgICB1cmwsCiAgICAgICAgICAgIH07CiAgICAgICAgfQogICAgICAgIF91cGRhdGVJbWFnZVVybCgpIHsKICAgICAgICAgICAgdmFyIGN1cnJlbnRTdGVwID0gdGhpcy5fY3VycmVudFN0ZXA7CiAgICAgICAgICAgIHZhciBicmlnaHRuZXNzQWRqdXN0bWVudCA9IHRoaXMuYnJpZ2h0bmVzc0FkanVzdG1lbnQ7CiAgICAgICAgICAgIHZhciBjb250cmFzdFBlcmNlbnRhZ2UgPSB0aGlzLmNvbnRyYXN0UGVyY2VudGFnZTsKICAgICAgICAgICAgLy8gV2UgbWFudWFsbHkgY2hhbmdlIHRoZSBpbWFnZSBVUkwgKGluc3RlYWQgb2YgYmluZGluZyB0byB0aGUKICAgICAgICAgICAgLy8gaW1hZ2UncyBzcmMgYXR0cmlidXRlKSBiZWNhdXNlIHdlIHdvdWxkIGxpa2UgdG8gbWFuYWdlIHdoYXQKICAgICAgICAgICAgLy8gaGFwcGVucyB3aGVuIHRoZSBpbWFnZSBzdGFydHMgYW5kIHN0b3BzIGxvYWRpbmcuCiAgICAgICAgICAgIGlmICghY3VycmVudFN0ZXApCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIGNvbnN0IGltZyA9IG5ldyBJbWFnZSgpOwogICAgICAgICAgICB0aGlzLl9pbWFnZUNhbmNlbGxlci5jYW5jZWxBbGwoKTsKICAgICAgICAgICAgaW1nLm9ubG9hZCA9IGltZy5vbmVycm9yID0gdGhpcy5faW1hZ2VDYW5jZWxsZXIKICAgICAgICAgICAgICAgIC5jYW5jZWxsYWJsZSgocmVzdWx0KSA9PiB7CiAgICAgICAgICAgICAgICBpZiAocmVzdWx0LmNhbmNlbGxlZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybjsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgIGNvbnN0IG1haW5JbWFnZUNvbnRhaW5lciA9IHRoaXMuJCQoJyNtYWluLWltYWdlLWNvbnRhaW5lcicpOwogICAgICAgICAgICAgICAgbWFpbkltYWdlQ29udGFpbmVyLnRleHRDb250ZW50ID0gJyc7CiAgICAgICAgICAgICAgICBkb20obWFpbkltYWdlQ29udGFpbmVyKS5hcHBlbmRDaGlsZChpbWcpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19pc0ltYWdlTG9hZGluZycsIGZhbHNlKTsKICAgICAgICAgICAgfSkKICAgICAgICAgICAgICAgIC5iaW5kKHRoaXMpOwogICAgICAgICAgICBpbWcuc3R5bGUuZmlsdGVyID0gYGNvbnRyYXN0KCR7Y29udHJhc3RQZXJjZW50YWdlfSUpIGA7CiAgICAgICAgICAgIGltZy5zdHlsZS5maWx0ZXIgKz0gYGJyaWdodG5lc3MoJHticmlnaHRuZXNzQWRqdXN0bWVudH0pYDsKICAgICAgICAgICAgLy8gTG9hZCB0aGUgbmV3IGltYWdlLgogICAgICAgICAgICB0aGlzLnNldCgnX2lzSW1hZ2VMb2FkaW5nJywgdHJ1ZSk7CiAgICAgICAgICAgIGltZy5zcmMgPSBjdXJyZW50U3RlcC51cmw7CiAgICAgICAgfQogICAgICAgIF9oYW5kbGVUYXAoZSkgewogICAgICAgICAgICB0aGlzLnNldCgnYWN0dWFsU2l6ZScsICF0aGlzLmFjdHVhbFNpemUpOwogICAgICAgIH0KICAgICAgICBfdG9Mb2NhbGVTdHJpbmcobnVtYmVyKSB7CiAgICAgICAgICAgIC8vIFNob3dzIGNvbW1hcyAob3IgbG9jYWxlLWFwcHJvcHJpYXRlIHB1bmN0dWF0aW9uKSBmb3IgbGFyZ2UgbnVtYmVycy4KICAgICAgICAgICAgcmV0dXJuIG51bWJlci50b0xvY2FsZVN0cmluZygpOwogICAgICAgIH0KICAgIH07CiAgICBUZkltYWdlTG9hZGVyLnRlbXBsYXRlID0gaHRtbCBgCiAgICA8dGYtY2FyZC1oZWFkaW5nCiAgICAgIHRhZz0iW1t0YWddXSIKICAgICAgcnVuPSJbW3J1bl1dIgogICAgICBkaXNwbGF5LW5hbWU9IltbdGFnTWV0YWRhdGEuZGlzcGxheU5hbWVdXSIKICAgICAgZGVzY3JpcHRpb249IltbdGFnTWV0YWRhdGEuZGVzY3JpcHRpb25dXSIKICAgICAgY29sb3I9IltbX3J1bkNvbG9yXV0iCiAgICA+CiAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfaGFzTXVsdGlwbGVTYW1wbGVzXV0iPgogICAgICAgIDxkaXY+c2FtcGxlOiBbW19zYW1wbGVUZXh0XV0gb2YgW1tvZlNhbXBsZXNdXTwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc0F0TGVhc3RPbmVTdGVwXV0iPgogICAgICAgIDxkaXYgY2xhc3M9ImhlYWRpbmctcm93Ij4KICAgICAgICAgIDxkaXYgY2xhc3M9ImhlYWRpbmctbGFiZWwiPgogICAgICAgICAgICBzdGVwCiAgICAgICAgICAgIDxzcGFuIHN0eWxlPSJmb250LXdlaWdodDogYm9sZCIKICAgICAgICAgICAgICA+W1tfdG9Mb2NhbGVTdHJpbmcoX3N0ZXBWYWx1ZSldXTwvc3BhbgogICAgICAgICAgICA+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImhlYWRpbmctbGFiZWwgaGVhZGluZy1yaWdodCBkYXRldGltZSI+CiAgICAgICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfY3VycmVudFdhbGxUaW1lXV0iPgogICAgICAgICAgICAgIFtbX2N1cnJlbnRXYWxsVGltZV1dCiAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9ImxhYmVsIHJpZ2h0Ij4KICAgICAgICAgICAgPHBhcGVyLXNwaW5uZXItbGl0ZSBhY3RpdmUgaGlkZGVuJD0iW1shX2lzSW1hZ2VMb2FkaW5nXV0iPgogICAgICAgICAgICA8L3BhcGVyLXNwaW5uZXItbGl0ZT4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvZGl2PgogICAgICA8L3RlbXBsYXRlPgogICAgICA8dGVtcGxhdGUgaXM9ImRvbS1pZiIgaWY9IltbX2hhc011bHRpcGxlU3RlcHNdXSI+CiAgICAgICAgPGRpdj4KICAgICAgICAgIDxwYXBlci1zbGlkZXIKICAgICAgICAgICAgaWQ9InN0ZXBzIgogICAgICAgICAgICBpbW1lZGlhdGUtdmFsdWU9Int7X3N0ZXBJbmRleH19IgogICAgICAgICAgICBtYXg9IltbX21heFN0ZXBJbmRleF1dIgogICAgICAgICAgICBtYXgtbWFya2Vycz0iW1tfbWF4U3RlcEluZGV4XV0iCiAgICAgICAgICAgIHNuYXBzCiAgICAgICAgICAgIHN0ZXA9IjEiCiAgICAgICAgICAgIHZhbHVlPSJ7e19zdGVwSW5kZXh9fSIKICAgICAgICAgID48L3BhcGVyLXNsaWRlcj4KICAgICAgICA8L2Rpdj4KICAgICAgPC90ZW1wbGF0ZT4KICAgIDwvdGYtY2FyZC1oZWFkaW5nPgoKICAgIDwhLS0gU2VtYW50aWNhbGx5IGEgYnV0dG9uIGJ1dCA8aW1nPiBpbnNpZGUgYSA8YnV0dG9uPiBkaXNhbGxvd3MgdXNlciB0byBkbwogICAgYW4gaW50ZXJlc3Rpbmcgb3BlcmF0aW9uIGxpa2UgIkNvcHkgSW1hZ2UiIGluIG5vbi1DaHJvbWl1bSBicm93c2Vycy4gLS0+CiAgICA8YQogICAgICBpZD0ibWFpbi1pbWFnZS1jb250YWluZXIiCiAgICAgIHJvbGU9ImJ1dHRvbiIKICAgICAgYXJpYS1sYWJlbD0iVG9nZ2xlIGFjdHVhbCBzaXplIgogICAgICBhcmlhLWV4cGFuZGVkJD0iW1tfZ2V0QXJpYUV4cGFuZGVkKGFjdHVhbFNpemUpXV0iCiAgICAgIG9uLXRhcD0iX2hhbmRsZVRhcCIKICAgID48L2E+CgogICAgPHN0eWxlIGluY2x1ZGU9InRmLWNhcmQtaGVhZGluZy1zdHlsZSI+CiAgICAgIC8qKiBNYWtlIGJ1dHRvbiBhIGRpdi4gKi8KICAgICAgYnV0dG9uIHsKICAgICAgICB3aWR0aDogMTAwJTsKICAgICAgICBkaXNwbGF5OiBibG9jazsKICAgICAgICBiYWNrZ3JvdW5kOiBub25lOwogICAgICAgIGJvcmRlcjogMDsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICB9CgogICAgICAvKiogRmlyZWZveDogR2V0IHJpZCBvZiBkb3R0ZWQgbGluZSBpbnNpZGUgYnV0dG9uLiAqLwogICAgICBidXR0b246Oi1tb3otZm9jdXMtaW5uZXIgewogICAgICAgIGJvcmRlcjogMDsKICAgICAgICBwYWRkaW5nOiAwOwogICAgICB9CgogICAgICAvKiogRmlyZWZveDogU2ltdWxhdGUgQ2hyb21lJ3Mgb3V0ZXIgZ2xvdyBvbiBidXR0b24gd2hlbiBmb2N1c2VkLiAqLwogICAgICBidXR0b246LW1vei1mb2N1c3JpbmcgewogICAgICAgIG91dGxpbmU6IG5vbmU7CiAgICAgICAgYm94LXNoYWRvdzogMHB4IDBweCAxcHggMnB4IEhpZ2hsaWdodDsKICAgICAgfQoKICAgICAgOmhvc3QgewogICAgICAgIGRpc3BsYXk6IGJsb2NrOwogICAgICAgIHdpZHRoOiAzNTBweDsKICAgICAgICBoZWlnaHQ6IGF1dG87CiAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlOwogICAgICAgIG1hcmdpbjogMCAxNXB4IDQwcHggMDsKICAgICAgICBvdmVyZmxvdy14OiBhdXRvOwogICAgICB9CgogICAgICAvKiogV2hlbiBhY3R1YWwgc2l6ZSBzaG93biBpcyBvbiwgdXNlIHRoZSBhY3R1YWwgaW1hZ2Ugd2lkdGguICovCiAgICAgIDpob3N0KFthY3R1YWwtc2l6ZV0pIHsKICAgICAgICBtYXgtd2lkdGg6IDEwMCU7CiAgICAgICAgd2lkdGg6IGF1dG87CiAgICAgIH0KCiAgICAgIDpob3N0KFthY3R1YWwtc2l6ZV0pICNtYWluLWltYWdlLWNvbnRhaW5lciB7CiAgICAgICAgbWF4LWhlaWdodDogbm9uZTsKICAgICAgICB3aWR0aDogYXV0bzsKICAgICAgfQoKICAgICAgOmhvc3QoW2FjdHVhbC1zaXplXSkgI21haW4taW1hZ2UtY29udGFpbmVyIGltZyB7CiAgICAgICAgd2lkdGg6IGF1dG87CiAgICAgIH0KCiAgICAgIHBhcGVyLXNwaW5uZXItbGl0ZSB7CiAgICAgICAgd2lkdGg6IDE0cHg7CiAgICAgICAgaGVpZ2h0OiAxNHB4OwogICAgICAgIHZlcnRpY2FsLWFsaWduOiB0ZXh0LWJvdHRvbTsKICAgICAgICAtLXBhcGVyLXNwaW5uZXItY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICB9CgogICAgICAjc3RlcHMgewogICAgICAgIGhlaWdodDogMTVweDsKICAgICAgICBtYXJnaW46IDAgMCAwIC0xNXB4OwogICAgICAgIC8qCiAgICAgICAgICogMzEgY29tZXMgZnJvbSBhZGRpbmcgYSBwYWRkaW5nIG9mIDE1cHggZnJvbSBib3RoIHNpZGVzIG9mIHRoZQogICAgICAgICAqIHBhcGVyLXNsaWRlciwgc3VidHJhY3RpbmcgMXB4IHNvIHRoYXQgdGhlIHNsaWRlciB3aWR0aCBhbGlnbnMKICAgICAgICAgKiB3aXRoIHRoZSBpbWFnZSAodGhlIGxhc3Qgc2xpZGVyIG1hcmtlciB0YWtlcyB1cCAxcHgpLCBhbmQKICAgICAgICAgKiBhZGRpbmcgMnB4IHRvIGFjY291bnQgZm9yIGEgYm9yZGVyIG9mIDFweCBvbiBib3RoIHNpZGVzIG9mCiAgICAgICAgICogdGhlIGltYWdlLiAzMCAtIDEgKyAyLgogICAgICAgICAqLwogICAgICAgIHdpZHRoOiBjYWxjKDEwMCUgKyAzMXB4KTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1hY3RpdmUtY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLWtub2ItY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtYm9yZGVyLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1rbm9iLXN0YXJ0LWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1tYXJrZXJzLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1waW4tY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLXBpbi1zdGFydC1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgIH0KCiAgICAgICNtYWluLWltYWdlLWNvbnRhaW5lciB7CiAgICAgICAgbWF4LWhlaWdodDogMTAyNHB4OwogICAgICAgIG92ZXJmbG93OiBhdXRvOwogICAgICB9CgogICAgICAjbWFpbi1pbWFnZS1jb250YWluZXIgaW1nIHsKICAgICAgICBjdXJzb3I6IHBvaW50ZXI7CiAgICAgICAgZGlzcGxheTogYmxvY2s7CiAgICAgICAgaW1hZ2UtcmVuZGVyaW5nOiAtbW96LWNyaXNwLWVkZ2VzOwogICAgICAgIGltYWdlLXJlbmRlcmluZzogcGl4ZWxhdGVkOwogICAgICAgIHdpZHRoOiAxMDAlOwogICAgICAgIGhlaWdodDogYXV0bzsKICAgICAgfQoKICAgICAgcGFwZXItaWNvbi1idXR0b24gewogICAgICAgIGNvbG9yOiAjMjE5NmYzOwogICAgICAgIGJvcmRlci1yYWRpdXM6IDEwMCU7CiAgICAgICAgd2lkdGg6IDMycHg7CiAgICAgICAgaGVpZ2h0OiAzMnB4OwogICAgICAgIHBhZGRpbmc6IDRweDsKICAgICAgfQogICAgICBwYXBlci1pY29uLWJ1dHRvbltzZWxlY3RlZF0gewogICAgICAgIGJhY2tncm91bmQ6IHZhcigtLXRiLXVpLWxpZ2h0LWFjY2VudCk7CiAgICAgIH0KICAgICAgW2hpZGRlbl0gewogICAgICAgIGRpc3BsYXk6IG5vbmU7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogU3RyaW5nIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJydW4iLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgInRhZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE51bWJlciB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAic2FtcGxlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJvZlNhbXBsZXMiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBPYmplY3QgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgInRhZ01ldGFkYXRhIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICAgICAgcmVmbGVjdFRvQXR0cmlidXRlOiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiYWN0dWFsU2l6ZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlcikKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiYnJpZ2h0bmVzc0FkanVzdG1lbnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBOdW1iZXIsCiAgICAgICAgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgImNvbnRyYXN0UGVyY2VudGFnZSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIFJlcXVlc3RNYW5hZ2VyKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJyZXF1ZXN0TWFuYWdlciIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE9iamVjdCwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiX21ldGFkYXRhQ2FuY2VsbGVyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogT2JqZWN0LAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJfaW1hZ2VDYW5jZWxsZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoewogICAgICAgICAgICB0eXBlOiBBcnJheSwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgIl9zdGVwcyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7CiAgICAgICAgICAgIHR5cGU6IE51bWJlciwKICAgICAgICAgICAgbm90aWZ5OiB0cnVlLAogICAgICAgIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJfc3RlcEluZGV4Iiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsKICAgICAgICAgICAgdHlwZTogQm9vbGVhbiwKICAgICAgICB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgIl9pc0ltYWdlTG9hZGluZyIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgncnVuJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgIl9ydW5Db2xvciIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19zdGVwcycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiX2hhc0F0TGVhc3RPbmVTdGVwIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX3N0ZXBzJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBCb29sZWFuKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJfaGFzTXVsdGlwbGVTdGVwcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19zdGVwcycsICdfc3RlcEluZGV4JyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBPYmplY3QpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgIl9jdXJyZW50U3RlcCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ19jdXJyZW50U3RlcCcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJfc3RlcFZhbHVlIiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX2N1cnJlbnRTdGVwJyksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkltYWdlTG9hZGVyLnByb3RvdHlwZSwgIl9jdXJyZW50V2FsbFRpbWUiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfc3RlcHMnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE51bWJlciksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiX21heFN0ZXBJbmRleCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ3NhbXBsZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgU3RyaW5nKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJfc2FtcGxlVGV4dCIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgY29tcHV0ZWQoJ29mU2FtcGxlcycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiX2hhc011bHRpcGxlU2FtcGxlcyIsIG51bGwpOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgb2JzZXJ2ZSgncnVuJywgJ3RhZycpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgRnVuY3Rpb24pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpyZXR1cm50eXBlIiwgdm9pZCAwKQogICAgXSwgVGZJbWFnZUxvYWRlci5wcm90b3R5cGUsICJyZWxvYWQiLCBudWxsKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIG9ic2VydmUoJ19jdXJyZW50U3RlcCcsICdicmlnaHRuZXNzQWRqdXN0bWVudCcsICdjb250cmFzdFBlcmNlbnRhZ2UnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEZ1bmN0aW9uKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cGFyYW10eXBlcyIsIFtdKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246cmV0dXJudHlwZSIsIHZvaWQgMCkKICAgIF0sIFRmSW1hZ2VMb2FkZXIucHJvdG90eXBlLCAiX3VwZGF0ZUltYWdlVXJsIiwgbnVsbCk7CiAgICBUZkltYWdlTG9hZGVyID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtaW1hZ2UtbG9hZGVyJykKICAgIF0sIFRmSW1hZ2VMb2FkZXIpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgbGV0IFRmSW1hZ2VEYXNoYm9hcmQgPSBjbGFzcyBUZkltYWdlRGFzaGJvYXJkIGV4dGVuZHMgTGVnYWN5RWxlbWVudE1peGluKFBvbHltZXJFbGVtZW50KSB7CiAgICAgICAgY29uc3RydWN0b3IoKSB7CiAgICAgICAgICAgIHN1cGVyKC4uLmFyZ3VtZW50cyk7CiAgICAgICAgICAgIHRoaXMucmVsb2FkT25SZWFkeSA9IHRydWU7CiAgICAgICAgICAgIHRoaXMuX2RlZmF1bHRCcmlnaHRuZXNzQWRqdXN0bWVudCA9IDE7CiAgICAgICAgICAgIHRoaXMuX2RlZmF1bHRDb250cmFzdFBlcmNlbnRhZ2UgPSAxMDA7CiAgICAgICAgICAgIHRoaXMuX2JyaWdodG5lc3NBZGp1c3RtZW50ID0gMTsKICAgICAgICAgICAgdGhpcy5fY29udHJhc3RQZXJjZW50YWdlID0gMTAwOwogICAgICAgICAgICB0aGlzLl9yZXF1ZXN0TWFuYWdlciA9IG5ldyBSZXF1ZXN0TWFuYWdlcigpOwogICAgICAgIH0KICAgICAgICByZWFkeSgpIHsKICAgICAgICAgICAgc3VwZXIucmVhZHkoKTsKICAgICAgICAgICAgaWYgKHRoaXMucmVsb2FkT25SZWFkeSkKICAgICAgICAgICAgICAgIHRoaXMucmVsb2FkKCk7CiAgICAgICAgfQogICAgICAgIHJlbG9hZCgpIHsKICAgICAgICAgICAgdGhpcy5fZmV0Y2hUYWdzKCkudGhlbigoKSA9PiB7CiAgICAgICAgICAgICAgICB0aGlzLl9yZWxvYWRJbWFnZXMoKTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9mZXRjaFRhZ3MoKSB7CiAgICAgICAgICAgIGNvbnN0IHVybCA9IGdldFJvdXRlcigpLnBsdWdpblJvdXRlKCdpbWFnZXMnLCAnL3RhZ3MnKTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3RNYW5hZ2VyLnJlcXVlc3QodXJsKS50aGVuKChydW5Ub1RhZ0luZm8pID0+IHsKICAgICAgICAgICAgICAgIGlmIChsb2Rhc2guaXNFcXVhbChydW5Ub1RhZ0luZm8sIHRoaXMuX3J1blRvVGFnSW5mbykpIHsKICAgICAgICAgICAgICAgICAgICAvLyBObyBuZWVkIHRvIHVwZGF0ZSBhbnl0aGluZyBpZiB0aGVyZSBhcmUgbm8gY2hhbmdlcy4KICAgICAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBjb25zdCBydW5Ub1RhZyA9IGxvZGFzaC5tYXBWYWx1ZXMocnVuVG9UYWdJbmZvLCAoeCkgPT4gT2JqZWN0LmtleXMoeCkpOwogICAgICAgICAgICAgICAgY29uc3QgdGFncyA9IGdldFRhZ3MocnVuVG9UYWcpOwogICAgICAgICAgICAgICAgdGhpcy5zZXQoJ19kYXRhTm90Rm91bmQnLCB0YWdzLmxlbmd0aCA9PT0gMCk7CiAgICAgICAgICAgICAgICB0aGlzLnNldCgnX3J1blRvVGFnSW5mbycsIHJ1blRvVGFnSW5mbyk7CiAgICAgICAgICAgICAgICB0aGlzLmFzeW5jKCgpID0+IHsKICAgICAgICAgICAgICAgICAgICAvLyBTZWUgdGhlIGNvbW1lbnQgYWJvdmUgYF9jYXRlZ29yaWVzRG9tUmVhZHlgLgogICAgICAgICAgICAgICAgICAgIHRoaXMuc2V0KCdfY2F0ZWdvcmllc0RvbVJlYWR5JywgdHJ1ZSk7CiAgICAgICAgICAgICAgICB9KTsKICAgICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICAgIF9yZWxvYWRJbWFnZXMoKSB7CiAgICAgICAgICAgIHRoaXMucm9vdC5xdWVyeVNlbGVjdG9yQWxsKCd0Zi1pbWFnZS1sb2FkZXInKS5mb3JFYWNoKChpbWFnZSkgPT4gewogICAgICAgICAgICAgICAgaW1hZ2UucmVsb2FkKCk7CiAgICAgICAgICAgIH0pOwogICAgICAgIH0KICAgICAgICBfc2hvdWxkT3BlbihpbmRleCkgewogICAgICAgICAgICByZXR1cm4gaW5kZXggPD0gMjsKICAgICAgICB9CiAgICAgICAgX3Jlc2V0QnJpZ2h0bmVzcygpIHsKICAgICAgICAgICAgdGhpcy5fYnJpZ2h0bmVzc0FkanVzdG1lbnQgPSB0aGlzLl9kZWZhdWx0QnJpZ2h0bmVzc0FkanVzdG1lbnQ7CiAgICAgICAgfQogICAgICAgIF9yZXNldENvbnRyYXN0KCkgewogICAgICAgICAgICB0aGlzLl9jb250cmFzdFBlcmNlbnRhZ2UgPSB0aGlzLl9kZWZhdWx0Q29udHJhc3RQZXJjZW50YWdlOwogICAgICAgIH0KICAgICAgICBnZXQgX2JyaWdodG5lc3NJc0RlZmF1bHQoKSB7CiAgICAgICAgICAgIHZhciBicmlnaHRuZXNzQWRqdXN0bWVudCA9IHRoaXMuX2JyaWdodG5lc3NBZGp1c3RtZW50OwogICAgICAgICAgICByZXR1cm4gYnJpZ2h0bmVzc0FkanVzdG1lbnQgPT09IHRoaXMuX2RlZmF1bHRCcmlnaHRuZXNzQWRqdXN0bWVudDsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jb250cmFzdElzRGVmYXVsdCgpIHsKICAgICAgICAgICAgdmFyIGNvbnRyYXN0UGVyY2VudGFnZSA9IHRoaXMuX2NvbnRyYXN0UGVyY2VudGFnZTsKICAgICAgICAgICAgcmV0dXJuIGNvbnRyYXN0UGVyY2VudGFnZSA9PT0gdGhpcy5fZGVmYXVsdENvbnRyYXN0UGVyY2VudGFnZTsKICAgICAgICB9CiAgICAgICAgZ2V0IF9jYXRlZ29yaWVzKCkgewogICAgICAgICAgICB2YXIgcnVuVG9UYWdJbmZvID0gdGhpcy5fcnVuVG9UYWdJbmZvOwogICAgICAgICAgICB2YXIgc2VsZWN0ZWRSdW5zID0gdGhpcy5fc2VsZWN0ZWRSdW5zOwogICAgICAgICAgICB2YXIgdGFnRmlsdGVyID0gdGhpcy5fdGFnRmlsdGVyOwogICAgICAgICAgICB2YXIgY2F0ZWdvcmllc0RvbVJlYWR5ID0gdGhpcy5fY2F0ZWdvcmllc0RvbVJlYWR5OwogICAgICAgICAgICBjb25zdCBydW5Ub1RhZyA9IGxvZGFzaC5tYXBWYWx1ZXMocnVuVG9UYWdJbmZvLCAoeCkgPT4gT2JqZWN0LmtleXMoeCkpOwogICAgICAgICAgICBjb25zdCBiYXNlQ2F0ZWdvcmllcyA9IGNhdGVnb3JpemVSdW5UYWdDb21iaW5hdGlvbnMocnVuVG9UYWcsIHNlbGVjdGVkUnVucywgdGFnRmlsdGVyKTsKICAgICAgICAgICAgZnVuY3Rpb24gZXhwbG9kZUl0ZW0oaXRlbSkgewogICAgICAgICAgICAgICAgY29uc3Qgc2FtcGxlcyA9IHJ1blRvVGFnSW5mb1tpdGVtLnJ1bl1baXRlbS50YWddLnNhbXBsZXM7CiAgICAgICAgICAgICAgICByZXR1cm4gbG9kYXNoLnJhbmdlKHNhbXBsZXMpLm1hcCgoaSkgPT4gT2JqZWN0LmFzc2lnbih7fSwgaXRlbSwgewogICAgICAgICAgICAgICAgICAgIHNhbXBsZTogaSwKICAgICAgICAgICAgICAgICAgICBvZlNhbXBsZXM6IHNhbXBsZXMsCiAgICAgICAgICAgICAgICB9KSk7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgY29uc3Qgd2l0aFNhbXBsZXMgPSBiYXNlQ2F0ZWdvcmllcy5tYXAoKGNhdGVnb3J5KSA9PiBPYmplY3QuYXNzaWduKHt9LCBjYXRlZ29yeSwgewogICAgICAgICAgICAgICAgaXRlbXM6IFtdLmNvbmNhdC5hcHBseShbXSwgY2F0ZWdvcnkuaXRlbXMubWFwKGV4cGxvZGVJdGVtKSksCiAgICAgICAgICAgIH0pKTsKICAgICAgICAgICAgcmV0dXJuIHdpdGhTYW1wbGVzOwogICAgICAgIH0KICAgICAgICBfdGFnTWV0YWRhdGEocnVuVG9UYWdJbmZvLCBydW4sIHRhZykgewogICAgICAgICAgICByZXR1cm4gcnVuVG9UYWdJbmZvW3J1bl1bdGFnXTsKICAgICAgICB9CiAgICB9OwogICAgVGZJbWFnZURhc2hib2FyZC50ZW1wbGF0ZSA9IGh0bWwgYAogICAgPHRmLWRhc2hib2FyZC1sYXlvdXQ+CiAgICAgIDxkaXYgY2xhc3M9InNpZGViYXIiIHNsb3Q9InNpZGViYXIiPgogICAgICAgIDxkaXYgY2xhc3M9InNldHRpbmdzIj4KICAgICAgICAgIDxkaXYgY2xhc3M9InNpZGViYXItc2VjdGlvbiI+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9ImxpbmUtaXRlbSI+CiAgICAgICAgICAgICAgPHBhcGVyLWNoZWNrYm94IGNoZWNrZWQ9Int7X2FjdHVhbFNpemV9fSIKICAgICAgICAgICAgICAgID5TaG93IGFjdHVhbCBpbWFnZSBzaXplPC9wYXBlci1jaGVja2JveAogICAgICAgICAgICAgID4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICAgIDxkaXYgY2xhc3M9InNpZGViYXItc2VjdGlvbiI+CiAgICAgICAgICAgIDxoMyBjbGFzcz0idG9vbHRpcC1jb250YWluZXIiPkJyaWdodG5lc3MgYWRqdXN0bWVudDwvaDM+CiAgICAgICAgICAgIDxkaXYgY2xhc3M9InJlc2V0dGFibGUtc2xpZGVyLWNvbnRhaW5lciI+CiAgICAgICAgICAgICAgPHBhcGVyLXNsaWRlcgogICAgICAgICAgICAgICAgbWluPSIwIgogICAgICAgICAgICAgICAgbWF4PSIyIgogICAgICAgICAgICAgICAgc25hcHMKICAgICAgICAgICAgICAgIHBpbgogICAgICAgICAgICAgICAgc3RlcD0iMC4wMSIKICAgICAgICAgICAgICAgIHZhbHVlPSJ7e19icmlnaHRuZXNzQWRqdXN0bWVudH19IgogICAgICAgICAgICAgICAgaW1tZWRpYXRlLXZhbHVlPSJ7e19icmlnaHRuZXNzQWRqdXN0bWVudH19IgogICAgICAgICAgICAgID48L3BhcGVyLXNsaWRlcj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgICBjbGFzcz0ieC1idXR0b24iCiAgICAgICAgICAgICAgICBvbi10YXA9Il9yZXNldEJyaWdodG5lc3MiCiAgICAgICAgICAgICAgICBkaXNhYmxlZD0iW1tfYnJpZ2h0bmVzc0lzRGVmYXVsdF1dIgogICAgICAgICAgICAgICAgPlJlc2V0PC9wYXBlci1idXR0b24KICAgICAgICAgICAgICA+CiAgICAgICAgICAgIDwvZGl2PgogICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24iPgogICAgICAgICAgICA8aDMgY2xhc3M9InRvb2x0aXAtY29udGFpbmVyIj5Db250cmFzdCBhZGp1c3RtZW50PC9oMz4KICAgICAgICAgICAgPGRpdiBjbGFzcz0icmVzZXR0YWJsZS1zbGlkZXItY29udGFpbmVyIj4KICAgICAgICAgICAgICA8cGFwZXItc2xpZGVyCiAgICAgICAgICAgICAgICBtaW49IjAiCiAgICAgICAgICAgICAgICBtYXg9IjUwMCIKICAgICAgICAgICAgICAgIHNuYXBzCiAgICAgICAgICAgICAgICBwaW4KICAgICAgICAgICAgICAgIHN0ZXA9IjEiCiAgICAgICAgICAgICAgICB2YWx1ZT0ie3tfY29udHJhc3RQZXJjZW50YWdlfX0iCiAgICAgICAgICAgICAgICBpbW1lZGlhdGUtdmFsdWU9Int7X2NvbnRyYXN0UGVyY2VudGFnZX19IgogICAgICAgICAgICAgID48L3BhcGVyLXNsaWRlcj4KICAgICAgICAgICAgICA8cGFwZXItYnV0dG9uCiAgICAgICAgICAgICAgICBjbGFzcz0ieC1idXR0b24iCiAgICAgICAgICAgICAgICBvbi10YXA9Il9yZXNldENvbnRyYXN0IgogICAgICAgICAgICAgICAgZGlzYWJsZWQ9IltbX2NvbnRyYXN0SXNEZWZhdWx0XV0iCiAgICAgICAgICAgICAgICA+UmVzZXQ8L3BhcGVyLWJ1dHRvbgogICAgICAgICAgICAgID4KICAgICAgICAgICAgPC9kaXY+CiAgICAgICAgICA8L2Rpdj4KICAgICAgICA8L2Rpdj4KICAgICAgICA8ZGl2IGNsYXNzPSJzaWRlYmFyLXNlY3Rpb24gcnVucy1zZWxlY3RvciI+CiAgICAgICAgICA8dGYtcnVucy1zZWxlY3RvcgogICAgICAgICAgICBpZD0icnVucy1zZWxlY3RvciIKICAgICAgICAgICAgc2VsZWN0ZWQtcnVucz0ie3tfc2VsZWN0ZWRSdW5zfX0iCiAgICAgICAgICA+PC90Zi1ydW5zLXNlbGVjdG9yPgogICAgICAgIDwvZGl2PgogICAgICA8L2Rpdj4KICAgICAgPGRpdiBjbGFzcz0iY2VudGVyIiBzbG90PSJjZW50ZXIiPgogICAgICAgIDx0ZW1wbGF0ZSBpcz0iZG9tLWlmIiBpZj0iW1tfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPGRpdiBjbGFzcz0ibm8tZGF0YS13YXJuaW5nIj4KICAgICAgICAgICAgPGgzPk5vIGltYWdlIGRhdGEgd2FzIGZvdW5kLjwvaDM+CiAgICAgICAgICAgIDxwPlByb2JhYmxlIGNhdXNlczo8L3A+CiAgICAgICAgICAgIDx1bD4KICAgICAgICAgICAgICA8bGk+WW91IGhhdmVu4oCZdCB3cml0dGVuIGFueSBpbWFnZSBkYXRhIHRvIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgICA8bGk+VGVuc29yQm9hcmQgY2Fu4oCZdCBmaW5kIHlvdXIgZXZlbnQgZmlsZXMuPC9saT4KICAgICAgICAgICAgPC91bD4KCiAgICAgICAgICAgIDxwPgogICAgICAgICAgICAgIElmIHlvdeKAmXJlIG5ldyB0byB1c2luZyBUZW5zb3JCb2FyZCwgYW5kIHdhbnQgdG8gZmluZCBvdXQgaG93IHRvCiAgICAgICAgICAgICAgYWRkIGRhdGEgYW5kIHNldCB1cCB5b3VyIGV2ZW50IGZpbGVzLCBjaGVjayBvdXQgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vZ2l0aHViLmNvbS90ZW5zb3JmbG93L3RlbnNvcmJvYXJkL2Jsb2IvbWFzdGVyL1JFQURNRS5tZCIKICAgICAgICAgICAgICAgID5SRUFETUU8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIHBlcmhhcHMgdGhlCiAgICAgICAgICAgICAgPGEKICAgICAgICAgICAgICAgIGhyZWY9Imh0dHBzOi8vd3d3LnRlbnNvcmZsb3cub3JnL2dldF9zdGFydGVkL3N1bW1hcmllc19hbmRfdGVuc29yYm9hcmQiCiAgICAgICAgICAgICAgICA+VGVuc29yQm9hcmQgdHV0b3JpYWw8L2EKICAgICAgICAgICAgICA+LgogICAgICAgICAgICA8L3A+CgogICAgICAgICAgICA8cD4KICAgICAgICAgICAgICBJZiB5b3UgdGhpbmsgVGVuc29yQm9hcmQgaXMgY29uZmlndXJlZCBwcm9wZXJseSwgcGxlYXNlIHNlZQogICAgICAgICAgICAgIDxhCiAgICAgICAgICAgICAgICBocmVmPSJodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZW5zb3Jib2FyZC9ibG9iL21hc3Rlci9SRUFETUUubWQjbXktdGVuc29yYm9hcmQtaXNudC1zaG93aW5nLWFueS1kYXRhLXdoYXRzLXdyb25nIgogICAgICAgICAgICAgICAgPnRoZSBzZWN0aW9uIG9mIHRoZSBSRUFETUUgZGV2b3RlZCB0byBtaXNzaW5nIGRhdGEgcHJvYmxlbXM8L2EKICAgICAgICAgICAgICA+CiAgICAgICAgICAgICAgYW5kIGNvbnNpZGVyIGZpbGluZyBhbiBpc3N1ZSBvbiBHaXRIdWIuCiAgICAgICAgICAgIDwvcD4KICAgICAgICAgIDwvZGl2PgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgPHRlbXBsYXRlIGlzPSJkb20taWYiIGlmPSJbWyFfZGF0YU5vdEZvdW5kXV0iPgogICAgICAgICAgPHRmLXRhZy1maWx0ZXJlciB0YWctZmlsdGVyPSJ7e190YWdGaWx0ZXJ9fSI+PC90Zi10YWctZmlsdGVyZXI+CiAgICAgICAgICA8dGVtcGxhdGUgaXM9ImRvbS1yZXBlYXQiIGl0ZW1zPSJbW19jYXRlZ29yaWVzXV0iIGFzPSJjYXRlZ29yeSI+CiAgICAgICAgICAgIDx0Zi1jYXRlZ29yeS1wYWdpbmF0ZWQtdmlldwogICAgICAgICAgICAgIGNhdGVnb3J5PSJbW2NhdGVnb3J5XV0iCiAgICAgICAgICAgICAgaW5pdGlhbC1vcGVuZWQ9IltbX3Nob3VsZE9wZW4oaW5kZXgpXV0iCiAgICAgICAgICAgID4KICAgICAgICAgICAgICA8dGVtcGxhdGU+CiAgICAgICAgICAgICAgICA8dGYtaW1hZ2UtbG9hZGVyCiAgICAgICAgICAgICAgICAgIGFjdGl2ZT0iW1thY3RpdmVdXSIKICAgICAgICAgICAgICAgICAgcnVuPSJbW2l0ZW0ucnVuXV0iCiAgICAgICAgICAgICAgICAgIHRhZz0iW1tpdGVtLnRhZ11dIgogICAgICAgICAgICAgICAgICBzYW1wbGU9IltbaXRlbS5zYW1wbGVdXSIKICAgICAgICAgICAgICAgICAgb2Ytc2FtcGxlcz0iW1tpdGVtLm9mU2FtcGxlc11dIgogICAgICAgICAgICAgICAgICB0YWctbWV0YWRhdGE9IltbX3RhZ01ldGFkYXRhKF9ydW5Ub1RhZ0luZm8sIGl0ZW0ucnVuLCBpdGVtLnRhZyldXSIKICAgICAgICAgICAgICAgICAgcmVxdWVzdC1tYW5hZ2VyPSJbW19yZXF1ZXN0TWFuYWdlcl1dIgogICAgICAgICAgICAgICAgICBhY3R1YWwtc2l6ZT0iW1tfYWN0dWFsU2l6ZV1dIgogICAgICAgICAgICAgICAgICBicmlnaHRuZXNzLWFkanVzdG1lbnQ9IltbX2JyaWdodG5lc3NBZGp1c3RtZW50XV0iCiAgICAgICAgICAgICAgICAgIGNvbnRyYXN0LXBlcmNlbnRhZ2U9IltbX2NvbnRyYXN0UGVyY2VudGFnZV1dIgogICAgICAgICAgICAgICAgPjwvdGYtaW1hZ2UtbG9hZGVyPgogICAgICAgICAgICAgIDwvdGVtcGxhdGU+CiAgICAgICAgICAgIDwvdGYtY2F0ZWdvcnktcGFnaW5hdGVkLXZpZXc+CiAgICAgICAgICA8L3RlbXBsYXRlPgogICAgICAgIDwvdGVtcGxhdGU+CiAgICAgIDwvZGl2PgogICAgPC90Zi1kYXNoYm9hcmQtbGF5b3V0PgogICAgPHN0eWxlIGluY2x1ZGU9ImRhc2hib2FyZC1zdHlsZSI+PC9zdHlsZT4KICAgIDxzdHlsZT4KICAgICAgLnJlc2V0dGFibGUtc2xpZGVyLWNvbnRhaW5lciB7CiAgICAgICAgZGlzcGxheTogZmxleDsKICAgICAgfQogICAgICAucmVzZXR0YWJsZS1zbGlkZXItY29udGFpbmVyIHBhcGVyLXNsaWRlciB7CiAgICAgICAgZmxleC1ncm93OiAxOwogICAgICB9CiAgICAgIC5yZXNldHRhYmxlLXNsaWRlci1jb250YWluZXIgcGFwZXItYnV0dG9uIHsKICAgICAgICBmbGV4LWdyb3c6IDA7CiAgICAgIH0KICAgICAgLnJlc2V0dGFibGUtc2xpZGVyLWNvbnRhaW5lciBwYXBlci1idXR0b25bZGlzYWJsZWRdIHsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB1bnNldDsKICAgICAgfQogICAgICAueC1idXR0b24gewogICAgICAgIGZvbnQtc2l6ZTogMTNweDsKICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB2YXIoLS10Yi11aS1saWdodC1hY2NlbnQpOwogICAgICAgIGNvbG9yOiB2YXIoLS10Yi11aS1kYXJrLWFjY2VudCk7CiAgICAgIH0KICAgICAgLm5vLWRhdGEtd2FybmluZyB7CiAgICAgICAgbWF4LXdpZHRoOiA1NDBweDsKICAgICAgICBtYXJnaW46IDgwcHggYXV0byAwIGF1dG87CiAgICAgIH0KICAgICAgcGFwZXItc2xpZGVyIHsKICAgICAgICAtLXBhcGVyLXNsaWRlci1hY3RpdmUtY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLWtub2ItY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLWtub2Itc3RhcnQtYm9yZGVyLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1rbm9iLXN0YXJ0LWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1tYXJrZXJzLWNvbG9yOiB2YXIoLS10Yi1vcmFuZ2Utc3Ryb25nKTsKICAgICAgICAtLXBhcGVyLXNsaWRlci1waW4tY29sb3I6IHZhcigtLXRiLW9yYW5nZS1zdHJvbmcpOwogICAgICAgIC0tcGFwZXItc2xpZGVyLXBpbi1zdGFydC1jb2xvcjogdmFyKC0tdGItb3JhbmdlLXN0cm9uZyk7CiAgICAgIH0KICAgIDwvc3R5bGU+CiAgYDsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgInJlbG9hZE9uUmVhZHkiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBBcnJheSB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEFycmF5KQogICAgXSwgVGZJbWFnZURhc2hib2FyZC5wcm90b3R5cGUsICJfc2VsZWN0ZWRSdW5zIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogT2JqZWN0IH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgT2JqZWN0KQogICAgXSwgVGZJbWFnZURhc2hib2FyZC5wcm90b3R5cGUsICJfcnVuVG9UYWdJbmZvIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogQm9vbGVhbiB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kYXRhTm90Rm91bmQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSW1hZ2VEYXNoYm9hcmQucHJvdG90eXBlLCAiX2FjdHVhbFNpemUiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kZWZhdWx0QnJpZ2h0bmVzc0FkanVzdG1lbnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9kZWZhdWx0Q29udHJhc3RQZXJjZW50YWdlIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIHByb3BlcnR5KHsgdHlwZTogTnVtYmVyIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgTnVtYmVyKQogICAgXSwgVGZJbWFnZURhc2hib2FyZC5wcm90b3R5cGUsICJfYnJpZ2h0bmVzc0FkanVzdG1lbnQiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBOdW1iZXIgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBOdW1iZXIpCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9jb250cmFzdFBlcmNlbnRhZ2UiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBTdHJpbmcgfSksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnR5cGUiLCBTdHJpbmcpCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl90YWdGaWx0ZXIiLCB2b2lkIDApOwogICAgX19kZWNvcmF0ZShbCiAgICAgICAgcHJvcGVydHkoeyB0eXBlOiBCb29sZWFuIH0pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbikKICAgIF0sIFRmSW1hZ2VEYXNoYm9hcmQucHJvdG90eXBlLCAiX2NhdGVnb3JpZXNEb21SZWFkeSIsIHZvaWQgMCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBwcm9wZXJ0eSh7IHR5cGU6IE9iamVjdCB9KSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIE9iamVjdCkKICAgIF0sIFRmSW1hZ2VEYXNoYm9hcmQucHJvdG90eXBlLCAiX3JlcXVlc3RNYW5hZ2VyIiwgdm9pZCAwKTsKICAgIF9fZGVjb3JhdGUoWwogICAgICAgIGNvbXB1dGVkKCdfYnJpZ2h0bmVzc0FkanVzdG1lbnQnKSwKICAgICAgICBfX21ldGFkYXRhKCJkZXNpZ246dHlwZSIsIEJvb2xlYW4pLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9icmlnaHRuZXNzSXNEZWZhdWx0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX2NvbnRyYXN0UGVyY2VudGFnZScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQm9vbGVhbiksCiAgICAgICAgX19tZXRhZGF0YSgiZGVzaWduOnBhcmFtdHlwZXMiLCBbXSkKICAgIF0sIFRmSW1hZ2VEYXNoYm9hcmQucHJvdG90eXBlLCAiX2NvbnRyYXN0SXNEZWZhdWx0IiwgbnVsbCk7CiAgICBfX2RlY29yYXRlKFsKICAgICAgICBjb21wdXRlZCgnX3J1blRvVGFnSW5mbycsICdfc2VsZWN0ZWRSdW5zJywgJ190YWdGaWx0ZXInLCAnX2NhdGVnb3JpZXNEb21SZWFkeScpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjp0eXBlIiwgQXJyYXkpLAogICAgICAgIF9fbWV0YWRhdGEoImRlc2lnbjpwYXJhbXR5cGVzIiwgW10pCiAgICBdLCBUZkltYWdlRGFzaGJvYXJkLnByb3RvdHlwZSwgIl9jYXRlZ29yaWVzIiwgbnVsbCk7CiAgICBUZkltYWdlRGFzaGJvYXJkID0gX19kZWNvcmF0ZShbCiAgICAgICAgY3VzdG9tRWxlbWVudCgndGYtaW1hZ2UtZGFzaGJvYXJkJykKICAgIF0sIFRmSW1hZ2VEYXNoYm9hcmQpOwoKICAgIC8qIENvcHlyaWdodCAyMDIwIFRoZSBUZW5zb3JGbG93IEF1dGhvcnMuIEFsbCBSaWdodHMgUmVzZXJ2ZWQuCgogICAgTGljZW5zZWQgdW5kZXIgdGhlIEFwYWNoZSBMaWNlbnNlLCBWZXJzaW9uIDIuMCAodGhlICJMaWNlbnNlIik7CiAgICB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuCiAgICBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXQKCiAgICAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wCgogICAgVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZQogICAgZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gIkFTIElTIiBCQVNJUywKICAgIFdJVEhPVVQgV0FSUkFOVElFUyBPUiBDT05ESVRJT05TIE9GIEFOWSBLSU5ELCBlaXRoZXIgZXhwcmVzcyBvciBpbXBsaWVkLgogICAgU2VlIHRoZSBMaWNlbnNlIGZvciB0aGUgc3BlY2lmaWMgbGFuZ3VhZ2UgZ292ZXJuaW5nIHBlcm1pc3Npb25zIGFuZAogICAgbGltaXRhdGlvbnMgdW5kZXIgdGhlIExpY2Vuc2UuCiAgICA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0qLwogICAgLyoqCiAgICAgKiBUeXBlcyBvZiBlcnJvcnMgZHVyaW5nIG5ldHdvcmsgZGF0YSByb3VuZHRyaXAuCiAgICAgKiBAZW51bSB7bnVtYmVyfQogICAgICovCiAgICB2YXIgRXJyb3JDb2RlczsKICAgIChmdW5jdGlvbiAoRXJyb3JDb2RlcykgewogICAgICAgIEVycm9yQ29kZXNbRXJyb3JDb2Rlc1siQ0FOQ0VMTEVEIl0gPSAxXSA9ICJDQU5DRUxMRUQiOwogICAgfSkoRXJyb3JDb2RlcyB8fCAoRXJyb3JDb2RlcyA9IHt9KSk7CiAgICAvKioKICAgICAqIFR5cGVzIG9mIGNvbnRlbnQgZGlzcGxheWVkIGJ5IHRoZSBwbHVnaW4uCiAgICAgKiBAZW51bSB7bnVtYmVyfQogICAgICovCiAgICB2YXIgQ29udGVudFR5cGU7CiAgICAoZnVuY3Rpb24gKENvbnRlbnRUeXBlKSB7CiAgICAgICAgQ29udGVudFR5cGVbQ29udGVudFR5cGVbIlZFUlRFWCJdID0gMV0gPSAiVkVSVEVYIjsKICAgICAgICBDb250ZW50VHlwZVtDb250ZW50VHlwZVsiRkFDRSJdID0gMl0gPSAiRkFDRSI7CiAgICAgICAgQ29udGVudFR5cGVbQ29udGVudFR5cGVbIkNPTE9SIl0gPSAzXSA9ICJDT0xPUiI7CiAgICB9KShDb250ZW50VHlwZSB8fCAoQ29udGVudFR5cGUgPSB7fSkpOwogICAgLyoqCiAgICAgKiBUeXBlcyBvZiBjb250ZW50IGRpc3BsYXllZCBieSB0aGUgcGx1Z2luIG1hcHBlZCB0byB1bmRlcmx5aW5nIGRhdGEgdHlwZXMuCiAgICAgKiBAZW51bSB7c3RyaW5nfQogICAgICovCiAgICB2YXIgQ29udGVudFR5cGVUb0l0ZW1UeXBlOwogICAgKGZ1bmN0aW9uIChDb250ZW50VHlwZVRvSXRlbVR5cGUpIHsKICAgICAgICBDb250ZW50VHlwZVRvSXRlbVR5cGVbIlZFUlRFWCJdID0gImZsb2F0MzIiOwogICAgICAgIENvbnRlbnRUeXBlVG9JdGVtVHlwZVsiRkFDRSJdID0gImludDMyIjsKICAgICAgICBDb250ZW50VHlwZVRvSXRlbVR5cGVbIkNPTE9SIl0gPSAidWludDgiOwogICAgfSkoQ29udGVudFR5cGVUb0l0ZW1UeXBlIHx8IChDb250ZW50VHlwZVRvSXRlbVR5cGUgPSB7fSkpOwogICAgY2xhc3MgQXJyYXlCdWZmZXJEYXRhUHJvdmlkZXIgewogICAgICAgIC8qKgogICAgICAgICAqIEFycmF5QnVmZmVyRGF0YVByb3ZpZGVyIGNvbnN0cnVjdG9yLCBpbml0aWFsaXplcyBldmVyeXRoaW5nIG5lZWRlZCBmb3IKICAgICAgICAgKiBmdXR1cmUgcmVxdWVzdHMgdG8gdGhlIHNlcnZlci4KICAgICAgICAgKiBAcGFyYW0gcmVxdWVzdE1hbmFnZXIgUmVxdWVzdCBtYW5hZ2VyIHRvIGNvbW11bmljYXRlIHdpdGggdGhlCiAgICAgICAgICogIHNlcnZlci4KICAgICAgICAgKi8KICAgICAgICBjb25zdHJ1Y3RvcihyZXF1ZXN0TWFuYWdlcikgewogICAgICAgICAgICB0aGlzLl9jYW5jZWxsZXIgPSBuZXcgQ2FuY2VsbGVyKCk7CiAgICAgICAgICAgIHRoaXMuX3JlcXVlc3RNYW5hZ2VyID0gcmVxdWVzdE1hbmFnZXI7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJlcXVlc3RzIG5ldyBkYXRhIGZyb20gdGhlIHNlcnZlci4KICAgICAgICAgKi8KICAgICAgICByZWxvYWQocnVuLCB0YWcsIHNhbXBsZSkgewogICAgICAgICAgICB0aGlzLl9jYW5jZWxsZXIuY2FuY2VsQWxsKCk7CiAgICAgICAgICAgIHJldHVybiB0aGlzLl9mZXRjaE1ldGFkYXRhKHJ1biwgdGFnLCBzYW1wbGUpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgICAqIFJlcXVlc3RzIG5ldyBkYXRhIG9mIHNvbWUgcGFydGljdWxhciB0eXBlIGZyb20gdGhlIHNlcnZlci4KICAgICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBydW4gTmFtZSBvZiB0aGUgcnVuIHRvIGdldCBkYXRhIGZvci4KICAgICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSB0YWcgTmFtZSBvZiB0aGUgdGFnIHRvIGdldCBkYXRhIGZvci4KICAgICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjb250ZW50X3R5cGUgVHlwZSBvZiB0aGUgY29udGVudCB0byByZXRyaWV2ZS4KICAgICAgICAgICAqIEBwYXJhbSB7IWFycmF5fSBtZXRhZGF0YSBMaXN0IG9mIG1ldGFkYXRhIHRvIGNvbXBsZXRlIHdpdGggZGF0YSBmcm9tIHRoZQogICAgICAgICAgICogIHNlcnZlci4KICAgICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzYW1wbGUgU2FtcGxlIGluZGV4IGZyb20gYSBiYXRjaCBvZiBkYXRhLgogICAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHN0ZXAgU3RlcCB2YWx1ZSwgcmVwcmVzZW50aW5nIGEgcG9pbnQgaW4gdGhlIHRpbWUgd2hlbiB0aGUKICAgICAgICAgICAgICBldmVudCBvY2N1cnJlZC4KICAgICAgICAgICAqIEBwYXJhbSB7IU9iamVjdH0gbWVzaERhdGEgTWFwIHRvIHBvcHVsYXRlIHdpdGggbWVzaCBkYXRhLgogICAgICAgICAgICogQHJldHVybiB7IU9iamVjdH0gUHJvbWlzZSBvYmplY3QgcmVwcmVzZW50aW5nIHNlcnZlciByZXF1ZXN0LgogICAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgICAqLwogICAgICAgIF9mZXRjaERhdGFCeVN0ZXAocnVuLCB0YWcsIGNvbnRlbnRfdHlwZSwgc2FtcGxlLCBzdGVwLCBtZXNoRGF0YSkgewogICAgICAgICAgICBjb25zdCB1cmwgPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnbWVzaCcsICcvZGF0YScsIG5ldyBVUkxTZWFyY2hQYXJhbXMoewogICAgICAgICAgICAgICAgdGFnLAogICAgICAgICAgICAgICAgcnVuLAogICAgICAgICAgICAgICAgY29udGVudF90eXBlLAogICAgICAgICAgICAgICAgc2FtcGxlOiBTdHJpbmcoc2FtcGxlKSwKICAgICAgICAgICAgICAgIHN0ZXA6IFN0cmluZyhzdGVwKSwKICAgICAgICAgICAgfSkpOwogICAgICAgICAgICBjb25zdCByZXNoYXBlVG8xeE54MyA9IGZ1bmN0aW9uIChkYXRhKSB7CiAgICAgICAgICAgICAgICBjb25zdCBjaGFubmVsc0NvdW50ID0gMzsKICAgICAgICAgICAgICAgIGxldCBpdGVtcyA9IFtdOwogICAgICAgICAgICAgICAgZm9yIChsZXQgaSA9IDA7IGkgPCBkYXRhLmxlbmd0aCAvIGNoYW5uZWxzQ291bnQ7IGkrKykgewogICAgICAgICAgICAgICAgICAgIGxldCBkYXRhRW50cnkgPSBbXTsKICAgICAgICAgICAgICAgICAgICBmb3IgKGxldCBqID0gMDsgaiA8IGNoYW5uZWxzQ291bnQ7IGorKykgewogICAgICAgICAgICAgICAgICAgICAgICBkYXRhRW50cnkucHVzaChkYXRhW2kgKiBjaGFubmVsc0NvdW50ICsgal0pOwogICAgICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgICAgICAgICBpdGVtcy5wdXNoKGRhdGFFbnRyeSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICByZXR1cm4gaXRlbXM7CiAgICAgICAgICAgIH07CiAgICAgICAgICAgIGNvbnN0IHByb2Nlc3NEYXRhID0gdGhpcy5fY2FuY2VsbGVyLmNhbmNlbGxhYmxlKChyZXNwb25zZSkgPT4gewogICAgICAgICAgICAgICAgaWYgKHJlc3BvbnNlLmNhbmNlbGxlZCkgewogICAgICAgICAgICAgICAgICAgIHJldHVybiBQcm9taXNlLnJlamVjdCh7CiAgICAgICAgICAgICAgICAgICAgICAgIGNvZGU6IEVycm9yQ29kZXMuQ0FOQ0VMTEVELAogICAgICAgICAgICAgICAgICAgICAgICBtZXNzYWdlOiAnUmVzcG9uc2Ugd2FzIGludmFsaWRhdGVkLicsCiAgICAgICAgICAgICAgICAgICAgfSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBsZXQgYnVmZmVyID0gcmVzcG9uc2UudmFsdWU7CiAgICAgICAgICAgICAgICBzd2l0Y2ggKGNvbnRlbnRfdHlwZSkgewogICAgICAgICAgICAgICAgICAgIGNhc2UgJ1ZFUlRFWCc6CiAgICAgICAgICAgICAgICAgICAgICAgIG1lc2hEYXRhLnZlcnRpY2VzID0gcmVzaGFwZVRvMXhOeDMobmV3IEZsb2F0MzJBcnJheShidWZmZXIpKTsKICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7CiAgICAgICAgICAgICAgICAgICAgY2FzZSAnRkFDRSc6CiAgICAgICAgICAgICAgICAgICAgICAgIG1lc2hEYXRhLmZhY2VzID0gcmVzaGFwZVRvMXhOeDMobmV3IEludDMyQXJyYXkoYnVmZmVyKSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgICAgIGNhc2UgJ0NPTE9SJzoKICAgICAgICAgICAgICAgICAgICAgICAgbWVzaERhdGEuY29sb3JzID0gcmVzaGFwZVRvMXhOeDMobmV3IFVpbnQ4QXJyYXkoYnVmZmVyKSk7CiAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIG1lc2hEYXRhOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3RNYW5hZ2VyCiAgICAgICAgICAgICAgICAuZmV0Y2godXJsLCB7CiAgICAgICAgICAgICAgICBtZXRob2Q6ICdHRVQnLAogICAgICAgICAgICAgICAgaGVhZGVyczogewogICAgICAgICAgICAgICAgICAgIHJlc3BvbnNlVHlwZTogJ2FycmF5YnVmZmVyJywKICAgICAgICAgICAgICAgICAgICBjb250ZW50VHlwZTogQ29udGVudFR5cGVUb0l0ZW1UeXBlW2NvbnRlbnRfdHlwZV0sCiAgICAgICAgICAgICAgICB9LAogICAgICAgICAgICB9KQogICAgICAgICAgICAgICAgLnRoZW4oKHJlc3BvbnNlKSA9PiByZXNwb25zZS5hcnJheUJ1ZmZlcigpKQogICAgICAgICAgICAgICAgLnRoZW4ocHJvY2Vzc0RhdGEpOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBSZXF1ZXN0cyBuZXcgZGF0YSBmb3IgZWFjaCB0eXBlIG9mIG1ldGFkYXRhIGZyb20gdGhlIHNlcnZlci4KICAgICAgICAgKiBNZXRhZGF0YSBjb25zaXN0cyBvZiB3YWxsX3RpbWUsIHN0ZXAsIHRlbnNvciBzaGFwZSwgY29udGVudCB0eXBlIGFuZCBvdGhlcgogICAgICAgICAqIGluZm8sIGJ1dCBub3QgdGVuc29yIGRhdGEgaXRzZWxmLgogICAgICAgICAqIEBwYXJhbSB7IU9iamVjdH0gc3RlcERhdHVtIERpY3Rpb25hcnkgd2l0aCBtZXNoIGRhdGEgZm9yIGEgY3VycmVudCBzdGVwLgogICAgICAgICAqIEBwYXJhbSB7c3RyaW5nfSBydW4gTmFtZSBvZiB0aGUgcnVuIHRvIGdldCBkYXRhIGZvci4KICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gdGFnIE5hbWUgb2YgdGhlIHR1ZyB0byBnZXQgZGF0YSBmb3IuCiAgICAgICAgICogQHBhcmFtIHtudW1iZXJ9IHNhbXBsZSBTYW1wbGUgaW5kZXggZnJvbSBhIGJhdGNoIG9mIGRhdGEuCiAgICAgICAgICogQHJldHVybiB7IU9iamVjdH0gSm9pbnQgcHJvbWlzZSBmb3IgYWxsIHJlcXVlc3RzIGJlaW5nIHNlbnQuCiAgICAgICAgICogQHByaXZhdGUKICAgICAgICAgKi8KICAgICAgICBmZXRjaERhdGEoc3RlcERhdHVtLCBydW4sIHRhZywgc2FtcGxlKSB7CiAgICAgICAgICAgIGxldCBwcm9taXNlcyA9IFtdOwogICAgICAgICAgICAvLyBNYXAgdG8gcG9wdWxhdGUgd2l0aCBtZXNoIGRhdGEsIGkuZS4gdmVydGljZXMsIGZhY2VzLCBldGMuCiAgICAgICAgICAgIGxldCBtZXNoRGF0YSA9IG5ldyBNYXAoKTsKICAgICAgICAgICAgT2JqZWN0LmtleXMoQ29udGVudFR5cGUpLmZvckVhY2goKGNvbnRlbnRUeXBlKSA9PiB7CiAgICAgICAgICAgICAgICBjb25zdCBjb21wb25lbnQgPSAxIDw8IENvbnRlbnRUeXBlW2NvbnRlbnRUeXBlXTsKICAgICAgICAgICAgICAgIGlmIChzdGVwRGF0dW0uY29tcG9uZW50cyAmIGNvbXBvbmVudCkgewogICAgICAgICAgICAgICAgICAgIHByb21pc2VzLnB1c2godGhpcy5fZmV0Y2hEYXRhQnlTdGVwKHJ1biwgdGFnLCBjb250ZW50VHlwZSwgc2FtcGxlLCBzdGVwRGF0dW0uc3RlcCwgbWVzaERhdGEpKTsKICAgICAgICAgICAgICAgIH0KICAgICAgICAgICAgfSk7CiAgICAgICAgICAgIHJldHVybiBQcm9taXNlLmFsbChwcm9taXNlcyk7CiAgICAgICAgfQogICAgICAgIC8qKgogICAgICAgICAqIFJlcXVlc3RzIG5ldyBtZXRhZGF0YSBmcm9tIHRoZSBzZXJ2ZXIKICAgICAgICAgKiBAcGFyYW0ge3N0cmluZ30gcnVuIE5hbWUgb2YgdGhlIHJ1biB0byBnZXQgZGF0YSBmb3IuCiAgICAgICAgICogQHBhcmFtIHtzdHJpbmd9IHRhZyBOYW1lIG9mIHRoZSB0dWcgdG8gZ2V0IGRhdGEgZm9yLgogICAgICAgICAqIEBwYXJhbSB7bnVtYmVyfSBzYW1wbGUgU2FtcGxlIGluZGV4IGZyb20gYSBiYXRjaCBvZiBkYXRhLgogICAgICAgICAqICBjb21wbGV0aW9uLgogICAgICAgICAqIEByZXR1cm4geyFPYmplY3R9IFByb21pc2UgZm9yIHJlcXVlc3RlZCBtZXRhZGF0YS4KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIF9mZXRjaE1ldGFkYXRhKHJ1biwgdGFnLCBzYW1wbGUpIHsKICAgICAgICAgICAgdGhpcy5fY2FuY2VsbGVyLmNhbmNlbEFsbCgpOwogICAgICAgICAgICBjb25zdCB1cmwgPSBnZXRSb3V0ZXIoKS5wbHVnaW5Sb3V0ZSgnbWVzaCcsICcvbWVzaGVzJywgbmV3IFVSTFNlYXJjaFBhcmFtcyh7IHRhZywgcnVuLCBzYW1wbGUgfSkpOwogICAgICAgICAgICBjb25zdCByZXF1ZXN0RGF0YSA9IHRoaXMuX2NhbmNlbGxlci5jYW5jZWxsYWJsZSgocmVzcG9uc2UpID0+IHsKICAgICAgICAgICAgICAgIGlmIChyZXNwb25zZS5jYW5jZWxsZWQpIHsKICAgICAgICAgICAgICAgICAgICByZXR1cm4gUHJvbWlzZS5yZWplY3QoewogICAgICAgICAgICAgICAgICAgICAgICBjb2RlOiBFcnJvckNvZGVzLkNBTkNFTExFRCwKICAgICAgICAgICAgICAgICAgICAgICAgbWVzc2FnZTogJ1Jlc3BvbnNlIHdhcyBpbnZhbGlkYXRlZC4nLAogICAgICAgICAgICAgICAgICAgIH0pOwogICAgICAgICAgICAgICAgfQogICAgICAgICAgICAgICAgcmV0dXJuIHJlc3BvbnNlLnZhbHVlOwogICAgICAgICAgICB9KTsKICAgICAgICAgICAgcmV0dXJuIHRoaXMuX3JlcXVlc3RNYW5hZ2VyCiAgICAgICAgICAgICAgICAuZmV0Y2godXJsKQogICAgICAgICAgICAgICAgLnRoZW4oKHJlc3BvbnNlKSA9PiByZXNwb25zZS5qc29uKCkpCiAgICAgICAgICAgICAgICAudGhlbihyZXF1ZXN0RGF0YSkKICAgICAgICAgICAgICAgIC50aGVuKHRoaXMuX3Byb2Nlc3NNZXRhZGF0YS5iaW5kKHRoaXMpKTsKICAgICAgICB9CiAgICAgICAgLyoqCiAgICAgICAgICogUHJvY2VzcyBzZXJ2ZXIgcmF3IGRhdGEgaW50byBmcm9udGVuZCBmcmllbmRseSBmb3JtYXQuCiAgICAgICAgICogQHBhcmFtIHshQXJyYXl8dW5kZWZpbmVkfSBkYXRhIGxpc3Qgb2YgcmF3IHNlcnZlciByZWNvcmRzLgogICAgICAgICAqIEByZXR1cm4geyFBcnJheX0gbGlzdCBvZiBzdGVwIGRhdHVtcy4KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqLwogICAgICAgIF9wcm9jZXNzTWV0YWRhdGEoZGF0YSkgewogICAgICAgICAgICBpZiAoIWRhdGEpCiAgICAgICAgICAgICAgICByZXR1cm47CiAgICAgICAgICAgIGNvbnN0IHN0ZXBUb0RhdGEgPSBuZXcgTWFwKCk7CiAgICAgICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgZGF0YS5sZW5ndGg7IGkrKykgewogICAgICAgICAgICAgICAgbGV0IGRhdGFFbnRyeSA9IGRhdGFbaV07CiAgICAgICAgICAgICAgICBpZiAoIXN0ZXBUb0RhdGEuaGFzKGRhdGFFbnRyeS5zdGVwKSkgewogICAgICAgICAgICAgICAgICAgIHN0ZXBUb0RhdGEuc2V0KGRhdGFFbnRyeS5zdGVwLCBbXSk7CiAgICAgICAgICAgICAgICB9CiAgICAgICAgICAgICAgICBzdGVwVG9EYXRhLmdldChkYXRhRW50cnkuc3RlcCkucHVzaChkYXRhRW50cnkpOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGxldCBkYXR1bXMgPSBbXTsKICAgICAgICAgICAgc3RlcFRvRGF0YS5mb3JFYWNoKChkYXRhKSA9PiB7CiAgICAgICAgICAgICAgICBsZXQgZGF0dW0gPSB0aGlzLl9jcmVhdGVTdGVwRGF0dW0oZGF0YVswXSk7CiAgICAgICAgICAgICAgICBkYXR1bXMucHVzaChkYXR1bSk7CiAgICAgICAgICAgIH0pOwogICAgICAgICAgICByZXR1cm4gZGF0dW1zOwogICAgICAgIH0KICAgICAgICAvKioKICAgICAgICAgKiBQcm9jZXNzIHNpbmdsZSByb3cgb2Ygc2VydmVyLXNpZGUgZGF0YSBhbmQgcHV0cyBpdCBpbiBtb3JlIHN0cnVjdHVyZWQgZm9ybS4KICAgICAgICAgKiBAcGFyYW0geyFPYmplY3R9IG1ldGFkYXRhIE9iamVjdCBkZXNjcmliaW5nIHN0ZXAgc3VtbWFyeS4KICAgICAgICAgKiBAcHJpdmF0ZQogICAgICAgICAqIEByZXR1cm4geyFPYmplY3R9IHdpdGggd2FsbF90aW1lLCBzdGVwIG51bWJlciBhbmQgZGF0YSBmb3IgdGhlIHN0ZXAuCiAgICAgICAgICovCiAgICAgICAgX2NyZWF0ZVN0ZXBEYXR1bShtZXRhZGF0YSkgewogICAgICAgICAgICByZXR1cm4gewogICAgICAgICAgICAgICAgLy8gVGhlIHdhbGwgdGltZSB3aXRoaW4gdGhlIG1ldGFkYXRhIGlzIGluIHNlY29uZHMuIFRoZSBEYXRlCiAgICAgICAgICAgICAgICAvLyBjb25zdHJ1Y3RvciBhY2NlcHRzIGEgdGltZSBpbiBtaWxsaXNlY29uZHMsIHNvIHdlIG11bHRpcGx5IGJ5IDEwMDAuCiAgICAgICAgICAgICAgICB3YWxsX3RpbWU6IG5ldyBEYXRlKG1ldGFkYXRhLndhbGxfdGltZSAqIDEwMDApLAogICAgICAgICAgICAgICAgc3RlcDogbWV0YWRhdGEuc3RlcCwKICAgICAgICAgICAgICAgIGNvbmZpZzogbWV0YWRhdGEuY29uZmlnLAogICAgICAgICAgICAgICAgY29udGVudF90eXBlOiBtZXRhZGF0YS5jb250ZW50X3R5cGUsCiAgICAgICAgICAgICAgICBjb21wb25lbnRzOiBtZXRhZGF0YS5jb21wb25lbnRzLAogICAgICAgICAgICB9OwogICAgICAgIH0KICAgIH0KCiAgICAvLyBQb2x5ZmlsbHMKCiAgICBpZiAoIE51bWJlci5FUFNJTE9OID09PSB1bmRlZmluZWQgKSB7CgogICAgCU51bWJlci5FUFNJTE9OID0gTWF0aC5wb3coIDIsIC0gNTIgKTsKCiAgICB9CgogICAgaWYgKCBOdW1iZXIuaXNJbnRlZ2VyID09PSB1bmRlZmluZWQgKSB7CgogICAgCS8vIE1pc3NpbmcgaW4gSUUKICAgIAkvLyBodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9OdW1iZXIvaXNJbnRlZ2VyCgogICAgCU51bWJlci5pc0ludGVnZXIgPSBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJcmV0dXJuIHR5cGVvZiB2YWx1ZSA9PT0gJ251bWJlcicgJiYgaXNGaW5pdGUoIHZhbHVlICkgJiYgTWF0aC5mbG9vciggdmFsdWUgKSA9PT0gdmFsdWU7CgogICAgCX07CgogICAgfQoKICAgIC8vCgogICAgaWYgKCBNYXRoLnNpZ24gPT09IHVuZGVmaW5lZCApIHsKCiAgICAJLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvTWF0aC9zaWduCgogICAgCU1hdGguc2lnbiA9IGZ1bmN0aW9uICggeCApIHsKCiAgICAJCXJldHVybiAoIHggPCAwICkgPyAtIDEgOiAoIHggPiAwICkgPyAxIDogKyB4OwoKICAgIAl9OwoKICAgIH0KCiAgICBpZiAoICduYW1lJyBpbiBGdW5jdGlvbi5wcm90b3R5cGUgPT09IGZhbHNlICkgewoKICAgIAkvLyBNaXNzaW5nIGluIElFCiAgICAJLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvRnVuY3Rpb24vbmFtZQoKICAgIAlPYmplY3QuZGVmaW5lUHJvcGVydHkoIEZ1bmN0aW9uLnByb3RvdHlwZSwgJ25hbWUnLCB7CgogICAgCQlnZXQ6IGZ1bmN0aW9uICgpIHsKCiAgICAJCQlyZXR1cm4gdGhpcy50b1N0cmluZygpLm1hdGNoKCAvXlxzKmZ1bmN0aW9uXHMqKFteXChcc10qKS8gKVsgMSBdOwoKICAgIAkJfQoKICAgIAl9ICk7CgogICAgfQoKICAgIGlmICggT2JqZWN0LmFzc2lnbiA9PT0gdW5kZWZpbmVkICkgewoKICAgIAkvLyBNaXNzaW5nIGluIElFCiAgICAJLy8gaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvT2JqZWN0L2Fzc2lnbgoKICAgIAlPYmplY3QuYXNzaWduID0gZnVuY3Rpb24gKCB0YXJnZXQgKSB7CgogICAgCQlpZiAoIHRhcmdldCA9PT0gdW5kZWZpbmVkIHx8IHRhcmdldCA9PT0gbnVsbCApIHsKCiAgICAJCQl0aHJvdyBuZXcgVHlwZUVycm9yKCAnQ2Fubm90IGNvbnZlcnQgdW5kZWZpbmVkIG9yIG51bGwgdG8gb2JqZWN0JyApOwoKICAgIAkJfQoKICAgIAkJdmFyIG91dHB1dCA9IE9iamVjdCggdGFyZ2V0ICk7CgogICAgCQlmb3IgKCB2YXIgaW5kZXggPSAxOyBpbmRleCA8IGFyZ3VtZW50cy5sZW5ndGg7IGluZGV4ICsrICkgewoKICAgIAkJCXZhciBzb3VyY2UgPSBhcmd1bWVudHNbIGluZGV4IF07CgogICAgCQkJaWYgKCBzb3VyY2UgIT09IHVuZGVmaW5lZCAmJiBzb3VyY2UgIT09IG51bGwgKSB7CgogICAgCQkJCWZvciAoIHZhciBuZXh0S2V5IGluIHNvdXJjZSApIHsKCiAgICAJCQkJCWlmICggT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKCBzb3VyY2UsIG5leHRLZXkgKSApIHsKCiAgICAJCQkJCQlvdXRwdXRbIG5leHRLZXkgXSA9IHNvdXJjZVsgbmV4dEtleSBdOwoKICAgIAkJCQkJfQoKICAgIAkJCQl9CgogICAgCQkJfQoKICAgIAkJfQoKICAgIAkJcmV0dXJuIG91dHB1dDsKCiAgICAJfTsKCiAgICB9CgogICAgLyoqCiAgICAgKiBodHRwczovL2dpdGh1Yi5jb20vbXJkb29iL2V2ZW50ZGlzcGF0Y2hlci5qcy8KICAgICAqLwoKICAgIGZ1bmN0aW9uIEV2ZW50RGlzcGF0Y2hlcigpIHt9CgogICAgT2JqZWN0LmFzc2lnbiggRXZlbnREaXNwYXRjaGVyLnByb3RvdHlwZSwgewoKICAgIAlhZGRFdmVudExpc3RlbmVyOiBmdW5jdGlvbiAoIHR5cGUsIGxpc3RlbmVyICkgewoKICAgIAkJaWYgKCB0aGlzLl9saXN0ZW5lcnMgPT09IHVuZGVmaW5lZCApIHRoaXMuX2xpc3RlbmVycyA9IHt9OwoKICAgIAkJdmFyIGxpc3RlbmVycyA9IHRoaXMuX2xpc3RlbmVyczsKCiAgICAJCWlmICggbGlzdGVuZXJzWyB0eXBlIF0gPT09IHVuZGVmaW5lZCApIHsKCiAgICAJCQlsaXN0ZW5lcnNbIHR5cGUgXSA9IFtdOwoKICAgIAkJfQoKICAgIAkJaWYgKCBsaXN0ZW5lcnNbIHR5cGUgXS5pbmRleE9mKCBsaXN0ZW5lciApID09PSAtIDEgKSB7CgogICAgCQkJbGlzdGVuZXJzWyB0eXBlIF0ucHVzaCggbGlzdGVuZXIgKTsKCiAgICAJCX0KCiAgICAJfSwKCiAgICAJaGFzRXZlbnRMaXN0ZW5lcjogZnVuY3Rpb24gKCB0eXBlLCBsaXN0ZW5lciApIHsKCiAgICAJCWlmICggdGhpcy5fbGlzdGVuZXJzID09PSB1bmRlZmluZWQgKSByZXR1cm4gZmFsc2U7CgogICAgCQl2YXIgbGlzdGVuZXJzID0gdGhpcy5fbGlzdGVuZXJzOwoKICAgIAkJcmV0dXJuIGxpc3RlbmVyc1sgdHlwZSBdICE9PSB1bmRlZmluZWQgJiYgbGlzdGVuZXJzWyB0eXBlIF0uaW5kZXhPZiggbGlzdGVuZXIgKSAhPT0gLSAxOwoKICAgIAl9LAoKICAgIAlyZW1vdmVFdmVudExpc3RlbmVyOiBmdW5jdGlvbiAoIHR5cGUsIGxpc3RlbmVyICkgewoKICAgIAkJaWYgKCB0aGlzLl9saXN0ZW5lcnMgPT09IHVuZGVmaW5lZCApIHJldHVybjsKCiAgICAJCXZhciBsaXN0ZW5lcnMgPSB0aGlzLl9saXN0ZW5lcnM7CiAgICAJCXZhciBsaXN0ZW5lckFycmF5ID0gbGlzdGVuZXJzWyB0eXBlIF07CgogICAgCQlpZiAoIGxpc3RlbmVyQXJyYXkgIT09IHVuZGVmaW5lZCApIHsKCiAgICAJCQl2YXIgaW5kZXggPSBsaXN0ZW5lckFycmF5LmluZGV4T2YoIGxpc3RlbmVyICk7CgogICAgCQkJaWYgKCBpbmRleCAhPT0gLSAxICkgewoKICAgIAkJCQlsaXN0ZW5lckFycmF5LnNwbGljZSggaW5kZXgsIDEgKTsKCiAgICAJCQl9CgogICAgCQl9CgogICAgCX0sCgogICAgCWRpc3BhdGNoRXZlbnQ6IGZ1bmN0aW9uICggZXZlbnQgKSB7CgogICAgCQlpZiAoIHRoaXMuX2xpc3RlbmVycyA9PT0gdW5kZWZpbmVkICkgcmV0dXJuOwoKICAgIAkJdmFyIGxpc3RlbmVycyA9IHRoaXMuX2xpc3RlbmVyczsKICAgIAkJdmFyIGxpc3RlbmVyQXJyYXkgPSBsaXN0ZW5lcnNbIGV2ZW50LnR5cGUgXTsKCiAgICAJCWlmICggbGlzdGVuZXJBcnJheSAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWV2ZW50LnRhcmdldCA9IHRoaXM7CgogICAgCQkJdmFyIGFycmF5ID0gbGlzdGVuZXJBcnJheS5zbGljZSggMCApOwoKICAgIAkJCWZvciAoIHZhciBpID0gMCwgbCA9IGFycmF5Lmxlbmd0aDsgaSA8IGw7IGkgKysgKSB7CgogICAgCQkJCWFycmF5WyBpIF0uY2FsbCggdGhpcywgZXZlbnQgKTsKCiAgICAJCQl9CgogICAgCQl9CgogICAgCX0KCiAgICB9ICk7CgogICAgdmFyIFJFVklTSU9OID0gJzEwOCc7CiAgICB2YXIgTU9VU0UgPSB7IExFRlQ6IDAsIE1JRERMRTogMSwgUklHSFQ6IDIsIFJPVEFURTogMCwgRE9MTFk6IDEsIFBBTjogMiB9OwogICAgdmFyIFRPVUNIID0geyBST1RBVEU6IDAsIFBBTjogMSwgRE9MTFlfUEFOOiAyLCBET0xMWV9ST1RBVEU6IDMgfTsKICAgIHZhciBDdWxsRmFjZU5vbmUgPSAwOwogICAgdmFyIEN1bGxGYWNlQmFjayA9IDE7CiAgICB2YXIgQ3VsbEZhY2VGcm9udCA9IDI7CiAgICB2YXIgQ3VsbEZhY2VGcm9udEJhY2sgPSAzOwogICAgdmFyIEZyb250RmFjZURpcmVjdGlvbkNXID0gMDsKICAgIHZhciBGcm9udEZhY2VEaXJlY3Rpb25DQ1cgPSAxOwogICAgdmFyIEJhc2ljU2hhZG93TWFwID0gMDsKICAgIHZhciBQQ0ZTaGFkb3dNYXAgPSAxOwogICAgdmFyIFBDRlNvZnRTaGFkb3dNYXAgPSAyOwogICAgdmFyIFZTTVNoYWRvd01hcCA9IDM7CiAgICB2YXIgRnJvbnRTaWRlID0gMDsKICAgIHZhciBCYWNrU2lkZSA9IDE7CiAgICB2YXIgRG91YmxlU2lkZSA9IDI7CiAgICB2YXIgRmxhdFNoYWRpbmcgPSAxOwogICAgdmFyIFNtb290aFNoYWRpbmcgPSAyOwogICAgdmFyIE5vQ29sb3JzID0gMDsKICAgIHZhciBGYWNlQ29sb3JzID0gMTsKICAgIHZhciBWZXJ0ZXhDb2xvcnMgPSAyOwogICAgdmFyIE5vQmxlbmRpbmcgPSAwOwogICAgdmFyIE5vcm1hbEJsZW5kaW5nID0gMTsKICAgIHZhciBBZGRpdGl2ZUJsZW5kaW5nID0gMjsKICAgIHZhciBTdWJ0cmFjdGl2ZUJsZW5kaW5nID0gMzsKICAgIHZhciBNdWx0aXBseUJsZW5kaW5nID0gNDsKICAgIHZhciBDdXN0b21CbGVuZGluZyA9IDU7CiAgICB2YXIgQWRkRXF1YXRpb24gPSAxMDA7CiAgICB2YXIgU3VidHJhY3RFcXVhdGlvbiA9IDEwMTsKICAgIHZhciBSZXZlcnNlU3VidHJhY3RFcXVhdGlvbiA9IDEwMjsKICAgIHZhciBNaW5FcXVhdGlvbiA9IDEwMzsKICAgIHZhciBNYXhFcXVhdGlvbiA9IDEwNDsKICAgIHZhciBaZXJvRmFjdG9yID0gMjAwOwogICAgdmFyIE9uZUZhY3RvciA9IDIwMTsKICAgIHZhciBTcmNDb2xvckZhY3RvciA9IDIwMjsKICAgIHZhciBPbmVNaW51c1NyY0NvbG9yRmFjdG9yID0gMjAzOwogICAgdmFyIFNyY0FscGhhRmFjdG9yID0gMjA0OwogICAgdmFyIE9uZU1pbnVzU3JjQWxwaGFGYWN0b3IgPSAyMDU7CiAgICB2YXIgRHN0QWxwaGFGYWN0b3IgPSAyMDY7CiAgICB2YXIgT25lTWludXNEc3RBbHBoYUZhY3RvciA9IDIwNzsKICAgIHZhciBEc3RDb2xvckZhY3RvciA9IDIwODsKICAgIHZhciBPbmVNaW51c0RzdENvbG9yRmFjdG9yID0gMjA5OwogICAgdmFyIFNyY0FscGhhU2F0dXJhdGVGYWN0b3IgPSAyMTA7CiAgICB2YXIgTmV2ZXJEZXB0aCA9IDA7CiAgICB2YXIgQWx3YXlzRGVwdGggPSAxOwogICAgdmFyIExlc3NEZXB0aCA9IDI7CiAgICB2YXIgTGVzc0VxdWFsRGVwdGggPSAzOwogICAgdmFyIEVxdWFsRGVwdGggPSA0OwogICAgdmFyIEdyZWF0ZXJFcXVhbERlcHRoID0gNTsKICAgIHZhciBHcmVhdGVyRGVwdGggPSA2OwogICAgdmFyIE5vdEVxdWFsRGVwdGggPSA3OwogICAgdmFyIE11bHRpcGx5T3BlcmF0aW9uID0gMDsKICAgIHZhciBNaXhPcGVyYXRpb24gPSAxOwogICAgdmFyIEFkZE9wZXJhdGlvbiA9IDI7CiAgICB2YXIgTm9Ub25lTWFwcGluZyA9IDA7CiAgICB2YXIgTGluZWFyVG9uZU1hcHBpbmcgPSAxOwogICAgdmFyIFJlaW5oYXJkVG9uZU1hcHBpbmcgPSAyOwogICAgdmFyIFVuY2hhcnRlZDJUb25lTWFwcGluZyA9IDM7CiAgICB2YXIgQ2luZW9uVG9uZU1hcHBpbmcgPSA0OwogICAgdmFyIEFDRVNGaWxtaWNUb25lTWFwcGluZyA9IDU7CgogICAgdmFyIFVWTWFwcGluZyA9IDMwMDsKICAgIHZhciBDdWJlUmVmbGVjdGlvbk1hcHBpbmcgPSAzMDE7CiAgICB2YXIgQ3ViZVJlZnJhY3Rpb25NYXBwaW5nID0gMzAyOwogICAgdmFyIEVxdWlyZWN0YW5ndWxhclJlZmxlY3Rpb25NYXBwaW5nID0gMzAzOwogICAgdmFyIEVxdWlyZWN0YW5ndWxhclJlZnJhY3Rpb25NYXBwaW5nID0gMzA0OwogICAgdmFyIFNwaGVyaWNhbFJlZmxlY3Rpb25NYXBwaW5nID0gMzA1OwogICAgdmFyIEN1YmVVVlJlZmxlY3Rpb25NYXBwaW5nID0gMzA2OwogICAgdmFyIEN1YmVVVlJlZnJhY3Rpb25NYXBwaW5nID0gMzA3OwogICAgdmFyIFJlcGVhdFdyYXBwaW5nID0gMTAwMDsKICAgIHZhciBDbGFtcFRvRWRnZVdyYXBwaW5nID0gMTAwMTsKICAgIHZhciBNaXJyb3JlZFJlcGVhdFdyYXBwaW5nID0gMTAwMjsKICAgIHZhciBOZWFyZXN0RmlsdGVyID0gMTAwMzsKICAgIHZhciBOZWFyZXN0TWlwbWFwTmVhcmVzdEZpbHRlciA9IDEwMDQ7CiAgICB2YXIgTmVhcmVzdE1pcE1hcE5lYXJlc3RGaWx0ZXIgPSAxMDA0OwogICAgdmFyIE5lYXJlc3RNaXBtYXBMaW5lYXJGaWx0ZXIgPSAxMDA1OwogICAgdmFyIE5lYXJlc3RNaXBNYXBMaW5lYXJGaWx0ZXIgPSAxMDA1OwogICAgdmFyIExpbmVhckZpbHRlciA9IDEwMDY7CiAgICB2YXIgTGluZWFyTWlwbWFwTmVhcmVzdEZpbHRlciA9IDEwMDc7CiAgICB2YXIgTGluZWFyTWlwTWFwTmVhcmVzdEZpbHRlciA9IDEwMDc7CiAgICB2YXIgTGluZWFyTWlwbWFwTGluZWFyRmlsdGVyID0gMTAwODsKICAgIHZhciBMaW5lYXJNaXBNYXBMaW5lYXJGaWx0ZXIgPSAxMDA4OwogICAgdmFyIFVuc2lnbmVkQnl0ZVR5cGUgPSAxMDA5OwogICAgdmFyIEJ5dGVUeXBlID0gMTAxMDsKICAgIHZhciBTaG9ydFR5cGUgPSAxMDExOwogICAgdmFyIFVuc2lnbmVkU2hvcnRUeXBlID0gMTAxMjsKICAgIHZhciBJbnRUeXBlID0gMTAxMzsKICAgIHZhciBVbnNpZ25lZEludFR5cGUgPSAxMDE0OwogICAgdmFyIEZsb2F0VHlwZSA9IDEwMTU7CiAgICB2YXIgSGFsZkZsb2F0VHlwZSA9IDEwMTY7CiAgICB2YXIgVW5zaWduZWRTaG9ydDQ0NDRUeXBlID0gMTAxNzsKICAgIHZhciBVbnNpZ25lZFNob3J0NTU1MVR5cGUgPSAxMDE4OwogICAgdmFyIFVuc2lnbmVkU2hvcnQ1NjVUeXBlID0gMTAxOTsKICAgIHZhciBVbnNpZ25lZEludDI0OFR5cGUgPSAxMDIwOwogICAgdmFyIEFscGhhRm9ybWF0ID0gMTAyMTsKICAgIHZhciBSR0JGb3JtYXQgPSAxMDIyOwogICAgdmFyIFJHQkFGb3JtYXQgPSAxMDIzOwogICAgdmFyIEx1bWluYW5jZUZvcm1hdCA9IDEwMjQ7CiAgICB2YXIgTHVtaW5hbmNlQWxwaGFGb3JtYXQgPSAxMDI1OwogICAgdmFyIFJHQkVGb3JtYXQgPSBSR0JBRm9ybWF0OwogICAgdmFyIERlcHRoRm9ybWF0ID0gMTAyNjsKICAgIHZhciBEZXB0aFN0ZW5jaWxGb3JtYXQgPSAxMDI3OwogICAgdmFyIFJlZEZvcm1hdCA9IDEwMjg7CiAgICB2YXIgUkdCX1MzVENfRFhUMV9Gb3JtYXQgPSAzMzc3NjsKICAgIHZhciBSR0JBX1MzVENfRFhUMV9Gb3JtYXQgPSAzMzc3NzsKICAgIHZhciBSR0JBX1MzVENfRFhUM19Gb3JtYXQgPSAzMzc3ODsKICAgIHZhciBSR0JBX1MzVENfRFhUNV9Gb3JtYXQgPSAzMzc3OTsKICAgIHZhciBSR0JfUFZSVENfNEJQUFYxX0Zvcm1hdCA9IDM1ODQwOwogICAgdmFyIFJHQl9QVlJUQ18yQlBQVjFfRm9ybWF0ID0gMzU4NDE7CiAgICB2YXIgUkdCQV9QVlJUQ180QlBQVjFfRm9ybWF0ID0gMzU4NDI7CiAgICB2YXIgUkdCQV9QVlJUQ18yQlBQVjFfRm9ybWF0ID0gMzU4NDM7CiAgICB2YXIgUkdCX0VUQzFfRm9ybWF0ID0gMzYxOTY7CiAgICB2YXIgUkdCQV9BU1RDXzR4NF9Gb3JtYXQgPSAzNzgwODsKICAgIHZhciBSR0JBX0FTVENfNXg0X0Zvcm1hdCA9IDM3ODA5OwogICAgdmFyIFJHQkFfQVNUQ181eDVfRm9ybWF0ID0gMzc4MTA7CiAgICB2YXIgUkdCQV9BU1RDXzZ4NV9Gb3JtYXQgPSAzNzgxMTsKICAgIHZhciBSR0JBX0FTVENfNng2X0Zvcm1hdCA9IDM3ODEyOwogICAgdmFyIFJHQkFfQVNUQ184eDVfRm9ybWF0ID0gMzc4MTM7CiAgICB2YXIgUkdCQV9BU1RDXzh4Nl9Gb3JtYXQgPSAzNzgxNDsKICAgIHZhciBSR0JBX0FTVENfOHg4X0Zvcm1hdCA9IDM3ODE1OwogICAgdmFyIFJHQkFfQVNUQ18xMHg1X0Zvcm1hdCA9IDM3ODE2OwogICAgdmFyIFJHQkFfQVNUQ18xMHg2X0Zvcm1hdCA9IDM3ODE3OwogICAgdmFyIFJHQkFfQVNUQ18xMHg4X0Zvcm1hdCA9IDM3ODE4OwogICAgdmFyIFJHQkFfQVNUQ18xMHgxMF9Gb3JtYXQgPSAzNzgxOTsKICAgIHZhciBSR0JBX0FTVENfMTJ4MTBfRm9ybWF0ID0gMzc4MjA7CiAgICB2YXIgUkdCQV9BU1RDXzEyeDEyX0Zvcm1hdCA9IDM3ODIxOwogICAgdmFyIExvb3BPbmNlID0gMjIwMDsKICAgIHZhciBMb29wUmVwZWF0ID0gMjIwMTsKICAgIHZhciBMb29wUGluZ1BvbmcgPSAyMjAyOwogICAgdmFyIEludGVycG9sYXRlRGlzY3JldGUgPSAyMzAwOwogICAgdmFyIEludGVycG9sYXRlTGluZWFyID0gMjMwMTsKICAgIHZhciBJbnRlcnBvbGF0ZVNtb290aCA9IDIzMDI7CiAgICB2YXIgWmVyb0N1cnZhdHVyZUVuZGluZyA9IDI0MDA7CiAgICB2YXIgWmVyb1Nsb3BlRW5kaW5nID0gMjQwMTsKICAgIHZhciBXcmFwQXJvdW5kRW5kaW5nID0gMjQwMjsKICAgIHZhciBUcmlhbmdsZXNEcmF3TW9kZSA9IDA7CiAgICB2YXIgVHJpYW5nbGVTdHJpcERyYXdNb2RlID0gMTsKICAgIHZhciBUcmlhbmdsZUZhbkRyYXdNb2RlID0gMjsKICAgIHZhciBMaW5lYXJFbmNvZGluZyA9IDMwMDA7CiAgICB2YXIgc1JHQkVuY29kaW5nID0gMzAwMTsKICAgIHZhciBHYW1tYUVuY29kaW5nID0gMzAwNzsKICAgIHZhciBSR0JFRW5jb2RpbmcgPSAzMDAyOwogICAgdmFyIExvZ0x1dkVuY29kaW5nID0gMzAwMzsKICAgIHZhciBSR0JNN0VuY29kaW5nID0gMzAwNDsKICAgIHZhciBSR0JNMTZFbmNvZGluZyA9IDMwMDU7CiAgICB2YXIgUkdCREVuY29kaW5nID0gMzAwNjsKICAgIHZhciBCYXNpY0RlcHRoUGFja2luZyA9IDMyMDA7CiAgICB2YXIgUkdCQURlcHRoUGFja2luZyA9IDMyMDE7CiAgICB2YXIgVGFuZ2VudFNwYWNlTm9ybWFsTWFwID0gMDsKICAgIHZhciBPYmplY3RTcGFjZU5vcm1hbE1hcCA9IDE7CgogICAgdmFyIFplcm9TdGVuY2lsT3AgPSAwOwogICAgdmFyIEtlZXBTdGVuY2lsT3AgPSA3NjgwOwogICAgdmFyIFJlcGxhY2VTdGVuY2lsT3AgPSA3NjgxOwogICAgdmFyIEluY3JlbWVudFN0ZW5jaWxPcCA9IDc2ODI7CiAgICB2YXIgRGVjcmVtZW50U3RlbmNpbE9wID0gNzY4MzsKICAgIHZhciBJbmNyZW1lbnRXcmFwU3RlbmNpbE9wID0gMzQwNTU7CiAgICB2YXIgRGVjcmVtZW50V3JhcFN0ZW5jaWxPcCA9IDM0MDU2OwogICAgdmFyIEludmVydFN0ZW5jaWxPcCA9IDUzODY7CgogICAgdmFyIE5ldmVyU3RlbmNpbEZ1bmMgPSA1MTI7CiAgICB2YXIgTGVzc1N0ZW5jaWxGdW5jID0gNTEzOwogICAgdmFyIEVxdWFsU3RlbmNpbEZ1bmMgPSA1MTQ7CiAgICB2YXIgTGVzc0VxdWFsU3RlbmNpbEZ1bmMgPSA1MTU7CiAgICB2YXIgR3JlYXRlclN0ZW5jaWxGdW5jID0gNTE2OwogICAgdmFyIE5vdEVxdWFsU3RlbmNpbEZ1bmMgPSA1MTc7CiAgICB2YXIgR3JlYXRlckVxdWFsU3RlbmNpbEZ1bmMgPSA1MTg7CiAgICB2YXIgQWx3YXlzU3RlbmNpbEZ1bmMgPSA1MTk7CgogICAgLyoqCiAgICAgKiBAYXV0aG9yIGFsdGVyZWRxIC8gaHR0cDovL2FsdGVyZWRxdWFsaWEuY29tLwogICAgICogQGF1dGhvciBtcmRvb2IgLyBodHRwOi8vbXJkb29iLmNvbS8KICAgICAqLwoKICAgIHZhciBfbHV0ID0gW107CgogICAgZm9yICggdmFyIGkgPSAwOyBpIDwgMjU2OyBpICsrICkgewoKICAgIAlfbHV0WyBpIF0gPSAoIGkgPCAxNiA/ICcwJyA6ICcnICkgKyAoIGkgKS50b1N0cmluZyggMTYgKTsKCiAgICB9CgogICAgdmFyIF9NYXRoID0gewoKICAgIAlERUcyUkFEOiBNYXRoLlBJIC8gMTgwLAogICAgCVJBRDJERUc6IDE4MCAvIE1hdGguUEksCgogICAgCWdlbmVyYXRlVVVJRDogZnVuY3Rpb24gKCkgewoKICAgIAkJLy8gaHR0cDovL3N0YWNrb3ZlcmZsb3cuY29tL3F1ZXN0aW9ucy8xMDUwMzQvaG93LXRvLWNyZWF0ZS1hLWd1aWQtdXVpZC1pbi1qYXZhc2NyaXB0LzIxOTYzMTM2IzIxOTYzMTM2CgogICAgCQl2YXIgZDAgPSBNYXRoLnJhbmRvbSgpICogMHhmZmZmZmZmZiB8IDA7CiAgICAJCXZhciBkMSA9IE1hdGgucmFuZG9tKCkgKiAweGZmZmZmZmZmIHwgMDsKICAgIAkJdmFyIGQyID0gTWF0aC5yYW5kb20oKSAqIDB4ZmZmZmZmZmYgfCAwOwogICAgCQl2YXIgZDMgPSBNYXRoLnJhbmRvbSgpICogMHhmZmZmZmZmZiB8IDA7CiAgICAJCXZhciB1dWlkID0gX2x1dFsgZDAgJiAweGZmIF0gKyBfbHV0WyBkMCA+PiA4ICYgMHhmZiBdICsgX2x1dFsgZDAgPj4gMTYgJiAweGZmIF0gKyBfbHV0WyBkMCA+PiAyNCAmIDB4ZmYgXSArICctJyArCiAgICAJCQlfbHV0WyBkMSAmIDB4ZmYgXSArIF9sdXRbIGQxID4+IDggJiAweGZmIF0gKyAnLScgKyBfbHV0WyBkMSA+PiAxNiAmIDB4MGYgfCAweDQwIF0gKyBfbHV0WyBkMSA+PiAyNCAmIDB4ZmYgXSArICctJyArCiAgICAJCQlfbHV0WyBkMiAmIDB4M2YgfCAweDgwIF0gKyBfbHV0WyBkMiA+PiA4ICYgMHhmZiBdICsgJy0nICsgX2x1dFsgZDIgPj4gMTYgJiAweGZmIF0gKyBfbHV0WyBkMiA+PiAyNCAmIDB4ZmYgXSArCiAgICAJCQlfbHV0WyBkMyAmIDB4ZmYgXSArIF9sdXRbIGQzID4+IDggJiAweGZmIF0gKyBfbHV0WyBkMyA+PiAxNiAmIDB4ZmYgXSArIF9sdXRbIGQzID4+IDI0ICYgMHhmZiBdOwoKICAgIAkJLy8gLnRvVXBwZXJDYXNlKCkgaGVyZSBmbGF0dGVucyBjb25jYXRlbmF0ZWQgc3RyaW5ncyB0byBzYXZlIGhlYXAgbWVtb3J5IHNwYWNlLgogICAgCQlyZXR1cm4gdXVpZC50b1VwcGVyQ2FzZSgpOwoKICAgIAl9LAoKICAgIAljbGFtcDogZnVuY3Rpb24gKCB2YWx1ZSwgbWluLCBtYXggKSB7CgogICAgCQlyZXR1cm4gTWF0aC5tYXgoIG1pbiwgTWF0aC5taW4oIG1heCwgdmFsdWUgKSApOwoKICAgIAl9LAoKICAgIAkvLyBjb21wdXRlIGV1Y2xpZGlhbiBtb2R1bG8gb2YgbSAlIG4KICAgIAkvLyBodHRwczovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9Nb2R1bG9fb3BlcmF0aW9uCgogICAgCWV1Y2xpZGVhbk1vZHVsbzogZnVuY3Rpb24gKCBuLCBtICkgewoKICAgIAkJcmV0dXJuICggKCBuICUgbSApICsgbSApICUgbTsKCiAgICAJfSwKCiAgICAJLy8gTGluZWFyIG1hcHBpbmcgZnJvbSByYW5nZSA8YTEsIGEyPiB0byByYW5nZSA8YjEsIGIyPgoKICAgIAltYXBMaW5lYXI6IGZ1bmN0aW9uICggeCwgYTEsIGEyLCBiMSwgYjIgKSB7CgogICAgCQlyZXR1cm4gYjEgKyAoIHggLSBhMSApICogKCBiMiAtIGIxICkgLyAoIGEyIC0gYTEgKTsKCiAgICAJfSwKCiAgICAJLy8gaHR0cHM6Ly9lbi53aWtpcGVkaWEub3JnL3dpa2kvTGluZWFyX2ludGVycG9sYXRpb24KCiAgICAJbGVycDogZnVuY3Rpb24gKCB4LCB5LCB0ICkgewoKICAgIAkJcmV0dXJuICggMSAtIHQgKSAqIHggKyB0ICogeTsKCiAgICAJfSwKCiAgICAJLy8gaHR0cDovL2VuLndpa2lwZWRpYS5vcmcvd2lraS9TbW9vdGhzdGVwCgogICAgCXNtb290aHN0ZXA6IGZ1bmN0aW9uICggeCwgbWluLCBtYXggKSB7CgogICAgCQlpZiAoIHggPD0gbWluICkgcmV0dXJuIDA7CiAgICAJCWlmICggeCA+PSBtYXggKSByZXR1cm4gMTsKCiAgICAJCXggPSAoIHggLSBtaW4gKSAvICggbWF4IC0gbWluICk7CgogICAgCQlyZXR1cm4geCAqIHggKiAoIDMgLSAyICogeCApOwoKICAgIAl9LAoKICAgIAlzbW9vdGhlcnN0ZXA6IGZ1bmN0aW9uICggeCwgbWluLCBtYXggKSB7CgogICAgCQlpZiAoIHggPD0gbWluICkgcmV0dXJuIDA7CiAgICAJCWlmICggeCA+PSBtYXggKSByZXR1cm4gMTsKCiAgICAJCXggPSAoIHggLSBtaW4gKSAvICggbWF4IC0gbWluICk7CgogICAgCQlyZXR1cm4geCAqIHggKiB4ICogKCB4ICogKCB4ICogNiAtIDE1ICkgKyAxMCApOwoKICAgIAl9LAoKICAgIAkvLyBSYW5kb20gaW50ZWdlciBmcm9tIDxsb3csIGhpZ2g+IGludGVydmFsCgogICAgCXJhbmRJbnQ6IGZ1bmN0aW9uICggbG93LCBoaWdoICkgewoKICAgIAkJcmV0dXJuIGxvdyArIE1hdGguZmxvb3IoIE1hdGgucmFuZG9tKCkgKiAoIGhpZ2ggLSBsb3cgKyAxICkgKTsKCiAgICAJfSwKCiAgICAJLy8gUmFuZG9tIGZsb2F0IGZyb20gPGxvdywgaGlnaD4gaW50ZXJ2YWwKCiAgICAJcmFuZEZsb2F0OiBmdW5jdGlvbiAoIGxvdywgaGlnaCApIHsKCiAgICAJCXJldHVybiBsb3cgKyBNYXRoLnJhbmRvbSgpICogKCBoaWdoIC0gbG93ICk7CgogICAgCX0sCgogICAgCS8vIFJhbmRvbSBmbG9hdCBmcm9tIDwtcmFuZ2UvMiwgcmFuZ2UvMj4gaW50ZXJ2YWwKCiAgICAJcmFuZEZsb2F0U3ByZWFkOiBmdW5jdGlvbiAoIHJhbmdlICkgewoKICAgIAkJcmV0dXJuIHJhbmdlICogKCAwLjUgLSBNYXRoLnJhbmRvbSgpICk7CgogICAgCX0sCgogICAgCWRlZ1RvUmFkOiBmdW5jdGlvbiAoIGRlZ3JlZXMgKSB7CgogICAgCQlyZXR1cm4gZGVncmVlcyAqIF9NYXRoLkRFRzJSQUQ7CgogICAgCX0sCgogICAgCXJhZFRvRGVnOiBmdW5jdGlvbiAoIHJhZGlhbnMgKSB7CgogICAgCQlyZXR1cm4gcmFkaWFucyAqIF9NYXRoLlJBRDJERUc7CgogICAgCX0sCgogICAgCWlzUG93ZXJPZlR3bzogZnVuY3Rpb24gKCB2YWx1ZSApIHsKCiAgICAJCXJldHVybiAoIHZhbHVlICYgKCB2YWx1ZSAtIDEgKSApID09PSAwICYmIHZhbHVlICE9PSAwOwoKICAgIAl9LAoKICAgIAljZWlsUG93ZXJPZlR3bzogZnVuY3Rpb24gKCB2YWx1ZSApIHsKCiAgICAJCXJldHVybiBNYXRoLnBvdyggMiwgTWF0aC5jZWlsKCBNYXRoLmxvZyggdmFsdWUgKSAvIE1hdGguTE4yICkgKTsKCiAgICAJfSwKCiAgICAJZmxvb3JQb3dlck9mVHdvOiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJcmV0dXJuIE1hdGgucG93KCAyLCBNYXRoLmZsb29yKCBNYXRoLmxvZyggdmFsdWUgKSAvIE1hdGguTE4yICkgKTsKCiAgICAJfQoKICAgIH07CgogICAgLyoqCiAgICAgKiBAYXV0aG9yIG1yZG9vYiAvIGh0dHA6Ly9tcmRvb2IuY29tLwogICAgICogQGF1dGhvciBwaGlsb2diIC8gaHR0cDovL2Jsb2cudGhlaml0Lm9yZy8KICAgICAqIEBhdXRob3IgZWdyYWV0aGVyIC8gaHR0cDovL2VncmFldGhlci5jb20vCiAgICAgKiBAYXV0aG9yIHp6ODUgLyBodHRwOi8vd3d3LmxhYjRnYW1lcy5uZXQveno4NS9ibG9nCiAgICAgKi8KCiAgICBmdW5jdGlvbiBWZWN0b3IyKCB4LCB5ICkgewoKICAgIAl0aGlzLnggPSB4IHx8IDA7CiAgICAJdGhpcy55ID0geSB8fCAwOwoKICAgIH0KCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydGllcyggVmVjdG9yMi5wcm90b3R5cGUsIHsKCiAgICAJIndpZHRoIjogewoKICAgIAkJZ2V0OiBmdW5jdGlvbiAoKSB7CgogICAgCQkJcmV0dXJuIHRoaXMueDsKCiAgICAJCX0sCgogICAgCQlzZXQ6IGZ1bmN0aW9uICggdmFsdWUgKSB7CgogICAgCQkJdGhpcy54ID0gdmFsdWU7CgogICAgCQl9CgogICAgCX0sCgogICAgCSJoZWlnaHQiOiB7CgogICAgCQlnZXQ6IGZ1bmN0aW9uICgpIHsKCiAgICAJCQlyZXR1cm4gdGhpcy55OwoKICAgIAkJfSwKCiAgICAJCXNldDogZnVuY3Rpb24gKCB2YWx1ZSApIHsKCiAgICAJCQl0aGlzLnkgPSB2YWx1ZTsKCiAgICAJCX0KCiAgICAJfQoKICAgIH0gKTsKCiAgICBPYmplY3QuYXNzaWduKCBWZWN0b3IyLnByb3RvdHlwZSwgewoKICAgIAlpc1ZlY3RvcjI6IHRydWUsCgogICAgCXNldDogZnVuY3Rpb24gKCB4LCB5ICkgewoKICAgIAkJdGhpcy54ID0geDsKICAgIAkJdGhpcy55ID0geTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRTY2FsYXI6IGZ1bmN0aW9uICggc2NhbGFyICkgewoKICAgIAkJdGhpcy54ID0gc2NhbGFyOwogICAgCQl0aGlzLnkgPSBzY2FsYXI7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0WDogZnVuY3Rpb24gKCB4ICkgewoKICAgIAkJdGhpcy54ID0geDsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRZOiBmdW5jdGlvbiAoIHkgKSB7CgogICAgCQl0aGlzLnkgPSB5OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldENvbXBvbmVudDogZnVuY3Rpb24gKCBpbmRleCwgdmFsdWUgKSB7CgogICAgCQlzd2l0Y2ggKCBpbmRleCApIHsKCiAgICAJCQljYXNlIDA6IHRoaXMueCA9IHZhbHVlOyBicmVhazsKICAgIAkJCWNhc2UgMTogdGhpcy55ID0gdmFsdWU7IGJyZWFrOwogICAgCQkJZGVmYXVsdDogdGhyb3cgbmV3IEVycm9yKCAnaW5kZXggaXMgb3V0IG9mIHJhbmdlOiAnICsgaW5kZXggKTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlnZXRDb21wb25lbnQ6IGZ1bmN0aW9uICggaW5kZXggKSB7CgogICAgCQlzd2l0Y2ggKCBpbmRleCApIHsKCiAgICAJCQljYXNlIDA6IHJldHVybiB0aGlzLng7CiAgICAJCQljYXNlIDE6IHJldHVybiB0aGlzLnk7CiAgICAJCQlkZWZhdWx0OiB0aHJvdyBuZXcgRXJyb3IoICdpbmRleCBpcyBvdXQgb2YgcmFuZ2U6ICcgKyBpbmRleCApOwoKICAgIAkJfQoKICAgIAl9LAoKICAgIAljbG9uZTogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIG5ldyB0aGlzLmNvbnN0cnVjdG9yKCB0aGlzLngsIHRoaXMueSApOwoKICAgIAl9LAoKICAgIAljb3B5OiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQl0aGlzLnggPSB2Lng7CiAgICAJCXRoaXMueSA9IHYueTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhZGQ6IGZ1bmN0aW9uICggdiwgdyApIHsKCiAgICAJCWlmICggdyAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjI6IC5hZGQoKSBub3cgb25seSBhY2NlcHRzIG9uZSBhcmd1bWVudC4gVXNlIC5hZGRWZWN0b3JzKCBhLCBiICkgaW5zdGVhZC4nICk7CiAgICAJCQlyZXR1cm4gdGhpcy5hZGRWZWN0b3JzKCB2LCB3ICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggKz0gdi54OwogICAgCQl0aGlzLnkgKz0gdi55OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZFNjYWxhcjogZnVuY3Rpb24gKCBzICkgewoKICAgIAkJdGhpcy54ICs9IHM7CiAgICAJCXRoaXMueSArPSBzOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZFZlY3RvcnM6IGZ1bmN0aW9uICggYSwgYiApIHsKCiAgICAJCXRoaXMueCA9IGEueCArIGIueDsKICAgIAkJdGhpcy55ID0gYS55ICsgYi55OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZFNjYWxlZFZlY3RvcjogZnVuY3Rpb24gKCB2LCBzICkgewoKICAgIAkJdGhpcy54ICs9IHYueCAqIHM7CiAgICAJCXRoaXMueSArPSB2LnkgKiBzOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXN1YjogZnVuY3Rpb24gKCB2LCB3ICkgewoKICAgIAkJaWYgKCB3ICE9PSB1bmRlZmluZWQgKSB7CgogICAgCQkJY29uc29sZS53YXJuKCAnVEhSRUUuVmVjdG9yMjogLnN1YigpIG5vdyBvbmx5IGFjY2VwdHMgb25lIGFyZ3VtZW50LiBVc2UgLnN1YlZlY3RvcnMoIGEsIGIgKSBpbnN0ZWFkLicgKTsKICAgIAkJCXJldHVybiB0aGlzLnN1YlZlY3RvcnMoIHYsIHcgKTsKCiAgICAJCX0KCiAgICAJCXRoaXMueCAtPSB2Lng7CiAgICAJCXRoaXMueSAtPSB2Lnk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc3ViU2NhbGFyOiBmdW5jdGlvbiAoIHMgKSB7CgogICAgCQl0aGlzLnggLT0gczsKICAgIAkJdGhpcy55IC09IHM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc3ViVmVjdG9yczogZnVuY3Rpb24gKCBhLCBiICkgewoKICAgIAkJdGhpcy54ID0gYS54IC0gYi54OwogICAgCQl0aGlzLnkgPSBhLnkgLSBiLnk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbXVsdGlwbHk6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCAqPSB2Lng7CiAgICAJCXRoaXMueSAqPSB2Lnk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbXVsdGlwbHlTY2FsYXI6IGZ1bmN0aW9uICggc2NhbGFyICkgewoKICAgIAkJdGhpcy54ICo9IHNjYWxhcjsKICAgIAkJdGhpcy55ICo9IHNjYWxhcjsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkaXZpZGU6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCAvPSB2Lng7CiAgICAJCXRoaXMueSAvPSB2Lnk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZGl2aWRlU2NhbGFyOiBmdW5jdGlvbiAoIHNjYWxhciApIHsKCiAgICAJCXJldHVybiB0aGlzLm11bHRpcGx5U2NhbGFyKCAxIC8gc2NhbGFyICk7CgogICAgCX0sCgogICAgCWFwcGx5TWF0cml4MzogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJdmFyIHggPSB0aGlzLngsIHkgPSB0aGlzLnk7CiAgICAJCXZhciBlID0gbS5lbGVtZW50czsKCiAgICAJCXRoaXMueCA9IGVbIDAgXSAqIHggKyBlWyAzIF0gKiB5ICsgZVsgNiBdOwogICAgCQl0aGlzLnkgPSBlWyAxIF0gKiB4ICsgZVsgNCBdICogeSArIGVbIDcgXTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltaW46IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCA9IE1hdGgubWluKCB0aGlzLngsIHYueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1pbiggdGhpcy55LCB2LnkgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltYXg6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCA9IE1hdGgubWF4KCB0aGlzLngsIHYueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggdGhpcy55LCB2LnkgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAljbGFtcDogZnVuY3Rpb24gKCBtaW4sIG1heCApIHsKCiAgICAJCS8vIGFzc3VtZXMgbWluIDwgbWF4LCBjb21wb25lbnR3aXNlCgogICAgCQl0aGlzLnggPSBNYXRoLm1heCggbWluLngsIE1hdGgubWluKCBtYXgueCwgdGhpcy54ICkgKTsKICAgIAkJdGhpcy55ID0gTWF0aC5tYXgoIG1pbi55LCBNYXRoLm1pbiggbWF4LnksIHRoaXMueSApICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJY2xhbXBTY2FsYXI6IGZ1bmN0aW9uICggbWluVmFsLCBtYXhWYWwgKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLm1heCggbWluVmFsLCBNYXRoLm1pbiggbWF4VmFsLCB0aGlzLnggKSApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggbWluVmFsLCBNYXRoLm1pbiggbWF4VmFsLCB0aGlzLnkgKSApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsYW1wTGVuZ3RoOiBmdW5jdGlvbiAoIG1pbiwgbWF4ICkgewoKICAgIAkJdmFyIGxlbmd0aCA9IHRoaXMubGVuZ3RoKCk7CgogICAgCQlyZXR1cm4gdGhpcy5kaXZpZGVTY2FsYXIoIGxlbmd0aCB8fCAxICkubXVsdGlwbHlTY2FsYXIoIE1hdGgubWF4KCBtaW4sIE1hdGgubWluKCBtYXgsIGxlbmd0aCApICkgKTsKCiAgICAJfSwKCiAgICAJZmxvb3I6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMueCA9IE1hdGguZmxvb3IoIHRoaXMueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLmZsb29yKCB0aGlzLnkgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAljZWlsOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLmNlaWwoIHRoaXMueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLmNlaWwoIHRoaXMueSApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXJvdW5kOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLnJvdW5kKCB0aGlzLnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5yb3VuZCggdGhpcy55ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJcm91bmRUb1plcm86IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMueCA9ICggdGhpcy54IDwgMCApID8gTWF0aC5jZWlsKCB0aGlzLnggKSA6IE1hdGguZmxvb3IoIHRoaXMueCApOwogICAgCQl0aGlzLnkgPSAoIHRoaXMueSA8IDAgKSA/IE1hdGguY2VpbCggdGhpcy55ICkgOiBNYXRoLmZsb29yKCB0aGlzLnkgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAluZWdhdGU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMueCA9IC0gdGhpcy54OwogICAgCQl0aGlzLnkgPSAtIHRoaXMueTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkb3Q6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXJldHVybiB0aGlzLnggKiB2LnggKyB0aGlzLnkgKiB2Lnk7CgogICAgCX0sCgogICAgCWNyb3NzOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gdGhpcy54ICogdi55IC0gdGhpcy55ICogdi54OwoKICAgIAl9LAoKICAgIAlsZW5ndGhTcTogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIHRoaXMueCAqIHRoaXMueCArIHRoaXMueSAqIHRoaXMueTsKCiAgICAJfSwKCiAgICAJbGVuZ3RoOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gTWF0aC5zcXJ0KCB0aGlzLnggKiB0aGlzLnggKyB0aGlzLnkgKiB0aGlzLnkgKTsKCiAgICAJfSwKCiAgICAJbWFuaGF0dGFuTGVuZ3RoOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gTWF0aC5hYnMoIHRoaXMueCApICsgTWF0aC5hYnMoIHRoaXMueSApOwoKICAgIAl9LAoKICAgIAlub3JtYWxpemU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiB0aGlzLmRpdmlkZVNjYWxhciggdGhpcy5sZW5ndGgoKSB8fCAxICk7CgogICAgCX0sCgogICAgCWFuZ2xlOiBmdW5jdGlvbiAoKSB7CgogICAgCQkvLyBjb21wdXRlcyB0aGUgYW5nbGUgaW4gcmFkaWFucyB3aXRoIHJlc3BlY3QgdG8gdGhlIHBvc2l0aXZlIHgtYXhpcwoKICAgIAkJdmFyIGFuZ2xlID0gTWF0aC5hdGFuMiggdGhpcy55LCB0aGlzLnggKTsKCiAgICAJCWlmICggYW5nbGUgPCAwICkgYW5nbGUgKz0gMiAqIE1hdGguUEk7CgogICAgCQlyZXR1cm4gYW5nbGU7CgogICAgCX0sCgogICAgCWRpc3RhbmNlVG86IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXJldHVybiBNYXRoLnNxcnQoIHRoaXMuZGlzdGFuY2VUb1NxdWFyZWQoIHYgKSApOwoKICAgIAl9LAoKICAgIAlkaXN0YW5jZVRvU3F1YXJlZDogZnVuY3Rpb24gKCB2ICkgewoKICAgIAkJdmFyIGR4ID0gdGhpcy54IC0gdi54LCBkeSA9IHRoaXMueSAtIHYueTsKICAgIAkJcmV0dXJuIGR4ICogZHggKyBkeSAqIGR5OwoKICAgIAl9LAoKICAgIAltYW5oYXR0YW5EaXN0YW5jZVRvOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gTWF0aC5hYnMoIHRoaXMueCAtIHYueCApICsgTWF0aC5hYnMoIHRoaXMueSAtIHYueSApOwoKICAgIAl9LAoKICAgIAlzZXRMZW5ndGg6IGZ1bmN0aW9uICggbGVuZ3RoICkgewoKICAgIAkJcmV0dXJuIHRoaXMubm9ybWFsaXplKCkubXVsdGlwbHlTY2FsYXIoIGxlbmd0aCApOwoKICAgIAl9LAoKICAgIAlsZXJwOiBmdW5jdGlvbiAoIHYsIGFscGhhICkgewoKICAgIAkJdGhpcy54ICs9ICggdi54IC0gdGhpcy54ICkgKiBhbHBoYTsKICAgIAkJdGhpcy55ICs9ICggdi55IC0gdGhpcy55ICkgKiBhbHBoYTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlsZXJwVmVjdG9yczogZnVuY3Rpb24gKCB2MSwgdjIsIGFscGhhICkgewoKICAgIAkJcmV0dXJuIHRoaXMuc3ViVmVjdG9ycyggdjIsIHYxICkubXVsdGlwbHlTY2FsYXIoIGFscGhhICkuYWRkKCB2MSApOwoKICAgIAl9LAoKICAgIAllcXVhbHM6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXJldHVybiAoICggdi54ID09PSB0aGlzLnggKSAmJiAoIHYueSA9PT0gdGhpcy55ICkgKTsKCiAgICAJfSwKCiAgICAJZnJvbUFycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCXRoaXMueCA9IGFycmF5WyBvZmZzZXQgXTsKICAgIAkJdGhpcy55ID0gYXJyYXlbIG9mZnNldCArIDEgXTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAl0b0FycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIGFycmF5ID09PSB1bmRlZmluZWQgKSBhcnJheSA9IFtdOwogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCWFycmF5WyBvZmZzZXQgXSA9IHRoaXMueDsKICAgIAkJYXJyYXlbIG9mZnNldCArIDEgXSA9IHRoaXMueTsKCiAgICAJCXJldHVybiBhcnJheTsKCiAgICAJfSwKCiAgICAJZnJvbUJ1ZmZlckF0dHJpYnV0ZTogZnVuY3Rpb24gKCBhdHRyaWJ1dGUsIGluZGV4LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjI6IG9mZnNldCBoYXMgYmVlbiByZW1vdmVkIGZyb20gLmZyb21CdWZmZXJBdHRyaWJ1dGUoKS4nICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggPSBhdHRyaWJ1dGUuZ2V0WCggaW5kZXggKTsKICAgIAkJdGhpcy55ID0gYXR0cmlidXRlLmdldFkoIGluZGV4ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJcm90YXRlQXJvdW5kOiBmdW5jdGlvbiAoIGNlbnRlciwgYW5nbGUgKSB7CgogICAgCQl2YXIgYyA9IE1hdGguY29zKCBhbmdsZSApLCBzID0gTWF0aC5zaW4oIGFuZ2xlICk7CgogICAgCQl2YXIgeCA9IHRoaXMueCAtIGNlbnRlci54OwogICAgCQl2YXIgeSA9IHRoaXMueSAtIGNlbnRlci55OwoKICAgIAkJdGhpcy54ID0geCAqIGMgLSB5ICogcyArIGNlbnRlci54OwogICAgCQl0aGlzLnkgPSB4ICogcyArIHkgKiBjICsgY2VudGVyLnk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfQoKICAgIH0gKTsKCiAgICAvKioKICAgICAqIEBhdXRob3IgbWlrYWVsIGVtdGluZ2VyIC8gaHR0cDovL2dvbW8uc2UvCiAgICAgKiBAYXV0aG9yIGFsdGVyZWRxIC8gaHR0cDovL2FsdGVyZWRxdWFsaWEuY29tLwogICAgICogQGF1dGhvciBXZXN0TGFuZ2xleSAvIGh0dHA6Ly9naXRodWIuY29tL1dlc3RMYW5nbGV5CiAgICAgKiBAYXV0aG9yIGJob3VzdG9uIC8gaHR0cDovL2NsYXJhLmlvCiAgICAgKi8KCiAgICBmdW5jdGlvbiBRdWF0ZXJuaW9uKCB4LCB5LCB6LCB3ICkgewoKICAgIAl0aGlzLl94ID0geCB8fCAwOwogICAgCXRoaXMuX3kgPSB5IHx8IDA7CiAgICAJdGhpcy5feiA9IHogfHwgMDsKICAgIAl0aGlzLl93ID0gKCB3ICE9PSB1bmRlZmluZWQgKSA/IHcgOiAxOwoKICAgIH0KCiAgICBPYmplY3QuYXNzaWduKCBRdWF0ZXJuaW9uLCB7CgogICAgCXNsZXJwOiBmdW5jdGlvbiAoIHFhLCBxYiwgcW0sIHQgKSB7CgogICAgCQlyZXR1cm4gcW0uY29weSggcWEgKS5zbGVycCggcWIsIHQgKTsKCiAgICAJfSwKCiAgICAJc2xlcnBGbGF0OiBmdW5jdGlvbiAoIGRzdCwgZHN0T2Zmc2V0LCBzcmMwLCBzcmNPZmZzZXQwLCBzcmMxLCBzcmNPZmZzZXQxLCB0ICkgewoKICAgIAkJLy8gZnV6ei1mcmVlLCBhcnJheS1iYXNlZCBRdWF0ZXJuaW9uIFNMRVJQIG9wZXJhdGlvbgoKICAgIAkJdmFyIHgwID0gc3JjMFsgc3JjT2Zmc2V0MCArIDAgXSwKICAgIAkJCXkwID0gc3JjMFsgc3JjT2Zmc2V0MCArIDEgXSwKICAgIAkJCXowID0gc3JjMFsgc3JjT2Zmc2V0MCArIDIgXSwKICAgIAkJCXcwID0gc3JjMFsgc3JjT2Zmc2V0MCArIDMgXSwKCiAgICAJCQl4MSA9IHNyYzFbIHNyY09mZnNldDEgKyAwIF0sCiAgICAJCQl5MSA9IHNyYzFbIHNyY09mZnNldDEgKyAxIF0sCiAgICAJCQl6MSA9IHNyYzFbIHNyY09mZnNldDEgKyAyIF0sCiAgICAJCQl3MSA9IHNyYzFbIHNyY09mZnNldDEgKyAzIF07CgogICAgCQlpZiAoIHcwICE9PSB3MSB8fCB4MCAhPT0geDEgfHwgeTAgIT09IHkxIHx8IHowICE9PSB6MSApIHsKCiAgICAJCQl2YXIgcyA9IDEgLSB0LAoKICAgIAkJCQljb3MgPSB4MCAqIHgxICsgeTAgKiB5MSArIHowICogejEgKyB3MCAqIHcxLAoKICAgIAkJCQlkaXIgPSAoIGNvcyA+PSAwID8gMSA6IC0gMSApLAogICAgCQkJCXNxclNpbiA9IDEgLSBjb3MgKiBjb3M7CgogICAgCQkJLy8gU2tpcCB0aGUgU2xlcnAgZm9yIHRpbnkgc3RlcHMgdG8gYXZvaWQgbnVtZXJpYyBwcm9ibGVtczoKICAgIAkJCWlmICggc3FyU2luID4gTnVtYmVyLkVQU0lMT04gKSB7CgogICAgCQkJCXZhciBzaW4gPSBNYXRoLnNxcnQoIHNxclNpbiApLAogICAgCQkJCQlsZW4gPSBNYXRoLmF0YW4yKCBzaW4sIGNvcyAqIGRpciApOwoKICAgIAkJCQlzID0gTWF0aC5zaW4oIHMgKiBsZW4gKSAvIHNpbjsKICAgIAkJCQl0ID0gTWF0aC5zaW4oIHQgKiBsZW4gKSAvIHNpbjsKCiAgICAJCQl9CgogICAgCQkJdmFyIHREaXIgPSB0ICogZGlyOwoKICAgIAkJCXgwID0geDAgKiBzICsgeDEgKiB0RGlyOwogICAgCQkJeTAgPSB5MCAqIHMgKyB5MSAqIHREaXI7CiAgICAJCQl6MCA9IHowICogcyArIHoxICogdERpcjsKICAgIAkJCXcwID0gdzAgKiBzICsgdzEgKiB0RGlyOwoKICAgIAkJCS8vIE5vcm1hbGl6ZSBpbiBjYXNlIHdlIGp1c3QgZGlkIGEgbGVycDoKICAgIAkJCWlmICggcyA9PT0gMSAtIHQgKSB7CgogICAgCQkJCXZhciBmID0gMSAvIE1hdGguc3FydCggeDAgKiB4MCArIHkwICogeTAgKyB6MCAqIHowICsgdzAgKiB3MCApOwoKICAgIAkJCQl4MCAqPSBmOwogICAgCQkJCXkwICo9IGY7CiAgICAJCQkJejAgKj0gZjsKICAgIAkJCQl3MCAqPSBmOwoKICAgIAkJCX0KCiAgICAJCX0KCiAgICAJCWRzdFsgZHN0T2Zmc2V0IF0gPSB4MDsKICAgIAkJZHN0WyBkc3RPZmZzZXQgKyAxIF0gPSB5MDsKICAgIAkJZHN0WyBkc3RPZmZzZXQgKyAyIF0gPSB6MDsKICAgIAkJZHN0WyBkc3RPZmZzZXQgKyAzIF0gPSB3MDsKCiAgICAJfQoKICAgIH0gKTsKCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydGllcyggUXVhdGVybmlvbi5wcm90b3R5cGUsIHsKCiAgICAJeDogewoKICAgIAkJZ2V0OiBmdW5jdGlvbiAoKSB7CgogICAgCQkJcmV0dXJuIHRoaXMuX3g7CgogICAgCQl9LAoKICAgIAkJc2V0OiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJCXRoaXMuX3ggPSB2YWx1ZTsKICAgIAkJCXRoaXMuX29uQ2hhbmdlQ2FsbGJhY2soKTsKCiAgICAJCX0KCiAgICAJfSwKCiAgICAJeTogewoKICAgIAkJZ2V0OiBmdW5jdGlvbiAoKSB7CgogICAgCQkJcmV0dXJuIHRoaXMuX3k7CgogICAgCQl9LAoKICAgIAkJc2V0OiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJCXRoaXMuX3kgPSB2YWx1ZTsKICAgIAkJCXRoaXMuX29uQ2hhbmdlQ2FsbGJhY2soKTsKCiAgICAJCX0KCiAgICAJfSwKCiAgICAJejogewoKICAgIAkJZ2V0OiBmdW5jdGlvbiAoKSB7CgogICAgCQkJcmV0dXJuIHRoaXMuX3o7CgogICAgCQl9LAoKICAgIAkJc2V0OiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJCXRoaXMuX3ogPSB2YWx1ZTsKICAgIAkJCXRoaXMuX29uQ2hhbmdlQ2FsbGJhY2soKTsKCiAgICAJCX0KCiAgICAJfSwKCiAgICAJdzogewoKICAgIAkJZ2V0OiBmdW5jdGlvbiAoKSB7CgogICAgCQkJcmV0dXJuIHRoaXMuX3c7CgogICAgCQl9LAoKICAgIAkJc2V0OiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJCXRoaXMuX3cgPSB2YWx1ZTsKICAgIAkJCXRoaXMuX29uQ2hhbmdlQ2FsbGJhY2soKTsKCiAgICAJCX0KCiAgICAJfQoKICAgIH0gKTsKCiAgICBPYmplY3QuYXNzaWduKCBRdWF0ZXJuaW9uLnByb3RvdHlwZSwgewoKICAgIAlpc1F1YXRlcm5pb246IHRydWUsCgogICAgCXNldDogZnVuY3Rpb24gKCB4LCB5LCB6LCB3ICkgewoKICAgIAkJdGhpcy5feCA9IHg7CiAgICAJCXRoaXMuX3kgPSB5OwogICAgCQl0aGlzLl96ID0gejsKICAgIAkJdGhpcy5fdyA9IHc7CgogICAgCQl0aGlzLl9vbkNoYW5nZUNhbGxiYWNrKCk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJY2xvbmU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBuZXcgdGhpcy5jb25zdHJ1Y3RvciggdGhpcy5feCwgdGhpcy5feSwgdGhpcy5feiwgdGhpcy5fdyApOwoKICAgIAl9LAoKICAgIAljb3B5OiBmdW5jdGlvbiAoIHF1YXRlcm5pb24gKSB7CgogICAgCQl0aGlzLl94ID0gcXVhdGVybmlvbi54OwogICAgCQl0aGlzLl95ID0gcXVhdGVybmlvbi55OwogICAgCQl0aGlzLl96ID0gcXVhdGVybmlvbi56OwogICAgCQl0aGlzLl93ID0gcXVhdGVybmlvbi53OwoKICAgIAkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldEZyb21FdWxlcjogZnVuY3Rpb24gKCBldWxlciwgdXBkYXRlICkgewoKICAgIAkJaWYgKCAhICggZXVsZXIgJiYgZXVsZXIuaXNFdWxlciApICkgewoKICAgIAkJCXRocm93IG5ldyBFcnJvciggJ1RIUkVFLlF1YXRlcm5pb246IC5zZXRGcm9tRXVsZXIoKSBub3cgZXhwZWN0cyBhbiBFdWxlciByb3RhdGlvbiByYXRoZXIgdGhhbiBhIFZlY3RvcjMgYW5kIG9yZGVyLicgKTsKCiAgICAJCX0KCiAgICAJCXZhciB4ID0gZXVsZXIuX3gsIHkgPSBldWxlci5feSwgeiA9IGV1bGVyLl96LCBvcmRlciA9IGV1bGVyLm9yZGVyOwoKICAgIAkJLy8gaHR0cDovL3d3dy5tYXRod29ya3MuY29tL21hdGxhYmNlbnRyYWwvZmlsZWV4Y2hhbmdlLwogICAgCQkvLyAJMjA2OTYtZnVuY3Rpb24tdG8tY29udmVydC1iZXR3ZWVuLWRjbS1ldWxlci1hbmdsZXMtcXVhdGVybmlvbnMtYW5kLWV1bGVyLXZlY3RvcnMvCiAgICAJCS8vCWNvbnRlbnQvU3BpbkNhbGMubQoKICAgIAkJdmFyIGNvcyA9IE1hdGguY29zOwogICAgCQl2YXIgc2luID0gTWF0aC5zaW47CgogICAgCQl2YXIgYzEgPSBjb3MoIHggLyAyICk7CiAgICAJCXZhciBjMiA9IGNvcyggeSAvIDIgKTsKICAgIAkJdmFyIGMzID0gY29zKCB6IC8gMiApOwoKICAgIAkJdmFyIHMxID0gc2luKCB4IC8gMiApOwogICAgCQl2YXIgczIgPSBzaW4oIHkgLyAyICk7CiAgICAJCXZhciBzMyA9IHNpbiggeiAvIDIgKTsKCiAgICAJCWlmICggb3JkZXIgPT09ICdYWVonICkgewoKICAgIAkJCXRoaXMuX3ggPSBzMSAqIGMyICogYzMgKyBjMSAqIHMyICogczM7CiAgICAJCQl0aGlzLl95ID0gYzEgKiBzMiAqIGMzIC0gczEgKiBjMiAqIHMzOwogICAgCQkJdGhpcy5feiA9IGMxICogYzIgKiBzMyArIHMxICogczIgKiBjMzsKICAgIAkJCXRoaXMuX3cgPSBjMSAqIGMyICogYzMgLSBzMSAqIHMyICogczM7CgogICAgCQl9IGVsc2UgaWYgKCBvcmRlciA9PT0gJ1lYWicgKSB7CgogICAgCQkJdGhpcy5feCA9IHMxICogYzIgKiBjMyArIGMxICogczIgKiBzMzsKICAgIAkJCXRoaXMuX3kgPSBjMSAqIHMyICogYzMgLSBzMSAqIGMyICogczM7CiAgICAJCQl0aGlzLl96ID0gYzEgKiBjMiAqIHMzIC0gczEgKiBzMiAqIGMzOwogICAgCQkJdGhpcy5fdyA9IGMxICogYzIgKiBjMyArIHMxICogczIgKiBzMzsKCiAgICAJCX0gZWxzZSBpZiAoIG9yZGVyID09PSAnWlhZJyApIHsKCiAgICAJCQl0aGlzLl94ID0gczEgKiBjMiAqIGMzIC0gYzEgKiBzMiAqIHMzOwogICAgCQkJdGhpcy5feSA9IGMxICogczIgKiBjMyArIHMxICogYzIgKiBzMzsKICAgIAkJCXRoaXMuX3ogPSBjMSAqIGMyICogczMgKyBzMSAqIHMyICogYzM7CiAgICAJCQl0aGlzLl93ID0gYzEgKiBjMiAqIGMzIC0gczEgKiBzMiAqIHMzOwoKICAgIAkJfSBlbHNlIGlmICggb3JkZXIgPT09ICdaWVgnICkgewoKICAgIAkJCXRoaXMuX3ggPSBzMSAqIGMyICogYzMgLSBjMSAqIHMyICogczM7CiAgICAJCQl0aGlzLl95ID0gYzEgKiBzMiAqIGMzICsgczEgKiBjMiAqIHMzOwogICAgCQkJdGhpcy5feiA9IGMxICogYzIgKiBzMyAtIHMxICogczIgKiBjMzsKICAgIAkJCXRoaXMuX3cgPSBjMSAqIGMyICogYzMgKyBzMSAqIHMyICogczM7CgogICAgCQl9IGVsc2UgaWYgKCBvcmRlciA9PT0gJ1laWCcgKSB7CgogICAgCQkJdGhpcy5feCA9IHMxICogYzIgKiBjMyArIGMxICogczIgKiBzMzsKICAgIAkJCXRoaXMuX3kgPSBjMSAqIHMyICogYzMgKyBzMSAqIGMyICogczM7CiAgICAJCQl0aGlzLl96ID0gYzEgKiBjMiAqIHMzIC0gczEgKiBzMiAqIGMzOwogICAgCQkJdGhpcy5fdyA9IGMxICogYzIgKiBjMyAtIHMxICogczIgKiBzMzsKCiAgICAJCX0gZWxzZSBpZiAoIG9yZGVyID09PSAnWFpZJyApIHsKCiAgICAJCQl0aGlzLl94ID0gczEgKiBjMiAqIGMzIC0gYzEgKiBzMiAqIHMzOwogICAgCQkJdGhpcy5feSA9IGMxICogczIgKiBjMyAtIHMxICogYzIgKiBzMzsKICAgIAkJCXRoaXMuX3ogPSBjMSAqIGMyICogczMgKyBzMSAqIHMyICogYzM7CiAgICAJCQl0aGlzLl93ID0gYzEgKiBjMiAqIGMzICsgczEgKiBzMiAqIHMzOwoKICAgIAkJfQoKICAgIAkJaWYgKCB1cGRhdGUgIT09IGZhbHNlICkgdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldEZyb21BeGlzQW5nbGU6IGZ1bmN0aW9uICggYXhpcywgYW5nbGUgKSB7CgogICAgCQkvLyBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9nZW9tZXRyeS9yb3RhdGlvbnMvY29udmVyc2lvbnMvYW5nbGVUb1F1YXRlcm5pb24vaW5kZXguaHRtCgogICAgCQkvLyBhc3N1bWVzIGF4aXMgaXMgbm9ybWFsaXplZAoKICAgIAkJdmFyIGhhbGZBbmdsZSA9IGFuZ2xlIC8gMiwgcyA9IE1hdGguc2luKCBoYWxmQW5nbGUgKTsKCiAgICAJCXRoaXMuX3ggPSBheGlzLnggKiBzOwogICAgCQl0aGlzLl95ID0gYXhpcy55ICogczsKICAgIAkJdGhpcy5feiA9IGF4aXMueiAqIHM7CiAgICAJCXRoaXMuX3cgPSBNYXRoLmNvcyggaGFsZkFuZ2xlICk7CgogICAgCQl0aGlzLl9vbkNoYW5nZUNhbGxiYWNrKCk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0RnJvbVJvdGF0aW9uTWF0cml4OiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQkvLyBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9nZW9tZXRyeS9yb3RhdGlvbnMvY29udmVyc2lvbnMvbWF0cml4VG9RdWF0ZXJuaW9uL2luZGV4Lmh0bQoKICAgIAkJLy8gYXNzdW1lcyB0aGUgdXBwZXIgM3gzIG9mIG0gaXMgYSBwdXJlIHJvdGF0aW9uIG1hdHJpeCAoaS5lLCB1bnNjYWxlZCkKCiAgICAJCXZhciB0ZSA9IG0uZWxlbWVudHMsCgogICAgCQkJbTExID0gdGVbIDAgXSwgbTEyID0gdGVbIDQgXSwgbTEzID0gdGVbIDggXSwKICAgIAkJCW0yMSA9IHRlWyAxIF0sIG0yMiA9IHRlWyA1IF0sIG0yMyA9IHRlWyA5IF0sCiAgICAJCQltMzEgPSB0ZVsgMiBdLCBtMzIgPSB0ZVsgNiBdLCBtMzMgPSB0ZVsgMTAgXSwKCiAgICAJCQl0cmFjZSA9IG0xMSArIG0yMiArIG0zMywKICAgIAkJCXM7CgogICAgCQlpZiAoIHRyYWNlID4gMCApIHsKCiAgICAJCQlzID0gMC41IC8gTWF0aC5zcXJ0KCB0cmFjZSArIDEuMCApOwoKICAgIAkJCXRoaXMuX3cgPSAwLjI1IC8gczsKICAgIAkJCXRoaXMuX3ggPSAoIG0zMiAtIG0yMyApICogczsKICAgIAkJCXRoaXMuX3kgPSAoIG0xMyAtIG0zMSApICogczsKICAgIAkJCXRoaXMuX3ogPSAoIG0yMSAtIG0xMiApICogczsKCiAgICAJCX0gZWxzZSBpZiAoIG0xMSA+IG0yMiAmJiBtMTEgPiBtMzMgKSB7CgogICAgCQkJcyA9IDIuMCAqIE1hdGguc3FydCggMS4wICsgbTExIC0gbTIyIC0gbTMzICk7CgogICAgCQkJdGhpcy5fdyA9ICggbTMyIC0gbTIzICkgLyBzOwogICAgCQkJdGhpcy5feCA9IDAuMjUgKiBzOwogICAgCQkJdGhpcy5feSA9ICggbTEyICsgbTIxICkgLyBzOwogICAgCQkJdGhpcy5feiA9ICggbTEzICsgbTMxICkgLyBzOwoKICAgIAkJfSBlbHNlIGlmICggbTIyID4gbTMzICkgewoKICAgIAkJCXMgPSAyLjAgKiBNYXRoLnNxcnQoIDEuMCArIG0yMiAtIG0xMSAtIG0zMyApOwoKICAgIAkJCXRoaXMuX3cgPSAoIG0xMyAtIG0zMSApIC8gczsKICAgIAkJCXRoaXMuX3ggPSAoIG0xMiArIG0yMSApIC8gczsKICAgIAkJCXRoaXMuX3kgPSAwLjI1ICogczsKICAgIAkJCXRoaXMuX3ogPSAoIG0yMyArIG0zMiApIC8gczsKCiAgICAJCX0gZWxzZSB7CgogICAgCQkJcyA9IDIuMCAqIE1hdGguc3FydCggMS4wICsgbTMzIC0gbTExIC0gbTIyICk7CgogICAgCQkJdGhpcy5fdyA9ICggbTIxIC0gbTEyICkgLyBzOwogICAgCQkJdGhpcy5feCA9ICggbTEzICsgbTMxICkgLyBzOwogICAgCQkJdGhpcy5feSA9ICggbTIzICsgbTMyICkgLyBzOwogICAgCQkJdGhpcy5feiA9IDAuMjUgKiBzOwoKICAgIAkJfQoKICAgIAkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldEZyb21Vbml0VmVjdG9yczogZnVuY3Rpb24gKCB2RnJvbSwgdlRvICkgewoKICAgIAkJLy8gYXNzdW1lcyBkaXJlY3Rpb24gdmVjdG9ycyB2RnJvbSBhbmQgdlRvIGFyZSBub3JtYWxpemVkCgogICAgCQl2YXIgRVBTID0gMC4wMDAwMDE7CgogICAgCQl2YXIgciA9IHZGcm9tLmRvdCggdlRvICkgKyAxOwoKICAgIAkJaWYgKCByIDwgRVBTICkgewoKICAgIAkJCXIgPSAwOwoKICAgIAkJCWlmICggTWF0aC5hYnMoIHZGcm9tLnggKSA+IE1hdGguYWJzKCB2RnJvbS56ICkgKSB7CgogICAgCQkJCXRoaXMuX3ggPSAtIHZGcm9tLnk7CiAgICAJCQkJdGhpcy5feSA9IHZGcm9tLng7CiAgICAJCQkJdGhpcy5feiA9IDA7CiAgICAJCQkJdGhpcy5fdyA9IHI7CgogICAgCQkJfSBlbHNlIHsKCiAgICAJCQkJdGhpcy5feCA9IDA7CiAgICAJCQkJdGhpcy5feSA9IC0gdkZyb20uejsKICAgIAkJCQl0aGlzLl96ID0gdkZyb20ueTsKICAgIAkJCQl0aGlzLl93ID0gcjsKCiAgICAJCQl9CgogICAgCQl9IGVsc2UgewoKICAgIAkJCS8vIGNyb3NzVmVjdG9ycyggdkZyb20sIHZUbyApOyAvLyBpbmxpbmVkIHRvIGF2b2lkIGN5Y2xpYyBkZXBlbmRlbmN5IG9uIFZlY3RvcjMKCiAgICAJCQl0aGlzLl94ID0gdkZyb20ueSAqIHZUby56IC0gdkZyb20ueiAqIHZUby55OwogICAgCQkJdGhpcy5feSA9IHZGcm9tLnogKiB2VG8ueCAtIHZGcm9tLnggKiB2VG8uejsKICAgIAkJCXRoaXMuX3ogPSB2RnJvbS54ICogdlRvLnkgLSB2RnJvbS55ICogdlRvLng7CiAgICAJCQl0aGlzLl93ID0gcjsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0aGlzLm5vcm1hbGl6ZSgpOwoKICAgIAl9LAoKICAgIAlhbmdsZVRvOiBmdW5jdGlvbiAoIHEgKSB7CgogICAgCQlyZXR1cm4gMiAqIE1hdGguYWNvcyggTWF0aC5hYnMoIF9NYXRoLmNsYW1wKCB0aGlzLmRvdCggcSApLCAtIDEsIDEgKSApICk7CgogICAgCX0sCgogICAgCXJvdGF0ZVRvd2FyZHM6IGZ1bmN0aW9uICggcSwgc3RlcCApIHsKCiAgICAJCXZhciBhbmdsZSA9IHRoaXMuYW5nbGVUbyggcSApOwoKICAgIAkJaWYgKCBhbmdsZSA9PT0gMCApIHJldHVybiB0aGlzOwoKICAgIAkJdmFyIHQgPSBNYXRoLm1pbiggMSwgc3RlcCAvIGFuZ2xlICk7CgogICAgCQl0aGlzLnNsZXJwKCBxLCB0ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJaW52ZXJzZTogZnVuY3Rpb24gKCkgewoKICAgIAkJLy8gcXVhdGVybmlvbiBpcyBhc3N1bWVkIHRvIGhhdmUgdW5pdCBsZW5ndGgKCiAgICAJCXJldHVybiB0aGlzLmNvbmp1Z2F0ZSgpOwoKICAgIAl9LAoKICAgIAljb25qdWdhdGU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMuX3ggKj0gLSAxOwogICAgCQl0aGlzLl95ICo9IC0gMTsKICAgIAkJdGhpcy5feiAqPSAtIDE7CgogICAgCQl0aGlzLl9vbkNoYW5nZUNhbGxiYWNrKCk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZG90OiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gdGhpcy5feCAqIHYuX3ggKyB0aGlzLl95ICogdi5feSArIHRoaXMuX3ogKiB2Ll96ICsgdGhpcy5fdyAqIHYuX3c7CgogICAgCX0sCgogICAgCWxlbmd0aFNxOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gdGhpcy5feCAqIHRoaXMuX3ggKyB0aGlzLl95ICogdGhpcy5feSArIHRoaXMuX3ogKiB0aGlzLl96ICsgdGhpcy5fdyAqIHRoaXMuX3c7CgogICAgCX0sCgogICAgCWxlbmd0aDogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIE1hdGguc3FydCggdGhpcy5feCAqIHRoaXMuX3ggKyB0aGlzLl95ICogdGhpcy5feSArIHRoaXMuX3ogKiB0aGlzLl96ICsgdGhpcy5fdyAqIHRoaXMuX3cgKTsKCiAgICAJfSwKCiAgICAJbm9ybWFsaXplOiBmdW5jdGlvbiAoKSB7CgogICAgCQl2YXIgbCA9IHRoaXMubGVuZ3RoKCk7CgogICAgCQlpZiAoIGwgPT09IDAgKSB7CgogICAgCQkJdGhpcy5feCA9IDA7CiAgICAJCQl0aGlzLl95ID0gMDsKICAgIAkJCXRoaXMuX3ogPSAwOwogICAgCQkJdGhpcy5fdyA9IDE7CgogICAgCQl9IGVsc2UgewoKICAgIAkJCWwgPSAxIC8gbDsKCiAgICAJCQl0aGlzLl94ID0gdGhpcy5feCAqIGw7CiAgICAJCQl0aGlzLl95ID0gdGhpcy5feSAqIGw7CiAgICAJCQl0aGlzLl96ID0gdGhpcy5feiAqIGw7CiAgICAJCQl0aGlzLl93ID0gdGhpcy5fdyAqIGw7CgogICAgCQl9CgogICAgCQl0aGlzLl9vbkNoYW5nZUNhbGxiYWNrKCk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbXVsdGlwbHk6IGZ1bmN0aW9uICggcSwgcCApIHsKCiAgICAJCWlmICggcCAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlF1YXRlcm5pb246IC5tdWx0aXBseSgpIG5vdyBvbmx5IGFjY2VwdHMgb25lIGFyZ3VtZW50LiBVc2UgLm11bHRpcGx5UXVhdGVybmlvbnMoIGEsIGIgKSBpbnN0ZWFkLicgKTsKICAgIAkJCXJldHVybiB0aGlzLm11bHRpcGx5UXVhdGVybmlvbnMoIHEsIHAgKTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0aGlzLm11bHRpcGx5UXVhdGVybmlvbnMoIHRoaXMsIHEgKTsKCiAgICAJfSwKCiAgICAJcHJlbXVsdGlwbHk6IGZ1bmN0aW9uICggcSApIHsKCiAgICAJCXJldHVybiB0aGlzLm11bHRpcGx5UXVhdGVybmlvbnMoIHEsIHRoaXMgKTsKCiAgICAJfSwKCiAgICAJbXVsdGlwbHlRdWF0ZXJuaW9uczogZnVuY3Rpb24gKCBhLCBiICkgewoKICAgIAkJLy8gZnJvbSBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9hbGdlYnJhL3JlYWxOb3JtZWRBbGdlYnJhL3F1YXRlcm5pb25zL2NvZGUvaW5kZXguaHRtCgogICAgCQl2YXIgcWF4ID0gYS5feCwgcWF5ID0gYS5feSwgcWF6ID0gYS5feiwgcWF3ID0gYS5fdzsKICAgIAkJdmFyIHFieCA9IGIuX3gsIHFieSA9IGIuX3ksIHFieiA9IGIuX3osIHFidyA9IGIuX3c7CgogICAgCQl0aGlzLl94ID0gcWF4ICogcWJ3ICsgcWF3ICogcWJ4ICsgcWF5ICogcWJ6IC0gcWF6ICogcWJ5OwogICAgCQl0aGlzLl95ID0gcWF5ICogcWJ3ICsgcWF3ICogcWJ5ICsgcWF6ICogcWJ4IC0gcWF4ICogcWJ6OwogICAgCQl0aGlzLl96ID0gcWF6ICogcWJ3ICsgcWF3ICogcWJ6ICsgcWF4ICogcWJ5IC0gcWF5ICogcWJ4OwogICAgCQl0aGlzLl93ID0gcWF3ICogcWJ3IC0gcWF4ICogcWJ4IC0gcWF5ICogcWJ5IC0gcWF6ICogcWJ6OwoKICAgIAkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNsZXJwOiBmdW5jdGlvbiAoIHFiLCB0ICkgewoKICAgIAkJaWYgKCB0ID09PSAwICkgcmV0dXJuIHRoaXM7CiAgICAJCWlmICggdCA9PT0gMSApIHJldHVybiB0aGlzLmNvcHkoIHFiICk7CgogICAgCQl2YXIgeCA9IHRoaXMuX3gsIHkgPSB0aGlzLl95LCB6ID0gdGhpcy5feiwgdyA9IHRoaXMuX3c7CgogICAgCQkvLyBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9hbGdlYnJhL3JlYWxOb3JtZWRBbGdlYnJhL3F1YXRlcm5pb25zL3NsZXJwLwoKICAgIAkJdmFyIGNvc0hhbGZUaGV0YSA9IHcgKiBxYi5fdyArIHggKiBxYi5feCArIHkgKiBxYi5feSArIHogKiBxYi5fejsKCiAgICAJCWlmICggY29zSGFsZlRoZXRhIDwgMCApIHsKCiAgICAJCQl0aGlzLl93ID0gLSBxYi5fdzsKICAgIAkJCXRoaXMuX3ggPSAtIHFiLl94OwogICAgCQkJdGhpcy5feSA9IC0gcWIuX3k7CiAgICAJCQl0aGlzLl96ID0gLSBxYi5fejsKCiAgICAJCQljb3NIYWxmVGhldGEgPSAtIGNvc0hhbGZUaGV0YTsKCiAgICAJCX0gZWxzZSB7CgogICAgCQkJdGhpcy5jb3B5KCBxYiApOwoKICAgIAkJfQoKICAgIAkJaWYgKCBjb3NIYWxmVGhldGEgPj0gMS4wICkgewoKICAgIAkJCXRoaXMuX3cgPSB3OwogICAgCQkJdGhpcy5feCA9IHg7CiAgICAJCQl0aGlzLl95ID0geTsKICAgIAkJCXRoaXMuX3ogPSB6OwoKICAgIAkJCXJldHVybiB0aGlzOwoKICAgIAkJfQoKICAgIAkJdmFyIHNxclNpbkhhbGZUaGV0YSA9IDEuMCAtIGNvc0hhbGZUaGV0YSAqIGNvc0hhbGZUaGV0YTsKCiAgICAJCWlmICggc3FyU2luSGFsZlRoZXRhIDw9IE51bWJlci5FUFNJTE9OICkgewoKICAgIAkJCXZhciBzID0gMSAtIHQ7CiAgICAJCQl0aGlzLl93ID0gcyAqIHcgKyB0ICogdGhpcy5fdzsKICAgIAkJCXRoaXMuX3ggPSBzICogeCArIHQgKiB0aGlzLl94OwogICAgCQkJdGhpcy5feSA9IHMgKiB5ICsgdCAqIHRoaXMuX3k7CiAgICAJCQl0aGlzLl96ID0gcyAqIHogKyB0ICogdGhpcy5fejsKCiAgICAJCQl0aGlzLm5vcm1hbGl6ZSgpOwogICAgCQkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJCXJldHVybiB0aGlzOwoKICAgIAkJfQoKICAgIAkJdmFyIHNpbkhhbGZUaGV0YSA9IE1hdGguc3FydCggc3FyU2luSGFsZlRoZXRhICk7CiAgICAJCXZhciBoYWxmVGhldGEgPSBNYXRoLmF0YW4yKCBzaW5IYWxmVGhldGEsIGNvc0hhbGZUaGV0YSApOwogICAgCQl2YXIgcmF0aW9BID0gTWF0aC5zaW4oICggMSAtIHQgKSAqIGhhbGZUaGV0YSApIC8gc2luSGFsZlRoZXRhLAogICAgCQkJcmF0aW9CID0gTWF0aC5zaW4oIHQgKiBoYWxmVGhldGEgKSAvIHNpbkhhbGZUaGV0YTsKCiAgICAJCXRoaXMuX3cgPSAoIHcgKiByYXRpb0EgKyB0aGlzLl93ICogcmF0aW9CICk7CiAgICAJCXRoaXMuX3ggPSAoIHggKiByYXRpb0EgKyB0aGlzLl94ICogcmF0aW9CICk7CiAgICAJCXRoaXMuX3kgPSAoIHkgKiByYXRpb0EgKyB0aGlzLl95ICogcmF0aW9CICk7CiAgICAJCXRoaXMuX3ogPSAoIHogKiByYXRpb0EgKyB0aGlzLl96ICogcmF0aW9CICk7CgogICAgCQl0aGlzLl9vbkNoYW5nZUNhbGxiYWNrKCk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZXF1YWxzOiBmdW5jdGlvbiAoIHF1YXRlcm5pb24gKSB7CgogICAgCQlyZXR1cm4gKCBxdWF0ZXJuaW9uLl94ID09PSB0aGlzLl94ICkgJiYgKCBxdWF0ZXJuaW9uLl95ID09PSB0aGlzLl95ICkgJiYgKCBxdWF0ZXJuaW9uLl96ID09PSB0aGlzLl96ICkgJiYgKCBxdWF0ZXJuaW9uLl93ID09PSB0aGlzLl93ICk7CgogICAgCX0sCgogICAgCWZyb21BcnJheTogZnVuY3Rpb24gKCBhcnJheSwgb2Zmc2V0ICkgewoKICAgIAkJaWYgKCBvZmZzZXQgPT09IHVuZGVmaW5lZCApIG9mZnNldCA9IDA7CgogICAgCQl0aGlzLl94ID0gYXJyYXlbIG9mZnNldCBdOwogICAgCQl0aGlzLl95ID0gYXJyYXlbIG9mZnNldCArIDEgXTsKICAgIAkJdGhpcy5feiA9IGFycmF5WyBvZmZzZXQgKyAyIF07CiAgICAJCXRoaXMuX3cgPSBhcnJheVsgb2Zmc2V0ICsgMyBdOwoKICAgIAkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjaygpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXRvQXJyYXk6IGZ1bmN0aW9uICggYXJyYXksIG9mZnNldCApIHsKCiAgICAJCWlmICggYXJyYXkgPT09IHVuZGVmaW5lZCApIGFycmF5ID0gW107CiAgICAJCWlmICggb2Zmc2V0ID09PSB1bmRlZmluZWQgKSBvZmZzZXQgPSAwOwoKICAgIAkJYXJyYXlbIG9mZnNldCBdID0gdGhpcy5feDsKICAgIAkJYXJyYXlbIG9mZnNldCArIDEgXSA9IHRoaXMuX3k7CiAgICAJCWFycmF5WyBvZmZzZXQgKyAyIF0gPSB0aGlzLl96OwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMyBdID0gdGhpcy5fdzsKCiAgICAJCXJldHVybiBhcnJheTsKCiAgICAJfSwKCiAgICAJX29uQ2hhbmdlOiBmdW5jdGlvbiAoIGNhbGxiYWNrICkgewoKICAgIAkJdGhpcy5fb25DaGFuZ2VDYWxsYmFjayA9IGNhbGxiYWNrOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCV9vbkNoYW5nZUNhbGxiYWNrOiBmdW5jdGlvbiAoKSB7fQoKICAgIH0gKTsKCiAgICAvKioKICAgICAqIEBhdXRob3IgbXJkb29iIC8gaHR0cDovL21yZG9vYi5jb20vCiAgICAgKiBAYXV0aG9yIGtpbGUgLyBodHRwOi8va2lsZS5zdHJhdmFnYW56YS5vcmcvCiAgICAgKiBAYXV0aG9yIHBoaWxvZ2IgLyBodHRwOi8vYmxvZy50aGVqaXQub3JnLwogICAgICogQGF1dGhvciBtaWthZWwgZW10aW5nZXIgLyBodHRwOi8vZ29tby5zZS8KICAgICAqIEBhdXRob3IgZWdyYWV0aGVyIC8gaHR0cDovL2VncmFldGhlci5jb20vCiAgICAgKiBAYXV0aG9yIFdlc3RMYW5nbGV5IC8gaHR0cDovL2dpdGh1Yi5jb20vV2VzdExhbmdsZXkKICAgICAqLwoKICAgIHZhciBfdmVjdG9yID0gbmV3IFZlY3RvcjMoKTsKICAgIHZhciBfcXVhdGVybmlvbiA9IG5ldyBRdWF0ZXJuaW9uKCk7CgogICAgZnVuY3Rpb24gVmVjdG9yMyggeCwgeSwgeiApIHsKCiAgICAJdGhpcy54ID0geCB8fCAwOwogICAgCXRoaXMueSA9IHkgfHwgMDsKICAgIAl0aGlzLnogPSB6IHx8IDA7CgogICAgfQoKICAgIE9iamVjdC5hc3NpZ24oIFZlY3RvcjMucHJvdG90eXBlLCB7CgogICAgCWlzVmVjdG9yMzogdHJ1ZSwKCiAgICAJc2V0OiBmdW5jdGlvbiAoIHgsIHksIHogKSB7CgogICAgCQl0aGlzLnggPSB4OwogICAgCQl0aGlzLnkgPSB5OwogICAgCQl0aGlzLnogPSB6OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldFNjYWxhcjogZnVuY3Rpb24gKCBzY2FsYXIgKSB7CgogICAgCQl0aGlzLnggPSBzY2FsYXI7CiAgICAJCXRoaXMueSA9IHNjYWxhcjsKICAgIAkJdGhpcy56ID0gc2NhbGFyOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldFg6IGZ1bmN0aW9uICggeCApIHsKCiAgICAJCXRoaXMueCA9IHg7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0WTogZnVuY3Rpb24gKCB5ICkgewoKICAgIAkJdGhpcy55ID0geTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRaOiBmdW5jdGlvbiAoIHogKSB7CgogICAgCQl0aGlzLnogPSB6OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldENvbXBvbmVudDogZnVuY3Rpb24gKCBpbmRleCwgdmFsdWUgKSB7CgogICAgCQlzd2l0Y2ggKCBpbmRleCApIHsKCiAgICAJCQljYXNlIDA6IHRoaXMueCA9IHZhbHVlOyBicmVhazsKICAgIAkJCWNhc2UgMTogdGhpcy55ID0gdmFsdWU7IGJyZWFrOwogICAgCQkJY2FzZSAyOiB0aGlzLnogPSB2YWx1ZTsgYnJlYWs7CiAgICAJCQlkZWZhdWx0OiB0aHJvdyBuZXcgRXJyb3IoICdpbmRleCBpcyBvdXQgb2YgcmFuZ2U6ICcgKyBpbmRleCApOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWdldENvbXBvbmVudDogZnVuY3Rpb24gKCBpbmRleCApIHsKCiAgICAJCXN3aXRjaCAoIGluZGV4ICkgewoKICAgIAkJCWNhc2UgMDogcmV0dXJuIHRoaXMueDsKICAgIAkJCWNhc2UgMTogcmV0dXJuIHRoaXMueTsKICAgIAkJCWNhc2UgMjogcmV0dXJuIHRoaXMuejsKICAgIAkJCWRlZmF1bHQ6IHRocm93IG5ldyBFcnJvciggJ2luZGV4IGlzIG91dCBvZiByYW5nZTogJyArIGluZGV4ICk7CgogICAgCQl9CgogICAgCX0sCgogICAgCWNsb25lOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gbmV3IHRoaXMuY29uc3RydWN0b3IoIHRoaXMueCwgdGhpcy55LCB0aGlzLnogKTsKCiAgICAJfSwKCiAgICAJY29weTogZnVuY3Rpb24gKCB2ICkgewoKICAgIAkJdGhpcy54ID0gdi54OwogICAgCQl0aGlzLnkgPSB2Lnk7CiAgICAJCXRoaXMueiA9IHYuejsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhZGQ6IGZ1bmN0aW9uICggdiwgdyApIHsKCiAgICAJCWlmICggdyAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjM6IC5hZGQoKSBub3cgb25seSBhY2NlcHRzIG9uZSBhcmd1bWVudC4gVXNlIC5hZGRWZWN0b3JzKCBhLCBiICkgaW5zdGVhZC4nICk7CiAgICAJCQlyZXR1cm4gdGhpcy5hZGRWZWN0b3JzKCB2LCB3ICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggKz0gdi54OwogICAgCQl0aGlzLnkgKz0gdi55OwogICAgCQl0aGlzLnogKz0gdi56OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZFNjYWxhcjogZnVuY3Rpb24gKCBzICkgewoKICAgIAkJdGhpcy54ICs9IHM7CiAgICAJCXRoaXMueSArPSBzOwogICAgCQl0aGlzLnogKz0gczsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhZGRWZWN0b3JzOiBmdW5jdGlvbiAoIGEsIGIgKSB7CgogICAgCQl0aGlzLnggPSBhLnggKyBiLng7CiAgICAJCXRoaXMueSA9IGEueSArIGIueTsKICAgIAkJdGhpcy56ID0gYS56ICsgYi56OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZFNjYWxlZFZlY3RvcjogZnVuY3Rpb24gKCB2LCBzICkgewoKICAgIAkJdGhpcy54ICs9IHYueCAqIHM7CiAgICAJCXRoaXMueSArPSB2LnkgKiBzOwogICAgCQl0aGlzLnogKz0gdi56ICogczsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzdWI6IGZ1bmN0aW9uICggdiwgdyApIHsKCiAgICAJCWlmICggdyAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjM6IC5zdWIoKSBub3cgb25seSBhY2NlcHRzIG9uZSBhcmd1bWVudC4gVXNlIC5zdWJWZWN0b3JzKCBhLCBiICkgaW5zdGVhZC4nICk7CiAgICAJCQlyZXR1cm4gdGhpcy5zdWJWZWN0b3JzKCB2LCB3ICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggLT0gdi54OwogICAgCQl0aGlzLnkgLT0gdi55OwogICAgCQl0aGlzLnogLT0gdi56OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXN1YlNjYWxhcjogZnVuY3Rpb24gKCBzICkgewoKICAgIAkJdGhpcy54IC09IHM7CiAgICAJCXRoaXMueSAtPSBzOwogICAgCQl0aGlzLnogLT0gczsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzdWJWZWN0b3JzOiBmdW5jdGlvbiAoIGEsIGIgKSB7CgogICAgCQl0aGlzLnggPSBhLnggLSBiLng7CiAgICAJCXRoaXMueSA9IGEueSAtIGIueTsKICAgIAkJdGhpcy56ID0gYS56IC0gYi56OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCW11bHRpcGx5OiBmdW5jdGlvbiAoIHYsIHcgKSB7CgogICAgCQlpZiAoIHcgIT09IHVuZGVmaW5lZCApIHsKCiAgICAJCQljb25zb2xlLndhcm4oICdUSFJFRS5WZWN0b3IzOiAubXVsdGlwbHkoKSBub3cgb25seSBhY2NlcHRzIG9uZSBhcmd1bWVudC4gVXNlIC5tdWx0aXBseVZlY3RvcnMoIGEsIGIgKSBpbnN0ZWFkLicgKTsKICAgIAkJCXJldHVybiB0aGlzLm11bHRpcGx5VmVjdG9ycyggdiwgdyApOwoKICAgIAkJfQoKICAgIAkJdGhpcy54ICo9IHYueDsKICAgIAkJdGhpcy55ICo9IHYueTsKICAgIAkJdGhpcy56ICo9IHYuejsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltdWx0aXBseVNjYWxhcjogZnVuY3Rpb24gKCBzY2FsYXIgKSB7CgogICAgCQl0aGlzLnggKj0gc2NhbGFyOwogICAgCQl0aGlzLnkgKj0gc2NhbGFyOwogICAgCQl0aGlzLnogKj0gc2NhbGFyOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCW11bHRpcGx5VmVjdG9yczogZnVuY3Rpb24gKCBhLCBiICkgewoKICAgIAkJdGhpcy54ID0gYS54ICogYi54OwogICAgCQl0aGlzLnkgPSBhLnkgKiBiLnk7CiAgICAJCXRoaXMueiA9IGEueiAqIGIuejsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhcHBseUV1bGVyOiBmdW5jdGlvbiAoIGV1bGVyICkgewoKICAgIAkJaWYgKCAhICggZXVsZXIgJiYgZXVsZXIuaXNFdWxlciApICkgewoKICAgIAkJCWNvbnNvbGUuZXJyb3IoICdUSFJFRS5WZWN0b3IzOiAuYXBwbHlFdWxlcigpIG5vdyBleHBlY3RzIGFuIEV1bGVyIHJvdGF0aW9uIHJhdGhlciB0aGFuIGEgVmVjdG9yMyBhbmQgb3JkZXIuJyApOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIHRoaXMuYXBwbHlRdWF0ZXJuaW9uKCBfcXVhdGVybmlvbi5zZXRGcm9tRXVsZXIoIGV1bGVyICkgKTsKCiAgICAJfSwKCiAgICAJYXBwbHlBeGlzQW5nbGU6IGZ1bmN0aW9uICggYXhpcywgYW5nbGUgKSB7CgogICAgCQlyZXR1cm4gdGhpcy5hcHBseVF1YXRlcm5pb24oIF9xdWF0ZXJuaW9uLnNldEZyb21BeGlzQW5nbGUoIGF4aXMsIGFuZ2xlICkgKTsKCiAgICAJfSwKCiAgICAJYXBwbHlNYXRyaXgzOiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQl2YXIgeCA9IHRoaXMueCwgeSA9IHRoaXMueSwgeiA9IHRoaXMuejsKICAgIAkJdmFyIGUgPSBtLmVsZW1lbnRzOwoKICAgIAkJdGhpcy54ID0gZVsgMCBdICogeCArIGVbIDMgXSAqIHkgKyBlWyA2IF0gKiB6OwogICAgCQl0aGlzLnkgPSBlWyAxIF0gKiB4ICsgZVsgNCBdICogeSArIGVbIDcgXSAqIHo7CiAgICAJCXRoaXMueiA9IGVbIDIgXSAqIHggKyBlWyA1IF0gKiB5ICsgZVsgOCBdICogejsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhcHBseU1hdHJpeDQ6IGZ1bmN0aW9uICggbSApIHsKCiAgICAJCXZhciB4ID0gdGhpcy54LCB5ID0gdGhpcy55LCB6ID0gdGhpcy56OwogICAgCQl2YXIgZSA9IG0uZWxlbWVudHM7CgogICAgCQl2YXIgdyA9IDEgLyAoIGVbIDMgXSAqIHggKyBlWyA3IF0gKiB5ICsgZVsgMTEgXSAqIHogKyBlWyAxNSBdICk7CgogICAgCQl0aGlzLnggPSAoIGVbIDAgXSAqIHggKyBlWyA0IF0gKiB5ICsgZVsgOCBdICogeiArIGVbIDEyIF0gKSAqIHc7CiAgICAJCXRoaXMueSA9ICggZVsgMSBdICogeCArIGVbIDUgXSAqIHkgKyBlWyA5IF0gKiB6ICsgZVsgMTMgXSApICogdzsKICAgIAkJdGhpcy56ID0gKCBlWyAyIF0gKiB4ICsgZVsgNiBdICogeSArIGVbIDEwIF0gKiB6ICsgZVsgMTQgXSApICogdzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhcHBseVF1YXRlcm5pb246IGZ1bmN0aW9uICggcSApIHsKCiAgICAJCXZhciB4ID0gdGhpcy54LCB5ID0gdGhpcy55LCB6ID0gdGhpcy56OwogICAgCQl2YXIgcXggPSBxLngsIHF5ID0gcS55LCBxeiA9IHEueiwgcXcgPSBxLnc7CgogICAgCQkvLyBjYWxjdWxhdGUgcXVhdCAqIHZlY3RvcgoKICAgIAkJdmFyIGl4ID0gcXcgKiB4ICsgcXkgKiB6IC0gcXogKiB5OwogICAgCQl2YXIgaXkgPSBxdyAqIHkgKyBxeiAqIHggLSBxeCAqIHo7CiAgICAJCXZhciBpeiA9IHF3ICogeiArIHF4ICogeSAtIHF5ICogeDsKICAgIAkJdmFyIGl3ID0gLSBxeCAqIHggLSBxeSAqIHkgLSBxeiAqIHo7CgogICAgCQkvLyBjYWxjdWxhdGUgcmVzdWx0ICogaW52ZXJzZSBxdWF0CgogICAgCQl0aGlzLnggPSBpeCAqIHF3ICsgaXcgKiAtIHF4ICsgaXkgKiAtIHF6IC0gaXogKiAtIHF5OwogICAgCQl0aGlzLnkgPSBpeSAqIHF3ICsgaXcgKiAtIHF5ICsgaXogKiAtIHF4IC0gaXggKiAtIHF6OwogICAgCQl0aGlzLnogPSBpeiAqIHF3ICsgaXcgKiAtIHF6ICsgaXggKiAtIHF5IC0gaXkgKiAtIHF4OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXByb2plY3Q6IGZ1bmN0aW9uICggY2FtZXJhICkgewoKICAgIAkJcmV0dXJuIHRoaXMuYXBwbHlNYXRyaXg0KCBjYW1lcmEubWF0cml4V29ybGRJbnZlcnNlICkuYXBwbHlNYXRyaXg0KCBjYW1lcmEucHJvamVjdGlvbk1hdHJpeCApOwoKICAgIAl9LAoKICAgIAl1bnByb2plY3Q6IGZ1bmN0aW9uICggY2FtZXJhICkgewoKICAgIAkJcmV0dXJuIHRoaXMuYXBwbHlNYXRyaXg0KCBjYW1lcmEucHJvamVjdGlvbk1hdHJpeEludmVyc2UgKS5hcHBseU1hdHJpeDQoIGNhbWVyYS5tYXRyaXhXb3JsZCApOwoKICAgIAl9LAoKICAgIAl0cmFuc2Zvcm1EaXJlY3Rpb246IGZ1bmN0aW9uICggbSApIHsKCiAgICAJCS8vIGlucHV0OiBUSFJFRS5NYXRyaXg0IGFmZmluZSBtYXRyaXgKICAgIAkJLy8gdmVjdG9yIGludGVycHJldGVkIGFzIGEgZGlyZWN0aW9uCgogICAgCQl2YXIgeCA9IHRoaXMueCwgeSA9IHRoaXMueSwgeiA9IHRoaXMuejsKICAgIAkJdmFyIGUgPSBtLmVsZW1lbnRzOwoKICAgIAkJdGhpcy54ID0gZVsgMCBdICogeCArIGVbIDQgXSAqIHkgKyBlWyA4IF0gKiB6OwogICAgCQl0aGlzLnkgPSBlWyAxIF0gKiB4ICsgZVsgNSBdICogeSArIGVbIDkgXSAqIHo7CiAgICAJCXRoaXMueiA9IGVbIDIgXSAqIHggKyBlWyA2IF0gKiB5ICsgZVsgMTAgXSAqIHo7CgogICAgCQlyZXR1cm4gdGhpcy5ub3JtYWxpemUoKTsKCiAgICAJfSwKCiAgICAJZGl2aWRlOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQl0aGlzLnggLz0gdi54OwogICAgCQl0aGlzLnkgLz0gdi55OwogICAgCQl0aGlzLnogLz0gdi56OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWRpdmlkZVNjYWxhcjogZnVuY3Rpb24gKCBzY2FsYXIgKSB7CgogICAgCQlyZXR1cm4gdGhpcy5tdWx0aXBseVNjYWxhciggMSAvIHNjYWxhciApOwoKICAgIAl9LAoKICAgIAltaW46IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCA9IE1hdGgubWluKCB0aGlzLngsIHYueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1pbiggdGhpcy55LCB2LnkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5taW4oIHRoaXMueiwgdi56ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWF4OiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLm1heCggdGhpcy54LCB2LnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5tYXgoIHRoaXMueSwgdi55ICk7CiAgICAJCXRoaXMueiA9IE1hdGgubWF4KCB0aGlzLnosIHYueiApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsYW1wOiBmdW5jdGlvbiAoIG1pbiwgbWF4ICkgewoKICAgIAkJLy8gYXNzdW1lcyBtaW4gPCBtYXgsIGNvbXBvbmVudHdpc2UKCiAgICAJCXRoaXMueCA9IE1hdGgubWF4KCBtaW4ueCwgTWF0aC5taW4oIG1heC54LCB0aGlzLnggKSApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggbWluLnksIE1hdGgubWluKCBtYXgueSwgdGhpcy55ICkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5tYXgoIG1pbi56LCBNYXRoLm1pbiggbWF4LnosIHRoaXMueiApICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJY2xhbXBTY2FsYXI6IGZ1bmN0aW9uICggbWluVmFsLCBtYXhWYWwgKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLm1heCggbWluVmFsLCBNYXRoLm1pbiggbWF4VmFsLCB0aGlzLnggKSApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggbWluVmFsLCBNYXRoLm1pbiggbWF4VmFsLCB0aGlzLnkgKSApOwogICAgCQl0aGlzLnogPSBNYXRoLm1heCggbWluVmFsLCBNYXRoLm1pbiggbWF4VmFsLCB0aGlzLnogKSApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsYW1wTGVuZ3RoOiBmdW5jdGlvbiAoIG1pbiwgbWF4ICkgewoKICAgIAkJdmFyIGxlbmd0aCA9IHRoaXMubGVuZ3RoKCk7CgogICAgCQlyZXR1cm4gdGhpcy5kaXZpZGVTY2FsYXIoIGxlbmd0aCB8fCAxICkubXVsdGlwbHlTY2FsYXIoIE1hdGgubWF4KCBtaW4sIE1hdGgubWluKCBtYXgsIGxlbmd0aCApICkgKTsKCiAgICAJfSwKCiAgICAJZmxvb3I6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMueCA9IE1hdGguZmxvb3IoIHRoaXMueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLmZsb29yKCB0aGlzLnkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5mbG9vciggdGhpcy56ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJY2VpbDogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy54ID0gTWF0aC5jZWlsKCB0aGlzLnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5jZWlsKCB0aGlzLnkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5jZWlsKCB0aGlzLnogKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlyb3VuZDogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy54ID0gTWF0aC5yb3VuZCggdGhpcy54ICk7CiAgICAJCXRoaXMueSA9IE1hdGgucm91bmQoIHRoaXMueSApOwogICAgCQl0aGlzLnogPSBNYXRoLnJvdW5kKCB0aGlzLnogKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlyb3VuZFRvWmVybzogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy54ID0gKCB0aGlzLnggPCAwICkgPyBNYXRoLmNlaWwoIHRoaXMueCApIDogTWF0aC5mbG9vciggdGhpcy54ICk7CiAgICAJCXRoaXMueSA9ICggdGhpcy55IDwgMCApID8gTWF0aC5jZWlsKCB0aGlzLnkgKSA6IE1hdGguZmxvb3IoIHRoaXMueSApOwogICAgCQl0aGlzLnogPSAoIHRoaXMueiA8IDAgKSA/IE1hdGguY2VpbCggdGhpcy56ICkgOiBNYXRoLmZsb29yKCB0aGlzLnogKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAluZWdhdGU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXRoaXMueCA9IC0gdGhpcy54OwogICAgCQl0aGlzLnkgPSAtIHRoaXMueTsKICAgIAkJdGhpcy56ID0gLSB0aGlzLno7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZG90OiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gdGhpcy54ICogdi54ICsgdGhpcy55ICogdi55ICsgdGhpcy56ICogdi56OwoKICAgIAl9LAoKICAgIAkvLyBUT0RPIGxlbmd0aFNxdWFyZWQ/CgogICAgCWxlbmd0aFNxOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gdGhpcy54ICogdGhpcy54ICsgdGhpcy55ICogdGhpcy55ICsgdGhpcy56ICogdGhpcy56OwoKICAgIAl9LAoKICAgIAlsZW5ndGg6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBNYXRoLnNxcnQoIHRoaXMueCAqIHRoaXMueCArIHRoaXMueSAqIHRoaXMueSArIHRoaXMueiAqIHRoaXMueiApOwoKICAgIAl9LAoKICAgIAltYW5oYXR0YW5MZW5ndGg6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBNYXRoLmFicyggdGhpcy54ICkgKyBNYXRoLmFicyggdGhpcy55ICkgKyBNYXRoLmFicyggdGhpcy56ICk7CgogICAgCX0sCgogICAgCW5vcm1hbGl6ZTogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIHRoaXMuZGl2aWRlU2NhbGFyKCB0aGlzLmxlbmd0aCgpIHx8IDEgKTsKCiAgICAJfSwKCiAgICAJc2V0TGVuZ3RoOiBmdW5jdGlvbiAoIGxlbmd0aCApIHsKCiAgICAJCXJldHVybiB0aGlzLm5vcm1hbGl6ZSgpLm11bHRpcGx5U2NhbGFyKCBsZW5ndGggKTsKCiAgICAJfSwKCiAgICAJbGVycDogZnVuY3Rpb24gKCB2LCBhbHBoYSApIHsKCiAgICAJCXRoaXMueCArPSAoIHYueCAtIHRoaXMueCApICogYWxwaGE7CiAgICAJCXRoaXMueSArPSAoIHYueSAtIHRoaXMueSApICogYWxwaGE7CiAgICAJCXRoaXMueiArPSAoIHYueiAtIHRoaXMueiApICogYWxwaGE7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbGVycFZlY3RvcnM6IGZ1bmN0aW9uICggdjEsIHYyLCBhbHBoYSApIHsKCiAgICAJCXJldHVybiB0aGlzLnN1YlZlY3RvcnMoIHYyLCB2MSApLm11bHRpcGx5U2NhbGFyKCBhbHBoYSApLmFkZCggdjEgKTsKCiAgICAJfSwKCiAgICAJY3Jvc3M6IGZ1bmN0aW9uICggdiwgdyApIHsKCiAgICAJCWlmICggdyAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjM6IC5jcm9zcygpIG5vdyBvbmx5IGFjY2VwdHMgb25lIGFyZ3VtZW50LiBVc2UgLmNyb3NzVmVjdG9ycyggYSwgYiApIGluc3RlYWQuJyApOwogICAgCQkJcmV0dXJuIHRoaXMuY3Jvc3NWZWN0b3JzKCB2LCB3ICk7CgogICAgCQl9CgogICAgCQlyZXR1cm4gdGhpcy5jcm9zc1ZlY3RvcnMoIHRoaXMsIHYgKTsKCiAgICAJfSwKCiAgICAJY3Jvc3NWZWN0b3JzOiBmdW5jdGlvbiAoIGEsIGIgKSB7CgogICAgCQl2YXIgYXggPSBhLngsIGF5ID0gYS55LCBheiA9IGEuejsKICAgIAkJdmFyIGJ4ID0gYi54LCBieSA9IGIueSwgYnogPSBiLno7CgogICAgCQl0aGlzLnggPSBheSAqIGJ6IC0gYXogKiBieTsKICAgIAkJdGhpcy55ID0gYXogKiBieCAtIGF4ICogYno7CiAgICAJCXRoaXMueiA9IGF4ICogYnkgLSBheSAqIGJ4OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXByb2plY3RPblZlY3RvcjogZnVuY3Rpb24gKCB2ZWN0b3IgKSB7CgogICAgCQl2YXIgc2NhbGFyID0gdmVjdG9yLmRvdCggdGhpcyApIC8gdmVjdG9yLmxlbmd0aFNxKCk7CgogICAgCQlyZXR1cm4gdGhpcy5jb3B5KCB2ZWN0b3IgKS5tdWx0aXBseVNjYWxhciggc2NhbGFyICk7CgogICAgCX0sCgogICAgCXByb2plY3RPblBsYW5lOiBmdW5jdGlvbiAoIHBsYW5lTm9ybWFsICkgewoKICAgIAkJX3ZlY3Rvci5jb3B5KCB0aGlzICkucHJvamVjdE9uVmVjdG9yKCBwbGFuZU5vcm1hbCApOwoKICAgIAkJcmV0dXJuIHRoaXMuc3ViKCBfdmVjdG9yICk7CgogICAgCX0sCgogICAgCXJlZmxlY3Q6IGZ1bmN0aW9uICggbm9ybWFsICkgewoKICAgIAkJLy8gcmVmbGVjdCBpbmNpZGVudCB2ZWN0b3Igb2ZmIHBsYW5lIG9ydGhvZ29uYWwgdG8gbm9ybWFsCiAgICAJCS8vIG5vcm1hbCBpcyBhc3N1bWVkIHRvIGhhdmUgdW5pdCBsZW5ndGgKCiAgICAJCXJldHVybiB0aGlzLnN1YiggX3ZlY3Rvci5jb3B5KCBub3JtYWwgKS5tdWx0aXBseVNjYWxhciggMiAqIHRoaXMuZG90KCBub3JtYWwgKSApICk7CgogICAgCX0sCgogICAgCWFuZ2xlVG86IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXZhciB0aGV0YSA9IHRoaXMuZG90KCB2ICkgLyAoIE1hdGguc3FydCggdGhpcy5sZW5ndGhTcSgpICogdi5sZW5ndGhTcSgpICkgKTsKCiAgICAJCS8vIGNsYW1wLCB0byBoYW5kbGUgbnVtZXJpY2FsIHByb2JsZW1zCgogICAgCQlyZXR1cm4gTWF0aC5hY29zKCBfTWF0aC5jbGFtcCggdGhldGEsIC0gMSwgMSApICk7CgogICAgCX0sCgogICAgCWRpc3RhbmNlVG86IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXJldHVybiBNYXRoLnNxcnQoIHRoaXMuZGlzdGFuY2VUb1NxdWFyZWQoIHYgKSApOwoKICAgIAl9LAoKICAgIAlkaXN0YW5jZVRvU3F1YXJlZDogZnVuY3Rpb24gKCB2ICkgewoKICAgIAkJdmFyIGR4ID0gdGhpcy54IC0gdi54LCBkeSA9IHRoaXMueSAtIHYueSwgZHogPSB0aGlzLnogLSB2Lno7CgogICAgCQlyZXR1cm4gZHggKiBkeCArIGR5ICogZHkgKyBkeiAqIGR6OwoKICAgIAl9LAoKICAgIAltYW5oYXR0YW5EaXN0YW5jZVRvOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gTWF0aC5hYnMoIHRoaXMueCAtIHYueCApICsgTWF0aC5hYnMoIHRoaXMueSAtIHYueSApICsgTWF0aC5hYnMoIHRoaXMueiAtIHYueiApOwoKICAgIAl9LAoKICAgIAlzZXRGcm9tU3BoZXJpY2FsOiBmdW5jdGlvbiAoIHMgKSB7CgogICAgCQlyZXR1cm4gdGhpcy5zZXRGcm9tU3BoZXJpY2FsQ29vcmRzKCBzLnJhZGl1cywgcy5waGksIHMudGhldGEgKTsKCiAgICAJfSwKCiAgICAJc2V0RnJvbVNwaGVyaWNhbENvb3JkczogZnVuY3Rpb24gKCByYWRpdXMsIHBoaSwgdGhldGEgKSB7CgogICAgCQl2YXIgc2luUGhpUmFkaXVzID0gTWF0aC5zaW4oIHBoaSApICogcmFkaXVzOwoKICAgIAkJdGhpcy54ID0gc2luUGhpUmFkaXVzICogTWF0aC5zaW4oIHRoZXRhICk7CiAgICAJCXRoaXMueSA9IE1hdGguY29zKCBwaGkgKSAqIHJhZGl1czsKICAgIAkJdGhpcy56ID0gc2luUGhpUmFkaXVzICogTWF0aC5jb3MoIHRoZXRhICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0RnJvbUN5bGluZHJpY2FsOiBmdW5jdGlvbiAoIGMgKSB7CgogICAgCQlyZXR1cm4gdGhpcy5zZXRGcm9tQ3lsaW5kcmljYWxDb29yZHMoIGMucmFkaXVzLCBjLnRoZXRhLCBjLnkgKTsKCiAgICAJfSwKCiAgICAJc2V0RnJvbUN5bGluZHJpY2FsQ29vcmRzOiBmdW5jdGlvbiAoIHJhZGl1cywgdGhldGEsIHkgKSB7CgogICAgCQl0aGlzLnggPSByYWRpdXMgKiBNYXRoLnNpbiggdGhldGEgKTsKICAgIAkJdGhpcy55ID0geTsKICAgIAkJdGhpcy56ID0gcmFkaXVzICogTWF0aC5jb3MoIHRoZXRhICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0RnJvbU1hdHJpeFBvc2l0aW9uOiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQl2YXIgZSA9IG0uZWxlbWVudHM7CgogICAgCQl0aGlzLnggPSBlWyAxMiBdOwogICAgCQl0aGlzLnkgPSBlWyAxMyBdOwogICAgCQl0aGlzLnogPSBlWyAxNCBdOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldEZyb21NYXRyaXhTY2FsZTogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJdmFyIHN4ID0gdGhpcy5zZXRGcm9tTWF0cml4Q29sdW1uKCBtLCAwICkubGVuZ3RoKCk7CiAgICAJCXZhciBzeSA9IHRoaXMuc2V0RnJvbU1hdHJpeENvbHVtbiggbSwgMSApLmxlbmd0aCgpOwogICAgCQl2YXIgc3ogPSB0aGlzLnNldEZyb21NYXRyaXhDb2x1bW4oIG0sIDIgKS5sZW5ndGgoKTsKCiAgICAJCXRoaXMueCA9IHN4OwogICAgCQl0aGlzLnkgPSBzeTsKICAgIAkJdGhpcy56ID0gc3o7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0RnJvbU1hdHJpeENvbHVtbjogZnVuY3Rpb24gKCBtLCBpbmRleCApIHsKCiAgICAJCXJldHVybiB0aGlzLmZyb21BcnJheSggbS5lbGVtZW50cywgaW5kZXggKiA0ICk7CgogICAgCX0sCgogICAgCWVxdWFsczogZnVuY3Rpb24gKCB2ICkgewoKICAgIAkJcmV0dXJuICggKCB2LnggPT09IHRoaXMueCApICYmICggdi55ID09PSB0aGlzLnkgKSAmJiAoIHYueiA9PT0gdGhpcy56ICkgKTsKCiAgICAJfSwKCiAgICAJZnJvbUFycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCXRoaXMueCA9IGFycmF5WyBvZmZzZXQgXTsKICAgIAkJdGhpcy55ID0gYXJyYXlbIG9mZnNldCArIDEgXTsKICAgIAkJdGhpcy56ID0gYXJyYXlbIG9mZnNldCArIDIgXTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAl0b0FycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIGFycmF5ID09PSB1bmRlZmluZWQgKSBhcnJheSA9IFtdOwogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCWFycmF5WyBvZmZzZXQgXSA9IHRoaXMueDsKICAgIAkJYXJyYXlbIG9mZnNldCArIDEgXSA9IHRoaXMueTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDIgXSA9IHRoaXMuejsKCiAgICAJCXJldHVybiBhcnJheTsKCiAgICAJfSwKCiAgICAJZnJvbUJ1ZmZlckF0dHJpYnV0ZTogZnVuY3Rpb24gKCBhdHRyaWJ1dGUsIGluZGV4LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjM6IG9mZnNldCBoYXMgYmVlbiByZW1vdmVkIGZyb20gLmZyb21CdWZmZXJBdHRyaWJ1dGUoKS4nICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggPSBhdHRyaWJ1dGUuZ2V0WCggaW5kZXggKTsKICAgIAkJdGhpcy55ID0gYXR0cmlidXRlLmdldFkoIGluZGV4ICk7CiAgICAJCXRoaXMueiA9IGF0dHJpYnV0ZS5nZXRaKCBpbmRleCApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0KCiAgICB9ICk7CgogICAgLyoqCiAgICAgKiBAYXV0aG9yIGFsdGVyZWRxIC8gaHR0cDovL2FsdGVyZWRxdWFsaWEuY29tLwogICAgICogQGF1dGhvciBXZXN0TGFuZ2xleSAvIGh0dHA6Ly9naXRodWIuY29tL1dlc3RMYW5nbGV5CiAgICAgKiBAYXV0aG9yIGJob3VzdG9uIC8gaHR0cDovL2NsYXJhLmlvCiAgICAgKiBAYXV0aG9yIHRzY2h3CiAgICAgKi8KCiAgICB2YXIgX3ZlY3RvciQxID0gbmV3IFZlY3RvcjMoKTsKCiAgICBmdW5jdGlvbiBNYXRyaXgzKCkgewoKICAgIAl0aGlzLmVsZW1lbnRzID0gWwoKICAgIAkJMSwgMCwgMCwKICAgIAkJMCwgMSwgMCwKICAgIAkJMCwgMCwgMQoKICAgIAldOwoKICAgIAlpZiAoIGFyZ3VtZW50cy5sZW5ndGggPiAwICkgewoKICAgIAkJY29uc29sZS5lcnJvciggJ1RIUkVFLk1hdHJpeDM6IHRoZSBjb25zdHJ1Y3RvciBubyBsb25nZXIgcmVhZHMgYXJndW1lbnRzLiB1c2UgLnNldCgpIGluc3RlYWQuJyApOwoKICAgIAl9CgogICAgfQoKICAgIE9iamVjdC5hc3NpZ24oIE1hdHJpeDMucHJvdG90eXBlLCB7CgogICAgCWlzTWF0cml4MzogdHJ1ZSwKCiAgICAJc2V0OiBmdW5jdGlvbiAoIG4xMSwgbjEyLCBuMTMsIG4yMSwgbjIyLCBuMjMsIG4zMSwgbjMyLCBuMzMgKSB7CgogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwoKICAgIAkJdGVbIDAgXSA9IG4xMTsgdGVbIDEgXSA9IG4yMTsgdGVbIDIgXSA9IG4zMTsKICAgIAkJdGVbIDMgXSA9IG4xMjsgdGVbIDQgXSA9IG4yMjsgdGVbIDUgXSA9IG4zMjsKICAgIAkJdGVbIDYgXSA9IG4xMzsgdGVbIDcgXSA9IG4yMzsgdGVbIDggXSA9IG4zMzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlpZGVudGl0eTogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy5zZXQoCgogICAgCQkJMSwgMCwgMCwKICAgIAkJCTAsIDEsIDAsCiAgICAJCQkwLCAwLCAxCgogICAgCQkpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsb25lOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gbmV3IHRoaXMuY29uc3RydWN0b3IoKS5mcm9tQXJyYXkoIHRoaXMuZWxlbWVudHMgKTsKCiAgICAJfSwKCiAgICAJY29weTogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKICAgIAkJdmFyIG1lID0gbS5lbGVtZW50czsKCiAgICAJCXRlWyAwIF0gPSBtZVsgMCBdOyB0ZVsgMSBdID0gbWVbIDEgXTsgdGVbIDIgXSA9IG1lWyAyIF07CiAgICAJCXRlWyAzIF0gPSBtZVsgMyBdOyB0ZVsgNCBdID0gbWVbIDQgXTsgdGVbIDUgXSA9IG1lWyA1IF07CiAgICAJCXRlWyA2IF0gPSBtZVsgNiBdOyB0ZVsgNyBdID0gbWVbIDcgXTsgdGVbIDggXSA9IG1lWyA4IF07CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0RnJvbU1hdHJpeDQ6IGZ1bmN0aW9uICggbSApIHsKCiAgICAJCXZhciBtZSA9IG0uZWxlbWVudHM7CgogICAgCQl0aGlzLnNldCgKCiAgICAJCQltZVsgMCBdLCBtZVsgNCBdLCBtZVsgOCBdLAogICAgCQkJbWVbIDEgXSwgbWVbIDUgXSwgbWVbIDkgXSwKICAgIAkJCW1lWyAyIF0sIG1lWyA2IF0sIG1lWyAxMCBdCgogICAgCQkpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFwcGx5VG9CdWZmZXJBdHRyaWJ1dGU6IGZ1bmN0aW9uICggYXR0cmlidXRlICkgewoKICAgIAkJZm9yICggdmFyIGkgPSAwLCBsID0gYXR0cmlidXRlLmNvdW50OyBpIDwgbDsgaSArKyApIHsKCiAgICAJCQlfdmVjdG9yJDEueCA9IGF0dHJpYnV0ZS5nZXRYKCBpICk7CiAgICAJCQlfdmVjdG9yJDEueSA9IGF0dHJpYnV0ZS5nZXRZKCBpICk7CiAgICAJCQlfdmVjdG9yJDEueiA9IGF0dHJpYnV0ZS5nZXRaKCBpICk7CgogICAgCQkJX3ZlY3RvciQxLmFwcGx5TWF0cml4MyggdGhpcyApOwoKICAgIAkJCWF0dHJpYnV0ZS5zZXRYWVooIGksIF92ZWN0b3IkMS54LCBfdmVjdG9yJDEueSwgX3ZlY3RvciQxLnogKTsKCiAgICAJCX0KCiAgICAJCXJldHVybiBhdHRyaWJ1dGU7CgogICAgCX0sCgogICAgCW11bHRpcGx5OiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQlyZXR1cm4gdGhpcy5tdWx0aXBseU1hdHJpY2VzKCB0aGlzLCBtICk7CgogICAgCX0sCgogICAgCXByZW11bHRpcGx5OiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQlyZXR1cm4gdGhpcy5tdWx0aXBseU1hdHJpY2VzKCBtLCB0aGlzICk7CgogICAgCX0sCgogICAgCW11bHRpcGx5TWF0cmljZXM6IGZ1bmN0aW9uICggYSwgYiApIHsKCiAgICAJCXZhciBhZSA9IGEuZWxlbWVudHM7CiAgICAJCXZhciBiZSA9IGIuZWxlbWVudHM7CiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl2YXIgYTExID0gYWVbIDAgXSwgYTEyID0gYWVbIDMgXSwgYTEzID0gYWVbIDYgXTsKICAgIAkJdmFyIGEyMSA9IGFlWyAxIF0sIGEyMiA9IGFlWyA0IF0sIGEyMyA9IGFlWyA3IF07CiAgICAJCXZhciBhMzEgPSBhZVsgMiBdLCBhMzIgPSBhZVsgNSBdLCBhMzMgPSBhZVsgOCBdOwoKICAgIAkJdmFyIGIxMSA9IGJlWyAwIF0sIGIxMiA9IGJlWyAzIF0sIGIxMyA9IGJlWyA2IF07CiAgICAJCXZhciBiMjEgPSBiZVsgMSBdLCBiMjIgPSBiZVsgNCBdLCBiMjMgPSBiZVsgNyBdOwogICAgCQl2YXIgYjMxID0gYmVbIDIgXSwgYjMyID0gYmVbIDUgXSwgYjMzID0gYmVbIDggXTsKCiAgICAJCXRlWyAwIF0gPSBhMTEgKiBiMTEgKyBhMTIgKiBiMjEgKyBhMTMgKiBiMzE7CiAgICAJCXRlWyAzIF0gPSBhMTEgKiBiMTIgKyBhMTIgKiBiMjIgKyBhMTMgKiBiMzI7CiAgICAJCXRlWyA2IF0gPSBhMTEgKiBiMTMgKyBhMTIgKiBiMjMgKyBhMTMgKiBiMzM7CgogICAgCQl0ZVsgMSBdID0gYTIxICogYjExICsgYTIyICogYjIxICsgYTIzICogYjMxOwogICAgCQl0ZVsgNCBdID0gYTIxICogYjEyICsgYTIyICogYjIyICsgYTIzICogYjMyOwogICAgCQl0ZVsgNyBdID0gYTIxICogYjEzICsgYTIyICogYjIzICsgYTIzICogYjMzOwoKICAgIAkJdGVbIDIgXSA9IGEzMSAqIGIxMSArIGEzMiAqIGIyMSArIGEzMyAqIGIzMTsKICAgIAkJdGVbIDUgXSA9IGEzMSAqIGIxMiArIGEzMiAqIGIyMiArIGEzMyAqIGIzMjsKICAgIAkJdGVbIDggXSA9IGEzMSAqIGIxMyArIGEzMiAqIGIyMyArIGEzMyAqIGIzMzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltdWx0aXBseVNjYWxhcjogZnVuY3Rpb24gKCBzICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKCiAgICAJCXRlWyAwIF0gKj0gczsgdGVbIDMgXSAqPSBzOyB0ZVsgNiBdICo9IHM7CiAgICAJCXRlWyAxIF0gKj0gczsgdGVbIDQgXSAqPSBzOyB0ZVsgNyBdICo9IHM7CiAgICAJCXRlWyAyIF0gKj0gczsgdGVbIDUgXSAqPSBzOyB0ZVsgOCBdICo9IHM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZGV0ZXJtaW5hbnQ6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl2YXIgYSA9IHRlWyAwIF0sIGIgPSB0ZVsgMSBdLCBjID0gdGVbIDIgXSwKICAgIAkJCWQgPSB0ZVsgMyBdLCBlID0gdGVbIDQgXSwgZiA9IHRlWyA1IF0sCiAgICAJCQlnID0gdGVbIDYgXSwgaCA9IHRlWyA3IF0sIGkgPSB0ZVsgOCBdOwoKICAgIAkJcmV0dXJuIGEgKiBlICogaSAtIGEgKiBmICogaCAtIGIgKiBkICogaSArIGIgKiBmICogZyArIGMgKiBkICogaCAtIGMgKiBlICogZzsKCiAgICAJfSwKCiAgICAJZ2V0SW52ZXJzZTogZnVuY3Rpb24gKCBtYXRyaXgsIHRocm93T25EZWdlbmVyYXRlICkgewoKICAgIAkJaWYgKCBtYXRyaXggJiYgbWF0cml4LmlzTWF0cml4NCApIHsKCiAgICAJCQljb25zb2xlLmVycm9yKCAiVEhSRUUuTWF0cml4MzogLmdldEludmVyc2UoKSBubyBsb25nZXIgdGFrZXMgYSBNYXRyaXg0IGFyZ3VtZW50LiIgKTsKCiAgICAJCX0KCiAgICAJCXZhciBtZSA9IG1hdHJpeC5lbGVtZW50cywKICAgIAkJCXRlID0gdGhpcy5lbGVtZW50cywKCiAgICAJCQluMTEgPSBtZVsgMCBdLCBuMjEgPSBtZVsgMSBdLCBuMzEgPSBtZVsgMiBdLAogICAgCQkJbjEyID0gbWVbIDMgXSwgbjIyID0gbWVbIDQgXSwgbjMyID0gbWVbIDUgXSwKICAgIAkJCW4xMyA9IG1lWyA2IF0sIG4yMyA9IG1lWyA3IF0sIG4zMyA9IG1lWyA4IF0sCgogICAgCQkJdDExID0gbjMzICogbjIyIC0gbjMyICogbjIzLAogICAgCQkJdDEyID0gbjMyICogbjEzIC0gbjMzICogbjEyLAogICAgCQkJdDEzID0gbjIzICogbjEyIC0gbjIyICogbjEzLAoKICAgIAkJCWRldCA9IG4xMSAqIHQxMSArIG4yMSAqIHQxMiArIG4zMSAqIHQxMzsKCiAgICAJCWlmICggZGV0ID09PSAwICkgewoKICAgIAkJCXZhciBtc2cgPSAiVEhSRUUuTWF0cml4MzogLmdldEludmVyc2UoKSBjYW4ndCBpbnZlcnQgbWF0cml4LCBkZXRlcm1pbmFudCBpcyAwIjsKCiAgICAJCQlpZiAoIHRocm93T25EZWdlbmVyYXRlID09PSB0cnVlICkgewoKICAgIAkJCQl0aHJvdyBuZXcgRXJyb3IoIG1zZyApOwoKICAgIAkJCX0gZWxzZSB7CgogICAgCQkJCWNvbnNvbGUud2FybiggbXNnICk7CgogICAgCQkJfQoKICAgIAkJCXJldHVybiB0aGlzLmlkZW50aXR5KCk7CgogICAgCQl9CgogICAgCQl2YXIgZGV0SW52ID0gMSAvIGRldDsKCiAgICAJCXRlWyAwIF0gPSB0MTEgKiBkZXRJbnY7CiAgICAJCXRlWyAxIF0gPSAoIG4zMSAqIG4yMyAtIG4zMyAqIG4yMSApICogZGV0SW52OwogICAgCQl0ZVsgMiBdID0gKCBuMzIgKiBuMjEgLSBuMzEgKiBuMjIgKSAqIGRldEludjsKCiAgICAJCXRlWyAzIF0gPSB0MTIgKiBkZXRJbnY7CiAgICAJCXRlWyA0IF0gPSAoIG4zMyAqIG4xMSAtIG4zMSAqIG4xMyApICogZGV0SW52OwogICAgCQl0ZVsgNSBdID0gKCBuMzEgKiBuMTIgLSBuMzIgKiBuMTEgKSAqIGRldEludjsKCiAgICAJCXRlWyA2IF0gPSB0MTMgKiBkZXRJbnY7CiAgICAJCXRlWyA3IF0gPSAoIG4yMSAqIG4xMyAtIG4yMyAqIG4xMSApICogZGV0SW52OwogICAgCQl0ZVsgOCBdID0gKCBuMjIgKiBuMTEgLSBuMjEgKiBuMTIgKSAqIGRldEludjsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAl0cmFuc3Bvc2U6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXZhciB0bXAsIG0gPSB0aGlzLmVsZW1lbnRzOwoKICAgIAkJdG1wID0gbVsgMSBdOyBtWyAxIF0gPSBtWyAzIF07IG1bIDMgXSA9IHRtcDsKICAgIAkJdG1wID0gbVsgMiBdOyBtWyAyIF0gPSBtWyA2IF07IG1bIDYgXSA9IHRtcDsKICAgIAkJdG1wID0gbVsgNSBdOyBtWyA1IF0gPSBtWyA3IF07IG1bIDcgXSA9IHRtcDsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlnZXROb3JtYWxNYXRyaXg6IGZ1bmN0aW9uICggbWF0cml4NCApIHsKCiAgICAJCXJldHVybiB0aGlzLnNldEZyb21NYXRyaXg0KCBtYXRyaXg0ICkuZ2V0SW52ZXJzZSggdGhpcyApLnRyYW5zcG9zZSgpOwoKICAgIAl9LAoKICAgIAl0cmFuc3Bvc2VJbnRvQXJyYXk6IGZ1bmN0aW9uICggciApIHsKCiAgICAJCXZhciBtID0gdGhpcy5lbGVtZW50czsKCiAgICAJCXJbIDAgXSA9IG1bIDAgXTsKICAgIAkJclsgMSBdID0gbVsgMyBdOwogICAgCQlyWyAyIF0gPSBtWyA2IF07CiAgICAJCXJbIDMgXSA9IG1bIDEgXTsKICAgIAkJclsgNCBdID0gbVsgNCBdOwogICAgCQlyWyA1IF0gPSBtWyA3IF07CiAgICAJCXJbIDYgXSA9IG1bIDIgXTsKICAgIAkJclsgNyBdID0gbVsgNSBdOwogICAgCQlyWyA4IF0gPSBtWyA4IF07CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0VXZUcmFuc2Zvcm06IGZ1bmN0aW9uICggdHgsIHR5LCBzeCwgc3ksIHJvdGF0aW9uLCBjeCwgY3kgKSB7CgogICAgCQl2YXIgYyA9IE1hdGguY29zKCByb3RhdGlvbiApOwogICAgCQl2YXIgcyA9IE1hdGguc2luKCByb3RhdGlvbiApOwoKICAgIAkJdGhpcy5zZXQoCiAgICAJCQlzeCAqIGMsIHN4ICogcywgLSBzeCAqICggYyAqIGN4ICsgcyAqIGN5ICkgKyBjeCArIHR4LAogICAgCQkJLSBzeSAqIHMsIHN5ICogYywgLSBzeSAqICggLSBzICogY3ggKyBjICogY3kgKSArIGN5ICsgdHksCiAgICAJCQkwLCAwLCAxCiAgICAJCSk7CgogICAgCX0sCgogICAgCXNjYWxlOiBmdW5jdGlvbiAoIHN4LCBzeSApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl0ZVsgMCBdICo9IHN4OyB0ZVsgMyBdICo9IHN4OyB0ZVsgNiBdICo9IHN4OwogICAgCQl0ZVsgMSBdICo9IHN5OyB0ZVsgNCBdICo9IHN5OyB0ZVsgNyBdICo9IHN5OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXJvdGF0ZTogZnVuY3Rpb24gKCB0aGV0YSApIHsKCiAgICAJCXZhciBjID0gTWF0aC5jb3MoIHRoZXRhICk7CiAgICAJCXZhciBzID0gTWF0aC5zaW4oIHRoZXRhICk7CgogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwoKICAgIAkJdmFyIGExMSA9IHRlWyAwIF0sIGExMiA9IHRlWyAzIF0sIGExMyA9IHRlWyA2IF07CiAgICAJCXZhciBhMjEgPSB0ZVsgMSBdLCBhMjIgPSB0ZVsgNCBdLCBhMjMgPSB0ZVsgNyBdOwoKICAgIAkJdGVbIDAgXSA9IGMgKiBhMTEgKyBzICogYTIxOwogICAgCQl0ZVsgMyBdID0gYyAqIGExMiArIHMgKiBhMjI7CiAgICAJCXRlWyA2IF0gPSBjICogYTEzICsgcyAqIGEyMzsKCiAgICAJCXRlWyAxIF0gPSAtIHMgKiBhMTEgKyBjICogYTIxOwogICAgCQl0ZVsgNCBdID0gLSBzICogYTEyICsgYyAqIGEyMjsKICAgIAkJdGVbIDcgXSA9IC0gcyAqIGExMyArIGMgKiBhMjM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJdHJhbnNsYXRlOiBmdW5jdGlvbiAoIHR4LCB0eSApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl0ZVsgMCBdICs9IHR4ICogdGVbIDIgXTsgdGVbIDMgXSArPSB0eCAqIHRlWyA1IF07IHRlWyA2IF0gKz0gdHggKiB0ZVsgOCBdOwogICAgCQl0ZVsgMSBdICs9IHR5ICogdGVbIDIgXTsgdGVbIDQgXSArPSB0eSAqIHRlWyA1IF07IHRlWyA3IF0gKz0gdHkgKiB0ZVsgOCBdOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWVxdWFsczogZnVuY3Rpb24gKCBtYXRyaXggKSB7CgogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwogICAgCQl2YXIgbWUgPSBtYXRyaXguZWxlbWVudHM7CgogICAgCQlmb3IgKCB2YXIgaSA9IDA7IGkgPCA5OyBpICsrICkgewoKICAgIAkJCWlmICggdGVbIGkgXSAhPT0gbWVbIGkgXSApIHJldHVybiBmYWxzZTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0cnVlOwoKICAgIAl9LAoKICAgIAlmcm9tQXJyYXk6IGZ1bmN0aW9uICggYXJyYXksIG9mZnNldCApIHsKCiAgICAJCWlmICggb2Zmc2V0ID09PSB1bmRlZmluZWQgKSBvZmZzZXQgPSAwOwoKICAgIAkJZm9yICggdmFyIGkgPSAwOyBpIDwgOTsgaSArKyApIHsKCiAgICAJCQl0aGlzLmVsZW1lbnRzWyBpIF0gPSBhcnJheVsgaSArIG9mZnNldCBdOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXRvQXJyYXk6IGZ1bmN0aW9uICggYXJyYXksIG9mZnNldCApIHsKCiAgICAJCWlmICggYXJyYXkgPT09IHVuZGVmaW5lZCApIGFycmF5ID0gW107CiAgICAJCWlmICggb2Zmc2V0ID09PSB1bmRlZmluZWQgKSBvZmZzZXQgPSAwOwoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKCiAgICAJCWFycmF5WyBvZmZzZXQgXSA9IHRlWyAwIF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyAxIF0gPSB0ZVsgMSBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMiBdID0gdGVbIDIgXTsKCiAgICAJCWFycmF5WyBvZmZzZXQgKyAzIF0gPSB0ZVsgMyBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgNCBdID0gdGVbIDQgXTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDUgXSA9IHRlWyA1IF07CgogICAgCQlhcnJheVsgb2Zmc2V0ICsgNiBdID0gdGVbIDYgXTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDcgXSA9IHRlWyA3IF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyA4IF0gPSB0ZVsgOCBdOwoKICAgIAkJcmV0dXJuIGFycmF5OwoKICAgIAl9CgogICAgfSApOwoKICAgIC8qKgogICAgICogQGF1dGhvciBtcmRvb2IgLyBodHRwOi8vbXJkb29iLmNvbS8KICAgICAqIEBhdXRob3IgYWx0ZXJlZHEgLyBodHRwOi8vYWx0ZXJlZHF1YWxpYS5jb20vCiAgICAgKiBAYXV0aG9yIHN6aW1layAvIGh0dHBzOi8vZ2l0aHViLmNvbS9zemltZWsvCiAgICAgKi8KCiAgICB2YXIgX2NhbnZhczsKCiAgICB2YXIgSW1hZ2VVdGlscyA9IHsKCiAgICAJZ2V0RGF0YVVSTDogZnVuY3Rpb24gKCBpbWFnZSApIHsKCiAgICAJCXZhciBjYW52YXM7CgogICAgCQlpZiAoIHR5cGVvZiBIVE1MQ2FudmFzRWxlbWVudCA9PSAndW5kZWZpbmVkJyApIHsKCiAgICAJCQlyZXR1cm4gaW1hZ2Uuc3JjOwoKICAgIAkJfSBlbHNlIGlmICggaW1hZ2UgaW5zdGFuY2VvZiBIVE1MQ2FudmFzRWxlbWVudCApIHsKCiAgICAJCQljYW52YXMgPSBpbWFnZTsKCiAgICAJCX0gZWxzZSB7CgogICAgCQkJaWYgKCBfY2FudmFzID09PSB1bmRlZmluZWQgKSBfY2FudmFzID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudE5TKCAnaHR0cDovL3d3dy53My5vcmcvMTk5OS94aHRtbCcsICdjYW52YXMnICk7CgogICAgCQkJX2NhbnZhcy53aWR0aCA9IGltYWdlLndpZHRoOwogICAgCQkJX2NhbnZhcy5oZWlnaHQgPSBpbWFnZS5oZWlnaHQ7CgogICAgCQkJdmFyIGNvbnRleHQgPSBfY2FudmFzLmdldENvbnRleHQoICcyZCcgKTsKCiAgICAJCQlpZiAoIGltYWdlIGluc3RhbmNlb2YgSW1hZ2VEYXRhICkgewoKICAgIAkJCQljb250ZXh0LnB1dEltYWdlRGF0YSggaW1hZ2UsIDAsIDAgKTsKCiAgICAJCQl9IGVsc2UgewoKICAgIAkJCQljb250ZXh0LmRyYXdJbWFnZSggaW1hZ2UsIDAsIDAsIGltYWdlLndpZHRoLCBpbWFnZS5oZWlnaHQgKTsKCiAgICAJCQl9CgogICAgCQkJY2FudmFzID0gX2NhbnZhczsKCiAgICAJCX0KCiAgICAJCWlmICggY2FudmFzLndpZHRoID4gMjA0OCB8fCBjYW52YXMuaGVpZ2h0ID4gMjA0OCApIHsKCiAgICAJCQlyZXR1cm4gY2FudmFzLnRvRGF0YVVSTCggJ2ltYWdlL2pwZWcnLCAwLjYgKTsKCiAgICAJCX0gZWxzZSB7CgogICAgCQkJcmV0dXJuIGNhbnZhcy50b0RhdGFVUkwoICdpbWFnZS9wbmcnICk7CgogICAgCQl9CgogICAgCX0KCiAgICB9OwoKICAgIC8qKgogICAgICogQGF1dGhvciBtcmRvb2IgLyBodHRwOi8vbXJkb29iLmNvbS8KICAgICAqIEBhdXRob3IgYWx0ZXJlZHEgLyBodHRwOi8vYWx0ZXJlZHF1YWxpYS5jb20vCiAgICAgKiBAYXV0aG9yIHN6aW1layAvIGh0dHBzOi8vZ2l0aHViLmNvbS9zemltZWsvCiAgICAgKi8KCiAgICB2YXIgdGV4dHVyZUlkID0gMDsKCiAgICBmdW5jdGlvbiBUZXh0dXJlKCBpbWFnZSwgbWFwcGluZywgd3JhcFMsIHdyYXBULCBtYWdGaWx0ZXIsIG1pbkZpbHRlciwgZm9ybWF0LCB0eXBlLCBhbmlzb3Ryb3B5LCBlbmNvZGluZyApIHsKCiAgICAJT2JqZWN0LmRlZmluZVByb3BlcnR5KCB0aGlzLCAnaWQnLCB7IHZhbHVlOiB0ZXh0dXJlSWQgKysgfSApOwoKICAgIAl0aGlzLnV1aWQgPSBfTWF0aC5nZW5lcmF0ZVVVSUQoKTsKCiAgICAJdGhpcy5uYW1lID0gJyc7CgogICAgCXRoaXMuaW1hZ2UgPSBpbWFnZSAhPT0gdW5kZWZpbmVkID8gaW1hZ2UgOiBUZXh0dXJlLkRFRkFVTFRfSU1BR0U7CiAgICAJdGhpcy5taXBtYXBzID0gW107CgogICAgCXRoaXMubWFwcGluZyA9IG1hcHBpbmcgIT09IHVuZGVmaW5lZCA/IG1hcHBpbmcgOiBUZXh0dXJlLkRFRkFVTFRfTUFQUElORzsKCiAgICAJdGhpcy53cmFwUyA9IHdyYXBTICE9PSB1bmRlZmluZWQgPyB3cmFwUyA6IENsYW1wVG9FZGdlV3JhcHBpbmc7CiAgICAJdGhpcy53cmFwVCA9IHdyYXBUICE9PSB1bmRlZmluZWQgPyB3cmFwVCA6IENsYW1wVG9FZGdlV3JhcHBpbmc7CgogICAgCXRoaXMubWFnRmlsdGVyID0gbWFnRmlsdGVyICE9PSB1bmRlZmluZWQgPyBtYWdGaWx0ZXIgOiBMaW5lYXJGaWx0ZXI7CiAgICAJdGhpcy5taW5GaWx0ZXIgPSBtaW5GaWx0ZXIgIT09IHVuZGVmaW5lZCA/IG1pbkZpbHRlciA6IExpbmVhck1pcG1hcExpbmVhckZpbHRlcjsKCiAgICAJdGhpcy5hbmlzb3Ryb3B5ID0gYW5pc290cm9weSAhPT0gdW5kZWZpbmVkID8gYW5pc290cm9weSA6IDE7CgogICAgCXRoaXMuZm9ybWF0ID0gZm9ybWF0ICE9PSB1bmRlZmluZWQgPyBmb3JtYXQgOiBSR0JBRm9ybWF0OwogICAgCXRoaXMudHlwZSA9IHR5cGUgIT09IHVuZGVmaW5lZCA/IHR5cGUgOiBVbnNpZ25lZEJ5dGVUeXBlOwoKICAgIAl0aGlzLm9mZnNldCA9IG5ldyBWZWN0b3IyKCAwLCAwICk7CiAgICAJdGhpcy5yZXBlYXQgPSBuZXcgVmVjdG9yMiggMSwgMSApOwogICAgCXRoaXMuY2VudGVyID0gbmV3IFZlY3RvcjIoIDAsIDAgKTsKICAgIAl0aGlzLnJvdGF0aW9uID0gMDsKCiAgICAJdGhpcy5tYXRyaXhBdXRvVXBkYXRlID0gdHJ1ZTsKICAgIAl0aGlzLm1hdHJpeCA9IG5ldyBNYXRyaXgzKCk7CgogICAgCXRoaXMuZ2VuZXJhdGVNaXBtYXBzID0gdHJ1ZTsKICAgIAl0aGlzLnByZW11bHRpcGx5QWxwaGEgPSBmYWxzZTsKICAgIAl0aGlzLmZsaXBZID0gdHJ1ZTsKICAgIAl0aGlzLnVucGFja0FsaWdubWVudCA9IDQ7CS8vIHZhbGlkIHZhbHVlczogMSwgMiwgNCwgOCAoc2VlIGh0dHA6Ly93d3cua2hyb25vcy5vcmcvb3BlbmdsZXMvc2RrL2RvY3MvbWFuL3hodG1sL2dsUGl4ZWxTdG9yZWkueG1sKQoKICAgIAkvLyBWYWx1ZXMgb2YgZW5jb2RpbmcgIT09IFRIUkVFLkxpbmVhckVuY29kaW5nIG9ubHkgc3VwcG9ydGVkIG9uIG1hcCwgZW52TWFwIGFuZCBlbWlzc2l2ZU1hcC4KICAgIAkvLwogICAgCS8vIEFsc28gY2hhbmdpbmcgdGhlIGVuY29kaW5nIGFmdGVyIGFscmVhZHkgdXNlZCBieSBhIE1hdGVyaWFsIHdpbGwgbm90IGF1dG9tYXRpY2FsbHkgbWFrZSB0aGUgTWF0ZXJpYWwKICAgIAkvLyB1cGRhdGUuIFlvdSBuZWVkIHRvIGV4cGxpY2l0bHkgY2FsbCBNYXRlcmlhbC5uZWVkc1VwZGF0ZSB0byB0cmlnZ2VyIGl0IHRvIHJlY29tcGlsZS4KICAgIAl0aGlzLmVuY29kaW5nID0gZW5jb2RpbmcgIT09IHVuZGVmaW5lZCA/IGVuY29kaW5nIDogTGluZWFyRW5jb2Rpbmc7CgogICAgCXRoaXMudmVyc2lvbiA9IDA7CiAgICAJdGhpcy5vblVwZGF0ZSA9IG51bGw7CgogICAgfQoKICAgIFRleHR1cmUuREVGQVVMVF9JTUFHRSA9IHVuZGVmaW5lZDsKICAgIFRleHR1cmUuREVGQVVMVF9NQVBQSU5HID0gVVZNYXBwaW5nOwoKICAgIFRleHR1cmUucHJvdG90eXBlID0gT2JqZWN0LmFzc2lnbiggT2JqZWN0LmNyZWF0ZSggRXZlbnREaXNwYXRjaGVyLnByb3RvdHlwZSApLCB7CgogICAgCWNvbnN0cnVjdG9yOiBUZXh0dXJlLAoKICAgIAlpc1RleHR1cmU6IHRydWUsCgogICAgCXVwZGF0ZU1hdHJpeDogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy5tYXRyaXguc2V0VXZUcmFuc2Zvcm0oIHRoaXMub2Zmc2V0LngsIHRoaXMub2Zmc2V0LnksIHRoaXMucmVwZWF0LngsIHRoaXMucmVwZWF0LnksIHRoaXMucm90YXRpb24sIHRoaXMuY2VudGVyLngsIHRoaXMuY2VudGVyLnkgKTsKCiAgICAJfSwKCiAgICAJY2xvbmU6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBuZXcgdGhpcy5jb25zdHJ1Y3RvcigpLmNvcHkoIHRoaXMgKTsKCiAgICAJfSwKCiAgICAJY29weTogZnVuY3Rpb24gKCBzb3VyY2UgKSB7CgogICAgCQl0aGlzLm5hbWUgPSBzb3VyY2UubmFtZTsKCiAgICAJCXRoaXMuaW1hZ2UgPSBzb3VyY2UuaW1hZ2U7CiAgICAJCXRoaXMubWlwbWFwcyA9IHNvdXJjZS5taXBtYXBzLnNsaWNlKCAwICk7CgogICAgCQl0aGlzLm1hcHBpbmcgPSBzb3VyY2UubWFwcGluZzsKCiAgICAJCXRoaXMud3JhcFMgPSBzb3VyY2Uud3JhcFM7CiAgICAJCXRoaXMud3JhcFQgPSBzb3VyY2Uud3JhcFQ7CgogICAgCQl0aGlzLm1hZ0ZpbHRlciA9IHNvdXJjZS5tYWdGaWx0ZXI7CiAgICAJCXRoaXMubWluRmlsdGVyID0gc291cmNlLm1pbkZpbHRlcjsKCiAgICAJCXRoaXMuYW5pc290cm9weSA9IHNvdXJjZS5hbmlzb3Ryb3B5OwoKICAgIAkJdGhpcy5mb3JtYXQgPSBzb3VyY2UuZm9ybWF0OwogICAgCQl0aGlzLnR5cGUgPSBzb3VyY2UudHlwZTsKCiAgICAJCXRoaXMub2Zmc2V0LmNvcHkoIHNvdXJjZS5vZmZzZXQgKTsKICAgIAkJdGhpcy5yZXBlYXQuY29weSggc291cmNlLnJlcGVhdCApOwogICAgCQl0aGlzLmNlbnRlci5jb3B5KCBzb3VyY2UuY2VudGVyICk7CiAgICAJCXRoaXMucm90YXRpb24gPSBzb3VyY2Uucm90YXRpb247CgogICAgCQl0aGlzLm1hdHJpeEF1dG9VcGRhdGUgPSBzb3VyY2UubWF0cml4QXV0b1VwZGF0ZTsKICAgIAkJdGhpcy5tYXRyaXguY29weSggc291cmNlLm1hdHJpeCApOwoKICAgIAkJdGhpcy5nZW5lcmF0ZU1pcG1hcHMgPSBzb3VyY2UuZ2VuZXJhdGVNaXBtYXBzOwogICAgCQl0aGlzLnByZW11bHRpcGx5QWxwaGEgPSBzb3VyY2UucHJlbXVsdGlwbHlBbHBoYTsKICAgIAkJdGhpcy5mbGlwWSA9IHNvdXJjZS5mbGlwWTsKICAgIAkJdGhpcy51bnBhY2tBbGlnbm1lbnQgPSBzb3VyY2UudW5wYWNrQWxpZ25tZW50OwogICAgCQl0aGlzLmVuY29kaW5nID0gc291cmNlLmVuY29kaW5nOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXRvSlNPTjogZnVuY3Rpb24gKCBtZXRhICkgewoKICAgIAkJdmFyIGlzUm9vdE9iamVjdCA9ICggbWV0YSA9PT0gdW5kZWZpbmVkIHx8IHR5cGVvZiBtZXRhID09PSAnc3RyaW5nJyApOwoKICAgIAkJaWYgKCAhIGlzUm9vdE9iamVjdCAmJiBtZXRhLnRleHR1cmVzWyB0aGlzLnV1aWQgXSAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCXJldHVybiBtZXRhLnRleHR1cmVzWyB0aGlzLnV1aWQgXTsKCiAgICAJCX0KCiAgICAJCXZhciBvdXRwdXQgPSB7CgogICAgCQkJbWV0YWRhdGE6IHsKICAgIAkJCQl2ZXJzaW9uOiA0LjUsCiAgICAJCQkJdHlwZTogJ1RleHR1cmUnLAogICAgCQkJCWdlbmVyYXRvcjogJ1RleHR1cmUudG9KU09OJwogICAgCQkJfSwKCiAgICAJCQl1dWlkOiB0aGlzLnV1aWQsCiAgICAJCQluYW1lOiB0aGlzLm5hbWUsCgogICAgCQkJbWFwcGluZzogdGhpcy5tYXBwaW5nLAoKICAgIAkJCXJlcGVhdDogWyB0aGlzLnJlcGVhdC54LCB0aGlzLnJlcGVhdC55IF0sCiAgICAJCQlvZmZzZXQ6IFsgdGhpcy5vZmZzZXQueCwgdGhpcy5vZmZzZXQueSBdLAogICAgCQkJY2VudGVyOiBbIHRoaXMuY2VudGVyLngsIHRoaXMuY2VudGVyLnkgXSwKICAgIAkJCXJvdGF0aW9uOiB0aGlzLnJvdGF0aW9uLAoKICAgIAkJCXdyYXA6IFsgdGhpcy53cmFwUywgdGhpcy53cmFwVCBdLAoKICAgIAkJCWZvcm1hdDogdGhpcy5mb3JtYXQsCiAgICAJCQl0eXBlOiB0aGlzLnR5cGUsCiAgICAJCQllbmNvZGluZzogdGhpcy5lbmNvZGluZywKCiAgICAJCQltaW5GaWx0ZXI6IHRoaXMubWluRmlsdGVyLAogICAgCQkJbWFnRmlsdGVyOiB0aGlzLm1hZ0ZpbHRlciwKICAgIAkJCWFuaXNvdHJvcHk6IHRoaXMuYW5pc290cm9weSwKCiAgICAJCQlmbGlwWTogdGhpcy5mbGlwWSwKCiAgICAJCQlwcmVtdWx0aXBseUFscGhhOiB0aGlzLnByZW11bHRpcGx5QWxwaGEsCiAgICAJCQl1bnBhY2tBbGlnbm1lbnQ6IHRoaXMudW5wYWNrQWxpZ25tZW50CgogICAgCQl9OwoKICAgIAkJaWYgKCB0aGlzLmltYWdlICE9PSB1bmRlZmluZWQgKSB7CgogICAgCQkJLy8gVE9ETzogTW92ZSB0byBUSFJFRS5JbWFnZQoKICAgIAkJCXZhciBpbWFnZSA9IHRoaXMuaW1hZ2U7CgogICAgCQkJaWYgKCBpbWFnZS51dWlkID09PSB1bmRlZmluZWQgKSB7CgogICAgCQkJCWltYWdlLnV1aWQgPSBfTWF0aC5nZW5lcmF0ZVVVSUQoKTsgLy8gVUdICgogICAgCQkJfQoKICAgIAkJCWlmICggISBpc1Jvb3RPYmplY3QgJiYgbWV0YS5pbWFnZXNbIGltYWdlLnV1aWQgXSA9PT0gdW5kZWZpbmVkICkgewoKICAgIAkJCQl2YXIgdXJsOwoKICAgIAkJCQlpZiAoIEFycmF5LmlzQXJyYXkoIGltYWdlICkgKSB7CgogICAgCQkJCQkvLyBwcm9jZXNzIGFycmF5IG9mIGltYWdlcyBlLmcuIEN1YmVUZXh0dXJlCgogICAgCQkJCQl1cmwgPSBbXTsKCiAgICAJCQkJCWZvciAoIHZhciBpID0gMCwgbCA9IGltYWdlLmxlbmd0aDsgaSA8IGw7IGkgKysgKSB7CgogICAgCQkJCQkJdXJsLnB1c2goIEltYWdlVXRpbHMuZ2V0RGF0YVVSTCggaW1hZ2VbIGkgXSApICk7CgogICAgCQkJCQl9CgogICAgCQkJCX0gZWxzZSB7CgogICAgCQkJCQkvLyBwcm9jZXNzIHNpbmdsZSBpbWFnZQoKICAgIAkJCQkJdXJsID0gSW1hZ2VVdGlscy5nZXREYXRhVVJMKCBpbWFnZSApOwoKICAgIAkJCQl9CgogICAgCQkJCW1ldGEuaW1hZ2VzWyBpbWFnZS51dWlkIF0gPSB7CiAgICAJCQkJCXV1aWQ6IGltYWdlLnV1aWQsCiAgICAJCQkJCXVybDogdXJsCiAgICAJCQkJfTsKCiAgICAJCQl9CgogICAgCQkJb3V0cHV0LmltYWdlID0gaW1hZ2UudXVpZDsKCiAgICAJCX0KCiAgICAJCWlmICggISBpc1Jvb3RPYmplY3QgKSB7CgogICAgCQkJbWV0YS50ZXh0dXJlc1sgdGhpcy51dWlkIF0gPSBvdXRwdXQ7CgogICAgCQl9CgogICAgCQlyZXR1cm4gb3V0cHV0OwoKICAgIAl9LAoKICAgIAlkaXNwb3NlOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLmRpc3BhdGNoRXZlbnQoIHsgdHlwZTogJ2Rpc3Bvc2UnIH0gKTsKCiAgICAJfSwKCiAgICAJdHJhbnNmb3JtVXY6IGZ1bmN0aW9uICggdXYgKSB7CgogICAgCQlpZiAoIHRoaXMubWFwcGluZyAhPT0gVVZNYXBwaW5nICkgcmV0dXJuIHV2OwoKICAgIAkJdXYuYXBwbHlNYXRyaXgzKCB0aGlzLm1hdHJpeCApOwoKICAgIAkJaWYgKCB1di54IDwgMCB8fCB1di54ID4gMSApIHsKCiAgICAJCQlzd2l0Y2ggKCB0aGlzLndyYXBTICkgewoKICAgIAkJCQljYXNlIFJlcGVhdFdyYXBwaW5nOgoKICAgIAkJCQkJdXYueCA9IHV2LnggLSBNYXRoLmZsb29yKCB1di54ICk7CiAgICAJCQkJCWJyZWFrOwoKICAgIAkJCQljYXNlIENsYW1wVG9FZGdlV3JhcHBpbmc6CgogICAgCQkJCQl1di54ID0gdXYueCA8IDAgPyAwIDogMTsKICAgIAkJCQkJYnJlYWs7CgogICAgCQkJCWNhc2UgTWlycm9yZWRSZXBlYXRXcmFwcGluZzoKCiAgICAJCQkJCWlmICggTWF0aC5hYnMoIE1hdGguZmxvb3IoIHV2LnggKSAlIDIgKSA9PT0gMSApIHsKCiAgICAJCQkJCQl1di54ID0gTWF0aC5jZWlsKCB1di54ICkgLSB1di54OwoKICAgIAkJCQkJfSBlbHNlIHsKCiAgICAJCQkJCQl1di54ID0gdXYueCAtIE1hdGguZmxvb3IoIHV2LnggKTsKCiAgICAJCQkJCX0KICAgIAkJCQkJYnJlYWs7CgogICAgCQkJfQoKICAgIAkJfQoKICAgIAkJaWYgKCB1di55IDwgMCB8fCB1di55ID4gMSApIHsKCiAgICAJCQlzd2l0Y2ggKCB0aGlzLndyYXBUICkgewoKICAgIAkJCQljYXNlIFJlcGVhdFdyYXBwaW5nOgoKICAgIAkJCQkJdXYueSA9IHV2LnkgLSBNYXRoLmZsb29yKCB1di55ICk7CiAgICAJCQkJCWJyZWFrOwoKICAgIAkJCQljYXNlIENsYW1wVG9FZGdlV3JhcHBpbmc6CgogICAgCQkJCQl1di55ID0gdXYueSA8IDAgPyAwIDogMTsKICAgIAkJCQkJYnJlYWs7CgogICAgCQkJCWNhc2UgTWlycm9yZWRSZXBlYXRXcmFwcGluZzoKCiAgICAJCQkJCWlmICggTWF0aC5hYnMoIE1hdGguZmxvb3IoIHV2LnkgKSAlIDIgKSA9PT0gMSApIHsKCiAgICAJCQkJCQl1di55ID0gTWF0aC5jZWlsKCB1di55ICkgLSB1di55OwoKICAgIAkJCQkJfSBlbHNlIHsKCiAgICAJCQkJCQl1di55ID0gdXYueSAtIE1hdGguZmxvb3IoIHV2LnkgKTsKCiAgICAJCQkJCX0KICAgIAkJCQkJYnJlYWs7CgogICAgCQkJfQoKICAgIAkJfQoKICAgIAkJaWYgKCB0aGlzLmZsaXBZICkgewoKICAgIAkJCXV2LnkgPSAxIC0gdXYueTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB1djsKCiAgICAJfQoKICAgIH0gKTsKCiAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkoIFRleHR1cmUucHJvdG90eXBlLCAibmVlZHNVcGRhdGUiLCB7CgogICAgCXNldDogZnVuY3Rpb24gKCB2YWx1ZSApIHsKCiAgICAJCWlmICggdmFsdWUgPT09IHRydWUgKSB0aGlzLnZlcnNpb24gKys7CgogICAgCX0KCiAgICB9ICk7CgogICAgLyoqCiAgICAgKiBAYXV0aG9yIHN1cGVyZWdnYmVydCAvIGh0dHA6Ly93d3cucGF1bGJydW50LmNvLnVrLwogICAgICogQGF1dGhvciBwaGlsb2diIC8gaHR0cDovL2Jsb2cudGhlaml0Lm9yZy8KICAgICAqIEBhdXRob3IgbWlrYWVsIGVtdGluZ2VyIC8gaHR0cDovL2dvbW8uc2UvCiAgICAgKiBAYXV0aG9yIGVncmFldGhlciAvIGh0dHA6Ly9lZ3JhZXRoZXIuY29tLwogICAgICogQGF1dGhvciBXZXN0TGFuZ2xleSAvIGh0dHA6Ly9naXRodWIuY29tL1dlc3RMYW5nbGV5CiAgICAgKi8KCiAgICBmdW5jdGlvbiBWZWN0b3I0KCB4LCB5LCB6LCB3ICkgewoKICAgIAl0aGlzLnggPSB4IHx8IDA7CiAgICAJdGhpcy55ID0geSB8fCAwOwogICAgCXRoaXMueiA9IHogfHwgMDsKICAgIAl0aGlzLncgPSAoIHcgIT09IHVuZGVmaW5lZCApID8gdyA6IDE7CgogICAgfQoKICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0aWVzKCBWZWN0b3I0LnByb3RvdHlwZSwgewoKICAgIAkid2lkdGgiOiB7CgogICAgCQlnZXQ6IGZ1bmN0aW9uICgpIHsKCiAgICAJCQlyZXR1cm4gdGhpcy56OwoKICAgIAkJfSwKCiAgICAJCXNldDogZnVuY3Rpb24gKCB2YWx1ZSApIHsKCiAgICAJCQl0aGlzLnogPSB2YWx1ZTsKCiAgICAJCX0KCiAgICAJfSwKCiAgICAJImhlaWdodCI6IHsKCiAgICAJCWdldDogZnVuY3Rpb24gKCkgewoKICAgIAkJCXJldHVybiB0aGlzLnc7CgogICAgCQl9LAoKICAgIAkJc2V0OiBmdW5jdGlvbiAoIHZhbHVlICkgewoKICAgIAkJCXRoaXMudyA9IHZhbHVlOwoKICAgIAkJfQoKICAgIAl9CgogICAgfSApOwoKICAgIE9iamVjdC5hc3NpZ24oIFZlY3RvcjQucHJvdG90eXBlLCB7CgogICAgCWlzVmVjdG9yNDogdHJ1ZSwKCiAgICAJc2V0OiBmdW5jdGlvbiAoIHgsIHksIHosIHcgKSB7CgogICAgCQl0aGlzLnggPSB4OwogICAgCQl0aGlzLnkgPSB5OwogICAgCQl0aGlzLnogPSB6OwogICAgCQl0aGlzLncgPSB3OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldFNjYWxhcjogZnVuY3Rpb24gKCBzY2FsYXIgKSB7CgogICAgCQl0aGlzLnggPSBzY2FsYXI7CiAgICAJCXRoaXMueSA9IHNjYWxhcjsKICAgIAkJdGhpcy56ID0gc2NhbGFyOwogICAgCQl0aGlzLncgPSBzY2FsYXI7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0WDogZnVuY3Rpb24gKCB4ICkgewoKICAgIAkJdGhpcy54ID0geDsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRZOiBmdW5jdGlvbiAoIHkgKSB7CgogICAgCQl0aGlzLnkgPSB5OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXNldFo6IGZ1bmN0aW9uICggeiApIHsKCiAgICAJCXRoaXMueiA9IHo7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0VzogZnVuY3Rpb24gKCB3ICkgewoKICAgIAkJdGhpcy53ID0gdzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRDb21wb25lbnQ6IGZ1bmN0aW9uICggaW5kZXgsIHZhbHVlICkgewoKICAgIAkJc3dpdGNoICggaW5kZXggKSB7CgogICAgCQkJY2FzZSAwOiB0aGlzLnggPSB2YWx1ZTsgYnJlYWs7CiAgICAJCQljYXNlIDE6IHRoaXMueSA9IHZhbHVlOyBicmVhazsKICAgIAkJCWNhc2UgMjogdGhpcy56ID0gdmFsdWU7IGJyZWFrOwogICAgCQkJY2FzZSAzOiB0aGlzLncgPSB2YWx1ZTsgYnJlYWs7CiAgICAJCQlkZWZhdWx0OiB0aHJvdyBuZXcgRXJyb3IoICdpbmRleCBpcyBvdXQgb2YgcmFuZ2U6ICcgKyBpbmRleCApOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWdldENvbXBvbmVudDogZnVuY3Rpb24gKCBpbmRleCApIHsKCiAgICAJCXN3aXRjaCAoIGluZGV4ICkgewoKICAgIAkJCWNhc2UgMDogcmV0dXJuIHRoaXMueDsKICAgIAkJCWNhc2UgMTogcmV0dXJuIHRoaXMueTsKICAgIAkJCWNhc2UgMjogcmV0dXJuIHRoaXMuejsKICAgIAkJCWNhc2UgMzogcmV0dXJuIHRoaXMudzsKICAgIAkJCWRlZmF1bHQ6IHRocm93IG5ldyBFcnJvciggJ2luZGV4IGlzIG91dCBvZiByYW5nZTogJyArIGluZGV4ICk7CgogICAgCQl9CgogICAgCX0sCgogICAgCWNsb25lOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gbmV3IHRoaXMuY29uc3RydWN0b3IoIHRoaXMueCwgdGhpcy55LCB0aGlzLnosIHRoaXMudyApOwoKICAgIAl9LAoKICAgIAljb3B5OiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQl0aGlzLnggPSB2Lng7CiAgICAJCXRoaXMueSA9IHYueTsKICAgIAkJdGhpcy56ID0gdi56OwogICAgCQl0aGlzLncgPSAoIHYudyAhPT0gdW5kZWZpbmVkICkgPyB2LncgOiAxOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWFkZDogZnVuY3Rpb24gKCB2LCB3ICkgewoKICAgIAkJaWYgKCB3ICE9PSB1bmRlZmluZWQgKSB7CgogICAgCQkJY29uc29sZS53YXJuKCAnVEhSRUUuVmVjdG9yNDogLmFkZCgpIG5vdyBvbmx5IGFjY2VwdHMgb25lIGFyZ3VtZW50LiBVc2UgLmFkZFZlY3RvcnMoIGEsIGIgKSBpbnN0ZWFkLicgKTsKICAgIAkJCXJldHVybiB0aGlzLmFkZFZlY3RvcnMoIHYsIHcgKTsKCiAgICAJCX0KCiAgICAJCXRoaXMueCArPSB2Lng7CiAgICAJCXRoaXMueSArPSB2Lnk7CiAgICAJCXRoaXMueiArPSB2Lno7CiAgICAJCXRoaXMudyArPSB2Lnc7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJYWRkU2NhbGFyOiBmdW5jdGlvbiAoIHMgKSB7CgogICAgCQl0aGlzLnggKz0gczsKICAgIAkJdGhpcy55ICs9IHM7CiAgICAJCXRoaXMueiArPSBzOwogICAgCQl0aGlzLncgKz0gczsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlhZGRWZWN0b3JzOiBmdW5jdGlvbiAoIGEsIGIgKSB7CgogICAgCQl0aGlzLnggPSBhLnggKyBiLng7CiAgICAJCXRoaXMueSA9IGEueSArIGIueTsKICAgIAkJdGhpcy56ID0gYS56ICsgYi56OwogICAgCQl0aGlzLncgPSBhLncgKyBiLnc7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJYWRkU2NhbGVkVmVjdG9yOiBmdW5jdGlvbiAoIHYsIHMgKSB7CgogICAgCQl0aGlzLnggKz0gdi54ICogczsKICAgIAkJdGhpcy55ICs9IHYueSAqIHM7CiAgICAJCXRoaXMueiArPSB2LnogKiBzOwogICAgCQl0aGlzLncgKz0gdi53ICogczsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzdWI6IGZ1bmN0aW9uICggdiwgdyApIHsKCiAgICAJCWlmICggdyAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjQ6IC5zdWIoKSBub3cgb25seSBhY2NlcHRzIG9uZSBhcmd1bWVudC4gVXNlIC5zdWJWZWN0b3JzKCBhLCBiICkgaW5zdGVhZC4nICk7CiAgICAJCQlyZXR1cm4gdGhpcy5zdWJWZWN0b3JzKCB2LCB3ICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggLT0gdi54OwogICAgCQl0aGlzLnkgLT0gdi55OwogICAgCQl0aGlzLnogLT0gdi56OwogICAgCQl0aGlzLncgLT0gdi53OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXN1YlNjYWxhcjogZnVuY3Rpb24gKCBzICkgewoKICAgIAkJdGhpcy54IC09IHM7CiAgICAJCXRoaXMueSAtPSBzOwogICAgCQl0aGlzLnogLT0gczsKICAgIAkJdGhpcy53IC09IHM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc3ViVmVjdG9yczogZnVuY3Rpb24gKCBhLCBiICkgewoKICAgIAkJdGhpcy54ID0gYS54IC0gYi54OwogICAgCQl0aGlzLnkgPSBhLnkgLSBiLnk7CiAgICAJCXRoaXMueiA9IGEueiAtIGIuejsKICAgIAkJdGhpcy53ID0gYS53IC0gYi53OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCW11bHRpcGx5U2NhbGFyOiBmdW5jdGlvbiAoIHNjYWxhciApIHsKCiAgICAJCXRoaXMueCAqPSBzY2FsYXI7CiAgICAJCXRoaXMueSAqPSBzY2FsYXI7CiAgICAJCXRoaXMueiAqPSBzY2FsYXI7CiAgICAJCXRoaXMudyAqPSBzY2FsYXI7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJYXBwbHlNYXRyaXg0OiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQl2YXIgeCA9IHRoaXMueCwgeSA9IHRoaXMueSwgeiA9IHRoaXMueiwgdyA9IHRoaXMudzsKICAgIAkJdmFyIGUgPSBtLmVsZW1lbnRzOwoKICAgIAkJdGhpcy54ID0gZVsgMCBdICogeCArIGVbIDQgXSAqIHkgKyBlWyA4IF0gKiB6ICsgZVsgMTIgXSAqIHc7CiAgICAJCXRoaXMueSA9IGVbIDEgXSAqIHggKyBlWyA1IF0gKiB5ICsgZVsgOSBdICogeiArIGVbIDEzIF0gKiB3OwogICAgCQl0aGlzLnogPSBlWyAyIF0gKiB4ICsgZVsgNiBdICogeSArIGVbIDEwIF0gKiB6ICsgZVsgMTQgXSAqIHc7CiAgICAJCXRoaXMudyA9IGVbIDMgXSAqIHggKyBlWyA3IF0gKiB5ICsgZVsgMTEgXSAqIHogKyBlWyAxNSBdICogdzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkaXZpZGVTY2FsYXI6IGZ1bmN0aW9uICggc2NhbGFyICkgewoKICAgIAkJcmV0dXJuIHRoaXMubXVsdGlwbHlTY2FsYXIoIDEgLyBzY2FsYXIgKTsKCiAgICAJfSwKCiAgICAJc2V0QXhpc0FuZ2xlRnJvbVF1YXRlcm5pb246IGZ1bmN0aW9uICggcSApIHsKCiAgICAJCS8vIGh0dHA6Ly93d3cuZXVjbGlkZWFuc3BhY2UuY29tL21hdGhzL2dlb21ldHJ5L3JvdGF0aW9ucy9jb252ZXJzaW9ucy9xdWF0ZXJuaW9uVG9BbmdsZS9pbmRleC5odG0KCiAgICAJCS8vIHEgaXMgYXNzdW1lZCB0byBiZSBub3JtYWxpemVkCgogICAgCQl0aGlzLncgPSAyICogTWF0aC5hY29zKCBxLncgKTsKCiAgICAJCXZhciBzID0gTWF0aC5zcXJ0KCAxIC0gcS53ICogcS53ICk7CgogICAgCQlpZiAoIHMgPCAwLjAwMDEgKSB7CgogICAgCQkJdGhpcy54ID0gMTsKICAgIAkJCXRoaXMueSA9IDA7CiAgICAJCQl0aGlzLnogPSAwOwoKICAgIAkJfSBlbHNlIHsKCiAgICAJCQl0aGlzLnggPSBxLnggLyBzOwogICAgCQkJdGhpcy55ID0gcS55IC8gczsKICAgIAkJCXRoaXMueiA9IHEueiAvIHM7CgogICAgCQl9CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2V0QXhpc0FuZ2xlRnJvbVJvdGF0aW9uTWF0cml4OiBmdW5jdGlvbiAoIG0gKSB7CgogICAgCQkvLyBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9nZW9tZXRyeS9yb3RhdGlvbnMvY29udmVyc2lvbnMvbWF0cml4VG9BbmdsZS9pbmRleC5odG0KCiAgICAJCS8vIGFzc3VtZXMgdGhlIHVwcGVyIDN4MyBvZiBtIGlzIGEgcHVyZSByb3RhdGlvbiBtYXRyaXggKGkuZSwgdW5zY2FsZWQpCgogICAgCQl2YXIgYW5nbGUsIHgsIHksIHosCQkvLyB2YXJpYWJsZXMgZm9yIHJlc3VsdAogICAgCQkJZXBzaWxvbiA9IDAuMDEsCQkvLyBtYXJnaW4gdG8gYWxsb3cgZm9yIHJvdW5kaW5nIGVycm9ycwogICAgCQkJZXBzaWxvbjIgPSAwLjEsCQkvLyBtYXJnaW4gdG8gZGlzdGluZ3Vpc2ggYmV0d2VlbiAwIGFuZCAxODAgZGVncmVlcwoKICAgIAkJCXRlID0gbS5lbGVtZW50cywKCiAgICAJCQltMTEgPSB0ZVsgMCBdLCBtMTIgPSB0ZVsgNCBdLCBtMTMgPSB0ZVsgOCBdLAogICAgCQkJbTIxID0gdGVbIDEgXSwgbTIyID0gdGVbIDUgXSwgbTIzID0gdGVbIDkgXSwKICAgIAkJCW0zMSA9IHRlWyAyIF0sIG0zMiA9IHRlWyA2IF0sIG0zMyA9IHRlWyAxMCBdOwoKICAgIAkJaWYgKCAoIE1hdGguYWJzKCBtMTIgLSBtMjEgKSA8IGVwc2lsb24gKSAmJgogICAgCQkgICAgICggTWF0aC5hYnMoIG0xMyAtIG0zMSApIDwgZXBzaWxvbiApICYmCiAgICAJCSAgICAgKCBNYXRoLmFicyggbTIzIC0gbTMyICkgPCBlcHNpbG9uICkgKSB7CgogICAgCQkJLy8gc2luZ3VsYXJpdHkgZm91bmQKICAgIAkJCS8vIGZpcnN0IGNoZWNrIGZvciBpZGVudGl0eSBtYXRyaXggd2hpY2ggbXVzdCBoYXZlICsxIGZvciBhbGwgdGVybXMKICAgIAkJCS8vIGluIGxlYWRpbmcgZGlhZ29uYWwgYW5kIHplcm8gaW4gb3RoZXIgdGVybXMKCiAgICAJCQlpZiAoICggTWF0aC5hYnMoIG0xMiArIG0yMSApIDwgZXBzaWxvbjIgKSAmJgogICAgCQkJICAgICAoIE1hdGguYWJzKCBtMTMgKyBtMzEgKSA8IGVwc2lsb24yICkgJiYKICAgIAkJCSAgICAgKCBNYXRoLmFicyggbTIzICsgbTMyICkgPCBlcHNpbG9uMiApICYmCiAgICAJCQkgICAgICggTWF0aC5hYnMoIG0xMSArIG0yMiArIG0zMyAtIDMgKSA8IGVwc2lsb24yICkgKSB7CgogICAgCQkJCS8vIHRoaXMgc2luZ3VsYXJpdHkgaXMgaWRlbnRpdHkgbWF0cml4IHNvIGFuZ2xlID0gMAoKICAgIAkJCQl0aGlzLnNldCggMSwgMCwgMCwgMCApOwoKICAgIAkJCQlyZXR1cm4gdGhpczsgLy8gemVybyBhbmdsZSwgYXJiaXRyYXJ5IGF4aXMKCiAgICAJCQl9CgogICAgCQkJLy8gb3RoZXJ3aXNlIHRoaXMgc2luZ3VsYXJpdHkgaXMgYW5nbGUgPSAxODAKCiAgICAJCQlhbmdsZSA9IE1hdGguUEk7CgogICAgCQkJdmFyIHh4ID0gKCBtMTEgKyAxICkgLyAyOwogICAgCQkJdmFyIHl5ID0gKCBtMjIgKyAxICkgLyAyOwogICAgCQkJdmFyIHp6ID0gKCBtMzMgKyAxICkgLyAyOwogICAgCQkJdmFyIHh5ID0gKCBtMTIgKyBtMjEgKSAvIDQ7CiAgICAJCQl2YXIgeHogPSAoIG0xMyArIG0zMSApIC8gNDsKICAgIAkJCXZhciB5eiA9ICggbTIzICsgbTMyICkgLyA0OwoKICAgIAkJCWlmICggKCB4eCA+IHl5ICkgJiYgKCB4eCA+IHp6ICkgKSB7CgogICAgCQkJCS8vIG0xMSBpcyB0aGUgbGFyZ2VzdCBkaWFnb25hbCB0ZXJtCgogICAgCQkJCWlmICggeHggPCBlcHNpbG9uICkgewoKICAgIAkJCQkJeCA9IDA7CiAgICAJCQkJCXkgPSAwLjcwNzEwNjc4MTsKICAgIAkJCQkJeiA9IDAuNzA3MTA2NzgxOwoKICAgIAkJCQl9IGVsc2UgewoKICAgIAkJCQkJeCA9IE1hdGguc3FydCggeHggKTsKICAgIAkJCQkJeSA9IHh5IC8geDsKICAgIAkJCQkJeiA9IHh6IC8geDsKCiAgICAJCQkJfQoKICAgIAkJCX0gZWxzZSBpZiAoIHl5ID4genogKSB7CgogICAgCQkJCS8vIG0yMiBpcyB0aGUgbGFyZ2VzdCBkaWFnb25hbCB0ZXJtCgogICAgCQkJCWlmICggeXkgPCBlcHNpbG9uICkgewoKICAgIAkJCQkJeCA9IDAuNzA3MTA2NzgxOwogICAgCQkJCQl5ID0gMDsKICAgIAkJCQkJeiA9IDAuNzA3MTA2NzgxOwoKICAgIAkJCQl9IGVsc2UgewoKICAgIAkJCQkJeSA9IE1hdGguc3FydCggeXkgKTsKICAgIAkJCQkJeCA9IHh5IC8geTsKICAgIAkJCQkJeiA9IHl6IC8geTsKCiAgICAJCQkJfQoKICAgIAkJCX0gZWxzZSB7CgogICAgCQkJCS8vIG0zMyBpcyB0aGUgbGFyZ2VzdCBkaWFnb25hbCB0ZXJtIHNvIGJhc2UgcmVzdWx0IG9uIHRoaXMKCiAgICAJCQkJaWYgKCB6eiA8IGVwc2lsb24gKSB7CgogICAgCQkJCQl4ID0gMC43MDcxMDY3ODE7CiAgICAJCQkJCXkgPSAwLjcwNzEwNjc4MTsKICAgIAkJCQkJeiA9IDA7CgogICAgCQkJCX0gZWxzZSB7CgogICAgCQkJCQl6ID0gTWF0aC5zcXJ0KCB6eiApOwogICAgCQkJCQl4ID0geHogLyB6OwogICAgCQkJCQl5ID0geXogLyB6OwoKICAgIAkJCQl9CgogICAgCQkJfQoKICAgIAkJCXRoaXMuc2V0KCB4LCB5LCB6LCBhbmdsZSApOwoKICAgIAkJCXJldHVybiB0aGlzOyAvLyByZXR1cm4gMTgwIGRlZyByb3RhdGlvbgoKICAgIAkJfQoKICAgIAkJLy8gYXMgd2UgaGF2ZSByZWFjaGVkIGhlcmUgdGhlcmUgYXJlIG5vIHNpbmd1bGFyaXRpZXMgc28gd2UgY2FuIGhhbmRsZSBub3JtYWxseQoKICAgIAkJdmFyIHMgPSBNYXRoLnNxcnQoICggbTMyIC0gbTIzICkgKiAoIG0zMiAtIG0yMyApICsKICAgIAkJICAgICAgICAgICAgICAgICAgICggbTEzIC0gbTMxICkgKiAoIG0xMyAtIG0zMSApICsKICAgIAkJICAgICAgICAgICAgICAgICAgICggbTIxIC0gbTEyICkgKiAoIG0yMSAtIG0xMiApICk7IC8vIHVzZWQgdG8gbm9ybWFsaXplCgogICAgCQlpZiAoIE1hdGguYWJzKCBzICkgPCAwLjAwMSApIHMgPSAxOwoKICAgIAkJLy8gcHJldmVudCBkaXZpZGUgYnkgemVybywgc2hvdWxkIG5vdCBoYXBwZW4gaWYgbWF0cml4IGlzIG9ydGhvZ29uYWwgYW5kIHNob3VsZCBiZQogICAgCQkvLyBjYXVnaHQgYnkgc2luZ3VsYXJpdHkgdGVzdCBhYm92ZSwgYnV0IEkndmUgbGVmdCBpdCBpbiBqdXN0IGluIGNhc2UKCiAgICAJCXRoaXMueCA9ICggbTMyIC0gbTIzICkgLyBzOwogICAgCQl0aGlzLnkgPSAoIG0xMyAtIG0zMSApIC8gczsKICAgIAkJdGhpcy56ID0gKCBtMjEgLSBtMTIgKSAvIHM7CiAgICAJCXRoaXMudyA9IE1hdGguYWNvcyggKCBtMTEgKyBtMjIgKyBtMzMgLSAxICkgLyAyICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWluOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLm1pbiggdGhpcy54LCB2LnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5taW4oIHRoaXMueSwgdi55ICk7CiAgICAJCXRoaXMueiA9IE1hdGgubWluKCB0aGlzLnosIHYueiApOwogICAgCQl0aGlzLncgPSBNYXRoLm1pbiggdGhpcy53LCB2LncgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltYXg6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXRoaXMueCA9IE1hdGgubWF4KCB0aGlzLngsIHYueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggdGhpcy55LCB2LnkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5tYXgoIHRoaXMueiwgdi56ICk7CiAgICAJCXRoaXMudyA9IE1hdGgubWF4KCB0aGlzLncsIHYudyApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsYW1wOiBmdW5jdGlvbiAoIG1pbiwgbWF4ICkgewoKICAgIAkJLy8gYXNzdW1lcyBtaW4gPCBtYXgsIGNvbXBvbmVudHdpc2UKCiAgICAJCXRoaXMueCA9IE1hdGgubWF4KCBtaW4ueCwgTWF0aC5taW4oIG1heC54LCB0aGlzLnggKSApOwogICAgCQl0aGlzLnkgPSBNYXRoLm1heCggbWluLnksIE1hdGgubWluKCBtYXgueSwgdGhpcy55ICkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5tYXgoIG1pbi56LCBNYXRoLm1pbiggbWF4LnosIHRoaXMueiApICk7CiAgICAJCXRoaXMudyA9IE1hdGgubWF4KCBtaW4udywgTWF0aC5taW4oIG1heC53LCB0aGlzLncgKSApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsYW1wU2NhbGFyOiBmdW5jdGlvbiAoIG1pblZhbCwgbWF4VmFsICkgewoKICAgIAkJdGhpcy54ID0gTWF0aC5tYXgoIG1pblZhbCwgTWF0aC5taW4oIG1heFZhbCwgdGhpcy54ICkgKTsKICAgIAkJdGhpcy55ID0gTWF0aC5tYXgoIG1pblZhbCwgTWF0aC5taW4oIG1heFZhbCwgdGhpcy55ICkgKTsKICAgIAkJdGhpcy56ID0gTWF0aC5tYXgoIG1pblZhbCwgTWF0aC5taW4oIG1heFZhbCwgdGhpcy56ICkgKTsKICAgIAkJdGhpcy53ID0gTWF0aC5tYXgoIG1pblZhbCwgTWF0aC5taW4oIG1heFZhbCwgdGhpcy53ICkgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAljbGFtcExlbmd0aDogZnVuY3Rpb24gKCBtaW4sIG1heCApIHsKCiAgICAJCXZhciBsZW5ndGggPSB0aGlzLmxlbmd0aCgpOwoKICAgIAkJcmV0dXJuIHRoaXMuZGl2aWRlU2NhbGFyKCBsZW5ndGggfHwgMSApLm11bHRpcGx5U2NhbGFyKCBNYXRoLm1heCggbWluLCBNYXRoLm1pbiggbWF4LCBsZW5ndGggKSApICk7CgogICAgCX0sCgogICAgCWZsb29yOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLmZsb29yKCB0aGlzLnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5mbG9vciggdGhpcy55ICk7CiAgICAJCXRoaXMueiA9IE1hdGguZmxvb3IoIHRoaXMueiApOwogICAgCQl0aGlzLncgPSBNYXRoLmZsb29yKCB0aGlzLncgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAljZWlsOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLmNlaWwoIHRoaXMueCApOwogICAgCQl0aGlzLnkgPSBNYXRoLmNlaWwoIHRoaXMueSApOwogICAgCQl0aGlzLnogPSBNYXRoLmNlaWwoIHRoaXMueiApOwogICAgCQl0aGlzLncgPSBNYXRoLmNlaWwoIHRoaXMudyApOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCXJvdW5kOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSBNYXRoLnJvdW5kKCB0aGlzLnggKTsKICAgIAkJdGhpcy55ID0gTWF0aC5yb3VuZCggdGhpcy55ICk7CiAgICAJCXRoaXMueiA9IE1hdGgucm91bmQoIHRoaXMueiApOwogICAgCQl0aGlzLncgPSBNYXRoLnJvdW5kKCB0aGlzLncgKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlyb3VuZFRvWmVybzogZnVuY3Rpb24gKCkgewoKICAgIAkJdGhpcy54ID0gKCB0aGlzLnggPCAwICkgPyBNYXRoLmNlaWwoIHRoaXMueCApIDogTWF0aC5mbG9vciggdGhpcy54ICk7CiAgICAJCXRoaXMueSA9ICggdGhpcy55IDwgMCApID8gTWF0aC5jZWlsKCB0aGlzLnkgKSA6IE1hdGguZmxvb3IoIHRoaXMueSApOwogICAgCQl0aGlzLnogPSAoIHRoaXMueiA8IDAgKSA/IE1hdGguY2VpbCggdGhpcy56ICkgOiBNYXRoLmZsb29yKCB0aGlzLnogKTsKICAgIAkJdGhpcy53ID0gKCB0aGlzLncgPCAwICkgPyBNYXRoLmNlaWwoIHRoaXMudyApIDogTWF0aC5mbG9vciggdGhpcy53ICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbmVnYXRlOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnggPSAtIHRoaXMueDsKICAgIAkJdGhpcy55ID0gLSB0aGlzLnk7CiAgICAJCXRoaXMueiA9IC0gdGhpcy56OwogICAgCQl0aGlzLncgPSAtIHRoaXMudzsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkb3Q6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXJldHVybiB0aGlzLnggKiB2LnggKyB0aGlzLnkgKiB2LnkgKyB0aGlzLnogKiB2LnogKyB0aGlzLncgKiB2Lnc7CgogICAgCX0sCgogICAgCWxlbmd0aFNxOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gdGhpcy54ICogdGhpcy54ICsgdGhpcy55ICogdGhpcy55ICsgdGhpcy56ICogdGhpcy56ICsgdGhpcy53ICogdGhpcy53OwoKICAgIAl9LAoKICAgIAlsZW5ndGg6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBNYXRoLnNxcnQoIHRoaXMueCAqIHRoaXMueCArIHRoaXMueSAqIHRoaXMueSArIHRoaXMueiAqIHRoaXMueiArIHRoaXMudyAqIHRoaXMudyApOwoKICAgIAl9LAoKICAgIAltYW5oYXR0YW5MZW5ndGg6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXJldHVybiBNYXRoLmFicyggdGhpcy54ICkgKyBNYXRoLmFicyggdGhpcy55ICkgKyBNYXRoLmFicyggdGhpcy56ICkgKyBNYXRoLmFicyggdGhpcy53ICk7CgogICAgCX0sCgogICAgCW5vcm1hbGl6ZTogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIHRoaXMuZGl2aWRlU2NhbGFyKCB0aGlzLmxlbmd0aCgpIHx8IDEgKTsKCiAgICAJfSwKCiAgICAJc2V0TGVuZ3RoOiBmdW5jdGlvbiAoIGxlbmd0aCApIHsKCiAgICAJCXJldHVybiB0aGlzLm5vcm1hbGl6ZSgpLm11bHRpcGx5U2NhbGFyKCBsZW5ndGggKTsKCiAgICAJfSwKCiAgICAJbGVycDogZnVuY3Rpb24gKCB2LCBhbHBoYSApIHsKCiAgICAJCXRoaXMueCArPSAoIHYueCAtIHRoaXMueCApICogYWxwaGE7CiAgICAJCXRoaXMueSArPSAoIHYueSAtIHRoaXMueSApICogYWxwaGE7CiAgICAJCXRoaXMueiArPSAoIHYueiAtIHRoaXMueiApICogYWxwaGE7CiAgICAJCXRoaXMudyArPSAoIHYudyAtIHRoaXMudyApICogYWxwaGE7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbGVycFZlY3RvcnM6IGZ1bmN0aW9uICggdjEsIHYyLCBhbHBoYSApIHsKCiAgICAJCXJldHVybiB0aGlzLnN1YlZlY3RvcnMoIHYyLCB2MSApLm11bHRpcGx5U2NhbGFyKCBhbHBoYSApLmFkZCggdjEgKTsKCiAgICAJfSwKCiAgICAJZXF1YWxzOiBmdW5jdGlvbiAoIHYgKSB7CgogICAgCQlyZXR1cm4gKCAoIHYueCA9PT0gdGhpcy54ICkgJiYgKCB2LnkgPT09IHRoaXMueSApICYmICggdi56ID09PSB0aGlzLnogKSAmJiAoIHYudyA9PT0gdGhpcy53ICkgKTsKCiAgICAJfSwKCiAgICAJZnJvbUFycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCXRoaXMueCA9IGFycmF5WyBvZmZzZXQgXTsKICAgIAkJdGhpcy55ID0gYXJyYXlbIG9mZnNldCArIDEgXTsKICAgIAkJdGhpcy56ID0gYXJyYXlbIG9mZnNldCArIDIgXTsKICAgIAkJdGhpcy53ID0gYXJyYXlbIG9mZnNldCArIDMgXTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAl0b0FycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIGFycmF5ID09PSB1bmRlZmluZWQgKSBhcnJheSA9IFtdOwogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCWFycmF5WyBvZmZzZXQgXSA9IHRoaXMueDsKICAgIAkJYXJyYXlbIG9mZnNldCArIDEgXSA9IHRoaXMueTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDIgXSA9IHRoaXMuejsKICAgIAkJYXJyYXlbIG9mZnNldCArIDMgXSA9IHRoaXMudzsKCiAgICAJCXJldHVybiBhcnJheTsKCiAgICAJfSwKCiAgICAJZnJvbUJ1ZmZlckF0dHJpYnV0ZTogZnVuY3Rpb24gKCBhdHRyaWJ1dGUsIGluZGV4LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIG9mZnNldCAhPT0gdW5kZWZpbmVkICkgewoKICAgIAkJCWNvbnNvbGUud2FybiggJ1RIUkVFLlZlY3RvcjQ6IG9mZnNldCBoYXMgYmVlbiByZW1vdmVkIGZyb20gLmZyb21CdWZmZXJBdHRyaWJ1dGUoKS4nICk7CgogICAgCQl9CgogICAgCQl0aGlzLnggPSBhdHRyaWJ1dGUuZ2V0WCggaW5kZXggKTsKICAgIAkJdGhpcy55ID0gYXR0cmlidXRlLmdldFkoIGluZGV4ICk7CiAgICAJCXRoaXMueiA9IGF0dHJpYnV0ZS5nZXRaKCBpbmRleCApOwogICAgCQl0aGlzLncgPSBhdHRyaWJ1dGUuZ2V0VyggaW5kZXggKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9CgogICAgfSApOwoKICAgIC8qKgogICAgICogQGF1dGhvciBzemltZWsgLyBodHRwczovL2dpdGh1Yi5jb20vc3ppbWVrLwogICAgICogQGF1dGhvciBhbHRlcmVkcSAvIGh0dHA6Ly9hbHRlcmVkcXVhbGlhLmNvbS8KICAgICAqIEBhdXRob3IgTWFyaXVzIEtpbnRlbCAvIGh0dHBzOi8vZ2l0aHViLmNvbS9raW50ZWwKICAgICAqLwoKICAgIC8qCiAgICAgSW4gb3B0aW9ucywgd2UgY2FuIHNwZWNpZnk6CiAgICAgKiBUZXh0dXJlIHBhcmFtZXRlcnMgZm9yIGFuIGF1dG8tZ2VuZXJhdGVkIHRhcmdldCB0ZXh0dXJlCiAgICAgKiBkZXB0aEJ1ZmZlci9zdGVuY2lsQnVmZmVyOiBCb29sZWFucyB0byBpbmRpY2F0ZSBpZiB3ZSBzaG91bGQgZ2VuZXJhdGUgdGhlc2UgYnVmZmVycwogICAgKi8KICAgIGZ1bmN0aW9uIFdlYkdMUmVuZGVyVGFyZ2V0KCB3aWR0aCwgaGVpZ2h0LCBvcHRpb25zICkgewoKICAgIAl0aGlzLndpZHRoID0gd2lkdGg7CiAgICAJdGhpcy5oZWlnaHQgPSBoZWlnaHQ7CgogICAgCXRoaXMuc2Npc3NvciA9IG5ldyBWZWN0b3I0KCAwLCAwLCB3aWR0aCwgaGVpZ2h0ICk7CiAgICAJdGhpcy5zY2lzc29yVGVzdCA9IGZhbHNlOwoKICAgIAl0aGlzLnZpZXdwb3J0ID0gbmV3IFZlY3RvcjQoIDAsIDAsIHdpZHRoLCBoZWlnaHQgKTsKCiAgICAJb3B0aW9ucyA9IG9wdGlvbnMgfHwge307CgogICAgCXRoaXMudGV4dHVyZSA9IG5ldyBUZXh0dXJlKCB1bmRlZmluZWQsIHVuZGVmaW5lZCwgb3B0aW9ucy53cmFwUywgb3B0aW9ucy53cmFwVCwgb3B0aW9ucy5tYWdGaWx0ZXIsIG9wdGlvbnMubWluRmlsdGVyLCBvcHRpb25zLmZvcm1hdCwgb3B0aW9ucy50eXBlLCBvcHRpb25zLmFuaXNvdHJvcHksIG9wdGlvbnMuZW5jb2RpbmcgKTsKCiAgICAJdGhpcy50ZXh0dXJlLmltYWdlID0ge307CiAgICAJdGhpcy50ZXh0dXJlLmltYWdlLndpZHRoID0gd2lkdGg7CiAgICAJdGhpcy50ZXh0dXJlLmltYWdlLmhlaWdodCA9IGhlaWdodDsKCiAgICAJdGhpcy50ZXh0dXJlLmdlbmVyYXRlTWlwbWFwcyA9IG9wdGlvbnMuZ2VuZXJhdGVNaXBtYXBzICE9PSB1bmRlZmluZWQgPyBvcHRpb25zLmdlbmVyYXRlTWlwbWFwcyA6IGZhbHNlOwogICAgCXRoaXMudGV4dHVyZS5taW5GaWx0ZXIgPSBvcHRpb25zLm1pbkZpbHRlciAhPT0gdW5kZWZpbmVkID8gb3B0aW9ucy5taW5GaWx0ZXIgOiBMaW5lYXJGaWx0ZXI7CgogICAgCXRoaXMuZGVwdGhCdWZmZXIgPSBvcHRpb25zLmRlcHRoQnVmZmVyICE9PSB1bmRlZmluZWQgPyBvcHRpb25zLmRlcHRoQnVmZmVyIDogdHJ1ZTsKICAgIAl0aGlzLnN0ZW5jaWxCdWZmZXIgPSBvcHRpb25zLnN0ZW5jaWxCdWZmZXIgIT09IHVuZGVmaW5lZCA/IG9wdGlvbnMuc3RlbmNpbEJ1ZmZlciA6IHRydWU7CiAgICAJdGhpcy5kZXB0aFRleHR1cmUgPSBvcHRpb25zLmRlcHRoVGV4dHVyZSAhPT0gdW5kZWZpbmVkID8gb3B0aW9ucy5kZXB0aFRleHR1cmUgOiBudWxsOwoKICAgIH0KCiAgICBXZWJHTFJlbmRlclRhcmdldC5wcm90b3R5cGUgPSBPYmplY3QuYXNzaWduKCBPYmplY3QuY3JlYXRlKCBFdmVudERpc3BhdGNoZXIucHJvdG90eXBlICksIHsKCiAgICAJY29uc3RydWN0b3I6IFdlYkdMUmVuZGVyVGFyZ2V0LAoKICAgIAlpc1dlYkdMUmVuZGVyVGFyZ2V0OiB0cnVlLAoKICAgIAlzZXRTaXplOiBmdW5jdGlvbiAoIHdpZHRoLCBoZWlnaHQgKSB7CgogICAgCQlpZiAoIHRoaXMud2lkdGggIT09IHdpZHRoIHx8IHRoaXMuaGVpZ2h0ICE9PSBoZWlnaHQgKSB7CgogICAgCQkJdGhpcy53aWR0aCA9IHdpZHRoOwogICAgCQkJdGhpcy5oZWlnaHQgPSBoZWlnaHQ7CgogICAgCQkJdGhpcy50ZXh0dXJlLmltYWdlLndpZHRoID0gd2lkdGg7CiAgICAJCQl0aGlzLnRleHR1cmUuaW1hZ2UuaGVpZ2h0ID0gaGVpZ2h0OwoKICAgIAkJCXRoaXMuZGlzcG9zZSgpOwoKICAgIAkJfQoKICAgIAkJdGhpcy52aWV3cG9ydC5zZXQoIDAsIDAsIHdpZHRoLCBoZWlnaHQgKTsKICAgIAkJdGhpcy5zY2lzc29yLnNldCggMCwgMCwgd2lkdGgsIGhlaWdodCApOwoKICAgIAl9LAoKICAgIAljbG9uZTogZnVuY3Rpb24gKCkgewoKICAgIAkJcmV0dXJuIG5ldyB0aGlzLmNvbnN0cnVjdG9yKCkuY29weSggdGhpcyApOwoKICAgIAl9LAoKICAgIAljb3B5OiBmdW5jdGlvbiAoIHNvdXJjZSApIHsKCiAgICAJCXRoaXMud2lkdGggPSBzb3VyY2Uud2lkdGg7CiAgICAJCXRoaXMuaGVpZ2h0ID0gc291cmNlLmhlaWdodDsKCiAgICAJCXRoaXMudmlld3BvcnQuY29weSggc291cmNlLnZpZXdwb3J0ICk7CgogICAgCQl0aGlzLnRleHR1cmUgPSBzb3VyY2UudGV4dHVyZS5jbG9uZSgpOwoKICAgIAkJdGhpcy5kZXB0aEJ1ZmZlciA9IHNvdXJjZS5kZXB0aEJ1ZmZlcjsKICAgIAkJdGhpcy5zdGVuY2lsQnVmZmVyID0gc291cmNlLnN0ZW5jaWxCdWZmZXI7CiAgICAJCXRoaXMuZGVwdGhUZXh0dXJlID0gc291cmNlLmRlcHRoVGV4dHVyZTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkaXNwb3NlOiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLmRpc3BhdGNoRXZlbnQoIHsgdHlwZTogJ2Rpc3Bvc2UnIH0gKTsKCiAgICAJfQoKICAgIH0gKTsKCiAgICAvKioKICAgICAqIEBhdXRob3IgTXVnZW44NyAvIGh0dHBzOi8vZ2l0aHViLmNvbS9NdWdlbjg3CiAgICAgKiBAYXV0aG9yIE1hdHQgRGVzTGF1cmllcnMgLyBAbWF0dGRlc2wKICAgICAqLwoKICAgIGZ1bmN0aW9uIFdlYkdMTXVsdGlzYW1wbGVSZW5kZXJUYXJnZXQoIHdpZHRoLCBoZWlnaHQsIG9wdGlvbnMgKSB7CgogICAgCVdlYkdMUmVuZGVyVGFyZ2V0LmNhbGwoIHRoaXMsIHdpZHRoLCBoZWlnaHQsIG9wdGlvbnMgKTsKCiAgICAJdGhpcy5zYW1wbGVzID0gNDsKCiAgICB9CgogICAgV2ViR0xNdWx0aXNhbXBsZVJlbmRlclRhcmdldC5wcm90b3R5cGUgPSBPYmplY3QuYXNzaWduKCBPYmplY3QuY3JlYXRlKCBXZWJHTFJlbmRlclRhcmdldC5wcm90b3R5cGUgKSwgewoKICAgIAljb25zdHJ1Y3RvcjogV2ViR0xNdWx0aXNhbXBsZVJlbmRlclRhcmdldCwKCiAgICAJaXNXZWJHTE11bHRpc2FtcGxlUmVuZGVyVGFyZ2V0OiB0cnVlLAoKICAgIAljb3B5OiBmdW5jdGlvbiAoIHNvdXJjZSApIHsKCiAgICAJCVdlYkdMUmVuZGVyVGFyZ2V0LnByb3RvdHlwZS5jb3B5LmNhbGwoIHRoaXMsIHNvdXJjZSApOwoKICAgIAkJdGhpcy5zYW1wbGVzID0gc291cmNlLnNhbXBsZXM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfQoKICAgIH0gKTsKCiAgICB2YXIgX3YxID0gbmV3IFZlY3RvcjMoKTsKICAgIHZhciBfbTEgPSBuZXcgTWF0cml4NCgpOwogICAgdmFyIF96ZXJvID0gbmV3IFZlY3RvcjMoIDAsIDAsIDAgKTsKICAgIHZhciBfb25lID0gbmV3IFZlY3RvcjMoIDEsIDEsIDEgKTsKICAgIHZhciBfeCA9IG5ldyBWZWN0b3IzKCk7CiAgICB2YXIgX3kgPSBuZXcgVmVjdG9yMygpOwogICAgdmFyIF96ID0gbmV3IFZlY3RvcjMoKTsKCiAgICAvKioKICAgICAqIEBhdXRob3IgbXJkb29iIC8gaHR0cDovL21yZG9vYi5jb20vCiAgICAgKiBAYXV0aG9yIHN1cGVyZWdnYmVydCAvIGh0dHA6Ly93d3cucGF1bGJydW50LmNvLnVrLwogICAgICogQGF1dGhvciBwaGlsb2diIC8gaHR0cDovL2Jsb2cudGhlaml0Lm9yZy8KICAgICAqIEBhdXRob3Igam9yZGlfcm9zIC8gaHR0cDovL3BsYXR0c29mdC5jb20KICAgICAqIEBhdXRob3IgRDFwbG8xZCAvIGh0dHA6Ly9naXRodWIuY29tL0QxcGxvMWQKICAgICAqIEBhdXRob3IgYWx0ZXJlZHEgLyBodHRwOi8vYWx0ZXJlZHF1YWxpYS5jb20vCiAgICAgKiBAYXV0aG9yIG1pa2FlbCBlbXRpbmdlciAvIGh0dHA6Ly9nb21vLnNlLwogICAgICogQGF1dGhvciB0aW1rbmlwIC8gaHR0cDovL3d3dy5mbG9vcnBsYW5uZXIuY29tLwogICAgICogQGF1dGhvciBiaG91c3RvbiAvIGh0dHA6Ly9jbGFyYS5pbwogICAgICogQGF1dGhvciBXZXN0TGFuZ2xleSAvIGh0dHA6Ly9naXRodWIuY29tL1dlc3RMYW5nbGV5CiAgICAgKi8KCiAgICBmdW5jdGlvbiBNYXRyaXg0KCkgewoKICAgIAl0aGlzLmVsZW1lbnRzID0gWwoKICAgIAkJMSwgMCwgMCwgMCwKICAgIAkJMCwgMSwgMCwgMCwKICAgIAkJMCwgMCwgMSwgMCwKICAgIAkJMCwgMCwgMCwgMQoKICAgIAldOwoKICAgIAlpZiAoIGFyZ3VtZW50cy5sZW5ndGggPiAwICkgewoKICAgIAkJY29uc29sZS5lcnJvciggJ1RIUkVFLk1hdHJpeDQ6IHRoZSBjb25zdHJ1Y3RvciBubyBsb25nZXIgcmVhZHMgYXJndW1lbnRzLiB1c2UgLnNldCgpIGluc3RlYWQuJyApOwoKICAgIAl9CgogICAgfQoKICAgIE9iamVjdC5hc3NpZ24oIE1hdHJpeDQucHJvdG90eXBlLCB7CgogICAgCWlzTWF0cml4NDogdHJ1ZSwKCiAgICAJc2V0OiBmdW5jdGlvbiAoIG4xMSwgbjEyLCBuMTMsIG4xNCwgbjIxLCBuMjIsIG4yMywgbjI0LCBuMzEsIG4zMiwgbjMzLCBuMzQsIG40MSwgbjQyLCBuNDMsIG40NCApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl0ZVsgMCBdID0gbjExOyB0ZVsgNCBdID0gbjEyOyB0ZVsgOCBdID0gbjEzOyB0ZVsgMTIgXSA9IG4xNDsKICAgIAkJdGVbIDEgXSA9IG4yMTsgdGVbIDUgXSA9IG4yMjsgdGVbIDkgXSA9IG4yMzsgdGVbIDEzIF0gPSBuMjQ7CiAgICAJCXRlWyAyIF0gPSBuMzE7IHRlWyA2IF0gPSBuMzI7IHRlWyAxMCBdID0gbjMzOyB0ZVsgMTQgXSA9IG4zNDsKICAgIAkJdGVbIDMgXSA9IG40MTsgdGVbIDcgXSA9IG40MjsgdGVbIDExIF0gPSBuNDM7IHRlWyAxNSBdID0gbjQ0OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWlkZW50aXR5OiBmdW5jdGlvbiAoKSB7CgogICAgCQl0aGlzLnNldCgKCiAgICAJCQkxLCAwLCAwLCAwLAogICAgCQkJMCwgMSwgMCwgMCwKICAgIAkJCTAsIDAsIDEsIDAsCiAgICAJCQkwLCAwLCAwLCAxCgogICAgCQkpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNsb25lOiBmdW5jdGlvbiAoKSB7CgogICAgCQlyZXR1cm4gbmV3IE1hdHJpeDQoKS5mcm9tQXJyYXkoIHRoaXMuZWxlbWVudHMgKTsKCiAgICAJfSwKCiAgICAJY29weTogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKICAgIAkJdmFyIG1lID0gbS5lbGVtZW50czsKCiAgICAJCXRlWyAwIF0gPSBtZVsgMCBdOyB0ZVsgMSBdID0gbWVbIDEgXTsgdGVbIDIgXSA9IG1lWyAyIF07IHRlWyAzIF0gPSBtZVsgMyBdOwogICAgCQl0ZVsgNCBdID0gbWVbIDQgXTsgdGVbIDUgXSA9IG1lWyA1IF07IHRlWyA2IF0gPSBtZVsgNiBdOyB0ZVsgNyBdID0gbWVbIDcgXTsKICAgIAkJdGVbIDggXSA9IG1lWyA4IF07IHRlWyA5IF0gPSBtZVsgOSBdOyB0ZVsgMTAgXSA9IG1lWyAxMCBdOyB0ZVsgMTEgXSA9IG1lWyAxMSBdOwogICAgCQl0ZVsgMTIgXSA9IG1lWyAxMiBdOyB0ZVsgMTMgXSA9IG1lWyAxMyBdOyB0ZVsgMTQgXSA9IG1lWyAxNCBdOyB0ZVsgMTUgXSA9IG1lWyAxNSBdOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWNvcHlQb3NpdGlvbjogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50cywgbWUgPSBtLmVsZW1lbnRzOwoKICAgIAkJdGVbIDEyIF0gPSBtZVsgMTIgXTsKICAgIAkJdGVbIDEzIF0gPSBtZVsgMTMgXTsKICAgIAkJdGVbIDE0IF0gPSBtZVsgMTQgXTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlleHRyYWN0QmFzaXM6IGZ1bmN0aW9uICggeEF4aXMsIHlBeGlzLCB6QXhpcyApIHsKCiAgICAJCXhBeGlzLnNldEZyb21NYXRyaXhDb2x1bW4oIHRoaXMsIDAgKTsKICAgIAkJeUF4aXMuc2V0RnJvbU1hdHJpeENvbHVtbiggdGhpcywgMSApOwogICAgCQl6QXhpcy5zZXRGcm9tTWF0cml4Q29sdW1uKCB0aGlzLCAyICk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZUJhc2lzOiBmdW5jdGlvbiAoIHhBeGlzLCB5QXhpcywgekF4aXMgKSB7CgogICAgCQl0aGlzLnNldCgKICAgIAkJCXhBeGlzLngsIHlBeGlzLngsIHpBeGlzLngsIDAsCiAgICAJCQl4QXhpcy55LCB5QXhpcy55LCB6QXhpcy55LCAwLAogICAgCQkJeEF4aXMueiwgeUF4aXMueiwgekF4aXMueiwgMCwKICAgIAkJCTAsIDAsIDAsIDEKICAgIAkJKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlleHRyYWN0Um90YXRpb246IGZ1bmN0aW9uICggbSApIHsKCiAgICAJCS8vIHRoaXMgbWV0aG9kIGRvZXMgbm90IHN1cHBvcnQgcmVmbGVjdGlvbiBtYXRyaWNlcwoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKICAgIAkJdmFyIG1lID0gbS5lbGVtZW50czsKCiAgICAJCXZhciBzY2FsZVggPSAxIC8gX3YxLnNldEZyb21NYXRyaXhDb2x1bW4oIG0sIDAgKS5sZW5ndGgoKTsKICAgIAkJdmFyIHNjYWxlWSA9IDEgLyBfdjEuc2V0RnJvbU1hdHJpeENvbHVtbiggbSwgMSApLmxlbmd0aCgpOwogICAgCQl2YXIgc2NhbGVaID0gMSAvIF92MS5zZXRGcm9tTWF0cml4Q29sdW1uKCBtLCAyICkubGVuZ3RoKCk7CgogICAgCQl0ZVsgMCBdID0gbWVbIDAgXSAqIHNjYWxlWDsKICAgIAkJdGVbIDEgXSA9IG1lWyAxIF0gKiBzY2FsZVg7CiAgICAJCXRlWyAyIF0gPSBtZVsgMiBdICogc2NhbGVYOwogICAgCQl0ZVsgMyBdID0gMDsKCiAgICAJCXRlWyA0IF0gPSBtZVsgNCBdICogc2NhbGVZOwogICAgCQl0ZVsgNSBdID0gbWVbIDUgXSAqIHNjYWxlWTsKICAgIAkJdGVbIDYgXSA9IG1lWyA2IF0gKiBzY2FsZVk7CiAgICAJCXRlWyA3IF0gPSAwOwoKICAgIAkJdGVbIDggXSA9IG1lWyA4IF0gKiBzY2FsZVo7CiAgICAJCXRlWyA5IF0gPSBtZVsgOSBdICogc2NhbGVaOwogICAgCQl0ZVsgMTAgXSA9IG1lWyAxMCBdICogc2NhbGVaOwogICAgCQl0ZVsgMTEgXSA9IDA7CgogICAgCQl0ZVsgMTIgXSA9IDA7CiAgICAJCXRlWyAxMyBdID0gMDsKICAgIAkJdGVbIDE0IF0gPSAwOwogICAgCQl0ZVsgMTUgXSA9IDE7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZVJvdGF0aW9uRnJvbUV1bGVyOiBmdW5jdGlvbiAoIGV1bGVyICkgewoKICAgIAkJaWYgKCAhICggZXVsZXIgJiYgZXVsZXIuaXNFdWxlciApICkgewoKICAgIAkJCWNvbnNvbGUuZXJyb3IoICdUSFJFRS5NYXRyaXg0OiAubWFrZVJvdGF0aW9uRnJvbUV1bGVyKCkgbm93IGV4cGVjdHMgYSBFdWxlciByb3RhdGlvbiByYXRoZXIgdGhhbiBhIFZlY3RvcjMgYW5kIG9yZGVyLicgKTsKCiAgICAJCX0KCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl2YXIgeCA9IGV1bGVyLngsIHkgPSBldWxlci55LCB6ID0gZXVsZXIuejsKICAgIAkJdmFyIGEgPSBNYXRoLmNvcyggeCApLCBiID0gTWF0aC5zaW4oIHggKTsKICAgIAkJdmFyIGMgPSBNYXRoLmNvcyggeSApLCBkID0gTWF0aC5zaW4oIHkgKTsKICAgIAkJdmFyIGUgPSBNYXRoLmNvcyggeiApLCBmID0gTWF0aC5zaW4oIHogKTsKCiAgICAJCWlmICggZXVsZXIub3JkZXIgPT09ICdYWVonICkgewoKICAgIAkJCXZhciBhZSA9IGEgKiBlLCBhZiA9IGEgKiBmLCBiZSA9IGIgKiBlLCBiZiA9IGIgKiBmOwoKICAgIAkJCXRlWyAwIF0gPSBjICogZTsKICAgIAkJCXRlWyA0IF0gPSAtIGMgKiBmOwogICAgCQkJdGVbIDggXSA9IGQ7CgogICAgCQkJdGVbIDEgXSA9IGFmICsgYmUgKiBkOwogICAgCQkJdGVbIDUgXSA9IGFlIC0gYmYgKiBkOwogICAgCQkJdGVbIDkgXSA9IC0gYiAqIGM7CgogICAgCQkJdGVbIDIgXSA9IGJmIC0gYWUgKiBkOwogICAgCQkJdGVbIDYgXSA9IGJlICsgYWYgKiBkOwogICAgCQkJdGVbIDEwIF0gPSBhICogYzsKCiAgICAJCX0gZWxzZSBpZiAoIGV1bGVyLm9yZGVyID09PSAnWVhaJyApIHsKCiAgICAJCQl2YXIgY2UgPSBjICogZSwgY2YgPSBjICogZiwgZGUgPSBkICogZSwgZGYgPSBkICogZjsKCiAgICAJCQl0ZVsgMCBdID0gY2UgKyBkZiAqIGI7CiAgICAJCQl0ZVsgNCBdID0gZGUgKiBiIC0gY2Y7CiAgICAJCQl0ZVsgOCBdID0gYSAqIGQ7CgogICAgCQkJdGVbIDEgXSA9IGEgKiBmOwogICAgCQkJdGVbIDUgXSA9IGEgKiBlOwogICAgCQkJdGVbIDkgXSA9IC0gYjsKCiAgICAJCQl0ZVsgMiBdID0gY2YgKiBiIC0gZGU7CiAgICAJCQl0ZVsgNiBdID0gZGYgKyBjZSAqIGI7CiAgICAJCQl0ZVsgMTAgXSA9IGEgKiBjOwoKICAgIAkJfSBlbHNlIGlmICggZXVsZXIub3JkZXIgPT09ICdaWFknICkgewoKICAgIAkJCXZhciBjZSA9IGMgKiBlLCBjZiA9IGMgKiBmLCBkZSA9IGQgKiBlLCBkZiA9IGQgKiBmOwoKICAgIAkJCXRlWyAwIF0gPSBjZSAtIGRmICogYjsKICAgIAkJCXRlWyA0IF0gPSAtIGEgKiBmOwogICAgCQkJdGVbIDggXSA9IGRlICsgY2YgKiBiOwoKICAgIAkJCXRlWyAxIF0gPSBjZiArIGRlICogYjsKICAgIAkJCXRlWyA1IF0gPSBhICogZTsKICAgIAkJCXRlWyA5IF0gPSBkZiAtIGNlICogYjsKCiAgICAJCQl0ZVsgMiBdID0gLSBhICogZDsKICAgIAkJCXRlWyA2IF0gPSBiOwogICAgCQkJdGVbIDEwIF0gPSBhICogYzsKCiAgICAJCX0gZWxzZSBpZiAoIGV1bGVyLm9yZGVyID09PSAnWllYJyApIHsKCiAgICAJCQl2YXIgYWUgPSBhICogZSwgYWYgPSBhICogZiwgYmUgPSBiICogZSwgYmYgPSBiICogZjsKCiAgICAJCQl0ZVsgMCBdID0gYyAqIGU7CiAgICAJCQl0ZVsgNCBdID0gYmUgKiBkIC0gYWY7CiAgICAJCQl0ZVsgOCBdID0gYWUgKiBkICsgYmY7CgogICAgCQkJdGVbIDEgXSA9IGMgKiBmOwogICAgCQkJdGVbIDUgXSA9IGJmICogZCArIGFlOwogICAgCQkJdGVbIDkgXSA9IGFmICogZCAtIGJlOwoKICAgIAkJCXRlWyAyIF0gPSAtIGQ7CiAgICAJCQl0ZVsgNiBdID0gYiAqIGM7CiAgICAJCQl0ZVsgMTAgXSA9IGEgKiBjOwoKICAgIAkJfSBlbHNlIGlmICggZXVsZXIub3JkZXIgPT09ICdZWlgnICkgewoKICAgIAkJCXZhciBhYyA9IGEgKiBjLCBhZCA9IGEgKiBkLCBiYyA9IGIgKiBjLCBiZCA9IGIgKiBkOwoKICAgIAkJCXRlWyAwIF0gPSBjICogZTsKICAgIAkJCXRlWyA0IF0gPSBiZCAtIGFjICogZjsKICAgIAkJCXRlWyA4IF0gPSBiYyAqIGYgKyBhZDsKCiAgICAJCQl0ZVsgMSBdID0gZjsKICAgIAkJCXRlWyA1IF0gPSBhICogZTsKICAgIAkJCXRlWyA5IF0gPSAtIGIgKiBlOwoKICAgIAkJCXRlWyAyIF0gPSAtIGQgKiBlOwogICAgCQkJdGVbIDYgXSA9IGFkICogZiArIGJjOwogICAgCQkJdGVbIDEwIF0gPSBhYyAtIGJkICogZjsKCiAgICAJCX0gZWxzZSBpZiAoIGV1bGVyLm9yZGVyID09PSAnWFpZJyApIHsKCiAgICAJCQl2YXIgYWMgPSBhICogYywgYWQgPSBhICogZCwgYmMgPSBiICogYywgYmQgPSBiICogZDsKCiAgICAJCQl0ZVsgMCBdID0gYyAqIGU7CiAgICAJCQl0ZVsgNCBdID0gLSBmOwogICAgCQkJdGVbIDggXSA9IGQgKiBlOwoKICAgIAkJCXRlWyAxIF0gPSBhYyAqIGYgKyBiZDsKICAgIAkJCXRlWyA1IF0gPSBhICogZTsKICAgIAkJCXRlWyA5IF0gPSBhZCAqIGYgLSBiYzsKCiAgICAJCQl0ZVsgMiBdID0gYmMgKiBmIC0gYWQ7CiAgICAJCQl0ZVsgNiBdID0gYiAqIGU7CiAgICAJCQl0ZVsgMTAgXSA9IGJkICogZiArIGFjOwoKICAgIAkJfQoKICAgIAkJLy8gYm90dG9tIHJvdwogICAgCQl0ZVsgMyBdID0gMDsKICAgIAkJdGVbIDcgXSA9IDA7CiAgICAJCXRlWyAxMSBdID0gMDsKCiAgICAJCS8vIGxhc3QgY29sdW1uCiAgICAJCXRlWyAxMiBdID0gMDsKICAgIAkJdGVbIDEzIF0gPSAwOwogICAgCQl0ZVsgMTQgXSA9IDA7CiAgICAJCXRlWyAxNSBdID0gMTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltYWtlUm90YXRpb25Gcm9tUXVhdGVybmlvbjogZnVuY3Rpb24gKCBxICkgewoKICAgIAkJcmV0dXJuIHRoaXMuY29tcG9zZSggX3plcm8sIHEsIF9vbmUgKTsKCiAgICAJfSwKCiAgICAJbG9va0F0OiBmdW5jdGlvbiAoIGV5ZSwgdGFyZ2V0LCB1cCApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQlfei5zdWJWZWN0b3JzKCBleWUsIHRhcmdldCApOwoKICAgIAkJaWYgKCBfei5sZW5ndGhTcSgpID09PSAwICkgewoKICAgIAkJCS8vIGV5ZSBhbmQgdGFyZ2V0IGFyZSBpbiB0aGUgc2FtZSBwb3NpdGlvbgoKICAgIAkJCV96LnogPSAxOwoKICAgIAkJfQoKICAgIAkJX3oubm9ybWFsaXplKCk7CiAgICAJCV94LmNyb3NzVmVjdG9ycyggdXAsIF96ICk7CgogICAgCQlpZiAoIF94Lmxlbmd0aFNxKCkgPT09IDAgKSB7CgogICAgCQkJLy8gdXAgYW5kIHogYXJlIHBhcmFsbGVsCgogICAgCQkJaWYgKCBNYXRoLmFicyggdXAueiApID09PSAxICkgewoKICAgIAkJCQlfei54ICs9IDAuMDAwMTsKCiAgICAJCQl9IGVsc2UgewoKICAgIAkJCQlfei56ICs9IDAuMDAwMTsKCiAgICAJCQl9CgogICAgCQkJX3oubm9ybWFsaXplKCk7CiAgICAJCQlfeC5jcm9zc1ZlY3RvcnMoIHVwLCBfeiApOwoKICAgIAkJfQoKICAgIAkJX3gubm9ybWFsaXplKCk7CiAgICAJCV95LmNyb3NzVmVjdG9ycyggX3osIF94ICk7CgogICAgCQl0ZVsgMCBdID0gX3gueDsgdGVbIDQgXSA9IF95Lng7IHRlWyA4IF0gPSBfei54OwogICAgCQl0ZVsgMSBdID0gX3gueTsgdGVbIDUgXSA9IF95Lnk7IHRlWyA5IF0gPSBfei55OwogICAgCQl0ZVsgMiBdID0gX3guejsgdGVbIDYgXSA9IF95Lno7IHRlWyAxMCBdID0gX3ouejsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltdWx0aXBseTogZnVuY3Rpb24gKCBtLCBuICkgewoKICAgIAkJaWYgKCBuICE9PSB1bmRlZmluZWQgKSB7CgogICAgCQkJY29uc29sZS53YXJuKCAnVEhSRUUuTWF0cml4NDogLm11bHRpcGx5KCkgbm93IG9ubHkgYWNjZXB0cyBvbmUgYXJndW1lbnQuIFVzZSAubXVsdGlwbHlNYXRyaWNlcyggYSwgYiApIGluc3RlYWQuJyApOwogICAgCQkJcmV0dXJuIHRoaXMubXVsdGlwbHlNYXRyaWNlcyggbSwgbiApOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIHRoaXMubXVsdGlwbHlNYXRyaWNlcyggdGhpcywgbSApOwoKICAgIAl9LAoKICAgIAlwcmVtdWx0aXBseTogZnVuY3Rpb24gKCBtICkgewoKICAgIAkJcmV0dXJuIHRoaXMubXVsdGlwbHlNYXRyaWNlcyggbSwgdGhpcyApOwoKICAgIAl9LAoKICAgIAltdWx0aXBseU1hdHJpY2VzOiBmdW5jdGlvbiAoIGEsIGIgKSB7CgogICAgCQl2YXIgYWUgPSBhLmVsZW1lbnRzOwogICAgCQl2YXIgYmUgPSBiLmVsZW1lbnRzOwogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwoKICAgIAkJdmFyIGExMSA9IGFlWyAwIF0sIGExMiA9IGFlWyA0IF0sIGExMyA9IGFlWyA4IF0sIGExNCA9IGFlWyAxMiBdOwogICAgCQl2YXIgYTIxID0gYWVbIDEgXSwgYTIyID0gYWVbIDUgXSwgYTIzID0gYWVbIDkgXSwgYTI0ID0gYWVbIDEzIF07CiAgICAJCXZhciBhMzEgPSBhZVsgMiBdLCBhMzIgPSBhZVsgNiBdLCBhMzMgPSBhZVsgMTAgXSwgYTM0ID0gYWVbIDE0IF07CiAgICAJCXZhciBhNDEgPSBhZVsgMyBdLCBhNDIgPSBhZVsgNyBdLCBhNDMgPSBhZVsgMTEgXSwgYTQ0ID0gYWVbIDE1IF07CgogICAgCQl2YXIgYjExID0gYmVbIDAgXSwgYjEyID0gYmVbIDQgXSwgYjEzID0gYmVbIDggXSwgYjE0ID0gYmVbIDEyIF07CiAgICAJCXZhciBiMjEgPSBiZVsgMSBdLCBiMjIgPSBiZVsgNSBdLCBiMjMgPSBiZVsgOSBdLCBiMjQgPSBiZVsgMTMgXTsKICAgIAkJdmFyIGIzMSA9IGJlWyAyIF0sIGIzMiA9IGJlWyA2IF0sIGIzMyA9IGJlWyAxMCBdLCBiMzQgPSBiZVsgMTQgXTsKICAgIAkJdmFyIGI0MSA9IGJlWyAzIF0sIGI0MiA9IGJlWyA3IF0sIGI0MyA9IGJlWyAxMSBdLCBiNDQgPSBiZVsgMTUgXTsKCiAgICAJCXRlWyAwIF0gPSBhMTEgKiBiMTEgKyBhMTIgKiBiMjEgKyBhMTMgKiBiMzEgKyBhMTQgKiBiNDE7CiAgICAJCXRlWyA0IF0gPSBhMTEgKiBiMTIgKyBhMTIgKiBiMjIgKyBhMTMgKiBiMzIgKyBhMTQgKiBiNDI7CiAgICAJCXRlWyA4IF0gPSBhMTEgKiBiMTMgKyBhMTIgKiBiMjMgKyBhMTMgKiBiMzMgKyBhMTQgKiBiNDM7CiAgICAJCXRlWyAxMiBdID0gYTExICogYjE0ICsgYTEyICogYjI0ICsgYTEzICogYjM0ICsgYTE0ICogYjQ0OwoKICAgIAkJdGVbIDEgXSA9IGEyMSAqIGIxMSArIGEyMiAqIGIyMSArIGEyMyAqIGIzMSArIGEyNCAqIGI0MTsKICAgIAkJdGVbIDUgXSA9IGEyMSAqIGIxMiArIGEyMiAqIGIyMiArIGEyMyAqIGIzMiArIGEyNCAqIGI0MjsKICAgIAkJdGVbIDkgXSA9IGEyMSAqIGIxMyArIGEyMiAqIGIyMyArIGEyMyAqIGIzMyArIGEyNCAqIGI0MzsKICAgIAkJdGVbIDEzIF0gPSBhMjEgKiBiMTQgKyBhMjIgKiBiMjQgKyBhMjMgKiBiMzQgKyBhMjQgKiBiNDQ7CgogICAgCQl0ZVsgMiBdID0gYTMxICogYjExICsgYTMyICogYjIxICsgYTMzICogYjMxICsgYTM0ICogYjQxOwogICAgCQl0ZVsgNiBdID0gYTMxICogYjEyICsgYTMyICogYjIyICsgYTMzICogYjMyICsgYTM0ICogYjQyOwogICAgCQl0ZVsgMTAgXSA9IGEzMSAqIGIxMyArIGEzMiAqIGIyMyArIGEzMyAqIGIzMyArIGEzNCAqIGI0MzsKICAgIAkJdGVbIDE0IF0gPSBhMzEgKiBiMTQgKyBhMzIgKiBiMjQgKyBhMzMgKiBiMzQgKyBhMzQgKiBiNDQ7CgogICAgCQl0ZVsgMyBdID0gYTQxICogYjExICsgYTQyICogYjIxICsgYTQzICogYjMxICsgYTQ0ICogYjQxOwogICAgCQl0ZVsgNyBdID0gYTQxICogYjEyICsgYTQyICogYjIyICsgYTQzICogYjMyICsgYTQ0ICogYjQyOwogICAgCQl0ZVsgMTEgXSA9IGE0MSAqIGIxMyArIGE0MiAqIGIyMyArIGE0MyAqIGIzMyArIGE0NCAqIGI0MzsKICAgIAkJdGVbIDE1IF0gPSBhNDEgKiBiMTQgKyBhNDIgKiBiMjQgKyBhNDMgKiBiMzQgKyBhNDQgKiBiNDQ7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbXVsdGlwbHlTY2FsYXI6IGZ1bmN0aW9uICggcyApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl0ZVsgMCBdICo9IHM7IHRlWyA0IF0gKj0gczsgdGVbIDggXSAqPSBzOyB0ZVsgMTIgXSAqPSBzOwogICAgCQl0ZVsgMSBdICo9IHM7IHRlWyA1IF0gKj0gczsgdGVbIDkgXSAqPSBzOyB0ZVsgMTMgXSAqPSBzOwogICAgCQl0ZVsgMiBdICo9IHM7IHRlWyA2IF0gKj0gczsgdGVbIDEwIF0gKj0gczsgdGVbIDE0IF0gKj0gczsKICAgIAkJdGVbIDMgXSAqPSBzOyB0ZVsgNyBdICo9IHM7IHRlWyAxMSBdICo9IHM7IHRlWyAxNSBdICo9IHM7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJYXBwbHlUb0J1ZmZlckF0dHJpYnV0ZTogZnVuY3Rpb24gKCBhdHRyaWJ1dGUgKSB7CgogICAgCQlmb3IgKCB2YXIgaSA9IDAsIGwgPSBhdHRyaWJ1dGUuY291bnQ7IGkgPCBsOyBpICsrICkgewoKICAgIAkJCV92MS54ID0gYXR0cmlidXRlLmdldFgoIGkgKTsKICAgIAkJCV92MS55ID0gYXR0cmlidXRlLmdldFkoIGkgKTsKICAgIAkJCV92MS56ID0gYXR0cmlidXRlLmdldFooIGkgKTsKCiAgICAJCQlfdjEuYXBwbHlNYXRyaXg0KCB0aGlzICk7CgogICAgCQkJYXR0cmlidXRlLnNldFhZWiggaSwgX3YxLngsIF92MS55LCBfdjEueiApOwoKICAgIAkJfQoKICAgIAkJcmV0dXJuIGF0dHJpYnV0ZTsKCiAgICAJfSwKCiAgICAJZGV0ZXJtaW5hbnQ6IGZ1bmN0aW9uICgpIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl2YXIgbjExID0gdGVbIDAgXSwgbjEyID0gdGVbIDQgXSwgbjEzID0gdGVbIDggXSwgbjE0ID0gdGVbIDEyIF07CiAgICAJCXZhciBuMjEgPSB0ZVsgMSBdLCBuMjIgPSB0ZVsgNSBdLCBuMjMgPSB0ZVsgOSBdLCBuMjQgPSB0ZVsgMTMgXTsKICAgIAkJdmFyIG4zMSA9IHRlWyAyIF0sIG4zMiA9IHRlWyA2IF0sIG4zMyA9IHRlWyAxMCBdLCBuMzQgPSB0ZVsgMTQgXTsKICAgIAkJdmFyIG40MSA9IHRlWyAzIF0sIG40MiA9IHRlWyA3IF0sIG40MyA9IHRlWyAxMSBdLCBuNDQgPSB0ZVsgMTUgXTsKCiAgICAJCS8vVE9ETzogbWFrZSB0aGlzIG1vcmUgZWZmaWNpZW50CiAgICAJCS8vKCBiYXNlZCBvbiBodHRwOi8vd3d3LmV1Y2xpZGVhbnNwYWNlLmNvbS9tYXRocy9hbGdlYnJhL21hdHJpeC9mdW5jdGlvbnMvaW52ZXJzZS9mb3VyRC9pbmRleC5odG0gKQoKICAgIAkJcmV0dXJuICgKICAgIAkJCW40MSAqICgKICAgIAkJCQkrIG4xNCAqIG4yMyAqIG4zMgogICAgCQkJCSAtIG4xMyAqIG4yNCAqIG4zMgogICAgCQkJCSAtIG4xNCAqIG4yMiAqIG4zMwogICAgCQkJCSArIG4xMiAqIG4yNCAqIG4zMwogICAgCQkJCSArIG4xMyAqIG4yMiAqIG4zNAogICAgCQkJCSAtIG4xMiAqIG4yMyAqIG4zNAogICAgCQkJKSArCiAgICAJCQluNDIgKiAoCiAgICAJCQkJKyBuMTEgKiBuMjMgKiBuMzQKICAgIAkJCQkgLSBuMTEgKiBuMjQgKiBuMzMKICAgIAkJCQkgKyBuMTQgKiBuMjEgKiBuMzMKICAgIAkJCQkgLSBuMTMgKiBuMjEgKiBuMzQKICAgIAkJCQkgKyBuMTMgKiBuMjQgKiBuMzEKICAgIAkJCQkgLSBuMTQgKiBuMjMgKiBuMzEKICAgIAkJCSkgKwogICAgCQkJbjQzICogKAogICAgCQkJCSsgbjExICogbjI0ICogbjMyCiAgICAJCQkJIC0gbjExICogbjIyICogbjM0CiAgICAJCQkJIC0gbjE0ICogbjIxICogbjMyCiAgICAJCQkJICsgbjEyICogbjIxICogbjM0CiAgICAJCQkJICsgbjE0ICogbjIyICogbjMxCiAgICAJCQkJIC0gbjEyICogbjI0ICogbjMxCiAgICAJCQkpICsKICAgIAkJCW40NCAqICgKICAgIAkJCQktIG4xMyAqIG4yMiAqIG4zMQogICAgCQkJCSAtIG4xMSAqIG4yMyAqIG4zMgogICAgCQkJCSArIG4xMSAqIG4yMiAqIG4zMwogICAgCQkJCSArIG4xMyAqIG4yMSAqIG4zMgogICAgCQkJCSAtIG4xMiAqIG4yMSAqIG4zMwogICAgCQkJCSArIG4xMiAqIG4yMyAqIG4zMQogICAgCQkJKQoKICAgIAkJKTsKCiAgICAJfSwKCiAgICAJdHJhbnNwb3NlOiBmdW5jdGlvbiAoKSB7CgogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwogICAgCQl2YXIgdG1wOwoKICAgIAkJdG1wID0gdGVbIDEgXTsgdGVbIDEgXSA9IHRlWyA0IF07IHRlWyA0IF0gPSB0bXA7CiAgICAJCXRtcCA9IHRlWyAyIF07IHRlWyAyIF0gPSB0ZVsgOCBdOyB0ZVsgOCBdID0gdG1wOwogICAgCQl0bXAgPSB0ZVsgNiBdOyB0ZVsgNiBdID0gdGVbIDkgXTsgdGVbIDkgXSA9IHRtcDsKCiAgICAJCXRtcCA9IHRlWyAzIF07IHRlWyAzIF0gPSB0ZVsgMTIgXTsgdGVbIDEyIF0gPSB0bXA7CiAgICAJCXRtcCA9IHRlWyA3IF07IHRlWyA3IF0gPSB0ZVsgMTMgXTsgdGVbIDEzIF0gPSB0bXA7CiAgICAJCXRtcCA9IHRlWyAxMSBdOyB0ZVsgMTEgXSA9IHRlWyAxNCBdOyB0ZVsgMTQgXSA9IHRtcDsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlzZXRQb3NpdGlvbjogZnVuY3Rpb24gKCB4LCB5LCB6ICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKCiAgICAJCWlmICggeC5pc1ZlY3RvcjMgKSB7CgogICAgCQkJdGVbIDEyIF0gPSB4Lng7CiAgICAJCQl0ZVsgMTMgXSA9IHgueTsKICAgIAkJCXRlWyAxNCBdID0geC56OwoKICAgIAkJfSBlbHNlIHsKCiAgICAJCQl0ZVsgMTIgXSA9IHg7CiAgICAJCQl0ZVsgMTMgXSA9IHk7CiAgICAJCQl0ZVsgMTQgXSA9IHo7CgogICAgCQl9CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZ2V0SW52ZXJzZTogZnVuY3Rpb24gKCBtLCB0aHJvd09uRGVnZW5lcmF0ZSApIHsKCiAgICAJCS8vIGJhc2VkIG9uIGh0dHA6Ly93d3cuZXVjbGlkZWFuc3BhY2UuY29tL21hdGhzL2FsZ2VicmEvbWF0cml4L2Z1bmN0aW9ucy9pbnZlcnNlL2ZvdXJEL2luZGV4Lmh0bQogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzLAogICAgCQkJbWUgPSBtLmVsZW1lbnRzLAoKICAgIAkJCW4xMSA9IG1lWyAwIF0sIG4yMSA9IG1lWyAxIF0sIG4zMSA9IG1lWyAyIF0sIG40MSA9IG1lWyAzIF0sCiAgICAJCQluMTIgPSBtZVsgNCBdLCBuMjIgPSBtZVsgNSBdLCBuMzIgPSBtZVsgNiBdLCBuNDIgPSBtZVsgNyBdLAogICAgCQkJbjEzID0gbWVbIDggXSwgbjIzID0gbWVbIDkgXSwgbjMzID0gbWVbIDEwIF0sIG40MyA9IG1lWyAxMSBdLAogICAgCQkJbjE0ID0gbWVbIDEyIF0sIG4yNCA9IG1lWyAxMyBdLCBuMzQgPSBtZVsgMTQgXSwgbjQ0ID0gbWVbIDE1IF0sCgogICAgCQkJdDExID0gbjIzICogbjM0ICogbjQyIC0gbjI0ICogbjMzICogbjQyICsgbjI0ICogbjMyICogbjQzIC0gbjIyICogbjM0ICogbjQzIC0gbjIzICogbjMyICogbjQ0ICsgbjIyICogbjMzICogbjQ0LAogICAgCQkJdDEyID0gbjE0ICogbjMzICogbjQyIC0gbjEzICogbjM0ICogbjQyIC0gbjE0ICogbjMyICogbjQzICsgbjEyICogbjM0ICogbjQzICsgbjEzICogbjMyICogbjQ0IC0gbjEyICogbjMzICogbjQ0LAogICAgCQkJdDEzID0gbjEzICogbjI0ICogbjQyIC0gbjE0ICogbjIzICogbjQyICsgbjE0ICogbjIyICogbjQzIC0gbjEyICogbjI0ICogbjQzIC0gbjEzICogbjIyICogbjQ0ICsgbjEyICogbjIzICogbjQ0LAogICAgCQkJdDE0ID0gbjE0ICogbjIzICogbjMyIC0gbjEzICogbjI0ICogbjMyIC0gbjE0ICogbjIyICogbjMzICsgbjEyICogbjI0ICogbjMzICsgbjEzICogbjIyICogbjM0IC0gbjEyICogbjIzICogbjM0OwoKICAgIAkJdmFyIGRldCA9IG4xMSAqIHQxMSArIG4yMSAqIHQxMiArIG4zMSAqIHQxMyArIG40MSAqIHQxNDsKCiAgICAJCWlmICggZGV0ID09PSAwICkgewoKICAgIAkJCXZhciBtc2cgPSAiVEhSRUUuTWF0cml4NDogLmdldEludmVyc2UoKSBjYW4ndCBpbnZlcnQgbWF0cml4LCBkZXRlcm1pbmFudCBpcyAwIjsKCiAgICAJCQlpZiAoIHRocm93T25EZWdlbmVyYXRlID09PSB0cnVlICkgewoKICAgIAkJCQl0aHJvdyBuZXcgRXJyb3IoIG1zZyApOwoKICAgIAkJCX0gZWxzZSB7CgogICAgCQkJCWNvbnNvbGUud2FybiggbXNnICk7CgogICAgCQkJfQoKICAgIAkJCXJldHVybiB0aGlzLmlkZW50aXR5KCk7CgogICAgCQl9CgogICAgCQl2YXIgZGV0SW52ID0gMSAvIGRldDsKCiAgICAJCXRlWyAwIF0gPSB0MTEgKiBkZXRJbnY7CiAgICAJCXRlWyAxIF0gPSAoIG4yNCAqIG4zMyAqIG40MSAtIG4yMyAqIG4zNCAqIG40MSAtIG4yNCAqIG4zMSAqIG40MyArIG4yMSAqIG4zNCAqIG40MyArIG4yMyAqIG4zMSAqIG40NCAtIG4yMSAqIG4zMyAqIG40NCApICogZGV0SW52OwogICAgCQl0ZVsgMiBdID0gKCBuMjIgKiBuMzQgKiBuNDEgLSBuMjQgKiBuMzIgKiBuNDEgKyBuMjQgKiBuMzEgKiBuNDIgLSBuMjEgKiBuMzQgKiBuNDIgLSBuMjIgKiBuMzEgKiBuNDQgKyBuMjEgKiBuMzIgKiBuNDQgKSAqIGRldEludjsKICAgIAkJdGVbIDMgXSA9ICggbjIzICogbjMyICogbjQxIC0gbjIyICogbjMzICogbjQxIC0gbjIzICogbjMxICogbjQyICsgbjIxICogbjMzICogbjQyICsgbjIyICogbjMxICogbjQzIC0gbjIxICogbjMyICogbjQzICkgKiBkZXRJbnY7CgogICAgCQl0ZVsgNCBdID0gdDEyICogZGV0SW52OwogICAgCQl0ZVsgNSBdID0gKCBuMTMgKiBuMzQgKiBuNDEgLSBuMTQgKiBuMzMgKiBuNDEgKyBuMTQgKiBuMzEgKiBuNDMgLSBuMTEgKiBuMzQgKiBuNDMgLSBuMTMgKiBuMzEgKiBuNDQgKyBuMTEgKiBuMzMgKiBuNDQgKSAqIGRldEludjsKICAgIAkJdGVbIDYgXSA9ICggbjE0ICogbjMyICogbjQxIC0gbjEyICogbjM0ICogbjQxIC0gbjE0ICogbjMxICogbjQyICsgbjExICogbjM0ICogbjQyICsgbjEyICogbjMxICogbjQ0IC0gbjExICogbjMyICogbjQ0ICkgKiBkZXRJbnY7CiAgICAJCXRlWyA3IF0gPSAoIG4xMiAqIG4zMyAqIG40MSAtIG4xMyAqIG4zMiAqIG40MSArIG4xMyAqIG4zMSAqIG40MiAtIG4xMSAqIG4zMyAqIG40MiAtIG4xMiAqIG4zMSAqIG40MyArIG4xMSAqIG4zMiAqIG40MyApICogZGV0SW52OwoKICAgIAkJdGVbIDggXSA9IHQxMyAqIGRldEludjsKICAgIAkJdGVbIDkgXSA9ICggbjE0ICogbjIzICogbjQxIC0gbjEzICogbjI0ICogbjQxIC0gbjE0ICogbjIxICogbjQzICsgbjExICogbjI0ICogbjQzICsgbjEzICogbjIxICogbjQ0IC0gbjExICogbjIzICogbjQ0ICkgKiBkZXRJbnY7CiAgICAJCXRlWyAxMCBdID0gKCBuMTIgKiBuMjQgKiBuNDEgLSBuMTQgKiBuMjIgKiBuNDEgKyBuMTQgKiBuMjEgKiBuNDIgLSBuMTEgKiBuMjQgKiBuNDIgLSBuMTIgKiBuMjEgKiBuNDQgKyBuMTEgKiBuMjIgKiBuNDQgKSAqIGRldEludjsKICAgIAkJdGVbIDExIF0gPSAoIG4xMyAqIG4yMiAqIG40MSAtIG4xMiAqIG4yMyAqIG40MSAtIG4xMyAqIG4yMSAqIG40MiArIG4xMSAqIG4yMyAqIG40MiArIG4xMiAqIG4yMSAqIG40MyAtIG4xMSAqIG4yMiAqIG40MyApICogZGV0SW52OwoKICAgIAkJdGVbIDEyIF0gPSB0MTQgKiBkZXRJbnY7CiAgICAJCXRlWyAxMyBdID0gKCBuMTMgKiBuMjQgKiBuMzEgLSBuMTQgKiBuMjMgKiBuMzEgKyBuMTQgKiBuMjEgKiBuMzMgLSBuMTEgKiBuMjQgKiBuMzMgLSBuMTMgKiBuMjEgKiBuMzQgKyBuMTEgKiBuMjMgKiBuMzQgKSAqIGRldEludjsKICAgIAkJdGVbIDE0IF0gPSAoIG4xNCAqIG4yMiAqIG4zMSAtIG4xMiAqIG4yNCAqIG4zMSAtIG4xNCAqIG4yMSAqIG4zMiArIG4xMSAqIG4yNCAqIG4zMiArIG4xMiAqIG4yMSAqIG4zNCAtIG4xMSAqIG4yMiAqIG4zNCApICogZGV0SW52OwogICAgCQl0ZVsgMTUgXSA9ICggbjEyICogbjIzICogbjMxIC0gbjEzICogbjIyICogbjMxICsgbjEzICogbjIxICogbjMyIC0gbjExICogbjIzICogbjMyIC0gbjEyICogbjIxICogbjMzICsgbjExICogbjIyICogbjMzICkgKiBkZXRJbnY7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJc2NhbGU6IGZ1bmN0aW9uICggdiApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CiAgICAJCXZhciB4ID0gdi54LCB5ID0gdi55LCB6ID0gdi56OwoKICAgIAkJdGVbIDAgXSAqPSB4OyB0ZVsgNCBdICo9IHk7IHRlWyA4IF0gKj0gejsKICAgIAkJdGVbIDEgXSAqPSB4OyB0ZVsgNSBdICo9IHk7IHRlWyA5IF0gKj0gejsKICAgIAkJdGVbIDIgXSAqPSB4OyB0ZVsgNiBdICo9IHk7IHRlWyAxMCBdICo9IHo7CiAgICAJCXRlWyAzIF0gKj0geDsgdGVbIDcgXSAqPSB5OyB0ZVsgMTEgXSAqPSB6OwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCWdldE1heFNjYWxlT25BeGlzOiBmdW5jdGlvbiAoKSB7CgogICAgCQl2YXIgdGUgPSB0aGlzLmVsZW1lbnRzOwoKICAgIAkJdmFyIHNjYWxlWFNxID0gdGVbIDAgXSAqIHRlWyAwIF0gKyB0ZVsgMSBdICogdGVbIDEgXSArIHRlWyAyIF0gKiB0ZVsgMiBdOwogICAgCQl2YXIgc2NhbGVZU3EgPSB0ZVsgNCBdICogdGVbIDQgXSArIHRlWyA1IF0gKiB0ZVsgNSBdICsgdGVbIDYgXSAqIHRlWyA2IF07CiAgICAJCXZhciBzY2FsZVpTcSA9IHRlWyA4IF0gKiB0ZVsgOCBdICsgdGVbIDkgXSAqIHRlWyA5IF0gKyB0ZVsgMTAgXSAqIHRlWyAxMCBdOwoKICAgIAkJcmV0dXJuIE1hdGguc3FydCggTWF0aC5tYXgoIHNjYWxlWFNxLCBzY2FsZVlTcSwgc2NhbGVaU3EgKSApOwoKICAgIAl9LAoKICAgIAltYWtlVHJhbnNsYXRpb246IGZ1bmN0aW9uICggeCwgeSwgeiApIHsKCiAgICAJCXRoaXMuc2V0KAoKICAgIAkJCTEsIDAsIDAsIHgsCiAgICAJCQkwLCAxLCAwLCB5LAogICAgCQkJMCwgMCwgMSwgeiwKICAgIAkJCTAsIDAsIDAsIDEKCiAgICAJCSk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZVJvdGF0aW9uWDogZnVuY3Rpb24gKCB0aGV0YSApIHsKCiAgICAJCXZhciBjID0gTWF0aC5jb3MoIHRoZXRhICksIHMgPSBNYXRoLnNpbiggdGhldGEgKTsKCiAgICAJCXRoaXMuc2V0KAoKICAgIAkJCTEsIDAsIDAsIDAsCiAgICAJCQkwLCBjLCAtIHMsIDAsCiAgICAJCQkwLCBzLCBjLCAwLAogICAgCQkJMCwgMCwgMCwgMQoKICAgIAkJKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltYWtlUm90YXRpb25ZOiBmdW5jdGlvbiAoIHRoZXRhICkgewoKICAgIAkJdmFyIGMgPSBNYXRoLmNvcyggdGhldGEgKSwgcyA9IE1hdGguc2luKCB0aGV0YSApOwoKICAgIAkJdGhpcy5zZXQoCgogICAgCQkJIGMsIDAsIHMsIDAsCiAgICAJCQkgMCwgMSwgMCwgMCwKICAgIAkJCS0gcywgMCwgYywgMCwKICAgIAkJCSAwLCAwLCAwLCAxCgogICAgCQkpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCW1ha2VSb3RhdGlvblo6IGZ1bmN0aW9uICggdGhldGEgKSB7CgogICAgCQl2YXIgYyA9IE1hdGguY29zKCB0aGV0YSApLCBzID0gTWF0aC5zaW4oIHRoZXRhICk7CgogICAgCQl0aGlzLnNldCgKCiAgICAJCQljLCAtIHMsIDAsIDAsCiAgICAJCQlzLCBjLCAwLCAwLAogICAgCQkJMCwgMCwgMSwgMCwKICAgIAkJCTAsIDAsIDAsIDEKCiAgICAJCSk7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZVJvdGF0aW9uQXhpczogZnVuY3Rpb24gKCBheGlzLCBhbmdsZSApIHsKCiAgICAJCS8vIEJhc2VkIG9uIGh0dHA6Ly93d3cuZ2FtZWRldi5uZXQvcmVmZXJlbmNlL2FydGljbGVzL2FydGljbGUxMTk5LmFzcAoKICAgIAkJdmFyIGMgPSBNYXRoLmNvcyggYW5nbGUgKTsKICAgIAkJdmFyIHMgPSBNYXRoLnNpbiggYW5nbGUgKTsKICAgIAkJdmFyIHQgPSAxIC0gYzsKICAgIAkJdmFyIHggPSBheGlzLngsIHkgPSBheGlzLnksIHogPSBheGlzLno7CiAgICAJCXZhciB0eCA9IHQgKiB4LCB0eSA9IHQgKiB5OwoKICAgIAkJdGhpcy5zZXQoCgogICAgCQkJdHggKiB4ICsgYywgdHggKiB5IC0gcyAqIHosIHR4ICogeiArIHMgKiB5LCAwLAogICAgCQkJdHggKiB5ICsgcyAqIHosIHR5ICogeSArIGMsIHR5ICogeiAtIHMgKiB4LCAwLAogICAgCQkJdHggKiB6IC0gcyAqIHksIHR5ICogeiArIHMgKiB4LCB0ICogeiAqIHogKyBjLCAwLAogICAgCQkJMCwgMCwgMCwgMQoKICAgIAkJKTsKCiAgICAJCSByZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZVNjYWxlOiBmdW5jdGlvbiAoIHgsIHksIHogKSB7CgogICAgCQl0aGlzLnNldCgKCiAgICAJCQl4LCAwLCAwLCAwLAogICAgCQkJMCwgeSwgMCwgMCwKICAgIAkJCTAsIDAsIHosIDAsCiAgICAJCQkwLCAwLCAwLCAxCgogICAgCQkpOwoKICAgIAkJcmV0dXJuIHRoaXM7CgogICAgCX0sCgogICAgCW1ha2VTaGVhcjogZnVuY3Rpb24gKCB4LCB5LCB6ICkgewoKICAgIAkJdGhpcy5zZXQoCgogICAgCQkJMSwgeSwgeiwgMCwKICAgIAkJCXgsIDEsIHosIDAsCiAgICAJCQl4LCB5LCAxLCAwLAogICAgCQkJMCwgMCwgMCwgMQoKICAgIAkJKTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAljb21wb3NlOiBmdW5jdGlvbiAoIHBvc2l0aW9uLCBxdWF0ZXJuaW9uLCBzY2FsZSApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQl2YXIgeCA9IHF1YXRlcm5pb24uX3gsIHkgPSBxdWF0ZXJuaW9uLl95LCB6ID0gcXVhdGVybmlvbi5feiwgdyA9IHF1YXRlcm5pb24uX3c7CiAgICAJCXZhciB4MiA9IHggKyB4LAl5MiA9IHkgKyB5LCB6MiA9IHogKyB6OwogICAgCQl2YXIgeHggPSB4ICogeDIsIHh5ID0geCAqIHkyLCB4eiA9IHggKiB6MjsKICAgIAkJdmFyIHl5ID0geSAqIHkyLCB5eiA9IHkgKiB6MiwgenogPSB6ICogejI7CiAgICAJCXZhciB3eCA9IHcgKiB4Miwgd3kgPSB3ICogeTIsIHd6ID0gdyAqIHoyOwoKICAgIAkJdmFyIHN4ID0gc2NhbGUueCwgc3kgPSBzY2FsZS55LCBzeiA9IHNjYWxlLno7CgogICAgCQl0ZVsgMCBdID0gKCAxIC0gKCB5eSArIHp6ICkgKSAqIHN4OwogICAgCQl0ZVsgMSBdID0gKCB4eSArIHd6ICkgKiBzeDsKICAgIAkJdGVbIDIgXSA9ICggeHogLSB3eSApICogc3g7CiAgICAJCXRlWyAzIF0gPSAwOwoKICAgIAkJdGVbIDQgXSA9ICggeHkgLSB3eiApICogc3k7CiAgICAJCXRlWyA1IF0gPSAoIDEgLSAoIHh4ICsgenogKSApICogc3k7CiAgICAJCXRlWyA2IF0gPSAoIHl6ICsgd3ggKSAqIHN5OwogICAgCQl0ZVsgNyBdID0gMDsKCiAgICAJCXRlWyA4IF0gPSAoIHh6ICsgd3kgKSAqIHN6OwogICAgCQl0ZVsgOSBdID0gKCB5eiAtIHd4ICkgKiBzejsKICAgIAkJdGVbIDEwIF0gPSAoIDEgLSAoIHh4ICsgeXkgKSApICogc3o7CiAgICAJCXRlWyAxMSBdID0gMDsKCiAgICAJCXRlWyAxMiBdID0gcG9zaXRpb24ueDsKICAgIAkJdGVbIDEzIF0gPSBwb3NpdGlvbi55OwogICAgCQl0ZVsgMTQgXSA9IHBvc2l0aW9uLno7CiAgICAJCXRlWyAxNSBdID0gMTsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAlkZWNvbXBvc2U6IGZ1bmN0aW9uICggcG9zaXRpb24sIHF1YXRlcm5pb24sIHNjYWxlICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKCiAgICAJCXZhciBzeCA9IF92MS5zZXQoIHRlWyAwIF0sIHRlWyAxIF0sIHRlWyAyIF0gKS5sZW5ndGgoKTsKICAgIAkJdmFyIHN5ID0gX3YxLnNldCggdGVbIDQgXSwgdGVbIDUgXSwgdGVbIDYgXSApLmxlbmd0aCgpOwogICAgCQl2YXIgc3ogPSBfdjEuc2V0KCB0ZVsgOCBdLCB0ZVsgOSBdLCB0ZVsgMTAgXSApLmxlbmd0aCgpOwoKICAgIAkJLy8gaWYgZGV0ZXJtaW5lIGlzIG5lZ2F0aXZlLCB3ZSBuZWVkIHRvIGludmVydCBvbmUgc2NhbGUKICAgIAkJdmFyIGRldCA9IHRoaXMuZGV0ZXJtaW5hbnQoKTsKICAgIAkJaWYgKCBkZXQgPCAwICkgc3ggPSAtIHN4OwoKICAgIAkJcG9zaXRpb24ueCA9IHRlWyAxMiBdOwogICAgCQlwb3NpdGlvbi55ID0gdGVbIDEzIF07CiAgICAJCXBvc2l0aW9uLnogPSB0ZVsgMTQgXTsKCiAgICAJCS8vIHNjYWxlIHRoZSByb3RhdGlvbiBwYXJ0CiAgICAJCV9tMS5jb3B5KCB0aGlzICk7CgogICAgCQl2YXIgaW52U1ggPSAxIC8gc3g7CiAgICAJCXZhciBpbnZTWSA9IDEgLyBzeTsKICAgIAkJdmFyIGludlNaID0gMSAvIHN6OwoKICAgIAkJX20xLmVsZW1lbnRzWyAwIF0gKj0gaW52U1g7CiAgICAJCV9tMS5lbGVtZW50c1sgMSBdICo9IGludlNYOwogICAgCQlfbTEuZWxlbWVudHNbIDIgXSAqPSBpbnZTWDsKCiAgICAJCV9tMS5lbGVtZW50c1sgNCBdICo9IGludlNZOwogICAgCQlfbTEuZWxlbWVudHNbIDUgXSAqPSBpbnZTWTsKICAgIAkJX20xLmVsZW1lbnRzWyA2IF0gKj0gaW52U1k7CgogICAgCQlfbTEuZWxlbWVudHNbIDggXSAqPSBpbnZTWjsKICAgIAkJX20xLmVsZW1lbnRzWyA5IF0gKj0gaW52U1o7CiAgICAJCV9tMS5lbGVtZW50c1sgMTAgXSAqPSBpbnZTWjsKCiAgICAJCXF1YXRlcm5pb24uc2V0RnJvbVJvdGF0aW9uTWF0cml4KCBfbTEgKTsKCiAgICAJCXNjYWxlLnggPSBzeDsKICAgIAkJc2NhbGUueSA9IHN5OwogICAgCQlzY2FsZS56ID0gc3o7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJbWFrZVBlcnNwZWN0aXZlOiBmdW5jdGlvbiAoIGxlZnQsIHJpZ2h0LCB0b3AsIGJvdHRvbSwgbmVhciwgZmFyICkgewoKICAgIAkJaWYgKCBmYXIgPT09IHVuZGVmaW5lZCApIHsKCiAgICAJCQljb25zb2xlLndhcm4oICdUSFJFRS5NYXRyaXg0OiAubWFrZVBlcnNwZWN0aXZlKCkgaGFzIGJlZW4gcmVkZWZpbmVkIGFuZCBoYXMgYSBuZXcgc2lnbmF0dXJlLiBQbGVhc2UgY2hlY2sgdGhlIGRvY3MuJyApOwoKICAgIAkJfQoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKICAgIAkJdmFyIHggPSAyICogbmVhciAvICggcmlnaHQgLSBsZWZ0ICk7CiAgICAJCXZhciB5ID0gMiAqIG5lYXIgLyAoIHRvcCAtIGJvdHRvbSApOwoKICAgIAkJdmFyIGEgPSAoIHJpZ2h0ICsgbGVmdCApIC8gKCByaWdodCAtIGxlZnQgKTsKICAgIAkJdmFyIGIgPSAoIHRvcCArIGJvdHRvbSApIC8gKCB0b3AgLSBib3R0b20gKTsKICAgIAkJdmFyIGMgPSAtICggZmFyICsgbmVhciApIC8gKCBmYXIgLSBuZWFyICk7CiAgICAJCXZhciBkID0gLSAyICogZmFyICogbmVhciAvICggZmFyIC0gbmVhciApOwoKICAgIAkJdGVbIDAgXSA9IHg7CXRlWyA0IF0gPSAwOwl0ZVsgOCBdID0gYTsJdGVbIDEyIF0gPSAwOwogICAgCQl0ZVsgMSBdID0gMDsJdGVbIDUgXSA9IHk7CXRlWyA5IF0gPSBiOwl0ZVsgMTMgXSA9IDA7CiAgICAJCXRlWyAyIF0gPSAwOwl0ZVsgNiBdID0gMDsJdGVbIDEwIF0gPSBjOwl0ZVsgMTQgXSA9IGQ7CiAgICAJCXRlWyAzIF0gPSAwOwl0ZVsgNyBdID0gMDsJdGVbIDExIF0gPSAtIDE7CXRlWyAxNSBdID0gMDsKCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAltYWtlT3J0aG9ncmFwaGljOiBmdW5jdGlvbiAoIGxlZnQsIHJpZ2h0LCB0b3AsIGJvdHRvbSwgbmVhciwgZmFyICkgewoKICAgIAkJdmFyIHRlID0gdGhpcy5lbGVtZW50czsKICAgIAkJdmFyIHcgPSAxLjAgLyAoIHJpZ2h0IC0gbGVmdCApOwogICAgCQl2YXIgaCA9IDEuMCAvICggdG9wIC0gYm90dG9tICk7CiAgICAJCXZhciBwID0gMS4wIC8gKCBmYXIgLSBuZWFyICk7CgogICAgCQl2YXIgeCA9ICggcmlnaHQgKyBsZWZ0ICkgKiB3OwogICAgCQl2YXIgeSA9ICggdG9wICsgYm90dG9tICkgKiBoOwogICAgCQl2YXIgeiA9ICggZmFyICsgbmVhciApICogcDsKCiAgICAJCXRlWyAwIF0gPSAyICogdzsJdGVbIDQgXSA9IDA7CXRlWyA4IF0gPSAwOwl0ZVsgMTIgXSA9IC0geDsKICAgIAkJdGVbIDEgXSA9IDA7CXRlWyA1IF0gPSAyICogaDsJdGVbIDkgXSA9IDA7CXRlWyAxMyBdID0gLSB5OwogICAgCQl0ZVsgMiBdID0gMDsJdGVbIDYgXSA9IDA7CXRlWyAxMCBdID0gLSAyICogcDsJdGVbIDE0IF0gPSAtIHo7CiAgICAJCXRlWyAzIF0gPSAwOwl0ZVsgNyBdID0gMDsJdGVbIDExIF0gPSAwOwl0ZVsgMTUgXSA9IDE7CgogICAgCQlyZXR1cm4gdGhpczsKCiAgICAJfSwKCiAgICAJZXF1YWxzOiBmdW5jdGlvbiAoIG1hdHJpeCApIHsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CiAgICAJCXZhciBtZSA9IG1hdHJpeC5lbGVtZW50czsKCiAgICAJCWZvciAoIHZhciBpID0gMDsgaSA8IDE2OyBpICsrICkgewoKICAgIAkJCWlmICggdGVbIGkgXSAhPT0gbWVbIGkgXSApIHJldHVybiBmYWxzZTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0cnVlOwoKICAgIAl9LAoKICAgIAlmcm9tQXJyYXk6IGZ1bmN0aW9uICggYXJyYXksIG9mZnNldCApIHsKCiAgICAJCWlmICggb2Zmc2V0ID09PSB1bmRlZmluZWQgKSBvZmZzZXQgPSAwOwoKICAgIAkJZm9yICggdmFyIGkgPSAwOyBpIDwgMTY7IGkgKysgKSB7CgogICAgCQkJdGhpcy5lbGVtZW50c1sgaSBdID0gYXJyYXlbIGkgKyBvZmZzZXQgXTsKCiAgICAJCX0KCiAgICAJCXJldHVybiB0aGlzOwoKICAgIAl9LAoKICAgIAl0b0FycmF5OiBmdW5jdGlvbiAoIGFycmF5LCBvZmZzZXQgKSB7CgogICAgCQlpZiAoIGFycmF5ID09PSB1bmRlZmluZWQgKSBhcnJheSA9IFtdOwogICAgCQlpZiAoIG9mZnNldCA9PT0gdW5kZWZpbmVkICkgb2Zmc2V0ID0gMDsKCiAgICAJCXZhciB0ZSA9IHRoaXMuZWxlbWVudHM7CgogICAgCQlhcnJheVsgb2Zmc2V0IF0gPSB0ZVsgMCBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMSBdID0gdGVbIDEgXTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDIgXSA9IHRlWyAyIF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyAzIF0gPSB0ZVsgMyBdOwoKICAgIAkJYXJyYXlbIG9mZnNldCArIDQgXSA9IHRlWyA0IF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyA1IF0gPSB0ZVsgNSBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgNiBdID0gdGVbIDYgXTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDcgXSA9IHRlWyA3IF07CgogICAgCQlhcnJheVsgb2Zmc2V0ICsgOCBdID0gdGVbIDggXTsKICAgIAkJYXJyYXlbIG9mZnNldCArIDkgXSA9IHRlWyA5IF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyAxMCBdID0gdGVbIDEwIF07CiAgICAJCWFycmF5WyBvZmZzZXQgKyAxMSBdID0gdGVbIDExIF07CgogICAgCQlhcnJheVsgb2Zmc2V0ICsgMTIgXSA9IHRlWyAxMiBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMTMgXSA9IHRlWyAxMyBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMTQgXSA9IHRlWyAxNCBdOwogICAgCQlhcnJheVsgb2Zmc2V0ICsgMTUgXSA9IHRlWyAxNSBdOwoKICAgIAkJcmV0dXJuIGFycmF5OwoKICAgIAl9CgogICAgfSApOwoKICAgIC8qKgogICAgICogQGF1dGhvciBtcmRvb2IgLyBodHRwOi8vbXJkb29iLmNvbS8KICAgICAqIEBhdXRob3IgV2VzdExhbmdsZXkgLyBodHRwOi8vZ2l0aHViLmNvbS9XZXN0TGFuZ2xleQogICAgICogQGF1dGhvciBiaG91c3RvbiAvIGh0dHA6Ly9jbGFyYS5pbwogICAgICovCgogICAgdmFyIF9tYXRyaXggPSBuZXcgTWF0cml4NCgpOwogICAgdmFyIF9xdWF0ZXJuaW9uJDEgPSBuZXcgUXVhdGVybmlvbigpOwoKICAgIGZ1bmN0aW9uIEV1bGVyKCB4LCB5LCB6LCBvcmRlciApIHsKCiAgICAJdGhpcy5feCA9IHggfHwgMDsKICAgIAl0aGlzLl95ID0geSB8fCAwOwogICAgCXRoaXMuX3ogPSB6IHx8IDA7CiAgICAJdGhpcy5fb3JkZXIgPSBvcmRlciB8fCBFdWxlci5EZWZhdWx0T3JkZXI7CgogICAgfQoKICAgIEV1bGVyLlJvdGF0aW9uT3JkZXJzID0gWyAnWFlaJywgJ1laWCcsICdaWFknLCAnWFpZJywgJ1lYWicsICda